aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rwxr-xr-x.gitignore8
-rw-r--r--.travis.yml170
-rw-r--r--CHANGELOG397
-rw-r--r--Zotlabs/Access/AccessList.php128
-rw-r--r--Zotlabs/Access/PermissionLimits.php2
-rw-r--r--Zotlabs/Access/Permissions.php159
-rw-r--r--Zotlabs/Daemon/Cron.php6
-rw-r--r--Zotlabs/Daemon/Cron_daily.php10
-rw-r--r--Zotlabs/Daemon/Deliver.php3
-rw-r--r--Zotlabs/Daemon/Gprobe.php2
-rwxr-xr-xZotlabs/Daemon/Importdoc.php14
-rw-r--r--Zotlabs/Daemon/Importfile.php47
-rw-r--r--Zotlabs/Daemon/Notifier.php248
-rw-r--r--Zotlabs/Daemon/Onepoll.php24
-rw-r--r--Zotlabs/Extend/Hook.php9
-rw-r--r--Zotlabs/Lib/ActivityStreams.php199
-rw-r--r--Zotlabs/Lib/Apps.php196
-rw-r--r--Zotlabs/Lib/Cache.php12
-rw-r--r--Zotlabs/Lib/Config.php2
-rw-r--r--Zotlabs/Lib/DB_Upgrade.php121
-rw-r--r--Zotlabs/Lib/Enotify.php24
-rw-r--r--Zotlabs/Lib/JSalmon.php38
-rw-r--r--Zotlabs/Lib/LDSignatures.php135
-rw-r--r--Zotlabs/Lib/MarkdownSoap.php103
-rw-r--r--Zotlabs/Lib/NativeWiki.php90
-rw-r--r--Zotlabs/Lib/NativeWikiPage.php131
-rw-r--r--Zotlabs/Lib/PConfig.php11
-rw-r--r--Zotlabs/Lib/SConfig.php25
-rw-r--r--Zotlabs/Lib/System.php21
-rw-r--r--Zotlabs/Lib/Techlevels.php12
-rw-r--r--Zotlabs/Lib/ThreadItem.php66
-rw-r--r--Zotlabs/Lib/ThreadStream.php18
-rw-r--r--Zotlabs/Module/Acl.php91
-rw-r--r--Zotlabs/Module/Admin.php25
-rw-r--r--Zotlabs/Module/Admin/Plugins.php82
-rw-r--r--Zotlabs/Module/Admin/Site.php40
-rw-r--r--Zotlabs/Module/Admin/Themes.php89
-rw-r--r--Zotlabs/Module/Appman.php19
-rw-r--r--Zotlabs/Module/Apporder.php45
-rw-r--r--Zotlabs/Module/Apps.php7
-rw-r--r--Zotlabs/Module/Attach.php2
-rw-r--r--Zotlabs/Module/Authorize.php71
-rw-r--r--Zotlabs/Module/Block.php2
-rw-r--r--Zotlabs/Module/Bookmarks.php6
-rw-r--r--Zotlabs/Module/Cal.php3
-rw-r--r--Zotlabs/Module/Card_edit.php138
-rw-r--r--Zotlabs/Module/Cards.php187
-rw-r--r--Zotlabs/Module/Cdav.php1259
-rw-r--r--Zotlabs/Module/Changeaddr.php88
-rw-r--r--Zotlabs/Module/Channel.php70
-rw-r--r--Zotlabs/Module/Chanview.php19
-rw-r--r--Zotlabs/Module/Chat.php13
-rw-r--r--Zotlabs/Module/Cloud.php13
-rw-r--r--Zotlabs/Module/Common.php31
-rw-r--r--Zotlabs/Module/Connections.php27
-rw-r--r--Zotlabs/Module/Connedit.php103
-rw-r--r--Zotlabs/Module/Cover_photo.php64
-rw-r--r--Zotlabs/Module/Dav.php74
-rw-r--r--Zotlabs/Module/Directory.php5
-rw-r--r--Zotlabs/Module/Display.php312
-rw-r--r--Zotlabs/Module/Editblock.php7
-rw-r--r--Zotlabs/Module/Editlayout.php1
-rw-r--r--Zotlabs/Module/Editpost.php18
-rw-r--r--Zotlabs/Module/Editwebpage.php23
-rw-r--r--Zotlabs/Module/Embedphotos.php1
-rw-r--r--Zotlabs/Module/Events.php2
-rw-r--r--Zotlabs/Module/Feed.php49
-rw-r--r--Zotlabs/Module/File_upload.php29
-rw-r--r--Zotlabs/Module/Filer.php4
-rw-r--r--Zotlabs/Module/Filestorage.php28
-rw-r--r--Zotlabs/Module/Getfile.php37
-rw-r--r--Zotlabs/Module/Group.php4
-rw-r--r--Zotlabs/Module/Hcard.php27
-rw-r--r--Zotlabs/Module/Help.php79
-rw-r--r--Zotlabs/Module/Impel.php14
-rw-r--r--Zotlabs/Module/Import.php287
-rw-r--r--Zotlabs/Module/Import_items.php94
-rw-r--r--Zotlabs/Module/Invite.php6
-rw-r--r--Zotlabs/Module/Item.php200
-rw-r--r--Zotlabs/Module/Lang.php1
-rw-r--r--Zotlabs/Module/Layouts.php1
-rw-r--r--Zotlabs/Module/Like.php11
-rw-r--r--Zotlabs/Module/Linkinfo.php2
-rw-r--r--Zotlabs/Module/Lockview.php22
-rw-r--r--Zotlabs/Module/Logout.php12
-rw-r--r--Zotlabs/Module/Magic.php31
-rw-r--r--Zotlabs/Module/Mail.php118
-rw-r--r--Zotlabs/Module/Manage.php162
-rw-r--r--Zotlabs/Module/Moderate.php90
-rw-r--r--Zotlabs/Module/Mood.php8
-rw-r--r--Zotlabs/Module/Network.php74
-rw-r--r--Zotlabs/Module/New_channel.php4
-rw-r--r--Zotlabs/Module/Notifications.php37
-rw-r--r--Zotlabs/Module/Notify.php16
-rw-r--r--Zotlabs/Module/Oembed.php2
-rw-r--r--Zotlabs/Module/Oep.php208
-rw-r--r--Zotlabs/Module/Ofeed.php48
-rw-r--r--Zotlabs/Module/Owa.php53
-rw-r--r--Zotlabs/Module/Page.php60
-rw-r--r--Zotlabs/Module/Pdledit.php26
-rw-r--r--Zotlabs/Module/Photo.php9
-rw-r--r--Zotlabs/Module/Photos.php258
-rw-r--r--Zotlabs/Module/Ping.php205
-rw-r--r--Zotlabs/Module/Poke.php34
-rw-r--r--Zotlabs/Module/Post.php8
-rw-r--r--Zotlabs/Module/Probe.php4
-rw-r--r--Zotlabs/Module/Profile.php33
-rw-r--r--Zotlabs/Module/Profile_photo.php35
-rw-r--r--Zotlabs/Module/Profiles.php43
-rw-r--r--Zotlabs/Module/Pubsites.php7
-rw-r--r--Zotlabs/Module/Pubstream.php100
-rw-r--r--Zotlabs/Module/Randprof.php2
-rw-r--r--Zotlabs/Module/React.php4
-rw-r--r--Zotlabs/Module/Register.php28
-rw-r--r--Zotlabs/Module/Rmagic.php8
-rw-r--r--Zotlabs/Module/Rpost.php84
-rw-r--r--Zotlabs/Module/Search.php14
-rw-r--r--Zotlabs/Module/Settings.php2
-rw-r--r--Zotlabs/Module/Settings/Account.php2
-rw-r--r--Zotlabs/Module/Settings/Channel.php17
-rw-r--r--Zotlabs/Module/Settings/Display.php87
-rw-r--r--Zotlabs/Module/Settings/Featured.php18
-rw-r--r--Zotlabs/Module/Settings/Permcats.php6
-rw-r--r--Zotlabs/Module/Setup.php53
-rw-r--r--Zotlabs/Module/Share.php2
-rw-r--r--Zotlabs/Module/Sharedwithme.php8
-rw-r--r--Zotlabs/Module/Siteinfo.php7
-rw-r--r--Zotlabs/Module/Siteinfo_json.php14
-rw-r--r--Zotlabs/Module/Suggest.php6
-rw-r--r--Zotlabs/Module/Tasks.php3
-rw-r--r--Zotlabs/Module/Thing.php4
-rw-r--r--Zotlabs/Module/Token.php40
-rw-r--r--Zotlabs/Module/Update_cards.php39
-rw-r--r--Zotlabs/Module/Update_display.php18
-rw-r--r--Zotlabs/Module/Viewconnections.php2
-rw-r--r--Zotlabs/Module/Viewsrc.php17
-rw-r--r--Zotlabs/Module/Wall_attach.php71
-rw-r--r--Zotlabs/Module/Webpages.php25
-rw-r--r--Zotlabs/Module/Wfinger.php189
-rw-r--r--Zotlabs/Module/Wiki.php232
-rw-r--r--Zotlabs/Module/Xrd.php22
-rw-r--r--Zotlabs/Module/Zfinger.php30
-rw-r--r--Zotlabs/Module/Zotfeed.php3
-rw-r--r--Zotlabs/Render/Comanche.php75
-rw-r--r--Zotlabs/Render/Theme.php56
-rw-r--r--Zotlabs/Storage/BasicAuth.php11
-rw-r--r--Zotlabs/Storage/Browser.php28
-rw-r--r--Zotlabs/Storage/Directory.php64
-rw-r--r--Zotlabs/Storage/File.php18
-rw-r--r--Zotlabs/Web/CheckJS.php6
-rw-r--r--Zotlabs/Web/HTTPHeaders.php60
-rw-r--r--Zotlabs/Web/HTTPSig.php313
-rw-r--r--Zotlabs/Web/Router.php21
-rw-r--r--Zotlabs/Web/WebServer.php63
-rw-r--r--Zotlabs/Widget/Activity.php61
-rw-r--r--Zotlabs/Widget/Admin.php68
-rw-r--r--Zotlabs/Widget/Affinity.php60
-rw-r--r--Zotlabs/Widget/Album.php106
-rw-r--r--Zotlabs/Widget/Appcategories.php49
-rw-r--r--Zotlabs/Widget/Appcloud.php13
-rw-r--r--Zotlabs/Widget/Archive.php55
-rw-r--r--Zotlabs/Widget/Bookmarkedchats.php28
-rw-r--r--Zotlabs/Widget/Catcloud_wall.php19
-rw-r--r--Zotlabs/Widget/Categories.php32
-rw-r--r--Zotlabs/Widget/Cdav.php176
-rw-r--r--Zotlabs/Widget/Chatroom_list.php24
-rw-r--r--Zotlabs/Widget/Chatroom_members.php15
-rw-r--r--Zotlabs/Widget/Clock.php63
-rw-r--r--Zotlabs/Widget/Collections.php51
-rw-r--r--Zotlabs/Widget/Common_friends.php19
-rw-r--r--Zotlabs/Widget/Conversations.php74
-rw-r--r--Zotlabs/Widget/Cover_photo.php59
-rw-r--r--Zotlabs/Widget/Design_tools.php21
-rw-r--r--Zotlabs/Widget/Dirsort.php11
-rw-r--r--Zotlabs/Widget/Dirtags.php13
-rw-r--r--Zotlabs/Widget/Eventstools.php19
-rw-r--r--Zotlabs/Widget/Filer.php36
-rw-r--r--Zotlabs/Widget/Findpeople.php12
-rw-r--r--Zotlabs/Widget/Follow.php37
-rw-r--r--Zotlabs/Widget/Forums.php97
-rw-r--r--Zotlabs/Widget/Fullprofile.php16
-rw-r--r--Zotlabs/Widget/Helpindex.php55
-rw-r--r--Zotlabs/Widget/Item.php54
-rw-r--r--Zotlabs/Widget/Mailmenu.php36
-rw-r--r--Zotlabs/Widget/Menu_preview.php16
-rw-r--r--Zotlabs/Widget/Notes.php23
-rw-r--r--Zotlabs/Widget/Notifications.php150
-rw-r--r--Zotlabs/Widget/Photo.php55
-rw-r--r--Zotlabs/Widget/Photo_albums.php25
-rw-r--r--Zotlabs/Widget/Photo_rand.php66
-rw-r--r--Zotlabs/Widget/Portfolio.php108
-rw-r--r--Zotlabs/Widget/Profile.php13
-rw-r--r--Zotlabs/Widget/Pubsites.php16
-rw-r--r--Zotlabs/Widget/Random_block.php46
-rw-r--r--Zotlabs/Widget/Rating.php67
-rw-r--r--Zotlabs/Widget/Savedsearch.php91
-rw-r--r--Zotlabs/Widget/Settings_menu.php139
-rw-r--r--Zotlabs/Widget/Shortprofile.php18
-rw-r--r--Zotlabs/Widget/Sitesearch.php38
-rw-r--r--Zotlabs/Widget/Suggestedchats.php37
-rw-r--r--Zotlabs/Widget/Suggestions.php58
-rw-r--r--Zotlabs/Widget/Tagcloud.php33
-rw-r--r--Zotlabs/Widget/Tagcloud_wall.php20
-rw-r--r--Zotlabs/Widget/Tasklist.php30
-rw-r--r--Zotlabs/Widget/Vcard.php12
-rw-r--r--Zotlabs/Widget/Website_portation_tools.php22
-rw-r--r--Zotlabs/Widget/Wiki_list.php23
-rw-r--r--Zotlabs/Widget/Wiki_page_history.php27
-rw-r--r--Zotlabs/Widget/Wiki_pages.php66
-rw-r--r--Zotlabs/Widget/Zcard.php11
-rw-r--r--Zotlabs/Zot/Auth.php16
-rw-r--r--Zotlabs/Zot/Finger.php27
-rw-r--r--Zotlabs/Zot/IHandler.php2
-rw-r--r--Zotlabs/Zot/Receiver.php8
-rw-r--r--Zotlabs/Zot/Verify.php16
-rw-r--r--Zotlabs/Zot/ZotHandler.php4
-rw-r--r--app/admin.apd6
-rw-r--r--app/admin.pngbin2852 -> 0 bytes
-rw-r--r--app/caldav.apd6
-rw-r--r--app/carddav.apd6
-rw-r--r--app/cards.apd6
-rw-r--r--app/features.apd6
-rw-r--r--app/features.pngbin8542 -> 0 bytes
-rw-r--r--app/login.apd5
-rw-r--r--app/manage.apd6
-rw-r--r--app/manage.pngbin7355 -> 0 bytes
-rw-r--r--app/photos.apd2
-rw-r--r--app/profile.apd6
-rw-r--r--app/profile.pngbin3550 -> 0 bytes
-rw-r--r--app/pubstream.apd6
-rw-r--r--app/settings.apd6
-rw-r--r--app/settings.pngbin7958 -> 0 bytes
-rw-r--r--app/storage.apd2
-rwxr-xr-xboot.php507
-rw-r--r--composer.json25
-rw-r--r--composer.lock3924
-rw-r--r--doc/Privacy.md77
-rw-r--r--doc/Widgets.md1
-rw-r--r--doc/about.bb24
-rw-r--r--doc/about/about.bb204
-rw-r--r--doc/about/about_hubzilla.bb209
-rw-r--r--doc/about/hubzilla_project.bb185
-rw-r--r--doc/about/project.bb186
-rw-r--r--doc/account_basics.bb38
-rw-r--r--doc/accounts.bb4
-rw-r--r--doc/addons.bb15
-rw-r--r--doc/admin/administrator_guide.md60
-rw-r--r--doc/bugs.bb21
-rw-r--r--doc/context/en/appman/help.html4
-rw-r--r--doc/context/en/apps/edit/help.html4
-rw-r--r--doc/context/en/apps/help.html6
-rw-r--r--doc/context/en/cards/help.html20
-rw-r--r--doc/context/en/channel/help.html4
-rw-r--r--doc/context/en/wiki/help.html10
-rw-r--r--doc/contributor/covenant.html106
-rw-r--r--doc/database.bb4
-rw-r--r--doc/database/db_account.bb1
-rw-r--r--doc/dev-function-overview.md4
-rw-r--r--doc/developer/api_zot.bb27
-rw-r--r--doc/developer/covenant.bb47
-rw-r--r--doc/developer/developer_guide.bb178
-rw-r--r--doc/developer/developer_guide.md422
-rw-r--r--doc/developer/unorganized.md73
-rw-r--r--doc/developer/zot_protocol.bb19
-rw-r--r--doc/feature/saved_search.bb19
-rw-r--r--doc/feature/techlevels.bb15
-rw-r--r--doc/hook/author_is_pmable.bb14
-rw-r--r--doc/hook/can_comment_on_post.bb13
-rw-r--r--doc/hook/channel_links.bb12
-rw-r--r--doc/hook/connection_remove.bb9
-rw-r--r--doc/hook/legal_webbie.bb10
-rw-r--r--doc/hook/legal_webbie_text.bb7
-rw-r--r--doc/hook/probe_well_known.bb3
-rw-r--r--doc/hook/update_unseen.bb9
-rw-r--r--doc/hooklist.bb26
-rw-r--r--doc/main.bb13
-rw-r--r--doc/member/bbcode.html7
-rw-r--r--doc/member/member_guide.bb85
-rw-r--r--doc/members.bb25
-rw-r--r--doc/profiles.bb37
-rw-r--r--doc/project/governance.bb29
-rw-r--r--doc/project/toc.html5
-rw-r--r--doc/project/versions.bb30
-rw-r--r--doc/server_roles.bb27
-rw-r--r--doc/service_classes.bb38
-rw-r--r--doc/theme_management.bb10
-rw-r--r--doc/to_do_code.bb42
-rw-r--r--doc/to_do_doco.md31
-rw-r--r--doc/toc.html123
-rw-r--r--doc/tutorials/personal_channel.html10
-rw-r--r--images/emoji/0023-20e3.pngbin604 -> 0 bytes
-rw-r--r--images/emoji/0023.pngbin634 -> 0 bytes
-rw-r--r--images/emoji/002a-20e3.pngbin627 -> 0 bytes
-rw-r--r--images/emoji/002a.pngbin645 -> 0 bytes
-rw-r--r--images/emoji/0030-20e3.pngbin560 -> 0 bytes
-rw-r--r--images/emoji/0030.pngbin573 -> 0 bytes
-rw-r--r--images/emoji/0031-20e3.pngbin442 -> 0 bytes
-rw-r--r--images/emoji/0031.pngbin505 -> 0 bytes
-rw-r--r--images/emoji/0032-20e3.pngbin567 -> 0 bytes
-rw-r--r--images/emoji/0032.pngbin604 -> 0 bytes
-rw-r--r--images/emoji/0033-20e3.pngbin602 -> 0 bytes
-rw-r--r--images/emoji/0033.pngbin644 -> 0 bytes
-rw-r--r--images/emoji/0034-20e3.pngbin497 -> 0 bytes
-rw-r--r--images/emoji/0034.pngbin542 -> 0 bytes
-rw-r--r--images/emoji/0035-20e3.pngbin577 -> 0 bytes
-rw-r--r--images/emoji/0035.pngbin615 -> 0 bytes
-rw-r--r--images/emoji/0036-20e3.pngbin612 -> 0 bytes
-rw-r--r--images/emoji/0036.pngbin649 -> 0 bytes
-rw-r--r--images/emoji/0037-20e3.pngbin522 -> 0 bytes
-rw-r--r--images/emoji/0037.pngbin559 -> 0 bytes
-rw-r--r--images/emoji/0038-20e3.pngbin608 -> 0 bytes
-rw-r--r--images/emoji/0038.pngbin646 -> 0 bytes
-rw-r--r--images/emoji/0039-20e3.pngbin607 -> 0 bytes
-rw-r--r--images/emoji/0039.pngbin654 -> 0 bytes
-rw-r--r--images/emoji/00a9.pngbin530 -> 0 bytes
-rw-r--r--images/emoji/00ae.pngbin547 -> 0 bytes
-rw-r--r--images/emoji/1f004.pngbin951 -> 0 bytes
-rw-r--r--images/emoji/1f0cf.pngbin1091 -> 0 bytes
-rw-r--r--images/emoji/1f170.pngbin469 -> 0 bytes
-rw-r--r--images/emoji/1f171.pngbin391 -> 0 bytes
-rw-r--r--images/emoji/1f17e.pngbin425 -> 0 bytes
-rw-r--r--images/emoji/1f17f.pngbin385 -> 0 bytes
-rw-r--r--images/emoji/1f18e.pngbin505 -> 0 bytes
-rw-r--r--images/emoji/1f191.pngbin393 -> 0 bytes
-rw-r--r--images/emoji/1f192.pngbin396 -> 0 bytes
-rw-r--r--images/emoji/1f193.pngbin370 -> 0 bytes
-rw-r--r--images/emoji/1f194.pngbin348 -> 0 bytes
-rw-r--r--images/emoji/1f195.pngbin486 -> 0 bytes
-rw-r--r--images/emoji/1f196.pngbin445 -> 0 bytes
-rw-r--r--images/emoji/1f197.pngbin511 -> 0 bytes
-rw-r--r--images/emoji/1f198.pngbin604 -> 0 bytes
-rw-r--r--images/emoji/1f199.pngbin405 -> 0 bytes
-rw-r--r--images/emoji/1f19a.pngbin604 -> 0 bytes
-rw-r--r--images/emoji/1f1e6-1f1e8.pngbin1935 -> 0 bytes
-rw-r--r--images/emoji/1f1e6-1f1e9.pngbin1285 -> 0 bytes
-rw-r--r--images/emoji/1f1e6-1f1ea.pngbin544 -> 0 bytes
-rw-r--r--images/emoji/1f1e6-1f1eb.pngbin942 -> 0 bytes
-rw-r--r--images/emoji/1f1e6-1f1ec.pngbin913 -> 0 bytes
-rw-r--r--images/emoji/1f1e6-1f1ee.pngbin1056 -> 0 bytes
-rw-r--r--images/emoji/1f1e6-1f1f1.pngbin905 -> 0 bytes
-rw-r--r--images/emoji/1f1e6-1f1f2.pngbin514 -> 0 bytes
-rw-r--r--images/emoji/1f1e6-1f1f4.pngbin997 -> 0 bytes
-rw-r--r--images/emoji/1f1e6-1f1f6.pngbin657 -> 0 bytes
-rw-r--r--images/emoji/1f1e6-1f1f7.pngbin975 -> 0 bytes
-rw-r--r--images/emoji/1f1e6-1f1f8.pngbin1489 -> 0 bytes
-rw-r--r--images/emoji/1f1e6-1f1f9.pngbin430 -> 0 bytes
-rw-r--r--images/emoji/1f1e6-1f1fa.pngbin962 -> 0 bytes
-rw-r--r--images/emoji/1f1e6-1f1fc.pngbin709 -> 0 bytes
-rw-r--r--images/emoji/1f1e6-1f1fd.pngbin496 -> 0 bytes
-rw-r--r--images/emoji/1f1e6-1f1ff.pngbin709 -> 0 bytes
-rw-r--r--images/emoji/1f1e7-1f1e6.pngbin848 -> 0 bytes
-rw-r--r--images/emoji/1f1e7-1f1e7.pngbin789 -> 0 bytes
-rw-r--r--images/emoji/1f1e7-1f1e9.pngbin490 -> 0 bytes
-rw-r--r--images/emoji/1f1e7-1f1ea.pngbin444 -> 0 bytes
-rw-r--r--images/emoji/1f1e7-1f1eb.pngbin717 -> 0 bytes
-rw-r--r--images/emoji/1f1e7-1f1ec.pngbin513 -> 0 bytes
-rw-r--r--images/emoji/1f1e7-1f1ed.pngbin593 -> 0 bytes
-rw-r--r--images/emoji/1f1e7-1f1ee.pngbin795 -> 0 bytes
-rw-r--r--images/emoji/1f1e7-1f1ef.pngbin554 -> 0 bytes
-rw-r--r--images/emoji/1f1e7-1f1f1.pngbin1692 -> 0 bytes
-rw-r--r--images/emoji/1f1e7-1f1f2.pngbin1374 -> 0 bytes
-rw-r--r--images/emoji/1f1e7-1f1f3.pngbin1358 -> 0 bytes
-rw-r--r--images/emoji/1f1e7-1f1f4.pngbin1132 -> 0 bytes
-rw-r--r--images/emoji/1f1e7-1f1f6.pngbin1144 -> 0 bytes
-rw-r--r--images/emoji/1f1e7-1f1f7.pngbin819 -> 0 bytes
-rw-r--r--images/emoji/1f1e7-1f1f8.pngbin448 -> 0 bytes
-rw-r--r--images/emoji/1f1e7-1f1f9.pngbin1214 -> 0 bytes
-rw-r--r--images/emoji/1f1e7-1f1fb.pngbin495 -> 0 bytes
-rw-r--r--images/emoji/1f1e7-1f1fc.pngbin391 -> 0 bytes
-rw-r--r--images/emoji/1f1e7-1f1fe.pngbin1120 -> 0 bytes
-rw-r--r--images/emoji/1f1e7-1f1ff.pngbin1597 -> 0 bytes
-rw-r--r--images/emoji/1f1e7.pngbin572 -> 0 bytes
-rw-r--r--images/emoji/1f1e8-1f1e6.pngbin755 -> 0 bytes
-rw-r--r--images/emoji/1f1e8-1f1e8.pngbin851 -> 0 bytes
-rw-r--r--images/emoji/1f1e8-1f1e9.pngbin707 -> 0 bytes
-rw-r--r--images/emoji/1f1e8-1f1eb.pngbin673 -> 0 bytes
-rw-r--r--images/emoji/1f1e8-1f1ec.pngbin586 -> 0 bytes
-rw-r--r--images/emoji/1f1e8-1f1ed.pngbin390 -> 0 bytes
-rw-r--r--images/emoji/1f1e8-1f1ee.pngbin440 -> 0 bytes
-rw-r--r--images/emoji/1f1e8-1f1f0.pngbin1083 -> 0 bytes
-rw-r--r--images/emoji/1f1e8-1f1f1.pngbin748 -> 0 bytes
-rw-r--r--images/emoji/1f1e8-1f1f2.pngbin627 -> 0 bytes
-rw-r--r--images/emoji/1f1e8-1f1f3.pngbin676 -> 0 bytes
-rw-r--r--images/emoji/1f1e8-1f1f4.pngbin524 -> 0 bytes
-rw-r--r--images/emoji/1f1e8-1f1f5.pngbin443 -> 0 bytes
-rw-r--r--images/emoji/1f1e8-1f1f7.pngbin419 -> 0 bytes
-rw-r--r--images/emoji/1f1e8-1f1fa.pngbin586 -> 0 bytes
-rw-r--r--images/emoji/1f1e8-1f1fb.pngbin642 -> 0 bytes
-rw-r--r--images/emoji/1f1e8-1f1fc.pngbin665 -> 0 bytes
-rw-r--r--images/emoji/1f1e8-1f1fd.pngbin1142 -> 0 bytes
-rw-r--r--images/emoji/1f1e8-1f1fe.pngbin830 -> 0 bytes
-rw-r--r--images/emoji/1f1e8-1f1ff.pngbin600 -> 0 bytes
-rw-r--r--images/emoji/1f1e8.pngbin612 -> 0 bytes
-rw-r--r--images/emoji/1f1e9-1f1ea.pngbin502 -> 0 bytes
-rw-r--r--images/emoji/1f1e9-1f1ec.pngbin1918 -> 0 bytes
-rw-r--r--images/emoji/1f1e9-1f1ef.pngbin753 -> 0 bytes
-rw-r--r--images/emoji/1f1e9-1f1f0.pngbin450 -> 0 bytes
-rw-r--r--images/emoji/1f1e9-1f1f2.pngbin1077 -> 0 bytes
-rw-r--r--images/emoji/1f1e9-1f1f4.pngbin1135 -> 0 bytes
-rw-r--r--images/emoji/1f1e9-1f1ff.pngbin734 -> 0 bytes
-rw-r--r--images/emoji/1f1e9.pngbin561 -> 0 bytes
-rw-r--r--images/emoji/1f1ea-1f1e6.pngbin1338 -> 0 bytes
-rw-r--r--images/emoji/1f1ea-1f1e8.pngbin1431 -> 0 bytes
-rw-r--r--images/emoji/1f1ea-1f1ea.pngbin512 -> 0 bytes
-rw-r--r--images/emoji/1f1ea-1f1ec.pngbin818 -> 0 bytes
-rw-r--r--images/emoji/1f1ea-1f1ed.pngbin742 -> 0 bytes
-rw-r--r--images/emoji/1f1ea-1f1f7.pngbin1218 -> 0 bytes
-rw-r--r--images/emoji/1f1ea-1f1f8.pngbin1338 -> 0 bytes
-rw-r--r--images/emoji/1f1ea-1f1f9.pngbin947 -> 0 bytes
-rw-r--r--images/emoji/1f1ea-1f1fa.pngbin760 -> 0 bytes
-rw-r--r--images/emoji/1f1ea.pngbin443 -> 0 bytes
-rw-r--r--images/emoji/1f1eb-1f1ee.pngbin487 -> 0 bytes
-rw-r--r--images/emoji/1f1eb-1f1ef.pngbin1381 -> 0 bytes
-rw-r--r--images/emoji/1f1eb-1f1f0.pngbin1558 -> 0 bytes
-rw-r--r--images/emoji/1f1eb-1f1f2.pngbin554 -> 0 bytes
-rw-r--r--images/emoji/1f1eb-1f1f4.pngbin495 -> 0 bytes
-rw-r--r--images/emoji/1f1eb-1f1f7.pngbin443 -> 0 bytes
-rw-r--r--images/emoji/1f1eb.pngbin462 -> 0 bytes
-rw-r--r--images/emoji/1f1ec-1f1e6.pngbin512 -> 0 bytes
-rw-r--r--images/emoji/1f1ec-1f1e7.pngbin919 -> 0 bytes
-rw-r--r--images/emoji/1f1ec-1f1e9.pngbin1017 -> 0 bytes
-rw-r--r--images/emoji/1f1ec-1f1ea.pngbin583 -> 0 bytes
-rw-r--r--images/emoji/1f1ec-1f1eb.pngbin865 -> 0 bytes
-rw-r--r--images/emoji/1f1ec-1f1ec.pngbin521 -> 0 bytes
-rw-r--r--images/emoji/1f1ec-1f1ed.pngbin723 -> 0 bytes
-rw-r--r--images/emoji/1f1ec-1f1ee.pngbin1053 -> 0 bytes
-rw-r--r--images/emoji/1f1ec-1f1f1.pngbin700 -> 0 bytes
-rw-r--r--images/emoji/1f1ec-1f1f2.pngbin501 -> 0 bytes
-rw-r--r--images/emoji/1f1ec-1f1f3.pngbin434 -> 0 bytes
-rw-r--r--images/emoji/1f1ec-1f1f5.pngbin1587 -> 0 bytes
-rw-r--r--images/emoji/1f1ec-1f1f6.pngbin1132 -> 0 bytes
-rw-r--r--images/emoji/1f1ec-1f1f7.pngbin549 -> 0 bytes
-rw-r--r--images/emoji/1f1ec-1f1f8.pngbin2115 -> 0 bytes
-rw-r--r--images/emoji/1f1ec-1f1f9.pngbin1087 -> 0 bytes
-rw-r--r--images/emoji/1f1ec-1f1fa.pngbin1045 -> 0 bytes
-rw-r--r--images/emoji/1f1ec-1f1fc.pngbin705 -> 0 bytes
-rw-r--r--images/emoji/1f1ec-1f1fe.pngbin690 -> 0 bytes
-rw-r--r--images/emoji/1f1ec.pngbin644 -> 0 bytes
-rw-r--r--images/emoji/1f1ed-1f1f0.pngbin759 -> 0 bytes
-rw-r--r--images/emoji/1f1ed-1f1f2.pngbin1036 -> 0 bytes
-rw-r--r--images/emoji/1f1ed-1f1f3.pngbin513 -> 0 bytes
-rw-r--r--images/emoji/1f1ed-1f1f7.pngbin1411 -> 0 bytes
-rw-r--r--images/emoji/1f1ed-1f1f9.pngbin1205 -> 0 bytes
-rw-r--r--images/emoji/1f1ed-1f1fa.pngbin513 -> 0 bytes
-rw-r--r--images/emoji/1f1ed.pngbin434 -> 0 bytes
-rw-r--r--images/emoji/1f1ee-1f1e8.pngbin1330 -> 0 bytes
-rw-r--r--images/emoji/1f1ee-1f1e9.pngbin498 -> 0 bytes
-rw-r--r--images/emoji/1f1ee-1f1ea.pngbin478 -> 0 bytes
-rw-r--r--images/emoji/1f1ee-1f1f1.pngbin658 -> 0 bytes
-rw-r--r--images/emoji/1f1ee-1f1f2.pngbin976 -> 0 bytes
-rw-r--r--images/emoji/1f1ee-1f1f3.pngbin773 -> 0 bytes
-rw-r--r--images/emoji/1f1ee-1f1f4.pngbin1918 -> 0 bytes
-rw-r--r--images/emoji/1f1ee-1f1f6.pngbin811 -> 0 bytes
-rw-r--r--images/emoji/1f1ee-1f1f7.pngbin1036 -> 0 bytes
-rw-r--r--images/emoji/1f1ee-1f1f8.pngbin491 -> 0 bytes
-rw-r--r--images/emoji/1f1ee-1f1f9.pngbin472 -> 0 bytes
-rw-r--r--images/emoji/1f1ee.pngbin395 -> 0 bytes
-rw-r--r--images/emoji/1f1ef-1f1ea.pngbin956 -> 0 bytes
-rw-r--r--images/emoji/1f1ef-1f1f2.pngbin837 -> 0 bytes
-rw-r--r--images/emoji/1f1ef-1f1f4.pngbin740 -> 0 bytes
-rw-r--r--images/emoji/1f1ef-1f1f5.pngbin455 -> 0 bytes
-rw-r--r--images/emoji/1f1ef.pngbin527 -> 0 bytes
-rw-r--r--images/emoji/1f1f0-1f1ea.pngbin1160 -> 0 bytes
-rw-r--r--images/emoji/1f1f0-1f1ec.pngbin1081 -> 0 bytes
-rw-r--r--images/emoji/1f1f0-1f1ed.pngbin872 -> 0 bytes
-rw-r--r--images/emoji/1f1f0-1f1ee.pngbin1375 -> 0 bytes
-rw-r--r--images/emoji/1f1f0-1f1f2.pngbin783 -> 0 bytes
-rw-r--r--images/emoji/1f1f0-1f1f3.pngbin1316 -> 0 bytes
-rw-r--r--images/emoji/1f1f0-1f1f5.pngbin696 -> 0 bytes
-rw-r--r--images/emoji/1f1f0-1f1f7.pngbin968 -> 0 bytes
-rw-r--r--images/emoji/1f1f0-1f1fc.pngbin560 -> 0 bytes
-rw-r--r--images/emoji/1f1f0-1f1fe.pngbin1671 -> 0 bytes
-rw-r--r--images/emoji/1f1f0-1f1ff.pngbin1136 -> 0 bytes
-rw-r--r--images/emoji/1f1f0.pngbin582 -> 0 bytes
-rw-r--r--images/emoji/1f1f1-1f1e6.pngbin479 -> 0 bytes
-rw-r--r--images/emoji/1f1f1-1f1e7.pngbin740 -> 0 bytes
-rw-r--r--images/emoji/1f1f1-1f1e8.pngbin561 -> 0 bytes
-rw-r--r--images/emoji/1f1f1-1f1ee.pngbin946 -> 0 bytes
-rw-r--r--images/emoji/1f1f1-1f1f0.pngbin974 -> 0 bytes
-rw-r--r--images/emoji/1f1f1-1f1f7.pngbin772 -> 0 bytes
-rw-r--r--images/emoji/1f1f1-1f1f8.pngbin775 -> 0 bytes
-rw-r--r--images/emoji/1f1f1-1f1f9.pngbin510 -> 0 bytes
-rw-r--r--images/emoji/1f1f1-1f1fa.pngbin512 -> 0 bytes
-rw-r--r--images/emoji/1f1f1-1f1fb.pngbin388 -> 0 bytes
-rw-r--r--images/emoji/1f1f1-1f1fe.pngbin685 -> 0 bytes
-rw-r--r--images/emoji/1f1f1.pngbin436 -> 0 bytes
-rw-r--r--images/emoji/1f1f2-1f1e6.pngbin626 -> 0 bytes
-rw-r--r--images/emoji/1f1f2-1f1e8.pngbin528 -> 0 bytes
-rw-r--r--images/emoji/1f1f2-1f1e9.pngbin1170 -> 0 bytes
-rw-r--r--images/emoji/1f1f2-1f1ea.pngbin1074 -> 0 bytes
-rw-r--r--images/emoji/1f1f2-1f1eb.pngbin443 -> 0 bytes
-rw-r--r--images/emoji/1f1f2-1f1ec.pngbin556 -> 0 bytes
-rw-r--r--images/emoji/1f1f2-1f1ed.pngbin1138 -> 0 bytes
-rw-r--r--images/emoji/1f1f2-1f1f0.pngbin1023 -> 0 bytes
-rw-r--r--images/emoji/1f1f2-1f1f1.pngbin440 -> 0 bytes
-rw-r--r--images/emoji/1f1f2-1f1f2.pngbin937 -> 0 bytes
-rw-r--r--images/emoji/1f1f2-1f1f3.pngbin698 -> 0 bytes
-rw-r--r--images/emoji/1f1f2-1f1f4.pngbin792 -> 0 bytes
-rw-r--r--images/emoji/1f1f2-1f1f5.pngbin1797 -> 0 bytes
-rw-r--r--images/emoji/1f1f2-1f1f6.pngbin780 -> 0 bytes
-rw-r--r--images/emoji/1f1f2-1f1f7.pngbin657 -> 0 bytes
-rw-r--r--images/emoji/1f1f2-1f1f8.pngbin1477 -> 0 bytes
-rw-r--r--images/emoji/1f1f2-1f1f9.pngbin799 -> 0 bytes
-rw-r--r--images/emoji/1f1f2-1f1fa.pngbin544 -> 0 bytes
-rw-r--r--images/emoji/1f1f2-1f1fb.pngbin598 -> 0 bytes
-rw-r--r--images/emoji/1f1f2-1f1fc.pngbin825 -> 0 bytes
-rw-r--r--images/emoji/1f1f2-1f1fd.pngbin951 -> 0 bytes
-rw-r--r--images/emoji/1f1f2-1f1fe.pngbin775 -> 0 bytes
-rw-r--r--images/emoji/1f1f2-1f1ff.pngbin1159 -> 0 bytes
-rw-r--r--images/emoji/1f1f2.pngbin666 -> 0 bytes
-rw-r--r--images/emoji/1f1f3-1f1e6.pngbin1249 -> 0 bytes
-rw-r--r--images/emoji/1f1f3-1f1e8.pngbin1151 -> 0 bytes
-rw-r--r--images/emoji/1f1f3-1f1ea.pngbin593 -> 0 bytes
-rw-r--r--images/emoji/1f1f3-1f1eb.pngbin877 -> 0 bytes
-rw-r--r--images/emoji/1f1f3-1f1ec.pngbin438 -> 0 bytes
-rw-r--r--images/emoji/1f1f3-1f1ee.pngbin823 -> 0 bytes
-rw-r--r--images/emoji/1f1f3-1f1f1.pngbin499 -> 0 bytes
-rw-r--r--images/emoji/1f1f3-1f1f4.pngbin484 -> 0 bytes
-rw-r--r--images/emoji/1f1f3-1f1f5.pngbin802 -> 0 bytes
-rw-r--r--images/emoji/1f1f3-1f1f7.pngbin529 -> 0 bytes
-rw-r--r--images/emoji/1f1f3-1f1fa.pngbin1128 -> 0 bytes
-rw-r--r--images/emoji/1f1f3-1f1ff.pngbin1099 -> 0 bytes
-rw-r--r--images/emoji/1f1f3.pngbin579 -> 0 bytes
-rw-r--r--images/emoji/1f1f4-1f1f2.pngbin754 -> 0 bytes
-rw-r--r--images/emoji/1f1f4.pngbin607 -> 0 bytes
-rw-r--r--images/emoji/1f1f5-1f1e6.pngbin830 -> 0 bytes
-rw-r--r--images/emoji/1f1f5-1f1ea.pngbin439 -> 0 bytes
-rw-r--r--images/emoji/1f1f5-1f1eb.pngbin1091 -> 0 bytes
-rw-r--r--images/emoji/1f1f5-1f1ec.pngbin1076 -> 0 bytes
-rw-r--r--images/emoji/1f1f5-1f1ed.pngbin867 -> 0 bytes
-rw-r--r--images/emoji/1f1f5-1f1f0.pngbin753 -> 0 bytes
-rw-r--r--images/emoji/1f1f5-1f1f1.pngbin522 -> 0 bytes
-rw-r--r--images/emoji/1f1f5-1f1f2.pngbin2314 -> 0 bytes
-rw-r--r--images/emoji/1f1f5-1f1f3.pngbin1896 -> 0 bytes
-rw-r--r--images/emoji/1f1f5-1f1f7.pngbin605 -> 0 bytes
-rw-r--r--images/emoji/1f1f5-1f1f8.pngbin574 -> 0 bytes
-rw-r--r--images/emoji/1f1f5-1f1f9.pngbin1055 -> 0 bytes
-rw-r--r--images/emoji/1f1f5-1f1fc.pngbin475 -> 0 bytes
-rw-r--r--images/emoji/1f1f5-1f1fe.pngbin1085 -> 0 bytes
-rw-r--r--images/emoji/1f1f5.pngbin541 -> 0 bytes
-rw-r--r--images/emoji/1f1f6-1f1e6.pngbin657 -> 0 bytes
-rw-r--r--images/emoji/1f1f6.pngbin659 -> 0 bytes
-rw-r--r--images/emoji/1f1f7-1f1ea.pngbin837 -> 0 bytes
-rw-r--r--images/emoji/1f1f7-1f1f4.pngbin441 -> 0 bytes
-rw-r--r--images/emoji/1f1f7-1f1f8.pngbin1237 -> 0 bytes
-rw-r--r--images/emoji/1f1f7-1f1fa.pngbin496 -> 0 bytes
-rw-r--r--images/emoji/1f1f7-1f1fc.pngbin940 -> 0 bytes
-rw-r--r--images/emoji/1f1f7.pngbin580 -> 0 bytes
-rw-r--r--images/emoji/1f1f8-1f1e6.pngbin781 -> 0 bytes
-rw-r--r--images/emoji/1f1f8-1f1e7.pngbin1102 -> 0 bytes
-rw-r--r--images/emoji/1f1f8-1f1e8.pngbin1073 -> 0 bytes
-rw-r--r--images/emoji/1f1f8-1f1e9.pngbin578 -> 0 bytes
-rw-r--r--images/emoji/1f1f8-1f1ea.pngbin455 -> 0 bytes
-rw-r--r--images/emoji/1f1f8-1f1ec.pngbin730 -> 0 bytes
-rw-r--r--images/emoji/1f1f8-1f1ed.pngbin1369 -> 0 bytes
-rw-r--r--images/emoji/1f1f8-1f1ee.pngbin1030 -> 0 bytes
-rw-r--r--images/emoji/1f1f8-1f1ef.pngbin495 -> 0 bytes
-rw-r--r--images/emoji/1f1f8-1f1f0.pngbin780 -> 0 bytes
-rw-r--r--images/emoji/1f1f8-1f1f1.pngbin510 -> 0 bytes
-rw-r--r--images/emoji/1f1f8-1f1f2.pngbin2001 -> 0 bytes
-rw-r--r--images/emoji/1f1f8-1f1f3.pngbin621 -> 0 bytes
-rw-r--r--images/emoji/1f1f8-1f1f4.pngbin609 -> 0 bytes
-rw-r--r--images/emoji/1f1f8-1f1f7.pngbin650 -> 0 bytes
-rw-r--r--images/emoji/1f1f8-1f1f8.pngbin722 -> 0 bytes
-rw-r--r--images/emoji/1f1f8-1f1f9.pngbin562 -> 0 bytes
-rw-r--r--images/emoji/1f1f8-1f1fb.pngbin1125 -> 0 bytes
-rw-r--r--images/emoji/1f1f8-1f1fd.pngbin1195 -> 0 bytes
-rw-r--r--images/emoji/1f1f8-1f1fe.pngbin696 -> 0 bytes
-rw-r--r--images/emoji/1f1f8-1f1ff.pngbin1102 -> 0 bytes
-rw-r--r--images/emoji/1f1f8.pngbin653 -> 0 bytes
-rw-r--r--images/emoji/1f1f9-1f1e6.pngbin1907 -> 0 bytes
-rw-r--r--images/emoji/1f1f9-1f1e8.pngbin1538 -> 0 bytes
-rw-r--r--images/emoji/1f1f9-1f1e9.pngbin443 -> 0 bytes
-rw-r--r--images/emoji/1f1f9-1f1eb.pngbin857 -> 0 bytes
-rw-r--r--images/emoji/1f1f9-1f1ec.pngbin790 -> 0 bytes
-rw-r--r--images/emoji/1f1f9-1f1ed.pngbin421 -> 0 bytes
-rw-r--r--images/emoji/1f1f9-1f1ef.pngbin906 -> 0 bytes
-rw-r--r--images/emoji/1f1f9-1f1f0.pngbin835 -> 0 bytes
-rw-r--r--images/emoji/1f1f9-1f1f1.pngbin849 -> 0 bytes
-rw-r--r--images/emoji/1f1f9-1f1f2.pngbin1178 -> 0 bytes
-rw-r--r--images/emoji/1f1f9-1f1f3.pngbin625 -> 0 bytes
-rw-r--r--images/emoji/1f1f9-1f1f4.pngbin553 -> 0 bytes
-rw-r--r--images/emoji/1f1f9-1f1f7.pngbin576 -> 0 bytes
-rw-r--r--images/emoji/1f1f9-1f1f9.pngbin604 -> 0 bytes
-rw-r--r--images/emoji/1f1f9-1f1fb.pngbin1120 -> 0 bytes
-rw-r--r--images/emoji/1f1f9-1f1fc.pngbin761 -> 0 bytes
-rw-r--r--images/emoji/1f1f9-1f1ff.pngbin1061 -> 0 bytes
-rw-r--r--images/emoji/1f1f9.pngbin453 -> 0 bytes
-rw-r--r--images/emoji/1f1fa-1f1e6.pngbin528 -> 0 bytes
-rw-r--r--images/emoji/1f1fa-1f1ec.pngbin887 -> 0 bytes
-rw-r--r--images/emoji/1f1fa-1f1f2.pngbin776 -> 0 bytes
-rw-r--r--images/emoji/1f1fa-1f1f8.pngbin776 -> 0 bytes
-rw-r--r--images/emoji/1f1fa-1f1fe.pngbin966 -> 0 bytes
-rw-r--r--images/emoji/1f1fa-1f1ff.pngbin750 -> 0 bytes
-rw-r--r--images/emoji/1f1fa.pngbin544 -> 0 bytes
-rw-r--r--images/emoji/1f1fb-1f1e6.pngbin1335 -> 0 bytes
-rw-r--r--images/emoji/1f1fb-1f1e8.pngbin897 -> 0 bytes
-rw-r--r--images/emoji/1f1fb-1f1ea.pngbin748 -> 0 bytes
-rw-r--r--images/emoji/1f1fb-1f1ec.pngbin1789 -> 0 bytes
-rw-r--r--images/emoji/1f1fb-1f1ee.pngbin1380 -> 0 bytes
-rw-r--r--images/emoji/1f1fb-1f1f3.pngbin583 -> 0 bytes
-rw-r--r--images/emoji/1f1fb-1f1fa.pngbin844 -> 0 bytes
-rw-r--r--images/emoji/1f1fb.pngbin632 -> 0 bytes
-rw-r--r--images/emoji/1f1fc-1f1eb.pngbin443 -> 0 bytes
-rw-r--r--images/emoji/1f1fc-1f1f8.pngbin634 -> 0 bytes
-rw-r--r--images/emoji/1f1fc.pngbin737 -> 0 bytes
-rw-r--r--images/emoji/1f1fd-1f1f0.pngbin722 -> 0 bytes
-rw-r--r--images/emoji/1f1fd.pngbin635 -> 0 bytes
-rw-r--r--images/emoji/1f1fe-1f1ea.pngbin507 -> 0 bytes
-rw-r--r--images/emoji/1f1fe-1f1f9.pngbin1627 -> 0 bytes
-rw-r--r--images/emoji/1f1fe.pngbin590 -> 0 bytes
-rw-r--r--images/emoji/1f1ff-1f1e6.pngbin676 -> 0 bytes
-rw-r--r--images/emoji/1f1ff-1f1f2.pngbin881 -> 0 bytes
-rw-r--r--images/emoji/1f1ff-1f1fc.pngbin993 -> 0 bytes
-rw-r--r--images/emoji/1f1ff.pngbin571 -> 0 bytes
-rw-r--r--images/emoji/1f201.pngbin266 -> 0 bytes
-rw-r--r--images/emoji/1f202.pngbin420 -> 0 bytes
-rw-r--r--images/emoji/1f21a.pngbin534 -> 0 bytes
-rw-r--r--images/emoji/1f22f.pngbin504 -> 0 bytes
-rw-r--r--images/emoji/1f232.pngbin584 -> 0 bytes
-rw-r--r--images/emoji/1f233.pngbin456 -> 0 bytes
-rw-r--r--images/emoji/1f234.pngbin484 -> 0 bytes
-rw-r--r--images/emoji/1f235.pngbin564 -> 0 bytes
-rw-r--r--images/emoji/1f236.pngbin434 -> 0 bytes
-rw-r--r--images/emoji/1f237.pngbin409 -> 0 bytes
-rw-r--r--images/emoji/1f238.pngbin306 -> 0 bytes
-rw-r--r--images/emoji/1f239.pngbin411 -> 0 bytes
-rw-r--r--images/emoji/1f23a.pngbin460 -> 0 bytes
-rw-r--r--images/emoji/1f250.pngbin716 -> 0 bytes
-rw-r--r--images/emoji/1f251.pngbin491 -> 0 bytes
-rw-r--r--images/emoji/1f300.pngbin797 -> 0 bytes
-rw-r--r--images/emoji/1f301.pngbin1069 -> 0 bytes
-rw-r--r--images/emoji/1f302.pngbin1002 -> 0 bytes
-rw-r--r--images/emoji/1f303.pngbin835 -> 0 bytes
-rw-r--r--images/emoji/1f304.pngbin1578 -> 0 bytes
-rw-r--r--images/emoji/1f305.pngbin812 -> 0 bytes
-rw-r--r--images/emoji/1f306.pngbin431 -> 0 bytes
-rw-r--r--images/emoji/1f307.pngbin997 -> 0 bytes
-rw-r--r--images/emoji/1f308.pngbin1299 -> 0 bytes
-rw-r--r--images/emoji/1f309.pngbin637 -> 0 bytes
-rw-r--r--images/emoji/1f30a.pngbin1018 -> 0 bytes
-rw-r--r--images/emoji/1f30b.pngbin1259 -> 0 bytes
-rw-r--r--images/emoji/1f30c.pngbin622 -> 0 bytes
-rw-r--r--images/emoji/1f30d.pngbin978 -> 0 bytes
-rw-r--r--images/emoji/1f30e.pngbin1031 -> 0 bytes
-rw-r--r--images/emoji/1f30f.pngbin966 -> 0 bytes
-rw-r--r--images/emoji/1f310.pngbin796 -> 0 bytes
-rw-r--r--images/emoji/1f311.pngbin829 -> 0 bytes
-rw-r--r--images/emoji/1f312.pngbin1200 -> 0 bytes
-rw-r--r--images/emoji/1f313.pngbin1152 -> 0 bytes
-rw-r--r--images/emoji/1f314.pngbin1229 -> 0 bytes
-rw-r--r--images/emoji/1f315.pngbin841 -> 0 bytes
-rw-r--r--images/emoji/1f316.pngbin1211 -> 0 bytes
-rw-r--r--images/emoji/1f317.pngbin1180 -> 0 bytes
-rw-r--r--images/emoji/1f318.pngbin1213 -> 0 bytes
-rw-r--r--images/emoji/1f319.pngbin446 -> 0 bytes
-rw-r--r--images/emoji/1f31a.pngbin975 -> 0 bytes
-rw-r--r--images/emoji/1f31b.pngbin1068 -> 0 bytes
-rw-r--r--images/emoji/1f31c.pngbin1030 -> 0 bytes
-rw-r--r--images/emoji/1f31d.pngbin1186 -> 0 bytes
-rw-r--r--images/emoji/1f31e.pngbin741 -> 0 bytes
-rw-r--r--images/emoji/1f31f.pngbin732 -> 0 bytes
-rw-r--r--images/emoji/1f320.pngbin1048 -> 0 bytes
-rw-r--r--images/emoji/1f321.pngbin759 -> 0 bytes
-rw-r--r--images/emoji/1f324.pngbin989 -> 0 bytes
-rw-r--r--images/emoji/1f325.pngbin968 -> 0 bytes
-rw-r--r--images/emoji/1f326.pngbin1161 -> 0 bytes
-rw-r--r--images/emoji/1f327.pngbin876 -> 0 bytes
-rw-r--r--images/emoji/1f328.pngbin823 -> 0 bytes
-rw-r--r--images/emoji/1f329.pngbin767 -> 0 bytes
-rw-r--r--images/emoji/1f32a.pngbin1519 -> 0 bytes
-rw-r--r--images/emoji/1f32b.pngbin713 -> 0 bytes
-rw-r--r--images/emoji/1f32c.pngbin1827 -> 0 bytes
-rw-r--r--images/emoji/1f32d.pngbin1770 -> 0 bytes
-rw-r--r--images/emoji/1f32e.pngbin3045 -> 0 bytes
-rw-r--r--images/emoji/1f32f.pngbin2938 -> 0 bytes
-rw-r--r--images/emoji/1f330.pngbin1339 -> 0 bytes
-rw-r--r--images/emoji/1f331.pngbin749 -> 0 bytes
-rw-r--r--images/emoji/1f332.pngbin719 -> 0 bytes
-rw-r--r--images/emoji/1f333.pngbin1270 -> 0 bytes
-rw-r--r--images/emoji/1f334.pngbin1452 -> 0 bytes
-rw-r--r--images/emoji/1f335.pngbin628 -> 0 bytes
-rw-r--r--images/emoji/1f336.pngbin677 -> 0 bytes
-rw-r--r--images/emoji/1f337.pngbin1065 -> 0 bytes
-rw-r--r--images/emoji/1f338.pngbin1129 -> 0 bytes
-rw-r--r--images/emoji/1f339.pngbin1182 -> 0 bytes
-rw-r--r--images/emoji/1f33a.pngbin1815 -> 0 bytes
-rw-r--r--images/emoji/1f33b.pngbin1915 -> 0 bytes
-rw-r--r--images/emoji/1f33c.pngbin867 -> 0 bytes
-rw-r--r--images/emoji/1f33d.pngbin1547 -> 0 bytes
-rw-r--r--images/emoji/1f33e.pngbin1422 -> 0 bytes
-rw-r--r--images/emoji/1f33f.pngbin886 -> 0 bytes
-rw-r--r--images/emoji/1f340.pngbin1156 -> 0 bytes
-rw-r--r--images/emoji/1f341.pngbin1117 -> 0 bytes
-rw-r--r--images/emoji/1f342.pngbin951 -> 0 bytes
-rw-r--r--images/emoji/1f343.pngbin993 -> 0 bytes
-rw-r--r--images/emoji/1f344.pngbin1024 -> 0 bytes
-rw-r--r--images/emoji/1f345.pngbin1055 -> 0 bytes
-rw-r--r--images/emoji/1f346.pngbin773 -> 0 bytes
-rw-r--r--images/emoji/1f347.pngbin1552 -> 0 bytes
-rw-r--r--images/emoji/1f348.pngbin2005 -> 0 bytes
-rw-r--r--images/emoji/1f349.pngbin1275 -> 0 bytes
-rw-r--r--images/emoji/1f34a.pngbin1184 -> 0 bytes
-rw-r--r--images/emoji/1f34b.pngbin1033 -> 0 bytes
-rw-r--r--images/emoji/1f34c.pngbin1157 -> 0 bytes
-rw-r--r--images/emoji/1f34d.pngbin1643 -> 0 bytes
-rw-r--r--images/emoji/1f34e.pngbin655 -> 0 bytes
-rw-r--r--images/emoji/1f34f.pngbin656 -> 0 bytes
-rw-r--r--images/emoji/1f350.pngbin747 -> 0 bytes
-rw-r--r--images/emoji/1f351.pngbin1189 -> 0 bytes
-rw-r--r--images/emoji/1f352.pngbin1211 -> 0 bytes
-rw-r--r--images/emoji/1f353.pngbin1206 -> 0 bytes
-rw-r--r--images/emoji/1f354.pngbin1974 -> 0 bytes
-rw-r--r--images/emoji/1f355.pngbin2009 -> 0 bytes
-rw-r--r--images/emoji/1f356.pngbin1465 -> 0 bytes
-rw-r--r--images/emoji/1f357.pngbin925 -> 0 bytes
-rw-r--r--images/emoji/1f358.pngbin1443 -> 0 bytes
-rw-r--r--images/emoji/1f359.pngbin1091 -> 0 bytes
-rw-r--r--images/emoji/1f35a.pngbin1195 -> 0 bytes
-rw-r--r--images/emoji/1f35b.pngbin1754 -> 0 bytes
-rw-r--r--images/emoji/1f35c.pngbin1992 -> 0 bytes
-rw-r--r--images/emoji/1f35d.pngbin1797 -> 0 bytes
-rw-r--r--images/emoji/1f35e.pngbin1419 -> 0 bytes
-rw-r--r--images/emoji/1f35f.pngbin1874 -> 0 bytes
-rw-r--r--images/emoji/1f360.pngbin951 -> 0 bytes
-rw-r--r--images/emoji/1f361.pngbin802 -> 0 bytes
-rw-r--r--images/emoji/1f362.pngbin794 -> 0 bytes
-rw-r--r--images/emoji/1f363.pngbin2101 -> 0 bytes
-rw-r--r--images/emoji/1f364.pngbin1241 -> 0 bytes
-rw-r--r--images/emoji/1f365.pngbin1245 -> 0 bytes
-rw-r--r--images/emoji/1f366.pngbin1502 -> 0 bytes
-rw-r--r--images/emoji/1f367.pngbin997 -> 0 bytes
-rw-r--r--images/emoji/1f368.pngbin1780 -> 0 bytes
-rw-r--r--images/emoji/1f369.pngbin1322 -> 0 bytes
-rw-r--r--images/emoji/1f36a.pngbin1351 -> 0 bytes
-rw-r--r--images/emoji/1f36b.pngbin771 -> 0 bytes
-rw-r--r--images/emoji/1f36c.pngbin1054 -> 0 bytes
-rw-r--r--images/emoji/1f36d.pngbin2164 -> 0 bytes
-rw-r--r--images/emoji/1f36e.pngbin1273 -> 0 bytes
-rw-r--r--images/emoji/1f36f.pngbin1217 -> 0 bytes
-rw-r--r--images/emoji/1f370.pngbin2266 -> 0 bytes
-rw-r--r--images/emoji/1f371.pngbin1128 -> 0 bytes
-rw-r--r--images/emoji/1f372.pngbin1960 -> 0 bytes
-rw-r--r--images/emoji/1f373.pngbin764 -> 0 bytes
-rw-r--r--images/emoji/1f374.pngbin668 -> 0 bytes
-rw-r--r--images/emoji/1f375.pngbin1297 -> 0 bytes
-rw-r--r--images/emoji/1f376.pngbin826 -> 0 bytes
-rw-r--r--images/emoji/1f377.pngbin655 -> 0 bytes
-rw-r--r--images/emoji/1f378.pngbin1027 -> 0 bytes
-rw-r--r--images/emoji/1f379.pngbin1428 -> 0 bytes
-rw-r--r--images/emoji/1f37a.pngbin1340 -> 0 bytes
-rw-r--r--images/emoji/1f37b.pngbin2100 -> 0 bytes
-rw-r--r--images/emoji/1f37c.pngbin818 -> 0 bytes
-rw-r--r--images/emoji/1f37d.pngbin976 -> 0 bytes
-rw-r--r--images/emoji/1f37f.pngbin1844 -> 0 bytes
-rw-r--r--images/emoji/1f380.pngbin968 -> 0 bytes
-rw-r--r--images/emoji/1f381.pngbin1966 -> 0 bytes
-rw-r--r--images/emoji/1f382.pngbin2219 -> 0 bytes
-rw-r--r--images/emoji/1f383.pngbin2289 -> 0 bytes
-rw-r--r--images/emoji/1f384.pngbin1542 -> 0 bytes
-rw-r--r--images/emoji/1f385-1f3fb.pngbin1588 -> 0 bytes
-rw-r--r--images/emoji/1f385-1f3fc.pngbin1579 -> 0 bytes
-rw-r--r--images/emoji/1f385-1f3fd.pngbin1579 -> 0 bytes
-rw-r--r--images/emoji/1f385-1f3fe.pngbin1579 -> 0 bytes
-rw-r--r--images/emoji/1f385-1f3ff.pngbin1579 -> 0 bytes
-rw-r--r--images/emoji/1f385.pngbin1588 -> 0 bytes
-rw-r--r--images/emoji/1f386.pngbin1365 -> 0 bytes
-rw-r--r--images/emoji/1f387.pngbin910 -> 0 bytes
-rw-r--r--images/emoji/1f388.pngbin501 -> 0 bytes
-rw-r--r--images/emoji/1f389.pngbin1778 -> 0 bytes
-rw-r--r--images/emoji/1f38a.pngbin1703 -> 0 bytes
-rw-r--r--images/emoji/1f38b.pngbin1479 -> 0 bytes
-rw-r--r--images/emoji/1f38c.pngbin1239 -> 0 bytes
-rw-r--r--images/emoji/1f38d.pngbin1947 -> 0 bytes
-rw-r--r--images/emoji/1f38e.pngbin2249 -> 0 bytes
-rw-r--r--images/emoji/1f38f.pngbin1725 -> 0 bytes
-rw-r--r--images/emoji/1f390.pngbin1046 -> 0 bytes
-rw-r--r--images/emoji/1f391.pngbin1350 -> 0 bytes
-rw-r--r--images/emoji/1f392.pngbin1490 -> 0 bytes
-rw-r--r--images/emoji/1f393.pngbin710 -> 0 bytes
-rw-r--r--images/emoji/1f396.pngbin949 -> 0 bytes
-rw-r--r--images/emoji/1f397.pngbin921 -> 0 bytes
-rw-r--r--images/emoji/1f399.pngbin839 -> 0 bytes
-rw-r--r--images/emoji/1f39a.pngbin454 -> 0 bytes
-rw-r--r--images/emoji/1f39b.pngbin1104 -> 0 bytes
-rw-r--r--images/emoji/1f39e.pngbin560 -> 0 bytes
-rw-r--r--images/emoji/1f39f.pngbin1750 -> 0 bytes
-rw-r--r--images/emoji/1f3a0.pngbin1739 -> 0 bytes
-rw-r--r--images/emoji/1f3a1.pngbin2185 -> 0 bytes
-rw-r--r--images/emoji/1f3a2.pngbin1724 -> 0 bytes
-rw-r--r--images/emoji/1f3a3.pngbin1442 -> 0 bytes
-rw-r--r--images/emoji/1f3a4.pngbin1165 -> 0 bytes
-rw-r--r--images/emoji/1f3a5.pngbin576 -> 0 bytes
-rw-r--r--images/emoji/1f3a6.pngbin585 -> 0 bytes
-rw-r--r--images/emoji/1f3a7.pngbin1202 -> 0 bytes
-rw-r--r--images/emoji/1f3a8.pngbin1455 -> 0 bytes
-rw-r--r--images/emoji/1f3a9.pngbin845 -> 0 bytes
-rw-r--r--images/emoji/1f3aa.pngbin1369 -> 0 bytes
-rw-r--r--images/emoji/1f3ab.pngbin763 -> 0 bytes
-rw-r--r--images/emoji/1f3ac.pngbin1535 -> 0 bytes
-rw-r--r--images/emoji/1f3ad.pngbin1971 -> 0 bytes
-rw-r--r--images/emoji/1f3ae.pngbin765 -> 0 bytes
-rw-r--r--images/emoji/1f3af.pngbin1374 -> 0 bytes
-rw-r--r--images/emoji/1f3b0.pngbin1648 -> 0 bytes
-rw-r--r--images/emoji/1f3b1.pngbin810 -> 0 bytes
-rw-r--r--images/emoji/1f3b2.pngbin1136 -> 0 bytes
-rw-r--r--images/emoji/1f3b3.pngbin1426 -> 0 bytes
-rw-r--r--images/emoji/1f3b4.pngbin449 -> 0 bytes
-rw-r--r--images/emoji/1f3b5.pngbin419 -> 0 bytes
-rw-r--r--images/emoji/1f3b6.pngbin501 -> 0 bytes
-rw-r--r--images/emoji/1f3b7.pngbin1442 -> 0 bytes
-rw-r--r--images/emoji/1f3b8.pngbin1056 -> 0 bytes
-rw-r--r--images/emoji/1f3b9.pngbin1695 -> 0 bytes
-rw-r--r--images/emoji/1f3ba.pngbin1286 -> 0 bytes
-rw-r--r--images/emoji/1f3bb.pngbin1156 -> 0 bytes
-rw-r--r--images/emoji/1f3bc.pngbin1289 -> 0 bytes
-rw-r--r--images/emoji/1f3bd.pngbin784 -> 0 bytes
-rw-r--r--images/emoji/1f3be.pngbin1561 -> 0 bytes
-rw-r--r--images/emoji/1f3bf.pngbin1762 -> 0 bytes
-rw-r--r--images/emoji/1f3c0.pngbin1546 -> 0 bytes
-rw-r--r--images/emoji/1f3c1.pngbin787 -> 0 bytes
-rw-r--r--images/emoji/1f3c2.pngbin2020 -> 0 bytes
-rw-r--r--images/emoji/1f3c3-1f3fb.pngbin1163 -> 0 bytes
-rw-r--r--images/emoji/1f3c3-1f3fc.pngbin1162 -> 0 bytes
-rw-r--r--images/emoji/1f3c3-1f3fd.pngbin1151 -> 0 bytes
-rw-r--r--images/emoji/1f3c3-1f3fe.pngbin1156 -> 0 bytes
-rw-r--r--images/emoji/1f3c3-1f3ff.pngbin1145 -> 0 bytes
-rw-r--r--images/emoji/1f3c3.pngbin1161 -> 0 bytes
-rw-r--r--images/emoji/1f3c4-1f3fb.pngbin1781 -> 0 bytes
-rw-r--r--images/emoji/1f3c4-1f3fc.pngbin1769 -> 0 bytes
-rw-r--r--images/emoji/1f3c4-1f3fd.pngbin1777 -> 0 bytes
-rw-r--r--images/emoji/1f3c4-1f3fe.pngbin1784 -> 0 bytes
-rw-r--r--images/emoji/1f3c4-1f3ff.pngbin1782 -> 0 bytes
-rw-r--r--images/emoji/1f3c4.pngbin1777 -> 0 bytes
-rw-r--r--images/emoji/1f3c5.pngbin1702 -> 0 bytes
-rw-r--r--images/emoji/1f3c6.pngbin863 -> 0 bytes
-rw-r--r--images/emoji/1f3c7-1f3fb.pngbin2099 -> 0 bytes
-rw-r--r--images/emoji/1f3c7-1f3fc.pngbin2103 -> 0 bytes
-rw-r--r--images/emoji/1f3c7-1f3fd.pngbin2090 -> 0 bytes
-rw-r--r--images/emoji/1f3c7-1f3fe.pngbin2090 -> 0 bytes
-rw-r--r--images/emoji/1f3c7-1f3ff.pngbin2085 -> 0 bytes
-rw-r--r--images/emoji/1f3c7.pngbin2096 -> 0 bytes
-rw-r--r--images/emoji/1f3c8.pngbin958 -> 0 bytes
-rw-r--r--images/emoji/1f3c9.pngbin1620 -> 0 bytes
-rw-r--r--images/emoji/1f3ca-1f3fb.pngbin1184 -> 0 bytes
-rw-r--r--images/emoji/1f3ca-1f3fc.pngbin1184 -> 0 bytes
-rw-r--r--images/emoji/1f3ca-1f3fd.pngbin1184 -> 0 bytes
-rw-r--r--images/emoji/1f3ca-1f3fe.pngbin1184 -> 0 bytes
-rw-r--r--images/emoji/1f3ca-1f3ff.pngbin1184 -> 0 bytes
-rw-r--r--images/emoji/1f3ca.pngbin1184 -> 0 bytes
-rw-r--r--images/emoji/1f3cb-1f3fb.pngbin1346 -> 0 bytes
-rw-r--r--images/emoji/1f3cb-1f3fc.pngbin1347 -> 0 bytes
-rw-r--r--images/emoji/1f3cb-1f3fd.pngbin1339 -> 0 bytes
-rw-r--r--images/emoji/1f3cb-1f3fe.pngbin1343 -> 0 bytes
-rw-r--r--images/emoji/1f3cb-1f3ff.pngbin1337 -> 0 bytes
-rw-r--r--images/emoji/1f3cb.pngbin1356 -> 0 bytes
-rw-r--r--images/emoji/1f3cc.pngbin1189 -> 0 bytes
-rw-r--r--images/emoji/1f3cd.pngbin2081 -> 0 bytes
-rw-r--r--images/emoji/1f3ce.pngbin2140 -> 0 bytes
-rw-r--r--images/emoji/1f3cf.pngbin1060 -> 0 bytes
-rw-r--r--images/emoji/1f3d0.pngbin1204 -> 0 bytes
-rw-r--r--images/emoji/1f3d1.pngbin947 -> 0 bytes
-rw-r--r--images/emoji/1f3d2.pngbin1010 -> 0 bytes
-rw-r--r--images/emoji/1f3d3.pngbin823 -> 0 bytes
-rw-r--r--images/emoji/1f3d4.pngbin1194 -> 0 bytes
-rw-r--r--images/emoji/1f3d5.pngbin1515 -> 0 bytes
-rw-r--r--images/emoji/1f3d6.pngbin942 -> 0 bytes
-rw-r--r--images/emoji/1f3d7.pngbin668 -> 0 bytes
-rw-r--r--images/emoji/1f3d8.pngbin981 -> 0 bytes
-rw-r--r--images/emoji/1f3d9.pngbin599 -> 0 bytes
-rw-r--r--images/emoji/1f3da.pngbin1606 -> 0 bytes
-rw-r--r--images/emoji/1f3db.pngbin1006 -> 0 bytes
-rw-r--r--images/emoji/1f3dc.pngbin1443 -> 0 bytes
-rw-r--r--images/emoji/1f3dd.pngbin1273 -> 0 bytes
-rw-r--r--images/emoji/1f3de.pngbin929 -> 0 bytes
-rw-r--r--images/emoji/1f3df.pngbin1516 -> 0 bytes
-rw-r--r--images/emoji/1f3e0.pngbin863 -> 0 bytes
-rw-r--r--images/emoji/1f3e1.pngbin1614 -> 0 bytes
-rw-r--r--images/emoji/1f3e2.pngbin524 -> 0 bytes
-rw-r--r--images/emoji/1f3e3.pngbin676 -> 0 bytes
-rw-r--r--images/emoji/1f3e4.pngbin551 -> 0 bytes
-rw-r--r--images/emoji/1f3e5.pngbin530 -> 0 bytes
-rw-r--r--images/emoji/1f3e6.pngbin1358 -> 0 bytes
-rw-r--r--images/emoji/1f3e7.pngbin1397 -> 0 bytes
-rw-r--r--images/emoji/1f3e8.pngbin1322 -> 0 bytes
-rw-r--r--images/emoji/1f3e9.pngbin372 -> 0 bytes
-rw-r--r--images/emoji/1f3ea.pngbin528 -> 0 bytes
-rw-r--r--images/emoji/1f3eb.pngbin1234 -> 0 bytes
-rw-r--r--images/emoji/1f3ec.pngbin673 -> 0 bytes
-rw-r--r--images/emoji/1f3ed.pngbin936 -> 0 bytes
-rw-r--r--images/emoji/1f3ee.pngbin1228 -> 0 bytes
-rw-r--r--images/emoji/1f3ef.pngbin1404 -> 0 bytes
-rw-r--r--images/emoji/1f3f0.pngbin965 -> 0 bytes
-rw-r--r--images/emoji/1f3f3.pngbin699 -> 0 bytes
-rw-r--r--images/emoji/1f3f4.pngbin702 -> 0 bytes
-rw-r--r--images/emoji/1f3f5.pngbin1023 -> 0 bytes
-rw-r--r--images/emoji/1f3f7.pngbin669 -> 0 bytes
-rw-r--r--images/emoji/1f3f8.pngbin1255 -> 0 bytes
-rw-r--r--images/emoji/1f3f9.pngbin1402 -> 0 bytes
-rw-r--r--images/emoji/1f3fa.pngbin1044 -> 0 bytes
-rw-r--r--images/emoji/1f400.pngbin1193 -> 0 bytes
-rw-r--r--images/emoji/1f401.pngbin1324 -> 0 bytes
-rw-r--r--images/emoji/1f402.pngbin1436 -> 0 bytes
-rw-r--r--images/emoji/1f403.pngbin1536 -> 0 bytes
-rw-r--r--images/emoji/1f404.pngbin1810 -> 0 bytes
-rw-r--r--images/emoji/1f405.pngbin2623 -> 0 bytes
-rw-r--r--images/emoji/1f406.pngbin2222 -> 0 bytes
-rw-r--r--images/emoji/1f407.pngbin1805 -> 0 bytes
-rw-r--r--images/emoji/1f408.pngbin1781 -> 0 bytes
-rw-r--r--images/emoji/1f409.pngbin1575 -> 0 bytes
-rw-r--r--images/emoji/1f40a.pngbin2408 -> 0 bytes
-rw-r--r--images/emoji/1f40b.pngbin1196 -> 0 bytes
-rw-r--r--images/emoji/1f40c.pngbin1731 -> 0 bytes
-rw-r--r--images/emoji/1f40d.pngbin1579 -> 0 bytes
-rw-r--r--images/emoji/1f40e.pngbin1404 -> 0 bytes
-rw-r--r--images/emoji/1f40f.pngbin1951 -> 0 bytes
-rw-r--r--images/emoji/1f410.pngbin981 -> 0 bytes
-rw-r--r--images/emoji/1f411.pngbin1374 -> 0 bytes
-rw-r--r--images/emoji/1f412.pngbin1349 -> 0 bytes
-rw-r--r--images/emoji/1f413.pngbin1333 -> 0 bytes
-rw-r--r--images/emoji/1f414.pngbin1267 -> 0 bytes
-rw-r--r--images/emoji/1f415.pngbin2085 -> 0 bytes
-rw-r--r--images/emoji/1f416.pngbin1548 -> 0 bytes
-rw-r--r--images/emoji/1f417.pngbin1368 -> 0 bytes
-rw-r--r--images/emoji/1f418.pngbin1293 -> 0 bytes
-rw-r--r--images/emoji/1f419.pngbin1188 -> 0 bytes
-rw-r--r--images/emoji/1f41a.pngbin1497 -> 0 bytes
-rw-r--r--images/emoji/1f41b.pngbin1604 -> 0 bytes
-rw-r--r--images/emoji/1f41c.pngbin1412 -> 0 bytes
-rw-r--r--images/emoji/1f41d.pngbin1383 -> 0 bytes
-rw-r--r--images/emoji/1f41e.pngbin1288 -> 0 bytes
-rw-r--r--images/emoji/1f41f.pngbin1080 -> 0 bytes
-rw-r--r--images/emoji/1f420.pngbin1676 -> 0 bytes
-rw-r--r--images/emoji/1f421.pngbin1621 -> 0 bytes
-rw-r--r--images/emoji/1f422.pngbin1516 -> 0 bytes
-rw-r--r--images/emoji/1f423.pngbin1599 -> 0 bytes
-rw-r--r--images/emoji/1f424.pngbin1181 -> 0 bytes
-rw-r--r--images/emoji/1f425.pngbin1174 -> 0 bytes
-rw-r--r--images/emoji/1f426.pngbin1068 -> 0 bytes
-rw-r--r--images/emoji/1f427.pngbin1034 -> 0 bytes
-rw-r--r--images/emoji/1f428.pngbin1430 -> 0 bytes
-rw-r--r--images/emoji/1f429.pngbin1531 -> 0 bytes
-rw-r--r--images/emoji/1f42a.pngbin1515 -> 0 bytes
-rw-r--r--images/emoji/1f42b.pngbin1190 -> 0 bytes
-rw-r--r--images/emoji/1f42c.pngbin1700 -> 0 bytes
-rw-r--r--images/emoji/1f42d.pngbin1246 -> 0 bytes
-rw-r--r--images/emoji/1f42e.pngbin1641 -> 0 bytes
-rw-r--r--images/emoji/1f42f.pngbin2104 -> 0 bytes
-rw-r--r--images/emoji/1f430.pngbin1661 -> 0 bytes
-rw-r--r--images/emoji/1f431.pngbin1358 -> 0 bytes
-rw-r--r--images/emoji/1f432.pngbin1769 -> 0 bytes
-rw-r--r--images/emoji/1f433.pngbin1578 -> 0 bytes
-rw-r--r--images/emoji/1f434.pngbin1695 -> 0 bytes
-rw-r--r--images/emoji/1f435.pngbin1027 -> 0 bytes
-rw-r--r--images/emoji/1f436.pngbin1680 -> 0 bytes
-rw-r--r--images/emoji/1f437.pngbin1138 -> 0 bytes
-rw-r--r--images/emoji/1f438.pngbin897 -> 0 bytes
-rw-r--r--images/emoji/1f439.pngbin1280 -> 0 bytes
-rw-r--r--images/emoji/1f43a.pngbin1528 -> 0 bytes
-rw-r--r--images/emoji/1f43b.pngbin1023 -> 0 bytes
-rw-r--r--images/emoji/1f43c.pngbin1478 -> 0 bytes
-rw-r--r--images/emoji/1f43d.pngbin820 -> 0 bytes
-rw-r--r--images/emoji/1f43e.pngbin603 -> 0 bytes
-rw-r--r--images/emoji/1f43f.pngbin1459 -> 0 bytes
-rw-r--r--images/emoji/1f440.pngbin791 -> 0 bytes
-rw-r--r--images/emoji/1f441-1f5e8.pngbin698 -> 0 bytes
-rw-r--r--images/emoji/1f441.pngbin664 -> 0 bytes
-rw-r--r--images/emoji/1f442-1f3fb.pngbin860 -> 0 bytes
-rw-r--r--images/emoji/1f442-1f3fc.pngbin860 -> 0 bytes
-rw-r--r--images/emoji/1f442-1f3fd.pngbin860 -> 0 bytes
-rw-r--r--images/emoji/1f442-1f3fe.pngbin860 -> 0 bytes
-rw-r--r--images/emoji/1f442-1f3ff.pngbin860 -> 0 bytes
-rw-r--r--images/emoji/1f442.pngbin860 -> 0 bytes
-rw-r--r--images/emoji/1f443-1f3fb.pngbin703 -> 0 bytes
-rw-r--r--images/emoji/1f443-1f3fc.pngbin703 -> 0 bytes
-rw-r--r--images/emoji/1f443-1f3fd.pngbin703 -> 0 bytes
-rw-r--r--images/emoji/1f443-1f3fe.pngbin703 -> 0 bytes
-rw-r--r--images/emoji/1f443-1f3ff.pngbin703 -> 0 bytes
-rw-r--r--images/emoji/1f443.pngbin703 -> 0 bytes
-rw-r--r--images/emoji/1f444.pngbin599 -> 0 bytes
-rw-r--r--images/emoji/1f445.pngbin599 -> 0 bytes
-rw-r--r--images/emoji/1f446-1f3fb.pngbin822 -> 0 bytes
-rw-r--r--images/emoji/1f446-1f3fc.pngbin822 -> 0 bytes
-rw-r--r--images/emoji/1f446-1f3fd.pngbin871 -> 0 bytes
-rw-r--r--images/emoji/1f446-1f3fe.pngbin822 -> 0 bytes
-rw-r--r--images/emoji/1f446-1f3ff.pngbin822 -> 0 bytes
-rw-r--r--images/emoji/1f446.pngbin822 -> 0 bytes
-rw-r--r--images/emoji/1f447-1f3fb.pngbin856 -> 0 bytes
-rw-r--r--images/emoji/1f447-1f3fc.pngbin856 -> 0 bytes
-rw-r--r--images/emoji/1f447-1f3fd.pngbin858 -> 0 bytes
-rw-r--r--images/emoji/1f447-1f3fe.pngbin856 -> 0 bytes
-rw-r--r--images/emoji/1f447-1f3ff.pngbin856 -> 0 bytes
-rw-r--r--images/emoji/1f447.pngbin853 -> 0 bytes
-rw-r--r--images/emoji/1f448-1f3fb.pngbin832 -> 0 bytes
-rw-r--r--images/emoji/1f448-1f3fc.pngbin830 -> 0 bytes
-rw-r--r--images/emoji/1f448-1f3fd.pngbin830 -> 0 bytes
-rw-r--r--images/emoji/1f448-1f3fe.pngbin830 -> 0 bytes
-rw-r--r--images/emoji/1f448-1f3ff.pngbin832 -> 0 bytes
-rw-r--r--images/emoji/1f448.pngbin825 -> 0 bytes
-rw-r--r--images/emoji/1f449-1f3fb.pngbin805 -> 0 bytes
-rw-r--r--images/emoji/1f449-1f3fc.pngbin805 -> 0 bytes
-rw-r--r--images/emoji/1f449-1f3fd.pngbin805 -> 0 bytes
-rw-r--r--images/emoji/1f449-1f3fe.pngbin805 -> 0 bytes
-rw-r--r--images/emoji/1f449-1f3ff.pngbin805 -> 0 bytes
-rw-r--r--images/emoji/1f449.pngbin805 -> 0 bytes
-rw-r--r--images/emoji/1f44a-1f3fb.pngbin838 -> 0 bytes
-rw-r--r--images/emoji/1f44a-1f3fc.pngbin838 -> 0 bytes
-rw-r--r--images/emoji/1f44a-1f3fd.pngbin838 -> 0 bytes
-rw-r--r--images/emoji/1f44a-1f3fe.pngbin838 -> 0 bytes
-rw-r--r--images/emoji/1f44a-1f3ff.pngbin838 -> 0 bytes
-rw-r--r--images/emoji/1f44a.pngbin838 -> 0 bytes
-rw-r--r--images/emoji/1f44b-1f3fb.pngbin1311 -> 0 bytes
-rw-r--r--images/emoji/1f44b-1f3fc.pngbin1311 -> 0 bytes
-rw-r--r--images/emoji/1f44b-1f3fd.pngbin1295 -> 0 bytes
-rw-r--r--images/emoji/1f44b-1f3fe.pngbin1311 -> 0 bytes
-rw-r--r--images/emoji/1f44b-1f3ff.pngbin1311 -> 0 bytes
-rw-r--r--images/emoji/1f44b.pngbin1311 -> 0 bytes
-rw-r--r--images/emoji/1f44c-1f3fb.pngbin979 -> 0 bytes
-rw-r--r--images/emoji/1f44c-1f3fc.pngbin979 -> 0 bytes
-rw-r--r--images/emoji/1f44c-1f3fd.pngbin979 -> 0 bytes
-rw-r--r--images/emoji/1f44c-1f3fe.pngbin979 -> 0 bytes
-rw-r--r--images/emoji/1f44c-1f3ff.pngbin979 -> 0 bytes
-rw-r--r--images/emoji/1f44c.pngbin979 -> 0 bytes
-rw-r--r--images/emoji/1f44d-1f3fb.pngbin814 -> 0 bytes
-rw-r--r--images/emoji/1f44d-1f3fc.pngbin814 -> 0 bytes
-rw-r--r--images/emoji/1f44d-1f3fd.pngbin814 -> 0 bytes
-rw-r--r--images/emoji/1f44d-1f3fe.pngbin814 -> 0 bytes
-rw-r--r--images/emoji/1f44d-1f3ff.pngbin814 -> 0 bytes
-rw-r--r--images/emoji/1f44d.pngbin814 -> 0 bytes
-rw-r--r--images/emoji/1f44e-1f3fb.pngbin815 -> 0 bytes
-rw-r--r--images/emoji/1f44e-1f3fc.pngbin815 -> 0 bytes
-rw-r--r--images/emoji/1f44e-1f3fd.pngbin815 -> 0 bytes
-rw-r--r--images/emoji/1f44e-1f3fe.pngbin815 -> 0 bytes
-rw-r--r--images/emoji/1f44e-1f3ff.pngbin815 -> 0 bytes
-rw-r--r--images/emoji/1f44e.pngbin815 -> 0 bytes
-rw-r--r--images/emoji/1f44f-1f3fb.pngbin1460 -> 0 bytes
-rw-r--r--images/emoji/1f44f-1f3fc.pngbin1460 -> 0 bytes
-rw-r--r--images/emoji/1f44f-1f3fd.pngbin1460 -> 0 bytes
-rw-r--r--images/emoji/1f44f-1f3fe.pngbin1459 -> 0 bytes
-rw-r--r--images/emoji/1f44f-1f3ff.pngbin1445 -> 0 bytes
-rw-r--r--images/emoji/1f450-1f3fb.pngbin1053 -> 0 bytes
-rw-r--r--images/emoji/1f450-1f3fc.pngbin1053 -> 0 bytes
-rw-r--r--images/emoji/1f450-1f3fd.pngbin1053 -> 0 bytes
-rw-r--r--images/emoji/1f450-1f3fe.pngbin1053 -> 0 bytes
-rw-r--r--images/emoji/1f450-1f3ff.pngbin1053 -> 0 bytes
-rw-r--r--images/emoji/1f450.pngbin1053 -> 0 bytes
-rw-r--r--images/emoji/1f451.pngbin1534 -> 0 bytes
-rw-r--r--images/emoji/1f452.pngbin1553 -> 0 bytes
-rw-r--r--images/emoji/1f453.pngbin577 -> 0 bytes
-rw-r--r--images/emoji/1f454.pngbin995 -> 0 bytes
-rw-r--r--images/emoji/1f455.pngbin670 -> 0 bytes
-rw-r--r--images/emoji/1f456.pngbin1158 -> 0 bytes
-rw-r--r--images/emoji/1f457.pngbin1001 -> 0 bytes
-rw-r--r--images/emoji/1f458.pngbin1539 -> 0 bytes
-rw-r--r--images/emoji/1f459.pngbin613 -> 0 bytes
-rw-r--r--images/emoji/1f45a.pngbin1042 -> 0 bytes
-rw-r--r--images/emoji/1f45b.pngbin1558 -> 0 bytes
-rw-r--r--images/emoji/1f45c.pngbin1285 -> 0 bytes
-rw-r--r--images/emoji/1f45d.pngbin1259 -> 0 bytes
-rw-r--r--images/emoji/1f45e.pngbin1652 -> 0 bytes
-rw-r--r--images/emoji/1f45f.pngbin1595 -> 0 bytes
-rw-r--r--images/emoji/1f460.pngbin1008 -> 0 bytes
-rw-r--r--images/emoji/1f461.pngbin1180 -> 0 bytes
-rw-r--r--images/emoji/1f462.pngbin662 -> 0 bytes
-rw-r--r--images/emoji/1f463.pngbin621 -> 0 bytes
-rw-r--r--images/emoji/1f464.pngbin426 -> 0 bytes
-rw-r--r--images/emoji/1f465.pngbin526 -> 0 bytes
-rw-r--r--images/emoji/1f466-1f3fb.pngbin876 -> 0 bytes
-rw-r--r--images/emoji/1f466-1f3fc.pngbin876 -> 0 bytes
-rw-r--r--images/emoji/1f466-1f3fd.pngbin876 -> 0 bytes
-rw-r--r--images/emoji/1f466-1f3fe.pngbin870 -> 0 bytes
-rw-r--r--images/emoji/1f466-1f3ff.pngbin873 -> 0 bytes
-rw-r--r--images/emoji/1f466.pngbin881 -> 0 bytes
-rw-r--r--images/emoji/1f467-1f3fb.pngbin1260 -> 0 bytes
-rw-r--r--images/emoji/1f467-1f3fc.pngbin1255 -> 0 bytes
-rw-r--r--images/emoji/1f467-1f3fd.pngbin1255 -> 0 bytes
-rw-r--r--images/emoji/1f467-1f3fe.pngbin1241 -> 0 bytes
-rw-r--r--images/emoji/1f467-1f3ff.pngbin1245 -> 0 bytes
-rw-r--r--images/emoji/1f467.pngbin1262 -> 0 bytes
-rw-r--r--images/emoji/1f468-1f3fb.pngbin1069 -> 0 bytes
-rw-r--r--images/emoji/1f468-1f3fc.pngbin1069 -> 0 bytes
-rw-r--r--images/emoji/1f468-1f3fd.pngbin1069 -> 0 bytes
-rw-r--r--images/emoji/1f468-1f3fe.pngbin1069 -> 0 bytes
-rw-r--r--images/emoji/1f468-1f3ff.pngbin1087 -> 0 bytes
-rw-r--r--images/emoji/1f468-1f468-1f466-1f466.pngbin1354 -> 0 bytes
-rw-r--r--images/emoji/1f468-1f468-1f466.pngbin1206 -> 0 bytes
-rw-r--r--images/emoji/1f468-1f468-1f467-1f466.pngbin1626 -> 0 bytes
-rw-r--r--images/emoji/1f468-1f468-1f467-1f467.pngbin1448 -> 0 bytes
-rw-r--r--images/emoji/1f468-1f468-1f467.pngbin1362 -> 0 bytes
-rw-r--r--images/emoji/1f468-1f469-1f466-1f466.pngbin1641 -> 0 bytes
-rw-r--r--images/emoji/1f468-1f469-1f467-1f466.pngbin1838 -> 0 bytes
-rw-r--r--images/emoji/1f468-1f469-1f467-1f467.pngbin1739 -> 0 bytes
-rw-r--r--images/emoji/1f468-1f469-1f467.pngbin1555 -> 0 bytes
-rw-r--r--images/emoji/1f468-2764-1f468.pngbin1091 -> 0 bytes
-rw-r--r--images/emoji/1f468-2764-1f48b-1f468.pngbin1269 -> 0 bytes
-rw-r--r--images/emoji/1f468.pngbin1092 -> 0 bytes
-rw-r--r--images/emoji/1f469-1f3fb.pngbin1212 -> 0 bytes
-rw-r--r--images/emoji/1f469-1f3fc.pngbin1212 -> 0 bytes
-rw-r--r--images/emoji/1f469-1f3fd.pngbin1206 -> 0 bytes
-rw-r--r--images/emoji/1f469-1f3fe.pngbin1197 -> 0 bytes
-rw-r--r--images/emoji/1f469-1f3ff.pngbin1203 -> 0 bytes
-rw-r--r--images/emoji/1f469-1f469-1f466-1f466.pngbin1297 -> 0 bytes
-rw-r--r--images/emoji/1f469-1f469-1f466.pngbin1155 -> 0 bytes
-rw-r--r--images/emoji/1f469-1f469-1f467-1f466.pngbin1550 -> 0 bytes
-rw-r--r--images/emoji/1f469-1f469-1f467-1f467.pngbin1374 -> 0 bytes
-rw-r--r--images/emoji/1f469-1f469-1f467.pngbin1290 -> 0 bytes
-rw-r--r--images/emoji/1f469-2764-1f469.pngbin1034 -> 0 bytes
-rw-r--r--images/emoji/1f469-2764-1f48b-1f469.pngbin1150 -> 0 bytes
-rw-r--r--images/emoji/1f469.pngbin1212 -> 0 bytes
-rw-r--r--images/emoji/1f46a.pngbin1437 -> 0 bytes
-rw-r--r--images/emoji/1f46b.pngbin1538 -> 0 bytes
-rw-r--r--images/emoji/1f46c.pngbin1347 -> 0 bytes
-rw-r--r--images/emoji/1f46d.pngbin1547 -> 0 bytes
-rw-r--r--images/emoji/1f46e-1f3fb.pngbin1421 -> 0 bytes
-rw-r--r--images/emoji/1f46e-1f3fc.pngbin1424 -> 0 bytes
-rw-r--r--images/emoji/1f46e-1f3fd.pngbin1422 -> 0 bytes
-rw-r--r--images/emoji/1f46e-1f3fe.pngbin1422 -> 0 bytes
-rw-r--r--images/emoji/1f46e-1f3ff.pngbin1434 -> 0 bytes
-rw-r--r--images/emoji/1f46e.pngbin1442 -> 0 bytes
-rw-r--r--images/emoji/1f46f.pngbin1876 -> 0 bytes
-rw-r--r--images/emoji/1f470-1f3fb.pngbin2464 -> 0 bytes
-rw-r--r--images/emoji/1f470-1f3fc.pngbin2457 -> 0 bytes
-rw-r--r--images/emoji/1f470-1f3fd.pngbin2463 -> 0 bytes
-rw-r--r--images/emoji/1f470-1f3fe.pngbin2463 -> 0 bytes
-rw-r--r--images/emoji/1f470-1f3ff.pngbin2462 -> 0 bytes
-rw-r--r--images/emoji/1f470.pngbin2452 -> 0 bytes
-rw-r--r--images/emoji/1f471-1f3fb.pngbin1181 -> 0 bytes
-rw-r--r--images/emoji/1f471-1f3fc.pngbin1181 -> 0 bytes
-rw-r--r--images/emoji/1f471-1f3fd.pngbin1181 -> 0 bytes
-rw-r--r--images/emoji/1f471-1f3fe.pngbin1189 -> 0 bytes
-rw-r--r--images/emoji/1f471-1f3ff.pngbin1214 -> 0 bytes
-rw-r--r--images/emoji/1f471.pngbin1205 -> 0 bytes
-rw-r--r--images/emoji/1f472-1f3fb.pngbin1328 -> 0 bytes
-rw-r--r--images/emoji/1f472-1f3fc.pngbin1332 -> 0 bytes
-rw-r--r--images/emoji/1f472-1f3fd.pngbin1329 -> 0 bytes
-rw-r--r--images/emoji/1f472-1f3fe.pngbin1325 -> 0 bytes
-rw-r--r--images/emoji/1f472-1f3ff.pngbin1337 -> 0 bytes
-rw-r--r--images/emoji/1f472.pngbin1339 -> 0 bytes
-rw-r--r--images/emoji/1f473-1f3fb.pngbin1584 -> 0 bytes
-rw-r--r--images/emoji/1f473-1f3fc.pngbin1591 -> 0 bytes
-rw-r--r--images/emoji/1f473-1f3fd.pngbin1584 -> 0 bytes
-rw-r--r--images/emoji/1f473-1f3fe.pngbin1583 -> 0 bytes
-rw-r--r--images/emoji/1f473-1f3ff.pngbin1607 -> 0 bytes
-rw-r--r--images/emoji/1f473.pngbin1619 -> 0 bytes
-rw-r--r--images/emoji/1f474-1f3fb.pngbin1256 -> 0 bytes
-rw-r--r--images/emoji/1f474-1f3fc.pngbin1256 -> 0 bytes
-rw-r--r--images/emoji/1f474-1f3fd.pngbin1256 -> 0 bytes
-rw-r--r--images/emoji/1f474-1f3fe.pngbin1254 -> 0 bytes
-rw-r--r--images/emoji/1f474-1f3ff.pngbin1254 -> 0 bytes
-rw-r--r--images/emoji/1f474.pngbin1256 -> 0 bytes
-rw-r--r--images/emoji/1f475-1f3fb.pngbin1562 -> 0 bytes
-rw-r--r--images/emoji/1f475-1f3fc.pngbin1564 -> 0 bytes
-rw-r--r--images/emoji/1f475-1f3fd.pngbin1555 -> 0 bytes
-rw-r--r--images/emoji/1f475-1f3fe.pngbin1563 -> 0 bytes
-rw-r--r--images/emoji/1f475-1f3ff.pngbin1544 -> 0 bytes
-rw-r--r--images/emoji/1f475.pngbin1472 -> 0 bytes
-rw-r--r--images/emoji/1f476-1f3fb.pngbin1394 -> 0 bytes
-rw-r--r--images/emoji/1f476-1f3fc.pngbin1394 -> 0 bytes
-rw-r--r--images/emoji/1f476-1f3fd.pngbin1405 -> 0 bytes
-rw-r--r--images/emoji/1f476-1f3fe.pngbin1414 -> 0 bytes
-rw-r--r--images/emoji/1f476-1f3ff.pngbin1408 -> 0 bytes
-rw-r--r--images/emoji/1f476.pngbin1383 -> 0 bytes
-rw-r--r--images/emoji/1f477-1f3fb.pngbin1102 -> 0 bytes
-rw-r--r--images/emoji/1f477-1f3fc.pngbin1102 -> 0 bytes
-rw-r--r--images/emoji/1f477-1f3fd.pngbin1102 -> 0 bytes
-rw-r--r--images/emoji/1f477-1f3fe.pngbin1095 -> 0 bytes
-rw-r--r--images/emoji/1f477-1f3ff.pngbin1119 -> 0 bytes
-rw-r--r--images/emoji/1f477.pngbin1126 -> 0 bytes
-rw-r--r--images/emoji/1f478-1f3fb.pngbin1814 -> 0 bytes
-rw-r--r--images/emoji/1f478-1f3fc.pngbin1808 -> 0 bytes
-rw-r--r--images/emoji/1f478-1f3fd.pngbin1808 -> 0 bytes
-rw-r--r--images/emoji/1f478-1f3fe.pngbin1813 -> 0 bytes
-rw-r--r--images/emoji/1f478-1f3ff.pngbin1812 -> 0 bytes
-rw-r--r--images/emoji/1f478.pngbin1816 -> 0 bytes
-rw-r--r--images/emoji/1f479.pngbin1864 -> 0 bytes
-rw-r--r--images/emoji/1f47a.pngbin1563 -> 0 bytes
-rw-r--r--images/emoji/1f47b.pngbin1468 -> 0 bytes
-rw-r--r--images/emoji/1f47c-1f3fb.pngbin2088 -> 0 bytes
-rw-r--r--images/emoji/1f47c-1f3fc.pngbin2075 -> 0 bytes
-rw-r--r--images/emoji/1f47c-1f3fd.pngbin2078 -> 0 bytes
-rw-r--r--images/emoji/1f47c-1f3fe.pngbin2076 -> 0 bytes
-rw-r--r--images/emoji/1f47c-1f3ff.pngbin2078 -> 0 bytes
-rw-r--r--images/emoji/1f47c.pngbin2077 -> 0 bytes
-rw-r--r--images/emoji/1f47d.pngbin839 -> 0 bytes
-rw-r--r--images/emoji/1f47e.pngbin1325 -> 0 bytes
-rw-r--r--images/emoji/1f47f.pngbin1990 -> 0 bytes
-rw-r--r--images/emoji/1f480.pngbin628 -> 0 bytes
-rw-r--r--images/emoji/1f481-1f3fb.pngbin1597 -> 0 bytes
-rw-r--r--images/emoji/1f481-1f3fc.pngbin1591 -> 0 bytes
-rw-r--r--images/emoji/1f481-1f3fd.pngbin1580 -> 0 bytes
-rw-r--r--images/emoji/1f481-1f3fe.pngbin1578 -> 0 bytes
-rw-r--r--images/emoji/1f481-1f3ff.pngbin1588 -> 0 bytes
-rw-r--r--images/emoji/1f481.pngbin1585 -> 0 bytes
-rw-r--r--images/emoji/1f482-1f3fb.pngbin1122 -> 0 bytes
-rw-r--r--images/emoji/1f482-1f3fc.pngbin1164 -> 0 bytes
-rw-r--r--images/emoji/1f482-1f3fd.pngbin1164 -> 0 bytes
-rw-r--r--images/emoji/1f482-1f3fe.pngbin1157 -> 0 bytes
-rw-r--r--images/emoji/1f482-1f3ff.pngbin1167 -> 0 bytes
-rw-r--r--images/emoji/1f482.pngbin1140 -> 0 bytes
-rw-r--r--images/emoji/1f483-1f3fb.pngbin1421 -> 0 bytes
-rw-r--r--images/emoji/1f483-1f3fc.pngbin1423 -> 0 bytes
-rw-r--r--images/emoji/1f483-1f3fd.pngbin1429 -> 0 bytes
-rw-r--r--images/emoji/1f483-1f3fe.pngbin1428 -> 0 bytes
-rw-r--r--images/emoji/1f483-1f3ff.pngbin1418 -> 0 bytes
-rw-r--r--images/emoji/1f483.pngbin1406 -> 0 bytes
-rw-r--r--images/emoji/1f484.pngbin549 -> 0 bytes
-rw-r--r--images/emoji/1f485-1f3fb.pngbin1717 -> 0 bytes
-rw-r--r--images/emoji/1f485-1f3fc.pngbin1716 -> 0 bytes
-rw-r--r--images/emoji/1f485-1f3fd.pngbin1733 -> 0 bytes
-rw-r--r--images/emoji/1f485-1f3fe.pngbin1730 -> 0 bytes
-rw-r--r--images/emoji/1f485-1f3ff.pngbin1719 -> 0 bytes
-rw-r--r--images/emoji/1f485.pngbin1639 -> 0 bytes
-rw-r--r--images/emoji/1f486-1f3fb.pngbin1585 -> 0 bytes
-rw-r--r--images/emoji/1f486-1f3fc.pngbin1565 -> 0 bytes
-rw-r--r--images/emoji/1f486-1f3fd.pngbin1554 -> 0 bytes
-rw-r--r--images/emoji/1f486-1f3fe.pngbin1550 -> 0 bytes
-rw-r--r--images/emoji/1f486-1f3ff.pngbin1557 -> 0 bytes
-rw-r--r--images/emoji/1f486.pngbin1572 -> 0 bytes
-rw-r--r--images/emoji/1f487-1f3fb.pngbin1945 -> 0 bytes
-rw-r--r--images/emoji/1f487-1f3fc.pngbin1936 -> 0 bytes
-rw-r--r--images/emoji/1f487-1f3fd.pngbin1923 -> 0 bytes
-rw-r--r--images/emoji/1f487-1f3fe.pngbin1904 -> 0 bytes
-rw-r--r--images/emoji/1f487-1f3ff.pngbin1920 -> 0 bytes
-rw-r--r--images/emoji/1f487.pngbin1935 -> 0 bytes
-rw-r--r--images/emoji/1f488.pngbin820 -> 0 bytes
-rw-r--r--images/emoji/1f489.pngbin737 -> 0 bytes
-rw-r--r--images/emoji/1f48a.pngbin442 -> 0 bytes
-rw-r--r--images/emoji/1f48c.pngbin923 -> 0 bytes
-rw-r--r--images/emoji/1f48d.pngbin1113 -> 0 bytes
-rw-r--r--images/emoji/1f48e.pngbin715 -> 0 bytes
-rw-r--r--images/emoji/1f48f.pngbin1380 -> 0 bytes
-rw-r--r--images/emoji/1f490.pngbin1662 -> 0 bytes
-rw-r--r--images/emoji/1f491.pngbin1285 -> 0 bytes
-rw-r--r--images/emoji/1f492.pngbin1260 -> 0 bytes
-rw-r--r--images/emoji/1f493.pngbin699 -> 0 bytes
-rw-r--r--images/emoji/1f494.pngbin556 -> 0 bytes
-rw-r--r--images/emoji/1f495.pngbin493 -> 0 bytes
-rw-r--r--images/emoji/1f496.pngbin821 -> 0 bytes
-rw-r--r--images/emoji/1f497.pngbin675 -> 0 bytes
-rw-r--r--images/emoji/1f498.pngbin846 -> 0 bytes
-rw-r--r--images/emoji/1f499.pngbin435 -> 0 bytes
-rw-r--r--images/emoji/1f49a.pngbin435 -> 0 bytes
-rw-r--r--images/emoji/1f49b.pngbin435 -> 0 bytes
-rw-r--r--images/emoji/1f49c.pngbin435 -> 0 bytes
-rw-r--r--images/emoji/1f49d.pngbin1141 -> 0 bytes
-rw-r--r--images/emoji/1f49e.pngbin920 -> 0 bytes
-rw-r--r--images/emoji/1f49f.pngbin557 -> 0 bytes
-rw-r--r--images/emoji/1f4a0.pngbin693 -> 0 bytes
-rw-r--r--images/emoji/1f4a1.pngbin805 -> 0 bytes
-rw-r--r--images/emoji/1f4a2.pngbin594 -> 0 bytes
-rw-r--r--images/emoji/1f4a3.pngbin702 -> 0 bytes
-rw-r--r--images/emoji/1f4a4.pngbin540 -> 0 bytes
-rw-r--r--images/emoji/1f4a5.pngbin1110 -> 0 bytes
-rw-r--r--images/emoji/1f4a6.pngbin549 -> 0 bytes
-rw-r--r--images/emoji/1f4a7.pngbin411 -> 0 bytes
-rw-r--r--images/emoji/1f4a8.pngbin840 -> 0 bytes
-rw-r--r--images/emoji/1f4a9.pngbin1273 -> 0 bytes
-rw-r--r--images/emoji/1f4aa-1f3fb.pngbin1012 -> 0 bytes
-rw-r--r--images/emoji/1f4aa-1f3fc.pngbin1012 -> 0 bytes
-rw-r--r--images/emoji/1f4aa-1f3fd.pngbin1012 -> 0 bytes
-rw-r--r--images/emoji/1f4aa-1f3fe.pngbin1012 -> 0 bytes
-rw-r--r--images/emoji/1f4aa-1f3ff.pngbin1012 -> 0 bytes
-rw-r--r--images/emoji/1f4aa.pngbin1012 -> 0 bytes
-rw-r--r--images/emoji/1f4ab.pngbin795 -> 0 bytes
-rw-r--r--images/emoji/1f4ac.pngbin384 -> 0 bytes
-rw-r--r--images/emoji/1f4ad.pngbin489 -> 0 bytes
-rw-r--r--images/emoji/1f4ae.pngbin941 -> 0 bytes
-rw-r--r--images/emoji/1f4af.pngbin793 -> 0 bytes
-rw-r--r--images/emoji/1f4b0.pngbin2310 -> 0 bytes
-rw-r--r--images/emoji/1f4b1.pngbin576 -> 0 bytes
-rw-r--r--images/emoji/1f4b2.pngbin429 -> 0 bytes
-rw-r--r--images/emoji/1f4b3.pngbin1012 -> 0 bytes
-rw-r--r--images/emoji/1f4b4.pngbin421 -> 0 bytes
-rw-r--r--images/emoji/1f4b5.pngbin405 -> 0 bytes
-rw-r--r--images/emoji/1f4b6.pngbin460 -> 0 bytes
-rw-r--r--images/emoji/1f4b7.pngbin452 -> 0 bytes
-rw-r--r--images/emoji/1f4b8.pngbin2327 -> 0 bytes
-rw-r--r--images/emoji/1f4b9.pngbin724 -> 0 bytes
-rw-r--r--images/emoji/1f4ba.pngbin884 -> 0 bytes
-rw-r--r--images/emoji/1f4bb.pngbin369 -> 0 bytes
-rw-r--r--images/emoji/1f4bc.pngbin1275 -> 0 bytes
-rw-r--r--images/emoji/1f4bd.pngbin522 -> 0 bytes
-rw-r--r--images/emoji/1f4be.pngbin258 -> 0 bytes
-rw-r--r--images/emoji/1f4bf.pngbin908 -> 0 bytes
-rw-r--r--images/emoji/1f4c0.pngbin933 -> 0 bytes
-rw-r--r--images/emoji/1f4c1.pngbin1445 -> 0 bytes
-rw-r--r--images/emoji/1f4c2.pngbin755 -> 0 bytes
-rw-r--r--images/emoji/1f4c3.pngbin1157 -> 0 bytes
-rw-r--r--images/emoji/1f4c4.pngbin1110 -> 0 bytes
-rw-r--r--images/emoji/1f4c5.pngbin788 -> 0 bytes
-rw-r--r--images/emoji/1f4c6.pngbin2077 -> 0 bytes
-rw-r--r--images/emoji/1f4c7.pngbin1929 -> 0 bytes
-rw-r--r--images/emoji/1f4c8.pngbin688 -> 0 bytes
-rw-r--r--images/emoji/1f4c9.pngbin709 -> 0 bytes
-rw-r--r--images/emoji/1f4ca.pngbin408 -> 0 bytes
-rw-r--r--images/emoji/1f4cb.pngbin1349 -> 0 bytes
-rw-r--r--images/emoji/1f4cc.pngbin640 -> 0 bytes
-rw-r--r--images/emoji/1f4cd.pngbin455 -> 0 bytes
-rw-r--r--images/emoji/1f4ce.pngbin439 -> 0 bytes
-rw-r--r--images/emoji/1f4cf.pngbin1406 -> 0 bytes
-rw-r--r--images/emoji/1f4d0.pngbin369 -> 0 bytes
-rw-r--r--images/emoji/1f4d1.pngbin1398 -> 0 bytes
-rw-r--r--images/emoji/1f4d2.pngbin1530 -> 0 bytes
-rw-r--r--images/emoji/1f4d3.pngbin1215 -> 0 bytes
-rw-r--r--images/emoji/1f4d4.pngbin1782 -> 0 bytes
-rw-r--r--images/emoji/1f4d5.pngbin1359 -> 0 bytes
-rw-r--r--images/emoji/1f4d6.pngbin1716 -> 0 bytes
-rw-r--r--images/emoji/1f4d7.pngbin1366 -> 0 bytes
-rw-r--r--images/emoji/1f4d8.pngbin1348 -> 0 bytes
-rw-r--r--images/emoji/1f4d9.pngbin1329 -> 0 bytes
-rw-r--r--images/emoji/1f4da.pngbin2474 -> 0 bytes
-rw-r--r--images/emoji/1f4db.pngbin632 -> 0 bytes
-rw-r--r--images/emoji/1f4dc.pngbin989 -> 0 bytes
-rw-r--r--images/emoji/1f4dd.pngbin1625 -> 0 bytes
-rw-r--r--images/emoji/1f4de.pngbin941 -> 0 bytes
-rw-r--r--images/emoji/1f4df.pngbin553 -> 0 bytes
-rw-r--r--images/emoji/1f4e0.pngbin1188 -> 0 bytes
-rw-r--r--images/emoji/1f4e1.pngbin1173 -> 0 bytes
-rw-r--r--images/emoji/1f4e2.pngbin1316 -> 0 bytes
-rw-r--r--images/emoji/1f4e3.pngbin1751 -> 0 bytes
-rw-r--r--images/emoji/1f4e4.pngbin1002 -> 0 bytes
-rw-r--r--images/emoji/1f4e5.pngbin1029 -> 0 bytes
-rw-r--r--images/emoji/1f4e6.pngbin950 -> 0 bytes
-rw-r--r--images/emoji/1f4e7.pngbin1196 -> 0 bytes
-rw-r--r--images/emoji/1f4e8.pngbin1129 -> 0 bytes
-rw-r--r--images/emoji/1f4e9.pngbin1062 -> 0 bytes
-rw-r--r--images/emoji/1f4ea.pngbin1192 -> 0 bytes
-rw-r--r--images/emoji/1f4eb.pngbin1166 -> 0 bytes
-rw-r--r--images/emoji/1f4ec.pngbin1307 -> 0 bytes
-rw-r--r--images/emoji/1f4ed.pngbin960 -> 0 bytes
-rw-r--r--images/emoji/1f4ee.pngbin1077 -> 0 bytes
-rw-r--r--images/emoji/1f4ef.pngbin809 -> 0 bytes
-rw-r--r--images/emoji/1f4f0.pngbin1178 -> 0 bytes
-rw-r--r--images/emoji/1f4f1.pngbin695 -> 0 bytes
-rw-r--r--images/emoji/1f4f2.pngbin815 -> 0 bytes
-rw-r--r--images/emoji/1f4f3.pngbin683 -> 0 bytes
-rw-r--r--images/emoji/1f4f4.pngbin621 -> 0 bytes
-rw-r--r--images/emoji/1f4f5.pngbin790 -> 0 bytes
-rw-r--r--images/emoji/1f4f6.pngbin445 -> 0 bytes
-rw-r--r--images/emoji/1f4f7.pngbin1783 -> 0 bytes
-rw-r--r--images/emoji/1f4f8.pngbin2097 -> 0 bytes
-rw-r--r--images/emoji/1f4f9.pngbin1613 -> 0 bytes
-rw-r--r--images/emoji/1f4fa.pngbin776 -> 0 bytes
-rw-r--r--images/emoji/1f4fb.pngbin851 -> 0 bytes
-rw-r--r--images/emoji/1f4fc.pngbin632 -> 0 bytes
-rw-r--r--images/emoji/1f4fd.pngbin943 -> 0 bytes
-rw-r--r--images/emoji/1f4ff.pngbin1059 -> 0 bytes
-rw-r--r--images/emoji/1f500.pngbin574 -> 0 bytes
-rw-r--r--images/emoji/1f501.pngbin644 -> 0 bytes
-rw-r--r--images/emoji/1f502.pngbin688 -> 0 bytes
-rw-r--r--images/emoji/1f503.pngbin519 -> 0 bytes
-rw-r--r--images/emoji/1f504.pngbin693 -> 0 bytes
-rw-r--r--images/emoji/1f505.pngbin431 -> 0 bytes
-rw-r--r--images/emoji/1f506.pngbin474 -> 0 bytes
-rw-r--r--images/emoji/1f507.pngbin823 -> 0 bytes
-rw-r--r--images/emoji/1f508.pngbin575 -> 0 bytes
-rw-r--r--images/emoji/1f509.pngbin690 -> 0 bytes
-rw-r--r--images/emoji/1f50a.pngbin977 -> 0 bytes
-rw-r--r--images/emoji/1f50b.pngbin228 -> 0 bytes
-rw-r--r--images/emoji/1f50c.pngbin548 -> 0 bytes
-rw-r--r--images/emoji/1f50d.pngbin1240 -> 0 bytes
-rw-r--r--images/emoji/1f50e.pngbin1251 -> 0 bytes
-rw-r--r--images/emoji/1f50f.pngbin1123 -> 0 bytes
-rw-r--r--images/emoji/1f510.pngbin1250 -> 0 bytes
-rw-r--r--images/emoji/1f511.pngbin770 -> 0 bytes
-rw-r--r--images/emoji/1f512.pngbin986 -> 0 bytes
-rw-r--r--images/emoji/1f513.pngbin856 -> 0 bytes
-rw-r--r--images/emoji/1f514.pngbin1497 -> 0 bytes
-rw-r--r--images/emoji/1f515.pngbin823 -> 0 bytes
-rw-r--r--images/emoji/1f516.pngbin747 -> 0 bytes
-rw-r--r--images/emoji/1f517.pngbin477 -> 0 bytes
-rw-r--r--images/emoji/1f518.pngbin674 -> 0 bytes
-rw-r--r--images/emoji/1f519.pngbin562 -> 0 bytes
-rw-r--r--images/emoji/1f51a.pngbin393 -> 0 bytes
-rw-r--r--images/emoji/1f51b.pngbin459 -> 0 bytes
-rw-r--r--images/emoji/1f51c.pngbin483 -> 0 bytes
-rw-r--r--images/emoji/1f51d.pngbin389 -> 0 bytes
-rw-r--r--images/emoji/1f51e.pngbin863 -> 0 bytes
-rw-r--r--images/emoji/1f51f.pngbin621 -> 0 bytes
-rw-r--r--images/emoji/1f520.pngbin805 -> 0 bytes
-rw-r--r--images/emoji/1f521.pngbin670 -> 0 bytes
-rw-r--r--images/emoji/1f522.pngbin676 -> 0 bytes
-rw-r--r--images/emoji/1f523.pngbin746 -> 0 bytes
-rw-r--r--images/emoji/1f524.pngbin646 -> 0 bytes
-rw-r--r--images/emoji/1f525.pngbin1020 -> 0 bytes
-rw-r--r--images/emoji/1f526.pngbin964 -> 0 bytes
-rw-r--r--images/emoji/1f527.pngbin418 -> 0 bytes
-rw-r--r--images/emoji/1f528.pngbin834 -> 0 bytes
-rw-r--r--images/emoji/1f529.pngbin899 -> 0 bytes
-rw-r--r--images/emoji/1f52a.pngbin616 -> 0 bytes
-rw-r--r--images/emoji/1f52b.pngbin1859 -> 0 bytes
-rw-r--r--images/emoji/1f52c.pngbin1113 -> 0 bytes
-rw-r--r--images/emoji/1f52d.pngbin1256 -> 0 bytes
-rw-r--r--images/emoji/1f52e.pngbin1914 -> 0 bytes
-rw-r--r--images/emoji/1f52f.pngbin540 -> 0 bytes
-rw-r--r--images/emoji/1f530.pngbin545 -> 0 bytes
-rw-r--r--images/emoji/1f531.pngbin668 -> 0 bytes
-rw-r--r--images/emoji/1f532.pngbin122 -> 0 bytes
-rw-r--r--images/emoji/1f533.pngbin122 -> 0 bytes
-rw-r--r--images/emoji/1f534.pngbin374 -> 0 bytes
-rw-r--r--images/emoji/1f535.pngbin371 -> 0 bytes
-rw-r--r--images/emoji/1f536.pngbin248 -> 0 bytes
-rw-r--r--images/emoji/1f537.pngbin245 -> 0 bytes
-rw-r--r--images/emoji/1f538.pngbin194 -> 0 bytes
-rw-r--r--images/emoji/1f539.pngbin191 -> 0 bytes
-rw-r--r--images/emoji/1f53a.pngbin273 -> 0 bytes
-rw-r--r--images/emoji/1f53b.pngbin291 -> 0 bytes
-rw-r--r--images/emoji/1f53c.pngbin454 -> 0 bytes
-rw-r--r--images/emoji/1f53d.pngbin455 -> 0 bytes
-rw-r--r--images/emoji/1f549.pngbin773 -> 0 bytes
-rw-r--r--images/emoji/1f54a.pngbin967 -> 0 bytes
-rw-r--r--images/emoji/1f54b.pngbin1251 -> 0 bytes
-rw-r--r--images/emoji/1f54c.pngbin984 -> 0 bytes
-rw-r--r--images/emoji/1f54d.pngbin1309 -> 0 bytes
-rw-r--r--images/emoji/1f54e.pngbin1279 -> 0 bytes
-rw-r--r--images/emoji/1f550.pngbin586 -> 0 bytes
-rw-r--r--images/emoji/1f551.pngbin591 -> 0 bytes
-rw-r--r--images/emoji/1f552.pngbin482 -> 0 bytes
-rw-r--r--images/emoji/1f553.pngbin592 -> 0 bytes
-rw-r--r--images/emoji/1f554.pngbin585 -> 0 bytes
-rw-r--r--images/emoji/1f555.pngbin466 -> 0 bytes
-rw-r--r--images/emoji/1f556.pngbin581 -> 0 bytes
-rw-r--r--images/emoji/1f557.pngbin590 -> 0 bytes
-rw-r--r--images/emoji/1f558.pngbin484 -> 0 bytes
-rw-r--r--images/emoji/1f559.pngbin593 -> 0 bytes
-rw-r--r--images/emoji/1f55a.pngbin590 -> 0 bytes
-rw-r--r--images/emoji/1f55b.pngbin480 -> 0 bytes
-rw-r--r--images/emoji/1f55c.pngbin526 -> 0 bytes
-rw-r--r--images/emoji/1f55d.pngbin576 -> 0 bytes
-rw-r--r--images/emoji/1f55e.pngbin568 -> 0 bytes
-rw-r--r--images/emoji/1f55f.pngbin531 -> 0 bytes
-rw-r--r--images/emoji/1f560.pngbin552 -> 0 bytes
-rw-r--r--images/emoji/1f561.pngbin536 -> 0 bytes
-rw-r--r--images/emoji/1f562.pngbin531 -> 0 bytes
-rw-r--r--images/emoji/1f563.pngbin570 -> 0 bytes
-rw-r--r--images/emoji/1f564.pngbin576 -> 0 bytes
-rw-r--r--images/emoji/1f565.pngbin530 -> 0 bytes
-rw-r--r--images/emoji/1f566.pngbin583 -> 0 bytes
-rw-r--r--images/emoji/1f567.pngbin579 -> 0 bytes
-rw-r--r--images/emoji/1f56f.pngbin1250 -> 0 bytes
-rw-r--r--images/emoji/1f570.pngbin592 -> 0 bytes
-rw-r--r--images/emoji/1f573.pngbin1390 -> 0 bytes
-rw-r--r--images/emoji/1f574.pngbin914 -> 0 bytes
-rw-r--r--images/emoji/1f575-1f3fb.pngbin1639 -> 0 bytes
-rw-r--r--images/emoji/1f575-1f3fc.pngbin1636 -> 0 bytes
-rw-r--r--images/emoji/1f575-1f3fd.pngbin1647 -> 0 bytes
-rw-r--r--images/emoji/1f575-1f3fe.pngbin1639 -> 0 bytes
-rw-r--r--images/emoji/1f575-1f3ff.pngbin1639 -> 0 bytes
-rw-r--r--images/emoji/1f575.pngbin1650 -> 0 bytes
-rw-r--r--images/emoji/1f576.pngbin829 -> 0 bytes
-rw-r--r--images/emoji/1f577.pngbin1724 -> 0 bytes
-rw-r--r--images/emoji/1f578.pngbin929 -> 0 bytes
-rw-r--r--images/emoji/1f579.pngbin1039 -> 0 bytes
-rw-r--r--images/emoji/1f57a-1f3fb.pngbin1404 -> 0 bytes
-rw-r--r--images/emoji/1f57a-1f3fc.pngbin1402 -> 0 bytes
-rw-r--r--images/emoji/1f57a-1f3fd.pngbin1409 -> 0 bytes
-rw-r--r--images/emoji/1f57a-1f3fe.pngbin1421 -> 0 bytes
-rw-r--r--images/emoji/1f57a-1f3ff.pngbin1418 -> 0 bytes
-rw-r--r--images/emoji/1f57a.pngbin1400 -> 0 bytes
-rw-r--r--images/emoji/1f587.pngbin642 -> 0 bytes
-rw-r--r--images/emoji/1f58a.pngbin696 -> 0 bytes
-rw-r--r--images/emoji/1f58b.pngbin623 -> 0 bytes
-rw-r--r--images/emoji/1f58c.pngbin950 -> 0 bytes
-rw-r--r--images/emoji/1f58d.pngbin633 -> 0 bytes
-rw-r--r--images/emoji/1f590-1f3fb.pngbin1081 -> 0 bytes
-rw-r--r--images/emoji/1f590-1f3fc.pngbin1081 -> 0 bytes
-rw-r--r--images/emoji/1f590-1f3fd.pngbin1081 -> 0 bytes
-rw-r--r--images/emoji/1f590-1f3fe.pngbin1081 -> 0 bytes
-rw-r--r--images/emoji/1f590-1f3ff.pngbin1081 -> 0 bytes
-rw-r--r--images/emoji/1f590.pngbin1081 -> 0 bytes
-rw-r--r--images/emoji/1f595-1f3fb.pngbin892 -> 0 bytes
-rw-r--r--images/emoji/1f595-1f3fc.pngbin892 -> 0 bytes
-rw-r--r--images/emoji/1f595-1f3fd.pngbin892 -> 0 bytes
-rw-r--r--images/emoji/1f595-1f3fe.pngbin892 -> 0 bytes
-rw-r--r--images/emoji/1f595-1f3ff.pngbin892 -> 0 bytes
-rw-r--r--images/emoji/1f595.pngbin893 -> 0 bytes
-rw-r--r--images/emoji/1f596-1f3fb.pngbin1083 -> 0 bytes
-rw-r--r--images/emoji/1f596-1f3fc.pngbin1083 -> 0 bytes
-rw-r--r--images/emoji/1f596-1f3fd.pngbin1083 -> 0 bytes
-rw-r--r--images/emoji/1f596-1f3fe.pngbin1083 -> 0 bytes
-rw-r--r--images/emoji/1f596-1f3ff.pngbin1083 -> 0 bytes
-rw-r--r--images/emoji/1f596.pngbin1083 -> 0 bytes
-rw-r--r--images/emoji/1f5a4.pngbin435 -> 0 bytes
-rw-r--r--images/emoji/1f5a5.pngbin311 -> 0 bytes
-rw-r--r--images/emoji/1f5a8.pngbin926 -> 0 bytes
-rw-r--r--images/emoji/1f5b1.pngbin934 -> 0 bytes
-rw-r--r--images/emoji/1f5b2.pngbin892 -> 0 bytes
-rw-r--r--images/emoji/1f5bc.pngbin514 -> 0 bytes
-rw-r--r--images/emoji/1f5c2.pngbin810 -> 0 bytes
-rw-r--r--images/emoji/1f5c3.pngbin1523 -> 0 bytes
-rw-r--r--images/emoji/1f5c4.pngbin1420 -> 0 bytes
-rw-r--r--images/emoji/1f5d1.pngbin2414 -> 0 bytes
-rw-r--r--images/emoji/1f5d2.pngbin1377 -> 0 bytes
-rw-r--r--images/emoji/1f5d3.pngbin1491 -> 0 bytes
-rw-r--r--images/emoji/1f5dc.pngbin1614 -> 0 bytes
-rw-r--r--images/emoji/1f5dd.pngbin593 -> 0 bytes
-rw-r--r--images/emoji/1f5de.pngbin1046 -> 0 bytes
-rw-r--r--images/emoji/1f5e1.pngbin916 -> 0 bytes
-rw-r--r--images/emoji/1f5e3.pngbin531 -> 0 bytes
-rw-r--r--images/emoji/1f5e8.pngbin390 -> 0 bytes
-rw-r--r--images/emoji/1f5ef.pngbin551 -> 0 bytes
-rw-r--r--images/emoji/1f5f3.pngbin1355 -> 0 bytes
-rw-r--r--images/emoji/1f5fa.pngbin2352 -> 0 bytes
-rw-r--r--images/emoji/1f5fb.pngbin881 -> 0 bytes
-rw-r--r--images/emoji/1f5fc.pngbin765 -> 0 bytes
-rw-r--r--images/emoji/1f5fd.pngbin1145 -> 0 bytes
-rw-r--r--images/emoji/1f5fe.pngbin539 -> 0 bytes
-rw-r--r--images/emoji/1f5ff.pngbin1593 -> 0 bytes
-rw-r--r--images/emoji/1f600.pngbin810 -> 0 bytes
-rw-r--r--images/emoji/1f601.pngbin767 -> 0 bytes
-rw-r--r--images/emoji/1f602.pngbin1136 -> 0 bytes
-rw-r--r--images/emoji/1f603.pngbin686 -> 0 bytes
-rw-r--r--images/emoji/1f604.pngbin737 -> 0 bytes
-rw-r--r--images/emoji/1f605.pngbin851 -> 0 bytes
-rw-r--r--images/emoji/1f609.pngbin746 -> 0 bytes
-rw-r--r--images/emoji/1f60b.pngbin896 -> 0 bytes
-rw-r--r--images/emoji/1f60c.pngbin785 -> 0 bytes
-rw-r--r--images/emoji/1f60d.pngbin1069 -> 0 bytes
-rw-r--r--images/emoji/1f60e.pngbin824 -> 0 bytes
-rw-r--r--images/emoji/1f60f.pngbin775 -> 0 bytes
-rw-r--r--images/emoji/1f610.pngbin517 -> 0 bytes
-rw-r--r--images/emoji/1f611.pngbin438 -> 0 bytes
-rw-r--r--images/emoji/1f612.pngbin632 -> 0 bytes
-rw-r--r--images/emoji/1f613.pngbin861 -> 0 bytes
-rw-r--r--images/emoji/1f614.pngbin718 -> 0 bytes
-rw-r--r--images/emoji/1f615.pngbin647 -> 0 bytes
-rw-r--r--images/emoji/1f616.pngbin844 -> 0 bytes
-rw-r--r--images/emoji/1f617.pngbin738 -> 0 bytes
-rw-r--r--images/emoji/1f618.pngbin843 -> 0 bytes
-rw-r--r--images/emoji/1f619.pngbin648 -> 0 bytes
-rw-r--r--images/emoji/1f61a.pngbin888 -> 0 bytes
-rw-r--r--images/emoji/1f61b.pngbin752 -> 0 bytes
-rw-r--r--images/emoji/1f61d.pngbin867 -> 0 bytes
-rw-r--r--images/emoji/1f61f.pngbin715 -> 0 bytes
-rw-r--r--images/emoji/1f620.pngbin845 -> 0 bytes
-rw-r--r--images/emoji/1f621.pngbin845 -> 0 bytes
-rw-r--r--images/emoji/1f622.pngbin1123 -> 0 bytes
-rw-r--r--images/emoji/1f623.pngbin891 -> 0 bytes
-rw-r--r--images/emoji/1f624.pngbin1532 -> 0 bytes
-rw-r--r--images/emoji/1f625.pngbin835 -> 0 bytes
-rw-r--r--images/emoji/1f626.pngbin633 -> 0 bytes
-rw-r--r--images/emoji/1f627.pngbin821 -> 0 bytes
-rw-r--r--images/emoji/1f628.pngbin1002 -> 0 bytes
-rw-r--r--images/emoji/1f629.pngbin871 -> 0 bytes
-rw-r--r--images/emoji/1f62a.pngbin1185 -> 0 bytes
-rw-r--r--images/emoji/1f62b.pngbin1132 -> 0 bytes
-rw-r--r--images/emoji/1f62c.pngbin694 -> 0 bytes
-rw-r--r--images/emoji/1f62d.pngbin1241 -> 0 bytes
-rw-r--r--images/emoji/1f62f.pngbin634 -> 0 bytes
-rw-r--r--images/emoji/1f630.pngbin971 -> 0 bytes
-rw-r--r--images/emoji/1f631.pngbin1588 -> 0 bytes
-rw-r--r--images/emoji/1f632.pngbin862 -> 0 bytes
-rw-r--r--images/emoji/1f633.pngbin1127 -> 0 bytes
-rw-r--r--images/emoji/1f635.pngbin710 -> 0 bytes
-rw-r--r--images/emoji/1f636.pngbin465 -> 0 bytes
-rw-r--r--images/emoji/1f637.pngbin1323 -> 0 bytes
-rw-r--r--images/emoji/1f638.pngbin1407 -> 0 bytes
-rw-r--r--images/emoji/1f639.pngbin1633 -> 0 bytes
-rw-r--r--images/emoji/1f63a.pngbin1677 -> 0 bytes
-rw-r--r--images/emoji/1f63b.pngbin1513 -> 0 bytes
-rw-r--r--images/emoji/1f63c.pngbin1665 -> 0 bytes
-rw-r--r--images/emoji/1f63d.pngbin1469 -> 0 bytes
-rw-r--r--images/emoji/1f63e.pngbin1675 -> 0 bytes
-rw-r--r--images/emoji/1f63f.pngbin1876 -> 0 bytes
-rw-r--r--images/emoji/1f640.pngbin2120 -> 0 bytes
-rw-r--r--images/emoji/1f641.pngbin580 -> 0 bytes
-rw-r--r--images/emoji/1f642.pngbin600 -> 0 bytes
-rw-r--r--images/emoji/1f643.pngbin602 -> 0 bytes
-rw-r--r--images/emoji/1f644.pngbin743 -> 0 bytes
-rw-r--r--images/emoji/1f645-1f3fb.pngbin1768 -> 0 bytes
-rw-r--r--images/emoji/1f645-1f3fc.pngbin1756 -> 0 bytes
-rw-r--r--images/emoji/1f645-1f3fd.pngbin1766 -> 0 bytes
-rw-r--r--images/emoji/1f645-1f3fe.pngbin1786 -> 0 bytes
-rw-r--r--images/emoji/1f645-1f3ff.pngbin1786 -> 0 bytes
-rw-r--r--images/emoji/1f645.pngbin1751 -> 0 bytes
-rw-r--r--images/emoji/1f646-1f3fb.pngbin1702 -> 0 bytes
-rw-r--r--images/emoji/1f646-1f3fc.pngbin1695 -> 0 bytes
-rw-r--r--images/emoji/1f646-1f3fd.pngbin1699 -> 0 bytes
-rw-r--r--images/emoji/1f646-1f3fe.pngbin1692 -> 0 bytes
-rw-r--r--images/emoji/1f646-1f3ff.pngbin1702 -> 0 bytes
-rw-r--r--images/emoji/1f646.pngbin1702 -> 0 bytes
-rw-r--r--images/emoji/1f647-1f3fb.pngbin1396 -> 0 bytes
-rw-r--r--images/emoji/1f647-1f3fc.pngbin1396 -> 0 bytes
-rw-r--r--images/emoji/1f647-1f3fd.pngbin1396 -> 0 bytes
-rw-r--r--images/emoji/1f647-1f3fe.pngbin1396 -> 0 bytes
-rw-r--r--images/emoji/1f647-1f3ff.pngbin1396 -> 0 bytes
-rw-r--r--images/emoji/1f647.pngbin1396 -> 0 bytes
-rw-r--r--images/emoji/1f648.pngbin1227 -> 0 bytes
-rw-r--r--images/emoji/1f649.pngbin1210 -> 0 bytes
-rw-r--r--images/emoji/1f64a.pngbin1503 -> 0 bytes
-rw-r--r--images/emoji/1f64b-1f3fb.pngbin1678 -> 0 bytes
-rw-r--r--images/emoji/1f64b-1f3fc.pngbin1665 -> 0 bytes
-rw-r--r--images/emoji/1f64b-1f3fd.pngbin1661 -> 0 bytes
-rw-r--r--images/emoji/1f64b-1f3fe.pngbin1658 -> 0 bytes
-rw-r--r--images/emoji/1f64b-1f3ff.pngbin1661 -> 0 bytes
-rw-r--r--images/emoji/1f64b.pngbin1669 -> 0 bytes
-rw-r--r--images/emoji/1f64c-1f3fb.pngbin1098 -> 0 bytes
-rw-r--r--images/emoji/1f64c-1f3fc.pngbin1098 -> 0 bytes
-rw-r--r--images/emoji/1f64c-1f3fd.pngbin1098 -> 0 bytes
-rw-r--r--images/emoji/1f64c-1f3fe.pngbin1098 -> 0 bytes
-rw-r--r--images/emoji/1f64c-1f3ff.pngbin1098 -> 0 bytes
-rw-r--r--images/emoji/1f64c.pngbin1098 -> 0 bytes
-rw-r--r--images/emoji/1f64d-1f3fb.pngbin1141 -> 0 bytes
-rw-r--r--images/emoji/1f64d-1f3fc.pngbin1141 -> 0 bytes
-rw-r--r--images/emoji/1f64d-1f3fd.pngbin1141 -> 0 bytes
-rw-r--r--images/emoji/1f64d-1f3fe.pngbin1109 -> 0 bytes
-rw-r--r--images/emoji/1f64d-1f3ff.pngbin1114 -> 0 bytes
-rw-r--r--images/emoji/1f64d.pngbin1148 -> 0 bytes
-rw-r--r--images/emoji/1f64e-1f3fb.pngbin1309 -> 0 bytes
-rw-r--r--images/emoji/1f64e-1f3fc.pngbin1292 -> 0 bytes
-rw-r--r--images/emoji/1f64e-1f3fd.pngbin1305 -> 0 bytes
-rw-r--r--images/emoji/1f64e-1f3fe.pngbin1296 -> 0 bytes
-rw-r--r--images/emoji/1f64e-1f3ff.pngbin1303 -> 0 bytes
-rw-r--r--images/emoji/1f64e.pngbin1297 -> 0 bytes
-rw-r--r--images/emoji/1f64f-1f3fb.pngbin1131 -> 0 bytes
-rw-r--r--images/emoji/1f64f-1f3fc.pngbin1134 -> 0 bytes
-rw-r--r--images/emoji/1f64f-1f3fd.pngbin1137 -> 0 bytes
-rw-r--r--images/emoji/1f64f-1f3fe.pngbin1126 -> 0 bytes
-rw-r--r--images/emoji/1f64f-1f3ff.pngbin1117 -> 0 bytes
-rw-r--r--images/emoji/1f64f.pngbin1122 -> 0 bytes
-rw-r--r--images/emoji/1f680.pngbin1639 -> 0 bytes
-rw-r--r--images/emoji/1f681.pngbin1098 -> 0 bytes
-rw-r--r--images/emoji/1f682.pngbin1736 -> 0 bytes
-rw-r--r--images/emoji/1f683.pngbin847 -> 0 bytes
-rw-r--r--images/emoji/1f684.pngbin1538 -> 0 bytes
-rw-r--r--images/emoji/1f685.pngbin1450 -> 0 bytes
-rw-r--r--images/emoji/1f686.pngbin1501 -> 0 bytes
-rw-r--r--images/emoji/1f687.pngbin1020 -> 0 bytes
-rw-r--r--images/emoji/1f688.pngbin902 -> 0 bytes
-rw-r--r--images/emoji/1f689.pngbin1336 -> 0 bytes
-rw-r--r--images/emoji/1f68a.pngbin1065 -> 0 bytes
-rw-r--r--images/emoji/1f68b.pngbin1031 -> 0 bytes
-rw-r--r--images/emoji/1f68c.pngbin1086 -> 0 bytes
-rw-r--r--images/emoji/1f68d.pngbin964 -> 0 bytes
-rw-r--r--images/emoji/1f68e.pngbin1168 -> 0 bytes
-rw-r--r--images/emoji/1f68f.pngbin626 -> 0 bytes
-rw-r--r--images/emoji/1f690.pngbin1256 -> 0 bytes
-rw-r--r--images/emoji/1f691.pngbin1238 -> 0 bytes
-rw-r--r--images/emoji/1f692.pngbin1658 -> 0 bytes
-rw-r--r--images/emoji/1f693.pngbin1431 -> 0 bytes
-rw-r--r--images/emoji/1f694.pngbin1548 -> 0 bytes
-rw-r--r--images/emoji/1f695.pngbin1230 -> 0 bytes
-rw-r--r--images/emoji/1f696.pngbin1410 -> 0 bytes
-rw-r--r--images/emoji/1f697.pngbin1065 -> 0 bytes
-rw-r--r--images/emoji/1f698.pngbin1238 -> 0 bytes
-rw-r--r--images/emoji/1f699.pngbin1275 -> 0 bytes
-rw-r--r--images/emoji/1f69a.pngbin1367 -> 0 bytes
-rw-r--r--images/emoji/1f69b.pngbin1711 -> 0 bytes
-rw-r--r--images/emoji/1f69c.pngbin1192 -> 0 bytes
-rw-r--r--images/emoji/1f69d.pngbin1068 -> 0 bytes
-rw-r--r--images/emoji/1f69e.pngbin1320 -> 0 bytes
-rw-r--r--images/emoji/1f69f.pngbin927 -> 0 bytes
-rw-r--r--images/emoji/1f6a0.pngbin811 -> 0 bytes
-rw-r--r--images/emoji/1f6a1.pngbin759 -> 0 bytes
-rw-r--r--images/emoji/1f6a2.pngbin1405 -> 0 bytes
-rw-r--r--images/emoji/1f6a3-1f3fb.pngbin1972 -> 0 bytes
-rw-r--r--images/emoji/1f6a3-1f3fc.pngbin1972 -> 0 bytes
-rw-r--r--images/emoji/1f6a3-1f3fd.pngbin1967 -> 0 bytes
-rw-r--r--images/emoji/1f6a3-1f3fe.pngbin1974 -> 0 bytes
-rw-r--r--images/emoji/1f6a3-1f3ff.pngbin1971 -> 0 bytes
-rw-r--r--images/emoji/1f6a3.pngbin1963 -> 0 bytes
-rw-r--r--images/emoji/1f6a4.pngbin1255 -> 0 bytes
-rw-r--r--images/emoji/1f6a5.pngbin590 -> 0 bytes
-rw-r--r--images/emoji/1f6a6.pngbin752 -> 0 bytes
-rw-r--r--images/emoji/1f6a7.pngbin1083 -> 0 bytes
-rw-r--r--images/emoji/1f6a8.pngbin1969 -> 0 bytes
-rw-r--r--images/emoji/1f6a9.pngbin415 -> 0 bytes
-rw-r--r--images/emoji/1f6aa.pngbin1105 -> 0 bytes
-rw-r--r--images/emoji/1f6ab.pngbin555 -> 0 bytes
-rw-r--r--images/emoji/1f6ac.pngbin417 -> 0 bytes
-rw-r--r--images/emoji/1f6ad.pngbin1140 -> 0 bytes
-rw-r--r--images/emoji/1f6ae.pngbin650 -> 0 bytes
-rw-r--r--images/emoji/1f6af.pngbin1010 -> 0 bytes
-rw-r--r--images/emoji/1f6b0.pngbin633 -> 0 bytes
-rw-r--r--images/emoji/1f6b1.pngbin827 -> 0 bytes
-rw-r--r--images/emoji/1f6b2.pngbin1506 -> 0 bytes
-rw-r--r--images/emoji/1f6b3.pngbin998 -> 0 bytes
-rw-r--r--images/emoji/1f6b4-1f3fb.pngbin1860 -> 0 bytes
-rw-r--r--images/emoji/1f6b4-1f3fc.pngbin1866 -> 0 bytes
-rw-r--r--images/emoji/1f6b4-1f3fd.pngbin1851 -> 0 bytes
-rw-r--r--images/emoji/1f6b4-1f3fe.pngbin1852 -> 0 bytes
-rw-r--r--images/emoji/1f6b4-1f3ff.pngbin1840 -> 0 bytes
-rw-r--r--images/emoji/1f6b4.pngbin1911 -> 0 bytes
-rw-r--r--images/emoji/1f6b5-1f3fb.pngbin2294 -> 0 bytes
-rw-r--r--images/emoji/1f6b5-1f3fc.pngbin2298 -> 0 bytes
-rw-r--r--images/emoji/1f6b5-1f3fd.pngbin2284 -> 0 bytes
-rw-r--r--images/emoji/1f6b5-1f3fe.pngbin2288 -> 0 bytes
-rw-r--r--images/emoji/1f6b5-1f3ff.pngbin2281 -> 0 bytes
-rw-r--r--images/emoji/1f6b5.pngbin2288 -> 0 bytes
-rw-r--r--images/emoji/1f6b6-1f3fb.pngbin1084 -> 0 bytes
-rw-r--r--images/emoji/1f6b6-1f3fc.pngbin1084 -> 0 bytes
-rw-r--r--images/emoji/1f6b6-1f3fd.pngbin1066 -> 0 bytes
-rw-r--r--images/emoji/1f6b6-1f3fe.pngbin1075 -> 0 bytes
-rw-r--r--images/emoji/1f6b6-1f3ff.pngbin1065 -> 0 bytes
-rw-r--r--images/emoji/1f6b6.pngbin1082 -> 0 bytes
-rw-r--r--images/emoji/1f6b7.pngbin875 -> 0 bytes
-rw-r--r--images/emoji/1f6b8.pngbin778 -> 0 bytes
-rw-r--r--images/emoji/1f6b9.pngbin561 -> 0 bytes
-rw-r--r--images/emoji/1f6ba.pngbin577 -> 0 bytes
-rw-r--r--images/emoji/1f6bb.pngbin676 -> 0 bytes
-rw-r--r--images/emoji/1f6bc.pngbin665 -> 0 bytes
-rw-r--r--images/emoji/1f6bd.pngbin726 -> 0 bytes
-rw-r--r--images/emoji/1f6be.pngbin752 -> 0 bytes
-rw-r--r--images/emoji/1f6bf.pngbin2537 -> 0 bytes
-rw-r--r--images/emoji/1f6c0-1f3fb.pngbin1235 -> 0 bytes
-rw-r--r--images/emoji/1f6c0-1f3fc.pngbin1231 -> 0 bytes
-rw-r--r--images/emoji/1f6c0-1f3fd.pngbin1236 -> 0 bytes
-rw-r--r--images/emoji/1f6c0-1f3fe.pngbin1252 -> 0 bytes
-rw-r--r--images/emoji/1f6c0-1f3ff.pngbin1239 -> 0 bytes
-rw-r--r--images/emoji/1f6c0.pngbin1238 -> 0 bytes
-rw-r--r--images/emoji/1f6c1.pngbin767 -> 0 bytes
-rw-r--r--images/emoji/1f6c2.pngbin683 -> 0 bytes
-rw-r--r--images/emoji/1f6c3.pngbin648 -> 0 bytes
-rw-r--r--images/emoji/1f6c4.pngbin490 -> 0 bytes
-rw-r--r--images/emoji/1f6c5.pngbin576 -> 0 bytes
-rw-r--r--images/emoji/1f6cb.pngbin1362 -> 0 bytes
-rw-r--r--images/emoji/1f6cc.pngbin926 -> 0 bytes
-rw-r--r--images/emoji/1f6cd.pngbin1234 -> 0 bytes
-rw-r--r--images/emoji/1f6ce.pngbin891 -> 0 bytes
-rw-r--r--images/emoji/1f6cf.pngbin1573 -> 0 bytes
-rw-r--r--images/emoji/1f6d0.pngbin487 -> 0 bytes
-rw-r--r--images/emoji/1f6d1.pngbin260 -> 0 bytes
-rw-r--r--images/emoji/1f6d2.pngbin1072 -> 0 bytes
-rw-r--r--images/emoji/1f6e0.pngbin1225 -> 0 bytes
-rw-r--r--images/emoji/1f6e1.pngbin1602 -> 0 bytes
-rw-r--r--images/emoji/1f6e2.pngbin674 -> 0 bytes
-rw-r--r--images/emoji/1f6e3.pngbin1102 -> 0 bytes
-rw-r--r--images/emoji/1f6e4.pngbin1552 -> 0 bytes
-rw-r--r--images/emoji/1f6e5.pngbin990 -> 0 bytes
-rw-r--r--images/emoji/1f6e9.pngbin1229 -> 0 bytes
-rw-r--r--images/emoji/1f6eb.pngbin1111 -> 0 bytes
-rw-r--r--images/emoji/1f6ec.pngbin1101 -> 0 bytes
-rw-r--r--images/emoji/1f6f0.pngbin762 -> 0 bytes
-rw-r--r--images/emoji/1f6f3.pngbin2272 -> 0 bytes
-rw-r--r--images/emoji/1f6f4.pngbin1228 -> 0 bytes
-rw-r--r--images/emoji/1f6f5.pngbin1207 -> 0 bytes
-rw-r--r--images/emoji/1f6f6.pngbin1244 -> 0 bytes
-rw-r--r--images/emoji/1f910.pngbin722 -> 0 bytes
-rw-r--r--images/emoji/1f911.pngbin967 -> 0 bytes
-rw-r--r--images/emoji/1f912.pngbin1507 -> 0 bytes
-rw-r--r--images/emoji/1f913.pngbin975 -> 0 bytes
-rw-r--r--images/emoji/1f914.pngbin1345 -> 0 bytes
-rw-r--r--images/emoji/1f915.pngbin1201 -> 0 bytes
-rw-r--r--images/emoji/1f916.pngbin1228 -> 0 bytes
-rw-r--r--images/emoji/1f917.pngbin1427 -> 0 bytes
-rw-r--r--images/emoji/1f918-1f3fb.pngbin894 -> 0 bytes
-rw-r--r--images/emoji/1f918-1f3fc.pngbin888 -> 0 bytes
-rw-r--r--images/emoji/1f918-1f3fd.pngbin894 -> 0 bytes
-rw-r--r--images/emoji/1f918-1f3fe.pngbin888 -> 0 bytes
-rw-r--r--images/emoji/1f918-1f3ff.pngbin894 -> 0 bytes
-rw-r--r--images/emoji/1f918.pngbin894 -> 0 bytes
-rw-r--r--images/emoji/1f919-1f3fb.pngbin893 -> 0 bytes
-rw-r--r--images/emoji/1f919-1f3fc.pngbin891 -> 0 bytes
-rw-r--r--images/emoji/1f919-1f3fd.pngbin891 -> 0 bytes
-rw-r--r--images/emoji/1f919-1f3fe.pngbin891 -> 0 bytes
-rw-r--r--images/emoji/1f919-1f3ff.pngbin893 -> 0 bytes
-rw-r--r--images/emoji/1f919.pngbin894 -> 0 bytes
-rw-r--r--images/emoji/1f91a-1f3fb.pngbin848 -> 0 bytes
-rw-r--r--images/emoji/1f91a-1f3fc.pngbin848 -> 0 bytes
-rw-r--r--images/emoji/1f91a-1f3fd.pngbin848 -> 0 bytes
-rw-r--r--images/emoji/1f91a-1f3fe.pngbin848 -> 0 bytes
-rw-r--r--images/emoji/1f91a-1f3ff.pngbin848 -> 0 bytes
-rw-r--r--images/emoji/1f91a.pngbin848 -> 0 bytes
-rw-r--r--images/emoji/1f91b-1f3fb.pngbin960 -> 0 bytes
-rw-r--r--images/emoji/1f91b-1f3fc.pngbin972 -> 0 bytes
-rw-r--r--images/emoji/1f91b-1f3fd.pngbin960 -> 0 bytes
-rw-r--r--images/emoji/1f91b-1f3fe.pngbin960 -> 0 bytes
-rw-r--r--images/emoji/1f91b-1f3ff.pngbin976 -> 0 bytes
-rw-r--r--images/emoji/1f91b.pngbin972 -> 0 bytes
-rw-r--r--images/emoji/1f91c-1f3fb.pngbin964 -> 0 bytes
-rw-r--r--images/emoji/1f91c-1f3fc.pngbin964 -> 0 bytes
-rw-r--r--images/emoji/1f91c-1f3fd.pngbin964 -> 0 bytes
-rw-r--r--images/emoji/1f91c-1f3fe.pngbin964 -> 0 bytes
-rw-r--r--images/emoji/1f91c-1f3ff.pngbin964 -> 0 bytes
-rw-r--r--images/emoji/1f91c.pngbin975 -> 0 bytes
-rw-r--r--images/emoji/1f91d-1f3fb.pngbin1384 -> 0 bytes
-rw-r--r--images/emoji/1f91d-1f3fc.pngbin1384 -> 0 bytes
-rw-r--r--images/emoji/1f91d-1f3fd.pngbin1384 -> 0 bytes
-rw-r--r--images/emoji/1f91d-1f3fe.pngbin1384 -> 0 bytes
-rw-r--r--images/emoji/1f91d-1f3ff.pngbin1384 -> 0 bytes
-rw-r--r--images/emoji/1f91d.pngbin1369 -> 0 bytes
-rw-r--r--images/emoji/1f91e-1f3fb.pngbin1047 -> 0 bytes
-rw-r--r--images/emoji/1f91e-1f3fc.pngbin1050 -> 0 bytes
-rw-r--r--images/emoji/1f91e-1f3fd.pngbin1050 -> 0 bytes
-rw-r--r--images/emoji/1f91e-1f3fe.pngbin1046 -> 0 bytes
-rw-r--r--images/emoji/1f91e-1f3ff.pngbin1050 -> 0 bytes
-rw-r--r--images/emoji/1f91e.pngbin1050 -> 0 bytes
-rw-r--r--images/emoji/1f920.pngbin1361 -> 0 bytes
-rw-r--r--images/emoji/1f921.pngbin1820 -> 0 bytes
-rw-r--r--images/emoji/1f922.pngbin965 -> 0 bytes
-rw-r--r--images/emoji/1f923.pngbin1760 -> 0 bytes
-rw-r--r--images/emoji/1f924.pngbin1049 -> 0 bytes
-rw-r--r--images/emoji/1f925.pngbin1103 -> 0 bytes
-rw-r--r--images/emoji/1f926-1f3fb.pngbin1563 -> 0 bytes
-rw-r--r--images/emoji/1f926-1f3fc.pngbin1548 -> 0 bytes
-rw-r--r--images/emoji/1f926-1f3fd.pngbin1550 -> 0 bytes
-rw-r--r--images/emoji/1f926-1f3fe.pngbin1553 -> 0 bytes
-rw-r--r--images/emoji/1f926-1f3ff.pngbin1532 -> 0 bytes
-rw-r--r--images/emoji/1f926.pngbin1523 -> 0 bytes
-rw-r--r--images/emoji/1f927.pngbin1292 -> 0 bytes
-rw-r--r--images/emoji/1f930-1f3fb.pngbin1255 -> 0 bytes
-rw-r--r--images/emoji/1f930-1f3fc.pngbin1246 -> 0 bytes
-rw-r--r--images/emoji/1f930-1f3fd.pngbin1237 -> 0 bytes
-rw-r--r--images/emoji/1f930-1f3fe.pngbin1246 -> 0 bytes
-rw-r--r--images/emoji/1f930-1f3ff.pngbin1235 -> 0 bytes
-rw-r--r--images/emoji/1f930.pngbin1252 -> 0 bytes
-rw-r--r--images/emoji/1f933-1f3fb.pngbin1166 -> 0 bytes
-rw-r--r--images/emoji/1f933-1f3fc.pngbin1167 -> 0 bytes
-rw-r--r--images/emoji/1f933-1f3fd.pngbin1154 -> 0 bytes
-rw-r--r--images/emoji/1f933-1f3fe.pngbin1153 -> 0 bytes
-rw-r--r--images/emoji/1f933-1f3ff.pngbin1148 -> 0 bytes
-rw-r--r--images/emoji/1f933.pngbin1160 -> 0 bytes
-rw-r--r--images/emoji/1f934-1f3fb.pngbin1622 -> 0 bytes
-rw-r--r--images/emoji/1f934-1f3fc.pngbin1621 -> 0 bytes
-rw-r--r--images/emoji/1f934-1f3fd.pngbin1623 -> 0 bytes
-rw-r--r--images/emoji/1f934-1f3fe.pngbin1619 -> 0 bytes
-rw-r--r--images/emoji/1f934-1f3ff.pngbin1616 -> 0 bytes
-rw-r--r--images/emoji/1f934.pngbin1616 -> 0 bytes
-rw-r--r--images/emoji/1f935-1f3fb.pngbin1307 -> 0 bytes
-rw-r--r--images/emoji/1f935-1f3fc.pngbin1307 -> 0 bytes
-rw-r--r--images/emoji/1f935-1f3fd.pngbin1307 -> 0 bytes
-rw-r--r--images/emoji/1f935-1f3fe.pngbin1307 -> 0 bytes
-rw-r--r--images/emoji/1f935-1f3ff.pngbin1302 -> 0 bytes
-rw-r--r--images/emoji/1f935.pngbin1307 -> 0 bytes
-rw-r--r--images/emoji/1f936-1f3fb.pngbin1999 -> 0 bytes
-rw-r--r--images/emoji/1f936-1f3fc.pngbin2006 -> 0 bytes
-rw-r--r--images/emoji/1f936-1f3fd.pngbin2018 -> 0 bytes
-rw-r--r--images/emoji/1f936-1f3fe.pngbin2016 -> 0 bytes
-rw-r--r--images/emoji/1f936-1f3ff.pngbin2016 -> 0 bytes
-rw-r--r--images/emoji/1f936.pngbin2206 -> 0 bytes
-rw-r--r--images/emoji/1f937-1f3fb.pngbin1676 -> 0 bytes
-rw-r--r--images/emoji/1f937-1f3fc.pngbin1675 -> 0 bytes
-rw-r--r--images/emoji/1f937-1f3fd.pngbin1679 -> 0 bytes
-rw-r--r--images/emoji/1f937-1f3fe.pngbin1641 -> 0 bytes
-rw-r--r--images/emoji/1f937-1f3ff.pngbin1635 -> 0 bytes
-rw-r--r--images/emoji/1f937.pngbin1671 -> 0 bytes
-rw-r--r--images/emoji/1f938-1f3fb.pngbin1234 -> 0 bytes
-rw-r--r--images/emoji/1f938-1f3fc.pngbin1235 -> 0 bytes
-rw-r--r--images/emoji/1f938-1f3fd.pngbin1229 -> 0 bytes
-rw-r--r--images/emoji/1f938-1f3fe.pngbin1227 -> 0 bytes
-rw-r--r--images/emoji/1f938-1f3ff.pngbin1214 -> 0 bytes
-rw-r--r--images/emoji/1f938.pngbin1233 -> 0 bytes
-rw-r--r--images/emoji/1f939-1f3fb.pngbin1171 -> 0 bytes
-rw-r--r--images/emoji/1f939-1f3fc.pngbin1160 -> 0 bytes
-rw-r--r--images/emoji/1f939-1f3fd.pngbin1170 -> 0 bytes
-rw-r--r--images/emoji/1f939-1f3fe.pngbin1167 -> 0 bytes
-rw-r--r--images/emoji/1f939-1f3ff.pngbin1161 -> 0 bytes
-rw-r--r--images/emoji/1f939.pngbin1165 -> 0 bytes
-rw-r--r--images/emoji/1f93a.pngbin1871 -> 0 bytes
-rw-r--r--images/emoji/1f93b-1f3fb.pngbin2045 -> 0 bytes
-rw-r--r--images/emoji/1f93b-1f3fc.pngbin2049 -> 0 bytes
-rw-r--r--images/emoji/1f93b-1f3fd.pngbin2039 -> 0 bytes
-rw-r--r--images/emoji/1f93b-1f3fe.pngbin2042 -> 0 bytes
-rw-r--r--images/emoji/1f93b-1f3ff.pngbin2035 -> 0 bytes
-rw-r--r--images/emoji/1f93b.pngbin2556 -> 0 bytes
-rw-r--r--images/emoji/1f93c-1f3fb.pngbin2563 -> 0 bytes
-rw-r--r--images/emoji/1f93c-1f3fc.pngbin2553 -> 0 bytes
-rw-r--r--images/emoji/1f93c-1f3fd.pngbin2541 -> 0 bytes
-rw-r--r--images/emoji/1f93c-1f3fe.pngbin2553 -> 0 bytes
-rw-r--r--images/emoji/1f93c-1f3ff.pngbin2542 -> 0 bytes
-rw-r--r--images/emoji/1f93c.pngbin1575 -> 0 bytes
-rw-r--r--images/emoji/1f93d-1f3fb.pngbin1758 -> 0 bytes
-rw-r--r--images/emoji/1f93d-1f3fc.pngbin1757 -> 0 bytes
-rw-r--r--images/emoji/1f93d-1f3fd.pngbin1760 -> 0 bytes
-rw-r--r--images/emoji/1f93d-1f3fe.pngbin1749 -> 0 bytes
-rw-r--r--images/emoji/1f93d-1f3ff.pngbin1749 -> 0 bytes
-rw-r--r--images/emoji/1f93d.pngbin1412 -> 0 bytes
-rw-r--r--images/emoji/1f93e-1f3fb.pngbin1646 -> 0 bytes
-rw-r--r--images/emoji/1f93e-1f3fc.pngbin1629 -> 0 bytes
-rw-r--r--images/emoji/1f93e-1f3fd.pngbin1639 -> 0 bytes
-rw-r--r--images/emoji/1f93e-1f3fe.pngbin1634 -> 0 bytes
-rw-r--r--images/emoji/1f93e-1f3ff.pngbin1606 -> 0 bytes
-rw-r--r--images/emoji/1f93e.pngbin1755 -> 0 bytes
-rw-r--r--images/emoji/1f93f.pngbin1636 -> 0 bytes
-rw-r--r--images/emoji/1f940.pngbin1349 -> 0 bytes
-rw-r--r--images/emoji/1f942.pngbin1986 -> 0 bytes
-rw-r--r--images/emoji/1f943.pngbin2312 -> 0 bytes
-rw-r--r--images/emoji/1f944.pngbin700 -> 0 bytes
-rw-r--r--images/emoji/1f945.pngbin1244 -> 0 bytes
-rw-r--r--images/emoji/1f946.pngbin828 -> 0 bytes
-rw-r--r--images/emoji/1f947.pngbin1421 -> 0 bytes
-rw-r--r--images/emoji/1f948.pngbin1514 -> 0 bytes
-rw-r--r--images/emoji/1f949.pngbin1531 -> 0 bytes
-rw-r--r--images/emoji/1f950.pngbin1315 -> 0 bytes
-rw-r--r--images/emoji/1f951.pngbin1523 -> 0 bytes
-rw-r--r--images/emoji/1f952.pngbin1358 -> 0 bytes
-rw-r--r--images/emoji/1f953.pngbin2148 -> 0 bytes
-rw-r--r--images/emoji/1f954.pngbin1247 -> 0 bytes
-rw-r--r--images/emoji/1f955.pngbin1236 -> 0 bytes
-rw-r--r--images/emoji/1f956.pngbin1556 -> 0 bytes
-rw-r--r--images/emoji/1f957.pngbin2398 -> 0 bytes
-rw-r--r--images/emoji/1f958.pngbin1738 -> 0 bytes
-rw-r--r--images/emoji/1f959.pngbin2160 -> 0 bytes
-rw-r--r--images/emoji/1f95a.pngbin710 -> 0 bytes
-rw-r--r--images/emoji/1f95b.pngbin1224 -> 0 bytes
-rw-r--r--images/emoji/1f95c.pngbin3266 -> 0 bytes
-rw-r--r--images/emoji/1f95d.pngbin1896 -> 0 bytes
-rw-r--r--images/emoji/1f95e.pngbin3661 -> 0 bytes
-rw-r--r--images/emoji/1f960.pngbin2051 -> 0 bytes
-rw-r--r--images/emoji/1f961.pngbin1344 -> 0 bytes
-rw-r--r--images/emoji/1f980.pngbin1488 -> 0 bytes
-rw-r--r--images/emoji/1f981.pngbin1728 -> 0 bytes
-rw-r--r--images/emoji/1f982.pngbin1503 -> 0 bytes
-rw-r--r--images/emoji/1f983.pngbin1240 -> 0 bytes
-rw-r--r--images/emoji/1f984.pngbin2107 -> 0 bytes
-rw-r--r--images/emoji/1f985.pngbin2222 -> 0 bytes
-rw-r--r--images/emoji/1f986.pngbin1729 -> 0 bytes
-rw-r--r--images/emoji/1f987.pngbin1194 -> 0 bytes
-rw-r--r--images/emoji/1f988.pngbin1811 -> 0 bytes
-rw-r--r--images/emoji/1f989.pngbin2046 -> 0 bytes
-rw-r--r--images/emoji/1f98a.pngbin1557 -> 0 bytes
-rw-r--r--images/emoji/1f98b.pngbin1981 -> 0 bytes
-rw-r--r--images/emoji/1f98c.pngbin1608 -> 0 bytes
-rw-r--r--images/emoji/1f98d.pngbin1096 -> 0 bytes
-rw-r--r--images/emoji/1f98e.pngbin1709 -> 0 bytes
-rw-r--r--images/emoji/1f98f.pngbin1558 -> 0 bytes
-rw-r--r--images/emoji/1f990.pngbin1376 -> 0 bytes
-rw-r--r--images/emoji/1f991.pngbin1395 -> 0 bytes
-rw-r--r--images/emoji/1f9c0.pngbin1697 -> 0 bytes
-rw-r--r--images/emoji/203c.pngbin390 -> 0 bytes
-rw-r--r--images/emoji/2049.pngbin601 -> 0 bytes
-rw-r--r--images/emoji/2122.pngbin300 -> 0 bytes
-rw-r--r--images/emoji/2139.pngbin506 -> 0 bytes
-rw-r--r--images/emoji/2194.pngbin495 -> 0 bytes
-rw-r--r--images/emoji/2195.pngbin474 -> 0 bytes
-rw-r--r--images/emoji/2196.pngbin521 -> 0 bytes
-rw-r--r--images/emoji/2197.pngbin524 -> 0 bytes
-rw-r--r--images/emoji/2198.pngbin526 -> 0 bytes
-rw-r--r--images/emoji/2199.pngbin520 -> 0 bytes
-rw-r--r--images/emoji/21a9.pngbin643 -> 0 bytes
-rw-r--r--images/emoji/21aa.pngbin644 -> 0 bytes
-rw-r--r--images/emoji/231a.pngbin785 -> 0 bytes
-rw-r--r--images/emoji/231b.pngbin800 -> 0 bytes
-rw-r--r--images/emoji/2328.pngbin429 -> 0 bytes
-rw-r--r--images/emoji/23cf.pngbin548 -> 0 bytes
-rw-r--r--images/emoji/23e9.pngbin523 -> 0 bytes
-rw-r--r--images/emoji/23ea.pngbin523 -> 0 bytes
-rw-r--r--images/emoji/23eb.pngbin535 -> 0 bytes
-rw-r--r--images/emoji/23ec.pngbin543 -> 0 bytes
-rw-r--r--images/emoji/23ed.pngbin551 -> 0 bytes
-rw-r--r--images/emoji/23ee.pngbin549 -> 0 bytes
-rw-r--r--images/emoji/23ef.pngbin509 -> 0 bytes
-rw-r--r--images/emoji/23f0.pngbin1044 -> 0 bytes
-rw-r--r--images/emoji/23f1.pngbin1330 -> 0 bytes
-rw-r--r--images/emoji/23f2.pngbin1897 -> 0 bytes
-rw-r--r--images/emoji/23f3.pngbin847 -> 0 bytes
-rw-r--r--images/emoji/23f8.pngbin395 -> 0 bytes
-rw-r--r--images/emoji/23f9.pngbin385 -> 0 bytes
-rw-r--r--images/emoji/23fa.pngbin475 -> 0 bytes
-rw-r--r--images/emoji/24c2.pngbin500 -> 0 bytes
-rw-r--r--images/emoji/25aa.pngbin108 -> 0 bytes
-rw-r--r--images/emoji/25ab.pngbin108 -> 0 bytes
-rw-r--r--images/emoji/25b6.pngbin429 -> 0 bytes
-rw-r--r--images/emoji/25c0.pngbin429 -> 0 bytes
-rw-r--r--images/emoji/25fb.pngbin108 -> 0 bytes
-rw-r--r--images/emoji/25fc.pngbin108 -> 0 bytes
-rw-r--r--images/emoji/25fd.pngbin110 -> 0 bytes
-rw-r--r--images/emoji/25fe.pngbin110 -> 0 bytes
-rw-r--r--images/emoji/2600.pngbin746 -> 0 bytes
-rw-r--r--images/emoji/2601.pngbin626 -> 0 bytes
-rw-r--r--images/emoji/2602.pngbin897 -> 0 bytes
-rw-r--r--images/emoji/2603.pngbin2176 -> 0 bytes
-rw-r--r--images/emoji/2604.pngbin1821 -> 0 bytes
-rw-r--r--images/emoji/260e.pngbin1761 -> 0 bytes
-rw-r--r--images/emoji/2611.pngbin639 -> 0 bytes
-rw-r--r--images/emoji/2614.pngbin1229 -> 0 bytes
-rw-r--r--images/emoji/2615.pngbin1679 -> 0 bytes
-rw-r--r--images/emoji/2618.pngbin1023 -> 0 bytes
-rw-r--r--images/emoji/261d-1f3fb.pngbin820 -> 0 bytes
-rw-r--r--images/emoji/261d-1f3fc.pngbin820 -> 0 bytes
-rw-r--r--images/emoji/261d-1f3fd.pngbin820 -> 0 bytes
-rw-r--r--images/emoji/261d-1f3fe.pngbin820 -> 0 bytes
-rw-r--r--images/emoji/261d-1f3ff.pngbin820 -> 0 bytes
-rw-r--r--images/emoji/261d.pngbin819 -> 0 bytes
-rw-r--r--images/emoji/2620.pngbin726 -> 0 bytes
-rw-r--r--images/emoji/2622.pngbin858 -> 0 bytes
-rw-r--r--images/emoji/2623.pngbin794 -> 0 bytes
-rw-r--r--images/emoji/2626.pngbin239 -> 0 bytes
-rw-r--r--images/emoji/262a.pngbin490 -> 0 bytes
-rw-r--r--images/emoji/262e.pngbin933 -> 0 bytes
-rw-r--r--images/emoji/262f.pngbin776 -> 0 bytes
-rw-r--r--images/emoji/2638.pngbin666 -> 0 bytes
-rw-r--r--images/emoji/2639.pngbin589 -> 0 bytes
-rw-r--r--images/emoji/263a.pngbin636 -> 0 bytes
-rw-r--r--images/emoji/2648.pngbin711 -> 0 bytes
-rw-r--r--images/emoji/2649.pngbin701 -> 0 bytes
-rw-r--r--images/emoji/264a.pngbin547 -> 0 bytes
-rw-r--r--images/emoji/264b.pngbin729 -> 0 bytes
-rw-r--r--images/emoji/264c.pngbin745 -> 0 bytes
-rw-r--r--images/emoji/264d.pngbin618 -> 0 bytes
-rw-r--r--images/emoji/264e.pngbin657 -> 0 bytes
-rw-r--r--images/emoji/264f.pngbin612 -> 0 bytes
-rw-r--r--images/emoji/2650.pngbin602 -> 0 bytes
-rw-r--r--images/emoji/2651.pngbin688 -> 0 bytes
-rw-r--r--images/emoji/2652.pngbin648 -> 0 bytes
-rw-r--r--images/emoji/2653.pngbin678 -> 0 bytes
-rw-r--r--images/emoji/2660.pngbin454 -> 0 bytes
-rw-r--r--images/emoji/2663.pngbin458 -> 0 bytes
-rw-r--r--images/emoji/2666.pngbin247 -> 0 bytes
-rw-r--r--images/emoji/2668.pngbin733 -> 0 bytes
-rw-r--r--images/emoji/267b.pngbin914 -> 0 bytes
-rw-r--r--images/emoji/267f.pngbin683 -> 0 bytes
-rw-r--r--images/emoji/2692.pngbin1068 -> 0 bytes
-rw-r--r--images/emoji/2693.pngbin779 -> 0 bytes
-rw-r--r--images/emoji/2694.pngbin1591 -> 0 bytes
-rw-r--r--images/emoji/2696.pngbin1181 -> 0 bytes
-rw-r--r--images/emoji/2697.pngbin953 -> 0 bytes
-rw-r--r--images/emoji/2699.pngbin747 -> 0 bytes
-rw-r--r--images/emoji/269b.pngbin912 -> 0 bytes
-rw-r--r--images/emoji/269c.pngbin632 -> 0 bytes
-rw-r--r--images/emoji/26a0.pngbin565 -> 0 bytes
-rw-r--r--images/emoji/26a1.pngbin413 -> 0 bytes
-rw-r--r--images/emoji/26aa.pngbin351 -> 0 bytes
-rw-r--r--images/emoji/26ab.pngbin374 -> 0 bytes
-rw-r--r--images/emoji/26b0.pngbin2195 -> 0 bytes
-rw-r--r--images/emoji/26b1.pngbin742 -> 0 bytes
-rw-r--r--images/emoji/26bd.pngbin1034 -> 0 bytes
-rw-r--r--images/emoji/26be.pngbin1185 -> 0 bytes
-rw-r--r--images/emoji/26c4.pngbin1481 -> 0 bytes
-rw-r--r--images/emoji/26c5.pngbin977 -> 0 bytes
-rw-r--r--images/emoji/26c8.pngbin1020 -> 0 bytes
-rw-r--r--images/emoji/26ce.pngbin723 -> 0 bytes
-rw-r--r--images/emoji/26cf.pngbin1023 -> 0 bytes
-rw-r--r--images/emoji/26d1.pngbin1014 -> 0 bytes
-rw-r--r--images/emoji/26d3.pngbin708 -> 0 bytes
-rw-r--r--images/emoji/26d4.pngbin377 -> 0 bytes
-rw-r--r--images/emoji/26e9.pngbin579 -> 0 bytes
-rw-r--r--images/emoji/26ea.pngbin1302 -> 0 bytes
-rw-r--r--images/emoji/26f0.pngbin1409 -> 0 bytes
-rw-r--r--images/emoji/26f1.pngbin1488 -> 0 bytes
-rw-r--r--images/emoji/26f2.pngbin1768 -> 0 bytes
-rw-r--r--images/emoji/26f3.pngbin823 -> 0 bytes
-rw-r--r--images/emoji/26f4.pngbin528 -> 0 bytes
-rw-r--r--images/emoji/26f5.pngbin1274 -> 0 bytes
-rw-r--r--images/emoji/26f7.pngbin1539 -> 0 bytes
-rw-r--r--images/emoji/26f8.pngbin1576 -> 0 bytes
-rw-r--r--images/emoji/26f9-1f3fb.pngbin1493 -> 0 bytes
-rw-r--r--images/emoji/26f9-1f3fc.pngbin1493 -> 0 bytes
-rw-r--r--images/emoji/26f9-1f3fd.pngbin1492 -> 0 bytes
-rw-r--r--images/emoji/26f9-1f3fe.pngbin1494 -> 0 bytes
-rw-r--r--images/emoji/26f9-1f3ff.pngbin1479 -> 0 bytes
-rw-r--r--images/emoji/26f9.pngbin1493 -> 0 bytes
-rw-r--r--images/emoji/26fa.pngbin1684 -> 0 bytes
-rw-r--r--images/emoji/26fd.pngbin864 -> 0 bytes
-rw-r--r--images/emoji/2702.pngbin937 -> 0 bytes
-rw-r--r--images/emoji/2705.pngbin547 -> 0 bytes
-rw-r--r--images/emoji/2708.pngbin1152 -> 0 bytes
-rw-r--r--images/emoji/2709.pngbin916 -> 0 bytes
-rw-r--r--images/emoji/270a-1f3fb.pngbin1014 -> 0 bytes
-rw-r--r--images/emoji/270a-1f3fc.pngbin1014 -> 0 bytes
-rw-r--r--images/emoji/270a-1f3fd.pngbin1014 -> 0 bytes
-rw-r--r--images/emoji/270a-1f3fe.pngbin1014 -> 0 bytes
-rw-r--r--images/emoji/270a-1f3ff.pngbin1014 -> 0 bytes
-rw-r--r--images/emoji/270a.pngbin1014 -> 0 bytes
-rw-r--r--images/emoji/270b-1f3fb.pngbin791 -> 0 bytes
-rw-r--r--images/emoji/270b-1f3fc.pngbin791 -> 0 bytes
-rw-r--r--images/emoji/270b-1f3fd.pngbin791 -> 0 bytes
-rw-r--r--images/emoji/270b-1f3fe.pngbin791 -> 0 bytes
-rw-r--r--images/emoji/270b-1f3ff.pngbin791 -> 0 bytes
-rw-r--r--images/emoji/270b.pngbin791 -> 0 bytes
-rw-r--r--images/emoji/270c-1f3fb.pngbin1009 -> 0 bytes
-rw-r--r--images/emoji/270c-1f3fc.pngbin1009 -> 0 bytes
-rw-r--r--images/emoji/270c-1f3fd.pngbin1009 -> 0 bytes
-rw-r--r--images/emoji/270c-1f3fe.pngbin1009 -> 0 bytes
-rw-r--r--images/emoji/270c-1f3ff.pngbin1009 -> 0 bytes
-rw-r--r--images/emoji/270c.pngbin1009 -> 0 bytes
-rw-r--r--images/emoji/270d-1f3fb.pngbin988 -> 0 bytes
-rw-r--r--images/emoji/270d-1f3fc.pngbin987 -> 0 bytes
-rw-r--r--images/emoji/270d-1f3fd.pngbin977 -> 0 bytes
-rw-r--r--images/emoji/270d-1f3fe.pngbin973 -> 0 bytes
-rw-r--r--images/emoji/270d-1f3ff.pngbin970 -> 0 bytes
-rw-r--r--images/emoji/270d.pngbin1001 -> 0 bytes
-rw-r--r--images/emoji/270f.pngbin654 -> 0 bytes
-rw-r--r--images/emoji/2712.pngbin620 -> 0 bytes
-rw-r--r--images/emoji/2714.pngbin438 -> 0 bytes
-rw-r--r--images/emoji/2716.pngbin298 -> 0 bytes
-rw-r--r--images/emoji/271d.pngbin408 -> 0 bytes
-rw-r--r--images/emoji/2721.pngbin491 -> 0 bytes
-rw-r--r--images/emoji/2728.pngbin651 -> 0 bytes
-rw-r--r--images/emoji/2733.pngbin493 -> 0 bytes
-rw-r--r--images/emoji/2734.pngbin493 -> 0 bytes
-rw-r--r--images/emoji/2744.pngbin691 -> 0 bytes
-rw-r--r--images/emoji/2747.pngbin663 -> 0 bytes
-rw-r--r--images/emoji/274c.pngbin298 -> 0 bytes
-rw-r--r--images/emoji/274e.pngbin370 -> 0 bytes
-rw-r--r--images/emoji/2753.pngbin449 -> 0 bytes
-rw-r--r--images/emoji/2754.pngbin449 -> 0 bytes
-rw-r--r--images/emoji/2755.pngbin354 -> 0 bytes
-rw-r--r--images/emoji/2757.pngbin354 -> 0 bytes
-rw-r--r--images/emoji/2763.pngbin471 -> 0 bytes
-rw-r--r--images/emoji/2764.pngbin435 -> 0 bytes
-rw-r--r--images/emoji/2795.pngbin115 -> 0 bytes
-rw-r--r--images/emoji/2796.pngbin108 -> 0 bytes
-rw-r--r--images/emoji/2797.pngbin204 -> 0 bytes
-rw-r--r--images/emoji/27a1.pngbin468 -> 0 bytes
-rw-r--r--images/emoji/27b0.pngbin545 -> 0 bytes
-rw-r--r--images/emoji/27bf.pngbin550 -> 0 bytes
-rw-r--r--images/emoji/2934.pngbin559 -> 0 bytes
-rw-r--r--images/emoji/2935.pngbin563 -> 0 bytes
-rw-r--r--images/emoji/2b05.pngbin471 -> 0 bytes
-rw-r--r--images/emoji/2b06.pngbin507 -> 0 bytes
-rw-r--r--images/emoji/2b07.pngbin512 -> 0 bytes
-rw-r--r--images/emoji/2b1b.pngbin110 -> 0 bytes
-rw-r--r--images/emoji/2b1c.pngbin110 -> 0 bytes
-rw-r--r--images/emoji/2b50.pngbin456 -> 0 bytes
-rw-r--r--images/emoji/2b55.pngbin475 -> 0 bytes
-rw-r--r--images/emoji/3030.pngbin359 -> 0 bytes
-rw-r--r--images/emoji/303d.pngbin521 -> 0 bytes
-rw-r--r--images/emoji/3297.pngbin729 -> 0 bytes
-rw-r--r--images/emoji/3299.pngbin857 -> 0 bytes
-rw-r--r--images/red-koala.jpgbin0 -> 15832 bytes
-rw-r--r--images/red-koala.pngbin0 -> 14669 bytes
-rw-r--r--images/red-koala.svg151
-rw-r--r--images/red-koala.xcfbin0 -> 21756 bytes
-rw-r--r--include/account.php104
-rw-r--r--include/api.php28
-rw-r--r--include/api_auth.php79
-rw-r--r--include/attach.php457
-rw-r--r--include/auth.php7
-rw-r--r--include/bbcode.php112
-rw-r--r--include/channel.php748
-rw-r--r--include/config.php16
-rw-r--r--include/connections.php282
-rw-r--r--include/contact_widgets.php72
-rw-r--r--include/conversation.php348
-rw-r--r--include/crypto.php58
-rwxr-xr-xinclude/dba/dba_driver.php32
-rwxr-xr-xinclude/dba/dba_pdo.php14
-rw-r--r--include/dir_fns.php31
-rw-r--r--include/environment.php2
-rw-r--r--include/event.php223
-rw-r--r--include/features.php41
-rw-r--r--include/feedutils.php1236
-rw-r--r--include/follow.php67
-rw-r--r--include/group.php3
-rw-r--r--include/help.php85
-rw-r--r--include/html2bbcode.php3
-rw-r--r--include/hubloc.php129
-rw-r--r--include/import.php659
-rwxr-xr-xinclude/items.php583
-rw-r--r--include/markdown.php558
-rw-r--r--include/message.php147
-rw-r--r--include/nav.php450
-rw-r--r--include/network.php1323
-rw-r--r--include/oauth2.php23
-rwxr-xr-xinclude/oembed.php28
-rw-r--r--include/page_widgets.php52
-rw-r--r--include/perm_upgrade.php3
-rw-r--r--include/permissions.php427
-rw-r--r--include/photo/photo_driver.php168
-rw-r--r--include/photos.php251
-rwxr-xr-xinclude/plugin.php37
-rw-r--r--include/probe.php99
-rw-r--r--include/queue_fn.php12
-rw-r--r--include/security.php62
-rw-r--r--include/socgraph.php81
-rw-r--r--include/statistics_fns.php20
-rw-r--r--include/taxonomy.php117
-rw-r--r--include/text.php481
-rw-r--r--include/widgets.php1735
-rw-r--r--include/xchan.php80
-rw-r--r--include/zid.php79
-rw-r--r--include/zot.php498
-rw-r--r--install/INSTALL.txt46
-rwxr-xr-xinstall/htconfig.sample.php8
-rw-r--r--install/sample-nginx.conf2
-rw-r--r--install/schema_mysql.sql1279
-rw-r--r--install/schema_postgres.sql331
-rw-r--r--install/update.php555
-rw-r--r--library/HTMLPurifier.composer.php4
-rw-r--r--library/HTMLPurifier.includes.php229
-rw-r--r--library/HTMLPurifier.php292
-rw-r--r--library/HTMLPurifier.safe-includes.php223
-rw-r--r--library/HTMLPurifier/Arborize.php71
-rw-r--r--library/HTMLPurifier/AttrCollections.php143
-rw-r--r--library/HTMLPurifier/AttrDef.php138
-rw-r--r--library/HTMLPurifier/AttrDef/CSS.php106
-rw-r--r--library/HTMLPurifier/AttrDef/CSS/Color.php105
-rw-r--r--library/HTMLPurifier/AttrDef/CSS/Multiple.php71
-rw-r--r--library/HTMLPurifier/AttrDef/CSS/URI.php74
-rw-r--r--library/HTMLPurifier/AttrDef/HTML/Bool.php51
-rw-r--r--library/HTMLPurifier/AttrDef/HTML/ID.php105
-rw-r--r--library/HTMLPurifier/AttrDef/URI/Host.php128
-rw-r--r--library/HTMLPurifier/AttrTransform/ImgRequired.php48
-rw-r--r--library/HTMLPurifier/CSSDefinition.php474
-rw-r--r--library/HTMLPurifier/ChildDef/List.php86
-rw-r--r--library/HTMLPurifier/ChildDef/Table.php224
-rw-r--r--library/HTMLPurifier/Config.php911
-rw-r--r--library/HTMLPurifier/ConfigSchema.php176
-rw-r--r--library/HTMLPurifier/ConfigSchema/schema.serbin15000 -> 0 bytes
-rw-r--r--library/HTMLPurifier/ConfigSchema/schema/Cache.SerializerPermissions.txt11
-rw-r--r--library/HTMLPurifier/ConfigSchema/schema/HTML.CustomDoctype.txt9
-rw-r--r--library/HTMLPurifier/ConfigSchema/schema/URI.AllowedSchemes.txt17
-rw-r--r--library/HTMLPurifier/ConfigSchema/schema/URI.DefaultScheme.txt10
-rw-r--r--library/HTMLPurifier/DefinitionCache.php129
-rw-r--r--library/HTMLPurifier/DefinitionCache/Serializer.php285
-rw-r--r--library/HTMLPurifier/Encoder.php611
-rw-r--r--library/HTMLPurifier/EntityParser.php153
-rw-r--r--library/HTMLPurifier/Filter/ExtractStyleBlocks.php338
-rw-r--r--library/HTMLPurifier/Filter/YouTube.php65
-rw-r--r--library/HTMLPurifier/Generator.php286
-rw-r--r--library/HTMLPurifier/HTMLModuleManager.php459
-rw-r--r--library/HTMLPurifier/Injector/Linkify.php59
-rw-r--r--library/HTMLPurifier/Injector/RemoveEmpty.php101
-rw-r--r--library/HTMLPurifier/Injector/SafeObject.php121
-rw-r--r--library/HTMLPurifier/Lexer.php357
-rw-r--r--library/HTMLPurifier/Lexer/DOMLex.php280
-rw-r--r--library/HTMLPurifier/Lexer/DirectLex.php539
-rw-r--r--library/HTMLPurifier/Lexer/PH5P.php4788
-rw-r--r--library/HTMLPurifier/Printer/ConfigForm.php447
-rw-r--r--library/HTMLPurifier/Strategy/MakeWellFormed.php600
-rw-r--r--library/HTMLPurifier/Token.php100
-rw-r--r--library/HTMLPurifier/URI.php314
-rw-r--r--library/HTMLPurifier/URIScheme/data.php127
-rw-r--r--library/Text_Highlighter/README455
-rw-r--r--library/Text_Highlighter/TODO12
-rw-r--r--library/Text_Highlighter/Text/Highlighter.php398
-rw-r--r--library/Text_Highlighter/Text/Highlighter/ABAP.php519
-rw-r--r--library/Text_Highlighter/Text/Highlighter/AVRC.php894
-rw-r--r--library/Text_Highlighter/Text/Highlighter/CPP.php891
-rw-r--r--library/Text_Highlighter/Text/Highlighter/CSS.php437
-rw-r--r--library/Text_Highlighter/Text/Highlighter/DIFF.php384
-rw-r--r--library/Text_Highlighter/Text/Highlighter/DTD.php426
-rw-r--r--library/Text_Highlighter/Text/Highlighter/Generator.php1291
-rw-r--r--library/Text_Highlighter/Text/Highlighter/HTML.php234
-rw-r--r--library/Text_Highlighter/Text/Highlighter/JAVA.php802
-rw-r--r--library/Text_Highlighter/Text/Highlighter/JAVASCRIPT.php631
-rw-r--r--library/Text_Highlighter/Text/Highlighter/MYSQL.php434
-rw-r--r--library/Text_Highlighter/Text/Highlighter/PERL.php1352
-rw-r--r--library/Text_Highlighter/Text/Highlighter/PHP.php1107
-rw-r--r--library/Text_Highlighter/Text/Highlighter/PYTHON.php647
-rw-r--r--library/Text_Highlighter/Text/Highlighter/RUBY.php825
-rw-r--r--library/Text_Highlighter/Text/Highlighter/Renderer.php164
-rw-r--r--library/Text_Highlighter/Text/Highlighter/Renderer/Array.php202
-rw-r--r--library/Text_Highlighter/Text/Highlighter/Renderer/BB.php238
-rw-r--r--library/Text_Highlighter/Text/Highlighter/Renderer/Console.php208
-rw-r--r--library/Text_Highlighter/Text/Highlighter/Renderer/Html.php465
-rw-r--r--library/Text_Highlighter/Text/Highlighter/Renderer/HtmlTags.php187
-rw-r--r--library/Text_Highlighter/Text/Highlighter/Renderer/JSON.php86
-rw-r--r--library/Text_Highlighter/Text/Highlighter/Renderer/XML.php104
-rw-r--r--library/Text_Highlighter/Text/Highlighter/SH.php1225
-rw-r--r--library/Text_Highlighter/Text/Highlighter/SQL.php419
-rw-r--r--library/Text_Highlighter/Text/Highlighter/VBSCRIPT.php318
-rw-r--r--library/Text_Highlighter/Text/Highlighter/XML.php263
-rw-r--r--library/Text_Highlighter/abap.xml802
-rw-r--r--library/Text_Highlighter/avrc.xml316
-rw-r--r--library/Text_Highlighter/cpp.xml201
-rw-r--r--library/Text_Highlighter/css.xml368
-rw-r--r--library/Text_Highlighter/diff.xml45
-rw-r--r--library/Text_Highlighter/dtd.xml66
-rw-r--r--library/Text_Highlighter/generate171
-rw-r--r--library/Text_Highlighter/generate.bat188
-rw-r--r--library/Text_Highlighter/html.xml33
-rw-r--r--library/Text_Highlighter/java.xml2824
-rw-r--r--library/Text_Highlighter/javascript.xml174
-rw-r--r--library/Text_Highlighter/mysql.xml424
-rw-r--r--library/Text_Highlighter/perl.xml439
-rw-r--r--library/Text_Highlighter/php.xml194
-rw-r--r--library/Text_Highlighter/python.xml229
-rw-r--r--library/Text_Highlighter/release4
-rw-r--r--library/Text_Highlighter/ruby.xml141
-rw-r--r--library/Text_Highlighter/sample.css62
-rw-r--r--library/Text_Highlighter/sh.xml242
-rw-r--r--library/Text_Highlighter/sql.xml496
-rw-r--r--library/Text_Highlighter/vbscript.xml305
-rw-r--r--library/Text_Highlighter/xml.xml37
-rw-r--r--library/blueimp_upload/.gitignore3
-rw-r--r--library/blueimp_upload/.jshintrc81
-rw-r--r--library/blueimp_upload/CONTRIBUTING.md43
-rw-r--r--library/blueimp_upload/Gruntfile.js37
-rw-r--r--library/blueimp_upload/LICENSE20
-rw-r--r--library/blueimp_upload/README.md58
-rw-r--r--library/blueimp_upload/angularjs.html14
-rw-r--r--library/blueimp_upload/basic-plus.html14
-rw-r--r--library/blueimp_upload/basic.html14
-rw-r--r--library/blueimp_upload/blueimp-file-upload.jquery.json50
-rwxr-xr-xlibrary/blueimp_upload/bower-version-update.js16
-rw-r--r--library/blueimp_upload/bower.json29
-rw-r--r--library/blueimp_upload/cors/postmessage.html6
-rw-r--r--library/blueimp_upload/cors/result.html4
-rw-r--r--library/blueimp_upload/css/demo-ie8.css4
-rw-r--r--library/blueimp_upload/css/demo.css4
-rw-r--r--library/blueimp_upload/css/jquery.fileupload-noscript.css6
-rw-r--r--library/blueimp_upload/css/jquery.fileupload-ui-noscript.css4
-rw-r--r--library/blueimp_upload/css/jquery.fileupload-ui.css4
-rw-r--r--library/blueimp_upload/css/jquery.fileupload.css7
-rw-r--r--library/blueimp_upload/css/style.css4
-rw-r--r--library/blueimp_upload/index.html12
-rw-r--r--library/blueimp_upload/jquery-ui.html14
-rw-r--r--library/blueimp_upload/js/app.js8
-rw-r--r--library/blueimp_upload/js/cors/jquery.postmessage-transport.js17
-rw-r--r--library/blueimp_upload/js/cors/jquery.xdr-transport.js11
-rw-r--r--library/blueimp_upload/js/jquery.fileupload-angular.js50
-rw-r--r--library/blueimp_upload/js/jquery.fileupload-audio.js15
-rw-r--r--library/blueimp_upload/js/jquery.fileupload-image.js23
-rw-r--r--[-rwxr-xr-x]library/blueimp_upload/js/jquery.fileupload-jquery-ui.js19
-rw-r--r--library/blueimp_upload/js/jquery.fileupload-process.js18
-rw-r--r--library/blueimp_upload/js/jquery.fileupload-ui.js23
-rw-r--r--library/blueimp_upload/js/jquery.fileupload-validate.js16
-rw-r--r--library/blueimp_upload/js/jquery.fileupload-video.js15
-rw-r--r--library/blueimp_upload/js/jquery.fileupload.js71
-rw-r--r--library/blueimp_upload/js/jquery.iframe-transport.js22
-rw-r--r--library/blueimp_upload/js/main.js6
-rw-r--r--library/blueimp_upload/js/vendor/jquery.ui.widget.js44
-rw-r--r--library/blueimp_upload/package.json39
-rw-r--r--library/blueimp_upload/server/gae-go/app/main.go297
-rw-r--r--library/blueimp_upload/server/gae-python/app.yaml5
-rw-r--r--library/blueimp_upload/server/gae-python/main.py208
-rw-r--r--library/blueimp_upload/server/node/.gitignore2
-rw-r--r--library/blueimp_upload/server/node/package.json41
-rw-r--r--library/blueimp_upload/server/node/public/files/.gitignore2
-rwxr-xr-xlibrary/blueimp_upload/server/node/server.js292
-rw-r--r--library/blueimp_upload/server/node/tmp/.gitignore0
-rw-r--r--library/blueimp_upload/server/php/Dockerfile38
-rwxr-xr-xlibrary/blueimp_upload/server/php/UploadHandler.php250
-rw-r--r--library/blueimp_upload/server/php/docker-compose.yml6
-rw-r--r--library/blueimp_upload/server/php/files/.htaccess14
-rw-r--r--library/blueimp_upload/server/php/index.php4
-rw-r--r--library/blueimp_upload/test/index.html16
-rw-r--r--library/blueimp_upload/test/test.js10
-rw-r--r--library/bootstrap/css/bootstrap-grid.css1353
-rw-r--r--library/bootstrap/css/bootstrap-grid.css.map1
-rw-r--r--library/bootstrap/css/bootstrap-grid.min.css2
-rw-r--r--library/bootstrap/css/bootstrap-grid.min.css.map1
-rw-r--r--library/bootstrap/css/bootstrap-reboot.css330
-rw-r--r--library/bootstrap/css/bootstrap-reboot.css.map1
-rw-r--r--library/bootstrap/css/bootstrap-reboot.min.css2
-rw-r--r--library/bootstrap/css/bootstrap-reboot.min.css.map1
-rw-r--r--library/bootstrap/css/bootstrap-theme.css587
-rw-r--r--library/bootstrap/css/bootstrap-theme.css.map1
-rw-r--r--library/bootstrap/css/bootstrap-theme.min.css6
-rw-r--r--library/bootstrap/css/bootstrap-theme.min.css.map1
-rw-r--r--library/bootstrap/css/bootstrap.css12052
-rw-r--r--library/bootstrap/css/bootstrap.css.map2
-rw-r--r--library/bootstrap/css/bootstrap.min.css7
-rw-r--r--library/bootstrap/css/bootstrap.min.css.map2
-rw-r--r--library/bootstrap/fonts/glyphicons-halflings-regular.eotbin20127 -> 0 bytes
-rw-r--r--library/bootstrap/fonts/glyphicons-halflings-regular.svg288
-rw-r--r--library/bootstrap/fonts/glyphicons-halflings-regular.ttfbin45404 -> 0 bytes
-rw-r--r--library/bootstrap/fonts/glyphicons-halflings-regular.woffbin23424 -> 0 bytes
-rw-r--r--library/bootstrap/fonts/glyphicons-halflings-regular.woff2bin18028 -> 0 bytes
-rw-r--r--library/bootstrap/js/bootstrap.js5022
-rw-r--r--library/bootstrap/js/bootstrap.min.js9
-rw-r--r--library/cacert.pem650
-rw-r--r--library/certs/cacert.pem650
-rw-r--r--library/emoji.json1
-rw-r--r--library/fullcalendar/CHANGELOG.txt21
-rw-r--r--library/fullcalendar/fullcalendar.css6
-rw-r--r--library/fullcalendar/fullcalendar.js1109
-rw-r--r--library/fullcalendar/fullcalendar.min.css6
-rw-r--r--library/fullcalendar/fullcalendar.min.js16
-rw-r--r--library/fullcalendar/fullcalendar.print.css6
-rw-r--r--library/fullcalendar/fullcalendar.print.min.css6
-rw-r--r--library/fullcalendar/gcal.js6
-rw-r--r--library/fullcalendar/gcal.min.js6
-rw-r--r--library/fullcalendar/locale-all.js8
-rw-r--r--library/htmlpurifier-4.6.0-lite/INSTALL374
-rw-r--r--library/htmlpurifier-4.6.0-lite/NEWS1078
-rw-r--r--library/jquery-textcomplete/LICENSE21
-rw-r--r--library/jquery-textcomplete/jquery.textcomplete.js157
-rw-r--r--library/jquery-textcomplete/jquery.textcomplete.min.js4
-rw-r--r--library/jquery-textcomplete/jquery.textcomplete.min.map1
-rw-r--r--library/jquery_ac/friendica.complete.js4
-rw-r--r--library/jsonld/LICENSE30
-rw-r--r--library/jsonld/README.md193
-rw-r--r--library/jsonld/composer.json29
-rw-r--r--library/jsonld/jsonld.php6038
-rw-r--r--library/jsonld/test.php765
-rw-r--r--library/markdown.php2932
-rw-r--r--library/markdownify/LICENSE_LGPL.txt504
-rw-r--r--library/markdownify/TODO29
-rw-r--r--library/markdownify/example.php51
-rw-r--r--library/markdownify/markdownify.php1197
-rwxr-xr-xlibrary/markdownify/markdownify_cli.php33
-rw-r--r--library/markdownify/markdownify_extra.php489
-rw-r--r--library/markdownify/parsehtml/parsehtml.php618
-rw-r--r--library/oauth2/.gitignore5
-rw-r--r--library/oauth2/.travis.yml30
-rw-r--r--library/oauth2/CHANGELOG.md152
-rw-r--r--library/oauth2/phpunit.xml25
-rw-r--r--library/oauth2/src/OAuth2/Controller/AuthorizeController.php388
-rw-r--r--library/oauth2/src/OAuth2/Controller/ResourceController.php111
-rw-r--r--library/oauth2/src/OAuth2/Controller/TokenController.php278
-rw-r--r--library/oauth2/src/OAuth2/GrantType/AuthorizationCode.php100
-rw-r--r--library/oauth2/src/OAuth2/Response.php369
-rw-r--r--library/oauth2/src/OAuth2/ResponseType/AccessToken.php194
-rw-r--r--library/oauth2/src/OAuth2/ResponseType/AuthorizationCode.php100
-rw-r--r--library/oauth2/src/OAuth2/Server.php832
-rw-r--r--library/oauth2/src/OAuth2/Storage/AuthorizationCodeInterface.php86
-rw-r--r--library/oauth2/src/OAuth2/Storage/Cassandra.php480
-rw-r--r--library/oauth2/src/OAuth2/Storage/Mongo.php339
-rw-r--r--library/oauth2/src/OAuth2/Storage/RefreshTokenInterface.php82
-rw-r--r--library/oauth2/test/OAuth2/Controller/ResourceControllerTest.php175
-rw-r--r--library/oauth2/test/OAuth2/GrantType/AuthorizationCodeTest.php207
-rw-r--r--library/oauth2/test/config/storage.json181
-rwxr-xr-xlibrary/oauth2/test/lib/OAuth2/Storage/BaseTest.php34
-rwxr-xr-xlibrary/oauth2/test/lib/OAuth2/Storage/Bootstrap.php888
-rw-r--r--library/popper/popper.min.js4
-rw-r--r--library/simplepie/README.markdown53
-rw-r--r--library/simplepie/compatibility_test/COMPATIBILITY README.txt7
-rw-r--r--library/simplepie/compatibility_test/sp_compatibility_test.php330
-rw-r--r--library/simplepie/create.php178
-rw-r--r--library/simplepie/db.sql38
-rw-r--r--library/simplepie/demo/cli_test.php23
-rw-r--r--library/simplepie/demo/for_the_demo/alternate_favicon.pngbin28621 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/background_blockquote.pngbin27353 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/background_menuitem.gifbin533 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/background_menuitem_off.gifbin533 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/background_menuitem_shadow.gifbin250 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/favicons/alternate.pngbin28621 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/favicons/blinklist.pngbin4377 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/favicons/blogmarks.pngbin3823 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/favicons/delicious.pngbin3739 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/favicons/digg.pngbin4004 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/favicons/magnolia.pngbin4574 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/favicons/myweb2.pngbin4010 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/favicons/newsvine.pngbin3804 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/favicons/reddit.pngbin4239 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/favicons/segnalo.pngbin4116 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/favicons/simpy.pngbin4256 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/favicons/spurl.pngbin3970 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/favicons/technorati.pngbin4087 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/favicons/wists.pngbin3974 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/feed.pngbin715 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/logo_simplepie_demo.pngbin3047 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/lucida-grande-bold.swfbin21159 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/mediaplayer.swfbin32008 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/mediaplayer_readme.htm5
-rw-r--r--library/simplepie/demo/for_the_demo/mini_podcast.pngbin1202 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/place_audio.pngbin851 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/place_video.pngbin36713 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/sIFR-print.css35
-rw-r--r--library/simplepie/demo/for_the_demo/sIFR-screen.css39
-rw-r--r--library/simplepie/demo/for_the_demo/sifr-config.js40
-rw-r--r--library/simplepie/demo/for_the_demo/sifr.js19
-rw-r--r--library/simplepie/demo/for_the_demo/simplepie.css397
-rw-r--r--library/simplepie/demo/for_the_demo/sleight.js31
-rw-r--r--library/simplepie/demo/for_the_demo/source_files/place_audio_fireworksfile.pngbin39177 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/source_files/place_video_fireworksfile.pngbin115826 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/source_files/sIFR-r245/SifrStyleSheet.as71
-rw-r--r--library/simplepie/demo/for_the_demo/source_files/sIFR-r245/_README_.txt12
-rw-r--r--library/simplepie/demo/for_the_demo/source_files/sIFR-r245/options.as12
-rw-r--r--library/simplepie/demo/for_the_demo/source_files/sIFR-r245/sIFR.as359
-rw-r--r--library/simplepie/demo/for_the_demo/source_files/sIFR-r245/sifr.flabin47104 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/top_gradient.gifbin1378 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/verdana.swfbin28575 -> 0 bytes
-rw-r--r--library/simplepie/demo/for_the_demo/yanone-kaffeesatz-bold.swfbin76780 -> 0 bytes
-rw-r--r--library/simplepie/demo/handler_image.php6
-rw-r--r--library/simplepie/demo/index.php295
-rw-r--r--library/simplepie/demo/minimalistic.php137
-rw-r--r--library/simplepie/demo/multifeeds.php108
-rw-r--r--library/simplepie/demo/test.php62
-rw-r--r--library/simplepie/idn/idna_convert.class.php969
-rw-r--r--library/simplepie/simplepie.inc15150
-rw-r--r--library/sticky-kit/sticky-kit.js2
l---------tests/phpunit-mariadb.xml1
-rw-r--r--tests/phpunit-mysql.xml37
-rw-r--r--tests/phpunit-pgsql.xml34
-rwxr-xr-xtests/travis/gen_apidocs.sh69
-rwxr-xr-xtests/travis/prepare.sh35
-rwxr-xr-xtests/travis/prepare_mysql.sh53
-rwxr-xr-xtests/travis/prepare_pgsql.sh44
-rw-r--r--tests/unit/Access/AccessListTest.php189
-rw-r--r--tests/unit/Access/PermissionsTest.php148
-rw-r--r--tests/unit/Lib/PermissionDescriptionTest.php131
-rw-r--r--tests/unit/TextTest.php33
-rw-r--r--tests/unit/includes/FeedutilsText.php55
-rw-r--r--tests/unit/includes/MarkdownTest.php149
-rw-r--r--tests/unit/includes/TextTest.php82
-rw-r--r--tests/unit/template_test.php6
-rw-r--r--util/Doxyfile12
-rw-r--r--util/Doxygen_phpvarfilter.php18
-rw-r--r--util/db_update.php3
-rwxr-xr-xutil/dcp143
-rwxr-xr-xutil/dmkdir57
-rwxr-xr-xutil/fresh2
-rw-r--r--util/hmessages.po13950
-rwxr-xr-xutil/pconfig6
-rw-r--r--util/typo.php26
-rw-r--r--vendor/autoload.php2
l---------vendor/bin/html-to-markdown1
-rw-r--r--vendor/bshaffer/oauth2-server-php/CHANGELOG.md182
-rw-r--r--vendor/bshaffer/oauth2-server-php/LICENSE (renamed from library/oauth2/LICENSE)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/README.md (renamed from library/oauth2/README.md)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/composer.json34
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Autoloader.php (renamed from library/oauth2/src/OAuth2/Autoloader.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/ClientAssertionType/ClientAssertionTypeInterface.php (renamed from library/oauth2/src/OAuth2/ClientAssertionType/ClientAssertionTypeInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/ClientAssertionType/HttpBasic.php (renamed from library/oauth2/src/OAuth2/ClientAssertionType/HttpBasic.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Controller/AuthorizeController.php393
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Controller/AuthorizeControllerInterface.php (renamed from library/oauth2/src/OAuth2/Controller/AuthorizeControllerInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Controller/ResourceController.php111
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Controller/ResourceControllerInterface.php (renamed from library/oauth2/src/OAuth2/Controller/ResourceControllerInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Controller/TokenController.php295
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Controller/TokenControllerInterface.php (renamed from library/oauth2/src/OAuth2/Controller/TokenControllerInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Encryption/EncryptionInterface.php (renamed from library/oauth2/src/OAuth2/Encryption/EncryptionInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Encryption/FirebaseJwt.php (renamed from library/oauth2/src/OAuth2/Encryption/FirebaseJwt.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Encryption/Jwt.php (renamed from library/oauth2/src/OAuth2/Encryption/Jwt.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/GrantType/AuthorizationCode.php100
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/GrantType/ClientCredentials.php (renamed from library/oauth2/src/OAuth2/GrantType/ClientCredentials.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/GrantType/GrantTypeInterface.php (renamed from library/oauth2/src/OAuth2/GrantType/GrantTypeInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/GrantType/JwtBearer.php (renamed from library/oauth2/src/OAuth2/GrantType/JwtBearer.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/GrantType/RefreshToken.php (renamed from library/oauth2/src/OAuth2/GrantType/RefreshToken.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/GrantType/UserCredentials.php (renamed from library/oauth2/src/OAuth2/GrantType/UserCredentials.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Controller/AuthorizeController.php (renamed from library/oauth2/src/OAuth2/OpenID/Controller/AuthorizeController.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Controller/AuthorizeControllerInterface.php (renamed from library/oauth2/src/OAuth2/OpenID/Controller/AuthorizeControllerInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Controller/UserInfoController.php (renamed from library/oauth2/src/OAuth2/OpenID/Controller/UserInfoController.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Controller/UserInfoControllerInterface.php (renamed from library/oauth2/src/OAuth2/OpenID/Controller/UserInfoControllerInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/GrantType/AuthorizationCode.php (renamed from library/oauth2/src/OAuth2/OpenID/GrantType/AuthorizationCode.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/AuthorizationCode.php (renamed from library/oauth2/src/OAuth2/OpenID/ResponseType/AuthorizationCode.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/AuthorizationCodeInterface.php (renamed from library/oauth2/src/OAuth2/OpenID/ResponseType/AuthorizationCodeInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/CodeIdToken.php (renamed from library/oauth2/src/OAuth2/OpenID/ResponseType/CodeIdToken.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/CodeIdTokenInterface.php (renamed from library/oauth2/src/OAuth2/OpenID/ResponseType/CodeIdTokenInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/IdToken.php (renamed from library/oauth2/src/OAuth2/OpenID/ResponseType/IdToken.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/IdTokenInterface.php (renamed from library/oauth2/src/OAuth2/OpenID/ResponseType/IdTokenInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/IdTokenToken.php (renamed from library/oauth2/src/OAuth2/OpenID/ResponseType/IdTokenToken.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/IdTokenTokenInterface.php (renamed from library/oauth2/src/OAuth2/OpenID/ResponseType/IdTokenTokenInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Storage/AuthorizationCodeInterface.php (renamed from library/oauth2/src/OAuth2/OpenID/Storage/AuthorizationCodeInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Storage/UserClaimsInterface.php (renamed from library/oauth2/src/OAuth2/OpenID/Storage/UserClaimsInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Request.php (renamed from library/oauth2/src/OAuth2/Request.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/RequestInterface.php (renamed from library/oauth2/src/OAuth2/RequestInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Response.php369
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/ResponseInterface.php (renamed from library/oauth2/src/OAuth2/ResponseInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/AccessToken.php194
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/AccessTokenInterface.php (renamed from library/oauth2/src/OAuth2/ResponseType/AccessTokenInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/AuthorizationCode.php100
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/AuthorizationCodeInterface.php (renamed from library/oauth2/src/OAuth2/ResponseType/AuthorizationCodeInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/JwtAccessToken.php (renamed from library/oauth2/src/OAuth2/ResponseType/JwtAccessToken.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/ResponseTypeInterface.php (renamed from library/oauth2/src/OAuth2/ResponseType/ResponseTypeInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Scope.php (renamed from library/oauth2/src/OAuth2/Scope.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/ScopeInterface.php (renamed from library/oauth2/src/OAuth2/ScopeInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Server.php879
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/AccessTokenInterface.php (renamed from library/oauth2/src/OAuth2/Storage/AccessTokenInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/AuthorizationCodeInterface.php86
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/Cassandra.php480
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/ClientCredentialsInterface.php (renamed from library/oauth2/src/OAuth2/Storage/ClientCredentialsInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/ClientInterface.php (renamed from library/oauth2/src/OAuth2/Storage/ClientInterface.php)0
-rwxr-xr-xvendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/CouchbaseDB.php (renamed from library/oauth2/src/OAuth2/Storage/CouchbaseDB.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/DynamoDB.php (renamed from library/oauth2/src/OAuth2/Storage/DynamoDB.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/JwtAccessToken.php (renamed from library/oauth2/src/OAuth2/Storage/JwtAccessToken.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/JwtAccessTokenInterface.php (renamed from library/oauth2/src/OAuth2/Storage/JwtAccessTokenInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/JwtBearerInterface.php (renamed from library/oauth2/src/OAuth2/Storage/JwtBearerInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/Memory.php (renamed from library/oauth2/src/OAuth2/Storage/Memory.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/Mongo.php392
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/MongoDB.php380
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/Pdo.php (renamed from library/oauth2/src/OAuth2/Storage/Pdo.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/PublicKeyInterface.php (renamed from library/oauth2/src/OAuth2/Storage/PublicKeyInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/Redis.php (renamed from library/oauth2/src/OAuth2/Storage/Redis.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/RefreshTokenInterface.php82
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/ScopeInterface.php (renamed from library/oauth2/src/OAuth2/Storage/ScopeInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/UserCredentialsInterface.php (renamed from library/oauth2/src/OAuth2/Storage/UserCredentialsInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/TokenType/Bearer.php (renamed from library/oauth2/src/OAuth2/TokenType/Bearer.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/TokenType/Mac.php (renamed from library/oauth2/src/OAuth2/TokenType/Mac.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/src/OAuth2/TokenType/TokenTypeInterface.php (renamed from library/oauth2/src/OAuth2/TokenType/TokenTypeInterface.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/AutoloadTest.php (renamed from library/oauth2/test/OAuth2/AutoloadTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/Controller/AuthorizeControllerTest.php (renamed from library/oauth2/test/OAuth2/Controller/AuthorizeControllerTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/Controller/ResourceControllerTest.php176
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/Controller/TokenControllerTest.php (renamed from library/oauth2/test/OAuth2/Controller/TokenControllerTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/Encryption/FirebaseJwtTest.php (renamed from library/oauth2/test/OAuth2/Encryption/FirebaseJwtTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/Encryption/JwtTest.php (renamed from library/oauth2/test/OAuth2/Encryption/JwtTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/GrantType/AuthorizationCodeTest.php223
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/GrantType/ClientCredentialsTest.php (renamed from library/oauth2/test/OAuth2/GrantType/ClientCredentialsTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/GrantType/ImplicitTest.php (renamed from library/oauth2/test/OAuth2/GrantType/ImplicitTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/GrantType/JwtBearerTest.php (renamed from library/oauth2/test/OAuth2/GrantType/JwtBearerTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/GrantType/RefreshTokenTest.php (renamed from library/oauth2/test/OAuth2/GrantType/RefreshTokenTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/GrantType/UserCredentialsTest.php (renamed from library/oauth2/test/OAuth2/GrantType/UserCredentialsTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/Controller/AuthorizeControllerTest.php (renamed from library/oauth2/test/OAuth2/OpenID/Controller/AuthorizeControllerTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/Controller/UserInfoControllerTest.php (renamed from library/oauth2/test/OAuth2/OpenID/Controller/UserInfoControllerTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/GrantType/AuthorizationCodeTest.php (renamed from library/oauth2/test/OAuth2/OpenID/GrantType/AuthorizationCodeTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/ResponseType/CodeIdTokenTest.php (renamed from library/oauth2/test/OAuth2/OpenID/ResponseType/CodeIdTokenTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/ResponseType/IdTokenTest.php (renamed from library/oauth2/test/OAuth2/OpenID/ResponseType/IdTokenTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/ResponseType/IdTokenTokenTest.php (renamed from library/oauth2/test/OAuth2/OpenID/ResponseType/IdTokenTokenTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/Storage/AuthorizationCodeTest.php (renamed from library/oauth2/test/OAuth2/OpenID/Storage/AuthorizationCodeTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/Storage/UserClaimsTest.php (renamed from library/oauth2/test/OAuth2/OpenID/Storage/UserClaimsTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/RequestTest.php (renamed from library/oauth2/test/OAuth2/RequestTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/ResponseTest.php (renamed from library/oauth2/test/OAuth2/ResponseTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/ResponseType/AccessTokenTest.php (renamed from library/oauth2/test/OAuth2/ResponseType/AccessTokenTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/ResponseType/JwtAccessTokenTest.php (renamed from library/oauth2/test/OAuth2/ResponseType/JwtAccessTokenTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/ScopeTest.php (renamed from library/oauth2/test/OAuth2/ScopeTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/ServerTest.php (renamed from library/oauth2/test/OAuth2/ServerTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/AccessTokenTest.php (renamed from library/oauth2/test/OAuth2/Storage/AccessTokenTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/AuthorizationCodeTest.php (renamed from library/oauth2/test/OAuth2/Storage/AuthorizationCodeTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/ClientCredentialsTest.php (renamed from library/oauth2/test/OAuth2/Storage/ClientCredentialsTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/ClientTest.php (renamed from library/oauth2/test/OAuth2/Storage/ClientTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/DynamoDBTest.php (renamed from library/oauth2/test/OAuth2/Storage/DynamoDBTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/JwtAccessTokenTest.php (renamed from library/oauth2/test/OAuth2/Storage/JwtAccessTokenTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/JwtBearerTest.php (renamed from library/oauth2/test/OAuth2/Storage/JwtBearerTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/PdoTest.php (renamed from library/oauth2/test/OAuth2/Storage/PdoTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/PublicKeyTest.php (renamed from library/oauth2/test/OAuth2/Storage/PublicKeyTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/RefreshTokenTest.php (renamed from library/oauth2/test/OAuth2/Storage/RefreshTokenTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/ScopeTest.php (renamed from library/oauth2/test/OAuth2/Storage/ScopeTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/UserCredentialsTest.php (renamed from library/oauth2/test/OAuth2/Storage/UserCredentialsTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/OAuth2/TokenType/BearerTest.php (renamed from library/oauth2/test/OAuth2/TokenType/BearerTest.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/bootstrap.php (renamed from library/oauth2/test/bootstrap.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/cleanup.php (renamed from library/oauth2/test/cleanup.php)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/config/keys/id_rsa (renamed from library/oauth2/test/config/keys/id_rsa)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/config/keys/id_rsa.pub (renamed from library/oauth2/test/config/keys/id_rsa.pub)0
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/config/storage.json188
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/lib/OAuth2/Request/TestRequest.php (renamed from library/oauth2/test/lib/OAuth2/Request/TestRequest.php)0
-rwxr-xr-xvendor/bshaffer/oauth2-server-php/test/lib/OAuth2/Storage/BaseTest.php36
-rwxr-xr-xvendor/bshaffer/oauth2-server-php/test/lib/OAuth2/Storage/Bootstrap.php967
-rw-r--r--vendor/bshaffer/oauth2-server-php/test/lib/OAuth2/Storage/NullStorage.php (renamed from library/oauth2/test/lib/OAuth2/Storage/NullStorage.php)0
-rw-r--r--vendor/composer/ClassLoader.php46
-rw-r--r--vendor/composer/LICENSE2
-rw-r--r--vendor/composer/autoload_classmap.php450
-rw-r--r--vendor/composer/autoload_files.php1
-rw-r--r--vendor/composer/autoload_namespaces.php4
-rw-r--r--vendor/composer/autoload_psr4.php1
-rw-r--r--vendor/composer/autoload_real.php2
-rw-r--r--vendor/composer/autoload_static.php493
-rw-r--r--vendor/composer/installed.json688
-rw-r--r--vendor/ezyang/htmlpurifier/CREDITS (renamed from library/htmlpurifier-4.6.0-lite/CREDITS)0
-rw-r--r--vendor/ezyang/htmlpurifier/INSTALL373
-rw-r--r--vendor/ezyang/htmlpurifier/INSTALL.fr.utf860
-rw-r--r--vendor/ezyang/htmlpurifier/LICENSE (renamed from library/htmlpurifier-4.6.0-lite/LICENSE)0
-rw-r--r--vendor/ezyang/htmlpurifier/NEWS1176
-rw-r--r--vendor/ezyang/htmlpurifier/README.md29
-rw-r--r--vendor/ezyang/htmlpurifier/TODO150
-rw-r--r--vendor/ezyang/htmlpurifier/VERSION1
-rw-r--r--vendor/ezyang/htmlpurifier/WHATSNEW13
-rw-r--r--vendor/ezyang/htmlpurifier/WYSIWYG20
-rw-r--r--vendor/ezyang/htmlpurifier/composer.json25
-rw-r--r--vendor/ezyang/htmlpurifier/extras/ConfigDoc/HTMLXSLTProcessor.php91
-rw-r--r--vendor/ezyang/htmlpurifier/extras/FSTools.php164
-rw-r--r--vendor/ezyang/htmlpurifier/extras/FSTools/File.php141
-rw-r--r--vendor/ezyang/htmlpurifier/extras/HTMLPurifierExtras.auto.php11
-rw-r--r--vendor/ezyang/htmlpurifier/extras/HTMLPurifierExtras.autoload.php26
-rw-r--r--vendor/ezyang/htmlpurifier/extras/HTMLPurifierExtras.php31
-rw-r--r--vendor/ezyang/htmlpurifier/extras/README32
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier.auto.php (renamed from library/HTMLPurifier.auto.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier.autoload.php (renamed from library/HTMLPurifier.autoload.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier.composer.php4
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier.func.php (renamed from library/HTMLPurifier.func.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier.includes.php234
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier.kses.php (renamed from library/HTMLPurifier.kses.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier.path.php (renamed from library/HTMLPurifier.path.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier.php292
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier.safe-includes.php228
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Arborize.php71
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrCollections.php148
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef.php144
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS.php136
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/AlphaValue.php (renamed from library/HTMLPurifier/AttrDef/CSS/AlphaValue.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Background.php (renamed from library/HTMLPurifier/AttrDef/CSS/Background.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/BackgroundPosition.php (renamed from library/HTMLPurifier/AttrDef/CSS/BackgroundPosition.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Border.php (renamed from library/HTMLPurifier/AttrDef/CSS/Border.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Color.php161
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Composite.php (renamed from library/HTMLPurifier/AttrDef/CSS/Composite.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/DenyElementDecorator.php (renamed from library/HTMLPurifier/AttrDef/CSS/DenyElementDecorator.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Filter.php (renamed from library/HTMLPurifier/AttrDef/CSS/Filter.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Font.php (renamed from library/HTMLPurifier/AttrDef/CSS/Font.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/FontFamily.php (renamed from library/HTMLPurifier/AttrDef/CSS/FontFamily.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Ident.php (renamed from library/HTMLPurifier/AttrDef/CSS/Ident.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/ImportantDecorator.php (renamed from library/HTMLPurifier/AttrDef/CSS/ImportantDecorator.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Length.php (renamed from library/HTMLPurifier/AttrDef/CSS/Length.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/ListStyle.php (renamed from library/HTMLPurifier/AttrDef/CSS/ListStyle.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Multiple.php71
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Number.php (renamed from library/HTMLPurifier/AttrDef/CSS/Number.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Percentage.php (renamed from library/HTMLPurifier/AttrDef/CSS/Percentage.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/TextDecoration.php (renamed from library/HTMLPurifier/AttrDef/CSS/TextDecoration.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/URI.php77
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Clone.php (renamed from library/HTMLPurifier/AttrDef/Clone.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Enum.php (renamed from library/HTMLPurifier/AttrDef/Enum.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Bool.php48
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Class.php (renamed from library/HTMLPurifier/AttrDef/HTML/Class.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Color.php (renamed from library/HTMLPurifier/AttrDef/HTML/Color.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/FrameTarget.php (renamed from library/HTMLPurifier/AttrDef/HTML/FrameTarget.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/ID.php113
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Length.php (renamed from library/HTMLPurifier/AttrDef/HTML/Length.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/LinkTypes.php (renamed from library/HTMLPurifier/AttrDef/HTML/LinkTypes.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/MultiLength.php (renamed from library/HTMLPurifier/AttrDef/HTML/MultiLength.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Nmtokens.php (renamed from library/HTMLPurifier/AttrDef/HTML/Nmtokens.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Pixels.php (renamed from library/HTMLPurifier/AttrDef/HTML/Pixels.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Integer.php (renamed from library/HTMLPurifier/AttrDef/Integer.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Lang.php (renamed from library/HTMLPurifier/AttrDef/Lang.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Switch.php (renamed from library/HTMLPurifier/AttrDef/Switch.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Text.php (renamed from library/HTMLPurifier/AttrDef/Text.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI.php (renamed from library/HTMLPurifier/AttrDef/URI.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/Email.php (renamed from library/HTMLPurifier/AttrDef/URI/Email.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/Email/SimpleCheck.php (renamed from library/HTMLPurifier/AttrDef/URI/Email/SimpleCheck.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/Host.php138
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/IPv4.php (renamed from library/HTMLPurifier/AttrDef/URI/IPv4.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/IPv6.php (renamed from library/HTMLPurifier/AttrDef/URI/IPv6.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform.php (renamed from library/HTMLPurifier/AttrTransform.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Background.php (renamed from library/HTMLPurifier/AttrTransform/Background.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/BdoDir.php (renamed from library/HTMLPurifier/AttrTransform/BdoDir.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/BgColor.php (renamed from library/HTMLPurifier/AttrTransform/BgColor.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/BoolToCSS.php (renamed from library/HTMLPurifier/AttrTransform/BoolToCSS.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Border.php (renamed from library/HTMLPurifier/AttrTransform/Border.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/EnumToCSS.php (renamed from library/HTMLPurifier/AttrTransform/EnumToCSS.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/ImgRequired.php47
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/ImgSpace.php (renamed from library/HTMLPurifier/AttrTransform/ImgSpace.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Input.php (renamed from library/HTMLPurifier/AttrTransform/Input.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Lang.php (renamed from library/HTMLPurifier/AttrTransform/Lang.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Length.php (renamed from library/HTMLPurifier/AttrTransform/Length.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Name.php (renamed from library/HTMLPurifier/AttrTransform/Name.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/NameSync.php (renamed from library/HTMLPurifier/AttrTransform/NameSync.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Nofollow.php (renamed from library/HTMLPurifier/AttrTransform/Nofollow.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/SafeEmbed.php (renamed from library/HTMLPurifier/AttrTransform/SafeEmbed.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/SafeObject.php (renamed from library/HTMLPurifier/AttrTransform/SafeObject.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/SafeParam.php (renamed from library/HTMLPurifier/AttrTransform/SafeParam.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/ScriptRequired.php (renamed from library/HTMLPurifier/AttrTransform/ScriptRequired.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/TargetBlank.php (renamed from library/HTMLPurifier/AttrTransform/TargetBlank.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/TargetNoopener.php37
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/TargetNoreferrer.php37
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Textarea.php (renamed from library/HTMLPurifier/AttrTransform/Textarea.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTypes.php (renamed from library/HTMLPurifier/AttrTypes.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrValidator.php (renamed from library/HTMLPurifier/AttrValidator.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Bootstrap.php (renamed from library/HTMLPurifier/Bootstrap.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/CSSDefinition.php491
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef.php (renamed from library/HTMLPurifier/ChildDef.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Chameleon.php (renamed from library/HTMLPurifier/ChildDef/Chameleon.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Custom.php (renamed from library/HTMLPurifier/ChildDef/Custom.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Empty.php (renamed from library/HTMLPurifier/ChildDef/Empty.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/List.php92
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Optional.php (renamed from library/HTMLPurifier/ChildDef/Optional.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Required.php (renamed from library/HTMLPurifier/ChildDef/Required.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/StrictBlockquote.php (renamed from library/HTMLPurifier/ChildDef/StrictBlockquote.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Table.php224
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Config.php920
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema.php176
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Builder/ConfigSchema.php (renamed from library/HTMLPurifier/ConfigSchema/Builder/ConfigSchema.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Builder/Xml.php (renamed from library/HTMLPurifier/ConfigSchema/Builder/Xml.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Exception.php (renamed from library/HTMLPurifier/ConfigSchema/Exception.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Interchange.php (renamed from library/HTMLPurifier/ConfigSchema/Interchange.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Interchange/Directive.php (renamed from library/HTMLPurifier/ConfigSchema/Interchange/Directive.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Interchange/Id.php (renamed from library/HTMLPurifier/ConfigSchema/Interchange/Id.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/InterchangeBuilder.php (renamed from library/HTMLPurifier/ConfigSchema/InterchangeBuilder.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Validator.php (renamed from library/HTMLPurifier/ConfigSchema/Validator.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/ValidatorAtom.php (renamed from library/HTMLPurifier/ConfigSchema/ValidatorAtom.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema.serbin0 -> 15923 bytes
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedClasses.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedClasses.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedFrameTargets.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedFrameTargets.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedRel.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedRel.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedRev.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedRev.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.ClassUseCDATA.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Attr.ClassUseCDATA.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultImageAlt.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultImageAlt.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultInvalidImage.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultInvalidImage.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultInvalidImageAlt.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultInvalidImageAlt.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultTextDir.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultTextDir.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.EnableID.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Attr.EnableID.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.ForbiddenClasses.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Attr.ForbiddenClasses.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.ID.HTML5.txt10
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.IDBlacklist.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Attr.IDBlacklist.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.IDBlacklistRegexp.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Attr.IDBlacklistRegexp.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.IDPrefix.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Attr.IDPrefix.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.IDPrefixLocal.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Attr.IDPrefixLocal.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.AutoParagraph.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/AutoFormat.AutoParagraph.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.Custom.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/AutoFormat.Custom.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.DisplayLinkURI.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/AutoFormat.DisplayLinkURI.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.Linkify.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/AutoFormat.Linkify.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.PurifierLinkify.DocURL.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/AutoFormat.PurifierLinkify.DocURL.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.PurifierLinkify.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/AutoFormat.PurifierLinkify.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveEmpty.Predicate.txt14
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveEmpty.RemoveNbsp.Exceptions.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveEmpty.RemoveNbsp.Exceptions.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveEmpty.RemoveNbsp.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveEmpty.RemoveNbsp.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveEmpty.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveEmpty.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveSpansWithoutAttributes.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveSpansWithoutAttributes.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowDuplicates.txt11
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowImportant.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/CSS.AllowImportant.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowTricky.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/CSS.AllowTricky.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowedFonts.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/CSS.AllowedFonts.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowedProperties.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/CSS.AllowedProperties.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.DefinitionRev.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/CSS.DefinitionRev.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.ForbiddenProperties.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/CSS.ForbiddenProperties.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.MaxImgLength.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/CSS.MaxImgLength.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.Proprietary.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/CSS.Proprietary.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.Trusted.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/CSS.Trusted.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Cache.DefinitionImpl.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Cache.DefinitionImpl.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Cache.SerializerPath.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Cache.SerializerPath.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Cache.SerializerPermissions.txt16
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.AggressivelyFixLt.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Core.AggressivelyFixLt.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.AggressivelyRemoveScript.txt16
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.AllowHostnameUnderscore.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Core.AllowHostnameUnderscore.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.CollectErrors.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Core.CollectErrors.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.ColorKeywords.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Core.ColorKeywords.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.ConvertDocumentToFragment.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Core.ConvertDocumentToFragment.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.DirectLexLineNumberSyncInterval.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Core.DirectLexLineNumberSyncInterval.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.DisableExcludes.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Core.DisableExcludes.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.EnableIDNA.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Core.EnableIDNA.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.Encoding.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Core.Encoding.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.EscapeInvalidChildren.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Core.EscapeInvalidChildren.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.EscapeInvalidTags.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Core.EscapeInvalidTags.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.EscapeNonASCIICharacters.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Core.EscapeNonASCIICharacters.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.HiddenElements.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Core.HiddenElements.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.Language.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Core.Language.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.LegacyEntityDecoder.txt36
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.LexerImpl.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Core.LexerImpl.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.MaintainLineNumbers.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Core.MaintainLineNumbers.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.NormalizeNewlines.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Core.NormalizeNewlines.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.RemoveInvalidImg.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Core.RemoveInvalidImg.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.RemoveProcessingInstructions.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Core.RemoveProcessingInstructions.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.RemoveScriptContents.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Core.RemoveScriptContents.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Filter.Custom.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Filter.Custom.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.Escaping.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.Escaping.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.Scope.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.Scope.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.TidyImpl.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.TidyImpl.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Filter.YouTube.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Filter.YouTube.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Allowed.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.Allowed.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedAttributes.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedAttributes.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedComments.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedComments.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedCommentsRegexp.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedCommentsRegexp.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedElements.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedElements.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedModules.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedModules.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Attr.Name.UseCDATA.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.Attr.Name.UseCDATA.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.BlockWrapper.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.BlockWrapper.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.CoreModules.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.CoreModules.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.CustomDoctype.txt9
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.DefinitionID.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.DefinitionID.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.DefinitionRev.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.DefinitionRev.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Doctype.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.Doctype.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.FlashAllowFullScreen.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.FlashAllowFullScreen.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.ForbiddenAttributes.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.ForbiddenAttributes.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.ForbiddenElements.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.ForbiddenElements.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.MaxImgLength.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.MaxImgLength.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Nofollow.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.Nofollow.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Parent.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.Parent.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Proprietary.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.Proprietary.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.SafeEmbed.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.SafeEmbed.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.SafeIframe.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.SafeIframe.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.SafeObject.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.SafeObject.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.SafeScripting.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.SafeScripting.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Strict.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.Strict.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.TargetBlank.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.TargetBlank.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.TargetNoopener.txt10
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.TargetNoreferrer.txt9
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.TidyAdd.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.TidyAdd.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.TidyLevel.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.TidyLevel.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.TidyRemove.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.TidyRemove.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Trusted.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.Trusted.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.XHTML.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/HTML.XHTML.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Output.CommentScriptContents.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Output.CommentScriptContents.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Output.FixInnerHTML.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Output.FixInnerHTML.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Output.FlashCompat.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Output.FlashCompat.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Output.Newline.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Output.Newline.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Output.SortAttr.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Output.SortAttr.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Output.TidyFormat.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Output.TidyFormat.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Test.ForceNoIconv.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/Test.ForceNoIconv.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.AllowedSchemes.txt18
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.Base.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/URI.Base.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.DefaultScheme.txt15
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.DefinitionID.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/URI.DefinitionID.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.DefinitionRev.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/URI.DefinitionRev.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.Disable.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/URI.Disable.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.DisableExternal.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/URI.DisableExternal.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.DisableExternalResources.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/URI.DisableExternalResources.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.DisableResources.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/URI.DisableResources.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.Host.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/URI.Host.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.HostBlacklist.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/URI.HostBlacklist.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.MakeAbsolute.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/URI.MakeAbsolute.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.Munge.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/URI.Munge.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.MungeResources.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/URI.MungeResources.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.MungeSecretKey.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/URI.MungeSecretKey.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.OverrideAllowedSchemes.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/URI.OverrideAllowedSchemes.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.SafeIframeRegexp.txt (renamed from library/HTMLPurifier/ConfigSchema/schema/URI.SafeIframeRegexp.txt)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/info.ini (renamed from library/HTMLPurifier/ConfigSchema/schema/info.ini)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ContentSets.php (renamed from library/HTMLPurifier/ContentSets.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Context.php (renamed from library/HTMLPurifier/Context.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Definition.php (renamed from library/HTMLPurifier/Definition.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache.php129
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Decorator.php (renamed from library/HTMLPurifier/DefinitionCache/Decorator.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Decorator/Cleanup.php (renamed from library/HTMLPurifier/DefinitionCache/Decorator/Cleanup.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Decorator/Memory.php (renamed from library/HTMLPurifier/DefinitionCache/Decorator/Memory.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Decorator/Template.php.in (renamed from library/HTMLPurifier/DefinitionCache/Decorator/Template.php.in)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Null.php (renamed from library/HTMLPurifier/DefinitionCache/Null.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Serializer.php306
-rwxr-xr-x[-rw-r--r--]vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Serializer/README (renamed from library/HTMLPurifier/DefinitionCache/Serializer/README)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCacheFactory.php (renamed from library/HTMLPurifier/DefinitionCacheFactory.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Doctype.php (renamed from library/HTMLPurifier/Doctype.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/DoctypeRegistry.php (renamed from library/HTMLPurifier/DoctypeRegistry.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ElementDef.php (renamed from library/HTMLPurifier/ElementDef.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Encoder.php617
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/EntityLookup.php (renamed from library/HTMLPurifier/EntityLookup.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/EntityLookup/entities.ser (renamed from library/HTMLPurifier/EntityLookup/entities.ser)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/EntityParser.php285
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ErrorCollector.php (renamed from library/HTMLPurifier/ErrorCollector.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/ErrorStruct.php (renamed from library/HTMLPurifier/ErrorStruct.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Exception.php (renamed from library/HTMLPurifier/Exception.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Filter.php (renamed from library/HTMLPurifier/Filter.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Filter/ExtractStyleBlocks.php341
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Filter/YouTube.php65
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Generator.php286
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLDefinition.php (renamed from library/HTMLPurifier/HTMLDefinition.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule.php (renamed from library/HTMLPurifier/HTMLModule.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Bdo.php (renamed from library/HTMLPurifier/HTMLModule/Bdo.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/CommonAttributes.php (renamed from library/HTMLPurifier/HTMLModule/CommonAttributes.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Edit.php (renamed from library/HTMLPurifier/HTMLModule/Edit.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Forms.php (renamed from library/HTMLPurifier/HTMLModule/Forms.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Hypertext.php (renamed from library/HTMLPurifier/HTMLModule/Hypertext.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Iframe.php (renamed from library/HTMLPurifier/HTMLModule/Iframe.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Image.php (renamed from library/HTMLPurifier/HTMLModule/Image.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Legacy.php (renamed from library/HTMLPurifier/HTMLModule/Legacy.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/List.php (renamed from library/HTMLPurifier/HTMLModule/List.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Name.php (renamed from library/HTMLPurifier/HTMLModule/Name.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Nofollow.php (renamed from library/HTMLPurifier/HTMLModule/Nofollow.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/NonXMLCommonAttributes.php (renamed from library/HTMLPurifier/HTMLModule/NonXMLCommonAttributes.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Object.php (renamed from library/HTMLPurifier/HTMLModule/Object.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Presentation.php (renamed from library/HTMLPurifier/HTMLModule/Presentation.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Proprietary.php (renamed from library/HTMLPurifier/HTMLModule/Proprietary.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Ruby.php (renamed from library/HTMLPurifier/HTMLModule/Ruby.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/SafeEmbed.php (renamed from library/HTMLPurifier/HTMLModule/SafeEmbed.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/SafeObject.php (renamed from library/HTMLPurifier/HTMLModule/SafeObject.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/SafeScripting.php (renamed from library/HTMLPurifier/HTMLModule/SafeScripting.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Scripting.php (renamed from library/HTMLPurifier/HTMLModule/Scripting.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/StyleAttribute.php (renamed from library/HTMLPurifier/HTMLModule/StyleAttribute.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tables.php (renamed from library/HTMLPurifier/HTMLModule/Tables.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Target.php (renamed from library/HTMLPurifier/HTMLModule/Target.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/TargetBlank.php (renamed from library/HTMLPurifier/HTMLModule/TargetBlank.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/TargetNoopener.php21
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/TargetNoreferrer.php21
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Text.php (renamed from library/HTMLPurifier/HTMLModule/Text.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy.php (renamed from library/HTMLPurifier/HTMLModule/Tidy.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/Name.php (renamed from library/HTMLPurifier/HTMLModule/Tidy/Name.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/Proprietary.php (renamed from library/HTMLPurifier/HTMLModule/Tidy/Proprietary.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/Strict.php (renamed from library/HTMLPurifier/HTMLModule/Tidy/Strict.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/Transitional.php (renamed from library/HTMLPurifier/HTMLModule/Tidy/Transitional.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/XHTML.php (renamed from library/HTMLPurifier/HTMLModule/Tidy/XHTML.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/XHTMLAndHTML4.php (renamed from library/HTMLPurifier/HTMLModule/Tidy/XHTMLAndHTML4.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/XMLCommonAttributes.php (renamed from library/HTMLPurifier/HTMLModule/XMLCommonAttributes.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModuleManager.php467
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/IDAccumulator.php (renamed from library/HTMLPurifier/IDAccumulator.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector.php (renamed from library/HTMLPurifier/Injector.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/AutoParagraph.php (renamed from library/HTMLPurifier/Injector/AutoParagraph.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/DisplayLinkURI.php (renamed from library/HTMLPurifier/Injector/DisplayLinkURI.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/Linkify.php64
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/PurifierLinkify.php (renamed from library/HTMLPurifier/Injector/PurifierLinkify.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/RemoveEmpty.php112
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/RemoveSpansWithoutAttributes.php (renamed from library/HTMLPurifier/Injector/RemoveSpansWithoutAttributes.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/SafeObject.php124
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Language.php (renamed from library/HTMLPurifier/Language.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Language/classes/en-x-test.php (renamed from library/HTMLPurifier/Language/classes/en-x-test.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Language/messages/en-x-test.php (renamed from library/HTMLPurifier/Language/messages/en-x-test.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Language/messages/en-x-testmini.php (renamed from library/HTMLPurifier/Language/messages/en-x-testmini.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Language/messages/en.php (renamed from library/HTMLPurifier/Language/messages/en.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/LanguageFactory.php (renamed from library/HTMLPurifier/LanguageFactory.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Length.php (renamed from library/HTMLPurifier/Length.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Lexer.php382
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Lexer/DOMLex.php291
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Lexer/DirectLex.php539
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Lexer/PH5P.php4788
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Node.php (renamed from library/HTMLPurifier/Node.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Node/Comment.php (renamed from library/HTMLPurifier/Node/Comment.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Node/Element.php (renamed from library/HTMLPurifier/Node/Element.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Node/Text.php (renamed from library/HTMLPurifier/Node/Text.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/PercentEncoder.php (renamed from library/HTMLPurifier/PercentEncoder.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Printer.php (renamed from library/HTMLPurifier/Printer.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Printer/CSSDefinition.php (renamed from library/HTMLPurifier/Printer/CSSDefinition.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Printer/ConfigForm.css (renamed from library/HTMLPurifier/Printer/ConfigForm.css)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Printer/ConfigForm.js (renamed from library/HTMLPurifier/Printer/ConfigForm.js)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Printer/ConfigForm.php451
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Printer/HTMLDefinition.php (renamed from library/HTMLPurifier/Printer/HTMLDefinition.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/PropertyList.php (renamed from library/HTMLPurifier/PropertyList.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/PropertyListIterator.php (renamed from library/HTMLPurifier/PropertyListIterator.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Queue.php (renamed from library/HTMLPurifier/Queue.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Strategy.php (renamed from library/HTMLPurifier/Strategy.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/Composite.php (renamed from library/HTMLPurifier/Strategy/Composite.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/Core.php (renamed from library/HTMLPurifier/Strategy/Core.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/FixNesting.php (renamed from library/HTMLPurifier/Strategy/FixNesting.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/MakeWellFormed.php659
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/RemoveForeignElements.php (renamed from library/HTMLPurifier/Strategy/RemoveForeignElements.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/ValidateAttributes.php (renamed from library/HTMLPurifier/Strategy/ValidateAttributes.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/StringHash.php (renamed from library/HTMLPurifier/StringHash.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/StringHashParser.php (renamed from library/HTMLPurifier/StringHashParser.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/TagTransform.php (renamed from library/HTMLPurifier/TagTransform.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/TagTransform/Font.php (renamed from library/HTMLPurifier/TagTransform/Font.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/TagTransform/Simple.php (renamed from library/HTMLPurifier/TagTransform/Simple.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Token.php100
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Token/Comment.php (renamed from library/HTMLPurifier/Token/Comment.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Token/Empty.php (renamed from library/HTMLPurifier/Token/Empty.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Token/End.php (renamed from library/HTMLPurifier/Token/End.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Token/Start.php (renamed from library/HTMLPurifier/Token/Start.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Token/Tag.php (renamed from library/HTMLPurifier/Token/Tag.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Token/Text.php (renamed from library/HTMLPurifier/Token/Text.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/TokenFactory.php (renamed from library/HTMLPurifier/TokenFactory.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/URI.php316
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIDefinition.php (renamed from library/HTMLPurifier/URIDefinition.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter.php (renamed from library/HTMLPurifier/URIFilter.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/DisableExternal.php (renamed from library/HTMLPurifier/URIFilter/DisableExternal.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/DisableExternalResources.php (renamed from library/HTMLPurifier/URIFilter/DisableExternalResources.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/DisableResources.php (renamed from library/HTMLPurifier/URIFilter/DisableResources.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/HostBlacklist.php (renamed from library/HTMLPurifier/URIFilter/HostBlacklist.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/MakeAbsolute.php (renamed from library/HTMLPurifier/URIFilter/MakeAbsolute.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/Munge.php (renamed from library/HTMLPurifier/URIFilter/Munge.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/SafeIframe.php (renamed from library/HTMLPurifier/URIFilter/SafeIframe.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIParser.php (renamed from library/HTMLPurifier/URIParser.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme.php (renamed from library/HTMLPurifier/URIScheme.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/data.php136
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/file.php (renamed from library/HTMLPurifier/URIScheme/file.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/ftp.php (renamed from library/HTMLPurifier/URIScheme/ftp.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/http.php (renamed from library/HTMLPurifier/URIScheme/http.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/https.php (renamed from library/HTMLPurifier/URIScheme/https.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/mailto.php (renamed from library/HTMLPurifier/URIScheme/mailto.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/news.php (renamed from library/HTMLPurifier/URIScheme/news.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/nntp.php (renamed from library/HTMLPurifier/URIScheme/nntp.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/tel.php46
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/URISchemeRegistry.php (renamed from library/HTMLPurifier/URISchemeRegistry.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/UnitConverter.php (renamed from library/HTMLPurifier/UnitConverter.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/VarParser.php (renamed from library/HTMLPurifier/VarParser.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/VarParser/Flexible.php (renamed from library/HTMLPurifier/VarParser/Flexible.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/VarParser/Native.php (renamed from library/HTMLPurifier/VarParser/Native.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/VarParserException.php (renamed from library/HTMLPurifier/VarParserException.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/library/HTMLPurifier/Zipper.php (renamed from library/HTMLPurifier/Zipper.php)0
-rw-r--r--vendor/ezyang/htmlpurifier/maintenance/.htaccess1
-rw-r--r--vendor/ezyang/htmlpurifier/maintenance/PH5P.patch102
-rw-r--r--vendor/ezyang/htmlpurifier/maintenance/PH5P.php3889
-rw-r--r--vendor/ezyang/htmlpurifier/maintenance/add-vimline.php130
-rw-r--r--vendor/ezyang/htmlpurifier/maintenance/common.php25
-rwxr-xr-xvendor/ezyang/htmlpurifier/maintenance/compile-doxygen.sh11
-rw-r--r--vendor/ezyang/htmlpurifier/maintenance/config-scanner.php155
-rwxr-xr-xvendor/ezyang/htmlpurifier/maintenance/flush-definition-cache.php42
-rw-r--r--vendor/ezyang/htmlpurifier/maintenance/flush.php30
-rwxr-xr-xvendor/ezyang/htmlpurifier/maintenance/generate-entity-file.php75
-rw-r--r--vendor/ezyang/htmlpurifier/maintenance/generate-includes.php192
-rw-r--r--vendor/ezyang/htmlpurifier/maintenance/generate-ph5p-patch.php22
-rw-r--r--vendor/ezyang/htmlpurifier/maintenance/generate-schema-cache.php45
-rwxr-xr-xvendor/ezyang/htmlpurifier/maintenance/generate-standalone.php159
-rwxr-xr-xvendor/ezyang/htmlpurifier/maintenance/merge-library.php11
-rw-r--r--vendor/ezyang/htmlpurifier/maintenance/old-extract-schema.php71
-rw-r--r--vendor/ezyang/htmlpurifier/maintenance/old-remove-require-once.php32
-rw-r--r--vendor/ezyang/htmlpurifier/maintenance/old-remove-schema-def.php32
-rwxr-xr-xvendor/ezyang/htmlpurifier/maintenance/regenerate-docs.sh5
-rw-r--r--vendor/ezyang/htmlpurifier/maintenance/remove-trailing-whitespace.php37
-rw-r--r--vendor/ezyang/htmlpurifier/maintenance/rename-config.php84
-rw-r--r--vendor/ezyang/htmlpurifier/maintenance/update-config.php34
-rw-r--r--vendor/ezyang/htmlpurifier/package.php61
-rw-r--r--vendor/ezyang/htmlpurifier/phpdoc.ini102
-rw-r--r--vendor/ezyang/htmlpurifier/plugins/modx.txt112
-rw-r--r--vendor/ezyang/htmlpurifier/plugins/phorum/.gitignore2
-rw-r--r--vendor/ezyang/htmlpurifier/plugins/phorum/Changelog27
-rw-r--r--vendor/ezyang/htmlpurifier/plugins/phorum/INSTALL84
-rw-r--r--vendor/ezyang/htmlpurifier/plugins/phorum/README45
-rw-r--r--vendor/ezyang/htmlpurifier/plugins/phorum/config.default.php57
-rw-r--r--vendor/ezyang/htmlpurifier/plugins/phorum/htmlpurifier.php316
-rw-r--r--vendor/ezyang/htmlpurifier/plugins/phorum/info.txt18
-rw-r--r--vendor/ezyang/htmlpurifier/plugins/phorum/init-config.php30
-rw-r--r--vendor/ezyang/htmlpurifier/plugins/phorum/migrate.bbcode.php31
-rw-r--r--vendor/ezyang/htmlpurifier/plugins/phorum/settings.php64
-rw-r--r--vendor/ezyang/htmlpurifier/plugins/phorum/settings/form.php95
-rw-r--r--vendor/ezyang/htmlpurifier/plugins/phorum/settings/migrate-sigs-form.php22
-rw-r--r--vendor/ezyang/htmlpurifier/plugins/phorum/settings/migrate-sigs.php79
-rw-r--r--vendor/ezyang/htmlpurifier/plugins/phorum/settings/save.php29
-rw-r--r--vendor/ezyang/htmlpurifier/release1-update.php110
-rw-r--r--vendor/ezyang/htmlpurifier/release2-tag.php22
-rw-r--r--vendor/ezyang/htmlpurifier/test-settings.sample.php74
-rw-r--r--vendor/ezyang/htmlpurifier/test-settings.travis.php72
-rw-r--r--vendor/league/html-to-markdown/CHANGELOG.md214
-rw-r--r--vendor/league/html-to-markdown/CONDUCT.md22
-rw-r--r--vendor/league/html-to-markdown/LICENSE22
-rw-r--r--vendor/league/html-to-markdown/README.md196
-rwxr-xr-xvendor/league/html-to-markdown/bin/html-to-markdown108
-rw-r--r--vendor/league/html-to-markdown/composer.json48
-rw-r--r--vendor/league/html-to-markdown/src/Configuration.php60
-rw-r--r--vendor/league/html-to-markdown/src/ConfigurationAwareInterface.php11
-rw-r--r--vendor/league/html-to-markdown/src/Converter/BlockquoteConverter.php44
-rw-r--r--vendor/league/html-to-markdown/src/Converter/CodeConverter.php62
-rw-r--r--vendor/league/html-to-markdown/src/Converter/CommentConverter.php26
-rw-r--r--vendor/league/html-to-markdown/src/Converter/ConverterInterface.php20
-rw-r--r--vendor/league/html-to-markdown/src/Converter/DefaultConverter.php50
-rw-r--r--vendor/league/html-to-markdown/src/Converter/DivConverter.php45
-rw-r--r--vendor/league/html-to-markdown/src/Converter/EmphasisConverter.php57
-rw-r--r--vendor/league/html-to-markdown/src/Converter/HardBreakConverter.php41
-rw-r--r--vendor/league/html-to-markdown/src/Converter/HeaderConverter.php78
-rw-r--r--vendor/league/html-to-markdown/src/Converter/HorizontalRuleConverter.php26
-rw-r--r--vendor/league/html-to-markdown/src/Converter/ImageConverter.php35
-rw-r--r--vendor/league/html-to-markdown/src/Converter/LinkConverter.php52
-rw-r--r--vendor/league/html-to-markdown/src/Converter/ListBlockConverter.php26
-rw-r--r--vendor/league/html-to-markdown/src/Converter/ListItemConverter.php47
-rw-r--r--vendor/league/html-to-markdown/src/Converter/ParagraphConverter.php124
-rw-r--r--vendor/league/html-to-markdown/src/Converter/PreformattedConverter.php59
-rw-r--r--vendor/league/html-to-markdown/src/Converter/TextConverter.php46
-rw-r--r--vendor/league/html-to-markdown/src/Element.php257
-rw-r--r--vendor/league/html-to-markdown/src/ElementInterface.php80
-rw-r--r--vendor/league/html-to-markdown/src/Environment.php104
-rw-r--r--vendor/league/html-to-markdown/src/HtmlConverter.php231
-rw-r--r--vendor/michelf/php-markdown/License.md36
-rw-r--r--vendor/michelf/php-markdown/Michelf/Markdown.inc.php10
-rw-r--r--vendor/michelf/php-markdown/Michelf/Markdown.php1896
-rw-r--r--vendor/michelf/php-markdown/Michelf/MarkdownExtra.inc.php11
-rw-r--r--vendor/michelf/php-markdown/Michelf/MarkdownExtra.php1785
-rw-r--r--vendor/michelf/php-markdown/Michelf/MarkdownInterface.inc.php9
-rw-r--r--vendor/michelf/php-markdown/Michelf/MarkdownInterface.php38
-rw-r--r--vendor/michelf/php-markdown/Readme.md384
-rw-r--r--vendor/michelf/php-markdown/Readme.php31
-rw-r--r--vendor/michelf/php-markdown/composer.json31
-rw-r--r--vendor/sabre/dav/.travis.yml7
-rw-r--r--vendor/sabre/dav/CHANGELOG.md56
-rw-r--r--vendor/sabre/dav/README.md2
-rwxr-xr-x[-rw-r--r--]vendor/sabre/dav/bin/build.php0
-rwxr-xr-x[-rw-r--r--]vendor/sabre/dav/bin/googlecode_upload.py0
-rwxr-xr-x[-rw-r--r--]vendor/sabre/dav/bin/migrateto20.php0
-rwxr-xr-x[-rw-r--r--]vendor/sabre/dav/bin/migrateto21.php0
-rwxr-xr-x[-rw-r--r--]vendor/sabre/dav/bin/migrateto30.php0
-rwxr-xr-x[-rw-r--r--]vendor/sabre/dav/bin/migrateto32.php0
-rwxr-xr-x[-rw-r--r--]vendor/sabre/dav/bin/sabredav.php0
-rw-r--r--vendor/sabre/dav/composer.json4
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Backend/AbstractBackend.php6
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Backend/NotificationSupport.php4
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Backend/PDO.php68
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Backend/SharingSupport.php6
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Backend/SimplePDO.php14
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Backend/SubscriptionSupport.php2
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Calendar.php2
-rw-r--r--vendor/sabre/dav/lib/CalDAV/CalendarHome.php8
-rw-r--r--vendor/sabre/dav/lib/CalDAV/CalendarObject.php2
-rw-r--r--vendor/sabre/dav/lib/CalDAV/CalendarQueryValidator.php4
-rw-r--r--vendor/sabre/dav/lib/CalDAV/CalendarRoot.php2
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Exception/InvalidComponentType.php2
-rw-r--r--vendor/sabre/dav/lib/CalDAV/ICSExportPlugin.php6
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Notifications/Collection.php4
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Notifications/INode.php8
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Notifications/Node.php12
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Notifications/Plugin.php4
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Plugin.php10
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Principal/ProxyRead.php4
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Principal/ProxyWrite.php4
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Schedule/IMipPlugin.php2
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Schedule/Inbox.php6
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Schedule/Outbox.php2
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Schedule/Plugin.php33
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Schedule/SchedulingObject.php2
-rw-r--r--vendor/sabre/dav/lib/CalDAV/SharingPlugin.php3
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Subscriptions/Plugin.php2
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Subscriptions/Subscription.php12
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Xml/Filter/CalendarData.php8
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Xml/Filter/CompFilter.php8
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Xml/Filter/ParamFilter.php4
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Xml/Filter/PropFilter.php8
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Xml/Notification/Invite.php10
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Xml/Notification/InviteReply.php6
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Xml/Notification/NotificationInterface.php2
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Xml/Notification/SystemStatus.php2
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Xml/Property/AllowedSharingModes.php8
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Xml/Property/EmailAddressSet.php4
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Xml/Property/Invite.php13
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Xml/Property/ScheduleCalendarTransp.php10
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Xml/Property/SupportedCalendarComponentSet.php8
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Xml/Property/SupportedCalendarData.php8
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Xml/Property/SupportedCollationSet.php6
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Xml/Request/CalendarMultiGetReport.php6
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Xml/Request/CalendarQueryReport.php8
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Xml/Request/FreeBusyQueryReport.php2
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Xml/Request/InviteReply.php4
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Xml/Request/MkCalendar.php6
-rw-r--r--vendor/sabre/dav/lib/CalDAV/Xml/Request/Share.php2
-rw-r--r--vendor/sabre/dav/lib/CardDAV/AddressBook.php2
-rw-r--r--vendor/sabre/dav/lib/CardDAV/AddressBookHome.php2
-rw-r--r--vendor/sabre/dav/lib/CardDAV/AddressBookRoot.php2
-rw-r--r--vendor/sabre/dav/lib/CardDAV/Backend/BackendInterface.php2
-rw-r--r--vendor/sabre/dav/lib/CardDAV/Backend/PDO.php6
-rw-r--r--vendor/sabre/dav/lib/CardDAV/Card.php2
-rw-r--r--vendor/sabre/dav/lib/CardDAV/Plugin.php19
-rw-r--r--vendor/sabre/dav/lib/CardDAV/VCFExportPlugin.php4
-rw-r--r--vendor/sabre/dav/lib/CardDAV/Xml/Filter/AddressData.php8
-rw-r--r--vendor/sabre/dav/lib/CardDAV/Xml/Filter/ParamFilter.php6
-rw-r--r--vendor/sabre/dav/lib/CardDAV/Xml/Filter/PropFilter.php6
-rw-r--r--vendor/sabre/dav/lib/CardDAV/Xml/Property/SupportedAddressData.php6
-rw-r--r--vendor/sabre/dav/lib/CardDAV/Xml/Property/SupportedCollationSet.php4
-rw-r--r--vendor/sabre/dav/lib/CardDAV/Xml/Request/AddressBookMultiGetReport.php2
-rw-r--r--vendor/sabre/dav/lib/CardDAV/Xml/Request/AddressBookQueryReport.php13
-rw-r--r--vendor/sabre/dav/lib/DAV/Auth/Backend/AbstractDigest.php2
-rw-r--r--vendor/sabre/dav/lib/DAV/Auth/Backend/PDO.php2
-rw-r--r--vendor/sabre/dav/lib/DAV/Auth/Plugin.php6
-rw-r--r--vendor/sabre/dav/lib/DAV/Browser/GuessContentType.php4
-rw-r--r--vendor/sabre/dav/lib/DAV/Browser/MapGetToPropFind.php2
-rw-r--r--vendor/sabre/dav/lib/DAV/Browser/Plugin.php62
-rw-r--r--vendor/sabre/dav/lib/DAV/Browser/PropFindAll.php2
-rw-r--r--vendor/sabre/dav/lib/DAV/Client.php6
-rw-r--r--vendor/sabre/dav/lib/DAV/Collection.php2
-rw-r--r--vendor/sabre/dav/lib/DAV/CorePlugin.php30
-rw-r--r--vendor/sabre/dav/lib/DAV/Exception/InvalidResourceType.php2
-rw-r--r--vendor/sabre/dav/lib/DAV/FS/Node.php2
-rw-r--r--vendor/sabre/dav/lib/DAV/File.php2
-rw-r--r--vendor/sabre/dav/lib/DAV/IFile.php4
-rw-r--r--vendor/sabre/dav/lib/DAV/IMoveTarget.php2
-rw-r--r--vendor/sabre/dav/lib/DAV/Locks/Backend/PDO.php4
-rw-r--r--vendor/sabre/dav/lib/DAV/Locks/Plugin.php6
-rw-r--r--vendor/sabre/dav/lib/DAV/MkCol.php1
-rw-r--r--vendor/sabre/dav/lib/DAV/Mount/Plugin.php2
-rw-r--r--vendor/sabre/dav/lib/DAV/Node.php4
-rw-r--r--vendor/sabre/dav/lib/DAV/PartialUpdate/Plugin.php2
-rw-r--r--vendor/sabre/dav/lib/DAV/PropFind.php2
-rw-r--r--vendor/sabre/dav/lib/DAV/PropertyStorage/Backend/BackendInterface.php2
-rw-r--r--vendor/sabre/dav/lib/DAV/PropertyStorage/Backend/PDO.php2
-rw-r--r--vendor/sabre/dav/lib/DAV/PropertyStorage/Plugin.php13
-rw-r--r--vendor/sabre/dav/lib/DAV/Server.php101
-rw-r--r--vendor/sabre/dav/lib/DAV/Sharing/Plugin.php4
-rw-r--r--vendor/sabre/dav/lib/DAV/Sync/Plugin.php2
-rw-r--r--vendor/sabre/dav/lib/DAV/TemporaryFileFilterPlugin.php8
-rw-r--r--vendor/sabre/dav/lib/DAV/Version.php2
-rw-r--r--vendor/sabre/dav/lib/DAV/Xml/Element/Prop.php6
-rw-r--r--vendor/sabre/dav/lib/DAV/Xml/Element/Response.php2
-rw-r--r--vendor/sabre/dav/lib/DAV/Xml/Element/Sharee.php4
-rw-r--r--vendor/sabre/dav/lib/DAV/Xml/Property/Complex.php2
-rw-r--r--vendor/sabre/dav/lib/DAV/Xml/Property/GetLastModified.php8
-rw-r--r--vendor/sabre/dav/lib/DAV/Xml/Property/Href.php10
-rw-r--r--vendor/sabre/dav/lib/DAV/Xml/Property/Invite.php6
-rw-r--r--vendor/sabre/dav/lib/DAV/Xml/Property/LocalHref.php4
-rw-r--r--vendor/sabre/dav/lib/DAV/Xml/Property/ResourceType.php4
-rw-r--r--vendor/sabre/dav/lib/DAV/Xml/Property/ShareAccess.php6
-rw-r--r--vendor/sabre/dav/lib/DAV/Xml/Property/SupportedLock.php8
-rw-r--r--vendor/sabre/dav/lib/DAV/Xml/Property/SupportedMethodSet.php4
-rw-r--r--vendor/sabre/dav/lib/DAV/Xml/Property/SupportedReportSet.php4
-rw-r--r--vendor/sabre/dav/lib/DAV/Xml/Request/Lock.php2
-rw-r--r--vendor/sabre/dav/lib/DAV/Xml/Request/MkCol.php6
-rw-r--r--vendor/sabre/dav/lib/DAV/Xml/Request/PropFind.php2
-rw-r--r--vendor/sabre/dav/lib/DAV/Xml/Request/PropPatch.php10
-rw-r--r--vendor/sabre/dav/lib/DAV/Xml/Request/ShareResource.php4
-rw-r--r--vendor/sabre/dav/lib/DAV/Xml/Request/SyncCollectionReport.php8
-rw-r--r--vendor/sabre/dav/lib/DAV/Xml/Response/MultiStatus.php2
-rw-r--r--vendor/sabre/dav/lib/DAVACL/Exception/NotRecognizedPrincipal.php2
-rw-r--r--vendor/sabre/dav/lib/DAVACL/FS/Collection.php4
-rw-r--r--vendor/sabre/dav/lib/DAVACL/FS/File.php2
-rw-r--r--vendor/sabre/dav/lib/DAVACL/FS/HomeCollection.php2
-rw-r--r--vendor/sabre/dav/lib/DAVACL/Plugin.php38
-rw-r--r--vendor/sabre/dav/lib/DAVACL/Principal.php2
-rw-r--r--vendor/sabre/dav/lib/DAVACL/PrincipalBackend/BackendInterface.php2
-rw-r--r--vendor/sabre/dav/lib/DAVACL/PrincipalBackend/PDO.php8
-rw-r--r--vendor/sabre/dav/lib/DAVACL/PrincipalCollection.php2
-rw-r--r--vendor/sabre/dav/lib/DAVACL/Xml/Property/Acl.php6
-rw-r--r--vendor/sabre/dav/lib/DAVACL/Xml/Property/AclRestrictions.php6
-rw-r--r--vendor/sabre/dav/lib/DAVACL/Xml/Property/CurrentUserPrivilegeSet.php6
-rw-r--r--vendor/sabre/dav/lib/DAVACL/Xml/Property/Principal.php4
-rw-r--r--vendor/sabre/dav/lib/DAVACL/Xml/Property/SupportedPrivilegeSet.php11
-rw-r--r--vendor/sabre/dav/lib/DAVACL/Xml/Request/AclPrincipalPropSetReport.php6
-rw-r--r--vendor/sabre/dav/lib/DAVACL/Xml/Request/ExpandPropertyReport.php2
-rw-r--r--vendor/sabre/dav/lib/DAVACL/Xml/Request/PrincipalMatchReport.php6
-rw-r--r--vendor/sabre/dav/lib/DAVACL/Xml/Request/PrincipalPropertySearchReport.php4
-rw-r--r--vendor/sabre/dav/lib/DAVACL/Xml/Request/PrincipalSearchPropertySetReport.php4
-rw-r--r--vendor/sabre/dav/tests/Sabre/CalDAV/Backend/AbstractPDOTest.php14
-rw-r--r--vendor/sabre/dav/tests/Sabre/CalDAV/Backend/Mock.php2
-rw-r--r--vendor/sabre/dav/tests/Sabre/CalDAV/CalendarObjectTest.php2
-rw-r--r--vendor/sabre/dav/tests/Sabre/CalDAV/CalendarQueryValidatorTest.php3
-rw-r--r--vendor/sabre/dav/tests/Sabre/CalDAV/FreeBusyReportTest.php4
-rw-r--r--vendor/sabre/dav/tests/Sabre/CalDAV/ICSExportPluginTest.php2
-rw-r--r--vendor/sabre/dav/tests/Sabre/CalDAV/PluginTest.php6
-rw-r--r--vendor/sabre/dav/tests/Sabre/CalDAV/SharingPluginTest.php4
-rw-r--r--vendor/sabre/dav/tests/Sabre/CardDAV/AddressBookQueryTest.php51
-rw-r--r--vendor/sabre/dav/tests/Sabre/CardDAV/AddressBookTest.php6
-rw-r--r--vendor/sabre/dav/tests/Sabre/CardDAV/Backend/Mock.php13
-rw-r--r--vendor/sabre/dav/tests/Sabre/CardDAV/MultiGetTest.php2
-rw-r--r--vendor/sabre/dav/tests/Sabre/CardDAV/SogoStripContentTypeTest.php2
-rw-r--r--vendor/sabre/dav/tests/Sabre/CardDAV/ValidateFilterTest.php5
-rw-r--r--vendor/sabre/dav/tests/Sabre/CardDAV/ValidateVCardTest.php10
-rw-r--r--vendor/sabre/dav/tests/Sabre/DAV/Auth/Backend/Mock.php2
-rw-r--r--vendor/sabre/dav/tests/Sabre/DAV/Auth/PluginTest.php2
-rw-r--r--vendor/sabre/dav/tests/Sabre/DAV/ClientTest.php6
-rw-r--r--vendor/sabre/dav/tests/Sabre/DAV/Exception/LockedTest.php2
-rw-r--r--vendor/sabre/dav/tests/Sabre/DAV/Issue33Test.php2
-rw-r--r--vendor/sabre/dav/tests/Sabre/DAV/Locks/MSWordTest.php8
-rw-r--r--vendor/sabre/dav/tests/Sabre/DAV/Locks/PluginTest.php6
-rw-r--r--vendor/sabre/dav/tests/Sabre/DAV/Mock/Collection.php3
-rw-r--r--vendor/sabre/dav/tests/Sabre/DAV/Mock/File.php7
-rw-r--r--vendor/sabre/dav/tests/Sabre/DAV/PartialUpdate/SpecificationTest.php5
-rw-r--r--vendor/sabre/dav/tests/Sabre/DAV/ServerEventsTest.php8
-rw-r--r--vendor/sabre/dav/tests/Sabre/DAV/ServerRangeTest.php2
-rw-r--r--vendor/sabre/dav/tests/Sabre/DAV/StringUtilTest.php7
-rw-r--r--vendor/sabre/dav/tests/Sabre/DAV/TreeTest.php5
-rw-r--r--vendor/sabre/dav/tests/Sabre/DAVACL/PrincipalBackend/Mock.php2
-rw-r--r--vendor/sabre/http/.travis.yml4
-rw-r--r--vendor/sabre/http/CHANGELOG.md14
-rw-r--r--vendor/sabre/http/LICENSE2
-rw-r--r--vendor/sabre/http/composer.json1
-rw-r--r--vendor/sabre/http/lib/Message.php12
-rw-r--r--vendor/sabre/http/lib/MessageDecoratorTrait.php7
-rw-r--r--vendor/sabre/http/lib/MessageInterface.php3
-rw-r--r--vendor/sabre/http/lib/Request.php2
-rw-r--r--vendor/sabre/http/lib/Response.php3
-rw-r--r--vendor/sabre/http/lib/ResponseInterface.php2
-rw-r--r--vendor/sabre/http/lib/Sapi.php10
-rw-r--r--vendor/sabre/http/lib/URLUtil.php2
-rw-r--r--vendor/sabre/http/lib/Util.php2
-rw-r--r--vendor/sabre/http/lib/Version.php2
-rw-r--r--vendor/sabre/http/lib/functions.php4
-rw-r--r--vendor/sabre/uri/.travis.yml2
-rw-r--r--vendor/sabre/uri/CHANGELOG.md23
-rw-r--r--vendor/sabre/uri/LICENSE2
-rw-r--r--vendor/sabre/uri/README.md8
-rw-r--r--vendor/sabre/uri/composer.json4
-rw-r--r--vendor/sabre/uri/lib/InvalidUriException.php17
-rw-r--r--vendor/sabre/uri/lib/Version.php2
-rw-r--r--vendor/sabre/uri/lib/functions.php99
-rw-r--r--vendor/sabre/vobject/.travis.yml3
-rw-r--r--vendor/sabre/vobject/CHANGELOG.md18
-rwxr-xr-xvendor/sabre/vobject/bin/fetch_windows_zones.php2
-rw-r--r--vendor/sabre/vobject/composer.json4
-rw-r--r--vendor/sabre/vobject/lib/BirthdayCalendarGenerator.php8
-rw-r--r--vendor/sabre/vobject/lib/Component/VAlarm.php4
-rw-r--r--vendor/sabre/vobject/lib/Component/VCalendar.php112
-rw-r--r--vendor/sabre/vobject/lib/Component/VCard.php44
-rw-r--r--vendor/sabre/vobject/lib/DateTimeParser.php14
-rw-r--r--vendor/sabre/vobject/lib/FreeBusyGenerator.php6
-rw-r--r--vendor/sabre/vobject/lib/Parameter.php2
-rw-r--r--vendor/sabre/vobject/lib/Parser/Json.php2
-rw-r--r--vendor/sabre/vobject/lib/Parser/MimeDir.php4
-rw-r--r--vendor/sabre/vobject/lib/Parser/XML.php22
-rw-r--r--vendor/sabre/vobject/lib/Property/ICalendar/Duration.php2
-rw-r--r--vendor/sabre/vobject/lib/Property/ICalendar/Period.php2
-rw-r--r--vendor/sabre/vobject/lib/Property/ICalendar/Recur.php48
-rw-r--r--vendor/sabre/vobject/lib/Property/Text.php4
-rw-r--r--vendor/sabre/vobject/lib/Property/Uri.php2
-rw-r--r--vendor/sabre/vobject/lib/Property/VCard/DateAndOrTime.php24
-rw-r--r--vendor/sabre/vobject/lib/Recur/EventIterator.php6
-rw-r--r--vendor/sabre/vobject/lib/Recur/RRuleIterator.php93
-rw-r--r--vendor/sabre/vobject/lib/TimeZoneUtil.php10
-rw-r--r--vendor/sabre/vobject/lib/Version.php2
-rw-r--r--vendor/sabre/vobject/lib/timezonedata/lotuszones.php158
-rw-r--r--vendor/sabre/vobject/lib/timezonedata/windowszones.php32
-rw-r--r--vendor/simplepie/simplepie/LICENSE.txt (renamed from library/simplepie/LICENSE.txt)0
-rw-r--r--vendor/simplepie/simplepie/README.markdown113
-rw-r--r--vendor/simplepie/simplepie/autoloader.php85
-rw-r--r--vendor/simplepie/simplepie/composer.json40
-rw-r--r--vendor/simplepie/simplepie/db.sql40
-rw-r--r--vendor/simplepie/simplepie/idn/LICENCE (renamed from library/simplepie/idn/LICENCE)0
-rw-r--r--vendor/simplepie/simplepie/idn/ReadMe.txt (renamed from library/simplepie/idn/ReadMe.txt)0
-rw-r--r--vendor/simplepie/simplepie/idn/idna_convert.class.php969
-rw-r--r--vendor/simplepie/simplepie/idn/npdata.ser (renamed from library/simplepie/idn/npdata.ser)0
-rwxr-xr-xvendor/simplepie/simplepie/library/SimplePie.php3303
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Author.php156
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Cache.php134
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Cache/Base.php113
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Cache/DB.php136
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Cache/File.php164
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Cache/Memcache.php180
-rwxr-xr-xvendor/simplepie/simplepie/library/SimplePie/Cache/Memcached.php166
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Cache/MySQL.php454
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Cache/Redis.php166
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Caption.php209
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Category.php163
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Content/Type/Sniffer.php331
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Copyright.php129
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Core.php56
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Credit.php155
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Decode/HTML/Entities.php615
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Enclosure.php1379
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Exception.php51
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/File.php306
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/HTTP/Parser.php499
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/IRI.php1257
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Item.php3009
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Locator.php429
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Misc.php2279
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Net/IPv6.php275
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Parse/Date.php983
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Parser.php656
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Rating.php128
-rwxr-xr-xvendor/simplepie/simplepie/library/SimplePie/Registry.php224
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Restriction.php154
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Sanitize.php591
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/Source.php610
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/XML/Declaration/Parser.php361
-rw-r--r--vendor/simplepie/simplepie/library/SimplePie/gzdecode.php370
-rw-r--r--view/css/bootstrap-red.css89
-rw-r--r--view/css/cdav_addressbook.css103
-rw-r--r--view/css/cdav_calendar.css22
-rw-r--r--view/css/conversation.css152
-rw-r--r--view/css/default.css4
-rw-r--r--view/css/mod_apps.css5
-rw-r--r--view/css/mod_chat.css4
-rw-r--r--view/css/mod_events.css5
-rw-r--r--view/css/mod_help.css16
-rw-r--r--view/css/mod_mail.css31
-rw-r--r--view/css/mod_manage.css12
-rw-r--r--view/css/mod_setup.css34
-rw-r--r--view/css/mod_webpages.css16
-rw-r--r--view/css/mod_wiki.css20
-rw-r--r--view/css/navbar_tucson.css3
-rw-r--r--view/css/widgets.css71
-rw-r--r--view/de/hmessages.po17951
-rw-r--r--view/de/hstrings.php4369
-rw-r--r--view/de/htconfig.tpl7
-rw-r--r--view/en-au/htconfig.tpl7
-rw-r--r--view/en-gb/htconfig.tpl8
-rw-r--r--view/en/htconfig.tpl9
-rw-r--r--view/fr/hmessages.po17098
-rw-r--r--view/fr/hstrings.php4120
-rw-r--r--view/fr/htconfig.tpl9
-rw-r--r--view/it/htconfig.tpl8
-rw-r--r--view/js/acl.js20
-rw-r--r--view/js/autocomplete.js36
-rw-r--r--view/js/jquery.js8
-rw-r--r--view/js/jquery.spin.js79
-rw-r--r--view/js/main.js450
-rw-r--r--view/js/mod_cards.js9
-rw-r--r--view/js/mod_cloud.js2
-rw-r--r--view/js/mod_connedit.js2
-rw-r--r--view/js/mod_display.js5
-rw-r--r--view/js/mod_help.js124
-rw-r--r--view/js/mod_network.js1
-rw-r--r--view/js/mod_new_channel.js8
-rw-r--r--view/js/mod_profiles.js4
-rw-r--r--view/js/mod_register.js8
-rw-r--r--view/js/mod_settings.js13
-rw-r--r--view/js/spin.js377
-rw-r--r--view/nb-no/htconfig.tpl8
-rw-r--r--view/nl/hmessages.po11635
-rw-r--r--view/nl/hstrings.php2534
-rw-r--r--view/pdl/mod_admin.pdl5
-rw-r--r--view/pdl/mod_appman.pdl3
-rw-r--r--view/pdl/mod_apps.pdl4
-rw-r--r--view/pdl/mod_blocks.pdl5
-rw-r--r--view/pdl/mod_cal.pdl3
-rw-r--r--view/pdl/mod_cards.pdl8
-rw-r--r--view/pdl/mod_cdav.pdl6
-rw-r--r--view/pdl/mod_channel.pdl5
-rw-r--r--view/pdl/mod_chanview.pdl3
-rw-r--r--view/pdl/mod_chat.pdl3
-rw-r--r--view/pdl/mod_cloud.pdl3
-rw-r--r--view/pdl/mod_common.pdl3
-rw-r--r--view/pdl/mod_connect.pdl3
-rw-r--r--view/pdl/mod_connections.pdl3
-rw-r--r--view/pdl/mod_connedit.pdl3
-rw-r--r--view/pdl/mod_directory.pdl3
-rw-r--r--view/pdl/mod_display.pdl3
-rw-r--r--view/pdl/mod_editblock.pdl5
-rw-r--r--view/pdl/mod_editlayout.pdl5
-rw-r--r--view/pdl/mod_editwebpage.pdl5
-rw-r--r--view/pdl/mod_events.pdl3
-rw-r--r--view/pdl/mod_group.pdl3
-rw-r--r--view/pdl/mod_help.pdl3
-rw-r--r--view/pdl/mod_id.pdl4
-rw-r--r--view/pdl/mod_layouts.pdl5
-rw-r--r--view/pdl/mod_locs.pdl4
-rw-r--r--view/pdl/mod_mail.pdl3
-rw-r--r--view/pdl/mod_menu.pdl5
-rw-r--r--view/pdl/mod_message.pdl3
-rw-r--r--view/pdl/mod_mitem.pdl5
-rw-r--r--view/pdl/mod_network.pdl5
-rw-r--r--view/pdl/mod_photos.pdl3
-rw-r--r--view/pdl/mod_profile.pdl3
-rw-r--r--view/pdl/mod_profile_photo.pdl3
-rw-r--r--view/pdl/mod_profiles.pdl3
-rw-r--r--view/pdl/mod_profperm.pdl3
-rw-r--r--view/pdl/mod_pubstream.pdl3
-rw-r--r--view/pdl/mod_rate.pdl3
-rw-r--r--view/pdl/mod_ratings.pdl3
-rw-r--r--view/pdl/mod_search.pdl3
-rw-r--r--view/pdl/mod_settings.pdl4
-rw-r--r--view/pdl/mod_sharedwithme.pdl3
-rw-r--r--view/pdl/mod_suggest.pdl5
-rw-r--r--view/pdl/mod_uexport.pdl4
-rw-r--r--view/pdl/mod_viewconnections.pdl3
-rw-r--r--view/pdl/mod_webpages.pdl5
-rw-r--r--view/pdl/mod_wiki.pdl3
-rw-r--r--view/php/default.php4
-rw-r--r--view/php/full.php2
-rw-r--r--view/php/mod_import.php2
-rw-r--r--view/php/mod_setup.php2
-rw-r--r--view/php/theme_init.php59
-rw-r--r--view/pt-br/htconfig.tpl8
-rw-r--r--view/ru/htconfig.tpl7
-rw-r--r--view/sv/htconfig.tpl7
-rw-r--r--view/theme/redbasic/css/align_left.css8
-rw-r--r--view/theme/redbasic/css/narrow_navbar.css66
-rw-r--r--view/theme/redbasic/css/style.css1035
-rw-r--r--view/theme/redbasic/img/bbedit.pngbin2145 -> 0 bytes
-rw-r--r--view/theme/redbasic/img/border.jpgbin342 -> 0 bytes
-rw-r--r--view/theme/redbasic/img/editicons.pngbin6300 -> 0 bytes
-rw-r--r--view/theme/redbasic/img/ff-16.jpgbin644 -> 0 bytes
-rw-r--r--view/theme/redbasic/img/file.gifbin613 -> 0 bytes
-rw-r--r--view/theme/redbasic/img/friendika-16.pngbin699 -> 0 bytes
-rw-r--r--view/theme/redbasic/img/jotperms.pngbin510 -> 0 bytes
-rw-r--r--view/theme/redbasic/img/login-bg.gifbin237 -> 0 bytes
-rw-r--r--view/theme/redbasic/img/notify_on.pngbin721 -> 0 bytes
-rw-r--r--view/theme/redbasic/img/photo-menu.jpgbin459 -> 0 bytes
-rw-r--r--view/theme/redbasic/img/shiny.pngbin362 -> 0 bytes
-rw-r--r--view/theme/redbasic/js/redbasic.js78
-rw-r--r--view/theme/redbasic/php/config.php57
-rw-r--r--view/theme/redbasic/php/style.php129
-rw-r--r--view/theme/redbasic/php/theme.php4
-rw-r--r--view/theme/redbasic/php/theme_init.php27
-rw-r--r--view/theme/redbasic/schema/BS-Default.css7
-rw-r--r--view/theme/redbasic/schema/BS-Default.php20
-rw-r--r--view/theme/redbasic/schema/bluegrid.css491
-rw-r--r--view/theme/redbasic/schema/bluegrid.php28
-rw-r--r--view/theme/redbasic/schema/dark.css27
-rw-r--r--view/theme/redbasic/schema/simple_black_on_white.css2
-rw-r--r--view/theme/redbasic/schema/simple_green_on_black.css1
-rw-r--r--view/theme/redbasic/schema/simple_white_on_black.css1
-rw-r--r--view/theme/redbasic/tpl/theme_settings.tpl18
-rwxr-xr-xview/tpl/abook_edit.tpl69
-rwxr-xr-xview/tpl/acl_selector.tpl34
-rw-r--r--view/tpl/admin_account_edit.tpl5
-rwxr-xr-xview/tpl/admin_accounts.tpl6
-rwxr-xr-xview/tpl/admin_aside.tpl18
-rwxr-xr-xview/tpl/admin_channels.tpl2
-rwxr-xr-xview/tpl/admin_plugins.tpl16
-rw-r--r--view/tpl/admin_profiles.tpl4
-rw-r--r--view/tpl/admin_queue.tpl2
-rwxr-xr-xview/tpl/admin_site.tpl12
-rwxr-xr-xview/tpl/admin_summary.tpl4
-rw-r--r--view/tpl/app.tpl22
-rw-r--r--view/tpl/app_create.tpl4
-rw-r--r--view/tpl/app_nav.tpl1
-rw-r--r--view/tpl/app_select.tpl10
-rw-r--r--view/tpl/apporder.tpl7
-rwxr-xr-xview/tpl/atom_feed.tpl26
-rw-r--r--view/tpl/attach_edit.tpl8
-rw-r--r--view/tpl/blocklist.tpl10
-rwxr-xr-xview/tpl/build_query.tpl2
-rw-r--r--view/tpl/cards.tpl4
-rwxr-xr-xview/tpl/categories_widget.tpl6
-rw-r--r--view/tpl/cdav_addressbook.tpl462
-rw-r--r--view/tpl/cdav_calendar.tpl349
-rw-r--r--view/tpl/cdav_widget_addressbook.tpl67
-rw-r--r--view/tpl/cdav_widget_calendar.tpl121
-rwxr-xr-xview/tpl/channel.tpl6
-rwxr-xr-xview/tpl/channel_import.tpl5
-rwxr-xr-xview/tpl/channel_rename.tpl20
-rwxr-xr-xview/tpl/channels.tpl2
-rw-r--r--view/tpl/chat.tpl90
-rw-r--r--view/tpl/chatroom_new.tpl2
-rw-r--r--view/tpl/chatroomlist.tpl6
-rw-r--r--view/tpl/chatrooms.tpl10
-rw-r--r--view/tpl/cloud_actionspanel.tpl7
-rw-r--r--view/tpl/cloud_directory.tpl14
-rw-r--r--view/tpl/cloud_header.tpl6
-rwxr-xr-xview/tpl/comment_item.tpl52
-rwxr-xr-xview/tpl/common_friends.tpl26
-rwxr-xr-xview/tpl/common_tabs.tpl17
-rwxr-xr-xview/tpl/connection_template.tpl12
-rwxr-xr-xview/tpl/connections.tpl28
-rwxr-xr-xview/tpl/contact_slider.tpl6
-rwxr-xr-xview/tpl/conv_frame.tpl5
-rwxr-xr-xview/tpl/conv_item.tpl240
-rwxr-xr-xview/tpl/conv_list.tpl258
-rwxr-xr-xview/tpl/cover_photo_widget.tpl33
-rw-r--r--view/tpl/design_tools.tpl14
-rw-r--r--view/tpl/diaspora_vcard.tpl69
-rwxr-xr-xview/tpl/directory_header.tpl22
-rwxr-xr-xview/tpl/direntry.tpl10
-rw-r--r--view/tpl/dreport.tpl2
-rwxr-xr-xview/tpl/edpost_head.tpl2
-rwxr-xr-xview/tpl/event.tpl6
-rwxr-xr-xview/tpl/event_cal.tpl2
-rwxr-xr-xview/tpl/event_form.tpl60
-rwxr-xr-xview/tpl/event_head.tpl9
-rwxr-xr-xview/tpl/events-js.tpl24
-rwxr-xr-xview/tpl/events_cal-js.tpl10
-rwxr-xr-xview/tpl/events_tools_side.tpl22
-rwxr-xr-xview/tpl/field_checkbox.tpl7
-rwxr-xr-xview/tpl/field_combobox.tpl33
-rwxr-xr-xview/tpl/field_input.tpl9
-rwxr-xr-xview/tpl/field_intcheckbox.tpl9
-rwxr-xr-xview/tpl/field_password.tpl8
-rwxr-xr-xview/tpl/field_select.tpl8
-rwxr-xr-xview/tpl/field_textarea.tpl8
-rwxr-xr-xview/tpl/field_yesno.tpl4
-rwxr-xr-xview/tpl/fileas_widget.tpl6
-rwxr-xr-xview/tpl/filer_dialog.tpl23
-rwxr-xr-xview/tpl/follow.tpl11
-rwxr-xr-xview/tpl/generic_links_widget.tpl4
-rw-r--r--view/tpl/generic_modal.tpl4
-rwxr-xr-xview/tpl/group_drop.tpl2
-rwxr-xr-xview/tpl/group_side.tpl14
-rw-r--r--view/tpl/hdr.tpl8
-rw-r--r--view/tpl/help.tpl33
-rwxr-xr-xview/tpl/install.tpl20
-rwxr-xr-xview/tpl/install_checks.tpl49
-rwxr-xr-xview/tpl/install_db.tpl59
-rwxr-xr-xview/tpl/install_settings.tpl57
-rw-r--r--view/tpl/item_attach.tpl2
-rw-r--r--view/tpl/item_binary.tpl3
-rw-r--r--view/tpl/item_categories.tpl6
-rw-r--r--view/tpl/item_filer.tpl6
-rwxr-xr-xview/tpl/item_import.tpl4
-rwxr-xr-xview/tpl/jot-header.tpl289
-rwxr-xr-xview/tpl/jot.tpl123
-rw-r--r--view/tpl/layoutlist.tpl12
-rwxr-xr-xview/tpl/like_noshare.tpl4
-rw-r--r--view/tpl/locmanage.tpl6
-rwxr-xr-xview/tpl/login.tpl2
-rwxr-xr-xview/tpl/mail_conv.tpl57
-rwxr-xr-xview/tpl/mail_display.tpl6
-rwxr-xr-xview/tpl/mail_head.tpl2
-rwxr-xr-xview/tpl/mail_list.tpl6
-rwxr-xr-xview/tpl/main_slider.tpl10
-rw-r--r--view/tpl/menuedit.tpl2
-rw-r--r--view/tpl/menulist.tpl10
-rwxr-xr-xview/tpl/message_side.tpl10
-rw-r--r--view/tpl/mitemedit.tpl2
-rw-r--r--view/tpl/mitemlist.tpl4
-rwxr-xr-xview/tpl/msg-header.tpl66
-rwxr-xr-xview/tpl/myapps.tpl14
-rwxr-xr-xview/tpl/nav.tpl210
-rw-r--r--view/tpl/nav_login.tpl3
-rwxr-xr-xview/tpl/navbar_default.tpl207
-rwxr-xr-xview/tpl/navbar_tucson.tpl293
-rwxr-xr-xview/tpl/new_channel.tpl4
-rwxr-xr-xview/tpl/notifications.tpl20
-rw-r--r--view/tpl/notifications_widget.tpl62
-rwxr-xr-xview/tpl/notify.tpl11
-rw-r--r--view/tpl/nwiki_page_history.tpl10
-rw-r--r--view/tpl/page_display_empty.tpl1
-rw-r--r--view/tpl/pdledit.tpl3
-rwxr-xr-xview/tpl/peoplefind.tpl20
-rwxr-xr-xview/tpl/photo_album.tpl19
-rwxr-xr-xview/tpl/photo_album_portfolio.tpl49
-rwxr-xr-xview/tpl/photo_albums.tpl8
-rwxr-xr-xview/tpl/photo_drop.tpl2
-rwxr-xr-xview/tpl/photo_item.tpl12
-rwxr-xr-xview/tpl/photo_portfolio.tpl13
-rw-r--r--view/tpl/photo_portfolio_card.tpl6
-rw-r--r--view/tpl/photo_portfolio_orbit.tpl5
-rwxr-xr-xview/tpl/photo_view.tpl40
-rwxr-xr-xview/tpl/photos_recent.tpl15
-rwxr-xr-xview/tpl/photos_upload.tpl4
-rwxr-xr-xview/tpl/posted_date_widget.tpl20
-rwxr-xr-xview/tpl/profile_advanced.tpl52
-rwxr-xr-xview/tpl/profile_edit.tpl181
-rwxr-xr-xview/tpl/profile_listing_header.tpl2
-rw-r--r--view/tpl/profile_tabs.tpl4
-rwxr-xr-xview/tpl/profile_vcard.tpl29
-rwxr-xr-xview/tpl/profile_vcard_short.tpl4
-rwxr-xr-xview/tpl/prv_message.tpl66
-rwxr-xr-xview/tpl/register.tpl4
-rwxr-xr-xview/tpl/remote_friends_common.tpl27
-rw-r--r--view/tpl/saved_searches.tpl12
-rwxr-xr-xview/tpl/search_item.tpl78
-rw-r--r--view/tpl/searchbox.tpl6
-rwxr-xr-xview/tpl/settings.tpl36
-rwxr-xr-xview/tpl/settings_account.tpl4
-rwxr-xr-xview/tpl/settings_display.tpl8
-rwxr-xr-xview/tpl/settings_features.tpl2
-rwxr-xr-xview/tpl/settings_oauth.tpl4
-rw-r--r--view/tpl/sharedwithme.tpl12
-rw-r--r--view/tpl/show_thing.tpl4
-rwxr-xr-xview/tpl/suggest_friends.tpl4
-rw-r--r--view/tpl/thing_edit.tpl2
-rw-r--r--view/tpl/thing_input.tpl2
-rwxr-xr-xview/tpl/threaded_conversation.tpl3
-rw-r--r--view/tpl/usermenu.tpl6
-rwxr-xr-xview/tpl/viewcontact_template.tpl26
-rw-r--r--view/tpl/webpage_export_list.tpl2
-rw-r--r--view/tpl/webpage_import.tpl2
-rw-r--r--view/tpl/webpagelist.tpl14
-rw-r--r--view/tpl/website_portation_tools.tpl128
-rw-r--r--view/tpl/wiki.tpl153
-rw-r--r--view/tpl/wiki_page_history.tpl4
-rw-r--r--view/tpl/wiki_page_list.tpl50
-rw-r--r--view/tpl/wikilist.tpl45
-rw-r--r--view/tpl/wikilist_widget.tpl4
-rw-r--r--view/tpl/xrd_diaspora.tpl3
-rwxr-xr-xview/tpl/xrd_person.tpl7
3643 files changed, 148675 insertions, 128099 deletions
diff --git a/.gitignore b/.gitignore
index 75be5b0c2..0e5233eaf 100755
--- a/.gitignore
+++ b/.gitignore
@@ -14,7 +14,7 @@
*.rej
# OSX .DS_Store files
.DS_Store
-# version scripts (repo master only)
+# version scripts (repo master only)
.version*
Thumbs.db
@@ -27,6 +27,7 @@ custom/
/store/
# site apps
apps/
+!doc/context/*/apps
# default startpage
home.html
# page header plugin
@@ -44,7 +45,8 @@ doc/html/
.zotshrc
# external repositories for themes/addons
extend/
-
+# files generated by phpunit
+tests/results/
## exclude IDE files
# config files and folders from Eclipse
@@ -63,6 +65,8 @@ nbproject/
## composer
# locally installed composer binary
composer.phar
+# allow composer.lock, as it is required to have a common state
+!composer.lock
# vendor/ is managed by composer, no need to include in our repository
# requires new deployment and needs discussion first
#vendor/
diff --git a/.travis.yml b/.travis.yml
index 2830d1b9f..41b480cf9 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -1,44 +1,164 @@
+#
+# Travis-CI configuration file for Hubzilla
+#
+## configure things
+#
+
# see http://about.travis-ci.org/docs/user/languages/php/ for more hints
language: php
-# list any PHP version you want to test against
-php:
- # using major version aliases
+# use newer 'trusty' based distro, old one is 'precise'
+dist: trusty
+# use docker based containers
+sudo: false
+
+# Git branches whitelist to build on Travis CI
+branches:
+ only:
+ - master
+ - dev
+ # whitelist our tags for release deployments e.g. 2.2
+ - /^\d+\.\d+(\.\d+)?(-\S*)?$/
- # aliased to a recent 5.6.x version
- - 5.6
- # aliased to a recent 7.x version
- - 7.0
- # aliased to a recent hhvm version
- - hhvm
+# Install additional software
+addons:
+ # Install dependencies for generating API documentation with doxygen
+ apt:
+ packages:
+ - doxygen
+ - doxygen-latex
+ - graphviz
+ - ttf-liberation
-# optionally specify a list of environments, for example to test different RDBMS
-#env:
-# - DB=mysql
-# - DB=pgsql
+# enable and start databases on a per job basis
+#services:
+# - mariadb
+# - postgresql
+
+# any PHP version we want to test against, current stable phpunit requires PHP >= 7.0
+php:
+ - '7.0'
+ - '7.1'
+ # HHVM does not fulfil PHPUnit platform requirements as being compatible with PHP7 yet
+ #- 'hhvm'
-# optionally set up exclutions and allowed failures in the matrix
+# list of environments to test
+env:
+ global:
+ # used for doxygen deployment script
+ - DOXYFILE: $TRAVIS_BUILD_DIR/util/Doxyfile
+ # Uncomment if a newer/specific version of Doxygen should be used
+ #- DOXY_VER: 1.8.12
+ # Code Coverage is slow, no need to have it in every build
+ - PHPUCOV: "--no-coverage"
+ # use matrix only for PHP and MySQL, all other combinations added through includes
+ matrix:
+ # trusty default MySQL 5.6
+ - DB=mysql MYSQL_VERSION=5.6
+
+# Matrix configuration details
matrix:
+ fast_finish: true
+ # Additional check combinations
+ include:
+ # PHP7.1, mariadb 10.1
+ - php: '7.1'
+ env: DB=mariadb MARIADB_VERSION=10.1 CODECOV=1
+ # use mariadb instead of MySQL
+ addons:
+ mariadb: '10.1'
+ # PHP7.1, PostgreSQL 9.6
+ - php: '7.1'
+ env: DB=pgsql POSTGRESQL_VERSION=9.6
+ # Use newer postgres than 9.2 default
+ addons:
+ postgresql: '9.6'
+ services:
+ - postgresql
+ # PHP7.1, old precise distribution with MySQL 5.5
+ - php: '7.1'
+ env: DB=mysql MYSQL_VERSION=5.5
+ dist: precise
+ services:
+ - mysql
+ # MySQL 5.7 with Docker container
+ - php: '7.1'
+ env: DB=mysql MYSQL_VERSION=5.7
+ sudo: required
+ services:
+ - docker
+ # Excludes from default matrix combinations
# exclude:
# - php: hhvm
# env: DB=pgsql # PDO driver for pgsql is unsupported by HHVM (3rd party install for support)
- allow_failures:
- - php: hhvm
-# execute any number of scripts before the test run, custom env's are available as variables
-#before_script:
-# - if [[ "$DB" == "pgsql" ]]; then psql -c "DROP DATABASE IF EXISTS hello_world_test;" -U postgres; fi
-# - if [[ "$DB" == "pgsql" ]]; then psql -c "create database hello_world_test;" -U postgres; fi
-# - if [[ "$DB" == "mysql" ]]; then mysql -e "create database IF NOT EXISTS hello_world_test;" -uroot; fi
+# cache composer downloads between runs
+cache:
+ directories:
+ - $HOME/.composer/cache
+ #- $HOME/doxygen/doxygen-$DOXY_VER/bin
+
+
+#
+## execute things
+#
+
+before_install:
+ - travis_retry composer self-update
+ # Start MySQL 5.7 Docker container, needs some time to come up
+ - if [[ "$MYSQL_VERSION" == "5.7" ]]; then sudo service mysql stop; docker run -d -p 3306:3306 -e MYSQL_ALLOW_EMPTY_PASSWORD=yes mysql:5.7 && sleep 25 && docker ps; fi
+
+# Install composer dev libs
install:
- - composer require phpunit/phpunit
+ - travis_retry composer install --optimize-autoloader --no-progress
+
+# execute any number of scripts before the test run, custom env's are available as variables
+before_script:
+ # Use code coverage config for phpunit
+ - if [[ ! -z $CODECOV ]]; then export PHPUCOV=""; fi
+ # Some preparation tasks of environment
+ - ./tests/travis/prepare.sh
+ # DB specific prepare scripts
+ - if [[ "$DB" == "mysql" ]]; then ./tests/travis/prepare_mysql.sh; fi
+ - if [[ "$DB" == "mariadb" ]]; then ./tests/travis/prepare_mysql.sh; fi
+ - if [[ "$DB" == "pgsql" ]]; then ./tests/travis/prepare_pgsql.sh; fi
# omitting "script:" will default to phpunit
-# use the $DB env variable to determine the phpunit.xml to use
-script: vendor/bin/phpunit tests/unit/
+script: ./vendor/bin/phpunit $PHPUCOV -c tests/phpunit-$DB.xml
+
+after_success:
+ # Generate API documentation and deploy it to gh-pages
+ - ./tests/travis/gen_apidocs.sh
+#after_failure:
+
+# Deploying release and API documentation to GitHub
+#before_deploy:
+deploy:
+ - provider: pages
+ skip_cleanup: true
+ local_dir: $TRAVIS_BUILD_DIR/doc/html
+ github_token: $GH_TOKEN
+ on:
+ repo: redmatrix/hubzilla
+ branch: master
+ condition: '(-n "$GH_TOKEN") && ("$TRAVIS_JOB_NUMBER" == "${TRAVIS_BUILD_NUMBER}.1")'
+ # add API documentation to release, could also be used to provide full packages if we want to drop vendor from our repo
+ - provider: releases
+ skip_cleanup: true
+ api_key: $GH_TOKEN
+ file: 'doc/hubzilla-api-documentation.zip'
+ on:
+ repo: redmatrix/hubzilla
+ tags: true
+ condition: '(-n "$GH_TOKEN") && ("$TRAVIS_JOB_NUMBER" == "${TRAVIS_BUILD_NUMBER}.1")'
+#after_deploy:
+
+#after_script:
+
+
# configure notifications (email, IRC, campfire etc)
-notifications:
+#notifications:
# irc: "irc.freenode.org#yourfavouriteroomfortravis"
# a plugin/script to post to a hubzilla channel would be neat here
diff --git a/CHANGELOG b/CHANGELOG
index 642506016..e547e1fbe 100644
--- a/CHANGELOG
+++ b/CHANGELOG
@@ -1,3 +1,400 @@
+Hubzilla 2.8 (????-??-??)
+ - Redirect to be moderated items to /moderate
+ - Update notifications if notifications area remains open
+ - Create an actual logout module instead of relying on internal variables
+ - Add local_channel as a comanche condition variable
+ - Implement possibility to pin app-tray apps in the navbar via app category navbar_default
+ - Introduce custom navbars
+ - Re-implement single delivery
+ - Pdledit usability improvements
+ - Implement next generation notifications in right aside
+ - Implement single post view for /pubstream
+ - Make anonymous comments work in mod display
+ - Introduce notifications for unseen public stream posts (off by default)
+ - Preperatory work on Zot VI
+ - Add app for site admin
+ - Introduce experimental alternate channel_menu navigation (off by default)
+ - Introduce notifications for shared files
+ - Bring back notifications for account approvals
+ - Urlencode hashes from mod_acl
+ - Don't use chanlink_url() for feed mentions
+ - Design common friends widget to fit better in the app and move it to left aside
+ - Allow navbar to be used when cover photo is displayed in mod channel
+ - Implement admin setting to use imagick converter for large photos
+ - Process activity deletes from OStatus which for whatever reason do not use the industry standard tombstone mechanism
+ - Implement new css based spinner
+ - Move the link header initialisation from Router to Webserver
+ ⁻ Extend activity_match() to work with arrays
+ - Updated the trusted CA cert database
+ - Ostatus - support likes of comments
+ - Provide ability to mention a forum by using !forumname as well as the traditional red style (@forumname+)
+ - Encrypt delivery reports (not backward compatible)
+ - Provide a space between link header params (draft-cavage-http-signatures-08)
+ - Turn common_friends into a widget
+ - Update to jquery-3.2.1
+ - Wiki pages sorted by name
+ - Create new hooks for permissions_accept and permissions_reject
+ - Provide rel=alternate link if no reshare content in post
+ - Add remote login button to login page
+ - DB update to add index to item.resource_id
+ - Implement wiki editing (name and acl)
+ - Provide a hook for importing a channel photo at channel creation time
+ - Implement wiki mimetype lock
+ - Bring back wiki downloads
+ - Add text/plain mimetype to wiki
+ - Implement per page mimetype selection for wikis
+ - Added english context help for apps and appman
+ - Implement owa (open web auth)
+ - Ignore diaspora_meta column on item import
+ - Check code permissions on cloud files
+ - Remove period from characters allowed in username
+ - Make comment highlighting more reliable
+ - Sign zot-info packets with httpsignatures
+ - Implement server to server magic auth
+ - Provide support for json-ld signatures
+ - Rewrite comment form open/close handling to be more reliable
+ - Radically reduce code duplication in updateConvItems()
+ - Remove discover tab in favour of the public stream app
+ - Apply autotime to all autotime classed elements when static loading a page
+ - Implement cards feature
+ - Extended support for help page translations including table of contents files at the top level
+ - Introduce util/dmkdir - a mkdir tool for DAV
+ - Various doco improvements
+ - Introduce util/dcp (DAV-copy) - copy file or directory from local system to Hubzilla
+ - Provide support for HTTPsig
+ - Implement mechanism for selective network following in protocol connectors (diaspora, ostatus, activitypub, zot, rss)
+
+ Bugfixes
+ - Fix w2w posts not removed in contact_remove() - github issue #837
+ - Fix guests not having a unique (non-existent) url
+ - Fix mod register re-using the password
+ - Fix write_storage permission not checked in /display
+ - Fix discovery of moderated items in enotify
+ - Fix profile thing image not deleted when thing deleted - github issue #868
+ - Fix deletions to comments not synced on wall posts
+ - Fix community tags not preserved on post edit - github issue #865
+ - Fix profile photo propagation issue if the local xchan_photo_[l|m|s] fields were changed from the /photo/profile/l/n form to photo/[hash] form by a clone operation
+ - Fix lockstate and current permissions not handed over to editor in mod card_edit
+ - Fix profile edit dropdown for multiple profiles
+ - Fix affinity slider spinner
+ - Fix mod pubsites broken
+ - Fix directory server admin selection includes known dead sites
+ - Fix sticky-kit issue where the bottom of left aside was not visible when section content was short
+ - Fix possibility to set bogus my_address
+ - Fix deleting of wiki pages
+ - Fix selected theme not appearing selected after change - github issue #855
+ - Fix an issue where some encoded mids were not found in /display
+ - Fix issue with mentions and xchans with @ or /
+ - Fix webfinger returns invalid XML - github issue #851
+ - Fix last remaining task in tasklist was not removed from view when completed
+
+ Plugins/Addon
+ Hubwall: Remove errant $1 string in sender name
+ Map federation protocols for zotinfo
+ Gnusoc: force ostatus profile photos to get refreshed monthly
+ Gnusoc: fix ostatus mention notifications
+ Gnusoc: unsubscribe to gnusoc feeds if connector is disabled
+ Phpmailer: not using load/unload
+ Gnusoc: don't provide some information if gnusoc is disabled by the channel
+ Diaspora: add a predelivery interval
+ Diaspora: support for likes on comments
+ Introduce the pubcrawl plugin - an unapologetically non-compliant ActivityPub Protocol implemention
+ Introduce gravatar plugin
+ Pubsubhubbub: produce much more compact PuSH feeds
+ Diaspora: support text comments on reshare posts
+ Diaspora: changes to delivery scenarios for the special handling of profile messages
+ Diaspora: put diaspora seed_location in json webfinger
+ Gnusoc: fix mis-attributed comments from mastodon
+ Gnusoc: allow discovery by url (not just reddress) and permit upgrade from 'unknown' network to gnusoc
+ Implement mechanism for selective network following in protocol connectors
+
+
+Hubzilla 2.6.3 (2017-09-18)
+ - Fix anonymous comments/likes on photos - this is not yet implemented
+ - Fix favicon not displayed on certain pages
+ - Fix hubzilla logo icon for favicon and email notifications
+ - Fix an issue with displaying selected theme in settings/display
+ - [SECURITY] Restrict the input characters we accept in token verification strings to hex digits
+ - Remove hubzilla.nl from fallback directory servers
+
+Hubzilla 2.6.2 (2017-08-31)
+ - Fix webfinger returns invalid XML (github issue #851)
+
+
+Hubzilla 2.6.1 (2017-08-18)
+ - Fix a regression with dav clients
+ - Raise install requirements
+
+ Plugins/Addon
+ - Diaspora: fix PHP warning
+ - GNU-Social: fix PHP warning
+
+
+Hubzilla 2.6 (2017-08-16)
+ - Upgrade to bootstrap-4 beta
+ - Consolidate disable_discover_tab config
+ - Fix some bbcode to markdown conversion issues
+ - Improved finding of recursive attachment permissions
+ - Smaller line-height for notification badges
+ - Bluegrid schema removed - will be added again if someone is willing to maintain it
+ - Improved file_activity()
+ - DB - add index for item.obj_type
+ - Add options flag to bb_to_markdown() so we can distinguish between diaspora use and other use and therefore filter and adjust content selectively
+ - Close the apps-menu if the notifications-menu is open and vice versa
+ - Remove redundant call to jquery ready function in photo albums view
+ - Remove borders from navbar toggler in mobile view
+ - Improve the formatting of shares when converting from bbcode to markdown
+ - Suppress fopen errors from dav
+ - Make local channel (not our own) nav menus appear similar to what we are used from remote channels
+ - Indicate the selected channel in the dropdown menu if the feature is enabled
+ - Provide a mechanism to mark apps active in the app tray
+ - Allow wildcard tag and category searches
+ - Improved installer
+ - Update some addon docs and ensure we only generate statistics once a day
+ - Turn url requests where argv[0] is something.xyz into module='something' and $_REQUEST['module_format'] = 'xyz'; But leave modules beginning with . (like .well_known) alone (convert the initial . to _ and then strip it)
+ - Turn platform name and std_version into config variables
+ - Implement chunked uploads on the wall
+ - Prevent expiration of conversations you are involved with
+ - Update htmlpurifier to version 4.9.3
+ - Update sabre/http to version 4.2.3
+ - Add optimize-autoloader to composer config
+ - Missing abook_{my,their}_perms in pg schema and missing keys in mysql schema
+ - Provide a gender icon on the profile sidebar within reason
+ - Provide more comprehensible information on the admin summary page
+ - Upgrade blueimp from 9.8 to 9.18
+ - Chanview - if already connected, bypass the chanview intermediary page and go straight to the remote profile.
+ - Allow poke by xchan_hash
+ - guess_image_type() - ignore scheme when checking for urls
+ - Remove unused page_widgets.php include and provide a general function for loading sql from file
+ - Migrate cdav from addons to core
+ - Address several mail issues
+ - Add files and photos to featured apps by default
+ - import_author_zot() fixes
+ - Remove deprecated app parameter from conversation()
+ - Implement anonymous comments (like wordpress)
+ - Add rel=noopener to all external target _blank links
+ - Add 'can_comment_on_post' hook so we can better deal with the complications of Diaspora policy
+ - Added Portfolio widget (requires foundation)
+ - Convert schema_mysql engine to InnoDB and charset utf8mb4
+ - Put unreachable federated connections in the archived tab of the connections list page
+ - Indicate on connections page if a federated connection from another network is unavailable from the current location
+ - Make authenticated oembeds optional, default to false.
+ - Remove text_highlight css load from core
+ - Numerous ostatus feed improvements (mastodon, gnu-social)
+ - Provide hook when deleting a connection - we need this to clean up dangling PuSH subscriptions
+ - Move code syntax highlighting to plugin
+ - Oembed: ensure that width and height are returned as type int and not float
+ - Rewrite wiki pages widget - no need for ajax on pageload, show the pages to not authenticated people.
+ - Convert randprof to use chanlink_hash() instead of chanlink_url() and filter sys channels by xchan.xchan_system instead of xchan_addr != sys@%
+ - Update Sabre libraries
+ - Only provide "connected apps" on the settings menu if techlevel > 0.
+ - Provide ability to search webpage
+ - Move disapora xrd stuff to plugin
+ - Deprecate server_role
+ - Introduce automatic language selection for help, webpages, and wiki content
+ - Provide ability to order apps in app-tray
+ - Replace Markdownify library with html-to-markdown library
+
+ Bugfixes
+ - Fix channel manager and nav channel select visible if in a delegate session
+ - Fix wrong wiki pages in the sidebar github issue #841
+ - Fix a bug where if multiple channels uploaded the same file to the same folder, the uploaded file would end up with an incremental number added to the filename for each upload even if the file did not exist yet in the channels folder
+ - Fix privacy groups not syncing across clones properly (github issue #832)
+ - Fix an issue where the ability to use a portion of the message-id to display a message wasn't honoured in all cases
+ - Fix minor issues in the bs-default schema
+ - Fix backward compatibility for album links generated in earlier times before the ambiguity of photo album names was solved (github issue #827)
+ - Fix photo item comments not ported to bs4
+ - Fix incorrect album link
+ - Fix incorrect follow url in webfinger
+ - Fix regression - allow position attributes in oembedable zcards
+ - Fix affinitiy slider settings were being updated on any submit of of settings/featured
+ - Fix minor weirdness in zot finger results after deleting a clone from a channel that was on a site which was previously migrated from http to https and still had the old hubloc
+ - Fix cloud headers already sent issue
+ - Partial fix for failure to sync photos - appears to be memory exhaustion and dependent on filesize although an unrelated issue was found with directory creation during file sync (we didn't check ownership when looking for duplicates)
+ - Fix github issue #810
+ - Don't allow negative age in directory listings
+ - Fix allow setting a default schema for the hub (github issue #797) and allow selecting of focus (hubzilla default) schema if a default is set
+ - Fix update_r1189() for mysql and postgres
+
+ Plugins/Addon
+ Diaspora: Rewrite the addon to implemented Diaspora Version 2 federation protocol
+ GNU-Social: GNU-Social and Mastodon compatibility was greatly increased and a "fetch conversations" feature added to try and locate missing contextual references and maintain conversations in posts from those networks
+ Rename statistics_json to statistics and implement nodeinfo v2
+ New authchoose addon to restrict what sites you authenticate to by default
+ Cdav addon moved to core
+ head_add_css() needs a preceding '/' to find files in the addons dir
+ New addon code syntax highlighting (moved from core to addon)
+ Pubsubhubbub: specify a minimum number of records - otherwise it defaults to zero
+
+
+Hubzilla 2.4 (2017-05-31)
+ - Silence php warning during install
+ - Implemented switch statement logic in Comanche layout parser
+ - Don't allow html in plugin comment blocks
+ - Handle Mastodon urls in markdown/bbcode conversion
+ - Get rid of edit activities
+ - Collapse sysapps if viewing a remote channel
+ - Various Doxygen fixes
+ - Update SimplePie library to version 1.5
+ - Add check for PHP zip extension during install
+ - Add unit tests for AccessList class
+ - Authenticate onepoll so we can receive private posts/comments in zotfeed
+ - Various postgres fixes
+ - Some work on preparing clientside e2ee
+ - Allow to set a default channel for the rare case where a default channel is not selected but channels actually exist
+ - Support reverse magic-auth in oembed requests
+ - Improved handling of Mastodon feeds
+ - When template "none" is used in a webpage layout, then the contents of the page should be the sole output, with no other code before or after the page element content
+ - If there is no site record, site_dead won't be 0, in a left join it will in fact be null. As long as it isn't 1, we should attempt delivery
+ - Order wiki pages by creation date
+ - Backend infrastructure for channel protection password; which will be used to optionally encrypt export files and resolve channel/identity ownership/hijacking disputes
+ - Don't allow any null fields in notify creation
+ - Webfinger cleanup
+ - Envelope privacy
+ - We do not parse the body in discover_by_url(), so no need to preserve iframes in SimplePie
+ - Correct the mastodon "boost" (aka 'share') author attribution by checking for share activities and pulling the original author info from the activity:object
+ - Only log zot_refresh content if json decode was successful
+ - Revisit the import_author_zot algorithm yet again. There was one bug that we weren't returning necessary information in the first SQL query - and performance/loading problem if one tries to refresh a dead site
+ - Import_author_xchan - since we rarely refresh zot-info for non-connections, force a cache reload once a week to catch things like profile photo updates and location changes
+ - Create site_store_lowlevel() to initialise data structures for the site table
+ - Change hook for perm_is_allowed while retaining backwards compatibility
+ - import_author_zot() - check for both hubloc and xchan entries. This should catch and repair entries which were subject to transient storage failures
+ - Import authors from any unrecognised network as network 'unknown'
+ - Crypto update - default is now aes-256-ctr
+ - Get rid of get_app()
+ - Add 'author_is_pmable()' function with plugin hooks to control whether or not to display a 'send mail' link in the thread author menu
+ - Provide platform specific install script
+ - Allow for project specific DB updates
+ - Get rid of davguest
+ - Move db_upgrade to zlib
+ - Add CSRF protection for import and import_items
+ - Add some documentation for import functions
+ - Do not allow creating two wikis with the same name
+ - Update textcomplete library to version 1.8.0
+ - Create channel_store_lowlevel()
+ - Allow setting the system email name/address/reply
+ - Use the same host macro for sender address as for reply_to address
+ - Use the relevant attach directory/path for photo albums instead of an album basename which may not be unique. Created an 'ellipsify()' function to shorten long names and keep the beginning and end intact
+ - Simplify the message signing spaghetti
+ - Class MarkdownSoap to safely store markdown by purifying and preserving (escaped) what may be unsafe code in codeblocks. The stored item needs to be unescaped just prior to calling the markdown-to-html processor
+ - Remove the unimplemented upload limit site settings from UI
+ - Cleanup code_allowed
+ - Move widgets to standalone classes
+ - Upgrade redbasic to bootstrap 4
+ - Updated HTML Purifier from 4.6.0 to 4.9.2 with better PHP7 compatibility
+ - Remove redundant and non-functional/broken check for successfully cloned channel record which was left over from an earlier method of creating the table; which was deprecated a few months back
+ - Update bshaffer/oauth2-server-php library
+ - Add unit test for purify_html()
+
+ Bugfixes
+ - Fix website export tool creating invalid zip file - issue #790
+ - Fix files not synced correctly - issue #769
+ - Fix empty ACL should not result in no ACL when uploading a file
+ - Fix cover photo was unintentionally disabled when block_public in effect
+ - Fix markdown autolinks - issue 752
+ - Fix connectDefaultShare generated js function, though it isn't obvious if we still use it
+ - Fix a couple more instances where we were still calling mail() directly for site critical messages
+ - Fix when clicking a notification to view a private mail message, actually view that message instead of the most recent
+ - Fix group by item query
+
+ Plugins/Addon
+ - smileybutton: do not load emojis
+ - pubsubhubbub: fixes associated with recent compatibility feed mods
+ - gnusoc: mastodon follow_activity compatibility issues
+ - gnusoc: add profile photo to feed meta
+ - gnusoc: add salmon link information to the public feed when GNU-Social is enabled
+ - chess: fix bugs when deleting games
+
+Hubzilla 2.2 (2017-03-08)
+ - Provide version compatibility check for themes (minversion, maxversion)
+ - Use chanlink_hash() instead of chanlink_url() where appropriate
+ - Use head_add_link() for feed discovery
+ - Provide HTTP header parser which honours continuation lines
+ - Numerous doco improvements
+ - Implement virtual privacy groups from restricted profile access list
+ - Implement permission roles
+ - Implement app-tray
+ - Default to manual conversation updates
+ - Implement channel move for all server roles
+ - Implement nav login modal
+ - Rename bb2diaspora.php to markdown.php
+ - Remove obsolete module 'match'
+ - Move firefox social api configuration to plugin
+ - Move rsd service to twitter_api plugin
+ - Add build_pagehead hook
+ - Move opensearch to plugins
+ - Move dreamhost hack to plugin
+ - Add wiki permissions
+ - Introduce hubloc_store_lowlevel() and xchan_store_lowlevel()
+ - Move diaspora account import to the diaspora plugin
+ - Allow export of single data sets instead of always exporting everything we know about in channel export
+ - Queue optimisations for sites that have lingered in the queue for more than a couple of days
+ - Add affinity slider tool settings for min and max defaults in settings/featured
+ - Provide lowlevel xchan storage function to ensure that all non-null rows are initialised
+ - Implement native wiki
+ - Block well-known from oembed
+ - Implement observer.language bbcode and observer.language comanche conditional
+ - Implement daemon_addon hook to let plugins create custom background processes
+ - Implement profile vcards
+ - Implement connection vcards
+ - Implement 'click to call' in address book
+ - Default cover photo
+ - Remove fullscreen functionality in photo album view
+ - Update fontawesome lib to version 4.7.0
+ - Implement a menu to select a section to be open by default in connedit
+ - Improve comanche conditionals
+ - Add enclosures and categories to atom feed parsing
+ - Allow the atom_entry hook to change the results
+ - Set 'adjust for viewer timezone' as the default for new events
+ - Allow event creation in other timezones than your own
+ - Update fullcalendar lib to version 3.1
+ - Move api version call back to core
+ - Create first webpage as 'home' if none exist
+ - Show webpages link to visitors if a 'home' page exists
+
+ Bugfixes
+ - Fix schema not saved if session theme != selected theme and schema select display issue
+ - Fix no acl not detected in post_activity_item()
+ - Fix find_folder_hash_by_path() was not safe against multiple attach structures with the same filename but in different directories
+ - Fix don't search on empty filename - we shouldn't find it. The reason why this change is being made is because we actually did find it due to a development glitch
+ - Fix several places where head_add_(css|js) functions have been used incorrectly.
+ - Fix webpage import tool
+ - Fix numerous bugs with the addon repo management GUI
+ - Fix attach_delete() to remove photo resources even if the attach table row wasn't found
+ - Fix choking if photo_factory() returns null
+ - Fix embedimage if an albumname contains quotes
+ - Fix chat member list when one or more members are connected via access tokens
+ - Fix issue #636 - some localised (e.g. Italian) strings have single quotes which throw JS errors when used in single quoted template constructs
+ - Fix issues #629 and #635 - edited post arriving from downstream source was not being rejected
+ - Fix peoplefind widget not honouring directory option settings
+ - Fix issue with HTML in code blocks in markdown in wiki
+ - Fix issue with post signatures if posted from api and logged in locally with a different identity
+
+ Plugins/Addon
+ - Add experimental webmention plugin
+ - NSFW: Use button instead of text link
+ - Diaspora: gracefully handle multiple photos per post
+ - Diaspora: change profile photo permission call
+ - Logrotate: don't throw an error if another server process renamed the logfile before we got to it
+ - Chess: the channel owner must be one of the players, so only require selecting one connection for an opponent
+ - Move firefox social api configuration to plugin from core
+ - Move rsd service to twitter_api plugin from core
+ - Move opensearch to plugins from core
+ - Move dreamhost hack to plugin from
+ - Move diaspora account import to addon from core
+ - Reflect hubloc store changes in plugins
+ - Reflect xchan store changes in plugins
+ - Rendezvous: Fixed marker creation bug
+ - Rendezvous: Center on marker if specified in URL, and update browser address bar with shareable link when selecting markers on the map
+ - Rendezvous: Set default value of 0 for priximity alert when making new markers
+ - Move gitwiki to plugins from core which has been replaced by native wiki
+ - Openclipatar: reflect changes to files and photos which were unified in core some time ago
+ - Reintroduce gnusocial plugin after security/functionality review
+ - Twitter_api: hubzilla core issue 638 - unsupported message-id field not available in all twitter api functions
+ - Superblock: update to reflect core changes
+ - Rendezvous: implement static marker proximity alert
+ - Phpmailer: security update
+
Hubzilla 2.0 (2016-12-23)
- Deprecate bb_iframe
- Note widget: resize the textarea to reveal full content
diff --git a/Zotlabs/Access/AccessList.php b/Zotlabs/Access/AccessList.php
index b073f9d3c..6471b0b1d 100644
--- a/Zotlabs/Access/AccessList.php
+++ b/Zotlabs/Access/AccessList.php
@@ -2,21 +2,55 @@
namespace Zotlabs\Access;
-
+/**
+ * @brief AccessList class.
+ *
+ * A class to hold an AccessList object with allowed and denied contacts and
+ * groups.
+ */
class AccessList {
-
+ /**
+ * @brief Allow contacts
+ * @var string
+ */
private $allow_cid;
+ /**
+ * @brief Allow groups
+ * @var string
+ */
private $allow_gid;
+ /**
+ * @brief Deny contacts
+ * @var string
+ */
private $deny_cid;
+ /**
+ * @brief Deny groups
+ * @var string
+ */
private $deny_gid;
+ /**
+ * @brief Indicates if we are using the default constructor values or
+ * values that have been set explicitly.
+ * @var boolean
+ */
+ private $explicit;
- /* indicates if we are using the default constructor values or values that have been set explicitly. */
-
- private $explicit;
+ /**
+ * @brief Constructor for AccessList class.
+ *
+ * @note The array to pass to the constructor is different from the array
+ * that you provide to the set() or set_from_array() functions.
+ *
+ * @param array $channel A channel array, where these entries are evaluated:
+ * * \e string \b channel_allow_cid => string of allowed cids
+ * * \e string \b channel_allow_gid => string of allowed gids
+ * * \e string \b channel_deny_cid => string of denied cids
+ * * \e string \b channel_deny_gid => string of denied gids
+ */
function __construct($channel) {
-
- if($channel) {
+ if($channel) {
$this->allow_cid = $channel['channel_allow_cid'];
$this->allow_gid = $channel['channel_allow_gid'];
$this->deny_cid = $channel['channel_deny_cid'];
@@ -32,61 +66,95 @@ class AccessList {
$this->explicit = false;
}
+ /**
+ * @brief Get if we are using the default constructor values
+ * or values that have been set explicitly.
+ *
+ * @return boolean
+ */
function get_explicit() {
return $this->explicit;
}
/**
- * Set AccessList from strings such as those in already
- * existing stored data items
+ * @brief Set access list from strings such as those in already
+ * existing stored data items.
+ *
+ * @note The array to pass to this set function is different from the array
+ * that you provide to the constructor or set_from_array().
+ *
+ * @param array $arr
+ * * \e string \b allow_cid => string of allowed cids
+ * * \e string \b allow_gid => string of allowed gids
+ * * \e string \b deny_cid => string of denied cids
+ * * \e string \b deny_gid => string of denied gids
+ * @param boolean $explicit (optional) default true
*/
-
- function set($arr,$explicit = true) {
+ function set($arr, $explicit = true) {
$this->allow_cid = $arr['allow_cid'];
$this->allow_gid = $arr['allow_gid'];
$this->deny_cid = $arr['deny_cid'];
$this->deny_gid = $arr['deny_gid'];
- $this->explicit = $explicit;
+ $this->explicit = $explicit;
}
/**
- * return an array consisting of the current
- * access list components where the elements
- * are directly storable.
+ * @brief Return an array consisting of the current access list components
+ * where the elements are directly storable.
+ *
+ * @return Associative array with:
+ * * \e string \b allow_cid => string of allowed cids
+ * * \e string \b allow_gid => string of allowed gids
+ * * \e string \b deny_cid => string of denied cids
+ * * \e string \b deny_gid => string of denied gids
*/
-
function get() {
- return array(
+ return [
'allow_cid' => $this->allow_cid,
'allow_gid' => $this->allow_gid,
'deny_cid' => $this->deny_cid,
'deny_gid' => $this->deny_gid,
- );
+ ];
}
/**
- * Set AccessList from arrays, such as those provided by
- * acl_selector(). For convenience, a string (or non-array) input is
- * assumed to be a comma-separated list and auto-converted into an array.
- */
-
- function set_from_array($arr,$explicit = true) {
- $this->allow_cid = perms2str((is_array($arr['contact_allow']))
- ? $arr['contact_allow'] : explode(',',$arr['contact_allow']));
+ * @brief Set access list components from arrays, such as those provided by
+ * acl_selector().
+ *
+ * For convenience, a string (or non-array) input is assumed to be a
+ * comma-separated list and auto-converted into an array.
+ *
+ * @note The array to pass to this set function is different from the array
+ * that you provide to the constructor or set().
+ *
+ * @param array $arr An associative array with:
+ * * \e array|string \b contact_allow => array with cids or comma-seperated string
+ * * \e array|string \b group_allow => array with gids or comma-seperated string
+ * * \e array|string \b contact_deny => array with cids or comma-seperated string
+ * * \e array|string \b group_deny => array with gids or comma-seperated string
+ * @param boolean $explicit (optional) default true
+ */
+ function set_from_array($arr, $explicit = true) {
+ $this->allow_cid = perms2str((is_array($arr['contact_allow']))
+ ? $arr['contact_allow'] : explode(',', $arr['contact_allow']));
$this->allow_gid = perms2str((is_array($arr['group_allow']))
- ? $arr['group_allow'] : explode(',',$arr['group_allow']));
+ ? $arr['group_allow'] : explode(',', $arr['group_allow']));
$this->deny_cid = perms2str((is_array($arr['contact_deny']))
- ? $arr['contact_deny'] : explode(',',$arr['contact_deny']));
+ ? $arr['contact_deny'] : explode(',', $arr['contact_deny']));
$this->deny_gid = perms2str((is_array($arr['group_deny']))
- ? $arr['group_deny'] : explode(',',$arr['group_deny']));
+ ? $arr['group_deny'] : explode(',', $arr['group_deny']));
$this->explicit = $explicit;
}
+ /**
+ * @brief Returns true if any access lists component is set.
+ *
+ * @return boolean Return true if any of allow_* deny_* values is set.
+ */
function is_private() {
return (($this->allow_cid || $this->allow_gid || $this->deny_cid || $this->deny_gid) ? true : false);
}
}
-
diff --git a/Zotlabs/Access/PermissionLimits.php b/Zotlabs/Access/PermissionLimits.php
index 909b654d5..8caeedb91 100644
--- a/Zotlabs/Access/PermissionLimits.php
+++ b/Zotlabs/Access/PermissionLimits.php
@@ -10,7 +10,7 @@ class PermissionLimits {
$perms = Permissions::Perms();
$limits = array();
foreach($perms as $k => $v) {
- if(strstr($k,'view'))
+ if(strstr($k,'view') || $k === 'post_comments')
$limits[$k] = PERMS_PUBLIC;
else
$limits[$k] = PERMS_SPECIFIC;
diff --git a/Zotlabs/Access/Permissions.php b/Zotlabs/Access/Permissions.php
index d51e4d0ea..62c4af0ff 100644
--- a/Zotlabs/Access/Permissions.php
+++ b/Zotlabs/Access/Permissions.php
@@ -1,45 +1,52 @@
<?php
-
namespace Zotlabs\Access;
use Zotlabs\Lib as Zlib;
+/**
+ * @brief Extensible permissions.
+ *
+ * To add new permissions, add to the list of $perms below, with a simple description.
+ *
+ * Also visit PermissionRoles.php and add to the $ret['perms_connect'] property for any role
+ * if this permission should be granted to new connections.
+ *
+ * Next look at PermissionRoles::new_custom_perms() and provide a handler for updating custom
+ * permission roles. You will want to set a default PermissionLimit for each channel and also
+ * provide a sane default for any existing connections. You may or may not wish to provide a
+ * default auto permission. If in doubt, leave this alone as custom permissions by definition
+ * are the responsibility of the channel owner to manage. You just don't want to create any
+ * suprises or break things so you have an opportunity to provide sane settings.
+ *
+ * Update the version here and in PermissionRoles.
+ *
+ *
+ * Permissions with 'view' in the name are considered read permissions. Anything
+ * else requires authentication. Read permission limits are PERMS_PUBLIC and anything else
+ * is given PERMS_SPECIFIC.
+ *
+ * PermissionLimits::Std_limits() retrieves the standard limits. A permission role
+ * MAY alter an individual setting after retrieving the Std_limits if you require
+ * something different for a specific permission within the given role.
+ *
+ */
class Permissions {
- /**
- * Extensible permissions.
- * To add new permissions, add to the list of $perms below, with a simple description.
- *
- * Also visit PermissionRoles.php and add to the $ret['perms_connect'] property for any role
- * if this permission should be granted to new connections.
- *
- * Next look at PermissionRoles::new_custom_perms() and provide a handler for updating custom
- * permission roles. You will want to set a default PermissionLimit for each channel and also
- * provide a sane default for any existing connections. You may or may not wish to provide a
- * default auto permission. If in doubt, leave this alone as custom permissions by definition
- * are the responsibility of the channel owner to manage. You just don't want to create any
- * suprises or break things so you have an opportunity to provide sane settings.
- *
- * Update the version here and in PermissionRoles
- *
- *
- * Permissions with 'view' in the name are considered read permissions. Anything
- * else requires authentication. Read permission limits are PERMS_PUBLIC and anything else
- * is given PERMS_SPECIFIC.
- *
- * PermissionLimits::Std_limits() retrieves the standard limits. A permission role
- * MAY alter an individual setting after retrieving the Std_limits if you require
- * something different for a specific permission within the given role.
- *
- */
-
static public function version() {
// This must match the version in PermissionRoles.php before permission updates can run.
return 2;
}
-
+ /**
+ * @brief Return an array with Permissions.
+ *
+ * @hooks permissions_list
+ * * \e array \b permissions
+ * * \e string \b filter
+ * @param string $filter (optional) only passed to hook permission_list
+ * @return Associative array with permissions and short description.
+ */
static public function Perms($filter = '') {
$perms = [
@@ -63,18 +70,27 @@ class Permissions {
'delegate' => t('Can administer my channel')
];
- $x = array('permissions' => $perms, 'filter' => $filter);
- call_hooks('permissions_list',$x);
- return($x['permissions']);
+ $x = [
+ 'permissions' => $perms,
+ 'filter' => $filter
+ ];
+ call_hooks('permissions_list', $x);
+ return($x['permissions']);
}
+ /**
+ * @brief Perms from the above list that are blocked from anonymous observers.
+ *
+ * e.g. you must be authenticated.
+ *
+ * @hooks write_perms
+ * * \e array \b permissions
+ * @return Associative array with permissions and short description.
+ */
static public function BlockedAnonPerms() {
- // Perms from the above list that are blocked from anonymous observers.
- // e.g. you must be authenticated.
-
- $res = array();
+ $res = [];
$perms = PermissionLimits::Std_limits();
foreach($perms as $perm => $limit) {
if($limit != PERMS_PUBLIC) {
@@ -82,17 +98,22 @@ class Permissions {
}
}
- $x = array('permissions' => $res);
- call_hooks('write_perms',$x);
- return($x['permissions']);
+ $x = ['permissions' => $res];
+ call_hooks('write_perms', $x);
+ return($x['permissions']);
}
- // converts [ 0 => 'view_stream', ... ]
- // to [ 'view_stream' => 1 ]
- // for any permissions in $arr;
- // Undeclared permissions are set to 0
-
+ /**
+ * @brief Converts indexed perms array to associative perms array.
+ *
+ * Converts [ 0 => 'view_stream', ... ]
+ * to [ 'view_stream' => 1 ] for any permissions in $arr;
+ * Undeclared permissions which exist in Perms() are added and set to 0.
+ *
+ * @param array $arr
+ * @return array
+ */
static public function FilledPerms($arr) {
if(is_null($arr)) {
btlogger('FilledPerms: null');
@@ -101,15 +122,26 @@ class Permissions {
$everything = self::Perms();
$ret = [];
foreach($everything as $k => $v) {
- if(in_array($k,$arr))
+ if(in_array($k, $arr))
$ret[$k] = 1;
else
$ret[$k] = 0;
}
- return $ret;
+ return $ret;
}
+ /**
+ * @brief Convert perms array to indexed array.
+ *
+ * Converts [ 'view_stream' => 1 ] for any permissions in $arr
+ * to [ 0 => ['name' => 'view_stream', 'value' => 1], ... ]
+ *
+ * @param array $arr associative perms array 'view_stream' => 1
+ * @return Indexed array with elements that look like
+ * * \e string \b name the perm name (e.g. view_stream)
+ * * \e int \b value the value of the perm (e.g. 1)
+ */
static public function OPerms($arr) {
$ret = [];
if($arr) {
@@ -120,7 +152,12 @@ class Permissions {
return $ret;
}
-
+ /**
+ * @brief
+ *
+ * @param int $channel_id
+ * @return boolean|array
+ */
static public function FilledAutoperms($channel_id) {
if(! intval(get_pconfig($channel_id,'system','autoperms')))
return false;
@@ -137,16 +174,34 @@ class Permissions {
return $arr;
}
- static public function PermsCompare($p1,$p2) {
+ /**
+ * @brief Compares that all Permissions from $p1 exist also in $p2.
+ *
+ * @param array $p1 The perms that have to exist in $p2
+ * @param array $p2 The perms to compare against
+ * @return boolean true if all perms from $p1 exist also in $p2
+ */
+ static public function PermsCompare($p1, $p2) {
foreach($p1 as $k => $v) {
- if(! array_key_exists($k,$p2))
+ if(! array_key_exists($k, $p2))
return false;
+
if($p1[$k] != $p2[$k])
return false;
}
+
return true;
}
+ /**
+ * @brief
+ *
+ * @param int $channel_id A channel id
+ * @return associative array
+ * * \e array \b perms Permission array
+ * * \e int \b automatic 0 or 1
+ */
+
static public function connect_perms($channel_id) {
$my_perms = [];
@@ -155,7 +210,7 @@ class Permissions {
// If a default permcat exists, use that
- $pc = ((feature_enabled($channel_id,'permcats')) ? get_pconfig($channel_id,'system','default_permcat') : 'default');
+ $pc = ((feature_enabled($channel_id,'permcats')) ? get_pconfig($channel_id,'system','default_permcat') : 'default');
if(! in_array($pc, [ '','default' ])) {
$pcp = new Zlib\Permcat($channel_id);
$permcat = $pcp->fetch($pc);
@@ -167,7 +222,7 @@ class Permissions {
}
// look up the permission role to see if it specified auto-connect
- // and if there was no permcat or a default permcat, set the perms
+ // and if there was no permcat or a default permcat, set the perms
// from the role
$role = get_pconfig($channel_id,'system','permissions_role');
@@ -195,7 +250,7 @@ class Permissions {
}
// If we reached this point with no permissions, the channel is using
- // custom perms but they are not automatic. They will be stored in abconfig with
+ // custom perms but they are not automatic. They will be stored in abconfig with
// the channel's channel_hash (the 'self' connection).
if(! $my_perms) {
diff --git a/Zotlabs/Daemon/Cron.php b/Zotlabs/Daemon/Cron.php
index 350dda7a0..65edbedfa 100644
--- a/Zotlabs/Daemon/Cron.php
+++ b/Zotlabs/Daemon/Cron.php
@@ -121,6 +121,9 @@ class Cron {
}
}
+ require_once('include/attach.php');
+ attach_upgrade();
+
$abandon_days = intval(get_config('system','account_abandon_days'));
if($abandon_days < 1)
$abandon_days = 0;
@@ -171,7 +174,8 @@ class Cron {
// pull in some public posts
- if(! get_config('system','disable_discover_tab'))
+ $disable_discover_tab = get_config('system','disable_discover_tab') || get_config('system','disable_discover_tab') === false;
+ if(! $disable_discover_tab)
Master::Summon(array('Externals'));
$generation = 0;
diff --git a/Zotlabs/Daemon/Cron_daily.php b/Zotlabs/Daemon/Cron_daily.php
index 0f0001890..f0351fcdd 100644
--- a/Zotlabs/Daemon/Cron_daily.php
+++ b/Zotlabs/Daemon/Cron_daily.php
@@ -38,12 +38,20 @@ class Cron_daily {
db_utcnow(), db_quoteinterval('30 DAY')
);
+ // expire any unread notifications over a year old
+
+ q("delete from notify where seen = 0 and created < %s - INTERVAL %s",
+ db_utcnow(), db_quoteinterval('1 YEAR')
+ );
+
+
//update statistics in config
require_once('include/statistics_fns.php');
update_channels_total_stat();
update_channels_active_halfyear_stat();
update_channels_active_monthly_stat();
update_local_posts_stat();
+ update_local_comments_stat();
// expire old delivery reports
@@ -80,7 +88,7 @@ class Cron_daily {
call_hooks('cron_daily',datetime_convert());
- set_config('system','last_expire_day',$d2);
+ set_config('system','last_expire_day',intval(datetime_convert('UTC','UTC','now','d')));
/**
* End Cron Daily
diff --git a/Zotlabs/Daemon/Deliver.php b/Zotlabs/Daemon/Deliver.php
index dbc311cf5..394a7bf3e 100644
--- a/Zotlabs/Daemon/Deliver.php
+++ b/Zotlabs/Daemon/Deliver.php
@@ -53,6 +53,9 @@ class Deliver {
remove_queue_item($r[0]['outq_hash']);
if($dresult && is_array($dresult)) {
+
+ // delivery reports for local deliveries do not require encryption
+
foreach($dresult as $xx) {
if(is_array($xx) && array_key_exists('message_id',$xx)) {
if(delivery_report_is_storable($xx)) {
diff --git a/Zotlabs/Daemon/Gprobe.php b/Zotlabs/Daemon/Gprobe.php
index 43cce93c3..f1ffb2d81 100644
--- a/Zotlabs/Daemon/Gprobe.php
+++ b/Zotlabs/Daemon/Gprobe.php
@@ -17,7 +17,7 @@ class Gprobe {
if(! strpos($url,'@'))
return;
- $r = q("select * from xchan where xchan_addr = '%s' limit 1",
+ $r = q("select * from hubloc where hubloc_addr = '%s' limit 1",
dbesc($url)
);
diff --git a/Zotlabs/Daemon/Importdoc.php b/Zotlabs/Daemon/Importdoc.php
index 3109a5d86..0ca589e4a 100755
--- a/Zotlabs/Daemon/Importdoc.php
+++ b/Zotlabs/Daemon/Importdoc.php
@@ -21,12 +21,18 @@ class Importdoc {
$files = glob("$d/$f");
if($files) {
foreach($files as $fi) {
- if($fi === 'doc/html')
+ if($fi === 'doc/html') {
continue;
- if(is_dir($fi))
+ }
+ if(is_dir($fi)) {
self::update_docs_dir("$fi/*");
- else
- store_doc_file($fi);
+ }
+ else {
+ // don't update media content
+ if(strpos(z_mime_content_type($fi),'text') === 0) {
+ store_doc_file($fi);
+ }
+ }
}
}
}
diff --git a/Zotlabs/Daemon/Importfile.php b/Zotlabs/Daemon/Importfile.php
new file mode 100644
index 000000000..c68ed21cf
--- /dev/null
+++ b/Zotlabs/Daemon/Importfile.php
@@ -0,0 +1,47 @@
+<?php /** @file */
+
+namespace Zotlabs\Daemon;
+
+class Importfile {
+
+ static public function run($argc,$argv){
+
+ logger('Importfile: ' . print_r($argv,true));
+
+ if($argc < 3)
+ return;
+
+ $channel = channelx_by_n($argv[1]);
+ if(! $channel)
+ return;
+
+ $srcfile = $argv[2];
+ $folder = (($argc > 3) ? $argv[3] : '');
+ $dstname = (($argc > 4) ? $argv[4] : '');
+
+ $hash = random_string();
+
+ $arr = [
+ 'src' => $srcfile,
+ 'filename' => (($dstname) ? $dstname : basename($srcfile)),
+ 'hash' => $hash,
+ 'allow_cid' => $channel['channel_allow_cid'],
+ 'allow_gid' => $channel['channel_allow_gid'],
+ 'deny_cid' => $channel['channel_deny_cid'],
+ 'deny_gid' => $channel['channel_deny_gid'],
+ 'preserve_original' => true,
+ 'replace' => true
+ ];
+
+ if($folder)
+ $arr['folder'] = $folder;
+
+ attach_store($channel,$channel['channel_hash'],'import',$arr);
+
+ $sync = attach_export_data($channel,$hash);
+ if($sync)
+ build_sync_packet($channel['channel_id'],array('file' => array($sync)));
+
+ return;
+ }
+}
diff --git a/Zotlabs/Daemon/Notifier.php b/Zotlabs/Daemon/Notifier.php
index 63ced4f56..d0175549b 100644
--- a/Zotlabs/Daemon/Notifier.php
+++ b/Zotlabs/Daemon/Notifier.php
@@ -5,6 +5,11 @@ namespace Zotlabs\Daemon;
require_once('include/queue_fn.php');
require_once('include/html2plain.php');
require_once('include/conversation.php');
+require_once('include/zot.php');
+require_once('include/items.php');
+require_once('include/bbcode.php');
+
+
/*
* This file was at one time responsible for doing all deliveries, but this caused
@@ -54,6 +59,8 @@ require_once('include/conversation.php');
*
* ZOT
* permission_create abook_id
+ * permission_accept abook_id
+ * permission_reject abook_id
* permission_update abook_id
* refresh_all channel_id
* purge_all channel_id
@@ -64,17 +71,11 @@ require_once('include/conversation.php');
* location channel_id
* request channel_id xchan_hash message_id
* rating xlink_id
+ * keychange channel_id
*
*/
-require_once('include/zot.php');
-require_once('include/queue_fn.php');
-require_once('include/datetime.php');
-require_once('include/items.php');
-require_once('include/bbcode.php');
-require_once('include/channel.php');
-
class Notifier {
@@ -98,16 +99,6 @@ class Notifier {
$deliveries = array();
- $dead_hubs = array();
-
- $dh = q("select site_url from site where site_dead = 1");
- if($dh) {
- foreach($dh as $dead) {
- $dead_hubs[] = $dead['site_url'];
- }
- }
-
-
$request = false;
$mail = false;
$top_level = false;
@@ -158,7 +149,21 @@ class Notifier {
$packet_type = 'request';
$normal_mode = false;
}
- elseif($cmd == 'permission_update' || $cmd == 'permission_create') {
+ elseif($cmd === 'keychange') {
+ $channel = channelx_by_n($item_id);
+ $r = q("select abook_xchan from abook where abook_channel = %d",
+ intval($item_id)
+ );
+ if($r) {
+ foreach($r as $rr) {
+ $recipients[] = $rr['abook_xchan'];
+ }
+ }
+ $private = false;
+ $packet_type = 'keychange';
+ $normal_mode = false;
+ }
+ elseif(in_array($cmd, [ 'permission_update', 'permission_reject', 'permission_accept', 'permission_create' ])) {
// Get the (single) recipient
$r = q("select * from abook left join xchan on abook_xchan = xchan_hash where abook_id = %d and abook_self = 0",
intval($item_id)
@@ -170,8 +175,12 @@ class Notifier {
if($channel) {
$perm_update = array('sender' => $channel, 'recipient' => $r[0], 'success' => false, 'deliveries' => '');
- if($cmd == 'permission_create')
+ if($cmd === 'permission_create')
call_hooks('permissions_create',$perm_update);
+ elseif($cmd === 'permission_accept')
+ call_hooks('permissions_accept',$perm_update);
+ elseif($cmd === 'permission_reject')
+ call_hooks('permissions_reject',$perm_update);
else
call_hooks('permissions_update',$perm_update);
@@ -275,14 +284,15 @@ class Notifier {
$deleted_item = true;
}
- if(intval($target_item['item_type']) != ITEM_TYPE_POST) {
+ if(! in_array(intval($target_item['item_type']), [ ITEM_TYPE_POST ] )) {
logger('notifier: target item not forwardable: type ' . $target_item['item_type'], LOGGER_DEBUG);
return;
}
// Check for non published items, but allow an exclusion for transmitting hidden file activities
- if(intval($target_item['item_unpublished']) || intval($target_item['item_delayed']) ||
+ if(intval($target_item['item_unpublished']) || intval($target_item['item_delayed']) ||
+ intval($target_item['item_blocked']) ||
( intval($target_item['item_hidden']) && ($target_item['obj_type'] !== ACTIVITY_OBJ_FILE))) {
logger('notifier: target item not published, so not forwardable', LOGGER_DEBUG);
return;
@@ -403,7 +413,6 @@ class Notifier {
return;
}
}
-
}
$walltowall = (($top_level_post && $channel['xchan_hash'] === $target_item['author_xchan']) ? true : false);
@@ -420,11 +429,11 @@ class Notifier {
if(! $recipients)
return;
-// logger('notifier: recipients: ' . print_r($recipients,true), LOGGER_NORMAL, LOG_DEBUG);
+ // logger('notifier: recipients: ' . print_r($recipients,true), LOGGER_NORMAL, LOG_DEBUG);
$env_recips = (($private) ? array() : null);
- $details = q("select xchan_hash, xchan_instance_url, xchan_network, xchan_addr, xchan_guid, xchan_guid_sig from xchan where xchan_hash in (" . implode(',',$recipients) . ")");
+ $details = q("select xchan_hash, xchan_instance_url, xchan_network, xchan_addr, xchan_guid, xchan_guid_sig from xchan where xchan_hash in (" . protect_sprintf(implode(',',$recipients)) . ")");
$recip_list = array();
@@ -433,40 +442,40 @@ class Notifier {
foreach($details as $d) {
$recip_list[] = $d['xchan_addr'] . ' (' . $d['xchan_hash'] . ')';
- if($private)
- $env_recips[] = array('guid' => $d['xchan_guid'],'guid_sig' => $d['xchan_guid_sig'],'hash' => $d['xchan_hash']);
-
- if($d['xchan_network'] === 'mail' && $normal_mode) {
- $delivery_options = get_xconfig($d['xchan_hash'],'system','delivery_mode');
- if(! $delivery_options)
- format_and_send_email($channel,$d,$target_item);
+ if($private) {
+ $env_recips[] = [
+ 'guid' => $d['xchan_guid'],
+ 'guid_sig' => $d['xchan_guid_sig'],
+ 'hash' => $d['xchan_hash']
+ ];
}
}
}
- $narr = array(
- 'channel' => $channel,
- 'upstream' => $upstream,
- 'env_recips' => $env_recips,
- 'packet_recips' => $packet_recips,
- 'recipients' => $recipients,
- 'item' => $item,
- 'target_item' => $target_item,
+ $narr = [
+ 'channel' => $channel,
+ 'upstream' => $upstream,
+ 'env_recips' => $env_recips,
+ 'packet_recips' => $packet_recips,
+ 'recipients' => $recipients,
+ 'item' => $item,
+ 'target_item' => $target_item,
+ 'parent_item' => $parent_item,
'top_level_post' => $top_level_post,
- 'private' => $private,
+ 'private' => $private,
'relay_to_owner' => $relay_to_owner,
- 'uplink' => $uplink,
- 'cmd' => $cmd,
- 'mail' => $mail,
- 'single' => (($cmd === 'single_mail' || $cmd === 'single_activity') ? true : false),
- 'location' => $location,
- 'request' => $request,
- 'normal_mode' => $normal_mode,
- 'packet_type' => $packet_type,
- 'walltowall' => $walltowall,
- 'queued' => array()
- );
+ 'uplink' => $uplink,
+ 'cmd' => $cmd,
+ 'mail' => $mail,
+ 'single' => (($cmd === 'single_mail' || $cmd === 'single_activity') ? true : false),
+ 'location' => $location,
+ 'request' => $request,
+ 'normal_mode' => $normal_mode,
+ 'packet_type' => $packet_type,
+ 'walltowall' => $walltowall,
+ 'queued' => []
+ ];
call_hooks('notifier_process', $narr);
if($narr['queued']) {
@@ -489,10 +498,10 @@ class Notifier {
// Now we have collected recipients (except for external mentions, FIXME)
- // Let's reduce this to a set of hubs.
+ // Let's reduce this to a set of hubs; checking that the site is not dead.
- $r = q("select hubloc.*, site.site_crypto from hubloc left join site on site_url = hubloc_url where hubloc_hash in (" . implode(',',$recipients) . ")
- and hubloc_error = 0 and hubloc_deleted = 0"
+ $r = q("select hubloc.*, site.site_crypto, site.site_flags from hubloc left join site on site_url = hubloc_url where hubloc_hash in (" . protect_sprintf(implode(',',$recipients)) . ")
+ and hubloc_error = 0 and hubloc_deleted = 0 and ( site_dead = 0 OR site_dead is null ) "
);
@@ -503,73 +512,78 @@ class Notifier {
$hubs = $r;
-
-
/**
- * Reduce the hubs to those that are unique. For zot hubs, we need to verify uniqueness by the sitekey, since it may have been
- * a re-install which has not yet been detected and pruned.
+ * Reduce the hubs to those that are unique. For zot hubs, we need to verify uniqueness by the sitekey,
+ * since it may have been a re-install which has not yet been detected and pruned.
* For other networks which don't have or require sitekeys, we'll have to use the URL
*/
- $hublist = array(); // this provides an easily printable list for the logs
- $dhubs = array(); // delivery hubs where we store our resulting unique array
- $keys = array(); // array of keys to check uniquness for zot hubs
- $urls = array(); // array of urls to check uniqueness of hubs from other networks
-
+ $hublist = []; // this provides an easily printable list for the logs
+ $dhubs = []; // delivery hubs where we store our resulting unique array
+ $keys = []; // array of keys to check uniquness for zot hubs
+ $urls = []; // array of urls to check uniqueness of hubs from other networks
+ $hub_env = []; // per-hub envelope so we don't broadcast the entire envelope to all
foreach($hubs as $hub) {
- if(in_array($hub['hubloc_url'],$dead_hubs)) {
- logger('skipping dead hub: ' . $hub['hubloc_url'], LOGGER_DEBUG, LOG_INFO);
- continue;
+
+ if($env_recips) {
+ foreach($env_recips as $er) {
+ if($hub['hubloc_hash'] === $er['hash']) {
+ if(! array_key_exists($hub['hubloc_host'] . $hub['hubloc_sitekey'], $hub_env)) {
+ $hub_env[$hub['hubloc_host'] . $hub['hubloc_sitekey']] = [];
+ }
+ $hub_env[$hub['hubloc_host'] . $hub['hubloc_sitekey']][] = $er;
+ }
+ }
}
+
if($hub['hubloc_network'] == 'zot') {
if(! in_array($hub['hubloc_sitekey'],$keys)) {
- $hublist[] = $hub['hubloc_host'];
- $dhubs[] = $hub;
- $keys[] = $hub['hubloc_sitekey'];
+ $hublist[] = $hub['hubloc_host'] . ' ' . $hub['hubloc_network'];
+ $dhubs[] = $hub;
+ $keys[] = $hub['hubloc_sitekey'];
}
}
else {
if(! in_array($hub['hubloc_url'],$urls)) {
- $hublist[] = $hub['hubloc_host'];
- $dhubs[] = $hub;
- $urls[] = $hub['hubloc_url'];
+ $hublist[] = $hub['hubloc_host'] . ' ' . $hub['hubloc_network'];
+ $dhubs[] = $hub;
+ $urls[] = $hub['hubloc_url'];
}
}
}
logger('notifier: will notify/deliver to these hubs: ' . print_r($hublist,true), LOGGER_DEBUG, LOG_DEBUG);
-
foreach($dhubs as $hub) {
if($hub['hubloc_network'] !== 'zot') {
-
- $narr = array(
- 'channel' => $channel,
- 'upstream' => $upstream,
- 'env_recips' => $env_recips,
- 'packet_recips' => $packet_recips,
- 'recipients' => $recipients,
- 'item' => $item,
- 'target_item' => $target_item,
- 'hub' => $hub,
+ $narr = [
+ 'channel' => $channel,
+ 'upstream' => $upstream,
+ 'env_recips' => $env_recips,
+ 'packet_recips' => $packet_recips,
+ 'recipients' => $recipients,
+ 'item' => $item,
+ 'target_item' => $target_item,
+ 'parent_item' => $parent_item,
+ 'hub' => $hub,
'top_level_post' => $top_level_post,
- 'private' => $private,
+ 'private' => $private,
'relay_to_owner' => $relay_to_owner,
- 'uplink' => $uplink,
- 'cmd' => $cmd,
- 'mail' => $mail,
- 'single' => (($cmd === 'single_mail' || $cmd === 'single_activity') ? true : false),
- 'location' => $location,
- 'request' => $request,
- 'normal_mode' => $normal_mode,
- 'packet_type' => $packet_type,
- 'walltowall' => $walltowall,
- 'queued' => array()
- );
+ 'uplink' => $uplink,
+ 'cmd' => $cmd,
+ 'mail' => $mail,
+ 'single' => (($cmd === 'single_mail' || $cmd === 'single_activity') ? true : false),
+ 'location' => $location,
+ 'request' => $request,
+ 'normal_mode' => $normal_mode,
+ 'packet_type' => $packet_type,
+ 'walltowall' => $walltowall,
+ 'queued' => []
+ ];
call_hooks('notifier_hub',$narr);
@@ -582,13 +596,13 @@ class Notifier {
}
// singleton deliveries by definition 'not got zot'.
- // Single deliveries are other federated networks (plugins) and we're essentially
+ // Single deliveries are other federated networks (plugins) and we're essentially
// delivering only to those that have this site url in their abook_instance
// and only from within a sync operation. This means if you post from a clone,
// and a connection is connected to one of your other clones; assuming that hub
// is running it will receive a sync packet. On receipt of this sync packet it
// will invoke a delivery to those connections which are connected to just that
- // hub instance.
+ // hub instance.
if($cmd === 'single_mail' || $cmd === 'single_activity') {
continue;
@@ -596,14 +610,20 @@ class Notifier {
// default: zot protocol
- $hash = random_string();
+ $hash = random_string();
$packet = null;
+ $pmsg = '';
if($packet_type === 'refresh' || $packet_type === 'purge') {
$packet = zot_build_packet($channel,$packet_type,(($packet_recips) ? $packet_recips : null));
}
+ if($packet_type === 'keychange') {
+ $packet = zot_build_packet($channel,$packet_type,(($packet_recips) ? $packet_recips : null));
+ $pmsg = get_pconfig($channel['channel_id'],'system','keychange');
+ }
elseif($packet_type === 'request') {
- $packet = zot_build_packet($channel,$packet_type,$env_recips,$hub['hubloc_sitekey'],$hub['site_crypto'],
+ $env = (($hub_env && $hub_env[$hub['hubloc_host'] . $hub['hubloc_sitekey']]) ? $hub_env[$hub['hubloc_host'] . $hub['hubloc_sitekey']] : '');
+ $packet = zot_build_packet($channel,$packet_type,$env,$hub['hubloc_sitekey'],$hub['site_crypto'],
$hash, array('message_id' => $request_message_id)
);
}
@@ -614,19 +634,23 @@ class Notifier {
'account_id' => $channel['channel_account_id'],
'channel_id' => $channel['channel_id'],
'posturl' => $hub['hubloc_callback'],
- 'notify' => $packet
+ 'notify' => $packet,
+ 'msg' => (($pmsg) ? json_encode($pmsg) : '')
));
}
else {
- $packet = zot_build_packet($channel,'notify',$env_recips,(($private) ? $hub['hubloc_sitekey'] : null), $hub['site_crypto'],$hash);
- queue_insert(array(
- 'hash' => $hash,
- 'account_id' => $target_item['aid'],
- 'channel_id' => $target_item['uid'],
- 'posturl' => $hub['hubloc_callback'],
- 'notify' => $packet,
- 'msg' => json_encode($encoded_item)
- ));
+ $env = (($hub_env && $hub_env[$hub['hubloc_host'] . $hub['hubloc_sitekey']]) ? $hub_env[$hub['hubloc_host'] . $hub['hubloc_sitekey']] : '');
+ $packet = zot_build_packet($channel,'notify',$env,(($private) ? $hub['hubloc_sitekey'] : null), $hub['site_crypto'],$hash);
+ queue_insert(
+ [
+ 'hash' => $hash,
+ 'account_id' => $target_item['aid'],
+ 'channel_id' => $target_item['uid'],
+ 'posturl' => $hub['hubloc_callback'],
+ 'notify' => $packet,
+ 'msg' => json_encode($encoded_item)
+ ]
+ );
// only create delivery reports for normal undeleted items
if(is_array($target_item) && array_key_exists('postopts',$target_item) && (! $target_item['item_deleted']) && (! get_config('system','disable_dreport'))) {
@@ -647,9 +671,9 @@ class Notifier {
if($normal_mode) {
$x = q("select * from hook where hook = 'notifier_normal'");
- if($x)
- Master::Summon(array('Deliver_hooks',$target_item['id']));
-
+ if($x) {
+ Master::Summon( [ 'Deliver_hooks', $target_item['id'] ] );
+ }
}
if($deliveries)
diff --git a/Zotlabs/Daemon/Onepoll.php b/Zotlabs/Daemon/Onepoll.php
index 33b244dc5..920916828 100644
--- a/Zotlabs/Daemon/Onepoll.php
+++ b/Zotlabs/Daemon/Onepoll.php
@@ -118,13 +118,29 @@ class Onepoll {
if($fetch_feed) {
- $feedurl = str_replace('/poco/','/zotfeed/',$contact['xchan_connurl']);
- $feedurl .= '?f=&mindate=' . urlencode($last_update);
+ if(strpos($contact['xchan_connurl'],z_root()) === 0) {
+ // local channel - save a network fetch
+ $c = channelx_by_hash($contact['xchan_hash']);
+ if($c) {
+ $x = [
+ 'success' => true,
+ 'body' => json_encode( [
+ 'success' => true,
+ 'messages' => zot_feed($c['channel_id'], $importer['xchan_hash'], [ 'mindate' => $last_update ])
+ ])
+ ];
+ }
+ }
+ else {
+ // remote fetch
- $x = z_fetch_url($feedurl);
+ $feedurl = str_replace('/poco/','/zotfeed/',$contact['xchan_connurl']);
+ $feedurl .= '?f=&mindate=' . urlencode($last_update) . '&zid=' . $importer['channel_address'] . '@' . \App::get_hostname();
+ $recurse = 0;
+ $x = z_fetch_url($feedurl, false, $recurse, [ 'session' => true ]);
+ }
logger('feed_update: ' . print_r($x,true), LOGGER_DATA);
-
}
if(($x) && ($x['success'])) {
diff --git a/Zotlabs/Extend/Hook.php b/Zotlabs/Extend/Hook.php
index fef3ebe9b..c6f9ea850 100644
--- a/Zotlabs/Extend/Hook.php
+++ b/Zotlabs/Extend/Hook.php
@@ -40,6 +40,15 @@ class Hook {
return $r;
}
+ static public function register_array($file,$arr) {
+ if($arr) {
+ foreach($arr as $k => $v) {
+ self::register($k,$file,$v);
+ }
+ }
+ }
+
+
static public function unregister($hook,$file,$function,$version = 1,$priority = 0) {
if(is_array($function)) {
$function = serialize($function);
diff --git a/Zotlabs/Lib/ActivityStreams.php b/Zotlabs/Lib/ActivityStreams.php
new file mode 100644
index 000000000..379e78a59
--- /dev/null
+++ b/Zotlabs/Lib/ActivityStreams.php
@@ -0,0 +1,199 @@
+<?php
+
+namespace Zotlabs\Lib;
+
+class ActivityStreams {
+
+ public $data;
+ public $valid = false;
+ public $id = '';
+ public $type = '';
+ public $actor = null;
+ public $obj = null;
+ public $tgt = null;
+ public $origin = null;
+ public $owner = null;
+ public $signer = null;
+ public $ldsig = null;
+ public $sigok = false;
+ public $recips = null;
+ public $raw_recips = null;
+
+ function __construct($string) {
+
+ $this->data = json_decode($string,true);
+ if($this->data) {
+ $this->valid = true;
+ }
+
+ if($this->is_valid()) {
+ $this->id = $this->get_property_obj('id');
+ $this->type = $this->get_primary_type();
+ $this->actor = $this->get_compound_property('actor');
+ $this->obj = $this->get_compound_property('object');
+ $this->tgt = $this->get_compound_property('target');
+ $this->origin = $this->get_compound_property('origin');
+ $this->recips = $this->collect_recips();
+
+ $this->ldsig = $this->get_compound_property('signature');
+ if($this->ldsig) {
+ $this->signer = $this->get_compound_property('creator',$this->ldsig);
+ if($this->signer && $this->signer['publicKey'] && $this->signer['publicKey']['publicKeyPem']) {
+ $this->sigok = \Zotlabs\Lib\LDSignatures::verify($this->data,$this->signer['publicKey']['publicKeyPem']);
+ }
+ }
+
+ if(($this->type === 'Note') && (! $this->obj)) {
+ $this->obj = $this->data;
+ $this->type = 'Create';
+ }
+ }
+ }
+
+ function is_valid() {
+ return $this->valid;
+ }
+
+ function set_recips($arr) {
+ $this->saved_recips = $arr;
+ }
+
+ function collect_recips($base = '',$namespace = '') {
+ $x = [];
+ $fields = [ 'to','cc','bto','bcc','audience'];
+ foreach($fields as $f) {
+ $y = $this->get_compound_property($f,$base,$namespace);
+ if($y) {
+ $x = array_merge($x,$y);
+ if(! is_array($this->raw_recips))
+ $this->raw_recips = [];
+ $this->raw_recips[$f] = $x;
+ }
+ }
+// not yet ready for prime time
+// $x = $this->expand($x,$base,$namespace);
+ return $x;
+ }
+
+ function expand($arr,$base = '',$namespace = '') {
+ $ret = [];
+
+ // right now use a hardwired recursion depth of 5
+
+ for($z = 0; $z < 5; $z ++) {
+ if(is_array($arr) && $arr) {
+ foreach($arr as $a) {
+ if(is_array($a)) {
+ $ret[] = $a;
+ }
+ else {
+ $x = $this->get_compound_property($a,$base,$namespace);
+ if($x) {
+ $ret = array_merge($ret,$x);
+ }
+ }
+ }
+ }
+ }
+
+ // @fixme de-duplicate
+
+ return $ret;
+ }
+
+ function get_namespace($base,$namespace) {
+
+ if(! $namespace)
+ return '';
+
+ $key = null;
+
+
+ foreach( [ $this->data, $base ] as $b ) {
+ if(! $b)
+ continue;
+ if(array_key_exists('@context',$b)) {
+ if(is_array($b['@context'])) {
+ foreach($b['@context'] as $ns) {
+ if(is_array($ns)) {
+ foreach($ns as $k => $v) {
+ if($namespace === $v)
+ $key = $k;
+ }
+ }
+ else {
+ if($namespace === $ns) {
+ $key = '';
+ }
+ }
+ }
+ }
+ else {
+ if($namespace === $b['@context']) {
+ $key = '';
+ }
+ }
+ }
+ }
+ return $key;
+ }
+
+
+ function get_property_obj($property,$base = '',$namespace = '' ) {
+ $prefix = $this->get_namespace($base,$namespace);
+ if($prefix === null)
+ return null;
+ $base = (($base) ? $base : $this->data);
+ $propname = (($prefix) ? $prefix . ':' : '') . $property;
+ return ((array_key_exists($propname,$base)) ? $base[$propname] : null);
+ }
+
+ function fetch_property($url) {
+ $redirects = 0;
+ if(! check_siteallowed($url)) {
+ logger('blacklisted: ' . $url);
+ return null;
+ }
+
+ $x = z_fetch_url($url,true,$redirects,
+ ['headers' => [ 'Accept: application/ld+json; profile="https://www.w3.org/ns/activitystreams", application/activity+json' ]]);
+ if($x['success'])
+ return json_decode($x['body'],true);
+ return null;
+ }
+
+ function get_compound_property($property,$base = '',$namespace = '') {
+ $x = $this->get_property_obj($property,$base,$namespace);
+ if($this->is_url($x)) {
+ $x = $this->fetch_property($x);
+ }
+ return $x;
+ }
+
+ function is_url($url) {
+ if(($url) && (! is_array($url)) && (strpos($url,'http') === 0)) {
+ return true;
+ }
+ return false;
+ }
+
+ function get_primary_type($base = '',$namespace = '') {
+ if(! $base)
+ $base = $this->data;
+ $x = $this->get_property_obj('type',$base,$namespace);
+ if(is_array($x)) {
+ foreach($x as $y) {
+ if(strpos($y,':') === false) {
+ return $y;
+ }
+ }
+ }
+ return $x;
+ }
+
+ function debug() {
+ $x = var_export($this,true);
+ return $x;
+ }
+
+} \ No newline at end of file
diff --git a/Zotlabs/Lib/Apps.php b/Zotlabs/Lib/Apps.php
index 1432cbdcf..f13fbe362 100644
--- a/Zotlabs/Lib/Apps.php
+++ b/Zotlabs/Lib/Apps.php
@@ -34,7 +34,7 @@ class Apps {
if($files) {
foreach($files as $f) {
$path = explode('/',$f);
- $plugin = $path[1];
+ $plugin = trim($path[1]);
if(plugin_is_installed($plugin)) {
$x = self::parse_app_description($f,$translate);
if($x) {
@@ -169,6 +169,14 @@ class Apps {
$requires = explode(',',$ret['requires']);
foreach($requires as $require) {
$require = trim(strtolower($require));
+ $config = false;
+
+ if(substr($require, 0, 7) == 'config:') {
+ $config = true;
+ $require = ltrim($require, 'config:');
+ $require = explode('=', $require);
+ }
+
switch($require) {
case 'nologin':
if(local_channel())
@@ -191,10 +199,13 @@ class Apps {
unset($ret);
break;
default:
- if(! (local_channel() && feature_enabled(local_channel(),$require)))
+ if($config)
+ $unset = ((get_config('system', $require[0]) == $require[1]) ? false : true);
+ else
+ $unset = ((local_channel() && feature_enabled(local_channel(),$require)) ? false : true);
+ if($unset)
unset($ret);
break;
-
}
}
}
@@ -209,7 +220,9 @@ class Apps {
static public function translate_system_apps(&$arr) {
$apps = array(
- 'Site Admin' => t('Site Admin'),
+ 'Apps' => t('Apps'),
+ 'Cards' => t('Cards'),
+ 'Admin' => t('Site Admin'),
'Report Bug' => t('Report Bug'),
'View Bookmarks' => t('View Bookmarks'),
'My Chatrooms' => t('My Chatrooms'),
@@ -219,7 +232,7 @@ class Apps {
'Suggest Channels' => t('Suggest Channels'),
'Login' => t('Login'),
'Channel Manager' => t('Channel Manager'),
- 'Grid' => t('Grid'),
+ 'Grid' => t('Activity'),
'Settings' => t('Settings'),
'Files' => t('Files'),
'Webpages' => t('Webpages'),
@@ -245,9 +258,19 @@ class Apps {
'Profile Photo' => t('Profile Photo')
);
- if(array_key_exists($arr['name'],$apps)) {
- $arr['name'] = $apps[$arr['name']];
+ if(array_key_exists('name',$arr)) {
+ if(array_key_exists($arr['name'],$apps)) {
+ $arr['name'] = $apps[$arr['name']];
+ }
+ }
+ else {
+ for($x = 0; $x < count($arr); $x++) {
+ if(array_key_exists($arr[$x]['name'],$apps)) {
+ $arr[$x]['name'] = $apps[$arr[$x]['name']];
+ }
+ }
}
+
}
@@ -275,7 +298,7 @@ class Apps {
self::translate_system_apps($papp);
- if(($papp['plugin']) && (! plugin_is_installed($papp['plugin'])))
+ if(trim($papp['plugin']) && (! plugin_is_installed(trim($papp['plugin']))))
return '';
$papp['papp'] = self::papp_encode($papp);
@@ -294,8 +317,17 @@ class Apps {
if($k === 'requires') {
$requires = explode(',',$v);
+
foreach($requires as $require) {
$require = trim(strtolower($require));
+ $config = false;
+
+ if(substr($require, 0, 7) == 'config:') {
+ $config = true;
+ $require = ltrim($require, 'config:');
+ $require = explode('=', $require);
+ }
+
switch($require) {
case 'nologin':
if(local_channel())
@@ -319,10 +351,13 @@ class Apps {
return '';
break;
default:
- if(! (local_channel() && feature_enabled(local_channel(),$require)))
+ if($config)
+ $unset = ((get_config('system', $require[0]) == $require[1]) ? false : true);
+ else
+ $unset = ((local_channel() && feature_enabled(local_channel(),$require)) ? false : true);
+ if($unset)
return '';
break;
-
}
}
}
@@ -348,6 +383,13 @@ class Apps {
$install_action = (($installed) ? t('Update') : t('Install'));
$icon = ((strpos($papp['photo'],'icon:') === 0) ? substr($papp['photo'],5) : '');
+ if($mode === 'navbar') {
+ return replace_macros(get_markup_template('app_nav.tpl'),array(
+ '$app' => $papp,
+ '$icon' => $icon,
+ ));
+ }
+
return replace_macros(get_markup_template('app.tpl'),array(
'$app' => $papp,
'$icon' => $icon,
@@ -360,7 +402,10 @@ class Apps {
'$deleted' => $papp['deleted'],
'$feature' => (($papp['embed']) ? false : true),
'$featured' => ((strpos($papp['categories'], 'nav_featured_app') === false) ? false : true),
- '$navapps' => (($mode == 'nav') ? true : false)
+ '$navapps' => (($mode == 'nav') ? true : false),
+ '$order' => (($mode == 'nav-order') ? true : false),
+ '$add' => t('Add to app-tray'),
+ '$remove' => t('Remove from app-tray')
));
}
@@ -527,6 +572,129 @@ class Apps {
return($r);
}
+ static public function app_order($uid,$apps) {
+
+ if(! $apps)
+ return $apps;
+
+ $x = (($uid) ? get_pconfig($uid,'system','app_order') : get_config('system','app_order'));
+ if(($x) && (! is_array($x))) {
+ $y = explode(',',$x);
+ $y = array_map('trim',$y);
+ $x = $y;
+ }
+
+ if(! (is_array($x) && ($x)))
+ return $apps;
+
+ $ret = [];
+ foreach($x as $xx) {
+ $y = self::find_app_in_array($xx,$apps);
+ if($y) {
+ $ret[] = $y;
+ }
+ }
+ foreach($apps as $ap) {
+ if(! self::find_app_in_array($ap['name'],$ret)) {
+ $ret[] = $ap;
+ }
+ }
+ return $ret;
+
+ }
+
+ static function find_app_in_array($name,$arr) {
+ if(! $arr)
+ return false;
+ foreach($arr as $x) {
+ if($x['name'] === $name) {
+ return $x;
+ }
+ }
+ return false;
+ }
+
+ static function moveup($uid,$guid) {
+ $syslist = array();
+ $list = self::app_list($uid, false, 'nav_featured_app');
+ if($list) {
+ foreach($list as $li) {
+ $syslist[] = self::app_encode($li);
+ }
+ }
+ self::translate_system_apps($syslist);
+
+ usort($syslist,'self::app_name_compare');
+
+ $syslist = self::app_order($uid,$syslist);
+
+ if(! $syslist)
+ return;
+
+ $newlist = [];
+
+ foreach($syslist as $k => $li) {
+ if($li['guid'] === $guid) {
+ $position = $k;
+ break;
+ }
+ }
+ if(! $position)
+ return;
+ $dest_position = $position - 1;
+ $saved = $syslist[$dest_position];
+ $syslist[$dest_position] = $syslist[$position];
+ $syslist[$position] = $saved;
+
+ $narr = [];
+ foreach($syslist as $x) {
+ $narr[] = $x['name'];
+ }
+
+ set_pconfig($uid,'system','app_order',implode(',',$narr));
+
+ }
+
+ static function movedown($uid,$guid) {
+ $syslist = array();
+ $list = self::app_list($uid, false, 'nav_featured_app');
+ if($list) {
+ foreach($list as $li) {
+ $syslist[] = self::app_encode($li);
+ }
+ }
+ self::translate_system_apps($syslist);
+
+ usort($syslist,'self::app_name_compare');
+
+ $syslist = self::app_order($uid,$syslist);
+
+ if(! $syslist)
+ return;
+
+ $newlist = [];
+
+ foreach($syslist as $k => $li) {
+ if($li['guid'] === $guid) {
+ $position = $k;
+ break;
+ }
+ }
+ if($position >= count($syslist) - 1)
+ return;
+ $dest_position = $position + 1;
+ $saved = $syslist[$dest_position];
+ $syslist[$dest_position] = $syslist[$position];
+ $syslist[$position] = $saved;
+
+ $narr = [];
+ foreach($syslist as $x) {
+ $narr[] = $x['name'];
+ }
+
+ set_pconfig($uid,'system','app_order',implode(',',$narr));
+
+ }
static public function app_decode($s) {
$x = base64_decode(str_replace(array('<br />',"\r","\n",' '),array('','','',''),$s));
@@ -563,7 +731,7 @@ class Apps {
$darray['app_addr'] = ((x($arr,'addr')) ? escape_tags($arr['addr']) : '');
$darray['app_price'] = ((x($arr,'price')) ? escape_tags($arr['price']) : '');
$darray['app_page'] = ((x($arr,'page')) ? escape_tags($arr['page']) : '');
- $darray['app_plugin'] = ((x($arr,'plugin')) ? escape_tags($arr['plugin']) : '');
+ $darray['app_plugin'] = ((x($arr,'plugin')) ? escape_tags(trim($arr['plugin'])) : '');
$darray['app_requires'] = ((x($arr,'requires')) ? escape_tags($arr['requires']) : '');
$darray['app_system'] = ((x($arr,'system')) ? intval($arr['system']) : 0);
$darray['app_deleted'] = ((x($arr,'deleted')) ? intval($arr['deleted']) : 0);
@@ -641,7 +809,7 @@ class Apps {
$darray['app_addr'] = ((x($arr,'addr')) ? escape_tags($arr['addr']) : '');
$darray['app_price'] = ((x($arr,'price')) ? escape_tags($arr['price']) : '');
$darray['app_page'] = ((x($arr,'page')) ? escape_tags($arr['page']) : '');
- $darray['app_plugin'] = ((x($arr,'plugin')) ? escape_tags($arr['plugin']) : '');
+ $darray['app_plugin'] = ((x($arr,'plugin')) ? escape_tags(trim($arr['plugin'])) : '');
$darray['app_requires'] = ((x($arr,'requires')) ? escape_tags($arr['requires']) : '');
$darray['app_system'] = ((x($arr,'system')) ? intval($arr['system']) : 0);
$darray['app_deleted'] = ((x($arr,'deleted')) ? intval($arr['deleted']) : 0);
@@ -751,7 +919,7 @@ class Apps {
$ret['system'] = $app['app_system'];
if($app['app_plugin'])
- $ret['plugin'] = $app['app_plugin'];
+ $ret['plugin'] = trim($app['app_plugin']);
if($app['app_deleted'])
$ret['deleted'] = $app['app_deleted'];
diff --git a/Zotlabs/Lib/Cache.php b/Zotlabs/Lib/Cache.php
index f211269be..cea075659 100644
--- a/Zotlabs/Lib/Cache.php
+++ b/Zotlabs/Lib/Cache.php
@@ -9,10 +9,10 @@ namespace Zotlabs\Lib;
class Cache {
public static function get($key) {
- $key = substr($key,0,254);
+ $hash = hash('whirlpool',$key);
$r = q("SELECT v FROM cache WHERE k = '%s' limit 1",
- dbesc($key)
+ dbesc($hash)
);
if ($r)
@@ -22,20 +22,20 @@ class Cache {
public static function set($key,$value) {
- $key = substr($key,0,254);
+ $hash = hash('whirlpool',$key);
$r = q("SELECT * FROM cache WHERE k = '%s' limit 1",
- dbesc($key)
+ dbesc($hash)
);
if($r) {
q("UPDATE cache SET v = '%s', updated = '%s' WHERE k = '%s'",
dbesc($value),
dbesc(datetime_convert()),
- dbesc($key));
+ dbesc($hash));
}
else {
q("INSERT INTO cache ( k, v, updated) VALUES ('%s','%s','%s')",
- dbesc($key),
+ dbesc($hash),
dbesc($value),
dbesc(datetime_convert()));
}
diff --git a/Zotlabs/Lib/Config.php b/Zotlabs/Lib/Config.php
index 5625a3f79..6e042feba 100644
--- a/Zotlabs/Lib/Config.php
+++ b/Zotlabs/Lib/Config.php
@@ -53,7 +53,7 @@ class Config {
$dbvalue = ((is_array($value)) ? serialize($value) : $value);
$dbvalue = ((is_bool($dbvalue)) ? intval($dbvalue) : $dbvalue);
- if(get_config($family, $key) === false || (! self::get_from_storage($family, $key))) {
+ if(self::Get($family, $key) === false || (! self::get_from_storage($family, $key))) {
$ret = q("INSERT INTO config ( cat, k, v ) VALUES ( '%s', '%s', '%s' ) ",
dbesc($family),
dbesc($key),
diff --git a/Zotlabs/Lib/DB_Upgrade.php b/Zotlabs/Lib/DB_Upgrade.php
new file mode 100644
index 000000000..8f0488f6f
--- /dev/null
+++ b/Zotlabs/Lib/DB_Upgrade.php
@@ -0,0 +1,121 @@
+<?php
+
+namespace Zotlabs\Lib;
+
+
+class DB_Upgrade {
+
+ public $config_name = '';
+ public $func_prefix = '';
+
+ function __construct($db_revision) {
+
+ $platform_name = System::get_platform_name();
+
+ $update_file = 'install/' . $platform_name . '/update.php';
+ if(! file_exists($update_file)) {
+ $update_file = 'install/update.php';
+ $this->config_name = 'db_version';
+ $this->func_prefix = 'update_r';
+ }
+ else {
+ $this->config_name = $platform_name . '_db_version';
+ $this->func_prefix = $platform_name . '_update_';
+ }
+
+ $build = get_config('system', $this->config_name, 0);
+ if(! intval($build))
+ $build = set_config('system', $this->config_name, $db_revision);
+
+ if($build == $db_revision) {
+ // Nothing to be done.
+ return;
+ }
+ else {
+ $stored = intval($build);
+ if(! $stored) {
+ logger('Critical: check_config unable to determine database schema version');
+ return;
+ }
+
+ $current = intval($db_revision);
+
+ if(($stored < $current) && file_exists($update_file)) {
+
+ Config::Load('database');
+
+ // We're reporting a different version than what is currently installed.
+ // Run any existing update scripts to bring the database up to current.
+
+ require_once($update_file);
+
+ // make sure that boot.php and update.php are the same release, we might be
+ // updating from git right this very second and the correct version of the update.php
+ // file may not be here yet. This can happen on a very busy site.
+
+ if($db_revision == UPDATE_VERSION) {
+ for($x = $stored; $x < $current; $x ++) {
+ $func = $this->func_prefix . $x;
+ if(function_exists($func)) {
+ // There could be a lot of processes running or about to run.
+ // We want exactly one process to run the update command.
+ // So store the fact that we're taking responsibility
+ // after first checking to see if somebody else already has.
+
+ // If the update fails or times-out completely you may need to
+ // delete the config entry to try again.
+
+ if(get_config('database', $func))
+ break;
+ set_config('database',$func, '1');
+ // call the specific update
+
+ $retval = $func();
+ if($retval) {
+
+ // Prevent sending hundreds of thousands of emails by creating
+ // a lockfile.
+
+ $lockfile = 'store/[data]/mailsent';
+
+ if ((file_exists($lockfile)) && (filemtime($lockfile) > (time() - 86400)))
+ return;
+ @unlink($lockfile);
+ //send the administrator an e-mail
+ file_put_contents($lockfile, $x);
+
+ $r = q("select account_language from account where account_email = '%s' limit 1",
+ dbesc(\App::$config['system']['admin_email'])
+ );
+ push_lang(($r) ? $r[0]['account_language'] : 'en');
+
+ z_mail(
+ [
+ 'toEmail' => \App::$config['system']['admin_email'],
+ 'messageSubject' => sprintf( t('Update Error at %s'), z_root()),
+ 'textVersion' => replace_macros(get_intltext_template('update_fail_eml.tpl'),
+ [
+ '$sitename' => \App::$config['system']['sitename'],
+ '$siteurl' => z_root(),
+ '$update' => $x,
+ '$error' => sprintf( t('Update %s failed. See error logs.'), $x)
+ ]
+ )
+ ]
+ );
+
+ //try the logger
+ logger('CRITICAL: Update Failed: ' . $x);
+ pop_lang();
+ }
+ else {
+ set_config('database',$func, 'success');
+ }
+ }
+ }
+ set_config('system', $this->config_name, $db_revision);
+ }
+ }
+ }
+ }
+} \ No newline at end of file
diff --git a/Zotlabs/Lib/Enotify.php b/Zotlabs/Lib/Enotify.php
index 257687567..e82c11a35 100644
--- a/Zotlabs/Lib/Enotify.php
+++ b/Zotlabs/Lib/Enotify.php
@@ -67,7 +67,7 @@ class Enotify {
$sender_name = $product;
$hostname = \App::get_hostname();
if(strpos($hostname,':'))
- $hostname = substr($hostname,0,strpos($hostname,':'));
+ $hostname = substr($hostname,0,strpos($hostname,':'));
// Do not translate 'noreply' as it must be a legal 7-bit email address
@@ -77,7 +77,7 @@ class Enotify {
$sender_email = get_config('system','from_email');
if(! $sender_email)
- $sender_email = 'Administrator' . '@' . \App::get_hostname();
+ $sender_email = 'Administrator' . '@' . $hostname;
$sender_name = get_config('system','from_email_name');
if(! $sender_name)
@@ -130,7 +130,9 @@ class Enotify {
if ($params['type'] == NOTIFY_COMMENT) {
// logger("notification: params = " . print_r($params, true), LOGGER_DEBUG);
- $itemlink = $params['link'];
+ $moderated = (($params['item']['item_blocked'] == ITEM_MODERATED) ? true : false);
+
+ $itemlink = $params['link'];
// ignore like/unlike activity on posts - they probably require a separate notification preference
@@ -170,7 +172,6 @@ class Enotify {
xchan_query($p);
-
$item_post_type = item_post_type($p[0]);
// $private = $p[0]['item_private'];
$parent_id = $p[0]['id'];
@@ -208,13 +209,21 @@ class Enotify {
// Before this we have the name of the replier on the subject rendering
// differents subjects for messages on the same thread.
- $subject = sprintf( t('[$Projectname:Notify] Comment to conversation #%1$d by %2$s'), $parent_id, $sender['xchan_name']);
+ if($moderated)
+ $subject = sprintf( t('[$Projectname:Notify] Moderated Comment to conversation #%1$d by %2$s'), $parent_id, $sender['xchan_name']);
+ else
+ $subject = sprintf( t('[$Projectname:Notify] Comment to conversation #%1$d by %2$s'), $parent_id, $sender['xchan_name']);
$preamble = sprintf( t('%1$s, %2$s commented on an item/conversation you have been following.'), $recip['channel_name'], $sender['xchan_name']);
$epreamble = $dest_str;
$sitelink = t('Please visit %s to view and/or reply to the conversation.');
$tsitelink = sprintf( $sitelink, $siteurl );
$hsitelink = sprintf( $sitelink, '<a href="' . $siteurl . '">' . $sitename . '</a>');
+ if($moderated) {
+ $tsitelink .= "\n\n" . sprintf( t('Please visit %s to approve or reject this comment.'), z_root() . '/moderate' );
+ $hsitelink .= "<br><br>" . sprintf( t('Please visit %s to approve or reject this comment.'), '<a href="' . z_root() . '/moderate">' . z_root() . '/moderate</a>' );
+ }
+
}
if ($params['type'] == NOTIFY_LIKE) {
@@ -495,13 +504,14 @@ class Enotify {
}
}
- $r = q("insert into notify (hash,xname,url,photo,created,aid,uid,link,parent,seen,ntype,verb,otype)
- values('%s','%s','%s','%s','%s',%d,%d,'%s','%s',%d,%d,'%s','%s')",
+ $r = q("insert into notify (hash,xname,url,photo,created,msg,aid,uid,link,parent,seen,ntype,verb,otype)
+ values('%s','%s','%s','%s','%s','%s',%d,%d,'%s','%s',%d,%d,'%s','%s')",
dbesc($datarray['hash']),
dbesc($datarray['xname']),
dbesc($datarray['url']),
dbesc($datarray['photo']),
dbesc($datarray['created']),
+ dbesc(''), // will fill this in below after the record is created
intval($datarray['aid']),
intval($datarray['uid']),
dbesc($datarray['link']),
diff --git a/Zotlabs/Lib/JSalmon.php b/Zotlabs/Lib/JSalmon.php
new file mode 100644
index 000000000..43d5f9d09
--- /dev/null
+++ b/Zotlabs/Lib/JSalmon.php
@@ -0,0 +1,38 @@
+<?php
+
+namespace Zotlabs\Lib;
+
+
+class JSalmon {
+
+ static function sign($data,$key_id,$key) {
+
+ $arr = $data;
+ $data = json_encode($data,JSON_UNESCAPED_SLASHES);
+ $data = base64url_encode($data, false); // do not strip padding
+ $data_type = 'application/x-zot+json';
+ $encoding = 'base64url';
+ $algorithm = 'RSA-SHA256';
+
+ $data = preg_replace('/\s+/','',$data);
+
+ // precomputed base64url encoding of data_type, encoding, algorithm concatenated with periods
+
+ $precomputed = '.' . base64url_encode($data_type,false) . '.YmFzZTY0dXJs.UlNBLVNIQTI1Ng==';
+
+ $signature = base64url_encode(rsa_sign($data . $precomputed, $key), false);
+
+ return ([
+ 'signed' => true,
+ 'data' => $data,
+ 'data_type' => $data_type,
+ 'encoding' => $encoding,
+ 'alg' => $algorithm,
+ 'sigs' => [
+ 'value' => $signature,
+ 'key_id' => base64url_encode($key_id)
+ ]
+ ]);
+
+ }
+} \ No newline at end of file
diff --git a/Zotlabs/Lib/LDSignatures.php b/Zotlabs/Lib/LDSignatures.php
new file mode 100644
index 000000000..6d7127cde
--- /dev/null
+++ b/Zotlabs/Lib/LDSignatures.php
@@ -0,0 +1,135 @@
+<?php
+
+namespace Zotlabs\Lib;
+
+require_once('library/jsonld/jsonld.php');
+
+class LDSignatures {
+
+
+ static function verify($data,$pubkey) {
+
+ $ohash = self::hash(self::signable_options($data['signature']));
+ $dhash = self::hash(self::signable_data($data));
+
+ $x = rsa_verify($ohash . $dhash,base64_decode($data['signature']['signatureValue']), $pubkey);
+ logger('LD-verify: ' . intval($x));
+
+ return $x;
+ }
+
+ static function dopplesign(&$data,$channel) {
+ // remove for the time being - performance issues
+ // $data['magicEnv'] = self::salmon_sign($data,$channel);
+ return self::sign($data,$channel);
+ }
+
+ static function sign($data,$channel) {
+
+ $options = [
+ 'type' => 'RsaSignature2017',
+ 'nonce' => random_string(64),
+ 'creator' => z_root() . '/channel/' . $channel['channel_address'] . '/public_key_pem',
+ 'created' => datetime_convert('UTC','UTC', 'now', 'Y-m-d\Th:i:s\Z')
+ ];
+
+ $ohash = self::hash(self::signable_options($options));
+ $dhash = self::hash(self::signable_data($data));
+ $options['signatureValue'] = base64_encode(rsa_sign($ohash . $dhash,$channel['channel_prvkey']));
+
+ $signed = array_merge([
+ '@context' => [
+ ACTIVITYSTREAMS_JSONLD_REV,
+ 'https://w3id.org/security/v1' ],
+ ],$options);
+
+ return $signed;
+ }
+
+
+ static function signable_data($data) {
+
+ $newdata = [];
+ if($data) {
+ foreach($data as $k => $v) {
+ if(! in_array($k,[ 'signature' ])) {
+ $newdata[$k] = $v;
+ }
+ }
+ }
+ return json_encode($newdata,JSON_UNESCAPED_SLASHES);
+ }
+
+
+ static function signable_options($options) {
+
+ $newopts = [ '@context' => 'https://w3id.org/identity/v1' ];
+ if($options) {
+ foreach($options as $k => $v) {
+ if(! in_array($k,[ 'type','id','signatureValue' ])) {
+ $newopts[$k] = $v;
+ }
+ }
+ }
+ return json_encode($newopts,JSON_UNESCAPED_SLASHES);
+ }
+
+ static function hash($obj) {
+
+ return hash('sha256',self::normalise($obj));
+ }
+
+ static function normalise($data) {
+ if(is_string($data)) {
+ $data = json_decode($data);
+ }
+
+ if(! is_object($data))
+ return '';
+
+ jsonld_set_document_loader('jsonld_document_loader');
+
+ try {
+ $d = jsonld_normalize($data,[ 'algorithm' => 'URDNA2015', 'format' => 'application/nquads' ]);
+ }
+ catch (\Exception $e) {
+ logger('normalise error:' . print_r($e,true));
+ logger('normalise error: ' . print_r($data,true));
+ }
+
+ return $d;
+ }
+
+ static function salmon_sign($data,$channel) {
+
+ $arr = $data;
+ $data = json_encode($data,JSON_UNESCAPED_SLASHES);
+ $data = base64url_encode($data, false); // do not strip padding
+ $data_type = 'application/activity+json';
+ $encoding = 'base64url';
+ $algorithm = 'RSA-SHA256';
+ $keyhash = base64url_encode(z_root() . '/channel/' . $channel['channel_address']);
+
+ $data = str_replace(array(" ","\t","\r","\n"),array("","","",""),$data);
+
+ // precomputed base64url encoding of data_type, encoding, algorithm concatenated with periods
+
+ $precomputed = '.' . base64url_encode($data_type,false) . '.YmFzZTY0dXJs.UlNBLVNIQTI1Ng==';
+
+ $signature = base64url_encode(rsa_sign($data . $precomputed,$channel['channel_prvkey']));
+
+ return ([
+ 'id' => $arr['id'],
+ 'meData' => $data,
+ 'meDataType' => $data_type,
+ 'meEncoding' => $encoding,
+ 'meAlgorithm' => $algorithm,
+ 'meCreator' => z_root() . '/channel/' . $channel['channel_address'] . '/public_key_pem',
+ 'meSignatureValue' => $signature
+ ]);
+
+ }
+
+
+
+} \ No newline at end of file
diff --git a/Zotlabs/Lib/MarkdownSoap.php b/Zotlabs/Lib/MarkdownSoap.php
new file mode 100644
index 000000000..fa279b07c
--- /dev/null
+++ b/Zotlabs/Lib/MarkdownSoap.php
@@ -0,0 +1,103 @@
+<?php
+
+namespace Zotlabs\Lib;
+
+/**
+ * MarkdownSoap
+ * Purify Markdown for storage
+ * $x = new MarkdownSoap($string_to_be_cleansed);
+ * $text = $x->clean();
+ *
+ * What this does:
+ * 1. extracts code blocks and privately escapes them from processing
+ * 2. Run html purifier on the content
+ * 3. put back the code blocks
+ * 4. run htmlspecialchars on the entire content for safe storage
+ *
+ * At render time:
+ * $markdown = \Zotlabs\Lib\MarkdownSoap::unescape($text);
+ * $html = \Michelf\MarkdownExtra::DefaultTransform($markdown);
+ */
+
+
+
+class MarkdownSoap {
+
+ private $token;
+
+ private $str;
+
+ function __construct($s) {
+ $this->str = $s;
+ $this->token = random_string(20);
+ }
+
+
+ function clean() {
+
+ $x = $this->extract_code($this->str);
+
+ $x = $this->purify($x);
+
+ $x = $this->putback_code($x);
+
+ $x = $this->escape($x);
+
+ return $x;
+ }
+
+ function extract_code($s) {
+
+ $text = preg_replace_callback('{
+ (?:\n\n|\A\n?)
+ ( # $1 = the code block -- one or more lines, starting with a space/tab
+ (?>
+ [ ]{'.'4'.'} # Lines must start with a tab or a tab-width of spaces
+ .*\n+
+ )+
+ )
+ ((?=^[ ]{0,'.'4'.'}\S)|\Z) # Lookahead for non-space at line-start, or end of doc
+ }xm',
+ [ $this , 'encode_code' ], $s);
+
+ return $text;
+ }
+
+ function encode_code($matches) {
+ return $this->token . ';' . base64_encode($matches[0]) . ';' ;
+ }
+
+ function decode_code($matches) {
+ return base64_decode($matches[1]);
+ }
+
+ function putback_code($s) {
+ $text = preg_replace_callback('{' . $this->token . '\;(.*?)\;}xm',[ $this, 'decode_code' ], $s);
+ return $text;
+ }
+
+ function purify($s) {
+ $s = $this->protect_autolinks($s);
+ $s = purify_html($s);
+ $s = $this->unprotect_autolinks($s);
+ return $s;
+ }
+
+ function protect_autolinks($s) {
+ $s = preg_replace('/\<(https?\:\/\/)(.*?)\>/','[$1$2]($1$2)',$s);
+ return $s;
+ }
+
+ function unprotect_autolinks($s) {
+ return $s;
+
+ }
+
+ function escape($s) {
+ return htmlspecialchars($s,ENT_QUOTES,'UTF-8',false);
+ }
+
+ static public function unescape($s) {
+ return htmlspecialchars_decode($s,ENT_QUOTES);
+ }
+}
diff --git a/Zotlabs/Lib/NativeWiki.php b/Zotlabs/Lib/NativeWiki.php
index 519102d24..7642dbb3e 100644
--- a/Zotlabs/Lib/NativeWiki.php
+++ b/Zotlabs/Lib/NativeWiki.php
@@ -18,11 +18,18 @@ class NativeWiki {
if($wikis) {
foreach($wikis as &$w) {
+
+ $w['json_allow_cid'] = acl2json($w['allow_cid']);
+ $w['json_allow_gid'] = acl2json($w['allow_gid']);
+ $w['json_deny_cid'] = acl2json($w['deny_cid']);
+ $w['json_deny_gid'] = acl2json($w['deny_gid']);
+
$w['rawName'] = get_iconfig($w, 'wiki', 'rawName');
$w['htmlName'] = escape_tags($w['rawName']);
$w['urlName'] = urlencode(urlencode($w['rawName']));
$w['mimeType'] = get_iconfig($w, 'wiki', 'mimeType');
- $w['lock'] = (($w['item_private'] || $w['allow_cid'] || $w['allow_gid'] || $w['deny_cid'] || $w['deny_gid']) ? true : false);
+ $w['typelock'] = get_iconfig($w, 'wiki', 'typelock');
+ $w['lockstate'] = (($w['allow_cid'] || $w['allow_gid'] || $w['deny_cid'] || $w['deny_gid']) ? 'lock' : 'unlock');
}
}
// TODO: query db for wikis the observer can access. Return with two lists, for read and write access
@@ -75,6 +82,8 @@ class NativeWiki {
$arr['obj_type'] = ACTIVITY_OBJ_WIKI;
$arr['body'] = '[table][tr][td][h1]New Wiki[/h1][/td][/tr][tr][td][zrl=' . $wiki_url . ']' . $wiki['htmlName'] . '[/zrl][/td][/tr][/table]';
+ $arr['public_policy'] = map_scope(\Zotlabs\Access\PermissionLimits::Get($channel['channel_id'],'view_wiki'),true);
+
// Save the wiki name information using iconfig. This is shareable.
if(! set_iconfig($arr, 'wiki', 'rawName', $wiki['rawName'], true)) {
return array('item' => null, 'success' => false);
@@ -82,7 +91,9 @@ class NativeWiki {
if(! set_iconfig($arr, 'wiki', 'mimeType', $wiki['mimeType'], true)) {
return array('item' => null, 'success' => false);
}
-
+
+ set_iconfig($arr,'wiki','typelock',$wiki['typelock'],true);
+
$post = item_store($arr);
$item_id = $post['item_id'];
@@ -96,16 +107,77 @@ class NativeWiki {
}
}
+ function update_wiki($channel_id, $observer_hash, $arr, $acl) {
+
+ $w = self::get_wiki($channel_id, $observer_hash, $arr['resource_id']);
+ $item = $w['wiki'];
+
+ if(! $item) {
+ return array('item' => null, 'success' => false);
+ }
+
+ $x = $acl->get();
+
+ $item['allow_cid'] = $x['allow_cid'];
+ $item['allow_gid'] = $x['allow_gid'];
+ $item['deny_cid'] = $x['deny_cid'];
+ $item['deny_gid'] = $x['deny_gid'];
+ $item['item_private'] = intval($acl->is_private());
+
+ $update_title = false;
+
+ if($item['title'] !== $arr['updateRawName']) {
+ $update_title = true;
+ $item['title'] = $arr['updateRawName'];
+ }
+
+ $update = item_store_update($item);
+
+ $item_id = $update['item_id'];
+
+ // update acl for any existing wiki pages
+
+ q("update item set allow_cid = '%s', allow_gid = '%s', deny_cid = '%s', deny_gid = '%s', item_private = %d where resource_type = 'nwikipage' and resource_id = '%s'",
+ dbesc($item['allow_cid']),
+ dbesc($item['allow_gid']),
+ dbesc($item['deny_cid']),
+ dbesc($item['deny_gid']),
+ dbesc($item['item_private']),
+ dbesc($arr['resource_id'])
+ );
+
+
+ if($update['item_id']) {
+ info( t('Wiki updated successfully'));
+ if($update_title) {
+ // Update the wiki name information using iconfig.
+ if(! set_iconfig($update['item_id'], 'wiki', 'rawName', $arr['updateRawName'], true)) {
+ return array('item' => null, 'success' => false);
+ }
+ }
+ return array('item' => $update['item'], 'item_id' => $update['item_id'], 'success' => $update['success']);
+ }
+ else {
+ return array('item' => null, 'success' => false);
+ }
+ }
+
static public function sync_a_wiki_item($uid,$id,$resource_id) {
- $r = q("SELECT * from item WHERE uid = %d AND ( id = %d OR ( resource_type = '%s' and resource_id = %d )) ",
+ $r = q("SELECT * from item WHERE uid = %d AND ( id = %d OR ( resource_type = '%s' and resource_id = '%s' )) ",
intval($uid),
intval($id),
dbesc(NWIKI_ITEM_RESOURCE_TYPE),
- intval($resource_id)
+ dbesc($resource_id)
);
if($r) {
+ $q = q("select * from item where resource_type = 'nwikipage' and resource_id = '%s'",
+ dbesc($r[0]['resource_type'])
+ );
+ if($q) {
+ $r = array_merge($r,$q);
+ }
xchan_query($r);
$sync_item = fetch_post_tags($r);
build_sync_packet($uid,array('wiki' => array(encode_item($sync_item[0],true))));
@@ -148,13 +220,15 @@ class NativeWiki {
// Get wiki metadata
$rawName = get_iconfig($w, 'wiki', 'rawName');
$mimeType = get_iconfig($w, 'wiki', 'mimeType');
+ $typelock = get_iconfig($w, 'wiki', 'typelock');
return array(
- 'wiki' => $w,
- 'rawName' => $rawName,
+ 'wiki' => $w,
+ 'rawName' => $rawName,
'htmlName' => escape_tags($rawName),
- 'urlName' => urlencode(urlencode($rawName)),
- 'mimeType' => $mimeType
+ 'urlName' => urlencode(urlencode($rawName)),
+ 'mimeType' => $mimeType,
+ 'typelock' => $typelock
);
}
}
diff --git a/Zotlabs/Lib/NativeWikiPage.php b/Zotlabs/Lib/NativeWikiPage.php
index 1467a1cfb..209a5ef3c 100644
--- a/Zotlabs/Lib/NativeWikiPage.php
+++ b/Zotlabs/Lib/NativeWikiPage.php
@@ -21,19 +21,30 @@ class NativeWikiPage {
$sql_extra = item_permissions_sql($channel_id,$observer_hash);
$r = q("select * from item where resource_type = 'nwikipage' and resource_id = '%s' and uid = %d and item_deleted = 0
- $sql_extra group by mid",
+ $sql_extra order by title asc",
dbesc($resource_id),
intval($channel_id)
);
if($r) {
- $items = fetch_post_tags($r,true);
+ $x = [];
+ $y = [];
+
+ foreach($r as $rv) {
+ if(! in_array($rv['mid'],$x)) {
+ $y[] = $rv;
+ $x[] = $rv['mid'];
+ }
+ }
+
+ $items = fetch_post_tags($y,true);
+
foreach($items as $page_item) {
$title = get_iconfig($page_item['id'],'nwikipage','pagetitle',t('(No Title)'));
if(urldecode($title) !== 'Home') {
$pages[] = [
'resource_id' => $resource_id,
'title' => escape_tags($title),
- 'url' => urlencode(urlencode($title)),
+ 'url' => str_replace('%2F','/',urlencode(str_replace('%2F','/',urlencode($title)))),
'link_id' => 'id_' . substr($resource_id, 0, 10) . '_' . $page_item['id']
];
}
@@ -44,17 +55,34 @@ class NativeWikiPage {
}
- static public function create_page($channel_id, $observer_hash, $name, $resource_id) {
+ static public function create_page($channel_id, $observer_hash, $name, $resource_id, $mimetype = 'text/bbcode') {
+
+ logger('mimetype: ' . $mimetype);
+
+ if(! in_array($mimetype,[ 'text/markdown','text/bbcode','text/plain','text/html' ]))
+ $mimetype = 'text/markdown';
$w = Zlib\NativeWiki::get_wiki($channel_id, $observer_hash, $resource_id);
+ if (! $w['wiki']) {
+ return array('content' => null, 'message' => 'Error reading wiki', 'success' => false);
+ }
+
// create an empty activity
$arr = [];
- $arr['uid'] = $channel_id;
- $arr['author_xchan'] = $observer_hash;
+ $arr['uid'] = $channel_id;
+ $arr['author_xchan'] = $observer_hash;
+ $arr['mimetype'] = $mimetype;
+ $arr['title'] = $name;
$arr['resource_type'] = 'nwikipage';
- $arr['resource_id'] = $resource_id;
+ $arr['resource_id'] = $resource_id;
+ $arr['allow_cid'] = $w['wiki']['allow_cid'];
+ $arr['allow_gid'] = $w['wiki']['allow_gid'];
+ $arr['deny_cid'] = $w['wiki']['deny_cid'];
+ $arr['deny_gid'] = $w['wiki']['deny_gid'];
+
+ $arr['public_policy'] = map_scope(\Zotlabs\Access\PermissionLimits::Get($channel_id,'view_wiki'),true);
// We may wish to change this some day.
$arr['item_unpublished'] = 1;
@@ -112,8 +140,14 @@ class NativeWikiPage {
if($ic) {
foreach($ic as $c) {
set_iconfig($c['item_id'],'nwikipage','pagetitle',$pageNewName);
+ $ids[] = $c['item_id'];
}
+ $str_ids = implode(',', $ids);
+ q("update item set title = '%s' where id in ($str_ids)",
+ dbesc($pageNewName)
+ );
+
$page = [
'rawName' => $pageNewName,
'htmlName' => escape_tags($pageNewName),
@@ -146,10 +180,11 @@ class NativeWikiPage {
$content = $item['body'];
return [
- 'content' => json_encode($content),
- 'mimeType' => $w['mimeType'],
- 'message' => '',
- 'success' => true
+ 'content' => $content,
+ 'mimeType' => $w['mimeType'],
+ 'pageMimeType' => $item['mimetype'],
+ 'message' => '',
+ 'success' => true
];
}
@@ -180,7 +215,7 @@ class NativeWikiPage {
$processed ++;
$history[] = [
'revision' => $item['revision'],
- 'date' => datetime_convert('UTC',date_default_timezone_get(),$item['created']),
+ 'date' => datetime_convert('UTC',date_default_timezone_get(),$item['edited']),
'name' => $item['author']['xchan_name'],
'title' => get_iconfig($item,'nwikipage','commit_msg')
];
@@ -225,6 +260,7 @@ class NativeWikiPage {
}
$sql_extra = item_permissions_sql($channel_id,$observer_hash);
+
if($revision == (-1))
$sql_extra .= " order by revision desc ";
elseif($revision)
@@ -277,6 +313,7 @@ class NativeWikiPage {
}
$sql_extra = item_permissions_sql($channel_id,$observer_hash);
+
$sql_extra .= " order by revision desc ";
$r = null;
@@ -295,48 +332,21 @@ class NativeWikiPage {
return null;
}
-
-
- static public function prepare_content($s) {
-
- $text = preg_replace_callback('{
- (?:\n\n|\A\n?)
- ( # $1 = the code block -- one or more lines, starting with a space/tab
- (?>
- [ ]{'.'4'.'} # Lines must start with a tab or a tab-width of spaces
- .*\n+
- )+
- )
- ((?=^[ ]{0,'.'4'.'}\S)|\Z) # Lookahead for non-space at line-start, or end of doc
- }xm',
- 'self::nwiki_prepare_content_callback', $s);
-
- return $text;
- }
-
- static public function nwiki_prepare_content_callback($matches) {
- $codeblock = $matches[1];
-
- $codeblock = htmlspecialchars($codeblock, ENT_NOQUOTES, UTF8, false);
- return "\n\n" . $codeblock ;
- }
-
-
-
static public function save_page($arr) {
- $pageUrlName = ((array_key_exists('pageUrlName',$arr)) ? $arr['pageUrlName'] : '');
- $content = ((array_key_exists('content',$arr)) ? purify_html(Zlib\NativeWikiPage::prepare_content($arr['content'])) : '');
- $resource_id = ((array_key_exists('resource_id',$arr)) ? $arr['resource_id'] : '');
+ $pageUrlName = ((array_key_exists('pageUrlName',$arr)) ? $arr['pageUrlName'] : '');
+ $content = ((array_key_exists('content',$arr)) ? $arr['content'] : '');
+ $resource_id = ((array_key_exists('resource_id',$arr)) ? $arr['resource_id'] : '');
$observer_hash = ((array_key_exists('observer_hash',$arr)) ? $arr['observer_hash'] : '');
$channel_id = ((array_key_exists('channel_id',$arr)) ? $arr['channel_id'] : 0);
- $revision = ((array_key_exists('revision',$arr)) ? $arr['revision'] : 0);
+ $revision = ((array_key_exists('revision',$arr)) ? $arr['revision'] : 0);
$w = Zlib\NativeWiki::get_wiki($channel_id, $observer_hash, $resource_id);
if (!$w['wiki']) {
return array('message' => t('Error reading wiki'), 'success' => false);
}
+
// fetch the most recently saved revision.
@@ -345,6 +355,8 @@ class NativeWikiPage {
return array('message' => t('Page not found'), 'success' => false);
}
+ $mimetype = $item['mimetype'];
+
// change just the fields we need to change to create a revision;
unset($item['id']);
@@ -355,6 +367,7 @@ class NativeWikiPage {
$item['author_xchan'] = $observer_hash;
$item['revision'] = (($arr['revision']) ? intval($arr['revision']) + 1 : intval($item['revision']) + 1);
$item['edited'] = datetime_convert();
+ $item['mimetype'] = $mimetype;
if($item['iconfig'] && is_array($item['iconfig']) && count($item['iconfig'])) {
for($x = 0; $x < count($item['iconfig']); $x ++) {
@@ -522,6 +535,29 @@ class NativeWikiPage {
}
return $s;
}
+
+ static public function render_page_history($arr) {
+
+ $pageUrlName = ((array_key_exists('pageUrlName', $arr)) ? $arr['pageUrlName'] : '');
+ $resource_id = ((array_key_exists('resource_id', $arr)) ? $arr['resource_id'] : '');
+
+ $pageHistory = self::page_history([
+ 'channel_id' => \App::$profile_uid,
+ 'observer_hash' => get_observer_hash(),
+ 'resource_id' => $resource_id,
+ 'pageUrlName' => $pageUrlName
+ ]);
+
+ return replace_macros(get_markup_template('nwiki_page_history.tpl'), array(
+ '$pageHistory' => $pageHistory['history'],
+ '$permsWrite' => $arr['permsWrite'],
+ '$name_lbl' => t('Name'),
+ '$msg_label' => t('Message','wiki_history')
+ ));
+
+ }
+
+
/**
* Replace the instances of the string [toc] with a list element that will be populated by
@@ -578,10 +614,13 @@ class NativeWikiPage {
}
static public function get_file_ext($arr) {
- if($arr['mimeType'] == 'text/bbcode')
+ if($arr['mimetype'] === 'text/bbcode')
return '.bb';
- else
+ elseif($arr['mimetype'] === 'text/markdown')
return '.md';
+ elseif($arr['mimetype'] === 'text/plain')
+ return '.txt';
+
}
// This function is derived from
diff --git a/Zotlabs/Lib/PConfig.php b/Zotlabs/Lib/PConfig.php
index d70697fbc..2a0b18aac 100644
--- a/Zotlabs/Lib/PConfig.php
+++ b/Zotlabs/Lib/PConfig.php
@@ -20,11 +20,12 @@ class PConfig {
if(is_null($uid) || $uid === false)
return false;
- if(! array_key_exists($uid, \App::$config))
- \App::$config[$uid] = array();
-
if(! is_array(\App::$config)) {
- btlogger('App::$config not an array: ' . $uid);
+ btlogger('App::$config not an array');
+ }
+
+ if(! array_key_exists($uid, \App::$config)) {
+ \App::$config[$uid] = array();
}
if(! is_array(\App::$config[$uid])) {
@@ -119,7 +120,7 @@ class PConfig {
$dbvalue = ((is_array($value)) ? serialize($value) : $value);
$dbvalue = ((is_bool($dbvalue)) ? intval($dbvalue) : $dbvalue);
- if(get_pconfig($uid, $family, $key) === false) {
+ if(self::Get($uid, $family, $key) === false) {
if(! array_key_exists($uid, \App::$config))
\App::$config[$uid] = array();
if(! array_key_exists($family, \App::$config[$uid]))
diff --git a/Zotlabs/Lib/SConfig.php b/Zotlabs/Lib/SConfig.php
new file mode 100644
index 000000000..ca0d133b2
--- /dev/null
+++ b/Zotlabs/Lib/SConfig.php
@@ -0,0 +1,25 @@
+<?php
+
+namespace Zotlabs\Lib;
+
+// account configuration storage is built on top of the under-utilised xconfig
+
+class SConfig {
+
+ static public function Load($server_id) {
+ return XConfig::Load('s_' . $server_id);
+ }
+
+ static public function Get($server_id,$family,$key,$default = false) {
+ return XConfig::Get('s_' . $server_id,$family,$key, $default);
+ }
+
+ static public function Set($server_id,$family,$key,$value) {
+ return XConfig::Set('s_' . $server_id,$family,$key,$value);
+ }
+
+ static public function Delete($server_id,$family,$key) {
+ return XConfig::Delete('s_' . $server_id,$family,$key);
+ }
+
+}
diff --git a/Zotlabs/Lib/System.php b/Zotlabs/Lib/System.php
index 306c90f4a..c3e11eb6a 100644
--- a/Zotlabs/Lib/System.php
+++ b/Zotlabs/Lib/System.php
@@ -19,6 +19,9 @@ class System {
static public function get_project_version() {
if(is_array(\App::$config) && is_array(\App::$config['system']) && \App::$config['system']['hide_version'])
return '';
+ if(is_array(\App::$config) && is_array(\App::$config['system']) && array_key_exists('std_version',\App::$config['system']))
+ return \App::$config['system']['std_version'];
+
return self::get_std_version();
}
@@ -54,12 +57,15 @@ class System {
return 'https://github.com/redmatrix/hubzilla';
}
+ static public function get_server_role() {
+ return 'pro';
+ }
- static public function get_server_role() {
- if(is_array(\App::$config) && is_array(\App::$config['system']) && \App::$config['system']['server_role'])
- return \App::$config['system']['server_role'];
- return 'standard';
+ static public function get_zot_revision() {
+ $x = [ 'revision' => ZOT_REVISION ];
+ call_hooks('zot_revision',$x);
+ return $x['revision'];
}
static public function get_std_version() {
@@ -72,11 +78,8 @@ class System {
if(get_directory_realm() != DIRECTORY_REALM)
return true;
-
- foreach(['hubzilla','zap'] as $t) {
- if(stristr($p,$t))
- return true;
- }
+ if(in_array(strtolower($p),['hubzilla','zap','red']))
+ return true;
return false;
}
}
diff --git a/Zotlabs/Lib/Techlevels.php b/Zotlabs/Lib/Techlevels.php
index 6a8c36fb3..380901678 100644
--- a/Zotlabs/Lib/Techlevels.php
+++ b/Zotlabs/Lib/Techlevels.php
@@ -7,12 +7,12 @@ class Techlevels {
static public function levels() {
$techlevels = [
- '0' => t('Beginner/Basic'),
- '1' => t('Novice - not skilled but willing to learn'),
- '2' => t('Intermediate - somewhat comfortable'),
- '3' => t('Advanced - very comfortable'),
- '4' => t('Expert - I can write computer code'),
- '5' => t('Wizard - I probably know more than you do')
+ '0' => t('0. Beginner/Basic'),
+ '1' => t('1. Novice - not skilled but willing to learn'),
+ '2' => t('2. Intermediate - somewhat comfortable'),
+ '3' => t('3. Advanced - very comfortable'),
+ '4' => t('4. Expert - I can write computer code'),
+ '5' => t('5. Wizard - I probably know more than you do')
];
return $techlevels;
}
diff --git a/Zotlabs/Lib/ThreadItem.php b/Zotlabs/Lib/ThreadItem.php
index 0ee8e6680..67a507025 100644
--- a/Zotlabs/Lib/ThreadItem.php
+++ b/Zotlabs/Lib/ThreadItem.php
@@ -29,6 +29,7 @@ class ThreadItem {
private $visiting = false;
private $channel = null;
private $display_mode = 'normal';
+ private $reload = '';
public function __construct($data) {
@@ -82,7 +83,8 @@ class ThreadItem {
$dropping = false;
$star = false;
$isstarred = "unstarred fa-star-o";
- $indent = '';
+ $is_comment = false;
+ $is_item = false;
$osparkle = '';
$total_children = $this->count_descendants();
$unseen_comments = (($item['real_uid']) ? 0 : $this->count_unseen_descendants());
@@ -100,10 +102,13 @@ class ThreadItem {
if($item['author']['xchan_network'] === 'rss')
$shareable = true;
+
$mode = $conv->get_mode();
+ $edlink = (($item['item_type'] == ITEM_TYPE_CARD) ? 'card_edit' : 'editpost');
+
if(local_channel() && $observer['xchan_hash'] === $item['author_xchan'])
- $edpost = array(z_root()."/editpost/".$item['id'], t("Edit"));
+ $edpost = array(z_root() . '/' . $edlink . '/' . $item['id'], t('Edit'));
else
$edpost = false;
@@ -136,7 +141,7 @@ class ThreadItem {
$filer = ((($conv->get_profile_owner() == local_channel()) && (! array_key_exists('real_uid',$item))) ? t("Save to Folder") : false);
$profile_avatar = $item['author']['xchan_photo_m'];
- $profile_link = chanlink_url($item['author']['xchan_url']);
+ $profile_link = chanlink_hash($item['author_xchan']);
$profile_name = $item['author']['xchan_name'];
$location = format_location($item);
@@ -152,7 +157,7 @@ class ThreadItem {
$response_verbs[] = 'attendyes';
$response_verbs[] = 'attendno';
$response_verbs[] = 'attendmaybe';
- if($this->is_commentable()) {
+ if($this->is_commentable() && $observer) {
$isevent = true;
$attend = array( t('I will attend'), t('I will not attend'), t('I might attend'));
}
@@ -163,7 +168,7 @@ class ThreadItem {
$response_verbs[] = 'agree';
$response_verbs[] = 'disagree';
$response_verbs[] = 'abstain';
- if($this->is_commentable()) {
+ if($this->is_commentable() && $observer) {
$conlabels = array( t('I agree'), t('I disagree'), t('I abstain'));
$canvote = true;
}
@@ -183,7 +188,7 @@ class ThreadItem {
$like_list = ((x($conv_responses['like'],$item['mid'])) ? $conv_responses['like'][$item['mid'] . '-l'] : '');
if (count($like_list) > MAX_LIKERS) {
$like_list_part = array_slice($like_list, 0, MAX_LIKERS);
- array_push($like_list_part, '<a href="#" data-toggle="modal" data-target="#likeModal-' . $this->get_id() . '"><b>' . t('View all') . '</b></a>');
+ array_push($like_list_part, '<a class="dropdown-item" href="#" data-toggle="modal" data-target="#likeModal-' . $this->get_id() . '"><b>' . t('View all') . '</b></a>');
} else {
$like_list_part = '';
}
@@ -195,7 +200,7 @@ class ThreadItem {
$dislike_button_label = tt('Dislike','Dislikes',$dislike_count,'noun');
if (count($dislike_list) > MAX_LIKERS) {
$dislike_list_part = array_slice($dislike_list, 0, MAX_LIKERS);
- array_push($dislike_list_part, '<a href="#" data-toggle="modal" data-target="#dislikeModal-' . $this->get_id() . '"><b>' . t('View all') . '</b></a>');
+ array_push($dislike_list_part, '<a class="dropdown-item" href="#" data-toggle="modal" data-target="#dislikeModal-' . $this->get_id() . '"><b>' . t('View all') . '</b></a>');
} else {
$dislike_list_part = '';
}
@@ -232,7 +237,7 @@ class ThreadItem {
}
}
else {
- $indent = 'comment';
+ $is_comment = true;
}
@@ -250,8 +255,6 @@ class ThreadItem {
);
}
- $server_role = get_config('system','server_role');
-
$has_bookmarks = false;
if(is_array($item['term'])) {
foreach($item['term'] as $t) {
@@ -264,7 +267,7 @@ class ThreadItem {
if(($item['obj_type'] === ACTIVITY_OBJ_EVENT) && $conv->get_profile_owner() == local_channel())
$has_event = true;
- if($this->is_commentable()) {
+ if($this->is_commentable() && $observer) {
$like = array( t("I like this \x28toggle\x29"), t("like"));
$dislike = array( t("I don't like this \x28toggle\x29"), t("dislike"));
}
@@ -276,13 +279,13 @@ class ThreadItem {
$keep_reports = intval(get_config('system','expire_delivery_reports'));
if($keep_reports === 0)
- $keep_reports = 30;
+ $keep_reports = 10;
if((! get_config('system','disable_dreport')) && strcmp(datetime_convert('UTC','UTC',$item['created']),datetime_convert('UTC','UTC',"now - $keep_reports days")) > 0)
$dreport = t('Delivery Report');
if(strcmp(datetime_convert('UTC','UTC',$item['created']),datetime_convert('UTC','UTC','now - 12 hours')) > 0)
- $indent .= ' shiny';
+ $is_new = true;
localize_item($item);
@@ -310,7 +313,8 @@ class ThreadItem {
$tmp_item = array(
'template' => $this->get_template(),
- 'mode' => $mode,
+ 'mode' => $mode,
+ 'item_type' => intval($item['item_type']),
'type' => implode("",array_slice(explode("/",$item['verb']),-1)),
'body' => $body['html'],
'tags' => $body['tags'],
@@ -337,7 +341,6 @@ class ThreadItem {
'profile_url' => $profile_link,
'thread_action_menu' => thread_action_menu($item,$conv->get_mode()),
'thread_author_menu' => thread_author_menu($item,$conv->get_mode()),
- 'item_photo_menu' => item_photo_menu($item),
'dreport' => $dreport,
'name' => $profile_name,
'thumb' => $profile_avatar,
@@ -361,7 +364,8 @@ class ThreadItem {
'attend_title' => t('Attendance Options'),
'vote_label' => t('Vote'),
'vote_title' => t('Voting Options'),
- 'indent' => $indent,
+ 'is_comment' => $is_comment,
+ 'is_new' => $is_new,
'owner_url' => $this->get_owner_url(),
'owner_photo' => $this->get_owner_photo(),
'owner_name' => $this->get_owner_name(),
@@ -370,7 +374,7 @@ class ThreadItem {
'has_tags' => $has_tags,
'reactions' => $this->reactions,
// Item toolbar buttons
- 'emojis' => (($this->is_toplevel() && $this->is_commentable() && feature_enabled($conv->get_profile_owner(),'emojis')) ? '1' : ''),
+ 'emojis' => (($this->is_toplevel() && $this->is_commentable() && $observer && feature_enabled($conv->get_profile_owner(),'emojis')) ? '1' : ''),
'like' => $like,
'dislike' => ((feature_enabled($conv->get_profile_owner(),'dislike')) ? $dislike : ''),
'share' => $share,
@@ -407,9 +411,10 @@ class ThreadItem {
'showlike' => $showlike,
'showdislike' => $showdislike,
'comment' => $this->get_comment_box($indent),
- 'previewing' => ($conv->is_preview() ? ' preview ' : ''),
+ 'previewing' => ($conv->is_preview() ? true : false ),
+ 'preview_lbl' => t('This is an unsaved preview'),
'wait' => t('Please wait'),
- 'submid' => str_replace(['+','='], ['',''], base64_encode(substr($item['mid'],0,32))),
+ 'submid' => str_replace(['+','='], ['',''], base64_encode($item['mid'])),
'thread_level' => $thread_level
);
@@ -480,6 +485,14 @@ class ThreadItem {
return $this->threaded;
}
+ public function set_reload($val) {
+ $this->reload = $val;
+ }
+
+ public function get_reload() {
+ return $this->reload;
+ }
+
public function set_commentable($val) {
$this->commentable = $val;
foreach($this->get_children() as $child)
@@ -713,11 +726,10 @@ class ThreadItem {
call_hooks('comment_buttons',$arr);
$comment_buttons = $arr['comment_buttons'];
-
$comment_box = replace_macros($template,array(
'$return_path' => '',
'$threaded' => $this->is_threaded(),
- '$jsreload' => '', //(($conv->get_mode() === 'display') ? $_SESSION['return_url'] : ''),
+ '$jsreload' => $conv->reload,
'$type' => (($conv->get_mode() === 'channel') ? 'wall-comment' : 'net-comment'),
'$id' => $this->get_id(),
'$parent' => $this->get_id(),
@@ -735,15 +747,21 @@ class ThreadItem {
'$edquote' => t('Quote'),
'$edcode' => t('Code'),
'$edimg' => t('Image'),
+ '$edatt' => t('Attach File'),
'$edurl' => t('Insert Link'),
'$edvideo' => t('Video'),
'$preview' => t('Preview'), // ((feature_enabled($conv->get_profile_owner(),'preview')) ? t('Preview') : ''),
'$indent' => $indent,
+ '$can_upload' => (perm_is_allowed($conv->get_profile_owner(),get_observer_hash(),'write_storage') && $conv->is_uploadable()),
'$feature_encrypt' => ((feature_enabled($conv->get_profile_owner(),'content_encrypt')) ? true : false),
'$encrypt' => t('Encrypt text'),
'$cipher' => $conv->get_cipher(),
- '$sourceapp' => \App::$sourcename
-
+ '$sourceapp' => \App::$sourcename,
+ '$observer' => get_observer_hash(),
+ '$anoncomments' => ((($conv->get_mode() === 'channel' || $conv->get_mode() === 'display') && perm_is_allowed($conv->get_profile_owner(),'','post_comments')) ? true : false),
+ '$anonname' => [ 'anonname', t('Your full name (required)') ],
+ '$anonmail' => [ 'anonmail', t('Your email address (required)') ],
+ '$anonurl' => [ 'anonurl', t('Your website URL (optional)') ]
));
return $comment_box;
@@ -767,7 +785,7 @@ class ThreadItem {
return;
if($this->is_toplevel() && ($this->get_data_value('author_xchan') != $this->get_data_value('owner_xchan'))) {
- $this->owner_url = chanlink_url($this->data['owner']['xchan_url']);
+ $this->owner_url = chanlink_hash($this->data['owner']['xchan_hash']);
$this->owner_photo = $this->data['owner']['xchan_photo_m'];
$this->owner_name = $this->data['owner']['xchan_name'];
$this->wall_to_wall = true;
diff --git a/Zotlabs/Lib/ThreadStream.php b/Zotlabs/Lib/ThreadStream.php
index beb626f31..436723f8c 100644
--- a/Zotlabs/Lib/ThreadStream.php
+++ b/Zotlabs/Lib/ThreadStream.php
@@ -18,18 +18,21 @@ class ThreadStream {
private $observer = null;
private $writable = false;
private $commentable = false;
+ private $uploadable = false;
private $profile_owner = 0;
private $preview = false;
private $prepared_item = '';
+ public $reload = '';
private $cipher = 'aes256';
// $prepared_item is for use by alternate conversation structures such as photos
// wherein we've already prepared a top level item which doesn't look anything like
// a normal "post" item
- public function __construct($mode, $preview, $prepared_item = '') {
+ public function __construct($mode, $preview, $uploadable, $prepared_item = '') {
$this->set_mode($mode);
$this->preview = $preview;
+ $this->uploadable = $uploadable;
$this->prepared_item = $prepared_item;
$c = ((local_channel()) ? get_pconfig(local_channel(),'system','default_cipher') : '');
if($c)
@@ -55,11 +58,17 @@ class ThreadStream {
$this->profile_owner = \App::$profile['profile_uid'];
$this->writable = perm_is_allowed($this->profile_owner,$ob_hash,'post_comments');
break;
+ case 'cards':
+ $this->profile_owner = \App::$profile['profile_uid'];
+ $this->writable = perm_is_allowed($this->profile_owner,$ob_hash,'post_comments');
+ $this->reload = $_SESSION['return_url'];
+ break;
case 'display':
// in this mode we set profile_owner after initialisation (from conversation()) and then
// pull some trickery which allows us to re-invoke this function afterward
// it's an ugly hack so @FIXME
$this->writable = perm_is_allowed($this->profile_owner,$ob_hash,'post_comments');
+ $this->uploadable = perm_is_allowed($this->profile_owner,$ob_hash,'write_storage');
break;
case 'page':
$this->profile_owner = \App::$profile['uid'];
@@ -91,6 +100,11 @@ class ThreadStream {
return $this->commentable;
}
+ public function is_uploadable() {
+ return $this->uploadable;
+ }
+
+
/**
* Check if page is a preview
*/
@@ -158,7 +172,7 @@ class ThreadStream {
if(intval($item->get_data_value('item_nocomment'))) {
$item->set_commentable(false);
}
- elseif(($this->observer) && (! $item->is_commentable())) {
+ elseif(! $item->is_commentable()) {
if((array_key_exists('owner',$item->data)) && intval($item->data['owner']['abook_self']))
$item->set_commentable(perm_is_allowed($this->profile_owner,$ob_hash,'post_comments'));
else
diff --git a/Zotlabs/Module/Acl.php b/Zotlabs/Module/Acl.php
index 6f5b0ddf9..e164875e8 100644
--- a/Zotlabs/Module/Acl.php
+++ b/Zotlabs/Module/Acl.php
@@ -19,9 +19,9 @@ require_once("include/group.php");
class Acl extends \Zotlabs\Web\Controller {
- function init(){
+ function init() {
- // logger('mod_acl: ' . print_r($_REQUEST,true));
+ logger('mod_acl: ' . print_r($_REQUEST,true));
$start = (x($_REQUEST,'start') ? $_REQUEST['start'] : 0);
$count = (x($_REQUEST,'count') ? $_REQUEST['count'] : 500);
@@ -33,6 +33,7 @@ class Acl extends \Zotlabs\Web\Controller {
// $type =
// '' => standard ACL request
// 'g' => Groups only ACL request
+ // 'f' => forums only ACL request
// 'c' => Connections only ACL request or editor (textarea) mention request
// $_REQUEST['search'] contains ACL search text.
@@ -49,19 +50,19 @@ class Acl extends \Zotlabs\Web\Controller {
$extra_channels = (x($_REQUEST,'extra_channels') ? $_REQUEST['extra_channels'] : array());
// The different autocomplete libraries use different names for the search text
- // parameter. Internaly we'll use $search to represent the search text no matter
+ // parameter. Internally we'll use $search to represent the search text no matter
// what request variable it was attached to.
if(array_key_exists('query',$_REQUEST)) {
$search = $_REQUEST['query'];
}
- if( (! local_channel()) && (! ($type == 'x' || $type == 'c')))
+ if( (! local_channel()) && (! in_array($type, [ 'x', 'c', 'f' ])))
killme();
$permitted = [];
- if(in_array($type, [ 'm', 'a', 'c' ])) {
+ if(in_array($type, [ 'm', 'a', 'c', 'f' ])) {
// These queries require permission checking. We'll create a simple array of xchan_hash for those with
// the requisite permissions which we can check against.
@@ -104,6 +105,8 @@ class Acl extends \Zotlabs\Web\Controller {
if($type == '' || $type == 'g') {
+ // virtual groups based on private profile viewing ability
+
$r = q("select id, profile_guid, profile_name from profile where is_default = 0 and uid = %d",
intval(local_channel())
);
@@ -121,6 +124,8 @@ class Acl extends \Zotlabs\Web\Controller {
}
}
+ // Normal privacy groups
+
$r = q("SELECT groups.id, groups.hash, groups.gname
FROM groups, group_member
WHERE groups.deleted = 0 AND groups.uid = %d
@@ -150,26 +155,35 @@ class Acl extends \Zotlabs\Web\Controller {
}
}
- if($type == '' || $type == 'c') {
+ if($type == '' || $type == 'c' || $type === 'f') {
+
$extra_channels_sql = '';
- // Only include channels who allow the observer to view their permissions
- foreach($extra_channels as $channel) {
- if(perm_is_allowed(intval($channel), get_observer_hash(),'view_contacts'))
- $extra_channels_sql .= "," . intval($channel);
+
+ // Only include channels who allow the observer to view their connections
+ if($extra_channels) {
+ foreach($extra_channels as $channel) {
+ if(perm_is_allowed(intval($channel), get_observer_hash(),'view_contacts')) {
+ if($extra_channel_sql)
+ $extra_channels_sql .= ',';
+ $extra_channels_sql .= intval($channel);
+ }
+ }
}
- $extra_channels_sql = substr($extra_channels_sql,1); // Remove initial comma
-
// Getting info from the abook is better for local users because it contains info about permissions
if(local_channel()) {
if($extra_channels_sql != '')
$extra_channels_sql = " OR (abook_channel IN ($extra_channels_sql)) and abook_hidden = 0 ";
+
+ // Add atokens belonging to the local channel @TODO restrict by search
+
$r2 = null;
$r1 = q("select * from atoken where atoken_uid = %d",
intval(local_channel())
);
+
if($r1) {
require_once('include/security.php');
$r2 = array();
@@ -189,6 +203,7 @@ class Acl extends \Zotlabs\Web\Controller {
}
}
+ // add connections
$r = q("SELECT abook_id as id, xchan_hash as hash, xchan_name as name, xchan_photo_s as micro, xchan_url as url, xchan_addr as nick, abook_their_perms, xchan_pubforum, abook_flags, abook_self
FROM abook left join xchan on abook_xchan = xchan_hash
@@ -293,7 +308,7 @@ class Acl extends \Zotlabs\Web\Controller {
$contacts[] = array(
"photo" => $g['photo'],
"name" => $g['name'],
- "nick" => $g['address'],
+ "nick" => $g['address']
);
}
}
@@ -310,18 +325,24 @@ class Acl extends \Zotlabs\Web\Controller {
$r = array();
if($r) {
- foreach($r as $g){
+ foreach($r as $g) {
- // remove RSS feeds from ACLs - they are inaccessible
- if(strpos($g['hash'],'/') && $type != 'a')
+ if(($g['network'] === 'rss') && ($type != 'a'))
continue;
-
- if(in_array($g['hash'],$permitted) && $type == 'c' && (! $noforums)) {
+
+ $g['hash'] = urlencode($g['hash']);
+
+ if(! $g['nick']) {
+ $t = explode(' ',strtolower($g['name']));
+ $g['nick'] = $t[0] . '@';
+ }
+
+ if(in_array($g['hash'],$permitted) && in_array($type, [ 'c', 'f' ]) && (! $noforums)) {
$contacts[] = array(
"type" => "c",
"photo" => "images/twopeople.png",
- "name" => $g['name'] . '+',
- "id" => $g['id'] . '+',
+ "name" => $g['name'] . (($type === 'f') ? '' : '+'),
+ "id" => urlencode($g['id']) . (($type === 'f') ? '' : '+'),
"xid" => $g['hash'],
"link" => $g['nick'],
"nick" => substr($g['nick'],0,strpos($g['nick'],'@')),
@@ -330,18 +351,20 @@ class Acl extends \Zotlabs\Web\Controller {
"label" => t('network')
);
}
- $contacts[] = array(
- "type" => "c",
- "photo" => $g['micro'],
- "name" => $g['name'],
- "id" => $g['id'],
- "xid" => $g['hash'],
- "link" => $g['nick'],
- "nick" => (($g['nick']) ? substr($g['nick'],0,strpos($g['nick'],'@')) : t('RSS')),
- "self" => (intval($g['abook_self']) ? 'abook-self' : ''),
- "taggable" => '',
- "label" => '',
- );
+ if($type !== 'f') {
+ $contacts[] = array(
+ "type" => "c",
+ "photo" => $g['micro'],
+ "name" => $g['name'],
+ "id" => urlencode($g['id']),
+ "xid" => $g['hash'],
+ "link" => $g['nick'],
+ "nick" => (($g['nick']) ? substr($g['nick'],0,strpos($g['nick'],'@')) : $g['nick']),
+ "self" => (intval($g['abook_self']) ? 'abook-self' : ''),
+ "taggable" => '',
+ "label" => '',
+ );
+ }
}
}
@@ -398,10 +421,12 @@ class Acl extends \Zotlabs\Web\Controller {
$directory = find_upstream_directory($dirmode);
$url = $directory['url'] . '/dirsearch';
}
+
+ $token = get_config('system','realm_token');
$count = (x($_REQUEST,'count') ? $_REQUEST['count'] : 100);
if($url) {
- $query = $url . '?f=' ;
+ $query = $url . '?f=' . (($token) ? '&t=' . urlencode($token) : '');
$query .= '&name=' . urlencode($search) . "&limit=$count" . (($address) ? '&address=' . urlencode($search) : '');
$x = z_fetch_url($query);
diff --git a/Zotlabs/Module/Admin.php b/Zotlabs/Module/Admin.php
index 536d85dde..30f3dfa48 100644
--- a/Zotlabs/Module/Admin.php
+++ b/Zotlabs/Module/Admin.php
@@ -52,6 +52,8 @@ class Admin extends \Zotlabs\Web\Controller {
* Page content
*/
+ nav_set_selected('Admin');
+
$o = '';
if(argc() > 1) {
@@ -91,10 +93,10 @@ class Admin extends \Zotlabs\Web\Controller {
intval(ACCOUNT_BLOCKED)
);
if ($r) {
- $accounts['total'] = array('label' => t('# Accounts'), 'val' => $r[0]['total']);
- $accounts['blocked'] = array('label' => t('# blocked accounts'), 'val' => $r[0]['blocked']);
- $accounts['expired'] = array('label' => t('# expired accounts'), 'val' => $r[0]['expired']);
- $accounts['expiring'] = array('label' => t('# expiring accounts'), 'val' => $r[0]['expiring']);
+ $accounts['total'] = array('label' => t('Accounts'), 'val' => $r[0]['total']);
+ $accounts['blocked'] = array('label' => t('Blocked accounts'), 'val' => $r[0]['blocked']);
+ $accounts['expired'] = array('label' => t('Expired accounts'), 'val' => $r[0]['expired']);
+ $accounts['expiring'] = array('label' => t('Expiring accounts'), 'val' => $r[0]['expiring']);
}
// pending registrations
@@ -105,9 +107,9 @@ class Admin extends \Zotlabs\Web\Controller {
$channels = array();
$r = q("SELECT COUNT(*) AS total, COUNT(CASE WHEN channel_primary = 1 THEN 1 ELSE NULL END) AS main, COUNT(CASE WHEN channel_primary = 0 THEN 1 ELSE NULL END) AS clones FROM channel WHERE channel_removed = 0");
if ($r) {
- $channels['total'] = array('label' => t('# Channels'), 'val' => $r[0]['total']);
- $channels['main'] = array('label' => t('# primary'), 'val' => $r[0]['main']);
- $channels['clones'] = array('label' => t('# clones'), 'val' => $r[0]['clones']);
+ $channels['total'] = array('label' => t('Channels'), 'val' => $r[0]['total']);
+ $channels['main'] = array('label' => t('Primary'), 'val' => $r[0]['main']);
+ $channels['clones'] = array('label' => t('Clones'), 'val' => $r[0]['clones']);
}
// We can do better, but this is a quick queue status
@@ -118,14 +120,11 @@ class Admin extends \Zotlabs\Web\Controller {
// If no plugins active return 0, otherwise list of plugin names
$plugins = (count(\App::$plugins) == 0) ? count(\App::$plugins) : \App::$plugins;
+ if(is_array($plugins))
+ sort($plugins);
+
// Could be extended to provide also other alerts to the admin
$alertmsg = '';
- // annoy admin about upcoming unsupported PHP version
- if (version_compare(PHP_VERSION, '5.4', '<')) {
- $alertmsg = 'Your PHP version ' . PHP_VERSION . ' will not be supported with the next major release of $Projectname. You are strongly urged to upgrade to a current version.'
- . '<br>PHP 5.3 has reached its <a href="http://php.net/eol.php" class="alert-link">End of Life (EOL)</a> in August 2014.'
- . ' A list about current PHP versions can be found <a href="http://php.net/supported-versions.php" class="alert-link">here</a>.';
- }
$vmaster = get_repository_version('master');
$vdev = get_repository_version('dev');
diff --git a/Zotlabs/Module/Admin/Plugins.php b/Zotlabs/Module/Admin/Plugins.php
index 527e96496..feb29e9d6 100644
--- a/Zotlabs/Module/Admin/Plugins.php
+++ b/Zotlabs/Module/Admin/Plugins.php
@@ -3,10 +3,14 @@
namespace Zotlabs\Module\Admin;
use \Zotlabs\Storage\GitRepo as GitRepo;
+use \Michelf\MarkdownExtra;
class Plugins {
-
+ /**
+ * @brief
+ *
+ */
function post() {
if(argc() > 2 && is_file("addon/" . argv(2) . "/" . argv(2) . ".php")) {
@@ -15,16 +19,15 @@ class Plugins {
$func = argv(2) . '_plugin_admin_post';
$func($a);
}
-
- goaway(z_root() . '/admin/plugins/' . argv(2) );
+ goaway(z_root() . '/admin/plugins/' . argv(2) );
}
elseif(argc() > 2) {
switch(argv(2)) {
case 'updaterepo':
if (array_key_exists('repoName', $_REQUEST)) {
$repoName = $_REQUEST['repoName'];
- }
+ }
else {
json_return_and_die(array('message' => 'No repo name provided.', 'success' => false));
}
@@ -101,16 +104,15 @@ class Plugins {
logger('Repo directory not writable to web server: ' . $repoDir);
json_return_and_die(array('message' => 'Repo directory not writable to web server.', 'success' => false));
}
- // TODO: remove directory and unlink /addon/files
+ /// @TODO remove directory and unlink /addon/files
if (rrmdir($repoDir)) {
json_return_and_die(array('message' => 'Repo deleted.', 'success' => true));
} else {
json_return_and_die(array('message' => 'Error deleting addon repo.', 'success' => false));
}
case 'installrepo':
- require_once('library/markdown.php');
if (array_key_exists('repoURL', $_REQUEST)) {
- require_once('library/PHPGit.autoload.php'); // Load PHPGit dependencies
+ require_once('library/PHPGit.autoload.php'); // Load PHPGit dependencies
$repoURL = $_REQUEST['repoURL'];
$extendDir = 'store/[data]/git/sys/extend';
$addonDir = $extendDir . '/addon';
@@ -170,9 +172,8 @@ class Plugins {
json_return_and_die(array('repo' => $repo, 'message' => '', 'success' => true));
}
case 'addrepo':
- require_once('library/markdown.php');
if (array_key_exists('repoURL', $_REQUEST)) {
- require_once('library/PHPGit.autoload.php'); // Load PHPGit dependencies
+ require_once('library/PHPGit.autoload.php'); // Load PHPGit dependencies
$repoURL = $_REQUEST['repoURL'];
$extendDir = 'store/[data]/git/sys/extend';
$addonDir = $extendDir . '/addon';
@@ -225,7 +226,7 @@ class Plugins {
$repo['readme'] = $repo['manifest'] = null;
foreach ($git->git->tree('master') as $object) {
if ($object['type'] == 'blob' && (strtolower($object['file']) === 'readme.md' || strtolower($object['file']) === 'readme')) {
- $repo['readme'] = Markdown($git->git->cat->blob($object['hash']));
+ $repo['readme'] = MarkdownExtra::defaultTransform($git->git->cat->blob($object['hash']));
} else if ($object['type'] == 'blob' && strtolower($object['file']) === 'manifest.json') {
$repo['manifest'] = $git->git->cat->blob($object['hash']);
}
@@ -241,7 +242,11 @@ class Plugins {
}
}
-
+ /**
+ * @brief Plugins admin page.
+ *
+ * @return string with parsed HTML
+ */
function get() {
/*
@@ -254,13 +259,13 @@ class Plugins {
notice( t("Item not found.") );
return '';
}
-
+
$enabled = in_array($plugin,\App::$plugins);
$info = get_plugin_info($plugin);
$x = check_plugin_versions($info);
-
+
// disable plugins which are installed but incompatible versions
-
+
if($enabled && ! $x) {
$enabled = false;
$idz = array_search($plugin, \App::$plugins);
@@ -271,7 +276,7 @@ class Plugins {
}
}
$info['disabled'] = 1-intval($x);
-
+
if (x($_GET,"a") && $_GET['a']=="t"){
check_form_security_token_redirectOnErr('/admin/plugins', 'admin_plugins', 't');
$pinstalled = false;
@@ -297,9 +302,9 @@ class Plugins {
}
goaway(z_root() . '/admin/plugins' );
}
+
// display plugin details
- require_once('library/markdown.php');
-
+
if (in_array($plugin, \App::$plugins)){
$status = 'on';
$action = t('Disable');
@@ -307,21 +312,21 @@ class Plugins {
$status = 'off';
$action = t('Enable');
}
-
+
$readme = null;
if (is_file("addon/$plugin/README.md")){
$readme = file_get_contents("addon/$plugin/README.md");
- $readme = Markdown($readme);
+ $readme = MarkdownExtra::defaultTransform($readme);
} else if (is_file("addon/$plugin/README")){
$readme = "<pre>". file_get_contents("addon/$plugin/README") ."</pre>";
}
-
+
$admin_form = '';
-
+
$r = q("select * from addon where plugin_admin = 1 and aname = '%s' limit 1",
dbesc($plugin)
);
-
+
if($r) {
@require_once("addon/$plugin/$plugin.php");
if(function_exists($plugin.'_plugin_admin')) {
@@ -329,8 +334,8 @@ class Plugins {
$func($a, $admin_form);
}
}
-
-
+
+
$t = get_markup_template('admin_plugins_details.tpl');
return replace_macros($t, array(
'$title' => t('Administration'),
@@ -338,7 +343,7 @@ class Plugins {
'$toggle' => t('Toggle'),
'$settings' => t('Settings'),
'$baseurl' => z_root(),
-
+
'$plugin' => $plugin,
'$status' => $status,
'$action' => $action,
@@ -351,17 +356,17 @@ class Plugins {
'$str_serverroles' => t('Compatible Server Roles: '),
'$str_requires' => t('Requires: '),
'$disabled' => t('Disabled - version incompatibility'),
-
+
'$admin_form' => $admin_form,
'$function' => 'plugins',
'$screenshot' => '',
'$readme' => $readme,
-
+
'$form_security_token' => get_form_security_token('admin_plugins'),
));
}
-
-
+
+
/*
* List plugins
*/
@@ -374,9 +379,9 @@ class Plugins {
$info = get_plugin_info($id);
$enabled = in_array($id,\App::$plugins);
$x = check_plugin_versions($info);
-
+
// disable plugins which are installed but incompatible versions
-
+
if($enabled && ! $x) {
$enabled = false;
$idz = array_search($id, \App::$plugins);
@@ -387,19 +392,19 @@ class Plugins {
}
}
$info['disabled'] = 1-intval($x);
-
+
$plugins[] = array( $id, (($enabled)?"on":"off") , $info);
}
}
}
-
+
usort($plugins,'self::plugin_sort');
$allowManageRepos = false;
if(is_writable('extend/addon') && is_writable('store/[data]')) {
$allowManageRepos = true;
- }
-
+ }
+
$admin_plugins_add_repo_form= replace_macros(
get_markup_template('admin_plugins_addrepo.tpl'), array(
'$post' => 'admin/plugins/addrepo',
@@ -418,14 +423,14 @@ class Plugins {
'$cancel' => t('Cancel')
)
);
-
+
$reponames = $this->listAddonRepos();
$addonrepos = [];
foreach($reponames as $repo) {
$addonrepos[] = array('name' => $repo, 'description' => '');
- // TODO: Parse repo info to provide more information about repos
+ /// @TODO Parse repo info to provide more information about repos
}
-
+
$t = get_markup_template('admin_plugins.tpl');
return replace_macros($t, array(
'$title' => t('Administration'),
@@ -471,5 +476,4 @@ class Plugins {
return(strcmp(strtolower($a[2]['name']),strtolower($b[2]['name'])));
}
-
} \ No newline at end of file
diff --git a/Zotlabs/Module/Admin/Site.php b/Zotlabs/Module/Admin/Site.php
index 829ca71e4..d3d058c53 100644
--- a/Zotlabs/Module/Admin/Site.php
+++ b/Zotlabs/Module/Admin/Site.php
@@ -17,7 +17,6 @@ class Site {
check_form_security_token_redirectOnErr('/admin/site', 'admin_site');
$sitename = ((x($_POST,'sitename')) ? notags(trim($_POST['sitename'])) : '');
- $server_role = ((x($_POST,'server_role')) ? notags(trim($_POST['server_role'])) : 'standard');
$banner = ((x($_POST,'banner')) ? trim($_POST['banner']) : false);
@@ -48,6 +47,10 @@ class Site {
$no_community_page = !((x($_POST,'no_community_page')) ? True : False);
$default_expire_days = ((array_key_exists('default_expire_days',$_POST)) ? intval($_POST['default_expire_days']) : 0);
+ $reply_address = ((array_key_exists('reply_address',$_POST) && trim($_POST['reply_address'])) ? trim($_POST['reply_address']) : 'noreply@' . \App::get_hostname());
+ $from_email = ((array_key_exists('from_email',$_POST) && trim($_POST['from_email'])) ? trim($_POST['from_email']) : 'Administrator@' . \App::get_hostname());
+ $from_email_name = ((array_key_exists('from_email_name',$_POST) && trim($_POST['from_email_name'])) ? trim($_POST['from_email_name']) : \Zotlabs\Lib\System::get_site_name());
+
$verifyssl = ((x($_POST,'verifyssl')) ? True : False);
$proxyuser = ((x($_POST,'proxyuser')) ? notags(trim($_POST['proxyuser'])) : '');
$proxy = ((x($_POST,'proxy')) ? notags(trim($_POST['proxy'])) : '');
@@ -59,12 +62,12 @@ class Site {
$feed_contacts = ((x($_POST,'feed_contacts')) ? intval($_POST['feed_contacts']) : 0);
$verify_email = ((x($_POST,'verify_email')) ? 1 : 0);
$techlevel_lock = ((x($_POST,'techlock')) ? intval($_POST['techlock']) : 0);
+ $imagick_path = ((x($_POST,'imagick_path')) ? trim($_POST['imagick_path']) : '');
$techlevel = null;
if(array_key_exists('techlevel', $_POST))
$techlevel = intval($_POST['techlevel']);
- set_config('system', 'server_role', $server_role);
set_config('system', 'feed_contacts', $feed_contacts);
set_config('system', 'delivery_interval', $delivery_interval);
set_config('system', 'delivery_batch_count', $delivery_batch_count);
@@ -77,8 +80,16 @@ class Site {
set_config('system', 'enable_context_help', $enable_context_help);
set_config('system', 'verify_email', $verify_email);
set_config('system', 'default_expire_days', $default_expire_days);
+ set_config('system', 'reply_address', $reply_address);
+ set_config('system', 'from_email', $from_email);
+ set_config('system', 'from_email_name' , $from_email_name);
+ set_config('system', 'imagick_convert_path' , $imagick_path);
+
+
set_config('system', 'techlevel_lock', $techlevel_lock);
+
+
if(! is_null($techlevel))
set_config('system', 'techlevel', $techlevel);
@@ -163,6 +174,14 @@ class Site {
foreach($files as $file) {
$vars = '';
$f = basename($file);
+
+ $info = get_theme_info($f);
+ $compatible = check_plugin_versions($info);
+ if(!$compatible) {
+ $theme_choices[$f] = $theme_choices_mobile[$f] = sprintf(t('%s - (Incompatible)'), $f);
+ continue;
+ }
+
if (file_exists($file . '/library'))
continue;
if (file_exists($file . '/mobile'))
@@ -189,7 +208,7 @@ class Site {
// directory server should not be set or settable unless we are a directory client
if($dirmode == DIRECTORY_MODE_NORMAL) {
- $x = q("select site_url from site where site_flags in (%d,%d) and site_realm = '%s'",
+ $x = q("select site_url from site where site_flags in (%d,%d) and site_realm = '%s' and site_dead = 0",
intval(DIRECTORY_MODE_SECONDARY),
intval(DIRECTORY_MODE_PRIMARY),
dbesc($realm)
@@ -235,12 +254,6 @@ class Site {
// now invert the logic for the setting.
$discover_tab = (1 - $discover_tab);
- $server_roles = [
- 'basic' => t('Basic/Minimal Social Networking'),
- 'standard' => t('Standard Configuration (default)'),
- 'pro' => t('Professional')
- ];
-
$techlevels = [
'0' => t('Beginner/Basic'),
'1' => t('Novice - not skilled but willing to learn'),
@@ -267,8 +280,6 @@ class Site {
// name, label, value, help string, extra data...
'$sitename' => array('sitename', t("Site name"), htmlspecialchars(get_config('system','sitename'), ENT_QUOTES, 'UTF-8'),''),
- '$server_role' => array('server_role', t("Server Configuration/Role"), get_config('system','server_role'),'',$server_roles),
-
'$techlevel' => [ 'techlevel', t('Site default technical skill level'), get_config('system','techlevel'), t('Used to provide a member experience matched to technical comfort level'), $techlevels ],
'$techlock' => [ 'techlock', t('Lock the technical skill level setting'), get_config('system','techlevel_lock'), t('Members can set their own technical comfort level by default') ],
@@ -296,6 +307,10 @@ class Site {
'$login_on_homepage' => array('login_on_homepage', t("Login on Homepage"),((intval($homelogin) || $homelogin === false) ? 1 : '') , t("Present a login box to visitors on the home page if no other content has been configured.")),
'$enable_context_help' => array('enable_context_help', t("Enable context help"),((intval($enable_context_help) === 1 || $enable_context_help === false) ? 1 : 0) , t("Display contextual help for the current page when the help button is pressed.")),
+ '$reply_address' => [ 'reply_address', t('Reply-to email address for system generated email.'), get_config('system','reply_address','noreply@' . \App::get_hostname()),'' ],
+ '$from_email' => [ 'from_email', t('Sender (From) email address for system generated email.'), get_config('system','from_email','Administrator@' . \App::get_hostname()),'' ],
+ '$from_email_name' => [ 'from_email_name', t('Name of email sender for system generated email.'), get_config('system','from_email_name',\Zotlabs\Lib\System::get_site_name()),'' ],
+
'$directory_server' => (($dir_choices) ? array('directory_server', t("Directory Server URL"), get_config('system','directory_server'), t("Default directory server"), $dir_choices) : null),
'$proxyuser' => array('proxyuser', t("Proxy user"), get_config('system','proxyuser'), ""),
@@ -304,10 +319,11 @@ class Site {
'$delivery_interval' => array('delivery_interval', t("Delivery interval"), (x(get_config('system','delivery_interval'))?get_config('system','delivery_interval'):2), t("Delay background delivery processes by this many seconds to reduce system load. Recommend: 4-5 for shared hosts, 2-3 for virtual private servers. 0-1 for large dedicated servers.")),
'$delivery_batch_count' => array('delivery_batch_count', t('Deliveries per process'),(x(get_config('system','delivery_batch_count'))?get_config('system','delivery_batch_count'):1), t("Number of deliveries to attempt in a single operating system process. Adjust if necessary to tune system performance. Recommend: 1-5.")),
'$poll_interval' => array('poll_interval', t("Poll interval"), (x(get_config('system','poll_interval'))?get_config('system','poll_interval'):2), t("Delay background polling processes by this many seconds to reduce system load. If 0, use delivery interval.")),
+ '$imagick_path' => array('imagick_path', t("Path to ImageMagick convert program"), get_config('system','imagick_convert_path'), t("If set, use this program to generate photo thumbnails for huge images ( > 4000 pixels in either dimension), otherwise memory exhaustion may occur. Example: /usr/bin/convert")),
'$maxloadavg' => array('maxloadavg', t("Maximum Load Average"), ((intval(get_config('system','maxloadavg')) > 0)?get_config('system','maxloadavg'):50), t("Maximum system load before delivery and poll processes are deferred - default 50.")),
'$default_expire_days' => array('default_expire_days', t('Expiration period in days for imported (grid/network) content'), intval(get_config('system','default_expire_days')), t('0 for no expiration of imported content')),
'$form_security_token' => get_form_security_token("admin_site"),
));
}
-} \ No newline at end of file
+}
diff --git a/Zotlabs/Module/Admin/Themes.php b/Zotlabs/Module/Admin/Themes.php
index 63a9a1670..8e72a1318 100644
--- a/Zotlabs/Module/Admin/Themes.php
+++ b/Zotlabs/Module/Admin/Themes.php
@@ -2,38 +2,41 @@
namespace Zotlabs\Module\Admin;
+use \Michelf\MarkdownExtra;
+/**
+ * @brief Admin area theme settings.
+ */
class Themes {
+ /**
+ * @brief
+ *
+ */
function post() {
$theme = argv(2);
if (is_file("view/theme/$theme/php/config.php")){
require_once("view/theme/$theme/php/config.php");
- // fixme add parent theme if derived
- if (function_exists("theme_admin_post")){
+ /// @FIXME add parent theme if derived
+ if (function_exists('theme_admin_post')){
theme_admin_post($a);
}
}
info(t('Theme settings updated.'));
- if(is_ajax())
+ if(is_ajax())
return;
-
+
goaway(z_root() . '/admin/themes/' . $theme );
}
-
-
-
/**
* @brief Themes admin page.
*
- * @return string
+ * @return string with parsed HTML
*/
-
function get(){
-
$allowed_themes_str = get_config('system', 'allowed_themes');
$allowed_themes_raw = explode(',', $allowed_themes_str);
$allowed_themes = array();
@@ -41,7 +44,7 @@ class Themes {
foreach($allowed_themes_raw as $x)
if(strlen(trim($x)))
$allowed_themes[] = trim($x);
-
+
$themes = array();
$files = glob('view/theme/*');
if($files) {
@@ -53,56 +56,55 @@ class Themes {
$themes[] = array('name' => $f, 'experimental' => $is_experimental, 'supported' => $is_supported, 'allowed' => $is_allowed);
}
}
-
+
if(! count($themes)) {
notice( t('No themes found.'));
return '';
}
-
+
/*
* Single theme
*/
-
+
if (\App::$argc == 3){
$theme = \App::$argv[2];
if(! is_dir("view/theme/$theme")){
notice( t("Item not found.") );
return '';
}
-
+
if (x($_GET,"a") && $_GET['a']=="t"){
check_form_security_token_redirectOnErr('/admin/themes', 'admin_themes', 't');
-
+
// Toggle theme status
-
+
$this->toggle_theme($themes, $theme, $result);
$s = $this->rebuild_theme_table($themes);
if($result)
info( sprintf('Theme %s enabled.', $theme));
else
info( sprintf('Theme %s disabled.', $theme));
-
+
set_config('system', 'allowed_themes', $s);
goaway(z_root() . '/admin/themes' );
}
-
+
// display theme details
- require_once('library/markdown.php');
-
+
if ($this->theme_status($themes,$theme)) {
$status="on"; $action= t("Disable");
} else {
$status="off"; $action= t("Enable");
}
-
+
$readme=Null;
if (is_file("view/theme/$theme/README.md")){
$readme = file_get_contents("view/theme/$theme/README.md");
- $readme = Markdown($readme);
+ $readme = MarkdownExtra::defaultTransform($readme);
} else if (is_file("view/theme/$theme/README")){
- $readme = "<pre>". file_get_contents("view/theme/$theme/README") ."</pre>";
+ $readme = '<pre>'. file_get_contents("view/theme/$theme/README") .'</pre>';
}
-
+
$admin_form = '';
if (is_file("view/theme/$theme/php/config.php")){
require_once("view/theme/$theme/php/config.php");
@@ -110,11 +112,11 @@ class Themes {
$admin_form = theme_admin($a);
}
}
-
+
$screenshot = array( get_theme_screenshot($theme), t('Screenshot'));
if(! stristr($screenshot[0],$theme))
$screenshot = null;
-
+
$t = get_markup_template('admin_plugins_details.tpl');
return replace_macros($t, array(
'$title' => t('Administration'),
@@ -122,7 +124,7 @@ class Themes {
'$toggle' => t('Toggle'),
'$settings' => t('Settings'),
'$baseurl' => z_root(),
-
+
'$plugin' => $theme,
'$status' => $status,
'$action' => $action,
@@ -133,22 +135,22 @@ class Themes {
'$str_maintainer' => t('Maintainer: '),
'$screenshot' => $screenshot,
'$readme' => $readme,
-
+
'$form_security_token' => get_form_security_token('admin_themes'),
));
}
-
+
/*
* List themes
*/
-
+
$xthemes = array();
if($themes) {
foreach($themes as $th) {
$xthemes[] = array($th['name'],(($th['allowed']) ? "on" : "off"), get_theme_info($th['name']));
}
}
-
+
$t = get_markup_template('admin_plugins.tpl');
return replace_macros($t, array(
'$title' => t('Administration'),
@@ -162,13 +164,14 @@ class Themes {
'$form_security_token' => get_form_security_token('admin_themes'),
));
}
-
/**
- * @param array $themes
- * @param string $th
- * @param int $result
+ * @brief Toggle a theme.
+ *
+ * @param array &$themes
+ * @param[in] string $th
+ * @param[out] int &$result
*/
function toggle_theme(&$themes, $th, &$result) {
for($x = 0; $x < count($themes); $x ++) {
@@ -184,7 +187,7 @@ class Themes {
}
}
}
-
+
/**
* @param array $themes
* @param string $th
@@ -203,8 +206,7 @@ class Themes {
}
return 0;
}
-
-
+
/**
* @param array $themes
* @return string
@@ -222,12 +224,5 @@ class Themes {
}
return $o;
}
-
-
-
-
-
-
-
-} \ No newline at end of file
+}
diff --git a/Zotlabs/Module/Appman.php b/Zotlabs/Module/Appman.php
index 270301d34..5c0667357 100644
--- a/Zotlabs/Module/Appman.php
+++ b/Zotlabs/Module/Appman.php
@@ -36,8 +36,9 @@ class Appman extends \Zotlabs\Web\Controller {
if(Zlib\Apps::app_installed(local_channel(),$arr))
info( t('App installed.') . EOL);
-
- return;
+
+ goaway(z_root() . '/apps');
+ return; //not reached
}
@@ -83,6 +84,20 @@ class Appman extends \Zotlabs\Web\Controller {
}
$channel = \App::get_channel();
+
+ if(argc() > 2) {
+ if(argv(2) === 'moveup') {
+ Zlib\Apps::moveup(local_channel(),argv(1));
+ }
+ if(argv(2) === 'movedown') {
+ Zlib\Apps::movedown(local_channel(),argv(1));
+ }
+ goaway(z_root() . '/apporder');
+ }
+
+
+
+
$app = null;
$embed = null;
if($_REQUEST['appid']) {
diff --git a/Zotlabs/Module/Apporder.php b/Zotlabs/Module/Apporder.php
new file mode 100644
index 000000000..956548d1f
--- /dev/null
+++ b/Zotlabs/Module/Apporder.php
@@ -0,0 +1,45 @@
+<?php
+
+namespace Zotlabs\Module;
+
+use \Zotlabs\Lib as Zlib;
+
+class Apporder extends \Zotlabs\Web\Controller {
+
+ function post() {
+
+ }
+
+ function get() {
+
+ if(! local_channel())
+ return;
+
+ nav_set_selected('Order Apps');
+
+ $syslist = array();
+ $list = Zlib\Apps::app_list(local_channel(), false, 'nav_featured_app');
+ if($list) {
+ foreach($list as $li) {
+ $syslist[] = Zlib\Apps::app_encode($li);
+ }
+ }
+ Zlib\Apps::translate_system_apps($syslist);
+
+ usort($syslist,'Zotlabs\\Lib\\Apps::app_name_compare');
+
+ $syslist = Zlib\Apps::app_order(local_channel(),$syslist);
+
+ foreach($syslist as $app) {
+ $nav_apps[] = Zlib\Apps::app_render($app,'nav-order');
+ }
+
+ return replace_macros(get_markup_template('apporder.tpl'),
+ [
+ '$header' => t('Change Order of Navigation Apps'),
+ '$desc' => t('Use arrows to move the corresponding app up or down in the display list'),
+ '$nav_apps' => $nav_apps
+ ]
+ );
+ }
+}
diff --git a/Zotlabs/Module/Apps.php b/Zotlabs/Module/Apps.php
index 2df6d675f..2f61f2932 100644
--- a/Zotlabs/Module/Apps.php
+++ b/Zotlabs/Module/Apps.php
@@ -7,6 +7,8 @@ use \Zotlabs\Lib as Zlib;
class Apps extends \Zotlabs\Web\Controller {
function get() {
+
+ nav_set_selected('Apps');
if(argc() == 2 && argv(1) == 'edit')
$mode = 'edit';
@@ -41,9 +43,12 @@ class Apps extends \Zotlabs\Web\Controller {
return replace_macros(get_markup_template('myapps.tpl'), array(
'$sitename' => get_config('system','sitename'),
- '$cat' => ((array_key_exists('cat',$_GET) && $_GET['cat']) ? ' - ' . escape_tags($_GET['cat']) : ''),
+ '$cat' => ((array_key_exists('cat',$_GET) && $_GET['cat']) ? escape_tags($_GET['cat']) : ''),
'$title' => t('Apps'),
'$apps' => $apps,
+ '$authed' => ((local_channel()) ? true : false),
+ '$manage' => t('Manage apps'),
+ '$create' => (($mode == 'edit') ? t('Create new app') : '')
));
}
diff --git a/Zotlabs/Module/Attach.php b/Zotlabs/Module/Attach.php
index 94f46978a..490d5edd0 100644
--- a/Zotlabs/Module/Attach.php
+++ b/Zotlabs/Module/Attach.php
@@ -31,7 +31,7 @@ class Attach extends \Zotlabs\Web\Controller {
$unsafe_types = array('text/html','text/css','application/javascript');
- if(in_array($r['data']['filetype'],$unsafe_types)) {
+ if(in_array($r['data']['filetype'],$unsafe_types) && (! channel_codeallowed($r['data']['uid']))) {
header('Content-type: text/plain');
}
else {
diff --git a/Zotlabs/Module/Authorize.php b/Zotlabs/Module/Authorize.php
new file mode 100644
index 000000000..06f66c456
--- /dev/null
+++ b/Zotlabs/Module/Authorize.php
@@ -0,0 +1,71 @@
+<?php
+
+namespace Zotlabs\Module;
+
+
+class Authorize extends \Zotlabs\Web\Controller {
+
+
+ function get() {
+
+
+ // workaround for HTTP-auth in CGI mode
+ if (x($_SERVER, 'REDIRECT_REMOTE_USER')) {
+ $userpass = base64_decode(substr($_SERVER["REDIRECT_REMOTE_USER"], 6)) ;
+ if(strlen($userpass)) {
+ list($name, $password) = explode(':', $userpass);
+ $_SERVER['PHP_AUTH_USER'] = $name;
+ $_SERVER['PHP_AUTH_PW'] = $password;
+ }
+ }
+
+ if (x($_SERVER, 'HTTP_AUTHORIZATION')) {
+ $userpass = base64_decode(substr($_SERVER["HTTP_AUTHORIZATION"], 6)) ;
+ if(strlen($userpass)) {
+ list($name, $password) = explode(':', $userpass);
+ $_SERVER['PHP_AUTH_USER'] = $name;
+ $_SERVER['PHP_AUTH_PW'] = $password;
+ }
+ }
+
+
+
+
+ require_once('include/oauth2.php');
+
+ $request = \OAuth2\Request::createFromGlobals();
+ $response = new \OAuth2\Response();
+
+ // validate the authorize request
+ if (! $oauth2_server->validateAuthorizeRequest($request, $response)) {
+ $response->send();
+ killme();
+ }
+
+ // display an authorization form
+ if (empty($_POST)) {
+
+ return '
+<form method="post">
+ <label>Do You Authorize TestClient?</label><br />
+ <input type="submit" name="authorized" value="yes">
+ <input type="submit" name="authorized" value="no">
+</form>';
+ }
+
+ // print the authorization code if the user has authorized your client
+ $is_authorized = ($_POST['authorized'] === 'yes');
+ $oauth2_server->handleAuthorizeRequest($request, $response, $is_authorized);
+ if ($is_authorized) {
+ // this is only here so that you get to see your code in the cURL request. Otherwise,
+ // we'd redirect back to the client
+ $code = substr($response->getHttpHeader('Location'), strpos($response->getHttpHeader('Location'), 'code=')+5, 40);
+ echo("SUCCESS! Authorization Code: $code");
+
+ }
+
+ $response->send();
+ killme();
+ }
+
+} \ No newline at end of file
diff --git a/Zotlabs/Module/Block.php b/Zotlabs/Module/Block.php
index e671730f6..d0fed44fe 100644
--- a/Zotlabs/Module/Block.php
+++ b/Zotlabs/Module/Block.php
@@ -3,8 +3,6 @@ namespace Zotlabs\Module;
require_once('include/items.php');
require_once('include/conversation.php');
-require_once('include/page_widgets.php');
-
class Block extends \Zotlabs\Web\Controller {
diff --git a/Zotlabs/Module/Bookmarks.php b/Zotlabs/Module/Bookmarks.php
index 733bfd4e3..e147ffe6c 100644
--- a/Zotlabs/Module/Bookmarks.php
+++ b/Zotlabs/Module/Bookmarks.php
@@ -7,6 +7,9 @@ class Bookmarks extends \Zotlabs\Web\Controller {
function init() {
if(! local_channel())
return;
+
+ nav_set_selected('View Bookmarks');
+
$item_id = intval($_REQUEST['item']);
$burl = trim($_REQUEST['burl']);
@@ -68,7 +71,8 @@ class Bookmarks extends \Zotlabs\Web\Controller {
$channel = \App::get_channel();
- $o = profile_tabs($a,true,$channel['channel_address']);
+ //$o = profile_tabs($a,true,$channel['channel_address']);
+ $o = '';
$o .= '<div class="generic-content-wrapper-styled">';
diff --git a/Zotlabs/Module/Cal.php b/Zotlabs/Module/Cal.php
index b982d19a8..41676ce02 100644
--- a/Zotlabs/Module/Cal.php
+++ b/Zotlabs/Module/Cal.php
@@ -86,7 +86,8 @@ class Cal extends \Zotlabs\Web\Controller {
$o = '';
- $tabs = profile_tabs($a, True, $channel['channel_address']);
+ //$tabs = profile_tabs($a, True, $channel['channel_address']);
+ $tabs = '';
$mode = 'view';
$y = 0;
diff --git a/Zotlabs/Module/Card_edit.php b/Zotlabs/Module/Card_edit.php
new file mode 100644
index 000000000..7cc563fd2
--- /dev/null
+++ b/Zotlabs/Module/Card_edit.php
@@ -0,0 +1,138 @@
+<?php
+namespace Zotlabs\Module;
+
+require_once('include/channel.php');
+require_once('include/acl_selectors.php');
+require_once('include/conversation.php');
+
+class Card_edit extends \Zotlabs\Web\Controller {
+
+
+ function get() {
+
+ // Figure out which post we're editing
+ $post_id = ((argc() > 1) ? intval(argv(1)) : 0);
+
+ if(! $post_id) {
+ notice( t('Item not found') . EOL);
+ return;
+ }
+
+ $itm = q("SELECT * FROM item WHERE id = %d and item_type = %d LIMIT 1",
+ intval($post_id),
+ intval(ITEM_TYPE_CARD)
+ );
+ if($itm) {
+ $item_id = q("select * from iconfig where cat = 'system' and k = 'CARD' and iid = %d limit 1",
+ intval($itm[0]['id'])
+ );
+ if($item_id)
+ $card_title = $item_id[0]['v'];
+ }
+ else {
+ notice( t('Item not found') . EOL);
+ return;
+ }
+
+ $owner = $itm[0]['uid'];
+ $uid = local_channel();
+
+ $observer = \App::get_observer();
+
+ $channel = channelx_by_n($owner);
+ if(! $channel) {
+ notice( t('Channel not found.') . EOL);
+ return;
+ }
+
+ $ob_hash = (($observer) ? $observer['xchan_hash'] : '');
+
+ if(! perm_is_allowed($owner,$ob_hash,'write_pages')) {
+ notice( t('Permission denied.') . EOL);
+ return;
+ }
+
+ $is_owner = (($uid && $uid == $owner) ? true : false);
+
+ $o = '';
+
+
+
+ $category = '';
+ $catsenabled = ((feature_enabled($owner,'categories')) ? 'categories' : '');
+
+ if ($catsenabled){
+ $itm = fetch_post_tags($itm);
+
+ $cats = get_terms_oftype($itm[0]['term'], TERM_CATEGORY);
+
+ foreach ($cats as $cat) {
+ if (strlen($category))
+ $category .= ', ';
+ $category .= $cat['term'];
+ }
+ }
+
+ if($itm[0]['attach']) {
+ $j = json_decode($itm[0]['attach'],true);
+ if($j) {
+ foreach($j as $jj) {
+ $itm[0]['body'] .= "\n" . '[attachment]' . basename($jj['href']) . ',' . $jj['revision'] . '[/attachment]' . "\n";
+ }
+ }
+ }
+
+
+ $mimetype = $itm[0]['mimetype'];
+
+ $content = $itm[0]['body'];
+
+
+
+ $rp = 'cards/' . $channel['channel_address'];
+
+ $x = array(
+ 'nickname' => $channel['channel_address'],
+ 'bbco_autocomplete'=> 'bbcode',
+ 'return_path' => $rp,
+ 'webpage' => ITEM_TYPE_CARD,
+ 'button' => t('Edit'),
+ 'writefiles' => perm_is_allowed($owner, get_observer_hash(), 'write_pages'),
+ 'weblink' => t('Insert web link'),
+ 'hide_voting' => false,
+ 'hide_future' => false,
+ 'hide_location' => false,
+ 'hide_expire' => false,
+ 'showacl' => true,
+ 'acl' => populate_acl($itm[0],false,\Zotlabs\Lib\PermissionDescription::fromGlobalPermission('view_pages')),
+ 'permissions' => $itm[0],
+ 'lockstate' => (($itm[0]['allow_cid'] || $itm[0]['allow_gid'] || $itm[0]['deny_cid'] || $itm[0]['deny_gid']) ? 'lock' : 'unlock'),
+ 'ptyp' => $itm[0]['type'],
+ 'mimeselect' => false,
+ 'mimetype' => $itm[0]['mimetype'],
+ 'body' => undo_post_tagging($content),
+ 'post_id' => $post_id,
+ 'visitor' => true,
+ 'title' => htmlspecialchars($itm[0]['title'],ENT_COMPAT,'UTF-8'),
+ 'placeholdertitle' => t('Title (optional)'),
+ 'pagetitle' => $card_title,
+ 'profile_uid' => (intval($channel['channel_id'])),
+ 'catsenabled' => $catsenabled,
+ 'category' => $category,
+ 'bbcode' => (($mimetype == 'text/bbcode') ? true : false)
+ );
+
+ $editor = status_editor($a, $x);
+
+ $o .= replace_macros(get_markup_template('edpost_head.tpl'), array(
+ '$title' => t('Edit Card'),
+ '$delete' => ((($itm[0]['author_xchan'] === $ob_hash) || ($itm[0]['owner_xchan'] === $ob_hash)) ? t('Delete') : false),
+ '$id' => $itm[0]['id'],
+ '$editor' => $editor
+ ));
+
+ return $o;
+
+ }
+
+}
diff --git a/Zotlabs/Module/Cards.php b/Zotlabs/Module/Cards.php
new file mode 100644
index 000000000..22c5d673c
--- /dev/null
+++ b/Zotlabs/Module/Cards.php
@@ -0,0 +1,187 @@
+<?php
+namespace Zotlabs\Module;
+
+require_once('include/channel.php');
+require_once('include/conversation.php');
+require_once('include/acl_selectors.php');
+
+
+class Cards extends \Zotlabs\Web\Controller {
+
+ function init() {
+
+ if(argc() > 1)
+ $which = argv(1);
+ else
+ return;
+
+ profile_load($which);
+
+ }
+
+ function get($update = 0, $load = false) {
+
+ if(observer_prohibited(true)) {
+ return login();
+ }
+
+ if(! \App::$profile) {
+ notice( t('Requested profile is not available.') . EOL );
+ \App::$error = 404;
+ return;
+ }
+
+ if(! feature_enabled(\App::$profile_uid,'cards')) {
+ return;
+ }
+
+ nav_set_selected(t('Cards'));
+
+ head_add_link([
+ 'rel' => 'alternate',
+ 'type' => 'application/json+oembed',
+ 'href' => z_root() . '/oep?f=&url=' . urlencode(z_root() . '/' . \App::$query_string),
+ 'title' => 'oembed'
+ ]);
+
+
+ $category = (($_REQUEST['cat']) ? escape_tags(trim($_REQUEST['cat'])) : '');
+
+ if($category) {
+ $sql_extra2 .= protect_sprintf(term_item_parent_query(\App::$profile['profile_uid'],'item', $category, TERM_CATEGORY));
+ }
+
+
+ $which = argv(1);
+
+ $selected_card = ((argc() > 2) ? argv(2) : '');
+
+ $_SESSION['return_url'] = \App::$query_string;
+
+ $uid = local_channel();
+ $owner = \App::$profile_uid;
+ $observer = \App::get_observer();
+
+ $ob_hash = (($observer) ? $observer['xchan_hash'] : '');
+
+ if(! perm_is_allowed($owner,$ob_hash,'view_pages')) {
+ notice( t('Permission denied.') . EOL);
+ return;
+ }
+
+ $is_owner = ($uid && $uid == $owner);
+
+ $channel = channelx_by_n($owner);
+
+ if($channel) {
+ $channel_acl = array(
+ 'allow_cid' => $channel['channel_allow_cid'],
+ 'allow_gid' => $channel['channel_allow_gid'],
+ 'deny_cid' => $channel['channel_deny_cid'],
+ 'deny_gid' => $channel['channel_deny_gid']
+ );
+ }
+ else {
+ $channel_acl = [ 'allow_cid' => '', 'allow_gid' => '', 'deny_cid' => '', 'deny_gid' => '' ];
+ }
+
+
+
+ if(perm_is_allowed($owner,$ob_hash,'write_pages')) {
+
+ $x = [
+ 'webpage' => ITEM_TYPE_CARD,
+ 'is_owner' => true,
+ 'content_label' => t('Add Card'),
+ 'button' => t('Create'),
+ 'nickname' => $channel['channel_address'],
+ 'lockstate' => (($channel['channel_allow_cid'] || $channel['channel_allow_gid']
+ || $channel['channel_deny_cid'] || $channel['channel_deny_gid']) ? 'lock' : 'unlock'),
+ 'acl' => (($is_owner) ? populate_acl($channel_acl, false,
+ \Zotlabs\Lib\PermissionDescription::fromGlobalPermission('view_pages')) : ''),
+ 'permissions' => $channel_acl,
+ 'showacl' => (($is_owner) ? true : false),
+ 'visitor' => true,
+ 'hide_location' => false,
+ 'hide_voting' => false,
+ 'profile_uid' => intval($owner),
+ 'mimetype' => 'text/bbcode',
+ 'mimeselect' => false,
+ 'layoutselect' => false,
+ 'expanded' => false,
+ 'novoting' => false,
+ 'catsenabled' => feature_enabled($owner,'categories'),
+ 'bbco_autocomplete' => 'bbcode',
+ 'bbcode' => true
+ ];
+
+ if($_REQUEST['title'])
+ $x['title'] = $_REQUEST['title'];
+ if($_REQUEST['body'])
+ $x['body'] = $_REQUEST['body'];
+ $editor = status_editor($a,$x);
+
+ }
+ else {
+ $editor = '';
+ }
+
+
+ $sql_extra = item_permissions_sql($owner);
+
+ if($selected_card) {
+ $r = q("select * from iconfig where iconfig.cat = 'system' and iconfig.k = 'CARD' and iconfig.v = '%s' limit 1",
+ dbesc($selected_card)
+ );
+ if($r) {
+ $sql_extra .= "and item.id = " . intval($r[0]['iid']) . " ";
+ }
+ }
+
+ $r = q("select * from item
+ where item.uid = %d and item_type = %d
+ $sql_extra order by item.created desc",
+ intval($owner),
+ intval(ITEM_TYPE_CARD)
+ );
+
+ $item_normal = " and item.item_hidden = 0 and item.item_type in (0,6) and item.item_deleted = 0
+ and item.item_unpublished = 0 and item.item_delayed = 0 and item.item_pending_remove = 0
+ and item.item_blocked = 0 ";
+
+ if($r) {
+
+ $parents_str = ids_to_querystr($r,'id');
+
+ $items = q("SELECT item.*, item.id AS item_id
+ FROM item
+ WHERE item.uid = %d $item_normal
+ AND item.parent IN ( %s )
+ $sql_extra $sql_extra2 ",
+ intval(\App::$profile['profile_uid']),
+ dbesc($parents_str)
+ );
+ if($items) {
+ xchan_query($items);
+ $items = fetch_post_tags($items, true);
+ $items = conv_sort($items,'updated');
+ }
+ else
+ $items = [];
+ }
+
+ $mode = 'cards';
+
+ $content = conversation($items,$mode,false,'traditional');
+
+ $o = replace_macros(get_markup_template('cards.tpl'), [
+ '$title' => t('Cards'),
+ '$editor' => $editor,
+ '$content' => $content,
+ '$pager' => alt_pager($a,count($items))
+ ]);
+
+ return $o;
+ }
+
+}
diff --git a/Zotlabs/Module/Cdav.php b/Zotlabs/Module/Cdav.php
new file mode 100644
index 000000000..77052f97c
--- /dev/null
+++ b/Zotlabs/Module/Cdav.php
@@ -0,0 +1,1259 @@
+<?php
+namespace Zotlabs\Module;
+
+require_once('include/event.php');
+
+require_once('include/auth.php');
+require_once('include/security.php');
+
+class Cdav extends \Zotlabs\Web\Controller {
+
+ function init() {
+
+ $record = null;
+ $channel_login = false;
+
+ if((argv(1) !== 'calendar') && (argv(1) !== 'addressbook')) {
+
+ foreach([ 'REDIRECT_REMOTE_USER', 'HTTP_AUTHORIZATION' ] as $head) {
+
+ /* Basic authentication */
+
+ if(array_key_exists($head,$_SERVER) && substr(trim($_SERVER[$head]),0,5) === 'Basic') {
+ $userpass = @base64_decode(substr(trim($_SERVER[$head]),6)) ;
+ if(strlen($userpass)) {
+ list($name, $password) = explode(':', $userpass);
+ $_SERVER['PHP_AUTH_USER'] = $name;
+ $_SERVER['PHP_AUTH_PW'] = $password;
+ }
+ break;
+ }
+
+ /* Signature authentication */
+
+ if(array_key_exists($head,$_SERVER) && substr(trim($_SERVER[$head]),0,9) === 'Signature') {
+ if($head !== 'HTTP_AUTHORIZATION') {
+ $_SERVER['HTTP_AUTHORIZATION'] = $_SERVER[$head];
+ continue;
+ }
+
+ $sigblock = \Zotlabs\Web\HTTPSig::parse_sigheader($_SERVER[$head]);
+ if($sigblock) {
+ $keyId = $sigblock['keyId'];
+ if($keyId) {
+ $r = q("select * from hubloc where hubloc_addr = '%s' limit 1",
+ dbesc($keyId)
+ );
+ if($r) {
+ $c = channelx_by_hash($r[0]['hubloc_hash']);
+ if($c) {
+ $a = q("select * from account where account_id = %d limit 1",
+ intval($c['channel_account_id'])
+ );
+ if($a) {
+ $record = [ 'channel' => $c, 'account' => $a[0] ];
+ $channel_login = $c['channel_id'];
+ }
+ }
+ }
+ if(! $record)
+ continue;
+
+ if($record) {
+ $verified = \Zotlabs\Web\HTTPSig::verify('',$record['channel']['channel_pubkey']);
+ if(! ($verified && $verified['header_signed'] && $verified['header_valid'])) {
+ $record = null;
+ }
+ if($record['account']) {
+ authenticate_success($record['account']);
+ if($channel_login) {
+ change_channel($channel_login);
+ }
+ }
+ break;
+ }
+ }
+ }
+ }
+ }
+
+
+ /**
+ * This server combines both CardDAV and CalDAV functionality into a single
+ * server. It is assumed that the server runs at the root of a HTTP domain (be
+ * that a domainname-based vhost or a specific TCP port.
+ *
+ * This example also assumes that you're using SQLite and the database has
+ * already been setup (along with the database tables).
+ *
+ * You may choose to use MySQL instead, just change the PDO connection
+ * statement.
+ */
+
+ /**
+ * UTC or GMT is easy to work with, and usually recommended for any
+ * application.
+ */
+ date_default_timezone_set('UTC');
+
+ /**
+ * Make sure this setting is turned on and reflect the root url for your WebDAV
+ * server.
+ *
+ * This can be for example the root / or a complete path to your server script.
+ */
+
+ $baseUri = '/cdav/';
+
+ /**
+ * Database
+ *
+ */
+
+ $pdo = \DBA::$dba->db;
+
+ // Autoloader
+ require_once 'vendor/autoload.php';
+
+ /**
+ * The backends. Yes we do really need all of them.
+ *
+ * This allows any developer to subclass just any of them and hook into their
+ * own backend systems.
+ */
+
+ $auth = new \Zotlabs\Storage\BasicAuth();
+ $auth->setRealm(ucfirst(\Zotlabs\Lib\System::get_platform_name()) . 'CalDAV/CardDAV');
+
+ if (local_channel()) {
+ logger('loggedin');
+ $channel = \App::get_channel();
+ $auth->setCurrentUser($channel['channel_address']);
+ $auth->channel_id = $channel['channel_id'];
+ $auth->channel_hash = $channel['channel_hash'];
+ $auth->channel_account_id = $channel['channel_account_id'];
+ if($channel['channel_timezone'])
+ $auth->setTimezone($channel['channel_timezone']);
+ $auth->observer = $channel['channel_hash'];
+
+ $principalUri = 'principals/' . $channel['channel_address'];
+ if(!cdav_principal($principalUri)) {
+ $this->activate($pdo, $channel);
+ if(!cdav_principal($principalUri)) {
+ return;
+ }
+ }
+
+ }
+
+
+ $principalBackend = new \Sabre\DAVACL\PrincipalBackend\PDO($pdo);
+ $carddavBackend = new \Sabre\CardDAV\Backend\PDO($pdo);
+ $caldavBackend = new \Sabre\CalDAV\Backend\PDO($pdo);
+
+ /**
+ * The directory tree
+ *
+ * Basically this is an array which contains the 'top-level' directories in the
+ * WebDAV server.
+ */
+
+ $nodes = [
+ // /principals
+ new \Sabre\CalDAV\Principal\Collection($principalBackend),
+ // /calendars
+ new \Sabre\CalDAV\CalendarRoot($principalBackend, $caldavBackend),
+ // /addressbook
+ new \Sabre\CardDAV\AddressBookRoot($principalBackend, $carddavBackend),
+ ];
+
+ // The object tree needs in turn to be passed to the server class
+
+ $server = new \Sabre\DAV\Server($nodes);
+
+ if(isset($baseUri))
+ $server->setBaseUri($baseUri);
+
+ // Plugins
+ $server->addPlugin(new \Sabre\DAV\Auth\Plugin($auth));
+ //$server->addPlugin(new \Sabre\DAV\Browser\Plugin());
+ $server->addPlugin(new \Sabre\DAV\Sync\Plugin());
+ $server->addPlugin(new \Sabre\DAV\Sharing\Plugin());
+ $server->addPlugin(new \Sabre\DAVACL\Plugin());
+
+ // CalDAV plugins
+ $server->addPlugin(new \Sabre\CalDAV\Plugin());
+ $server->addPlugin(new \Sabre\CalDAV\SharingPlugin());
+ //$server->addPlugin(new \Sabre\CalDAV\Schedule\Plugin());
+ $server->addPlugin(new \Sabre\CalDAV\ICSExportPlugin());
+
+ // CardDAV plugins
+ $server->addPlugin(new \Sabre\CardDAV\Plugin());
+ $server->addPlugin(new \Sabre\CardDAV\VCFExportPlugin());
+
+ // And off we go!
+ $server->exec();
+
+ killme();
+
+ }
+
+ }
+
+ function post() {
+ if(! local_channel())
+ return;
+
+ $channel = \App::get_channel();
+ $principalUri = 'principals/' . $channel['channel_address'];
+
+ if(!cdav_principal($principalUri))
+ return;
+
+ $pdo = \DBA::$dba->db;
+
+ require_once 'vendor/autoload.php';
+
+ if(argc() == 2 && argv(1) === 'calendar') {
+
+ $caldavBackend = new \Sabre\CalDAV\Backend\PDO($pdo);
+ $calendars = $caldavBackend->getCalendarsForUser($principalUri);
+
+ //create new calendar
+ if($_REQUEST['{DAV:}displayname'] && $_REQUEST['create']) {
+ do {
+ $duplicate = false;
+ $calendarUri = random_string(40);
+
+ $r = q("SELECT uri FROM calendarinstances WHERE principaluri = '%s' AND uri = '%s' LIMIT 1",
+ dbesc($principalUri),
+ dbesc($calendarUri)
+ );
+
+ if (count($r))
+ $duplicate = true;
+ } while ($duplicate == true);
+
+ $properties = [
+ '{DAV:}displayname' => $_REQUEST['{DAV:}displayname'],
+ '{http://apple.com/ns/ical/}calendar-color' => $_REQUEST['color'],
+ '{urn:ietf:params:xml:ns:caldav}calendar-description' => $channel['channel_name']
+ ];
+
+ $id = $caldavBackend->createCalendar($principalUri, $calendarUri, $properties);
+
+ // set new calendar to be visible
+ set_pconfig(local_channel(), 'cdav_calendar' , $id[0], 1);
+ }
+
+ //create new calendar object via ajax request
+ if($_REQUEST['submit'] === 'create_event' && $_REQUEST['title'] && $_REQUEST['target'] && $_REQUEST['dtstart']) {
+
+ $id = explode(':', $_REQUEST['target']);
+
+ if(!cdav_perms($id[0],$calendars,true))
+ return;
+
+ $title = $_REQUEST['title'];
+ $dtstart = new \DateTime($_REQUEST['dtstart']);
+ if($_REQUEST['dtend'])
+ $dtend = new \DateTime($_REQUEST['dtend']);
+ $description = $_REQUEST['description'];
+ $location = $_REQUEST['location'];
+
+ do {
+ $duplicate = false;
+ $objectUri = random_string(40) . '.ics';
+
+ $r = q("SELECT uri FROM calendarobjects WHERE calendarid = %s AND uri = '%s' LIMIT 1",
+ intval($id[0]),
+ dbesc($objectUri)
+ );
+
+ if (count($r))
+ $duplicate = true;
+ } while ($duplicate == true);
+
+
+ $vcalendar = new \Sabre\VObject\Component\VCalendar([
+ 'VEVENT' => [
+ 'SUMMARY' => $title,
+ 'DTSTART' => $dtstart
+ ]
+ ]);
+ if($dtend)
+ $vcalendar->VEVENT->add('DTEND', $dtend);
+ if($description)
+ $vcalendar->VEVENT->add('DESCRIPTION', $description);
+ if($location)
+ $vcalendar->VEVENT->add('LOCATION', $location);
+
+ $calendarData = $vcalendar->serialize();
+
+ $caldavBackend->createCalendarObject($id, $objectUri, $calendarData);
+
+ killme();
+ }
+
+ //edit calendar name and color
+ if($_REQUEST['{DAV:}displayname'] && $_REQUEST['edit'] && $_REQUEST['id']) {
+
+ $id = explode(':', $_REQUEST['id']);
+
+ if(! cdav_perms($id[0],$calendars))
+ return;
+
+ $mutations = [
+ '{DAV:}displayname' => $_REQUEST['{DAV:}displayname'],
+ '{http://apple.com/ns/ical/}calendar-color' => $_REQUEST['color']
+ ];
+
+ $patch = new \Sabre\DAV\PropPatch($mutations);
+
+ $caldavBackend->updateCalendar($id, $patch);
+
+ $patch->commit();
+
+ }
+
+ //edit calendar object via ajax request
+ if($_REQUEST['submit'] === 'update_event' && $_REQUEST['uri'] && $_REQUEST['title'] && $_REQUEST['target'] && $_REQUEST['dtstart']) {
+
+ $id = explode(':', $_REQUEST['target']);
+
+ if(!cdav_perms($id[0],$calendars,true))
+ return;
+
+ $uri = $_REQUEST['uri'];
+ $title = $_REQUEST['title'];
+ $dtstart = new \DateTime($_REQUEST['dtstart']);
+ $dtend = $_REQUEST['dtend'] ? new \DateTime($_REQUEST['dtend']) : '';
+ $description = $_REQUEST['description'];
+ $location = $_REQUEST['location'];
+
+ $object = $caldavBackend->getCalendarObject($id, $uri);
+
+ $vcalendar = \Sabre\VObject\Reader::read($object['calendardata']);
+
+ if($title)
+ $vcalendar->VEVENT->SUMMARY = $title;
+ if($dtstart)
+ $vcalendar->VEVENT->DTSTART = $dtstart;
+ if($dtend)
+ $vcalendar->VEVENT->DTEND = $dtend;
+ else
+ unset($vcalendar->VEVENT->DTEND);
+ if($description)
+ $vcalendar->VEVENT->DESCRIPTION = $description;
+ if($location)
+ $vcalendar->VEVENT->LOCATION = $location;
+
+ $calendarData = $vcalendar->serialize();
+
+ $caldavBackend->updateCalendarObject($id, $uri, $calendarData);
+
+ killme();
+ }
+
+ //delete calendar object via ajax request
+ if($_REQUEST['delete'] && $_REQUEST['uri'] && $_REQUEST['target']) {
+
+ $id = explode(':', $_REQUEST['target']);
+
+ if(!cdav_perms($id[0],$calendars,true))
+ return;
+
+ $uri = $_REQUEST['uri'];
+
+ $caldavBackend->deleteCalendarObject($id, $uri);
+
+ killme();
+ }
+
+ //edit calendar object date/timeme via ajax request (drag and drop)
+ if($_REQUEST['update'] && $_REQUEST['id'] && $_REQUEST['uri']) {
+
+ $id = [$_REQUEST['id'][0], $_REQUEST['id'][1]];
+
+ if(!cdav_perms($id[0],$calendars,true))
+ return;
+
+ $uri = $_REQUEST['uri'];
+ $dtstart = new \DateTime($_REQUEST['dtstart']);
+ $dtend = $_REQUEST['dtend'] ? new \DateTime($_REQUEST['dtend']) : '';
+
+ $object = $caldavBackend->getCalendarObject($id, $uri);
+
+ $vcalendar = \Sabre\VObject\Reader::read($object['calendardata']);
+
+ if($dtstart) {
+ $vcalendar->VEVENT->DTSTART = $dtstart;
+ }
+ if($dtend) {
+ $vcalendar->VEVENT->DTEND = $dtend;
+ }
+ else {
+ unset($vcalendar->VEVENT->DTEND);
+ }
+
+ $calendarData = $vcalendar->serialize();
+
+ $caldavBackend->updateCalendarObject($id, $uri, $calendarData);
+
+ killme();
+ }
+
+ //share a calendar - this only works on local system (with channels on the same server)
+ if($_REQUEST['sharee'] && $_REQUEST['share']) {
+
+ $id = [intval($_REQUEST['calendarid']), intval($_REQUEST['instanceid'])];
+
+ if(! cdav_perms($id[0],$calendars))
+ return;
+
+ $hash = $_REQUEST['sharee'];
+
+ $sharee_arr = channelx_by_hash($hash);
+
+ $sharee = new \Sabre\DAV\Xml\Element\Sharee();
+
+ $sharee->href = 'mailto:' . $sharee_arr['xchan_addr'];
+ $sharee->principal = 'principals/' . $sharee_arr['channel_address'];
+ $sharee->access = intval($_REQUEST['access']);
+ $sharee->properties = ['{DAV:}displayname' => $channel['channel_name']];
+
+ $caldavBackend->updateInvites($id, [$sharee]);
+ }
+ }
+
+ if(argc() >= 2 && argv(1) === 'addressbook') {
+
+ $carddavBackend = new \Sabre\CardDAV\Backend\PDO($pdo);
+ $addressbooks = $carddavBackend->getAddressBooksForUser($principalUri);
+
+ //create new addressbook
+ if($_REQUEST['{DAV:}displayname'] && $_REQUEST['create']) {
+ do {
+ $duplicate = false;
+ $addressbookUri = random_string(20);
+
+ $r = q("SELECT uri FROM addressbooks WHERE principaluri = '%s' AND uri = '%s' LIMIT 1",
+ dbesc($principalUri),
+ dbesc($addressbookUri)
+ );
+
+ if (count($r))
+ $duplicate = true;
+ } while ($duplicate == true);
+
+ $properties = ['{DAV:}displayname' => $_REQUEST['{DAV:}displayname']];
+
+ $carddavBackend->createAddressBook($principalUri, $addressbookUri, $properties);
+ }
+
+ //edit addressbook
+ if($_REQUEST['{DAV:}displayname'] && $_REQUEST['edit'] && intval($_REQUEST['id'])) {
+
+ $id = $_REQUEST['id'];
+
+ if(! cdav_perms($id,$addressbooks))
+ return;
+
+ $mutations = [
+ '{DAV:}displayname' => $_REQUEST['{DAV:}displayname']
+ ];
+
+ $patch = new \Sabre\DAV\PropPatch($mutations);
+
+ $carddavBackend->updateAddressBook($id, $patch);
+
+ $patch->commit();
+ }
+
+ //create addressbook card
+ if($_REQUEST['create'] && $_REQUEST['target'] && $_REQUEST['fn']) {
+ $id = $_REQUEST['target'];
+
+ do {
+ $duplicate = false;
+ $uri = random_string(40) . '.vcf';
+
+ $r = q("SELECT uri FROM cards WHERE addressbookid = %s AND uri = '%s' LIMIT 1",
+ intval($id),
+ dbesc($uri)
+ );
+
+ if (count($r))
+ $duplicate = true;
+ } while ($duplicate == true);
+
+ //TODO: this mostly duplictes the procedure in update addressbook card. should move this part to a function to avoid duplication
+ $fn = $_REQUEST['fn'];
+
+ $vcard = new \Sabre\VObject\Component\VCard([
+ 'FN' => $fn,
+ 'N' => array_reverse(explode(' ', $fn))
+ ]);
+
+ $org = $_REQUEST['org'];
+ if($org) {
+ $vcard->ORG = $org;
+ }
+
+ $title = $_REQUEST['title'];
+ if($title) {
+ $vcard->TITLE = $title;
+ }
+
+ $tel = $_REQUEST['tel'];
+ $tel_type = $_REQUEST['tel_type'];
+ if($tel) {
+ $i = 0;
+ foreach($tel as $item) {
+ if($item) {
+ $vcard->add('TEL', $item, ['type' => $tel_type[$i]]);
+ }
+ $i++;
+ }
+ }
+
+ $email = $_REQUEST['email'];
+ $email_type = $_REQUEST['email_type'];
+ if($email) {
+ $i = 0;
+ foreach($email as $item) {
+ if($item) {
+ $vcard->add('EMAIL', $item, ['type' => $email_type[$i]]);
+ }
+ $i++;
+ }
+ }
+
+ $impp = $_REQUEST['impp'];
+ $impp_type = $_REQUEST['impp_type'];
+ if($impp) {
+ $i = 0;
+ foreach($impp as $item) {
+ if($item) {
+ $vcard->add('IMPP', $item, ['type' => $impp_type[$i]]);
+ }
+ $i++;
+ }
+ }
+
+ $url = $_REQUEST['url'];
+ $url_type = $_REQUEST['url_type'];
+ if($url) {
+ $i = 0;
+ foreach($url as $item) {
+ if($item) {
+ $vcard->add('URL', $item, ['type' => $url_type[$i]]);
+ }
+ $i++;
+ }
+ }
+
+ $adr = $_REQUEST['adr'];
+ $adr_type = $_REQUEST['adr_type'];
+
+ if($adr) {
+ $i = 0;
+ foreach($adr as $item) {
+ if($item) {
+ $vcard->add('ADR', $item, ['type' => $adr_type[$i]]);
+ }
+ $i++;
+ }
+ }
+
+ $note = $_REQUEST['note'];
+ if($note) {
+ $vcard->NOTE = $note;
+ }
+
+ $cardData = $vcard->serialize();
+
+ $carddavBackend->createCard($id, $uri, $cardData);
+
+ }
+
+ //edit addressbook card
+ if($_REQUEST['update'] && $_REQUEST['uri'] && $_REQUEST['target']) {
+
+ $id = $_REQUEST['target'];
+
+ if(!cdav_perms($id,$addressbooks))
+ return;
+
+ $uri = $_REQUEST['uri'];
+
+ $object = $carddavBackend->getCard($id, $uri);
+ $vcard = \Sabre\VObject\Reader::read($object['carddata']);
+
+ $fn = $_REQUEST['fn'];
+ if($fn) {
+ $vcard->FN = $fn;
+ $vcard->N = array_reverse(explode(' ', $fn));
+ }
+
+ $org = $_REQUEST['org'];
+ if($org) {
+ $vcard->ORG = $org;
+ }
+ else {
+ unset($vcard->ORG);
+ }
+
+ $title = $_REQUEST['title'];
+ if($title) {
+ $vcard->TITLE = $title;
+ }
+ else {
+ unset($vcard->TITLE);
+ }
+
+ $tel = $_REQUEST['tel'];
+ $tel_type = $_REQUEST['tel_type'];
+ if($tel) {
+ $i = 0;
+ unset($vcard->TEL);
+ foreach($tel as $item) {
+ if($item) {
+ $vcard->add('TEL', $item, ['type' => $tel_type[$i]]);
+ }
+ $i++;
+ }
+ }
+ else {
+ unset($vcard->TEL);
+ }
+
+ $email = $_REQUEST['email'];
+ $email_type = $_REQUEST['email_type'];
+ if($email) {
+ $i = 0;
+ unset($vcard->EMAIL);
+ foreach($email as $item) {
+ if($item) {
+ $vcard->add('EMAIL', $item, ['type' => $email_type[$i]]);
+ }
+ $i++;
+ }
+ }
+ else {
+ unset($vcard->EMAIL);
+ }
+
+ $impp = $_REQUEST['impp'];
+ $impp_type = $_REQUEST['impp_type'];
+ if($impp) {
+ $i = 0;
+ unset($vcard->IMPP);
+ foreach($impp as $item) {
+ if($item) {
+ $vcard->add('IMPP', $item, ['type' => $impp_type[$i]]);
+ }
+ $i++;
+ }
+ }
+ else {
+ unset($vcard->IMPP);
+ }
+
+ $url = $_REQUEST['url'];
+ $url_type = $_REQUEST['url_type'];
+ if($url) {
+ $i = 0;
+ unset($vcard->URL);
+ foreach($url as $item) {
+ if($item) {
+ $vcard->add('URL', $item, ['type' => $url_type[$i]]);
+ }
+ $i++;
+ }
+ }
+ else {
+ unset($vcard->URL);
+ }
+
+ $adr = $_REQUEST['adr'];
+ $adr_type = $_REQUEST['adr_type'];
+ if($adr) {
+ $i = 0;
+ unset($vcard->ADR);
+ foreach($adr as $item) {
+ if($item) {
+ $vcard->add('ADR', $item, ['type' => $adr_type[$i]]);
+ }
+ $i++;
+ }
+ }
+ else {
+ unset($vcard->ADR);
+ }
+
+ $note = $_REQUEST['note'];
+ if($note) {
+ $vcard->NOTE = $note;
+ }
+ else {
+ unset($vcard->NOTE);
+ }
+
+ $cardData = $vcard->serialize();
+
+ $carddavBackend->updateCard($id, $uri, $cardData);
+ }
+
+ //delete addressbook card
+ if($_REQUEST['delete'] && $_REQUEST['uri'] && $_REQUEST['target']) {
+
+ $id = $_REQUEST['target'];
+
+ if(!cdav_perms($id,$addressbooks))
+ return;
+
+ $uri = $_REQUEST['uri'];
+
+ $carddavBackend->deleteCard($id, $uri);
+ }
+ }
+
+ //Import calendar or addressbook
+ if(($_FILES) && array_key_exists('userfile',$_FILES) && intval($_FILES['userfile']['size']) && $_REQUEST['target']) {
+
+ $src = @file_get_contents($_FILES['userfile']['tmp_name']);
+
+ if($src) {
+
+ if($_REQUEST['c_upload']) {
+ $id = explode(':', $_REQUEST['target']);
+ $ext = 'ics';
+ $table = 'calendarobjects';
+ $column = 'calendarid';
+ $objects = new \Sabre\VObject\Splitter\ICalendar($src);
+ $profile = \Sabre\VObject\Node::PROFILE_CALDAV;
+ $backend = new \Sabre\CalDAV\Backend\PDO($pdo);
+ }
+
+ if($_REQUEST['a_upload']) {
+ $id[] = intval($_REQUEST['target']);
+ $ext = 'vcf';
+ $table = 'cards';
+ $column = 'addressbookid';
+ $objects = new \Sabre\VObject\Splitter\VCard($src);
+ $profile = \Sabre\VObject\Node::PROFILE_CARDDAV;
+ $backend = new \Sabre\CardDAV\Backend\PDO($pdo);
+ }
+
+ while ($object = $objects->getNext()) {
+
+ if($_REQUEST['a_upload']) {
+ $object = $object->convert(\Sabre\VObject\Document::VCARD40);
+ }
+
+ $ret = $object->validate($profile & \Sabre\VObject\Node::REPAIR);
+
+ //level 3 Means that the document is invalid,
+ //level 2 means a warning. A warning means it's valid but it could cause interopability issues,
+ //level 1 means that there was a problem earlier, but the problem was automatically repaired.
+
+ if($ret[0]['level'] < 3) {
+ do {
+ $duplicate = false;
+ $objectUri = random_string(40) . '.' . $ext;
+
+ $r = q("SELECT uri FROM $table WHERE $column = %d AND uri = '%s' LIMIT 1",
+ dbesc($id[0]),
+ dbesc($objectUri)
+ );
+
+ if (count($r))
+ $duplicate = true;
+ } while ($duplicate == true);
+
+ if($_REQUEST['c_upload']) {
+ $backend->createCalendarObject($id, $objectUri, $object->serialize());
+ }
+
+ if($_REQUEST['a_upload']) {
+ $backend->createCard($id[0], $objectUri, $object->serialize());
+ }
+ }
+ else {
+ if($_REQUEST['c_upload']) {
+ notice( '<strong>' . t('INVALID EVENT DISMISSED!') . '</strong>' . EOL .
+ '<strong>' . t('Summary: ') . '</strong>' . (($object->VEVENT->SUMMARY) ? $object->VEVENT->SUMMARY : t('Unknown')) . EOL .
+ '<strong>' . t('Date: ') . '</strong>' . (($object->VEVENT->DTSTART) ? $object->VEVENT->DTSTART : t('Unknown')) . EOL .
+ '<strong>' . t('Reason: ') . '</strong>' . $ret[0]['message'] . EOL
+ );
+ }
+
+ if($_REQUEST['a_upload']) {
+ notice( '<strong>' . t('INVALID CARD DISMISSED!') . '</strong>' . EOL .
+ '<strong>' . t('Name: ') . '</strong>' . (($object->FN) ? $object->FN : t('Unknown')) . EOL .
+ '<strong>' . t('Reason: ') . '</strong>' . $ret[0]['message'] . EOL
+ );
+ }
+ }
+ }
+ }
+ @unlink($src);
+ }
+ }
+
+ function get() {
+
+ if(!local_channel())
+ return;
+
+ $channel = \App::get_channel();
+ $principalUri = 'principals/' . $channel['channel_address'];
+
+ $pdo = \DBA::$dba->db;
+
+ require_once 'vendor/autoload.php';
+
+ head_add_css('cdav.css');
+
+ if(!cdav_principal($principalUri)) {
+ $this->activate($pdo, $channel);
+ if(!cdav_principal($principalUri)) {
+ return;
+ }
+ }
+
+ if(argv(1) === 'calendar') {
+ nav_set_selected('CalDAV');
+ $caldavBackend = new \Sabre\CalDAV\Backend\PDO($pdo);
+ $calendars = $caldavBackend->getCalendarsForUser($principalUri);
+ }
+
+ //Display calendar(s) here
+ if(argc() == 2 && argv(1) === 'calendar') {
+
+ head_add_css('/library/fullcalendar/fullcalendar.css');
+ head_add_css('cdav_calendar.css');
+
+ head_add_js('/library/moment/moment.min.js', 1);
+ head_add_js('/library/fullcalendar/fullcalendar.min.js', 1);
+ head_add_js('/library/fullcalendar/locale-all.js', 1);
+
+ foreach($calendars as $calendar) {
+ $editable = (($calendar['share-access'] == 2) ? 'false' : 'true'); // false/true must be string since we're passing it to javascript
+ $color = (($calendar['{http://apple.com/ns/ical/}calendar-color']) ? $calendar['{http://apple.com/ns/ical/}calendar-color'] : '#3a87ad');
+ $sharer = (($calendar['share-access'] == 3) ? $calendar['{urn:ietf:params:xml:ns:caldav}calendar-description'] : '');
+ $switch = get_pconfig(local_channel(), 'cdav_calendar', $calendar['id'][0]);
+ if($switch) {
+ $sources .= '{
+ url: \'/cdav/calendar/json/' . $calendar['id'][0] . '/' . $calendar['id'][1] . '\',
+ color: \'' . $color . '\'
+ }, ';
+ }
+
+ if($calendar['share-access'] != 2) {
+ $writable_calendars[] = [
+ 'displayname' => $calendar['{DAV:}displayname'],
+ 'sharer' => $sharer,
+ 'id' => $calendar['id']
+ ];
+ }
+ }
+
+ $sources = rtrim($sources, ', ');
+
+ $first_day = get_pconfig(local_channel(),'system','cal_first_day');
+ $first_day = (($first_day) ? $first_day : 0);
+
+ $title = ['title', t('Event title')];
+ $dtstart = ['dtstart', t('Start date and time'), '', t('Example: YYYY-MM-DD HH:mm')];
+ $dtend = ['dtend', t('End date and time'), '', t('Example: YYYY-MM-DD HH:mm')];
+ $description = ['description', t('Description')];
+ $location = ['location', t('Location')];
+
+ $o .= replace_macros(get_markup_template('cdav_calendar.tpl'), [
+ '$sources' => $sources,
+ '$color' => $color,
+ '$lang' => \App::$language,
+ '$first_day' => $first_day,
+ '$prev' => t('Previous'),
+ '$next' => t('Next'),
+ '$today' => t('Today'),
+ '$month' => t('Month'),
+ '$week' => t('Week'),
+ '$day' => t('Day'),
+ '$list_month' => t('List month'),
+ '$list_week' => t('List week'),
+ '$list_day' => t('List day'),
+ '$title' => $title,
+ '$writable_calendars' => $writable_calendars,
+ '$dtstart' => $dtstart,
+ '$dtend' => $dtend,
+ '$description' => $description,
+ '$location' => $location,
+ '$more' => t('More'),
+ '$less' => t('Less'),
+ '$calendar_select_label' => t('Select calendar'),
+ '$delete' => t('Delete'),
+ '$delete_all' => t('Delete all'),
+ '$cancel' => t('Cancel'),
+ '$recurrence_warning' => t('Sorry! Editing of recurrent events is not yet implemented.')
+ ]);
+
+ return $o;
+
+ }
+
+ //Provide json data for calendar
+ if(argc() == 5 && argv(1) === 'calendar' && argv(2) === 'json' && intval(argv(3)) && intval(argv(4))) {
+
+ $id = [argv(3), argv(4)];
+
+ if(! cdav_perms($id[0],$calendars))
+ killme();
+
+ if (x($_GET,'start'))
+ $start = new \DateTime($_GET['start']);
+ if (x($_GET,'end'))
+ $end = new \DateTime($_GET['end']);
+
+ $filters['name'] = 'VCALENDAR';
+ $filters['prop-filters'][0]['name'] = 'VEVENT';
+ $filters['comp-filters'][0]['name'] = 'VEVENT';
+ $filters['comp-filters'][0]['time-range']['start'] = $start;
+ $filters['comp-filters'][0]['time-range']['end'] = $end;
+
+ $uris = $caldavBackend->calendarQuery($id, $filters);
+ if($uris) {
+
+ $objects = $caldavBackend->getMultipleCalendarObjects($id, $uris);
+
+ foreach($objects as $object) {
+
+ $vcalendar = \Sabre\VObject\Reader::read($object['calendardata']);
+
+ if(isset($vcalendar->VEVENT->RRULE))
+ $vcalendar = $vcalendar->expand($start, $end);
+
+ foreach($vcalendar->VEVENT as $vevent) {
+ $title = (string)$vevent->SUMMARY;
+ $dtstart = (string)$vevent->DTSTART;
+ $dtend = (string)$vevent->DTEND;
+ $description = (string)$vevent->DESCRIPTION;
+ $location = (string)$vevent->LOCATION;
+
+ $rw = ((cdav_perms($id[0],$calendars,true)) ? true : false);
+ $recurrent = ((isset($vevent->{'RECURRENCE-ID'})) ? true : false);
+
+ $editable = $rw ? true : false;
+
+ if($recurrent)
+ $editable = false;
+
+ $allDay = false;
+
+ // allDay event rules
+ if(!strpos($dtstart, 'T') && !strpos($dtend, 'T'))
+ $allDay = true;
+ if(strpos($dtstart, 'T000000') && strpos($dtend, 'T000000'))
+ $allDay = true;
+
+ $events[] = [
+ 'calendar_id' => $id,
+ 'uri' => $object['uri'],
+ 'title' => $title,
+ 'start' => $dtstart,
+ 'end' => $dtend,
+ 'description' => $description,
+ 'location' => $location,
+ 'allDay' => $allDay,
+ 'editable' => $editable,
+ 'recurrent' => $recurrent,
+ 'rw' => $rw
+ ];
+ }
+ }
+ json_return_and_die($events);
+ }
+ else {
+ killme();
+ }
+ }
+
+ //enable/disable calendars
+ if(argc() == 5 && argv(1) === 'calendar' && argv(2) === 'switch' && intval(argv(3)) && (argv(4) == 1 || argv(4) == 0)) {
+ $id = argv(3);
+
+ if(! cdav_perms($id,$calendars))
+ killme();
+
+ set_pconfig(local_channel(), 'cdav_calendar' , argv(3), argv(4));
+ killme();
+ }
+
+ //drop calendar
+ if(argc() == 5 && argv(1) === 'calendar' && argv(2) === 'drop' && intval(argv(3)) && intval(argv(4))) {
+ $id = [argv(3), argv(4)];
+
+ if(! cdav_perms($id[0],$calendars))
+ killme();
+
+ $caldavBackend->deleteCalendar($id);
+ killme();
+ }
+
+ //drop sharee
+ if(argc() == 6 && argv(1) === 'calendar' && argv(2) === 'dropsharee' && intval(argv(3)) && intval(argv(4))) {
+
+ $id = [argv(3), argv(4)];
+ $hash = argv(5);
+
+ if(! cdav_perms($id[0],$calendars))
+ killme();
+
+ $sharee_arr = channelx_by_hash($hash);
+
+ $sharee = new \Sabre\DAV\Xml\Element\Sharee();
+
+ $sharee->href = 'mailto:' . $sharee_arr['xchan_addr'];
+ $sharee->principal = 'principals/' . $sharee_arr['channel_address'];
+ $sharee->access = 4;
+ $caldavBackend->updateInvites($id, [$sharee]);
+
+ killme();
+ }
+
+
+ if(argv(1) === 'addressbook') {
+ nav_set_selected('CardDAV');
+ $carddavBackend = new \Sabre\CardDAV\Backend\PDO($pdo);
+ $addressbooks = $carddavBackend->getAddressBooksForUser($principalUri);
+ }
+
+ //Display Adressbook here
+ if(argc() == 3 && argv(1) === 'addressbook' && intval(argv(2))) {
+
+ $id = argv(2);
+
+ $displayname = cdav_perms($id,$addressbooks);
+
+ if(!$displayname)
+ return;
+
+ head_add_css('cdav_addressbook.css');
+
+ $o = '';
+
+ $sabrecards = $carddavBackend->getCards($id);
+ foreach($sabrecards as $sabrecard) {
+ $uris[] = $sabrecard['uri'];
+ }
+
+ if($uris) {
+ $objects = $carddavBackend->getMultipleCards($id, $uris);
+
+ foreach($objects as $object) {
+ $vcard = \Sabre\VObject\Reader::read($object['carddata']);
+
+ $photo = '';
+ if($vcard->PHOTO) {
+ $photo_value = strtolower($vcard->PHOTO->getValueType()); // binary or uri
+ if($photo_value === 'binary') {
+ $photo_type = strtolower($vcard->PHOTO['TYPE']); // mime jpeg, png or gif
+ $photo = 'data:image/' . $photo_type . ';base64,' . base64_encode((string)$vcard->PHOTO);
+ }
+ else {
+ $url = parse_url((string)$vcard->PHOTO);
+ $photo = 'data:' . $url['path'];
+ }
+ }
+
+ $fn = '';
+ if($vcard->FN) {
+ $fn = (string)$vcard->FN;
+ }
+
+ $org = '';
+ if($vcard->ORG) {
+ $org = (string)$vcard->ORG;
+ }
+
+ $title = '';
+ if($vcard->TITLE) {
+ $title = (string)$vcard->TITLE;
+ }
+
+ $tels = [];
+ if($vcard->TEL) {
+ foreach($vcard->TEL as $tel) {
+ $type = (($tel['TYPE']) ? translate_type((string)$tel['TYPE']) : '');
+ $tels[] = [
+ 'type' => $type,
+ 'nr' => (string)$tel
+ ];
+ }
+ }
+
+ $emails = [];
+ if($vcard->EMAIL) {
+ foreach($vcard->EMAIL as $email) {
+ $type = (($email['TYPE']) ? translate_type((string)$email['TYPE']) : '');
+ $emails[] = [
+ 'type' => $type,
+ 'address' => (string)$email
+ ];
+ }
+ }
+
+ $impps = [];
+ if($vcard->IMPP) {
+ foreach($vcard->IMPP as $impp) {
+ $type = (($impp['TYPE']) ? translate_type((string)$impp['TYPE']) : '');
+ $impps[] = [
+ 'type' => $type,
+ 'address' => (string)$impp
+ ];
+ }
+ }
+
+ $urls = [];
+ if($vcard->URL) {
+ foreach($vcard->URL as $url) {
+ $type = (($url['TYPE']) ? translate_type((string)$url['TYPE']) : '');
+ $urls[] = [
+ 'type' => $type,
+ 'address' => (string)$url
+ ];
+ }
+ }
+
+ $adrs = [];
+ if($vcard->ADR) {
+ foreach($vcard->ADR as $adr) {
+ $type = (($adr['TYPE']) ? translate_type((string)$adr['TYPE']) : '');
+ $adrs[] = [
+ 'type' => $type,
+ 'address' => $adr->getParts()
+ ];
+ }
+ }
+
+ $note = '';
+ if($vcard->NOTE) {
+ $note = (string)$vcard->NOTE;
+ }
+
+ $cards[] = [
+ 'id' => $object['id'],
+ 'uri' => $object['uri'],
+
+ 'photo' => $photo,
+ 'fn' => $fn,
+ 'org' => $org,
+ 'title' => $title,
+ 'tels' => $tels,
+ 'emails' => $emails,
+ 'impps' => $impps,
+ 'urls' => $urls,
+ 'adrs' => $adrs,
+ 'note' => $note
+ ];
+ }
+
+ usort($cards, function($a, $b) { return strcasecmp($a['fn'], $b['fn']); });
+ }
+
+ $o .= replace_macros(get_markup_template('cdav_addressbook.tpl'), [
+ '$id' => $id,
+ '$cards' => $cards,
+ '$displayname' => $displayname,
+ '$name_label' => t('Name'),
+ '$org_label' => t('Organisation'),
+ '$title_label' => t('Title'),
+ '$tel_label' => t('Phone'),
+ '$email_label' => t('Email'),
+ '$impp_label' => t('Instant messenger'),
+ '$url_label' => t('Website'),
+ '$adr_label' => t('Address'),
+ '$note_label' => t('Note'),
+ '$mobile' => t('Mobile'),
+ '$home' => t('Home'),
+ '$work' => t('Work'),
+ '$other' => t('Other'),
+ '$add_card' => t('Add Contact'),
+ '$add_field' => t('Add Field'),
+ '$create' => t('Create'),
+ '$update' => t('Update'),
+ '$delete' => t('Delete'),
+ '$cancel' => t('Cancel'),
+ '$po_box' => t('P.O. Box'),
+ '$extra' => t('Additional'),
+ '$street' => t('Street'),
+ '$locality' => t('Locality'),
+ '$region' => t('Region'),
+ '$zip_code' => t('ZIP Code'),
+ '$country' => t('Country')
+ ]);
+
+ return $o;
+ }
+
+ //delete addressbook
+ if(argc() > 3 && argv(1) === 'addressbook' && argv(2) === 'drop' && intval(argv(3))) {
+ $id = argv(3);
+
+ if(! cdav_perms($id,$addressbooks))
+ return;
+
+ $carddavBackend->deleteAddressBook($id);
+ killme();
+ }
+
+ }
+
+ function activate($pdo, $channel) {
+
+ if(! $channel)
+ return;
+
+ $uri = 'principals/' . $channel['channel_address'];
+
+
+ $r = q("select * from principals where uri = '%s' limit 1",
+ dbesc($uri)
+ );
+ if($r) {
+ $r = q("update principals set email = '%s', displayname = '%s' where uri = '%s' ",
+ dbesc($channel['xchan_addr']),
+ dbesc($channel['channel_name']),
+ dbesc($uri)
+ );
+ }
+ else {
+ $r = q("insert into principals ( uri, email, displayname ) values('%s','%s','%s') ",
+ dbesc($uri),
+ dbesc($channel['xchan_addr']),
+ dbesc($channel['channel_name'])
+ );
+
+ //create default calendar
+ $caldavBackend = new \Sabre\CalDAV\Backend\PDO($pdo);
+ $properties = [
+ '{DAV:}displayname' => t('Default Calendar'),
+ '{http://apple.com/ns/ical/}calendar-color' => '#3a87ad',
+ '{urn:ietf:params:xml:ns:caldav}calendar-description' => $channel['channel_name']
+ ];
+
+ $id = $caldavBackend->createCalendar($uri, 'default', $properties);
+ set_pconfig(local_channel(), 'cdav_calendar' , $id[0], 1);
+
+ //create default addressbook
+ $carddavBackend = new \Sabre\CardDAV\Backend\PDO($pdo);
+ $properties = ['{DAV:}displayname' => t('Default Addressbook')];
+ $carddavBackend->createAddressBook($uri, $default, $properties);
+
+ }
+ }
+
+
+}
diff --git a/Zotlabs/Module/Changeaddr.php b/Zotlabs/Module/Changeaddr.php
new file mode 100644
index 000000000..5cd236394
--- /dev/null
+++ b/Zotlabs/Module/Changeaddr.php
@@ -0,0 +1,88 @@
+<?php
+namespace Zotlabs\Module;
+
+
+class Changeaddr extends \Zotlabs\Web\Controller {
+
+ function post() {
+
+ if(! local_channel())
+ return;
+
+ if($_SESSION['delegate'])
+ return;
+
+ if((! x($_POST,'qxz_password')) || (! strlen(trim($_POST['qxz_password']))))
+ return;
+
+ if((! x($_POST,'verify')) || (! strlen(trim($_POST['verify']))))
+ return;
+
+ if($_POST['verify'] !== $_SESSION['remove_account_verify'])
+ return;
+
+
+ $account = \App::get_account();
+ $channel = \App::get_channel();
+
+ $x = account_verify_password($account['account_email'],$_POST['qxz_password']);
+ if(! ($x && $x['account']))
+ return;
+
+ if($account['account_password_changed'] > NULL_DATE) {
+ $d1 = datetime_convert('UTC','UTC','now - 48 hours');
+ if($account['account_password_changed'] > d1) {
+ notice( t('Channel name changes are not allowed within 48 hours of changing the account password.') . EOL);
+ return;
+ }
+ }
+
+ $new_address = trim($_POST['newname']);
+
+ if($new_address === $channel['channel_address'])
+ return;
+
+ if($new_address === 'sys') {
+ notice( t('Reserved nickname. Please choose another.') . EOL);
+ return;
+ }
+
+ if(check_webbie(array($new_address)) !== $new_address) {
+ notice( t('Nickname has unsupported characters or is already being used on this site.') . EOL);
+ return $ret;
+ }
+
+ channel_change_address($channel,$new_address);
+
+ goaway(z_root() . '/changeaddr');
+
+ }
+
+
+ function get() {
+
+ if(! local_channel())
+ goaway(z_root());
+
+ $channel = \App::get_channel();
+
+ $hash = random_string();
+
+ $_SESSION['remove_account_verify'] = $hash;
+
+ $tpl = get_markup_template('channel_rename.tpl');
+ $o .= replace_macros($tpl, array(
+ '$basedir' => z_root(),
+ '$hash' => $hash,
+ '$title' => t('Change channel nickname/address'),
+ '$desc' => array(t('WARNING: '), t('Any/all connections on other networks will be lost!')),
+ '$passwd' => t('Please enter your password for verification:'),
+ '$newname' => array('newname', t('New channel address'),$channel['channel_address'], ''),
+ '$submit' => t('Rename Channel')
+ ));
+
+ return $o;
+
+ }
+
+}
diff --git a/Zotlabs/Module/Channel.php b/Zotlabs/Module/Channel.php
index 45da92184..14d02d873 100644
--- a/Zotlabs/Module/Channel.php
+++ b/Zotlabs/Module/Channel.php
@@ -41,12 +41,20 @@ class Channel extends \Zotlabs\Web\Controller {
$profile = argv(1);
}
- \App::$page['htmlhead'] .= '<link rel="alternate" type="application/atom+xml" title="' . t('Posts and comments') . '" href="' . z_root() . '/feed/' . $which . '" />' . "\r\n" ;
- \App::$page['htmlhead'] .= '<link rel="alternate" type="application/atom+xml" title="' . t('Only posts') . '" href="' . z_root() . '/feed/' . $which . '?top=1" />' . "\r\n" ;
+ head_add_link( [
+ 'rel' => 'alternate',
+ 'type' => 'application/atom+xml',
+ 'title' => t('Posts and comments'),
+ 'href' => z_root() . '/feed/' . $which
+ ]);
+
+ head_add_link( [
+ 'rel' => 'alternate',
+ 'type' => 'application/atom+xml',
+ 'title' => t('Only posts'),
+ 'href' => z_root() . '/feed/' . $which . '?f=&top=1'
+ ]);
- // Not yet ready for prime time
- // \App::$page['htmlhead'] .= '<link rel="openid.server" href="' . z_root() . '/id/' . $which .'?f=" />' . "\r\n" ;
- // \App::$page['htmlhead'] .= '<link rel="openid.delegate" href="' . z_root() . '/channel/' . $which .'" />' . "\r\n" ;
// Run profile_load() here to make sure the theme is set before
// we start loading content
@@ -84,11 +92,6 @@ class Channel extends \Zotlabs\Web\Controller {
// Ensure we've got a profile owner if updating.
\App::$profile['profile_uid'] = \App::$profile_uid = $update;
}
- else {
- if(\App::$profile['profile_uid'] == local_channel()) {
- nav_set_selected('home');
- }
- }
$is_owner = (((local_channel()) && (\App::$profile['profile_uid'] == local_channel())) ? true : false);
@@ -111,11 +114,13 @@ class Channel extends \Zotlabs\Web\Controller {
if(! $update) {
+ nav_set_selected('Channel Home');
+
$static = channel_manual_conv_update(\App::$profile['profile_uid']);
- $o .= profile_tabs($a, $is_owner, \App::$profile['channel_address']);
+ //$o .= profile_tabs($a, $is_owner, \App::$profile['channel_address']);
- $o .= common_friends_visitor_widget(\App::$profile['profile_uid']);
+ // $o .= common_friends_visitor_widget(\App::$profile['profile_uid']);
if($channel && $is_owner) {
$channel_acl = array(
@@ -161,6 +166,7 @@ class Channel extends \Zotlabs\Web\Controller {
*/
$item_normal = item_normal();
+ $item_normal_update = item_normal_update();
$sql_extra = item_permissions_sql(\App::$profile['profile_uid']);
if(get_pconfig(\App::$profile['profile_uid'],'system','channel_list_mode') && (! $mid))
@@ -172,7 +178,12 @@ class Channel extends \Zotlabs\Web\Controller {
$simple_update = (($update) ? " AND item_unseen = 1 " : '');
- \App::$page['htmlhead'] .= "\r\n" . '<link rel="alternate" type="application/json+oembed" href="' . z_root() . '/oep?f=&url=' . urlencode(z_root() . '/' . \App::$query_string) . '" title="oembed" />' . "\r\n";
+ head_add_link([
+ 'rel' => 'alternate',
+ 'type' => 'application/json+oembed',
+ 'href' => z_root() . '/oep?f=&url=' . urlencode(z_root() . '/' . \App::$query_string),
+ 'title' => 'oembed'
+ ]);
if($update && $_SESSION['loadtime'])
$simple_update = " AND (( item_unseen = 1 AND item.changed > '" . datetime_convert('UTC','UTC',$_SESSION['loadtime']) . "' ) OR item.changed > '" . datetime_convert('UTC','UTC',$_SESSION['loadtime']) . "' ) ";
@@ -180,12 +191,12 @@ class Channel extends \Zotlabs\Web\Controller {
$simple_update = '';
if($static && $simple_update)
- $simple_update .= " and item_thread_top = 0 and author_xchan = '" . protect_sprintf(get_observer_hash()) . "' ";
+ $simple_update .= " and author_xchan = '" . protect_sprintf(get_observer_hash()) . "' ";
if(($update) && (! $load)) {
if($mid) {
- $r = q("SELECT parent AS item_id from item where mid like '%s' and uid = %d $item_normal
+ $r = q("SELECT parent AS item_id from item where mid like '%s' and uid = %d $item_normal_update
AND item_wall = 1 $simple_update $sql_extra limit 1",
dbesc($mid . '%'),
intval(\App::$profile['profile_uid'])
@@ -195,7 +206,7 @@ class Channel extends \Zotlabs\Web\Controller {
else {
$r = q("SELECT distinct parent AS item_id, created from item
left join abook on ( item.owner_xchan = abook.abook_xchan $abook_uids )
- WHERE uid = %d $item_normal
+ WHERE uid = %d $item_normal_update
AND item_wall = 1 $simple_update
AND (abook.abook_blocked = 0 or abook.abook_flags is null)
$sql_extra
@@ -209,10 +220,10 @@ class Channel extends \Zotlabs\Web\Controller {
else {
if(x($category)) {
- $sql_extra .= protect_sprintf(term_query('item', $category, TERM_CATEGORY));
+ $sql_extra2 .= protect_sprintf(term_item_parent_query(\App::$profile['profile_uid'],'item', $category, TERM_CATEGORY));
}
if(x($hashtags)) {
- $sql_extra .= protect_sprintf(term_query('item', $hashtags, TERM_HASHTAG, TERM_COMMUNITYTAG));
+ $sql_extra2 .= protect_sprintf(term_item_parent_query(\App::$profile['profile_uid'],'item', $hashtags, TERM_HASHTAG, TERM_COMMUNITYTAG));
}
if($datequery) {
@@ -228,9 +239,9 @@ class Channel extends \Zotlabs\Web\Controller {
if($load || ($checkjs->disabled())) {
if($mid) {
- $r = q("SELECT parent AS item_id from item where mid = '%s' and uid = %d $item_normal
+ $r = q("SELECT distinct parent AS item_id from item where mid like '%s' and uid = %d $item_normal
AND item_wall = 1 $sql_extra limit 1",
- dbesc($mid),
+ dbesc($mid . '%'),
intval(\App::$profile['profile_uid'])
);
if (! $r) {
@@ -313,11 +324,12 @@ class Channel extends \Zotlabs\Web\Controller {
'$static' => $static,
'$page' => ((\App::$pager['page'] != 1) ? \App::$pager['page'] : 1),
'$search' => '',
+ '$xchan' => '',
'$order' => '',
'$list' => ((x($_REQUEST,'list')) ? intval($_REQUEST['list']) : 0),
'$file' => '',
- '$cats' => (($category) ? $category : ''),
- '$tags' => (($hashtags) ? $hashtags : ''),
+ '$cats' => (($category) ? urlencode($category) : ''),
+ '$tags' => (($hashtags) ? urlencode($hashtags) : ''),
'$mid' => $mid,
'$verb' => '',
'$dend' => $datequery,
@@ -349,17 +361,21 @@ class Channel extends \Zotlabs\Web\Controller {
}
if($is_owner && $update_unseen) {
- $r = q("UPDATE item SET item_unseen = 0 where item_unseen = 1 and item_wall = 1 AND uid = %d $update_unseen",
- intval(local_channel())
- );
+ $x = [ 'channel_id' => local_channel(), 'update' => 'unset' ];
+ call_hooks('update_unseen',$x);
+ if($x['update'] === 'unset' || intval($x['update'])) {
+ $r = q("UPDATE item SET item_unseen = 0 where item_unseen = 1 and item_wall = 1 AND uid = %d $update_unseen",
+ intval(local_channel())
+ );
+ }
}
if($checkjs->disabled()) {
- $o .= conversation($a,$items,'channel',$update,'traditional');
+ $o .= conversation($items,'channel',$update,'traditional');
}
else {
- $o .= conversation($a,$items,'channel',$update,$page_mode);
+ $o .= conversation($items,'channel',$update,$page_mode);
}
if((! $update) || ($checkjs->disabled())) {
diff --git a/Zotlabs/Module/Chanview.php b/Zotlabs/Module/Chanview.php
index 01ee74d5a..24ab9b022 100644
--- a/Zotlabs/Module/Chanview.php
+++ b/Zotlabs/Module/Chanview.php
@@ -102,27 +102,32 @@ class Chanview extends \Zotlabs\Web\Controller {
}
$is_zot = false;
+ $connected = false;
if (\App::$poi) {
$url = \App::$poi['xchan_url'];
if(\App::$poi['xchan_network'] === 'zot') {
$is_zot = true;
}
+ if(local_channel()) {
+ $c = q("select abook_id from abook where abook_channel = %d and abook_xchan = '%s' limit 1",
+ intval(local_channel()),
+ dbesc(\App::$poi['xchan_hash'])
+ );
+ if($c)
+ $connected = true;
+ }
}
-
+
// We will load the chanview template if it's a foreign network,
// just so that we can provide a connect button along with a profile
// photo. Chances are we can't load the remote profile into an iframe
// because of cross-domain security headers. So provide a link to
// the remote profile.
-
+ // If we are already connected, just go to the profile.
// Zot channels will usually have a connect link.
- // If it isn't zot, 'pro' members won't be able to use the connect
- // button as it is a foreign network so just send them to the remote
- // profile.
-
- if($is_zot || \Zotlabs\Lib\System::get_server_role() === 'pro') {
+ if($is_zot || $connected) {
if($is_zot && $observer) {
$url = zid($url);
}
diff --git a/Zotlabs/Module/Chat.php b/Zotlabs/Module/Chat.php
index 2c0e7a155..378c9f4dd 100644
--- a/Zotlabs/Module/Chat.php
+++ b/Zotlabs/Module/Chat.php
@@ -33,9 +33,7 @@ class Chat extends \Zotlabs\Web\Controller {
$which = $channel['channel_address'];
$profile = argv(1);
}
-
- \App::$page['htmlhead'] .= '<link rel="alternate" type="application/atom+xml" href="' . z_root() . '/feed/' . $which .'" />' . "\r\n" ;
-
+
// Run profile_load() here to make sure the theme is set before
// we start loading content
@@ -91,9 +89,11 @@ class Chat extends \Zotlabs\Web\Controller {
function get() {
- if(local_channel())
+ if(local_channel()) {
$channel = \App::get_channel();
-
+ nav_set_selected('My Chatrooms');
+ }
+
$ob = \App::get_observer();
$observer = get_observer_hash();
if(! $observer) {
@@ -212,7 +212,8 @@ class Chat extends \Zotlabs\Web\Controller {
require_once('include/conversation.php');
- $o = profile_tabs($a,((local_channel() && local_channel() == \App::$profile['profile_uid']) ? true : false),\App::$profile['channel_address']);
+ //$o = profile_tabs($a,((local_channel() && local_channel() == \App::$profile['profile_uid']) ? true : false),\App::$profile['channel_address']);
+ $o = '';
if(! feature_enabled(\App::$profile['profile_uid'],'ajaxchat')) {
notice( t('Feature disabled.') . EOL);
diff --git a/Zotlabs/Module/Cloud.php b/Zotlabs/Module/Cloud.php
index 1fda8e32b..75191a279 100644
--- a/Zotlabs/Module/Cloud.php
+++ b/Zotlabs/Module/Cloud.php
@@ -37,8 +37,6 @@ class Cloud extends \Zotlabs\Web\Controller {
$profile = 0;
- \App::$page['htmlhead'] .= '<link rel="alternate" type="application/atom+xml" href="' . z_root() . '/feed/' . $which . '" />' . "\r\n";
-
if ($which)
profile_load( $which, $profile);
@@ -59,16 +57,12 @@ class Cloud extends \Zotlabs\Web\Controller {
$auth->observer = $ob_hash;
}
- if ($_GET['davguest'])
- $_SESSION['davguest'] = true;
$_SERVER['QUERY_STRING'] = str_replace(array('?f=', '&f='), array('', ''), $_SERVER['QUERY_STRING']);
$_SERVER['QUERY_STRING'] = strip_zids($_SERVER['QUERY_STRING']);
- $_SERVER['QUERY_STRING'] = preg_replace('/[\?&]davguest=(.*?)([\?&]|$)/ism', '', $_SERVER['QUERY_STRING']);
$_SERVER['REQUEST_URI'] = str_replace(array('?f=', '&f='), array('', ''), $_SERVER['REQUEST_URI']);
$_SERVER['REQUEST_URI'] = strip_zids($_SERVER['REQUEST_URI']);
- $_SERVER['REQUEST_URI'] = preg_replace('/[\?&]davguest=(.*?)([\?&]|$)/ism', '', $_SERVER['REQUEST_URI']);
$rootDirectory = new \Zotlabs\Storage\Directory('/', $auth);
@@ -92,12 +86,13 @@ class Cloud extends \Zotlabs\Web\Controller {
// require_once('\Zotlabs\Storage/QuotaPlugin.php');
// $server->addPlugin(new \Zotlabs\Storage\\QuotaPlugin($auth));
- ob_start();
+// ob_start();
// All we need to do now, is to fire up the server
$server->exec();
- ob_end_flush();
-
+// ob_end_flush();
+ if($browser->build_page)
+ construct_page();
killme();
}
diff --git a/Zotlabs/Module/Common.php b/Zotlabs/Module/Common.php
index 2f3c57267..eebc56d2b 100644
--- a/Zotlabs/Module/Common.php
+++ b/Zotlabs/Module/Common.php
@@ -25,7 +25,7 @@ class Common extends \Zotlabs\Web\Controller {
}
- function get() {
+ function get() {
$o = '';
@@ -34,38 +34,37 @@ class Common extends \Zotlabs\Web\Controller {
$observer_hash = get_observer_hash();
-
if(! perm_is_allowed(\App::$profile['profile_uid'],$observer_hash,'view_contacts')) {
notice( t('Permission denied.') . EOL);
return;
}
- $o .= '<h2>' . t('Common connections') . '</h2>';
-
$t = count_common_friends(\App::$profile['profile_uid'],$observer_hash);
if(! $t) {
notice( t('No connections in common.') . EOL);
- return $o;
+ return;
}
$r = common_friends(\App::$profile['profile_uid'],$observer_hash);
if($r) {
-
- $tpl = get_markup_template('common_friends.tpl');
-
foreach($r as $rr) {
- $o .= replace_macros($tpl,array(
- '$url' => $rr['xchan_url'],
- '$name' => $rr['xchan_name'],
- '$photo' => $rr['xchan_photo_m'],
- '$tags' => ''
- ));
+ $items[] = [
+ 'url' => $rr['xchan_url'],
+ 'name' => $rr['xchan_name'],
+ 'photo' => $rr['xchan_photo_m'],
+ 'tags' => ''
+ ];
}
-
- $o .= cleardiv();
}
+
+ $tpl = get_markup_template('common_friends.tpl');
+
+ $o = replace_macros($tpl, [
+ '$title' => t('View Common Connections'),
+ '$items' => $items
+ ]);
return $o;
}
diff --git a/Zotlabs/Module/Connections.php b/Zotlabs/Module/Connections.php
index 950be660d..f42ff9b84 100644
--- a/Zotlabs/Module/Connections.php
+++ b/Zotlabs/Module/Connections.php
@@ -5,10 +5,6 @@ namespace Zotlabs\Module;
require_once('include/socgraph.php');
require_once('include/selectors.php');
require_once('include/group.php');
-require_once('include/contact_widgets.php');
-require_once('include/zot.php');
-require_once('include/widgets.php');
-
class Connections extends \Zotlabs\Web\Controller {
@@ -23,7 +19,7 @@ class Connections extends \Zotlabs\Web\Controller {
}
- function get() {
+ function get() {
$sort_type = 0;
$o = '';
@@ -33,6 +29,8 @@ class Connections extends \Zotlabs\Web\Controller {
notice( t('Permission denied.') . EOL);
return login();
}
+
+ nav_set_selected('Connections');
$blocked = false;
$hidden = false;
@@ -67,15 +65,14 @@ class Connections extends \Zotlabs\Web\Controller {
$hidden = true;
break;
case 'archived':
- $search_flags = " and abook_archived = 1 ";
- $head = t('Archived');
+ $search_flags = " and ( abook_archived = 1 OR abook_not_here = 1) ";
+ $head = t('Archived/Unreachable');
$archived = true;
break;
case 'pending':
$search_flags = " and abook_pending = 1 ";
$head = t('New');
$pending = true;
- nav_set_selected('intros');
break;
case 'ifpending':
$r = q("SELECT COUNT(abook.abook_id) AS total FROM abook left join xchan on abook.abook_xchan = xchan.xchan_hash where abook_channel = %d and abook_pending = 1 and abook_self = 0 and abook_ignored = 0 and xchan_deleted = 0 and xchan_orphan = 0 ",
@@ -85,7 +82,6 @@ class Connections extends \Zotlabs\Web\Controller {
$search_flags = " and abook_pending = 1 ";
$head = t('New');
$pending = true;
- nav_set_selected('intros');
\App::$argv[1] = 'pending';
}
else {
@@ -95,7 +91,6 @@ class Connections extends \Zotlabs\Web\Controller {
\App::$argc = 1;
unset(\App::$argv[1]);
}
- nav_set_selected('intros');
break;
// case 'unconnected':
// $search_flags = " and abook_unconnected = 1 ";
@@ -172,10 +167,10 @@ class Connections extends \Zotlabs\Web\Controller {
),
'archived' => array(
- 'label' => t('Archived'),
+ 'label' => t('Archived/Unreachable'),
'url' => z_root() . '/connections/archived',
'sel' => ($archived) ? 'active' : '',
- 'title' => t('Only show archived connections'),
+ 'title' => t('Only show archived/unreachable connections'),
),
'hidden' => array(
@@ -247,7 +242,8 @@ class Connections extends \Zotlabs\Web\Controller {
((intval($rr['abook_archived'])) ? t('Archived') : ''),
((intval($rr['abook_hidden'])) ? t('Hidden') : ''),
((intval($rr['abook_ignored'])) ? t('Ignored') : ''),
- ((intval($rr['abook_blocked'])) ? t('Blocked') : '')
+ ((intval($rr['abook_blocked'])) ? t('Blocked') : ''),
+ ((intval($rr['abook_not_here'])) ? t('Not connected at this location') : '')
);
foreach($status as $str) {
@@ -261,15 +257,16 @@ class Connections extends \Zotlabs\Web\Controller {
$contacts[] = array(
'img_hover' => sprintf( t('%1$s [%2$s]'),$rr['xchan_name'],$rr['xchan_url']),
'edit_hover' => t('Edit connection'),
+ 'edit' => t('Edit'),
'delete_hover' => t('Delete connection'),
'id' => $rr['abook_id'],
'thumb' => $rr['xchan_photo_m'],
'name' => $rr['xchan_name'],
- 'classes' => (intval($rr['abook_archived']) ? 'archived' : ''),
+ 'classes' => ((intval($rr['abook_archived']) || intval($rr['abook_not_here'])) ? 'archived' : ''),
'link' => z_root() . '/connedit/' . $rr['abook_id'],
'deletelink' => z_root() . '/connedit/' . intval($rr['abook_id']) . '/drop',
'delete' => t('Delete'),
- 'url' => chanlink_url($rr['xchan_url']),
+ 'url' => chanlink_hash($rr['xchan_hash']),
'webbie_label' => t('Channel address'),
'webbie' => $rr['xchan_addr'],
'network_label' => t('Network'),
diff --git a/Zotlabs/Module/Connedit.php b/Zotlabs/Module/Connedit.php
index 7a753c286..23c5282e3 100644
--- a/Zotlabs/Module/Connedit.php
+++ b/Zotlabs/Module/Connedit.php
@@ -11,9 +11,6 @@ namespace Zotlabs\Module;
require_once('include/socgraph.php');
require_once('include/selectors.php');
require_once('include/group.php');
-require_once('include/contact_widgets.php');
-require_once('include/zot.php');
-require_once('include/widgets.php');
require_once('include/photos.php');
@@ -251,6 +248,10 @@ class Connedit extends \Zotlabs\Web\Controller {
notice( t('Failed to update connection record.') . EOL);
if(! intval(\App::$poi['abook_self'])) {
+ if($new_friend) {
+ \Zotlabs\Daemon\Master::Summon( [ 'Notifier', 'permission_accept', $contact_id ] );
+ }
+
\Zotlabs\Daemon\Master::Summon( [
'Notifier',
(($new_friend) ? 'permission_create' : 'permission_update'),
@@ -391,30 +392,22 @@ class Connedit extends \Zotlabs\Web\Controller {
$section = ((array_key_exists('section',$_REQUEST)) ? $_REQUEST['section'] : '');
$channel = \App::get_channel();
- $my_perms = get_channel_default_perms(local_channel());
- $role = get_pconfig(local_channel(),'system','permissions_role');
- if($role) {
- $x = \Zotlabs\Access\PermissionRoles::role_perms($role);
- if($x['perms_connect'])
- $my_perms = $x['perms_connect'];
- }
$yes_no = array(t('No'),t('Yes'));
- if($my_perms) {
- $o .= "<script>function connectDefaultShare() {
- \$('.abook-edit-me').each(function() {
- if(! $(this).is(':disabled'))
- $(this).prop('checked', false);
- });\n\n";
- $perms = get_perms();
- foreach($perms as $p => $v) {
- if($my_perms & $v[1]) {
- $o .= "\$('#me_id_perms_" . $p . "').prop('checked', true); \n";
- }
+ $connect_perms = \Zotlabs\Access\Permissions::connect_perms(local_channel());
+
+ $o .= "<script>function connectDefaultShare() {
+ \$('.abook-edit-me').each(function() {
+ if(! $(this).is(':disabled'))
+ $(this).prop('checked', false);
+ });\n\n";
+ foreach($connect_perms['perms'] as $p => $v) {
+ if($v) {
+ $o .= "\$('#me_id_perms_" . $p . "').prop('checked', true); \n";
}
- $o .= " }\n</script>\n";
}
+ $o .= " }\n</script>\n";
if(argc() == 3) {
@@ -441,6 +434,34 @@ class Connedit extends \Zotlabs\Web\Controller {
goaway(z_root() . '/connedit/' . $contact_id);
}
+
+ if($cmd === 'fetchvc') {
+ $url = str_replace('/channel/','/profile/',$orig_record[0]['xchan_url']) . '/vcard';
+ $recurse = 0;
+ $x = z_fetch_url(zid($url),false,$recurse,['session' => true]);
+ if($x['success']) {
+ $h = new \Zotlabs\Web\HTTPHeaders($x['header']);
+ $fields = $h->fetch();
+ if($fields) {
+ foreach($fields as $y) {
+ if(array_key_exists('content-type',$y)) {
+ $type = explode(';',trim($y['content-type']));
+ if($type && $type[0] === 'text/vcard' && $x['body']) {
+ $vc = \Sabre\VObject\Reader::read($x['body']);
+ $vcard = $vc->serialize();
+ if($vcard) {
+ set_abconfig(local_channel(),$orig_record[0]['abook_xchan'],'system','vcard',$vcard);
+ $this->connedit_clone($a);
+ }
+ }
+ }
+ }
+ }
+ }
+ goaway(z_root() . '/connedit/' . $contact_id);
+ }
+
+
if($cmd === 'resetphoto') {
q("update xchan set xchan_photo_date = '2001-01-01 00:00:00' where xchan_hash = '%s'",
dbesc($orig_record[0]['xchan_hash'])
@@ -582,6 +603,13 @@ class Connedit extends \Zotlabs\Web\Controller {
'sel' => '',
'title' => t('Fetch updated permissions'),
),
+
+ 'rephoto' => array(
+ 'label' => t('Refresh Photo'),
+ 'url' => z_root() . '/connedit/' . $contact['abook_id'] . '/resetphoto',
+ 'sel' => '',
+ 'title' => t('Fetch updated photo'),
+ ),
'recent' => array(
'label' => t('Recent Activity'),
@@ -631,6 +659,17 @@ class Connedit extends \Zotlabs\Web\Controller {
);
+
+ if($contact['xchan_network'] === 'zot') {
+ $tools['fetchvc'] = [
+ 'label' => t('Fetch Vcard'),
+ 'url' => z_root() . '/connedit/' . $contact['abook_id'] . '/fetchvc',
+ 'sel' => '',
+ 'title' => t('Fetch electronic calling card for this connection')
+ ];
+ }
+
+
$sections = [];
$sections['perms'] = [
@@ -806,7 +845,23 @@ class Connedit extends \Zotlabs\Web\Controller {
}
}
else
- $locstr = t('none');
+ $locstr = $contact['xchan_url'];
+
+ $clone_warn = '';
+ $clonable = (in_array($contact['xchan_network'],['zot','rss']) ? true : false);
+ if(! $clonable) {
+ $clone_warn = '<strong>';
+ $clone_warn .= ((intval($contact['abook_not_here']))
+ ? t('This connection is unreachable from this location.')
+ : t('This connection may be unreachable from other channel locations.')
+ );
+ $clone_warn .= '</strong><br>' . t('Location independence is not supported by their network.');
+ }
+
+
+
+ if(intval($contact['abook_not_here']) && $unclonable)
+ $not_here = t('This connection is unreachable from this location. Location independence is not supported by their network.');
$o .= replace_macros($tpl, [
'$header' => (($self) ? t('Connection Default Permissions') : sprintf( t('Connection: %s'),$contact['xchan_name'])),
@@ -815,12 +870,14 @@ class Connedit extends \Zotlabs\Web\Controller {
'$permcat_new' => t('Add permission role'),
'$permcat_enable' => feature_enabled(local_channel(),'permcats'),
'$addr' => $contact['xchan_addr'],
+ '$primeurl' => $contact['xchan_url'],
'$section' => $section,
'$sections' => $sections,
'$vcard' => $vcard,
'$addr_text' => t('This connection\'s primary address is'),
'$loc_text' => t('Available locations:'),
'$locstr' => $locstr,
+ '$unclonable' => $clone_warn,
'$notself' => (($self) ? '' : '1'),
'$self' => (($self) ? '1' : ''),
'$autolbl' => t('The permissions indicated on this page will be applied to all new connections.'),
diff --git a/Zotlabs/Module/Cover_photo.php b/Zotlabs/Module/Cover_photo.php
index 72ec1020d..47bce6c2b 100644
--- a/Zotlabs/Module/Cover_photo.php
+++ b/Zotlabs/Module/Cover_photo.php
@@ -23,19 +23,17 @@ require_once('include/channel.php');
class Cover_photo extends \Zotlabs\Web\Controller {
function init() {
-
if(! local_channel()) {
return;
}
$channel = \App::get_channel();
- profile_load($channel['channel_address']);
-
+ profile_load($channel['channel_address']);
}
- /* @brief Evaluate posted values
+ /**
+ * @brief Evaluate posted values
*
- * @param $a Current application
* @return void
*
*/
@@ -130,8 +128,15 @@ class Cover_photo extends \Zotlabs\Web\Controller {
$aid = get_account_id();
- $p = array('aid' => $aid, 'uid' => local_channel(), 'resource_id' => $base_image['resource_id'],
- 'filename' => $base_image['filename'], 'album' => t('Cover Photos'));
+ $p = [
+ 'aid' => $aid,
+ 'uid' => local_channel(),
+ 'resource_id' => $base_image['resource_id'],
+ 'filename' => $base_image['filename'],
+ 'album' => t('Cover Photos'),
+ 'os_path' => $base_image['os_path'],
+ 'display_path' => $base_image['display_path']
+ ];
$p['imgscale'] = 7;
$p['photo_usage'] = PHOTO_COVER;
@@ -195,11 +200,10 @@ class Cover_photo extends \Zotlabs\Web\Controller {
$os_storage = false;
foreach($i as $ii) {
- $smallest = intval($ii['imgscale']);
+ $smallest = intval($ii['imgscale']);
$os_storage = intval($ii['os_storage']);
- $imagedata = $ii['content'];
- $filetype = $ii['mimetype'];
-
+ $imagedata = $ii['content'];
+ $filetype = $ii['mimetype'];
}
}
@@ -263,10 +267,10 @@ class Cover_photo extends \Zotlabs\Web\Controller {
}
- /* @brief Generate content of profile-photo view
+ /**
+ * @brief Generate content of profile-photo view
*
- * @param $a Current application
- * @return void
+ * @return string
*
*/
@@ -350,15 +354,15 @@ class Cover_photo extends \Zotlabs\Web\Controller {
$tpl = get_markup_template('cover_photo.tpl');
$o .= replace_macros($tpl,array(
- '$user' => \App::$channel['channel_address'],
- '$lbl_upfile' => t('Upload File:'),
- '$lbl_profiles' => t('Select a profile:'),
- '$title' => t('Upload Cover Photo'),
- '$submit' => t('Upload'),
- '$profiles' => $profiles,
+ '$user' => \App::$channel['channel_address'],
+ '$lbl_upfile' => t('Upload File:'),
+ '$lbl_profiles' => t('Select a profile:'),
+ '$title' => t('Upload Cover Photo'),
+ '$submit' => t('Upload'),
+ '$profiles' => $profiles,
'$form_security_token' => get_form_security_token("cover_photo"),
- // FIXME - yuk
- '$select' => sprintf('%s %s', t('or'), ($newuser) ? '<a href="' . z_root() . '">' . t('skip this step') . '</a>' : '<a href="'. z_root() . '/photos/' . \App::$channel['channel_address'] . '">' . t('select a photo from your photo albums') . '</a>')
+ /// @FIXME - yuk
+ '$select' => sprintf('%s %s', t('or'), ($newuser) ? '<a href="' . z_root() . '">' . t('skip this step') . '</a>' : '<a href="'. z_root() . '/photos/' . \App::$channel['channel_address'] . '">' . t('select a photo from your photo albums') . '</a>')
));
call_hooks('cover_photo_content_end', $o);
@@ -370,14 +374,14 @@ class Cover_photo extends \Zotlabs\Web\Controller {
$resolution = 3;
$tpl = get_markup_template("cropcover.tpl");
$o .= replace_macros($tpl,array(
- '$filename' => $filename,
- '$profile' => intval($_REQUEST['profile']),
- '$resource' => \App::$data['imagecrop'] . '-3',
- '$image_url' => z_root() . '/photo/' . $filename,
- '$title' => t('Crop Image'),
- '$desc' => t('Please adjust the image cropping for optimum viewing.'),
+ '$filename' => $filename,
+ '$profile' => intval($_REQUEST['profile']),
+ '$resource' => \App::$data['imagecrop'] . '-3',
+ '$image_url' => z_root() . '/photo/' . $filename,
+ '$title' => t('Crop Image'),
+ '$desc' => t('Please adjust the image cropping for optimum viewing.'),
'$form_security_token' => get_form_security_token("cover_photo"),
- '$done' => t('Done Editing')
+ '$done' => t('Done Editing')
));
return $o;
}
@@ -393,8 +397,6 @@ class Cover_photo extends \Zotlabs\Web\Controller {
*
*/
-
-
function cover_photo_crop_ui_head(&$a, $ph, $hash, $smallest){
$max_length = get_config('system','max_image_length');
diff --git a/Zotlabs/Module/Dav.php b/Zotlabs/Module/Dav.php
index 8ae2e8991..d506fe9f5 100644
--- a/Zotlabs/Module/Dav.php
+++ b/Zotlabs/Module/Dav.php
@@ -12,6 +12,9 @@ use \Sabre\DAV as SDAV;
use \Zotlabs\Storage;
require_once('include/attach.php');
+require_once('include/auth.php');
+require_once('include/security.php');
+
class Dav extends \Zotlabs\Web\Controller {
@@ -21,22 +24,65 @@ class Dav extends \Zotlabs\Web\Controller {
*/
function init() {
- // workaround for HTTP-auth in CGI mode
- if (x($_SERVER, 'REDIRECT_REMOTE_USER')) {
- $userpass = base64_decode(substr($_SERVER["REDIRECT_REMOTE_USER"], 6)) ;
- if(strlen($userpass)) {
- list($name, $password) = explode(':', $userpass);
- $_SERVER['PHP_AUTH_USER'] = $name;
- $_SERVER['PHP_AUTH_PW'] = $password;
+ foreach([ 'REDIRECT_REMOTE_USER', 'HTTP_AUTHORIZATION' ] as $head) {
+
+ /* Basic authentication */
+
+ if(array_key_exists($head,$_SERVER) && substr(trim($_SERVER[$head]),0,5) === 'Basic') {
+ $userpass = @base64_decode(substr(trim($_SERVER[$head]),6)) ;
+ if(strlen($userpass)) {
+ list($name, $password) = explode(':', $userpass);
+ $_SERVER['PHP_AUTH_USER'] = $name;
+ $_SERVER['PHP_AUTH_PW'] = $password;
+ }
+ break;
}
- }
- if (x($_SERVER, 'HTTP_AUTHORIZATION')) {
- $userpass = base64_decode(substr($_SERVER["HTTP_AUTHORIZATION"], 6)) ;
- if(strlen($userpass)) {
- list($name, $password) = explode(':', $userpass);
- $_SERVER['PHP_AUTH_USER'] = $name;
- $_SERVER['PHP_AUTH_PW'] = $password;
+ /* Signature authentication */
+
+ if(array_key_exists($head,$_SERVER) && substr(trim($_SERVER[$head]),0,9) === 'Signature') {
+ if($head !== 'HTTP_AUTHORIZATION') {
+ $_SERVER['HTTP_AUTHORIZATION'] = $_SERVER[$head];
+ continue;
+ }
+
+ $sigblock = \Zotlabs\Web\HTTPSig::parse_sigheader($_SERVER[$head]);
+ if($sigblock) {
+ $keyId = $sigblock['keyId'];
+ if($keyId) {
+ $r = q("select * from hubloc where hubloc_addr = '%s' limit 1",
+ dbesc($keyId)
+ );
+ if($r) {
+ $c = channelx_by_hash($r[0]['hubloc_hash']);
+ if($c) {
+ $a = q("select * from account where account_id = %d limit 1",
+ intval($c['channel_account_id'])
+ );
+ if($a) {
+ $record = [ 'channel' => $c, 'account' => $a[0] ];
+ $channel_login = $c['channel_id'];
+ }
+ }
+ }
+ if(! $record)
+ continue;
+
+ if($record) {
+ $verified = \Zotlabs\Web\HTTPSig::verify('',$record['channel']['channel_pubkey']);
+ if(! ($verified && $verified['header_signed'] && $verified['header_valid'])) {
+ $record = null;
+ }
+ if($record['account']) {
+ authenticate_success($record['account']);
+ if($channel_login) {
+ change_channel($channel_login);
+ }
+ }
+ break;
+ }
+ }
+ }
}
}
diff --git a/Zotlabs/Module/Directory.php b/Zotlabs/Module/Directory.php
index 59ae88857..caf0190ae 100644
--- a/Zotlabs/Module/Directory.php
+++ b/Zotlabs/Module/Directory.php
@@ -4,7 +4,6 @@ namespace Zotlabs\Module;
require_once('include/socgraph.php');
require_once('include/dir_fns.php');
-require_once('include/widgets.php');
require_once('include/bbcode.php');
@@ -78,7 +77,7 @@ class Directory extends \Zotlabs\Web\Controller {
$pubforums = get_directory_setting($observer, 'pubforums');
$o = '';
- nav_set_selected('directory');
+ nav_set_selected('Directory');
if(x($_POST,'search'))
$search = notags(trim($_POST['search']));
@@ -234,7 +233,7 @@ class Directory extends \Zotlabs\Web\Controller {
$age = '';
if(strlen($rr['birthday'])) {
- if(($years = age($rr['birthday'],'UTC','')) != 0)
+ if(($years = age($rr['birthday'],'UTC','')) > 0)
$age = $years;
}
diff --git a/Zotlabs/Module/Display.php b/Zotlabs/Module/Display.php
index 638aa881a..785274105 100644
--- a/Zotlabs/Module/Display.php
+++ b/Zotlabs/Module/Display.php
@@ -1,84 +1,86 @@
<?php
namespace Zotlabs\Module;
+require_once("include/bbcode.php");
+require_once('include/security.php');
+require_once('include/conversation.php');
+require_once('include/acl_selectors.php');
+require_once('include/items.php');
class Display extends \Zotlabs\Web\Controller {
function get($update = 0, $load = false) {
-
+
+ if(argc() > 1) {
+ $module_format = substr(argv(1),strrpos(argv(1),'.') + 1);
+ if(! in_array($module_format,['atom','zot','json']))
+ $module_format = 'html';
+ }
+
$checkjs = new \Zotlabs\Web\CheckJS(1);
if($load)
$_SESSION['loadtime'] = datetime_convert();
-
if(observer_prohibited()) {
notice( t('Public access denied.') . EOL);
return;
}
- require_once("include/bbcode.php");
- require_once('include/security.php');
- require_once('include/conversation.php');
- require_once('include/acl_selectors.php');
- require_once('include/items.php');
-
-
- \App::$page['htmlhead'] .= replace_macros(get_markup_template('display-head.tpl'), array());
-
- if(argc() > 1 && argv(1) !== 'load')
+ if(argc() > 1 && argv(1) !== 'load') {
$item_hash = argv(1);
+ if($module_format !== 'html') {
+ $item_hash = substr($item_hash,0,strrpos($item_hash,'.'));
+ }
+ }
if($_REQUEST['mid'])
$item_hash = $_REQUEST['mid'];
- if(! $item_hash) {
+ if(! $item_hash) {
\App::$error = 404;
notice( t('Item not found.') . EOL);
return;
}
$observer_is_owner = false;
-
-
+ $updateable = false;
+
if(local_channel() && (! $update)) {
$channel = \App::get_channel();
-
-
+
$channel_acl = array(
'allow_cid' => $channel['channel_allow_cid'],
'allow_gid' => $channel['channel_allow_gid'],
- 'deny_cid' => $channel['channel_deny_cid'],
- 'deny_gid' => $channel['channel_deny_gid']
+ 'deny_cid' => $channel['channel_deny_cid'],
+ 'deny_gid' => $channel['channel_deny_gid']
);
-
-
+
$x = array(
- 'is_owner' => true,
- 'allow_location' => ((intval(get_pconfig($channel['channel_id'],'system','use_browser_location'))) ? '1' : ''),
- 'default_location' => $channel['channel_location'],
- 'nickname' => $channel['channel_address'],
- 'lockstate' => (($group || $cid || $channel['channel_allow_cid'] || $channel['channel_allow_gid'] || $channel['channel_deny_cid'] || $channel['channel_deny_gid']) ? 'lock' : 'unlock'),
-
- 'acl' => populate_acl($channel_acl),
- 'permissions' => $channel_acl,
- 'bang' => '',
- 'visitor' => true,
- 'profile_uid' => local_channel(),
- 'return_path' => 'channel/' . $channel['channel_address'],
- 'expanded' => true,
+ 'is_owner' => true,
+ 'allow_location' => ((intval(get_pconfig($channel['channel_id'],'system','use_browser_location'))) ? '1' : ''),
+ 'default_location' => $channel['channel_location'],
+ 'nickname' => $channel['channel_address'],
+ 'lockstate' => (($group || $cid || $channel['channel_allow_cid'] || $channel['channel_allow_gid'] || $channel['channel_deny_cid'] || $channel['channel_deny_gid']) ? 'lock' : 'unlock'),
+
+ 'acl' => populate_acl($channel_acl),
+ 'permissions' => $channel_acl,
+ 'bang' => '',
+ 'visitor' => true,
+ 'profile_uid' => local_channel(),
+ 'return_path' => 'channel/' . $channel['channel_address'],
+ 'expanded' => true,
'editor_autocomplete' => true,
- 'bbco_autocomplete' => 'bbcode',
- 'bbcode' => true,
- 'jotnets' => true
+ 'bbco_autocomplete' => 'bbcode',
+ 'bbcode' => true,
+ 'jotnets' => true
);
$o = '<div id="jot-popup">';
$o .= status_editor($a,$x);
$o .= '</div>';
-
}
// This page can be viewed by anybody so the query could be complicated
@@ -97,14 +99,18 @@ class Display extends \Zotlabs\Web\Controller {
if($decoded)
$item_hash = $decoded;
- $r = q("select id, uid, mid, parent_mid, item_type, item_deleted from item where mid like '%s' limit 1",
- dbesc($item_hash . '%'),
- dbesc($decoded . '%')
+ $r = q("select id, uid, mid, parent_mid, thr_parent, verb, item_type, item_deleted, item_blocked from item where mid like '%s' limit 1",
+ dbesc($item_hash . '%')
);
if($r) {
$target_item = $r[0];
}
+
+ //if the item is to be moderated redirect to /moderate
+ if($target_item['item_blocked'] == ITEM_MODERATED) {
+ goaway(z_root() . '/moderate/' . $target_item['id']);
+ }
$r = null;
@@ -140,66 +146,79 @@ class Display extends \Zotlabs\Web\Controller {
$simple_update .= " and item_thread_top = 0 and author_xchan = '" . protect_sprintf(get_observer_hash()) . "' ";
if((! $update) && (! $load)) {
-
- $static = ((local_channel()) ? channel_manual_conv_update(local_channel()) : 0);
-
+ $static = ((local_channel()) ? channel_manual_conv_update(local_channel()) : 1);
+
+ // if the target item is not a post (eg a like) we want to address its thread parent
+
+ $mid = ((($target_item['verb'] == ACTIVITY_LIKE) || ($target_item['verb'] == ACTIVITY_DISLIKE)) ? $target_item['thr_parent'] : $target_item['mid']);
+
+ // if we got a decoded hash we must encode it again before handing to javascript
+ if($decoded)
+ $mid = 'b64.' . base64url_encode($mid);
+
$o .= '<div id="live-display"></div>' . "\r\n";
$o .= "<script> var profile_uid = " . ((intval(local_channel())) ? local_channel() : (-1))
. "; var netargs = '?f='; var profile_page = " . \App::$pager['page'] . "; </script>\r\n";
\App::$page['htmlhead'] .= replace_macros(get_markup_template("build_query.tpl"),array(
'$baseurl' => z_root(),
- '$pgtype' => 'display',
- '$uid' => '0',
- '$gid' => '0',
- '$cid' => '0',
- '$cmin' => '0',
- '$cmax' => '99',
- '$star' => '0',
- '$liked' => '0',
- '$conv' => '0',
- '$spam' => '0',
- '$fh' => '0',
+ '$pgtype' => 'display',
+ '$uid' => '0',
+ '$gid' => '0',
+ '$cid' => '0',
+ '$cmin' => '0',
+ '$cmax' => '99',
+ '$star' => '0',
+ '$liked' => '0',
+ '$conv' => '0',
+ '$spam' => '0',
+ '$fh' => '0',
'$nouveau' => '0',
- '$wall' => '0',
- '$static' => $static,
- '$page' => ((\App::$pager['page'] != 1) ? \App::$pager['page'] : 1),
- '$list' => ((x($_REQUEST,'list')) ? intval($_REQUEST['list']) : 0),
- '$search' => '',
- '$order' => '',
- '$file' => '',
- '$cats' => '',
- '$tags' => '',
- '$dend' => '',
- '$dbegin' => '',
- '$verb' => '',
- '$mid' => $item_hash
+ '$wall' => '0',
+ '$static' => $static,
+ '$page' => ((\App::$pager['page'] != 1) ? \App::$pager['page'] : 1),
+ '$list' => ((x($_REQUEST,'list')) ? intval($_REQUEST['list']) : 0),
+ '$search' => '',
+ '$xchan' => '',
+ '$order' => '',
+ '$file' => '',
+ '$cats' => '',
+ '$tags' => '',
+ '$dend' => '',
+ '$dbegin' => '',
+ '$verb' => '',
+ '$mid' => $mid
));
-
-
+
+ head_add_link([
+ 'rel' => 'alternate',
+ 'type' => 'application/json+oembed',
+ 'href' => z_root() . '/oep?f=&url=' . urlencode(z_root() . '/' . \App::$query_string),
+ 'title' => 'oembed'
+ ]);
+
}
-
+
$observer_hash = get_observer_hash();
$item_normal = item_normal();
-
+ $item_normal_update = item_normal_update();
+
$sql_extra = public_permissions_sql($observer_hash);
-
- if(($update && $load) || ($checkjs->disabled())) {
-
- $updateable = false;
-
+
+ if(($update && $load) || ($checkjs->disabled()) || ($module_format !== 'html')) {
+
$pager_sql = sprintf(" LIMIT %d OFFSET %d ", intval(\App::$pager['itemspage']),intval(\App::$pager['start']));
-
- if($load || ($checkjs->disabled())) {
+
+ if($load || ($checkjs->disabled()) || ($module_format !== 'html')) {
$r = null;
-
+
require_once('include/channel.php');
$sys = get_sys_channel();
$sysid = $sys['channel_id'];
-
+
if(local_channel()) {
- $r = q("SELECT * from item
+ $r = q("SELECT item.id as item_id from item
WHERE uid = %d
and mid = '%s'
$item_normal
@@ -209,24 +228,22 @@ class Display extends \Zotlabs\Web\Controller {
);
if($r) {
$updateable = true;
-
}
-
}
+
if($r === null) {
-
+
// in case somebody turned off public access to sys channel content using permissions
- // make that content unsearchable by ensuring the owner_xchan can't match
-
+ // make that content unsearchable by ensuring the owner uid can't match
+
if(! perm_is_allowed($sysid,$observer_hash,'view_stream'))
$sysid = 0;
-
-
- $r = q("SELECT * from item
+
+ $r = q("SELECT item.id as item_id from item
WHERE mid = '%s'
AND (((( item.allow_cid = '' AND item.allow_gid = '' AND item.deny_cid = ''
AND item.deny_gid = '' AND item_private = 0 )
- and owner_xchan in ( " . stream_perms_xchans(($observer_hash) ? (PERMS_NETWORK|PERMS_PUBLIC) : PERMS_PUBLIC) . " ))
+ and uid in ( " . stream_perms_api_uids(($observer_hash) ? (PERMS_NETWORK|PERMS_PUBLIC) : PERMS_PUBLIC) . " ))
OR uid = %d )
$sql_extra )
$item_normal
@@ -234,7 +251,6 @@ class Display extends \Zotlabs\Web\Controller {
dbesc($target_item['parent_mid']),
intval($sysid)
);
-
}
}
}
@@ -245,12 +261,12 @@ class Display extends \Zotlabs\Web\Controller {
require_once('include/channel.php');
$sys = get_sys_channel();
$sysid = $sys['channel_id'];
-
+
if(local_channel()) {
- $r = q("SELECT * from item
+ $r = q("SELECT item.parent AS item_id from item
WHERE uid = %d
- and mid = '%s'
- $item_normal
+ and parent_mid = '%s'
+ $item_normal_update
$simple_update
limit 1",
intval(local_channel()),
@@ -260,20 +276,21 @@ class Display extends \Zotlabs\Web\Controller {
$updateable = true;
}
}
+
if($r === null) {
// in case somebody turned off public access to sys channel content using permissions
// make that content unsearchable by ensuring the owner_xchan can't match
if(! perm_is_allowed($sysid,$observer_hash,'view_stream'))
$sysid = 0;
-
- $r = q("SELECT * from item
- WHERE mid = '%s'
+
+ $r = q("SELECT item.parent AS item_id from item
+ WHERE parent_mid = '%s'
AND (((( item.allow_cid = '' AND item.allow_gid = '' AND item.deny_cid = ''
AND item.deny_gid = '' AND item_private = 0 )
- and owner_xchan in ( " . stream_perms_xchans(($observer_hash) ? (PERMS_NETWORK|PERMS_PUBLIC) : PERMS_PUBLIC) . " ))
+ and uid in ( " . stream_perms_api_uids(($observer_hash) ? (PERMS_NETWORK|PERMS_PUBLIC) : PERMS_PUBLIC) . " ))
OR uid = %d )
$sql_extra )
- $item_normal
+ $item_normal_update
$simple_update
limit 1",
dbesc($target_item['parent_mid']),
@@ -288,10 +305,8 @@ class Display extends \Zotlabs\Web\Controller {
}
if($r) {
-
- $parents_str = ids_to_querystr($r,'id');
+ $parents_str = ids_to_querystr($r,'item_id');
if($parents_str) {
-
$items = q("SELECT item.*, item.id AS item_id
FROM item
WHERE parent in ( %s ) $item_normal ",
@@ -302,39 +317,83 @@ class Display extends \Zotlabs\Web\Controller {
$items = fetch_post_tags($items,true);
$items = conv_sort($items,'created');
}
- } else {
+ }
+ else {
$items = array();
}
-
- if ($checkjs->disabled()) {
- $o .= conversation($a, $items, 'display', $update, 'traditional');
- if ($items[0]['title'])
- \App::$page['title'] = $items[0]['title'] . " - " . \App::$page['title'];
- }
- else {
- $o .= conversation($a, $items, 'display', $update, 'client');
+
+ switch($module_format) {
+
+ case 'html':
+
+ if ($checkjs->disabled()) {
+ $o .= conversation($items, 'display', $update, 'traditional');
+ if ($items[0]['title'])
+ \App::$page['title'] = $items[0]['title'] . " - " . \App::$page['title'];
+ }
+ else {
+ $o .= conversation($items, 'display', $update, 'client');
+ }
+
+ break;
+
+ case 'atom':
+
+ $atom = replace_macros(get_markup_template('atom_feed.tpl'), array(
+ '$version' => xmlify(\Zotlabs\Lib\System::get_project_version()),
+ '$red' => xmlify(\Zotlabs\Lib\System::get_platform_name()),
+ '$feed_id' => xmlify(\App::$cmd),
+ '$feed_title' => xmlify(t('Article')),
+ '$feed_updated' => xmlify(datetime_convert('UTC', 'UTC', 'now', ATOM_TIME)),
+ '$author' => '',
+ '$owner' => '',
+ '$profile_page' => xmlify(z_root() . '/display/' . $target_item['mid']),
+ ));
+
+ $x = [ 'xml' => $atom, 'channel' => $channel, 'observer_hash' => $observer_hash, 'params' => $params ];
+ call_hooks('atom_feed_top',$x);
+
+ $atom = $x['xml'];
+
+ // a much simpler interface
+ call_hooks('atom_feed', $atom);
+
+
+ if($items) {
+ $type = 'html';
+ foreach($items as $item) {
+ if($item['item_private'])
+ continue;
+ $atom .= atom_entry($item, $type, null, '', true, '', false);
+ }
+ }
+
+ call_hooks('atom_feed_end', $atom);
+
+ $atom .= '</feed>' . "\r\n";
+
+ header('Content-type: application/atom+xml');
+ echo $atom;
+ killme();
+
}
if($updateable) {
$x = q("UPDATE item SET item_unseen = 0 where item_unseen = 1 AND uid = %d and parent = %d ",
intval(local_channel()),
- intval($r[0]['parent'])
+ intval($r[0]['item_id'])
);
}
-
+
$o .= '<div id="content-complete"></div>';
-
- return $o;
-
-
- /*
- elseif((! $update) && (! {
+
+ if((($update && $load) || $checkjs->disabled()) && (! $items)) {
- $r = q("SELECT id, item_flags FROM item WHERE id = '%s' OR mid = '%s' LIMIT 1",
- dbesc($item_hash),
+ $r = q("SELECT id, item_deleted FROM item WHERE mid = '%s' LIMIT 1",
dbesc($item_hash)
);
+
if($r) {
if(intval($r[0]['item_deleted'])) {
notice( t('Item has been removed.') . EOL );
@@ -348,8 +407,9 @@ class Display extends \Zotlabs\Web\Controller {
}
}
- */
+
+ return $o;
+
}
-
-
+
}
diff --git a/Zotlabs/Module/Editblock.php b/Zotlabs/Module/Editblock.php
index 654e2251d..8a7e87a09 100644
--- a/Zotlabs/Module/Editblock.php
+++ b/Zotlabs/Module/Editblock.php
@@ -98,6 +98,11 @@ class Editblock extends \Zotlabs\Web\Controller {
$mimetype = $itm[0]['mimetype'];
+ $content = $itm[0]['body'];
+ if($itm[0]['mimetype'] === 'text/markdown')
+ $content = \Zotlabs\Lib\MarkdownSoap::unescape($itm[0]['body']);
+
+
$rp = 'blocks/' . $channel['channel_address'];
$x = array(
@@ -117,7 +122,7 @@ class Editblock extends \Zotlabs\Web\Controller {
'ptyp' => $itm[0]['type'],
'mimeselect' => true,
'mimetype' => $itm[0]['mimetype'],
- 'body' => undo_post_tagging($itm[0]['body']),
+ 'body' => undo_post_tagging($content),
'post_id' => $post_id,
'visitor' => true,
'title' => htmlspecialchars($itm[0]['title'],ENT_COMPAT,'UTF-8'),
diff --git a/Zotlabs/Module/Editlayout.php b/Zotlabs/Module/Editlayout.php
index ea637fcba..3d6a79507 100644
--- a/Zotlabs/Module/Editlayout.php
+++ b/Zotlabs/Module/Editlayout.php
@@ -119,6 +119,7 @@ class Editlayout extends \Zotlabs\Web\Controller {
'hide_weblink' => true,
'hide_attach' => true,
'hide_preview' => true,
+ 'disable_comments' => true,
'ptyp' => $itm[0]['obj_type'],
'body' => undo_post_tagging($itm[0]['body']),
'post_id' => $post_id,
diff --git a/Zotlabs/Module/Editpost.php b/Zotlabs/Module/Editpost.php
index d7612b165..a54c42e7f 100644
--- a/Zotlabs/Module/Editpost.php
+++ b/Zotlabs/Module/Editpost.php
@@ -31,7 +31,15 @@ class Editpost extends \Zotlabs\Web\Controller {
dbesc(get_observer_hash())
);
- if(! count($itm)) {
+ // don't allow web editing of potentially binary content (item_obscured = 1)
+ // @FIXME how do we do it instead?
+
+ if((! $itm) || intval($itm[0]['item_obscured'])) {
+ notice( t('Item is not editable') . EOL);
+ return;
+ }
+
+ if($itm[0]['resource_type'] === 'photo' && $itm[0]['resource_id']) {
notice( t('Item is not editable') . EOL);
return;
}
@@ -44,14 +52,6 @@ class Editpost extends \Zotlabs\Web\Controller {
$channel = \App::get_channel();
- if(intval($itm[0]['item_obscured'])) {
- $key = get_config('system','prvkey');
- if($itm[0]['title'])
- $itm[0]['title'] = crypto_unencapsulate(json_decode($itm[0]['title'],true),$key);
- if($itm[0]['body'])
- $itm[0]['body'] = crypto_unencapsulate(json_decode($itm[0]['body'],true),$key);
- }
-
$category = '';
$catsenabled = ((feature_enabled($owner_uid,'categories')) ? 'categories' : '');
diff --git a/Zotlabs/Module/Editwebpage.php b/Zotlabs/Module/Editwebpage.php
index 3d4af107d..da536a729 100644
--- a/Zotlabs/Module/Editwebpage.php
+++ b/Zotlabs/Module/Editwebpage.php
@@ -100,24 +100,19 @@ class Editwebpage extends \Zotlabs\Web\Controller {
intval($owner)
);
- if(! $itm) {
+ // don't allow web editing of potentially binary content (item_obscured = 1)
+ // @FIXME how do we do it instead?
+
+ if((! $itm) || intval($itm[0]['item_obscured'])) {
notice( t('Permission denied.') . EOL);
return;
}
- if(intval($itm[0]['item_obscured'])) {
- $key = get_config('system','prvkey');
- if($itm[0]['title'])
- $itm[0]['title'] = crypto_unencapsulate(json_decode($itm[0]['title'],true),$key);
- if($itm[0]['body'])
- $itm[0]['body'] = crypto_unencapsulate(json_decode($itm[0]['body'],true),$key);
- }
-
$item_id = q("select * from iconfig where cat = 'system' and k = 'WEBPAGE' and iid = %d limit 1",
intval($itm[0]['id'])
);
if($item_id)
- $page_title = $item_id[0]['v'];
+ $page_title = urldecode($item_id[0]['v']);
$mimetype = $itm[0]['mimetype'];
@@ -129,9 +124,11 @@ class Editwebpage extends \Zotlabs\Web\Controller {
}
$layout = $itm[0]['layout_mid'];
-
- $tpl = get_markup_template("jot.tpl");
+ $content = $itm[0]['body'];
+ if($itm[0]['mimetype'] === 'text/markdown')
+ $content = \Zotlabs\Lib\MarkdownSoap::unescape($itm[0]['body']);
+
$rp = 'webpages/' . $which;
$x = array(
@@ -147,7 +144,7 @@ class Editwebpage extends \Zotlabs\Web\Controller {
'hide_location' => true,
'hide_voting' => true,
'ptyp' => $itm[0]['type'],
- 'body' => undo_post_tagging($itm[0]['body']),
+ 'body' => undo_post_tagging($content),
'post_id' => $post_id,
'visitor' => ($is_owner) ? true : false,
'acl' => populate_acl($itm[0],false,\Zotlabs\Lib\PermissionDescription::fromGlobalPermission('view_pages')),
diff --git a/Zotlabs/Module/Embedphotos.php b/Zotlabs/Module/Embedphotos.php
index 48667795c..c92af27d6 100644
--- a/Zotlabs/Module/Embedphotos.php
+++ b/Zotlabs/Module/Embedphotos.php
@@ -92,6 +92,7 @@ class Embedphotos extends \Zotlabs\Web\Controller {
* It is a limitation of the photo table using a name for a photo album instead of a folder hash
*/
if($album) {
+ require_once('include/attach.php');
$x = q("select hash from attach where filename = '%s' and uid = %d limit 1",
dbesc($album),
intval($owner_uid)
diff --git a/Zotlabs/Module/Events.php b/Zotlabs/Module/Events.php
index edc6dd3f0..33c8b8249 100644
--- a/Zotlabs/Module/Events.php
+++ b/Zotlabs/Module/Events.php
@@ -272,7 +272,7 @@ class Events extends \Zotlabs\Web\Controller {
return;
}
- nav_set_selected('all_events');
+ nav_set_selected('Events');
if((argc() > 2) && (argv(1) === 'ignore') && intval(argv(2))) {
$r = q("update event set dismissed = 1 where id = %d and uid = %d",
diff --git a/Zotlabs/Module/Feed.php b/Zotlabs/Module/Feed.php
index 47871eafb..06637b6d2 100644
--- a/Zotlabs/Module/Feed.php
+++ b/Zotlabs/Module/Feed.php
@@ -1,40 +1,41 @@
<?php
+
namespace Zotlabs\Module;
require_once('include/items.php');
-
class Feed extends \Zotlabs\Web\Controller {
function init() {
- $params = array();
-
- $params['begin'] = ((x($_REQUEST,'date_begin')) ? $_REQUEST['date_begin'] : NULL_DATE);
- $params['end'] = ((x($_REQUEST,'date_end')) ? $_REQUEST['date_end'] : '');
- $params['type'] = ((stristr(argv(0),'json')) ? 'json' : 'xml');
- $params['pages'] = ((x($_REQUEST,'pages')) ? intval($_REQUEST['pages']) : 0);
- $params['top'] = ((x($_REQUEST,'top')) ? intval($_REQUEST['top']) : 0);
- $params['start'] = ((x($params,'start')) ? intval($params['start']) : 0);
- $params['records'] = ((x($params,'records')) ? intval($params['records']) : 40);
- $params['direction'] = ((x($params,'direction')) ? dbesc($params['direction']) : 'desc');
- $params['cat'] = ((x($_REQUEST,'cat')) ? escape_tags($_REQUEST['cat']) : '');
-
- $channel = '';
+ $params = [];
+
+ $params['begin'] = ((x($_REQUEST,'date_begin')) ? $_REQUEST['date_begin'] : NULL_DATE);
+ $params['end'] = ((x($_REQUEST,'date_end')) ? $_REQUEST['date_end'] : '');
+ $params['type'] = ((stristr(argv(0),'json')) ? 'json' : 'xml');
+ $params['pages'] = ((x($_REQUEST,'pages')) ? intval($_REQUEST['pages']) : 0);
+ $params['top'] = ((x($_REQUEST,'top')) ? intval($_REQUEST['top']) : 0);
+ $params['start'] = ((x($params,'start')) ? intval($params['start']) : 0);
+ $params['records'] = ((x($params,'records')) ? intval($params['records']) : 40);
+ $params['direction'] = ((x($params,'direction')) ? dbesc($params['direction']) : 'desc');
+ $params['cat'] = ((x($_REQUEST,'cat')) ? escape_tags($_REQUEST['cat']) : '');
+ $params['compat'] = ((x($_REQUEST,'compat')) ? intval($_REQUEST['compat']) : 0);
+
+
if(argc() > 1) {
- $r = q("select * from channel left join xchan on channel_hash = xchan_hash where channel_address = '%s' limit 1",
- dbesc(argv(1))
- );
- if(!($r && count($r)))
+
+ if(observer_prohibited(true)) {
killme();
-
- $channel = $r[0];
-
- if(observer_prohibited(true))
+ }
+
+ $channel = channelx_by_nick(argv(1));
+ if(! $channel) {
killme();
+ }
+
- logger('mod_feed: public feed request from ' . $_SERVER['REMOTE_ADDR'] . ' for ' . $channel['channel_address']);
+ logger('public feed request from ' . $_SERVER['REMOTE_ADDR'] . ' for ' . $channel['channel_address']);
echo get_public_feed($channel,$params);
@@ -43,6 +44,4 @@ class Feed extends \Zotlabs\Web\Controller {
}
-
-
}
diff --git a/Zotlabs/Module/File_upload.php b/Zotlabs/Module/File_upload.php
index 769134808..5c4b9a502 100644
--- a/Zotlabs/Module/File_upload.php
+++ b/Zotlabs/Module/File_upload.php
@@ -28,15 +28,32 @@ class File_upload extends \Zotlabs\Web\Controller {
$_REQUEST['group_deny'] = expand_acl($channel['channel_deny_gid']);
}
+ $_REQUEST['allow_cid'] = perms2str($_REQUEST['contact_allow']);
+ $_REQUEST['allow_gid'] = perms2str($_REQUEST['group_allow']);
+ $_REQUEST['deny_cid'] = perms2str($_REQUEST['contact_deny']);
+ $_REQUEST['deny_gid'] = perms2str($_REQUEST['group_deny']);
+
if($_REQUEST['filename']) {
- $_REQUEST['allow_cid'] = perms2str($_REQUEST['contact_allow']);
- $_REQUEST['allow_gid'] = perms2str($_REQUEST['group_allow']);
- $_REQUEST['deny_cid'] = perms2str($_REQUEST['contact_deny']);
- $_REQUEST['deny_gid'] = perms2str($_REQUEST['group_deny']);
- $r = attach_mkdir($channel,get_observer_hash(),$_REQUEST);
+ $r = attach_mkdir($channel, get_observer_hash(), $_REQUEST);
+ if($r['success']) {
+ $hash = $r['data']['hash'];
+
+ $sync = attach_export_data($channel,$hash);
+ if($sync) {
+ build_sync_packet($channel['channel_id'],array('file' => array($sync)));
+ }
+ goaway(z_root() . '/cloud/' . $channel['channel_address'] . '/' . $r['data']['display_path']);
+
+ }
}
else {
- $r = attach_store($channel,get_observer_hash(), '', $_REQUEST);
+ $r = attach_store($channel, get_observer_hash(), '', $_REQUEST);
+ if($r['success']) {
+ $sync = attach_export_data($channel,$r['data']['hash']);
+ if($sync)
+ build_sync_packet($channel['channel_id'],array('file' => array($sync)));
+
+ }
}
goaway(z_root() . '/' . $_REQUEST['return_url']);
diff --git a/Zotlabs/Module/Filer.php b/Zotlabs/Module/Filer.php
index 6a57cdb2a..af59f28fb 100644
--- a/Zotlabs/Module/Filer.php
+++ b/Zotlabs/Module/Filer.php
@@ -49,8 +49,10 @@ class Filer extends \Zotlabs\Web\Controller {
}
$tpl = get_markup_template("filer_dialog.tpl");
$o = replace_macros($tpl, array(
- '$field' => array('term', t("Save to Folder:"), '', '', $filetags, t('- select -')),
+ '$field' => array('term', t('Enter a folder name'), '', '', $filetags, 'placeholder="' . t('or select an existing folder (doubleclick)') . '"'),
'$submit' => t('Save'),
+ '$title' => t('Save to Folder'),
+ '$cancel' => t('Cancel')
));
echo $o;
diff --git a/Zotlabs/Module/Filestorage.php b/Zotlabs/Module/Filestorage.php
index 874445145..55713027a 100644
--- a/Zotlabs/Module/Filestorage.php
+++ b/Zotlabs/Module/Filestorage.php
@@ -5,14 +5,6 @@ namespace Zotlabs\Module;
*
*/
-require_once('include/attach.php');
-
-
-/**
- *
- * @param object &$a
- */
-
class Filestorage extends \Zotlabs\Web\Controller {
function post() {
@@ -26,7 +18,7 @@ class Filestorage extends \Zotlabs\Web\Controller {
$recurse = ((x($_POST, 'recurse')) ? intval($_POST['recurse']) : 0);
$resource = ((x($_POST, 'filehash')) ? notags($_POST['filehash']) : '');
- $notify = ((x($_POST, 'notify')) ? intval($_POST['notify']) : 0);
+ $notify = ((x($_POST, 'notify_edit')) ? intval($_POST['notify_edit']) : 0);
if(! $resource) {
notice(t('Item not found.') . EOL);
@@ -36,19 +28,19 @@ class Filestorage extends \Zotlabs\Web\Controller {
$channel = \App::get_channel();
$acl = new \Zotlabs\Access\AccessList($channel);
- $acl->set_from_array($_REQUEST);
+ $acl->set_from_array($_POST);
$x = $acl->get();
- $cloudPath = get_parent_cloudpath($channel_id, $channel['channel_address'], $resource);
+ $url = get_cloud_url($channel_id, $channel['channel_address'], $resource);
//get the object before permissions change so we can catch eventual former allowed members
- $object = get_file_activity_object($channel_id, $resource, $cloudPath);
+ $object = get_file_activity_object($channel_id, $resource, $url);
attach_change_permissions($channel_id, $resource, $x['allow_cid'], $x['allow_gid'], $x['deny_cid'], $x['deny_gid'], $recurse, true);
file_activity($channel_id, $object, $x['allow_cid'], $x['allow_gid'], $x['deny_cid'], $x['deny_gid'], 'post', $notify);
- goaway($cloudPath);
+ goaway(dirname($url));
}
function get() {
@@ -107,11 +99,11 @@ class Filestorage extends \Zotlabs\Web\Controller {
$f = $r[0];
$channel = \App::get_channel();
- $parentpath = get_parent_cloudpath($channel['channel_id'], $channel['channel_address'], $f['hash']);
+ $url = get_cloud_url($channel['channel_id'], $channel['channel_address'], $f['hash']);
attach_delete($owner, $f['hash']);
- goaway($parentpath);
+ goaway(dirname($url));
}
if(argc() > 3 && argv(3) === 'edit') {
@@ -130,8 +122,7 @@ class Filestorage extends \Zotlabs\Web\Controller {
$f = $r[0];
$channel = \App::get_channel();
- $cloudpath = get_cloudpath($f) . (intval($f['is_dir']) ? '?f=&davguest=1' : '');
- $parentpath = get_parent_cloudpath($channel['channel_id'], $channel['channel_address'], $f['hash']);
+ $cloudpath = get_cloudpath($f);
$aclselect_e = populate_acl($f, false, \Zotlabs\Lib\PermissionDescription::fromGlobalPermission('view_storage'));
$is_a_dir = (intval($f['is_dir']) ? true : false);
@@ -146,7 +137,6 @@ class Filestorage extends \Zotlabs\Web\Controller {
'$header' => t('Edit file permissions'),
'$file' => $f,
'$cloudpath' => z_root() . '/' . $encoded_path,
- '$parentpath' => $parentpath,
'$uid' => $channel['channel_id'],
'$channelnick' => $channel['channel_address'],
'$permissions' => t('Permissions'),
@@ -165,7 +155,7 @@ class Filestorage extends \Zotlabs\Web\Controller {
'$submit' => t('Submit'),
'$attach_btn_title' => t('Share this file'),
'$link_btn_title' => t('Show URL to this file'),
- '$notify' => array('notify', t('Notify your contacts about this file'), 0, '', array(t('No'), t('Yes'))),
+ '$notify' => array('notify_edit', t('Show in your contacts shared folder'), 0, '', array(t('No'), t('Yes'))),
));
echo $o;
diff --git a/Zotlabs/Module/Getfile.php b/Zotlabs/Module/Getfile.php
index 3d859d94b..413a68e0c 100644
--- a/Zotlabs/Module/Getfile.php
+++ b/Zotlabs/Module/Getfile.php
@@ -35,6 +35,7 @@ class Getfile extends \Zotlabs\Web\Controller {
$sig = $_POST['signature'];
$resource = $_POST['resource'];
$revision = intval($_POST['revision']);
+ $resolution = (-1);
if(! $hash)
killme();
@@ -46,6 +47,11 @@ class Getfile extends \Zotlabs\Web\Controller {
killme();
}
+ if(substr($resource,-2,1) == '-') {
+ $resolution = intval(substr($resource,-1,1));
+ $resource = substr($resource,0,-2);
+ }
+
$slop = intval(get_pconfig($channel['channel_id'],'system','getfile_time_slop'));
if($slop < 1)
$slop = 3;
@@ -63,6 +69,35 @@ class Getfile extends \Zotlabs\Web\Controller {
killme();
}
+
+ if($resolution > 0) {
+ $r = q("select * from photo where resource_id = '%s' and uid = %d limit 1",
+ dbesc($resource),
+ intval($channel['channel_id'])
+ );
+ if($r) {
+ header('Content-type: ' . $r[0]['mimetype']);
+
+ if(intval($r[0]['os_storage'])) {
+ $fname = dbunescbin($r[0]['content']);
+ if(strpos($fname,'store') !== false)
+ $istream = fopen($fname,'rb');
+ else
+ $istream = fopen('store/' . $channel['channel_address'] . '/' . $fname,'rb');
+ $ostream = fopen('php://output','wb');
+ if($istream && $ostream) {
+ pipe_streams($istream,$ostream);
+ fclose($istream);
+ fclose($ostream);
+ }
+ }
+ else {
+ echo dbunescbin($r[0]['content']);
+ }
+ }
+ killme();
+ }
+
$r = attach_by_hash($resource,$channel['channel_hash'],$revision);
if(! $r['success']) {
@@ -73,7 +108,7 @@ class Getfile extends \Zotlabs\Web\Controller {
$unsafe_types = array('text/html','text/css','application/javascript');
- if(in_array($r['data']['filetype'],$unsafe_types)) {
+ if(in_array($r['data']['filetype'],$unsafe_types) && (! channel_codeallowed($channel['channel_id']))) {
header('Content-type: text/plain');
}
else {
diff --git a/Zotlabs/Module/Group.php b/Zotlabs/Module/Group.php
index 646310356..93a089d02 100644
--- a/Zotlabs/Module/Group.php
+++ b/Zotlabs/Module/Group.php
@@ -56,6 +56,7 @@ class Group extends \Zotlabs\Web\Controller {
);
if($r)
info( t('Privacy group updated.') . EOL );
+ build_sync_packet(local_channel(),null,true);
}
goaway(z_root() . '/group/' . argv(1) . '/' . argv(2));
@@ -63,7 +64,8 @@ class Group extends \Zotlabs\Web\Controller {
return;
}
- function get() {
+ function get() {
+
$change = false;
logger('mod_group: ' . \App::$cmd,LOGGER_DEBUG);
diff --git a/Zotlabs/Module/Hcard.php b/Zotlabs/Module/Hcard.php
index 93c8d3ece..912c84fd2 100644
--- a/Zotlabs/Module/Hcard.php
+++ b/Zotlabs/Module/Hcard.php
@@ -14,6 +14,8 @@ class Hcard extends \Zotlabs\Web\Controller {
return;
}
+ logger('hcard_request: ' . $which, LOGGER_DEBUG);
+
$profile = '';
$channel = \App::get_channel();
@@ -29,7 +31,20 @@ class Hcard extends \Zotlabs\Web\Controller {
$profile = $r[0]['profile_guid'];
}
- \App::$page['htmlhead'] .= '<link rel="alternate" type="application/atom+xml" href="' . z_root() . '/feed/' . $which .'" />' . "\r\n" ;
+ head_add_link( [
+ 'rel' => 'alternate',
+ 'type' => 'application/atom+xml',
+ 'title' => t('Posts and comments'),
+ 'href' => z_root() . '/feed/' . $which
+ ]);
+
+ head_add_link( [
+ 'rel' => 'alternate',
+ 'type' => 'application/atom+xml',
+ 'title' => t('Only posts'),
+ 'href' => z_root() . '/feed/' . $which . '?f=&top=1'
+ ]);
+
if(! $profile) {
$x = q("select channel_id as profile_uid from channel where channel_address = '%s' limit 1",
@@ -46,12 +61,10 @@ class Hcard extends \Zotlabs\Web\Controller {
}
- function get() {
-
- require_once('include/widgets.php');
- return widget_profile(array());
-
-
+ function get() {
+
+ $x = new \Zotlabs\Widget\Profile();
+ return $x->widget(array());
}
diff --git a/Zotlabs/Module/Help.php b/Zotlabs/Module/Help.php
index e247416d9..f1b1acaef 100644
--- a/Zotlabs/Module/Help.php
+++ b/Zotlabs/Module/Help.php
@@ -15,7 +15,7 @@ require_once('include/help.php');
class Help extends \Zotlabs\Web\Controller {
function get() {
- nav_set_selected('help');
+ nav_set_selected('Help');
if($_REQUEST['search']) {
$o .= '<div id="help-content" class="generic-content-wrapper">';
@@ -44,42 +44,42 @@ class Help extends \Zotlabs\Web\Controller {
return $o;
}
-
-
- if(argc() > 2 && argv(argc()-2) === 'assets') {
- $path = '';
- for($x = 1; $x < argc(); $x ++) {
- if(strlen($path))
- $path .= '/';
- $path .= argv($x);
- }
- $realpath = 'doc/' . $path;
- //Set the content-type header as appropriate
- $imageInfo = getimagesize($realpath);
- switch ($imageInfo[2]) {
- case IMAGETYPE_JPEG:
- header("Content-Type: image/jpeg");
- break;
- case IMAGETYPE_GIF:
- header("Content-Type: image/gif");
- break;
- case IMAGETYPE_PNG:
- header("Content-Type: image/png");
- break;
- default:
- break;
- }
- header("Content-Length: " . filesize($realpath));
+
+
+ if(argc() > 2 && argv(argc()-2) === 'assets') {
+ $path = '';
+ for($x = 1; $x < argc(); $x ++) {
+ if(strlen($path))
+ $path .= '/';
+ $path .= argv($x);
+ }
+ $realpath = 'doc/' . $path;
+ //Set the content-type header as appropriate
+ $imageInfo = getimagesize($realpath);
+ switch ($imageInfo[2]) {
+ case IMAGETYPE_JPEG:
+ header("Content-Type: image/jpeg");
+ break;
+ case IMAGETYPE_GIF:
+ header("Content-Type: image/gif");
+ break;
+ case IMAGETYPE_PNG:
+ header("Content-Type: image/png");
+ break;
+ default:
+ break;
+ }
+ header("Content-Length: " . filesize($realpath));
- // dump the picture and stop the script
- readfile($realpath);
- killme();
- }
+ // dump the picture and stop the script
+ readfile($realpath);
+ killme();
+ }
$headings = [
- 'about' => t('About'),
- 'member' => t('Members'),
- 'admin' => t('Administrators'),
+ 'about' => t('About'),
+ 'member' => t('Members'),
+ 'admin' => t('Administrators'),
'developer' => t('Developers'),
'tutorials' => t('Tutorials')
];
@@ -87,13 +87,16 @@ class Help extends \Zotlabs\Web\Controller {
if(array_key_exists(argv(1), $headings))
$heading = $headings[argv(1)];
- $content = get_help_content();
+ $content = get_help_content();
+
+ $language = determine_help_language()['language'];
return replace_macros(get_markup_template('help.tpl'), array(
- '$title' => t('$Projectname Documentation'),
+ '$title' => t('$Projectname Documentation'),
'$tocHeading' => t('Contents'),
- '$content' => $content,
- '$heading' => $heading
+ '$content' => $content,
+ '$heading' => $heading,
+ '$language' => $language
));
}
diff --git a/Zotlabs/Module/Impel.php b/Zotlabs/Module/Impel.php
index 197d9f859..77f488d26 100644
--- a/Zotlabs/Module/Impel.php
+++ b/Zotlabs/Module/Impel.php
@@ -144,18 +144,8 @@ class Impel extends \Zotlabs\Web\Controller {
// Verify ability to use html or php!!!
- $execflag = false;
-
- if($arr['mimetype'] === 'application/x-php') {
- $z = q("select account_id, account_roles, channel_pageflags from account left join channel on channel_account_id = account_id where channel_id = %d limit 1",
- intval(local_channel())
- );
-
- if($z && (($z[0]['account_roles'] & ACCOUNT_ROLE_ALLOWCODE) || ($z[0]['channel_pageflags'] & PAGE_ALLOWCODE))) {
- $execflag = true;
- }
- }
-
+ $execflag = ((intval($channel['channel_id']) == intval(local_channel()) && ($channel['channel_pageflags'] & PAGE_ALLOWCODE)) ? true : false);
+
$i = q("select id, edited, item_deleted from item where mid = '%s' and uid = %d limit 1",
dbesc($arr['mid']),
intval(local_channel())
diff --git a/Zotlabs/Module/Import.php b/Zotlabs/Module/Import.php
index 3969f25e0..2b16ff4e1 100644
--- a/Zotlabs/Module/Import.php
+++ b/Zotlabs/Module/Import.php
@@ -2,26 +2,32 @@
namespace Zotlabs\Module;
-// Import a channel, either by direct file upload or via
-// connection to original server.
-
-
require_once('include/zot.php');
require_once('include/channel.php');
require_once('include/import.php');
require_once('include/perm_upgrade.php');
-
+/**
+ * @brief Module for channel import.
+ *
+ * Import a channel, either by direct file upload or via
+ * connection to another server.
+ */
class Import extends \Zotlabs\Web\Controller {
+ /**
+ * @brief Import channel into account.
+ *
+ * @param int $account_id
+ */
function import_account($account_id) {
-
+
if(! $account_id){
- logger("import_account: No account ID supplied");
+ logger('No account ID supplied');
return;
}
-
+
$max_friends = account_service_class_fetch($account_id,'total_channels');
$max_feeds = account_service_class_fetch($account_id,'total_feeds');
$data = null;
@@ -32,35 +38,39 @@ class Import extends \Zotlabs\Web\Controller {
$filename = basename($_FILES['filename']['name']);
$filesize = intval($_FILES['filename']['size']);
$filetype = $_FILES['filename']['type'];
-
+ // import channel from file
if($src) {
-
- // This is OS specific and could also fail if your tmpdir isn't very large
- // mostly used for Diaspora which exports gzipped files.
-
+
+ // This is OS specific and could also fail if your tmpdir isn't very
+ // large mostly used for Diaspora which exports gzipped files.
+
if(strpos($filename,'.gz')){
@rename($src,$src . '.gz');
@system('gunzip ' . escapeshellarg($src . '.gz'));
}
-
+
if($filesize) {
$data = @file_get_contents($src);
}
unlink($src);
}
-
+
+ // import channel from another server
if(! $src) {
$old_address = ((x($_REQUEST,'old_address')) ? $_REQUEST['old_address'] : '');
if(! $old_address) {
- logger('mod_import: nothing to import.');
+ logger('Nothing to import.');
notice( t('Nothing to import.') . EOL);
return;
+ } else if(strpos($old_address, '@')) {
+ // if you copy the identity address from your profile page, make it work for convenience
+ $old_address = str_replace('@', '@', $old_address);
}
-
+
$email = ((x($_REQUEST,'email')) ? $_REQUEST['email'] : '');
$password = ((x($_REQUEST,'password')) ? $_REQUEST['password'] : '');
-
+
$channelname = substr($old_address,0,strpos($old_address,'@'));
$servername = substr($old_address,strpos($old_address,'@')+1);
@@ -73,6 +83,7 @@ class Import extends \Zotlabs\Web\Controller {
$api_path .= 'channel/export/basic?f=&channel=' . $channelname;
if($import_posts)
$api_path .= '&posts=1';
+
$binary = false;
$redirects = 0;
$opts = array('http_auth' => $email . ':' . $password);
@@ -85,19 +96,18 @@ class Import extends \Zotlabs\Web\Controller {
return;
}
}
-
+
if(! $data) {
- logger('mod_import: empty file.');
+ logger('Empty import file.');
notice( t('Imported file is empty.') . EOL);
return;
}
-
+
$data = json_decode($data,true);
-
- // logger('import: data: ' . print_r($data,true));
- // print_r($data);
-
-
+
+ //logger('import: data: ' . print_r($data,true));
+ //print_r($data);
+
if(! array_key_exists('compatibility',$data)) {
call_hooks('import_foreign_channel_data',$data);
if($data['handled'])
@@ -108,24 +118,23 @@ class Import extends \Zotlabs\Web\Controller {
$v1 = substr($data['compatibility']['database'],-4);
$v2 = substr(DB_UPDATE_VERSION,-4);
if($v2 > $v1) {
- $t = sprintf( t('Warning: Database versions differ by %1$d updates.'), $v2 - $v1 );
+ $t = sprintf( t('Warning: Database versions differ by %1$d updates.'), $v2 - $v1 );
notice($t);
}
- if(array_key_exists('server_role',$data['compatibility']) && $data['compatibility']['server_role'] == 'basic')
- $moving = true;
+
}
-
+
if($moving)
$seize = 1;
-
+
// import channel
-
+
$relocate = ((array_key_exists('relocate',$data)) ? $data['relocate'] : null);
if(array_key_exists('channel',$data)) {
-
+
$max_identities = account_service_class_fetch($account_id,'total_identities');
-
+
if($max_identities !== false) {
$r = q("select channel_id from channel where channel_account_id = %d",
intval($account_id)
@@ -137,46 +146,40 @@ class Import extends \Zotlabs\Web\Controller {
}
$channel = import_channel($data['channel'], $account_id, $seize);
-
}
else {
$moving = false;
$channel = \App::get_channel();
}
-
+
if(! $channel) {
- logger('mod_import: channel not found. ', print_r($channel,true));
+ logger('Channel not found. ', print_r($channel,true));
notice( t('No channel. Import failed.') . EOL);
return;
}
-
-
if(is_array($data['config'])) {
import_config($channel,$data['config']);
}
-
+
logger('import step 2');
-
-
-
if(array_key_exists('channel',$data)) {
if($data['photo']) {
require_once('include/photo/photo_driver.php');
import_channel_photo(base64url_decode($data['photo']['data']),$data['photo']['type'],$account_id,$channel['channel_id']);
}
-
+
if(is_array($data['profile']))
import_profiles($channel,$data['profile']);
}
-
+
logger('import step 3');
-
+
if(is_array($data['hubloc'])) {
import_hublocs($channel,$data['hubloc'],$seize,$moving);
}
-
+
logger('import step 4');
// create new hubloc for the new channel at this site
@@ -200,7 +203,7 @@ class Import extends \Zotlabs\Web\Controller {
);
// reset the original primary hubloc if it is being seized
-
+
if($seize) {
$r = q("update hubloc set hubloc_primary = 0 where hubloc_primary = 1 and hubloc_hash = '%s' and hubloc_url != '%s' ",
dbesc($channel['channel_hash']),
@@ -210,20 +213,18 @@ class Import extends \Zotlabs\Web\Controller {
}
logger('import step 5');
-
-
-
+
+
// import xchans and contact photos
-
+
if(array_key_exists('channel',$data) && $seize) {
-
+
// replace any existing xchan we may have on this site if we're seizing control
-
+
$r = q("delete from xchan where xchan_hash = '%s'",
dbesc($channel['channel_hash'])
);
-
$r = xchan_store_lowlevel(
[
'xchan_hash' => $channel['channel_hash'],
@@ -242,23 +243,22 @@ class Import extends \Zotlabs\Web\Controller {
'xchan_photo_date' => datetime_convert(),
'xchan_name_date' => datetime_convert()
]
- );
+ );
}
-
+
logger('import step 6');
-
-
+ // import xchans
$xchans = $data['xchan'];
if($xchans) {
foreach($xchans as $xchan) {
-
+
$hash = make_xchan_hash($xchan['xchan_guid'],$xchan['xchan_guid_sig']);
if($xchan['xchan_network'] === 'zot' && $hash !== $xchan['xchan_hash']) {
logger('forged xchan: ' . print_r($xchan,true));
continue;
}
-
+
if(! array_key_exists('xchan_hidden',$xchan)) {
$xchan['xchan_hidden'] = (($xchan['xchan_flags'] & 0x0001) ? 1 : 0);
$xchan['xchan_orphan'] = (($xchan['xchan_flags'] & 0x0002) ? 1 : 0);
@@ -268,57 +268,67 @@ class Import extends \Zotlabs\Web\Controller {
$xchan['xchan_pubforum'] = (($xchan['xchan_flags'] & 0x0020) ? 1 : 0);
$xchan['xchan_deleted'] = (($xchan['xchan_flags'] & 0x1000) ? 1 : 0);
}
-
+
$r = q("select xchan_hash from xchan where xchan_hash = '%s' limit 1",
dbesc($xchan['xchan_hash'])
);
if($r)
continue;
- create_table_from_array('xchan',$xchan);
-
+ create_table_from_array('xchan',$xchan);
+
require_once('include/photo/photo_driver.php');
- $photos = import_xchan_photo($xchan['xchan_photo_l'],$xchan['xchan_hash']);
- if($photos[4])
- $photodate = NULL_DATE;
- else
- $photodate = $xchan['xchan_photo_date'];
-
- $r = q("update xchan set xchan_photo_l = '%s', xchan_photo_m = '%s', xchan_photo_s = '%s', xchan_photo_mimetype = '%s', xchan_photo_date = '%s' where xchan_hash = '%s'",
- dbesc($photos[0]),
- dbesc($photos[1]),
- dbesc($photos[2]),
- dbesc($photos[3]),
- dbesc($photodate),
- dbesc($xchan['xchan_hash'])
- );
-
+
+ if($xchan['xchan_hash'] === $channel['channel_hash']) {
+ $r = q("update xchan set xchan_photo_l = '%s', xchan_photo_m = '%s', xchan_photo_s = '%s' where xchan_hash = '%s'",
+ dbesc(z_root() . '/photo/profile/l/' . $channel['channel_id']),
+ dbesc(z_root() . '/photo/profile/m/' . $channel['channel_id']),
+ dbesc(z_root() . '/photo/profile/s/' . $channel['channel_id']),
+ dbesc($xchan['xchan_hash'])
+ );
+ }
+ else {
+ $photos = import_xchan_photo($xchan['xchan_photo_l'],$xchan['xchan_hash']);
+ if($photos[4])
+ $photodate = NULL_DATE;
+ else
+ $photodate = $xchan['xchan_photo_date'];
+
+ $r = q("update xchan set xchan_photo_l = '%s', xchan_photo_m = '%s', xchan_photo_s = '%s', xchan_photo_mimetype = '%s', xchan_photo_date = '%s' where xchan_hash = '%s'",
+ dbesc($photos[0]),
+ dbesc($photos[1]),
+ dbesc($photos[2]),
+ dbesc($photos[3]),
+ dbesc($photodate),
+ dbesc($xchan['xchan_hash'])
+ );
+ }
}
- logger('import step 7');
+ logger('import step 7');
}
-
$friends = 0;
$feeds = 0;
-
+
// import contacts
$abooks = $data['abook'];
if($abooks) {
foreach($abooks as $abook) {
$abook_copy = $abook;
-
+
$abconfig = null;
if(array_key_exists('abconfig',$abook) && is_array($abook['abconfig']) && count($abook['abconfig']))
$abconfig = $abook['abconfig'];
-
+
unset($abook['abook_id']);
unset($abook['abook_rating']);
unset($abook['abook_rating_text']);
unset($abook['abconfig']);
unset($abook['abook_their_perms']);
unset($abook['abook_my_perms']);
+ unset($abook['abook_not_here']);
$abook['abook_account'] = $account_id;
$abook['abook_channel'] = $channel['channel_id'];
@@ -332,7 +342,11 @@ class Import extends \Zotlabs\Web\Controller {
$abook['abook_self'] = (($abook['abook_flags'] & 0x0080 ) ? 1 : 0);
$abook['abook_feed'] = (($abook['abook_flags'] & 0x0100 ) ? 1 : 0);
}
-
+
+ if(array_key_exists('abook_instance',$abook) && $abook['abook_instance'] && strpos($abook['abook_instance'],z_root()) === false) {
+ $abook['abook_not_here'] = 1;
+ }
+
if($abook['abook_self']) {
$role = get_pconfig($channel['channel_id'],'system','permissions_role');
if(($role === 'forum') || ($abook['abook_my_perms'] & PERMS_W_TAGWALL)) {
@@ -340,24 +354,24 @@ class Import extends \Zotlabs\Web\Controller {
dbesc($abook['abook_xchan'])
);
}
- }
+ }
else {
if($max_friends !== false && $friends > $max_friends)
continue;
if($max_feeds !== false && intval($abook['abook_feed']) && ($feeds > $max_feeds))
continue;
}
-
- create_table_from_array('abook',$abook);
+
+ abook_store_lowlevel($abook);
$friends ++;
if(intval($abook['abook_feed']))
$feeds ++;
translate_abook_perms_inbound($channel,$abook_copy);
-
+
if($abconfig) {
- // @fixme does not handle sync of del_abconfig
+ /// @FIXME does not handle sync of del_abconfig
foreach($abconfig as $abc) {
set_abconfig($channel['channel_id'],$abc['xchan'],$abc['cat'],$abc['k'],$abc['v']);
}
@@ -366,20 +380,21 @@ class Import extends \Zotlabs\Web\Controller {
logger('import step 8');
}
-
+
+ // import groups
$groups = $data['group'];
if($groups) {
$saved = array();
foreach($groups as $group) {
$saved[$group['hash']] = array('old' => $group['id']);
- if(array_key_exists('name',$group)) {
+ if(array_key_exists('name', $group)) {
$group['gname'] = $group['name'];
unset($group['name']);
}
unset($group['id']);
$group['uid'] = $channel['channel_id'];
- create_table_from_array('groups',$group);
+ create_table_from_array('groups', $group);
}
$r = q("select * from groups where uid = %d",
intval($channel['channel_id'])
@@ -388,10 +403,10 @@ class Import extends \Zotlabs\Web\Controller {
foreach($r as $rr) {
$saved[$rr['hash']]['new'] = $rr['id'];
}
- }
+ }
}
-
-
+
+ // import group members
$group_members = $data['group_member'];
if($group_members) {
foreach($group_members as $group_member) {
@@ -401,36 +416,36 @@ class Import extends \Zotlabs\Web\Controller {
if($x['old'] == $group_member['gid'])
$group_member['gid'] = $x['new'];
}
- create_table_from_array('group_member',$group_member);
+ create_table_from_array('group_member', $group_member);
}
}
logger('import step 9');
-
+
if(is_array($data['obj']))
import_objs($channel,$data['obj']);
-
+
if(is_array($data['likes']))
import_likes($channel,$data['likes']);
-
+
if(is_array($data['app']))
import_apps($channel,$data['app']);
-
+
if(is_array($data['chatroom']))
import_chatrooms($channel,$data['chatroom']);
-
+
if(is_array($data['conv']))
import_conv($channel,$data['conv']);
-
+
if(is_array($data['mail']))
import_mail($channel,$data['mail']);
-
+
if(is_array($data['event']))
import_events($channel,$data['event']);
-
+
if(is_array($data['event_item']))
import_items($channel,$data['event_item'],false,$relocate);
-
+
if(is_array($data['menu']))
import_menus($channel,$data['menu']);
@@ -439,56 +454,62 @@ class Import extends \Zotlabs\Web\Controller {
if(is_array($data['webpages']))
import_items($channel,$data['webpages'],false,$relocate);
-
+
$addon = array('channel' => $channel,'data' => $data);
call_hooks('import_channel',$addon);
-
+
$saved_notification_flags = notifications_off($channel['channel_id']);
-
+
if($import_posts && array_key_exists('item',$data) && $data['item'])
import_items($channel,$data['item'],false,$relocate);
-
+
notifications_on($channel['channel_id'],$saved_notification_flags);
-
-
+
if(array_key_exists('item_id',$data) && $data['item_id'])
import_item_ids($channel,$data['item_id']);
-
+
// send out refresh requests
// notify old server that it may no longer be primary.
-
+
\Zotlabs\Daemon\Master::Summon(array('Notifier','location',$channel['channel_id']));
-
+
// This will indirectly perform a refresh_all *and* update the directory
-
+
\Zotlabs\Daemon\Master::Summon(array('Directory', $channel['channel_id']));
-
-
+
+
notice( t('Import completed.') . EOL);
-
+
change_channel($channel['channel_id']);
-
+
goaway(z_root() . '/network' );
-
}
-
-
+
+ /**
+ * @brief Handle POST action on channel import page.
+ */
function post() {
-
$account_id = get_account_id();
if(! $account_id)
return;
-
+
+ check_form_security_token_redirectOnErr('/import', 'channel_import');
+
$this->import_account($account_id);
}
-
+
+ /**
+ * @brief Generate channel import page.
+ *
+ * @return string with parsed HTML.
+ */
function get() {
-
+
if(! get_account_id()) {
- notice( t('You must be logged in to use this feature.'));
+ notice( t('You must be logged in to use this feature.') . EOL);
return '';
}
-
+
$o = replace_macros(get_markup_template('channel_import.tpl'),array(
'$title' => t('Import Channel'),
'$desc' => t('Use this form to import an existing channel from a different server/hub. You may retrieve the channel identity from the old server/hub via the network or provide an export file.'),
@@ -501,14 +522,14 @@ class Import extends \Zotlabs\Web\Controller {
'$label_import_primary' => t('Make this hub my primary location'),
'$label_import_moving' => t('Move this channel (disable all previous locations)'),
'$label_import_posts' => t('Import a few months of posts if possible (limited by available memory'),
- '$pleasewait' => t('This process may take several minutes to complete. Please submit the form only once and leave this page open until finished.'),
+ '$pleasewait' => t('This process may take several minutes to complete. Please submit the form only once and leave this page open until finished.'),
'$email' => '',
'$pass' => '',
+ '$form_security_token' => get_form_security_token('channel_import'),
'$submit' => t('Submit')
));
-
+
return $o;
-
}
-
+
}
diff --git a/Zotlabs/Module/Import_items.php b/Zotlabs/Module/Import_items.php
index f20cbfe7e..c2b2506fe 100644
--- a/Zotlabs/Module/Import_items.php
+++ b/Zotlabs/Module/Import_items.php
@@ -3,54 +3,60 @@ namespace Zotlabs\Module;
require_once('include/import.php');
-
+/**
+ * @brief Module for importing items.
+ *
+ * Import existing posts and content from an export file.
+ */
class Import_items extends \Zotlabs\Web\Controller {
function post() {
-
+
if(! local_channel())
return;
-
+
+ check_form_security_token_redirectOnErr('/import_items', 'import_items');
+
$data = null;
-
+
$src = $_FILES['filename']['tmp_name'];
$filename = basename($_FILES['filename']['name']);
$filesize = intval($_FILES['filename']['size']);
$filetype = $_FILES['filename']['type'];
-
+
if($src) {
// This is OS specific and could also fail if your tmpdir isn't very large
// mostly used for Diaspora which exports gzipped files.
-
+
if(strpos($filename,'.gz')){
@rename($src,$src . '.gz');
@system('gunzip ' . escapeshellarg($src . '.gz'));
}
-
+
if($filesize) {
$data = @file_get_contents($src);
}
unlink($src);
}
-
+
if(! $src) {
-
+
$old_address = ((x($_REQUEST,'old_address')) ? $_REQUEST['old_address'] : '');
-
+
if(! $old_address) {
- logger('mod_import: nothing to import.');
+ logger('Nothing to import.');
notice( t('Nothing to import.') . EOL);
return;
}
-
+
$email = ((x($_REQUEST,'email')) ? $_REQUEST['email'] : '');
$password = ((x($_REQUEST,'password')) ? $_REQUEST['password'] : '');
-
+
$year = ((x($_REQUEST,'year')) ? $_REQUEST['year'] : '');
-
+
$channelname = substr($old_address,0,strpos($old_address,'@'));
$servername = substr($old_address,strpos($old_address,'@')+1);
-
+
$scheme = 'https://';
$api_path = '/api/red/channel/export/items?f=&channel=' . $channelname . '&year=' . intval($year);
$binary = false;
@@ -64,68 +70,66 @@ class Import_items extends \Zotlabs\Web\Controller {
$data = $ret['body'];
else
notice( t('Unable to download data from old server') . EOL);
-
}
-
+
if(! $data) {
- logger('mod_import: empty file.');
+ logger('Empty file.');
notice( t('Imported file is empty.') . EOL);
return;
}
-
- $data = json_decode($data,true);
-
- // logger('import: data: ' . print_r($data,true));
- // print_r($data);
-
+
+ $data = json_decode($data, true);
+
+ //logger('import: data: ' . print_r($data,true));
+ //print_r($data);
+
if(! is_array($data))
return;
-
+
if(array_key_exists('compatibility',$data) && array_key_exists('database',$data['compatibility'])) {
$v1 = substr($data['compatibility']['database'],-4);
$v2 = substr(DB_UPDATE_VERSION,-4);
if($v2 > $v1) {
- $t = sprintf( t('Warning: Database versions differ by %1$d updates.'), $v2 - $v1 );
- notice($t);
+ $t = sprintf( t('Warning: Database versions differ by %1$d updates.'), $v2 - $v1 );
+ notice($t . EOL);
}
}
-
+
$channel = \App::get_channel();
-
-
+
if(array_key_exists('item',$data) && $data['item']) {
import_items($channel,$data['item'],false,((array_key_exists('relocate',$data)) ? $data['relocate'] : null));
}
-
+
if(array_key_exists('item_id',$data) && $data['item_id']) {
import_item_ids($channel,$data['item_id']);
}
-
+
info( t('Import completed') . EOL);
- return;
}
-
-
-
-
+
+
+ /**
+ * @brief Generate item import page.
+ *
+ * @return string with parsed HTML.
+ */
function get() {
-
+
if(! local_channel()) {
notice( t('Permission denied') . EOL);
return login();
}
-
- $o = replace_macros(get_markup_template('item_import.tpl'),array(
+
+ $o = replace_macros(get_markup_template('item_import.tpl'), array(
'$title' => t('Import Items'),
'$desc' => t('Use this form to import existing posts and content from an export file.'),
'$label_filename' => t('File to Upload'),
+ '$form_security_token' => get_form_security_token('import_items'),
'$submit' => t('Submit')
));
-
+
return $o;
-
}
-
-
-
+
}
diff --git a/Zotlabs/Module/Invite.php b/Zotlabs/Module/Invite.php
index 6b6f80a31..0bcd1c1fa 100644
--- a/Zotlabs/Module/Invite.php
+++ b/Zotlabs/Module/Invite.php
@@ -49,7 +49,7 @@ class Invite extends \Zotlabs\Web\Controller {
if(! $recip)
continue;
- if(! valid_email($recip)) {
+ if(! validate_email($recip)) {
notice( sprintf( t('%s : Not a valid email address.'), $recip) . EOL);
continue;
}
@@ -88,12 +88,14 @@ class Invite extends \Zotlabs\Web\Controller {
}
- function get() {
+ function get() {
if(! local_channel()) {
notice( t('Permission denied.') . EOL);
return;
}
+
+ nav_set_selected('Invite');
$tpl = get_markup_template('invite.tpl');
$invonly = false;
diff --git a/Zotlabs/Module/Item.php b/Zotlabs/Module/Item.php
index 4725ecb38..b54de0fb9 100644
--- a/Zotlabs/Module/Item.php
+++ b/Zotlabs/Module/Item.php
@@ -33,7 +33,7 @@ class Item extends \Zotlabs\Web\Controller {
// This will change. Figure out who the observer is and whether or not
// they have permission to post here. Else ignore the post.
- if((! local_channel()) && (! remote_channel()) && (! x($_REQUEST,'commenter')))
+ if((! local_channel()) && (! remote_channel()) && (! x($_REQUEST,'anonname')))
return;
$uid = local_channel();
@@ -77,7 +77,7 @@ class Item extends \Zotlabs\Web\Controller {
call_hooks('post_local_start', $_REQUEST);
- // logger('postvars ' . print_r($_REQUEST,true), LOGGER_DATA);
+ // logger('postvars ' . print_r($_REQUEST,true), LOGGER_DATA);
$api_source = ((x($_REQUEST,'api_source') && $_REQUEST['api_source']) ? true : false);
@@ -110,6 +110,7 @@ class Item extends \Zotlabs\Web\Controller {
$preview = ((x($_REQUEST,'preview')) ? intval($_REQUEST['preview']) : 0);
$categories = ((x($_REQUEST,'category')) ? escape_tags($_REQUEST['category']) : '');
$webpage = ((x($_REQUEST,'webpage')) ? intval($_REQUEST['webpage']) : 0);
+ $item_obscured = ((x($_REQUEST,'obscured')) ? intval($_REQUEST['obscured']) : 0);
$pagetitle = ((x($_REQUEST,'pagetitle')) ? escape_tags(urlencode($_REQUEST['pagetitle'])) : '');
$layout_mid = ((x($_REQUEST,'layout_mid')) ? escape_tags($_REQUEST['layout_mid']): '');
$plink = ((x($_REQUEST,'permalink')) ? escape_tags($_REQUEST['permalink']) : '');
@@ -204,10 +205,29 @@ class Item extends \Zotlabs\Web\Controller {
$route = $parent_item['route'];
}
+
+ $moderated = false;
- if(! $observer)
+ if(! $observer) {
$observer = \App::get_observer();
+ if(! $observer) {
+ $observer = anon_identity_init($_REQUEST);
+ if($observer) {
+ $moderated = true;
+ $remote_xchan = $remote_observer = $observer;
+ }
+ }
+ }
+ if(! $observer) {
+ notice( t('Permission denied.') . EOL) ;
+ if($api_source)
+ return ( [ 'success' => false, 'message' => 'permission denied' ] );
+ if(x($_REQUEST,'return'))
+ goaway(z_root() . "/" . $return_path );
+ killme();
+ }
+
if($parent) {
logger('mod_item: item_post parent=' . $parent);
$can_comment = false;
@@ -311,7 +331,7 @@ class Item extends \Zotlabs\Web\Controller {
$walltowall = false;
$walltowall_comment = false;
- if($remote_xchan)
+ if($remote_xchan && ! $moderated)
$observer = $remote_observer;
if($observer) {
@@ -471,34 +491,16 @@ class Item extends \Zotlabs\Web\Controller {
if(! $mimetype)
$mimetype = 'text/bbcode';
+
+ $execflag = ((intval($uid) == intval($profile_uid)
+ && ($channel['channel_pageflags'] & PAGE_ALLOWCODE)) ? true : false);
+
if($preview) {
- $body = z_input_filter($profile_uid,$body,$mimetype);
+ $body = z_input_filter($body,$mimetype,$execflag);
}
-
// Verify ability to use html or php!!!
- $execflag = false;
-
- if($mimetype !== 'text/bbcode') {
- $z = q("select account_id, account_roles, channel_pageflags from account left join channel on channel_account_id = account_id where channel_id = %d limit 1",
- intval($profile_uid)
- );
- if($z && (($z[0]['account_roles'] & ACCOUNT_ROLE_ALLOWCODE) || ($z[0]['channel_pageflags'] & PAGE_ALLOWCODE))) {
- if($uid && (get_account_id() == $z[0]['account_id'])) {
- $execflag = true;
- }
- else {
- notice( t('Executable content type not permitted to this channel.') . EOL);
- if($api_source)
- return ( [ 'success' => false, 'message' => 'forbidden content type' ] );
- if(x($_REQUEST,'return'))
- goaway(z_root() . "/" . $return_path );
- killme();
- }
- }
- }
-
$gacl = $acl->get();
$str_contact_allow = $gacl['allow_cid'];
$str_group_allow = $gacl['allow_gid'];
@@ -509,48 +511,20 @@ class Item extends \Zotlabs\Web\Controller {
require_once('include/text.php');
- // Markdown doesn't work correctly. Do not re-enable unless you're willing to fix it and support it.
-
- // Sample that will probably give you grief - you must preserve the linebreaks
- // and provide the correct markdown interpretation and you cannot allow unfiltered HTML
-
- // Markdown
- // ========
- //
- // **bold** abcde
- // fghijkl
- // *italic*
- // <img src="javascript:alert('hacked');" />
-
- // if($uid && $uid == $profile_uid && feature_enabled($uid,'markdown')) {
- // require_once('include/markdown.php');
- // $body = escape_tags(trim($body));
- // $body = str_replace("\n",'<br />', $body);
- // $body = preg_replace_callback('/\[share(.*?)\]/ism','\share_shield',$body);
- // $body = markdown_to_bb($body,true);
- // $body = preg_replace_callback('/\[share(.*?)\]/ism','\share_unshield',$body);
- // }
+ if($uid && $uid == $profile_uid && feature_enabled($uid,'markdown')) {
+ require_once('include/markdown.php');
+ $body = preg_replace_callback('/\[share(.*?)\]/ism','\share_shield',$body);
+ $body = markdown_to_bb($body,true,['preserve_lf' => true]);
+ $body = preg_replace_callback('/\[share(.*?)\]/ism','\share_unshield',$body);
+
+ }
// BBCODE alert: the following functions assume bbcode input
// and will require alternatives for alternative content-types (text/html, text/markdown, text/plain, etc.)
// we may need virtual or template classes to implement the possible alternatives
-
- // Work around doubled linefeeds in Tinymce 3.5b2
- // First figure out if it's a status post that would've been
- // created using tinymce. Otherwise leave it alone.
-
- $plaintext = true;
-
- // $plaintext = ((feature_enabled($profile_uid,'richtext')) ? false : true);
- // if((! $parent) && (! $api_source) && (! $plaintext)) {
- // $body = fix_mce_lf($body);
- // }
-
-
-
+
// If we're sending a private top-level message with a single @-taggable channel as a recipient, @-tag it, if our pconfig is set.
-
-
+
if((! $parent) && (get_pconfig($profile_uid,'system','tagifonlyrecip')) && (substr_count($str_contact_allow,'<') == 1) && ($str_group_allow == '') && ($str_contact_deny == '') && ($str_group_deny == '')) {
$x = q("select abook_id, abconfig.v from abook left join abconfig on abook_xchan = abconfig.xchan and abook_channel = abconfig.chan and cat= 'their_perms' and abconfig.k = 'tag_deliver' and abconfig.v = 1 and abook_xchan = '%s' and abook_channel = %d limit 1",
dbesc(str_replace(array('<','>'),array('',''),$str_contact_allow)),
@@ -632,7 +606,7 @@ class Item extends \Zotlabs\Web\Controller {
$attach_link = '';
$hash = substr($mtch,0,strpos($mtch,','));
$rev = intval(substr($mtch,strpos($mtch,',')));
- $r = attach_by_hash_nodata($hash,$rev);
+ $r = attach_by_hash_nodata($hash, $observer['xchan_hash'], $rev);
if($r['success']) {
$attachments[] = array(
'href' => z_root() . '/attach/' . $r['data']['hash'],
@@ -657,14 +631,23 @@ class Item extends \Zotlabs\Web\Controller {
// BBCODE end alert
if(strlen($categories)) {
+
$cats = explode(',',$categories);
foreach($cats as $cat) {
+
+ if($webpage == ITEM_TYPE_CARD) {
+ $catlink = z_root() . '/cards/' . $channel['channel_address'] . '?f=&cat=' . urlencode(trim($cat));
+ }
+ else {
+ $catlink = $owner_xchan['xchan_url'] . '?f=&cat=' . urlencode(trim($cat));
+ }
+
$post_tags[] = array(
'uid' => $profile_uid,
'ttype' => TERM_CATEGORY,
'otype' => TERM_OBJ_POST,
'term' => trim($cat),
- 'url' => $owner_xchan['xchan_url'] . '?f=&cat=' . urlencode(trim($cat))
+ 'url' => $catlink
);
}
}
@@ -683,7 +666,7 @@ class Item extends \Zotlabs\Web\Controller {
foreach($t as $t1) {
$post_tags[] = array(
'uid' => $profile_uid,
- 'ttype' => $t1['type'],
+ 'ttype' => $t1['ttype'],
'otype' => TERM_OBJ_POST,
'term' => $t1['term'],
'url' => $t1['url'],
@@ -732,7 +715,9 @@ class Item extends \Zotlabs\Web\Controller {
if($parent_item)
$parent_mid = $parent_item['mid'];
-
+
+
+
// Fallback so that we alway have a thr_parent
if(!$thr_parent)
@@ -742,6 +727,21 @@ class Item extends \Zotlabs\Web\Controller {
$item_thread_top = ((! $parent) ? 1 : 0);
+
+ // fix permalinks for cards
+
+ if($webpage == ITEM_TYPE_CARD) {
+ $plink = z_root() . '/cards/' . $channel['channel_address'] . '/' . (($pagetitle) ? $pagetitle : substr($mid,0,16));
+ }
+ if(($parent_item) && ($parent_item['item_type'] == ITEM_TYPE_CARD)) {
+ $r = q("select v from iconfig where iconfig.cat = 'system' and iconfig.k = 'CARD' and iconfig.iid = %d limit 1",
+ intval($parent_item['id'])
+ );
+ if($r) {
+ $plink = z_root() . '/cards/' . $channel['channel_address'] . '/' . $r[0]['v'];
+ }
+ }
+
if ((! $plink) && ($item_thread_top)) {
$plink = z_root() . '/channel/' . $channel['channel_address'] . '/?f=&mid=' . $mid;
}
@@ -816,7 +816,7 @@ class Item extends \Zotlabs\Web\Controller {
$datarray['owner'] = $owner_xchan;
$datarray['author'] = $observer;
$datarray['attach'] = json_encode($datarray['attach']);
- $o = conversation($a,array($datarray),'search',false,'preview');
+ $o = conversation(array($datarray),'search',false,'preview');
// logger('preview: ' . $o, LOGGER_DEBUG);
echo json_encode(array('preview' => $o));
killme();
@@ -859,20 +859,8 @@ class Item extends \Zotlabs\Web\Controller {
}
- if(mb_strlen($datarray['title']) > 255)
- $datarray['title'] = mb_substr($datarray['title'],0,255);
-
- if(array_key_exists('item_private',$datarray) && $datarray['item_private']) {
-
- $datarray['body'] = trim(z_input_filter($datarray['uid'],$datarray['body'],$datarray['mimetype']));
-
- if($uid) {
- if($channel['channel_hash'] === $datarray['author_xchan']) {
- $datarray['sig'] = base64url_encode(rsa_sign($datarray['body'],$channel['channel_prvkey']));
- $datarray['item_verified'] = 1;
- }
- }
- }
+ if(mb_strlen($datarray['title']) > 191)
+ $datarray['title'] = mb_substr($datarray['title'],0,191);
if($webpage) {
Zlib\IConfig::Set($datarray,'system', webpage_to_namespace($webpage),
@@ -889,7 +877,17 @@ class Item extends \Zotlabs\Web\Controller {
$x = item_store_update($datarray,$execflag);
- item_create_edit_activity($x);
+ // We only need edit activities for other federated protocols
+ // which do not support edits natively. While this does federate
+ // edits, it presents a number of issues locally - such as #757 and #758.
+ // The SQL check for an edit activity would not perform that well so to fix these issues
+ // requires an additional item flag (perhaps 'item_edit_activity') that we can add to the
+ // query for searches and notifications.
+
+ // For now we'll just forget about trying to make edits work on network protocols that
+ // don't support them.
+
+ // item_create_edit_activity($x);
if(! $parent) {
$r = q("select * from item where id = %d",
@@ -928,6 +926,11 @@ class Item extends \Zotlabs\Web\Controller {
if($parent) {
+ // prevent conversations which you are involved from being expired
+
+ if(local_channel())
+ retain_item($parent);
+
// only send comment notification if this is a wall-to-wall comment,
// otherwise it will happen during delivery
@@ -1015,6 +1018,10 @@ class Item extends \Zotlabs\Web\Controller {
\Zotlabs\Daemon\Master::Summon(array('Notifier', $notify_type, $post_id));
logger('post_complete');
+
+ if($moderated) {
+ info(t('Your comment is awaiting approval.') . EOL);
+ }
// figure out how to return, depending on from whence we came
@@ -1070,21 +1077,28 @@ class Item extends \Zotlabs\Web\Controller {
// if this is a different page type or it's just a local delete
// but not by the item author or owner, do a simple deletion
-
+
+ $complex = false;
+
if(intval($i[0]['item_type']) || ($local_delete && (! $can_delete))) {
drop_item($i[0]['id']);
}
else {
// complex deletion that needs to propagate and be performed in phases
drop_item($i[0]['id'],true,DROPITEM_PHASE1);
- $r = q("select * from item where id = %d",
- intval($i[0]['id'])
- );
- if($r) {
- xchan_query($r);
- $sync_item = fetch_post_tags($r);
- build_sync_packet($i[0]['uid'],array('item' => array(encode_item($sync_item[0],true))));
- }
+ $complex = true;
+ }
+
+ $r = q("select * from item where id = %d",
+ intval($i[0]['id'])
+ );
+ if($r) {
+ xchan_query($r);
+ $sync_item = fetch_post_tags($r);
+ build_sync_packet($i[0]['uid'],array('item' => array(encode_item($sync_item[0],true))));
+ }
+
+ if($complex) {
tag_deliver($i[0]['uid'],$i[0]['id']);
}
}
diff --git a/Zotlabs/Module/Lang.php b/Zotlabs/Module/Lang.php
index 69f10fe6d..0e5d85d05 100644
--- a/Zotlabs/Module/Lang.php
+++ b/Zotlabs/Module/Lang.php
@@ -5,6 +5,7 @@ namespace Zotlabs\Module;
class Lang extends \Zotlabs\Web\Controller {
function get() {
+ nav_set_selected('Language');
return lang_selector();
}
diff --git a/Zotlabs/Module/Layouts.php b/Zotlabs/Module/Layouts.php
index c07f65ce1..34d754029 100644
--- a/Zotlabs/Module/Layouts.php
+++ b/Zotlabs/Module/Layouts.php
@@ -125,6 +125,7 @@ class Layouts extends \Zotlabs\Web\Controller {
'hide_weblink' => true,
'hide_attach' => true,
'hide_preview' => true,
+ 'disable_comments' => true,
'ptlabel' => t('Layout Name'),
'profile_uid' => intval($owner),
'expanded' => true,
diff --git a/Zotlabs/Module/Like.php b/Zotlabs/Module/Like.php
index 5ce8ec7f0..b104a5f5f 100644
--- a/Zotlabs/Module/Like.php
+++ b/Zotlabs/Module/Like.php
@@ -255,7 +255,7 @@ class Like extends \Zotlabs\Web\Controller {
// get the item. Allow linked photos (which are normally hidden) to be liked
$r = q("SELECT * FROM item WHERE id = %d
- and item_type = 0 and item_deleted = 0 and item_unpublished = 0
+ and (item_type = 0 or item_type = 6) and item_deleted = 0 and item_unpublished = 0
and item_delayed = 0 and item_pending_remove = 0 and item_blocked = 0 LIMIT 1",
intval($item_id)
);
@@ -373,6 +373,10 @@ class Like extends \Zotlabs\Web\Controller {
$links = array(array('rel' => 'alternate','type' => 'text/html', 'href' => $item['plink']));
$objtype = (($item['resource_type'] === 'photo') ? ACTIVITY_OBJ_PHOTO : ACTIVITY_OBJ_NOTE );
+
+ if($objtype === ACTIVITY_OBJ_NOTE && (! intval($item['item_thread_top'])))
+ $objtype = ACTIVITY_OBJ_COMMENT;
+
$body = $item['body'];
@@ -500,6 +504,11 @@ class Like extends \Zotlabs\Web\Controller {
$post = item_store($arr);
$post_id = $post['item_id'];
+
+ // save the conversation from expiration
+
+ if(local_channel() && array_key_exists('item',$post) && (intval($post['item']['id']) != intval($post['item']['parent'])))
+ retain_item($post['item']['parent']);
$arr['id'] = $post_id;
diff --git a/Zotlabs/Module/Linkinfo.php b/Zotlabs/Module/Linkinfo.php
index 8f8231c49..78c34583e 100644
--- a/Zotlabs/Module/Linkinfo.php
+++ b/Zotlabs/Module/Linkinfo.php
@@ -95,7 +95,7 @@ class Linkinfo extends \Zotlabs\Web\Controller {
echo $arr['text'];
killme();
}
-
+
if($process_oembed) {
$x = oembed_process($url);
if($x) {
diff --git a/Zotlabs/Module/Lockview.php b/Zotlabs/Module/Lockview.php
index fc7d5c7c8..466d16997 100644
--- a/Zotlabs/Module/Lockview.php
+++ b/Zotlabs/Module/Lockview.php
@@ -72,7 +72,7 @@ class Lockview extends \Zotlabs\Web\Controller {
}
if($uid != local_channel()) {
- echo '<li>' . t('Remote privacy information not available.') . '</li>';
+ echo '<div class="dropdown-item">' . t('Remote privacy information not available.') . '</div>';
killme();
}
@@ -84,7 +84,7 @@ class Lockview extends \Zotlabs\Web\Controller {
// as unknown specific recipients. The sender will have the visibility list and will fall through to the
// next section.
- echo '<li>' . translate_scope((! $item['public_policy']) ? 'specific' : $item['public_policy']) . '</li>';
+ echo '<div class="dropdown-item">' . translate_scope((! $item['public_policy']) ? 'specific' : $item['public_policy']) . '</div>';
killme();
}
@@ -93,7 +93,7 @@ class Lockview extends \Zotlabs\Web\Controller {
$deny_users = expand_acl($item['deny_cid']);
$deny_groups = expand_acl($item['deny_gid']);
- $o = '<li>' . t('Visible to:') . '</li>';
+ $o = '<div class="dropdown-item">' . t('Visible to:') . '</div>';
$l = array();
stringify_array_elms($allowed_groups,true);
@@ -114,24 +114,24 @@ class Lockview extends \Zotlabs\Web\Controller {
$r = q("SELECT profile_name FROM profile WHERE profile_guid IN ( " . implode(', ', $profile_groups) . " )");
if($r)
foreach($r as $rr)
- $l[] = '<li><b>' . t('Profile','acl') . ' ' . $rr['profile_name'] . '</b></li>';
+ $l[] = '<div class="dropdown-item"><b>' . t('Profile','acl') . ' ' . $rr['profile_name'] . '</b></div>';
}
if(count($allowed_groups)) {
$r = q("SELECT gname FROM groups WHERE hash IN ( " . implode(', ', $allowed_groups) . " )");
if($r)
foreach($r as $rr)
- $l[] = '<li><b>' . $rr['gname'] . '</b></li>';
+ $l[] = '<div class="dropdown-item"><b>' . $rr['gname'] . '</b></div>';
}
if(count($allowed_users)) {
$r = q("SELECT xchan_name FROM xchan WHERE xchan_hash IN ( " . implode(', ',$allowed_users) . " )");
if($r)
foreach($r as $rr)
- $l[] = '<li>' . $rr['xchan_name'] . '</li>';
+ $l[] = '<div class="dropdown-item">' . $rr['xchan_name'] . '</div>';
if($atokens) {
foreach($atokens as $at) {
if(in_array("'" . $at['xchan_hash'] . "'",$allowed_users)) {
- $l[] = '<li>' . $at['xchan_name'] . '</li>';
+ $l[] = '<div class="dropdown-item">' . $at['xchan_name'] . '</div>';
}
}
}
@@ -150,7 +150,7 @@ class Lockview extends \Zotlabs\Web\Controller {
$r = q("SELECT profile_name FROM profile WHERE profile_guid IN ( " . implode(', ', $profile_groups) . " )");
if($r)
foreach($r as $rr)
- $l[] = '<li><b><strike>' . t('Profile','acl') . ' ' . $rr['profile_name'] . '</strike></b></li>';
+ $l[] = '<div class="dropdown-item"><b><strike>' . t('Profile','acl') . ' ' . $rr['profile_name'] . '</strike></b></div>';
}
@@ -159,18 +159,18 @@ class Lockview extends \Zotlabs\Web\Controller {
$r = q("SELECT gname FROM groups WHERE hash IN ( " . implode(', ', $deny_groups) . " )");
if($r)
foreach($r as $rr)
- $l[] = '<li><b><strike>' . $rr['gname'] . '</strike></b></li>';
+ $l[] = '<div class="dropdown-item"><b><strike>' . $rr['gname'] . '</strike></b></div>';
}
if(count($deny_users)) {
$r = q("SELECT xchan_name FROM xchan WHERE xchan_hash IN ( " . implode(', ', $deny_users) . " )");
if($r)
foreach($r as $rr)
- $l[] = '<li><strike>' . $rr['xchan_name'] . '</strike></li>';
+ $l[] = '<div class="dropdown-item"><strike>' . $rr['xchan_name'] . '</strike></div>';
if($atokens) {
foreach($atokens as $at) {
if(in_array("'" . $at['xchan_hash'] . "'",$deny_users)) {
- $l[] = '<li><strike>' . $at['xchan_name'] . '</strike></li>';
+ $l[] = '<div class="dropdown-item"><strike>' . $at['xchan_name'] . '</strike></div>';
}
}
}
diff --git a/Zotlabs/Module/Logout.php b/Zotlabs/Module/Logout.php
new file mode 100644
index 000000000..6aa11d110
--- /dev/null
+++ b/Zotlabs/Module/Logout.php
@@ -0,0 +1,12 @@
+<?php
+
+namespace Zotlabs\Module;
+
+class Logout extends \Zotlabs\Web\Controller {
+
+ function init() {
+ \App::$session->nuke();
+ goaway(z_root());
+
+ }
+} \ No newline at end of file
diff --git a/Zotlabs/Module/Magic.php b/Zotlabs/Module/Magic.php
index 9ee5f9324..879085f96 100644
--- a/Zotlabs/Module/Magic.php
+++ b/Zotlabs/Module/Magic.php
@@ -17,6 +17,7 @@ class Magic extends \Zotlabs\Web\Controller {
$dest = ((x($_REQUEST,'dest')) ? $_REQUEST['dest'] : '');
$test = ((x($_REQUEST,'test')) ? intval($_REQUEST['test']) : 0);
$rev = ((x($_REQUEST,'rev')) ? intval($_REQUEST['rev']) : 0);
+ $owa = ((x($_REQUEST,'owa')) ? intval($_REQUEST['owa']) : 0);
$delegate = ((x($_REQUEST,'delegate')) ? $_REQUEST['delegate'] : '');
$parsed = parse_url($dest);
@@ -132,12 +133,32 @@ class Magic extends \Zotlabs\Web\Controller {
if(local_channel()) {
$channel = \App::get_channel();
+ // OpenWebAuth
+
+ if($owa) {
+
+ $headers = [];
+ $headers['Accept'] = 'application/x-zot+json' ;
+ $headers['X-Open-Web-Auth'] = random_string();
+ $headers = \Zotlabs\Web\HTTPSig::create_sig('',$headers,$channel['channel_prvkey'],
+ 'acct:' . $channel['channel_address'] . '@' . \App::get_hostname(),false,true,'sha512');
+ $x = z_fetch_url($basepath . '/owa',false,$redirects,[ 'headers' => $headers ]);
+
+ if($x['success']) {
+ $j = json_decode($x['body'],true);
+ if($j['success'] && $j['token']) {
+ $x = strpbrk($dest,'?&');
+ $args = (($x) ? '&owt=' . $j['token'] : '?f=&owt=' . $j['token']) . (($delegate) ? '&delegate=1' : '');
+
+ goaway($dest . $args);
+ }
+ }
+ goaway($dest);
+ }
+
+
$token = random_string();
- $token_sig = base64url_encode(rsa_sign($token,$channel['channel_prvkey']));
-
- $channel['token'] = $token;
- $channel['token_sig'] = $token_sig;
-
+
\Zotlabs\Zot\Verify::create('auth',$channel['channel_id'],$token,$x[0]['hubloc_url']);
$target_url = $x[0]['hubloc_callback'] . '/?f=&auth=' . urlencode(channel_reddress($channel))
diff --git a/Zotlabs/Module/Mail.php b/Zotlabs/Module/Mail.php
index 459ce5acf..12f3b8152 100644
--- a/Zotlabs/Module/Mail.php
+++ b/Zotlabs/Module/Mail.php
@@ -22,32 +22,40 @@ class Mail extends \Zotlabs\Web\Controller {
$recipient = ((x($_REQUEST,'messageto')) ? notags(trim($_REQUEST['messageto'])) : '');
$rstr = ((x($_REQUEST,'messagerecip')) ? notags(trim($_REQUEST['messagerecip'])) : '');
$preview = ((x($_REQUEST,'preview')) ? intval($_REQUEST['preview']) : 0);
- $expires = ((x($_REQUEST,'expires')) ? datetime_convert(date_default_timezone_get(),'UTC', $_REQUEST['expires']) : NULL_DATE);
+ $expires = ((x($_REQUEST,'expires')) ? datetime_convert(date_default_timezone_get(),'UTC', $_REQUEST['expires']) : NULL_DATE);
+ $raw = ((x($_REQUEST,'raw')) ? intval($_REQUEST['raw']) : 0);
+ $mimetype = ((x($_REQUEST,'mimetype')) ? notags(trim($_REQUEST['mimetype'])) : 'text/bbcode');
if($preview) {
- $body = cleanup_bbcode($body);
- $results = linkify_tags($a, $body, local_channel());
+ if($raw) {
+ $body = mail_prepare_binary(['id' => 'M0']);
+ echo json_encode(['preview' => $body]);
+ }
+ else {
+ $body = cleanup_bbcode($body);
+ $results = linkify_tags($a, $body, local_channel());
- if(preg_match_all('/(\[attachment\](.*?)\[\/attachment\])/',$body,$match)) {
- $attachments = array();
- foreach($match[2] as $mtch) {
- $hash = substr($mtch,0,strpos($mtch,','));
- $rev = intval(substr($mtch,strpos($mtch,',')));
- $r = attach_by_hash_nodata($hash,get_observer_hash(),$rev);
- if($r['success']) {
- $attachments[] = array(
- 'href' => z_root() . '/attach/' . $r['data']['hash'],
- 'length' => $r['data']['filesize'],
- 'type' => $r['data']['filetype'],
- 'title' => urlencode($r['data']['filename']),
- 'revision' => $r['data']['revision']
- );
+ if(preg_match_all('/(\[attachment\](.*?)\[\/attachment\])/',$body,$match)) {
+ $attachments = array();
+ foreach($match[2] as $mtch) {
+ $hash = substr($mtch,0,strpos($mtch,','));
+ $rev = intval(substr($mtch,strpos($mtch,',')));
+ $r = attach_by_hash_nodata($hash,get_observer_hash(),$rev);
+ if($r['success']) {
+ $attachments[] = array(
+ 'href' => z_root() . '/attach/' . $r['data']['hash'],
+ 'length' => $r['data']['filesize'],
+ 'type' => $r['data']['filetype'],
+ 'title' => urlencode($r['data']['filename']),
+ 'revision' => $r['data']['revision']
+ );
+ }
+ $body = trim(str_replace($match[1],'',$body));
}
- $body = trim(str_replace($match[1],'',$body));
}
+ echo json_encode(['preview' => zidify_links(smilies(bbcode($body)))]);
}
- echo json_encode(['preview' => zidify_links(smilies(bbcode($body)))]);
killme();
}
@@ -102,36 +110,10 @@ class Mail extends \Zotlabs\Web\Controller {
}
}
- // if(feature_enabled(local_channel(),'richtext')) {
- // $body = fix_mce_lf($body);
- // }
-
require_once('include/text.php');
linkify_tags($a, $body, local_channel());
- // I don't think this is used any more.
-
- if($preview) {
- $mail = [
- 'mailbox' => 'outbox',
- 'id' => 0,
- 'mid' => 'M0',
- 'from_name' => $channel['xchan_name'],
- 'from_url' => $channel['xchan_url'],
- 'from_photo' => $channel['xchan_photo_s'],
- 'subject' => zidify_links(smilies(bbcode($subject))),
- 'body' => zidify_links(smilies(bbcode($body))),
- 'attachments' => '',
- 'can_recall' => false,
- 'is_recalled' => '',
- 'date' => datetime_convert('UTC',date_default_timezone_get(),$message['created'], 'c')
- ];
-
- echo replace_macros(get_markup_template('mail_conv.tpl'), [ '$mail' => $mail ] );
- killme();
- }
-
if(! $recipient) {
notice('No recipient found.');
\App::$argc = 2;
@@ -141,7 +123,7 @@ class Mail extends \Zotlabs\Web\Controller {
// We have a local_channel, let send_message use the session channel and save a lookup
- $ret = send_message(0, $recipient, $body, $subject, $replyto, $expires);
+ $ret = send_message(0, $recipient, $body, $subject, $replyto, $expires, $mimetype, $raw);
if($ret['success']) {
xchan_mail_query($ret['mail']);
@@ -158,7 +140,7 @@ class Mail extends \Zotlabs\Web\Controller {
function get() {
$o = '';
- nav_set_selected('messages');
+ nav_set_selected('Mail');
if(! local_channel()) {
notice( t('Permission denied.') . EOL);
@@ -178,6 +160,25 @@ class Mail extends \Zotlabs\Web\Controller {
'$header' => t('Messages'),
));
+ if(argc() == 3 && intval(argv(1)) && argv(2) === 'download') {
+
+ $r = q("select * from mail where id = %d and channel_id = %d",
+ intval(argv(1)),
+ intval(local_channel())
+ );
+
+ if($r) {
+
+ header('Content-type: ' . $r[0]['mail_mimetype']);
+ header('Content-disposition: attachment; filename="' . t('message') . '-' . $r[0]['id'] . '"' );
+ $body = (($r[0]['mail_obscured']) ? base64url_decode(str_rot47($r[0]['body'])) : $r[0]['body']);
+ echo $body;
+ killme();
+ }
+
+ }
+
+
if((argc() == 4) && (argv(2) === 'drop')) {
if(! intval(argv(3)))
return;
@@ -296,7 +297,9 @@ class Mail extends \Zotlabs\Web\Controller {
return $o;
}
-
+
+ $direct_mid = 0;
+
switch(argv(1)) {
case 'combined':
$mailbox = 'combined';
@@ -309,12 +312,22 @@ class Mail extends \Zotlabs\Web\Controller {
break;
default:
$mailbox = 'combined';
+
+ // notifications direct to mail/nn
+
+ if(intval(argv(1)))
+ $direct_mid = intval(argv(1));
break;
}
+
$last_message = private_messages_list(local_channel(), $mailbox, 0, 1);
-
+
$mid = ((argc() > 2) && (intval(argv(2)))) ? argv(2) : $last_message[0]['id'];
+
+ if($direct_mid)
+ $mid = $direct_mid;
+
$plaintext = true;
@@ -358,6 +371,11 @@ class Mail extends \Zotlabs\Web\Controller {
foreach($messages as $message) {
$s = theme_attachments($message);
+
+ if($message['mail_raw'])
+ $message['body'] = mail_prepare_binary([ 'id' => $message['id'] ]);
+ else
+ $message['body'] = zidify_links(smilies(bbcode($message['body'])));
$mails[] = array(
'mailbox' => $mailbox,
@@ -370,7 +388,7 @@ class Mail extends \Zotlabs\Web\Controller {
'to_url' => chanlink_hash($message['to_xchan']),
'to_photo' => $message['to']['xchan_photo_s'],
'subject' => $message['title'],
- 'body' => zidify_links(smilies(bbcode($message['body']))),
+ 'body' => $message['body'],
'attachments' => $s,
'delete' => t('Delete message'),
'dreport' => t('Delivery report'),
diff --git a/Zotlabs/Module/Manage.php b/Zotlabs/Module/Manage.php
index 3b7b3c3dd..9c5c32294 100644
--- a/Zotlabs/Module/Manage.php
+++ b/Zotlabs/Module/Manage.php
@@ -10,6 +10,8 @@ class Manage extends \Zotlabs\Web\Controller {
notice( t('Permission denied.') . EOL);
return;
}
+
+ nav_set_selected('Channel Manager');
require_once('include/security.php');
@@ -46,107 +48,111 @@ class Manage extends \Zotlabs\Web\Controller {
$channels = null;
- if(local_channel()) {
- $r = q("select channel.*, xchan.* from channel left join xchan on channel.channel_hash = xchan.xchan_hash where channel.channel_account_id = %d and channel_removed = 0 order by channel_name ",
- intval(get_account_id())
- );
+ $r = q("select channel.*, xchan.* from channel left join xchan on channel.channel_hash = xchan.xchan_hash where channel.channel_account_id = %d and channel_removed = 0 order by channel_name ",
+ intval(get_account_id())
+ );
- $account = \App::get_account();
+ $account = \App::get_account();
- if($r && count($r)) {
- $channels = $r;
- for($x = 0; $x < count($channels); $x ++) {
- $channels[$x]['link'] = 'manage/' . intval($channels[$x]['channel_id']);
- $channels[$x]['default'] = (($channels[$x]['channel_id'] == $account['account_default_channel']) ? "1" : '');
- $channels[$x]['default_links'] = '1';
+ if($r && count($r)) {
+ $channels = $r;
+ for($x = 0; $x < count($channels); $x ++) {
+ $channels[$x]['link'] = 'manage/' . intval($channels[$x]['channel_id']);
+ $channels[$x]['default'] = (($channels[$x]['channel_id'] == $account['account_default_channel']) ? "1" : '');
+ $channels[$x]['default_links'] = '1';
- $c = q("SELECT id, item_wall FROM item
- WHERE item_unseen = 1 and uid = %d " . item_normal(),
- intval($channels[$x]['channel_id'])
- );
+ $c = q("SELECT id, item_wall FROM item
+ WHERE item_unseen = 1 and uid = %d " . item_normal(),
+ intval($channels[$x]['channel_id'])
+ );
- if($c) {
- foreach ($c as $it) {
- if(intval($it['item_wall']))
- $channels[$x]['home'] ++;
- else
- $channels[$x]['network'] ++;
- }
+ if($c) {
+ foreach ($c as $it) {
+ if(intval($it['item_wall']))
+ $channels[$x]['home'] ++;
+ else
+ $channels[$x]['network'] ++;
}
+ }
- $intr = q("SELECT COUNT(abook.abook_id) AS total FROM abook left join xchan on abook.abook_xchan = xchan.xchan_hash where abook_channel = %d and abook_pending = 1 and abook_self = 0 and abook_ignored = 0 and xchan_deleted = 0 and xchan_orphan = 0 ",
- intval($channels[$x]['channel_id'])
- );
+ $intr = q("SELECT COUNT(abook.abook_id) AS total FROM abook left join xchan on abook.abook_xchan = xchan.xchan_hash where abook_channel = %d and abook_pending = 1 and abook_self = 0 and abook_ignored = 0 and xchan_deleted = 0 and xchan_orphan = 0 ",
+ intval($channels[$x]['channel_id'])
+ );
- if($intr)
- $channels[$x]['intros'] = intval($intr[0]['total']);
+ if($intr)
+ $channels[$x]['intros'] = intval($intr[0]['total']);
- $mails = q("SELECT count(id) as total from mail WHERE channel_id = %d AND mail_seen = 0 and from_xchan != '%s' ",
- intval($channels[$x]['channel_id']),
- dbesc($channels[$x]['channel_hash'])
- );
+ $mails = q("SELECT count(id) as total from mail WHERE channel_id = %d AND mail_seen = 0 and from_xchan != '%s' ",
+ intval($channels[$x]['channel_id']),
+ dbesc($channels[$x]['channel_hash'])
+ );
- if($mails)
- $channels[$x]['mail'] = intval($mails[0]['total']);
+ if($mails)
+ $channels[$x]['mail'] = intval($mails[0]['total']);
- $events = q("SELECT etype, dtstart, adjust FROM event
- WHERE event.uid = %d AND dtstart < '%s' AND dtstart > '%s' and dismissed = 0
- ORDER BY dtstart ASC ",
- intval($channels[$x]['channel_id']),
- dbesc(datetime_convert('UTC', date_default_timezone_get(), 'now + 7 days')),
- dbesc(datetime_convert('UTC', date_default_timezone_get(), 'now - 1 days'))
- );
-
- if($events) {
- $channels[$x]['all_events'] = count($events);
-
- if($channels[$x]['all_events']) {
- $str_now = datetime_convert('UTC', date_default_timezone_get(), 'now', 'Y-m-d');
- foreach($events as $e) {
- $bd = false;
- if($e['etype'] === 'birthday') {
- $channels[$x]['birthdays'] ++;
- $bd = true;
- }
- else {
- $channels[$x]['events'] ++;
- }
- if(datetime_convert('UTC', ((intval($e['adjust'])) ? date_default_timezone_get() : 'UTC'), $e['dtstart'], 'Y-m-d') === $str_now) {
- $channels[$x]['all_events_today'] ++;
- if($bd)
- $channels[$x]['birthdays_today'] ++;
- else
- $channels[$x]['events_today'] ++;
- }
+ $events = q("SELECT etype, dtstart, adjust FROM event
+ WHERE event.uid = %d AND dtstart < '%s' AND dtstart > '%s' and dismissed = 0
+ ORDER BY dtstart ASC ",
+ intval($channels[$x]['channel_id']),
+ dbesc(datetime_convert('UTC', date_default_timezone_get(), 'now + 7 days')),
+ dbesc(datetime_convert('UTC', date_default_timezone_get(), 'now - 1 days'))
+ );
+
+ if($events) {
+ $channels[$x]['all_events'] = count($events);
+
+ if($channels[$x]['all_events']) {
+ $str_now = datetime_convert('UTC', date_default_timezone_get(), 'now', 'Y-m-d');
+ foreach($events as $e) {
+ $bd = false;
+ if($e['etype'] === 'birthday') {
+ $channels[$x]['birthdays'] ++;
+ $bd = true;
+ }
+ else {
+ $channels[$x]['events'] ++;
+ }
+ if(datetime_convert('UTC', ((intval($e['adjust'])) ? date_default_timezone_get() : 'UTC'), $e['dtstart'], 'Y-m-d') === $str_now) {
+ $channels[$x]['all_events_today'] ++;
+ if($bd)
+ $channels[$x]['birthdays_today'] ++;
+ else
+ $channels[$x]['events_today'] ++;
}
}
}
}
}
-
- $r = q("select count(channel_id) as total from channel where channel_account_id = %d and channel_removed = 0",
- intval(get_account_id())
- );
- $limit = account_service_class_fetch(get_account_id(),'total_identities');
- if($limit !== false) {
- $channel_usage_message = sprintf( t("You have created %1$.0f of %2$.0f allowed channels."), $r[0]['total'], $limit);
- }
- else {
- $channel_usage_message = '';
- }
+
+ }
+
+ $r = q("select count(channel_id) as total from channel where channel_account_id = %d and channel_removed = 0",
+ intval(get_account_id())
+ );
+ $limit = account_service_class_fetch(get_account_id(),'total_identities');
+ if($limit !== false) {
+ $channel_usage_message = sprintf( t("You have created %1$.0f of %2$.0f allowed channels."), $r[0]['total'], $limit);
}
+ else {
+ $channel_usage_message = '';
+ }
+
$create = array( 'new_channel', t('Create a new channel'), t('Create New'));
- $delegates = q("select * from abook left join xchan on abook_xchan = xchan_hash where
- abook_channel = %d and abook_xchan in ( select xchan from abconfig where chan = %d and cat = 'their_perms' and k = 'delegate' and v = '1' )",
- intval(local_channel()),
- intval(local_channel())
- );
+ $delegates = null;
+
+ if(local_channel()) {
+ $delegates = q("select * from abook left join xchan on abook_xchan = xchan_hash where
+ abook_channel = %d and abook_xchan in ( select xchan from abconfig where chan = %d and cat = 'their_perms' and k = 'delegate' and v = '1' )",
+ intval(local_channel()),
+ intval(local_channel())
+ );
+ }
if($delegates) {
for($x = 0; $x < count($delegates); $x ++) {
diff --git a/Zotlabs/Module/Moderate.php b/Zotlabs/Module/Moderate.php
new file mode 100644
index 000000000..cf1625a6b
--- /dev/null
+++ b/Zotlabs/Module/Moderate.php
@@ -0,0 +1,90 @@
+<?php
+
+namespace Zotlabs\Module;
+
+require_once('include/conversation.php');
+
+
+class Moderate extends \Zotlabs\Web\Controller {
+
+
+ function get() {
+ if(! local_channel()) {
+ notice( t('Permission denied.') . EOL);
+ return;
+ }
+
+ //show all items
+ if(argc() == 1) {
+ $r = q("select item.id as item_id, item.* from item where item.uid = %d and item_blocked = %d and item_deleted = 0 order by created desc limit 60",
+ intval(local_channel()),
+ intval(ITEM_MODERATED)
+ );
+ }
+
+ //show a single item
+ if(argc() == 2) {
+ $post_id = intval(argv(1));
+
+ $r = q("select item.id as item_id, item.* from item where item.id = %d and item.uid = %d and item_blocked = %d and item_deleted = 0 order by created desc limit 60",
+ intval($post_id),
+ intval(local_channel()),
+ intval(ITEM_MODERATED)
+ );
+ }
+
+ if(argc() > 2) {
+ $post_id = intval(argv(1));
+ if(! $post_id)
+ goaway(z_root() . '/moderate');
+
+ $action = argv(2);
+
+ $r = q("select * from item where uid = %d and id = %d and item_blocked = %d limit 1",
+ intval(local_channel()),
+ intval($post_id),
+ intval(ITEM_MODERATED)
+ );
+
+ if($r) {
+ if($action === 'approve') {
+ q("update item set item_blocked = 0 where uid = %d and id = %d",
+ intval(local_channel()),
+ intval($post_id)
+ );
+ notice( t('Comment approved') . EOL);
+ }
+ elseif($action === 'drop') {
+ drop_item($post_id,false);
+ notice( t('Comment deleted') . EOL);
+ }
+
+ $r = q("select * from item where id = %d",
+ intval($post_id)
+ );
+ if($r) {
+ xchan_query($r);
+ $sync_item = fetch_post_tags($r);
+ build_sync_packet(local_channel(),array('item' => array(encode_item($sync_item[0],true))));
+ }
+ if($action === 'approve') {
+ \Zotlabs\Daemon\Master::Summon(array('Notifier', 'comment-new', $post_id));
+ }
+ goaway(z_root() . '/moderate');
+ }
+ }
+
+ if($r) {
+ xchan_query($r);
+ $items = fetch_post_tags($r,true);
+ }
+ else {
+ $items = array();
+ }
+
+ $o = conversation($items,'moderate',false,'traditional');
+ return $o;
+
+ }
+
+}
diff --git a/Zotlabs/Module/Mood.php b/Zotlabs/Module/Mood.php
index eeb050040..ad29ec7e8 100644
--- a/Zotlabs/Module/Mood.php
+++ b/Zotlabs/Module/Mood.php
@@ -110,17 +110,17 @@ class Mood extends \Zotlabs\Web\Controller {
- function get() {
+ function get() {
if(! local_channel()) {
notice( t('Permission denied.') . EOL);
return;
}
-
+
+ nav_set_selected('Mood');
+
$parent = ((x($_GET,'parent')) ? intval($_GET['parent']) : '0');
-
-
$verbs = get_mood_verbs();
$shortlist = array();
diff --git a/Zotlabs/Module/Network.php b/Zotlabs/Module/Network.php
index 8263420b6..ee736ff42 100644
--- a/Zotlabs/Module/Network.php
+++ b/Zotlabs/Module/Network.php
@@ -44,6 +44,7 @@ class Network extends \Zotlabs\Web\Controller {
$channel = \App::get_channel();
$item_normal = item_normal();
+ $item_normal_update = item_normal_update();
$datequery = $datequery2 = '';
@@ -116,10 +117,9 @@ class Network extends \Zotlabs\Web\Controller {
$spam = ((x($_GET,'spam')) ? intval($_GET['spam']) : 0);
$cmin = ((x($_GET,'cmin')) ? intval($_GET['cmin']) : 0);
$cmax = ((x($_GET,'cmax')) ? intval($_GET['cmax']) : 99);
- $firehose = ((x($_GET,'fh')) ? intval($_GET['fh']) : 0);
$file = ((x($_GET,'file')) ? $_GET['file'] : '');
-
-
+ $xchan = ((x($_GET,'xchan')) ? $_GET['xchan'] : '');
+
$deftag = '';
if(x($_GET,'search') || x($_GET,'file'))
@@ -154,7 +154,7 @@ class Network extends \Zotlabs\Web\Controller {
));
}
- nav_set_selected('network');
+ nav_set_selected('Grid');
$channel_acl = array(
'allow_cid' => $channel['channel_allow_cid'],
@@ -257,6 +257,26 @@ class Network extends \Zotlabs\Web\Controller {
goaway(z_root() . '/network');
}
}
+ elseif($xchan) {
+ $r = q("select * from xchan where xchan_hash = '%s'",
+ dbesc($xchan)
+ );
+ if($r) {
+ $sql_extra = " AND item.parent IN ( SELECT DISTINCT parent FROM item WHERE true $sql_options AND uid = " . intval(local_channel()) . " AND ( author_xchan = '" . dbesc($xchan) . "' or owner_xchan = '" . dbesc($xchan) . "' ) $item_normal ) ";
+ $title = replace_macros(get_markup_template("section_title.tpl"),array(
+ '$title' => '<a href="' . zid($r[0]['xchan_url']) . '" ><img src="' . zid($r[0]['xchan_photo_s']) . '" alt="' . urlencode($r[0]['xchan_name']) . '" /></a> <a href="' . zid($r[0]['xchan_url']) . '" >' . $r[0]['xchan_name'] . '</a>'
+ ));
+ $o = $tabs;
+ $o .= $title;
+ $o .= $status_editor;
+
+ }
+ else {
+ notice( t('Invalid channel.') . EOL);
+ goaway(z_root() . '/network');
+ }
+
+ }
if(x($category)) {
$sql_extra .= protect_sprintf(term_query('item', $category, TERM_CATEGORY));
@@ -270,9 +290,6 @@ class Network extends \Zotlabs\Web\Controller {
// We only launch liveUpdate if you aren't filtering in some incompatible
// way and also you aren't writing a comment (discovered in javascript).
- if($gid || $cid || $cmin || ($cmax != 99) || $star || $liked || $conv || $spam || $nouveau || $list)
- $firehose = 0;
-
$maxheight = get_pconfig(local_channel(),'system','network_divmore_height');
if(! $maxheight)
$maxheight = 400;
@@ -295,17 +312,18 @@ class Network extends \Zotlabs\Web\Controller {
'$liked' => (($liked) ? $liked : '0'),
'$conv' => (($conv) ? $conv : '0'),
'$spam' => (($spam) ? $spam : '0'),
- '$fh' => (($firehose) ? $firehose : '0'),
+ '$fh' => '0',
'$nouveau' => (($nouveau) ? $nouveau : '0'),
'$wall' => '0',
'$static' => $static,
'$list' => ((x($_REQUEST,'list')) ? intval($_REQUEST['list']) : 0),
'$page' => ((\App::$pager['page'] != 1) ? \App::$pager['page'] : 1),
'$search' => (($search) ? $search : ''),
+ '$xchan' => $xchan,
'$order' => $order,
'$file' => $file,
- '$cats' => $category,
- '$tags' => $hashtags,
+ '$cats' => urlencode($category),
+ '$tags' => urlencode($hashtags),
'$dend' => $datequery,
'$mid' => '',
'$verb' => $verb,
@@ -388,16 +406,7 @@ class Network extends \Zotlabs\Web\Controller {
}
$abook_uids = " and abook.abook_channel = " . local_channel() . " ";
-
- if($firehose && (! get_config('system','disable_discover_tab'))) {
- require_once('include/channel.php');
- $sys = get_sys_channel();
- $uids = " and item.uid = " . intval($sys['channel_id']) . " ";
- \App::$data['firehose'] = intval($sys['channel_id']);
- }
- else {
- $uids = " and item.uid = " . local_channel() . " ";
- }
+ $uids = " and item.uid = " . local_channel() . " ";
if(get_pconfig(local_channel(),'system','network_list_mode'))
$page_mode = 'list';
@@ -469,10 +478,11 @@ class Network extends \Zotlabs\Web\Controller {
}
else {
+
// this is an update
$r = q("SELECT item.parent AS item_id FROM item
left join abook on ( item.owner_xchan = abook.abook_xchan $abook_uids )
- WHERE true $uids $item_normal $simple_update
+ WHERE true $uids $item_normal_update $simple_update
and (abook.abook_blocked = 0 or abook.abook_flags is null)
$sql_extra3 $sql_extra $sql_nets "
);
@@ -494,14 +504,14 @@ class Network extends \Zotlabs\Web\Controller {
dbesc($parents_str)
);
- xchan_query($items,true,(($firehose) ? local_channel() : 0));
+ xchan_query($items,true);
$items = fetch_post_tags($items,true);
$items = conv_sort($items,$ordering);
}
else {
$items = array();
}
-
+
if($page_mode === 'list') {
/**
@@ -513,24 +523,30 @@ class Network extends \Zotlabs\Web\Controller {
if($parents_str) {
$update_unseen = " AND ( id IN ( " . dbesc($parents_str) . " )";
+ $update_unseen .= " AND obj_type != '" . dbesc(ACTIVITY_OBJ_FILE) . "'";
$update_unseen .= " OR ( parent IN ( " . dbesc($parents_str) . " ) AND verb in ( '" . dbesc(ACTIVITY_LIKE) . "','" . dbesc(ACTIVITY_DISLIKE) . "' ))) ";
}
}
else {
if($parents_str) {
- $update_unseen = " AND parent IN ( " . dbesc($parents_str) . " )";
+ $update_unseen = " AND parent IN ( " . dbesc($parents_str) . " ) AND obj_type != '" . dbesc(ACTIVITY_OBJ_FILE) . "'";
}
}
}
- if(($update_unseen) && (! $firehose))
- $r = q("UPDATE item SET item_unseen = 0 WHERE item_unseen = 1 AND uid = %d $update_unseen ",
- intval(local_channel())
- );
+ if($update_unseen) {
+ $x = [ 'channel_id' => local_channel(), 'update' => 'unset' ];
+ call_hooks('update_unseen',$x);
+ if($x['update'] === 'unset' || intval($x['update'])) {
+ $r = q("UPDATE item SET item_unseen = 0 WHERE item_unseen = 1 AND uid = %d $update_unseen ",
+ intval(local_channel())
+ );
+ }
+ }
$mode = (($nouveau) ? 'network-new' : 'network');
- $o .= conversation($a,$items,$mode,$update,$page_mode);
+ $o .= conversation($items,$mode,$update,$page_mode);
if(($items) && (! $update))
$o .= alt_pager($a,count($items));
diff --git a/Zotlabs/Module/New_channel.php b/Zotlabs/Module/New_channel.php
index 8e6fd1d37..2b73fa191 100644
--- a/Zotlabs/Module/New_channel.php
+++ b/Zotlabs/Module/New_channel.php
@@ -9,7 +9,7 @@ require_once('include/permissions.php');
class New_channel extends \Zotlabs\Web\Controller {
function init() {
-
+
$cmd = ((argc() > 1) ? argv(1) : '');
if($cmd === 'autofill.json') {
@@ -134,7 +134,7 @@ class New_channel extends \Zotlabs\Web\Controller {
$name = array('name', t('Name or caption'), ((x($_REQUEST,'name')) ? $_REQUEST['name'] : ''), t('Examples: "Bob Jameson", "Lisa and her Horses", "Soccer", "Aviation Group"'), "*");
$nickhub = '@' . \App::get_hostname();
$nickname = array('nickname', t('Choose a short nickname'), ((x($_REQUEST,'nickname')) ? $_REQUEST['nickname'] : ''), sprintf( t('Your nickname will be used to create an easy to remember channel address e.g. nickname%s'), $nickhub), "*");
- $role = array('permissions_role' , t('Channel role and privacy'), ($privacy_role) ? $privacy_role : 'social', t('Select a channel role with your privacy requirements.') . ' <a href="help/roles" target="_blank">' . t('Read more about roles') . '</a>',$perm_roles);
+ $role = array('permissions_role' , t('Channel role and privacy'), ($privacy_role) ? $privacy_role : 'social', t('Select a channel role with your privacy requirements.') . ' <a href="help/member/member_guide#Account_Permission_Roles" target="_blank">' . t('Read more about roles') . '</a>',$perm_roles);
$o = replace_macros(get_markup_template('new_channel.tpl'), array(
'$title' => t('Create Channel'),
diff --git a/Zotlabs/Module/Notifications.php b/Zotlabs/Module/Notifications.php
index e0313dd8b..dfa007548 100644
--- a/Zotlabs/Module/Notifications.php
+++ b/Zotlabs/Module/Notifications.php
@@ -12,25 +12,44 @@ class Notifications extends \Zotlabs\Web\Controller {
return;
}
- nav_set_selected('notifications');
+ nav_set_selected('Notifications');
$o = '';
-
- $r = q("SELECT * from notify where uid = %d and seen = 0 order by created desc",
+
+ $r = q("select count(*) as total from notify where uid = %d and seen = 0",
intval(local_channel())
);
+ if($r && intval($t[0]['total']) > 49) {
+ $r = q("select * from notify where uid = %d
+ and seen = 0 order by created desc limit 50",
+ intval(local_channel())
+ );
+ } else {
+ $r1 = q("select * from notify where uid = %d
+ and seen = 0 order by created desc limit 50",
+ intval(local_channel())
+ );
+ $r2 = q("select * from notify where uid = %d
+ and seen = 1 order by created desc limit %d",
+ intval(local_channel()),
+ intval(50 - intval($t[0]['total']))
+ );
+ $r = array_merge($r1,$r2);
+ }
if($r) {
$notifications_available = 1;
- foreach ($r as $it) {
- $x = strip_tags(bbcode($it['msg']));
+ foreach ($r as $rr) {
+ $x = strip_tags(bbcode($rr['msg']));
if(strpos($x,','))
$x = substr($x,strpos($x,',')+1);
$notif_content .= replace_macros(get_markup_template('notify.tpl'),array(
- '$item_link' => z_root().'/notify/view/'. $it['id'],
- '$item_image' => $it['photo'],
+ '$item_link' => z_root().'/notify/view/'. $rr['id'],
+ '$item_image' => $rr['photo'],
'$item_text' => $x,
- '$item_when' => relative_date($it['created'])
+ '$item_when' => relative_date($rr['created']),
+ '$item_seen' => (($rr['seen']) ? true : false),
+ '$new' => t('New')
));
}
}
@@ -40,7 +59,7 @@ class Notifications extends \Zotlabs\Web\Controller {
$o .= replace_macros(get_markup_template('notifications.tpl'),array(
'$notif_header' => t('System Notifications'),
- '$notif_link_mark_seen' => t('Mark all system notifications seen'),
+ '$notif_link_mark_seen' => t('Mark all seen'),
'$notif_content' => $notif_content,
'$notifications_available' => $notifications_available,
));
diff --git a/Zotlabs/Module/Notify.php b/Zotlabs/Module/Notify.php
index f592f6f37..3d6e1c2e7 100644
--- a/Zotlabs/Module/Notify.php
+++ b/Zotlabs/Module/Notify.php
@@ -15,12 +15,16 @@ class Notify extends \Zotlabs\Web\Controller {
intval(local_channel())
);
if($r) {
- q("update notify set seen = 1 where (( parent != '' and parent = '%s' and otype = '%s' ) or link = '%s' ) and uid = %d",
- dbesc($r[0]['parent']),
- dbesc($r[0]['otype']),
- dbesc($r[0]['link']),
- intval(local_channel())
- );
+ $x = [ 'channel_id' => local_channel(), 'update' => 'unset' ];
+ call_hooks('update_unseen',$x);
+ if($x['update'] === 'unset' || intval($x['update'])) {
+ q("update notify set seen = 1 where (( parent != '' and parent = '%s' and otype = '%s' ) or link = '%s' ) and uid = %d",
+ dbesc($r[0]['parent']),
+ dbesc($r[0]['otype']),
+ dbesc($r[0]['link']),
+ intval(local_channel())
+ );
+ }
goaway($r[0]['link']);
}
goaway(z_root());
diff --git a/Zotlabs/Module/Oembed.php b/Zotlabs/Module/Oembed.php
index 9394e5942..aee5ea079 100644
--- a/Zotlabs/Module/Oembed.php
+++ b/Zotlabs/Module/Oembed.php
@@ -22,7 +22,7 @@ class Oembed extends \Zotlabs\Web\Controller {
}
else {
- echo "<html><head><base target=\"_blank\" /></head><body>";
+ echo "<html><head><base target=\"_blank\" rel=\"nofollow noopener\" /></head><body>";
$src = base64url_decode(argv(1));
$j = oembed_fetch_url($src);
echo $j['html'];
diff --git a/Zotlabs/Module/Oep.php b/Zotlabs/Module/Oep.php
index dc0547a42..5e06d3540 100644
--- a/Zotlabs/Module/Oep.php
+++ b/Zotlabs/Module/Oep.php
@@ -1,6 +1,8 @@
<?php
namespace Zotlabs\Module;
+require_once('include/security.php');
+
// oembed provider
@@ -41,6 +43,8 @@ class Oep extends \Zotlabs\Web\Controller {
$arr = $this->oep_profile_reply($_REQUEST);
elseif(fnmatch('*/profile/*',$url))
$arr = $this->oep_profile_reply($_REQUEST);
+ elseif(fnmatch('*/cards/*',$url))
+ $arr = $this->oep_cards_reply($_REQUEST);
if($arr) {
if($html) {
@@ -66,49 +70,158 @@ class Oep extends \Zotlabs\Web\Controller {
$url = $args['url'];
$maxwidth = intval($args['maxwidth']);
$maxheight = intval($args['maxheight']);
-
- if(preg_match('#//(.*?)/(.*?)/(.*?)/(.*?)mid\=(.*?)(&|$)#',$url,$matches)) {
- $chn = $matches[3];
- $res = $matches[5];
+ logger('processing display');
+ if(preg_match('#//(.*?)/display/(.*?)(&|\?|$)#',$url,$matches)) {
+ $res = $matches[2];
}
-
- if(! ($chn && $res))
- return;
- $c = q("select * from channel where channel_address = '%s' limit 1",
- dbesc($chn)
+
+ if(strpos($res,'b64.') === 0) {
+ $res = base64url_decode(substr($res,4));
+ }
+
+ $item_normal = item_normal();
+
+ $p = q("select * from item where mid like '%s' limit 1",
+ dbesc($res . '%')
);
-
- if(! $c)
+
+ if(! $p)
return;
+
+ $c = channelx_by_n($p[0]['uid']);
+
- $sql_extra = item_permissions_sql($c[0]['channel_id']);
+ if(! ($c && $res))
+ return;
+
+ if(! perm_is_allowed($c[0]['channel_id'],get_observer_hash(),'view_stream'))
+ return;
+
+ $sql_extra = item_permissions_sql($c['channel_id']);
- $p = q("select * from item where mid = '%s' and uid = %d $sql_extra limit 1",
- dbesc($res),
- intval($c[0]['channel_id'])
+ $p = q("select * from item where mid like '%s' and uid = %d $sql_extra $item_normal limit 1",
+ dbesc($res . '%'),
+ intval($c['channel_id'])
);
+
if(! $p)
return;
xchan_query($p,true);
$p = fetch_post_tags($p,true);
+
+ // This function can get tripped up if the item is already a reshare
+ // (the multiple share declarations do not parse cleanly if nested)
+ // So build a template with a known nonsense string as the content, and then
+ // replace that known string with the actual rendered content, sending
+ // each content layer through bbcode() separately.
+
+ $x = '2eGriplW^*Jmf4';
+
+
+ $o = "[share author='".urlencode($p[0]['author']['xchan_name']).
+ "' profile='".$p[0]['author']['xchan_url'] .
+ "' avatar='".$p[0]['author']['xchan_photo_s'].
+ "' link='".$p[0]['plink'].
+ "' posted='".$p[0]['created'].
+ "' message_id='".$p[0]['mid']."']";
+ if($p[0]['title'])
+ $o .= '[b]'.$p[0]['title'].'[/b]'."\r\n";
+
+ $o .= $x;
+ $o .= "[/share]";
+ $o = bbcode($o);
+
+ $o = str_replace($x,bbcode($p[0]['body']),$o);
+
+ $ret['type'] = 'rich';
+
+ $w = (($maxwidth) ? $maxwidth : 640);
+ $h = (($maxheight) ? $maxheight : intval($w * 2 / 3));
+
+ $ret['html'] = '<div style="width: ' . $w . '; height: ' . $h . '; font-family: sans-serif,arial,freesans;" >' . $o . '</div>';
+
+ $ret['width'] = $w;
+ $ret['height'] = $h;
+
+ return $ret;
+
+ }
+
+
+ function oep_cards_reply($args) {
+
+ $ret = [];
+ $url = $args['url'];
+ $maxwidth = intval($args['maxwidth']);
+ $maxheight = intval($args['maxheight']);
+
+ if(preg_match('#//(.*?)/cards/(.*?)/(.*?)(&|\?|$)#',$url,$matches)) {
+ $nick = $matches[2];
+ $res = $matches[3];
+ }
+ if(! ($nick && $res))
+ return $ret;
+
+ $channel = channelx_by_nick($nick);
+
+ if(! $channel)
+ return $ret;
+
+
+ if(! perm_is_allowed($channel['channel_id'],get_observer_hash(),'view_pages'))
+ return $ret;
+
+ $sql_extra = item_permissions_sql($channel['channel_id'],get_observer_hash());
+
+ $r = q("select * from iconfig where iconfig.cat = 'system' and iconfig.k = 'CARD' and iconfig.v = '%s' limit 1",
+ dbesc($res)
+ );
+ if($r) {
+ $sql_extra = "and item.id = " . intval($r[0]['iid']) . " ";
+ }
+ else {
+ return $ret;
+ }
+
+ $r = q("select * from item
+ where item.uid = %d and item_type = %d
+ $sql_extra order by item.created desc",
+ intval($channel['channel_id']),
+ intval(ITEM_TYPE_CARD)
+ );
+
+ $item_normal = " and item.item_hidden = 0 and item.item_type in (0,6) and item.item_deleted = 0
+ and item.item_unpublished = 0 and item.item_delayed = 0 and item.item_pending_remove = 0
+ and item.item_blocked = 0 ";
+
+ if($r) {
+ xchan_query($r);
+ $p = fetch_post_tags($r, true);
+ }
+
+ $x = '2eGriplW^*Jmf4';
+
$o = "[share author='".urlencode($p[0]['author']['xchan_name']).
- "' profile='".$p[0]['author']['xchan_url'] .
- "' avatar='".$p[0]['author']['xchan_photo_s'].
- "' link='".$p[0]['plink'].
- "' posted='".$p[0]['created'].
- "' message_id='".$p[0]['mid']."']";
+ "' profile='".$p[0]['author']['xchan_url'] .
+ "' avatar='".$p[0]['author']['xchan_photo_s'].
+ "' link='".$p[0]['plink'].
+ "' posted='".$p[0]['created'].
+ "' message_id='".$p[0]['mid']."']";
if($p[0]['title'])
- $o .= '[b]'.$p[0]['title'].'[/b]'."\r\n";
- $o .= $p[0]['body'];
- $o .= "[/share]";
+ $o .= '[b]'.$p[0]['title'].'[/b]'."\r\n";
+
+ $o .= $x;
+ $o .= "[/share]";
$o = bbcode($o);
+ $o = str_replace($x,bbcode($p[0]['body']),$o);
+
$ret['type'] = 'rich';
$w = (($maxwidth) ? $maxwidth : 640);
- $h = (($maxheight) ? $maxheight : $w * 2 / 3);
+ $h = (($maxheight) ? $maxheight : intval($w * 2 / 3));
$ret['html'] = '<div style="width: ' . $w . '; height: ' . $h . '; font-family: sans-serif,arial,freesans;" >' . $o . '</div>';
@@ -118,6 +231,7 @@ class Oep extends \Zotlabs\Web\Controller {
return $ret;
}
+
function oep_mid_reply($args) {
@@ -139,6 +253,9 @@ class Oep extends \Zotlabs\Web\Controller {
if(! $c)
return;
+
+ if(! perm_is_allowed($c[0]['channel_id'],get_observer_hash(),'view_stream'))
+ return;
$sql_extra = item_permissions_sql($c[0]['channel_id']);
@@ -151,23 +268,33 @@ class Oep extends \Zotlabs\Web\Controller {
xchan_query($p,true);
$p = fetch_post_tags($p,true);
-
+
+ // This function can get tripped up if the item is already a reshare
+ // (the multiple share declarations do not parse cleanly if nested)
+ // So build a template with a known nonsense string as the content, and then
+ // replace that known string with the actual rendered content, sending
+ // each content layer through bbcode() separately.
+
+ $x = '2eGriplW^*Jmf4';
+
$o = "[share author='".urlencode($p[0]['author']['xchan_name']).
- "' profile='".$p[0]['author']['xchan_url'] .
- "' avatar='".$p[0]['author']['xchan_photo_s'].
- "' link='".$p[0]['plink'].
- "' posted='".$p[0]['created'].
- "' message_id='".$p[0]['mid']."']";
- if($p[0]['title'])
- $o .= '[b]'.$p[0]['title'].'[/b]'."\r\n";
- $o .= $p[0]['body'];
- $o .= "[/share]";
+ "' profile='".$p[0]['author']['xchan_url'] .
+ "' avatar='".$p[0]['author']['xchan_photo_s'].
+ "' link='".$p[0]['plink'].
+ "' posted='".$p[0]['created'].
+ "' message_id='".$p[0]['mid']."']";
+ if($p[0]['title'])
+ $o .= '[b]'.$p[0]['title'].'[/b]'."\r\n";
+ $o .= $x;
+ $o .= "[/share]";
$o = bbcode($o);
+ $o = str_replace($x,bbcode($p[0]['body']),$o);
+
$ret['type'] = 'rich';
$w = (($maxwidth) ? $maxwidth : 640);
- $h = (($maxheight) ? $maxheight : $w * 2 / 3);
+ $h = (($maxheight) ? $maxheight : intval($w * 2 / 3));
$ret['html'] = '<div style="width: ' . $w . '; height: ' . $h . '; font-family: sans-serif,arial,freesans;" >' . $o . '</div>';
@@ -247,6 +374,9 @@ class Oep extends \Zotlabs\Web\Controller {
if(! $c)
return;
+ if(! perm_is_allowed($c[0]['channel_id'],get_observer_hash(),'view_files'))
+ return;
+
$sql_extra = permissions_sql($c[0]['channel_id']);
$p = q("select resource_id from photo where album = '%s' and uid = %d and imgscale = 0 $sql_extra order by created desc limit 1",
@@ -308,6 +438,9 @@ class Oep extends \Zotlabs\Web\Controller {
if(! $c)
return;
+ if(! perm_is_allowed($c[0]['channel_id'],get_observer_hash(),'view_files'))
+ return;
+
$sql_extra = permissions_sql($c[0]['channel_id']);
$p = q("select resource_id from photo where uid = %d and imgscale = 0 $sql_extra order by created desc limit 1",
@@ -368,7 +501,10 @@ class Oep extends \Zotlabs\Web\Controller {
if(! $c)
return;
-
+
+ if(! perm_is_allowed($c[0]['channel_id'],get_observer_hash(),'view_files'))
+ return;
+
$sql_extra = permissions_sql($c[0]['channel_id']);
diff --git a/Zotlabs/Module/Ofeed.php b/Zotlabs/Module/Ofeed.php
new file mode 100644
index 000000000..58488d4af
--- /dev/null
+++ b/Zotlabs/Module/Ofeed.php
@@ -0,0 +1,48 @@
+<?php
+
+namespace Zotlabs\Module;
+
+/* Ofeed: Broken feed for software which requires broken feeds */
+
+require_once('include/items.php');
+
+class Ofeed extends \Zotlabs\Web\Controller {
+
+ function init() {
+
+ $params = [];
+
+ $params['begin'] = ((x($_REQUEST,'date_begin')) ? $_REQUEST['date_begin'] : NULL_DATE);
+ $params['end'] = ((x($_REQUEST,'date_end')) ? $_REQUEST['date_end'] : '');
+ $params['type'] = ((stristr(argv(0),'json')) ? 'json' : 'xml');
+ $params['pages'] = ((x($_REQUEST,'pages')) ? intval($_REQUEST['pages']) : 0);
+ $params['top'] = ((x($_REQUEST,'top')) ? intval($_REQUEST['top']) : 0);
+ $params['start'] = ((x($params,'start')) ? intval($params['start']) : 0);
+ $params['records'] = ((x($params,'records')) ? intval($params['records']) : 10);
+ $params['direction'] = ((x($params,'direction')) ? dbesc($params['direction']) : 'desc');
+ $params['cat'] = ((x($_REQUEST,'cat')) ? escape_tags($_REQUEST['cat']) : '');
+ $params['compat'] = ((x($_REQUEST,'compat')) ? intval($_REQUEST['compat']) : 1);
+
+
+ if(argc() > 1) {
+
+ if(observer_prohibited(true)) {
+ killme();
+ }
+
+ $channel = channelx_by_nick(argv(1));
+ if(! $channel) {
+ killme();
+ }
+
+
+ logger('public feed request from ' . $_SERVER['REMOTE_ADDR'] . ' for ' . $channel['channel_address']);
+
+ echo get_public_feed($channel,$params);
+
+ killme();
+ }
+
+ }
+
+}
diff --git a/Zotlabs/Module/Owa.php b/Zotlabs/Module/Owa.php
new file mode 100644
index 000000000..4b0d855c5
--- /dev/null
+++ b/Zotlabs/Module/Owa.php
@@ -0,0 +1,53 @@
+<?php
+
+namespace Zotlabs\Module;
+
+/**
+ * OpenWebAuth verifier and token generator
+ * See https://macgirvin.com/wiki/mike/OpenWebAuth/Home
+ * Requests to this endpoint should be signed using HTTP Signatures
+ * using the 'Authorization: Signature' authentication method
+ * If the signature verifies a token is returned.
+ *
+ * This token may be exchanged for an authenticated cookie.
+ */
+
+class Owa extends \Zotlabs\Web\Controller {
+
+ function init() {
+
+ $ret = [ 'success' => false ];
+
+ foreach([ 'REDIRECT_REMOTE_USER', 'HTTP_AUTHORIZATION' ] as $head) {
+ if(array_key_exists($head,$_SERVER) && substr(trim($_SERVER[$head]),0,9) === 'Signature') {
+ if($head !== 'HTTP_AUTHORIZATION') {
+ $_SERVER['HTTP_AUTHORIZATION'] = $_SERVER[$head];
+ continue;
+ }
+
+ $sigblock = \Zotlabs\Web\HTTPSig::parse_sigheader($_SERVER[$head]);
+ if($sigblock) {
+ $keyId = $sigblock['keyId'];
+
+ if($keyId) {
+ $r = q("select * from hubloc left join xchan on hubloc_hash = xchan_hash
+ where hubloc_addr = '%s' limit 1",
+ dbesc(str_replace('acct:','',$keyId))
+ );
+ if($r) {
+ $hubloc = $r[0];
+ $verified = \Zotlabs\Web\HTTPSig::verify('',$hubloc['xchan_pubkey']);
+ if($verified && $verified['header_signed'] && $verified['header_valid']) {
+ $ret['success'] = true;
+ $token = random_string(32);
+ \Zotlabs\Zot\Verify::create('owt',0,$token,$r[0]['hubloc_addr']);
+ $ret['token'] = $token;
+ }
+ }
+ }
+ }
+ }
+ }
+ json_return_and_die($ret,'application/x-zot+json');
+ }
+}
diff --git a/Zotlabs/Module/Page.php b/Zotlabs/Module/Page.php
index 6ef285dd0..c142afe77 100644
--- a/Zotlabs/Module/Page.php
+++ b/Zotlabs/Module/Page.php
@@ -3,7 +3,6 @@ namespace Zotlabs\Module;
require_once('include/items.php');
require_once('include/conversation.php');
-require_once('include/page_widgets.php');
class Page extends \Zotlabs\Web\Controller {
@@ -43,11 +42,31 @@ class Page extends \Zotlabs\Web\Controller {
$channel_address = argv(1);
+ // Always look first for the page name prefixed by the observer language; for instance page/nickname/de/foo
+ // followed by page/nickname/foo if that is not found.
+ // If your browser language is de and you want to access the default in this case,
+ // use page/nickname/-/foo to over-ride the language and access only the page with pagelink of 'foo'
+
+ $page_name = '';
+ $ignore_language = false;
+
+ for($x = 2; $x < argc(); $x ++) {
+ if($page_name === '' && argv($x) === '-') {
+ $ignore_language = true;
+ continue;
+ }
+ if($page_name)
+ $page_name .= '/';
+ $page_name .= argv($x);
+ }
+
+
// The page link title was stored in a urlencoded format
// php or the browser may/will have decoded it, so re-encode it for our search
- $page_id = urlencode(argv(2));
-
+ $page_id = urlencode($page_name);
+ $lang_page_id = urlencode(\App::$language . '/' . $page_name);
+
$u = q("select channel_id from channel where channel_address = '%s' limit 1",
dbesc($channel_address)
);
@@ -64,16 +83,31 @@ class Page extends \Zotlabs\Web\Controller {
require_once('include/security.php');
$sql_options = item_permissions_sql($u[0]['channel_id']);
-
- $r = q("select item.* from item left join iconfig on item.id = iconfig.iid
- where item.uid = %d and iconfig.cat = 'system' and iconfig.v = '%s' and item.item_delayed = 0
- and (( iconfig.k = 'WEBPAGE' and item_type = %d )
- OR ( iconfig.k = 'PDL' AND item_type = %d )) $sql_options $revision limit 1",
- intval($u[0]['channel_id']),
- dbesc($page_id),
- intval(ITEM_TYPE_WEBPAGE),
- intval(ITEM_TYPE_PDL)
- );
+
+ $r = null;
+
+ if(! $ignore_language) {
+ $r = q("select item.* from item left join iconfig on item.id = iconfig.iid
+ where item.uid = %d and iconfig.cat = 'system' and iconfig.v = '%s' and item.item_delayed = 0
+ and (( iconfig.k = 'WEBPAGE' and item_type = %d )
+ OR ( iconfig.k = 'PDL' AND item_type = %d )) $sql_options $revision limit 1",
+ intval($u[0]['channel_id']),
+ dbesc($lang_page_id),
+ intval(ITEM_TYPE_WEBPAGE),
+ intval(ITEM_TYPE_PDL)
+ );
+ }
+ if(! $r) {
+ $r = q("select item.* from item left join iconfig on item.id = iconfig.iid
+ where item.uid = %d and iconfig.cat = 'system' and iconfig.v = '%s' and item.item_delayed = 0
+ and (( iconfig.k = 'WEBPAGE' and item_type = %d )
+ OR ( iconfig.k = 'PDL' AND item_type = %d )) $sql_options $revision limit 1",
+ intval($u[0]['channel_id']),
+ dbesc($page_id),
+ intval(ITEM_TYPE_WEBPAGE),
+ intval(ITEM_TYPE_PDL)
+ );
+ }
if(! $r) {
// Check again with no permissions clause to see if it is a permissions issue
diff --git a/Zotlabs/Module/Pdledit.php b/Zotlabs/Module/Pdledit.php
index 618444480..f8af470ac 100644
--- a/Zotlabs/Module/Pdledit.php
+++ b/Zotlabs/Module/Pdledit.php
@@ -14,7 +14,7 @@ class Pdledit extends \Zotlabs\Web\Controller {
if(! trim($_REQUEST['content'])) {
del_pconfig(local_channel(),'system','mod_' . $_REQUEST['module'] . '.pdl');
- goaway(z_root() . '/pdledit/' . $_REQUEST['module']);
+ goaway(z_root() . '/pdledit');
}
set_pconfig(local_channel(),'system','mod_' . $_REQUEST['module'] . '.pdl',escape_tags($_REQUEST['content']));
build_sync_packet();
@@ -34,19 +34,38 @@ class Pdledit extends \Zotlabs\Web\Controller {
notice( t('Feature disabled.') . EOL);
return;
}
-
+
+ if(argc() > 2 && argv(2) === 'reset') {
+ del_pconfig(local_channel(),'system','mod_' . argv(1) . '.pdl');
+ goaway(z_root() . '/pdledit');
+ }
+
if(argc() > 1)
$module = 'mod_' . argv(1) . '.pdl';
else {
$o .= '<div class="generic-content-wrapper-styled">';
$o .= '<h1>' . t('Edit System Page Description') . '</h1>';
+
+ $edited = [];
+
+ $r = q("select k from pconfig where uid = %d and cat = 'system' and k like '%s' ",
+ intval(local_channel()),
+ dbesc('mod_%.pdl')
+ );
+
+ if($r) {
+ foreach($r as $rv) {
+ $edited[] = substr(str_replace('.pdl','',$rv['k']),4);
+ }
+ }
+
$files = glob('Zotlabs/Module/*.php');
if($files) {
foreach($files as $f) {
$name = lcfirst(basename($f,'.php'));
$x = theme_include('mod_' . $name . '.pdl');
if($x) {
- $o .= '<a href="pdledit/' . $name . '" >' . $name . '</a><br />';
+ $o .= '<a href="pdledit/' . $name . '" >' . $name . '</a>' . ((in_array($name,$edited)) ? ' ' . t('(modified)') . ' <a href="pdledit/' . $name . '/reset" >' . t('Reset') . '</a>': '' ) . '<br />';
}
}
}
@@ -69,6 +88,7 @@ class Pdledit extends \Zotlabs\Web\Controller {
'$header' => t('Edit System Page Description'),
'$mname' => t('Module Name:'),
'$help' => t('Layout Help'),
+ '$another' => t('Edit another layout'),
'$module' => argv(1),
'$content' => htmlspecialchars($t,ENT_COMPAT,'UTF-8'),
'$submit' => t('Submit')
diff --git a/Zotlabs/Module/Photo.php b/Zotlabs/Module/Photo.php
index 256a51e71..8a110f925 100644
--- a/Zotlabs/Module/Photo.php
+++ b/Zotlabs/Module/Photo.php
@@ -127,7 +127,6 @@ class Photo extends \Zotlabs\Web\Controller {
}
}
-
$r = q("SELECT uid FROM photo WHERE resource_id = '%s' AND imgscale = %d LIMIT 1",
dbesc($photo),
intval($resolution)
@@ -150,12 +149,16 @@ class Photo extends \Zotlabs\Web\Controller {
$channel = channelx_by_n($r[0]['uid']);
// Now we'll see if we can access the photo
-
$r = q("SELECT * FROM photo WHERE resource_id = '%s' AND imgscale = %d $sql_extra LIMIT 1",
dbesc($photo),
intval($resolution)
);
-
+
+ // viewing cover photos is allowed unless a plugin chooses to block it.
+
+ if($r && intval($r[0]['photo_usage']) === PHOTO_COVER && $resolution >= PHOTO_RES_COVER_1200)
+ $allowed = 1;
+
$d = [ 'imgscale' => $resolution, 'resource_id' => $photo, 'photo' => $r, 'allowed' => $allowed ];
call_hooks('get_photo',$d);
diff --git a/Zotlabs/Module/Photos.php b/Zotlabs/Module/Photos.php
index 582174d0e..caef45d98 100644
--- a/Zotlabs/Module/Photos.php
+++ b/Zotlabs/Module/Photos.php
@@ -15,13 +15,10 @@ class Photos extends \Zotlabs\Web\Controller {
function init() {
-
if(observer_prohibited()) {
return;
}
- $o = '';
-
if(argc() > 1) {
$nick = argv(1);
@@ -54,7 +51,6 @@ class Photos extends \Zotlabs\Web\Controller {
logger('mod-photos: photos_post: begin' , LOGGER_DEBUG);
-
logger('mod_photos: REQUEST ' . print_r($_REQUEST,true), LOGGER_DATA);
logger('mod_photos: FILES ' . print_r($_FILES,true), LOGGER_DATA);
@@ -92,14 +88,9 @@ class Photos extends \Zotlabs\Web\Controller {
if((argc() > 3) && (argv(2) === 'album')) {
- $album = hex2bin(argv(3));
-
- if($album === t('Profile Photos')) {
- // not allowed
- goaway(z_root() . '/' . $_SESSION['photo_return']);
- }
-
- if(! photos_album_exists($page_owner_uid,$album)) {
+ $album = argv(3);
+
+ if(! photos_album_exists($page_owner_uid, get_observer_hash(), $album)) {
notice( t('Album not found.') . EOL);
goaway(z_root() . '/' . $_SESSION['photo_return']);
}
@@ -121,7 +112,7 @@ class Photos extends \Zotlabs\Web\Controller {
$folder_hash = '';
- $r = q("select * from attach where is_dir = 1 and uid = %d and filename = '%s'",
+ $r = q("select * from attach where is_dir = 1 and uid = %d and hash = '%s'",
intval($page_owner_uid),
dbesc($album)
);
@@ -129,14 +120,7 @@ class Photos extends \Zotlabs\Web\Controller {
notice( t('Album not found.') . EOL);
return;
}
- if(count($r) > 1) {
- notice( t('Multiple storage folders exist with this album name, but within different directories. Please remove the desired folder or folders using the Files manager') . EOL);
- return;
- }
- else {
- $folder_hash = $r[0]['hash'];
- }
-
+ $folder_hash = $r[0]['hash'];
$res = array();
@@ -468,7 +452,7 @@ class Photos extends \Zotlabs\Web\Controller {
* default post action - upload a photo
*/
- $channel = \App::$data['channel'];
+ $channel = \App::$data['channel'];
$observer = \App::$data['observer'];
$_REQUEST['source'] = 'photos';
@@ -485,12 +469,10 @@ class Photos extends \Zotlabs\Web\Controller {
if(! $r['success']) {
notice($r['message'] . EOL);
+ goaway(z_root() . '/photos/' . \App::$data['channel']['channel_address']);
}
-
- if($_REQUEST['newalbum'])
- goaway(z_root() . '/photos/' . \App::$data['channel']['channel_address'] . '/album/' . bin2hex($_REQUEST['newalbum']));
- else
- goaway(z_root() . '/photos/' . \App::$data['channel']['channel_address'] . '/album/' . bin2hex(datetime_convert('UTC',date_default_timezone_get(),'now', 'Y')));
+
+ goaway(z_root() . '/photos/' . \App::$data['channel']['channel_address'] . '/album/' . $r['data']['folder']);
}
@@ -569,7 +551,11 @@ class Photos extends \Zotlabs\Web\Controller {
return;
}
- $sql_extra = permissions_sql($owner_uid);
+ $sql_item = item_permissions_sql($owner_uid,get_observer_hash());
+ $sql_extra = permissions_sql($owner_uid,get_observer_hash(),'photo');
+ $sql_attach = permissions_sql($owner_uid,get_observer_hash(),'attach');
+
+ nav_set_selected('Photos');
$o = "";
@@ -579,7 +565,7 @@ class Photos extends \Zotlabs\Web\Controller {
// tabs
$_is_owner = (local_channel() && (local_channel() == $owner_uid));
- $o .= profile_tabs($a,$_is_owner, \App::$data['channel']['channel_address']);
+ //$o .= profile_tabs($a,$_is_owner, \App::$data['channel']['channel_address']);
/**
* Display upload form
@@ -628,8 +614,14 @@ class Photos extends \Zotlabs\Web\Controller {
if(! $aclselect) {
$aclselect = '<input id="group_allow" type="hidden" name="allow_gid[]" value="" /><input id="contact_allow" type="hidden" name="allow_cid[]" value="" /><input id="group_deny" type="hidden" name="deny_gid[]" value="" /><input id="contact_deny" type="hidden" name="deny_cid[]" value="" />';
}
-
- $selname = (($datum) ? hex2bin($datum) : '');
+
+ $selname = '';
+
+ if($datum) {
+ $h = attach_by_hash_nodata($datum,get_observer_hash());
+ $selname = $h['data']['display_path'];
+ }
+
$albums = ((array_key_exists('albums', \App::$data)) ? \App::$data['albums'] : photos_albums_list(\App::$data['channel'],\App::$data['observer']));
@@ -679,30 +671,19 @@ class Photos extends \Zotlabs\Web\Controller {
*/
if($datatype === 'album') {
-
- if(strlen($datum)) {
- if((strlen($datum) & 1) || (! ctype_xdigit($datum))) {
- notice( t('Album name could not be decoded') . EOL);
- logger('mod_photos: illegal album encoding: ' . $datum);
- $datum = '';
- goaway(z_root() . '/photos/' . \App::$data['channel']['channel_address']);
- }
- }
-
- $album = (($datum) ? hex2bin($datum) : '');
-
- \App::$page['htmlhead'] .= "\r\n" . '<link rel="alternate" type="application/json+oembed" href="' . z_root() . '/oep?f=&url=' . urlencode(z_root() . '/' . \App::$cmd) . '" title="oembed" />' . "\r\n";
- //check if the album exists and if we have perms
- $r = q("SELECT album FROM photo WHERE uid = %d AND album = '%s' and is_nsfw = %d $sql_extra LIMIT 1",
- intval($owner_uid),
- dbesc($album),
- intval($unsafe)
- );
+ head_add_link([
+ 'rel' => 'alternate',
+ 'type' => 'application/json+oembed',
+ 'href' => z_root() . '/oep?f=&url=' . urlencode(z_root() . '/' . \App::$query_string),
+ 'title' => 'oembed'
+ ]);
- if($r) {
+ if($x = photos_album_exists($owner_uid, get_observer_hash(), $datum)) {
\App::set_pager_itemspage(60);
- } else {
+ $album = $x['display_path'];
+ }
+ else {
goaway(z_root() . '/photos/' . \App::$data['channel']['channel_address']);
}
@@ -712,26 +693,26 @@ class Photos extends \Zotlabs\Web\Controller {
$order = 'DESC';
$r = q("SELECT p.resource_id, p.id, p.filename, p.mimetype, p.imgscale, p.description, p.created FROM photo p INNER JOIN
- (SELECT resource_id, max(imgscale) imgscale FROM photo WHERE uid = %d AND album = '%s' AND imgscale <= 4 AND photo_usage IN ( %d, %d ) and is_nsfw = %d $sql_extra GROUP BY resource_id) ph
+ (SELECT resource_id, max(imgscale) imgscale FROM photo left join attach on folder = '%s' and photo.resource_id = attach.hash WHERE attach.uid = %d AND imgscale <= 4 AND photo_usage IN ( %d, %d ) and is_nsfw = %d $sql_extra GROUP BY resource_id) ph
ON (p.resource_id = ph.resource_id AND p.imgscale = ph.imgscale)
ORDER BY created $order LIMIT %d OFFSET %d",
+ dbesc($x['hash']),
intval($owner_uid),
- dbesc($album),
intval(PHOTO_NORMAL),
intval(PHOTO_PROFILE),
intval($unsafe),
intval(\App::$pager['itemspage']),
intval(\App::$pager['start'])
);
-
- //edit album name
+
+ // edit album name
$album_edit = null;
- if(($album !== t('Profile Photos')) && ($album !== 'Profile Photos') && ($album !== 'Contact Photos') && ($album !== t('Contact Photos'))) {
- if($can_post) {
- $album_e = $album;
- $albums = ((array_key_exists('albums', \App::$data)) ? \App::$data['albums'] : photos_albums_list(\App::$data['channel'],\App::$data['observer']));
+
+ if($can_post) {
+ $album_e = $album;
+ $albums = ((array_key_exists('albums', \App::$data)) ? \App::$data['albums'] : photos_albums_list(\App::$data['channel'],\App::$data['observer']));
- // @fixme - syncronise actions with DAV
+ // @fixme - syncronise actions with DAV
// $edit_tpl = get_markup_template('album_edit.tpl');
// $album_edit = replace_macros($edit_tpl,array(
@@ -745,13 +726,12 @@ class Photos extends \Zotlabs\Web\Controller {
// '$dropsubmit' => t('Delete Album')
// ));
- }
}
if($_GET['order'] === 'posted')
- $order = array(t('Show Newest First'), z_root() . '/photos/' . \App::$data['channel']['channel_address'] . '/album/' . bin2hex($album));
+ $order = array(t('Show Newest First'), z_root() . '/photos/' . \App::$data['channel']['channel_address'] . '/album/' . $datum);
else
- $order = array(t('Show Oldest First'), z_root() . '/photos/' . \App::$data['channel']['channel_address'] . '/album/' . bin2hex($album) . '?f=&order=posted');
+ $order = array(t('Show Oldest First'), z_root() . '/photos/' . \App::$data['channel']['channel_address'] . '/album/' . $datum . '?f=&order=posted');
$photos = array();
if(count($r)) {
@@ -790,7 +770,7 @@ class Photos extends \Zotlabs\Web\Controller {
if($photos) {
$o = replace_macros(get_markup_template('photosajax.tpl'),array(
'$photos' => $photos,
- '$album_id' => bin2hex($album)
+ '$album_id' => $datum
));
}
else {
@@ -805,10 +785,10 @@ class Photos extends \Zotlabs\Web\Controller {
$o .= replace_macros($tpl, array(
'$photos' => $photos,
'$album' => $album,
- '$album_id' => bin2hex($album),
+ '$album_id' => $datum,
'$album_edit' => array(t('Edit Album'), $album_edit),
'$can_post' => $can_post,
- '$upload' => array(t('Upload'), z_root() . '/photos/' . \App::$data['channel']['channel_address'] . '/upload/' . bin2hex($album)),
+ '$upload' => array(t('Upload'), z_root() . '/photos/' . \App::$data['channel']['channel_address'] . '/upload/' . $datum),
'$order' => $order,
'$upload_form' => $upload_form,
'$usage' => $usage_message
@@ -822,8 +802,6 @@ class Photos extends \Zotlabs\Web\Controller {
killme();
}
- // $o .= paginate($a);
-
return $o;
}
@@ -836,6 +814,11 @@ class Photos extends \Zotlabs\Web\Controller {
\App::$page['htmlhead'] .= "\r\n" . '<link rel="alternate" type="application/json+oembed" href="' . z_root() . '/oep?f=&url=' . urlencode(z_root() . '/' . \App::$cmd) . '" title="oembed" />' . "\r\n";
+ $x = q("select folder from attach where hash = '%s' and uid = %d $sql_attach limit 1",
+ dbesc($datum),
+ intval($owner_uid)
+ );
+
// fetch image, item containing image, then comments
$ph = q("SELECT id,aid,uid,xchan,resource_id,created,edited,title,description,album,filename,mimetype,height,width,filesize,imgscale,photo_usage,is_nsfw,allow_cid,allow_gid,deny_cid,deny_gid FROM photo WHERE uid = %d AND resource_id = '%s'
@@ -844,7 +827,7 @@ class Photos extends \Zotlabs\Web\Controller {
dbesc($datum)
);
- if(! $ph) {
+ if(! ($ph && $x)) {
/* Check again - this time without specifying permissions */
@@ -869,16 +852,16 @@ class Photos extends \Zotlabs\Web\Controller {
else
$order = 'DESC';
-
- $prvnxt = q("SELECT resource_id FROM photo WHERE album = '%s' AND uid = %d AND imgscale = 0
- $sql_extra ORDER BY created $order ",
- dbesc($ph[0]['album']),
+
+ $prvnxt = q("SELECT hash FROM attach WHERE folder = '%s' AND uid = %d AND is_photo = 1
+ $sql_attach ORDER BY created $order ",
+ dbesc($x[0]['folder']),
intval($owner_uid)
);
-
+
if(count($prvnxt)) {
for($z = 0; $z < count($prvnxt); $z++) {
- if($prvnxt[$z]['resource_id'] == $ph[0]['resource_id']) {
+ if($prvnxt[$z]['hash'] == $ph[0]['resource_id']) {
$prv = $z - 1;
$nxt = $z + 1;
if($prv < 0)
@@ -889,8 +872,8 @@ class Photos extends \Zotlabs\Web\Controller {
}
}
- $prevlink = z_root() . '/photos/' . \App::$data['channel']['channel_address'] . '/image/' . $prvnxt[$prv]['resource_id'] . (($_GET['order'] === 'posted') ? '?f=&order=posted' : '');
- $nextlink = z_root() . '/photos/' . \App::$data['channel']['channel_address'] . '/image/' . $prvnxt[$nxt]['resource_id'] . (($_GET['order'] === 'posted') ? '?f=&order=posted' : '');
+ $prevlink = z_root() . '/photos/' . \App::$data['channel']['channel_address'] . '/image/' . $prvnxt[$prv]['hash'] . (($_GET['order'] === 'posted') ? '?f=&order=posted' : '');
+ $nextlink = z_root() . '/photos/' . \App::$data['channel']['channel_address'] . '/image/' . $prvnxt[$nxt]['hash'] . (($_GET['order'] === 'posted') ? '?f=&order=posted' : '');
}
@@ -907,7 +890,7 @@ class Photos extends \Zotlabs\Web\Controller {
}
}
- $album_link = z_root() . '/photos/' . \App::$data['channel']['channel_address'] . '/album/' . bin2hex($ph[0]['album']);
+ $album_link = z_root() . '/photos/' . \App::$data['channel']['channel_address'] . '/album/' . $x[0]['folder'];
$tools = Null;
$lock = Null;
@@ -947,7 +930,7 @@ class Photos extends \Zotlabs\Web\Controller {
// Do we have an item for this photo?
$linked_items = q("SELECT * FROM item WHERE resource_id = '%s' and resource_type = 'photo'
- $sql_extra LIMIT 1",
+ $sql_item LIMIT 1",
dbesc($datum)
);
@@ -962,7 +945,7 @@ class Photos extends \Zotlabs\Web\Controller {
$item_normal = item_normal();
$r = q("select * from item where parent_mid = '%s'
- $item_normal and uid = %d $sql_extra ",
+ $item_normal and uid = %d $sql_item ",
dbesc($link_item['mid']),
intval($link_item['uid'])
@@ -1008,13 +991,6 @@ class Photos extends \Zotlabs\Web\Controller {
$edit = null;
if($can_post) {
- $m = q("select folder from attach where hash = '%s' and uid = %d limit 1",
- dbesc($ph[0]['resource_id']),
- intval($ph[0]['uid'])
- );
- if($m)
- $album_hash = $m[0]['folder'];
-
$album_e = $ph[0]['album'];
$caption_e = $ph[0]['description'];
$aclselect_e = (($_is_owner) ? populate_acl($ph[0], true, \Zotlabs\Lib\PermissionDescription::fromGlobalPermission('view_storage')) : '');
@@ -1024,35 +1000,35 @@ class Photos extends \Zotlabs\Web\Controller {
$folder_list = attach_folder_select_list($ph[0]['uid']);
- $edit = array(
+ $edit = [
'edit' => t('Edit photo'),
'id' => $link_item['id'],
- 'rotatecw' => t('Rotate CW (right)'),
- 'rotateccw' => t('Rotate CCW (left)'),
- 'albums' => $albums['albums'],
- 'album' => $album_e,
- 'album_select' => [ 'move_to_album', t('Move photo to album'), $album_hash, '', $folder_list ],
- 'newalbum_label' => t('Enter a new album name'),
+ 'rotatecw' => t('Rotate CW (right)'),
+ 'rotateccw' => t('Rotate CCW (left)'),
+ 'albums' => $albums['albums'],
+ 'album' => $album_e,
+ 'album_select' => [ 'move_to_album', t('Move photo to album'), $x[0]['folder'], '', $folder_list ],
+ 'newalbum_label' => t('Enter a new album name'),
'newalbum_placeholder' => t('or select an existing one (doubleclick)'),
- 'nickname' => \App::$data['channel']['channel_address'],
- 'resource_id' => $ph[0]['resource_id'],
- 'capt_label' => t('Caption'),
- 'caption' => $caption_e,
- 'tag_label' => t('Add a Tag'),
- 'permissions' => t('Permissions'),
- 'aclselect' => $aclselect_e,
- 'allow_cid' => acl2json($ph[0]['allow_cid']),
- 'allow_gid' => acl2json($ph[0]['allow_gid']),
- 'deny_cid' => acl2json($ph[0]['deny_cid']),
- 'deny_gid' => acl2json($ph[0]['deny_gid']),
- 'lockstate' => $lockstate[0],
- 'help_tags' => t('Example: @bob, @Barbara_Jensen, @jim@example.com'),
- 'item_id' => ((count($linked_items)) ? $link_item['id'] : 0),
- 'adult_enabled' => feature_enabled($owner_uid,'adult_photo_flagging'),
- 'adult' => array('adult',t('Flag as adult in album view'), intval($ph[0]['is_nsfw']),''),
- 'submit' => t('Submit'),
- 'delete' => t('Delete Photo')
- );
+ 'nickname' => \App::$data['channel']['channel_address'],
+ 'resource_id' => $ph[0]['resource_id'],
+ 'capt_label' => t('Caption'),
+ 'caption' => $caption_e,
+ 'tag_label' => t('Add a Tag'),
+ 'permissions' => t('Permissions'),
+ 'aclselect' => $aclselect_e,
+ 'allow_cid' => acl2json($ph[0]['allow_cid']),
+ 'allow_gid' => acl2json($ph[0]['allow_gid']),
+ 'deny_cid' => acl2json($ph[0]['deny_cid']),
+ 'deny_gid' => acl2json($ph[0]['deny_gid']),
+ 'lockstate' => $lockstate[0],
+ 'help_tags' => t('Example: @bob, @Barbara_Jensen, @jim@example.com'),
+ 'item_id' => ((count($linked_items)) ? $link_item['id'] : 0),
+ 'adult_enabled' => feature_enabled($owner_uid,'adult_photo_flagging'),
+ 'adult' => array('adult',t('Flag as adult in album view'), intval($ph[0]['is_nsfw']),''),
+ 'submit' => t('Submit'),
+ 'delete' => t('Delete Photo')
+ ];
}
if(count($linked_items)) {
@@ -1065,19 +1041,19 @@ class Photos extends \Zotlabs\Web\Controller {
$likebuttons = '';
- if($can_post || $can_comment) {
- $likebuttons = array(
- 'id' => $link_item['id'],
+ if($observer && ($can_post || $can_comment)) {
+ $likebuttons = [
+ 'id' => $link_item['id'],
'likethis' => t("I like this \x28toggle\x29"),
- 'nolike' => t("I don't like this \x28toggle\x29"),
- 'share' => t('Share'),
- 'wait' => t('Please wait')
- );
+ 'nolike' => t("I don't like this \x28toggle\x29"),
+ 'share' => t('Share'),
+ 'wait' => t('Please wait')
+ ];
}
$comments = '';
if(! count($r)) {
- if($can_post || $can_comment) {
+ if($observer && ($can_post || $can_comment)) {
$commentbox = replace_macros($cmnt_tpl,array(
'$return_path' => '',
'$mode' => 'photos',
@@ -1196,7 +1172,7 @@ class Photos extends \Zotlabs\Web\Controller {
}
- if($can_post || $can_comment) {
+ if($observer && ($can_post || $can_comment)) {
$commentbox = replace_macros($cmnt_tpl,array(
'$return_path' => '',
'$jsreload' => $return_url,
@@ -1277,25 +1253,13 @@ class Photos extends \Zotlabs\Web\Controller {
\App::$page['htmlhead'] .= "\r\n" . '<link rel="alternate" type="application/json+oembed" href="' . z_root() . '/oep?f=&url=' . urlencode(z_root() . '/' . \App::$cmd) . '" title="oembed" />' . "\r\n";
- /*
- $r = q("SELECT resource_id, max(imgscale) AS imgscale FROM photo WHERE uid = %d
- and photo_usage in ( %d, %d ) and is_nsfw = %d $sql_extra GROUP BY resource_id",
- intval(\App::$data['channel']['channel_id']),
- intval(PHOTO_NORMAL),
- intval(PHOTO_PROFILE),
- intval($unsafe)
- );
- if($r) {
- \App::set_pager_total(count($r));
- \App::set_pager_itemspage(60);
- }
- */
\App::set_pager_itemspage(60);
- $r = q("SELECT p.resource_id, p.id, p.filename, p.mimetype, p.album, p.imgscale, p.created FROM photo p
+ $r = q("SELECT p.resource_id, p.id, p.filename, p.mimetype, p.album, p.imgscale, p.created, p.display_path
+ FROM photo p
INNER JOIN ( SELECT resource_id, max(imgscale) imgscale FROM photo
- WHERE uid = %d AND photo_usage IN ( %d, %d )
+ WHERE photo.uid = %d AND photo_usage IN ( %d, %d )
AND is_nsfw = %d $sql_extra group by resource_id ) ph
ON (p.resource_id = ph.resource_id and p.imgscale = ph.imgscale)
ORDER by p.created DESC LIMIT %d OFFSET %d",
@@ -1313,21 +1277,19 @@ class Photos extends \Zotlabs\Web\Controller {
if($r) {
$twist = 'rotright';
foreach($r as $rr) {
+
+ if(! attach_can_view_folder(\App::$data['channel']['channel_id'],get_observer_hash(),$rr['resource_id']))
+ continue;
+
if($twist == 'rotright')
$twist = 'rotleft';
else
$twist = 'rotright';
$ext = $phototypes[$rr['mimetype']];
- if(\App::get_template_engine() === 'internal') {
- $alt_e = template_escape($rr['filename']);
- $name_e = template_escape($rr['album']);
- }
- else {
- $alt_e = $rr['filename'];
- $name_e = $rr['album'];
- }
-
+ $alt_e = $rr['filename'];
+ $name_e = dirname($rr['display_path']);
+
$photos[] = array(
'id' => $rr['id'],
'twist' => ' ' . $twist . rand(2,4),
@@ -1336,9 +1298,7 @@ class Photos extends \Zotlabs\Web\Controller {
'src' => z_root() . '/photo/' . $rr['resource_id'] . '-' . ((($rr['imgscale']) == 6) ? 4 : $rr['imgscale']) . '.' . $ext,
'alt' => $alt_e,
'album' => array(
- 'link' => z_root() . '/photos/' . \App::$data['channel']['channel_address'] . '/album/' . bin2hex($rr['album']),
'name' => $name_e,
- 'alt' => t('View Album'),
),
);
diff --git a/Zotlabs/Module/Ping.php b/Zotlabs/Module/Ping.php
index bf2fa5cc9..c91659f2f 100644
--- a/Zotlabs/Module/Ping.php
+++ b/Zotlabs/Module/Ping.php
@@ -19,6 +19,7 @@ class Ping extends \Zotlabs\Web\Controller {
* @result JSON
*/
function init() {
+
$result = array();
$notifs = array();
@@ -36,6 +37,11 @@ class Ping extends \Zotlabs\Web\Controller {
$result['all_events_today'] = 0;
$result['notice'] = array();
$result['info'] = array();
+ $result['pubs'] = 0;
+ $result['files'] = 0;
+
+ if(! $_SESSION['static_loadtime'])
+ $_SESSION['static_loadtime'] = datetime_convert();
$t0 = dba_timer();
@@ -134,6 +140,61 @@ class Ping extends \Zotlabs\Web\Controller {
db_utcnow(), db_quoteinterval('3 MINUTE')
);
+ $discover_tab_on = ((get_config('system','disable_discover_tab') != 1) ? true : false);
+ $notify_pubs = ((local_channel()) ? ($vnotify & VNOTIFY_PUBS) && $discover_tab_on : $discover_tab_on);
+
+ if($notify_pubs) {
+ $sys = get_sys_channel();
+
+ $pubs = q("SELECT count(id) as total from item
+ WHERE uid = %d
+ AND author_xchan != '%s'
+ AND obj_type != '%s'
+ AND item_unseen = 1
+ AND created > '" . datetime_convert('UTC','UTC',$_SESSION['static_loadtime']) . "'
+ $item_normal",
+ intval($sys['channel_id']),
+ dbesc(get_observer_hash()),
+ dbesc(ACTIVITY_OBJ_FILE)
+ );
+
+ if($pubs)
+ $result['pubs'] = intval($pubs[0]['total']);
+ }
+
+ if((argc() > 1) && (argv(1) === 'pubs') && ($notify_pubs)) {
+ $sys = get_sys_channel();
+ $result = array();
+
+ $r = q("SELECT * FROM item
+ WHERE uid = %d
+ AND author_xchan != '%s'
+ AND obj_type != '%s'
+ AND item_unseen = 1
+ AND created > '" . datetime_convert('UTC','UTC',$_SESSION['static_loadtime']) . "'
+ $item_normal
+ ORDER BY created DESC
+ LIMIT 300",
+ intval($sys['channel_id']),
+ dbesc(get_observer_hash()),
+ dbesc(ACTIVITY_OBJ_FILE)
+ );
+
+ if($r) {
+ xchan_query($r);
+ foreach($r as $rr) {
+ $rr['llink'] = str_replace('display/', 'pubstream/?f=&mid=', $rr['llink']);
+ $result[] = \Zotlabs\Lib\Enotify::format($rr);
+ }
+ }
+
+// logger('ping (network||home): ' . print_r($result, true), LOGGER_DATA);
+ echo json_encode(array('notify' => $result));
+ killme();
+ }
+
+ $t1 = dba_timer();
+
if((! local_channel()) || ($result['invalid'])) {
echo json_encode($result);
killme();
@@ -177,6 +238,9 @@ class Ping extends \Zotlabs\Web\Controller {
intval(local_channel())
);
break;
+ case 'pubs':
+ unset($_SESSION['static_loadtime']);
+ break;
default:
break;
}
@@ -194,37 +258,20 @@ class Ping extends \Zotlabs\Web\Controller {
* dropdown menu.
*/
if(argc() > 1 && argv(1) === 'notify') {
- $t = q("select count(*) as total from notify where uid = %d and seen = 0",
+ $t = q("select * from notify where uid = %d and seen = 0 order by created desc",
intval(local_channel())
);
- if($t && intval($t[0]['total']) > 49) {
- $z = q("select * from notify where uid = %d
- and seen = 0 order by created desc limit 50",
- intval(local_channel())
- );
- } else {
- $z1 = q("select * from notify where uid = %d
- and seen = 0 order by created desc limit 50",
- intval(local_channel())
- );
- $z2 = q("select * from notify where uid = %d
- and seen = 1 order by created desc limit %d",
- intval(local_channel()),
- intval(50 - intval($t[0]['total']))
- );
- $z = array_merge($z1,$z2);
- }
- if(count($z)) {
- foreach($z as $zz) {
+ if($t) {
+ foreach($t as $tt) {
$notifs[] = array(
- 'notify_link' => z_root() . '/notify/view/' . $zz['id'],
- 'name' => $zz['xname'],
- 'url' => $zz['url'],
- 'photo' => $zz['photo'],
- 'when' => relative_date($zz['created']),
- 'hclass' => (($zz['seen']) ? 'notify-seen' : 'notify-unseen'),
- 'message' => strip_tags(bbcode($zz['msg']))
+ 'notify_link' => z_root() . '/notify/view/' . $tt['id'],
+ 'name' => $tt['xname'],
+ 'url' => $tt['url'],
+ 'photo' => $tt['photo'],
+ 'when' => relative_date($tt['created']),
+ 'hclass' => (($tt['seen']) ? 'notify-seen' : 'notify-unseen'),
+ 'message' => strip_tags(bbcode($tt['msg']))
);
}
}
@@ -233,7 +280,7 @@ class Ping extends \Zotlabs\Web\Controller {
killme();
}
- if(argc() > 1 && argv(1) === 'messages') {
+ if(argc() > 1 && argv(1) === 'mail') {
$channel = \App::get_channel();
$t = q("select mail.*, xchan.* from mail left join xchan on xchan_hash = from_xchan
where channel_id = %d and mail_seen = 0 and mail_deleted = 0
@@ -265,9 +312,12 @@ class Ping extends \Zotlabs\Web\Controller {
$r = q("SELECT * FROM item
WHERE item_unseen = 1 and uid = %d $item_normal
- and author_xchan != '%s' ORDER BY created DESC limit 300",
+ AND author_xchan != '%s'
+ AND obj_type != '%s'
+ ORDER BY created DESC limit 300",
intval(local_channel()),
- dbesc($ob_hash)
+ dbesc($ob_hash),
+ dbesc(ACTIVITY_OBJ_FILE)
);
if($r) {
@@ -308,6 +358,30 @@ class Ping extends \Zotlabs\Web\Controller {
killme();
}
+ if((argc() > 1 && (argv(1) === 'register')) && is_site_admin()) {
+ $result = array();
+
+ $r = q("SELECT account_email, account_created from account where (account_flags & %d) > 0",
+ intval(ACCOUNT_PENDING)
+ );
+ if($r) {
+ foreach($r as $rr) {
+ $result[] = array(
+ 'notify_link' => z_root() . '/admin/accounts',
+ 'name' => $rr['account_email'],
+ 'url' => '',
+ 'photo' => get_default_profile_photo(48),
+ 'when' => relative_date($rr['account_created']),
+ 'hclass' => ('notify-unseen'),
+ 'message' => t('requires approval')
+ );
+ }
+ }
+ logger('ping (register): ' . print_r($result, true), LOGGER_DATA);
+ echo json_encode(array('notify' => $result));
+ killme();
+ }
+
if(argc() > 1 && (argv(1) === 'all_events')) {
$bd_format = t('g A l F d') ; // 8 AM Friday January 18
@@ -345,6 +419,39 @@ class Ping extends \Zotlabs\Web\Controller {
killme();
}
+ if(argc() > 1 && (argv(1) === 'files')) {
+ $result = array();
+
+ $r = q("SELECT item.created, xchan.xchan_name, xchan.xchan_url, xchan.xchan_photo_s FROM item
+ LEFT JOIN xchan on author_xchan = xchan_hash
+ WHERE item.verb = '%s'
+ AND item.obj_type = '%s'
+ AND item.uid = %d
+ AND item.owner_xchan != '%s'
+ AND item.item_unseen = 1",
+ dbesc(ACTIVITY_POST),
+ dbesc(ACTIVITY_OBJ_FILE),
+ intval(local_channel()),
+ dbesc($ob_hash)
+ );
+ if($r) {
+ foreach($r as $rr) {
+ $result[] = array(
+ 'notify_link' => z_root() . '/sharedwithme',
+ 'name' => $rr['xchan_name'],
+ 'url' => $rr['xchan_url'],
+ 'photo' => $rr['xchan_photo_s'],
+ 'when' => relative_date($rr['created']),
+ 'hclass' => ('notify-unseen'),
+ 'message' => t('shared a file with you')
+ );
+ }
+ }
+ logger('ping (files): ' . print_r($result, true), LOGGER_DATA);
+ echo json_encode(array('notify' => $result));
+ killme();
+ }
+
/**
* Normal ping - just the counts, no detail
*/
@@ -356,15 +463,35 @@ class Ping extends \Zotlabs\Web\Controller {
$result['notify'] = intval($t[0]['total']);
}
- $t1 = dba_timer();
+ $t2 = dba_timer();
+
+ if($vnotify & VNOTIFY_FILES) {
+ $files = q("SELECT count(id) as total FROM item
+ WHERE verb = '%s'
+ AND obj_type = '%s'
+ AND uid = %d
+ AND owner_xchan != '%s'
+ AND item_unseen = 1",
+ dbesc(ACTIVITY_POST),
+ dbesc(ACTIVITY_OBJ_FILE),
+ intval(local_channel()),
+ dbesc($ob_hash)
+ );
+ if($files)
+ $result['files'] = intval($files[0]['total']);
+ }
+
+ $t3 = dba_timer();
if($vnotify & (VNOTIFY_NETWORK|VNOTIFY_CHANNEL)) {
$r = q("SELECT id, item_wall FROM item
WHERE item_unseen = 1 and uid = %d
$item_normal
- and author_xchan != '%s'",
+ AND author_xchan != '%s'
+ AND obj_type != '%s'",
intval(local_channel()),
- dbesc($ob_hash)
+ dbesc($ob_hash),
+ dbesc(ACTIVITY_OBJ_FILE)
);
if($r) {
@@ -384,20 +511,20 @@ class Ping extends \Zotlabs\Web\Controller {
if(! ($vnotify & VNOTIFY_CHANNEL))
$result['home'] = 0;
- $t2 = dba_timer();
+ $t4 = dba_timer();
if($vnotify & VNOTIFY_INTRO) {
$intr = q("SELECT COUNT(abook.abook_id) AS total FROM abook left join xchan on abook.abook_xchan = xchan.xchan_hash where abook_channel = %d and abook_pending = 1 and abook_self = 0 and abook_ignored = 0 and xchan_deleted = 0 and xchan_orphan = 0 ",
intval(local_channel())
);
- $t3 = dba_timer();
+ $t5 = dba_timer();
if($intr)
$result['intros'] = intval($intr[0]['total']);
}
- $t4 = dba_timer();
+ $t6 = dba_timer();
$channel = \App::get_channel();
if($vnotify & VNOTIFY_MAIL) {
@@ -420,7 +547,7 @@ class Ping extends \Zotlabs\Web\Controller {
}
}
- $t5 = dba_timer();
+ $t7 = dba_timer();
if($vnotify & (VNOTIFY_EVENT|VNOTIFY_EVENTTODAY|VNOTIFY_BIRTHDAY)) {
$events = q("SELECT etype, dtstart, adjust FROM event
@@ -466,9 +593,9 @@ class Ping extends \Zotlabs\Web\Controller {
$x = json_encode($result);
- $t6 = dba_timer();
+ $t8 = dba_timer();
-// logger('ping timer: ' . sprintf('%01.4f %01.4f %01.4f %01.4f %01.4f %01.4f',$t6 - $t5, $t5 - $t4, $t4 - $t3, $t3 - $t2, $t2 - $t1, $t1 - $t0));
+// logger('ping timer: ' . sprintf('%01.4f %01.4f %01.4f %01.4f %01.4f %01.4f %01.4f %01.4f',$t8 - $t7, $t7 - $t6, $t6 - $t5, $t5 - $t4, $t4 - $t3, $t3 - $t2, $t2 - $t1, $t1 - $t0));
echo $x;
killme();
diff --git a/Zotlabs/Module/Poke.php b/Zotlabs/Module/Poke.php
index cf8d83023..d13ec5ced 100644
--- a/Zotlabs/Module/Poke.php
+++ b/Zotlabs/Module/Poke.php
@@ -41,7 +41,10 @@ class Poke extends \Zotlabs\Web\Controller {
$activity = ACTIVITY_POKE . '#' . urlencode($verbs[$verb][0]);
$contact_id = intval($_REQUEST['cid']);
- if(! $contact_id)
+
+ $xchan = trim($_REQUEST['xchan']);
+
+ if(! ($contact_id || $xchan))
return;
$parent = ((x($_REQUEST,'parent')) ? intval($_REQUEST['parent']) : 0);
@@ -49,13 +52,20 @@ class Poke extends \Zotlabs\Web\Controller {
logger('poke: verb ' . $verb . ' contact ' . $contact_id, LOGGER_DEBUG);
- $r = q("SELECT * FROM abook left join xchan on xchan_hash = abook_xchan where abook_id = %d and abook_channel = %d LIMIT 1",
- intval($contact_id),
- intval($uid)
- );
-
+ if($contact_id) {
+ $r = q("SELECT * FROM abook left join xchan on xchan_hash = abook_xchan where abook_id = %d and abook_channel = %d LIMIT 1",
+ intval($contact_id),
+ intval($uid)
+ );
+ }
+ if($xchan) {
+ $r = q("SELECT * FROM xchan where xchan_hash like ( '%s' ) LIMIT 1",
+ dbesc($xchan . '%')
+ );
+ }
+
if(! $r) {
- logger('poke: no target ' . $contact_id);
+ logger('poke: no target.');
return;
}
@@ -79,7 +89,7 @@ class Poke extends \Zotlabs\Web\Controller {
$deny_gid = $r[0]['deny_gid'];
}
}
- else {
+ elseif($contact_id) {
$item_private = ((x($_GET,'private')) ? intval($_GET['private']) : 0);
@@ -92,9 +102,11 @@ class Poke extends \Zotlabs\Web\Controller {
$arr = array();
+
+
$arr['item_wall'] = 1;
$arr['owner_xchan'] = (($parent_item) ? $parent_item['owner_xchan'] : $channel['channel_hash']);
- $arr['parent_mid'] = (($parent_mid) ? $parent_mid : $mid);
+ $arr['parent_mid'] = (($parent_mid) ? $parent_mid : '');
$arr['title'] = '';
$arr['allow_cid'] = $allow_cid;
$arr['allow_gid'] = $allow_gid;
@@ -131,12 +143,14 @@ class Poke extends \Zotlabs\Web\Controller {
- function get() {
+ function get() {
if(! local_channel()) {
notice( t('Permission denied.') . EOL);
return;
}
+
+ nav_set_selected('Poke');
$name = '';
$id = '';
diff --git a/Zotlabs/Module/Post.php b/Zotlabs/Module/Post.php
index c78484a45..f67cbf020 100644
--- a/Zotlabs/Module/Post.php
+++ b/Zotlabs/Module/Post.php
@@ -19,16 +19,16 @@ class Post extends \Zotlabs\Web\Controller {
function init() {
if(array_key_exists('auth', $_REQUEST)) {
$x = new \Zotlabs\Zot\Auth($_REQUEST);
-
exit;
}
}
function post() {
- $z = new \Zotlabs\Zot\Receiver($_REQUEST['data'], get_config('system', 'prvkey'), new \Zotlabs\Zot\ZotHandler());
+ if(array_key_exists('data',$_REQUEST)) {
+ $z = new \Zotlabs\Zot\Receiver($_REQUEST['data'], get_config('system', 'prvkey'), new \Zotlabs\Zot\ZotHandler());
+ exit;
+ }
- // notreached;
- exit;
}
}
diff --git a/Zotlabs/Module/Probe.php b/Zotlabs/Module/Probe.php
index 7fc0e8ff5..2e65f107c 100644
--- a/Zotlabs/Module/Probe.php
+++ b/Zotlabs/Module/Probe.php
@@ -7,7 +7,9 @@ require_once('include/zot.php');
class Probe extends \Zotlabs\Web\Controller {
function get() {
-
+
+ nav_set_selected('Remote Diagnostics');
+
$o .= '<h3>Probe Diagnostic</h3>';
$o .= '<form action="probe" method="get">';
diff --git a/Zotlabs/Module/Profile.php b/Zotlabs/Module/Profile.php
index 0bc23952b..43106e3af 100644
--- a/Zotlabs/Module/Profile.php
+++ b/Zotlabs/Module/Profile.php
@@ -21,6 +21,8 @@ class Profile extends \Zotlabs\Web\Controller {
\App::$error = 404;
return;
}
+
+ nav_set_selected('Profile');
$profile = '';
$channel = \App::get_channel();
@@ -37,8 +39,21 @@ class Profile extends \Zotlabs\Web\Controller {
$profile = $r[0]['profile_guid'];
}
- \App::$page['htmlhead'] .= '<link rel="alternate" type="application/atom+xml" href="' . z_root() . '/feed/' . $which .'" />' . "\r\n" ;
-
+ head_add_link( [
+ 'rel' => 'alternate',
+ 'type' => 'application/atom+xml',
+ 'title' => t('Posts and comments'),
+ 'href' => z_root() . '/feed/' . $which
+ ]);
+
+ head_add_link( [
+ 'rel' => 'alternate',
+ 'type' => 'application/atom+xml',
+ 'title' => t('Only posts'),
+ 'href' => z_root() . '/feed/' . $which . '?f=&top=1'
+ ]);
+
+
if(! $profile) {
$x = q("select channel_id as profile_uid from channel where channel_address = '%s' limit 1",
dbesc(argv(1))
@@ -79,7 +94,6 @@ class Profile extends \Zotlabs\Web\Controller {
echo \App::$profile['profile_vcard'];
killme();
}
-
$is_owner = ((local_channel()) && (local_channel() == \App::$profile['profile_uid']) ? true : false);
@@ -87,11 +101,14 @@ class Profile extends \Zotlabs\Web\Controller {
notice( t('Permission denied.') . EOL);
return;
}
-
- $o .= profile_tabs($a, $is_owner, \App::$profile['channel_address']);
-
- \App::$page['htmlhead'] .= "\r\n" . '<link rel="alternate" type="application/json+oembed" href="' . z_root() . '/oep?f=&url=' . urlencode(z_root() . '/' . \App::$query_string) . '" title="oembed" />' . "\r\n";
-
+
+ head_add_link([
+ 'rel' => 'alternate',
+ 'type' => 'application/json+oembed',
+ 'href' => z_root() . '/oep?f=&url=' . urlencode(z_root() . '/' . \App::$query_string),
+ 'title' => 'oembed'
+ ]);
+
$o .= advanced_profile($a);
call_hooks('profile_advanced',$o);
return $o;
diff --git a/Zotlabs/Module/Profile_photo.php b/Zotlabs/Module/Profile_photo.php
index 29a239f4d..27e6bc445 100644
--- a/Zotlabs/Module/Profile_photo.php
+++ b/Zotlabs/Module/Profile_photo.php
@@ -108,11 +108,13 @@ class Profile_photo extends \Zotlabs\Web\Controller {
$aid = get_account_id();
$p = [
- 'aid' => $aid,
- 'uid' => local_channel(),
- 'resource_id' => $base_image['resource_id'],
- 'filename' => $base_image['filename'],
- 'album' => t('Profile Photos')
+ 'aid' => $aid,
+ 'uid' => local_channel(),
+ 'resource_id' => $base_image['resource_id'],
+ 'filename' => $base_image['filename'],
+ 'album' => t('Profile Photos'),
+ 'os_path' => $base_image['os_path'],
+ 'display_path' => $base_image['display_path']
];
$p['imgscale'] = PHOTO_RES_PROFILE_300;
@@ -156,6 +158,9 @@ class Profile_photo extends \Zotlabs\Web\Controller {
intval(local_channel())
);
+
+
+
send_profile_photo_activity($channel,$base_image,$profile);
}
@@ -172,19 +177,28 @@ class Profile_photo extends \Zotlabs\Web\Controller {
// We'll set the updated profile-photo timestamp even if it isn't the default profile,
// so that browsers will do a cache update unconditionally
+ // Also set links back to site-specific profile photo url in case it was
+ // changed to a generic URL by a clone operation. Otherwise the new photo may
+ // not get pushed to other sites correctly.
-
- $r = q("UPDATE xchan set xchan_photo_mimetype = '%s', xchan_photo_date = '%s'
+ $r = q("UPDATE xchan set xchan_photo_mimetype = '%s', xchan_photo_date = '%s', xchan_photo_l = '%s', xchan_photo_m = '%s', xchan_photo_s = '%s'
where xchan_hash = '%s'",
dbesc($im->getType()),
dbesc(datetime_convert()),
+ dbesc(z_root() . '/photo/profile/l/' . $channel['channel_id']),
+ dbesc(z_root() . '/photo/profile/m/' . $channel['channel_id']),
+ dbesc(z_root() . '/photo/profile/s/' . $channel['channel_id']),
dbesc($channel['xchan_hash'])
);
photo_profile_setperms(local_channel(),$base_image['resource_id'],$_REQUEST['profile']);
+ $sync = attach_export_data($channel,$base_image['resource_id']);
+ if($sync)
+ build_sync_packet($channel['channel_id'],array('file' => array($sync)));
- // Similarly, tell the nav bar to bypass the cache and update the avater image.
+
+ // Similarly, tell the nav bar to bypass the cache and update the avatar image.
$_SESSION['reload_avatar'] = true;
info( t('Shift-reload the page or clear browser cache if the new photo does not display immediately.') . EOL);
@@ -341,6 +355,11 @@ class Profile_photo extends \Zotlabs\Web\Controller {
photo_profile_setperms(local_channel(),$resource_id,$_REQUEST['profile']);
+ $sync = attach_export_data($channel,$resource_id);
+ if($sync)
+ build_sync_packet($channel['channel_id'],array('file' => array($sync)));
+
+
\Zotlabs\Daemon\Master::Summon(array('Directory',local_channel()));
goaway(z_root() . '/profiles');
}
diff --git a/Zotlabs/Module/Profiles.php b/Zotlabs/Module/Profiles.php
index 32e888f14..b1cf9596c 100644
--- a/Zotlabs/Module/Profiles.php
+++ b/Zotlabs/Module/Profiles.php
@@ -9,7 +9,7 @@ class Profiles extends \Zotlabs\Web\Controller {
function init() {
- nav_set_selected('profiles');
+ nav_set_selected('Profiles');
if(! local_channel()) {
return;
@@ -317,8 +317,10 @@ class Profiles extends \Zotlabs\Web\Controller {
$hide_friends = ((intval($_POST['hide_friends'])) ? 1: 0);
+// start fresh and create a new vcard. TODO: preserve the original guid or whatever else needs saving
+// $orig_vcard = (($orig[0]['profile_vcard']) ? \Sabre\VObject\Reader::read($orig[0]['profile_vcard']) : null);
- $orig_vcard = (($orig[0]['profile_vcard']) ? \Sabre\VObject\Reader::read($orig[0]['profile_vcard']) : null);
+ $orig_vcard = null;
$channel = \App::get_channel();
@@ -330,13 +332,7 @@ class Profiles extends \Zotlabs\Web\Controller {
'photo' => $channel['xchan_photo_l'],
'adr' => [],
'adr_type' => [ $default_vcard_cat ],
- 'tel' => [],
- 'tel_type' => [ $default_vcard_cat ],
- 'email' => [],
- 'email_type' => [ $default_vcard_cat ],
- 'impp' => [],
- 'impp_type' => [ $default_vcard_cat ],
- 'url' => [],
+ 'url' => [ $homepage ],
'url_type' => [ $default_vcard_cat ]
];
@@ -350,9 +346,12 @@ class Profiles extends \Zotlabs\Web\Controller {
6 => $country_name
];
-
$profile_vcard = update_vcard($defcard,$orig_vcard);
+ $orig_vcard = \Sabre\VObject\Reader::read($profile_vcard);
+
+ $profile_vcard = update_vcard($_REQUEST,$orig_vcard);
+
require_once('include/text.php');
linkify_tags($a, $likes, local_channel());
@@ -700,6 +699,10 @@ class Profiles extends \Zotlabs\Web\Controller {
}
//logger('extra_fields: ' . print_r($extra_fields,true));
+
+ $vc = $r[0]['profile_vcard'];
+ $vctmp = (($vc) ? \Sabre\VObject\Reader::read($vc) : null);
+ $vcard = (($vctmp) ? get_vcard_array($vctmp,$r[0]['id']) : [] );
$f = get_config('system','birthday_input_format');
if(! $f)
@@ -717,6 +720,7 @@ class Profiles extends \Zotlabs\Web\Controller {
. get_form_security_token("profile_drop"),
'$fields' => $fields,
+ '$vcard' => $vcard,
'$guid' => $r[0]['profile_guid'],
'$banner' => t('Edit Profile Details'),
'$submit' => t('Submit'),
@@ -776,11 +780,28 @@ class Profiles extends \Zotlabs\Web\Controller {
'$film' => array('film', t('Film/Dance/Culture/Entertainment'), $r[0]['film']),
'$interest' => array('interest', t('Hobbies/Interests'), $r[0]['interest']),
'$romance' => array('romance',t('Love/Romance'), $r[0]['romance']),
- '$work' => array('work', t('Work/Employment'), $r[0]['employment']),
+ '$employ' => array('work', t('Work/Employment'), $r[0]['employment']),
'$education' => array('education', t('School/Education'), $r[0]['education']),
'$contact' => array('contact', t('Contact information and social networks'), $r[0]['contact']),
'$channels' => array('channels', t('My other channels'), $r[0]['channels']),
'$extra_fields' => $extra_fields,
+ '$comms' => t('Communications'),
+ '$tel_label' => t('Phone'),
+ '$email_label' => t('Email'),
+ '$impp_label' => t('Instant messenger'),
+ '$url_label' => t('Website'),
+ '$adr_label' => t('Address'),
+ '$note_label' => t('Note'),
+ '$mobile' => t('Mobile'),
+ '$home' => t('Home'),
+ '$work' => t('Work'),
+ '$other' => t('Other'),
+ '$add_card' => t('Add Contact'),
+ '$add_field' => t('Add Field'),
+ '$create' => t('Create'),
+ '$update' => t('Update'),
+ '$delete' => t('Delete'),
+ '$cancel' => t('Cancel'),
));
$arr = array('profile' => $r[0], 'entry' => $o);
diff --git a/Zotlabs/Module/Pubsites.php b/Zotlabs/Module/Pubsites.php
index d87967189..daec5dde3 100644
--- a/Zotlabs/Module/Pubsites.php
+++ b/Zotlabs/Module/Pubsites.php
@@ -30,13 +30,14 @@ class Pubsites extends \Zotlabs\Web\Controller {
if($ret['success']) {
$j = json_decode($ret['body'],true);
if($j) {
- $o .= '<table class="table table-striped table-hover"><tr><td>' . t('Hub URL') . '</td><td>' . t('Access Type') . '</td><td>' . t('Registration Policy') . '</td><td>' . t('Stats') . '</td><td>' . t('Software') . '</td>';
+ $o .= '<table class="table table-striped table-hover"><tr><td>' . t('Hub URL') . '</td><td>' . t('Access Type') . '</td><td>' . t('Registration Policy') . '</td><!--td>' . t('Stats') . '</td--><td>' . t('Software') . '</td>';
if($rating_enabled)
$o .= '<td colspan="2">' . t('Ratings') . '</td>';
$o .= '</tr>';
if($j['sites']) {
foreach($j['sites'] as $jj) {
- if(! \Zotlabs\Lib\System::compatible_project($jj['project']))
+ $projectname = explode(' ',$jj['project']);
+ if(! \Zotlabs\Lib\System::compatible_project($projectname[0]))
continue;
if(strpos($jj['version'],' ')) {
$x = explode(' ', $jj['version']);
@@ -54,7 +55,7 @@ class Pubsites extends \Zotlabs\Web\Controller {
$location = '<br />&nbsp;';
}
$urltext = str_replace(array('https://'), '', $jj['url']);
- $o .= '<tr><td><a href="'. (($jj['sellpage']) ? $jj['sellpage'] : $jj['url'] . '/register' ) . '" ><i class="fa fa-link"></i> ' . $urltext . '</a>' . $location . '</td><td>' . $jj['access'] . '</td><td>' . $jj['register'] . '</td><td>' . '<a target="stats" href="https://hubchart-tarine.rhcloud.com/hub.jsp?hubFqdn=' . $m['host'] . '"><i class="fa fa-area-chart"></i></a></td><td>' . ucwords($jj['project']) . (($jj['version']) ? ' ' . $jj['version'] : '') . '</td>';
+ $o .= '<tr><td><a href="'. (($jj['sellpage']) ? $jj['sellpage'] : $jj['url'] . '/register' ) . '" ><i class="fa fa-link"></i> ' . $urltext . '</a>' . $location . '</td><td>' . $jj['access'] . '</td><td>' . $jj['register'] . '</td><!--td>' . '<a target="stats" href="https://hubchart-tarine.rhcloud.com/hub.jsp?hubFqdn=' . $m['host'] . '"><i class="fa fa-area-chart"></i></a></td--><td>' . ucwords($jj['project']) . (($jj['version']) ? ' ' . $jj['version'] : '') . '</td>';
if($rating_enabled)
$o .= '<td><a href="ratings/' . $host . '" class="btn-btn-default"><i class="fa fa-eye"></i> ' . t('View') . '</a></td>' . $rate_links ;
$o .= '</tr>';
diff --git a/Zotlabs/Module/Pubstream.php b/Zotlabs/Module/Pubstream.php
index 6c4d479d4..15e2d8a74 100644
--- a/Zotlabs/Module/Pubstream.php
+++ b/Zotlabs/Module/Pubstream.php
@@ -7,27 +7,40 @@ require_once('include/conversation.php');
class Pubstream extends \Zotlabs\Web\Controller {
function get($update = 0, $load = false) {
-
+
if($load)
$_SESSION['loadtime'] = datetime_convert();
-
+
if(observer_prohibited(true)) {
return login();
}
-
- if(get_config('system','disable_discover_tab'))
+ $disable_discover_tab = get_config('system','disable_discover_tab') || get_config('system','disable_discover_tab') === false;
+ if($disable_discover_tab)
return;
-
+
+ $mid = ((x($_REQUEST,'mid')) ? $_REQUEST['mid'] : '');
+
+ if(strpos($mid,'b64.') === 0)
+ $decoded = @base64url_decode(substr($mid,4));
+ if($decoded)
+ $mid = $decoded;
+
$item_normal = item_normal();
+ $item_normal_update = item_normal_update();
$static = ((array_key_exists('static',$_REQUEST)) ? intval($_REQUEST['static']) : 0);
- if(! $update) {
+ if(! $update && !$load) {
+
+ nav_set_selected(t('Public Stream'));
+
+ if(!$mid)
+ $_SESSION['static_loadtime'] = datetime_convert();
- $static = ((local_channel()) ? channel_manual_conv_update(local_channel()) : 0);
+ $static = ((local_channel()) ? channel_manual_conv_update(local_channel()) : 1);
$maxheight = get_config('system','home_divmore_height');
if(! $maxheight)
@@ -38,6 +51,10 @@ class Pubstream extends \Zotlabs\Web\Controller {
. "; var profile_page = " . \App::$pager['page']
. "; divmore_height = " . intval($maxheight) . "; </script>\r\n";
+ //if we got a decoded hash we must encode it again before handing to javascript
+ if($decoded)
+ $mid = 'b64.' . base64url_encode($mid);
+
\App::$page['htmlhead'] .= replace_macros(get_markup_template("build_query.tpl"),array(
'$baseurl' => z_root(),
'$pgtype' => 'pubstream',
@@ -57,12 +74,13 @@ class Pubstream extends \Zotlabs\Web\Controller {
'$static' => $static,
'$page' => ((\App::$pager['page'] != 1) ? \App::$pager['page'] : 1),
'$search' => '',
+ '$xchan' => '',
'$order' => 'comment',
'$file' => '',
'$cats' => '',
'$tags' => '',
'$dend' => '',
- '$mid' => '',
+ '$mid' => $mid,
'$verb' => '',
'$dbegin' => ''
));
@@ -104,7 +122,7 @@ class Pubstream extends \Zotlabs\Web\Controller {
$simple_update = '';
if($static && $simple_update)
- $simple_update .= " and item_thread_top = 0 and author_xchan = '" . protect_sprintf(get_observer_hash()) . "' ";
+ $simple_update .= " and item_thread_top = 0 and author_xchan = '" . protect_sprintf(get_observer_hash()) . "' ";
//logger('update: ' . $update . ' load: ' . $load);
@@ -113,29 +131,46 @@ class Pubstream extends \Zotlabs\Web\Controller {
$ordering = "commented";
if($load) {
-
- // Fetch a page full of parent items for this page
-
- $r = q("SELECT distinct item.id AS item_id, $ordering FROM item
- left join abook on item.author_xchan = abook.abook_xchan
- WHERE true $uids $item_normal
- AND item.parent = item.id
- and (abook.abook_blocked = 0 or abook.abook_flags is null)
- $sql_extra3 $sql_extra $sql_nets
- ORDER BY $ordering DESC $pager_sql "
- );
-
-
+ if($mid) {
+ $r = q("SELECT parent AS item_id FROM item
+ left join abook on item.author_xchan = abook.abook_xchan
+ WHERE mid like '%s' $uids $item_normal
+ and (abook.abook_blocked = 0 or abook.abook_flags is null)
+ $sql_extra3 $sql_extra $sql_nets LIMIT 1",
+ dbesc($mid . '%')
+ );
+ }
+ else {
+ // Fetch a page full of parent items for this page
+ $r = q("SELECT distinct item.id AS item_id, $ordering FROM item
+ left join abook on item.author_xchan = abook.abook_xchan
+ WHERE true $uids $item_normal
+ AND item.parent = item.id
+ and (abook.abook_blocked = 0 or abook.abook_flags is null)
+ $sql_extra3 $sql_extra $sql_nets
+ ORDER BY $ordering DESC $pager_sql "
+ );
+ }
}
elseif($update) {
-
- $r = q("SELECT distinct item.id AS item_id, $ordering FROM item
- left join abook on item.author_xchan = abook.abook_xchan
- WHERE true $uids $item_normal
- AND item.parent = item.id $simple_update
- and (abook.abook_blocked = 0 or abook.abook_flags is null)
- $sql_extra3 $sql_extra $sql_nets"
- );
+ if($mid) {
+ $r = q("SELECT parent AS item_id FROM item
+ left join abook on item.author_xchan = abook.abook_xchan
+ WHERE mid like '%s' $uids $item_normal_update $simple_update
+ and (abook.abook_blocked = 0 or abook.abook_flags is null)
+ $sql_extra3 $sql_extra $sql_nets LIMIT 1",
+ dbesc($mid . '%')
+ );
+ }
+ else {
+ $r = q("SELECT distinct item.id AS item_id, $ordering FROM item
+ left join abook on item.author_xchan = abook.abook_xchan
+ WHERE true $uids $item_normal_update
+ AND item.parent = item.id $simple_update
+ and (abook.abook_blocked = 0 or abook.abook_flags is null)
+ $sql_extra3 $sql_extra $sql_nets"
+ );
+ }
$_SESSION['loadtime'] = datetime_convert();
}
// Then fetch all the children of the parents that are on this page
@@ -166,7 +201,10 @@ class Pubstream extends \Zotlabs\Web\Controller {
// fake it
$mode = ('network');
- $o .= conversation($a,$items,$mode,$update,$page_mode);
+ $o .= conversation($items,$mode,$update,$page_mode);
+
+ if($mid)
+ $o .= '<div id="content-complete"></div>';
if(($items) && (! $update))
$o .= alt_pager($a,count($items));
diff --git a/Zotlabs/Module/Randprof.php b/Zotlabs/Module/Randprof.php
index dc2e925fe..94ec095cb 100644
--- a/Zotlabs/Module/Randprof.php
+++ b/Zotlabs/Module/Randprof.php
@@ -8,7 +8,7 @@ class Randprof extends \Zotlabs\Web\Controller {
function init() {
$x = random_profile();
if($x)
- goaway(chanlink_url($x));
+ goaway(chanlink_hash($x));
/** FIXME this doesn't work at the moment as a fallback */
goaway(z_root() . '/profile');
diff --git a/Zotlabs/Module/React.php b/Zotlabs/Module/React.php
index ed4f87e7e..6cd79c952 100644
--- a/Zotlabs/Module/React.php
+++ b/Zotlabs/Module/React.php
@@ -39,6 +39,10 @@ class React extends \Zotlabs\Web\Controller {
$n['author_xchan'] = $channel['channel_hash'];
$x = item_store($n);
+
+ if(local_channel())
+ retain_item($postid);
+
if($x['success']) {
$nid = $x['item_id'];
\Zotlabs\Daemon\Master::Summon(array('Notifier','like',$nid));
diff --git a/Zotlabs/Module/Register.php b/Zotlabs/Module/Register.php
index 1d8944d8e..95e3ca96f 100644
--- a/Zotlabs/Module/Register.php
+++ b/Zotlabs/Module/Register.php
@@ -27,7 +27,7 @@ class Register extends \Zotlabs\Web\Controller {
$result = check_account_email($_REQUEST['email']);
break;
case 'password_check.json':
- $result = check_account_password($_REQUEST['password']);
+ $result = check_account_password($_REQUEST['password1']);
break;
default:
break;
@@ -123,12 +123,19 @@ class Register extends \Zotlabs\Web\Controller {
if($policy == REGISTER_OPEN ) {
if($email_verify) {
$res = verify_email_address($result);
+ if($res) {
+ info( t('Registration successful. Please check your email for validation instructions.') . EOL ) ;
+ }
}
else {
$res = send_register_success_email($result['email'],$result['password']);
}
if($res) {
- info( t('Registration successful. Please check your email for validation instructions.') . EOL ) ;
+ if($invite_code) {
+ info( t('Registration successful. Continue to create your first channel...') . EOL ) ;
+ } else {
+ info( t('Registration successful. Please check your email for validation instructions.') . EOL ) ;
+ }
}
}
elseif($policy == REGISTER_APPROVE) {
@@ -151,7 +158,7 @@ class Register extends \Zotlabs\Web\Controller {
$new_channel = false;
$next_page = 'new_channel';
- if(get_config('system','auto_channel_create') || get_config('system','server_role') == 'basic') {
+ if(get_config('system','auto_channel_create')) {
$new_channel = auto_channel_create($result['account']['account_id']);
if($new_channel['success']) {
$channel_id = $new_channel['channel']['channel_id'];
@@ -167,7 +174,8 @@ class Register extends \Zotlabs\Web\Controller {
$next_page = $x;
$_SESSION['workflow'] = true;
}
-
+
+ unset($_SESSION['login_return_url']);
goaway(z_root() . '/' . $next_page);
}
@@ -231,20 +239,18 @@ class Register extends \Zotlabs\Web\Controller {
$enable_tos = 1 - intval(get_config('system','no_termsofservice'));
$email = array('email', t('Your email address'), ((x($_REQUEST,'email')) ? strip_tags(trim($_REQUEST['email'])) : ""));
- $password = array('password', t('Choose a password'), ((x($_REQUEST,'password')) ? trim($_REQUEST['password']) : ""));
- $password2 = array('password2', t('Please re-enter your password'), ((x($_REQUEST,'password2')) ? trim($_REQUEST['password2']) : ""));
+ $password = array('password', t('Choose a password'), '');
+ $password2 = array('password2', t('Please re-enter your password'), '');
$invite_code = array('invite_code', t('Please enter your invitation code'), ((x($_REQUEST,'invite_code')) ? strip_tags(trim($_REQUEST['invite_code'])) : ""));
$name = array('name', t('Name or caption'), ((x($_REQUEST,'name')) ? $_REQUEST['name'] : ''), t('Examples: "Bob Jameson", "Lisa and her Horses", "Soccer", "Aviation Group"'));
$nickhub = '@' . str_replace(array('http://','https://','/'), '', get_config('system','baseurl'));
$nickname = array('nickname', t('Choose a short nickname'), ((x($_REQUEST,'nickname')) ? $_REQUEST['nickname'] : ''), sprintf( t('Your nickname will be used to create an easy to remember channel address e.g. nickname%s'), $nickhub));
- $role = array('permissions_role' , t('Channel role and privacy'), ($privacy_role) ? $privacy_role : 'social', t('Select a channel role with your privacy requirements.') . ' <a href="help/roles" target="_blank">' . t('Read more about roles') . '</a>',$perm_roles);
+ $role = array('permissions_role' , t('Channel role and privacy'), ($privacy_role) ? $privacy_role : 'social', t('Select a channel role with your privacy requirements.') . ' <a href="help/member/member_guide#Account_Permission_Roles" target="_blank">' . t('Read more about roles') . '</a>',$perm_roles);
$tos = array('tos', $label_tos, '', '', array(t('no'),t('yes')));
- $server_role = get_config('system','server_role');
-
- $auto_create = (($server_role == 'basic') || (get_config('system','auto_channel_create')) ? true : false);
- $default_role = (($server_role == 'basic') ? 'social' : get_config('system','default_permissions_role'));
+ $auto_create = (get_config('system','auto_channel_create') ? true : false);
+ $default_role = get_config('system','default_permissions_role');
require_once('include/bbcode.php');
diff --git a/Zotlabs/Module/Rmagic.php b/Zotlabs/Module/Rmagic.php
index 9fcc72441..bfc03f6ec 100644
--- a/Zotlabs/Module/Rmagic.php
+++ b/Zotlabs/Module/Rmagic.php
@@ -17,8 +17,8 @@ class Rmagic extends \Zotlabs\Web\Controller {
if($r) {
if($r[0]['hubloc_url'] === z_root())
goaway(z_root() . '/login');
- $dest = z_root() . '/' . str_replace('zid=','zid_=',\App::$query_string);
- goaway($r[0]['hubloc_url'] . '/magic' . '?f=&dest=' . $dest);
+ $dest = z_root() . '/' . str_replace(['rmagic','zid='],['','zid_='],\App::$query_string);
+ goaway($r[0]['hubloc_url'] . '/magic' . '?f=&owa=1&dest=' . $dest);
}
}
}
@@ -61,9 +61,9 @@ class Rmagic extends \Zotlabs\Web\Controller {
if($_SESSION['return_url'])
$dest = urlencode(z_root() . '/' . str_replace('zid=','zid_=',$_SESSION['return_url']));
else
- $dest = urlencode(z_root() . '/' . str_replace('zid=','zid_=',\App::$query_string));
+ $dest = urlencode(z_root() . '/' . str_replace([ 'rmagic', 'zid=' ] ,[ '', 'zid_='],\App::$query_string));
- goaway($url . '/magic' . '?f=&dest=' . $dest);
+ goaway($url . '/magic' . '?f=&owa=1&dest=' . $dest);
}
}
}
diff --git a/Zotlabs/Module/Rpost.php b/Zotlabs/Module/Rpost.php
index 1349cd1c5..5d2f0d7e8 100644
--- a/Zotlabs/Module/Rpost.php
+++ b/Zotlabs/Module/Rpost.php
@@ -20,6 +20,7 @@ require_once('include/zot.php');
* body= Body of post
* url= URL which will be parsed and the results appended to the body
* source= Source application
+ * post_id= post_id of post to 'share' (local use only)
* remote_return= absolute URL to return after posting is finished
* type= choices are 'html' or 'bbcode', default is 'bbcode'
*
@@ -59,6 +60,8 @@ class Rpost extends \Zotlabs\Web\Controller {
}
return login();
}
+
+ nav_set_selected('Post');
// If we have saved rpost session variables, but nothing in the current $_REQUEST, recover the saved variables
@@ -88,8 +91,6 @@ class Rpost extends \Zotlabs\Web\Controller {
}
$plaintext = true;
- // if(feature_enabled(local_channel(),'richtext'))
- // $plaintext = false;
if(array_key_exists('type', $_REQUEST) && $_REQUEST['type'] === 'html') {
require_once('include/html2bbcode.php');
@@ -108,28 +109,67 @@ class Rpost extends \Zotlabs\Web\Controller {
if($x['success'])
$_REQUEST['body'] = $_REQUEST['body'] . $x['body'];
}
+
+ if($_REQUEST['post_id']) {
+ $r = q("SELECT * from item WHERE id = %d LIMIT 1",
+ intval($_REQUEST['post_id'])
+ );
+ if(($r) && (! intval($r[0]['item_private']))) {
+ $sql_extra = item_permissions_sql($r[0]['uid']);
+
+ $r = q("select * from item where id = %d $sql_extra",
+ intval($_REQUEST['post_id'])
+ );
+ if($r && $r[0]['mimetype'] === 'text/bbcode') {
+
+ xchan_query($r);
+
+ $is_photo = (($r[0]['obj_type'] === ACTIVITY_OBJ_PHOTO) ? true : false);
+ if($is_photo) {
+ $object = json_decode($r[0]['obj'],true);
+ $photo_bb = $object['body'];
+ }
+
+ if (strpos($r[0]['body'], "[/share]") !== false) {
+ $pos = strpos($r[0]['body'], "[share");
+ $i = substr($r[0]['body'], $pos);
+ } else {
+ $i = "[share author='".urlencode($r[0]['author']['xchan_name']).
+ "' profile='".$r[0]['author']['xchan_url'] .
+ "' avatar='".$r[0]['author']['xchan_photo_s'].
+ "' link='".$r[0]['plink'].
+ "' posted='".$r[0]['created'].
+ "' message_id='".$r[0]['mid']."']";
+ if($r[0]['title'])
+ $i .= '[b]'.$r[0]['title'].'[/b]'."\r\n";
+ $i .= (($is_photo) ? $photo_bb . "\r\n" . $r[0]['body'] : $r[0]['body']);
+ $i .= "[/share]";
+ }
+ }
+ }
+ $_REQUEST['body'] = $_REQUEST['body'] . $i;
+ }
$x = array(
- 'is_owner' => true,
- 'allow_location' => ((intval(get_pconfig($channel['channel_id'],'system','use_browser_location'))) ? '1' : ''),
- 'default_location' => $channel['channel_location'],
- 'nickname' => $channel['channel_address'],
- 'lockstate' => (($acl->is_private()) ? 'lock' : 'unlock'),
- 'acl' => populate_acl($channel_acl, true, \Zotlabs\Lib\PermissionDescription::fromGlobalPermission('view_stream'), get_post_aclDialogDescription(), 'acl_dialog_post'),
- 'permissions' => $channel_acl,
- 'bang' => '',
- 'visitor' => true,
- 'profile_uid' => local_channel(),
- 'title' => $_REQUEST['title'],
- 'body' => $_REQUEST['body'],
- 'attachment' => $_REQUEST['attachment'],
- 'source' => ((x($_REQUEST,'source')) ? strip_tags($_REQUEST['source']) : ''),
- 'return_path' => 'rpost/return',
- 'bbco_autocomplete' => 'bbcode',
- 'editor_autocomplete'=> true,
- 'bbcode' => true,
- 'jotnets' => true
-
+ 'is_owner' => true,
+ 'allow_location' => ((intval(get_pconfig($channel['channel_id'],'system','use_browser_location'))) ? '1' : ''),
+ 'default_location' => $channel['channel_location'],
+ 'nickname' => $channel['channel_address'],
+ 'lockstate' => (($acl->is_private()) ? 'lock' : 'unlock'),
+ 'acl' => populate_acl($channel_acl, true, \Zotlabs\Lib\PermissionDescription::fromGlobalPermission('view_stream'), get_post_aclDialogDescription(), 'acl_dialog_post'),
+ 'permissions' => $channel_acl,
+ 'bang' => '',
+ 'visitor' => true,
+ 'profile_uid' => local_channel(),
+ 'title' => $_REQUEST['title'],
+ 'body' => $_REQUEST['body'],
+ 'attachment' => $_REQUEST['attachment'],
+ 'source' => ((x($_REQUEST,'source')) ? strip_tags($_REQUEST['source']) : ''),
+ 'return_path' => 'rpost/return',
+ 'bbco_autocomplete' => 'bbcode',
+ 'editor_autocomplete' => true,
+ 'bbcode' => true,
+ 'jotnets' => true
);
$editor = status_editor($a,$x);
diff --git a/Zotlabs/Module/Search.php b/Zotlabs/Module/Search.php
index 89eaa4ffa..37e9a336f 100644
--- a/Zotlabs/Module/Search.php
+++ b/Zotlabs/Module/Search.php
@@ -15,14 +15,14 @@ class Search extends \Zotlabs\Web\Controller {
if((get_config('system','block_public')) || (get_config('system','block_public_search'))) {
if ((! local_channel()) && (! remote_channel())) {
notice( t('Public access denied.') . EOL);
- return;
+ return;
}
}
if($load)
$_SESSION['loadtime'] = datetime_convert();
- nav_set_selected('search');
+ nav_set_selected('Search');
require_once("include/bbcode.php");
require_once('include/security.php');
@@ -81,11 +81,12 @@ class Search extends \Zotlabs\Web\Controller {
return $o;
if($tag) {
- $sql_extra = sprintf(" AND item.id IN (select oid from term where otype = %d and ttype in ( %d , %d) and term = '%s') ",
+ $wildtag = str_replace('*','%',$search);
+ $sql_extra = sprintf(" AND item.id IN (select oid from term where otype = %d and ttype in ( %d , %d) and term like '%s') ",
intval(TERM_OBJ_POST),
intval(TERM_HASHTAG),
intval(TERM_COMMUNITYTAG),
- dbesc(protect_sprintf($search))
+ dbesc(protect_sprintf($wildtag))
);
}
else {
@@ -130,6 +131,7 @@ class Search extends \Zotlabs\Web\Controller {
'$list' => ((x($_REQUEST,'list')) ? intval($_REQUEST['list']) : 0),
'$page' => ((\App::$pager['page'] != 1) ? \App::$pager['page'] : 1),
'$search' => (($tag) ? urlencode('#') : '') . $search,
+ '$xchan' => '',
'$order' => '',
'$file' => '',
'$cats' => '',
@@ -143,7 +145,7 @@ class Search extends \Zotlabs\Web\Controller {
}
- $item_normal = item_normal();
+ $item_normal = item_normal_search();
$pub_sql = public_permissions_sql($observer_hash);
require_once('include/channel.php');
@@ -224,7 +226,7 @@ class Search extends \Zotlabs\Web\Controller {
else
$o .= '<h2>' . sprintf( t('Search results for: %s'),htmlspecialchars($search, ENT_COMPAT,'UTF-8')) . '</h2>';
- $o .= conversation($a,$items,'search',$update,'client');
+ $o .= conversation($items,'search',$update,'client');
$o .= '</div>';
diff --git a/Zotlabs/Module/Settings.php b/Zotlabs/Module/Settings.php
index 76794e21c..79031c98f 100644
--- a/Zotlabs/Module/Settings.php
+++ b/Zotlabs/Module/Settings.php
@@ -53,7 +53,7 @@ class Settings extends \Zotlabs\Web\Controller {
function get() {
- nav_set_selected('settings');
+ nav_set_selected('Settings');
if((! local_channel()) || ($_SESSION['delegate'])) {
notice( t('Permission denied.') . EOL );
diff --git a/Zotlabs/Module/Settings/Account.php b/Zotlabs/Module/Settings/Account.php
index ec176797d..18890e89f 100644
--- a/Zotlabs/Module/Settings/Account.php
+++ b/Zotlabs/Module/Settings/Account.php
@@ -16,7 +16,7 @@ class Account {
$account = \App::get_account();
if($email != $account['account_email']) {
- if(! valid_email($email))
+ if(! validate_email($email))
$errs[] = t('Not valid email.');
$adm = trim(get_config('system','admin_email'));
if(($adm) && (strcasecmp($email,$adm) == 0)) {
diff --git a/Zotlabs/Module/Settings/Channel.php b/Zotlabs/Module/Settings/Channel.php
index 5b9cfdaca..41e23b717 100644
--- a/Zotlabs/Module/Settings/Channel.php
+++ b/Zotlabs/Module/Settings/Channel.php
@@ -199,6 +199,10 @@ class Channel {
$vnotify += intval($_POST['vnotify10']);
if(x($_POST,'vnotify11'))
$vnotify += intval($_POST['vnotify11']);
+ if(x($_POST,'vnotify12'))
+ $vnotify += intval($_POST['vnotify12']);
+ if(x($_POST,'vnotify13') && (get_config('system', 'disable_discover_tab') != 1))
+ $vnotify += intval($_POST['vnotify13']);
$always_show_in_notices = x($_POST,'always_show_in_notices') ? 1 : 0;
@@ -277,8 +281,8 @@ class Channel {
if($email_changed && \App::$config['system']['register_policy'] == REGISTER_VERIFY) {
// FIXME - set to un-verified, blocked and redirect to logout
- // Why? Are we verifying people or email addresses?
-
+ // Q: Why? Are we verifying people or email addresses?
+ // A: the policy is to verify email addresses
}
goaway(z_root() . '/settings' );
@@ -324,7 +328,7 @@ class Channel {
foreach($global_perms as $k => $perm) {
$options = array();
foreach($perm_opts as $opt) {
- if((! strstr($k,'view')) && $opt[1] == PERMS_PUBLIC)
+ if(((! strstr($k,'view')) && $k !== 'post_comments') && $opt[1] == PERMS_PUBLIC)
continue;
$options[$opt[1]] = $opt[0];
}
@@ -489,7 +493,6 @@ class Channel {
'$h_prv' => t('Security and Privacy Settings'),
'$permissions_set' => $permissions_set,
- '$server_role' => \Zotlabs\Lib\System::get_server_role(),
'$perms_set_msg' => t('Your permissions are already configured. Click to view/adjust'),
'$hide_presence' => array('hide_presence', t('Hide my online presence'),$hide_presence, t('Prevents displaying in your profile that you are online'), $yes_no),
@@ -506,7 +509,7 @@ class Channel {
'$expire' => array('expire',t('Expire other channel content after this many days'),$expire, t('0 or blank to use the website limit.') . ' ' . ((intval($sys_expire)) ? sprintf( t('This website expires after %d days.'),intval($sys_expire)) : t('This website does not expire imported content.')) . ' ' . t('The website limit takes precedence if lower than your limit.')),
'$maxreq' => array('maxreq', t('Maximum Friend Requests/Day:'), intval($channel['channel_max_friend_req']) , t('May reduce spam activity')),
- '$permissions' => t('Default Access Control List (ACL)'),
+ '$permissions' => t('Default Privacy Group'),
'$permdesc' => t("\x28click to open/close\x29"),
'$aclselect' => populate_acl($perm_defaults, false, \Zotlabs\Lib\PermissionDescription::fromDescription(t('Use my default audience setting for the type of object published'))),
'$allow_cid' => acl2json($perm_defaults['allow_cid']),
@@ -556,6 +559,8 @@ class Channel {
'$vnotify9' => array('vnotify9', t('System critical alerts'), ($vnotify & VNOTIFY_ALERT), VNOTIFY_ALERT, t('Recommended'), $yes_no),
'$vnotify10' => array('vnotify10', t('New connections'), ($vnotify & VNOTIFY_INTRO), VNOTIFY_INTRO, t('Recommended'), $yes_no),
'$vnotify11' => array('vnotify11', t('System Registrations'), ($vnotify & VNOTIFY_REGISTER), VNOTIFY_REGISTER, '', $yes_no),
+ '$vnotify12' => array('vnotify12', t('Unseen shared files'), ($vnotify & VNOTIFY_FILES), VNOTIFY_FILES, '', $yes_no),
+ '$vnotify13' => ((get_config('system', 'disable_discover_tab') != 1) ? array('vnotify13', t('Unseen public activity'), ($vnotify & VNOTIFY_PUBS), VNOTIFY_PUBS, '', $yes_no) : array()),
'$always_show_in_notices' => array('always_show_in_notices', t('Also show new wall posts, private messages and connections under Notices'), $always_show_in_notices, 1, '', $yes_no),
'$evdays' => array('evdays', t('Notify me of events this many days in advance'), $evdays, t('Must be greater than 0')),
@@ -575,7 +580,7 @@ class Channel {
'$removeme' => t('Remove Channel'),
'$removechannel' => t('Remove this channel.'),
'$firefoxshare' => t('Firefox Share $Projectname provider'),
- '$cal_first_day' => array('first_day', t('Start calendar week on monday'), ((get_pconfig(local_channel(),'system','cal_first_day')) ? 1 : ''), '', $yes_no),
+ '$cal_first_day' => array('first_day', t('Start calendar week on Monday'), ((get_pconfig(local_channel(),'system','cal_first_day')) ? 1 : ''), '', $yes_no),
));
call_hooks('settings_form',$o);
diff --git a/Zotlabs/Module/Settings/Display.php b/Zotlabs/Module/Settings/Display.php
index 67cecf1f5..a444d28a2 100644
--- a/Zotlabs/Module/Settings/Display.php
+++ b/Zotlabs/Module/Settings/Display.php
@@ -24,34 +24,34 @@ class Display {
$mobile_theme = ((x($_POST,'mobile_theme')) ? notags(trim($_POST['mobile_theme'])) : '');
$preload_images = ((x($_POST,'preload_images')) ? intval($_POST['preload_images']) : 0);
$user_scalable = ((x($_POST,'user_scalable')) ? intval($_POST['user_scalable']) : 0);
- $nosmile = ((x($_POST,'nosmile')) ? intval($_POST['nosmile']) : 0);
- $title_tosource = ((x($_POST,'title_tosource')) ? intval($_POST['title_tosource']) : 0);
+ $nosmile = ((x($_POST,'nosmile')) ? intval($_POST['nosmile']) : 0);
+ $title_tosource = ((x($_POST,'title_tosource')) ? intval($_POST['title_tosource']) : 0);
$channel_list_mode = ((x($_POST,'channel_list_mode')) ? intval($_POST['channel_list_mode']) : 0);
$network_list_mode = ((x($_POST,'network_list_mode')) ? intval($_POST['network_list_mode']) : 0);
$manual_update = ((array_key_exists('manual_update',$_POST)) ? intval($_POST['manual_update']) : 0);
-
+
$channel_divmore_height = ((x($_POST,'channel_divmore_height')) ? intval($_POST['channel_divmore_height']) : 400);
if($channel_divmore_height < 50)
$channel_divmore_height = 50;
$network_divmore_height = ((x($_POST,'network_divmore_height')) ? intval($_POST['network_divmore_height']) : 400);
if($network_divmore_height < 50)
$network_divmore_height = 50;
-
+
$browser_update = ((x($_POST,'browser_update')) ? intval($_POST['browser_update']) : 0);
$browser_update = $browser_update * 1000;
if($browser_update < 10000)
$browser_update = 10000;
-
+
$itemspage = ((x($_POST,'itemspage')) ? intval($_POST['itemspage']) : 20);
if($itemspage > 100)
$itemspage = 100;
-
- if ($mobile_theme == "---")
+
+ if ($mobile_theme == "---")
del_pconfig(local_channel(),'system','mobile_theme');
else {
set_pconfig(local_channel(),'system','mobile_theme',$mobile_theme);
}
-
+
set_pconfig(local_channel(),'system','preload_images',$preload_images);
set_pconfig(local_channel(),'system','user_scalable',$user_scalable);
set_pconfig(local_channel(),'system','update_interval', $browser_update);
@@ -63,9 +63,9 @@ class Display {
set_pconfig(local_channel(),'system','channel_divmore_height', $channel_divmore_height);
set_pconfig(local_channel(),'system','network_divmore_height', $network_divmore_height);
set_pconfig(local_channel(),'system','manual_conversation_update', $manual_update);
-
+
$newschema = '';
- if($theme == $existing_theme){
+ if($theme){
// call theme_post only if theme has not been changed
if( ($themeconfigfile = $this->get_theme_config_file($theme)) != null){
require_once($themeconfigfile);
@@ -76,7 +76,7 @@ class Display {
if(array_key_exists($_POST['schema'],$schemas))
$newschema = $_POST['schema'];
if($newschema === '---')
- $newschema = '';
+ $newschema = '';
$theme_config->post();
}
}
@@ -85,18 +85,18 @@ class Display {
logger('theme: ' . $theme . (($newschema) ? ':' . $newschema : ''));
$_SESSION['theme'] = $theme . (($newschema) ? ':' . $newschema : '');
-
+
$r = q("UPDATE channel SET channel_theme = '%s' WHERE channel_id = %d",
dbesc($theme . (($newschema) ? ':' . $newschema : '')),
intval(local_channel())
);
-
+
call_hooks('display_settings_post', $_POST);
build_sync_packet();
goaway(z_root() . '/settings/display' );
return; // NOTREACHED
}
-
+
function get() {
@@ -115,28 +115,36 @@ class Display {
$default_mobile_theme = get_config('system','mobile_theme');
if(! $mobile_default_theme)
$mobile_default_theme = 'none';
-
+
$allowed_themes_str = get_config('system','allowed_themes');
$allowed_themes_raw = explode(',',$allowed_themes_str);
$allowed_themes = array();
if(count($allowed_themes_raw))
- foreach($allowed_themes_raw as $x)
+ foreach($allowed_themes_raw as $x)
if(strlen(trim($x)) && is_dir("view/theme/$x"))
$allowed_themes[] = trim($x);
-
+
$themes = array();
$files = glob('view/theme/*');
if($allowed_themes) {
foreach($allowed_themes as $th) {
$f = $th;
+
+ $info = get_theme_info($th);
+ $compatible = check_plugin_versions($info);
+ if(!$compatible) {
+ $mobile_themes[$f] = $themes[$f] = sprintf(t('%s - (Incompatible)'), $f);
+ continue;
+ }
+
$is_experimental = file_exists('view/theme/' . $th . '/experimental');
$unsupported = file_exists('view/theme/' . $th . '/unsupported');
$is_mobile = file_exists('view/theme/' . $th . '/mobile');
$is_library = file_exists('view/theme/'. $th . '/library');
- $mobile_themes["---"] = t("No special theme for mobile devices");
-
- if (!$is_experimental or ($is_experimental && (get_config('experimentals','exp_themes')==1 or get_config('experimentals','exp_themes')===false))){
+ $mobile_themes['---'] = t("No special theme for mobile devices");
+
+ if (!$is_experimental or ($is_experimental && (get_config('experimentals','exp_themes')==1 or get_config('experimentals','exp_themes')===false))){
$theme_name = (($is_experimental) ? sprintf(t('%s - (Experimental)'), $f) : $f);
if (! $is_library) {
if($is_mobile) {
@@ -147,32 +155,35 @@ class Display {
}
}
}
-
}
}
$theme_selected = ((array_key_exists('theme',$_SESSION) && $_SESSION['theme']) ? $_SESSION['theme'] : $theme);
+ if (strpos($theme_selected, ':')) {
+ $theme_selected = explode(':', $theme_selected)[0];
+ }
+
$mobile_theme_selected = (!x($_SESSION,'mobile_theme')? $default_mobile_theme : $_SESSION['mobile_theme']);
-
+
$preload_images = get_pconfig(local_channel(),'system','preload_images');
$preload_images = (($preload_images===false)? '0': $preload_images); // default if not set: 0
-
+
$user_scalable = get_pconfig(local_channel(),'system','user_scalable');
$user_scalable = (($user_scalable===false)? '0': $user_scalable); // default if not set: 0
-
+
$browser_update = intval(get_pconfig(local_channel(), 'system','update_interval'));
$browser_update = (($browser_update == 0) ? 80 : $browser_update / 1000); // default if not set: 40 seconds
-
+
$itemspage = intval(get_pconfig(local_channel(), 'system','itemspage'));
$itemspage = (($itemspage > 0 && $itemspage < 101) ? $itemspage : 20); // default if not set: 20 items
-
+
$nosmile = get_pconfig(local_channel(),'system','no_smilies');
$nosmile = (($nosmile===false)? '0': $nosmile); // default if not set: 0
-
+
$title_tosource = get_pconfig(local_channel(),'system','title_tosource');
$title_tosource = (($title_tosource===false)? '0': $title_tosource); // default if not set: 0
-
+
$theme_config = "";
if(($themeconfigfile = $this->get_theme_config_file($theme)) != null){
require_once($themeconfigfile);
@@ -185,18 +196,18 @@ class Display {
}
// logger('schemas: ' . print_r($schemas,true));
-
+
$tpl = get_markup_template("settings_display.tpl");
$o = replace_macros($tpl, array(
'$ptitle' => t('Display Settings'),
- '$d_tset' => t('Theme Settings'),
- '$d_ctset' => t('Custom Theme Settings'),
+ '$d_tset' => t('Theme Settings'),
+ '$d_ctset' => t('Custom Theme Settings'),
'$d_cset' => t('Content Settings'),
'$form_security_token' => get_form_security_token("settings_display"),
'$submit' => t('Submit'),
'$baseurl' => z_root(),
'$uid' => local_channel(),
-
+
'$theme' => (($themes) ? array('theme', t('Display Theme:'), $theme_selected, '', $themes, 'preview') : false),
'$schema' => array('schema', t('Select scheme'), $existing_schema, '' , $schemas),
@@ -215,11 +226,11 @@ class Display {
'$network_list_mode' => array('network_list_mode', t('Use blog/list mode on grid page'), get_pconfig(local_channel(),'system','network_list_mode'), t('(comments displayed separately)'), $yes_no),
'$channel_divmore_height' => array('channel_divmore_height', t('Channel page max height of content (in pixels)'), ((get_pconfig(local_channel(),'system','channel_divmore_height')) ? get_pconfig(local_channel(),'system','channel_divmore_height') : 400), t('click to expand content exceeding this height')),
'$network_divmore_height' => array('network_divmore_height', t('Grid page max height of content (in pixels)'), ((get_pconfig(local_channel(),'system','network_divmore_height')) ? get_pconfig(local_channel(),'system','network_divmore_height') : 400) , t('click to expand content exceeding this height')),
-
-
+
+
));
- call_hooks('display_settings',$o);
+ call_hooks('display_settings',$o);
return $o;
}
@@ -227,10 +238,10 @@ class Display {
function get_theme_config_file($theme){
$base_theme = \App::$theme_info['extends'];
-
+
if (file_exists("view/theme/$theme/php/config.php")){
return "view/theme/$theme/php/config.php";
- }
+ }
if (file_exists("view/theme/$base_theme/php/config.php")){
return "view/theme/$base_theme/php/config.php";
}
@@ -239,5 +250,5 @@ class Display {
-
+
}
diff --git a/Zotlabs/Module/Settings/Featured.php b/Zotlabs/Module/Settings/Featured.php
index 4885abd1d..ebe2996d3 100644
--- a/Zotlabs/Module/Settings/Featured.php
+++ b/Zotlabs/Module/Settings/Featured.php
@@ -10,14 +10,16 @@ class Featured {
call_hooks('feature_settings_post', $_POST);
- if(intval($_POST['affinity_cmax'])) {
- set_pconfig(local_channel(),'affinity','cmax',intval($_POST['affinity_cmax']));
- }
- if(intval($_POST['affinity_cmin'])) {
- set_pconfig(local_channel(),'affinity','cmin',intval($_POST['affinity_cmin']));
- }
- if(intval($_POST['affinity_cmax']) || intval($_POST['affinity_cmin'])) {
- info( t('Affinity Slider settings updated.') . EOL);
+ if($_POST['affinity_slider-submit']) {
+ if(intval($_POST['affinity_cmax'])) {
+ set_pconfig(local_channel(),'affinity','cmax',intval($_POST['affinity_cmax']));
+ }
+ if(intval($_POST['affinity_cmin'])) {
+ set_pconfig(local_channel(),'affinity','cmin',intval($_POST['affinity_cmin']));
+ }
+ if(intval($_POST['affinity_cmax']) || intval($_POST['affinity_cmin'])) {
+ info( t('Affinity Slider settings updated.') . EOL);
+ }
}
build_sync_packet();
diff --git a/Zotlabs/Module/Settings/Permcats.php b/Zotlabs/Module/Settings/Permcats.php
index 35d533196..336f69653 100644
--- a/Zotlabs/Module/Settings/Permcats.php
+++ b/Zotlabs/Module/Settings/Permcats.php
@@ -42,8 +42,6 @@ class Permcats {
function get() {
-logger('cmd: ' . \App::$cmd);
-
if(! local_channel())
return;
@@ -85,7 +83,7 @@ logger('cmd: ' . \App::$cmd);
if($existing[$k])
$thisperm = "1";
- $perms[] = array('perms_' . $k, $v, ((array_key_exists($k,$their_perms)) ? intval($their_perms[$k]) : ''),$thisperm, 1, (($checkinherited & PERMS_SPECIFIC) ? '' : '1'), '', $checkinherited);
+ $perms[] = array('perms_' . $k, $v, '',$thisperm, 1, (($checkinherited & PERMS_SPECIFIC) ? '' : '1'), '', $checkinherited);
}
@@ -114,4 +112,4 @@ logger('cmd: ' . \App::$cmd);
return $o;
}
-} \ No newline at end of file
+}
diff --git a/Zotlabs/Module/Setup.php b/Zotlabs/Module/Setup.php
index 9c688af01..8e7fbbddf 100644
--- a/Zotlabs/Module/Setup.php
+++ b/Zotlabs/Module/Setup.php
@@ -38,7 +38,7 @@ class Setup extends \Zotlabs\Web\Controller {
ini_set('log_errors', '0');
ini_set('display_errors', '1');
- // $baseurl/setup/testrwrite to test if rewite in .htaccess is working
+ // $baseurl/setup/testrewrite to test if rewrite in .htaccess is working
if (argc() == 2 && argv(1) == "testrewrite") {
echo 'ok';
killme();
@@ -73,9 +73,6 @@ class Setup extends \Zotlabs\Web\Controller {
$phpath = trim($_POST['phpath']);
$adminmail = trim($_POST['adminmail']);
$siteurl = trim($_POST['siteurl']);
- $server_role = trim($_POST['server_role']);
- if(! $server_role)
- $server_role = 'standard';
// $siteurl should not have a trailing slash
@@ -103,9 +100,6 @@ class Setup extends \Zotlabs\Web\Controller {
$timezone = trim($_POST['timezone']);
$adminmail = trim($_POST['adminmail']);
$siteurl = trim($_POST['siteurl']);
- $server_role = trim($_POST['server_role']);
- if(! $server_role)
- $server_role = 'standard';
if($siteurl != z_root()) {
$test = z_fetch_url($siteurl."/setup/testrewrite");
@@ -134,7 +128,7 @@ class Setup extends \Zotlabs\Web\Controller {
'$dbpass' => $dbpass,
'$dbdata' => $dbdata,
'$dbtype' => $dbtype,
- '$server_role' => $server_role,
+ '$server_role' => 'pro',
'$timezone' => $timezone,
'$siteurl' => $siteurl,
'$site_id' => random_string(),
@@ -192,14 +186,17 @@ class Setup extends \Zotlabs\Web\Controller {
}
$db_return_text = '';
if(x(\App::$data, 'db_installed')) {
- $txt = '<p style="font-size: 130%;">';
- $txt .= t('Your site database has been installed.') . EOL;
+ $pass = 'Installation succeeded!';
+ $icon = 'check';
+ $txt = t('Your site database has been installed.') . EOL;
$db_return_text .= $txt;
}
if(x(\App::$data, 'db_failed')) {
+ $pass = 'Database install failed!';
+ $icon = 'exclamation-triangle';
$txt = t('You may need to import the file "install/schema_xxx.sql" manually using a database client.') . EOL;
$txt .= t('Please see the file "install/INSTALL.txt".') . EOL ."<hr>" ;
- $txt .= "<pre>".\App::$data['db_failed'] . "</pre>". EOL ;
+ $txt .= "<pre>" . \App::$data['db_failed'] . "</pre>". EOL ;
$db_return_text .= $txt;
}
if(\DBA::$dba && \DBA::$dba->connected) {
@@ -223,8 +220,10 @@ class Setup extends \Zotlabs\Web\Controller {
$tpl = get_markup_template('install.tpl');
return replace_macros($tpl, array(
'$title' => $install_title,
- '$pass' => '',
- '$text' => $db_return_text . $this->what_next(),
+ '$icon' => $icon,
+ '$pass' => $pass,
+ '$text' => $db_return_text,
+ '$what_next' => $this->what_next()
));
}
@@ -324,11 +323,6 @@ class Setup extends \Zotlabs\Web\Controller {
$siteurl = trim($_POST['siteurl']);
$timezone = ((x($_POST,'timezone')) ? ($_POST['timezone']) : 'America/Los_Angeles');
- $server_roles = [
- 'basic' => t('Basic/Minimal Social Networking'),
- 'standard' => t('Standard Configuration (default)'),
- 'pro' => t('Professional')
- ];
$tpl = get_markup_template('install_settings.tpl');
$o .= replace_macros($tpl, array(
@@ -348,8 +342,6 @@ class Setup extends \Zotlabs\Web\Controller {
'$siteurl' => array('siteurl', t('Website URL'), z_root(), t('Please use SSL (https) URL if available.')),
- '$server_role' => array('server_role', t("Server Configuration/Role"), 'standard','',$server_roles),
-
'$timezone' => array('timezone', t('Please select a default timezone for your website'), $timezone, '', get_timezones()),
'$baseurl' => z_root(),
@@ -408,7 +400,7 @@ class Setup extends \Zotlabs\Web\Controller {
if(!$passed) {
$help .= t('Could not find a command line version of PHP in the web server PATH.'). EOL;
$help .= t('If you don\'t have a command line version of PHP installed on server, you will not be able to run background polling via cron.') . EOL;
- $help .= EOL . EOL ;
+ $help .= EOL;
$tpl = get_markup_template('field_input.tpl');
$help .= replace_macros($tpl, array(
'$field' => array('phpath', t('PHP executable path'), $phpath, t('Enter full path to php executable. You can leave this blank to continue the installation.')),
@@ -456,7 +448,7 @@ class Setup extends \Zotlabs\Web\Controller {
userReadableSize($result['max_upload_filesize']),
$result['max_file_uploads']
);
- $help .= '<br>' . t('You can adjust these settings in the server php.ini file.');
+ $help .= '<br><br>' . t('You can adjust these settings in the server php.ini file.');
$this->check_add($checks, t('PHP upload limits'), true, false, $help);
}
@@ -508,6 +500,7 @@ class Setup extends \Zotlabs\Web\Controller {
$this->check_add($ck_funcs, t('PDO database PHP module'), true, true);
$this->check_add($ck_funcs, t('mb_string PHP module'), true, true);
$this->check_add($ck_funcs, t('xml PHP module'), true, true);
+ $this->check_add($ck_funcs, t('zip PHP module'), true, true);
if(function_exists('apache_get_modules')){
if (! in_array('mod_rewrite', apache_get_modules())) {
@@ -550,8 +543,12 @@ class Setup extends \Zotlabs\Web\Controller {
$ck_funcs[4]['help'] = t('Error: mb_string PHP module required but not installed.');
}
if(! extension_loaded('xml')) {
+ $ck_funcs[5]['status'] = false;
+ $ck_funcs[5]['help'] = t('Error: xml PHP module required for DAV but not installed.');
+ }
+ if(! extension_loaded('zip')) {
$ck_funcs[6]['status'] = false;
- $ck_funcs[6]['help'] = t('Error: xml PHP module required for DAV but not installed.');
+ $ck_funcs[6]['help'] = t('Error: zip PHP module required but not installed.');
}
$checks = array_merge($checks, $ck_funcs);
@@ -624,7 +621,6 @@ class Setup extends \Zotlabs\Web\Controller {
* @param[out] array &$checks
*/
function check_htaccess(&$checks) {
- $a = get_app();
$status = true;
$help = '';
$ssl_error = false;
@@ -718,7 +714,6 @@ class Setup extends \Zotlabs\Web\Controller {
* @return string with parsed HTML
*/
function what_next() {
- $a = get_app();
// install the standard theme
set_config('system', 'allowed_themes', 'redbasic');
@@ -745,12 +740,12 @@ class Setup extends \Zotlabs\Web\Controller {
$baseurl = z_root();
return
- t('<h1>What next</h1>')
- ."<p>".t('IMPORTANT: You will need to [manually] setup a scheduled task for the poller.')
+ t('<h1>What next?</h1>')
+ ."<div class=\"alert alert-info\">".t('IMPORTANT: You will need to [manually] setup a scheduled task for the poller.').EOL
.t('Please see the file "install/INSTALL.txt".')
- ."</p><p>"
+ ."</div><div>"
.t("Go to your new hub <a href='$baseurl/register'>registration page</a> and register as new member. Remember to use the same email you have entered as administrator email. This will allow you to enter the site admin panel.")
- ."</p>";
+ ."</div>";
}
/**
diff --git a/Zotlabs/Module/Share.php b/Zotlabs/Module/Share.php
index fcc2486ba..5c4811c59 100644
--- a/Zotlabs/Module/Share.php
+++ b/Zotlabs/Module/Share.php
@@ -76,7 +76,7 @@ class Share extends \Zotlabs\Web\Controller {
$observer = \App::get_observer();
$parsed = $observer['xchan_url'];
if($parsed) {
- $post_url = $parsed['scheme'] . ':' . $parsed['host'] . (($parsed['port']) ? ':' . $parsed['port'] : '')
+ $post_url = $parsed['scheme'] . '://' . $parsed['host'] . (($parsed['port']) ? ':' . $parsed['port'] : '')
. '/rpost';
/**
diff --git a/Zotlabs/Module/Sharedwithme.php b/Zotlabs/Module/Sharedwithme.php
index 25bc7dba3..2c97e9726 100644
--- a/Zotlabs/Module/Sharedwithme.php
+++ b/Zotlabs/Module/Sharedwithme.php
@@ -4,6 +4,11 @@ require_once('include/conversation.php');
require_once('include/text.php');
+/**
+ * @file Zotlabs/Module/Sharedwithme.php
+ *
+ */
+
class Sharedwithme extends \Zotlabs\Web\Controller {
function get() {
@@ -92,7 +97,8 @@ class Sharedwithme extends \Zotlabs\Web\Controller {
}
- $o = profile_tabs($a, $is_owner, $channel['channel_address']);
+ //$o = profile_tabs($a, $is_owner, $channel['channel_address']);
+ $o = '';
$o .= replace_macros(get_markup_template('sharedwithme.tpl'), array(
'$header' => t('Files: shared with me'),
diff --git a/Zotlabs/Module/Siteinfo.php b/Zotlabs/Module/Siteinfo.php
index 7c3918425..fafd51f65 100644
--- a/Zotlabs/Module/Siteinfo.php
+++ b/Zotlabs/Module/Siteinfo.php
@@ -5,14 +5,13 @@ namespace Zotlabs\Module;
class Siteinfo extends \Zotlabs\Web\Controller {
function init() {
- if (argv(1) === 'json') {
+logger(print_r($_REQUEST,true));
+ if (argv(1) === 'json' || $_REQUEST['module_format'] === 'json') {
$data = get_site_info();
json_return_and_die($data);
}
}
-
-
-
+
function get() {
$siteinfo = replace_macros(get_markup_template('siteinfo.tpl'),
diff --git a/Zotlabs/Module/Siteinfo_json.php b/Zotlabs/Module/Siteinfo_json.php
deleted file mode 100644
index 99c22610f..000000000
--- a/Zotlabs/Module/Siteinfo_json.php
+++ /dev/null
@@ -1,14 +0,0 @@
-<?php
-namespace Zotlabs\Module;
-
-
-class Siteinfo_json extends \Zotlabs\Web\Controller {
-
- function init() {
-
- $data = get_site_info();
- json_return_and_die($data);
-
- }
-
-}
diff --git a/Zotlabs/Module/Suggest.php b/Zotlabs/Module/Suggest.php
index 367308d90..f79e4e245 100644
--- a/Zotlabs/Module/Suggest.php
+++ b/Zotlabs/Module/Suggest.php
@@ -3,8 +3,6 @@ namespace Zotlabs\Module;
require_once('include/socgraph.php');
require_once('include/contact_widgets.php');
-require_once('include/widgets.php');
-
class Suggest extends \Zotlabs\Web\Controller {
@@ -23,13 +21,15 @@ class Suggest extends \Zotlabs\Web\Controller {
}
- function get() {
+ function get() {
$o = '';
if(! local_channel()) {
notice( t('Permission denied.') . EOL);
return;
}
+
+ nav_set_selected('Suggest Channels');
$_SESSION['return_url'] = z_root() . '/' . \App::$cmd;
diff --git a/Zotlabs/Module/Tasks.php b/Zotlabs/Module/Tasks.php
index c8deb11bf..0709f31f6 100644
--- a/Zotlabs/Module/Tasks.php
+++ b/Zotlabs/Module/Tasks.php
@@ -19,8 +19,8 @@ class Tasks extends \Zotlabs\Web\Controller {
$arr['all'] = 1;
$x = tasks_fetch($arr);
+ $x['html'] = '';
if($x['tasks']) {
- $x['html'] = '';
foreach($x['tasks'] as $y) {
$x['html'] .= '<div class="tasklist-item"><input type="checkbox" onchange="taskComplete(' . $y['id'] . '); return false;" /> ' . $y['summary'] . '</div>';
}
@@ -69,6 +69,7 @@ class Tasks extends \Zotlabs\Web\Controller {
if($x)
$ret['success'] = true;
}
+
json_return_and_die($ret);
}
diff --git a/Zotlabs/Module/Thing.php b/Zotlabs/Module/Thing.php
index 95c6c5636..f816632ab 100644
--- a/Zotlabs/Module/Thing.php
+++ b/Zotlabs/Module/Thing.php
@@ -91,6 +91,7 @@ class Thing extends \Zotlabs\Web\Controller {
}
$orig_record = $t[0];
if($photo != $orig_record['obj_imgurl']) {
+ delete_thing_photo($orig_record['obj_imgurl'],get_observer_hash());
$arr = import_xchan_photo($photo,get_observer_hash(),true);
$local_photo = $arr[0];
$local_photo_type = $arr[3];
@@ -336,6 +337,9 @@ class Thing extends \Zotlabs\Web\Controller {
return '';
}
+
+ delete_thing_photo($r[0]['obj_imgurl'],get_observer_hash());
+
$x = q("delete from obj where obj_obj = '%s' and obj_type = %d and obj_channel = %d",
dbesc($thing_hash),
intval(TERM_OBJ_THING),
diff --git a/Zotlabs/Module/Token.php b/Zotlabs/Module/Token.php
new file mode 100644
index 000000000..e0d9d74d7
--- /dev/null
+++ b/Zotlabs/Module/Token.php
@@ -0,0 +1,40 @@
+<?php
+
+namespace Zotlabs\Module;
+
+
+class Token extends \Zotlabs\Web\Controller {
+
+
+ function get() {
+
+
+ // workaround for HTTP-auth in CGI mode
+ if (x($_SERVER, 'REDIRECT_REMOTE_USER')) {
+ $userpass = base64_decode(substr($_SERVER["REDIRECT_REMOTE_USER"], 6)) ;
+ if(strlen($userpass)) {
+ list($name, $password) = explode(':', $userpass);
+ $_SERVER['PHP_AUTH_USER'] = $name;
+ $_SERVER['PHP_AUTH_PW'] = $password;
+ }
+ }
+
+ if (x($_SERVER, 'HTTP_AUTHORIZATION')) {
+ $userpass = base64_decode(substr($_SERVER["HTTP_AUTHORIZATION"], 6)) ;
+ if(strlen($userpass)) {
+ list($name, $password) = explode(':', $userpass);
+ $_SERVER['PHP_AUTH_USER'] = $name;
+ $_SERVER['PHP_AUTH_PW'] = $password;
+ }
+ }
+
+
+
+
+ require_once('include/oauth2.php');
+ $oauth2_server->handleTokenRequest(\OAuth2\Request::createFromGlobals())->send();
+
+ killme();
+ }
+
+} \ No newline at end of file
diff --git a/Zotlabs/Module/Update_cards.php b/Zotlabs/Module/Update_cards.php
new file mode 100644
index 000000000..bb87357e8
--- /dev/null
+++ b/Zotlabs/Module/Update_cards.php
@@ -0,0 +1,39 @@
+<?php
+
+namespace Zotlabs\Module;
+
+/**
+ * Module: update_profile
+ * Purpose: AJAX synchronisation of profile page
+ *
+ */
+
+
+class Update_cards extends \Zotlabs\Web\Controller {
+
+function get() {
+
+ $profile_uid = intval($_GET['p']);
+ $load = (((argc() > 1) && (argv(1) == 'load')) ? 1 : 0);
+
+ header("Content-type: text/html");
+ echo "<!DOCTYPE html><html><body><section></section></body></html>\r\n";
+
+ killme();
+
+
+ $mod = new Cards();
+
+ $text = $mod->get($profile_uid,$load);
+
+ /**
+ * reportedly some versions of MSIE don't handle tabs in XMLHttpRequest documents very well
+ */
+
+ echo str_replace("\t",' ',$text);
+ echo (($_GET['msie'] == 1) ? '</div>' : '</section>');
+ echo "</body></html>\r\n";
+ killme();
+
+}
+}
diff --git a/Zotlabs/Module/Update_display.php b/Zotlabs/Module/Update_display.php
index 13b04204d..b2c6a56f5 100644
--- a/Zotlabs/Module/Update_display.php
+++ b/Zotlabs/Module/Update_display.php
@@ -21,26 +21,10 @@ class Update_display extends \Zotlabs\Web\Controller {
$mod = new Display();
$text = $mod->get($profile_uid, $load);
- $pattern = "/<img([^>]*) src=\"([^\"]*)\"/";
- $replace = "<img\${1} dst=\"\${2}\"";
- // $text = preg_replace($pattern, $replace, $text);
- /*
- if(! $load) {
- $replace = '<br />' . t('[Embedded content - reload page to view]') . '<br />';
- $pattern = "/<\s*audio[^>]*>(.*?)<\s*\/\s*audio>/i";
- $text = preg_replace($pattern, $replace, $text);
- $pattern = "/<\s*video[^>]*>(.*?)<\s*\/\s*video>/i";
- $text = preg_replace($pattern, $replace, $text);
- $pattern = "/<\s*embed[^>]*>(.*?)<\s*\/\s*embed>/i";
- $text = preg_replace($pattern, $replace, $text);
- $pattern = "/<\s*iframe[^>]*>(.*?)<\s*\/\s*iframe>/i";
- $text = preg_replace($pattern, $replace, $text);
- }
- */
echo str_replace("\t",' ',$text);
echo (($_GET['msie'] == 1) ? '</div>' : '</section>');
echo "</body></html>\r\n";
- // logger('update_display: ' . $text);
+
killme();
}
diff --git a/Zotlabs/Module/Viewconnections.php b/Zotlabs/Module/Viewconnections.php
index 4364d482a..1f9c03751 100644
--- a/Zotlabs/Module/Viewconnections.php
+++ b/Zotlabs/Module/Viewconnections.php
@@ -70,7 +70,7 @@ class Viewconnections extends \Zotlabs\Web\Controller {
foreach($r as $rr) {
- $url = chanlink_url($rr['xchan_url']);
+ $url = chanlink_hash($rr['xchan_hash']);
if($url) {
$contacts[] = array(
'id' => $rr['abook_id'],
diff --git a/Zotlabs/Module/Viewsrc.php b/Zotlabs/Module/Viewsrc.php
index fa755a3ec..54ab89e81 100644
--- a/Zotlabs/Module/Viewsrc.php
+++ b/Zotlabs/Module/Viewsrc.php
@@ -13,6 +13,7 @@ class Viewsrc extends \Zotlabs\Web\Controller {
$item_id = ((argc() > 1) ? intval(argv(1)) : 0);
$json = ((argc() > 2 && argv(2) === 'json') ? true : false);
+ $dload = ((argc() > 2 && argv(2) === 'download') ? true : false);
if(! local_channel()) {
notice( t('Permission denied.') . EOL);
@@ -27,7 +28,7 @@ class Viewsrc extends \Zotlabs\Web\Controller {
$item_normal = item_normal();
if(local_channel() && $item_id) {
- $r = q("select id, item_flags, item_obscured, body from item where uid in (%d , %d) and id = %d $item_normal limit 1",
+ $r = q("select id, item_flags, mimetype, item_obscured, body from item where uid in (%d , %d) and id = %d $item_normal limit 1",
intval(local_channel()),
intval($sys['channel_id']),
intval($item_id)
@@ -35,8 +36,18 @@ class Viewsrc extends \Zotlabs\Web\Controller {
if($r) {
if(intval($r[0]['item_obscured']))
- $r[0]['body'] = crypto_unencapsulate(json_decode($r[0]['body'],true),get_config('system','prvkey'));
- $o = (($json) ? json_encode($r[0]['body']) : str_replace("\n",'<br />',$r[0]['body']));
+ $dload = true;
+
+ if($dload) {
+ header('Content-type: ' . $r[0]['mimetype']);
+ header('Content-disposition: attachment; filename="' . t('item') . '-' . $item_id . '"' );
+ echo $r[0]['body'];
+ killme();
+ }
+
+
+ $content = escape_tags($r[0]['body']);
+ $o = (($json) ? json_encode($content) : str_replace("\n",'<br />',$content));
}
}
diff --git a/Zotlabs/Module/Wall_attach.php b/Zotlabs/Module/Wall_attach.php
index c6fe7518e..e001ad929 100644
--- a/Zotlabs/Module/Wall_attach.php
+++ b/Zotlabs/Module/Wall_attach.php
@@ -2,16 +2,25 @@
namespace Zotlabs\Module;
require_once('include/attach.php');
-require_once('include/channel.php');
require_once('include/photos.php');
-
class Wall_attach extends \Zotlabs\Web\Controller {
+ function init() {
+ logger('request_method: ' . $_SERVER['REQUEST_METHOD'],LOGGER_DATA,LOG_INFO);
+ logger('wall_attach: ' . print_r($_REQUEST,true),LOGGER_DEBUG,LOG_INFO);
+ logger('wall_attach files: ' . print_r($_FILES,true),LOGGER_DEBUG,LOG_INFO);
+ // for testing without actually storing anything
+ // http_status_exit(200,'OK');
+ }
+
+
function post() {
$using_api = false;
-
+
+ $result = [];
+
if($_REQUEST['api_source'] && array_key_exists('media',$_FILES)) {
$using_api = true;
}
@@ -28,7 +37,46 @@ class Wall_attach extends \Zotlabs\Web\Controller {
if(! $channel)
killme();
-
+
+ $matches = [];
+ $partial = false;
+
+ $x = preg_match('/bytes (\d*)\-(\d*)\/(\d*)/',$_SERVER['HTTP_CONTENT_RANGE'],$matches);
+ if($x) {
+ // logger('Content-Range: ' . print_r($matches,true));
+ $partial = true;
+ }
+
+ if($partial) {
+ $x = save_chunk($channel,$matches[1],$matches[2],$matches[3]);
+ if($x['partial']) {
+ header('Range: bytes=0-' . (($x['length']) ? $x['length'] - 1 : 0));
+ json_return_and_die($result);
+ }
+ else {
+ header('Range: bytes=0-' . (($x['size']) ? $x['size'] - 1 : 0));
+
+ $_FILES['userfile'] = [
+ 'name' => $x['name'],
+ 'type' => $x['type'],
+ 'tmp_name' => $x['tmp_name'],
+ 'error' => $x['error'],
+ 'size' => $x['size']
+ ];
+ }
+ }
+ else {
+ if(! array_key_exists('userfile',$_FILES)) {
+ $_FILES['userfile'] = [
+ 'name' => $_FILES['files']['name'],
+ 'type' => $_FILES['files']['type'],
+ 'tmp_name' => $_FILES['files']['tmp_name'],
+ 'error' => $_FILES['files']['error'],
+ 'size' => $_FILES['files']['size']
+ ];
+ }
+ }
+
$observer = \App::get_observer();
@@ -49,12 +97,19 @@ class Wall_attach extends \Zotlabs\Web\Controller {
$s = "\n\n" . '[attachment]' . $r['data']['hash'] . ',' . $r['data']['revision'] . '[/attachment]' . "\n";
}
+
+ $sync = attach_export_data($channel,$r['data']['hash']);
+ if($sync) {
+ build_sync_packet($channel['channel_id'],array('file' => array($sync)));
+ }
+
if($using_api)
return $s;
-
- echo $s;
- killme();
-
+
+ $result['message'] = $s;
+ json_return_and_die($result);
+
}
+
}
diff --git a/Zotlabs/Module/Webpages.php b/Zotlabs/Module/Webpages.php
index 46b94f091..97ec55ba3 100644
--- a/Zotlabs/Module/Webpages.php
+++ b/Zotlabs/Module/Webpages.php
@@ -34,7 +34,9 @@ class Webpages extends \Zotlabs\Web\Controller {
\App::$error = 404;
return;
}
-
+
+ nav_set_selected('Webpages');
+
$which = argv(1);
$_SESSION['return_url'] = \App::$query_string;
@@ -142,7 +144,8 @@ class Webpages extends \Zotlabs\Web\Controller {
$is_owner = ($uid && $uid == $owner);
- $o = profile_tabs($a, $is_owner, \App::$profile['channel_address']);
+ //$o = profile_tabs($a, $is_owner, \App::$profile['channel_address']);
+ $o = '';
$x = array(
'webpage' => ITEM_TYPE_WEBPAGE,
@@ -178,11 +181,8 @@ class Webpages extends \Zotlabs\Web\Controller {
// so just list titles and an edit link.
- /** @TODO - this should be replaced with pagelist_widget */
-
$sql_extra = item_permissions_sql($owner);
-
$r = q("select * from iconfig left join item on iconfig.iid = item.id
where item.uid = %d and iconfig.cat = 'system' and iconfig.k = 'WEBPAGE' and item_type = %d
$sql_extra order by item.created desc",
@@ -190,12 +190,6 @@ class Webpages extends \Zotlabs\Web\Controller {
intval(ITEM_TYPE_WEBPAGE)
);
-// $r = q("select * from item_id left join item on item_id.iid = item.id
-// where item_id.uid = %d and service = 'WEBPAGE' and item_type = %d $sql_extra order by item.created desc",
-// intval($owner),
-// intval(ITEM_TYPE_WEBPAGE)
-// );
-
if(! $r)
$x['pagetitle'] = 'home';
@@ -217,13 +211,15 @@ class Webpages extends \Zotlabs\Web\Controller {
'created' => $rr['created'],
'edited' => $rr['edited'],
'mimetype' => $rr['mimetype'],
- 'pagetitle' => $rr['v'],
+ 'pageurl' => str_replace('%2f','/',$rr['v']),
+ 'pagetitle' => urldecode($rr['v']),
'mid' => $rr['mid'],
'layout_mid' => $rr['layout_mid']
);
$pages[$rr['iid']][] = array(
'url' => $rr['iid'],
- 'pagetitle' => $rr['v'],
+ 'pageurl' => str_replace('%2f','/',$rr['v']),
+ 'pagetitle' => urldecode($rr['v']),
'title' => $rr['title'],
'created' => datetime_convert('UTC',date_default_timezone_get(),$rr['created']),
'edited' => datetime_convert('UTC',date_default_timezone_get(),$rr['edited']),
@@ -693,7 +689,8 @@ class Webpages extends \Zotlabs\Web\Controller {
}
rrmdir($zip_folderpath); rrmdir($tmp_folderpath); // delete temporary files
-
+ killme();
+
break;
default :
break;
diff --git a/Zotlabs/Module/Wfinger.php b/Zotlabs/Module/Wfinger.php
index 04eed47c3..753721d27 100644
--- a/Zotlabs/Module/Wfinger.php
+++ b/Zotlabs/Module/Wfinger.php
@@ -30,14 +30,24 @@ class Wfinger extends \Zotlabs\Web\Controller {
$resource = $_REQUEST['resource'];
logger('webfinger: ' . $resource,LOGGER_DEBUG);
+
+ $root_resource = false;
+ $pchan = false;
+
+ if(strcasecmp(rtrim($resource,'/'),z_root()) === 0)
+ $root_resource = true;
+
$r = null;
- if($resource) {
+ if(($resource) && (! $root_resource)) {
if(strpos($resource,'acct:') === 0) {
$channel = str_replace('acct:','',$resource);
if(strpos($channel,'@') !== false) {
$host = substr($channel,strpos($channel,'@')+1);
+
+ // If the webfinger address points off site, redirect to the correct site
+
if(strcasecmp($host,\App::get_hostname())) {
goaway('https://' . $host . '/.well-known/webfinger?f=&resource=' . $resource . (($zot) ? '&zot=' . $zot : ''));
}
@@ -48,16 +58,47 @@ class Wfinger extends \Zotlabs\Web\Controller {
$channel = str_replace('~','',basename($resource));
}
- $r = q("select * from channel left join xchan on channel_hash = xchan_hash
- where channel_address = '%s' limit 1",
- dbesc($channel)
- );
-
+ if(substr($channel,0,1) === '[' ) {
+ $channel = substr($channel,1);
+ $channel = substr($channel,0,-1);
+ $pchan = true;
+ $r = q("select * from pchan left join xchan on pchan_hash = xchan_hash
+ where pchan_guid = '%s' limit 1",
+ dbesc($channel)
+ );
+ if($r) {
+ $r[0] = pchan_to_chan($r[0]);
+ }
+ }
+ else {
+ $r = q("select * from channel left join xchan on channel_hash = xchan_hash
+ where channel_address = '%s' limit 1",
+ dbesc($channel)
+ );
+ }
}
header('Access-Control-Allow-Origin: *');
+
+ if($root_resource) {
+ $result['subject'] = $resource;
+ $result['properties'] = [
+ 'https://w3id.org/security/v1#publicKeyPem' => get_config('system','pubkey')
+ ];
+ $result['links'] = [
+ [
+ 'rel' => 'http://purl.org/openwebauth/v1',
+ 'type' => 'application/x-zot+json',
+ 'href' => z_root() . '/owa',
+ ],
+ ];
+
+
+
+ }
+
if($resource && $r) {
$h = q("select hubloc_addr from hubloc where hubloc_hash = '%s' and hubloc_deleted = 0",
@@ -67,7 +108,7 @@ class Wfinger extends \Zotlabs\Web\Controller {
$result['subject'] = $resource;
$aliases = array(
- z_root() . '/channel/' . $r[0]['channel_address'],
+ z_root() . (($pchan) ? '/pchan/' : '/channel/') . $r[0]['channel_address'],
z_root() . '/~' . $r[0]['channel_address']
);
@@ -77,64 +118,114 @@ class Wfinger extends \Zotlabs\Web\Controller {
}
}
- $result['aliases'] = array();
+ $result['aliases'] = [];
- $result['properties'] = array(
- 'http://webfinger.net/ns/name' => $r[0]['channel_name'],
- 'http://xmlns.com/foaf/0.1/name' => $r[0]['channel_name']
- );
+ $result['properties'] = [
+ 'http://webfinger.net/ns/name' => $r[0]['channel_name'],
+ 'http://xmlns.com/foaf/0.1/name' => $r[0]['channel_name'],
+ 'https://w3id.org/security/v1#publicKeyPem' => $r[0]['xchan_pubkey']
+ ];
foreach($aliases as $alias)
if($alias != $resource)
$result['aliases'][] = $alias;
- $result['links'] = array(
-
- array(
- 'rel' => 'http://webfinger.net/rel/avatar',
- 'type' => $r[0]['xchan_photo_mimetype'],
- 'href' => $r[0]['xchan_photo_l']
- ),
-
- array(
- 'rel' => 'http://webfinger.net/rel/profile-page',
- 'href' => z_root() . '/profile/' . $r[0]['channel_address'],
- ),
-
- array(
- 'rel' => 'http://webfinger.net/rel/blog',
- 'href' => z_root() . '/channel/' . $r[0]['channel_address'],
- ),
-
- array(
- 'rel' => 'http://ostatus.org/schema/1.0/subscribe',
- 'template' => z_root() . '/follow/url={uri}',
- ),
-
- array(
- 'rel' => 'http://purl.org/zot/protocol',
- 'href' => z_root() . '/.well-known/zot-info' . '?address=' . $r[0]['xchan_addr'],
- ),
-
- array(
- 'rel' => 'magic-public-key',
- 'href' => 'data:application/magic-public-key,' . salmon_key($r[0]['channel_pubkey']),
- )
- );
+
+ if($pchan) {
+ $result['links'] = [
+
+ [
+ 'rel' => 'http://webfinger.net/rel/avatar',
+ 'type' => $r[0]['xchan_photo_mimetype'],
+ 'href' => $r[0]['xchan_photo_l']
+ ],
+
+ [
+ 'rel' => 'http://webfinger.net/rel/profile-page',
+ 'href' => $r[0]['xchan_url'],
+ ],
+
+ [
+ 'rel' => 'magic-public-key',
+ 'href' => 'data:application/magic-public-key,' . salmon_key($r[0]['channel_pubkey']),
+ ]
+
+ ];
+
+
+ }
+ else {
+
+ $result['links'] = [
+
+ [
+ 'rel' => 'http://webfinger.net/rel/avatar',
+ 'type' => $r[0]['xchan_photo_mimetype'],
+ 'href' => $r[0]['xchan_photo_l']
+ ],
+
+ [
+ 'rel' => 'http://microformats.org/profile/hcard',
+ 'type' => 'text/html',
+ 'href' => z_root() . '/hcard/' . $r[0]['channel_address']
+ ],
+
+
+ [
+ 'rel' => 'http://webfinger.net/rel/profile-page',
+ 'href' => z_root() . '/profile/' . $r[0]['channel_address'],
+ ],
+
+ [
+ 'rel' => 'http://schemas.google.com/g/2010#updates-from',
+ 'type' => 'application/atom+xml',
+ 'href' => z_root() . '/ofeed/' . $r[0]['channel_address']
+ ],
+
+ [
+ 'rel' => 'http://webfinger.net/rel/blog',
+ 'href' => z_root() . '/channel/' . $r[0]['channel_address'],
+ ],
+
+ [
+ 'rel' => 'http://ostatus.org/schema/1.0/subscribe',
+ 'template' => z_root() . '/follow?f=&url={uri}',
+ ],
+
+ [
+ 'rel' => 'http://purl.org/zot/protocol',
+ 'href' => z_root() . '/.well-known/zot-info' . '?address=' . $r[0]['xchan_addr'],
+ ],
+
+ [
+ 'rel' => 'http://purl.org/openwebauth/v1',
+ 'type' => 'application/x-zot+json',
+ 'href' => z_root() . '/owa',
+ ],
+
+ [
+ 'rel' => 'magic-public-key',
+ 'href' => 'data:application/magic-public-key,' . salmon_key($r[0]['channel_pubkey']),
+ ]
+ ];
+ }
+
if($zot) {
// get a zotinfo packet and return it with webfinger
- $result['zot'] = zotinfo(array('address' => $r[0]['xchan_addr']));
+ $result['zot'] = zotinfo( [ 'address' => $r[0]['xchan_addr'] ]);
}
}
- else {
+
+ if(! $result) {
header($_SERVER["SERVER_PROTOCOL"] . ' ' . 400 . ' ' . 'Bad Request');
killme();
}
- $arr = array('channel' => $r[0], 'request' => $_REQUEST, 'result' => $result);
+ $arr = [ 'channel' => $r[0], 'pchan' => $pchan, 'request' => $_REQUEST, 'result' => $result ];
call_hooks('webfinger',$arr);
-
+
+
json_return_and_die($arr['result'],'application/jrd+json');
}
diff --git a/Zotlabs/Module/Wiki.php b/Zotlabs/Module/Wiki.php
index d42c26681..d6a01af11 100644
--- a/Zotlabs/Module/Wiki.php
+++ b/Zotlabs/Module/Wiki.php
@@ -3,6 +3,7 @@
namespace Zotlabs\Module;
use \Zotlabs\Lib as Zlib;
+use \Michelf\MarkdownExtra;
require_once('include/acl_selectors.php');
require_once('include/conversation.php');
@@ -41,7 +42,7 @@ class Wiki extends \Zotlabs\Web\Controller {
if(! feature_enabled(\App::$profile_uid,'wiki')) {
notice( t('Not found') . EOL);
- return;
+ return;
}
@@ -75,6 +76,8 @@ class Wiki extends \Zotlabs\Web\Controller {
$wiki_owner = true;
+ nav_set_selected('Wiki');
+
// Obtain the default permission settings of the channel
$owner_acl = array(
'allow_cid' => $owner['channel_allow_cid'],
@@ -106,15 +109,17 @@ class Wiki extends \Zotlabs\Web\Controller {
}
$is_owner = ((local_channel()) && (local_channel() == \App::$profile['profile_uid']) ? true : false);
- $o = profile_tabs($a, $is_owner, \App::$profile['channel_address']);
+ //$o = profile_tabs($a, $is_owner, \App::$profile['channel_address']);
+ $o = '';
// Download a wiki
-/*
+
if((argc() > 3) && (argv(2) === 'download') && (argv(3) === 'wiki')) {
$resource_id = argv(4);
+ $w = Zlib\NativeWiki::get_wiki($owner['channel_id'],$observer_hash,$resource_id);
- $w = Zlib\NativeWiki::get_wiki($owner,$observer_hash,$resource_id);
+// $w = Zlib\NativeWiki::get_wiki($owner,$observer_hash,$resource_id);
if(! $w['htmlName']) {
notice(t('Error retrieving wiki') . EOL);
}
@@ -129,8 +134,41 @@ class Wiki extends \Zotlabs\Web\Controller {
$zip_filename = $w['urlName'];
$zip_filepath = '/tmp/' . $zip_folder_name . '/' . $zip_filename;
+
// Generate the zip file
- ZLib\ExtendedZip::zipTree($w['path'], $zip_filepath, \ZipArchive::CREATE);
+
+ $zip = new \ZipArchive;
+ $r = $zip->open($zip_filepath, \ZipArchive::CREATE);
+ if($r === true) {
+ $pages = [];
+ $i = q("select * from item where resource_type = 'nwikipage' and resource_id = '%s' order by revision desc",
+ dbesc($resource_id)
+ );
+
+ if($i) {
+ foreach($i as $iv) {
+ if(in_array($iv['mid'],$pages))
+ continue;
+
+ if($iv['mimetype'] === 'text/plain') {
+ $content = html_entity_decode($iv['body'],ENT_COMPAT,'UTF-8');
+ }
+ elseif($iv['mimetype'] === 'text/bbcode') {
+ $content = html_entity_decode($iv['body'],ENT_COMPAT,'UTF-8');
+ }
+ elseif($iv['mimetype'] === 'text/markdown') {
+ $content = html_entity_decode(Zlib\MarkdownSoap::unescape($iv['body']),ENT_COMPAT,'UTF-8');
+ }
+ $fname = get_iconfig($iv['id'],'nwikipage','pagetitle') . Zlib\NativeWikiPage::get_file_ext($iv);
+ $zip->addFromString($fname,$content);
+ $pages[] = $iv['mid'];
+ }
+
+
+ }
+
+ }
+ $zip->close();
// Output the file for download
@@ -149,10 +187,11 @@ class Wiki extends \Zotlabs\Web\Controller {
killme();
}
-*/
+
switch(argc()) {
case 2:
$wikis = Zlib\NativeWiki::listwikis($owner, get_observer_hash());
+
if($wikis) {
$o .= replace_macros(get_markup_template('wikilist.tpl'), array(
'$header' => t('Wikis'),
@@ -166,16 +205,19 @@ class Wiki extends \Zotlabs\Web\Controller {
'$create' => t('Create New'),
'$submit' => t('Submit'),
'$wikiName' => array('wikiName', t('Wiki name')),
- '$mimeType' => array('mimeType', t('Content type'), '', '', ['text/markdown' => 'Markdown', 'text/bbcode' => 'BB Code']),
+ '$mimeType' => array('mimeType', t('Content type'), '', '', ['text/markdown' => t('Markdown'), 'text/bbcode' => t('BBcode'), 'text/plain' => t('Text') ]),
'$name' => t('Name'),
'$type' => t('Type'),
+ '$unlocked' => t('Any&nbsp;type'),
'$lockstate' => $x['lockstate'],
'$acl' => $x['acl'],
'$allow_cid' => $x['allow_cid'],
'$allow_gid' => $x['allow_gid'],
'$deny_cid' => $x['deny_cid'],
'$deny_gid' => $x['deny_gid'],
- '$notify' => array('postVisible', t('Create a status post for this wiki'), '', '', array(t('No'), t('Yes')))
+ '$typelock' => array('typelock', t('Lock content type'), '', '', array(t('No'), t('Yes'))),
+ '$notify' => array('postVisible', t('Create a status post for this wiki'), '', '', array(t('No'), t('Yes'))),
+ '$edit_wiki_name' => t('Edit Wiki Name')
));
return $o;
@@ -190,12 +232,29 @@ class Wiki extends \Zotlabs\Web\Controller {
goaway(z_root() . '/' . argv(0) . '/' . argv(1) . '/' . $wikiUrlName . '/Home');
case 4:
+ default:
// GET /wiki/channel/wiki/page
// Fetch the wiki info and determine observer permissions
$wikiUrlName = urldecode(argv(2));
- $pageUrlName = urldecode(argv(3));
+
+ $page_name = '';
+ $ignore_language = false;
+
+ for($x = 3; $x < argc(); $x ++) {
+ if($page_name === '' && argv($x) === '-') {
+ $ignore_language = true;
+ continue;
+ }
+ if($page_name) {
+ $page_name .= '/';
+ }
+ $page_name .= argv($x);
+ }
+
+ $pageUrlName = urldecode($page_name);
+ $langPageUrlName = urldecode(\App::$language . '/' . $page_name);
$w = Zlib\NativeWiki::exists_by_name($owner['channel_id'], $wikiUrlName);
@@ -225,35 +284,46 @@ class Wiki extends \Zotlabs\Web\Controller {
$wikiheaderPage = urldecode($pageUrlName);
$renamePage = (($wikiheaderPage === 'Home') ? '' : t('Rename page'));
+ $p = [];
- $p = Zlib\NativeWikiPage::get_page_content(array('channel_id' => $owner['channel_id'], 'observer_hash' => $observer_hash, 'resource_id' => $resource_id, 'pageUrlName' => $pageUrlName));
- if(! $p['success']) {
+ if(! $ignore_language) {
+ $p = Zlib\NativeWikiPage::get_page_content(array('channel_id' => $owner['channel_id'], 'observer_hash' => $observer_hash, 'resource_id' => $resource_id, 'pageUrlName' => $langPageUrlName));
+ }
+ if(! ($p && $p['success'])) {
+ $p = Zlib\NativeWikiPage::get_page_content(array('channel_id' => $owner['channel_id'], 'observer_hash' => $observer_hash, 'resource_id' => $resource_id, 'pageUrlName' => $pageUrlName));
+ }
+ if(! ($p && $p['success'])) {
notice( t('Error retrieving page content') . EOL);
goaway(z_root() . '/' . argv(0) . '/' . argv(1) );
}
- $mimeType = $p['mimeType'];
+ $mimeType = $p['pageMimeType'];
+
+ $sampleContent = (($mimeType == 'text/bbcode') ? '[h3]' . t('New page') . '[/h3]' : '### ' . t('New page'));
+ if($mimeType === 'text/plain')
+ $sampleContent = t('New page');
+
+ $content = (($p['content'] == '') ? $sampleContent : $p['content']);
- $rawContent = (($p['mimeType'] == 'text/bbcode')
- ? htmlspecialchars_decode(json_decode($p['content']),ENT_COMPAT)
- : htmlspecialchars_decode($p['content'],ENT_COMPAT)
- );
- $content = ($p['content'] !== '' ? $rawContent : '"# New page\n"');
// Render the Markdown-formatted page content in HTML
if($mimeType == 'text/bbcode') {
$renderedContent = Zlib\NativeWikiPage::convert_links(zidify_links(smilies(bbcode($content))), argv(0) . '/' . argv(1) . '/' . $wikiUrlName);
}
- else {
- require_once('library/markdown.php');
- $html = Zlib\NativeWikiPage::generate_toc(zidify_text(purify_html(Markdown(Zlib\NativeWikiPage::bbcode(json_decode($content))))));
+ elseif($mimeType === 'text/plain') {
+ $renderedContent = str_replace(["\n",' ',"\t"],[EOL,'&nbsp;','&nbsp;&nbsp;&nbsp;&nbsp;'],htmlentities($content,ENT_COMPAT,'UTF-8',false));
+ }
+ elseif($mimeType === 'text/markdown') {
+ $content = Zlib\MarkdownSoap::unescape($content);
+ $html = Zlib\NativeWikiPage::generate_toc(zidify_text(MarkdownExtra::defaultTransform(Zlib\NativeWikiPage::bbcode($content))));
$renderedContent = Zlib\NativeWikiPage::convert_links($html, argv(0) . '/' . argv(1) . '/' . $wikiUrlName);
}
$showPageControls = $wiki_editor;
break;
- default: // Strip the extraneous URL components
- goaway('/' . argv(0) . '/' . argv(1) . '/' . $wikiUrlName . '/' . $pageUrlName);
+// default: // Strip the extraneous URL components
+// goaway('/' . argv(0) . '/' . argv(1) . '/' . $wikiUrlName . '/' . $pageUrlName);
}
+
$wikiModalID = random_string(3);
$wikiModal = replace_macros(get_markup_template('generic_modal.tpl'), array(
@@ -263,6 +333,9 @@ class Wiki extends \Zotlabs\Web\Controller {
'$cancel' => t('Cancel')
));
+ $types = [ 'text/bbcode' => t('BBcode'), 'text/markdown' => t('Markdown'), 'text/plain' => 'Text' ];
+ $currenttype = $types[$mimeType];
+
$placeholder = t('Short description of your changes (optional)');
$o .= replace_macros(get_markup_template('wiki.tpl'),array(
@@ -272,10 +345,12 @@ class Wiki extends \Zotlabs\Web\Controller {
'$showPageControls' => $showPageControls,
'$editOrSourceLabel' => (($showPageControls) ? t('Edit') : t('Source')),
'$tools_label' => 'Page Tools',
- '$channel' => $owner['channel_address'],
+ '$channel_address' => $owner['channel_address'],
+ '$channel_id' => $owner['channel_id'],
'$resource_id' => $resource_id,
'$page' => $pageUrlName,
'$mimeType' => $mimeType,
+ '$typename' => $currenttype,
'$content' => $content,
'$renderedContent' => $renderedContent,
'$pageRename' => array('pageRename', t('New page name'), '', ''),
@@ -295,8 +370,8 @@ class Wiki extends \Zotlabs\Web\Controller {
'$modalerroralbum' => t('Error getting album'),
));
- if($p['mimeType'] != 'text/bbcode')
- head_add_js('library/ace/ace.js'); // Ace Code Editor
+ if($p['pageMimeType'] === 'text/markdown')
+ head_add_js('/library/ace/ace.js'); // Ace Code Editor
return $o;
}
@@ -314,31 +389,33 @@ class Wiki extends \Zotlabs\Web\Controller {
return;
}
- if(! perm_is_allowed(\App::$profile_uid,get_observer_hash(),'write_wiki')) {
- notice( t('Permission denied.') . EOL);
- return;
- }
-
// /wiki/channel/preview
// Render mardown-formatted text in HTML for preview
if((argc() > 2) && (argv(2) === 'preview')) {
$content = $_POST['content'];
$resource_id = $_POST['resource_id'];
+
$w = Zlib\NativeWiki::get_wiki($owner['channel_id'],$observer_hash,$resource_id);
$wikiURL = argv(0) . '/' . argv(1) . '/' . $w['urlName'];
- $mimeType = $w['mimeType'];
+ $mimeType = $_POST['mimetype'];
- if($mimeType == 'text/bbcode') {
+ if($mimeType === 'text/bbcode') {
$html = Zlib\NativeWikiPage::convert_links(zidify_links(smilies(bbcode($content))),$wikiURL);
}
- else {
- require_once('library/markdown.php');
- $content = Zlib\NativeWikiPage::bbcode($content);
- $html = Zlib\NativeWikiPage::generate_toc(zidify_text(purify_html(Markdown($content))));
+ elseif($mimeType === 'text/markdown') {
+ $bb = Zlib\NativeWikiPage::bbcode($content);
+ $x = new ZLib\MarkdownSoap($bb);
+ $md = $x->clean();
+ $md = ZLib\MarkdownSoap::unescape($md);
+ $html = MarkdownExtra::defaultTransform($md);
+ $html = Zlib\NativeWikiPage::generate_toc(zidify_text($html));
$html = Zlib\NativeWikiPage::convert_links($html,$wikiURL);
}
+ elseif($mimeType === 'text/plain') {
+ $html = str_replace(["\n",' ',"\t"],[EOL,'&nbsp;','&nbsp;&nbsp;&nbsp;&nbsp;'],htmlentities($content,ENT_COMPAT,'UTF-8',false));
+ }
json_return_and_die(array('html' => $html, 'success' => true));
}
@@ -359,10 +436,19 @@ class Wiki extends \Zotlabs\Web\Controller {
$wiki['htmlName'] = escape_tags($_POST['wikiName']);
$wiki['urlName'] = urlencode(urlencode($_POST['wikiName']));
$wiki['mimeType'] = $_POST['mimeType'];
+ $wiki['typelock'] = $_POST['typelock'];
if($wiki['urlName'] === '') {
notice( t('Error creating wiki. Invalid name.') . EOL);
goaway('/wiki');
+ return; //not reached
+ }
+
+ $exists = Zlib\NativeWiki::exists_by_name($owner['channel_id'], $wiki['urlName']);
+ if($exists['id']) {
+ notice( t('A wiki with this name already exists.') . EOL);
+ goaway('/wiki');
+ return; //not reached
}
// Get ACL for permissions
@@ -371,7 +457,7 @@ class Wiki extends \Zotlabs\Web\Controller {
$r = Zlib\NativeWiki::create_wiki($owner, $observer_hash, $wiki, $acl);
if($r['success']) {
Zlib\NativeWiki::sync_a_wiki_item($owner['channel_id'],$r['item_id'],$r['item']['resource_id']);
- $homePage = Zlib\NativeWikiPage::create_page($owner['channel_id'],$observer_hash,'Home', $r['item']['resource_id']);
+ $homePage = Zlib\NativeWikiPage::create_page($owner['channel_id'],$observer_hash,'Home', $r['item']['resource_id'], $wiki['mimeType']);
if(! $homePage['success']) {
notice( t('Wiki created, but error creating Home page.'));
goaway(z_root() . '/wiki/' . $nick . '/' . $wiki['urlName']);
@@ -385,6 +471,52 @@ class Wiki extends \Zotlabs\Web\Controller {
}
}
+ // Update a wiki
+ // /wiki/channel/update/wiki
+ if ((argc() > 3) && (argv(2) === 'update') && (argv(3) === 'wiki')) {
+ // Only the channel owner can update a wiki, at least until we create a
+ // more detail permissions framework
+
+ if (local_channel() !== intval($owner['channel_id'])) {
+ goaway('/' . argv(0) . '/' . $nick . '/');
+ }
+
+ $arr = [];
+
+ $arr['urlName'] = urlencode(urlencode($_POST['origRawName']));
+
+ if($_POST['updateRawName'])
+ $arr['updateRawName'] = $_POST['updateRawName'];
+
+ if(($arr['urlName'] || $arr['updateRawName']) === '') {
+ notice( t('Error updating wiki. Invalid name.') . EOL);
+ goaway('/wiki');
+ return; //not reached
+ }
+
+ $wiki = Zlib\NativeWiki::exists_by_name($owner['channel_id'], $arr['urlName']);
+
+ if($wiki['resource_id']) {
+
+ $arr['resource_id'] = $wiki['resource_id'];
+
+ $acl = new \Zotlabs\Access\AccessList($owner);
+ $acl->set_from_array($_POST);
+
+ $r = Zlib\NativeWiki::update_wiki($owner['channel_id'], $observer_hash, $arr, $acl);
+ if($r['success']) {
+ Zlib\NativeWiki::sync_a_wiki_item($owner['channel_id'],$r['item_id'],$r['item']['resource_id']);
+ goaway(z_root() . '/wiki/' . $nick);
+ }
+ else {
+ notice( t('Error updating wiki'));
+ goaway(z_root() . '/wiki');
+ }
+
+ }
+ goaway(z_root() . '/wiki');
+ }
+
// Delete a wiki
if ((argc() > 3) && (argv(2) === 'delete') && (argv(3) === 'wiki')) {
@@ -410,11 +542,13 @@ class Wiki extends \Zotlabs\Web\Controller {
// Create a page
if ((argc() === 4) && (argv(2) === 'create') && (argv(3) === 'page')) {
+ $mimetype = $_POST['mimetype'];
+
$resource_id = $_POST['resource_id'];
// Determine if observer has permission to create a page
+
-
- $perms = Zlib\NativeWiki::get_permissions($resource_id, intval($owner['channel_id']), $observer_hash);
+ $perms = Zlib\NativeWiki::get_permissions($resource_id, intval($owner['channel_id']), $observer_hash, $mimetype);
if(! $perms['write']) {
logger('Wiki write permission denied. ' . EOL);
json_return_and_die(array('success' => false));
@@ -424,7 +558,7 @@ class Wiki extends \Zotlabs\Web\Controller {
if(urlencode(escape_tags($_POST['pageName'])) === '') {
json_return_and_die(array('message' => 'Error creating page. Invalid name.', 'success' => false));
}
- $page = Zlib\NativeWikiPage::create_page($owner['channel_id'],$observer_hash, $name, $resource_id);
+ $page = Zlib\NativeWikiPage::create_page($owner['channel_id'],$observer_hash, $name, $resource_id, $mimetype);
if($page['item_id']) {
$commit = Zlib\NativeWikiPage::commit(array(
@@ -461,10 +595,16 @@ class Wiki extends \Zotlabs\Web\Controller {
json_return_and_die(array('pages' => null, 'message' => 'Permission denied.', 'success' => false));
}
- $page_list_html = widget_wiki_pages(array(
- 'resource_id' => $resource_id,
- 'refresh' => true,
- 'channel' => argv(1)));
+ // @FIXME - we shouldn't invoke this if it isn't in the PDL or has been over-ridden
+
+ $x = new \Zotlabs\Widget\Wiki_pages();
+
+ $page_list_html = $x->widget([
+ 'resource_id' => $resource_id,
+ 'channel_id' => $owner['channel_id'],
+ 'channel_address' => $owner['channel_address'],
+ 'refresh' => true
+ ]);
json_return_and_die(array('pages' => $page_list_html, 'message' => '', 'success' => true));
}
@@ -519,7 +659,6 @@ class Wiki extends \Zotlabs\Web\Controller {
$resource_id = $_POST['resource_id'];
$pageUrlName = $_POST['name'];
-
// Determine if observer has permission to read content
$perms = Zlib\NativeWiki::get_permissions($resource_id, intval($owner['channel_id']), $observer_hash);
@@ -528,11 +667,12 @@ class Wiki extends \Zotlabs\Web\Controller {
json_return_and_die(array('historyHTML' => '', 'message' => 'Permission denied.', 'success' => false));
}
- $historyHTML = widget_wiki_page_history(array(
+ $historyHTML = \Zotlabs\Lib\NativeWikiPage::render_page_history(array(
'resource_id' => $resource_id,
'pageUrlName' => $pageUrlName,
'permsWrite' => $perms['write']
));
+
json_return_and_die(array('historyHTML' => $historyHTML, 'message' => '', 'success' => true));
}
diff --git a/Zotlabs/Module/Xrd.php b/Zotlabs/Module/Xrd.php
index 3ed19962b..959e31cbe 100644
--- a/Zotlabs/Module/Xrd.php
+++ b/Zotlabs/Module/Xrd.php
@@ -9,6 +9,7 @@ class Xrd extends \Zotlabs\Web\Controller {
function init() {
$uri = urldecode(notags(trim($_GET['uri'])));
+ $subject = $uri;
logger('xrd: ' . $uri,LOGGER_DEBUG);
$resource = $uri;
@@ -30,13 +31,7 @@ class Xrd extends \Zotlabs\Web\Controller {
);
if(! $r)
killme();
-
- $dspr = replace_macros(get_markup_template('xrd_diaspora.tpl'),array(
- '$baseurl' => z_root(),
- '$dspr_guid' => $r[0]['channel_guid'] . str_replace('.','',\App::get_hostname()),
- '$dspr_key' => base64_encode(pemtorsa($r[0]['channel_pubkey']))
- ));
-
+
$salmon_key = salmon_key($r[0]['channel_pubkey']);
header('Access-Control-Allow-Origin: *');
@@ -49,24 +44,21 @@ class Xrd extends \Zotlabs\Web\Controller {
if($aliases[$x] === $resource)
unset($aliases[$x]);
}
-
-
+
$o = replace_macros(get_markup_template('xrd_person.tpl'), array(
'$nick' => $r[0]['channel_address'],
'$accturi' => $resource,
+ '$subject' => $subject,
'$aliases' => $aliases,
+ '$channel_url' => z_root() . '/channel/' . $r[0]['channel_address'],
'$profile_url' => z_root() . '/channel/' . $r[0]['channel_address'],
'$hcard_url' => z_root() . '/hcard/' . $r[0]['channel_address'],
- '$atom' => z_root() . '/feed/' . $r[0]['channel_address'],
+ '$atom' => z_root() . '/ofeed/' . $r[0]['channel_address'],
'$zot_post' => z_root() . '/post/' . $r[0]['channel_address'],
'$poco_url' => z_root() . '/poco/' . $r[0]['channel_address'],
'$photo' => z_root() . '/photo/profile/l/' . $r[0]['channel_id'],
- '$dspr' => $dspr,
- // '$salmon' => z_root() . '/salmon/' . $r[0]['channel_address'],
- // '$salmen' => z_root() . '/salmon/' . $r[0]['channel_address'] . '/mention',
'$modexp' => 'data:application/magic-public-key,' . $salmon_key,
- '$subscribe' => z_root() . '/follow?url={uri}',
- '$bigkey' => salmon_key($r[0]['channel_pubkey'])
+ '$subscribe' => z_root() . '/follow?f=&amp;url={uri}',
));
diff --git a/Zotlabs/Module/Zfinger.php b/Zotlabs/Module/Zfinger.php
index 2ff605fc9..0f7f6a64b 100644
--- a/Zotlabs/Module/Zfinger.php
+++ b/Zotlabs/Module/Zfinger.php
@@ -9,8 +9,36 @@ class Zfinger extends \Zotlabs\Web\Controller {
require_once('include/zot.php');
require_once('include/crypto.php');
-
$x = zotinfo($_REQUEST);
+
+ if($x && $x['guid'] && $x['guid_sig']) {
+ $chan_hash = make_xchan_hash($x['guid'],$x['guid_sig']);
+ if($chan_hash) {
+ $chan = channelx_by_hash($chan_hash);
+ }
+ }
+
+ $headers = [];
+ $headers['Content-Type'] = 'application/json' ;
+ $ret = json_encode($x);
+
+ if($chan) {
+ $hash = \Zotlabs\Web\HTTPSig::generate_digest($ret,false);
+ $headers['Digest'] = 'SHA-256=' . $hash;
+ \Zotlabs\Web\HTTPSig::create_sig('',$headers,$chan['channel_prvkey'],
+ 'acct:' . $chan['channel_address'] . '@' . \App::get_hostname(),true);
+ }
+ else {
+ foreach($headers as $k => $v) {
+ header($k . ': ' . $v);
+ }
+ }
+
+ echo $ret;
+ killme();
+
+
+
json_return_and_die($x);
}
diff --git a/Zotlabs/Module/Zotfeed.php b/Zotlabs/Module/Zotfeed.php
index 6b505c890..381e3acb2 100644
--- a/Zotlabs/Module/Zotfeed.php
+++ b/Zotlabs/Module/Zotfeed.php
@@ -22,7 +22,8 @@ class Zotfeed extends \Zotlabs\Web\Controller {
$observer = \App::get_observer();
-
+ logger('observer: ' . get_observer_hash(), LOGGER_DEBUG);
+
$channel_address = ((argc() > 1) ? argv(1) : '');
if($channel_address) {
$r = q("select channel_id, channel_name from channel where channel_address = '%s' and channel_removed = 0 limit 1",
diff --git a/Zotlabs/Render/Comanche.php b/Zotlabs/Render/Comanche.php
index 5826063fd..8831bd117 100644
--- a/Zotlabs/Render/Comanche.php
+++ b/Zotlabs/Render/Comanche.php
@@ -4,8 +4,6 @@ namespace Zotlabs\Render;
require_once('include/security.php');
require_once('include/menu.php');
-require_once('include/widgets.php');
-
class Comanche {
@@ -20,7 +18,49 @@ class Comanche {
$s = str_replace($mtch[0], '', $s);
}
}
-
+
+ /*
+ * This section supports the "switch" statement of the form given by the following
+ * example. The [default][/default] block must be the last in the arbitrary
+ * list of cases. The first case that matches the switch variable is used
+ * and the rest are not evaluated.
+ *
+ * [switch observer.language]
+ * [case de]
+ * [block]german-content[/block]
+ * [/case]
+ * [case es]
+ * [block]spanish-content[/block]
+ * [/case]
+ * [default]
+ * [block]english-content[/block]
+ * [/default]
+ * [/switch]
+ */
+
+ $cnt = preg_match_all("/\[switch (.*?)\](.*?)\[default\](.*?)\[\/default\]\s*\[\/switch\]/ism", $s, $matches, PREG_SET_ORDER);
+ if($cnt) {
+ foreach($matches as $mtch) {
+ $switch_done = 0;
+ $switch_var = $this->get_condition_var($mtch[1]);
+ $default = $mtch[3];
+ $cases = array();
+ $cntt = preg_match_all("/\[case (.*?)\](.*?)\[\/case\]/ism", $mtch[2], $cases, PREG_SET_ORDER);
+ if($cntt) {
+ foreach($cases as $case) {
+ if($case[1] === $switch_var) {
+ $switch_done = 1;
+ $s = str_replace($mtch[0], $case[2], $s);
+ break;
+ }
+ }
+ if($switch_done === 0) {
+ $s = str_replace($mtch[0], $default, $s);
+ }
+ }
+ }
+ }
+
$cnt = preg_match_all("/\[if (.*?)\](.*?)\[else\](.*?)\[\/if\]/ism", $s, $matches, PREG_SET_ORDER);
if($cnt) {
foreach($matches as $mtch) {
@@ -81,6 +121,11 @@ class Comanche {
if($cnt)
\App::$layout['theme'] = trim($matches[1]);
+ $cnt = preg_match("/\[navbar\](.*?)\[\/navbar\]/ism", $s, $matches);
+ if($cnt)
+ \App::$layout['navbar'] = trim($matches[1]);
+
+
$cnt = preg_match_all("/\[webpage\](.*?)\[\/webpage\]/ism", $s, $matches, PREG_SET_ORDER);
if($cnt) {
// only the last webpage definition is used if there is more than one
@@ -108,6 +153,7 @@ class Comanche {
* $observer.address - xchan_addr or false
* $observer.name - xchan_name or false
* $observer - xchan_hash of observer or empty string
+ * $local_channel - logged in channel_id or false
*/
function get_condition_var($v) {
@@ -117,6 +163,9 @@ class Comanche {
return get_config($x[1],$x[2]);
elseif($x[0] === 'request')
return $_SERVER['REQUEST_URI'];
+ elseif($x[0] === 'local_channel') {
+ return local_channel();
+ }
elseif($x[0] === 'observer') {
if(count($x) > 1) {
if($x[1] == 'language')
@@ -128,6 +177,8 @@ class Comanche {
return $y['xchan_addr'];
elseif($x[1] == 'name')
return $y['xchan_name'];
+ elseif($x[1] == 'webname')
+ return substr($y['xchan_addr'],0,strpos($y['xchan_addr'],'@'));
return false;
}
return get_observer_hash();
@@ -410,6 +461,24 @@ class Comanche {
}
}
+ if(! purify_filename($name))
+ return '';
+
+ $clsname = ucfirst($name);
+ $nsname = "\\Zotlabs\\Widget\\" . $clsname;
+
+ if(file_exists('Zotlabs/SiteWidget/' . $clsname . '.php'))
+ require_once('Zotlabs/SiteWidget/' . $clsname . '.php');
+ elseif(file_exists('Zotlabs/Widget/' . $clsname . '.php'))
+ require_once('Zotlabs/Widget/' . $clsname . '.php');
+ if(class_exists($nsname)) {
+ $x = new $nsname;
+ $f = 'widget';
+ if(method_exists($x,$f)) {
+ return $x->$f($vars);
+ }
+ }
+
$func = 'widget_' . trim($name);
if(! function_exists($func)) {
diff --git a/Zotlabs/Render/Theme.php b/Zotlabs/Render/Theme.php
index 9f9009d72..09cc7a4d4 100644
--- a/Zotlabs/Render/Theme.php
+++ b/Zotlabs/Render/Theme.php
@@ -2,6 +2,8 @@
namespace Zotlabs\Render;
+use App;
+
class Theme {
@@ -11,17 +13,28 @@ class Theme {
static $session_theme = null;
static $session_mobile_theme = null;
- static $base_themes = array('redbasic');
+ /**
+ * @brief Array with base or fallback themes.
+ */
+ static $base_themes = array('redbasic');
+
+ /**
+ * @brief Figure out the best matching theme and return it.
+ *
+ * The theme will depend on channel settings, mobile, session, core compatibility, etc.
+ *
+ * @return array
+ */
static public function current(){
- self::$system_theme = ((isset(\App::$config['system']['theme']))
+ self::$system_theme = ((isset(\App::$config['system']['theme']))
? \App::$config['system']['theme'] : '');
- self::$session_theme = ((isset($_SESSION) && x($_SESSION,'theme'))
+ self::$session_theme = ((isset($_SESSION) && x($_SESSION, 'theme'))
? $_SESSION['theme'] : self::$system_theme);
- self::$system_mobile_theme = ((isset(\App::$config['system']['mobile_theme']))
+ self::$system_mobile_theme = ((isset(\App::$config['system']['mobile_theme']))
? \App::$config['system']['mobile_theme'] : '');
- self::$session_mobile_theme = ((isset($_SESSION) && x($_SESSION,'mobile_theme'))
+ self::$session_mobile_theme = ((isset($_SESSION) && x($_SESSION, 'mobile_theme'))
? $_SESSION['mobile_theme'] : self::$system_mobile_theme);
$page_theme = null;
@@ -66,13 +79,19 @@ class Theme {
$chosen_theme = $page_theme;
}
}
- if(array_key_exists('theme_preview',$_GET))
+ if(array_key_exists('theme_preview', $_GET))
$chosen_theme = $_GET['theme_preview'];
// Allow theme selection of the form 'theme_name:schema_name'
-
$themepair = explode(':', $chosen_theme);
+ // Check if $chosen_theme is compatible with core. If not fall back to default
+ $info = get_theme_info($themepair[0]);
+ $compatible = check_plugin_versions($info);
+ if(!$compatible) {
+ $chosen_theme = '';
+ }
+
if($chosen_theme && (file_exists('view/theme/' . $themepair[0] . '/css/style.css') || file_exists('view/theme/' . $themepair[0] . '/php/style.php'))) {
return($themepair);
}
@@ -85,14 +104,12 @@ class Theme {
}
// Worst case scenario, the default base theme or themes don't exist; perhaps somebody renamed it/them.
-
- // Find any theme at all and use it.
-
- $fallback = array_merge(glob('view/theme/*/css/style.css'),glob('view/theme/*/php/style.php'));
- if(count($fallback))
- return(array(str_replace('view/theme/','', substr($fallback[0],0,-14))));
+ // Find any theme at all and use it.
+ $fallback = array_merge(glob('view/theme/*/css/style.css'), glob('view/theme/*/php/style.php'));
+ if(count($fallback))
+ return(array(str_replace('view/theme/', '', substr($fallback[0], 0, -14))));
}
@@ -101,12 +118,11 @@ class Theme {
*
* Provide a sane default if nothing is chosen or the specified theme does not exist.
*
- * @param bool $installing default false
+ * @param bool $installing (optional) default false, if true return the name of the first base theme
*
* @return string
*/
-
- function url($installing = false) {
+ static public function url($installing = false) {
if($installing)
return self::$base_themes[0];
@@ -119,21 +135,21 @@ class Theme {
$opts = '';
$opts = ((\App::$profile_uid) ? '?f=&puid=' . \App::$profile_uid : '');
- $schema_str = ((x(\App::$layout,'schema')) ? '&schema=' . App::$layout['schema'] : '');
+ $schema_str = ((x(\App::$layout,'schema')) ? '&schema=' . App::$layout['schema'] : '');
if(($s) && (! $schema_str))
$schema_str = '&schema=' . $s;
+
$opts .= $schema_str;
if(file_exists('view/theme/' . $t . '/php/style.php'))
- return('view/theme/' . $t . '/php/style.pcss' . $opts);
+ return('/view/theme/' . $t . '/php/style.pcss' . $opts);
- return('view/theme/' . $t . '/css/style.css');
+ return('/view/theme/' . $t . '/css/style.css');
}
function debug() {
logger('system_theme: ' . self::$system_theme);
logger('session_theme: ' . self::$session_theme);
-
}
}
diff --git a/Zotlabs/Storage/BasicAuth.php b/Zotlabs/Storage/BasicAuth.php
index 0ff9fad13..d8af03703 100644
--- a/Zotlabs/Storage/BasicAuth.php
+++ b/Zotlabs/Storage/BasicAuth.php
@@ -187,14 +187,11 @@ class BasicAuth extends DAV\Auth\Backend\AbstractBasic {
}
protected function check_module_access($channel_id) {
- if($channel_id && \App::$module === 'cdav') {
- $x = get_pconfig($channel_id,'cdav','enabled');
- if(! $x) {
- $this->module_disabled = true;
- return false;
- }
+ if($channel_id && in_array(\App::$module,[ 'dav', 'cdav', 'snap'] )) {
+ return true;
}
- return true;
+ $this->module_disabled = true;
+ return false;
}
/**
diff --git a/Zotlabs/Storage/Browser.php b/Zotlabs/Storage/Browser.php
index a30eedba5..6f6f4a292 100644
--- a/Zotlabs/Storage/Browser.php
+++ b/Zotlabs/Storage/Browser.php
@@ -17,6 +17,7 @@ use Sabre\DAV;
*/
class Browser extends DAV\Browser\Plugin {
+ public $build_page = false;
/**
* @see set_writeable()
* @see \\Sabre\\DAV\\Auth\\Backend\\BackendInterface
@@ -84,7 +85,7 @@ class Browser extends DAV\Browser\Plugin {
require_once('include/conversation.php');
require_once('include/text.php');
if ($this->auth->owner_nick) {
- $html = profile_tabs(get_app(), (($is_owner) ? true : false), $this->auth->owner_nick);
+ $html = '';
}
$files = $this->server->getPropertiesForPath($path, array(
@@ -240,9 +241,13 @@ class Browser extends DAV\Browser\Plugin {
'$nick' => $this->auth->getCurrentUser()
));
- $a = get_app();
+
+ $a = false;
+
+ nav_set_selected('Files');
+
\App::$page['content'] = $html;
- load_pdl($a);
+ load_pdl();
$current_theme = \Zotlabs\Render\Theme::current();
@@ -255,7 +260,7 @@ class Browser extends DAV\Browser\Plugin {
}
}
$this->server->httpResponse->setHeader('Content-Security-Policy', "script-src 'self' 'unsafe-inline' 'unsafe-eval'; style-src 'self' 'unsafe-inline'");
- construct_page($a);
+ $this->build_page = true;
}
/**
@@ -314,7 +319,16 @@ class Browser extends DAV\Browser\Plugin {
$quota['desc'] = $quotaDesc;
$quota['warning'] = ((($limit) && ((round($used / $limit, 1) * 100) >= 90)) ? t('WARNING:') : ''); // 10485760 bytes = 100MB
- $path = trim(str_replace('cloud/' . $this->auth->owner_nick, '', $path), '/');
+ // strip 'cloud/nickname', but only at the beginning of the path
+
+ $special = 'cloud/' . $this->auth->owner_nick;
+ $count = strlen($special);
+
+ if(strpos($path,$special) === 0)
+ $path = trim(substr($path,$count),'/');
+
+ $info = t('Please use DAV to upload large (video, audio) files.<br>See <a class="zrl" href="help/member/member_guide#Cloud_Desktop_Clients">Cloud Desktop Clients</a>');
+
$output .= replace_macros(get_markup_template('cloud_actionspanel.tpl'), array(
'$folder_header' => t('Create new folder'),
@@ -322,6 +336,7 @@ class Browser extends DAV\Browser\Plugin {
'$upload_header' => t('Upload file'),
'$upload_submit' => t('Upload'),
'$quota' => $quota,
+ '$info' => $info,
'$channick' => $this->auth->owner_nick,
'$aclselect' => $aclselect,
'$allow_cid' => acl2json($channel_acl['allow_cid']),
@@ -332,7 +347,8 @@ class Browser extends DAV\Browser\Plugin {
'$return_url' => \App::$cmd,
'$path' => $path,
'$folder' => find_folder_hash_by_path($this->auth->owner_id, $path),
- '$dragdroptext' => t('Drop files here to immediately upload')
+ '$dragdroptext' => t('Drop files here to immediately upload'),
+ '$notify' => ['notify', t('Show in your contacts shared folder'), 0, '', [t('No'), t('Yes')]]
));
}
diff --git a/Zotlabs/Storage/Directory.php b/Zotlabs/Storage/Directory.php
index 5d078b04e..0ed7a3c68 100644
--- a/Zotlabs/Storage/Directory.php
+++ b/Zotlabs/Storage/Directory.php
@@ -49,7 +49,7 @@ class Directory extends DAV\Node implements DAV\ICollection, DAV\IQuota {
* @param BasicAuth &$auth_plugin
*/
public function __construct($ext_path, &$auth_plugin) {
-// $ext_path = urldecode($ext_path);
+ // $ext_path = urldecode($ext_path);
logger('directory ' . $ext_path, LOGGER_DATA);
$this->ext_path = $ext_path;
// remove "/cloud" from the beginning of the path
@@ -167,6 +167,14 @@ class Directory extends DAV\Node implements DAV\ICollection, DAV\IQuota {
intval($this->auth->owner_id)
);
+ $x = attach_syspaths($this->auth->owner_id,$this->folder_hash);
+
+ $y = q("update attach set display_path = '%s where hash = '%s' and uid = %d",
+ dbesc($x['path']),
+ dbesc($this->folder_hash),
+ intval($this->auth->owner_id)
+ );
+
$ch = channelx_by_n($this->auth->owner_id);
if ($ch) {
$sync = attach_export_data($ch, $this->folder_hash);
@@ -260,14 +268,18 @@ class Directory extends DAV\Node implements DAV\ICollection, DAV\IQuota {
dbesc($f),
dbesc(datetime_convert()),
dbesc(datetime_convert()),
- '', //TODO: use os_path
- '', //TODO: use display_path
+ '',
+ '',
dbesc($allow_cid),
dbesc($allow_gid),
dbesc($deny_cid),
dbesc($deny_gid)
);
+ // fetch the actual storage paths
+
+ $xpath = attach_syspaths($this->auth->owner_id, $hash);
+
// returns the number of bytes that were written to the file, or FALSE on failure
$size = file_put_contents($f, $data);
// delete attach entry if file_put_contents() failed
@@ -281,15 +293,17 @@ class Directory extends DAV\Node implements DAV\ICollection, DAV\IQuota {
$edited = datetime_convert();
$is_photo = 0;
- $x = @getimagesize($f);
- logger('getimagesize: ' . print_r($x,true), LOGGER_DATA);
- if (($x) && ($x[2] === IMAGETYPE_GIF || $x[2] === IMAGETYPE_JPEG || $x[2] === IMAGETYPE_PNG)) {
+ $gis = @getimagesize($f);
+ logger('getimagesize: ' . print_r($gis,true), LOGGER_DATA);
+ if (($gis) && ($gis[2] === IMAGETYPE_GIF || $gis[2] === IMAGETYPE_JPEG || $gis[2] === IMAGETYPE_PNG)) {
$is_photo = 1;
}
// updates entry with filesize and timestamp
- $d = q("UPDATE attach SET filesize = '%s', is_photo = %d, edited = '%s' WHERE hash = '%s' AND uid = %d",
+ $d = q("UPDATE attach SET filesize = '%s', os_path = '%s', display_path = '%s', is_photo = %d, edited = '%s' WHERE hash = '%s' AND uid = %d",
dbesc($size),
+ dbesc($xpath['os_path']),
+ dbesc($xpath['display_path']),
intval($is_photo),
dbesc($edited),
dbesc($hash),
@@ -312,29 +326,29 @@ class Directory extends DAV\Node implements DAV\ICollection, DAV\IQuota {
// check against service class quota
$limit = engr_units_to_bytes(service_class_fetch($c[0]['channel_id'], 'attach_upload_limit'));
if ($limit !== false) {
- $x = q("SELECT SUM(filesize) AS total FROM attach WHERE aid = %d ",
+ $z = q("SELECT SUM(filesize) AS total FROM attach WHERE aid = %d ",
intval($c[0]['channel_account_id'])
);
- if (($x) && ($x[0]['total'] + $size > $limit)) {
- logger('service class limit exceeded for ' . $c[0]['channel_name'] . ' total usage is ' . $x[0]['total'] . ' limit is ' . userReadableSize($limit));
+ if (($z) && ($z[0]['total'] + $size > $limit)) {
+ logger('service class limit exceeded for ' . $c[0]['channel_name'] . ' total usage is ' . $z[0]['total'] . ' limit is ' . userReadableSize($limit));
attach_delete($c[0]['channel_id'], $hash);
return;
}
}
- if ($is_photo) {
+ if($is_photo) {
$album = '';
if ($this->folder_hash) {
- $f1 = q("select filename from attach WHERE hash = '%s' AND uid = %d",
+ $f1 = q("select filename, display_path from attach WHERE hash = '%s' AND uid = %d",
dbesc($this->folder_hash),
intval($c[0]['channel_id'])
);
if ($f1)
- $album = $f1[0]['filename'];
+ $album = (($f1[0]['display_path']) ? $f1[0]['display_path'] : $f1[0]['filename']);
}
require_once('include/photos.php');
- $args = array( 'resource_id' => $hash, 'album' => $album, 'os_path' => $f, 'filename' => $name, 'getimagesize' => $x, 'directory' => $direct);
+ $args = array( 'resource_id' => $hash, 'album' => $album, 'os_syspath' => $f, 'os_path' => $xpath['os_path'], 'display_path' => $xpath['path'], 'filename' => $name, 'getimagesize' => $gis, 'directory' => $direct);
$p = photo_upload($c[0], \App::get_observer(), $args);
}
@@ -646,20 +660,24 @@ class Directory extends DAV\Node implements DAV\ICollection, DAV\IQuota {
logger("Path mismatch: $path !== /$file");
return NULL;
}
- if(ACTIVE_DBTYPE == DBTYPE_POSTGRES) {
- $prefix = 'DISTINCT ON (filename)';
- $suffix = 'ORDER BY filename';
- }
- else {
- $prefix = '';
- $suffix = 'GROUP BY filename';
- }
+
+ $prefix = '';
+ $suffix = '';
+
$r = q("select $prefix id, uid, hash, filename, filetype, filesize, revision, folder, flags, is_dir, created, edited from attach where folder = '%s' and uid = %d $perms $suffix",
dbesc($folder),
intval($channel_id)
);
foreach ($r as $rr) {
+
+ // @FIXME I don't think we use revisions currently in attach structures.
+ // In case we see any in the wild provide a unique filename. This
+ // name may or may not be accessible
+
+ if($rr['revision'])
+ $rr['filename'] .= '-' . $rr['revision'];
+
//logger('filename: ' . $rr['filename'], LOGGER_DEBUG);
if (intval($rr['is_dir'])) {
$ret[] = new Directory($path . '/' . $rr['filename'], $auth);
@@ -687,7 +705,7 @@ class Directory extends DAV\Node implements DAV\ICollection, DAV\IQuota {
$ret = array();
$r = q("SELECT channel_id, channel_address FROM channel WHERE channel_removed = 0
- AND channel_system = 0 AND NOT (channel_pageflags & %d)>0",
+ AND channel_system = 0 AND (channel_pageflags & %d) = 0",
intval(PAGE_HIDDEN)
);
diff --git a/Zotlabs/Storage/File.php b/Zotlabs/Storage/File.php
index d2bca3964..332bf6896 100644
--- a/Zotlabs/Storage/File.php
+++ b/Zotlabs/Storage/File.php
@@ -85,13 +85,23 @@ class File extends DAV\Node implements DAV\IFile {
intval($this->data['id'])
);
+ $x = attach_syspaths($this->auth->owner_id,$this->data['hash']);
+
+ $y = q("update attach set display_path = '%s where hash = '%s' and uid = %d",
+ dbesc($x['path']),
+ dbesc($this->data['hash']),
+ intval($this->auth->owner_id)
+ );
+
if($this->data->is_photo) {
- $r = q("update photo set filename = '%s' where resource_id = '%s' and uid = %d",
+ $r = q("update photo set filename = '%s', display_path = '%s' where resource_id = '%s' and uid = %d",
dbesc($newName),
+ dbesc($x['path']),
dbesc($this->data['hash']),
intval($this->auth->owner_id)
);
}
+
$ch = channelx_by_n($this->auth->owner_id);
if($ch) {
$sync = attach_export_data($ch,$this->data['hash']);
@@ -244,7 +254,7 @@ class File extends DAV\Node implements DAV\IFile {
// @todo this should be a global definition
$unsafe_types = array('text/html', 'text/css', 'application/javascript');
- if (in_array($r[0]['filetype'], $unsafe_types)) {
+ if (in_array($r[0]['filetype'], $unsafe_types) && (! channel_codeallowed($this->data['uid']))) {
header('Content-disposition: attachment; filename="' . $r[0]['filename'] . '"');
header('Content-type: text/plain');
}
@@ -255,7 +265,7 @@ class File extends DAV\Node implements DAV\IFile {
$f = 'store/' . $this->auth->owner_nick . '/' . (($this->os_path) ? $this->os_path . '/' : '') . $x;
else
$f = $x;
- return fopen($f, 'rb');
+ return @fopen($f, 'rb');
}
return dbunescbin($r[0]['content']);
}
@@ -290,7 +300,7 @@ class File extends DAV\Node implements DAV\IFile {
public function getContentType() {
// @todo this should be a global definition.
$unsafe_types = array('text/html', 'text/css', 'application/javascript');
- if (in_array($this->data['filetype'], $unsafe_types)) {
+ if (in_array($this->data['filetype'], $unsafe_types) && (! channel_codeallowed($this->data['uid']))) {
return 'text/plain';
}
return $this->data['filetype'];
diff --git a/Zotlabs/Web/CheckJS.php b/Zotlabs/Web/CheckJS.php
index 109790fa5..8179ceb15 100644
--- a/Zotlabs/Web/CheckJS.php
+++ b/Zotlabs/Web/CheckJS.php
@@ -21,9 +21,9 @@ class CheckJS {
$page = urlencode(\App::$query_string);
if($test) {
- self::$jsdisabled = 1;
+ $this->jsdisabled = 1;
if(array_key_exists('jsdisabled',$_COOKIE))
- self::$jsdisabled = $_COOKIE['jsdisabled'];
+ $this->jsdisabled = $_COOKIE['jsdisabled'];
if(! array_key_exists('jsdisabled',$_COOKIE)) {
\App::$page['htmlhead'] .= "\r\n" . '<script>document.cookie="jsdisabled=0; path=/"; var jsMatch = /\&jsdisabled=0/; if (!jsMatch.exec(location.href)) { location.href = "' . z_root() . '/nojs/0?f=&redir=' . $page . '" ; }</script>' . "\r\n";
@@ -41,7 +41,7 @@ class CheckJS {
}
function disabled() {
- return self::$jsdisabled;
+ return $this->jsdisabled;
}
diff --git a/Zotlabs/Web/HTTPHeaders.php b/Zotlabs/Web/HTTPHeaders.php
new file mode 100644
index 000000000..4be51a8f3
--- /dev/null
+++ b/Zotlabs/Web/HTTPHeaders.php
@@ -0,0 +1,60 @@
+<?php
+
+namespace Zotlabs\Web;
+
+class HTTPHeaders {
+
+ private $in_progress = [];
+ private $parsed = [];
+
+
+ function __construct($headers) {
+
+ $lines = explode("\n",str_replace("\r",'',$headers));
+ if($lines) {
+ foreach($lines as $line) {
+ if(preg_match('/^\s+/',$line,$matches) && trim($line)) {
+ if($this->in_progress['k']) {
+ $this->in_progress['v'] .= ' ' . ltrim($line);
+ continue;
+ }
+ }
+ else {
+ if($this->in_progress['k']) {
+ $this->parsed[] = [ $this->in_progress['k'] => $this->in_progress['v'] ];
+ $this->in_progress = [];
+ }
+
+ $this->in_progress['k'] = strtolower(substr($line,0,strpos($line,':')));
+ $this->in_progress['v'] = ltrim(substr($line,strpos($line,':') + 1));
+ }
+
+ }
+ if($this->in_progress['k']) {
+ $this->parsed[] = [ $this->in_progress['k'] => $this->in_progress['v'] ];
+ $this->in_progress = [];
+ }
+ }
+ }
+
+ function fetch() {
+ return $this->parsed;
+ }
+
+ function fetcharr() {
+ $ret = [];
+ if($this->parsed) {
+ foreach($this->parsed as $x) {
+ foreach($x as $y => $z) {
+ $ret[$y] = $z;
+ }
+ }
+ }
+ return $ret;
+ }
+
+
+}
+
+
+
diff --git a/Zotlabs/Web/HTTPSig.php b/Zotlabs/Web/HTTPSig.php
new file mode 100644
index 000000000..1c66b8cf4
--- /dev/null
+++ b/Zotlabs/Web/HTTPSig.php
@@ -0,0 +1,313 @@
+<?php
+
+namespace Zotlabs\Web;
+
+/**
+ * Implements HTTP Signatures per draft-cavage-http-signatures-07
+ */
+
+
+class HTTPSig {
+
+ // See RFC5843
+
+ static function generate_digest($body,$set = true) {
+ $digest = base64_encode(hash('sha256',$body,true));
+
+ if($set) {
+ header('Digest: SHA-256=' . $digest);
+ }
+ return $digest;
+ }
+
+ // See draft-cavage-http-signatures-08
+
+ static function verify($data,$key = '') {
+
+ $body = $data;
+ $headers = null;
+ $spoofable = false;
+
+ $result = [
+ 'signer' => '',
+ 'header_signed' => false,
+ 'header_valid' => false,
+ 'content_signed' => false,
+ 'content_valid' => false
+ ];
+
+ // decide if $data arrived via controller submission or curl
+ if(is_array($data) && $data['header']) {
+ if(! $data['success'])
+ return $result;
+ $h = new \Zotlabs\Web\HTTPHeaders($data['header']);
+ $headers = $h->fetcharr();
+ $body = $data['body'];
+ }
+
+ else {
+ $headers = [];
+ $headers['(request-target)'] =
+ strtolower($_SERVER['REQUEST_METHOD']) . ' ' .
+ $_SERVER['REQUEST_URI'];
+ foreach($_SERVER as $k => $v) {
+ if(strpos($k,'HTTP_') === 0) {
+ $field = str_replace('_','-',strtolower(substr($k,5)));
+ $headers[$field] = $v;
+ }
+ }
+ }
+
+ $sig_block = null;
+
+ if(array_key_exists('signature',$headers)) {
+ $sig_block = self::parse_sigheader($headers['signature']);
+ }
+ elseif(array_key_exists('authorization',$headers)) {
+ $sig_block = self::parse_sigheader($headers['authorization']);
+ }
+
+ if(! $sig_block) {
+ logger('no signature provided.');
+ return $result;
+ }
+
+ // Warning: This log statement includes binary data
+ // logger('sig_block: ' . print_r($sig_block,true), LOGGER_DATA);
+
+ $result['header_signed'] = true;
+
+ $signed_headers = $sig_block['headers'];
+ if(! $signed_headers)
+ $signed_headers = [ 'date' ];
+
+ $signed_data = '';
+ foreach($signed_headers as $h) {
+ if(array_key_exists($h,$headers)) {
+ $signed_data .= $h . ': ' . $headers[$h] . "\n";
+ }
+ if(strpos($h,'.')) {
+ $spoofable = true;
+ }
+ }
+ $signed_data = rtrim($signed_data,"\n");
+
+ $algorithm = null;
+ if($sig_block['algorithm'] === 'rsa-sha256') {
+ $algorithm = 'sha256';
+ }
+ if($sig_block['algorithm'] === 'rsa-sha512') {
+ $algorithm = 'sha512';
+ }
+
+ if($key && function_exists($key)) {
+ $result['signer'] = $sig_block['keyId'];
+ $key = $key($sig_block['keyId']);
+ }
+
+ if(! $key) {
+ $result['signer'] = $sig_block['keyId'];
+ $key = self::get_activitypub_key($sig_block['keyId']);
+ }
+
+ if(! $key)
+ return $result;
+
+ $x = rsa_verify($signed_data,$sig_block['signature'],$key,$algorithm);
+
+ logger('verified: ' . $x, LOGGER_DEBUG);
+
+ if($x === false)
+ return $result;
+
+ if(! $spoofable)
+ $result['header_valid'] = true;
+
+ if(in_array('digest',$signed_headers)) {
+ $result['content_signed'] = true;
+ $digest = explode('=', $headers['digest']);
+ if($digest[0] === 'SHA-256')
+ $hashalg = 'sha256';
+ if($digest[0] === 'SHA-512')
+ $hashalg = 'sha512';
+
+ // The explode operation will have stripped the '=' padding, so compare against unpadded base64
+ if(rtrim(base64_encode(hash($hashalg,$body,true)),'=') === $digest[1]) {
+ $result['content_valid'] = true;
+ }
+ }
+
+ logger('Content_Valid: ' . $result['content_valid']);
+
+ return $result;
+
+ }
+
+ function get_activitypub_key($id) {
+
+ if(strpos($id,'acct:') === 0) {
+ $x = q("select xchan_pubkey from xchan left join hubloc on xchan_hash = hubloc_hash where hubloc_addr = '%s' limit 1",
+ dbesc(str_replace('acct:','',$id))
+ );
+ }
+ else {
+ $x = q("select xchan_pubkey from xchan where xchan_hash = '%s' and xchan_network = 'activitypub' ",
+ dbesc($id)
+ );
+ }
+
+ if($x && $x[0]['xchan_pubkey']) {
+ return ($x[0]['xchan_pubkey']);
+ }
+ $r = as_fetch($id);
+
+ if($r) {
+ $j = json_decode($r,true);
+
+ if($j['id'] !== $id)
+ return false;
+ if(array_key_exists('publicKey',$j) && array_key_exists('publicKeyPem',$j['publicKey'])) {
+ return($j['publicKey']['publicKeyPem']);
+ }
+ }
+ return false;
+ }
+
+
+
+
+ static function create_sig($request,$head,$prvkey,$keyid = 'Key',$send_headers = false,$auth = false,$alg = 'sha256',
+ $crypt_key = null, $crypt_algo = 'aes256ctr') {
+
+ $return_headers = [];
+
+ if($alg === 'sha256') {
+ $algorithm = 'rsa-sha256';
+ }
+ if($alg === 'sha512') {
+ $algorithm = 'rsa-sha512';
+ }
+
+ $x = self::sign($request,$head,$prvkey,$alg);
+
+ $headerval = 'keyId="' . $keyid . '",algorithm="' . $algorithm
+ . '",headers="' . $x['headers'] . '",signature="' . $x['signature'] . '"';
+
+ if($crypt_key) {
+ $x = crypto_encapsulate($headerval,$crypt_key,$crypt_alg);
+ $headerval = 'iv="' . $x['iv'] . '",key="' . $x['key'] . '",alg="' . $x['alg'] . '",data="' . $x['data'];
+ }
+
+ if($auth) {
+ $sighead = 'Authorization: Signature ' . $headerval;
+ }
+ else {
+ $sighead = 'Signature: ' . $headerval;
+ }
+
+ if($head) {
+ foreach($head as $k => $v) {
+ if($send_headers) {
+ header($k . ': ' . $v);
+ }
+ else {
+ $return_headers[] = $k . ': ' . $v;
+ }
+ }
+ }
+ if($send_headers) {
+ header($sighead);
+ }
+ else {
+ $return_headers[] = $sighead;
+ }
+ return $return_headers;
+ }
+
+
+
+ static function sign($request,$head,$prvkey,$alg = 'sha256') {
+
+ $ret = [];
+
+ $headers = '';
+ $fields = '';
+ if($request) {
+ $headers = '(request-target)' . ': ' . trim($request) . "\n";
+ $fields = '(request-target)';
+ }
+
+ if(head) {
+ foreach($head as $k => $v) {
+ $headers .= strtolower($k) . ': ' . trim($v) . "\n";
+ if($fields)
+ $fields .= ' ';
+ $fields .= strtolower($k);
+ }
+ // strip the trailing linefeed
+ $headers = rtrim($headers,"\n");
+ }
+
+ $sig = base64_encode(rsa_sign($headers,$prvkey,$alg));
+
+ $ret['headers'] = $fields;
+ $ret['signature'] = $sig;
+
+ return $ret;
+ }
+
+ static function parse_sigheader($header) {
+
+ $ret = [];
+ $matches = [];
+
+ // if the header is encrypted, decrypt with (default) site private key and continue
+
+ if(preg_match('/iv="(.*?)"/ism',$header,$matches))
+ $header = self::decrypt_sigheader($header);
+
+ if(preg_match('/keyId="(.*?)"/ism',$header,$matches))
+ $ret['keyId'] = $matches[1];
+ if(preg_match('/algorithm="(.*?)"/ism',$header,$matches))
+ $ret['algorithm'] = $matches[1];
+ if(preg_match('/headers="(.*?)"/ism',$header,$matches))
+ $ret['headers'] = explode(' ', $matches[1]);
+ if(preg_match('/signature="(.*?)"/ism',$header,$matches))
+ $ret['signature'] = base64_decode(preg_replace('/\s+/','',$matches[1]));
+
+ if(($ret['signature']) && ($ret['algorithm']) && (! $ret['headers']))
+ $ret['headers'] = [ 'date' ];
+
+ return $ret;
+ }
+
+
+ static function decrypt_sigheader($header,$prvkey = null) {
+
+ $iv = $key = $alg = $data = null;
+
+ if(! $prvkey) {
+ $prvkey = get_config('system','prvkey');
+ }
+
+ $matches = [];
+
+ if(preg_match('/iv="(.*?)"/ism',$header,$matches))
+ $iv = $matches[1];
+ if(preg_match('/key="(.*?)"/ism',$header,$matches))
+ $key = $matches[1];
+ if(preg_match('/alg="(.*?)"/ism',$header,$matches))
+ $alg = $matches[1];
+ if(preg_match('/data="(.*?)"/ism',$header,$matches))
+ $data = $matches[1];
+
+ if($iv && $key && $alg && $data) {
+ return crypto_unencapsulate([ 'iv' => $iv, 'key' => $key, 'alg' => $alg, 'data' => $data ] , $prvkey);
+ }
+ return '';
+
+ }
+
+}
+
+
diff --git a/Zotlabs/Web/Router.php b/Zotlabs/Web/Router.php
index ba2e78b25..9486130cb 100644
--- a/Zotlabs/Web/Router.php
+++ b/Zotlabs/Web/Router.php
@@ -62,12 +62,6 @@ class Router {
}
}
- if((strpos($module,'admin') === 0) && (! is_site_admin())) {
- \App::$module_loaded = false;
- notice( t('Permission denied.') . EOL);
- goaway(z_root());
- }
-
/*
* If the site has a custom module to over-ride the standard module, use it.
* Otherwise, look for the standard program module
@@ -125,6 +119,18 @@ class Router {
if(! (\App::$module_loaded)) {
+ // undo the setting of a letsencrypt acme-challenge rewrite rule
+ // which blocks access to our .well-known routes.
+ // Also provide a config setting for sites that have a legitimate need
+ // for a custom .htaccess in the .well-known directory; but they should
+ // make the file read-only so letsencrypt doesn't modify it
+
+ if(strpos($_SERVER['REQUEST_URI'],'/.well-known/') === 0) {
+ if(file_exists('.well-known/.htaccess') && get_config('system','fix_apache_acme',true)) {
+ rename('.well-known/.htaccess','.well-known/.htaccess.old');
+ }
+ }
+
$x = [
'module' => $module,
'installed' => \App::$module_loaded,
@@ -172,6 +178,7 @@ class Router {
*/
if(\App::$module_loaded) {
+
\App::$page['page_title'] = \App::$module;
$placeholder = '';
@@ -208,7 +215,7 @@ class Router {
* The member may have also created a customised PDL that's stored in the config
*/
- load_pdl($a);
+ load_pdl();
/*
* load current theme info
diff --git a/Zotlabs/Web/WebServer.php b/Zotlabs/Web/WebServer.php
index 5bb0e08e8..9e6af8c4c 100644
--- a/Zotlabs/Web/WebServer.php
+++ b/Zotlabs/Web/WebServer.php
@@ -58,7 +58,11 @@ class WebServer {
if((x($_GET,'zid')) && (! \App::$install)) {
\App::$query_string = strip_zids(\App::$query_string);
if(! local_channel()) {
- $_SESSION['my_address'] = $_GET['zid'];
+ if ($_SESSION['my_address']!=$_GET['zid'])
+ {
+ $_SESSION['my_address'] = $_GET['zid'];
+ $_SESSION['authenticated'] = 0;
+ }
zid_init();
}
}
@@ -70,6 +74,12 @@ class WebServer {
}
}
+ if((x($_REQUEST,'owt')) && (! \App::$install)) {
+ $token = $_REQUEST['owt'];
+ \App::$query_string = strip_query_param(\App::$query_string,'owt');
+ owt_init($token);
+ }
+
if((x($_SESSION, 'authenticated')) || (x($_POST, 'auth-params')) || (\App::$module === 'login'))
require('include/auth.php');
@@ -79,11 +89,6 @@ class WebServer {
if(! x($_SESSION, 'sysmsg_info'))
$_SESSION['sysmsg_info'] = array();
- /*
- * check_config() is responsible for running update scripts. These automatically
- * update the DB schema whenever we push a new one out. It also checks to see if
- * any plugins have been added or removed and reacts accordingly.
- */
if(\App::$install) {
@@ -91,13 +96,49 @@ class WebServer {
if(\App::$module != 'view')
\App::$module = 'setup';
}
- else
- check_config($a);
+ else {
+
+ /*
+ * check_config() is responsible for running update scripts. These automatically
+ * update the DB schema whenever we push a new one out. It also checks to see if
+ * any plugins have been added or removed and reacts accordingly.
+ */
+
+ check_config();
+ }
- nav_set_selected('nothing');
+ //nav_set_selected('nothing');
$Router = new Router($a);
+ /* Initialise the Link: response header if this is a channel page.
+ * This cannot be done inside the channel module because some protocol
+ * addons over-ride the module functions and these links are common
+ * to all protocol drivers; thus doing it here avoids duplication.
+ */
+
+ if (( \App::$module === 'channel' ) && argc() > 1) {
+ \App::$channel_links = [
+ [
+ 'rel' => 'lrdd',
+ 'type' => 'application/xrd+xml',
+ 'url' => z_root() . '/xrd?f=&uri=acct%3A' . argv(1) . '%40' . \App::get_hostname()
+ ],
+ [
+ 'rel' => 'jrd',
+ 'type' => 'application/jrd+json',
+ 'url' => z_root() . '/.well-known/webfinger?f=&resource=acct%3A' . argv(1) . '%40' . \App::get_hostname()
+ ],
+ ];
+ $x = [ 'channel_address' => argv(1), 'channel_links' => \App::$channel_links ];
+ call_hooks('channel_links', $x );
+ \App::$channel_links = $x['channel_links'];
+ header('Link: ' . \App::get_channel_links());
+ }
+
+
+
+
/* initialise content region */
if(! x(\App::$page, 'content'))
@@ -130,8 +171,8 @@ class WebServer {
call_hooks('page_end', \App::$page['content']);
- construct_page($a);
+ construct_page();
killme();
}
-} \ No newline at end of file
+}
diff --git a/Zotlabs/Widget/Activity.php b/Zotlabs/Widget/Activity.php
new file mode 100644
index 000000000..04e9fc4b1
--- /dev/null
+++ b/Zotlabs/Widget/Activity.php
@@ -0,0 +1,61 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Activity {
+
+ function widget($arr) {
+
+ if(! local_channel())
+ return '';
+
+ $o = '';
+
+ if(is_array($arr) && array_key_exists('limit',$arr))
+ $limit = " limit " . intval($limit) . " ";
+ else
+ $limit = '';
+
+ $perms_sql = item_permissions_sql(local_channel()) . item_normal();
+
+ $r = q("select author_xchan from item where item_unseen = 1 and uid = %d $perms_sql",
+ intval(local_channel())
+ );
+
+ $contributors = [];
+ $arr = [];
+
+ if($r) {
+ foreach($r as $rv) {
+ if(array_key_exists($rv['author_xchan'],$contributors)) {
+ $contributors[$rv['author_xchan']] ++;
+ }
+ else {
+ $contributors[$rv['author_xchan']] = 1;
+ }
+ }
+ foreach($contributors as $k => $v) {
+ $arr[] = [ 'author_xchan' => $k, 'total' => $v ];
+ }
+ usort($arr,'total_sort');
+ xchan_query($arr);
+ }
+
+ $x = [ 'entries' => $arr ];
+ call_hooks('activity_widget',$x);
+ $arr = $x['entries'];
+
+ if($arr) {
+ $o .= '<div class="widget">';
+ $o .= '<h3>' . t('Activity','widget') . '</h3><ul class="nav nav-pills flex-column">';
+
+ foreach($arr as $rv) {
+ $o .= '<li class="nav-item"><a class="nav-link" href="network?f=&xchan=' . urlencode($rv['author_xchan']) . '" ><span class="badge badge-secondary float-right">' . ((intval($rv['total'])) ? intval($rv['total']) : '') . '</span><img src="' . $rv['author']['xchan_photo_s'] . '" class="menu-img-1" /> ' . $rv['author']['xchan_name'] . '</a></li>';
+ }
+ $o .= '</ul></div>';
+ }
+ return $o;
+ }
+
+}
+
diff --git a/Zotlabs/Widget/Admin.php b/Zotlabs/Widget/Admin.php
new file mode 100644
index 000000000..a761eebe3
--- /dev/null
+++ b/Zotlabs/Widget/Admin.php
@@ -0,0 +1,68 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Admin {
+
+ function widget($arr) {
+
+ /*
+ * Side bar links
+ */
+
+ if(! is_site_admin()) {
+ return '';
+ }
+
+ $o = '';
+
+ // array( url, name, extra css classes )
+
+ $aside = [
+ 'site' => array(z_root() . '/admin/site/', t('Site'), 'site'),
+ 'accounts' => array(z_root() . '/admin/accounts/', t('Accounts'), 'accounts', 'pending-update', t('Member registrations waiting for confirmation')),
+ 'channels' => array(z_root() . '/admin/channels/', t('Channels'), 'channels'),
+ 'security' => array(z_root() . '/admin/security/', t('Security'), 'security'),
+ 'features' => array(z_root() . '/admin/features/', t('Features'), 'features'),
+ 'plugins' => array(z_root() . '/admin/plugins/', t('Plugins'), 'plugins'),
+ 'themes' => array(z_root() . '/admin/themes/', t('Themes'), 'themes'),
+ 'queue' => array(z_root() . '/admin/queue', t('Inspect queue'), 'queue'),
+ 'profs' => array(z_root() . '/admin/profs', t('Profile Fields'), 'profs'),
+ 'dbsync' => array(z_root() . '/admin/dbsync/', t('DB updates'), 'dbsync')
+ ];
+
+ /* get plugins admin page */
+
+ $r = q("SELECT * FROM addon WHERE plugin_admin = 1");
+
+ $plugins = array();
+ if($r) {
+ foreach ($r as $h){
+ $plugin = $h['aname'];
+ $plugins[] = array(z_root() . '/admin/plugins/' . $plugin, $plugin, 'plugin');
+ // temp plugins with admin
+ \App::$plugins_admin[] = $plugin;
+ }
+ }
+
+ $logs = array(z_root() . '/admin/logs/', t('Logs'), 'logs');
+
+ $arr = array('links' => $aside,'plugins' => $plugins,'logs' => $logs);
+ call_hooks('admin_aside',$arr);
+
+ $o .= replace_macros(get_markup_template('admin_aside.tpl'), array(
+ '$admin' => $aside,
+ '$admtxt' => t('Admin'),
+ '$plugadmtxt' => t('Plugin Features'),
+ '$plugins' => $plugins,
+ '$logtxt' => t('Logs'),
+ '$logs' => $logs,
+ '$h_pending' => t('Member registrations waiting for confirmation'),
+ '$admurl'=> z_root() . '/admin/'
+ ));
+
+ return $o;
+
+ }
+}
+
diff --git a/Zotlabs/Widget/Affinity.php b/Zotlabs/Widget/Affinity.php
new file mode 100644
index 000000000..439ba1f33
--- /dev/null
+++ b/Zotlabs/Widget/Affinity.php
@@ -0,0 +1,60 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Affinity {
+
+ function widget($arr) {
+
+ if(! local_channel())
+ return '';
+
+ // Get default cmin value from pconfig, but allow GET parameter to override
+ $cmin = intval(get_pconfig(local_channel(),'affinity','cmin'));
+ $cmin = (($cmin) ? $cmin : 0);
+ $cmin = ((x($_REQUEST,'cmin')) ? intval($_REQUEST['cmin']) : $cmin);
+
+ // Get default cmax value from pconfig, but allow GET parameter to override
+ $cmax = intval(get_pconfig(local_channel(),'affinity','cmax'));
+ $cmax = (($cmax) ? $cmax : 99);
+ $cmax = ((x($_REQUEST,'cmax')) ? intval($_REQUEST['cmax']) : $cmax);
+
+
+ if(feature_enabled(local_channel(),'affinity')) {
+
+ $labels = array(
+ t('Me'),
+ t('Family'),
+ t('Friends'),
+ t('Acquaintances'),
+ t('All')
+ );
+ call_hooks('affinity_labels',$labels);
+ $label_str = '';
+
+ if($labels) {
+ foreach($labels as $l) {
+ if($label_str) {
+ $label_str .= ", '|'";
+ $label_str .= ", '" . $l . "'";
+ }
+ else
+ $label_str .= "'" . $l . "'";
+ }
+ }
+
+ $tpl = get_markup_template('main_slider.tpl');
+ $x = replace_macros($tpl,array(
+ '$val' => $cmin . ',' . $cmax,
+ '$refresh' => t('Refresh'),
+ '$labels' => $label_str,
+ ));
+
+ $arr = array('html' => $x);
+ call_hooks('main_slider',$arr);
+ return $arr['html'];
+ }
+ return '';
+ }
+}
+ \ No newline at end of file
diff --git a/Zotlabs/Widget/Album.php b/Zotlabs/Widget/Album.php
new file mode 100644
index 000000000..f359e6d0f
--- /dev/null
+++ b/Zotlabs/Widget/Album.php
@@ -0,0 +1,106 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+require_once('include/attach.php');
+
+class Album {
+
+ function widget($args) {
+
+
+ $owner_uid = \App::$profile_uid;
+ $sql_extra = permissions_sql($owner_uid);
+
+
+ if(! perm_is_allowed($owner_uid,get_observer_hash(),'view_storage'))
+ return '';
+
+ if($args['album'])
+ $album = $args['album'];
+ if($args['title'])
+ $title = $args['title'];
+
+ /**
+ * This may return incorrect permissions if you have multiple directories of the same name.
+ * It is a limitation of the photo table using a name for a photo album instead of a folder hash
+ */
+
+ if($album) {
+ $x = q("select hash from attach where filename = '%s' and uid = %d limit 1",
+ dbesc($album),
+ intval($owner_uid)
+ );
+ if($x) {
+ $y = attach_can_view_folder($owner_uid,get_observer_hash(),$x[0]['hash']);
+ if(! $y)
+ return '';
+ }
+ }
+
+ $order = 'DESC';
+
+ $r = q("SELECT p.resource_id, p.id, p.filename, p.mimetype, p.imgscale, p.description, p.created FROM photo p INNER JOIN
+ (SELECT resource_id, max(imgscale) imgscale FROM photo WHERE uid = %d AND album = '%s' AND imgscale <= 4 AND photo_usage IN ( %d, %d ) $sql_extra GROUP BY resource_id) ph
+ ON (p.resource_id = ph.resource_id AND p.imgscale = ph.imgscale)
+ ORDER BY created $order ",
+ intval($owner_uid),
+ dbesc($album),
+ intval(PHOTO_NORMAL),
+ intval(PHOTO_PROFILE)
+ );
+
+ //edit album name
+ $album_edit = null;
+
+ $photos = array();
+ if($r) {
+ $twist = 'rotright';
+ foreach($r as $rr) {
+
+ if($twist == 'rotright')
+ $twist = 'rotleft';
+ else
+ $twist = 'rotright';
+
+ $ext = $phototypes[$rr['mimetype']];
+
+ $imgalt_e = $rr['filename'];
+ $desc_e = $rr['description'];
+
+ $imagelink = (z_root() . '/photos/' . \App::$profile['channel_address'] . '/image/' . $rr['resource_id']);
+
+
+ $photos[] = array(
+ 'id' => $rr['id'],
+ 'twist' => ' ' . $twist . rand(2,4),
+ 'link' => $imagelink,
+ 'title' => t('View Photo'),
+ 'src' => z_root() . '/photo/' . $rr['resource_id'] . '-' . $rr['imgscale'] . '.' .$ext,
+ 'alt' => $imgalt_e,
+ 'desc'=> $desc_e,
+ 'ext' => $ext,
+ 'hash'=> $rr['resource_id'],
+ 'unknown' => t('Unknown')
+ );
+ }
+ }
+
+
+ $tpl = get_markup_template('photo_album.tpl');
+ $o .= replace_macros($tpl, array(
+ '$photos' => $photos,
+ '$album' => (($title) ? $title : $album),
+ '$album_id' => rand(),
+ '$album_edit' => array(t('Edit Album'), $album_edit),
+ '$can_post' => false,
+ '$upload' => array(t('Upload'), z_root() . '/photos/' . \App::$profile['channel_address'] . '/upload/' . bin2hex($album)),
+ '$order' => false,
+ '$upload_form' => $upload_form,
+ '$usage' => $usage_message
+ ));
+
+ return $o;
+ }
+}
+
diff --git a/Zotlabs/Widget/Appcategories.php b/Zotlabs/Widget/Appcategories.php
new file mode 100644
index 000000000..490ec1abc
--- /dev/null
+++ b/Zotlabs/Widget/Appcategories.php
@@ -0,0 +1,49 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Appcategories {
+
+ function widget($arr) {
+
+ if(! local_channel())
+ return '';
+
+ $selected = ((x($_REQUEST,'cat')) ? htmlspecialchars($_REQUEST['cat'],ENT_COMPAT,'UTF-8') : '');
+
+ // @FIXME ??? $srchurl undefined here - commented out until is reviewed
+ //$srchurl = rtrim(preg_replace('/cat\=[^\&].*?(\&|$)/is','',$srchurl),'&');
+ //$srchurl = str_replace(array('?f=','&f='),array('',''),$srchurl);
+
+ // Leaving this line which negates the effect of the two invalid lines prior
+ $srchurl = z_root() . '/apps';
+
+ $terms = array();
+
+ $r = q("select distinct(term.term)
+ from term join app on term.oid = app.id
+ where app_channel = %d
+ and term.uid = app_channel
+ and term.otype = %d
+ and term.term != 'nav_featured_app'
+ order by term.term asc",
+ intval(local_channel()),
+ intval(TERM_OBJ_APP)
+ );
+
+ if($r) {
+ foreach($r as $rr)
+ $terms[] = array('name' => $rr['term'], 'selected' => (($selected == $rr['term']) ? 'selected' : ''));
+
+ return replace_macros(get_markup_template('categories_widget.tpl'),array(
+ '$title' => t('Categories'),
+ '$desc' => '',
+ '$sel_all' => (($selected == '') ? 'selected' : ''),
+ '$all' => t('Everything'),
+ '$terms' => $terms,
+ '$base' => $srchurl,
+
+ ));
+ }
+ }
+}
diff --git a/Zotlabs/Widget/Appcloud.php b/Zotlabs/Widget/Appcloud.php
new file mode 100644
index 000000000..2a4671eee
--- /dev/null
+++ b/Zotlabs/Widget/Appcloud.php
@@ -0,0 +1,13 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Appcloud {
+
+ function widget($arr) {
+ if(! local_channel())
+ return '';
+ return app_tagblock(z_root() . '/apps');
+ }
+}
+
diff --git a/Zotlabs/Widget/Archive.php b/Zotlabs/Widget/Archive.php
new file mode 100644
index 000000000..c151ca563
--- /dev/null
+++ b/Zotlabs/Widget/Archive.php
@@ -0,0 +1,55 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+
+class Archive {
+
+ function widget($arr) {
+
+ $o = '';
+
+ if(! \App::$profile_uid) {
+ return '';
+ }
+
+ $uid = \App::$profile_uid;
+
+ if(! feature_enabled($uid,'archives'))
+ return '';
+
+ if(! perm_is_allowed($uid,get_observer_hash(),'view_stream'))
+ return '';
+
+ $wall = ((array_key_exists('wall', $arr)) ? intval($arr['wall']) : 0);
+ $style = ((array_key_exists('style', $arr)) ? $arr['style'] : 'select');
+ $showend = ((get_pconfig($uid,'system','archive_show_end_date')) ? true : false);
+ $mindate = get_pconfig($uid,'system','archive_mindate');
+ $visible_years = get_pconfig($uid,'system','archive_visible_years');
+ if(! $visible_years)
+ $visible_years = 5;
+
+ $url = z_root() . '/' . \App::$cmd;
+
+ $ret = list_post_dates($uid,$wall,$mindate);
+
+ if(! count($ret))
+ return '';
+
+ $cutoff_year = intval(datetime_convert('',date_default_timezone_get(),'now','Y')) - $visible_years;
+ $cutoff = ((array_key_exists($cutoff_year,$ret))? true : false);
+
+ $o = replace_macros(get_markup_template('posted_date_widget.tpl'),array(
+ '$title' => t('Archives'),
+ '$size' => $visible_years,
+ '$cutoff_year' => $cutoff_year,
+ '$cutoff' => $cutoff,
+ '$url' => $url,
+ '$style' => $style,
+ '$showend' => $showend,
+ '$dates' => $ret
+ ));
+ return $o;
+ }
+}
+
diff --git a/Zotlabs/Widget/Bookmarkedchats.php b/Zotlabs/Widget/Bookmarkedchats.php
new file mode 100644
index 000000000..d64bbdb4b
--- /dev/null
+++ b/Zotlabs/Widget/Bookmarkedchats.php
@@ -0,0 +1,28 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Bookmarkedchats {
+
+ function widget($arr) {
+
+ if(! feature_enabled(\App::$profile['profile_uid'],'ajaxchat'))
+ return '';
+
+ $h = get_observer_hash();
+ if(! $h)
+ return;
+ $r = q("select xchat_url, xchat_desc from xchat where xchat_xchan = '%s' order by xchat_desc",
+ dbesc($h)
+ );
+ if($r) {
+ for($x = 0; $x < count($r); $x ++) {
+ $r[$x]['xchat_url'] = zid($r[$x]['xchat_url']);
+ }
+ }
+ return replace_macros(get_markup_template('bookmarkedchats.tpl'),array(
+ '$header' => t('Bookmarked Chatrooms'),
+ '$rooms' => $r
+ ));
+ }
+}
diff --git a/Zotlabs/Widget/Catcloud_wall.php b/Zotlabs/Widget/Catcloud_wall.php
new file mode 100644
index 000000000..3795987cc
--- /dev/null
+++ b/Zotlabs/Widget/Catcloud_wall.php
@@ -0,0 +1,19 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Catcloud_wall {
+
+ function widget($arr) {
+
+ if((! \App::$profile['profile_uid']) || (! \App::$profile['channel_hash']))
+ return '';
+ if(! perm_is_allowed(\App::$profile['profile_uid'], get_observer_hash(), 'view_stream'))
+ return '';
+
+ $limit = ((array_key_exists('limit',$arr)) ? intval($arr['limit']) : 50);
+
+ return catblock(\App::$profile['profile_uid'], $limit, '', \App::$profile['channel_hash'], 'wall');
+ }
+
+}
diff --git a/Zotlabs/Widget/Categories.php b/Zotlabs/Widget/Categories.php
new file mode 100644
index 000000000..305869706
--- /dev/null
+++ b/Zotlabs/Widget/Categories.php
@@ -0,0 +1,32 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+require_once('include/contact_widgets.php');
+
+class Categories {
+
+ function widget($arr) {
+
+ $cards = ((array_key_exists('cards',$arr) && $arr['cards']) ? true : false);
+
+ if(($cards) && (! feature_enabled(\App::$profile['profile_uid'],'cards')))
+ return '';
+
+ if((! \App::$profile['profile_uid'])
+ || (! perm_is_allowed(\App::$profile['profile_uid'],get_observer_hash(),(($cards) ? 'view_pages' : 'view_stream')))) {
+ return '';
+ }
+
+ $cat = ((x($_REQUEST,'cat')) ? htmlspecialchars($_REQUEST['cat'],ENT_COMPAT,'UTF-8') : '');
+ $srchurl = (($cards) ? \App::$argv[0] . '/' . \App::$argv[1] : \App::$query_string);
+ $srchurl = rtrim(preg_replace('/cat\=[^\&].*?(\&|$)/is','',$srchurl),'&');
+ $srchurl = str_replace(array('?f=','&f='),array('',''),$srchurl);
+
+ if($cards)
+ return cardcategories_widget($srchurl, $cat);
+ else
+ return categories_widget($srchurl, $cat);
+
+ }
+}
diff --git a/Zotlabs/Widget/Cdav.php b/Zotlabs/Widget/Cdav.php
new file mode 100644
index 000000000..60a860f93
--- /dev/null
+++ b/Zotlabs/Widget/Cdav.php
@@ -0,0 +1,176 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+
+
+class Cdav {
+
+ function widget() {
+ if(!local_channel())
+ return;
+
+ $channel = \App::get_channel();
+ $principalUri = 'principals/' . $channel['channel_address'];
+
+ if(!cdav_principal($principalUri))
+ return;
+
+ $pdo = \DBA::$dba->db;
+
+ require_once 'vendor/autoload.php';
+
+ $o = '';
+
+ if(argc() == 2 && argv(1) === 'calendar') {
+
+ $caldavBackend = new \Sabre\CalDAV\Backend\PDO($pdo);
+
+ $sabrecals = $caldavBackend->getCalendarsForUser($principalUri);
+
+ //TODO: we should probably also check for permission to send stream here
+ $local_channels = q("SELECT * FROM channel LEFT JOIN abook ON abook_xchan = channel_hash WHERE channel_system = 0 AND channel_removed = 0 AND channel_hash != '%s' AND abook_channel = %d",
+ dbesc($channel['channel_hash']),
+ intval($channel['channel_id'])
+ );
+
+ $sharee_options .= '<option value="">' . t('Select Channel') . '</option>' . "\r\n";
+ foreach($local_channels as $local_channel) {
+ $sharee_options .= '<option value="' . $local_channel['channel_hash'] . '">' . $local_channel['channel_name'] . '</option>' . "\r\n";
+ }
+
+ $access_options = '<option value="3">' . t('Read-write') . '</option>' . "\r\n";
+ $access_options .= '<option value="2">' . t('Read-only') . '</option>' . "\r\n";
+
+ //list calendars
+ foreach($sabrecals as $sabrecal) {
+ if($sabrecal['share-access'] == 1)
+ $access = '';
+ if($sabrecal['share-access'] == 2)
+ $access = 'read';
+ if($sabrecal['share-access'] == 3)
+ $access = 'read-write';
+
+ $invites = $caldavBackend->getInvites($sabrecal['id']);
+
+ $json_source = '/cdav/calendar/json/' . $sabrecal['id'][0] . '/' . $sabrecal['id'][1];
+
+ $switch = get_pconfig(local_channel(), 'cdav_calendar', $sabrecal['id'][0]);
+
+ $color = (($sabrecal['{http://apple.com/ns/ical/}calendar-color']) ? $sabrecal['{http://apple.com/ns/ical/}calendar-color'] : '#3a87ad');
+
+ $editable = (($sabrecal['share-access'] == 2) ? 'false' : 'true'); // false/true must be string since we're passing it to javascript
+
+ $sharees = [];
+ $share_displayname = [];
+ foreach($invites as $invite) {
+ if(strpos($invite->href, 'mailto:') !== false) {
+ $sharee = channelx_by_hash(substr($invite->href, 7));
+ $sharees[] = [
+ 'name' => $sharee['channel_name'],
+ 'access' => (($invite->access == 3) ? ' (RW)' : ' (R)'),
+ 'hash' => $sharee['channel_hash']
+ ];
+ }
+ }
+
+ if(!$access) {
+ $my_calendars[] = [
+ 'ownernick' => $channel['channel_address'],
+ 'uri' => $sabrecal['uri'],
+ 'displayname' => $sabrecal['{DAV:}displayname'],
+ 'calendarid' => $sabrecal['id'][0],
+ 'instanceid' => $sabrecal['id'][1],
+ 'json_source' => $json_source,
+ 'color' => $color,
+ 'editable' => $editable,
+ 'switch' => $switch,
+ 'sharees' => $sharees
+ ];
+ }
+ else {
+ $shared_calendars[] = [
+ 'ownernick' => $channel['channel_address'],
+ 'uri' => $sabrecal['uri'],
+ 'displayname' => $sabrecal['{DAV:}displayname'],
+ 'calendarid' => $sabrecal['id'][0],
+ 'instanceid' => $sabrecal['id'][1],
+ 'json_source' => $json_source,
+ 'color' => $color,
+ 'editable' => $editable,
+ 'switch' => $switch,
+ 'sharer' => $sabrecal['{urn:ietf:params:xml:ns:caldav}calendar-description'],
+ 'access' => $access
+ ];
+ }
+
+ if(!$access || $access === 'read-write') {
+ $writable_calendars[] = [
+ 'displayname' => ((!$access) ? $sabrecal['{DAV:}displayname'] : $share_displayname[0]),
+ 'id' => $sabrecal['id']
+ ];
+ }
+ }
+
+ $o .= replace_macros(get_markup_template('cdav_widget_calendar.tpl'), [
+ '$my_calendars_label' => t('My Calendars'),
+ '$my_calendars' => $my_calendars,
+ '$shared_calendars_label' => t('Shared Calendars'),
+ '$shared_calendars' => $shared_calendars,
+ '$sharee_options' => $sharee_options,
+ '$access_options' => $access_options,
+ '$share_label' => t('Share this calendar'),
+ '$share' => t('Share'),
+ '$edit_label' => t('Calendar name and color'),
+ '$edit' => t('Edit'),
+ '$create_label' => t('Create new calendar'),
+ '$create' => t('Create'),
+ '$create_placeholder' => t('Calendar Name'),
+ '$tools_label' => t('Calendar Tools'),
+ '$import_label' => t('Import calendar'),
+ '$import_placeholder' => t('Select a calendar to import to'),
+ '$upload' => t('Upload'),
+ '$writable_calendars' => $writable_calendars
+ ]);
+
+ return $o;
+
+ }
+
+ if(argc() >= 2 && argv(1) === 'addressbook') {
+
+ $carddavBackend = new \Sabre\CardDAV\Backend\PDO($pdo);
+
+ $sabreabooks = $carddavBackend->getAddressBooksForUser($principalUri);
+
+ //list addressbooks
+ foreach($sabreabooks as $sabreabook) {
+ $addressbooks[] = [
+ 'ownernick' => $channel['channel_address'],
+ 'uri' => $sabreabook['uri'],
+ 'displayname' => $sabreabook['{DAV:}displayname'],
+ 'id' => $sabreabook['id']
+
+ ];
+ }
+
+ $o .= replace_macros(get_markup_template('cdav_widget_addressbook.tpl'), [
+ '$addressbooks_label' => t('Addressbooks'),
+ '$addressbooks' => $addressbooks,
+ '$edit_label' => t('Addressbook name'),
+ '$edit' => t('Edit'),
+ '$create_label' => t('Create new addressbook'),
+ '$create_placeholder' => t('Addressbook Name'),
+ '$create' => t('Create'),
+ '$tools_label' => t('Addressbook Tools'),
+ '$import_label' => t('Import addressbook'),
+ '$import_placeholder' => t('Select an addressbook to import to'),
+ '$upload' => t('Upload')
+ ]);
+
+ return $o;
+
+ }
+
+ }
+} \ No newline at end of file
diff --git a/Zotlabs/Widget/Chatroom_list.php b/Zotlabs/Widget/Chatroom_list.php
new file mode 100644
index 000000000..e2aad0e05
--- /dev/null
+++ b/Zotlabs/Widget/Chatroom_list.php
@@ -0,0 +1,24 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Chatroom_list {
+
+ function widget($arr) {
+
+ if(! \App::$profile)
+ return '';
+
+ $r = \Zotlabs\Lib\Chatroom::roomlist(\App::$profile['profile_uid']);
+
+ if($r) {
+ return replace_macros(get_markup_template('chatroomlist.tpl'), array(
+ '$header' => t('Chatrooms'),
+ '$baseurl' => z_root(),
+ '$nickname' => \App::$profile['channel_address'],
+ '$items' => $r,
+ '$overview' => t('Overview')
+ ));
+ }
+ }
+}
diff --git a/Zotlabs/Widget/Chatroom_members.php b/Zotlabs/Widget/Chatroom_members.php
new file mode 100644
index 000000000..8ed77fb3c
--- /dev/null
+++ b/Zotlabs/Widget/Chatroom_members.php
@@ -0,0 +1,15 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Chatroom_members {
+
+ // The actual contents are filled in via AJAX
+
+ function widget() {
+ return replace_macros(get_markup_template('chatroom_members.tpl'), array(
+ '$header' => t('Chat Members')
+ ));
+ }
+
+}
diff --git a/Zotlabs/Widget/Clock.php b/Zotlabs/Widget/Clock.php
new file mode 100644
index 000000000..b63b5f748
--- /dev/null
+++ b/Zotlabs/Widget/Clock.php
@@ -0,0 +1,63 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Clock {
+
+ function widget($arr) {
+
+ $miltime = 0;
+ if(isset($arr['military']) && $arr['military'])
+ $miltime = 1;
+
+ $o = <<< EOT
+<div class="widget">
+<h3 class="clockface"></h3>
+<script>
+
+var timerID = null
+var timerRunning = false
+
+function stopclock(){
+ if(timerRunning)
+ clearTimeout(timerID)
+ timerRunning = false
+}
+
+function startclock(){
+ stopclock()
+ showtime()
+}
+
+function showtime(){
+ var now = new Date()
+ var hours = now.getHours()
+ var minutes = now.getMinutes()
+ var seconds = now.getSeconds()
+ var military = $miltime
+ var timeValue = ""
+ if(military)
+ timeValue = hours
+ else
+ timeValue = ((hours > 12) ? hours - 12 : hours)
+ timeValue += ((minutes < 10) ? ":0" : ":") + minutes
+// timeValue += ((seconds < 10) ? ":0" : ":") + seconds
+ if(! military)
+ timeValue += (hours >= 12) ? " P.M." : " A.M."
+ $('.clockface').html(timeValue)
+ timerID = setTimeout("showtime()",1000)
+ timerRunning = true
+}
+
+$(document).ready(function() {
+ startclock();
+});
+
+</script>
+</div>
+EOT;
+
+ return $o;
+ }
+}
+
diff --git a/Zotlabs/Widget/Collections.php b/Zotlabs/Widget/Collections.php
new file mode 100644
index 000000000..d2b29679a
--- /dev/null
+++ b/Zotlabs/Widget/Collections.php
@@ -0,0 +1,51 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+require_once('include/group.php');
+
+class Collections {
+
+ function widget($args) {
+
+ $mode = ((array_key_exists('mode',$args)) ? $args['mode'] : 'conversation');
+ switch($mode) {
+ case 'conversation':
+ $every = argv(0);
+ $each = argv(0);
+ $edit = true;
+ $current = $_REQUEST['gid'];
+ $abook_id = 0;
+ $wmode = 0;
+ break;
+ case 'connections':
+ $every = 'connections';
+ $each = 'group';
+ $edit = true;
+ $current = $_REQUEST['gid'];
+ $abook_id = 0;
+ $wmode = 0;
+ case 'groups':
+ $every = 'connections';
+ $each = argv(0);
+ $edit = false;
+ $current = intval(argv(1));
+ $abook_id = 0;
+ $wmode = 1;
+ break;
+ case 'abook':
+ $every = 'connections';
+ $each = 'group';
+ $edit = false;
+ $current = 0;
+ $abook_id = \App::$poi['abook_xchan'];
+ $wmode = 1;
+ break;
+ default:
+ return '';
+ break;
+ }
+
+ return group_side($every, $each, $edit, $current, $abook_id, $wmode);
+ }
+}
diff --git a/Zotlabs/Widget/Common_friends.php b/Zotlabs/Widget/Common_friends.php
new file mode 100644
index 000000000..a67b9312c
--- /dev/null
+++ b/Zotlabs/Widget/Common_friends.php
@@ -0,0 +1,19 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+require_once('include/contact_widgets.php');
+
+class Common_friends {
+
+ function widget($arr) {
+
+ if((! \App::$profile['profile_uid'])
+ || (! perm_is_allowed(\App::$profile['profile_uid'],get_observer_hash(),'view_contacts'))) {
+ return '';
+ }
+
+ return common_friends_visitor_widget(\App::$profile['profile_uid']);
+
+ }
+}
diff --git a/Zotlabs/Widget/Conversations.php b/Zotlabs/Widget/Conversations.php
new file mode 100644
index 000000000..56510750f
--- /dev/null
+++ b/Zotlabs/Widget/Conversations.php
@@ -0,0 +1,74 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Conversations {
+
+ function widget($arr) {
+
+ if (! local_channel())
+ return;
+
+ if(argc() > 1) {
+
+ switch(argv(1)) {
+ case 'inbox':
+ $mailbox = 'inbox';
+ $header = t('Received Messages');
+ break;
+ case 'outbox':
+ $mailbox = 'outbox';
+ $header = t('Sent Messages');
+ break;
+ default:
+ $mailbox = 'combined';
+ $header = t('Conversations');
+ break;
+ }
+
+ require_once('include/message.php');
+
+ // private_messages_list() can do other more complicated stuff, for now keep it simple
+ $r = private_messages_list(local_channel(), $mailbox, \App::$pager['start'], \App::$pager['itemspage']);
+
+ if(! $r) {
+ info( t('No messages.') . EOL);
+ return $o;
+ }
+
+ $messages = array();
+
+ foreach($r as $rr) {
+
+ $selected = ((argc() == 3) ? intval(argv(2)) == intval($rr['id']) : $r[0]['id'] == $rr['id']);
+
+ $messages[] = array(
+ 'mailbox' => $mailbox,
+ 'id' => $rr['id'],
+ 'from_name' => $rr['from']['xchan_name'],
+ 'from_url' => chanlink_hash($rr['from_xchan']),
+ 'from_photo' => $rr['from']['xchan_photo_s'],
+ 'to_name' => $rr['to']['xchan_name'],
+ 'to_url' => chanlink_hash($rr['to_xchan']),
+ 'to_photo' => $rr['to']['xchan_photo_s'],
+ 'subject' => (($rr['seen']) ? $rr['title'] : '<strong>' . $rr['title'] . '</strong>'),
+ 'delete' => t('Delete conversation'),
+ 'body' => $rr['body'],
+ 'date' => datetime_convert('UTC',date_default_timezone_get(),$rr['created'], 'c'),
+ 'seen' => $rr['seen'],
+ 'selected' => ((argv(1) != 'new') ? $selected : '')
+ );
+ }
+
+ $tpl = get_markup_template('mail_head.tpl');
+ $o .= replace_macros($tpl, array(
+ '$header' => $header,
+ '$messages' => $messages
+ ));
+
+ }
+ return $o;
+ }
+
+}
+
diff --git a/Zotlabs/Widget/Cover_photo.php b/Zotlabs/Widget/Cover_photo.php
new file mode 100644
index 000000000..d2eb1be92
--- /dev/null
+++ b/Zotlabs/Widget/Cover_photo.php
@@ -0,0 +1,59 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Cover_photo {
+
+ function widget($arr) {
+
+ require_once('include/channel.php');
+ $o = '';
+
+ if(\App::$module == 'channel' && $_REQUEST['mid'])
+ return '';
+
+ $channel_id = 0;
+ if(array_key_exists('channel_id', $arr) && intval($arr['channel_id']))
+ $channel_id = intval($arr['channel_id']);
+ if(! $channel_id)
+ $channel_id = \App::$profile_uid;
+ if(! $channel_id)
+ return '';
+
+ $channel = channelx_by_n($channel_id);
+
+ if(array_key_exists('style', $arr) && isset($arr['style']))
+ $style = $arr['style'];
+ else
+ $style = 'width:100%; height: auto;';
+
+ // ensure they can't sneak in an eval(js) function
+
+ if(strpbrk($style,'(\'"<>') !== false)
+ $style = '';
+
+ if(array_key_exists('title', $arr) && isset($arr['title']))
+ $title = $arr['title'];
+ else
+ $title = $channel['channel_name'];
+
+ if(array_key_exists('subtitle', $arr) && isset($arr['subtitle']))
+ $subtitle = $arr['subtitle'];
+ else
+ $subtitle = str_replace('@','&#x40;',$channel['xchan_addr']);
+
+ $c = get_cover_photo($channel_id,'html');
+
+ if($c) {
+ $photo_html = (($style) ? str_replace('alt=',' style="' . $style . '" alt=',$c) : $c);
+
+ $o = replace_macros(get_markup_template('cover_photo_widget.tpl'),array(
+ '$photo_html' => $photo_html,
+ '$title' => $title,
+ '$subtitle' => $subtitle,
+ '$hovertitle' => t('Click to show more'),
+ ));
+ }
+ return $o;
+ }
+}
diff --git a/Zotlabs/Widget/Design_tools.php b/Zotlabs/Widget/Design_tools.php
new file mode 100644
index 000000000..8ab6a235d
--- /dev/null
+++ b/Zotlabs/Widget/Design_tools.php
@@ -0,0 +1,21 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Design_tools {
+
+ function widget($arr) {
+
+ // mod menu doesn't load a profile. For any modules which load a profile, check it.
+ // otherwise local_channel() is sufficient for permissions.
+
+ if(\App::$profile['profile_uid'])
+ if((\App::$profile['profile_uid'] != local_channel()) && (! \App::$is_sys))
+ return '';
+
+ if(! local_channel())
+ return '';
+
+ return design_tools();
+ }
+} \ No newline at end of file
diff --git a/Zotlabs/Widget/Dirsort.php b/Zotlabs/Widget/Dirsort.php
new file mode 100644
index 000000000..e75a00e50
--- /dev/null
+++ b/Zotlabs/Widget/Dirsort.php
@@ -0,0 +1,11 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+require_once('include/dir_fns.php');
+
+class Dirsort {
+ function widget($arr) {
+ return dir_sort_links();
+ }
+}
diff --git a/Zotlabs/Widget/Dirtags.php b/Zotlabs/Widget/Dirtags.php
new file mode 100644
index 000000000..f211d5942
--- /dev/null
+++ b/Zotlabs/Widget/Dirtags.php
@@ -0,0 +1,13 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+require_once('include/dir_fns.php');
+
+class Dirtags {
+
+ function widget($arr) {
+ return dir_tagblock(z_root() . '/directory', null);
+ }
+
+}
diff --git a/Zotlabs/Widget/Eventstools.php b/Zotlabs/Widget/Eventstools.php
new file mode 100644
index 000000000..7efd3f72e
--- /dev/null
+++ b/Zotlabs/Widget/Eventstools.php
@@ -0,0 +1,19 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Eventstools {
+
+ function widget($arr) {
+
+ if(! local_channel())
+ return;
+
+ return replace_macros(get_markup_template('events_tools_side.tpl'), array(
+ '$title' => t('Events Tools'),
+ '$export' => t('Export Calendar'),
+ '$import' => t('Import Calendar'),
+ '$submit' => t('Submit')
+ ));
+ }
+}
diff --git a/Zotlabs/Widget/Filer.php b/Zotlabs/Widget/Filer.php
new file mode 100644
index 000000000..5d6f96a87
--- /dev/null
+++ b/Zotlabs/Widget/Filer.php
@@ -0,0 +1,36 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+require_once('include/contact_widgets.php');
+
+class Filer {
+
+ function widget($arr) {
+ if(! local_channel())
+ return '';
+
+
+ $selected = ((x($_REQUEST,'file')) ? $_REQUEST['file'] : '');
+
+ $terms = array();
+ $r = q("select distinct term from term where uid = %d and ttype = %d order by term asc",
+ intval(local_channel()),
+ intval(TERM_FILE)
+ );
+ if(! $r)
+ return;
+
+ foreach($r as $rr)
+ $terms[] = array('name' => $rr['term'], 'selected' => (($selected == $rr['term']) ? 'selected' : ''));
+
+ return replace_macros(get_markup_template('fileas_widget.tpl'),array(
+ '$title' => t('Saved Folders'),
+ '$desc' => '',
+ '$sel_all' => (($selected == '') ? 'selected' : ''),
+ '$all' => t('Everything'),
+ '$terms' => $terms,
+ '$base' => z_root() . '/' . \App::$cmd
+ ));
+ }
+}
diff --git a/Zotlabs/Widget/Findpeople.php b/Zotlabs/Widget/Findpeople.php
new file mode 100644
index 000000000..f450b96ae
--- /dev/null
+++ b/Zotlabs/Widget/Findpeople.php
@@ -0,0 +1,12 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+require_once('include/contact_widgets.php');
+
+class Findpeople {
+ function widget($arr) {
+ return findpeople_widget();
+ }
+}
+
diff --git a/Zotlabs/Widget/Follow.php b/Zotlabs/Widget/Follow.php
new file mode 100644
index 000000000..c4aecc8e1
--- /dev/null
+++ b/Zotlabs/Widget/Follow.php
@@ -0,0 +1,37 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+
+class Follow {
+
+ function widget($args) {
+ if(! local_channel())
+ return '';
+
+ $uid = \App::$channel['channel_id'];
+ $r = q("select count(*) as total from abook where abook_channel = %d and abook_self = 0 ",
+ intval($uid)
+ );
+
+ if($r)
+ $total_channels = $r[0]['total'];
+
+ $limit = service_class_fetch($uid,'total_channels');
+ if($limit !== false) {
+ $abook_usage_message = sprintf( t("You have %1$.0f of %2$.0f allowed connections."), $total_channels, $limit);
+ }
+ else {
+ $abook_usage_message = '';
+ }
+
+ return replace_macros(get_markup_template('follow.tpl'),array(
+ '$connect' => t('Add New Connection'),
+ '$desc' => t('Enter channel address'),
+ '$hint' => t('Examples: bob@example.com, https://example.com/barbara'),
+ '$follow' => t('Connect'),
+ '$abook_usage_message' => $abook_usage_message
+ ));
+ }
+}
+
diff --git a/Zotlabs/Widget/Forums.php b/Zotlabs/Widget/Forums.php
new file mode 100644
index 000000000..002c0ee21
--- /dev/null
+++ b/Zotlabs/Widget/Forums.php
@@ -0,0 +1,97 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Forums {
+
+ function widget($arr) {
+
+ if(! local_channel())
+ return '';
+
+ $o = '';
+
+ if(is_array($arr) && array_key_exists('limit',$arr))
+ $limit = " limit " . intval($limit) . " ";
+ else
+ $limit = '';
+
+ $unseen = 0;
+ if(is_array($arr) && array_key_exists('unseen',$arr) && intval($arr['unseen']))
+ $unseen = 1;
+
+ $perms_sql = item_permissions_sql(local_channel()) . item_normal();
+
+ $xf = false;
+
+ $x1 = q("select xchan from abconfig where chan = %d and cat = 'their_perms' and k = 'send_stream' and v = '0'",
+ intval(local_channel())
+ );
+ if($x1) {
+ $xc = ids_to_querystr($x1,'xchan',true);
+ $x2 = q("select xchan from abconfig where chan = %d and cat = 'their_perms' and k = 'tag_deliver' and v = '1' and xchan in (" . $xc . ") ",
+ intval(local_channel())
+ );
+ if($x2)
+ $xf = ids_to_querystr($x2,'xchan',true);
+ }
+
+ $sql_extra = (($xf) ? " and ( xchan_hash in (" . $xf . ") or xchan_pubforum = 1 ) " : " and xchan_pubforum = 1 ");
+
+ $r1 = q("select abook_id, xchan_hash, xchan_name, xchan_url, xchan_photo_s from abook left join xchan on abook_xchan = xchan_hash where xchan_deleted = 0 and abook_channel = %d $sql_extra order by xchan_name $limit ",
+ intval(local_channel())
+ );
+ if(! $r1)
+ return $o;
+
+ $str = '';
+
+ // Trying to cram all this into a single query with joins and the proper group by's is tough.
+ // There also should be a way to update this via ajax.
+
+ for($x = 0; $x < count($r1); $x ++) {
+ $r = q("select sum(item_unseen) as unseen from item where owner_xchan = '%s' and uid = %d and item_unseen = 1 $perms_sql ",
+ dbesc($r1[$x]['xchan_hash']),
+ intval(local_channel())
+ );
+ if($r)
+ $r1[$x]['unseen'] = $r[0]['unseen'];
+
+ /**
+ * @FIXME
+ * This SQL makes the counts correct when you get forum posts arriving from different routes/sources
+ * (like personal channels). However the network query for these posts doesn't yet include this
+ * correction and it makes the SQL for that query pretty hairy so this is left as a future exercise.
+ * It may make more sense in that query to look for the mention in the body rather than another join,
+ * but that makes it very inefficient.
+ *
+ $r = q("select sum(item_unseen) as unseen from item left join term on oid = id where otype = %d and owner_xchan != '%s' and item.uid = %d and url = '%s' and ttype = %d $perms_sql ",
+ intval(TERM_OBJ_POST),
+ dbesc($r1[$x]['xchan_hash']),
+ intval(local_channel()),
+ dbesc($r1[$x]['xchan_url']),
+ intval(TERM_MENTION)
+ );
+ if($r)
+ $r1[$x]['unseen'] = ((array_key_exists('unseen',$r1[$x])) ? $r1[$x]['unseen'] + $r[0]['unseen'] : $r[0]['unseen']);
+ *
+ * end @FIXME
+ */
+
+ }
+
+ if($r1) {
+ $o .= '<div class="widget">';
+ $o .= '<h3>' . t('Forums') . '</h3><ul class="nav nav-pills flex-column">';
+
+ foreach($r1 as $rr) {
+ if($unseen && (! intval($rr['unseen'])))
+ continue;
+ $o .= '<li class="nav-item"><a class="nav-link" href="network?f=&pf=1&cid=' . $rr['abook_id'] . '" ><span class="badge badge-secondary float-right">' . ((intval($rr['unseen'])) ? intval($rr['unseen']) : '') . '</span><img class ="menu-img-1" src="' . $rr['xchan_photo_s'] . '" /> ' . $rr['xchan_name'] . '</a></li>';
+ }
+ $o .= '</ul></div>';
+ }
+ return $o;
+
+ }
+}
diff --git a/Zotlabs/Widget/Fullprofile.php b/Zotlabs/Widget/Fullprofile.php
new file mode 100644
index 000000000..d7340ef40
--- /dev/null
+++ b/Zotlabs/Widget/Fullprofile.php
@@ -0,0 +1,16 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Fullprofile {
+
+ function widget($arr) {
+
+ if(! \App::$profile['profile_uid'])
+ return;
+
+ $block = observer_prohibited();
+
+ return profile_sidebar(\App::$profile, $block);
+ }
+}
diff --git a/Zotlabs/Widget/Helpindex.php b/Zotlabs/Widget/Helpindex.php
new file mode 100644
index 000000000..6c8748194
--- /dev/null
+++ b/Zotlabs/Widget/Helpindex.php
@@ -0,0 +1,55 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Helpindex {
+
+ function widget($arr) {
+
+ $o .= '<div class="widget">';
+
+ $level_0 = get_help_content('sitetoc');
+ if(! $level_0) {
+ $path = 'toc';
+ $x = determine_help_language();
+ $lang = $x['language'];
+ if($lang !== 'en') {
+ $path = $lang . '/toc';
+ }
+ $level_0 = get_help_content($path);
+ }
+
+ $level_0 = preg_replace('/\<ul(.*?)\>/','<ul class="nav nav-pills flex-column">',$level_0);
+
+ $levels = array();
+
+
+ // TODO: Implement support for translations in hierarchical table of content files
+ /*
+ if(argc() > 2) {
+ $path = '';
+ for($x = 1; $x < argc(); $x ++) {
+ $path .= argv($x) . '/';
+ $y = get_help_content($path . 'sitetoc');
+ if(! $y)
+ $y = get_help_content($path . 'toc');
+ if($y)
+ $levels[] = preg_replace('/\<ul(.*?)\>/','<ul class="nav nav-pills flex-column">',$y);
+ }
+ }
+ */
+
+ if($level_0)
+ $o .= $level_0;
+ if($levels) {
+ foreach($levels as $l) {
+ $o .= '<br /><br />';
+ $o .= $l;
+ }
+ }
+
+ $o .= '</div>';
+
+ return $o;
+ }
+}
diff --git a/Zotlabs/Widget/Item.php b/Zotlabs/Widget/Item.php
new file mode 100644
index 000000000..273d5649c
--- /dev/null
+++ b/Zotlabs/Widget/Item.php
@@ -0,0 +1,54 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+require_once('include/security.php');
+
+class Item {
+
+ function widget($arr) {
+
+ $channel_id = 0;
+ if(array_key_exists('channel_id',$arr) && intval($arr['channel_id']))
+ $channel_id = intval($arr['channel_id']);
+ if(! $channel_id)
+ $channel_id = \App::$profile_uid;
+ if(! $channel_id)
+ return '';
+
+
+ if((! $arr['mid']) && (! $arr['title']))
+ return '';
+
+ if(! perm_is_allowed($channel_id, get_observer_hash(), 'view_pages'))
+ return '';
+
+ $sql_extra = item_permissions_sql($channel_id);
+
+ if($arr['title']) {
+ $r = q("select item.* from item left join iconfig on item.id = iconfig.iid
+ where item.uid = %d and iconfig.cat = 'system' and iconfig.v = '%s'
+ and iconfig.k = 'WEBPAGE' and item_type = %d $sql_options $revision limit 1",
+ intval($channel_id),
+ dbesc($arr['title']),
+ intval(ITEM_TYPE_WEBPAGE)
+ );
+ }
+ else {
+ $r = q("select * from item where mid = '%s' and uid = %d and item_type = "
+ . intval(ITEM_TYPE_WEBPAGE) . " $sql_extra limit 1",
+ dbesc($arr['mid']),
+ intval($channel_id)
+ );
+ }
+
+ if(! $r)
+ return '';
+
+ xchan_query($r);
+ $r = fetch_post_tags($r, true);
+
+ $o = prepare_page($r[0]);
+ return $o;
+ }
+}
diff --git a/Zotlabs/Widget/Mailmenu.php b/Zotlabs/Widget/Mailmenu.php
new file mode 100644
index 000000000..512f7d9c0
--- /dev/null
+++ b/Zotlabs/Widget/Mailmenu.php
@@ -0,0 +1,36 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Mailmenu {
+
+ function widget($arr) {
+
+ if (! local_channel())
+ return;
+
+ return replace_macros(get_markup_template('message_side.tpl'), array(
+ '$title' => t('Private Mail Menu'),
+ '$combined' => array(
+ 'label' => t('Combined View'),
+ 'url' => z_root() . '/mail/combined',
+ 'sel' => (argv(1) == 'combined'),
+ ),
+ '$inbox' => array(
+ 'label' => t('Inbox'),
+ 'url' => z_root() . '/mail/inbox',
+ 'sel' => (argv(1) == 'inbox'),
+ ),
+ '$outbox' => array(
+ 'label' => t('Outbox'),
+ 'url' => z_root() . '/mail/outbox',
+ 'sel' => (argv(1) == 'outbox'),
+ ),
+ '$new' => array(
+ 'label' => t('New Message'),
+ 'url' => z_root() . '/mail/new',
+ 'sel'=> (argv(1) == 'new'),
+ )
+ ));
+ }
+}
diff --git a/Zotlabs/Widget/Menu_preview.php b/Zotlabs/Widget/Menu_preview.php
new file mode 100644
index 000000000..51218f6cf
--- /dev/null
+++ b/Zotlabs/Widget/Menu_preview.php
@@ -0,0 +1,16 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+require_once('include/menu.php');
+
+class Menu_preview {
+
+ function widget($arr) {
+ if(! \App::$data['menu_item'])
+ return;
+
+ return menu_render(\App::$data['menu_item']);
+ }
+
+}
diff --git a/Zotlabs/Widget/Notes.php b/Zotlabs/Widget/Notes.php
new file mode 100644
index 000000000..5c83a550f
--- /dev/null
+++ b/Zotlabs/Widget/Notes.php
@@ -0,0 +1,23 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Notes {
+
+ function widget($arr) {
+ if(! local_channel())
+ return '';
+ if(! feature_enabled(local_channel(),'private_notes'))
+ return '';
+
+ $text = get_pconfig(local_channel(),'notes','text');
+
+ $o = replace_macros(get_markup_template('notes.tpl'), array(
+ '$banner' => t('Notes'),
+ '$text' => $text,
+ '$save' => t('Save'),
+ ));
+
+ return $o;
+ }
+}
diff --git a/Zotlabs/Widget/Notifications.php b/Zotlabs/Widget/Notifications.php
new file mode 100644
index 000000000..a857f1ad9
--- /dev/null
+++ b/Zotlabs/Widget/Notifications.php
@@ -0,0 +1,150 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Notifications {
+
+ function widget($arr) {
+
+ $channel = \App::get_channel();
+
+ if(local_channel()) {
+ $notifications[] = [
+ 'type' => 'network',
+ 'icon' => 'th',
+ 'severity' => 'secondary',
+ 'label' => t('New Network Activity'),
+ 'title' => t('New Network Activity Notifications'),
+ 'viewall' => [
+ 'url' => 'network',
+ 'label' => t('View your network activity')
+ ],
+ 'markall' => [
+ 'url' => '#',
+ 'label' => t('Mark all notifications read')
+ ]
+ ];
+
+ $notifications[] = [
+ 'type' => 'home',
+ 'icon' => 'home',
+ 'severity' => 'danger',
+ 'label' => t('New Home Activity'),
+ 'title' => t('New Home Activity Notifications'),
+ 'viewall' => [
+ 'url' => 'channel/' . $channel['channel_address'],
+ 'label' => t('View your home activity')
+ ],
+ 'markall' => [
+ 'url' => '#',
+ 'label' => t('Mark all notifications seen')
+ ]
+ ];
+
+ $notifications[] = [
+ 'type' => 'mail',
+ 'icon' => 'envelope',
+ 'severity' => 'danger',
+ 'label' => t('New Mails'),
+ 'title' => t('New Mails Notifications'),
+ 'viewall' => [
+ 'url' => 'mail/combined',
+ 'label' => t('View your private mails')
+ ],
+ 'markall' => [
+ 'url' => '#',
+ 'label' => t('Mark all messages seen')
+ ]
+ ];
+
+ $notifications[] = [
+ 'type' => 'all_events',
+ 'icon' => 'calendar',
+ 'severity' => 'secondary',
+ 'label' => t('New Events'),
+ 'title' => t('New Events Notifications'),
+ 'viewall' => [
+ 'url' => 'mail/combined',
+ 'label' => t('View events')
+ ],
+ 'markall' => [
+ 'url' => '#',
+ 'label' => t('Mark all events seen')
+ ]
+ ];
+
+ $notifications[] = [
+ 'type' => 'intros',
+ 'icon' => 'users',
+ 'severity' => 'danger',
+ 'label' => t('New Connections'),
+ 'title' => t('New Connections Notifications'),
+ 'viewall' => [
+ 'url' => 'connections',
+ 'label' => t('View all connections')
+ ]
+ ];
+
+ $notifications[] = [
+ 'type' => 'files',
+ 'icon' => 'folder',
+ 'severity' => 'danger',
+ 'label' => t('New Files'),
+ 'title' => t('New Files Notifications'),
+ ];
+
+ $notifications[] = [
+ 'type' => 'notify',
+ 'icon' => 'exclamation',
+ 'severity' => 'danger',
+ 'label' => t('Notices'),
+ 'title' => t('Notices'),
+ 'viewall' => [
+ 'url' => 'notifications/system',
+ 'label' => t('View all notices')
+ ],
+ 'markall' => [
+ 'url' => '#',
+ 'label' => t('Mark all notices seen')
+ ]
+ ];
+ }
+
+ if(local_channel() && is_site_admin()) {
+ $notifications[] = [
+ 'type' => 'register',
+ 'icon' => 'user-o',
+ 'severity' => 'danger',
+ 'label' => t('New Registrations'),
+ 'title' => t('New Registrations Notifications'),
+ ];
+ }
+
+ if(get_config('system', 'disable_discover_tab') != 1) {
+ $notifications[] = [
+ 'type' => 'pubs',
+ 'icon' => 'globe',
+ 'severity' => 'secondary',
+ 'label' => t('Public Stream'),
+ 'title' => t('Public Stream Notifications'),
+ 'viewall' => [
+ 'url' => 'pubstream',
+ 'label' => t('View the public stream')
+ ],
+ 'markall' => [
+ 'url' => '#',
+ 'label' => t('Mark all notifications seen')
+ ]
+ ];
+ }
+
+ $o = replace_macros(get_markup_template('notifications_widget.tpl'), array(
+ '$notifications' => $notifications,
+ '$loading' => t('Loading...')
+ ));
+
+ return $o;
+
+ }
+}
+
diff --git a/Zotlabs/Widget/Photo.php b/Zotlabs/Widget/Photo.php
new file mode 100644
index 000000000..10031f028
--- /dev/null
+++ b/Zotlabs/Widget/Photo.php
@@ -0,0 +1,55 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+
+class Photo {
+
+
+ /**
+ * @brief Widget to display a single photo.
+ *
+ * @param array $arr associative array with
+ * * \e string \b src URL of photo; URL must be an http or https URL
+ * * \e boolean \b zrl use zid in URL
+ * * \e string \b style CSS string
+ *
+ * @return string with parsed HTML
+ */
+
+ function widget($arr) {
+
+ $style = $zrl = false;
+
+ if(array_key_exists('src', $arr) && isset($arr['src']))
+ $url = $arr['src'];
+
+ if(strpos($url, 'http') !== 0)
+ return '';
+
+ if(array_key_exists('style', $arr) && isset($arr['style']))
+ $style = $arr['style'];
+
+ // ensure they can't sneak in an eval(js) function
+
+ if(strpbrk($style, '(\'"<>' ) !== false)
+ $style = '';
+
+ if(array_key_exists('zrl', $arr) && isset($arr['zrl']))
+ $zrl = (($arr['zrl']) ? true : false);
+
+ if($zrl)
+ $url = zid($url);
+
+ $o = '<div class="widget">';
+
+ $o .= '<img ' . (($zrl) ? ' class="zrl" ' : '')
+ . (($style) ? ' style="' . $style . '"' : '')
+ . ' src="' . $url . '" alt="' . t('photo/image') . '">';
+
+ $o .= '</div>';
+
+ return $o;
+ }
+}
+
diff --git a/Zotlabs/Widget/Photo_albums.php b/Zotlabs/Widget/Photo_albums.php
new file mode 100644
index 000000000..6df8ddf3c
--- /dev/null
+++ b/Zotlabs/Widget/Photo_albums.php
@@ -0,0 +1,25 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+require_once('include/photos.php');
+
+class Photo_albums {
+
+ function widget($arr) {
+
+ if(! \App::$profile['profile_uid'])
+ return '';
+
+ $channelx = channelx_by_n(\App::$profile['profile_uid']);
+
+ if((! $channelx) || (! perm_is_allowed(\App::$profile['profile_uid'], get_observer_hash(), 'view_storage')))
+ return '';
+
+ $sortkey = ((array_key_exists('sortkey',$arr)) ? $arr['sortkey'] : 'display_path');
+ $direction = ((array_key_exists('direction',$arr)) ? $arr['direction'] : 'asc');
+
+ return photos_album_widget($channelx, \App::get_observer(),$sortkey,$direction);
+ }
+}
+
diff --git a/Zotlabs/Widget/Photo_rand.php b/Zotlabs/Widget/Photo_rand.php
new file mode 100644
index 000000000..af80a3b9f
--- /dev/null
+++ b/Zotlabs/Widget/Photo_rand.php
@@ -0,0 +1,66 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+require_once('include/photos.php');
+
+class Photo_rand {
+
+ function widget($arr) {
+
+ $style = false;
+
+ if(array_key_exists('album', $arr) && isset($arr['album']))
+ $album = $arr['album'];
+ else
+ $album = '';
+
+ $channel_id = 0;
+ if(array_key_exists('channel_id', $arr) && intval($arr['channel_id']))
+ $channel_id = intval($arr['channel_id']);
+ if(! $channel_id)
+ $channel_id = \App::$profile_uid;
+ if(! $channel_id)
+ return '';
+
+ $scale = ((array_key_exists('scale',$arr)) ? intval($arr['scale']) : 0);
+
+ $ret = photos_list_photos(array('channel_id' => $channel_id),\App::get_observer(),$album);
+
+ $filtered = array();
+ if($ret['success'] && $ret['photos'])
+ foreach($ret['photos'] as $p)
+ if($p['imgscale'] == $scale)
+ $filtered[] = $p['src'];
+
+ if($filtered) {
+ $e = mt_rand(0, count($filtered) - 1);
+ $url = $filtered[$e];
+ }
+
+ if(strpos($url, 'http') !== 0)
+ return '';
+
+ if(array_key_exists('style', $arr) && isset($arr['style']))
+ $style = $arr['style'];
+
+ // ensure they can't sneak in an eval(js) function
+
+ if(strpos($style,'(') !== false)
+ return '';
+
+ $url = zid($url);
+
+ $o = '<div class="widget">';
+
+ $o .= '<img class="zrl" '
+ . (($style) ? ' style="' . $style . '"' : '')
+ . ' src="' . $url . '" alt="' . t('photo/image') . '">';
+
+ $o .= '</div>';
+
+ return $o;
+ }
+}
+
+
diff --git a/Zotlabs/Widget/Portfolio.php b/Zotlabs/Widget/Portfolio.php
new file mode 100644
index 000000000..216ca952c
--- /dev/null
+++ b/Zotlabs/Widget/Portfolio.php
@@ -0,0 +1,108 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+require_once('include/attach.php');
+
+class Portfolio {
+
+ function widget($args) {
+
+
+ $owner_uid = \App::$profile_uid;
+ $sql_extra = permissions_sql($owner_uid);
+
+
+ if(! perm_is_allowed($owner_uid,get_observer_hash(),'view_storage'))
+ return '';
+
+ if($args['album'])
+ $album = $args['album'];
+ if($args['title'])
+ $title = $args['title'];
+
+ /**
+ * This may return incorrect permissions if you have multiple directories of the same name.
+ * It is a limitation of the photo table using a name for a photo album instead of a folder hash
+ */
+
+ if($album) {
+ $x = q("select hash from attach where filename = '%s' and uid = %d limit 1",
+ dbesc($album),
+ intval($owner_uid)
+ );
+ if($x) {
+ $y = attach_can_view_folder($owner_uid,get_observer_hash(),$x[0]['hash']);
+ if(! $y)
+ return '';
+ }
+ }
+
+ $order = 'DESC';
+
+ $r = q("SELECT p.resource_id, p.id, p.filename, p.mimetype, p.imgscale, p.description, p.created FROM photo p INNER JOIN
+ (SELECT resource_id, max(imgscale) imgscale FROM photo WHERE uid = %d AND album = '%s' AND imgscale <= 4 AND photo_usage IN ( %d, %d ) $sql_extra GROUP BY resource_id) ph
+ ON (p.resource_id = ph.resource_id AND p.imgscale = ph.imgscale)
+ ORDER BY created $order ",
+ intval($owner_uid),
+ dbesc($album),
+ intval(PHOTO_NORMAL),
+ intval(PHOTO_PROFILE)
+ );
+
+ //edit album name
+ $album_edit = null;
+
+ $photos = array();
+ if($r) {
+ $twist = 'rotright';
+ foreach($r as $rr) {
+
+ if($twist == 'rotright')
+ $twist = 'rotleft';
+ else
+ $twist = 'rotright';
+
+ $ext = $phototypes[$rr['mimetype']];
+
+ $imgalt_e = $rr['filename'];
+ $desc_e = $rr['description'];
+
+ $imagelink = (z_root() . '/photos/' . \App::$profile['channel_address'] . '/image/' . $rr['resource_id']);
+
+
+ $photos[] = array(
+ 'id' => $rr['id'],
+ 'twist' => ' ' . $twist . rand(2,4),
+ 'link' => $imagelink,
+ 'title' => t('View Photo'),
+ 'src' => z_root() . '/photo/' . $rr['resource_id'] . '-' . $rr['imgscale'] . '.' .$ext,
+ 'fullsrc' => z_root() . '/photo/' . $rr['resource_id'] . '-' . '1' . '.' .$ext,
+ 'resource_id' => $rr['resource_id'],
+ 'alt' => $imgalt_e,
+ 'desc'=> $desc_e,
+ 'ext' => $ext,
+ 'hash'=> $rr['resource_id'],
+ 'unknown' => t('Unknown')
+ );
+ }
+ }
+
+
+ $tpl = get_markup_template('photo_album_portfolio.tpl');
+ $o .= replace_macros($tpl, array(
+ '$photos' => $photos,
+ '$album' => (($title) ? $title : $album),
+ '$album_id' => rand(),
+ '$album_edit' => array(t('Edit Album'), $album_edit),
+ '$can_post' => false,
+ '$upload' => array(t('Upload'), z_root() . '/photos/' . \App::$profile['channel_address'] . '/upload/' . bin2hex($album)),
+ '$order' => false,
+ '$upload_form' => $upload_form,
+ '$usage' => $usage_message
+ ));
+
+ return $o;
+ }
+}
+
diff --git a/Zotlabs/Widget/Profile.php b/Zotlabs/Widget/Profile.php
new file mode 100644
index 000000000..bffd910b6
--- /dev/null
+++ b/Zotlabs/Widget/Profile.php
@@ -0,0 +1,13 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+
+class Profile {
+
+ function widget($args) {
+ $block = observer_prohibited();
+ return profile_sidebar(\App::$profile, $block, true);
+ }
+
+} \ No newline at end of file
diff --git a/Zotlabs/Widget/Pubsites.php b/Zotlabs/Widget/Pubsites.php
new file mode 100644
index 000000000..958ba68c2
--- /dev/null
+++ b/Zotlabs/Widget/Pubsites.php
@@ -0,0 +1,16 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Pubsites {
+
+ // used by site ratings pages to provide a return link
+
+ function widget($arr) {
+ if(\App::$poi)
+ return;
+ return '<div class="widget"><ul class="nav nav-pills"><li><a href="pubsites">' . t('Public Hubs') . '</a></li></ul></div>';
+ }
+}
+
+
diff --git a/Zotlabs/Widget/Random_block.php b/Zotlabs/Widget/Random_block.php
new file mode 100644
index 000000000..465a51f97
--- /dev/null
+++ b/Zotlabs/Widget/Random_block.php
@@ -0,0 +1,46 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Random_block {
+
+ function widget($arr) {
+
+ $channel_id = 0;
+ if(array_key_exists('channel_id',$arr) && intval($arr['channel_id']))
+ $channel_id = intval($arr['channel_id']);
+ if(! $channel_id)
+ $channel_id = \App::$profile_uid;
+ if(! $channel_id)
+ return '';
+
+ if(array_key_exists('contains',$arr))
+ $contains = $arr['contains'];
+
+ $o = '';
+
+ require_once('include/security.php');
+ $sql_options = item_permissions_sql($channel_id);
+
+ $randfunc = db_getfunc('RAND');
+
+ $r = q("select item.* from item left join iconfig on item.id = iconfig.iid
+ where item.uid = %d and iconfig.cat = 'system' and iconfig.v like '%s' and iconfig.k = 'BUILDBLOCK' and
+ item_type = %d $sql_options order by $randfunc limit 1",
+ intval($channel_id),
+ dbesc('%' . $contains . '%'),
+ intval(ITEM_TYPE_BLOCK)
+ );
+
+ if($r) {
+ $o = '<div class="widget bblock">';
+ if($r[0]['title'])
+ $o .= '<h3>' . $r[0]['title'] . '</h3>';
+
+ $o .= prepare_text($r[0]['body'],$r[0]['mimetype']);
+ $o .= '</div>';
+ }
+
+ return $o;
+ }
+}
diff --git a/Zotlabs/Widget/Rating.php b/Zotlabs/Widget/Rating.php
new file mode 100644
index 000000000..5e09f457b
--- /dev/null
+++ b/Zotlabs/Widget/Rating.php
@@ -0,0 +1,67 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Rating {
+
+ function widget($arr) {
+
+
+ $rating_enabled = get_config('system','rating_enabled');
+ if(! $rating_enabled) {
+ return;
+ }
+
+ if($arr['target'])
+ $hash = $arr['target'];
+ else
+ $hash = \App::$poi['xchan_hash'];
+
+ if(! $hash)
+ return;
+
+ $url = '';
+ $remote = false;
+
+ if(remote_channel() && ! local_channel()) {
+ $ob = \App::get_observer();
+ if($ob && $ob['xchan_url']) {
+ $p = parse_url($ob['xchan_url']);
+ if($p) {
+ $url = $p['scheme'] . '://' . $p['host'] . (($p['port']) ? ':' . $p['port'] : '');
+ $url .= '/rate?f=&target=' . urlencode($hash);
+ }
+ $remote = true;
+ }
+ }
+
+ $self = false;
+
+ if(local_channel()) {
+ $channel = \App::get_channel();
+
+ if($hash == $channel['channel_hash'])
+ $self = true;
+
+ head_add_js('ratings.js');
+ }
+
+
+ $o = '<div class="widget">';
+ $o .= '<h3>' . t('Rating Tools') . '</h3>';
+
+ if((($remote) || (local_channel())) && (! $self)) {
+ if($remote)
+ $o .= '<a class="btn btn-block btn-primary btn-sm" href="' . $url . '"><i class="fa fa-pencil"></i> ' . t('Rate Me') . '</a>';
+ else
+ $o .= '<div class="btn btn-block btn-primary btn-sm" onclick="doRatings(\'' . $hash . '\'); return false;"><i class="fa fa-pencil"></i> ' . t('Rate Me') . '</div>';
+ }
+
+ $o .= '<a class="btn btn-block btn-default btn-sm" href="ratings/' . $hash . '"><i class="fa fa-eye"></i> ' . t('View Ratings') . '</a>';
+ $o .= '</div>';
+
+ return $o;
+
+ }
+}
+
diff --git a/Zotlabs/Widget/Savedsearch.php b/Zotlabs/Widget/Savedsearch.php
new file mode 100644
index 000000000..378c27139
--- /dev/null
+++ b/Zotlabs/Widget/Savedsearch.php
@@ -0,0 +1,91 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Savedsearch {
+
+ function widget($arr) {
+
+ if((! local_channel()) || (! feature_enabled(local_channel(),'savedsearch')))
+ return '';
+
+ $search = ((x($_GET,'netsearch')) ? $_GET['netsearch'] : '');
+ if(! $search)
+ $search = ((x($_GET,'search')) ? $_GET['search'] : '');
+
+ if(x($_GET,'searchsave') && $search) {
+ $r = q("select * from term where uid = %d and ttype = %d and term = '%s' limit 1",
+ intval(local_channel()),
+ intval(TERM_SAVEDSEARCH),
+ dbesc($search)
+ );
+ if(! $r) {
+ q("insert into term ( uid,ttype,term ) values ( %d, %d, '%s') ",
+ intval(local_channel()),
+ intval(TERM_SAVEDSEARCH),
+ dbesc($search)
+ );
+ }
+ }
+
+ if(x($_GET,'searchremove') && $search) {
+ q("delete from term where uid = %d and ttype = %d and term = '%s'",
+ intval(local_channel()),
+ intval(TERM_SAVEDSEARCH),
+ dbesc($search)
+ );
+ $search = '';
+ }
+
+ $srchurl = \App::$query_string;
+
+ $srchurl = rtrim(preg_replace('/searchsave\=[^\&].*?(\&|$)/is','',$srchurl),'&');
+ $hasq = ((strpos($srchurl,'?') !== false) ? true : false);
+ $srchurl = rtrim(preg_replace('/searchremove\=[^\&].*?(\&|$)/is','',$srchurl),'&');
+
+ $srchurl = rtrim(preg_replace('/search\=[^\&].*?(\&|$)/is','',$srchurl),'&');
+ $srchurl = rtrim(preg_replace('/submit\=[^\&].*?(\&|$)/is','',$srchurl),'&');
+ $srchurl = str_replace(array('?f=','&f='),array('',''),$srchurl);
+
+
+ $hasq = ((strpos($srchurl,'?') !== false) ? true : false);
+ $hasamp = ((strpos($srchurl,'&') !== false) ? true : false);
+
+ if(($hasamp) && (! $hasq))
+ $srchurl = substr($srchurl,0,strpos($srchurl,'&')) . '?f=&' . substr($srchurl,strpos($srchurl,'&')+1);
+
+ $o = '';
+
+ $r = q("select tid,term from term WHERE uid = %d and ttype = %d ",
+ intval(local_channel()),
+ intval(TERM_SAVEDSEARCH)
+ );
+
+ $saved = array();
+
+ if(count($r)) {
+ foreach($r as $rr) {
+ $saved[] = array(
+ 'id' => $rr['tid'],
+ 'term' => $rr['term'],
+ 'dellink' => z_root() . '/' . $srchurl . (($hasq || $hasamp) ? '' : '?f=') . '&amp;searchremove=1&amp;search=' . urlencode($rr['term']),
+ 'srchlink' => z_root() . '/' . $srchurl . (($hasq || $hasamp) ? '' : '?f=') . '&amp;search=' . urlencode($rr['term']),
+ 'displayterm' => htmlspecialchars($rr['term'], ENT_COMPAT,'UTF-8'),
+ 'encodedterm' => urlencode($rr['term']),
+ 'delete' => t('Remove term'),
+ 'selected' => ($search==$rr['term']),
+ );
+ }
+ }
+
+ $tpl = get_markup_template("saved_searches.tpl");
+ $o = replace_macros($tpl, array(
+ '$title' => t('Saved Searches'),
+ '$add' => t('add'),
+ '$searchbox' => searchbox($search, 'netsearch-box', $srchurl . (($hasq) ? '' : '?f='), true),
+ '$saved' => $saved,
+ ));
+
+ return $o;
+ }
+}
diff --git a/Zotlabs/Widget/Settings_menu.php b/Zotlabs/Widget/Settings_menu.php
new file mode 100644
index 000000000..c15ad0980
--- /dev/null
+++ b/Zotlabs/Widget/Settings_menu.php
@@ -0,0 +1,139 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Settings_menu {
+
+ function widget($arr) {
+
+ if(! local_channel())
+ return;
+
+
+ $channel = \App::get_channel();
+
+ $abook_self_id = 0;
+
+ // Retrieve the 'self' address book entry for use in the auto-permissions link
+
+ $role = get_pconfig(local_channel(),'system','permissions_role');
+
+ $abk = q("select abook_id from abook where abook_channel = %d and abook_self = 1 limit 1",
+ intval(local_channel())
+ );
+ if($abk)
+ $abook_self_id = $abk[0]['abook_id'];
+
+ $x = q("select count(*) as total from hubloc where hubloc_hash = '%s' and hubloc_deleted = 0 ",
+ dbesc($channel['channel_hash'])
+ );
+
+ $hublocs = (($x && $x[0]['total'] > 1) ? true : false);
+
+ $tabs = array(
+ array(
+ 'label' => t('Account settings'),
+ 'url' => z_root().'/settings/account',
+ 'selected' => ((argv(1) === 'account') ? 'active' : ''),
+ ),
+
+ array(
+ 'label' => t('Channel settings'),
+ 'url' => z_root().'/settings/channel',
+ 'selected' => ((argv(1) === 'channel') ? 'active' : ''),
+ ),
+
+ );
+
+ if(get_account_techlevel() > 0 && get_features()) {
+ $tabs[] = array(
+ 'label' => t('Additional features'),
+ 'url' => z_root().'/settings/features',
+ 'selected' => ((argv(1) === 'features') ? 'active' : ''),
+ );
+ }
+
+ $tabs[] = array(
+ 'label' => t('Feature/Addon settings'),
+ 'url' => z_root().'/settings/featured',
+ 'selected' => ((argv(1) === 'featured') ? 'active' : ''),
+ );
+
+ $tabs[] = array(
+ 'label' => t('Display settings'),
+ 'url' => z_root().'/settings/display',
+ 'selected' => ((argv(1) === 'display') ? 'active' : ''),
+ );
+
+ if($hublocs) {
+ $tabs[] = array(
+ 'label' => t('Manage locations'),
+ 'url' => z_root() . '/locs',
+ 'selected' => ((argv(1) === 'locs') ? 'active' : ''),
+ );
+ }
+
+ $tabs[] = array(
+ 'label' => t('Export channel'),
+ 'url' => z_root() . '/uexport',
+ 'selected' => ''
+ );
+
+ if(get_account_techlevel() > 0) {
+ $tabs[] = array(
+ 'label' => t('Connected apps'),
+ 'url' => z_root() . '/settings/oauth',
+ 'selected' => ((argv(1) === 'oauth') ? 'active' : ''),
+ );
+ }
+
+ if(get_account_techlevel() > 2) {
+ $tabs[] = array(
+ 'label' => t('Guest Access Tokens'),
+ 'url' => z_root() . '/settings/tokens',
+ 'selected' => ((argv(1) === 'tokens') ? 'active' : ''),
+ );
+ }
+
+ if(feature_enabled(local_channel(),'permcats')) {
+ $tabs[] = array(
+ 'label' => t('Permission Groups'),
+ 'url' => z_root() . '/settings/permcats',
+ 'selected' => ((argv(1) === 'permcats') ? 'active' : ''),
+ );
+ }
+
+
+ if($role === false || $role === 'custom') {
+ $tabs[] = array(
+ 'label' => t('Connection Default Permissions'),
+ 'url' => z_root() . '/connedit/' . $abook_self_id,
+ 'selected' => ''
+ );
+ }
+
+ if(feature_enabled(local_channel(),'premium_channel')) {
+ $tabs[] = array(
+ 'label' => t('Premium Channel Settings'),
+ 'url' => z_root() . '/connect/' . $channel['channel_address'],
+ 'selected' => ''
+ );
+ }
+
+ if(feature_enabled(local_channel(),'channel_sources')) {
+ $tabs[] = array(
+ 'label' => t('Channel Sources'),
+ 'url' => z_root() . '/sources',
+ 'selected' => ''
+ );
+ }
+
+ $tabtpl = get_markup_template("generic_links_widget.tpl");
+ return replace_macros($tabtpl, array(
+ '$title' => t('Settings'),
+ '$class' => 'settings-widget',
+ '$items' => $tabs,
+ ));
+ }
+
+} \ No newline at end of file
diff --git a/Zotlabs/Widget/Shortprofile.php b/Zotlabs/Widget/Shortprofile.php
new file mode 100644
index 000000000..9c2a46e75
--- /dev/null
+++ b/Zotlabs/Widget/Shortprofile.php
@@ -0,0 +1,18 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Shortprofile {
+
+ function widget($arr) {
+
+ if(! \App::$profile['profile_uid'])
+ return;
+
+ $block = observer_prohibited();
+
+ return profile_sidebar(\App::$profile, $block, true, true);
+ }
+
+}
+
diff --git a/Zotlabs/Widget/Sitesearch.php b/Zotlabs/Widget/Sitesearch.php
new file mode 100644
index 000000000..b3a25d76a
--- /dev/null
+++ b/Zotlabs/Widget/Sitesearch.php
@@ -0,0 +1,38 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+
+class Sitesearch {
+
+ function widget($arr) {
+
+ $search = ((x($_GET,'search')) ? $_GET['search'] : '');
+
+ $srchurl = \App::$query_string;
+
+ $srchurl = rtrim(preg_replace('/search\=[^\&].*?(\&|$)/is','',$srchurl),'&');
+ $srchurl = rtrim(preg_replace('/submit\=[^\&].*?(\&|$)/is','',$srchurl),'&');
+ $srchurl = str_replace(array('?f=','&f='),array('',''),$srchurl);
+
+
+ $hasq = ((strpos($srchurl,'?') !== false) ? true : false);
+ $hasamp = ((strpos($srchurl,'&') !== false) ? true : false);
+
+ if(($hasamp) && (! $hasq))
+ $srchurl = substr($srchurl,0,strpos($srchurl,'&')) . '?f=&' . substr($srchurl,strpos($srchurl,'&')+1);
+
+ $o = '';
+
+ $saved = array();
+
+ $tpl = get_markup_template("sitesearch.tpl");
+ $o = replace_macros($tpl, array(
+ '$title' => t('Search'),
+ '$searchbox' => searchbox($search, 'netsearch-box', $srchurl . (($hasq) ? '' : '?f='), false),
+ '$saved' => $saved,
+ ));
+
+ return $o;
+ }
+}
diff --git a/Zotlabs/Widget/Suggestedchats.php b/Zotlabs/Widget/Suggestedchats.php
new file mode 100644
index 000000000..7df42944d
--- /dev/null
+++ b/Zotlabs/Widget/Suggestedchats.php
@@ -0,0 +1,37 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Suggestedchats {
+
+ function widget($arr) {
+
+ if(! feature_enabled(\App::$profile['profile_uid'],'ajaxchat'))
+ return '';
+
+ // There are reports that this tool does not ever remove chatrooms on dead sites,
+ // and also will happily link to private chats which you cannot enter.
+ // For those reasons, it will be disabled until somebody decides it's worth
+ // fixing and comes up with a plan for doing so.
+
+ return '';
+
+ // probably should restrict this to your friends, but then the widget will only work
+ // if you are logged in locally.
+
+ $h = get_observer_hash();
+ if(! $h)
+ return;
+ $r = q("select xchat_url, xchat_desc, count(xchat_xchan) as total from xchat group by xchat_url, xchat_desc order by total desc, xchat_desc limit 24");
+ if($r) {
+ for($x = 0; $x < count($r); $x ++) {
+ $r[$x]['xchat_url'] = zid($r[$x]['xchat_url']);
+ }
+ }
+ return replace_macros(get_markup_template('bookmarkedchats.tpl'),array(
+ '$header' => t('Suggested Chatrooms'),
+ '$rooms' => $r
+ ));
+ }
+}
+
diff --git a/Zotlabs/Widget/Suggestions.php b/Zotlabs/Widget/Suggestions.php
new file mode 100644
index 000000000..5fb3d3e8b
--- /dev/null
+++ b/Zotlabs/Widget/Suggestions.php
@@ -0,0 +1,58 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+require_once('include/socgraph.php');
+
+
+class Suggestions {
+
+ function widget($arr) {
+
+ if((! local_channel()) || (! feature_enabled(local_channel(),'suggest')))
+ return '';
+
+
+ $r = suggestion_query(local_channel(),get_observer_hash(),0,20);
+
+ if(! $r) {
+ return;
+ }
+
+ $arr = array();
+
+ // Get two random entries from the top 20 returned.
+ // We'll grab the first one and the one immediately following.
+ // This will throw some entropy intot he situation so you won't
+ // be looking at the same two mug shots every time the widget runs
+
+ $index = ((count($r) > 2) ? mt_rand(0,count($r) - 2) : 0);
+
+ for($x = $index; $x <= ($index+1); $x ++) {
+ $rr = $r[$x];
+ if(! $rr['xchan_url'])
+ break;
+
+ $connlnk = z_root() . '/follow/?url=' . $rr['xchan_addr'];
+
+ $arr[] = array(
+ 'url' => chanlink_url($rr['xchan_url']),
+ 'profile' => $rr['xchan_url'],
+ 'name' => $rr['xchan_name'],
+ 'photo' => $rr['xchan_photo_m'],
+ 'ignlnk' => z_root() . '/directory?ignore=' . $rr['xchan_hash'],
+ 'conntxt' => t('Connect'),
+ 'connlnk' => $connlnk,
+ 'ignore' => t('Ignore/Hide')
+ );
+ }
+
+ $o = replace_macros(get_markup_template('suggest_widget.tpl'),array(
+ '$title' => t('Suggestions'),
+ '$more' => t('See more...'),
+ '$entries' => $arr
+ ));
+
+ return $o;
+ }
+}
diff --git a/Zotlabs/Widget/Tagcloud.php b/Zotlabs/Widget/Tagcloud.php
new file mode 100644
index 000000000..cf7a4932e
--- /dev/null
+++ b/Zotlabs/Widget/Tagcloud.php
@@ -0,0 +1,33 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+// @FIXME The problem with this widget is that we don't have a search function for webpages
+// that we can send the links to. Then we should also provide an option to search webpages
+// and conversations.
+
+class Tagcloud {
+
+ function widget($args) {
+
+ $o = '';
+ $uid = \App::$profile_uid;
+ $count = ((x($args,'count')) ? intval($args['count']) : 24);
+ $flags = 0;
+ $type = TERM_CATEGORY;
+
+ // @FIXME there exists no $authors variable
+ $r = tagadelic($uid, $count, $authors, $owner, $flags, ITEM_TYPE_WEBPAGE, $type);
+
+ // @FIXME this should use a template
+
+ if($r) {
+ $o = '<div class="tagblock widget"><h3>' . t('Categories') . '</h3><div class="tags" align="center">';
+ foreach($r as $rv) {
+ $o .= '<span class="tag' . $rv[2] . '">' . $rv[0] .' </span> ' . "\r\n";
+ }
+ $o .= '</div></div>';
+ }
+ return $o;
+ }
+}
diff --git a/Zotlabs/Widget/Tagcloud_wall.php b/Zotlabs/Widget/Tagcloud_wall.php
new file mode 100644
index 000000000..7cff6ce09
--- /dev/null
+++ b/Zotlabs/Widget/Tagcloud_wall.php
@@ -0,0 +1,20 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Tagcloud_wall {
+
+ function widget($arr) {
+
+ if((! \App::$profile['profile_uid']) || (! \App::$profile['channel_hash']))
+ return '';
+ if(! perm_is_allowed(\App::$profile['profile_uid'], get_observer_hash(), 'view_stream'))
+ return '';
+
+ $limit = ((array_key_exists('limit', $arr)) ? intval($arr['limit']) : 50);
+ if(feature_enabled(\App::$profile['profile_uid'], 'tagadelic'))
+ return wtagblock(\App::$profile['profile_uid'], $limit, '', \App::$profile['channel_hash'], 'wall');
+
+ return '';
+ }
+}
diff --git a/Zotlabs/Widget/Tasklist.php b/Zotlabs/Widget/Tasklist.php
new file mode 100644
index 000000000..3961eecce
--- /dev/null
+++ b/Zotlabs/Widget/Tasklist.php
@@ -0,0 +1,30 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+require_once('include/event.php');
+
+class Tasklist {
+
+ function widget($arr) {
+
+ if (! local_channel())
+ return;
+
+ $o .= '<script>var tasksShowAll = 0; $(document).ready(function() { tasksFetch(); $("#tasklist-new-form").submit(function(event) { event.preventDefault(); $.post( "tasks/new", $("#tasklist-new-form").serialize(), function(data) { tasksFetch(); $("#tasklist-new-summary").val(""); } ); return false; } )});</script>';
+ $o .= '<script>function taskComplete(id) { $.post("tasks/complete/"+id, function(data) { tasksFetch();}); }
+ function tasksFetch() {
+ $.get("tasks/fetch" + ((tasksShowAll) ? "/all" : ""), function(data) {
+ $(".tasklist-tasks").html(data.html);
+ });
+ }
+ </script>';
+
+ $o .= '<div class="widget">' . '<h3>' . t('Tasks') . '</h3><div class="tasklist-tasks">';
+ $o .= '</div><form id="tasklist-new-form" action="" ><input id="tasklist-new-summary" type="text" name="summary" value="" /></form>';
+ $o .= '</div>';
+ return $o;
+
+ }
+}
+
diff --git a/Zotlabs/Widget/Vcard.php b/Zotlabs/Widget/Vcard.php
new file mode 100644
index 000000000..cab05dfdd
--- /dev/null
+++ b/Zotlabs/Widget/Vcard.php
@@ -0,0 +1,12 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Vcard {
+
+ function widget($arr) {
+ return vcard_from_xchan('', \App::get_observer());
+ }
+
+}
+
diff --git a/Zotlabs/Widget/Website_portation_tools.php b/Zotlabs/Widget/Website_portation_tools.php
new file mode 100644
index 000000000..1cf3bb78a
--- /dev/null
+++ b/Zotlabs/Widget/Website_portation_tools.php
@@ -0,0 +1,22 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+
+class Website_portation_tools {
+
+ function widget($arr) {
+
+ // mod menu doesn't load a profile. For any modules which load a profile, check it.
+ // otherwise local_channel() is sufficient for permissions.
+
+ if(\App::$profile['profile_uid'])
+ if((\App::$profile['profile_uid'] != local_channel()) && (! \App::$is_sys))
+ return '';
+
+ if(! local_channel())
+ return '';
+
+ return website_portation_tools();
+ }
+}
diff --git a/Zotlabs/Widget/Wiki_list.php b/Zotlabs/Widget/Wiki_list.php
new file mode 100644
index 000000000..62f32dbf0
--- /dev/null
+++ b/Zotlabs/Widget/Wiki_list.php
@@ -0,0 +1,23 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Wiki_list {
+
+ function widget($arr) {
+
+ $channel = channelx_by_n(\App::$profile_uid);
+
+ $wikis = \Zotlabs\Lib\NativeWiki::listwikis($channel,get_observer_hash());
+
+ if($wikis) {
+ return replace_macros(get_markup_template('wikilist_widget.tpl'), array(
+ '$header' => t('Wiki List'),
+ '$channel' => $channel['channel_address'],
+ '$wikis' => $wikis['wikis']
+ ));
+ }
+ return '';
+ }
+
+}
diff --git a/Zotlabs/Widget/Wiki_page_history.php b/Zotlabs/Widget/Wiki_page_history.php
new file mode 100644
index 000000000..dcec9a037
--- /dev/null
+++ b/Zotlabs/Widget/Wiki_page_history.php
@@ -0,0 +1,27 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Wiki_page_history {
+
+ function widget($arr) {
+
+ $pageUrlName = ((array_key_exists('pageUrlName', $arr)) ? $arr['pageUrlName'] : '');
+ $resource_id = ((array_key_exists('resource_id', $arr)) ? $arr['resource_id'] : '');
+
+ $pageHistory = \Zotlabs\Lib\NativeWikiPage::page_history([
+ 'channel_id' => \App::$profile_uid,
+ 'observer_hash' => get_observer_hash(),
+ 'resource_id' => $resource_id,
+ 'pageUrlName' => $pageUrlName
+ ]);
+
+ return replace_macros(get_markup_template('nwiki_page_history.tpl'), array(
+ '$pageHistory' => $pageHistory['history'],
+ '$permsWrite' => $arr['permsWrite'],
+ '$name_lbl' => t('Name'),
+ '$msg_label' => t('Message','wiki_history')
+ ));
+
+ }
+}
diff --git a/Zotlabs/Widget/Wiki_pages.php b/Zotlabs/Widget/Wiki_pages.php
new file mode 100644
index 000000000..ac44b8d88
--- /dev/null
+++ b/Zotlabs/Widget/Wiki_pages.php
@@ -0,0 +1,66 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+
+class Wiki_pages {
+
+ function widget($arr) {
+
+ if(argc() < 3)
+ return;
+
+ if(! $arr['resource_id']) {
+ $c = channelx_by_nick(argv(1));
+ $w = \Zotlabs\Lib\NativeWiki::exists_by_name($c['channel_id'],argv(2));
+ $arr = array(
+ 'resource_id' => $w['resource_id'],
+ 'channel_id' => $c['channel_id'],
+ 'channel_address' => $c['channel_address'],
+ 'refresh' => false
+ );
+ }
+
+ $wikiname = '';
+
+ $pages = array();
+
+ $p = \Zotlabs\Lib\NativeWikiPage::page_list($arr['channel_id'],get_observer_hash(),$arr['resource_id']);
+
+ if($p['pages']) {
+ $pages = $p['pages'];
+ $w = $p['wiki'];
+ // Wiki item record is $w['wiki']
+ $wikiname = $w['urlName'];
+ if (!$wikiname) {
+ $wikiname = '';
+ }
+ $typelock = $w['typelock'];
+ }
+
+ $can_create = perm_is_allowed(\App::$profile['uid'],get_observer_hash(),'write_wiki');
+
+ $can_delete = ((local_channel() && (local_channel() == \App::$profile['uid'])) ? true : false);
+
+ return replace_macros(get_markup_template('wiki_page_list.tpl'), array(
+ '$resource_id' => $arr['resource_id'],
+ '$header' => t('Wiki Pages'),
+ '$channel_address' => $arr['channel_address'],
+ '$wikiname' => $wikiname,
+ '$pages' => $pages,
+ '$canadd' => $can_create,
+ '$candel' => $can_delete,
+ '$addnew' => t('Add new page'),
+ '$typelock' => $typelock,
+ '$lockedtype' => $w['mimeType'],
+ '$mimetype' => mimetype_select(0,$w['mimeType'],
+ [ 'text/markdown' => t('Markdown'), 'text/bbcode' => t('BBcode'), 'text/plain' => t('Text') ]),
+ '$pageName' => array('pageName', t('Page name')),
+ '$refresh' => $arr['refresh'],
+ '$options' => t('Options'),
+ '$submit' => t('Submit')
+ ));
+ }
+}
+
+
diff --git a/Zotlabs/Widget/Zcard.php b/Zotlabs/Widget/Zcard.php
new file mode 100644
index 000000000..12e53eaab
--- /dev/null
+++ b/Zotlabs/Widget/Zcard.php
@@ -0,0 +1,11 @@
+<?php
+
+namespace Zotlabs\Widget;
+
+class Zcard {
+
+ function widget($args) {
+ $channel = channelx_by_n(\App::$profile_uid);
+ return get_zcard($channel,get_observer_hash(),array('width' => 875));
+ }
+}
diff --git a/Zotlabs/Zot/Auth.php b/Zotlabs/Zot/Auth.php
index d4d3bee1d..8d198f506 100644
--- a/Zotlabs/Zot/Auth.php
+++ b/Zotlabs/Zot/Auth.php
@@ -43,6 +43,12 @@ class Auth {
$this->Finalise();
}
+ if(strpbrk($this->sec,'.:')) {
+ logger('illegal security context');
+ $this->Debug('illegal security context.');
+ $this->Finalise();
+ }
+
$x = $this->GetHublocs($this->address);
if($x) {
@@ -109,6 +115,14 @@ class Auth {
$this->remote_hub = $hubloc['hubloc_url'];
$this->dnt = 0;
+ if(! $this->sec) {
+ logger('missing security context.');
+ if($this->test)
+ $this->Debug('missing security context.');
+ return false;
+ }
+
+
// check credentials and access
// If they are already authenticated and haven't changed credentials,
@@ -176,7 +190,7 @@ class Auth {
return false;
}
- $this->Debug('auth check request returned .' . print_r($j, true));
+ $this->Debug('auth check request returned ' . print_r($j, true));
if(! $j['success'])
return false;
diff --git a/Zotlabs/Zot/Finger.php b/Zotlabs/Zot/Finger.php
index 7e0f5fb7c..348171bdc 100644
--- a/Zotlabs/Zot/Finger.php
+++ b/Zotlabs/Zot/Finger.php
@@ -22,6 +22,7 @@ class Finger {
*
* @return zotinfo array (with 'success' => true) or array('success' => false);
*/
+
static public function run($webbie, $channel = null, $autofallback = true) {
$ret = array('success' => false);
@@ -84,18 +85,27 @@ class Finger {
'token' => self::$token
);
- $result = z_post_url($url . $rhs,$postvars);
+ $headers = [];
+ $headers['X-Zot-Channel'] = $channel['channel_address'] . '@' . \App::get_hostname();
+ $headers['X-Zot-Nonce'] = random_string();
+ $xhead = \Zotlabs\Web\HTTPSig::create_sig('',$headers,$channel['channel_prvkey'],
+ 'acct:' . $channel['channel_address'] . '@' . \App::get_hostname(),false);
+
+ $retries = 0;
+
+ $result = z_post_url($url . $rhs,$postvars,$retries, [ 'headers' => $xhead ]);
if ((! $result['success']) && ($autofallback)) {
if ($https) {
logger('zot_finger: https failed. falling back to http');
- $result = z_post_url('http://' . $host . $rhs,$postvars);
+ $result = z_post_url('http://' . $host . $rhs,$postvars, $retries, [ 'headers' => $xhead ]);
}
}
- } else {
+ }
+ else {
$rhs .= '?f=&address=' . urlencode($address) . '&token=' . self::$token;
- $result = z_fetch_url($url . $rhs);
+ $result = z_fetch_url($url . $rhs);
if((! $result['success']) && ($autofallback)) {
if($https) {
logger('zot_finger: https failed. falling back to http');
@@ -111,7 +121,10 @@ class Finger {
}
$x = json_decode($result['body'], true);
- if($x) {
+
+ $verify = \Zotlabs\Web\HTTPSig::verify($result,(($x) ? $x['key'] : ''));
+
+ if($x && (! $verify['header_valid'])) {
$signed_token = ((is_array($x) && array_key_exists('signed_token', $x)) ? $x['signed_token'] : null);
if($signed_token) {
$valid = rsa_verify('token.' . self::$token, base64url_decode($signed_token), $x['key']);
@@ -123,9 +136,7 @@ class Finger {
}
else {
logger('No signed token from ' . $url . $rhs, LOGGER_NORMAL, LOG_WARNING);
- // after 2017-01-01 this will be a hard error unless you over-ride it.
- if((time() > 1483228800) && (! get_config('system', 'allow_unsigned_zotfinger')))
- return $ret;
+ return $ret;
}
}
diff --git a/Zotlabs/Zot/IHandler.php b/Zotlabs/Zot/IHandler.php
index eeca1555c..dd82f5be6 100644
--- a/Zotlabs/Zot/IHandler.php
+++ b/Zotlabs/Zot/IHandler.php
@@ -12,6 +12,8 @@ interface IHandler {
function Request($data);
+ function Rekey($sender,$data);
+
function AuthCheck($data,$encrypted);
function Purge($sender,$recipients);
diff --git a/Zotlabs/Zot/Receiver.php b/Zotlabs/Zot/Receiver.php
index 71d57eb35..c521c9d64 100644
--- a/Zotlabs/Zot/Receiver.php
+++ b/Zotlabs/Zot/Receiver.php
@@ -120,6 +120,10 @@ class Receiver {
$this->handler->Notify($this->data);
break;
+ case 'rekey':
+ $this->handler->Rekey($this->sender, $this->data);
+ break;
+
default:
$this->response['message'] = 'Not implemented';
json_return_and_die($this->response);
@@ -138,7 +142,6 @@ class Receiver {
* This packet is optionally encrypted, which we will discover if the json has an 'iv' element.
* $contents => array( 'alg' => 'aes256cbc', 'iv' => initialisation vector, 'key' => decryption key, 'data' => encrypted data);
* $contents->iv and $contents->key are random strings encrypted with this site's RSA public key and then base64url encoded.
- * Currently only 'aes256cbc' is used, but this is extensible should that algorithm prove inadequate.
*
* Once decrypted, one will find the normal json_encoded zot message packet.
*
@@ -156,7 +159,8 @@ class Receiver {
* },
* "recipients": { optional recipient array },
* "callback":"\/post",
- * "version":1,
+ * "version":"1.2",
+ * "encryption":["aes256cbc"],
* "secret":"1eaa...",
* "secret_sig": "df89025470fac8..."
* }
diff --git a/Zotlabs/Zot/Verify.php b/Zotlabs/Zot/Verify.php
index 06bd3188c..1d9e6de3f 100644
--- a/Zotlabs/Zot/Verify.php
+++ b/Zotlabs/Zot/Verify.php
@@ -31,6 +31,22 @@ class Verify {
return false;
}
+
+ function get_meta($type,$channel_id,$token) {
+ $r = q("select id, meta from verify where vtype = '%s' and channel = %d and token = '%s' limit 1",
+ dbesc($type),
+ intval($channel_id),
+ dbesc($token)
+ );
+ if($r) {
+ q("delete from verify where id = %d",
+ intval($r[0]['id'])
+ );
+ return $r[0]['meta'];
+ }
+ return false;
+ }
+
function purge($type,$interval) {
q("delete from verify where vtype = '%s' and created < %s - INTERVAL %s",
dbesc($type),
diff --git a/Zotlabs/Zot/ZotHandler.php b/Zotlabs/Zot/ZotHandler.php
index aab336545..ab8815b3d 100644
--- a/Zotlabs/Zot/ZotHandler.php
+++ b/Zotlabs/Zot/ZotHandler.php
@@ -20,6 +20,10 @@ class ZotHandler implements IHandler {
zot_reply_message_request($data);
}
+ function Rekey($sender,$data) {
+ zot_rekey_request($sender,$data);
+ }
+
function AuthCheck($data,$encrypted) {
zot_reply_auth_check($data,$encrypted);
}
diff --git a/app/admin.apd b/app/admin.apd
new file mode 100644
index 000000000..68c07568e
--- /dev/null
+++ b/app/admin.apd
@@ -0,0 +1,6 @@
+version: 1
+url: $baseurl/admin
+requires: admin
+name: Admin
+photo: icon:wrench
+categories: nav_featured_app
diff --git a/app/admin.png b/app/admin.png
deleted file mode 100644
index cde922e8e..000000000
--- a/app/admin.png
+++ /dev/null
Binary files differ
diff --git a/app/caldav.apd b/app/caldav.apd
new file mode 100644
index 000000000..a5839fd6e
--- /dev/null
+++ b/app/caldav.apd
@@ -0,0 +1,6 @@
+version: 1
+url: $baseurl/cdav/calendar
+requires: local_channel
+name: CalDAV
+photo: icon:calendar
+categories: Productivity, Personal
diff --git a/app/carddav.apd b/app/carddav.apd
new file mode 100644
index 000000000..3b60ebcfe
--- /dev/null
+++ b/app/carddav.apd
@@ -0,0 +1,6 @@
+version: 1
+url: $baseurl/cdav/addressbook
+requires: local_channel
+name: CardDAV
+photo: icon:vcard-o
+categories: Productivity, Personal
diff --git a/app/cards.apd b/app/cards.apd
new file mode 100644
index 000000000..047aaeac9
--- /dev/null
+++ b/app/cards.apd
@@ -0,0 +1,6 @@
+version: 1.1
+url: $baseurl/cards/$nick
+name: Cards
+requires: local_channel, cards
+photo: icon:list
+categories: Productivity
diff --git a/app/features.apd b/app/features.apd
deleted file mode 100644
index bffbdffec..000000000
--- a/app/features.apd
+++ /dev/null
@@ -1,6 +0,0 @@
-version: 1
-url: $baseurl/settings/features
-requires: local_channel
-name: Features
-photo: icon:cogs
-categories: System
diff --git a/app/features.png b/app/features.png
deleted file mode 100644
index 5faf14bc3..000000000
--- a/app/features.png
+++ /dev/null
Binary files differ
diff --git a/app/login.apd b/app/login.apd
deleted file mode 100644
index 1cbb44f1b..000000000
--- a/app/login.apd
+++ /dev/null
@@ -1,5 +0,0 @@
-version: 1
-url: $baseurl/login
-requires: nologin
-name: Login
-photo: icon:sign-in
diff --git a/app/manage.apd b/app/manage.apd
deleted file mode 100644
index b525efa6c..000000000
--- a/app/manage.apd
+++ /dev/null
@@ -1,6 +0,0 @@
-version: 1
-url: $baseurl/manage
-requires: local_channel
-name: Channel Manager
-photo: icon:id-card-o
-categories: Personal
diff --git a/app/manage.png b/app/manage.png
deleted file mode 100644
index 38a4dcbae..000000000
--- a/app/manage.png
+++ /dev/null
Binary files differ
diff --git a/app/photos.apd b/app/photos.apd
index 7a7a4b7b6..048e623bb 100644
--- a/app/photos.apd
+++ b/app/photos.apd
@@ -3,4 +3,4 @@ url: $baseurl/photos/$nick
requires: local_channel
name: Photos
photo: icon:photo
-categories: Multimedia
+categories: nav_featured_app, Multimedia
diff --git a/app/profile.apd b/app/profile.apd
deleted file mode 100644
index c8205df63..000000000
--- a/app/profile.apd
+++ /dev/null
@@ -1,6 +0,0 @@
-version: 1
-url: $baseurl/profile/$nick
-requires: local_channel
-name: View Profile
-photo: icon:user
-categories: Personal
diff --git a/app/profile.png b/app/profile.png
deleted file mode 100644
index e6e137c82..000000000
--- a/app/profile.png
+++ /dev/null
Binary files differ
diff --git a/app/pubstream.apd b/app/pubstream.apd
new file mode 100644
index 000000000..ebfcf38b0
--- /dev/null
+++ b/app/pubstream.apd
@@ -0,0 +1,6 @@
+version: 2
+url: $baseurl/pubstream
+requires: config:disable_discover_tab=0
+name: Public Stream
+photo: icon:globe
+categories: Social
diff --git a/app/settings.apd b/app/settings.apd
deleted file mode 100644
index b244f6774..000000000
--- a/app/settings.apd
+++ /dev/null
@@ -1,6 +0,0 @@
-version: 1
-url: $baseurl/settings
-requires: local_channel
-name: Settings
-photo: icon:cog
-categories: System
diff --git a/app/settings.png b/app/settings.png
deleted file mode 100644
index 2ba11a79a..000000000
--- a/app/settings.png
+++ /dev/null
Binary files differ
diff --git a/app/storage.apd b/app/storage.apd
index 7dcbcc089..cafcf81e8 100644
--- a/app/storage.apd
+++ b/app/storage.apd
@@ -3,4 +3,4 @@ url: $baseurl/cloud/$nick
requires: local_channel
name: Files
photo: icon:folder-open
-categories: Productivity
+categories: nav_featured_app, Productivity
diff --git a/boot.php b/boot.php
index 127a45065..9238b38f0 100755
--- a/boot.php
+++ b/boot.php
@@ -5,14 +5,13 @@
*/
/**
- * Hubzilla.
*
- * Hubzilla is an open source decentralised communications
+ * This is an open source decentralised communications
* platform combined with a decentralised identity/authentication framework
* wrapped in an extensible content management system, providing website designers
* the ability to embed fully decentralised communications and social tools
* into many traditional website designs (blogs, forums, small business
- * websites, charitable organisations, etc.). Hubzilla also provides DNS mobility
+ * websites, charitable organisations, etc.). Also provided is DNS mobility
* and internet scale privacy/access control.
*
* This allows any individual website to participate in a matrix of linked
@@ -47,13 +46,13 @@ require_once('include/account.php');
require_once('include/zid.php');
require_once('include/xchan.php');
require_once('include/hubloc.php');
-
+require_once('include/attach.php');
define ( 'PLATFORM_NAME', 'hubzilla' );
-define ( 'STD_VERSION', '2.1' );
-define ( 'ZOT_REVISION', '1.2' );
+define ( 'STD_VERSION', '2.9' );
+define ( 'ZOT_REVISION', '1.3' );
-define ( 'DB_UPDATE_VERSION', 1188 );
+define ( 'DB_UPDATE_VERSION', 1197 );
define ( 'PROJECT_BASE', __DIR__ );
@@ -65,7 +64,7 @@ define ( 'PROJECT_BASE', __DIR__ );
* This can be used in HTML and JavaScript where needed a line break.
*/
define ( 'EOL', '<br>' . "\r\n" );
-define ( 'ATOM_TIME', 'Y-m-d\TH:i:s\Z' );
+define ( 'ATOM_TIME', 'Y-m-d\\TH:i:s\\Z' ); // aka ISO 8601 "Zulu"
define ( 'TEMPLATE_BUILD_PATH', 'store/[data]/smarty3' );
define ( 'DIRECTORY_MODE_NORMAL', 0x0000); // A directory client
@@ -79,14 +78,12 @@ define ( 'DIRECTORY_MODE_STANDALONE', 0x0100); // A detached (off the grid) hub
// point to go out and find the rest of the world.
define ( 'DIRECTORY_REALM', 'RED_GLOBAL');
-define ( 'DIRECTORY_FALLBACK_MASTER', 'https://hub.pixelbits.de');
+define ( 'DIRECTORY_FALLBACK_MASTER', 'https://gravizot.de');
-$DIRECTORY_FALLBACK_SERVERS = array(
- 'https://hubzilla.site',
+$DIRECTORY_FALLBACK_SERVERS = array(
'https://hubzilla.zottel.net',
- 'https://hub.pixelbits.de',
'https://my.federated.social',
- 'https://hubzilla.nl',
+ //'https://hubzilla.nl',
'https://gravizot.de'
);
@@ -127,7 +124,9 @@ define ( 'LANGUAGE_DETECT_MIN_CONFIDENCE', 0.01 );
* either more or less restrictive.
*/
-define ( 'STORAGE_DEFAULT_PERMISSIONS', 0770 );
+if(! defined('STORAGE_DEFAULT_PERMISSIONS')) {
+ define ( 'STORAGE_DEFAULT_PERMISSIONS', 0770 );
+}
/**
@@ -150,12 +149,6 @@ define ( 'MAX_IMAGE_LENGTH', -1 );
/**
- * Not yet used
- */
-
-define ( 'DEFAULT_DB_ENGINE', 'MyISAM' );
-
-/**
* log levels
*/
@@ -167,14 +160,6 @@ define ( 'LOGGER_ALL', 4 );
/**
- * Server roles
- */
-
-define ( 'SERVER_ROLE_BASIC', 0x0001 );
-define ( 'SERVER_ROLE_STANDARD', 0x0002 );
-define ( 'SERVER_ROLE_PRO', 0x0004 );
-
-/**
* registration policies
*/
@@ -193,15 +178,6 @@ define ( 'ACCESS_FREE', 2 );
define ( 'ACCESS_TIERED', 3 );
/**
- * relationship types
- */
-
-define ( 'CONTACT_IS_FOLLOWER', 1);
-define ( 'CONTACT_IS_SHARING', 2);
-define ( 'CONTACT_IS_FRIEND', 3);
-
-
-/**
* DB update return values
*/
@@ -229,7 +205,7 @@ define ( 'PAGE_PREMIUM', 0x0010 );
define ( 'PAGE_ADULT', 0x0020 );
define ( 'PAGE_CENSORED', 0x0040 ); // Site admin has blocked this channel from appearing in casual search results and site feeds
define ( 'PAGE_SYSTEM', 0x1000 );
-define ( 'PAGE_HUBADMIN', 0x2000 ); // set this to indicate a preferred admin channel rather than the
+define ( 'PAGE_HUBADMIN', 0x2000 ); // set this to indicate a preferred admin channel rather than the
// default channel of any accounts with the admin role.
define ( 'PAGE_REMOVED', 0x8000 );
@@ -280,6 +256,7 @@ define ( 'NETWORK_OSTATUS', 'stat'); // status.net, identi.ca, GNU-s
define ( 'NETWORK_GNUSOCIAL', 'gnusoc'); // status.net, identi.ca, GNU-social, other OStatus implementations
define ( 'NETWORK_FEED', 'rss'); // RSS/Atom feeds with no known "post/notify" protocol
define ( 'NETWORK_DIASPORA', 'diaspora'); // Diaspora
+define ( 'NETWORK_ACTIVITYPUB', 'activitypub');
define ( 'NETWORK_MAIL', 'mail'); // IMAP/POP
define ( 'NETWORK_MAIL2', 'mai2'); // extended IMAP/POP
define ( 'NETWORK_FACEBOOK', 'face'); // Facebook API
@@ -426,6 +403,8 @@ define ( 'VNOTIFY_INFO', 0x0080 );
define ( 'VNOTIFY_ALERT', 0x0100 );
define ( 'VNOTIFY_INTRO', 0x0200 );
define ( 'VNOTIFY_REGISTER', 0x0400 );
+define ( 'VNOTIFY_FILES', 0x0800 );
+define ( 'VNOTIFY_PUBS', 0x1000 );
@@ -444,6 +423,7 @@ define ( 'TERM_THING', 7 );
define ( 'TERM_BOOKMARK', 8 );
define ( 'TERM_HIERARCHY', 9 );
define ( 'TERM_COMMUNITYTAG', 10 );
+define ( 'TERM_FORUM', 11 );
define ( 'TERM_OBJ_POST', 1 );
define ( 'TERM_OBJ_PHOTO', 2 );
@@ -475,10 +455,23 @@ define ( 'NAMESPACE_STATUSNET', 'http://status.net/schema/api/1/' );
define ( 'NAMESPACE_ATOM1', 'http://www.w3.org/2005/Atom' );
define ( 'NAMESPACE_YMEDIA', 'http://search.yahoo.com/mrss/' );
+// We should be using versioned jsonld contexts so that signatures will be slightly more reliable.
+// Why signatures are unreliable by design is a problem nobody seems to care about
+// "because it's a proposed W3C standard". .
+
+// Anyway, if you use versioned contexts, communication with Mastodon fails. Have not yet investigated
+// the reason for the dependency but for the current time, use the standard non-versioned context.
+//define ( 'ACTIVITYSTREAMS_JSONLD_REV', 'https://www.w3.org/ns/activitystreams-history/v1.8.jsonld' );
+
+define ( 'ACTIVITYSTREAMS_JSONLD_REV', 'https://www.w3.org/ns/activitystreams' );
+
+define ( 'ZOT_APSCHEMA_REV', '/apschema/v1.2' );
/**
* activity stream defines
*/
+define ( 'ACTIVITY_PUBLIC_INBOX', 'https://www.w3.org/ns/activitystreams#Public' );
+
define ( 'ACTIVITY_REACT', NAMESPACE_ZOT . '/activity/react' );
define ( 'ACTIVITY_LIKE', NAMESPACE_ACTIVITY_SCHEMA . 'like' );
define ( 'ACTIVITY_DISLIKE', NAMESPACE_ZOT . '/activity/dislike' );
@@ -501,8 +494,10 @@ define ( 'ACTIVITY_JOIN', NAMESPACE_ACTIVITY_SCHEMA . 'join' );
define ( 'ACTIVITY_POST', NAMESPACE_ACTIVITY_SCHEMA . 'post' );
define ( 'ACTIVITY_UPDATE', NAMESPACE_ACTIVITY_SCHEMA . 'update' );
define ( 'ACTIVITY_TAG', NAMESPACE_ACTIVITY_SCHEMA . 'tag' );
+define ( 'ACTIVITY_SHARE', NAMESPACE_ACTIVITY_SCHEMA . 'share' );
define ( 'ACTIVITY_FAVORITE', NAMESPACE_ACTIVITY_SCHEMA . 'favorite' );
define ( 'ACTIVITY_CREATE', NAMESPACE_ACTIVITY_SCHEMA . 'create' );
+define ( 'ACTIVITY_DELETE', NAMESPACE_ACTIVITY_SCHEMA . 'delete' );
define ( 'ACTIVITY_WIN', NAMESPACE_ACTIVITY_SCHEMA . 'win' );
define ( 'ACTIVITY_LOSE', NAMESPACE_ACTIVITY_SCHEMA . 'lose' );
define ( 'ACTIVITY_TIE', NAMESPACE_ACTIVITY_SCHEMA . 'tie' );
@@ -512,6 +507,7 @@ define ( 'ACTIVITY_POKE', NAMESPACE_ZOT . '/activity/poke' );
define ( 'ACTIVITY_MOOD', NAMESPACE_ZOT . '/activity/mood' );
define ( 'ACTIVITY_OBJ_COMMENT', NAMESPACE_ACTIVITY_SCHEMA . 'comment' );
+define ( 'ACTIVITY_OBJ_ACTIVITY',NAMESPACE_ACTIVITY_SCHEMA . 'activity' );
define ( 'ACTIVITY_OBJ_NOTE', NAMESPACE_ACTIVITY_SCHEMA . 'note' );
define ( 'ACTIVITY_OBJ_PERSON', NAMESPACE_ACTIVITY_SCHEMA . 'person' );
define ( 'ACTIVITY_OBJ_PHOTO', NAMESPACE_ACTIVITY_SCHEMA . 'photo' );
@@ -526,14 +522,7 @@ define ( 'ACTIVITY_OBJ_PROFILE', NAMESPACE_ZOT . '/activity/profile' );
define ( 'ACTIVITY_OBJ_THING', NAMESPACE_ZOT . '/activity/thing' );
define ( 'ACTIVITY_OBJ_LOCATION',NAMESPACE_ZOT . '/activity/location' );
define ( 'ACTIVITY_OBJ_FILE', NAMESPACE_ZOT . '/activity/file' );
-
-/**
- * item weight for query ordering
- */
-
-define ( 'GRAVITY_PARENT', 0);
-define ( 'GRAVITY_LIKE', 3);
-define ( 'GRAVITY_COMMENT', 6);
+define ( 'ACTIVITY_OBJ_CARD', NAMESPACE_ZOT . '/activity/card' );
/**
* Account Flags
@@ -550,7 +539,6 @@ define ( 'ACCOUNT_PENDING', 0x0010 );
* Account roles
*/
-define ( 'ACCOUNT_ROLE_ALLOWCODE', 0x0001 );
define ( 'ACCOUNT_ROLE_SYSTEM', 0x0002 );
define ( 'ACCOUNT_ROLE_DEVELOPER', 0x0004 );
define ( 'ACCOUNT_ROLE_ADMIN', 0x1000 );
@@ -560,19 +548,21 @@ define ( 'ACCOUNT_ROLE_ADMIN', 0x1000 );
*/
define ( 'ITEM_VISIBLE', 0x0000);
-//define ( 'ITEM_HIDDEN', 0x0001);
+define ( 'ITEM_HIDDEN', 0x0001);
define ( 'ITEM_BLOCKED', 0x0002);
define ( 'ITEM_MODERATED', 0x0004);
define ( 'ITEM_SPAM', 0x0008);
-//define ( 'ITEM_DELETED', 0x0010);
+define ( 'ITEM_DELETED', 0x0010);
define ( 'ITEM_UNPUBLISHED', 0x0020);
-//define ( 'ITEM_WEBPAGE', 0x0040); // is a static web page, not a conversational item
+define ( 'ITEM_WEBPAGE', 0x0040); // is a static web page, not a conversational item
define ( 'ITEM_DELAYED_PUBLISH', 0x0080);
define ( 'ITEM_BUILDBLOCK', 0x0100); // Named thusly to make sure nobody confuses this with ITEM_BLOCKED
-//define ( 'ITEM_PDL', 0x0200); // Page Description Language - e.g. Comanche
+define ( 'ITEM_PDL', 0x0200); // Page Description Language - e.g. Comanche
define ( 'ITEM_BUG', 0x0400); // Is a bug, can be used by the internal bug tracker
define ( 'ITEM_PENDING_REMOVE', 0x0800); // deleted, notification period has lapsed
define ( 'ITEM_DOC', 0x1000); // hubzilla only, define here so that item import does the right thing
+define ( 'ITEM_CARD', 0x2000);
+
define ( 'ITEM_TYPE_POST', 0 );
define ( 'ITEM_TYPE_BLOCK', 1 );
@@ -580,6 +570,7 @@ define ( 'ITEM_TYPE_PDL', 2 );
define ( 'ITEM_TYPE_WEBPAGE', 3 );
define ( 'ITEM_TYPE_BUG', 4 );
define ( 'ITEM_TYPE_DOC', 5 );
+define ( 'ITEM_TYPE_CARD', 6 );
define ( 'ITEM_IS_STICKY', 1000 );
@@ -621,15 +612,7 @@ function sys_boot() {
$a->convert();
- if(defined('UNO')) {
- if(UNO)
- App::$config['system']['server_role'] = 'basic';
- else
- App::$config['system']['server_role'] = 'standard';
- }
-
- if(! (array_key_exists('server_role',App::$config['system']) && App::$config['system']['server_role']))
- App::$config['system']['server_role'] = 'standard';
+ App::$config['system']['server_role'] = 'pro';
App::$timezone = ((App::$config['system']['timezone']) ? App::$config['system']['timezone'] : 'UTC');
date_default_timezone_set(App::$timezone);
@@ -640,12 +623,10 @@ function sys_boot() {
}
if(! defined('DEFAULT_NOTIFY_ICON')) {
- define( 'DEFAULT_NOTIFY_ICON', '/images/hz-white-32.png' );
+ define( 'DEFAULT_NOTIFY_ICON', '/images/hz-white-64.png' );
}
- if(! defined('CRYPTO_ALGORITHM')) {
- define( 'CRYPTO_ALGORITHM', 'aes256cbc' );
- }
+ App::head_set_icon(DEFAULT_PLATFORM_ICON);
/*
* Try to open the database;
@@ -728,6 +709,7 @@ function startup() {
* which is now static (although currently constructed at startup). We are only converting
* 'system' config settings.
*/
+
class miniApp {
public $config = array('system' => array());
@@ -756,7 +738,6 @@ class miniApp {
class App {
public static $install = false; // true if we are installing the software
- public static $role = 0; // server role (constant, not the string)
public static $account = null; // account record of the logged-in account
public static $channel = null; // channel record of the current channel of the logged-in account
public static $observer = null; // xchan record of the page observer
@@ -810,6 +791,10 @@ class App {
public static $is_tablet = false;
public static $comanche;
+
+ public static $channel_links;
+
+
public static $category;
// Allow themes to control internal parameters
@@ -937,11 +922,19 @@ class App {
*
* There will always be one argument. If provided a naked domain
* URL, self::$argv[0] is set to "home".
+ *
+ * If $argv[0] has a period in it, for example foo.json; rewrite
+ * to module = 'foo' and set $_REQUEST['module_format'] = 'json';
*/
self::$argv = explode('/', self::$cmd);
self::$argc = count(self::$argv);
if ((array_key_exists('0', self::$argv)) && strlen(self::$argv[0])) {
+ if(strpos(self::$argv[0],'.')) {
+ $_REQUEST['module_format'] = substr(self::$argv[0],strpos(self::$argv[0],'.')+1);
+ self::$argv[0] = substr(self::$argv[0],0,strpos(self::$argv[0],'.'));
+ }
+
self::$module = str_replace(".", "_", self::$argv[0]);
self::$module = str_replace("-", "_", self::$module);
if(strpos(self::$module,'_') === 0)
@@ -952,6 +945,7 @@ class App {
self::$module = 'home';
}
+
/*
* See if there is any page number information, and initialise
* pagination
@@ -972,8 +966,6 @@ class App {
self::$is_mobile = $mobile_detect->isMobile();
self::$is_tablet = $mobile_detect->isTablet();
- self::head_set_icon(DEFAULT_PLATFORM_ICON);
-
/*
* register template engines
*/
@@ -1031,36 +1023,10 @@ class App {
}
}
- public static function get_role() {
- if(! self::$role)
- return self::set_role();
- return self::$role;
- }
-
- public static function set_role() {
- $role_str = \Zotlabs\Lib\System::get_server_role();
- switch($role_str) {
- case 'basic':
- $role = SERVER_ROLE_BASIC;
- break;
- case 'pro':
- $role = SERVER_ROLE_PRO;
- break;
- case 'standard':
- default:
- $role = SERVER_ROLE_STANDARD;
- break;
- }
- self::$role = $role;
- return $role;
- }
-
-
public static function get_scheme() {
return self::$scheme;
}
-
public static function get_hostname() {
return self::$hostname;
}
@@ -1077,6 +1043,19 @@ class App {
return self::$path;
}
+ public static function get_channel_links() {
+ $s = '';
+ $x = self::$channel_links;
+ if($x && is_array($x) && count($x)) {
+ foreach($x as $y) {
+ if($s) {
+ $s .= ',';
+ }
+ $s .= '<' . $y['url'] . '>; rel="' . $y['rel'] . '"; type="' . $y['type'] . '"';
+ }
+ }
+ return $s;
+ }
public static function set_account($acct) {
self::$account = $acct;
}
@@ -1174,24 +1153,25 @@ class App {
* since the code added by the modules frequently depends on it
* being first
*/
- $tpl = get_markup_template('head.tpl');
- self::$page['htmlhead'] = replace_macros($tpl, array(
- '$preload_images' => $preload_images,
- '$user_scalable' => $user_scalable,
- '$query' => urlencode(self::$query_string),
- '$baseurl' => self::get_baseurl(),
- '$local_channel' => local_channel(),
- '$metas' => self::$meta->get(),
- '$plugins' => $x['header'],
- '$update_interval' => $interval,
- 'osearch' => sprintf( t('Search %1$s (%2$s)','opensearch'), Zotlabs\Lib\System::get_site_name(), t('$Projectname','opensearch')),
- '$head_css' => head_get_css(),
- '$head_js' => head_get_js(),
- '$linkrel' => head_get_links(),
- '$js_strings' => js_strings(),
- '$zid' => get_my_address(),
- '$channel_id' => self::$profile['uid'],
- )) . self::$page['htmlhead'];
+
+ self::$page['htmlhead'] = replace_macros(get_markup_template('head.tpl'),
+ [
+ '$preload_images' => $preload_images,
+ '$user_scalable' => $user_scalable,
+ '$query' => urlencode(self::$query_string),
+ '$baseurl' => self::get_baseurl(),
+ '$local_channel' => local_channel(),
+ '$metas' => self::$meta->get(),
+ '$plugins' => $x['header'],
+ '$update_interval' => $interval,
+ '$head_css' => head_get_css(),
+ '$head_js' => head_get_js(),
+ '$linkrel' => head_get_links(),
+ '$js_strings' => js_strings(),
+ '$zid' => get_my_address(),
+ '$channel_id' => self::$profile['uid']
+ ]
+ ) . self::$page['htmlhead'];
// always put main.js at the end
self::$page['htmlhead'] .= head_get_main_js();
@@ -1204,11 +1184,13 @@ class App {
* @param string $name
*/
public static function register_template_engine($class, $name = '') {
- if ($name === ""){
- $v = get_class_vars( $class );
- if(x($v, "name")) $name = $v['name'];
+ if(! $name) {
+ $v = get_class_vars($class);
+ if(x($v, "name")) {
+ $name = $v['name'];
+ }
}
- if ($name === ""){
+ if (! $name) {
echo "template engine <tt>$class</tt> cannot be registered without a name.\n";
killme();
}
@@ -1224,19 +1206,21 @@ class App {
* @return object Template Engine instance
*/
public static function template_engine($name = ''){
- if ($name !== "") {
+ if($name !== '') {
$template_engine = $name;
- } else {
+ }
+ else {
$template_engine = 'smarty3';
- if (x(self::$theme, 'template_engine')) {
+ if(x(self::$theme, 'template_engine')) {
$template_engine = self::$theme['template_engine'];
}
}
- if (isset(self::$template_engines[$template_engine])){
+ if(isset(self::$template_engines[$template_engine])){
if(isset(self::$template_engine_instance[$template_engine])){
return self::$template_engine_instance[$template_engine];
- } else {
+ }
+ else {
$class = self::$template_engines[$template_engine];
$obj = new $class;
self::$template_engine_instance[$template_engine] = $obj;
@@ -1244,7 +1228,8 @@ class App {
}
}
- echo "template engine <tt>$template_engine</tt> is not registered!\n"; killme();
+ echo "template engine <tt>$template_engine</tt> is not registered!\n";
+ killme();
}
/**
@@ -1283,18 +1268,6 @@ class App {
/**
- * @brief Retrieve the App structure.
- *
- * Useful in functions which require it but don't get it passed to them
- *
- * @return App
- */
-function get_app() {
- return $a;
-}
-
-
-/**
* @brief Multi-purpose function to check variable state.
*
* Usage: x($var) or $x($array, 'key')
@@ -1382,9 +1355,27 @@ function os_mkdir($path, $mode = 0777, $recursive = false) {
$oldumask = @umask(0);
$result = @mkdir($path, $mode, $recursive);
@umask($oldumask);
- return $result;
+ return $result;
+}
+
+
+// recursively delete a directory
+function rrmdir($path) {
+ if(is_dir($path) === true) {
+ $files = array_diff(scandir($path), array('.', '..'));
+ foreach($files as $file) {
+ rrmdir(realpath($path) . '/' . $file);
+ }
+ return rmdir($path);
+ }
+ elseif(is_file($path) === true) {
+ return unlink($path);
+ }
+
+ return false;
}
+
/**
* @brief Function to check if request was an AJAX (xmlhttprequest) request.
*
@@ -1399,11 +1390,7 @@ function is_ajax() {
// base url for use in cmdline programs which don't have
// $_SERVER variables, and synchronising the state of installed plugins.
-function check_config(&$a) {
-
- $build = get_config('system','db_version');
- if(! intval($build))
- $build = set_config('system','db_version',DB_UPDATE_VERSION);
+function check_config() {
$saved = get_config('system','urlverify');
if(! $saved)
@@ -1441,88 +1428,8 @@ function check_config(&$a) {
if (! $syschan_exists)
create_sys_channel();
- if($build != DB_UPDATE_VERSION) {
- $stored = intval($build);
- if(! $stored) {
- logger('Critical: check_config unable to determine database schema version');
- return;
- }
- $current = intval(DB_UPDATE_VERSION);
- if(($stored < $current) && file_exists('install/update.php')) {
-
- load_config('database');
-
- // We're reporting a different version than what is currently installed.
- // Run any existing update scripts to bring the database up to current.
- require_once('install/update.php');
-
- // make sure that boot.php and update.php are the same release, we might be
- // updating right this very second and the correct version of the update.php
- // file may not be here yet. This can happen on a very busy site.
-
- if(DB_UPDATE_VERSION == UPDATE_VERSION) {
- for($x = $stored; $x < $current; $x ++) {
- if(function_exists('update_r' . $x)) {
- // There could be a lot of processes running or about to run.
- // We want exactly one process to run the update command.
- // So store the fact that we're taking responsibility
- // after first checking to see if somebody else already has.
-
- // If the update fails or times-out completely you may need to
- // delete the config entry to try again.
-
- if(get_config('database','update_r' . $x))
- break;
- set_config('database','update_r' . $x, '1');
- // call the specific update
-
- $func = 'update_r' . $x;
- $retval = $func();
- if($retval) {
-
- // Prevent sending hundreds of thousands of emails by creating
- // a lockfile.
-
- $lockfile = 'store/[data]/mailsent';
-
- if ((file_exists($lockfile)) && (filemtime($lockfile) > (time() - 86400)))
- return;
- @unlink($lockfile);
- //send the administrator an e-mail
- file_put_contents($lockfile, $x);
-
- $r = q("select account_language from account where account_email = '%s' limit 1",
- dbesc(App::$config['system']['admin_email'])
- );
- push_lang(($r) ? $r[0]['account_language'] : 'en');
-
-
- $email_tpl = get_intltext_template("update_fail_eml.tpl");
- $email_msg = replace_macros($email_tpl, array(
- '$sitename' => App::$config['system']['sitename'],
- '$siteurl' => z_root(),
- '$update' => $x,
- '$error' => sprintf( t('Update %s failed. See error logs.'), $x)
- ));
-
- $subject = email_header_encode(sprintf(t('Update Error at %s'), z_root()));
-
- mail(App::$config['system']['admin_email'], $subject, $email_msg,
- 'From: Administrator' . '@' . $_SERVER['SERVER_NAME'] . "\n"
- . 'Content-type: text/plain; charset=UTF-8' . "\n"
- . 'Content-transfer-encoding: 8bit' );
- //try the logger
- logger('CRITICAL: Update Failed: ' . $x);
- pop_lang();
- }
- else
- set_config('database','update_r' . $x, 'success');
- }
- }
- set_config('system','db_version', DB_UPDATE_VERSION);
- }
- }
- }
+ $x = new \Zotlabs\Lib\DB_Upgrade(DB_UPDATE_VERSION);
+
/**
*
@@ -1730,6 +1637,7 @@ function login($register = false, $form_id = 'main-login', $hiddens=false, $logi
'$login_page' => $login_page,
'$logout' => t('Logout'),
'$login' => t('Login'),
+ '$remote_login' => t('Remote Authentication'),
'$form_id' => $form_id,
'$lname' => array('username', t('Login/Email') , '', ''),
'$lpassword' => array('password', t('Password'), '', ''),
@@ -1798,8 +1706,8 @@ function get_account_id() {
* @return int|bool channel_id or false
*/
function local_channel() {
- if(session_id()
- && array_key_exists('authenticated',$_SESSION) && $_SESSION['authenticated']
+ if(session_id()
+ && array_key_exists('authenticated',$_SESSION) && $_SESSION['authenticated']
&& array_key_exists('uid',$_SESSION) && intval($_SESSION['uid']))
return intval($_SESSION['uid']);
@@ -1807,18 +1715,6 @@ function local_channel() {
}
/**
- * local_user() got deprecated and replaced by local_channel().
- *
- * @deprecated since v2.1, use local_channel()
- * @see local_channel()
- */
-function local_user() {
- logger('local_user() is DEPRECATED, use local_channel()');
- return local_channel();
-}
-
-
-/**
* @brief Returns a xchan_hash (visitor_id) of remote authenticated visitor
* or false.
*
@@ -1831,8 +1727,8 @@ function local_user() {
* @return string|bool visitor_id or false
*/
function remote_channel() {
- if(session_id()
- && array_key_exists('authenticated',$_SESSION) && $_SESSION['authenticated']
+ if(session_id()
+ && array_key_exists('authenticated',$_SESSION) && $_SESSION['authenticated']
&& array_key_exists('visitor_id',$_SESSION) && $_SESSION['visitor_id'])
return $_SESSION['visitor_id'];
@@ -1840,18 +1736,6 @@ function remote_channel() {
}
/**
- * remote_user() got deprecated and replaced by remote_channel().
- *
- * @deprecated since v2.1, use remote_channel()
- * @see remote_channel()
- */
-function remote_user() {
- logger('remote_user() is DEPRECATED, use remote_channel()');
- return remote_channel();
-}
-
-
-/**
* Contents of $s are displayed prominently on the page the next time
* a page is loaded. Usually used for errors or alerts.
*
@@ -1863,8 +1747,8 @@ function notice($s) {
if(! x($_SESSION, 'sysmsg')) $_SESSION['sysmsg'] = array();
- // ignore duplicated error messages which haven't yet been displayed
- // - typically seen as multiple 'permission denied' messages
+ // ignore duplicated error messages which haven't yet been displayed
+ // - typically seen as multiple 'permission denied' messages
// as a result of auto-reloading a protected page with &JS=1
if(in_array($s,$_SESSION['sysmsg']))
@@ -1886,7 +1770,7 @@ function notice($s) {
function info($s) {
if(! session_id())
return;
- if(! x($_SESSION, 'sysmsg_info'))
+ if(! x($_SESSION, 'sysmsg_info'))
$_SESSION['sysmsg_info'] = array();
if(App::$interactive)
$_SESSION['sysmsg_info'][] = $s;
@@ -1962,7 +1846,7 @@ function proc_run(){
proc_close(proc_open($cmd, array(), $foo));
}
else {
- if(get_config('system','use_proc_open'))
+ if(get_config('system','use_proc_open'))
proc_close(proc_open($cmdline ." &", array(), $foo));
else
exec($cmdline . ' > /dev/null &');
@@ -1975,8 +1859,8 @@ function proc_run(){
* @return bool true if we run on M$ Windows
*
* It's possible you might be able to run on WAMP or XAMPP, and this
- * has been accomplished, but is not officially supported. Good luck.
- *
+ * has been accomplished, but is not officially supported. Good luck.
+ *
*/
function is_windows() {
return ((strtoupper(substr(PHP_OS, 0, 3)) === 'WIN') ? true : false);
@@ -2143,7 +2027,7 @@ function curPageURL() {
*
* @return mixed
*/
-function get_custom_nav(&$a, $navname) {
+function get_custom_nav($navname) {
if (! $navname)
return App::$page['nav'];
// load custom nav menu by name here
@@ -2155,9 +2039,8 @@ function get_custom_nav(&$a, $navname) {
* If there is no parsed Comanche template already load a module's pdl file
* and parse it with Comanche.
*
- * @param App &$a global application object
*/
-function load_pdl(&$a) {
+function load_pdl() {
App::$comanche = new Zotlabs\Render\Comanche();
@@ -2184,7 +2067,7 @@ function load_pdl(&$a) {
}
-function exec_pdl(&$a) {
+function exec_pdl() {
if(App::$pdl) {
App::$comanche->parse(App::$pdl,1);
}
@@ -2196,11 +2079,10 @@ function exec_pdl(&$a) {
*
* Build the page - now that we have all the components
*
- * @param App &$a global application object
*/
-function construct_page(&$a) {
+function construct_page() {
- exec_pdl($a);
+ exec_pdl();
$comanche = ((count(App::$layout)) ? true : false);
@@ -2208,17 +2090,23 @@ function construct_page(&$a) {
$installing = false;
+ $uid = ((App::$profile_uid) ? App::$profile_uid : local_channel());
+
+ $navbar = get_config('system','navbar','default');
+ if($uid) {
+ $navbar = get_pconfig($uid,'system','navbar',$navbar);
+ }
+
+ if($comanche && App::$layout['navbar']) {
+ $navbar = App::$layout['navbar'];
+ }
+
if (App::$module == 'setup') {
$installing = true;
} else {
- nav($a);
+ nav($navbar);
}
- if ($comanche) {
- if (App::$layout['nav']) {
- App::$page['nav'] = get_custom_nav($a, App::$layout['nav']);
- }
- }
$current_theme = Zotlabs\Render\Theme::current();
@@ -2226,7 +2114,7 @@ function construct_page(&$a) {
// Zotlabs\Render\Theme::debug();
if (($p = theme_include($current_theme[0] . '.js')) != '')
- head_add_js($p);
+ head_add_js('/' . $p);
if (($p = theme_include('mod_' . App::$module . '.php')) != '')
require_once($p);
@@ -2238,10 +2126,13 @@ function construct_page(&$a) {
else
head_add_css(((x(App::$page, 'template')) ? App::$page['template'] : 'default' ) . '.css');
- head_add_css('mod_' . App::$module . '.css');
+ if (($p = theme_include('mod_' . App::$module . '.css')) != '')
+ head_add_css('mod_' . App::$module . '.css');
+
head_add_css(Zotlabs\Render\Theme::url($installing));
- head_add_js('mod_' . App::$module . '.js');
+ if (($p = theme_include('mod_' . App::$module . '.js')) != '')
+ head_add_js('mod_' . App::$module . '.js');
App::build_pagehead();
@@ -2324,7 +2215,7 @@ function construct_page(&$a) {
if(App::$config['system']['x_security_headers']) {
header("X-Frame-Options: SAMEORIGIN");
header("X-Xss-Protection: 1; mode=block;");
- header("X-Content-Type-Options: nosniff");
+ header("X-Content-Type-Options: nosniff");
}
if(App::$config['system']['public_key_pins']) {
@@ -2337,7 +2228,7 @@ function construct_page(&$a) {
}
/**
- * @brief Returns Hubzilla's root directory.
+ * @brief Returns appplication root directory.
*
* @return string
*/
@@ -2353,7 +2244,7 @@ function appdirpath() {
function head_set_icon($icon) {
App::$data['pageicon'] = $icon;
-// logger('head_set_icon: ' . $icon);
+
}
/**
@@ -2429,37 +2320,38 @@ function z_get_temp_dir() {
function z_check_cert() {
if(strpos(z_root(),'https://') !== false) {
- $x = z_fetch_url(z_root() . '/siteinfo/json');
+ $x = z_fetch_url(z_root() . '/siteinfo.json');
if(! $x['success']) {
$recurse = 0;
- $y = z_fetch_url(z_root() . '/siteinfo/json',false,$recurse,array('novalidate' => true));
+ $y = z_fetch_url(z_root() . '/siteinfo.json',false,$recurse,array('novalidate' => true));
if($y['success'])
cert_bad_email();
}
}
-}
+}
/**
* @brief Send email to admin if server has an invalid certificate.
*
- * If a Hubzilla hub is available over https it must have a publicly valid
- * certificate.
+ * If a hub is available over https it must have a publicly valid certificate.
*/
-function cert_bad_email() {
- $email_tpl = get_intltext_template("cert_bad_eml.tpl");
- $email_msg = replace_macros($email_tpl, array(
- '$sitename' => App::$config['system']['sitename'],
- '$siteurl' => z_root(),
- '$error' => t('Website SSL certificate is not valid. Please correct.')
- ));
+function cert_bad_email() {
+ return z_mail(
+ [
+ 'toEmail' => \App::$config['system']['admin_email'],
+ 'messageSubject' => sprintf(t('[$Projectname] Website SSL error for %s'), App::get_hostname()),
+ 'textVersion' => replace_macros(get_intltext_template('cert_bad_eml.tpl'),
+ [
+ '$sitename' => App::$config['system']['sitename'],
+ '$siteurl' => z_root(),
+ '$error' => t('Website SSL certificate is not valid. Please correct.')
+ ]
+ )
+ ]
+ );
- $subject = email_header_encode(sprintf(t('[hubzilla] Website SSL error for %s'), App::get_hostname()));
- mail(App::$config['system']['admin_email'], $subject, $email_msg,
- 'From: Administrator' . '@' . App::get_hostname() . "\n"
- . 'Content-type: text/plain; charset=UTF-8' . "\n"
- . 'Content-transfer-encoding: 8bit' );
}
@@ -2545,7 +2437,7 @@ function check_for_new_perms() {
function check_cron_broken() {
$d = get_config('system','lastcron');
-
+
if((! $d) || ($d < datetime_convert('UTC','UTC','now - 4 hours'))) {
Zotlabs\Daemon\Master::Summon(array('Cron'));
set_config('system','lastcron',datetime_convert());
@@ -2570,29 +2462,28 @@ function check_cron_broken() {
return;
}
- $email_tpl = get_intltext_template("cron_bad_eml.tpl");
- $email_msg = replace_macros($email_tpl, array(
- '$sitename' => App::$config['system']['sitename'],
- '$siteurl' => z_root(),
- '$error' => t('Cron/Scheduled tasks not running.'),
- '$lastdate' => (($d)? $d : t('never'))
- ));
-
- $subject = email_header_encode(sprintf(t('[hubzilla] Cron tasks not running on %s'), App::get_hostname()));
- mail(App::$config['system']['admin_email'], $subject, $email_msg,
- 'From: Administrator' . '@' . App::get_hostname() . "\n"
- . 'Content-type: text/plain; charset=UTF-8' . "\n"
- . 'Content-transfer-encoding: 8bit' );
- return;
+ return z_mail(
+ [
+ 'toEmail' => \App::$config['system']['admin_email'],
+ 'messageSubject' => sprintf(t('[$Projectname] Cron tasks not running on %s'), App::get_hostname()),
+ 'textVersion' => replace_macros(get_intltext_template('cron_bad_eml.tpl'),
+ [
+ '$sitename' => App::$config['system']['sitename'],
+ '$siteurl' => z_root(),
+ '$error' => t('Cron/Scheduled tasks not running.'),
+ '$lastdate' => (($d)? $d : t('never'))
+ ]
+ )
+ ]
+ );
}
function observer_prohibited($allow_account = false) {
- if($allow_account)
+ if($allow_account)
return (((get_config('system','block_public')) && (! get_account_id()) && (! remote_channel())) ? true : false );
return (((get_config('system','block_public')) && (! local_channel()) && (! remote_channel())) ? true : false );
}
-
diff --git a/composer.json b/composer.json
index abf583875..e6bdba61c 100644
--- a/composer.json
+++ b/composer.json
@@ -28,14 +28,20 @@
"ext-mbstring" : "*",
"ext-xml" : "*",
"ext-openssl" : "*",
- "sabre/dav" : "~3.2"
+ "sabre/dav" : "~3.2",
+ "michelf/php-markdown" : "^1.7",
+ "bshaffer/oauth2-server-php": "^1.9",
+ "ezyang/htmlpurifier": "^4.9",
+ "simplepie/simplepie": "~1.5",
+ "league/html-to-markdown": "^4.4"
},
"require-dev" : {
- "php" : ">=5.6",
- "phpunit/phpunit" : "^5.6",
+ "php" : ">=7.0",
+ "phpunit/phpunit" : "^6.1",
"behat/behat" : "@stable",
"behat/mink-extension": "@stable",
- "behat/mink-goutte-driver": "@stable"
+ "behat/mink-goutte-driver": "@stable",
+ "php-mock/php-mock-phpunit": "^2.0"
},
"autoload" : {
"psr-4" : {
@@ -50,6 +56,11 @@
},
"minimum-stability" : "stable",
"config" : {
- "notify-on-install" : false
- }
-} \ No newline at end of file
+ "notify-on-install" : false,
+ "optimize-autoloader" : true
+ },
+ "repositories": [{
+ "type": "vcs",
+ "url": "https://github.com/simplepie/simplepie"
+ }]
+}
diff --git a/composer.lock b/composer.lock
new file mode 100644
index 000000000..f31a719c3
--- /dev/null
+++ b/composer.lock
@@ -0,0 +1,3924 @@
+{
+ "_readme": [
+ "This file locks the dependencies of your project to a known state",
+ "Read more about it at https://getcomposer.org/doc/01-basic-usage.md#composer-lock-the-lock-file",
+ "This file is @generated automatically"
+ ],
+ "content-hash": "4a78983d966b7641fd532909d625c21a",
+ "packages": [
+ {
+ "name": "bshaffer/oauth2-server-php",
+ "version": "v1.9.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/bshaffer/oauth2-server-php.git",
+ "reference": "8856aed1a98d6da596ae3f9b8095b5c7a1581697"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/bshaffer/oauth2-server-php/zipball/8856aed1a98d6da596ae3f9b8095b5c7a1581697",
+ "reference": "8856aed1a98d6da596ae3f9b8095b5c7a1581697",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.3.9"
+ },
+ "require-dev": {
+ "aws/aws-sdk-php": "~2.8",
+ "firebase/php-jwt": "~2.2",
+ "mongodb/mongodb": "^1.1",
+ "predis/predis": "dev-master",
+ "thobbs/phpcassa": "dev-master"
+ },
+ "suggest": {
+ "aws/aws-sdk-php": "~2.8 is required to use DynamoDB storage",
+ "firebase/php-jwt": "~1.1 is required to use MondoDB storage",
+ "predis/predis": "Required to use Redis storage",
+ "thobbs/phpcassa": "Required to use Cassandra storage"
+ },
+ "type": "library",
+ "autoload": {
+ "psr-0": {
+ "OAuth2": "src/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Brent Shaffer",
+ "email": "bshafs@gmail.com",
+ "homepage": "http://brentertainment.com"
+ }
+ ],
+ "description": "OAuth2 Server for PHP",
+ "homepage": "http://github.com/bshaffer/oauth2-server-php",
+ "keywords": [
+ "auth",
+ "oauth",
+ "oauth2"
+ ],
+ "time": "2017-01-06T23:20:00+00:00"
+ },
+ {
+ "name": "ezyang/htmlpurifier",
+ "version": "v4.9.3",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/ezyang/htmlpurifier.git",
+ "reference": "95e1bae3182efc0f3422896a3236e991049dac69"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/ezyang/htmlpurifier/zipball/95e1bae3182efc0f3422896a3236e991049dac69",
+ "reference": "95e1bae3182efc0f3422896a3236e991049dac69",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.2"
+ },
+ "require-dev": {
+ "simpletest/simpletest": "^1.1"
+ },
+ "type": "library",
+ "autoload": {
+ "psr-0": {
+ "HTMLPurifier": "library/"
+ },
+ "files": [
+ "library/HTMLPurifier.composer.php"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "LGPL"
+ ],
+ "authors": [
+ {
+ "name": "Edward Z. Yang",
+ "email": "admin@htmlpurifier.org",
+ "homepage": "http://ezyang.com"
+ }
+ ],
+ "description": "Standards compliant HTML filter written in PHP",
+ "homepage": "http://htmlpurifier.org/",
+ "keywords": [
+ "html"
+ ],
+ "time": "2017-06-03T02:28:16+00:00"
+ },
+ {
+ "name": "league/html-to-markdown",
+ "version": "4.4.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/thephpleague/html-to-markdown.git",
+ "reference": "82ea375b5b2b1da1da222644c0565c695bf88186"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/thephpleague/html-to-markdown/zipball/82ea375b5b2b1da1da222644c0565c695bf88186",
+ "reference": "82ea375b5b2b1da1da222644c0565c695bf88186",
+ "shasum": ""
+ },
+ "require": {
+ "ext-dom": "*",
+ "ext-xml": "*",
+ "php": ">=5.3.3"
+ },
+ "require-dev": {
+ "mikehaertl/php-shellcommand": "~1.1.0",
+ "phpunit/phpunit": "4.*",
+ "scrutinizer/ocular": "~1.1"
+ },
+ "bin": [
+ "bin/html-to-markdown"
+ ],
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "4.5-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "League\\HTMLToMarkdown\\": "src/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Colin O'Dell",
+ "email": "colinodell@gmail.com",
+ "homepage": "http://www.colinodell.com",
+ "role": "Lead Developer"
+ },
+ {
+ "name": "Nick Cernis",
+ "email": "nick@cern.is",
+ "homepage": "http://modernnerd.net",
+ "role": "Original Author"
+ }
+ ],
+ "description": "An HTML-to-markdown conversion helper for PHP",
+ "homepage": "https://github.com/thephpleague/html-to-markdown",
+ "keywords": [
+ "html",
+ "markdown"
+ ],
+ "time": "2017-03-16T00:45:59+00:00"
+ },
+ {
+ "name": "michelf/php-markdown",
+ "version": "1.7.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/michelf/php-markdown.git",
+ "reference": "1f51cc520948f66cd2af8cbc45a5ee175e774220"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/michelf/php-markdown/zipball/1f51cc520948f66cd2af8cbc45a5ee175e774220",
+ "reference": "1f51cc520948f66cd2af8cbc45a5ee175e774220",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.3.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-lib": "1.4.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-0": {
+ "Michelf": ""
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Michel Fortin",
+ "email": "michel.fortin@michelf.ca",
+ "homepage": "https://michelf.ca/",
+ "role": "Developer"
+ },
+ {
+ "name": "John Gruber",
+ "homepage": "https://daringfireball.net/"
+ }
+ ],
+ "description": "PHP Markdown",
+ "homepage": "https://michelf.ca/projects/php-markdown/",
+ "keywords": [
+ "markdown"
+ ],
+ "time": "2016-10-29T18:58:20+00:00"
+ },
+ {
+ "name": "psr/log",
+ "version": "1.0.2",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/php-fig/log.git",
+ "reference": "4ebe3a8bf773a19edfe0a84b6585ba3d401b724d"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/php-fig/log/zipball/4ebe3a8bf773a19edfe0a84b6585ba3d401b724d",
+ "reference": "4ebe3a8bf773a19edfe0a84b6585ba3d401b724d",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.3.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.0.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Psr\\Log\\": "Psr/Log/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "PHP-FIG",
+ "homepage": "http://www.php-fig.org/"
+ }
+ ],
+ "description": "Common interface for logging libraries",
+ "homepage": "https://github.com/php-fig/log",
+ "keywords": [
+ "log",
+ "psr",
+ "psr-3"
+ ],
+ "time": "2016-10-10T12:19:37+00:00"
+ },
+ {
+ "name": "sabre/dav",
+ "version": "3.2.2",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/fruux/sabre-dav.git",
+ "reference": "e987775e619728f12205606c9cc3ee565ffb1516"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/fruux/sabre-dav/zipball/e987775e619728f12205606c9cc3ee565ffb1516",
+ "reference": "e987775e619728f12205606c9cc3ee565ffb1516",
+ "shasum": ""
+ },
+ "require": {
+ "ext-ctype": "*",
+ "ext-date": "*",
+ "ext-dom": "*",
+ "ext-iconv": "*",
+ "ext-mbstring": "*",
+ "ext-pcre": "*",
+ "ext-simplexml": "*",
+ "ext-spl": "*",
+ "lib-libxml": ">=2.7.0",
+ "php": ">=5.5.0",
+ "psr/log": "^1.0",
+ "sabre/event": ">=2.0.0, <4.0.0",
+ "sabre/http": "^4.2.1",
+ "sabre/uri": "^1.0.1",
+ "sabre/vobject": "^4.1.0",
+ "sabre/xml": "^1.4.0"
+ },
+ "require-dev": {
+ "evert/phpdoc-md": "~0.1.0",
+ "monolog/monolog": "^1.18",
+ "phpunit/phpunit": "> 4.8, <6.0.0",
+ "sabre/cs": "^1.0.0"
+ },
+ "suggest": {
+ "ext-curl": "*",
+ "ext-pdo": "*"
+ },
+ "bin": [
+ "bin/sabredav",
+ "bin/naturalselection"
+ ],
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.1.0-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Sabre\\DAV\\": "lib/DAV/",
+ "Sabre\\DAVACL\\": "lib/DAVACL/",
+ "Sabre\\CalDAV\\": "lib/CalDAV/",
+ "Sabre\\CardDAV\\": "lib/CardDAV/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Evert Pot",
+ "email": "me@evertpot.com",
+ "homepage": "http://evertpot.com/",
+ "role": "Developer"
+ }
+ ],
+ "description": "WebDAV Framework for PHP",
+ "homepage": "http://sabre.io/",
+ "keywords": [
+ "CalDAV",
+ "CardDAV",
+ "WebDAV",
+ "framework",
+ "iCalendar"
+ ],
+ "time": "2017-02-15T03:06:08+00:00"
+ },
+ {
+ "name": "sabre/event",
+ "version": "3.0.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/fruux/sabre-event.git",
+ "reference": "831d586f5a442dceacdcf5e9c4c36a4db99a3534"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/fruux/sabre-event/zipball/831d586f5a442dceacdcf5e9c4c36a4db99a3534",
+ "reference": "831d586f5a442dceacdcf5e9c4c36a4db99a3534",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.5"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "*",
+ "sabre/cs": "~0.0.4"
+ },
+ "type": "library",
+ "autoload": {
+ "psr-4": {
+ "Sabre\\Event\\": "lib/"
+ },
+ "files": [
+ "lib/coroutine.php",
+ "lib/Loop/functions.php",
+ "lib/Promise/functions.php"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Evert Pot",
+ "email": "me@evertpot.com",
+ "homepage": "http://evertpot.com/",
+ "role": "Developer"
+ }
+ ],
+ "description": "sabre/event is a library for lightweight event-based programming",
+ "homepage": "http://sabre.io/event/",
+ "keywords": [
+ "EventEmitter",
+ "async",
+ "events",
+ "hooks",
+ "plugin",
+ "promise",
+ "signal"
+ ],
+ "time": "2015-11-05T20:14:39+00:00"
+ },
+ {
+ "name": "sabre/http",
+ "version": "4.2.3",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/fruux/sabre-http.git",
+ "reference": "0295f9a3ee39be97e0898592fc19e42421e0cd93"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/fruux/sabre-http/zipball/0295f9a3ee39be97e0898592fc19e42421e0cd93",
+ "reference": "0295f9a3ee39be97e0898592fc19e42421e0cd93",
+ "shasum": ""
+ },
+ "require": {
+ "ext-ctype": "*",
+ "ext-mbstring": "*",
+ "php": ">=5.4",
+ "sabre/event": ">=1.0.0,<4.0.0",
+ "sabre/uri": "~1.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "~4.3",
+ "sabre/cs": "~0.0.1"
+ },
+ "suggest": {
+ "ext-curl": " to make http requests with the Client class"
+ },
+ "type": "library",
+ "autoload": {
+ "files": [
+ "lib/functions.php"
+ ],
+ "psr-4": {
+ "Sabre\\HTTP\\": "lib/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Evert Pot",
+ "email": "me@evertpot.com",
+ "homepage": "http://evertpot.com/",
+ "role": "Developer"
+ }
+ ],
+ "description": "The sabre/http library provides utilities for dealing with http requests and responses. ",
+ "homepage": "https://github.com/fruux/sabre-http",
+ "keywords": [
+ "http"
+ ],
+ "time": "2017-06-12T07:53:04+00:00"
+ },
+ {
+ "name": "sabre/uri",
+ "version": "1.2.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/fruux/sabre-uri.git",
+ "reference": "ada354d83579565949d80b2e15593c2371225e61"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/fruux/sabre-uri/zipball/ada354d83579565949d80b2e15593c2371225e61",
+ "reference": "ada354d83579565949d80b2e15593c2371225e61",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.4.7"
+ },
+ "require-dev": {
+ "phpunit/phpunit": ">=4.0,<6.0",
+ "sabre/cs": "~1.0.0"
+ },
+ "type": "library",
+ "autoload": {
+ "files": [
+ "lib/functions.php"
+ ],
+ "psr-4": {
+ "Sabre\\Uri\\": "lib/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Evert Pot",
+ "email": "me@evertpot.com",
+ "homepage": "http://evertpot.com/",
+ "role": "Developer"
+ }
+ ],
+ "description": "Functions for making sense out of URIs.",
+ "homepage": "http://sabre.io/uri/",
+ "keywords": [
+ "rfc3986",
+ "uri",
+ "url"
+ ],
+ "time": "2017-02-20T19:59:28+00:00"
+ },
+ {
+ "name": "sabre/vobject",
+ "version": "4.1.2",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/fruux/sabre-vobject.git",
+ "reference": "d0fde2fafa2a3dad1f559c2d1c2591d4fd75ae3c"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/fruux/sabre-vobject/zipball/d0fde2fafa2a3dad1f559c2d1c2591d4fd75ae3c",
+ "reference": "d0fde2fafa2a3dad1f559c2d1c2591d4fd75ae3c",
+ "shasum": ""
+ },
+ "require": {
+ "ext-mbstring": "*",
+ "php": ">=5.5",
+ "sabre/xml": ">=1.5 <3.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "*",
+ "sabre/cs": "^1.0.0"
+ },
+ "suggest": {
+ "hoa/bench": "If you would like to run the benchmark scripts"
+ },
+ "bin": [
+ "bin/vobject",
+ "bin/generate_vcards"
+ ],
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "4.0.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Sabre\\VObject\\": "lib/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Evert Pot",
+ "email": "me@evertpot.com",
+ "homepage": "http://evertpot.com/",
+ "role": "Developer"
+ },
+ {
+ "name": "Dominik Tobschall",
+ "email": "dominik@fruux.com",
+ "homepage": "http://tobschall.de/",
+ "role": "Developer"
+ },
+ {
+ "name": "Ivan Enderlin",
+ "email": "ivan.enderlin@hoa-project.net",
+ "homepage": "http://mnt.io/",
+ "role": "Developer"
+ }
+ ],
+ "description": "The VObject library for PHP allows you to easily parse and manipulate iCalendar and vCard objects",
+ "homepage": "http://sabre.io/vobject/",
+ "keywords": [
+ "availability",
+ "freebusy",
+ "iCalendar",
+ "ical",
+ "ics",
+ "jCal",
+ "jCard",
+ "recurrence",
+ "rfc2425",
+ "rfc2426",
+ "rfc2739",
+ "rfc4770",
+ "rfc5545",
+ "rfc5546",
+ "rfc6321",
+ "rfc6350",
+ "rfc6351",
+ "rfc6474",
+ "rfc6638",
+ "rfc6715",
+ "rfc6868",
+ "vCalendar",
+ "vCard",
+ "vcf",
+ "xCal",
+ "xCard"
+ ],
+ "time": "2016-12-06T04:14:09+00:00"
+ },
+ {
+ "name": "sabre/xml",
+ "version": "1.5.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/fruux/sabre-xml.git",
+ "reference": "59b20e5bbace9912607481634f97d05a776ffca7"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/fruux/sabre-xml/zipball/59b20e5bbace9912607481634f97d05a776ffca7",
+ "reference": "59b20e5bbace9912607481634f97d05a776ffca7",
+ "shasum": ""
+ },
+ "require": {
+ "ext-dom": "*",
+ "ext-xmlreader": "*",
+ "ext-xmlwriter": "*",
+ "lib-libxml": ">=2.6.20",
+ "php": ">=5.5.5",
+ "sabre/uri": ">=1.0,<3.0.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "*",
+ "sabre/cs": "~1.0.0"
+ },
+ "type": "library",
+ "autoload": {
+ "psr-4": {
+ "Sabre\\Xml\\": "lib/"
+ },
+ "files": [
+ "lib/Deserializer/functions.php",
+ "lib/Serializer/functions.php"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Evert Pot",
+ "email": "me@evertpot.com",
+ "homepage": "http://evertpot.com/",
+ "role": "Developer"
+ },
+ {
+ "name": "Markus Staab",
+ "email": "markus.staab@redaxo.de",
+ "role": "Developer"
+ }
+ ],
+ "description": "sabre/xml is an XML library that you may not hate.",
+ "homepage": "https://sabre.io/xml/",
+ "keywords": [
+ "XMLReader",
+ "XMLWriter",
+ "dom",
+ "xml"
+ ],
+ "time": "2016-10-09T22:57:52+00:00"
+ },
+ {
+ "name": "simplepie/simplepie",
+ "version": "1.5",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/simplepie/simplepie.git",
+ "reference": "5de5551953f95feef12cf355a7a26a70f94aa3ab"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/simplepie/simplepie/zipball/5de5551953f95feef12cf355a7a26a70f94aa3ab",
+ "reference": "5de5551953f95feef12cf355a7a26a70f94aa3ab",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.3.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "~4 || ~5"
+ },
+ "suggest": {
+ "mf2/mf2": "Microformat module that allows for parsing HTML for microformats"
+ },
+ "type": "library",
+ "autoload": {
+ "psr-0": {
+ "SimplePie": "library"
+ }
+ },
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Ryan Parman",
+ "homepage": "http://ryanparman.com/",
+ "role": "Creator, alumnus developer"
+ },
+ {
+ "name": "Geoffrey Sneddon",
+ "homepage": "http://gsnedders.com/",
+ "role": "Alumnus developer"
+ },
+ {
+ "name": "Ryan McCue",
+ "email": "me@ryanmccue.info",
+ "homepage": "http://ryanmccue.info/",
+ "role": "Developer"
+ }
+ ],
+ "description": "A simple Atom/RSS parsing library for PHP",
+ "homepage": "http://simplepie.org/",
+ "keywords": [
+ "atom",
+ "feeds",
+ "rss"
+ ],
+ "support": {
+ "source": "https://github.com/simplepie/simplepie/tree/1.5",
+ "issues": "https://github.com/simplepie/simplepie/issues"
+ },
+ "time": "2017-04-17T07:29:31+00:00"
+ }
+ ],
+ "packages-dev": [
+ {
+ "name": "behat/behat",
+ "version": "v3.3.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/Behat/Behat.git",
+ "reference": "44a58c1480d6144b2dc2c2bf02b9cef73c83840d"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/Behat/Behat/zipball/44a58c1480d6144b2dc2c2bf02b9cef73c83840d",
+ "reference": "44a58c1480d6144b2dc2c2bf02b9cef73c83840d",
+ "shasum": ""
+ },
+ "require": {
+ "behat/gherkin": "^4.4.4",
+ "behat/transliterator": "^1.2",
+ "container-interop/container-interop": "^1.1",
+ "ext-mbstring": "*",
+ "php": ">=5.3.3",
+ "symfony/class-loader": "~2.1||~3.0",
+ "symfony/config": "~2.3||~3.0",
+ "symfony/console": "~2.5||~3.0",
+ "symfony/dependency-injection": "~2.1||~3.0",
+ "symfony/event-dispatcher": "~2.1||~3.0",
+ "symfony/translation": "~2.3||~3.0",
+ "symfony/yaml": "~2.1||~3.0"
+ },
+ "require-dev": {
+ "herrera-io/box": "~1.6.1",
+ "phpunit/phpunit": "~4.5",
+ "symfony/process": "~2.5|~3.0"
+ },
+ "suggest": {
+ "behat/mink-extension": "for integration with Mink testing framework",
+ "behat/symfony2-extension": "for integration with Symfony2 web framework",
+ "behat/yii-extension": "for integration with Yii web framework"
+ },
+ "bin": [
+ "bin/behat"
+ ],
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.2.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-0": {
+ "Behat\\Behat": "src/",
+ "Behat\\Testwork": "src/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Konstantin Kudryashov",
+ "email": "ever.zet@gmail.com",
+ "homepage": "http://everzet.com"
+ }
+ ],
+ "description": "Scenario-oriented BDD framework for PHP 5.3",
+ "homepage": "http://behat.org/",
+ "keywords": [
+ "Agile",
+ "BDD",
+ "ScenarioBDD",
+ "Scrum",
+ "StoryBDD",
+ "User story",
+ "business",
+ "development",
+ "documentation",
+ "examples",
+ "symfony",
+ "testing"
+ ],
+ "time": "2017-05-15T16:49:16+00:00"
+ },
+ {
+ "name": "behat/gherkin",
+ "version": "v4.4.5",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/Behat/Gherkin.git",
+ "reference": "5c14cff4f955b17d20d088dec1bde61c0539ec74"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/Behat/Gherkin/zipball/5c14cff4f955b17d20d088dec1bde61c0539ec74",
+ "reference": "5c14cff4f955b17d20d088dec1bde61c0539ec74",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.3.1"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "~4.5|~5",
+ "symfony/phpunit-bridge": "~2.7|~3",
+ "symfony/yaml": "~2.3|~3"
+ },
+ "suggest": {
+ "symfony/yaml": "If you want to parse features, represented in YAML files"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "4.4-dev"
+ }
+ },
+ "autoload": {
+ "psr-0": {
+ "Behat\\Gherkin": "src/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Konstantin Kudryashov",
+ "email": "ever.zet@gmail.com",
+ "homepage": "http://everzet.com"
+ }
+ ],
+ "description": "Gherkin DSL parser for PHP 5.3",
+ "homepage": "http://behat.org/",
+ "keywords": [
+ "BDD",
+ "Behat",
+ "Cucumber",
+ "DSL",
+ "gherkin",
+ "parser"
+ ],
+ "time": "2016-10-30T11:50:56+00:00"
+ },
+ {
+ "name": "behat/mink",
+ "version": "v1.7.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/minkphp/Mink.git",
+ "reference": "e6930b9c74693dff7f4e58577e1b1743399f3ff9"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/minkphp/Mink/zipball/e6930b9c74693dff7f4e58577e1b1743399f3ff9",
+ "reference": "e6930b9c74693dff7f4e58577e1b1743399f3ff9",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.3.1",
+ "symfony/css-selector": "~2.1|~3.0"
+ },
+ "require-dev": {
+ "symfony/phpunit-bridge": "~2.7|~3.0"
+ },
+ "suggest": {
+ "behat/mink-browserkit-driver": "extremely fast headless driver for Symfony\\Kernel-based apps (Sf2, Silex)",
+ "behat/mink-goutte-driver": "fast headless driver for any app without JS emulation",
+ "behat/mink-selenium2-driver": "slow, but JS-enabled driver for any app (requires Selenium2)",
+ "behat/mink-zombie-driver": "fast and JS-enabled headless driver for any app (requires node.js)"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.7.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Behat\\Mink\\": "src/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Konstantin Kudryashov",
+ "email": "ever.zet@gmail.com",
+ "homepage": "http://everzet.com"
+ }
+ ],
+ "description": "Browser controller/emulator abstraction for PHP",
+ "homepage": "http://mink.behat.org/",
+ "keywords": [
+ "browser",
+ "testing",
+ "web"
+ ],
+ "time": "2016-03-05T08:26:18+00:00"
+ },
+ {
+ "name": "behat/mink-browserkit-driver",
+ "version": "v1.3.2",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/minkphp/MinkBrowserKitDriver.git",
+ "reference": "10e67fb4a295efcd62ea0bf16025a85ea19534fb"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/minkphp/MinkBrowserKitDriver/zipball/10e67fb4a295efcd62ea0bf16025a85ea19534fb",
+ "reference": "10e67fb4a295efcd62ea0bf16025a85ea19534fb",
+ "shasum": ""
+ },
+ "require": {
+ "behat/mink": "^1.7.1@dev",
+ "php": ">=5.3.6",
+ "symfony/browser-kit": "~2.3|~3.0",
+ "symfony/dom-crawler": "~2.3|~3.0"
+ },
+ "require-dev": {
+ "silex/silex": "~1.2",
+ "symfony/phpunit-bridge": "~2.7|~3.0"
+ },
+ "type": "mink-driver",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.3.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Behat\\Mink\\Driver\\": "src/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Konstantin Kudryashov",
+ "email": "ever.zet@gmail.com",
+ "homepage": "http://everzet.com"
+ }
+ ],
+ "description": "Symfony2 BrowserKit driver for Mink framework",
+ "homepage": "http://mink.behat.org/",
+ "keywords": [
+ "Mink",
+ "Symfony2",
+ "browser",
+ "testing"
+ ],
+ "time": "2016-03-05T08:59:47+00:00"
+ },
+ {
+ "name": "behat/mink-extension",
+ "version": "v2.2",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/Behat/MinkExtension.git",
+ "reference": "5b4bda64ff456104564317e212c823e45cad9d59"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/Behat/MinkExtension/zipball/5b4bda64ff456104564317e212c823e45cad9d59",
+ "reference": "5b4bda64ff456104564317e212c823e45cad9d59",
+ "shasum": ""
+ },
+ "require": {
+ "behat/behat": "~3.0,>=3.0.5",
+ "behat/mink": "~1.5",
+ "php": ">=5.3.2",
+ "symfony/config": "~2.2|~3.0"
+ },
+ "require-dev": {
+ "behat/mink-goutte-driver": "~1.1",
+ "phpspec/phpspec": "~2.0"
+ },
+ "type": "behat-extension",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "2.1.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-0": {
+ "Behat\\MinkExtension": "src/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Christophe Coevoet",
+ "email": "stof@notk.org"
+ },
+ {
+ "name": "Konstantin Kudryashov",
+ "email": "ever.zet@gmail.com"
+ }
+ ],
+ "description": "Mink extension for Behat",
+ "homepage": "http://extensions.behat.org/mink",
+ "keywords": [
+ "browser",
+ "gui",
+ "test",
+ "web"
+ ],
+ "time": "2016-02-15T07:55:18+00:00"
+ },
+ {
+ "name": "behat/mink-goutte-driver",
+ "version": "v1.2.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/minkphp/MinkGoutteDriver.git",
+ "reference": "8b9ad6d2d95bc70b840d15323365f52fcdaea6ca"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/minkphp/MinkGoutteDriver/zipball/8b9ad6d2d95bc70b840d15323365f52fcdaea6ca",
+ "reference": "8b9ad6d2d95bc70b840d15323365f52fcdaea6ca",
+ "shasum": ""
+ },
+ "require": {
+ "behat/mink": "~1.6@dev",
+ "behat/mink-browserkit-driver": "~1.2@dev",
+ "fabpot/goutte": "~1.0.4|~2.0|~3.1",
+ "php": ">=5.3.1"
+ },
+ "require-dev": {
+ "symfony/phpunit-bridge": "~2.7|~3.0"
+ },
+ "type": "mink-driver",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.2.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Behat\\Mink\\Driver\\": "src/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Konstantin Kudryashov",
+ "email": "ever.zet@gmail.com",
+ "homepage": "http://everzet.com"
+ }
+ ],
+ "description": "Goutte driver for Mink framework",
+ "homepage": "http://mink.behat.org/",
+ "keywords": [
+ "browser",
+ "goutte",
+ "headless",
+ "testing"
+ ],
+ "time": "2016-03-05T09:04:22+00:00"
+ },
+ {
+ "name": "behat/transliterator",
+ "version": "v1.2.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/Behat/Transliterator.git",
+ "reference": "826ce7e9c2a6664c0d1f381cbb38b1fb80a7ee2c"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/Behat/Transliterator/zipball/826ce7e9c2a6664c0d1f381cbb38b1fb80a7ee2c",
+ "reference": "826ce7e9c2a6664c0d1f381cbb38b1fb80a7ee2c",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.3.3"
+ },
+ "require-dev": {
+ "chuyskywalker/rolling-curl": "^3.1",
+ "php-yaoi/php-yaoi": "^1.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.2-dev"
+ }
+ },
+ "autoload": {
+ "psr-0": {
+ "Behat\\Transliterator": "src/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "Artistic-1.0"
+ ],
+ "description": "String transliterator",
+ "keywords": [
+ "i18n",
+ "slug",
+ "transliterator"
+ ],
+ "time": "2017-04-04T11:38:05+00:00"
+ },
+ {
+ "name": "container-interop/container-interop",
+ "version": "1.2.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/container-interop/container-interop.git",
+ "reference": "79cbf1341c22ec75643d841642dd5d6acd83bdb8"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/container-interop/container-interop/zipball/79cbf1341c22ec75643d841642dd5d6acd83bdb8",
+ "reference": "79cbf1341c22ec75643d841642dd5d6acd83bdb8",
+ "shasum": ""
+ },
+ "require": {
+ "psr/container": "^1.0"
+ },
+ "type": "library",
+ "autoload": {
+ "psr-4": {
+ "Interop\\Container\\": "src/Interop/Container/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "description": "Promoting the interoperability of container objects (DIC, SL, etc.)",
+ "homepage": "https://github.com/container-interop/container-interop",
+ "time": "2017-02-14T19:40:03+00:00"
+ },
+ {
+ "name": "doctrine/instantiator",
+ "version": "1.0.5",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/doctrine/instantiator.git",
+ "reference": "8e884e78f9f0eb1329e445619e04456e64d8051d"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/doctrine/instantiator/zipball/8e884e78f9f0eb1329e445619e04456e64d8051d",
+ "reference": "8e884e78f9f0eb1329e445619e04456e64d8051d",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.3,<8.0-DEV"
+ },
+ "require-dev": {
+ "athletic/athletic": "~0.1.8",
+ "ext-pdo": "*",
+ "ext-phar": "*",
+ "phpunit/phpunit": "~4.0",
+ "squizlabs/php_codesniffer": "~2.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.0.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Doctrine\\Instantiator\\": "src/Doctrine/Instantiator/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Marco Pivetta",
+ "email": "ocramius@gmail.com",
+ "homepage": "http://ocramius.github.com/"
+ }
+ ],
+ "description": "A small, lightweight utility to instantiate objects in PHP without invoking their constructors",
+ "homepage": "https://github.com/doctrine/instantiator",
+ "keywords": [
+ "constructor",
+ "instantiate"
+ ],
+ "time": "2015-06-14T21:17:01+00:00"
+ },
+ {
+ "name": "fabpot/goutte",
+ "version": "v3.2.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/FriendsOfPHP/Goutte.git",
+ "reference": "db5c28f4a010b4161d507d5304e28a7ebf211638"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/FriendsOfPHP/Goutte/zipball/db5c28f4a010b4161d507d5304e28a7ebf211638",
+ "reference": "db5c28f4a010b4161d507d5304e28a7ebf211638",
+ "shasum": ""
+ },
+ "require": {
+ "guzzlehttp/guzzle": "^6.0",
+ "php": ">=5.5.0",
+ "symfony/browser-kit": "~2.1|~3.0",
+ "symfony/css-selector": "~2.1|~3.0",
+ "symfony/dom-crawler": "~2.1|~3.0"
+ },
+ "type": "application",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.2-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Goutte\\": "Goutte"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Fabien Potencier",
+ "email": "fabien@symfony.com"
+ }
+ ],
+ "description": "A simple PHP Web Scraper",
+ "homepage": "https://github.com/FriendsOfPHP/Goutte",
+ "keywords": [
+ "scraper"
+ ],
+ "time": "2017-01-03T13:21:43+00:00"
+ },
+ {
+ "name": "guzzlehttp/guzzle",
+ "version": "6.3.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/guzzle/guzzle.git",
+ "reference": "f4db5a78a5ea468d4831de7f0bf9d9415e348699"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/guzzle/guzzle/zipball/f4db5a78a5ea468d4831de7f0bf9d9415e348699",
+ "reference": "f4db5a78a5ea468d4831de7f0bf9d9415e348699",
+ "shasum": ""
+ },
+ "require": {
+ "guzzlehttp/promises": "^1.0",
+ "guzzlehttp/psr7": "^1.4",
+ "php": ">=5.5"
+ },
+ "require-dev": {
+ "ext-curl": "*",
+ "phpunit/phpunit": "^4.0 || ^5.0",
+ "psr/log": "^1.0"
+ },
+ "suggest": {
+ "psr/log": "Required for using the Log middleware"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "6.2-dev"
+ }
+ },
+ "autoload": {
+ "files": [
+ "src/functions_include.php"
+ ],
+ "psr-4": {
+ "GuzzleHttp\\": "src/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Michael Dowling",
+ "email": "mtdowling@gmail.com",
+ "homepage": "https://github.com/mtdowling"
+ }
+ ],
+ "description": "Guzzle is a PHP HTTP client library",
+ "homepage": "http://guzzlephp.org/",
+ "keywords": [
+ "client",
+ "curl",
+ "framework",
+ "http",
+ "http client",
+ "rest",
+ "web service"
+ ],
+ "time": "2017-06-22T18:50:49+00:00"
+ },
+ {
+ "name": "guzzlehttp/promises",
+ "version": "v1.3.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/guzzle/promises.git",
+ "reference": "a59da6cf61d80060647ff4d3eb2c03a2bc694646"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/guzzle/promises/zipball/a59da6cf61d80060647ff4d3eb2c03a2bc694646",
+ "reference": "a59da6cf61d80060647ff4d3eb2c03a2bc694646",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.5.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^4.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.4-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "GuzzleHttp\\Promise\\": "src/"
+ },
+ "files": [
+ "src/functions_include.php"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Michael Dowling",
+ "email": "mtdowling@gmail.com",
+ "homepage": "https://github.com/mtdowling"
+ }
+ ],
+ "description": "Guzzle promises library",
+ "keywords": [
+ "promise"
+ ],
+ "time": "2016-12-20T10:07:11+00:00"
+ },
+ {
+ "name": "guzzlehttp/psr7",
+ "version": "1.4.2",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/guzzle/psr7.git",
+ "reference": "f5b8a8512e2b58b0071a7280e39f14f72e05d87c"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/guzzle/psr7/zipball/f5b8a8512e2b58b0071a7280e39f14f72e05d87c",
+ "reference": "f5b8a8512e2b58b0071a7280e39f14f72e05d87c",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.4.0",
+ "psr/http-message": "~1.0"
+ },
+ "provide": {
+ "psr/http-message-implementation": "1.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "~4.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.4-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "GuzzleHttp\\Psr7\\": "src/"
+ },
+ "files": [
+ "src/functions_include.php"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Michael Dowling",
+ "email": "mtdowling@gmail.com",
+ "homepage": "https://github.com/mtdowling"
+ },
+ {
+ "name": "Tobias Schultze",
+ "homepage": "https://github.com/Tobion"
+ }
+ ],
+ "description": "PSR-7 message implementation that also provides common utility methods",
+ "keywords": [
+ "http",
+ "message",
+ "request",
+ "response",
+ "stream",
+ "uri",
+ "url"
+ ],
+ "time": "2017-03-20T17:10:46+00:00"
+ },
+ {
+ "name": "myclabs/deep-copy",
+ "version": "1.6.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/myclabs/DeepCopy.git",
+ "reference": "8e6e04167378abf1ddb4d3522d8755c5fd90d102"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/myclabs/DeepCopy/zipball/8e6e04167378abf1ddb4d3522d8755c5fd90d102",
+ "reference": "8e6e04167378abf1ddb4d3522d8755c5fd90d102",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.4.0"
+ },
+ "require-dev": {
+ "doctrine/collections": "1.*",
+ "phpunit/phpunit": "~4.1"
+ },
+ "type": "library",
+ "autoload": {
+ "psr-4": {
+ "DeepCopy\\": "src/DeepCopy/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "description": "Create deep copies (clones) of your objects",
+ "homepage": "https://github.com/myclabs/DeepCopy",
+ "keywords": [
+ "clone",
+ "copy",
+ "duplicate",
+ "object",
+ "object graph"
+ ],
+ "time": "2017-04-12T18:52:22+00:00"
+ },
+ {
+ "name": "phar-io/manifest",
+ "version": "1.0.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/phar-io/manifest.git",
+ "reference": "2df402786ab5368a0169091f61a7c1e0eb6852d0"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/phar-io/manifest/zipball/2df402786ab5368a0169091f61a7c1e0eb6852d0",
+ "reference": "2df402786ab5368a0169091f61a7c1e0eb6852d0",
+ "shasum": ""
+ },
+ "require": {
+ "ext-dom": "*",
+ "ext-phar": "*",
+ "phar-io/version": "^1.0.1",
+ "php": "^5.6 || ^7.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.0.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Arne Blankerts",
+ "email": "arne@blankerts.de",
+ "role": "Developer"
+ },
+ {
+ "name": "Sebastian Heuer",
+ "email": "sebastian@phpeople.de",
+ "role": "Developer"
+ },
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de",
+ "role": "Developer"
+ }
+ ],
+ "description": "Component for reading phar.io manifest information from a PHP Archive (PHAR)",
+ "time": "2017-03-05T18:14:27+00:00"
+ },
+ {
+ "name": "phar-io/version",
+ "version": "1.0.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/phar-io/version.git",
+ "reference": "a70c0ced4be299a63d32fa96d9281d03e94041df"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/phar-io/version/zipball/a70c0ced4be299a63d32fa96d9281d03e94041df",
+ "reference": "a70c0ced4be299a63d32fa96d9281d03e94041df",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^5.6 || ^7.0"
+ },
+ "type": "library",
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Arne Blankerts",
+ "email": "arne@blankerts.de",
+ "role": "Developer"
+ },
+ {
+ "name": "Sebastian Heuer",
+ "email": "sebastian@phpeople.de",
+ "role": "Developer"
+ },
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de",
+ "role": "Developer"
+ }
+ ],
+ "description": "Library for handling version information and constraints",
+ "time": "2017-03-05T17:38:23+00:00"
+ },
+ {
+ "name": "php-mock/php-mock",
+ "version": "2.0.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/php-mock/php-mock.git",
+ "reference": "22d297231118e6fd5b9db087fbe1ef866c2b95d2"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/php-mock/php-mock/zipball/22d297231118e6fd5b9db087fbe1ef866c2b95d2",
+ "reference": "22d297231118e6fd5b9db087fbe1ef866c2b95d2",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.6",
+ "phpunit/php-text-template": "^1"
+ },
+ "replace": {
+ "malkusch/php-mock": "*"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^5.7"
+ },
+ "suggest": {
+ "php-mock/php-mock-phpunit": "Allows integration into PHPUnit testcase with the trait PHPMock."
+ },
+ "type": "library",
+ "autoload": {
+ "psr-4": {
+ "phpmock\\": [
+ "classes/",
+ "tests/"
+ ]
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "WTFPL"
+ ],
+ "authors": [
+ {
+ "name": "Markus Malkusch",
+ "email": "markus@malkusch.de",
+ "homepage": "http://markus.malkusch.de",
+ "role": "Developer"
+ }
+ ],
+ "description": "PHP-Mock can mock built-in PHP functions (e.g. time()). PHP-Mock relies on PHP's namespace fallback policy. No further extension is needed.",
+ "homepage": "https://github.com/php-mock/php-mock",
+ "keywords": [
+ "BDD",
+ "TDD",
+ "function",
+ "mock",
+ "stub",
+ "test",
+ "test double"
+ ],
+ "time": "2017-02-17T20:52:52+00:00"
+ },
+ {
+ "name": "php-mock/php-mock-integration",
+ "version": "2.0.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/php-mock/php-mock-integration.git",
+ "reference": "5a0d7d7755f823bc2a230cfa45058b40f9013bc4"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/php-mock/php-mock-integration/zipball/5a0d7d7755f823bc2a230cfa45058b40f9013bc4",
+ "reference": "5a0d7d7755f823bc2a230cfa45058b40f9013bc4",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.6",
+ "php-mock/php-mock": "^2",
+ "phpunit/php-text-template": "^1"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^4|^5"
+ },
+ "type": "library",
+ "autoload": {
+ "psr-4": {
+ "phpmock\\integration\\": "classes/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "WTFPL"
+ ],
+ "authors": [
+ {
+ "name": "Markus Malkusch",
+ "email": "markus@malkusch.de",
+ "homepage": "http://markus.malkusch.de",
+ "role": "Developer"
+ }
+ ],
+ "description": "Integration package for PHP-Mock",
+ "homepage": "https://github.com/php-mock/php-mock-integration",
+ "keywords": [
+ "BDD",
+ "TDD",
+ "function",
+ "mock",
+ "stub",
+ "test",
+ "test double"
+ ],
+ "time": "2017-02-17T21:31:34+00:00"
+ },
+ {
+ "name": "php-mock/php-mock-phpunit",
+ "version": "2.0.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/php-mock/php-mock-phpunit.git",
+ "reference": "173781abdc632c59200253e12e2b991ae6a4574f"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/php-mock/php-mock-phpunit/zipball/173781abdc632c59200253e12e2b991ae6a4574f",
+ "reference": "173781abdc632c59200253e12e2b991ae6a4574f",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=7",
+ "php-mock/php-mock-integration": "^2",
+ "phpunit/phpunit": "^6"
+ },
+ "type": "library",
+ "autoload": {
+ "psr-4": {
+ "phpmock\\phpunit\\": "classes/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "WTFPL"
+ ],
+ "authors": [
+ {
+ "name": "Markus Malkusch",
+ "email": "markus@malkusch.de",
+ "homepage": "http://markus.malkusch.de",
+ "role": "Developer"
+ }
+ ],
+ "description": "Mock built-in PHP functions (e.g. time()) with PHPUnit. This package relies on PHP's namespace fallback policy. No further extension is needed.",
+ "homepage": "https://github.com/php-mock/php-mock-phpunit",
+ "keywords": [
+ "BDD",
+ "TDD",
+ "function",
+ "mock",
+ "phpunit",
+ "stub",
+ "test",
+ "test double"
+ ],
+ "time": "2017-02-17T22:44:38+00:00"
+ },
+ {
+ "name": "phpdocumentor/reflection-common",
+ "version": "1.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/phpDocumentor/ReflectionCommon.git",
+ "reference": "144c307535e82c8fdcaacbcfc1d6d8eeb896687c"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/phpDocumentor/ReflectionCommon/zipball/144c307535e82c8fdcaacbcfc1d6d8eeb896687c",
+ "reference": "144c307535e82c8fdcaacbcfc1d6d8eeb896687c",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.5"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^4.6"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.0.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "phpDocumentor\\Reflection\\": [
+ "src"
+ ]
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Jaap van Otterdijk",
+ "email": "opensource@ijaap.nl"
+ }
+ ],
+ "description": "Common reflection classes used by phpdocumentor to reflect the code structure",
+ "homepage": "http://www.phpdoc.org",
+ "keywords": [
+ "FQSEN",
+ "phpDocumentor",
+ "phpdoc",
+ "reflection",
+ "static analysis"
+ ],
+ "time": "2015-12-27T11:43:31+00:00"
+ },
+ {
+ "name": "phpdocumentor/reflection-docblock",
+ "version": "3.1.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/phpDocumentor/ReflectionDocBlock.git",
+ "reference": "8331b5efe816ae05461b7ca1e721c01b46bafb3e"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/phpDocumentor/ReflectionDocBlock/zipball/8331b5efe816ae05461b7ca1e721c01b46bafb3e",
+ "reference": "8331b5efe816ae05461b7ca1e721c01b46bafb3e",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.5",
+ "phpdocumentor/reflection-common": "^1.0@dev",
+ "phpdocumentor/type-resolver": "^0.2.0",
+ "webmozart/assert": "^1.0"
+ },
+ "require-dev": {
+ "mockery/mockery": "^0.9.4",
+ "phpunit/phpunit": "^4.4"
+ },
+ "type": "library",
+ "autoload": {
+ "psr-4": {
+ "phpDocumentor\\Reflection\\": [
+ "src/"
+ ]
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Mike van Riel",
+ "email": "me@mikevanriel.com"
+ }
+ ],
+ "description": "With this component, a library can provide support for annotations via DocBlocks or otherwise retrieve information that is embedded in a DocBlock.",
+ "time": "2016-09-30T07:12:33+00:00"
+ },
+ {
+ "name": "phpdocumentor/type-resolver",
+ "version": "0.2.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/phpDocumentor/TypeResolver.git",
+ "reference": "e224fb2ea2fba6d3ad6fdaef91cd09a172155ccb"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/phpDocumentor/TypeResolver/zipball/e224fb2ea2fba6d3ad6fdaef91cd09a172155ccb",
+ "reference": "e224fb2ea2fba6d3ad6fdaef91cd09a172155ccb",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.5",
+ "phpdocumentor/reflection-common": "^1.0"
+ },
+ "require-dev": {
+ "mockery/mockery": "^0.9.4",
+ "phpunit/phpunit": "^5.2||^4.8.24"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.0.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "phpDocumentor\\Reflection\\": [
+ "src/"
+ ]
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Mike van Riel",
+ "email": "me@mikevanriel.com"
+ }
+ ],
+ "time": "2016-11-25T06:54:22+00:00"
+ },
+ {
+ "name": "phpspec/prophecy",
+ "version": "v1.7.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/phpspec/prophecy.git",
+ "reference": "93d39f1f7f9326d746203c7c056f300f7f126073"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/phpspec/prophecy/zipball/93d39f1f7f9326d746203c7c056f300f7f126073",
+ "reference": "93d39f1f7f9326d746203c7c056f300f7f126073",
+ "shasum": ""
+ },
+ "require": {
+ "doctrine/instantiator": "^1.0.2",
+ "php": "^5.3|^7.0",
+ "phpdocumentor/reflection-docblock": "^2.0|^3.0.2",
+ "sebastian/comparator": "^1.1|^2.0",
+ "sebastian/recursion-context": "^1.0|^2.0|^3.0"
+ },
+ "require-dev": {
+ "phpspec/phpspec": "^2.5|^3.2",
+ "phpunit/phpunit": "^4.8 || ^5.6.5"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.6.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-0": {
+ "Prophecy\\": "src/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Konstantin Kudryashov",
+ "email": "ever.zet@gmail.com",
+ "homepage": "http://everzet.com"
+ },
+ {
+ "name": "Marcello Duarte",
+ "email": "marcello.duarte@gmail.com"
+ }
+ ],
+ "description": "Highly opinionated mocking framework for PHP 5.3+",
+ "homepage": "https://github.com/phpspec/prophecy",
+ "keywords": [
+ "Double",
+ "Dummy",
+ "fake",
+ "mock",
+ "spy",
+ "stub"
+ ],
+ "time": "2017-03-02T20:05:34+00:00"
+ },
+ {
+ "name": "phpunit/php-code-coverage",
+ "version": "5.2.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/php-code-coverage.git",
+ "reference": "dc421f9ca5082a0c0cb04afb171c765f79add85b"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/php-code-coverage/zipball/dc421f9ca5082a0c0cb04afb171c765f79add85b",
+ "reference": "dc421f9ca5082a0c0cb04afb171c765f79add85b",
+ "shasum": ""
+ },
+ "require": {
+ "ext-dom": "*",
+ "ext-xmlwriter": "*",
+ "php": "^7.0",
+ "phpunit/php-file-iterator": "^1.3",
+ "phpunit/php-text-template": "^1.2",
+ "phpunit/php-token-stream": "^1.4.11 || ^2.0",
+ "sebastian/code-unit-reverse-lookup": "^1.0",
+ "sebastian/environment": "^3.0",
+ "sebastian/version": "^2.0",
+ "theseer/tokenizer": "^1.1"
+ },
+ "require-dev": {
+ "ext-xdebug": "^2.5",
+ "phpunit/phpunit": "^6.0"
+ },
+ "suggest": {
+ "ext-xdebug": "^2.5.3"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "5.2.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sb@sebastian-bergmann.de",
+ "role": "lead"
+ }
+ ],
+ "description": "Library that provides collection, processing, and rendering functionality for PHP code coverage information.",
+ "homepage": "https://github.com/sebastianbergmann/php-code-coverage",
+ "keywords": [
+ "coverage",
+ "testing",
+ "xunit"
+ ],
+ "time": "2017-04-21T08:03:57+00:00"
+ },
+ {
+ "name": "phpunit/php-file-iterator",
+ "version": "1.4.2",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/php-file-iterator.git",
+ "reference": "3cc8f69b3028d0f96a9078e6295d86e9bf019be5"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/php-file-iterator/zipball/3cc8f69b3028d0f96a9078e6295d86e9bf019be5",
+ "reference": "3cc8f69b3028d0f96a9078e6295d86e9bf019be5",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.3.3"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.4.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sb@sebastian-bergmann.de",
+ "role": "lead"
+ }
+ ],
+ "description": "FilterIterator implementation that filters files based on a list of suffixes.",
+ "homepage": "https://github.com/sebastianbergmann/php-file-iterator/",
+ "keywords": [
+ "filesystem",
+ "iterator"
+ ],
+ "time": "2016-10-03T07:40:28+00:00"
+ },
+ {
+ "name": "phpunit/php-text-template",
+ "version": "1.2.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/php-text-template.git",
+ "reference": "31f8b717e51d9a2afca6c9f046f5d69fc27c8686"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/php-text-template/zipball/31f8b717e51d9a2afca6c9f046f5d69fc27c8686",
+ "reference": "31f8b717e51d9a2afca6c9f046f5d69fc27c8686",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.3.3"
+ },
+ "type": "library",
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de",
+ "role": "lead"
+ }
+ ],
+ "description": "Simple template engine.",
+ "homepage": "https://github.com/sebastianbergmann/php-text-template/",
+ "keywords": [
+ "template"
+ ],
+ "time": "2015-06-21T13:50:34+00:00"
+ },
+ {
+ "name": "phpunit/php-timer",
+ "version": "1.0.9",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/php-timer.git",
+ "reference": "3dcf38ca72b158baf0bc245e9184d3fdffa9c46f"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/php-timer/zipball/3dcf38ca72b158baf0bc245e9184d3fdffa9c46f",
+ "reference": "3dcf38ca72b158baf0bc245e9184d3fdffa9c46f",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^5.3.3 || ^7.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^4.8.35 || ^5.7 || ^6.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.0-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sb@sebastian-bergmann.de",
+ "role": "lead"
+ }
+ ],
+ "description": "Utility class for timing",
+ "homepage": "https://github.com/sebastianbergmann/php-timer/",
+ "keywords": [
+ "timer"
+ ],
+ "time": "2017-02-26T11:10:40+00:00"
+ },
+ {
+ "name": "phpunit/php-token-stream",
+ "version": "1.4.11",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/php-token-stream.git",
+ "reference": "e03f8f67534427a787e21a385a67ec3ca6978ea7"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/php-token-stream/zipball/e03f8f67534427a787e21a385a67ec3ca6978ea7",
+ "reference": "e03f8f67534427a787e21a385a67ec3ca6978ea7",
+ "shasum": ""
+ },
+ "require": {
+ "ext-tokenizer": "*",
+ "php": ">=5.3.3"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "~4.2"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.4-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Wrapper around PHP's tokenizer extension.",
+ "homepage": "https://github.com/sebastianbergmann/php-token-stream/",
+ "keywords": [
+ "tokenizer"
+ ],
+ "time": "2017-02-27T10:12:30+00:00"
+ },
+ {
+ "name": "phpunit/phpunit",
+ "version": "6.2.3",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/phpunit.git",
+ "reference": "fa5711d0559fc4b64deba0702be52d41434cbcb7"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/phpunit/zipball/fa5711d0559fc4b64deba0702be52d41434cbcb7",
+ "reference": "fa5711d0559fc4b64deba0702be52d41434cbcb7",
+ "shasum": ""
+ },
+ "require": {
+ "ext-dom": "*",
+ "ext-json": "*",
+ "ext-libxml": "*",
+ "ext-mbstring": "*",
+ "ext-xml": "*",
+ "myclabs/deep-copy": "^1.3",
+ "phar-io/manifest": "^1.0.1",
+ "phar-io/version": "^1.0",
+ "php": "^7.0",
+ "phpspec/prophecy": "^1.7",
+ "phpunit/php-code-coverage": "^5.2",
+ "phpunit/php-file-iterator": "^1.4",
+ "phpunit/php-text-template": "^1.2",
+ "phpunit/php-timer": "^1.0.6",
+ "phpunit/phpunit-mock-objects": "^4.0",
+ "sebastian/comparator": "^2.0",
+ "sebastian/diff": "^1.4.3 || ^2.0",
+ "sebastian/environment": "^3.0.2",
+ "sebastian/exporter": "^3.1",
+ "sebastian/global-state": "^1.1 || ^2.0",
+ "sebastian/object-enumerator": "^3.0.2",
+ "sebastian/resource-operations": "^1.0",
+ "sebastian/version": "^2.0"
+ },
+ "conflict": {
+ "phpdocumentor/reflection-docblock": "3.0.2",
+ "phpunit/dbunit": "<3.0"
+ },
+ "require-dev": {
+ "ext-pdo": "*"
+ },
+ "suggest": {
+ "ext-xdebug": "*",
+ "phpunit/php-invoker": "^1.1"
+ },
+ "bin": [
+ "phpunit"
+ ],
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "6.2.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de",
+ "role": "lead"
+ }
+ ],
+ "description": "The PHP Unit Testing framework.",
+ "homepage": "https://phpunit.de/",
+ "keywords": [
+ "phpunit",
+ "testing",
+ "xunit"
+ ],
+ "time": "2017-07-03T15:54:24+00:00"
+ },
+ {
+ "name": "phpunit/phpunit-mock-objects",
+ "version": "4.0.2",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/phpunit-mock-objects.git",
+ "reference": "d8833b396dce9162bb2eb5d59aee5a3ab3cfa5b4"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/phpunit-mock-objects/zipball/d8833b396dce9162bb2eb5d59aee5a3ab3cfa5b4",
+ "reference": "d8833b396dce9162bb2eb5d59aee5a3ab3cfa5b4",
+ "shasum": ""
+ },
+ "require": {
+ "doctrine/instantiator": "^1.0.2",
+ "php": "^7.0",
+ "phpunit/php-text-template": "^1.2",
+ "sebastian/exporter": "^3.0"
+ },
+ "conflict": {
+ "phpunit/phpunit": "<6.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^6.0"
+ },
+ "suggest": {
+ "ext-soap": "*"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "4.0.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sb@sebastian-bergmann.de",
+ "role": "lead"
+ }
+ ],
+ "description": "Mock Object library for PHPUnit",
+ "homepage": "https://github.com/sebastianbergmann/phpunit-mock-objects/",
+ "keywords": [
+ "mock",
+ "xunit"
+ ],
+ "time": "2017-06-30T08:15:21+00:00"
+ },
+ {
+ "name": "psr/container",
+ "version": "1.0.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/php-fig/container.git",
+ "reference": "b7ce3b176482dbbc1245ebf52b181af44c2cf55f"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/php-fig/container/zipball/b7ce3b176482dbbc1245ebf52b181af44c2cf55f",
+ "reference": "b7ce3b176482dbbc1245ebf52b181af44c2cf55f",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.3.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.0.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Psr\\Container\\": "src/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "PHP-FIG",
+ "homepage": "http://www.php-fig.org/"
+ }
+ ],
+ "description": "Common Container Interface (PHP FIG PSR-11)",
+ "homepage": "https://github.com/php-fig/container",
+ "keywords": [
+ "PSR-11",
+ "container",
+ "container-interface",
+ "container-interop",
+ "psr"
+ ],
+ "time": "2017-02-14T16:28:37+00:00"
+ },
+ {
+ "name": "psr/http-message",
+ "version": "1.0.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/php-fig/http-message.git",
+ "reference": "f6561bf28d520154e4b0ec72be95418abe6d9363"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/php-fig/http-message/zipball/f6561bf28d520154e4b0ec72be95418abe6d9363",
+ "reference": "f6561bf28d520154e4b0ec72be95418abe6d9363",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.3.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.0.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Psr\\Http\\Message\\": "src/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "PHP-FIG",
+ "homepage": "http://www.php-fig.org/"
+ }
+ ],
+ "description": "Common interface for HTTP messages",
+ "homepage": "https://github.com/php-fig/http-message",
+ "keywords": [
+ "http",
+ "http-message",
+ "psr",
+ "psr-7",
+ "request",
+ "response"
+ ],
+ "time": "2016-08-06T14:39:51+00:00"
+ },
+ {
+ "name": "sebastian/code-unit-reverse-lookup",
+ "version": "1.0.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/code-unit-reverse-lookup.git",
+ "reference": "4419fcdb5eabb9caa61a27c7a1db532a6b55dd18"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/code-unit-reverse-lookup/zipball/4419fcdb5eabb9caa61a27c7a1db532a6b55dd18",
+ "reference": "4419fcdb5eabb9caa61a27c7a1db532a6b55dd18",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^5.6 || ^7.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^5.7 || ^6.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.0.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Looks up which function or method a line of code belongs to",
+ "homepage": "https://github.com/sebastianbergmann/code-unit-reverse-lookup/",
+ "time": "2017-03-04T06:30:41+00:00"
+ },
+ {
+ "name": "sebastian/comparator",
+ "version": "2.0.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/comparator.git",
+ "reference": "20f84f468cb67efee293246e6a09619b891f55f0"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/comparator/zipball/20f84f468cb67efee293246e6a09619b891f55f0",
+ "reference": "20f84f468cb67efee293246e6a09619b891f55f0",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.0",
+ "sebastian/diff": "^1.2",
+ "sebastian/exporter": "^3.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^6.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "2.0.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Jeff Welch",
+ "email": "whatthejeff@gmail.com"
+ },
+ {
+ "name": "Volker Dusch",
+ "email": "github@wallbash.com"
+ },
+ {
+ "name": "Bernhard Schussek",
+ "email": "bschussek@2bepublished.at"
+ },
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Provides the functionality to compare PHP values for equality",
+ "homepage": "http://www.github.com/sebastianbergmann/comparator",
+ "keywords": [
+ "comparator",
+ "compare",
+ "equality"
+ ],
+ "time": "2017-03-03T06:26:08+00:00"
+ },
+ {
+ "name": "sebastian/diff",
+ "version": "1.4.3",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/diff.git",
+ "reference": "7f066a26a962dbe58ddea9f72a4e82874a3975a4"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/diff/zipball/7f066a26a962dbe58ddea9f72a4e82874a3975a4",
+ "reference": "7f066a26a962dbe58ddea9f72a4e82874a3975a4",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^5.3.3 || ^7.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^4.8.35 || ^5.7 || ^6.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.4-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Kore Nordmann",
+ "email": "mail@kore-nordmann.de"
+ },
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Diff implementation",
+ "homepage": "https://github.com/sebastianbergmann/diff",
+ "keywords": [
+ "diff"
+ ],
+ "time": "2017-05-22T07:24:03+00:00"
+ },
+ {
+ "name": "sebastian/environment",
+ "version": "3.1.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/environment.git",
+ "reference": "cd0871b3975fb7fc44d11314fd1ee20925fce4f5"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/environment/zipball/cd0871b3975fb7fc44d11314fd1ee20925fce4f5",
+ "reference": "cd0871b3975fb7fc44d11314fd1ee20925fce4f5",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^6.1"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.1.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Provides functionality to handle HHVM/PHP environments",
+ "homepage": "http://www.github.com/sebastianbergmann/environment",
+ "keywords": [
+ "Xdebug",
+ "environment",
+ "hhvm"
+ ],
+ "time": "2017-07-01T08:51:00+00:00"
+ },
+ {
+ "name": "sebastian/exporter",
+ "version": "3.1.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/exporter.git",
+ "reference": "234199f4528de6d12aaa58b612e98f7d36adb937"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/exporter/zipball/234199f4528de6d12aaa58b612e98f7d36adb937",
+ "reference": "234199f4528de6d12aaa58b612e98f7d36adb937",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.0",
+ "sebastian/recursion-context": "^3.0"
+ },
+ "require-dev": {
+ "ext-mbstring": "*",
+ "phpunit/phpunit": "^6.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.1.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Jeff Welch",
+ "email": "whatthejeff@gmail.com"
+ },
+ {
+ "name": "Volker Dusch",
+ "email": "github@wallbash.com"
+ },
+ {
+ "name": "Bernhard Schussek",
+ "email": "bschussek@2bepublished.at"
+ },
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ },
+ {
+ "name": "Adam Harvey",
+ "email": "aharvey@php.net"
+ }
+ ],
+ "description": "Provides the functionality to export PHP variables for visualization",
+ "homepage": "http://www.github.com/sebastianbergmann/exporter",
+ "keywords": [
+ "export",
+ "exporter"
+ ],
+ "time": "2017-04-03T13:19:02+00:00"
+ },
+ {
+ "name": "sebastian/global-state",
+ "version": "2.0.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/global-state.git",
+ "reference": "e8ba02eed7bbbb9e59e43dedd3dddeff4a56b0c4"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/global-state/zipball/e8ba02eed7bbbb9e59e43dedd3dddeff4a56b0c4",
+ "reference": "e8ba02eed7bbbb9e59e43dedd3dddeff4a56b0c4",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^6.0"
+ },
+ "suggest": {
+ "ext-uopz": "*"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "2.0-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Snapshotting of global state",
+ "homepage": "http://www.github.com/sebastianbergmann/global-state",
+ "keywords": [
+ "global state"
+ ],
+ "time": "2017-04-27T15:39:26+00:00"
+ },
+ {
+ "name": "sebastian/object-enumerator",
+ "version": "3.0.2",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/object-enumerator.git",
+ "reference": "31dd3379d16446c5d86dec32ab1ad1f378581ad8"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/object-enumerator/zipball/31dd3379d16446c5d86dec32ab1ad1f378581ad8",
+ "reference": "31dd3379d16446c5d86dec32ab1ad1f378581ad8",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.0",
+ "sebastian/object-reflector": "^1.0",
+ "sebastian/recursion-context": "^3.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^6.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.0.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Traverses array structures and object graphs to enumerate all referenced objects",
+ "homepage": "https://github.com/sebastianbergmann/object-enumerator/",
+ "time": "2017-03-12T15:17:29+00:00"
+ },
+ {
+ "name": "sebastian/object-reflector",
+ "version": "1.1.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/object-reflector.git",
+ "reference": "773f97c67f28de00d397be301821b06708fca0be"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/object-reflector/zipball/773f97c67f28de00d397be301821b06708fca0be",
+ "reference": "773f97c67f28de00d397be301821b06708fca0be",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^6.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.1-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Allows reflection of object attributes, including inherited and non-public ones",
+ "homepage": "https://github.com/sebastianbergmann/object-reflector/",
+ "time": "2017-03-29T09:07:27+00:00"
+ },
+ {
+ "name": "sebastian/recursion-context",
+ "version": "3.0.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/recursion-context.git",
+ "reference": "5b0cd723502bac3b006cbf3dbf7a1e3fcefe4fa8"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/recursion-context/zipball/5b0cd723502bac3b006cbf3dbf7a1e3fcefe4fa8",
+ "reference": "5b0cd723502bac3b006cbf3dbf7a1e3fcefe4fa8",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^6.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.0.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Jeff Welch",
+ "email": "whatthejeff@gmail.com"
+ },
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ },
+ {
+ "name": "Adam Harvey",
+ "email": "aharvey@php.net"
+ }
+ ],
+ "description": "Provides functionality to recursively process PHP variables",
+ "homepage": "http://www.github.com/sebastianbergmann/recursion-context",
+ "time": "2017-03-03T06:23:57+00:00"
+ },
+ {
+ "name": "sebastian/resource-operations",
+ "version": "1.0.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/resource-operations.git",
+ "reference": "ce990bb21759f94aeafd30209e8cfcdfa8bc3f52"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/resource-operations/zipball/ce990bb21759f94aeafd30209e8cfcdfa8bc3f52",
+ "reference": "ce990bb21759f94aeafd30209e8cfcdfa8bc3f52",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.6.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.0.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Provides a list of PHP built-in functions that operate on resources",
+ "homepage": "https://www.github.com/sebastianbergmann/resource-operations",
+ "time": "2015-07-28T20:34:47+00:00"
+ },
+ {
+ "name": "sebastian/version",
+ "version": "2.0.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/version.git",
+ "reference": "99732be0ddb3361e16ad77b68ba41efc8e979019"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/version/zipball/99732be0ddb3361e16ad77b68ba41efc8e979019",
+ "reference": "99732be0ddb3361e16ad77b68ba41efc8e979019",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.6"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "2.0.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de",
+ "role": "lead"
+ }
+ ],
+ "description": "Library that helps with managing the version number of Git-hosted PHP projects",
+ "homepage": "https://github.com/sebastianbergmann/version",
+ "time": "2016-10-03T07:35:21+00:00"
+ },
+ {
+ "name": "symfony/browser-kit",
+ "version": "v3.3.4",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/symfony/browser-kit.git",
+ "reference": "3a4435e79a8401746e8525e98039199d0924b4e5"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/symfony/browser-kit/zipball/3a4435e79a8401746e8525e98039199d0924b4e5",
+ "reference": "3a4435e79a8401746e8525e98039199d0924b4e5",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.5.9",
+ "symfony/dom-crawler": "~2.8|~3.0"
+ },
+ "require-dev": {
+ "symfony/css-selector": "~2.8|~3.0",
+ "symfony/process": "~2.8|~3.0"
+ },
+ "suggest": {
+ "symfony/process": ""
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.3-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Symfony\\Component\\BrowserKit\\": ""
+ },
+ "exclude-from-classmap": [
+ "/Tests/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Fabien Potencier",
+ "email": "fabien@symfony.com"
+ },
+ {
+ "name": "Symfony Community",
+ "homepage": "https://symfony.com/contributors"
+ }
+ ],
+ "description": "Symfony BrowserKit Component",
+ "homepage": "https://symfony.com",
+ "time": "2017-06-24T09:29:48+00:00"
+ },
+ {
+ "name": "symfony/class-loader",
+ "version": "v3.3.4",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/symfony/class-loader.git",
+ "reference": "386a294d621576302e7cc36965d6ed53b8c73c4f"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/symfony/class-loader/zipball/386a294d621576302e7cc36965d6ed53b8c73c4f",
+ "reference": "386a294d621576302e7cc36965d6ed53b8c73c4f",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.5.9"
+ },
+ "require-dev": {
+ "symfony/finder": "~2.8|~3.0",
+ "symfony/polyfill-apcu": "~1.1"
+ },
+ "suggest": {
+ "symfony/polyfill-apcu": "For using ApcClassLoader on HHVM"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.3-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Symfony\\Component\\ClassLoader\\": ""
+ },
+ "exclude-from-classmap": [
+ "/Tests/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Fabien Potencier",
+ "email": "fabien@symfony.com"
+ },
+ {
+ "name": "Symfony Community",
+ "homepage": "https://symfony.com/contributors"
+ }
+ ],
+ "description": "Symfony ClassLoader Component",
+ "homepage": "https://symfony.com",
+ "time": "2017-06-02T09:51:43+00:00"
+ },
+ {
+ "name": "symfony/config",
+ "version": "v3.3.4",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/symfony/config.git",
+ "reference": "a094618deb9a3fe1c3cf500a796e167d0495a274"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/symfony/config/zipball/a094618deb9a3fe1c3cf500a796e167d0495a274",
+ "reference": "a094618deb9a3fe1c3cf500a796e167d0495a274",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.5.9",
+ "symfony/filesystem": "~2.8|~3.0"
+ },
+ "conflict": {
+ "symfony/dependency-injection": "<3.3",
+ "symfony/finder": "<3.3"
+ },
+ "require-dev": {
+ "symfony/dependency-injection": "~3.3",
+ "symfony/finder": "~3.3",
+ "symfony/yaml": "~3.0"
+ },
+ "suggest": {
+ "symfony/yaml": "To use the yaml reference dumper"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.3-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Symfony\\Component\\Config\\": ""
+ },
+ "exclude-from-classmap": [
+ "/Tests/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Fabien Potencier",
+ "email": "fabien@symfony.com"
+ },
+ {
+ "name": "Symfony Community",
+ "homepage": "https://symfony.com/contributors"
+ }
+ ],
+ "description": "Symfony Config Component",
+ "homepage": "https://symfony.com",
+ "time": "2017-06-16T12:40:34+00:00"
+ },
+ {
+ "name": "symfony/console",
+ "version": "v3.3.4",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/symfony/console.git",
+ "reference": "a97e45d98c59510f085fa05225a1acb74dfe0546"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/symfony/console/zipball/a97e45d98c59510f085fa05225a1acb74dfe0546",
+ "reference": "a97e45d98c59510f085fa05225a1acb74dfe0546",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.5.9",
+ "symfony/debug": "~2.8|~3.0",
+ "symfony/polyfill-mbstring": "~1.0"
+ },
+ "conflict": {
+ "symfony/dependency-injection": "<3.3"
+ },
+ "require-dev": {
+ "psr/log": "~1.0",
+ "symfony/config": "~3.3",
+ "symfony/dependency-injection": "~3.3",
+ "symfony/event-dispatcher": "~2.8|~3.0",
+ "symfony/filesystem": "~2.8|~3.0",
+ "symfony/http-kernel": "~2.8|~3.0",
+ "symfony/process": "~2.8|~3.0"
+ },
+ "suggest": {
+ "psr/log": "For using the console logger",
+ "symfony/event-dispatcher": "",
+ "symfony/filesystem": "",
+ "symfony/process": ""
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.3-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Symfony\\Component\\Console\\": ""
+ },
+ "exclude-from-classmap": [
+ "/Tests/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Fabien Potencier",
+ "email": "fabien@symfony.com"
+ },
+ {
+ "name": "Symfony Community",
+ "homepage": "https://symfony.com/contributors"
+ }
+ ],
+ "description": "Symfony Console Component",
+ "homepage": "https://symfony.com",
+ "time": "2017-07-03T13:19:36+00:00"
+ },
+ {
+ "name": "symfony/css-selector",
+ "version": "v3.3.4",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/symfony/css-selector.git",
+ "reference": "4d882dced7b995d5274293039370148e291808f2"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/symfony/css-selector/zipball/4d882dced7b995d5274293039370148e291808f2",
+ "reference": "4d882dced7b995d5274293039370148e291808f2",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.5.9"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.3-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Symfony\\Component\\CssSelector\\": ""
+ },
+ "exclude-from-classmap": [
+ "/Tests/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Jean-François Simon",
+ "email": "jeanfrancois.simon@sensiolabs.com"
+ },
+ {
+ "name": "Fabien Potencier",
+ "email": "fabien@symfony.com"
+ },
+ {
+ "name": "Symfony Community",
+ "homepage": "https://symfony.com/contributors"
+ }
+ ],
+ "description": "Symfony CssSelector Component",
+ "homepage": "https://symfony.com",
+ "time": "2017-05-01T15:01:29+00:00"
+ },
+ {
+ "name": "symfony/debug",
+ "version": "v3.3.4",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/symfony/debug.git",
+ "reference": "63b85a968486d95ff9542228dc2e4247f16f9743"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/symfony/debug/zipball/63b85a968486d95ff9542228dc2e4247f16f9743",
+ "reference": "63b85a968486d95ff9542228dc2e4247f16f9743",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.5.9",
+ "psr/log": "~1.0"
+ },
+ "conflict": {
+ "symfony/http-kernel": ">=2.3,<2.3.24|~2.4.0|>=2.5,<2.5.9|>=2.6,<2.6.2"
+ },
+ "require-dev": {
+ "symfony/http-kernel": "~2.8|~3.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.3-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Symfony\\Component\\Debug\\": ""
+ },
+ "exclude-from-classmap": [
+ "/Tests/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Fabien Potencier",
+ "email": "fabien@symfony.com"
+ },
+ {
+ "name": "Symfony Community",
+ "homepage": "https://symfony.com/contributors"
+ }
+ ],
+ "description": "Symfony Debug Component",
+ "homepage": "https://symfony.com",
+ "time": "2017-07-05T13:02:37+00:00"
+ },
+ {
+ "name": "symfony/dependency-injection",
+ "version": "v3.3.4",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/symfony/dependency-injection.git",
+ "reference": "986a633c92220ecb22ad06820a1df126c7a4f9eb"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/symfony/dependency-injection/zipball/986a633c92220ecb22ad06820a1df126c7a4f9eb",
+ "reference": "986a633c92220ecb22ad06820a1df126c7a4f9eb",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.5.9",
+ "psr/container": "^1.0"
+ },
+ "conflict": {
+ "symfony/config": "<3.3.1",
+ "symfony/finder": "<3.3",
+ "symfony/yaml": "<3.3"
+ },
+ "provide": {
+ "psr/container-implementation": "1.0"
+ },
+ "require-dev": {
+ "symfony/config": "~3.3",
+ "symfony/expression-language": "~2.8|~3.0",
+ "symfony/yaml": "~3.3"
+ },
+ "suggest": {
+ "symfony/config": "",
+ "symfony/expression-language": "For using expressions in service container configuration",
+ "symfony/finder": "For using double-star glob patterns or when GLOB_BRACE portability is required",
+ "symfony/proxy-manager-bridge": "Generate service proxies to lazy load them",
+ "symfony/yaml": ""
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.3-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Symfony\\Component\\DependencyInjection\\": ""
+ },
+ "exclude-from-classmap": [
+ "/Tests/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Fabien Potencier",
+ "email": "fabien@symfony.com"
+ },
+ {
+ "name": "Symfony Community",
+ "homepage": "https://symfony.com/contributors"
+ }
+ ],
+ "description": "Symfony DependencyInjection Component",
+ "homepage": "https://symfony.com",
+ "time": "2017-06-20T14:01:46+00:00"
+ },
+ {
+ "name": "symfony/dom-crawler",
+ "version": "v3.3.4",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/symfony/dom-crawler.git",
+ "reference": "fc2c588ce376e9fe04a7b8c79e3ec62fe32d95b1"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/symfony/dom-crawler/zipball/fc2c588ce376e9fe04a7b8c79e3ec62fe32d95b1",
+ "reference": "fc2c588ce376e9fe04a7b8c79e3ec62fe32d95b1",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.5.9",
+ "symfony/polyfill-mbstring": "~1.0"
+ },
+ "require-dev": {
+ "symfony/css-selector": "~2.8|~3.0"
+ },
+ "suggest": {
+ "symfony/css-selector": ""
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.3-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Symfony\\Component\\DomCrawler\\": ""
+ },
+ "exclude-from-classmap": [
+ "/Tests/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Fabien Potencier",
+ "email": "fabien@symfony.com"
+ },
+ {
+ "name": "Symfony Community",
+ "homepage": "https://symfony.com/contributors"
+ }
+ ],
+ "description": "Symfony DomCrawler Component",
+ "homepage": "https://symfony.com",
+ "time": "2017-05-25T23:10:31+00:00"
+ },
+ {
+ "name": "symfony/event-dispatcher",
+ "version": "v3.3.4",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/symfony/event-dispatcher.git",
+ "reference": "67535f1e3fd662bdc68d7ba317c93eecd973617e"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/symfony/event-dispatcher/zipball/67535f1e3fd662bdc68d7ba317c93eecd973617e",
+ "reference": "67535f1e3fd662bdc68d7ba317c93eecd973617e",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.5.9"
+ },
+ "conflict": {
+ "symfony/dependency-injection": "<3.3"
+ },
+ "require-dev": {
+ "psr/log": "~1.0",
+ "symfony/config": "~2.8|~3.0",
+ "symfony/dependency-injection": "~3.3",
+ "symfony/expression-language": "~2.8|~3.0",
+ "symfony/stopwatch": "~2.8|~3.0"
+ },
+ "suggest": {
+ "symfony/dependency-injection": "",
+ "symfony/http-kernel": ""
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.3-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Symfony\\Component\\EventDispatcher\\": ""
+ },
+ "exclude-from-classmap": [
+ "/Tests/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Fabien Potencier",
+ "email": "fabien@symfony.com"
+ },
+ {
+ "name": "Symfony Community",
+ "homepage": "https://symfony.com/contributors"
+ }
+ ],
+ "description": "Symfony EventDispatcher Component",
+ "homepage": "https://symfony.com",
+ "time": "2017-06-09T14:53:08+00:00"
+ },
+ {
+ "name": "symfony/filesystem",
+ "version": "v3.3.4",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/symfony/filesystem.git",
+ "reference": "311fa718389efbd8b627c272b9324a62437018cc"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/symfony/filesystem/zipball/311fa718389efbd8b627c272b9324a62437018cc",
+ "reference": "311fa718389efbd8b627c272b9324a62437018cc",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.5.9"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.3-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Symfony\\Component\\Filesystem\\": ""
+ },
+ "exclude-from-classmap": [
+ "/Tests/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Fabien Potencier",
+ "email": "fabien@symfony.com"
+ },
+ {
+ "name": "Symfony Community",
+ "homepage": "https://symfony.com/contributors"
+ }
+ ],
+ "description": "Symfony Filesystem Component",
+ "homepage": "https://symfony.com",
+ "time": "2017-06-24T09:29:48+00:00"
+ },
+ {
+ "name": "symfony/polyfill-mbstring",
+ "version": "v1.4.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/symfony/polyfill-mbstring.git",
+ "reference": "f29dca382a6485c3cbe6379f0c61230167681937"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/symfony/polyfill-mbstring/zipball/f29dca382a6485c3cbe6379f0c61230167681937",
+ "reference": "f29dca382a6485c3cbe6379f0c61230167681937",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.3.3"
+ },
+ "suggest": {
+ "ext-mbstring": "For best performance"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.4-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Symfony\\Polyfill\\Mbstring\\": ""
+ },
+ "files": [
+ "bootstrap.php"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Nicolas Grekas",
+ "email": "p@tchwork.com"
+ },
+ {
+ "name": "Symfony Community",
+ "homepage": "https://symfony.com/contributors"
+ }
+ ],
+ "description": "Symfony polyfill for the Mbstring extension",
+ "homepage": "https://symfony.com",
+ "keywords": [
+ "compatibility",
+ "mbstring",
+ "polyfill",
+ "portable",
+ "shim"
+ ],
+ "time": "2017-06-09T14:24:12+00:00"
+ },
+ {
+ "name": "symfony/translation",
+ "version": "v3.3.4",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/symfony/translation.git",
+ "reference": "35dd5fb003c90e8bd4d8cabdf94bf9c96d06fdc3"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/symfony/translation/zipball/35dd5fb003c90e8bd4d8cabdf94bf9c96d06fdc3",
+ "reference": "35dd5fb003c90e8bd4d8cabdf94bf9c96d06fdc3",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.5.9",
+ "symfony/polyfill-mbstring": "~1.0"
+ },
+ "conflict": {
+ "symfony/config": "<2.8",
+ "symfony/yaml": "<3.3"
+ },
+ "require-dev": {
+ "psr/log": "~1.0",
+ "symfony/config": "~2.8|~3.0",
+ "symfony/intl": "^2.8.18|^3.2.5",
+ "symfony/yaml": "~3.3"
+ },
+ "suggest": {
+ "psr/log": "To use logging capability in translator",
+ "symfony/config": "",
+ "symfony/yaml": ""
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.3-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Symfony\\Component\\Translation\\": ""
+ },
+ "exclude-from-classmap": [
+ "/Tests/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Fabien Potencier",
+ "email": "fabien@symfony.com"
+ },
+ {
+ "name": "Symfony Community",
+ "homepage": "https://symfony.com/contributors"
+ }
+ ],
+ "description": "Symfony Translation Component",
+ "homepage": "https://symfony.com",
+ "time": "2017-06-24T16:45:30+00:00"
+ },
+ {
+ "name": "symfony/yaml",
+ "version": "v3.3.4",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/symfony/yaml.git",
+ "reference": "1f93a8d19b8241617f5074a123e282575b821df8"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/symfony/yaml/zipball/1f93a8d19b8241617f5074a123e282575b821df8",
+ "reference": "1f93a8d19b8241617f5074a123e282575b821df8",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.5.9"
+ },
+ "require-dev": {
+ "symfony/console": "~2.8|~3.0"
+ },
+ "suggest": {
+ "symfony/console": "For validating YAML files using the lint command"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.3-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Symfony\\Component\\Yaml\\": ""
+ },
+ "exclude-from-classmap": [
+ "/Tests/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Fabien Potencier",
+ "email": "fabien@symfony.com"
+ },
+ {
+ "name": "Symfony Community",
+ "homepage": "https://symfony.com/contributors"
+ }
+ ],
+ "description": "Symfony Yaml Component",
+ "homepage": "https://symfony.com",
+ "time": "2017-06-15T12:58:50+00:00"
+ },
+ {
+ "name": "theseer/tokenizer",
+ "version": "1.1.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/theseer/tokenizer.git",
+ "reference": "cb2f008f3f05af2893a87208fe6a6c4985483f8b"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/theseer/tokenizer/zipball/cb2f008f3f05af2893a87208fe6a6c4985483f8b",
+ "reference": "cb2f008f3f05af2893a87208fe6a6c4985483f8b",
+ "shasum": ""
+ },
+ "require": {
+ "ext-dom": "*",
+ "ext-tokenizer": "*",
+ "ext-xmlwriter": "*",
+ "php": "^7.0"
+ },
+ "type": "library",
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Arne Blankerts",
+ "email": "arne@blankerts.de",
+ "role": "Developer"
+ }
+ ],
+ "description": "A small library for converting tokenized PHP source code into XML and potentially other formats",
+ "time": "2017-04-07T12:08:54+00:00"
+ },
+ {
+ "name": "webmozart/assert",
+ "version": "1.2.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/webmozart/assert.git",
+ "reference": "2db61e59ff05fe5126d152bd0655c9ea113e550f"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/webmozart/assert/zipball/2db61e59ff05fe5126d152bd0655c9ea113e550f",
+ "reference": "2db61e59ff05fe5126d152bd0655c9ea113e550f",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^5.3.3 || ^7.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^4.6",
+ "sebastian/version": "^1.0.1"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.3-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Webmozart\\Assert\\": "src/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Bernhard Schussek",
+ "email": "bschussek@gmail.com"
+ }
+ ],
+ "description": "Assertions to validate method input/output with nice error messages.",
+ "keywords": [
+ "assert",
+ "check",
+ "validate"
+ ],
+ "time": "2016-11-23T20:04:58+00:00"
+ }
+ ],
+ "aliases": [],
+ "minimum-stability": "stable",
+ "stability-flags": {
+ "behat/behat": 0,
+ "behat/mink-extension": 0,
+ "behat/mink-goutte-driver": 0
+ },
+ "prefer-stable": false,
+ "prefer-lowest": false,
+ "platform": {
+ "php": ">=5.5",
+ "ext-curl": "*",
+ "ext-gd": "*",
+ "ext-mbstring": "*",
+ "ext-xml": "*",
+ "ext-openssl": "*"
+ },
+ "platform-dev": {
+ "php": ">=7.0"
+ }
+}
diff --git a/doc/Privacy.md b/doc/Privacy.md
deleted file mode 100644
index 1ac019f5a..000000000
--- a/doc/Privacy.md
+++ /dev/null
@@ -1,77 +0,0 @@
-Privacy Policy
-==============
-
-
-##Summary##
-
-
-Q: Who can see my content?
-
-A: By default ANYBODY on the internet, UNLESS you restrict it. $Projectname allows you to choose the privacy level you desire. Restricted content will NOT be visible to "spy networks" and advertisers. It will be protected against eavesdropping by outsiders - to the best of our ability. Hub administrators with sufficient skills and patience MAY be able to eavesdrop on some private communications but they must expend effort to do so. Privacy modes exist within $Projectname which are even resistant to eavesdropping by skilled and determined hub administrators.
-
-Q: Can my content be censored?
-
-A: $Projectname (the network) CANNOT censor your content. Server and hub administrators are subject to local laws and MAY remove objectionable content from their site/hub. Anybody MAY become a hub administrator, including you; and therefore publish content which might otherwise be censored. You still MAY be subject to local laws.
-
-
-##Definitions
-
-**$Projectname**
-
-Otherwise referred to as "the network", $Projectname is a collection of individual computers/servers (aka **hubs**) which connect together to form a larger cooperative network.
-
-**hub**
-
-An individual computer or server connected to $Projectname. These are provided by a **hub administrator** and may be public or private, paid or free.
-
-**hub administrator**
-
-The system operator of an individual hub.
-
-##Policies
-
-**Public Information**
-
-Any information or anything posted by you within $Projectname MAY be public or visible to anybody on the internet. To the extent possible, $Projectname allows you to protect content and restrict who can view it.
-
-Your profile photo, your channel name, and the location (URL or network address) of your channel are visible to anybody on the internet and privacy controls will not affect the display of these items.
-
-You MAY additionally provide other profile information. Any information which you provide in your "default" or **public profile** MAY be transmitted to other hubs in $Projectname and additionally MAY be displayed in the channel directory. You can restrict the viewing of this profile information. It may be restricted only to members of your hub, or only connections (friends), or other limited sets of viewers as you desire. If you wish for your profile to be restricted, you must set the appropriate privacy setting, or simply DO NOT provide additional information.
-
-**Content**
-
-Content you provide (status posts, photos, files, etc.) belongs to you. $Projectname default is to publish content openly and visible to anybody on the internet (PUBLIC). You MAY control this in your channel settings and restrict the default permissions or you MAY restrict the visibility of any single published item separately (PRIVATE). $Projectname developers will ensure that restricted content is ONLY visible to those in the restriction list - to the best of their ability.
-
-Content (especially status posts) that you share with other networks or that you have made visible to anybody on the internet (PUBLIC) cannot easily be taken back once it has been published. It MAY be shared with other networks and made available through RSS/Atom feeds. It may also be syndicated on other $Projectname sites. It MAY appear on other networks and websites and be visible in internet searches. If you do not wish this default behaviour please adjust your channel settings and restrict who can see your content.
-
-**Comments and Forum posts**
-
-Comments to posts that were created by others and posts which are designated as forum posts belong to you as the creator/author, but the distribution of these posts is not under your direct control, and you relinquish SOME rights to these items. These posts/comments MAY be re-distributed to others, and MAY be visible to anybody on the internet. In the case of comments, the creator of the "first message" in the thread (conversation) to which you are replying controls the distribution of all comments and replies to that message. They "own" and therefore have certain rights with regard to the entire conversation (including all comments contained within it). You can still edit or delete the comment, but the conversation owner also has rights to edit, delete, re-distribute, and backup/restore any or all the content from the conversation.
-
-**Private Information**
-
-$Projectname developers will ensure that any content you provide which is designated as PRIVATE will be protected against eavesdropping - to the best of their ability. Private channel content CAN be seen in the database of every involved hub administrator, but private messages are obscured in the database. The latter means that it is very difficult, but NOT impossible for this content to be seen by a hub administrator. Private channel content and private messages are also stripped from email notifications. End to end encryption is provided as an optional feature and this CANNOT be seen, even by a determined administrator.
-
-##Identity Privacy
-
-Privacy for your identity is another aspect. Because you have a decentralized identity in $Projectname, your privacy extends beyond your home hub. If you want to have complete control of your privacy and security you should run your own hub on a dedicated server. For many people, this is complicated and may stretch their technical abilities. So let's list a few precautions you can make to assure your privacy as much as possible.
-
-A decentralized identity has a lot of advantages and gives you al lot of interesting features, but you should be aware of the fact that your identity is known by other hubs in $Projectname network. One of those advantages is that other channels can serve you customized content and allow you to see private things (such as private photos which others wish to share with you). Because of this those channels need to know who you are. But we understand that sometimes those other channels know more from you than you might desire. For instance the plug-in Visage that can tell a channel owner the last time you visit their profile. You can easily OPT-OUT of this low level and we think, harmless tracking.
-
-* You can enable [Do Not Track (DNT)](http://donottrack.us/) in your web browser. We respect this new privacy policy proposal. All modern browsers support DNT. You will find it in the privacy settings of your browsers or else you can consult the web browser's manual. This will not affect the functionality of $Projectname. This setting is probably enough for most people.
-
-*You can [disable publication](settings) of your channel in our channel directory. If you want people to find your channel, you should give your channel address directly to them. We think this is a good indication that you prefer extra privacy and automatically enable "Do Not Track" if this is the case.
-
-* You can have a blocked hub. That means that all channels and content on that hub is not public, and not visible to the outside world. This is something only your hub administrator can do. We also respect this and automatically enable "Do Not Track" if it is set.
-
-###Censorship
-
-$Projectname is a global network which is inclusive of all religions and cultures. This does not imply that every member of the network feels the same way you do on contentious issues, and some people may be STRONGLY opposed to the content you post. In general, if you wish to post something that you know may nor be universally acceptable, the best approach is to restrict the audience using privacy controls to a small circle of friends.
-
-$Projectname as a network provider is unable to censor content. However, hub administrators MAY censor any content which appears on their hub to comply with local laws or even personal judgement. Their decision is final. If you have issues with any hub administrator, you may move your account and postings to another site which is more in line with your expectations. Please check (periodically) the [Terms of Service](help/TermsOfService) of your hub to learn about any rules or guidelines. If your content consists of material which is illegal or may cause issues, you are STRONGLY encouraged to host your own (become a hub administrator). You may still find that your content is blocked on some hubs, but $Projectname as a network cannot block it from being posted.
-
-$Projectname RECOMMENDS that hub administrators provide a grace period of 1-2 days between warning an account holder of content that needs to be removed and physically removing or disabling the account. This will give the content owner an opportunity to export their channel meta-data and import it to another site. In rare cases the content may be of such a nature to justify the immediate termination of the account. This is a hub decision, not a $Projectname decision.
-
-If you typically and regularly post content of an adult or offensive nature, you are STRONGLY encouraged to mark your account "NSFW" (Not Safe For Work). This will prevent the display of your profile photo in the directory except to viewers that have chosen to disable "safe mode". If your profile photo is found by directory administrators to be adult or offensive, the directory administrator MAY flag your profile photo as NSFW. There is currently no official mechanism to contest or reverse this decision, which is why you SHOULD mark your own account NSFW if it is likely to be inappropriate for general audiences.
-
-#include doc/macros/main_footer.bb;
diff --git a/doc/Widgets.md b/doc/Widgets.md
index 8442bf687..4ad899a0f 100644
--- a/doc/Widgets.md
+++ b/doc/Widgets.md
@@ -117,6 +117,7 @@ Some/many of these widgets have restrictions which may restrict the type of page
* forums - provide a list of connected public forums with unseen counts for the current logged-in channel.
<br />&nbsp;<br />
+* activity - provide a list of authors of unread network content for the current logged-in channel.
* album - provides a widget containing a complete photo album from albums belonging to the page owner; this may be too large to present in a sidebar region as is best implemented as a content region widget.
* args:
diff --git a/doc/about.bb b/doc/about.bb
deleted file mode 100644
index 1ec1cf28e..000000000
--- a/doc/about.bb
+++ /dev/null
@@ -1,24 +0,0 @@
-[b]About[/b]
-
-$Projectname is a decentralized communication network, which aims to provide communication that is censorship-resistant, privacy-respecting, and thus free from the oppressive claws of contemporary corporate communication giants. These giants function primarily as spy networks for paying clients of all sorts and types, in addition to monopolizing and centralizing the Internet; a feature that was not part of the original and revolutionary goals that produced the World Wide Web.
-
-$Projectname is free and open source. It is designed to scale from a $35 Raspberry Pi, to top of the line AMD and Intel Xeon-powered multi-core enterprise servers. It can be used to support communication between a few individuals, or scale to many thousands and more.
-
-$Projectname aims to be skill and resource agnostic. It is easy to use by everyday computer users, as well as by systems administrators and developers.
-
-How you use it depends on how you want to use it.
-
-It is written in the PHP scripting language, thus making it trivial to install on any hosting platform in use today. This includes self-hosting at home, at hosting providers such as [url=http://mediatemple.com/]Media Temple[/url] and [url=http://www.dreamhost.com/]Dreamhost[/url], or on virtual and dedicated servers, offered by the likes of [url=https://www.linode.com]Linode[/url], [url=http://greenqloud.com]GreenQloud[/url] or [url=https://aws.amazon.com]Amazon AWS[/url].
-
-In other words, $Projectname can run on any computing platform that comes with a web server, a MySQL-compatible database, and the PHP scripting language.
-
-Along the way, $Projectname offers a number of unique goodies:
-
-[b]Single-click user identification:[/b] meaning you can access sites on $Projectname simply by clicking on links to remote sites. Authentication just happens automagically behind the scenes. Forget about remembering multiple user names with multiple passwords when accessing different sites online.
-
-[b]Cloning:[/b] of online identities. Your online presence no longer has to be tied to a single server, domain name or IP address. You can clone and import your identity (or channel as we call it) to another server (or, a hub as servers are known in $Projectname). Now, should your primary hub go down, no worries, your contacts, posts[i]*[/i], and messages[i]*[/i] will automagically continue to be available and accessible under your cloned channel. [i](*: only posts and messages as from the moment you cloned your channel)[/i]
-
-[b]Privacy:[/b] $Projectname identities (Zot IDs) can be deleted, backed up/downloaded, and cloned. The user is in full control of their data. Should you decide to delete all your content and erase your Zot ID, all you have to do is click on a link and it's immediately deleted from the hub. No questions, no fuss.
-
-#include doc/macros/main_footer.bb;
-
diff --git a/doc/about/about.bb b/doc/about/about.bb
new file mode 100644
index 000000000..b927e80c0
--- /dev/null
+++ b/doc/about/about.bb
@@ -0,0 +1,204 @@
+[h3]What is $Projectname?[/h3]
+$Projectname is a [b]free and open source[/b] set of web applications and services running on a special kind of web server, called a "hub", that can connect to other hubs in a decentralised network we like to call "the grid", providing sophisticated communications, identity, and access control services which work together seamlessly across domains and independent websites. It allows anybody to publicly or [b]privately[/b] publish content via "channels", which are the fundamental, cryptographically secured identities that provide authentication independently of the hubs which host them. This revolutionary liberation of online identity from individual servers and domains is called "nomadic identity", and it is powered by the Zot protocol, a new framework for decentralised access control with fine-grained, extensible permissions.
+
+[h3]Right... so what is $Projectname?[/h3]
+From the practical perspective of hub members who use the software, $Projectname offers a variety of familiar, integrated web apps and services, including:
+[ul]
+[li]social networking discussion threads[/li]
+[li]cloud file storage[/li]
+[li]calendar and contacts (with CalDAV and CardDAV support)[/li]
+[li]webpage hosting with a content management system[/li]
+[li]wiki[/li]
+[li]and more...[/li][/ul]
+While all of these apps and services can be found in other software packages, only $Projectname allows you to set permissions for groups and individuals who may not even have accounts on your hub! In typical web apps, if you want to share things privately on the internet, the people you share with must have accounts on the server hosting your data; otherwise, there is no robust way for your server to [i]authenticate[/i] visitors to the site to know whether to grant them access. $Projectname solves this problem with an advanced system of [i]remote authentication[/i] that validates the identity of visitors by employing techniques that include public key cryptography.
+
+[h3]Software Stack[/h3]
+The $Projectname software stack is a relatively standard webserver application written primarily in PHP/MySQL and [url=https://github.com/redmatrix/hubzilla/blob/master/install/INSTALL.txt]requiring little more than a web server, a MySQL-compatible database, and the PHP scripting language[/url]. It is designed to be easily installable by those with basic website administration skills on typical shared hosting platforms with a broad range of computing hardware. It is also easily extended via plugins and themes and other third-party tools.
+
+[h3]Glossary[/h3]
+[dl terms="b"]
+[*= hub] An instance of this software running on a standard web server
+
+[*= grid] The global network of hubs that exchange information with each other using the Zot protocol.
+
+[*= channel] The fundamental identity on the grid. A channel can represent a person, a blog, or a forum to name a few. Channels can make connections with other channels to share information with highly detailed permissions.
+
+[*= clone] Channels can have clones associated with separate and otherwise unrelated accounts on independent hubs. Communications shared with a channel are synchronized among the channel clones, allowing a channel to send and receive messages and access shared content from multiple hubs. This provides resilience against network and hardware failures, which can be a significant problem for self-hosted or limited-resource web servers. Cloning allows you to completely move a channel from one hub to another, taking your data and connections with you. See nomadic identity.
+
+[*= nomadic identity] The ability to authenticate and easily migrate an identity across independent hubs and web domains. Nomadic identity provides true ownership of an online identity, because the identities of the channels controlled by an account on a hub are not tied to the hub itself. A hub is more like a "host" for channels. With Hubzilla, you don't have an "account" on a server like you do on typical websites; you own an identity that you can take with you across the grid by using clones.
+
+[*= [url=[baseurl]/help/developer/zot_protocol]Zot[/url]] The novel JSON-based protocol for implementing secure decentralised communications and services. It differs from many other communication protocols by building communications on top of a decentralised identity and authentication framework. The authentication component is similar to OpenID conceptually but is insulated from DNS-based identities. Where possible remote authentication is silent and invisible. This provides a mechanism for internet-scale distributed access control which is unobtrusive.
+[/dl]
+
+[h3]Features[/h3]
+This page lists some of the core features of $Projectname that are bundled with the official release. $Projectname is a highly extensible platform, so more features and capabilities can be added via additional themes and plugins.
+
+[h4]Affinity Slider[/h4]
+
+When adding connnections in $Projectname, members have the option of assigning "affinity" levels (how close your friendship is) to the new connection. For example, when adding someone who happens to be a person whose blog you follow, you could assign their channel an affinity level of &quot;Acquaintances&quot;.
+
+On the other hand, when adding a friend's channel, they could be placed under the affinity level of &quot;Friends&quot;.
+
+At this point, $Projectname [i]Affinity Slider[/i] tool, which usually appears at the top of your &quot;Matrix&quot; page, adjusts the content on the page to include those within the desired affinity range. Channels outside that range will not be displayed, unless you adjust the slider to include them.
+
+The Affinity Slider allows instantaneous filtering of large amounts of content, grouped by levels of closeness.
+
+[h4]Connection Filtering[/h4]
+
+You have the ability to control precisely what appears in your stream using the optional "Connection Filter". When enabled, the Connection Editor provides inputs for selecting criteria which needs to be matched in order to include or exclude a specific post from a specific channel. Once a post has been allowed, all comments to that post are allowed regardless of whether they match the selection criteria. You may select words that if present block the post or ensure it is included in your stream. Regular expressions may be used for even finer control, as well as hashtags or even the detected language of the post.
+
+[h4]Access Control Lists[/h4]
+
+When sharing content, members have the option of restricting who sees the content. By clicking on the padlock underneath the sharing box, one may choose desired recipients of the post, by clicking on their names.
+
+Once sent, the message will be viewable only by the sender and the selected recipients. In other words, the message will not appear on any public walls.
+
+Access Control Lists may be applied to content and posts, photos, events, webpages, chatrooms and files.
+
+[h4]Single Sign-on[/h4]
+
+Access Control Lists work for all channels in the grid due to our unique single sign-on technology. Most internal links provide an identity token which can be verified on other $Projectname sites and used to control access to private resources. You login once to your home hub. After that, authentication to all $Projectname resources is "magic".
+
+
+[h4]WebDAV enabled File Storage[/h4]
+
+Files may be uploaded to your personal storage area using your operating system utilities (drag and drop in most cases). You may protect these files with Access Control Lists to any combination of $Projectname members (including some third party network members) or make them public.
+
+[h4]Photo Albums[/h4]
+
+Store photos in albums. All your photos may be protected by Access Control Lists.
+
+[h4]Events Calendar[/h4]
+
+Create and manage events and tasks, which may also be protected with Access Control Lists. Events can be imported/exported to other software using the industry standard vcalendar/iCal format and shared in posts with others. Birthday events are automatically added from your friends and converted to your correct timezone so that you will know precisely when the birthday occurs - no matter where you are located in the world in relation to the birthday person. Events are normally created with attendance counters so your friends and connections can RSVP instantly.
+
+[h4]Chatrooms[/h4]
+
+You may create any number of personal chatrooms and allow access via Access Control Lists. These are typically more secure than XMPP, IRC, and other Instant Messaging transports, though we also allow using these other services via plugins.
+
+[h4]Webpage Building[/h4]
+
+$Projectname has many "Content Management" creation tools for building webpages, including layout editing, menus, blocks, widgets, and page/content regions. All of these may be access controlled so that the resulting pages are private to their intended audience.
+
+[h4]Apps[/h4]
+
+Apps may be built and distributed by members. These are different from traditional "vendor lockin" apps because they are controlled completely by the author - who can provide access control on the destination app pages and charge accordingly for this access. Most apps in $Projectname are free and can be created easily by those with no programming skills.
+
+[h4]Layout[/h4]
+
+Page layout is based on a description language called Comanche. $Projectname is itself written in Comanche layouts which you can change. This allows a level of customisation you won't typically find in so-called "multi-user environments".
+
+[h4]Bookmarks[/h4]
+
+Share and save/manage bookmarks from links provided in conversations.
+
+
+[h4]Private Message Encryption and Privacy Concerns[/h4]
+
+Private mail is stored in an obscured format. While this is not bullet-proof it typically prevents casual snooping by the site administrator or ISP.
+
+Each $Projectname channel has it's own unique set of private and associated public RSA 4096-bit keys, generated when the channels is first created. This is used to protect private messages and posts in transit.
+
+Additionally, messages may be created utilising "end-to-end encryption" which cannot be read by $Projectname operators or ISPs or anybody who does not know the passcode.
+
+Public messages are generally not encrypted in transit or in storage.
+
+Private messages may be retracted (unsent) although there is no guarantee the recipient hasn't read it yet.
+
+Posts and messages may be created with an expiration date, at which time they will be deleted/removed on the recipient's site.
+
+
+[h4]Service Federation[/h4]
+
+In addition to addon "cross-post connectors" to a variety of alternate networks, there is native support for importation of content from RSS/Atom feeds and using this to create special channels. Plugins are also available to communicate with others using the Diaspora and GNU-Social (OStatus) protocols. These networks do not support nomadic identity or cross-domain access control; however basic communications are supported to/from Diaspora, Friendica, GNU-Social, Mastodon and other providers which use these protocols.
+
+There is also experimental support for OpenID authentication which may be used in Access Control Lists. This is a work in progress. Your $Projectname hub may be used as an OpenID provider to authenticate you to external services which use this technology.
+
+Channels may have permissions to become "derivative channels" where two or more existing channels combine to create a new topical channel.
+
+[h4]Privacy Groups[/h4]
+
+Our implementation of privacy groups is similar to Google "Circles" and Diaspora "Aspects". This allows you to filter your incoming stream by selected groups, and automatically set the outbound Access Control List to only those in that privacy group when you post. You may over-ride this at any time (prior to sending the post).
+
+
+[h4]Directory Services[/h4]
+
+We provide easy access to a directory of members and provide decentralised tools capable of providing friend "suggestions". The directories are normal $Projectname sites which have chosen to accept the directory server role. This requires more resources than most typical sites so is not the default. Directories are synchronised and mirrored so that they all contain up-to-date information on the entire network (subject to normal propagation delays).
+
+
+[h4]TLS/SSL[/h4]
+
+For $Projectname hubs that use TLS/SSL, client to server communications are encrypted via TLS/SSL. Given recent disclosures in the media regarding widespread, global surveillance and encryption circumvention by the NSA and GCHQ, it is reasonable to assume that HTTPS-protected communications may be compromised in various ways. Private communications are consequently encrypted at a higher level before sending offsite.
+
+[h4]Channel Settings[/h4]
+
+When a channel is created, a role is chosen which applies a number of pre-configured security and privacy settings. These are chosen for best practives to maintain privacy at the requested levels.
+
+If you choose a "custom" privacy role, each channel allows fine-grained permissions to be set for various aspects of communication. For example, under the &quot;Security and Privacy Settings&quot; heading, each aspect on the left side of the page, has six (6) possible viewing/access options, that can be selected by clicking on the dropdown menu. There are also a number of other privacy settings you may edit.
+
+The options are:
+
+ - Nobody except yourself.
+ - Only those you specifically allow.
+ - Anybody in your address book.
+ - Anybody on this website.
+ - Anybody in this network.
+ - Anybody authenticated.
+ - Anybody on the Internet.
+
+
+[h4]Public and Private Forums[/h4]
+
+Forums are typically channels which may be open to participation from multiple authors. There are currently two mechanisms to post to forums: 1) "wall-to-wall" posts and 2) via forum @mention tags. Forums can be created by anybody and used for any purpose. The directory contains an option to search for public forums. Private forums can only be posted to and often only seen by members.
+
+
+[h4]Account Cloning[/h4]
+
+Accounts in $Projectname are referred to as [i]nomadic identities[/i], because a member's identity is not bound to the hub where the identity was originally created. For example, when you create a Facebook or Gmail account, it is tied to those services. They cannot function without Facebook.com or Gmail.com.
+
+By contrast, say you've created a $Projectname identity called [b]tina@$Projectnamehub.com[/b]. You can clone it to another $Projectname hub by choosing the same, or a different name: [b]liveForever@Some$ProjectnameHub.info[/b]
+
+Both channels are now synchronized, which means all your contacts and preferences will be duplicated on your clone. It doesn't matter whether you send a post from your original hub, or the new hub. Posts will be mirrored on both accounts.
+
+This is a rather revolutionary feature, if we consider some scenarios:
+
+ - What happens if the hub where an identity is based suddenly goes offline? Without cloning, a member will not be able to communicate until that hub comes back online (no doubt many of you have seen and cursed the Twitter "Fail Whale"). With cloning, you just log into your cloned account, and life goes on happily ever after.
+
+ - The administrator of your hub can no longer afford to pay for his free and public $Projectname hub. He announces that the hub will be shutting down in two weeks. This gives you ample time to clone your identity(ies) and preserve your$Projectname relationships, friends and content.
+
+ - What if your identity is subject to government censorship? Your hub provider may be compelled to delete your account, along with any identities and associated data. With cloning, $Projectname offers [b]censorship resistance[/b]. You can have hundreds of clones, if you wanted to, all named different, and existing on many different hubs, strewn around the internet.
+
+$Projectname offers interesting new possibilities for privacy. You can read more at the &lt;&lt;Private Communications Best Practices&gt;&gt; page.
+
+Some caveats apply. For a full explanation of identity cloning, read the &lt;HOW TO CLONE MY IDENTITY&gt;.
+
+[h4]Multiple Profiles[/h4]
+
+Any number of profiles may be created containing different information and these may be made visible to certain of your connections/friends. A "default" profile can be seen by anybody and may contain limited information, with more information available to select groups or people. This means that the profile (and site content) your beer-drinking buddies see may be different than what your co-workers see, and also completely different from what is visible to the general public.
+
+[h4]Account Backup[/h4]
+
+$Projectname offers a simple, one-click account backup, where you can download a complete backup of your profile(s). Backups can then be used to clone or restore a profile.
+
+[h4]Account Deletion[/h4]
+Accounts can be immediately deleted by clicking on a link. That's it. All associated content is then deleted from the grid (this includes posts and any other content produced by the deleted profile). Depending on the number of connections you have, the process of deleting remote content could take some time but it is scheduled to happen as quickly as is practical.
+
+[h4]Deletion of content[/h4]
+Any content created in $Projectname remains under the control of the member (or channel) that originally created it. At any time, a member can delete a message, or a range of messages. The deletion process ensures that the content is deleted, regardless of whether it was posted on a channel's primary (home) hub, or on another hub, where the channel was remotely authenticated via Zot ($Projectname communication and authentication protocol).
+
+[h4]Media[/h4]
+Similar to any other modern blogging system, social network, or a micro-blogging service, $Projectname supports the uploading of files, embedding of videos, linking web pages.
+
+[h4]Previewing/Editing[/h4]
+Posts and comments can be previewed prior to sending and edited after sending.
+
+[h4]Voting/Consensus[/h4]
+Posts can be turned into "consensus" items which allows readers to offer feedback, which is collated into "agree", "disagree", and "abstain" counters. This lets you gauge interest for ideas and create informal surveys.
+
+[h4]Extending $Projectname[/h4]
+
+$Projectname can be extended in a number of ways, through site customisation, personal customisation, option setting, themes, and addons/plugins.
+
+[h4]API[/h4]
+
+An API is available for use by third-party services. A plugin also provides a basic implementation of the Twitter API (for which hundreds of third-party tools exist). Access may be provided by login/password or OAuth, and client registration of OAuth applications is provided.
diff --git a/doc/about/about_hubzilla.bb b/doc/about/about_hubzilla.bb
deleted file mode 100644
index e9485ffa6..000000000
--- a/doc/about/about_hubzilla.bb
+++ /dev/null
@@ -1,209 +0,0 @@
-[h3]What is Hubzilla?[/h3]
-$Projectname is a [b]free and open source[/b] set of web applications and services running on a special kind of web server, called a "hub", that can connect to other hubs in a decentralised network we like to call "the grid", providing sophisticated communications, identity, and access control services which work together seamlessly across domains and independent websites. It allows anybody to publicly or [b]privately[/b] publish content via "channels", which are the fundamental, cryptographically secured identities that provide authentication independently of the hubs which host them. This revolutionary liberation of online identity from individual servers and domains is called "nomadic identity", and it is powered by the Zot protocol, a new framework for decentralised access control with fine-grained, extensible permissions.
-
-[h3]Right... so what is Hubzilla?[/h3]
-From the practical perspective of hub members who use the software, $Projectname offers a variety of familiar, integrated web apps and services, including:
-[ul]
-[li]social networking discussion threads[/li]
-[li]cloud file storage[/li]
-[li]calendar and contacts (with CalDAV and CardDAV support)[/li]
-[li]webpage hosting with a content management system[/li]
-[li]wiki[/li]
-[li]and more...[/li][/ul]
-While all of these apps and services can be found in other software packages, only $Projectname allows you to set permissions for groups and individuals who may not even have accounts on your hub! In typical web apps, if you want to share things privately on the internet, the people you share with must have accounts on the server hosting your data; otherwise, there is no robust way for your server to [i]authenticate[/i] visitors to the site to know whether to grant them access. $Projectname solves this problem with an advanced system of [i]remote authentication[/i] that validates the identity of visitors by employing techniques that include public key cryptography.
-
-[h3]Software Stack[/h3]
-The $Projectname software stack is a relatively standard webserver application written primarily in PHP/MySQL and [url=https://github.com/redmatrix/hubzilla/blob/master/install/INSTALL.txt]requiring little more than a web server, a MySQL-compatible database, and the PHP scripting language[/url]. It is designed to be easily installable by those with basic website administration skills on typical shared hosting platforms with a broad range of computing hardware. It is also easily extended via plugins and themes and other third-party tools.
-
-[h3]Additional Resources and Links[/h3]
-[list][*][url=http://hubzilla.org]Hubzilla project website[/url]
-[*][url=https://github.com/redmatrix/hubzilla]Hubzilla core code repository[/url]
-[*][url=https://github.com/redmatrix/hubzilla-addons]Hubzilla official addons repository[/url][/list]
-
-[h3]Glossary[/h3]
-[dl terms="b"]
-[*= hub] An instance of the Hubzilla software running on a standard web server
-
-[*= grid] The global network of hubs that exchange information with each other using the Zot protocol.
-
-[*= channel] The fundamental identity on the grid. A channel can represent a person, a blog, or a forum to name a few. Channels can make connections with other channels to share information with highly detailed permissions.
-
-[*= clone] Channels can have clones associated with separate and otherwise unrelated accounts on independent hubs. Communications shared with a channel are synchronized among the channel clones, allowing a channel to send and receive messages and access shared content from multiple hubs. This provides resilience against network and hardware failures, which can be a significant problem for self-hosted or limited-resource web servers. Cloning allows you to completely move a channel from one hub to another, taking your data and connections with you. See nomadic identity.
-
-[*= nomadic identity] The ability to authenticate and easily migrate an identity across independent hubs and web domains. Nomadic identity provides true ownership of an online identity, because the identities of the channels controlled by an account on a hub are not tied to the hub itself. A hub is more like a "host" for channels. With Hubzilla, you don't have an "account" on a server like you do on typical websites; you own an identity that you can take with you across the grid by using clones.
-
-[*= [url=[baseurl]/help/developer/zot_protocol]Zot[/url]] The novel JSON-based protocol for implementing secure decentralised communications and services. It differs from many other communication protocols by building communications on top of a decentralised identity and authentication framework. The authentication component is similar to OpenID conceptually but is insulated from DNS-based identities. Where possible remote authentication is silent and invisible. This provides a mechanism for internet-scale distributed access control which is unobtrusive.
-[/dl]
-
-[h3]Features[/h3]
-This page lists some of the core features of $Projectname that are bundled with the official release. $Projectname is a highly extensible platform, so more features and capabilities can be added via additional themes and plugins.
-
-[h4]Affinity Slider[/h4]
-
-When adding connnections in $Projectname, members have the option of assigning "affinity" levels (how close your friendship is) to the new connection. For example, when adding someone who happens to be a person whose blog you follow, you could assign their channel an affinity level of &quot;Acquaintances&quot;.
-
-On the other hand, when adding a friend's channel, they could be placed under the affinity level of &quot;Friends&quot;.
-
-At this point, $Projectname [i]Affinity Slider[/i] tool, which usually appears at the top of your &quot;Matrix&quot; page, adjusts the content on the page to include those within the desired affinity range. Channels outside that range will not be displayed, unless you adjust the slider to include them.
-
-The Affinity Slider allows instantaneous filtering of large amounts of content, grouped by levels of closeness.
-
-[h4]Connection Filtering[/h4]
-
-You have the ability to control precisely what appears in your stream using the optional "Connection Filter". When enabled, the Connection Editor provides inputs for selecting criteria which needs to be matched in order to include or exclude a specific post from a specific channel. Once a post has been allowed, all comments to that post are allowed regardless of whether they match the selection criteria. You may select words that if present block the post or ensure it is included in your stream. Regular expressions may be used for even finer control, as well as hashtags or even the detected language of the post.
-
-[h4]Access Control Lists[/h4]
-
-When sharing content, members have the option of restricting who sees the content. By clicking on the padlock underneath the sharing box, one may choose desired recipients of the post, by clicking on their names.
-
-Once sent, the message will be viewable only by the sender and the selected recipients. In other words, the message will not appear on any public walls.
-
-Access Control Lists may be applied to content and posts, photos, events, webpages, chatrooms and files.
-
-[h4]Single Sign-on[/h4]
-
-Access Control Lists work for all channels in the grid due to our unique single sign-on technology. Most internal links provide an identity token which can be verified on other $Projectname sites and used to control access to private resources. You login once to your home hub. After that, authentication to all $Projectname resources is "magic".
-
-
-[h4]WebDAV enabled File Storage[/h4]
-
-Files may be uploaded to your personal storage area using your operating system utilities (drag and drop in most cases). You may protect these files with Access Control Lists to any combination of $Projectname members (including some third party network members) or make them public.
-
-[h4]Photo Albums[/h4]
-
-Store photos in albums. All your photos may be protected by Access Control Lists.
-
-[h4]Events Calendar[/h4]
-
-Create and manage events and tasks, which may also be protected with Access Control Lists. Events can be imported/exported to other software using the industry standard vcalendar/iCal format and shared in posts with others. Birthday events are automatically added from your friends and converted to your correct timezone so that you will know precisely when the birthday occurs - no matter where you are located in the world in relation to the birthday person. Events are normally created with attendance counters so your friends and connections can RSVP instantly.
-
-[h4]Chatrooms[/h4]
-
-You may create any number of personal chatrooms and allow access via Access Control Lists. These are typically more secure than XMPP, IRC, and other Instant Messaging transports, though we also allow using these other services via plugins.
-
-[h4]Webpage Building[/h4]
-
-$Projectname has many "Content Management" creation tools for building webpages, including layout editing, menus, blocks, widgets, and page/content regions. All of these may be access controlled so that the resulting pages are private to their intended audience.
-
-[h4]Apps[/h4]
-
-Apps may be built and distributed by members. These are different from traditional "vendor lockin" apps because they are controlled completely by the author - who can provide access control on the destination app pages and charge accordingly for this access. Most apps in $Projectname are free and can be created easily by those with no programming skills.
-
-[h4]Layout[/h4]
-
-Page layout is based on a description language called Comanche. $Projectname is itself written in Comanche layouts which you can change. This allows a level of customisation you won't typically find in so-called "multi-user environments".
-
-[h4]Bookmarks[/h4]
-
-Share and save/manage bookmarks from links provided in conversations.
-
-
-[h4]Private Message Encryption and Privacy Concerns[/h4]
-
-Private mail is stored in an obscured format. While this is not bullet-proof it typically prevents casual snooping by the site administrator or ISP.
-
-Each $Projectname channel has it's own unique set of private and associated public RSA 4096-bit keys, generated when the channels is first created. This is used to protect private messages and posts in transit.
-
-Additionally, messages may be created utilising "end-to-end encryption" which cannot be read by $Projectname operators or ISPs or anybody who does not know the passcode.
-
-Public messages are generally not encrypted in transit or in storage.
-
-Private messages may be retracted (unsent) although there is no guarantee the recipient hasn't read it yet.
-
-Posts and messages may be created with an expiration date, at which time they will be deleted/removed on the recipient's site.
-
-
-[h4]Service Federation[/h4]
-
-In addition to addon "cross-post connectors" to a variety of alternate networks, there is native support for importation of content from RSS/Atom feeds and using this to create special channels. Also, an experimental but working implementation of the Diaspora protocol allows communication with people on the Friendica and Diaspora decentralised social networks. This is currently marked experimental because these networks do not have the same level of privacy and encryption features and abilities as $Projectname and may present privacy risks.
-
-There is also experimental support for OpenID authentication which may be used in Access Control Lists. This is a work in progress. Your $Projectname hub may be used as an OpenID provider to authenticate you to external services which use this technology.
-
-Channels may have permissions to become "derivative channels" where two or more existing channels combine to create a new topical channel.
-
-[h4]Privacy Groups[/h4]
-
-Our implementation of privacy groups is similar to Google "Circles" and Diaspora "Aspects". This allows you to filter your incoming stream by selected groups, and automatically set the outbound Access Control List to only those in that privacy group when you post. You may over-ride this at any time (prior to sending the post).
-
-
-[h4]Directory Services[/h4]
-
-We provide easy access to a directory of members and provide decentralised tools capable of providing friend "suggestions". The directories are normal $Projectname sites which have chosen to accept the directory server role. This requires more resources than most typical sites so is not the default. Directories are synchronised and mirrored so that they all contain up-to-date information on the entire network (subject to normal propagation delays).
-
-
-[h4]TLS/SSL[/h4]
-
-For $Projectname hubs that use TLS/SSL, client to server communications are encrypted via TLS/SSL. Given recent disclosures in the media regarding widespread, global surveillance and encryption circumvention by the NSA and GCHQ, it is reasonable to assume that HTTPS-protected communications may be compromised in various ways. Private communications are consequently encrypted at a higher level before sending offsite.
-
-[h4]Channel Settings[/h4]
-
-When a channel is created, a role is chosen which applies a number of pre-configured security and privacy settings. These are chosen for best practives to maintain privacy at the requested levels.
-
-If you choose a "custom" privacy role, each channel allows fine-grained permissions to be set for various aspects of communication. For example, under the &quot;Security and Privacy Settings&quot; heading, each aspect on the left side of the page, has six (6) possible viewing/access options, that can be selected by clicking on the dropdown menu. There are also a number of other privacy settings you may edit.
-
-The options are:
-
- - Nobody except yourself.
- - Only those you specifically allow.
- - Anybody in your address book.
- - Anybody on this website.
- - Anybody in this network.
- - Anybody authenticated.
- - Anybody on the Internet.
-
-
-[h4]Public and Private Forums[/h4]
-
-Forums are typically channels which may be open to participation from multiple authors. There are currently two mechanisms to post to forums: 1) "wall-to-wall" posts and 2) via forum @mention tags. Forums can be created by anybody and used for any purpose. The directory contains an option to search for public forums. Private forums can only be posted to and often only seen by members.
-
-
-[h4]Account Cloning[/h4]
-
-Accounts in $Projectname are referred to as [i]nomadic identities[/i], because a member's identity is not bound to the hub where the identity was originally created. For example, when you create a Facebook or Gmail account, it is tied to those services. They cannot function without Facebook.com or Gmail.com.
-
-By contrast, say you've created a $Projectname identity called [b]tina@$Projectnamehub.com[/b]. You can clone it to another $Projectname hub by choosing the same, or a different name: [b]liveForever@Some$ProjectnameHub.info[/b]
-
-Both channels are now synchronized, which means all your contacts and preferences will be duplicated on your clone. It doesn't matter whether you send a post from your original hub, or the new hub. Posts will be mirrored on both accounts.
-
-This is a rather revolutionary feature, if we consider some scenarios:
-
- - What happens if the hub where an identity is based suddenly goes offline? Without cloning, a member will not be able to communicate until that hub comes back online (no doubt many of you have seen and cursed the Twitter "Fail Whale"). With cloning, you just log into your cloned account, and life goes on happily ever after.
-
- - The administrator of your hub can no longer afford to pay for his free and public $Projectname hub. He announces that the hub will be shutting down in two weeks. This gives you ample time to clone your identity(ies) and preserve your$Projectname relationships, friends and content.
-
- - What if your identity is subject to government censorship? Your hub provider may be compelled to delete your account, along with any identities and associated data. With cloning, $Projectname offers [b]censorship resistance[/b]. You can have hundreds of clones, if you wanted to, all named different, and existing on many different hubs, strewn around the internet.
-
-$Projectname offers interesting new possibilities for privacy. You can read more at the &lt;&lt;Private Communications Best Practices&gt;&gt; page.
-
-Some caveats apply. For a full explanation of identity cloning, read the &lt;HOW TO CLONE MY IDENTITY&gt;.
-
-[h4]Multiple Profiles[/h4]
-
-Any number of profiles may be created containing different information and these may be made visible to certain of your connections/friends. A "default" profile can be seen by anybody and may contain limited information, with more information available to select groups or people. This means that the profile (and site content) your beer-drinking buddies see may be different than what your co-workers see, and also completely different from what is visible to the general public.
-
-[h4]Account Backup[/h4]
-
-$Projectname offers a simple, one-click account backup, where you can download a complete backup of your profile(s). Backups can then be used to clone or restore a profile.
-
-[h4]Account Deletion[/h4]
-Accounts can be immediately deleted by clicking on a link. That's it. All associated content is then deleted from the grid (this includes posts and any other content produced by the deleted profile). Depending on the number of connections you have, the process of deleting remote content could take some time but it is scheduled to happen as quickly as is practical.
-
-[h4]Deletion of content[/h4]
-Any content created in $Projectname remains under the control of the member (or channel) that originally created it. At any time, a member can delete a message, or a range of messages. The deletion process ensures that the content is deleted, regardless of whether it was posted on a channel's primary (home) hub, or on another hub, where the channel was remotely authenticated via Zot ($Projectname communication and authentication protocol).
-
-[h4]Media[/h4]
-Similar to any other modern blogging system, social network, or a micro-blogging service, $Projectname supports the uploading of files, embedding of videos, linking web pages.
-
-[h4]Previewing/Editing[/h4]
-Post can be previewed prior to sending and edited after sending.
-
-[h4]Voting/Consensus[/h4]
-Posts can be turned into "consensus" items which allows readers to offer feedback, which is collated into "agree", "disagree", and "abstain" counters. This lets you gauge interest for ideas and create informal surveys.
-
-[h4]Extending $Projectname[/h4]
-
-$Projectname can be extended in a number of ways, through site customisation, personal customisation, option setting, themes, and addons/plugins.
-
-[h4]API[/h4]
-
-An API is available for use by third-party services. This is based originally on the early Twitter API (for which hundreds of third-party tools exist). It is currently being extended to provide access to facilities and abilities which are specific to $Projectname. Access may be provided by login/password or OAuth and client registration of OAuth applications is provided.
diff --git a/doc/about/hubzilla_project.bb b/doc/about/hubzilla_project.bb
deleted file mode 100644
index 7a584687d..000000000
--- a/doc/about/hubzilla_project.bb
+++ /dev/null
@@ -1,185 +0,0 @@
-[h3]$Projectname Governance[/h3]
-Governance relates to the management of a project and particularly how this relates to conflict resolution.
-
-[h4]Community Governance[/h4]
-The project is maintained and decisions made by the 'community'. The governance structure is still evolving. Until the structure is finalised, decisions are made in the following order:
-
-[ol]
-[*] Lazy Consensus
-
-If a project proposal is made to one of the community governance forums and there are no serious objections in a "reasonable" amount of time from date of proposal (we usually provide 2-3 days for all interested parties to weigh in), no vote needs to be taken and the proposal will be considered approved. Some concerns may be raised at this time, but if these are addressed during discussion and work-arounds provided, it will still be considered approved.
-
-
-[*] Veto
-
-Senior developers with a significant history of project commits may veto any decision. The decision may not proceed until the veto is removed or an alternative proposal is presented.
-
-
-[*] Community Vote
-
-A decision which does not have a clear mandate or clear consensus, but is not vetoed, can be taken to a community vote. At present this is a simple popular vote in one of the applicable community forums. At this time, popular vote decides the outcome. This may change in the future if the community adopts a 'council' governance model. This document will be updated at that time with the updated governance rules.
-[/ol]
-
-Community Voting does not always provide a pleasant outcome and can generate polarised factions in the community (hence the reason why other models are under consideration). If the proposal is 'down voted' there are still several things which can be done and the proposal re-submitted with slightly different parameters (convert to an addon, convert to an optional feature which is disabled by default, etc.). If interest in the feature is high and the vote is "close", it can generate lots of bad feelings amongst the losing voters. On such close votes, it is [b]strongly recommended[/b] that the proposer take steps to address any concerns that were raised and re-submit.
-
-
-
-[h4]Privacy Policy[/h4]
-
-Q: Who can see my content?
-
-A: By default ANYBODY on the internet, UNLESS you restrict it. $Projectname allows you to choose the privacy level you desire. Restricted content will NOT be visible to "spy networks" and advertisers. It will be protected against eavesdropping by outsiders - to the best of our ability. Hub administrators with sufficient skills and patience MAY be able to eavesdrop on some private communications but they must expend effort to do so. Privacy modes exist within $Projectname which are even resistant to eavesdropping by skilled and determined hub administrators.
-
-Q: Can my content be censored?
-
-A: $Projectname (the network) CANNOT censor your content. Server and hub administrators are subject to local laws and MAY remove objectionable content from their site/hub. Anybody MAY become a hub administrator, including you; and therefore publish content which might otherwise be censored. You still MAY be subject to local laws.
-
-
-[h5]Definitions[/h5]
-
-**$Projectname**
-
-Otherwise referred to as "the network", $Projectname is a collection of individual computers/servers (aka **hubs**) which connect together to form a larger cooperative network.
-
-**hub**
-
-An individual computer or server connected to $Projectname. These are provided by a **hub administrator** and may be public or private, paid or free.
-
-**hub administrator**
-
-The system operator of an individual hub.
-
-[h5]Policies[/h5]
-
-**Public Information**
-
-Any information or anything posted by you within $Projectname MAY be public or visible to anybody on the internet. To the extent possible, $Projectname allows you to protect content and restrict who can view it.
-
-Your profile photo, your channel name, and the location (URL or network address) of your channel are visible to anybody on the internet and privacy controls will not affect the display of these items.
-
-You MAY additionally provide other profile information. Any information which you provide in your "default" or **public profile** MAY be transmitted to other hubs in $Projectname and additionally MAY be displayed in the channel directory. You can restrict the viewing of this profile information. It may be restricted only to members of your hub, or only connections (friends), or other limited sets of viewers as you desire. If you wish for your profile to be restricted, you must set the appropriate privacy setting, or simply DO NOT provide additional information.
-
-**Content**
-
-Content you provide (status posts, photos, files, etc.) belongs to you. $Projectname default is to publish content openly and visible to anybody on the internet (PUBLIC). You MAY control this in your channel settings and restrict the default permissions or you MAY restrict the visibility of any single published item separately (PRIVATE). $Projectname developers will ensure that restricted content is ONLY visible to those in the restriction list - to the best of their ability.
-
-Content (especially status posts) that you share with other networks or that you have made visible to anybody on the internet (PUBLIC) cannot easily be taken back once it has been published. It MAY be shared with other networks and made available through RSS/Atom feeds. It may also be syndicated on other $Projectname sites. It MAY appear on other networks and websites and be visible in internet searches. If you do not wish this default behaviour please adjust your channel settings and restrict who can see your content.
-
-**Comments and Forum posts**
-
-Comments to posts that were created by others and posts which are designated as forum posts belong to you as the creator/author, but the distribution of these posts is not under your direct control, and you relinquish SOME rights to these items. These posts/comments MAY be re-distributed to others, and MAY be visible to anybody on the internet. In the case of comments, the creator of the "first message" in the thread (conversation) to which you are replying controls the distribution of all comments and replies to that message. They "own" and therefore have certain rights with regard to the entire conversation (including all comments contained within it). You can still edit or delete the comment, but the conversation owner also has rights to edit, delete, re-distribute, and backup/restore any or all the content from the conversation.
-
-**Private Information**
-
-$Projectname developers will ensure that any content you provide which is designated as PRIVATE will be protected against eavesdropping - to the best of their ability. Private channel content CAN be seen in the database of every involved hub administrator, but private messages are obscured in the database. The latter means that it is very difficult, but NOT impossible for this content to be seen by a hub administrator. Private channel content and private messages are also stripped from email notifications. End to end encryption is provided as an optional feature and this CANNOT be seen, even by a determined administrator.
-
-[h5]Identity Privacy[/h5]
-
-Privacy for your identity is another aspect. Because you have a decentralized identity in $Projectname, your privacy extends beyond your home hub. If you want to have complete control of your privacy and security you should run your own hub on a dedicated server. For many people, this is complicated and may stretch their technical abilities. So let's list a few precautions you can make to assure your privacy as much as possible.
-
-A decentralized identity has a lot of advantages and gives you al lot of interesting features, but you should be aware of the fact that your identity is known by other hubs in $Projectname network. One of those advantages is that other channels can serve you customized content and allow you to see private things (such as private photos which others wish to share with you). Because of this those channels need to know who you are. But we understand that sometimes those other channels know more from you than you might desire. For instance the plug-in Visage that can tell a channel owner the last time you visit their profile. You can easily OPT-OUT of this low level and we think, harmless tracking.
-
-* You can enable [Do Not Track (DNT)](http://donottrack.us/) in your web browser. We respect this new privacy policy proposal. All modern browsers support DNT. You will find it in the privacy settings of your browsers or else you can consult the web browser's manual. This will not affect the functionality of $Projectname. This setting is probably enough for most people.
-
-*You can [disable publication](settings) of your channel in our channel directory. If you want people to find your channel, you should give your channel address directly to them. We think this is a good indication that you prefer extra privacy and automatically enable "Do Not Track" if this is the case.
-
-* You can have a blocked hub. That means that all channels and content on that hub is not public, and not visible to the outside world. This is something only your hub administrator can do. We also respect this and automatically enable "Do Not Track" if it is set.
-
-[h5]Censorship[/h5]
-
-$Projectname is a global network which is inclusive of all religions and cultures. This does not imply that every member of the network feels the same way you do on contentious issues, and some people may be STRONGLY opposed to the content you post. In general, if you wish to post something that you know may nor be universally acceptable, the best approach is to restrict the audience using privacy controls to a small circle of friends.
-
-$Projectname as a network provider is unable to censor content. However, hub administrators MAY censor any content which appears on their hub to comply with local laws or even personal judgement. Their decision is final. If you have issues with any hub administrator, you may move your account and postings to another site which is more in line with your expectations. Please check (periodically) the [Terms of Service](help/TermsOfService) of your hub to learn about any rules or guidelines. If your content consists of material which is illegal or may cause issues, you are STRONGLY encouraged to host your own (become a hub administrator). You may still find that your content is blocked on some hubs, but $Projectname as a network cannot block it from being posted.
-
-$Projectname RECOMMENDS that hub administrators provide a grace period of 1-2 days between warning an account holder of content that needs to be removed and physically removing or disabling the account. This will give the content owner an opportunity to export their channel meta-data and import it to another site. In rare cases the content may be of such a nature to justify the immediate termination of the account. This is a hub decision, not a $Projectname decision.
-
-If you typically and regularly post content of an adult or offensive nature, you are STRONGLY encouraged to mark your account "NSFW" (Not Safe For Work). This will prevent the display of your profile photo in the directory except to viewers that have chosen to disable "safe mode". If your profile photo is found by directory administrators to be adult or offensive, the directory administrator MAY flag your profile photo as NSFW. There is currently no official mechanism to contest or reverse this decision, which is why you SHOULD mark your own account NSFW if it is likely to be inappropriate for general audiences.
-
-[h3]Credits[/h3]
-
-Thanks to all who have helped and contributed to the project and its predecessors over the years.
-It is possible we missed in your name but this is unintentional. We also thank the community and
-its members for providing valuable input and without whom this entire effort would be meaningless.
-
-It is also worth acknowledging the contributions and solutions to problems which arose from
-discussions amongst members and developers of other somewhat related and competing projects;
-even if we have had our occasional disagreements.
-
-[list]
-[li]Mike Macgirvin[/li]
-[li]Fabio Comuni[/li]
-[li]Simon L'nu[/li]
-[li]marijus[/li]
-[li]Tobias Diekershoff[/li]
-[li]fabrixxm[/li]
-[li]tommy tomson[/li]
-[li]Simon[/li]
-[li]zottel[/li]
-[li]Christian Vogeley[/li]
-[li]Jeroen van Riet Paap (jeroenpraat)[/li]
-[li]Michael Vogel[/li]
-[li]erik[/li]
-[li]Zach Prezkuta[/li]
-[li]Paolo T[/li]
-[li]Michael Meer[/li]
-[li]Michael[/li]
-[li]Abinoam P. Marques Jr[/li]
-[li]Tobias Hößl[/li]
-[li]Alexander Kampmann[/li]
-[li]Olaf Conradi[/li]
-[li]Paolo Tacconi[/li]
-[li]tobiasd[/li]
-[li]Devlon Duthie[/li]
-[li]Zvi ben Yaakov (a.k.a rdc)[/li]
-[li]Alexandre Hannud Abdo[/li]
-[li]Olivier Migeot[/li]
-[li]Chris Case[/li]
-[li]Klaus Weidenbach[/li]
-[li]Michael Johnston[/li]
-[li]olivierm[/li]
-[li]Vasudev Kamath[/li]
-[li]pixelroot[/li]
-[li]Max Weller[/li]
-[li]duthied[/li]
-[li]Martin Schmitt[/li]
-[li]Sebastian Egbers[/li]
-[li]Erkan Yilmaz[/li]
-[li]sasiflo[/li]
-[li]Stefan Parviainen[/li]
-[li]Haakon Meland Eriksen[/li]
-[li]Oliver Hartmann (23n)[/li]
-[li]Erik Lundin[/li]
-[li]habeascodice[/li]
-[li]sirius[/li]
-[li]Charles[/li]
-[li]Tony Baldwin[/li]
-[li]Hauke Zuehl[/li]
-[li]Keith Fernie[/li]
-[li]Anne Walk[/li]
-[li]toclimb[/li]
-[li]Daniel Frank[/li]
-[li]Matthew Exon[/li]
-[li]Michal Supler[/li]
-[li]Tobias Luther[/li]
-[li]U-SOUND\mike[/li]
-[li]mrjive[/li]
-[li]nostupidzone[/li]
-[li]tonnerkiller[/li]
-[li]Antoine G[/li]
-[li]Christian Drechsler[/li]
-[li]Ludovic Grossard[/li]
-[li]RedmatrixCanada[/li]
-[li]Stanislav Lechev [0xAF][/li]
-[li]aweiher[/li]
-[li]bufalo1973[/li]
-[li]dsp1986[/li]
-[li]felixgilles[/li]
-[li]ike[/li]
-[li]maase2[/li]
-[li]mycocham[/li]
-[li]ndurchx[/li]
-[li]pafcu[/li]
-[li]Simó Albert i Beltran[/li]
-[li]Manuel Reva[/li]
-[li]Manuel Jiménez Friaza[/li]
-[/list] \ No newline at end of file
diff --git a/doc/about/project.bb b/doc/about/project.bb
new file mode 100644
index 000000000..f9bc920f8
--- /dev/null
+++ b/doc/about/project.bb
@@ -0,0 +1,186 @@
+[h3]$Projectname Governance[/h3]
+Governance relates to the management of a project and particularly how this relates to conflict resolution.
+
+[h4]Community Governance[/h4]
+The project is maintained and decisions made by the 'community'. The governance structure is still evolving. Until the structure is finalised, decisions are made in the following order:
+
+[ol]
+[*] Lazy Consensus
+
+If a project proposal is made to one of the community governance forums and there are no serious objections in a "reasonable" amount of time from date of proposal (we usually provide 2-3 days for all interested parties to weigh in), no vote needs to be taken and the proposal will be considered approved. Some concerns may be raised at this time, but if these are addressed during discussion and work-arounds provided, it will still be considered approved.
+
+
+[*] Veto
+
+Senior developers with a significant history of project commits may veto any decision. The decision may not proceed until the veto is removed or an alternative proposal is presented.
+
+
+[*] Community Vote
+
+A decision which does not have a clear mandate or clear consensus, but is not vetoed, can be taken to a community vote. At present this is a simple popular vote in one of the applicable community forums. At this time, popular vote decides the outcome. This may change in the future if the community adopts a 'council' governance model. This document will be updated at that time with the updated governance rules.
+[/ol]
+
+Community Voting does not always provide a pleasant outcome and can generate polarised factions in the community (hence the reason why other models are under consideration). If the proposal is 'down voted' there are still several things which can be done and the proposal re-submitted with slightly different parameters (convert to an addon, convert to an optional feature which is disabled by default, etc.). If interest in the feature is high and the vote is "close", it can generate lots of bad feelings amongst the losing voters. On such close votes, it is [b]strongly recommended[/b] that the proposer take steps to address any concerns that were raised and re-submit.
+
+
+
+[h4]Privacy Policy[/h4]
+
+Q: Who can see my content?
+
+A: By default ANYBODY on the internet, UNLESS you restrict it. $Projectname allows you to choose the privacy level you desire. Restricted content will NOT be visible to "spy networks" and advertisers. It will be protected against eavesdropping by outsiders - to the best of our ability. Hub administrators with sufficient skills and patience MAY be able to eavesdrop on some private communications but they must expend effort to do so. Privacy modes exist within $Projectname which are even resistant to eavesdropping by skilled and determined hub administrators.
+
+Q: Can my content be censored?
+
+A: $Projectname (the network) CANNOT censor your content. Server and hub administrators are subject to local laws and MAY remove objectionable content from their site/hub. Anybody MAY become a hub administrator, including you; and therefore publish content which might otherwise be censored. You still MAY be subject to local laws.
+
+
+[h5]Definitions[/h5]
+
+**$Projectname**
+
+Otherwise referred to as "the network", $Projectname is a collection of individual computers/servers (aka **hubs**) which connect together to form a larger cooperative network.
+
+**hub**
+
+An individual computer or server connected to $Projectname. These are provided by a **hub administrator** and may be public or private, paid or free.
+
+**hub administrator**
+
+The system operator of an individual hub.
+
+[h5]Policies[/h5]
+
+**Public Information**
+
+Any information or anything posted by you within $Projectname MAY be public or visible to anybody on the internet. To the extent possible, $Projectname allows you to protect content and restrict who can view it.
+
+Your profile photo, your channel name, and the location (URL or network address) of your channel are visible to anybody on the internet and privacy controls will not affect the display of these items.
+
+You MAY additionally provide other profile information. Any information which you provide in your "default" or **public profile** MAY be transmitted to other hubs in $Projectname and additionally MAY be displayed in the channel directory. You can restrict the viewing of this profile information. It may be restricted only to members of your hub, or only connections (friends), or other limited sets of viewers as you desire. If you wish for your profile to be restricted, you must set the appropriate privacy setting, or simply DO NOT provide additional information.
+
+**Content**
+
+Content you provide (status posts, photos, files, etc.) belongs to you. $Projectname default is to publish content openly and visible to anybody on the internet (PUBLIC). You MAY control this in your channel settings and restrict the default permissions or you MAY restrict the visibility of any single published item separately (PRIVATE). $Projectname developers will ensure that restricted content is ONLY visible to those in the restriction list - to the best of their ability.
+
+Content (especially status posts) that you share with other networks or that you have made visible to anybody on the internet (PUBLIC) cannot easily be taken back once it has been published. It MAY be shared with other networks and made available through RSS/Atom feeds. It may also be syndicated on other $Projectname sites. It MAY appear on other networks and websites and be visible in internet searches. If you do not wish this default behaviour please adjust your channel settings and restrict who can see your content.
+
+**Comments and Forum posts**
+
+Comments to posts that were created by others and posts which are designated as forum posts belong to you as the creator/author, but the distribution of these posts is not under your direct control, and you relinquish SOME rights to these items. These posts/comments MAY be re-distributed to others, and MAY be visible to anybody on the internet. In the case of comments, the creator of the "first message" in the thread (conversation) to which you are replying controls the distribution of all comments and replies to that message. They "own" and therefore have certain rights with regard to the entire conversation (including all comments contained within it). You can still edit or delete the comment, but the conversation owner also has rights to edit, delete, re-distribute, and backup/restore any or all the content from the conversation.
+
+**Private Information**
+
+$Projectname developers will ensure that any content you provide which is designated as PRIVATE will be protected against eavesdropping - to the best of their ability. Private channel content CAN be seen in the database of every involved hub administrator, but private messages are obscured in the database. The latter means that it is very difficult, but NOT impossible for this content to be seen by a hub administrator. Private channel content and private messages are also stripped from email notifications. End to end encryption is provided as an optional feature and this CANNOT be seen, even by a determined administrator.
+
+[h5]Identity Privacy[/h5]
+
+Privacy for your identity is another aspect. Because you have a decentralized identity in $Projectname, your privacy extends beyond your home hub. If you want to have complete control of your privacy and security you should run your own hub on a dedicated server. For many people, this is complicated and may stretch their technical abilities. So let's list a few precautions you can make to assure your privacy as much as possible.
+
+A decentralized identity has a lot of advantages and gives you al lot of interesting features, but you should be aware of the fact that your identity is known by other hubs in $Projectname network. One of those advantages is that other channels can serve you customized content and allow you to see private things (such as private photos which others wish to share with you). Because of this those channels need to know who you are. But we understand that sometimes those other channels know more from you than you might desire. For instance the plug-in Visage that can tell a channel owner the last time you visit their profile. You can easily OPT-OUT of this low level and we think, harmless tracking.
+
+* You can enable [Do Not Track (DNT)](http://donottrack.us/) in your web browser. We respect this new privacy policy proposal. All modern browsers support DNT. You will find it in the privacy settings of your browsers or else you can consult the web browser's manual. This will not affect the functionality of $Projectname. This setting is probably enough for most people.
+
+*You can [disable publication](settings) of your channel in our channel directory. If you want people to find your channel, you should give your channel address directly to them. We think this is a good indication that you prefer extra privacy and automatically enable "Do Not Track" if this is the case.
+
+* You can have a blocked hub. That means that all channels and content on that hub is not public, and not visible to the outside world. This is something only your hub administrator can do. We also respect this and automatically enable "Do Not Track" if it is set.
+
+[h5]Censorship[/h5]
+
+$Projectname is a global network which is inclusive of all religions and cultures. This does not imply that every member of the network feels the same way you do on contentious issues, and some people may be STRONGLY opposed to the content you post. In general, if you wish to post something that you know may nor be universally acceptable, the best approach is to restrict the audience using privacy controls to a small circle of friends.
+
+$Projectname as a network provider is unable to censor content. However, hub administrators MAY censor any content which appears on their hub to comply with local laws or even personal judgement. Their decision is final. If you have issues with any hub administrator, you may move your account and postings to another site which is more in line with your expectations. Please check (periodically) the [Terms of Service](help/TermsOfService) of your hub to learn about any rules or guidelines. If your content consists of material which is illegal or may cause issues, you are STRONGLY encouraged to host your own (become a hub administrator). You may still find that your content is blocked on some hubs, but $Projectname as a network cannot block it from being posted.
+
+$Projectname RECOMMENDS that hub administrators provide a grace period of 1-2 days between warning an account holder of content that needs to be removed and physically removing or disabling the account. This will give the content owner an opportunity to export their channel meta-data and import it to another site. In rare cases the content may be of such a nature to justify the immediate termination of the account. This is a hub decision, not a $Projectname decision.
+
+If you typically and regularly post content of an adult or offensive nature, you are STRONGLY encouraged to mark your account "NSFW" (Not Safe For Work). This will prevent the display of your profile photo in the directory except to viewers that have chosen to disable "safe mode". If your profile photo is found by directory administrators to be adult or offensive, the directory administrator MAY flag your profile photo as NSFW. There is currently no official mechanism to contest or reverse this decision, which is why you SHOULD mark your own account NSFW if it is likely to be inappropriate for general audiences.
+
+[h3]Credits[/h3]
+
+Thanks to all who have helped and contributed to the project and its predecessors over the years.
+It is possible we missed in your name but this is unintentional. We also thank the community and
+its members for providing valuable input and without whom this entire effort would be meaningless.
+
+It is also worth acknowledging the contributions and solutions to problems which arose from
+discussions amongst members and developers of other somewhat related and competing projects;
+even if we have had our occasional disagreements.
+
+[list]
+[li]Mike Macgirvin[/li]
+[li]Fabio Comuni[/li]
+[li]Simon L'nu[/li]
+[li]marijus[/li]
+[li]Tobias Diekershoff[/li]
+[li]fabrixxm[/li]
+[li]tommy tomson[/li]
+[li]Simon[/li]
+[li]zottel[/li]
+[li]Christian Vogeley[/li]
+[li]Jeroen van Riet Paap (jeroenpraat)[/li]
+[li]Michael Vogel[/li]
+[li]erik[/li]
+[li]Zach Prezkuta[/li]
+[li]Paolo T[/li]
+[li]Michael Meer[/li]
+[li]Michael[/li]
+[li]Abinoam P. Marques Jr[/li]
+[li]Tobias Hößl[/li]
+[li]Alexander Kampmann[/li]
+[li]Olaf Conradi[/li]
+[li]Paolo Tacconi[/li]
+[li]tobiasd[/li]
+[li]Devlon Duthie[/li]
+[li]Zvi ben Yaakov (a.k.a rdc)[/li]
+[li]Alexandre Hannud Abdo[/li]
+[li]Olivier Migeot[/li]
+[li]Chris Case[/li]
+[li]Klaus Weidenbach[/li]
+[li]Michael Johnston[/li]
+[li]olivierm[/li]
+[li]Vasudev Kamath[/li]
+[li]pixelroot[/li]
+[li]Max Weller[/li]
+[li]duthied[/li]
+[li]Martin Schmitt[/li]
+[li]Sebastian Egbers[/li]
+[li]Erkan Yilmaz[/li]
+[li]sasiflo[/li]
+[li]Stefan Parviainen[/li]
+[li]Haakon Meland Eriksen[/li]
+[li]Oliver Hartmann (23n)[/li]
+[li]Erik Lundin[/li]
+[li]habeascodice[/li]
+[li]sirius[/li]
+[li]Charles[/li]
+[li]Tony Baldwin[/li]
+[li]Hauke Zuehl[/li]
+[li]Keith Fernie[/li]
+[li]Anne Walk[/li]
+[li]toclimb[/li]
+[li]Daniel Frank[/li]
+[li]Matthew Exon[/li]
+[li]Michal Supler[/li]
+[li]Tobias Luther[/li]
+[li]U-SOUND\mike[/li]
+[li]mrjive[/li]
+[li]nostupidzone[/li]
+[li]tonnerkiller[/li]
+[li]Antoine G[/li]
+[li]Christian Drechsler[/li]
+[li]Ludovic Grossard[/li]
+[li]RedmatrixCanada[/li]
+[li]Stanislav Lechev [0xAF][/li]
+[li]aweiher[/li]
+[li]bufalo1973[/li]
+[li]dsp1986[/li]
+[li]felixgilles[/li]
+[li]ike[/li]
+[li]maase2[/li]
+[li]mycocham[/li]
+[li]ndurchx[/li]
+[li]pafcu[/li]
+[li]Simó Albert i Beltran[/li]
+[li]Manuel Reva[/li]
+[li]Manuel Jiménez Friaza[/li]
+[li]Gustav Wall aka "neue medienordnung plus"[/li]
+[/list]
diff --git a/doc/account_basics.bb b/doc/account_basics.bb
deleted file mode 100644
index 664949d6e..000000000
--- a/doc/account_basics.bb
+++ /dev/null
@@ -1,38 +0,0 @@
-[b]Account Basics[/b]
-
-[b]Registration[/b]
-
-Not all $Projectname sites allow open registration. If registration is allowed, you will see a &quot;Register&quot; link immediately below the login prompts on the site home page. Following this link will take you to the site Registration page. On some sites it may redirect you to another site which allow registrations. As all $Projectname sites are linked, it does not matter where your account resides.
-
-[b]Your Email Address[/b]
-
-Please provide a valid email address. Your email address is never published. This address will be used to (optionally) send email notifications for incoming messages or items, and used to recover lost passwords.
-
-[b]Password[/b]
-
-Enter a password of your choice, and repeat it in the second box to ensure it was typed correctly. As $Projectname offers a decentralised identity, your account can log you in to many other websites.
-
-[b]Terms Of Service[/b]
-
-Click the link to read the site's terms of service. Once you've read them, tick the box in the register form to confirm.
-
-[b]Register[/b]
-
-Once you have provided the necessary details, click the 'Register' button. Some sites may require administrator approval before the registration is processed, and you will be alerted if this is the case. Please watch your email (including spam folders) for your registration approval.
-
-[b]Create a Channel[/b]
-
-Next, you will be presented with the &quot;Add a channel&quot; screen. Normally, your first channel will be one that represents you - so using your own name (or psuedonym) as the channel name is a good idea. The channel name should be thought of as a title, or brief description of your channel. The &quot;choose a short nickname&quot; box is similar to a &quot;username&quot; field. We will use whatever you enter here to create a channel address, which other people will use to connect to you, and you will use to log in to other sites. This looks like an email address, and takes the form nickname@siteyouregisteredat.xyz*
-
-When your channel is created you will be taken straight to your settings page where you can define permissions, enable features, etc. All these things are covered in the appropriate section of the helpfiles.
-
-*Note: It is not possible to change this address after creating the channel.
-
-See Also
-
-[zrl=[baseurl]/help/permissions]Permissions[/zrl]
-[zrl=[baseurl]/help/privacy]Privacy[/zrl]
-[zrl=[baseurl]/help/profiles]Profiles[/zrl]
-[zrl=[baseurl]/help/remove_account]Remove Account[/zrl]
-
-#include doc/macros/main_footer.bb;
diff --git a/doc/accounts.bb b/doc/accounts.bb
deleted file mode 100644
index 7c0378504..000000000
--- a/doc/accounts.bb
+++ /dev/null
@@ -1,4 +0,0 @@
-This one still needs to be written.
-
-#include doc/macros/main_footer.bb;
-
diff --git a/doc/addons.bb b/doc/addons.bb
index 6fa9510f5..e6841d3d0 100644
--- a/doc/addons.bb
+++ b/doc/addons.bb
@@ -2,12 +2,12 @@
[list=1]
[*] abcjsplugin - Create musical scores in your posts
[*] adultphotoflag - prevents nsfw photos from being displayed in public albums
+[*] authchoose - only send identity assertions to sites of friends
[*] b2tbtn - provide button to go directly to top of page if you are scrolled a long way down
[*] bbmath - use complex math expressions in your posts
[*] bookmarker - replace #^ with bookmark link in posts
[*] buglink - provide a bug reporting icon in the lower-left corner of every page
[*] calc - a scientific calculator
-[*] cdav - CalDAV/CardDAV server
[*] chess - cross domain identity aware interactive chess games
[*] chords - generate fingering charts and alternatives for every known guitar chord
[*] custom_home - set a custom page as the hub start page
@@ -15,15 +15,19 @@
[*] dirstats - show some interesting statistics generated by the directory server
[*] docs - alternate documentation pages
[*] donate - provides a project donation page
+[*] dreamhost - provide a more reliable service on Dreamhost shared hosting
[*] dwpost - crosspost to Dreamwidth
+[*] emojione - allow emojis as emoticons
[*] extcron - use an external cron service to run your hub's scheduled tasks
+[*] firefox - provide a link to install the Firefox Sharing API
[*] flattrwidget - provides a "Flattr Us" button
[*] flip - create upside down text
[*] fortunate - displays random quote (fortune cookie). Requires setting up a fortune server.
[*] friendica - Friendica (DFRN) protocol. Under development.
[*] frphotos - import photo albums from Friendica
[*] gnusoc - GNU-Social (OStatus) protocol. Under development.
-[*] hexit - headecimal conversion tool
+[*] hexit - hexadecimal conversion tool
+[*] hilite - allow language-specific highlighted code blocks in posts
[*] hubwall - send an admin email to all hub accounts
[*] ijpost - crosspost to Insanejournal
[*] irc - connect to IRC chatrooms
@@ -50,12 +54,14 @@
[*] nsfw - Highly recommended plugin to collpase posts with inappropriate content
[*] openclipatar - choose a profile photo from hundreds of royalty free images
[*] openid - OpenID authentication and OpenID server. Your OpenID URL is [observer.baseurl]/id/[observer.webname]
+[*] opensearch - allow your site to become a browser search provider
[*] openstreetmap - render locations and maps using OpenStreetMap
[*] pageheader - display text at the top of every page on the site
[*] phpmailer - alternate mail delivery system with more configurability
[*] piwik - open source website analytics
[*] planets - set location field to a random planet from Star Wars
[*] pong - classic pong game
+[*] pubcrawl - ActivityPub protocol emulator
[*] pubsubhubbub - PuSH protocol for optimised delivery to feed subscribers (required by GNU-Social protocol)
[*] pumpio - crosspost to Pump.io
[*] qrator - generate QR code images
@@ -71,7 +77,7 @@
[*] smiley_pack - extend the built-in smilie (emoticon) support
[*] smileybutton - provides a smiley selector on the post window
[*] startpage - set a personal preferred page to redirect after logging in.
-[*] statistics_json - Diaspora statistics generator
+[*] statistics - Diaspora statistics generator
[*] statusnet - GNU-social and StatusNet crosspost [zrl=[baseurl]/help/addons_gnusocial]Posting To Gnu Social[/zrl]
[*] std_embeds - allow unfiltered embeds for popular providers like youtube, vimeo and soundcloud
[*] superblock - Highly recommended - completely block an offensive channel from your stream
@@ -79,9 +85,12 @@
[*] tictac - 3D tic-tac-toe
[*] torch - flashlight app
[*] tour - feature tour for new members
+[*] tripleaes - demo plugin for providing custom encryption algorithms
[*] twitter - crosspost to Twitter
+[*] twitter_api - Twitter/Statusnet compatible API
[*] upload_limits - discover what server setting (there are a few) may be causing large photo uploads to fail
[*] visage - show visitors to your channel
+[*] webmention - process webmentions
[*] wholikesme - provides a page to display what connections have 'liked' your posts the most
[*] webRTC - use an external server (mayfirst.org) to negotiate webRTC hookups
[*] wppost - crosspost to WordPress (or other wordpress XMLRPC service)
diff --git a/doc/admin/administrator_guide.md b/doc/admin/administrator_guide.md
index f21c55327..2fa52c7c6 100644
--- a/doc/admin/administrator_guide.md
+++ b/doc/admin/administrator_guide.md
@@ -150,7 +150,7 @@ web-based administrative tools to function:
#### Official addons
##### Installation
-Navigate to your webThen you should clone the addon repository (separately). We'll give this repository a nickname of 'hzaddons'. You can pull in other hubzilla addon repositories by giving them different nicknames::
+Navigate to your website. Then you should clone the addon repository (separately). We'll give this repository a nickname of 'hzaddons'. You can pull in other hubzilla addon repositories by giving them different nicknames::
cd mywebsite
util/add_addon_repo https://github.com/redmatrix/hubzilla-addons.git hzaddons
@@ -162,7 +162,7 @@ For keeping the addon tree updated, you should be on your top level website dire
util/update_addon_repo hzaddons
Create searchable representations of the online documentation. You may do this
- any time that the documentation is updated :
+any time that the documentation is updated :
cd mywebsite
util/importdoc
@@ -196,6 +196,45 @@ The installation script was originally designed for a small hardware server behi
1. `service apache2 reload`
1. Open your domain with a browser and step throught the initial configuration of $Projectname.
+### Recommended Addons
+
+We recommend the following addons be installed on all public sites:
+
+ nsfw - hide inappropriate posts/comments
+ superblock - block content from offensive channels
+
+### Federation Addons
+
+Several web communities have begun to converge using common protocols. The protocols involved are somewhat limited in their abilities. The GNU-Social protocol for instance offers no privacy modes, and the Diaspora protocol is somewhat restrictive in what kinds of communications are allowed. All comments must be signed in a very unique manner by the original author. The ActivityPub protocol is also being considered and may be supported at a future date. No other existing protocol supports nomadic location as used by this project. This presents some support challenges as some features work with some networks and don't work with others. Nevertheless the federation protocols allow connections to be made to a much larger community of people worldwide. They are provided as addons.
+
+> diaspora - The Diaspora Protocol used by Diaspora and Friendica. You should enable 'Diaspora Statistics' (statistics) first to enable all the available features.
+
+> gnusoc - The GNU-Social Protocol, used by GNU-Social, Mastodon and several other communities. This addon requires you first install the 'pubsubhubbub' service (also an addon).
+
+Each member of your site must choose whether or not to allow these protocols individually as they may conflict with several desirable core features and abilities of this software (such as channel migration and cloning). They do this from their 'Settings -> Feature/Addon Settings' page. The administrator may also set the following:
+
+ util/config system.diaspora_allowed 1
+ util/config system.gnusoc_allowed 1
+
+and enable these protocols automatically for all newly created channels.
+
+
+
+
+
+
+### Techlevels
+
+We've implemented several different mechanisms in order to reduce the apparent complexity and learning curve presented to new members. At the same time, we do not wish to limit any functionality for people who are able to grasp some slightly advanced technical technical features. The first mechanism was to move several features to an optional 'Features' page where they could be enabled at will; with the default interface kept somewhat lean.
+
+The problem we had now is that the number of features began to grow dramatically, and the Feature page is daunting in possibilities. There are also features present which probably should not be available to all members, but may be extremely useful to those with technical backgrounds.
+
+The techlevels seeeks to remedy this by grouping features within different levels of technical ability; starting at 0 (uncomfortable with technology), and up to 5 (Unix wizard or equivalent).
+
+When a new member registers, their account is provided a techlevel setting of 0. On the account settings page they may change this to any available level. A higher level opens more advanced features and possible interactions.
+
+The account administrator may also lock a particular level, lock a maximum level, or change/re-arrange the features available to any level. Those with the minimum level are typically not very exploratory and are unlikely to discover the advanced modes. This is by design. Those that look around and desire more interactions will find them. In the absence of administrator defaults they may choose any level. As they look at the features available to the level in question, it is generally expected that they will discover some features are beyond their comprehension and it is hoped they will back off to a level where the interface and features are comfortable to their skill level.
+
### Service Classes
Service classes allow you to set limits on system resources by limiting what individual
@@ -207,7 +246,7 @@ a _standard_ and _premium_ class using the following lines:
App::$config['system']['default_service_class']='standard'; // this is the default service class that is attached to every new account
- // configuration for parent service class
+ // configuration for standard service class
App::$config['service_class']['standard'] =
array('photo_upload_limit'=>2097152, // total photo storage limit per channel (here 2MB)
'total_identities' =>1, // number of channels an account can create
@@ -217,7 +256,7 @@ a _standard_ and _premium_ class using the following lines:
'attach_upload_limit' =>2097152, // total attachment storage limit per channel (here 2MB)
'chatters_inroom' =>20);
- // configuration for teacher service class
+ // configuration for premium service class
App::$config['service_class']['premium'] =
array('photo_upload_limit'=>20000000000, // total photo storage limit per channel (here 20GB)
'total_identities' =>20, // number of channels an account can create
@@ -307,6 +346,19 @@ empty:
1. After successful import (check!) delete your channel on the old RedMatrix Server.
1. On the $Projectname server visit new.hub/locs and upgrade to your channel to a primary one. And when the old Redmatrix server is still listed delete them here as well. Press "Sync" to inform all other server in the grid.
+### Administration
+
+#### Site Administration
+
+Administration of the website is commonly done through the admin webpage located at /admin on your website. In order to access this page you must have administration rights to the server. Administration rights are granted to the first account to register on your site, **provided** the email address of that account exactly matches the email address you provided as the administrator's email address during setup.
+
+There are several ways that this can fail and leave the system without an administrator account, for instance if the first account that was created provided a different email address than the administrator email address that was supplied during setup.
+
+For security reasons there is no web page or interface on the system which will give you administrator access. If you need to correct a situation where a system has no administrator account it **must** be done by editing the account table in the database. There is no other way. To do this, you will need to locate the entry in the account table which belongs to the desired administrator, and set 'account_roles' for that entry to 4096. You will then be able to access the admin page from your system's profile menu or directly via /admin .
+
+A hub can have multiple admins and there is no limit to how administrators you can have. Repeat the above process for every account you wish to provide with administration rights.
+
+
### Troubleshooting
#### Log files
diff --git a/doc/bugs.bb b/doc/bugs.bb
index f50337648..cc1ea3a20 100644
--- a/doc/bugs.bb
+++ b/doc/bugs.bb
@@ -1,31 +1,32 @@
[h2]Bugs, Issues, and things that go bump in the night...[/h2]
[h3]Something went wrong! Who is charge of fixing it?[/h3]
-[b]Hubzilla Community Server[/b]
+[b]$Projectname Community Server[/b]
-Hubzilla Community Server is open source software which is maintained by "the community" - essentially unpaid volunteers.
+$Projectname Community Server is open source software which is maintained by "the community" - essentially unpaid volunteers. Nobody is in charge of fixing bugs. We work together to keep the software and network running smoothly and error free. You are a member of this community, so we also require your help to provide quality software. There are no mythical "developers" who magically fix everything. It's up to all of us to pitch in and help.
The first thing you need to do is talk to your hub administrator - the person who runs and manages your site. They are in the unique position of having access to the internal software and database and [b]logfiles[/b] and will need to be involved in fixing your problem. Other people "on the net" can't really help with this. The first thing the hub administrator needs to do is look at their logs and/or try to reproduce the problem. So try to be as helpful and courteous as possible in helping them look into the problem.
-To find your hub administrator (if you don't know who they are) please look at [url=[baseurl]/siteinfo]this page[/url]. If they have not provided any contact info on that page or provided an "Impressum" there, see [url=[baseurl]/siteinfo/json]this site info summary[/url] under the heading "admin:".
+To find your hub administrator (if you don't know who they are) please look at [url=[baseurl]/siteinfo]this page[/url]. If they have not provided any contact info on that page or provided an "Impressum" there, see [url=[baseurl]/siteinfo.json]this site info summary[/url] under the heading "admin:".
+
+It is highly recommended that bug reports be filed by hub administrators so that they can include the relevant logfile and database information relevant to the issue and be available to try workarounds and followup tests. Without this level of cooperation it may not be possible to fix the problem.
[h3]I'm a hub administrator; what do I do?[/h3]
-The software instructions which provide this server are open source and are available for your inspection. If an error message was reported, often one can do a search on the source files for that error message and find out what triggered it. With this information and the site logfiles it may be possible to figure out the sequence of events leading to the error. There could also be other sites involved, and the problem may not even be on your site but elsewhere in the network. Try to pin down the communication endpoints (hubs or sites) involved in the problem and contact the administrator of that site or those sites. Please try and provide an event time of when things went wrong so it can be found in the logs. Work with the other administrator(s) to try and find the cause of the problem. Logfiles are your friend. When something happens in the software that we didn't expect, it is nearly always logged.
+The software instructions which provide this web service are open source and are available for your inspection. We encourage everybody to read it and see how everything works and verify that we aren't doing anything evil or negligent with your personal communications. If an error message was reported, often one can do a search on the source files for that error message and find out what triggered it. With this information and the site logfiles it may be possible to figure out the sequence of events leading to the error. There could also be other sites involved, and the problem may not even be on your site but elsewhere in the network. Try to pin down the communication endpoints (hubs or sites) involved in the problem and contact the administrator of that site or those sites. Please try and provide an event time of when things went wrong so it can be found in the logs. Work with the other administrator(s) to try and find the cause of the problem. Logfiles are your friend. When something happens in the software that we didn't expect, it is nearly always logged.
[h3]The white screen of death[/h3]
-If you get a blank white screen when doing something, this is almost always a code or syntax error. There are instructions in your .htconfig.php file for enabling syntax logging. We recommend all sites use this. With syntax logging enabled repeat the sequence which led to the error and it should log the offending line of code. Hopefully you will be able to fix the problem with this information. When you do, please submit the fix "upstream" so that we can share the fix with the rest of the project members and other communities. This is a key benefit of using open source software - we share with each other and everybody benefits.
+If you get a blank white screen when doing something, this is almost always a code or syntax error. There are instructions in the site .htconfig.php file which will allow the site administrator to enabling syntax logging. We recommend all sites use this. With syntax logging enabled repeat the sequence which led to the error and it should log the offending line of code. Hopefully you will be able to fix the problem with this information. When you do, please submit the fix "upstream" so that we can share the fix with the rest of the project members and other communities. This is a key benefit of using open source software - we share with each other and everybody benefits.
[h3]I'm stumped. I can't figure out what is wrong.[/h3]
-At this point it might be worthwhile discussing the issue on one of the online forums. There may be several of these and some may be more suited to your spoken language. As a last resort, try "Channel One", which is in English.
+At this point it might be worthwhile discussing the issue on one of the online forums. There may be several of these and some may be more suited to your spoken language. At this time, the 'Hubzilla Support' channel (support@gravizot.de) is the recommended forum for discussing bugs.
-If the community developers can't help you right away, understand that they are volunteers and may have a lot of other work and demands on their time. At this point you need to file a bug report. You will need an account on github.com to do this. So register, and then visit https://github.com/redmatrix/hubzilla/issues
-. Create an issue here and provide all the same information that you provided online. Don't leave out anything.
+If community members with software engineering training/expertise can't help you right away, understand that they are volunteers and may have a lot of other work and demands on their time. At this point you need to file a bug report. You will need an account on github.com to do this. So register, and then visit https://github.com/redmatrix/hubzilla/issues . Create an issue here and provide all the same information that you provided online. Don't leave out anything.
-Then you wait. If it's a high profile issue, it may get fixed quickly. But nobody is in charge of fixing bugs. If it lingers without resolution, please spend some more time investigating the problem. Ask about anything you don't understand related to the behaviour. You will learn more about how the software works and quite possibly figure out why it isn't working now. Ultimately it is somebody in the community who is going to fix this and you are a member of the community; and this is how the open source process works.
+Then you wait. If it's a high profile issue, it may get fixed quickly. But nobody is in charge of fixing bugs. If it lingers without resolution, please spend some more time investigating the problem. Ask about anything you don't understand related to the behaviour. You will learn more about how the software works and quite possibly figure out why it isn't working now. Ultimately it is somebody in the community who is going to fix this and you are a member of the community; and this is how the open source process works.
-Other developers working to fix the problem may need to find out more, so do your homework and document what is happening and everything you've tried. Don't say "I did xyz and it didn't work." That doesn't tell us anything. Tell us precisely what steps you took and what you expected the result to be, and precisely what happened as a result. If there were any error messages, don't say "there was an error message". Tell us exactly what the message said. Tell us what version you're running and any other details that may be unique about your site configuration.
+Other people working to fix the problem may need to find out more, so do your homework and document what is happening and everything you've tried. Don't say "I did xyz and it didn't work." That doesn't tell us anything. Tell us precisely what steps you took and what you expected the result to be, and precisely what happened as a result. What page/URL were you looking at or what form were you filling in? If there were any error messages, don't say "there was an error message". Tell us exactly what the message said. Also tell us what hub you are using, what software version you're running and any other details that may be unique about your site configuration. It is understood that you might wish to keep some information and your connections private, however if you aren't willing to share the information other people need to reproduce/fix the problem, it may not get fixed.
\ No newline at end of file
diff --git a/doc/context/en/appman/help.html b/doc/context/en/appman/help.html
new file mode 100644
index 000000000..27cb03624
--- /dev/null
+++ b/doc/context/en/appman/help.html
@@ -0,0 +1,4 @@
+<dl class="dl-horizontal">
+ <dt>General</dt>
+ <dd>Edit individual properties of the app you selected. Categories allow you to sort your apps to help you find them in the list more easily. Support for custom apps you or your administrator may choose to create includes fields such as "Price of app" and "Location for purchase" that are not applicable to core Hubzilla apps.</dd>
+</dl> \ No newline at end of file
diff --git a/doc/context/en/apps/edit/help.html b/doc/context/en/apps/edit/help.html
new file mode 100644
index 000000000..1d378f962
--- /dev/null
+++ b/doc/context/en/apps/edit/help.html
@@ -0,0 +1,4 @@
+<dl class="dl-horizontal">
+ <dt>General</dt>
+ <dd>Edit or delete your apps using the control buttons beside each app icon in the list.</dd>
+</dl> \ No newline at end of file
diff --git a/doc/context/en/apps/help.html b/doc/context/en/apps/help.html
new file mode 100644
index 000000000..ad6daade5
--- /dev/null
+++ b/doc/context/en/apps/help.html
@@ -0,0 +1,6 @@
+<dl class="dl-horizontal">
+ <dt>General</dt>
+ <dd>This page shows you what apps are available to your channel, including both core apps and those supplied by addons. To add an app to the <a href='#' onclick='contextualHelpFocus("#app-menu", 1); return false;' title="Click to open...">app menu</a> "star" the app in the list below.</dd>
+ <dt>Manage Apps</dt>
+ <dd>Press the "Manage Apps" button to open a page where you can edit the name, categories, and other properties of your apps.</dd>
+</dl> \ No newline at end of file
diff --git a/doc/context/en/cards/help.html b/doc/context/en/cards/help.html
new file mode 100644
index 000000000..9dbed3f97
--- /dev/null
+++ b/doc/context/en/cards/help.html
@@ -0,0 +1,20 @@
+<dl class="dl-horizontal">
+ <dt>General</dt>
+ <dd>Cards represent a persistent area for collaboration that is separate from the social stream. They are somewhat more lightweight than webpages and wikis for quick organisation of information and have the advantage of allowing collaboration and commentary. They are well suited for helping to organise complex tasks where there are frequent updates and feedback.
+ </dd>
+ <dt>Add Card</dt>
+ <dd>
+ Creating a new card is very similar to composing a new post.<br><br>
+ <ul>
+ <li>
+ <b>Page link name</b>: The page link name is the name of the card for the static URL
+ </li>
+ <li>
+ <b>Title</b>: The title is displayed at the top of the card
+ </li>
+ <li>
+ <b>Categories</b>: If you have the <a href="/settings/features">Post Categories feature</a> enabled for your channel, then you can add categories to the card. These categories populate the <b>Categories</b> list on the left panel and allow filtering your collection of cards.
+ </li>
+ </ul>
+ </dd>
+</dl>
diff --git a/doc/context/en/channel/help.html b/doc/context/en/channel/help.html
index 6e3181cbf..0c5b99754 100644
--- a/doc/context/en/channel/help.html
+++ b/doc/context/en/channel/help.html
@@ -3,6 +3,4 @@
<dd>This is the home page of a channel. It is similar to someone's profile "wall" in a social network context. Posts created by the channel are displayed according to the observer's viewing permissions.</dd>
<dt>Create a Post</dt>
<dd>If you have permission to create posts on the channel page, then you will see the post editor at the top.</dd>
- <dt><a href='#' onclick='contextualHelpFocus("#tabs-collapse-1", 0); return false;' title="Click to highlight element...">Channel Content Tabs</a></dt>
- <dd>The channel content tabs are links to other content published by the channel. The <b>About</b> tab links to the channel profile. The <b>Photos</b> tab links to the channel photo galleries. The <b>Files</b> tab links to the general shared files published by the channel.</dd>
-</dl> \ No newline at end of file
+</dl>
diff --git a/doc/context/en/wiki/help.html b/doc/context/en/wiki/help.html
index 5ac9b22ae..5dee85375 100644
--- a/doc/context/en/wiki/help.html
+++ b/doc/context/en/wiki/help.html
@@ -1,12 +1,10 @@
<dl class="dl-horizontal">
<dt>General</dt>
<dd>Each wiki is a collection of pages, composed as Markdown-formatted text files.</dd>
- <dt><a href='#' onclick='contextualHelpFocus("#wikis-index", 1); return false;' title="Click to highlight element...">Wiki List</a></dt>
+ <dt>Wiki List</dt>
<dd>Wikis owned by the channel <i>that you have permission to view</i> are listed in the side panel.</dd>
- <dt><a href='#' onclick='contextualHelpFocus("#wiki-get-history", 0); return false;' title="Click to highlight element...">Page History</a></dt>
+ <dt>Page History</dt>
<dd>Every revision of a page is saved to allow quick reversion. Click the <b>History</b> tab to view a history of page revisions, including the date and author of each. The revert button will load the selected revision but will not automatically save the page.</dd>
- <dt><a href='#' onclick='contextualHelpFocus("#wiki_page_list", 1); return false;' title="Click to highlight element...">Pages</a></dt>
+ <dt>Pages</dt>
<dd>The list of pages in the wiki are listed in the <b>Wiki Pages</b> panel. Prior to saving page edits using the <b>Page</b> control dropdown menu, you may <a href='#' onclick='contextualHelpFocus("#id_commitMsg", 0); return false;' title="Click to highlight element...">enter a custom message</a> to be displayed in the <a href='#' onclick='contextualHelpFocus("#wiki-get-history", 0); return false;' title="Click to highlight element..."><b>Page History</b></a> viewer along with the revision.</dd>
- <dt><a href='#' onclick='contextualHelpFocus("#tabs-collapse-1", 0); return false;' title="Click to highlight element...">Channel Content Tabs</a></dt>
- <dd>The channel content tabs are links to other content published by the channel. The <b>About</b> tab links to the channel profile. The <b>Photos</b> tab links to the channel photo galleries. The <b>Files</b> tab links to the general shared files published by the channel.</dd>
-</dl> \ No newline at end of file
+</dl>
diff --git a/doc/contributor/covenant.html b/doc/contributor/covenant.html
deleted file mode 100644
index 4facac24e..000000000
--- a/doc/contributor/covenant.html
+++ /dev/null
@@ -1,106 +0,0 @@
-<!DOCTYPE html>
-
-<html lang="en">
-<head>
- <meta charset="utf-8"/>
- <title>Contributor Covenant 1.4.0</title>
- <style>
- body {
- font-family: monospace;
- padding: 4em;
- }
- a {
- color: #990000;
- }
- </style>
- <link rel="alternate" hreflang="de" href="version/1/3/0/de/" />
- <link rel="alternate" hreflang="es" href="version/1/4/es/" />
- <link rel="alternate" hreflang="fr" href="version/1/3/0/fr/" />
- <link rel="alternate" hreflang="hu" href="version/1/3/0/hu/" />
- <link rel="alternate" hreflang="it" href="version/1/3/0/it/" />
- <link rel="alternate" hreflang="ja" href="version/1/3/0/ja/" />
- <link rel="alternate" hreflang="pl" href="version/1/4/pl/" />
- <link rel="alternate" hreflang="pt" href="version/1/3/0/pt/" />
- <link rel="alternate" hreflang="pt" href="version/1/3/0/pt_br/" />
- <link rel="alternate" hreflang="ru" href="version/1/3/0/ru/" />
- <link rel="alternate" hreflang="sl" href="version/1/4/sl/" />
- <link rel="alternate" hreflang="uk" href="version/1/4/uk/" />
-</head>
-
-<body>
-
-<h1>Contributor Covenant Code of Conduct</h1>
-
-<h2>Our Pledge</h2>
-
-<p>In the interest of fostering an open and welcoming environment, we as
-contributors and maintainers pledge to making participation in our project and
-our community a harassment-free experience for everyone, regardless of age, body
-size, disability, ethnicity, gender identity and expression, level of experience,
-nationality, personal appearance, race, religion, or sexual identity and
-orientation.</p>
-
-<h2>Our Standards</h2>
-
-<p>Examples of behavior that contributes to creating a positive environment
-include:</p>
-
-<ul>
- <li>Using welcoming and inclusive language</li>
- <li>Being respectful of differing viewpoints and experiences</li>
- <li>Gracefully accepting constructive criticism</li>
- <li>Focusing on what is best for the community</li>
- <li>Showing empathy towards other community members</li>
-</ul>
-
-<p>Examples of unacceptable behavior by participants include:</p>
-
-<ul>
- <li>The use of sexualized language or imagery and unwelcome sexual attention or advances</li>
- <li>Trolling, insulting/derogatory comments, and personal or political attacks</li>
- <li>Public or private harassment</li>
- <li>Publishing others' private information, such as a physical or electronic address, without explicit permission</li>
- <li>Other conduct which could reasonably be considered inappropriate in a professional setting</li>
-</ul>
-
-<h2>Our Responsibilities</h2>
-
-<p>Project maintainers are responsible for clarifying the standards of acceptable
-behavior and are expected to take appropriate and fair corrective action in
-response to any instances of unacceptable behavior.</p>
-
-<p>Project maintainers have the right and responsibility to remove, edit, or
-reject comments, commits, code, wiki edits, issues, and other contributions
-that are not aligned to this Code of Conduct, or to ban temporarily or
-permanently any contributor for other behaviors that they deem inappropriate,
-threatening, offensive, or harmful.</p>
-
-<h2>Scope</h2>
-
-<p>This Code of Conduct applies both within project spaces and in public spaces
-when an individual is representing the project or its community. Examples of
-representing a project or community include using an official project e-mail
-address, posting via an official social media account, or acting as an appointed
-representative at an online or offline event. Representation of a project may be
-further defined and clarified by project maintainers.</p>
-
-<h2>Enforcement</h2>
-
-<p>Instances of abusive, harassing, or otherwise unacceptable behavior may be
-reported by contacting the project team at project&#x40;hubzilla.org. All
-complaints will be reviewed and investigated and will result in a response that
-is deemed necessary and appropriate to the circumstances. The project team is
-obligated to maintain confidentiality with regard to the reporter of an incident.
-Further details of specific enforcement policies may be posted separately.</p>
-
-<p>Project maintainers who do not follow or enforce the Code of Conduct in good
-faith may face temporary or permanent repercussions as determined by other
-members of the project's leadership.</p>
-
-<h2>Attribution</h2>
-
-<p>This Code of Conduct is adapted from the <a href="http://contributor-covenant.org">Contributor Covenant</a>, version 1.4,
-available at <a href="http://contributor-covenant.org/version/1/4/">http://contributor-covenant.org/version/1/4</a>.</p>
-
-</body>
-</html>
diff --git a/doc/database.bb b/doc/database.bb
index 02a70e2c7..160ec505e 100644
--- a/doc/database.bb
+++ b/doc/database.bb
@@ -1,6 +1,4 @@
-[h2]Database Tables[/h2]
-[table]
-[tr][th]Table[/th][th]Description[/th][/tr]
+[h2]Database Tables[/h2][table border=1][tr][th]Table[/th][th]Description[/th][/tr]
[tr][td][zrl=[baseurl]/help/database/db_abconfig]abconfig[/zrl][/td][td]arbitrary storage for connections of local channels[/td][/tr]
[tr][td][zrl=[baseurl]/help/database/db_abook]abook[/zrl][/td][td]connections of local channels[/td][/tr]
[tr][td][zrl=[baseurl]/help/database/db_account]account[/zrl][/td][td]service provider account[/td][/tr]
diff --git a/doc/database/db_account.bb b/doc/database/db_account.bb
index 354f2d3a8..35d7a9eb3 100644
--- a/doc/database/db_account.bb
+++ b/doc/database/db_account.bb
@@ -58,7 +58,6 @@ define ( 'ACCOUNT_PENDING', 0x0010 );
* Account roles
*/
-define ( 'ACCOUNT_ROLE_ALLOWCODE', 0x0001 ); // 1 - this account can create content with PHP/Javascript
define ( 'ACCOUNT_ROLE_SYSTEM', 0x0002 ); // 2 - this is the special system account
define ( 'ACCOUNT_ROLE_DEVELOPER', 0x0004 );
define ( 'ACCOUNT_ROLE_ADMIN', 0x1000 ); // 4096 - this account is an administrator
diff --git a/doc/dev-function-overview.md b/doc/dev-function-overview.md
index fa8a98ff3..cd2526ead 100644
--- a/doc/dev-function-overview.md
+++ b/doc/dev-function-overview.md
@@ -15,10 +15,6 @@ Returns authenticated numeric channel_id if authenticated and connected to a cha
Returns authenticated string hash of Red global identifier, if authenticated via remote auth, or an empty string.
-* get_app()
-
-Returns the global app structure ($a). No longer used as App is a static class
-
* App::get_observer()
returns an xchan structure representing the current viewer if authenticated (locally or remotely).
diff --git a/doc/developer/api_zot.bb b/doc/developer/api_zot.bb
index f33faed17..b2c19d7a1 100644
--- a/doc/developer/api_zot.bb
+++ b/doc/developer/api_zot.bb
@@ -4,7 +4,20 @@ The API endpoints detailed below are relative to [code]api/z/1.0[/code], meaning
[h3]channel/export/basic[/h3]
-Export channel data
+Export basic channel data
+
+Options:
+ - sections
+ comma-separated list of data types to export
+
+ - posts
+ if true, return default sections plus 3 months of posts
+
+ If no sections are requested, the following sections are returned:
+ channel, connections, config, apps, chatrooms, events, webpages, mail, wikis
+
+ Files and large collections of posts may run into memory limits; these must generally be
+ requested separately.
[h3]channel/stream[/h3]
@@ -28,7 +41,7 @@ GET /api/z/1.0/files
Options:
- - hash
+ - filehash
return only entries matching hash (exactly)
- filename
@@ -286,7 +299,7 @@ list photo metadata
[h3]group[/h3]
-`GET /api/z/1.0/group`
+[code]GET /api/z/1.0/group[/code]
Description: list privacy groups
@@ -326,7 +339,7 @@ To use with API group_members, provide either 'group_id' from the id element ret
[h3]group_members[/h3]
-`GET /api/z/1.0/group_members`
+[code]GET /api/z/1.0/group_members[/code]
Required:
@@ -462,7 +475,7 @@ group_member+abook+xchan (DB join) for each member of the privacy group
An xchan is a global location independent channel and is the primary record for a network
identity. It may refer to channels on other websites, networks, or services.
-`GET /api/z/1.0/xchan`
+[code]GET /api/z/1.0/xchan[/code]
Required: one of [ address, hash, guid ] as GET parameters
@@ -506,7 +519,7 @@ Returns:
Create or update an item (post, activity, webpage, etc.)
-Usage: `POST /api/z/1.0/item/update`
+Usage: [code]POST /api/z/1.0/item/update[/code]
Description: item/update posts an item (typically a conversation item or post, but can be any item) using form input.
@@ -608,7 +621,7 @@ Optional:
application or network name to display with item
-- categories
+- category
comma separated categories for this item
diff --git a/doc/developer/covenant.bb b/doc/developer/covenant.bb
new file mode 100644
index 000000000..431cc74e9
--- /dev/null
+++ b/doc/developer/covenant.bb
@@ -0,0 +1,47 @@
+[size=large]Contributor Covenant Code of Conduct[/size]
+
+[h3]Our Pledge[/h3]
+
+In the interest of fostering an open and welcoming environment, we as contributors and maintainers pledge to making participation in our project and our community a harassment-free experience for everyone, regardless of age, body size, disability, ethnicity, gender identity and expression, level of experience, nationality, personal appearance, race, religion, or sexual identity and orientation.
+
+[h3]Our Standards[/h3]
+
+Examples of behavior that contributes to creating a positive environment
+include:
+
+[list]
+ [*]Using welcoming and inclusive language
+ [*]Being respectful of differing viewpoints and experiences
+ [*]Gracefully accepting constructive criticism
+ [*]Focusing on what is best for the community
+ [*]Showing empathy towards other community members
+[/list]
+
+Examples of unacceptable behavior by participants include:
+
+[list]
+ [*]The use of sexualized language or imagery and unwelcome sexual attention or advances
+ [*]Trolling, insulting/derogatory comments, and personal or political attacks
+ [*]Public or private harassment
+ [*]Publishing others' private information, such as a physical or electronic address, without explicit permission
+ [*]Other conduct which could reasonably be considered inappropriate in a professional setting
+[/list]
+
+[h3]Our Responsibilities[/h3]
+
+Project maintainers are responsible for clarifying the standards of acceptable behavior and are expected to take appropriate and fair corrective action in response to any instances of unacceptable behavior. Project maintainers have the right and responsibility to remove, edit, or reject comments, commits, code, wiki edits, issues, and other contributions that are not aligned to this Code of Conduct, or to ban temporarily or permanently any contributor for other behaviors that they deem inappropriate, threatening, offensive, or harmful.
+
+[h3]Scope[/h3]
+
+This Code of Conduct applies both within project spaces and in public spaces when an individual is representing the project or its community. Examples of representing a project or community include using an official project e-mail address, posting via an official social media account, or acting as an appointed representative at an online or offline event. Representation of a project may be further defined and clarified by project maintainers.
+
+[h3]Enforcement[/h3]
+
+Instances of abusive, harassing, or otherwise unacceptable behavior may be reported by contacting the project team at project&#x40;hubzilla.org. All complaints will be reviewed and investigated and will result in a response that is deemed necessary and appropriate to the circumstances. The project team is obligated to maintain confidentiality with regard to the reporter of an incident. Further details of specific enforcement policies may be posted separately.
+
+Project maintainers who do not follow or enforce the Code of Conduct in good faith may face temporary or permanent repercussions as determined by other members of the project's leadership.
+
+[h3]Attribution[/h3]
+
+This Code of Conduct is adapted from the [url=http://contributor-covenant.org]Contributor Covenant[/url], version 1.4, available at [url=http://contributor-covenant.org/version/1/4/]http://contributor-covenant.org/version/1/4[/url].
+
diff --git a/doc/developer/developer_guide.bb b/doc/developer/developer_guide.bb
new file mode 100644
index 000000000..f8ba0c1d8
--- /dev/null
+++ b/doc/developer/developer_guide.bb
@@ -0,0 +1,178 @@
+[h3]Who is a $Projectname developer? Should I read this?[/h3]
+
+Anyone who contributes to making $Projectname better is a developer. There are many different and important ways you can contribute to this amazing technology, [i]even if you do not know how to write code[/i]. The software itself is only a part of the $Projectname project. You can contribute by
+[list]
+[*] translating text to your language so that people around the world have the opportunity to use $Projectname
+[*] promoting $Projectname and spreading awareness of the platform through blog posts, articles, and word-of-mouth
+[*] creating artwork and graphics for project assets such as icons and marketing material
+[*] supporting project infrastructure like the project website and demo servers
+[/list]
+[i]Software[/i] developers are of course welcomed; there are so many great ideas to implement and not enough people to make them all a reality! The $Projectname code base is an advanced and mature system, but the platform is still very flexible and responsive to new ideas.
+
+We're pretty relaxed when it comes to developers. We don't have a lot of rules. Some of us are over-worked and if you want to help we're happy to let you help. That said, attention to a few guidelines will make the process smoother and make it easier to work together. All developers are expected to abide by our [zrl=[baseurl]/help/developer/covenant]code of conduct[/zrl]. We have developers from across the globe with different abilities and different cultural backgrounds and different levels of patience. Our primary rule is to respect others. Sometimes this is hard and sometimes we have very different opinions of how things should work, but if everybody makes an effort, we'll get along just fine.
+
+This document will help you get started learning and contributing to $Projectname.
+
+[h3]Versions and Releases[/h3]
+
+$Projectname currently uses a standard version numbering sequence of $x.$y(.$z), for instance '1.12' or '1.12.1'. The first digit is the major version number. Major versions are released "roughly" once per year; often in December.
+
+The second digit is the minor release number. If this number is odd, it is a development version. If the number is even, it is a released version. Minor versions are released (moved from dev to master) typically once per month when development is 'stable', but this is likely to increase. Going forward minor releases will be made somewhere between one and three months; corresponding to a stable code point and when there is general community consensus that the current code base is stable enough to consider a release.
+
+The final digit is an interface or patch designator.
+
+The release process involves changing the version number (by definition the minor version number will be odd, and the minor number will be incremented). Once a year for a major release the major version will be incremented, and the minor number reset to 0.
+
+The release candidate is moved to a new branch; and testing will commence/continue for a period of 1-2 weeks afterward or until any significant issues have been resolved. This branch is usually labelled with RC (release candidate); for instance 1.8RC represents the pending release of version 1.8. At this time, the minor version number on the dev branch is incremented to the next odd number. (For instance 1.9). New development can then take place in the dev branch.
+
+Bug fixes should always be applied to 'dev' and from there merged forward (typically with git cherry-pick) to the RC branch and if necessary applied to the master or official release branch.
+
+At the time a release candidate is produced, the language strings file is frozen until a release is made. Translation work may continue, but all translations should be submitted to 'dev' and merged forward to RC.
+
+Once RC testing is completed, RC is merged to 'master' and the RC version designator removed; resulting in one final checkin to change the version number. The CHANGELOG file should also be updated at or just prior to this time. If there are merge conflicts during this final merge, the merge will be abandoned; and 'git merge -s ours' applied. This results in a replacement of master with the contents of the RC branch. Conflicts often arise with string updates which were made to master after the last release and cannot easily be resolved without hand editing. Since this is a release of tested code, hand editing is discouraged, and the replacement merge strategy should be used instead. It is assumed that RC now contains the most recent well-tested code.
+
+Once the release is live and merged to master, the RC branch may be removed.
+
+Fixes may be made to master after release. Where possible these should be made to dev and 'git cherry-pick' used to merge forward; which preserves the commit info and prevents merge conflicts in the next cycle. Only rarely does a patch only apply to the master branch. If necessary this can be made. If the change is severe, the interface version number should be incremented. This is at the discretion of the community. In any event, a 'git pull' of the master branch should always result in the latest release with any post-release patches applied.
+
+The interface number (the $z in $x.$y.$z) should be incremented in dev whenever a change is made which changes the interfaces or API in incompatible ways so that any external packages (especially addons and API clients) relying on a the current behaviour can discover and change their own interfaces accordingly at the point that it changed.
+
+[h3]Git repository branches[/h3]
+
+There are two official branches of the $Projectname git repo.
+[list]
+[*] The stable version is maintained on the [b]master[/b] branch. The latest commit in this branch is considered to be suitable for production hubs.
+[*] Experimental development occurs on the [b]dev[/b] branch, which is merged into [b]master[/b] when it is deemed tested and stable enough.
+[/list]
+
+[h3]Developer tools and workflows[/h3]
+
+[h4]Hub Snapshots[/h4]
+
+The [url=[baseurl]/help/admin/hub_snapshots]hub snapshots[/url] page provides instructions and scripts for taking complete snapshots of a hub to support switching between consistent and completely known states. This is useful to prevent situations where the content or database schema might be incompatible with the code.
+
+[h3]Translations[/h3]
+
+Our translations are managed through Transifex. If you wish to help out translating $Projectname to another language, sign up on transifex.com, visit [url=https://www.transifex.com/Friendica/red-matrix/]Transifex[/url] and request to join one of the existing language teams or create a new one. Notify one of the core developers when you have a translation update which requires merging, or ask about merging it yourself if you're comfortable with git and PHP. We have a string file called 'messages.po' which is gettext compliant and a handful of email templates, and from there we automatically generate the application's language files.
+
+[h4]Translation Process[/h4]
+
+The strings used in the UI of $Projectname is translated at [url=https://www.transifex.com/Friendica/red-matrix/]Transifex[/url] and then
+included in the git repository at github. If you want to help with translation
+for any language, be it correcting terms or translating $Projectname to a
+currently not supported language, please register an account at transifex.com
+and contact the Redmatrix translation team there.
+
+Translating $Projectname is simple. Just use the online tool at transifex. If you
+don't want to deal with git & co. that is fine, we check the status of the[/td][/tr]
+[tr]ranslations regularly and import them into the source tree at github so that
+others can use them.
+
+We do not include every translation from transifex in the source tree to avoid
+a scattered and disturbed overall experience. As an uneducated guess we have a
+lower limit of 50% translated strings before we include the language. This
+limit is judging only by the amount of translated strings under the assumption[/td][/tr]
+[tr]hat the most prominent strings for the UI will be translated first by a[/td][/tr]
+[tr]ranslation team. If you feel your translation useable before this limit,
+please contact us and we will probably include your teams work in the source[/td][/tr]
+[tr]ree.
+
+If you want to get your work into the source tree yourself, feel free to do so
+and contact us with and question that arises. The process is simple and
+$Projectname ships with all the tools necessary.
+
+The location of the translated files in the source tree is
+ /view/LNG-CODE/
+where LNG-CODE is the language code used, e.g. de for German or fr for French.
+For the email templates (the *.tpl files) just place them into the directory
+and you are done. The translated strings come as a "hmessages.po" file from[/td][/tr]
+[tr]ransifex which needs to be translated into the PHP file $Projectname uses. To do
+so, place the file in the directory mentioned above and use the "po2php"
+utility from the util directory of your $Projectname installation.
+
+Assuming you want to convert the German localization which is placed in
+view/de/hmessages.po you would do the following.
+
+1. Navigate at the command prompt to the base directory of your
+ $Projectname installation
+
+2. Execute the po2php script, which will place the translation
+ in the hstrings.php file that is used by $Projectname.
+
+ $> php util/po2php.php view/de/hmessages.po
+
+ The output of the script will be placed at view/de/hstrings.php where
+ froemdoca os expecting it, so you can test your translation mmediately.
+
+3. Visit your $Projectname page to check if it still works in the language you
+ just translated. If not try to find the error, most likely PHP will give
+ you a hint in the log/warnings.about the error.
+
+ For debugging you can also try to "run" the file with PHP. This should
+ not give any output if the file is ok but might give a hint for
+ searching the bug in the file.
+
+ $> php view/de/hstrings.php
+
+4. commit the two files with a meaningful commit message to your git
+ repository, push it to your fork of the $Projectname repository at github and
+ issue a pull request for that commit.
+
+[h4]Utilities[/h4]
+
+Additional to the po2php script there are some more utilities for translation
+in the "util" directory of the $Projectname source tree. If you only want to[/td][/tr]
+[tr]ranslate $Projectname into another language you wont need any of these tools most
+likely but it gives you an idea how the translation process of $Projectname
+works.
+
+For further information see the utils/README file.
+
+[h4]Known Problems[/h4]
+
+* $Projectname uses the language setting of the visitors browser to determain the
+ language for the UI. Most of the time this works, but there are some known
+ quirks.
+* the early translations are based on the friendica translations, if you
+ some rough translations please let us know or fix them at Transifex.
+
+[h3]Licensing[/h3]
+
+All code contributed to the project falls under the MIT license, unless otherwise specified. We will accept third-party code which falls under MIT, BSD and LGPL, but copyleft licensing (GPL, and AGPL) is only permitted in addons. It must be possible to completely remove the GPL (copyleft) code from the main project without breaking anything.
+
+[h3]Coding Style[/h3]
+
+In the interests of consistency we adopt the following code styling. We may accept patches using other styles, but where possible please try to provide a consistent code style. We aren't going to argue or debate the merits of this style, and it is irrelevant what project 'xyz' uses. This is not project 'xyz'. This is a baseline to try and keep the code readable now and in the future.
+[list]
+[*]All comments should be in English.
+[*]We use doxygen to generate documentation. This hasn't been consistently applied, but learning it and using it are highly encouraged.
+[*]Indentation is accomplished primarily with tabs using a tab-width of 4.
+[*]String concatenation and operators should be separated by whitespace. e.g. "$foo = $bar . 'abc';" instead of "$foo=$bar.'abc';"
+[*]Generally speaking, we use single quotes for string variables and double quotes for SQL statements. "Here documents" should be avoided. Sometimes using double quoted strings with variable replacement is the most efficient means of creating the string. In most cases, you should be using single quotes.
+[*]Use whitespace liberally to enhance readability. When creating arrays with many elements, we will often set one key/value pair per line, indented from the parent line appropriately. Lining up the assignment operators takes a bit more work, but also increases readability.
+[*]Generally speaking, opening braces go on the same line as the thing which opens the brace. They are the last character on the line. Closing braces are on a line by themselves.
+[*]Some functions take arguments in argc/argv style like main() in C or function args in bash or Perl. Urls are broken up within a module. e.g, given "http://example.com/module/arg1/arg2", then $this->argc will be 3 (integer) and $this->argv will contain: [0] => 'module', [1] => 'arg1', [2] => 'arg2'. There will always be one argument. If provided a naked domain URL, $this->argv[0] is set to "home".
+[/list]
+
+[h3]File system layout[/h3]
+[table border=0]
+[th]Directory[/th][th]Description[/th][/tr]
+[tr][td]addon[/td][td]optional addons/plugins[/td][/tr]
+[tr][td]boot.php[/td][td]Every process uses this to bootstrap the application structure[/td][/tr]
+[tr][td]doc[/td][td]Help Files[/td][/tr]
+[tr][td]images[/td][td]core required images[/td][/tr]
+[tr][td]include[/td][td]The "model" in MVC - (back-end functions), also contains PHP "executables" for background processing[/td][/tr]
+[tr][td]index.php[/td][td]The front-end controller for web access[/td][/tr]
+[tr][td]install[/td][td]Installation and upgrade files and DB schema[/td][/tr]
+[tr][td]library[/td][td]Third party modules (must be license compatible)[/td][/tr]
+[tr][td]mod[/td][td]Controller modules based on URL pathname (e.g. [url=http://sitename/foo]http://sitename/foo[/url] loads mod/foo.php)[/td][/tr]
+[tr][td]mod/site/[/td][td]site-specific mod overrides, excluded from git[/td][/tr]
+[tr][td]util[/td][td]translation tools, main English string database and other miscellaneous utilities[/td][/tr]
+[tr][td]version.inc[/td][td]contains current version (auto-updated via cron for the master repository and distributed via git)[/td][/tr]
+[tr][td]view[/td][td]theming and language files[/td][/tr]
+[tr][td]view/(css,js,img,php,tpl)[/td][td]default theme files[/td][/tr]
+[tr][td]view/(en,it,es ...)[/td][td]language strings and resources[/td][/tr]
+[tr][td]view/theme/[/td][td]individual named themes containing (css,js,img,php,tpl) over-rides[/td][/tr]
+[/table]
+
+[b][url=[baseurl]/help/developer/unorganized]More information needing re-organization and updating...[/url][/b]
diff --git a/doc/developer/developer_guide.md b/doc/developer/developer_guide.md
deleted file mode 100644
index fa50de8a1..000000000
--- a/doc/developer/developer_guide.md
+++ /dev/null
@@ -1,422 +0,0 @@
-### Who is a Hubzilla developer? Should I read this?
-
-Anyone who contributes to making Hubzilla better is a developer. There are many different and important ways you can contribute to this amazing technology, _even if you do not know how to write code_. The software itself is only a part of the Hubzilla project. You can contribute by
-
-* translating text to your language so that people around the world have the opportunity to use Hubzilla
-* promoting Hubzilla and spreading awareness of the platform through blog posts, articles, and word-of-mouth
-* creating artwork and graphics for project assets such as icons and marketing material
-* supporting project infrastructure like the project website and demo servers
-
-_Software_ developers are of course welcomed; there are so many great ideas to implement and not enough people to make them all a reality! The Hubzilla code base is an advanced and mature system, but the platform is still very flexible and responsive to new ideas.
-
-This document will help you get started learning and contributing to Hubzilla.
-
-### Versioning system
-
-The versioning system is similar to the popular semantic versioning but less stringent. Given x.y.z, x changes yearly. y changes for "stable" monthly builds, and z increments when there are interface changes. We maintain our date and build numbers for medium grain version control (commits within a certain date range) and of course git revs for fine grained control.
-
-### Git repository branches
-
-There are two official branches of the Hubzilla git repo.
-
-* The stable version is maintained on the **master** branch. The latest commit in this branch is considered to be suitable for production hubs.
-* Experimental development occurs on the **dev** branch, which is merged into **master** when it is deemed tested and stable enough.
-
-### Developer tools and workflows
-
-#### Hub Snapshots
-
-The [hub snapshots](/help/admin/hub_snapshots) page provides instructions and scripts for taking complete
-snapshots of a hub to support switching between consistent and completely known
-states. This is useful to prevent situations where the content or database schema
-might be incompatible with the code.
-
-### Translations
-
-Our translations are managed through Transifex. If you wish to help out translating Hubzilla to another language, sign up on transifex.com, visit [https://www.transifex.com/projects/p/red-matrix/](https://www.transifex.com/projects/p/red-matrix/) and request to join one of the existing language teams or create a new one. Notify one of the core developers when you have a translation update which requires merging, or ask about merging it yourself if you're comfortable with git and PHP. We have a string file called 'messages.po' which is gettext compliant and a handful of email templates, and from there we automatically generate the application's language files.
-
-#### Translation Process
-
-The strings used in the UI of Hubzilla is translated at [Transifex][1] and then
-included in the git repository at github. If you want to help with translation
-for any language, be it correcting terms or translating Hubzilla to a
-currently not supported language, please register an account at transifex.com
-and contact the Redmatrix translation team there.
-
-Translating Hubzilla is simple. Just use the online tool at transifex. If you
-don't want to deal with git & co. that is fine, we check the status of the
-translations regularly and import them into the source tree at github so that
-others can use them.
-
-We do not include every translation from transifex in the source tree to avoid
-a scattered and disturbed overall experience. As an uneducated guess we have a
-lower limit of 50% translated strings before we include the language. This
-limit is judging only by the amount of translated strings under the assumption
-that the most prominent strings for the UI will be translated first by a
-translation team. If you feel your translation useable before this limit,
-please contact us and we will probably include your teams work in the source
-tree.
-
-If you want to get your work into the source tree yourself, feel free to do so
-and contact us with and question that arises. The process is simple and
-Hubzilla ships with all the tools necessary.
-
-The location of the translated files in the source tree is
- /view/LNG-CODE/
-where LNG-CODE is the language code used, e.g. de for German or fr for French.
-For the email templates (the *.tpl files) just place them into the directory
-and you are done. The translated strings come as a "hmessages.po" file from
-transifex which needs to be translated into the PHP file Hubzilla uses. To do
-so, place the file in the directory mentioned above and use the "po2php"
-utility from the util directory of your Hubzilla installation.
-
-Assuming you want to convert the German localization which is placed in
-view/de/hmessages.po you would do the following.
-
-1. Navigate at the command prompt to the base directory of your
- Hubzilla installation
-
-2. Execute the po2php script, which will place the translation
- in the hstrings.php file that is used by Hubzilla.
-
- $> php util/po2php.php view/de/hmessages.po
-
- The output of the script will be placed at view/de/hstrings.php where
- froemdoca os expecting it, so you can test your translation mmediately.
-
-3. Visit your Hubzilla page to check if it still works in the language you
- just translated. If not try to find the error, most likely PHP will give
- you a hint in the log/warnings.about the error.
-
- For debugging you can also try to "run" the file with PHP. This should
- not give any output if the file is ok but might give a hint for
- searching the bug in the file.
-
- $> php view/de/hstrings.php
-
-4. commit the two files with a meaningful commit message to your git
- repository, push it to your fork of the Hubzilla repository at github and
- issue a pull request for that commit.
-
-#### Utilities
-
-Additional to the po2php script there are some more utilities for translation
-in the "util" directory of the Hubzilla source tree. If you only want to
-translate Hubzilla into another language you wont need any of these tools most
-likely but it gives you an idea how the translation process of Hubzilla
-works.
-
-For further information see the utils/README file.
-
-#### Known Problems
-
-* Hubzilla uses the language setting of the visitors browser to determain the
- language for the UI. Most of the time this works, but there are some known
- quirks.
-* the early translations are based on the friendica translations, if you
- some rough translations please let us know or fix them at Transifex.
-
-### To-be-organized information
-
-**Here is how you can join us.**
-
-First, get yourself a working git package on the system where you will be
-doing development.
-
-Create your own github account.
-
-You may fork/clone the Red repository from [https://github.com/redmatrix/hubzilla.git](https://github.com/redmatrix/hubzilla.git).
-
-Follow the instructions provided here: [http://help.github.com/fork-a-repo/](http://help.github.com/fork-a-repo/)
-to create and use your own tracking fork on github
-
-Then go to your github page and create a "Pull request" when you are ready
-to notify us to merge your work.
-
-
-**Important**
-
-Please pull in any changes from the project repository and merge them with your work **before** issuing a pull request. We reserve the right to reject any patch which results in a large number of merge conflicts. This is especially true in the case of language translations - where we may not be able to understand the subtle differences between conflicting versions.
-
-Also - **test your changes**. Don't assume that a simple fix won't break something else. If possible get an experienced Red developer to review the code.
-
-
-**Licensing**
-
-All code contributed to the project falls under the MIT license, unless otherwise specified. We will accept third-party code which falls under MIT, BSD and LGPL, but copyleft licensing (GPL, and AGPL) is only permitted in addons. It must be possible to completely remove the GPL (copyleft) code from the main project without breaking anything.
-
-**Coding Style**
-
-In the interests of consistency we adopt the following code styling. We may accept patches using other styles, but where possible please try to provide a consistent code style. We aren't going to argue or debate the merits of this style, and it is irrelevant what project 'xyz' uses. This is not project 'xyz'. This is a baseline to try and keep the code readable now and in the future.
-
-* All comments should be in English.
-
-* We use doxygen to generate documentation. This hasn't been consistently applied, but learning it and using it are highly encouraged.
-
-* Indentation is accomplished primarily with tabs using a tab-width of 4.
-
-* String concatenation and operators should be separated by whitespace. e.g. "$foo = $bar . 'abc';" instead of "$foo=$bar.'abc';"
-
-* Generally speaking, we use single quotes for string variables and double quotes for SQL statements. "Here documents" should be avoided. Sometimes using double quoted strings with variable replacement is the most efficient means of creating the string. In most cases, you should be using single quotes.
-
-* Use whitespace liberally to enhance readability. When creating arrays with many elements, we will often set one key/value pair per line, indented from the parent line appropriately. Lining up the assignment operators takes a bit more work, but also increases readability.
-
-* Generally speaking, opening braces go on the same line as the thing which opens the brace. They are the last character on the line. Closing braces are on a line by themselves.
-
-
-**File system layout:**
-
-[addon] optional addons/plugins
-
-[boot.php] Every process uses this to bootstrap the application structure
-
-[doc] Help Files
-
-[images] core required images
-
-[include] The "model" in MVC - (back-end functions), also contains PHP "executables" for background processing
-
-[index.php] The front-end controller for web access
-
-[install] Installation and upgrade files and DB schema
-
-[library] Third party modules (must be license compatible)
-
-[mod] Controller modules based on URL pathname (e.g. #^[url=http://sitename/foo]http://sitename/foo[/url] loads mod/foo.php)
-
-[mod/site/] site-specific mod overrides, excluded from git
-
-[util] translation tools, main English string database and other miscellaneous utilities
-
-[version.inc] contains current version (auto-updated via cron for the master repository and distributed via git)
-
-[view] theming and language files
-
-[view/(css,js,img,php,tpl)] default theme files
-
-[view/(en,it,es ...)] language strings and resources
-
-[view/theme/] individual named themes containing (css,js,img,php,tpl) over-rides
-
-**The Database:**
-
-
-| Table | Description |
-|-------------------------|--------------------------------------------------------|
-| abconfig | contact table, replaces Friendica 'contact' |
-| abook | |
-| account | service provider account |
-| addon | |
-| addressbookchanges | |
-| addressbooks | |
-| app | |
-| atoken | |
-| attach | |
-| auth_codes | |
-| cache | |
-| cal | |
-| calendarchanges | |
-| calendarinstances | |
-| calendarobjects | |
-| calendars | |
-| calendarsubscriptions | |
-| cards | |
-| channel | |
-| chat | |
-| chatpresence | |
-| chatroom | |
-| clients | |
-| config | |
-| conv | |
-| dreport | |
-| event | |
-| group_member | |
-| groupmembers | |
-| groups | |
-| hook | |
-| hubloc | |
-| iconfig | |
-| issue | |
-| item | |
-| item_id | |
-| likes | |
-| locks | |
-| mail | |
-| menu | |
-| menu_item | |
-| notify | |
-| obj | |
-| outq | |
-| pconfig | personal (per channel) configuration storage |
-| photo | |
-| poll | |
-| poll_elm | |
-| principals | |
-| profdef | |
-| profext | |
-| profile | |
-| profile_check | |
-| propertystorage | |
-| register | |
-| schedulingobjects | |
-| session | |
-| shares | |
-| sign | |
-| site | |
-| source | |
-| sys_perms | |
-| term | |
-| tokens | |
-| updates | |
-| users | |
-| verify | |
-| vote | |
-| xchan | |
-| xchat | |
-| xconfig | |
-| xign | |
-| xlink | |
-| xperm | |
-| xprof | |
-| xtag | |
-
-
- * abook - contact table, replaces Friendica 'contact'
- * account - service provider account
- * addon - registered plugins
- * app - peronal app data
- * attach - file attachments
- * auth_codes - OAuth usage
- * cache - OEmbed cache
- * channel - replaces Friendica 'user'
- * chat - chat room content
- * chatpresence - channel presence information for chat
- * chatroom - data for the actual chat room
- * clients - OAuth usage
- * config - main configuration storage
- * conv - Diaspora private messages
- * event - Events
- * fcontact - friend suggestion stuff
- * ffinder - friend suggestion stuff
- * fserver - obsolete
- * fsuggest - friend suggestion stuff
- * groups - privacy groups
- * group_member - privacy groups
- * hook - plugin hook registry
- * hubloc - Red location storage, ties a location to an xchan
- * item - posts
- * item_id - other identifiers on other services for posts
- * likes - likes of 'things'
- * mail - private messages
- * menu - channel menu data
- * menu_item - items uses by channel menus
- * notify - notifications
- * notify-threads - need to factor this out and use item thread info on notifications
- * obj - object data for things (x has y)
- * outq - output queue
- * pconfig - personal (per channel) configuration storage
- * photo - photo storage
- * poll - data for polls
- * poll_elm - data for poll elements
- * profdef - custom profile field definitions
- * profext - custom profile field data
- * profile - channel profiles
- * profile_check - DFRN remote auth use, may be obsolete
- * register - registrations requiring admin approval
- * session - web session storage
- * shares - shared item information
- * sign - Diaspora signatures. To be phased out.
- * site - site table to find directory peers
- * source - channel sources data
- * spam - unfinished
- * sys_perms - extensible permissions for the sys channel
- * term - item taxonomy (categories, tags, etc.) table
- * tokens - OAuth usage
- * updates - directory sync updates
- * verify - general purpose verification structure
- * vote - vote data for polls
- * xchan - replaces 'gcontact', list of known channels in the universe
- * xchat - bookmarked chat rooms
- * xconfig - as pconfig but for channels with no local account
- * xlink - "friends of friends" linkages derived from poco
- * xprof - if this hub is a directory server, contains basic public profile info of everybody in the network
- * xtag - if this hub is a directory server, contains tags or interests of everybody in the network
-
-
-**How to theme Hubzilla**
-
-This is a short documentation on what I found while trying to modify Hubzilla's appearance.
-
-First, you'll need to create a new theme. This is in /view/theme, and I chose to copy 'redbasic' since it's the only available for now. Let's assume I named it .
-
-Oh, and don't forget to rename the _init function in /php/theme.php to be _init() instead of redbasic_init().
-
-At that point, if you need to add javascript or css files, add them to /js or /css, and then "register" them in _init() through head_add_js('file.js') and head_add_css('file.css').
-
-Now you'll probably want to alter a template. These can be found in in /view/tpl OR view//tpl. All you should have to do is copy whatever you want to tweak from the first place to your theme's own tpl directory.
-
-
-We're pretty relaxed when it comes to developers. We don't have a lot of rules. Some of us are over-worked and if you want to help we're happy to let you help. That said, attention to a few guidelines will make the process smoother and make it easier to work together. We have developers from across the globe with different abilities and different cultural backgrounds and different levels of patience. Our primary rule is to respect others. Sometimes this is hard and sometimes we have very different opinions of how things should work, but if everybody makes an effort, we'll get along just fine.
-
-**Here is how you can join us.**
-
-First, get yourself a working git package on the system where you will be
-doing development.
-
-Create your own github account.
-
-You may fork/clone the Red repository from [url=https://github.com/redmatrix/hubzilla.git]https://github.com/redmatrix/hubzilla.git[/url]
-
-Follow the instructions provided here: [url=http://help.github.com/fork-a-repo/]http://help.github.com/fork-a-repo/[/url]
-to create and use your own tracking fork on github
-
-Then go to your github page and create a "Pull request" when you are ready
-to notify us to merge your work.
-
-**Translations**
-
-Our translations are managed through Transifex. If you wish to help out translating the $Projectname to another language, sign up on transifex.com, visit [url=https://www.transifex.com/projects/p/red-matrix/]https://www.transifex.com/projects/p/red-matrix/[/url] and request to join one of the existing language teams or create a new one. Notify one of the core developers when you have a translation update which requires merging, or ask about merging it yourself if you're comfortable with git and PHP. We have a string file called 'messages.po' which is gettext compliant and a handful of email templates, and from there we automatically generate the application's language files.
-
-
-**Important**
-
-Please pull in any changes from the project repository and merge them with your work **before** issuing a pull request. We reserve the right to reject any patch which results in a large number of merge conflicts. This is especially true in the case of language translations - where we may not be able to understand the subtle differences between conflicting versions.
-
-Also - **test your changes**. Don't assume that a simple fix won't break something else. If possible get an experienced Red developer to review the code.
-
-Further documentation can be found at the Github wiki pages at: [url=https://github.com/friendica/red/wiki]https://github.com/friendica/red/wiki[/url]
-
-**Licensing**
-
-All code contributed to the project falls under the MIT license, unless otherwise specified. We will accept third-party code which falls under MIT, BSD and LGPL, but copyleft licensing (GPL, and AGPL) is only permitted in addons. It must be possible to completely remove the GPL (copyleft) code from the main project without breaking anything.
-
-**Concensus Building**
-
-Code changes which fix an obvious bug are pretty straight-forward. For instance if you click "Save" and the thing you're trying to save isn't saved, it's fairly obvious what the intended behaviour should be. Often when developing feature requests, it may affect large numbers of community members and it's possible that other members of the community won't agree with the need for the feature, or with your proposed implementation. They may not see something as a bug or a desirable feature.
-
-We encourage consensus building within the community when it comes to any feature which might be considered controversial or where there isn't unanimous decision that the proposed feature is the correct way to accomplish the task. The first place to pitch your ideas is to [url=https://zothub.com/channel/one]Channel One[/url]. Others may have some input or be able to point out facets of your concept which might be problematic in our environment. But also, you may encounter opposition to your plan. This doesn't mean you should stop and/or ignore the feature. Listen to the concerns of others and try and work through any implementation issues.
-
-There are places where opposition cannot be resolved. In these cases, please consider making your feature **optional** or non-default behaviour that must be specifically enabled. This technique can often be used when a feature has significant but less than unanimous support. Those who desire the feature can turn it on and those who don't want it - will leave it turned off.
-
-If a feature uses other networks or websites and or is only seen as desirable by a small minority of the community, consider making the functionality available via an addon or plugin. Once again, those who don't desire the feature won't need to install it. Plugins are relatively easy to create and "hooks" can be easily added or modified if the current hooks do not do what is needed to allow your plugin to work.
-
-
-**Coding Style**
-
-In the interests of consistency we adopt the following code styling. We may accept patches using other styles, but where possible please try to provide a consistent code style. We aren't going to argue or debate the merits of this style, and it is irrelevant what project 'xyz' uses. This is not project 'xyz'. This is a baseline to try and keep the code readable now and in the future.
-
-* All comments should be in English.
-
-* We use doxygen to generate documentation. This hasn't been consistently applied, but learning it and using it are highly encouraged.
-
-* Indentation is accomplished primarily with tabs using a tab-width of 4.
-
-* String concatenation and operators should be separated by whitespace. e.g. "$foo = $bar . 'abc';" instead of "$foo=$bar.'abc';"
-
-* Generally speaking, we use single quotes for string variables and double quotes for SQL statements. "Here documents" should be avoided. Sometimes using double quoted strings with variable replacement is the most efficient means of creating the string. In most cases, you should be using single quotes.
-
-* Use whitespace liberally to enhance readability. When creating arrays with many elements, we will often set one key/value pair per line, indented from the parent line appropriately. Lining up the assignment operators takes a bit more work, but also increases readability.
-
-* Generally speaking, opening braces go on the same line as the thing which opens the brace. They are the last character on the line. Closing braces are on a line by themselves.
-
-* Some functions take arguments in argc/argv style like main() in C or function args in bash or Perl. Urls are broken up within a module. e.g, given "http://example.com/module/arg1/arg2", then $this->argc will be 3 (integer) and $this->argv will contain: [0] => 'module', [1] => 'arg1', [2] => 'arg2'. There will always be one argument. If provided a naked domain URL, $this->argv[0] is set to "home". \ No newline at end of file
diff --git a/doc/developer/unorganized.md b/doc/developer/unorganized.md
new file mode 100644
index 000000000..74d914aaf
--- /dev/null
+++ b/doc/developer/unorganized.md
@@ -0,0 +1,73 @@
+### To-be-organized information
+
+**Here is how you can join us.**
+
+First, get yourself a working git package on the system where you will be
+doing development.
+
+Create your own github account.
+
+You may fork/clone the Red repository from [https://github.com/redmatrix/hubzilla.git](https://github.com/redmatrix/hubzilla.git).
+
+Follow the instructions provided here: [http://help.github.com/fork-a-repo/](http://help.github.com/fork-a-repo/)
+to create and use your own tracking fork on github
+
+Then go to your github page and create a "Pull request" when you are ready
+to notify us to merge your work.
+
+
+**Important**
+
+Please pull in any changes from the project repository and merge them with your work **before** issuing a pull request. We reserve the right to reject any patch which results in a large number of merge conflicts. This is especially true in the case of language translations - where we may not be able to understand the subtle differences between conflicting versions.
+
+Also - **test your changes**. Don't assume that a simple fix won't break something else. If possible get an experienced Red developer to review the code.
+
+**How to theme Hubzilla**
+
+This is a short documentation on what I found while trying to modify Hubzilla's appearance.
+
+First, you'll need to create a new theme. This is in /view/theme, and I chose to copy 'redbasic' since it's the only available for now. Let's assume I named it .
+
+Oh, and don't forget to rename the _init function in /php/theme.php to be _init() instead of redbasic_init().
+
+At that point, if you need to add javascript or css files, add them to /js or /css, and then "register" them in _init() through head_add_js('file.js') and head_add_css('file.css').
+
+Now you'll probably want to alter a template. These can be found in in /view/tpl OR view//tpl. All you should have to do is copy whatever you want to tweak from the first place to your theme's own tpl directory.
+
+
+We're pretty relaxed when it comes to developers. We don't have a lot of rules. Some of us are over-worked and if you want to help we're happy to let you help. That said, attention to a few guidelines will make the process smoother and make it easier to work together. We have developers from across the globe with different abilities and different cultural backgrounds and different levels of patience. Our primary rule is to respect others. Sometimes this is hard and sometimes we have very different opinions of how things should work, but if everybody makes an effort, we'll get along just fine.
+
+**Here is how you can join us.**
+
+First, get yourself a working git package on the system where you will be
+doing development.
+
+Create your own github account.
+
+You may fork/clone the Red repository from [url=https://github.com/redmatrix/hubzilla.git]https://github.com/redmatrix/hubzilla.git[/url]
+
+Follow the instructions provided here: [url=http://help.github.com/fork-a-repo/]http://help.github.com/fork-a-repo/[/url]
+to create and use your own tracking fork on github
+
+Then go to your github page and create a "Pull request" when you are ready
+to notify us to merge your work.
+
+
+**Important**
+
+Please pull in any changes from the project repository and merge them with your work **before** issuing a pull request. We reserve the right to reject any patch which results in a large number of merge conflicts. This is especially true in the case of language translations - where we may not be able to understand the subtle differences between conflicting versions.
+
+Also - **test your changes**. Don't assume that a simple fix won't break something else. If possible get an experienced Red developer to review the code.
+
+Further documentation can be found at the Github wiki pages at: [url=https://github.com/friendica/red/wiki]https://github.com/friendica/red/wiki[/url]
+
+**Concensus Building**
+
+Code changes which fix an obvious bug are pretty straight-forward. For instance if you click "Save" and the thing you're trying to save isn't saved, it's fairly obvious what the intended behaviour should be. Often when developing feature requests, it may affect large numbers of community members and it's possible that other members of the community won't agree with the need for the feature, or with your proposed implementation. They may not see something as a bug or a desirable feature.
+
+We encourage consensus building within the community when it comes to any feature which might be considered controversial or where there isn't unanimous decision that the proposed feature is the correct way to accomplish the task. The first place to pitch your ideas is to [url=https://zothub.com/channel/one]Channel One[/url]. Others may have some input or be able to point out facets of your concept which might be problematic in our environment. But also, you may encounter opposition to your plan. This doesn't mean you should stop and/or ignore the feature. Listen to the concerns of others and try and work through any implementation issues.
+
+There are places where opposition cannot be resolved. In these cases, please consider making your feature **optional** or non-default behaviour that must be specifically enabled. This technique can often be used when a feature has significant but less than unanimous support. Those who desire the feature can turn it on and those who don't want it - will leave it turned off.
+
+If a feature uses other networks or websites and or is only seen as desirable by a small minority of the community, consider making the functionality available via an addon or plugin. Once again, those who don't desire the feature won't need to install it. Plugins are relatively easy to create and "hooks" can be easily added or modified if the current hooks do not do what is needed to allow your plugin to work.
+
diff --git a/doc/developer/zot_protocol.bb b/doc/developer/zot_protocol.bb
index b87e1cd73..e9355bca8 100644
--- a/doc/developer/zot_protocol.bb
+++ b/doc/developer/zot_protocol.bb
@@ -79,7 +79,7 @@ We may also attempt to recover with even less information, but doing so is prone
In order to implement high performance communications, the data transfer format for all aspects of Zot is JSON. XML communications require way too much overhead.
-Bi-directional encryption is based on RSA 4096-bit keys expressed in DER/ASN.1 format using the PKCS#8 encoding variant, with AES-256-CBC used for block encryption of variable length or large items.
+Bi-directional encryption is based on RSA 4096-bit keys expressed in DER/ASN.1 format using the PKCS#8 encoding variant, with AES encryption of variable length or large items. The precise encryption algorithms are negotiable between sites.
Some aspects of well known "federation protocols" (webfinger, salmon, activitystreams, portablecontacts, etc.) may be used in zot, but we are not tied to them and will not be bound by them. $Projectname project is attempting some rather novel developments in decentralised communications and if there is any need to diverge from such "standard protocols" we will do so without question or hesitation.
@@ -242,7 +242,7 @@ Example of discovery packet for 'mike@zothub.com'
Discovery returns a JSON array with the following components:
-'success' => ('1' or '') Operation was successful if '1'. Otherwise an optional 'message' may be present indicating the source of error.
+'success' => (true or false) Operation was successful if true. Otherwise an optional 'message' may be present indicating the source of error.
'signed_token' => If a token parameter was provided in the request, it is prepended with the text 'token.' and then RSA signed with the channel private key and base64url encoded and returned as 'signed_token'.
@@ -272,12 +272,11 @@ Discovery returns a JSON array with the following components:
'target_sig' => if a permissions target was specified, the signature is mirrored.
-'searchable' => ('1' or '') '1' indicates this entry can be searched in a directory
+'searchable' => (true or false) true indicates this entry can be searched in a directory
[h5]Permissions[/h5]
-
-'permisssions' => extensible array of permissions appropriate to this target, values are '1' or ''
+'permissions' => extensible array of permissions appropriate to this target, values are true or false
Permissions may include:
[list]
@@ -328,7 +327,7 @@ Each location is an array of
'address' => the webbie or user@host identifier associated with this location
-'primary' => ('1' or '') whether or not this is the primary location for this channel where files and web pages are generally found
+'primary' => (true or false) whether or not this is the primary location for this channel where files and web pages are generally found
'url' => url of the root of this DNS location e.g. https://example.com
@@ -391,7 +390,7 @@ When this packet is received, a Zot message is initiated to the auth identity:
}
[/code]
-auth_check messages MUST be encrypted with AES256CBC. This message is sent to the origination site, which checks the 'secret' to see if it is the same as the 'sec' which it passed originally. It also checks the secret_sig which is the secret signed by the destination channel's private key and base64url encoded. If everything checks out, a json packet is returned:
+auth_check messages MUST be encrypted. This message is sent to the origination site, which checks the 'secret' to see if it is the same as the 'sec' which it passed originally. It also checks the secret_sig which is the secret signed by the destination channel's private key and base64url encoded. If everything checks out, a json packet is returned:
[code nowrap]
{
"success":1,
@@ -404,11 +403,11 @@ auth_check messages MUST be encrypted with AES256CBC. This message is sent to th
[h4]Zot Signatures[/h4]
All signed data in Zot is accomplished by performing an RSA sign operation using the private key of the initiator. The binary result is then base64url encoded for transport.
[h4]Zot Encryption[/h4]
-Encryption is currently provided by AES256-CBC, the Advanced Encryption Standard using 256-bit keys and the Cipher Block Chaining mode of operation. Additional algorithms MAY be supported. A 32-octet key and 16-octet initialisation vector are randomly generated. The desired data is then encrypted using these generated strings and the result base64url encoded. Then we build an array:
+Encryption is currently provided by AES256CTR. Additional algorithms MAY be supported. A 32-octet key and 16-octet initialisation vector are randomly generated. The desired data is then encrypted using these generated strings and the result base64url encoded. Then we build an array:
[dl terms="b"]
[*= data]The base64url encoded encrypted data
-[*= alg]The chosen algorithm, in this case the string 'aes256cbc'.
+[*= alg]The chosen algorithm, in this case the string 'aes256ctr'.
[*= key]The randomly generated key, RSA encrypted using the recipients public key, and the result base64url encoded
[*= iv]The randomly generated initialization vector, RSA encrypted using the recipient's public key, and the result base64url encoded
[/dl]
@@ -449,7 +448,7 @@ M23in0xqMVsyQvzjNkpImrO/QdbEFRIIMee83IHq+adbyjQR49Z2hNEIZhkLPc3U
"callback":"\/post",
"version":"1.2",
"encryption":{
- "aes256cbc"
+ "aes256ctr"
},
"secret":"1eaa6613699be6ebb2adcefa5379c61a3678aa0df89025470fac871431b70467",
"secret_sig":"0uShifsvhHnxnPIlDM9lWuZ1hSJTrk3NN9Ds6AKpyNRqf3DUdz81-Xvs8I2kj6y5vfFtm-FPKAqu77XP05r74vGaWbqb1r8zpWC7zxXakVVOHHC4plG6rLINjQzvdSFKCQb5R_xtGsPPfvuE24bv4fvN4ZG2ILvb6X4Dly37WW_HXBqBnUs24mngoTxFaPgNmz1nDQNYQu91-ekX4-BNaovjDx4tP379qIG3-NygHTjFoOMDVUvs-pOPi1kfaoMjmYF2mdZAmVYS2nNLWxbeUymkHXF8lT_iVsJSzyaRFJS1Iqn7zbvwH1iUBjD_pB9EmtNmnUraKrCU9eHES27xTwD-yaaH_GHNc1XwXNbhWJaPFAm35U8ki1Le4WbUVRluFx0qwVqlEF3ieGO84PMidrp51FPm83B_oGt80xpvf6P8Ht5WvVpytjMU8UG7-js8hAzWQeYiK05YTXk-78xg0AO6NoNe_RSRk05zYpF6KlA2yQ_My79rZBv9GFt4kUfIxNjd9OiV1wXdidO7Iaq_Q"
diff --git a/doc/feature/saved_search.bb b/doc/feature/saved_search.bb
deleted file mode 100644
index 1e75f5a85..000000000
--- a/doc/feature/saved_search.bb
+++ /dev/null
@@ -1,19 +0,0 @@
-[h2]Saved Searches[/h2]
-
-In order to quickly find information, the 'saved search' widget may be used. This widget may be presented as a sidebar tool on your network page and possibly from your channel page. It is differentiated from the 'navigation bar' search tool in that it does not search the entire site, but only the subset of information available to your channel.
-
-Additionally the search terms you provide may activate a one-tme search or be saved in a list for re-use. Saving the search item also invokes the search in addition to adding it to the saved list (which is displayed below the search text entry box). Any item in the list may be discarded if it is no longer needed.
-
-The saved search widget will provide autocompletion of channels (the results are prefixed with '@'), and hashtags (prefixed with '#'). You do not need to enter these tags; although entering the desired tag will reduce the autocomplete results to only hold the relevant information. The behaviour maps as follows:
-
-[ul]
-
-[li]@name - search your network stream for posts or comments written by 'name'. This will also change the post editor permissions to include only 'name'; as if this was a privacy group.[/li]
-
-[li]#hashtag - search you network stream for posts containing #hashtag.[/li]
-
-[li]text - search your network stream for posts containing 'text'.[/li]
-
-
-[/li]
-
diff --git a/doc/feature/techlevels.bb b/doc/feature/techlevels.bb
deleted file mode 100644
index 9b07f086f..000000000
--- a/doc/feature/techlevels.bb
+++ /dev/null
@@ -1,15 +0,0 @@
-[h2]Techlevels[/h2]
-
-Techlevels is a unique feature of Hubzilla 'pro'. It is not available in other server_roles, although it expands on the concepts introduced in Hubzilla 'basic'.
-
-[h3]Background[/h3]
-
-We've implemented several different mechanisms in order to reduce the apparent complexity and learning curve presented to new members. At the same time, we do not wish to limit any functionality for people who are able to grasp some slightly advanced technical technical features. The first mechanism was to move several features to an optional 'Features' page where they could be enabled at will; with the default interface kept somewhat lean.
-
-The problem we had now is that the number of features began to grow dramatically, and the Feature page is daunting in possibilities. There are also features present which probably should not be available to all members, but may be extremely useful to those with technical backgrounds.
-
-The techlevels seeeks to remedy this by grouping features within different levels of technical ability; starting at 0 (uncomfortable with technology), and up to 5 (Unix wizard or equivalent).
-
-When a new member registers, their account is provided a techlevel setting of 0. On the account settings page they may change this to any available level. A higher level opens more advanced features and possible interactions.
-
-The account administrator may also lock a particular level, lock a maximum level, or change/re-arrange the features available to any level. Those with the minimum level are typically not very exploratory and are unlikely to discover the advanced modes. This is by design. Those that look around and desire more interactions will find them. In the absence of administrator defaults they may choose any level. As they look at the features available to the level in question, it is generally expected that they will discover some features are beyond their comprehension and it is hoped they will back off to a level where the interface and features are comfortable to their skill level. This is somewhat experimental at present and for that reason is not part of the 'standard' server role. The standard server role is preset to level '5', and the basic server role is preset to level '0', with no possibility of change. Members in these roles may find themselves overwhelmed or underwhelmed by the feature set and complexity.
diff --git a/doc/hook/author_is_pmable.bb b/doc/hook/author_is_pmable.bb
new file mode 100644
index 000000000..11d1185f3
--- /dev/null
+++ b/doc/hook/author_is_pmable.bb
@@ -0,0 +1,14 @@
+[h2]author_is_pmable[/h2]
+
+Called from thread action menu before returning a 'send mail' link for the post author. Not all authors will be able to receive private mail, for instance those on other networks with incompatible mail systems.
+
+By default author_is_pmable() returns true for 'zot' xchans, and false for all others.
+
+The plugin is passed an array
+
+ [ 'xchan' => $author_xchan, 'abook' => abook record, 'result' => 'unset' ]
+
+A plugin which sets the 'result' to something besides 'unset' will over-ride the default behaviour. A value of true will enable the 'send mail' link and the private mail recipient will be set to the author's xchan_hash. A value of false will disable the 'send mail' link.
+
+
+
diff --git a/doc/hook/can_comment_on_post.bb b/doc/hook/can_comment_on_post.bb
new file mode 100644
index 000000000..2cfd3b2da
--- /dev/null
+++ b/doc/hook/can_comment_on_post.bb
@@ -0,0 +1,13 @@
+[h3]can_comment_on_post[/h3]
+
+Called when deciding whether or not to display a comment box for a post.
+
+
+Hook data (array):
+ observer_hash => xchan_hash of current observer
+ item => posted item
+ allowed => 'unset'
+
+
+To over-ride the default behaviour, change allowed to true or false
+
diff --git a/doc/hook/channel_links.bb b/doc/hook/channel_links.bb
new file mode 100644
index 000000000..c0243dac6
--- /dev/null
+++ b/doc/hook/channel_links.bb
@@ -0,0 +1,12 @@
+[h2]channel_links[/h2]
+
+Called when generating the Link HTTP header for the channel page. Different protocol stacks can add links to this header.
+
+Hook data = array
+ 'channel_address' => channel nickname, no checking is done to see if it is valid
+ 'channel_links' => array of channel links in the format
+ 'url' => url of resource
+ 'rel' => link relation
+ 'type' => MIME type
+
+All fields are required \ No newline at end of file
diff --git a/doc/hook/connection_remove.bb b/doc/hook/connection_remove.bb
new file mode 100644
index 000000000..bd13ae5f2
--- /dev/null
+++ b/doc/hook/connection_remove.bb
@@ -0,0 +1,9 @@
+[h3]connection_remove[/h3]
+
+Called when deleting a connection.
+
+
+Passed parameter array:
+
+ 'channel_id' => channel_id of the channel removing the connection
+ 'abook_id' => abook_id of the connection being removed
diff --git a/doc/hook/legal_webbie.bb b/doc/hook/legal_webbie.bb
new file mode 100644
index 000000000..8c7d32d56
--- /dev/null
+++ b/doc/hook/legal_webbie.bb
@@ -0,0 +1,10 @@
+[h2]legal_webbie[/h2]
+
+Called when validating a channel address. By default the valid characters are
+a-z,0-9,-,_, and . Uppercase ASCII characters are folded to lower and any invalid characters are stripped.
+
+Some federated networks require more restrictive rules.
+
+The hook is called with an array [ 'input' => (supplied text), 'output' => (validated text) ]
+
+A plugin will generally perform a regex filter or text operation on 'input' and provide the results in 'output'. \ No newline at end of file
diff --git a/doc/hook/legal_webbie_text.bb b/doc/hook/legal_webbie_text.bb
new file mode 100644
index 000000000..32c74c93b
--- /dev/null
+++ b/doc/hook/legal_webbie_text.bb
@@ -0,0 +1,7 @@
+[h2]legal_webbie_text[/h2]
+
+Returns a string describing the text rules applied to legal_webbie().
+
+Called with an array [ 'text' => (descriptive text describing text character limitations) ]
+
+A plugin should return the description of the allowed characters and operation performed in the 'legal_webbie' hook to assist people when creating a new channel. \ No newline at end of file
diff --git a/doc/hook/probe_well_known.bb b/doc/hook/probe_well_known.bb
deleted file mode 100644
index 62898c536..000000000
--- a/doc/hook/probe_well_known.bb
+++ /dev/null
@@ -1,3 +0,0 @@
-[h2]probe_well_known[/h2]
-
-This hook is under construction and not currently used - see include/probe.php \ No newline at end of file
diff --git a/doc/hook/update_unseen.bb b/doc/hook/update_unseen.bb
new file mode 100644
index 000000000..8fb02c239
--- /dev/null
+++ b/doc/hook/update_unseen.bb
@@ -0,0 +1,9 @@
+[h3]update_unseen[/h3]
+
+Called prior to automatically marking items 'seen'; allowing a plugin the choice to not perform this action.
+
+hook data
+
+[ 'channel_id' => local_channel(), 'update' => 'unset' ];
+
+If 'update' is set to 0 or false on return, the update operation is not performed. \ No newline at end of file
diff --git a/doc/hooklist.bb b/doc/hooklist.bb
index fcd0e2aff..1192a1506 100644
--- a/doc/hooklist.bb
+++ b/doc/hooklist.bb
@@ -28,7 +28,7 @@ Hooks allow plugins/addons to "hook into" the code at many points and alter the
[zrl=[baseurl]/help/hook/account_settings]account_settings[/zrl]
Called when generating the account settings form
-[zrl=[baseurl]/help/hook/settings_account]account_settings_post[/zrl]
+[zrl=[baseurl]/help/hook/account_settings_post]account_settings_post[/zrl]
Called when posting from the account settings form
[zrl=[baseurl]/help/hook/activity_received]activity_received[/zrl]
@@ -64,6 +64,9 @@ Hooks allow plugins/addons to "hook into" the code at many points and alter the
[zrl=[baseurl]/help/hook/authenticate]authenticate[/zrl]
Can provide alternate authentication mechanisms
+[zrl=[baseurl]/help/hook/author_is_pmable]author_is_pmable[/zrl]
+ Called from the thread action menu to determine if we can send private mail to the post author
+
[zrl=[baseurl]/help/hook/bb2diaspora]bb2diaspora[/zrl]
called when converting bbcode to markdown
@@ -79,12 +82,18 @@ Hooks allow plugins/addons to "hook into" the code at many points and alter the
[zrl=[baseurl]/help/hook/build_pagehead]build_pagehead[/zrl]
Called when creating the HTML page header
+[zrl=[baseurl]/help/hook/can_comment_on_post]can_comment_on_post[/zrl]
+ Called when deciding whether or not to present a comment box for a post
+
[zrl=[baseurl]/help/hook/change_channel]change_channel[/zrl]
Called when logging in to a channel (either during login or afterward through the channel manager)
[zrl=[baseurl]/help/hook/channel_remove]channel_remove[/zrl]
Called when removing a channel
+[zrl=[baseurl]/help/hook/channel_links]channel_links[/zrl]
+ Called when generating the Link: HTTP header for a channel
+
[zrl=[baseurl]/help/hook/channel_settings]channel_settings[/zrl]
Called when displaying the channel settings page
@@ -115,6 +124,9 @@ Hooks allow plugins/addons to "hook into" the code at many points and alter the
[zrl=[baseurl]/help/hook/connect_premium]connect_premium[/zrl]
Called when connecting to a premium channel
+[zrl=[baseurl]/help/hook/connection_remove]connection_remove[/zrl]
+ Called when deleting/removing a connection
+
[zrl=[baseurl]/help/hook/connector_settings]connector_settings[/zrl]
Called when posting to the features/addon settings page
@@ -314,6 +326,12 @@ Hooks allow plugins/addons to "hook into" the code at many points and alter the
[zrl=[baseurl]/help/hook/jot_tool]jot_tool[/zrl]
Deprecated and possibly obsolete. Allows one to add action buttons to the post editor.
+[zrl=[baseurl]/help/hook/legal_webbie]legal_webbie[/zrl]
+ Called to validate a channel address
+
+[zrl=[baseurl]/help/hook/legal_webbie_text]legal_webbie_text[/zrl]
+ Provides an explanation of text/character restrictions for legal_webbie()
+
[zrl=[baseurl]/help/hook/load_pdl]load_pdl[/zrl]
Called when we load a PDL file or description
@@ -491,9 +509,6 @@ Hooks allow plugins/addons to "hook into" the code at many points and alter the
[zrl=[baseurl]/help/hook/prepare_body_init]prepare_body_init[/zrl]
Called before generating the HTML for a displayed conversation item
-[zrl=[baseurl]/help/hook/probe_well_known]probe_well_known[/zrl]
- under construction
-
[zrl=[baseurl]/help/hook/proc_run]proc_run[/zrl]
Called when invoking PHP sub processes
@@ -560,6 +575,9 @@ Hooks allow plugins/addons to "hook into" the code at many points and alter the
[zrl=[baseurl]/help/hook/tagged]tagged[/zrl]
Called when a delivery is processed which results in you being tagged
+[zrl=[baseurl]/help/hook/update_unseen]update_unseen[/zrl]
+ Called prior to automatically marking items seen which were loaded in the browser
+
[zrl=[baseurl]/help/hook/validate_channelname]validate_channelname[/zrl]
Used to validate the names used by a channel
diff --git a/doc/main.bb b/doc/main.bb
deleted file mode 100644
index 8ba5d481b..000000000
--- a/doc/main.bb
+++ /dev/null
@@ -1,13 +0,0 @@
-
-[zrl=[baseurl]/help/about][b]What is $Projectname?[/b][/zrl]
-$Projectname is a decentralized communication and publishing platform that enables you to keep in control of your communication needs by automatic encryption and finely grained access control. It's you, and only you who decides who is allowed to see your stuff.
-
-[zrl=[baseurl]/help/features][b]$Projectname Features[/b][/zrl]
-
-$Projectname is already running as a global distributed network and proves its versatility and scalability from standalone to huge sites on a daily basis.
-Think of standalone family communication platforms, distributed online communities, support forums, blogs and homepages. Or professional content providers with commercial premium channels and targeted content acces. Whatever you want, $Projectname is there to cater to your creativity.
-
-[zrl=[baseurl]/help/what_is_zot][b]Got Zot? Well, you should.[/b][/zrl]
-Zot is the great new communicaton protocol invented especially for $Projectname. As a member you are no longer bound to a single site or hub thanks to "Nomadic Identities". Migrate easily to another server and keep your contacts intact, or clone it and run the same channel on several servers. Just in case one of them might shut down, you don't lose out. Plus once you are inside $Projectname there is no need for you to authenticate twice, even when accessing another $Projectname site. Zot is what sets $Projectname apart.
-
-
diff --git a/doc/member/bbcode.html b/doc/member/bbcode.html
index a4bc813d8..9b7080a32 100644
--- a/doc/member/bbcode.html
+++ b/doc/member/bbcode.html
@@ -26,6 +26,9 @@
<td><code>[color=red]red[/color]</code></td><td><span style="color: red;">red</span></td>
</tr>
<tr>
+ <td><code>[hl]highlighted[/hl]</code></td><td><span style="background-color: yellow;">highlighted</span></td>
+ </tr>
+ <tr>
<td><code>[font=courier]some text[/font] </code></td><td><span style="font-family: courier;">some text</span></td>
</tr>
<tr>
@@ -61,8 +64,10 @@ text</code></td><td>
</table>
<h3>Code blocks</h3>
-Code can be rendered generically in a block or inline format (depending on if there are new line characters in the text), or you can specify a supported language for enhanced syntax highlighting. Supported languages include <strong>php, css, mysql, sql, abap, diff, html, perl, ruby, vbscript, avrc, dtd, java, xml, cpp, python, javascript, js, json, sh </strong>.
+Code can be rendered generically in a block or inline format (depending on if there are new line characters in the text), or you can specify a supported language for enhanced syntax highlighting. Syntax highlighting requires a suitable rendering plugin such as <strong>hilite</strong>. Supported languages with the hilite plugin include <strong>php, css, mysql, sql, abap, diff, html, perl, ruby, vbscript, avrc, dtd, java, xml, cpp, python, javascript, js, json, sh </strong>.
<br><br>
+If a rendering plugin is not installed or an unsupported language is specified, the output for syntax highlighted code blocks is the same as the block format code tag.
+<br><br>
<table class="table table-responsive table-bordered">
<tbody>
<tr>
diff --git a/doc/member/member_guide.bb b/doc/member/member_guide.bb
index 6d95b230c..20d273f44 100644
--- a/doc/member/member_guide.bb
+++ b/doc/member/member_guide.bb
@@ -174,19 +174,40 @@ You can also delegate control of your channels' posts and connections, but not i
[h3]Connecting To Channels[/h3]
-Connections in $Projectname can take on a great many different meanings. But let's keep it simple, you want to be friends with somebody like you are familiar with from social networking. How do you do it?
+Connections in $Projectname can take on a great many different meanings. A connection is more accurately defined as a set of permissions that you have granted to somebody else. In traditional social network applications, all connections are granted the same permissions; or at most there two levels (friends and 'followers'). In $Projectname, a range of separate permissions may be set/adjusted depending on the siutation and relationship you have with the other channel. You can allow somebody to view your posts but not your photos. You can also deny them permission to comment on your posts or send private mail to you. But let's keep it simple, you want to be friends with somebody like you are familiar with from social networking. How do you do it?
First, you need to find some channels to connect to. There are two primary ways of doing this. Firstly, setting the &quot;Can send me their channel stream and posts&quot; permission to &quot;Anybody in this network&quot; will bring posts from complete strangers to your matrix. This will give you a lot of public content and should hopefully help you find interesting, entertaing people, forums, and channels.
-The next thing you can do is look at the Directory. The directory is available on every $Projectname website which means searching from your own site will bring in results from the entire network. You can search by name, interest, location and keyword. This is incomplete, so we'll improve this paragraph later.
+The next thing you can do is look at the Directory. The directory is available on every $Projectname website which means searching from your own site will bring in results from the entire network. You can search by name, interest, location, and keyword.
+
+If you already know somebody's 'webbie' you can connect with them directly. A webbie looks just like an email address (for instance bob@example.com) but refers to somebody in the open social web. In order to connect they must be using a compatible network protocol. By default, this software supports the 'zot' protocol, however additional protocols may be provided through plugins/addons. See below for more information on connecting to channels on other networks.
To connect with other $Projectname channels:
-Visit their profile by clicking their photograph in the directory, matrix, or comments, and it will open their channel home page in the channel viewer. At the left hand side of the screen, you will usually see a link called &quot;connect&quot;. Click it, and you're done. Depending on the settings of the channel you are connecting to, you may need to wait for them to approve your connection, but no further action is needed on your part. Once you've initiated the connection, you will be taken to the connection editor. This allows you to assign specific permissions for this channel. If you don't allow any permissions, communication will be very limited. There are some quick links which you can use to avoid setting individual permissions. To provide a social network environment, &quot;Full Sharing&quot; is recommended. You may review the settings that are applied with the quick links to ensure they are suitable for the channel you are connecting with and adjust if necessary. Then scroll to the bottom of the page and click &quot;Submit&quot;.
+Visit their profile by clicking their photograph in the directory, matrix, or comments, and it will open their channel home page in the channel viewer. At the left hand side of the screen, you will usually see a link called &quot;connect&quot;. Click it, and you're done. Depending on the settings of the channel you are connecting to, you may need to wait for them to approve your connection, but no further action is needed on your part. Once you've initiated the connection, you will be taken to the connection editor. This allows you to assign specific permissions for this channel if you wish to make any changes.
+
+You may also connect with any channel by visiting the &quot;Connections&quot; page of your site or the Directory and typing their &quot;webbie&quot; into the &quot;Add New Connection&quot; field. Use this method if somebody tells you their webbie and you wish to connect with them. The process is the same as connecting via the &quot;Connect&quot; button - you will then be taken to the connection editor to set permissions.
+
+To connect with channels on other networks:
+
+The process for connecting to channels on other networks (such as GNU-Social, Mastodon, and Diaspora) is similar - type their &quot;webbie&quot; into the &quot;Add New Connections&quot; box on the &quot;Connections&quot; page. Before you do this however, please visit your Settings page (Feature/Addon Settings) and ensure that the relevant protocol (Diaspora, GNU-Social/OStatus, or ActivityPub) is provided on your hub and [b][i]activated[/i] for your channel[/b]. These networks/protocols do not support account migration and location independence so if you move location or clone your channel elsewhere, communications with these connections may fail. For this reason these protocols are not activated by default, but only through your consent. Activating these protocols involves an important decision between communicating with friends on these networks or providing fail-safe account resilience if your server fails.
+
+Some communications offer more than one protocol. If you wish to connect with somebody on Mastodon (for instance) they can use either the 'ostatus' or the 'activitypub' protocol for communication. Generally the 'activitypub' protocol will provide a better experience than 'ostatus', but $Projectname will often choose the first protocol it discovers and this may not be the one you want. You may connect with somebody over a specific protocol by prepending the protocol name in square brackets to their &quot;webbie&quot;. For example
+
+[code]
+[activitypub]foobar@foo.bar
+[ostatus]foobar@foo.bar
+[diaspora]foobar@foo.bar
+[zot]foobar@foo.bar
+[rss]https://foo.bar/foobar
+[/code]
+
-You may also connect with any channel by visiting the &quot;Connections&quot; page of your site or the Directory and typing their &quot;webbie&quot; into the &quot;Add New Connection&quot; field. Use this method if somebody tells you their webbie and you wish to connect with them. A webbie looks like an email address; for example &quot;bob@example.com&quot;. The process is the same as connecting via the &quot;Connect&quot; button - you will then be taken to the connection editor to set permissions.
+To connect with RSS feeds:
-[h4] Block/Ignore/Archive/Hide channels [/h4]
+Your hub admin may allow connecting to RSS feeds. The process for connecting to an RSS feed is the same, exept type (or paste) the URL of the feed into the &quot;Add New Connection&quot; box. Feeds are only processed once or twice per day and your hub admin may impose limits on how many feeds you may add.
+
+[h4]Block/Ignore/Archive/Hide channels [/h4]
Channels in your address book can have statuses such as [i]blocked[/i], [i]ignored[/i], [i]archived[/i] and [i]hidden[/i]. From your connections page you can see tabs that display the channels with those statuses. From your edit connection pages you can change the statuses of a channel.
@@ -279,7 +300,7 @@ We highly recommend that you use the "typical social network" settings when you
[i]Note:[/i]
Plugins/addons may provide special permission settings, so you may be offered additional permission settings beyond what is described here.
-If you have set any of these permissions to &quot;only those I specifically allow&quot;, you may specify indivudal permissions on the connnection edit screen.
+If you have set any of these permissions to &quot;only those I specifically allow&quot;, you may specify individual permissions on the connnection edit screen.
[h4]Affinity[/h4]
@@ -294,8 +315,11 @@ To create and manage guest tokens, open the [zrl=[baseurl]/settings/tokens/]Gues
Additional permissions may be granted to the guest token by expanding the [b]Individual Permissions[/b] options and selecting privacy settings such as [b]Can view my channel stream and posts[/b] or [b]Can chat with me[/b].
+[url=[baseurl]/help/feature/access_tokens]More details can be found here...[/url]
+
[img][baseurl]/doc/member/assets/zat_dialog.png[/img]
+
[h3]Markup Languages[/h3]
$Projectname supports several markup languages for advanced formatting of content. The default markup language is a [url=[baseurl]/help/member/bbcode]custom variant of BBcode[/url], tailored for use in $Projectname. [url=[baseurl]/help/member/bbcode]BBcode[/url] is supported for posts, wiki pages, and web page elements. Wiki pages and webpage elements may also be written using standard Markdown.
[table border=0]
@@ -345,7 +369,7 @@ Topical tags are indicated by preceding the tag name with the # character. This
Topical tags are also not linked if they are purely numeric, e.g. #1. If you wish to use a numeric hashtag, please add some descriptive text such as #2012-elections.
[h4]Bookmarks[/h4]
-Bookmarks indicate a link which can be saved to your bookmark folder. They use the sequence #^ followed by the link. Often these are generatd automatically. If the 'bookmarker' addon is installed, this sequence will be converted to a bookmark icon when viewing the post or comment online and clicking the icon will save the bookmark. If the bookmarker addon is not installed, the post 'dropdown menu' contains a link for saving the bookmark or bookmarks.
+Bookmarks indicate a link which can be saved to your bookmark folder. They use the sequence #^ followed by the link. Often these are generated automatically. If the 'bookmarker' addon is installed, this sequence will be converted to a bookmark icon when viewing the post or comment online and clicking the icon will save the bookmark. If the bookmarker addon is not installed, the post 'dropdown menu' contains a link for saving the bookmark or bookmarks.
[h4]Spaces in Tags and Mentions[/h4]
Where possible please use the auto-complete window to select tag and mention recipients, because it will generate a coded tag which uniquely identifies one channel. Names are sometimes ambiguous. However, you can "manually" tag a channel by matching the channel name or address.
@@ -621,6 +645,15 @@ This will select the theme named &quot;suckerberg&quot; and select the &quot;pas
The condensed notation isn't part of Comanche itself but is recognised by $Projectname platform as a theme specifier.
+[h4]Navbar[/h4]
+
+[code]
+ [navbar]tucson[/navbar]
+[/code]
+
+Use the 'tucson' navbar template and CSS rules. By default the 'default' navbar template will be used.
+
+
[h4]Regions[/h4]
Each region has a name, as noted above. You will specify the region of interest using a 'region' tag, which includes the name. Any content you wish placed in this region should be placed between the opening region tag and the closing tag.
@@ -684,14 +717,8 @@ This places a block named &quot;contributors&quot; in this region. Additionally
The variable [var=wrap]none[/var] in a block removes the wrapping div element from the block.
[h4]Widgets[/h4]
-Widgets are executable apps provided by the system which you can place on your page. Some widgets take arguments which allows you to tailor the widget to your purpose. (TODO: list available widgets and arguments). The base system provides
-
-[code]
- profile - widget which duplicates the profile sidebar of your channel page. This widget takes no arguments
- tagcloud - provides a tag cloud of categories
- count - maximum number of category tags to list
+Widgets are executable apps provided by the system which you can place on your page. Some widgets take arguments which allows you to tailor the widget to your purpose. System widgets are listed [url=help/Widgets]here[/url]. Widgets can also ve created by plugins, themes, or your site administrator to provide additional functionality.
-[/code]
Widgets and arguments are specified with the 'widget' and 'var' tags.
[code]
@@ -813,23 +840,27 @@ To delete attachments or change the permissions on the stored files, visit [obse
[h4]Web Access[/h4]
-Your files are visible on the web at the location [observer=1][baseurl]/cloud/[observer.webname][/observer][observer=0][baseurl]/cloud/username[/observer] to anybody who is allowed to view them. If the viewer has sufficient privileges, they may also have the ability to create new files and folders/directories.
+Your files are visible on the web at the location [observer=1][baseurl]/cloud/[observer.webname][/observer][observer=0][baseurl]/cloud/username[/observer] to anybody who is allowed to view them. If the viewer has sufficient privileges, they may also have the ability to create new files and folders/directories. This should only be used for smaller files and photos (up to a few megabytes) as it uses internal memory. For larger files (videos, music, etc.), please upload using WebDAV. These files may still be retrieved via web access.
[h4]WebDAV access[/h4]
-See: [zrl=[baseurl]/help/member/member_guide#Cloud_Desktop_Clients]Cloud Desktop Clients[/zrl]
+WebDAV provides a way to copy files directly to or from your computer's operating system, where your cloud files appear as a virtual disk drive. This should be used to upload large files such as video and audio; as it is not limited to available memory. See [zrl=help/member/member_guide#Cloud_Desktop_Clients]Cloud Desktop Clients[/zrl] below.
+
[h4]Permissions[/h4]
When using WebDAV, the file is created with your channel's default file permissions and this cannot be changed from within the operating system. It also may not be as restrictive as you would like. What we've found is that the preferred method of making files private is to first create folders or directories; then visit [observer=1][baseurl]/cloud/[observer.webname][/observer][observer=0][baseurl]/cloud/username[/observer] select the directory and change the permissions. Do this before you put anything into the directory. The directory permissions take precedence so you can then put files or other folders into that container and they will be protected from unwanted viewers by the directory permissions. It is common for folks to create a &quot;personal&quot; or &quot;private&quot; folder which is restricted to themselves. You can use this as a personal cloud to store anything from anywhere on the web or any computer and it is protected from others. You might also create folders for &quot;family&quot; and &quot;friends&quot; with permission granted to appropriate privacy groups.
+[h3]Cloud Desktop Clients[/h3]
+
+
[h4]Cloud Desktop Clients - Windows[/h4]
WebDAV using Windows 7 graphical user interface wizard:
1. Left-click the Start-button to open the start menu.
2. Right-click the My computer icon to access its menu.
3. Left-click Map network drive... to open the connection dialog wizard.
-4. Type #^[url=https://example.net/dav/your_channel_name]https://example.net/dav/your_channel_name[/url] in the textbox and click the Complete button where &quot;example.net&quot; is the URL of your hub.
+4. Type '[baseurl]/dav/nickname' in the textbox (replace nickname with your channel nickname) and click the Complete button.
5. Type your $Projectname channel nickname. IMPORTANT - NO at-sign or domain name.
6. Type your $Projectname password
@@ -969,11 +1000,26 @@ Once open you can set a bookmark.
Note: There have been reported issues with clients that use "chunked transfer encoding", which includes Apple iOS services, and also the "AnyClient" and "CyberDuck" tools. These work fine for downloads, but uploads often end up with files of zero size. This is caused by an incorrect implemention of chunked encoding in some current FCGI (fast-cgi) implementations. Apache running with PHP as a module does not have these issues, but when running under FCGI you may need to use alternative clients or use the web uploader. At the time of this writing the issue has been open and no updates provided for at least a year. If you encounter zero size files with other clients, please check the client notes; as there are occasional configuration issues which can also produce these symptoms.
+[h3]Saved Searches[/h3]
+
+In order to quickly find information, the 'saved search' widget may be used. This widget may be presented as a sidebar tool on your network page and possibly from your channel page. It is differentiated from the 'navigation bar' search tool in that it does not search the entire site, but only the subset of information available to your channel.
+
+Additionally the search terms you provide may activate a one-time search or be saved in a list for re-use. Saving the search item also invokes the search in addition to adding it to the saved list (which is displayed below the search text entry box). Any item in the list may be discarded if it is no longer needed.
+
+The saved search widget will provide autocompletion of channels (the results are prefixed with '@'), and hashtags (prefixed with '#'). You do not need to enter these tags; although entering the desired tag will reduce the autocomplete results to only hold the relevant information. The behaviour maps as follows:
+
+[list]
+[*]@name - search your network stream for posts or comments written by 'name'. This will also change the post editor permissions to include only 'name'; as if this was a privacy group.
+[*]#hashtag - search you network stream for posts containing #hashtag.
+[*]text - search your network stream for posts containing 'text'.
+[/list]
+
+
[h3]Remove Channel or Account[/h3]
[h4]Remove Channel[/h4]
-Go to the bottom of your channel settings page or visit the URL:
+Select the 'Remove Channel' link on your channel settings page or visit the URL:
[baseurl]/removeme
@@ -985,7 +1031,7 @@ If you have identity clones on other hubs this only removes by default the chan
[h4]Remove Account[/h4]
-Go to the bottom of your account settings page or visit the URL:
+Select 'Remove Account' from your account settings page or visit the URL:
[baseurl]/removeaccount
@@ -994,3 +1040,4 @@ You will need to confirm your password and the account you are currently logged
[hl][i][b]This is irreversible.[/b][/i][/hl]
All your channels will be deleted. If you have identity clones on other hubs this only removes by default the channels instances which exists on this hub.
+
diff --git a/doc/members.bb b/doc/members.bb
deleted file mode 100644
index bf5b09898..000000000
--- a/doc/members.bb
+++ /dev/null
@@ -1,25 +0,0 @@
-[h2]Documentation for hub members[/h2]
-[h3]Getting started[/h3]
-[zrl=[baseurl]/help/registration]Account Registration[/zrl]
-[zrl=[baseurl]/help/accounts_profiles_channels_basics]You at $Projectname: accounts, profiles and channels in short[/zrl]
-[zrl=[baseurl]/help/profiles]Profiles[/zrl]
-[zrl=[baseurl]/help/channels]Channels[/zrl]
-[zrl=[baseurl]/help/roles]Permission roles and Channel types[/zrl]
-[zrl=[baseurl]/help/first-post]Your first posting[/zrl]
-[zrl=[baseurl]/help/connecting_to_channels]Connecting To Other Channels[/zrl]
-[zrl=[baseurl]/help/permissions]Permissions And Encryption: You Are In Control[/zrl]
-[zrl=[baseurl]/help/cloud]Cloud Storage[/zrl]
-[zrl=[baseurl]/help/remove_account]Remove Channel or Account[/zrl]
-[h3]Members help[/h3]
-[zrl=[baseurl]/help/tags_and_mentions]Tags and Mentions[/zrl]
-[zrl=[baseurl]/help/webpages]Web Pages[/zrl]
-[zrl=[baseurl]/help/bbcode]BBcode reference for posts and comments[/zrl]
-[zrl=[baseurl]/help/checking_account_quota_usage]Checking Account Quota Usage[/zrl]
-[zrl=[baseurl]/help/cloud_desktop_clients]Cloud Desktop Clients[/zrl]
-[zrl=[baseurl]/help/AdvancedSearch]Advanced Directory Search[/zrl]
-[zrl=[baseurl]/help/addons]Help With Addons[/zrl]
-[zrl=[baseurl]/help/diaspora_compat]Diaspora Communications Compatibility (Diaspora and Friendica)[/zrl]
-[zrl=[baseurl]/help/faq_members]FAQ For Members[/zrl]
-[zrl=[baseurl]/help/bugs]Bugs, Issues, and things that go bump in the night...[/zrl]
-
-#include doc/macros/main_footer.bb;
diff --git a/doc/profiles.bb b/doc/profiles.bb
deleted file mode 100644
index 513bf5fed..000000000
--- a/doc/profiles.bb
+++ /dev/null
@@ -1,37 +0,0 @@
-[b]Profiles[/b]
-
-$Projectname has unlimited profiles. You may use different profiles to show different &quot;sides of yourself&quot; to different audiences. This is different to having different channels. Different channels allow for completely different sets of information. You may have a channel for yourself, a channel for your sports team, a channel for your website, or whatever else. A profile allows for finely graded &quot;sides&quot; of each channel. For example, your default public profile might say &quot;Hello, I'm Fred, and I like laughing&quot;. You may show your close friends a profile that adds &quot;and I also enjoy dwarf tossing&quot;.
-
-You always have a profile known as your &quot;default&quot; or &quot;public&quot; profile. This profile is always available to the general public and cannot be hidden (there may be rare exceptions on privately run or disconnected sites). You may, and probably should restrict the information you make available on your public profile.
-
-That said, if you want other friends to be able to find you, it helps to have the following information in your public profile...
-
-[ul][*]Your real name or at least a nickname everybody knows
-[*]A photo of you
-[*]Your location on the planet, at least to a country level.[/ul]
-
-In addition, if you'd like to meet people that share some general interests with you, please take a moment and add some &quot;Keywords&quot; to your profile. Such as &quot;music, linux, photography&quot; or whatever. You can add as many keywords as you like.
-
-To create an alternate profile, first go to [zrl=[baseurl]/settings/features]Settings &gt; Additional Features[/zrl] and enable &quot;Multiple Profiles&quot; there, otherwise you won't have the ability to use more than just your default profile.
-
-Then select &quot;Edit Profiles&quot; from the menu of your $Projectname site. You may edit an existing profile, change the profile photo, add things to a profile or create a new profile. You may also create a &quot;clone&quot; of an existing profile if you only wish to change a few items but don't wish to enter all the information again. To do that, click on the profile you want to clone and choose &quot;Clone this profile&quot; there.
-
-In the list of your profiles, you can also choose the contacts who can see a specific profile. Just click on &quot;Edit visibility&quot; next to the profile in question (only available for the profiles that are not your default profile) and then click on user images to add them to or remove them from the group of people who can see this profile.
-
-Once a profile has been selected, when the person views your profile, they will see the private profile you have assigned. If they are not authenticated, they will see your public profile.
-
-There is a setting which allows you to publish your profile to a directory and ensure that it can be found by others. You can change this setting on the &quot;Settings&quot; page.
-
-If you do not wish to be found be people unless you give them your channel address, you may leave your profile unpublished.
-
-[b]Keywords and Directory Search[/b]
-
-On the directory page, you may search for people with published profiles. Currently, only the name field and the keywords are searched. You may also include such keywords in your default profile - which may be used to search for common interests with other members. Keywords are used in the channel suggestion tool and although they aren't visible in the directory, they are shown if people visit your profile page.
-
-On your Connnections page and in the directory there is a link to &quot;Suggestions&quot; or &quot;Channel Suggestions&quot;, respectively. This will find channels who have matching and/or similar keywords. The more keywords you provide, the more relevant the search results that are returned. These are sorted by relevance.
-
-See Also
-
-[zrl=[baseurl]/help/AdvancedSearch]Advanced Searching[/zrl]
-
-#include doc/macros/main_footer.bb;
diff --git a/doc/project/governance.bb b/doc/project/governance.bb
deleted file mode 100644
index 4c1538b4b..000000000
--- a/doc/project/governance.bb
+++ /dev/null
@@ -1,29 +0,0 @@
-[h2]$Projectname Governance[/h2]
-
-Governance relates to the management of a project and particularly how this relates to conflict resolution.
-
-[h3]Community Governance[/h3]
-
-The project is maintained and decisions made by the 'community'. The governance structure is still evolving. Until the structure is finalised, decisions are made in the following order:
-
-[ol]
-[*] Lazy Consensus
-
-If a project proposal is made to one of the community governance forums and there are no serious objections in a "reasonable" amount of time from date of proposal (we usually provide 2-3 days for all interested parties to weigh in), no vote needs to be taken and the proposal will be considered approved. Some concerns may be raised at this time, but if these are addressed during discussion and work-arounds provided, it will still be considered approved.
-
-[*] Veto
-
-Senior developers with a significant history of project commits may veto any decision. The decision may not proceed until the veto is removed or an alternative proposal is presented.
-
-[*] Community Vote
-
-A decision which does not have a clear mandate or clear consensus, but is not vetoed, can be taken to a community vote. At present this is a simple popular vote in one of the applicable community forums. At this time, popular vote decides the outcome. This may change in the future if the community adopts a 'council' governance model. This document will be updated at that time with the updated governance rules.
-[/ol]
-
-Community Voting does not always provide a pleasant outcome and can generate polarised factions in the community (hence the reason why other models are under consideration). If the proposal is 'down voted' there are still several things which can be done and the proposal re-submitted with slightly different parameters (convert to an addon, convert to an optional feature which is disabled by default, etc.). If interest in the feature is high and the vote is "close", it can generate lots of bad feelings amongst the losing voters. On such close votes, it is [b]strongly recommended[/b] that the proposer take steps to address any concerns that were raised and re-submit.
-
-
-
-
-
-
diff --git a/doc/project/toc.html b/doc/project/toc.html
deleted file mode 100644
index e264e014d..000000000
--- a/doc/project/toc.html
+++ /dev/null
@@ -1,5 +0,0 @@
-<h3>Project Information</h3>
-<ul>
-<li><a href="help/project/governance">Project Governance</a></li>
-<li><a href="help/project/versions">Versions and Versioning</a></li>
-</ul>
diff --git a/doc/project/versions.bb b/doc/project/versions.bb
deleted file mode 100644
index 451cd0448..000000000
--- a/doc/project/versions.bb
+++ /dev/null
@@ -1,30 +0,0 @@
-[h2]Versions and Releases[/h2]
-
-$Projectname currently uses a standard version numbering sequence of $x.$y(.$z), for instance '1.12' or '1.12.1'. The first digit is the major version number. Major versions are released "roughly" once per year; often in December.
-
-The second digit is the minor release number. If this number is odd, it is a development version. If the number is even, it is a released version. Minor versions are released (moved from dev to master) typically once per month when development is 'stable', but this is likely to increase. Going forward minor releases will be made somewhere between one and three months; corresponding to a stable code point and when there is general community consensus that the current code base is stable enough to consider a release.
-
-The final digit is an interface or patch designator.
-
-The release process involves changing the version number (by definition the minor version number will be odd, and the minor number will be incremented). Once a year for a major release the major version will be incremented, and the minor number reset to 0.
-
-The release candidate is moved to a new branch; and testing will commence/continue for a period of 1-2 weeks afterward or until any significant issues have been resolved. This branch is usually labelled with RC (release candidate); for instance 1.8RC represents the pending release of version 1.8. At this time, the minor version number on the dev branch is incremented to the next odd number. (For instance 1.9). New development can then take place in the dev branch.
-
-Bug fixes should always be applied to 'dev' and from there merged forward (typically with git cherry-pick) to the RC branch and if necessary applied to the master or official release branch.
-
-At the time a release candidate is produced, the language strings file is frozen until a release is made. Translation work may continue, but all translations should be submitted to 'dev' and merged forward to RC.
-
-
-Once RC testing is completed, RC is merged to 'master' and the RC version designator removed; resulting in one final checkin to change the version number. The CHANGELOG file should also be updated at or just prior to this time. If there are merge conflicts during this final merge, the merge will be abandoned; and 'git merge -s ours' applied. This results in a replacement of master with the contents of the RC branch. Conflicts often arise with string updates which were made to master after the last release and cannot easily be resolved without hand editing. Since this is a release of tested code, hand editing is discouraged, and the replacement merge strategy should be used instead. It is assumed that RC now contains the most recent well-tested code.
-
-Once the release is live and merged to master, the RC branch may be removed.
-
-Fixes may be made to master after release. Where possible these should be made to dev and 'git cherry-pick' used to merge forward; which preserves the commit info and prevents merge conflicts in the next cycle. Only rarely does a patch only apply to the master branch. If necessary this can be made. If the change is severe, the interface version number should be incremented. This is at the discretion of the community. In any event, a 'git pull' of the master branch should always result in the latest release with any post-release patches applied.
-
-The interface number (the $z in $x.$y.$z) should be incremented in dev whenever a change is made which changes the interfaces or API in incompatible ways so that any external packages (especially addons and API clients) relying on a the current behaviour can discover and change their own interfaces accordingly at the point that it changed.
-
-
-
-
-
- \ No newline at end of file
diff --git a/doc/server_roles.bb b/doc/server_roles.bb
deleted file mode 100644
index ef6ec28ae..000000000
--- a/doc/server_roles.bb
+++ /dev/null
@@ -1,27 +0,0 @@
-[h2]Server Roles[/h2]
-
-$Projectname can be configured in many different ways. One of the configurations available at installation is to select a 'server role'. There are currently three server roles. We highly recommend that you use 'standard' unless you have special needs.
-
-
-[h3]Basic[/h3]
-
-The 'basic' server role is designed to be relatively simple, and it doesn't present options or complicated features. The hub admin may configure additional features at a site level. This role is designed for simple social networking and social network federation. Many features which do not federate easily have been removed, including (and this is somewhat important) "nomadic identity". You may move a channel to or from a basic server, but you may not clone it. Once moved, it becomes read-only on the origination site. No updates of any kind will be provided. It is recommended that after the move, the original channel be deleted - as it is no longer useable. The data remains only in case there are issues making a copy of the data.
-
-This role is supported by the hubzilla community.
-
-[h3]Standard[/h3]
-
-
-The 'standard' server role is recommended for most sites. All features of the software are available to everybody unless locked by the hub administrator. Some features will not federate easily with other networks, so there is often an increased support burden explaining why sharing events with Diaspora (for instance) presents a different experience on that network. Additionally any member can enable "advanced" or "expert" features, and these may be beyond their technical skill level. This may also result in an increased support burden.
-
-This role is supported by the hubzilla community.
-
-[h3]Pro[/h3]
-
-The 'pro' server role is primarily designed for communities which want to present a uniform experience and be relieved of many federation support issues. In this role there is [b]no federation with other networks[/b]. Additional features [b]may[/b] be provided, such as channel ratings, premium channels, and e-commerce.
-
-By default a channel may set a "techlevel" appropriate to their technical skill. Higher levels provide more features. Everybody starts with techlevel 0 (similar to the 'basic' role) where all complicated features are hidden from view. Increasing the techlevel provides more advanced or complex features.
-
-The hub admin may also lock individual channels or their entire site at a defined techlevel which provides an installation with a selection of advanced features consistent with the perceived technical skills of the members. For instance, a community for horse racing might have a different techlevel than a community for Linux kernel developers.
-
-This role is not supported by the hubzilla community. \ No newline at end of file
diff --git a/doc/service_classes.bb b/doc/service_classes.bb
deleted file mode 100644
index 4dead5d29..000000000
--- a/doc/service_classes.bb
+++ /dev/null
@@ -1,38 +0,0 @@
-[b]Service Classes[/b]
-
-Service classes allow you to set limits on system resources. A GUI to configure this is currently under development.
-
-As a temporary measure, the following commandline utilities can be used:
-
-Usage:
-
-[code]util/service_class[/code]
-list service classes
-
-[code]util/config system default_service_class firstclass[/code]
-set the default service class to 'firstclass'
-
-[code]util/service_class firstclass[/code]
-list the services that are part of 'firstclass' service class
-
-[code]util/service_class firstclass photo_upload_limit 10000000[/code]
-set firstclass total photo disk usage to 10 million bytes
-
-[code]util/service_class --account=5 firstclass[/code]
-set account id 5 to service class 'firstclass' (with confirmation)
-
-[code]util/service_class --channel=blogchan firstclass[/code]
-set the account that owns channel 'blogchan' to service class 'firstclass' (with confirmation)
-
-[b]current limits[/b]
-photo_upload_limit - maximum total bytes for photos
-total_items - maximum total toplevel posts
-total_pages - maximum comanche pages
-total_identities - maximum number of channels owned by account
-total_channels - maximum number of connections
-total_feeds - maximum number of rss feed connections
-attach_upload_limit - maximum file upload storage (bytes)
-minimum_feedcheck_minutes - lowest setting allowed for polling rss feeds
-chatrooms - maximum chatrooms
-chatters_inroom - maximum chatters per room
-access_tokens - maximum number of Guest Access Tokens per channel \ No newline at end of file
diff --git a/doc/theme_management.bb b/doc/theme_management.bb
deleted file mode 100644
index 5691f7c48..000000000
--- a/doc/theme_management.bb
+++ /dev/null
@@ -1,10 +0,0 @@
-[h1]Theme Management[/h1]
-$Projectname allows hub admins to easily add and update themes hosted in common git repositories.
-[h2]Add new theme repo to your hub[/h2]
-1. Navigate to your hub web root
-[code]root@hub:~# cd /var/www[/code]
-2. Add the theme repo and give it a name
-[code][nobb]root@hub:/var/www# util/add_theme_repo https://github.com/username/theme-repo.git UniqueThemeRepoName[/nobb][/code]
-[h2]Update existing theme repo[/h2]
-Update the repo by using
-[code]root@hub:/var/www# util/update_theme_repo UniqueThemeRepoName[/code]
diff --git a/doc/to_do_code.bb b/doc/to_do_code.bb
deleted file mode 100644
index b1c4923b1..000000000
--- a/doc/to_do_code.bb
+++ /dev/null
@@ -1,42 +0,0 @@
-[b]Project Code To-Do List[/b]
-
-We need much more than this, but here are areas where developers can help. Please edit this page when items are finished. Another place for developers to start is with the issues list.
-
-[li]Documentation - see Red Documentation Project To-Do List[/li]
-[li]Include TOS link in registration/verification email[/li]
-[li]Auto preview posts/comments (configurable timer kicks in the preview if not 0)[/li]
-[li]SAML 2.0 and OpenID Connect provider functionality[/li]
-[li]relmeauth (aka indieauth) support[/li]
-[li]Create bug tracker module[/li]
-[li]Filing posts - provide a dropdown menu integrated with the 'post actions menu'[/li]
-[li]translation plugins - moses or apertium[/li]
-[li]plugins - provide 'disable' which is softer than 'uninstall' for those plugins which create additional DB tables[/li]
-[li]Infinite scroll improvements (i.e. embedded page links) see http://scrollsample.appspot.com/items [/li]
-[li]Finish the anti-spam bayesian engine[/li]
-[li]implement an email permission denied bounce message from the sys channel[/li]
-[li]provide a way for xchans with a certain network type to upgrade (unknown to rss, rss to statusnet, friendica-over-diaspora to friendica, for instance) based on new knowledge and/or redmatrix ability[/li]
-[li]Integrate the &quot;open site&quot; list with the register page[/li]
-[li]Support comments and member notes on documentation pages (to achieve an effect similar to php.net)[/li]
-[li]Support comments on webpages[/li]
-[li]Write more webpage layouts[/li]
-[li]Write more webpage widgets[/li]
-[li]restricted access OAuth clients[/li]
-[li](Advanced) create a UI for building Comanche pages[/li]
-[li](less advanced) create a way to preview Comanche results on a preview page while editing on another page[/li]
-[li]External post connectors - create standard interface[/li]
-[li]External post connectors, add popular services[/li]
-[li]service classes - provide a pluggable subscription payment gateway for premium accounts[/li]
-[li]service classes - account overview page showing resources consumed by channel. With special consideration this page can also be accessed at a meta level by the site admin to drill down on problematic accounts/channels.[/li]
-[li]Uploads - integrate #^[url=https://github.com/blueimp/jQuery-File-Upload]https://github.com/blueimp/jQuery-File-Upload[/url][/li]
-[li]API extensions, for Twitter API - search, friending, threading. For Red API, lots of stuff[/li]
-[li]Import channel from Diaspora/Friendica (Diaspora partially done)[/li]
-[li]MediaGoblin photo "crosspost" connector[/li]
-[li]provide a visual editor[/li]
-[li]Create mobile clients for the top platforms - which involves extending the API so that we can do stuff far beyond the current crop of Twitter/Statusnet clients. Ditto for mobile themes. We can probably use something like the Friendica Android app as a base to start from.[/li]
-[li]Implement owned and exchangeable &quot;things&quot;.[/li]
-[li]Family Account creation - using service classes (an account holder can create a certain number of sub-accounts which are all tied to their subscription - if the subscription lapses they all go away).[/li]
-
-
-In many cases some of the work has already been started and code exists so that you needn't start from scratch. Please contact one of the developer channels like Channel One (one@zothub.com) before embarking and we can tell you what we already have and provide some insights on how we envision these features fitting together.
-
-Return to the [url=[baseurl]/help/main]Main documentation page[/url]
diff --git a/doc/to_do_doco.md b/doc/to_do_doco.md
deleted file mode 100644
index 018b9efa2..000000000
--- a/doc/to_do_doco.md
+++ /dev/null
@@ -1,31 +0,0 @@
-# Documentation To-Do List #
-
-## How to contribute documentation ##
-
-Documentation files are in */doc*.
-
-When help is first accessed, the file loaded is *main.bb*. That file contains case sensitive links without an extension. The extensions is added automatically if the file is found, first *.md* then *.bb*.
-
-For translating documentation, create a directory in */doc* named by the language code, copy the files and translate the content.
-
-## Documentation we need to write ##
-
-* Database schema detailed descriptions
-
-* Complete plugin hook documentation
-
-* API documentation
-
-* Function and code documentation (doxygen)
-
-* New Member guide
-
-* &quot;Extra Feature&quot; reference, description of each
-
-* Detailed Personal Settings Documentation
-
-* Administration Guide (post-install)
-
-* Administration Guide (pre-install)
-
-#include doc/macros/main_footer.bb;
diff --git a/doc/toc.html b/doc/toc.html
index 851f356e6..1b7de3cb3 100644
--- a/doc/toc.html
+++ b/doc/toc.html
@@ -1,30 +1,31 @@
<div class="" id="accordion">
- <div class="panel">
+ <div class="">
<div class="">
<h3 class="panel-title">
About
</h3>
</div>
- <div id="about" class="panel-collapse collapse in">
- <ul class="list-group">
- <li class="doco-list-group-item"><a href="/help/about/about_hubzilla">About Hubzilla</a></li>
- <li class="doco-list-group-item"><a href="/help/about/hubzilla_project">Hubzilla project</a></li>
- <li class="doco-list-group-item"><a href="/help/about/about_hub">About this hub</a></li>
- </ul>
+ <div id="about" class="doco-section">
+ <div class="flex-column">
+ <a class="nav-link" href="/help/about/about">About</a>
+ <a class="nav-link" href="/help/about/project">Project</a>
+ <a class="nav-link" href="/help/about/about_hub">About this hub</a>
+ </div>
</div>
</div>
- <div class="panel">
+ <div class="">
<div class="">
<h3 class="panel-title">
Members
</h3>
</div>
- <div id="members" class="panel-collapse collapse in">
- <ul class="list-group">
- <li class="doco-list-group-item"><a href="/help/member/member_guide">Guide</a></li>
- <li class="doco-list-group-item"><a href="/help/member/bbcode">BBcode Reference</a></li>
- <li class="doco-list-group-item"><a href="/help/member/member_faq">FAQ</a></li>
- </ul>
+ <div id="members" class="doco-section">
+ <div class="flex-column">
+ <a class="nav-link" href="/help/member/member_guide">Guide</a>
+ <a class="nav-link" href="/help/member/bbcode">BBcode Reference</a>
+ <a class="nav-link" href="/help/bugs">Reporting Bugs</a>
+ <a class="nav-link" href="/help/member/member_faq">FAQ</a>
+ </div>
</div>
</div>
<div class="panel">
@@ -33,11 +34,12 @@
Administrators
</h3>
</div>
- <div id="administrators" class="panel-collapse collapse in">
- <ul class="list-group">
- <li class="doco-list-group-item"><a href="/help/admin/administrator_guide">Guide</a></li>
- <li class="doco-list-group-item"><a href="/help/admin/hub_snapshots">Hub Snapshots</a></li>
- </ul>
+ <div id="administrators" class="doco-section">
+ <div class="flex-column">
+ <a class="nav-link" href="/help/admin/administrator_guide">Guide</a>
+ <a class="nav-link" href="/help/admin/hub_snapshots">Hub Snapshots</a>
+ <a class="nav-link" href="/help/database">Database Tables</a>
+ </div>
</div>
</div>
<div class="panel">
@@ -46,12 +48,14 @@
Developers
</h3>
</div>
- <div id="developers" class="panel-collapse collapse in">
- <ul class="list-group">
- <li class="doco-list-group-item"><a href="/help/developer/developer_guide">Guide</a></li>
- <li class="doco-list-group-item"><a href="/help/developer/zot_protocol">Zot Protocol</a></li>
- <li class="doco-list-group-item"><a href="/help/developer/api_zot">Zot API</a></li>
- </ul>
+ <div id="developers" class="doco-section">
+ <div class="flex-column">
+ <a class="nav-link" href="/help/developer/developer_guide">Guide</a>
+ <a class="nav-link" href="/help/developer/covenant">Code of Conduct</a>
+ <a class="nav-link" href="/help/developer/zot_protocol">Zot Protocol</a>
+ <a class="nav-link" href="/help/developer/api_zot">Zot API</a>
+ <a class="nav-link" href="/help/hooklist">Hooks</a>
+ </div>
</div>
</div>
<div class="panel">
@@ -60,71 +64,10 @@
Tutorials
</h3>
</div>
- <div id="tutorials" class="panel-collapse collapse in">
- <ul class="list-group">
- <li class="doco-list-group-item"><a href="/help/tutorials/personal_channel">Personal Channel</a></li>
- </ul>
+ <div id="tutorials" class="doco-section">
+ <div class="flex-column">
+ <a class="nav-link" href="/help/tutorials/personal_channel">Personal Channel</a>
+ </div>
</div>
</div>
</div>
-<script>
- toc = {};
- // Generate the table of contents in the side nav menu (see view/tpl/help.tpl)
- $(document).ready(function () {
- $(".panel-collapse.in").find('a').each(function(){
- var url = document.createElement('a');
- url.href = window.location;
- var pageName = url.href.split('/').pop().split('#').shift().split('?').shift();
- var linkName = $(this).attr('href').split('/').pop();
- if(pageName === linkName) {
- var tocUl = $(this).closest('li').append('<ul>').find('ul');
- tocUl.removeClass(); // Classes are automatically added to <ul> elements by something else
- tocUl.toc({content: "#doco-content", headings: "h3"});
- tocUl.addClass('toc-content sub-menu');
- tocUl.attr('id', 'doco-side-toc');
-
- }
- });
-
- $(document.body).trigger("sticky_kit:recalc");
-
- toc.contentTop = [];
- toc.edgeMargin = 20; // margin above the top or margin from the end of the page
- toc.topRange = 200; // measure from the top of the viewport to X pixels down
- // Set up content an array of locations
- $('#doco-side-toc').find('a').each(function(){
- toc.contentTop.push( $( '#'+$(this).attr('href').split('#').pop() ).offset().top );
- });
-
-
- // adjust side menu
- $(window).scroll(function(){
- var winTop = $(window).scrollTop(),
- bodyHt = $(document).height(),
- vpHt = $(window).height() + toc.edgeMargin; // viewport height + margin
- $.each( toc.contentTop, function(i,loc){
- if ( ( loc > winTop - toc.edgeMargin && ( loc < winTop + toc.topRange || ( winTop + vpHt ) >= bodyHt ) ) ){
- $('#doco-side-toc li')
- .removeClass('selected-doco-nav')
- .eq(i).addClass('selected-doco-nav');
- if (typeof($('#doco-side-toc li').eq(i).find('a').attr('href').split('#')[1]) !== 'undefined') {
- window.history.pushState({}, '', location.href.split('#')[0] + '#' + $('#doco-side-toc li').eq(i).find('a').attr('href').split('#')[1]);
- }
- }
- });
- });
-
- // When the page loads, it does not scroll to the section specified in the URL because it
- // has not been constructed yet by the script. This will reload the URL
- if (typeof(location.href.split('#')[1]) !== 'undefined') {
- var p = document.createElement('a');
- p.href = location.href;
- var portstr = '';
- if(p.port !== '') {
- portstr = ':'+ p.port;
- }
- var newref = p.protocol + '//'+ p.hostname + portstr + p.pathname + p.hash.split('?').shift();
- location.replace(newref)
- }
- });
-</script>
diff --git a/doc/tutorials/personal_channel.html b/doc/tutorials/personal_channel.html
index f2ad87077..9dbc2aaec 100644
--- a/doc/tutorials/personal_channel.html
+++ b/doc/tutorials/personal_channel.html
@@ -6,7 +6,7 @@ to a personal channel in a natural way.</p>
<h3 id="Create_a_new_channel">Create a new channel</h3>
<p>When you log in for the first time after registering, you must create a channel.
-(Alternatively you can load https://grid.reticu.li/new_channel)</p>
+(Alternatively you can visit https://your_website/new_channel)</p>
<p><img class="img-responsive" src="/help/tutorials/assets/c9a880cc82ffa1f7c2f460397bb083bf7dc2a2b8f065e64da598b45b4a2b.png" alt="image"></p>
@@ -76,7 +76,7 @@ so you can specify exactly who can access this post.</p>
<h3 id="Use_an_uploaded_image_as_a_channel_cover_photo">Use an uploaded image as a channel cover photo</h3>
<p>One way to add some pizzazz your channel is to add a cover photo that visitors will
-see when they load your channel page. Hubzilla's integrated cloud file system
+see when they load your channel page. The integrated cloud file system
allows you to choose an existing photo for this purpose.</p>
<p>Visit your photos in the <strong>Photos</strong> app</p>
@@ -99,9 +99,9 @@ channel page will fade in as you scroll down.</p>
<h3 id="Make_a_connection">Make a connection</h3>
-<p>Making connections between channels to share things is what Hubzilla is all about.
+<p>Making connections between channels to share things is what social communications are all about.
Making a connection is simple. If you do not already know how to reach a channel's home
-page, you might try a directory search by opening the <strong>Directory</strong> link on the right
+page, you might try a directory search by opening the <strong>Directory</strong> link from the menu on the right
side of the top navbar.</p>
<p><img class="img-responsive" src="/help/tutorials/assets/ef78bc6aa3fafebd46f353514c907b3fdfe019918fc5553bb3f31388a36f.png" alt="image"></p>
@@ -160,4 +160,4 @@ editor by pressing the edit button beside the <strong>Delete</strong> button.</p
<p><img class="img-responsive" src="/help/tutorials/assets/c4cad3e4c356dd2a227df79bd4dc6d47edf1b66ea243f005b6b452ec366b.png" alt="image"></p>
- \ No newline at end of file
+
diff --git a/images/emoji/0023-20e3.png b/images/emoji/0023-20e3.png
deleted file mode 100644
index 6e26f0070..000000000
--- a/images/emoji/0023-20e3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/0023.png b/images/emoji/0023.png
deleted file mode 100644
index 811f22af8..000000000
--- a/images/emoji/0023.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/002a-20e3.png b/images/emoji/002a-20e3.png
deleted file mode 100644
index 2f8e51138..000000000
--- a/images/emoji/002a-20e3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/002a.png b/images/emoji/002a.png
deleted file mode 100644
index c39443e24..000000000
--- a/images/emoji/002a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/0030-20e3.png b/images/emoji/0030-20e3.png
deleted file mode 100644
index 13aca83e0..000000000
--- a/images/emoji/0030-20e3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/0030.png b/images/emoji/0030.png
deleted file mode 100644
index e730b28df..000000000
--- a/images/emoji/0030.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/0031-20e3.png b/images/emoji/0031-20e3.png
deleted file mode 100644
index e6d84b801..000000000
--- a/images/emoji/0031-20e3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/0031.png b/images/emoji/0031.png
deleted file mode 100644
index 9c4cbd6f7..000000000
--- a/images/emoji/0031.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/0032-20e3.png b/images/emoji/0032-20e3.png
deleted file mode 100644
index 927339c9b..000000000
--- a/images/emoji/0032-20e3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/0032.png b/images/emoji/0032.png
deleted file mode 100644
index 9a0b49a0e..000000000
--- a/images/emoji/0032.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/0033-20e3.png b/images/emoji/0033-20e3.png
deleted file mode 100644
index dbaa6183e..000000000
--- a/images/emoji/0033-20e3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/0033.png b/images/emoji/0033.png
deleted file mode 100644
index bc898b986..000000000
--- a/images/emoji/0033.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/0034-20e3.png b/images/emoji/0034-20e3.png
deleted file mode 100644
index b0e914aac..000000000
--- a/images/emoji/0034-20e3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/0034.png b/images/emoji/0034.png
deleted file mode 100644
index 7216ee32b..000000000
--- a/images/emoji/0034.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/0035-20e3.png b/images/emoji/0035-20e3.png
deleted file mode 100644
index d14371f3f..000000000
--- a/images/emoji/0035-20e3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/0035.png b/images/emoji/0035.png
deleted file mode 100644
index c64709a7e..000000000
--- a/images/emoji/0035.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/0036-20e3.png b/images/emoji/0036-20e3.png
deleted file mode 100644
index 371b3acef..000000000
--- a/images/emoji/0036-20e3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/0036.png b/images/emoji/0036.png
deleted file mode 100644
index 68e1e71e4..000000000
--- a/images/emoji/0036.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/0037-20e3.png b/images/emoji/0037-20e3.png
deleted file mode 100644
index 9b3476ae7..000000000
--- a/images/emoji/0037-20e3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/0037.png b/images/emoji/0037.png
deleted file mode 100644
index e4aa065c6..000000000
--- a/images/emoji/0037.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/0038-20e3.png b/images/emoji/0038-20e3.png
deleted file mode 100644
index 8c95874d4..000000000
--- a/images/emoji/0038-20e3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/0038.png b/images/emoji/0038.png
deleted file mode 100644
index 27eae28e6..000000000
--- a/images/emoji/0038.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/0039-20e3.png b/images/emoji/0039-20e3.png
deleted file mode 100644
index 9fce3d1ec..000000000
--- a/images/emoji/0039-20e3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/0039.png b/images/emoji/0039.png
deleted file mode 100644
index fd9e98055..000000000
--- a/images/emoji/0039.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/00a9.png b/images/emoji/00a9.png
deleted file mode 100644
index 6b9a6adbf..000000000
--- a/images/emoji/00a9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/00ae.png b/images/emoji/00ae.png
deleted file mode 100644
index 53ef9f2d4..000000000
--- a/images/emoji/00ae.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f004.png b/images/emoji/1f004.png
deleted file mode 100644
index 66fd32025..000000000
--- a/images/emoji/1f004.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f0cf.png b/images/emoji/1f0cf.png
deleted file mode 100644
index 3d0924b68..000000000
--- a/images/emoji/1f0cf.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f170.png b/images/emoji/1f170.png
deleted file mode 100644
index 8603ff05a..000000000
--- a/images/emoji/1f170.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f171.png b/images/emoji/1f171.png
deleted file mode 100644
index 25875bc6a..000000000
--- a/images/emoji/1f171.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f17e.png b/images/emoji/1f17e.png
deleted file mode 100644
index 73278ba19..000000000
--- a/images/emoji/1f17e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f17f.png b/images/emoji/1f17f.png
deleted file mode 100644
index 7be7dac27..000000000
--- a/images/emoji/1f17f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f18e.png b/images/emoji/1f18e.png
deleted file mode 100644
index d9f2d17de..000000000
--- a/images/emoji/1f18e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f191.png b/images/emoji/1f191.png
deleted file mode 100644
index 8b01b4343..000000000
--- a/images/emoji/1f191.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f192.png b/images/emoji/1f192.png
deleted file mode 100644
index 74674978d..000000000
--- a/images/emoji/1f192.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f193.png b/images/emoji/1f193.png
deleted file mode 100644
index b71956eb4..000000000
--- a/images/emoji/1f193.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f194.png b/images/emoji/1f194.png
deleted file mode 100644
index 5bf69bf7b..000000000
--- a/images/emoji/1f194.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f195.png b/images/emoji/1f195.png
deleted file mode 100644
index b4f85488d..000000000
--- a/images/emoji/1f195.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f196.png b/images/emoji/1f196.png
deleted file mode 100644
index ee8d20f5e..000000000
--- a/images/emoji/1f196.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f197.png b/images/emoji/1f197.png
deleted file mode 100644
index d0d775532..000000000
--- a/images/emoji/1f197.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f198.png b/images/emoji/1f198.png
deleted file mode 100644
index d7d8c9953..000000000
--- a/images/emoji/1f198.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f199.png b/images/emoji/1f199.png
deleted file mode 100644
index 0d42142ba..000000000
--- a/images/emoji/1f199.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f19a.png b/images/emoji/1f19a.png
deleted file mode 100644
index e1180f4a4..000000000
--- a/images/emoji/1f19a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e6-1f1e8.png b/images/emoji/1f1e6-1f1e8.png
deleted file mode 100644
index b939efeab..000000000
--- a/images/emoji/1f1e6-1f1e8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e6-1f1e9.png b/images/emoji/1f1e6-1f1e9.png
deleted file mode 100644
index 20f4b14e8..000000000
--- a/images/emoji/1f1e6-1f1e9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e6-1f1ea.png b/images/emoji/1f1e6-1f1ea.png
deleted file mode 100644
index d16ffe4b8..000000000
--- a/images/emoji/1f1e6-1f1ea.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e6-1f1eb.png b/images/emoji/1f1e6-1f1eb.png
deleted file mode 100644
index a51533b55..000000000
--- a/images/emoji/1f1e6-1f1eb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e6-1f1ec.png b/images/emoji/1f1e6-1f1ec.png
deleted file mode 100644
index 07f2ce397..000000000
--- a/images/emoji/1f1e6-1f1ec.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e6-1f1ee.png b/images/emoji/1f1e6-1f1ee.png
deleted file mode 100644
index 500b5ab09..000000000
--- a/images/emoji/1f1e6-1f1ee.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e6-1f1f1.png b/images/emoji/1f1e6-1f1f1.png
deleted file mode 100644
index 03a20132c..000000000
--- a/images/emoji/1f1e6-1f1f1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e6-1f1f2.png b/images/emoji/1f1e6-1f1f2.png
deleted file mode 100644
index 2ad60a273..000000000
--- a/images/emoji/1f1e6-1f1f2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e6-1f1f4.png b/images/emoji/1f1e6-1f1f4.png
deleted file mode 100644
index cb46c31f8..000000000
--- a/images/emoji/1f1e6-1f1f4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e6-1f1f6.png b/images/emoji/1f1e6-1f1f6.png
deleted file mode 100644
index b272021d3..000000000
--- a/images/emoji/1f1e6-1f1f6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e6-1f1f7.png b/images/emoji/1f1e6-1f1f7.png
deleted file mode 100644
index 73136caf3..000000000
--- a/images/emoji/1f1e6-1f1f7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e6-1f1f8.png b/images/emoji/1f1e6-1f1f8.png
deleted file mode 100644
index 3db45a0d9..000000000
--- a/images/emoji/1f1e6-1f1f8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e6-1f1f9.png b/images/emoji/1f1e6-1f1f9.png
deleted file mode 100644
index c43769dcb..000000000
--- a/images/emoji/1f1e6-1f1f9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e6-1f1fa.png b/images/emoji/1f1e6-1f1fa.png
deleted file mode 100644
index 7794309c7..000000000
--- a/images/emoji/1f1e6-1f1fa.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e6-1f1fc.png b/images/emoji/1f1e6-1f1fc.png
deleted file mode 100644
index 02c840d12..000000000
--- a/images/emoji/1f1e6-1f1fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e6-1f1fd.png b/images/emoji/1f1e6-1f1fd.png
deleted file mode 100644
index fc5466174..000000000
--- a/images/emoji/1f1e6-1f1fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e6-1f1ff.png b/images/emoji/1f1e6-1f1ff.png
deleted file mode 100644
index 89d3d15fd..000000000
--- a/images/emoji/1f1e6-1f1ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e7-1f1e6.png b/images/emoji/1f1e7-1f1e6.png
deleted file mode 100644
index 25fe407e1..000000000
--- a/images/emoji/1f1e7-1f1e6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e7-1f1e7.png b/images/emoji/1f1e7-1f1e7.png
deleted file mode 100644
index bccd8c5c9..000000000
--- a/images/emoji/1f1e7-1f1e7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e7-1f1e9.png b/images/emoji/1f1e7-1f1e9.png
deleted file mode 100644
index b0597a314..000000000
--- a/images/emoji/1f1e7-1f1e9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e7-1f1ea.png b/images/emoji/1f1e7-1f1ea.png
deleted file mode 100644
index 551f086e3..000000000
--- a/images/emoji/1f1e7-1f1ea.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e7-1f1eb.png b/images/emoji/1f1e7-1f1eb.png
deleted file mode 100644
index 444d4829f..000000000
--- a/images/emoji/1f1e7-1f1eb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e7-1f1ec.png b/images/emoji/1f1e7-1f1ec.png
deleted file mode 100644
index 821eee5e1..000000000
--- a/images/emoji/1f1e7-1f1ec.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e7-1f1ed.png b/images/emoji/1f1e7-1f1ed.png
deleted file mode 100644
index f33724249..000000000
--- a/images/emoji/1f1e7-1f1ed.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e7-1f1ee.png b/images/emoji/1f1e7-1f1ee.png
deleted file mode 100644
index ea20ac932..000000000
--- a/images/emoji/1f1e7-1f1ee.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e7-1f1ef.png b/images/emoji/1f1e7-1f1ef.png
deleted file mode 100644
index 7cca4f804..000000000
--- a/images/emoji/1f1e7-1f1ef.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e7-1f1f1.png b/images/emoji/1f1e7-1f1f1.png
deleted file mode 100644
index 0316ac99d..000000000
--- a/images/emoji/1f1e7-1f1f1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e7-1f1f2.png b/images/emoji/1f1e7-1f1f2.png
deleted file mode 100644
index ab8cafdac..000000000
--- a/images/emoji/1f1e7-1f1f2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e7-1f1f3.png b/images/emoji/1f1e7-1f1f3.png
deleted file mode 100644
index 16a58f8f6..000000000
--- a/images/emoji/1f1e7-1f1f3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e7-1f1f4.png b/images/emoji/1f1e7-1f1f4.png
deleted file mode 100644
index 98af62b3d..000000000
--- a/images/emoji/1f1e7-1f1f4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e7-1f1f6.png b/images/emoji/1f1e7-1f1f6.png
deleted file mode 100644
index cb978ef9d..000000000
--- a/images/emoji/1f1e7-1f1f6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e7-1f1f7.png b/images/emoji/1f1e7-1f1f7.png
deleted file mode 100644
index b139366a4..000000000
--- a/images/emoji/1f1e7-1f1f7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e7-1f1f8.png b/images/emoji/1f1e7-1f1f8.png
deleted file mode 100644
index d36bcd2fb..000000000
--- a/images/emoji/1f1e7-1f1f8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e7-1f1f9.png b/images/emoji/1f1e7-1f1f9.png
deleted file mode 100644
index b571dce1a..000000000
--- a/images/emoji/1f1e7-1f1f9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e7-1f1fb.png b/images/emoji/1f1e7-1f1fb.png
deleted file mode 100644
index 5884e6482..000000000
--- a/images/emoji/1f1e7-1f1fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e7-1f1fc.png b/images/emoji/1f1e7-1f1fc.png
deleted file mode 100644
index cb12f3473..000000000
--- a/images/emoji/1f1e7-1f1fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e7-1f1fe.png b/images/emoji/1f1e7-1f1fe.png
deleted file mode 100644
index 859c05beb..000000000
--- a/images/emoji/1f1e7-1f1fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e7-1f1ff.png b/images/emoji/1f1e7-1f1ff.png
deleted file mode 100644
index db2c28bd7..000000000
--- a/images/emoji/1f1e7-1f1ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e7.png b/images/emoji/1f1e7.png
deleted file mode 100644
index 8f69fa973..000000000
--- a/images/emoji/1f1e7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e8-1f1e6.png b/images/emoji/1f1e8-1f1e6.png
deleted file mode 100644
index 7c5b390e8..000000000
--- a/images/emoji/1f1e8-1f1e6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e8-1f1e8.png b/images/emoji/1f1e8-1f1e8.png
deleted file mode 100644
index b6555a23d..000000000
--- a/images/emoji/1f1e8-1f1e8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e8-1f1e9.png b/images/emoji/1f1e8-1f1e9.png
deleted file mode 100644
index fa9200977..000000000
--- a/images/emoji/1f1e8-1f1e9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e8-1f1eb.png b/images/emoji/1f1e8-1f1eb.png
deleted file mode 100644
index b969ae29e..000000000
--- a/images/emoji/1f1e8-1f1eb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e8-1f1ec.png b/images/emoji/1f1e8-1f1ec.png
deleted file mode 100644
index 3a38a40a9..000000000
--- a/images/emoji/1f1e8-1f1ec.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e8-1f1ed.png b/images/emoji/1f1e8-1f1ed.png
deleted file mode 100644
index 5ff86b8a3..000000000
--- a/images/emoji/1f1e8-1f1ed.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e8-1f1ee.png b/images/emoji/1f1e8-1f1ee.png
deleted file mode 100644
index e3b4d15c7..000000000
--- a/images/emoji/1f1e8-1f1ee.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e8-1f1f0.png b/images/emoji/1f1e8-1f1f0.png
deleted file mode 100644
index b6b53dbc1..000000000
--- a/images/emoji/1f1e8-1f1f0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e8-1f1f1.png b/images/emoji/1f1e8-1f1f1.png
deleted file mode 100644
index c9390da54..000000000
--- a/images/emoji/1f1e8-1f1f1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e8-1f1f2.png b/images/emoji/1f1e8-1f1f2.png
deleted file mode 100644
index 2d3f6ec45..000000000
--- a/images/emoji/1f1e8-1f1f2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e8-1f1f3.png b/images/emoji/1f1e8-1f1f3.png
deleted file mode 100644
index 0a7f350a6..000000000
--- a/images/emoji/1f1e8-1f1f3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e8-1f1f4.png b/images/emoji/1f1e8-1f1f4.png
deleted file mode 100644
index 7e0f5e0dc..000000000
--- a/images/emoji/1f1e8-1f1f4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e8-1f1f5.png b/images/emoji/1f1e8-1f1f5.png
deleted file mode 100644
index 70c761036..000000000
--- a/images/emoji/1f1e8-1f1f5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e8-1f1f7.png b/images/emoji/1f1e8-1f1f7.png
deleted file mode 100644
index a5fce1265..000000000
--- a/images/emoji/1f1e8-1f1f7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e8-1f1fa.png b/images/emoji/1f1e8-1f1fa.png
deleted file mode 100644
index 447328f7d..000000000
--- a/images/emoji/1f1e8-1f1fa.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e8-1f1fb.png b/images/emoji/1f1e8-1f1fb.png
deleted file mode 100644
index 43faf4d64..000000000
--- a/images/emoji/1f1e8-1f1fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e8-1f1fc.png b/images/emoji/1f1e8-1f1fc.png
deleted file mode 100644
index eb39e8d00..000000000
--- a/images/emoji/1f1e8-1f1fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e8-1f1fd.png b/images/emoji/1f1e8-1f1fd.png
deleted file mode 100644
index 09d21359f..000000000
--- a/images/emoji/1f1e8-1f1fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e8-1f1fe.png b/images/emoji/1f1e8-1f1fe.png
deleted file mode 100644
index 154a7aa31..000000000
--- a/images/emoji/1f1e8-1f1fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e8-1f1ff.png b/images/emoji/1f1e8-1f1ff.png
deleted file mode 100644
index 9737ca223..000000000
--- a/images/emoji/1f1e8-1f1ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e8.png b/images/emoji/1f1e8.png
deleted file mode 100644
index f94e668a2..000000000
--- a/images/emoji/1f1e8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e9-1f1ea.png b/images/emoji/1f1e9-1f1ea.png
deleted file mode 100644
index 98ed76b3b..000000000
--- a/images/emoji/1f1e9-1f1ea.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e9-1f1ec.png b/images/emoji/1f1e9-1f1ec.png
deleted file mode 100644
index fb6cc3cd4..000000000
--- a/images/emoji/1f1e9-1f1ec.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e9-1f1ef.png b/images/emoji/1f1e9-1f1ef.png
deleted file mode 100644
index 73c2a2acb..000000000
--- a/images/emoji/1f1e9-1f1ef.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e9-1f1f0.png b/images/emoji/1f1e9-1f1f0.png
deleted file mode 100644
index e5a60b062..000000000
--- a/images/emoji/1f1e9-1f1f0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e9-1f1f2.png b/images/emoji/1f1e9-1f1f2.png
deleted file mode 100644
index 4d4cf6444..000000000
--- a/images/emoji/1f1e9-1f1f2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e9-1f1f4.png b/images/emoji/1f1e9-1f1f4.png
deleted file mode 100644
index 037a45d7c..000000000
--- a/images/emoji/1f1e9-1f1f4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e9-1f1ff.png b/images/emoji/1f1e9-1f1ff.png
deleted file mode 100644
index 24945b10f..000000000
--- a/images/emoji/1f1e9-1f1ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1e9.png b/images/emoji/1f1e9.png
deleted file mode 100644
index 4a36666e5..000000000
--- a/images/emoji/1f1e9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ea-1f1e6.png b/images/emoji/1f1ea-1f1e6.png
deleted file mode 100644
index 9d05e1b0d..000000000
--- a/images/emoji/1f1ea-1f1e6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ea-1f1e8.png b/images/emoji/1f1ea-1f1e8.png
deleted file mode 100644
index 138145946..000000000
--- a/images/emoji/1f1ea-1f1e8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ea-1f1ea.png b/images/emoji/1f1ea-1f1ea.png
deleted file mode 100644
index 84f317e77..000000000
--- a/images/emoji/1f1ea-1f1ea.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ea-1f1ec.png b/images/emoji/1f1ea-1f1ec.png
deleted file mode 100644
index 57786064a..000000000
--- a/images/emoji/1f1ea-1f1ec.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ea-1f1ed.png b/images/emoji/1f1ea-1f1ed.png
deleted file mode 100644
index 4d7a76687..000000000
--- a/images/emoji/1f1ea-1f1ed.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ea-1f1f7.png b/images/emoji/1f1ea-1f1f7.png
deleted file mode 100644
index 0c3c724c1..000000000
--- a/images/emoji/1f1ea-1f1f7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ea-1f1f8.png b/images/emoji/1f1ea-1f1f8.png
deleted file mode 100644
index c37fdfe5c..000000000
--- a/images/emoji/1f1ea-1f1f8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ea-1f1f9.png b/images/emoji/1f1ea-1f1f9.png
deleted file mode 100644
index 9560a134c..000000000
--- a/images/emoji/1f1ea-1f1f9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ea-1f1fa.png b/images/emoji/1f1ea-1f1fa.png
deleted file mode 100644
index 0b456cf33..000000000
--- a/images/emoji/1f1ea-1f1fa.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ea.png b/images/emoji/1f1ea.png
deleted file mode 100644
index 66f7e8d8c..000000000
--- a/images/emoji/1f1ea.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1eb-1f1ee.png b/images/emoji/1f1eb-1f1ee.png
deleted file mode 100644
index ebcf58abf..000000000
--- a/images/emoji/1f1eb-1f1ee.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1eb-1f1ef.png b/images/emoji/1f1eb-1f1ef.png
deleted file mode 100644
index 9cc8c37fe..000000000
--- a/images/emoji/1f1eb-1f1ef.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1eb-1f1f0.png b/images/emoji/1f1eb-1f1f0.png
deleted file mode 100644
index 61372fd25..000000000
--- a/images/emoji/1f1eb-1f1f0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1eb-1f1f2.png b/images/emoji/1f1eb-1f1f2.png
deleted file mode 100644
index 0889825c8..000000000
--- a/images/emoji/1f1eb-1f1f2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1eb-1f1f4.png b/images/emoji/1f1eb-1f1f4.png
deleted file mode 100644
index 9a4431b08..000000000
--- a/images/emoji/1f1eb-1f1f4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1eb-1f1f7.png b/images/emoji/1f1eb-1f1f7.png
deleted file mode 100644
index 62ca19c3f..000000000
--- a/images/emoji/1f1eb-1f1f7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1eb.png b/images/emoji/1f1eb.png
deleted file mode 100644
index 913b230fd..000000000
--- a/images/emoji/1f1eb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ec-1f1e6.png b/images/emoji/1f1ec-1f1e6.png
deleted file mode 100644
index 2e68e527a..000000000
--- a/images/emoji/1f1ec-1f1e6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ec-1f1e7.png b/images/emoji/1f1ec-1f1e7.png
deleted file mode 100644
index 3ed10f623..000000000
--- a/images/emoji/1f1ec-1f1e7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ec-1f1e9.png b/images/emoji/1f1ec-1f1e9.png
deleted file mode 100644
index 527aad338..000000000
--- a/images/emoji/1f1ec-1f1e9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ec-1f1ea.png b/images/emoji/1f1ec-1f1ea.png
deleted file mode 100644
index a75d14248..000000000
--- a/images/emoji/1f1ec-1f1ea.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ec-1f1eb.png b/images/emoji/1f1ec-1f1eb.png
deleted file mode 100644
index 0cf96f327..000000000
--- a/images/emoji/1f1ec-1f1eb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ec-1f1ec.png b/images/emoji/1f1ec-1f1ec.png
deleted file mode 100644
index 970002c7f..000000000
--- a/images/emoji/1f1ec-1f1ec.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ec-1f1ed.png b/images/emoji/1f1ec-1f1ed.png
deleted file mode 100644
index f31b5eb7b..000000000
--- a/images/emoji/1f1ec-1f1ed.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ec-1f1ee.png b/images/emoji/1f1ec-1f1ee.png
deleted file mode 100644
index e554a2a1d..000000000
--- a/images/emoji/1f1ec-1f1ee.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ec-1f1f1.png b/images/emoji/1f1ec-1f1f1.png
deleted file mode 100644
index 2e795dd4e..000000000
--- a/images/emoji/1f1ec-1f1f1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ec-1f1f2.png b/images/emoji/1f1ec-1f1f2.png
deleted file mode 100644
index bb69c0975..000000000
--- a/images/emoji/1f1ec-1f1f2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ec-1f1f3.png b/images/emoji/1f1ec-1f1f3.png
deleted file mode 100644
index 1981f61db..000000000
--- a/images/emoji/1f1ec-1f1f3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ec-1f1f5.png b/images/emoji/1f1ec-1f1f5.png
deleted file mode 100644
index 10e42e672..000000000
--- a/images/emoji/1f1ec-1f1f5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ec-1f1f6.png b/images/emoji/1f1ec-1f1f6.png
deleted file mode 100644
index 11475e61e..000000000
--- a/images/emoji/1f1ec-1f1f6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ec-1f1f7.png b/images/emoji/1f1ec-1f1f7.png
deleted file mode 100644
index 0f6bb1b6b..000000000
--- a/images/emoji/1f1ec-1f1f7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ec-1f1f8.png b/images/emoji/1f1ec-1f1f8.png
deleted file mode 100644
index 6fc927804..000000000
--- a/images/emoji/1f1ec-1f1f8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ec-1f1f9.png b/images/emoji/1f1ec-1f1f9.png
deleted file mode 100644
index 7213d4139..000000000
--- a/images/emoji/1f1ec-1f1f9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ec-1f1fa.png b/images/emoji/1f1ec-1f1fa.png
deleted file mode 100644
index 4027549ca..000000000
--- a/images/emoji/1f1ec-1f1fa.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ec-1f1fc.png b/images/emoji/1f1ec-1f1fc.png
deleted file mode 100644
index 6357f6225..000000000
--- a/images/emoji/1f1ec-1f1fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ec-1f1fe.png b/images/emoji/1f1ec-1f1fe.png
deleted file mode 100644
index 746e2fb7e..000000000
--- a/images/emoji/1f1ec-1f1fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ec.png b/images/emoji/1f1ec.png
deleted file mode 100644
index 271163075..000000000
--- a/images/emoji/1f1ec.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ed-1f1f0.png b/images/emoji/1f1ed-1f1f0.png
deleted file mode 100644
index cf0c7151b..000000000
--- a/images/emoji/1f1ed-1f1f0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ed-1f1f2.png b/images/emoji/1f1ed-1f1f2.png
deleted file mode 100644
index b613509e4..000000000
--- a/images/emoji/1f1ed-1f1f2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ed-1f1f3.png b/images/emoji/1f1ed-1f1f3.png
deleted file mode 100644
index 402cdcefd..000000000
--- a/images/emoji/1f1ed-1f1f3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ed-1f1f7.png b/images/emoji/1f1ed-1f1f7.png
deleted file mode 100644
index 46f4f06b4..000000000
--- a/images/emoji/1f1ed-1f1f7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ed-1f1f9.png b/images/emoji/1f1ed-1f1f9.png
deleted file mode 100644
index d8d0c8884..000000000
--- a/images/emoji/1f1ed-1f1f9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ed-1f1fa.png b/images/emoji/1f1ed-1f1fa.png
deleted file mode 100644
index a898de636..000000000
--- a/images/emoji/1f1ed-1f1fa.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ed.png b/images/emoji/1f1ed.png
deleted file mode 100644
index ca88e46bf..000000000
--- a/images/emoji/1f1ed.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ee-1f1e8.png b/images/emoji/1f1ee-1f1e8.png
deleted file mode 100644
index 69fd990aa..000000000
--- a/images/emoji/1f1ee-1f1e8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ee-1f1e9.png b/images/emoji/1f1ee-1f1e9.png
deleted file mode 100644
index 85b4c063a..000000000
--- a/images/emoji/1f1ee-1f1e9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ee-1f1ea.png b/images/emoji/1f1ee-1f1ea.png
deleted file mode 100644
index a28295838..000000000
--- a/images/emoji/1f1ee-1f1ea.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ee-1f1f1.png b/images/emoji/1f1ee-1f1f1.png
deleted file mode 100644
index 85c410d45..000000000
--- a/images/emoji/1f1ee-1f1f1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ee-1f1f2.png b/images/emoji/1f1ee-1f1f2.png
deleted file mode 100644
index 60a2458e3..000000000
--- a/images/emoji/1f1ee-1f1f2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ee-1f1f3.png b/images/emoji/1f1ee-1f1f3.png
deleted file mode 100644
index feccc8952..000000000
--- a/images/emoji/1f1ee-1f1f3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ee-1f1f4.png b/images/emoji/1f1ee-1f1f4.png
deleted file mode 100644
index fb6cc3cd4..000000000
--- a/images/emoji/1f1ee-1f1f4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ee-1f1f6.png b/images/emoji/1f1ee-1f1f6.png
deleted file mode 100644
index 41fd1db6f..000000000
--- a/images/emoji/1f1ee-1f1f6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ee-1f1f7.png b/images/emoji/1f1ee-1f1f7.png
deleted file mode 100644
index ff7aaf62b..000000000
--- a/images/emoji/1f1ee-1f1f7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ee-1f1f8.png b/images/emoji/1f1ee-1f1f8.png
deleted file mode 100644
index ad8d4131d..000000000
--- a/images/emoji/1f1ee-1f1f8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ee-1f1f9.png b/images/emoji/1f1ee-1f1f9.png
deleted file mode 100644
index f21563ec5..000000000
--- a/images/emoji/1f1ee-1f1f9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ee.png b/images/emoji/1f1ee.png
deleted file mode 100644
index 48dc16788..000000000
--- a/images/emoji/1f1ee.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ef-1f1ea.png b/images/emoji/1f1ef-1f1ea.png
deleted file mode 100644
index 198a918f6..000000000
--- a/images/emoji/1f1ef-1f1ea.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ef-1f1f2.png b/images/emoji/1f1ef-1f1f2.png
deleted file mode 100644
index f84e4f9e8..000000000
--- a/images/emoji/1f1ef-1f1f2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ef-1f1f4.png b/images/emoji/1f1ef-1f1f4.png
deleted file mode 100644
index 20bfa147e..000000000
--- a/images/emoji/1f1ef-1f1f4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ef-1f1f5.png b/images/emoji/1f1ef-1f1f5.png
deleted file mode 100644
index 8d8838e47..000000000
--- a/images/emoji/1f1ef-1f1f5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ef.png b/images/emoji/1f1ef.png
deleted file mode 100644
index 16599daa7..000000000
--- a/images/emoji/1f1ef.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f0-1f1ea.png b/images/emoji/1f1f0-1f1ea.png
deleted file mode 100644
index 9e417ab30..000000000
--- a/images/emoji/1f1f0-1f1ea.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f0-1f1ec.png b/images/emoji/1f1f0-1f1ec.png
deleted file mode 100644
index b3eaf7e57..000000000
--- a/images/emoji/1f1f0-1f1ec.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f0-1f1ed.png b/images/emoji/1f1f0-1f1ed.png
deleted file mode 100644
index 9a2877dd6..000000000
--- a/images/emoji/1f1f0-1f1ed.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f0-1f1ee.png b/images/emoji/1f1f0-1f1ee.png
deleted file mode 100644
index 9a5abed3f..000000000
--- a/images/emoji/1f1f0-1f1ee.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f0-1f1f2.png b/images/emoji/1f1f0-1f1f2.png
deleted file mode 100644
index bd5a0588e..000000000
--- a/images/emoji/1f1f0-1f1f2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f0-1f1f3.png b/images/emoji/1f1f0-1f1f3.png
deleted file mode 100644
index 776207c96..000000000
--- a/images/emoji/1f1f0-1f1f3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f0-1f1f5.png b/images/emoji/1f1f0-1f1f5.png
deleted file mode 100644
index 6b3fd89ea..000000000
--- a/images/emoji/1f1f0-1f1f5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f0-1f1f7.png b/images/emoji/1f1f0-1f1f7.png
deleted file mode 100644
index faa466f2d..000000000
--- a/images/emoji/1f1f0-1f1f7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f0-1f1fc.png b/images/emoji/1f1f0-1f1fc.png
deleted file mode 100644
index 4d19bfa6c..000000000
--- a/images/emoji/1f1f0-1f1fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f0-1f1fe.png b/images/emoji/1f1f0-1f1fe.png
deleted file mode 100644
index 40daa4da5..000000000
--- a/images/emoji/1f1f0-1f1fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f0-1f1ff.png b/images/emoji/1f1f0-1f1ff.png
deleted file mode 100644
index 2f97a8fd3..000000000
--- a/images/emoji/1f1f0-1f1ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f0.png b/images/emoji/1f1f0.png
deleted file mode 100644
index 204b95d1b..000000000
--- a/images/emoji/1f1f0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f1-1f1e6.png b/images/emoji/1f1f1-1f1e6.png
deleted file mode 100644
index 4d4179f34..000000000
--- a/images/emoji/1f1f1-1f1e6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f1-1f1e7.png b/images/emoji/1f1f1-1f1e7.png
deleted file mode 100644
index 3d5944670..000000000
--- a/images/emoji/1f1f1-1f1e7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f1-1f1e8.png b/images/emoji/1f1f1-1f1e8.png
deleted file mode 100644
index 45547b1e4..000000000
--- a/images/emoji/1f1f1-1f1e8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f1-1f1ee.png b/images/emoji/1f1f1-1f1ee.png
deleted file mode 100644
index 0eafa6a22..000000000
--- a/images/emoji/1f1f1-1f1ee.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f1-1f1f0.png b/images/emoji/1f1f1-1f1f0.png
deleted file mode 100644
index ab4fe10c4..000000000
--- a/images/emoji/1f1f1-1f1f0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f1-1f1f7.png b/images/emoji/1f1f1-1f1f7.png
deleted file mode 100644
index f66f267fe..000000000
--- a/images/emoji/1f1f1-1f1f7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f1-1f1f8.png b/images/emoji/1f1f1-1f1f8.png
deleted file mode 100644
index 24745631e..000000000
--- a/images/emoji/1f1f1-1f1f8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f1-1f1f9.png b/images/emoji/1f1f1-1f1f9.png
deleted file mode 100644
index d644b56d6..000000000
--- a/images/emoji/1f1f1-1f1f9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f1-1f1fa.png b/images/emoji/1f1f1-1f1fa.png
deleted file mode 100644
index a2df9c929..000000000
--- a/images/emoji/1f1f1-1f1fa.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f1-1f1fb.png b/images/emoji/1f1f1-1f1fb.png
deleted file mode 100644
index ae680d5f0..000000000
--- a/images/emoji/1f1f1-1f1fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f1-1f1fe.png b/images/emoji/1f1f1-1f1fe.png
deleted file mode 100644
index f6e77b0f3..000000000
--- a/images/emoji/1f1f1-1f1fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f1.png b/images/emoji/1f1f1.png
deleted file mode 100644
index 7992b4f68..000000000
--- a/images/emoji/1f1f1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2-1f1e6.png b/images/emoji/1f1f2-1f1e6.png
deleted file mode 100644
index c4a056722..000000000
--- a/images/emoji/1f1f2-1f1e6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2-1f1e8.png b/images/emoji/1f1f2-1f1e8.png
deleted file mode 100644
index d479eab98..000000000
--- a/images/emoji/1f1f2-1f1e8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2-1f1e9.png b/images/emoji/1f1f2-1f1e9.png
deleted file mode 100644
index a7a725398..000000000
--- a/images/emoji/1f1f2-1f1e9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2-1f1ea.png b/images/emoji/1f1f2-1f1ea.png
deleted file mode 100644
index 7c771e7e1..000000000
--- a/images/emoji/1f1f2-1f1ea.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2-1f1eb.png b/images/emoji/1f1f2-1f1eb.png
deleted file mode 100644
index 70c761036..000000000
--- a/images/emoji/1f1f2-1f1eb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2-1f1ec.png b/images/emoji/1f1f2-1f1ec.png
deleted file mode 100644
index 2f3ccdda7..000000000
--- a/images/emoji/1f1f2-1f1ec.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2-1f1ed.png b/images/emoji/1f1f2-1f1ed.png
deleted file mode 100644
index 598016481..000000000
--- a/images/emoji/1f1f2-1f1ed.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2-1f1f0.png b/images/emoji/1f1f2-1f1f0.png
deleted file mode 100644
index 7ba775ee7..000000000
--- a/images/emoji/1f1f2-1f1f0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2-1f1f1.png b/images/emoji/1f1f2-1f1f1.png
deleted file mode 100644
index 683437854..000000000
--- a/images/emoji/1f1f2-1f1f1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2-1f1f2.png b/images/emoji/1f1f2-1f1f2.png
deleted file mode 100644
index 37dc7d715..000000000
--- a/images/emoji/1f1f2-1f1f2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2-1f1f3.png b/images/emoji/1f1f2-1f1f3.png
deleted file mode 100644
index 1f146bbcd..000000000
--- a/images/emoji/1f1f2-1f1f3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2-1f1f4.png b/images/emoji/1f1f2-1f1f4.png
deleted file mode 100644
index 7edde31f6..000000000
--- a/images/emoji/1f1f2-1f1f4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2-1f1f5.png b/images/emoji/1f1f2-1f1f5.png
deleted file mode 100644
index 17ec1c441..000000000
--- a/images/emoji/1f1f2-1f1f5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2-1f1f6.png b/images/emoji/1f1f2-1f1f6.png
deleted file mode 100644
index 1e672dc90..000000000
--- a/images/emoji/1f1f2-1f1f6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2-1f1f7.png b/images/emoji/1f1f2-1f1f7.png
deleted file mode 100644
index f87de46ef..000000000
--- a/images/emoji/1f1f2-1f1f7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2-1f1f8.png b/images/emoji/1f1f2-1f1f8.png
deleted file mode 100644
index 480b0d4eb..000000000
--- a/images/emoji/1f1f2-1f1f8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2-1f1f9.png b/images/emoji/1f1f2-1f1f9.png
deleted file mode 100644
index c9e1dbdce..000000000
--- a/images/emoji/1f1f2-1f1f9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2-1f1fa.png b/images/emoji/1f1f2-1f1fa.png
deleted file mode 100644
index 55b33cb7c..000000000
--- a/images/emoji/1f1f2-1f1fa.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2-1f1fb.png b/images/emoji/1f1f2-1f1fb.png
deleted file mode 100644
index ce5867126..000000000
--- a/images/emoji/1f1f2-1f1fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2-1f1fc.png b/images/emoji/1f1f2-1f1fc.png
deleted file mode 100644
index 003d85484..000000000
--- a/images/emoji/1f1f2-1f1fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2-1f1fd.png b/images/emoji/1f1f2-1f1fd.png
deleted file mode 100644
index 42572bcd0..000000000
--- a/images/emoji/1f1f2-1f1fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2-1f1fe.png b/images/emoji/1f1f2-1f1fe.png
deleted file mode 100644
index 17526c267..000000000
--- a/images/emoji/1f1f2-1f1fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2-1f1ff.png b/images/emoji/1f1f2-1f1ff.png
deleted file mode 100644
index 2352a78e7..000000000
--- a/images/emoji/1f1f2-1f1ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f2.png b/images/emoji/1f1f2.png
deleted file mode 100644
index 7b848b2ce..000000000
--- a/images/emoji/1f1f2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f3-1f1e6.png b/images/emoji/1f1f3-1f1e6.png
deleted file mode 100644
index ed31c3df0..000000000
--- a/images/emoji/1f1f3-1f1e6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f3-1f1e8.png b/images/emoji/1f1f3-1f1e8.png
deleted file mode 100644
index 3c57ee942..000000000
--- a/images/emoji/1f1f3-1f1e8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f3-1f1ea.png b/images/emoji/1f1f3-1f1ea.png
deleted file mode 100644
index f98a1173c..000000000
--- a/images/emoji/1f1f3-1f1ea.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f3-1f1eb.png b/images/emoji/1f1f3-1f1eb.png
deleted file mode 100644
index 9099e7674..000000000
--- a/images/emoji/1f1f3-1f1eb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f3-1f1ec.png b/images/emoji/1f1f3-1f1ec.png
deleted file mode 100644
index ea0abeff1..000000000
--- a/images/emoji/1f1f3-1f1ec.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f3-1f1ee.png b/images/emoji/1f1f3-1f1ee.png
deleted file mode 100644
index 772920dfa..000000000
--- a/images/emoji/1f1f3-1f1ee.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f3-1f1f1.png b/images/emoji/1f1f3-1f1f1.png
deleted file mode 100644
index 83a0e817e..000000000
--- a/images/emoji/1f1f3-1f1f1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f3-1f1f4.png b/images/emoji/1f1f3-1f1f4.png
deleted file mode 100644
index 99d3142eb..000000000
--- a/images/emoji/1f1f3-1f1f4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f3-1f1f5.png b/images/emoji/1f1f3-1f1f5.png
deleted file mode 100644
index 87425a8df..000000000
--- a/images/emoji/1f1f3-1f1f5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f3-1f1f7.png b/images/emoji/1f1f3-1f1f7.png
deleted file mode 100644
index b3e3a5d56..000000000
--- a/images/emoji/1f1f3-1f1f7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f3-1f1fa.png b/images/emoji/1f1f3-1f1fa.png
deleted file mode 100644
index f03614443..000000000
--- a/images/emoji/1f1f3-1f1fa.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f3-1f1ff.png b/images/emoji/1f1f3-1f1ff.png
deleted file mode 100644
index a4eeeab9c..000000000
--- a/images/emoji/1f1f3-1f1ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f3.png b/images/emoji/1f1f3.png
deleted file mode 100644
index 4a11e5043..000000000
--- a/images/emoji/1f1f3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f4-1f1f2.png b/images/emoji/1f1f4-1f1f2.png
deleted file mode 100644
index ea824ba31..000000000
--- a/images/emoji/1f1f4-1f1f2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f4.png b/images/emoji/1f1f4.png
deleted file mode 100644
index 2a0760b31..000000000
--- a/images/emoji/1f1f4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f5-1f1e6.png b/images/emoji/1f1f5-1f1e6.png
deleted file mode 100644
index c3091d898..000000000
--- a/images/emoji/1f1f5-1f1e6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f5-1f1ea.png b/images/emoji/1f1f5-1f1ea.png
deleted file mode 100644
index 39223aa9d..000000000
--- a/images/emoji/1f1f5-1f1ea.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f5-1f1eb.png b/images/emoji/1f1f5-1f1eb.png
deleted file mode 100644
index 113445f8f..000000000
--- a/images/emoji/1f1f5-1f1eb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f5-1f1ec.png b/images/emoji/1f1f5-1f1ec.png
deleted file mode 100644
index 825e9dcb7..000000000
--- a/images/emoji/1f1f5-1f1ec.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f5-1f1ed.png b/images/emoji/1f1f5-1f1ed.png
deleted file mode 100644
index 8260e15bd..000000000
--- a/images/emoji/1f1f5-1f1ed.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f5-1f1f0.png b/images/emoji/1f1f5-1f1f0.png
deleted file mode 100644
index a7b6a1c50..000000000
--- a/images/emoji/1f1f5-1f1f0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f5-1f1f1.png b/images/emoji/1f1f5-1f1f1.png
deleted file mode 100644
index 19de2edec..000000000
--- a/images/emoji/1f1f5-1f1f1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f5-1f1f2.png b/images/emoji/1f1f5-1f1f2.png
deleted file mode 100644
index 2ca605541..000000000
--- a/images/emoji/1f1f5-1f1f2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f5-1f1f3.png b/images/emoji/1f1f5-1f1f3.png
deleted file mode 100644
index 9a6327847..000000000
--- a/images/emoji/1f1f5-1f1f3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f5-1f1f7.png b/images/emoji/1f1f5-1f1f7.png
deleted file mode 100644
index d0209cddb..000000000
--- a/images/emoji/1f1f5-1f1f7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f5-1f1f8.png b/images/emoji/1f1f5-1f1f8.png
deleted file mode 100644
index 7ccab0977..000000000
--- a/images/emoji/1f1f5-1f1f8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f5-1f1f9.png b/images/emoji/1f1f5-1f1f9.png
deleted file mode 100644
index cc93f27c6..000000000
--- a/images/emoji/1f1f5-1f1f9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f5-1f1fc.png b/images/emoji/1f1f5-1f1fc.png
deleted file mode 100644
index 154b2f12d..000000000
--- a/images/emoji/1f1f5-1f1fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f5-1f1fe.png b/images/emoji/1f1f5-1f1fe.png
deleted file mode 100644
index 662ad2f6f..000000000
--- a/images/emoji/1f1f5-1f1fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f5.png b/images/emoji/1f1f5.png
deleted file mode 100644
index bcb3298f9..000000000
--- a/images/emoji/1f1f5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f6-1f1e6.png b/images/emoji/1f1f6-1f1e6.png
deleted file mode 100644
index a01d8b05c..000000000
--- a/images/emoji/1f1f6-1f1e6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f6.png b/images/emoji/1f1f6.png
deleted file mode 100644
index 6c92a9dfb..000000000
--- a/images/emoji/1f1f6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f7-1f1ea.png b/images/emoji/1f1f7-1f1ea.png
deleted file mode 100644
index 57f2bbe9d..000000000
--- a/images/emoji/1f1f7-1f1ea.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f7-1f1f4.png b/images/emoji/1f1f7-1f1f4.png
deleted file mode 100644
index 3e48c4477..000000000
--- a/images/emoji/1f1f7-1f1f4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f7-1f1f8.png b/images/emoji/1f1f7-1f1f8.png
deleted file mode 100644
index 9df6c9a52..000000000
--- a/images/emoji/1f1f7-1f1f8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f7-1f1fa.png b/images/emoji/1f1f7-1f1fa.png
deleted file mode 100644
index e50c9db90..000000000
--- a/images/emoji/1f1f7-1f1fa.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f7-1f1fc.png b/images/emoji/1f1f7-1f1fc.png
deleted file mode 100644
index c238c874e..000000000
--- a/images/emoji/1f1f7-1f1fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f7.png b/images/emoji/1f1f7.png
deleted file mode 100644
index 627892c91..000000000
--- a/images/emoji/1f1f7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f8-1f1e6.png b/images/emoji/1f1f8-1f1e6.png
deleted file mode 100644
index 4941be7d1..000000000
--- a/images/emoji/1f1f8-1f1e6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f8-1f1e7.png b/images/emoji/1f1f8-1f1e7.png
deleted file mode 100644
index 7d8f1ac61..000000000
--- a/images/emoji/1f1f8-1f1e7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f8-1f1e8.png b/images/emoji/1f1f8-1f1e8.png
deleted file mode 100644
index 6ae4d9076..000000000
--- a/images/emoji/1f1f8-1f1e8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f8-1f1e9.png b/images/emoji/1f1f8-1f1e9.png
deleted file mode 100644
index 963be1b36..000000000
--- a/images/emoji/1f1f8-1f1e9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f8-1f1ea.png b/images/emoji/1f1f8-1f1ea.png
deleted file mode 100644
index fc0d0e0ce..000000000
--- a/images/emoji/1f1f8-1f1ea.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f8-1f1ec.png b/images/emoji/1f1f8-1f1ec.png
deleted file mode 100644
index de3c7737c..000000000
--- a/images/emoji/1f1f8-1f1ec.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f8-1f1ed.png b/images/emoji/1f1f8-1f1ed.png
deleted file mode 100644
index 40cd9e44e..000000000
--- a/images/emoji/1f1f8-1f1ed.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f8-1f1ee.png b/images/emoji/1f1f8-1f1ee.png
deleted file mode 100644
index e308999db..000000000
--- a/images/emoji/1f1f8-1f1ee.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f8-1f1ef.png b/images/emoji/1f1f8-1f1ef.png
deleted file mode 100644
index 5884e6482..000000000
--- a/images/emoji/1f1f8-1f1ef.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f8-1f1f0.png b/images/emoji/1f1f8-1f1f0.png
deleted file mode 100644
index 4259d0e14..000000000
--- a/images/emoji/1f1f8-1f1f0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f8-1f1f1.png b/images/emoji/1f1f8-1f1f1.png
deleted file mode 100644
index d2cc68830..000000000
--- a/images/emoji/1f1f8-1f1f1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f8-1f1f2.png b/images/emoji/1f1f8-1f1f2.png
deleted file mode 100644
index b96ba87d0..000000000
--- a/images/emoji/1f1f8-1f1f2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f8-1f1f3.png b/images/emoji/1f1f8-1f1f3.png
deleted file mode 100644
index 5368bbe93..000000000
--- a/images/emoji/1f1f8-1f1f3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f8-1f1f4.png b/images/emoji/1f1f8-1f1f4.png
deleted file mode 100644
index 68a059736..000000000
--- a/images/emoji/1f1f8-1f1f4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f8-1f1f7.png b/images/emoji/1f1f8-1f1f7.png
deleted file mode 100644
index d32513270..000000000
--- a/images/emoji/1f1f8-1f1f7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f8-1f1f8.png b/images/emoji/1f1f8-1f1f8.png
deleted file mode 100644
index 122977e79..000000000
--- a/images/emoji/1f1f8-1f1f8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f8-1f1f9.png b/images/emoji/1f1f8-1f1f9.png
deleted file mode 100644
index f83a863d6..000000000
--- a/images/emoji/1f1f8-1f1f9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f8-1f1fb.png b/images/emoji/1f1f8-1f1fb.png
deleted file mode 100644
index efb83e2f2..000000000
--- a/images/emoji/1f1f8-1f1fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f8-1f1fd.png b/images/emoji/1f1f8-1f1fd.png
deleted file mode 100644
index 94b760fbe..000000000
--- a/images/emoji/1f1f8-1f1fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f8-1f1fe.png b/images/emoji/1f1f8-1f1fe.png
deleted file mode 100644
index 09a8ee8f7..000000000
--- a/images/emoji/1f1f8-1f1fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f8-1f1ff.png b/images/emoji/1f1f8-1f1ff.png
deleted file mode 100644
index f74e82ea1..000000000
--- a/images/emoji/1f1f8-1f1ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f8.png b/images/emoji/1f1f8.png
deleted file mode 100644
index 9d0dbf93a..000000000
--- a/images/emoji/1f1f8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f9-1f1e6.png b/images/emoji/1f1f9-1f1e6.png
deleted file mode 100644
index b44283e90..000000000
--- a/images/emoji/1f1f9-1f1e6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f9-1f1e8.png b/images/emoji/1f1f9-1f1e8.png
deleted file mode 100644
index 156b33d1b..000000000
--- a/images/emoji/1f1f9-1f1e8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f9-1f1e9.png b/images/emoji/1f1f9-1f1e9.png
deleted file mode 100644
index ebe7f5928..000000000
--- a/images/emoji/1f1f9-1f1e9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f9-1f1eb.png b/images/emoji/1f1f9-1f1eb.png
deleted file mode 100644
index a1a3ad68e..000000000
--- a/images/emoji/1f1f9-1f1eb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f9-1f1ec.png b/images/emoji/1f1f9-1f1ec.png
deleted file mode 100644
index 826b73c9a..000000000
--- a/images/emoji/1f1f9-1f1ec.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f9-1f1ed.png b/images/emoji/1f1f9-1f1ed.png
deleted file mode 100644
index 93ff542c5..000000000
--- a/images/emoji/1f1f9-1f1ed.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f9-1f1ef.png b/images/emoji/1f1f9-1f1ef.png
deleted file mode 100644
index 7a8a0b619..000000000
--- a/images/emoji/1f1f9-1f1ef.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f9-1f1f0.png b/images/emoji/1f1f9-1f1f0.png
deleted file mode 100644
index 2fa5a21b1..000000000
--- a/images/emoji/1f1f9-1f1f0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f9-1f1f1.png b/images/emoji/1f1f9-1f1f1.png
deleted file mode 100644
index 5b120eccc..000000000
--- a/images/emoji/1f1f9-1f1f1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f9-1f1f2.png b/images/emoji/1f1f9-1f1f2.png
deleted file mode 100644
index c3c4f5323..000000000
--- a/images/emoji/1f1f9-1f1f2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f9-1f1f3.png b/images/emoji/1f1f9-1f1f3.png
deleted file mode 100644
index 58ef16122..000000000
--- a/images/emoji/1f1f9-1f1f3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f9-1f1f4.png b/images/emoji/1f1f9-1f1f4.png
deleted file mode 100644
index 1ffa7bb9d..000000000
--- a/images/emoji/1f1f9-1f1f4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f9-1f1f7.png b/images/emoji/1f1f9-1f1f7.png
deleted file mode 100644
index 325251fae..000000000
--- a/images/emoji/1f1f9-1f1f7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f9-1f1f9.png b/images/emoji/1f1f9-1f1f9.png
deleted file mode 100644
index ed3bb39a3..000000000
--- a/images/emoji/1f1f9-1f1f9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f9-1f1fb.png b/images/emoji/1f1f9-1f1fb.png
deleted file mode 100644
index e82c65c7b..000000000
--- a/images/emoji/1f1f9-1f1fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f9-1f1fc.png b/images/emoji/1f1f9-1f1fc.png
deleted file mode 100644
index 3a8f00b59..000000000
--- a/images/emoji/1f1f9-1f1fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f9-1f1ff.png b/images/emoji/1f1f9-1f1ff.png
deleted file mode 100644
index 2a020853d..000000000
--- a/images/emoji/1f1f9-1f1ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1f9.png b/images/emoji/1f1f9.png
deleted file mode 100644
index 2d882f66b..000000000
--- a/images/emoji/1f1f9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1fa-1f1e6.png b/images/emoji/1f1fa-1f1e6.png
deleted file mode 100644
index cd84d1bbd..000000000
--- a/images/emoji/1f1fa-1f1e6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1fa-1f1ec.png b/images/emoji/1f1fa-1f1ec.png
deleted file mode 100644
index dc97690eb..000000000
--- a/images/emoji/1f1fa-1f1ec.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1fa-1f1f2.png b/images/emoji/1f1fa-1f1f2.png
deleted file mode 100644
index 4a7ee3cdf..000000000
--- a/images/emoji/1f1fa-1f1f2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1fa-1f1f8.png b/images/emoji/1f1fa-1f1f8.png
deleted file mode 100644
index 9f7303058..000000000
--- a/images/emoji/1f1fa-1f1f8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1fa-1f1fe.png b/images/emoji/1f1fa-1f1fe.png
deleted file mode 100644
index b8002a697..000000000
--- a/images/emoji/1f1fa-1f1fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1fa-1f1ff.png b/images/emoji/1f1fa-1f1ff.png
deleted file mode 100644
index d56ca9bc4..000000000
--- a/images/emoji/1f1fa-1f1ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1fa.png b/images/emoji/1f1fa.png
deleted file mode 100644
index ae0cabeb1..000000000
--- a/images/emoji/1f1fa.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1fb-1f1e6.png b/images/emoji/1f1fb-1f1e6.png
deleted file mode 100644
index 7f0676fc8..000000000
--- a/images/emoji/1f1fb-1f1e6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1fb-1f1e8.png b/images/emoji/1f1fb-1f1e8.png
deleted file mode 100644
index 43703c62a..000000000
--- a/images/emoji/1f1fb-1f1e8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1fb-1f1ea.png b/images/emoji/1f1fb-1f1ea.png
deleted file mode 100644
index 1b6279682..000000000
--- a/images/emoji/1f1fb-1f1ea.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1fb-1f1ec.png b/images/emoji/1f1fb-1f1ec.png
deleted file mode 100644
index 536f780f1..000000000
--- a/images/emoji/1f1fb-1f1ec.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1fb-1f1ee.png b/images/emoji/1f1fb-1f1ee.png
deleted file mode 100644
index 1b4219cb9..000000000
--- a/images/emoji/1f1fb-1f1ee.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1fb-1f1f3.png b/images/emoji/1f1fb-1f1f3.png
deleted file mode 100644
index 427036046..000000000
--- a/images/emoji/1f1fb-1f1f3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1fb-1f1fa.png b/images/emoji/1f1fb-1f1fa.png
deleted file mode 100644
index 706eba440..000000000
--- a/images/emoji/1f1fb-1f1fa.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1fb.png b/images/emoji/1f1fb.png
deleted file mode 100644
index e01e179b4..000000000
--- a/images/emoji/1f1fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1fc-1f1eb.png b/images/emoji/1f1fc-1f1eb.png
deleted file mode 100644
index 70c761036..000000000
--- a/images/emoji/1f1fc-1f1eb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1fc-1f1f8.png b/images/emoji/1f1fc-1f1f8.png
deleted file mode 100644
index a1ea07031..000000000
--- a/images/emoji/1f1fc-1f1f8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1fc.png b/images/emoji/1f1fc.png
deleted file mode 100644
index e8f614ac8..000000000
--- a/images/emoji/1f1fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1fd-1f1f0.png b/images/emoji/1f1fd-1f1f0.png
deleted file mode 100644
index e587a4466..000000000
--- a/images/emoji/1f1fd-1f1f0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1fd.png b/images/emoji/1f1fd.png
deleted file mode 100644
index e3bedba0b..000000000
--- a/images/emoji/1f1fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1fe-1f1ea.png b/images/emoji/1f1fe-1f1ea.png
deleted file mode 100644
index eadfebd5f..000000000
--- a/images/emoji/1f1fe-1f1ea.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1fe-1f1f9.png b/images/emoji/1f1fe-1f1f9.png
deleted file mode 100644
index e55fd8d85..000000000
--- a/images/emoji/1f1fe-1f1f9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1fe.png b/images/emoji/1f1fe.png
deleted file mode 100644
index 9bfa7f2db..000000000
--- a/images/emoji/1f1fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ff-1f1e6.png b/images/emoji/1f1ff-1f1e6.png
deleted file mode 100644
index f397ef507..000000000
--- a/images/emoji/1f1ff-1f1e6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ff-1f1f2.png b/images/emoji/1f1ff-1f1f2.png
deleted file mode 100644
index 2494a31f6..000000000
--- a/images/emoji/1f1ff-1f1f2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ff-1f1fc.png b/images/emoji/1f1ff-1f1fc.png
deleted file mode 100644
index e09b9652b..000000000
--- a/images/emoji/1f1ff-1f1fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f1ff.png b/images/emoji/1f1ff.png
deleted file mode 100644
index 5bf03f100..000000000
--- a/images/emoji/1f1ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f201.png b/images/emoji/1f201.png
deleted file mode 100644
index 6450eb44d..000000000
--- a/images/emoji/1f201.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f202.png b/images/emoji/1f202.png
deleted file mode 100644
index 900f96332..000000000
--- a/images/emoji/1f202.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f21a.png b/images/emoji/1f21a.png
deleted file mode 100644
index d3a19b420..000000000
--- a/images/emoji/1f21a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f22f.png b/images/emoji/1f22f.png
deleted file mode 100644
index 078e23e4f..000000000
--- a/images/emoji/1f22f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f232.png b/images/emoji/1f232.png
deleted file mode 100644
index 4c704e034..000000000
--- a/images/emoji/1f232.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f233.png b/images/emoji/1f233.png
deleted file mode 100644
index 47966c1ea..000000000
--- a/images/emoji/1f233.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f234.png b/images/emoji/1f234.png
deleted file mode 100644
index 8375ad9d9..000000000
--- a/images/emoji/1f234.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f235.png b/images/emoji/1f235.png
deleted file mode 100644
index f9dea8b88..000000000
--- a/images/emoji/1f235.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f236.png b/images/emoji/1f236.png
deleted file mode 100644
index a4510de41..000000000
--- a/images/emoji/1f236.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f237.png b/images/emoji/1f237.png
deleted file mode 100644
index c41bd36a2..000000000
--- a/images/emoji/1f237.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f238.png b/images/emoji/1f238.png
deleted file mode 100644
index 6b7af0ee2..000000000
--- a/images/emoji/1f238.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f239.png b/images/emoji/1f239.png
deleted file mode 100644
index c4f837fe6..000000000
--- a/images/emoji/1f239.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f23a.png b/images/emoji/1f23a.png
deleted file mode 100644
index d21cb30ea..000000000
--- a/images/emoji/1f23a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f250.png b/images/emoji/1f250.png
deleted file mode 100644
index 0c0d589ca..000000000
--- a/images/emoji/1f250.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f251.png b/images/emoji/1f251.png
deleted file mode 100644
index 8afd7ce99..000000000
--- a/images/emoji/1f251.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f300.png b/images/emoji/1f300.png
deleted file mode 100644
index ff00b1afe..000000000
--- a/images/emoji/1f300.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f301.png b/images/emoji/1f301.png
deleted file mode 100644
index 57702d8d3..000000000
--- a/images/emoji/1f301.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f302.png b/images/emoji/1f302.png
deleted file mode 100644
index ecefba9e4..000000000
--- a/images/emoji/1f302.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f303.png b/images/emoji/1f303.png
deleted file mode 100644
index ca2018f45..000000000
--- a/images/emoji/1f303.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f304.png b/images/emoji/1f304.png
deleted file mode 100644
index 39c57c86a..000000000
--- a/images/emoji/1f304.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f305.png b/images/emoji/1f305.png
deleted file mode 100644
index 4ad36003c..000000000
--- a/images/emoji/1f305.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f306.png b/images/emoji/1f306.png
deleted file mode 100644
index 80cdff7cf..000000000
--- a/images/emoji/1f306.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f307.png b/images/emoji/1f307.png
deleted file mode 100644
index 7cded0ba5..000000000
--- a/images/emoji/1f307.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f308.png b/images/emoji/1f308.png
deleted file mode 100644
index 154735d71..000000000
--- a/images/emoji/1f308.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f309.png b/images/emoji/1f309.png
deleted file mode 100644
index 1d444e0be..000000000
--- a/images/emoji/1f309.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f30a.png b/images/emoji/1f30a.png
deleted file mode 100644
index 45ff1e877..000000000
--- a/images/emoji/1f30a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f30b.png b/images/emoji/1f30b.png
deleted file mode 100644
index adb522980..000000000
--- a/images/emoji/1f30b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f30c.png b/images/emoji/1f30c.png
deleted file mode 100644
index b2b8ac59c..000000000
--- a/images/emoji/1f30c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f30d.png b/images/emoji/1f30d.png
deleted file mode 100644
index 66c3348c2..000000000
--- a/images/emoji/1f30d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f30e.png b/images/emoji/1f30e.png
deleted file mode 100644
index 538c3cddd..000000000
--- a/images/emoji/1f30e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f30f.png b/images/emoji/1f30f.png
deleted file mode 100644
index d8df97fec..000000000
--- a/images/emoji/1f30f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f310.png b/images/emoji/1f310.png
deleted file mode 100644
index 82450c1a4..000000000
--- a/images/emoji/1f310.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f311.png b/images/emoji/1f311.png
deleted file mode 100644
index ecff72caa..000000000
--- a/images/emoji/1f311.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f312.png b/images/emoji/1f312.png
deleted file mode 100644
index 921224a34..000000000
--- a/images/emoji/1f312.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f313.png b/images/emoji/1f313.png
deleted file mode 100644
index 5dccaf72a..000000000
--- a/images/emoji/1f313.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f314.png b/images/emoji/1f314.png
deleted file mode 100644
index 3a8081563..000000000
--- a/images/emoji/1f314.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f315.png b/images/emoji/1f315.png
deleted file mode 100644
index c9a2d6aa7..000000000
--- a/images/emoji/1f315.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f316.png b/images/emoji/1f316.png
deleted file mode 100644
index 741bd5931..000000000
--- a/images/emoji/1f316.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f317.png b/images/emoji/1f317.png
deleted file mode 100644
index 0842a0dd4..000000000
--- a/images/emoji/1f317.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f318.png b/images/emoji/1f318.png
deleted file mode 100644
index cf68706b8..000000000
--- a/images/emoji/1f318.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f319.png b/images/emoji/1f319.png
deleted file mode 100644
index 765420ece..000000000
--- a/images/emoji/1f319.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f31a.png b/images/emoji/1f31a.png
deleted file mode 100644
index 150dd1240..000000000
--- a/images/emoji/1f31a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f31b.png b/images/emoji/1f31b.png
deleted file mode 100644
index cd8a3d7ac..000000000
--- a/images/emoji/1f31b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f31c.png b/images/emoji/1f31c.png
deleted file mode 100644
index 94099343c..000000000
--- a/images/emoji/1f31c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f31d.png b/images/emoji/1f31d.png
deleted file mode 100644
index a5c25bbaf..000000000
--- a/images/emoji/1f31d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f31e.png b/images/emoji/1f31e.png
deleted file mode 100644
index 14a4ea971..000000000
--- a/images/emoji/1f31e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f31f.png b/images/emoji/1f31f.png
deleted file mode 100644
index 2f5cba592..000000000
--- a/images/emoji/1f31f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f320.png b/images/emoji/1f320.png
deleted file mode 100644
index aa45384d1..000000000
--- a/images/emoji/1f320.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f321.png b/images/emoji/1f321.png
deleted file mode 100644
index b11473924..000000000
--- a/images/emoji/1f321.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f324.png b/images/emoji/1f324.png
deleted file mode 100644
index cead0bfa5..000000000
--- a/images/emoji/1f324.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f325.png b/images/emoji/1f325.png
deleted file mode 100644
index 0a4cc1002..000000000
--- a/images/emoji/1f325.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f326.png b/images/emoji/1f326.png
deleted file mode 100644
index 491f9ca48..000000000
--- a/images/emoji/1f326.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f327.png b/images/emoji/1f327.png
deleted file mode 100644
index 385685e05..000000000
--- a/images/emoji/1f327.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f328.png b/images/emoji/1f328.png
deleted file mode 100644
index 9720384eb..000000000
--- a/images/emoji/1f328.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f329.png b/images/emoji/1f329.png
deleted file mode 100644
index 0831e88aa..000000000
--- a/images/emoji/1f329.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f32a.png b/images/emoji/1f32a.png
deleted file mode 100644
index 4821c89da..000000000
--- a/images/emoji/1f32a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f32b.png b/images/emoji/1f32b.png
deleted file mode 100644
index 4e73c2de2..000000000
--- a/images/emoji/1f32b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f32c.png b/images/emoji/1f32c.png
deleted file mode 100644
index df81b652e..000000000
--- a/images/emoji/1f32c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f32d.png b/images/emoji/1f32d.png
deleted file mode 100644
index 3c3354d94..000000000
--- a/images/emoji/1f32d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f32e.png b/images/emoji/1f32e.png
deleted file mode 100644
index 10e847a46..000000000
--- a/images/emoji/1f32e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f32f.png b/images/emoji/1f32f.png
deleted file mode 100644
index 02bd5601d..000000000
--- a/images/emoji/1f32f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f330.png b/images/emoji/1f330.png
deleted file mode 100644
index f8a01e281..000000000
--- a/images/emoji/1f330.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f331.png b/images/emoji/1f331.png
deleted file mode 100644
index ae0948bcf..000000000
--- a/images/emoji/1f331.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f332.png b/images/emoji/1f332.png
deleted file mode 100644
index f679d8dd7..000000000
--- a/images/emoji/1f332.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f333.png b/images/emoji/1f333.png
deleted file mode 100644
index 7cd2bc708..000000000
--- a/images/emoji/1f333.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f334.png b/images/emoji/1f334.png
deleted file mode 100644
index aaaa6aec3..000000000
--- a/images/emoji/1f334.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f335.png b/images/emoji/1f335.png
deleted file mode 100644
index 9b48ccf3d..000000000
--- a/images/emoji/1f335.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f336.png b/images/emoji/1f336.png
deleted file mode 100644
index 266675bd5..000000000
--- a/images/emoji/1f336.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f337.png b/images/emoji/1f337.png
deleted file mode 100644
index f799d75c1..000000000
--- a/images/emoji/1f337.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f338.png b/images/emoji/1f338.png
deleted file mode 100644
index 282f3e7bc..000000000
--- a/images/emoji/1f338.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f339.png b/images/emoji/1f339.png
deleted file mode 100644
index 52c286d31..000000000
--- a/images/emoji/1f339.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f33a.png b/images/emoji/1f33a.png
deleted file mode 100644
index 39dd35242..000000000
--- a/images/emoji/1f33a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f33b.png b/images/emoji/1f33b.png
deleted file mode 100644
index 08cc07761..000000000
--- a/images/emoji/1f33b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f33c.png b/images/emoji/1f33c.png
deleted file mode 100644
index 4083026c1..000000000
--- a/images/emoji/1f33c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f33d.png b/images/emoji/1f33d.png
deleted file mode 100644
index 36e201279..000000000
--- a/images/emoji/1f33d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f33e.png b/images/emoji/1f33e.png
deleted file mode 100644
index 3564d9d64..000000000
--- a/images/emoji/1f33e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f33f.png b/images/emoji/1f33f.png
deleted file mode 100644
index d984d1562..000000000
--- a/images/emoji/1f33f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f340.png b/images/emoji/1f340.png
deleted file mode 100644
index fdedfcc2b..000000000
--- a/images/emoji/1f340.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f341.png b/images/emoji/1f341.png
deleted file mode 100644
index c49acea67..000000000
--- a/images/emoji/1f341.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f342.png b/images/emoji/1f342.png
deleted file mode 100644
index 0d60e7bdf..000000000
--- a/images/emoji/1f342.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f343.png b/images/emoji/1f343.png
deleted file mode 100644
index 1e43e1af8..000000000
--- a/images/emoji/1f343.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f344.png b/images/emoji/1f344.png
deleted file mode 100644
index dd85742ba..000000000
--- a/images/emoji/1f344.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f345.png b/images/emoji/1f345.png
deleted file mode 100644
index 497da8f6b..000000000
--- a/images/emoji/1f345.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f346.png b/images/emoji/1f346.png
deleted file mode 100644
index fafd7c1a1..000000000
--- a/images/emoji/1f346.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f347.png b/images/emoji/1f347.png
deleted file mode 100644
index 30d222188..000000000
--- a/images/emoji/1f347.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f348.png b/images/emoji/1f348.png
deleted file mode 100644
index c01232d41..000000000
--- a/images/emoji/1f348.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f349.png b/images/emoji/1f349.png
deleted file mode 100644
index 0761488b4..000000000
--- a/images/emoji/1f349.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f34a.png b/images/emoji/1f34a.png
deleted file mode 100644
index ab14e5378..000000000
--- a/images/emoji/1f34a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f34b.png b/images/emoji/1f34b.png
deleted file mode 100644
index 9a7d95ca2..000000000
--- a/images/emoji/1f34b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f34c.png b/images/emoji/1f34c.png
deleted file mode 100644
index f49872795..000000000
--- a/images/emoji/1f34c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f34d.png b/images/emoji/1f34d.png
deleted file mode 100644
index d30d73307..000000000
--- a/images/emoji/1f34d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f34e.png b/images/emoji/1f34e.png
deleted file mode 100644
index da650c60f..000000000
--- a/images/emoji/1f34e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f34f.png b/images/emoji/1f34f.png
deleted file mode 100644
index 5fd51bd39..000000000
--- a/images/emoji/1f34f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f350.png b/images/emoji/1f350.png
deleted file mode 100644
index 3869f718b..000000000
--- a/images/emoji/1f350.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f351.png b/images/emoji/1f351.png
deleted file mode 100644
index 9ab57cbb7..000000000
--- a/images/emoji/1f351.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f352.png b/images/emoji/1f352.png
deleted file mode 100644
index 9b10cbaac..000000000
--- a/images/emoji/1f352.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f353.png b/images/emoji/1f353.png
deleted file mode 100644
index 7bb86f0b2..000000000
--- a/images/emoji/1f353.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f354.png b/images/emoji/1f354.png
deleted file mode 100644
index 4b13f3b8d..000000000
--- a/images/emoji/1f354.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f355.png b/images/emoji/1f355.png
deleted file mode 100644
index 240d5c469..000000000
--- a/images/emoji/1f355.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f356.png b/images/emoji/1f356.png
deleted file mode 100644
index b20a59d16..000000000
--- a/images/emoji/1f356.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f357.png b/images/emoji/1f357.png
deleted file mode 100644
index eea4a53a2..000000000
--- a/images/emoji/1f357.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f358.png b/images/emoji/1f358.png
deleted file mode 100644
index 7fbd08e4f..000000000
--- a/images/emoji/1f358.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f359.png b/images/emoji/1f359.png
deleted file mode 100644
index d3d8ee25c..000000000
--- a/images/emoji/1f359.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f35a.png b/images/emoji/1f35a.png
deleted file mode 100644
index 6e3ac7956..000000000
--- a/images/emoji/1f35a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f35b.png b/images/emoji/1f35b.png
deleted file mode 100644
index 69657ca81..000000000
--- a/images/emoji/1f35b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f35c.png b/images/emoji/1f35c.png
deleted file mode 100644
index c1cb7cd73..000000000
--- a/images/emoji/1f35c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f35d.png b/images/emoji/1f35d.png
deleted file mode 100644
index 4f0b7ed07..000000000
--- a/images/emoji/1f35d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f35e.png b/images/emoji/1f35e.png
deleted file mode 100644
index 6676510aa..000000000
--- a/images/emoji/1f35e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f35f.png b/images/emoji/1f35f.png
deleted file mode 100644
index 3a0899d5a..000000000
--- a/images/emoji/1f35f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f360.png b/images/emoji/1f360.png
deleted file mode 100644
index 92a425f2e..000000000
--- a/images/emoji/1f360.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f361.png b/images/emoji/1f361.png
deleted file mode 100644
index f73f37b01..000000000
--- a/images/emoji/1f361.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f362.png b/images/emoji/1f362.png
deleted file mode 100644
index d38a849fe..000000000
--- a/images/emoji/1f362.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f363.png b/images/emoji/1f363.png
deleted file mode 100644
index f171fd2f7..000000000
--- a/images/emoji/1f363.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f364.png b/images/emoji/1f364.png
deleted file mode 100644
index 752ba7f13..000000000
--- a/images/emoji/1f364.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f365.png b/images/emoji/1f365.png
deleted file mode 100644
index 157bded65..000000000
--- a/images/emoji/1f365.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f366.png b/images/emoji/1f366.png
deleted file mode 100644
index f1f21a3b8..000000000
--- a/images/emoji/1f366.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f367.png b/images/emoji/1f367.png
deleted file mode 100644
index 36dfb53ca..000000000
--- a/images/emoji/1f367.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f368.png b/images/emoji/1f368.png
deleted file mode 100644
index 720ae7428..000000000
--- a/images/emoji/1f368.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f369.png b/images/emoji/1f369.png
deleted file mode 100644
index 0ca4cd0bd..000000000
--- a/images/emoji/1f369.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f36a.png b/images/emoji/1f36a.png
deleted file mode 100644
index 1b6bcb155..000000000
--- a/images/emoji/1f36a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f36b.png b/images/emoji/1f36b.png
deleted file mode 100644
index 318bbd40e..000000000
--- a/images/emoji/1f36b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f36c.png b/images/emoji/1f36c.png
deleted file mode 100644
index 8c67ace3a..000000000
--- a/images/emoji/1f36c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f36d.png b/images/emoji/1f36d.png
deleted file mode 100644
index ad76d7bf9..000000000
--- a/images/emoji/1f36d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f36e.png b/images/emoji/1f36e.png
deleted file mode 100644
index fa3df67b8..000000000
--- a/images/emoji/1f36e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f36f.png b/images/emoji/1f36f.png
deleted file mode 100644
index 9d8f59295..000000000
--- a/images/emoji/1f36f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f370.png b/images/emoji/1f370.png
deleted file mode 100644
index 4368177be..000000000
--- a/images/emoji/1f370.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f371.png b/images/emoji/1f371.png
deleted file mode 100644
index 92cd17233..000000000
--- a/images/emoji/1f371.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f372.png b/images/emoji/1f372.png
deleted file mode 100644
index 6b3f010c1..000000000
--- a/images/emoji/1f372.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f373.png b/images/emoji/1f373.png
deleted file mode 100644
index 918c98057..000000000
--- a/images/emoji/1f373.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f374.png b/images/emoji/1f374.png
deleted file mode 100644
index 09f1feaea..000000000
--- a/images/emoji/1f374.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f375.png b/images/emoji/1f375.png
deleted file mode 100644
index b53b98f0c..000000000
--- a/images/emoji/1f375.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f376.png b/images/emoji/1f376.png
deleted file mode 100644
index 2933f5672..000000000
--- a/images/emoji/1f376.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f377.png b/images/emoji/1f377.png
deleted file mode 100644
index 3cc986891..000000000
--- a/images/emoji/1f377.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f378.png b/images/emoji/1f378.png
deleted file mode 100644
index 2e50c57e9..000000000
--- a/images/emoji/1f378.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f379.png b/images/emoji/1f379.png
deleted file mode 100644
index cd714f81b..000000000
--- a/images/emoji/1f379.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f37a.png b/images/emoji/1f37a.png
deleted file mode 100644
index 894da40a7..000000000
--- a/images/emoji/1f37a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f37b.png b/images/emoji/1f37b.png
deleted file mode 100644
index b55deb66b..000000000
--- a/images/emoji/1f37b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f37c.png b/images/emoji/1f37c.png
deleted file mode 100644
index 2bd105241..000000000
--- a/images/emoji/1f37c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f37d.png b/images/emoji/1f37d.png
deleted file mode 100644
index 7411755f7..000000000
--- a/images/emoji/1f37d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f37f.png b/images/emoji/1f37f.png
deleted file mode 100644
index 573ab05af..000000000
--- a/images/emoji/1f37f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f380.png b/images/emoji/1f380.png
deleted file mode 100644
index 0f253c3d8..000000000
--- a/images/emoji/1f380.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f381.png b/images/emoji/1f381.png
deleted file mode 100644
index 844e21645..000000000
--- a/images/emoji/1f381.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f382.png b/images/emoji/1f382.png
deleted file mode 100644
index 317e9a419..000000000
--- a/images/emoji/1f382.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f383.png b/images/emoji/1f383.png
deleted file mode 100644
index 44c3fc0ae..000000000
--- a/images/emoji/1f383.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f384.png b/images/emoji/1f384.png
deleted file mode 100644
index 4197d37a5..000000000
--- a/images/emoji/1f384.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f385-1f3fb.png b/images/emoji/1f385-1f3fb.png
deleted file mode 100644
index 2052920ab..000000000
--- a/images/emoji/1f385-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f385-1f3fc.png b/images/emoji/1f385-1f3fc.png
deleted file mode 100644
index ec9375e14..000000000
--- a/images/emoji/1f385-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f385-1f3fd.png b/images/emoji/1f385-1f3fd.png
deleted file mode 100644
index d1d16bceb..000000000
--- a/images/emoji/1f385-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f385-1f3fe.png b/images/emoji/1f385-1f3fe.png
deleted file mode 100644
index 1088f1c07..000000000
--- a/images/emoji/1f385-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f385-1f3ff.png b/images/emoji/1f385-1f3ff.png
deleted file mode 100644
index c92daf749..000000000
--- a/images/emoji/1f385-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f385.png b/images/emoji/1f385.png
deleted file mode 100644
index 8bf8757a3..000000000
--- a/images/emoji/1f385.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f386.png b/images/emoji/1f386.png
deleted file mode 100644
index e0a6c6a7c..000000000
--- a/images/emoji/1f386.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f387.png b/images/emoji/1f387.png
deleted file mode 100644
index 30339cd6e..000000000
--- a/images/emoji/1f387.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f388.png b/images/emoji/1f388.png
deleted file mode 100644
index 07916fe6d..000000000
--- a/images/emoji/1f388.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f389.png b/images/emoji/1f389.png
deleted file mode 100644
index 0244d60f2..000000000
--- a/images/emoji/1f389.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f38a.png b/images/emoji/1f38a.png
deleted file mode 100644
index ba4fd9b12..000000000
--- a/images/emoji/1f38a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f38b.png b/images/emoji/1f38b.png
deleted file mode 100644
index 46fcb3a1a..000000000
--- a/images/emoji/1f38b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f38c.png b/images/emoji/1f38c.png
deleted file mode 100644
index 273bd0f0f..000000000
--- a/images/emoji/1f38c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f38d.png b/images/emoji/1f38d.png
deleted file mode 100644
index 769f5ffae..000000000
--- a/images/emoji/1f38d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f38e.png b/images/emoji/1f38e.png
deleted file mode 100644
index 109556151..000000000
--- a/images/emoji/1f38e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f38f.png b/images/emoji/1f38f.png
deleted file mode 100644
index 5443bab90..000000000
--- a/images/emoji/1f38f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f390.png b/images/emoji/1f390.png
deleted file mode 100644
index 3c9ef3a95..000000000
--- a/images/emoji/1f390.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f391.png b/images/emoji/1f391.png
deleted file mode 100644
index 9bdc9d8d7..000000000
--- a/images/emoji/1f391.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f392.png b/images/emoji/1f392.png
deleted file mode 100644
index 9997c86e7..000000000
--- a/images/emoji/1f392.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f393.png b/images/emoji/1f393.png
deleted file mode 100644
index 8b17ddd9d..000000000
--- a/images/emoji/1f393.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f396.png b/images/emoji/1f396.png
deleted file mode 100644
index ecd3fb035..000000000
--- a/images/emoji/1f396.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f397.png b/images/emoji/1f397.png
deleted file mode 100644
index 3988bbd09..000000000
--- a/images/emoji/1f397.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f399.png b/images/emoji/1f399.png
deleted file mode 100644
index cd9167654..000000000
--- a/images/emoji/1f399.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f39a.png b/images/emoji/1f39a.png
deleted file mode 100644
index 720a3b341..000000000
--- a/images/emoji/1f39a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f39b.png b/images/emoji/1f39b.png
deleted file mode 100644
index 6635ac93b..000000000
--- a/images/emoji/1f39b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f39e.png b/images/emoji/1f39e.png
deleted file mode 100644
index 30143aedb..000000000
--- a/images/emoji/1f39e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f39f.png b/images/emoji/1f39f.png
deleted file mode 100644
index e510f4a7a..000000000
--- a/images/emoji/1f39f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3a0.png b/images/emoji/1f3a0.png
deleted file mode 100644
index a17074edf..000000000
--- a/images/emoji/1f3a0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3a1.png b/images/emoji/1f3a1.png
deleted file mode 100644
index 55c8ff047..000000000
--- a/images/emoji/1f3a1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3a2.png b/images/emoji/1f3a2.png
deleted file mode 100644
index 7d187be0c..000000000
--- a/images/emoji/1f3a2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3a3.png b/images/emoji/1f3a3.png
deleted file mode 100644
index dfcdf07eb..000000000
--- a/images/emoji/1f3a3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3a4.png b/images/emoji/1f3a4.png
deleted file mode 100644
index d4e6b0def..000000000
--- a/images/emoji/1f3a4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3a5.png b/images/emoji/1f3a5.png
deleted file mode 100644
index 4e73b1301..000000000
--- a/images/emoji/1f3a5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3a6.png b/images/emoji/1f3a6.png
deleted file mode 100644
index 65f27b386..000000000
--- a/images/emoji/1f3a6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3a7.png b/images/emoji/1f3a7.png
deleted file mode 100644
index e9fd34041..000000000
--- a/images/emoji/1f3a7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3a8.png b/images/emoji/1f3a8.png
deleted file mode 100644
index bd6afe9ff..000000000
--- a/images/emoji/1f3a8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3a9.png b/images/emoji/1f3a9.png
deleted file mode 100644
index 131b657b1..000000000
--- a/images/emoji/1f3a9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3aa.png b/images/emoji/1f3aa.png
deleted file mode 100644
index b0379775b..000000000
--- a/images/emoji/1f3aa.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3ab.png b/images/emoji/1f3ab.png
deleted file mode 100644
index 605936bb6..000000000
--- a/images/emoji/1f3ab.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3ac.png b/images/emoji/1f3ac.png
deleted file mode 100644
index 813908831..000000000
--- a/images/emoji/1f3ac.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3ad.png b/images/emoji/1f3ad.png
deleted file mode 100644
index 685441fda..000000000
--- a/images/emoji/1f3ad.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3ae.png b/images/emoji/1f3ae.png
deleted file mode 100644
index 316a9106a..000000000
--- a/images/emoji/1f3ae.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3af.png b/images/emoji/1f3af.png
deleted file mode 100644
index f6704aeb8..000000000
--- a/images/emoji/1f3af.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3b0.png b/images/emoji/1f3b0.png
deleted file mode 100644
index ee71b6c26..000000000
--- a/images/emoji/1f3b0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3b1.png b/images/emoji/1f3b1.png
deleted file mode 100644
index 38ca662ed..000000000
--- a/images/emoji/1f3b1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3b2.png b/images/emoji/1f3b2.png
deleted file mode 100644
index ad3626fe5..000000000
--- a/images/emoji/1f3b2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3b3.png b/images/emoji/1f3b3.png
deleted file mode 100644
index 63add89e5..000000000
--- a/images/emoji/1f3b3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3b4.png b/images/emoji/1f3b4.png
deleted file mode 100644
index 6766b044d..000000000
--- a/images/emoji/1f3b4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3b5.png b/images/emoji/1f3b5.png
deleted file mode 100644
index 06691ef61..000000000
--- a/images/emoji/1f3b5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3b6.png b/images/emoji/1f3b6.png
deleted file mode 100644
index 57d499aa1..000000000
--- a/images/emoji/1f3b6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3b7.png b/images/emoji/1f3b7.png
deleted file mode 100644
index a392faec2..000000000
--- a/images/emoji/1f3b7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3b8.png b/images/emoji/1f3b8.png
deleted file mode 100644
index 43d752f1e..000000000
--- a/images/emoji/1f3b8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3b9.png b/images/emoji/1f3b9.png
deleted file mode 100644
index 442b74568..000000000
--- a/images/emoji/1f3b9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3ba.png b/images/emoji/1f3ba.png
deleted file mode 100644
index 87674cf78..000000000
--- a/images/emoji/1f3ba.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3bb.png b/images/emoji/1f3bb.png
deleted file mode 100644
index e1e76cce2..000000000
--- a/images/emoji/1f3bb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3bc.png b/images/emoji/1f3bc.png
deleted file mode 100644
index 47dc05a8e..000000000
--- a/images/emoji/1f3bc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3bd.png b/images/emoji/1f3bd.png
deleted file mode 100644
index 6d83c06b8..000000000
--- a/images/emoji/1f3bd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3be.png b/images/emoji/1f3be.png
deleted file mode 100644
index 7e68ba8f3..000000000
--- a/images/emoji/1f3be.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3bf.png b/images/emoji/1f3bf.png
deleted file mode 100644
index 4a2d2c123..000000000
--- a/images/emoji/1f3bf.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c0.png b/images/emoji/1f3c0.png
deleted file mode 100644
index 64c76b79c..000000000
--- a/images/emoji/1f3c0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c1.png b/images/emoji/1f3c1.png
deleted file mode 100644
index 5a71eecb8..000000000
--- a/images/emoji/1f3c1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c2.png b/images/emoji/1f3c2.png
deleted file mode 100644
index 6361c0f2c..000000000
--- a/images/emoji/1f3c2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c3-1f3fb.png b/images/emoji/1f3c3-1f3fb.png
deleted file mode 100644
index 9355239a5..000000000
--- a/images/emoji/1f3c3-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c3-1f3fc.png b/images/emoji/1f3c3-1f3fc.png
deleted file mode 100644
index 6112fd5c3..000000000
--- a/images/emoji/1f3c3-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c3-1f3fd.png b/images/emoji/1f3c3-1f3fd.png
deleted file mode 100644
index 625ec708f..000000000
--- a/images/emoji/1f3c3-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c3-1f3fe.png b/images/emoji/1f3c3-1f3fe.png
deleted file mode 100644
index 242f1b563..000000000
--- a/images/emoji/1f3c3-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c3-1f3ff.png b/images/emoji/1f3c3-1f3ff.png
deleted file mode 100644
index 2976c6f01..000000000
--- a/images/emoji/1f3c3-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c3.png b/images/emoji/1f3c3.png
deleted file mode 100644
index e91491597..000000000
--- a/images/emoji/1f3c3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c4-1f3fb.png b/images/emoji/1f3c4-1f3fb.png
deleted file mode 100644
index b5faaa524..000000000
--- a/images/emoji/1f3c4-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c4-1f3fc.png b/images/emoji/1f3c4-1f3fc.png
deleted file mode 100644
index 6d92e412f..000000000
--- a/images/emoji/1f3c4-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c4-1f3fd.png b/images/emoji/1f3c4-1f3fd.png
deleted file mode 100644
index f05ef5949..000000000
--- a/images/emoji/1f3c4-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c4-1f3fe.png b/images/emoji/1f3c4-1f3fe.png
deleted file mode 100644
index 35e143d19..000000000
--- a/images/emoji/1f3c4-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c4-1f3ff.png b/images/emoji/1f3c4-1f3ff.png
deleted file mode 100644
index 38917658e..000000000
--- a/images/emoji/1f3c4-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c4.png b/images/emoji/1f3c4.png
deleted file mode 100644
index 3ab017adf..000000000
--- a/images/emoji/1f3c4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c5.png b/images/emoji/1f3c5.png
deleted file mode 100644
index 09718d001..000000000
--- a/images/emoji/1f3c5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c6.png b/images/emoji/1f3c6.png
deleted file mode 100644
index ac2895c18..000000000
--- a/images/emoji/1f3c6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c7-1f3fb.png b/images/emoji/1f3c7-1f3fb.png
deleted file mode 100644
index e9bf4092e..000000000
--- a/images/emoji/1f3c7-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c7-1f3fc.png b/images/emoji/1f3c7-1f3fc.png
deleted file mode 100644
index 031bbc3d8..000000000
--- a/images/emoji/1f3c7-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c7-1f3fd.png b/images/emoji/1f3c7-1f3fd.png
deleted file mode 100644
index b40ef891f..000000000
--- a/images/emoji/1f3c7-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c7-1f3fe.png b/images/emoji/1f3c7-1f3fe.png
deleted file mode 100644
index e286cb850..000000000
--- a/images/emoji/1f3c7-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c7-1f3ff.png b/images/emoji/1f3c7-1f3ff.png
deleted file mode 100644
index 453c51c60..000000000
--- a/images/emoji/1f3c7-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c7.png b/images/emoji/1f3c7.png
deleted file mode 100644
index addf9edac..000000000
--- a/images/emoji/1f3c7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c8.png b/images/emoji/1f3c8.png
deleted file mode 100644
index 909ddf95d..000000000
--- a/images/emoji/1f3c8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3c9.png b/images/emoji/1f3c9.png
deleted file mode 100644
index 659e134f7..000000000
--- a/images/emoji/1f3c9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3ca-1f3fb.png b/images/emoji/1f3ca-1f3fb.png
deleted file mode 100644
index 38441c9ca..000000000
--- a/images/emoji/1f3ca-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3ca-1f3fc.png b/images/emoji/1f3ca-1f3fc.png
deleted file mode 100644
index b0d431124..000000000
--- a/images/emoji/1f3ca-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3ca-1f3fd.png b/images/emoji/1f3ca-1f3fd.png
deleted file mode 100644
index 211e77e2a..000000000
--- a/images/emoji/1f3ca-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3ca-1f3fe.png b/images/emoji/1f3ca-1f3fe.png
deleted file mode 100644
index f34c34db9..000000000
--- a/images/emoji/1f3ca-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3ca-1f3ff.png b/images/emoji/1f3ca-1f3ff.png
deleted file mode 100644
index 3e9231ff8..000000000
--- a/images/emoji/1f3ca-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3ca.png b/images/emoji/1f3ca.png
deleted file mode 100644
index 55b4d72f9..000000000
--- a/images/emoji/1f3ca.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3cb-1f3fb.png b/images/emoji/1f3cb-1f3fb.png
deleted file mode 100644
index febaad123..000000000
--- a/images/emoji/1f3cb-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3cb-1f3fc.png b/images/emoji/1f3cb-1f3fc.png
deleted file mode 100644
index 27ae794a1..000000000
--- a/images/emoji/1f3cb-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3cb-1f3fd.png b/images/emoji/1f3cb-1f3fd.png
deleted file mode 100644
index 45c4c22c7..000000000
--- a/images/emoji/1f3cb-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3cb-1f3fe.png b/images/emoji/1f3cb-1f3fe.png
deleted file mode 100644
index 67dd21d24..000000000
--- a/images/emoji/1f3cb-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3cb-1f3ff.png b/images/emoji/1f3cb-1f3ff.png
deleted file mode 100644
index fa0152038..000000000
--- a/images/emoji/1f3cb-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3cb.png b/images/emoji/1f3cb.png
deleted file mode 100644
index afdeaa476..000000000
--- a/images/emoji/1f3cb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3cc.png b/images/emoji/1f3cc.png
deleted file mode 100644
index 39c552de8..000000000
--- a/images/emoji/1f3cc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3cd.png b/images/emoji/1f3cd.png
deleted file mode 100644
index 3d1d567e8..000000000
--- a/images/emoji/1f3cd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3ce.png b/images/emoji/1f3ce.png
deleted file mode 100644
index fe3f045f4..000000000
--- a/images/emoji/1f3ce.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3cf.png b/images/emoji/1f3cf.png
deleted file mode 100644
index d602294a2..000000000
--- a/images/emoji/1f3cf.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3d0.png b/images/emoji/1f3d0.png
deleted file mode 100644
index ce89e6d74..000000000
--- a/images/emoji/1f3d0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3d1.png b/images/emoji/1f3d1.png
deleted file mode 100644
index 839637716..000000000
--- a/images/emoji/1f3d1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3d2.png b/images/emoji/1f3d2.png
deleted file mode 100644
index be94e9cbf..000000000
--- a/images/emoji/1f3d2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3d3.png b/images/emoji/1f3d3.png
deleted file mode 100644
index ff3c51727..000000000
--- a/images/emoji/1f3d3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3d4.png b/images/emoji/1f3d4.png
deleted file mode 100644
index f63a205dc..000000000
--- a/images/emoji/1f3d4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3d5.png b/images/emoji/1f3d5.png
deleted file mode 100644
index 7da5a756e..000000000
--- a/images/emoji/1f3d5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3d6.png b/images/emoji/1f3d6.png
deleted file mode 100644
index 69108c8ea..000000000
--- a/images/emoji/1f3d6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3d7.png b/images/emoji/1f3d7.png
deleted file mode 100644
index 8206a20f6..000000000
--- a/images/emoji/1f3d7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3d8.png b/images/emoji/1f3d8.png
deleted file mode 100644
index 6ab4a2a26..000000000
--- a/images/emoji/1f3d8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3d9.png b/images/emoji/1f3d9.png
deleted file mode 100644
index d7b9844a0..000000000
--- a/images/emoji/1f3d9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3da.png b/images/emoji/1f3da.png
deleted file mode 100644
index c55e81de9..000000000
--- a/images/emoji/1f3da.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3db.png b/images/emoji/1f3db.png
deleted file mode 100644
index de7b559da..000000000
--- a/images/emoji/1f3db.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3dc.png b/images/emoji/1f3dc.png
deleted file mode 100644
index e9966ff8c..000000000
--- a/images/emoji/1f3dc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3dd.png b/images/emoji/1f3dd.png
deleted file mode 100644
index 7fd834389..000000000
--- a/images/emoji/1f3dd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3de.png b/images/emoji/1f3de.png
deleted file mode 100644
index 63ec70163..000000000
--- a/images/emoji/1f3de.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3df.png b/images/emoji/1f3df.png
deleted file mode 100644
index 1fee9a34b..000000000
--- a/images/emoji/1f3df.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3e0.png b/images/emoji/1f3e0.png
deleted file mode 100644
index 01c98a0ba..000000000
--- a/images/emoji/1f3e0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3e1.png b/images/emoji/1f3e1.png
deleted file mode 100644
index 1a276d153..000000000
--- a/images/emoji/1f3e1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3e2.png b/images/emoji/1f3e2.png
deleted file mode 100644
index 7eee927d1..000000000
--- a/images/emoji/1f3e2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3e3.png b/images/emoji/1f3e3.png
deleted file mode 100644
index a23848f9a..000000000
--- a/images/emoji/1f3e3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3e4.png b/images/emoji/1f3e4.png
deleted file mode 100644
index 3745aff8d..000000000
--- a/images/emoji/1f3e4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3e5.png b/images/emoji/1f3e5.png
deleted file mode 100644
index 1cbce4ae7..000000000
--- a/images/emoji/1f3e5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3e6.png b/images/emoji/1f3e6.png
deleted file mode 100644
index dffdcef36..000000000
--- a/images/emoji/1f3e6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3e7.png b/images/emoji/1f3e7.png
deleted file mode 100644
index 4d935307b..000000000
--- a/images/emoji/1f3e7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3e8.png b/images/emoji/1f3e8.png
deleted file mode 100644
index ea8f4c497..000000000
--- a/images/emoji/1f3e8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3e9.png b/images/emoji/1f3e9.png
deleted file mode 100644
index 5e136be6f..000000000
--- a/images/emoji/1f3e9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3ea.png b/images/emoji/1f3ea.png
deleted file mode 100644
index 26b53b566..000000000
--- a/images/emoji/1f3ea.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3eb.png b/images/emoji/1f3eb.png
deleted file mode 100644
index 269759534..000000000
--- a/images/emoji/1f3eb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3ec.png b/images/emoji/1f3ec.png
deleted file mode 100644
index 58867c7a6..000000000
--- a/images/emoji/1f3ec.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3ed.png b/images/emoji/1f3ed.png
deleted file mode 100644
index e1d2ddf4a..000000000
--- a/images/emoji/1f3ed.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3ee.png b/images/emoji/1f3ee.png
deleted file mode 100644
index 97cf5dbe1..000000000
--- a/images/emoji/1f3ee.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3ef.png b/images/emoji/1f3ef.png
deleted file mode 100644
index 64b4e33a1..000000000
--- a/images/emoji/1f3ef.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3f0.png b/images/emoji/1f3f0.png
deleted file mode 100644
index 888d11332..000000000
--- a/images/emoji/1f3f0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3f3.png b/images/emoji/1f3f3.png
deleted file mode 100644
index 86d6e96d5..000000000
--- a/images/emoji/1f3f3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3f4.png b/images/emoji/1f3f4.png
deleted file mode 100644
index 0e28d05d5..000000000
--- a/images/emoji/1f3f4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3f5.png b/images/emoji/1f3f5.png
deleted file mode 100644
index 8030e494b..000000000
--- a/images/emoji/1f3f5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3f7.png b/images/emoji/1f3f7.png
deleted file mode 100644
index d41c9b4f1..000000000
--- a/images/emoji/1f3f7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3f8.png b/images/emoji/1f3f8.png
deleted file mode 100644
index e0af4d99b..000000000
--- a/images/emoji/1f3f8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3f9.png b/images/emoji/1f3f9.png
deleted file mode 100644
index 6a538bf47..000000000
--- a/images/emoji/1f3f9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f3fa.png b/images/emoji/1f3fa.png
deleted file mode 100644
index 96de50560..000000000
--- a/images/emoji/1f3fa.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f400.png b/images/emoji/1f400.png
deleted file mode 100644
index 86219144f..000000000
--- a/images/emoji/1f400.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f401.png b/images/emoji/1f401.png
deleted file mode 100644
index 20fb041f0..000000000
--- a/images/emoji/1f401.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f402.png b/images/emoji/1f402.png
deleted file mode 100644
index badf5708f..000000000
--- a/images/emoji/1f402.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f403.png b/images/emoji/1f403.png
deleted file mode 100644
index 80446615c..000000000
--- a/images/emoji/1f403.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f404.png b/images/emoji/1f404.png
deleted file mode 100644
index 4d0ca534f..000000000
--- a/images/emoji/1f404.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f405.png b/images/emoji/1f405.png
deleted file mode 100644
index 871a8b74d..000000000
--- a/images/emoji/1f405.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f406.png b/images/emoji/1f406.png
deleted file mode 100644
index 8aac3d494..000000000
--- a/images/emoji/1f406.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f407.png b/images/emoji/1f407.png
deleted file mode 100644
index 2c8a29c64..000000000
--- a/images/emoji/1f407.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f408.png b/images/emoji/1f408.png
deleted file mode 100644
index 46abe8cbc..000000000
--- a/images/emoji/1f408.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f409.png b/images/emoji/1f409.png
deleted file mode 100644
index e298d2f6c..000000000
--- a/images/emoji/1f409.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f40a.png b/images/emoji/1f40a.png
deleted file mode 100644
index 3005c46f1..000000000
--- a/images/emoji/1f40a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f40b.png b/images/emoji/1f40b.png
deleted file mode 100644
index 0df9d3c73..000000000
--- a/images/emoji/1f40b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f40c.png b/images/emoji/1f40c.png
deleted file mode 100644
index f4ea071e2..000000000
--- a/images/emoji/1f40c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f40d.png b/images/emoji/1f40d.png
deleted file mode 100644
index f041d3b2e..000000000
--- a/images/emoji/1f40d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f40e.png b/images/emoji/1f40e.png
deleted file mode 100644
index 0b4d8903c..000000000
--- a/images/emoji/1f40e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f40f.png b/images/emoji/1f40f.png
deleted file mode 100644
index 52a44464c..000000000
--- a/images/emoji/1f40f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f410.png b/images/emoji/1f410.png
deleted file mode 100644
index f9d9e38a1..000000000
--- a/images/emoji/1f410.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f411.png b/images/emoji/1f411.png
deleted file mode 100644
index eea1f2f8d..000000000
--- a/images/emoji/1f411.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f412.png b/images/emoji/1f412.png
deleted file mode 100644
index 65042c09f..000000000
--- a/images/emoji/1f412.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f413.png b/images/emoji/1f413.png
deleted file mode 100644
index bbf2bbff9..000000000
--- a/images/emoji/1f413.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f414.png b/images/emoji/1f414.png
deleted file mode 100644
index 9a6992e55..000000000
--- a/images/emoji/1f414.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f415.png b/images/emoji/1f415.png
deleted file mode 100644
index 976143dbd..000000000
--- a/images/emoji/1f415.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f416.png b/images/emoji/1f416.png
deleted file mode 100644
index 5f31c1a2d..000000000
--- a/images/emoji/1f416.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f417.png b/images/emoji/1f417.png
deleted file mode 100644
index 3073bf026..000000000
--- a/images/emoji/1f417.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f418.png b/images/emoji/1f418.png
deleted file mode 100644
index b8a6d1405..000000000
--- a/images/emoji/1f418.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f419.png b/images/emoji/1f419.png
deleted file mode 100644
index 72c84074a..000000000
--- a/images/emoji/1f419.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f41a.png b/images/emoji/1f41a.png
deleted file mode 100644
index 55721629f..000000000
--- a/images/emoji/1f41a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f41b.png b/images/emoji/1f41b.png
deleted file mode 100644
index c9a00cf3e..000000000
--- a/images/emoji/1f41b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f41c.png b/images/emoji/1f41c.png
deleted file mode 100644
index 994127ed6..000000000
--- a/images/emoji/1f41c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f41d.png b/images/emoji/1f41d.png
deleted file mode 100644
index 6bf6f67e1..000000000
--- a/images/emoji/1f41d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f41e.png b/images/emoji/1f41e.png
deleted file mode 100644
index 3d93174d7..000000000
--- a/images/emoji/1f41e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f41f.png b/images/emoji/1f41f.png
deleted file mode 100644
index c2d2faaac..000000000
--- a/images/emoji/1f41f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f420.png b/images/emoji/1f420.png
deleted file mode 100644
index 252105235..000000000
--- a/images/emoji/1f420.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f421.png b/images/emoji/1f421.png
deleted file mode 100644
index 2939344a5..000000000
--- a/images/emoji/1f421.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f422.png b/images/emoji/1f422.png
deleted file mode 100644
index 46f59337b..000000000
--- a/images/emoji/1f422.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f423.png b/images/emoji/1f423.png
deleted file mode 100644
index 56515ad34..000000000
--- a/images/emoji/1f423.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f424.png b/images/emoji/1f424.png
deleted file mode 100644
index dccd96576..000000000
--- a/images/emoji/1f424.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f425.png b/images/emoji/1f425.png
deleted file mode 100644
index 31dfb511e..000000000
--- a/images/emoji/1f425.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f426.png b/images/emoji/1f426.png
deleted file mode 100644
index e201c22be..000000000
--- a/images/emoji/1f426.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f427.png b/images/emoji/1f427.png
deleted file mode 100644
index c0064fb97..000000000
--- a/images/emoji/1f427.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f428.png b/images/emoji/1f428.png
deleted file mode 100644
index c846cd223..000000000
--- a/images/emoji/1f428.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f429.png b/images/emoji/1f429.png
deleted file mode 100644
index 8ec39e396..000000000
--- a/images/emoji/1f429.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f42a.png b/images/emoji/1f42a.png
deleted file mode 100644
index 5271637c7..000000000
--- a/images/emoji/1f42a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f42b.png b/images/emoji/1f42b.png
deleted file mode 100644
index b421d07a8..000000000
--- a/images/emoji/1f42b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f42c.png b/images/emoji/1f42c.png
deleted file mode 100644
index c2a914f59..000000000
--- a/images/emoji/1f42c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f42d.png b/images/emoji/1f42d.png
deleted file mode 100644
index a52c8414f..000000000
--- a/images/emoji/1f42d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f42e.png b/images/emoji/1f42e.png
deleted file mode 100644
index 602495bd9..000000000
--- a/images/emoji/1f42e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f42f.png b/images/emoji/1f42f.png
deleted file mode 100644
index a4d3ef086..000000000
--- a/images/emoji/1f42f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f430.png b/images/emoji/1f430.png
deleted file mode 100644
index 20c67d11b..000000000
--- a/images/emoji/1f430.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f431.png b/images/emoji/1f431.png
deleted file mode 100644
index 10e20b530..000000000
--- a/images/emoji/1f431.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f432.png b/images/emoji/1f432.png
deleted file mode 100644
index 3c2720446..000000000
--- a/images/emoji/1f432.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f433.png b/images/emoji/1f433.png
deleted file mode 100644
index c2f52b443..000000000
--- a/images/emoji/1f433.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f434.png b/images/emoji/1f434.png
deleted file mode 100644
index f4f45047c..000000000
--- a/images/emoji/1f434.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f435.png b/images/emoji/1f435.png
deleted file mode 100644
index fe49a5467..000000000
--- a/images/emoji/1f435.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f436.png b/images/emoji/1f436.png
deleted file mode 100644
index 4a5b7b859..000000000
--- a/images/emoji/1f436.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f437.png b/images/emoji/1f437.png
deleted file mode 100644
index afe05ca16..000000000
--- a/images/emoji/1f437.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f438.png b/images/emoji/1f438.png
deleted file mode 100644
index 8825d1ad5..000000000
--- a/images/emoji/1f438.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f439.png b/images/emoji/1f439.png
deleted file mode 100644
index 376c36b0a..000000000
--- a/images/emoji/1f439.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f43a.png b/images/emoji/1f43a.png
deleted file mode 100644
index ba7220f2d..000000000
--- a/images/emoji/1f43a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f43b.png b/images/emoji/1f43b.png
deleted file mode 100644
index 272d56bbb..000000000
--- a/images/emoji/1f43b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f43c.png b/images/emoji/1f43c.png
deleted file mode 100644
index 978382775..000000000
--- a/images/emoji/1f43c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f43d.png b/images/emoji/1f43d.png
deleted file mode 100644
index 3610ae4a9..000000000
--- a/images/emoji/1f43d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f43e.png b/images/emoji/1f43e.png
deleted file mode 100644
index 5fe568cee..000000000
--- a/images/emoji/1f43e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f43f.png b/images/emoji/1f43f.png
deleted file mode 100644
index a9ab60f51..000000000
--- a/images/emoji/1f43f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f440.png b/images/emoji/1f440.png
deleted file mode 100644
index 2102ada7e..000000000
--- a/images/emoji/1f440.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f441-1f5e8.png b/images/emoji/1f441-1f5e8.png
deleted file mode 100644
index 21bd22bbc..000000000
--- a/images/emoji/1f441-1f5e8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f441.png b/images/emoji/1f441.png
deleted file mode 100644
index 9d989cdd3..000000000
--- a/images/emoji/1f441.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f442-1f3fb.png b/images/emoji/1f442-1f3fb.png
deleted file mode 100644
index d09e1e419..000000000
--- a/images/emoji/1f442-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f442-1f3fc.png b/images/emoji/1f442-1f3fc.png
deleted file mode 100644
index 300d60a99..000000000
--- a/images/emoji/1f442-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f442-1f3fd.png b/images/emoji/1f442-1f3fd.png
deleted file mode 100644
index 2a56eebe4..000000000
--- a/images/emoji/1f442-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f442-1f3fe.png b/images/emoji/1f442-1f3fe.png
deleted file mode 100644
index bd270f776..000000000
--- a/images/emoji/1f442-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f442-1f3ff.png b/images/emoji/1f442-1f3ff.png
deleted file mode 100644
index b96bb441d..000000000
--- a/images/emoji/1f442-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f442.png b/images/emoji/1f442.png
deleted file mode 100644
index f84f9ff15..000000000
--- a/images/emoji/1f442.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f443-1f3fb.png b/images/emoji/1f443-1f3fb.png
deleted file mode 100644
index 8008d1750..000000000
--- a/images/emoji/1f443-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f443-1f3fc.png b/images/emoji/1f443-1f3fc.png
deleted file mode 100644
index ac17f26e8..000000000
--- a/images/emoji/1f443-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f443-1f3fd.png b/images/emoji/1f443-1f3fd.png
deleted file mode 100644
index d8b6cbe0f..000000000
--- a/images/emoji/1f443-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f443-1f3fe.png b/images/emoji/1f443-1f3fe.png
deleted file mode 100644
index 004b2631e..000000000
--- a/images/emoji/1f443-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f443-1f3ff.png b/images/emoji/1f443-1f3ff.png
deleted file mode 100644
index 7b33821f6..000000000
--- a/images/emoji/1f443-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f443.png b/images/emoji/1f443.png
deleted file mode 100644
index 2f04ac5f9..000000000
--- a/images/emoji/1f443.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f444.png b/images/emoji/1f444.png
deleted file mode 100644
index 35f3cc200..000000000
--- a/images/emoji/1f444.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f445.png b/images/emoji/1f445.png
deleted file mode 100644
index 70ce9c122..000000000
--- a/images/emoji/1f445.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f446-1f3fb.png b/images/emoji/1f446-1f3fb.png
deleted file mode 100644
index a12a7e784..000000000
--- a/images/emoji/1f446-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f446-1f3fc.png b/images/emoji/1f446-1f3fc.png
deleted file mode 100644
index cdff40cea..000000000
--- a/images/emoji/1f446-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f446-1f3fd.png b/images/emoji/1f446-1f3fd.png
deleted file mode 100644
index a07ce9e5a..000000000
--- a/images/emoji/1f446-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f446-1f3fe.png b/images/emoji/1f446-1f3fe.png
deleted file mode 100644
index 4f86c88ba..000000000
--- a/images/emoji/1f446-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f446-1f3ff.png b/images/emoji/1f446-1f3ff.png
deleted file mode 100644
index ed1b26c35..000000000
--- a/images/emoji/1f446-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f446.png b/images/emoji/1f446.png
deleted file mode 100644
index bc496dfea..000000000
--- a/images/emoji/1f446.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f447-1f3fb.png b/images/emoji/1f447-1f3fb.png
deleted file mode 100644
index 140f157d8..000000000
--- a/images/emoji/1f447-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f447-1f3fc.png b/images/emoji/1f447-1f3fc.png
deleted file mode 100644
index d518544f7..000000000
--- a/images/emoji/1f447-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f447-1f3fd.png b/images/emoji/1f447-1f3fd.png
deleted file mode 100644
index 018b688b8..000000000
--- a/images/emoji/1f447-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f447-1f3fe.png b/images/emoji/1f447-1f3fe.png
deleted file mode 100644
index 98845bf6f..000000000
--- a/images/emoji/1f447-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f447-1f3ff.png b/images/emoji/1f447-1f3ff.png
deleted file mode 100644
index 9a9b039a9..000000000
--- a/images/emoji/1f447-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f447.png b/images/emoji/1f447.png
deleted file mode 100644
index 00d3d13ab..000000000
--- a/images/emoji/1f447.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f448-1f3fb.png b/images/emoji/1f448-1f3fb.png
deleted file mode 100644
index 88e2c3060..000000000
--- a/images/emoji/1f448-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f448-1f3fc.png b/images/emoji/1f448-1f3fc.png
deleted file mode 100644
index d3c89d87c..000000000
--- a/images/emoji/1f448-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f448-1f3fd.png b/images/emoji/1f448-1f3fd.png
deleted file mode 100644
index b23b91673..000000000
--- a/images/emoji/1f448-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f448-1f3fe.png b/images/emoji/1f448-1f3fe.png
deleted file mode 100644
index 3093f325c..000000000
--- a/images/emoji/1f448-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f448-1f3ff.png b/images/emoji/1f448-1f3ff.png
deleted file mode 100644
index 2b4cbfa12..000000000
--- a/images/emoji/1f448-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f448.png b/images/emoji/1f448.png
deleted file mode 100644
index 599fa2e3c..000000000
--- a/images/emoji/1f448.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f449-1f3fb.png b/images/emoji/1f449-1f3fb.png
deleted file mode 100644
index 4a28c6bbc..000000000
--- a/images/emoji/1f449-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f449-1f3fc.png b/images/emoji/1f449-1f3fc.png
deleted file mode 100644
index 7cb132317..000000000
--- a/images/emoji/1f449-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f449-1f3fd.png b/images/emoji/1f449-1f3fd.png
deleted file mode 100644
index 5514807d7..000000000
--- a/images/emoji/1f449-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f449-1f3fe.png b/images/emoji/1f449-1f3fe.png
deleted file mode 100644
index b8541d644..000000000
--- a/images/emoji/1f449-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f449-1f3ff.png b/images/emoji/1f449-1f3ff.png
deleted file mode 100644
index 1b7aab07b..000000000
--- a/images/emoji/1f449-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f449.png b/images/emoji/1f449.png
deleted file mode 100644
index 93a3cd34a..000000000
--- a/images/emoji/1f449.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44a-1f3fb.png b/images/emoji/1f44a-1f3fb.png
deleted file mode 100644
index 93c7d17fb..000000000
--- a/images/emoji/1f44a-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44a-1f3fc.png b/images/emoji/1f44a-1f3fc.png
deleted file mode 100644
index c0a1af6e1..000000000
--- a/images/emoji/1f44a-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44a-1f3fd.png b/images/emoji/1f44a-1f3fd.png
deleted file mode 100644
index 1458b0212..000000000
--- a/images/emoji/1f44a-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44a-1f3fe.png b/images/emoji/1f44a-1f3fe.png
deleted file mode 100644
index c1466bfcd..000000000
--- a/images/emoji/1f44a-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44a-1f3ff.png b/images/emoji/1f44a-1f3ff.png
deleted file mode 100644
index 00b4ddb89..000000000
--- a/images/emoji/1f44a-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44a.png b/images/emoji/1f44a.png
deleted file mode 100644
index b14ca5f52..000000000
--- a/images/emoji/1f44a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44b-1f3fb.png b/images/emoji/1f44b-1f3fb.png
deleted file mode 100644
index beea09dda..000000000
--- a/images/emoji/1f44b-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44b-1f3fc.png b/images/emoji/1f44b-1f3fc.png
deleted file mode 100644
index a7679d5fe..000000000
--- a/images/emoji/1f44b-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44b-1f3fd.png b/images/emoji/1f44b-1f3fd.png
deleted file mode 100644
index 6283b670f..000000000
--- a/images/emoji/1f44b-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44b-1f3fe.png b/images/emoji/1f44b-1f3fe.png
deleted file mode 100644
index b771b52c3..000000000
--- a/images/emoji/1f44b-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44b-1f3ff.png b/images/emoji/1f44b-1f3ff.png
deleted file mode 100644
index 6bbedc9b5..000000000
--- a/images/emoji/1f44b-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44b.png b/images/emoji/1f44b.png
deleted file mode 100644
index 02ae68b85..000000000
--- a/images/emoji/1f44b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44c-1f3fb.png b/images/emoji/1f44c-1f3fb.png
deleted file mode 100644
index cecf7b2ab..000000000
--- a/images/emoji/1f44c-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44c-1f3fc.png b/images/emoji/1f44c-1f3fc.png
deleted file mode 100644
index c19239bcd..000000000
--- a/images/emoji/1f44c-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44c-1f3fd.png b/images/emoji/1f44c-1f3fd.png
deleted file mode 100644
index 94b65b03e..000000000
--- a/images/emoji/1f44c-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44c-1f3fe.png b/images/emoji/1f44c-1f3fe.png
deleted file mode 100644
index 03d26f08e..000000000
--- a/images/emoji/1f44c-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44c-1f3ff.png b/images/emoji/1f44c-1f3ff.png
deleted file mode 100644
index d4b240863..000000000
--- a/images/emoji/1f44c-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44c.png b/images/emoji/1f44c.png
deleted file mode 100644
index 028d69b0d..000000000
--- a/images/emoji/1f44c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44d-1f3fb.png b/images/emoji/1f44d-1f3fb.png
deleted file mode 100644
index 39684cd5c..000000000
--- a/images/emoji/1f44d-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44d-1f3fc.png b/images/emoji/1f44d-1f3fc.png
deleted file mode 100644
index a9b597235..000000000
--- a/images/emoji/1f44d-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44d-1f3fd.png b/images/emoji/1f44d-1f3fd.png
deleted file mode 100644
index c5e291670..000000000
--- a/images/emoji/1f44d-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44d-1f3fe.png b/images/emoji/1f44d-1f3fe.png
deleted file mode 100644
index 5bf4857a8..000000000
--- a/images/emoji/1f44d-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44d-1f3ff.png b/images/emoji/1f44d-1f3ff.png
deleted file mode 100644
index d829f787c..000000000
--- a/images/emoji/1f44d-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44d.png b/images/emoji/1f44d.png
deleted file mode 100644
index f9e6f13a3..000000000
--- a/images/emoji/1f44d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44e-1f3fb.png b/images/emoji/1f44e-1f3fb.png
deleted file mode 100644
index a1631af8e..000000000
--- a/images/emoji/1f44e-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44e-1f3fc.png b/images/emoji/1f44e-1f3fc.png
deleted file mode 100644
index 85fff82d5..000000000
--- a/images/emoji/1f44e-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44e-1f3fd.png b/images/emoji/1f44e-1f3fd.png
deleted file mode 100644
index eeba3be80..000000000
--- a/images/emoji/1f44e-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44e-1f3fe.png b/images/emoji/1f44e-1f3fe.png
deleted file mode 100644
index 1addafdae..000000000
--- a/images/emoji/1f44e-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44e-1f3ff.png b/images/emoji/1f44e-1f3ff.png
deleted file mode 100644
index 37ec07b57..000000000
--- a/images/emoji/1f44e-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44e.png b/images/emoji/1f44e.png
deleted file mode 100644
index b63da2f20..000000000
--- a/images/emoji/1f44e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44f-1f3fb.png b/images/emoji/1f44f-1f3fb.png
deleted file mode 100644
index 770aa9ca0..000000000
--- a/images/emoji/1f44f-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44f-1f3fc.png b/images/emoji/1f44f-1f3fc.png
deleted file mode 100644
index 37c6b559a..000000000
--- a/images/emoji/1f44f-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44f-1f3fd.png b/images/emoji/1f44f-1f3fd.png
deleted file mode 100644
index e95bf2fc7..000000000
--- a/images/emoji/1f44f-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44f-1f3fe.png b/images/emoji/1f44f-1f3fe.png
deleted file mode 100644
index b6e9a9160..000000000
--- a/images/emoji/1f44f-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f44f-1f3ff.png b/images/emoji/1f44f-1f3ff.png
deleted file mode 100644
index 59cccdb73..000000000
--- a/images/emoji/1f44f-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f450-1f3fb.png b/images/emoji/1f450-1f3fb.png
deleted file mode 100644
index 352d2614f..000000000
--- a/images/emoji/1f450-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f450-1f3fc.png b/images/emoji/1f450-1f3fc.png
deleted file mode 100644
index 70824a50c..000000000
--- a/images/emoji/1f450-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f450-1f3fd.png b/images/emoji/1f450-1f3fd.png
deleted file mode 100644
index d7d136bd3..000000000
--- a/images/emoji/1f450-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f450-1f3fe.png b/images/emoji/1f450-1f3fe.png
deleted file mode 100644
index df4eaa711..000000000
--- a/images/emoji/1f450-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f450-1f3ff.png b/images/emoji/1f450-1f3ff.png
deleted file mode 100644
index 7dc04eaeb..000000000
--- a/images/emoji/1f450-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f450.png b/images/emoji/1f450.png
deleted file mode 100644
index 1cf75c910..000000000
--- a/images/emoji/1f450.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f451.png b/images/emoji/1f451.png
deleted file mode 100644
index 93b82d92f..000000000
--- a/images/emoji/1f451.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f452.png b/images/emoji/1f452.png
deleted file mode 100644
index b837b6a2e..000000000
--- a/images/emoji/1f452.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f453.png b/images/emoji/1f453.png
deleted file mode 100644
index 865d8274a..000000000
--- a/images/emoji/1f453.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f454.png b/images/emoji/1f454.png
deleted file mode 100644
index 1804e7f3f..000000000
--- a/images/emoji/1f454.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f455.png b/images/emoji/1f455.png
deleted file mode 100644
index af08dec8b..000000000
--- a/images/emoji/1f455.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f456.png b/images/emoji/1f456.png
deleted file mode 100644
index 2a6869d67..000000000
--- a/images/emoji/1f456.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f457.png b/images/emoji/1f457.png
deleted file mode 100644
index a697ca5c5..000000000
--- a/images/emoji/1f457.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f458.png b/images/emoji/1f458.png
deleted file mode 100644
index 297a42c7e..000000000
--- a/images/emoji/1f458.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f459.png b/images/emoji/1f459.png
deleted file mode 100644
index 77a8a0aae..000000000
--- a/images/emoji/1f459.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f45a.png b/images/emoji/1f45a.png
deleted file mode 100644
index 01410dc81..000000000
--- a/images/emoji/1f45a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f45b.png b/images/emoji/1f45b.png
deleted file mode 100644
index 981346193..000000000
--- a/images/emoji/1f45b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f45c.png b/images/emoji/1f45c.png
deleted file mode 100644
index cbf75c5d2..000000000
--- a/images/emoji/1f45c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f45d.png b/images/emoji/1f45d.png
deleted file mode 100644
index 8795c6c66..000000000
--- a/images/emoji/1f45d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f45e.png b/images/emoji/1f45e.png
deleted file mode 100644
index 16ccafb93..000000000
--- a/images/emoji/1f45e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f45f.png b/images/emoji/1f45f.png
deleted file mode 100644
index 423fa07dd..000000000
--- a/images/emoji/1f45f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f460.png b/images/emoji/1f460.png
deleted file mode 100644
index b331cbccc..000000000
--- a/images/emoji/1f460.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f461.png b/images/emoji/1f461.png
deleted file mode 100644
index 9d9f5122b..000000000
--- a/images/emoji/1f461.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f462.png b/images/emoji/1f462.png
deleted file mode 100644
index 11f1065ed..000000000
--- a/images/emoji/1f462.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f463.png b/images/emoji/1f463.png
deleted file mode 100644
index b2673c5a1..000000000
--- a/images/emoji/1f463.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f464.png b/images/emoji/1f464.png
deleted file mode 100644
index 123b2cbe1..000000000
--- a/images/emoji/1f464.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f465.png b/images/emoji/1f465.png
deleted file mode 100644
index d7656860a..000000000
--- a/images/emoji/1f465.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f466-1f3fb.png b/images/emoji/1f466-1f3fb.png
deleted file mode 100644
index 2fc436ea5..000000000
--- a/images/emoji/1f466-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f466-1f3fc.png b/images/emoji/1f466-1f3fc.png
deleted file mode 100644
index 09a5f18d3..000000000
--- a/images/emoji/1f466-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f466-1f3fd.png b/images/emoji/1f466-1f3fd.png
deleted file mode 100644
index 3cfe675dd..000000000
--- a/images/emoji/1f466-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f466-1f3fe.png b/images/emoji/1f466-1f3fe.png
deleted file mode 100644
index 780be0ace..000000000
--- a/images/emoji/1f466-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f466-1f3ff.png b/images/emoji/1f466-1f3ff.png
deleted file mode 100644
index f32fe22e3..000000000
--- a/images/emoji/1f466-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f466.png b/images/emoji/1f466.png
deleted file mode 100644
index 8ecfb0a4e..000000000
--- a/images/emoji/1f466.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f467-1f3fb.png b/images/emoji/1f467-1f3fb.png
deleted file mode 100644
index 2be1f0bee..000000000
--- a/images/emoji/1f467-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f467-1f3fc.png b/images/emoji/1f467-1f3fc.png
deleted file mode 100644
index a59ed4a3f..000000000
--- a/images/emoji/1f467-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f467-1f3fd.png b/images/emoji/1f467-1f3fd.png
deleted file mode 100644
index 517e7f2a7..000000000
--- a/images/emoji/1f467-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f467-1f3fe.png b/images/emoji/1f467-1f3fe.png
deleted file mode 100644
index 542d96c84..000000000
--- a/images/emoji/1f467-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f467-1f3ff.png b/images/emoji/1f467-1f3ff.png
deleted file mode 100644
index 66b7c28c2..000000000
--- a/images/emoji/1f467-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f467.png b/images/emoji/1f467.png
deleted file mode 100644
index 649eea6a5..000000000
--- a/images/emoji/1f467.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f468-1f3fb.png b/images/emoji/1f468-1f3fb.png
deleted file mode 100644
index bb86e963a..000000000
--- a/images/emoji/1f468-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f468-1f3fc.png b/images/emoji/1f468-1f3fc.png
deleted file mode 100644
index fdeeaff46..000000000
--- a/images/emoji/1f468-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f468-1f3fd.png b/images/emoji/1f468-1f3fd.png
deleted file mode 100644
index 7ae0b5df9..000000000
--- a/images/emoji/1f468-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f468-1f3fe.png b/images/emoji/1f468-1f3fe.png
deleted file mode 100644
index db14cde99..000000000
--- a/images/emoji/1f468-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f468-1f3ff.png b/images/emoji/1f468-1f3ff.png
deleted file mode 100644
index 7c67a7052..000000000
--- a/images/emoji/1f468-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f468-1f468-1f466-1f466.png b/images/emoji/1f468-1f468-1f466-1f466.png
deleted file mode 100644
index 0944001a3..000000000
--- a/images/emoji/1f468-1f468-1f466-1f466.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f468-1f468-1f466.png b/images/emoji/1f468-1f468-1f466.png
deleted file mode 100644
index 7a2e4e2c4..000000000
--- a/images/emoji/1f468-1f468-1f466.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f468-1f468-1f467-1f466.png b/images/emoji/1f468-1f468-1f467-1f466.png
deleted file mode 100644
index 41e351666..000000000
--- a/images/emoji/1f468-1f468-1f467-1f466.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f468-1f468-1f467-1f467.png b/images/emoji/1f468-1f468-1f467-1f467.png
deleted file mode 100644
index 8e8ccfe6c..000000000
--- a/images/emoji/1f468-1f468-1f467-1f467.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f468-1f468-1f467.png b/images/emoji/1f468-1f468-1f467.png
deleted file mode 100644
index 9bca550d0..000000000
--- a/images/emoji/1f468-1f468-1f467.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f468-1f469-1f466-1f466.png b/images/emoji/1f468-1f469-1f466-1f466.png
deleted file mode 100644
index 579eb59f8..000000000
--- a/images/emoji/1f468-1f469-1f466-1f466.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f468-1f469-1f467-1f466.png b/images/emoji/1f468-1f469-1f467-1f466.png
deleted file mode 100644
index c5c7b0942..000000000
--- a/images/emoji/1f468-1f469-1f467-1f466.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f468-1f469-1f467-1f467.png b/images/emoji/1f468-1f469-1f467-1f467.png
deleted file mode 100644
index b47f3b1c7..000000000
--- a/images/emoji/1f468-1f469-1f467-1f467.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f468-1f469-1f467.png b/images/emoji/1f468-1f469-1f467.png
deleted file mode 100644
index ffa6f4293..000000000
--- a/images/emoji/1f468-1f469-1f467.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f468-2764-1f468.png b/images/emoji/1f468-2764-1f468.png
deleted file mode 100644
index 8759fa5db..000000000
--- a/images/emoji/1f468-2764-1f468.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f468-2764-1f48b-1f468.png b/images/emoji/1f468-2764-1f48b-1f468.png
deleted file mode 100644
index a9a0edae1..000000000
--- a/images/emoji/1f468-2764-1f48b-1f468.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f468.png b/images/emoji/1f468.png
deleted file mode 100644
index 857a02e51..000000000
--- a/images/emoji/1f468.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f469-1f3fb.png b/images/emoji/1f469-1f3fb.png
deleted file mode 100644
index ff089b888..000000000
--- a/images/emoji/1f469-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f469-1f3fc.png b/images/emoji/1f469-1f3fc.png
deleted file mode 100644
index 0719c3780..000000000
--- a/images/emoji/1f469-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f469-1f3fd.png b/images/emoji/1f469-1f3fd.png
deleted file mode 100644
index b4d7f21f4..000000000
--- a/images/emoji/1f469-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f469-1f3fe.png b/images/emoji/1f469-1f3fe.png
deleted file mode 100644
index 6f21d631f..000000000
--- a/images/emoji/1f469-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f469-1f3ff.png b/images/emoji/1f469-1f3ff.png
deleted file mode 100644
index cd47bfdd6..000000000
--- a/images/emoji/1f469-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f469-1f469-1f466-1f466.png b/images/emoji/1f469-1f469-1f466-1f466.png
deleted file mode 100644
index e3fc2686e..000000000
--- a/images/emoji/1f469-1f469-1f466-1f466.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f469-1f469-1f466.png b/images/emoji/1f469-1f469-1f466.png
deleted file mode 100644
index 836feae7c..000000000
--- a/images/emoji/1f469-1f469-1f466.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f469-1f469-1f467-1f466.png b/images/emoji/1f469-1f469-1f467-1f466.png
deleted file mode 100644
index 284d29ab5..000000000
--- a/images/emoji/1f469-1f469-1f467-1f466.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f469-1f469-1f467-1f467.png b/images/emoji/1f469-1f469-1f467-1f467.png
deleted file mode 100644
index d8d3f49b8..000000000
--- a/images/emoji/1f469-1f469-1f467-1f467.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f469-1f469-1f467.png b/images/emoji/1f469-1f469-1f467.png
deleted file mode 100644
index d8619fa1f..000000000
--- a/images/emoji/1f469-1f469-1f467.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f469-2764-1f469.png b/images/emoji/1f469-2764-1f469.png
deleted file mode 100644
index 08fdabcdc..000000000
--- a/images/emoji/1f469-2764-1f469.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f469-2764-1f48b-1f469.png b/images/emoji/1f469-2764-1f48b-1f469.png
deleted file mode 100644
index 4905a5b3e..000000000
--- a/images/emoji/1f469-2764-1f48b-1f469.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f469.png b/images/emoji/1f469.png
deleted file mode 100644
index ece440e7a..000000000
--- a/images/emoji/1f469.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f46a.png b/images/emoji/1f46a.png
deleted file mode 100644
index 0350719a2..000000000
--- a/images/emoji/1f46a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f46b.png b/images/emoji/1f46b.png
deleted file mode 100644
index 73f22f0ad..000000000
--- a/images/emoji/1f46b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f46c.png b/images/emoji/1f46c.png
deleted file mode 100644
index a511fda82..000000000
--- a/images/emoji/1f46c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f46d.png b/images/emoji/1f46d.png
deleted file mode 100644
index 8623da423..000000000
--- a/images/emoji/1f46d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f46e-1f3fb.png b/images/emoji/1f46e-1f3fb.png
deleted file mode 100644
index 6ccba3879..000000000
--- a/images/emoji/1f46e-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f46e-1f3fc.png b/images/emoji/1f46e-1f3fc.png
deleted file mode 100644
index 7814ea9f5..000000000
--- a/images/emoji/1f46e-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f46e-1f3fd.png b/images/emoji/1f46e-1f3fd.png
deleted file mode 100644
index c29f0709b..000000000
--- a/images/emoji/1f46e-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f46e-1f3fe.png b/images/emoji/1f46e-1f3fe.png
deleted file mode 100644
index 8a009e55e..000000000
--- a/images/emoji/1f46e-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f46e-1f3ff.png b/images/emoji/1f46e-1f3ff.png
deleted file mode 100644
index 5bdc53c99..000000000
--- a/images/emoji/1f46e-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f46e.png b/images/emoji/1f46e.png
deleted file mode 100644
index bd37a787e..000000000
--- a/images/emoji/1f46e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f46f.png b/images/emoji/1f46f.png
deleted file mode 100644
index 7a33d199b..000000000
--- a/images/emoji/1f46f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f470-1f3fb.png b/images/emoji/1f470-1f3fb.png
deleted file mode 100644
index c4fb141ae..000000000
--- a/images/emoji/1f470-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f470-1f3fc.png b/images/emoji/1f470-1f3fc.png
deleted file mode 100644
index c248769fc..000000000
--- a/images/emoji/1f470-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f470-1f3fd.png b/images/emoji/1f470-1f3fd.png
deleted file mode 100644
index 962c0a6ee..000000000
--- a/images/emoji/1f470-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f470-1f3fe.png b/images/emoji/1f470-1f3fe.png
deleted file mode 100644
index 740ca208c..000000000
--- a/images/emoji/1f470-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f470-1f3ff.png b/images/emoji/1f470-1f3ff.png
deleted file mode 100644
index 5cc559858..000000000
--- a/images/emoji/1f470-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f470.png b/images/emoji/1f470.png
deleted file mode 100644
index eaf4bd978..000000000
--- a/images/emoji/1f470.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f471-1f3fb.png b/images/emoji/1f471-1f3fb.png
deleted file mode 100644
index 7d18ef244..000000000
--- a/images/emoji/1f471-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f471-1f3fc.png b/images/emoji/1f471-1f3fc.png
deleted file mode 100644
index dae130731..000000000
--- a/images/emoji/1f471-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f471-1f3fd.png b/images/emoji/1f471-1f3fd.png
deleted file mode 100644
index 684677e8e..000000000
--- a/images/emoji/1f471-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f471-1f3fe.png b/images/emoji/1f471-1f3fe.png
deleted file mode 100644
index 012be0b51..000000000
--- a/images/emoji/1f471-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f471-1f3ff.png b/images/emoji/1f471-1f3ff.png
deleted file mode 100644
index d4ecc4cf4..000000000
--- a/images/emoji/1f471-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f471.png b/images/emoji/1f471.png
deleted file mode 100644
index ad6f01a7d..000000000
--- a/images/emoji/1f471.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f472-1f3fb.png b/images/emoji/1f472-1f3fb.png
deleted file mode 100644
index 5b7b3def1..000000000
--- a/images/emoji/1f472-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f472-1f3fc.png b/images/emoji/1f472-1f3fc.png
deleted file mode 100644
index c8b9cf87f..000000000
--- a/images/emoji/1f472-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f472-1f3fd.png b/images/emoji/1f472-1f3fd.png
deleted file mode 100644
index effdd0c4c..000000000
--- a/images/emoji/1f472-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f472-1f3fe.png b/images/emoji/1f472-1f3fe.png
deleted file mode 100644
index f885ff46f..000000000
--- a/images/emoji/1f472-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f472-1f3ff.png b/images/emoji/1f472-1f3ff.png
deleted file mode 100644
index a6d55ca13..000000000
--- a/images/emoji/1f472-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f472.png b/images/emoji/1f472.png
deleted file mode 100644
index 7841e1360..000000000
--- a/images/emoji/1f472.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f473-1f3fb.png b/images/emoji/1f473-1f3fb.png
deleted file mode 100644
index 1e12ee4b2..000000000
--- a/images/emoji/1f473-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f473-1f3fc.png b/images/emoji/1f473-1f3fc.png
deleted file mode 100644
index 7fe9f01c6..000000000
--- a/images/emoji/1f473-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f473-1f3fd.png b/images/emoji/1f473-1f3fd.png
deleted file mode 100644
index f607afd34..000000000
--- a/images/emoji/1f473-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f473-1f3fe.png b/images/emoji/1f473-1f3fe.png
deleted file mode 100644
index c05695888..000000000
--- a/images/emoji/1f473-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f473-1f3ff.png b/images/emoji/1f473-1f3ff.png
deleted file mode 100644
index df935551c..000000000
--- a/images/emoji/1f473-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f473.png b/images/emoji/1f473.png
deleted file mode 100644
index 993fd952c..000000000
--- a/images/emoji/1f473.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f474-1f3fb.png b/images/emoji/1f474-1f3fb.png
deleted file mode 100644
index cd7d20789..000000000
--- a/images/emoji/1f474-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f474-1f3fc.png b/images/emoji/1f474-1f3fc.png
deleted file mode 100644
index 3574be8d4..000000000
--- a/images/emoji/1f474-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f474-1f3fd.png b/images/emoji/1f474-1f3fd.png
deleted file mode 100644
index bbd95afe0..000000000
--- a/images/emoji/1f474-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f474-1f3fe.png b/images/emoji/1f474-1f3fe.png
deleted file mode 100644
index b350a764b..000000000
--- a/images/emoji/1f474-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f474-1f3ff.png b/images/emoji/1f474-1f3ff.png
deleted file mode 100644
index 05fe24a17..000000000
--- a/images/emoji/1f474-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f474.png b/images/emoji/1f474.png
deleted file mode 100644
index 5f214571b..000000000
--- a/images/emoji/1f474.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f475-1f3fb.png b/images/emoji/1f475-1f3fb.png
deleted file mode 100644
index b49e82140..000000000
--- a/images/emoji/1f475-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f475-1f3fc.png b/images/emoji/1f475-1f3fc.png
deleted file mode 100644
index e86bf5ab3..000000000
--- a/images/emoji/1f475-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f475-1f3fd.png b/images/emoji/1f475-1f3fd.png
deleted file mode 100644
index 83fc14b08..000000000
--- a/images/emoji/1f475-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f475-1f3fe.png b/images/emoji/1f475-1f3fe.png
deleted file mode 100644
index ebbf7930f..000000000
--- a/images/emoji/1f475-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f475-1f3ff.png b/images/emoji/1f475-1f3ff.png
deleted file mode 100644
index 4009012bb..000000000
--- a/images/emoji/1f475-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f475.png b/images/emoji/1f475.png
deleted file mode 100644
index 52dc49871..000000000
--- a/images/emoji/1f475.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f476-1f3fb.png b/images/emoji/1f476-1f3fb.png
deleted file mode 100644
index 8c1cada59..000000000
--- a/images/emoji/1f476-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f476-1f3fc.png b/images/emoji/1f476-1f3fc.png
deleted file mode 100644
index 4ba95bd75..000000000
--- a/images/emoji/1f476-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f476-1f3fd.png b/images/emoji/1f476-1f3fd.png
deleted file mode 100644
index f4734c0dc..000000000
--- a/images/emoji/1f476-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f476-1f3fe.png b/images/emoji/1f476-1f3fe.png
deleted file mode 100644
index 02d864833..000000000
--- a/images/emoji/1f476-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f476-1f3ff.png b/images/emoji/1f476-1f3ff.png
deleted file mode 100644
index 0653e1603..000000000
--- a/images/emoji/1f476-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f476.png b/images/emoji/1f476.png
deleted file mode 100644
index 7b28ba891..000000000
--- a/images/emoji/1f476.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f477-1f3fb.png b/images/emoji/1f477-1f3fb.png
deleted file mode 100644
index 2f24a2bab..000000000
--- a/images/emoji/1f477-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f477-1f3fc.png b/images/emoji/1f477-1f3fc.png
deleted file mode 100644
index 93c8fec5a..000000000
--- a/images/emoji/1f477-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f477-1f3fd.png b/images/emoji/1f477-1f3fd.png
deleted file mode 100644
index abc1f2af2..000000000
--- a/images/emoji/1f477-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f477-1f3fe.png b/images/emoji/1f477-1f3fe.png
deleted file mode 100644
index eed83289a..000000000
--- a/images/emoji/1f477-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f477-1f3ff.png b/images/emoji/1f477-1f3ff.png
deleted file mode 100644
index acbb220b8..000000000
--- a/images/emoji/1f477-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f477.png b/images/emoji/1f477.png
deleted file mode 100644
index a9970a890..000000000
--- a/images/emoji/1f477.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f478-1f3fb.png b/images/emoji/1f478-1f3fb.png
deleted file mode 100644
index 7e4d850d1..000000000
--- a/images/emoji/1f478-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f478-1f3fc.png b/images/emoji/1f478-1f3fc.png
deleted file mode 100644
index 8179de403..000000000
--- a/images/emoji/1f478-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f478-1f3fd.png b/images/emoji/1f478-1f3fd.png
deleted file mode 100644
index de04809d1..000000000
--- a/images/emoji/1f478-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f478-1f3fe.png b/images/emoji/1f478-1f3fe.png
deleted file mode 100644
index c71e69caa..000000000
--- a/images/emoji/1f478-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f478-1f3ff.png b/images/emoji/1f478-1f3ff.png
deleted file mode 100644
index 063e26459..000000000
--- a/images/emoji/1f478-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f478.png b/images/emoji/1f478.png
deleted file mode 100644
index a9958dfff..000000000
--- a/images/emoji/1f478.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f479.png b/images/emoji/1f479.png
deleted file mode 100644
index fe8670fda..000000000
--- a/images/emoji/1f479.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f47a.png b/images/emoji/1f47a.png
deleted file mode 100644
index e2ffb0c19..000000000
--- a/images/emoji/1f47a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f47b.png b/images/emoji/1f47b.png
deleted file mode 100644
index d22b1ccba..000000000
--- a/images/emoji/1f47b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f47c-1f3fb.png b/images/emoji/1f47c-1f3fb.png
deleted file mode 100644
index 391694dc0..000000000
--- a/images/emoji/1f47c-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f47c-1f3fc.png b/images/emoji/1f47c-1f3fc.png
deleted file mode 100644
index 700cbe6ed..000000000
--- a/images/emoji/1f47c-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f47c-1f3fd.png b/images/emoji/1f47c-1f3fd.png
deleted file mode 100644
index be597437d..000000000
--- a/images/emoji/1f47c-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f47c-1f3fe.png b/images/emoji/1f47c-1f3fe.png
deleted file mode 100644
index b06d3c853..000000000
--- a/images/emoji/1f47c-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f47c-1f3ff.png b/images/emoji/1f47c-1f3ff.png
deleted file mode 100644
index 17bd677e3..000000000
--- a/images/emoji/1f47c-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f47c.png b/images/emoji/1f47c.png
deleted file mode 100644
index 66ea97a3b..000000000
--- a/images/emoji/1f47c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f47d.png b/images/emoji/1f47d.png
deleted file mode 100644
index 3b90e9743..000000000
--- a/images/emoji/1f47d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f47e.png b/images/emoji/1f47e.png
deleted file mode 100644
index 2e73f5f32..000000000
--- a/images/emoji/1f47e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f47f.png b/images/emoji/1f47f.png
deleted file mode 100644
index 83b68e404..000000000
--- a/images/emoji/1f47f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f480.png b/images/emoji/1f480.png
deleted file mode 100644
index 26abb1729..000000000
--- a/images/emoji/1f480.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f481-1f3fb.png b/images/emoji/1f481-1f3fb.png
deleted file mode 100644
index 3d9e22479..000000000
--- a/images/emoji/1f481-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f481-1f3fc.png b/images/emoji/1f481-1f3fc.png
deleted file mode 100644
index 7853bc60a..000000000
--- a/images/emoji/1f481-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f481-1f3fd.png b/images/emoji/1f481-1f3fd.png
deleted file mode 100644
index 307514eab..000000000
--- a/images/emoji/1f481-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f481-1f3fe.png b/images/emoji/1f481-1f3fe.png
deleted file mode 100644
index 95cc7ff36..000000000
--- a/images/emoji/1f481-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f481-1f3ff.png b/images/emoji/1f481-1f3ff.png
deleted file mode 100644
index 26f8f22b2..000000000
--- a/images/emoji/1f481-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f481.png b/images/emoji/1f481.png
deleted file mode 100644
index 328cfb316..000000000
--- a/images/emoji/1f481.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f482-1f3fb.png b/images/emoji/1f482-1f3fb.png
deleted file mode 100644
index cea9ba274..000000000
--- a/images/emoji/1f482-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f482-1f3fc.png b/images/emoji/1f482-1f3fc.png
deleted file mode 100644
index c8c3c6444..000000000
--- a/images/emoji/1f482-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f482-1f3fd.png b/images/emoji/1f482-1f3fd.png
deleted file mode 100644
index 29d9fc477..000000000
--- a/images/emoji/1f482-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f482-1f3fe.png b/images/emoji/1f482-1f3fe.png
deleted file mode 100644
index 85fcf9a3b..000000000
--- a/images/emoji/1f482-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f482-1f3ff.png b/images/emoji/1f482-1f3ff.png
deleted file mode 100644
index b140a2d23..000000000
--- a/images/emoji/1f482-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f482.png b/images/emoji/1f482.png
deleted file mode 100644
index 8d7ab3c47..000000000
--- a/images/emoji/1f482.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f483-1f3fb.png b/images/emoji/1f483-1f3fb.png
deleted file mode 100644
index 27975615e..000000000
--- a/images/emoji/1f483-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f483-1f3fc.png b/images/emoji/1f483-1f3fc.png
deleted file mode 100644
index cb04b1f90..000000000
--- a/images/emoji/1f483-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f483-1f3fd.png b/images/emoji/1f483-1f3fd.png
deleted file mode 100644
index 98c5bca7b..000000000
--- a/images/emoji/1f483-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f483-1f3fe.png b/images/emoji/1f483-1f3fe.png
deleted file mode 100644
index fdb1e00cb..000000000
--- a/images/emoji/1f483-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f483-1f3ff.png b/images/emoji/1f483-1f3ff.png
deleted file mode 100644
index 0e34e0e23..000000000
--- a/images/emoji/1f483-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f483.png b/images/emoji/1f483.png
deleted file mode 100644
index d1cdad8dd..000000000
--- a/images/emoji/1f483.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f484.png b/images/emoji/1f484.png
deleted file mode 100644
index 61a0c084c..000000000
--- a/images/emoji/1f484.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f485-1f3fb.png b/images/emoji/1f485-1f3fb.png
deleted file mode 100644
index f1fbfcf52..000000000
--- a/images/emoji/1f485-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f485-1f3fc.png b/images/emoji/1f485-1f3fc.png
deleted file mode 100644
index 02b836b2f..000000000
--- a/images/emoji/1f485-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f485-1f3fd.png b/images/emoji/1f485-1f3fd.png
deleted file mode 100644
index 7432e3cf2..000000000
--- a/images/emoji/1f485-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f485-1f3fe.png b/images/emoji/1f485-1f3fe.png
deleted file mode 100644
index e4272692c..000000000
--- a/images/emoji/1f485-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f485-1f3ff.png b/images/emoji/1f485-1f3ff.png
deleted file mode 100644
index d29e1c553..000000000
--- a/images/emoji/1f485-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f485.png b/images/emoji/1f485.png
deleted file mode 100644
index aa52af705..000000000
--- a/images/emoji/1f485.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f486-1f3fb.png b/images/emoji/1f486-1f3fb.png
deleted file mode 100644
index f9dea75f3..000000000
--- a/images/emoji/1f486-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f486-1f3fc.png b/images/emoji/1f486-1f3fc.png
deleted file mode 100644
index 0bb244a27..000000000
--- a/images/emoji/1f486-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f486-1f3fd.png b/images/emoji/1f486-1f3fd.png
deleted file mode 100644
index 06941c86b..000000000
--- a/images/emoji/1f486-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f486-1f3fe.png b/images/emoji/1f486-1f3fe.png
deleted file mode 100644
index 671d52310..000000000
--- a/images/emoji/1f486-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f486-1f3ff.png b/images/emoji/1f486-1f3ff.png
deleted file mode 100644
index 6a388c0d0..000000000
--- a/images/emoji/1f486-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f486.png b/images/emoji/1f486.png
deleted file mode 100644
index 9ed04ff13..000000000
--- a/images/emoji/1f486.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f487-1f3fb.png b/images/emoji/1f487-1f3fb.png
deleted file mode 100644
index c743b74ab..000000000
--- a/images/emoji/1f487-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f487-1f3fc.png b/images/emoji/1f487-1f3fc.png
deleted file mode 100644
index dbbddcb34..000000000
--- a/images/emoji/1f487-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f487-1f3fd.png b/images/emoji/1f487-1f3fd.png
deleted file mode 100644
index d5ad19563..000000000
--- a/images/emoji/1f487-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f487-1f3fe.png b/images/emoji/1f487-1f3fe.png
deleted file mode 100644
index 244fd3af0..000000000
--- a/images/emoji/1f487-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f487-1f3ff.png b/images/emoji/1f487-1f3ff.png
deleted file mode 100644
index 20a94a886..000000000
--- a/images/emoji/1f487-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f487.png b/images/emoji/1f487.png
deleted file mode 100644
index 91266b129..000000000
--- a/images/emoji/1f487.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f488.png b/images/emoji/1f488.png
deleted file mode 100644
index 896f4d716..000000000
--- a/images/emoji/1f488.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f489.png b/images/emoji/1f489.png
deleted file mode 100644
index 71c1a9528..000000000
--- a/images/emoji/1f489.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f48a.png b/images/emoji/1f48a.png
deleted file mode 100644
index 1d4530e77..000000000
--- a/images/emoji/1f48a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f48c.png b/images/emoji/1f48c.png
deleted file mode 100644
index 3c3c767e7..000000000
--- a/images/emoji/1f48c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f48d.png b/images/emoji/1f48d.png
deleted file mode 100644
index 87d227adb..000000000
--- a/images/emoji/1f48d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f48e.png b/images/emoji/1f48e.png
deleted file mode 100644
index db122d26a..000000000
--- a/images/emoji/1f48e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f48f.png b/images/emoji/1f48f.png
deleted file mode 100644
index 9aa519da9..000000000
--- a/images/emoji/1f48f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f490.png b/images/emoji/1f490.png
deleted file mode 100644
index 11455af6d..000000000
--- a/images/emoji/1f490.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f491.png b/images/emoji/1f491.png
deleted file mode 100644
index 62111601b..000000000
--- a/images/emoji/1f491.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f492.png b/images/emoji/1f492.png
deleted file mode 100644
index d0d8aa0bf..000000000
--- a/images/emoji/1f492.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f493.png b/images/emoji/1f493.png
deleted file mode 100644
index 0bcf2d1d5..000000000
--- a/images/emoji/1f493.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f494.png b/images/emoji/1f494.png
deleted file mode 100644
index 718e26ee1..000000000
--- a/images/emoji/1f494.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f495.png b/images/emoji/1f495.png
deleted file mode 100644
index 4d8c33860..000000000
--- a/images/emoji/1f495.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f496.png b/images/emoji/1f496.png
deleted file mode 100644
index 670926945..000000000
--- a/images/emoji/1f496.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f497.png b/images/emoji/1f497.png
deleted file mode 100644
index d6e694e97..000000000
--- a/images/emoji/1f497.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f498.png b/images/emoji/1f498.png
deleted file mode 100644
index 2df0078dd..000000000
--- a/images/emoji/1f498.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f499.png b/images/emoji/1f499.png
deleted file mode 100644
index bdf1287e5..000000000
--- a/images/emoji/1f499.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f49a.png b/images/emoji/1f49a.png
deleted file mode 100644
index c52d60a58..000000000
--- a/images/emoji/1f49a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f49b.png b/images/emoji/1f49b.png
deleted file mode 100644
index 7901a9d01..000000000
--- a/images/emoji/1f49b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f49c.png b/images/emoji/1f49c.png
deleted file mode 100644
index 95c53a9ad..000000000
--- a/images/emoji/1f49c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f49d.png b/images/emoji/1f49d.png
deleted file mode 100644
index 902ceafe4..000000000
--- a/images/emoji/1f49d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f49e.png b/images/emoji/1f49e.png
deleted file mode 100644
index 7b9d1948f..000000000
--- a/images/emoji/1f49e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f49f.png b/images/emoji/1f49f.png
deleted file mode 100644
index 5443f60bc..000000000
--- a/images/emoji/1f49f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4a0.png b/images/emoji/1f4a0.png
deleted file mode 100644
index 2a22a26d1..000000000
--- a/images/emoji/1f4a0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4a1.png b/images/emoji/1f4a1.png
deleted file mode 100644
index 38e32e02d..000000000
--- a/images/emoji/1f4a1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4a2.png b/images/emoji/1f4a2.png
deleted file mode 100644
index d63c2e000..000000000
--- a/images/emoji/1f4a2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4a3.png b/images/emoji/1f4a3.png
deleted file mode 100644
index c7f8f81c9..000000000
--- a/images/emoji/1f4a3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4a4.png b/images/emoji/1f4a4.png
deleted file mode 100644
index 9bc72b446..000000000
--- a/images/emoji/1f4a4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4a5.png b/images/emoji/1f4a5.png
deleted file mode 100644
index 9b0f027b1..000000000
--- a/images/emoji/1f4a5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4a6.png b/images/emoji/1f4a6.png
deleted file mode 100644
index 4106117eb..000000000
--- a/images/emoji/1f4a6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4a7.png b/images/emoji/1f4a7.png
deleted file mode 100644
index 71241ec30..000000000
--- a/images/emoji/1f4a7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4a8.png b/images/emoji/1f4a8.png
deleted file mode 100644
index 064b8525c..000000000
--- a/images/emoji/1f4a8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4a9.png b/images/emoji/1f4a9.png
deleted file mode 100644
index 10b15e72d..000000000
--- a/images/emoji/1f4a9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4aa-1f3fb.png b/images/emoji/1f4aa-1f3fb.png
deleted file mode 100644
index 1522942ce..000000000
--- a/images/emoji/1f4aa-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4aa-1f3fc.png b/images/emoji/1f4aa-1f3fc.png
deleted file mode 100644
index 569c6e832..000000000
--- a/images/emoji/1f4aa-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4aa-1f3fd.png b/images/emoji/1f4aa-1f3fd.png
deleted file mode 100644
index 0a76b00fa..000000000
--- a/images/emoji/1f4aa-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4aa-1f3fe.png b/images/emoji/1f4aa-1f3fe.png
deleted file mode 100644
index f0cf31328..000000000
--- a/images/emoji/1f4aa-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4aa-1f3ff.png b/images/emoji/1f4aa-1f3ff.png
deleted file mode 100644
index 4fda92460..000000000
--- a/images/emoji/1f4aa-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4aa.png b/images/emoji/1f4aa.png
deleted file mode 100644
index 7e67c1880..000000000
--- a/images/emoji/1f4aa.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4ab.png b/images/emoji/1f4ab.png
deleted file mode 100644
index 85f52efad..000000000
--- a/images/emoji/1f4ab.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4ac.png b/images/emoji/1f4ac.png
deleted file mode 100644
index a34ef7417..000000000
--- a/images/emoji/1f4ac.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4ad.png b/images/emoji/1f4ad.png
deleted file mode 100644
index 72fe8fa70..000000000
--- a/images/emoji/1f4ad.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4ae.png b/images/emoji/1f4ae.png
deleted file mode 100644
index d6af8b600..000000000
--- a/images/emoji/1f4ae.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4af.png b/images/emoji/1f4af.png
deleted file mode 100644
index 6903ff030..000000000
--- a/images/emoji/1f4af.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4b0.png b/images/emoji/1f4b0.png
deleted file mode 100644
index b9296be09..000000000
--- a/images/emoji/1f4b0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4b1.png b/images/emoji/1f4b1.png
deleted file mode 100644
index 4d46c6050..000000000
--- a/images/emoji/1f4b1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4b2.png b/images/emoji/1f4b2.png
deleted file mode 100644
index ef2c2e205..000000000
--- a/images/emoji/1f4b2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4b3.png b/images/emoji/1f4b3.png
deleted file mode 100644
index 372777d5c..000000000
--- a/images/emoji/1f4b3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4b4.png b/images/emoji/1f4b4.png
deleted file mode 100644
index 63ee4799d..000000000
--- a/images/emoji/1f4b4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4b5.png b/images/emoji/1f4b5.png
deleted file mode 100644
index a9904c282..000000000
--- a/images/emoji/1f4b5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4b6.png b/images/emoji/1f4b6.png
deleted file mode 100644
index a49020820..000000000
--- a/images/emoji/1f4b6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4b7.png b/images/emoji/1f4b7.png
deleted file mode 100644
index a0d4c4099..000000000
--- a/images/emoji/1f4b7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4b8.png b/images/emoji/1f4b8.png
deleted file mode 100644
index f022b04b3..000000000
--- a/images/emoji/1f4b8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4b9.png b/images/emoji/1f4b9.png
deleted file mode 100644
index 9773f03be..000000000
--- a/images/emoji/1f4b9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4ba.png b/images/emoji/1f4ba.png
deleted file mode 100644
index a6d72d95a..000000000
--- a/images/emoji/1f4ba.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4bb.png b/images/emoji/1f4bb.png
deleted file mode 100644
index c1fee27e3..000000000
--- a/images/emoji/1f4bb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4bc.png b/images/emoji/1f4bc.png
deleted file mode 100644
index b9912ba21..000000000
--- a/images/emoji/1f4bc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4bd.png b/images/emoji/1f4bd.png
deleted file mode 100644
index 9fa94cfbe..000000000
--- a/images/emoji/1f4bd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4be.png b/images/emoji/1f4be.png
deleted file mode 100644
index 072a76d3c..000000000
--- a/images/emoji/1f4be.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4bf.png b/images/emoji/1f4bf.png
deleted file mode 100644
index e6b01449c..000000000
--- a/images/emoji/1f4bf.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4c0.png b/images/emoji/1f4c0.png
deleted file mode 100644
index 045a6f7a0..000000000
--- a/images/emoji/1f4c0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4c1.png b/images/emoji/1f4c1.png
deleted file mode 100644
index addedaf08..000000000
--- a/images/emoji/1f4c1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4c2.png b/images/emoji/1f4c2.png
deleted file mode 100644
index 3993b0922..000000000
--- a/images/emoji/1f4c2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4c3.png b/images/emoji/1f4c3.png
deleted file mode 100644
index 06355319c..000000000
--- a/images/emoji/1f4c3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4c4.png b/images/emoji/1f4c4.png
deleted file mode 100644
index ba4ed757e..000000000
--- a/images/emoji/1f4c4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4c5.png b/images/emoji/1f4c5.png
deleted file mode 100644
index f05b3da97..000000000
--- a/images/emoji/1f4c5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4c6.png b/images/emoji/1f4c6.png
deleted file mode 100644
index 47353b744..000000000
--- a/images/emoji/1f4c6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4c7.png b/images/emoji/1f4c7.png
deleted file mode 100644
index 151e11cb3..000000000
--- a/images/emoji/1f4c7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4c8.png b/images/emoji/1f4c8.png
deleted file mode 100644
index f13cfcf99..000000000
--- a/images/emoji/1f4c8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4c9.png b/images/emoji/1f4c9.png
deleted file mode 100644
index 5222ec72d..000000000
--- a/images/emoji/1f4c9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4ca.png b/images/emoji/1f4ca.png
deleted file mode 100644
index 53c894550..000000000
--- a/images/emoji/1f4ca.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4cb.png b/images/emoji/1f4cb.png
deleted file mode 100644
index ffd5b315d..000000000
--- a/images/emoji/1f4cb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4cc.png b/images/emoji/1f4cc.png
deleted file mode 100644
index 57e07d7f4..000000000
--- a/images/emoji/1f4cc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4cd.png b/images/emoji/1f4cd.png
deleted file mode 100644
index 28b9d7286..000000000
--- a/images/emoji/1f4cd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4ce.png b/images/emoji/1f4ce.png
deleted file mode 100644
index 8cd8d4f87..000000000
--- a/images/emoji/1f4ce.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4cf.png b/images/emoji/1f4cf.png
deleted file mode 100644
index 1017b7433..000000000
--- a/images/emoji/1f4cf.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4d0.png b/images/emoji/1f4d0.png
deleted file mode 100644
index 77dee9ee8..000000000
--- a/images/emoji/1f4d0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4d1.png b/images/emoji/1f4d1.png
deleted file mode 100644
index 23a3083ad..000000000
--- a/images/emoji/1f4d1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4d2.png b/images/emoji/1f4d2.png
deleted file mode 100644
index ef0ea3b1f..000000000
--- a/images/emoji/1f4d2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4d3.png b/images/emoji/1f4d3.png
deleted file mode 100644
index f6c28b491..000000000
--- a/images/emoji/1f4d3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4d4.png b/images/emoji/1f4d4.png
deleted file mode 100644
index 03f566b6d..000000000
--- a/images/emoji/1f4d4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4d5.png b/images/emoji/1f4d5.png
deleted file mode 100644
index 6395cf215..000000000
--- a/images/emoji/1f4d5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4d6.png b/images/emoji/1f4d6.png
deleted file mode 100644
index 0f4447ed3..000000000
--- a/images/emoji/1f4d6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4d7.png b/images/emoji/1f4d7.png
deleted file mode 100644
index e5e411cf3..000000000
--- a/images/emoji/1f4d7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4d8.png b/images/emoji/1f4d8.png
deleted file mode 100644
index d73dfd725..000000000
--- a/images/emoji/1f4d8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4d9.png b/images/emoji/1f4d9.png
deleted file mode 100644
index ab40e6ae6..000000000
--- a/images/emoji/1f4d9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4da.png b/images/emoji/1f4da.png
deleted file mode 100644
index 59a8bafeb..000000000
--- a/images/emoji/1f4da.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4db.png b/images/emoji/1f4db.png
deleted file mode 100644
index ec5ee213e..000000000
--- a/images/emoji/1f4db.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4dc.png b/images/emoji/1f4dc.png
deleted file mode 100644
index 50ee5dcd4..000000000
--- a/images/emoji/1f4dc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4dd.png b/images/emoji/1f4dd.png
deleted file mode 100644
index 9e44f60f4..000000000
--- a/images/emoji/1f4dd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4de.png b/images/emoji/1f4de.png
deleted file mode 100644
index 69388316c..000000000
--- a/images/emoji/1f4de.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4df.png b/images/emoji/1f4df.png
deleted file mode 100644
index b24b99306..000000000
--- a/images/emoji/1f4df.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4e0.png b/images/emoji/1f4e0.png
deleted file mode 100644
index 6f929e294..000000000
--- a/images/emoji/1f4e0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4e1.png b/images/emoji/1f4e1.png
deleted file mode 100644
index db0372795..000000000
--- a/images/emoji/1f4e1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4e2.png b/images/emoji/1f4e2.png
deleted file mode 100644
index 5fd76a95b..000000000
--- a/images/emoji/1f4e2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4e3.png b/images/emoji/1f4e3.png
deleted file mode 100644
index 4e6735188..000000000
--- a/images/emoji/1f4e3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4e4.png b/images/emoji/1f4e4.png
deleted file mode 100644
index 46493ed5b..000000000
--- a/images/emoji/1f4e4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4e5.png b/images/emoji/1f4e5.png
deleted file mode 100644
index 41a6be2b0..000000000
--- a/images/emoji/1f4e5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4e6.png b/images/emoji/1f4e6.png
deleted file mode 100644
index 85431756a..000000000
--- a/images/emoji/1f4e6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4e7.png b/images/emoji/1f4e7.png
deleted file mode 100644
index d22e654a2..000000000
--- a/images/emoji/1f4e7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4e8.png b/images/emoji/1f4e8.png
deleted file mode 100644
index fd22e8818..000000000
--- a/images/emoji/1f4e8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4e9.png b/images/emoji/1f4e9.png
deleted file mode 100644
index 7448a6b76..000000000
--- a/images/emoji/1f4e9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4ea.png b/images/emoji/1f4ea.png
deleted file mode 100644
index ddc705db0..000000000
--- a/images/emoji/1f4ea.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4eb.png b/images/emoji/1f4eb.png
deleted file mode 100644
index ef5174e40..000000000
--- a/images/emoji/1f4eb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4ec.png b/images/emoji/1f4ec.png
deleted file mode 100644
index 5460616a5..000000000
--- a/images/emoji/1f4ec.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4ed.png b/images/emoji/1f4ed.png
deleted file mode 100644
index f9aeee6b1..000000000
--- a/images/emoji/1f4ed.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4ee.png b/images/emoji/1f4ee.png
deleted file mode 100644
index 07c9c4ab3..000000000
--- a/images/emoji/1f4ee.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4ef.png b/images/emoji/1f4ef.png
deleted file mode 100644
index c173b8dbd..000000000
--- a/images/emoji/1f4ef.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4f0.png b/images/emoji/1f4f0.png
deleted file mode 100644
index 2aa8f060b..000000000
--- a/images/emoji/1f4f0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4f1.png b/images/emoji/1f4f1.png
deleted file mode 100644
index fd377acf8..000000000
--- a/images/emoji/1f4f1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4f2.png b/images/emoji/1f4f2.png
deleted file mode 100644
index e2f308f8e..000000000
--- a/images/emoji/1f4f2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4f3.png b/images/emoji/1f4f3.png
deleted file mode 100644
index cc46510e4..000000000
--- a/images/emoji/1f4f3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4f4.png b/images/emoji/1f4f4.png
deleted file mode 100644
index 8b661ec1c..000000000
--- a/images/emoji/1f4f4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4f5.png b/images/emoji/1f4f5.png
deleted file mode 100644
index 7b1ae6ea5..000000000
--- a/images/emoji/1f4f5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4f6.png b/images/emoji/1f4f6.png
deleted file mode 100644
index ee2b5a4b5..000000000
--- a/images/emoji/1f4f6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4f7.png b/images/emoji/1f4f7.png
deleted file mode 100644
index 0a3429f72..000000000
--- a/images/emoji/1f4f7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4f8.png b/images/emoji/1f4f8.png
deleted file mode 100644
index 27471da20..000000000
--- a/images/emoji/1f4f8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4f9.png b/images/emoji/1f4f9.png
deleted file mode 100644
index 8008d1414..000000000
--- a/images/emoji/1f4f9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4fa.png b/images/emoji/1f4fa.png
deleted file mode 100644
index 999f1fb5c..000000000
--- a/images/emoji/1f4fa.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4fb.png b/images/emoji/1f4fb.png
deleted file mode 100644
index dec381fa2..000000000
--- a/images/emoji/1f4fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4fc.png b/images/emoji/1f4fc.png
deleted file mode 100644
index b9eb78ecd..000000000
--- a/images/emoji/1f4fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4fd.png b/images/emoji/1f4fd.png
deleted file mode 100644
index ce9ab0daa..000000000
--- a/images/emoji/1f4fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f4ff.png b/images/emoji/1f4ff.png
deleted file mode 100644
index a4b6dfcc6..000000000
--- a/images/emoji/1f4ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f500.png b/images/emoji/1f500.png
deleted file mode 100644
index 5904badde..000000000
--- a/images/emoji/1f500.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f501.png b/images/emoji/1f501.png
deleted file mode 100644
index 540ce4e0f..000000000
--- a/images/emoji/1f501.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f502.png b/images/emoji/1f502.png
deleted file mode 100644
index 9567e8333..000000000
--- a/images/emoji/1f502.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f503.png b/images/emoji/1f503.png
deleted file mode 100644
index 26e49c383..000000000
--- a/images/emoji/1f503.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f504.png b/images/emoji/1f504.png
deleted file mode 100644
index 8d06d8e09..000000000
--- a/images/emoji/1f504.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f505.png b/images/emoji/1f505.png
deleted file mode 100644
index 543011d39..000000000
--- a/images/emoji/1f505.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f506.png b/images/emoji/1f506.png
deleted file mode 100644
index c41f2d5fd..000000000
--- a/images/emoji/1f506.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f507.png b/images/emoji/1f507.png
deleted file mode 100644
index 7c1788e50..000000000
--- a/images/emoji/1f507.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f508.png b/images/emoji/1f508.png
deleted file mode 100644
index 7bcffb8fc..000000000
--- a/images/emoji/1f508.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f509.png b/images/emoji/1f509.png
deleted file mode 100644
index e75ddca53..000000000
--- a/images/emoji/1f509.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f50a.png b/images/emoji/1f50a.png
deleted file mode 100644
index 8370033a5..000000000
--- a/images/emoji/1f50a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f50b.png b/images/emoji/1f50b.png
deleted file mode 100644
index f593e2bdb..000000000
--- a/images/emoji/1f50b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f50c.png b/images/emoji/1f50c.png
deleted file mode 100644
index 31d1eb215..000000000
--- a/images/emoji/1f50c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f50d.png b/images/emoji/1f50d.png
deleted file mode 100644
index 55487156a..000000000
--- a/images/emoji/1f50d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f50e.png b/images/emoji/1f50e.png
deleted file mode 100644
index 0f4b1bca8..000000000
--- a/images/emoji/1f50e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f50f.png b/images/emoji/1f50f.png
deleted file mode 100644
index 19a07d162..000000000
--- a/images/emoji/1f50f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f510.png b/images/emoji/1f510.png
deleted file mode 100644
index 1c1cd5d07..000000000
--- a/images/emoji/1f510.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f511.png b/images/emoji/1f511.png
deleted file mode 100644
index 319cd1b88..000000000
--- a/images/emoji/1f511.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f512.png b/images/emoji/1f512.png
deleted file mode 100644
index 5a739c466..000000000
--- a/images/emoji/1f512.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f513.png b/images/emoji/1f513.png
deleted file mode 100644
index 4a74a6939..000000000
--- a/images/emoji/1f513.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f514.png b/images/emoji/1f514.png
deleted file mode 100644
index 776f4fdd0..000000000
--- a/images/emoji/1f514.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f515.png b/images/emoji/1f515.png
deleted file mode 100644
index 15cb38dd1..000000000
--- a/images/emoji/1f515.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f516.png b/images/emoji/1f516.png
deleted file mode 100644
index bbb444611..000000000
--- a/images/emoji/1f516.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f517.png b/images/emoji/1f517.png
deleted file mode 100644
index ae20f0f8e..000000000
--- a/images/emoji/1f517.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f518.png b/images/emoji/1f518.png
deleted file mode 100644
index 3a23449d9..000000000
--- a/images/emoji/1f518.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f519.png b/images/emoji/1f519.png
deleted file mode 100644
index d32c5d4f1..000000000
--- a/images/emoji/1f519.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f51a.png b/images/emoji/1f51a.png
deleted file mode 100644
index ef3ccd5f3..000000000
--- a/images/emoji/1f51a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f51b.png b/images/emoji/1f51b.png
deleted file mode 100644
index a0c371ae2..000000000
--- a/images/emoji/1f51b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f51c.png b/images/emoji/1f51c.png
deleted file mode 100644
index 8cdfd8669..000000000
--- a/images/emoji/1f51c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f51d.png b/images/emoji/1f51d.png
deleted file mode 100644
index 49dea8c08..000000000
--- a/images/emoji/1f51d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f51e.png b/images/emoji/1f51e.png
deleted file mode 100644
index 6dfe6da51..000000000
--- a/images/emoji/1f51e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f51f.png b/images/emoji/1f51f.png
deleted file mode 100644
index 782d40049..000000000
--- a/images/emoji/1f51f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f520.png b/images/emoji/1f520.png
deleted file mode 100644
index fe9482d2d..000000000
--- a/images/emoji/1f520.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f521.png b/images/emoji/1f521.png
deleted file mode 100644
index 0996a8705..000000000
--- a/images/emoji/1f521.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f522.png b/images/emoji/1f522.png
deleted file mode 100644
index 248dc7e55..000000000
--- a/images/emoji/1f522.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f523.png b/images/emoji/1f523.png
deleted file mode 100644
index ac2fc1f35..000000000
--- a/images/emoji/1f523.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f524.png b/images/emoji/1f524.png
deleted file mode 100644
index 7688de692..000000000
--- a/images/emoji/1f524.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f525.png b/images/emoji/1f525.png
deleted file mode 100644
index bd3775a46..000000000
--- a/images/emoji/1f525.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f526.png b/images/emoji/1f526.png
deleted file mode 100644
index eee36c250..000000000
--- a/images/emoji/1f526.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f527.png b/images/emoji/1f527.png
deleted file mode 100644
index c16b74396..000000000
--- a/images/emoji/1f527.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f528.png b/images/emoji/1f528.png
deleted file mode 100644
index 00736cce4..000000000
--- a/images/emoji/1f528.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f529.png b/images/emoji/1f529.png
deleted file mode 100644
index 4b9ae1553..000000000
--- a/images/emoji/1f529.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f52a.png b/images/emoji/1f52a.png
deleted file mode 100644
index 1acb9f307..000000000
--- a/images/emoji/1f52a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f52b.png b/images/emoji/1f52b.png
deleted file mode 100644
index 89c5c244c..000000000
--- a/images/emoji/1f52b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f52c.png b/images/emoji/1f52c.png
deleted file mode 100644
index 90f5acf6a..000000000
--- a/images/emoji/1f52c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f52d.png b/images/emoji/1f52d.png
deleted file mode 100644
index d63154614..000000000
--- a/images/emoji/1f52d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f52e.png b/images/emoji/1f52e.png
deleted file mode 100644
index 54334c18b..000000000
--- a/images/emoji/1f52e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f52f.png b/images/emoji/1f52f.png
deleted file mode 100644
index 2eb170745..000000000
--- a/images/emoji/1f52f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f530.png b/images/emoji/1f530.png
deleted file mode 100644
index bc434fb7c..000000000
--- a/images/emoji/1f530.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f531.png b/images/emoji/1f531.png
deleted file mode 100644
index 777a1dad1..000000000
--- a/images/emoji/1f531.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f532.png b/images/emoji/1f532.png
deleted file mode 100644
index a78fc2f6b..000000000
--- a/images/emoji/1f532.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f533.png b/images/emoji/1f533.png
deleted file mode 100644
index 934b1cedf..000000000
--- a/images/emoji/1f533.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f534.png b/images/emoji/1f534.png
deleted file mode 100644
index 4bef930d9..000000000
--- a/images/emoji/1f534.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f535.png b/images/emoji/1f535.png
deleted file mode 100644
index 84078ef31..000000000
--- a/images/emoji/1f535.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f536.png b/images/emoji/1f536.png
deleted file mode 100644
index 73ff0ac36..000000000
--- a/images/emoji/1f536.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f537.png b/images/emoji/1f537.png
deleted file mode 100644
index 416a58bd5..000000000
--- a/images/emoji/1f537.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f538.png b/images/emoji/1f538.png
deleted file mode 100644
index e1c6ed9b2..000000000
--- a/images/emoji/1f538.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f539.png b/images/emoji/1f539.png
deleted file mode 100644
index b86b5bc4d..000000000
--- a/images/emoji/1f539.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f53a.png b/images/emoji/1f53a.png
deleted file mode 100644
index 785887c19..000000000
--- a/images/emoji/1f53a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f53b.png b/images/emoji/1f53b.png
deleted file mode 100644
index a83beff19..000000000
--- a/images/emoji/1f53b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f53c.png b/images/emoji/1f53c.png
deleted file mode 100644
index 20a13dcd5..000000000
--- a/images/emoji/1f53c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f53d.png b/images/emoji/1f53d.png
deleted file mode 100644
index 5870b9a22..000000000
--- a/images/emoji/1f53d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f549.png b/images/emoji/1f549.png
deleted file mode 100644
index a35c63c45..000000000
--- a/images/emoji/1f549.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f54a.png b/images/emoji/1f54a.png
deleted file mode 100644
index 9580c4917..000000000
--- a/images/emoji/1f54a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f54b.png b/images/emoji/1f54b.png
deleted file mode 100644
index 1778c1138..000000000
--- a/images/emoji/1f54b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f54c.png b/images/emoji/1f54c.png
deleted file mode 100644
index ef770b26d..000000000
--- a/images/emoji/1f54c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f54d.png b/images/emoji/1f54d.png
deleted file mode 100644
index ee347904c..000000000
--- a/images/emoji/1f54d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f54e.png b/images/emoji/1f54e.png
deleted file mode 100644
index b42973628..000000000
--- a/images/emoji/1f54e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f550.png b/images/emoji/1f550.png
deleted file mode 100644
index d6e34941f..000000000
--- a/images/emoji/1f550.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f551.png b/images/emoji/1f551.png
deleted file mode 100644
index a54253d7d..000000000
--- a/images/emoji/1f551.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f552.png b/images/emoji/1f552.png
deleted file mode 100644
index 27ec4b1f5..000000000
--- a/images/emoji/1f552.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f553.png b/images/emoji/1f553.png
deleted file mode 100644
index 60a1ef4cc..000000000
--- a/images/emoji/1f553.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f554.png b/images/emoji/1f554.png
deleted file mode 100644
index c9382d1e0..000000000
--- a/images/emoji/1f554.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f555.png b/images/emoji/1f555.png
deleted file mode 100644
index 8fd5d3f5b..000000000
--- a/images/emoji/1f555.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f556.png b/images/emoji/1f556.png
deleted file mode 100644
index 8c7084036..000000000
--- a/images/emoji/1f556.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f557.png b/images/emoji/1f557.png
deleted file mode 100644
index fcddf722e..000000000
--- a/images/emoji/1f557.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f558.png b/images/emoji/1f558.png
deleted file mode 100644
index dfbe01179..000000000
--- a/images/emoji/1f558.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f559.png b/images/emoji/1f559.png
deleted file mode 100644
index e62b245cd..000000000
--- a/images/emoji/1f559.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f55a.png b/images/emoji/1f55a.png
deleted file mode 100644
index 098334527..000000000
--- a/images/emoji/1f55a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f55b.png b/images/emoji/1f55b.png
deleted file mode 100644
index e61caa4b3..000000000
--- a/images/emoji/1f55b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f55c.png b/images/emoji/1f55c.png
deleted file mode 100644
index 86b7689b8..000000000
--- a/images/emoji/1f55c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f55d.png b/images/emoji/1f55d.png
deleted file mode 100644
index 7a787e018..000000000
--- a/images/emoji/1f55d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f55e.png b/images/emoji/1f55e.png
deleted file mode 100644
index c6860395c..000000000
--- a/images/emoji/1f55e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f55f.png b/images/emoji/1f55f.png
deleted file mode 100644
index 3c05b3621..000000000
--- a/images/emoji/1f55f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f560.png b/images/emoji/1f560.png
deleted file mode 100644
index c21fa926d..000000000
--- a/images/emoji/1f560.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f561.png b/images/emoji/1f561.png
deleted file mode 100644
index 2aec87fef..000000000
--- a/images/emoji/1f561.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f562.png b/images/emoji/1f562.png
deleted file mode 100644
index f7a1135e0..000000000
--- a/images/emoji/1f562.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f563.png b/images/emoji/1f563.png
deleted file mode 100644
index 799b4aebc..000000000
--- a/images/emoji/1f563.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f564.png b/images/emoji/1f564.png
deleted file mode 100644
index 4a2092ee6..000000000
--- a/images/emoji/1f564.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f565.png b/images/emoji/1f565.png
deleted file mode 100644
index 0802b3c65..000000000
--- a/images/emoji/1f565.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f566.png b/images/emoji/1f566.png
deleted file mode 100644
index d970d03b8..000000000
--- a/images/emoji/1f566.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f567.png b/images/emoji/1f567.png
deleted file mode 100644
index f2b1d2617..000000000
--- a/images/emoji/1f567.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f56f.png b/images/emoji/1f56f.png
deleted file mode 100644
index 0b56444e3..000000000
--- a/images/emoji/1f56f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f570.png b/images/emoji/1f570.png
deleted file mode 100644
index ffdb451e3..000000000
--- a/images/emoji/1f570.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f573.png b/images/emoji/1f573.png
deleted file mode 100644
index 517d2ae0d..000000000
--- a/images/emoji/1f573.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f574.png b/images/emoji/1f574.png
deleted file mode 100644
index 3dc315a3d..000000000
--- a/images/emoji/1f574.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f575-1f3fb.png b/images/emoji/1f575-1f3fb.png
deleted file mode 100644
index 2d1c022ca..000000000
--- a/images/emoji/1f575-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f575-1f3fc.png b/images/emoji/1f575-1f3fc.png
deleted file mode 100644
index 13e01ad93..000000000
--- a/images/emoji/1f575-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f575-1f3fd.png b/images/emoji/1f575-1f3fd.png
deleted file mode 100644
index a814dca2e..000000000
--- a/images/emoji/1f575-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f575-1f3fe.png b/images/emoji/1f575-1f3fe.png
deleted file mode 100644
index d8300af49..000000000
--- a/images/emoji/1f575-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f575-1f3ff.png b/images/emoji/1f575-1f3ff.png
deleted file mode 100644
index ca1462595..000000000
--- a/images/emoji/1f575-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f575.png b/images/emoji/1f575.png
deleted file mode 100644
index a729e9584..000000000
--- a/images/emoji/1f575.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f576.png b/images/emoji/1f576.png
deleted file mode 100644
index b1b6db0ac..000000000
--- a/images/emoji/1f576.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f577.png b/images/emoji/1f577.png
deleted file mode 100644
index 3849fa90b..000000000
--- a/images/emoji/1f577.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f578.png b/images/emoji/1f578.png
deleted file mode 100644
index ba448ee7f..000000000
--- a/images/emoji/1f578.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f579.png b/images/emoji/1f579.png
deleted file mode 100644
index 1ee190543..000000000
--- a/images/emoji/1f579.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f57a-1f3fb.png b/images/emoji/1f57a-1f3fb.png
deleted file mode 100644
index e0b9f82d9..000000000
--- a/images/emoji/1f57a-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f57a-1f3fc.png b/images/emoji/1f57a-1f3fc.png
deleted file mode 100644
index a5beed56e..000000000
--- a/images/emoji/1f57a-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f57a-1f3fd.png b/images/emoji/1f57a-1f3fd.png
deleted file mode 100644
index 2fa20180a..000000000
--- a/images/emoji/1f57a-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f57a-1f3fe.png b/images/emoji/1f57a-1f3fe.png
deleted file mode 100644
index bd3528c83..000000000
--- a/images/emoji/1f57a-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f57a-1f3ff.png b/images/emoji/1f57a-1f3ff.png
deleted file mode 100644
index 41fd4f880..000000000
--- a/images/emoji/1f57a-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f57a.png b/images/emoji/1f57a.png
deleted file mode 100644
index ccff3bede..000000000
--- a/images/emoji/1f57a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f587.png b/images/emoji/1f587.png
deleted file mode 100644
index 76021e8c7..000000000
--- a/images/emoji/1f587.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f58a.png b/images/emoji/1f58a.png
deleted file mode 100644
index 6ef7a3424..000000000
--- a/images/emoji/1f58a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f58b.png b/images/emoji/1f58b.png
deleted file mode 100644
index 3ca4bd2c2..000000000
--- a/images/emoji/1f58b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f58c.png b/images/emoji/1f58c.png
deleted file mode 100644
index 28bffbaa3..000000000
--- a/images/emoji/1f58c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f58d.png b/images/emoji/1f58d.png
deleted file mode 100644
index 8d7b427aa..000000000
--- a/images/emoji/1f58d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f590-1f3fb.png b/images/emoji/1f590-1f3fb.png
deleted file mode 100644
index a7888e6bd..000000000
--- a/images/emoji/1f590-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f590-1f3fc.png b/images/emoji/1f590-1f3fc.png
deleted file mode 100644
index cc10fbc27..000000000
--- a/images/emoji/1f590-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f590-1f3fd.png b/images/emoji/1f590-1f3fd.png
deleted file mode 100644
index 707236ae8..000000000
--- a/images/emoji/1f590-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f590-1f3fe.png b/images/emoji/1f590-1f3fe.png
deleted file mode 100644
index 1430df9c6..000000000
--- a/images/emoji/1f590-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f590-1f3ff.png b/images/emoji/1f590-1f3ff.png
deleted file mode 100644
index 80bec971b..000000000
--- a/images/emoji/1f590-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f590.png b/images/emoji/1f590.png
deleted file mode 100644
index fb5ae8ebb..000000000
--- a/images/emoji/1f590.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f595-1f3fb.png b/images/emoji/1f595-1f3fb.png
deleted file mode 100644
index 61ef12a15..000000000
--- a/images/emoji/1f595-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f595-1f3fc.png b/images/emoji/1f595-1f3fc.png
deleted file mode 100644
index c31a69be9..000000000
--- a/images/emoji/1f595-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f595-1f3fd.png b/images/emoji/1f595-1f3fd.png
deleted file mode 100644
index 73ac216ce..000000000
--- a/images/emoji/1f595-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f595-1f3fe.png b/images/emoji/1f595-1f3fe.png
deleted file mode 100644
index 80b8ab770..000000000
--- a/images/emoji/1f595-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f595-1f3ff.png b/images/emoji/1f595-1f3ff.png
deleted file mode 100644
index a8826b196..000000000
--- a/images/emoji/1f595-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f595.png b/images/emoji/1f595.png
deleted file mode 100644
index 697f7a25e..000000000
--- a/images/emoji/1f595.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f596-1f3fb.png b/images/emoji/1f596-1f3fb.png
deleted file mode 100644
index 8aff5d8fa..000000000
--- a/images/emoji/1f596-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f596-1f3fc.png b/images/emoji/1f596-1f3fc.png
deleted file mode 100644
index 82b7ad519..000000000
--- a/images/emoji/1f596-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f596-1f3fd.png b/images/emoji/1f596-1f3fd.png
deleted file mode 100644
index d1400e1dd..000000000
--- a/images/emoji/1f596-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f596-1f3fe.png b/images/emoji/1f596-1f3fe.png
deleted file mode 100644
index 47e2b2801..000000000
--- a/images/emoji/1f596-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f596-1f3ff.png b/images/emoji/1f596-1f3ff.png
deleted file mode 100644
index 60b5c6077..000000000
--- a/images/emoji/1f596-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f596.png b/images/emoji/1f596.png
deleted file mode 100644
index 54728bcaf..000000000
--- a/images/emoji/1f596.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5a4.png b/images/emoji/1f5a4.png
deleted file mode 100644
index b4068c3e6..000000000
--- a/images/emoji/1f5a4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5a5.png b/images/emoji/1f5a5.png
deleted file mode 100644
index 909bd42b5..000000000
--- a/images/emoji/1f5a5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5a8.png b/images/emoji/1f5a8.png
deleted file mode 100644
index 027c830f0..000000000
--- a/images/emoji/1f5a8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5b1.png b/images/emoji/1f5b1.png
deleted file mode 100644
index e84e96ff6..000000000
--- a/images/emoji/1f5b1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5b2.png b/images/emoji/1f5b2.png
deleted file mode 100644
index 3bea84ad7..000000000
--- a/images/emoji/1f5b2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5bc.png b/images/emoji/1f5bc.png
deleted file mode 100644
index 9fe84607b..000000000
--- a/images/emoji/1f5bc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5c2.png b/images/emoji/1f5c2.png
deleted file mode 100644
index 46a7e403f..000000000
--- a/images/emoji/1f5c2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5c3.png b/images/emoji/1f5c3.png
deleted file mode 100644
index f2e764ce5..000000000
--- a/images/emoji/1f5c3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5c4.png b/images/emoji/1f5c4.png
deleted file mode 100644
index fddc65dde..000000000
--- a/images/emoji/1f5c4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5d1.png b/images/emoji/1f5d1.png
deleted file mode 100644
index 2b3c484b4..000000000
--- a/images/emoji/1f5d1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5d2.png b/images/emoji/1f5d2.png
deleted file mode 100644
index 85faa10d8..000000000
--- a/images/emoji/1f5d2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5d3.png b/images/emoji/1f5d3.png
deleted file mode 100644
index dec8d49bf..000000000
--- a/images/emoji/1f5d3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5dc.png b/images/emoji/1f5dc.png
deleted file mode 100644
index 67c13258d..000000000
--- a/images/emoji/1f5dc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5dd.png b/images/emoji/1f5dd.png
deleted file mode 100644
index e11d706c6..000000000
--- a/images/emoji/1f5dd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5de.png b/images/emoji/1f5de.png
deleted file mode 100644
index f64748df2..000000000
--- a/images/emoji/1f5de.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5e1.png b/images/emoji/1f5e1.png
deleted file mode 100644
index 66e97b0aa..000000000
--- a/images/emoji/1f5e1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5e3.png b/images/emoji/1f5e3.png
deleted file mode 100644
index 2df93aaae..000000000
--- a/images/emoji/1f5e3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5e8.png b/images/emoji/1f5e8.png
deleted file mode 100644
index 00c05959b..000000000
--- a/images/emoji/1f5e8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5ef.png b/images/emoji/1f5ef.png
deleted file mode 100644
index f5c97c4d2..000000000
--- a/images/emoji/1f5ef.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5f3.png b/images/emoji/1f5f3.png
deleted file mode 100644
index 9b6767aea..000000000
--- a/images/emoji/1f5f3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5fa.png b/images/emoji/1f5fa.png
deleted file mode 100644
index 15efe32c7..000000000
--- a/images/emoji/1f5fa.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5fb.png b/images/emoji/1f5fb.png
deleted file mode 100644
index 88a547524..000000000
--- a/images/emoji/1f5fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5fc.png b/images/emoji/1f5fc.png
deleted file mode 100644
index 37df7fc65..000000000
--- a/images/emoji/1f5fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5fd.png b/images/emoji/1f5fd.png
deleted file mode 100644
index 05df8289b..000000000
--- a/images/emoji/1f5fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5fe.png b/images/emoji/1f5fe.png
deleted file mode 100644
index d86d0a59e..000000000
--- a/images/emoji/1f5fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f5ff.png b/images/emoji/1f5ff.png
deleted file mode 100644
index e6a7779c4..000000000
--- a/images/emoji/1f5ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f600.png b/images/emoji/1f600.png
deleted file mode 100644
index 3e8e0dab7..000000000
--- a/images/emoji/1f600.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f601.png b/images/emoji/1f601.png
deleted file mode 100644
index 418d94c81..000000000
--- a/images/emoji/1f601.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f602.png b/images/emoji/1f602.png
deleted file mode 100644
index 0ba3b1859..000000000
--- a/images/emoji/1f602.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f603.png b/images/emoji/1f603.png
deleted file mode 100644
index 30957a659..000000000
--- a/images/emoji/1f603.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f604.png b/images/emoji/1f604.png
deleted file mode 100644
index aa47ffe97..000000000
--- a/images/emoji/1f604.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f605.png b/images/emoji/1f605.png
deleted file mode 100644
index cb18d9c89..000000000
--- a/images/emoji/1f605.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f609.png b/images/emoji/1f609.png
deleted file mode 100644
index 7ea7810a3..000000000
--- a/images/emoji/1f609.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f60b.png b/images/emoji/1f60b.png
deleted file mode 100644
index 2df15753c..000000000
--- a/images/emoji/1f60b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f60c.png b/images/emoji/1f60c.png
deleted file mode 100644
index 715ad0bf5..000000000
--- a/images/emoji/1f60c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f60d.png b/images/emoji/1f60d.png
deleted file mode 100644
index 73fbee29d..000000000
--- a/images/emoji/1f60d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f60e.png b/images/emoji/1f60e.png
deleted file mode 100644
index 200117351..000000000
--- a/images/emoji/1f60e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f60f.png b/images/emoji/1f60f.png
deleted file mode 100644
index 878521099..000000000
--- a/images/emoji/1f60f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f610.png b/images/emoji/1f610.png
deleted file mode 100644
index 065d193af..000000000
--- a/images/emoji/1f610.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f611.png b/images/emoji/1f611.png
deleted file mode 100644
index 2954017f6..000000000
--- a/images/emoji/1f611.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f612.png b/images/emoji/1f612.png
deleted file mode 100644
index 25e3677f2..000000000
--- a/images/emoji/1f612.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f613.png b/images/emoji/1f613.png
deleted file mode 100644
index f0dae7b78..000000000
--- a/images/emoji/1f613.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f614.png b/images/emoji/1f614.png
deleted file mode 100644
index 490fb5669..000000000
--- a/images/emoji/1f614.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f615.png b/images/emoji/1f615.png
deleted file mode 100644
index 502b6bf0e..000000000
--- a/images/emoji/1f615.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f616.png b/images/emoji/1f616.png
deleted file mode 100644
index aa4b29e93..000000000
--- a/images/emoji/1f616.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f617.png b/images/emoji/1f617.png
deleted file mode 100644
index 39d325fd8..000000000
--- a/images/emoji/1f617.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f618.png b/images/emoji/1f618.png
deleted file mode 100644
index 0ff808fd6..000000000
--- a/images/emoji/1f618.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f619.png b/images/emoji/1f619.png
deleted file mode 100644
index e181f1709..000000000
--- a/images/emoji/1f619.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f61a.png b/images/emoji/1f61a.png
deleted file mode 100644
index b684d7d4d..000000000
--- a/images/emoji/1f61a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f61b.png b/images/emoji/1f61b.png
deleted file mode 100644
index 25757341f..000000000
--- a/images/emoji/1f61b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f61d.png b/images/emoji/1f61d.png
deleted file mode 100644
index 5c0401e9b..000000000
--- a/images/emoji/1f61d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f61f.png b/images/emoji/1f61f.png
deleted file mode 100644
index 7074afcf5..000000000
--- a/images/emoji/1f61f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f620.png b/images/emoji/1f620.png
deleted file mode 100644
index cfc4a6ecd..000000000
--- a/images/emoji/1f620.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f621.png b/images/emoji/1f621.png
deleted file mode 100644
index 9d739bd40..000000000
--- a/images/emoji/1f621.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f622.png b/images/emoji/1f622.png
deleted file mode 100644
index b7877f8a1..000000000
--- a/images/emoji/1f622.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f623.png b/images/emoji/1f623.png
deleted file mode 100644
index 646a05fe9..000000000
--- a/images/emoji/1f623.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f624.png b/images/emoji/1f624.png
deleted file mode 100644
index 4f3312854..000000000
--- a/images/emoji/1f624.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f625.png b/images/emoji/1f625.png
deleted file mode 100644
index aef864d2b..000000000
--- a/images/emoji/1f625.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f626.png b/images/emoji/1f626.png
deleted file mode 100644
index 43ab6b0a1..000000000
--- a/images/emoji/1f626.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f627.png b/images/emoji/1f627.png
deleted file mode 100644
index f99026a3b..000000000
--- a/images/emoji/1f627.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f628.png b/images/emoji/1f628.png
deleted file mode 100644
index eb8b347ce..000000000
--- a/images/emoji/1f628.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f629.png b/images/emoji/1f629.png
deleted file mode 100644
index 98bfbd24a..000000000
--- a/images/emoji/1f629.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f62a.png b/images/emoji/1f62a.png
deleted file mode 100644
index 836b41077..000000000
--- a/images/emoji/1f62a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f62b.png b/images/emoji/1f62b.png
deleted file mode 100644
index 19aba1bc1..000000000
--- a/images/emoji/1f62b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f62c.png b/images/emoji/1f62c.png
deleted file mode 100644
index 871b2f071..000000000
--- a/images/emoji/1f62c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f62d.png b/images/emoji/1f62d.png
deleted file mode 100644
index e4f818360..000000000
--- a/images/emoji/1f62d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f62f.png b/images/emoji/1f62f.png
deleted file mode 100644
index cad0e2313..000000000
--- a/images/emoji/1f62f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f630.png b/images/emoji/1f630.png
deleted file mode 100644
index 85b2231bb..000000000
--- a/images/emoji/1f630.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f631.png b/images/emoji/1f631.png
deleted file mode 100644
index 6ab43a0d3..000000000
--- a/images/emoji/1f631.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f632.png b/images/emoji/1f632.png
deleted file mode 100644
index bd0ac55ec..000000000
--- a/images/emoji/1f632.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f633.png b/images/emoji/1f633.png
deleted file mode 100644
index 829220bc4..000000000
--- a/images/emoji/1f633.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f635.png b/images/emoji/1f635.png
deleted file mode 100644
index 3120316ab..000000000
--- a/images/emoji/1f635.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f636.png b/images/emoji/1f636.png
deleted file mode 100644
index b642f6c11..000000000
--- a/images/emoji/1f636.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f637.png b/images/emoji/1f637.png
deleted file mode 100644
index 23852e578..000000000
--- a/images/emoji/1f637.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f638.png b/images/emoji/1f638.png
deleted file mode 100644
index e27290a67..000000000
--- a/images/emoji/1f638.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f639.png b/images/emoji/1f639.png
deleted file mode 100644
index aac353179..000000000
--- a/images/emoji/1f639.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f63a.png b/images/emoji/1f63a.png
deleted file mode 100644
index d5b1cef0b..000000000
--- a/images/emoji/1f63a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f63b.png b/images/emoji/1f63b.png
deleted file mode 100644
index 5a59eed04..000000000
--- a/images/emoji/1f63b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f63c.png b/images/emoji/1f63c.png
deleted file mode 100644
index 0bfeae4eb..000000000
--- a/images/emoji/1f63c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f63d.png b/images/emoji/1f63d.png
deleted file mode 100644
index 7f1ef2056..000000000
--- a/images/emoji/1f63d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f63e.png b/images/emoji/1f63e.png
deleted file mode 100644
index 41ddfeab4..000000000
--- a/images/emoji/1f63e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f63f.png b/images/emoji/1f63f.png
deleted file mode 100644
index ccc8d4f25..000000000
--- a/images/emoji/1f63f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f640.png b/images/emoji/1f640.png
deleted file mode 100644
index 15803ad8e..000000000
--- a/images/emoji/1f640.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f641.png b/images/emoji/1f641.png
deleted file mode 100644
index b2f1d983d..000000000
--- a/images/emoji/1f641.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f642.png b/images/emoji/1f642.png
deleted file mode 100644
index ddd7d65dd..000000000
--- a/images/emoji/1f642.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f643.png b/images/emoji/1f643.png
deleted file mode 100644
index 128f31c98..000000000
--- a/images/emoji/1f643.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f644.png b/images/emoji/1f644.png
deleted file mode 100644
index 2f77b9fc3..000000000
--- a/images/emoji/1f644.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f645-1f3fb.png b/images/emoji/1f645-1f3fb.png
deleted file mode 100644
index 7f28bf121..000000000
--- a/images/emoji/1f645-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f645-1f3fc.png b/images/emoji/1f645-1f3fc.png
deleted file mode 100644
index 80d8021f8..000000000
--- a/images/emoji/1f645-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f645-1f3fd.png b/images/emoji/1f645-1f3fd.png
deleted file mode 100644
index 635e6a008..000000000
--- a/images/emoji/1f645-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f645-1f3fe.png b/images/emoji/1f645-1f3fe.png
deleted file mode 100644
index 42006e7da..000000000
--- a/images/emoji/1f645-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f645-1f3ff.png b/images/emoji/1f645-1f3ff.png
deleted file mode 100644
index 309096cba..000000000
--- a/images/emoji/1f645-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f645.png b/images/emoji/1f645.png
deleted file mode 100644
index 381753cd8..000000000
--- a/images/emoji/1f645.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f646-1f3fb.png b/images/emoji/1f646-1f3fb.png
deleted file mode 100644
index ac28746a5..000000000
--- a/images/emoji/1f646-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f646-1f3fc.png b/images/emoji/1f646-1f3fc.png
deleted file mode 100644
index 5d845b042..000000000
--- a/images/emoji/1f646-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f646-1f3fd.png b/images/emoji/1f646-1f3fd.png
deleted file mode 100644
index 74c7b794f..000000000
--- a/images/emoji/1f646-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f646-1f3fe.png b/images/emoji/1f646-1f3fe.png
deleted file mode 100644
index 2fbcd7f67..000000000
--- a/images/emoji/1f646-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f646-1f3ff.png b/images/emoji/1f646-1f3ff.png
deleted file mode 100644
index da2d13546..000000000
--- a/images/emoji/1f646-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f646.png b/images/emoji/1f646.png
deleted file mode 100644
index 3de4594bd..000000000
--- a/images/emoji/1f646.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f647-1f3fb.png b/images/emoji/1f647-1f3fb.png
deleted file mode 100644
index 003d66052..000000000
--- a/images/emoji/1f647-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f647-1f3fc.png b/images/emoji/1f647-1f3fc.png
deleted file mode 100644
index d774be9c9..000000000
--- a/images/emoji/1f647-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f647-1f3fd.png b/images/emoji/1f647-1f3fd.png
deleted file mode 100644
index 43e06fd86..000000000
--- a/images/emoji/1f647-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f647-1f3fe.png b/images/emoji/1f647-1f3fe.png
deleted file mode 100644
index 2d0f1a7c7..000000000
--- a/images/emoji/1f647-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f647-1f3ff.png b/images/emoji/1f647-1f3ff.png
deleted file mode 100644
index 91f1a8ace..000000000
--- a/images/emoji/1f647-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f647.png b/images/emoji/1f647.png
deleted file mode 100644
index 3a0e83ee8..000000000
--- a/images/emoji/1f647.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f648.png b/images/emoji/1f648.png
deleted file mode 100644
index 5187e4745..000000000
--- a/images/emoji/1f648.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f649.png b/images/emoji/1f649.png
deleted file mode 100644
index 74b6be0c6..000000000
--- a/images/emoji/1f649.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64a.png b/images/emoji/1f64a.png
deleted file mode 100644
index c75f42ae7..000000000
--- a/images/emoji/1f64a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64b-1f3fb.png b/images/emoji/1f64b-1f3fb.png
deleted file mode 100644
index 1c90e3e26..000000000
--- a/images/emoji/1f64b-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64b-1f3fc.png b/images/emoji/1f64b-1f3fc.png
deleted file mode 100644
index 82c3ef2bf..000000000
--- a/images/emoji/1f64b-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64b-1f3fd.png b/images/emoji/1f64b-1f3fd.png
deleted file mode 100644
index 92a389f72..000000000
--- a/images/emoji/1f64b-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64b-1f3fe.png b/images/emoji/1f64b-1f3fe.png
deleted file mode 100644
index 8b95f0533..000000000
--- a/images/emoji/1f64b-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64b-1f3ff.png b/images/emoji/1f64b-1f3ff.png
deleted file mode 100644
index b86200fd8..000000000
--- a/images/emoji/1f64b-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64b.png b/images/emoji/1f64b.png
deleted file mode 100644
index 7c803b315..000000000
--- a/images/emoji/1f64b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64c-1f3fb.png b/images/emoji/1f64c-1f3fb.png
deleted file mode 100644
index 1168b8236..000000000
--- a/images/emoji/1f64c-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64c-1f3fc.png b/images/emoji/1f64c-1f3fc.png
deleted file mode 100644
index 322de6229..000000000
--- a/images/emoji/1f64c-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64c-1f3fd.png b/images/emoji/1f64c-1f3fd.png
deleted file mode 100644
index 2aa24e05a..000000000
--- a/images/emoji/1f64c-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64c-1f3fe.png b/images/emoji/1f64c-1f3fe.png
deleted file mode 100644
index f31bf0db9..000000000
--- a/images/emoji/1f64c-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64c-1f3ff.png b/images/emoji/1f64c-1f3ff.png
deleted file mode 100644
index 5e95067f9..000000000
--- a/images/emoji/1f64c-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64c.png b/images/emoji/1f64c.png
deleted file mode 100644
index c0155f728..000000000
--- a/images/emoji/1f64c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64d-1f3fb.png b/images/emoji/1f64d-1f3fb.png
deleted file mode 100644
index 21d3bb439..000000000
--- a/images/emoji/1f64d-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64d-1f3fc.png b/images/emoji/1f64d-1f3fc.png
deleted file mode 100644
index 973f5fc83..000000000
--- a/images/emoji/1f64d-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64d-1f3fd.png b/images/emoji/1f64d-1f3fd.png
deleted file mode 100644
index 41fbcc788..000000000
--- a/images/emoji/1f64d-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64d-1f3fe.png b/images/emoji/1f64d-1f3fe.png
deleted file mode 100644
index 5a37c7410..000000000
--- a/images/emoji/1f64d-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64d-1f3ff.png b/images/emoji/1f64d-1f3ff.png
deleted file mode 100644
index e08141f3e..000000000
--- a/images/emoji/1f64d-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64d.png b/images/emoji/1f64d.png
deleted file mode 100644
index 579324959..000000000
--- a/images/emoji/1f64d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64e-1f3fb.png b/images/emoji/1f64e-1f3fb.png
deleted file mode 100644
index 57e826b75..000000000
--- a/images/emoji/1f64e-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64e-1f3fc.png b/images/emoji/1f64e-1f3fc.png
deleted file mode 100644
index 3f317c0c2..000000000
--- a/images/emoji/1f64e-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64e-1f3fd.png b/images/emoji/1f64e-1f3fd.png
deleted file mode 100644
index d2fbb6c20..000000000
--- a/images/emoji/1f64e-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64e-1f3fe.png b/images/emoji/1f64e-1f3fe.png
deleted file mode 100644
index 643ceb4a5..000000000
--- a/images/emoji/1f64e-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64e-1f3ff.png b/images/emoji/1f64e-1f3ff.png
deleted file mode 100644
index b2eb6859c..000000000
--- a/images/emoji/1f64e-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64e.png b/images/emoji/1f64e.png
deleted file mode 100644
index 10eb05710..000000000
--- a/images/emoji/1f64e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64f-1f3fb.png b/images/emoji/1f64f-1f3fb.png
deleted file mode 100644
index 060ef2571..000000000
--- a/images/emoji/1f64f-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64f-1f3fc.png b/images/emoji/1f64f-1f3fc.png
deleted file mode 100644
index 56dc607c0..000000000
--- a/images/emoji/1f64f-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64f-1f3fd.png b/images/emoji/1f64f-1f3fd.png
deleted file mode 100644
index 0f33b8620..000000000
--- a/images/emoji/1f64f-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64f-1f3fe.png b/images/emoji/1f64f-1f3fe.png
deleted file mode 100644
index 2ea8dc116..000000000
--- a/images/emoji/1f64f-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64f-1f3ff.png b/images/emoji/1f64f-1f3ff.png
deleted file mode 100644
index 2128a6c47..000000000
--- a/images/emoji/1f64f-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f64f.png b/images/emoji/1f64f.png
deleted file mode 100644
index 8347f2435..000000000
--- a/images/emoji/1f64f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f680.png b/images/emoji/1f680.png
deleted file mode 100644
index 0d8da089a..000000000
--- a/images/emoji/1f680.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f681.png b/images/emoji/1f681.png
deleted file mode 100644
index 7ec5f39a5..000000000
--- a/images/emoji/1f681.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f682.png b/images/emoji/1f682.png
deleted file mode 100644
index 9ac0d999c..000000000
--- a/images/emoji/1f682.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f683.png b/images/emoji/1f683.png
deleted file mode 100644
index a9acbf130..000000000
--- a/images/emoji/1f683.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f684.png b/images/emoji/1f684.png
deleted file mode 100644
index ed61c67bf..000000000
--- a/images/emoji/1f684.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f685.png b/images/emoji/1f685.png
deleted file mode 100644
index 4f698e056..000000000
--- a/images/emoji/1f685.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f686.png b/images/emoji/1f686.png
deleted file mode 100644
index 8701e41e7..000000000
--- a/images/emoji/1f686.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f687.png b/images/emoji/1f687.png
deleted file mode 100644
index 1de8f0551..000000000
--- a/images/emoji/1f687.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f688.png b/images/emoji/1f688.png
deleted file mode 100644
index a64829f50..000000000
--- a/images/emoji/1f688.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f689.png b/images/emoji/1f689.png
deleted file mode 100644
index 5c26fee52..000000000
--- a/images/emoji/1f689.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f68a.png b/images/emoji/1f68a.png
deleted file mode 100644
index b6f0e6903..000000000
--- a/images/emoji/1f68a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f68b.png b/images/emoji/1f68b.png
deleted file mode 100644
index 3c80321f7..000000000
--- a/images/emoji/1f68b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f68c.png b/images/emoji/1f68c.png
deleted file mode 100644
index 641ddc56c..000000000
--- a/images/emoji/1f68c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f68d.png b/images/emoji/1f68d.png
deleted file mode 100644
index ad91e256c..000000000
--- a/images/emoji/1f68d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f68e.png b/images/emoji/1f68e.png
deleted file mode 100644
index 139a9931b..000000000
--- a/images/emoji/1f68e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f68f.png b/images/emoji/1f68f.png
deleted file mode 100644
index b2b62208b..000000000
--- a/images/emoji/1f68f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f690.png b/images/emoji/1f690.png
deleted file mode 100644
index c60dd8f47..000000000
--- a/images/emoji/1f690.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f691.png b/images/emoji/1f691.png
deleted file mode 100644
index 6fb8076d7..000000000
--- a/images/emoji/1f691.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f692.png b/images/emoji/1f692.png
deleted file mode 100644
index 249ffaabd..000000000
--- a/images/emoji/1f692.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f693.png b/images/emoji/1f693.png
deleted file mode 100644
index 3da4253de..000000000
--- a/images/emoji/1f693.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f694.png b/images/emoji/1f694.png
deleted file mode 100644
index a50388fc9..000000000
--- a/images/emoji/1f694.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f695.png b/images/emoji/1f695.png
deleted file mode 100644
index 55f4cc847..000000000
--- a/images/emoji/1f695.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f696.png b/images/emoji/1f696.png
deleted file mode 100644
index b4a9ddde4..000000000
--- a/images/emoji/1f696.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f697.png b/images/emoji/1f697.png
deleted file mode 100644
index b3e6a774d..000000000
--- a/images/emoji/1f697.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f698.png b/images/emoji/1f698.png
deleted file mode 100644
index 3c7e1d52e..000000000
--- a/images/emoji/1f698.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f699.png b/images/emoji/1f699.png
deleted file mode 100644
index e8ba817d3..000000000
--- a/images/emoji/1f699.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f69a.png b/images/emoji/1f69a.png
deleted file mode 100644
index c7677a769..000000000
--- a/images/emoji/1f69a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f69b.png b/images/emoji/1f69b.png
deleted file mode 100644
index b3b7742e6..000000000
--- a/images/emoji/1f69b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f69c.png b/images/emoji/1f69c.png
deleted file mode 100644
index c1bf8cae4..000000000
--- a/images/emoji/1f69c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f69d.png b/images/emoji/1f69d.png
deleted file mode 100644
index 11eb1f574..000000000
--- a/images/emoji/1f69d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f69e.png b/images/emoji/1f69e.png
deleted file mode 100644
index d136d60aa..000000000
--- a/images/emoji/1f69e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f69f.png b/images/emoji/1f69f.png
deleted file mode 100644
index a59d5f48c..000000000
--- a/images/emoji/1f69f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6a0.png b/images/emoji/1f6a0.png
deleted file mode 100644
index 1dea73ca5..000000000
--- a/images/emoji/1f6a0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6a1.png b/images/emoji/1f6a1.png
deleted file mode 100644
index 3eb4b61bf..000000000
--- a/images/emoji/1f6a1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6a2.png b/images/emoji/1f6a2.png
deleted file mode 100644
index 62d54f7d6..000000000
--- a/images/emoji/1f6a2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6a3-1f3fb.png b/images/emoji/1f6a3-1f3fb.png
deleted file mode 100644
index 947471874..000000000
--- a/images/emoji/1f6a3-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6a3-1f3fc.png b/images/emoji/1f6a3-1f3fc.png
deleted file mode 100644
index 9b123ef88..000000000
--- a/images/emoji/1f6a3-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6a3-1f3fd.png b/images/emoji/1f6a3-1f3fd.png
deleted file mode 100644
index 8ebd89a55..000000000
--- a/images/emoji/1f6a3-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6a3-1f3fe.png b/images/emoji/1f6a3-1f3fe.png
deleted file mode 100644
index 2b0d04f87..000000000
--- a/images/emoji/1f6a3-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6a3-1f3ff.png b/images/emoji/1f6a3-1f3ff.png
deleted file mode 100644
index b346f2dfc..000000000
--- a/images/emoji/1f6a3-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6a3.png b/images/emoji/1f6a3.png
deleted file mode 100644
index dd4dfc095..000000000
--- a/images/emoji/1f6a3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6a4.png b/images/emoji/1f6a4.png
deleted file mode 100644
index 74059d12d..000000000
--- a/images/emoji/1f6a4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6a5.png b/images/emoji/1f6a5.png
deleted file mode 100644
index 6b312285b..000000000
--- a/images/emoji/1f6a5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6a6.png b/images/emoji/1f6a6.png
deleted file mode 100644
index 8085973ee..000000000
--- a/images/emoji/1f6a6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6a7.png b/images/emoji/1f6a7.png
deleted file mode 100644
index ef8db5f47..000000000
--- a/images/emoji/1f6a7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6a8.png b/images/emoji/1f6a8.png
deleted file mode 100644
index cad66b0af..000000000
--- a/images/emoji/1f6a8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6a9.png b/images/emoji/1f6a9.png
deleted file mode 100644
index c12d8b068..000000000
--- a/images/emoji/1f6a9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6aa.png b/images/emoji/1f6aa.png
deleted file mode 100644
index 36ae3e274..000000000
--- a/images/emoji/1f6aa.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6ab.png b/images/emoji/1f6ab.png
deleted file mode 100644
index d2efd65e7..000000000
--- a/images/emoji/1f6ab.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6ac.png b/images/emoji/1f6ac.png
deleted file mode 100644
index 910f648c8..000000000
--- a/images/emoji/1f6ac.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6ad.png b/images/emoji/1f6ad.png
deleted file mode 100644
index d33b9de53..000000000
--- a/images/emoji/1f6ad.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6ae.png b/images/emoji/1f6ae.png
deleted file mode 100644
index 82a84f9a3..000000000
--- a/images/emoji/1f6ae.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6af.png b/images/emoji/1f6af.png
deleted file mode 100644
index 341d2575f..000000000
--- a/images/emoji/1f6af.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b0.png b/images/emoji/1f6b0.png
deleted file mode 100644
index 2c6100494..000000000
--- a/images/emoji/1f6b0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b1.png b/images/emoji/1f6b1.png
deleted file mode 100644
index 827d4193f..000000000
--- a/images/emoji/1f6b1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b2.png b/images/emoji/1f6b2.png
deleted file mode 100644
index 6125842f8..000000000
--- a/images/emoji/1f6b2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b3.png b/images/emoji/1f6b3.png
deleted file mode 100644
index 19c85421c..000000000
--- a/images/emoji/1f6b3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b4-1f3fb.png b/images/emoji/1f6b4-1f3fb.png
deleted file mode 100644
index decc2f728..000000000
--- a/images/emoji/1f6b4-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b4-1f3fc.png b/images/emoji/1f6b4-1f3fc.png
deleted file mode 100644
index 0067717b8..000000000
--- a/images/emoji/1f6b4-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b4-1f3fd.png b/images/emoji/1f6b4-1f3fd.png
deleted file mode 100644
index a4f7b5e27..000000000
--- a/images/emoji/1f6b4-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b4-1f3fe.png b/images/emoji/1f6b4-1f3fe.png
deleted file mode 100644
index a3c8a797d..000000000
--- a/images/emoji/1f6b4-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b4-1f3ff.png b/images/emoji/1f6b4-1f3ff.png
deleted file mode 100644
index 1606a8740..000000000
--- a/images/emoji/1f6b4-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b4.png b/images/emoji/1f6b4.png
deleted file mode 100644
index 9274da110..000000000
--- a/images/emoji/1f6b4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b5-1f3fb.png b/images/emoji/1f6b5-1f3fb.png
deleted file mode 100644
index e9f1daf5e..000000000
--- a/images/emoji/1f6b5-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b5-1f3fc.png b/images/emoji/1f6b5-1f3fc.png
deleted file mode 100644
index 555b9e29d..000000000
--- a/images/emoji/1f6b5-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b5-1f3fd.png b/images/emoji/1f6b5-1f3fd.png
deleted file mode 100644
index 7df5508ec..000000000
--- a/images/emoji/1f6b5-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b5-1f3fe.png b/images/emoji/1f6b5-1f3fe.png
deleted file mode 100644
index f94b34506..000000000
--- a/images/emoji/1f6b5-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b5-1f3ff.png b/images/emoji/1f6b5-1f3ff.png
deleted file mode 100644
index 16a45861e..000000000
--- a/images/emoji/1f6b5-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b5.png b/images/emoji/1f6b5.png
deleted file mode 100644
index 41d3dc3ac..000000000
--- a/images/emoji/1f6b5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b6-1f3fb.png b/images/emoji/1f6b6-1f3fb.png
deleted file mode 100644
index 4e391b45a..000000000
--- a/images/emoji/1f6b6-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b6-1f3fc.png b/images/emoji/1f6b6-1f3fc.png
deleted file mode 100644
index 31f94a1bc..000000000
--- a/images/emoji/1f6b6-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b6-1f3fd.png b/images/emoji/1f6b6-1f3fd.png
deleted file mode 100644
index f7ed8e39c..000000000
--- a/images/emoji/1f6b6-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b6-1f3fe.png b/images/emoji/1f6b6-1f3fe.png
deleted file mode 100644
index e58dc04c7..000000000
--- a/images/emoji/1f6b6-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b6-1f3ff.png b/images/emoji/1f6b6-1f3ff.png
deleted file mode 100644
index ba4e1b58f..000000000
--- a/images/emoji/1f6b6-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b6.png b/images/emoji/1f6b6.png
deleted file mode 100644
index 06dc169a3..000000000
--- a/images/emoji/1f6b6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b7.png b/images/emoji/1f6b7.png
deleted file mode 100644
index 286aa577a..000000000
--- a/images/emoji/1f6b7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b8.png b/images/emoji/1f6b8.png
deleted file mode 100644
index fa4c091c7..000000000
--- a/images/emoji/1f6b8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6b9.png b/images/emoji/1f6b9.png
deleted file mode 100644
index f5a1e1ba0..000000000
--- a/images/emoji/1f6b9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6ba.png b/images/emoji/1f6ba.png
deleted file mode 100644
index d4ecc22e7..000000000
--- a/images/emoji/1f6ba.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6bb.png b/images/emoji/1f6bb.png
deleted file mode 100644
index 9588e0f0e..000000000
--- a/images/emoji/1f6bb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6bc.png b/images/emoji/1f6bc.png
deleted file mode 100644
index 64a10b717..000000000
--- a/images/emoji/1f6bc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6bd.png b/images/emoji/1f6bd.png
deleted file mode 100644
index 1392f7618..000000000
--- a/images/emoji/1f6bd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6be.png b/images/emoji/1f6be.png
deleted file mode 100644
index aa433e84b..000000000
--- a/images/emoji/1f6be.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6bf.png b/images/emoji/1f6bf.png
deleted file mode 100644
index 156776a2e..000000000
--- a/images/emoji/1f6bf.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6c0-1f3fb.png b/images/emoji/1f6c0-1f3fb.png
deleted file mode 100644
index 2152eabf2..000000000
--- a/images/emoji/1f6c0-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6c0-1f3fc.png b/images/emoji/1f6c0-1f3fc.png
deleted file mode 100644
index 2102e6133..000000000
--- a/images/emoji/1f6c0-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6c0-1f3fd.png b/images/emoji/1f6c0-1f3fd.png
deleted file mode 100644
index fae66181e..000000000
--- a/images/emoji/1f6c0-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6c0-1f3fe.png b/images/emoji/1f6c0-1f3fe.png
deleted file mode 100644
index 1f8959d0d..000000000
--- a/images/emoji/1f6c0-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6c0-1f3ff.png b/images/emoji/1f6c0-1f3ff.png
deleted file mode 100644
index c8a08e84f..000000000
--- a/images/emoji/1f6c0-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6c0.png b/images/emoji/1f6c0.png
deleted file mode 100644
index 43fba5c8a..000000000
--- a/images/emoji/1f6c0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6c1.png b/images/emoji/1f6c1.png
deleted file mode 100644
index 9a5f09361..000000000
--- a/images/emoji/1f6c1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6c2.png b/images/emoji/1f6c2.png
deleted file mode 100644
index 079e34ee4..000000000
--- a/images/emoji/1f6c2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6c3.png b/images/emoji/1f6c3.png
deleted file mode 100644
index 21b7ce2c6..000000000
--- a/images/emoji/1f6c3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6c4.png b/images/emoji/1f6c4.png
deleted file mode 100644
index 409b593e7..000000000
--- a/images/emoji/1f6c4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6c5.png b/images/emoji/1f6c5.png
deleted file mode 100644
index 887b23f3f..000000000
--- a/images/emoji/1f6c5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6cb.png b/images/emoji/1f6cb.png
deleted file mode 100644
index 27b19b13b..000000000
--- a/images/emoji/1f6cb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6cc.png b/images/emoji/1f6cc.png
deleted file mode 100644
index c739e7fb6..000000000
--- a/images/emoji/1f6cc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6cd.png b/images/emoji/1f6cd.png
deleted file mode 100644
index 99f2a2b13..000000000
--- a/images/emoji/1f6cd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6ce.png b/images/emoji/1f6ce.png
deleted file mode 100644
index 6b3297cea..000000000
--- a/images/emoji/1f6ce.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6cf.png b/images/emoji/1f6cf.png
deleted file mode 100644
index cf75349a3..000000000
--- a/images/emoji/1f6cf.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6d0.png b/images/emoji/1f6d0.png
deleted file mode 100644
index 207d59cce..000000000
--- a/images/emoji/1f6d0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6d1.png b/images/emoji/1f6d1.png
deleted file mode 100644
index 5ed610040..000000000
--- a/images/emoji/1f6d1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6d2.png b/images/emoji/1f6d2.png
deleted file mode 100644
index 1086fe6e4..000000000
--- a/images/emoji/1f6d2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6e0.png b/images/emoji/1f6e0.png
deleted file mode 100644
index 3c6049273..000000000
--- a/images/emoji/1f6e0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6e1.png b/images/emoji/1f6e1.png
deleted file mode 100644
index 610bf033c..000000000
--- a/images/emoji/1f6e1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6e2.png b/images/emoji/1f6e2.png
deleted file mode 100644
index c4c4d42da..000000000
--- a/images/emoji/1f6e2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6e3.png b/images/emoji/1f6e3.png
deleted file mode 100644
index 8c3d3d03e..000000000
--- a/images/emoji/1f6e3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6e4.png b/images/emoji/1f6e4.png
deleted file mode 100644
index 3bde6fb65..000000000
--- a/images/emoji/1f6e4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6e5.png b/images/emoji/1f6e5.png
deleted file mode 100644
index 0506db1a4..000000000
--- a/images/emoji/1f6e5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6e9.png b/images/emoji/1f6e9.png
deleted file mode 100644
index b731b15e3..000000000
--- a/images/emoji/1f6e9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6eb.png b/images/emoji/1f6eb.png
deleted file mode 100644
index a5766f9f4..000000000
--- a/images/emoji/1f6eb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6ec.png b/images/emoji/1f6ec.png
deleted file mode 100644
index d66841962..000000000
--- a/images/emoji/1f6ec.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6f0.png b/images/emoji/1f6f0.png
deleted file mode 100644
index 4ba55d6e2..000000000
--- a/images/emoji/1f6f0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6f3.png b/images/emoji/1f6f3.png
deleted file mode 100644
index 19d4acbe4..000000000
--- a/images/emoji/1f6f3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6f4.png b/images/emoji/1f6f4.png
deleted file mode 100644
index 4ab7ef59c..000000000
--- a/images/emoji/1f6f4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6f5.png b/images/emoji/1f6f5.png
deleted file mode 100644
index c5afa72d8..000000000
--- a/images/emoji/1f6f5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f6f6.png b/images/emoji/1f6f6.png
deleted file mode 100644
index e26cdb9da..000000000
--- a/images/emoji/1f6f6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f910.png b/images/emoji/1f910.png
deleted file mode 100644
index f8ced2502..000000000
--- a/images/emoji/1f910.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f911.png b/images/emoji/1f911.png
deleted file mode 100644
index 75fd1e90c..000000000
--- a/images/emoji/1f911.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f912.png b/images/emoji/1f912.png
deleted file mode 100644
index 8a1e841af..000000000
--- a/images/emoji/1f912.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f913.png b/images/emoji/1f913.png
deleted file mode 100644
index 7820bd581..000000000
--- a/images/emoji/1f913.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f914.png b/images/emoji/1f914.png
deleted file mode 100644
index c18f6fd14..000000000
--- a/images/emoji/1f914.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f915.png b/images/emoji/1f915.png
deleted file mode 100644
index 53c7be1d2..000000000
--- a/images/emoji/1f915.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f916.png b/images/emoji/1f916.png
deleted file mode 100644
index 7cc62612c..000000000
--- a/images/emoji/1f916.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f917.png b/images/emoji/1f917.png
deleted file mode 100644
index f398b783a..000000000
--- a/images/emoji/1f917.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f918-1f3fb.png b/images/emoji/1f918-1f3fb.png
deleted file mode 100644
index c080d2add..000000000
--- a/images/emoji/1f918-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f918-1f3fc.png b/images/emoji/1f918-1f3fc.png
deleted file mode 100644
index 12313529b..000000000
--- a/images/emoji/1f918-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f918-1f3fd.png b/images/emoji/1f918-1f3fd.png
deleted file mode 100644
index ca9be6ae6..000000000
--- a/images/emoji/1f918-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f918-1f3fe.png b/images/emoji/1f918-1f3fe.png
deleted file mode 100644
index abe28cbf8..000000000
--- a/images/emoji/1f918-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f918-1f3ff.png b/images/emoji/1f918-1f3ff.png
deleted file mode 100644
index 0c6b5dd34..000000000
--- a/images/emoji/1f918-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f918.png b/images/emoji/1f918.png
deleted file mode 100644
index 4aa6e7e0a..000000000
--- a/images/emoji/1f918.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f919-1f3fb.png b/images/emoji/1f919-1f3fb.png
deleted file mode 100644
index 2c9320118..000000000
--- a/images/emoji/1f919-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f919-1f3fc.png b/images/emoji/1f919-1f3fc.png
deleted file mode 100644
index c39f45a41..000000000
--- a/images/emoji/1f919-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f919-1f3fd.png b/images/emoji/1f919-1f3fd.png
deleted file mode 100644
index 83a57f63c..000000000
--- a/images/emoji/1f919-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f919-1f3fe.png b/images/emoji/1f919-1f3fe.png
deleted file mode 100644
index 65b3468fe..000000000
--- a/images/emoji/1f919-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f919-1f3ff.png b/images/emoji/1f919-1f3ff.png
deleted file mode 100644
index 94ef68ff3..000000000
--- a/images/emoji/1f919-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f919.png b/images/emoji/1f919.png
deleted file mode 100644
index a10c59ba7..000000000
--- a/images/emoji/1f919.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91a-1f3fb.png b/images/emoji/1f91a-1f3fb.png
deleted file mode 100644
index 813d28499..000000000
--- a/images/emoji/1f91a-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91a-1f3fc.png b/images/emoji/1f91a-1f3fc.png
deleted file mode 100644
index 192ff795e..000000000
--- a/images/emoji/1f91a-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91a-1f3fd.png b/images/emoji/1f91a-1f3fd.png
deleted file mode 100644
index 61a727abe..000000000
--- a/images/emoji/1f91a-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91a-1f3fe.png b/images/emoji/1f91a-1f3fe.png
deleted file mode 100644
index 2e83da511..000000000
--- a/images/emoji/1f91a-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91a-1f3ff.png b/images/emoji/1f91a-1f3ff.png
deleted file mode 100644
index d7a5b95a0..000000000
--- a/images/emoji/1f91a-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91a.png b/images/emoji/1f91a.png
deleted file mode 100644
index 479234294..000000000
--- a/images/emoji/1f91a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91b-1f3fb.png b/images/emoji/1f91b-1f3fb.png
deleted file mode 100644
index 1262a6b4b..000000000
--- a/images/emoji/1f91b-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91b-1f3fc.png b/images/emoji/1f91b-1f3fc.png
deleted file mode 100644
index 40bf70b82..000000000
--- a/images/emoji/1f91b-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91b-1f3fd.png b/images/emoji/1f91b-1f3fd.png
deleted file mode 100644
index 93f581451..000000000
--- a/images/emoji/1f91b-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91b-1f3fe.png b/images/emoji/1f91b-1f3fe.png
deleted file mode 100644
index d82b5ec91..000000000
--- a/images/emoji/1f91b-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91b-1f3ff.png b/images/emoji/1f91b-1f3ff.png
deleted file mode 100644
index 09ae4cd49..000000000
--- a/images/emoji/1f91b-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91b.png b/images/emoji/1f91b.png
deleted file mode 100644
index a9d9fd8d5..000000000
--- a/images/emoji/1f91b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91c-1f3fb.png b/images/emoji/1f91c-1f3fb.png
deleted file mode 100644
index 33ded2f61..000000000
--- a/images/emoji/1f91c-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91c-1f3fc.png b/images/emoji/1f91c-1f3fc.png
deleted file mode 100644
index 88054e335..000000000
--- a/images/emoji/1f91c-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91c-1f3fd.png b/images/emoji/1f91c-1f3fd.png
deleted file mode 100644
index 84b9f5da7..000000000
--- a/images/emoji/1f91c-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91c-1f3fe.png b/images/emoji/1f91c-1f3fe.png
deleted file mode 100644
index e741cfea6..000000000
--- a/images/emoji/1f91c-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91c-1f3ff.png b/images/emoji/1f91c-1f3ff.png
deleted file mode 100644
index cf66d760c..000000000
--- a/images/emoji/1f91c-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91c.png b/images/emoji/1f91c.png
deleted file mode 100644
index 754ed066d..000000000
--- a/images/emoji/1f91c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91d-1f3fb.png b/images/emoji/1f91d-1f3fb.png
deleted file mode 100644
index 255fc7ec6..000000000
--- a/images/emoji/1f91d-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91d-1f3fc.png b/images/emoji/1f91d-1f3fc.png
deleted file mode 100644
index 1aec7450e..000000000
--- a/images/emoji/1f91d-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91d-1f3fd.png b/images/emoji/1f91d-1f3fd.png
deleted file mode 100644
index 104d65691..000000000
--- a/images/emoji/1f91d-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91d-1f3fe.png b/images/emoji/1f91d-1f3fe.png
deleted file mode 100644
index 999966d4b..000000000
--- a/images/emoji/1f91d-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91d-1f3ff.png b/images/emoji/1f91d-1f3ff.png
deleted file mode 100644
index 9a38f1b66..000000000
--- a/images/emoji/1f91d-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91d.png b/images/emoji/1f91d.png
deleted file mode 100644
index 75e8d58e9..000000000
--- a/images/emoji/1f91d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91e-1f3fb.png b/images/emoji/1f91e-1f3fb.png
deleted file mode 100644
index dd2384a6c..000000000
--- a/images/emoji/1f91e-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91e-1f3fc.png b/images/emoji/1f91e-1f3fc.png
deleted file mode 100644
index 6228401be..000000000
--- a/images/emoji/1f91e-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91e-1f3fd.png b/images/emoji/1f91e-1f3fd.png
deleted file mode 100644
index b1074da15..000000000
--- a/images/emoji/1f91e-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91e-1f3fe.png b/images/emoji/1f91e-1f3fe.png
deleted file mode 100644
index 75e05e4d3..000000000
--- a/images/emoji/1f91e-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91e-1f3ff.png b/images/emoji/1f91e-1f3ff.png
deleted file mode 100644
index 761aebdc3..000000000
--- a/images/emoji/1f91e-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f91e.png b/images/emoji/1f91e.png
deleted file mode 100644
index 4cd18514e..000000000
--- a/images/emoji/1f91e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f920.png b/images/emoji/1f920.png
deleted file mode 100644
index e67709b88..000000000
--- a/images/emoji/1f920.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f921.png b/images/emoji/1f921.png
deleted file mode 100644
index f0e05bac4..000000000
--- a/images/emoji/1f921.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f922.png b/images/emoji/1f922.png
deleted file mode 100644
index a566c109c..000000000
--- a/images/emoji/1f922.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f923.png b/images/emoji/1f923.png
deleted file mode 100644
index b1736fedf..000000000
--- a/images/emoji/1f923.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f924.png b/images/emoji/1f924.png
deleted file mode 100644
index a54605325..000000000
--- a/images/emoji/1f924.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f925.png b/images/emoji/1f925.png
deleted file mode 100644
index 02827e262..000000000
--- a/images/emoji/1f925.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f926-1f3fb.png b/images/emoji/1f926-1f3fb.png
deleted file mode 100644
index 2f4b010bb..000000000
--- a/images/emoji/1f926-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f926-1f3fc.png b/images/emoji/1f926-1f3fc.png
deleted file mode 100644
index 9cba0b0e1..000000000
--- a/images/emoji/1f926-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f926-1f3fd.png b/images/emoji/1f926-1f3fd.png
deleted file mode 100644
index b5b5c1e53..000000000
--- a/images/emoji/1f926-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f926-1f3fe.png b/images/emoji/1f926-1f3fe.png
deleted file mode 100644
index 2840b1134..000000000
--- a/images/emoji/1f926-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f926-1f3ff.png b/images/emoji/1f926-1f3ff.png
deleted file mode 100644
index 6f070db98..000000000
--- a/images/emoji/1f926-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f926.png b/images/emoji/1f926.png
deleted file mode 100644
index defc796cf..000000000
--- a/images/emoji/1f926.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f927.png b/images/emoji/1f927.png
deleted file mode 100644
index d6c796746..000000000
--- a/images/emoji/1f927.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f930-1f3fb.png b/images/emoji/1f930-1f3fb.png
deleted file mode 100644
index a78703b33..000000000
--- a/images/emoji/1f930-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f930-1f3fc.png b/images/emoji/1f930-1f3fc.png
deleted file mode 100644
index 0068c6c4a..000000000
--- a/images/emoji/1f930-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f930-1f3fd.png b/images/emoji/1f930-1f3fd.png
deleted file mode 100644
index 3206296b6..000000000
--- a/images/emoji/1f930-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f930-1f3fe.png b/images/emoji/1f930-1f3fe.png
deleted file mode 100644
index 120fda5cd..000000000
--- a/images/emoji/1f930-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f930-1f3ff.png b/images/emoji/1f930-1f3ff.png
deleted file mode 100644
index 569bfdf05..000000000
--- a/images/emoji/1f930-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f930.png b/images/emoji/1f930.png
deleted file mode 100644
index 084e83a41..000000000
--- a/images/emoji/1f930.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f933-1f3fb.png b/images/emoji/1f933-1f3fb.png
deleted file mode 100644
index 290e075b5..000000000
--- a/images/emoji/1f933-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f933-1f3fc.png b/images/emoji/1f933-1f3fc.png
deleted file mode 100644
index fcd9595b6..000000000
--- a/images/emoji/1f933-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f933-1f3fd.png b/images/emoji/1f933-1f3fd.png
deleted file mode 100644
index f3a22fdf4..000000000
--- a/images/emoji/1f933-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f933-1f3fe.png b/images/emoji/1f933-1f3fe.png
deleted file mode 100644
index cdecf6d9f..000000000
--- a/images/emoji/1f933-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f933-1f3ff.png b/images/emoji/1f933-1f3ff.png
deleted file mode 100644
index 86acbb6c2..000000000
--- a/images/emoji/1f933-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f933.png b/images/emoji/1f933.png
deleted file mode 100644
index 6a1ba75c7..000000000
--- a/images/emoji/1f933.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f934-1f3fb.png b/images/emoji/1f934-1f3fb.png
deleted file mode 100644
index 9102f9c46..000000000
--- a/images/emoji/1f934-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f934-1f3fc.png b/images/emoji/1f934-1f3fc.png
deleted file mode 100644
index 23d8b3b12..000000000
--- a/images/emoji/1f934-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f934-1f3fd.png b/images/emoji/1f934-1f3fd.png
deleted file mode 100644
index e7692efb7..000000000
--- a/images/emoji/1f934-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f934-1f3fe.png b/images/emoji/1f934-1f3fe.png
deleted file mode 100644
index 8e10f8be6..000000000
--- a/images/emoji/1f934-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f934-1f3ff.png b/images/emoji/1f934-1f3ff.png
deleted file mode 100644
index 138d4ea70..000000000
--- a/images/emoji/1f934-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f934.png b/images/emoji/1f934.png
deleted file mode 100644
index 38d69344c..000000000
--- a/images/emoji/1f934.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f935-1f3fb.png b/images/emoji/1f935-1f3fb.png
deleted file mode 100644
index 7b6b3acd9..000000000
--- a/images/emoji/1f935-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f935-1f3fc.png b/images/emoji/1f935-1f3fc.png
deleted file mode 100644
index 7975191b3..000000000
--- a/images/emoji/1f935-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f935-1f3fd.png b/images/emoji/1f935-1f3fd.png
deleted file mode 100644
index a2816f600..000000000
--- a/images/emoji/1f935-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f935-1f3fe.png b/images/emoji/1f935-1f3fe.png
deleted file mode 100644
index ea8291760..000000000
--- a/images/emoji/1f935-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f935-1f3ff.png b/images/emoji/1f935-1f3ff.png
deleted file mode 100644
index c743e05fc..000000000
--- a/images/emoji/1f935-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f935.png b/images/emoji/1f935.png
deleted file mode 100644
index 5f7e9303f..000000000
--- a/images/emoji/1f935.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f936-1f3fb.png b/images/emoji/1f936-1f3fb.png
deleted file mode 100644
index d8a695d70..000000000
--- a/images/emoji/1f936-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f936-1f3fc.png b/images/emoji/1f936-1f3fc.png
deleted file mode 100644
index 0e17e8c51..000000000
--- a/images/emoji/1f936-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f936-1f3fd.png b/images/emoji/1f936-1f3fd.png
deleted file mode 100644
index 195ebc400..000000000
--- a/images/emoji/1f936-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f936-1f3fe.png b/images/emoji/1f936-1f3fe.png
deleted file mode 100644
index 68a556da2..000000000
--- a/images/emoji/1f936-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f936-1f3ff.png b/images/emoji/1f936-1f3ff.png
deleted file mode 100644
index ccab3c40f..000000000
--- a/images/emoji/1f936-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f936.png b/images/emoji/1f936.png
deleted file mode 100644
index 078f0657f..000000000
--- a/images/emoji/1f936.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f937-1f3fb.png b/images/emoji/1f937-1f3fb.png
deleted file mode 100644
index 1c895e644..000000000
--- a/images/emoji/1f937-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f937-1f3fc.png b/images/emoji/1f937-1f3fc.png
deleted file mode 100644
index d76ac4b19..000000000
--- a/images/emoji/1f937-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f937-1f3fd.png b/images/emoji/1f937-1f3fd.png
deleted file mode 100644
index dc3a5a9fb..000000000
--- a/images/emoji/1f937-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f937-1f3fe.png b/images/emoji/1f937-1f3fe.png
deleted file mode 100644
index 5fbef3f22..000000000
--- a/images/emoji/1f937-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f937-1f3ff.png b/images/emoji/1f937-1f3ff.png
deleted file mode 100644
index 303640fe7..000000000
--- a/images/emoji/1f937-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f937.png b/images/emoji/1f937.png
deleted file mode 100644
index 76e63bfac..000000000
--- a/images/emoji/1f937.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f938-1f3fb.png b/images/emoji/1f938-1f3fb.png
deleted file mode 100644
index db6d65895..000000000
--- a/images/emoji/1f938-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f938-1f3fc.png b/images/emoji/1f938-1f3fc.png
deleted file mode 100644
index e00ffbc27..000000000
--- a/images/emoji/1f938-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f938-1f3fd.png b/images/emoji/1f938-1f3fd.png
deleted file mode 100644
index 49321be39..000000000
--- a/images/emoji/1f938-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f938-1f3fe.png b/images/emoji/1f938-1f3fe.png
deleted file mode 100644
index d4562b5e3..000000000
--- a/images/emoji/1f938-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f938-1f3ff.png b/images/emoji/1f938-1f3ff.png
deleted file mode 100644
index 6e09a8707..000000000
--- a/images/emoji/1f938-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f938.png b/images/emoji/1f938.png
deleted file mode 100644
index cbcaa5782..000000000
--- a/images/emoji/1f938.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f939-1f3fb.png b/images/emoji/1f939-1f3fb.png
deleted file mode 100644
index c18eda400..000000000
--- a/images/emoji/1f939-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f939-1f3fc.png b/images/emoji/1f939-1f3fc.png
deleted file mode 100644
index de3b7a555..000000000
--- a/images/emoji/1f939-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f939-1f3fd.png b/images/emoji/1f939-1f3fd.png
deleted file mode 100644
index 74ab6d854..000000000
--- a/images/emoji/1f939-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f939-1f3fe.png b/images/emoji/1f939-1f3fe.png
deleted file mode 100644
index 1c5782320..000000000
--- a/images/emoji/1f939-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f939-1f3ff.png b/images/emoji/1f939-1f3ff.png
deleted file mode 100644
index c343d6ee9..000000000
--- a/images/emoji/1f939-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f939.png b/images/emoji/1f939.png
deleted file mode 100644
index a37f6224a..000000000
--- a/images/emoji/1f939.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93a.png b/images/emoji/1f93a.png
deleted file mode 100644
index 9f6cb6ff8..000000000
--- a/images/emoji/1f93a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93b-1f3fb.png b/images/emoji/1f93b-1f3fb.png
deleted file mode 100644
index f29209325..000000000
--- a/images/emoji/1f93b-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93b-1f3fc.png b/images/emoji/1f93b-1f3fc.png
deleted file mode 100644
index fea2cc7ee..000000000
--- a/images/emoji/1f93b-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93b-1f3fd.png b/images/emoji/1f93b-1f3fd.png
deleted file mode 100644
index 030f32fdd..000000000
--- a/images/emoji/1f93b-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93b-1f3fe.png b/images/emoji/1f93b-1f3fe.png
deleted file mode 100644
index d4d011091..000000000
--- a/images/emoji/1f93b-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93b-1f3ff.png b/images/emoji/1f93b-1f3ff.png
deleted file mode 100644
index 69a9789f5..000000000
--- a/images/emoji/1f93b-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93b.png b/images/emoji/1f93b.png
deleted file mode 100644
index 71e67cfad..000000000
--- a/images/emoji/1f93b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93c-1f3fb.png b/images/emoji/1f93c-1f3fb.png
deleted file mode 100644
index 379070fd0..000000000
--- a/images/emoji/1f93c-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93c-1f3fc.png b/images/emoji/1f93c-1f3fc.png
deleted file mode 100644
index 6863ea920..000000000
--- a/images/emoji/1f93c-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93c-1f3fd.png b/images/emoji/1f93c-1f3fd.png
deleted file mode 100644
index b7e629101..000000000
--- a/images/emoji/1f93c-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93c-1f3fe.png b/images/emoji/1f93c-1f3fe.png
deleted file mode 100644
index 750f95892..000000000
--- a/images/emoji/1f93c-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93c-1f3ff.png b/images/emoji/1f93c-1f3ff.png
deleted file mode 100644
index 36ab9bb3f..000000000
--- a/images/emoji/1f93c-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93c.png b/images/emoji/1f93c.png
deleted file mode 100644
index 9838f24e5..000000000
--- a/images/emoji/1f93c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93d-1f3fb.png b/images/emoji/1f93d-1f3fb.png
deleted file mode 100644
index bed1a908d..000000000
--- a/images/emoji/1f93d-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93d-1f3fc.png b/images/emoji/1f93d-1f3fc.png
deleted file mode 100644
index 2e44151d3..000000000
--- a/images/emoji/1f93d-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93d-1f3fd.png b/images/emoji/1f93d-1f3fd.png
deleted file mode 100644
index b081a4a5a..000000000
--- a/images/emoji/1f93d-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93d-1f3fe.png b/images/emoji/1f93d-1f3fe.png
deleted file mode 100644
index 82cfbc3b0..000000000
--- a/images/emoji/1f93d-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93d-1f3ff.png b/images/emoji/1f93d-1f3ff.png
deleted file mode 100644
index 6b8e245dc..000000000
--- a/images/emoji/1f93d-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93d.png b/images/emoji/1f93d.png
deleted file mode 100644
index 8d6114761..000000000
--- a/images/emoji/1f93d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93e-1f3fb.png b/images/emoji/1f93e-1f3fb.png
deleted file mode 100644
index a68057a7d..000000000
--- a/images/emoji/1f93e-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93e-1f3fc.png b/images/emoji/1f93e-1f3fc.png
deleted file mode 100644
index 74972f8a5..000000000
--- a/images/emoji/1f93e-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93e-1f3fd.png b/images/emoji/1f93e-1f3fd.png
deleted file mode 100644
index 0e3a37c3d..000000000
--- a/images/emoji/1f93e-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93e-1f3fe.png b/images/emoji/1f93e-1f3fe.png
deleted file mode 100644
index e1233f382..000000000
--- a/images/emoji/1f93e-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93e-1f3ff.png b/images/emoji/1f93e-1f3ff.png
deleted file mode 100644
index 6b1eb9b64..000000000
--- a/images/emoji/1f93e-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93e.png b/images/emoji/1f93e.png
deleted file mode 100644
index cb4457678..000000000
--- a/images/emoji/1f93e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f93f.png b/images/emoji/1f93f.png
deleted file mode 100644
index 677c060b4..000000000
--- a/images/emoji/1f93f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f940.png b/images/emoji/1f940.png
deleted file mode 100644
index 62412b143..000000000
--- a/images/emoji/1f940.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f942.png b/images/emoji/1f942.png
deleted file mode 100644
index 32f18d4c9..000000000
--- a/images/emoji/1f942.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f943.png b/images/emoji/1f943.png
deleted file mode 100644
index 7bf092298..000000000
--- a/images/emoji/1f943.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f944.png b/images/emoji/1f944.png
deleted file mode 100644
index 3c4da766a..000000000
--- a/images/emoji/1f944.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f945.png b/images/emoji/1f945.png
deleted file mode 100644
index 3bec11c5b..000000000
--- a/images/emoji/1f945.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f946.png b/images/emoji/1f946.png
deleted file mode 100644
index 2815a1bb3..000000000
--- a/images/emoji/1f946.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f947.png b/images/emoji/1f947.png
deleted file mode 100644
index 83011ad99..000000000
--- a/images/emoji/1f947.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f948.png b/images/emoji/1f948.png
deleted file mode 100644
index 41926fcf5..000000000
--- a/images/emoji/1f948.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f949.png b/images/emoji/1f949.png
deleted file mode 100644
index c713851bc..000000000
--- a/images/emoji/1f949.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f950.png b/images/emoji/1f950.png
deleted file mode 100644
index 502df5b15..000000000
--- a/images/emoji/1f950.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f951.png b/images/emoji/1f951.png
deleted file mode 100644
index 96b847232..000000000
--- a/images/emoji/1f951.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f952.png b/images/emoji/1f952.png
deleted file mode 100644
index c01fd0edd..000000000
--- a/images/emoji/1f952.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f953.png b/images/emoji/1f953.png
deleted file mode 100644
index f38a485fb..000000000
--- a/images/emoji/1f953.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f954.png b/images/emoji/1f954.png
deleted file mode 100644
index 5fa341216..000000000
--- a/images/emoji/1f954.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f955.png b/images/emoji/1f955.png
deleted file mode 100644
index c68829b58..000000000
--- a/images/emoji/1f955.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f956.png b/images/emoji/1f956.png
deleted file mode 100644
index 72477ff78..000000000
--- a/images/emoji/1f956.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f957.png b/images/emoji/1f957.png
deleted file mode 100644
index c89f93411..000000000
--- a/images/emoji/1f957.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f958.png b/images/emoji/1f958.png
deleted file mode 100644
index 663a1006a..000000000
--- a/images/emoji/1f958.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f959.png b/images/emoji/1f959.png
deleted file mode 100644
index a2e10df40..000000000
--- a/images/emoji/1f959.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f95a.png b/images/emoji/1f95a.png
deleted file mode 100644
index c171974d9..000000000
--- a/images/emoji/1f95a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f95b.png b/images/emoji/1f95b.png
deleted file mode 100644
index e4fcf2e64..000000000
--- a/images/emoji/1f95b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f95c.png b/images/emoji/1f95c.png
deleted file mode 100644
index b64fadad0..000000000
--- a/images/emoji/1f95c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f95d.png b/images/emoji/1f95d.png
deleted file mode 100644
index f04835776..000000000
--- a/images/emoji/1f95d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f95e.png b/images/emoji/1f95e.png
deleted file mode 100644
index 6223d1a28..000000000
--- a/images/emoji/1f95e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f960.png b/images/emoji/1f960.png
deleted file mode 100644
index e890c30d4..000000000
--- a/images/emoji/1f960.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f961.png b/images/emoji/1f961.png
deleted file mode 100644
index 4d09f0ee4..000000000
--- a/images/emoji/1f961.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f980.png b/images/emoji/1f980.png
deleted file mode 100644
index ca9350f51..000000000
--- a/images/emoji/1f980.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f981.png b/images/emoji/1f981.png
deleted file mode 100644
index 5062ab47e..000000000
--- a/images/emoji/1f981.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f982.png b/images/emoji/1f982.png
deleted file mode 100644
index 449a6b281..000000000
--- a/images/emoji/1f982.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f983.png b/images/emoji/1f983.png
deleted file mode 100644
index 344af94c9..000000000
--- a/images/emoji/1f983.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f984.png b/images/emoji/1f984.png
deleted file mode 100644
index 05a97969f..000000000
--- a/images/emoji/1f984.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f985.png b/images/emoji/1f985.png
deleted file mode 100644
index 4f277debe..000000000
--- a/images/emoji/1f985.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f986.png b/images/emoji/1f986.png
deleted file mode 100644
index 74330b77c..000000000
--- a/images/emoji/1f986.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f987.png b/images/emoji/1f987.png
deleted file mode 100644
index c8f23c515..000000000
--- a/images/emoji/1f987.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f988.png b/images/emoji/1f988.png
deleted file mode 100644
index c75076d57..000000000
--- a/images/emoji/1f988.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f989.png b/images/emoji/1f989.png
deleted file mode 100644
index a2c318b15..000000000
--- a/images/emoji/1f989.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f98a.png b/images/emoji/1f98a.png
deleted file mode 100644
index aaf1dad35..000000000
--- a/images/emoji/1f98a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f98b.png b/images/emoji/1f98b.png
deleted file mode 100644
index 5631fe992..000000000
--- a/images/emoji/1f98b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f98c.png b/images/emoji/1f98c.png
deleted file mode 100644
index 4a501f880..000000000
--- a/images/emoji/1f98c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f98d.png b/images/emoji/1f98d.png
deleted file mode 100644
index 4f2f9bb38..000000000
--- a/images/emoji/1f98d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f98e.png b/images/emoji/1f98e.png
deleted file mode 100644
index 836387605..000000000
--- a/images/emoji/1f98e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f98f.png b/images/emoji/1f98f.png
deleted file mode 100644
index 12f4e0d9d..000000000
--- a/images/emoji/1f98f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f990.png b/images/emoji/1f990.png
deleted file mode 100644
index 49eff28a7..000000000
--- a/images/emoji/1f990.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f991.png b/images/emoji/1f991.png
deleted file mode 100644
index f01eeba24..000000000
--- a/images/emoji/1f991.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/1f9c0.png b/images/emoji/1f9c0.png
deleted file mode 100644
index 00e997622..000000000
--- a/images/emoji/1f9c0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/203c.png b/images/emoji/203c.png
deleted file mode 100644
index 58a9c528f..000000000
--- a/images/emoji/203c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2049.png b/images/emoji/2049.png
deleted file mode 100644
index 509813e9b..000000000
--- a/images/emoji/2049.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2122.png b/images/emoji/2122.png
deleted file mode 100644
index 7a0c44a2c..000000000
--- a/images/emoji/2122.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2139.png b/images/emoji/2139.png
deleted file mode 100644
index 871f2db93..000000000
--- a/images/emoji/2139.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2194.png b/images/emoji/2194.png
deleted file mode 100644
index 7937f24f2..000000000
--- a/images/emoji/2194.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2195.png b/images/emoji/2195.png
deleted file mode 100644
index dfa32b971..000000000
--- a/images/emoji/2195.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2196.png b/images/emoji/2196.png
deleted file mode 100644
index f38718fbe..000000000
--- a/images/emoji/2196.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2197.png b/images/emoji/2197.png
deleted file mode 100644
index c43e12d0f..000000000
--- a/images/emoji/2197.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2198.png b/images/emoji/2198.png
deleted file mode 100644
index 7e807da73..000000000
--- a/images/emoji/2198.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2199.png b/images/emoji/2199.png
deleted file mode 100644
index 88b377160..000000000
--- a/images/emoji/2199.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/21a9.png b/images/emoji/21a9.png
deleted file mode 100644
index ba45c2ad9..000000000
--- a/images/emoji/21a9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/21aa.png b/images/emoji/21aa.png
deleted file mode 100644
index e7258ad32..000000000
--- a/images/emoji/21aa.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/231a.png b/images/emoji/231a.png
deleted file mode 100644
index 64819bc6e..000000000
--- a/images/emoji/231a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/231b.png b/images/emoji/231b.png
deleted file mode 100644
index a5db2d1d3..000000000
--- a/images/emoji/231b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2328.png b/images/emoji/2328.png
deleted file mode 100644
index 75027cb9a..000000000
--- a/images/emoji/2328.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/23cf.png b/images/emoji/23cf.png
deleted file mode 100644
index ec5cfc489..000000000
--- a/images/emoji/23cf.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/23e9.png b/images/emoji/23e9.png
deleted file mode 100644
index c406fedfd..000000000
--- a/images/emoji/23e9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/23ea.png b/images/emoji/23ea.png
deleted file mode 100644
index e22e2bd3d..000000000
--- a/images/emoji/23ea.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/23eb.png b/images/emoji/23eb.png
deleted file mode 100644
index 13543d5ee..000000000
--- a/images/emoji/23eb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/23ec.png b/images/emoji/23ec.png
deleted file mode 100644
index 90193bfcb..000000000
--- a/images/emoji/23ec.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/23ed.png b/images/emoji/23ed.png
deleted file mode 100644
index f8880d33b..000000000
--- a/images/emoji/23ed.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/23ee.png b/images/emoji/23ee.png
deleted file mode 100644
index 1ffd0566c..000000000
--- a/images/emoji/23ee.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/23ef.png b/images/emoji/23ef.png
deleted file mode 100644
index a9f857139..000000000
--- a/images/emoji/23ef.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/23f0.png b/images/emoji/23f0.png
deleted file mode 100644
index cdbc2fbb9..000000000
--- a/images/emoji/23f0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/23f1.png b/images/emoji/23f1.png
deleted file mode 100644
index 6a3a2ef64..000000000
--- a/images/emoji/23f1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/23f2.png b/images/emoji/23f2.png
deleted file mode 100644
index 8a3be574c..000000000
--- a/images/emoji/23f2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/23f3.png b/images/emoji/23f3.png
deleted file mode 100644
index b93b15ed6..000000000
--- a/images/emoji/23f3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/23f8.png b/images/emoji/23f8.png
deleted file mode 100644
index 4f07e7ebf..000000000
--- a/images/emoji/23f8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/23f9.png b/images/emoji/23f9.png
deleted file mode 100644
index cfa99988a..000000000
--- a/images/emoji/23f9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/23fa.png b/images/emoji/23fa.png
deleted file mode 100644
index ada52830f..000000000
--- a/images/emoji/23fa.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/24c2.png b/images/emoji/24c2.png
deleted file mode 100644
index 8a3506fc1..000000000
--- a/images/emoji/24c2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/25aa.png b/images/emoji/25aa.png
deleted file mode 100644
index 48595d3e1..000000000
--- a/images/emoji/25aa.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/25ab.png b/images/emoji/25ab.png
deleted file mode 100644
index d7ebdb0c0..000000000
--- a/images/emoji/25ab.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/25b6.png b/images/emoji/25b6.png
deleted file mode 100644
index 4e2b68285..000000000
--- a/images/emoji/25b6.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/25c0.png b/images/emoji/25c0.png
deleted file mode 100644
index ee38e3b03..000000000
--- a/images/emoji/25c0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/25fb.png b/images/emoji/25fb.png
deleted file mode 100644
index 8daacf570..000000000
--- a/images/emoji/25fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/25fc.png b/images/emoji/25fc.png
deleted file mode 100644
index 05a30a6aa..000000000
--- a/images/emoji/25fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/25fd.png b/images/emoji/25fd.png
deleted file mode 100644
index ae8741267..000000000
--- a/images/emoji/25fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/25fe.png b/images/emoji/25fe.png
deleted file mode 100644
index 39765bba6..000000000
--- a/images/emoji/25fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2600.png b/images/emoji/2600.png
deleted file mode 100644
index fd521ae31..000000000
--- a/images/emoji/2600.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2601.png b/images/emoji/2601.png
deleted file mode 100644
index 5b4f57f77..000000000
--- a/images/emoji/2601.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2602.png b/images/emoji/2602.png
deleted file mode 100644
index 97fe859e7..000000000
--- a/images/emoji/2602.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2603.png b/images/emoji/2603.png
deleted file mode 100644
index 896f28502..000000000
--- a/images/emoji/2603.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2604.png b/images/emoji/2604.png
deleted file mode 100644
index d775d6387..000000000
--- a/images/emoji/2604.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/260e.png b/images/emoji/260e.png
deleted file mode 100644
index 0fbb8c12c..000000000
--- a/images/emoji/260e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2611.png b/images/emoji/2611.png
deleted file mode 100644
index 284d95738..000000000
--- a/images/emoji/2611.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2614.png b/images/emoji/2614.png
deleted file mode 100644
index 5b35b7ff6..000000000
--- a/images/emoji/2614.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2615.png b/images/emoji/2615.png
deleted file mode 100644
index 553061471..000000000
--- a/images/emoji/2615.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2618.png b/images/emoji/2618.png
deleted file mode 100644
index f202aecfe..000000000
--- a/images/emoji/2618.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/261d-1f3fb.png b/images/emoji/261d-1f3fb.png
deleted file mode 100644
index 6a9db21d6..000000000
--- a/images/emoji/261d-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/261d-1f3fc.png b/images/emoji/261d-1f3fc.png
deleted file mode 100644
index 15aa9ea0e..000000000
--- a/images/emoji/261d-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/261d-1f3fd.png b/images/emoji/261d-1f3fd.png
deleted file mode 100644
index 652b73a9c..000000000
--- a/images/emoji/261d-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/261d-1f3fe.png b/images/emoji/261d-1f3fe.png
deleted file mode 100644
index 692bad926..000000000
--- a/images/emoji/261d-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/261d-1f3ff.png b/images/emoji/261d-1f3ff.png
deleted file mode 100644
index 1e1b10fb7..000000000
--- a/images/emoji/261d-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/261d.png b/images/emoji/261d.png
deleted file mode 100644
index f4978ff0f..000000000
--- a/images/emoji/261d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2620.png b/images/emoji/2620.png
deleted file mode 100644
index b459df922..000000000
--- a/images/emoji/2620.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2622.png b/images/emoji/2622.png
deleted file mode 100644
index 3b46199fe..000000000
--- a/images/emoji/2622.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2623.png b/images/emoji/2623.png
deleted file mode 100644
index 007b4fc2d..000000000
--- a/images/emoji/2623.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2626.png b/images/emoji/2626.png
deleted file mode 100644
index 0530e33a4..000000000
--- a/images/emoji/2626.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/262a.png b/images/emoji/262a.png
deleted file mode 100644
index e18263645..000000000
--- a/images/emoji/262a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/262e.png b/images/emoji/262e.png
deleted file mode 100644
index 86033faf4..000000000
--- a/images/emoji/262e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/262f.png b/images/emoji/262f.png
deleted file mode 100644
index f2900f633..000000000
--- a/images/emoji/262f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2638.png b/images/emoji/2638.png
deleted file mode 100644
index 3666db001..000000000
--- a/images/emoji/2638.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2639.png b/images/emoji/2639.png
deleted file mode 100644
index 6ae71f233..000000000
--- a/images/emoji/2639.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/263a.png b/images/emoji/263a.png
deleted file mode 100644
index e9e53c03d..000000000
--- a/images/emoji/263a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2648.png b/images/emoji/2648.png
deleted file mode 100644
index 21a189d0e..000000000
--- a/images/emoji/2648.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2649.png b/images/emoji/2649.png
deleted file mode 100644
index b2a370df4..000000000
--- a/images/emoji/2649.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/264a.png b/images/emoji/264a.png
deleted file mode 100644
index 1a09698cf..000000000
--- a/images/emoji/264a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/264b.png b/images/emoji/264b.png
deleted file mode 100644
index a64af07cb..000000000
--- a/images/emoji/264b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/264c.png b/images/emoji/264c.png
deleted file mode 100644
index 30158d34d..000000000
--- a/images/emoji/264c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/264d.png b/images/emoji/264d.png
deleted file mode 100644
index a6b56c2cb..000000000
--- a/images/emoji/264d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/264e.png b/images/emoji/264e.png
deleted file mode 100644
index 8fd133a35..000000000
--- a/images/emoji/264e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/264f.png b/images/emoji/264f.png
deleted file mode 100644
index c31a99204..000000000
--- a/images/emoji/264f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2650.png b/images/emoji/2650.png
deleted file mode 100644
index f8d94ff29..000000000
--- a/images/emoji/2650.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2651.png b/images/emoji/2651.png
deleted file mode 100644
index 6293d31d4..000000000
--- a/images/emoji/2651.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2652.png b/images/emoji/2652.png
deleted file mode 100644
index 641a4f688..000000000
--- a/images/emoji/2652.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2653.png b/images/emoji/2653.png
deleted file mode 100644
index 7f6f646a9..000000000
--- a/images/emoji/2653.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2660.png b/images/emoji/2660.png
deleted file mode 100644
index f822f184c..000000000
--- a/images/emoji/2660.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2663.png b/images/emoji/2663.png
deleted file mode 100644
index 4f2abf791..000000000
--- a/images/emoji/2663.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2666.png b/images/emoji/2666.png
deleted file mode 100644
index 1f25f51f9..000000000
--- a/images/emoji/2666.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2668.png b/images/emoji/2668.png
deleted file mode 100644
index 3d9df2d94..000000000
--- a/images/emoji/2668.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/267b.png b/images/emoji/267b.png
deleted file mode 100644
index 9221f095c..000000000
--- a/images/emoji/267b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/267f.png b/images/emoji/267f.png
deleted file mode 100644
index 4e5b2698e..000000000
--- a/images/emoji/267f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2692.png b/images/emoji/2692.png
deleted file mode 100644
index 3bee30ec5..000000000
--- a/images/emoji/2692.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2693.png b/images/emoji/2693.png
deleted file mode 100644
index b036f70a0..000000000
--- a/images/emoji/2693.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2694.png b/images/emoji/2694.png
deleted file mode 100644
index 907e96071..000000000
--- a/images/emoji/2694.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2696.png b/images/emoji/2696.png
deleted file mode 100644
index 0757eda16..000000000
--- a/images/emoji/2696.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2697.png b/images/emoji/2697.png
deleted file mode 100644
index 307a73242..000000000
--- a/images/emoji/2697.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2699.png b/images/emoji/2699.png
deleted file mode 100644
index 2a1cc2c0f..000000000
--- a/images/emoji/2699.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/269b.png b/images/emoji/269b.png
deleted file mode 100644
index 5f4567aa0..000000000
--- a/images/emoji/269b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/269c.png b/images/emoji/269c.png
deleted file mode 100644
index c9250d27f..000000000
--- a/images/emoji/269c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26a0.png b/images/emoji/26a0.png
deleted file mode 100644
index 35691c2ed..000000000
--- a/images/emoji/26a0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26a1.png b/images/emoji/26a1.png
deleted file mode 100644
index 47e68e48e..000000000
--- a/images/emoji/26a1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26aa.png b/images/emoji/26aa.png
deleted file mode 100644
index c19e15684..000000000
--- a/images/emoji/26aa.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26ab.png b/images/emoji/26ab.png
deleted file mode 100644
index b62b87170..000000000
--- a/images/emoji/26ab.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26b0.png b/images/emoji/26b0.png
deleted file mode 100644
index fb2932aa5..000000000
--- a/images/emoji/26b0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26b1.png b/images/emoji/26b1.png
deleted file mode 100644
index 6b5b35034..000000000
--- a/images/emoji/26b1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26bd.png b/images/emoji/26bd.png
deleted file mode 100644
index 28cfa218d..000000000
--- a/images/emoji/26bd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26be.png b/images/emoji/26be.png
deleted file mode 100644
index f8463f153..000000000
--- a/images/emoji/26be.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26c4.png b/images/emoji/26c4.png
deleted file mode 100644
index 20c177c2a..000000000
--- a/images/emoji/26c4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26c5.png b/images/emoji/26c5.png
deleted file mode 100644
index a55e59c34..000000000
--- a/images/emoji/26c5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26c8.png b/images/emoji/26c8.png
deleted file mode 100644
index 31a26a1b6..000000000
--- a/images/emoji/26c8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26ce.png b/images/emoji/26ce.png
deleted file mode 100644
index 0a780a700..000000000
--- a/images/emoji/26ce.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26cf.png b/images/emoji/26cf.png
deleted file mode 100644
index 6370fe6d7..000000000
--- a/images/emoji/26cf.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26d1.png b/images/emoji/26d1.png
deleted file mode 100644
index 7140a6760..000000000
--- a/images/emoji/26d1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26d3.png b/images/emoji/26d3.png
deleted file mode 100644
index 57f46139a..000000000
--- a/images/emoji/26d3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26d4.png b/images/emoji/26d4.png
deleted file mode 100644
index 476800fc5..000000000
--- a/images/emoji/26d4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26e9.png b/images/emoji/26e9.png
deleted file mode 100644
index 5a344975b..000000000
--- a/images/emoji/26e9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26ea.png b/images/emoji/26ea.png
deleted file mode 100644
index 24df10f1a..000000000
--- a/images/emoji/26ea.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26f0.png b/images/emoji/26f0.png
deleted file mode 100644
index 6722ebdd2..000000000
--- a/images/emoji/26f0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26f1.png b/images/emoji/26f1.png
deleted file mode 100644
index 258e1e757..000000000
--- a/images/emoji/26f1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26f2.png b/images/emoji/26f2.png
deleted file mode 100644
index 293f5d91c..000000000
--- a/images/emoji/26f2.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26f3.png b/images/emoji/26f3.png
deleted file mode 100644
index f65a21d8a..000000000
--- a/images/emoji/26f3.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26f4.png b/images/emoji/26f4.png
deleted file mode 100644
index 41816b3ae..000000000
--- a/images/emoji/26f4.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26f5.png b/images/emoji/26f5.png
deleted file mode 100644
index 772ef11da..000000000
--- a/images/emoji/26f5.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26f7.png b/images/emoji/26f7.png
deleted file mode 100644
index 2eb3bdce2..000000000
--- a/images/emoji/26f7.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26f8.png b/images/emoji/26f8.png
deleted file mode 100644
index c56b7b8a5..000000000
--- a/images/emoji/26f8.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26f9-1f3fb.png b/images/emoji/26f9-1f3fb.png
deleted file mode 100644
index 43f97e7c3..000000000
--- a/images/emoji/26f9-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26f9-1f3fc.png b/images/emoji/26f9-1f3fc.png
deleted file mode 100644
index f892fd596..000000000
--- a/images/emoji/26f9-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26f9-1f3fd.png b/images/emoji/26f9-1f3fd.png
deleted file mode 100644
index e109997a9..000000000
--- a/images/emoji/26f9-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26f9-1f3fe.png b/images/emoji/26f9-1f3fe.png
deleted file mode 100644
index 354e8f9c2..000000000
--- a/images/emoji/26f9-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26f9-1f3ff.png b/images/emoji/26f9-1f3ff.png
deleted file mode 100644
index 9581dbbea..000000000
--- a/images/emoji/26f9-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26f9.png b/images/emoji/26f9.png
deleted file mode 100644
index 63bff9c3e..000000000
--- a/images/emoji/26f9.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26fa.png b/images/emoji/26fa.png
deleted file mode 100644
index 3fddcfc56..000000000
--- a/images/emoji/26fa.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/26fd.png b/images/emoji/26fd.png
deleted file mode 100644
index 05b187944..000000000
--- a/images/emoji/26fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2702.png b/images/emoji/2702.png
deleted file mode 100644
index 270571c8c..000000000
--- a/images/emoji/2702.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2705.png b/images/emoji/2705.png
deleted file mode 100644
index e55f087e5..000000000
--- a/images/emoji/2705.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2708.png b/images/emoji/2708.png
deleted file mode 100644
index 268d2ac3c..000000000
--- a/images/emoji/2708.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2709.png b/images/emoji/2709.png
deleted file mode 100644
index ec77ac375..000000000
--- a/images/emoji/2709.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270a-1f3fb.png b/images/emoji/270a-1f3fb.png
deleted file mode 100644
index 02809e2dd..000000000
--- a/images/emoji/270a-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270a-1f3fc.png b/images/emoji/270a-1f3fc.png
deleted file mode 100644
index 5de348103..000000000
--- a/images/emoji/270a-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270a-1f3fd.png b/images/emoji/270a-1f3fd.png
deleted file mode 100644
index 0d5240129..000000000
--- a/images/emoji/270a-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270a-1f3fe.png b/images/emoji/270a-1f3fe.png
deleted file mode 100644
index a95c0dd63..000000000
--- a/images/emoji/270a-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270a-1f3ff.png b/images/emoji/270a-1f3ff.png
deleted file mode 100644
index a2f092fd8..000000000
--- a/images/emoji/270a-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270a.png b/images/emoji/270a.png
deleted file mode 100644
index de33592bf..000000000
--- a/images/emoji/270a.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270b-1f3fb.png b/images/emoji/270b-1f3fb.png
deleted file mode 100644
index 3b752902c..000000000
--- a/images/emoji/270b-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270b-1f3fc.png b/images/emoji/270b-1f3fc.png
deleted file mode 100644
index 44e2a514c..000000000
--- a/images/emoji/270b-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270b-1f3fd.png b/images/emoji/270b-1f3fd.png
deleted file mode 100644
index 5bb62a752..000000000
--- a/images/emoji/270b-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270b-1f3fe.png b/images/emoji/270b-1f3fe.png
deleted file mode 100644
index c7f8c9ec2..000000000
--- a/images/emoji/270b-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270b-1f3ff.png b/images/emoji/270b-1f3ff.png
deleted file mode 100644
index c601b58a7..000000000
--- a/images/emoji/270b-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270b.png b/images/emoji/270b.png
deleted file mode 100644
index 6b2954315..000000000
--- a/images/emoji/270b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270c-1f3fb.png b/images/emoji/270c-1f3fb.png
deleted file mode 100644
index 6ac54a745..000000000
--- a/images/emoji/270c-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270c-1f3fc.png b/images/emoji/270c-1f3fc.png
deleted file mode 100644
index 6dd966986..000000000
--- a/images/emoji/270c-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270c-1f3fd.png b/images/emoji/270c-1f3fd.png
deleted file mode 100644
index a615e53f0..000000000
--- a/images/emoji/270c-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270c-1f3fe.png b/images/emoji/270c-1f3fe.png
deleted file mode 100644
index 33a34bd5a..000000000
--- a/images/emoji/270c-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270c-1f3ff.png b/images/emoji/270c-1f3ff.png
deleted file mode 100644
index 45ad14b6c..000000000
--- a/images/emoji/270c-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270c.png b/images/emoji/270c.png
deleted file mode 100644
index 70c5516ff..000000000
--- a/images/emoji/270c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270d-1f3fb.png b/images/emoji/270d-1f3fb.png
deleted file mode 100644
index 7923d8ebb..000000000
--- a/images/emoji/270d-1f3fb.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270d-1f3fc.png b/images/emoji/270d-1f3fc.png
deleted file mode 100644
index bcb304e15..000000000
--- a/images/emoji/270d-1f3fc.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270d-1f3fd.png b/images/emoji/270d-1f3fd.png
deleted file mode 100644
index fd885fd2d..000000000
--- a/images/emoji/270d-1f3fd.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270d-1f3fe.png b/images/emoji/270d-1f3fe.png
deleted file mode 100644
index d065b8c64..000000000
--- a/images/emoji/270d-1f3fe.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270d-1f3ff.png b/images/emoji/270d-1f3ff.png
deleted file mode 100644
index a44b3dd75..000000000
--- a/images/emoji/270d-1f3ff.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270d.png b/images/emoji/270d.png
deleted file mode 100644
index 85639f8ac..000000000
--- a/images/emoji/270d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/270f.png b/images/emoji/270f.png
deleted file mode 100644
index 3833d590f..000000000
--- a/images/emoji/270f.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2712.png b/images/emoji/2712.png
deleted file mode 100644
index 872d0ae15..000000000
--- a/images/emoji/2712.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2714.png b/images/emoji/2714.png
deleted file mode 100644
index 03bd69537..000000000
--- a/images/emoji/2714.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2716.png b/images/emoji/2716.png
deleted file mode 100644
index e47cc1b68..000000000
--- a/images/emoji/2716.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/271d.png b/images/emoji/271d.png
deleted file mode 100644
index 42b10e822..000000000
--- a/images/emoji/271d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2721.png b/images/emoji/2721.png
deleted file mode 100644
index fc59d0dde..000000000
--- a/images/emoji/2721.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2728.png b/images/emoji/2728.png
deleted file mode 100644
index 169bc10b0..000000000
--- a/images/emoji/2728.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2733.png b/images/emoji/2733.png
deleted file mode 100644
index 3307ffa62..000000000
--- a/images/emoji/2733.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2734.png b/images/emoji/2734.png
deleted file mode 100644
index 820179bda..000000000
--- a/images/emoji/2734.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2744.png b/images/emoji/2744.png
deleted file mode 100644
index db319a77e..000000000
--- a/images/emoji/2744.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2747.png b/images/emoji/2747.png
deleted file mode 100644
index 6aa7b6ec9..000000000
--- a/images/emoji/2747.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/274c.png b/images/emoji/274c.png
deleted file mode 100644
index 9f9ed0f7a..000000000
--- a/images/emoji/274c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/274e.png b/images/emoji/274e.png
deleted file mode 100644
index dae487f1f..000000000
--- a/images/emoji/274e.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2753.png b/images/emoji/2753.png
deleted file mode 100644
index 5a58f3458..000000000
--- a/images/emoji/2753.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2754.png b/images/emoji/2754.png
deleted file mode 100644
index 6e7824c75..000000000
--- a/images/emoji/2754.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2755.png b/images/emoji/2755.png
deleted file mode 100644
index 9b64da8bf..000000000
--- a/images/emoji/2755.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2757.png b/images/emoji/2757.png
deleted file mode 100644
index 2c1440642..000000000
--- a/images/emoji/2757.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2763.png b/images/emoji/2763.png
deleted file mode 100644
index 91b520be4..000000000
--- a/images/emoji/2763.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2764.png b/images/emoji/2764.png
deleted file mode 100644
index 638cb72dc..000000000
--- a/images/emoji/2764.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2795.png b/images/emoji/2795.png
deleted file mode 100644
index 40799798a..000000000
--- a/images/emoji/2795.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2796.png b/images/emoji/2796.png
deleted file mode 100644
index 054211caf..000000000
--- a/images/emoji/2796.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2797.png b/images/emoji/2797.png
deleted file mode 100644
index df32ab21b..000000000
--- a/images/emoji/2797.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/27a1.png b/images/emoji/27a1.png
deleted file mode 100644
index 4755670b5..000000000
--- a/images/emoji/27a1.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/27b0.png b/images/emoji/27b0.png
deleted file mode 100644
index 440aa56d5..000000000
--- a/images/emoji/27b0.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/27bf.png b/images/emoji/27bf.png
deleted file mode 100644
index 0b82c8fe3..000000000
--- a/images/emoji/27bf.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2934.png b/images/emoji/2934.png
deleted file mode 100644
index f29bfcfc0..000000000
--- a/images/emoji/2934.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2935.png b/images/emoji/2935.png
deleted file mode 100644
index 2d9d24bca..000000000
--- a/images/emoji/2935.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2b05.png b/images/emoji/2b05.png
deleted file mode 100644
index 8c685e0a8..000000000
--- a/images/emoji/2b05.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2b06.png b/images/emoji/2b06.png
deleted file mode 100644
index af8218a87..000000000
--- a/images/emoji/2b06.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2b07.png b/images/emoji/2b07.png
deleted file mode 100644
index b8eefd0b1..000000000
--- a/images/emoji/2b07.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2b1b.png b/images/emoji/2b1b.png
deleted file mode 100644
index 162f2bb42..000000000
--- a/images/emoji/2b1b.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2b1c.png b/images/emoji/2b1c.png
deleted file mode 100644
index 6f06c1c79..000000000
--- a/images/emoji/2b1c.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2b50.png b/images/emoji/2b50.png
deleted file mode 100644
index c93094707..000000000
--- a/images/emoji/2b50.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/2b55.png b/images/emoji/2b55.png
deleted file mode 100644
index 3fe75ce46..000000000
--- a/images/emoji/2b55.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/3030.png b/images/emoji/3030.png
deleted file mode 100644
index 001c8d6e4..000000000
--- a/images/emoji/3030.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/303d.png b/images/emoji/303d.png
deleted file mode 100644
index 70453d415..000000000
--- a/images/emoji/303d.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/3297.png b/images/emoji/3297.png
deleted file mode 100644
index ba8c89d95..000000000
--- a/images/emoji/3297.png
+++ /dev/null
Binary files differ
diff --git a/images/emoji/3299.png b/images/emoji/3299.png
deleted file mode 100644
index 5fd72608e..000000000
--- a/images/emoji/3299.png
+++ /dev/null
Binary files differ
diff --git a/images/red-koala.jpg b/images/red-koala.jpg
new file mode 100644
index 000000000..4cbedd264
--- /dev/null
+++ b/images/red-koala.jpg
Binary files differ
diff --git a/images/red-koala.png b/images/red-koala.png
new file mode 100644
index 000000000..005a37fe2
--- /dev/null
+++ b/images/red-koala.png
Binary files differ
diff --git a/images/red-koala.svg b/images/red-koala.svg
new file mode 100644
index 000000000..f303b32dd
--- /dev/null
+++ b/images/red-koala.svg
@@ -0,0 +1,151 @@
+<?xml version="1.0" encoding="UTF-8" standalone="no"?>
+<!-- Created with Inkscape (http://www.inkscape.org/) -->
+
+<svg
+ xmlns:dc="http://purl.org/dc/elements/1.1/"
+ xmlns:cc="http://creativecommons.org/ns#"
+ xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
+ xmlns:svg="http://www.w3.org/2000/svg"
+ xmlns="http://www.w3.org/2000/svg"
+ xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
+ xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
+ version="1.1"
+ width="744.09448"
+ height="1052.3622"
+ id="svg2"
+ inkscape:version="0.48.2 r9819"
+ sodipodi:docname="red-koala.svg">
+ <sodipodi:namedview
+ pagecolor="#ffffff"
+ bordercolor="#666666"
+ borderopacity="1"
+ objecttolerance="10"
+ gridtolerance="10"
+ guidetolerance="10"
+ inkscape:pageopacity="0"
+ inkscape:pageshadow="2"
+ inkscape:window-width="640"
+ inkscape:window-height="480"
+ id="namedview26"
+ showgrid="false"
+ inkscape:zoom="0.50332378"
+ inkscape:cx="476.12273"
+ inkscape:cy="572.78569"
+ inkscape:window-x="38"
+ inkscape:window-y="616"
+ inkscape:window-maximized="0"
+ inkscape:current-layer="svg2" />
+ <defs
+ id="defs4" />
+ <metadata
+ id="metadata7">
+ <rdf:RDF>
+ <cc:Work
+ rdf:about="">
+ <dc:format>image/svg+xml</dc:format>
+ <dc:type
+ rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
+ <dc:title></dc:title>
+ </cc:Work>
+ </rdf:RDF>
+ </metadata>
+ <g
+ id="layer1"
+ transform="translate(0.17560932,-0.17560932)">
+ <path
+ d=""
+ id="path6167"
+ style="fill:#ffffff;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:0.08838835;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
+ inkscape:connector-curvature="0" />
+ <path
+ d="m 497.9857,1088.5424 c 0,-16.225 0.13752,-22.8625 0.30561,-14.75 0.16808,8.1125 0.16808,21.3875 0,29.5 -0.16809,8.1125 -0.30561,1.475 -0.30561,-14.75 z m 290.93182,18.5 c -0.002,-6.05 0.1606,-8.6539 0.36191,-5.7865 0.2013,2.8674 0.20315,7.8174 0.004,11 -0.19905,3.1826 -0.36376,0.8365 -0.36601,-5.2135 z m 17.08867,-37.5 c 0,-26.675 0.12889,-37.5875 0.28641,-24.25 0.15752,13.3375 0.15752,35.1625 0,48.5 -0.15752,13.3375 -0.28641,2.425 -0.28641,-24.25 z m 27.96202,27 c 0,-11.825 0.14466,-16.6625 0.32145,-10.75 0.1768,5.9125 0.1768,15.5875 0,21.5 -0.17679,5.9125 -0.32145,1.075 -0.32145,-10.75 z m -495.42476,10.5 c 1.29175,-1.375 2.57363,-2.5 2.84863,-2.5 0.275,0 -0.55688,1.125 -1.84863,2.5 -1.29175,1.375 -2.57363,2.5 -2.84863,2.5 -0.275,0 0.55688,-1.125 1.84863,-2.5 z m 68.27083,-7.1042 c 0.33229,-0.3322 1.19479,-0.3678 1.91667,-0.079 0.79773,0.3193 0.56078,0.5562 -0.60417,0.6042 -1.05416,0.043 -1.64479,-0.1929 -1.3125,-0.5252 z m 376.47917,-3.0581 c 0.6875,-0.2774 1.8125,-0.2774 2.5,0 0.6875,0.2774 0.125,0.5044 -1.25,0.5044 -1.375,0 -1.9375,-0.227 -1.25,-0.5044 z m -462.75,-2.8377 c 0.68469,-0.825 1.46989,-1.5 1.74489,-1.5 0.275,0 -0.0602,0.675 -0.74489,1.5 -0.68469,0.825 -1.46989,1.5 -1.74489,1.5 -0.275,0 0.0602,-0.675 0.74489,-1.5 z m 303.07895,-3.9167 c -0.0434,-1.0541 0.19293,-1.6447 0.52522,-1.3125 0.33229,0.3323 0.36781,1.1948 0.0789,1.9167 -0.31922,0.7977 -0.55618,0.5608 -0.60416,-0.6042 z m -281.80812,-4.1875 c 0.33229,-0.3322 1.19479,-0.3678 1.91667,-0.079 0.79773,0.3193 0.56078,0.5562 -0.60417,0.6042 -1.05416,0.043 -1.64479,-0.1929 -1.3125,-0.5252 z m 20.80812,-11.8125 c -0.0434,-1.0541 0.19292,-1.6447 0.52522,-1.3125 0.33229,0.3323 0.36781,1.1948 0.0789,1.9167 -0.31922,0.7977 -0.55618,0.5608 -0.60416,-0.6042 z m 0.0789,-7.5833 c 0,-1.375 0.22698,-1.9375 0.50439,-1.25 0.27741,0.6875 0.27741,1.8125 0,2.5 -0.27741,0.6875 -0.50439,0.125 -0.50439,-1.25 z m 477.84211,-13.5 c 0.68469,-0.825 1.46989,-1.5 1.74489,-1.5 0.275,0 -0.0602,0.675 -0.74489,1.5 -0.68469,0.825 -1.46989,1.5 -1.74489,1.5 -0.275,0 0.0602,-0.675 0.74489,-1.5 z m -588.60544,-20 c 0.002,-7.7 0.15853,-10.7178 0.34883,-6.7062 0.1903,4.0115 0.18902,10.3115 -0.003,14 -0.19189,3.6884 -0.34759,0.4062 -0.34603,-7.2938 z m 606,0 c 0.002,-7.7 0.15853,-10.7178 0.34883,-6.7062 0.1903,4.0115 0.18902,10.3115 -0.003,14 -0.19169,3.6884 -0.34739,0.4062 -0.34583,-7.2938 z m -585.39456,-1 c 1.29175,-1.375 2.57363,-2.5 2.84863,-2.5 0.275,0 -0.55688,1.125 -1.84863,2.5 -1.29175,1.375 -2.57363,2.5 -2.84863,2.5 -0.275,0 0.55688,-1.125 1.84863,-2.5 z m 454.75,-11.2322 c 2.3375,-0.2105 6.1625,-0.2105 8.5,0 2.3375,0.2105 0.425,0.3828 -4.25,0.3828 -4.675,0 -6.5875,-0.1723 -4.25,-0.3828 z m 43.96349,0 c 2.86742,-0.2013 7.81742,-0.2032 11,0 3.18258,0.1991 0.83651,0.3638 -5.21349,0.366 -6.05,0 -8.65393,-0.1606 -5.78651,-0.3619 z m 106.03651,-9.0063 c 3.9875,-0.1898 10.5125,-0.1898 14.5,0 3.9875,0.1898 0.725,0.3451 -7.25,0.3451 -7.975,0 -11.2375,-0.1553 -7.25,-0.3451 z M 454.81581,605.54241 c 0,-2.475 0.19502,-3.4875 0.43337,-2.25 0.23836,1.2375 0.23836,3.2625 0,4.5 -0.23835,1.2375 -0.43337,0.225 -0.43337,-2.25 z m -16.34805,-45.75 -2.42431,-2.75 2.75,2.42431 c 1.5125,1.33338 2.75,2.57088 2.75,2.75 0,0.78428 -0.8098,0.14598 -3.07569,-2.42431 z m 130.82569,-1.99507 c 5.0875,-0.18149 13.4125,-0.18149 18.5,0 5.0875,0.18149 0.925,0.32999 -9.25,0.32999 -10.175,0 -14.3375,-0.1485 -9.25,-0.32999 z m 159.5,-0.004 c 14.1625,-0.15649 37.3375,-0.15649 51.5,0 14.1625,0.15649 2.575,0.28452 -25.75,0.28452 -28.325,0 -39.9125,-0.12803 -25.75,-0.28452 z m 208.5,3e-5 c 13.8875,-0.15682 36.6125,-0.15682 50.5,0 13.88755,0.15682 2.525,0.28513 -25.25,0.28513 -27.775,0 -39.1375,-0.12831 -25.25,-0.28513 z M 388.81428,541.93824 c 0.33229,-0.33229 1.19479,-0.36781 1.91667,-0.0789 0.79773,0.31922 0.56078,0.55618 -0.60417,0.60416 -1.05416,0.0434 -1.64479,-0.19293 -1.3125,-0.52522 z"
+ id="path6242"
+ style="fill:#5f5b5b"
+ inkscape:connector-curvature="0" />
+ <path
+ d="m 552.98651,1088.0424 c -4.5e-4,-16.5 0.13655,-23.3903 0.30444,-15.3118 0.16789,8.0785 0.16826,21.5785 8.2e-4,30 -0.16745,8.4215 -0.30481,1.8118 -0.30526,-14.6882 z m 54.80912,26 c -0.0111,-2.2 0.18461,-3.2177 0.4349,-2.2617 0.25029,0.9561 0.25937,2.7561 0.0202,4 -0.23919,1.244 -0.44398,0.4617 -0.45508,-1.7383 z m -105.25218,-86 c 0.68469,-0.825 1.46989,-1.5 1.74489,-1.5 0.275,0 -0.0602,0.675 -0.74489,1.5 -0.68469,0.825 -1.46989,1.5 -1.74489,1.5 -0.275,0 0.0602,-0.675 0.74489,-1.5 z m 41.40499,-0.75 -1.90499,-2.25 2.25,1.905 c 2.11444,1.7902 2.70524,2.595 1.90499,2.595 -0.18976,0 -1.20226,-1.0125 -2.25,-2.25 z m 117.86584,-7.3542 c 0.33229,-0.3322 1.19479,-0.3678 1.91667,-0.079 0.79773,0.3193 0.56078,0.5562 -0.60417,0.6042 -1.05416,0.043 -1.64479,-0.1929 -1.3125,-0.5252 z M 545.72943,857.7944 c 9.17729,-0.16487 24.47729,-0.16517 34,-6.6e-4 9.52271,0.16451 2.01402,0.29941 -16.68598,0.29977 -18.7,3.6e-4 -26.49131,-0.13424 -17.31402,-0.29911 z m 183.06402,-10e-4 c 14.1625,-0.15649 37.3375,-0.15649 51.5,0 14.1625,0.15649 2.575,0.28452 -25.75,0.28452 -28.325,0 -39.9125,-0.12803 -25.75,-0.28452 z m 208.5,3e-5 c 13.8875,-0.15682 36.6125,-0.15682 50.5,0 13.88745,0.15682 2.525,0.28513 -25.25,0.28513 -27.775,0 -39.1375,-0.12831 -25.25,-0.28513 z M 382.78179,541.85533 c 0.95609,-0.25029 2.75609,-0.25937 4,-0.0202 1.24391,0.23919 0.46166,0.44398 -1.73834,0.45508 -2.2,0.0111 -3.21775,-0.18461 -2.26166,-0.4349 z m 139.26166,-55.31292 c -1.5808,-1.65 -2.64918,-3 -2.37418,-3 0.275,0 1.79338,1.35 3.37418,3 1.5808,1.65 2.64918,3 2.37418,3 -0.275,0 -1.79338,-1.35 -3.37418,-3 z"
+ id="path6236"
+ style="fill:#292222"
+ inkscape:connector-curvature="0" />
+ <g
+ id="g6312">
+ <g
+ id="g6286">
+ <g
+ transform="translate(43.475438,27.243334)"
+ id="g6190">
+ <g
+ id="g6035"
+ style="stroke:#000000;stroke-width:0.69999999;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none">
+ <path
+ d="m 230.00007,643.07523 c -3.43799,-0.73575 -5.99718,-1.74825 -5.68708,-2.25 0.3101,-0.50175 0.12499,-0.91227 -0.41135,-0.91227 -1.48706,0 -8.54066,-7.1481 -10.08081,-10.21587 -0.74992,-1.49373 -1.69468,-2.51118 -2.09947,-2.26101 -0.40479,0.25017 -1.34946,-0.32769 -2.09928,-1.28413 -1.2337,-1.57367 -1.19694,-1.60851 0.38669,-0.36655 1.82477,1.43109 2.46942,0.24698 0.78342,-1.43902 -0.99993,-0.99993 -5.85993,-14.40317 -6.50264,-17.93342 -0.20026,-1.1 -0.42292,-2 -0.49479,-2 -0.80622,0 -0.75379,-10.80804 0.0645,-13.29479 0.5963,-1.81214 1.42743,-5.63714 1.84696,-8.5 1.01816,-6.94791 1.28046,-7.7525 3.17755,-9.74688 0.89375,-0.93958 1.79375,-2.12857 2,-2.64219 0.6726,-1.67498 11.51235,-9.31614 13.21587,-9.31614 0.91252,0 1.65913,-0.46973 1.65913,-1.04384 0,-0.57411 0.5625,-0.95313 1.25,-0.84228 0.6875,0.11086 2.03333,-0.14096 2.99074,-0.5596 0.9574,-0.41863 3.9949,-0.56502 6.75,-0.32531 2.75509,0.23972 5.00926,0.0613 5.00926,-0.39656 0,-0.45783 0.47656,-0.83241 1.05902,-0.83241 0.58246,0 0.79485,0.42742 0.47199,0.94983 -0.51182,0.82814 2.33166,3.05017 3.90325,3.05017 1.48687,0 0.34183,-2.0101 -1.18426,-2.07895 -0.9625,-0.0434 -1.2463,-0.28632 -0.63067,-0.53977 0.80908,-0.3331 0.75814,-1.5092 -0.1838,-4.2432 -1.6748,-4.86113 -1.58978,-22.34502 0.14495,-29.80756 0.72638,-3.12478 1.11621,-6.01227 0.86629,-6.41664 -0.45531,-0.73672 3.57389,-13.97353 4.53969,-14.91388 0.28245,-0.275 1.38572,-2.21316 2.45172,-4.30703 1.066,-2.09387 2.94358,-4.89187 4.17239,-6.21777 1.22881,-1.32591 2.51101,-3.28292 2.84934,-4.3489 0.7171,-2.25937 11.83409,-14.1263 13.23359,-14.1263 0.52178,0 3.06923,-2.03183 5.661,-4.51518 l 4.7123,-4.51517 -3.47612,-3.57925 c -1.91186,-1.96858 -3.94674,-3.28838 -4.52194,-2.93288 -0.58125,0.35923 -0.84131,0.068 -0.58544,-0.65558 0.60298,-1.70518 -1.691,-4.6672 -3.5363,-4.56613 -5.13701,0.28137 -7.97051,-0.4819 -10.09204,-2.71853 -1.29523,-1.3655 -2.7246,-2.4905 -3.17639,-2.5 -1.88718,-0.0397 -8.08561,-8.54966 -7.23261,-9.92984 0.31483,-0.50941 -0.10671,-1.60534 -0.93677,-2.43539 -0.83005,-0.83006 -1.50919,-2.11633 -1.50919,-2.85838 0,-0.74205 -0.7875,-2.06805 -1.75,-2.94666 -5.45757,-4.98188 -7.84532,-8.79242 -10.76413,-17.17818 -2.03246,-5.83926 -2.92733,-9.89511 -2.46426,-11.16883 0.39992,-1.1 0.3336,-2.75804 -0.14738,-3.68453 -1.00661,-1.93897 0.14895,-5.54804 3.06731,-9.57991 1.08904,-1.50456 2.22871,-4.91121 2.53261,-7.57033 0.30389,-2.65913 1.24741,-5.52965 2.0967,-6.37894 0.8493,-0.84929 1.31621,-2.13823 1.03759,-2.8643 -0.32214,-0.83947 0.021,-1.11767 0.94249,-0.76407 0.98287,0.37716 1.44907,-0.12181 1.44907,-1.55093 0,-1.2555 0.63987,-2.10699 1.58333,-2.10699 0.87084,0 1.39046,-0.5625 1.15471,-1.25 -0.62048,-1.80954 5.44327,-8.54821 9.59822,-10.66652 3.70647,-1.88967 7.8224,-1.93142 20.16374,-0.20452 3.3,0.46176 6.15761,0.70779 6.35024,0.54673 0.19263,-0.16106 2.79027,1.02727 5.77254,2.64074 2.98226,1.61346 6.06164,2.93357 6.84306,2.93357 0.78141,0 2.09306,0.95986 2.91478,2.13302 0.99008,1.41354 2.17361,1.95531 3.50876,1.60616 1.1081,-0.28978 2.16007,-0.0908 2.33771,0.44209 0.19299,0.57898 3.38657,0.2344 7.93498,-0.85616 5.60405,-1.34367 9.90949,-1.69322 16.32165,-1.32511 4.79031,0.275 8.94555,0.11745 9.23386,-0.35012 0.73918,-1.19874 13.76024,0.44069 18.84022,2.37209 1.43552,0.54579 3.03342,0.73067 3.55089,0.41085 0.51748,-0.31981 0.81721,-0.0717 0.66609,0.55133 -0.15113,0.62304 1.41272,1.72847 3.47522,2.45649 2.0625,0.72803 3.75,1.09661 3.75,0.81908 0,-0.27754 0.675,0.0556 1.5,0.74028 1.03636,0.8601 1.5,0.89795 1.5,0.12244 0,-0.61734 0.6794,-1.12244 1.50979,-1.12244 0.83038,0 2.28039,-0.9 3.22224,-2 0.94185,-1.1 2.43486,-2 3.3178,-2 0.88295,0 4.49544,-1.18497 8.02776,-2.63327 8.46052,-3.46892 14.63942,-3.97669 17.37205,-1.42762 1.1277,1.05195 3.3242,2.22889 4.88112,2.61544 1.55692,0.38654 3.06757,1.3199 3.35699,2.07413 0.28943,0.75422 1.12457,1.37132 1.85588,1.37132 0.75838,0 1.46428,1.353 1.64301,3.14915 0.1875,1.88431 1.11665,3.5913 2.31336,4.25 1.1,0.60547 2.22893,1.40174 2.50874,1.7695 0.2798,0.36775 2.0798,0.81775 4,1 2.27368,0.21579 3.50048,0.85448 3.51769,1.83135 0.0145,0.825 0.35938,2.03141 0.76631,2.6809 0.40694,0.6495 0.2487,1.48447 -0.35163,1.8555 -0.71159,0.43978 -0.31705,1.49898 1.13348,3.043 1.98819,2.11632 2.04669,2.43683 0.54968,3.01128 -1.38588,0.53182 -1.45495,0.90995 -0.39979,2.18872 1.03517,1.25456 1.03212,1.62774 -0.0162,1.98047 -0.99232,0.33388 -1.02188,0.75978 -0.12755,1.83738 0.73955,0.8911 0.82539,1.85868 0.23535,2.65275 -0.51086,0.6875 -0.88128,2.57782 -0.82317,4.20072 0.0581,1.6229 -0.67967,3.73606 -1.63952,4.69591 -1.26468,1.26468 -1.59142,2.69275 -1.1867,5.1867 0.42623,2.6266 0.078,3.92203 -1.47076,5.47076 -1.11608,1.11608 -1.77762,2.28087 -1.47008,2.58841 0.30755,0.30754 0.0263,1.20128 -0.62507,1.98609 -0.91938,1.10779 -0.89534,1.54346 0.1075,1.94803 0.83366,0.33632 0.93712,0.81408 0.29174,1.34725 -0.55,0.45437 -1.13902,1.72613 -1.30894,2.82613 -0.16991,1.1 -1.10266,3.125 -2.07278,4.5 -0.97011,1.375 -2.40344,3.9625 -3.18517,5.75 -1.03908,2.37593 -2.09527,3.27123 -3.92722,3.32895 -1.37824,0.0434 -1.94339,0.30592 -1.25589,0.58333 1.88994,0.76261 1.50594,2.12802 -1,3.55578 -1.2375,0.70507 -2.25,1.95694 -2.25,2.78194 0,0.825 -0.675,1.41017 -1.5,1.30038 -0.825,-0.1098 -2.43628,1.2402 -3.58062,3 -1.14434,1.75979 -2.61936,3.08295 -3.27782,2.94034 -1.08968,-0.23598 -1.45305,0.37488 -2.74933,4.6219 -0.32054,1.05021 -0.73669,1.0964 -1.81504,0.20145 -0.99034,-0.82192 -1.59437,-0.84529 -2.06734,-0.08 -0.44576,0.72125 -1.76948,0.40055 -3.97628,-0.96333 -3.11614,-1.92587 -7.17568,-1.86871 -5.96881,0.084 0.3043,0.49237 0.14557,0.89522 -0.35273,0.89522 -1.51282,0 -5.22477,3.65392 -4.47432,4.40437 0.38573,0.38574 -0.0725,0.40441 -1.01819,0.0415 -1.24342,-0.47714 -1.72376,-0.14568 -1.73483,1.19715 -0.0131,1.58573 -0.17028,1.63788 -1.07613,0.35699 -0.94295,-1.33333 -1.01588,-1.33333 -0.65636,0 0.22245,0.825 1.38171,1.6438 2.57613,1.81955 1.19442,0.17575 2.17167,0.73825 2.17167,1.25 0,0.51175 0.70156,0.93045 1.55902,0.93045 0.85746,0 1.31241,0.39901 1.01101,0.88669 -0.30141,0.48768 0.12204,1.44278 0.94098,2.12245 1.00214,0.8317 1.48899,0.87575 1.48899,0.13474 0,-1.50115 4.95297,0.59164 7.16029,3.02546 0.91316,1.00687 1.92566,1.83066 2.25,1.83066 1.34484,0 4.72208,4.29595 7.25599,9.22983 1.48864,2.89859 3.52272,6.34336 4.52017,7.65503 0.99745,1.31167 1.81355,3.07624 1.81355,3.92126 0,0.84502 0.72,2.33199 1.6,3.30438 0.88,0.97239 1.6,3.43675 1.6,5.47636 0,2.03962 0.76793,5.10446 1.70651,6.81077 0.93858,1.7063 1.61471,4.79182 1.50251,6.85671 -0.1122,2.06489 0.20721,4.00848 0.7098,4.3191 0.50259,0.31061 0.67661,0.94855 0.3867,1.41762 -0.2899,0.46908 -0.76403,3.92549 -1.05361,7.68091 -0.28959,3.75541 -0.71708,8.48392 -0.94998,10.50777 -0.2329,2.02386 0.003,3.82386 0.5249,4 0.52709,0.178 0.28756,1.5926 -0.53924,3.18457 -0.81817,1.57537 -1.48759,3.61274 -1.48759,4.52749 0,0.91475 -0.70052,2.66332 -1.5567,3.88569 -0.87255,1.24574 -1.0923,2.22251 -0.5,2.22251 0.58118,0 1.0567,-0.5051 1.0567,-1.12244 0,-0.792 0.42748,-0.76768 1.45201,0.0826 0.79861,0.66279 2.29858,0.93638 3.33327,0.60798 1.03469,-0.3284 3.81286,0.0844 6.17371,0.91738 2.36086,0.83296 6.23433,1.51447 8.60772,1.51447 2.37339,0 4.61956,0.49238 4.99149,1.09417 0.37193,0.60179 1.76406,0.88622 3.09363,0.63206 1.32956,-0.25417 2.23378,-0.27851 2.00937,-0.0541 -0.2244,0.22441 1.91928,2.75397 4.76374,5.62125 6.91688,6.97236 6.84708,6.79218 7.96086,20.54842 0.37147,4.58799 0.71492,8.63799 0.76322,9 0.0483,0.36201 0.0337,0.79697 -0.10711,1.1582 -0.80187,2.05678 -1.31054,4.99435 -1.34682,7.77778 -0.0235,1.80277 -0.41672,1.48669 -0.74391,2.14323 -0.15813,0.31731 0.25315,0.79264 -0.63886,0.98195 -0.37621,0.60872 -0.45106,0.16598 -0.58513,0.9003 -0.0521,0.28524 -0.25816,0.17907 -0.74263,0.68717 -0.43248,0.45357 -0.35784,-0.0516 -0.66596,0.89743 -0.31216,0.96149 -0.20602,0.77316 -0.22528,1.16979 -0.0334,0.68828 -0.15481,0.85715 0.19242,2.05829 0.143,0.49469 -0.42203,1.27822 -0.89555,2.24755 -0.88043,1.80233 -0.25484,1.80931 -2.10364,2.00505 -0.26599,0.0282 0.44276,-0.20257 -1.17031,0.10247 -0.97461,0.1843 -1.19198,1.67998 -0.96659,2.29972 0.22539,0.61973 -1.01695,0.42266 -2.90511,3.15273 -2.25936,3.26679 -3.52602,1.58301 -4.03544,3.64173 -0.54849,2.21667 0.58003,0.14982 -0.11326,1.62782 -1.05669,2.25269 -0.47931,1.15177 -0.88709,1.80055 0,0 -0.22285,0.54501 -0.88857,0.87087 -0.44625,0.21842 1.17998,-0.12796 -2.60139,0.47671 -0.63646,0.29734 -0.46202,-0.80807 -3.19227,1.72224 l -2.76552,2.563 -22.1305,-0.23761 c -15.88014,-0.1705 -23.06085,-0.62092 -25.42453,-1.59481 -1.81171,-0.74645 -3.73536,-1.08443 -4.27478,-0.75105 -0.53941,0.33338 -0.8571,0.0102 -0.70598,-0.71819 0.16117,-0.77676 -0.44879,-1.20284 -1.47522,-1.03049 -0.9625,0.16161 -1.75,-0.25089 -1.75,-0.91667 0,-0.66578 -0.27444,-0.93607 -0.60986,-0.60064 -0.78027,0.78026 -7.41837,-3.39567 -10.84536,-6.82266 -1.44854,-1.44854 -3.25963,-2.39353 -4.02464,-2.09997 -0.76501,0.29356 -1.5575,0.034 -1.76109,-0.57674 -0.20359,-0.61077 -1.78787,-1.11049 -3.52062,-1.11049 -1.73275,0 -2.90921,-0.39034 -2.61436,-0.86741 0.29485,-0.47708 -0.35864,-1.51606 -1.91518,-1.22854 -1.55654,0.28751 -11.53389,1.69766 -21.70889,2.05337 -14.52324,0.50772 -19.12609,-3.02326 -21.87373,-1.66976 -1.925,0.94825 -7.96545,6.36524 -12.49725,8.6425 -4.53181,2.27733 -8.72086,4.14055 -9.30903,4.14055 -0.58816,0 -0.1631,1.70754 0.17292,2.25124 0.3629,0.58718 -0.0858,0.72119 -1.10503,0.33006 -1.25638,-0.48212 -1.49674,-0.30375 -0.89743,0.66596 0.5495,0.88911 0.43265,1.08594 -0.3555,0.59884 -1.02239,-0.63187 -5.26154,0.26637 -10.13496,2.1475 -3.07686,1.18766 -31.55601,0.75877 -37.7587,-0.56864 z"
+ id="path3028"
+ style="fill:#ff0000;fill-opacity:1;stroke:#000000;stroke-width:0.69999999;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
+ inkscape:connector-curvature="0"
+ sodipodi:nodetypes="cssssssssssssssscsssssscssscsssssscsssssssssssssssssssscssssssscsscsccsssssssssscssssscscssssssssssccssssscssscscsssscssccssssscsssssssssssccsscssssssssssscsssssscsssasssssssscscscssscsscsscssssscsscssssc" />
+ <path
+ d="m 335.35714,412.00504 c 7.82838,2.22626 13.55258,9.07397 16.11064,16.58597 1.77331,5.10242 2.2904,10.63429 1.66409,15.98751 -0.69791,5.10295 -3.46584,10.04442 -8.00784,12.65844 -7.35888,4.77106 -18.18995,4.75934 -24.65496,-1.57547 -4.82902,-5.00061 -6.04119,-12.54296 -4.81793,-19.19027 1.46182,-8.18673 6.2227,-15.59326 12.57325,-20.87012 2.41956,-1.79458 5.22351,-3.69025 8.38275,-3.41755"
+ id="path3800"
+ style="fill:#000000;fill-opacity:1;stroke:#000000;stroke-width:0.69999999;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
+ inkscape:connector-curvature="0" />
+ <path
+ d="m 310.53571,412.36218 c -1.40641,-1.17116 -3.58861,-1.66135 -5.16196,-0.51893 -2.22395,1.52051 -3.19556,4.27879 -3.55744,6.84075 -0.33384,2.53795 0.27807,5.51425 2.44186,7.10488 1.90236,1.39111 4.56075,0.65579 6.25684,-0.72054 1.97274,-1.54803 3.35558,-4.07045 3.02805,-6.62562 0.37908,-2.01145 -0.015,-4.50186 -1.88689,-5.65872 -0.34622,-0.20237 -0.72717,-0.34426 -1.12046,-0.42182 z"
+ id="path3843"
+ style="fill:#000000;fill-opacity:1;stroke:#000000;stroke-width:0.69999999;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
+ inkscape:connector-curvature="0" />
+ <path
+ d="m 362.32143,415.04075 c 1.82028,-0.2869 3.79491,0.35598 4.9485,1.82847 1.8159,2.28393 2.02126,5.56951 0.97481,8.2301 -0.74786,1.96459 -2.45847,3.56523 -4.53699,3.99866 -2.04621,0.51877 -4.27055,-0.27745 -5.67674,-1.81667 -2.21845,-2.35017 -3.09901,-6.10321 -1.64239,-9.07066 0.7981,-1.56589 2.2933,-2.80679 4.01266,-3.20954 0.63251,-0.12753 1.2939,-0.11857 1.92015,0.0396 z"
+ id="path3860"
+ style="fill:#000000;fill-opacity:1;stroke:#000000;stroke-width:0.69999999;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
+ inkscape:connector-curvature="0" />
+ <path
+ d="m 313.21429,418.25504 c -0.65312,0.86871 -1.78813,1.29333 -2.8566,1.15862 -1.51532,-0.1724 -2.94976,-1.09631 -3.68229,-2.44106 -0.48041,-0.86232 -0.47858,-1.97724 0.0673,-2.80913 0.63734,-1.05476 1.94102,-1.71218 3.16653,-1.43208 1.54168,0.34032 2.74335,1.63795 3.2515,3.09573 0.26622,0.77734 0.31965,1.64275 0.0536,2.42792 z"
+ id="path3876"
+ style="fill:#ffffff;fill-opacity:1;stroke:#000000;stroke-width:0.69999999;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
+ inkscape:connector-curvature="0" />
+ <path
+ d="m 368.21429,421.46932 c -0.55015,0.72499 -1.45802,1.18031 -2.37461,1.09864 -1.30459,-0.10649 -2.47133,-0.95018 -3.16425,-2.03402 -0.49974,-0.77749 -0.73307,-1.82753 -0.25762,-2.67243 0.38894,-0.68396 1.10834,-1.14173 1.85648,-1.33873 0.96656,-0.2404 1.98591,0.18488 2.64956,0.89186 0.93289,0.98053 1.46507,2.36797 1.3435,3.72376 -0.012,0.11111 -0.0295,0.22166 -0.0531,0.33092 z"
+ id="path3895"
+ style="fill:#ffffff;fill-opacity:1;stroke:#000000;stroke-width:0.69999999;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
+ inkscape:connector-curvature="0" />
+ <path
+ d="m 303.04576,597.66727 c 0.89898,4.35249 2.17849,8.87576 1.08581,13.31695 -0.98289,3.59314 -0.74817,7.37439 -1.46656,11.01441 -0.0643,0.90932 -0.11707,1.84689 -0.50302,2.68838"
+ id="path6133"
+ style="fill:none;stroke:#000000;stroke-width:0.69999999;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
+ inkscape:connector-curvature="0" />
+ <path
+ d="m 349.51278,594.76308 c -1.58181,2.33253 -1.39144,5.56411 -3.53003,7.56876 -0.74878,3.62541 -0.71177,7.35102 -1.21455,11.00843 -0.10351,3.82135 -0.0162,7.71947 1.08376,11.4103"
+ id="path6143"
+ style="fill:none;stroke:#000000;stroke-width:0.69999999;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
+ inkscape:connector-curvature="0" />
+ </g>
+ <path
+ d="m 409.49059,562.817 c -6.67512,0.0141 -12.72539,2.68679 -18.37595,5.87319 -5.33515,2.18172 -7.45099,7.69796 -12.7301,9.94852 -4.12835,4.17446 -7.57404,7.9756 -11.12192,12.52392 -2.6138,5.46222 -7.29966,10.95705 -13.63968,6.46078 -4.52118,-3.54734 -10.14186,-6.62102 -12.94899,-11.82544 -2.65925,-5.83356 -3.26085,-12.84467 -1.90417,-19.32125 0.65245,-6.59597 4.3386,-12.21307 7.7841,-17.72679 2.52977,-5.2597 6.29469,-8.24419 7.64728,-13.87964 2.44434,-5.87935 2.40037,-12.09314 2.93216,-18.33486 0.0486,-2.55913 0.45478,-5.2273 -0.67574,-7.63532"
+ id="path6125"
+ style="fill:none;stroke:#000000;stroke-width:0.69999999;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
+ inkscape:connector-curvature="0" />
+ <path
+ d="m 247.99245,560.54416 c 6.76369,0.22082 13.24135,2.3829 18.17002,6.74782 3.36251,5.76075 8.86908,9.4273 12.13456,15.223 3.40989,5.65472 7.64278,11.01568 10.16352,16.76182 5.33282,4.95503 12.09713,-2.9069 18.35687,-2.90228 3.07966,-5.12791 6.1634,-10.09309 10.89959,-13.65497 3.57662,-4.51201 1.53442,-12.1972 3.96354,-17.84779 0.65412,-6.29983 -5.71452,-10.1283 -7.74494,-15.55479 -5.11189,-5.20658 -9.57769,-10.17315 -13.01542,-16.77188 -3.03275,-6.36273 -3.86358,-13.67482 -2.19127,-20.51204 1.29002,-1.18262 1.10017,-2.57287 1.53892,-3.89055"
+ id="path6127"
+ style="fill:none;stroke:#000000;stroke-width:0.69999999;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
+ inkscape:connector-curvature="0" />
+ <path
+ d="m 264.49757,451.68163 c -0.83348,-0.36325 -1.85626,-1.07502 -2.27284,-1.58172 -0.41658,-0.5067 -1.7802,-1.5663 -3.03026,-2.35468 -2.64376,-1.66732 -6.90902,-7.0392 -7.34147,-9.24618 -0.59726,-3.04812 -3.54506,-8.15921 -6.60743,-11.45641 -4.03542,-4.34485 -6.20805,-8.31132 -8.70689,-15.89577 -1.7921,-5.43936 -2.03866,-6.78071 -2.18289,-11.87582 l -0.1626,-5.74387 2.14733,-3.61858 c 1.49005,-2.51097 2.45643,-4.98256 3.15715,-8.07469 0.5554,-2.45086 1.46859,-5.37083 2.02932,-6.48881 l 1.01951,-2.0327 6.17741,-0.24014 c 3.39757,-0.13208 8.19146,-0.18277 10.65308,-0.11265 4.44806,0.12672 11.48416,1.5513 13.68386,2.77053 0.63259,0.35063 2.29197,1.25362 3.68752,2.00665 3.98522,2.1504 4.30748,2.61329 3.37531,4.84826 -0.42755,1.0251 -1.42299,2.54567 -2.2121,3.37904 -1.43662,1.51721 -3.05975,6.05037 -3.05975,8.54542 0,0.72538 -0.68185,2.52705 -1.51523,4.00371 -0.83337,1.47666 -1.51523,3.19279 -1.51523,3.81363 0,0.62083 -0.27818,1.62523 -0.61819,2.232 -0.58367,1.04162 -1.16789,5.63751 -2.41505,18.9987 -0.45164,4.83847 -0.70286,5.88848 -1.551,6.48254 -0.89587,0.62749 -0.97423,1.0664 -0.68253,3.8228 0.18125,1.71265 0.64492,3.6173 1.03039,4.23256 0.38547,0.61526 0.70085,2.16071 0.70085,3.43435 0,1.27363 0.31405,2.92943 0.69789,3.67957 0.38384,0.75013 0.85915,2.33434 1.05624,3.52046 0.19709,1.18612 0.69477,2.49301 1.10595,2.90419 0.66009,0.66009 0.40341,0.74529 -2.19266,0.72783 -1.61715,-0.0109 -3.62221,-0.31697 -4.45569,-0.68022 l 0,0 z"
+ id="path6163"
+ style="fill:#ffffff;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:0.35355338;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
+ inkscape:connector-curvature="0" />
+ <path
+ d="m 396.41236,460.39021 c -0.50626,-0.28797 -1.47514,-0.38438 -2.15306,-0.21422 -0.97746,0.24532 -5.45503,-1.12035 -6.703,-2.04444 -0.099,-0.0733 0.62934,-0.96678 1.61864,-1.98543 1.35515,-1.39535 1.87342,-2.4304 2.10166,-4.19725 0.16662,-1.28984 0.76652,-4.0498 1.3331,-6.13324 0.56659,-2.08344 1.5235,-5.60635 2.12647,-7.82868 0.85499,-3.15121 1.06501,-5.15235 0.95413,-9.09137 -0.24568,-8.72732 -0.64405,-14.10608 -1.12226,-15.15229 -0.25394,-0.55559 -0.53774,-2.64127 -0.63065,-4.63486 -0.11344,-2.43421 -0.43818,-3.92719 -0.98873,-4.54568 -0.58913,-0.66183 -0.91354,-2.41327 -1.15292,-6.22429 l -0.3331,-5.3033 1.6724,-2.61886 c 0.91982,-1.44037 2.52021,-3.145 3.55641,-3.78807 1.0362,-0.64307 2.0247,-1.58971 2.19666,-2.10365 0.17195,-0.51394 1.30987,-1.37556 2.5287,-1.9147 1.21883,-0.53915 2.45435,-1.42554 2.74561,-1.96975 0.39448,-0.73711 1.07253,-0.99386 2.65836,-1.00663 1.17084,-0.009 3.03794,-0.45628 4.14911,-0.99301 1.11116,-0.53674 2.62785,-0.98359 3.37041,-0.99302 0.79847,-0.0101 1.94627,-0.6133 2.80919,-1.47622 l 1.45909,-1.45909 1.98903,1.20358 c 1.09397,0.66197 3.29507,1.4616 4.89135,1.77697 2.77989,0.5492 2.9243,0.65506 3.42363,2.50943 0.28673,1.06482 0.376,2.51507 0.19837,3.22277 -0.23988,0.95577 0.0373,1.75897 1.07743,3.12273 1.2757,1.67252 1.32566,1.89062 0.56112,2.44967 -0.98074,0.71713 -1.09884,2.31355 -0.23507,3.17733 0.46889,0.46888 0.40779,0.74782 -0.2728,1.24548 -0.81374,0.59502 -0.81889,0.75778 -0.0714,2.25615 0.54968,1.10185 0.65784,1.90156 0.34048,2.51733 -0.25581,0.49636 -0.62128,2.15254 -0.81214,3.6804 -0.20022,1.60272 -0.86987,3.5746 -1.58291,4.66112 -1.00727,1.53485 -1.23588,2.52258 -1.23588,5.3396 0,3.05151 -0.17585,3.68879 -1.50118,5.4404 -0.82565,1.0912 -1.5075,2.3088 -1.51523,2.70576 -0.008,0.39697 -0.29148,1.48898 -0.63057,2.4267 -0.5085,1.40624 -0.49207,1.78186 0.0938,2.14394 0.51371,0.31749 0.56277,0.62439 0.17726,1.10883 -0.29318,0.36842 -0.80141,1.50347 -1.12941,2.52235 -0.54409,1.69015 -3.63547,7.55893 -5.93115,11.25991 -0.6016,0.96988 -1.5138,1.61512 -2.59487,1.83549 -2.15117,0.43849 -2.32413,0.65034 -1.54695,1.89481 0.56684,0.90765 0.47994,1.16021 -0.72534,2.10829 -2.14287,1.68558 -2.87911,2.52914 -2.87911,3.29881 0,0.39155 -0.57263,0.85563 -1.27252,1.03129 -0.69989,0.17566 -2.31849,1.5437 -3.59689,3.04008 -1.32232,1.5478 -2.7445,2.7207 -3.29893,2.7207 -0.65584,0 -1.22039,0.61945 -1.72618,1.89404 -1.49574,3.76925 -1.40087,3.64682 -2.39016,3.08409 l 0,0 z"
+ id="path6165"
+ style="fill:#ffffff;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:0.35355338;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
+ inkscape:connector-curvature="0" />
+ </g>
+ <path
+ d="m 327.4876,492.39499 c 2.2644,2.66632 6.07748,3.19909 8.63579,5.43274 2.86007,2.28019 6.66345,0.59268 9.87447,1.65009 3.09838,0.67486 5.93629,2.75922 9.39536,2.88839 3.32499,0.37833 6.55094,0.57956 9.53617,1.55177 2.6564,0.95363 5.25607,-2.99638 7.07288,-0.0245 3.26765,2.24544 7.81367,0.6425 11.58781,1.00892 3.32915,0.008 5.80304,-2.7396 9.17467,-2.25665 3.08744,-0.22194 6.69298,0.88515 9.12364,-1.39255 3.30181,0.0682 6.36091,-0.78244 9.0003,-2.76185 1.51143,-1.14436 3.49477,-0.47019 5.25963,-0.64998 0.0806,-1.61182 2.11123,-1.97141 2.85714,-3.21429"
+ id="path6159"
+ style="fill:none;stroke:#000000;stroke-width:0.69999999;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
+ inkscape:connector-curvature="0" />
+ </g>
+ </g>
+ </g>
+</svg>
diff --git a/images/red-koala.xcf b/images/red-koala.xcf
new file mode 100644
index 000000000..a95baf62c
--- /dev/null
+++ b/images/red-koala.xcf
Binary files differ
diff --git a/include/account.php b/include/account.php
index 5e57d53a8..6c6fdece4 100644
--- a/include/account.php
+++ b/include/account.php
@@ -31,7 +31,7 @@ function check_account_email($email) {
if(! strlen($email))
return $result;
- if((! valid_email($email)) || (! validate_email($email)))
+ if(! validate_email($email))
$result['message'] .= t('Not a valid email address') . EOL;
elseif(! allowed_email($email))
$result['message'] = t('Your email domain is not among those allowed on this site');
@@ -105,6 +105,33 @@ function account_total() {
}
+function account_store_lowlevel($arr) {
+
+ $store = [
+ 'account_parent' => ((array_key_exists('account_parent',$arr)) ? $arr['account_parent'] : '0'),
+ 'account_default_channel' => ((array_key_exists('account_default_channel',$arr)) ? $arr['account_default_channel'] : '0'),
+ 'account_salt' => ((array_key_exists('account_salt',$arr)) ? $arr['account_salt'] : ''),
+ 'account_password' => ((array_key_exists('account_password',$arr)) ? $arr['account_password'] : ''),
+ 'account_email' => ((array_key_exists('account_email',$arr)) ? $arr['account_email'] : ''),
+ 'account_external' => ((array_key_exists('account_external',$arr)) ? $arr['account_external'] : ''),
+ 'account_language' => ((array_key_exists('account_language',$arr)) ? $arr['account_language'] : 'en'),
+ 'account_created' => ((array_key_exists('account_created',$arr)) ? $arr['account_created'] : '0001-01-01 00:00:00'),
+ 'account_lastlog' => ((array_key_exists('account_lastlog',$arr)) ? $arr['account_lastlog'] : '0001-01-01 00:00:00'),
+ 'account_flags' => ((array_key_exists('account_flags',$arr)) ? $arr['account_flags'] : '0'),
+ 'account_roles' => ((array_key_exists('account_roles',$arr)) ? $arr['account_roles'] : '0'),
+ 'account_reset' => ((array_key_exists('account_reset',$arr)) ? $arr['account_reset'] : ''),
+ 'account_expires' => ((array_key_exists('account_expires',$arr)) ? $arr['account_expires'] : '0001-01-01 00:00:00'),
+ 'account_expire_notified' => ((array_key_exists('account_expire_notified',$arr)) ? $arr['account_expire_notified'] : '0001-01-01 00:00:00'),
+ 'account_service_class' => ((array_key_exists('account_service_class',$arr)) ? $arr['account_service_class'] : ''),
+ 'account_level' => ((array_key_exists('account_level',$arr)) ? $arr['account_level'] : '0'),
+ 'account_password_changed' => ((array_key_exists('account_password_changed',$arr)) ? $arr['account_password_changed'] : '0001-01-01 00:00:00')
+ ];
+
+ return create_table_from_array('account',$store);
+
+}
+
+
function create_account($arr) {
// Required: { email, password }
@@ -177,21 +204,20 @@ function create_account($arr) {
$salt = random_string(32);
$password_encoded = hash('whirlpool', $salt . $password);
- $r = q("INSERT INTO account
- ( account_parent, account_salt, account_password, account_email, account_language,
- account_created, account_flags, account_roles, account_level, account_expires, account_service_class )
- VALUES ( %d, '%s', '%s', '%s', '%s', '%s', %d, %d, %d, '%s', '%s' )",
- intval($parent),
- dbesc($salt),
- dbesc($password_encoded),
- dbesc($email),
- dbesc(get_best_language()),
- dbesc(datetime_convert()),
- intval($flags),
- intval($roles),
- intval($techlevel),
- dbesc($expires),
- dbesc($default_service_class)
+ $r = account_store_lowlevel(
+ [
+ 'account_parent' => intval($parent),
+ 'account_salt' => $salt,
+ 'account_password' => $password_encoded,
+ 'account_email' => $email,
+ 'account_language' => get_best_language(),
+ 'account_created' => datetime_convert(),
+ 'account_flags' => intval($flags),
+ 'account_roles' => intval($roles),
+ 'account_level' => intval($techlevel),
+ 'account_expires' => $expires,
+ 'account_service_class' => $default_service_class
+ ]
);
if(! $r) {
logger('create_account: DB INSERT failed.');
@@ -246,16 +272,18 @@ function verify_email_address($arr) {
dbesc($arr['account']['account_language'])
);
-//@fixme - get correct language template
+ push_lang(($arr['account']['account_language']) ? $arr['account']['account_language'] : 'en');
- $email_msg = replace_macros(get_intltext_template('register_verify_member.tpl'), array(
- '$sitename' => get_config('system','sitename'),
- '$siteurl' => z_root(),
- '$email' => $arr['email'],
- '$uid' => $arr['account']['account_id'],
- '$hash' => $hash,
- '$details' => $details
- ));
+ $email_msg = replace_macros(get_intltext_template('register_verify_member.tpl'),
+ [
+ '$sitename' => get_config('system','sitename'),
+ '$siteurl' => z_root(),
+ '$email' => $arr['email'],
+ '$uid' => $arr['account']['account_id'],
+ '$hash' => $hash,
+ '$details' => $details
+ ]
+ );
$res = z_mail(
[
@@ -265,10 +293,12 @@ function verify_email_address($arr) {
]
);
+ pop_lang();
+
if($res)
$delivered ++;
else
- logger('send_reg_approval_email: failed to ' . $admin['email'] . 'account_id: ' . $arr['account']['account_id']);
+ logger('send_reg_approval_email: failed to account_id: ' . $arr['account']['account_id']);
return $res;
}
@@ -354,9 +384,9 @@ function send_register_success_email($email,$password) {
$res = z_mail(
[
- 'toEmail' => $email,
- 'messageSubject' => sprintf( t('Registration details for %s'), get_config('system','sitename')),
- 'textVersion' => $email_msg,
+ 'toEmail' => $email,
+ 'messageSubject' => sprintf( t('Registration details for %s'), get_config('system','sitename')),
+ 'textVersion' => $email_msg,
]
);
@@ -424,7 +454,7 @@ function account_allow($hash) {
pop_lang();
- if(get_config('system','auto_channel_create') || get_config('system','server_role') === 'basic')
+ if(get_config('system','auto_channel_create'))
auto_channel_create($register[0]['uid']);
if ($res) {
@@ -525,19 +555,13 @@ function account_approve($hash) {
if(! $account)
return $ret;
-
-
-
- if(get_config('system','auto_channel_create') || get_config('system','server_role') === 'basic')
+ if(get_config('system','auto_channel_create'))
auto_channel_create($register[0]['uid']);
else {
$_SESSION['login_return_url'] = 'new_channel';
authenticate_success($account[0],null,true,true,false,true);
}
-
- // info( t('Account verified. Please login.') . EOL );
-
return true;
}
@@ -772,12 +796,6 @@ function upgrade_bool_message($bbcode = false) {
function get_account_techlevel($account_id = 0) {
- $role = \Zotlabs\Lib\System::get_server_role();
- if($role == 'basic')
- return 0;
- if($role == 'standard')
- return 5;
-
if(! $account_id) {
$x = \App::get_account();
}
diff --git a/include/api.php b/include/api.php
index 693967696..c91590070 100644
--- a/include/api.php
+++ b/include/api.php
@@ -194,15 +194,25 @@ require_once('include/api_zot.php');
else
$redirect = trim($_REQUEST['redirect_uris']);
$icon = trim($_REQUEST['logo_uri']);
- $r = q("INSERT INTO clients (client_id, pw, clname, redirect_uri, icon, uid)
- VALUES ('%s','%s','%s','%s','%s',%d)",
- dbesc($key),
- dbesc($secret),
- dbesc($name),
- dbesc($redirect),
- dbesc($icon),
- intval(0)
- );
+ if($oauth2) {
+ $r = q("INSERT INTO oauth_clients (client_id, client_secret, redirect_uri, grant_types, scope, user_id)
+ VALUES ( '%s', '%s', '%s', null, null, null ) ",
+ dbesc($key),
+ dbesc($secret),
+ dbesc($redirect)
+ );
+ }
+ else {
+ $r = q("INSERT INTO clients (client_id, pw, clname, redirect_uri, icon, uid)
+ VALUES ('%s','%s','%s','%s','%s',%d)",
+ dbesc($key),
+ dbesc($secret),
+ dbesc($name),
+ dbesc($redirect),
+ dbesc($icon),
+ intval(0)
+ );
+ }
$ret['client_id'] = $key;
$ret['client_secret'] = $secret;
diff --git a/include/api_auth.php b/include/api_auth.php
index e5cd7cab3..0818fa54b 100644
--- a/include/api_auth.php
+++ b/include/api_auth.php
@@ -7,6 +7,8 @@
function api_login(&$a){
$record = null;
+ $remote_auth = false;
+ $sigblock = null;
require_once('include/oauth.php');
@@ -33,21 +35,66 @@ function api_login(&$a){
// workarounds for HTTP-auth in CGI mode
- if(x($_SERVER,'REDIRECT_REMOTE_USER')) {
- $userpass = base64_decode(substr($_SERVER["REDIRECT_REMOTE_USER"],6)) ;
- if(strlen($userpass)) {
- list($name, $password) = explode(':', $userpass);
- $_SERVER['PHP_AUTH_USER'] = $name;
- $_SERVER['PHP_AUTH_PW'] = $password;
+ foreach([ 'REDIRECT_REMOTE_USER', 'HTTP_AUTHORIZATION' ] as $head) {
+
+ /* Basic authentication */
+
+ if(array_key_exists($head,$_SERVER) && substr(trim($_SERVER[$head]),0,5) === 'Basic') {
+ $userpass = @base64_decode(substr(trim($_SERVER[$head]),6)) ;
+ if(strlen($userpass)) {
+ list($name, $password) = explode(':', $userpass);
+ $_SERVER['PHP_AUTH_USER'] = $name;
+ $_SERVER['PHP_AUTH_PW'] = $password;
+ }
+ break;
}
- }
- if(x($_SERVER,'HTTP_AUTHORIZATION')) {
- $userpass = base64_decode(substr($_SERVER["HTTP_AUTHORIZATION"],6)) ;
- if(strlen($userpass)) {
- list($name, $password) = explode(':', $userpass);
- $_SERVER['PHP_AUTH_USER'] = $name;
- $_SERVER['PHP_AUTH_PW'] = $password;
+ /* Signature authentication */
+
+ if(array_key_exists($head,$_SERVER) && substr(trim($_SERVER[$head]),0,9) === 'Signature') {
+ if($head !== 'HTTP_AUTHORIZATION') {
+ $_SERVER['HTTP_AUTHORIZATION'] = $_SERVER[$head];
+ continue;
+ }
+
+ $sigblock = \Zotlabs\Web\HTTPSig::parse_sigheader($_SERVER[$head]);
+ if($sigblock) {
+ $keyId = $sigblock['keyId'];
+ if($keyId) {
+ $r = q("select * from hubloc where hubloc_addr = '%s' limit 1",
+ dbesc($keyId)
+ );
+ if($r) {
+ $c = channelx_by_hash($r[0]['hubloc_hash']);
+ if($c) {
+ $a = q("select * from account where account_id = %d limit 1",
+ intval($c['channel_account_id'])
+ );
+ if($a) {
+ $record = [ 'channel' => $c, 'account' => $a[0] ];
+ $channel_login = $c['channel_id'];
+ }
+ else {
+ continue;
+ }
+ }
+ else {
+ continue;
+ }
+ }
+ else {
+ continue;
+ }
+
+ if($record) {
+ $verified = \Zotlabs\Web\HTTPSig::verify('',$record['channel']['channel_pubkey']);
+ if(! ($verified && $verified['header_signed'] && $verified['header_valid'])) {
+ $record = null;
+ }
+ break;
+ }
+ }
+ }
}
}
@@ -64,8 +111,6 @@ function api_login(&$a){
}
}
-
-
if($record['account']) {
authenticate_success($record['account']);
@@ -85,8 +130,8 @@ function api_login(&$a){
}
-function retry_basic_auth() {
- header('WWW-Authenticate: Basic realm="Hubzilla"');
+function retry_basic_auth($method = 'Basic') {
+ header('WWW-Authenticate: ' . $method . ' realm="Hubzilla"');
header('HTTP/1.0 401 Unauthorized');
echo('This api requires login');
killme();
diff --git a/include/attach.php b/include/attach.php
index 937d33ea3..78e133b03 100644
--- a/include/attach.php
+++ b/include/attach.php
@@ -209,7 +209,7 @@ function attach_list_files($channel_id, $observer, $hash = '', $filename = '', $
// Retrieve all columns except 'data'
- $r = q("select id, aid, uid, hash, filename, filetype, filesize, revision, folder, os_storage, is_dir, is_photo, flags, created, edited, allow_cid, allow_gid, deny_cid, deny_gid from attach where uid = %d $sql_extra ORDER BY $orderby $limit",
+ $r = q("select id, aid, uid, hash, filename, filetype, filesize, revision, folder, os_path, display_path, os_storage, is_dir, is_photo, flags, created, edited, allow_cid, allow_gid, deny_cid, deny_gid from attach where uid = %d $sql_extra ORDER BY $orderby $limit",
intval($channel_id)
);
@@ -284,6 +284,7 @@ function attach_by_hash($hash, $observer_hash, $rev = 0) {
return $ret;
}
+
function attach_can_view_folder($uid,$ob_hash,$folder_hash) {
$sql_extra = permissions_sql($uid,$ob_hash);
@@ -348,7 +349,7 @@ function attach_by_hash_nodata($hash, $observer_hash, $rev = 0) {
// Now we'll see if we can access the attachment
- $r = q("select id, aid, uid, hash, creator, filename, filetype, filesize, revision, folder, os_storage, is_photo, is_dir, flags, created, edited, allow_cid, allow_gid, deny_cid, deny_gid from attach where uid = %d and hash = '%s' $sql_extra limit 1",
+ $r = q("select id, aid, uid, hash, creator, filename, filetype, filesize, revision, folder, os_storage, is_photo, os_path, display_path, is_dir, flags, created, edited, allow_cid, allow_gid, deny_cid, deny_gid from attach where uid = %d and hash = '%s' $sql_extra limit 1",
intval($r[0]['uid']),
dbesc($hash)
);
@@ -422,6 +423,7 @@ function attach_store($channel, $observer_hash, $options = '', $arr = null) {
$hash = (($arr && $arr['hash']) ? $arr['hash'] : null);
$upload_path = (($arr && $arr['directory']) ? $arr['directory'] : '');
$visible = (($arr && $arr['visible']) ? $arr['visible'] : '');
+ $notify = (($arr && $arr['notify']) ? $arr['notify'] : '');
$observer = array();
@@ -458,6 +460,7 @@ function attach_store($channel, $observer_hash, $options = '', $arr = null) {
// By default remove $src when finished
$remove_when_processed = true;
+ $import_replace = false;
if($options === 'import') {
$src = $arr['src'];
@@ -474,6 +477,9 @@ function attach_store($channel, $observer_hash, $options = '', $arr = null) {
if($arr['preserve_original'])
$remove_when_processed = false;
+ if($arr['replace'])
+ $import_replace = true;
+
// if importing a directory, just do it now and go home - we're done.
if(array_key_exists('is_dir',$arr) && intval($arr['is_dir'])) {
@@ -531,7 +537,7 @@ function attach_store($channel, $observer_hash, $options = '', $arr = null) {
if($options === 'update' && $arr && array_key_exists('revision',$arr))
$sql_options = " and revision = " . intval($arr['revision']) . " ";
- $x = q("select id, aid, uid, filename, filetype, filesize, hash, revision, folder, os_storage, is_photo, flags, created, edited, allow_cid, allow_gid, deny_cid, deny_gid from attach where hash = '%s' and uid = %d $sql_options limit 1",
+ $x = q("select id, aid, uid, filename, filetype, filesize, hash, revision, folder, os_storage, is_photo, os_path, display_path, flags, created, edited, allow_cid, allow_gid, deny_cid, deny_gid from attach where hash = '%s' and uid = %d $sql_options limit 1",
dbesc($arr['hash']),
intval($channel_id)
);
@@ -609,13 +615,16 @@ function attach_store($channel, $observer_hash, $options = '', $arr = null) {
// A freshly uploaded file. Check for duplicate and resolve with the channel's overwrite settings.
- $r = q("select filename, id, hash, filesize from attach where filename = '%s' and folder = '%s' ",
+ $r = q("select filename, id, hash, filesize from attach where uid = %d and filename = '%s' and folder = '%s' ",
+ intval($channel_id),
dbesc($filename),
dbesc($folder_hash)
);
if($r) {
- $overwrite = get_pconfig($channel_id,'system','overwrite_dup_files');
+ $overwrite = (($import_replace || get_pconfig($channel_id,'system','overwrite_dup_files')) ? true : false);
if(($overwrite) || ($options === 'import')) {
+ if(! array_key_exists('edited',$arr))
+ $arr['edited'] = datetime_convert();
$options = 'replace';
$existing_id = $x[0]['id'];
$existing_size = intval($x[0]['filesize']);
@@ -631,7 +640,8 @@ function attach_store($channel, $observer_hash, $options = '', $arr = null) {
$ext = $def_extension;
}
- $r = q("select filename from attach where ( filename = '%s' OR filename like '%s' ) and folder = '%s' ",
+ $r = q("select filename from attach where uid = %d and ( filename = '%s' OR filename like '%s' ) and folder = '%s' ",
+ intval($channel_id),
dbesc($basename . $ext),
dbesc($basename . '(%)' . $ext),
dbesc($folder_hash)
@@ -702,11 +712,11 @@ function attach_store($channel, $observer_hash, $options = '', $arr = null) {
$os_relpath .= $folder_hash . '/';
}
- $os_relpath .= $hash;
+ $os_relpath .= $hash;
+ $os_relpath = ltrim($os_relpath,'/');
- // not yet used
- $os_path = '';
- $display_path = '';
+ $os_path = $os_relpath;
+ $display_path = ltrim($pathname . '/' . $filename,'/');
if($src)
@file_put_contents($os_basepath . $os_relpath,@file_get_contents($src));
@@ -810,7 +820,7 @@ function attach_store($channel, $observer_hash, $options = '', $arr = null) {
if($is_photo) {
- $args = array( 'source' => $source, 'visible' => $visible, 'resource_id' => $hash, 'album' => basename($pathname), 'os_path' => $os_basepath . $os_relpath, 'filename' => $filename, 'getimagesize' => $gis, 'directory' => $direct, 'options' => $options );
+ $args = array( 'source' => $source, 'visible' => $visible, 'resource_id' => $hash, 'album' => $pathname, 'os_syspath' => $os_basepath . $os_relpath, 'os_path' => $os_path, 'display_path' => $display_path, 'filename' => $filename, 'getimagesize' => $gis, 'directory' => $direct, 'options' => $options );
if($arr['contact_allow'])
$args['contact_allow'] = $arr['contact_allow'];
if($arr['group_allow'])
@@ -883,6 +893,12 @@ function attach_store($channel, $observer_hash, $options = '', $arr = null) {
build_sync_packet($channel['channel_id'],array('file' => array($sync)));
}
+ if($notify) {
+ //$cloudPath = z_root() . '/cloud/' . $channel['channel_address'] . '/' . $r['0']['display_path'];
+ //$object = get_file_activity_object($channel['channel_id'], $r['0']['hash'], $cloudPath);
+ //file_activity($channel['channel_id'], $object, $r['0']['allow_cid'], $r['0']['allow_gid'], $r['0']['deny_cid'], $r['0']['deny_gid'], 'post', $notify);
+ }
+
return $ret;
}
@@ -914,7 +930,7 @@ function z_readdir($channel_id, $observer_hash, $pathname, $parent_hash = '') {
if(count($paths) > 1) {
$curpath = array_shift($paths);
- $r = q("select hash, id, is_dir from attach where uid = %d and filename = '%s' and is_dir != 0 " . permissions_sql($channel_id) . " limit 1",
+ $r = q("select hash, id, is_dir from attach where uid = %d and filename = '%s' and is_dir != 0 " . permissions_sql($channel_id,$observer_hash) . " limit 1",
intval($channel_id),
dbesc($curpath)
);
@@ -929,7 +945,7 @@ function z_readdir($channel_id, $observer_hash, $pathname, $parent_hash = '') {
else
$paths = array($pathname);
- $r = q("select id, aid, uid, hash, creator, filename, filetype, filesize, revision, folder, is_photo, is_dir, os_storage, flags, created, edited, allow_cid, allow_gid, deny_cid, deny_gid from attach where id = %d and folder = '%s' and filename = '%s' and is_dir != 0 " . permissions_sql($channel_id),
+ $r = q("select id, aid, uid, hash, creator, filename, filetype, filesize, revision, folder, os_path, display_path, is_photo, is_dir, os_storage, flags, created, edited, allow_cid, allow_gid, deny_cid, deny_gid from attach where id = %d and folder = '%s' and filename = '%s' and is_dir != 0 " . permissions_sql($channel_id),
intval($channel_id),
dbesc($parent_hash),
dbesc($paths[0])
@@ -968,12 +984,15 @@ function attach_mkdir($channel, $observer_hash, $arr = null) {
$sql_options = '';
- $basepath = 'store/' . $channel['channel_address'];
+ $os_basepath = 'store/' . $channel['channel_address'];
- logger('attach_mkdir: basepath: ' . $basepath);
+ logger('attach_mkdir: basepath: ' . $os_basepath);
- if(! is_dir($basepath))
- os_mkdir($basepath,STORAGE_DEFAULT_PERMISSIONS, true);
+ if(! is_dir($os_basepath))
+ os_mkdir($os_basepath,STORAGE_DEFAULT_PERMISSIONS, true);
+
+
+ $os_basepath .= '/';
if(! perm_is_allowed($channel_id, $observer_hash, 'write_storage')) {
$ret['message'] = t('Permission denied.');
@@ -1019,10 +1038,13 @@ function attach_mkdir($channel, $observer_hash, $arr = null) {
$lpath = '';
$lfile = $arr['folder'];
+ $dpath = '';
+
$sql_options = permissions_sql($channel['channel_id']);
+
do {
- $r = q("select filename, hash, flags, is_dir, folder from attach where uid = %d and hash = '%s' and is_dir != 0
+ $r = q("select filename, hash, flags, is_dir, folder, display_path from attach where uid = %d and hash = '%s' and is_dir = 1
$sql_options limit 1",
intval($channel['channel_id']),
dbesc($lfile)
@@ -1032,22 +1054,26 @@ function attach_mkdir($channel, $observer_hash, $arr = null) {
$ret['message'] = t('Path not found.');
return $ret;
}
+
+ $dpath = $r[0]['filename'] . (($dpath) ? '/' . $dpath : '');
+
if($lfile)
- $lpath = $r[0]['hash'] . '/' . $lpath;
+ $lpath = $r[0]['hash'] . (($lpath) ? '/' . $lpath : '');
+
$lfile = $r[0]['folder'];
+
} while ( ($r[0]['folder']) && intval($r[0]['is_dir'])) ;
- $path = $basepath . '/' . $lpath;
+
+ $path = $lpath;
}
else
- $path = $basepath . '/';
-
- $path .= $arr['hash'];
+ $path = '';
$created = datetime_convert();
- // not yet used
- $os_path = '';
- $display_path = '';
+ $os_path = ltrim($path . '/' . $arr['hash'],'/');
+ $display_path = ltrim($dpath . '/' . $arr['filename'],'/');
+
$r = q("INSERT INTO attach ( aid, uid, hash, creator, filename, filetype, filesize, revision, folder, os_storage, is_dir, content, created, edited, os_path, display_path, allow_cid, allow_gid, deny_cid, deny_gid )
VALUES ( %d, %d, '%s', '%s', '%s', '%s', %d, %d, '%s', %d, '%s', '%s', '%s', '%s', '%s', '%s', '%s', '%s', '%s', '%s' ) ",
@@ -1062,7 +1088,7 @@ function attach_mkdir($channel, $observer_hash, $arr = null) {
dbesc($arr['folder']),
intval(1),
intval(1),
- dbescbin($path),
+ dbescbin($os_basepath . $os_path),
dbesc($created),
dbesc($created),
dbesc($os_path),
@@ -1074,7 +1100,7 @@ function attach_mkdir($channel, $observer_hash, $arr = null) {
);
if($r) {
- if(os_mkdir($path, STORAGE_DEFAULT_PERMISSIONS, true)) {
+ if(os_mkdir($os_basepath . $os_path, STORAGE_DEFAULT_PERMISSIONS, true)) {
$ret['success'] = true;
// update the parent folder's lastmodified timestamp
@@ -1092,7 +1118,7 @@ function attach_mkdir($channel, $observer_hash, $arr = null) {
$ret['data'] = $z[0];
}
else {
- logger('attach_mkdir: ' . mkdir . ' ' . $path . ' failed.');
+ logger('attach_mkdir: ' . mkdir . ' ' . $os_basepath . $os_path . ' failed.');
$ret['message'] = t('mkdir failed.');
}
}
@@ -1286,8 +1312,8 @@ function attach_delete($channel_id, $resource, $is_photo = 0) {
return;
}
- $cloudpath = get_parent_cloudpath($channel_id, $channel_address, $resource);
- $object = get_file_activity_object($channel_id, $resource, $cloudpath);
+ $url = get_cloudpath($channel_id, $channel_address, $resource);
+ $object = get_file_activity_object($channel_id, $resource, $url);
// If resource is a directory delete everything in the directory recursive
if(intval($r[0]['is_dir'])) {
@@ -1428,7 +1454,7 @@ function get_cloudpath($arr) {
* @param string $attachHash
* @return string with the full folder path
*/
-function get_parent_cloudpath($channel_id, $channel_name, $attachHash) {
+function get_cloud_url($channel_id, $channel_name, $attachHash) {
$parentFullPath = '';
// build directory tree
$parentHash = $attachHash;
@@ -1440,9 +1466,9 @@ function get_parent_cloudpath($channel_id, $channel_name, $attachHash) {
}
} while ($parentHash);
- $parentFullPath = z_root() . '/cloud/' . $channel_name . '/' . $parentFullPath;
+ $url = z_root() . '/cloud/' . $channel_name . '/' . $parentFullPath . find_filename_by_hash($channel_id, $attachHash);
- return $parentFullPath;
+ return $url;
}
/**
@@ -1477,18 +1503,34 @@ function find_folder_hash_by_attach_hash($channel_id, $attachHash, $recurse = fa
function find_folder_hash_by_path($channel_id, $path) {
- $filename = end(explode('/', $path));
+ if(! $path)
+ return '';
- $r = q("SELECT hash FROM attach WHERE uid = %d AND filename = '%s' LIMIT 1",
- intval($channel_id),
- dbesc($filename)
- );
+ $comps = explode('/',$path);
+ $errors = false;
+ $parent_hash = '';
- $hash = '';
- if($r && $r[0]['hash']) {
- $hash = $r[0]['hash'];
+ for($x = 0; $x < count($comps); $x ++) {
+ $element = $comps[$x];
+ $r = q("SELECT hash FROM attach WHERE uid = %d AND filename = '%s' AND folder = '%s' LIMIT 1",
+ intval($channel_id),
+ dbesc($element),
+ dbesc($parent_hash)
+ );
+ if($r) {
+ $parent_hash = $r[0]['hash'];
+ }
+ else {
+ $errors ++;
+ break;
+ }
}
- return $hash;
+
+ if($errors)
+ return '';
+
+ return $parent_hash;
+
}
/**
@@ -1569,7 +1611,10 @@ function file_activity($channel_id, $object, $allow_cid, $allow_gid, $deny_cid,
$folder_hash = $object['folder'];
- $r_perms = recursive_activity_recipients($arr_allow_cid, $arr_allow_gid, $arr_deny_cid, $arr_deny_gid, $folder_hash);
+ $r_perms = attach_recursive_perms($arr_allow_cid, $arr_allow_gid, $arr_deny_cid, $arr_deny_gid, $folder_hash);
+
+ if($r_perms === false) //nobody has recursive perms - nobody must be notified
+ return;
//split up returned perms
$arr_allow_cid = $r_perms['allow_cid'];
@@ -1648,17 +1693,9 @@ function file_activity($channel_id, $object, $allow_cid, $allow_gid, $deny_cid,
$arr['obj'] = $u_jsonobject;
$arr['body'] = '';
- $post = item_store($arr);
- $item_id = $post['item_id'];
- if($item_id) {
- Zotlabs\Daemon\Master::Summon(array('Notifier','activity',$item_id));
- }
-
- call_hooks('post_local_end', $arr);
+ post_activity_item($arr);
$update = false;
-
- //notice( t('File activity updated') . EOL);
}
//don't create new activity if notify was not enabled
@@ -1683,16 +1720,7 @@ function file_activity($channel_id, $object, $allow_cid, $allow_gid, $deny_cid,
$arr['obj'] = (($update) ? $u_jsonobject : $jsonobject);
$arr['body'] = '';
- $post = item_store($arr);
- $item_id = $post['item_id'];
-
- if($item_id) {
- Zotlabs\Daemon\Master::Summon(array('Notifier','activity',$item_id));
- }
-
- call_hooks('post_local_end', $arr);
-
- //(($verb === 'post') ? notice( t('File activity posted') . EOL) : notice( t('File activity dropped') . EOL));
+ post_activity_item($arr);
return;
}
@@ -1704,14 +1732,14 @@ function file_activity($channel_id, $object, $allow_cid, $allow_gid, $deny_cid,
* @param string $hash
* @param string $cloudpath
*/
-function get_file_activity_object($channel_id, $hash, $cloudpath) {
+function get_file_activity_object($channel_id, $hash, $url) {
$x = q("SELECT creator, filename, filetype, filesize, revision, folder, os_storage, is_photo, is_dir, flags, created, edited, allow_cid, allow_gid, deny_cid, deny_gid FROM attach WHERE uid = %d AND hash = '%s' LIMIT 1",
intval($channel_id),
dbesc($hash)
);
- $url = rawurlencode($cloudpath . $x[0]['filename']);
+ $url = rawurlencode($url);
$links = array();
$links[] = array(
@@ -1749,7 +1777,7 @@ function get_file_activity_object($channel_id, $hash, $cloudpath) {
}
/**
- * @brief Returns array of channels which have recursive permission for a file
+ * @brief Returns recursive permissions array or false if nobody has recursive permissions
*
* @param array $arr_allow_cid
* @param array $arr_allow_gid
@@ -1757,19 +1785,20 @@ function get_file_activity_object($channel_id, $hash, $cloudpath) {
* @param array $arr_deny_gid
* @param string $folder_hash
*/
-function recursive_activity_recipients($arr_allow_cid, $arr_allow_gid, $arr_deny_cid, $arr_deny_gid, $folder_hash) {
+function attach_recursive_perms($arr_allow_cid, $arr_allow_gid, $arr_deny_cid, $arr_deny_gid, $folder_hash) {
$ret = array();
$parent_arr = array();
$count_values = array();
$poster = App::get_observer();
- //turn allow_gid into allow_cid's
- foreach($arr_allow_gid as $gid) {
- $in_group = group_get_members($gid);
+ //lookup all channels in sharee group and add them to sharee $arr_allow_cid
+ if($arr_allow_gid) {
+ $in_group = expand_groups($arr_allow_gid);
$arr_allow_cid = array_unique(array_merge($arr_allow_cid, $in_group));
}
+ //count existing parent folders - we will compare to that count later
$count = 0;
while($folder_hash) {
$x = q("SELECT allow_cid, allow_gid, deny_cid, deny_gid, folder FROM attach WHERE hash = '%s' LIMIT 1",
@@ -1778,30 +1807,20 @@ function recursive_activity_recipients($arr_allow_cid, $arr_allow_gid, $arr_deny
//only process private folders
if($x[0]['allow_cid'] || $x[0]['allow_gid'] || $x[0]['deny_cid'] || $x[0]['deny_gid']) {
-
$parent_arr['allow_cid'][] = expand_acl($x[0]['allow_cid']);
$parent_arr['allow_gid'][] = expand_acl($x[0]['allow_gid']);
-
- /**
- * @TODO should find a much better solution for the allow_cid <-> allow_gid problem.
- * Do not use allow_gid for now. Instead lookup the members of the group directly and add them to allow_cid.
- * */
- if($parent_arr['allow_gid']) {
- foreach($parent_arr['allow_gid'][$count] as $gid) {
- $in_group = group_get_members($gid);
- $parent_arr['allow_cid'][$count] = array_unique(array_merge($parent_arr['allow_cid'][$count], $in_group));
- }
- }
-
$parent_arr['deny_cid'][] = expand_acl($x[0]['deny_cid']);
$parent_arr['deny_gid'][] = expand_acl($x[0]['deny_gid']);
+ //this is the number of all existing parent folders - we will compare to that count later
$count++;
}
$folder_hash = $x[0]['folder'];
}
+ //logger(EOL . 'parent_arr: ' . print_r($parent_arr,true));
+
//if none of the parent folders is private just return file perms
if(!$parent_arr['allow_cid'] && !$parent_arr['allow_gid'] && !$parent_arr['deny_cid'] && !$parent_arr['deny_gid']) {
$ret['allow_gid'] = $arr_allow_gid;
@@ -1812,7 +1831,7 @@ function recursive_activity_recipients($arr_allow_cid, $arr_allow_gid, $arr_deny
return $ret;
}
- //if there are no perms on the file we get them from the first parent folder
+ //if there are no perms on the file we will work with the perms from the first parent folder
if(!$arr_allow_cid && !$arr_allow_gid && !$arr_deny_cid && !$arr_deny_gid) {
$arr_allow_cid = $parent_arr['allow_cid'][0];
$arr_allow_gid = $parent_arr['allow_gid'][0];
@@ -1820,52 +1839,83 @@ function recursive_activity_recipients($arr_allow_cid, $arr_allow_gid, $arr_deny
$arr_deny_gid = $parent_arr['deny_gid'][0];
}
- //allow_cid
- $r_arr_allow_cid = false;
- foreach ($parent_arr['allow_cid'] as $folder_arr_allow_cid) {
- foreach ($folder_arr_allow_cid as $ac_hash) {
- $count_values[$ac_hash]++;
+
+ /***
+ *
+ * check if sharee has perms for all parent folders
+ *
+ ***/
+
+ $r_arr_allow_cid = [];
+
+ if($parent_arr['allow_cid']) {
+ //check sharee arr_allow_cid against allow_cid of all parent folders
+ foreach($parent_arr['allow_cid'] as $folder_arr_allow_cid) {
+ foreach($folder_arr_allow_cid as $ac_hash) {
+ $count_values[$ac_hash]++;
+ }
}
- }
- foreach ($arr_allow_cid as $fac_hash) {
- if($count_values[$fac_hash] == $count)
- $r_arr_allow_cid[] = $fac_hash;
+ foreach($arr_allow_cid as $fac_hash) {
+ if($count_values[$fac_hash] == $count)
+ $r_arr_allow_cid[] = $fac_hash;
+ }
+ //logger(EOL . 'r_arr_allow_cid: ' . print_r($r_arr_allow_cid,true));
}
- //allow_gid
- $r_arr_allow_gid = false;
- foreach ($parent_arr['allow_gid'] as $folder_arr_allow_gid) {
- foreach ($folder_arr_allow_gid as $ag_hash) {
- $count_values[$ag_hash]++;
+ if($parent_arr['allow_gid']) {
+ //check sharee arr_allow_cid against members of allow_gid of all parent folders
+ foreach($parent_arr['allow_gid'] as $folder_arr_allow_gid) {
+ //get the group members
+ $folder_arr_allow_cid = expand_groups($folder_arr_allow_gid);
+ foreach($folder_arr_allow_cid as $ac_hash) {
+ $count_values[$ac_hash]++;
+ }
}
- }
- foreach ($arr_allow_gid as $fag_hash) {
- if($count_values[$fag_hash] == $count)
- $r_arr_allow_gid[] = $fag_hash;
+ foreach($arr_allow_cid as $fac_hash) {
+ if($count_values[$fac_hash] == $count)
+ $r_arr_allow_cid[] = $fac_hash;
+ }
+ //logger(EOL . 'groups - r_arr_allow_cid: ' . print_r($r_arr_allow_cid,true));
}
- //deny_gid
- foreach($parent_arr['deny_gid'] as $folder_arr_deny_gid) {
- $r_arr_deny_gid = array_merge($arr_deny_gid, $folder_arr_deny_gid);
- }
- $r_arr_deny_gid = array_unique($r_arr_deny_gid);
+
+ /***
+ *
+ * check if sharee is denied somewhere in parent folders and deny him if so
+ *
+ ***/
//deny_cid
- foreach($parent_arr['deny_cid'] as $folder_arr_deny_cid) {
- $r_arr_deny_cid = array_merge($arr_deny_cid, $folder_arr_deny_cid);
+ $r_arr_deny_cid = [];
+
+ if($parent_arr['deny_cid']) {
+ foreach($parent_arr['deny_cid'] as $folder_arr_deny_cid) {
+ $r_arr_deny_cid = array_merge($arr_deny_cid, $folder_arr_deny_cid);
+ }
+ $r_arr_deny_cid = array_unique($r_arr_deny_cid);
+ //logger(EOL . 'r_arr_deny_cid: ' . print_r($r_arr_deny_cid,true));
}
- $r_arr_deny_cid = array_unique($r_arr_deny_cid);
- //if none is allowed restrict to self
- if(($r_arr_allow_gid === false) && ($r_arr_allow_cid === false)) {
- $ret['allow_cid'] = $poster['xchan_hash'];
- } else {
- $ret['allow_gid'] = $r_arr_allow_gid;
- $ret['allow_cid'] = $r_arr_allow_cid;
- $ret['deny_gid'] = $r_arr_deny_gid;
- $ret['deny_cid'] = $r_arr_deny_cid;
+ //deny_gid
+ $r_arr_deny_gid = [];
+
+ if($parent_arr['deny_cid']) {
+ foreach($parent_arr['deny_gid'] as $folder_arr_deny_gid) {
+ $r_arr_deny_gid = array_merge($arr_deny_gid, $folder_arr_deny_gid);
+ }
+ $r_arr_deny_gid = array_unique($r_arr_deny_gid);
+ //logger(EOL . 'r_arr_deny_gid: ' . print_r($r_arr_dr_arr_deny_gideny_cid,true));
}
+ //if no channel is allowed return false
+ if(! $r_arr_allow_cid)
+ return false;
+
+ $ret['allow_gid'] = []; // eventual group members are already collected in $r_arr_allow_cid
+ $ret['allow_cid'] = $r_arr_allow_cid;
+ $ret['deny_gid'] = $r_arr_deny_gid;
+ $ret['deny_cid'] = $r_arr_deny_cid;
+
return $ret;
}
@@ -2196,10 +2246,23 @@ function attach_move($channel_id, $resource_id, $new_folder_hash) {
intval($r[0]['id'])
);
+
+ $x = attach_syspaths($channel_id,$resource_id);
+
+ $t1 = q("update attach set os_path = '%s', display_path = '%s' where id = %d",
+ dbesc($x['os_path']),
+ dbesc($x['path']),
+ intval($r[0]['id'])
+ );
+
+
if($r[0]['is_photo']) {
- $t = q("update photo set album = '%s', filename = '%s' where resource_id = '%s' and uid = %d",
+ $t = q("update photo set album = '%s', filename = '%s', os_path = '%s', display_path = '%s'
+ where resource_id = '%s' and uid = %d",
dbesc($newdirname),
dbesc($filename),
+ dbesc($x['os_path']),
+ dbesc($x['path']),
dbesc($resource_id),
intval($channel_id)
);
@@ -2227,8 +2290,9 @@ function attach_folder_select_list($channel_id) {
if($r) {
foreach($r as $rv) {
$x = attach_folder_rpaths($r,$rv);
- if($x)
+ if($x) {
$out[$x[0]] = $x[1];
+ }
}
}
@@ -2250,7 +2314,6 @@ function attach_folder_rpaths($all_folders,$that_folder) {
continue;
if($selected['hash'] == $parent_hash) {
$path = '/' . $selected['filename'] . $path;
- $current_hash = $selected['hash'];
$parent_hash = $selected['folder'];
$found = true;
break;
@@ -2264,3 +2327,155 @@ function attach_folder_rpaths($all_folders,$that_folder) {
return (($error) ? false : [ $current_hash , $path ]);
}
+
+
+function attach_syspaths($channel_id,$attach_hash) {
+
+ $os_path = '';
+ $path = '';
+ do {
+
+ $r = q("select folder, filename, hash from attach where hash = '%s' and uid = %d",
+ dbesc($attach_hash),
+ intval($channel_id)
+ );
+ if(! $r)
+ break;
+
+ $os_path = $r[0]['hash'] . (($os_path) ? '/' . $os_path : '');
+ $path = $r[0]['filename'] . (($path) ? '/' . $path : '');
+ $attach_hash = $r[0]['folder'];
+ }
+ while($attach_hash);
+
+ return [ 'os_path' => $os_path, 'path' => $path ];
+
+
+}
+
+
+
+function attach_upgrade() {
+
+ $r = q("select id, uid, hash from attach where os_path = '' and display_path = '' limit 100");
+ if($r) {
+ foreach($r as $rv) {
+ $x = attach_syspaths($rv['uid'],$rv['hash']);
+ if($x) {
+ $w = q("update attach set os_path = '%s', display_path = '%s' where id = %d",
+ dbesc($x['os_path']),
+ dbesc($x['path']),
+ intval($rv['id'])
+ );
+ $y = q("update photo set os_path = '%s', display_path = '%s' where uid = %d and resource_id = '%s'",
+ dbesc($x['os_path']),
+ dbesc($x['path']),
+ intval($rv['uid']),
+ dbesc($rv['hash'])
+ );
+ }
+ }
+ }
+}
+
+
+function save_chunk($channel,$start,$end,$len) {
+
+ $result = [];
+
+ $tmp_path = $_FILES['files']['tmp_name'];
+ $new_base = 'store/[data]/' . $channel['channel_address'] . '/tmp';
+ os_mkdir($new_base,STORAGE_DEFAULT_PERMISSIONS,true);
+
+ $new_path = $new_base . '/' . $_FILES['files']['name'];
+
+ if(! file_exists($new_path)) {
+ rename($tmp_path,$new_path);
+ }
+ else {
+ $istream = fopen($tmp_path,'rb');
+ $ostream = fopen($new_path,'ab');
+ if($istream && $ostream) {
+ pipe_streams($istream,$ostream);
+ fclose($istream);
+ fclose($ostream);
+ }
+ }
+ if(($len - 1) == $end) {
+ unlink($tmp_path);
+ $result['name'] = $_FILES['files']['tmp_name'];
+ $result['type'] = $_FILES['files']['type'];
+ $result['tmp_name'] = $new_path;
+ $result['error'] = 0;
+ $result['size'] = $len;
+ $result['complete'] = true;
+ return $result;
+ }
+ $result['partial'] = true;
+ $result['length'] = intval(filesize($new_path));
+ return $result;
+}
+
+
+/*
+ * chunkloader
+ * Submit handler for chunked uploads
+ *
+ */
+
+function chunkloader($channel,$arr) {
+
+ logger('request: ' . print_r($arr,true), LOGGER_DEBUG);
+ logger('files: ' . print_r($_FILES,true), LOGGER_DEBUG);
+
+
+ $result = [];
+
+
+ $tmp_path = $_FILES['file']['tmp_name'];
+ $new_base = 'store/[data]/' . $channel['channel_address'] . '/tmp';
+ os_mkdir($new_base,STORAGE_DEFAULT_PERMISSIONS,true);
+
+ $new_path = $new_base . '/' . $arr['resumableFilename'];
+
+ rename($tmp_path,$new_path . '.' . intval($arr['resumableChunkNumber']));
+
+ $missing_parts = false;
+ for($x = 1; $x <= intval($arr['resumableTotalChunks']); $x ++) {
+ if(! file_exists($new_path . '.' . $x)) {
+ $missing_parts = true;
+ break;
+ }
+ }
+
+ if($missing_parts) {
+ $result['partial'] = true;
+ return $result;
+ }
+
+ if(intval($arr['resumableTotalChunks']) === 1) {
+ rename($new_path . '.' . '1', $new_path);
+ }
+ else {
+ for($x = 1; $x <= intval($arr['resumableTotalChunks']); $x ++) {
+ $istream = fopen($new_path . '.' . $x,'rb');
+ $ostream = fopen($new_path,'ab');
+ if($istream && $ostream) {
+ pipe_streams($istream,$ostream);
+ fclose($istream);
+ fclose($ostream);
+ }
+ unlink($new_path . '.' . $x);
+ }
+ }
+
+ $result['name'] = $arr['resumableFilename'];
+ $result['type'] = $arr['resumableType'];
+ $result['tmp_name'] = $new_path;
+ $result['error'] = 0;
+ $result['size'] = $arr['resumableTotalSize'];
+ $result['complete'] = true;
+ return $result;
+
+}
+
diff --git a/include/auth.php b/include/auth.php
index c7be69583..78be32bf4 100644
--- a/include/auth.php
+++ b/include/auth.php
@@ -83,7 +83,7 @@ function account_verify_password($login, $pass) {
if(($email_verify) && ($register_policy == REGISTER_OPEN) && ($account['account_flags'] & ACCOUNT_UNVERIFIED)) {
logger('email verification required for ' . $login);
- return null;
+ return ( [ 'reason' => 'unvalidated' ] );
}
if(($account['account_flags'] == ACCOUNT_OK)
@@ -259,7 +259,10 @@ else {
}
else {
$verify = account_verify_password($_POST['username'], $_POST['password']);
- if($verify) {
+ if($verify && array_key_exists('reason',$verify) && $verify['reason'] === 'unvalidated') {
+ notice( t('Email validation is incomplete. Please check your email.'));
+ }
+ elseif($verify) {
$atoken = $verify['xchan'];
$channel = $verify['channel'];
$account = App::$account = $verify['account'];
diff --git a/include/bbcode.php b/include/bbcode.php
index c0033f280..9a2a6eb9b 100644
--- a/include/bbcode.php
+++ b/include/bbcode.php
@@ -7,6 +7,66 @@
require_once('include/oembed.php');
require_once('include/event.php');
require_once('include/zot.php');
+require_once('include/html2plain.php');
+
+function get_bb_tag_pos($s, $name, $occurance = 1) {
+
+ if($occurance < 1)
+ $occurance = 1;
+
+ $start_open = -1;
+ for($i = 1; $i <= $occurance; $i++) {
+ if( $start_open !== false)
+ $start_open = strpos($s, '[' . $name, $start_open + 1); // allow [name= type tags
+ }
+
+ if( $start_open === false)
+ return false;
+
+ $start_equal = strpos($s, '=', $start_open);
+ $start_close = strpos($s, ']', $start_open);
+
+ if( $start_close === false)
+ return false;
+
+ $start_close++;
+
+ $end_open = strpos($s, '[/' . $name . ']', $start_close);
+
+ if( $end_open === false)
+ return false;
+
+ $res = array( 'start' => array('open' => $start_open, 'close' => $start_close),
+ 'end' => array('open' => $end_open, 'close' => $end_open + strlen('[/' . $name . ']')) );
+ if( $start_equal !== false)
+ $res['start']['equal'] = $start_equal + 1;
+
+ return $res;
+}
+
+function bb_tag_preg_replace($pattern, $replace, $name, $s) {
+
+ $string = $s;
+
+ $occurance = 1;
+ $pos = get_bb_tag_pos($string, $name, $occurance);
+ while($pos !== false && $occurance < 1000) {
+
+ $start = substr($string, 0, $pos['start']['open']);
+ $subject = substr($string, $pos['start']['open'], $pos['end']['close'] - $pos['start']['open']);
+ $end = substr($string, $pos['end']['close']);
+ if($end === false)
+ $end = '';
+
+ $subject = preg_replace($pattern, $replace, $subject);
+ $string = $start . $subject . $end;
+
+ $occurance++;
+ $pos = get_bb_tag_pos($string, $name, $occurance);
+ }
+
+ return $string;
+}
function tryoembed($match) {
@@ -267,11 +327,16 @@ function bb_ShareAttributes($match) {
if ($avatar != "")
$headline .= '<a href="' . zid($profile) . '" ><img src="' . $avatar . '" alt="' . $author . '" height="32" width="32" /></a>';
+ if(strpos($link,'/cards/'))
+ $type = t('card');
+ else
+ $type = t('post');
+
// Bob Smith wrote the following post 2 hours ago
$fmt = sprintf( t('%1$s wrote the following %2$s %3$s'),
'<a href="' . zid($profile) . '" >' . $author . '</a>',
- '<a href="' . zid($link) . '" >' . t('post') . '</a>',
+ '<a href="' . zid($link) . '" >' . $type . '</a>',
$reldate
);
@@ -383,7 +448,7 @@ function bb_definitionList($match) {
$eatLeadingSpaces = '(?:&nbsp;|[ \t])*'; // prevent spaces infront of [*= from adding another line to the previous element
$listElements = preg_replace('/^(\n|<br \/>)/', '', $match[2]); // ltrim the first newline
$listElements = preg_replace(
- '/' . $eatLeadingSpaces . '\[\*=([[:print:]]*?)(?<!\\\)\]/ism',
+ '/' . $eatLeadingSpaces . '\[\*=([[:print:]]*?)(?<!\\\)\]/uism',
$closeDescriptionTag . '<dt>$1</dt><dd>',
$listElements
);
@@ -555,10 +620,7 @@ function bb_code_options($match) {
}
function bb_highlight($match) {
- $lang = ((in_array(strtolower($match[1]),['php','css','mysql','sql','abap','diff','html','perl','ruby',
- 'vbscript','avrc','dtd','java','xml','cpp','python','javascript','js','json','sh']))
- ? strtolower($match[1]) : 'php' );
- return text_highlight($match[2],$lang);
+ return text_highlight($match[2],strtolower($match[1]));
}
function bb_fixtable_lf($match) {
@@ -776,13 +838,13 @@ function bbcode($Text, $preserve_nl = false, $tryoembed = true, $cache = false)
// Perform URL Search
- $urlchars = '[a-zA-Z0-9\:\/\-\?\&\;\.\=\@\_\~\#\%\$\!\+\,\@\(\)]';
+ $urlchars = '[a-zA-Z0-9\:\/\-\?\&\;\.\=\_\~\#\%\$\!\+\,\@\(\)]';
if (strpos($Text,'http') !== false) {
if($tryoembed) {
$Text = preg_replace_callback("/([^\]\='".'"'."\/]|^|\#\^)(https?\:\/\/$urlchars+)/ism", 'tryoembed', $Text);
}
- $Text = preg_replace("/([^\]\='".'"'."\/]|^|\#\^)(https?\:\/\/$urlchars+)/ism", '$1<a href="$2" target="_blank" >$2</a>', $Text);
+ $Text = preg_replace("/([^\]\='".'"'."\/]|^|\#\^)(https?\:\/\/$urlchars+)/ism", '$1<a href="$2" target="_blank" rel="nofollow noopener">$2</a>', $Text);
}
if (strpos($Text,'[/share]') !== false) {
@@ -794,16 +856,16 @@ function bbcode($Text, $preserve_nl = false, $tryoembed = true, $cache = false)
}
}
if (strpos($Text,'[/url]') !== false) {
- $Text = preg_replace("/\#\^\[url\]([$URLSearchString]*)\[\/url\]/ism", '<span class="bookmark-identifier">#^</span><a class="bookmark" href="$1" target="_blank" >$1</a>', $Text);
- $Text = preg_replace("/\#\^\[url\=([$URLSearchString]*)\](.*?)\[\/url\]/ism", '<span class="bookmark-identifier">#^</span><a class="bookmark" href="$1" target="_blank" >$2</a>', $Text);
- $Text = preg_replace("/\[url\]([$URLSearchString]*)\[\/url\]/ism", '<a href="$1" target="_blank" >$1</a>', $Text);
- $Text = preg_replace("/\[url\=([$URLSearchString]*)\](.*?)\[\/url\]/ism", '<a href="$1" target="_blank" >$2</a>', $Text);
+ $Text = preg_replace("/\#\^\[url\]([$URLSearchString]*)\[\/url\]/ism", '<span class="bookmark-identifier">#^</span><a class="bookmark" href="$1" target="_blank" rel="nofollow noopener" >$1</a>', $Text);
+ $Text = preg_replace("/\#\^\[url\=([$URLSearchString]*)\](.*?)\[\/url\]/ism", '<span class="bookmark-identifier">#^</span><a class="bookmark" href="$1" target="_blank" rel="nofollow noopener" >$2</a>', $Text);
+ $Text = preg_replace("/\[url\]([$URLSearchString]*)\[\/url\]/ism", '<a href="$1" target="_blank" rel="nofollow noopener" >$1</a>', $Text);
+ $Text = preg_replace("/\[url\=([$URLSearchString]*)\](.*?)\[\/url\]/ism", '<a href="$1" target="_blank" rel="nofollow noopener" >$2</a>', $Text);
}
if (strpos($Text,'[/zrl]') !== false) {
- $Text = preg_replace("/\#\^\[zrl\]([$URLSearchString]*)\[\/zrl\]/ism", '<span class="bookmark-identifier">#^</span><a class="zrl bookmark" href="$1" target="_blank" >$1</a>', $Text);
- $Text = preg_replace("/\#\^\[zrl\=([$URLSearchString]*)\](.*?)\[\/zrl\]/ism", '<span class="bookmark-identifier">#^</span><a class="zrl bookmark" href="$1" target="_blank" >$2</a>', $Text);
- $Text = preg_replace("/\[zrl\]([$URLSearchString]*)\[\/zrl\]/ism", '<a class="zrl" href="$1" target="_blank" >$1</a>', $Text);
- $Text = preg_replace("/\[zrl\=([$URLSearchString]*)\](.*?)\[\/zrl\]/ism", '<a class="zrl" href="$1" target="_blank" >$2</a>', $Text);
+ $Text = preg_replace("/\#\^\[zrl\]([$URLSearchString]*)\[\/zrl\]/ism", '<span class="bookmark-identifier">#^</span><a class="zrl bookmark" href="$1" target="_blank" rel="nofollow noopener" >$1</a>', $Text);
+ $Text = preg_replace("/\#\^\[zrl\=([$URLSearchString]*)\](.*?)\[\/zrl\]/ism", '<span class="bookmark-identifier">#^</span><a class="zrl bookmark" href="$1" target="_blank" rel="nofollow noopener" >$2</a>', $Text);
+ $Text = preg_replace("/\[zrl\]([$URLSearchString]*)\[\/zrl\]/ism", '<a class="zrl" href="$1" target="_blank" rel="nofollow noopener" >$1</a>', $Text);
+ $Text = preg_replace("/\[zrl\=([$URLSearchString]*)\](.*?)\[\/zrl\]/ism", '<a class="zrl" href="$1" target="_blank" rel="nofollow noopener" >$2</a>', $Text);
}
if (get_account_techlevel() < 2)
@@ -811,8 +873,8 @@ function bbcode($Text, $preserve_nl = false, $tryoembed = true, $cache = false)
// Perform MAIL Search
if (strpos($Text,'[/mail]') !== false) {
- $Text = preg_replace("/\[mail\]([$MAILSearchString]*)\[\/mail\]/", '<a href="mailto:$1" target="_blank" >$1</a>', $Text);
- $Text = preg_replace("/\[mail\=([$MAILSearchString]*)\](.*?)\[\/mail\]/", '<a href="mailto:$1" target="_blank" >$2</a>', $Text);
+ $Text = preg_replace("/\[mail\]([$MAILSearchString]*)\[\/mail\]/", '<a href="mailto:$1" target="_blank" rel="nofollow noopener" >$1</a>', $Text);
+ $Text = preg_replace("/\[mail\=([$MAILSearchString]*)\](.*?)\[\/mail\]/", '<a href="mailto:$1" target="_blank" rel="nofollow noopener" >$2</a>', $Text);
}
@@ -1132,17 +1194,17 @@ function bbcode($Text, $preserve_nl = false, $tryoembed = true, $cache = false)
// if video couldn't be embedded, link to it instead.
if (strpos($Text,'[/video]') !== false) {
- $Text = preg_replace("/\[video\](.*?)\[\/video\]/", '<a href="$1" target="_blank" >$1</a>', $Text);
+ $Text = preg_replace("/\[video\](.*?)\[\/video\]/", '<a href="$1" target="_blank" rel="nofollow noopener" >$1</a>', $Text);
}
if (strpos($Text,'[/audio]') !== false) {
- $Text = preg_replace("/\[audio\](.*?)\[\/audio\]/", '<a href="$1" target="_blank" >$1</a>', $Text);
+ $Text = preg_replace("/\[audio\](.*?)\[\/audio\]/", '<a href="$1" target="_blank" rel="nofollow noopener" >$1</a>', $Text);
}
if (strpos($Text,'[/zvideo]') !== false) {
- $Text = preg_replace("/\[zvideo\](.*?)\[\/zvideo\]/", '<a class="zid" href="$1" target="_blank" >$1</a>', $Text);
+ $Text = preg_replace("/\[zvideo\](.*?)\[\/zvideo\]/", '<a class="zid" href="$1" target="_blank" rel="nofollow noopener" >$1</a>', $Text);
}
if (strpos($Text,'[/zaudio]') !== false) {
- $Text = preg_replace("/\[zaudio\](.*?)\[\/zaudio\]/", '<a class="zid" href="$1" target="_blank" >$1</a>', $Text);
+ $Text = preg_replace("/\[zaudio\](.*?)\[\/zaudio\]/", '<a class="zid" href="$1" target="_blank" rel="nofollow noopener" >$1</a>', $Text);
}
// if ($tryoembed){
@@ -1151,7 +1213,7 @@ function bbcode($Text, $preserve_nl = false, $tryoembed = true, $cache = false)
// }
// } else {
// if (strpos($Text,'[/iframe]') !== false) {
-// $Text = preg_replace("/\[iframe\](.*?)\[\/iframe\]/ism", '<a href="$1" target="_blank" >$1</a>', $Text);
+// $Text = preg_replace("/\[iframe\](.*?)\[\/iframe\]/ism", '<a href="$1" target="_blank" rel="nofollow noopener" >$1</a>', $Text);
// }
// }
@@ -1174,6 +1236,7 @@ function bbcode($Text, $preserve_nl = false, $tryoembed = true, $cache = false)
$Text = preg_replace("/\[event\-start\](.*?)\[\/event\-start\]/ism",$sub,$Text);
+ $Text = preg_replace("/\[event\](.*?)\[\/event\]/ism",'',$Text);
$Text = preg_replace("/\[event\-summary\](.*?)\[\/event\-summary\]/ism",'',$Text);
$Text = preg_replace("/\[event\-description\](.*?)\[\/event\-description\]/ism",'',$Text);
$Text = preg_replace("/\[event\-finish\](.*?)\[\/event\-finish\]/ism",'',$Text);
@@ -1197,6 +1260,9 @@ function bbcode($Text, $preserve_nl = false, $tryoembed = true, $cache = false)
$Text = preg_replace_callback("/\[pre\](.*?)\[\/pre\]/ism", 'bb_unspacefy_and_trim', $Text);
}
+ // replace escaped links in code= blocks
+ $Text = str_replace('%eY9-!','http', $Text);
+
$Text = preg_replace('/\[\&amp\;([#a-z0-9]+)\;\]/', '&$1;', $Text);
// fix any escaped ampersands that may have been converted into links
diff --git a/include/channel.php b/include/channel.php
index 856fb6303..399dff87e 100644
--- a/include/channel.php
+++ b/include/channel.php
@@ -7,6 +7,7 @@ require_once('include/zot.php');
require_once('include/crypto.php');
require_once('include/menu.php');
require_once('include/perm_upgrade.php');
+require_once('include/photo/photo_driver.php');
/**
* @brief Called when creating a new channel.
@@ -52,13 +53,14 @@ function identity_check_service_class($account_id) {
*
* This action is pluggable.
* We're currently only checking for an empty name or one that exceeds our
- * storage limit (255 chars). 255 chars is probably going to create a mess on
+ * storage limit (191 chars). 191 chars is probably going to create a mess on
* some pages.
* Plugins can set additional policies such as full name requirements, character
* sets, multi-byte length, etc.
*
+ * @hooks validate_channelname
+ * * \e array \b name
* @param string $name
- *
* @returns nil return if name is valid, or string describing the error state.
*/
function validate_channelname($name) {
@@ -66,10 +68,10 @@ function validate_channelname($name) {
if (! $name)
return t('Empty name');
- if (strlen($name) > 255)
+ if (mb_strlen($name) > 191)
return t('Name too long');
- $arr = array('name' => $name);
+ $arr = ['name' => $name];
call_hooks('validate_channelname', $arr);
if (x($arr, 'message'))
@@ -242,24 +244,23 @@ function create_identity($arr) {
$expire = 0;
- $r = q("insert into channel ( channel_account_id, channel_primary,
- channel_name, channel_address, channel_guid, channel_guid_sig,
- channel_hash, channel_prvkey, channel_pubkey, channel_pageflags, channel_system, channel_expire_days, channel_timezone )
- values ( %d, %d, '%s', '%s', '%s', '%s', '%s', '%s', '%s', %d, %d, %d, '%s' ) ",
+ $r = channel_store_lowlevel(
+ [
+ 'channel_account_id' => intval($arr['account_id']),
+ 'channel_primary' => intval($primary),
+ 'channel_name' => $name,
+ 'channel_address' => $nick,
+ 'channel_guid' => $guid,
+ 'channel_guid_sig' => $sig,
+ 'channel_hash' => $hash,
+ 'channel_prvkey' => $key['prvkey'],
+ 'channel_pubkey' => $key['pubkey'],
+ 'channel_pageflags' => intval($pageflags),
+ 'channel_system' => intval($system),
+ 'channel_expire_days' => intval($expire),
+ 'channel_timezone' => App::$timezone
- intval($arr['account_id']),
- intval($primary),
- dbesc($name),
- dbesc($nick),
- dbesc($guid),
- dbesc($sig),
- dbesc($hash),
- dbesc($key['prvkey']),
- dbesc($key['pubkey']),
- intval($pageflags),
- intval($system),
- intval($expire),
- dbesc(App::$timezone)
+ ]
);
$r = q("select * from channel where channel_account_id = %d
@@ -273,6 +274,19 @@ function create_identity($arr) {
return $ret;
}
+ $a = q("select * from account where account_id = %d",
+ intval($arr['account_id'])
+ );
+
+ $photo_type = null;
+
+ $z = [ 'account' => $a[0], 'channel' => $r[0], 'photo_url' => '' ];
+ call_hooks('create_channel_photo',$z);
+
+ if($z['photo_url']) {
+ $photo_type = import_channel_photo_from_url($z['photo_url'],$arr['account_id'],$r[0]['channel_id']);
+ }
+
if($role_permissions && array_key_exists('limits',$role_permissions))
$perm_limits = $role_permissions['limits'];
else
@@ -318,6 +332,7 @@ function create_identity($arr) {
'xchan_guid' => $guid,
'xchan_guid_sig' => $sig,
'xchan_pubkey' => $key['pubkey'],
+ 'xchan_photo_mimetype' => (($photo_type) ? $photo_type : 'image/png'),
'xchan_photo_l' => z_root() . "/photo/profile/l/{$newuid}",
'xchan_photo_m' => z_root() . "/photo/profile/m/{$newuid}",
'xchan_photo_s' => z_root() . "/photo/profile/s/{$newuid}",
@@ -454,6 +469,194 @@ function create_identity($arr) {
return $ret;
}
+
+function change_channel_keys($channel) {
+
+ $ret = array('success' => false);
+
+ $stored = [];
+
+ $key = new_keypair(4096);
+
+ $sig = base64url_encode(rsa_sign($channel['channel_guid'],$key['prvkey']));
+ $hash = make_xchan_hash($channel['channel_guid'],$sig);
+
+ $stored['old_guid'] = $channel['channel_guid'];
+ $stored['old_guid_sig'] = $channel['channel_guid_sig'];
+ $stored['old_key'] = $channel['channel_pubkey'];
+ $stored['old_hash'] = $channel['channel_hash'];
+
+ $stored['new_key'] = $key['pubkey'];
+ $stored['new_sig'] = base64url_encode(rsa_sign($key['pubkey'],$channel['channel_prvkey']));
+
+ // Save this info for the notifier to collect
+
+ set_pconfig($channel['channel_id'],'system','keychange',$stored);
+
+ $r = q("update channel set channel_prvkey = '%s', channel_pubkey = '%s', channel_guid_sig = '%s', channel_hash = '%s' where channel_id = %d",
+ dbesc($key['prvkey']),
+ dbesc($key['pubkey']),
+ dbesc($sig),
+ dbesc($hash),
+ intval($channel['channel_id'])
+ );
+ if(! $r) {
+ return $ret;
+ }
+
+ $r = q("select * from channel where channel_id = %d",
+ intval($channel['channel_id'])
+ );
+
+ if(! $r) {
+ $ret['message'] = t('Unable to retrieve modified identity');
+ return $ret;
+ }
+
+ $modified = $r[0];
+
+ $h = q("select * from hubloc where hubloc_hash = '%s' and hubloc_url = '%s' ",
+ dbesc($stored['old_hash']),
+ dbesc(z_root())
+ );
+
+ if($h) {
+ foreach($h as $hv) {
+ $hv['hubloc_guid_sig'] = $sig;
+ $hv['hubloc_hash'] = $hash;
+ $hv['hubloc_url_sig'] = base64url_encode(rsa_sign(z_root(),$modifed['channel_prvkey']));
+ hubloc_store_lowlevel($hv);
+ }
+ }
+
+ $x = q("select * from xchan where xchan_hash = '%s' ",
+ dbesc($stored['old_hash'])
+ );
+
+ $check = q("select * from xchan where xchan_hash = '%s'",
+ dbesc($hash)
+ );
+
+ if(($x) && (! $check)) {
+ $oldxchan = $x[0];
+ foreach($x as $xv) {
+ $xv['xchan_guid_sig'] = $sig;
+ $xv['xchan_hash'] = $hash;
+ $xv['xchan_pubkey'] = $key['pubkey'];
+ xchan_store_lowlevel($xv);
+ $newxchan = $xv;
+ }
+ }
+
+ build_sync_packet($channel['channel_id'], [ 'keychange' => $stored ]);
+
+ $a = q("select * from abook where abook_xchan = '%s' and abook_self = 1",
+ dbesc($stored['old_hash'])
+ );
+
+ if($a) {
+ q("update abook set abook_xchan = '%s' where abook_id = %d",
+ dbesc($hash),
+ intval($a[0]['abook_id'])
+ );
+ }
+
+ xchan_change_key($oldxchan,$newxchan,$stored);
+
+ Zotlabs\Daemon\Master::Summon(array('Notifier', 'keychange', $channel['channel_id']));
+
+ $ret['success'] = true;
+ return $ret;
+}
+
+function channel_change_address($channel,$new_address) {
+
+ $ret = array('success' => false);
+
+ $old_address = $channel['channel_address'];
+
+ if($new_address === 'sys') {
+ $ret['message'] = t('Reserved nickname. Please choose another.');
+ return $ret;
+ }
+
+ if(check_webbie(array($new_address)) !== $new_address) {
+ $ret['message'] = t('Nickname has unsupported characters or is already being used on this site.');
+ return $ret;
+ }
+
+ $r = q("update channel set channel_address = '%s' where channel_id = %d",
+ dbesc($new_address),
+ intval($channel['channel_id'])
+ );
+ if(! $r) {
+ return $ret;
+ }
+
+ $r = q("select * from channel where channel_id = %d",
+ intval($channel['channel_id'])
+ );
+
+ if(! $r) {
+ $ret['message'] = t('Unable to retrieve modified identity');
+ return $ret;
+ }
+
+ $r = q("update xchan set xchan_addr = '%s' where xchan_hash = '%s'",
+ dbesc($new_address . '@' . App::get_hostname()),
+ dbesc($channel['channel_hash'])
+ );
+
+ $h = q("select * from hubloc where hubloc_hash = '%s' and hubloc_url = '%s' ",
+ dbesc($channel['channel_hash']),
+ dbesc(z_root())
+ );
+
+ if($h) {
+ foreach($h as $hv) {
+ if($hv['hubloc_primary']) {
+ q("update hubloc set hubloc_primary = 0 where hubloc_id = %d",
+ intval($hv['hubloc_id'])
+ );
+ }
+ q("update hubloc set hubloc_deleted = 1 where hubloc_id = %d",
+ intval($hv['hubloc_id'])
+ );
+
+ unset($hv['hubloc_id']);
+ $hv['hubloc_addr'] = $new_address . '@' . App::get_hostname();
+ hubloc_store_lowlevel($hv);
+ }
+ }
+
+ // fix apps which were stored with the actual name rather than a macro
+
+ $r = q("select * from app where app_channel = %d and app_system = 1",
+ intval($channel['channel_id'])
+ );
+ if($r) {
+ foreach($r as $rv) {
+ $replace = preg_replace('/([\=\/])(' . $old_address . ')($|[\%\/])/ism','$1' . $new_address . '$3',$rv['app_url']);
+ if($replace != $rv['app_url']) {
+ q("update app set app_url = '%s' where id = %d",
+ dbesc($replace),
+ intval($rv['id'])
+ );
+ }
+ }
+ }
+
+ Zotlabs\Daemon\Master::Summon(array('Notifier', 'refresh_all', $channel['channel_id']));
+
+ $ret['success'] = true;
+ return $ret;
+}
+
+
+
+
+
+
/**
* @brief Set default channel to be used on login.
*
@@ -465,7 +668,6 @@ function create_identity($arr) {
* if true, set this default unconditionally
* if $force is false only do this if there is no existing default
*/
-
function set_default_login_identity($account_id, $channel_id, $force = true) {
$r = q("select account_default_channel from account where account_id = %d limit 1",
intval($account_id)
@@ -480,12 +682,29 @@ function set_default_login_identity($account_id, $channel_id, $force = true) {
}
}
-
+/**
+ * @brief Return an array with default list of sections to export.
+ *
+ * @hooks get_default_export_sections
+ * * \e array \b sections
+ * @return array with default section names to export
+ */
function get_default_export_sections() {
- $sections = [ 'channel', 'connections', 'config', 'apps', 'chatrooms', 'events', 'webpages', 'mail', 'wikis' ];
+ $sections = [
+ 'channel',
+ 'connections',
+ 'config',
+ 'apps',
+ 'chatrooms',
+ 'events',
+ 'webpages',
+ 'mail',
+ 'wikis'
+ ];
$cb = [ 'sections' => $sections ];
call_hooks('get_default_export_sections', $cb);
+
return $cb['sections'];
}
@@ -495,15 +714,17 @@ function get_default_export_sections() {
* which would be necessary to create a nomadic identity clone. This includes
* most channel resources and connection information with the exception of content.
*
+ * @hooks identity_basic_export
+ * * \e int \b channel_id
+ * * \e array \b sections
+ * * \e array \b data
* @param int $channel_id
* Channel_id to export
- * @param boolean $items
- * Include channel posts (wall items), default false
- *
+ * @param array $sections (optional)
+ * Which sections to include in the export, default see get_default_export_sections()
* @returns array
* See function for details
*/
-
function identity_basic_export($channel_id, $sections = null) {
/*
@@ -513,16 +734,16 @@ function identity_basic_export($channel_id, $sections = null) {
if(! $sections) {
$sections = get_default_export_sections();
}
-
+
$ret = [];
// use constants here as otherwise we will have no idea if we can import from a site
// with a non-standard platform and version.
$ret['compatibility'] = [
- 'project' => PLATFORM_NAME,
- 'version' => STD_VERSION,
- 'database' => DB_UPDATE_VERSION,
+ 'project' => PLATFORM_NAME,
+ 'version' => STD_VERSION,
+ 'database' => DB_UPDATE_VERSION,
'server_role' => Zotlabs\Lib\System::get_server_role()
];
@@ -539,6 +760,8 @@ function identity_basic_export($channel_id, $sections = null) {
$ret['relocate'] = [ 'channel_address' => $r[0]['channel_address'], 'url' => z_root()];
if(in_array('channel',$sections)) {
$ret['channel'] = $r[0];
+ unset($ret['channel']['channel_password']);
+ unset($ret['channel']['channel_salt']);
}
}
@@ -549,8 +772,7 @@ function identity_basic_export($channel_id, $sections = null) {
if($r)
$ret['profile'] = $r;
-
- $r = q("select mimetype, content, os_storage from photo
+ $r = q("select mimetype, content, os_storage from photo
where imgscale = 4 and photo_usage = %d and uid = %d limit 1",
intval(PHOTO_PROFILE),
intval($channel_id)
@@ -558,8 +780,8 @@ function identity_basic_export($channel_id, $sections = null) {
if($r) {
$ret['photo'] = [
- 'type' => $r[0]['mimetype'],
- 'data' => (($r[0]['os_storage'])
+ 'type' => $r[0]['mimetype'],
+ 'data' => (($r[0]['os_storage'])
? base64url_encode(file_get_contents($r[0]['content'])) : base64url_encode($r[0]['content']))
];
}
@@ -605,7 +827,6 @@ function identity_basic_export($channel_id, $sections = null) {
);
if($r)
$ret['group_member'] = $r;
-
}
if(in_array('config',$sections)) {
@@ -614,7 +835,7 @@ function identity_basic_export($channel_id, $sections = null) {
);
if($r)
$ret['config'] = $r;
-
+
// All other term types will be included in items, if requested.
$r = q("select * from term where ttype in (%d,%d) and uid = %d",
@@ -641,7 +862,6 @@ function identity_basic_export($channel_id, $sections = null) {
if($r)
$ret['likes'] = $r;
-
}
if(in_array('apps',$sections)) {
@@ -667,7 +887,6 @@ function identity_basic_export($channel_id, $sections = null) {
$ret['chatroom'] = $r;
}
-
if(in_array('events',$sections)) {
$r = q("select * from event where uid = %d",
intval($channel_id)
@@ -697,7 +916,7 @@ function identity_basic_export($channel_id, $sections = null) {
$ret['menu'][] = menu_element($ret['channel'],$m);
}
}
- $r = q("select * from item where item_type in ( "
+ $r = q("select * from item where item_type in ( "
. ITEM_TYPE_BLOCK . "," . ITEM_TYPE_PDL . "," . ITEM_TYPE_WEBPAGE . " ) and uid = %d",
intval($channel_id)
);
@@ -707,7 +926,6 @@ function identity_basic_export($channel_id, $sections = null) {
$r = fetch_post_tags($r,true);
foreach($r as $rr)
$ret['webpages'][] = encode_item($rr,true);
-
}
}
@@ -722,14 +940,14 @@ function identity_basic_export($channel_id, $sections = null) {
$ret['conv'] = $r;
}
- $r = q("select * from mail where mail.uid = %d",
+ $r = q("select * from mail where channel_id = %d",
intval($channel_id)
);
if($r) {
$m = array();
foreach($r as $rr) {
xchan_mail_query($rr);
- $m[] = mail_encode($rr,true);
+ $m[] = encode_mail($rr,true);
}
$ret['mail'] = $m;
}
@@ -758,7 +976,7 @@ function identity_basic_export($channel_id, $sections = null) {
* Don't export linked resource items. we'll have to pull those out separately.
*/
- $r = q("select * from item where item_wall = 1 and item_deleted = 0 and uid = %d
+ $r = q("select * from item where item_wall = 1 and item_deleted = 0 and uid = %d
and created > %s - INTERVAL %s and resource_type = '' order by created",
intval($channel_id),
db_utcnow(),
@@ -1147,30 +1365,14 @@ function profile_sidebar($profile, $block = 0, $show_connect = true, $zcard = fa
$location = $reddress = $pdesc = $gender = $marital = $homepage = False;
}
+ if($profile['gender']) {
+ $profile['gender_icon'] = gender_icon($profile['gender']);
+ }
+
$firstname = ((strpos($profile['channel_name'],' '))
? trim(substr($profile['channel_name'],0,strpos($profile['channel_name'],' '))) : $profile['channel_name']);
$lastname = (($firstname === $profile['channel_name']) ? '' : trim(substr($profile['channel_name'],strlen($firstname))));
- // @fixme move this to the diaspora plugin itself
-
- if(plugin_is_installed('diaspora')) {
- $diaspora = array(
- 'podloc' => z_root(),
- 'guid' => $profile['channel_guid'] . str_replace('.','',App::get_hostname()),
- 'pubkey' => pemtorsa($profile['channel_pubkey']),
- 'searchable' => (($block) ? 'false' : 'true'),
- 'nickname' => $profile['channel_address'],
- 'fullname' => $profile['channel_name'],
- 'firstname' => $firstname,
- 'lastname' => $lastname,
- 'photo300' => z_root() . '/photo/profile/300/' . $profile['uid'] . '.jpg',
- 'photo100' => z_root() . '/photo/profile/100/' . $profile['uid'] . '.jpg',
- 'photo50' => z_root() . '/photo/profile/50/' . $profile['uid'] . '.jpg',
- );
- }
- else
- $diaspora = '';
-
$contact_block = contact_block();
@@ -1193,11 +1395,6 @@ function profile_sidebar($profile, $block = 0, $show_connect = true, $zcard = fa
else
$tpl = get_markup_template('profile_vcard.tpl');
- require_once('include/widgets.php');
-
-// if(! feature_enabled($profile['uid'],'hide_rating'))
- $z = widget_rating(array('target' => $profile['channel_hash']));
-
$o .= replace_macros($tpl, array(
'$zcard' => $zcard,
'$profile' => $profile,
@@ -1209,9 +1406,8 @@ function profile_sidebar($profile, $block = 0, $show_connect = true, $zcard = fa
'$marital' => $marital,
'$homepage' => $homepage,
'$chanmenu' => $channel_menu,
- '$diaspora' => $diaspora,
'$reddress' => $reddress,
- '$rating' => $z,
+ '$rating' => '',
'$contact_block' => $contact_block,
'$editmenu' => profile_edit_menu($profile['uid'])
));
@@ -1220,7 +1416,29 @@ function profile_sidebar($profile, $block = 0, $show_connect = true, $zcard = fa
call_hooks('profile_sidebar', $arr);
- return $o;
+ return $arr['entry'];
+
+}
+
+function gender_icon($gender) {
+
+// logger('gender: ' . $gender);
+
+ // This can easily get throw off if the observer language is different
+ // than the channel owner language.
+
+ if(strpos(strtolower($gender),strtolower(t('Female'))) !== false)
+ return 'venus';
+ if(strpos(strtolower($gender),strtolower(t('Male'))) !== false)
+ return 'mars';
+ if(strpos(strtolower($gender),strtolower(t('Trans'))) !== false)
+ return 'transgender';
+ if(strpos(strtolower($gender),strtolower(t('Neuter'))) !== false)
+ return 'neuter';
+ if(strpos(strtolower($gender),strtolower(t('Non-specific'))) !== false)
+ return 'genderless';
+
+ return '';
}
@@ -1399,26 +1617,28 @@ function get_my_address() {
}
/**
- * @brief
+ * @brief Add visitor's zid to our xchan and attempt authentication.
*
- * If somebody arrives at our site using a zid, add their xchan to our DB if we don't have it already.
+ * If somebody arrives at our site using a zid, add their xchan to our DB if we
+ * don't have it already.
* And if they aren't already authenticated here, attempt reverse magic auth.
*
- *
- * @hooks 'zid_init'
- * string 'zid' - their zid
- * string 'url' - the destination url
+ * @hooks zid_init
+ * * \e string \b zid - their zid
+ * * \e string \b url - the destination url
*/
function zid_init() {
$tmp_str = get_my_address();
if(validate_email($tmp_str)) {
- Zotlabs\Daemon\Master::Summon(array('Gprobe',bin2hex($tmp_str)));
$arr = array('zid' => $tmp_str, 'url' => App::$cmd);
call_hooks('zid_init',$arr);
if(! local_channel()) {
$r = q("select * from hubloc where hubloc_addr = '%s' order by hubloc_connected desc limit 1",
dbesc($tmp_str)
);
+ if(! $r) {
+ Zotlabs\Daemon\Master::Summon(array('Gprobe',bin2hex($tmp_str)));
+ }
if($r && remote_channel() && remote_channel() === $r[0]['hubloc_hash'])
return;
logger('zid_init: not authenticated. Invoking reverse magic-auth for ' . $tmp_str);
@@ -1427,7 +1647,7 @@ function zid_init() {
$query = str_replace(array('?zid=','&zid='),array('?rzid=','&rzid='),$query);
$dest = '/' . urlencode($query);
if($r && ($r[0]['hubloc_url'] != z_root()) && (! strstr($dest,'/magic')) && (! strstr($dest,'/rmagic'))) {
- goaway($r[0]['hubloc_url'] . '/magic' . '?f=&rev=1&dest=' . z_root() . $dest);
+ goaway($r[0]['hubloc_url'] . '/magic' . '?f=&rev=1&owa=1&dest=' . z_root() . $dest);
}
else
logger('zid_init: no hubloc found.');
@@ -1436,12 +1656,9 @@ function zid_init() {
}
/**
- * @brief
- *
- * If somebody arrives at our site using a zat, authenticate them
+ * @brief If somebody arrives at our site using a zat, authenticate them.
*
*/
-
function zat_init() {
if(local_channel() || remote_channel())
return;
@@ -1453,7 +1670,6 @@ function zat_init() {
$xchan = atoken_xchan($r[0]);
atoken_login($xchan);
}
-
}
@@ -1486,7 +1702,7 @@ function get_theme_uid() {
*
* @param int $size
* one of (300, 80, 48)
-* @returns string
+* @returns string with path to profile photo
*/
function get_default_profile_photo($size = 300) {
$scheme = get_config('system','default_profile_photo');
@@ -1608,7 +1824,7 @@ function get_profile_fields_basic($filter = 0) {
$profile_fields_basic = (($filter == 0) ? get_config('system','profile_fields_basic') : null);
if(! $profile_fields_basic)
- $profile_fields_basic = array('fullname','pdesc','chandesc','gender','dob','dob_tz','address','locality','region','postal_code','country_name','marital','sexual','homepage','hometown','keywords','about','contact');
+ $profile_fields_basic = array('fullname','pdesc','chandesc','comms','gender','dob','dob_tz','address','locality','region','postal_code','country_name','marital','sexual','homepage','hometown','keywords','about','contact');
$x = array();
if($profile_fields_basic)
@@ -1976,12 +2192,9 @@ function channel_manual_conv_update($channel_id) {
$x = get_pconfig($channel_id, 'system','manual_conversation_update');
if($x === false)
- $x = get_config('system','manual_conversation_update');
- if($x === false)
- $x = 1;
+ $x = get_config('system','manual_conversation_update', 1);
return intval($x);
-
}
@@ -1996,7 +2209,47 @@ function remote_login() {
}
+function channel_store_lowlevel($arr) {
+ $store = [
+ 'channel_account_id' => ((array_key_exists('channel_account_id',$arr)) ? $arr['channel_account_id'] : '0'),
+ 'channel_primary' => ((array_key_exists('channel_primary',$arr)) ? $arr['channel_primary'] : '0'),
+ 'channel_name' => ((array_key_exists('channel_name',$arr)) ? $arr['channel_name'] : ''),
+ 'channel_address' => ((array_key_exists('channel_address',$arr)) ? $arr['channel_address'] : ''),
+ 'channel_guid' => ((array_key_exists('channel_guid',$arr)) ? $arr['channel_guid'] : ''),
+ 'channel_guid_sig' => ((array_key_exists('channel_guid_sig',$arr)) ? $arr['channel_guid_sig'] : ''),
+ 'channel_hash' => ((array_key_exists('channel_hash',$arr)) ? $arr['channel_hash'] : ''),
+ 'channel_timezone' => ((array_key_exists('channel_timezone',$arr)) ? $arr['channel_timezone'] : 'UTC'),
+ 'channel_location' => ((array_key_exists('channel_location',$arr)) ? $arr['channel_location'] : ''),
+ 'channel_theme' => ((array_key_exists('channel_theme',$arr)) ? $arr['channel_theme'] : ''),
+ 'channel_startpage' => ((array_key_exists('channel_startpage',$arr)) ? $arr['channel_startpage'] : ''),
+ 'channel_pubkey' => ((array_key_exists('channel_pubkey',$arr)) ? $arr['channel_pubkey'] : ''),
+ 'channel_prvkey' => ((array_key_exists('channel_prvkey',$arr)) ? $arr['channel_prvkey'] : ''),
+ 'channel_notifyflags' => ((array_key_exists('channel_notifyflags',$arr)) ? $arr['channel_notifyflags'] : '65535'),
+ 'channel_pageflags' => ((array_key_exists('channel_pageflags',$arr)) ? $arr['channel_pageflags'] : '0'),
+ 'channel_dirdate' => ((array_key_exists('channel_dirdate',$arr)) ? $arr['channel_dirdate'] : NULL_DATE),
+ 'channel_lastpost' => ((array_key_exists('channel_lastpost',$arr)) ? $arr['channel_lastpost'] : NULL_DATE),
+ 'channel_deleted' => ((array_key_exists('channel_deleted',$arr)) ? $arr['channel_deleted'] : NULL_DATE),
+ 'channel_max_anon_mail' => ((array_key_exists('channel_max_anon_mail',$arr)) ? $arr['channel_max_anon_mail'] : '10'),
+ 'channel_max_friend_req' => ((array_key_exists('channel_max_friend_req',$arr)) ? $arr['channel_max_friend_req'] : '10'),
+ 'channel_expire_days' => ((array_key_exists('channel_expire_days',$arr)) ? $arr['channel_expire_days'] : '0'),
+ 'channel_passwd_reset' => ((array_key_exists('channel_passwd_reset',$arr)) ? $arr['channel_passwd_reset'] : ''),
+ 'channel_default_group' => ((array_key_exists('channel_default_group',$arr)) ? $arr['channel_default_group'] : ''),
+ 'channel_allow_cid' => ((array_key_exists('channel_allow_cid',$arr)) ? $arr['channel_allow_cid'] : ''),
+ 'channel_allow_gid' => ((array_key_exists('channel_allow_gid',$arr)) ? $arr['channel_allow_gid'] : ''),
+ 'channel_deny_cid' => ((array_key_exists('channel_deny_cid',$arr)) ? $arr['channel_deny_cid'] : ''),
+ 'channel_deny_gid' => ((array_key_exists('channel_deny_gid',$arr)) ? $arr['channel_deny_gid'] : ''),
+ 'channel_removed' => ((array_key_exists('channel_removed',$arr)) ? $arr['channel_removed'] : '0'),
+ 'channel_system' => ((array_key_exists('channel_system',$arr)) ? $arr['channel_system'] : '0'),
+
+ 'channel_moved' => ((array_key_exists('channel_moved',$arr)) ? $arr['channel_moved'] : ''),
+ 'channel_password' => ((array_key_exists('channel_password',$arr)) ? $arr['channel_password'] : ''),
+ 'channel_salt' => ((array_key_exists('channel_salt',$arr)) ? $arr['channel_salt'] : '')
+
+ ];
+ return create_table_from_array('channel',$store);
+
+}
function profile_store_lowlevel($arr) {
@@ -2048,4 +2301,315 @@ function profile_store_lowlevel($arr) {
];
return create_table_from_array('profile',$store);
+}
+
+
+// Included here for completeness, but this is a very dangerous operation.
+// It is the caller's responsibility to confirm the requestor's intent and
+// authorisation to do this.
+
+function account_remove($account_id,$local = true,$unset_session = true) {
+
+ logger('account_remove: ' . $account_id);
+
+ if(! intval($account_id)) {
+ logger('account_remove: no account.');
+ return false;
+ }
+
+ // Don't let anybody nuke the only admin account.
+
+ $r = q("select account_id from account where (account_roles & %d) > 0",
+ intval(ACCOUNT_ROLE_ADMIN)
+ );
+
+ if($r !== false && count($r) == 1 && $r[0]['account_id'] == $account_id) {
+ logger("Unable to remove the only remaining admin account");
+ return false;
+ }
+
+ $r = q("select * from account where account_id = %d limit 1",
+ intval($account_id)
+ );
+ $account_email=$r[0]['account_email'];
+
+ if(! $r) {
+ logger('account_remove: No account with id: ' . $account_id);
+ return false;
+ }
+
+ $x = q("select channel_id from channel where channel_account_id = %d",
+ intval($account_id)
+ );
+ if($x) {
+ foreach($x as $xx) {
+ channel_remove($xx['channel_id'],$local,false);
+ }
+ }
+
+ $r = q("delete from account where account_id = %d",
+ intval($account_id)
+ );
+
+
+ if ($unset_session) {
+ App::$session->nuke();
+ notice( sprintf(t('Account \'%s\' deleted'),$account_email) . EOL);
+ goaway(z_root());
+ }
+
+ return $r;
+}
+
+/**
+ * @brief Removes a channel.
+ *
+ * @hooks channel_remove
+ * * \e array \b entry from channel tabel for $channel_id
+ * @param int $channel_id
+ * @param boolean $local default true
+ * @param boolean $unset_session default false
+ */
+function channel_remove($channel_id, $local = true, $unset_session = false) {
+
+ if(! $channel_id)
+ return;
+
+ logger('Removing channel: ' . $channel_id);
+ logger('local only: ' . intval($local));
+
+ $r = q("select * from channel where channel_id = %d limit 1", intval($channel_id));
+ if(! $r) {
+ logger('channel not found: ' . $channel_id);
+ return;
+ }
+
+ $channel = $r[0];
+
+ call_hooks('channel_remove', $r[0]);
+
+ if(! $local) {
+
+ $r = q("update channel set channel_deleted = '%s', channel_removed = 1 where channel_id = %d",
+ dbesc(datetime_convert()),
+ intval($channel_id)
+ );
+
+ q("delete from pconfig where uid = %d",
+ intval($channel_id)
+ );
+
+ logger('deleting hublocs',LOGGER_DEBUG);
+
+ $r = q("update hubloc set hubloc_deleted = 1 where hubloc_hash = '%s'",
+ dbesc($channel['channel_hash'])
+ );
+
+ $r = q("update xchan set xchan_deleted = 1 where xchan_hash = '%s'",
+ dbesc($channel['channel_hash'])
+ );
+
+ Zotlabs\Daemon\Master::Summon(array('Notifier','purge_all',$channel_id));
+ }
+
+
+ $r = q("select * from iconfig left join item on item.id = iconfig.iid
+ where item.uid = %d",
+ intval($channel_id)
+ );
+ if($r) {
+ foreach($r as $rr) {
+ q("delete from iconfig where iid = %d",
+ intval($rr['iid'])
+ );
+ }
+ }
+
+
+ q("DELETE FROM groups WHERE uid = %d", intval($channel_id));
+ q("DELETE FROM group_member WHERE uid = %d", intval($channel_id));
+ q("DELETE FROM event WHERE uid = %d", intval($channel_id));
+ q("DELETE FROM item WHERE uid = %d", intval($channel_id));
+ q("DELETE FROM mail WHERE channel_id = %d", intval($channel_id));
+ q("DELETE FROM notify WHERE uid = %d", intval($channel_id));
+ q("DELETE FROM photo WHERE uid = %d", intval($channel_id));
+ q("DELETE FROM attach WHERE uid = %d", intval($channel_id));
+ q("DELETE FROM profile WHERE uid = %d", intval($channel_id));
+ q("DELETE FROM pconfig WHERE uid = %d", intval($channel_id));
+
+ /// @FIXME At this stage we need to remove the file resources located under /store/$nickname
+
+ q("delete from abook where abook_xchan = '%s' and abook_self = 1 ",
+ dbesc($channel['channel_hash'])
+ );
+
+ $r = q("update channel set channel_deleted = '%s', channel_removed = 1 where channel_id = %d",
+ dbesc(datetime_convert()),
+ intval($channel_id)
+ );
+
+ // if this was the default channel, set another one as default
+ if(App::$account['account_default_channel'] == $channel_id) {
+ $r = q("select channel_id from channel where channel_account_id = %d and channel_removed = 0 limit 1",
+ intval(App::$account['account_id']),
+ intval(PAGE_REMOVED));
+ if ($r) {
+ $rr = q("update account set account_default_channel = %d where account_id = %d",
+ intval($r[0]['channel_id']),
+ intval(App::$account['account_id']));
+ logger("Default channel deleted, changing default to channel_id " . $r[0]['channel_id']);
+ }
+ else {
+ $rr = q("update account set account_default_channel = 0 where account_id = %d",
+ intval(App::$account['account_id'])
+ );
+ }
+ }
+
+ logger('deleting hublocs',LOGGER_DEBUG);
+
+ $r = q("update hubloc set hubloc_deleted = 1 where hubloc_hash = '%s' and hubloc_url = '%s' ",
+ dbesc($channel['channel_hash']),
+ dbesc(z_root())
+ );
+
+ // Do we have any valid hublocs remaining?
+
+ $hublocs = 0;
+
+ $r = q("select hubloc_id from hubloc where hubloc_hash = '%s' and hubloc_deleted = 0",
+ dbesc($channel['channel_hash'])
+ );
+ if($r)
+ $hublocs = count($r);
+
+ if(! $hublocs) {
+ $r = q("update xchan set xchan_deleted = 1 where xchan_hash = '%s' ",
+ dbesc($channel['channel_hash'])
+ );
+ }
+
+ //remove from file system
+ $r = q("select channel_address from channel where channel_id = %d limit 1",
+ intval($channel_id)
+ );
+
+ if($r) {
+ $channel_address = $r[0]['channel_address'] ;
+ }
+ if($channel_address) {
+ $f = 'store/' . $channel_address.'/';
+ logger('delete '. $f);
+ if(is_dir($f)) {
+ @rrmdir($f);
+ }
+ }
+
+ Zotlabs\Daemon\Master::Summon(array('Directory',$channel_id));
+
+ if($channel_id == local_channel() && $unset_session) {
+ App::$session->nuke();
+ goaway(z_root());
+ }
+}
+
+/**
+ * @brief This checks if a channel is allowed to publish executable code.
+ *
+ * It is up to the caller to determine if the observer or local_channel
+ * is in fact the resource owner whose channel_id is being checked.
+ *
+ * @param int $channel_id
+ * @return boolean
+ */
+function channel_codeallowed($channel_id) {
+ if(! intval($channel_id))
+ return false;
+
+ $x = channelx_by_n($channel_id);
+ if(($x) && ($x['channel_pageflags'] & PAGE_ALLOWCODE))
+ return true;
+
+ return false;
+
+}
+
+function anon_identity_init($reqvars) {
+
+ $x = [ 'request_vars' => $reqvars, 'xchan' => null, 'success' => 'unset' ];
+ call_hooks('anon_identity_init',$x);
+ if($x['success'] !== 'unset' && intval($x['success']) && $x['xchan'])
+ return $x['xchan'];
+
+ // allow a captcha handler to over-ride
+ if($x['success'] !== 'unset' && (intval($x['success']) === 0))
+ return false;
+
+
+ $anon_name = strip_tags(trim($reqvars['anonname']));
+ $anon_email = strip_tags(trim($reqvars['anonmail']));
+ $anon_url = strip_tags(trim($reqvars['anonurl']));
+
+ if(! ($anon_name && $anon_email)) {
+ logger('anonymous commenter did not complete form');
+ return false;
+ }
+
+ if(! validate_email($anon_email)) {
+ logger('enonymous email not valid');
+ return false;
+ }
+
+ if(! $anon_url)
+ $anon_url = z_root();
+
+ $hash = hash('md5',$anon_email);
+
+ $x = q("select * from xchan where xchan_guid = '%s' and xchan_hash = '%s' and xchan_network = 'unknown' limit 1",
+ dbesc($anon_email),
+ dbesc($hash)
+ );
+
+ if(! $x) {
+ xchan_store_lowlevel([
+ 'xchan_guid' => $anon_email,
+ 'xchan_hash' => $hash,
+ 'xchan_name' => $anon_name,
+ 'xchan_url' => $anon_url,
+ 'xchan_network' => 'unknown',
+ 'xchan_name_date' => datetime_convert()
+ ]);
+
+
+ $x = q("select * from xchan where xchan_guid = '%s' and xchan_hash = '%s' and xchan_network = 'unknown' limit 1",
+ dbesc($anon_email),
+ dbesc($hash)
+ );
+
+ $photo = z_root() . '/' . get_default_profile_photo(300);
+ $photos = import_xchan_photo($photo,$hash);
+ $r = q("update xchan set xchan_photo_date = '%s', xchan_photo_l = '%s', xchan_photo_m = '%s', xchan_photo_s = '%s', xchan_photo_mimetype = '%s' where xchan_guid = '%s' and xchan_hash = '%s' and xchan_network = 'unknown' ",
+ dbesc(datetime_convert()),
+ dbesc($photos[0]),
+ dbesc($photos[1]),
+ dbesc($photos[2]),
+ dbesc($photos[3]),
+ dbesc($anon_email),
+ dbesc($hash)
+ );
+
+ }
+
+ return $x[0];
+}
+
+
+function pchan_to_chan($pchan) {
+ $chan = $pchan;
+ $chan['channel_address'] = $pchan['pchan_guid'];
+ $chan['channel_hash'] = $pchan['pchan_hash'];
+ $chan['channel_pubkey'] = $pchan['pchan_pubkey'];
+ $chan['channel_prvkey'] = $pchan['pchan_prvkey'];
+ $chan['channel_name'] = $pchan['xchan_name'];
+ return $chan;
} \ No newline at end of file
diff --git a/include/config.php b/include/config.php
index 0b0e639ab..0be791715 100644
--- a/include/config.php
+++ b/include/config.php
@@ -126,3 +126,19 @@ function set_iconfig(&$item, $family, $key, $value, $sharing = false) {
function del_iconfig(&$item, $family, $key) {
return Zlib\IConfig::Delete($item, $family, $key);
}
+
+function load_sconfig($server_id) {
+ Zlib\SConfig::Load($server_id);
+}
+
+function get_sconfig($server_id, $family, $key, $default = false) {
+ return Zlib\SConfig::Get($server_id, $family, $key, $default);
+}
+
+function set_sconfig($server_id, $family, $key, $value) {
+ return Zlib\SConfig::Set($server_id, $family, $key, $value);
+}
+
+function del_sconfig($server_id, $family, $key) {
+ return Zlib\SConfig::Delete($server_id, $family, $key);
+}
diff --git a/include/connections.php b/include/connections.php
index e26943b68..60bce018e 100644
--- a/include/connections.php
+++ b/include/connections.php
@@ -23,6 +23,7 @@ function abook_store_lowlevel($arr) {
'abook_unconnected' => ((array_key_exists('abook_unconnected',$arr)) ? $arr['abook_unconnected'] : 0),
'abook_self' => ((array_key_exists('abook_self',$arr)) ? $arr['abook_self'] : 0),
'abook_feed' => ((array_key_exists('abook_feed',$arr)) ? $arr['abook_feed'] : 0),
+ 'abook_not_here' => ((array_key_exists('abook_not_here',$arr)) ? $arr['abook_not_here'] : 0),
'abook_profile' => ((array_key_exists('abook_profile',$arr)) ? $arr['abook_profile'] : ''),
'abook_incl' => ((array_key_exists('abook_incl',$arr)) ? $arr['abook_incl'] : ''),
'abook_excl' => ((array_key_exists('abook_excl',$arr)) ? $arr['abook_excl'] : ''),
@@ -114,7 +115,7 @@ function vcard_from_xchan($xchan, $observer = null, $mode = '') {
App::$profile_uid = $xchan['channel_id'];
$url = (($observer)
- ? z_root() . '/magic?f=&dest=' . $xchan['xchan_url'] . '&addr=' . $xchan['xchan_addr']
+ ? z_root() . '/magic?f=&owa=1&dest=' . $xchan['xchan_url'] . '&addr=' . $xchan['xchan_addr']
: $xchan['xchan_url']
);
@@ -188,232 +189,6 @@ function abook_toggle_flag($abook,$flag) {
}
-// Included here for completeness, but this is a very dangerous operation.
-// It is the caller's responsibility to confirm the requestor's intent and
-// authorisation to do this.
-
-function user_remove($uid) {
-
-}
-
-function account_remove($account_id,$local = true,$unset_session=true) {
-
- logger('account_remove: ' . $account_id);
-
- if(! intval($account_id)) {
- logger('account_remove: no account.');
- return false;
- }
-
- // Don't let anybody nuke the only admin account.
-
- $r = q("select account_id from account where (account_roles & %d) > 0",
- intval(ACCOUNT_ROLE_ADMIN)
- );
-
- if($r !== false && count($r) == 1 && $r[0]['account_id'] == $account_id) {
- logger("Unable to remove the only remaining admin account");
- return false;
- }
-
- $r = q("select * from account where account_id = %d limit 1",
- intval($account_id)
- );
- $account_email=$r[0]['account_email'];
-
- if(! $r) {
- logger('account_remove: No account with id: ' . $account_id);
- return false;
- }
-
- $x = q("select channel_id from channel where channel_account_id = %d",
- intval($account_id)
- );
- if($x) {
- foreach($x as $xx) {
- channel_remove($xx['channel_id'],$local,false);
- }
- }
-
- $r = q("delete from account where account_id = %d",
- intval($account_id)
- );
-
-
- if ($unset_session) {
- unset($_SESSION['authenticated']);
- unset($_SESSION['uid']);
- notice( sprintf(t("User '%s' deleted"),$account_email) . EOL);
- goaway(z_root());
- }
- return $r;
-
-}
-// recursively delete a directory
-function rrmdir($path)
-{
- if (is_dir($path) === true)
- {
- $files = array_diff(scandir($path), array('.', '..'));
-
- foreach ($files as $file)
- {
- rrmdir(realpath($path) . '/' . $file);
- }
-
- return rmdir($path);
- }
-
- else if (is_file($path) === true)
- {
- return unlink($path);
- }
-
- return false;
-}
-
-function channel_remove($channel_id, $local = true, $unset_session=false) {
-
- if(! $channel_id)
- return;
-
- logger('Removing channel: ' . $channel_id);
- logger('channel_remove: local only: ' . intval($local));
-
- $r = q("select * from channel where channel_id = %d limit 1", intval($channel_id));
- if(! $r) {
- logger('channel_remove: channel not found: ' . $channel_id);
- return;
- }
-
- $channel = $r[0];
-
- call_hooks('channel_remove',$r[0]);
-
- if(! $local) {
-
- $r = q("update channel set channel_deleted = '%s', channel_removed = 1 where channel_id = %d",
- dbesc(datetime_convert()),
- intval($channel_id)
- );
-
- q("delete from pconfig where uid = %d",
- intval($channel_id)
- );
-
- logger('deleting hublocs',LOGGER_DEBUG);
-
- $r = q("update hubloc set hubloc_deleted = 1 where hubloc_hash = '%s'",
- dbesc($channel['channel_hash'])
- );
-
-
- $r = q("update xchan set xchan_deleted = 1 where xchan_hash = '%s'",
- dbesc($channel['channel_hash'])
- );
-
- Zotlabs\Daemon\Master::Summon(array('Notifier','purge_all',$channel_id));
- }
-
-
- $r = q("select * from iconfig left join item on item.id = iconfig.iid
- where item.uid = %d",
- intval($channel_id)
- );
- if($r) {
- foreach($r as $rr) {
- q("delete from iconfig where iid = %d",
- intval($rr['iid'])
- );
- }
- }
-
-
- q("DELETE FROM groups WHERE uid = %d", intval($channel_id));
- q("DELETE FROM group_member WHERE uid = %d", intval($channel_id));
- q("DELETE FROM event WHERE uid = %d", intval($channel_id));
- q("DELETE FROM item WHERE uid = %d", intval($channel_id));
- q("DELETE FROM mail WHERE channel_id = %d", intval($channel_id));
- q("DELETE FROM notify WHERE uid = %d", intval($channel_id));
- q("DELETE FROM photo WHERE uid = %d", intval($channel_id));
- q("DELETE FROM attach WHERE uid = %d", intval($channel_id));
- q("DELETE FROM profile WHERE uid = %d", intval($channel_id));
- q("DELETE FROM pconfig WHERE uid = %d", intval($channel_id));
-
- // @FIXME At this stage we need to remove the file resources located under /store/$nickname
-
-
- q("delete from abook where abook_xchan = '%s' and abook_self = 1 ",
- dbesc($channel['channel_hash'])
- );
-
- $r = q("update channel set channel_deleted = '%s', channel_removed = 1 where channel_id = %d",
- dbesc(datetime_convert()),
- intval($channel_id)
- );
-
- // if this was the default channel, set another one as default
- if(App::$account['account_default_channel'] == $channel_id) {
- $r = q("select channel_id from channel where channel_account_id = %d and channel_removed = 0 limit 1",
- intval(App::$account['account_id']),
- intval(PAGE_REMOVED));
- if ($r) {
- $rr = q("update account set account_default_channel = %d where account_id = %d",
- intval($r[0]['channel_id']),
- intval(App::$account['account_id']));
- logger("Default channel deleted, changing default to channel_id " . $r[0]['channel_id']);
- }
- else {
- $rr = q("update account set account_default_channel = 0 where account_id = %d",
- intval(App::$account['account_id'])
- );
- }
- }
-
- logger('deleting hublocs',LOGGER_DEBUG);
-
- $r = q("update hubloc set hubloc_deleted = 1 where hubloc_hash = '%s' and hubloc_url = '%s' ",
- dbesc($channel['channel_hash']),
- dbesc(z_root())
- );
-
- // Do we have any valid hublocs remaining?
-
- $hublocs = 0;
-
- $r = q("select hubloc_id from hubloc where hubloc_hash = '%s' and hubloc_deleted = 0",
- dbesc($channel['channel_hash'])
- );
- if($r)
- $hublocs = count($r);
-
- if(! $hublocs) {
- $r = q("update xchan set xchan_deleted = 1 where xchan_hash = '%s' ",
- dbesc($channel['channel_hash'])
- );
- }
-
- //remove from file system
- $r = q("select channel_address from channel where channel_id = %d limit 1",
- intval($channel_id)
- );
- if($r)
- $channel_address = $r[0]['channel_address'] ;
- if ($channel_address !== '') {
- $f = 'store/' . $channel_address.'/';
- logger ('delete '. $f);
- if(is_dir($f))
- @rrmdir($f);
- }
-
- Zotlabs\Daemon\Master::Summon(array('Directory',$channel_id));
-
- if($channel_id == local_channel() && $unset_session) {
- App::$session->nuke();
- goaway(z_root());
- }
-
-}
/**
* mark any hubs "offline" that haven't been heard from in more than 30 days
@@ -430,10 +205,10 @@ function mark_orphan_hubsxchans() {
if($dirmode == DIRECTORY_MODE_NORMAL)
return;
- $r = q("update hubloc set hubloc_error = 1 where hubloc_error = 0
+ $r = q("update hubloc set hubloc_error = 1 where hubloc_error = 0
and hubloc_network = 'zot' and hubloc_connected < %s - interval %s",
- db_utcnow(), db_quoteinterval('36 day')
- );
+ db_utcnow(), db_quoteinterval('36 day')
+ );
// $realm = get_directory_realm();
// if($realm == DIRECTORY_REALM) {
@@ -547,13 +322,13 @@ function remove_all_xchan_resources($xchan, $channel_id = 0) {
// directory servers need to keep the record around for sync purposes - mark it deleted
- $r = q("update hubloc set hubloc_deleted = 1 where hubloc_hash = '%s'",
- dbesc($xchan)
- );
+ $r = q("update hubloc set hubloc_deleted = 1 where hubloc_hash = '%s'",
+ dbesc($xchan)
+ );
- $r = q("update xchan set xchan_deleted = 1 where xchan_hash = '%s'",
- dbesc($xchan)
- );
+ $r = q("update xchan set xchan_deleted = 1 where xchan_hash = '%s'",
+ dbesc($xchan)
+ );
}
}
}
@@ -566,6 +341,11 @@ function contact_remove($channel_id, $abook_id) {
logger('removing contact ' . $abook_id . ' for channel ' . $channel_id,LOGGER_DEBUG);
+
+ $x = [ 'channel_id' => $channel_id, 'abook_id' => $abook_id ];
+ call_hooks('connection_remove',$x);
+
+
$archive = get_pconfig($channel_id, 'system','archive_removed_contacts');
if($archive) {
q("update abook set abook_archived = 1 where abook_id = %d and abook_channel = %d",
@@ -589,7 +369,8 @@ function contact_remove($channel_id, $abook_id) {
return false;
- $r = q("select * from item where author_xchan = '%s' and uid = %d",
+ $r = q("select * from item where (owner_xchan = '%s' or author_xchan = '%s') and uid = %d",
+ dbesc($abook['abook_xchan']),
dbesc($abook['abook_xchan']),
intval($channel_id)
);
@@ -640,9 +421,9 @@ function random_profile() {
for($i = 0; $i < $retryrandom; $i++) {
- $r = q("select xchan_url from xchan left join hubloc on hubloc_hash = xchan_hash where xchan_addr not like '%s' and xchan_hidden = 0 and hubloc_connected > %s - interval %s order by $randfunc limit 1",
- dbesc('sys@%'),
- db_utcnow(), db_quoteinterval('30 day')
+ $r = q("select xchan_url, xchan_hash from xchan left join hubloc on hubloc_hash = xchan_hash where xchan_hidden = 0 and xchan_system = 0 and hubloc_connected > %s - interval %s order by $randfunc limit 1",
+ db_utcnow(),
+ db_quoteinterval('30 day')
);
if(!$r) return ''; // Couldn't get a random channel
@@ -650,12 +431,12 @@ function random_profile() {
if($checkrandom) {
$x = z_fetch_url($r[0]['xchan_url']);
if($x['success'])
- return $r[0]['xchan_url'];
+ return $r[0]['xchan_hash'];
else
logger('Random channel turned out to be bad.');
}
else {
- return $r[0]['xchan_url'];
+ return $r[0]['xchan_hash'];
}
}
@@ -849,13 +630,20 @@ function get_vcard_array($vc,$id) {
if($vc->ADR) {
foreach($vc->ADR as $adr) {
$type = (($adr['TYPE']) ? vcard_translate_type((string)$adr['TYPE']) : '');
- $adrs[] = [
+ $entry = [
'type' => $type,
'address' => $adr->getParts()
];
- $last_entry = end($adrs);
- if($adrs[$last_entry]['address'])
- array_walk($adrs[$last_entry]['address'],'array_escape_tags');
+
+ if(is_array($entry['address'])) {
+ array_walk($entry['address'],'array_escape_tags');
+ }
+ else {
+ $entry['address'] = (string) escape_tags($entry['address']);
+ }
+
+ $adrs[] = $entry;
+
}
}
@@ -937,4 +725,4 @@ function vcard_query(&$r) {
}
}
}
-} \ No newline at end of file
+}
diff --git a/include/contact_widgets.php b/include/contact_widgets.php
index 8f76bb4bc..9cc9f0baf 100644
--- a/include/contact_widgets.php
+++ b/include/contact_widgets.php
@@ -65,6 +65,10 @@ function categories_widget($baseurl,$selected = '') {
if(! feature_enabled(App::$profile['profile_uid'],'categories'))
return '';
+ require_once('include/security.php');
+
+ $sql_extra = item_permissions_sql(App::$profile['profile_uid']);
+
$item_normal = item_normal();
$terms = array();
@@ -77,6 +81,7 @@ function categories_widget($baseurl,$selected = '') {
and item.owner_xchan = '%s'
and item.item_wall = 1
$item_normal
+ $sql_extra
order by term.term asc",
intval(App::$profile['profile_uid']),
intval(TERM_CATEGORY),
@@ -100,7 +105,53 @@ function categories_widget($baseurl,$selected = '') {
return '';
}
-function common_friends_visitor_widget($profile_uid) {
+function cardcategories_widget($baseurl,$selected = '') {
+
+ if(! feature_enabled(App::$profile['profile_uid'],'categories'))
+ return '';
+
+ $sql_extra = item_permissions_sql(App::$profile['profile_uid']);
+
+ $item_normal = "and item.item_hidden = 0 and item.item_type = 6 and item.item_deleted = 0
+ and item.item_unpublished = 0 and item.item_delayed = 0 and item.item_pending_remove = 0
+ and item.item_blocked = 0 ";
+
+ $terms = array();
+ $r = q("select distinct(term.term)
+ from term join item on term.oid = item.id
+ where item.uid = %d
+ and term.uid = item.uid
+ and term.ttype = %d
+ and term.otype = %d
+ and item.owner_xchan = '%s'
+ $item_normal
+ $sql_extra
+ order by term.term asc",
+ intval(App::$profile['profile_uid']),
+ intval(TERM_CATEGORY),
+ intval(TERM_OBJ_POST),
+ dbesc(App::$profile['channel_hash'])
+ );
+ if($r && count($r)) {
+ foreach($r as $rr)
+ $terms[] = array('name' => $rr['term'], 'selected' => (($selected == $rr['term']) ? 'selected' : ''));
+
+ return replace_macros(get_markup_template('categories_widget.tpl'),array(
+ '$title' => t('Categories'),
+ '$desc' => '',
+ '$sel_all' => (($selected == '') ? 'selected' : ''),
+ '$all' => t('Everything'),
+ '$terms' => $terms,
+ '$base' => $baseurl,
+
+ ));
+ }
+ return '';
+}
+
+
+
+function common_friends_visitor_widget($profile_uid,$cnt = 25) {
if(local_channel() == $profile_uid)
return;
@@ -113,19 +164,20 @@ function common_friends_visitor_widget($profile_uid) {
require_once('include/socgraph.php');
$t = count_common_friends($profile_uid,$observer_hash);
+
if(! $t)
return;
- $r = common_friends($profile_uid,$observer_hash,0,5,true);
-
+ $r = common_friends($profile_uid,$observer_hash,0,$cnt,true);
+
return replace_macros(get_markup_template('remote_friends_common.tpl'), array(
- '$desc' => sprintf( tt("%d connection in common", "%d connections in common", $t), $t),
- '$base' => z_root(),
- '$uid' => $profile_uid,
- '$cid' => $observer,
- '$linkmore' => (($t > 5) ? 'true' : ''),
- '$more' => t('show more'),
- '$items' => $r
+ '$desc' => t('Common Connections'),
+ '$base' => z_root(),
+ '$uid' => $profile_uid,
+ '$cid' => $observer,
+ '$linkmore' => (($t > $cnt) ? 'true' : ''),
+ '$more' => sprintf( t('View all %d common connections'), $t),
+ '$items' => $r
));
};
diff --git a/include/conversation.php b/include/conversation.php
index 285ee752f..f395b2cbe 100644
--- a/include/conversation.php
+++ b/include/conversation.php
@@ -2,10 +2,6 @@
require_once('include/items.php');
-// Note: the code in 'item_extract_images' and 'item_redir_and_replace_images'
-// is identical to the code in mod/message.php for 'item_extract_images' and
-// 'item_redir_and_replace_images'
-
function item_extract_images($body) {
@@ -299,7 +295,7 @@ function localize_item(&$item){
}
$plink = '[zrl=' . $obj['plink'] . ']' . $post_type . '[/zrl]';
- $parsedobj = parse_xml_string($xmlhead.$item['obj']);
+// $parsedobj = parse_xml_string($xmlhead.$item['obj']);
$tag = sprintf('#[zrl=%s]%s[/zrl]', $parsedobj->id, $parsedobj->content);
$item['body'] = sprintf( t('%1$s tagged %2$s\'s %3$s with %4$s'), $author, $objauthor, $plink, $tag );
@@ -316,7 +312,7 @@ function localize_item(&$item){
$xmlhead="<"."?xml version='1.0' encoding='UTF-8' ?".">";
- $obj = parse_xml_string($xmlhead.$item['obj']);
+// $obj = parse_xml_string($xmlhead.$item['obj']);
if(strlen($obj->id)) {
$r = q("select * from item where mid = '%s' and uid = %d limit 1",
dbesc($obj->id),
@@ -357,14 +353,6 @@ function localize_item(&$item){
}
*/
- // if item body was obscured and we changed it, re-obscure it
- // FIXME - we need a better filter than just the string 'data'; try and
- // match the fact that it's json encoded
-
- if(intval($item['item_obscured'])
- && strlen($item['body']) && (! strpos($item['body'],'data'))) {
- $item['body'] = z_obscure($item['body']);
- }
}
@@ -375,13 +363,14 @@ function localize_item(&$item){
* * \e array \b children
* @return number
*/
+
function count_descendants($item) {
$total = count($item['children']);
- if ($total > 0) {
- foreach ($item['children'] as $child) {
- if (! visible_activity($child))
+ if($total > 0) {
+ foreach($item['children'] as $child) {
+ if(! visible_activity($child))
$total --;
$total += count_descendants($child);
@@ -408,8 +397,8 @@ function visible_activity($item) {
if(intval($item['item_notshown']))
return false;
- foreach ($hidden_activities as $act) {
- if ((activity_match($item['verb'], $act)) && ($item['mid'] != $item['parent_mid'])) {
+ foreach($hidden_activities as $act) {
+ if((activity_match($item['verb'], $act)) && ($item['mid'] != $item['parent_mid'])) {
return false;
}
}
@@ -453,7 +442,6 @@ function is_edit_activity($item) {
* figures out how to determine page owner and other contextual items
* that are based on unique features of the calling module.
*
- * @param App &$a
* @param array $items
* @param string $mode
* @param boolean $update
@@ -461,7 +449,7 @@ function is_edit_activity($item) {
* @param string $prepared_item
* @return string
*/
-function conversation(&$a, $items, $mode, $update, $page_mode = 'traditional', $prepared_item = '') {
+function conversation($items, $mode, $update, $page_mode = 'traditional', $prepared_item = '') {
$content_html = '';
$o = '';
@@ -476,9 +464,11 @@ function conversation(&$a, $items, $mode, $update, $page_mode = 'traditional', $
$profile_owner = 0;
$page_writeable = false;
$live_update_div = '';
+ $jsreload = '';
$preview = (($page_mode === 'preview') ? true : false);
$previewing = (($preview) ? ' preview ' : '');
+ $preview_lbl = t('This is an unsaved preview');
if ($mode === 'network') {
@@ -528,6 +518,16 @@ function conversation(&$a, $items, $mode, $update, $page_mode = 'traditional', $
}
}
+ elseif ($mode === 'cards') {
+ $profile_owner = App::$profile['profile_uid'];
+ $page_writeable = ($profile_owner == local_channel());
+ $live_update_div = '<div id="live-cards"></div>' . "\r\n"
+ . "<script> var profile_uid = " . App::$profile['profile_uid']
+ . "; var netargs = '?f='; var profile_page = " . App::$pager['page'] . "; </script>\r\n";
+ $jsreload = $_SESSION['return_url'];
+ }
+
+
elseif ($mode === 'display') {
$profile_owner = local_channel();
$page_writeable = false;
@@ -544,8 +544,12 @@ function conversation(&$a, $items, $mode, $update, $page_mode = 'traditional', $
$live_update_div = '<div id="live-search"></div>' . "\r\n";
}
+ elseif ($mode === 'moderate') {
+ $profile_owner = local_channel();
+ }
+
elseif ($mode === 'photos') {
- $profile_onwer = App::$profile['profile_uid'];
+ $profile_owner = App::$profile['profile_uid'];
$page_writeable = ($profile_owner == local_channel());
$live_update_div = '<div id="live-photos"></div>' . "\r\n";
// for photos we've already formatted the top-level item (the photo)
@@ -557,6 +561,19 @@ function conversation(&$a, $items, $mode, $update, $page_mode = 'traditional', $
if (! feature_enabled($profile_owner,'multi_delete'))
$page_dropping = false;
+ $uploading = true;
+
+ if($profile_owner > 0) {
+ $owner_channel = channelx_by_n($profile_owner);
+ if($owner_channel['channel_allow_cid'] || $owner_channel['channel_allow_gid']
+ || $owner_channel['channel_deny_cid'] || $owner_channel['channel_deny_gid']) {
+ $uploading = false;
+ }
+ }
+ else {
+ $uploading = false;
+ }
+
$channel = App::get_channel();
$observer = App::get_observer();
@@ -588,7 +605,7 @@ function conversation(&$a, $items, $mode, $update, $page_mode = 'traditional', $
if($items) {
- if($mode === 'network-new' || $mode === 'search' || $mode === 'community') {
+ if(in_array($mode, [ 'network-new', 'search', 'community', 'moderate' ])) {
// "New Item View" on network page or search page results
// - just loop through the items and format them minimally for display
@@ -614,19 +631,20 @@ function conversation(&$a, $items, $mode, $update, $page_mode = 'traditional', $
$owner_photo = '';
$owner_name = '';
$sparkle = '';
+ $is_new = false;
if($mode === 'search' || $mode === 'community') {
if(((activity_match($item['verb'],ACTIVITY_LIKE)) || (activity_match($item['verb'],ACTIVITY_DISLIKE)))
&& ($item['id'] != $item['parent']))
continue;
- $nickname = $item['nickname'];
+// $nickname = $item['nickname'];
}
- else
- $nickname = App::$user['nickname'];
+// else
+// $nickname = App::$user['nickname'];
- $profile_name = ((strlen($item['author-name'])) ? $item['author-name'] : $item['name']);
- if($item['author-link'] && (! $item['author-name']))
- $profile_name = $item['author-link'];
+// $profile_name = ((strlen($item['author-name'])) ? $item['author-name'] : $item['name']);
+// if($item['author-link'] && (! $item['author-name']))
+// $profile_name = $item['author-link'];
$sp = false;
$profile_link = best_link_url($item,$sp);
@@ -635,7 +653,7 @@ function conversation(&$a, $items, $mode, $update, $page_mode = 'traditional', $
else
$profile_link = zid($profile_link);
- $normalised = normalise_link((strlen($item['author-link'])) ? $item['author-link'] : $item['url']);
+// $normalised = normalise_link((strlen($item['author-link'])) ? $item['author-link'] : $item['url']);
$profile_name = $item['author']['xchan_name'];
$profile_link = $item['author']['xchan_url'];
@@ -682,10 +700,22 @@ function conversation(&$a, $items, $mode, $update, $page_mode = 'traditional', $
$has_tags = (($body['tags'] || $body['categories'] || $body['mentions'] || $body['attachments'] || $body['folders']) ? true : false);
+ if(strcmp(datetime_convert('UTC','UTC',$item['created']),datetime_convert('UTC','UTC','now - 12 hours')) > 0)
+ $is_new = true;
+
+ $conv_link_mid = (($mode == 'moderate') ? $item['parent_mid'] : $item['mid']);
+
+ $conv_link = (($item['item_type'] == ITEM_TYPE_CARD) ? $item['plink'] : z_root() . '/display/' . gen_link_id($conv_link_mid));
+
+
$tmp_item = array(
'template' => $tpl,
'toplevel' => 'toplevel_item',
+ 'item_type' => intval($item['item_type']),
'mode' => $mode,
+ 'approve' => t('Approve'),
+ 'delete' => t('Delete'),
+ 'preview_lbl' => $preview_lbl,
'id' => (($preview) ? 'P0' : $item['item_id']),
'linktitle' => sprintf( t('View %s\'s profile @ %s'), $profile_name, $profile_url),
'profile_url' => $profile_link,
@@ -733,11 +763,12 @@ function conversation(&$a, $items, $mode, $update, $page_mode = 'traditional', $
'like' => '',
'dislike' => '',
'comment' => '',
- 'conv' => (($preview) ? '' : array('href'=> z_root() . '/display/' . gen_link_id($item['mid']), 'title'=> t('View in context'))),
+ 'conv' => (($preview) ? '' : array('href'=> $conv_link, 'title'=> t('View in context'))),
'previewing' => $previewing,
'wait' => t('Please wait'),
'thread_level' => 1,
'has_tags' => $has_tags,
+ 'is_new' => $is_new
);
$arr = array('item' => $item, 'output' => $tmp_item);
@@ -752,7 +783,7 @@ function conversation(&$a, $items, $mode, $update, $page_mode = 'traditional', $
// Normal View
// logger('conv: items: ' . print_r($items,true));
- $conv = new Zotlabs\Lib\ThreadStream($mode, $preview, $prepared_item);
+ $conv = new Zotlabs\Lib\ThreadStream($mode, $preview, $uploading, $prepared_item);
// In the display mode we don't have a profile owner.
@@ -794,6 +825,10 @@ function conversation(&$a, $items, $mode, $update, $page_mode = 'traditional', $
$item_object->set_template('conv_list.tpl');
$item_object->set_display_mode('list');
}
+ if($page_mode === 'cards') {
+ $item_object->set_reload($jsreload);
+ }
+
}
}
@@ -870,98 +905,6 @@ function best_link_url($item) {
-function item_photo_menu($item){
-
- $contact = null;
-
- $ssl_state = false;
-
- $sub_link="";
- $poke_link="";
- $contact_url="";
- $pm_url="";
- $vsrc_link = "";
- $follow_url = "";
-
- $local_channel = local_channel();
-
- if($local_channel) {
- $ssl_state = true;
- if(! count(App::$contacts))
- load_contact_links($local_channel);
- $channel = App::get_channel();
- $channel_hash = (($channel) ? $channel['channel_hash'] : '');
- }
-
- if(($local_channel) && $local_channel == $item['uid']) {
- $vsrc_link = 'javascript:viewsrc(' . $item['id'] . '); return false;';
- if($item['parent'] == $item['id'] && $channel && ($channel_hash != $item['author_xchan'])) {
- $sub_link = 'javascript:dosubthread(' . $item['id'] . '); return false;';
- }
- if($channel) {
- $unsub_link = 'javascript:dounsubthread(' . $item['id'] . '); return false;';
- }
- }
-
- $profile_link = chanlink_hash($item['author_xchan']);
- if($item['uid'] > 0)
- $pm_url = z_root() . '/mail/new/?f=&hash=' . $item['author_xchan'];
-
- if(App::$contacts && array_key_exists($item['author_xchan'],App::$contacts))
- $contact = App::$contacts[$item['author_xchan']];
- else
- if($local_channel && $item['author']['xchan_addr'])
- $follow_url = z_root() . '/follow/?f=&url=' . $item['author']['xchan_addr'];
-
- if($contact) {
- $poke_link = z_root() . '/poke/?f=&c=' . $contact['abook_id'];
- if (! intval($contact['abook_self']))
- $contact_url = z_root() . '/connedit/' . $contact['abook_id'];
- $posts_link = z_root() . '/network/?cid=' . $contact['abook_id'];
-
- $clean_url = normalise_link($item['author-link']);
- }
-
- $rating_enabled = get_config('system','rating_enabled');
-
- $ratings_url = (($rating_enabled) ? z_root() . '/ratings/' . urlencode($item['author_xchan']) : '');
-
- $post_menu = Array(
- t("View Source") => $vsrc_link,
- t("Follow Thread") => $sub_link,
- t("Unfollow Thread") => $unsub_link,
- );
-
- $author_menu = array(
- t("View Profile") => $profile_link,
- t("Activity/Posts") => $posts_link,
- t("Connect") => $follow_url,
- t("Edit Connection") => $contact_url,
- t("Message") => $pm_url,
- t('Ratings') => $ratings_url,
- t("Poke") => $poke_link
- );
-
-
- $args = array('item' => $item, 'post_menu' => $post_menu, 'author_menu' => $author_menu);
-
- call_hooks('item_photo_menu', $args);
-
- $menu = array_merge($args['post_menu'],$args['author_menu']);
-
- $o = "";
- foreach($menu as $k=>$v){
- if(strpos($v,'javascript:') === 0) {
- $v = substr($v,11);
- $o .= "<li><a href=\"#\" onclick=\"$v\">$k</a></li>\n";
- }
- elseif ($v!="") $o .= "<li><a href=\"$v\">$k</a></li>\n";
- }
-
- return $o;
-}
-
-
function thread_action_menu($item,$mode = '') {
$menu = [];
@@ -1007,6 +950,24 @@ function thread_action_menu($item,$mode = '') {
}
+function author_is_pmable($xchan, $abook) {
+
+ $x = [ 'xchan' => $xchan, 'abook' => $abook, 'result' => 'unset' ];
+ call_hooks('author_is_pmable',$x);
+ if($x['result'] !== 'unset')
+ return $x['result'];
+
+ if($xchan['xchan_network'] === 'zot')
+ return true;
+ return false;
+
+}
+
+
+
+
+
+
function thread_author_menu($item, $mode = '') {
$menu = [];
@@ -1021,14 +982,19 @@ function thread_author_menu($item, $mode = '') {
}
$profile_link = chanlink_hash($item['author_xchan']);
- if($item['uid'] > 0)
- $pm_url = z_root() . '/mail/new/?f=&hash=' . $item['author_xchan'];
+ $contact = false;
if(App::$contacts && array_key_exists($item['author_xchan'],App::$contacts))
$contact = App::$contacts[$item['author_xchan']];
else
if($local_channel && $item['author']['xchan_addr'])
- $follow_url = z_root() . '/follow/?f=&url=' . $item['author']['xchan_addr'];
+ $follow_url = z_root() . '/follow/?f=&url=' . urlencode($item['author']['xchan_addr']);
+
+
+ if($item['uid'] > 0 && author_is_pmable($item['author'],$contact)) {
+ $pm_url = z_root() . '/mail/new/?f=&hash=' . urlencode($item['author_xchan']);
+ }
+
if($contact) {
$poke_link = z_root() . '/poke/?f=&c=' . $contact['abook_id'];
@@ -1175,9 +1141,9 @@ function builtin_activity_puller($item, &$conv_responses) {
if((activity_match($item['verb'], $verb)) && ($item['id'] != $item['parent'])) {
$name = (($item['author']['xchan_name']) ? $item['author']['xchan_name'] : t('Unknown'));
- $url = (($item['author']['xchan_url'] && $item['author']['xchan_photo_s'])
- ? '<a href="' . chanlink_url($item['author']['xchan_url']) . '">' . '<img class="dropdown-menu-img-xs" src="' . zid($item['author']['xchan_photo_s']) . '" alt="' . urlencode($name) . '" />' . $name . '</a>'
- : '<a href="#" class="disabled">' . $name . '</a>'
+ $url = (($item['author_xchan'] && $item['author']['xchan_photo_s'])
+ ? '<a class="dropdown-item" href="' . chanlink_hash($item['author_xchan']) . '">' . '<img class="menu-img-1" src="' . zid($item['author']['xchan_photo_s']) . '" alt="' . urlencode($name) . '" />' . $name . '</a>'
+ : '<a class="dropdown-item" href="#" class="disabled">' . $name . '</a>'
);
if(! $item['thr_parent'])
@@ -1360,6 +1326,11 @@ function status_editor($a, $x, $popup = false) {
if(! $cipher)
$cipher = 'aes256';
+ if(array_key_exists('catsenabled',$x))
+ $catsenabled = $x['catsenabled'];
+ else
+ $catsenabled = ((feature_enabled($x['profile_uid'], 'categories') && (! $webpage)) ? 'categories' : '');
+
// avoid illegal offset errors
if(! array_key_exists('permissions',$x))
$x['permissions'] = [ 'allow_cid' => '', 'allow_gid' => '', 'deny_cid' => '', 'deny_gid' => '' ];
@@ -1372,10 +1343,14 @@ function status_editor($a, $x, $popup = false) {
call_hooks('jot_networks', $jotnets);
}
+ $sharebutton = (x($x,'button') ? $x['button'] : t('Share'));
+ $placeholdtext = (x($x,'content_label') ? $x['content_label'] : $sharebutton);
+
$o .= replace_macros($tpl, array(
'$return_path' => ((x($x, 'return_path')) ? $x['return_path'] : App::$query_string),
'$action' => z_root() . '/item',
- '$share' => (x($x,'button') ? $x['button'] : t('Share')),
+ '$share' => $sharebutton,
+ '$placeholdtext' => $placeholdtext,
'$webpage' => $webpage,
'$placeholdpagetitle' => ((x($x,'ptlabel')) ? $x['ptlabel'] : t('Page link name')),
'$pagetitle' => (x($x,'pagetitle') ? $x['pagetitle'] : ''),
@@ -1404,7 +1379,7 @@ function status_editor($a, $x, $popup = false) {
'$clearloc' => $clearloc,
'$title' => ((x($x, 'title')) ? htmlspecialchars($x['title'], ENT_COMPAT,'UTF-8') : ''),
'$placeholdertitle' => ((x($x, 'placeholdertitle')) ? $x['placeholdertitle'] : t('Title (optional)')),
- '$catsenabled' => ((feature_enabled($x['profile_uid'], 'categories') && (! $webpage)) ? 'categories' : ''),
+ '$catsenabled' => $catsenabled,
'$category' => ((x($x, 'category')) ? $x['category'] : ''),
'$placeholdercategory' => t('Categories (optional, comma-separated list)'),
'$permset' => t('Permission settings'),
@@ -1511,6 +1486,8 @@ function conv_sort($arr, $order) {
usort($parents,'sort_thr_created');
elseif(stristr($order,'commented'))
usort($parents,'sort_thr_commented');
+ elseif(stristr($order,'updated'))
+ usort($parents,'sort_thr_updated');
elseif(stristr($order,'ascending'))
usort($parents,'sort_thr_created_rev');
@@ -1552,6 +1529,12 @@ function sort_thr_commented($a,$b) {
return strcmp($b['commented'],$a['commented']);
}
+function sort_thr_updated($a,$b) {
+ $indexa = (($a['changed'] > $a['edited']) ? $a['changed'] : $a['edited']);
+ $indexb = (($b['changed'] > $b['edited']) ? $b['changed'] : $b['edited']);
+ return strcmp($indexb,$indexa);
+}
+
function find_thread_parent_index($arr,$x) {
foreach($arr as $k => $v)
if($v['id'] == $x['parent'])
@@ -1608,6 +1591,15 @@ function prepare_page($item) {
// the template will get passed an unobscured title.
$body = prepare_body($item, true);
+ if(App::$page['template'] == 'none') {
+ $tpl = 'page_display_empty.tpl';
+
+ return replace_macros(get_markup_template($tpl), array(
+ '$body' => $body['html']
+ ));
+
+ }
+
$tpl = get_pconfig($item['uid'], 'system', 'pagetemplate');
if (! $tpl)
$tpl = 'page_display.tpl';
@@ -1634,7 +1626,6 @@ function network_tabs() {
$conv_active = '';
$spam_active = '';
$postord_active = '';
- $public_active = '';
if(x($_GET,'new')) {
$new_active = 'active';
@@ -1656,16 +1647,11 @@ function network_tabs() {
$spam_active = 'active';
}
- if(x($_GET,'fh')) {
- $public_active = 'active';
- }
-
if (($new_active == '')
&& ($starred_active == '')
&& ($conv_active == '')
&& ($search_active == '')
- && ($spam_active == '')
- && ($public_active == '')) {
+ && ($spam_active == '')) {
$no_active = 'active';
}
@@ -1683,19 +1669,6 @@ function network_tabs() {
// tabs
$tabs = array();
- $d = get_config('system','disable_discover_tab');
- if($d === false)
- $d = 1;
-
- if(! $d) {
- $tabs[] = array(
- 'label' => t('Discover'),
- 'url' => z_root() . '/' . $cmd . '?f=&fh=1' ,
- 'sel' => $public_active,
- 'title' => t('Imported public streams'),
- );
- }
-
$tabs[] = array(
'label' => t('Commented Order'),
'url'=>z_root() . '/' . $cmd . '?f=&order=comment' . ((x($_GET,'cid')) ? '&cid=' . $_GET['cid'] : '') . ((x($_GET,'gid')) ? '&gid=' . $_GET['gid'] : ''),
@@ -1770,6 +1743,9 @@ function profile_tabs($a, $is_owner = false, $nickname = null){
if (App::$is_sys)
return;
+ if (get_pconfig($uid, 'system', 'noprofiletabs'))
+ return;
+
$channel = App::get_channel();
if (is_null($nickname))
@@ -1779,6 +1755,9 @@ function profile_tabs($a, $is_owner = false, $nickname = null){
$uid = ((App::$profile['profile_uid']) ? App::$profile['profile_uid'] : local_channel());
$account_id = ((App::$profile['profile_uid']) ? App::$profile['channel_account_id'] : App::$channel['channel_account_id']);
+ if ($uid == local_channel())
+ return;
+
if($uid == local_channel()) {
$cal_link = '';
}
@@ -1801,9 +1780,6 @@ function profile_tabs($a, $is_owner = false, $nickname = null){
$has_webpages = (($r) ? true : false);
- if (get_pconfig($uid, 'system', 'noprofiletabs'))
- return;
-
if (x($_GET, 'tab'))
$tab = notags(trim($_GET['tab']));
@@ -1817,6 +1793,7 @@ function profile_tabs($a, $is_owner = false, $nickname = null){
'sel' => ((argv(0) == 'channel') ? 'active' : ''),
'title' => t('Status Messages and Posts'),
'id' => 'status-tab',
+ 'icon' => 'home'
),
);
@@ -1829,6 +1806,7 @@ function profile_tabs($a, $is_owner = false, $nickname = null){
'sel' => ((argv(0) == 'profile') ? 'active' : ''),
'title' => t('Profile Details'),
'id' => 'profile-tab',
+ 'icon' => 'user'
);
}
if ($p['view_storage']) {
@@ -1838,6 +1816,7 @@ function profile_tabs($a, $is_owner = false, $nickname = null){
'sel' => ((argv(0) == 'photos') ? 'active' : ''),
'title' => t('Photo Albums'),
'id' => 'photo-tab',
+ 'icon' => 'photo'
);
$tabs[] = array(
'label' => t('Files'),
@@ -1845,6 +1824,7 @@ function profile_tabs($a, $is_owner = false, $nickname = null){
'sel' => ((argv(0) == 'cloud' || argv(0) == 'sharedwithme') ? 'active' : ''),
'title' => t('Files and Storage'),
'id' => 'files-tab',
+ 'icon' => 'folder-open'
);
}
@@ -1855,6 +1835,7 @@ function profile_tabs($a, $is_owner = false, $nickname = null){
'sel' => ((argv(0) == 'cal' || argv(0) == 'events') ? 'active' : ''),
'title' => t('Events'),
'id' => 'event-tab',
+ 'icon' => 'calendar'
);
}
@@ -1868,22 +1849,36 @@ function profile_tabs($a, $is_owner = false, $nickname = null){
'sel' => ((argv(0) == 'chat') ? 'active' : '' ),
'title' => t('Chatrooms'),
'id' => 'chat-tab',
+ 'icon' => 'comments-o'
);
}
}
require_once('include/menu.php');
$has_bookmarks = menu_list_count(local_channel(),'',MENU_BOOKMARK) + menu_list_count(local_channel(),'',MENU_SYSTEM|MENU_BOOKMARK);
- if ($is_owner && $has_bookmarks) {
+
+ if($is_owner && $has_bookmarks) {
$tabs[] = array(
'label' => t('Bookmarks'),
'url' => z_root() . '/bookmarks',
'sel' => ((argv(0) == 'bookmarks') ? 'active' : ''),
'title' => t('Saved Bookmarks'),
'id' => 'bookmarks-tab',
+ 'icon' => 'bookmark'
);
}
+ if(feature_enabled($uid,'cards')) {
+ $tabs[] = array(
+ 'label' => t('Cards'),
+ 'url' => z_root() . '/cards/' . $nickname,
+ 'sel' => ((argv(0) == 'cards') ? 'active' : ''),
+ 'title' => t('View Cards'),
+ 'id' => 'cards-tab',
+ 'icon' => 'list'
+ );
+ }
+
if($has_webpages && feature_enabled($uid,'webpages')) {
$tabs[] = array(
'label' => t('Webpages'),
@@ -1891,27 +1886,34 @@ function profile_tabs($a, $is_owner = false, $nickname = null){
'sel' => ((argv(0) == 'webpages') ? 'active' : ''),
'title' => t('View Webpages'),
'id' => 'webpages-tab',
+ 'icon' => 'newspaper-o'
);
}
-
- if(feature_enabled($uid,'wiki') && (get_account_techlevel($account_id) > 3)) {
- $tabs[] = array(
- 'label' => t('Wikis'),
- 'url' => z_root() . '/wiki/' . $nickname,
- 'sel' => ((argv(0) == 'wiki') ? 'active' : ''),
- 'title' => t('Wiki'),
- 'id' => 'wiki-tab',
- );
- }
+ if ($p['view_wiki']) {
+ if(feature_enabled($uid,'wiki') && (get_account_techlevel($account_id) > 3)) {
+ $tabs[] = array(
+ 'label' => t('Wikis'),
+ 'url' => z_root() . '/wiki/' . $nickname,
+ 'sel' => ((argv(0) == 'wiki') ? 'active' : ''),
+ 'title' => t('Wiki'),
+ 'id' => 'wiki-tab',
+ 'icon' => 'pencil-square-o'
+ );
+ }
+ }
$arr = array('is_owner' => $is_owner, 'nickname' => $nickname, 'tab' => (($tab) ? $tab : false), 'tabs' => $tabs);
call_hooks('profile_tabs', $arr);
- $tpl = get_markup_template('common_tabs.tpl');
+ $tpl = get_markup_template('profile_tabs.tpl');
- return replace_macros($tpl,array('$tabs' => $arr['tabs']));
+ return replace_macros($tpl, array(
+ '$tabs' => $arr['tabs'],
+ '$name' => App::$profile['channel_name'],
+ '$thumb' => App::$profile['thumb']
+ ));
}
@@ -1922,15 +1924,11 @@ function get_responses($conv_responses,$response_verbs,$ob,$item) {
$ret[$v] = array();
$ret[$v]['count'] = ((x($conv_responses[$v],$item['mid'])) ? $conv_responses[$v][$item['mid']] : '');
$ret[$v]['list'] = ((x($conv_responses[$v],$item['mid'])) ? $conv_responses[$v][$item['mid'] . '-l'] : '');
- if(count($ret[$v]['list']) > MAX_LIKERS) {
- $ret[$v]['list_part'] = array_slice($ret[$v]['list'], 0, MAX_LIKERS);
- array_push($ret[$v]['list_part'], '<a href="#" data-toggle="modal" data-target="#' . $v . 'Modal-'
- . (($ob) ? $ob->get_id() : $item['id']) . '"><b>' . t('View all') . '</b></a>');
- } else {
- $ret[$v]['list_part'] = '';
- }
$ret[$v]['button'] = get_response_button_text($v,$ret[$v]['count']);
$ret[$v]['title'] = $conv_responses[$v]['title'];
+ if($ret[$v]['count'] > MAX_LIKERS) {
+ $ret[$v]['modal'] = true;
+ }
}
$count = 0;
diff --git a/include/crypto.php b/include/crypto.php
index f75390985..622add4dc 100644
--- a/include/crypto.php
+++ b/include/crypto.php
@@ -55,6 +55,7 @@ function AES256CBC_decrypt($data,$key,$iv) {
return openssl_decrypt($data,'aes-256-cbc',str_pad($key,32,"\0"),OPENSSL_RAW_DATA,str_pad($iv,16,"\0"));
}
+
function AES128CBC_encrypt($data,$key,$iv) {
$key = substr($key,0,16);
$iv = substr($iv,0,16);
@@ -67,18 +68,33 @@ function AES128CBC_decrypt($data,$key,$iv) {
return openssl_decrypt($data,'aes-128-cbc',str_pad($key,16,"\0"),OPENSSL_RAW_DATA,str_pad($iv,16,"\0"));
}
-function STD_encrypt($data,$key,$iv) {
+
+function AES256CTR_encrypt($data,$key,$iv) {
$key = substr($key,0,32);
$iv = substr($iv,0,16);
- return openssl_encrypt($data,'aes-256-cbc',str_pad($key,32,"\0"),OPENSSL_RAW_DATA,str_pad($iv,16,"\0"));
+ return openssl_encrypt($data,'aes-256-ctr',str_pad($key,32,"\0"),OPENSSL_RAW_DATA,str_pad($iv,16,"\0"));
}
-function STD_decrypt($data,$key,$iv) {
+function AES256CTR_decrypt($data,$key,$iv) {
$key = substr($key,0,32);
$iv = substr($iv,0,16);
- return openssl_decrypt($data,'aes-256-cbc',str_pad($key,32,"\0"),OPENSSL_RAW_DATA,str_pad($iv,16,"\0"));
+ return openssl_decrypt($data,'aes-256-ctr',str_pad($key,32,"\0"),OPENSSL_RAW_DATA,str_pad($iv,16,"\0"));
+}
+
+
+function CAMELLIA256CFB_encrypt($data,$key,$iv) {
+ $key = substr($key,0,32);
+ $iv = substr($iv,0,16);
+ return openssl_encrypt($data,'camellia-256-cfb',str_pad($key,32,"\0"),OPENSSL_RAW_DATA,str_pad($iv,16,"\0"));
}
+function CAMELLIA256CFB_decrypt($data,$key,$iv) {
+ $key = substr($key,0,32);
+ $iv = substr($iv,0,16);
+ return openssl_decrypt($data,'camellia-256-cfb',str_pad($key,32,"\0"),OPENSSL_RAW_DATA,str_pad($iv,16,"\0"));
+}
+
+
function CAST5CBC_encrypt($data,$key,$iv) {
$key = substr($key,0,16);
$iv = substr($iv,0,8);
@@ -91,6 +107,20 @@ function CAST5CBC_decrypt($data,$key,$iv) {
return openssl_decrypt($data,'cast5-cbc',str_pad($key,16,"\0"),OPENSSL_RAW_DATA,str_pad($iv,8,"\0"));
}
+function CAST5CFB_encrypt($data,$key,$iv) {
+ $key = substr($key,0,16);
+ $iv = substr($iv,0,8);
+ return openssl_encrypt($data,'cast5-cfb',str_pad($key,16,"\0"),OPENSSL_RAW_DATA,str_pad($iv,8,"\0"));
+}
+
+function CAST5CFB_decrypt($data,$key,$iv) {
+ $key = substr($key,0,16);
+ $iv = substr($iv,0,8);
+ return openssl_decrypt($data,'cast5-cfb',str_pad($key,16,"\0"),OPENSSL_RAW_DATA,str_pad($iv,8,"\0"));
+}
+
+
+
function crypto_encapsulate($data,$pubkey,$alg='aes256cbc') {
$fn = strtoupper($alg) . '_encrypt';
@@ -118,6 +148,7 @@ function other_encapsulate($data,$pubkey,$alg) {
// compromised by state actors and evidence is mounting that this has
// already happened.
+ $result = [ 'encrypted' => true ];
$key = openssl_random_pseudo_bytes(256);
$iv = openssl_random_pseudo_bytes(256);
$result['data'] = base64url_encode($fn($data,$key,$iv),true);
@@ -142,28 +173,37 @@ function other_encapsulate($data,$pubkey,$alg) {
function crypto_methods() {
- if(\Zotlabs\Lib\System::get_server_role() !== 'pro')
- return [ 'aes256cbc' ];
-
- // 'std' is the new project standard which is aes256cbc but transmits/receives 256-byte key and iv.
// aes256cbc is provided for compatibility with earlier zot implementations which assume 32-byte key and 16-byte iv.
// other_encapsulate() now produces these longer keys/ivs by default so that it is difficult to guess a
// particular implementation or choice of underlying implementations based on the key/iv length.
// The actual methods are responsible for deriving the actual key/iv from the provided parameters;
// possibly by truncation or segmentation - though many other methods could be used.
- $r = [ 'std', 'aes256cbc', 'aes128cbc', 'cast5cbc' ];
+ $r = [ 'aes256ctr', 'camellia256cfb', 'cast5cfb', 'aes256cbc', 'aes128cbc', 'cast5cbc' ];
call_hooks('crypto_methods',$r);
return $r;
}
+function signing_methods() {
+
+
+ $r = [ 'sha256' ];
+ call_hooks('signing_methods',$r);
+ return $r;
+
+}
+
+
function aes_encapsulate($data,$pubkey) {
if(! $pubkey)
logger('aes_encapsulate: no key. data: ' . $data);
$key = openssl_random_pseudo_bytes(32);
$iv = openssl_random_pseudo_bytes(16);
+
+ $result = [ 'encrypted' => true ];
+
$result['data'] = base64url_encode(AES256CBC_encrypt($data,$key,$iv),true);
// log the offending call so we can track it down
if(! openssl_public_encrypt($key,$k,$pubkey)) {
diff --git a/include/dba/dba_driver.php b/include/dba/dba_driver.php
index e47f97387..7e925a106 100755
--- a/include/dba/dba_driver.php
+++ b/include/dba/dba_driver.php
@@ -15,7 +15,7 @@ class DBA {
static public $scheme = 'mysql';
static public $logging = false;
- static public $install_script = 'install/schema_mysql.sql';
+ static public $install_script = 'schema_mysql.sql';
static public $null_date = '0001-01-01 00:00:00';
static public $utc_now = 'UTC_TIMESTAMP()';
static public $tquot = "`";
@@ -46,7 +46,7 @@ class DBA {
if(!($port))
$port = 5432;
- self::$install_script = 'install/schema_postgres.sql';
+ self::$install_script = 'schema_postgres.sql';
self::$utc_now = "now() at time zone 'UTC'";
self::$tquot = '"';
self::$scheme = 'pgsql';
@@ -163,7 +163,10 @@ abstract class dba_driver {
}
function get_install_script() {
- return \DBA::$install_script;
+ $platform_name = \Zotlabs\Lib\System::get_platform_name();
+ if(file_exists('install/' . $platform_name . '/' . \DBA::$install_script))
+ return 'install/' . $platform_name . '/' . \DBA::$install_script;
+ return 'install/' . \DBA::$install_script;
}
function get_table_quote() {
@@ -342,11 +345,8 @@ function q($sql) {
if(\DBA::$dba && \DBA::$dba->connected) {
$stmt = vsprintf($sql, $args);
if($stmt === false) {
- if(version_compare(PHP_VERSION, '5.4.0') >= 0)
- db_logger('dba: vsprintf error: ' .
- print_r(debug_backtrace(DEBUG_BACKTRACE_PROVIDE_OBJECT, 1), true),LOGGER_NORMAL,LOG_CRIT);
- else
- db_logger('dba: vsprintf error: ' . print_r(debug_backtrace(), true),LOGGER_NORMAL,LOG_CRIT);
+ db_logger('dba: vsprintf error: ' .
+ print_r(debug_backtrace(DEBUG_BACKTRACE_PROVIDE_OBJECT, 1), true),LOGGER_NORMAL,LOG_CRIT);
}
if(\DBA::$dba->debug)
db_logger('Sql: ' . $stmt, LOGGER_DEBUG, LOG_INFO);
@@ -443,6 +443,20 @@ function db_getfunc($f) {
return $f;
}
+function db_load_file($f) {
+ // db errors should get logged to the logfile
+ $str = @file_get_contents($f);
+ $arr = explode(';', $str);
+ if($arr) {
+ foreach($arr as $a) {
+ if(strlen(trim($a))) {
+ $r = dbq(trim($a));
+ }
+ }
+ }
+}
+
+
// The logger function may make DB calls internally to query the system logging parameters.
// This can cause a recursion if database debugging is enabled.
// So this function preserves the current database debugging state and then turns it off
@@ -450,7 +464,7 @@ function db_getfunc($f) {
function db_logger($s,$level = LOGGER_NORMAL,$syslog = LOG_INFO) {
- if(\DBA::$logging)
+ if(\DBA::$logging || ! \DBA::$dba)
return;
$saved = \DBA::$dba->debug;
diff --git a/include/dba/dba_pdo.php b/include/dba/dba_pdo.php
index f76e6cdd7..f119d8926 100755
--- a/include/dba/dba_pdo.php
+++ b/include/dba/dba_pdo.php
@@ -74,19 +74,19 @@ class dba_pdo extends dba_driver {
return $result;
}
- if($this->debug) {
- db_logger('dba_pdo: DEBUG: ' . printable($sql) . ' returned ' . count($result) . ' results.', LOGGER_NORMAL, LOG_INFO);
- }
-
$r = array();
if($result) {
foreach($result as $x) {
$r[] = $x;
}
- if($this->debug) {
- db_logger('dba_pdo: ' . printable(print_r($r,true)), LOGGER_NORMAL, LOG_INFO);
- }
}
+
+ if($this->debug) {
+ db_logger('dba_pdo: DEBUG: ' . printable($sql) . ' returned ' . count($r) . ' results.', LOGGER_NORMAL, LOG_INFO);
+ db_logger('dba_pdo: ' . printable(print_r($r,true)), LOGGER_NORMAL, LOG_INFO);
+ }
+
+
return (($this->error) ? false : $r);
}
diff --git a/include/dir_fns.php b/include/dir_fns.php
index 3922730fc..2bd1228ec 100644
--- a/include/dir_fns.php
+++ b/include/dir_fns.php
@@ -185,26 +185,17 @@ function sync_directories($dirmode) {
/** @FIXME What to do if we're in a different realm? */
if ((! $r) && (z_root() != DIRECTORY_FALLBACK_MASTER)) {
- $r = array();
- $r[] = array(
- 'site_url' => DIRECTORY_FALLBACK_MASTER,
- 'site_flags' => DIRECTORY_MODE_PRIMARY,
- 'site_update' => NULL_DATE,
- 'site_directory' => DIRECTORY_FALLBACK_MASTER . '/dirsearch',
- 'site_realm' => DIRECTORY_REALM,
- 'site_valid' => 1,
- 'site_crypto' => 'aes256cbc'
-
- );
- $x = q("insert into site ( site_url, site_flags, site_update, site_directory, site_realm, site_valid, site_crypto )
- values ( '%s', %d, '%s', '%s', '%s', %d, '%s' ) ",
- dbesc($r[0]['site_url']),
- intval($r[0]['site_flags']),
- dbesc($r[0]['site_update']),
- dbesc($r[0]['site_directory']),
- dbesc($r[0]['site_realm']),
- intval($r[0]['site_valid']),
- dbesc($r[0]['site_crypto'])
+
+ $x = site_store_lowlevel(
+ [
+ 'site_url' => DIRECTORY_FALLBACK_MASTER,
+ 'site_flags' => DIRECTORY_MODE_PRIMARY,
+ 'site_update' => NULL_DATE,
+ 'site_directory' => DIRECTORY_FALLBACK_MASTER . '/dirsearch',
+ 'site_realm' => DIRECTORY_REALM,
+ 'site_valid' => 1,
+ 'site_crypto' => 'aes256cbc'
+ ]
);
$r = q("select * from site where site_flags in (%d, %d) and site_url != '%s' and site_type = %d ",
diff --git a/include/environment.php b/include/environment.php
index 11d465b84..96a614821 100644
--- a/include/environment.php
+++ b/include/environment.php
@@ -65,4 +65,4 @@ function phpiniSizeToBytes($val) {
}
return (int)$val;
-} \ No newline at end of file
+}
diff --git a/include/event.php b/include/event.php
index cf1cc331d..b56a5fb3e 100644
--- a/include/event.php
+++ b/include/event.php
@@ -210,6 +210,10 @@ function format_event_bbcode($ev) {
$o = '';
+ if($ev['event_vdata']) {
+ $o .= '[event]' . $ev['event_vdata'] . '[/event]';
+ }
+
if($ev['summary'])
$o .= '[event-summary]' . $ev['summary'] . '[/event-summary]';
@@ -249,6 +253,15 @@ function bbtoevent($s) {
$ev = array();
+
+ $match = '';
+ if(preg_match("/\[event\](.*?)\[\/event\]/is",$s,$match)) {
+ // only parse one object per event tag
+ $x = ical_to_ev($match[1]);
+ if($x)
+ $ev = $x[0];
+ }
+
$match = '';
if(preg_match("/\[event\-summary\](.*?)\[\/event\-summary\]/is",$s,$match))
$ev['summary'] = $match[1];
@@ -283,6 +296,8 @@ function bbtoevent($s) {
$ev['nofinish'] = 1;
}
+// logger('bbtoevent: ' . print_r($ev,true));
+
return $ev;
}
@@ -555,6 +570,136 @@ function event_addtocal($item_id, $uid) {
}
+function ical_to_ev($s) {
+ require_once('vendor/autoload.php');
+
+ $saved_timezone = date_default_timezone_get();
+ date_default_timezone_set('Australia/Sydney');
+
+ $ical = VObject\Reader::read($s);
+
+ $ev = [];
+
+ if($ical) {
+ if($ical->VEVENT) {
+ foreach($ical->VEVENT as $event) {
+ $ev[] = parse_vobject($event,'event');
+ }
+ }
+ if($ical->VTODO) {
+ foreach($ical->VTODO as $event) {
+ $ev[] = parse_vobject($event,'task');
+ }
+ }
+ }
+
+ date_default_timezone_set($saved_timezone);
+
+ return $ev;
+
+}
+
+
+
+function parse_vobject($ical, $type) {
+
+
+ $ev = [];
+
+ if(! isset($ical->DTSTART)) {
+ logger('no event start');
+ return $ev;
+ }
+
+ $ev['etype'] = $type;
+
+ $dtstart = $ical->DTSTART->getDateTime();
+ $ev['adjust'] = (($ical->DTSTART->isFloating()) ? 0 : 1);
+
+ $ev['dtstart'] = datetime_convert((($ev['adjust']) ? 'UTC' : date_default_timezone_get()),'UTC',
+ $dtstart->format(\DateTime::W3C));
+
+
+ if(isset($ical->DUE)) {
+ $dtend = $ical->DUE->getDateTime();
+ $ev['dtend'] = datetime_convert((($ev['adjust']) ? 'UTC' : date_default_timezone_get()),'UTC',
+ $dtend->format(\DateTime::W3C));
+ }
+ elseif(isset($ical->DTEND)) {
+ $dtend = $ical->DTEND->getDateTime();
+ $ev['dtend'] = datetime_convert((($ev['adjust']) ? 'UTC' : date_default_timezone_get()),'UTC',
+ $dtend->format(\DateTime::W3C));
+ }
+ else
+ $ev['nofinish'] = 1;
+
+
+ if($ev['dtstart'] === $ev['dtend'])
+ $ev['nofinish'] = 1;
+
+ if(isset($ical->CREATED)) {
+ $created = $ical->CREATED->getDateTime();
+ $ev['created'] = datetime_convert('UTC','UTC',$created->format(\DateTime::W3C));
+ }
+
+ if(isset($ical->{'DTSTAMP'})) {
+ $edited = $ical->{'DTSTAMP'}->getDateTime();
+ $ev['edited'] = datetime_convert('UTC','UTC',$edited->format(\DateTime::W3C));
+ }
+ if(isset($ical->{'LAST-MODIFIED'})) {
+ $edited = $ical->{'LAST-MODIFIED'}->getDateTime();
+ $ev['edited'] = datetime_convert('UTC','UTC',$edited->format(\DateTime::W3C));
+ }
+
+ if(isset($ical->{'X-ZOT-LOCATION'}))
+ $ev['location'] = event_ical_get_sourcetext( (string) $ical->{'X-ZOT-LOCATION'});
+ elseif(isset($ical->LOCATION))
+ $ev['location'] = (string) $ical->LOCATION;
+
+ if(isset($ical->{'X-ZOT-DESCRIPTION'}))
+ $ev['description'] = event_ical_get_sourcetext( (string) $ical->{'X-ZOT-DESCRIPTION'});
+ elseif(isset($ical->DESCRIPTION))
+ $ev['description'] = (string) $ical->DESCRIPTION;
+
+ if(isset($ical->{'X-ZOT-SUMMARY'}))
+ $ev['summary'] = event_ical_get_sourcetext( (string) $ical->{'X-ZOT-SUMMARY'});
+ elseif(isset($ical->SUMMARY))
+ $ev['summary'] = (string) $ical->SUMMARY;
+
+ if(isset($ical->PRIORITY))
+ $ev['event_priority'] = intval((string) $ical->PRIORITY);
+
+ if(isset($ical->UID)) {
+ $evuid = (string) $ical->UID;
+ $ev['event_hash'] = $evuid;
+ }
+
+ if(isset($ical->SEQUENCE)) {
+ $ev['event_sequence'] = (string) $ical->SEQUENCE;
+ }
+
+ if(isset($ical->STATUS)) {
+ $ev['event_status'] = (string) $ical->STATUS;
+ }
+
+ if(isset($ical->{'COMPLETED'})) {
+ $completed = $ical->{'COMPLETED'}->getDateTime();
+ $ev['event_status_date'] = datetime_convert('UTC','UTC',$completed->format(\DateTime::W3C));
+ }
+
+ if(isset($ical->{'PERCENT-COMPLETE'})) {
+ $ev['event_percent'] = (string) $ical->{'PERCENT-COMPLETE'} ;
+ }
+
+ $ev['event_vdata'] = $ical->serialize();
+
+ return $ev;
+}
+
+
+
+
+
function parse_ical_file($f,$uid) {
require_once('vendor/autoload.php');
@@ -610,22 +755,21 @@ function event_import_ical($ical, $uid) {
}
$dtstart = $ical->DTSTART->getDateTime();
- $ev['adjust'] = (($ical->DTSTART->isFloating()) ? 1 : 0);
+ $ev['adjust'] = (($ical->DTSTART->isFloating()) ? 0 : 1);
// logger('dtstart: ' . var_export($dtstart,true));
$ev['dtstart'] = datetime_convert((($ev['adjust']) ? 'UTC' : date_default_timezone_get()),'UTC',
$dtstart->format(\DateTime::W3C));
-
if(isset($ical->DTEND)) {
$dtend = $ical->DTEND->getDateTime();
$ev['dtend'] = datetime_convert((($ev['adjust']) ? 'UTC' : date_default_timezone_get()),'UTC',
$dtend->format(\DateTime::W3C));
}
- else
+ else {
$ev['nofinish'] = 1;
-
+ }
if($ev['dtstart'] === $ev['dtend'])
$ev['nofinish'] = 1;
@@ -635,6 +779,7 @@ function event_import_ical($ical, $uid) {
$ev['created'] = datetime_convert('UTC','UTC',$created->format(\DateTime::W3C));
}
+
if(isset($ical->{'LAST-MODIFIED'})) {
$edited = $ical->{'LAST-MODIFIED'}->getDateTime();
$ev['edited'] = datetime_convert('UTC','UTC',$edited->format(\DateTime::W3C));
@@ -713,7 +858,7 @@ function event_import_ical_task($ical, $uid) {
$dtstart = $ical->DTSTART->getDateTime();
- $ev['adjust'] = (($ical->DTSTART->isFloating()) ? 1 : 0);
+ $ev['adjust'] = (($ical->DTSTART->isFloating()) ? 0 : 1);
// logger('dtstart: ' . var_export($dtstart,true));
@@ -1091,3 +1236,71 @@ function tasks_fetch($arr) {
return $ret;
}
+
+function cdav_principal($uri) {
+ $r = q("SELECT uri FROM principals WHERE uri = '%s' LIMIT 1",
+ dbesc($uri)
+ );
+
+ if($r[0]['uri'] === $uri)
+ return true;
+ else
+ return false;
+}
+
+function cdav_perms($needle, $haystack, $check_rw = false) {
+ foreach ($haystack as $item) {
+ if($check_rw) {
+ if(is_array($item['id'])) {
+ if ($item['id'][0] == $needle && $item['share-access'] != 2) {
+ return $item['{DAV:}displayname'];
+ }
+ }
+ else {
+ if ($item['id'] == $needle && $item['share-access'] != 2) {
+ return $item['{DAV:}displayname'];
+ }
+ }
+ }
+ else {
+ if(is_array($item['id'])) {
+ if ($item['id'][0] == $needle) {
+ return $item['{DAV:}displayname'];
+ }
+ }
+ else {
+ if ($item['id'] == $needle) {
+ return $item['{DAV:}displayname'];
+ }
+ }
+ }
+ }
+ return false;
+}
+
+
+function translate_type($type) {
+
+ if(!$type)
+ return;
+
+ $type = strtoupper($type);
+
+ $map = [
+ 'CELL' => t('Mobile'),
+ 'HOME' => t('Home'),
+ 'HOME,VOICE' => t('Home, Voice'),
+ 'HOME,FAX' => t('Home, Fax'),
+ 'WORK' => t('Work'),
+ 'WORK,VOICE' => t('Work, Voice'),
+ 'WORK,FAX' => t('Work, Fax'),
+ 'OTHER' => t('Other')
+ ];
+
+ if (array_key_exists($type, $map)) {
+ return [$type, $map[$type]];
+ }
+ else {
+ return [$type, t('Other') . ' (' . $type . ')'];
+ }
+}
diff --git a/include/features.php b/include/features.php
index 0fc6fbc1d..d8d98dbaa 100644
--- a/include/features.php
+++ b/include/features.php
@@ -45,10 +45,6 @@ function feature_level($feature,$def) {
function get_features($filtered = true) {
- $server_role = \Zotlabs\Lib\System::get_server_role();
-
- if($server_role === 'basic' && $filtered)
- return array();
$arr = [
@@ -122,6 +118,15 @@ function get_features($filtered = true) {
],
[
+ 'cards',
+ t('Cards'),
+ t('Create personal planning cards'),
+ false,
+ get_config('feature_lock','cards'),
+ feature_level('cards',1),
+ ],
+
+ [
'nav_channel_select',
t('Navigation Channel Select'),
t('Change channels directly from within the navigation dropdown menu'),
@@ -359,6 +364,15 @@ function get_features($filtered = true) {
t('Post/Comment Tools'),
[
+ 'markdown',
+ t('Markdown'),
+ t('Use markdown for editing posts'),
+ false,
+ get_config('feature_lock','markdown'),
+ feature_level('markdown',2),
+ ],
+
+ [
'commtag',
t('Community Tagging'),
t('Ability to tag existing posts'),
@@ -424,16 +438,15 @@ function get_features($filtered = true) {
];
- if($server_role === 'pro') {
- $arr['general'][] = [
- 'premium_channel',
- t('Premium Channel'),
- t('Allows you to set restrictions and terms on those that connect with your channel'),
- false,
- get_config('feature_lock','premium_channel'),
- feature_level('premium_channel',4),
- ];
- }
+ $arr['general'][] = [
+ 'premium_channel',
+ t('Premium Channel'),
+ t('Allows you to set restrictions and terms on those that connect with your channel'),
+ false,
+ get_config('feature_lock','premium_channel'),
+ feature_level('premium_channel',4),
+ ];
+
$techlevel = get_account_techlevel();
diff --git a/include/feedutils.php b/include/feedutils.php
index b122a8e4b..217da8188 100644
--- a/include/feedutils.php
+++ b/include/feedutils.php
@@ -2,39 +2,39 @@
/**
- * @brief Generate an Atom feed.
+ * @brief Return an Atom feed for channel.
+ *
+ * @see get_feed_for()
*
* @param array $channel
- * @param array $params
+ * @param array $params associative array which configures the feed
+ * @return string with an atom feed
*/
function get_public_feed($channel, $params) {
- $type = 'xml';
+/* $type = 'xml';
$begin = NULL_DATE;
$end = '';
$start = 0;
$records = 40;
$direction = 'desc';
$pages = 0;
+*/
if(! $params)
- $params = array();
-
- $params['type'] = ((x($params,'type')) ? $params['type'] : 'xml');
- $params['begin'] = ((x($params,'begin')) ? $params['begin'] : NULL_DATE);
- $params['end'] = ((x($params,'end')) ? $params['end'] : datetime_convert('UTC','UTC','now'));
- $params['start'] = ((x($params,'start')) ? $params['start'] : 0);
- $params['records'] = ((x($params,'records')) ? $params['records'] : 40);
- $params['direction'] = ((x($params,'direction')) ? $params['direction'] : 'desc');
- $params['pages'] = ((x($params,'pages')) ? intval($params['pages']) : 0);
- $params['top'] = ((x($params,'top')) ? intval($params['top']) : 0);
- $params['cat'] = ((x($params,'cat')) ? $params['cat'] : '');
-
+ $params = [];
- // put a sane lower limit on feed requests if not specified
+ $params['type'] = ((x($params,'type')) ? $params['type'] : 'xml');
+ $params['begin'] = ((x($params,'begin')) ? $params['begin'] : NULL_DATE);
+ $params['end'] = ((x($params,'end')) ? $params['end'] : datetime_convert('UTC','UTC','now'));
+ $params['start'] = ((x($params,'start')) ? $params['start'] : 0);
+ $params['records'] = ((x($params,'records')) ? $params['records'] : 40);
+ $params['direction'] = ((x($params,'direction'))? $params['direction'] : 'desc');
+ $params['pages'] = ((x($params,'pages')) ? intval($params['pages']) : 0);
+ $params['top'] = ((x($params,'top')) ? intval($params['top']) : 0);
+ $params['cat'] = ((x($params,'cat')) ? $params['cat'] : '');
+ $params['compat'] = ((x($params,'compat')) ? intval($params['compat']) : 0);
-// if($params['begin'] <= NULL_DATE)
-// $params['begin'] = datetime_convert('UTC','UTC','now - 1 month');
switch($params['type']) {
case 'json':
@@ -50,16 +50,17 @@ function get_public_feed($channel, $params) {
}
/**
- * @brief
+ * @brief Create an atom feed for $channel from template.
*
* @param array $channel
- * @param string $observer_hash
+ * @param string $observer_hash xchan_hash from observer
* @param array $params
- * @return string
+ * @return string with an atom feed
*/
+
function get_feed_for($channel, $observer_hash, $params) {
- if(! channel)
+ if(! $channel)
http_status_exit(401);
if($params['pages']) {
@@ -69,32 +70,28 @@ function get_feed_for($channel, $observer_hash, $params) {
if(! perm_is_allowed($channel['channel_id'],$observer_hash,'view_stream'))
http_status_exit(403);
}
- $items = items_fetch(array(
- 'wall' => '1',
- 'datequery' => $params['end'],
- 'datequery2' => $params['begin'],
- 'start' => $params['start'], // FIXME
- 'records' => $params['records'], // FIXME
- 'direction' => $params['direction'], // FIXME
- 'pages' => $params['pages'],
- 'order' => 'post',
- 'top' => $params['top'],
- 'cat' => $params['cat']
- ), $channel, $observer_hash, CLIENT_MODE_NORMAL, App::$module);
-
+
+ // logger('params: ' . print_r($params,true));
$feed_template = get_markup_template('atom_feed.tpl');
$atom = '';
+ $feed_author = '';
+ if(intval($params['compat']) === 1) {
+ $feed_author = atom_render_author('author',$channel);
+ }
+
+ $owner = atom_render_author('zot:owner',$channel);
+
$atom .= replace_macros($feed_template, array(
'$version' => xmlify(Zotlabs\Lib\System::get_project_version()),
'$red' => xmlify(Zotlabs\Lib\System::get_platform_name()),
'$feed_id' => xmlify($channel['xchan_url']),
'$feed_title' => xmlify($channel['channel_name']),
- '$feed_updated' => xmlify(datetime_convert('UTC', 'UTC', 'now' , ATOM_TIME)) ,
- '$hub' => '', // feed_hublinks(),
- '$salmon' => '', // feed_salmonlinks($channel['channel_address']),
+ '$feed_updated' => xmlify(datetime_convert('UTC', 'UTC', 'now', ATOM_TIME)),
+ '$author' => $feed_author,
+ '$owner' => $owner,
'$name' => xmlify($channel['channel_name']),
'$profile_page' => xmlify($channel['xchan_url']),
'$mimephoto' => xmlify($channel['xchan_photo_mimetype']),
@@ -108,8 +105,30 @@ function get_feed_for($channel, $observer_hash, $params) {
));
+ $x = [ 'xml' => $atom, 'channel' => $channel, 'observer_hash' => $observer_hash, 'params' => $params ];
+ call_hooks('atom_feed_top',$x);
+
+ $atom = $x['xml'];
+
+ // a much simpler interface
call_hooks('atom_feed', $atom);
+ $items = items_fetch(
+ [
+ 'wall' => '1',
+ 'datequery' => $params['end'],
+ 'datequery2' => $params['begin'],
+ 'start' => intval($params['start']),
+ 'records' => intval($params['records']),
+ 'direction' => dbesc($params['direction']),
+ 'pages' => $params['pages'],
+ 'order' => dbesc('post'),
+ 'top' => $params['top'],
+ 'cat' => $params['cat'],
+ 'compat' => $params['compat']
+ ], $channel, $observer_hash, CLIENT_MODE_NORMAL, App::$module
+ );
+
if($items) {
$type = 'html';
foreach($items as $item) {
@@ -117,7 +136,7 @@ function get_feed_for($channel, $observer_hash, $params) {
continue;
/** @BUG $owner is undefined in this call */
- $atom .= atom_entry($item, $type, null, $owner, true);
+ $atom .= atom_entry($item, $type, null, $owner, true, '', $params['compat']);
}
}
@@ -129,10 +148,10 @@ function get_feed_for($channel, $observer_hash, $params) {
}
/**
- * @brief
+ * @brief Return the verb for an item, or fall back to ACTIVITY_POST.
*
* @param array $item an associative array with
- * * \b string \b verb
+ * * \e string \b verb
* @return string item's verb if set, default ACTIVITY_POST see boot.php
*/
function construct_verb($item) {
@@ -165,9 +184,11 @@ function construct_activity_object($item) {
else
$o .= '<link rel="alternate" type="text/html" href="' . xmlify($r->link) . '" />' . "\r\n";
}
- if($r->content)
+ if($r->content) {
$o .= '<content type="html" >' . xmlify(bbcode($r->content)) . '</content>' . "\r\n";
+ }
$o .= '</as:object>' . "\r\n";
+
return $o;
}
@@ -210,22 +231,32 @@ function construct_activity_target($item) {
}
/**
- * @param object $feed
+ * @brief Return an array with a parsed atom item.
+ *
+ * @param SimplePie $feed
* @param array $item
* @param[out] array $author
- * @return multitype:multitype: string NULL number Ambigous <NULL, string, number> Ambigous <mixed, string> Ambigous <multitype:multitype:string Ambigous <NULL, string> , multitype:multitype:string unknown > multitype:NULL unknown
+ * @return array Associative array with the parsed item data
*/
function get_atom_elements($feed, $item, &$author) {
- //$best_photo = array();
+ require_once('include/html2bbcode.php');
$res = array();
$found_author = $item->get_author();
if($found_author) {
+ if($rawauthor) {
+ if($rawauthor[0]['child'][NAMESPACE_POCO]['displayName'][0]['data'])
+ $author['full_name'] = unxmlify($rawauthor[0]['child'][NAMESPACE_POCO]['displayName'][0]['data']);
+ }
$author['author_name'] = unxmlify($found_author->get_name());
$author['author_link'] = unxmlify($found_author->get_link());
$author['author_is_feed'] = false;
+
+ $rawauthor = $feed->get_feed_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'author');
+ //logger('rawauthor: ' . print_r($rawauthor, true));
+
}
else {
$author['author_name'] = unxmlify($feed->get_title());
@@ -236,17 +267,19 @@ function get_atom_elements($feed, $item, &$author) {
if(substr($author['author_link'],-1,1) == '/')
$author['author_link'] = substr($author['author_link'],0,-1);
- $res['mid'] = unxmlify($item->get_id());
+ $res['mid'] = normalise_id(unxmlify($item->get_id()));
$res['title'] = unxmlify($item->get_title());
$res['body'] = unxmlify($item->get_content());
$res['plink'] = unxmlify($item->get_link(0));
$res['item_rss'] = 1;
+ $summary = unxmlify($item->get_description(true));
+
// removing the content of the title if its identically to the body
// This helps with auto generated titles e.g. from tumblr
- if (title_is_body($res["title"], $res["body"]))
+ if (title_is_body($res['title'], $res['body']))
$res['title'] = "";
if($res['plink'])
@@ -254,6 +287,33 @@ function get_atom_elements($feed, $item, &$author) {
else
$base_url = '';
+
+ $rawcreated = $item->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'published');
+ if($rawcreated)
+ $res['created'] = unxmlify($rawcreated[0]['data']);
+
+ $rawedited = $item->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'updated');
+ if($rawedited)
+ $res['edited'] = unxmlify($rawedited[0]['data']);
+
+ if((x($res,'edited')) && (! (x($res,'created'))))
+ $res['created'] = $res['edited'];
+
+ if(! $res['created'])
+ $res['created'] = $item->get_date('c');
+
+ if(! $res['edited'])
+ $res['edited'] = $item->get_date('c');
+
+ $rawverb = $item->get_item_tags(NAMESPACE_ACTIVITY, 'verb');
+
+ // select between supported verbs
+
+ if($rawverb) {
+ $res['verb'] = unxmlify($rawverb[0]['data']);
+ }
+
+
// look for a photo. We should check media size and find the best one,
// but for now let's just find any author photo
@@ -268,10 +328,9 @@ function get_atom_elements($feed, $item, &$author) {
}
}
}
-
$rawactor = $item->get_item_tags(NAMESPACE_ACTIVITY, 'actor');
- if($rawactor && activity_match($rawactor[0]['child'][NAMESPACE_ACTIVITY]['obj_type'][0]['data'],ACTIVITY_OBJ_PERSON)) {
+ if($rawactor && activity_match($rawactor[0]['child'][NAMESPACE_ACTIVITY]['obj_type'][0]['data'], ACTIVITY_OBJ_PERSON)) {
$base = $rawactor[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['link'];
if($base && count($base)) {
foreach($base as $link) {
@@ -297,6 +356,7 @@ function get_atom_elements($feed, $item, &$author) {
// No photo/profile-link on the item - look at the feed level
+
if((! (x($author,'author_link'))) || (! (x($author,'author_photo')))) {
$rawauthor = $feed->get_feed_tags(SIMPLEPIE_NAMESPACE_ATOM_10,'author');
if($rawauthor && $rawauthor[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['link']) {
@@ -331,13 +391,49 @@ function get_atom_elements($feed, $item, &$author) {
}
}
- $ostatus_protocol = (($item->get_item_tags(NAMESPACE_OSTATUS,'conversation')) ? true : false);
+ $rawcnv = $item->get_item_tags(NAMESPACE_OSTATUS, 'conversation');
+ if($rawcnv) {
+ // new style
+ $ostatus_conversation = normalise_id(unxmlify($rawcnv[0]['attribs']['']['ref']));
+ if(! $ostatus_conversation) {
+ // old style
+ $ostatus_conversation = normalise_id(unxmlify($rawcnv[0]['data']));
+ }
+ if($ostatus_conversation) {
+ set_iconfig($res,'ostatus','conversation',$ostatus_conversation,true);
+ logger('ostatus_conversation: ' . $ostatus_conversation, LOGGER_DATA, LOG_INFO);
+ }
+ }
+
+ $ostatus_protocol = (($ostatus_conversation) ? true : false);
+
+ $mastodon = (($item->get_item_tags('http://mastodon.social/schema/1.0','scope')) ? true : false);
+ if($mastodon) {
+ $ostatus_protocol = true;
+ if(($mastodon[0]['data']) && ($mastodon[0]['data'] !== 'public'))
+ $res['item_private'] = 1;
+ }
- $apps = $item->get_item_tags(NAMESPACE_STATUSNET,'notice_info');
+ $apps = $item->get_item_tags(NAMESPACE_STATUSNET, 'notice_info');
if($apps && $apps[0]['attribs']['']['source']) {
$res['app'] = strip_tags(unxmlify($apps[0]['attribs']['']['source']));
}
+ if($ostatus_protocol) {
+
+ // translate OStatus unfollow to activity streams if it happened to get selected
+
+ if((x($res,'verb')) && ($res['verb'] === 'http://ostatus.org/schema/1.0/unfollow')) {
+ $res['verb'] = ACTIVITY_UNFOLLOW;
+ }
+
+ // And OStatus 'favorite' is pretty much what we call 'like' on other networks
+
+ if((x($res,'verb')) && ($res['verb'] === ACTIVITY_FAVORITE)) {
+ $res['verb'] = ACTIVITY_LIKE;
+ }
+ }
+
/*
* If there's a copy of the body content which is guaranteed to have survived mangling in transit, use it.
*/
@@ -346,7 +442,7 @@ function get_atom_elements($feed, $item, &$author) {
$rawenv = $item->get_item_tags(NAMESPACE_DFRN, 'env');
if(! $rawenv)
- $rawenv = $item->get_item_tags(NAMESPACE_ZOT,'source');
+ $rawenv = $item->get_item_tags(NAMESPACE_ZOT, 'source');
if($rawenv) {
$have_real_body = true;
$res['body'] = $rawenv[0]['data'];
@@ -393,9 +489,9 @@ function get_atom_elements($feed, $item, &$author) {
}
- // strip title and don't apply "title-in-body" if the feed involved
+ // strip title and don't apply "title-in-body" if the feed involved
// uses the OStatus stack. We need a more generalised way for the calling
- // function to specify this behaviour or for plugins to alter it.
+ // function to specify this behaviour or for plugins to alter it.
if($ostatus_protocol) {
$res['title'] = '';
@@ -421,7 +517,13 @@ function get_atom_elements($feed, $item, &$author) {
);
}
- $private = $item->get_item_tags(NAMESPACE_DFRN,'private');
+ // turn Mastodon content warning into a #nsfw hashtag
+ if($mastodon && $summary) {
+ $res['body'] = $summary . "\n\n" . $res['body'] . "\n\n#ContentWarning\n";
+ }
+
+
+ $private = $item->get_item_tags(NAMESPACE_DFRN, 'private');
if($private && intval($private[0]['data']) > 0)
$res['item_private'] = ((intval($private[0]['data'])) ? 1 : 0);
else
@@ -431,23 +533,6 @@ function get_atom_elements($feed, $item, &$author) {
if($rawlocation)
$res['location'] = unxmlify($rawlocation[0]['data']);
- $rawcreated = $item->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10,'published');
- if($rawcreated)
- $res['created'] = unxmlify($rawcreated[0]['data']);
-
- $rawedited = $item->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10,'updated');
- if($rawedited)
- $res['edited'] = unxmlify($rawedited[0]['data']);
-
- if((x($res,'edited')) && (! (x($res,'created'))))
- $res['created'] = $res['edited'];
-
- if(! $res['created'])
- $res['created'] = $item->get_date('c');
-
- if(! $res['edited'])
- $res['edited'] = $item->get_date('c');
-
// Disallow time travelling posts
@@ -465,7 +550,7 @@ function get_atom_elements($feed, $item, &$author) {
$rawowner = $item->get_item_tags(NAMESPACE_DFRN, 'owner');
if(! $rawowner)
- $rawowner = $item->get_item_tags(NAMESPACE_ZOT,'owner');
+ $rawowner = $item->get_item_tags(NAMESPACE_ZOT, 'owner');
if($rawowner[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'])
$author['owner_name'] = unxmlify($rawowner[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data']);
@@ -487,32 +572,21 @@ function get_atom_elements($feed, $item, &$author) {
}
}
- $rawgeo = $item->get_item_tags(NAMESPACE_GEORSS,'point');
+ $rawgeo = $item->get_item_tags(NAMESPACE_GEORSS, 'point');
if($rawgeo)
$res['coord'] = unxmlify($rawgeo[0]['data']);
- $rawverb = $item->get_item_tags(NAMESPACE_ACTIVITY, 'verb');
-
- // select between supported verbs
-
- if($rawverb) {
- $res['verb'] = unxmlify($rawverb[0]['data']);
- }
-
- // translate OStatus unfollow to activity streams if it happened to get selected
-
- if((x($res,'verb')) && ($res['verb'] === 'http://ostatus.org/schema/1.0/unfollow'))
- $res['verb'] = ACTIVITY_UNFOLLOW;
-
$cats = $item->get_categories();
if($cats) {
if(is_null($terms))
$terms = array();
+
foreach($cats as $cat) {
$term = $cat->get_term();
if(! $term)
$term = $cat->get_label();
+
$scheme = $cat->get_scheme();
$termurl = '';
if($scheme && $term && stristr($scheme,'X-DFRN:')) {
@@ -527,7 +601,7 @@ function get_atom_elements($feed, $item, &$author) {
if($termterm) {
$terms[] = array(
'otype' => TERM_OBJ_POST,
- 'ttype' => $termtype,
+ 'ttype' => $termtype,
'url' => $termurl,
'term' => $termterm,
);
@@ -540,6 +614,7 @@ function get_atom_elements($feed, $item, &$author) {
$attach = $item->get_enclosures();
if($attach) {
+
$res['attach'] = array();
foreach($attach as $att) {
$len = intval($att->get_length());
@@ -556,9 +631,21 @@ function get_atom_elements($feed, $item, &$author) {
if(! $type)
$type = 'application/octet-stream';
+ if($ostatus_protocol) {
+ if((strpos($type,'image') === 0) && (strpos($res['body'], ']' . $link . '[/img]') === false) && (strpos($link,'http') === 0)) {
+ $res['body'] .= "\n\n" . '[img]' . $link . '[/img]';
+ }
+ if((strpos($type,'video') === 0) && (strpos($res['body'], ']' . $link . '[/video]') === false) && (strpos($link,'http') === 0)) {
+ $res['body'] .= "\n\n" . '[video]' . $link . '[/video]';
+ }
+ if((strpos($type,'audio') === 0) && (strpos($res['body'], ']' . $link . '[/audio]') === false) && (strpos($link,'http') === 0)) {
+ $res['body'] .= "\n\n" . '[audio]' . $link . '[/audio]';
+ }
+ }
$res['attach'][] = array('href' => $link, 'length' => $len, 'type' => $type, 'title' => $title );
}
}
+
$rawobj = $item->get_item_tags(NAMESPACE_ACTIVITY, 'object');
@@ -584,6 +671,7 @@ function get_atom_elements($feed, $item, &$author) {
$body = $child[SIMPLEPIE_NAMESPACE_ATOM_10]['content'][0]['data'];
if(! $body)
$body = $child[SIMPLEPIE_NAMESPACE_ATOM_10]['summary'][0]['data'];
+
// preserve a copy of the original body content in case we later need to parse out any microformat information, e.g. events
$obj['orig'] = xmlify($body);
if((strpos($body,'<') !== false) || (strpos($body,'>') !== false)) {
@@ -635,18 +723,154 @@ function get_atom_elements($feed, $item, &$author) {
$res['target'] = $obj;
}
+
- $arr = array('feed' => $feed, 'item' => $item, 'author' => $author, 'result' => $res);
+ if(array_key_exists('verb',$res) && $res['verb'] === ACTIVITY_SHARE
+ && array_key_exists('obj_type',$res) && in_array($res['obj_type'], [ ACTIVITY_OBJ_NOTE, ACTIVITY_OBJ_COMMENT, ACTIVITY_OBJ_ACTIVITY ] )) {
+ feed_get_reshare($res,$item);
+ }
- call_hooks('parse_atom', $arr);
+ // build array to pass to hook
+ $arr = [
+ 'feed' => $feed,
+ 'item' => $item,
+ 'author' => $author,
+ 'result' => $res
+ ];
- logger('get_atom_elements: author: ' . print_r($arr['author'],true),LOGGER_DATA);
+ call_hooks('parse_atom', $arr);
- logger('get_atom_elements: ' . print_r($arr['result'],true),LOGGER_DATA);
+ logger('author: ' .print_r($arr['author'], true), LOGGER_DATA);
+ logger('result: ' .print_r($arr['result'], true), LOGGER_DATA);
return $arr['result'];
}
+function feed_get_reshare(&$res,$item) {
+
+ $share = [];
+
+ // For Mastodon shares ("boosts"), we need to parse the original author information
+ // from the activity:object -> author structure
+ $rawobj = $item->get_item_tags(NAMESPACE_ACTIVITY, 'object');
+
+ if($rawobj) {
+
+ $rawauthor = $rawobj[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['author'];
+
+ if($rawauthor && $rawauthor[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name']) {
+ $share['author'] = unxmlify($rawauthor[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data']);
+ }
+
+ if($rawauthor && $rawauthor[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri']) {
+ $share['profile'] = unxmlify($rawauthor[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data']);
+ }
+
+ if($rawauthor && $rawauthor[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['link']) {
+ $base = $rawauthor[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['link'];
+ foreach($base as $link) {
+ if(! (array_key_exists('avatar',$share) && $share['avatar'])) {
+ if($link['attribs']['']['rel'] === 'photo' || $link['attribs']['']['rel'] === 'avatar')
+ $share['avatar'] = unxmlify($link['attribs']['']['href']);
+ }
+ }
+ }
+
+ if(! $share['author'])
+ $share['author'] = t('unknown');
+ if(! $share['avatar'])
+ $share['avatar'] = z_root() . '/' . get_default_profile_photo(80);
+ if(! $share['profile'])
+ $share['profile'] = z_root();
+
+ $child = $rawobj[0]['child'];
+
+
+ if(x($child[SIMPLEPIE_NAMESPACE_ATOM_10], 'link') && $child[SIMPLEPIE_NAMESPACE_ATOM_10]['link'])
+ $share['links'] = encode_rel_links($child[SIMPLEPIE_NAMESPACE_ATOM_10]['link']);
+
+ $rawcreated = $rawobj[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['published'];
+
+ if($rawcreated)
+ $share['created'] = unxmlify($rawcreated[0]['data']);
+ else
+ $share['created'] = $res['created'];
+
+ if(x($child[SIMPLEPIE_NAMESPACE_ATOM_10], 'id') && $child[SIMPLEPIE_NAMESPACE_ATOM_10]['id'][0]['data'])
+ $share['message_id'] = unxmlify($child[SIMPLEPIE_NAMESPACE_ATOM_10]['id'][0]['data']);
+
+ if(x($child[SIMPLEPIE_NAMESPACE_ATOM_10], 'content') && $child[SIMPLEPIE_NAMESPACE_ATOM_10]['content'][0]['data']) {
+ $body = unxmlify($child[SIMPLEPIE_NAMESPACE_ATOM_10]['content'][0]['data']);
+ if(! $body)
+ $body = unxmlify($child[SIMPLEPIE_NAMESPACE_ATOM_10]['summary'][0]['data']);
+
+ if((strpos($body,'<') !== false) || (strpos($body,'>') !== false)) {
+ $body = purify_html($body);
+ $body = html2bbcode($body);
+ }
+ }
+
+ $attach = $share['links'];
+
+ if($attach) {
+ foreach($attach as $att) {
+ if($att['rel'] === 'alternate') {
+ $share['alternate'] = str_replace(array(',','"'),array('%2D','%22'),notags(trim(unxmlify($att['href']))));
+ continue;
+ }
+ if($att['rel'] !== 'enclosure')
+ continue;
+ $len = intval($att['length']);
+ $link = str_replace(array(',','"'),array('%2D','%22'),notags(trim(unxmlify($att['href']))));
+ $title = str_replace(array(',','"'),array('%2D','%22'),notags(trim(unxmlify($att['title']))));
+ $type = str_replace(array(',','"'),array('%2D','%22'),notags(trim(unxmlify($att['type']))));
+ if(strpos($type,';'))
+ $type = substr($type,0,strpos($type,';'));
+ if((! $link) || (strpos($link,'http') !== 0))
+ continue;
+
+ if(! $title)
+ $title = ' ';
+ if(! $type)
+ $type = 'application/octet-stream';
+
+ if((strpos($type,'image') === 0) && (strpos($body, ']' . $link . '[/img]') === false) && (strpos($link,'http') === 0)) {
+ $body .= "\n\n" . '[img]' . $link . '[/img]';
+ }
+ if((strpos($type,'video') === 0) && (strpos($body, ']' . $link . '[/video]') === false) && (strpos($link,'http') === 0)) {
+ $body .= "\n\n" . '[video]' . $link . '[/video]';
+ }
+ if((strpos($type,'audio') === 0) && (strpos($body, ']' . $link . '[/audio]') === false) && (strpos($link,'http') === 0)) {
+ $body .= "\n\n" . '[audio]' . $link . '[/audio]';
+ }
+ }
+ }
+
+ if((! $body) && ($share['alternate'])) {
+ $body = $share['alternate'];
+ }
+
+ $res['body'] = "[share author='" . urlencode($share['author']) .
+ "' profile='" . $share['profile'] .
+ "' avatar='" . $share['avatar'] .
+ "' link='" . $share['alternate'] .
+ "' posted='" . $share['created'] .
+ "' message_id='" . $share['message_id'] . "']";
+
+ $res['body'] .= $body;
+ $res['body'] .= "[/share]";
+ }
+
+}
+
+
+
+/**
+ * @brief Encodes SimplePie_Item link arrays.
+ *
+ * @param array $links Array with SimplePie_Item link tags
+ * @return array
+ */
function encode_rel_links($links) {
$o = array();
if(! ((is_array($links)) && (count($links))))
@@ -656,30 +880,70 @@ function encode_rel_links($links) {
$l = array();
if($link['attribs']['']['rel'])
$l['rel'] = $link['attribs']['']['rel'];
+ if($link['attribs']['']['length'])
+ $l['length'] = $link['attribs']['']['length'];
+ if($link['attribs']['']['title'])
+ $l['title'] = $link['attribs']['']['title'];
if($link['attribs']['']['type'])
$l['type'] = $link['attribs']['']['type'];
if($link['attribs']['']['href'])
$l['href'] = $link['attribs']['']['href'];
- if( (x($link['attribs'],NAMESPACE_MEDIA)) && $link['attribs'][NAMESPACE_MEDIA]['width'])
+ if( (x($link['attribs'], NAMESPACE_MEDIA)) && $link['attribs'][NAMESPACE_MEDIA]['width'])
$l['width'] = $link['attribs'][NAMESPACE_MEDIA]['width'];
- if( (x($link['attribs'],NAMESPACE_MEDIA)) && $link['attribs'][NAMESPACE_MEDIA]['height'])
+ if( (x($link['attribs'], NAMESPACE_MEDIA)) && $link['attribs'][NAMESPACE_MEDIA]['height'])
$l['height'] = $link['attribs'][NAMESPACE_MEDIA]['height'];
if($l)
$o[] = $l;
}
+
return $o;
}
+
+function process_feed_tombstones($feed,$importer,$contact,$pass) {
+
+ $arr_deleted = [];
+
+ $del_entries = $feed->get_feed_tags(NAMESPACE_TOMB, 'deleted-entry');
+ if(is_array($del_entries) && count($del_entries) && $pass != 2) {
+ foreach($del_entries as $dentry) {
+ if(isset($dentry['attribs']['']['ref'])) {
+ $arr_deleted[] = normalise_id($dentry['attribs']['']['ref']);
+ }
+ }
+ }
+
+ if($arr_deleted && is_array($contact)) {
+ foreach($arr_deleted as $mid) {
+ $r = q("SELECT * from item where mid = '%s' and author_xchan = '%s' and uid = %d limit 1",
+ dbesc($mid),
+ dbesc($contact['xchan_hash']),
+ intval($importer['channel_id'])
+ );
+
+ if($r) {
+ $item = $r[0];
+
+ if(! intval($item['item_deleted'])) {
+ logger('deleting item ' . $item['id'] . ' mid=' . $item['mid'], LOGGER_DEBUG);
+ drop_item($item['id'],false);
+ }
+ }
+ }
+ }
+}
+
+
/**
* @brief Process atom feed and update anything/everything we might need to update.
*
- * @param array $xml
+ * @param string $xml
* The (atom) feed to consume - RSS isn't as fully supported but may work for simple feeds.
* @param $importer
* The contact_record (joined to user_record) of the local user who owns this
* relationship. It is this person's stuff that is going to be updated.
- * @param $contact
+ * @param[in,out] array $contact
* The person who is sending us stuff. If not set, we MAY be processing a "follow" activity
* from an external network and MAY create an appropriate contact record. Otherwise, we MUST
* have a contact record.
@@ -697,14 +961,12 @@ function encode_rel_links($links) {
*/
function consume_feed($xml, $importer, &$contact, $pass = 0) {
- require_once('library/simplepie/simplepie.inc');
-
if(! strlen($xml)) {
- logger('consume_feed: empty input');
+ logger('Empty input');
return;
}
- $sys_expire = intval(get_config('system','default_expire_days'));
+ $sys_expire = intval(get_config('system', 'default_expire_days'));
$chn_expire = intval($importer['channel_expire_days']);
$expire_days = $sys_expire;
@@ -712,75 +974,54 @@ function consume_feed($xml, $importer, &$contact, $pass = 0) {
if(($chn_expire != 0) && ($chn_expire < $sys_expire))
$expire_days = $chn_expire;
- // logger('expire_days: ' . $expire_days);
-
$feed = new SimplePie();
$feed->set_raw_data($xml);
+
+ // We can preserve iframes because we will strip them in the purifier after
+ // checking for supported video sources.
+ $strip_htmltags = $feed->strip_htmltags;
+ array_splice($strip_htmltags, array_search('iframe', $strip_htmltags), 1);
+ $feed->strip_htmltags($strip_htmltags);
+
$feed->init();
if($feed->error())
- logger('consume_feed: Error parsing XML: ' . $feed->error());
+ logger('Error parsing XML: ' . $feed->error());
$permalink = $feed->get_permalink();
- // Check at the feed level for updated contact name and/or photo
-
- // process any deleted entries
-
- $del_entries = $feed->get_feed_tags(NAMESPACE_TOMB, 'deleted-entry');
- if(is_array($del_entries) && count($del_entries) && $pass != 2) {
- foreach($del_entries as $dentry) {
- $deleted = false;
- if(isset($dentry['attribs']['']['ref'])) {
- $mid = normalise_id($dentry['attribs']['']['ref']);
- $deleted = true;
- if(isset($dentry['attribs']['']['when'])) {
- $when = $dentry['attribs']['']['when'];
- $when = datetime_convert('UTC','UTC', $when, 'Y-m-d H:i:s');
- }
- else
- $when = datetime_convert('UTC','UTC','now','Y-m-d H:i:s');
- }
- if($deleted && is_array($contact)) {
- $r = q("SELECT * from item where mid = '%s' and author_xchan = '%s' and uid = %d limit 1",
- dbesc($mid),
- dbesc($contact['xchan_hash']),
- intval($importer['channel_id'])
- );
+ // Check at the feed level for tombstones
- if($r) {
- $item = $r[0];
+ process_feed_tombstones($feed,$importer,$contact,$pass);
- if(! intval($item['item_deleted'])) {
- logger('consume_feed: deleting item ' . $item['id'] . ' mid=' . $item['mid'], LOGGER_DEBUG);
- drop_item($item['id'],false);
- }
- }
- }
- }
- }
// Now process the feed
if($feed->get_item_quantity()) {
- logger('consume_feed: feed item count = ' . $feed->get_item_quantity(), LOGGER_DEBUG);
+ logger('feed item count = ' . $feed->get_item_quantity(), LOGGER_DEBUG);
$items = $feed->get_items();
foreach($items as $item) {
$is_reply = false;
- $item_id = normalise_id($item->get_id());
+ $send_downstream = false;
+ $parent_link = '';
- logger('consume_feed: processing ' . $raw_item_id, LOGGER_DEBUG);
+ logger('processing ' . $item->get_id(), LOGGER_DEBUG);
$rawthread = $item->get_item_tags( NAMESPACE_THREAD,'in-reply-to');
if(isset($rawthread[0]['attribs']['']['ref'])) {
$is_reply = true;
$parent_mid = normalise_id($rawthread[0]['attribs']['']['ref']);
}
+ if(isset($rawthread[0]['attribs']['']['href'])) {
+ $parent_link = $rawthread[0]['attribs']['']['href'];
+ }
+
+ logger('in-reply-to: ' . $parent_mid, LOGGER_DEBUG);
if($is_reply) {
@@ -789,15 +1030,42 @@ function consume_feed($xml, $importer, &$contact, $pass = 0) {
// Have we seen it? If not, import it.
- $item_id = normalise_id($item->get_id());
$author = array();
$datarray = get_atom_elements($feed,$item,$author);
+ if(! $datarray['mid'])
+ continue;
+
+
+ $item_parent_mid = q("select parent_mid from item where mid = '%s' and uid = %d limit 1",
+ dbesc($parent_mid),
+ intval($importer['channel_id'])
+ );
+
+
+ // This probably isn't an appropriate default but we're about to change it
+ // if it's wrong.
+
+ $datarray['comment_policy'] = 'authenticated';
+
+ // A Mastodon privacy tag has been found. We cannot send private comments
+ // through the OStatus protocol, so block commenting.
+
+ if(array_key_exists('item_private',$datarray) && intval($datarray['item_private'])) {
+ $datarray['public_policy'] = 'specific';
+ $datarray['comment_policy'] = 'none';
+ }
+
if($contact['xchan_network'] === 'rss') {
$datarray['public_policy'] = 'specific';
$datarray['comment_policy'] = 'none';
}
+ // if we have everything but a photo, provide the default profile photo
+
+ if($author['author_name'] && $author['author_link'] && (! $author['author_photo']))
+ $author['author_photo'] = z_root() . '/' . get_default_profile_photo(80);
+
if((! x($author,'author_name')) || ($author['author_is_feed']))
$author['author_name'] = $contact['xchan_name'];
if((! x($author,'author_link')) || ($author['author_is_feed']))
@@ -808,7 +1076,16 @@ function consume_feed($xml, $importer, &$contact, $pass = 0) {
$datarray['author_xchan'] = '';
if($author['author_link'] != $contact['xchan_url']) {
- $x = import_author_unknown(array('name' => $author['author_name'],'url' => $author['author_link'],'photo' => array('src' => $author['author_photo'])));
+ $name = '';
+ if($author['full_name']) {
+ $name = $author['full_name'];
+ if($author['author_name'])
+ $name .= ' (' . $author['author_name'] . ')';
+ }
+ else {
+ $name = $author['author_name'];
+ }
+ $x = import_author_unknown(array('name' => $name,'url' => $author['author_link'],'photo' => array('src' => $author['author_photo'])));
if($x)
$datarray['author_xchan'] = $x;
}
@@ -817,8 +1094,8 @@ function consume_feed($xml, $importer, &$contact, $pass = 0) {
$datarray['owner_xchan'] = $contact['xchan_hash'];
- $r = q("SELECT edited FROM item WHERE mid = '%s' AND uid = %d LIMIT 1",
- dbesc($item_id),
+ $r = q("SELECT id, edited, author_xchan, item_deleted FROM item WHERE mid = '%s' AND uid = %d LIMIT 1",
+ dbesc($datarray['mid']),
intval($importer['channel_id'])
);
@@ -826,6 +1103,15 @@ function consume_feed($xml, $importer, &$contact, $pass = 0) {
// Update content if 'updated' changes
if($r) {
+ if(activity_match($datarray['verb'],ACTIVITY_DELETE)
+ && $datarray['author_xchan'] === $r[0]['author_xchan']) {
+ if(! intval($r[0]['item_deleted'])) {
+ logger('deleting item ' . $r[0]['id'] . ' mid=' . $datarray['mid'], LOGGER_DEBUG);
+ drop_item($r[0]['id'],false);
+ }
+ continue;
+ }
+
if((x($datarray,'edited') !== false)
&& (datetime_convert('UTC','UTC',$datarray['edited']) !== $r[0]['edited'])) {
@@ -833,44 +1119,199 @@ function consume_feed($xml, $importer, &$contact, $pass = 0) {
if(datetime_convert('UTC','UTC',$datarray['edited']) < $r[0]['edited'])
continue;
+ $datarray['uid'] = $importer['channel_id'];
+ $datarray['aid'] = $importer['channel_account_id'];
+ $datarray['id'] = $r[0]['id'];
+
update_feed_item($importer['channel_id'],$datarray);
+
}
continue;
}
- $x = q("select mid from item where mid = '%s' and uid = %d limit 1",
- dbesc($parent_mid),
- intval($importer['channel_id'])
- );
- if($x)
- $parent_mid = $x[0]['mid'];
+ $pmid = '';
+ $conv_id = get_iconfig($datarray,'ostatus','conversation');
+
+ // match conversations - first try ostatus:conversation
+ // next try thr:in_reply_to
+
+ if($conv_id) {
+ logger('find_parent: conversation_id: ' . $conv_id, LOGGER_DEBUG);
+ $c = q("select parent_mid from item left join iconfig on item.id = iconfig.iid where iconfig.cat = 'ostatus' and iconfig.k = 'conversation' and iconfig.v = '%s' and item.uid = %d order by item.id limit 1",
+ dbesc($conv_id),
+ intval($importer['channel_id'])
+ );
+ if($c) {
+ logger('find_parent: matched conversation: ' . $conv_id, LOGGER_DEBUG);
+ $pmid = $c[0]['parent_mid'];
+ $datarray['parent_mid'] = $pmid;
+ }
+ }
+ if(($item_parent_mid) && (! $pmid)) {
+ logger('find_parent: matched in-reply-to: ' . $parent_mid, LOGGER_DEBUG);
+ $pmid = $item_parent_mid[0]['parent_mid'];
+ $datarray['parent_mid'] = $pmid;
+ }
+
+ if((! $pmid) && $parent_link !== '') {
+ $f = feed_conversation_fetch($importer,$contact,$parent_link);
+ if($f) {
+ // check both potential conversation parents again
+ if($conv_id) {
+ $c = q("select parent_mid from item left join iconfig on item.id = iconfig.iid where iconfig.cat = 'ostatus' and iconfig.k = 'conversation' and iconfig.v = '%s' and item.uid = %d order by item.id limit 1",
+ dbesc($conv_id),
+ intval($importer['channel_id'])
+ );
+ if($c) {
+ $pmid = $c[0]['parent_mid'];
+ $datarray['parent_mid'] = $pmid;
+ }
+ }
+ if(! $pmid) {
+ $x = q("select parent_mid from item where mid = '%s' and uid = %d limit 1",
+ dbesc($parent_mid),
+ intval($importer['channel_id'])
+ );
+
+ if($x) {
+ $item_parent_mid = $x;
+ $pmid = $x[0]['parent_mid'];
+ $datarray['parent_mid'] = $pmid;
+ }
+ }
+ }
+
+ // the conversation parent might just be the post we are trying to import.
+ // check existence again in case it was just delivered.
+
+ $r = q("SELECT id FROM item WHERE mid = '%s' AND uid = %d LIMIT 1",
+ dbesc($datarray['mid']),
+ intval($importer['channel_id'])
+ );
+ if($r) {
+ continue;
+ }
+ }
+
+ if($pmid) {
+
+ // check comment permissions on the parent
+
+ $parent_item = 0;
+
+ $r = q("select * from item where parent_mid = '%s' and parent_mid = mid and uid = %d limit 1",
+ dbesc($pmid),
+ intval($importer['channel_id'])
+ );
+ if($r) {
+ $parent_item = $r[0];
+ if(intval($parent_item['item_nocomment']) || $parent_item['comment_policy'] === 'none'
+ || ($parent_item['comments_closed'] > NULL_DATE && $parent_item['comments_closed'] < datetime_convert())) {
+ logger('comments disabled for post ' . $parent_item['mid']);
+ continue;
+ }
+ }
- $datarray['parent_mid'] = $parent_mid;
+ $allowed = false;
+ if($parent_item) {
+ if($parent_item['owner_xchan'] == $importer['channel_hash'])
+ $allowed = perm_is_allowed($importer['channel_id'],$contact['xchan_hash'],'post_comments');
+ else
+ $allowed = true;
+
+ if(! $allowed) {
+ logger('Ignoring this comment author.');
+ $status = 202;
+ continue;
+ }
+
+ // The salmon endpoint sets this to indicate that we should send comments from
+ // interactive feeds (such as OStatus) downstream to our followers
+ // We do not want to set it for non-interactive feeds or conversations we do not own
+
+ if(array_key_exists('send_downstream',$importer) && intval($importer['send_downstream'])
+ && ($parent_item['owner_xchan'] == $importer['channel_hash'])) {
+ $send_downstream = true;
+ }
+ }
+ else {
+ if((! perm_is_allowed($importer['channel_id'],$contact['xchan_hash'],'send_stream')) && (! $importer['system'])) {
+ // @fixme check for and process ostatus autofriend
+ // otherwise
+
+ logger('Ignoring this author.');
+ continue;
+ }
+ }
+ }
+ else {
+
+ // immediate parent wasn't found. Turn into a top-level post if permissions allow
+ // but save the thread_parent in case we need to refer to it later.
+
+ if(! post_is_importable($datarray, $contact))
+ continue;
+ $datarray['parent_mid'] = $datarray['mid'];
+ set_iconfig($datarray,'system','parent_mid',$parent_mid,true);
+ }
+
+
+ // allow likes of comments
+
+ if($item_parent_mid && activity_match($datarray['verb'],ACTVITY_LIKE)) {
+ $datarray['thr_parent'] = $item_parent_mid[0]['parent_mid'];
+ }
$datarray['aid'] = $importer['channel_account_id'];
$datarray['uid'] = $importer['channel_id'];
- logger('consume_feed: ' . print_r($datarray,true),LOGGER_DATA);
+ logger('data: ' . print_r($datarray, true), LOGGER_DATA);
$xx = item_store($datarray);
$r = $xx['item_id'];
+
+ if($send_downstream) {
+ \Zotlabs\Daemon\Master::Summon(array('Notifier', 'comment', $r));
+ }
+
continue;
}
else {
// Head post of a conversation. Have we seen it? If not, import it.
- $item_id = normalise_id($item->get_id());
$author = array();
$datarray = get_atom_elements($feed,$item,$author);
+ if(! $datarray['mid'])
+ continue;
+
+ // This probably isn't an appropriate default but we're about to change it
+ // if it's wrong.
+
+ $datarray['comment_policy'] = 'authenticated';
+
+ // A Mastodon privacy tag has been found. We cannot send private comments
+ // through the OStatus protocol, so block commenting.
+
+ if(array_key_exists('item_private',$datarray) && intval($datarray['item_private'])) {
+ $datarray['public_policy'] = 'specific';
+ $datarray['comment_policy'] = 'none';
+ }
+
if($contact['xchan_network'] === 'rss') {
$datarray['public_policy'] = 'specific';
$datarray['comment_policy'] = 'none';
}
+
+ // if we have everything but a photo, provide the default profile photo
+
+ if($author['author_name'] && $author['author_link'] && (! $author['author_photo']))
+ $author['author_photo'] = z_root() . '/' . get_default_profile_photo(80);
+
if(is_array($contact)) {
if((! x($author,'author_name')) || ($author['author_is_feed']))
$author['author_name'] = $contact['xchan_name'];
@@ -881,24 +1322,23 @@ function consume_feed($xml, $importer, &$contact, $pass = 0) {
}
if((! x($author,'author_name')) || (! x($author,'author_link'))) {
- logger('consume_feed: no author information! ' . print_r($author,true));
+ logger('No author information! ' . print_r($author,true));
continue;
}
$datarray['author_xchan'] = '';
- if(activity_match($datarray['verb'],ACTIVITY_FOLLOW) && $datarray['obj_type'] === ACTIVITY_OBJ_PERSON) {
- $cb = array('item' => $datarray,'channel' => $importer, 'xchan' => null, 'author' => $author, 'caught' => false);
- call_hooks('follow_from_feed',$cb);
- if($cb['caught']) {
- if($cb['return_code'])
- http_status_exit($cb['return_code']);
- continue;
- }
- }
-
if($author['author_link'] != $contact['xchan_url']) {
- $x = import_author_unknown(array('name' => $author['author_name'],'url' => $author['author_link'],'photo' => array('src' => $author['author_photo'])));
+ $name = '';
+ if($author['full_name']) {
+ $name = $author['full_name'];
+ if($author['author_name'])
+ $name .= ' (' . $author['author_name'] . ')';
+ }
+ else {
+ $name = $author['author_name'];
+ }
+ $x = import_author_unknown(array('name' => $name,'url' => $author['author_link'],'photo' => array('src' => $author['author_photo'])));
if($x)
$datarray['author_xchan'] = $x;
}
@@ -916,16 +1356,23 @@ function consume_feed($xml, $importer, &$contact, $pass = 0) {
}
}
-
-
- $r = q("SELECT edited FROM item WHERE mid = '%s' AND uid = %d LIMIT 1",
- dbesc($item_id),
+ $r = q("SELECT id, edited, author_xchan, item_deleted FROM item WHERE mid = '%s' AND uid = %d LIMIT 1",
+ dbesc($datarray['mid']),
intval($importer['channel_id'])
);
// Update content if 'updated' changes
if($r) {
+ if(activity_match($datarray['verb'],ACTIVITY_DELETE)
+ && $datarray['author_xchan'] === $r[0]['author_xchan']) {
+ if(! intval($r[0]['item_deleted'])) {
+ logger('deleting item ' . $r[0]['id'] . ' mid=' . $datarray['mid'], LOGGER_DEBUG);
+ drop_item($r[0]['id'],false);
+ }
+ continue;
+ }
+
if((x($datarray,'edited') !== false)
&& (datetime_convert('UTC','UTC',$datarray['edited']) !== $r[0]['edited'])) {
@@ -933,32 +1380,36 @@ function consume_feed($xml, $importer, &$contact, $pass = 0) {
if(datetime_convert('UTC','UTC',$datarray['edited']) < $r[0]['edited'])
continue;
+ $datarray['uid'] = $importer['channel_id'];
+ $datarray['aid'] = $importer['channel_account_id'];
+ $datarray['id'] = $r[0]['id'];
+
update_feed_item($importer['channel_id'],$datarray);
}
continue;
}
- $datarray['parent_mid'] = $item_id;
+ $datarray['parent_mid'] = $datarray['mid'];
$datarray['uid'] = $importer['channel_id'];
$datarray['aid'] = $importer['channel_account_id'];
- if(! link_compare($author['owner_link'],$contact['xchan_url'])) {
- logger('consume_feed: Correcting item owner.', LOGGER_DEBUG);
+ if(! link_compare($author['owner_link'], $contact['xchan_url'])) {
+ logger('Correcting item owner.', LOGGER_DEBUG);
$author['owner_name'] = $contact['name'];
$author['owner_link'] = $contact['url'];
$author['owner_avatar'] = $contact['thumb'];
}
- if(! post_is_importable($datarray,$contact))
+ if(! post_is_importable($datarray, $contact))
continue;
- logger('consume_feed: author ' . print_r($author,true),LOGGER_DEBUG);
-
- logger('consume_feed: ' . print_r($datarray,true),LOGGER_DATA);
+ logger('author: ' . print_r($author, true), LOGGER_DEBUG);
+ logger('data: ' . print_r($datarray, true), LOGGER_DATA);
$xx = item_store($datarray);
$r = $xx['item_id'];
+
continue;
}
}
@@ -966,27 +1417,76 @@ function consume_feed($xml, $importer, &$contact, $pass = 0) {
}
+function feed_conversation_fetch($importer,$contact,$parent_link) {
+
+ logger('parent_link: ' . $parent_link, LOGGER_DEBUG, LOG_INFO);
+
+ $link = '';
+
+ // GNU-Social flavoured feeds
+ if(strpos($parent_link,'/notice/')) {
+ $link = str_replace('/notice/','/api/statuses/show/',$parent_link) . '.atom';
+ }
+
+ // Mastodon flavoured feeds
+ if(strpos($parent_link,'/users/') && strpos($parent_link,'/updates/')) {
+ $link = $parent_link . '.atom';
+ }
+
+ if(! $link)
+ return false;
+
+ logger('fetching: ' . $link, LOGGER_DEBUG, LOG_INFO);
+
+ $fetch = z_fetch_url($link);
+
+ if(! $fetch['success'])
+ return false;
+
+ $data = $fetch['body'];
+
+ // We will probably receive an atom 'entry' and not an atom 'feed'. Unfortunately
+ // our parser is a bit strict about compliance so we'll insert just enough of a feed
+ // tag to trick it into believing it's a compliant feed.
+
+ if(! strstr($data,'<feed')) {
+ $data = str_replace('<entry ','<feed xmlns="http://www.w3.org/2005/Atom"><entry ',$data);
+ $data .= '</feed>';
+ }
+
+ consume_feed($data,$importer,$contact,1);
+ consume_feed($data,$importer,$contact,2);
+
+ return true;
+
+}
+
+/**
+ * @brief Normalise an id.
+ *
+ * Strip "X-ZOT:" from $id.
+ *
+ * @param string $id
+ * @return string
+ */
function normalise_id($id) {
- return str_replace('X-ZOT:','',$id);
+ return str_replace('X-ZOT:', '', $id);
}
/**
- * @brief Process atom feed and return the first post and structure
+ * @brief Process atom feed and return the first post and structure.
*
- * @param array $xml
+ * @param string $xml
* The (atom) feed to consume - RSS isn't as fully supported but may work for simple feeds.
* @param $importer
* The contact_record (joined to user_record) of the local user who owns this
* relationship. It is this person's stuff that is going to be updated.
*/
-
function process_salmon_feed($xml, $importer) {
$ret = array();
- require_once('library/simplepie/simplepie.inc');
-
if(! strlen($xml)) {
logger('process_feed: empty input');
return;
@@ -994,6 +1494,13 @@ function process_salmon_feed($xml, $importer) {
$feed = new SimplePie();
$feed->set_raw_data($xml);
+
+ // We can preserve iframes because we will strip them in the purifier after
+ // checking for supported video sources.
+ $strip_htmltags = $feed->strip_htmltags;
+ array_splice($strip_htmltags, array_search('iframe', $strip_htmltags), 1);
+ $feed->strip_htmltags($strip_htmltags);
+
$feed->init();
if($feed->error())
@@ -1015,7 +1522,7 @@ function process_salmon_feed($xml, $importer) {
logger('processing ' . $item_id, LOGGER_DEBUG);
- $rawthread = $item->get_item_tags( NAMESPACE_THREAD,'in-reply-to');
+ $rawthread = $item->get_item_tags( NAMESPACE_THREAD, 'in-reply-to');
if(isset($rawthread[0]['attribs']['']['ref'])) {
$is_reply = true;
$parent_mid = normalise_id($rawthread[0]['attribs']['']['ref']);
@@ -1026,94 +1533,111 @@ function process_salmon_feed($xml, $importer) {
$ret['author'] = array();
- $datarray = get_atom_elements($feed,$item,$ret['author']);
+ $datarray = get_atom_elements($feed, $item, $ret['author']);
// reset policies which are restricted by default for RSS connections
- // This item is likely coming from GNU-social via salmon and allows public interaction
+ // This item is likely coming from GNU-social via salmon and allows public interaction
$datarray['public_policy'] = '';
- $datarray['comment_policy'] = '';
+ $datarray['comment_policy'] = 'authenticated';
- $ret['item'] = $datarray;
+ $ret['item'] = $datarray;
}
}
return $ret;
}
-/*
- * Given an xml (atom) feed, find author and hub links
- */
-
+/**
+ * @brief Given an xml (atom) feed, find author and hub links.
+ *
+ * @param string $xml
+ * @return array
+ */
function feed_meta($xml) {
- require_once('library/simplepie/simplepie.inc');
$ret = array();
- if(! strlen($xml)) {
- logger('empty input');
- return $ret;
- }
+ if(! strlen($xml)) {
+ logger('empty input');
+ return $ret;
+ }
- $feed = new SimplePie();
- $feed->set_raw_data($xml);
- $feed->init();
+ $feed = new SimplePie();
+ $feed->set_raw_data($xml);
+ $feed->init();
- if($feed->error()) {
- logger('Error parsing XML: ' . $feed->error());
+ if($feed->error()) {
+ logger('Error parsing XML: ' . $feed->error());
return $ret;
}
- $ret['hubs'] = $feed->get_links('hub');
+ $ret['hubs'] = $feed->get_links('hub');
+
+ //logger('hubs: ' . print_r($hubs,true), LOGGER_DATA);
-// logger('consume_feed: hubs: ' . print_r($hubs,true), LOGGER_DATA);
-
$author = array();
- $found_author = $feed->get_author();
- if($found_author) {
- $author['author_name'] = unxmlify($found_author->get_name());
- $author['author_link'] = unxmlify($found_author->get_link());
+ $found_author = $feed->get_author();
+ if($found_author) {
+ $author['author_name'] = unxmlify($found_author->get_name());
+ $author['author_link'] = unxmlify($found_author->get_link());
- $rawauthor = $feed->get_feed_tags(SIMPLEPIE_NAMESPACE_ATOM_10,'author');
- logger('rawauthor: ' . print_r($rawauthor,true));
+ $rawauthor = $feed->get_feed_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'author');
+ logger('rawauthor: ' . print_r($rawauthor, true));
- if($rawauthor) {
+ if($rawauthor) {
if($rawauthor[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['link']) {
- $base = $rawauthor[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['link'];
- foreach($base as $link) {
- if(!x($author, 'author_photo') || ! $author['author_photo']) {
- if($link['attribs']['']['rel'] === 'photo' || $link['attribs']['']['rel'] === 'avatar') {
- $author['author_photo'] = unxmlify($link['attribs']['']['href']);
+ $base = $rawauthor[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['link'];
+ foreach($base as $link) {
+ if(!x($author, 'author_photo') || ! $author['author_photo']) {
+ if($link['attribs']['']['rel'] === 'photo' || $link['attribs']['']['rel'] === 'avatar') {
+ $author['author_photo'] = unxmlify($link['attribs']['']['href']);
break;
}
- }
- }
+ }
+ }
}
if($rawauthor[0]['child'][NAMESPACE_POCO]['displayName'][0]['data'])
$author['full_name'] = unxmlify($rawauthor[0]['child'][NAMESPACE_POCO]['displayName'][0]['data']);
if($rawauthor[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'])
$author['author_uri'] = unxmlify($rawauthor[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data']);
-
}
- }
-
- if(substr($author['author_link'],-1,1) == '/')
- $author['author_link'] = substr($author['author_link'],0,-1);
+ }
- $ret['author'] = $author;
+ if(! $author['author_photo'])
+ $author['author_photo'] = $feed->get_image_url();
- return $ret;
-}
+ if(substr($author['author_link'],-1,1) == '/')
+ $author['author_link'] = substr($author['author_link'],0,-1);
+ $ret['author'] = $author;
-function update_feed_item($uid,$datarray) {
- logger('update_feed_item: not implemented! ' . $uid . ' ' . print_r($datarray,true), LOGGER_DATA);
+ return $ret;
}
+/**
+ * @brief Not yet implemented function to update feed item.
+ *
+ * @param int $uid
+ * @param array $datarray
+ */
+function update_feed_item($uid, $datarray) {
+ item_store_update($datarray);
+}
-function handle_feed($uid,$abook_id,$url) {
+/**
+ * @brief Fetch the content of a feed and further consume it.
+ *
+ * It will first process parent items and in a second run child items.
+ * @see consume_feed()
+ *
+ * @param int $uid
+ * @param int $abook_id
+ * @param string $url URL of the feed
+ */
+function handle_feed($uid, $abook_id, $url) {
$channel = channelx_by_n($uid);
if(! $channel)
@@ -1125,22 +1649,37 @@ function handle_feed($uid,$abook_id,$url) {
);
$recurse = 0;
- $z = z_fetch_url($url,false,$recurse,array('novalidate' => true));
+ $z = z_fetch_url($url, false, $recurse, array('novalidate' => true));
-//logger('handle_feed:' . print_r($z,true));
+ //logger('data:' . print_r($z, true), LOGGER_DATA);
if($z['success']) {
- consume_feed($z['body'],$channel,$x[0],1);
- consume_feed($z['body'],$channel,$x[0],2);
+ consume_feed($z['body'], $channel, $x[0], 1);
+ consume_feed($z['body'], $channel, $x[0], 2);
}
}
-
-function atom_author($tag,$name,$uri,$h,$w,$type,$photo) {
+/**
+ * @brief Return a XML tag with author information.
+ *
+ * @hooks \b atom_author Possibility to add further tags to returned XML string
+ * * \e string The created XML tag as a string without closing tag
+ * @param string $tag The XML tag to create
+ * @param string $nick preferred username
+ * @param string $name displayed name of the author
+ * @param string $uri
+ * @param int $h image height
+ * @param int $w image width
+ * @param string $type profile photo mime type
+ * @param string $photo Fully qualified URL to a profile/avator photo
+ * @return string
+ */
+function atom_author($tag, $nick, $name, $uri, $h, $w, $type, $photo) {
$o = '';
if(! $tag)
return $o;
+ $nick = xmlify($nick);
$name = xmlify($name);
$uri = xmlify($uri);
$h = intval($h);
@@ -1148,10 +1687,13 @@ function atom_author($tag,$name,$uri,$h,$w,$type,$photo) {
$photo = xmlify($photo);
$o .= "<$tag>\r\n";
- $o .= "<name>$name</name>\r\n";
- $o .= "<uri>$uri</uri>\r\n";
- $o .= '<link rel="photo" type="' . $type . '" media:width="' . $w . '" media:height="' . $h . '" href="' . $photo . '" />' . "\r\n";
- $o .= '<link rel="avatar" type="' . $type . '" media:width="' . $w . '" media:height="' . $h . '" href="' . $photo . '" />' . "\r\n";
+ $o .= " <id>$uri</id>\r\n";
+ $o .= " <name>$nick</name>\r\n";
+ $o .= " <uri>$uri</uri>\r\n";
+ $o .= ' <link rel="photo" type="' . $type . '" media:width="' . $w . '" media:height="' . $h . '" href="' . $photo . '" />' . "\r\n";
+ $o .= ' <link rel="avatar" type="' . $type . '" media:width="' . $w . '" media:height="' . $h . '" href="' . $photo . '" />' . "\r\n";
+ $o .= ' <poco:preferredUsername>' . $nick . '</poco:preferredUsername>' . "\r\n";
+ $o .= ' <poco:displayName>' . $name . '</poco:displayName>' . "\r\n";
call_hooks('atom_author', $o);
@@ -1160,7 +1702,74 @@ function atom_author($tag,$name,$uri,$h,$w,$type,$photo) {
return $o;
}
-function atom_entry($item,$type,$author,$owner,$comment = false,$cid = 0) {
+
+function atom_render_author($tag,$xchan) {
+
+
+ $nick = xmlify(substr($xchan['xchan_addr'],0,strpos($xchan['xchan_addr'],'@')));
+ $id = xmlify($xchan['xchan_url']);
+ $name = xmlify($xchan['xchan_name']);
+ $photo = xmlify($xchan['xchan_photo_l']);
+ $type = xmlify($xchan['xchan_photo_mimetype']);
+ $w = $h = 300;
+
+ $o .= "<$tag>\r\n";
+ $o .= " <as:object-type>http://activitystrea.ms/schema/1.0/person</as:object-type>\r\n";
+ $o .= " <id>$id</id>\r\n";
+ $o .= " <name>$nick</name>\r\n";
+ $o .= " <uri>$id</uri>\r\n";
+ $o .= ' <link rel="alternate" type="text/html" href="' . $id . '" />' . "\r\n";
+ $o .= ' <link rel="photo" type="' . $type . '" media:width="' . $w . '" media:height="' . $h . '" href="' . $photo . '" />' . "\r\n";
+ $o .= ' <link rel="avatar" type="' . $type . '" media:width="' . $w . '" media:height="' . $h . '" href="' . $photo . '" />' . "\r\n";
+ $o .= ' <poco:preferredUsername>' . $nick . '</poco:preferredUsername>' . "\r\n";
+ $o .= ' <poco:displayName>' . $name . '</poco:displayName>' . "\r\n";
+
+ call_hooks('atom_render_author', $o);
+
+ $o .= "</$tag>\r\n";
+
+ return $o;
+
+
+}
+
+function compat_photos_list($s) {
+
+ $ret = [];
+
+ $found = preg_match_all('/\[[zi]mg(.*?)\](.*?)\[/ism',$s,$matches,PREG_SET_ORDER);
+
+ if($found) {
+ foreach($matches as $match) {
+ $ret[] = [
+ 'href' => $match[2],
+ 'length' => 0,
+ 'type' => guess_image_type($match[2])
+ ];
+
+ }
+ }
+
+ return $ret;
+}
+
+
+
+/**
+ * @brief Create an item for the Atom feed.
+ *
+ * @see get_feed_for()
+ *
+ * @param array $item
+ * @param string $type
+ * @param array $author
+ * @param array $owner
+ * @param string $comment default false
+ * @param number $cid default 0
+ * @return void|string
+ */
+function atom_entry($item, $type, $author, $owner, $comment = false, $cid = 0, $compat = false) {
+
if(! $item['parent'])
return;
@@ -1168,7 +1777,6 @@ function atom_entry($item,$type,$author,$owner,$comment = false,$cid = 0) {
if($item['deleted'])
return '<at:deleted-entry ref="' . xmlify($item['mid']) . '" when="' . xmlify(datetime_convert('UTC','UTC',$item['edited'] . '+00:00',ATOM_TIME)) . '" />' . "\r\n";
-
create_export_photo_body($item);
if($item['allow_cid'] || $item['allow_gid'] || $item['deny_cid'] || $item['deny_gid'])
@@ -1176,24 +1784,36 @@ function atom_entry($item,$type,$author,$owner,$comment = false,$cid = 0) {
else
$body = $item['body'];
+ if($compat) {
+ $compat_photos = compat_photos_list($body);
+ }
+ else {
+ $compat_photos = null;
+ }
+
$o = "\r\n\r\n<entry>\r\n";
- if(is_array($author))
- $o .= atom_author('author',$author['xchan_name'],$author['xchan_url'],80,80,$author['xchan_photo_mimetype'],$author['xchan_photo_m']);
- else
- $o .= atom_author('author',$item['author']['xchan_name'],$item['author']['xchan_url'],80,80,$item['author']['xchan_photo_mimetype'], $item['author']['xchan_photo_m']);
+ if(is_array($author)) {
+ $o .= atom_render_author('author',$author);
+ }
+ else {
+ $o .= atom_render_author('author',$item['author']);
+ }
- $o .= atom_author('zot:owner',$item['owner']['xchan_name'],$item['owner']['xchan_url'],80,80,$item['owner']['xchan_photo_mimetype'],$item['owner']['xchan_photo_m']);
+ $o .= atom_render_author('zot:owner',$item['owner']);
if(($item['parent'] != $item['id']) || ($item['parent_mid'] !== $item['mid']) || (($item['thr_parent'] !== '') && ($item['thr_parent'] !== $item['mid']))) {
$parent_item = (($item['thr_parent']) ? $item['thr_parent'] : $item['parent_mid']);
- $o .= '<thr:in-reply-to ref="' . 'X-ZOT:' . xmlify($parent_item) . '" type="text/html" href="' . xmlify($item['plink']) . '" />' . "\r\n";
+ // ensure it's a legal uri and not just a message-id
+ if(! strpos($parent_item,':'))
+ $parent_item = 'X-ZOT:' . $parent_item;
+ $o .= '<thr:in-reply-to ref="' . xmlify($parent_item) . '" type="text/html" href="' . xmlify($item['plink']) . '" />' . "\r\n";
}
if(activity_match($item['obj_type'],ACTIVITY_OBJ_EVENT) && activity_match($item['verb'],ACTIVITY_POST)) {
$obj = ((is_array($item['obj'])) ? $item['obj'] : json_decode($item['obj'],true));
-
+
$o .= '<title>' . xmlify($item['title']) . '</title>' . "\r\n";
$o .= '<summary xmlns="urn:ietf:params:xml:ns:xcal">' . xmlify(bbcode($obj['title'])) . '</summary>' . "\r\n";
$o .= '<dtstart xmlns="urn:ietf:params:xml:ns:xcal">' . datetime_convert('UTC','UTC', $obj['dtstart'],'Ymd\\THis' . (($obj['adjust']) ? '\\Z' : '')) . '</dtstart>' . "\r\n";
@@ -1231,28 +1851,37 @@ function atom_entry($item,$type,$author,$owner,$comment = false,$cid = 0) {
$actobj = construct_activity_object($item);
if(strlen($actobj))
$o .= $actobj;
+
$actarg = construct_activity_target($item);
if(strlen($actarg))
$o .= $actarg;
-
if($item['attach']) {
- $enclosures = json_decode($item['attach'],true);
+ $enclosures = json_decode($item['attach'], true);
if($enclosures) {
foreach($enclosures as $enc) {
$o .= '<link rel="enclosure" '
. (($enc['href']) ? 'href="' . $enc['href'] . '" ' : '')
. (($enc['length']) ? 'length="' . $enc['length'] . '" ' : '')
. (($enc['type']) ? 'type="' . $enc['type'] . '" ' : '')
- . ' />';
+ . ' />' . "\r\n";
}
}
}
+ if($compat_photos) {
+ foreach($compat_photos as $enc) {
+ $o .= '<link rel="enclosure" '
+ . (($enc['href']) ? 'href="' . $enc['href'] . '" ' : '')
+ . ((array_key_exists('length',$enc)) ? 'length="' . $enc['length'] . '" ' : '')
+ . (($enc['type']) ? 'type="' . $enc['type'] . '" ' : '')
+ . ' />' . "\r\n";
+ }
+ }
if($item['term']) {
foreach($item['term'] as $term) {
$scheme = '';
- $label = '';
+ $label = '';
switch($term['ttype']) {
case TERM_UNKNOWN:
$scheme = NAMESPACE_ZOT . '/term/unknown';
@@ -1283,104 +1912,19 @@ function atom_entry($item,$type,$author,$owner,$comment = false,$cid = 0) {
$o .= '</entry>' . "\r\n";
- $x = [
- 'item' => $item,
- 'type' => $type,
- 'author' => $author,
- 'owner' => $owner,
- 'comment' => $comment,
- 'abook_id' => $cid,
- 'entry' => $o
+ // build array to pass to hook
+ $x = [
+ 'item' => $item,
+ 'type' => $type,
+ 'author' => $author,
+ 'owner' => $owner,
+ 'comment' => $comment,
+ 'abook_id' => $cid,
+ 'entry' => $o
];
-
call_hooks('atom_entry', $x);
return $x['entry'];
}
-
-function gen_asld($items) {
- $ret = array();
- if(! $items)
- return $ret;
- foreach($items as $item) {
- $ret[] = i2asld($item);
- }
- return $ret;
-}
-
-
-function i2asld($i) {
-
- if(! $i)
- return array();
-
- $ret = array();
-
- $ret['@context'] = array( 'http://www.w3.org/ns/activitystreams', 'zot' => 'http://purl.org/zot/protocol');
-
- if($i['verb']) {
- if(strpos(dirname($i['verb'],'activitystrea.ms/schema/1.0'))) {
- $ret['@type'] = ucfirst(basename($i['verb']));
- }
- elseif(strpos(dirname($i['verb'],'purl.org/zot'))) {
- $ret['@type'] = 'zot:' . ucfirst(basename($i['verb']));
- }
- }
- $ret['@id'] = $i['plink'];
-
- $ret['published'] = datetime_convert('UTC','UTC',$i['created'],ATOM_TIME);
-
- // we need to pass the parent into this
-// if($i['id'] != $i['parent'] && $i['obj_type'] === ACTIVITY_OBJ_NOTE) {
-// $ret['inReplyTo'] = asencode_note
-// }
-
- if($i['obj_type'] === ACTIVITY_OBJ_NOTE)
- $ret['object'] = asencode_note($i);
-
-
- $ret['actor'] = asencode_person($i['author']);
-
-
- return $ret;
-
-}
-
-function asencode_note($i) {
-
- $ret = array();
-
- $ret['@type'] = 'Note';
- $ret['@id'] = $i['plink'];
- if($i['title'])
- $ret['title'] = bbcode($i['title']);
- $ret['content'] = bbcode($i['body']);
- $ret['zot:owner'] = asencode_person($i['owner']);
- $ret['published'] = datetime_convert('UTC','UTC',$i['created'],ATOM_TIME);
- if($i['created'] !== $i['edited'])
- $ret['updated'] = datetime_convert('UTC','UTC',$i['edited'],ATOM_TIME);
-
- return $ret;
-}
-
-
-function asencode_person($p) {
- $ret = array();
- $ret['@type'] = 'Person';
- $ret['@id'] = 'acct:' . $p['xchan_addr'];
- $ret['displayName'] = $p['xchan_name'];
- $ret['icon'] = array(
- '@type' => 'Link',
- 'mediaType' => $p['xchan_photo_mimetype'],
- 'href' => $p['xchan_photo_m']
- );
- $ret['url'] = array(
- '@type' => 'Link',
- 'mediaType' => 'text/html',
- 'href' => $p['xchan_url']
- );
-
- return $ret;
-}
diff --git a/include/follow.php b/include/follow.php
index 751d86db1..56d8294c5 100644
--- a/include/follow.php
+++ b/include/follow.php
@@ -17,6 +17,17 @@ function new_contact($uid,$url,$channel,$interactive = false, $confirm = false)
$my_perms = false;
$is_zot = false;
+ $protocol = '';
+
+
+ if(substr($url,0,1) === '[') {
+ $x = strpos($url,']');
+ if($x) {
+ $protocol = substr($url,1,$x-1);
+ $url = substr($url,$x+1);
+ }
+ }
+
$is_http = ((strpos($url,'://') !== false) ? true : false);
if($is_http && substr($url,-1,1) === '/')
@@ -47,13 +58,13 @@ function new_contact($uid,$url,$channel,$interactive = false, $confirm = false)
}
- $arr = array('url' => $url, 'channel' => array());
+ $arr = array('url' => $url, 'protocol', 'channel' => array());
- call_hooks('follow', $arr);
+ call_hooks('follow_init', $arr);
if($arr['channel']['success'])
$ret = $arr['channel'];
- elseif(! $is_http)
+ elseif((! $is_http) && ((! $protocol) || (strtolower($protocol) === 'zot')))
$ret = Zotlabs\Zot\Finger::run($url,$channel);
if($ret && is_array($ret) && $ret['success']) {
@@ -118,26 +129,31 @@ function new_contact($uid,$url,$channel,$interactive = false, $confirm = false)
else {
$xchan_hash = '';
+ $sql_options = (($protocol) ? " and xchan_network = '" . dbesc($protocol) . "' " : '');
+
- $r = q("select * from xchan where xchan_hash = '%s' or xchan_url = '%s' limit 1",
+ $r = q("select * from xchan where xchan_hash = '%s' or xchan_url = '%s' $sql_options limit 1",
dbesc($url),
dbesc($url)
);
if(! $r) {
+
// attempt network auto-discovery
- $d = discover_by_webbie($url);
+ $d = discover_by_webbie($url,$protocol);
if((! $d) && ($is_http)) {
// try RSS discovery
- if(get_config('system','feed_contacts')) {
+ $feeds = get_config('system','feed_contacts');
+
+ if(($feeds) && ($protocol === '' || $protocol === 'feed')) {
$d = discover_by_url($url);
}
else {
- $result['message'] = t('Protocol disabled.');
+ $result['message'] = t('Remote channel or protocol unavailable.');
return $result;
}
}
@@ -182,6 +198,11 @@ function new_contact($uid,$url,$channel,$interactive = false, $confirm = false)
$hash = get_observer_hash();
$default_group = $channel['channel_default_group'];
+ if($hash == $xchan_hash) {
+ $result['message'] = t('Cannot connect to yourself.');
+ return $result;
+ }
+
if($xchan['xchan_network'] === 'rss') {
// check service class feed limits
@@ -196,28 +217,22 @@ function new_contact($uid,$url,$channel,$interactive = false, $confirm = false)
$result['message'] = upgrade_message();
return $result;
}
- }
- if($hash == $xchan_hash) {
- $result['message'] = t('Cannot connect to yourself.');
- return $result;
+ // Always set these "remote" permissions for feeds since we cannot interact with them
+ // to negotiate a suitable permission response
+
+ set_abconfig($uid,$xchan_hash,'their_perms','view_stream',1);
+ set_abconfig($uid,$xchan_hash,'their_perms','republish',1);
+
}
+
$r = q("select abook_id, abook_xchan, abook_pending, abook_instance from abook
where abook_xchan = '%s' and abook_channel = %d limit 1",
dbesc($xchan_hash),
intval($uid)
);
- if($is_http) {
-
- // Always set these "remote" permissions for feeds since we cannot interact with them
- // to negotiate a suitable permission response
-
- set_abconfig($uid,$xchan_hash,'their_perms','view_stream',1);
- set_abconfig($uid,$xchan_hash,'their_perms','republish',1);
- }
-
if($r) {
$abook_instance = $r[0]['abook_instance'];
@@ -226,12 +241,12 @@ function new_contact($uid,$url,$channel,$interactive = false, $confirm = false)
if($abook_instance)
$abook_instance .= ',';
$abook_instance .= z_root();
- }
- $x = q("update abook set abook_instance = '%s' where abook_id = %d",
- dbesc($abook_instance),
- intval($r[0]['abook_id'])
- );
+ $x = q("update abook set abook_instance = '%s', abook_not_here = 0 where abook_id = %d",
+ dbesc($abook_instance),
+ intval($r[0]['abook_id'])
+ );
+ }
if(intval($r[0]['abook_pending'])) {
$x = q("update abook set abook_pending = 0 where abook_id = %d",
@@ -250,7 +265,7 @@ function new_contact($uid,$url,$channel,$interactive = false, $confirm = false)
'abook_channel' => intval($uid),
'abook_closeness' => intval($closeness),
'abook_xchan' => $xchan_hash,
- 'abook_feed' => intval(($is_http) ? 1 : 0),
+ 'abook_feed' => intval(($xchan['xchan_network'] === 'rss') ? 1 : 0),
'abook_created' => datetime_convert(),
'abook_updated' => datetime_convert(),
'abook_instance' => (($singleton) ? z_root() : '')
diff --git a/include/group.php b/include/group.php
index 3b208ef95..e0c20b536 100644
--- a/include/group.php
+++ b/include/group.php
@@ -278,8 +278,9 @@ function group_side($every="connections",$each="group",$edit = false, $group_id
$o = '';
- if(! (local_channel() && feature_enabled(local_channel(),'groups')))
+ if(! (local_channel() && feature_enabled(local_channel(),'groups'))) {
return '';
+ }
$groups = array();
diff --git a/include/help.php b/include/help.php
index 6e779f000..02c3cb8e4 100644
--- a/include/help.php
+++ b/include/help.php
@@ -1,5 +1,7 @@
<?php
+use \Michelf\MarkdownExtra;
+
/**
* @brief
*
@@ -15,7 +17,7 @@ function get_help_content($tocpath = false) {
$text = '';
$path = (($tocpath !== false) ? $tocpath : '');
-
+
if($tocpath === false && argc() > 1) {
$path = '';
for($x = 1; $x < argc(); $x ++) {
@@ -26,10 +28,23 @@ function get_help_content($tocpath = false) {
}
if($path) {
+
$title = basename($path);
if(! $tocpath)
\App::$page['title'] = t('Help:') . ' ' . ucwords(str_replace('-',' ',notags($title)));
+ // Check that there is a "toc" or "sitetoc" located at the specified path.
+ // If there is not, then there was not a translation of the table of contents
+ // available and so default back to the English TOC at /doc/toc.{html,bb,md}
+ // TODO: This is incompatible with the hierarchical TOC construction
+ // defined in /Zotlabs/Widget/Helpindex.php.
+ if($tocpath !== false &&
+ load_doc_file('doc/' . $path . '.md') === '' &&
+ load_doc_file('doc/' . $path . '.bb') === '' &&
+ load_doc_file('doc/' . $path . '.html') === ''
+ ) {
+ $path = $title;
+ }
$text = load_doc_file('doc/' . $path . '.md');
if(! $text) {
@@ -55,7 +70,7 @@ function get_help_content($tocpath = false) {
if(! $text) {
$doctype = 'bbcode';
$text = load_doc_file('doc/main.bb');
- goaway('/help/about/about_hubzilla');
+ goaway('/help/about/about');
\App::$page['title'] = t('Help');
}
@@ -69,12 +84,11 @@ function get_help_content($tocpath = false) {
}
if($doctype === 'html')
- $content = parseIdentityAwareHTML($text);
- if($doctype === 'markdown') {
- require_once('library/markdown.php');
+ $content = parseIdentityAwareHTML($text);
+ if($doctype === 'markdown') {
# escape #include tags
$text = preg_replace('/#include/ism', '%%include', $text);
- $content = Markdown($text);
+ $content = MarkdownExtra::defaultTransform($text);
$content = preg_replace('/%%include/ism', '#include', $content);
}
if($doctype === 'bbcode') {
@@ -99,26 +113,62 @@ function preg_callback_help_include($matches) {
$include = str_replace(' target="_blank"','',$include);
}
elseif(preg_match('/\.md$/', $matches[1])) {
- require_once('library/markdown.php');
- $include = Markdown($include);
+ $include = MarkdownExtra::defaultTransform($include);
}
return $include;
}
}
-
+function determine_help_language() {
+ require_once('Text/LanguageDetect.php');
+ $lang_detect = new Text_LanguageDetect();
+ // Set this mode to recognize language by the short code like "en", "ru", etc.
+ $lang_detect->setNameMode(2);
+ // If the language was specified in the URL, override the language preference
+ // of the browser. Default to English if both of these are absent.
+ if($lang_detect->languageExists(argv(1))) {
+ $lang = argv(1);
+ $from_url = true;
+ } else {
+ $lang = \App::$language;
+ if(! isset($lang))
+ $lang = 'en';
+ $from_url = false;
+ }
+ return array('language' => $lang, 'from_url' => $from_url);
+}
function load_doc_file($s) {
- $lang = \App::$language;
- if(! isset($lang))
- $lang = 'en';
- $b = basename($s);
- $d = dirname($s);
+ $path = 'doc';
+ // Determine the language and modify the path accordingly
+ $x = determine_help_language();
+ $lang = $x['language'];
+ $url_idx = ($x['from_url'] ? 1 : 0);
+ // The English translation is at the root of /doc/. Other languages are in
+ // subfolders named by the language code such as "de", "es", etc.
+ if($lang !== 'en') {
+ $path .= '/' . $lang;
+ }
- $c = find_doc_file("$d/$lang/$b");
+ $b = basename($s);
+
+ for($i=1+$url_idx; $i<argc()-1; $i++) {
+ $path .= '/' . argv($i);
+ }
+ $c = find_doc_file($path . '/' . $b);
+ if($c)
+ return $c;
+ // Possibly a translation was requested that has not been translated, so fall
+ // back to the English version
+ $path = 'doc';
+ for($i=1+$url_idx; $i<argc()-1; $i++) {
+ $path .= '/' . argv($i);
+ }
+ $c = find_doc_file($path . '/' . $b);
if($c)
return $c;
+ // Try one last time to find the file at the explicit path input to the function
$c = find_doc_file($s);
if($c)
return $c;
@@ -140,8 +190,8 @@ function find_doc_file($s) {
*/
function search_doc_files($s) {
- $itemspage = get_pconfig(local_channel(),'system','itemspage');
- \App::set_pager_itemspage(((intval($itemspage)) ? $itemspage : 20));
+
+ \App::set_pager_itemspage(60);
$pager_sql = sprintf(" LIMIT %d OFFSET %d ", intval(\App::$pager['itemspage']), intval(\App::$pager['start']));
$regexop = db_getfunc('REGEXP');
@@ -198,6 +248,7 @@ function doc_rank_sort($s1, $s2) {
*
* @return string
*/
+
function load_context_help() {
$path = App::$cmd;
diff --git a/include/html2bbcode.php b/include/html2bbcode.php
index 29880a627..d7fbd8660 100644
--- a/include/html2bbcode.php
+++ b/include/html2bbcode.php
@@ -87,9 +87,6 @@ function deletenode(&$doc, $node)
function html2bbcode($message)
{
- //$file = tempnam("/tmp/", "html");
- //file_put_contents($file, $message);
-
$message = str_replace("\r", "", $message);
$message = str_replace(array(
diff --git a/include/hubloc.php b/include/hubloc.php
index e17be028c..0daa5908c 100644
--- a/include/hubloc.php
+++ b/include/hubloc.php
@@ -1,6 +1,17 @@
-<?php /** @file */
-
-
+<?php
+/**
+ * @file include/hubloc.php
+ * @brief Hubloc related functions.
+ */
+
+/**
+ * @brief Create an array for hubloc table and insert record.
+ *
+ * Creates an assoziative array which will be inserted into the hubloc table.
+ *
+ * @param array $arr An assoziative array with hubloc values
+ * @return boolean|PDOStatement
+ */
function hubloc_store_lowlevel($arr) {
$store = [
@@ -25,12 +36,38 @@ function hubloc_store_lowlevel($arr) {
'hubloc_deleted' => ((array_key_exists('hubloc_deleted',$arr)) ? $arr['hubloc_deleted'] : 0)
];
- return create_table_from_array('hubloc',$store);
+ return create_table_from_array('hubloc', $store);
+}
+
+function site_store_lowlevel($arr) {
+ $store = [
+ 'site_url' => ((array_key_exists('site_url',$arr)) ? $arr['site_url'] : ''),
+ 'site_access' => ((array_key_exists('site_access',$arr)) ? $arr['site_access'] : 0),
+ 'site_flags' => ((array_key_exists('site_flags',$arr)) ? $arr['site_flags'] : 0),
+ 'site_update' => ((array_key_exists('site_update',$arr)) ? $arr['site_update'] : NULL_DATE),
+ 'site_pull' => ((array_key_exists('site_pull',$arr)) ? $arr['site_pull'] : NULL_DATE),
+ 'site_sync' => ((array_key_exists('site_sync',$arr)) ? $arr['site_sync'] : NULL_DATE),
+ 'site_directory' => ((array_key_exists('site_directory',$arr)) ? $arr['site_directory'] : ''),
+ 'site_register' => ((array_key_exists('site_register',$arr)) ? $arr['site_register'] : 0),
+ 'site_sellpage' => ((array_key_exists('site_sellpage',$arr)) ? $arr['site_sellpage'] : ''),
+ 'site_location' => ((array_key_exists('site_location',$arr)) ? $arr['site_location'] : ''),
+ 'site_realm' => ((array_key_exists('site_realm',$arr)) ? $arr['site_realm'] : ''),
+ 'site_valid' => ((array_key_exists('site_valid',$arr)) ? $arr['site_valid'] : 0),
+ 'site_dead' => ((array_key_exists('site_dead',$arr)) ? $arr['site_dead'] : 0),
+ 'site_type' => ((array_key_exists('site_type',$arr)) ? $arr['site_type'] : 0),
+ 'site_project' => ((array_key_exists('site_project',$arr)) ? $arr['site_project'] : ''),
+ 'site_version' => ((array_key_exists('site_version',$arr)) ? $arr['site_version'] : ''),
+ 'site_crypto' => ((array_key_exists('site_crypto',$arr)) ? $arr['site_crypto'] : '')
+ ];
+
+ return create_table_from_array('site', $store);
}
+
+
function prune_hub_reinstalls() {
$r = q("select site_url from site where site_type = %d",
@@ -45,9 +82,8 @@ function prune_hub_reinstalls() {
// see if this url has more than one sitekey, indicating it has been re-installed.
if(count($x) > 1) {
-
- $d1 = datetime_convert('UTC','UTC',$x[0]['c']);
- $d2 = datetime_convert('UTC','UTC','now - 3 days');
+ $d1 = datetime_convert('UTC', 'UTC', $x[0]['c']);
+ $d2 = datetime_convert('UTC', 'UTC', 'now - 3 days');
// allow some slop period, say 3 days - just in case this is a glitch or transient occurrence
// Then remove any hublocs pointing to the oldest entry.
@@ -63,18 +99,22 @@ function prune_hub_reinstalls() {
}
}
-function remove_obsolete_hublocs() {
-
- logger('remove_obsolete_hublocs',LOGGER_DEBUG);
- // Get rid of any hublocs which are ours but aren't valid anymore -
- // e.g. they point to a different and perhaps transient URL that we aren't using.
+/**
+ * @brief Remove obsolete hublocs.
+ *
+ * Get rid of any hublocs which are ours but aren't valid anymore -
+ * e.g. they point to a different and perhaps transient URL that we aren't using.
+ *
+ * I need to stress that this shouldn't happen. fix_system_urls() fixes hublocs
+ * when it discovers the URL has changed. So it's unclear how we could end up
+ * with URLs pointing to the old site name. But it happens. This may be an artifact
+ * of an old bug or maybe a regression in some newer code. In any event, they
+ * mess up communications and we have to take action if we find any.
+ */
+function remove_obsolete_hublocs() {
- // I need to stress that this shouldn't happen. fix_system_urls() fixes hublocs
- // when it discovers the URL has changed. So it's unclear how we could end up
- // with URLs pointing to the old site name. But it happens. This may be an artifact
- // of an old bug or maybe a regression in some newer code. In any event, they
- // mess up communications and we have to take action if we find any.
+ logger('remove_obsolete_hublocs', LOGGER_DEBUG);
// First make sure we have any hublocs (at all) with this URL and sitekey.
// We don't want to perform this operation while somebody is in the process
@@ -82,27 +122,25 @@ function remove_obsolete_hublocs() {
$r = q("select hubloc_id from hubloc where hubloc_url = '%s' and hubloc_sitekey = '%s'",
dbesc(z_root()),
- dbesc(get_config('system','pubkey'))
+ dbesc(get_config('system', 'pubkey'))
);
if((! $r) || (! count($r)))
return;
- $channels = array();
-
// Good. We have at least one *valid* hubloc.
// Do we have any invalid ones?
$r = q("select hubloc_id from hubloc where hubloc_sitekey = '%s' and hubloc_url != '%s'",
- dbesc(get_config('system','pubkey')),
+ dbesc(get_config('system', 'pubkey')),
dbesc(z_root())
);
$p = q("select hubloc_id from hubloc where hubloc_sitekey != '%s' and hubloc_url = '%s'",
- dbesc(get_config('system','pubkey')),
+ dbesc(get_config('system', 'pubkey')),
dbesc(z_root())
);
if(is_array($r) && is_array($p))
- $r = array_merge($r,$p);
+ $r = array_merge($r, $p);
if(! $r)
return;
@@ -111,8 +149,8 @@ function remove_obsolete_hublocs() {
logger('remove_obsolete_hublocs: removing ' . count($r) . ' hublocs.');
- $interval = ((get_config('system','delivery_interval') !== false)
- ? intval(get_config('system','delivery_interval')) : 2 );
+ $interval = ((get_config('system', 'delivery_interval') !== false)
+ ? intval(get_config('system', 'delivery_interval')) : 2 );
foreach($r as $rr) {
q("update hubloc set hubloc_deleted = 1 where hubloc_id = %d",
@@ -120,10 +158,10 @@ function remove_obsolete_hublocs() {
);
$x = q("select channel_id from channel where channel_hash = '%s' limit 1",
- dbesc($rr['hubloc_hash'])
+ dbesc($rr['hubloc_hash'])
);
if($x) {
- Zotlabs\Daemon\Master::Summon(array('Notifier','location',$x[0]['channel_id']));
+ Zotlabs\Daemon\Master::Summon(array('Notifier', 'location', $x[0]['channel_id']));
if($interval)
@time_sleep_until(microtime(true) + (float) $interval);
}
@@ -131,8 +169,15 @@ function remove_obsolete_hublocs() {
}
-// This actually changes other structures to match the given (presumably current) hubloc primary selection
-
+/**
+ * @brief Change primary hubloc.
+ *
+ * This actually changes other structures to match the given (presumably current)
+ * hubloc primary selection.
+ *
+ * @param array $hubloc
+ * @return boolean
+ */
function hubloc_change_primary($hubloc) {
if(! is_array($hubloc)) {
@@ -170,7 +215,7 @@ function hubloc_change_primary($hubloc) {
dbesc($hubloc['hubloc_hash'])
);
if(! $r) {
- logger('xchan not found');
+ logger('xchan not found');
return false;
}
if($r[0]['xchan_addr'] === $hubloc['hubloc_addr']) {
@@ -179,7 +224,7 @@ function hubloc_change_primary($hubloc) {
}
$url = $hubloc['hubloc_url'];
- $lwebbie = substr($hubloc['hubloc_addr'],0,strpos($hubloc['hubloc_addr'],'@'));
+ $lwebbie = substr($hubloc['hubloc_addr'], 0, strpos($hubloc['hubloc_addr'], '@'));
$r = q("update xchan set xchan_addr = '%s', xchan_url = '%s', xchan_follow = '%s', xchan_connurl = '%s' where xchan_hash = '%s'",
dbesc($hubloc['hubloc_addr']),
@@ -191,14 +236,19 @@ function hubloc_change_primary($hubloc) {
if(! $r)
logger('xchan_update failed.');
- logger('primary hubloc changed.' . print_r($hubloc,true),LOGGER_DEBUG);
+ logger('primary hubloc changed.' . print_r($hubloc, true), LOGGER_DEBUG);
return true;
-
}
-// We use the post url to distinguish between http and https hublocs.
-// The https might be alive, and the http dead.
+/**
+ * @brief Mark a hubloc as down.
+ *
+ * We use the post url to distinguish between http and https hublocs.
+ * The https might be alive, and the http dead.
+ *
+ * @param string $posturl Hubloc callback url which to disable
+ */
function hubloc_mark_as_down($posturl) {
$r = q("update hubloc set hubloc_status = ( hubloc_status | %d ) where hubloc_callback = '%s'",
intval(HUBLOC_OFFLINE),
@@ -208,22 +258,21 @@ function hubloc_mark_as_down($posturl) {
-
function ping_site($url) {
$ret = array('success' => false);
$sys = get_sys_channel();
- $m = zot_build_packet($sys,'ping');
- $r = zot_zot($url . '/post',$m);
+ $m = zot_build_packet($sys, 'ping');
+ $r = zot_zot($url . '/post', $m);
if(! $r['success']) {
$ret['message'] = 'no answer from ' . $url;
return $ret;
}
- $packet_result = json_decode($r['body'],true);
+ $packet_result = json_decode($r['body'], true);
if(! $packet_result['success']) {
- $ret['message'] = 'packet failure from ' . $url;
+ $ret['message'] = 'packet failure from ' . $url;
return $ret;
}
diff --git a/include/import.php b/include/import.php
index 5c73b7ca3..702fa7e54 100644
--- a/include/import.php
+++ b/include/import.php
@@ -1,8 +1,19 @@
<?php
+use Zotlabs\Lib\IConfig;
+
require_once('include/menu.php');
require_once('include/perm_upgrade.php');
+
+/**
+ * @brief Import a channel.
+ *
+ * @param array $channel
+ * @param int $account_id
+ * @param int $seize
+ * @return boolean|array
+ */
function import_channel($channel, $account_id, $seize) {
if(! array_key_exists('channel_system',$channel)) {
@@ -51,7 +62,7 @@ function import_channel($channel, $account_id, $seize) {
notice( t('Unable to create a unique channel address. Import failed.') . EOL);
return false;
}
- }
+ }
}
unset($channel['channel_id']);
@@ -66,12 +77,12 @@ function import_channel($channel, $account_id, $seize) {
// remove all the permissions related settings, we will import/upgrade them after the channel
// is created.
- $disallowed = [
- 'channel_id', 'channel_r_stream', 'channel_r_profile', 'channel_r_abook',
- 'channel_r_storage', 'channel_r_pages', 'channel_w_stream', 'channel_w_wall',
- 'channel_w_comment', 'channel_w_mail', 'channel_w_like', 'channel_w_tagwall',
- 'channel_w_chat', 'channel_w_storage', 'channel_w_pages', 'channel_a_republish',
- 'channel_a_delegate', 'perm_limits'
+ $disallowed = [
+ 'channel_id', 'channel_r_stream', 'channel_r_profile', 'channel_r_abook',
+ 'channel_r_storage', 'channel_r_pages', 'channel_w_stream', 'channel_w_wall',
+ 'channel_w_comment', 'channel_w_mail', 'channel_w_like', 'channel_w_tagwall',
+ 'channel_w_chat', 'channel_w_storage', 'channel_w_pages', 'channel_a_republish',
+ 'channel_a_delegate', 'perm_limits', 'channel_password', 'channel_salt'
];
$clean = array();
@@ -85,15 +96,9 @@ function import_channel($channel, $account_id, $seize) {
create_table_from_array('channel',$clean);
}
- if(! $r) {
- logger('mod_import: channel clone failed. ' . print_r($channel,true));
- notice( t('Channel clone failed. Import failed.') . EOL);
- return false;
- }
-
$r = q("select * from channel where channel_account_id = %d and channel_guid = '%s' limit 1",
intval($account_id),
- $channel['channel_guid'] // Already dbesc'd
+ dbesc($channel['channel_guid'])
);
if(! $r) {
logger('mod_import: channel not found. ' . print_r($channel,true));
@@ -114,24 +119,37 @@ function import_channel($channel, $account_id, $seize) {
set_default_login_identity($account_id,$channel['channel_id'],false);
logger('import step 1');
$_SESSION['import_step'] = 1;
- return $channel;
+ return $channel;
}
-function import_config($channel,$configs) {
+/**
+ * @brief Import pconfig for channel.
+ *
+ * @param array $channel
+ * @param array $configs
+ */
+function import_config($channel, $configs) {
if($channel && $configs) {
foreach($configs as $config) {
unset($config['id']);
$config['uid'] = $channel['channel_id'];
- create_table_from_array('pconfig',$config);
+
+ create_table_from_array('pconfig', $config);
}
+
load_pconfig($channel['channel_id']);
- }
+ }
}
-
-function import_profiles($channel,$profiles) {
+/**
+ * @brief Import profiles.
+ *
+ * @param array $channel
+ * @param array $profiles
+ */
+function import_profiles($channel, $profiles) {
if($channel && $profiles) {
foreach($profiles as $profile) {
@@ -143,19 +161,29 @@ function import_profiles($channel,$profiles) {
convert_oldfields($profile,'with','partner');
convert_oldfields($profile,'work','employment');
+ /**
+ * @TODO we are going to reset all profile photos to the original
+ * somebody will have to fix this later and put all the applicable
+ * photos into the export.
+ */
- // we are going to reset all profile photos to the original
- // somebody will have to fix this later and put all the applicable photos into the export
-
$profile['photo'] = z_root() . '/photo/profile/l/' . $channel['channel_id'];
$profile['thumb'] = z_root() . '/photo/profile/m/' . $channel['channel_id'];
- create_table_from_array('profile',$profile);
+
+ create_table_from_array('profile', $profile);
}
}
}
-
-function import_hublocs($channel,$hublocs,$seize,$moving = false) {
+/**
+ * @brief Import hublocs.
+ *
+ * @param array $channel
+ * @param array $hublocs
+ * @param unknown $seize
+ * @param boolean $moving (optional) default false
+ */
+function import_hublocs($channel, $hublocs, $seize, $moving = false) {
if($channel && $hublocs) {
foreach($hublocs as $hubloc) {
@@ -167,45 +195,49 @@ function import_hublocs($channel,$hublocs,$seize,$moving = false) {
}
if(! array_key_exists('hubloc_primary',$hubloc)) {
- $hubloc['hubloc_primary'] = (($hubloc['hubloc_flags'] & 0x0001) ? 1 : 0);
- $hubloc['hubloc_orphancheck'] = (($hubloc['hubloc_flags'] & 0x0004) ? 1 : 0);
- $hubloc['hubloc_error'] = (($hubloc['hubloc_status'] & 0x0003) ? 1 : 0);
- $hubloc['hubloc_deleted'] = (($hubloc['hubloc_flags'] & 0x1000) ? 1 : 0);
+ $hubloc['hubloc_primary'] = (($hubloc['hubloc_flags'] & 0x0001) ? 1 : 0);
+ $hubloc['hubloc_orphancheck'] = (($hubloc['hubloc_flags'] & 0x0004) ? 1 : 0);
+ $hubloc['hubloc_error'] = (($hubloc['hubloc_status'] & 0x0003) ? 1 : 0);
+ $hubloc['hubloc_deleted'] = (($hubloc['hubloc_flags'] & 0x1000) ? 1 : 0);
}
if($moving && $hubloc['hubloc_hash'] === $channel['channel_hash'] && $hubloc['hubloc_url'] !== z_root()) {
$hubloc['hubloc_deleted'] = 1;
}
- $arr = array(
- 'guid' => $hubloc['hubloc_guid'],
+ $arr = [
+ 'guid' => $hubloc['hubloc_guid'],
'guid_sig' => $hubloc['hubloc_guid_sig'],
- 'url' => $hubloc['hubloc_url'],
- 'url_sig' => $hubloc['hubloc_url_sig'],
- 'sitekey' => ((array_key_exists('hubloc_sitekey',$hubloc)) ? $hubloc['hubloc_sitekey'] : '')
- );
+ 'url' => $hubloc['hubloc_url'],
+ 'url_sig' => $hubloc['hubloc_url_sig'],
+ 'sitekey' => ((array_key_exists('hubloc_sitekey',$hubloc)) ? $hubloc['hubloc_sitekey'] : '')
+ ];
+
if(($hubloc['hubloc_hash'] === $channel['channel_hash']) && intval($hubloc['hubloc_primary']) && ($seize))
$hubloc['hubloc_primary'] = 0;
- if(($x = zot_gethub($arr,false)) === false) {
+ if(($x = zot_gethub($arr,false)) === false) {
unset($hubloc['hubloc_id']);
- create_table_from_array('hubloc',$hubloc);
+ create_table_from_array('hubloc', $hubloc);
}
else {
q("UPDATE hubloc set hubloc_primary = %d, hubloc_deleted = %d where hubloc_id = %d",
intval($hubloc['hubloc_primary']),
intval($hubloc['hubloc_deleted']),
intval($x['hubloc_id'])
- );
-
+ );
}
}
}
}
-
-
-function import_objs($channel,$objs) {
+/**
+ * @brief Import things.
+ *
+ * @param array $channel
+ * @param array $objs
+ */
+function import_objs($channel, $objs) {
if($channel && $objs) {
foreach($objs as $obj) {
@@ -220,21 +252,27 @@ function import_objs($channel,$objs) {
$obj['obj_channel'] = $channel['channel_id'];
- if($baseurl && (strpos($obj['obj_url'],$baseurl . '/thing/') !== false)) {
- $obj['obj_url'] = str_replace($baseurl,z_root(),$obj['obj_url']);
+ if($baseurl && (strpos($obj['obj_url'], $baseurl . '/thing/') !== false)) {
+ $obj['obj_url'] = str_replace($baseurl, z_root(), $obj['obj_url']);
}
if($obj['obj_imgurl']) {
- $x = import_xchan_photo($obj['obj_imgurl'],$channel['channel_hash'],true);
+ $x = import_xchan_photo($obj['obj_imgurl'], $channel['channel_hash'], true);
$obj['obj_imgurl'] = $x[0];
}
- create_table_from_array('obj',$obj);
+ create_table_from_array('obj', $obj);
}
}
}
-function sync_objs($channel,$objs) {
+/**
+ * @brief Import things.
+ *
+ * @param array $channel
+ * @param array $objs
+ */
+function sync_objs($channel, $objs) {
if($channel && $objs) {
foreach($objs as $obj) {
@@ -257,8 +295,8 @@ function sync_objs($channel,$objs) {
$obj['obj_channel'] = $channel['channel_id'];
- if($baseurl && (strpos($obj['obj_url'],$baseurl . '/thing/') !== false)) {
- $obj['obj_url'] = str_replace($baseurl,z_root(),$obj['obj_url']);
+ if($baseurl && (strpos($obj['obj_url'], $baseurl . '/thing/') !== false)) {
+ $obj['obj_url'] = str_replace($baseurl, z_root(), $obj['obj_url']);
}
$exists = false;
@@ -275,12 +313,12 @@ function sync_objs($channel,$objs) {
}
if($obj['obj_imgurl']) {
- $x = import_xchan_photo($obj['obj_imgurl'],$channel['channel_hash'],true);
+ $x = import_xchan_photo($obj['obj_imgurl'], $channel['channel_hash'], true);
$obj['obj_imgurl'] = $x[0];
}
$hash = $obj['obj_obj'];
-
+
if($exists) {
unset($obj['obj_obj']);
foreach($obj as $k => $v) {
@@ -292,23 +330,25 @@ function sync_objs($channel,$objs) {
);
}
}
- else {
- create_table_from_array('obj',$obj);
+ else {
+ create_table_from_array('obj', $obj);
}
}
}
}
-
-
-
-
-function import_apps($channel,$apps) {
+/**
+ * @brief Import apps.
+ *
+ * @param array $channel
+ * @param array $apps
+ */
+function import_apps($channel, $apps) {
if($channel && $apps) {
foreach($apps as $app) {
- $term = ((array_key_exists('term',$app) && is_array($app['term'])) ? $app['term'] : null);
+ $term = ((array_key_exists('term',$app) && is_array($app['term'])) ? $app['term'] : null);
unset($app['id']);
unset($app['app_channel']);
@@ -317,13 +357,13 @@ function import_apps($channel,$apps) {
$app['app_channel'] = $channel['channel_id'];
if($app['app_photo']) {
- $x = import_xchan_photo($app['app_photo'],$channel['channel_hash'],true);
+ $x = import_xchan_photo($app['app_photo'], $channel['channel_hash'], true);
$app['app_photo'] = $x[0];
}
$hash = $app['app_id'];
- create_table_from_array('app',$app);
+ create_table_from_array('app', $app);
if($term) {
$x = q("select * from app where app_id = '%s' and app_channel = %d limit 1",
@@ -334,20 +374,22 @@ function import_apps($channel,$apps) {
foreach($term as $t) {
if(array_key_exists('type',$t))
$t['ttype'] = $t['type'];
+
store_item_tag($channel['channel_id'],$x[0]['id'],TERM_OBJ_APP,$t['ttype'],escape_tags($t['term']),escape_tags($t['url']));
}
}
}
-
-
-
}
}
}
-
-
-function sync_apps($channel,$apps) {
+/**
+ * @brief Sync apps.
+ *
+ * @param array $channel
+ * @param array $apps
+ */
+function sync_apps($channel, $apps) {
if($channel && $apps) {
foreach($apps as $app) {
@@ -362,20 +404,20 @@ function sync_apps($channel,$apps) {
if($x) {
$exists = $x[0];
}
-
+
if(array_key_exists('app_deleted',$app) && $app['app_deleted'] && $app['app_id']) {
- q("delete from app where app_id = '%s' and app_channel = %d",
- dbesc($app['app_id']),
- intval($channel['channel_id'])
- );
+ q("delete from app where app_id = '%s' and app_channel = %d",
+ dbesc($app['app_id']),
+ intval($channel['channel_id'])
+ );
if($exists) {
q("delete from term where otype = %d and oid = %d",
intval(TERM_OBJ_APP),
intval($exists['id'])
- );
+ );
}
- continue;
- }
+ continue;
+ }
unset($app['id']);
unset($app['app_channel']);
@@ -385,7 +427,7 @@ function sync_apps($channel,$apps) {
q("delete from term where otype = %d and oid = %d",
intval(TERM_OBJ_APP),
intval($exists['id'])
- );
+ );
}
if((! $app['app_created']) || ($app['app_created'] <= NULL_DATE))
@@ -446,9 +488,13 @@ function sync_apps($channel,$apps) {
}
}
-
-
-function import_chatrooms($channel,$chatrooms) {
+/**
+ * @brief Import chatrooms.
+ *
+ * @param array $channel
+ * @param array $chatrooms
+ */
+function import_chatrooms($channel, $chatrooms) {
if($channel && $chatrooms) {
foreach($chatrooms as $chatroom) {
@@ -463,14 +509,18 @@ function import_chatrooms($channel,$chatrooms) {
$chatroom['cr_aid'] = $channel['channel_account_id'];
$chatroom['cr_uid'] = $channel['channel_id'];
- create_table_from_array('chatroom',$chatroom);
+ create_table_from_array('chatroom', $chatroom);
}
}
}
-
-
-function sync_chatrooms($channel,$chatrooms) {
+/**
+ * @brief Sync chatrooms.
+ *
+ * @param array $channel
+ * @param array $chatrooms
+ */
+function sync_chatrooms($channel, $chatrooms) {
if($channel && $chatrooms) {
foreach($chatrooms as $chatroom) {
@@ -479,13 +529,12 @@ function sync_chatrooms($channel,$chatrooms) {
continue;
if(array_key_exists('cr_deleted',$chatroom) && $chatroom['cr_deleted']) {
- q("delete from chatroom where cr_name = '%s' and cr_uid = %d",
- dbesc($chatroom['cr_name']),
- intval($channel['channel_id'])
- );
- continue;
- }
-
+ q("delete from chatroom where cr_name = '%s' and cr_uid = %d",
+ dbesc($chatroom['cr_name']),
+ intval($channel['channel_id'])
+ );
+ continue;
+ }
unset($chatroom['cr_id']);
unset($chatroom['cr_aid']);
@@ -508,6 +557,7 @@ function sync_chatrooms($channel,$chatrooms) {
if($x) {
if($x[0]['cr_edited'] >= $chatroom['cr_edited'])
continue;
+
$exists = true;
}
$name = $chatroom['cr_name'];
@@ -523,29 +573,28 @@ function sync_chatrooms($channel,$chatrooms) {
}
}
else {
- create_table_from_array('chatroom',$chatroom);
+ create_table_from_array('chatroom', $chatroom);
}
}
}
}
-
-function import_items($channel,$items,$sync = false,$relocate = null) {
+/**
+ * @brief Import items to channel.
+ *
+ * @param array $channel where to import to
+ * @param array $items
+ * @param boolean $sync default false
+ * @param array $relocate default null
+ */
+function import_items($channel, $items, $sync = false, $relocate = null) {
if($channel && $items) {
- $allow_code = false;
- $r = q("select account_id, account_roles, channel_pageflags from account left join channel on channel_account_id = account_id
- where channel_id = %d limit 1",
- intval($channel['channel_id'])
- );
- if($r) {
- if(($r[0]['account_roles'] & ACCOUNT_ROLE_ALLOWCODE) || ($r[0]['channel_pageflags'] & PAGE_ALLOWCODE)) {
- $allow_code = true;
- }
- }
- $deliver = false; // Don't deliver any messages or notifications when importing
+ $allow_code = channel_codeallowed($channel['channel_id']);
+
+ $deliver = false; // Don't deliver any messages or notifications when importing
foreach($items as $i) {
$item_result = false;
@@ -553,6 +602,11 @@ function import_items($channel,$items,$sync = false,$relocate = null) {
if(! $item)
continue;
+ // deprecated
+
+ if(array_key_exists('diaspora_meta',$item))
+ unset($item['diaspora_meta']);
+
if($relocate && $item['mid'] === $item['parent_mid']) {
item_url_replace($channel,$item,$relocate['url'],z_root(),$relocate['channel_address']);
}
@@ -563,14 +617,14 @@ function import_items($channel,$items,$sync = false,$relocate = null) {
);
if($r) {
- // flags may have changed and we are probably relocating the post,
+ // flags may have changed and we are probably relocating the post,
// so force an update even if we have the same timestamp
if($item['edited'] >= $r[0]['edited']) {
$item['id'] = $r[0]['id'];
$item['uid'] = $channel['channel_id'];
$item_result = item_store_update($item,$allow_code,$deliver);
- }
+ }
}
else {
$item['aid'] = $channel['channel_account_id'];
@@ -578,6 +632,14 @@ function import_items($channel,$items,$sync = false,$relocate = null) {
$item_result = item_store($item,$allow_code,$deliver);
}
+ // preserve conversations you've been involved in from being expired
+
+ $stored = $item_result['item'];
+ if((is_array($stored)) && ($stored['id'] != $stored['parent'])
+ && ($stored['author_xchan'] === $channel['channel_hash'])) {
+ retain_item($stored['item']['parent']);
+ }
+
fix_attached_photo_permissions($channel['channel_id'],$item['author_xchan'],$item['body'],$item['allow_cid'],$item['allow_gid'],$item['deny_cid'],$item['deny_gid']);
fix_attached_file_permissions($channel,$item['author_xchan'],$item['body'],$item['allow_cid'],$item['allow_gid'],$item['deny_cid'],$item['deny_gid']);
@@ -592,14 +654,26 @@ function import_items($channel,$items,$sync = false,$relocate = null) {
}
}
-
-function sync_items($channel,$items,$relocate = null) {
- import_items($channel,$items,true,$relocate);
+/**
+ * @brief Sync items to channel.
+ *
+ * @see import_items
+ *
+ * @param array $channel where to import to
+ * @param array $items
+ * @param array $relocate default null
+ */
+function sync_items($channel, $items, $relocate = null) {
+ import_items($channel, $items, true, $relocate);
}
-
-
-function import_item_ids($channel,$itemids) {
+/**
+ * @brief
+ *
+ * @param array $channel A channel array.
+ * @param array $itemids
+ */
+function import_item_ids($channel, $itemids) {
if($channel && $itemids) {
foreach($itemids as $i) {
$r = q("select id from item where mid = '%s' and uid = %d limit 1",
@@ -608,20 +682,26 @@ function import_item_ids($channel,$itemids) {
);
if(! $r)
continue;
- $z = q("select * from iconfig where iconfig.cat = 'system' and iconfig.k = '%s'
+ $z = q("select * from iconfig where iconfig.cat = 'system' and iconfig.k = '%s'
and iconfig.v = '%s' and iid = %d limit 1",
dbesc($i['service']),
dbesc($i['sid']),
intval($r[0]['id'])
);
if(! $z) {
- \Zotlabs\Lib\IConfig::Set($r[0]['id'],'system',$i['service'],$i['sid'],true);
+ IConfig::Set($r[0]['id'],'system',$i['service'],$i['sid'],true);
}
}
}
}
-function import_events($channel,$events) {
+/**
+ * @brief Import events.
+ *
+ * @param array $channel
+ * @param array $events
+ */
+function import_events($channel, $events) {
if($channel && $events) {
foreach($events as $event) {
@@ -633,13 +713,18 @@ function import_events($channel,$events) {
convert_oldfields($event,'type','etype');
convert_oldfields($event,'ignore','dismissed');
- create_table_from_array('event',$event);
+ create_table_from_array('event', $event);
}
}
}
-
-function sync_events($channel,$events) {
+/**
+ * @brief Sync events.
+ *
+ * @param array $channel
+ * @param array $events
+ */
+function sync_events($channel, $events) {
if($channel && $events) {
foreach($events as $event) {
@@ -651,7 +736,7 @@ function sync_events($channel,$events) {
$r = q("delete from event where event_hash = '%s' and uid = %d",
dbesc($event['event_hash']),
intval($channel['channel_id'])
- );
+ );
continue;
}
@@ -664,7 +749,6 @@ function sync_events($channel,$events) {
convert_oldfields($event,'type','etype');
convert_oldfields($event,'ignore','dismissed');
-
$exists = false;
$x = q("select * from event where event_hash = '%s' and uid = %d limit 1",
@@ -674,6 +758,7 @@ function sync_events($channel,$events) {
if($x) {
if($x[0]['edited'] >= $event['edited'])
continue;
+
$exists = true;
}
@@ -688,15 +773,19 @@ function sync_events($channel,$events) {
}
}
else {
- create_table_from_array('event',$event);
+ create_table_from_array('event', $event);
}
}
}
}
-
-function import_menus($channel,$menus) {
-
+/**
+ * @brief Import menus.
+ *
+ * @param array $channel
+ * @param array $menus
+ */
+function import_menus($channel, $menus) {
if($channel && $menus) {
foreach($menus as $menu) {
@@ -715,7 +804,6 @@ function import_menus($channel,$menus) {
$m['menu_flags'] |= MENU_BOOKMARK;
if(in_array('system',$menu['flags']))
$m['menu_flags'] |= MENU_SYSTEM;
-
}
$menu_id = menu_create($m);
@@ -743,16 +831,19 @@ function import_menus($channel,$menus) {
}
menu_add_item($menu_id,$channel['channel_id'],$mitem);
}
- }
+ }
}
}
}
-
-
}
-
-function sync_menus($channel,$menus) {
+/**
+ * @brief Sync menus.
+ *
+ * @param array $channel
+ * @param array $menus
+ */
+function sync_menus($channel, $menus) {
if($channel && $menus) {
foreach($menus as $menu) {
@@ -809,7 +900,6 @@ function sync_menus($channel,$menus) {
foreach($menu['items'] as $it) {
$mitem = array();
-
$mitem['mitem_link'] = str_replace('[channelurl]',z_root() . '/channel/' . $channel['channel_address'],$it['link']);
$mitem['mitem_link'] = str_replace('[pageurl]',z_root() . '/page/' . $channel['channel_address'],$it['link']);
$mitem['mitem_link'] = str_replace('[cloudurl]',z_root() . '/cloud/' . $channel['channel_address'],$it['link']);
@@ -828,15 +918,19 @@ function sync_menus($channel,$menus) {
}
menu_add_item($menu_id,$channel['channel_id'],$mitem);
}
- }
+ }
}
}
}
}
-
-
-function import_likes($channel,$likes) {
+/**
+ * @brief Import likes.
+ *
+ * @param array $channel
+ * @param array $likes
+ */
+function import_likes($channel, $likes) {
if($channel && $likes) {
foreach($likes as $like) {
if($like['deleted']) {
@@ -849,7 +943,7 @@ function import_likes($channel,$likes) {
);
continue;
}
-
+
unset($like['id']);
unset($like['iid']);
$like['channel_id'] = $channel['channel_id'];
@@ -864,9 +958,9 @@ function import_likes($channel,$likes) {
if($r)
continue;
- create_table_from_array('likes',$like);
+ create_table_from_array('likes', $like);
}
- }
+ }
}
function import_conv($channel,$convs) {
@@ -879,7 +973,7 @@ function import_conv($channel,$convs) {
);
continue;
}
-
+
unset($conv['id']);
$conv['uid'] = $channel['channel_id'];
@@ -891,14 +985,20 @@ function import_conv($channel,$convs) {
);
if($r)
continue;
+
create_table_from_array('conv',$conv);
}
- }
+ }
}
-
-
-function import_mail($channel,$mails,$sync = false) {
+/**
+ * @brief Import mails.
+ *
+ * @param array $channel
+ * @param array $mails
+ * @param boolean $sync (optional) default false
+ */
+function import_mail($channel, $mails, $sync = false) {
if($channel && $mails) {
foreach($mails as $mail) {
if(array_key_exists('flags',$mail) && in_array('deleted',$mail['flags'])) {
@@ -927,14 +1027,27 @@ function import_mail($channel,$mails,$sync = false) {
Zotlabs\Daemon\Master::Summon(array('Notifier','single_mail',$mail_id));
}
}
- }
+ }
}
-function sync_mail($channel,$mails) {
- import_mail($channel,$mails,true);
+/**
+ * @brief Synchronise mails.
+ *
+ * @see import_mail
+ * @param array $channel
+ * @param array $mails
+ */
+function sync_mail($channel, $mails) {
+ import_mail($channel, $mails, true);
}
-function sync_files($channel,$files) {
+/**
+ * @brief Synchronise files.
+ *
+ * @param array $channel
+ * @param array $files
+ */
+function sync_files($channel, $files) {
require_once('include/attach.php');
@@ -948,7 +1061,7 @@ function sync_files($channel,$files) {
$original_channel = $f['original_channel'];
if(! ($fetch_url && $original_channel))
- continue;
+ continue;
if($f['attach']) {
$attachment_stored = false;
@@ -978,12 +1091,11 @@ function sync_files($channel,$files) {
$att['aid'] = $channel['channel_account_id'];
$att['uid'] = $channel['channel_id'];
-
- // check for duplicate folder names with the same parent.
+ // check for duplicate folder names with the same parent.
// If we have a duplicate that doesn't match this hash value
- // change the name so that the contents won't be "covered over"
- // by the existing directory. Use the same logic we use for
- // duplicate files.
+ // change the name so that the contents won't be "covered over"
+ // by the existing directory. Use the same logic we use for
+ // duplicate files.
if(strpos($att['filename'],'.') !== false) {
$basename = substr($att['filename'],0,strrpos($att['filename'],'.'));
@@ -994,11 +1106,12 @@ function sync_files($channel,$files) {
$ext = '';
}
- $r = q("select filename from attach where ( filename = '%s' OR filename like '%s' ) and folder = '%s' and hash != '%s' ",
+ $r = q("select filename from attach where ( filename = '%s' OR filename like '%s' ) and folder = '%s' and hash != '%s' and uid = %d ",
dbesc($basename . $ext),
dbesc($basename . '(%)' . $ext),
dbesc($att['folder']),
- dbesc($att['hash'])
+ dbesc($att['hash']),
+ intval($channel['channel_id'])
);
if($r) {
@@ -1014,7 +1127,7 @@ function sync_files($channel,$files) {
}
if($found)
$x++;
- }
+ }
while($found);
$att['filename'] = $basename . '(' . $x . ')' . $ext;
}
@@ -1023,30 +1136,31 @@ function sync_files($channel,$files) {
// end duplicate detection
-// @fixme - update attachment structures if they are modified rather than created
+ /// @FIXME update attachment structures if they are modified rather than created
$att['content'] = $newfname;
// Note: we use $att['hash'] below after it has been escaped to
- // fetch the file contents.
+ // fetch the file contents.
// If the hash ever contains any escapable chars this could cause
- // problems. Currently it does not.
+ // problems. Currently it does not.
- // @TODO implement os_path
+ /// @TODO implement os_path
if(!isset($att['os_path']))
$att['os_path'] = '';
-
if($attach_exists) {
logger('sync_files attach exists: ' . print_r($att,true), LOGGER_DEBUG);
if(! dbesc_array($att))
continue;
+
$str = '';
- foreach($att as $k => $v) {
- if($str)
- $str .= ",";
- $str .= " " . TQUOT . $k . TQUOT . " = '" . $v . "' ";
- }
+ foreach($att as $k => $v) {
+ if($str)
+ $str .= ",";
+
+ $str .= " " . TQUOT . $k . TQUOT . " = '" . $v . "' ";
+ }
$r = dbq("update attach set " . $str . " where id = " . intval($attach_id) );
}
else {
@@ -1054,7 +1168,6 @@ function sync_files($channel,$files) {
create_table_from_array('attach',$att);
}
-
// is this a directory?
if($att['filetype'] === 'multipart/mixed' && $att['is_dir']) {
@@ -1063,17 +1176,16 @@ function sync_files($channel,$files) {
continue;
}
else {
-
// it's a file
// for the sync version of this algorithm (as opposed to 'offline import')
- // we will fetch the actual file from the source server so it can be
+ // we will fetch the actual file from the source server so it can be
// streamed directly to disk and avoid consuming PHP memory if it's a huge
- // audio/video file or something.
+ // audio/video file or something.
$time = datetime_convert();
- $parr = array('hash' => $channel['channel_hash'],
- 'time' => $time,
+ $parr = array('hash' => $channel['channel_hash'],
+ 'time' => $time,
'resource' => $att['hash'],
'revision' => 0,
'signature' => base64url_encode(rsa_sign($channel['channel_hash'] . '.' . $time, $channel['channel_prvkey']))
@@ -1098,7 +1210,7 @@ function sync_files($channel,$files) {
}
}
if(! $attachment_stored) {
- // @TODO should we queue this and retry or delete everything or what?
+ /// @TODO should we queue this and retry or delete everything or what?
logger('attachment store failed',LOGGER_NORMAL,LOG_ERR);
}
if($f['photo']) {
@@ -1142,7 +1254,6 @@ function sync_files($channel,$files) {
else
$p['content'] = base64_decode($p['content']);
-
if(!isset($p['display_path']))
$p['display_path'] = '';
@@ -1152,20 +1263,21 @@ function sync_files($channel,$files) {
intval($channel['channel_id'])
);
-
if($exists) {
if(! dbesc_array($p))
continue;
- $str = '';
- foreach($p as $k => $v) {
- if($str)
- $str .= ",";
- $str .= " " . TQUOT . $k . TQUOT . " = '" . $v . "' ";
- }
- $r = dbq("update photo set " . $str . " where id = " . intval($exists[0]['id']) );
+
+ $str = '';
+ foreach($p as $k => $v) {
+ if($str)
+ $str .= ",";
+
+ $str .= " " . TQUOT . $k . TQUOT . " = '" . $v . "' ";
+ }
+ $r = dbq("update photo set " . $str . " where id = " . intval($exists[0]['id']) );
}
else {
- create_attach_from_array('photo',$p);
+ create_table_from_array('photo',$p);
}
}
}
@@ -1178,9 +1290,17 @@ function sync_files($channel,$files) {
}
}
-
-function convert_oldfields(&$arr,$old,$new) {
- if(array_key_exists($old,$arr)) {
+/**
+ * @brief Rename a key in an array.
+ *
+ * Replaces $old key with $new key in $arr.
+ *
+ * @param[in,out] array &$arr The array where to work on
+ * @param string $old The old key in the array
+ * @param string $new The new key in the array
+ */
+function convert_oldfields(&$arr, $old, $new) {
+ if(array_key_exists($old, $arr)) {
$arr[$new] = $arr[$old];
unset($arr[$old]);
}
@@ -1254,14 +1374,15 @@ function scan_webpage_elements($path, $type, $cloud = false) {
}
}
}
+
return $elements;
}
-
+
function import_webpage_element($element, $channel, $type) {
-
+
$arr = array(); // construct information for the webpage element item table record
-
+
switch($type) {
//
// PAGES
@@ -1270,26 +1391,26 @@ function import_webpage_element($element, $channel, $type) {
$arr['item_type'] = ITEM_TYPE_WEBPAGE;
$namespace = 'WEBPAGE';
$name = $element['pagelink'];
- if($name) {
+ if($name) {
require_once('library/urlify/URLify.php');
$name = strtolower(\URLify::transliterate($name));
- }
+ }
$arr['title'] = $element['title'];
$arr['term'] = $element['term'];
$arr['layout_mid'] = ''; // by default there is no layout associated with the page
// If a layout was specified, find it in the database and get its info. If
- // it does not exist, leave layout_mid empty
- if($element['layout'] !== '') {
- $liid = q("select iid from iconfig where k = 'PDL' and v = '%s' and cat = 'system'",
+ // it does not exist, leave layout_mid empty
+ if($element['layout'] !== '') {
+ $liid = q("select iid from iconfig where k = 'PDL' and v = '%s' and cat = 'system'",
dbesc($element['layout'])
- );
+ );
if($liid) {
- $linfo = q("select mid from item where id = %d",
+ $linfo = q("select mid from item where id = %d",
intval($liid[0]['iid'])
- );
- $arr['layout_mid'] = $linfo[0]['mid'];
- }
- }
+ );
+ $arr['layout_mid'] = $linfo[0]['mid'];
+ }
+ }
break;
//
// LAYOUTS
@@ -1309,15 +1430,15 @@ function import_webpage_element($element, $channel, $type) {
$namespace = 'BUILDBLOCK';
$name = $element['name'];
$arr['title'] = $element['title'];
-
+
break;
default :
return null; // return null if invalid element type
}
-
+
$arr['uid'] = local_channel();
$arr['aid'] = $channel['channel_account_id'];
-
+
// Check if an item already exists based on the name
$iid = q("select iid from iconfig where k = '" . $namespace . "' and v = '%s' and cat = 'system'",
dbesc($name)
@@ -1342,12 +1463,13 @@ function import_webpage_element($element, $channel, $type) {
// The author is either the owner or whomever was specified
$arr['author_xchan'] = (($element['author_xchan']) ? $element['author_xchan'] : get_observer_hash());
// Import mimetype if it is a valid mimetype for the element
- $mimetypes = [ 'text/bbcode',
+ $mimetypes = [
+ 'text/bbcode',
'text/html',
'text/markdown',
'text/plain',
'application/x-pdl',
- 'application/x-php'
+ 'application/x-php'
];
// Blocks and pages can have any of the valid mimetypes, but layouts must be text/bbcode
if((in_array($element['mimetype'], $mimetypes)) && ($type === 'page' || $type === 'block') ) {
@@ -1358,37 +1480,16 @@ function import_webpage_element($element, $channel, $type) {
}
// Verify ability to use html or php!!!
- $execflag = false;
- if($arr['mimetype'] === 'application/x-php' || $arr['mimetype'] === 'text/html') {
- $z = q("select account_id, account_roles, channel_pageflags from account "
- . "left join channel on channel_account_id = account_id where channel_id = %d limit 1",
- intval(local_channel())
- );
- if($z && (($z[0]['account_roles'] & ACCOUNT_ROLE_ALLOWCODE) || ($z[0]['channel_pageflags'] & PAGE_ALLOWCODE))) {
- $execflag = true;
- }
- else {
- logger('Unable to import element "' . $name .'" because AllowCode permission is denied.');
- notice( t('Unable to import element "' . $name .'" because AllowCode permission is denied.') . EOL);
- $element['import_success'] = 0;
- return $element;
- }
- }
-
-// $z = q("select * from iconfig where v = '%s' and k = '%s' and cat = 'system' limit 1",
-// dbesc($name),
-// dbesc($namespace)
-// );
-
- $i = q("select id, edited, item_deleted from item where mid = '%s' and uid = %d limit 1",
- dbesc($arr['mid']),
+ $execflag = channel_codeallowed(local_channel());
+
+ $i = q("select id, edited, item_deleted from item where mid = '%s' and uid = %d limit 1",
+ dbesc($arr['mid']),
intval(local_channel())
);
-
- \Zotlabs\Lib\IConfig::Set($arr,'system',$namespace,(($name) ? $name : substr($arr['mid'],0,16)),true);
-
-
+
+ IConfig::Set($arr,'system',$namespace,(($name) ? $name : substr($arr['mid'],0,16)),true);
+
if($i) {
$arr['id'] = $i[0]['id'];
// don't update if it has the same timestamp as the original
@@ -1406,23 +1507,23 @@ function import_webpage_element($element, $channel, $type) {
else
$x = item_store($arr,$execflag);
}
-
+
if($x && $x['success']) {
- $item_id = $x['item_id'];
+ //$item_id = $x['item_id'];
//update_remote_id($channel, $item_id, $arr['item_type'], $name, $namespace, $remote_id, $arr['mid']);
$element['import_success'] = 1;
}
else {
$element['import_success'] = 0;
}
-
- return $element;
+
+ return $element;
}
function get_webpage_elements($channel, $type = 'all') {
$elements = array();
- if(!$channel['channel_id']) {
- return null;
+ if(!$channel['channel_id']) {
+ return null;
}
switch($type) {
case 'all':
@@ -1430,17 +1531,16 @@ function get_webpage_elements($channel, $type = 'all') {
case 'pages':
$elements['pages'] = null;
$owner = $channel['channel_id'];
-
- $sql_extra = item_permissions_sql($owner);
+ $sql_extra = item_permissions_sql($owner);
- $r = q("select * from iconfig left join item on iconfig.iid = item.id
- where item.uid = %d and iconfig.cat = 'system' and iconfig.k = 'WEBPAGE' and item_type = %d
+ $r = q("select * from iconfig left join item on iconfig.iid = item.id
+ where item.uid = %d and iconfig.cat = 'system' and iconfig.k = 'WEBPAGE' and item_type = %d
$sql_extra order by item.created desc",
intval($owner),
intval(ITEM_TYPE_WEBPAGE)
);
-
+
$pages = null;
if($r) {
@@ -1473,7 +1573,6 @@ function get_webpage_elements($channel, $type = 'all') {
);
$elements['pages'][] = $element_arr;
}
-
}
if($type !== 'all') {
break;
@@ -1482,91 +1581,91 @@ function get_webpage_elements($channel, $type = 'all') {
case 'layouts':
$elements['layouts'] = null;
$owner = $channel['channel_id'];
-
- $sql_extra = item_permissions_sql($owner);
+ $sql_extra = item_permissions_sql($owner);
- $r = q("select * from iconfig left join item on iconfig.iid = item.id
- where item.uid = %d and iconfig.cat = 'system' and iconfig.k = 'PDL' and item_type = %d
+ $r = q("select * from iconfig left join item on iconfig.iid = item.id
+ where item.uid = %d and iconfig.cat = 'system' and iconfig.k = 'PDL' and item_type = %d
$sql_extra order by item.created desc",
intval($owner),
intval(ITEM_TYPE_PDL)
);
-
- $layouts = null;
if($r) {
$elements['layouts'] = array();
- $layouts = array();
+
foreach($r as $rr) {
unobscure($rr);
$elements['layouts'][] = array(
- 'type' => 'layout',
- 'description' => $rr['title'], // description of the layout
- 'body' => $rr['body'],
- 'created' => $rr['created'],
- 'edited' => $rr['edited'],
- 'mimetype' => $rr['mimetype'],
- 'name' => $rr['v'], // name of reference for the layout
- 'mid' => $rr['mid'],
+ 'type' => 'layout',
+ 'description' => $rr['title'], // description of the layout
+ 'body' => $rr['body'],
+ 'created' => $rr['created'],
+ 'edited' => $rr['edited'],
+ 'mimetype' => $rr['mimetype'],
+ 'name' => $rr['v'], // name of reference for the layout
+ 'mid' => $rr['mid'],
);
}
}
-
+
if($type !== 'all') {
break;
}
-
+
case 'blocks':
$elements['blocks'] = null;
$owner = $channel['channel_id'];
-
- $sql_extra = item_permissions_sql($owner);
+ $sql_extra = item_permissions_sql($owner);
- $r = q("select iconfig.iid, iconfig.k, iconfig.v, mid, title, body, mimetype, created, edited from iconfig
+ $r = q("select iconfig.iid, iconfig.k, iconfig.v, mid, title, body, mimetype, created, edited from iconfig
left join item on iconfig.iid = item.id
- where uid = %d and iconfig.cat = 'system' and iconfig.k = 'BUILDBLOCK'
+ where uid = %d and iconfig.cat = 'system' and iconfig.k = 'BUILDBLOCK'
and item_type = %d order by item.created desc",
intval($owner),
intval(ITEM_TYPE_BLOCK)
);
-
- $blocks = null;
if($r) {
$elements['blocks'] = array();
- $blocks = array();
+
foreach($r as $rr) {
unobscure($rr);
$elements['blocks'][] = array(
'type' => 'block',
- 'title' => $rr['title'],
+ 'title' => $rr['title'],
'body' => $rr['body'],
'created' => $rr['created'],
'edited' => $rr['edited'],
'mimetype' => $rr['mimetype'],
- 'name' => $rr['v'],
+ 'name' => $rr['v'],
'mid' => $rr['mid']
);
}
-
}
-
+
if($type !== 'all') {
break;
}
-
+
default:
break;
}
+
return $elements;
}
-/* creates a compressed zip file */
-
+/**
+ * @brief Create a compressed zip file.
+ *
+ * @param array $files List of files to put in zip file
+ * @param string $destination
+ * @param boolean $overwrite
+ * @return boolean Success status
+ */
function create_zip_file($files = array(), $destination = '', $overwrite = false) {
// if the zip file already exists and overwrite is false, return false
if(file_exists($destination) && !$overwrite) {
@@ -1583,13 +1682,13 @@ function create_zip_file($files = array(), $destination = '', $overwrite = false
$valid_files[] = $file;
}
}
- }
+ }
// if we have good files...
if(count($valid_files)) {
//create the archive
$zip = new ZipArchive();
- if($zip->open($destination, $overwrite ? ZIPARCHIVE::OVERWRITE : ZIPARCHIVE::CREATE) !== true) {
+ if($zip->open($destination, $overwrite ? ZipArchive::OVERWRITE : ZipArchive::CREATE) !== true) {
return false;
}
// add the files
@@ -1603,7 +1702,7 @@ function create_zip_file($files = array(), $destination = '', $overwrite = false
// check to make sure the file exists
return file_exists($destination);
- }
+ }
else {
return false;
}
diff --git a/include/items.php b/include/items.php
index 139c637e5..dd8b394d3 100755
--- a/include/items.php
+++ b/include/items.php
@@ -8,6 +8,7 @@ use Zotlabs\Lib as Zlib;
require_once('include/bbcode.php');
require_once('include/oembed.php');
require_once('include/crypto.php');
+require_once('include/message.php');
require_once('include/feedutils.php');
require_once('include/photo/photo_driver.php');
require_once('include/permissions.php');
@@ -175,6 +176,19 @@ function item_normal() {
and item.item_blocked = 0 ";
}
+function item_normal_search() {
+ return " and item.item_hidden = 0 and item.item_type in (0,3,6) and item.item_deleted = 0
+ and item.item_unpublished = 0 and item.item_delayed = 0 and item.item_pending_remove = 0
+ and item.item_blocked = 0 ";
+}
+
+function item_normal_update() {
+ return " and item.item_hidden = 0 and item.item_type = 0
+ and item.item_unpublished = 0 and item.item_delayed = 0 and item.item_pending_remove = 0
+ and item.item_blocked = 0 ";
+}
+
+
/**
* @brief
*
@@ -212,6 +226,11 @@ function can_comment_on_post($observer_xchan, $item) {
// logger('can_comment_on_post: comment_policy: ' . $item['comment_policy'], LOGGER_DEBUG);
+ $x = [ 'observer_hash' => $observer_xchan, 'item' => $item, 'allowed' => 'unset' ];
+ call_hooks('can_comment_on_post',$x);
+ if($x['allowed'] !== 'unset')
+ return $x['allowed'];
+
if(! $observer_xchan)
return false;
@@ -248,8 +267,6 @@ function can_comment_on_post($observer_xchan, $item) {
}
if(strstr($item['comment_policy'],'network:') && strstr($item['comment_policy'],'red'))
return true;
- if(strstr($item['comment_policy'],'network:') && strstr($item['comment_policy'],'diaspora'))
- return true;
if(strstr($item['comment_policy'],'site:') && strstr($item['comment_policy'],App::get_hostname()))
return true;
@@ -298,11 +315,13 @@ function add_source_route($iid, $hash) {
* or other processing is performed.
*
* @param array $arr
+ * @param boolean $allow_code (optional) default false
+ * @param boolean $deliver (optional) default true
* @returns array
* * \e boolean \b success true or false
* * \e array \b activity the resulting activity if successful
*/
-function post_activity_item($arr,$allow_code = false,$deliver = true) {
+function post_activity_item($arr, $allow_code = false, $deliver = true) {
$ret = array('success' => false);
@@ -328,25 +347,14 @@ function post_activity_item($arr,$allow_code = false,$deliver = true) {
return $ret;
}
- $arr['public_policy'] = ((x($_REQUEST,'public_policy')) ? escape_tags($_REQUEST['public_policy']) : map_scope(\Zotlabs\Access\PermissionLimits::Get($channel['channel_id'],'view_stream'),true));
+ $arr['public_policy'] = ((array_key_exists('public_policy',$arr)) ? escape_tags($arr['public_policy']) : map_scope(\Zotlabs\Access\PermissionLimits::Get($channel['channel_id'],'view_stream'),true));
+
if($arr['public_policy'])
$arr['item_private'] = 1;
if(! array_key_exists('mimetype',$arr))
$arr['mimetype'] = 'text/bbcode';
- if(array_key_exists('item_private',$arr) && $arr['item_private']) {
-
- $arr['body'] = trim(z_input_filter($arr['uid'],$arr['body'],$arr['mimetype']));
-
- if($channel) {
- if($channel['channel_hash'] === $arr['author_xchan']) {
- $arr['sig'] = base64url_encode(rsa_sign($arr['body'],$channel['channel_prvkey']));
- $arr['item_verified'] = 1;
- }
- }
- }
-
$arr['mid'] = ((x($arr,'mid')) ? $arr['mid'] : item_message_id());
$arr['parent_mid'] = ((x($arr,'parent_mid')) ? $arr['parent_mid'] : $arr['mid']);
$arr['thr_parent'] = ((x($arr,'thr_parent')) ? $arr['thr_parent'] : $arr['mid']);
@@ -359,10 +367,13 @@ function post_activity_item($arr,$allow_code = false,$deliver = true) {
if(($is_comment) && ($arr['obj_type'] === ACTIVITY_OBJ_NOTE))
$arr['obj_type'] = ACTIVITY_OBJ_COMMENT;
- $arr['allow_cid'] = ((x($arr,'allow_cid')) ? $arr['allow_cid'] : $channel['channel_allow_cid']);
- $arr['allow_gid'] = ((x($arr,'allow_gid')) ? $arr['allow_gid'] : $channel['channel_allow_gid']);
- $arr['deny_cid'] = ((x($arr,'deny_cid')) ? $arr['deny_cid'] : $channel['channel_deny_cid']);
- $arr['deny_gid'] = ((x($arr,'deny_gid')) ? $arr['deny_gid'] : $channel['channel_deny_gid']);
+ if(! ( array_key_exists('allow_cid',$arr) || array_key_exists('allow_gid',$arr)
+ || array_key_exists('deny_cid',$arr) || array_key_exists('deny_gid',$arr))) {
+ $arr['allow_cid'] = $channel['channel_allow_cid'];
+ $arr['allow_gid'] = $channel['channel_allow_gid'];
+ $arr['deny_cid'] = $channel['channel_deny_cid'];
+ $arr['deny_gid'] = $channel['channel_deny_gid'];
+ }
$arr['comment_policy'] = map_scope(\Zotlabs\Access\PermissionLimits::Get($channel['channel_id'],'post_comments'));
@@ -424,7 +435,7 @@ function validate_item_elements($message,$arr) {
/**
- * @brief Limit lenght on imported system messages.
+ * @brief Limit length on imported system messages.
*
* The purpose of this function is to apply system message length limits to
* imported messages without including any embedded photos in the length.
@@ -538,12 +549,7 @@ function get_item_elements($x,$allow_code = false) {
$arr = array();
- if($allow_code)
- $arr['body'] = $x['body'];
- else
- $arr['body'] = (($x['body']) ? htmlspecialchars($x['body'],ENT_COMPAT,'UTF-8',false) : '');
-
- $key = get_config('system','pubkey');
+ $arr['body'] = $x['body'];
$maxlen = get_max_import_size();
@@ -598,11 +604,6 @@ function get_item_elements($x,$allow_code = false) {
$arr['sig'] = (($x['signature']) ? htmlspecialchars($x['signature'], ENT_COMPAT,'UTF-8',false) : '');
- if(array_key_exists('diaspora_signature',$x) && is_array($x['diaspora_signature']))
- $x['diaspora_signature'] = json_encode($x['diaspora_signature']);
-
- $arr['diaspora_meta'] = (($x['diaspora_signature']) ? $x['diaspora_signature'] : '');
-
$arr['obj'] = activity_sanitise($x['object']);
$arr['target'] = activity_sanitise($x['target']);
@@ -625,6 +626,9 @@ function get_item_elements($x,$allow_code = false) {
if(in_array('notshown',$x['flags']))
$arr['item_notshown'] = 1;
+ if(in_array('obscured',$x['flags']))
+ $arr['item_obscured'] = 1;
+
// hidden item are no longer propagated - notshown may be a suitable alternative
if(in_array('hidden',$x['flags']))
@@ -645,26 +649,62 @@ function get_item_elements($x,$allow_code = false) {
return array();
// save a potentially expensive lookup if author == owner
+
if($arr['author_xchan'] === make_xchan_hash($x['owner']['guid'],$x['owner']['guid_sig']))
$arr['owner_xchan'] = $arr['author_xchan'];
else {
$xchan_hash = import_author_xchan($x['owner']);
- if($xchan_hash)
+ if($xchan_hash) {
$arr['owner_xchan'] = $xchan_hash;
- else
+ }
+ else {
return array();
+ }
}
+ // Check signature on the body text received.
+ // This presents an issue that we aren't verifying the text that is actually displayed
+ // on this site. We are however verifying the received text was exactly as received.
+ // We have every right to strip content that poses a security risk. You are welcome to
+ // create a plugin to verify the content after filtering if this offends you.
+
if($arr['sig']) {
+
+ // check the supplied signature against the supplied content.
+ // Note that we will purify the content which could change it.
+
$r = q("select xchan_pubkey from xchan where xchan_hash = '%s' limit 1",
dbesc($arr['author_xchan'])
);
- if($r && rsa_verify($x['body'],base64url_decode($arr['sig']),$r[0]['xchan_pubkey']))
- $arr['item_verified'] = 1;
- else
- logger('get_item_elements: message verification failed.');
+ if($r) {
+ if($r[0]['xchan_pubkey']) {
+ if(rsa_verify($x['body'],base64url_decode($arr['sig']),$r[0]['xchan_pubkey'])) {
+ $arr['item_verified'] = 1;
+ }
+ else {
+ logger('get_item_elements: message verification failed.');
+ }
+ }
+ else {
+
+ // If we don't have a public key, strip the signature so it won't show as invalid.
+ // This won't happen in normal use, but could happen if import_author_xchan()
+ // failed to load the zot-info packet due to a server failure and had
+ // to create an alternate xchan with network 'unknown'
+
+ unset($arr['sig']);
+ }
+ }
}
+ // if the input is markdown, remove one level of html escaping.
+ // It will be re-applied in item_store() and/or item_store_update().
+ // Do this after signature checking as the original signature
+ // was generated on the escaped content.
+
+ if($arr['mimetype'] === 'text/markdown')
+ $arr['body'] = \Zotlabs\Lib\MarkdownSoap::unescape($arr['body']);
+
if(array_key_exists('revision',$x)) {
// extended export encoding
@@ -691,7 +731,7 @@ function get_item_elements($x,$allow_code = false) {
// local only $arr['item_relay'] = $x['item_relay'];
$arr['item_mentionsme'] = $x['item_mentionsme'];
$arr['item_nocomment'] = $x['item_nocomment'];
- // local only $arr['item_obscured'] = $x['item_obscured'];
+ $arr['item_obscured'] = $x['item_obscured'];
// local only $arr['item_verified'] = $x['item_verified'];
$arr['item_retained'] = $x['item_retained'];
$arr['item_rss'] = $x['item_rss'];
@@ -764,51 +804,26 @@ function import_author_xchan($x) {
if($arr['xchan_hash'])
return $arr['xchan_hash'];
+ $y = false;
+
if((! array_key_exists('network', $x)) || ($x['network'] === 'zot')) {
$y = import_author_zot($x);
}
- if(! $y)
- $y = import_author_diaspora($x);
+
+ // if we were told that it's a zot connection, don't probe/import anything else
+ if(array_key_exists('network',$x) && $x['network'] === 'zot')
+ return $y;
if($x['network'] === 'rss') {
$y = import_author_rss($x);
}
- if($x['network'] === 'unknown') {
+ if(! $y) {
$y = import_author_unknown($x);
}
- return(($y) ? $y : false);
-}
-
-/**
- * @brief Imports an author from Diaspora.
- *
- * @param array $x an associative array with
- * * \e string \b address
- * @return boolean|string false on error, otherwise xchan_hash of the new entry
- */
-function import_author_diaspora($x) {
- if(! $x['address'])
- return false;
-
- $r = q("select * from xchan where xchan_addr = '%s' limit 1",
- dbesc($x['address'])
- );
- if($r) {
- logger('in_cache: ' . $x['address'], LOGGER_DATA);
- return $r[0]['xchan_hash'];
- }
-
- if(discover_by_webbie($x['address'])) {
- $r = q("select xchan_hash from xchan where xchan_addr = '%s' limit 1",
- dbesc($x['address'])
- );
- if($r)
- return $r[0]['xchan_hash'];
- }
+ return($y);
- return false;
}
/**
@@ -820,6 +835,7 @@ function import_author_diaspora($x) {
* * \e string \b guid
* @return boolean|string
*/
+
function import_author_rss($x) {
if(! $x['url'])
return false;
@@ -867,6 +883,11 @@ function import_author_rss($x) {
function import_author_unknown($x) {
+ $arr = [ 'author' => $x, 'result' => false ];
+ call_hooks('import_author', $arr);
+ if($arr['result'])
+ return $arr['result'];
+
if(! $x['url'])
return false;
@@ -896,7 +917,7 @@ function import_author_unknown($x) {
$photos = import_xchan_photo($x['photo']['src'],$x['url']);
if($photos) {
- $r = q("update xchan set xchan_photo_date = '%s', xchan_photo_l = '%s', xchan_photo_m = '%s', xchan_photo_s = '%s', xchan_photo_mimetype = '%s' where xchan_url = '%s' and xchan_network = 'unknown'",
+ $r = q("update xchan set xchan_photo_date = '%s', xchan_photo_l = '%s', xchan_photo_m = '%s', xchan_photo_s = '%s', xchan_photo_mimetype = '%s' where xchan_hash = '%s' and xchan_network = 'unknown'",
dbesc(datetime_convert()),
dbesc($photos[0]),
dbesc($photos[1]),
@@ -936,13 +957,6 @@ function encode_item($item,$mirror = false) {
$key = get_config('system','prvkey');
- if(array_key_exists('item_obscured',$item) && intval($item['item_obscured'])) {
- if($item['title'])
- $item['title'] = crypto_unencapsulate(json_decode($item['title'],true),$key);
- if($item['body'])
- $item['body'] = crypto_unencapsulate(json_decode($item['body'],true),$key);
- }
-
// If we're trying to backup an item so that it's recoverable or for export/imprt,
// add all the attributes we need to recover it
@@ -1033,17 +1047,7 @@ function encode_item($item,$mirror = false) {
if($item['iconfig'])
$x['meta'] = encode_item_meta($item['iconfig'],$mirror);
- if($item['diaspora_meta']) {
- $z = json_decode($item['diaspora_meta'],true);
- if($z) {
- if(is_array($z) && array_key_exists('iv',$z))
- $x['diaspora_signature'] = crypto_unencapsulate($z,$key);
- else
- $x['diaspora_signature'] = $z;
- if(! is_array($z))
- logger('encode_item: diaspora meta is not an array: ' . print_r($z,true));
- }
- }
+
logger('encode_item: ' . print_r($x,true), LOGGER_DATA);
return $x;
@@ -1116,7 +1120,7 @@ function encode_item_xchan($xchan) {
$ret['address'] = $xchan['xchan_addr'];
$ret['url'] = $xchan['xchan_url'];
$ret['network'] = $xchan['xchan_network'];
- $ret['photo'] = array('mimetype' => $xchan['xchan_photo_mimetype'], 'src' => $xchan['xchan_photo_m']);
+ $ret['photo'] = [ 'mimetype' => $xchan['xchan_photo_mimetype'], 'src' => $xchan['xchan_photo_m'] ];
$ret['guid'] = $xchan['xchan_guid'];
$ret['guid_sig'] = $xchan['xchan_guid_sig'];
@@ -1126,7 +1130,7 @@ function encode_item_xchan($xchan) {
function encode_item_terms($terms,$mirror = false) {
$ret = array();
- $allowed_export_terms = array( TERM_UNKNOWN, TERM_HASHTAG, TERM_MENTION, TERM_CATEGORY, TERM_BOOKMARK, TERM_COMMUNITYTAG );
+ $allowed_export_terms = array( TERM_UNKNOWN, TERM_HASHTAG, TERM_MENTION, TERM_CATEGORY, TERM_BOOKMARK, TERM_COMMUNITYTAG, TERM_FORUM );
if($mirror) {
$allowed_export_terms[] = TERM_PCATEGORY;
@@ -1174,7 +1178,7 @@ function decode_item_meta($meta) {
* @return string
*/
function termtype($t) {
- $types = array('unknown','hashtag','mention','category','private_category','file','search','thing','bookmark', 'hierarchy', 'communitytag');
+ $types = array('unknown','hashtag','mention','category','private_category','file','search','thing','bookmark', 'hierarchy', 'communitytag', 'forum');
return(($types[$t]) ? $types[$t] : 'unknown');
}
@@ -1223,6 +1227,9 @@ function decode_tags($t) {
case 'communitytag':
$tag['ttype'] = TERM_COMMUNITYTAG;
break;
+ case 'forum':
+ $tag['ttype'] = TERM_FORUM;
+ break;
default:
case 'unknown':
$tag['ttype'] = TERM_UNKNOWN;
@@ -1300,6 +1307,8 @@ function encode_item_flags($item) {
$ret[] = 'nsfw';
if(intval($item['item_consensus']))
$ret[] = 'consensus';
+ if(intval($item['item_obscured']))
+ $ret[] = 'obscured';
if(intval($item['item_private']))
$ret[] = 'private';
@@ -1322,11 +1331,12 @@ function encode_mail($item,$extended = false) {
$x['message_parent'] = $item['parent_mid'];
$x['created'] = $item['created'];
$x['expires'] = $item['expires'];
- $x['diaspora_meta'] = $item['diaspora_meta'];
$x['title'] = $item['title'];
$x['body'] = $item['body'];
$x['from'] = encode_item_xchan($item['from']);
$x['to'] = encode_item_xchan($item['to']);
+ $x['raw'] = $item['mail_raw'];
+ $x['mimetype'] = $item['mail_mimetype'];
if($item['attach'])
$x['attach'] = json_decode($item['attach'],true);
@@ -1360,9 +1370,16 @@ function get_mail_elements($x) {
$arr = array();
- $arr['body'] = (($x['body']) ? htmlspecialchars($x['body'], ENT_COMPAT,'UTF-8',false) : '');
- $arr['title'] = (($x['title'])? htmlspecialchars($x['title'],ENT_COMPAT,'UTF-8',false) : '');
+ if(intval($x['raw'])) {
+ $arr['mail_raw'] = intval($x['raw']);
+ $arr['body'] = $x['body'];
+ }
+ else {
+ $arr['body'] = (($x['body']) ? htmlspecialchars($x['body'], ENT_COMPAT,'UTF-8',false) : '');
+ }
+ $arr['title'] = (($x['title'])? htmlspecialchars($x['title'],ENT_COMPAT,'UTF-8',false) : '');
+ $arr['mail_mimetype'] = (($x['mimetype']) ? htmlspecialchars($x['mimetype'],ENT_COMPAT,'UTF-8',false) : 'text/bbcode');
$arr['conv_guid'] = (($x['conv_guid'])? htmlspecialchars($x['conv_guid'],ENT_COMPAT,'UTF-8',false) : '');
$arr['created'] = datetime_convert('UTC','UTC',$x['created']);
@@ -1452,6 +1469,26 @@ function get_profile_elements($x) {
}
+
+
+function item_sign(&$item) {
+
+ if(array_key_exists('sig',$item) && $item['sig'])
+ return;
+
+ $r = q("select channel_prvkey from channel where channel_id = %d and channel_hash = '%s' ",
+ intval($item['uid']),
+ dbesc($item['author_xchan'])
+ );
+ if(! $r)
+ return;
+
+ $item['sig'] = base64url_encode(rsa_sign($item['body'],$r[0]['channel_prvkey']));
+ $item['item_verified'] = 1;
+
+}
+
+
/**
* @brief
*
@@ -1475,7 +1512,7 @@ function item_store($arr, $allow_exec = false, $deliver = true) {
if(array_key_exists('cancel',$arr) && $arr['cancel']) {
logger('cancelled by plugin');
return $ret;
- }
+ }
if(! $arr['uid']) {
logger('item_store: no uid');
@@ -1515,7 +1552,6 @@ function item_store($arr, $allow_exec = false, $deliver = true) {
$arr['title'] = ((array_key_exists('title',$arr) && strlen($arr['title'])) ? trim($arr['title']) : '');
$arr['body'] = ((array_key_exists('body',$arr) && strlen($arr['body'])) ? trim($arr['body']) : '');
- $arr['diaspora_meta'] = ((x($arr,'diaspora_meta')) ? $arr['diaspora_meta'] : '');
$arr['allow_cid'] = ((x($arr,'allow_cid')) ? trim($arr['allow_cid']) : '');
$arr['allow_gid'] = ((x($arr,'allow_gid')) ? trim($arr['allow_gid']) : '');
$arr['deny_cid'] = ((x($arr,'deny_cid')) ? trim($arr['deny_cid']) : '');
@@ -1529,35 +1565,30 @@ function item_store($arr, $allow_exec = false, $deliver = true) {
// obsolete, but needed so as not to throw not-null constraints on some database driveres
$arr['item_flags'] = ((x($arr,'item_flags')) ? intval($arr['item_flags']) : 0 );
- // only detect language if we have text content, and if the post is private but not yet
- // obscured, make it so.
- if((! array_key_exists('item_obscured',$arr)) || $arr['item_obscured'] == 0) {
- $arr['lang'] = detect_language($arr['body']);
- // apply the input filter here - if it is obscured it has been filtered already
- $arr['body'] = trim(z_input_filter($arr['uid'],$arr['body'],$arr['mimetype']));
+ $arr['lang'] = detect_language($arr['body']);
- if(local_channel() && (local_channel() == $arr['uid']) && (! $arr['sig'])) {
- $channel = App::get_channel();
- if($channel['channel_hash'] === $arr['author_xchan']) {
- $arr['sig'] = base64url_encode(rsa_sign($arr['body'],$channel['channel_prvkey']));
- $arr['item_verified'] = 1;
- }
- }
+ // apply the input filter here
- $allowed_languages = get_pconfig($arr['uid'],'system','allowed_languages');
+ $arr['body'] = trim(z_input_filter($arr['body'],$arr['mimetype'],$allow_exec));
- if((is_array($allowed_languages)) && ($arr['lang']) && (! array_key_exists($arr['lang'],$allowed_languages))) {
- $translate = array('item' => $arr, 'from' => $arr['lang'], 'to' => $allowed_languages, 'translated' => false);
- call_hooks('item_translate', $translate);
- if((! $translate['translated']) && (intval(get_pconfig($arr['uid'],'system','reject_disallowed_languages')))) {
- logger('item_store: language ' . $arr['lang'] . ' not accepted for uid ' . $arr['uid']);
- $ret['message'] = 'language not accepted';
- return $ret;
- }
- $arr = $translate['item'];
+ item_sign($arr);
+
+ if(! array_key_exists('sig',$arr))
+ $arr['sig'] = '';
+
+ $allowed_languages = get_pconfig($arr['uid'],'system','allowed_languages');
+
+ if((is_array($allowed_languages)) && ($arr['lang']) && (! array_key_exists($arr['lang'],$allowed_languages))) {
+ $translate = array('item' => $arr, 'from' => $arr['lang'], 'to' => $allowed_languages, 'translated' => false);
+ call_hooks('item_translate', $translate);
+ if((! $translate['translated']) && (intval(get_pconfig($arr['uid'],'system','reject_disallowed_languages')))) {
+ logger('item_store: language ' . $arr['lang'] . ' not accepted for uid ' . $arr['uid']);
+ $ret['message'] = 'language not accepted';
+ return $ret;
}
+ $arr = $translate['item'];
}
if((x($arr,'obj')) && is_array($arr['obj'])) {
@@ -1578,7 +1609,6 @@ function item_store($arr, $allow_exec = false, $deliver = true) {
$arr['aid'] = ((x($arr,'aid')) ? intval($arr['aid']) : 0);
$arr['mid'] = ((x($arr,'mid')) ? notags(trim($arr['mid'])) : random_string());
$arr['revision'] = ((x($arr,'revision') && intval($arr['revision']) > 0) ? intval($arr['revision']) : 0);
-logger('revision: ' . $arr['revision']);
$arr['author_xchan'] = ((x($arr,'author_xchan')) ? notags(trim($arr['author_xchan'])) : '');
$arr['owner_xchan'] = ((x($arr,'owner_xchan')) ? notags(trim($arr['owner_xchan'])) : '');
@@ -1715,7 +1745,7 @@ logger('revision: ' . $arr['revision']);
if($r[0]['owner_xchan'] !== $arr['owner_xchan']) {
$arr['owner_xchan'] = $r[0]['owner_xchan'];
-// $uplinked_comment = true;
+ // $uplinked_comment = true;
}
// if the parent is private, force privacy for the entire conversation
@@ -1804,9 +1834,12 @@ logger('revision: ' . $arr['revision']);
intval($arr['revision'])
);
- if($r && count($r)) {
+ if($r) {
+ // This will gives us a fresh copy of what's now in the DB and undo the db escaping,
+ // which really messes up the notifications
+
$current_post = $r[0]['id'];
- $arr = $r[0]; // This will gives us a fresh copy of what's now in the DB and undo the db escaping, which really messes up the notifications
+ $arr = $r[0];
logger('item_store: created item ' . $current_post, LOGGER_DEBUG);
}
else {
@@ -1865,7 +1898,7 @@ logger('revision: ' . $arr['revision']);
// update the commented timestamp on the parent - unless this is potentially a clone of an older item
// which we don't wish to bring to the surface. As the queue only holds deliveries for 3 days, it's
- // suspected of being an older cloned item if the creation time is older than that.
+ // suspected of being an older cloned item if the creation time is older than that.
if($arr['created'] > datetime_convert('','','now - 4 days')) {
$z = q("select max(created) as commented from item where parent_mid = '%s' and uid = %d and item_delayed = 0 ",
@@ -1911,7 +1944,7 @@ function item_store_update($arr,$allow_exec = false, $deliver = true) {
if(array_key_exists('cancel',$arr) && $arr['cancel']) {
logger('cancelled by plugin');
return $ret;
- }
+ }
if(! intval($arr['uid'])) {
logger('item_store_update: no uid');
@@ -1953,46 +1986,38 @@ function item_store_update($arr,$allow_exec = false, $deliver = true) {
return $ret;
}
- if((! array_key_exists('item_obscured', $arr)) || $arr['item_obscured'] == 0) {
+ $arr['lang'] = detect_language($arr['body']);
- $arr['lang'] = detect_language($arr['body']);
+ // apply the input filter here
- // apply the input filter here - if it is obscured it has been filtered already
- $arr['body'] = trim(z_input_filter($arr['uid'],$arr['body'],$arr['mimetype']));
+ $arr['body'] = trim(z_input_filter($arr['body'],$arr['mimetype'],$allow_exec));
- if(local_channel() && (local_channel() == $arr['uid']) && (! $arr['sig'])) {
- $channel = App::get_channel();
- if($channel['channel_hash'] === $arr['author_xchan']) {
- $arr['sig'] = base64url_encode(rsa_sign($arr['body'],$channel['channel_prvkey']));
- $arr['item_verified'] = 1;
- }
- }
+ item_sign($arr);
- $allowed_languages = get_pconfig($arr['uid'],'system','allowed_languages');
+ $allowed_languages = get_pconfig($arr['uid'],'system','allowed_languages');
- if((is_array($allowed_languages)) && ($arr['lang']) && (! array_key_exists($arr['lang'],$allowed_languages))) {
- $translate = array('item' => $arr, 'from' => $arr['lang'], 'to' => $allowed_languages, 'translated' => false);
- call_hooks('item_translate', $translate);
- if((! $translate['translated']) && (intval(get_pconfig($arr['uid'],'system','reject_disallowed_languages')))) {
- logger('item_store: language ' . $arr['lang'] . ' not accepted for uid ' . $arr['uid']);
- $ret['message'] = 'language not accepted';
- return $ret;
- }
- $arr = $translate['item'];
+ if((is_array($allowed_languages)) && ($arr['lang']) && (! array_key_exists($arr['lang'],$allowed_languages))) {
+ $translate = array('item' => $arr, 'from' => $arr['lang'], 'to' => $allowed_languages, 'translated' => false);
+ call_hooks('item_translate', $translate);
+ if((! $translate['translated']) && (intval(get_pconfig($arr['uid'],'system','reject_disallowed_languages')))) {
+ logger('item_store: language ' . $arr['lang'] . ' not accepted for uid ' . $arr['uid']);
+ $ret['message'] = 'language not accepted';
+ return $ret;
}
+ $arr = $translate['item'];
}
- if((x($arr,'obj')) && is_array($arr['obj'])) {
+ if((array_key_exists('obj',$arr)) && is_array($arr['obj'])) {
activity_sanitise($arr['obj']);
$arr['obj'] = json_encode($arr['obj']);
}
- if((x($arr,'target')) && is_array($arr['target'])) {
+ if((array_key_exists('target',$arr)) && is_array($arr['target'])) {
activity_sanitise($arr['target']);
$arr['target'] = json_encode($arr['target']);
}
- if((x($arr,'attach')) && is_array($arr['attach'])) {
+ if((array_key_exists('attach',$arr)) && is_array($arr['attach'])) {
activity_sanitise($arr['attach']);
$arr['attach'] = json_encode($arr['attach']);
}
@@ -2025,7 +2050,7 @@ function item_store_update($arr,$allow_exec = false, $deliver = true) {
$arr['changed'] = $orig[0]['changed'];
$arr['route'] = ((array_key_exists('route',$arr)) ? trim($arr['route']) : $orig[0]['route']);
- $arr['diaspora_meta'] = ((x($arr,'diaspora_meta')) ? $arr['diaspora_meta'] : $orig[0]['diaspora_meta']);
+
$arr['location'] = ((x($arr,'location')) ? notags(trim($arr['location'])) : $orig[0]['location']);
$arr['coord'] = ((x($arr,'coord')) ? notags(trim($arr['coord'])) : $orig[0]['coord']);
$arr['verb'] = ((x($arr,'verb')) ? notags(trim($arr['verb'])) : $orig[0]['verb']);
@@ -2184,55 +2209,6 @@ function item_store_update($arr,$allow_exec = false, $deliver = true) {
-function store_diaspora_comment_sig($datarray, $channel, $parent_item, $post_id, $walltowall = false) {
-
- // We won't be able to sign Diaspora comments for authenticated visitors
- // - we don't have their private key
-
- // since Diaspora doesn't handle edits we can only do this for the original text and not update it.
-
- require_once('include/markdown.php');
- $signed_body = bb2diaspora_itembody($datarray,$walltowall);
-
- if($walltowall) {
- logger('wall to wall comment',LOGGER_DEBUG);
- // post will come across with the owner's identity. Throw a preamble onto the post to indicate the true author.
- $signed_body = "\n\n"
- . '![' . $datarray['author']['xchan_name'] . '](' . $datarray['author']['xchan_photo_m'] . ')'
- . '[' . $datarray['author']['xchan_name'] . '](' . $datarray['author']['xchan_url'] . ')' . "\n\n"
- . $signed_body;
- }
-
- logger('storing diaspora comment signature',LOGGER_DEBUG);
-
- $diaspora_handle = channel_reddress($channel);
-
- $signed_text = $datarray['mid'] . ';' . $parent_item['mid'] . ';' . $signed_body . ';' . $diaspora_handle;
-
-
- if( $channel && $channel['channel_prvkey'] )
- $authorsig = base64_encode(rsa_sign($signed_text, $channel['channel_prvkey'], 'sha256'));
- else
- $authorsig = '';
-
- $x = array('signer' => $diaspora_handle, 'body' => $signed_body, 'signed_text' => $signed_text, 'signature' => $authorsig);
-
- $y = json_encode($x);
-
- $r = q("update item set diaspora_meta = '%s' where id = %d",
- dbesc($y),
- intval($post_id)
- );
-
-
- if(! $r)
- logger('store_diaspora_comment_sig: DB write failed');
-
- return;
-}
-
-
-
function send_status_notifications($post_id,$item) {
// only send notifications for comments
@@ -2484,7 +2460,7 @@ function tag_deliver($uid, $item_id) {
* Now we've got those out of the way. Let's see if this is a post that's tagged for re-delivery
*/
- $terms = get_terms_oftype($item['term'],TERM_MENTION);
+ $terms = array_merge(get_terms_oftype($item['term'],TERM_MENTION),get_terms_oftype($item['term'],TERM_FORUM));
if($terms)
logger('tag_deliver: post mentions: ' . print_r($terms,true), LOGGER_DATA);
@@ -2511,15 +2487,7 @@ function tag_deliver($uid, $item_id) {
// Now let's check if this mention was inside a reshare so we don't spam a forum
// If it's private we may have to unobscure it momentarily so that we can parse it.
- $body = '';
-
- if(intval($item['item_obscured'])) {
- $key = get_config('system','prvkey');
- if($item['body'])
- $body = crypto_unencapsulate(json_decode($item['body'],true),$key);
- }
- else
- $body = $item['body'];
+ $body = $item['body'];
$body = preg_replace('/\[share(.*?)\[\/share\]/','',$body);
@@ -2527,22 +2495,46 @@ function tag_deliver($uid, $item_id) {
$plustagged = false;
$matches = array();
- $pattern = '/@\!?\[zrl\=' . preg_quote($term['url'],'/') . '\]' . preg_quote($term['term'],'/') . '\[\/zrl\]/';
+ $pattern = '/[\!@]\!?\[zrl\=' . preg_quote($term['url'],'/') . '\]' . preg_quote($term['term'],'/') . '\[\/zrl\]/';
if(preg_match($pattern,$body,$matches))
$tagged = true;
- $pattern = '/@\!?\[zrl\=([^\]]*?)\]((?:.(?!\[zrl\=))*?)\+\[\/zrl\]/';
+ // original red forum tagging sequence @forumname+
+ // standard forum tagging sequence !forumname
+
+ $pluspattern = '/@\!?\[zrl\=([^\]]*?)\]((?:.(?!\[zrl\=))*?)\+\[\/zrl\]/';
+
+ $forumpattern = '/\!\!?\[zrl\=([^\]]*?)\]((?:.(?!\[zrl\=))*?)\[\/zrl\]/';
+
+ $found = false;
- if(preg_match_all($pattern,$body,$matches,PREG_SET_ORDER)) {
- $max_forums = get_config('system','max_tagged_forums');
- if(! $max_forums)
- $max_forums = 2;
- $matched_forums = 0;
+ $max_forums = get_config('system','max_tagged_forums');
+ if(! $max_forums)
+ $max_forums = 2;
+ $matched_forums = 0;
+ $matches = array();
+
+ if(preg_match_all($pluspattern,$body,$matches,PREG_SET_ORDER)) {
foreach($matches as $match) {
$matched_forums ++;
if($term['url'] === $match[1] && $term['term'] === $match[2]) {
if($matched_forums <= $max_forums) {
$plustagged = true;
+ $found = true;
+ break;
+ }
+ logger('forum ' . $term['term'] . ' exceeded max_tagged_forums - ignoring');
+ }
+ }
+ }
+
+ if(preg_match_all($forumpattern,$body,$matches,PREG_SET_ORDER)) {
+ foreach($matches as $match) {
+ $matched_forums ++;
+ if($term['url'] === $match[1] && $term['term'] === $match[2]) {
+ if($matched_forums <= $max_forums) {
+ $plustagged = true;
+ $found = true;
break;
}
logger('forum ' . $term['term'] . ' exceeded max_tagged_forums - ignoring');
@@ -2641,7 +2633,8 @@ function tgroup_check($uid,$item) {
if(! $u)
return false;
- $terms = get_terms_oftype($item['term'],TERM_MENTION);
+
+ $terms = array_merge(get_terms_oftype($item['term'],TERM_MENTION),get_terms_oftype($item['term'],TERM_FORUM));
if($terms)
logger('tgroup_check: post mentions: ' . print_r($terms,true), LOGGER_DATA);
@@ -2670,25 +2663,36 @@ function tgroup_check($uid,$item) {
$body = $item['body'];
- if(array_key_exists('item_obscured',$item) && intval($item['item_obscured']) && $body) {
- $key = get_config('system','prvkey');
- $body = crypto_unencapsulate(json_decode($body,true),$key);
- }
-
$body = preg_replace('/\[share(.*?)\[\/share\]/','',$body);
-// $pattern = '/@\!?\[zrl\=' . preg_quote($term['url'],'/') . '\]' . preg_quote($term['term'] . '+','/') . '\[\/zrl\]/';
- $pattern = '/@\!?\[zrl\=([^\]]*?)\]((?:.(?!\[zrl\=))*?)\+\[\/zrl\]/';
+ $pluspattern = '/@\!?\[zrl\=([^\]]*?)\]((?:.(?!\[zrl\=))*?)\+\[\/zrl\]/';
+
+ $forumpattern = '/\!\!?\[zrl\=([^\]]*?)\]((?:.(?!\[zrl\=))*?)\[\/zrl\]/';
+
$found = false;
+
+ $max_forums = get_config('system','max_tagged_forums');
+ if(! $max_forums)
+ $max_forums = 2;
+ $matched_forums = 0;
$matches = array();
- if(preg_match_all($pattern,$body,$matches,PREG_SET_ORDER)) {
- $max_forums = get_config('system','max_tagged_forums');
- if(! $max_forums)
- $max_forums = 2;
- $matched_forums = 0;
+ if(preg_match_all($pluspattern,$body,$matches,PREG_SET_ORDER)) {
+ foreach($matches as $match) {
+ $matched_forums ++;
+ if($term['url'] === $match[1] && $term['term'] === $match[2]) {
+ if($matched_forums <= $max_forums) {
+ $found = true;
+ break;
+ }
+ logger('forum ' . $term['term'] . ' exceeded max_tagged_forums - ignoring');
+ }
+ }
+ }
+
+ if(preg_match_all($forumpattern,$body,$matches,PREG_SET_ORDER)) {
foreach($matches as $match) {
$matched_forums ++;
if($term['url'] === $match[1] && $term['term'] === $match[2]) {
@@ -2768,7 +2772,6 @@ function start_delivery_chain($channel, $item, $item_id, $parent) {
$item_origin = 1;
$item_uplink = 0;
$item_nocomment = 0;
- $item_obscured = 0;
$flag_bits = $item['item_flags'];
@@ -2791,11 +2794,10 @@ function start_delivery_chain($channel, $item, $item_id, $parent) {
$title = $item['title'];
$body = $item['body'];
- $r = q("update item set item_uplink = %d, item_nocomment = %d, item_obscured = %d, item_flags = %d, owner_xchan = '%s', allow_cid = '%s', allow_gid = '%s',
+ $r = q("update item set item_uplink = %d, item_nocomment = %d, item_flags = %d, owner_xchan = '%s', allow_cid = '%s', allow_gid = '%s',
deny_cid = '%s', deny_gid = '%s', item_private = %d, public_policy = '%s', comment_policy = '%s', title = '%s', body = '%s', item_wall = %d, item_origin = %d where id = %d",
intval($item_uplink),
intval($item_nocomment),
- intval($item_obscured),
intval($flag_bits),
dbesc($channel['channel_hash']),
dbesc($channel['channel_allow_cid']),
@@ -2980,13 +2982,21 @@ function mail_store($arr) {
return 0;
}
+ $channel = channelx_by_n($arr['channel_id']);
+
if(! $arr['mail_obscured']) {
if((strpos($arr['body'],'<') !== false) || (strpos($arr['body'],'>') !== false))
$arr['body'] = escape_tags($arr['body']);
}
- if(array_key_exists('attach',$arr) && is_array($arr['attach']))
- $arr['attach'] = json_encode($arr['attach']);
+ if(array_key_exists('attach',$arr)) {
+ if(is_array($arr['attach'])) {
+ $arr['attach'] = json_encode($arr['attach']);
+ }
+ }
+ else {
+ $arr['attach'] = '';
+ }
$arr['account_id'] = ((x($arr,'account_id')) ? intval($arr['account_id']) : 0);
$arr['mid'] = ((x($arr,'mid')) ? notags(trim($arr['mid'])) : random_string());
@@ -2997,15 +3007,41 @@ function mail_store($arr) {
$arr['title'] = ((x($arr,'title')) ? trim($arr['title']) : '');
$arr['parent_mid'] = ((x($arr,'parent_mid')) ? notags(trim($arr['parent_mid'])) : '');
$arr['body'] = ((x($arr,'body')) ? trim($arr['body']) : '');
+ $arr['sig'] = ((x($arr,'sig')) ? trim($arr['sig']) : '');
$arr['conv_guid'] = ((x($arr,'conv_guid')) ? trim($arr['conv_guid']) : '');
+ $arr['mail_mimetype'] = ((x($arr,'mail_mimetype')) ? trim($arr['mail_mimetype']) : 'text/bbcode');
$arr['mail_flags'] = ((x($arr,'mail_flags')) ? intval($arr['mail_flags']) : 0 );
+ $arr['mail_raw'] = ((x($arr,'mail_raw')) ? intval($arr['mail_raw']) : 0 );
+
+
- if(! $arr['parent_mid']) {
+ if($arr['parent_mid']) {
+ $parent_item = q("select * from mail where mid = '%s' and channel_id = %d limit 1",
+ dbesc($arr['parent_mid']),
+ intval($arr['channel_id'])
+ );
+ if(($parent_item) && (! $arr['conv_guid'])) {
+ $arr['conv_guid'] = $parent_item[0]['conv_guid'];
+ }
+ }
+ else {
logger('mail_store: missing parent');
$arr['parent_mid'] = $arr['mid'];
}
+ if($arr['from_xchan'] === $channel['channel_hash'])
+ $conversant = $arr['to_xchan'];
+ else
+ $conversant = $arr['from_xchan'];
+
+
+ if(! $arr['conv_guid']) {
+ $x = create_conversation($channel,$conversant,(($arr['title']) ? base64url_decode(str_rot47($arr['title'])) : ''));
+ $arr['conv_guid'] = (($x) ? $x['guid'] : '');
+ }
+
+
$r = q("SELECT id FROM mail WHERE mid = '%s' AND channel_id = %d LIMIT 1",
dbesc($arr['mid']),
intval($arr['channel_id'])
@@ -3070,6 +3106,14 @@ function mail_store($arr) {
Zlib\Enotify::submit($notif_params);
}
+ if($arr['conv_guid']) {
+ $c = q("update conv set updated = '%s' where guid = '%s' and uid = %d",
+ dbesc(datetime_convert()),
+ dbesc($arr['conv_guid']),
+ intval($arr['channel_id'])
+ );
+ }
+
call_hooks('post_mail_end',$arr);
return $current_post;
}
@@ -3769,7 +3813,7 @@ function zot_feed($uid,$observer_hash,$arr) {
if(! is_sys_channel($uid))
$sql_extra = item_permissions_sql($uid,$observer_hash);
- $limit = " LIMIT 100 ";
+ $limit = " LIMIT 5000 ";
if($mindate > NULL_DATE) {
$sql_extra .= " and ( created > '$mindate' or changed > '$mindate' ) ";
@@ -3781,15 +3825,7 @@ function zot_feed($uid,$observer_hash,$arr) {
}
- $items = array();
-
- /** @FIXME re-unite these SQL statements. There is no need for them to be separate. The mySQL is convoluted with misuse of group by. As it stands, there is a slight difference where the postgres version doesn't remove the duplicate parents up to 100. In practice this doesn't matter. It could be made to match behavior by adding "distinct on (parent) " to the front of the selection list, at a not-worth-it performance penalty (page temp results to disk). duplicates are still ignored in the in() clause, you just get less than 100 parents if there are many children. */
-
- if(ACTIVE_DBTYPE == DBTYPE_POSTGRES) {
- $groupby = '';
- } else {
- $groupby = 'GROUP BY parent';
- }
+ $items = [];
$item_normal = item_normal();
@@ -3798,7 +3834,7 @@ function zot_feed($uid,$observer_hash,$arr) {
WHERE uid != %d
$item_normal
AND item_wall = 1
- and item_private = 0 $sql_extra $groupby ORDER BY created ASC $limit",
+ and item_private = 0 $sql_extra ORDER BY created ASC $limit",
intval($uid)
);
}
@@ -3806,19 +3842,25 @@ function zot_feed($uid,$observer_hash,$arr) {
$r = q("SELECT parent, created, postopts from item
WHERE uid = %d $item_normal
AND item_wall = 1
- $sql_extra $groupby ORDER BY created ASC $limit",
+ $sql_extra ORDER BY created ASC $limit",
intval($uid)
);
}
+ $parents = [];
+
if($r) {
- for($x = 0; $x < count($r); $x ++) {
- if(strpos($r[$x]['postopts'],'nodeliver') !== false) {
- unset($r[$x]);
- }
+ foreach($r as $rv) {
+ if(array_key_exists($rv['parent'],$parents))
+ continue;
+ if(strpos($rv['postopts'],'nodeliver') !== false)
+ continue;
+ $parents[$rv['parent']] = $rv;
+ if(count($parents) > 200)
+ break;
}
- $parents_str = ids_to_querystr($r,'parent');
+ $parents_str = ids_to_querystr($parents,'parent');
$sys_query = ((is_sys_channel($uid)) ? $sql_extra : '');
$item_normal = item_normal();
@@ -3936,6 +3978,10 @@ function items_fetch($arr,$channel = null,$observer_hash = null,$client_mode = C
}
}
+ if($channel && intval($arr['compat']) === 1) {
+ $sql_extra = " AND author_xchan = '" . $channel['channel_hash'] . "' and item_private = 0 ";
+ }
+
if ($arr['datequery']) {
$sql_extra3 .= protect_sprintf(sprintf(" AND item.created <= '%s' ", dbesc(datetime_convert('UTC','UTC',$arr['datequery']))));
}
@@ -3943,11 +3989,6 @@ function items_fetch($arr,$channel = null,$observer_hash = null,$client_mode = C
$sql_extra3 .= protect_sprintf(sprintf(" AND item.created >= '%s' ", dbesc(datetime_convert('UTC','UTC',$arr['datequery2']))));
}
- if(! array_key_exists('nouveau',$arr)) {
- $sql_extra2 = " AND item.parent = item.id ";
-// $sql_extra3 = '';
- }
-
if($arr['search']) {
if(strpos($arr['search'],'#') === 0)
@@ -4019,7 +4060,8 @@ function items_fetch($arr,$channel = null,$observer_hash = null,$client_mode = C
if($arr['item_type'] === '*')
$item_restrict = '';
- if ($arr['nouveau'] && ($client_mode & CLIENT_MODE_LOAD) && $channel) {
+ if ((($arr['compat']) || ($arr['nouveau'] && ($client_mode & CLIENT_MODE_LOAD))) && $channel) {
+
// "New Item View" - show all items unthreaded in reverse created date order
$items = q("SELECT item.*, item.id AS item_id FROM item
@@ -4091,7 +4133,7 @@ function items_fetch($arr,$channel = null,$observer_hash = null,$client_mode = C
//$third = dba_timer();
- $items = fetch_post_tags($items,true);
+ $items = fetch_post_tags($items,false);
//$fourth = dba_timer();
@@ -4119,6 +4161,8 @@ function webpage_to_namespace($webpage) {
$page_type = 'BUILDBLOCK';
elseif($webpage == ITEM_TYPE_PDL)
$page_type = 'PDL';
+ elseif($webpage == ITEM_TYPE_CARD)
+ $page_type = 'CARD';
elseif($webpage == ITEM_TYPE_DOC)
$page_type = 'docfile';
else
@@ -4314,10 +4358,7 @@ function sync_an_item($channel_id,$item_id) {
if($r) {
xchan_query($r);
$sync_item = fetch_post_tags($r);
- $rid = q("select * from item_id where iid = %d",
- intval($item_id)
- );
- build_sync_packet($channel_d,array('item' => array(encode_item($sync_item[0],true)),'item_id' => $rid));
+ build_sync_packet($channel_d,array('item' => array(encode_item($sync_item[0],true))));
}
}
@@ -4475,12 +4516,12 @@ function item_create_edit_activity($post) {
$new_item['id'] = 0;
$new_item['parent'] = 0;
$new_item['mid'] = item_message_id();
-
+
$new_item['body'] = sprintf( t('[Edited %s]'), (($update_item['item_thread_top']) ? t('Post','edit_activity') : t('Comment','edit_activity')));
$new_item['body'] .= "\n\n";
$new_item['body'] .= $update_item['body'];
-
+
$new_item['sig'] = '';
$new_item['verb'] = ACTIVITY_UPDATE;
@@ -4506,10 +4547,10 @@ function item_create_edit_activity($post) {
array('rel' => 'photo', 'type' => $item_author['xchan_photo_mimetype'], 'href' => $item_author['xchan_photo_m'])),
),
));
-
- $x = post_activity_item($new_item);
+
+ $x = post_activity_item($new_item);
$post_id = $x['id'];
if($post_id) {
@@ -4524,5 +4565,5 @@ function item_create_edit_activity($post) {
}
\Zotlabs\Daemon\Master::Summon(array('Notifier', 'edit_activity', $post_id));
-
+
}
diff --git a/include/markdown.php b/include/markdown.php
index 7afdc6c54..0464cf71a 100644
--- a/include/markdown.php
+++ b/include/markdown.php
@@ -4,144 +4,13 @@
* @brief Some functions for BB conversions for Diaspora protocol.
*/
+use Michelf\MarkdownExtra;
+use League\HTMLToMarkdown\HtmlConverter;
+
require_once("include/oembed.php");
require_once("include/event.php");
-require_once("library/markdown.php");
require_once("include/html2bbcode.php");
require_once("include/bbcode.php");
-require_once("library/markdownify/markdownify.php");
-
-
-function get_bb_tag_pos($s, $name, $occurance = 1) {
-
- if($occurance < 1)
- $occurance = 1;
-
- $start_open = -1;
- for($i = 1; $i <= $occurance; $i++) {
- if( $start_open !== false)
- $start_open = strpos($s, '[' . $name, $start_open + 1); // allow [name= type tags
- }
-
- if( $start_open === false)
- return false;
-
- $start_equal = strpos($s, '=', $start_open);
- $start_close = strpos($s, ']', $start_open);
-
- if( $start_close === false)
- return false;
-
- $start_close++;
-
- $end_open = strpos($s, '[/' . $name . ']', $start_close);
-
- if( $end_open === false)
- return false;
-
- $res = array( 'start' => array('open' => $start_open, 'close' => $start_close),
- 'end' => array('open' => $end_open, 'close' => $end_open + strlen('[/' . $name . ']')) );
- if( $start_equal !== false)
- $res['start']['equal'] = $start_equal + 1;
-
- return $res;
-}
-
-function bb_tag_preg_replace($pattern, $replace, $name, $s) {
-
- $string = $s;
-
- $occurance = 1;
- $pos = get_bb_tag_pos($string, $name, $occurance);
- while($pos !== false && $occurance < 1000) {
-
- $start = substr($string, 0, $pos['start']['open']);
- $subject = substr($string, $pos['start']['open'], $pos['end']['close'] - $pos['start']['open']);
- $end = substr($string, $pos['end']['close']);
- if($end === false)
- $end = '';
-
- $subject = preg_replace($pattern, $replace, $subject);
- $string = $start . $subject . $end;
-
- $occurance++;
- $pos = get_bb_tag_pos($string, $name, $occurance);
- }
-
- return $string;
-}
-
-function share_shield($m) {
- return str_replace($m[1],'!=+=+=!' . base64url_encode($m[1]) . '=+!=+!=',$m[0]);
-}
-
-function share_unshield($m) {
- $x = str_replace(array('!=+=+=!','=+!=+!='),array('',''),$m[1]);
- return str_replace($m[1], base64url_decode($x), $m[0]);
-}
-
-
-function diaspora_mention_callback($matches) {
-
- $webbie = $matches[2] . '@' . $matches[3];
- $link = '';
- if($webbie) {
- $r = q("select * from hubloc left join xchan on hubloc_hash = xchan_hash where hubloc_addr = '%s' limit 1",
- dbesc($webbie)
- );
- if(! $r) {
- $x = discover_by_webbie($webbie);
- if($x) {
- $r = q("select * from hubloc left join xchan on hubloc_hash = xchan_hash where hubloc_addr = '%s' limit 1",
- dbesc($webbie)
- );
- }
- }
- if($r)
- $link = $r[0]['xchan_url'];
- }
- if(! $link)
- $link = 'https://' . $matches[3] . '/u/' . $matches[2];
-
- if($r && $r[0]['hubloc_network'] === 'zot')
- return '@[zrl=' . $link . ']' . trim($matches[1]) . ((substr($matches[0],-1,1) === '+') ? '+' : '') . '[/zrl]' ;
- else
- return '@[url=' . $link . ']' . trim($matches[1]) . ((substr($matches[0],-1,1) === '+') ? '+' : '') . '[/url]' ;
-
-}
-
-function diaspora_mention_callback2($matches) {
-
- $webbie = $matches[1] . '@' . $matches[2];
- $link = '';
- if($webbie) {
- $r = q("select * from hubloc left join xchan on hubloc_hash = xchan_hash where hubloc_addr = '%s' limit 1",
- dbesc($webbie)
- );
- if(! $r) {
- $x = discover_by_webbie($webbie);
- if($x) {
- $r = q("select * from hubloc left join xchan on hubloc_hash = xchan_hash where hubloc_addr = '%s' limit 1",
- dbesc($webbie)
- );
- }
- }
- if($r)
- $link = $r[0]['xchan_url'];
- }
-
- $name = (($r) ? $r[0]['xchan_name'] : $matches[1]);
-
- if(! $link)
- $link = 'https://' . $matches[2] . '/u/' . $matches[1];
-
- if($r && $r[0]['hubloc_network'] === 'zot')
- return '@[zrl=' . $link . ']' . trim($name) . ((substr($matches[0],-1,1) === '+') ? '+' : '') . '[/zrl]' ;
- else
- return '@[url=' . $link . ']' . trim($name) . ((substr($matches[0],-1,1) === '+') ? '+' : '') . '[/url]' ;
-
-}
-
/**
@@ -156,52 +25,53 @@ function diaspora_mention_callback2($matches) {
* @param boolean $use_zrl default false
* @return string
*/
-function markdown_to_bb($s, $use_zrl = false) {
- $s = str_replace("&#xD;","\r",$s);
- $s = str_replace("&#xD;\n&gt;","",$s);
+function markdown_to_bb($s, $use_zrl = false, $options = []) {
+
if(is_array($s)) {
btlogger('markdown_to_bb called with array. ' . print_r($s,true), LOGGER_NORMAL, LOG_WARNING);
return '';
}
+
+ $s = str_replace("&#xD;","\r",$s);
+ $s = str_replace("&#xD;\n&gt;","",$s);
+
$s = html_entity_decode($s,ENT_COMPAT,'UTF-8');
// if empty link text replace with the url
$s = preg_replace("/\[\]\((.*?)\)/ism",'[$1]($1)',$s);
- // first try plustags
+ $x = [ 'text' => $s , 'zrl' => $use_zrl, 'options' => $options ];
- $s = preg_replace_callback('/\@\{(.+?)\; (.+?)\@(.+?)\}\+/','diaspora_mention_callback',$s);
- $s = preg_replace_callback('/\@\{(.+?)\; (.+?)\@(.+?)\}/','diaspora_mention_callback',$s);
+ call_hooks('markdown_to_bb_init',$x);
- $s = preg_replace_callback('/\@\{(.+?)\@(.+?)\}\+/','diaspora_mention_callback2',$s);
- $s = preg_replace_callback('/\@\{(.+?)\@(.+?)\}/','diaspora_mention_callback2',$s);
+ $s = $x['text'];
- // Escaping the hash tags - doesn't always seem to work
- // $s = preg_replace('/\#([^\s\#])/','\\#$1',$s);
- // This seems to work
+ // Escaping the hash tags
$s = preg_replace('/\#([^\s\#])/','&#35;$1',$s);
- $s = Markdown($s);
+ $s = MarkdownExtra::defaultTransform($s);
- $s = str_replace("\r","",$s);
+ if($options && $options['preserve_lf']) {
+ $s = str_replace(["\r","\n"],["",'<br>'],$s);
+ }
+ else {
+ $s = str_replace("\r","",$s);
+ }
$s = str_replace('&#35;','#',$s);
$s = html2bbcode($s);
- // protect the recycle symbol from turning into a tag, but without unescaping angles and naked ampersands
- $s = str_replace('&#x2672;',html_entity_decode('&#x2672;',ENT_QUOTES,'UTF-8'),$s);
-
// Convert everything that looks like a link to a link
if($use_zrl) {
$s = str_replace(array('[img','/img]'),array('[zmg','/zmg]'),$s);
- $s = preg_replace("/([^\]\=]|^)(https?\:\/\/)([a-zA-Z0-9\:\/\-\?\&\;\.\=\_\~\#\%\$\!\+\,\(\)]+)/ism", '$1[zrl=$2$3]$2$3[/zrl]',$s);
+ $s = preg_replace("/([^\]\=]|^)(https?\:\/\/)([a-zA-Z0-9\:\/\-\?\&\;\.\=\_\~\#\%\$\!\+\,\@\(\)]+)/ism", '$1[zrl=$2$3]$2$3[/zrl]',$s);
}
else {
- $s = preg_replace("/([^\]\=]|^)(https?\:\/\/)([a-zA-Z0-9\:\/\-\?\&\;\.\=\_\~\#\%\$\!\+\,\(\)]+)/ism", '$1[url=$2$3]$2$3[/url]',$s);
+ $s = preg_replace("/([^\]\=]|^)(https?\:\/\/)([a-zA-Z0-9\:\/\-\?\&\;\.\=\_\~\#\%\$\!\+\,\@\(\)]+)/ism", '$1[url=$2$3]$2$3[/url]',$s);
}
// remove duplicate adjacent code tags
@@ -216,291 +86,108 @@ function markdown_to_bb($s, $use_zrl = false) {
}
-function stripdcode_br_cb($s) {
- return '[code]' . str_replace('<br />', "\n\t", $s[1]) . '[/code]';
-}
-
-
-//////////////////////
-// The following "diaspora_ul" and "diaspora_ol" are only appropriate for the
-// pre-Markdownify conversion. If Markdownify isn't used, use the non-Markdownify
-// versions below
-//////////////////////
-/*
-function diaspora_ul($s) {
- // Replace "[*]" followed by any number (including zero) of
- // spaces by "* " to match Diaspora's list format
- if( strpos($s[0], "[list]") === 0 )
- return '<ul class="listbullet" style="list-style-type: circle;">' . preg_replace("/\[\*\]( *)/", "* ", $s[1]) . '</ul>';
- elseif( strpos($s[0], "[ul]") === 0 )
- return '<ul class="listbullet" style="list-style-type: circle;">' . preg_replace("/\[\*\]( *)/", "* ", $s[1]) . '</ul>';
- else
- return $s[0];
-}
-
-function diaspora_ol($s) {
- // A hack: Diaspora will create a properly-numbered ordered list even
- // if you use '1.' for each element of the list, like:
- // 1. First element
- // 1. Second element
- // 1. Third element
- if( strpos($s[0], "[list=1]") === 0 )
- return '<ul class="listdecimal" style="list-style-type: decimal;">' . preg_replace("/\[\*\]( *)/", "1. ", $s[1]) . '</ul>';
- elseif( strpos($s[0], "[list=i]") === 0 )
- return '<ul class="listlowerroman" style="list-style-type: lower-roman;">' . preg_replace("/\[\*\]( *)/", "1. ", $s[1]) . '</ul>';
- elseif( strpos($s[0], "[list=I]") === 0 )
- return '<ul class="listupperroman" style="list-style-type: upper-roman;">' . preg_replace("/\[\*\]( *)/", "1. ", $s[1]) . '</ul>';
- elseif( strpos($s[0], "[list=a]") === 0 )
- return '<ul class="listloweralpha" style="list-style-type: lower-alpha;">' . preg_replace("/\[\*\]( *)/", "1. ", $s[1]) . '</ul>';
- elseif( strpos($s[0], "[list=A]") === 0 )
- return '<ul class="listupperalpha" style="list-style-type: upper-alpha;">' . preg_replace("/\[\*\]( *)/", "1. ", $s[1]) . '</ul>';
- elseif( strpos($s[0], "[ol]") === 0 )
- return '<ul class="listdecimal" style="list-style-type: decimal;">' . preg_replace("/\[\*\]( *)/", "1. ", $s[1]) . '</ul>';
- else
- return $s[0];
-}
-*/
-
-//////////////////////
-// Non-Markdownify versions of "diaspora_ol" and "diaspora_ul"
-//////////////////////
-/**
- * @brief
- *
- * Replace "[\\*]" followed by any number (including zero) of
- * spaces by "* " to match Diaspora's list format.
- *
- * @param string $s
- * @return string
- */
-function diaspora_ul($s) {
- return preg_replace("/\[\\\\\*\]( *)/", "* ", $s[1]);
-}
-
-/**
- * @brief
- *
- * A hack: Diaspora will create a properly-numbered ordered list even
- * if you use '1.' for each element of the list, like:
- * \code
- * 1. First element
- * 1. Second element
- * 1. Third element
- * \endcode
- * @param string $s
- * @return string
- */
-function diaspora_ol($s) {
- return preg_replace("/\[\\\\\*\]( *)/", "1. ", $s[1]);
-}
-
-function bb2dmention_callback($match) {
-
- $r = q("select xchan_addr from xchan where xchan_url = '%s'",
- dbesc($match[2])
- );
-
- if($r)
- return '@{' . $match[3] . ' ; ' . $r[0]['xchan_addr'] . '}';
-
- return '@' . $match[3];
-}
-
-
-function bb2diaspora_itemwallwall(&$item,$uplink = false) {
-
- // We will provide wallwall (embedded author on the Diaspora side) if
- // 1. It is a wall-to-wall post
- // 2. A comment arrived which has no Diaspora signature info
-
-
- $wallwall = false;
- $author_exists = true;
-
- if(! array_key_exists('author',$item)) {
- $author_exists = false;
- logger('bb2diaspora_itemwallwall: no author');
- $r = q("select * from xchan where xchan_hash = '%s' limit 1",
- dbesc($item['author_xchan'])
- );
- if($r)
- $item['author'] = $r[0];
- }
-
- $has_meta = false;
- if($item['diaspora_meta'] || get_iconfig($item,'diaspora','fields'))
- $has_meta = true;
-
- if($item['author_xchan'] != $item['owner_xchan']) {
- if($item['mid'] == $item['parent_mid'])
- $wallwall = true;
- else {
- if(! $has_meta) {
- $wallwall = true;
- }
- }
- }
-
- if($uplink)
- $wallwall = true;
-
- if(($wallwall) && (is_array($item['author'])) && $item['author']['xchan_url'] && $item['author']['xchan_name'] && $item['author']['xchan_photo_s']) {
- logger('bb2diaspora_itemwallwall: wall to wall post',LOGGER_DEBUG);
- // post will come across with the owner's identity. Throw a preamble onto the post to indicate the true author.
- $item['body'] = "\n\n"
- . '[quote]'
- . '[img]' . $item['author']['xchan_photo_s'] . '[/img]'
- . ' '
- . '[url=' . $item['author']['xchan_url'] . '][b]' . $item['author']['xchan_name'] . '[/b][/url]' . "\n\n"
- . $item['body']
- . '[/quote]';
- }
-
- // $item['author'] might cause a surprise further down the line if it wasn't expected to be here.
-
- if(! $author_exists)
- unset($item['author']);
-}
-
-
-function bb2diaspora_itembody($item, $force_update = false, $have_channel = false, $uplink = false) {
-
-
- if(! get_iconfig($item,'diaspora','fields')) {
- $force_update = true;
- }
+function bb_to_markdown_share($match) {
$matches = array();
-
- if(($item['diaspora_meta']) && (! $force_update)) {
- $diaspora_meta = json_decode($item['diaspora_meta'],true);
- if($diaspora_meta) {
- if(array_key_exists('iv',$diaspora_meta)) {
- $key = get_config('system','prvkey');
- $meta = json_decode(crypto_unencapsulate($diaspora_meta,$key),true);
- }
- else {
- $meta = $diaspora_meta;
- }
- if($meta) {
- logger('bb2diaspora_itembody: cached ');
- $newitem = $item;
- $newitem['body'] = $meta['body'];
- return $newitem['body'];
- }
- }
+ $attributes = $match[1];
+
+ $author = "";
+ preg_match("/author='(.*?)'/ism", $attributes, $matches);
+ if ($matches[1] != "")
+ $author = urldecode($matches[1]);
+
+ $link = "";
+ preg_match("/link='(.*?)'/ism", $attributes, $matches);
+ if ($matches[1] != "")
+ $link = $matches[1];
+
+ $avatar = "";
+ preg_match("/avatar='(.*?)'/ism", $attributes, $matches);
+ if ($matches[1] != "")
+ $avatar = $matches[1];
+
+ $profile = "";
+ preg_match("/profile='(.*?)'/ism", $attributes, $matches);
+ if ($matches[1] != "")
+ $profile = $matches[1];
+
+ $posted = "";
+ preg_match("/posted='(.*?)'/ism", $attributes, $matches);
+ if ($matches[1] != "")
+ $posted = $matches[1];
+
+ // message_id is never used, do we still need it?
+ $message_id = "";
+ preg_match("/message_id='(.*?)'/ism", $attributes, $matches);
+ if ($matches[1] != "")
+ $message_id = $matches[1];
+
+ if(! $message_id) {
+ preg_match("/guid='(.*?)'/ism", $attributes, $matches);
+ if ($matches[1] != "")
+ $message_id = $matches[1];
}
- create_export_photo_body($item);
-
- $newitem = $item;
- if(array_key_exists('item_obscured',$item) && intval($item['item_obscured'])) {
- $key = get_config('system','prvkey');
- $b = json_decode($item['body'],true);
- // if called from diaspora_process_outbound, this decoding has already been done.
- // Everything else that calls us will not yet be decoded.
- if($b && is_array($b) && array_key_exists('iv',$b)) {
- $newitem['title'] = (($item['title']) ? crypto_unencapsulate(json_decode($item['title'],true),$key) : '');
- $newitem['body'] = (($item['body']) ? crypto_unencapsulate(json_decode($item['body'],true),$key) : '');
- }
- }
-
- if(! $have_channel)
- bb2diaspora_itemwallwall($newitem,$uplink);
+ $reldate = datetime_convert('UTC', date_default_timezone_get(), $posted, 'r');
- $title = $newitem['title'];
- $body = preg_replace('/\#\^http/i', 'http', $newitem['body']);
+ $headline = '';
- // protect tags and mentions from hijacking
+ if ($avatar != "")
+ $headline .= '[url=' . zid($profile) . '][img]' . $avatar . '[/img][/url]';
- if(intval(get_pconfig($item['uid'],'system','prevent_tag_hijacking'))) {
- $new_tag = html_entity_decode('&#x22d5;',ENT_COMPAT,'UTF-8');
- $new_mention = html_entity_decode('&#xff20;',ENT_COMPAT,'UTF-8');
+ // Bob Smith wrote the following post 2 hours ago
- // #-tags
- $body = preg_replace('/\#\[url/i', $new_tag . '[url', $body);
- $body = preg_replace('/\#\[zrl/i', $new_tag . '[zrl', $body);
- // @-mentions
- $body = preg_replace('/\@\!?\[url/i', $new_mention . '[url', $body);
- $body = preg_replace('/\@\!?\[zrl/i', $new_mention . '[zrl', $body);
- }
+ $fmt = sprintf( t('%1$s wrote the following %2$s %3$s'),
+ '[url=' . zid($profile) . ']' . $author . '[/url]',
+ '[url=' . zid($link) . ']' . t('post') . '[/url]',
+ $reldate
+ );
- // remove multiple newlines
- do {
- $oldbody = $body;
- $body = str_replace("\n\n\n", "\n\n", $body);
- } while ($oldbody != $body);
-
- $body = bb2diaspora($body);
-
- if(strlen($title))
- $body = "## " . $title . "\n\n" . $body;
-
- if($item['attach']) {
- $cnt = preg_match_all('/href=\"(.*?)\"(.*?)title=\"(.*?)\"/ism', $item['attach'], $matches, PREG_SET_ORDER);
- if($cnt) {
- $body .= "\n" . t('Attachments:') . "\n";
- foreach($matches as $mtch) {
- $body .= '[' . $mtch[3] . '](' . $mtch[1] . ')' . "\n";
- }
- }
- }
+ $headline .= $fmt . "\n\n";
-// logger('bb2diaspora_itembody : ' . $body, LOGGER_DATA);
+ $text = $headline . trim($match[2]);
- return html_entity_decode($body);
+ return $text;
}
-function bb2diaspora($Text,$preserve_nl = false, $fordiaspora = true) {
- // Re-enabling the converter again.
- // The bbcode parser now handles youtube-links (and the other stuff) correctly.
- // Additionally the html code is now fixed so that lists are now working.
+
+function bb_to_markdown($Text, $options = []) {
/*
* Transform #tags, strip off the [url] and replace spaces with underscore
*/
- $Text = preg_replace_callback('/#\[([zu])rl\=(\w+.*?)\](\w+.*?)\[\/[(zu)]rl\]/i', create_function('$match',
- 'return \'#\'. str_replace(\' \', \'_\', $match[3]);'
- ), $Text);
-
- $Text = preg_replace('/#\^\[([zu])rl\=(\w+.*?)\](\w+.*?)\[\/([zu])rl\]/i', '[$1rl=$2]$3[/$4rl]', $Text);
- $Text = preg_replace_callback('/\@\!?\[([zu])rl\=(\w+.*?)\](\w+.*?)\[\/([zu])rl\]/i', 'bb2dmention_callback', $Text);
+ $Text = preg_replace_callback('/#\[([zu])rl\=(.*?)\](.*?)\[\/[(zu)]rl\]/i',
+ create_function('$match', 'return \'#\'. str_replace(\' \', \'_\', $match[3]);'), $Text);
- // strip map tags, as the rendering is performed in bbcode() and the resulting output
- // is not compatible with Diaspora (at least in the case of openstreetmap and probably
- // due to the inclusion of an html iframe)
- $Text = preg_replace("/\[map\=(.*?)\]/ism", '$1', $Text);
- $Text = preg_replace("/\[map\](.*?)\[\/map\]/ism", '$1', $Text);
+ $Text = preg_replace('/#\^\[([zu])rl\=(.*?)\](.*?)\[\/([zu])rl\]/i', '[$1rl=$2]$3[/$4rl]', $Text);
// Converting images with size parameters to simple images. Markdown doesn't know it.
$Text = preg_replace("/\[img\=([0-9]*)x([0-9]*)\](.*?)\[\/img\]/ism", '[img]$3[/img]', $Text);
- // the following was added on 10-January-2012 due to an inability of Diaspora's
- // new javascript markdown processor to handle links with images as the link "text"
- // It is not optimal and may be removed if this ability is restored in the future
- //if ($fordiaspora)
- // $Text = preg_replace("/\[url\=([^\[\]]*)\]\s*\[img\](.*?)\[\/img\]\s*\[\/url\]/ism",
- // "[url]$1[/url]\n[img]$2[/img]", $Text);
+ $Text = preg_replace_callback("/\[share(.*?)\](.*?)\[\/share\]/ism", 'bb_to_markdown_share', $Text);
+
+ $x = [ 'bbcode' => $Text, 'options' => $options ];
+
+ call_hooks('bb_to_markdown_bb',$x);
+
+ $Text = $x['bbcode'];
// Convert it to HTML - don't try oembed
$Text = bbcode($Text, $preserve_nl, false);
- // Markdownify does not preserve previously escaped html entities such as <> and &.
-
+ // Markdownify does not preserve previously escaped html entities such as <> and &.
$Text = str_replace(array('&lt;','&gt;','&amp;'),array('&_lt_;','&_gt_;','&_amp_;'),$Text);
// Now convert HTML to Markdown
- $md = new Markdownify(false, false, false);
- $Text = $md->parseString($Text);
+ $Text = html2markdown($Text);
-
- // It also adds backslashes to our attempt at getting around the html entity preservation for some weird reason.
+ // It also adds backslashes to our attempt at getting around the html entity preservation for some weird reason.
$Text = str_replace(array('&\\_lt\\_;','&\\_gt\\_;','&\\_amp\\_;'),array('&lt;','&gt;','&amp;'),$Text);
@@ -510,58 +197,43 @@ function bb2diaspora($Text,$preserve_nl = false, $fordiaspora = true) {
// So take off the angle brackets of any such URL
$Text = preg_replace("/<http(.*?)>/is", "http$1", $Text);
- // Remove empty zrl links
+ // Remove empty zrl links
$Text = preg_replace("/\[zrl\=\].*?\[\/zrl\]/is", "", $Text);
- // Remove all unconverted tags
- $Text = strip_tags($Text);
-
- // Remove any leading or trailing whitespace, as this will mess up
- // the Diaspora signature verification and cause the item to disappear
-
$Text = trim($Text);
- call_hooks('bb2diaspora',$Text);
+ call_hooks('bb_to_markdown', $Text);
return $Text;
-}
-function unescape_underscores_in_links($m) {
- $y = str_replace('\\_','_', $m[2]);
- return('[' . $m[1] . '](' . $y . ')');
}
-function format_event_diaspora($ev) {
-
- if(! ((is_array($ev)) && count($ev)))
- return '';
-
- $bd_format = t('l F d, Y \@ g:i A') ; // Friday January 18, 2011 @ 8 AM
-
- $o = t('$Projectname event notification:') . "\n";
-
- $o .= '**' . (($ev['summary']) ? bb2diaspora($ev['summary']) : bb2diaspora($ev['desc'])) . '**' . "\n";
-
- $o .= t('Starts:') . ' ' . '['
- . (($ev['adjust']) ? day_translate(datetime_convert('UTC', 'UTC',
- $ev['start'] , $bd_format ))
- : day_translate(datetime_convert('UTC', 'UTC',
- $ev['start'] , $bd_format)))
- . '](' . z_root() . '/localtime/?f=&time=' . urlencode(datetime_convert('UTC','UTC',$ev['start'])) . ")\n";
- if(! $ev['nofinish'])
- $o .= t('Finishes:') . ' ' . '['
- . (($ev['adjust']) ? day_translate(datetime_convert('UTC', 'UTC',
- $ev['finish'] , $bd_format ))
- : day_translate(datetime_convert('UTC', 'UTC',
- $ev['finish'] , $bd_format )))
- . '](' . z_root() . '/localtime/?f=&time=' . urlencode(datetime_convert('UTC','UTC',$ev['finish'])) . ")\n";
- if(strlen($ev['location']))
- $o .= t('Location:') . bb2diaspora($ev['location'])
- . "\n";
-
- $o .= "\n";
+/**
+ * @brief Convert a HTML text into Markdown.
+ *
+ * This function uses the library league/html-to-markdown for this task.
+ *
+ * If the HTML text can not get parsed it will return an empty string.
+ *
+ * @see HTMLToMarkdown
+ *
+ * @param string $html The HTML code to convert
+ * @return string Markdown representation of the given HTML text, empty on error
+ */
+function html2markdown($html) {
+ $markdown = '';
+ $converter = new HtmlConverter();
+
+ try {
+ $markdown = $converter->convert($html);
+ } catch (InvalidArgumentException $e) {
+ logger("Invalid HTML. HTMLToMarkdown library threw an exception.");
+ }
- return $o;
+ // The old html 2 markdown library "pixel418/markdownify": "^2.2",
+ //$md = new HtmlConverter();
+ //$markdown = $md->convert($Text);
+ return $markdown;
}
diff --git a/include/message.php b/include/message.php
index bde07afd8..3f003e020 100644
--- a/include/message.php
+++ b/include/message.php
@@ -5,18 +5,26 @@
require_once('include/crypto.php');
require_once('include/attach.php');
+
+function mail_prepare_binary($item) {
+
+ return replace_macros(get_markup_template('item_binary.tpl'), [
+ '$download' => t('Download binary/encrypted content'),
+ '$url' => z_root() . '/mail/' . $item['id'] . '/download'
+ ]);
+}
+
+
// send a private message
-function send_message($uid = 0, $recipient = '', $body = '', $subject = '', $replyto = '', $expires = NULL_DATE) {
+function send_message($uid = 0, $recipient = '', $body = '', $subject = '', $replyto = '', $expires = NULL_DATE, $mimetype = 'text/bbcode', $raw = false) {
$ret = array('success' => false);
$is_reply = false;
- $a = get_app();
$observer_hash = get_observer_hash();
-
if($uid) {
$r = q("select * from channel where channel_id = %d limit 1",
intval($uid)
@@ -37,13 +45,15 @@ function send_message($uid = 0, $recipient = '', $body = '', $subject = '', $rep
$body = cleanup_bbcode($body);
$results = linkify_tags($a, $body, $uid);
-
- if(preg_match_all("/\[attachment\](.*?)\[\/attachment\]/",((strpos($body,'[/crypt]')) ? $_POST['media_str'] : $body),$match))
- $attaches = $match[1];
+ if(! $raw) {
+ if(preg_match_all("/\[attachment\](.*?)\[\/attachment\]/",((strpos($body,'[/crypt]')) ? $_POST['media_str'] : $body),$match)) {
+ $attaches = $match[1];
+ }
+ }
$attachments = '';
- if(preg_match_all('/(\[attachment\](.*?)\[\/attachment\])/',$body,$match)) {
+ if((! $raw) && preg_match_all('/(\[attachment\](.*?)\[\/attachment\])/',$body,$match)) {
$attachments = array();
foreach($match[2] as $mtch) {
$hash = substr($mtch,0,strpos($mtch,','));
@@ -94,38 +104,9 @@ function send_message($uid = 0, $recipient = '', $body = '', $subject = '', $rep
// create a new conversation
- $conv_guid = random_string();
-
- $recip = q("select * from xchan where xchan_hash = '%s' limit 1",
- dbesc($recipient)
- );
- if($recip)
- $recip_handle = $recip[0]['xchan_addr'];
-
- $sender_handle = channel_reddress($channel);
-
- $handles = $recip_handle . ';' . $sender_handle;
-
- if($subject)
- $nsubject = str_rot47(base64url_encode($subject));
-
- $r = q("insert into conv (uid,guid,creator,created,updated,subject,recips) values(%d, '%s', '%s', '%s', '%s', '%s', '%s') ",
- intval(local_channel()),
- dbesc($conv_guid),
- dbesc($sender_handle),
- dbesc(datetime_convert()),
- dbesc(datetime_convert()),
- dbesc($nsubject),
- dbesc($handles)
- );
-
- $r = q("select * from conv where guid = '%s' and uid = %d limit 1",
- dbesc($conv_guid),
- intval(local_channel())
- );
- if($r) {
- $retconv = $r[0];
- $retconv['subject'] = base64url_decode(str_rot47($retconv['subject']));
+ $retconv = create_conversation($channel,$recipient,$subject);
+ if($retconv) {
+ $conv_guid = $retconv['guid'];
}
}
@@ -136,7 +117,6 @@ function send_message($uid = 0, $recipient = '', $body = '', $subject = '', $rep
);
if($r) {
$retconv = $r[0];
- $retconv['subject'] = base64url_decode(str_rot47($retconv['subject']));
}
}
@@ -145,6 +125,12 @@ function send_message($uid = 0, $recipient = '', $body = '', $subject = '', $rep
return $ret;
}
+ $c = q("update conv set updated = '%s' where guid = '%s' and uid = %d",
+ dbesc(datetime_convert()),
+ dbesc($conv_guid),
+ intval(local_channel())
+ );
+
// generate a unique message_id
do {
@@ -186,19 +172,21 @@ function send_message($uid = 0, $recipient = '', $body = '', $subject = '', $rep
if($subject)
$subject = str_rot47(base64url_encode($subject));
- if($body)
+ if(($body )&& (! $raw))
$body = str_rot47(base64url_encode($body));
$sig = ''; // placeholder
+ $mimetype = ''; //placeholder
- $r = q("INSERT INTO mail ( account_id, conv_guid, mail_obscured, channel_id, from_xchan, to_xchan, title, body, sig, attach, mid, parent_mid, created, expires, mail_isreply )
- VALUES ( %d, '%s', %d, %d, '%s', '%s', '%s', '%s', '%s', '%s', '%s', '%s', '%s', '%s', %d )",
+ $r = q("INSERT INTO mail ( account_id, conv_guid, mail_obscured, channel_id, from_xchan, to_xchan, mail_mimetype, title, body, sig, attach, mid, parent_mid, created, expires, mail_isreply, mail_raw )
+ VALUES ( %d, '%s', %d, %d, '%s', '%s', '%s', '%s', '%s', '%s', '%s', '%s', '%s', '%s', '%s', %d, %d )",
intval($channel['channel_account_id']),
dbesc($conv_guid),
intval(1),
intval($channel['channel_id']),
dbesc($channel['channel_hash']),
dbesc($recipient),
+ dbesc(($mimetype)? $mimetype : 'text/bbcode'),
dbesc($subject),
dbesc($body),
dbesc($sig),
@@ -207,7 +195,8 @@ function send_message($uid = 0, $recipient = '', $body = '', $subject = '', $rep
dbesc($replyto),
dbesc(datetime_convert()),
dbescdate($expires),
- intval($is_reply)
+ intval($is_reply),
+ intval($raw)
);
// verify the save
@@ -271,6 +260,49 @@ function send_message($uid = 0, $recipient = '', $body = '', $subject = '', $rep
}
+function create_conversation($channel,$recipient,$subject) {
+
+ // create a new conversation
+
+ $conv_guid = random_string();
+
+ $recip = q("select * from xchan where xchan_hash = '%s' limit 1",
+ dbesc($recipient)
+ );
+ if($recip)
+ $recip_handle = $recip[0]['xchan_addr'];
+
+ $sender_handle = channel_reddress($channel);
+
+ $handles = $recip_handle . ';' . $sender_handle;
+
+ if($subject)
+ $nsubject = str_rot47(base64url_encode($subject));
+
+ $r = q("insert into conv (uid,guid,creator,created,updated,subject,recips) values(%d, '%s', '%s', '%s', '%s', '%s', '%s') ",
+ intval($channel['channel_id']),
+ dbesc($conv_guid),
+ dbesc($sender_handle),
+ dbesc(datetime_convert()),
+ dbesc(datetime_convert()),
+ dbesc($nsubject),
+ dbesc($handles)
+ );
+
+ $r = q("select * from conv where guid = '%s' and uid = %d limit 1",
+ dbesc($conv_guid),
+ intval($channel['channel_id'])
+ );
+
+ return $r[0];
+
+}
+
+
+
+
+
+
function private_messages_list($uid, $mailbox = '', $start = 0, $numitems = 0) {
$where = '';
@@ -302,6 +334,8 @@ function private_messages_list($uid, $mailbox = '', $start = 0, $numitems = 0) {
break;
case 'combined':
+ default:
+
$parents = q("SELECT parent_mid FROM mail WHERE mid = parent_mid AND channel_id = %d ORDER BY created DESC",
dbesc($local_channel)
);
@@ -313,15 +347,21 @@ function private_messages_list($uid, $mailbox = '', $start = 0, $numitems = 0) {
}
+ $r = null;
+
if($parents) {
foreach($parents as $parent) {
- $all[] = q("SELECT * FROM mail WHERE parent_mid = '%s' AND channel_id = %d ORDER BY created DESC",
+ $all = q("SELECT * FROM mail WHERE parent_mid = '%s' AND channel_id = %d ORDER BY created DESC limit 1",
dbesc($parent['parent_mid']),
dbesc($local_channel)
);
+
+ if($all) {
+ foreach($all as $single) {
+ $r[] = $single;
+ }
+ }
}
- foreach($all as $single)
- $r[] = $single[0];
}
else {
$r = q($sql);
@@ -439,10 +479,12 @@ function private_messages_drop($channel_id, $messageitem_id, $drop_conversation
intval($channel_id)
);
if($z) {
- q("delete from conv where guid = '%s' and uid = %d",
- dbesc($x[0]['conv_guid']),
- intval($channel_id)
- );
+ if($x[0]['conv_guid']) {
+ q("delete from conv where guid = '%s' and uid = %d",
+ dbesc($x[0]['conv_guid']),
+ intval($channel_id)
+ );
+ }
$m['mail'] = array();
foreach($z as $zz) {
xchan_mail_query($zz);
@@ -514,6 +556,9 @@ function private_messages_fetch_conversation($channel_id, $messageitem_id, $upda
if($messages[$k]['body'])
$messages[$k]['body'] = base64url_decode(str_rot47($messages[$k]['body']));
}
+ if($messages[$k]['mail_raw'])
+ $messages[$k]['body'] = mail_prepare_binary([ 'id' => $messages[$k]['id'] ]);
+
}
diff --git a/include/nav.php b/include/nav.php
index 43c7771ec..89947e270 100644
--- a/include/nav.php
+++ b/include/nav.php
@@ -2,7 +2,11 @@
use \Zotlabs\Lib as Zlib;
-function nav() {
+require_once('include/security.php');
+require_once('include/menu.php');
+
+
+function nav($template = 'default') {
/**
*
@@ -30,20 +34,23 @@ EOT;
intval($channel['channel_id'])
);
- $chans = q("select channel_name, channel_id from channel where channel_account_id = %d and channel_removed = 0 order by channel_name ",
- intval(get_account_id())
- );
+ if(! $_SESSION['delegate']) {
+ $chans = q("select channel_name, channel_id from channel where channel_account_id = %d and channel_removed = 0 order by channel_name ",
+ intval(get_account_id())
+ );
+ }
}
elseif(remote_channel())
$observer = App::get_observer();
-
+
+ require_once('include/conversation.php');
+ $is_owner = (((local_channel()) && ((App::$profile_uid == local_channel()) || (App::$profile_uid == 0))) ? true : false);
+ $channel_apps[] = channel_apps($is_owner, App::$profile['channel_address']);
$myident = (($channel) ? $channel['xchan_addr'] : '');
$sitelocation = (($myident) ? $myident : App::get_hostname());
-
-
/**
*
* Provide a banner/logo/whatever
@@ -56,31 +63,27 @@ EOT;
$banner = get_config('system','sitename');
App::$page['header'] .= replace_macros(get_markup_template('hdr.tpl'), array(
- '$baseurl' => z_root(),
- '$sitelocation' => $sitelocation,
- '$banner' => $banner
+ //we could additionally use this to display important system notifications e.g. for updates
));
- $server_role = get_config('system','server_role');
- $basic = (($server_role === 'basic') ? true : false);
$techlevel = get_account_techlevel();
// nav links: array of array('href', 'text', 'extra css classes', 'title')
- $nav = Array();
+ $nav = [];
/**
* Display login or logout
*/
- $nav['usermenu']=array();
+ $nav['usermenu'] = [];
$userinfo = null;
- $nav['loginmenu']=array();
+ $nav['loginmenu'] = [];
if($observer) {
- $userinfo = array(
+ $userinfo = [
'icon' => $observer['xchan_photo_m'],
'name' => $observer['xchan_addr'],
- );
+ ];
}
elseif(! $_SESSION['authenticated']) {
@@ -88,56 +91,80 @@ EOT;
$nav['loginmenu'][] = Array('rmagic',t('Remote authentication'),'',t('Click to authenticate to your home hub'),'rmagic_nav_btn');
}
+ if(local_channel()) {
- if(local_channel()) {
+ $nav['network'] = array('network', t('Activity'), "", t('Network Activity'),'network_nav_btn');
+ $nav['network']['all'] = [ 'network', t('View your network activity'), '','' ];
+ $nav['network']['mark'] = array('', t('Mark all activity notifications seen'), '','');
- if($chans && count($chans) > 1 && feature_enabled(local_channel(),'nav_channel_select') && (! $basic))
- $nav['channels'] = $chans;
+ $nav['home'] = array('channel/' . $channel['channel_address'], t('Channel Home'), "", t('Channel home'),'home_nav_btn');
+ $nav['home']['all'] = [ 'channel/' . $channel['channel_address'], t('View your channel home'), '' , '' ];
+ $nav['home']['mark'] = array('', t('Mark all channel notifications seen'), '','');
- $nav['logout'] = Array('logout',t('Logout'), "", t('End this session'),'logout_nav_btn');
-
- // user menu
- //$nav['usermenu'][] = Array('channel/' . $channel['channel_address'], t('Home'), "", t('Your posts and conversations'),'channel_nav_btn');
- $nav['usermenu'][] = Array('profile/' . $channel['channel_address'], t('View Profile'), "", t('Your profile page'),'profile_nav_btn');
- if(feature_enabled(local_channel(),'multi_profiles') && (! $basic))
- $nav['usermenu'][] = Array('profiles', t('Edit Profiles'),"", t('Manage/Edit profiles'),'profiles_nav_btn');
- else
- $nav['usermenu'][] = Array('profiles/' . $prof[0]['id'], t('Edit Profile'),"", t('Edit your profile'),'profiles_nav_btn');
- //$nav['usermenu'][] = Array('photos/' . $channel['channel_address'], t('Photos'), "", t('Your photos'),'photos_nav_btn');
- //$nav['usermenu'][] = Array('cloud/' . $channel['channel_address'],t('Files'),"",t('Your files'),'cloud_nav_btn');
+ $nav['intros'] = array('connections/ifpending', t('Connections'), "", t('Connections'),'connections_nav_btn');
+ if(is_site_admin())
+ $nav['registrations'] = array('admin/accounts', t('Registrations'), "", t('Registrations'),'registrations_nav_btn');
+
+
+ $nav['notifications'] = array('notifications/system', t('Notices'), "", t('Notifications'),'notifications_nav_btn');
+ $nav['notifications']['all']=array('notifications/system', t('View all notifications'), "", "");
+ $nav['notifications']['mark'] = array('', t('Mark all system notifications seen'), '','');
+
+ $nav['messages'] = array('mail/combined', t('Mail'), "", t('Private mail'),'mail_nav_btn');
+ $nav['messages']['all']=array('mail/combined', t('View your private messages'), "", "");
+ $nav['messages']['mark'] = array('', t('Mark all private messages seen'), '','');
+ $nav['messages']['inbox'] = array('mail/inbox', t('Inbox'), "", t('Inbox'));
+ $nav['messages']['outbox']= array('mail/outbox', t('Outbox'), "", t('Outbox'));
+ $nav['messages']['new'] = array('mail/new', t('New Message'), "", t('New Message'));
+
+
+ $nav['all_events'] = array('events', t('Events'), "", t('Event Calendar'),'events_nav_btn');
+ $nav['all_events']['all']=array('events', t('View events'), "", "");
+ $nav['all_events']['mark'] = array('', t('Mark all events seen'), '','');
+
+ if(! $_SESSION['delegate']) {
+ $nav['manage'] = array('manage', t('Channel Manager'), "", t('Manage Your Channels'),'manage_nav_btn');
+ }
+
+ $nav['settings'] = array('settings', t('Settings'),"", t('Account/Channel Settings'),'settings_nav_btn');
- //if((! $basic) && feature_enabled(local_channel(),'ajaxchat'))
- // $nav['usermenu'][] = Array('chat/' . $channel['channel_address'], t('Chat'),"",t('Your chatrooms'),'chat_nav_btn');
+
+ if($chans && count($chans) > 1 && feature_enabled(local_channel(),'nav_channel_select'))
+ $nav['channels'] = $chans;
+ $nav['logout'] = ['logout',t('Logout'), "", t('End this session'),'logout_nav_btn'];
+
+ // user menu
+ $nav['usermenu'][] = ['profile/' . $channel['channel_address'], t('View Profile'), ((\App::$nav_sel['name'] == 'Profile') ? 'active' : ''), t('Your profile page'),'profile_nav_btn'];
- //require_once('include/menu.php');
- //$has_bookmarks = menu_list_count(local_channel(),'',MENU_BOOKMARK) + menu_list_count(local_channel(),'',MENU_SYSTEM|MENU_BOOKMARK);
- //if(($has_bookmarks) && (! $basic)) {
- // $nav['usermenu'][] = Array('bookmarks', t('Bookmarks'), "", t('Your bookmarks'),'bookmarks_nav_btn');
- //}
+ if(feature_enabled(local_channel(),'multi_profiles'))
+ $nav['usermenu'][] = ['profiles', t('Edit Profiles'), ((\App::$nav_sel['name'] == 'Profiles') ? 'active' : '') , t('Manage/Edit profiles'),'profiles_nav_btn'];
+ else
+ $nav['usermenu'][] = ['profiles/' . $prof[0]['id'], t('Edit Profile'), ((\App::$nav_sel['name'] == 'Profiles') ? 'active' : ''), t('Edit your profile'),'profiles_nav_btn'];
- //if(feature_enabled($channel['channel_id'],'webpages') && (! $basic))
- // $nav['usermenu'][] = Array('webpages/' . $channel['channel_address'],t('Webpages'),"",t('Your webpages'),'webpages_nav_btn');
- //if(feature_enabled($channel['channel_id'],'wiki') && (! $basic))
- // $nav['usermenu'][] = Array('wiki/' . $channel['channel_address'],t('Wikis'),"",t('Your wikis'),'wiki_nav_btn');
}
else {
if(! get_account_id()) {
- $nav['login'] = login(true,'main-login',false,false);
- $nav['loginmenu'][] = Array('login',t('Login'),'',t('Sign in'),'login_nav_btn');
- App::$page['content'] .= replace_macros(get_markup_template('nav_login.tpl'),
- [
- '$nav' => $nav,
- 'userinfo' => $userinfo
- ]
- );
-
+ if(App::$module === 'channel') {
+ $nav['login'] = login(true,'main-login',false,false);
+ $nav['loginmenu'][] = ['login',t('Login'),'',t('Sign in'),''];
+ }
+ else {
+ $nav['login'] = login(true,'main-login',false,false);
+ $nav['loginmenu'][] = ['login',t('Login'),'',t('Sign in'),'login_nav_btn'];
+ App::$page['content'] .= replace_macros(get_markup_template('nav_login.tpl'),
+ [
+ '$nav' => $nav,
+ 'userinfo' => $userinfo
+ ]
+ );
+ }
}
else
- $nav['alogout'] = Array('logout',t('Logout'), "", t('End this session'),'logout_nav_btn');
+ $nav['alogout'] = ['logout',t('Logout'), "", t('End this session'),'logout_nav_btn'];
}
@@ -149,17 +176,17 @@ EOT;
$homelink = (($observer) ? $observer['xchan_url'] : '');
}
- if(! local_channel()) {
+ if(! $is_owner) {
$nav['rusermenu'] = array(
$homelink,
- t('Get me home'),
+ t('Take me home'),
'logout',
- t('Log me out of this site')
+ ((local_channel()) ? t('Logout') : t('Log me out of this site'))
);
}
if(((get_config('system','register_policy') == REGISTER_OPEN) || (get_config('system','register_policy') == REGISTER_APPROVE)) && (! $_SESSION['authenticated']))
- $nav['register'] = array('register',t('Register'), "", t('Create an account'),'register_nav_btn');
+ $nav['register'] = ['register',t('Register'), "", t('Create an account'),'register_nav_btn'];
if(! get_config('system','hide_help')) {
$help_url = z_root() . '/help?f=&cmd=' . App::$cmd;
@@ -171,15 +198,10 @@ EOT;
//point directly to /help if $context_help is empty - this can be removed once we have context help for all modules
$enable_context_help = (($context_help) ? true : false);
}
- $nav['help'] = array($help_url, t('Help'), "", t('Help and documentation'), 'help_nav_btn', $context_help, $enable_context_help);
+ $nav['help'] = [$help_url, t('Help'), "", t('Help and documentation'), 'help_nav_btn', $context_help, $enable_context_help];
}
- if(! $basic)
- $nav['apps'] = array('apps', t('Apps'), "", t('Applications, utilities, links, games'),'apps_nav_btn');
-
- $nav['search'] = array('search', t('Search'), "", t('Search site @name, #tag, ?docs, content'));
-
- $nav['directory'] = array('directory', t('Directory'), "", t('Channel Directory'),'directory_nav_btn');
+ $nav['search'] = ['search', t('Search'), "", t('Search site @name, #tag, ?docs, content')];
/**
@@ -189,74 +211,40 @@ EOT;
*/
if(local_channel()) {
-
-
- $nav['network'] = array('network', t('Grid'), "", t('Your grid'),'network_nav_btn');
- $nav['network']['all'] = [ 'network', t('View your network/grid'), '','' ];
- $nav['network']['mark'] = array('', t('Mark all grid notifications seen'), '','');
-
- $nav['home'] = array('channel/' . $channel['channel_address'], t('Channel Home'), "", t('Channel home'),'home_nav_btn');
- $nav['home']['all'] = [ 'channel/' . $channel['channel_address'], t('View your channel home'), '' , '' ];
- $nav['home']['mark'] = array('', t('Mark all channel notifications seen'), '','');
-
-
- $nav['intros'] = array('connections/ifpending', t('Connections'), "", t('Connections'),'connections_nav_btn');
-
-
- $nav['notifications'] = array('notifications/system', t('Notices'), "", t('Notifications'),'notifications_nav_btn');
- $nav['notifications']['all']=array('notifications/system', t('View all notifications'), "", "");
- $nav['notifications']['mark'] = array('', t('Mark all system notifications seen'), '','');
-
- $nav['messages'] = array('mail/combined', t('Mail'), "", t('Private mail'),'mail_nav_btn');
- $nav['messages']['all']=array('mail/combined', t('View your private messages'), "", "");
- $nav['messages']['mark'] = array('', t('Mark all private messages seen'), '','');
- $nav['messages']['inbox'] = array('mail/inbox', t('Inbox'), "", t('Inbox'));
- $nav['messages']['outbox']= array('mail/outbox', t('Outbox'), "", t('Outbox'));
- $nav['messages']['new'] = array('mail/new', t('New Message'), "", t('New Message'));
-
-
- $nav['all_events'] = array('events', t('Events'), "", t('Event Calendar'),'events_nav_btn');
- $nav['all_events']['all']=array('events', t('View events'), "", "");
- $nav['all_events']['mark'] = array('', t('Mark all events seen'), '','');
-
- if(! $basic)
+ if(! $_SESSION['delegate']) {
$nav['manage'] = array('manage', t('Channel Manager'), "", t('Manage Your Channels'),'manage_nav_btn');
-
+ }
$nav['settings'] = array('settings', t('Settings'),"", t('Account/Channel Settings'),'settings_nav_btn');
-
}
/**
* Admin page
*/
- if (is_site_admin()){
+ if (is_site_admin()) {
$nav['admin'] = array('admin/', t('Admin'), "", t('Site Setup and Configuration'),'admin_nav_btn');
}
-
- /**
- *
- * Provide a banner/logo/whatever
- *
- */
-
- $banner = get_config('system','banner');
-
- if($banner === false)
- $banner = get_config('system','sitename');
-
$x = array('nav' => $nav, 'usermenu' => $userinfo );
+
call_hooks('nav', $x);
// Not sure the best place to put this on the page. So I'm implementing it but leaving it
// turned off until somebody discovers this and figures out a good location for it.
$powered_by = '';
- // $powered_by = '<strong>red<img class="smiley" src="' . z_root() . '/images/rm-16.png" alt="r#" />matrix</strong>';
-
+ if(App::$profile_uid && App::$nav_sel['raw_name']) {
+ $active_app = q("SELECT app_url FROM app WHERE app_channel = %d AND app_name = '%s' LIMIT 1",
+ intval(App::$profile_uid),
+ dbesc(App::$nav_sel['raw_name'])
+ );
+
+ if($active_app) {
+ $url = $active_app[0]['app_url'];
+ }
+ }
//app bin
- if(local_channel()) {
+ if($is_owner) {
if(get_pconfig(local_channel(), 'system','initial_import_system_apps') === false) {
Zlib\Apps::import_system_apps();
set_pconfig(local_channel(), 'system','initial_import_system_apps', 1);
@@ -277,26 +265,60 @@ EOT;
usort($syslist,'Zotlabs\\Lib\\Apps::app_name_compare');
+ $syslist = Zlib\Apps::app_order(local_channel(),$syslist);
+
foreach($syslist as $app) {
- $navapps[] = Zlib\Apps::app_render($app,'nav');
+ if(\App::$nav_sel['name'] == $app['name'])
+ $app['active'] = true;
+
+ if($is_owner) {
+ $nav_apps[] = Zlib\Apps::app_render($app,'nav');
+ if(strpos($app['categories'],'navbar_' . $template)) {
+ $navbar_apps[] = Zlib\Apps::app_render($app,'navbar');
+ }
+ }
+ elseif(! $is_owner && strpos($app['requires'], 'local_channel') === false) {
+ $nav_apps[] = Zlib\Apps::app_render($app,'nav');
+ if(strpos($app['categories'],'navbar_' . $template)) {
+ $navbar_apps[] = Zlib\Apps::app_render($app,'navbar');
+ }
+ }
}
- $tpl = get_markup_template('nav.tpl');
+ $c = theme_include('navbar_' . purify_filename($template) . '.css');
+ $tpl = get_markup_template('navbar_' . purify_filename($template) . '.tpl');
+
+ if($c && $tpl) {
+ head_add_css('navbar_' . $template . '.css');
+ }
+
+ if(! $tpl) {
+ $tpl = get_markup_template('navbar_default.tpl');
+ }
App::$page['nav'] .= replace_macros($tpl, array(
'$baseurl' => z_root(),
- '$fulldocs' => t('Documentation'),
+ '$fulldocs' => t('Help'),
'$sitelocation' => $sitelocation,
'$nav' => $x['nav'],
'$banner' => $banner,
'$emptynotifications' => t('Loading...'),
'$userinfo' => $x['usermenu'],
'$localuser' => local_channel(),
- '$sel' => App::$nav_sel,
+ '$is_owner' => $is_owner,
+ '$sel' => App::$nav_sel,
'$powered_by' => $powered_by,
'$help' => t('@name, #tag, ?doc, content'),
'$pleasewait' => t('Please wait...'),
- '$navapps' => $navapps
+ '$nav_apps' => $nav_apps,
+ '$navbar_apps' => $navbar_apps,
+ '$channel_menu' => get_config('system','channel_menu'),
+ '$channel_thumb' => ((App::$profile) ? App::$profile['thumb'] : ''),
+ '$channel_apps' => $channel_apps,
+ '$addapps' => t('Add Apps'),
+ '$orderapps' => t('Arrange Apps'),
+ '$sysapps_toggle' => t('Toggle System Apps'),
+ '$url' => (($url) ? $url : App::$cmd)
));
if(x($_SESSION, 'reload_avatar') && $observer) {
@@ -319,19 +341,185 @@ EOT;
*
*/
function nav_set_selected($item){
- App::$nav_sel = array(
- 'community' => null,
- 'network' => null,
- 'home' => null,
- 'profiles' => null,
- 'intros' => null,
- 'notifications' => null,
- 'messages' => null,
- 'directory' => null,
- 'settings' => null,
- 'contacts' => null,
- 'manage' => null,
- 'register' => null,
+ App::$nav_sel['raw_name'] = $item;
+ $item = ['name' => $item];
+ Zlib\Apps::translate_system_apps($item);
+ App::$nav_sel['name'] = $item['name'];
+}
+
+
+
+function channel_apps($is_owner = false, $nickname = null) {
+
+ // Don't provide any channel apps if we're running as the sys channel
+
+ if(App::$is_sys)
+ return '';
+
+ if(! get_pconfig($uid, 'system', 'channelapps','1'))
+ return '';
+
+ $channel = App::get_channel();
+
+ if($channel && is_null($nickname))
+ $nickname = $channel['channel_address'];
+
+ $uid = ((App::$profile['profile_uid']) ? App::$profile['profile_uid'] : local_channel());
+ $account_id = ((App::$profile['profile_uid']) ? App::$profile['channel_account_id'] : App::$channel['channel_account_id']);
+
+ if($uid == local_channel()) {
+ return;
+ }
+ else {
+ $cal_link = '/cal/' . $nickname;
+ }
+
+ $sql_options = item_permissions_sql($uid);
+
+ $r = q("select item.* from item left join iconfig on item.id = iconfig.iid
+ where item.uid = %d and iconfig.cat = 'system' and iconfig.v = '%s'
+ and item.item_delayed = 0 and item.item_deleted = 0
+ and ( iconfig.k = 'WEBPAGE' and item_type = %d )
+ $sql_options limit 1",
+ intval($uid),
+ dbesc('home'),
+ intval(ITEM_TYPE_WEBPAGE)
+ );
+
+ $has_webpages = (($r) ? true : false);
+
+ if(x($_GET, 'tab'))
+ $tab = notags(trim($_GET['tab']));
+
+ $url = z_root() . '/channel/' . $nickname;
+ $pr = z_root() . '/profile/' . $nickname;
+
+ $tabs = [
+ [
+ 'label' => t('Channel'),
+ 'url' => $url,
+ 'sel' => ((argv(0) == 'channel') ? 'active' : ''),
+ 'title' => t('Status Messages and Posts'),
+ 'id' => 'status-tab',
+ 'icon' => 'home'
+ ],
+ ];
+
+ $p = get_all_perms($uid,get_observer_hash());
+
+ if ($p['view_profile']) {
+ $tabs[] = [
+ 'label' => t('About'),
+ 'url' => $pr,
+ 'sel' => ((argv(0) == 'profile') ? 'active' : ''),
+ 'title' => t('Profile Details'),
+ 'id' => 'profile-tab',
+ 'icon' => 'user'
+ ];
+ }
+ if ($p['view_storage']) {
+ $tabs[] = [
+ 'label' => t('Photos'),
+ 'url' => z_root() . '/photos/' . $nickname,
+ 'sel' => ((argv(0) == 'photos') ? 'active' : ''),
+ 'title' => t('Photo Albums'),
+ 'id' => 'photo-tab',
+ 'icon' => 'photo'
+ ];
+ $tabs[] = [
+ 'label' => t('Files'),
+ 'url' => z_root() . '/cloud/' . $nickname,
+ 'sel' => ((argv(0) == 'cloud' || argv(0) == 'sharedwithme') ? 'active' : ''),
+ 'title' => t('Files and Storage'),
+ 'id' => 'files-tab',
+ 'icon' => 'folder-open'
+ ];
+ }
+
+ if($p['view_stream'] && $cal_link) {
+ $tabs[] = [
+ 'label' => t('Events'),
+ 'url' => z_root() . $cal_link,
+ 'sel' => ((argv(0) == 'cal' || argv(0) == 'events') ? 'active' : ''),
+ 'title' => t('Events'),
+ 'id' => 'event-tab',
+ 'icon' => 'calendar'
+ ];
+ }
+
+
+ if ($p['chat'] && feature_enabled($uid,'ajaxchat')) {
+ $has_chats = ZLib\Chatroom::list_count($uid);
+ if ($has_chats) {
+ $tabs[] = [
+ 'label' => t('Chatrooms'),
+ 'url' => z_root() . '/chat/' . $nickname,
+ 'sel' => ((argv(0) == 'chat') ? 'active' : '' ),
+ 'title' => t('Chatrooms'),
+ 'id' => 'chat-tab',
+ 'icon' => 'comments-o'
+ ];
+ }
+ }
+
+ $has_bookmarks = menu_list_count(local_channel(),'',MENU_BOOKMARK) + menu_list_count(local_channel(),'',MENU_SYSTEM|MENU_BOOKMARK);
+ if ($is_owner && $has_bookmarks) {
+ $tabs[] = [
+ 'label' => t('Bookmarks'),
+ 'url' => z_root() . '/bookmarks',
+ 'sel' => ((argv(0) == 'bookmarks') ? 'active' : ''),
+ 'title' => t('Saved Bookmarks'),
+ 'id' => 'bookmarks-tab',
+ 'icon' => 'bookmark'
+ ];
+ }
+
+ if($p['view_pages'] && feature_enabled($uid,'cards')) {
+ $tabs[] = [
+ 'label' => t('Cards'),
+ 'url' => z_root() . '/cards/' . $nickname ,
+ 'sel' => ((argv(0) == 'cards') ? 'active' : ''),
+ 'title' => t('View Cards'),
+ 'id' => 'cards-tab',
+ 'icon' => 'list'
+ ];
+ }
+
+
+ if($has_webpages && feature_enabled($uid,'webpages')) {
+ $tabs[] = [
+ 'label' => t('Webpages'),
+ 'url' => z_root() . '/page/' . $nickname . '/home',
+ 'sel' => ((argv(0) == 'webpages') ? 'active' : ''),
+ 'title' => t('View Webpages'),
+ 'id' => 'webpages-tab',
+ 'icon' => 'newspaper-o'
+ ];
+ }
+
+
+ if ($p['view_wiki']) {
+ if(feature_enabled($uid,'wiki') && (get_account_techlevel($account_id) > 3)) {
+ $tabs[] = [
+ 'label' => t('Wikis'),
+ 'url' => z_root() . '/wiki/' . $nickname,
+ 'sel' => ((argv(0) == 'wiki') ? 'active' : ''),
+ 'title' => t('Wiki'),
+ 'id' => 'wiki-tab',
+ 'icon' => 'pencil-square-o'
+ ];
+ }
+ }
+
+ $arr = array('is_owner' => $is_owner, 'nickname' => $nickname, 'tab' => (($tab) ? $tab : false), 'tabs' => $tabs);
+ call_hooks('profile_tabs', $arr);
+ call_hooks('channel_apps', $arr);
+
+ return replace_macros(get_markup_template('profile_tabs.tpl'),
+ [
+ '$tabs' => $arr['tabs'],
+ '$name' => App::$profile['channel_name'],
+ '$thumb' => App::$profile['thumb'],
+ ]
);
- App::$nav_sel[$item] = 'active';
}
diff --git a/include/network.php b/include/network.php
index 66716ef9e..2f29a70c4 100644
--- a/include/network.php
+++ b/include/network.php
@@ -22,8 +22,8 @@ function get_capath() {
* @param int $redirects default 0
* internal use, recursion counter
* @param array $opts (optional parameters) associative array with:
- * * \b accept_content => supply Accept: header with 'accept_content' as the value
* * \b timeout => int seconds, default system config value or 60 seconds
+ * * \b headers => array of additional header fields
* * \b http_auth => username:password
* * \b novalidate => do not validate SSL certs, default is to validate using our CA list
* * \b nobody => only return the header
@@ -31,6 +31,7 @@ function get_capath() {
* * \b custom => custom request method: e.g. 'PUT', 'DELETE'
* * \b cookiejar => cookie file (write)
* * \b cookiefile => cookie file (read)
+ * * \b session => boolean; append session cookie *if* $url is our own site
*
* @return array an associative array with:
* * \e int \b return_code => HTTP return code or 0 if timeout or failure
@@ -74,8 +75,21 @@ function z_fetch_url($url, $binary = false, $redirects = 0, $opts = array()) {
if(x($opts,'readfunc'))
@curl_setopt($ch, CURLOPT_READFUNCTION, $opts['readfunc']);
- if(x($opts,'headers'))
- @curl_setopt($ch, CURLOPT_HTTPHEADER, $opts['headers']);
+ // When using the session option and fetching from our own site,
+ // append the PHPSESSID cookie to any existing headers.
+ // Don't add to $opts['headers'] so that the cookie does not get
+ // sent to other sites via redirects
+
+ $instance_headers = ((array_key_exists('headers',$opts) && is_array($opts['headers'])) ? $opts['headers'] : []);
+
+ if(x($opts,'session')) {
+ if(strpos($url,z_root()) === 0) {
+ $instance_headers[] = 'Cookie: PHPSESSID=' . session_id();
+ }
+ }
+ if($instance_headers)
+ @curl_setopt($ch, CURLOPT_HTTPHEADER, $instance_headers);
+
if(x($opts,'nobody'))
@curl_setopt($ch, CURLOPT_NOBODY, $opts['nobody']);
@@ -91,6 +105,7 @@ function z_fetch_url($url, $binary = false, $redirects = 0, $opts = array()) {
@curl_setopt($ch, CURLOPT_TIMEOUT, (($curl_time !== false) ? $curl_time : 60));
}
+
if(x($opts,'http_auth')) {
// "username" . ':' . "password"
@curl_setopt($ch, CURLOPT_USERPWD, $opts['http_auth']);
@@ -186,7 +201,6 @@ function z_fetch_url($url, $binary = false, $redirects = 0, $opts = array()) {
* @param int $redirects = 0
* internal use, recursion counter
* @param array $opts (optional parameters)
- * 'accept_content' => supply Accept: header with 'accept_content' as the value
* 'timeout' => int seconds, default system config value or 60 seconds
* 'http_auth' => username:password
* 'novalidate' => do not validate SSL certs, default is to validate using our CA list
@@ -229,9 +243,16 @@ function z_post_url($url,$params, $redirects = 0, $opts = array()) {
@curl_setopt($ch, CURLOPT_HEADER, false);
}
- if(x($opts,'headers')) {
- @curl_setopt($ch, CURLOPT_HTTPHEADER, $opts['headers']);
+ $instance_headers = ((array_key_exists('headers',$opts) && is_array($opts['headers'])) ? $opts['headers'] : []);
+
+ if(x($opts,'session')) {
+ if(strpos($url,z_root()) === 0) {
+ $instance_headers[] = 'Cookie: PHPSESSID=' . session_id();
+ }
}
+ if($instance_headers)
+ @curl_setopt($ch, CURLOPT_HTTPHEADER, $instance_headers);
+
if(x($opts,'nobody'))
@curl_setopt($ch, CURLOPT_NOBODY, $opts['nobody']);
@@ -322,7 +343,7 @@ function z_post_url($url,$params, $redirects = 0, $opts = array()) {
if (isset($url_parsed)) {
curl_close($ch);
if($http_code == 303) {
- return z_fetch_url($newurl,false,$redirects++,$opts);
+ return z_fetch_url($newurl,false,++$redirects,$opts);
} else {
return z_post_url($newurl,$params,++$redirects,$opts);
}
@@ -376,36 +397,13 @@ function json_return_and_die($x, $content_type = 'application/json') {
killme();
}
-
-
-// Generic XML return
-// Outputs a basic dfrn XML status structure to STDOUT, with a <status> variable
-// of $st and an optional text <message> of $message and terminates the current process.
-
-
-function xml_status($st, $message = '') {
-
- $xml_message = ((strlen($message)) ? "\t<message>" . xmlify($message) . "</message>\r\n" : '');
-
- if($st)
- logger('xml_status returning non_zero: ' . $st . " message=" . $message);
-
- header( "Content-type: text/xml" );
- echo '<?xml version="1.0" encoding="UTF-8"?>'."\r\n";
- echo "<result>\r\n\t<status>$st</status>\r\n$xml_message</result>\r\n";
- killme();
-}
-
-
-
/**
- * @brief Send HTTP status header
+ * @brief Send HTTP status header.
*
* @param int $val
* integer HTTP status result value
* @param string $msg
* optional message
- * @returns nil
*/
function http_status($val, $msg = '') {
if ($val >= 400)
@@ -413,12 +411,11 @@ function http_status($val, $msg = '') {
if ($val >= 200 && $val < 300)
$msg = (($msg) ? $msg : 'OK');
- logger('http_status_exit ' . $val . ' ' . $msg);
+ logger(\App::$query_string . ':' . $val . ' ' . $msg);
header($_SERVER['SERVER_PROTOCOL'] . ' ' . $val . ' ' . $msg);
}
-
/**
* @brief Send HTTP status header and exit.
*
@@ -426,58 +423,57 @@ function http_status($val, $msg = '') {
* integer HTTP status result value
* @param string $msg
* optional message
- * @returns (does not return, process is terminated)
+ * @return does not return, process is terminated
*/
function http_status_exit($val, $msg = '') {
http_status($val, $msg);
killme();
}
-
-
-// convert an XML document to a normalised, case-corrected array
-// used by webfinger
-
-
+/**
+ * @brief convert an XML document to a normalised, case-corrected array used by webfinger.
+ *
+ * @param string|array|SimpleXMLElement $xml_element
+ * @param int $recursion_depth[in,out]
+ * @return NULL|string|array
+ */
function convert_xml_element_to_array($xml_element, &$recursion_depth=0) {
- // If we're getting too deep, bail out
- if ($recursion_depth > 512) {
- return(null);
- }
-
- if (!is_string($xml_element) &&
- !is_array($xml_element) &&
- (get_class($xml_element) == 'SimpleXMLElement')) {
- $xml_element_copy = $xml_element;
- $xml_element = get_object_vars($xml_element);
- }
+ // If we're getting too deep, bail out
+ if ($recursion_depth > 512) {
+ return(null);
+ }
- if (is_array($xml_element)) {
- $result_array = array();
- if (count($xml_element) <= 0) {
- return (trim(strval($xml_element_copy)));
- }
+ if (!is_string($xml_element) &&
+ !is_array($xml_element) &&
+ (get_class($xml_element) == 'SimpleXMLElement')) {
+ $xml_element_copy = $xml_element;
+ $xml_element = get_object_vars($xml_element);
+ }
- foreach($xml_element as $key=>$value) {
+ if (is_array($xml_element)) {
+ $result_array = array();
+ if (count($xml_element) <= 0) {
+ return (trim(strval($xml_element_copy)));
+ }
- $recursion_depth++;
- $result_array[strtolower($key)] =
+ foreach($xml_element as $key=>$value) {
+ $recursion_depth++;
+ $result_array[strtolower($key)] =
convert_xml_element_to_array($value, $recursion_depth);
- $recursion_depth--;
- }
- if ($recursion_depth == 0) {
- $temp_array = $result_array;
- $result_array = array(
- strtolower($xml_element_copy->getName()) => $temp_array,
- );
- }
-
- return ($result_array);
-
- } else {
- return (trim(strval($xml_element)));
+ $recursion_depth--;
}
+ if ($recursion_depth == 0) {
+ $temp_array = $result_array;
+ $result_array = array(
+ strtolower($xml_element_copy->getName()) => $temp_array,
+ );
+ }
+
+ return ($result_array);
+ } else {
+ return (trim(strval($xml_element)));
+ }
}
@@ -491,7 +487,7 @@ function z_dns_check($h,$check_mx = 0) {
if(is_array(\App::$config) && array_key_exists('system',\App::$config)
&& is_array(\App::$config['system'])
- && array_key_exists('do_not_check_dns',\App::$config['system'])
+ && array_key_exists('do_not_check_dns',\App::$config['system'])
&& \App::$config['system']['do_not_check_dns'])
return true;
@@ -499,56 +495,71 @@ function z_dns_check($h,$check_mx = 0) {
//$opts = DNS_A + DNS_CNAME + DNS_PTR;
//if($check_mx)
// $opts += DNS_MX;
- // Specific record type flags are unreliable on FreeBSD and Mac,
- // so now we'll ignore these and just check for the existence of any DNS record.
+ // Specific record type flags are unreliable on FreeBSD and Mac,
+ // so now we'll ignore these and just check for the existence of any DNS record.
return((@dns_get_record($h) || filter_var($h, FILTER_VALIDATE_IP)) ? true : false);
-
}
-// Take a URL from the wild, prepend http:// if necessary
-// and check DNS to see if it's real (or check if is a valid IP address)
-// return true if it's OK, false if something is wrong with it
-
-
+/**
+ * @brief Validates a given URL
+ *
+ * Take a URL from the wild, prepend http:// if necessary and check DNS to see
+ * if it's real (or check if is a valid IP address).
+ *
+ * @see z_dns_check()
+ *
+ * @param string $url[in,out] URL to check
+ * @return boolean Return true if it's OK, false if something is wrong with it
+ */
function validate_url(&$url) {
// no naked subdomains (allow localhost for tests)
- if(strpos($url,'.') === false && strpos($url,'/localhost/') === false)
+ if(strpos($url, '.') === false && strpos($url, '/localhost/') === false)
return false;
- if(substr($url,0,4) != 'http')
+
+ if(substr($url, 0, 4) != 'http')
$url = 'http://' . $url;
+
$h = @parse_url($url);
if(($h) && z_dns_check($h['host'])) {
return true;
}
+
return false;
}
-// checks that email is an actual resolvable internet address
-
-
+/**
+ * @brief Checks that email is an actual resolvable internet address.
+ *
+ * @param string $addr
+ * @return boolean
+ */
function validate_email($addr) {
- if(get_config('system','disable_email_validation'))
+ if(get_config('system', 'disable_email_validation'))
return true;
- if(! strpos($addr,'@'))
+ if(! strpos($addr, '@'))
return false;
- $h = substr($addr,strpos($addr,'@') + 1);
- if(($h) && z_dns_check($h,true)) {
+ $h = substr($addr, strpos($addr, '@') + 1);
+
+ if(($h) && z_dns_check($h, true)) {
return true;
}
+
return false;
}
-// Check $url against our list of allowed sites,
-// wildcards allowed. If allowed_sites is unset return true;
-// If url is allowed, return true.
-// otherwise, return false
-
-
+/**
+ * @brief Check $url against our list of allowed sites.
+ *
+ * Wildcards allowed. If allowed_sites is unset return true.
+ *
+ * @param string $url
+ * @return boolean Return true if url is allowed, otherwise return false
+ */
function allowed_url($url) {
$h = @parse_url($url);
@@ -557,7 +568,7 @@ function allowed_url($url) {
return false;
}
- $str_allowed = get_config('system','allowed_sites');
+ $str_allowed = get_config('system', 'allowed_sites');
if(! $str_allowed)
return true;
@@ -585,21 +596,23 @@ function allowed_url($url) {
return $found;
}
-// check if email address is allowed to register here.
-// Compare against our list (wildcards allowed).
-// Returns false if not allowed, true if allowed or if
-// allowed list is not configured.
-
-
+/**
+ * @brief Check if email address is allowed to register here.
+ *
+ * Compare against our list (wildcards allowed).
+ *
+ * @param string $email
+ * @return boolean Returns false if not allowed, true if allowed or if allowed list is
+ * not configured.
+ */
function allowed_email($email) {
-
- $domain = strtolower(substr($email,strpos($email,'@') + 1));
+ $domain = strtolower(substr($email, strpos($email, '@') + 1));
if(! $domain)
return false;
- $str_allowed = get_config('system','allowed_email');
- $str_not_allowed = get_config('system','not_allowed_email');
+ $str_allowed = get_config('system', 'allowed_email');
+ $str_not_allowed = get_config('system', 'not_allowed_email');
if(! $str_allowed && ! $str_not_allowed)
return true;
@@ -610,7 +623,7 @@ function allowed_email($email) {
$fnmatch = function_exists('fnmatch');
- $allowed = explode(',',$str_allowed);
+ $allowed = explode(',', $str_allowed);
if(count($allowed)) {
foreach($allowed as $a) {
@@ -622,7 +635,7 @@ function allowed_email($email) {
}
}
- $not_allowed = explode(',',$str_not_allowed);
+ $not_allowed = explode(',', $str_not_allowed);
if(count($not_allowed)) {
foreach($not_allowed as $na) {
@@ -639,6 +652,7 @@ function allowed_email($email) {
} elseif (!$str_allowed && !$found_not_allowed) {
$return = true;
}
+
return $return;
}
@@ -648,19 +662,24 @@ function parse_xml_string($s,$strict = true) {
if($strict) {
if(! strstr($s,'<?xml'))
return false;
+
$s2 = substr($s,strpos($s,'<?xml'));
}
else
$s2 = $s;
+
libxml_use_internal_errors(true);
$x = @simplexml_load_string($s2);
- if(! $x) {
+ if($x === false) {
logger('libxml: parse: error: ' . $s2, LOGGER_DATA);
- foreach(libxml_get_errors() as $err)
- logger('libxml: parse: ' . $err->code." at ".$err->line.":".$err->column." : ".$err->message, LOGGER_DATA);
+ foreach(libxml_get_errors() as $err) {
+ logger('libxml: parse: ' . $err->code . ' at ' . $err->line
+ . ':' . $err->column . ' : ' . $err->message, LOGGER_DATA);
+ }
libxml_clear_errors();
}
+
return $x;
}
@@ -676,7 +695,7 @@ function scale_external_images($s, $include_link = true, $scale_replace = false)
require_once('include/photo/photo_driver.php');
foreach($matches as $mtch) {
- logger('scale_external_image: ' . $mtch[2] . ' ' . $mtch[3]);
+ logger('data: ' . $mtch[2] . ' ' . $mtch[3]);
if(substr($mtch[1],0,1) == '=') {
$owidth = intval(substr($mtch[2],1));
@@ -697,6 +716,10 @@ function scale_external_images($s, $include_link = true, $scale_replace = false)
$scaled = str_replace($scale_replace[0], $scale_replace[1], $mtch[3]);
else
$scaled = $mtch[3];
+
+ if(! strpbrk(substr($scaled,0,1),'zhfmt'))
+ continue;
+
$i = z_fetch_url($scaled,true);
@@ -727,12 +750,12 @@ function scale_external_images($s, $include_link = true, $scale_replace = false)
$ph->scaleImage(1024);
$new_width = $ph->getWidth();
$new_height = $ph->getHeight();
- logger('scale_external_images: ' . $orig_width . '->' . $new_width . 'w ' . $orig_height . '->' . $new_height . 'h' . ' match: ' . $mtch[0], LOGGER_DEBUG);
+ logger('data: ' . $orig_width . '->' . $new_width . 'w ' . $orig_height . '->' . $new_height . 'h' . ' match: ' . $mtch[0], LOGGER_DEBUG);
$s = str_replace($mtch[0],'[' . $tag . '=' . $new_width . 'x' . $new_height. ']' . $scaled . '[/' . $tag . ']'
. "\n" . (($include_link)
? '[zrl=' . $mtch[2] . ']' . t('view full size') . '[/zrl]' . "\n"
: ''),$s);
- logger('scale_external_images: new string: ' . $s, LOGGER_DEBUG);
+ logger('new string: ' . $s, LOGGER_DEBUG);
}
}
}
@@ -747,27 +770,31 @@ function scale_external_images($s, $include_link = true, $scale_replace = false)
}
/**
- * xml2array() will convert the given XML text to an array in the XML structure.
+ * @brief xml2array() will convert the given XML text to an array in the XML structure.
+ *
* Link: http://www.bin-co.com/php/scripts/xml2array/
- * Portions significantly re-written by mike@macgirvin.com for Friendica (namespaces, lowercase tags, get_attribute default changed, more...)
- * Arguments : $contents - The XML text
- * $namespaces - true or false include namespace information in the returned array as array elements.
- * $get_attributes - 1 or 0. If this is 1 the function will get the attributes as well as the tag values - this results in a different array structure in the return value.
- * $priority - Can be 'tag' or 'attribute'. This will change the way the resulting array sturcture. For 'tag', the tags are given more importance.
- * Return: The parsed XML in an array form. Use print_r() to see the resulting array structure.
+ * Portions significantly re-written by mike@macgirvin.com for Friendica
+ * (namespaces, lowercase tags, get_attribute default changed, more...)
+ *
* Examples: $array = xml2array(file_get_contents('feed.xml'));
- * $array = xml2array(file_get_contents('feed.xml', true, 1, 'attribute'));
+ * $array = xml2array(file_get_contents('feed.xml', true, 1, 'attribute'));
+ *
+ * @param string $contents The XML text
+ * @param boolean $namespaces true or false include namespace information in the returned array as array elements
+ * @param int $get_attributes 1 or 0. If this is 1 the function will get the attributes as well as the tag values - this results in a different array structure in the return value.
+ * @param string $priority Can be 'tag' or 'attribute'. This will change the way the resulting array sturcture. For 'tag', the tags are given more importance.
+ *
+ * @return array The parsed XML in an array form. Use print_r() to see the resulting array structure.
*/
-
function xml2array($contents, $namespaces = true, $get_attributes=1, $priority = 'attribute') {
- if(!$contents) return array();
+ if(!$contents)
+ return array();
if(!function_exists('xml_parser_create')) {
logger('xml2array: parser function missing');
return array();
}
-
libxml_use_internal_errors(true);
libxml_clear_errors();
@@ -793,6 +820,7 @@ function xml2array($contents, $namespaces = true, $get_attributes=1, $priority =
foreach(libxml_get_errors() as $err)
logger('libxml: parse: ' . $err->code . " at " . $err->line . ":" . $err->column . " : " . $err->message, LOGGER_DATA);
libxml_clear_errors();
+
return;
}
@@ -859,7 +887,6 @@ function xml2array($contents, $namespaces = true, $get_attributes=1, $priority =
$current[$tag]['0_attr'] = $current[$tag.'_attr'];
unset($current[$tag.'_attr']);
}
-
}
$last_item_index = $repeated_tag_index[$tag.'_'.$level]-1;
$current = &$current[$tag][$last_item_index];
@@ -870,7 +897,8 @@ function xml2array($contents, $namespaces = true, $get_attributes=1, $priority =
if(!isset($current[$tag])) { //New Key
$current[$tag] = $result;
$repeated_tag_index[$tag.'_'.$level] = 1;
- if($priority == 'tag' and $attributes_data) $current[$tag. '_attr'] = $attributes_data;
+ if($priority == 'tag' and $attributes_data)
+ $current[$tag. '_attr'] = $attributes_data;
} else { // If taken, put all things inside a list(array)
if(isset($current[$tag][0]) and is_array($current[$tag])) { // If it is already an array...
@@ -882,13 +910,11 @@ function xml2array($contents, $namespaces = true, $get_attributes=1, $priority =
$current[$tag][$repeated_tag_index[$tag.'_'.$level] . '_attr'] = $attributes_data;
}
$repeated_tag_index[$tag.'_'.$level]++;
-
} else { // If it is not an array...
$current[$tag] = array($current[$tag],$result); //...Make it an array using using the existing value and the new value
$repeated_tag_index[$tag.'_'.$level] = 1;
if($priority == 'tag' and $get_attributes) {
if(isset($current[$tag.'_attr'])) { // The attribute of the last(0th) tag must be moved as well
-
$current[$tag]['0_attr'] = $current[$tag.'_attr'];
unset($current[$tag.'_attr']);
}
@@ -961,53 +987,26 @@ function email_header_encode($in_str, $charset = 'UTF-8') {
return $out_str;
}
-function email_send($addr, $subject, $headers, $item) {
- //$headers .= 'MIME-Version: 1.0' . "\n";
- //$headers .= 'Content-Type: text/html; charset=UTF-8' . "\n";
- //$headers .= 'Content-Type: text/plain; charset=UTF-8' . "\n";
- //$headers .= 'Content-Transfer-Encoding: 8bit' . "\n\n";
-
- $part = uniqid("", true);
-
- $html = prepare_body($item);
-
- $headers .= "Mime-Version: 1.0\n";
- $headers .= 'Content-Type: multipart/alternative; boundary="=_'.$part.'"'."\n\n";
-
- $body = "\n--=_".$part."\n";
- $body .= "Content-Transfer-Encoding: 8bit\n";
- $body .= "Content-Type: text/plain; charset=utf-8; format=flowed\n\n";
-
- $body .= html2plain($html)."\n";
-
- $body .= "--=_".$part."\n";
- $body .= "Content-Transfer-Encoding: 8bit\n";
- $body .= "Content-Type: text/html; charset=utf-8\n\n";
-
- $body .= '<html><head></head><body style="word-wrap: break-word; -webkit-nbsp-mode: space; -webkit-line-break: after-white-space; ">'.$html."</body></html>\n";
-
- $body .= "--=_".$part."--";
-
- //$message = '<html><body>' . $html . '</body></html>';
- //$message = html2plain($html);
- logger('notifier: email delivery to ' . $addr);
- mail($addr, $subject, $body, $headers);
-}
-
-
-
-function discover_by_url($url,$arr = null) {
- require_once('library/HTML5/Parser.php');
+/**
+ * @brief Creates an xchan entry for URL.
+ *
+ * @param string $url URL to discover
+ * @param array $arr fallback values if scrape_feed() is empty
+ *
+ * @return boolean
+ */
+function discover_by_url($url, $arr = null) {
$x = scrape_feed($url);
if(! $x) {
if(! $arr)
return false;
+
$network = (($arr['network']) ? $arr['network'] : 'unknown');
- $name = (($arr['name']) ? $arr['name'] : 'unknown');
- $photo = (($arr['photo']) ? $arr['photo'] : '');
- $addr = (($arr['addr']) ? $arr['addr'] : '');
- $guid = $url;
+ $name = (($arr['name']) ? $arr['name'] : 'unknown');
+ $photo = (($arr['photo']) ? $arr['photo'] : '');
+ $addr = (($arr['addr']) ? $arr['addr'] : '');
+ $guid = $url;
}
$profile = $url;
@@ -1025,27 +1024,26 @@ function discover_by_url($url,$arr = null) {
// try and discover stuff from the feeed
- require_once('library/simplepie/simplepie.inc');
$feed = new SimplePie();
$level = 0;
- $x = z_fetch_url($guid,false,$level,array('novalidate' => true));
+ $x = z_fetch_url($guid, false, $level, array('novalidate' => true));
if(! $x['success']) {
- logger('probe_url: feed fetch failed for ' . $poll);
+ logger('Feed fetch failed for ' . $guid);
return false;
}
$xml = $x['body'];
- logger('probe_url: fetch feed: ' . $guid . ' returns: ' . $xml, LOGGER_DATA);
- logger('probe_url: scrape_feed: headers: ' . $x['header'], LOGGER_DATA);
+ logger('Fetch feed: ' . $guid . ' returns: ' . $xml, LOGGER_DATA);
+ logger('scrape_feed: headers: ' . $x['header'], LOGGER_DATA);
// Don't try and parse an empty string
$feed->set_raw_data(($xml) ? $xml : '<?xml version="1.0" encoding="utf-8" ?><xml></xml>');
$feed->init();
if($feed->error())
- logger('probe_url: scrape_feed: Error parsing XML: ' . $feed->error());
+ logger('scrape_feed: Error parsing XML: ' . $feed->error());
- $name = unxmlify(trim($feed->get_title()));
- $photo = $feed->get_image_url();
+ $name = unxmlify(trim($feed->get_title()));
+ $photo = $feed->get_image_url();
$author = $feed->get_author();
if($author) {
@@ -1083,7 +1081,7 @@ function discover_by_url($url,$arr = null) {
$profile = trim(unxmlify($author->get_link()));
}
if(! $photo) {
- $rawmedia = $item->get_item_tags('http://search.yahoo.com/mrss/','thumbnail');
+ $rawmedia = $item->get_item_tags('http://search.yahoo.com/mrss/', 'thumbnail');
if($rawmedia && $rawmedia[0]['attribs']['']['url'])
$photo = unxmlify($rawmedia[0]['attribs']['']['url']);
}
@@ -1097,7 +1095,7 @@ function discover_by_url($url,$arr = null) {
}
}
}
- if($poll === $profile)
+ if($guid === $profile)
$lnk = $feed->get_permalink();
if(isset($lnk) && strlen($lnk))
$profile = $lnk;
@@ -1109,9 +1107,6 @@ function discover_by_url($url,$arr = null) {
if(! $name)
$name = notags($feed->get_description());
- if(! $guid)
- return false;
-
$r = q("select * from xchan where xchan_hash = '%s' limit 1",
dbesc($guid)
);
@@ -1125,7 +1120,6 @@ function discover_by_url($url,$arr = null) {
[
'xchan_hash' => $guid,
'xchan_guid' => $guid,
- 'xchan_pubkey' => $pubkey,
'xchan_addr' => $addr,
'xchan_url' => $profile,
'xchan_name' => $name,
@@ -1143,30 +1137,17 @@ function discover_by_url($url,$arr = null) {
dbesc($photos[3]),
dbesc($guid)
);
- return true;
+ return true;
}
+function discover_by_webbie($webbie,$protocol = '') {
-function discover_by_webbie($webbie) {
- require_once('library/HTML5/Parser.php');
-
- $result = array();
+ $result = [];
$network = null;
- $diaspora = false;
- $gnusoc = false;
- $dfrn = false;
-
- $has_salmon = false;
- $salmon_key = false;
- $atom_feed = false;
- $diaspora_base = '';
- $diaspora_guid = '';
- $diaspora_key = '';
-
- $webbie = strtolower($webbie);
+// $webbie = strtolower($webbie);
$x = webfinger_rfc7033($webbie,true);
if($x && array_key_exists('links',$x) && $x['links']) {
@@ -1176,7 +1157,7 @@ function discover_by_webbie($webbie) {
// If we discover zot - don't search further; grab the info and get out of
// here.
- if($link['rel'] === PROTOCOL_ZOT) {
+ if($link['rel'] === PROTOCOL_ZOT && ((! $protocol) || (strtolower($protocol) === 'zot'))) {
logger('discover_by_webbie: zot found for ' . $webbie, LOGGER_DEBUG);
if(array_key_exists('zot',$x) && $x['zot']['success']) {
$i = import_xchan($x['zot']);
@@ -1191,317 +1172,23 @@ function discover_by_webbie($webbie) {
}
}
}
- if($link['rel'] == NAMESPACE_DFRN) {
- $dfrn = $link['href'];
- }
- if($link['rel'] == 'magic-public-key') {
- if(substr($link['href'],0,5) === 'data:') {
- $salmon_key = convert_salmon_key($link['href']);
- }
- }
- if($link['rel'] == 'salmon') {
- $has_salmon = true;
- $salmon = $link['href'];
- }
- if($link['rel'] == 'http://schemas.google.com/g/2010#updates-from') {
- $atom_feed = $link['href'];
- }
}
}
}
logger('webfinger: ' . print_r($x,true), LOGGER_DATA, LOG_INFO);
- $arr = array('address' => $webbie, 'success' => false, 'webfinger' => $x);
+ $arr = array('address' => $webbie, 'protocol' => $protocol, 'success' => false, 'webfinger' => $x);
call_hooks('discover_channel_webfinger', $arr);
if($arr['success'])
return true;
- $aliases = array();
-
- // Now let's make some decisions on what we may need
- // to obtain further info
-
- $probe_atom = false;
- $probe_old = false;
- $probe_hcard = false;
-
- $address = '';
- $location = '';
- $nickname = '';
- $fullname = '';
- $avatar = '';
- $pubkey = '';
-
- if(is_array($x)) {
- if(array_key_exists('address',$x))
- $address = $x['address'];
- if(array_key_exists('location',$x))
- $location = $x['location'];
- if(array_key_exists('nickname',$x))
- $nickname = $x['nickname'];
- }
-
- if(! $x)
- $probe_old = true;
-
-
- if((! $dfrn) && (! $has_salmon))
- $probe_old = true;
-
- if($probe_old) {
- $y = old_webfinger($webbie);
- if($y) {
- logger('old_webfinger: ' . print_r($x,true));
- foreach($y as $link) {
- if($link['@attributes']['rel'] === NAMESPACE_DFRN)
- $dfrn = unamp($link['@attributes']['href']);
- if($link['@attributes']['rel'] === 'salmon')
- $notify = unamp($link['@attributes']['href']);
- if($link['@attributes']['rel'] === NAMESPACE_FEED)
- $poll = unamp($link['@attributes']['href']);
- if($link['@attributes']['rel'] === 'http://microformats.org/profile/hcard')
- $hcard = unamp($link['@attributes']['href']);
- if($link['@attributes']['rel'] === 'http://webfinger.net/rel/profile-page')
- $profile = unamp($link['@attributes']['href']);
- if($link['@attributes']['rel'] === 'http://portablecontacts.net/spec/1.0')
- $poco = unamp($link['@attributes']['href']);
- if($link['@attributes']['rel'] === 'http://joindiaspora.com/seed_location') {
- $diaspora_base = unamp($link['@attributes']['href']);
- $diaspora = true;
- }
- if($link['@attributes']['rel'] === 'http://joindiaspora.com/guid') {
- $diaspora_guid = unamp($link['@attributes']['href']);
- $diaspora = true;
- }
- if($link['@attributes']['rel'] === 'diaspora-public-key') {
- $diaspora_key = base64_decode(unamp($link['@attributes']['href']));
- if(strstr($diaspora_key,'RSA '))
- $pubkey = rsatopem($diaspora_key);
- else
- $pubkey = $diaspora_key;
- $diaspora = true;
- }
- if($link['@attributes']['rel'] == 'magic-public-key') {
- if(substr($link['@attributes']['href'],0,5) === 'data:') {
- $salmon_key = convert_salmon_key($link['@attributes']['href']);
- }
- }
- if($link['@attributes']['rel'] == 'salmon') {
- $has_salmon = true;
- $salmon = $link['@attributes']['href'];
- }
-
- if($link['@attributes']['rel'] == 'http://schemas.google.com/g/2010#updates-from') {
- $atom_feed = $link['@attributes']['href'];
- }
- if($link['@attributes']['rel'] === 'alias') {
- $aliases[] = $link['@attributes']['href'];
- }
- if($link['@attributes']['rel'] === 'subject') {
- $subject = $link['@attributes']['href'];
- }
- }
- }
- }
-
- if($subject || $aliases) {
- if(strpos($webbie,'@')) {
- $rhs = substr($webbie,strpos($webbie,'@')+1);
- }
- else {
- $m = parse_url($webbie);
- if($m) {
- $rhs = $m['host'] . (($m['port']) ? ':' . $m['port'] : '');
- }
- }
-
- $v = array('subject' => $subject,'aliases' => $aliases);
- $address = find_webfinger_address($v,$rhs);
- $location = find_webfinger_location($v,$rhs);
- if($address)
- $nickname = substr($address,0,strpos($address,'@'));
-
- }
-
- if($salmon_key && $has_salmon && $atom_feed && (! $dfrn) && (! $diaspora)) {
- $gnusoc = true;
- $probe_atom = true;
- }
-
- if(! $pubkey)
- $pubkey = $salmon_key;
-
- if(($dfrn || $diaspora) && $hcard)
- $probe_hcard = true;
-
- if(! $fullname)
- $fullname = $nickname;
-
- if($probe_atom) {
- $k = z_fetch_url($atom_feed);
- if($k['success'])
- $feed_meta = feed_meta($k['body']);
- if($feed_meta) {
-
- // stash any discovered pubsubhubbub hubs in case we need to follow them
- // this will save an expensive lookup later
-
- if($feed_meta['hubs'] && $address) {
- set_xconfig($address,'system','push_hubs',$feed_meta['hubs']);
- set_xconfig($address,'system','feed_url',$atom_feed);
- }
- if($feed_meta['author']['author_name']) {
- $fullname = $feed_meta['author']['author_name'];
- }
- if(! $avatar) {
- if($feed_meta['author']['author_photo'])
- $avatar = $feed_meta['author']['author_photo'];
- }
-
- // for GNU-social over-ride any url aliases we may have picked up in webfinger
- // The author.uri element in the feed is likely to be more accurate
-
- if($gnusoc && $feed_meta['author']['author_uri'])
- $location = $feed_meta['author']['author_uri'];
- }
- }
- else {
- if($probe_hcard) {
- $vcard = scrape_vcard($hcard);
- if($vcard) {
- logger('vcard: ' . print_r($vcard,true), LOGGER_DATA);
- if($vcard['fn'])
- $fullname = $vcard['fn'];
- if($vcard['photo'] && (strpos($vcard['photo'],'http') !== 0))
- $vcard['photo'] = $diaspora_base . '/' . $vcard['photo'];
- if(($vcard['public_key']) && (! $pubkey)) {
- $diaspora_key = $vcard['public_key'];
- if(strstr($diaspora_key,'RSA '))
- $pubkey = rsatopem($diaspora_key);
- else
- $pubkey = $diaspora_key;
- }
- if(! $avatar)
- $avatar = $vcard['photo'];
- if($diaspora) {
- if(($vcard['uid']) && (! $diaspora_guid))
- $diaspora_guid = $vcard['uid'];
- if(($vcard['url']) && (! $diaspora_base))
- $diaspora_base = $vcard['url'];
-
-
-
-
- }
-
- }
- }
- }
-
- if(($profile) && (! $location))
- $location = $profile;
-
- if($location) {
- $m = parse_url($location);
- $base = $m['scheme'] . '://' . $m['host'];
- $host = $m['host'];
- }
-
-
- if($diaspora && $diaspora_base && $diaspora_guid) {
- if($dfrn)
- $network = 'friendica-over-diaspora';
- else
- $network = 'diaspora';
-
- $base = trim($diaspora_base,'/');
- $notify = $base . '/receive';
-
- }
- else {
- if($gnusoc) {
- $network = 'gnusoc';
- $notify = $salmon;
- }
- }
-
-
- logger('network: ' . $network);
- logger('address: ' . $address);
- logger('fullname: ' . $fullname);
- logger('pubkey: ' . $pubkey);
- logger('location: ' . $location);
-
-
-
- // if we have everything we need, let's create the records
-
- if($network && $address && $fullname && $pubkey && $location) {
- $r = q("select * from xchan where xchan_hash = '%s' limit 1",
- dbesc($address)
- );
- if($r) {
- $r = q("update xchan set xchan_name = '%s', xchan_network = '%s', xchan_name_date = '%s' where xchan_hash = '%s'",
- dbesc($fullname),
- dbesc($network),
- dbesc(datetime_convert()),
- dbesc($address)
- );
- }
- else {
- $r = xchan_store_lowlevel(
- [
- 'xchan_hash' => $address,
- 'xchan_guid' => (($diaspora_guid) ? $diaspora_guid : $location),
- 'xchan_pubkey' => $pubkey,
- 'xchan_addr' => $address,
- 'xchan_url' => $location,
- 'xchan_name' => $fullname,
- 'xchan_name_date' => datetime_convert(),
- 'xchan_network' => $network
- ]
- );
- }
-
- $r = q("select * from hubloc where hubloc_hash = '%s' limit 1",
- dbesc($address)
- );
-
- if(! $r) {
- $r = hubloc_store_lowlevel(
- [
- 'hubloc_guid' => (($diaspora_guid) ? $diaspora_guid : $location),
- 'hubloc_hash' => $address,
- 'hubloc_addr' => $address,
- 'hubloc_network' => $network,
- 'hubloc_url' => $base,
- 'hubloc_host' => $host,
- 'hubloc_callback' => $notify,
- 'hubloc_updated' => datetime_convert(),
- 'hubloc_primary' => 1
- ]
- );
- }
- $photos = import_xchan_photo($avatar,$address);
- $r = q("update xchan set xchan_photo_date = '%s', xchan_photo_l = '%s', xchan_photo_m = '%s', xchan_photo_s = '%s', xchan_photo_mimetype = '%s' where xchan_hash = '%s'",
- dbescdate(datetime_convert()),
- dbesc($photos[0]),
- dbesc($photos[1]),
- dbesc($photos[2]),
- dbesc($photos[3]),
- dbesc($address)
- );
- return true;
- }
return false;
-}
-
+}
function webfinger_rfc7033($webbie,$zot = false) {
-
if(strpos($webbie,'@')) {
$lhs = substr($webbie,0,strpos($webbie,'@'));
$rhs = substr($webbie,strpos($webbie,'@')+1);
@@ -1520,92 +1207,26 @@ function webfinger_rfc7033($webbie,$zot = false) {
}
logger('fetching url from resource: ' . $rhs . ':' . $webbie);
- $s = z_fetch_url('https://' . $rhs . '/.well-known/webfinger?f=&resource=' . $resource . (($zot) ? '&zot=1' : ''));
+ // The default curl Accept: header is */*, which is incorrectly handled by Mastodon servers
+ // and results in a 406 (Not Acceptable) response, and will also incorrectly produce an XML
+ // document if you use 'application/jrd+json, */*'. We could set this to application/jrd+json,
+ // but some test webfinger servers may not explicitly set the content type and they would be
+ // blocked. The best compromise until Mastodon is fixed is to remove the Accept header which is
+ // accomplished by setting it to nothing.
+
+ $counter = 0;
+ $s = z_fetch_url('https://' . $rhs . '/.well-known/webfinger?f=&resource=' . $resource . (($zot) ? '&zot=1' : ''),
+ false, $counter, [ 'headers' => [ 'Accept:' ] ]);
if($s['success']) {
$j = json_decode($s['body'],true);
-
- // We could have a number of URL aliases and webbies
- // make an executive decision about the most likely "best" of each
- // by comparing against some examples from known networks we're likely to encounter.
- // Otherwise we have to store every alias that we may ever encounter and
- // validate every URL we ever find against every possible alias
-
- // @fixme pump.io is going to be a real bugger since it doesn't return subject or aliases
- // or provide lookup by url
-
- $j['address'] = find_webfinger_address($j,$rhs);
- $j['location'] = find_webfinger_location($j,$rhs);
- if($j['address'])
- $j['nickname'] = substr($j['address'],0,strpos($j['address'],'@'));
- }
- else
- return false;
-
- return($j);
-}
-
-function find_webfinger_address($j,$rhs) {
- if(is_array($j) && ($j)) {
- if(strpos($j['subject'],'acct:') !== false && strpos($j['subject'],'@' . $rhs))
- return str_replace('acct:','',$j['subject']);
- if($j['aliases']) {
- foreach($j['aliases'] as $alias) {
- if(strpos($alias,'acct:') !== false && strpos($alias,'@' . $rhs)) {
- return str_replace('acct:','',$alias);
- }
- }
- }
+ return($j);
}
- return '';
-}
+ return false;
-function find_webfinger_location($j,$rhs) {
- if(is_array($j) && ($j)) {
- if(strpos($j['subject'],'http') === 0) {
- $x = match_webfinger_location($j['subject'],$rhs);
- if($x)
- return $x;
- }
- if($j['aliases']) {
- foreach($j['aliases'] as $alias) {
- if(strpos($alias,'http') === 0) {
- $x = match_webfinger_location($alias,$rhs);
- if($x)
- return($x);
- }
- }
- }
- }
- return '';
}
-function match_webfinger_location($s,$h) {
-
- // GNU-social and the older StatusNet - the $host/user/123 form doesn't work
- if(preg_match('|' . $h . '/index.php/user/([0-9]*?)$|',$s))
- return $s;
- // Redmatrix / hubzilla
- if(preg_match('|' . $h . '/channel/|',$s))
- return $s;
- // Friendica
- if(preg_match('|' . $h . '/profile/|',$s))
- return $s;
-
- $arr = array('test' => $s, 'host' => $h, 'success' => false);
- call_hooks('match_webfinger_location',$arr);
- if($arr['success'])
- return $s;
- return '';
-}
-
-
-
-
-
-
-
function old_webfinger($webbie) {
$host = '';
@@ -1652,14 +1273,14 @@ function fetch_lrdd_template($host) {
}
if(! strpos($tpl,'{uri}'))
$tpl = '';
- return $tpl;
+ return $tpl;
}
function fetch_xrd_links($url) {
- logger('fetch_xrd_links: ' . $url, LOGGER_DEBUG);
+ logger('url: ' . $url, LOGGER_DEBUG);
$redirects = 0;
$x = z_fetch_url($url,false,$redirects,array('timeout' => 20));
@@ -1668,16 +1289,13 @@ function fetch_xrd_links($url) {
return array();
$xml = $x['body'];
- logger('fetch_xrd_links: ' . $xml, LOGGER_DATA);
+ logger('data: ' . $xml, LOGGER_DATA);
if ((! $xml) || (! stristr($xml,'<xrd')))
return array();
- // fix diaspora's bad xml
- $xml = str_replace(array('href=&quot;','&quot;/>'),array('href="','"/>'),$xml);
-
$h = parse_xml_string($xml);
- if(! $h)
+ if($h === false)
return array();
$arr = convert_xml_element_to_array($h);
@@ -1709,92 +1327,21 @@ function fetch_xrd_links($url) {
$links[]['@attributes'] = array('rel' => 'subject' , 'href' => $arr['xrd']['subject']);
}
- logger('fetch_xrd_links: ' . print_r($links,true), LOGGER_DATA);
+ logger('data: ' . print_r($links, true), LOGGER_DATA);
return $links;
}
-function scrape_vcard($url) {
-
- $ret = array();
-
- logger('scrape_vcard: url=' . $url);
-
- $x = z_fetch_url($url);
- if(! $x['success'])
- return $ret;
-
- $s = $x['body'];
-
- if(! $s)
- return $ret;
-
- $headers = $x['header'];
- $lines = explode("\n",$headers);
- if(count($lines)) {
- foreach($lines as $line) {
- // don't try and run feeds through the html5 parser
- if(stristr($line,'content-type:') && ((stristr($line,'application/atom+xml')) || (stristr($line,'application/rss+xml'))))
- return ret;
- }
- }
-
- try {
- $dom = HTML5_Parser::parse($s);
- } catch (DOMException $e) {
- logger('scrape_vcard: parse error: ' . $e);
- }
-
- if(! $dom)
- return $ret;
-
- // Pull out hCard profile elements
-
- $largest_photo = 0;
-
- $items = $dom->getElementsByTagName('*');
- foreach($items as $item) {
- if(attribute_contains($item->getAttribute('class'), 'vcard')) {
- $level2 = $item->getElementsByTagName('*');
- foreach($level2 as $x) {
- if(attribute_contains($x->getAttribute('id'),'pod_location'))
- $ret['pod_location'] = $x->textContent;
- if(attribute_contains($x->getAttribute('class'),'fn'))
- $ret['fn'] = $x->textContent;
- if(attribute_contains($x->getAttribute('class'),'uid'))
- $ret['uid'] = $x->textContent;
- if(attribute_contains($x->getAttribute('class'),'nickname'))
- $ret['nick'] = $x->textContent;
- if(attribute_contains($x->getAttribute('class'),'searchable'))
- $ret['searchable'] = $x->textContent;
- if(attribute_contains($x->getAttribute('class'),'key'))
- $ret['public_key'] = $x->textContent;
- if(attribute_contains($x->getAttribute('class'),'given_name'))
- $ret['given_name'] = $x->textContent;
- if(attribute_contains($x->getAttribute('class'),'family_name'))
- $ret['family_name'] = $x->textContent;
- if(attribute_contains($x->getAttribute('class'),'url'))
- $ret['url'] = $x->textContent;
-
- if((attribute_contains($x->getAttribute('class'),'photo'))
- || (attribute_contains($x->getAttribute('class'),'avatar'))) {
- $size = intval($x->getAttribute('width'));
- if(($size > $largest_photo) || (! $largest_photo)) {
- $ret['photo'] = $x->getAttribute('src');
- $largest_photo = $size;
- }
- }
- }
- }
- }
-
- return $ret;
-}
-
-
+/**
+ * @brief
+ *
+ * @param string $url The URL to scrape
+ * @return array
+ */
function scrape_feed($url) {
+ require_once('library/HTML5/Parser.php');
$ret = array();
$level = 0;
@@ -1807,15 +1354,14 @@ function scrape_feed($url) {
$code = $x['return_code'];
$s = $x['body'];
- logger('scrape_feed: returns: ' . $code . ' headers=' . $headers, LOGGER_DEBUG);
+ logger('returns: ' . $code . ' headers=' . $headers, LOGGER_DEBUG);
if(! $s) {
- logger('scrape_feed: no data returned for ' . $url);
+ logger('No data returned for ' . $url);
return $ret;
}
-
- $lines = explode("\n",$headers);
+ $lines = explode("\n", $headers);
if(count($lines)) {
foreach($lines as $line) {
if(stristr($line,'content-type:')) {
@@ -1839,15 +1385,14 @@ function scrape_feed($url) {
try {
$dom = HTML5_Parser::parse($s);
} catch (DOMException $e) {
- logger('scrape_feed: parse error: ' . $e);
+ logger('Parse error: ' . $e);
}
if(! $dom) {
- logger('scrape_feed: failed to parse.');
+ logger('Failed to parse.');
return $ret;
}
-
$head = $dom->getElementsByTagName('base');
if($head) {
foreach($head as $head0) {
@@ -1888,112 +1433,6 @@ function scrape_feed($url) {
-function service_plink($contact, $guid) {
-
- $plink = '';
-
- $m = parse_url($contact['xchan_url']);
- if($m) {
- $url = $m['scheme'] . '://' . $m['host'] . (($m['port']) ? ':' . $m['port'] : '');
- }
- else
- $url = 'https://' . substr($contact['xchan_addr'],strpos($contact['xchan_addr'],'@')+1);
-
- $handle = substr($contact['xchan_addr'], 0, strpos($contact['xchan_addr'],'@'));
-
- if($contact['xchan_network'] === 'diaspora')
- $plink = $url . '/posts/' . $guid;
- if($contact['xchan_network'] === 'friendica-over-diaspora')
- $plink = $url . '/display/' . $handle . '/' . $guid;
- if($contact['xchan_network'] === 'zot')
- $plink = $url . '/channel/' . $handle . '?f=&mid=' . $guid;
-
- return $plink;
-}
-
-
-function format_and_send_email($sender,$xchan,$item) {
-
- $title = $item['title'];
- $body = $item['body'];
-
- $textversion = strip_tags(html_entity_decode(bbcode(str_replace(array("\\r", "\\n"), array( "", "\n"), $body)),ENT_QUOTES,'UTF-8'));
-
- $htmlversion = bbcode(str_replace(array("\\r","\\n"), array("","<br />\n"),$body));
-
- $banner = t('$Projectname Notification');
- $product = t('$projectname'); // PLATFORM_NAME;
- $siteurl = z_root();
- $thanks = t('Thank You,');
- $sitename = get_config('system','sitename');
- $site_admin = sprintf( t('%s Administrator'), $sitename);
-
- // load the template for private message notifications
- $tpl = get_markup_template('email_notify_html.tpl');
- $email_html_body = replace_macros($tpl,array(
- '$banner' => $banner,
- '$notify_icon' => Zotlabs\Lib\System::get_notify_icon(),
- '$product' => $product,
- '$preamble' => '',
- '$sitename' => $sitename,
- '$siteurl' => $siteurl,
- '$source_name' => $sender['xchan_name'],
- '$source_link' => $sender['xchan_url'],
- '$source_photo' => $sender['xchan_photo_m'],
- '$username' => $xchan['xchan_name'],
- '$hsitelink' => $datarray['hsitelink'],
- '$hitemlink' => $datarray['hitemlink'],
- '$thanks' => $thanks,
- '$site_admin' => $site_admin,
- '$title' => $title,
- '$htmlversion' => $htmlversion,
- ));
-
- // load the template for private message notifications
- $tpl = get_markup_template('email_notify_text.tpl');
- $email_text_body = replace_macros($tpl, array(
- '$banner' => $banner,
- '$product' => $product,
- '$preamble' => '',
- '$sitename' => $sitename,
- '$siteurl' => $siteurl,
- '$source_name' => $sender['xchan_name'],
- '$source_link' => $sender['xchan_url'],
- '$source_photo' => $sender['xchan_photo_m'],
- '$username' => $xchan['xchan_name'],
- '$hsitelink' => $datarray['hsitelink'],
- '$hitemlink' => $datarray['hitemlink'],
- '$thanks' => $thanks,
- '$site_admin' => $site_admin,
- '$title' => $title,
- '$textversion' => $textversion
- ));
-
- $sender_name = t('Administrator');
-
- $hostname = App::get_hostname();
- if(strpos($hostname,':'))
- $hostname = substr($hostname,0,strpos($hostname,':'));
- $sender_email = get_config('system','reply_address');
- if(! $sender_email)
- $sender_email = 'noreply' . '@' . $hostname;
-
- // use the EmailNotification library to send the message
-
- Zotlabs\Lib\Enotify::send(array(
- 'fromName' => $product,
- 'fromEmail' => $sender_email,
- 'replyTo' => $sender_email,
- 'toEmail' => str_replace('mailto:','',$xchan['xchan_addr']),
- 'messageSubject' => (($title) ? $title : t('No Subject')),
- 'htmlVersion' => $email_html_body,
- 'textVersion' => $email_text_body,
- 'additionalMailHeader' => '',
- ));
-
-}
-
-
function do_delivery($deliveries) {
if(! (is_array($deliveries) && count($deliveries)))
@@ -2028,8 +1467,6 @@ function do_delivery($deliveries) {
if($deliver)
Zotlabs\Daemon\Master::Summon(array('Deliver',$deliver));
-
-
}
@@ -2086,7 +1523,7 @@ function get_site_info() {
$commit = '';
}
else {
- $version = $commit = '';
+ $version = $commit = '';
}
//Statistics
@@ -2103,49 +1540,53 @@ function get_site_info() {
foreach(App::$config['feature_lock'] as $k => $v) {
if($k === 'config_loaded')
continue;
+
$locked_features[$k] = intval($v);
}
}
-
- $data = Array(
- 'version' => $version,
- 'version_tag' => $tag,
- 'server_role' => Zotlabs\Lib\System::get_server_role(),
- 'commit' => $commit,
- 'url' => z_root(),
- 'plugins' => $visible_plugins,
- 'register_policy' => $register_policy[get_config('system','register_policy')],
- 'invitation_only' => intval(get_config('system','invitation_only')),
- 'directory_mode' => $directory_mode[get_config('system','directory_mode')],
- 'language' => get_config('system','language'),
- 'rss_connections' => intval(get_config('system','feed_contacts')),
- 'expiration' => $site_expire,
+ $data = [
+ 'url' => z_root(),
+ 'platform' => Zotlabs\Lib\System::get_platform_name(),
+ 'site_name' => (($site_name) ? $site_name : ''),
+ 'version' => $version,
+ 'version_tag' => $tag,
+ 'server_role' => Zotlabs\Lib\System::get_server_role(),
+ 'commit' => $commit,
+ 'plugins' => $visible_plugins,
+ 'register_policy' => $register_policy[get_config('system','register_policy')],
+ 'invitation_only' => intval(get_config('system','invitation_only')),
+ 'directory_mode' => $directory_mode[get_config('system','directory_mode')],
+ 'language' => get_config('system','language'),
+ 'rss_connections' => intval(get_config('system','feed_contacts')),
+ 'expiration' => $site_expire,
'default_service_restrictions' => $service_class,
- 'locked_features' => $locked_features,
- 'admin' => $admin,
- 'site_name' => (($site_name) ? $site_name : ''),
- 'platform' => Zotlabs\Lib\System::get_platform_name(),
- 'dbdriver' => DBA::$dba->getdriver(),
- 'lastpoll' => get_config('system','lastpoll'),
- 'info' => (($site_info) ? $site_info : ''),
- 'channels_total' => $channels_total_stat,
- 'channels_active_halfyear' => $channels_active_halfyear_stat,
- 'channels_active_monthly' => $channels_active_monthly_stat,
- 'local_posts' => $local_posts_stat,
- 'hide_in_statistics' => $hide_in_statistics
- );
+ 'locked_features' => $locked_features,
+ 'admin' => $admin,
+ 'dbdriver' => DBA::$dba->getdriver(),
+ 'lastpoll' => get_config('system','lastpoll'),
+ 'info' => (($site_info) ? $site_info : ''),
+ 'channels_total' => $channels_total_stat,
+ 'channels_active_halfyear' => $channels_active_halfyear_stat,
+ 'channels_active_monthly' => $channels_active_monthly_stat,
+ 'local_posts' => $local_posts_stat,
+ 'hide_in_statistics' => $hide_in_statistics
+ ];
+
return $data;
}
-
-
+/**
+ * @brief
+ *
+ * @param string $url
+ * @return boolean
+ */
function check_siteallowed($url) {
$retvalue = true;
-
$arr = array('url' => $url);
call_hooks('check_siteallowed',$arr);
@@ -2171,9 +1612,16 @@ function check_siteallowed($url) {
}
}
}
+
return $retvalue;
}
+/**
+ * @brief
+ *
+ * @param string $hash
+ * @return boolean
+ */
function check_channelallowed($hash) {
$retvalue = true;
@@ -2203,13 +1651,22 @@ function check_channelallowed($hash) {
}
}
}
+
return $retvalue;
}
function deliverable_singleton($channel_id,$xchan) {
+
+ if(array_key_exists('xchan_hash',$xchan))
+ $xchan_hash = $xchan['xchan_hash'];
+ elseif(array_key_exists('hubloc_hash',$xchan))
+ $xchan_hash = $xchan['hubloc_hash'];
+ else
+ return true;
+
$r = q("select abook_instance from abook where abook_channel = %d and abook_xchan = '%s' limit 1",
intval($channel_id),
- dbesc($xchan['xchan_hash'])
+ dbesc($xchan_hash)
);
if($r) {
if(! $r[0]['abook_instance'])
@@ -2233,24 +1690,30 @@ function get_repository_version($branch = 'master') {
return $matches[3];
}
return '?.?';
-
}
+/**
+ * @brief Get translated network name.
+ *
+ * @param string $s Network string, see boot.php
+ * @return string Translated name of the network
+ */
function network_to_name($s) {
$nets = array(
- NETWORK_DFRN => t('Friendica'),
- NETWORK_FRND => t('Friendica'),
- NETWORK_OSTATUS => t('OStatus'),
- NETWORK_GNUSOCIAL => t('GNU-Social'),
- NETWORK_FEED => t('RSS/Atom'),
- NETWORK_MAIL => t('Email'),
- NETWORK_DIASPORA => t('Diaspora'),
- NETWORK_FACEBOOK => t('Facebook'),
- NETWORK_ZOT => t('Zot'),
- NETWORK_LINKEDIN => t('LinkedIn'),
- NETWORK_XMPP => t('XMPP/IM'),
- NETWORK_MYSPACE => t('MySpace'),
+ NETWORK_DFRN => t('Friendica'),
+ NETWORK_FRND => t('Friendica'),
+ NETWORK_OSTATUS => t('OStatus'),
+ NETWORK_GNUSOCIAL => t('GNU-Social'),
+ NETWORK_FEED => t('RSS/Atom'),
+ NETWORK_ACTIVITYPUB => t('ActivityPub'),
+ NETWORK_MAIL => t('Email'),
+ NETWORK_DIASPORA => t('Diaspora'),
+ NETWORK_FACEBOOK => t('Facebook'),
+ NETWORK_ZOT => t('Zot'),
+ NETWORK_LINKEDIN => t('LinkedIn'),
+ NETWORK_XMPP => t('XMPP/IM'),
+ NETWORK_MYSPACE => t('MySpace'),
);
call_hooks('network_to_name', $nets);
@@ -2258,27 +1721,24 @@ function network_to_name($s) {
$search = array_keys($nets);
$replace = array_values($nets);
- return str_replace($search,$replace,$s);
-
+ return str_replace($search, $replace, $s);
}
-
+/**
+ * @brief Send a text email message.
+ *
+ * @param array $params an assoziative array with:
+ * * \e string \b fromName name of the sender
+ * * \e string \b fromEmail email of the sender
+ * * \e string \b replyTo replyTo address to direct responses
+ * * \e string \b toEmail destination email address
+ * * \e string \b messageSubject subject of the message
+ * * \e string \b htmlVersion html version of the message
+ * * \e string \b textVersion text only version of the message
+ * * \e string \b additionalMailHeader additions to the smtp mail header
+ */
function z_mail($params) {
- /**
- * @brief Send a text email message
- *
- * @param array $params an assoziative array with:
- * * \e string \b fromName name of the sender
- * * \e string \b fromEmail email of the sender
- * * \e string \b replyTo replyTo address to direct responses
- * * \e string \b toEmail destination email address
- * * \e string \b messageSubject subject of the message
- * * \e string \b htmlVersion html version of the message
- * * \e string \b textVersion text only version of the message
- * * \e string \b additionalMailHeader additions to the smtp mail header
- */
-
if(! $params['fromEmail']) {
$params['fromEmail'] = get_config('system','from_email');
if(! $params['fromEmail'])
@@ -2324,8 +1784,13 @@ function z_mail($params) {
return $res;
}
-// discover the best API path available for redmatrix/hubzilla servers
+/**
+ * @brief Discover the best API path available for redmatrix/hubzilla servers.
+ *
+ * @param string $host
+ * @return string
+ */
function probe_api_path($host) {
$schemes = ['https', 'http' ];
@@ -2335,10 +1800,182 @@ function probe_api_path($host) {
foreach($paths as $path) {
$curpath = $scheme . '://' . $host . $path;
$x = z_fetch_url($curpath);
- if($x['success'] && ! strlen($x['body'],'not implemented'))
- return str_replace('version','',$curpath);
+ if($x['success'] && ! strlen($x['body'], 'not implemented'))
+ return str_replace('version', '', $curpath);
}
}
return '';
}
+
+
+function scrape_vcard($url) {
+
+ require_once('library/HTML5/Parser.php');
+
+ $ret = array();
+
+ logger('url=' . $url);
+
+ $x = z_fetch_url($url);
+ if(! $x['success'])
+ return $ret;
+
+ $s = $x['body'];
+
+ if(! $s)
+ return $ret;
+
+ $headers = $x['header'];
+ $lines = explode("\n",$headers);
+ if(count($lines)) {
+ foreach($lines as $line) {
+ // don't try and run feeds through the html5 parser
+ if(stristr($line,'content-type:') && ((stristr($line,'application/atom+xml')) || (stristr($line,'application/rss+xml'))))
+ return ret;
+ }
+ }
+
+ try {
+ $dom = HTML5_Parser::parse($s);
+ } catch (DOMException $e) {
+ logger('Parse error: ' . $e);
+ }
+
+ if(! $dom)
+ return $ret;
+
+ // Pull out hCard profile elements
+
+ $largest_photo = 0;
+
+ $items = $dom->getElementsByTagName('*');
+ foreach($items as $item) {
+ if(attribute_contains($item->getAttribute('class'), 'vcard')) {
+ $level2 = $item->getElementsByTagName('*');
+ foreach($level2 as $x) {
+ if(attribute_contains($x->getAttribute('id'),'pod_location'))
+ $ret['pod_location'] = $x->textContent;
+ if(attribute_contains($x->getAttribute('class'),'fn'))
+ $ret['fn'] = $x->textContent;
+ if(attribute_contains($x->getAttribute('class'),'uid'))
+ $ret['uid'] = $x->textContent;
+ if(attribute_contains($x->getAttribute('class'),'nickname'))
+ $ret['nick'] = $x->textContent;
+ if(attribute_contains($x->getAttribute('class'),'searchable'))
+ $ret['searchable'] = $x->textContent;
+ if(attribute_contains($x->getAttribute('class'),'key'))
+ $ret['public_key'] = $x->textContent;
+ if(attribute_contains($x->getAttribute('class'),'given_name'))
+ $ret['given_name'] = $x->textContent;
+ if(attribute_contains($x->getAttribute('class'),'family_name'))
+ $ret['family_name'] = $x->textContent;
+ if(attribute_contains($x->getAttribute('class'),'url'))
+ $ret['url'] = $x->textContent;
+
+ if((attribute_contains($x->getAttribute('class'),'photo'))
+ || (attribute_contains($x->getAttribute('class'),'avatar'))) {
+ $size = intval($x->getAttribute('width'));
+ if(($size > $largest_photo) || (! $largest_photo)) {
+ $ret['photo'] = $x->getAttribute('src');
+ $largest_photo = $size;
+ }
+ }
+ }
+ }
+ }
+
+ return $ret;
+}
+
+function service_plink($contact, $guid) {
+
+ $plink = '';
+
+ $m = parse_url($contact['xchan_url']);
+ if($m) {
+ $url = $m['scheme'] . '://' . $m['host'] . (($m['port']) ? ':' . $m['port'] : '');
+ }
+ else {
+ $url = 'https://' . substr($contact['xchan_addr'],strpos($contact['xchan_addr'],'@')+1);
+ }
+
+ $handle = substr($contact['xchan_addr'], 0, strpos($contact['xchan_addr'],'@'));
+
+ $plink = $url . '/channel/' . $handle . '?f=&mid=' . $guid;
+
+ $x = [ 'xchan' => $contact, 'guid' => $guid, 'url' => $url, 'plink' => $plink ];
+ call_hooks('service_plink', $x);
+
+ return $x['plink'];
+}
+
+function getBestSupportedMimeType($mimeTypes = null, $acceptedTypes = false) {
+ // Values will be stored in this array
+
+ if($acceptedTypes === false)
+ $acceptedTypes = $_SERVER['HTTP_ACCEPT'];
+
+ $AcceptTypes = Array ();
+
+ // Accept header is case insensitive, and whitespace isn’t important
+ $accept = strtolower(str_replace(' ', '', $acceptedTypes));
+ // divide it into parts in the place of a ","
+ $accept = explode(',', $accept);
+ foreach ($accept as $a) {
+ // the default quality is 1.
+ $q = 1;
+ // check if there is a different quality
+ if (strpos($a, ';q=')) {
+ // divide "mime/type;q=X" into two parts: "mime/type" i "X"
+ list($a, $q) = explode(';q=', $a);
+ }
+ // mime-type $a is accepted with the quality $q
+ // WARNING: $q == 0 means, that mime-type isn’t supported!
+ $AcceptTypes[$a] = $q;
+ }
+ arsort($AcceptTypes);
+
+ // if no parameter was passed, just return parsed data
+ if (!$mimeTypes) return $AcceptTypes;
+
+ $mimeTypes = array_map('strtolower', (array)$mimeTypes);
+
+ // let’s check our supported types:
+ foreach ($AcceptTypes as $mime => $q) {
+ if ($q && in_array($mime, $mimeTypes)) return $mime;
+ }
+ // no mime-type found
+ return null;
+}
+
+
+function jsonld_document_loader($url) {
+
+ // perform caching for jsonld normaliser
+
+ require_once('library/jsonld/jsonld.php');
+
+ $cachepath = 'store/[data]/ldcache';
+ if(! is_dir($cachepath))
+ os_mkdir($cachepath,STORAGE_DEFAULT_PERMISSIONS,true);
+
+ $filename = $cachepath . '/' . urlencode($url);
+ if(file_exists($filename) && filemtime($filename) > time() - (12 * 60 * 60)) {
+ return json_decode(file_get_contents($filename));
+ }
+
+ $r = jsonld_default_document_loader($url);
+ if($r) {
+ file_put_contents($filename,json_encode($r));
+ return $r;
+ }
+
+ logger('not found');
+ if(file_exists($filename)) {
+ return json_decode(file_get_contents($filename));
+ }
+
+ return [];
+
+} \ No newline at end of file
diff --git a/include/oauth2.php b/include/oauth2.php
new file mode 100644
index 000000000..3a71a651d
--- /dev/null
+++ b/include/oauth2.php
@@ -0,0 +1,23 @@
+<?php
+
+/*
+ $storage = new OAuth2\Storage\Pdo(\DBA::$dba->db);
+ $config = [
+ 'use_openid_connect' => true,
+ 'issuer' => \Zotlabs\Lib\System::get_site_name()
+ ];
+
+ $oauth2_server = new OAuth2\Server($storage,$config);
+
+ $oauth2_server->addGrantType(new OAuth2\GrantType\ClientCredentials($storage));
+ $oauth2_server->addGrantType(new OAuth2\GrantType\AuthorizationCode($storage));
+
+ $keyStorage = new OAuth2\Storage\Memory( [
+ 'keys' => [
+ 'public_key' => get_config('system','pubkey'),
+ 'private_key' => get_config('system','prvkey')
+ ]
+ ]);
+
+ $oauth2_server->addStorage($keyStorage,'public_key');
+*/ \ No newline at end of file
diff --git a/include/oembed.php b/include/oembed.php
index aac7d15b4..c2bf0a0ed 100755
--- a/include/oembed.php
+++ b/include/oembed.php
@@ -134,7 +134,9 @@ function oembed_fetch_url($embedurl){
$txt = null;
// we should try to cache this and avoid a lookup on each render
- $zrl = is_matrix_url($embedurl);
+ $is_matrix = is_matrix_url($embedurl);
+
+ $zrl = ((get_config('system','oembed_zrl')) ? $is_matrix : false);
$furl = ((local_channel() && $zrl) ? zid($embedurl) : $embedurl);
@@ -149,7 +151,14 @@ function oembed_fetch_url($embedurl){
if ($action !== 'block') {
// try oembed autodiscovery
$redirects = 0;
- $result = z_fetch_url($furl, false, $redirects, array('timeout' => 30, 'accept_content' => "text/*", 'novalidate' => true ));
+ $result = z_fetch_url($furl, false, $redirects,
+ [
+ 'timeout' => 30,
+ 'accept_content' => "text/*",
+ 'novalidate' => true,
+ 'session' => ((local_channel() && $zrl) ? true : false)
+ ]
+ );
if($result['success'])
$html_text = $result['body'];
@@ -200,7 +209,7 @@ function oembed_fetch_url($embedurl){
if ($txt[0]!="{") $txt='{"type":"error"}';
- //save in cache
+ // save in cache
if(! get_config('system','oembed_cache_disable'))
Zlib\Cache::set('[' . App::$videowidth . '] ' . $furl, $txt);
@@ -215,7 +224,18 @@ function oembed_fetch_url($embedurl){
if($action === 'filter') {
if($j['html']) {
$orig = $j['html'];
- $allow_position = (($zrl) ? true : false);
+ $allow_position = (($is_matrix) ? true : false);
+
+ // some sites wrap their entire embed in an iframe
+ // which we will purify away and which we provide anyway.
+ // So if we see this, grab the frame src url and use that
+ // as the embed content - which will still need to be purified.
+
+ if(preg_match('#\<iframe(.*?)src\=[\'\"](.*?)[\'\"]#',$j['html'],$matches)) {
+ $x = z_fetch_url($matches[2]);
+ $j['html'] = $x['body'];
+ }
+
$j['html'] = purify_html($j['html'],$allow_position);
if($j['html'] != $orig) {
logger('oembed html was purified. original: ' . $orig . ' purified: ' . $j['html'], LOGGER_DEBUG, LOG_INFO);
diff --git a/include/page_widgets.php b/include/page_widgets.php
deleted file mode 100644
index 3270de4a3..000000000
--- a/include/page_widgets.php
+++ /dev/null
@@ -1,52 +0,0 @@
-<?php
-
-// A basic toolbar for observers with write_pages permissions
-
-function writepages_widget ($who,$which) {
- return replace_macros(get_markup_template('write_pages.tpl'), array(
- '$new' => t('New Page'),
- '$newurl' => "webpages/$who",
- '$edit' => t('Edit'),
- '$editurl' => "editwebpage/$who/$which"
- ));
-}
-
-
-
-// Chan is channel_id, $which is channel_address - we'll need to pass observer later too.
-
-function pagelist_widget ($owner,$which) {
-
- $r = q("select * from iconfig left join item on iconfig.iid = item.id where item_id.uid = %d
- and iconfig.cat = 'system' and iconfig.k = 'WEBPAGE' order by item.created desc",
- intval($owner)
- );
-
- $pages = null;
-
- if($r) {
- $pages = array();
- foreach($r as $rr) {
- $pages[$rr['iid']][] = array('url' => $rr['iid'],'pagetitle' => $rr['v'],'title' => $rr['title'],'created' => datetime_convert('UTC',date_default_timezone_get(),$rr['created']),'edited' => datetime_convert('UTC',date_default_timezone_get(),$rr['edited']));
- }
- }
-
- //Build the base URL for edit links
- $url = z_root() . "/editwebpage/" . $which;
- // This isn't pretty, but it works. Until I figure out what to do with the UI, it's Good Enough(TM).
- return $o . replace_macros(get_markup_template("webpagelist.tpl"), array(
- '$baseurl' => $url,
- '$edit' => t('Edit'),
- '$pages' => $pages,
- '$channel' => $which,
- '$view' => t('View'),
- '$preview' => t('Preview'),
- '$actions_txt' => t('Actions'),
- '$pagelink_txt' => t('Page Link'),
- '$title_txt' => t('Title'),
- '$created_txt' => t('Created'),
- '$edited_txt' => t('Edited')
-
- ));
-
-}
diff --git a/include/perm_upgrade.php b/include/perm_upgrade.php
index 5be1ffbb2..9eb1efba2 100644
--- a/include/perm_upgrade.php
+++ b/include/perm_upgrade.php
@@ -135,6 +135,9 @@ function translate_abook_perms_outbound(&$abook) {
$my_perms = 0;
$their_perms = 0;
+ if(! $abook)
+ return;
+
if(array_key_exists('abconfig',$abook) && is_array($abook['abconfig']) && $abook['abconfig']) {
foreach($abook['abconfig'] as $p) {
if($p['cat'] === 'their_perms') {
diff --git a/include/permissions.php b/include/permissions.php
index d21b45550..f97142fab 100644
--- a/include/permissions.php
+++ b/include/permissions.php
@@ -7,61 +7,11 @@ require_once('include/security.php');
*
* This file conntains functions to check and work with permissions.
*
- * Most of this file is obsolete and has been superceded by extensible permissions in v1.12; it is left here
- * for reference and because we haven't yet checked that all functions have been replaced and are available
- * elsewhere (typically Zotlabs/Access/*).
*/
/**
- * @brief Return an array with all available permissions.
- *
- * These are channel specific permissions.
- * The list of available permissions can get manipulated by the <i>hook</i>
- * <b>global_permissions</b>.
- *
- * @return array associative array containing all permissions
- */
-function get_perms() {
-
-// thinking about making element[2] a bitmask instead of boolean so that we can provide a list of applicable selections
-// for any given permission. Currently we use the boolean to disallow write access to "everybody", but we also want to be
-// able to handle troublesome settings such as allowing channel_w_stream to anybody in the network. You can allow it, but
-// there's no way to implement sending it.
-
- $global_perms = array(
- // Read only permissions
- 'view_stream' => array('channel_r_stream', intval(PERMS_R_STREAM), true, t('Can view my normal stream and posts'), ''),
- 'view_profile' => array('channel_r_profile', intval(PERMS_R_PROFILE), true, t('Can view my default channel profile'), ''),
- 'view_contacts' => array('channel_r_abook', intval(PERMS_R_ABOOK), true, t('Can view my connections'), ''),
- 'view_storage' => array('channel_r_storage', intval(PERMS_R_STORAGE), true, t('Can view my file storage and photos'), ''),
- 'view_pages' => array('channel_r_pages', intval(PERMS_R_PAGES), true, t('Can view my webpages'), ''),
-
- // Write permissions
- 'send_stream' => array('channel_w_stream', intval(PERMS_W_STREAM), false, t('Can send me their channel stream and posts'), ''),
- 'post_wall' => array('channel_w_wall', intval(PERMS_W_WALL), false, t('Can post on my channel page ("wall")'), ''),
- 'post_comments' => array('channel_w_comment', intval(PERMS_W_COMMENT), false, t('Can comment on or like my posts'), ''),
- 'post_mail' => array('channel_w_mail', intval(PERMS_W_MAIL), false, t('Can send me private mail messages'), ''),
- 'post_like' => array('channel_w_like', intval(PERMS_W_LIKE), false, t('Can like/dislike stuff'), t('Profiles and things other than posts/comments')),
-
- 'tag_deliver' => array('channel_w_tagwall', intval(PERMS_W_TAGWALL), false, t('Can forward to all my channel contacts via post @mentions'), t('Advanced - useful for creating group forum channels')),
- 'chat' => array('channel_w_chat', intval(PERMS_W_CHAT), false, t('Can chat with me (when available)'), t('')),
- 'write_storage' => array('channel_w_storage', intval(PERMS_W_STORAGE), false, t('Can write to my file storage and photos'), ''),
- 'write_pages' => array('channel_w_pages', intval(PERMS_W_PAGES), false, t('Can edit my webpages'), ''),
-
- 'republish' => array('channel_a_republish', intval(PERMS_A_REPUBLISH), false, t('Can source my public posts in derived channels'), t('Somewhat advanced - very useful in open communities')),
-
- 'delegate' => array('channel_a_delegate', intval(PERMS_A_DELEGATE), false, t('Can administer my channel resources'), t('Extremely advanced. Leave this alone unless you know what you are doing')),
- );
- $ret = array('global_permissions' => $global_perms);
- call_hooks('global_permissions', $ret);
-
- return $ret['global_permissions'];
-}
-
-
-/**
* get_all_perms($uid,$observer_xchan)
*
* @param int $uid The channel_id associated with the resource owner
@@ -297,7 +247,6 @@ function get_all_perms($uid, $observer_xchan, $internal_use = true) {
*
* Checks if the given observer with the hash $observer_xchan has permission
* $permission on channel_id $uid.
- * $permission is one defined in get_perms();
*
* @param int $uid The channel_id associated with the resource owner
* @param string $observer_xchan The xchan_hash representing the observer
@@ -314,11 +263,12 @@ function perm_is_allowed($uid, $observer_xchan, $permission) {
'channel_id' => $uid,
'observer_hash' => $observer_xchan,
'permission' => $permission,
- 'result' => false);
+ 'result' => 'unset');
call_hooks('perm_is_allowed', $arr);
- if($arr['result'])
- return true;
+ if($arr['result'] !== 'unset') {
+ return $arr['result'];
+ }
$global_perms = \Zotlabs\Access\Permissions::Perms();
@@ -464,7 +414,7 @@ function perm_is_allowed($uid, $observer_xchan, $permission) {
function get_all_api_perms($uid,$api) {
- $global_perms = get_perms();
+ $global_perms = \Zotlabs\Access\Permissions::Perms();
$ret = array();
@@ -567,6 +517,7 @@ function site_default_perms() {
'view_contacts' => PERMS_PUBLIC,
'view_storage' => PERMS_PUBLIC,
'view_pages' => PERMS_PUBLIC,
+ 'view_wiki' => PERMS_PUBLIC,
'send_stream' => PERMS_SPECIFIC,
'post_wall' => PERMS_SPECIFIC,
'post_comments' => PERMS_SPECIFIC,
@@ -575,16 +526,15 @@ function site_default_perms() {
'chat' => PERMS_SPECIFIC,
'write_storage' => PERMS_SPECIFIC,
'write_pages' => PERMS_SPECIFIC,
+ 'write_wiki' => PERMS_SPECIFIC,
'delegate' => PERMS_SPECIFIC,
'post_like' => PERMS_NETWORK
);
- $global_perms = get_perms();
+ $global_perms = \Zotlabs\Access\Permissions::Perms();
foreach($global_perms as $perm => $v) {
- $x = get_config('default_perms', $perm);
- if($x === false)
- $x = $typical[$perm];
+ $x = get_config('default_perms', $perm, $typical[$perm]);
$ret[$perm] = $x;
}
@@ -592,362 +542,3 @@ function site_default_perms() {
}
-/**
- * @brief Return an array of all permissions for this role.
- *
- * Given a string for the channel role ('social','forum', etc)
- * return an array of all permission fields pre-filled for this role.
- * This includes the channel permission scope indicators (anything beginning with 'channel_') as well as
- * * perms_auto: true or false to create auto-permissions for this channel
- * * perms_follow: The permissions to apply when initiating a connection request to another channel
- * * perms_accept: The permissions to apply when accepting a connection request from another channel (not automatic)
- * * default_collection: true or false to make the default ACL include the channel's default collection
- * * directory_publish: true or false to publish this channel in the directory
- * Any attributes may be extended (new roles defined) and modified (specific permissions altered) by plugins
- *
- * @param string $role
- * @return array
- */
-function get_role_perms($role) {
-
- $ret = array();
-
- $ret['role'] = $role;
-
- switch($role) {
- case 'social':
- $ret['perms_auto'] = false;
- $ret['default_collection'] = false;
- $ret['directory_publish'] = true;
- $ret['online'] = true;
- $ret['perms_connect'] = [
- 'view_stream', 'view_profile', 'view_contacts', 'view_storage',
- 'view_pages', 'send_stream', 'post_wall', 'post_comments',
- 'post_mail', 'chat', 'post_like', 'republish' ];
- $ret['limits'] = [
- 'view_stream' => PERMS_PUBLIC,
- 'view_profile' => PERMS_PUBLIC,
- 'view_contacts' => PERMS_PUBLIC,
- 'view_storage' => PERMS_PUBLIC,
- 'view_pages' => PERMS_PUBLIC,
- 'send_stream' => PERMS_SPECIFIC,
- 'post_wall' => PERMS_SPECIFIC,
- 'post_comments' => PERMS_SPECIFIC,
- 'post_mail' => PERMS_SPECIFIC,
- 'post_like' => PERMS_SPECIFIC,
- 'tag_deliver' => PERMS_SPECIFIC,
- 'chat' => PERMS_SPECIFIC,
- 'write_storage' => PERMS_SPECIFIC,
- 'write_pages' => PERMS_SPECIFIC,
- 'republish' => PERMS_SPECIFIC,
- 'delegate' => PERMS_SPECIFIC
- ];
-
- break;
-
- case 'social_restricted':
- $ret['perms_auto'] = false;
- $ret['default_collection'] = true;
- $ret['directory_publish'] = true;
- $ret['online'] = true;
- $ret['perms_connect'] = [
- 'view_stream', 'view_profile', 'view_contacts', 'view_storage',
- 'view_pages', 'send_stream', 'post_wall', 'post_comments',
- 'post_mail', 'chat', 'post_like' ];
- $ret['limits'] = [
- 'view_stream' => PERMS_PUBLIC,
- 'view_profile' => PERMS_PUBLIC,
- 'view_contacts' => PERMS_PUBLIC,
- 'view_storage' => PERMS_PUBLIC,
- 'view_pages' => PERMS_PUBLIC,
- 'send_stream' => PERMS_SPECIFIC,
- 'post_wall' => PERMS_SPECIFIC,
- 'post_comments' => PERMS_SPECIFIC,
- 'post_mail' => PERMS_SPECIFIC,
- 'post_like' => PERMS_SPECIFIC,
- 'tag_deliver' => PERMS_SPECIFIC,
- 'chat' => PERMS_SPECIFIC,
- 'write_storage' => PERMS_SPECIFIC,
- 'write_pages' => PERMS_SPECIFIC,
- 'republish' => PERMS_SPECIFIC,
- 'delegate' => PERMS_SPECIFIC
- ];
-
-
- break;
-
- case 'social_private':
- $ret['perms_auto'] = false;
- $ret['default_collection'] = true;
- $ret['directory_publish'] = false;
- $ret['online'] = false;
- $ret['perms_connect'] = [
- 'view_stream', 'view_profile', 'view_contacts', 'view_storage',
- 'view_pages', 'send_stream', 'post_wall', 'post_comments',
- 'post_mail', 'post_like' ];
- $ret['limits'] = [
- 'view_stream' => PERMS_PUBLIC,
- 'view_profile' => PERMS_PUBLIC,
- 'view_contacts' => PERMS_SPECIFIC,
- 'view_storage' => PERMS_SPECIFIC,
- 'view_pages' => PERMS_PUBLIC,
- 'send_stream' => PERMS_SPECIFIC,
- 'post_wall' => PERMS_SPECIFIC,
- 'post_comments' => PERMS_SPECIFIC,
- 'post_mail' => PERMS_SPECIFIC,
- 'post_like' => PERMS_SPECIFIC,
- 'tag_deliver' => PERMS_SPECIFIC,
- 'chat' => PERMS_SPECIFIC,
- 'write_storage' => PERMS_SPECIFIC,
- 'write_pages' => PERMS_SPECIFIC,
- 'republish' => PERMS_SPECIFIC,
- 'delegate' => PERMS_SPECIFIC
- ];
-
- break;
-
- case 'forum':
- $ret['perms_auto'] = true;
- $ret['default_collection'] = false;
- $ret['directory_publish'] = true;
- $ret['online'] = false;
- $ret['perms_connect'] = [
- 'view_stream', 'view_profile', 'view_contacts', 'view_storage',
- 'view_pages', 'post_wall', 'post_comments', 'tag_deliver',
- 'post_mail', 'post_like' , 'republish', 'chat' ];
- $ret['limits'] = [
- 'view_stream' => PERMS_PUBLIC,
- 'view_profile' => PERMS_PUBLIC,
- 'view_contacts' => PERMS_PUBLIC,
- 'view_storage' => PERMS_PUBLIC,
- 'view_pages' => PERMS_PUBLIC,
- 'send_stream' => PERMS_SPECIFIC,
- 'post_wall' => PERMS_SPECIFIC,
- 'post_comments' => PERMS_SPECIFIC,
- 'post_mail' => PERMS_SPECIFIC,
- 'post_like' => PERMS_SPECIFIC,
- 'tag_deliver' => PERMS_SPECIFIC,
- 'chat' => PERMS_SPECIFIC,
- 'write_storage' => PERMS_SPECIFIC,
- 'write_pages' => PERMS_SPECIFIC,
- 'republish' => PERMS_SPECIFIC,
- 'delegate' => PERMS_SPECIFIC
- ];
-
- break;
-
- case 'forum_restricted':
- $ret['perms_auto'] = false;
- $ret['default_collection'] = true;
- $ret['directory_publish'] = true;
- $ret['online'] = false;
- $ret['perms_connect'] = [
- 'view_stream', 'view_profile', 'view_contacts', 'view_storage',
- 'view_pages', 'post_wall', 'post_comments', 'tag_deliver',
- 'post_mail', 'post_like' , 'chat' ];
- $ret['limits'] = [
- 'view_stream' => PERMS_PUBLIC,
- 'view_profile' => PERMS_PUBLIC,
- 'view_contacts' => PERMS_PUBLIC,
- 'view_storage' => PERMS_PUBLIC,
- 'view_pages' => PERMS_PUBLIC,
- 'send_stream' => PERMS_SPECIFIC,
- 'post_wall' => PERMS_SPECIFIC,
- 'post_comments' => PERMS_SPECIFIC,
- 'post_mail' => PERMS_SPECIFIC,
- 'post_like' => PERMS_SPECIFIC,
- 'tag_deliver' => PERMS_SPECIFIC,
- 'chat' => PERMS_SPECIFIC,
- 'write_storage' => PERMS_SPECIFIC,
- 'write_pages' => PERMS_SPECIFIC,
- 'republish' => PERMS_SPECIFIC,
- 'delegate' => PERMS_SPECIFIC
- ];
-
- break;
-
- case 'forum_private':
- $ret['perms_auto'] = false;
- $ret['default_collection'] = true;
- $ret['directory_publish'] = false;
- $ret['online'] = false;
-
- $ret['perms_connect'] = [
- 'view_stream', 'view_profile', 'view_contacts', 'view_storage',
- 'view_pages', 'post_wall', 'post_comments',
- 'post_mail', 'post_like' , 'chat' ];
- $ret['limits'] = [
- 'view_stream' => PERMS_PUBLIC,
- 'view_profile' => PERMS_SPECIFIC,
- 'view_contacts' => PERMS_SPECIFIC,
- 'view_storage' => PERMS_SPECIFIC,
- 'view_pages' => PERMS_SPECIFIC,
- 'send_stream' => PERMS_SPECIFIC,
- 'post_wall' => PERMS_SPECIFIC,
- 'post_comments' => PERMS_SPECIFIC,
- 'post_mail' => PERMS_SPECIFIC,
- 'post_like' => PERMS_SPECIFIC,
- 'tag_deliver' => PERMS_SPECIFIC,
- 'chat' => PERMS_SPECIFIC,
- 'write_storage' => PERMS_SPECIFIC,
- 'write_pages' => PERMS_SPECIFIC,
- 'republish' => PERMS_SPECIFIC,
- 'delegate' => PERMS_SPECIFIC
- ];
-
- break;
-
- case 'feed':
- $ret['perms_auto'] = true;
- $ret['default_collection'] = false;
- $ret['directory_publish'] = true;
- $ret['online'] = false;
-
- $ret['perms_connect'] = [
- 'view_stream', 'view_profile', 'view_contacts', 'view_storage',
- 'view_pages', 'send_stream', 'post_wall', 'post_comments',
- 'post_mail', 'post_like' , 'republish' ];
- $ret['limits'] = [
- 'view_stream' => PERMS_PUBLIC,
- 'view_profile' => PERMS_PUBLIC,
- 'view_contacts' => PERMS_PUBLIC,
- 'view_storage' => PERMS_PUBLIC,
- 'view_pages' => PERMS_PUBLIC,
- 'send_stream' => PERMS_SPECIFIC,
- 'post_wall' => PERMS_SPECIFIC,
- 'post_comments' => PERMS_SPECIFIC,
- 'post_mail' => PERMS_SPECIFIC,
- 'post_like' => PERMS_SPECIFIC,
- 'tag_deliver' => PERMS_SPECIFIC,
- 'chat' => PERMS_SPECIFIC,
- 'write_storage' => PERMS_SPECIFIC,
- 'write_pages' => PERMS_SPECIFIC,
- 'republish' => PERMS_SPECIFIC,
- 'delegate' => PERMS_SPECIFIC
- ];
-
- break;
-
- case 'feed_restricted':
- $ret['perms_auto'] = false;
- $ret['default_collection'] = true;
- $ret['directory_publish'] = false;
- $ret['online'] = false;
- $ret['perms_connect'] = [
- 'view_stream', 'view_profile', 'view_contacts', 'view_storage',
- 'view_pages', 'send_stream', 'post_wall', 'post_comments',
- 'post_mail', 'post_like' , 'republish' ];
- $ret['limits'] = [
- 'view_stream' => PERMS_PUBLIC,
- 'view_profile' => PERMS_PUBLIC,
- 'view_contacts' => PERMS_PUBLIC,
- 'view_storage' => PERMS_PUBLIC,
- 'view_pages' => PERMS_PUBLIC,
- 'send_stream' => PERMS_SPECIFIC,
- 'post_wall' => PERMS_SPECIFIC,
- 'post_comments' => PERMS_SPECIFIC,
- 'post_mail' => PERMS_SPECIFIC,
- 'post_like' => PERMS_SPECIFIC,
- 'tag_deliver' => PERMS_SPECIFIC,
- 'chat' => PERMS_SPECIFIC,
- 'write_storage' => PERMS_SPECIFIC,
- 'write_pages' => PERMS_SPECIFIC,
- 'republish' => PERMS_SPECIFIC,
- 'delegate' => PERMS_SPECIFIC
- ];
-
- break;
-
- case 'soapbox':
- $ret['perms_auto'] = true;
- $ret['default_collection'] = false;
- $ret['directory_publish'] = true;
- $ret['online'] = false;
-
- $ret['perms_connect'] = [
- 'view_stream', 'view_profile', 'view_contacts', 'view_storage',
- 'view_pages', 'post_like' , 'republish' ];
-
- $ret['limits'] = [
- 'view_stream' => PERMS_PUBLIC,
- 'view_profile' => PERMS_PUBLIC,
- 'view_contacts' => PERMS_PUBLIC,
- 'view_storage' => PERMS_PUBLIC,
- 'view_pages' => PERMS_PUBLIC,
- 'send_stream' => PERMS_SPECIFIC,
- 'post_wall' => PERMS_SPECIFIC,
- 'post_comments' => PERMS_SPECIFIC,
- 'post_mail' => PERMS_SPECIFIC,
- 'post_like' => PERMS_SPECIFIC,
- 'tag_deliver' => PERMS_SPECIFIC,
- 'chat' => PERMS_SPECIFIC,
- 'write_storage' => PERMS_SPECIFIC,
- 'write_pages' => PERMS_SPECIFIC,
- 'republish' => PERMS_SPECIFIC,
- 'delegate' => PERMS_SPECIFIC
- ];
-
- break;
-
- case 'repository':
- $ret['perms_auto'] = true;
- $ret['default_collection'] = false;
- $ret['directory_publish'] = true;
- $ret['online'] = false;
-
- $ret['perms_connect'] = [
- 'view_stream', 'view_profile', 'view_contacts', 'view_storage',
- 'view_pages', 'write_storage', 'write_pages', 'post_wall', 'post_comments', 'tag_deliver',
- 'post_mail', 'post_like' , 'republish', 'chat' ];
- $ret['limits'] = [
- 'view_stream' => PERMS_PUBLIC,
- 'view_profile' => PERMS_PUBLIC,
- 'view_contacts' => PERMS_PUBLIC,
- 'view_storage' => PERMS_PUBLIC,
- 'view_pages' => PERMS_PUBLIC,
- 'send_stream' => PERMS_SPECIFIC,
- 'post_wall' => PERMS_SPECIFIC,
- 'post_comments' => PERMS_SPECIFIC,
- 'post_mail' => PERMS_SPECIFIC,
- 'post_like' => PERMS_SPECIFIC,
- 'tag_deliver' => PERMS_SPECIFIC,
- 'chat' => PERMS_SPECIFIC,
- 'write_storage' => PERMS_SPECIFIC,
- 'write_pages' => PERMS_SPECIFIC,
- 'republish' => PERMS_SPECIFIC,
- 'delegate' => PERMS_SPECIFIC
- ];
-
-
- break;
-
- default:
- break;
- }
-
- $x = get_config('system','role_perms');
- // let system settings over-ride any or all
- if($x && is_array($x) && array_key_exists($role,$x))
- $ret = array_merge($ret,$x[$role]);
-
- call_hooks('get_role_perms',$ret);
-
- return $ret;
-}
-
-/**
- * @brief Returns a list or roles, grouped by type.
- *
- * @return string Returns an array of roles, grouped by type
- */
-function get_roles() {
- $roles = array(
- t('Social Networking') => array('social' => t('Social - Mostly Public'), 'social_restricted' => t('Social - Restricted'), 'social_private' => t('Social - Private')),
- t('Community Forum') => array('forum' => t('Forum - Mostly Public'), 'forum_restricted' => t('Forum - Restricted'), 'forum_private' => t('Forum - Private')),
- t('Feed Republish') => array('feed' => t('Feed - Mostly Public'), 'feed_restricted' => t('Feed - Restricted')),
- t('Special Purpose') => array('soapbox' => t('Special - Celebrity/Soapbox'), 'repository' => t('Special - Group Repository')),
- t('Other') => array('custom' => t('Custom/Expert Mode'))
- );
-
- return $roles;
-}
diff --git a/include/photo/photo_driver.php b/include/photo/photo_driver.php
index c8b3c3782..5eb1f9113 100644
--- a/include/photo/photo_driver.php
+++ b/include/photo/photo_driver.php
@@ -252,11 +252,10 @@ abstract class photo_driver {
*/
if(! $this->is_valid())
- return FALSE;
-
+ return false;
if((! function_exists('exif_read_data')) || ($this->getType() !== 'image/jpeg'))
- return;
+ return false;
$exif = @exif_read_data($filename,null,true);
@@ -330,6 +329,7 @@ abstract class photo_driver {
$p['photo_usage'] = intval($arr['photo_usage']);
$p['os_storage'] = intval($arr['os_storage']);
$p['os_path'] = $arr['os_path'];
+ $p['os_syspath'] = ((array_key_exists('os_syspath',$arr)) ? $arr['os_syspath'] : '');
$p['display_path'] = (($arr['display_path']) ? $arr['display_path'] : '');
if(! intval($p['imgscale']))
@@ -380,7 +380,7 @@ abstract class photo_driver {
dbesc($p['album']),
intval($this->getHeight()),
intval($this->getWidth()),
- (intval($p['os_storage']) ? dbescbin($p['os_path']) : dbescbin($this->imageString())),
+ (intval($p['os_storage']) ? dbescbin($p['os_syspath']) : dbescbin($this->imageString())),
intval($p['os_storage']),
intval(strlen($this->imageString())),
intval($p['imgscale']),
@@ -411,7 +411,7 @@ abstract class photo_driver {
dbesc($p['album']),
intval($this->getHeight()),
intval($this->getWidth()),
- (intval($p['os_storage']) ? dbescbin($p['os_path']) : dbescbin($this->imageString())),
+ (intval($p['os_storage']) ? dbescbin($p['os_syspath']) : dbescbin($this->imageString())),
intval($p['os_storage']),
intval(strlen($this->imageString())),
intval($p['imgscale']),
@@ -429,90 +429,6 @@ abstract class photo_driver {
return $r;
}
-
- // should be obsolete now
-
- public function store($aid, $uid, $xchan, $rid, $filename, $album, $scale, $usage = PHOTO_NORMAL, $allow_cid = '', $allow_gid = '', $deny_cid = '', $deny_gid = '') {
-
- $x = q("select id from photo where resource_id = '%s' and uid = %d and xchan = '%s' and imgscale = %d limit 1",
- dbesc($rid),
- intval($uid),
- dbesc($xchan),
- intval($scale)
- );
- if(count($x)) {
- $r = q("UPDATE photo
- set aid = %d,
- uid = %d,
- xchan = '%s',
- resource_id = '%s',
- created = '%s',
- edited = '%s',
- filename = '%s',
- mimetype = '%s',
- album = '%s',
- height = %d,
- width = %d,
- content = '%s',
- filesize = %d,
- imgscale = %d,
- photo_usage = %d,
- allow_cid = '%s',
- allow_gid = '%s',
- deny_cid = '%s',
- deny_gid = '%s'
- where id = %d",
-
- intval($aid),
- intval($uid),
- dbesc($xchan),
- dbesc($rid),
- dbesc(datetime_convert()),
- dbesc(datetime_convert()),
- dbesc(basename($filename)),
- dbesc($this->getType()),
- dbesc($album),
- intval($this->getHeight()),
- intval($this->getWidth()),
- dbescbin($this->imageString()),
- intval(strlen($this->imageString())),
- intval($scale),
- intval($photo_usage),
- dbesc($allow_cid),
- dbesc($allow_gid),
- dbesc($deny_cid),
- dbesc($deny_gid),
- intval($x[0]['id'])
- );
- }
- else {
- $r = q("INSERT INTO photo
- ( aid, uid, xchan, resource_id, created, edited, filename, mimetype, album, height, width, content, filesize, imgscale, photo_usage, allow_cid, allow_gid, deny_cid, deny_gid )
- VALUES ( %d, %d, '%s', '%s', '%s', '%s', '%s', '%s', '%s', %d, %d, '%s', %d, %d, %d, '%s', '%s', '%s', '%s' )",
- intval($aid),
- intval($uid),
- dbesc($xchan),
- dbesc($rid),
- dbesc(datetime_convert()),
- dbesc(datetime_convert()),
- dbesc(basename($filename)),
- dbesc($this->getType()),
- dbesc($album),
- intval($this->getHeight()),
- intval($this->getWidth()),
- dbescbin($this->imageString()),
- intval(strlen($this->imageString())),
- intval($scale),
- intval($photo_usage),
- dbesc($allow_cid),
- dbesc($allow_gid),
- dbesc($deny_cid),
- dbesc($deny_gid)
- );
- }
- return $r;
- }
-
}
@@ -530,7 +446,7 @@ abstract class photo_driver {
*/
function guess_image_type($filename, $headers = '') {
- logger('Photo: guess_image_type: '.$filename . ($headers?' from curl headers':''), LOGGER_DEBUG);
+// logger('Photo: guess_image_type: '.$filename . ($headers?' from curl headers':''), LOGGER_DEBUG);
$type = null;
if ($headers) {
@@ -572,24 +488,57 @@ function guess_image_type($filename, $headers = '') {
$ext = pathinfo($filename, PATHINFO_EXTENSION);
$ph = photo_factory('');
$types = $ph->supportedTypes();
- foreach ($types as $m=>$e){
- if ($ext==$e) $type = $m;
+ foreach($types as $m => $e) {
+ if($ext === $e) {
+ $type = $m;
+ }
}
}
- if(is_null($type)) {
+ if(is_null($type) && (strpos($filename,'http') === false)) {
$size = getimagesize($filename);
$ph = photo_factory('');
$types = $ph->supportedTypes();
$type = ((array_key_exists($size['mime'], $types)) ? $size['mime'] : 'image/jpeg');
}
+ if(is_null($type)) {
+ if(strpos(strtolower($filename),'jpg') !== false)
+ $type = 'image/jpeg';
+ elseif(strpos(strtolower($filename),'jpeg') !== false)
+ $type = 'image/jpeg';
+ elseif(strpos(strtolower($filename),'gif') !== false)
+ $type = 'image/gif';
+ elseif(strpos(strtolower($filename),'png') !== false)
+ $type = 'image/png';
+ }
}
- logger('Photo: guess_image_type: type='.$type, LOGGER_DEBUG);
+ logger('Photo: guess_image_type: filename = ' . $filename . ' type = ' . $type, LOGGER_DEBUG);
return $type;
}
+
+function delete_thing_photo($url,$ob_hash) {
+
+ $hash = basename($url);
+ $hash = substr($hash,0,strpos($hash,'-'));
+
+ // hashes should be 32 bytes.
+
+ if((! $ob_hash) || (strlen($hash) < 16))
+ return;
+
+ $r = q("delete from photo where xchan = '%s' and photo_usage = %d and resource_id = '%s'",
+ dbesc($ob_hash),
+ intval(PHOTO_THING),
+ dbesc($hash)
+ );
+
+}
+
+
+
function import_xchan_photo($photo,$xchan,$thing = false) {
$flags = (($thing) ? PHOTO_THING : PHOTO_XCHAN);
@@ -709,6 +658,37 @@ function import_xchan_photo($photo,$xchan,$thing = false) {
}
+function import_channel_photo_from_url($photo,$aid,$uid) {
+
+ if($photo) {
+ $filename = basename($photo);
+
+ $result = z_fetch_url($photo,true);
+
+ if($result['success']) {
+ $img_str = $result['body'];
+ $type = guess_image_type($photo, $result['header']);
+
+ $h = explode("\n",$result['header']);
+ if($h) {
+ foreach($h as $hl) {
+ if(stristr($hl,'content-type:')) {
+ if(! stristr($hl,'image/')) {
+ $photo_failure = true;
+ }
+ }
+ }
+ }
+ }
+ }
+ else {
+ $photo_failure = true;
+ }
+
+ import_channel_photo($img_str,$type,$aid,$uid);
+
+ return $type;
+}
function import_channel_photo($photo,$type,$aid,$uid) {
diff --git a/include/photos.php b/include/photos.php
index c0f7dc8c4..5de68f162 100644
--- a/include/photos.php
+++ b/include/photos.php
@@ -17,6 +17,7 @@ require_once('include/text.php');
* @param array $args
* @return array
*/
+
function photo_upload($channel, $observer, $args) {
$ret = array('success' => false);
@@ -28,9 +29,6 @@ function photo_upload($channel, $observer, $args) {
return $ret;
}
-
-//call_hooks('photo_upload_begin', $args);
-
/*
* Determine the album to use
*/
@@ -67,8 +65,20 @@ function photo_upload($channel, $observer, $args) {
$os_storage = 0;
- if($args['os_path'] && $args['getimagesize']) {
- $imagedata = @file_get_contents($args['os_path']);
+ if($args['os_syspath'] && $args['getimagesize']) {
+ if($args['getimagesize'][0] > 1600 || $args['getimagesize'][1] > 1600) {
+ $imagick_path = get_config('system','imagick_convert_path');
+ if($imagick_path && @file_exists($imagick_path)) {
+ $tmp_name = $args['os_syspath'] . '-001';
+ $newsize = photo_calculate_1600_scale($args['getimagesize']);
+ exec($imagick_path . ' ' . $args['os_syspath'] . ' -resize ' . $newsize . '^ ' . $tmp_name);
+ $imagedata = @file_get_contents($tmp_name);
+ @unlink($tmp_name);
+ }
+ }
+ else {
+ $imagedata = @file_get_contents($args['os_syspath']);
+ }
$filename = $args['filename'];
$filesize = strlen($imagedata);
// this is going to be deleted if it exists
@@ -90,8 +100,6 @@ function photo_upload($channel, $observer, $args) {
} else {
$f = array('src' => '', 'filename' => '', 'filesize' => 0, 'type' => '');
-// call_hooks('photo_upload_file',$f);
-
if (x($f,'src') && x($f,'filesize')) {
$src = $f['src'];
$filename = $f['filename'];
@@ -126,7 +134,6 @@ function photo_upload($channel, $observer, $args) {
}
logger('photo_upload: loading the contents of ' . $src , LOGGER_DEBUG);
-
$imagedata = @file_get_contents($src);
}
@@ -153,7 +160,7 @@ function photo_upload($channel, $observer, $args) {
return $ret;
}
- $exif = $ph->orient(($args['os_path']) ? $args['os_path'] : $src);
+ $exif = $ph->orient(($args['os_syspath']) ? $args['os_syspath'] : $src);
@unlink($src);
@@ -180,7 +187,8 @@ function photo_upload($channel, $observer, $args) {
'filename' => $filename, 'album' => $album, 'imgscale' => 0, 'photo_usage' => PHOTO_NORMAL,
'allow_cid' => $ac['allow_cid'], 'allow_gid' => $ac['allow_gid'],
'deny_cid' => $ac['deny_cid'], 'deny_gid' => $ac['deny_gid'],
- 'os_storage' => $os_storage, 'os_path' => $args['os_path']
+ 'os_storage' => $os_storage, 'os_syspath' => $args['os_syspath'],
+ 'os_path' => $args['os_path'], 'display_path' => $args['display_path']
);
if($args['created'])
$p['created'] = $args['created'];
@@ -205,7 +213,7 @@ function photo_upload($channel, $observer, $args) {
$errors = true;
unset($p['os_storage']);
- unset($p['os_path']);
+ unset($p['os_syspath']);
if(($width > 1024 || $height > 1024) && (! $errors))
$ph->scaleImage(1024);
@@ -299,7 +307,7 @@ function photo_upload($channel, $observer, $args) {
$photo_link = '[zrl=' . z_root() . '/photos/' . $channel['channel_address'] . '/image/' . $photo_hash . ']' . t('a new photo') . '[/zrl]';
- $album_link = '[zrl=' . z_root() . '/photos/' . $channel['channel_address'] . '/album/' . bin2hex($album) . ']' . ((strlen($album)) ? $album : '/') . '[/zrl]';
+ $album_link = '[zrl=' . z_root() . '/photos/' . $channel['channel_address'] . '/album/' . $args['directory']['hash'] . ']' . ((strlen($album)) ? $album : '/') . '[/zrl]';
$activity_format = sprintf(t('%1$s posted %2$s to %3$s','photo_upload'), $author_link, $photo_link, $album_link);
@@ -336,19 +344,13 @@ function photo_upload($channel, $observer, $args) {
if($item['mid'] === $item['parent_mid']) {
$item['body'] = $summary;
+ $item['mimetype'] = 'text/bbcode';
$item['obj_type'] = ACTIVITY_OBJ_PHOTO;
$item['obj'] = json_encode($object);
$item['tgt_type'] = ACTIVITY_OBJ_ALBUM;
$item['target'] = json_encode($target);
- if($item['author_xchan'] === $channel['channel_hash']) {
- $item['sig'] = base64url_encode(rsa_sign($item['body'],$channel['channel_prvkey']));
- $item['item_verified'] = 1;
- }
- else {
- $item['sig'] = '';
- }
$force = true;
}
@@ -374,37 +376,37 @@ function photo_upload($channel, $observer, $args) {
else {
$mid = item_message_id();
- $arr = array();
+ $arr = [
+ 'aid' => $account_id,
+ 'uid' => $channel_id,
+ 'mid' => $mid,
+ 'parent_mid' => $mid,
+ 'item_hidden' => $item_hidden,
+ 'resource_type' => 'photo',
+ 'resource_id' => $photo_hash,
+ 'owner_xchan' => $channel['channel_hash'],
+ 'author_xchan' => $observer['xchan_hash'],
+ 'title' => $title,
+ 'allow_cid' => $ac['allow_cid'],
+ 'allow_gid' => $ac['allow_gid'],
+ 'deny_cid' => $ac['deny_cid'],
+ 'deny_gid' => $ac['deny_gid'],
+ 'verb' => ACTIVITY_POST,
+ 'obj_type' => ACTIVITY_OBJ_PHOTO,
+ 'obj' => json_encode($object),
+ 'tgt_type' => ACTIVITY_OBJ_ALBUM,
+ 'target' => json_encode($target),
+ 'item_wall' => $visible,
+ 'item_origin' => 1,
+ 'item_thread_top' => 1,
+ 'item_private' => intval($acl->is_private()),
+ 'body' => $summary
+ ];
- if($lat && $lon)
- $arr['coord'] = $lat . ' ' . $lon;
-
- $arr['aid'] = $account_id;
- $arr['uid'] = $channel_id;
- $arr['mid'] = $mid;
- $arr['parent_mid'] = $mid;
- $arr['item_hidden'] = $item_hidden;
- $arr['resource_type'] = 'photo';
- $arr['resource_id'] = $photo_hash;
- $arr['owner_xchan'] = $channel['channel_hash'];
- $arr['author_xchan'] = $observer['xchan_hash'];
- $arr['title'] = $title;
- $arr['allow_cid'] = $ac['allow_cid'];
- $arr['allow_gid'] = $ac['allow_gid'];
- $arr['deny_cid'] = $ac['deny_cid'];
- $arr['deny_gid'] = $ac['deny_gid'];
- $arr['verb'] = ACTIVITY_POST;
- $arr['obj_type'] = ACTIVITY_OBJ_PHOTO;
- $arr['obj'] = json_encode($object);
- $arr['tgt_type'] = ACTIVITY_OBJ_ALBUM;
- $arr['target'] = json_encode($target);
- $arr['item_wall'] = 1;
- $arr['item_origin'] = 1;
- $arr['item_thread_top'] = 1;
- $arr['item_private'] = intval($acl->is_private());
$arr['plink'] = z_root() . '/channel/' . $channel['channel_address'] . '/?f=&mid=' . urlencode($arr['mid']);
- $arr['body'] = $summary;
+ if($lat && $lon)
+ $arr['coord'] = $lat . ' ' . $lon;
// this one is tricky because the item and the photo have the same permissions, those of the photo.
// Use the channel read_stream permissions to get the correct public_policy for the item and recalculate the
@@ -437,6 +439,70 @@ function photo_upload($channel, $observer, $args) {
return $ret;
}
+
+function photo_calculate_1600_scale($arr) {
+
+ $max = 1600;
+ $width = $arr[0];
+ $height = $arr[1];
+
+ $dest_width = $dest_height = 0;
+
+ if((! $width)|| (! $height))
+ return FALSE;
+
+ if($width > $max && $height > $max) {
+
+ // very tall image (greater than 16:9)
+ // constrain the width - let the height float.
+
+ if((($height * 9) / 16) > $width) {
+ $dest_width = $max;
+ $dest_height = intval(( $height * $max ) / $width);
+ }
+
+ // else constrain both dimensions
+
+ elseif($width > $height) {
+ $dest_width = $max;
+ $dest_height = intval(( $height * $max ) / $width);
+ }
+ else {
+ $dest_width = intval(( $width * $max ) / $height);
+ $dest_height = $max;
+ }
+ }
+ else {
+ if( $width > $max ) {
+ $dest_width = $max;
+ $dest_height = intval(( $height * $max ) / $width);
+ }
+ else {
+ if( $height > $max ) {
+ // very tall image (greater than 16:9)
+ // but width is OK - don't do anything
+
+ if((($height * 9) / 16) > $width) {
+ $dest_width = $width;
+ $dest_height = $height;
+ }
+ else {
+ $dest_width = intval(( $width * $max ) / $height);
+ $dest_height = $max;
+ }
+ }
+ else {
+ $dest_width = $width;
+ $dest_height = $height;
+ }
+ }
+ }
+
+ return $dest_width . 'x' . $dest_height;
+
+}
+
+
/**
* @brief Returns a list with all photo albums observer is allowed to see.
*
@@ -451,7 +517,8 @@ function photo_upload($channel, $observer, $args) {
* * \e boolean \b success
* * \e array \b albums
*/
-function photos_albums_list($channel, $observer, $sort_key = 'album', $direction = 'asc') {
+
+function photos_albums_list($channel, $observer, $sort_key = 'display_path', $direction = 'asc') {
$channel_id = $channel['channel_id'];
$observer_xchan = (($observer) ? $observer['xchan_hash'] : '');
@@ -464,17 +531,34 @@ function photos_albums_list($channel, $observer, $sort_key = 'album', $direction
$sort_key = dbesc($sort_key);
$direction = dbesc($direction);
- //$albums = q("SELECT count( distinct resource_id ) as total, album from photo where uid = %d and photo_usage IN ( %d, %d ) $sql_extra group by album order by $sort_key $direction",
- // intval($channel_id),
- // intval(PHOTO_NORMAL),
- // intval(PHOTO_PROFILE)
- //);
-
- // this query provides the same results but might perform better
- $albums = q("SELECT count( distinct resource_id ) as total, album from photo where uid = %d and os_storage = 1 $sql_extra group by album order by $sort_key $direction",
+ $r = q("select display_path, hash from attach where is_dir = 1 and uid = %d $sql_extra order by $sort_key $direction",
intval($channel_id)
);
+ array_unshift($r,[ 'display_path' => '/', 'hash' => '' ]);
+ $str = ids_to_querystr($r,'hash',true);
+
+ $albums = [];
+
+ if($str) {
+ $x = q("select count( distinct hash ) as total, folder from attach where is_photo = 1 and uid = %d and folder in ( $str ) $sql_extra group by folder ",
+ intval($channel_id)
+ );
+ if($x) {
+ require_once('include/attach.php');
+ foreach($r as $rv) {
+ foreach($x as $xv) {
+ if($xv['folder'] === $rv['hash']) {
+ if($xv['total'] != 0 && attach_can_view_folder($channel_id,$observer_xchan,$xv['folder'])) {
+ $albums[] = [ 'album' => $rv['display_path'], 'folder' => $xv['folder'], 'total' => $xv['total'] ];
+ }
+ continue;
+ }
+ }
+ }
+ }
+ }
+
// add various encodings to the array so we can just loop through and pick them out in a template
$ret = array('success' => false);
@@ -483,14 +567,15 @@ function photos_albums_list($channel, $observer, $sort_key = 'album', $direction
$ret['success'] = true;
$ret['albums'] = array();
foreach($albums as $k => $album) {
- $entry = array(
- 'text' => (($album['album']) ? $album['album'] : '/'),
- 'jstext' => (($album['album']) ? addslashes($album['album']) : '/'),
- 'total' => $album['total'],
- 'url' => z_root() . '/photos/' . $channel['channel_address'] . '/album/' . bin2hex($album['album']),
+ $entry = [
+ 'text' => (($album['album']) ? $album['album'] : '/'),
+ 'shorttext' => (($album['album']) ? ellipsify($album['album'],28) : '/'),
+ 'jstext' => (($album['album']) ? addslashes($album['album']) : '/'),
+ 'total' => $album['total'],
+ 'url' => z_root() . '/photos/' . $channel['channel_address'] . '/album/' . $album['folder'],
'urlencode' => urlencode($album['album']),
- 'bin2hex' => bin2hex($album['album'])
- );
+ 'bin2hex' => $album['folder']
+ ];
$ret['albums'][] = $entry;
}
}
@@ -500,7 +585,7 @@ function photos_albums_list($channel, $observer, $sort_key = 'album', $direction
return $ret;
}
-function photos_album_widget($channelx,$observer,$sortkey = 'album',$direction = 'asc') {
+function photos_album_widget($channelx,$observer,$sortkey = 'display_path',$direction = 'asc') {
$o = '';
@@ -513,6 +598,7 @@ function photos_album_widget($channelx,$observer,$sortkey = 'album',$direction =
$o = replace_macros(get_markup_template('photo_albums.tpl'),array(
'$nick' => $channelx['channel_address'],
'$title' => t('Photo Albums'),
+ '$recent' => t('Recent Photos'),
'$albums' => $albums['albums'],
'$baseurl' => z_root(),
'$upload' => ((perm_is_allowed($channelx['channel_id'],(($observer) ? $observer['xchan_hash'] : ''),'write_storage'))
@@ -531,6 +617,7 @@ function photos_album_widget($channelx,$observer,$sortkey = 'album',$direction =
* @param string $album default empty
* @return boolean|array
*/
+
function photos_list_photos($channel, $observer, $album = '') {
$channel_id = $channel['channel_id'];
@@ -570,13 +657,27 @@ function photos_list_photos($channel, $observer, $album = '') {
* @param string $album name of the album
* @return boolean
*/
-function photos_album_exists($channel_id, $album) {
- $r = q("SELECT id FROM photo WHERE album = '%s' AND uid = %d limit 1",
+
+
+function photos_album_exists($channel_id, $observer_hash, $album) {
+
+ $sql_extra = permissions_sql($channel_id,$observer_hash);
+
+ $r = q("SELECT folder, hash, is_dir, filename, os_path, display_path FROM attach WHERE hash = '%s' AND is_dir = 1 AND uid = %d $sql_extra limit 1",
dbesc($album),
intval($channel_id)
);
- return (($r) ? true : false);
+ // partial backward compatibility with Hubzilla < 2.4 when we used the filename only
+ // (ambiguous which would get chosen if you had two albums of the same name in different directories)
+ if(!$r && ctype_xdigit($album)) {
+ $r = q("SELECT folder, hash, is_dir, filename, os_path, display_path FROM attach WHERE filename = '%s' AND is_dir = 1 AND uid = %d $sql_extra limit 1",
+ dbesc(hex2bin($album)),
+ intval($channel_id)
+ );
+ }
+
+ return (($r) ? $r[0] : false);
}
/**
@@ -589,6 +690,7 @@ function photos_album_exists($channel_id, $album) {
* @param string $newname The new name of the album
* @return bool|array
*/
+
function photos_album_rename($channel_id, $oldname, $newname) {
return q("UPDATE photo SET album = '%s' WHERE album = '%s' AND uid = %d",
dbesc($newname),
@@ -607,16 +709,18 @@ function photos_album_rename($channel_id, $oldname, $newname) {
* @param string $remote_xchan
* @return string|boolean
*/
+
function photos_album_get_db_idstr($channel_id, $album, $remote_xchan = '') {
- if ($remote_xchan) {
- $r = q("SELECT distinct resource_id from photo where xchan = '%s' and uid = %d and album = '%s' ",
+ if($remote_xchan) {
+ $r = q("SELECT hash from attach where creator = '%s' and uid = %d and folder = '%s' ",
dbesc($remote_xchan),
intval($channel_id),
dbesc($album)
);
- } else {
- $r = q("SELECT distinct resource_id from photo where uid = %d and album = '%s' ",
+ }
+ else {
+ $r = q("SELECT hash from attach where uid = %d and folder = '%s' ",
intval($channel_id),
dbesc($album)
);
@@ -624,7 +728,7 @@ function photos_album_get_db_idstr($channel_id, $album, $remote_xchan = '') {
if ($r) {
$arr = array();
foreach ($r as $rr) {
- $arr[] = "'" . dbesc($rr['resource_id']) . "'" ;
+ $arr[] = "'" . dbesc($rr['hash']) . "'" ;
}
$str = implode(',',$arr);
return $str;
@@ -642,6 +746,7 @@ function photos_album_get_db_idstr($channel_id, $album, $remote_xchan = '') {
* @param boolean $visible default false
* @return int item_id
*/
+
function photos_create_item($channel, $creator_hash, $photo, $visible = false) {
// Create item container
@@ -697,7 +802,7 @@ function getGps($exifCoord, $hemi) {
function getGpstimestamp($exifCoord) {
- $hours = count($exifCoord) > 0 ? gps2Num($exifCoord[0]) : 0;
+ $hours = count($exifCoord) > 0 ? gps2Num($exifCoord[0]) : 0;
$minutes = count($exifCoord) > 1 ? gps2Num($exifCoord[1]) : 0;
$seconds = count($exifCoord) > 2 ? gps2Num($exifCoord[2]) : 0;
diff --git a/include/plugin.php b/include/plugin.php
index 3a64f67cc..db20152ea 100755
--- a/include/plugin.php
+++ b/include/plugin.php
@@ -356,6 +356,7 @@ function get_plugin_info($plugin){
return $info;
$f = file_get_contents("addon/$plugin/$plugin.php");
+ $f = escape_tags($f);
$r = preg_match("|/\*.*\*/|msU", $f, $m);
if ($r){
@@ -471,6 +472,8 @@ function get_theme_info($theme){
'description' => '',
'author' => array(),
'version' => '',
+ 'minversion' => '',
+ 'maxversion' => '',
'compat' => '',
'credits' => '',
'maintainer' => array(),
@@ -598,16 +601,23 @@ function head_get_links() {
function format_css_if_exists($source) {
- $path_prefix = script_path() . '/';
- if (strpos($source[0], '/') !== false) {
- // The source is a URL
- $path = $source[0];
+ // script_path() returns https://yoursite.tld
+
+ $path_prefix = script_path();
+
+ $script = $source[0];
+
+ if(strpos($script, '/') !== false) {
+ // The script is a path relative to the server root
+ $path = $script;
// If the url starts with // then it's an absolute URL
- if($source[0][0] === '/' && $source[0][1] === '/') $path_prefix = '';
+ if(substr($script,0,2) === '//') {
+ $path_prefix = '';
+ }
} else {
// It's a file from the theme
- $path = theme_include($source[0]);
+ $path = '/' . theme_include($script);
}
if($path) {
@@ -677,7 +687,7 @@ function head_get_js() {
foreach(App::$js_sources as $sources) {
if(count($sources)) {
foreach($sources as $source) {
- if($src === 'main.js')
+ if($source === 'main.js')
continue;
$str .= format_js_if_exists($source);
}
@@ -697,16 +707,19 @@ function head_get_main_js() {
}
function format_js_if_exists($source) {
- $path_prefix = script_path() . '/';
+ $path_prefix = script_path();
if(strpos($source,'/') !== false) {
- // The source is a URL
+ // The source is a known path on the system
$path = $source;
// If the url starts with // then it's an absolute URL
- if($source[0] === '/' && $source[1] === '/') $path_prefix = '';
- } else {
+ if(substr($source,0,2) === '//') {
+ $path_prefix = '';
+ }
+ }
+ else {
// It's a file from the theme
- $path = theme_include($source);
+ $path = '/' . theme_include($source);
}
if($path) {
$qstring = ((parse_url($path, PHP_URL_QUERY)) ? '&' : '?') . 'v=' . STD_VERSION;
diff --git a/include/probe.php b/include/probe.php
deleted file mode 100644
index 29635f963..000000000
--- a/include/probe.php
+++ /dev/null
@@ -1,99 +0,0 @@
-<?php /** @file */
-
-
-/**
- * Functions to assist in probing various legacy networks to figure out what kind of capabilities might be present.
- */
-
-
-function net_have_driver($net) {
-
- if(function_exists('net_discover_' . $net))
- return true;
- return false;
-}
-
-function probe_well_known($addr) {
-
- $ret = array();
-
- $ret['src'] = $addr;
-
- if(strpos($addr,'@') !== false) {
- $ret['address'] = $addr;
- }
- else {
- $ret['url'] = $addr;
- }
-
- if(stristr($addr,'facebook.com')) {
- $ret['network'] = 'facebook';
- }
- if(stristr($addr,'google.com')) {
- $ret['network'] = 'google';
- }
- if(stristr($addr,'linkedin.com')) {
- $ret['network'] = 'linkedin';
- }
-
- call_hooks('probe_well_known', $ret);
-
- if(array_key_exists('network',$ret) && net_have_driver($ret['network'])) {
- $fn = 'net_discover_' . $ret['network'];
- $ret = $fn($ret);
- }
-
-
- return $ret;
-
-}
-
-
-
-
-function probe_webfinger($addr) {
-
-
-
-
-
-}
-
-
-function probe_legacy_webfinger($addr) {
-
-
-
-
-}
-
-function probe_zot($addr) {
-
-
-
-}
-
-function probe_dfrn($addr) {
-
-
-}
-
-
-function probe_diaspora($addr) {
-
-
-}
-
-
-function probe_legacy_feed($addr) {
-
-
-
-}
-
-
-function probe_activity_stream($addr) {
-
-
-}
-
diff --git a/include/queue_fn.php b/include/queue_fn.php
index ede6c8f11..c9179b953 100644
--- a/include/queue_fn.php
+++ b/include/queue_fn.php
@@ -146,10 +146,14 @@ function queue_deliver($outq, $immediate = false) {
// your site has existed. Since we don't know for sure what these sites are,
// call them unknown
- q("insert into site (site_url, site_update, site_dead, site_type, site_crypto) values ('%s','%s',0,%d,'') ",
- dbesc($base),
- dbesc(datetime_convert()),
- intval(($outq['outq_driver'] === 'post') ? SITE_TYPE_NOTZOT : SITE_TYPE_UNKNOWN)
+ site_store_lowlevel(
+ [
+ 'site_url' => $base,
+ 'site_update' => datetime_convert(),
+ 'site_dead' => 0,
+ 'site_type' => intval(($outq['outq_driver'] === 'post') ? SITE_TYPE_NOTZOT : SITE_TYPE_UNKNOWN),
+ 'site_crypto' => ''
+ ]
);
}
}
diff --git a/include/security.php b/include/security.php
index b49ceec0d..450cc4f69 100644
--- a/include/security.php
+++ b/include/security.php
@@ -114,9 +114,9 @@ function atoken_xchan($atoken) {
'atoken_id' => $atoken['atoken_id'],
'xchan_hash' => substr($c['channel_hash'],0,16) . '.' . $atoken['atoken_name'],
'xchan_name' => $atoken['atoken_name'],
- 'xchan_addr' => t('guest:') . $atoken['atoken_name'] . '@' . \App::get_hostname(),
+ 'xchan_addr' => 'guest:' . $atoken['atoken_name'] . '@' . \App::get_hostname(),
'xchan_network' => 'unknown',
- 'xchan_url' => z_root(),
+ 'xchan_url' => z_root() . '/guest/' . substr($c['channel_hash'],0,16) . '.' . $atoken['atoken_name'],
'xchan_hidden' => 1,
'xchan_photo_mimetype' => 'image/jpeg',
'xchan_photo_l' => get_default_profile_photo(300),
@@ -467,7 +467,6 @@ function scopes_sql($uid,$observer) {
*/
function public_permissions_sql($observer_hash) {
- //$observer = App::get_observer();
$groups = init_groups_visitor($observer_hash);
$gs = '<<>>'; // should be impossible to match
@@ -597,18 +596,24 @@ function stream_perms_api_uids($perms = NULL, $limit = 0, $rand = 0 ) {
$random_sql = (($rand) ? " ORDER BY " . db_getfunc('RAND') . " " : '');
if(local_channel())
$ret[] = local_channel();
- $x = q("select uid from pconfig where cat = 'perm_limits' and k = 'view_stream' and ( v & %d ) > 0 ",
- intval($perms)
- );
+ $x = q("select uid, v from pconfig where cat = 'perm_limits' and k = 'view_stream' ");
if($x) {
- $ids = ids_to_querystr($x,'uid');
- $r = q("select channel_id from channel where channel_id in ( $ids ) and ( channel_pageflags & %d ) = 0 and channel_system = 0 and channel_removed = 0 $random_sql $limit_sql ",
- intval(PAGE_ADULT|PAGE_CENSORED)
- );
- if($r) {
- foreach($r as $rr)
- if(! in_array($rr['channel_id'], $ret))
- $ret[] = $rr['channel_id'];
+ $y = [];
+ foreach($x as $xv) {
+ if(intval($xv['v']) & $perms) {
+ $y[] = $xv;
+ }
+ }
+ if($y) {
+ $ids = ids_to_querystr($y,'uid');
+ $r = q("select channel_id from channel where channel_id in ( $ids ) and ( channel_pageflags & %d ) = 0 and channel_system = 0 and channel_removed = 0 $random_sql $limit_sql ",
+ intval(PAGE_ADULT|PAGE_CENSORED)
+ );
+ if($r) {
+ foreach($r as $rr)
+ if(! in_array($rr['channel_id'], $ret))
+ $ret[] = $rr['channel_id'];
+ }
}
}
@@ -635,19 +640,26 @@ function stream_perms_xchans($perms = NULL ) {
if(local_channel())
$ret[] = get_observer_hash();
- $x = q("select uid from pconfig where cat = 'perm_limits' and k = 'view_stream' and ( v & %d ) > 0 ",
- intval($perms)
- );
+ $x = q("select uid, v from pconfig where cat = 'perm_limits' and k = 'view_stream' ");
if($x) {
- $ids = ids_to_querystr($x,'uid');
- $r = q("select channel_hash from channel where channel_id in ( $ids ) and ( channel_pageflags & %d ) = 0 and channel_system = 0 and channel_removed = 0 ",
- intval(PAGE_ADULT|PAGE_CENSORED)
- );
+ $y = [];
+ foreach($x as $xv) {
+ if(intval($xv['v']) & $perms) {
+ $y[] = $xv;
+ }
+ }
+ if($y) {
+ $ids = ids_to_querystr($y,'uid');
- if($r) {
- foreach($r as $rr)
- if(! in_array($rr['channel_hash'], $ret))
- $ret[] = $rr['channel_hash'];
+ $r = q("select channel_hash from channel where channel_id in ( $ids ) and ( channel_pageflags & %d ) = 0 and channel_system = 0 and channel_removed = 0 ",
+ intval(PAGE_ADULT|PAGE_CENSORED)
+ );
+
+ if($r) {
+ foreach($r as $rr)
+ if(! in_array($rr['channel_hash'], $ret))
+ $ret[] = $rr['channel_hash'];
+ }
}
}
$str = '';
diff --git a/include/socgraph.php b/include/socgraph.php
index 69365f80f..a5b5d1378 100644
--- a/include/socgraph.php
+++ b/include/socgraph.php
@@ -122,7 +122,7 @@ function poco_load($xchan = '', $url = null) {
$profile_url = $url['value'];
continue;
}
- if($url['type'] == 'zot' || $url['type'] == 'diaspora' || $url['type'] == 'friendica') {
+ if($url['type'] == 'zot') {
$network = $url['type'];
$address = str_replace('acct:' , '', $url['value']);
continue;
@@ -163,12 +163,6 @@ function poco_load($xchan = '', $url = null) {
continue;
}
}
- else {
- $x = import_author_diaspora(array('address' => $address));
- if(! $x) {
- continue;
- }
- }
}
else {
continue;
@@ -243,77 +237,6 @@ function common_friends($uid,$xchan,$start = 0,$limit=100000000,$shuffle = false
}
-function count_common_friends_zcid($uid,$zcid) {
-
- $r = q("SELECT count(*) as total
- FROM glink left join gcontact on glink.gcid = gcontact.id
- where glink.zcid = %d
- and gcontact.nurl in (select nurl from contact where uid = %d and self = 0 and blocked = 0 and hidden = 0 ) ",
- intval($zcid),
- intval($uid)
- );
-
- if(count($r))
- return $r[0]['total'];
-
- return 0;
-}
-
-function common_friends_zcid($uid,$zcid,$start = 0, $limit = 9999,$shuffle = false) {
-
- if($shuffle)
- $sql_extra = " order by rand() ";
- else
- $sql_extra = " order by gcontact.name asc ";
-
- $r = q("SELECT gcontact.*
- FROM glink left join gcontact on glink.gcid = gcontact.id
- where glink.zcid = %d
- and gcontact.nurl in (select nurl from contact where uid = %d and self = 0 and blocked = 0 and hidden = 0 )
- $sql_extra limit %d offset %d",
- intval($zcid),
- intval($uid),
- intval($limit),
- intval($start)
- );
-
- return $r;
-}
-
-
-function count_all_friends($uid,$cid) {
-
- $r = q("SELECT count(*) as total
- FROM glink left join gcontact on glink.gcid = gcontact.id
- where glink.cid = %d and glink.uid = %d ",
- intval($cid),
- intval($uid)
- );
-
- if(count($r))
- return $r[0]['total'];
-
- return 0;
-}
-
-
-function all_friends($uid,$cid,$start = 0, $limit = 80) {
-
- $r = q("SELECT gcontact.*
- FROM glink left join gcontact on glink.gcid = gcontact.id
- where glink.cid = %d and glink.uid = %d
- order by gcontact.name asc LIMIT %d OFFSET %d ",
- intval($cid),
- intval($uid),
- intval($limit),
- intval($start)
- );
-
- return $r;
-}
-
-
-
function suggestion_query($uid, $myxchan, $start = 0, $limit = 80) {
if((! $uid) || (! $myxchan))
@@ -564,8 +487,6 @@ function poco($a,$extended = false) {
if($fields_ret['urls']) {
$entry['urls'] = array(array('value' => $rr['xchan_url'], 'type' => 'profile'));
$network = $rr['xchan_network'];
- if(strpos($network,'friendica') !== false)
- $network = 'friendica';
if($rr['xchan_addr'])
$entry['urls'][] = array('value' => 'acct:' . $rr['xchan_addr'], 'type' => $network);
}
diff --git a/include/statistics_fns.php b/include/statistics_fns.php
index cbff3b0b7..d213485bf 100644
--- a/include/statistics_fns.php
+++ b/include/statistics_fns.php
@@ -7,7 +7,7 @@ function update_channels_total_stat() {
$channels_total_stat = intval($r[0]['channels_total']);
set_config('system','channels_total_stat',$channels_total_stat);
} else {
- set_config('system','channels_total_stat',null);
+ set_config('system','channels_total_stat',0);
}
}
@@ -30,10 +30,10 @@ function update_channels_active_halfyear_stat() {
$channels_active_halfyear_stat = count($x);
set_config('system','channels_active_halfyear_stat',$channels_active_halfyear_stat);
} else {
- set_config('system','channels_active_halfyear_stat',null);
+ set_config('system','channels_active_halfyear_stat',0);
}
} else {
- set_config('system','channels_active_halfyear_stat',null);
+ set_config('system','channels_active_halfyear_stat',0);
}
}
@@ -56,10 +56,10 @@ function update_channels_active_monthly_stat() {
$channels_active_monthly_stat = count($x);
set_config('system','channels_active_monthly_stat',$channels_active_monthly_stat);
} else {
- set_config('system','channels_active_monthly_stat',null);
+ set_config('system','channels_active_monthly_stat',0);
}
} else {
- set_config('system','channels_active_monthly_stat',null);
+ set_config('system','channels_active_monthly_stat',0);
}
}
@@ -69,8 +69,16 @@ function update_local_posts_stat() {
$local_posts_stat = intval($posts[0]["local_posts"]);
set_config('system','local_posts_stat',$local_posts_stat);
} else {
- set_config('system','local_posts_stat',null);
+ set_config('system','local_posts_stat',0);
}
}
+function update_local_comments_stat() {
+ $posts = q("SELECT COUNT(*) AS local_posts FROM item WHERE item_wall = 1 and id != parent");
+ if (!is_array($posts))
+ $local_posts = 0;
+ else
+ $local_posts = $posts[0]["local_posts"];
+ set_config('system','local_comments_stat', $local_posts);
+} \ No newline at end of file
diff --git a/include/taxonomy.php b/include/taxonomy.php
index 0b4b2aa9a..23acaa24d 100644
--- a/include/taxonomy.php
+++ b/include/taxonomy.php
@@ -44,6 +44,45 @@ function term_query($table,$s,$type = TERM_UNKNOWN, $type2 = '') {
}
+function term_item_parent_query($uid,$table,$s,$type = TERM_UNKNOWN, $type2 = '') {
+
+ // Allow asterisks for wildcard search
+ // In theory this means '%' will also do a wildcard search, but there appear to be multiple escape
+ // issues with '%' in term names and trying to fix this with '\\%' here did not help.
+ // Ideally I think we want '*' to indicate wildcards and allow '%' literally in names, but that is being
+ // left for another developer on another day.
+
+ $s = str_replace('*','%',$s);
+
+ if($type2) {
+ $r = q("select parent from item left join term on term.oid = item.id where term.ttype in (%d, %d) and term.term like '%s' and term.uid = %d and term.otype = 1",
+ intval($type),
+ intval($type2),
+ dbesc($s),
+ intval($uid)
+ );
+ }
+ else {
+ $r = q("select parent from item left join term on term.oid = item.id where term.ttype = %d and term.term like '%s' and term.uid = %d and term.otype = 1",
+ intval($type),
+ dbesc($s),
+ intval($uid)
+ );
+ }
+
+ if($r) {
+ $str = '';
+ foreach($r as $rv) {
+ if($str)
+ $str .= ',';
+ $str .= intval($rv['parent']);
+ }
+ return " AND " . (($table) ? dbesc($table) . '.' : '') . "id in ( $str ) ";
+ }
+ return " AND false ";
+}
+
+
function store_item_tag($uid,$iid,$otype,$type,$term,$url = '') {
if(! $term)
return false;
@@ -95,6 +134,8 @@ function format_term_for_display($term) {
$s = '';
if(($term['ttype'] == TERM_HASHTAG) || ($term['ttype'] == TERM_COMMUNITYTAG))
$s .= '#';
+ elseif($term['ttype'] == TERM_FORUM)
+ $s .= '!';
elseif($term['ttype'] == TERM_MENTION)
$s .= '@';
else
@@ -160,6 +201,62 @@ function tagadelic($uid, $count = 0, $authors = '', $owner = '', $flags = 0, $re
}
+
+
+function card_tagadelic($uid, $count = 0, $authors = '', $owner = '', $flags = 0, $restrict = 0, $type = TERM_CATEGORY) {
+
+ require_once('include/security.php');
+
+ if(! perm_is_allowed($uid,get_observer_hash(),'view_pages'))
+ return array();
+
+
+ $item_normal = item_normal();
+ $sql_options = item_permissions_sql($uid);
+ $count = intval($count);
+
+ if($flags) {
+ if($flags === 'wall')
+ $sql_options .= " and item_wall = 1 ";
+ }
+
+ if($authors) {
+ if(! is_array($authors))
+ $authors = array($authors);
+
+ stringify_array_elms($authors,true);
+ $sql_options .= " and author_xchan in (" . implode(',',$authors) . ") ";
+ }
+
+ if($owner) {
+ $sql_options .= " and owner_xchan = '" . dbesc($owner) . "' ";
+ }
+
+
+ // Fetch tags
+ $r = q("select term, count(term) as total from term left join item on term.oid = item.id
+ where term.uid = %d and term.ttype = %d
+ and otype = %d and item_type = %d and item_private = 0
+ $sql_options $item_normal
+ group by term order by total desc %s",
+ intval($uid),
+ intval($type),
+ intval(TERM_OBJ_POST),
+ intval($restrict),
+ ((intval($count)) ? "limit $count" : '')
+ );
+
+ if(! $r)
+ return array();
+
+ return Zotlabs\Text\Tagadelic::calc($r);
+
+}
+
+
+
+
+
function dir_tagadelic($count = 0) {
$count = intval($count);
@@ -277,6 +374,26 @@ function catblock($uid,$count = 0,$authors = '',$owner = '', $flags = 0,$restric
return $o;
}
+function card_catblock($uid,$count = 0,$authors = '',$owner = '', $flags = 0,$restrict = 0,$type = TERM_CATEGORY) {
+ $o = '';
+
+ $r = card_tagadelic($uid,$count,$authors,$owner,$flags,$restrict,$type);
+
+ if($r) {
+ $c = q("select channel_address from channel where channel_id = %d limit 1",
+ intval($uid)
+ );
+
+ $o = '<div class="tagblock widget"><h3>' . t('Categories') . '</h3><div class="tags" align="center">';
+ foreach($r as $rr) {
+ $o .= '<a href="cards/' . $c[0]['channel_address']. '?f=&cat=' . urlencode($rr[0]).'" class="tag'.$rr[2].'">'.$rr[0].'</a> ' . "\r\n";
+ }
+ $o .= '</div></div>';
+ }
+
+ return $o;
+}
+
function dir_tagblock($link,$r) {
$o = '';
diff --git a/include/text.php b/include/text.php
index 8c01ed1d2..d81b59d75 100644
--- a/include/text.php
+++ b/include/text.php
@@ -3,8 +3,10 @@
* @file include/text.php
*/
-require_once("include/bbcode.php");
+use \Zotlabs\Lib as Zlib;
+use \Michelf\MarkdownExtra;
+require_once("include/bbcode.php");
// random string, there are 86 characters max in text mode, 128 for hex
// output is urlsafe
@@ -88,12 +90,10 @@ function escape_tags($string) {
}
-function z_input_filter($channel_id,$s,$type = 'text/bbcode') {
+function z_input_filter($s,$type = 'text/bbcode',$allow_code = false) {
if($type === 'text/bbcode')
return escape_tags($s);
- if($type === 'text/markdown')
- return escape_tags($s);
if($type == 'text/plain')
return escape_tags($s);
if($type == 'application/x-pdl')
@@ -103,15 +103,15 @@ function z_input_filter($channel_id,$s,$type = 'text/bbcode') {
return $s;
}
- $r = q("select account_id, account_roles, channel_pageflags from account left join channel on channel_account_id = account_id where channel_id = %d limit 1",
- intval($channel_id)
- );
- if($r) {
- if(($r[0]['account_roles'] & ACCOUNT_ROLE_ALLOWCODE) || ($r[0]['channel_pageflags'] & PAGE_ALLOWCODE)) {
- if(local_channel() && (get_account_id() == $r[0]['account_id'])) {
- return $s;
- }
- }
+ if($allow_code) {
+ if($type === 'text/markdown')
+ return htmlspecialchars($s,ENT_QUOTES);
+ return $s;
+ }
+
+ if($type === 'text/markdown') {
+ $x = new Zlib\MarkdownSoap($s);
+ return $x->clean();
}
if($type === 'text/html')
@@ -121,13 +121,23 @@ function z_input_filter($channel_id,$s,$type = 'text/bbcode') {
}
-
+/**
+ * @brief Use HTMLPurifier to get standards compliant HTML.
+ *
+ * Use the <a href="http://htmlpurifier.org/" target="_blank">HTMLPurifier</a>
+ * library to get filtered and standards compliant HTML.
+ *
+ * @see HTMLPurifier
+ *
+ * @param string $s raw HTML
+ * @param boolean $allow_position allow CSS position
+ * @return string standards compliant filtered HTML
+ */
function purify_html($s, $allow_position = false) {
- require_once('library/HTMLPurifier.auto.php');
- require_once('include/html2bbcode.php');
/**
* @FIXME this function has html output, not bbcode - so safely purify these
+ * require_once('include/html2bbcode.php');
* $s = html2bb_video($s);
* $s = oembed_html2bbcode($s);
*/
@@ -136,6 +146,15 @@ function purify_html($s, $allow_position = false) {
$config->set('Cache.DefinitionImpl', null);
$config->set('Attr.EnableID', true);
+ // If enabled, target=blank attributes are added to all links.
+ //$config->set('HTML.TargetBlank', true);
+ //$config->set('Attr.AllowedFrameTargets', ['_blank', '_self', '_parent', '_top']);
+ // restore old behavior of HTMLPurifier < 4.8, only used when targets allowed at all
+ // do not add rel="noreferrer" to all links with target attributes
+ //$config->set('HTML.TargetNoreferrer', false);
+ // do not add noopener rel attributes to links which have a target attribute associated with them
+ //$config->set('HTML.TargetNoopener', false);
+
//Allow some custom data- attributes used by built-in libs.
//In this way members which do not have allowcode set can still use the built-in js libs in webpages to some extent.
@@ -273,7 +292,6 @@ function purify_html($s, $allow_position = false) {
new HTMLPurifier_AttrDef_CSS_Length(),
new HTMLPurifier_AttrDef_CSS_Percentage()
));
-
}
$purifier = new HTMLPurifier($config);
@@ -586,8 +604,10 @@ function photo_new_resource() {
* @return boolean true if found
*/
function attribute_contains($attr, $s) {
+ // remove quotes
+ $attr = str_replace([ '"',"'" ],['',''],$attr);
$a = explode(' ', $attr);
- if(count($a) && in_array($s, $a))
+ if($a && in_array($s, $a))
return true;
return false;
@@ -628,14 +648,10 @@ function logger($msg, $level = LOGGER_NORMAL, $priority = LOG_INFO) {
$where = '';
- // We require > 5.4 but leave the version check so that install issues (including version) can be logged
-
- if(version_compare(PHP_VERSION, '5.4.0') >= 0) {
- $stack = debug_backtrace(DEBUG_BACKTRACE_IGNORE_ARGS, 2);
- $where = basename($stack[0]['file']) . ':' . $stack[0]['line'] . ':' . $stack[1]['function'] . ': ';
- }
+ $stack = debug_backtrace(DEBUG_BACKTRACE_IGNORE_ARGS, 2);
+ $where = basename($stack[0]['file']) . ':' . $stack[0]['line'] . ':' . $stack[1]['function'] . ': ';
- $s = datetime_convert() . ':' . log_priority_str($priority) . ':' . session_id() . ':' . $where . $msg . PHP_EOL;
+ $s = datetime_convert('UTC','UTC', 'now', ATOM_TIME) . ':' . log_priority_str($priority) . ':' . session_id() . ':' . $where . $msg . PHP_EOL;
$pluginfo = array('filename' => $logfile, 'loglevel' => $level, 'message' => $s,'priority' => $priority, 'logged' => false);
if(! (App::$module == 'setup'))
@@ -663,20 +679,18 @@ function btlogger($msg, $level = LOGGER_NORMAL, $priority = LOG_INFO) {
if(file_exists(BTLOGGER_DEBUG_FILE) && is_writable(BTLOGGER_DEBUG_FILE)) {
$stack = debug_backtrace(DEBUG_BACKTRACE_IGNORE_ARGS, 2);
$where = basename($stack[0]['file']) . ':' . $stack[0]['line'] . ':' . $stack[1]['function'] . ': ';
- $s = datetime_convert() . ':' . log_priority_str($priority) . ':' . session_id() . ':' . $where . $msg . PHP_EOL;
+ $s = datetime_convert('UTC','UTC', 'now', ATOM_TIME) . ':' . log_priority_str($priority) . ':' . session_id() . ':' . $where . $msg . PHP_EOL;
@file_put_contents(BTLOGGER_DEBUG_FILE, $s, FILE_APPEND);
}
- if(version_compare(PHP_VERSION, '5.4.0') >= 0) {
- $stack = debug_backtrace(DEBUG_BACKTRACE_IGNORE_ARGS);
- if($stack) {
- for($x = 1; $x < count($stack); $x ++) {
- $s = 'stack: ' . basename($stack[$x]['file']) . ':' . $stack[$x]['line'] . ':' . $stack[$x]['function'] . '()';
- logger($s,$level, $priority);
+ $stack = debug_backtrace(DEBUG_BACKTRACE_IGNORE_ARGS);
+ if($stack) {
+ for($x = 1; $x < count($stack); $x ++) {
+ $s = 'stack: ' . basename($stack[$x]['file']) . ':' . $stack[$x]['line'] . ':' . $stack[$x]['function'] . '()';
+ logger($s,$level, $priority);
- if(file_exists(BTLOGGER_DEBUG_FILE) && is_writable(BTLOGGER_DEBUG_FILE)) {
- @file_put_contents(BTLOGGER_DEBUG_FILE, $s . PHP_EOL, FILE_APPEND);
- }
+ if(file_exists(BTLOGGER_DEBUG_FILE) && is_writable(BTLOGGER_DEBUG_FILE)) {
+ @file_put_contents(BTLOGGER_DEBUG_FILE, $s . PHP_EOL, FILE_APPEND);
}
}
}
@@ -731,12 +745,12 @@ function dlogger($msg, $level = 0) {
return;
$where = '';
- if(version_compare(PHP_VERSION, '5.4.0') >= 0) {
- $stack = debug_backtrace(DEBUG_BACKTRACE_IGNORE_ARGS, 2);
- $where = basename($stack[0]['file']) . ':' . $stack[0]['line'] . ':' . $stack[1]['function'] . ': ';
- }
- @file_put_contents($logfile, datetime_convert() . ':' . session_id() . ' ' . $where . $msg . PHP_EOL, FILE_APPEND);
+ $stack = debug_backtrace(DEBUG_BACKTRACE_IGNORE_ARGS, 2);
+ $where = basename($stack[0]['file']) . ':' . $stack[0]['line'] . ':' . $stack[1]['function'] . ': ';
+
+
+ @file_put_contents($logfile, datetime_convert('UTC','UTC', 'now', ATOM_TIME) . ':' . session_id() . ' ' . $where . $msg . PHP_EOL, FILE_APPEND);
}
@@ -747,16 +761,24 @@ function profiler($t1,$t2,$label) {
function activity_match($haystack,$needle) {
- if(($haystack === $needle) || ((basename($needle) === $haystack) && strstr($needle,NAMESPACE_ACTIVITY_SCHEMA)))
- return true;
+ if(! is_array($needle))
+ $needle = [ $needle ];
+
+ if($needle) {
+ foreach($needle as $n) {
+ if(($haystack === $n) || (strtolower(basename($n)) === strtolower(basename($haystack)))) {
+ return true;
+ }
+ }
+ }
return false;
}
/**
- * @brief Pull out all #hashtags and @person tags from $s.
+ * @brief Pull out all \#hashtags and \@person tags from $s.
*
- * We also get @person@domain.com - which would make
+ * We also get \@person\@domain.com - which would make
* the regex quite complicated as tags can also
* end a sentence. So we'll run through our results
* and strip the period from any tags which end with one.
@@ -780,7 +802,7 @@ function get_tags($s) {
// match any double quoted tags
- if(preg_match_all('/([@#]\&quot\;.*?\&quot\;)/',$s,$match)) {
+ if(preg_match_all('/([@#!]\&quot\;.*?\&quot\;)/',$s,$match)) {
foreach($match[1] as $mtch) {
$ret[] = $mtch;
}
@@ -809,7 +831,7 @@ function get_tags($s) {
// Otherwise pull out single word tags. These can be @nickname, @first_last
// and #hash tags.
- if(preg_match_all('/(?<![a-zA-Z0-9=\/\?\;])([@#][^ \x0D\x0A,;:?\[]+)/',$s,$match)) {
+ if(preg_match_all('/(?<![a-zA-Z0-9=\/\?\;])([@#\!][^ \x0D\x0A,;:?\[]+)/',$s,$match)) {
foreach($match[1] as $mtch) {
if(substr($mtch,-1,1) === '.')
$mtch = substr($mtch,0,-1);
@@ -851,6 +873,11 @@ function tag_sort_length($a,$b) {
return((mb_strlen($b) < mb_strlen($a)) ? (-1) : 1);
}
+function total_sort($a,$b) {
+ if($a['total'] == $b['total'])
+ return 0;
+ return(($b['total'] > $a['total']) ? 1 : (-1));
+}
/**
@@ -968,7 +995,7 @@ function chanlink_cid($d) {
function magiclink_url($observer,$myaddr,$url) {
return (($observer)
- ? z_root() . '/magic?f=&dest=' . $url . '&addr=' . $myaddr
+ ? z_root() . '/magic?f=&owa=1&dest=' . $url . '&addr=' . $myaddr
: $url
);
}
@@ -1017,19 +1044,6 @@ function searchbox($s,$id='search-box',$url='/search',$save = false) {
));
}
-function valid_email_regex($x){
- if(preg_match('/^[_a-zA-Z0-9\-\+]+(\.[_a-zA-Z0-9\-\+]+)*@[a-zA-Z0-9-]+(\.[a-zA-Z0-9-]+)+$/',$x))
- return true;
- return false;
-}
-
-function valid_email($x){
- if(get_config('system','disable_email_validation'))
- return true;
-
- return valid_email_regex($x);
-}
-
/**
* @brief Replace naked text hyperlink with HTML formatted hyperlink.
*
@@ -1141,12 +1155,11 @@ function get_mood_verbs() {
*
* @return Returns array with keys 'texts' and 'icons'
*/
-function list_smilies() {
+function list_smilies($default_only = false) {
$texts = array(
'&lt;3',
'&lt;/3',
- '&lt;\\3',
':-)',
';-)',
':-(',
@@ -1175,14 +1188,12 @@ function list_smilies() {
':coffee',
':facepalm',
':like',
- ':dislike',
- ':hubzilla'
+ ':dislike'
);
$icons = array(
'<img class="smiley" src="' . z_root() . '/images/emoticons/smiley-heart.gif" alt="&lt;3" />',
'<img class="smiley" src="' . z_root() . '/images/emoticons/smiley-brokenheart.gif" alt="&lt;/3" />',
- '<img class="smiley" src="' . z_root() . '/images/emoticons/smiley-brokenheart.gif" alt="&lt;\\3" />',
'<img class="smiley" src="' . z_root() . '/images/emoticons/smiley-smile.gif" alt=":-)" />',
'<img class="smiley" src="' . z_root() . '/images/emoticons/smiley-wink.gif" alt=";-)" />',
'<img class="smiley" src="' . z_root() . '/images/emoticons/smiley-frown.gif" alt=":-(" />',
@@ -1211,30 +1222,20 @@ function list_smilies() {
'<img class="smiley" src="' . z_root() . '/images/emoticons/coffee.gif" alt=":coffee" />',
'<img class="smiley" src="' . z_root() . '/images/emoticons/smiley-facepalm.gif" alt=":facepalm" />',
'<img class="smiley" src="' . z_root() . '/images/emoticons/like.gif" alt=":like" />',
- '<img class="smiley" src="' . z_root() . '/images/emoticons/dislike.gif" alt=":dislike" />',
- '<img class="smiley" src="' . z_root() . '/images/hz-16.png" alt=":hubzilla" />',
+ '<img class="smiley" src="' . z_root() . '/images/emoticons/dislike.gif" alt=":dislike" />'
);
- $x = get_config('feature','emoji');
- if($x === false)
- $x = 1;
- if($x) {
- if(! App::$emojitab)
- App::$emojitab = json_decode(file_get_contents('library/emoji.json'),true);
- foreach(App::$emojitab as $e) {
- if(strpos($e['shortname'],':tone') === 0)
- continue;
- $texts[] = $e['shortname'];
- $icons[] = '<img class="smiley emoji" height="16" width="16" src="images/emoji/' . $e['unicode'] . '.png' . '" alt="' . $e['name'] . '" />';
- }
- }
-
$params = array('texts' => $texts, 'icons' => $icons);
+
+ if($default_only)
+ return $params;
+
call_hooks('smilie', $params);
return $params;
}
+
/**
* @brief Replaces text emoticons with graphical images.
*
@@ -1363,20 +1364,7 @@ function link_compare($a, $b) {
function unobscure(&$item) {
- if(array_key_exists('item_obscured',$item) && intval($item['item_obscured'])) {
- $key = get_config('system','prvkey');
- if($item['title'])
- $item['title'] = crypto_unencapsulate(json_decode($item['title'],true),$key);
- if($item['body'])
- $item['body'] = crypto_unencapsulate(json_decode($item['body'],true),$key);
- if(get_config('system','item_cache')) {
- q("update item set title = '%s', body = '%s', item_obscured = 0 where id = %d",
- dbesc($item['title']),
- dbesc($item['body']),
- intval($item['id'])
- );
- }
- }
+ return;
}
function unobscure_mail(&$item) {
@@ -1409,7 +1397,7 @@ function theme_attachments(&$item) {
if(is_foreigner($item['author_xchan']))
$url = $r['href'];
else
- $url = z_root() . '/magic?f=&hash=' . $item['author_xchan'] . '&dest=' . $r['href'] . '/' . $r['revision'];
+ $url = z_root() . '/magic?f=&owa=1&hash=' . $item['author_xchan'] . '&dest=' . $r['href'] . '/' . $r['revision'];
//$s .= '<a href="' . $url . '" title="' . $title . '" class="attachlink" >' . $icon . '</a>';
$attaches[] = array('label' => $label, 'url' => $url, 'icon' => $icon, 'title' => $title);
@@ -1465,11 +1453,10 @@ function format_hashtags(&$item) {
continue;
if(strpos($item['body'], $t['url']))
continue;
-
if($s)
- $s .= '&nbsp';
+ $s .= ' ';
- $s .= '#<a href="' . zid($t['url']) . '" >' . $term . '</a>';
+ $s .= '<span class="badge badge-pill badge-info"><i class="fa fa-hashtag"></i>&nbsp;<a class="text-white" href="' . zid($t['url']) . '" >' . $term . '</a></span>';
}
}
@@ -1489,11 +1476,9 @@ function format_mentions(&$item) {
continue;
if(strpos($item['body'], $t['url']))
continue;
-
if($s)
- $s .= '&nbsp';
-
- $s .= '@<a href="' . zid($t['url']) . '" >' . $term . '</a>';
+ $s .= ' ';
+ $s .= '<span class="badge badge-pill badge-success"><i class="fa fa-at"></i>&nbsp;<a class="text-white" href="' . zid($t['url']) . '" >' . $term . '</a></span>';
}
}
@@ -1554,17 +1539,22 @@ function prepare_body(&$item,$attach = false) {
// if original photo width is <= 640px prepend it to item body
if($object['link'][0]['width'] && $object['link'][0]['width'] <= 640) {
- $s .= '<div class="inline-photo-item-wrapper"><a href="' . zid(rawurldecode($object['id'])) . '" target="_blank"><img class="inline-photo-item" style="max-width:' . $object['link'][0]['width'] . 'px; width:100%; height:auto;" src="' . zid(rawurldecode($object['link'][0]['href'])) . '"></a></div>' . $s;
+ $s .= '<div class="inline-photo-item-wrapper"><a href="' . zid(rawurldecode($object['id'])) . '" target="_blank" rel="nofollow noopener" ><img class="inline-photo-item" style="max-width:' . $object['link'][0]['width'] . 'px; width:100%; height:auto;" src="' . zid(rawurldecode($object['link'][0]['href'])) . '"></a></div>' . $s;
}
// if original photo width is > 640px make it a cover photo
if($object['link'][0]['width'] && $object['link'][0]['width'] > 640) {
$scale = ((($object['link'][1]['width'] == 1024) || ($object['link'][1]['height'] == 1024)) ? 1 : 0);
- $photo = '<a href="' . zid(rawurldecode($object['id'])) . '" target="_blank"><img style="max-width:' . $object['link'][$scale]['width'] . 'px; width:100%; height:auto;" src="' . zid(rawurldecode($object['link'][$scale]['href'])) . '"></a>';
+ $photo = '<a href="' . zid(rawurldecode($object['id'])) . '" target="_blank" rel="nofollow noopener"><img style="max-width:' . $object['link'][$scale]['width'] . 'px; width:100%; height:auto;" src="' . zid(rawurldecode($object['link'][$scale]['href'])) . '"></a>';
}
}
- $s .= prepare_text($item['body'],$item['mimetype'], false);
+ if($item['item_obscured']) {
+ $s .= prepare_binary($item);
+ }
+ else {
+ $s .= prepare_text($item['body'],$item['mimetype'], false);
+ }
$event = (($item['obj_type'] === ACTIVITY_OBJ_EVENT) ? format_event_obj($item['obj']) : false);
@@ -1581,11 +1571,6 @@ function prepare_body(&$item,$attach = false) {
$photo = $prep_arr['photo'];
$event = $prep_arr['event'];
-// q("update item set html = '%s' where id = %d",
-// dbesc($s),
-// intval($item['id'])
-// );
-
if(! $attach) {
return $s;
}
@@ -1632,6 +1617,17 @@ function prepare_body(&$item,$attach = false) {
return $prep_arr;
}
+
+function prepare_binary($item) {
+ return replace_macros(get_markup_template('item_binary.tpl'), [
+ '$download' => t('Download binary/encrypted content'),
+ '$url' => z_root() . '/viewsrc/' . $item['id'] . '/download'
+ ]);
+}
+
+
+
+
/**
* @brief Given a text string, convert from bbcode to html and add smilie icons.
*
@@ -1653,8 +1649,8 @@ function prepare_text($text, $content_type = 'text/bbcode', $cache = false) {
break;
case 'text/markdown':
- require_once('library/markdown.php');
- $s = Markdown($text);
+ $text = Zlib\MarkdownSoap::unescape($text);
+ $s = MarkdownExtra::defaultTransform($text);
break;
case 'application/x-pdl';
@@ -1798,42 +1794,28 @@ function layout_select($channel_id, $current = '') {
}
-function mimetype_select($channel_id, $current = 'text/bbcode') {
+function mimetype_select($channel_id, $current = 'text/bbcode', $choices = null, $element = 'mimetype') {
- $x = array(
- 'text/bbcode',
- 'text/html',
- 'text/markdown',
- 'text/plain',
- 'application/x-pdl'
- );
+ $x = (($choices) ? $choices : [
+ 'text/bbcode' => t('BBcode'),
+ 'text/html' => t('HTML'),
+ 'text/markdown' => t('Markdown'),
+ 'text/plain' => t('Text'),
+ 'application/x-pdl' => t('Comanche Layout')
+ ]);
- if(App::$is_sys) {
- $x[] = 'application/x-php';
+ if((App::$is_sys) || (channel_codeallowed($channel_id) && $channel_id == local_channel())){
+ $x['application/x-php'] = t('PHP');
}
- else {
- $r = q("select account_id, account_roles, channel_pageflags from account left join channel on account_id = channel_account_id where
- channel_id = %d limit 1",
- intval($channel_id)
- );
- if($r) {
- if(($r[0]['account_roles'] & ACCOUNT_ROLE_ALLOWCODE) || ($r[0]['channel_pageflags'] & PAGE_ALLOWCODE)) {
- if(local_channel() && get_account_id() == $r[0]['account_id']) {
- $x[] = 'application/x-php';
- }
- }
- }
- }
-
- foreach($x as $y) {
+ foreach($x as $y => $z) {
$selected = (($y == $current) ? ' selected="selected" ' : '');
- $options .= '<option name="' . $y . '"' . $selected . '>' . $y . '</option>';
+ $options .= '<option value="' . $y . '"' . $selected . '>' . $z . '</option>';
}
$o = replace_macros(get_markup_template('field_select_raw.tpl'), array(
- '$field' => array('mimetype', t('Page content type'), $selected, '', $options)
+ '$field' => array( $element, t('Page content type'), $selected, '', $options)
));
return $o;
@@ -2010,26 +1992,47 @@ function is_a_date_arg($s) {
}
function legal_webbie($s) {
- if(! strlen($s))
+ if(! $s)
return '';
- $x = $s;
- do {
- $s = $x;
- $x = preg_replace('/^([^a-z])(.*?)/',"$2",$s);
- } while($x != $s);
+ // WARNING: This regex may not work in a federated environment.
+ // You will probably want something like
+ // preg_replace('/([^a-z0-9\_])/','',strtolower($s));
+
+ $r = preg_replace('/([^a-z0-9\-\_])/','',strtolower($s));
+
+ $x = [ 'input' => $s, 'output' => $r ];
+ call_hooks('legal_webbie',$x);
+ return $x['output'];
- return preg_replace('/([^a-z0-9\-\_])/','',$x);
}
+function legal_webbie_text() {
+
+ // WARNING: This will not work in a federated environment.
+
+ $s = t('a-z, 0-9, -, and _ only');
+
+ $x = [ 'text' => $s ];
+ call_hooks('legal_webbie_text',$x);
+ return $x['text'];
+
+}
+
+
+
+
function check_webbie($arr) {
+
+ // These names conflict with the CalDAV server
+ $taken = [ 'principals', 'addressbooks', 'calendars' ];
+
$reservechan = get_config('system','reserved_channels');
- if(strlen($reservechan))
- $taken = explode(',', $reservechan);
- else
- $taken = array('principals','addressbooks','calendars');
+ if(strlen($reservechan)) {
+ $taken = array_merge($taken,explode(',', $reservechan));
+ }
$str = '';
if(count($arr)) {
@@ -2065,7 +2068,7 @@ function ids_to_array($arr,$idx = 'id') {
$t = array();
if($arr) {
foreach($arr as $x) {
- if(array_key_exists($idx,$x) && strlen($x[$idx]) && (! in_array($x[$idx],$t))) {
+ if(array_key_exists($idx,$x) && strlen($x[$idx]) && (! in_array($x[$idx],$t))) {
$t[] = $x[$idx];
}
}
@@ -2081,7 +2084,7 @@ function ids_to_querystr($arr,$idx = 'id',$quote = false) {
if($arr) {
foreach($arr as $x) {
if(! in_array($x[$idx],$t)) {
- if($quote)
+ if($quote)
$t[] = "'" . dbesc($x[$idx]) . "'";
else
$t[] = $x[$idx];
@@ -2098,7 +2101,7 @@ function ids_to_querystr($arr,$idx = 'id',$quote = false) {
* If $abook is true also include the abook info. This is needed in the API to
* save extra per item lookups there.
*
- * @param array[in,out] &$items
+ * @param[in,out] array &$items
* @param boolean $abook If true also include the abook info
* @param number $effective_uid
*/
@@ -2194,10 +2197,10 @@ function magic_link($s) {
}
/**
- * if $escape is true, dbesc() each element before adding quotes
+ * @brief If $escape is true, dbesc() each element before adding quotes.
*
- * @param array[in,out] &$arr
- * @param boolean $escape default false
+ * @param[in,out] array &$arr
+ * @param boolean $escape (optional) default false
*/
function stringify_array_elms(&$arr, $escape = false) {
for($x = 0; $x < count($arr); $x ++)
@@ -2208,7 +2211,6 @@ function stringify_array_elms(&$arr, $escape = false) {
* @brief Indents a flat JSON string to make it more human-readable.
*
* @param string $json The original JSON string to process.
- *
* @return string Indented version of the original JSON string.
*/
function jindent($json) {
@@ -2280,13 +2282,13 @@ function design_tools() {
$who = $channel['channel_address'];
return replace_macros(get_markup_template('design_tools.tpl'), array(
- '$title' => t('Design Tools'),
- '$who' => $who,
- '$sys' => $sys,
+ '$title' => t('Design Tools'),
+ '$who' => $who,
+ '$sys' => $sys,
'$blocks' => t('Blocks'),
- '$menus' => t('Menus'),
+ '$menus' => t('Menus'),
'$layout' => t('Layouts'),
- '$pages' => t('Pages')
+ '$pages' => t('Pages')
));
}
@@ -2307,21 +2309,21 @@ function website_portation_tools() {
}
return replace_macros(get_markup_template('website_portation_tools.tpl'), array(
- '$title' => t('Import'),
- '$import_label' => t('Import website...'),
- '$import_placeholder' => t('Select folder to import'),
- '$file_upload_text' => t('Import from a zipped folder:'),
- '$file_import_text' => t('Import from cloud files:'),
- '$desc' => t('/cloud/channel/path/to/folder'),
- '$hint' => t('Enter path to website files'),
- '$select' => t('Select folder'),
- '$export_label' => t('Export website...'),
- '$file_download_text' => t('Export to a zip file'),
- '$filename_desc' => t('website.zip'),
- '$filename_hint' => t('Enter a name for the zip file.'),
- '$cloud_export_text' => t('Export to cloud files'),
- '$cloud_export_desc' => t('/path/to/export/folder'),
- '$cloud_export_hint' => t('Enter a path to a cloud files destination.'),
+ '$title' => t('Import'),
+ '$import_label' => t('Import website...'),
+ '$import_placeholder' => t('Select folder to import'),
+ '$file_upload_text' => t('Import from a zipped folder:'),
+ '$file_import_text' => t('Import from cloud files:'),
+ '$desc' => t('/cloud/channel/path/to/folder'),
+ '$hint' => t('Enter path to website files'),
+ '$select' => t('Select folder'),
+ '$export_label' => t('Export website...'),
+ '$file_download_text' => t('Export to a zip file'),
+ '$filename_desc' => t('website.zip'),
+ '$filename_hint' => t('Enter a name for the zip file.'),
+ '$cloud_export_text' => t('Export to cloud files'),
+ '$cloud_export_desc' => t('/path/to/export/folder'),
+ '$cloud_export_hint' => t('Enter a path to a cloud files destination.'),
'$cloud_export_select' => t('Specify folder'),
));
}
@@ -2389,8 +2391,9 @@ function handle_tag($a, &$body, &$access_tag, &$str_tags, $profile_uid, $tag, $d
$r = null;
$match = array();
- $termtype = ((strpos($tag,'#') === 0) ? TERM_HASHTAG : TERM_UNKNOWN);
- $termtype = ((strpos($tag,'@') === 0) ? TERM_MENTION : $termtype);
+ $termtype = ((strpos($tag,'#') === 0) ? TERM_HASHTAG : TERM_UNKNOWN);
+ $termtype = ((strpos($tag,'@') === 0) ? TERM_MENTION : $termtype);
+ $termtype = ((strpos($tag,'!') === 0) ? TERM_FORUM : $termtype);
$termtype = ((strpos($tag,'#^[') === 0) ? TERM_BOOKMARK : $termtype);
//is it a hash tag?
@@ -2407,16 +2410,9 @@ function handle_tag($a, &$body, &$access_tag, &$str_tags, $profile_uid, $tag, $d
//...do nothing
return $replaced;
}
- if($tag == '#getzot') {
- $basetag = 'getzot';
- $url = 'http://hubzilla.org';
- $newtag = '#[zrl=' . $url . ']' . $basetag . '[/zrl]';
- $body = str_replace($tag,$newtag,$body);
- $replaced = true;
- }
if(! $replaced) {
- //base tag has the tags name only
+ // base tag has the tags name only
if((substr($tag,0,7) === '#&quot;') && (substr($tag,-6,6) === '&quot;')) {
$basetag = substr($tag,7);
@@ -2454,10 +2450,16 @@ function handle_tag($a, &$body, &$access_tag, &$str_tags, $profile_uid, $tag, $d
//is it a person tag?
- if(strpos($tag,'@') === 0) {
+ $grouptag = false;
+
+ if(strpos($tag,'!') === 0) {
+ $grouptag = true;
+ }
+
+ if(strpos($tag,'@') === 0 || $grouptag) {
// The @! tag will alter permissions
- $exclusive = ((strpos($tag,'!') === 1 && (! $diaspora)) ? true : false);
+ $exclusive = (((! $grouptag) && (strpos($tag,'!') === 1) && (! $diaspora)) ? true : false);
//is it already replaced?
if(strpos($tag,'[zrl='))
@@ -2498,7 +2500,7 @@ function handle_tag($a, &$body, &$access_tag, &$str_tags, $profile_uid, $tag, $d
if(($t2) && (! $diaspora)) {
//get the id
- $tagcid = substr($newname,$t2 + 1);
+ $tagcid = urldecode(substr($newname,$t2 + 1));
if(strrpos($tagcid,' '))
$tagcid = substr($tagcid,0,strrpos($tagcid,' '));
@@ -2629,8 +2631,15 @@ function handle_tag($a, &$body, &$access_tag, &$str_tags, $profile_uid, $tag, $d
//create profile link
$profile = str_replace(',','%2c',$profile);
$url = $profile;
- $newtag = '@' . (($exclusive) ? '!' : '') . '[zrl=' . $profile . ']' . $newname . (($forum && ! $trailing_plus_name) ? '+' : '') . '[/zrl]';
- $body = str_replace('@' . (($exclusive) ? '!' : '') . $name, $newtag, $body);
+ if($grouptag) {
+ $newtag = '!' . '[zrl=' . $profile . ']' . $newname . '[/zrl]';
+ $body = str_replace('!' . $name, $newtag, $body);
+ }
+ else {
+ $newtag = '@' . (($exclusive) ? '!' : '') . '[zrl=' . $profile . ']' . $newname . (($forum && ! $trailing_plus_name) ? '+' : '') . '[/zrl]';
+ $body = str_replace('@' . (($exclusive) ? '!' : '') . $name, $newtag, $body);
+ }
+
//append tag to str_tags
if(! stristr($str_tags,$newtag)) {
if(strlen($str_tags))
@@ -2837,7 +2846,7 @@ function item_url_replace($channel,&$item,$old,$new,$oldnick = '') {
*/
function sanitise_acl(&$item) {
if (strlen($item))
- $item = '<' . notags(trim($item)) . '>';
+ $item = '<' . notags(trim(urldecode($item))) . '>';
else
unset($item);
}
@@ -2919,7 +2928,7 @@ function pdl_selector($uid, $current='') {
$sql_extra = item_permissions_sql($uid);
- $r = q("select iconfig.*, mid from item_id left join item on iconfig.iid = item.id
+ $r = q("select iconfig.*, mid from iconfig left join item on iconfig.iid = item.id
where item.uid = %d and iconfig.cat = 'system' and iconfig.k = 'PDL' $sql_extra order by v asc",
intval($uid)
);
@@ -2979,6 +2988,9 @@ function flatten_array_recursive($arr) {
* @param string $s Text to highlight
* @param string $lang Which language should be highlighted
* @return string
+ * Important: The returned text has the text pattern 'http' translated to '%eY9-!' which should be converted back
+ * after further processing. This was done to prevent oembed links from occurring inside code blocks.
+ * See include/bbcode.php
*/
function text_highlight($s, $lang) {
@@ -2991,40 +3003,15 @@ function text_highlight($s, $lang) {
$s = jindent($s);
}
- if(! strpos('Text_Highlighter', get_include_path())) {
- set_include_path(get_include_path() . PATH_SEPARATOR . 'library/Text_Highlighter');
- }
- require_once('library/Text_Highlighter/Text/Highlighter.php');
- require_once('library/Text_Highlighter/Text/Highlighter/Renderer/Html.php');
- $options = array(
- 'numbers' => HL_NUMBERS_LI,
- 'tabsize' => 4,
- );
- $tag_added = false;
- $s = trim(html_entity_decode($s, ENT_COMPAT));
- $s = str_replace(" ", "\t", $s);
-
- // The highlighter library insists on an opening php tag for php code blocks. If
- // it isn't present, nothing is highlighted. So we're going to see if it's present.
- // If not, we'll add it, and then quietly remove it after we get the processed output back.
-
- if($lang === 'php') {
- if(strpos('<?php', $s) !== 0) {
- $s = '<?php' . "\n" . $s;
- $tag_added = true;
- }
- }
- $renderer = new Text_Highlighter_Renderer_HTML($options);
- $hl = Text_Highlighter::factory($lang);
- $hl->setRenderer($renderer);
- $o = $hl->highlight($s);
- $o = str_replace([" ", "\n"], ["&nbsp;&nbsp;&nbsp;&nbsp;", ''], $o);
+ $arr = [ 'text' => $s, 'language' => $lang, 'success' => false ];
+ call_hooks('text_highlight',$arr);
- if($tag_added) {
- $b = substr($o, 0, strpos($o, '<li>'));
- $e = substr($o, strpos($o, '</li>'));
- $o = $b . $e;
- }
+ if($arr['success'])
+ $o = $arr['text'];
+ else
+ $o = $s;
+
+ $o = str_replace('http','%eY9-!',$o);
return('<code>' . $o . '</code>');
}
@@ -3055,13 +3042,22 @@ function array2XML($obj, $array) {
if(is_array($value)) {
$node = $obj->addChild($key);
array2XML($node, $value);
- } else {
+ }
+ else {
$obj->addChild($key, htmlspecialchars($value));
}
}
}
-
+/**
+ * @brief Inserts an array into $table.
+ *
+ * @TODO Why is this function in include/text.php?
+ *
+ * @param string $table
+ * @param array $arr
+ * @return boolean|PDOStatement
+ */
function create_table_from_array($table, $arr) {
if(! ($arr && $table))
@@ -3079,6 +3075,14 @@ function create_table_from_array($table, $arr) {
return $r;
}
+function share_shield($m) {
+ return str_replace($m[1],'!=+=+=!' . base64url_encode($m[1]) . '=+!=+!=',$m[0]);
+}
+
+function share_unshield($m) {
+ $x = str_replace(array('!=+=+=!','=+!=+!='),array('',''),$m[1]);
+ return str_replace($m[1], base64url_decode($x), $m[0]);
+}
function cleanup_bbcode($body) {
@@ -3141,3 +3145,20 @@ function array_escape_tags(&$v,$k) {
$v = escape_tags($v);
}
+function ellipsify($s,$maxlen) {
+ if($maxlen & 1)
+ $maxlen --;
+ if($maxlen < 4)
+ $maxlen = 4;
+
+ if(mb_strlen($s) < $maxlen)
+ return $s;
+
+ return mb_substr($s,0,$maxlen / 2) . '...' . mb_substr($s,mb_strlen($s) - ($maxlen / 2));
+}
+
+function purify_filename($s) {
+ if(($s[0] === '.') || strpos($s,'/') !== false)
+ return '';
+ return $s;
+}
diff --git a/include/widgets.php b/include/widgets.php
deleted file mode 100644
index cb8a6133e..000000000
--- a/include/widgets.php
+++ /dev/null
@@ -1,1735 +0,0 @@
-<?php
-/**
- * @file include/widgets.php
- *
- * @brief This file contains the widgets.
- */
-
-require_once('include/dir_fns.php');
-require_once('include/contact_widgets.php');
-require_once('include/attach.php');
-
-
-function widget_profile($args) {
-
- $block = observer_prohibited();
- return profile_sidebar(App::$profile, $block, true);
-}
-
-function widget_zcard($args) {
-
- $block = observer_prohibited();
- $channel = channelx_by_n(App::$profile_uid);
- return get_zcard($channel,get_observer_hash(),array('width' => 875));
-}
-
-
-
-
-// FIXME The problem with the next widget is that we don't have a search function for webpages that we can send the links to.
-// Then we should also provide an option to search webpages and conversations.
-
-function widget_tagcloud($args) {
-
- $o = '';
- //$tab = 0;
-
- $uid = App::$profile_uid;
- $count = ((x($args,'count')) ? intval($args['count']) : 24);
- $flags = 0;
- $type = TERM_CATEGORY;
-
- // FIXME there exists no $authors variable
- $r = tagadelic($uid, $count, $authors, $owner, $flags, ITEM_TYPE_WEBPAGE, $type);
-
- if($r) {
- $o = '<div class="tagblock widget"><h3>' . t('Categories') . '</h3><div class="tags" align="center">';
- foreach($r as $rr) {
- $o .= '<span class="tag'.$rr[2].'">'.$rr[0].'</span> ' . "\r\n";
- }
- $o .= '</div></div>';
- }
- return $o;
-}
-
-function widget_collections($args) {
- require_once('include/group.php');
-
- $mode = ((array_key_exists('mode',$args)) ? $args['mode'] : 'conversation');
- switch($mode) {
- case 'conversation':
- $every = argv(0);
- $each = argv(0);
- $edit = true;
- $current = $_REQUEST['gid'];
- $abook_id = 0;
- $wmode = 0;
- break;
- case 'connections':
- $every = 'connections';
- $each = 'group';
- $edit = true;
- $current = $_REQUEST['gid'];
- $abook_id = 0;
- $wmode = 0;
- case 'groups':
- $every = 'connections';
- $each = argv(0);
- $edit = false;
- $current = intval(argv(1));
- $abook_id = 0;
- $wmode = 1;
- break;
- case 'abook':
- $every = 'connections';
- $each = 'group';
- $edit = false;
- $current = 0;
- $abook_id = App::$poi['abook_xchan'];
- $wmode = 1;
- break;
- default:
- return '';
- break;
- }
-
- return group_side($every, $each, $edit, $current, $abook_id, $wmode);
-}
-
-
-function widget_appselect($arr) {
- return replace_macros(get_markup_template('app_select.tpl'),array(
- '$title' => t('Apps'),
- '$system' => t('System'),
- '$authed' => ((local_channel()) ? true : false),
- '$personal' => t('Personal'),
- '$new' => t('New App'),
- '$edit' => t('Edit Apps'),
- '$cat' => ((array_key_exists('cat',$_REQUEST)) ? $_REQUEST['cat'] : '')
- ));
-}
-
-
-function widget_suggestions($arr) {
-
- if((! local_channel()) || (! feature_enabled(local_channel(),'suggest')))
- return '';
-
- require_once('include/socgraph.php');
-
- $r = suggestion_query(local_channel(),get_observer_hash(),0,20);
-
- if(! $r) {
- return;
- }
-
- $arr = array();
-
- // Get two random entries from the top 20 returned.
- // We'll grab the first one and the one immediately following.
- // This will throw some entropy intot he situation so you won't
- // be looking at the same two mug shots every time the widget runs
-
- $index = ((count($r) > 2) ? mt_rand(0,count($r) - 2) : 0);
-
- for($x = $index; $x <= ($index+1); $x ++) {
- $rr = $r[$x];
- if(! $rr['xchan_url'])
- break;
-
- $connlnk = z_root() . '/follow/?url=' . $rr['xchan_addr'];
-
- $arr[] = array(
- 'url' => chanlink_url($rr['xchan_url']),
- 'profile' => $rr['xchan_url'],
- 'name' => $rr['xchan_name'],
- 'photo' => $rr['xchan_photo_m'],
- 'ignlnk' => z_root() . '/directory?ignore=' . $rr['xchan_hash'],
- 'conntxt' => t('Connect'),
- 'connlnk' => $connlnk,
- 'ignore' => t('Ignore/Hide')
- );
- }
-
- $o = replace_macros(get_markup_template('suggest_widget.tpl'),array(
- '$title' => t('Suggestions'),
- '$more' => t('See more...'),
- '$entries' => $arr
- ));
-
- return $o;
-}
-
-
-function widget_follow($args) {
- if(! local_channel())
- return '';
-
- $uid = App::$channel['channel_id'];
- $r = q("select count(*) as total from abook where abook_channel = %d and abook_self = 0 ",
- intval($uid)
- );
- if($r)
- $total_channels = $r[0]['total'];
- $limit = service_class_fetch($uid,'total_channels');
- if($limit !== false) {
- $abook_usage_message = sprintf( t("You have %1$.0f of %2$.0f allowed connections."), $total_channels, $limit);
- }
- else {
- $abook_usage_message = '';
- }
- return replace_macros(get_markup_template('follow.tpl'),array(
- '$connect' => t('Add New Connection'),
- '$desc' => t('Enter channel address'),
- '$hint' => t('Examples: bob@example.com, https://example.com/barbara'),
- '$follow' => t('Connect'),
- '$abook_usage_message' => $abook_usage_message
- ));
-}
-
-
-function widget_notes($arr) {
- if(! local_channel())
- return '';
- if(! feature_enabled(local_channel(),'private_notes'))
- return '';
-
- $text = get_pconfig(local_channel(),'notes','text');
-
- $o = replace_macros(get_markup_template('notes.tpl'), array(
- '$banner' => t('Notes'),
- '$text' => $text,
- '$save' => t('Save'),
- ));
-
- return $o;
-}
-
-
-function widget_savedsearch($arr) {
- if((! local_channel()) || (! feature_enabled(local_channel(),'savedsearch')))
- return '';
-
- $search = ((x($_GET,'netsearch')) ? $_GET['netsearch'] : '');
- if(! $search)
- $search = ((x($_GET,'search')) ? $_GET['search'] : '');
-
- if(x($_GET,'searchsave') && $search) {
- $r = q("select * from term where uid = %d and ttype = %d and term = '%s' limit 1",
- intval(local_channel()),
- intval(TERM_SAVEDSEARCH),
- dbesc($search)
- );
- if(! $r) {
- q("insert into term ( uid,ttype,term ) values ( %d, %d, '%s') ",
- intval(local_channel()),
- intval(TERM_SAVEDSEARCH),
- dbesc($search)
- );
- }
- }
-
- if(x($_GET,'searchremove') && $search) {
- q("delete from term where uid = %d and ttype = %d and term = '%s'",
- intval(local_channel()),
- intval(TERM_SAVEDSEARCH),
- dbesc($search)
- );
- $search = '';
- }
-
- $srchurl = App::$query_string;
-
- $srchurl = rtrim(preg_replace('/searchsave\=[^\&].*?(\&|$)/is','',$srchurl),'&');
- $hasq = ((strpos($srchurl,'?') !== false) ? true : false);
- $srchurl = rtrim(preg_replace('/searchremove\=[^\&].*?(\&|$)/is','',$srchurl),'&');
-
- $srchurl = rtrim(preg_replace('/search\=[^\&].*?(\&|$)/is','',$srchurl),'&');
- $srchurl = rtrim(preg_replace('/submit\=[^\&].*?(\&|$)/is','',$srchurl),'&');
- $srchurl = str_replace(array('?f=','&f='),array('',''),$srchurl);
-
-
- $hasq = ((strpos($srchurl,'?') !== false) ? true : false);
- $hasamp = ((strpos($srchurl,'&') !== false) ? true : false);
-
- if(($hasamp) && (! $hasq))
- $srchurl = substr($srchurl,0,strpos($srchurl,'&')) . '?f=&' . substr($srchurl,strpos($srchurl,'&')+1);
-
- $o = '';
-
- $r = q("select tid,term from term WHERE uid = %d and ttype = %d ",
- intval(local_channel()),
- intval(TERM_SAVEDSEARCH)
- );
-
- $saved = array();
-
- if(count($r)) {
- foreach($r as $rr) {
- $saved[] = array(
- 'id' => $rr['tid'],
- 'term' => $rr['term'],
- 'dellink' => z_root() . '/' . $srchurl . (($hasq || $hasamp) ? '' : '?f=') . '&amp;searchremove=1&amp;search=' . urlencode($rr['term']),
- 'srchlink' => z_root() . '/' . $srchurl . (($hasq || $hasamp) ? '' : '?f=') . '&amp;search=' . urlencode($rr['term']),
- 'displayterm' => htmlspecialchars($rr['term'], ENT_COMPAT,'UTF-8'),
- 'encodedterm' => urlencode($rr['term']),
- 'delete' => t('Remove term'),
- 'selected' => ($search==$rr['term']),
- );
- }
- }
-
- $tpl = get_markup_template("saved_searches.tpl");
- $o = replace_macros($tpl, array(
- '$title' => t('Saved Searches'),
- '$add' => t('add'),
- '$searchbox' => searchbox($search, 'netsearch-box', $srchurl . (($hasq) ? '' : '?f='), true),
- '$saved' => $saved,
- ));
-
- return $o;
-}
-
-function widget_sitesearch($arr) {
-
- $search = ((x($_GET,'search')) ? $_GET['search'] : '');
-
- $srchurl = App::$query_string;
-
- $srchurl = rtrim(preg_replace('/search\=[^\&].*?(\&|$)/is','',$srchurl),'&');
- $srchurl = rtrim(preg_replace('/submit\=[^\&].*?(\&|$)/is','',$srchurl),'&');
- $srchurl = str_replace(array('?f=','&f='),array('',''),$srchurl);
-
-
- $hasq = ((strpos($srchurl,'?') !== false) ? true : false);
- $hasamp = ((strpos($srchurl,'&') !== false) ? true : false);
-
- if(($hasamp) && (! $hasq))
- $srchurl = substr($srchurl,0,strpos($srchurl,'&')) . '?f=&' . substr($srchurl,strpos($srchurl,'&')+1);
-
- $o = '';
-
- $saved = array();
-
- $tpl = get_markup_template("sitesearch.tpl");
- $o = replace_macros($tpl, array(
- '$title' => t('Search'),
- '$searchbox' => searchbox($search, 'netsearch-box', $srchurl . (($hasq) ? '' : '?f='), false),
- '$saved' => $saved,
- ));
-
- return $o;
-}
-
-
-
-
-
-function widget_filer($arr) {
- if(! local_channel())
- return '';
-
-
- $selected = ((x($_REQUEST,'file')) ? $_REQUEST['file'] : '');
-
- $terms = array();
- $r = q("select distinct term from term where uid = %d and ttype = %d order by term asc",
- intval(local_channel()),
- intval(TERM_FILE)
- );
- if(! $r)
- return;
-
- foreach($r as $rr)
- $terms[] = array('name' => $rr['term'], 'selected' => (($selected == $rr['term']) ? 'selected' : ''));
-
- return replace_macros(get_markup_template('fileas_widget.tpl'),array(
- '$title' => t('Saved Folders'),
- '$desc' => '',
- '$sel_all' => (($selected == '') ? 'selected' : ''),
- '$all' => t('Everything'),
- '$terms' => $terms,
- '$base' => z_root() . '/' . App::$cmd
- ));
-}
-
-function widget_archive($arr) {
-
- $o = '';
-
- if(! App::$profile_uid) {
- return '';
- }
-
- $uid = App::$profile_uid;
-
- if(! feature_enabled($uid,'archives'))
- return '';
-
- if(! perm_is_allowed($uid,get_observer_hash(),'view_stream'))
- return '';
-
- $wall = ((array_key_exists('wall', $arr)) ? intval($arr['wall']) : 0);
- $style = ((array_key_exists('style', $arr)) ? $arr['style'] : 'select');
- $showend = ((get_pconfig($uid,'system','archive_show_end_date')) ? true : false);
- $mindate = get_pconfig($uid,'system','archive_mindate');
- $visible_years = get_pconfig($uid,'system','archive_visible_years');
- if(! $visible_years)
- $visible_years = 5;
-
- $url = z_root() . '/' . App::$cmd;
-
- $ret = list_post_dates($uid,$wall,$mindate);
-
- if(! count($ret))
- return '';
-
- $cutoff_year = intval(datetime_convert('',date_default_timezone_get(),'now','Y')) - $visible_years;
- $cutoff = ((array_key_exists($cutoff_year,$ret))? true : false);
-
- $o = replace_macros(get_markup_template('posted_date_widget.tpl'),array(
- '$title' => t('Archives'),
- '$size' => $visible_years,
- '$cutoff_year' => $cutoff_year,
- '$cutoff' => $cutoff,
- '$url' => $url,
- '$style' => $style,
- '$showend' => $showend,
- '$dates' => $ret
- ));
- return $o;
-}
-
-
-function widget_fullprofile($arr) {
-
- if(! App::$profile['profile_uid'])
- return;
-
- $block = observer_prohibited();
-
- return profile_sidebar(App::$profile, $block);
-}
-
-function widget_shortprofile($arr) {
-
- if(! App::$profile['profile_uid'])
- return;
-
- $block = observer_prohibited();
-
- return profile_sidebar(App::$profile, $block, true, true);
-}
-
-
-function widget_categories($arr) {
-
-
- if(App::$profile['profile_uid'] && (! perm_is_allowed(App::$profile['profile_uid'],get_observer_hash(),'view_stream')))
- return '';
-
- $cat = ((x($_REQUEST,'cat')) ? htmlspecialchars($_REQUEST['cat'],ENT_COMPAT,'UTF-8') : '');
- $srchurl = App::$query_string;
- $srchurl = rtrim(preg_replace('/cat\=[^\&].*?(\&|$)/is','',$srchurl),'&');
- $srchurl = str_replace(array('?f=','&f='),array('',''),$srchurl);
-
- return categories_widget($srchurl, $cat);
-
-}
-
-function widget_appcategories($arr) {
-
- if(! local_channel())
- return '';
-
- $selected = ((x($_REQUEST,'cat')) ? htmlspecialchars($_REQUEST['cat'],ENT_COMPAT,'UTF-8') : '');
-
- $srchurl = rtrim(preg_replace('/cat\=[^\&].*?(\&|$)/is','',$srchurl),'&');
- $srchurl = str_replace(array('?f=','&f='),array('',''),$srchurl);
-
- $srchurl = z_root() . '/apps';
-
- $terms = array();
-
- $r = q("select distinct(term.term)
- from term join app on term.oid = app.id
- where app_channel = %d
- and term.uid = app_channel
- and term.otype = %d
- and term.term != 'nav_featured_app'
- order by term.term asc",
- intval(local_channel()),
- intval(TERM_OBJ_APP)
- );
- if($r) {
- foreach($r as $rr)
- $terms[] = array('name' => $rr['term'], 'selected' => (($selected == $rr['term']) ? 'selected' : ''));
-
- return replace_macros(get_markup_template('categories_widget.tpl'),array(
- '$title' => t('Categories'),
- '$desc' => '',
- '$sel_all' => (($selected == '') ? 'selected' : ''),
- '$all' => t('Everything'),
- '$terms' => $terms,
- '$base' => $srchurl,
-
- ));
- }
-
-
-
-}
-
-
-
-function widget_appcloud($arr) {
- if(! local_channel())
- return '';
- return app_tagblock(z_root() . '/apps');
-}
-
-
-function widget_tagcloud_wall($arr) {
-
-
- if((! App::$profile['profile_uid']) || (! App::$profile['channel_hash']))
- return '';
- if(! perm_is_allowed(App::$profile['profile_uid'], get_observer_hash(), 'view_stream'))
- return '';
-
- $limit = ((array_key_exists('limit', $arr)) ? intval($arr['limit']) : 50);
- if(feature_enabled(App::$profile['profile_uid'], 'tagadelic'))
- return wtagblock(App::$profile['profile_uid'], $limit, '', App::$profile['channel_hash'], 'wall');
-
- return '';
-}
-
-function widget_catcloud_wall($arr) {
-
-
- if((! App::$profile['profile_uid']) || (! App::$profile['channel_hash']))
- return '';
- if(! perm_is_allowed(App::$profile['profile_uid'], get_observer_hash(), 'view_stream'))
- return '';
-
- $limit = ((array_key_exists('limit',$arr)) ? intval($arr['limit']) : 50);
-
- return catblock(App::$profile['profile_uid'], $limit, '', App::$profile['channel_hash'], 'wall');
-}
-
-
-function widget_affinity($arr) {
-
- if(! local_channel())
- return '';
-
- // Get default cmin value from pconfig, but allow GET parameter to override
- $cmin = intval(get_pconfig(local_channel(),'affinity','cmin'));
- $cmin = (($cmin) ? $cmin : 0);
- $cmin = ((x($_REQUEST,'cmin')) ? intval($_REQUEST['cmin']) : $cmin);
-
- // Get default cmax value from pconfig, but allow GET parameter to override
- $cmax = intval(get_pconfig(local_channel(),'affinity','cmax'));
- $cmax = (($cmax) ? $cmax : 99);
- $cmax = ((x($_REQUEST,'cmax')) ? intval($_REQUEST['cmax']) : $cmax);
-
-
- if(feature_enabled(local_channel(),'affinity')) {
-
- $labels = array(
- t('Me'),
- t('Family'),
- t('Friends'),
- t('Acquaintances'),
- t('All')
- );
- call_hooks('affinity_labels',$labels);
- $label_str = '';
-
- if($labels) {
- foreach($labels as $l) {
- if($label_str) {
- $label_str .= ", '|'";
- $label_str .= ", '" . $l . "'";
- }
- else
- $label_str .= "'" . $l . "'";
- }
- }
-
- $tpl = get_markup_template('main_slider.tpl');
- $x = replace_macros($tpl,array(
- '$val' => $cmin . ',' . $cmax,
- '$refresh' => t('Refresh'),
- '$labels' => $label_str,
- ));
- $arr = array('html' => $x);
- call_hooks('main_slider',$arr);
- return $arr['html'];
- }
-
- return '';
-}
-
-
-function widget_settings_menu($arr) {
-
- if(! local_channel())
- return;
-
-
- $channel = App::get_channel();
-
- $abook_self_id = 0;
-
- // Retrieve the 'self' address book entry for use in the auto-permissions link
-
- $role = get_pconfig(local_channel(),'system','permissions_role');
-
- $abk = q("select abook_id from abook where abook_channel = %d and abook_self = 1 limit 1",
- intval(local_channel())
- );
- if($abk)
- $abook_self_id = $abk[0]['abook_id'];
-
- $x = q("select count(*) as total from hubloc where hubloc_hash = '%s' and hubloc_deleted = 0 ",
- dbesc($channel['channel_hash'])
- );
-
- $hublocs = (($x && $x[0]['total'] > 1) ? true : false);
-
- $tabs = array(
- array(
- 'label' => t('Account settings'),
- 'url' => z_root().'/settings/account',
- 'selected' => ((argv(1) === 'account') ? 'active' : ''),
- ),
-
- array(
- 'label' => t('Channel settings'),
- 'url' => z_root().'/settings/channel',
- 'selected' => ((argv(1) === 'channel') ? 'active' : ''),
- ),
-
- );
-
- if(get_account_techlevel() > 0 && get_features()) {
- $tabs[] = array(
- 'label' => t('Additional features'),
- 'url' => z_root().'/settings/features',
- 'selected' => ((argv(1) === 'features') ? 'active' : ''),
- );
- }
-
- $tabs[] = array(
- 'label' => t('Feature/Addon settings'),
- 'url' => z_root().'/settings/featured',
- 'selected' => ((argv(1) === 'featured') ? 'active' : ''),
- );
-
- $tabs[] = array(
- 'label' => t('Display settings'),
- 'url' => z_root().'/settings/display',
- 'selected' => ((argv(1) === 'display') ? 'active' : ''),
- );
-
- if($hublocs) {
- $tabs[] = array(
- 'label' => t('Manage locations'),
- 'url' => z_root() . '/locs',
- 'selected' => ((argv(1) === 'locs') ? 'active' : ''),
- );
- }
-
- $tabs[] = array(
- 'label' => t('Export channel'),
- 'url' => z_root() . '/uexport',
- 'selected' => ''
- );
-
- $tabs[] = array(
- 'label' => t('Connected apps'),
- 'url' => z_root() . '/settings/oauth',
- 'selected' => ((argv(1) === 'oauth') ? 'active' : ''),
- );
-
- if(get_account_techlevel() > 2) {
- $tabs[] = array(
- 'label' => t('Guest Access Tokens'),
- 'url' => z_root() . '/settings/tokens',
- 'selected' => ((argv(1) === 'tokens') ? 'active' : ''),
- );
- }
-
- if(feature_enabled(local_channel(),'permcats')) {
- $tabs[] = array(
- 'label' => t('Permission Groups'),
- 'url' => z_root() . '/settings/permcats',
- 'selected' => ((argv(1) === 'permcats') ? 'active' : ''),
- );
- }
-
-
- if($role === false || $role === 'custom') {
- $tabs[] = array(
- 'label' => t('Connection Default Permissions'),
- 'url' => z_root() . '/connedit/' . $abook_self_id,
- 'selected' => ''
- );
- }
-
- if(feature_enabled(local_channel(),'premium_channel')) {
- $tabs[] = array(
- 'label' => t('Premium Channel Settings'),
- 'url' => z_root() . '/connect/' . $channel['channel_address'],
- 'selected' => ''
- );
- }
-
- if(feature_enabled(local_channel(),'channel_sources')) {
- $tabs[] = array(
- 'label' => t('Channel Sources'),
- 'url' => z_root() . '/sources',
- 'selected' => ''
- );
- }
-
- $tabtpl = get_markup_template("generic_links_widget.tpl");
- return replace_macros($tabtpl, array(
- '$title' => t('Settings'),
- '$class' => 'settings-widget',
- '$items' => $tabs,
- ));
-}
-
-
-function widget_mailmenu($arr) {
- if (! local_channel())
- return;
-
-
- return replace_macros(get_markup_template('message_side.tpl'), array(
- '$title' => t('Private Mail Menu'),
- '$combined'=>array(
- 'label' => t('Combined View'),
- 'url' => z_root() . '/mail/combined',
- 'sel' => (argv(1) == 'combined'),
- ),
- '$inbox'=>array(
- 'label' => t('Inbox'),
- 'url' => z_root() . '/mail/inbox',
- 'sel' => (argv(1) == 'inbox'),
- ),
- '$outbox'=>array(
- 'label' => t('Outbox'),
- 'url' => z_root() . '/mail/outbox',
- 'sel' => (argv(1) == 'outbox'),
- ),
- '$new'=>array(
- 'label' => t('New Message'),
- 'url' => z_root() . '/mail/new',
- 'sel'=> (argv(1) == 'new'),
- )
- ));
-}
-
-
-function widget_conversations($arr) {
- if (! local_channel())
- return;
-
- if(argc() > 1) {
-
- switch(argv(1)) {
- case 'combined':
- $mailbox = 'combined';
- $header = t('Conversations');
- break;
- case 'inbox':
- $mailbox = 'inbox';
- $header = t('Received Messages');
- break;
- case 'outbox':
- $mailbox = 'outbox';
- $header = t('Sent Messages');
- break;
- default:
- $mailbox = 'combined';
- $header = t('Conversations');
- break;
- }
-
- require_once('include/message.php');
-
- // private_messages_list() can do other more complicated stuff, for now keep it simple
- $r = private_messages_list(local_channel(), $mailbox, App::$pager['start'], App::$pager['itemspage']);
-
- if(! $r) {
- info( t('No messages.') . EOL);
- return $o;
- }
-
- $messages = array();
-
- foreach($r as $rr) {
-
- $messages[] = array(
- 'mailbox' => $mailbox,
- 'id' => $rr['id'],
- 'from_name' => $rr['from']['xchan_name'],
- 'from_url' => chanlink_hash($rr['from_xchan']),
- 'from_photo' => $rr['from']['xchan_photo_s'],
- 'to_name' => $rr['to']['xchan_name'],
- 'to_url' => chanlink_hash($rr['to_xchan']),
- 'to_photo' => $rr['to']['xchan_photo_s'],
- 'subject' => (($rr['seen']) ? $rr['title'] : '<strong>' . $rr['title'] . '</strong>'),
- 'delete' => t('Delete conversation'),
- 'body' => $rr['body'],
- 'date' => datetime_convert('UTC',date_default_timezone_get(),$rr['created'], 'c'),
- 'seen' => $rr['seen'],
- 'selected' => ((argv(2)) ? (argv(2) == $rr['id']) : ($r[0]['id'] == $rr['id']))
- );
- }
-
- $tpl = get_markup_template('mail_head.tpl');
- $o .= replace_macros($tpl, array(
- '$header' => $header,
- '$messages' => $messages
- ));
-
- //$o .= alt_pager($a,count($r));
-
- }
-
- return $o;
-}
-
-function widget_eventstools($arr) {
- if (! local_channel())
- return;
-
- return replace_macros(get_markup_template('events_tools_side.tpl'), array(
- '$title' => t('Events Tools'),
- '$export' => t('Export Calendar'),
- '$import' => t('Import Calendar'),
- '$submit' => t('Submit')
- ));
-}
-
-function widget_design_tools($arr) {
-
- // mod menu doesn't load a profile. For any modules which load a profile, check it.
- // otherwise local_channel() is sufficient for permissions.
-
- if(App::$profile['profile_uid'])
- if((App::$profile['profile_uid'] != local_channel()) && (! App::$is_sys))
- return '';
-
- if(! local_channel())
- return '';
-
- return design_tools();
-}
-
-function widget_website_portation_tools($arr) {
-
- // mod menu doesn't load a profile. For any modules which load a profile, check it.
- // otherwise local_channel() is sufficient for permissions.
-
- if(App::$profile['profile_uid'])
- if((App::$profile['profile_uid'] != local_channel()) && (! App::$is_sys))
- return '';
-
- if(! local_channel())
- return '';
-
- return website_portation_tools();
-}
-
-function widget_findpeople($arr) {
- return findpeople_widget();
-}
-
-
-function widget_photo_albums($arr) {
-
- if(! App::$profile['profile_uid'])
- return '';
- $channelx = channelx_by_n(App::$profile['profile_uid']);
- if((! $channelx) || (! perm_is_allowed(App::$profile['profile_uid'], get_observer_hash(), 'view_storage')))
- return '';
- require_once('include/photos.php');
- $sortkey = ((array_key_exists('sortkey',$arr)) ? $arr['sortkey'] : 'album');
- $direction = ((array_key_exists('direction',$arr)) ? $arr['direction'] : 'asc');
-
- return photos_album_widget($channelx, App::get_observer(),$sortkey,$direction);
-}
-
-
-function widget_vcard($arr) {
- return vcard_from_xchan('', App::get_observer());
-}
-
-
-/*
- * The following directory widgets are only useful on the directory page
- */
-
-
-function widget_dirsort($arr) {
- return dir_sort_links();
-}
-
-function widget_dirtags($arr) {
- return dir_tagblock(z_root() . '/directory', null);
-}
-
-function widget_menu_preview($arr) {
- if(! App::$data['menu_item'])
- return;
- require_once('include/menu.php');
-
- return menu_render(App::$data['menu_item']);
-}
-
-function widget_chatroom_list($arr) {
-
-
- $r = Zotlabs\Lib\Chatroom::roomlist(App::$profile['profile_uid']);
-
- if($r) {
- return replace_macros(get_markup_template('chatroomlist.tpl'), array(
- '$header' => t('Chatrooms'),
- '$baseurl' => z_root(),
- '$nickname' => App::$profile['channel_address'],
- '$items' => $r,
- '$overview' => t('Overview')
- ));
- }
-}
-
-function widget_chatroom_members() {
- $o = replace_macros(get_markup_template('chatroom_members.tpl'), array(
- '$header' => t('Chat Members')
- ));
-
- return $o;
-}
-
-function widget_wiki_list($arr) {
-
- $channel = channelx_by_n(App::$profile_uid);
-
- $wikis = Zotlabs\Lib\NativeWiki::listwikis($channel,get_observer_hash());
-
- if($wikis) {
- return replace_macros(get_markup_template('wikilist_widget.tpl'), array(
- '$header' => t('Wiki List'),
- '$channel' => $channel['channel_address'],
- '$wikis' => $wikis['wikis']
- ));
- }
- return '';
-}
-
-function widget_wiki_pages($arr) {
-
- $channelname = ((array_key_exists('channel',$arr)) ? $arr['channel'] : '');
- $c = channelx_by_nick($channelname);
-
- $wikiname = '';
- if (array_key_exists('refresh', $arr)) {
- $not_refresh = (($arr['refresh']=== true) ? false : true);
- } else {
- $not_refresh = true;
- }
- $pages = array();
- if (! array_key_exists('resource_id', $arr)) {
- $hide = true;
- } else {
- $p = Zotlabs\Lib\NativeWikiPage::page_list($c['channel_id'],get_observer_hash(),$arr['resource_id']);
-
- if($p['pages']) {
- $pages = $p['pages'];
- $w = $p['wiki'];
- // Wiki item record is $w['wiki']
- $wikiname = $w['urlName'];
- if (!$wikiname) {
- $wikiname = '';
- }
- }
- }
- $can_create = perm_is_allowed(\App::$profile['uid'],get_observer_hash(),'write_pages');
-
- $can_delete = ((local_channel() && (local_channel() == \App::$profile['uid'])) ? true : false);
-
- return replace_macros(get_markup_template('wiki_page_list.tpl'), array(
- '$hide' => $hide,
- '$resource_id' => $arr['resource_id'],
- '$not_refresh' => $not_refresh,
- '$header' => t('Wiki Pages'),
- '$channel' => $channelname,
- '$wikiname' => $wikiname,
- '$pages' => $pages,
- '$canadd' => $can_create,
- '$candel' => $can_delete,
- '$addnew' => t('Add new page'),
- '$pageName' => array('pageName', t('Page name')),
- ));
-}
-
-function widget_wiki_page_history($arr) {
-
- $pageUrlName = ((array_key_exists('pageUrlName', $arr)) ? $arr['pageUrlName'] : '');
- $resource_id = ((array_key_exists('resource_id', $arr)) ? $arr['resource_id'] : '');
-
- $pageHistory = Zotlabs\Lib\NativeWikiPage::page_history(array('channel_id' => App::$profile_uid, 'observer_hash' => get_observer_hash(), 'resource_id' => $resource_id, 'pageUrlName' => $pageUrlName));
- return replace_macros(get_markup_template('nwiki_page_history.tpl'), array(
- '$pageHistory' => $pageHistory['history'],
- '$permsWrite' => $arr['permsWrite'],
- '$name_lbl' => t('Name'),
- '$msg_label' => t('Message','wiki_history')
- ));
-
-}
-
-function widget_bookmarkedchats($arr) {
-
- if(! feature_enabled(App::$profile['profile_uid'],'ajaxchat'))
- return '';
-
- $h = get_observer_hash();
- if(! $h)
- return;
- $r = q("select xchat_url, xchat_desc from xchat where xchat_xchan = '%s' order by xchat_desc",
- dbesc($h)
- );
- if($r) {
- for($x = 0; $x < count($r); $x ++) {
- $r[$x]['xchat_url'] = zid($r[$x]['xchat_url']);
- }
- }
- return replace_macros(get_markup_template('bookmarkedchats.tpl'),array(
- '$header' => t('Bookmarked Chatrooms'),
- '$rooms' => $r
- ));
-}
-
-function widget_suggestedchats($arr) {
-
- if(! feature_enabled(App::$profile['profile_uid'],'ajaxchat'))
- return '';
-
- // There are reports that this tool does not ever remove chatrooms on dead sites,
- // and also will happily link to private chats which you cannot enter.
- // For those reasons, it will be disabled until somebody decides it's worth
- // fixing and comes up with a plan for doing so.
-
- return '';
-
-
- // probably should restrict this to your friends, but then the widget will only work
- // if you are logged in locally.
-
- $h = get_observer_hash();
- if(! $h)
- return;
- $r = q("select xchat_url, xchat_desc, count(xchat_xchan) as total from xchat group by xchat_url, xchat_desc order by total desc, xchat_desc limit 24");
- if($r) {
- for($x = 0; $x < count($r); $x ++) {
- $r[$x]['xchat_url'] = zid($r[$x]['xchat_url']);
- }
- }
- return replace_macros(get_markup_template('bookmarkedchats.tpl'),array(
- '$header' => t('Suggested Chatrooms'),
- '$rooms' => $r
- ));
-}
-
-function widget_item($arr) {
-
- $channel_id = 0;
- if(array_key_exists('channel_id',$arr) && intval($arr['channel_id']))
- $channel_id = intval($arr['channel_id']);
- if(! $channel_id)
- $channel_id = App::$profile_uid;
- if(! $channel_id)
- return '';
-
-
- if((! $arr['mid']) && (! $arr['title']))
- return '';
-
- if(! perm_is_allowed($channel_id, get_observer_hash(), 'view_pages'))
- return '';
-
- require_once('include/security.php');
- $sql_extra = item_permissions_sql($channel_id);
-
- if($arr['title']) {
- $r = q("select item.* from item left join iconfig on item.id = iconfig.iid
- where item.uid = %d and iconfig.cat = 'system' and iconfig.v = '%s'
- and iconfig.k = 'WEBPAGE' and item_type = %d $sql_options $revision limit 1",
- intval($channel_id),
- dbesc($arr['title']),
- intval(ITEM_TYPE_WEBPAGE)
- );
- }
- else {
- $r = q("select * from item where mid = '%s' and uid = %d and item_type = " . intval(ITEM_TYPE_WEBPAGE) . " $sql_extra limit 1",
- dbesc($arr['mid']),
- intval($channel_id)
- );
- }
-
- if(! $r)
- return '';
-
- xchan_query($r);
- $r = fetch_post_tags($r, true);
-
- $o = prepare_page($r[0]);
- return $o;
-}
-
-function widget_clock($arr) {
-
- $miltime = 0;
- if(isset($arr['military']) && $arr['military'])
- $miltime = 1;
-
-$o = <<< EOT
-<div class="widget">
-<h3 class="clockface"></h3>
-<script>
-
-var timerID = null
-var timerRunning = false
-
-function stopclock(){
- if(timerRunning)
- clearTimeout(timerID)
- timerRunning = false
-}
-
-function startclock(){
- stopclock()
- showtime()
-}
-
-function showtime(){
- var now = new Date()
- var hours = now.getHours()
- var minutes = now.getMinutes()
- var seconds = now.getSeconds()
- var military = $miltime
- var timeValue = ""
- if(military)
- timeValue = hours
- else
- timeValue = ((hours > 12) ? hours - 12 : hours)
- timeValue += ((minutes < 10) ? ":0" : ":") + minutes
-// timeValue += ((seconds < 10) ? ":0" : ":") + seconds
- if(! military)
- timeValue += (hours >= 12) ? " P.M." : " A.M."
- $('.clockface').html(timeValue)
- timerID = setTimeout("showtime()",1000)
- timerRunning = true
-}
-
-$(document).ready(function() {
- startclock();
-});
-
-</script>
-</div>
-EOT;
-return $o;
-
-}
-
-/**
- * @brief Widget to display a single photo.
- *
- * @param array $arr associative array with
- * * \e string \b src URL of photo; URL must be an http or https URL
- * * \e boolean \b zrl use zid in URL
- * * \e string \b style CSS string
- *
- * @return string with parsed HTML
- */
-function widget_photo($arr) {
-
- $style = $zrl = false;
-
- if(array_key_exists('src', $arr) && isset($arr['src']))
- $url = $arr['src'];
-
- if(strpos($url, 'http') !== 0)
- return '';
-
- if(array_key_exists('style', $arr) && isset($arr['style']))
- $style = $arr['style'];
-
- // ensure they can't sneak in an eval(js) function
-
- if(strpbrk($style, '(\'"<>') !== false)
- $style = '';
-
- if(array_key_exists('zrl', $arr) && isset($arr['zrl']))
- $zrl = (($arr['zrl']) ? true : false);
-
- if($zrl)
- $url = zid($url);
-
- $o = '<div class="widget">';
-
- $o .= '<img ' . (($zrl) ? ' class="zrl" ' : '')
- . (($style) ? ' style="' . $style . '"' : '')
- . ' src="' . $url . '" alt="' . t('photo/image') . '">';
-
- $o .= '</div>';
-
- return $o;
-}
-
-
-function widget_cover_photo($arr) {
-
- require_once('include/channel.php');
- $o = '';
-
- if(App::$module == 'channel' && $_REQUEST['mid'])
- return '';
-
- $channel_id = 0;
- if(array_key_exists('channel_id', $arr) && intval($arr['channel_id']))
- $channel_id = intval($arr['channel_id']);
- if(! $channel_id)
- $channel_id = App::$profile_uid;
- if(! $channel_id)
- return '';
-
- $channel = channelx_by_n($channel_id);
-
- if(array_key_exists('style', $arr) && isset($arr['style']))
- $style = $arr['style'];
- else
- $style = 'width:100%; height: auto;';
-
- // ensure they can't sneak in an eval(js) function
-
- if(strpbrk($style,'(\'"<>') !== false)
- $style = '';
-
- if(array_key_exists('title', $arr) && isset($arr['title']))
- $title = $arr['title'];
- else
- $title = $channel['channel_name'];
-
- if(array_key_exists('subtitle', $arr) && isset($arr['subtitle']))
- $subtitle = $arr['subtitle'];
- else
- $subtitle = str_replace('@','&#x40;',$channel['xchan_addr']);
-
- $c = get_cover_photo($channel_id,'html');
-
- if($c) {
- $photo_html = (($style) ? str_replace('alt=',' style="' . $style . '" alt=',$c) : $c);
-
- $o = replace_macros(get_markup_template('cover_photo_widget.tpl'),array(
- '$photo_html' => $photo_html,
- '$title' => $title,
- '$subtitle' => $subtitle,
- '$hovertitle' => t('Click to show more'),
- ));
- }
- return $o;
-}
-
-
-function widget_photo_rand($arr) {
-
- require_once('include/photos.php');
- $style = false;
-
- if(array_key_exists('album', $arr) && isset($arr['album']))
- $album = $arr['album'];
- else
- $album = '';
-
- $channel_id = 0;
- if(array_key_exists('channel_id', $arr) && intval($arr['channel_id']))
- $channel_id = intval($arr['channel_id']);
- if(! $channel_id)
- $channel_id = App::$profile_uid;
- if(! $channel_id)
- return '';
-
- $scale = ((array_key_exists('scale',$arr)) ? intval($arr['scale']) : 0);
-
- $ret = photos_list_photos(array('channel_id' => $channel_id),App::get_observer(),$album);
-
- $filtered = array();
- if($ret['success'] && $ret['photos'])
- foreach($ret['photos'] as $p)
- if($p['imgscale'] == $scale)
- $filtered[] = $p['src'];
-
- if($filtered) {
- $e = mt_rand(0, count($filtered) - 1);
- $url = $filtered[$e];
- }
-
- if(strpos($url, 'http') !== 0)
- return '';
-
- if(array_key_exists('style', $arr) && isset($arr['style']))
- $style = $arr['style'];
-
- // ensure they can't sneak in an eval(js) function
-
- if(strpos($style,'(') !== false)
- return '';
-
- $url = zid($url);
-
- $o = '<div class="widget">';
-
- $o .= '<img class="zrl" '
- . (($style) ? ' style="' . $style . '"' : '')
- . ' src="' . $url . '" alt="' . t('photo/image') . '">';
-
- $o .= '</div>';
-
- return $o;
-}
-
-
-function widget_random_block($arr) {
-
- $channel_id = 0;
- if(array_key_exists('channel_id',$arr) && intval($arr['channel_id']))
- $channel_id = intval($arr['channel_id']);
- if(! $channel_id)
- $channel_id = App::$profile_uid;
- if(! $channel_id)
- return '';
-
- if(array_key_exists('contains',$arr))
- $contains = $arr['contains'];
-
- $o = '';
-
- require_once('include/security.php');
- $sql_options = item_permissions_sql($channel_id);
-
- $randfunc = db_getfunc('RAND');
-
- $r = q("select item.* from item left join iconfig on item.id = iconfig.iid
- where item.uid = %d and iconfig.cat = 'system' and iconfig.v like '%s' and iconfig.k = 'BUILDBLOCK' and
- item_type = %d $sql_options order by $randfunc limit 1",
- intval($channel_id),
- dbesc('%' . $contains . '%'),
- intval(ITEM_TYPE_BLOCK)
- );
-
- if($r) {
- $o = '<div class="widget bblock">';
- if($r[0]['title'])
- $o .= '<h3>' . $r[0]['title'] . '</h3>';
-
- $o .= prepare_text($r[0]['body'],$r[0]['mimetype']);
- $o .= '</div>';
- }
-
- return $o;
-}
-
-
-function widget_rating($arr) {
-
-
- $rating_enabled = get_config('system','rating_enabled');
- if(! $rating_enabled) {
- return;
- }
-
- if($arr['target'])
- $hash = $arr['target'];
- else
- $hash = App::$poi['xchan_hash'];
-
- if(! $hash)
- return;
-
- $url = '';
- $remote = false;
-
- if(remote_channel() && ! local_channel()) {
- $ob = App::get_observer();
- if($ob && $ob['xchan_url']) {
- $p = parse_url($ob['xchan_url']);
- if($p) {
- $url = $p['scheme'] . '://' . $p['host'] . (($p['port']) ? ':' . $p['port'] : '');
- $url .= '/rate?f=&target=' . urlencode($hash);
- }
- $remote = true;
- }
- }
-
- $self = false;
-
- if(local_channel()) {
- $channel = App::get_channel();
-
- if($hash == $channel['channel_hash'])
- $self = true;
-
- head_add_js('ratings.js');
-
- }
-
-
- $o = '<div class="widget">';
- $o .= '<h3>' . t('Rating Tools') . '</h3>';
-
- if((($remote) || (local_channel())) && (! $self)) {
- if($remote)
- $o .= '<a class="btn btn-block btn-primary btn-sm" href="' . $url . '"><i class="fa fa-pencil"></i> ' . t('Rate Me') . '</a>';
- else
- $o .= '<div class="btn btn-block btn-primary btn-sm" onclick="doRatings(\'' . $hash . '\'); return false;"><i class="fa fa-pencil"></i> ' . t('Rate Me') . '</div>';
- }
-
- $o .= '<a class="btn btn-block btn-default btn-sm" href="ratings/' . $hash . '"><i class="fa fa-eye"></i> ' . t('View Ratings') . '</a>';
- $o .= '</div>';
-
- return $o;
-
-}
-
-// used by site ratings pages to provide a return link
-function widget_pubsites($arr) {
- if(App::$poi)
- return;
- return '<div class="widget"><ul class="nav nav-pills"><li><a href="pubsites">' . t('Public Hubs') . '</a></li></ul></div>';
-}
-
-
-function widget_forums($arr) {
-
- if(! local_channel())
- return '';
-
- $o = '';
-
- if(is_array($arr) && array_key_exists('limit',$arr))
- $limit = " limit " . intval($limit) . " ";
- else
- $limit = '';
-
- $unseen = 0;
- if(is_array($arr) && array_key_exists('unseen',$arr) && intval($arr['unseen']))
- $unseen = 1;
-
- $perms_sql = item_permissions_sql(local_channel()) . item_normal();
-
- $xf = false;
-
- $x1 = q("select xchan from abconfig where chan = %d and cat = 'their_perms' and k = 'send_stream' and v = '0'",
- intval(local_channel())
- );
- if($x1) {
- $xc = ids_to_querystr($x1,'xchan',true);
- $x2 = q("select xchan from abconfig where chan = %d and cat = 'their_perms' and k = 'tag_deliver' and v = '1' and xchan in (" . $xc . ") ",
- intval(local_channel())
- );
- if($x2)
- $xf = ids_to_querystr($x2,'xchan',true);
- }
-
- $sql_extra = (($xf) ? " and ( xchan_hash in (" . $xf . ") or xchan_pubforum = 1 ) " : " and xchan_pubforum = 1 ");
-
- $r1 = q("select abook_id, xchan_hash, xchan_name, xchan_url, xchan_photo_s from abook left join xchan on abook_xchan = xchan_hash where xchan_deleted = 0 and abook_channel = %d $sql_extra order by xchan_name $limit ",
- intval(local_channel())
- );
- if(! $r1)
- return $o;
-
- $str = '';
-
- // Trying to cram all this into a single query with joins and the proper group by's is tough.
- // There also should be a way to update this via ajax.
-
- for($x = 0; $x < count($r1); $x ++) {
- $r = q("select sum(item_unseen) as unseen from item where owner_xchan = '%s' and uid = %d and item_unseen = 1 $perms_sql ",
- dbesc($r1[$x]['xchan_hash']),
- intval(local_channel())
- );
- if($r)
- $r1[$x]['unseen'] = $r[0]['unseen'];
-
-/**
- * @FIXME
- * This SQL makes the counts correct when you get forum posts arriving from different routes/sources
- * (like personal channels). However the network query for these posts doesn't yet include this
- * correction and it makes the SQL for that query pretty hairy so this is left as a future exercise.
- * It may make more sense in that query to look for the mention in the body rather than another join,
- * but that makes it very inefficient.
- *
- $r = q("select sum(item_unseen) as unseen from item left join term on oid = id where otype = %d and owner_xchan != '%s' and item.uid = %d and url = '%s' and ttype = %d $perms_sql ",
- intval(TERM_OBJ_POST),
- dbesc($r1[$x]['xchan_hash']),
- intval(local_channel()),
- dbesc($r1[$x]['xchan_url']),
- intval(TERM_MENTION)
- );
- if($r)
- $r1[$x]['unseen'] = ((array_key_exists('unseen',$r1[$x])) ? $r1[$x]['unseen'] + $r[0]['unseen'] : $r[0]['unseen']);
- *
- * end @FIXME
- */
-
- }
-
- if($r1) {
- $o .= '<div class="widget">';
- $o .= '<h3>' . t('Forums') . '</h3><ul class="nav nav-pills nav-stacked">';
-
- foreach($r1 as $rr) {
- if($unseen && (! intval($rr['unseen'])))
- continue;
- $o .= '<li><a href="network?f=&pf=1&cid=' . $rr['abook_id'] . '" ><span class="badge pull-right">' . ((intval($rr['unseen'])) ? intval($rr['unseen']) : '') . '</span><img src="' . $rr['xchan_photo_s'] . '" style="width: 16px; height: 16px;" /> ' . $rr['xchan_name'] . '</a></li>';
- }
- $o .= '</ul></div>';
- }
- return $o;
-
-}
-
-
-function widget_tasklist($arr) {
-
- if (! local_channel())
- return;
-
- require_once('include/event.php');
- $o .= '<script>var tasksShowAll = 0; $(document).ready(function() { tasksFetch(); $("#tasklist-new-form").submit(function(event) { event.preventDefault(); $.post( "tasks/new", $("#tasklist-new-form").serialize(), function(data) { tasksFetch(); $("#tasklist-new-summary").val(""); } ); return false; } )});</script>';
- $o .= '<script>function taskComplete(id) { $.post("tasks/complete/"+id, function(data) { tasksFetch();}); }
- function tasksFetch() {
- $.get("tasks/fetch" + ((tasksShowAll) ? "/all" : ""), function(data) {
- $(".tasklist-tasks").html(data.html);
- });
- }
- </script>';
-
- $o .= '<div class="widget">' . '<h3>' . t('Tasks') . '</h3><div class="tasklist-tasks">';
- $o .= '</div><form id="tasklist-new-form" action="" ><input id="tasklist-new-summary" type="text" name="summary" value="" /></form>';
- $o .= '</div>';
- return $o;
-
-}
-
-
-function widget_helpindex($arr) {
-
- $o .= '<div class="widget">';
-
- $level_0 = get_help_content('sitetoc');
- if(! $level_0)
- $level_0 = get_help_content('toc');
-
- $level_0 = preg_replace('/\<ul(.*?)\>/','<ul class="nav nav-pills nav-stacked">',$level_0);
-
- $levels = array();
-
-
- if(argc() > 2) {
- $path = '';
- for($x = 1; $x < argc(); $x ++) {
- $path .= argv($x) . '/';
- $y = get_help_content($path . 'sitetoc');
- if(! $y)
- $y = get_help_content($path . 'toc');
- if($y)
- $levels[] = preg_replace('/\<ul(.*?)\>/','<ul class="nav nav-pills nav-stacked">',$y);
- }
- }
-
- if($level_0)
- $o .= $level_0;
- if($levels) {
- foreach($levels as $l) {
- $o .= '<br /><br />';
- $o .= $l;
- }
- }
-
- $o .= '</div>';
-
- return $o;
-
-}
-
-
-
-function widget_admin($arr) {
-
- /*
- * Side bar links
- */
-
- if(! is_site_admin()) {
- return login(false);
- }
-
- $o = '';
-
- // array( url, name, extra css classes )
-
- $aside = array(
- 'site' => array(z_root() . '/admin/site/', t('Site'), 'site'),
- 'accounts' => array(z_root() . '/admin/accounts/', t('Accounts'), 'accounts', 'pending-update', t('Member registrations waiting for confirmation')),
- 'channels' => array(z_root() . '/admin/channels/', t('Channels'), 'channels'),
- 'security' => array(z_root() . '/admin/security/', t('Security'), 'security'),
- 'features' => array(z_root() . '/admin/features/', t('Features'), 'features'),
- 'plugins' => array(z_root() . '/admin/plugins/', t('Plugins'), 'plugins'),
- 'themes' => array(z_root() . '/admin/themes/', t('Themes'), 'themes'),
- 'queue' => array(z_root() . '/admin/queue', t('Inspect queue'), 'queue'),
- 'profs' => array(z_root() . '/admin/profs', t('Profile Fields'), 'profs'),
- 'dbsync' => array(z_root() . '/admin/dbsync/', t('DB updates'), 'dbsync')
-
- );
-
- /* get plugins admin page */
-
- $r = q("SELECT * FROM addon WHERE plugin_admin = 1");
-
- $plugins = array();
- if($r) {
- foreach ($r as $h){
- $plugin = $h['aname'];
- $plugins[] = array(z_root() . '/admin/plugins/' . $plugin, $plugin, 'plugin');
- // temp plugins with admin
- App::$plugins_admin[] = $plugin;
- }
- }
-
- $logs = array(z_root() . '/admin/logs/', t('Logs'), 'logs');
-
- $arr = array('links' => $aside,'plugins' => $plugins,'logs' => $logs);
- call_hooks('admin_aside',$arr);
-
- $o .= replace_macros(get_markup_template('admin_aside.tpl'), array(
- '$admin' => $aside,
- '$admtxt' => t('Admin'),
- '$plugadmtxt' => t('Plugin Features'),
- '$plugins' => $plugins,
- '$logtxt' => t('Logs'),
- '$logs' => $logs,
- '$h_pending' => t('Member registrations waiting for confirmation'),
- '$admurl'=> z_root() . '/admin/'
- ));
-
- return $o;
-
-}
-
-
-
-function widget_album($args) {
-
- $owner_uid = App::$profile_uid;
- $sql_extra = permissions_sql($owner_uid);
-
-
- if(! perm_is_allowed($owner_uid,get_observer_hash(),'view_storage'))
- return '';
-
- if($args['album'])
- $album = $args['album'];
- if($args['title'])
- $title = $args['title'];
-
- /**
- * This may return incorrect permissions if you have multiple directories of the same name.
- * It is a limitation of the photo table using a name for a photo album instead of a folder hash
- */
-
- if($album) {
- $x = q("select hash from attach where filename = '%s' and uid = %d limit 1",
- dbesc($album),
- intval($owner_uid)
- );
- if($x) {
- $y = attach_can_view_folder($owner_uid,get_observer_hash(),$x[0]['hash']);
- if(! $y)
- return '';
- }
- }
-
- $order = 'DESC';
-
- $r = q("SELECT p.resource_id, p.id, p.filename, p.mimetype, p.imgscale, p.description, p.created FROM photo p INNER JOIN
- (SELECT resource_id, max(imgscale) imgscale FROM photo WHERE uid = %d AND album = '%s' AND imgscale <= 4 AND photo_usage IN ( %d, %d ) $sql_extra GROUP BY resource_id) ph
- ON (p.resource_id = ph.resource_id AND p.imgscale = ph.imgscale)
- ORDER BY created $order ",
- intval($owner_uid),
- dbesc($album),
- intval(PHOTO_NORMAL),
- intval(PHOTO_PROFILE)
- );
-
- //edit album name
- $album_edit = null;
-
- $photos = array();
- if($r) {
- $twist = 'rotright';
- foreach($r as $rr) {
-
- if($twist == 'rotright')
- $twist = 'rotleft';
- else
- $twist = 'rotright';
-
- $ext = $phototypes[$rr['mimetype']];
-
- $imgalt_e = $rr['filename'];
- $desc_e = $rr['description'];
-
- $imagelink = (z_root() . '/photos/' . App::$profile['channel_address'] . '/image/' . $rr['resource_id']);
-
-
- $photos[] = array(
- 'id' => $rr['id'],
- 'twist' => ' ' . $twist . rand(2,4),
- 'link' => $imagelink,
- 'title' => t('View Photo'),
- 'src' => z_root() . '/photo/' . $rr['resource_id'] . '-' . $rr['imgscale'] . '.' .$ext,
- 'alt' => $imgalt_e,
- 'desc'=> $desc_e,
- 'ext' => $ext,
- 'hash'=> $rr['resource_id'],
- 'unknown' => t('Unknown')
- );
- }
- }
-
-
- $tpl = get_markup_template('photo_album.tpl');
- $o .= replace_macros($tpl, array(
- '$photos' => $photos,
- '$album' => (($title) ? $title : $album),
- '$album_id' => rand(),
- '$album_edit' => array(t('Edit Album'), $album_edit),
- '$can_post' => false,
- '$upload' => array(t('Upload'), z_root() . '/photos/' . App::$profile['channel_address'] . '/upload/' . bin2hex($album)),
- '$order' => false,
- '$upload_form' => $upload_form,
- '$usage' => $usage_message
- ));
-
- return $o;
-}
-
diff --git a/include/xchan.php b/include/xchan.php
index 12eb674fa..8c9c09c72 100644
--- a/include/xchan.php
+++ b/include/xchan.php
@@ -137,3 +137,83 @@ function xchan_fetch($arr) {
}
+function xchan_keychange_table($table,$column,$oldxchan,$newxchan) {
+ $r = q("update $table set $column = '%s' where $column = '%s'",
+ dbesc($newxchan['xchan_hash']),
+ dbesc($oldxchan['xchan_hash'])
+ );
+ return $r;
+}
+
+function xchan_keychange_acl($table,$column,$oldxchan,$newxchan) {
+
+ $allow = (($table === 'channel') ? 'channel_allow_cid' : 'allow_cid');
+ $deny = (($table === 'channel') ? 'channel_deny_cid' : 'deny_cid');
+
+
+ $r = q("select $column, $allow, $deny from $table where ($allow like '%s' or $deny like '%s') ",
+ dbesc('<' . $oldxchan['xchan_hash'] . '>'),
+ dbesc('<' . $oldxchan['xchan_hash'] . '>')
+ );
+
+ if($r) {
+ foreach($r as $rv) {
+ $z = q("update $table set $allow = '%s', $deny = '%s' where $column = %d",
+ dbesc(str_replace('<' . $oldxchan['xchan_hash'] . '>', '<' . $newxchan['xchan_hash'] . '>',
+ $rv[$allow])),
+ dbesc(str_replace('<' . $oldxchan['xchan_hash'] . '>', '<' . $newxchan['xchan_hash'] . '>',
+ $rv[$deny])),
+ intval($rv[$column])
+ );
+ }
+ }
+ return $z;
+}
+
+
+function xchan_change_key($oldx,$newx,$data) {
+
+ $tables = [
+ 'abook' => 'abook_xchan',
+ 'abconfig' => 'xchan',
+ 'group_member' => 'xchan',
+ 'chat' => 'chat_xchan',
+ 'chatpresence' => 'cp_xchan',
+ 'event' => 'event_xchan',
+ 'item' => 'owner_xchan',
+ 'item' => 'author_xchan',
+ 'item' => 'source_xchan',
+ 'mail' => 'from_xchan',
+ 'mail' => 'to_xchan',
+ 'shares' => 'share_xchan',
+ 'source' => 'src_channel_xchan',
+ 'source' => 'src_xchan',
+ 'xchat' => 'xchat_xchan',
+ 'xconfig' => 'xchan',
+ 'xign' => 'xchan',
+ 'xlink' => 'xlink_xchan',
+ 'xprof' => 'xprof_hash',
+ 'xtag' => 'xtag_hash'
+ ];
+
+
+ $acls = [
+ 'channel' => 'channel_id',
+ 'attach' => 'id',
+ 'chatroom' => 'cr_id',
+ 'event' => 'id',
+ 'item' => 'id',
+ 'menu_item' => 'mitem_id',
+ 'obj' => 'obj_id',
+ 'photo' => 'id'
+ ];
+
+
+ foreach($tables as $k => $v) {
+ xchan_keychange_table($k,$v,$oldx,$newx);
+ }
+
+ foreach($acls as $k => $v) {
+ xchan_keychange_acl($k,$v,$oldx,$newx);
+ }
+} \ No newline at end of file
diff --git a/include/zid.php b/include/zid.php
index f5df1c611..ce9f70385 100644
--- a/include/zid.php
+++ b/include/zid.php
@@ -60,7 +60,7 @@ function zid($s,$address = '') {
/**
* @FIXME checking against our own channel url is no longer reliable. We may have a lot
- * of urls attached to out channel. Should probably match against our site, since we
+ * of urls attached to our channel. Should probably match against our site, since we
* will not need to remote authenticate on our own site anyway.
*/
@@ -81,6 +81,10 @@ function zid($s,$address = '') {
}
+function strip_query_param($s,$param) {
+ return preg_replace('/[\?&]' . $param . '=(.*?)(&|$)/ism','$2',$s);
+}
+
function strip_zids($s) {
return preg_replace('/[\?&]zid=(.*?)(&|$)/ism','$2',$s);
}
@@ -230,3 +234,76 @@ function red_zrlify_img_callback($matches) {
return $matches[0];
}
+function owt_init($token) {
+
+ \Zotlabs\Zot\Verify::purge('owt','3 MINUTE');
+
+ $ob_hash = \Zotlabs\Zot\Verify::get_meta('owt',0,$token);
+
+ if($ob_hash === false) {
+ return;
+ }
+
+ $r = q("select * from hubloc left join xchan on xchan_hash = hubloc_hash
+ where hubloc_addr = '%s' order by hubloc_id desc",
+ dbesc($ob_hash)
+ );
+
+ if(! $r) {
+ // finger them if they can't be found.
+ $j = \Zotlabs\Zot\Finger::run($ob_hash, null);
+ if ($j['success']) {
+ import_xchan($j);
+ $r = q("select * from hubloc left join xchan on xchan_hash = hubloc_hash
+ where hubloc_addr = '%s' order by hubloc_id desc",
+ dbesc($ob_hash)
+ );
+ }
+ }
+ if(! $r) {
+ logger('owt: unable to finger ' . $ob_hash);
+ return;
+ }
+ $hubloc = $r[0];
+
+ $_SESSION['authenticated'] = 1;
+
+ $delegate_success = false;
+ if($_REQUEST['delegate']) {
+ $r = q("select * from channel left join xchan on channel_hash = xchan_hash where xchan_addr = '%s' limit 1",
+ dbesc($_REQUEST['delegate'])
+ );
+ if ($r && intval($r[0]['channel_id'])) {
+ $allowed = perm_is_allowed($r[0]['channel_id'],$hubloc['xchan_hash'],'delegate');
+ if($allowed) {
+ $_SESSION['delegate_channel'] = $r[0]['channel_id'];
+ $_SESSION['delegate'] = $hubloc['xchan_hash'];
+ $_SESSION['account_id'] = intval($r[0]['channel_account_id']);
+ require_once('include/security.php');
+ // this will set the local_channel authentication in the session
+ change_channel($r[0]['channel_id']);
+ $delegate_success = true;
+ }
+ }
+ }
+
+ if (! $delegate_success) {
+ // normal visitor (remote_channel) login session credentials
+ $_SESSION['visitor_id'] = $hubloc['xchan_hash'];
+ $_SESSION['my_url'] = $hubloc['xchan_url'];
+ $_SESSION['my_address'] = $hubloc['hubloc_addr'];
+ $_SESSION['remote_hub'] = $hubloc['hubloc_url'];
+ $_SESSION['DNT'] = 1;
+ }
+
+ $arr = array('xchan' => $hubloc, 'url' => \App::$query_string, 'session' => $_SESSION);
+ call_hooks('magic_auth_success',$arr);
+ \App::set_observer($hubloc);
+ require_once('include/security.php');
+ \App::set_groups(init_groups_visitor($_SESSION['visitor_id']));
+ if(! get_config('system','hide_owa_greeting'))
+ info(sprintf( t('OpenWebAuth: %1$s welcomes %2$s'),\App::get_hostname(), $hubloc['xchan_name']));
+ logger('OpenWebAuth: auth success from ' . $hubloc['xchan_addr']);
+
+
+} \ No newline at end of file
diff --git a/include/zot.php b/include/zot.php
index 736712c81..dad30dbb0 100644
--- a/include/zot.php
+++ b/include/zot.php
@@ -31,9 +31,9 @@ require_once('include/perm_upgrade.php');
* @param string $channel_nick a unique nickname of controlling entity
* @returns string
*/
+
function zot_new_uid($channel_nick) {
$rawstr = z_root() . '/' . $channel_nick . '.' . mt_rand();
-
return(base64url_encode(hash('whirlpool', $rawstr, true), true));
}
@@ -49,6 +49,7 @@ function zot_new_uid($channel_nick) {
* @param string $guid
* @param string $guid_sig
*/
+
function make_xchan_hash($guid, $guid_sig) {
return base64url_encode(hash('whirlpool', $guid . $guid_sig, true));
}
@@ -62,17 +63,17 @@ function make_xchan_hash($guid, $guid_sig) {
* @param string $hash - xchan_hash
* @returns array of hubloc (hub location structures)
* * \b hubloc_id int
- * * \b hubloc_guid char(255)
+ * * \b hubloc_guid char(191)
* * \b hubloc_guid_sig text
- * * \b hubloc_hash char(255)
- * * \b hubloc_addr char(255)
+ * * \b hubloc_hash char(191)
+ * * \b hubloc_addr char(191)
* * \b hubloc_flags int
* * \b hubloc_status int
- * * \b hubloc_url char(255)
+ * * \b hubloc_url char(191)
* * \b hubloc_url_sig text
- * * \b hubloc_host char(255)
- * * \b hubloc_callback char(255)
- * * \b hubloc_connect char(255)
+ * * \b hubloc_host char(191)
+ * * \b hubloc_callback char(191)
+ * * \b hubloc_connect char(191)
* * \b hubloc_sitekey text
* * \b hubloc_updated datetime
* * \b hubloc_connected datetime
@@ -97,7 +98,7 @@ function zot_get_hublocs($hash) {
* @param array $channel
* sender channel structure
* @param string $type
- * packet type: one of 'ping', 'pickup', 'purge', 'refresh', 'force_refresh', 'notify', 'auth_check'
+ * packet type: one of 'ping', 'pickup', 'purge', 'refresh', 'keychange', 'force_refresh', 'notify', 'auth_check'
* @param array $recipients
* envelope information, array ( 'guid' => string, 'guid_sig' => string ); empty for public posts
* @param string $remote_key
@@ -111,18 +112,21 @@ function zot_get_hublocs($hash) {
*/
function zot_build_packet($channel, $type = 'notify', $recipients = null, $remote_key = null, $methods = '', $secret = null, $extra = null) {
+ $sig_method = get_config('system','signature_algorithm','sha256');
+
$data = [
'type' => $type,
'sender' => [
'guid' => $channel['channel_guid'],
- 'guid_sig' => base64url_encode(rsa_sign($channel['channel_guid'],$channel['channel_prvkey'])),
+ 'guid_sig' => base64url_encode(rsa_sign($channel['channel_guid'],$channel['channel_prvkey'],$sig_method)),
'url' => z_root(),
- 'url_sig' => base64url_encode(rsa_sign(z_root(),$channel['channel_prvkey'])),
+ 'url_sig' => base64url_encode(rsa_sign(z_root(),$channel['channel_prvkey'],$sig_method)),
'sitekey' => get_config('system','pubkey')
],
'callback' => '/post',
- 'version' => ZOT_REVISION,
- 'encryption' => crypto_methods()
+ 'version' => Zotlabs\Lib\System::get_zot_revision(),
+ 'encryption' => crypto_methods(),
+ 'signing' => signing_methods()
];
if ($recipients) {
@@ -133,8 +137,8 @@ function zot_build_packet($channel, $type = 'notify', $recipients = null, $remot
}
if ($secret) {
- $data['secret'] = $secret;
- $data['secret_sig'] = base64url_encode(rsa_sign($secret,$channel['channel_prvkey']));
+ $data['secret'] = preg_replace('/[^0-9a-fA-F]/','',$secret);
+ $data['secret_sig'] = base64url_encode(rsa_sign($secret,$channel['channel_prvkey'],$sig_method));
}
if ($extra) {
@@ -165,9 +169,6 @@ function zot_build_packet($channel, $type = 'notify', $recipients = null, $remot
function zot_best_algorithm($methods) {
- if(\Zotlabs\Lib\System::get_server_role() !== 'pro')
- return 'aes256cbc';
-
$x = [ 'methods' => $methods, 'result' => '' ];
call_hooks('zot_best_algorithm',$x);
if($x['result'])
@@ -311,9 +312,8 @@ function zot_refresh($them, $channel = null, $force = false) {
logger('zot_refresh: ' . $url, LOGGER_DATA, LOG_INFO);
- $result = z_post_url($url . $rhs,$postvars);
- logger('zot_refresh: zot-info: ' . print_r($result,true), LOGGER_DATA, LOG_DEBUG);
+ $result = z_post_url($url . $rhs,$postvars);
if ($result['success']) {
@@ -324,6 +324,8 @@ function zot_refresh($them, $channel = null, $force = false) {
return false;
}
+ logger('zot-info: ' . print_r($result,true), LOGGER_DATA, LOG_DEBUG);
+
$signed_token = ((is_array($j) && array_key_exists('signed_token',$j)) ? $j['signed_token'] : null);
if($signed_token) {
$valid = rsa_verify('token.' . $token,base64url_decode($signed_token),$j['key']);
@@ -334,10 +336,7 @@ function zot_refresh($them, $channel = null, $force = false) {
}
else {
logger('No signed token from ' . $url . $rhs, LOGGER_NORMAL, LOG_WARNING);
- // after 2017-01-01 this will be a hard error unless you over-ride it.
- if((time() > 1483228800) && (! get_config('system','allow_unsigned_zotfinger'))) {
- return false;
- }
+ return false;
}
$x = import_xchan($j, (($force) ? UPDATE_FLAGS_FORCED : UPDATE_FLAGS_UPDATED));
@@ -362,8 +361,6 @@ function zot_refresh($them, $channel = null, $force = false) {
else
$permissions = $j['permissions'];
- $connected_set = false;
-
if($permissions && is_array($permissions)) {
$old_read_stream_perm = get_abconfig($channel['channel_id'],$x['hash'],'their_perms','view_stream');
@@ -535,7 +532,7 @@ function zot_gethub($arr, $multiple = false) {
}
$limit = (($multiple) ? '' : ' limit 1 ');
- $sitekey = ((array_key_exists('sitekey',$arr) && $arr['sitekey']) ? " and hubloc_sitekey = '" . protect_sprintf($arr['sitekey']) . "' " : '');
+ $sitekey = ((array_key_exists('sitekey',$arr) && $arr['sitekey']) ? " and hubloc_sitekey = '" . dbesc(protect_sprintf($arr['sitekey'])) . "' " : '');
$r = q("select hubloc.*, site.site_crypto from hubloc left join site on hubloc_url = site_url
where hubloc_guid = '%s' and hubloc_guid_sig = '%s'
@@ -581,6 +578,8 @@ function zot_register_hub($arr) {
if($arr['url'] && $arr['url_sig'] && $arr['guid'] && $arr['guid_sig']) {
+ $sig_methods = ((array_key_exists('signing',$arr) && is_array($arr['signing'])) ? $arr['signing'] : [ 'sha256' ]);
+
$guid_hash = make_xchan_hash($arr['guid'],$arr['guid_sig']);
$url = $arr['url'] . '/.well-known/zot-info/?f=&guid_hash=' . $guid_hash;
@@ -600,17 +599,18 @@ function zot_register_hub($arr) {
* our current communication.
*/
- if((rsa_verify($arr['guid'],base64url_decode($arr['guid_sig']),$record['key']))
- && (rsa_verify($arr['url'],base64url_decode($arr['url_sig']),$record['key']))
+ foreach($sig_methods as $method) {
+ if((rsa_verify($arr['guid'],base64url_decode($arr['guid_sig']),$record['key'],$method))
+ && (rsa_verify($arr['url'],base64url_decode($arr['url_sig']),$record['key'],$method))
&& ($arr['guid'] === $record['guid'])
&& ($arr['guid_sig'] === $record['guid_sig'])) {
-
- $c = import_xchan($record);
- if($c['success'])
- $result['success'] = true;
- }
- else {
- logger('zot_register_hub: failure to verify returned packet.');
+ $c = import_xchan($record);
+ if($c['success'])
+ $result['success'] = true;
+ }
+ else {
+ logger('zot_register_hub: failure to verify returned packet using ' . $method);
+ }
}
}
}
@@ -663,8 +663,19 @@ function import_xchan($arr,$ud_flags = UPDATE_FLAGS_UPDATED, $ud_arr = null) {
$import_photos = false;
- if(! rsa_verify($arr['guid'],base64url_decode($arr['guid_sig']),$arr['key'])) {
- logger('import_xchan: Unable to verify channel signature for ' . $arr['address']);
+ $sig_methods = ((array_key_exists('signing',$arr) && is_array($arr['signing'])) ? $arr['signing'] : [ 'sha256' ]);
+ $verified = false;
+
+ foreach($sig_methods as $method) {
+ if(! rsa_verify($arr['guid'],base64url_decode($arr['guid_sig']),$arr['key'],$method)) {
+ logger('import_xchan: Unable to verify channel signature for ' . $arr['address'] . ' using ' . $method);
+ continue;
+ }
+ else {
+ $verified = true;
+ }
+ }
+ if(! $verified) {
$ret['message'] = t('Unable to verify channel signature');
return $ret;
}
@@ -706,6 +717,16 @@ function import_xchan($arr,$ud_flags = UPDATE_FLAGS_UPDATED, $ud_arr = null) {
if(intval($r[0]['xchan_pubforum']) != intval($arr['public_forum']))
$pubforum_changed = 1;
+ if($arr['protocols']) {
+ $protocols = implode(',',$arr['protocols']);
+ if($protocols !== 'zot') {
+ set_xconfig($xchan_hash,'system','protocols',$protocols);
+ }
+ else {
+ del_xconfig($xchan_hash,'system','protocols');
+ }
+ }
+
if(($r[0]['xchan_name_date'] != $arr['name_updated'])
|| ($r[0]['xchan_connurl'] != $arr['connections_url'])
|| ($r[0]['xchan_addr'] != $arr['address'])
@@ -923,7 +944,7 @@ function import_xchan($arr,$ud_flags = UPDATE_FLAGS_UPDATED, $ud_arr = null) {
}
elseif(! $ud_flags) {
// nothing changed but we still need to update the updates record
- q("update updates set ud_flags = ( ud_flags | %d ) where ud_addr = '%s' and not (ud_flags & %d)>0 ",
+ q("update updates set ud_flags = ( ud_flags | %d ) where ud_addr = '%s' and not (ud_flags & %d) > 0 ",
intval(UPDATE_FLAGS_UPDATED),
dbesc($address),
intval(UPDATE_FLAGS_UPDATED)
@@ -965,6 +986,18 @@ function zot_process_response($hub, $arr, $outq) {
}
if(is_array($x) && array_key_exists('delivery_report',$x) && is_array($x['delivery_report'])) {
+
+ if(array_key_exists('iv',$x['delivery_report'])) {
+ $j = crypto_unencapsulate($x['delivery_report'],get_config('system','prvkey'));
+ if($j) {
+ $x['delivery_report'] = json_decode($j,true);
+ }
+ if(! (is_array($x['delivery_report']) && count($x['delivery_report']))) {
+ logger('encrypted delivery report could not be decrypted');
+ return;
+ }
+ }
+
foreach($x['delivery_report'] as $xx) {
if(is_array($xx) && array_key_exists('message_id',$xx) && delivery_report_is_storable($xx)) {
q("insert into dreport ( dreport_mid, dreport_site, dreport_recip, dreport_result, dreport_time, dreport_xchan ) values ( '%s', '%s','%s','%s','%s','%s' ) ",
@@ -1036,13 +1069,15 @@ function zot_fetch($arr) {
foreach($ret_hubs as $ret_hub) {
+ $secret = substr(preg_replace('/[^0-9a-fA-F]/','',$arr['secret']),0,64);
+
$data = [
'type' => 'pickup',
'url' => z_root(),
'callback_sig' => base64url_encode(rsa_sign(z_root() . '/post', get_config('system','prvkey'))),
'callback' => z_root() . '/post',
- 'secret' => $arr['secret'],
- 'secret_sig' => base64url_encode(rsa_sign($arr['secret'], get_config('system','prvkey')))
+ 'secret' => $secret,
+ 'secret_sig' => base64url_encode(rsa_sign($secret, get_config('system','prvkey')))
];
$algorithm = zot_best_algorithm($ret_hub['site_crypto']);
@@ -1052,8 +1087,11 @@ function zot_fetch($arr) {
$result = zot_import($fetch, $arr['sender']['url']);
- if($result)
+ if($result) {
+ $result = crypto_encapsulate(json_encode($result),$ret_hub['hubloc_sitekey'], $algorithm);
return $result;
+ }
+
}
return;
@@ -1332,8 +1370,10 @@ function public_recips($msg) {
$include_sys = false;
if($msg['message']['type'] === 'activity') {
- if(! get_config('system','disable_discover_tab'))
+ $disable_discover_tab = get_config('system','disable_discover_tab') || get_config('system','disable_discover_tab') === false;
+ if(! $disable_discover_tab)
$include_sys = true;
+
$perm = 'send_stream';
if(array_key_exists('flags',$msg['message']) && in_array('thread_parent', $msg['message']['flags'])) {
@@ -1401,7 +1441,7 @@ function public_recips($msg) {
if($msg['message']['tags']) {
if(is_array($msg['message']['tags']) && $msg['message']['tags']) {
foreach($msg['message']['tags'] as $tag) {
- if(($tag['type'] === 'mention') && (strpos($tag['url'],z_root()) !== false)) {
+ if(($tag['type'] === 'mention' || $tag['type'] === 'forum') && (strpos($tag['url'],z_root()) !== false)) {
$address = basename($tag['url']);
if($address) {
$z = q("select channel_hash as hash from channel where channel_address = '%s'
@@ -1767,7 +1807,7 @@ function process_delivery($sender, $arr, $deliveries, $relay, $public = false, $
$result[] = $DR->get();
}
else {
- update_imported_item($sender,$arr,$r[0],$channel['channel_id'],$tag_delivery);
+ $item_result = update_imported_item($sender,$arr,$r[0],$channel['channel_id'],$tag_delivery);
$DR->update('updated');
$result[] = $DR->get();
if(! $relay)
@@ -1816,6 +1856,14 @@ function process_delivery($sender, $arr, $deliveries, $relay, $public = false, $
}
}
+ // preserve conversations with which you are involved from expiration
+
+ $stored = (($item_result && $item_result['item']) ? $item_result['item'] : false);
+ if((is_array($stored)) && ($stored['id'] != $stored['parent'])
+ && ($stored['author_xchan'] === $channel['channel_hash'])) {
+ retain_item($stored['item']['parent']);
+ }
+
if($relay && $item_id) {
logger('process_delivery: invoking relay');
Zotlabs\Daemon\Master::Summon(array('Notifier','relay',intval($item_id)));
@@ -1952,6 +2000,8 @@ function update_imported_item($sender, $item, $orig, $uid, $tag_delivery) {
logger('update_imported_item: failed: ' . $x['message']);
else
logger('update_imported_item');
+
+ return $x;
}
/**
@@ -2243,9 +2293,6 @@ function check_location_move($sender_hash,$locations) {
if(! $locations)
return;
- if(get_config('system','server_role') !== 'basic')
- return;
-
if(count($locations) != 1)
return;
@@ -2830,7 +2877,7 @@ function import_site($arr, $pubkey) {
$access_policy = ACCESS_PRIVATE;
if($access_policy != ACCESS_PRIVATE) {
- $x = z_fetch_url($arr['url'] . '/siteinfo/json');
+ $x = z_fetch_url($arr['url'] . '/siteinfo.json');
if(! $x['success'])
$access_policy = ACCESS_PRIVATE;
}
@@ -2854,8 +2901,14 @@ function import_site($arr, $pubkey) {
$site_directory = DIRECTORY_MODE_NORMAL;
}
+ $site_flags = $site_directory;
+
+ if(array_key_exists('zot',$arr)) {
+ set_sconfig($arr['url'],'system','zot_version',$arr['zot']);
+ }
+
if($exists) {
- if(($siterecord['site_flags'] != $site_directory)
+ if(($siterecord['site_flags'] != $site_flags)
|| ($siterecord['site_access'] != $access_policy)
|| ($siterecord['site_directory'] != $directory_url)
|| ($siterecord['site_sellpage'] != $sellpage)
@@ -2875,7 +2928,7 @@ function import_site($arr, $pubkey) {
$r = q("update site set site_dead = 0, site_location = '%s', site_flags = %d, site_access = %d, site_directory = '%s', site_register = %d, site_update = '%s', site_sellpage = '%s', site_realm = '%s', site_type = %d, site_project = '%s', site_version = '%s', site_crypto = '%s'
where site_url = '%s'",
dbesc($site_location),
- intval($site_directory),
+ intval($site_flags),
intval($access_policy),
dbesc($directory_url),
intval($register_policy),
@@ -2903,22 +2956,24 @@ function import_site($arr, $pubkey) {
else {
$update = true;
- $r = q("insert into site ( site_location, site_url, site_access, site_flags, site_update, site_directory, site_register, site_sellpage, site_realm, site_type, site_project, site_version, site_crypto )
- values ( '%s', '%s', %d, %d, '%s', '%s', %d, '%s', '%s', %d, '%s', '%s', '%s' )",
- dbesc($site_location),
- dbesc($url),
- intval($access_policy),
- intval($site_directory),
- dbesc(datetime_convert()),
- dbesc($directory_url),
- intval($register_policy),
- dbesc($sellpage),
- dbesc($site_realm),
- intval(SITE_TYPE_ZOT),
- dbesc($site_project),
- dbesc($site_version),
- dbesc($site_crypto)
+ $r = site_store_lowlevel(
+ [
+ 'site_location' => $site_location,
+ 'site_url' => $url,
+ 'site_access' => intval($access_policy),
+ 'site_flags' => intval($site_flags),
+ 'site_update' => datetime_convert(),
+ 'site_directory' => $directory_url,
+ 'site_register' => intval($register_policy),
+ 'site_sellpage' => $sellpage,
+ 'site_realm' => $site_realm,
+ 'site_type' => intval(SITE_TYPE_ZOT),
+ 'site_project' => $site_project,
+ 'site_version' => $site_version,
+ 'site_crypto' => $site_crypto
+ ]
);
+
if(! $r) {
logger('import_site: record create failed. ' . print_r($arr,true));
}
@@ -2939,13 +2994,14 @@ function import_site($arr, $pubkey) {
function build_sync_packet($uid = 0, $packet = null, $groups_changed = false) {
- if(get_config('system','server_role') === 'basic')
- return;
logger('build_sync_packet');
- if($packet)
- logger('packet: ' . print_r($packet, true),LOGGER_DATA, LOG_DEBUG);
+
+ $keychange = (($packet && array_key_exists('keychange',$packet)) ? true : false);
+ if($keychange) {
+ logger('keychange sync');
+ }
if(! $uid)
$uid = local_channel();
@@ -2961,6 +3017,9 @@ function build_sync_packet($uid = 0, $packet = null, $groups_changed = false) {
$channel = $r[0];
+ unset($channel['channel_password']);
+ unset($channel['channel_salt']);
+
translate_channel_perms_outbound($channel);
if($packet && array_key_exists('abook',$packet) && $packet['abook']) {
for($x = 0; $x < count($packet['abook']); $x ++) {
@@ -2968,12 +3027,11 @@ function build_sync_packet($uid = 0, $packet = null, $groups_changed = false) {
}
}
-
if(intval($channel['channel_removed']))
return;
$h = q("select hubloc.*, site.site_crypto from hubloc left join site on site_url = hubloc_url where hubloc_hash = '%s' and hubloc_deleted = 0",
- dbesc($channel['channel_hash'])
+ dbesc(($keychange) ? $packet['keychange']['old_hash'] : $channel['channel_hash'])
);
if(! $h)
@@ -3005,6 +3063,9 @@ function build_sync_packet($uid = 0, $packet = null, $groups_changed = false) {
$env_recips = array();
$env_recips[] = array('guid' => $r[0]['xchan_guid'],'guid_sig' => $r[0]['xchan_guid_sig']);
+ if($packet)
+ logger('packet: ' . print_r($packet, true),LOGGER_DATA, LOG_DEBUG);
+
$info = (($packet) ? $packet : array());
$info['type'] = 'channel_sync';
$info['encoding'] = 'red'; // note: not zot, this packet is very platform specific
@@ -3028,7 +3089,15 @@ function build_sync_packet($uid = 0, $packet = null, $groups_changed = false) {
// don't pass these elements, they should not be synchronised
- $disallowed = array('channel_id','channel_account_id','channel_primary','channel_prvkey','channel_address','channel_deleted','channel_removed','channel_system');
+
+ $disallowed = [
+ 'channel_id','channel_account_id','channel_primary','channel_address',
+ 'channel_deleted','channel_removed','channel_system'
+ ];
+
+ if(! $keychange) {
+ $disallowed[] = 'channel_prvkey';
+ }
if(in_array($k,$disallowed))
continue;
@@ -3088,19 +3157,18 @@ function build_sync_packet($uid = 0, $packet = null, $groups_changed = false) {
function process_channel_sync_delivery($sender, $arr, $deliveries) {
- if(get_config('system','server_role') === 'basic')
- return;
-
require_once('include/import.php');
/** @FIXME this will sync red structures (channel, pconfig and abook).
Eventually we need to make this application agnostic. */
- $result = array();
+ $result = [];
+
+ $keychange = ((array_key_exists('keychange',$arr)) ? true : false);
foreach ($deliveries as $d) {
$r = q("select * from channel where channel_hash = '%s' limit 1",
- dbesc($d['hash'])
+ dbesc(($keychange) ? $arr['keychange']['old_hash'] : $d['hash'])
);
if (! $r) {
@@ -3119,6 +3187,94 @@ function process_channel_sync_delivery($sender, $arr, $deliveries) {
continue;
}
+ if($keychange) {
+ // verify the keychange operation
+ if(! rsa_verify($arr['channel']['channel_pubkey'],base64url_decode($arr['keychange']['new_sig']),$channel['channel_prvkey'])) {
+ logger('sync keychange: verification failed');
+ continue;
+ }
+
+ $sig = base64url_encode(rsa_sign($channel['channel_guid'],$arr['channel']['channel_prvkey']));
+ $hash = make_xchan_hash($channel['channel_guid'],$sig);
+
+
+ $r = q("update channel set channel_prvkey = '%s', channel_pubkey = '%s', channel_guid_sig = '%s',
+ channel_hash = '%s' where channel_id = %d",
+ dbesc($arr['channel']['channel_prvkey']),
+ dbesc($arr['channel']['channel_pubkey']),
+ dbesc($sig),
+ dbesc($hash),
+ intval($channel['channel_id'])
+ );
+ if(! $r) {
+ logger('keychange sync: channel update failed');
+ continue;
+ }
+
+ $r = q("select * from channel where channel_id = %d",
+ intval($channel['channel_id'])
+ );
+
+ if(! $r) {
+ logger('keychange sync: channel retrieve failed');
+ continue;
+ }
+
+ $channel = $r[0];
+
+ $h = q("select * from hubloc where hubloc_hash = '%s' and hubloc_url = '%s' ",
+ dbesc($arr['keychange']['old_hash']),
+ dbesc(z_root())
+ );
+
+ if($h) {
+ foreach($h as $hv) {
+ $hv['hubloc_guid_sig'] = $sig;
+ $hv['hubloc_hash'] = $hash;
+ $hv['hubloc_url_sig'] = base64url_encode(rsa_sign(z_root(),$channel['channel_prvkey']));
+ hubloc_store_lowlevel($hv);
+ }
+ }
+
+ $x = q("select * from xchan where xchan_hash = '%s' ",
+ dbesc($arr['keychange']['old_hash'])
+ );
+
+ $check = q("select * from xchan where xchan_hash = '%s'",
+ dbesc($hash)
+ );
+
+ if(($x) && (! $check)) {
+ $oldxchan = $x[0];
+ foreach($x as $xv) {
+ $xv['xchan_guid_sig'] = $sig;
+ $xv['xchan_hash'] = $hash;
+ $xv['xchan_pubkey'] = $channel['channel_pubkey'];
+ xchan_store_lowlevel($xv);
+ $newxchan = $xv;
+ }
+ }
+
+ $a = q("select * from abook where abook_xchan = '%s' and abook_self = 1",
+ dbesc($arr['keychange']['old_hash'])
+ );
+
+ if($a) {
+ q("update abook set abook_xchan = '%s' where abook_id = %d",
+ dbesc($hash),
+ intval($a[0]['abook_id'])
+ );
+ }
+
+ xchan_change_key($oldxchan,$newxchan,$arr['keychange']);
+
+ // keychange operations can end up in a confused state if you try and sync anything else
+ // besides the channel keys, so ignore any other packets.
+
+ continue;
+ }
+
+
if(array_key_exists('config',$arr) && is_array($arr['config']) && count($arr['config'])) {
foreach($arr['config'] as $cat => $k) {
foreach($arr['config'][$cat] as $k => $v)
@@ -3162,8 +3318,8 @@ function process_channel_sync_delivery($sender, $arr, $deliveries) {
if(array_key_exists('menu',$arr) && $arr['menu'])
sync_menus($channel,$arr['menu']);
- if(array_key_exists('menu',$arr) && $arr['menu'])
- sync_menus($channel,$arr['menu']);
+ if(array_key_exists('file',$arr) && $arr['file'])
+ sync_files($channel,$arr['file']);
if(array_key_exists('wiki',$arr) && $arr['wiki'])
sync_items($channel,$arr['wiki'],((array_key_exists('relocate',$arr)) ? $arr['relocate'] : null));
@@ -3228,12 +3384,10 @@ function process_channel_sync_delivery($sender, $arr, $deliveries) {
}
- $disallowed = array('abook_id','abook_account','abook_channel','abook_rating','abook_rating_text');
+ $disallowed = array('abook_id','abook_account','abook_channel','abook_rating','abook_rating_text','abook_not_here');
foreach($arr['abook'] as $abook) {
-
-
$abconfig = null;
if(array_key_exists('abconfig',$abook) && is_array($abook['abconfig']) && count($abook['abconfig']))
@@ -3293,6 +3447,11 @@ function process_channel_sync_delivery($sender, $arr, $deliveries) {
if(! array_key_exists('abook_xchan',$clean))
continue;
+ if(array_key_exists('abook_instance',$clean) && $clean['abook_instance'] && strpos($clean['abook_instance'],z_root()) === false) {
+ $clean['abook_not_here'] = 1;
+ }
+
+
$r = q("select * from abook where abook_xchan = '%s' and abook_channel = %d limit 1",
dbesc($clean['abook_xchan']),
intval($channel['channel_id'])
@@ -3368,7 +3527,7 @@ function process_channel_sync_delivery($sender, $arr, $deliveries) {
dbesc($cl['name']),
intval($cl['visible']),
intval($cl['deleted']),
- dbesc($cl['hash']),
+ dbesc($cl['collection']),
intval($channel['channel_id'])
);
}
@@ -3584,21 +3743,72 @@ function get_rpost_path($observer) {
function import_author_zot($x) {
+ // Check that we have both a hubloc and xchan record - as occasionally storage calls will fail and
+ // we may only end up with one; which results in posts with no author name or photo and are a bit
+ // of a hassle to repair. If either or both are missing, do a full discovery probe.
+
$hash = make_xchan_hash($x['guid'],$x['guid_sig']);
- $r = q("select hubloc_url from hubloc where hubloc_guid = '%s' and hubloc_guid_sig = '%s' and hubloc_primary = 1 limit 1",
+
+ // also - this function may get passed a profile url as 'url' and zot_refresh wants a hubloc_url (site baseurl),
+ // so deconstruct the url (if we have one) and rebuild it with just the baseurl components.
+
+ if(array_key_exists('url',$x)) {
+ $m = parse_url($x['url']);
+ $desturl = $m['scheme'] . '://' . $m['host'];
+ }
+
+ $r1 = q("select hubloc_url, hubloc_updated, site_dead from hubloc left join site on
+ hubloc_url = site_url where hubloc_guid = '%s' and hubloc_guid_sig = '%s' and hubloc_primary = 1 limit 1",
dbesc($x['guid']),
dbesc($x['guid_sig'])
);
- if ($r) {
- logger('import_author_zot: in cache', LOGGER_DEBUG);
+ $r2 = q("select xchan_hash from xchan where xchan_guid = '%s' and xchan_guid_sig = '%s' limit 1",
+ dbesc($x['guid']),
+ dbesc($x['guid_sig'])
+ );
+
+ $site_dead = false;
+
+ if($r1 && intval($r1[0]['site_dead'])) {
+ $site_dead = true;
+ }
+
+ // We have valid and somewhat fresh information.
+
+ if($r1 && $r2 && $r1[0]['hubloc_updated'] > datetime_convert('UTC','UTC','now - 1 week')) {
+ logger('in cache', LOGGER_DEBUG);
return $hash;
}
- logger('import_author_zot: entry not in cache - probing: ' . print_r($x,true), LOGGER_DEBUG);
+ logger('not in cache or cache stale - probing: ' . print_r($x,true), LOGGER_DEBUG,LOG_INFO);
- $them = array('hubloc_url' => $x['url'], 'xchan_guid' => $x['guid'], 'xchan_guid_sig' => $x['guid_sig']);
- if (zot_refresh($them))
+ // The primary hub may be dead. Try to find another one associated with this identity that is
+ // still alive. If we find one, use that url for the discovery/refresh probe. Otherwise, the dead site
+ // is all we have and there is no point probing it. Just return the hash indicating we have a
+ // cached entry and the identity is valid. It's just unreachable until they bring back their
+ // server from the grave or create another clone elsewhere.
+
+ if($site_dead) {
+ logger('dead site - ignoring', LOGGER_DEBUG,LOG_INFO);
+
+ $r = q("select hubloc_url from hubloc left join site on hubloc_url = site_url
+ where hubloc_hash = '%s' and site_dead = 0",
+ dbesc($hash)
+ );
+ if($r) {
+ logger('found another site that is not dead: ' . $r[0]['hubloc_url'], LOGGER_DEBUG,LOG_INFO);
+ $desturl = $r[0]['hubloc_url'];
+ }
+ else {
+ return $hash;
+ }
+ }
+
+
+
+ $them = array('hubloc_url' => $desturl, 'xchan_guid' => $x['guid'], 'xchan_guid_sig' => $x['guid_sig']);
+ if(zot_refresh($them))
return $hash;
return false;
@@ -3702,11 +3912,57 @@ function zot_reply_message_request($data) {
json_return_and_die($ret);
}
+function zot_rekey_request($sender,$data) {
+
+ $ret = array('success' => false);
+
+ // newsig is newkey signed with oldkey
+
+ // The original xchan will remain. In Zot/Receiver we will have imported the new xchan and hubloc to verify
+ // the packet authenticity. What we will do now is verify that the keychange operation was signed by the
+ // oldkey, and if so change all the abook, abconfig, group, and permission elements which reference the
+ // old xchan_hash.
+
+ if((! $data['old_key']) && (! $data['new_key']) && (! $data['new_sig']))
+ json_return_and_die($ret);
+
+ $oldhash = make_xchan_hash($data['old_guid'],$data['old_guid_sig']);
+
+ $r = q("select * from xchan where xchan_hash = '%s' limit 1",
+ dbesc($oldhash)
+ );
+
+ if(! $r) {
+ json_return_and_die($ret);
+ }
+
+ $xchan = $r[0];
+
+ if(! rsa_verify($data['new_key'],base64url_decode($data['new_sig']),$xchan['xchan_pubkey'])) {
+ json_return_and_die($ret);
+ }
+
+ $newhash = make_xchan_hash($sender['guid'],$sender['guid_sig']);
+
+ $r = q("select * from xchan where xchan_hash = '%s' limit 1",
+ dbesc($newhash)
+ );
+
+ $newxchan = $r[0];
+
+ xchan_change_key($xchan,$newxchan,$data);
+
+ $ret['success'] = true;
+ json_return_and_die($ret);
+}
+
function zotinfo($arr) {
$ret = array('success' => false);
+ $sig_method = get_config('system','signature_algorithm','sha256');
+
$zhash = ((x($arr,'guid_hash')) ? $arr['guid_hash'] : '');
$zguid = ((x($arr,'guid')) ? $arr['guid'] : '');
$zguid_sig = ((x($arr,'guid_sig')) ? $arr['guid_sig'] : '');
@@ -3788,6 +4044,11 @@ function zotinfo($arr) {
$id = $e['channel_id'];
+ $x = [ 'channel_id' => $id, 'protocols' => ['zot'] ];
+ call_hooks('channel_protocols',$x);
+ $protocols = $x['protocols'];
+
+
$sys_channel = (intval($e['channel_system']) ? true : false);
$special_channel = (($e['channel_pageflags'] & PAGE_PREMIUM) ? true : false);
$adult_channel = (($e['channel_pageflags'] & PAGE_ADULT) ? true : false);
@@ -3870,7 +4131,7 @@ function zotinfo($arr) {
// Communication details
if($token)
- $ret['signed_token'] = base64url_encode(rsa_sign('token.' . $token,$e['channel_prvkey']));
+ $ret['signed_token'] = base64url_encode(rsa_sign('token.' . $token,$e['channel_prvkey'],$sig_method));
$ret['guid'] = $e['xchan_guid'];
@@ -3884,32 +4145,37 @@ function zotinfo($arr) {
$ret['photo_updated'] = $e['xchan_photo_date'];
$ret['url'] = $e['xchan_url'];
$ret['connections_url']= (($e['xchan_connurl']) ? $e['xchan_connurl'] : z_root() . '/poco/' . $e['channel_address']);
+ $ret['follow_url'] = $e['xchan_follow'];
$ret['target'] = $ztarget;
$ret['target_sig'] = $zsig;
$ret['searchable'] = $searchable;
+ $ret['protocols'] = $protocols;
$ret['adult_content'] = $adult_channel;
$ret['public_forum'] = $public_forum;
if($deleted)
$ret['deleted'] = $deleted;
+
if(intval($e['channel_removed']))
$ret['deleted_locally'] = true;
+
+
// premium or other channel desiring some contact with potential followers before connecting.
// This is a template - %s will be replaced with the follow_url we discover for the return channel.
- if($special_channel)
- $ret['connect_url'] = z_root() . '/connect/' . $e['channel_address'];
-
+ if($special_channel) {
+ $ret['connect_url'] = (($e['xchan_connpage']) ? $e['xchan_connpage'] : z_root() . '/connect/' . $e['channel_address']);
+ }
// This is a template for our follow url, %s will be replaced with a webbie
- $ret['follow_url'] = z_root() . '/follow?f=&url=%s';
-
+ if(! $ret['follow_url'])
+ $ret['follow_url'] = z_root() . '/follow?f=&url=%s';
$permissions = get_all_perms($e['channel_id'],$ztarget_hash,false);
if($ztarget_hash) {
$permissions['connected'] = false;
- $b = q("select * from abook where abook_xchan = '%s' and abook_channel = %d limit 1",
+ $b = q("select * from abook where abook_xchan = '%s' and abook_channel = %d and abook_pending = 0 limit 1",
dbesc($ztarget_hash),
intval($e['channel_id'])
);
@@ -3933,10 +4199,33 @@ function zotinfo($arr) {
if($x)
$ret['locations'] = $x;
- $ret['site'] = array();
+ $ret['site'] = zot_site_info($e['channel_prvkey']);
+
+ check_zotinfo($e,$x,$ret);
+
+
+ call_hooks('zot_finger',$ret);
+ return($ret);
+
+}
+
+
+function zot_site_info($channel_key = '') {
+
+ $signing_key = get_config('system','prvkey');
+ $sig_method = get_config('system','signature_algorithm','sha256');
+
+ $ret = [];
+ $ret['site'] = [];
$ret['site']['url'] = z_root();
- $ret['site']['url_sig'] = base64url_encode(rsa_sign(z_root(),$e['channel_prvkey']));
- $ret['site']['zot_auth'] = z_root() . '/magic';
+ if($channel_key) {
+ $ret['site']['url_sig'] = base64url_encode(rsa_sign(z_root(),$channel_key,$sig_method));
+ }
+ $ret['site']['url_site_sig'] = base64url_encode(rsa_sign(z_root(),$signing_key,$sig_method));
+ $ret['site']['post'] = z_root() . '/post';
+ $ret['site']['openWebAuth'] = z_root() . '/owa';
+ $ret['site']['authRedirect'] = z_root() . '/magic';
+ $ret['site']['key'] = get_config('system','pubkey');
$dirmode = get_config('system','directory_mode');
if(($dirmode === false) || ($dirmode == DIRECTORY_MODE_NORMAL))
@@ -3953,6 +4242,8 @@ function zotinfo($arr) {
$ret['site']['encryption'] = crypto_methods();
+ $ret['site']['signing'] = signing_methods();
+ $ret['site']['zot'] = Zotlabs\Lib\System::get_zot_revision();
// hide detailed site information if you're off the grid
@@ -4005,15 +4296,10 @@ function zotinfo($arr) {
}
- check_zotinfo($e,$x,$ret);
-
-
- call_hooks('zot_finger',$ret);
- return($ret);
+ return $ret['site'];
}
-
function check_zotinfo($channel,$locations,&$ret) {
diff --git a/install/INSTALL.txt b/install/INSTALL.txt
index 7d4ed9534..88269f032 100644
--- a/install/INSTALL.txt
+++ b/install/INSTALL.txt
@@ -7,14 +7,14 @@ such as XAMPP and WAMP are not officially supported at this time - however
we welcome patches if you manage to get it working.
Be aware that this software is more than a simple web application. It is a
-complex communications system which more closely resembles an email server
-than a web server. For reliability and performance, messages are delivered in
-the background and are queued for later delivery when sites are down. This
-kind of functionality requires a bit more of the host system than the typical
-blog. Not every PHP/MySQL hosting provider will be able to support the
-Hubzilla. Many will - but please review the requirements and confirm these
-with your hosting provider prior to installation. (And preferably before
-entering into a long-term contract.)
+complex communications and content management system which more closely
+resembles an email server than a web server. For reliability and performance,
+messages are delivered in the background and are queued for later delivery
+when sites are down. This kind of functionality requires a bit more of the
+host system than the typical blog. Not every PHP/MySQL hosting provider will
+be able to support Hubzilla. Many will - but please review the requirements
+and confirm these with your hosting provider prior to installation. (And
+preferably before entering into a long-term contract.)
If you encounter installation issues, please let us know via the Github issue
tracker where you downloaded the software. Please be as clear as
@@ -75,27 +75,6 @@ location may prevent some of these services from working correctly. This
should not be a problem with Apache, but may be an issue with nginx or other
web server platforms.
-**Server Roles**
-
-During installation you will be asked to choose a server role. Your choices are
-1. Basic
-2. Standard
-3. Pro
-
-Basic is highly simplified, with almost all the advanced functionality and
-complexity removed or permanently disabled.
-
-Standard is typically used for federated network use, when you wish to interact
-with other networks using other protocols. Not all the built in features and
-functionality work correctly when other networks are involved. All advanced
-and complex features are available to all members by default.
-
-Pro is for sites that wish to make full use of the built-in abilities and
-features, but **not** to interact with other networks. Advanced features are
-enabled according to a per-account 'techlevel' which reduces complexity
-initially and allows members to adjust the software complexity to match their
-technical abilities.
-
**Installation**
1. Requirements
@@ -104,19 +83,19 @@ technical abilities.
Example config scripts are available for these platforms in the install
directory. Apache and nginx have the most support.
- - PHP 5.5 or later.
+ - PHP 5.6 or later.
- PHP *command line* access with register_argc_argv set to true in the
php.ini file - and with no hosting provider restrictions on the use of
exec() and proc_open().
- - curl, gd (with at least jpeg and png support), mysqli, mbstring, xml,
+ - curl, gd (with at least jpeg and png support), mysqli, mbstring, xml, zip
and openssl extensions. The imagick extension MAY be used instead of gd,
but is not required and MAY also be disabled via configuration option.
- some form of email server or email gateway such that PHP mail() works.
- - Mysql 5.x or MariaDB or postgres database server.
+ - Mysql 5.5.3 or later or MariaDB or postgres database server.
- ability to schedule jobs with cron.
@@ -173,7 +152,8 @@ technical abilities.
cd mywebsite
util/update_addon_repo hzaddons
- - Create searchable representations of the online documentation. You may do this any time
+ - Once the software is configured and the database installed, create searchable
+ representations of the online documentation. You may do this any time
that the documentation is updated.
cd mywebsite
diff --git a/install/htconfig.sample.php b/install/htconfig.sample.php
index f37b3dc79..07725e3f4 100755
--- a/install/htconfig.sample.php
+++ b/install/htconfig.sample.php
@@ -44,14 +44,6 @@ App::$config['system']['sitename'] = "Hubzilla";
App::$config['system']['location_hash'] = 'if the auto install failed, put a unique random string here';
-// Choices are 'basic', 'standard', and 'pro'.
-// basic sets up the sevrer for basic social networking and removes "complicated" features
-// standard provides most desired features except e-commerce
-// pro gives you access to everything, but removes cross-platform federation/emulation
-
-App::$config['system']['server_role'] = 'standard';
-
-
// These lines set additional security headers to be sent with all responses
// You may wish to set transport_security_header to 0 if your server already sends
// this header. content_security_policy may need to be disabled if you wish to
diff --git a/install/sample-nginx.conf b/install/sample-nginx.conf
index 85178596a..4121ff2ec 100644
--- a/install/sample-nginx.conf
+++ b/install/sample-nginx.conf
@@ -56,7 +56,7 @@ server {
ssl_certificate_key /etc/nginx/ssl/example.net.key;
ssl_session_timeout 5m;
ssl_protocols TLSv1 TLSv1.1 TLSv1.2;
- ssl_ciphers ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES256-GCM-SHA384:DHE-DSS-AES128-GCM-SHA256:kEDH+AESGCM:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA:ECDHE-ECDSA-AES128-SHA:ECDHE-RSA-AES256-SHA384:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA:ECDHE-ECDSA-AES256-SHA:DHE-DSS-AES128-SHA256:DHE-DSS-AES256-SHA:AES128-GCM-SHA256:AES256-GCM-SHA384:AES128-SHA:AES256-SHA:AES:CAMELLIA:DES-CBC3-SHA:!aNULL:!eNULL:!EXPORT:!DES:!RC4:!MD5:!PSK:!aECDH:!EDH-DSS-DES-CBC3-SHA:!EDH-RSA-DES-CBC3-SHA:!KRB5-DES-CBC3-SHA:!DHE-RSA-AES128-GCM-SHA256:!DHE-RSA-AES256-GCM-SHA384:!DHE-RSA-AES128-SHA256:!DHE-RSA-AES256-SHA:!DHE-RSA-AES128-SHA:!DHE-RSA-AES256-SHA256:!DHE-RSA-CAMELLIA128-SHA:!DHE-RSA-CAMELLIA256-SHA;
+ ssl_ciphers ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305:ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:DHE-RSA-AES128-GCM-SHA256:DHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA:ECDHE-RSA-AES256-SHA384:ECDHE-RSA-AES128-SHA:ECDHE-ECDSA-AES256-SHA384:ECDHE-ECDSA-AES256-SHA:ECDHE-RSA-AES256-SHA:DHE-RSA-AES128-SHA256:DHE-RSA-AES128-SHA:DHE-RSA-AES256-SHA256:DHE-RSA-AES256-SHA:ECDHE-ECDSA-DES-CBC3-SHA:ECDHE-RSA-DES-CBC3-SHA:EDH-RSA-DES-CBC3-SHA:AES128-GCM-SHA256:AES256-GCM-SHA384:AES128-SHA256:AES256-SHA256:AES128-SHA:AES256-SHA:DES-CBC3-SHA:!DSS;
ssl_prefer_server_ciphers on;
fastcgi_param HTTPS on;
diff --git a/install/schema_mysql.sql b/install/schema_mysql.sql
index be5317722..afa3c095d 100644
--- a/install/schema_mysql.sql
+++ b/install/schema_mysql.sql
@@ -1,43 +1,44 @@
CREATE TABLE IF NOT EXISTS `abconfig` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `chan` int(10) unsigned NOT NULL DEFAULT '0',
- `xchan` char(255) NOT NULL DEFAULT '',
- `cat` char(255) NOT NULL DEFAULT '',
- `k` char(255) NOT NULL DEFAULT '',
+ `chan` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `xchan` char(191) NOT NULL DEFAULT '',
+ `cat` char(191) NOT NULL DEFAULT '',
+ `k` char(191) NOT NULL DEFAULT '',
`v` mediumtext NOT NULL,
PRIMARY KEY (`id`),
KEY `chan` (`chan`),
KEY `xchan` (`xchan`),
KEY `cat` (`cat`),
KEY `k` (`k`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `abook` (
`abook_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `abook_account` int(10) unsigned NOT NULL DEFAULT '0',
- `abook_channel` int(10) unsigned NOT NULL DEFAULT '0',
- `abook_xchan` char(255) NOT NULL DEFAULT '',
- `abook_my_perms` int(11) NOT NULL DEFAULT '0',
- `abook_their_perms` int(11) NOT NULL DEFAULT '0',
- `abook_closeness` tinyint(3) unsigned NOT NULL DEFAULT '99',
+ `abook_account` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `abook_channel` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `abook_xchan` char(191) NOT NULL DEFAULT '',
+ `abook_my_perms` int(11) NOT NULL DEFAULT 0 ,
+ `abook_their_perms` int(11) NOT NULL DEFAULT 0 ,
+ `abook_closeness` tinyint(3) unsigned NOT NULL DEFAULT 99,
`abook_created` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`abook_updated` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`abook_connected` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`abook_dob` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
- `abook_flags` int(11) NOT NULL DEFAULT '0',
- `abook_blocked` tinyint(4) NOT NULL DEFAULT '0',
- `abook_ignored` tinyint(4) NOT NULL DEFAULT '0',
- `abook_hidden` tinyint(4) NOT NULL DEFAULT '0',
- `abook_archived` tinyint(4) NOT NULL DEFAULT '0',
- `abook_pending` tinyint(4) NOT NULL DEFAULT '0',
- `abook_unconnected` tinyint(4) NOT NULL DEFAULT '0',
- `abook_self` tinyint(4) NOT NULL DEFAULT '0',
- `abook_feed` tinyint(4) NOT NULL DEFAULT '0',
- `abook_profile` char(64) NOT NULL DEFAULT '',
- `abook_incl` TEXT NOT NULL DEFAULT '',
- `abook_excl` TEXT NOT NULL DEFAULT '',
- `abook_instance` TEXT NOT NULL DEFAULT '',
+ `abook_flags` int(11) NOT NULL DEFAULT 0 ,
+ `abook_blocked` tinyint(4) NOT NULL DEFAULT 0 ,
+ `abook_ignored` tinyint(4) NOT NULL DEFAULT 0 ,
+ `abook_hidden` tinyint(4) NOT NULL DEFAULT 0 ,
+ `abook_archived` tinyint(4) NOT NULL DEFAULT 0 ,
+ `abook_pending` tinyint(4) NOT NULL DEFAULT 0 ,
+ `abook_unconnected` tinyint(4) NOT NULL DEFAULT 0 ,
+ `abook_self` tinyint(4) NOT NULL DEFAULT 0 ,
+ `abook_feed` tinyint(4) NOT NULL DEFAULT 0 ,
+ `abook_not_here` tinyint(4) NOT NULL DEFAULT 0 ,
+ `abook_profile` char(191) NOT NULL DEFAULT '',
+ `abook_incl` text NOT NULL,
+ `abook_excl` text NOT NULL,
+ `abook_instance` text NOT NULL,
PRIMARY KEY (`abook_id`),
KEY `abook_account` (`abook_account`),
KEY `abook_channel` (`abook_channel`),
@@ -58,27 +59,28 @@ CREATE TABLE IF NOT EXISTS `abook` (
KEY `abook_pending` (`abook_pending`),
KEY `abook_unconnected` (`abook_unconnected`),
KEY `abook_self` (`abook_self`),
+ KEY `abook_not_here` (`abook_not_here`),
KEY `abook_feed` (`abook_feed`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `account` (
`account_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `account_parent` int(10) unsigned NOT NULL DEFAULT '0',
- `account_default_channel` int(10) unsigned NOT NULL DEFAULT '0',
+ `account_parent` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `account_default_channel` int(10) unsigned NOT NULL DEFAULT 0 ,
`account_salt` char(32) NOT NULL DEFAULT '',
- `account_password` char(255) NOT NULL DEFAULT '',
- `account_email` char(255) NOT NULL DEFAULT '',
- `account_external` char(255) NOT NULL DEFAULT '',
+ `account_password` char(191) NOT NULL DEFAULT '',
+ `account_email` char(191) NOT NULL DEFAULT '',
+ `account_external` char(191) NOT NULL DEFAULT '',
`account_language` char(16) NOT NULL DEFAULT 'en',
`account_created` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`account_lastlog` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
- `account_flags` int(10) unsigned NOT NULL DEFAULT '0',
- `account_roles` int(10) unsigned NOT NULL DEFAULT '0',
- `account_reset` char(255) NOT NULL DEFAULT '',
+ `account_flags` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `account_roles` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `account_reset` char(191) NOT NULL DEFAULT '',
`account_expires` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`account_expire_notified` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`account_service_class` char(32) NOT NULL DEFAULT '',
- `account_level` int(10) unsigned NOT NULL DEFAULT '0',
+ `account_level` int(10) unsigned NOT NULL DEFAULT 0 ,
`account_password_changed` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
PRIMARY KEY (`account_id`),
KEY `account_email` (`account_email`),
@@ -92,40 +94,40 @@ CREATE TABLE IF NOT EXISTS `account` (
KEY `account_external` (`account_external`),
KEY `account_level` (`account_level`),
KEY `account_password_changed` (`account_password_changed`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `addon` (
`id` int(11) NOT NULL AUTO_INCREMENT,
- `aname` char(255) NOT NULL DEFAULT '',
- `version` char(255) NOT NULL DEFAULT '',
- `installed` tinyint(1) NOT NULL DEFAULT '0',
- `hidden` tinyint(1) NOT NULL DEFAULT '0',
- `tstamp` bigint(20) NOT NULL DEFAULT '0',
- `plugin_admin` tinyint(1) NOT NULL DEFAULT '0',
+ `aname` char(191) NOT NULL DEFAULT '',
+ `version` char(191) NOT NULL DEFAULT '',
+ `installed` tinyint(1) NOT NULL DEFAULT 0 ,
+ `hidden` tinyint(1) NOT NULL DEFAULT 0 ,
+ `tstamp` bigint(20) NOT NULL DEFAULT 0 ,
+ `plugin_admin` tinyint(1) NOT NULL DEFAULT 0 ,
PRIMARY KEY (`id`),
KEY `hidden` (`hidden`),
KEY `aname` (`aname`),
KEY `installed` (`installed`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `app` (
`id` int(11) NOT NULL AUTO_INCREMENT,
- `app_id` char(255) NOT NULL DEFAULT '',
- `app_sig` char(255) NOT NULL DEFAULT '',
- `app_author` char(255) NOT NULL DEFAULT '',
- `app_name` char(255) NOT NULL DEFAULT '',
- `app_desc` text NOT NULL DEFAULT '',
- `app_url` char(255) NOT NULL DEFAULT '',
- `app_photo` char(255) NOT NULL DEFAULT '',
- `app_version` char(255) NOT NULL DEFAULT '',
- `app_channel` int(11) NOT NULL DEFAULT '0',
- `app_addr` char(255) NOT NULL DEFAULT '',
- `app_price` char(255) NOT NULL DEFAULT '',
- `app_page` char(255) NOT NULL DEFAULT '',
- `app_requires` char(255) NOT NULL DEFAULT '',
- `app_deleted` int(11) NOT NULL DEFAULT '0',
- `app_system` int(11) NOT NULL DEFAULT '0',
- `app_plugin` char(255) NOT NULL DEFAULT '',
+ `app_id` char(191) NOT NULL DEFAULT '',
+ `app_sig` char(191) NOT NULL DEFAULT '',
+ `app_author` char(191) NOT NULL DEFAULT '',
+ `app_name` char(191) NOT NULL DEFAULT '',
+ `app_desc` text NOT NULL,
+ `app_url` char(191) NOT NULL DEFAULT '',
+ `app_photo` char(191) NOT NULL DEFAULT '',
+ `app_version` char(191) NOT NULL DEFAULT '',
+ `app_channel` int(11) NOT NULL DEFAULT 0 ,
+ `app_addr` char(191) NOT NULL DEFAULT '',
+ `app_price` char(191) NOT NULL DEFAULT '',
+ `app_page` char(191) NOT NULL DEFAULT '',
+ `app_requires` char(191) NOT NULL DEFAULT '',
+ `app_deleted` int(11) NOT NULL DEFAULT 0 ,
+ `app_system` int(11) NOT NULL DEFAULT 0 ,
+ `app_plugin` char(191) NOT NULL DEFAULT '',
`app_created` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`app_edited` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
PRIMARY KEY (`id`),
@@ -140,15 +142,15 @@ CREATE TABLE IF NOT EXISTS `app` (
KEY `app_deleted` (`app_deleted`),
KEY `app_system` (`app_system`),
KEY `app_edited` (`app_edited`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `atoken` (
`atoken_id` int(11) NOT NULL AUTO_INCREMENT,
- `atoken_aid` int(11) NOT NULL DEFAULT 0,
- `atoken_uid` int(11) NOT NULL DEFAULT 0,
- `atoken_name` char(255) NOT NULL DEFAULT '',
- `atoken_token` char(255) NOT NULL DEFAULT '',
+ `atoken_aid` int(11) NOT NULL DEFAULT 0 ,
+ `atoken_uid` int(11) NOT NULL DEFAULT 0 ,
+ `atoken_name` char(191) NOT NULL DEFAULT '',
+ `atoken_token` char(191) NOT NULL DEFAULT '',
`atoken_expires` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
PRIMARY KEY (`atoken_id`),
KEY `atoken_aid` (`atoken_aid`),
@@ -157,23 +159,23 @@ CREATE TABLE IF NOT EXISTS `atoken` (
KEY `atoken_name` (`atoken_name`),
KEY `atoken_token` (`atoken_token`),
KEY `atoken_expires` (`atoken_expires`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `attach` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `aid` int(10) unsigned NOT NULL DEFAULT '0',
- `uid` int(10) unsigned NOT NULL DEFAULT '0',
- `hash` char(64) NOT NULL DEFAULT '',
- `creator` char(128) NOT NULL DEFAULT '',
- `filename` char(255) NOT NULL DEFAULT '',
- `filetype` char(64) NOT NULL DEFAULT '',
- `filesize` int(10) unsigned NOT NULL DEFAULT '0',
- `revision` int(10) unsigned NOT NULL DEFAULT '0',
- `folder` char(64) NOT NULL DEFAULT '',
- `flags` int(10) unsigned NOT NULL DEFAULT '0',
- `is_dir` tinyint(1) NOT NULL DEFAULT '0',
- `is_photo` tinyint(1) NOT NULL DEFAULT '0',
- `os_storage` tinyint(1) NOT NULL DEFAULT '0',
+ `aid` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `uid` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `hash` char(191) NOT NULL DEFAULT '',
+ `creator` char(191) NOT NULL DEFAULT '',
+ `filename` char(191) NOT NULL DEFAULT '',
+ `filetype` char(191) NOT NULL DEFAULT '',
+ `filesize` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `revision` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `folder` char(191) NOT NULL DEFAULT '',
+ `flags` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `is_dir` tinyint(1) NOT NULL DEFAULT 0 ,
+ `is_photo` tinyint(1) NOT NULL DEFAULT 0 ,
+ `os_storage` tinyint(1) NOT NULL DEFAULT 0 ,
`os_path` mediumtext NOT NULL,
`display_path` mediumtext NOT NULL,
`content` longblob NOT NULL,
@@ -199,96 +201,98 @@ CREATE TABLE IF NOT EXISTS `attach` (
KEY `is_dir` (`is_dir`),
KEY `is_photo` (`is_photo`),
KEY `os_storage` (`os_storage`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `auth_codes` (
`id` varchar(40) NOT NULL DEFAULT '',
`client_id` varchar(20) NOT NULL DEFAULT '',
`redirect_uri` varchar(200) NOT NULL DEFAULT '',
- `expires` int(11) NOT NULL DEFAULT '0',
+ `expires` int(11) NOT NULL DEFAULT 0 ,
`auth_scope` varchar(512) NOT NULL DEFAULT '',
PRIMARY KEY (`id`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `cache` (
- `k` char(255) NOT NULL DEFAULT '',
+ `k` char(191) NOT NULL DEFAULT '',
`v` text NOT NULL,
`updated` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
PRIMARY KEY (`k`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `cal` (
`cal_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `cal_aid` int(10) unsigned NOT NULL DEFAULT '0',
- `cal_uid` int(10) unsigned NOT NULL DEFAULT '0',
- `cal_hash` varchar(255) NOT NULL DEFAULT '',
- `cal_name` varchar(255) NOT NULL DEFAULT '',
- `uri` varchar(255) NOT NULL DEFAULT '',
- `logname` varchar(255) NOT NULL DEFAULT '',
- `pass` varchar(255) NOT NULL DEFAULT '',
- `ctag` varchar(255) NOT NULL DEFAULT '',
- `synctoken` varchar(255) NOT NULL DEFAULT '',
- `cal_types` varchar(255) NOT NULL DEFAULT '',
+ `cal_aid` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `cal_uid` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `cal_hash` varchar(191) NOT NULL DEFAULT '',
+ `cal_name` varchar(191) NOT NULL DEFAULT '',
+ `uri` varchar(191) NOT NULL DEFAULT '',
+ `logname` varchar(191) NOT NULL DEFAULT '',
+ `pass` varchar(191) NOT NULL DEFAULT '',
+ `ctag` varchar(191) NOT NULL DEFAULT '',
+ `synctoken` varchar(191) NOT NULL DEFAULT '',
+ `cal_types` varchar(191) NOT NULL DEFAULT '',
PRIMARY KEY (`cal_id`),
KEY `cal_aid` (`cal_aid`),
KEY `cal_uid` (`cal_uid`),
KEY `cal_hash` (`cal_hash`),
KEY `cal_name` (`cal_name`),
KEY `cal_types` (`cal_types`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `channel` (
`channel_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `channel_account_id` int(10) unsigned NOT NULL DEFAULT '0',
- `channel_primary` tinyint(1) unsigned NOT NULL DEFAULT '0',
- `channel_name` char(255) NOT NULL DEFAULT '',
- `channel_address` char(255) NOT NULL DEFAULT '',
- `channel_guid` char(255) NOT NULL DEFAULT '',
+ `channel_account_id` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `channel_primary` tinyint(1) unsigned NOT NULL DEFAULT 0 ,
+ `channel_name` char(191) NOT NULL DEFAULT '',
+ `channel_address` char(191) NOT NULL DEFAULT '',
+ `channel_guid` char(191) NOT NULL DEFAULT '',
`channel_guid_sig` text NOT NULL,
- `channel_hash` char(255) NOT NULL DEFAULT '',
+ `channel_hash` char(191) NOT NULL DEFAULT '',
`channel_timezone` char(128) NOT NULL DEFAULT 'UTC',
- `channel_location` char(255) NOT NULL DEFAULT '',
- `channel_theme` char(255) NOT NULL DEFAULT '',
- `channel_startpage` char(255) NOT NULL DEFAULT '',
+ `channel_location` char(191) NOT NULL DEFAULT '',
+ `channel_theme` char(191) NOT NULL DEFAULT '',
+ `channel_startpage` char(191) NOT NULL DEFAULT '',
`channel_pubkey` text NOT NULL,
`channel_prvkey` text NOT NULL,
- `channel_notifyflags` int(10) unsigned NOT NULL DEFAULT '65535',
- `channel_pageflags` int(10) unsigned NOT NULL DEFAULT '0',
+ `channel_notifyflags` int(10) unsigned NOT NULL DEFAULT 65535,
+ `channel_pageflags` int(10) unsigned NOT NULL DEFAULT 0 ,
`channel_dirdate` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`channel_lastpost` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`channel_deleted` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
- `channel_max_anon_mail` int(10) unsigned NOT NULL DEFAULT '10',
- `channel_max_friend_req` int(10) unsigned NOT NULL DEFAULT '10',
- `channel_expire_days` int(11) NOT NULL DEFAULT '0',
- `channel_passwd_reset` char(255) NOT NULL DEFAULT '',
- `channel_default_group` char(255) NOT NULL DEFAULT '',
+ `channel_max_anon_mail` int(10) unsigned NOT NULL DEFAULT 10,
+ `channel_max_friend_req` int(10) unsigned NOT NULL DEFAULT 10,
+ `channel_expire_days` int(11) NOT NULL DEFAULT 0 ,
+ `channel_passwd_reset` char(191) NOT NULL DEFAULT '',
+ `channel_default_group` char(191) NOT NULL DEFAULT '',
`channel_allow_cid` mediumtext NOT NULL,
`channel_allow_gid` mediumtext NOT NULL,
`channel_deny_cid` mediumtext NOT NULL,
`channel_deny_gid` mediumtext NOT NULL,
- `channel_r_stream` int(10) unsigned NOT NULL DEFAULT '0',
- `channel_r_profile` int(10) unsigned NOT NULL DEFAULT '0',
- `channel_r_photos` int(10) unsigned NOT NULL DEFAULT '0',
- `channel_r_abook` int(10) unsigned NOT NULL DEFAULT '0',
- `channel_w_stream` int(10) unsigned NOT NULL DEFAULT '0',
- `channel_w_wall` int(10) unsigned NOT NULL DEFAULT '0',
- `channel_w_tagwall` int(10) unsigned NOT NULL DEFAULT '0',
- `channel_w_comment` int(10) unsigned NOT NULL DEFAULT '0',
- `channel_w_mail` int(10) unsigned NOT NULL DEFAULT '0',
- `channel_w_photos` int(10) unsigned NOT NULL DEFAULT '0',
- `channel_w_chat` int(10) unsigned NOT NULL DEFAULT '0',
- `channel_a_delegate` int(10) unsigned NOT NULL DEFAULT '0',
- `channel_r_storage` int(10) unsigned NOT NULL DEFAULT '0',
- `channel_w_storage` int(10) unsigned NOT NULL DEFAULT '0',
- `channel_r_pages` int(10) unsigned NOT NULL DEFAULT '0',
- `channel_w_pages` int(10) unsigned NOT NULL DEFAULT '0',
- `channel_a_republish` int(10) unsigned NOT NULL DEFAULT '0',
- `channel_w_like` int(10) unsigned NOT NULL DEFAULT '0',
- `channel_removed` tinyint(1) NOT NULL DEFAULT '0',
- `channel_system` tinyint(1) NOT NULL DEFAULT '0',
- `channel_moved` char(255) NOT NULL DEFAULT '',
+ `channel_r_stream` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `channel_r_profile` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `channel_r_photos` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `channel_r_abook` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `channel_w_stream` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `channel_w_wall` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `channel_w_tagwall` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `channel_w_comment` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `channel_w_mail` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `channel_w_photos` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `channel_w_chat` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `channel_a_delegate` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `channel_r_storage` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `channel_w_storage` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `channel_r_pages` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `channel_w_pages` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `channel_a_republish` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `channel_w_like` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `channel_removed` tinyint(1) NOT NULL DEFAULT 0 ,
+ `channel_system` tinyint(1) NOT NULL DEFAULT 0 ,
+ `channel_moved` char(191) NOT NULL DEFAULT '',
+ `channel_password` varchar(191) NOT NULL,
+ `channel_salt` varchar(191) NOT NULL,
PRIMARY KEY (`channel_id`),
- UNIQUE KEY `channel_address_unique` (`channel_address`),
+ KEY `channel_address` (`channel_address`),
KEY `channel_account_id` (`channel_account_id`),
KEY `channel_primary` (`channel_primary`),
KEY `channel_name` (`channel_name`),
@@ -300,69 +304,51 @@ CREATE TABLE IF NOT EXISTS `channel` (
KEY `channel_max_anon_mail` (`channel_max_anon_mail`),
KEY `channel_max_friend_req` (`channel_max_friend_req`),
KEY `channel_default_gid` (`channel_default_group`),
- KEY `channel_r_stream` (`channel_r_stream`),
- KEY `channel_r_profile` (`channel_r_profile`),
- KEY `channel_r_photos` (`channel_r_photos`),
- KEY `channel_r_abook` (`channel_r_abook`),
- KEY `channel_w_stream` (`channel_w_stream`),
- KEY `channel_w_wall` (`channel_w_wall`),
- KEY `channel_w_tagwall` (`channel_w_tagwall`),
- KEY `channel_w_comment` (`channel_w_comment`),
- KEY `channel_w_mail` (`channel_w_mail`),
- KEY `channel_w_photos` (`channel_w_photos`),
- KEY `channel_w_chat` (`channel_w_chat`),
KEY `channel_guid` (`channel_guid`),
KEY `channel_hash` (`channel_hash`),
KEY `channel_expire_days` (`channel_expire_days`),
- KEY `channel_a_delegate` (`channel_a_delegate`),
- KEY `channel_r_storage` (`channel_r_storage`),
- KEY `channel_w_storage` (`channel_w_storage`),
- KEY `channel_r_pages` (`channel_r_pages`),
- KEY `channel_w_pages` (`channel_w_pages`),
KEY `channel_deleted` (`channel_deleted`),
- KEY `channel_a_republish` (`channel_a_republish`),
KEY `channel_dirdate` (`channel_dirdate`),
- KEY `channel_w_like` (`channel_w_like`),
KEY `channel_removed` (`channel_removed`),
KEY `channel_system` (`channel_system`),
KEY `channel_lastpost` (`channel_lastpost`),
KEY `channel_moved` (`channel_moved`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `chat` (
`chat_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `chat_room` int(10) unsigned NOT NULL DEFAULT '0',
- `chat_xchan` char(255) NOT NULL DEFAULT '',
+ `chat_room` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `chat_xchan` char(191) NOT NULL DEFAULT '',
`chat_text` mediumtext NOT NULL,
`created` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
PRIMARY KEY (`chat_id`),
KEY `chat_room` (`chat_room`),
KEY `chat_xchan` (`chat_xchan`),
KEY `created` (`created`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `chatpresence` (
`cp_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `cp_room` int(10) unsigned NOT NULL DEFAULT '0',
- `cp_xchan` char(255) NOT NULL DEFAULT '',
+ `cp_room` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `cp_xchan` char(191) NOT NULL DEFAULT '',
`cp_last` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
- `cp_status` char(255) NOT NULL DEFAULT '',
+ `cp_status` char(191) NOT NULL DEFAULT '',
`cp_client` char(128) NOT NULL DEFAULT '',
PRIMARY KEY (`cp_id`),
KEY `cp_room` (`cp_room`),
KEY `cp_xchan` (`cp_xchan`),
KEY `cp_last` (`cp_last`),
KEY `cp_status` (`cp_status`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `chatroom` (
`cr_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `cr_aid` int(10) unsigned NOT NULL DEFAULT '0',
- `cr_uid` int(10) unsigned NOT NULL DEFAULT '0',
- `cr_name` char(255) NOT NULL DEFAULT '',
+ `cr_aid` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `cr_uid` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `cr_name` char(191) NOT NULL DEFAULT '',
`cr_created` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`cr_edited` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
- `cr_expire` int(10) unsigned NOT NULL DEFAULT '0',
+ `cr_expire` int(10) unsigned NOT NULL DEFAULT 0 ,
`allow_cid` mediumtext NOT NULL,
`allow_gid` mediumtext NOT NULL,
`deny_cid` mediumtext NOT NULL,
@@ -374,51 +360,51 @@ CREATE TABLE IF NOT EXISTS `chatroom` (
KEY `cr_created` (`cr_created`),
KEY `cr_edited` (`cr_edited`),
KEY `cr_expire` (`cr_expire`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `clients` (
- `client_id` varchar(20) NOT NULL DEFAULT '',
- `pw` varchar(20) NOT NULL DEFAULT '',
+ `client_id` varchar(191) NOT NULL DEFAULT '',
+ `pw` varchar(191) NOT NULL DEFAULT '',
`redirect_uri` varchar(200) NOT NULL DEFAULT '',
`clname` text,
`icon` text,
- `uid` int(11) NOT NULL DEFAULT '0',
+ `uid` int(11) NOT NULL DEFAULT 0 ,
PRIMARY KEY (`client_id`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `config` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `cat` char(255) CHARACTER SET ascii NOT NULL DEFAULT '',
- `k` char(255) CHARACTER SET ascii NOT NULL DEFAULT '',
+ `cat` char(191) NOT NULL DEFAULT '',
+ `k` char(191) NOT NULL DEFAULT '',
`v` text NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `access` (`cat`,`k`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `conv` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `guid` char(255) NOT NULL DEFAULT '',
+ `guid` char(191) NOT NULL DEFAULT '',
`recips` mediumtext NOT NULL,
- `uid` int(11) NOT NULL DEFAULT '0',
- `creator` char(255) NOT NULL DEFAULT '',
+ `uid` int(11) NOT NULL DEFAULT 0 ,
+ `creator` char(191) NOT NULL DEFAULT '',
`created` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`updated` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`subject` mediumtext NOT NULL,
PRIMARY KEY (`id`),
KEY `created` (`created`),
KEY `updated` (`updated`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `dreport` (
`dreport_id` int(11) NOT NULL AUTO_INCREMENT,
- `dreport_channel` int(11) NOT NULL DEFAULT '0',
- `dreport_mid` char(255) NOT NULL DEFAULT '',
- `dreport_site` char(255) NOT NULL DEFAULT '',
- `dreport_recip` char(255) NOT NULL DEFAULT '',
- `dreport_result` char(255) NOT NULL DEFAULT '',
+ `dreport_channel` int(11) NOT NULL DEFAULT 0 ,
+ `dreport_mid` char(191) NOT NULL DEFAULT '',
+ `dreport_site` char(191) NOT NULL DEFAULT '',
+ `dreport_recip` char(191) NOT NULL DEFAULT '',
+ `dreport_result` char(191) NOT NULL DEFAULT '',
`dreport_time` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
- `dreport_xchan` char(255) NOT NULL DEFAULT '',
- `dreport_queue` char(255) NOT NULL DEFAULT '',
+ `dreport_xchan` char(191) NOT NULL DEFAULT '',
+ `dreport_queue` char(191) NOT NULL DEFAULT '',
PRIMARY KEY (`dreport_id`),
KEY `dreport_mid` (`dreport_mid`),
KEY `dreport_site` (`dreport_site`),
@@ -426,15 +412,15 @@ CREATE TABLE IF NOT EXISTS `dreport` (
KEY `dreport_xchan` (`dreport_xchan`),
KEY `dreport_queue` (`dreport_queue`),
KEY `dreport_channel` (`dreport_channel`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `event` (
`id` int(11) NOT NULL AUTO_INCREMENT,
- `aid` int(10) unsigned NOT NULL DEFAULT '0',
- `uid` int(11) NOT NULL DEFAULT '0',
- `cal_id` int(11) unsigned NOT NULL DEFAULT '0',
- `event_xchan` char(255) NOT NULL DEFAULT '',
- `event_hash` char(255) NOT NULL DEFAULT '',
+ `aid` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `uid` int(11) NOT NULL DEFAULT 0 ,
+ `cal_id` int(11) unsigned NOT NULL DEFAULT 0 ,
+ `event_xchan` char(191) NOT NULL DEFAULT '',
+ `event_hash` char(191) NOT NULL DEFAULT '',
`created` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`edited` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`dtstart` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
@@ -442,20 +428,20 @@ CREATE TABLE IF NOT EXISTS `event` (
`summary` text NOT NULL,
`description` text NOT NULL,
`location` text NOT NULL,
- `etype` char(255) NOT NULL DEFAULT '',
- `nofinish` tinyint(1) NOT NULL DEFAULT '0',
- `adjust` tinyint(1) NOT NULL DEFAULT '1',
- `dismissed` tinyint(1) NOT NULL DEFAULT '0',
+ `etype` char(191) NOT NULL DEFAULT '',
+ `nofinish` tinyint(1) NOT NULL DEFAULT 0 ,
+ `adjust` tinyint(1) NOT NULL DEFAULT 1,
+ `dismissed` tinyint(1) NOT NULL DEFAULT 0 ,
`allow_cid` mediumtext NOT NULL,
`allow_gid` mediumtext NOT NULL,
`deny_cid` mediumtext NOT NULL,
`deny_gid` mediumtext NOT NULL,
- `event_status` char(255) NOT NULL DEFAULT '',
+ `event_status` char(191) NOT NULL DEFAULT '',
`event_status_date` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
- `event_percent` smallint(6) NOT NULL DEFAULT '0',
+ `event_percent` smallint(6) NOT NULL DEFAULT 0 ,
`event_repeat` text NOT NULL,
- `event_sequence` smallint(6) NOT NULL DEFAULT '0',
- `event_priority` smallint(6) NOT NULL DEFAULT '0',
+ `event_sequence` smallint(6) NOT NULL DEFAULT 0 ,
+ `event_priority` smallint(6) NOT NULL DEFAULT 0 ,
`event_vdata` text NOT NULL,
PRIMARY KEY (`id`),
KEY `uid` (`uid`),
@@ -472,71 +458,72 @@ CREATE TABLE IF NOT EXISTS `event` (
KEY `event_status` (`event_status`),
KEY `event_sequence` (`event_sequence`),
KEY `event_priority` (`event_priority`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `groups` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `hash` char(255) NOT NULL DEFAULT '',
- `uid` int(10) unsigned NOT NULL DEFAULT '0',
- `visible` tinyint(1) NOT NULL DEFAULT '0',
- `deleted` tinyint(1) NOT NULL DEFAULT '0',
- `gname` char(255) NOT NULL DEFAULT '',
+ `hash` char(191) NOT NULL DEFAULT '',
+ `uid` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `visible` tinyint(1) NOT NULL DEFAULT 0 ,
+ `deleted` tinyint(1) NOT NULL DEFAULT 0 ,
+ `gname` char(191) NOT NULL DEFAULT '',
PRIMARY KEY (`id`),
KEY `uid` (`uid`),
KEY `visible` (`visible`),
KEY `deleted` (`deleted`),
KEY `hash` (`hash`),
KEY `gname` (`gname`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `group_member` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `uid` int(10) unsigned NOT NULL DEFAULT '0',
- `gid` int(10) unsigned NOT NULL DEFAULT '0',
- `xchan` char(255) NOT NULL DEFAULT '',
+ `uid` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `gid` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `xchan` char(191) NOT NULL DEFAULT '',
PRIMARY KEY (`id`),
KEY `uid` (`uid`),
KEY `gid` (`gid`),
KEY `xchan` (`xchan`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `hook` (
`id` int(11) NOT NULL AUTO_INCREMENT,
- `hook` char(255) NOT NULL DEFAULT '',
- `file` char(255) NOT NULL DEFAULT '',
- `fn` char(255) NOT NULL DEFAULT '',
- `priority` smallint NOT NULL DEFAULT '0',
- `hook_version` int(11) NOT NULL DEFAULT '0',
+ `hook` char(191) NOT NULL DEFAULT '',
+ `file` char(191) NOT NULL DEFAULT '',
+ `fn` char(191) NOT NULL DEFAULT '',
+ `priority` smallint NOT NULL DEFAULT 0 ,
+ `hook_version` int(11) NOT NULL DEFAULT 0 ,
PRIMARY KEY (`id`),
KEY `hook` (`hook`),
KEY `priority` (`priority`),
KEY `hook_version` (`hook_version`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `hubloc` (
`hubloc_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `hubloc_guid` char(255) NOT NULL DEFAULT '',
+ `hubloc_guid` char(191) NOT NULL DEFAULT '',
`hubloc_guid_sig` text NOT NULL,
- `hubloc_hash` char(255) NOT NULL DEFAULT '',
- `hubloc_addr` char(255) NOT NULL DEFAULT '',
+ `hubloc_hash` char(191) NOT NULL DEFAULT '',
+ `hubloc_addr` char(191) NOT NULL DEFAULT '',
`hubloc_network` char(32) NOT NULL DEFAULT '',
- `hubloc_flags` int(10) unsigned NOT NULL DEFAULT '0',
- `hubloc_status` int(10) unsigned NOT NULL DEFAULT '0',
- `hubloc_url` char(255) NOT NULL DEFAULT '',
+ `hubloc_flags` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `hubloc_status` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `hubloc_url` char(191) NOT NULL DEFAULT '',
`hubloc_url_sig` text NOT NULL,
- `hubloc_host` char(255) NOT NULL DEFAULT '',
- `hubloc_callback` char(255) NOT NULL DEFAULT '',
- `hubloc_connect` char(255) NOT NULL DEFAULT '',
+ `hubloc_host` char(191) NOT NULL DEFAULT '',
+ `hubloc_callback` char(191) NOT NULL DEFAULT '',
+ `hubloc_connect` char(191) NOT NULL DEFAULT '',
`hubloc_sitekey` text NOT NULL,
`hubloc_updated` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`hubloc_connected` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
- `hubloc_primary` tinyint(1) NOT NULL DEFAULT '0',
- `hubloc_orphancheck` tinyint(1) NOT NULL DEFAULT '0',
- `hubloc_error` tinyint(1) NOT NULL DEFAULT '0',
- `hubloc_deleted` tinyint(1) NOT NULL DEFAULT '0',
+ `hubloc_primary` tinyint(1) NOT NULL DEFAULT 0 ,
+ `hubloc_orphancheck` tinyint(1) NOT NULL DEFAULT 0 ,
+ `hubloc_error` tinyint(1) NOT NULL DEFAULT 0 ,
+ `hubloc_deleted` tinyint(1) NOT NULL DEFAULT 0 ,
PRIMARY KEY (`hubloc_id`),
KEY `hubloc_url` (`hubloc_url`),
KEY `hubloc_guid` (`hubloc_guid`),
+ KEY `hubloc_hash` (`hubloc_hash`),
KEY `hubloc_flags` (`hubloc_flags`),
KEY `hubloc_connect` (`hubloc_connect`),
KEY `hubloc_host` (`hubloc_host`),
@@ -549,31 +536,31 @@ CREATE TABLE IF NOT EXISTS `hubloc` (
KEY `hubloc_orphancheck` (`hubloc_orphancheck`),
KEY `hubloc_deleted` (`hubloc_deleted`),
KEY `hubloc_error` (`hubloc_error`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `iconfig` (
`id` int(11) NOT NULL AUTO_INCREMENT,
- `iid` int(11) NOT NULL DEFAULT '0',
- `cat` char(255) NOT NULL DEFAULT '',
- `k` char(255) NOT NULL DEFAULT '',
+ `iid` int(11) NOT NULL DEFAULT 0 ,
+ `cat` char(191) NOT NULL DEFAULT '',
+ `k` char(191) NOT NULL DEFAULT '',
`v` mediumtext NOT NULL,
- `sharing` int(11) NOT NULL DEFAULT '0',
+ `sharing` int(11) NOT NULL DEFAULT 0 ,
PRIMARY KEY (`id`),
KEY `iid` (`iid`),
KEY `cat` (`cat`),
KEY `k` (`k`),
KEY `sharing` (`sharing`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `issue` (
`issue_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
`issue_created` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`issue_updated` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
- `issue_assigned` char(255) NOT NULL DEFAULT '',
- `issue_priority` int(11) NOT NULL DEFAULT '0',
- `issue_status` int(11) NOT NULL DEFAULT '0',
- `issue_component` char(255) NOT NULL DEFAULT '',
+ `issue_assigned` char(191) NOT NULL DEFAULT '',
+ `issue_priority` int(11) NOT NULL DEFAULT 0 ,
+ `issue_status` int(11) NOT NULL DEFAULT 0 ,
+ `issue_component` char(191) NOT NULL DEFAULT '',
PRIMARY KEY (`issue_id`),
KEY `issue_created` (`issue_created`),
KEY `issue_updated` (`issue_updated`),
@@ -581,16 +568,16 @@ CREATE TABLE IF NOT EXISTS `issue` (
KEY `issue_priority` (`issue_priority`),
KEY `issue_status` (`issue_status`),
KEY `issue_component` (`issue_component`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `item` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `mid` char(255) CHARACTER SET ascii NOT NULL DEFAULT '',
- `aid` int(10) unsigned NOT NULL DEFAULT '0',
- `uid` int(10) unsigned NOT NULL DEFAULT '0',
- `parent` int(10) unsigned NOT NULL DEFAULT '0',
- `parent_mid` char(255) CHARACTER SET ascii NOT NULL DEFAULT '',
- `thr_parent` char(255) NOT NULL DEFAULT '',
+ `mid` char(191) NOT NULL DEFAULT '',
+ `aid` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `uid` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `parent` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `parent_mid` char(191) NOT NULL DEFAULT '',
+ `thr_parent` char(191) NOT NULL DEFAULT '',
`created` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`edited` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`expires` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
@@ -598,81 +585,84 @@ CREATE TABLE IF NOT EXISTS `item` (
`received` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`changed` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`comments_closed` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
- `owner_xchan` char(255) NOT NULL DEFAULT '',
- `author_xchan` char(255) NOT NULL DEFAULT '',
- `source_xchan` char(255) NOT NULL DEFAULT '',
- `mimetype` char(255) NOT NULL DEFAULT '',
+ `owner_xchan` char(191) NOT NULL DEFAULT '',
+ `author_xchan` char(191) NOT NULL DEFAULT '',
+ `source_xchan` char(191) NOT NULL DEFAULT '',
+ `mimetype` char(191) NOT NULL DEFAULT '',
`title` text NOT NULL,
`body` mediumtext NOT NULL,
`html` mediumtext NOT NULL,
- `app` char(255) NOT NULL DEFAULT '',
+ `app` char(191) NOT NULL DEFAULT '',
`lang` char(64) NOT NULL DEFAULT '',
- `revision` int(10) unsigned NOT NULL DEFAULT '0',
- `verb` char(255) NOT NULL DEFAULT '',
- `obj_type` char(255) NOT NULL DEFAULT '',
+ `revision` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `verb` char(191) NOT NULL DEFAULT '',
+ `obj_type` char(191) NOT NULL DEFAULT '',
`obj` text NOT NULL,
- `tgt_type` char(255) NOT NULL DEFAULT '',
+ `tgt_type` char(191) NOT NULL DEFAULT '',
`target` text NOT NULL,
- `layout_mid` char(255) NOT NULL DEFAULT '',
+ `layout_mid` char(191) NOT NULL DEFAULT '',
`postopts` text NOT NULL,
`route` text NOT NULL,
- `llink` char(255) NOT NULL DEFAULT '',
- `plink` char(255) NOT NULL DEFAULT '',
- `resource_id` char(255) NOT NULL DEFAULT '',
+ `llink` char(191) NOT NULL DEFAULT '',
+ `plink` char(191) NOT NULL DEFAULT '',
+ `resource_id` char(191) NOT NULL DEFAULT '',
`resource_type` char(16) NOT NULL DEFAULT '',
`attach` mediumtext NOT NULL,
`sig` text NOT NULL,
`diaspora_meta` mediumtext NOT NULL,
- `location` char(255) NOT NULL DEFAULT '',
- `coord` char(255) NOT NULL DEFAULT '',
- `public_policy` char(255) NOT NULL DEFAULT '',
- `comment_policy` char(255) NOT NULL DEFAULT '',
+ `location` char(191) NOT NULL DEFAULT '',
+ `coord` char(191) NOT NULL DEFAULT '',
+ `public_policy` char(191) NOT NULL DEFAULT '',
+ `comment_policy` char(191) NOT NULL DEFAULT '',
`allow_cid` mediumtext NOT NULL,
`allow_gid` mediumtext NOT NULL,
`deny_cid` mediumtext NOT NULL,
`deny_gid` mediumtext NOT NULL,
- `item_restrict` int(11) NOT NULL DEFAULT '0',
- `item_flags` int(11) NOT NULL DEFAULT '0',
- `item_private` tinyint(1) NOT NULL DEFAULT '0',
- `item_origin` tinyint(1) NOT NULL DEFAULT '0',
- `item_unseen` tinyint(1) NOT NULL DEFAULT '0',
- `item_starred` tinyint(1) NOT NULL DEFAULT '0',
- `item_uplink` tinyint(1) NOT NULL DEFAULT '0',
- `item_consensus` tinyint(1) NOT NULL DEFAULT '0',
- `item_wall` tinyint(1) NOT NULL DEFAULT '0',
- `item_thread_top` tinyint(1) NOT NULL DEFAULT '0',
- `item_notshown` tinyint(1) NOT NULL DEFAULT '0',
- `item_nsfw` tinyint(1) NOT NULL DEFAULT '0',
- `item_relay` tinyint(1) NOT NULL DEFAULT '0',
- `item_mentionsme` tinyint(1) NOT NULL DEFAULT '0',
- `item_nocomment` tinyint(1) NOT NULL DEFAULT '0',
- `item_obscured` tinyint(1) NOT NULL DEFAULT '0',
- `item_verified` tinyint(1) NOT NULL DEFAULT '0',
- `item_retained` tinyint(1) NOT NULL DEFAULT '0',
- `item_rss` tinyint(1) NOT NULL DEFAULT '0',
- `item_deleted` tinyint(1) NOT NULL DEFAULT '0',
- `item_type` int(11) NOT NULL DEFAULT '0',
- `item_hidden` tinyint(1) NOT NULL DEFAULT '0',
- `item_unpublished` tinyint(1) NOT NULL DEFAULT '0',
- `item_delayed` tinyint(1) NOT NULL DEFAULT '0',
- `item_pending_remove` tinyint(1) NOT NULL DEFAULT '0',
- `item_blocked` tinyint(1) NOT NULL DEFAULT '0',
+ `item_restrict` int(11) NOT NULL DEFAULT 0 ,
+ `item_flags` int(11) NOT NULL DEFAULT 0 ,
+ `item_private` tinyint(1) NOT NULL DEFAULT 0 ,
+ `item_origin` tinyint(1) NOT NULL DEFAULT 0 ,
+ `item_unseen` tinyint(1) NOT NULL DEFAULT 0 ,
+ `item_starred` tinyint(1) NOT NULL DEFAULT 0 ,
+ `item_uplink` tinyint(1) NOT NULL DEFAULT 0 ,
+ `item_consensus` tinyint(1) NOT NULL DEFAULT 0 ,
+ `item_wall` tinyint(1) NOT NULL DEFAULT 0 ,
+ `item_thread_top` tinyint(1) NOT NULL DEFAULT 0 ,
+ `item_notshown` tinyint(1) NOT NULL DEFAULT 0 ,
+ `item_nsfw` tinyint(1) NOT NULL DEFAULT 0 ,
+ `item_relay` tinyint(1) NOT NULL DEFAULT 0 ,
+ `item_mentionsme` tinyint(1) NOT NULL DEFAULT 0 ,
+ `item_nocomment` tinyint(1) NOT NULL DEFAULT 0 ,
+ `item_obscured` tinyint(1) NOT NULL DEFAULT 0 ,
+ `item_verified` tinyint(1) NOT NULL DEFAULT 0 ,
+ `item_retained` tinyint(1) NOT NULL DEFAULT 0 ,
+ `item_rss` tinyint(1) NOT NULL DEFAULT 0 ,
+ `item_deleted` tinyint(1) NOT NULL DEFAULT 0 ,
+ `item_type` int(11) NOT NULL DEFAULT 0 ,
+ `item_hidden` tinyint(1) NOT NULL DEFAULT 0 ,
+ `item_unpublished` tinyint(1) NOT NULL DEFAULT 0 ,
+ `item_delayed` tinyint(1) NOT NULL DEFAULT 0 ,
+ `item_pending_remove` tinyint(1) NOT NULL DEFAULT 0 ,
+ `item_blocked` tinyint(1) NOT NULL DEFAULT 0 ,
PRIMARY KEY (`id`),
KEY `uid` (`uid`),
KEY `parent` (`parent`),
KEY `created` (`created`),
KEY `edited` (`edited`),
KEY `received` (`received`),
- KEY `uid_commented` (`uid`,`commented`),
- KEY `uid_created` (`uid`,`created`),
+ KEY `uid_commented` (`uid`, `commented`),
+ KEY `uid_created` (`uid`, `created`),
+ KEY `uid_item_unseen` (`uid`, `item_unseen`),
KEY `aid` (`aid`),
KEY `owner_xchan` (`owner_xchan`),
KEY `author_xchan` (`author_xchan`),
+ KEY `resource_id` (`resource_id`),
KEY `resource_type` (`resource_type`),
KEY `item_restrict` (`item_restrict`),
KEY `item_flags` (`item_flags`),
KEY `commented` (`commented`),
KEY `verb` (`verb`),
+ KEY `obj_type` (`obj_type`),
KEY `item_private` (`item_private`),
KEY `llink` (`llink`),
KEY `expires` (`expires`),
@@ -708,38 +698,32 @@ CREATE TABLE IF NOT EXISTS `item` (
KEY `item_unpublished` (`item_unpublished`),
KEY `item_delayed` (`item_delayed`),
KEY `item_pending_remove` (`item_pending_remove`),
- KEY `item_blocked` (`item_blocked`),
- FULLTEXT KEY `title` (`title`),
- FULLTEXT KEY `body` (`body`),
- FULLTEXT KEY `allow_cid` (`allow_cid`),
- FULLTEXT KEY `allow_gid` (`allow_gid`),
- FULLTEXT KEY `deny_cid` (`deny_cid`),
- FULLTEXT KEY `deny_gid` (`deny_gid`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+ KEY `item_blocked` (`item_blocked`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `item_id` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `iid` int(11) NOT NULL DEFAULT '0',
- `uid` int(11) NOT NULL DEFAULT '0',
- `sid` char(255) NOT NULL DEFAULT '',
- `service` char(255) NOT NULL DEFAULT '',
+ `iid` int(11) NOT NULL DEFAULT 0 ,
+ `uid` int(11) NOT NULL DEFAULT 0 ,
+ `sid` char(191) NOT NULL DEFAULT '',
+ `service` char(191) NOT NULL DEFAULT '',
PRIMARY KEY (`id`),
KEY `uid` (`uid`),
KEY `sid` (`sid`),
KEY `service` (`service`),
KEY `iid` (`iid`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `likes` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `channel_id` int(10) unsigned NOT NULL DEFAULT '0',
- `liker` char(128) NOT NULL DEFAULT '',
- `likee` char(128) NOT NULL DEFAULT '',
- `iid` int(11) unsigned NOT NULL DEFAULT '0',
- `i_mid` char(255) NOT NULL DEFAULT '',
- `verb` char(255) NOT NULL DEFAULT '',
- `target_type` char(255) NOT NULL DEFAULT '',
- `target_id` char(128) NOT NULL DEFAULT '',
+ `channel_id` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `liker` char(191) NOT NULL DEFAULT '',
+ `likee` char(191) NOT NULL DEFAULT '',
+ `iid` int(11) unsigned NOT NULL DEFAULT 0 ,
+ `i_mid` char(191) NOT NULL DEFAULT '',
+ `verb` char(191) NOT NULL DEFAULT '',
+ `target_type` char(191) NOT NULL DEFAULT '',
+ `target_id` char(191) NOT NULL DEFAULT '',
`target` mediumtext NOT NULL,
PRIMARY KEY (`id`),
KEY `liker` (`liker`),
@@ -750,29 +734,31 @@ CREATE TABLE IF NOT EXISTS `likes` (
KEY `target_type` (`target_type`),
KEY `channel_id` (`channel_id`),
KEY `target_id` (`target_id`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `mail` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `convid` int(10) unsigned NOT NULL DEFAULT '0',
- `conv_guid` char(255) NOT NULL DEFAULT '',
- `mail_flags` int(10) unsigned NOT NULL DEFAULT '0',
- `from_xchan` char(255) NOT NULL DEFAULT '',
- `to_xchan` char(255) NOT NULL DEFAULT '',
- `account_id` int(10) unsigned NOT NULL DEFAULT '0',
- `channel_id` int(10) unsigned NOT NULL DEFAULT '0',
+ `convid` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `conv_guid` char(191) NOT NULL DEFAULT '',
+ `mail_flags` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `from_xchan` char(191) NOT NULL DEFAULT '',
+ `to_xchan` char(191) NOT NULL DEFAULT '',
+ `account_id` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `channel_id` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `mail_mimetype` char(64) NOT NULL DEFAULT 'text/bbcode',
`title` text NOT NULL,
`body` mediumtext NOT NULL,
`sig` text NOT NULL,
`attach` mediumtext NOT NULL,
- `mid` char(255) NOT NULL DEFAULT '',
- `parent_mid` char(255) NOT NULL DEFAULT '',
- `mail_deleted` tinyint(4) NOT NULL DEFAULT '0',
- `mail_replied` tinyint(4) NOT NULL DEFAULT '0',
- `mail_isreply` tinyint(4) NOT NULL DEFAULT '0',
- `mail_seen` tinyint(4) NOT NULL DEFAULT '0',
- `mail_recalled` tinyint(4) NOT NULL DEFAULT '0',
- `mail_obscured` smallint(6) NOT NULL DEFAULT '0',
+ `mid` char(191) NOT NULL DEFAULT '',
+ `parent_mid` char(191) NOT NULL DEFAULT '',
+ `mail_deleted` tinyint(4) NOT NULL DEFAULT 0 ,
+ `mail_replied` tinyint(4) NOT NULL DEFAULT 0 ,
+ `mail_isreply` tinyint(4) NOT NULL DEFAULT 0 ,
+ `mail_seen` tinyint(4) NOT NULL DEFAULT 0 ,
+ `mail_recalled` tinyint(4) NOT NULL DEFAULT 0 ,
+ `mail_obscured` smallint(6) NOT NULL DEFAULT 0 ,
+ `mail_raw` tinyint(4) NOT NULL DEFAULT 0 ,
`created` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`expires` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
PRIMARY KEY (`id`),
@@ -793,14 +779,14 @@ CREATE TABLE IF NOT EXISTS `mail` (
KEY `mail_seen` (`mail_seen`),
KEY `mail_recalled` (`mail_recalled`),
KEY `mail_obscured` (`mail_obscured`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `menu` (
`menu_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `menu_channel_id` int(10) unsigned NOT NULL DEFAULT '0',
- `menu_name` char(255) NOT NULL DEFAULT '',
- `menu_desc` char(255) NOT NULL DEFAULT '',
- `menu_flags` int(11) NOT NULL DEFAULT '0',
+ `menu_channel_id` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `menu_name` char(191) NOT NULL DEFAULT '',
+ `menu_desc` char(191) NOT NULL DEFAULT '',
+ `menu_flags` int(11) NOT NULL DEFAULT 0 ,
`menu_created` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`menu_edited` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
PRIMARY KEY (`menu_id`),
@@ -809,41 +795,41 @@ CREATE TABLE IF NOT EXISTS `menu` (
KEY `menu_flags` (`menu_flags`),
KEY `menu_created` (`menu_created`),
KEY `menu_edited` (`menu_edited`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `menu_item` (
`mitem_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `mitem_link` char(255) NOT NULL DEFAULT '',
- `mitem_desc` char(255) NOT NULL DEFAULT '',
- `mitem_flags` int(11) NOT NULL DEFAULT '0',
+ `mitem_link` char(191) NOT NULL DEFAULT '',
+ `mitem_desc` char(191) NOT NULL DEFAULT '',
+ `mitem_flags` int(11) NOT NULL DEFAULT 0 ,
`allow_cid` mediumtext NOT NULL,
`allow_gid` mediumtext NOT NULL,
`deny_cid` mediumtext NOT NULL,
`deny_gid` mediumtext NOT NULL,
- `mitem_channel_id` int(10) unsigned NOT NULL DEFAULT '0',
- `mitem_menu_id` int(10) unsigned NOT NULL DEFAULT '0',
- `mitem_order` int(11) NOT NULL DEFAULT '0',
+ `mitem_channel_id` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `mitem_menu_id` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `mitem_order` int(11) NOT NULL DEFAULT 0 ,
PRIMARY KEY (`mitem_id`),
KEY `mitem_channel_id` (`mitem_channel_id`),
KEY `mitem_menu_id` (`mitem_menu_id`),
KEY `mitem_flags` (`mitem_flags`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `notify` (
`id` int(11) NOT NULL AUTO_INCREMENT,
- `hash` char(64) NOT NULL DEFAULT '',
- `xname` char(255) NOT NULL DEFAULT '',
- `url` char(255) NOT NULL DEFAULT '',
- `photo` char(255) NOT NULL DEFAULT '',
+ `hash` char(191) NOT NULL DEFAULT '',
+ `xname` char(191) NOT NULL DEFAULT '',
+ `url` char(191) NOT NULL DEFAULT '',
+ `photo` char(191) NOT NULL DEFAULT '',
`created` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`msg` mediumtext NOT NULL,
- `aid` int(11) NOT NULL DEFAULT '0',
- `uid` int(11) NOT NULL DEFAULT '0',
- `link` char(255) NOT NULL DEFAULT '',
- `parent` char(255) NOT NULL DEFAULT '',
- `seen` tinyint(1) NOT NULL DEFAULT '0',
- `ntype` int(11) NOT NULL DEFAULT '0',
- `verb` char(255) NOT NULL DEFAULT '',
+ `aid` int(11) NOT NULL DEFAULT 0 ,
+ `uid` int(11) NOT NULL DEFAULT 0 ,
+ `link` char(191) NOT NULL DEFAULT '',
+ `parent` char(191) NOT NULL DEFAULT '',
+ `seen` tinyint(1) NOT NULL DEFAULT 0 ,
+ `ntype` int(11) NOT NULL DEFAULT 0 ,
+ `verb` char(191) NOT NULL DEFAULT '',
`otype` char(16) NOT NULL DEFAULT '',
PRIMARY KEY (`id`),
KEY `ntype` (`ntype`),
@@ -855,21 +841,21 @@ CREATE TABLE IF NOT EXISTS `notify` (
KEY `link` (`link`),
KEY `otype` (`otype`),
KEY `aid` (`aid`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `obj` (
`obj_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
`obj_page` char(64) NOT NULL DEFAULT '',
- `obj_verb` char(255) NOT NULL DEFAULT '',
- `obj_type` int(10) unsigned NOT NULL DEFAULT '0',
- `obj_obj` char(255) NOT NULL DEFAULT '',
- `obj_channel` int(10) unsigned NOT NULL DEFAULT '0',
- `obj_term` char(255) NOT NULL DEFAULT '',
- `obj_url` char(255) NOT NULL DEFAULT '',
- `obj_imgurl` char(255) NOT NULL DEFAULT '',
+ `obj_verb` char(191) NOT NULL DEFAULT '',
+ `obj_type` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `obj_obj` char(191) NOT NULL DEFAULT '',
+ `obj_channel` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `obj_term` char(191) NOT NULL DEFAULT '',
+ `obj_url` char(191) NOT NULL DEFAULT '',
+ `obj_imgurl` char(191) NOT NULL DEFAULT '',
`obj_created` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`obj_edited` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
- `obj_quantity` int(11) NOT NULL DEFAULT '0',
+ `obj_quantity` int(11) NOT NULL DEFAULT 0 ,
`allow_cid` mediumtext NOT NULL,
`allow_gid` mediumtext NOT NULL,
`deny_cid` mediumtext NOT NULL,
@@ -886,22 +872,22 @@ CREATE TABLE IF NOT EXISTS `obj` (
KEY `obj_edited` (`obj_edited`),
KEY `obj_quantity` (`obj_quantity`),
KEY `obj_obj` (`obj_obj`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `outq` (
- `outq_hash` char(255) NOT NULL,
- `outq_account` int(10) unsigned NOT NULL DEFAULT '0',
- `outq_channel` int(10) unsigned NOT NULL DEFAULT '0',
+ `outq_hash` char(191) NOT NULL,
+ `outq_account` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `outq_channel` int(10) unsigned NOT NULL DEFAULT 0 ,
`outq_driver` char(32) NOT NULL DEFAULT '',
- `outq_posturl` char(255) NOT NULL DEFAULT '',
- `outq_async` tinyint(1) NOT NULL DEFAULT '0',
- `outq_delivered` tinyint(1) NOT NULL DEFAULT '0',
+ `outq_posturl` char(191) NOT NULL DEFAULT '',
+ `outq_async` tinyint(1) NOT NULL DEFAULT 0 ,
+ `outq_delivered` tinyint(1) NOT NULL DEFAULT 0 ,
`outq_created` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`outq_updated` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`outq_scheduled` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`outq_notify` mediumtext NOT NULL,
`outq_msg` mediumtext NOT NULL,
- `outq_priority` smallint(6) NOT NULL DEFAULT '0',
+ `outq_priority` smallint(6) NOT NULL DEFAULT 0 ,
PRIMARY KEY (`outq_hash`),
KEY `outq_account` (`outq_account`),
KEY `outq_channel` (`outq_channel`),
@@ -912,44 +898,56 @@ CREATE TABLE IF NOT EXISTS `outq` (
KEY `outq_async` (`outq_async`),
KEY `outq_delivered` (`outq_delivered`),
KEY `outq_priority` (`outq_priority`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
+
+
+CREATE TABLE IF NOT EXISTS pchan (
+ `pchan_id` int(11) UNSIGNED NOT NULL AUTO_INCREMENT,
+ `pchan_guid` char(191) NOT NULL DEFAULT '',
+ `pchan_hash` char(191) NOT NULL DEFAULT '',
+ `pchan_pubkey` text NOT NULL,
+ `pchan_prvkey` text NOT NULL,
+ PRIMARY KEY (`pchan_id`),
+ KEY `pchan_guid` (`pchan_guid`),
+ KEY `pchan_hash` (`pchan_hash`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
+
CREATE TABLE IF NOT EXISTS `pconfig` (
`id` int(11) NOT NULL AUTO_INCREMENT,
- `uid` int(11) NOT NULL DEFAULT '0',
- `cat` char(255) CHARACTER SET ascii NOT NULL DEFAULT '',
- `k` char(255) CHARACTER SET ascii NOT NULL DEFAULT '',
+ `uid` int(11) NOT NULL DEFAULT 0 ,
+ `cat` char(191) NOT NULL DEFAULT '',
+ `k` char(191) NOT NULL DEFAULT '',
`v` mediumtext NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `access` (`uid`,`cat`,`k`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
-
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `photo` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `aid` int(10) unsigned NOT NULL DEFAULT '0',
- `uid` int(10) unsigned NOT NULL DEFAULT '0',
- `xchan` char(255) NOT NULL DEFAULT '',
- `resource_id` char(255) NOT NULL DEFAULT '',
+ `aid` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `uid` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `xchan` char(191) NOT NULL DEFAULT '',
+ `resource_id` char(191) NOT NULL DEFAULT '',
`created` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`edited` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
- `title` char(255) NOT NULL DEFAULT '',
+ `title` char(191) NOT NULL DEFAULT '',
`description` text NOT NULL,
- `album` char(255) NOT NULL DEFAULT '',
- `filename` char(255) NOT NULL DEFAULT '',
+ `album` char(191) NOT NULL DEFAULT '',
+ `filename` char(191) NOT NULL DEFAULT '',
`mimetype` char(128) NOT NULL DEFAULT 'image/jpeg',
- `height` smallint(6) NOT NULL DEFAULT '0',
- `width` smallint(6) NOT NULL DEFAULT '0',
- `filesize` int(10) unsigned NOT NULL DEFAULT '0',
+ `height` smallint(6) NOT NULL DEFAULT 0 ,
+ `width` smallint(6) NOT NULL DEFAULT 0 ,
+ `filesize` int(10) unsigned NOT NULL DEFAULT 0 ,
`content` mediumblob NOT NULL,
- `imgscale` tinyint(3) NOT NULL DEFAULT '0',
- `photo_usage` smallint(6) NOT NULL DEFAULT '0',
- `profile` tinyint(1) NOT NULL DEFAULT '0',
- `is_nsfw` tinyint(1) NOT NULL DEFAULT '0',
- `os_storage` tinyint(1) NOT NULL DEFAULT '0',
+ `imgscale` tinyint(3) NOT NULL DEFAULT 0 ,
+ `photo_usage` smallint(6) NOT NULL DEFAULT 0 ,
+ `profile` tinyint(1) NOT NULL DEFAULT 0 ,
+ `is_nsfw` tinyint(1) NOT NULL DEFAULT 0 ,
+ `os_storage` tinyint(1) NOT NULL DEFAULT 0 ,
`os_path` mediumtext NOT NULL,
`display_path` mediumtext NOT NULL,
- `photo_flags` int(10) unsigned NOT NULL DEFAULT '0',
+ `photo_flags` int(10) unsigned NOT NULL DEFAULT 0 ,
`allow_cid` mediumtext NOT NULL,
`allow_gid` mediumtext NOT NULL,
`deny_cid` mediumtext NOT NULL,
@@ -968,85 +966,85 @@ CREATE TABLE IF NOT EXISTS `photo` (
KEY `is_nsfw` (`is_nsfw`),
KEY `os_storage` (`os_storage`),
KEY `photo_usage` (`photo_usage`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `poll` (
`poll_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `poll_channel` int(10) unsigned NOT NULL DEFAULT '0',
+ `poll_channel` int(10) unsigned NOT NULL DEFAULT 0 ,
`poll_desc` text NOT NULL,
- `poll_flags` int(11) NOT NULL DEFAULT '0',
- `poll_votes` int(11) NOT NULL DEFAULT '0',
+ `poll_flags` int(11) NOT NULL DEFAULT 0 ,
+ `poll_votes` int(11) NOT NULL DEFAULT 0 ,
PRIMARY KEY (`poll_id`),
KEY `poll_channel` (`poll_channel`),
KEY `poll_flags` (`poll_flags`),
KEY `poll_votes` (`poll_votes`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `poll_elm` (
`pelm_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `pelm_poll` int(10) unsigned NOT NULL DEFAULT '0',
+ `pelm_poll` int(10) unsigned NOT NULL DEFAULT 0 ,
`pelm_desc` text NOT NULL,
- `pelm_flags` int(11) NOT NULL DEFAULT '0',
- `pelm_result` float NOT NULL DEFAULT '0',
+ `pelm_flags` int(11) NOT NULL DEFAULT 0 ,
+ `pelm_result` float NOT NULL DEFAULT 0 ,
PRIMARY KEY (`pelm_id`),
KEY `pelm_poll` (`pelm_poll`),
KEY `pelm_result` (`pelm_result`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `profdef` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `field_name` char(255) NOT NULL DEFAULT '',
+ `field_name` char(191) NOT NULL DEFAULT '',
`field_type` char(16) NOT NULL DEFAULT '',
- `field_desc` char(255) NOT NULL DEFAULT '',
- `field_help` char(255) NOT NULL DEFAULT '',
+ `field_desc` char(191) NOT NULL DEFAULT '',
+ `field_help` char(191) NOT NULL DEFAULT '',
`field_inputs` mediumtext NOT NULL,
PRIMARY KEY (`id`),
KEY `field_name` (`field_name`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `profext` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `channel_id` int(10) unsigned NOT NULL DEFAULT '0',
- `hash` char(255) NOT NULL DEFAULT '',
- `k` char(255) NOT NULL DEFAULT '',
+ `channel_id` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `hash` char(191) NOT NULL DEFAULT '',
+ `k` char(191) NOT NULL DEFAULT '',
`v` mediumtext NOT NULL,
PRIMARY KEY (`id`),
KEY `channel_id` (`channel_id`),
KEY `hash` (`hash`),
KEY `k` (`k`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `profile` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`profile_guid` char(64) NOT NULL DEFAULT '',
- `aid` int(10) unsigned NOT NULL DEFAULT '0',
- `uid` int(11) NOT NULL DEFAULT '0',
- `profile_name` char(255) NOT NULL DEFAULT '',
- `is_default` tinyint(1) NOT NULL DEFAULT '0',
- `hide_friends` tinyint(1) NOT NULL DEFAULT '0',
- `fullname` char(255) NOT NULL DEFAULT '',
- `pdesc` char(255) NOT NULL DEFAULT '',
+ `aid` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `uid` int(11) NOT NULL DEFAULT 0 ,
+ `profile_name` char(191) NOT NULL DEFAULT '',
+ `is_default` tinyint(1) NOT NULL DEFAULT 0 ,
+ `hide_friends` tinyint(1) NOT NULL DEFAULT 0 ,
+ `fullname` char(191) NOT NULL DEFAULT '',
+ `pdesc` char(191) NOT NULL DEFAULT '',
`chandesc` text NOT NULL,
`dob` char(32) NOT NULL DEFAULT '0000-00-00',
- `dob_tz` char(255) NOT NULL DEFAULT 'UTC',
- `address` char(255) NOT NULL DEFAULT '',
- `locality` char(255) NOT NULL DEFAULT '',
- `region` char(255) NOT NULL DEFAULT '',
+ `dob_tz` char(191) NOT NULL DEFAULT 'UTC',
+ `address` char(191) NOT NULL DEFAULT '',
+ `locality` char(191) NOT NULL DEFAULT '',
+ `region` char(191) NOT NULL DEFAULT '',
`postal_code` char(32) NOT NULL DEFAULT '',
- `country_name` char(255) NOT NULL DEFAULT '',
- `hometown` char(255) NOT NULL DEFAULT '',
+ `country_name` char(191) NOT NULL DEFAULT '',
+ `hometown` char(191) NOT NULL DEFAULT '',
`gender` char(32) NOT NULL DEFAULT '',
- `marital` char(255) NOT NULL DEFAULT '',
+ `marital` char(191) NOT NULL DEFAULT '',
`partner` text NOT NULL,
`howlong` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
- `sexual` char(255) NOT NULL DEFAULT '',
- `politic` char(255) NOT NULL DEFAULT '',
- `religion` char(255) NOT NULL DEFAULT '',
+ `sexual` char(191) NOT NULL DEFAULT '',
+ `politic` char(191) NOT NULL DEFAULT '',
+ `religion` char(191) NOT NULL DEFAULT '',
`keywords` text NOT NULL,
`likes` text NOT NULL,
`dislikes` text NOT NULL,
`about` text NOT NULL,
- `summary` char(255) NOT NULL DEFAULT '',
+ `summary` char(191) NOT NULL DEFAULT '',
`music` text NOT NULL,
`book` text NOT NULL,
`tv` text NOT NULL,
@@ -1057,11 +1055,11 @@ CREATE TABLE IF NOT EXISTS `profile` (
`education` text NOT NULL,
`contact` text NOT NULL,
`channels` text NOT NULL,
- `homepage` char(255) NOT NULL DEFAULT '',
- `photo` char(255) NOT NULL DEFAULT '',
- `thumb` char(255) NOT NULL DEFAULT '',
- `publish` tinyint(1) NOT NULL DEFAULT '0',
- `profile_vcard` text NOT NULL DEFAULT '',
+ `homepage` char(191) NOT NULL DEFAULT '',
+ `photo` char(191) NOT NULL DEFAULT '',
+ `thumb` char(191) NOT NULL DEFAULT '',
+ `publish` tinyint(1) NOT NULL DEFAULT 0 ,
+ `profile_vcard` text NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `guid` (`profile_guid`,`uid`),
KEY `uid` (`uid`),
@@ -1077,87 +1075,87 @@ CREATE TABLE IF NOT EXISTS `profile` (
KEY `postal_code` (`postal_code`),
KEY `country_name` (`country_name`),
KEY `profile_guid` (`profile_guid`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `profile_check` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `uid` int(10) unsigned NOT NULL DEFAULT '0',
- `cid` int(10) unsigned NOT NULL DEFAULT '0',
- `dfrn_id` char(255) NOT NULL DEFAULT '',
- `sec` char(255) NOT NULL DEFAULT '',
- `expire` int(11) NOT NULL DEFAULT '0',
+ `uid` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `cid` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `dfrn_id` char(191) NOT NULL DEFAULT '',
+ `sec` char(191) NOT NULL DEFAULT '',
+ `expire` int(11) NOT NULL DEFAULT 0 ,
PRIMARY KEY (`id`),
KEY `uid` (`uid`),
KEY `cid` (`cid`),
KEY `dfrn_id` (`dfrn_id`),
KEY `sec` (`sec`),
KEY `expire` (`expire`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `register` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `hash` char(255) NOT NULL DEFAULT '',
+ `hash` char(191) NOT NULL DEFAULT '',
`created` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
- `uid` int(10) unsigned NOT NULL DEFAULT '0',
- `password` char(255) NOT NULL DEFAULT '',
+ `uid` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `password` char(191) NOT NULL DEFAULT '',
`lang` char(16) NOT NULL DEFAULT '',
PRIMARY KEY (`id`),
KEY `hash` (`hash`),
KEY `created` (`created`),
KEY `uid` (`uid`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `session` (
`id` bigint(20) unsigned NOT NULL AUTO_INCREMENT,
- `sid` char(255) NOT NULL DEFAULT '',
+ `sid` char(191) NOT NULL DEFAULT '',
`sess_data` text NOT NULL,
- `expire` bigint(20) unsigned NOT NULL DEFAULT '0',
+ `expire` bigint(20) unsigned NOT NULL DEFAULT 0 ,
PRIMARY KEY (`id`),
KEY `sid` (`sid`),
KEY `expire` (`expire`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `shares` (
`share_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `share_type` int(11) NOT NULL DEFAULT '0',
- `share_target` int(10) unsigned NOT NULL DEFAULT '0',
- `share_xchan` char(255) NOT NULL DEFAULT '',
+ `share_type` int(11) NOT NULL DEFAULT 0 ,
+ `share_target` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `share_xchan` char(191) NOT NULL DEFAULT '',
PRIMARY KEY (`share_id`),
KEY `share_type` (`share_type`),
KEY `share_target` (`share_target`),
KEY `share_xchan` (`share_xchan`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `sign` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `iid` int(10) unsigned NOT NULL DEFAULT '0',
- `retract_iid` int(10) unsigned NOT NULL DEFAULT '0',
+ `iid` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `retract_iid` int(10) unsigned NOT NULL DEFAULT 0 ,
`signed_text` mediumtext NOT NULL,
`signature` text NOT NULL,
- `signer` char(255) NOT NULL DEFAULT '',
+ `signer` char(191) NOT NULL DEFAULT '',
PRIMARY KEY (`id`),
KEY `iid` (`iid`),
KEY `retract_iid` (`retract_iid`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `site` (
- `site_url` char(255) NOT NULL,
- `site_access` int(11) NOT NULL DEFAULT '0',
- `site_flags` int(11) NOT NULL DEFAULT '0',
+ `site_url` char(191) NOT NULL,
+ `site_access` int(11) NOT NULL DEFAULT 0 ,
+ `site_flags` int(11) NOT NULL DEFAULT 0 ,
`site_update` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`site_pull` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`site_sync` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
- `site_directory` char(255) NOT NULL DEFAULT '',
- `site_register` int(11) NOT NULL DEFAULT '0',
- `site_sellpage` char(255) NOT NULL DEFAULT '',
- `site_location` char(255) NOT NULL DEFAULT '',
- `site_realm` char(255) NOT NULL DEFAULT '',
- `site_valid` smallint NOT NULL DEFAULT '0',
- `site_dead` smallint NOT NULL DEFAULT '0',
- `site_type` smallint NOT NULL DEFAULT '0',
- `site_project` char(255) NOT NULL DEFAULT '',
+ `site_directory` char(191) NOT NULL DEFAULT '',
+ `site_register` int(11) NOT NULL DEFAULT 0 ,
+ `site_sellpage` char(191) NOT NULL DEFAULT '',
+ `site_location` char(191) NOT NULL DEFAULT '',
+ `site_realm` char(191) NOT NULL DEFAULT '',
+ `site_valid` smallint NOT NULL DEFAULT 0 ,
+ `site_dead` smallint NOT NULL DEFAULT 0 ,
+ `site_type` smallint NOT NULL DEFAULT 0 ,
+ `site_project` char(191) NOT NULL DEFAULT '',
`site_version` varchar(32) NOT NULL DEFAULT '',
- `site_crypto` text NOT NULL DEFAULT '',
+ `site_crypto` text NOT NULL,
PRIMARY KEY (`site_url`),
KEY `site_flags` (`site_flags`),
KEY `site_update` (`site_update`),
@@ -1171,42 +1169,42 @@ CREATE TABLE IF NOT EXISTS `site` (
KEY `site_dead` (`site_dead`),
KEY `site_type` (`site_type`),
KEY `site_project` (`site_project`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `source` (
`src_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `src_channel_id` int(10) unsigned NOT NULL DEFAULT '0',
- `src_channel_xchan` char(255) NOT NULL DEFAULT '',
- `src_xchan` char(255) NOT NULL DEFAULT '',
+ `src_channel_id` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `src_channel_xchan` char(191) NOT NULL DEFAULT '',
+ `src_xchan` char(191) NOT NULL DEFAULT '',
`src_patt` mediumtext NOT NULL,
`src_tag` mediumtext NOT NULL,
PRIMARY KEY (`src_id`),
KEY `src_channel_id` (`src_channel_id`),
KEY `src_channel_xchan` (`src_channel_xchan`),
KEY `src_xchan` (`src_xchan`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `sys_perms` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `cat` char(255) NOT NULL DEFAULT '',
- `k` char(255) NOT NULL DEFAULT '',
+ `cat` char(191) NOT NULL DEFAULT '',
+ `k` char(191) NOT NULL DEFAULT '',
`v` mediumtext NOT NULL,
- `public_perm` tinyint(1) unsigned NOT NULL DEFAULT '0',
+ `public_perm` tinyint(1) unsigned NOT NULL DEFAULT 0 ,
PRIMARY KEY (`id`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `term` (
`tid` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `aid` int(10) unsigned NOT NULL DEFAULT '0',
- `uid` int(10) unsigned NOT NULL DEFAULT '0',
- `oid` int(10) unsigned NOT NULL DEFAULT '0',
- `otype` tinyint(3) unsigned NOT NULL DEFAULT '0',
- `ttype` tinyint(3) unsigned NOT NULL DEFAULT '0',
- `term` char(255) NOT NULL DEFAULT '',
- `url` char(255) NOT NULL DEFAULT '',
- `imgurl` char(255) NOT NULL DEFAULT '',
- `term_hash` char(255) NOT NULL DEFAULT '',
- `parent_hash` char(255) NOT NULL DEFAULT '',
+ `aid` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `uid` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `oid` int(10) unsigned NOT NULL DEFAULT 0 ,
+ `otype` tinyint(3) unsigned NOT NULL DEFAULT 0 ,
+ `ttype` tinyint(3) unsigned NOT NULL DEFAULT 0 ,
+ `term` char(191) NOT NULL DEFAULT '',
+ `url` char(191) NOT NULL DEFAULT '',
+ `imgurl` char(191) NOT NULL DEFAULT '',
+ `term_hash` char(191) NOT NULL DEFAULT '',
+ `parent_hash` char(191) NOT NULL DEFAULT '',
PRIMARY KEY (`tid`),
KEY `oid` (`oid`),
KEY `otype` (`otype`),
@@ -1217,29 +1215,29 @@ CREATE TABLE IF NOT EXISTS `term` (
KEY `imgurl` (`imgurl`),
KEY `term_hash` (`term_hash`),
KEY `parent_hash` (`parent_hash`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `tokens` (
- `id` varchar(40) NOT NULL DEFAULT '',
+ `id` varchar(191) NOT NULL DEFAULT '',
`secret` text NOT NULL,
- `client_id` varchar(20) NOT NULL DEFAULT '',
- `expires` bigint(20) unsigned NOT NULL DEFAULT '0',
+ `client_id` varchar(191) NOT NULL DEFAULT '',
+ `expires` bigint(20) unsigned NOT NULL DEFAULT 0 ,
`auth_scope` varchar(512) NOT NULL DEFAULT '',
- `uid` int(11) NOT NULL DEFAULT '0',
+ `uid` int(11) NOT NULL DEFAULT 0 ,
PRIMARY KEY (`id`),
KEY `client_id` (`client_id`),
KEY `expires` (`expires`),
KEY `uid` (`uid`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `updates` (
`ud_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `ud_hash` char(128) NOT NULL DEFAULT '',
- `ud_guid` char(255) NOT NULL DEFAULT '',
+ `ud_hash` char(191) NOT NULL DEFAULT '',
+ `ud_guid` char(191) NOT NULL DEFAULT '',
`ud_date` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`ud_last` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
- `ud_flags` int(11) NOT NULL DEFAULT '0',
- `ud_addr` char(255) NOT NULL DEFAULT '',
+ `ud_flags` int(11) NOT NULL DEFAULT 0 ,
+ `ud_addr` char(191) NOT NULL DEFAULT '',
PRIMARY KEY (`ud_id`),
KEY `ud_date` (`ud_date`),
KEY `ud_guid` (`ud_guid`),
@@ -1247,14 +1245,14 @@ CREATE TABLE IF NOT EXISTS `updates` (
KEY `ud_flags` (`ud_flags`),
KEY `ud_addr` (`ud_addr`),
KEY `ud_last` (`ud_last`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `verify` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `channel` int(10) unsigned NOT NULL DEFAULT '0',
+ `channel` int(10) unsigned NOT NULL DEFAULT 0 ,
`vtype` char(32) NOT NULL DEFAULT '',
- `token` char(255) NOT NULL DEFAULT '',
- `meta` char(255) NOT NULL DEFAULT '',
+ `token` char(191) NOT NULL DEFAULT '',
+ `meta` char(191) NOT NULL DEFAULT '',
`created` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
PRIMARY KEY (`id`),
KEY `channel` (`channel`),
@@ -1262,47 +1260,47 @@ CREATE TABLE IF NOT EXISTS `verify` (
KEY `token` (`token`),
KEY `meta` (`meta`),
KEY `created` (`created`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `vote` (
`vote_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `vote_poll` int(11) NOT NULL DEFAULT '0',
- `vote_element` int(11) NOT NULL DEFAULT '0',
+ `vote_poll` int(11) NOT NULL DEFAULT 0 ,
+ `vote_element` int(11) NOT NULL DEFAULT 0 ,
`vote_result` text NOT NULL,
- `vote_xchan` char(255) NOT NULL DEFAULT '',
+ `vote_xchan` char(191) NOT NULL DEFAULT '',
PRIMARY KEY (`vote_id`),
UNIQUE KEY `vote_vote` (`vote_poll`,`vote_element`,`vote_xchan`),
KEY `vote_poll` (`vote_poll`),
KEY `vote_element` (`vote_element`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `xchan` (
- `xchan_hash` char(255) NOT NULL,
- `xchan_guid` char(255) NOT NULL DEFAULT '',
+ `xchan_hash` char(191) NOT NULL,
+ `xchan_guid` char(191) NOT NULL DEFAULT '',
`xchan_guid_sig` text NOT NULL,
`xchan_pubkey` text NOT NULL,
`xchan_photo_mimetype` char(32) NOT NULL DEFAULT 'image/jpeg',
- `xchan_photo_l` char(255) NOT NULL DEFAULT '',
- `xchan_photo_m` char(255) NOT NULL DEFAULT '',
- `xchan_photo_s` char(255) NOT NULL DEFAULT '',
- `xchan_addr` char(255) NOT NULL DEFAULT '',
- `xchan_url` char(255) NOT NULL DEFAULT '',
- `xchan_connurl` char(255) NOT NULL DEFAULT '',
- `xchan_follow` char(255) NOT NULL DEFAULT '',
- `xchan_connpage` char(255) NOT NULL DEFAULT '',
- `xchan_name` char(255) NOT NULL DEFAULT '',
- `xchan_network` char(255) NOT NULL DEFAULT '',
- `xchan_instance_url` char(255) NOT NULL DEFAULT '',
- `xchan_flags` int(10) unsigned NOT NULL DEFAULT '0',
+ `xchan_photo_l` char(191) NOT NULL DEFAULT '',
+ `xchan_photo_m` char(191) NOT NULL DEFAULT '',
+ `xchan_photo_s` char(191) NOT NULL DEFAULT '',
+ `xchan_addr` char(191) NOT NULL DEFAULT '',
+ `xchan_url` char(191) NOT NULL DEFAULT '',
+ `xchan_connurl` char(191) NOT NULL DEFAULT '',
+ `xchan_follow` char(191) NOT NULL DEFAULT '',
+ `xchan_connpage` char(191) NOT NULL DEFAULT '',
+ `xchan_name` char(191) NOT NULL DEFAULT '',
+ `xchan_network` char(191) NOT NULL DEFAULT '',
+ `xchan_instance_url` char(191) NOT NULL DEFAULT '',
+ `xchan_flags` int(10) unsigned NOT NULL DEFAULT 0 ,
`xchan_photo_date` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
`xchan_name_date` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
- `xchan_hidden` tinyint(1) NOT NULL DEFAULT '0',
- `xchan_orphan` tinyint(1) NOT NULL DEFAULT '0',
- `xchan_censored` tinyint(1) NOT NULL DEFAULT '0',
- `xchan_selfcensored` tinyint(1) NOT NULL DEFAULT '0',
- `xchan_system` tinyint(1) NOT NULL DEFAULT '0',
- `xchan_pubforum` tinyint(1) NOT NULL DEFAULT '0',
- `xchan_deleted` tinyint(1) NOT NULL DEFAULT '0',
+ `xchan_hidden` tinyint(1) NOT NULL DEFAULT 0 ,
+ `xchan_orphan` tinyint(1) NOT NULL DEFAULT 0 ,
+ `xchan_censored` tinyint(1) NOT NULL DEFAULT 0 ,
+ `xchan_selfcensored` tinyint(1) NOT NULL DEFAULT 0 ,
+ `xchan_system` tinyint(1) NOT NULL DEFAULT 0 ,
+ `xchan_pubforum` tinyint(1) NOT NULL DEFAULT 0 ,
+ `xchan_deleted` tinyint(1) NOT NULL DEFAULT 0 ,
PRIMARY KEY (`xchan_hash`),
KEY `xchan_guid` (`xchan_guid`),
KEY `xchan_addr` (`xchan_addr`),
@@ -1320,50 +1318,50 @@ CREATE TABLE IF NOT EXISTS `xchan` (
KEY `xchan_system` (`xchan_system`),
KEY `xchan_pubforum` (`xchan_pubforum`),
KEY `xchan_deleted` (`xchan_deleted`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `xchat` (
`xchat_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `xchat_url` char(255) NOT NULL DEFAULT '',
- `xchat_desc` char(255) NOT NULL DEFAULT '',
- `xchat_xchan` char(255) NOT NULL DEFAULT '',
+ `xchat_url` char(191) NOT NULL DEFAULT '',
+ `xchat_desc` char(191) NOT NULL DEFAULT '',
+ `xchat_xchan` char(191) NOT NULL DEFAULT '',
`xchat_edited` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
PRIMARY KEY (`xchat_id`),
KEY `xchat_url` (`xchat_url`),
KEY `xchat_desc` (`xchat_desc`),
KEY `xchat_xchan` (`xchat_xchan`),
KEY `xchat_edited` (`xchat_edited`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `xconfig` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `xchan` char(255) NOT NULL DEFAULT '',
- `cat` char(255) NOT NULL DEFAULT '',
- `k` char(255) NOT NULL DEFAULT '',
+ `xchan` char(191) NOT NULL DEFAULT '',
+ `cat` char(191) NOT NULL DEFAULT '',
+ `k` char(191) NOT NULL DEFAULT '',
`v` mediumtext NOT NULL,
PRIMARY KEY (`id`),
KEY `xchan` (`xchan`),
KEY `cat` (`cat`),
KEY `k` (`k`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `xign` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `uid` int(11) NOT NULL DEFAULT '0',
- `xchan` char(255) NOT NULL DEFAULT '',
+ `uid` int(11) NOT NULL DEFAULT 0 ,
+ `xchan` char(191) NOT NULL DEFAULT '',
PRIMARY KEY (`id`),
KEY `uid` (`uid`),
KEY `xchan` (`xchan`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `xlink` (
`xlink_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `xlink_xchan` char(255) NOT NULL DEFAULT '',
- `xlink_link` char(255) NOT NULL DEFAULT '',
- `xlink_rating` int(11) NOT NULL DEFAULT '0',
+ `xlink_xchan` char(191) NOT NULL DEFAULT '',
+ `xlink_link` char(191) NOT NULL DEFAULT '',
+ `xlink_rating` int(11) NOT NULL DEFAULT 0 ,
`xlink_rating_text` text NOT NULL,
`xlink_updated` datetime NOT NULL DEFAULT '0001-01-01 00:00:00',
- `xlink_static` tinyint(1) NOT NULL DEFAULT '0',
+ `xlink_static` tinyint(1) NOT NULL DEFAULT 0 ,
`xlink_sig` text NOT NULL,
PRIMARY KEY (`xlink_id`),
KEY `xlink_xchan` (`xlink_xchan`),
@@ -1371,35 +1369,35 @@ CREATE TABLE IF NOT EXISTS `xlink` (
KEY `xlink_updated` (`xlink_updated`),
KEY `xlink_rating` (`xlink_rating`),
KEY `xlink_static` (`xlink_static`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `xperm` (
`xp_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
`xp_client` varchar(20) NOT NULL DEFAULT '',
- `xp_channel` int(10) unsigned NOT NULL DEFAULT '0',
+ `xp_channel` int(10) unsigned NOT NULL DEFAULT 0 ,
`xp_perm` varchar(64) NOT NULL DEFAULT '',
PRIMARY KEY (`xp_id`),
KEY `xp_client` (`xp_client`),
KEY `xp_channel` (`xp_channel`),
KEY `xp_perm` (`xp_perm`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `xprof` (
- `xprof_hash` char(255) NOT NULL,
- `xprof_age` tinyint(3) unsigned NOT NULL DEFAULT '0',
- `xprof_desc` char(255) NOT NULL DEFAULT '',
+ `xprof_hash` char(191) NOT NULL,
+ `xprof_age` tinyint(3) unsigned NOT NULL DEFAULT 0 ,
+ `xprof_desc` char(191) NOT NULL DEFAULT '',
`xprof_dob` char(12) NOT NULL DEFAULT '',
- `xprof_gender` char(255) NOT NULL DEFAULT '',
- `xprof_marital` char(255) NOT NULL DEFAULT '',
- `xprof_sexual` char(255) NOT NULL DEFAULT '',
- `xprof_locale` char(255) NOT NULL DEFAULT '',
- `xprof_region` char(255) NOT NULL DEFAULT '',
+ `xprof_gender` char(191) NOT NULL DEFAULT '',
+ `xprof_marital` char(191) NOT NULL DEFAULT '',
+ `xprof_sexual` char(191) NOT NULL DEFAULT '',
+ `xprof_locale` char(191) NOT NULL DEFAULT '',
+ `xprof_region` char(191) NOT NULL DEFAULT '',
`xprof_postcode` char(32) NOT NULL DEFAULT '',
- `xprof_country` char(255) NOT NULL DEFAULT '',
+ `xprof_country` char(191) NOT NULL DEFAULT '',
`xprof_keywords` text NOT NULL,
`xprof_about` text NOT NULL,
- `xprof_homepage` char(255) NOT NULL DEFAULT '',
- `xprof_hometown` char(255) NOT NULL DEFAULT '',
+ `xprof_homepage` char(191) NOT NULL DEFAULT '',
+ `xprof_hometown` char(191) NOT NULL DEFAULT '',
PRIMARY KEY (`xprof_hash`),
KEY `xprof_desc` (`xprof_desc`),
KEY `xprof_dob` (`xprof_dob`),
@@ -1412,15 +1410,186 @@ CREATE TABLE IF NOT EXISTS `xprof` (
KEY `xprof_country` (`xprof_country`),
KEY `xprof_age` (`xprof_age`),
KEY `xprof_hometown` (`xprof_hometown`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE IF NOT EXISTS `xtag` (
`xtag_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
- `xtag_hash` char(255) NOT NULL DEFAULT '',
- `xtag_term` char(255) NOT NULL DEFAULT '',
- `xtag_flags` int(11) NOT NULL DEFAULT '0',
+ `xtag_hash` char(191) NOT NULL DEFAULT '',
+ `xtag_term` char(191) NOT NULL DEFAULT '',
+ `xtag_flags` int(11) NOT NULL DEFAULT 0 ,
PRIMARY KEY (`xtag_id`),
KEY `xtag_term` (`xtag_term`),
KEY `xtag_hash` (`xtag_hash`),
KEY `xtag_flags` (`xtag_flags`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8;
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
+
+CREATE TABLE if not exists addressbooks (
+ id INT(11) UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ principaluri VARBINARY(255),
+ displayname VARCHAR(255),
+ uri VARBINARY(200),
+ description TEXT,
+ synctoken INT(11) UNSIGNED NOT NULL DEFAULT '1',
+ UNIQUE(principaluri(100), uri(100))
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
+
+CREATE TABLE if not exists cards (
+ id INT(11) UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ addressbookid INT(11) UNSIGNED NOT NULL,
+ carddata MEDIUMBLOB,
+ uri VARBINARY(200),
+ lastmodified INT(11) UNSIGNED,
+ etag VARBINARY(32),
+ size INT(11) UNSIGNED NOT NULL
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
+
+CREATE TABLE if not exists addressbookchanges (
+ id INT(11) UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ uri VARBINARY(200) NOT NULL,
+ synctoken INT(11) UNSIGNED NOT NULL,
+ addressbookid INT(11) UNSIGNED NOT NULL,
+ operation TINYINT(1) NOT NULL,
+ INDEX addressbookid_synctoken (addressbookid, synctoken)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
+
+CREATE TABLE if not exists calendarobjects (
+ id INT(11) UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ calendardata MEDIUMBLOB,
+ uri VARBINARY(200),
+ calendarid INTEGER UNSIGNED NOT NULL,
+ lastmodified INT(11) UNSIGNED,
+ etag VARBINARY(32),
+ size INT(11) UNSIGNED NOT NULL,
+ componenttype VARBINARY(8),
+ firstoccurence INT(11) UNSIGNED,
+ lastoccurence INT(11) UNSIGNED,
+ uid VARBINARY(200),
+ UNIQUE(calendarid, uri),
+ INDEX calendarid_time (calendarid, firstoccurence)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
+
+CREATE TABLE if not exists calendars (
+ id INTEGER UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ synctoken INTEGER UNSIGNED NOT NULL DEFAULT '1',
+ components VARBINARY(21)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
+
+CREATE TABLE if not exists calendarinstances (
+ id INTEGER UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ calendarid INTEGER UNSIGNED NOT NULL,
+ principaluri VARBINARY(100),
+ access TINYINT(1) NOT NULL DEFAULT '1' COMMENT '1 = owner, 2 = read, 3 = readwrite',
+ displayname VARCHAR(100),
+ uri VARBINARY(200),
+ description TEXT,
+ calendarorder INT(11) UNSIGNED NOT NULL DEFAULT '0',
+ calendarcolor VARBINARY(10),
+ timezone TEXT,
+ transparent TINYINT(1) NOT NULL DEFAULT '0',
+ share_href VARBINARY(100),
+ share_displayname VARCHAR(100),
+ share_invitestatus TINYINT(1) NOT NULL DEFAULT '2' COMMENT '1 = noresponse, 2 = accepted, 3 = declined, 4 = invalid',
+ UNIQUE(principaluri, uri),
+ UNIQUE(calendarid, principaluri),
+ UNIQUE(calendarid, share_href)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
+
+CREATE TABLE if not exists calendarchanges (
+ id INT(11) UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ uri VARBINARY(200) NOT NULL,
+ synctoken INT(11) UNSIGNED NOT NULL,
+ calendarid INT(11) UNSIGNED NOT NULL,
+ operation TINYINT(1) NOT NULL,
+ INDEX calendarid_synctoken (calendarid, synctoken)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
+
+CREATE TABLE if not exists calendarsubscriptions (
+ id INT(11) UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ uri VARBINARY(200) NOT NULL,
+ principaluri VARBINARY(100) NOT NULL,
+ source TEXT,
+ displayname VARCHAR(100),
+ refreshrate VARCHAR(10),
+ calendarorder INT(11) UNSIGNED NOT NULL DEFAULT '0',
+ calendarcolor VARBINARY(10),
+ striptodos TINYINT(1) NULL,
+ stripalarms TINYINT(1) NULL,
+ stripattachments TINYINT(1) NULL,
+ lastmodified INT(11) UNSIGNED,
+ UNIQUE(principaluri, uri)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
+
+CREATE TABLE if not exists schedulingobjects (
+ id INT(11) UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ principaluri VARBINARY(255),
+ calendardata MEDIUMBLOB,
+ uri VARBINARY(200),
+ lastmodified INT(11) UNSIGNED,
+ etag VARBINARY(32),
+ size INT(11) UNSIGNED NOT NULL
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
+
+CREATE TABLE if not exists locks (
+ id INTEGER UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ owner VARCHAR(100),
+ timeout INTEGER UNSIGNED,
+ created INTEGER,
+ token VARBINARY(100),
+ scope TINYINT,
+ depth TINYINT,
+ uri VARBINARY(1000),
+ INDEX(token),
+ INDEX(uri(100))
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
+
+CREATE TABLE if not exists principals (
+ id INTEGER UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ uri VARBINARY(200) NOT NULL,
+ email VARBINARY(80),
+ displayname VARCHAR(80),
+ UNIQUE(uri)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
+
+CREATE TABLE if not exists groupmembers (
+ id INTEGER UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ principal_id INTEGER UNSIGNED NOT NULL,
+ member_id INTEGER UNSIGNED NOT NULL,
+ UNIQUE(principal_id, member_id)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
+
+CREATE TABLE if not exists propertystorage (
+ id INT UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ path VARBINARY(1024) NOT NULL,
+ name VARBINARY(100) NOT NULL,
+ valuetype INT UNSIGNED,
+ value MEDIUMBLOB
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
+
+CREATE UNIQUE INDEX path_property ON propertystorage (path(600), name(100));
+
+CREATE TABLE if not exists users (
+ id INTEGER UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ username VARBINARY(50),
+ digesta1 VARBINARY(32),
+ UNIQUE(username)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
+
+CREATE TABLE if not exists calendarinstances (
+ id INTEGER UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ calendarid INTEGER UNSIGNED NOT NULL,
+ principaluri VARBINARY(100),
+ access TINYINT(1) NOT NULL DEFAULT '1' COMMENT '1 = owner, 2 = read, 3 = readwrite',
+ displayname VARCHAR(100),
+ uri VARBINARY(200),
+ description TEXT,
+ calendarorder INT(11) UNSIGNED NOT NULL DEFAULT '0',
+ calendarcolor VARBINARY(10),
+ timezone TEXT,
+ transparent TINYINT(1) NOT NULL DEFAULT '0',
+ share_href VARBINARY(100),
+ share_displayname VARCHAR(100),
+ share_invitestatus TINYINT(1) NOT NULL DEFAULT '2' COMMENT '1 = noresponse, 2 = accepted, 3 = declined, 4 = invalid',
+ UNIQUE(principaluri, uri),
+ UNIQUE(calendarid, principaluri),
+ UNIQUE(calendarid, share_href)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
diff --git a/install/schema_postgres.sql b/install/schema_postgres.sql
index e78425828..082817a60 100644
--- a/install/schema_postgres.sql
+++ b/install/schema_postgres.sql
@@ -16,8 +16,8 @@ CREATE TABLE "abook" (
"abook_account" bigint NOT NULL,
"abook_channel" bigint NOT NULL,
"abook_xchan" text NOT NULL DEFAULT '',
- "abook_my_perms" bigint NOT NULL DEFAULT '0',
- "abook_their_perms" bigint NOT NULL DEFAULT '0',
+ "abook_my_perms" bigint NOT NULL,
+ "abook_their_perms" bigint NOT NULL,
"abook_closeness" numeric(3) NOT NULL DEFAULT '99',
"abook_created" timestamp NOT NULL DEFAULT '0001-01-01 00:00:00',
"abook_updated" timestamp NOT NULL DEFAULT '0001-01-01 00:00:00',
@@ -32,7 +32,8 @@ CREATE TABLE "abook" (
"abook_unconnected" smallint NOT NULL DEFAULT '0',
"abook_self" smallint NOT NULL DEFAULT '0',
"abook_feed" smallint NOT NULL DEFAULT '0',
- "abook_profile" char(64) NOT NULL DEFAULT '',
+ "abook_not_here" smallint NOT NULL DEFAULT '0',
+ "abook_profile" varchar(64) NOT NULL DEFAULT '',
"abook_incl" TEXT NOT NULL DEFAULT '',
"abook_excl" TEXT NOT NULL DEFAULT '',
"abook_instance" TEXT NOT NULL DEFAULT '',
@@ -41,8 +42,8 @@ CREATE TABLE "abook" (
create index "abook_account" on abook ("abook_account");
create index "abook_channel" on abook ("abook_channel");
create index "abook_xchan" on abook ("abook_xchan");
- create index "abook_my_perms" on abook ("abook_my_perms");
- create index "abook_their_perms" on abook ("abook_their_perms");
+ create index "abook_my_perms" on abook ("abook_my_perms");
+ create index "abook_their_perms" on abook ("abook_their_perms");
create index "abook_closeness" on abook ("abook_closeness");
create index "abook_created" on abook ("abook_created");
create index "abook_updated" on abook ("abook_updated");
@@ -55,6 +56,7 @@ CREATE TABLE "abook" (
create index "abook_unconnected" on abook ("abook_unconnected");
create index "abook_self" on abook ("abook_self");
create index "abook_feed" on abook ("abook_feed");
+ create index "abook_not_here" on abook ("abook_not_here");
create index "abook_profile" on abook ("abook_profile");
create index "abook_dob" on abook ("abook_dob");
create index "abook_connected" on abook ("abook_connected");
@@ -64,7 +66,7 @@ CREATE TABLE "account" (
"account_id" serial NOT NULL,
"account_parent" bigint NOT NULL DEFAULT '0',
"account_default_channel" bigint NOT NULL DEFAULT '0',
- "account_salt" char(32) NOT NULL DEFAULT '',
+ "account_salt" varchar(32) NOT NULL DEFAULT '',
"account_password" text NOT NULL DEFAULT '',
"account_email" text NOT NULL DEFAULT '',
"account_external" text NOT NULL DEFAULT '',
@@ -259,27 +261,11 @@ CREATE TABLE "channel" (
"channel_allow_gid" text ,
"channel_deny_cid" text ,
"channel_deny_gid" text ,
- "channel_r_stream" bigint NOT NULL DEFAULT '128',
- "channel_r_profile" bigint NOT NULL DEFAULT '128',
- "channel_r_photos" bigint NOT NULL DEFAULT '128',
- "channel_r_abook" bigint NOT NULL DEFAULT '128',
- "channel_w_stream" bigint NOT NULL DEFAULT '128',
- "channel_w_wall" bigint NOT NULL DEFAULT '128',
- "channel_w_tagwall" bigint NOT NULL DEFAULT '128',
- "channel_w_comment" bigint NOT NULL DEFAULT '128',
- "channel_w_mail" bigint NOT NULL DEFAULT '128',
- "channel_w_photos" bigint NOT NULL DEFAULT '128',
- "channel_w_chat" bigint NOT NULL DEFAULT '128',
- "channel_a_delegate" bigint NOT NULL DEFAULT '0',
- "channel_r_storage" bigint NOT NULL DEFAULT '128',
- "channel_w_storage" bigint NOT NULL DEFAULT '128',
- "channel_r_pages" bigint NOT NULL DEFAULT '128',
- "channel_w_pages" bigint NOT NULL DEFAULT '128',
- "channel_a_republish" bigint NOT NULL DEFAULT '128',
- "channel_w_like" bigint NOT NULL DEFAULT '128',
"channel_removed" smallint NOT NULL DEFAULT '0',
"channel_system" smallint NOT NULL DEFAULT '0',
"channel_moved" text NOT NULL DEFAULT '',
+ "channel_password" varchar(255) NOT NULL,
+ "channel_salt" varchar(255) NOT NULL,
PRIMARY KEY ("channel_id"),
UNIQUE ("channel_address")
);
@@ -294,28 +280,10 @@ create index "channel_pageflags" on channel ("channel_pageflags");
create index "channel_max_anon_mail" on channel ("channel_max_anon_mail");
create index "channel_max_friend_req" on channel ("channel_max_friend_req");
create index "channel_default_gid" on channel ("channel_default_group");
-create index "channel_r_stream" on channel ("channel_r_stream");
-create index "channel_r_profile" on channel ("channel_r_profile");
-create index "channel_r_photos" on channel ("channel_r_photos");
-create index "channel_r_abook" on channel ("channel_r_abook");
-create index "channel_w_stream" on channel ("channel_w_stream");
-create index "channel_w_wall" on channel ("channel_w_wall");
-create index "channel_w_tagwall" on channel ("channel_w_tagwall");
-create index "channel_w_comment" on channel ("channel_w_comment");
-create index "channel_w_mail" on channel ("channel_w_mail");
-create index "channel_w_photos" on channel ("channel_w_photos");
-create index "channel_w_chat" on channel ("channel_w_chat");
create index "channel_guid" on channel ("channel_guid");
create index "channel_hash" on channel ("channel_hash");
create index "channel_expire_days" on channel ("channel_expire_days");
-create index "channel_a_delegate" on channel ("channel_a_delegate");
-create index "channel_r_storage" on channel ("channel_r_storage");
-create index "channel_w_storage" on channel ("channel_w_storage");
-create index "channel_r_pages" on channel ("channel_r_pages");
-create index "channel_w_pages" on channel ("channel_w_pages");
create index "channel_deleted" on channel ("channel_deleted");
-create index "channel_a_republish" on channel ("channel_a_republish");
-create index "channel_w_like" on channel ("channel_w_like");
create index "channel_dirdate" on channel ("channel_dirdate");
create index "channel_lastpost" on channel ("channel_lastpost");
create index "channel_removed" on channel ("channel_removed");
@@ -338,7 +306,7 @@ CREATE TABLE "chatpresence" (
"cp_xchan" text NOT NULL DEFAULT '',
"cp_last" timestamp NOT NULL DEFAULT '0001-01-01 00:00:00',
"cp_status" text NOT NULL,
- "cp_client" char(128) NOT NULL DEFAULT '',
+ "cp_client" varchar(128) NOT NULL DEFAULT '',
PRIMARY KEY ("cp_id")
);
create index "cp_room" on chatpresence ("cp_room");
@@ -400,13 +368,13 @@ create index "conv_updated_idx" on conv ("updated");
CREATE TABLE IF NOT EXISTS "dreport" (
"dreport_id" serial NOT NULL,
"dreport_channel" int NOT NULL DEFAULT '0',
- "dreport_mid" char(255) NOT NULL DEFAULT '',
- "dreport_site" char(255) NOT NULL DEFAULT '',
- "dreport_recip" char(255) NOT NULL DEFAULT '',
- "dreport_result" char(255) NOT NULL DEFAULT '',
+ "dreport_mid" varchar(255) NOT NULL DEFAULT '',
+ "dreport_site" varchar(255) NOT NULL DEFAULT '',
+ "dreport_recip" varchar(255) NOT NULL DEFAULT '',
+ "dreport_result" varchar(255) NOT NULL DEFAULT '',
"dreport_time" timestamp NOT NULL DEFAULT '0001-01-01 00:00:00',
- "dreport_xchan" char(255) NOT NULL DEFAULT '',
- "dreport_queue" char(255) NOT NULL DEFAULT '',
+ "dreport_xchan" varchar(255) NOT NULL DEFAULT '',
+ "dreport_queue" varchar(255) NOT NULL DEFAULT '',
PRIMARY KEY ("dreport_id")
);
@@ -439,7 +407,7 @@ CREATE TABLE "event" (
"allow_gid" text NOT NULL,
"deny_cid" text NOT NULL,
"deny_gid" text NOT NULL,
- "event_status" char(255) NOT NULL DEFAULT '',
+ "event_status" varchar(255) NOT NULL DEFAULT '',
"event_status_date" timestamp NOT NULL DEFAULT '0001-01-01 00:00:00',
"event_percent" smallint NOT NULL DEFAULT '0',
"event_repeat" text NOT NULL,
@@ -609,7 +577,6 @@ CREATE TABLE "item" (
"resource_type" varchar(16) NOT NULL DEFAULT '',
"attach" text NOT NULL,
"sig" text NOT NULL DEFAULT '',
- "diaspora_meta" text NOT NULL DEFAULT '',
"location" text NOT NULL DEFAULT '',
"coord" text NOT NULL DEFAULT '',
"public_policy" text NOT NULL DEFAULT '',
@@ -654,16 +621,19 @@ create index "item_edited" on item ("edited");
create index "item_received" on item ("received");
create index "item_uid_commented" on item ("uid","commented");
create index "item_uid_created" on item ("uid","created");
+create index "item_uid_unseen" on item ("uid","item_unseen");
create index "item_changed" on item ("changed");
create index "item_comments_closed" on item ("comments_closed");
create index "item_aid" on item ("aid");
create index "item_owner_xchan" on item ("owner_xchan");
create index "item_author_xchan" on item ("author_xchan");
+create index "item_resource_id" on item ("resource_id");
create index "item_resource_type" on item ("resource_type");
create index "item_restrict" on item ("item_restrict");
create index "item_flags" on item ("item_flags");
create index "item_commented" on item ("commented");
create index "item_verb" on item ("verb");
+create index "item_obj_type" on item ("obj_type");
create index "item_private" on item ("item_private");
create index "item_llink" on item ("llink");
create index "item_expires" on item ("expires");
@@ -722,13 +692,13 @@ create index "itemid_iid" on item_id ("iid");
CREATE TABLE "likes" (
"id" serial NOT NULL,
"channel_id" bigint NOT NULL DEFAULT '0',
- "liker" char(128) NOT NULL DEFAULT '',
- "likee" char(128) NOT NULL DEFAULT '',
+ "liker" varchar(128) NOT NULL DEFAULT '',
+ "likee" varchar(128) NOT NULL DEFAULT '',
"iid" bigint NOT NULL DEFAULT '0',
- "i_mid" char(255) NOT NULL DEFAULT '',
+ "i_mid" varchar(255) NOT NULL DEFAULT '',
"verb" text NOT NULL DEFAULT '',
"target_type" text NOT NULL DEFAULT '',
- "target_id" char(128) NOT NULL DEFAULT '',
+ "target_id" varchar(128) NOT NULL DEFAULT '',
"target" text NOT NULL,
PRIMARY KEY ("id")
);
@@ -749,6 +719,7 @@ CREATE TABLE "mail" (
"to_xchan" text NOT NULL DEFAULT '',
"account_id" bigint NOT NULL DEFAULT '0',
"channel_id" bigint NOT NULL DEFAULT '0',
+ "mail_mimetype" varchar(64) NOT NULL DEFAULT '0',
"title" text NOT NULL,
"body" text NOT NULL,
"sig" text NOT NULL,
@@ -761,6 +732,7 @@ CREATE TABLE "mail" (
"mail_seen" smallint NOT NULL DEFAULT '0',
"mail_recalled" smallint NOT NULL DEFAULT '0',
"mail_obscured" smallint NOT NULL DEFAULT '0',
+ "mail_raw" smallint NOT NULL DEFAULT '0',
"created" timestamp NOT NULL DEFAULT '0001-01-01 00:00:00',
"expires" timestamp NOT NULL DEFAULT '0001-01-01 00:00:00',
PRIMARY KEY ("id")
@@ -817,7 +789,7 @@ create index "mitem_menu_id" on menu_item ("mitem_menu_id");
create index "mitem_flags" on menu_item ("mitem_flags");
CREATE TABLE "notify" (
"id" serial NOT NULL,
- "hash" char(64) NOT NULL,
+ "hash" varchar(64) NOT NULL,
"xname" text NOT NULL,
"url" text NOT NULL,
"photo" text NOT NULL,
@@ -844,14 +816,14 @@ create index "notify_otype" on notify ("otype");
create index "notify_aid" on notify ("aid");
CREATE TABLE "obj" (
"obj_id" serial NOT NULL,
- "obj_page" char(64) NOT NULL DEFAULT '',
+ "obj_page" varchar(64) NOT NULL DEFAULT '',
"obj_verb" text NOT NULL DEFAULT '',
"obj_type" bigint NOT NULL DEFAULT 0,
"obj_obj" text NOT NULL DEFAULT '',
"obj_channel" bigint NOT NULL DEFAULT 0,
- "obj_term" char(255) NOT NULL DEFAULT '',
- "obj_url" char(255) NOT NULL DEFAULT '',
- "obj_imgurl" char(255) NOT NULL DEFAULT '',
+ "obj_term" varchar(255) NOT NULL DEFAULT '',
+ "obj_url" varchar(255) NOT NULL DEFAULT '',
+ "obj_imgurl" varchar(255) NOT NULL DEFAULT '',
"obj_created" timestamp NOT NULL DEFAULT '0001-01-01 00:00:00',
"obj_edited" timestamp NOT NULL DEFAULT '0001-01-01 00:00:00',
"obj_quantity" bigint NOT NULL DEFAULT 0,
@@ -900,6 +872,19 @@ create index "outq_async" on outq ("outq_async");
create index "outq_delivered" on outq ("outq_delivered");
create index "outq_priority" on outq ("outq_priority");
+
+CREATE TABLE "pchan" (
+ "pchan_id" serial NOT NULL,
+ "pchan_guid" text NOT NULL,
+ "pchan_hash" text NOT NULL,
+ "pchan_pubkey" text NOT NULL,
+ "pchan_prvkey" text NOT NULL,
+ PRIMARY KEY ("pchan_id")
+);
+
+create index "pchan_guid" on pchan ("pchan_guid");
+create index "pchan_hash" on pchan ("pchan_hash");
+
CREATE TABLE "pconfig" (
"id" serial NOT NULL,
"uid" bigint NOT NULL DEFAULT '0',
@@ -1002,7 +987,7 @@ create index "profext_k" on profext ("k");
CREATE TABLE "profile" (
"id" serial NOT NULL,
- "profile_guid" char(64) NOT NULL DEFAULT '',
+ "profile_guid" varchar(64) NOT NULL DEFAULT '',
"aid" bigint NOT NULL DEFAULT '0',
"uid" bigint NOT NULL,
"profile_name" text NOT NULL,
@@ -1212,7 +1197,7 @@ create index "tokens_uid" on tokens ("uid");
CREATE TABLE "updates" (
"ud_id" serial NOT NULL,
- "ud_hash" char(128) NOT NULL,
+ "ud_hash" varchar(128) NOT NULL,
"ud_guid" text NOT NULL DEFAULT '',
"ud_date" timestamp NOT NULL DEFAULT '0001-01-01 00:00:00',
"ud_last" timestamp NOT NULL DEFAULT '0001-01-01 00:00:00',
@@ -1393,3 +1378,225 @@ CREATE TABLE "xtag" (
create index "xtag_term" on xtag ("xtag_term");
create index "xtag_hash" on xtag ("xtag_hash");
create index "xtag_flags" on xtag ("xtag_flags");
+
+CREATE TABLE addressbooks (
+ id SERIAL NOT NULL,
+ principaluri VARCHAR(255),
+ displayname VARCHAR(255),
+ uri VARCHAR(200),
+ description TEXT,
+ synctoken INTEGER NOT NULL DEFAULT 1
+);
+
+ALTER TABLE ONLY addressbooks
+ ADD CONSTRAINT addressbooks_pkey PRIMARY KEY (id);
+
+CREATE UNIQUE INDEX addressbooks_ukey
+ ON addressbooks USING btree (principaluri, uri);
+
+CREATE TABLE cards (
+ id SERIAL NOT NULL,
+ addressbookid INTEGER NOT NULL,
+ carddata BYTEA,
+ uri VARCHAR(200),
+ lastmodified INTEGER,
+ etag VARCHAR(32),
+ size INTEGER NOT NULL
+);
+
+ALTER TABLE ONLY cards
+ ADD CONSTRAINT cards_pkey PRIMARY KEY (id);
+
+CREATE UNIQUE INDEX cards_ukey
+ ON cards USING btree (addressbookid, uri);
+
+CREATE TABLE addressbookchanges (
+ id SERIAL NOT NULL,
+ uri VARCHAR(200) NOT NULL,
+ synctoken INTEGER NOT NULL,
+ addressbookid INTEGER NOT NULL,
+ operation SMALLINT NOT NULL
+);
+
+ALTER TABLE ONLY addressbookchanges
+ ADD CONSTRAINT addressbookchanges_pkey PRIMARY KEY (id);
+
+CREATE INDEX addressbookchanges_addressbookid_synctoken_ix
+ ON addressbookchanges USING btree (addressbookid, synctoken);
+
+CREATE TABLE calendarobjects (
+ id SERIAL NOT NULL,
+ calendardata BYTEA,
+ uri VARCHAR(200),
+ calendarid INTEGER NOT NULL,
+ lastmodified INTEGER,
+ etag VARCHAR(32),
+ size INTEGER NOT NULL,
+ componenttype VARCHAR(8),
+ firstoccurence INTEGER,
+ lastoccurence INTEGER,
+ uid VARCHAR(200)
+);
+
+ALTER TABLE ONLY calendarobjects
+ ADD CONSTRAINT calendarobjects_pkey PRIMARY KEY (id);
+
+CREATE UNIQUE INDEX calendarobjects_ukey
+ ON calendarobjects USING btree (calendarid, uri);
+
+
+CREATE TABLE calendars (
+ id SERIAL NOT NULL,
+ synctoken INTEGER NOT NULL DEFAULT 1,
+ components VARCHAR(21)
+);
+
+ALTER TABLE ONLY calendars
+ ADD CONSTRAINT calendars_pkey PRIMARY KEY (id);
+
+
+CREATE TABLE calendarinstances (
+ id SERIAL NOT NULL,
+ calendarid INTEGER NOT NULL,
+ principaluri VARCHAR(100),
+ access SMALLINT NOT NULL DEFAULT '1', -- '1 = owner, 2 = read, 3 = readwrite'
+ displayname VARCHAR(100),
+ uri VARCHAR(200),
+ description TEXT,
+ calendarorder INTEGER NOT NULL DEFAULT 0,
+ calendarcolor VARCHAR(10),
+ timezone TEXT,
+ transparent SMALLINT NOT NULL DEFAULT '0',
+ share_href VARCHAR(100),
+ share_displayname VARCHAR(100),
+ share_invitestatus SMALLINT NOT NULL DEFAULT '2' -- '1 = noresponse, 2 = accepted, 3 = declined, 4 = invalid'
+);
+
+ALTER TABLE ONLY calendarinstances
+ ADD CONSTRAINT calendarinstances_pkey PRIMARY KEY (id);
+
+CREATE UNIQUE INDEX calendarinstances_principaluri_uri
+ ON calendarinstances USING btree (principaluri, uri);
+
+
+CREATE UNIQUE INDEX calendarinstances_principaluri_calendarid
+ ON calendarinstances USING btree (principaluri, calendarid);
+
+CREATE UNIQUE INDEX calendarinstances_principaluri_share_href
+ ON calendarinstances USING btree (principaluri, share_href);
+
+CREATE TABLE calendarsubscriptions (
+ id SERIAL NOT NULL,
+ uri VARCHAR(200) NOT NULL,
+ principaluri VARCHAR(100) NOT NULL,
+ source TEXT,
+ displayname VARCHAR(100),
+ refreshrate VARCHAR(10),
+ calendarorder INTEGER NOT NULL DEFAULT 0,
+ calendarcolor VARCHAR(10),
+ striptodos SMALLINT NULL,
+ stripalarms SMALLINT NULL,
+ stripattachments SMALLINT NULL,
+ lastmodified INTEGER
+);
+
+ALTER TABLE ONLY calendarsubscriptions
+ ADD CONSTRAINT calendarsubscriptions_pkey PRIMARY KEY (id);
+
+CREATE UNIQUE INDEX calendarsubscriptions_ukey
+ ON calendarsubscriptions USING btree (principaluri, uri);
+
+CREATE TABLE calendarchanges (
+ id SERIAL NOT NULL,
+ uri VARCHAR(200) NOT NULL,
+ synctoken INTEGER NOT NULL,
+ calendarid INTEGER NOT NULL,
+ operation SMALLINT NOT NULL DEFAULT 0
+);
+
+ALTER TABLE ONLY calendarchanges
+ ADD CONSTRAINT calendarchanges_pkey PRIMARY KEY (id);
+
+CREATE INDEX calendarchanges_calendarid_synctoken_ix
+ ON calendarchanges USING btree (calendarid, synctoken);
+
+CREATE TABLE schedulingobjects (
+ id SERIAL NOT NULL,
+ principaluri VARCHAR(255),
+ calendardata BYTEA,
+ uri VARCHAR(200),
+ lastmodified INTEGER,
+ etag VARCHAR(32),
+ size INTEGER NOT NULL
+);
+
+CREATE TABLE locks (
+ id SERIAL NOT NULL,
+ owner VARCHAR(100),
+ timeout INTEGER,
+ created INTEGER,
+ token VARCHAR(100),
+ scope SMALLINT,
+ depth SMALLINT,
+ uri TEXT
+);
+
+ALTER TABLE ONLY locks
+ ADD CONSTRAINT locks_pkey PRIMARY KEY (id);
+
+CREATE INDEX locks_token_ix
+ ON locks USING btree (token);
+
+CREATE INDEX locks_uri_ix
+ ON locks USING btree (uri);
+
+CREATE TABLE principals (
+ id SERIAL NOT NULL,
+ uri VARCHAR(200) NOT NULL,
+ email VARCHAR(80),
+ displayname VARCHAR(80)
+);
+
+ALTER TABLE ONLY principals
+ ADD CONSTRAINT principals_pkey PRIMARY KEY (id);
+
+CREATE UNIQUE INDEX principals_ukey
+ ON principals USING btree (uri);
+
+CREATE TABLE groupmembers (
+ id SERIAL NOT NULL,
+ principal_id INTEGER NOT NULL,
+ member_id INTEGER NOT NULL
+);
+
+ALTER TABLE ONLY groupmembers
+ ADD CONSTRAINT groupmembers_pkey PRIMARY KEY (id);
+
+CREATE UNIQUE INDEX groupmembers_ukey
+ ON groupmembers USING btree (principal_id, member_id);
+
+CREATE TABLE propertystorage (
+ id SERIAL NOT NULL,
+ path VARCHAR(1024) NOT NULL,
+ name VARCHAR(100) NOT NULL,
+ valuetype INT,
+ value BYTEA
+);
+
+ALTER TABLE ONLY propertystorage
+ ADD CONSTRAINT propertystorage_pkey PRIMARY KEY (id);
+
+CREATE UNIQUE INDEX propertystorage_ukey
+ ON propertystorage (path, name);
+
+CREATE TABLE users (
+ id SERIAL NOT NULL,
+ username VARCHAR(50),
+ digesta1 VARCHAR(32)
+);
+
+ALTER TABLE ONLY users
+ ADD CONSTRAINT users_pkey PRIMARY KEY (id);
+
+CREATE UNIQUE INDEX users_ukey
+ ON users USING btree (username);
diff --git a/install/update.php b/install/update.php
index 87cf4ba60..7d59555d3 100644
--- a/install/update.php
+++ b/install/update.php
@@ -1,6 +1,6 @@
<?php
-define( 'UPDATE_VERSION' , 1188 );
+define( 'UPDATE_VERSION' , 1197 );
/**
*
@@ -2475,7 +2475,7 @@ function update_r1184() {
function update_r1185() {
- $r1 = q("alter table app add app_plugin char(255) not null default '' ");
+ $r1 = q("alter table app add app_plugin text not null default '' ");
if($r1)
return UPDATE_SUCCESS;
@@ -2508,4 +2508,555 @@ function update_r1187() {
return UPDATE_FAILED;
+}
+
+function update_r1188() {
+
+ $r1 = q("alter table channel add channel_password varchar(255) not null default '' ");
+ $r2 = q("alter table channel add channel_salt varchar(255) not null default '' ");
+
+ if($r1 && $r2)
+ return UPDATE_SUCCESS;
+ return UPDATE_FAILED;
+
+}
+
+function update_r1189() {
+
+ $r1 = q("alter table mail add mail_mimetype varchar(64) not null default 'text/bbcode' ");
+
+ if(ACTIVE_DBTYPE == DBTYPE_POSTGRES) {
+ $r2 = q("alter table mail add mail_raw smallint not null default 0 ");
+ }
+ else {
+ $r2 = q("alter table mail add mail_raw tinyint(4) not null default 0 ");
+ }
+ if($r1 && $r2)
+ return UPDATE_SUCCESS;
+ return UPDATE_FAILED;
+
+}
+
+function update_r1190() {
+ $r1 = q("alter table abook add abook_not_here smallint not null default 0 ");
+
+ $r2 = q("create index abook_not_here on abook (abook_not_here)");
+
+ if($r1 && $r2)
+ return UPDATE_SUCCESS;
+ return UPDATE_FAILED;
+}
+
+function update_r1191() {
+
+ $r = q("SELECT 1 FROM principals LIMIT 1");
+
+ if($r !== false) {
+ return UPDATE_SUCCESS;
+ }
+ else {
+ if(ACTIVE_DBTYPE == DBTYPE_POSTGRES) {
+ $r1 = q("CREATE TABLE addressbooks (
+ id SERIAL NOT NULL,
+ principaluri VARCHAR(255),
+ displayname VARCHAR(255),
+ uri VARCHAR(200),
+ description TEXT,
+ synctoken INTEGER NOT NULL DEFAULT 1
+ );"
+ );
+
+ $r2 = q("ALTER TABLE ONLY addressbooks ADD CONSTRAINT addressbooks_pkey PRIMARY KEY (id);");
+
+ $r3 = q("CREATE UNIQUE INDEX addressbooks_ukey ON addressbooks USING btree (principaluri, uri);");
+
+ $r4 = q("CREATE TABLE cards (
+ id SERIAL NOT NULL,
+ addressbookid INTEGER NOT NULL,
+ carddata BYTEA,
+ uri VARCHAR(200),
+ lastmodified INTEGER,
+ etag VARCHAR(32),
+ size INTEGER NOT NULL
+ );"
+ );
+
+ $r5 = q("ALTER TABLE ONLY cards ADD CONSTRAINT cards_pkey PRIMARY KEY (id);");
+
+ $r6 = q("CREATE UNIQUE INDEX cards_ukey ON cards USING btree (addressbookid, uri);");
+
+ $r7 = q("CREATE TABLE addressbookchanges (
+ id SERIAL NOT NULL,
+ uri VARCHAR(200) NOT NULL,
+ synctoken INTEGER NOT NULL,
+ addressbookid INTEGER NOT NULL,
+ operation SMALLINT NOT NULL
+ );"
+ );
+
+ $r8 = q("ALTER TABLE ONLY addressbookchanges ADD CONSTRAINT addressbookchanges_pkey PRIMARY KEY (id);");
+
+ $r9 = q("CREATE INDEX addressbookchanges_addressbookid_synctoken_ix ON addressbookchanges USING btree (addressbookid, synctoken);");
+
+ $r10 = q("CREATE TABLE calendarobjects (
+ id SERIAL NOT NULL,
+ calendardata BYTEA,
+ uri VARCHAR(200),
+ calendarid INTEGER NOT NULL,
+ lastmodified INTEGER,
+ etag VARCHAR(32),
+ size INTEGER NOT NULL,
+ componenttype VARCHAR(8),
+ firstoccurence INTEGER,
+ lastoccurence INTEGER,
+ uid VARCHAR(200)
+ );"
+ );
+
+ $r11 = q("ALTER TABLE ONLY calendarobjects ADD CONSTRAINT calendarobjects_pkey PRIMARY KEY (id);");
+
+ $r12 = q("CREATE UNIQUE INDEX calendarobjects_ukey ON calendarobjects USING btree (calendarid, uri);");
+
+ $r13 = q("CREATE TABLE calendars (
+ id SERIAL NOT NULL,
+ synctoken INTEGER NOT NULL DEFAULT 1,
+ components VARCHAR(21)
+ );"
+ );
+
+ $r14 = q("ALTER TABLE ONLY calendars ADD CONSTRAINT calendars_pkey PRIMARY KEY (id);");
+
+ $r15 = q("CREATE TABLE calendarinstances (
+ id SERIAL NOT NULL,
+ calendarid INTEGER NOT NULL,
+ principaluri VARCHAR(100),
+ access SMALLINT NOT NULL DEFAULT '1', -- '1 = owner, 2 = read, 3 = readwrite'
+ displayname VARCHAR(100),
+ uri VARCHAR(200),
+ description TEXT,
+ calendarorder INTEGER NOT NULL DEFAULT 0,
+ calendarcolor VARCHAR(10),
+ timezone TEXT,
+ transparent SMALLINT NOT NULL DEFAULT '0',
+ share_href VARCHAR(100),
+ share_displayname VARCHAR(100),
+ share_invitestatus SMALLINT NOT NULL DEFAULT '2' -- '1 = noresponse, 2 = accepted, 3 = declined, 4 = invalid'
+ );"
+ );
+
+ $r16 = q("ALTER TABLE ONLY calendarinstances ADD CONSTRAINT calendarinstances_pkey PRIMARY KEY (id);");
+
+ $r17 = q("CREATE UNIQUE INDEX calendarinstances_principaluri_uri ON calendarinstances USING btree (principaluri, uri);");
+
+ $r18 = q("CREATE UNIQUE INDEX calendarinstances_principaluri_calendarid ON calendarinstances USING btree (principaluri, calendarid);");
+
+ $r19 = q("CREATE UNIQUE INDEX calendarinstances_principaluri_share_href ON calendarinstances USING btree (principaluri, share_href);");
+
+ $r20 = q("CREATE TABLE calendarsubscriptions (
+ id SERIAL NOT NULL,
+ uri VARCHAR(200) NOT NULL,
+ principaluri VARCHAR(100) NOT NULL,
+ source TEXT,
+ displayname VARCHAR(100),
+ refreshrate VARCHAR(10),
+ calendarorder INTEGER NOT NULL DEFAULT 0,
+ calendarcolor VARCHAR(10),
+ striptodos SMALLINT NULL,
+ stripalarms SMALLINT NULL,
+ stripattachments SMALLINT NULL,
+ lastmodified INTEGER
+ );"
+ );
+
+ $r21 = q("ALTER TABLE ONLY calendarsubscriptions ADD CONSTRAINT calendarsubscriptions_pkey PRIMARY KEY (id);");
+
+ $r22 = q("CREATE UNIQUE INDEX calendarsubscriptions_ukey ON calendarsubscriptions USING btree (principaluri, uri);");
+
+ $r23 = q("CREATE TABLE calendarchanges (
+ id SERIAL NOT NULL,
+ uri VARCHAR(200) NOT NULL,
+ synctoken INTEGER NOT NULL,
+ calendarid INTEGER NOT NULL,
+ operation SMALLINT NOT NULL DEFAULT 0
+ );"
+ );
+
+ $r24 = q("ALTER TABLE ONLY calendarchanges ADD CONSTRAINT calendarchanges_pkey PRIMARY KEY (id);");
+
+ $r25 = q("CREATE INDEX calendarchanges_calendarid_synctoken_ix ON calendarchanges USING btree (calendarid, synctoken);");
+
+ $r26 = q("CREATE TABLE schedulingobjects (
+ id SERIAL NOT NULL,
+ principaluri VARCHAR(255),
+ calendardata BYTEA,
+ uri VARCHAR(200),
+ lastmodified INTEGER,
+ etag VARCHAR(32),
+ size INTEGER NOT NULL
+ );"
+ );
+
+ $r27 = q("CREATE TABLE locks (
+ id SERIAL NOT NULL,
+ owner VARCHAR(100),
+ timeout INTEGER,
+ created INTEGER,
+ token VARCHAR(100),
+ scope SMALLINT,
+ depth SMALLINT,
+ uri TEXT
+ );"
+ );
+
+ $r28 = q("ALTER TABLE ONLY locks ADD CONSTRAINT locks_pkey PRIMARY KEY (id);");
+
+ $r29 = q("CREATE INDEX locks_token_ix ON locks USING btree (token);");
+
+ $r30 = q("CREATE INDEX locks_uri_ix ON locks USING btree (uri);");
+
+ $r31 = q("CREATE TABLE principals (
+ id SERIAL NOT NULL,
+ uri VARCHAR(200) NOT NULL,
+ email VARCHAR(80),
+ displayname VARCHAR(80)
+ );"
+ );
+
+ $r32 = q("ALTER TABLE ONLY principals ADD CONSTRAINT principals_pkey PRIMARY KEY (id);");
+
+ $r33 = q("CREATE UNIQUE INDEX principals_ukey ON principals USING btree (uri);");
+
+ $r34 = q("CREATE TABLE groupmembers (
+ id SERIAL NOT NULL,
+ principal_id INTEGER NOT NULL,
+ member_id INTEGER NOT NULL
+ );"
+ );
+
+ $r35 = q("ALTER TABLE ONLY groupmembers ADD CONSTRAINT groupmembers_pkey PRIMARY KEY (id);");
+
+ $r36 = q("CREATE UNIQUE INDEX groupmembers_ukey ON groupmembers USING btree (principal_id, member_id);");
+
+ $r37 = q("CREATE TABLE propertystorage (
+ id SERIAL NOT NULL,
+ path VARCHAR(1024) NOT NULL,
+ name VARCHAR(100) NOT NULL,
+ valuetype INT,
+ value BYTEA
+ );"
+ );
+
+ $r38 = q("ALTER TABLE ONLY propertystorage ADD CONSTRAINT propertystorage_pkey PRIMARY KEY (id);");
+
+ $r39 = q("CREATE UNIQUE INDEX propertystorage_ukey ON propertystorage (path, name);");
+
+ $r40 = q("CREATE TABLE users (
+ id SERIAL NOT NULL,
+ username VARCHAR(50),
+ digesta1 VARCHAR(32)
+ );"
+ );
+
+ $r41 = q("ALTER TABLE ONLY users ADD CONSTRAINT users_pkey PRIMARY KEY (id);");
+
+ $r42 = q("CREATE UNIQUE INDEX users_ukey ON users USING btree (username);");
+
+ if(
+ $r1 && $r2 && $r3 && $r4 && $r5 && $r6 && $r7 && $r8 && $r9 && $r10
+ && $r11 && $r12 && $r13 && $r14 && $r15 && $r16 && $r17 && $r18 && $r19 && $r20
+ && $r21 && $r22 && $r23 && $r24 && $r25 && $r26 && $r27 && $r28 && $r29 && $r30
+ && $r31 && $r32 && $r33 && $r34 && $r35 && $r36 && $r37 && $r38 && $r39 && $r40
+ && $r41 && $r42
+ )
+ return UPDATE_SUCCESS;
+ return UPDATE_FAILED;
+ }
+ else {
+ $r1 = q("CREATE TABLE if not exists addressbooks (
+ id INT(11) UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ principaluri VARBINARY(255),
+ displayname VARCHAR(255),
+ uri VARBINARY(200),
+ description TEXT,
+ synctoken INT(11) UNSIGNED NOT NULL DEFAULT '1',
+ UNIQUE(principaluri(100), uri(100))
+ ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
+ );
+
+ $r2 = q("CREATE TABLE if not exists cards (
+ id INT(11) UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ addressbookid INT(11) UNSIGNED NOT NULL,
+ carddata MEDIUMBLOB,
+ uri VARBINARY(200),
+ lastmodified INT(11) UNSIGNED,
+ etag VARBINARY(32),
+ size INT(11) UNSIGNED NOT NULL
+ ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
+ );
+
+ $r3 = q("CREATE TABLE if not exists addressbookchanges (
+ id INT(11) UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ uri VARBINARY(200) NOT NULL,
+ synctoken INT(11) UNSIGNED NOT NULL,
+ addressbookid INT(11) UNSIGNED NOT NULL,
+ operation TINYINT(1) NOT NULL,
+ INDEX addressbookid_synctoken (addressbookid, synctoken)
+ ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
+ );
+
+ $r4 = q("CREATE TABLE if not exists calendarobjects (
+ id INT(11) UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ calendardata MEDIUMBLOB,
+ uri VARBINARY(200),
+ calendarid INTEGER UNSIGNED NOT NULL,
+ lastmodified INT(11) UNSIGNED,
+ etag VARBINARY(32),
+ size INT(11) UNSIGNED NOT NULL,
+ componenttype VARBINARY(8),
+ firstoccurence INT(11) UNSIGNED,
+ lastoccurence INT(11) UNSIGNED,
+ uid VARBINARY(200),
+ UNIQUE(calendarid, uri),
+ INDEX calendarid_time (calendarid, firstoccurence)
+ ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
+ );
+
+ $r5 = q("CREATE TABLE if not exists calendars (
+ id INTEGER UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ synctoken INTEGER UNSIGNED NOT NULL DEFAULT '1',
+ components VARBINARY(21)
+ ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
+ );
+
+ $r6 = q("CREATE TABLE if not exists calendarinstances (
+ id INTEGER UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ calendarid INTEGER UNSIGNED NOT NULL,
+ principaluri VARBINARY(100),
+ access TINYINT(1) NOT NULL DEFAULT '1' COMMENT '1 = owner, 2 = read, 3 = readwrite',
+ displayname VARCHAR(100),
+ uri VARBINARY(200),
+ description TEXT,
+ calendarorder INT(11) UNSIGNED NOT NULL DEFAULT '0',
+ calendarcolor VARBINARY(10),
+ timezone TEXT,
+ transparent TINYINT(1) NOT NULL DEFAULT '0',
+ share_href VARBINARY(100),
+ share_displayname VARCHAR(100),
+ share_invitestatus TINYINT(1) NOT NULL DEFAULT '2' COMMENT '1 = noresponse, 2 = accepted, 3 = declined, 4 = invalid',
+ UNIQUE(principaluri, uri),
+ UNIQUE(calendarid, principaluri),
+ UNIQUE(calendarid, share_href)
+ ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
+ );
+
+ $r7 = q("CREATE TABLE if not exists calendarchanges (
+ id INT(11) UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ uri VARBINARY(200) NOT NULL,
+ synctoken INT(11) UNSIGNED NOT NULL,
+ calendarid INT(11) UNSIGNED NOT NULL,
+ operation TINYINT(1) NOT NULL,
+ INDEX calendarid_synctoken (calendarid, synctoken)
+ ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
+ );
+
+ $r8 = q("CREATE TABLE if not exists calendarsubscriptions (
+ id INT(11) UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ uri VARBINARY(200) NOT NULL,
+ principaluri VARBINARY(100) NOT NULL,
+ source TEXT,
+ displayname VARCHAR(100),
+ refreshrate VARCHAR(10),
+ calendarorder INT(11) UNSIGNED NOT NULL DEFAULT '0',
+ calendarcolor VARBINARY(10),
+ striptodos TINYINT(1) NULL,
+ stripalarms TINYINT(1) NULL,
+ stripattachments TINYINT(1) NULL,
+ lastmodified INT(11) UNSIGNED,
+ UNIQUE(principaluri, uri)
+ ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
+ );
+
+ $r9 = q("CREATE TABLE if not exists schedulingobjects (
+ id INT(11) UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ principaluri VARBINARY(255),
+ calendardata MEDIUMBLOB,
+ uri VARBINARY(200),
+ lastmodified INT(11) UNSIGNED,
+ etag VARBINARY(32),
+ size INT(11) UNSIGNED NOT NULL
+ ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
+ );
+
+ $r10 = q("CREATE TABLE if not exists locks (
+ id INTEGER UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ owner VARCHAR(100),
+ timeout INTEGER UNSIGNED,
+ created INTEGER,
+ token VARBINARY(100),
+ scope TINYINT,
+ depth TINYINT,
+ uri VARBINARY(1000),
+ INDEX(token),
+ INDEX(uri(100))
+ ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
+ );
+
+ $r11 = q("CREATE TABLE if not exists principals (
+ id INTEGER UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ uri VARBINARY(200) NOT NULL,
+ email VARBINARY(80),
+ displayname VARCHAR(80),
+ UNIQUE(uri)
+ ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
+ );
+
+ $r12 = q("CREATE TABLE if not exists groupmembers (
+ id INTEGER UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ principal_id INTEGER UNSIGNED NOT NULL,
+ member_id INTEGER UNSIGNED NOT NULL,
+ UNIQUE(principal_id, member_id)
+ ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
+ );
+
+ $r13 = q("CREATE TABLE if not exists propertystorage (
+ id INT UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ path VARBINARY(1024) NOT NULL,
+ name VARBINARY(100) NOT NULL,
+ valuetype INT UNSIGNED,
+ value MEDIUMBLOB
+ ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
+ );
+
+ $r14 = q("CREATE UNIQUE INDEX path_property ON propertystorage (path(600), name(100));");
+
+ $r15 = q("CREATE TABLE if not exists users (
+ id INTEGER UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ username VARBINARY(50),
+ digesta1 VARBINARY(32),
+ UNIQUE(username)
+ ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
+ );
+
+ $r16 = q("CREATE TABLE if not exists calendarinstances (
+ id INTEGER UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ calendarid INTEGER UNSIGNED NOT NULL,
+ principaluri VARBINARY(100),
+ access TINYINT(1) NOT NULL DEFAULT '1' COMMENT '1 = owner, 2 = read, 3 = readwrite',
+ displayname VARCHAR(100),
+ uri VARBINARY(200),
+ description TEXT,
+ calendarorder INT(11) UNSIGNED NOT NULL DEFAULT '0',
+ calendarcolor VARBINARY(10),
+ timezone TEXT,
+ transparent TINYINT(1) NOT NULL DEFAULT '0',
+ share_href VARBINARY(100),
+ share_displayname VARCHAR(100),
+ share_invitestatus TINYINT(1) NOT NULL DEFAULT '2' COMMENT '1 = noresponse, 2 = accepted, 3 = declined, 4 = invalid',
+ UNIQUE(principaluri, uri),
+ UNIQUE(calendarid, principaluri),
+ UNIQUE(calendarid, share_href)
+ ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
+ );
+
+ if($r1 && $r2 && $r3 && $r4 && $r5 && $r6 && $r7 && $r8 && $r9 && $r10 && $r11 && $r12 && $r13 && $r14 && $r15 && $r16)
+ return UPDATE_SUCCESS;
+ return UPDATE_FAILED;
+ }
+ }
+}
+
+function update_r1192() {
+
+ if(ACTIVE_DBTYPE == DBTYPE_POSTGRES) {
+ $r1 = q("CREATE INDEX item_obj_type ON item (obj_type)");
+ }
+ else {
+ $r1 = q("ALTER TABLE item ADD INDEX (obj_type)");
+ }
+
+ if($r1)
+ return UPDATE_SUCCESS;
+ return UPDATE_FAILED;
+}
+
+function update_r1193() {
+
+ if(ACTIVE_DBTYPE == DBTYPE_POSTGRES) {
+ $r1 = q("CREATE INDEX item_uid_unseen ON item (uid, item_unseen)");
+ }
+ else {
+ $r1 = q("ALTER TABLE item ADD INDEX uid_item_unseen (uid, item_unseen)");
+ }
+
+ if($r1)
+ return UPDATE_SUCCESS;
+ return UPDATE_FAILED;
+}
+
+
+function update_r1194() {
+ $r = q("select id, resource_id from item where resource_type = 'nwiki'");
+ if($r) {
+ foreach($r as $rv) {
+ $mimetype = get_iconfig($rv['id'],'wiki','mimeType');
+ q("update item set mimetype = '%s' where resource_type = 'nwikipage' and resource_id = '%s'",
+ dbesc($mimetype),
+ dbesc($rv['resource_id'])
+ );
+ }
+ }
+
+ return UPDATE_SUCCESS;
+}
+
+function update_r1195() {
+
+ if(ACTIVE_DBTYPE == DBTYPE_POSTGRES) {
+ $r1 = q("CREATE INDEX item_resource_id ON item (resource_id)");
+ }
+ else {
+ $r1 = q("ALTER TABLE item ADD INDEX (resource_id)");
+ }
+
+ if($r1)
+ return UPDATE_SUCCESS;
+ return UPDATE_FAILED;
+}
+
+function update_r1196() {
+
+ if(ACTIVE_DBTYPE == DBTYPE_POSTGRES) {
+ $r1 = q("CREATE TABLE \"pchan\" (
+ \"pchan_id\" serial NOT NULL,
+ \"pchan_guid\" text NOT NULL,
+ \"pchan_hash\" text NOT NULL,
+ \"pchan_pubkey\" text NOT NULL,
+ \"pchan_prvkey\" text NOT NULL,
+ PRIMARY KEY (\"pchan_id\")
+)");
+
+ $r2 = q("create index \"pchan_guid\" on pchan (\"pchan_guid\")");
+ $r3 = q("create index \"pchan_hash\" on pchan (\"pchan_hash\")");
+
+ if($r1 && $r2 && $r3) {
+ return UPDATE_SUCCESS;
+ }
+ }
+ else {
+ $r1 = q("CREATE TABLE IF NOT EXISTS pchan (
+ pchan_id int(11) UNSIGNED NOT NULL AUTO_INCREMENT,
+ pchan_guid char(191) NOT NULL DEFAULT '',
+ pchan_hash char(191) NOT NULL DEFAULT '',
+ pchan_pubkey text NOT NULL,
+ pchan_prvkey text NOT NULL,
+ PRIMARY KEY (pchan_id),
+ KEY pchan_guid (pchan_guid),
+ KEY pchan_hash (pchan_hash)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4");
+ if($r1) {
+ return UPDATE_SUCCESS;
+ }
+ }
+
+ return UPDATE_FAILED;
} \ No newline at end of file
diff --git a/library/HTMLPurifier.composer.php b/library/HTMLPurifier.composer.php
deleted file mode 100644
index 6706f4e39..000000000
--- a/library/HTMLPurifier.composer.php
+++ /dev/null
@@ -1,4 +0,0 @@
-<?php
-if (!defined('HTMLPURIFIER_PREFIX')) {
- define('HTMLPURIFIER_PREFIX', __DIR__);
-}
diff --git a/library/HTMLPurifier.includes.php b/library/HTMLPurifier.includes.php
deleted file mode 100644
index 9b7b88a87..000000000
--- a/library/HTMLPurifier.includes.php
+++ /dev/null
@@ -1,229 +0,0 @@
-<?php
-
-/**
- * @file
- * This file was auto-generated by generate-includes.php and includes all of
- * the core files required by HTML Purifier. Use this if performance is a
- * primary concern and you are using an opcode cache. PLEASE DO NOT EDIT THIS
- * FILE, changes will be overwritten the next time the script is run.
- *
- * @version 4.6.0
- *
- * @warning
- * You must *not* include any other HTML Purifier files before this file,
- * because 'require' not 'require_once' is used.
- *
- * @warning
- * This file requires that the include path contains the HTML Purifier
- * library directory; this is not auto-set.
- */
-
-require 'HTMLPurifier.php';
-require 'HTMLPurifier/Arborize.php';
-require 'HTMLPurifier/AttrCollections.php';
-require 'HTMLPurifier/AttrDef.php';
-require 'HTMLPurifier/AttrTransform.php';
-require 'HTMLPurifier/AttrTypes.php';
-require 'HTMLPurifier/AttrValidator.php';
-require 'HTMLPurifier/Bootstrap.php';
-require 'HTMLPurifier/Definition.php';
-require 'HTMLPurifier/CSSDefinition.php';
-require 'HTMLPurifier/ChildDef.php';
-require 'HTMLPurifier/Config.php';
-require 'HTMLPurifier/ConfigSchema.php';
-require 'HTMLPurifier/ContentSets.php';
-require 'HTMLPurifier/Context.php';
-require 'HTMLPurifier/DefinitionCache.php';
-require 'HTMLPurifier/DefinitionCacheFactory.php';
-require 'HTMLPurifier/Doctype.php';
-require 'HTMLPurifier/DoctypeRegistry.php';
-require 'HTMLPurifier/ElementDef.php';
-require 'HTMLPurifier/Encoder.php';
-require 'HTMLPurifier/EntityLookup.php';
-require 'HTMLPurifier/EntityParser.php';
-require 'HTMLPurifier/ErrorCollector.php';
-require 'HTMLPurifier/ErrorStruct.php';
-require 'HTMLPurifier/Exception.php';
-require 'HTMLPurifier/Filter.php';
-require 'HTMLPurifier/Generator.php';
-require 'HTMLPurifier/HTMLDefinition.php';
-require 'HTMLPurifier/HTMLModule.php';
-require 'HTMLPurifier/HTMLModuleManager.php';
-require 'HTMLPurifier/IDAccumulator.php';
-require 'HTMLPurifier/Injector.php';
-require 'HTMLPurifier/Language.php';
-require 'HTMLPurifier/LanguageFactory.php';
-require 'HTMLPurifier/Length.php';
-require 'HTMLPurifier/Lexer.php';
-require 'HTMLPurifier/Node.php';
-require 'HTMLPurifier/PercentEncoder.php';
-require 'HTMLPurifier/PropertyList.php';
-require 'HTMLPurifier/PropertyListIterator.php';
-require 'HTMLPurifier/Queue.php';
-require 'HTMLPurifier/Strategy.php';
-require 'HTMLPurifier/StringHash.php';
-require 'HTMLPurifier/StringHashParser.php';
-require 'HTMLPurifier/TagTransform.php';
-require 'HTMLPurifier/Token.php';
-require 'HTMLPurifier/TokenFactory.php';
-require 'HTMLPurifier/URI.php';
-require 'HTMLPurifier/URIDefinition.php';
-require 'HTMLPurifier/URIFilter.php';
-require 'HTMLPurifier/URIParser.php';
-require 'HTMLPurifier/URIScheme.php';
-require 'HTMLPurifier/URISchemeRegistry.php';
-require 'HTMLPurifier/UnitConverter.php';
-require 'HTMLPurifier/VarParser.php';
-require 'HTMLPurifier/VarParserException.php';
-require 'HTMLPurifier/Zipper.php';
-require 'HTMLPurifier/AttrDef/CSS.php';
-require 'HTMLPurifier/AttrDef/Clone.php';
-require 'HTMLPurifier/AttrDef/Enum.php';
-require 'HTMLPurifier/AttrDef/Integer.php';
-require 'HTMLPurifier/AttrDef/Lang.php';
-require 'HTMLPurifier/AttrDef/Switch.php';
-require 'HTMLPurifier/AttrDef/Text.php';
-require 'HTMLPurifier/AttrDef/URI.php';
-require 'HTMLPurifier/AttrDef/CSS/Number.php';
-require 'HTMLPurifier/AttrDef/CSS/AlphaValue.php';
-require 'HTMLPurifier/AttrDef/CSS/Background.php';
-require 'HTMLPurifier/AttrDef/CSS/BackgroundPosition.php';
-require 'HTMLPurifier/AttrDef/CSS/Border.php';
-require 'HTMLPurifier/AttrDef/CSS/Color.php';
-require 'HTMLPurifier/AttrDef/CSS/Composite.php';
-require 'HTMLPurifier/AttrDef/CSS/DenyElementDecorator.php';
-require 'HTMLPurifier/AttrDef/CSS/Filter.php';
-require 'HTMLPurifier/AttrDef/CSS/Font.php';
-require 'HTMLPurifier/AttrDef/CSS/FontFamily.php';
-require 'HTMLPurifier/AttrDef/CSS/Ident.php';
-require 'HTMLPurifier/AttrDef/CSS/ImportantDecorator.php';
-require 'HTMLPurifier/AttrDef/CSS/Length.php';
-require 'HTMLPurifier/AttrDef/CSS/ListStyle.php';
-require 'HTMLPurifier/AttrDef/CSS/Multiple.php';
-require 'HTMLPurifier/AttrDef/CSS/Percentage.php';
-require 'HTMLPurifier/AttrDef/CSS/TextDecoration.php';
-require 'HTMLPurifier/AttrDef/CSS/URI.php';
-require 'HTMLPurifier/AttrDef/HTML/Bool.php';
-require 'HTMLPurifier/AttrDef/HTML/Nmtokens.php';
-require 'HTMLPurifier/AttrDef/HTML/Class.php';
-require 'HTMLPurifier/AttrDef/HTML/Color.php';
-require 'HTMLPurifier/AttrDef/HTML/FrameTarget.php';
-require 'HTMLPurifier/AttrDef/HTML/ID.php';
-require 'HTMLPurifier/AttrDef/HTML/Pixels.php';
-require 'HTMLPurifier/AttrDef/HTML/Length.php';
-require 'HTMLPurifier/AttrDef/HTML/LinkTypes.php';
-require 'HTMLPurifier/AttrDef/HTML/MultiLength.php';
-require 'HTMLPurifier/AttrDef/URI/Email.php';
-require 'HTMLPurifier/AttrDef/URI/Host.php';
-require 'HTMLPurifier/AttrDef/URI/IPv4.php';
-require 'HTMLPurifier/AttrDef/URI/IPv6.php';
-require 'HTMLPurifier/AttrDef/URI/Email/SimpleCheck.php';
-require 'HTMLPurifier/AttrTransform/Background.php';
-require 'HTMLPurifier/AttrTransform/BdoDir.php';
-require 'HTMLPurifier/AttrTransform/BgColor.php';
-require 'HTMLPurifier/AttrTransform/BoolToCSS.php';
-require 'HTMLPurifier/AttrTransform/Border.php';
-require 'HTMLPurifier/AttrTransform/EnumToCSS.php';
-require 'HTMLPurifier/AttrTransform/ImgRequired.php';
-require 'HTMLPurifier/AttrTransform/ImgSpace.php';
-require 'HTMLPurifier/AttrTransform/Input.php';
-require 'HTMLPurifier/AttrTransform/Lang.php';
-require 'HTMLPurifier/AttrTransform/Length.php';
-require 'HTMLPurifier/AttrTransform/Name.php';
-require 'HTMLPurifier/AttrTransform/NameSync.php';
-require 'HTMLPurifier/AttrTransform/Nofollow.php';
-require 'HTMLPurifier/AttrTransform/SafeEmbed.php';
-require 'HTMLPurifier/AttrTransform/SafeObject.php';
-require 'HTMLPurifier/AttrTransform/SafeParam.php';
-require 'HTMLPurifier/AttrTransform/ScriptRequired.php';
-require 'HTMLPurifier/AttrTransform/TargetBlank.php';
-require 'HTMLPurifier/AttrTransform/Textarea.php';
-require 'HTMLPurifier/ChildDef/Chameleon.php';
-require 'HTMLPurifier/ChildDef/Custom.php';
-require 'HTMLPurifier/ChildDef/Empty.php';
-require 'HTMLPurifier/ChildDef/List.php';
-require 'HTMLPurifier/ChildDef/Required.php';
-require 'HTMLPurifier/ChildDef/Optional.php';
-require 'HTMLPurifier/ChildDef/StrictBlockquote.php';
-require 'HTMLPurifier/ChildDef/Table.php';
-require 'HTMLPurifier/DefinitionCache/Decorator.php';
-require 'HTMLPurifier/DefinitionCache/Null.php';
-require 'HTMLPurifier/DefinitionCache/Serializer.php';
-require 'HTMLPurifier/DefinitionCache/Decorator/Cleanup.php';
-require 'HTMLPurifier/DefinitionCache/Decorator/Memory.php';
-require 'HTMLPurifier/HTMLModule/Bdo.php';
-require 'HTMLPurifier/HTMLModule/CommonAttributes.php';
-require 'HTMLPurifier/HTMLModule/Edit.php';
-require 'HTMLPurifier/HTMLModule/Forms.php';
-require 'HTMLPurifier/HTMLModule/Hypertext.php';
-require 'HTMLPurifier/HTMLModule/Iframe.php';
-require 'HTMLPurifier/HTMLModule/Image.php';
-require 'HTMLPurifier/HTMLModule/Legacy.php';
-require 'HTMLPurifier/HTMLModule/List.php';
-require 'HTMLPurifier/HTMLModule/Name.php';
-require 'HTMLPurifier/HTMLModule/Nofollow.php';
-require 'HTMLPurifier/HTMLModule/NonXMLCommonAttributes.php';
-require 'HTMLPurifier/HTMLModule/Object.php';
-require 'HTMLPurifier/HTMLModule/Presentation.php';
-require 'HTMLPurifier/HTMLModule/Proprietary.php';
-require 'HTMLPurifier/HTMLModule/Ruby.php';
-require 'HTMLPurifier/HTMLModule/SafeEmbed.php';
-require 'HTMLPurifier/HTMLModule/SafeObject.php';
-require 'HTMLPurifier/HTMLModule/SafeScripting.php';
-require 'HTMLPurifier/HTMLModule/Scripting.php';
-require 'HTMLPurifier/HTMLModule/StyleAttribute.php';
-require 'HTMLPurifier/HTMLModule/Tables.php';
-require 'HTMLPurifier/HTMLModule/Target.php';
-require 'HTMLPurifier/HTMLModule/TargetBlank.php';
-require 'HTMLPurifier/HTMLModule/Text.php';
-require 'HTMLPurifier/HTMLModule/Tidy.php';
-require 'HTMLPurifier/HTMLModule/XMLCommonAttributes.php';
-require 'HTMLPurifier/HTMLModule/Tidy/Name.php';
-require 'HTMLPurifier/HTMLModule/Tidy/Proprietary.php';
-require 'HTMLPurifier/HTMLModule/Tidy/XHTMLAndHTML4.php';
-require 'HTMLPurifier/HTMLModule/Tidy/Strict.php';
-require 'HTMLPurifier/HTMLModule/Tidy/Transitional.php';
-require 'HTMLPurifier/HTMLModule/Tidy/XHTML.php';
-require 'HTMLPurifier/Injector/AutoParagraph.php';
-require 'HTMLPurifier/Injector/DisplayLinkURI.php';
-require 'HTMLPurifier/Injector/Linkify.php';
-require 'HTMLPurifier/Injector/PurifierLinkify.php';
-require 'HTMLPurifier/Injector/RemoveEmpty.php';
-require 'HTMLPurifier/Injector/RemoveSpansWithoutAttributes.php';
-require 'HTMLPurifier/Injector/SafeObject.php';
-require 'HTMLPurifier/Lexer/DOMLex.php';
-require 'HTMLPurifier/Lexer/DirectLex.php';
-require 'HTMLPurifier/Node/Comment.php';
-require 'HTMLPurifier/Node/Element.php';
-require 'HTMLPurifier/Node/Text.php';
-require 'HTMLPurifier/Strategy/Composite.php';
-require 'HTMLPurifier/Strategy/Core.php';
-require 'HTMLPurifier/Strategy/FixNesting.php';
-require 'HTMLPurifier/Strategy/MakeWellFormed.php';
-require 'HTMLPurifier/Strategy/RemoveForeignElements.php';
-require 'HTMLPurifier/Strategy/ValidateAttributes.php';
-require 'HTMLPurifier/TagTransform/Font.php';
-require 'HTMLPurifier/TagTransform/Simple.php';
-require 'HTMLPurifier/Token/Comment.php';
-require 'HTMLPurifier/Token/Tag.php';
-require 'HTMLPurifier/Token/Empty.php';
-require 'HTMLPurifier/Token/End.php';
-require 'HTMLPurifier/Token/Start.php';
-require 'HTMLPurifier/Token/Text.php';
-require 'HTMLPurifier/URIFilter/DisableExternal.php';
-require 'HTMLPurifier/URIFilter/DisableExternalResources.php';
-require 'HTMLPurifier/URIFilter/DisableResources.php';
-require 'HTMLPurifier/URIFilter/HostBlacklist.php';
-require 'HTMLPurifier/URIFilter/MakeAbsolute.php';
-require 'HTMLPurifier/URIFilter/Munge.php';
-require 'HTMLPurifier/URIFilter/SafeIframe.php';
-require 'HTMLPurifier/URIScheme/data.php';
-require 'HTMLPurifier/URIScheme/file.php';
-require 'HTMLPurifier/URIScheme/ftp.php';
-require 'HTMLPurifier/URIScheme/http.php';
-require 'HTMLPurifier/URIScheme/https.php';
-require 'HTMLPurifier/URIScheme/mailto.php';
-require 'HTMLPurifier/URIScheme/news.php';
-require 'HTMLPurifier/URIScheme/nntp.php';
-require 'HTMLPurifier/VarParser/Flexible.php';
-require 'HTMLPurifier/VarParser/Native.php';
diff --git a/library/HTMLPurifier.php b/library/HTMLPurifier.php
deleted file mode 100644
index 6f654fde5..000000000
--- a/library/HTMLPurifier.php
+++ /dev/null
@@ -1,292 +0,0 @@
-<?php
-
-/*! @mainpage
- *
- * HTML Purifier is an HTML filter that will take an arbitrary snippet of
- * HTML and rigorously test, validate and filter it into a version that
- * is safe for output onto webpages. It achieves this by:
- *
- * -# Lexing (parsing into tokens) the document,
- * -# Executing various strategies on the tokens:
- * -# Removing all elements not in the whitelist,
- * -# Making the tokens well-formed,
- * -# Fixing the nesting of the nodes, and
- * -# Validating attributes of the nodes; and
- * -# Generating HTML from the purified tokens.
- *
- * However, most users will only need to interface with the HTMLPurifier
- * and HTMLPurifier_Config.
- */
-
-/*
- HTML Purifier 4.6.0 - Standards Compliant HTML Filtering
- Copyright (C) 2006-2008 Edward Z. Yang
-
- This library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- This library 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
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with this library; if not, write to the Free Software
- Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
- */
-
-/**
- * Facade that coordinates HTML Purifier's subsystems in order to purify HTML.
- *
- * @note There are several points in which configuration can be specified
- * for HTML Purifier. The precedence of these (from lowest to
- * highest) is as follows:
- * -# Instance: new HTMLPurifier($config)
- * -# Invocation: purify($html, $config)
- * These configurations are entirely independent of each other and
- * are *not* merged (this behavior may change in the future).
- *
- * @todo We need an easier way to inject strategies using the configuration
- * object.
- */
-class HTMLPurifier
-{
-
- /**
- * Version of HTML Purifier.
- * @type string
- */
- public $version = '4.6.0';
-
- /**
- * Constant with version of HTML Purifier.
- */
- const VERSION = '4.6.0';
-
- /**
- * Global configuration object.
- * @type HTMLPurifier_Config
- */
- public $config;
-
- /**
- * Array of extra filter objects to run on HTML,
- * for backwards compatibility.
- * @type HTMLPurifier_Filter[]
- */
- private $filters = array();
-
- /**
- * Single instance of HTML Purifier.
- * @type HTMLPurifier
- */
- private static $instance;
-
- /**
- * @type HTMLPurifier_Strategy_Core
- */
- protected $strategy;
-
- /**
- * @type HTMLPurifier_Generator
- */
- protected $generator;
-
- /**
- * Resultant context of last run purification.
- * Is an array of contexts if the last called method was purifyArray().
- * @type HTMLPurifier_Context
- */
- public $context;
-
- /**
- * Initializes the purifier.
- *
- * @param HTMLPurifier_Config $config Optional HTMLPurifier_Config object
- * for all instances of the purifier, if omitted, a default
- * configuration is supplied (which can be overridden on a
- * per-use basis).
- * The parameter can also be any type that
- * HTMLPurifier_Config::create() supports.
- */
- public function __construct($config = null)
- {
- $this->config = HTMLPurifier_Config::create($config);
- $this->strategy = new HTMLPurifier_Strategy_Core();
- }
-
- /**
- * Adds a filter to process the output. First come first serve
- *
- * @param HTMLPurifier_Filter $filter HTMLPurifier_Filter object
- */
- public function addFilter($filter)
- {
- trigger_error(
- 'HTMLPurifier->addFilter() is deprecated, use configuration directives' .
- ' in the Filter namespace or Filter.Custom',
- E_USER_WARNING
- );
- $this->filters[] = $filter;
- }
-
- /**
- * Filters an HTML snippet/document to be XSS-free and standards-compliant.
- *
- * @param string $html String of HTML to purify
- * @param HTMLPurifier_Config $config Config object for this operation,
- * if omitted, defaults to the config object specified during this
- * object's construction. The parameter can also be any type
- * that HTMLPurifier_Config::create() supports.
- *
- * @return string Purified HTML
- */
- public function purify($html, $config = null)
- {
- // :TODO: make the config merge in, instead of replace
- $config = $config ? HTMLPurifier_Config::create($config) : $this->config;
-
- // implementation is partially environment dependant, partially
- // configuration dependant
- $lexer = HTMLPurifier_Lexer::create($config);
-
- $context = new HTMLPurifier_Context();
-
- // setup HTML generator
- $this->generator = new HTMLPurifier_Generator($config, $context);
- $context->register('Generator', $this->generator);
-
- // set up global context variables
- if ($config->get('Core.CollectErrors')) {
- // may get moved out if other facilities use it
- $language_factory = HTMLPurifier_LanguageFactory::instance();
- $language = $language_factory->create($config, $context);
- $context->register('Locale', $language);
-
- $error_collector = new HTMLPurifier_ErrorCollector($context);
- $context->register('ErrorCollector', $error_collector);
- }
-
- // setup id_accumulator context, necessary due to the fact that
- // AttrValidator can be called from many places
- $id_accumulator = HTMLPurifier_IDAccumulator::build($config, $context);
- $context->register('IDAccumulator', $id_accumulator);
-
- $html = HTMLPurifier_Encoder::convertToUTF8($html, $config, $context);
-
- // setup filters
- $filter_flags = $config->getBatch('Filter');
- $custom_filters = $filter_flags['Custom'];
- unset($filter_flags['Custom']);
- $filters = array();
- foreach ($filter_flags as $filter => $flag) {
- if (!$flag) {
- continue;
- }
- if (strpos($filter, '.') !== false) {
- continue;
- }
- $class = "HTMLPurifier_Filter_$filter";
- $filters[] = new $class;
- }
- foreach ($custom_filters as $filter) {
- // maybe "HTMLPurifier_Filter_$filter", but be consistent with AutoFormat
- $filters[] = $filter;
- }
- $filters = array_merge($filters, $this->filters);
- // maybe prepare(), but later
-
- for ($i = 0, $filter_size = count($filters); $i < $filter_size; $i++) {
- $html = $filters[$i]->preFilter($html, $config, $context);
- }
-
- // purified HTML
- $html =
- $this->generator->generateFromTokens(
- // list of tokens
- $this->strategy->execute(
- // list of un-purified tokens
- $lexer->tokenizeHTML(
- // un-purified HTML
- $html,
- $config,
- $context
- ),
- $config,
- $context
- )
- );
-
- for ($i = $filter_size - 1; $i >= 0; $i--) {
- $html = $filters[$i]->postFilter($html, $config, $context);
- }
-
- $html = HTMLPurifier_Encoder::convertFromUTF8($html, $config, $context);
- $this->context =& $context;
- return $html;
- }
-
- /**
- * Filters an array of HTML snippets
- *
- * @param string[] $array_of_html Array of html snippets
- * @param HTMLPurifier_Config $config Optional config object for this operation.
- * See HTMLPurifier::purify() for more details.
- *
- * @return string[] Array of purified HTML
- */
- public function purifyArray($array_of_html, $config = null)
- {
- $context_array = array();
- foreach ($array_of_html as $key => $html) {
- $array_of_html[$key] = $this->purify($html, $config);
- $context_array[$key] = $this->context;
- }
- $this->context = $context_array;
- return $array_of_html;
- }
-
- /**
- * Singleton for enforcing just one HTML Purifier in your system
- *
- * @param HTMLPurifier|HTMLPurifier_Config $prototype Optional prototype
- * HTMLPurifier instance to overload singleton with,
- * or HTMLPurifier_Config instance to configure the
- * generated version with.
- *
- * @return HTMLPurifier
- */
- public static function instance($prototype = null)
- {
- if (!self::$instance || $prototype) {
- if ($prototype instanceof HTMLPurifier) {
- self::$instance = $prototype;
- } elseif ($prototype) {
- self::$instance = new HTMLPurifier($prototype);
- } else {
- self::$instance = new HTMLPurifier();
- }
- }
- return self::$instance;
- }
-
- /**
- * Singleton for enforcing just one HTML Purifier in your system
- *
- * @param HTMLPurifier|HTMLPurifier_Config $prototype Optional prototype
- * HTMLPurifier instance to overload singleton with,
- * or HTMLPurifier_Config instance to configure the
- * generated version with.
- *
- * @return HTMLPurifier
- * @note Backwards compatibility, see instance()
- */
- public static function getInstance($prototype = null)
- {
- return HTMLPurifier::instance($prototype);
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier.safe-includes.php b/library/HTMLPurifier.safe-includes.php
deleted file mode 100644
index 9dea6d1ed..000000000
--- a/library/HTMLPurifier.safe-includes.php
+++ /dev/null
@@ -1,223 +0,0 @@
-<?php
-
-/**
- * @file
- * This file was auto-generated by generate-includes.php and includes all of
- * the core files required by HTML Purifier. This is a convenience stub that
- * includes all files using dirname(__FILE__) and require_once. PLEASE DO NOT
- * EDIT THIS FILE, changes will be overwritten the next time the script is run.
- *
- * Changes to include_path are not necessary.
- */
-
-$__dir = dirname(__FILE__);
-
-require_once $__dir . '/HTMLPurifier.php';
-require_once $__dir . '/HTMLPurifier/Arborize.php';
-require_once $__dir . '/HTMLPurifier/AttrCollections.php';
-require_once $__dir . '/HTMLPurifier/AttrDef.php';
-require_once $__dir . '/HTMLPurifier/AttrTransform.php';
-require_once $__dir . '/HTMLPurifier/AttrTypes.php';
-require_once $__dir . '/HTMLPurifier/AttrValidator.php';
-require_once $__dir . '/HTMLPurifier/Bootstrap.php';
-require_once $__dir . '/HTMLPurifier/Definition.php';
-require_once $__dir . '/HTMLPurifier/CSSDefinition.php';
-require_once $__dir . '/HTMLPurifier/ChildDef.php';
-require_once $__dir . '/HTMLPurifier/Config.php';
-require_once $__dir . '/HTMLPurifier/ConfigSchema.php';
-require_once $__dir . '/HTMLPurifier/ContentSets.php';
-require_once $__dir . '/HTMLPurifier/Context.php';
-require_once $__dir . '/HTMLPurifier/DefinitionCache.php';
-require_once $__dir . '/HTMLPurifier/DefinitionCacheFactory.php';
-require_once $__dir . '/HTMLPurifier/Doctype.php';
-require_once $__dir . '/HTMLPurifier/DoctypeRegistry.php';
-require_once $__dir . '/HTMLPurifier/ElementDef.php';
-require_once $__dir . '/HTMLPurifier/Encoder.php';
-require_once $__dir . '/HTMLPurifier/EntityLookup.php';
-require_once $__dir . '/HTMLPurifier/EntityParser.php';
-require_once $__dir . '/HTMLPurifier/ErrorCollector.php';
-require_once $__dir . '/HTMLPurifier/ErrorStruct.php';
-require_once $__dir . '/HTMLPurifier/Exception.php';
-require_once $__dir . '/HTMLPurifier/Filter.php';
-require_once $__dir . '/HTMLPurifier/Generator.php';
-require_once $__dir . '/HTMLPurifier/HTMLDefinition.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule.php';
-require_once $__dir . '/HTMLPurifier/HTMLModuleManager.php';
-require_once $__dir . '/HTMLPurifier/IDAccumulator.php';
-require_once $__dir . '/HTMLPurifier/Injector.php';
-require_once $__dir . '/HTMLPurifier/Language.php';
-require_once $__dir . '/HTMLPurifier/LanguageFactory.php';
-require_once $__dir . '/HTMLPurifier/Length.php';
-require_once $__dir . '/HTMLPurifier/Lexer.php';
-require_once $__dir . '/HTMLPurifier/Node.php';
-require_once $__dir . '/HTMLPurifier/PercentEncoder.php';
-require_once $__dir . '/HTMLPurifier/PropertyList.php';
-require_once $__dir . '/HTMLPurifier/PropertyListIterator.php';
-require_once $__dir . '/HTMLPurifier/Queue.php';
-require_once $__dir . '/HTMLPurifier/Strategy.php';
-require_once $__dir . '/HTMLPurifier/StringHash.php';
-require_once $__dir . '/HTMLPurifier/StringHashParser.php';
-require_once $__dir . '/HTMLPurifier/TagTransform.php';
-require_once $__dir . '/HTMLPurifier/Token.php';
-require_once $__dir . '/HTMLPurifier/TokenFactory.php';
-require_once $__dir . '/HTMLPurifier/URI.php';
-require_once $__dir . '/HTMLPurifier/URIDefinition.php';
-require_once $__dir . '/HTMLPurifier/URIFilter.php';
-require_once $__dir . '/HTMLPurifier/URIParser.php';
-require_once $__dir . '/HTMLPurifier/URIScheme.php';
-require_once $__dir . '/HTMLPurifier/URISchemeRegistry.php';
-require_once $__dir . '/HTMLPurifier/UnitConverter.php';
-require_once $__dir . '/HTMLPurifier/VarParser.php';
-require_once $__dir . '/HTMLPurifier/VarParserException.php';
-require_once $__dir . '/HTMLPurifier/Zipper.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/CSS.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/Clone.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/Enum.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/Integer.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/Lang.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/Switch.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/Text.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/URI.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/CSS/Number.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/CSS/AlphaValue.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/CSS/Background.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/CSS/BackgroundPosition.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/CSS/Border.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/CSS/Color.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/CSS/Composite.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/CSS/DenyElementDecorator.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/CSS/Filter.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/CSS/Font.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/CSS/FontFamily.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/CSS/Ident.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/CSS/ImportantDecorator.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/CSS/Length.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/CSS/ListStyle.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/CSS/Multiple.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/CSS/Percentage.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/CSS/TextDecoration.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/CSS/URI.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/HTML/Bool.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/HTML/Nmtokens.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/HTML/Class.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/HTML/Color.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/HTML/FrameTarget.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/HTML/ID.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/HTML/Pixels.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/HTML/Length.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/HTML/LinkTypes.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/HTML/MultiLength.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/URI/Email.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/URI/Host.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/URI/IPv4.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/URI/IPv6.php';
-require_once $__dir . '/HTMLPurifier/AttrDef/URI/Email/SimpleCheck.php';
-require_once $__dir . '/HTMLPurifier/AttrTransform/Background.php';
-require_once $__dir . '/HTMLPurifier/AttrTransform/BdoDir.php';
-require_once $__dir . '/HTMLPurifier/AttrTransform/BgColor.php';
-require_once $__dir . '/HTMLPurifier/AttrTransform/BoolToCSS.php';
-require_once $__dir . '/HTMLPurifier/AttrTransform/Border.php';
-require_once $__dir . '/HTMLPurifier/AttrTransform/EnumToCSS.php';
-require_once $__dir . '/HTMLPurifier/AttrTransform/ImgRequired.php';
-require_once $__dir . '/HTMLPurifier/AttrTransform/ImgSpace.php';
-require_once $__dir . '/HTMLPurifier/AttrTransform/Input.php';
-require_once $__dir . '/HTMLPurifier/AttrTransform/Lang.php';
-require_once $__dir . '/HTMLPurifier/AttrTransform/Length.php';
-require_once $__dir . '/HTMLPurifier/AttrTransform/Name.php';
-require_once $__dir . '/HTMLPurifier/AttrTransform/NameSync.php';
-require_once $__dir . '/HTMLPurifier/AttrTransform/Nofollow.php';
-require_once $__dir . '/HTMLPurifier/AttrTransform/SafeEmbed.php';
-require_once $__dir . '/HTMLPurifier/AttrTransform/SafeObject.php';
-require_once $__dir . '/HTMLPurifier/AttrTransform/SafeParam.php';
-require_once $__dir . '/HTMLPurifier/AttrTransform/ScriptRequired.php';
-require_once $__dir . '/HTMLPurifier/AttrTransform/TargetBlank.php';
-require_once $__dir . '/HTMLPurifier/AttrTransform/Textarea.php';
-require_once $__dir . '/HTMLPurifier/ChildDef/Chameleon.php';
-require_once $__dir . '/HTMLPurifier/ChildDef/Custom.php';
-require_once $__dir . '/HTMLPurifier/ChildDef/Empty.php';
-require_once $__dir . '/HTMLPurifier/ChildDef/List.php';
-require_once $__dir . '/HTMLPurifier/ChildDef/Required.php';
-require_once $__dir . '/HTMLPurifier/ChildDef/Optional.php';
-require_once $__dir . '/HTMLPurifier/ChildDef/StrictBlockquote.php';
-require_once $__dir . '/HTMLPurifier/ChildDef/Table.php';
-require_once $__dir . '/HTMLPurifier/DefinitionCache/Decorator.php';
-require_once $__dir . '/HTMLPurifier/DefinitionCache/Null.php';
-require_once $__dir . '/HTMLPurifier/DefinitionCache/Serializer.php';
-require_once $__dir . '/HTMLPurifier/DefinitionCache/Decorator/Cleanup.php';
-require_once $__dir . '/HTMLPurifier/DefinitionCache/Decorator/Memory.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Bdo.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/CommonAttributes.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Edit.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Forms.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Hypertext.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Iframe.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Image.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Legacy.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/List.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Name.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Nofollow.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/NonXMLCommonAttributes.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Object.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Presentation.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Proprietary.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Ruby.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/SafeEmbed.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/SafeObject.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/SafeScripting.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Scripting.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/StyleAttribute.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Tables.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Target.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/TargetBlank.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Text.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Tidy.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/XMLCommonAttributes.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Tidy/Name.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Tidy/Proprietary.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Tidy/XHTMLAndHTML4.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Tidy/Strict.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Tidy/Transitional.php';
-require_once $__dir . '/HTMLPurifier/HTMLModule/Tidy/XHTML.php';
-require_once $__dir . '/HTMLPurifier/Injector/AutoParagraph.php';
-require_once $__dir . '/HTMLPurifier/Injector/DisplayLinkURI.php';
-require_once $__dir . '/HTMLPurifier/Injector/Linkify.php';
-require_once $__dir . '/HTMLPurifier/Injector/PurifierLinkify.php';
-require_once $__dir . '/HTMLPurifier/Injector/RemoveEmpty.php';
-require_once $__dir . '/HTMLPurifier/Injector/RemoveSpansWithoutAttributes.php';
-require_once $__dir . '/HTMLPurifier/Injector/SafeObject.php';
-require_once $__dir . '/HTMLPurifier/Lexer/DOMLex.php';
-require_once $__dir . '/HTMLPurifier/Lexer/DirectLex.php';
-require_once $__dir . '/HTMLPurifier/Node/Comment.php';
-require_once $__dir . '/HTMLPurifier/Node/Element.php';
-require_once $__dir . '/HTMLPurifier/Node/Text.php';
-require_once $__dir . '/HTMLPurifier/Strategy/Composite.php';
-require_once $__dir . '/HTMLPurifier/Strategy/Core.php';
-require_once $__dir . '/HTMLPurifier/Strategy/FixNesting.php';
-require_once $__dir . '/HTMLPurifier/Strategy/MakeWellFormed.php';
-require_once $__dir . '/HTMLPurifier/Strategy/RemoveForeignElements.php';
-require_once $__dir . '/HTMLPurifier/Strategy/ValidateAttributes.php';
-require_once $__dir . '/HTMLPurifier/TagTransform/Font.php';
-require_once $__dir . '/HTMLPurifier/TagTransform/Simple.php';
-require_once $__dir . '/HTMLPurifier/Token/Comment.php';
-require_once $__dir . '/HTMLPurifier/Token/Tag.php';
-require_once $__dir . '/HTMLPurifier/Token/Empty.php';
-require_once $__dir . '/HTMLPurifier/Token/End.php';
-require_once $__dir . '/HTMLPurifier/Token/Start.php';
-require_once $__dir . '/HTMLPurifier/Token/Text.php';
-require_once $__dir . '/HTMLPurifier/URIFilter/DisableExternal.php';
-require_once $__dir . '/HTMLPurifier/URIFilter/DisableExternalResources.php';
-require_once $__dir . '/HTMLPurifier/URIFilter/DisableResources.php';
-require_once $__dir . '/HTMLPurifier/URIFilter/HostBlacklist.php';
-require_once $__dir . '/HTMLPurifier/URIFilter/MakeAbsolute.php';
-require_once $__dir . '/HTMLPurifier/URIFilter/Munge.php';
-require_once $__dir . '/HTMLPurifier/URIFilter/SafeIframe.php';
-require_once $__dir . '/HTMLPurifier/URIScheme/data.php';
-require_once $__dir . '/HTMLPurifier/URIScheme/file.php';
-require_once $__dir . '/HTMLPurifier/URIScheme/ftp.php';
-require_once $__dir . '/HTMLPurifier/URIScheme/http.php';
-require_once $__dir . '/HTMLPurifier/URIScheme/https.php';
-require_once $__dir . '/HTMLPurifier/URIScheme/mailto.php';
-require_once $__dir . '/HTMLPurifier/URIScheme/news.php';
-require_once $__dir . '/HTMLPurifier/URIScheme/nntp.php';
-require_once $__dir . '/HTMLPurifier/VarParser/Flexible.php';
-require_once $__dir . '/HTMLPurifier/VarParser/Native.php';
diff --git a/library/HTMLPurifier/Arborize.php b/library/HTMLPurifier/Arborize.php
deleted file mode 100644
index 9e6617be5..000000000
--- a/library/HTMLPurifier/Arborize.php
+++ /dev/null
@@ -1,71 +0,0 @@
-<?php
-
-/**
- * Converts a stream of HTMLPurifier_Token into an HTMLPurifier_Node,
- * and back again.
- *
- * @note This transformation is not an equivalence. We mutate the input
- * token stream to make it so; see all [MUT] markers in code.
- */
-class HTMLPurifier_Arborize
-{
- public static function arborize($tokens, $config, $context) {
- $definition = $config->getHTMLDefinition();
- $parent = new HTMLPurifier_Token_Start($definition->info_parent);
- $stack = array($parent->toNode());
- foreach ($tokens as $token) {
- $token->skip = null; // [MUT]
- $token->carryover = null; // [MUT]
- if ($token instanceof HTMLPurifier_Token_End) {
- $token->start = null; // [MUT]
- $r = array_pop($stack);
- assert($r->name === $token->name);
- assert(empty($token->attr));
- $r->endCol = $token->col;
- $r->endLine = $token->line;
- $r->endArmor = $token->armor;
- continue;
- }
- $node = $token->toNode();
- $stack[count($stack)-1]->children[] = $node;
- if ($token instanceof HTMLPurifier_Token_Start) {
- $stack[] = $node;
- }
- }
- assert(count($stack) == 1);
- return $stack[0];
- }
-
- public static function flatten($node, $config, $context) {
- $level = 0;
- $nodes = array($level => new HTMLPurifier_Queue(array($node)));
- $closingTokens = array();
- $tokens = array();
- do {
- while (!$nodes[$level]->isEmpty()) {
- $node = $nodes[$level]->shift(); // FIFO
- list($start, $end) = $node->toTokenPair();
- if ($level > 0) {
- $tokens[] = $start;
- }
- if ($end !== NULL) {
- $closingTokens[$level][] = $end;
- }
- if ($node instanceof HTMLPurifier_Node_Element) {
- $level++;
- $nodes[$level] = new HTMLPurifier_Queue();
- foreach ($node->children as $childNode) {
- $nodes[$level]->push($childNode);
- }
- }
- }
- $level--;
- if ($level && isset($closingTokens[$level])) {
- while ($token = array_pop($closingTokens[$level])) {
- $tokens[] = $token;
- }
- }
- } while ($level > 0);
- return $tokens;
- }
-}
diff --git a/library/HTMLPurifier/AttrCollections.php b/library/HTMLPurifier/AttrCollections.php
deleted file mode 100644
index 4f6c2e39a..000000000
--- a/library/HTMLPurifier/AttrCollections.php
+++ /dev/null
@@ -1,143 +0,0 @@
-<?php
-
-/**
- * Defines common attribute collections that modules reference
- */
-
-class HTMLPurifier_AttrCollections
-{
-
- /**
- * Associative array of attribute collections, indexed by name.
- * @type array
- */
- public $info = array();
-
- /**
- * Performs all expansions on internal data for use by other inclusions
- * It also collects all attribute collection extensions from
- * modules
- * @param HTMLPurifier_AttrTypes $attr_types HTMLPurifier_AttrTypes instance
- * @param HTMLPurifier_HTMLModule[] $modules Hash array of HTMLPurifier_HTMLModule members
- */
- public function __construct($attr_types, $modules)
- {
- // load extensions from the modules
- foreach ($modules as $module) {
- foreach ($module->attr_collections as $coll_i => $coll) {
- if (!isset($this->info[$coll_i])) {
- $this->info[$coll_i] = array();
- }
- foreach ($coll as $attr_i => $attr) {
- if ($attr_i === 0 && isset($this->info[$coll_i][$attr_i])) {
- // merge in includes
- $this->info[$coll_i][$attr_i] = array_merge(
- $this->info[$coll_i][$attr_i],
- $attr
- );
- continue;
- }
- $this->info[$coll_i][$attr_i] = $attr;
- }
- }
- }
- // perform internal expansions and inclusions
- foreach ($this->info as $name => $attr) {
- // merge attribute collections that include others
- $this->performInclusions($this->info[$name]);
- // replace string identifiers with actual attribute objects
- $this->expandIdentifiers($this->info[$name], $attr_types);
- }
- }
-
- /**
- * Takes a reference to an attribute associative array and performs
- * all inclusions specified by the zero index.
- * @param array &$attr Reference to attribute array
- */
- public function performInclusions(&$attr)
- {
- if (!isset($attr[0])) {
- return;
- }
- $merge = $attr[0];
- $seen = array(); // recursion guard
- // loop through all the inclusions
- for ($i = 0; isset($merge[$i]); $i++) {
- if (isset($seen[$merge[$i]])) {
- continue;
- }
- $seen[$merge[$i]] = true;
- // foreach attribute of the inclusion, copy it over
- if (!isset($this->info[$merge[$i]])) {
- continue;
- }
- foreach ($this->info[$merge[$i]] as $key => $value) {
- if (isset($attr[$key])) {
- continue;
- } // also catches more inclusions
- $attr[$key] = $value;
- }
- if (isset($this->info[$merge[$i]][0])) {
- // recursion
- $merge = array_merge($merge, $this->info[$merge[$i]][0]);
- }
- }
- unset($attr[0]);
- }
-
- /**
- * Expands all string identifiers in an attribute array by replacing
- * them with the appropriate values inside HTMLPurifier_AttrTypes
- * @param array &$attr Reference to attribute array
- * @param HTMLPurifier_AttrTypes $attr_types HTMLPurifier_AttrTypes instance
- */
- public function expandIdentifiers(&$attr, $attr_types)
- {
- // because foreach will process new elements we add, make sure we
- // skip duplicates
- $processed = array();
-
- foreach ($attr as $def_i => $def) {
- // skip inclusions
- if ($def_i === 0) {
- continue;
- }
-
- if (isset($processed[$def_i])) {
- continue;
- }
-
- // determine whether or not attribute is required
- if ($required = (strpos($def_i, '*') !== false)) {
- // rename the definition
- unset($attr[$def_i]);
- $def_i = trim($def_i, '*');
- $attr[$def_i] = $def;
- }
-
- $processed[$def_i] = true;
-
- // if we've already got a literal object, move on
- if (is_object($def)) {
- // preserve previous required
- $attr[$def_i]->required = ($required || $attr[$def_i]->required);
- continue;
- }
-
- if ($def === false) {
- unset($attr[$def_i]);
- continue;
- }
-
- if ($t = $attr_types->get($def)) {
- $attr[$def_i] = $t;
- $attr[$def_i]->required = $required;
- } else {
- unset($attr[$def_i]);
- }
- }
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/AttrDef.php b/library/HTMLPurifier/AttrDef.php
deleted file mode 100644
index 5ac06522b..000000000
--- a/library/HTMLPurifier/AttrDef.php
+++ /dev/null
@@ -1,138 +0,0 @@
-<?php
-
-/**
- * Base class for all validating attribute definitions.
- *
- * This family of classes forms the core for not only HTML attribute validation,
- * but also any sort of string that needs to be validated or cleaned (which
- * means CSS properties and composite definitions are defined here too).
- * Besides defining (through code) what precisely makes the string valid,
- * subclasses are also responsible for cleaning the code if possible.
- */
-
-abstract class HTMLPurifier_AttrDef
-{
-
- /**
- * Tells us whether or not an HTML attribute is minimized.
- * Has no meaning in other contexts.
- * @type bool
- */
- public $minimized = false;
-
- /**
- * Tells us whether or not an HTML attribute is required.
- * Has no meaning in other contexts
- * @type bool
- */
- public $required = false;
-
- /**
- * Validates and cleans passed string according to a definition.
- *
- * @param string $string String to be validated and cleaned.
- * @param HTMLPurifier_Config $config Mandatory HTMLPurifier_Config object.
- * @param HTMLPurifier_Context $context Mandatory HTMLPurifier_Context object.
- */
- abstract public function validate($string, $config, $context);
-
- /**
- * Convenience method that parses a string as if it were CDATA.
- *
- * This method process a string in the manner specified at
- * <http://www.w3.org/TR/html4/types.html#h-6.2> by removing
- * leading and trailing whitespace, ignoring line feeds, and replacing
- * carriage returns and tabs with spaces. While most useful for HTML
- * attributes specified as CDATA, it can also be applied to most CSS
- * values.
- *
- * @note This method is not entirely standards compliant, as trim() removes
- * more types of whitespace than specified in the spec. In practice,
- * this is rarely a problem, as those extra characters usually have
- * already been removed by HTMLPurifier_Encoder.
- *
- * @warning This processing is inconsistent with XML's whitespace handling
- * as specified by section 3.3.3 and referenced XHTML 1.0 section
- * 4.7. However, note that we are NOT necessarily
- * parsing XML, thus, this behavior may still be correct. We
- * assume that newlines have been normalized.
- */
- public function parseCDATA($string)
- {
- $string = trim($string);
- $string = str_replace(array("\n", "\t", "\r"), ' ', $string);
- return $string;
- }
-
- /**
- * Factory method for creating this class from a string.
- * @param string $string String construction info
- * @return HTMLPurifier_AttrDef Created AttrDef object corresponding to $string
- */
- public function make($string)
- {
- // default implementation, return a flyweight of this object.
- // If $string has an effect on the returned object (i.e. you
- // need to overload this method), it is best
- // to clone or instantiate new copies. (Instantiation is safer.)
- return $this;
- }
-
- /**
- * Removes spaces from rgb(0, 0, 0) so that shorthand CSS properties work
- * properly. THIS IS A HACK!
- * @param string $string a CSS colour definition
- * @return string
- */
- protected function mungeRgb($string)
- {
- return preg_replace('/rgb\((\d+)\s*,\s*(\d+)\s*,\s*(\d+)\)/', 'rgb(\1,\2,\3)', $string);
- }
-
- /**
- * Parses a possibly escaped CSS string and returns the "pure"
- * version of it.
- */
- protected function expandCSSEscape($string)
- {
- // flexibly parse it
- $ret = '';
- for ($i = 0, $c = strlen($string); $i < $c; $i++) {
- if ($string[$i] === '\\') {
- $i++;
- if ($i >= $c) {
- $ret .= '\\';
- break;
- }
- if (ctype_xdigit($string[$i])) {
- $code = $string[$i];
- for ($a = 1, $i++; $i < $c && $a < 6; $i++, $a++) {
- if (!ctype_xdigit($string[$i])) {
- break;
- }
- $code .= $string[$i];
- }
- // We have to be extremely careful when adding
- // new characters, to make sure we're not breaking
- // the encoding.
- $char = HTMLPurifier_Encoder::unichr(hexdec($code));
- if (HTMLPurifier_Encoder::cleanUTF8($char) === '') {
- continue;
- }
- $ret .= $char;
- if ($i < $c && trim($string[$i]) !== '') {
- $i--;
- }
- continue;
- }
- if ($string[$i] === "\n") {
- continue;
- }
- }
- $ret .= $string[$i];
- }
- return $ret;
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/AttrDef/CSS.php b/library/HTMLPurifier/AttrDef/CSS.php
deleted file mode 100644
index 02c1641fb..000000000
--- a/library/HTMLPurifier/AttrDef/CSS.php
+++ /dev/null
@@ -1,106 +0,0 @@
-<?php
-
-/**
- * Validates the HTML attribute style, otherwise known as CSS.
- * @note We don't implement the whole CSS specification, so it might be
- * difficult to reuse this component in the context of validating
- * actual stylesheet declarations.
- * @note If we were really serious about validating the CSS, we would
- * tokenize the styles and then parse the tokens. Obviously, we
- * are not doing that. Doing that could seriously harm performance,
- * but would make these components a lot more viable for a CSS
- * filtering solution.
- */
-class HTMLPurifier_AttrDef_CSS extends HTMLPurifier_AttrDef
-{
-
- /**
- * @param string $css
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return bool|string
- */
- public function validate($css, $config, $context)
- {
- $css = $this->parseCDATA($css);
-
- $definition = $config->getCSSDefinition();
-
- // we're going to break the spec and explode by semicolons.
- // This is because semicolon rarely appears in escaped form
- // Doing this is generally flaky but fast
- // IT MIGHT APPEAR IN URIs, see HTMLPurifier_AttrDef_CSSURI
- // for details
-
- $declarations = explode(';', $css);
- $propvalues = array();
-
- /**
- * Name of the current CSS property being validated.
- */
- $property = false;
- $context->register('CurrentCSSProperty', $property);
-
- foreach ($declarations as $declaration) {
- if (!$declaration) {
- continue;
- }
- if (!strpos($declaration, ':')) {
- continue;
- }
- list($property, $value) = explode(':', $declaration, 2);
- $property = trim($property);
- $value = trim($value);
- $ok = false;
- do {
- if (isset($definition->info[$property])) {
- $ok = true;
- break;
- }
- if (ctype_lower($property)) {
- break;
- }
- $property = strtolower($property);
- if (isset($definition->info[$property])) {
- $ok = true;
- break;
- }
- } while (0);
- if (!$ok) {
- continue;
- }
- // inefficient call, since the validator will do this again
- if (strtolower(trim($value)) !== 'inherit') {
- // inherit works for everything (but only on the base property)
- $result = $definition->info[$property]->validate(
- $value,
- $config,
- $context
- );
- } else {
- $result = 'inherit';
- }
- if ($result === false) {
- continue;
- }
- $propvalues[$property] = $result;
- }
-
- $context->destroy('CurrentCSSProperty');
-
- // procedure does not write the new CSS simultaneously, so it's
- // slightly inefficient, but it's the only way of getting rid of
- // duplicates. Perhaps config to optimize it, but not now.
-
- $new_declarations = '';
- foreach ($propvalues as $prop => $value) {
- $new_declarations .= "$prop:$value;";
- }
-
- return $new_declarations ? $new_declarations : false;
-
- }
-
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/AttrDef/CSS/Color.php b/library/HTMLPurifier/AttrDef/CSS/Color.php
deleted file mode 100644
index 16d2a6b98..000000000
--- a/library/HTMLPurifier/AttrDef/CSS/Color.php
+++ /dev/null
@@ -1,105 +0,0 @@
-<?php
-
-/**
- * Validates Color as defined by CSS.
- */
-class HTMLPurifier_AttrDef_CSS_Color extends HTMLPurifier_AttrDef
-{
-
- /**
- * @param string $color
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return bool|string
- */
- public function validate($color, $config, $context)
- {
- static $colors = null;
- if ($colors === null) {
- $colors = $config->get('Core.ColorKeywords');
- }
-
- $color = trim($color);
- if ($color === '') {
- return false;
- }
-
- $lower = strtolower($color);
- if (isset($colors[$lower])) {
- return $colors[$lower];
- }
-
- if (strpos($color, 'rgb(') !== false) {
- // rgb literal handling
- $length = strlen($color);
- if (strpos($color, ')') !== $length - 1) {
- return false;
- }
- $triad = substr($color, 4, $length - 4 - 1);
- $parts = explode(',', $triad);
- if (count($parts) !== 3) {
- return false;
- }
- $type = false; // to ensure that they're all the same type
- $new_parts = array();
- foreach ($parts as $part) {
- $part = trim($part);
- if ($part === '') {
- return false;
- }
- $length = strlen($part);
- if ($part[$length - 1] === '%') {
- // handle percents
- if (!$type) {
- $type = 'percentage';
- } elseif ($type !== 'percentage') {
- return false;
- }
- $num = (float)substr($part, 0, $length - 1);
- if ($num < 0) {
- $num = 0;
- }
- if ($num > 100) {
- $num = 100;
- }
- $new_parts[] = "$num%";
- } else {
- // handle integers
- if (!$type) {
- $type = 'integer';
- } elseif ($type !== 'integer') {
- return false;
- }
- $num = (int)$part;
- if ($num < 0) {
- $num = 0;
- }
- if ($num > 255) {
- $num = 255;
- }
- $new_parts[] = (string)$num;
- }
- }
- $new_triad = implode(',', $new_parts);
- $color = "rgb($new_triad)";
- } else {
- // hexadecimal handling
- if ($color[0] === '#') {
- $hex = substr($color, 1);
- } else {
- $hex = $color;
- $color = '#' . $color;
- }
- $length = strlen($hex);
- if ($length !== 3 && $length !== 6) {
- return false;
- }
- if (!ctype_xdigit($hex)) {
- return false;
- }
- }
- return $color;
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/AttrDef/CSS/Multiple.php b/library/HTMLPurifier/AttrDef/CSS/Multiple.php
deleted file mode 100644
index 9f266cdd1..000000000
--- a/library/HTMLPurifier/AttrDef/CSS/Multiple.php
+++ /dev/null
@@ -1,71 +0,0 @@
-<?php
-
-/**
- * Framework class for strings that involve multiple values.
- *
- * Certain CSS properties such as border-width and margin allow multiple
- * lengths to be specified. This class can take a vanilla border-width
- * definition and multiply it, usually into a max of four.
- *
- * @note Even though the CSS specification isn't clear about it, inherit
- * can only be used alone: it will never manifest as part of a multi
- * shorthand declaration. Thus, this class does not allow inherit.
- */
-class HTMLPurifier_AttrDef_CSS_Multiple extends HTMLPurifier_AttrDef
-{
- /**
- * Instance of component definition to defer validation to.
- * @type HTMLPurifier_AttrDef
- * @todo Make protected
- */
- public $single;
-
- /**
- * Max number of values allowed.
- * @todo Make protected
- */
- public $max;
-
- /**
- * @param HTMLPurifier_AttrDef $single HTMLPurifier_AttrDef to multiply
- * @param int $max Max number of values allowed (usually four)
- */
- public function __construct($single, $max = 4)
- {
- $this->single = $single;
- $this->max = $max;
- }
-
- /**
- * @param string $string
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return bool|string
- */
- public function validate($string, $config, $context)
- {
- $string = $this->parseCDATA($string);
- if ($string === '') {
- return false;
- }
- $parts = explode(' ', $string); // parseCDATA replaced \r, \t and \n
- $length = count($parts);
- $final = '';
- for ($i = 0, $num = 0; $i < $length && $num < $this->max; $i++) {
- if (ctype_space($parts[$i])) {
- continue;
- }
- $result = $this->single->validate($parts[$i], $config, $context);
- if ($result !== false) {
- $final .= $result . ' ';
- $num++;
- }
- }
- if ($final === '') {
- return false;
- }
- return rtrim($final);
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/AttrDef/CSS/URI.php b/library/HTMLPurifier/AttrDef/CSS/URI.php
deleted file mode 100644
index f9434230e..000000000
--- a/library/HTMLPurifier/AttrDef/CSS/URI.php
+++ /dev/null
@@ -1,74 +0,0 @@
-<?php
-
-/**
- * Validates a URI in CSS syntax, which uses url('http://example.com')
- * @note While theoretically speaking a URI in a CSS document could
- * be non-embedded, as of CSS2 there is no such usage so we're
- * generalizing it. This may need to be changed in the future.
- * @warning Since HTMLPurifier_AttrDef_CSS blindly uses semicolons as
- * the separator, you cannot put a literal semicolon in
- * in the URI. Try percent encoding it, in that case.
- */
-class HTMLPurifier_AttrDef_CSS_URI extends HTMLPurifier_AttrDef_URI
-{
-
- public function __construct()
- {
- parent::__construct(true); // always embedded
- }
-
- /**
- * @param string $uri_string
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return bool|string
- */
- public function validate($uri_string, $config, $context)
- {
- // parse the URI out of the string and then pass it onto
- // the parent object
-
- $uri_string = $this->parseCDATA($uri_string);
- if (strpos($uri_string, 'url(') !== 0) {
- return false;
- }
- $uri_string = substr($uri_string, 4);
- $new_length = strlen($uri_string) - 1;
- if ($uri_string[$new_length] != ')') {
- return false;
- }
- $uri = trim(substr($uri_string, 0, $new_length));
-
- if (!empty($uri) && ($uri[0] == "'" || $uri[0] == '"')) {
- $quote = $uri[0];
- $new_length = strlen($uri) - 1;
- if ($uri[$new_length] !== $quote) {
- return false;
- }
- $uri = substr($uri, 1, $new_length - 1);
- }
-
- $uri = $this->expandCSSEscape($uri);
-
- $result = parent::validate($uri, $config, $context);
-
- if ($result === false) {
- return false;
- }
-
- // extra sanity check; should have been done by URI
- $result = str_replace(array('"', "\\", "\n", "\x0c", "\r"), "", $result);
-
- // suspicious characters are ()'; we're going to percent encode
- // them for safety.
- $result = str_replace(array('(', ')', "'"), array('%28', '%29', '%27'), $result);
-
- // there's an extra bug where ampersands lose their escaping on
- // an innerHTML cycle, so a very unlucky query parameter could
- // then change the meaning of the URL. Unfortunately, there's
- // not much we can do about that...
- return "url(\"$result\")";
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/AttrDef/HTML/Bool.php b/library/HTMLPurifier/AttrDef/HTML/Bool.php
deleted file mode 100644
index 036a240e1..000000000
--- a/library/HTMLPurifier/AttrDef/HTML/Bool.php
+++ /dev/null
@@ -1,51 +0,0 @@
-<?php
-
-/**
- * Validates a boolean attribute
- */
-class HTMLPurifier_AttrDef_HTML_Bool extends HTMLPurifier_AttrDef
-{
-
- /**
- * @type bool
- */
- protected $name;
-
- /**
- * @type bool
- */
- public $minimized = true;
-
- /**
- * @param bool $name
- */
- public function __construct($name = false)
- {
- $this->name = $name;
- }
-
- /**
- * @param string $string
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return bool|string
- */
- public function validate($string, $config, $context)
- {
- if (empty($string)) {
- return false;
- }
- return $this->name;
- }
-
- /**
- * @param string $string Name of attribute
- * @return HTMLPurifier_AttrDef_HTML_Bool
- */
- public function make($string)
- {
- return new HTMLPurifier_AttrDef_HTML_Bool($string);
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/AttrDef/HTML/ID.php b/library/HTMLPurifier/AttrDef/HTML/ID.php
deleted file mode 100644
index 3d86efb44..000000000
--- a/library/HTMLPurifier/AttrDef/HTML/ID.php
+++ /dev/null
@@ -1,105 +0,0 @@
-<?php
-
-/**
- * Validates the HTML attribute ID.
- * @warning Even though this is the id processor, it
- * will ignore the directive Attr:IDBlacklist, since it will only
- * go according to the ID accumulator. Since the accumulator is
- * automatically generated, it will have already absorbed the
- * blacklist. If you're hacking around, make sure you use load()!
- */
-
-class HTMLPurifier_AttrDef_HTML_ID extends HTMLPurifier_AttrDef
-{
-
- // selector is NOT a valid thing to use for IDREFs, because IDREFs
- // *must* target IDs that exist, whereas selector #ids do not.
-
- /**
- * Determines whether or not we're validating an ID in a CSS
- * selector context.
- * @type bool
- */
- protected $selector;
-
- /**
- * @param bool $selector
- */
- public function __construct($selector = false)
- {
- $this->selector = $selector;
- }
-
- /**
- * @param string $id
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return bool|string
- */
- public function validate($id, $config, $context)
- {
- if (!$this->selector && !$config->get('Attr.EnableID')) {
- return false;
- }
-
- $id = trim($id); // trim it first
-
- if ($id === '') {
- return false;
- }
-
- $prefix = $config->get('Attr.IDPrefix');
- if ($prefix !== '') {
- $prefix .= $config->get('Attr.IDPrefixLocal');
- // prevent re-appending the prefix
- if (strpos($id, $prefix) !== 0) {
- $id = $prefix . $id;
- }
- } elseif ($config->get('Attr.IDPrefixLocal') !== '') {
- trigger_error(
- '%Attr.IDPrefixLocal cannot be used unless ' .
- '%Attr.IDPrefix is set',
- E_USER_WARNING
- );
- }
-
- if (!$this->selector) {
- $id_accumulator =& $context->get('IDAccumulator');
- if (isset($id_accumulator->ids[$id])) {
- return false;
- }
- }
-
- // we purposely avoid using regex, hopefully this is faster
-
- if (ctype_alpha($id)) {
- $result = true;
- } else {
- if (!ctype_alpha(@$id[0])) {
- return false;
- }
- // primitive style of regexps, I suppose
- $trim = trim(
- $id,
- 'A..Za..z0..9:-._'
- );
- $result = ($trim === '');
- }
-
- $regexp = $config->get('Attr.IDBlacklistRegexp');
- if ($regexp && preg_match($regexp, $id)) {
- return false;
- }
-
- if (!$this->selector && $result) {
- $id_accumulator->add($id);
- }
-
- // if no change was made to the ID, return the result
- // else, return the new id if stripping whitespace made it
- // valid, or return false.
- return $result ? $id : false;
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/AttrDef/URI/Host.php b/library/HTMLPurifier/AttrDef/URI/Host.php
deleted file mode 100644
index e7df800b1..000000000
--- a/library/HTMLPurifier/AttrDef/URI/Host.php
+++ /dev/null
@@ -1,128 +0,0 @@
-<?php
-
-/**
- * Validates a host according to the IPv4, IPv6 and DNS (future) specifications.
- */
-class HTMLPurifier_AttrDef_URI_Host extends HTMLPurifier_AttrDef
-{
-
- /**
- * IPv4 sub-validator.
- * @type HTMLPurifier_AttrDef_URI_IPv4
- */
- protected $ipv4;
-
- /**
- * IPv6 sub-validator.
- * @type HTMLPurifier_AttrDef_URI_IPv6
- */
- protected $ipv6;
-
- public function __construct()
- {
- $this->ipv4 = new HTMLPurifier_AttrDef_URI_IPv4();
- $this->ipv6 = new HTMLPurifier_AttrDef_URI_IPv6();
- }
-
- /**
- * @param string $string
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return bool|string
- */
- public function validate($string, $config, $context)
- {
- $length = strlen($string);
- // empty hostname is OK; it's usually semantically equivalent:
- // the default host as defined by a URI scheme is used:
- //
- // If the URI scheme defines a default for host, then that
- // default applies when the host subcomponent is undefined
- // or when the registered name is empty (zero length).
- if ($string === '') {
- return '';
- }
- if ($length > 1 && $string[0] === '[' && $string[$length - 1] === ']') {
- //IPv6
- $ip = substr($string, 1, $length - 2);
- $valid = $this->ipv6->validate($ip, $config, $context);
- if ($valid === false) {
- return false;
- }
- return '[' . $valid . ']';
- }
-
- // need to do checks on unusual encodings too
- $ipv4 = $this->ipv4->validate($string, $config, $context);
- if ($ipv4 !== false) {
- return $ipv4;
- }
-
- // A regular domain name.
-
- // This doesn't match I18N domain names, but we don't have proper IRI support,
- // so force users to insert Punycode.
-
- // There is not a good sense in which underscores should be
- // allowed, since it's technically not! (And if you go as
- // far to allow everything as specified by the DNS spec...
- // well, that's literally everything, modulo some space limits
- // for the components and the overall name (which, by the way,
- // we are NOT checking!). So we (arbitrarily) decide this:
- // let's allow underscores wherever we would have allowed
- // hyphens, if they are enabled. This is a pretty good match
- // for browser behavior, for example, a large number of browsers
- // cannot handle foo_.example.com, but foo_bar.example.com is
- // fairly well supported.
- $underscore = $config->get('Core.AllowHostnameUnderscore') ? '_' : '';
-
- // The productions describing this are:
- $a = '[a-z]'; // alpha
- $an = '[a-z0-9]'; // alphanum
- $and = "[a-z0-9-$underscore]"; // alphanum | "-"
- // domainlabel = alphanum | alphanum *( alphanum | "-" ) alphanum
- $domainlabel = "$an($and*$an)?";
- // toplabel = alpha | alpha *( alphanum | "-" ) alphanum
- $toplabel = "$a($and*$an)?";
- // hostname = *( domainlabel "." ) toplabel [ "." ]
- if (preg_match("/^($domainlabel\.)*$toplabel\.?$/i", $string)) {
- return $string;
- }
-
- // If we have Net_IDNA2 support, we can support IRIs by
- // punycoding them. (This is the most portable thing to do,
- // since otherwise we have to assume browsers support
-
- if ($config->get('Core.EnableIDNA')) {
- $idna = new Net_IDNA2(array('encoding' => 'utf8', 'overlong' => false, 'strict' => true));
- // we need to encode each period separately
- $parts = explode('.', $string);
- try {
- $new_parts = array();
- foreach ($parts as $part) {
- $encodable = false;
- for ($i = 0, $c = strlen($part); $i < $c; $i++) {
- if (ord($part[$i]) > 0x7a) {
- $encodable = true;
- break;
- }
- }
- if (!$encodable) {
- $new_parts[] = $part;
- } else {
- $new_parts[] = $idna->encode($part);
- }
- }
- $string = implode('.', $new_parts);
- if (preg_match("/^($domainlabel\.)*$toplabel\.?$/i", $string)) {
- return $string;
- }
- } catch (Exception $e) {
- // XXX error reporting
- }
- }
- return false;
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/AttrTransform/ImgRequired.php b/library/HTMLPurifier/AttrTransform/ImgRequired.php
deleted file mode 100644
index 7df6cb3e1..000000000
--- a/library/HTMLPurifier/AttrTransform/ImgRequired.php
+++ /dev/null
@@ -1,48 +0,0 @@
-<?php
-
-// must be called POST validation
-
-/**
- * Transform that supplies default values for the src and alt attributes
- * in img tags, as well as prevents the img tag from being removed
- * because of a missing alt tag. This needs to be registered as both
- * a pre and post attribute transform.
- */
-class HTMLPurifier_AttrTransform_ImgRequired extends HTMLPurifier_AttrTransform
-{
-
- /**
- * @param array $attr
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return array
- */
- public function transform($attr, $config, $context)
- {
- $src = true;
- if (!isset($attr['src'])) {
- if ($config->get('Core.RemoveInvalidImg')) {
- return $attr;
- }
- $attr['src'] = $config->get('Attr.DefaultInvalidImage');
- $src = false;
- }
-
- if (!isset($attr['alt'])) {
- if ($src) {
- $alt = $config->get('Attr.DefaultImageAlt');
- if ($alt === null) {
- // truncate if the alt is too long
- $attr['alt'] = substr(basename($attr['src']), 0, 40);
- } else {
- $attr['alt'] = $alt;
- }
- } else {
- $attr['alt'] = $config->get('Attr.DefaultInvalidImageAlt');
- }
- }
- return $attr;
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/CSSDefinition.php b/library/HTMLPurifier/CSSDefinition.php
deleted file mode 100644
index 0acdee2d9..000000000
--- a/library/HTMLPurifier/CSSDefinition.php
+++ /dev/null
@@ -1,474 +0,0 @@
-<?php
-
-/**
- * Defines allowed CSS attributes and what their values are.
- * @see HTMLPurifier_HTMLDefinition
- */
-class HTMLPurifier_CSSDefinition extends HTMLPurifier_Definition
-{
-
- public $type = 'CSS';
-
- /**
- * Assoc array of attribute name to definition object.
- * @type HTMLPurifier_AttrDef[]
- */
- public $info = array();
-
- /**
- * Constructs the info array. The meat of this class.
- * @param HTMLPurifier_Config $config
- */
- protected function doSetup($config)
- {
- $this->info['text-align'] = new HTMLPurifier_AttrDef_Enum(
- array('left', 'right', 'center', 'justify'),
- false
- );
-
- $border_style =
- $this->info['border-bottom-style'] =
- $this->info['border-right-style'] =
- $this->info['border-left-style'] =
- $this->info['border-top-style'] = new HTMLPurifier_AttrDef_Enum(
- array(
- 'none',
- 'hidden',
- 'dotted',
- 'dashed',
- 'solid',
- 'double',
- 'groove',
- 'ridge',
- 'inset',
- 'outset'
- ),
- false
- );
-
- $this->info['border-style'] = new HTMLPurifier_AttrDef_CSS_Multiple($border_style);
-
- $this->info['clear'] = new HTMLPurifier_AttrDef_Enum(
- array('none', 'left', 'right', 'both'),
- false
- );
- $this->info['float'] = new HTMLPurifier_AttrDef_Enum(
- array('none', 'left', 'right'),
- false
- );
- $this->info['font-style'] = new HTMLPurifier_AttrDef_Enum(
- array('normal', 'italic', 'oblique'),
- false
- );
- $this->info['font-variant'] = new HTMLPurifier_AttrDef_Enum(
- array('normal', 'small-caps'),
- false
- );
-
- $uri_or_none = new HTMLPurifier_AttrDef_CSS_Composite(
- array(
- new HTMLPurifier_AttrDef_Enum(array('none')),
- new HTMLPurifier_AttrDef_CSS_URI()
- )
- );
-
- $this->info['list-style-position'] = new HTMLPurifier_AttrDef_Enum(
- array('inside', 'outside'),
- false
- );
- $this->info['list-style-type'] = new HTMLPurifier_AttrDef_Enum(
- array(
- 'disc',
- 'circle',
- 'square',
- 'decimal',
- 'lower-roman',
- 'upper-roman',
- 'lower-alpha',
- 'upper-alpha',
- 'none'
- ),
- false
- );
- $this->info['list-style-image'] = $uri_or_none;
-
- $this->info['list-style'] = new HTMLPurifier_AttrDef_CSS_ListStyle($config);
-
- $this->info['text-transform'] = new HTMLPurifier_AttrDef_Enum(
- array('capitalize', 'uppercase', 'lowercase', 'none'),
- false
- );
- $this->info['color'] = new HTMLPurifier_AttrDef_CSS_Color();
-
- $this->info['background-image'] = $uri_or_none;
- $this->info['background-repeat'] = new HTMLPurifier_AttrDef_Enum(
- array('repeat', 'repeat-x', 'repeat-y', 'no-repeat')
- );
- $this->info['background-attachment'] = new HTMLPurifier_AttrDef_Enum(
- array('scroll', 'fixed')
- );
- $this->info['background-position'] = new HTMLPurifier_AttrDef_CSS_BackgroundPosition();
-
- $border_color =
- $this->info['border-top-color'] =
- $this->info['border-bottom-color'] =
- $this->info['border-left-color'] =
- $this->info['border-right-color'] =
- $this->info['background-color'] = new HTMLPurifier_AttrDef_CSS_Composite(
- array(
- new HTMLPurifier_AttrDef_Enum(array('transparent')),
- new HTMLPurifier_AttrDef_CSS_Color()
- )
- );
-
- $this->info['background'] = new HTMLPurifier_AttrDef_CSS_Background($config);
-
- $this->info['border-color'] = new HTMLPurifier_AttrDef_CSS_Multiple($border_color);
-
- $border_width =
- $this->info['border-top-width'] =
- $this->info['border-bottom-width'] =
- $this->info['border-left-width'] =
- $this->info['border-right-width'] = new HTMLPurifier_AttrDef_CSS_Composite(
- array(
- new HTMLPurifier_AttrDef_Enum(array('thin', 'medium', 'thick')),
- new HTMLPurifier_AttrDef_CSS_Length('0') //disallow negative
- )
- );
-
- $this->info['border-width'] = new HTMLPurifier_AttrDef_CSS_Multiple($border_width);
-
- $this->info['letter-spacing'] = new HTMLPurifier_AttrDef_CSS_Composite(
- array(
- new HTMLPurifier_AttrDef_Enum(array('normal')),
- new HTMLPurifier_AttrDef_CSS_Length()
- )
- );
-
- $this->info['word-spacing'] = new HTMLPurifier_AttrDef_CSS_Composite(
- array(
- new HTMLPurifier_AttrDef_Enum(array('normal')),
- new HTMLPurifier_AttrDef_CSS_Length()
- )
- );
-
- $this->info['font-size'] = new HTMLPurifier_AttrDef_CSS_Composite(
- array(
- new HTMLPurifier_AttrDef_Enum(
- array(
- 'xx-small',
- 'x-small',
- 'small',
- 'medium',
- 'large',
- 'x-large',
- 'xx-large',
- 'larger',
- 'smaller'
- )
- ),
- new HTMLPurifier_AttrDef_CSS_Percentage(),
- new HTMLPurifier_AttrDef_CSS_Length()
- )
- );
-
- $this->info['line-height'] = new HTMLPurifier_AttrDef_CSS_Composite(
- array(
- new HTMLPurifier_AttrDef_Enum(array('normal')),
- new HTMLPurifier_AttrDef_CSS_Number(true), // no negatives
- new HTMLPurifier_AttrDef_CSS_Length('0'),
- new HTMLPurifier_AttrDef_CSS_Percentage(true)
- )
- );
-
- $margin =
- $this->info['margin-top'] =
- $this->info['margin-bottom'] =
- $this->info['margin-left'] =
- $this->info['margin-right'] = new HTMLPurifier_AttrDef_CSS_Composite(
- array(
- new HTMLPurifier_AttrDef_CSS_Length(),
- new HTMLPurifier_AttrDef_CSS_Percentage(),
- new HTMLPurifier_AttrDef_Enum(array('auto'))
- )
- );
-
- $this->info['margin'] = new HTMLPurifier_AttrDef_CSS_Multiple($margin);
-
- // non-negative
- $padding =
- $this->info['padding-top'] =
- $this->info['padding-bottom'] =
- $this->info['padding-left'] =
- $this->info['padding-right'] = new HTMLPurifier_AttrDef_CSS_Composite(
- array(
- new HTMLPurifier_AttrDef_CSS_Length('0'),
- new HTMLPurifier_AttrDef_CSS_Percentage(true)
- )
- );
-
- $this->info['padding'] = new HTMLPurifier_AttrDef_CSS_Multiple($padding);
-
- $this->info['text-indent'] = new HTMLPurifier_AttrDef_CSS_Composite(
- array(
- new HTMLPurifier_AttrDef_CSS_Length(),
- new HTMLPurifier_AttrDef_CSS_Percentage()
- )
- );
-
- $trusted_wh = new HTMLPurifier_AttrDef_CSS_Composite(
- array(
- new HTMLPurifier_AttrDef_CSS_Length('0'),
- new HTMLPurifier_AttrDef_CSS_Percentage(true),
- new HTMLPurifier_AttrDef_Enum(array('auto'))
- )
- );
- $max = $config->get('CSS.MaxImgLength');
-
- $this->info['width'] =
- $this->info['height'] =
- $max === null ?
- $trusted_wh :
- new HTMLPurifier_AttrDef_Switch(
- 'img',
- // For img tags:
- new HTMLPurifier_AttrDef_CSS_Composite(
- array(
- new HTMLPurifier_AttrDef_CSS_Length('0', $max),
- new HTMLPurifier_AttrDef_Enum(array('auto'))
- )
- ),
- // For everyone else:
- $trusted_wh
- );
-
- $this->info['text-decoration'] = new HTMLPurifier_AttrDef_CSS_TextDecoration();
-
- $this->info['font-family'] = new HTMLPurifier_AttrDef_CSS_FontFamily();
-
- // this could use specialized code
- $this->info['font-weight'] = new HTMLPurifier_AttrDef_Enum(
- array(
- 'normal',
- 'bold',
- 'bolder',
- 'lighter',
- '100',
- '200',
- '300',
- '400',
- '500',
- '600',
- '700',
- '800',
- '900'
- ),
- false
- );
-
- // MUST be called after other font properties, as it references
- // a CSSDefinition object
- $this->info['font'] = new HTMLPurifier_AttrDef_CSS_Font($config);
-
- // same here
- $this->info['border'] =
- $this->info['border-bottom'] =
- $this->info['border-top'] =
- $this->info['border-left'] =
- $this->info['border-right'] = new HTMLPurifier_AttrDef_CSS_Border($config);
-
- $this->info['border-collapse'] = new HTMLPurifier_AttrDef_Enum(
- array('collapse', 'separate')
- );
-
- $this->info['caption-side'] = new HTMLPurifier_AttrDef_Enum(
- array('top', 'bottom')
- );
-
- $this->info['table-layout'] = new HTMLPurifier_AttrDef_Enum(
- array('auto', 'fixed')
- );
-
- $this->info['vertical-align'] = new HTMLPurifier_AttrDef_CSS_Composite(
- array(
- new HTMLPurifier_AttrDef_Enum(
- array(
- 'baseline',
- 'sub',
- 'super',
- 'top',
- 'text-top',
- 'middle',
- 'bottom',
- 'text-bottom'
- )
- ),
- new HTMLPurifier_AttrDef_CSS_Length(),
- new HTMLPurifier_AttrDef_CSS_Percentage()
- )
- );
-
- $this->info['border-spacing'] = new HTMLPurifier_AttrDef_CSS_Multiple(new HTMLPurifier_AttrDef_CSS_Length(), 2);
-
- // These CSS properties don't work on many browsers, but we live
- // in THE FUTURE!
- $this->info['white-space'] = new HTMLPurifier_AttrDef_Enum(
- array('nowrap', 'normal', 'pre', 'pre-wrap', 'pre-line')
- );
-
- if ($config->get('CSS.Proprietary')) {
- $this->doSetupProprietary($config);
- }
-
- if ($config->get('CSS.AllowTricky')) {
- $this->doSetupTricky($config);
- }
-
- if ($config->get('CSS.Trusted')) {
- $this->doSetupTrusted($config);
- }
-
- $allow_important = $config->get('CSS.AllowImportant');
- // wrap all attr-defs with decorator that handles !important
- foreach ($this->info as $k => $v) {
- $this->info[$k] = new HTMLPurifier_AttrDef_CSS_ImportantDecorator($v, $allow_important);
- }
-
- $this->setupConfigStuff($config);
- }
-
- /**
- * @param HTMLPurifier_Config $config
- */
- protected function doSetupProprietary($config)
- {
- // Internet Explorer only scrollbar colors
- $this->info['scrollbar-arrow-color'] = new HTMLPurifier_AttrDef_CSS_Color();
- $this->info['scrollbar-base-color'] = new HTMLPurifier_AttrDef_CSS_Color();
- $this->info['scrollbar-darkshadow-color'] = new HTMLPurifier_AttrDef_CSS_Color();
- $this->info['scrollbar-face-color'] = new HTMLPurifier_AttrDef_CSS_Color();
- $this->info['scrollbar-highlight-color'] = new HTMLPurifier_AttrDef_CSS_Color();
- $this->info['scrollbar-shadow-color'] = new HTMLPurifier_AttrDef_CSS_Color();
-
- // technically not proprietary, but CSS3, and no one supports it
- $this->info['opacity'] = new HTMLPurifier_AttrDef_CSS_AlphaValue();
- $this->info['-moz-opacity'] = new HTMLPurifier_AttrDef_CSS_AlphaValue();
- $this->info['-khtml-opacity'] = new HTMLPurifier_AttrDef_CSS_AlphaValue();
-
- // only opacity, for now
- $this->info['filter'] = new HTMLPurifier_AttrDef_CSS_Filter();
-
- // more CSS3
- $this->info['page-break-after'] =
- $this->info['page-break-before'] = new HTMLPurifier_AttrDef_Enum(
- array(
- 'auto',
- 'always',
- 'avoid',
- 'left',
- 'right'
- )
- );
- $this->info['page-break-inside'] = new HTMLPurifier_AttrDef_Enum(array('auto', 'avoid'));
-
- }
-
- /**
- * @param HTMLPurifier_Config $config
- */
- protected function doSetupTricky($config)
- {
- $this->info['display'] = new HTMLPurifier_AttrDef_Enum(
- array(
- 'inline',
- 'block',
- 'list-item',
- 'run-in',
- 'compact',
- 'marker',
- 'table',
- 'inline-block',
- 'inline-table',
- 'table-row-group',
- 'table-header-group',
- 'table-footer-group',
- 'table-row',
- 'table-column-group',
- 'table-column',
- 'table-cell',
- 'table-caption',
- 'none'
- )
- );
- $this->info['visibility'] = new HTMLPurifier_AttrDef_Enum(
- array('visible', 'hidden', 'collapse')
- );
- $this->info['overflow'] = new HTMLPurifier_AttrDef_Enum(array('visible', 'hidden', 'auto', 'scroll'));
- }
-
- /**
- * @param HTMLPurifier_Config $config
- */
- protected function doSetupTrusted($config)
- {
- $this->info['position'] = new HTMLPurifier_AttrDef_Enum(
- array('static', 'relative', 'absolute', 'fixed')
- );
- $this->info['top'] =
- $this->info['left'] =
- $this->info['right'] =
- $this->info['bottom'] = new HTMLPurifier_AttrDef_CSS_Composite(
- array(
- new HTMLPurifier_AttrDef_CSS_Length(),
- new HTMLPurifier_AttrDef_CSS_Percentage(),
- new HTMLPurifier_AttrDef_Enum(array('auto')),
- )
- );
- $this->info['z-index'] = new HTMLPurifier_AttrDef_CSS_Composite(
- array(
- new HTMLPurifier_AttrDef_Integer(),
- new HTMLPurifier_AttrDef_Enum(array('auto')),
- )
- );
- }
-
- /**
- * Performs extra config-based processing. Based off of
- * HTMLPurifier_HTMLDefinition.
- * @param HTMLPurifier_Config $config
- * @todo Refactor duplicate elements into common class (probably using
- * composition, not inheritance).
- */
- protected function setupConfigStuff($config)
- {
- // setup allowed elements
- $support = "(for information on implementing this, see the " .
- "support forums) ";
- $allowed_properties = $config->get('CSS.AllowedProperties');
- if ($allowed_properties !== null) {
- foreach ($this->info as $name => $d) {
- if (!isset($allowed_properties[$name])) {
- unset($this->info[$name]);
- }
- unset($allowed_properties[$name]);
- }
- // emit errors
- foreach ($allowed_properties as $name => $d) {
- // :TODO: Is this htmlspecialchars() call really necessary?
- $name = htmlspecialchars($name);
- trigger_error("Style attribute '$name' is not supported $support", E_USER_WARNING);
- }
- }
-
- $forbidden_properties = $config->get('CSS.ForbiddenProperties');
- if ($forbidden_properties !== null) {
- foreach ($this->info as $name => $d) {
- if (isset($forbidden_properties[$name])) {
- unset($this->info[$name]);
- }
- }
- }
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/ChildDef/List.php b/library/HTMLPurifier/ChildDef/List.php
deleted file mode 100644
index 891b9f6f5..000000000
--- a/library/HTMLPurifier/ChildDef/List.php
+++ /dev/null
@@ -1,86 +0,0 @@
-<?php
-
-/**
- * Definition for list containers ul and ol.
- *
- * What does this do? The big thing is to handle ol/ul at the top
- * level of list nodes, which should be handled specially by /folding/
- * them into the previous list node. We generally shouldn't ever
- * see other disallowed elements, because the autoclose behavior
- * in MakeWellFormed handles it.
- */
-class HTMLPurifier_ChildDef_List extends HTMLPurifier_ChildDef
-{
- /**
- * @type string
- */
- public $type = 'list';
- /**
- * @type array
- */
- // lying a little bit, so that we can handle ul and ol ourselves
- // XXX: This whole business with 'wrap' is all a bit unsatisfactory
- public $elements = array('li' => true, 'ul' => true, 'ol' => true);
-
- /**
- * @param array $children
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return array
- */
- public function validateChildren($children, $config, $context)
- {
- // Flag for subclasses
- $this->whitespace = false;
-
- // if there are no tokens, delete parent node
- if (empty($children)) {
- return false;
- }
-
- // the new set of children
- $result = array();
-
- // a little sanity check to make sure it's not ALL whitespace
- $all_whitespace = true;
-
- $current_li = false;
-
- foreach ($children as $node) {
- if (!empty($node->is_whitespace)) {
- $result[] = $node;
- continue;
- }
- $all_whitespace = false; // phew, we're not talking about whitespace
-
- if ($node->name === 'li') {
- // good
- $current_li = $node;
- $result[] = $node;
- } else {
- // we want to tuck this into the previous li
- // Invariant: we expect the node to be ol/ul
- // ToDo: Make this more robust in the case of not ol/ul
- // by distinguishing between existing li and li created
- // to handle non-list elements; non-list elements should
- // not be appended to an existing li; only li created
- // for non-list. This distinction is not currently made.
- if ($current_li === false) {
- $current_li = new HTMLPurifier_Node_Element('li');
- $result[] = $current_li;
- }
- $current_li->children[] = $node;
- $current_li->empty = false; // XXX fascinating! Check for this error elsewhere ToDo
- }
- }
- if (empty($result)) {
- return false;
- }
- if ($all_whitespace) {
- return false;
- }
- return $result;
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/ChildDef/Table.php b/library/HTMLPurifier/ChildDef/Table.php
deleted file mode 100644
index 3e4a0f218..000000000
--- a/library/HTMLPurifier/ChildDef/Table.php
+++ /dev/null
@@ -1,224 +0,0 @@
-<?php
-
-/**
- * Definition for tables. The general idea is to extract out all of the
- * essential bits, and then reconstruct it later.
- *
- * This is a bit confusing, because the DTDs and the W3C
- * validators seem to disagree on the appropriate definition. The
- * DTD claims:
- *
- * (CAPTION?, (COL*|COLGROUP*), THEAD?, TFOOT?, TBODY+)
- *
- * But actually, the HTML4 spec then has this to say:
- *
- * The TBODY start tag is always required except when the table
- * contains only one table body and no table head or foot sections.
- * The TBODY end tag may always be safely omitted.
- *
- * So the DTD is kind of wrong. The validator is, unfortunately, kind
- * of on crack.
- *
- * The definition changed again in XHTML1.1; and in my opinion, this
- * formulation makes the most sense.
- *
- * caption?, ( col* | colgroup* ), (( thead?, tfoot?, tbody+ ) | ( tr+ ))
- *
- * Essentially, we have two modes: thead/tfoot/tbody mode, and tr mode.
- * If we encounter a thead, tfoot or tbody, we are placed in the former
- * mode, and we *must* wrap any stray tr segments with a tbody. But if
- * we don't run into any of them, just have tr tags is OK.
- */
-class HTMLPurifier_ChildDef_Table extends HTMLPurifier_ChildDef
-{
- /**
- * @type bool
- */
- public $allow_empty = false;
-
- /**
- * @type string
- */
- public $type = 'table';
-
- /**
- * @type array
- */
- public $elements = array(
- 'tr' => true,
- 'tbody' => true,
- 'thead' => true,
- 'tfoot' => true,
- 'caption' => true,
- 'colgroup' => true,
- 'col' => true
- );
-
- public function __construct()
- {
- }
-
- /**
- * @param array $children
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return array
- */
- public function validateChildren($children, $config, $context)
- {
- if (empty($children)) {
- return false;
- }
-
- // only one of these elements is allowed in a table
- $caption = false;
- $thead = false;
- $tfoot = false;
-
- // whitespace
- $initial_ws = array();
- $after_caption_ws = array();
- $after_thead_ws = array();
- $after_tfoot_ws = array();
-
- // as many of these as you want
- $cols = array();
- $content = array();
-
- $tbody_mode = false; // if true, then we need to wrap any stray
- // <tr>s with a <tbody>.
-
- $ws_accum =& $initial_ws;
-
- foreach ($children as $node) {
- if ($node instanceof HTMLPurifier_Node_Comment) {
- $ws_accum[] = $node;
- continue;
- }
- switch ($node->name) {
- case 'tbody':
- $tbody_mode = true;
- // fall through
- case 'tr':
- $content[] = $node;
- $ws_accum =& $content;
- break;
- case 'caption':
- // there can only be one caption!
- if ($caption !== false) break;
- $caption = $node;
- $ws_accum =& $after_caption_ws;
- break;
- case 'thead':
- $tbody_mode = true;
- // XXX This breaks rendering properties with
- // Firefox, which never floats a <thead> to
- // the top. Ever. (Our scheme will float the
- // first <thead> to the top.) So maybe
- // <thead>s that are not first should be
- // turned into <tbody>? Very tricky, indeed.
- if ($thead === false) {
- $thead = $node;
- $ws_accum =& $after_thead_ws;
- } else {
- // Oops, there's a second one! What
- // should we do? Current behavior is to
- // transmutate the first and last entries into
- // tbody tags, and then put into content.
- // Maybe a better idea is to *attach
- // it* to the existing thead or tfoot?
- // We don't do this, because Firefox
- // doesn't float an extra tfoot to the
- // bottom like it does for the first one.
- $node->name = 'tbody';
- $content[] = $node;
- $ws_accum =& $content;
- }
- break;
- case 'tfoot':
- // see above for some aveats
- $tbody_mode = true;
- if ($tfoot === false) {
- $tfoot = $node;
- $ws_accum =& $after_tfoot_ws;
- } else {
- $node->name = 'tbody';
- $content[] = $node;
- $ws_accum =& $content;
- }
- break;
- case 'colgroup':
- case 'col':
- $cols[] = $node;
- $ws_accum =& $cols;
- break;
- case '#PCDATA':
- // How is whitespace handled? We treat is as sticky to
- // the *end* of the previous element. So all of the
- // nonsense we have worked on is to keep things
- // together.
- if (!empty($node->is_whitespace)) {
- $ws_accum[] = $node;
- }
- break;
- }
- }
-
- if (empty($content)) {
- return false;
- }
-
- $ret = $initial_ws;
- if ($caption !== false) {
- $ret[] = $caption;
- $ret = array_merge($ret, $after_caption_ws);
- }
- if ($cols !== false) {
- $ret = array_merge($ret, $cols);
- }
- if ($thead !== false) {
- $ret[] = $thead;
- $ret = array_merge($ret, $after_thead_ws);
- }
- if ($tfoot !== false) {
- $ret[] = $tfoot;
- $ret = array_merge($ret, $after_tfoot_ws);
- }
-
- if ($tbody_mode) {
- // we have to shuffle tr into tbody
- $current_tr_tbody = null;
-
- foreach($content as $node) {
- switch ($node->name) {
- case 'tbody':
- $current_tr_tbody = null;
- $ret[] = $node;
- break;
- case 'tr':
- if ($current_tr_tbody === null) {
- $current_tr_tbody = new HTMLPurifier_Node_Element('tbody');
- $ret[] = $current_tr_tbody;
- }
- $current_tr_tbody->children[] = $node;
- break;
- case '#PCDATA':
- assert($node->is_whitespace);
- if ($current_tr_tbody === null) {
- $ret[] = $node;
- } else {
- $current_tr_tbody->children[] = $node;
- }
- break;
- }
- }
- } else {
- $ret = array_merge($ret, $content);
- }
-
- return $ret;
-
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/Config.php b/library/HTMLPurifier/Config.php
deleted file mode 100644
index 7ada59b94..000000000
--- a/library/HTMLPurifier/Config.php
+++ /dev/null
@@ -1,911 +0,0 @@
-<?php
-
-/**
- * Configuration object that triggers customizable behavior.
- *
- * @warning This class is strongly defined: that means that the class
- * will fail if an undefined directive is retrieved or set.
- *
- * @note Many classes that could (although many times don't) use the
- * configuration object make it a mandatory parameter. This is
- * because a configuration object should always be forwarded,
- * otherwise, you run the risk of missing a parameter and then
- * being stumped when a configuration directive doesn't work.
- *
- * @todo Reconsider some of the public member variables
- */
-class HTMLPurifier_Config
-{
-
- /**
- * HTML Purifier's version
- * @type string
- */
- public $version = '4.6.0';
-
- /**
- * Whether or not to automatically finalize
- * the object if a read operation is done.
- * @type bool
- */
- public $autoFinalize = true;
-
- // protected member variables
-
- /**
- * Namespace indexed array of serials for specific namespaces.
- * @see getSerial() for more info.
- * @type string[]
- */
- protected $serials = array();
-
- /**
- * Serial for entire configuration object.
- * @type string
- */
- protected $serial;
-
- /**
- * Parser for variables.
- * @type HTMLPurifier_VarParser_Flexible
- */
- protected $parser = null;
-
- /**
- * Reference HTMLPurifier_ConfigSchema for value checking.
- * @type HTMLPurifier_ConfigSchema
- * @note This is public for introspective purposes. Please don't
- * abuse!
- */
- public $def;
-
- /**
- * Indexed array of definitions.
- * @type HTMLPurifier_Definition[]
- */
- protected $definitions;
-
- /**
- * Whether or not config is finalized.
- * @type bool
- */
- protected $finalized = false;
-
- /**
- * Property list containing configuration directives.
- * @type array
- */
- protected $plist;
-
- /**
- * Whether or not a set is taking place due to an alias lookup.
- * @type bool
- */
- private $aliasMode;
-
- /**
- * Set to false if you do not want line and file numbers in errors.
- * (useful when unit testing). This will also compress some errors
- * and exceptions.
- * @type bool
- */
- public $chatty = true;
-
- /**
- * Current lock; only gets to this namespace are allowed.
- * @type string
- */
- private $lock;
-
- /**
- * Constructor
- * @param HTMLPurifier_ConfigSchema $definition ConfigSchema that defines
- * what directives are allowed.
- * @param HTMLPurifier_PropertyList $parent
- */
- public function __construct($definition, $parent = null)
- {
- $parent = $parent ? $parent : $definition->defaultPlist;
- $this->plist = new HTMLPurifier_PropertyList($parent);
- $this->def = $definition; // keep a copy around for checking
- $this->parser = new HTMLPurifier_VarParser_Flexible();
- }
-
- /**
- * Convenience constructor that creates a config object based on a mixed var
- * @param mixed $config Variable that defines the state of the config
- * object. Can be: a HTMLPurifier_Config() object,
- * an array of directives based on loadArray(),
- * or a string filename of an ini file.
- * @param HTMLPurifier_ConfigSchema $schema Schema object
- * @return HTMLPurifier_Config Configured object
- */
- public static function create($config, $schema = null)
- {
- if ($config instanceof HTMLPurifier_Config) {
- // pass-through
- return $config;
- }
- if (!$schema) {
- $ret = HTMLPurifier_Config::createDefault();
- } else {
- $ret = new HTMLPurifier_Config($schema);
- }
- if (is_string($config)) {
- $ret->loadIni($config);
- } elseif (is_array($config)) $ret->loadArray($config);
- return $ret;
- }
-
- /**
- * Creates a new config object that inherits from a previous one.
- * @param HTMLPurifier_Config $config Configuration object to inherit from.
- * @return HTMLPurifier_Config object with $config as its parent.
- */
- public static function inherit(HTMLPurifier_Config $config)
- {
- return new HTMLPurifier_Config($config->def, $config->plist);
- }
-
- /**
- * Convenience constructor that creates a default configuration object.
- * @return HTMLPurifier_Config default object.
- */
- public static function createDefault()
- {
- $definition = HTMLPurifier_ConfigSchema::instance();
- $config = new HTMLPurifier_Config($definition);
- return $config;
- }
-
- /**
- * Retrieves a value from the configuration.
- *
- * @param string $key String key
- * @param mixed $a
- *
- * @return mixed
- */
- public function get($key, $a = null)
- {
- if ($a !== null) {
- $this->triggerError(
- "Using deprecated API: use \$config->get('$key.$a') instead",
- E_USER_WARNING
- );
- $key = "$key.$a";
- }
- if (!$this->finalized) {
- $this->autoFinalize();
- }
- if (!isset($this->def->info[$key])) {
- // can't add % due to SimpleTest bug
- $this->triggerError(
- 'Cannot retrieve value of undefined directive ' . htmlspecialchars($key),
- E_USER_WARNING
- );
- return;
- }
- if (isset($this->def->info[$key]->isAlias)) {
- $d = $this->def->info[$key];
- $this->triggerError(
- 'Cannot get value from aliased directive, use real name ' . $d->key,
- E_USER_ERROR
- );
- return;
- }
- if ($this->lock) {
- list($ns) = explode('.', $key);
- if ($ns !== $this->lock) {
- $this->triggerError(
- 'Cannot get value of namespace ' . $ns . ' when lock for ' .
- $this->lock .
- ' is active, this probably indicates a Definition setup method ' .
- 'is accessing directives that are not within its namespace',
- E_USER_ERROR
- );
- return;
- }
- }
- return $this->plist->get($key);
- }
-
- /**
- * Retrieves an array of directives to values from a given namespace
- *
- * @param string $namespace String namespace
- *
- * @return array
- */
- public function getBatch($namespace)
- {
- if (!$this->finalized) {
- $this->autoFinalize();
- }
- $full = $this->getAll();
- if (!isset($full[$namespace])) {
- $this->triggerError(
- 'Cannot retrieve undefined namespace ' .
- htmlspecialchars($namespace),
- E_USER_WARNING
- );
- return;
- }
- return $full[$namespace];
- }
-
- /**
- * Returns a SHA-1 signature of a segment of the configuration object
- * that uniquely identifies that particular configuration
- *
- * @param string $namespace Namespace to get serial for
- *
- * @return string
- * @note Revision is handled specially and is removed from the batch
- * before processing!
- */
- public function getBatchSerial($namespace)
- {
- if (empty($this->serials[$namespace])) {
- $batch = $this->getBatch($namespace);
- unset($batch['DefinitionRev']);
- $this->serials[$namespace] = sha1(serialize($batch));
- }
- return $this->serials[$namespace];
- }
-
- /**
- * Returns a SHA-1 signature for the entire configuration object
- * that uniquely identifies that particular configuration
- *
- * @return string
- */
- public function getSerial()
- {
- if (empty($this->serial)) {
- $this->serial = sha1(serialize($this->getAll()));
- }
- return $this->serial;
- }
-
- /**
- * Retrieves all directives, organized by namespace
- *
- * @warning This is a pretty inefficient function, avoid if you can
- */
- public function getAll()
- {
- if (!$this->finalized) {
- $this->autoFinalize();
- }
- $ret = array();
- foreach ($this->plist->squash() as $name => $value) {
- list($ns, $key) = explode('.', $name, 2);
- $ret[$ns][$key] = $value;
- }
- return $ret;
- }
-
- /**
- * Sets a value to configuration.
- *
- * @param string $key key
- * @param mixed $value value
- * @param mixed $a
- */
- public function set($key, $value, $a = null)
- {
- if (strpos($key, '.') === false) {
- $namespace = $key;
- $directive = $value;
- $value = $a;
- $key = "$key.$directive";
- $this->triggerError("Using deprecated API: use \$config->set('$key', ...) instead", E_USER_NOTICE);
- } else {
- list($namespace) = explode('.', $key);
- }
- if ($this->isFinalized('Cannot set directive after finalization')) {
- return;
- }
- if (!isset($this->def->info[$key])) {
- $this->triggerError(
- 'Cannot set undefined directive ' . htmlspecialchars($key) . ' to value',
- E_USER_WARNING
- );
- return;
- }
- $def = $this->def->info[$key];
-
- if (isset($def->isAlias)) {
- if ($this->aliasMode) {
- $this->triggerError(
- 'Double-aliases not allowed, please fix '.
- 'ConfigSchema bug with' . $key,
- E_USER_ERROR
- );
- return;
- }
- $this->aliasMode = true;
- $this->set($def->key, $value);
- $this->aliasMode = false;
- $this->triggerError("$key is an alias, preferred directive name is {$def->key}", E_USER_NOTICE);
- return;
- }
-
- // Raw type might be negative when using the fully optimized form
- // of stdclass, which indicates allow_null == true
- $rtype = is_int($def) ? $def : $def->type;
- if ($rtype < 0) {
- $type = -$rtype;
- $allow_null = true;
- } else {
- $type = $rtype;
- $allow_null = isset($def->allow_null);
- }
-
- try {
- $value = $this->parser->parse($value, $type, $allow_null);
- } catch (HTMLPurifier_VarParserException $e) {
- $this->triggerError(
- 'Value for ' . $key . ' is of invalid type, should be ' .
- HTMLPurifier_VarParser::getTypeName($type),
- E_USER_WARNING
- );
- return;
- }
- if (is_string($value) && is_object($def)) {
- // resolve value alias if defined
- if (isset($def->aliases[$value])) {
- $value = $def->aliases[$value];
- }
- // check to see if the value is allowed
- if (isset($def->allowed) && !isset($def->allowed[$value])) {
- $this->triggerError(
- 'Value not supported, valid values are: ' .
- $this->_listify($def->allowed),
- E_USER_WARNING
- );
- return;
- }
- }
- $this->plist->set($key, $value);
-
- // reset definitions if the directives they depend on changed
- // this is a very costly process, so it's discouraged
- // with finalization
- if ($namespace == 'HTML' || $namespace == 'CSS' || $namespace == 'URI') {
- $this->definitions[$namespace] = null;
- }
-
- $this->serials[$namespace] = false;
- }
-
- /**
- * Convenience function for error reporting
- *
- * @param array $lookup
- *
- * @return string
- */
- private function _listify($lookup)
- {
- $list = array();
- foreach ($lookup as $name => $b) {
- $list[] = $name;
- }
- return implode(', ', $list);
- }
-
- /**
- * Retrieves object reference to the HTML definition.
- *
- * @param bool $raw Return a copy that has not been setup yet. Must be
- * called before it's been setup, otherwise won't work.
- * @param bool $optimized If true, this method may return null, to
- * indicate that a cached version of the modified
- * definition object is available and no further edits
- * are necessary. Consider using
- * maybeGetRawHTMLDefinition, which is more explicitly
- * named, instead.
- *
- * @return HTMLPurifier_HTMLDefinition
- */
- public function getHTMLDefinition($raw = false, $optimized = false)
- {
- return $this->getDefinition('HTML', $raw, $optimized);
- }
-
- /**
- * Retrieves object reference to the CSS definition
- *
- * @param bool $raw Return a copy that has not been setup yet. Must be
- * called before it's been setup, otherwise won't work.
- * @param bool $optimized If true, this method may return null, to
- * indicate that a cached version of the modified
- * definition object is available and no further edits
- * are necessary. Consider using
- * maybeGetRawCSSDefinition, which is more explicitly
- * named, instead.
- *
- * @return HTMLPurifier_CSSDefinition
- */
- public function getCSSDefinition($raw = false, $optimized = false)
- {
- return $this->getDefinition('CSS', $raw, $optimized);
- }
-
- /**
- * Retrieves object reference to the URI definition
- *
- * @param bool $raw Return a copy that has not been setup yet. Must be
- * called before it's been setup, otherwise won't work.
- * @param bool $optimized If true, this method may return null, to
- * indicate that a cached version of the modified
- * definition object is available and no further edits
- * are necessary. Consider using
- * maybeGetRawURIDefinition, which is more explicitly
- * named, instead.
- *
- * @return HTMLPurifier_URIDefinition
- */
- public function getURIDefinition($raw = false, $optimized = false)
- {
- return $this->getDefinition('URI', $raw, $optimized);
- }
-
- /**
- * Retrieves a definition
- *
- * @param string $type Type of definition: HTML, CSS, etc
- * @param bool $raw Whether or not definition should be returned raw
- * @param bool $optimized Only has an effect when $raw is true. Whether
- * or not to return null if the result is already present in
- * the cache. This is off by default for backwards
- * compatibility reasons, but you need to do things this
- * way in order to ensure that caching is done properly.
- * Check out enduser-customize.html for more details.
- * We probably won't ever change this default, as much as the
- * maybe semantics is the "right thing to do."
- *
- * @throws HTMLPurifier_Exception
- * @return HTMLPurifier_Definition
- */
- public function getDefinition($type, $raw = false, $optimized = false)
- {
- if ($optimized && !$raw) {
- throw new HTMLPurifier_Exception("Cannot set optimized = true when raw = false");
- }
- if (!$this->finalized) {
- $this->autoFinalize();
- }
- // temporarily suspend locks, so we can handle recursive definition calls
- $lock = $this->lock;
- $this->lock = null;
- $factory = HTMLPurifier_DefinitionCacheFactory::instance();
- $cache = $factory->create($type, $this);
- $this->lock = $lock;
- if (!$raw) {
- // full definition
- // ---------------
- // check if definition is in memory
- if (!empty($this->definitions[$type])) {
- $def = $this->definitions[$type];
- // check if the definition is setup
- if ($def->setup) {
- return $def;
- } else {
- $def->setup($this);
- if ($def->optimized) {
- $cache->add($def, $this);
- }
- return $def;
- }
- }
- // check if definition is in cache
- $def = $cache->get($this);
- if ($def) {
- // definition in cache, save to memory and return it
- $this->definitions[$type] = $def;
- return $def;
- }
- // initialize it
- $def = $this->initDefinition($type);
- // set it up
- $this->lock = $type;
- $def->setup($this);
- $this->lock = null;
- // save in cache
- $cache->add($def, $this);
- // return it
- return $def;
- } else {
- // raw definition
- // --------------
- // check preconditions
- $def = null;
- if ($optimized) {
- if (is_null($this->get($type . '.DefinitionID'))) {
- // fatally error out if definition ID not set
- throw new HTMLPurifier_Exception(
- "Cannot retrieve raw version without specifying %$type.DefinitionID"
- );
- }
- }
- if (!empty($this->definitions[$type])) {
- $def = $this->definitions[$type];
- if ($def->setup && !$optimized) {
- $extra = $this->chatty ?
- " (try moving this code block earlier in your initialization)" :
- "";
- throw new HTMLPurifier_Exception(
- "Cannot retrieve raw definition after it has already been setup" .
- $extra
- );
- }
- if ($def->optimized === null) {
- $extra = $this->chatty ? " (try flushing your cache)" : "";
- throw new HTMLPurifier_Exception(
- "Optimization status of definition is unknown" . $extra
- );
- }
- if ($def->optimized !== $optimized) {
- $msg = $optimized ? "optimized" : "unoptimized";
- $extra = $this->chatty ?
- " (this backtrace is for the first inconsistent call, which was for a $msg raw definition)"
- : "";
- throw new HTMLPurifier_Exception(
- "Inconsistent use of optimized and unoptimized raw definition retrievals" . $extra
- );
- }
- }
- // check if definition was in memory
- if ($def) {
- if ($def->setup) {
- // invariant: $optimized === true (checked above)
- return null;
- } else {
- return $def;
- }
- }
- // if optimized, check if definition was in cache
- // (because we do the memory check first, this formulation
- // is prone to cache slamming, but I think
- // guaranteeing that either /all/ of the raw
- // setup code or /none/ of it is run is more important.)
- if ($optimized) {
- // This code path only gets run once; once we put
- // something in $definitions (which is guaranteed by the
- // trailing code), we always short-circuit above.
- $def = $cache->get($this);
- if ($def) {
- // save the full definition for later, but don't
- // return it yet
- $this->definitions[$type] = $def;
- return null;
- }
- }
- // check invariants for creation
- if (!$optimized) {
- if (!is_null($this->get($type . '.DefinitionID'))) {
- if ($this->chatty) {
- $this->triggerError(
- 'Due to a documentation error in previous version of HTML Purifier, your ' .
- 'definitions are not being cached. If this is OK, you can remove the ' .
- '%$type.DefinitionRev and %$type.DefinitionID declaration. Otherwise, ' .
- 'modify your code to use maybeGetRawDefinition, and test if the returned ' .
- 'value is null before making any edits (if it is null, that means that a ' .
- 'cached version is available, and no raw operations are necessary). See ' .
- '<a href="http://htmlpurifier.org/docs/enduser-customize.html#optimized">' .
- 'Customize</a> for more details',
- E_USER_WARNING
- );
- } else {
- $this->triggerError(
- "Useless DefinitionID declaration",
- E_USER_WARNING
- );
- }
- }
- }
- // initialize it
- $def = $this->initDefinition($type);
- $def->optimized = $optimized;
- return $def;
- }
- throw new HTMLPurifier_Exception("The impossible happened!");
- }
-
- /**
- * Initialise definition
- *
- * @param string $type What type of definition to create
- *
- * @return HTMLPurifier_CSSDefinition|HTMLPurifier_HTMLDefinition|HTMLPurifier_URIDefinition
- * @throws HTMLPurifier_Exception
- */
- private function initDefinition($type)
- {
- // quick checks failed, let's create the object
- if ($type == 'HTML') {
- $def = new HTMLPurifier_HTMLDefinition();
- } elseif ($type == 'CSS') {
- $def = new HTMLPurifier_CSSDefinition();
- } elseif ($type == 'URI') {
- $def = new HTMLPurifier_URIDefinition();
- } else {
- throw new HTMLPurifier_Exception(
- "Definition of $type type not supported"
- );
- }
- $this->definitions[$type] = $def;
- return $def;
- }
-
- public function maybeGetRawDefinition($name)
- {
- return $this->getDefinition($name, true, true);
- }
-
- public function maybeGetRawHTMLDefinition()
- {
- return $this->getDefinition('HTML', true, true);
- }
-
- public function maybeGetRawCSSDefinition()
- {
- return $this->getDefinition('CSS', true, true);
- }
-
- public function maybeGetRawURIDefinition()
- {
- return $this->getDefinition('URI', true, true);
- }
-
- /**
- * Loads configuration values from an array with the following structure:
- * Namespace.Directive => Value
- *
- * @param array $config_array Configuration associative array
- */
- public function loadArray($config_array)
- {
- if ($this->isFinalized('Cannot load directives after finalization')) {
- return;
- }
- foreach ($config_array as $key => $value) {
- $key = str_replace('_', '.', $key);
- if (strpos($key, '.') !== false) {
- $this->set($key, $value);
- } else {
- $namespace = $key;
- $namespace_values = $value;
- foreach ($namespace_values as $directive => $value2) {
- $this->set($namespace .'.'. $directive, $value2);
- }
- }
- }
- }
-
- /**
- * Returns a list of array(namespace, directive) for all directives
- * that are allowed in a web-form context as per an allowed
- * namespaces/directives list.
- *
- * @param array $allowed List of allowed namespaces/directives
- * @param HTMLPurifier_ConfigSchema $schema Schema to use, if not global copy
- *
- * @return array
- */
- public static function getAllowedDirectivesForForm($allowed, $schema = null)
- {
- if (!$schema) {
- $schema = HTMLPurifier_ConfigSchema::instance();
- }
- if ($allowed !== true) {
- if (is_string($allowed)) {
- $allowed = array($allowed);
- }
- $allowed_ns = array();
- $allowed_directives = array();
- $blacklisted_directives = array();
- foreach ($allowed as $ns_or_directive) {
- if (strpos($ns_or_directive, '.') !== false) {
- // directive
- if ($ns_or_directive[0] == '-') {
- $blacklisted_directives[substr($ns_or_directive, 1)] = true;
- } else {
- $allowed_directives[$ns_or_directive] = true;
- }
- } else {
- // namespace
- $allowed_ns[$ns_or_directive] = true;
- }
- }
- }
- $ret = array();
- foreach ($schema->info as $key => $def) {
- list($ns, $directive) = explode('.', $key, 2);
- if ($allowed !== true) {
- if (isset($blacklisted_directives["$ns.$directive"])) {
- continue;
- }
- if (!isset($allowed_directives["$ns.$directive"]) && !isset($allowed_ns[$ns])) {
- continue;
- }
- }
- if (isset($def->isAlias)) {
- continue;
- }
- if ($directive == 'DefinitionID' || $directive == 'DefinitionRev') {
- continue;
- }
- $ret[] = array($ns, $directive);
- }
- return $ret;
- }
-
- /**
- * Loads configuration values from $_GET/$_POST that were posted
- * via ConfigForm
- *
- * @param array $array $_GET or $_POST array to import
- * @param string|bool $index Index/name that the config variables are in
- * @param array|bool $allowed List of allowed namespaces/directives
- * @param bool $mq_fix Boolean whether or not to enable magic quotes fix
- * @param HTMLPurifier_ConfigSchema $schema Schema to use, if not global copy
- *
- * @return mixed
- */
- public static function loadArrayFromForm($array, $index = false, $allowed = true, $mq_fix = true, $schema = null)
- {
- $ret = HTMLPurifier_Config::prepareArrayFromForm($array, $index, $allowed, $mq_fix, $schema);
- $config = HTMLPurifier_Config::create($ret, $schema);
- return $config;
- }
-
- /**
- * Merges in configuration values from $_GET/$_POST to object. NOT STATIC.
- *
- * @param array $array $_GET or $_POST array to import
- * @param string|bool $index Index/name that the config variables are in
- * @param array|bool $allowed List of allowed namespaces/directives
- * @param bool $mq_fix Boolean whether or not to enable magic quotes fix
- */
- public function mergeArrayFromForm($array, $index = false, $allowed = true, $mq_fix = true)
- {
- $ret = HTMLPurifier_Config::prepareArrayFromForm($array, $index, $allowed, $mq_fix, $this->def);
- $this->loadArray($ret);
- }
-
- /**
- * Prepares an array from a form into something usable for the more
- * strict parts of HTMLPurifier_Config
- *
- * @param array $array $_GET or $_POST array to import
- * @param string|bool $index Index/name that the config variables are in
- * @param array|bool $allowed List of allowed namespaces/directives
- * @param bool $mq_fix Boolean whether or not to enable magic quotes fix
- * @param HTMLPurifier_ConfigSchema $schema Schema to use, if not global copy
- *
- * @return array
- */
- public static function prepareArrayFromForm($array, $index = false, $allowed = true, $mq_fix = true, $schema = null)
- {
- if ($index !== false) {
- $array = (isset($array[$index]) && is_array($array[$index])) ? $array[$index] : array();
- }
- $mq = $mq_fix && function_exists('get_magic_quotes_gpc') && get_magic_quotes_gpc();
-
- $allowed = HTMLPurifier_Config::getAllowedDirectivesForForm($allowed, $schema);
- $ret = array();
- foreach ($allowed as $key) {
- list($ns, $directive) = $key;
- $skey = "$ns.$directive";
- if (!empty($array["Null_$skey"])) {
- $ret[$ns][$directive] = null;
- continue;
- }
- if (!isset($array[$skey])) {
- continue;
- }
- $value = $mq ? stripslashes($array[$skey]) : $array[$skey];
- $ret[$ns][$directive] = $value;
- }
- return $ret;
- }
-
- /**
- * Loads configuration values from an ini file
- *
- * @param string $filename Name of ini file
- */
- public function loadIni($filename)
- {
- if ($this->isFinalized('Cannot load directives after finalization')) {
- return;
- }
- $array = parse_ini_file($filename, true);
- $this->loadArray($array);
- }
-
- /**
- * Checks whether or not the configuration object is finalized.
- *
- * @param string|bool $error String error message, or false for no error
- *
- * @return bool
- */
- public function isFinalized($error = false)
- {
- if ($this->finalized && $error) {
- $this->triggerError($error, E_USER_ERROR);
- }
- return $this->finalized;
- }
-
- /**
- * Finalizes configuration only if auto finalize is on and not
- * already finalized
- */
- public function autoFinalize()
- {
- if ($this->autoFinalize) {
- $this->finalize();
- } else {
- $this->plist->squash(true);
- }
- }
-
- /**
- * Finalizes a configuration object, prohibiting further change
- */
- public function finalize()
- {
- $this->finalized = true;
- $this->parser = null;
- }
-
- /**
- * Produces a nicely formatted error message by supplying the
- * stack frame information OUTSIDE of HTMLPurifier_Config.
- *
- * @param string $msg An error message
- * @param int $no An error number
- */
- protected function triggerError($msg, $no)
- {
- // determine previous stack frame
- $extra = '';
- if ($this->chatty) {
- $trace = debug_backtrace();
- // zip(tail(trace), trace) -- but PHP is not Haskell har har
- for ($i = 0, $c = count($trace); $i < $c - 1; $i++) {
- // XXX this is not correct on some versions of HTML Purifier
- if ($trace[$i + 1]['class'] === 'HTMLPurifier_Config') {
- continue;
- }
- $frame = $trace[$i];
- $extra = " invoked on line {$frame['line']} in file {$frame['file']}";
- break;
- }
- }
- trigger_error($msg . $extra, $no);
- }
-
- /**
- * Returns a serialized form of the configuration object that can
- * be reconstituted.
- *
- * @return string
- */
- public function serialize()
- {
- $this->getDefinition('HTML');
- $this->getDefinition('CSS');
- $this->getDefinition('URI');
- return serialize($this);
- }
-
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/ConfigSchema.php b/library/HTMLPurifier/ConfigSchema.php
deleted file mode 100644
index bfbb0f92f..000000000
--- a/library/HTMLPurifier/ConfigSchema.php
+++ /dev/null
@@ -1,176 +0,0 @@
-<?php
-
-/**
- * Configuration definition, defines directives and their defaults.
- */
-class HTMLPurifier_ConfigSchema
-{
- /**
- * Defaults of the directives and namespaces.
- * @type array
- * @note This shares the exact same structure as HTMLPurifier_Config::$conf
- */
- public $defaults = array();
-
- /**
- * The default property list. Do not edit this property list.
- * @type array
- */
- public $defaultPlist;
-
- /**
- * Definition of the directives.
- * The structure of this is:
- *
- * array(
- * 'Namespace' => array(
- * 'Directive' => new stdclass(),
- * )
- * )
- *
- * The stdclass may have the following properties:
- *
- * - If isAlias isn't set:
- * - type: Integer type of directive, see HTMLPurifier_VarParser for definitions
- * - allow_null: If set, this directive allows null values
- * - aliases: If set, an associative array of value aliases to real values
- * - allowed: If set, a lookup array of allowed (string) values
- * - If isAlias is set:
- * - namespace: Namespace this directive aliases to
- * - name: Directive name this directive aliases to
- *
- * In certain degenerate cases, stdclass will actually be an integer. In
- * that case, the value is equivalent to an stdclass with the type
- * property set to the integer. If the integer is negative, type is
- * equal to the absolute value of integer, and allow_null is true.
- *
- * This class is friendly with HTMLPurifier_Config. If you need introspection
- * about the schema, you're better of using the ConfigSchema_Interchange,
- * which uses more memory but has much richer information.
- * @type array
- */
- public $info = array();
-
- /**
- * Application-wide singleton
- * @type HTMLPurifier_ConfigSchema
- */
- protected static $singleton;
-
- public function __construct()
- {
- $this->defaultPlist = new HTMLPurifier_PropertyList();
- }
-
- /**
- * Unserializes the default ConfigSchema.
- * @return HTMLPurifier_ConfigSchema
- */
- public static function makeFromSerial()
- {
- $contents = file_get_contents(HTMLPURIFIER_PREFIX . '/HTMLPurifier/ConfigSchema/schema.ser');
- $r = unserialize($contents);
- if (!$r) {
- $hash = sha1($contents);
- trigger_error("Unserialization of configuration schema failed, sha1 of file was $hash", E_USER_ERROR);
- }
- return $r;
- }
-
- /**
- * Retrieves an instance of the application-wide configuration definition.
- * @param HTMLPurifier_ConfigSchema $prototype
- * @return HTMLPurifier_ConfigSchema
- */
- public static function instance($prototype = null)
- {
- if ($prototype !== null) {
- HTMLPurifier_ConfigSchema::$singleton = $prototype;
- } elseif (HTMLPurifier_ConfigSchema::$singleton === null || $prototype === true) {
- HTMLPurifier_ConfigSchema::$singleton = HTMLPurifier_ConfigSchema::makeFromSerial();
- }
- return HTMLPurifier_ConfigSchema::$singleton;
- }
-
- /**
- * Defines a directive for configuration
- * @warning Will fail of directive's namespace is defined.
- * @warning This method's signature is slightly different from the legacy
- * define() static method! Beware!
- * @param string $key Name of directive
- * @param mixed $default Default value of directive
- * @param string $type Allowed type of the directive. See
- * HTMLPurifier_DirectiveDef::$type for allowed values
- * @param bool $allow_null Whether or not to allow null values
- */
- public function add($key, $default, $type, $allow_null)
- {
- $obj = new stdclass();
- $obj->type = is_int($type) ? $type : HTMLPurifier_VarParser::$types[$type];
- if ($allow_null) {
- $obj->allow_null = true;
- }
- $this->info[$key] = $obj;
- $this->defaults[$key] = $default;
- $this->defaultPlist->set($key, $default);
- }
-
- /**
- * Defines a directive value alias.
- *
- * Directive value aliases are convenient for developers because it lets
- * them set a directive to several values and get the same result.
- * @param string $key Name of Directive
- * @param array $aliases Hash of aliased values to the real alias
- */
- public function addValueAliases($key, $aliases)
- {
- if (!isset($this->info[$key]->aliases)) {
- $this->info[$key]->aliases = array();
- }
- foreach ($aliases as $alias => $real) {
- $this->info[$key]->aliases[$alias] = $real;
- }
- }
-
- /**
- * Defines a set of allowed values for a directive.
- * @warning This is slightly different from the corresponding static
- * method definition.
- * @param string $key Name of directive
- * @param array $allowed Lookup array of allowed values
- */
- public function addAllowedValues($key, $allowed)
- {
- $this->info[$key]->allowed = $allowed;
- }
-
- /**
- * Defines a directive alias for backwards compatibility
- * @param string $key Directive that will be aliased
- * @param string $new_key Directive that the alias will be to
- */
- public function addAlias($key, $new_key)
- {
- $obj = new stdclass;
- $obj->key = $new_key;
- $obj->isAlias = true;
- $this->info[$key] = $obj;
- }
-
- /**
- * Replaces any stdclass that only has the type property with type integer.
- */
- public function postProcess()
- {
- foreach ($this->info as $key => $v) {
- if (count((array) $v) == 1) {
- $this->info[$key] = $v->type;
- } elseif (count((array) $v) == 2 && isset($v->allow_null)) {
- $this->info[$key] = -$v->type;
- }
- }
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/ConfigSchema/schema.ser b/library/HTMLPurifier/ConfigSchema/schema.ser
deleted file mode 100644
index 22ea32185..000000000
--- a/library/HTMLPurifier/ConfigSchema/schema.ser
+++ /dev/null
Binary files differ
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Cache.SerializerPermissions.txt b/library/HTMLPurifier/ConfigSchema/schema/Cache.SerializerPermissions.txt
deleted file mode 100644
index b2b83d9ab..000000000
--- a/library/HTMLPurifier/ConfigSchema/schema/Cache.SerializerPermissions.txt
+++ /dev/null
@@ -1,11 +0,0 @@
-Cache.SerializerPermissions
-TYPE: int
-VERSION: 4.3.0
-DEFAULT: 0755
---DESCRIPTION--
-
-<p>
- Directory permissions of the files and directories created inside
- the DefinitionCache/Serializer or other custom serializer path.
-</p>
---# vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.CustomDoctype.txt b/library/HTMLPurifier/ConfigSchema/schema/HTML.CustomDoctype.txt
deleted file mode 100644
index a64e3d7c3..000000000
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.CustomDoctype.txt
+++ /dev/null
@@ -1,9 +0,0 @@
-HTML.CustomDoctype
-TYPE: string/null
-VERSION: 2.0.1
-DEFAULT: NULL
---DESCRIPTION--
-
-A custom doctype for power-users who defined there own document
-type. This directive only applies when %HTML.Doctype is blank.
---# vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/ConfigSchema/schema/URI.AllowedSchemes.txt b/library/HTMLPurifier/ConfigSchema/schema/URI.AllowedSchemes.txt
deleted file mode 100644
index 666635a5f..000000000
--- a/library/HTMLPurifier/ConfigSchema/schema/URI.AllowedSchemes.txt
+++ /dev/null
@@ -1,17 +0,0 @@
-URI.AllowedSchemes
-TYPE: lookup
---DEFAULT--
-array (
- 'http' => true,
- 'https' => true,
- 'mailto' => true,
- 'ftp' => true,
- 'nntp' => true,
- 'news' => true,
-)
---DESCRIPTION--
-Whitelist that defines the schemes that a URI is allowed to have. This
-prevents XSS attacks from using pseudo-schemes like javascript or mocha.
-There is also support for the <code>data</code> and <code>file</code>
-URI schemes, but they are not enabled by default.
---# vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/ConfigSchema/schema/URI.DefaultScheme.txt b/library/HTMLPurifier/ConfigSchema/schema/URI.DefaultScheme.txt
deleted file mode 100644
index 728e378cb..000000000
--- a/library/HTMLPurifier/ConfigSchema/schema/URI.DefaultScheme.txt
+++ /dev/null
@@ -1,10 +0,0 @@
-URI.DefaultScheme
-TYPE: string
-DEFAULT: 'http'
---DESCRIPTION--
-
-<p>
- Defines through what scheme the output will be served, in order to
- select the proper object validator when no scheme information is present.
-</p>
---# vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/DefinitionCache.php b/library/HTMLPurifier/DefinitionCache.php
deleted file mode 100644
index 67bb5b1e6..000000000
--- a/library/HTMLPurifier/DefinitionCache.php
+++ /dev/null
@@ -1,129 +0,0 @@
-<?php
-
-/**
- * Abstract class representing Definition cache managers that implements
- * useful common methods and is a factory.
- * @todo Create a separate maintenance file advanced users can use to
- * cache their custom HTMLDefinition, which can be loaded
- * via a configuration directive
- * @todo Implement memcached
- */
-abstract class HTMLPurifier_DefinitionCache
-{
- /**
- * @type string
- */
- public $type;
-
- /**
- * @param string $type Type of definition objects this instance of the
- * cache will handle.
- */
- public function __construct($type)
- {
- $this->type = $type;
- }
-
- /**
- * Generates a unique identifier for a particular configuration
- * @param HTMLPurifier_Config $config Instance of HTMLPurifier_Config
- * @return string
- */
- public function generateKey($config)
- {
- return $config->version . ',' . // possibly replace with function calls
- $config->getBatchSerial($this->type) . ',' .
- $config->get($this->type . '.DefinitionRev');
- }
-
- /**
- * Tests whether or not a key is old with respect to the configuration's
- * version and revision number.
- * @param string $key Key to test
- * @param HTMLPurifier_Config $config Instance of HTMLPurifier_Config to test against
- * @return bool
- */
- public function isOld($key, $config)
- {
- if (substr_count($key, ',') < 2) {
- return true;
- }
- list($version, $hash, $revision) = explode(',', $key, 3);
- $compare = version_compare($version, $config->version);
- // version mismatch, is always old
- if ($compare != 0) {
- return true;
- }
- // versions match, ids match, check revision number
- if ($hash == $config->getBatchSerial($this->type) &&
- $revision < $config->get($this->type . '.DefinitionRev')) {
- return true;
- }
- return false;
- }
-
- /**
- * Checks if a definition's type jives with the cache's type
- * @note Throws an error on failure
- * @param HTMLPurifier_Definition $def Definition object to check
- * @return bool true if good, false if not
- */
- public function checkDefType($def)
- {
- if ($def->type !== $this->type) {
- trigger_error("Cannot use definition of type {$def->type} in cache for {$this->type}");
- return false;
- }
- return true;
- }
-
- /**
- * Adds a definition object to the cache
- * @param HTMLPurifier_Definition $def
- * @param HTMLPurifier_Config $config
- */
- abstract public function add($def, $config);
-
- /**
- * Unconditionally saves a definition object to the cache
- * @param HTMLPurifier_Definition $def
- * @param HTMLPurifier_Config $config
- */
- abstract public function set($def, $config);
-
- /**
- * Replace an object in the cache
- * @param HTMLPurifier_Definition $def
- * @param HTMLPurifier_Config $config
- */
- abstract public function replace($def, $config);
-
- /**
- * Retrieves a definition object from the cache
- * @param HTMLPurifier_Config $config
- */
- abstract public function get($config);
-
- /**
- * Removes a definition object to the cache
- * @param HTMLPurifier_Config $config
- */
- abstract public function remove($config);
-
- /**
- * Clears all objects from cache
- * @param HTMLPurifier_Config $config
- */
- abstract public function flush($config);
-
- /**
- * Clears all expired (older version or revision) objects from cache
- * @note Be carefuly implementing this method as flush. Flush must
- * not interfere with other Definition types, and cleanup()
- * should not be repeatedly called by userland code.
- * @param HTMLPurifier_Config $config
- */
- abstract public function cleanup($config);
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/DefinitionCache/Serializer.php b/library/HTMLPurifier/DefinitionCache/Serializer.php
deleted file mode 100644
index ecacb88fe..000000000
--- a/library/HTMLPurifier/DefinitionCache/Serializer.php
+++ /dev/null
@@ -1,285 +0,0 @@
-<?php
-
-class HTMLPurifier_DefinitionCache_Serializer extends HTMLPurifier_DefinitionCache
-{
-
- /**
- * @param HTMLPurifier_Definition $def
- * @param HTMLPurifier_Config $config
- * @return int|bool
- */
- public function add($def, $config)
- {
- if (!$this->checkDefType($def)) {
- return;
- }
- $file = $this->generateFilePath($config);
- if (file_exists($file)) {
- return false;
- }
- if (!$this->_prepareDir($config)) {
- return false;
- }
- return $this->_write($file, serialize($def), $config);
- }
-
- /**
- * @param HTMLPurifier_Definition $def
- * @param HTMLPurifier_Config $config
- * @return int|bool
- */
- public function set($def, $config)
- {
- if (!$this->checkDefType($def)) {
- return;
- }
- $file = $this->generateFilePath($config);
- if (!$this->_prepareDir($config)) {
- return false;
- }
- return $this->_write($file, serialize($def), $config);
- }
-
- /**
- * @param HTMLPurifier_Definition $def
- * @param HTMLPurifier_Config $config
- * @return int|bool
- */
- public function replace($def, $config)
- {
- if (!$this->checkDefType($def)) {
- return;
- }
- $file = $this->generateFilePath($config);
- if (!file_exists($file)) {
- return false;
- }
- if (!$this->_prepareDir($config)) {
- return false;
- }
- return $this->_write($file, serialize($def), $config);
- }
-
- /**
- * @param HTMLPurifier_Config $config
- * @return bool|HTMLPurifier_Config
- */
- public function get($config)
- {
- $file = $this->generateFilePath($config);
- if (!file_exists($file)) {
- return false;
- }
- return unserialize(file_get_contents($file));
- }
-
- /**
- * @param HTMLPurifier_Config $config
- * @return bool
- */
- public function remove($config)
- {
- $file = $this->generateFilePath($config);
- if (!file_exists($file)) {
- return false;
- }
- return unlink($file);
- }
-
- /**
- * @param HTMLPurifier_Config $config
- * @return bool
- */
- public function flush($config)
- {
- if (!$this->_prepareDir($config)) {
- return false;
- }
- $dir = $this->generateDirectoryPath($config);
- $dh = opendir($dir);
- while (false !== ($filename = readdir($dh))) {
- if (empty($filename)) {
- continue;
- }
- if ($filename[0] === '.') {
- continue;
- }
- unlink($dir . '/' . $filename);
- }
- }
-
- /**
- * @param HTMLPurifier_Config $config
- * @return bool
- */
- public function cleanup($config)
- {
- if (!$this->_prepareDir($config)) {
- return false;
- }
- $dir = $this->generateDirectoryPath($config);
- $dh = opendir($dir);
- while (false !== ($filename = readdir($dh))) {
- if (empty($filename)) {
- continue;
- }
- if ($filename[0] === '.') {
- continue;
- }
- $key = substr($filename, 0, strlen($filename) - 4);
- if ($this->isOld($key, $config)) {
- unlink($dir . '/' . $filename);
- }
- }
- }
-
- /**
- * Generates the file path to the serial file corresponding to
- * the configuration and definition name
- * @param HTMLPurifier_Config $config
- * @return string
- * @todo Make protected
- */
- public function generateFilePath($config)
- {
- $key = $this->generateKey($config);
- return $this->generateDirectoryPath($config) . '/' . $key . '.ser';
- }
-
- /**
- * Generates the path to the directory contain this cache's serial files
- * @param HTMLPurifier_Config $config
- * @return string
- * @note No trailing slash
- * @todo Make protected
- */
- public function generateDirectoryPath($config)
- {
- $base = $this->generateBaseDirectoryPath($config);
- return $base . '/' . $this->type;
- }
-
- /**
- * Generates path to base directory that contains all definition type
- * serials
- * @param HTMLPurifier_Config $config
- * @return mixed|string
- * @todo Make protected
- */
- public function generateBaseDirectoryPath($config)
- {
- $base = $config->get('Cache.SerializerPath');
- $base = is_null($base) ? HTMLPURIFIER_PREFIX . '/HTMLPurifier/DefinitionCache/Serializer' : $base;
- return $base;
- }
-
- /**
- * Convenience wrapper function for file_put_contents
- * @param string $file File name to write to
- * @param string $data Data to write into file
- * @param HTMLPurifier_Config $config
- * @return int|bool Number of bytes written if success, or false if failure.
- */
- private function _write($file, $data, $config)
- {
- $result = file_put_contents($file, $data);
- if ($result !== false) {
- // set permissions of the new file (no execute)
- $chmod = $config->get('Cache.SerializerPermissions');
- if (!$chmod) {
- $chmod = 0644; // invalid config or simpletest
- }
- $chmod = $chmod & 0666;
- chmod($file, $chmod);
- }
- return $result;
- }
-
- /**
- * Prepares the directory that this type stores the serials in
- * @param HTMLPurifier_Config $config
- * @return bool True if successful
- */
- private function _prepareDir($config)
- {
- $directory = $this->generateDirectoryPath($config);
- $chmod = $config->get('Cache.SerializerPermissions');
- if (!$chmod) {
- $chmod = 0755; // invalid config or simpletest
- }
- if (!is_dir($directory)) {
- $base = $this->generateBaseDirectoryPath($config);
- if (!is_dir($base)) {
- trigger_error(
- 'Base directory ' . $base . ' does not exist,
- please create or change using %Cache.SerializerPath',
- E_USER_WARNING
- );
- return false;
- } elseif (!$this->_testPermissions($base, $chmod)) {
- return false;
- }
- $old = umask(0000);
- mkdir($directory, $chmod);
- umask($old);
- } elseif (!$this->_testPermissions($directory, $chmod)) {
- return false;
- }
- return true;
- }
-
- /**
- * Tests permissions on a directory and throws out friendly
- * error messages and attempts to chmod it itself if possible
- * @param string $dir Directory path
- * @param int $chmod Permissions
- * @return bool True if directory is writable
- */
- private function _testPermissions($dir, $chmod)
- {
- // early abort, if it is writable, everything is hunky-dory
- if (is_writable($dir)) {
- return true;
- }
- if (!is_dir($dir)) {
- // generally, you'll want to handle this beforehand
- // so a more specific error message can be given
- trigger_error(
- 'Directory ' . $dir . ' does not exist',
- E_USER_WARNING
- );
- return false;
- }
- if (function_exists('posix_getuid')) {
- // POSIX system, we can give more specific advice
- if (fileowner($dir) === posix_getuid()) {
- // we can chmod it ourselves
- $chmod = $chmod | 0700;
- if (chmod($dir, $chmod)) {
- return true;
- }
- } elseif (filegroup($dir) === posix_getgid()) {
- $chmod = $chmod | 0070;
- } else {
- // PHP's probably running as nobody, so we'll
- // need to give global permissions
- $chmod = $chmod | 0777;
- }
- trigger_error(
- 'Directory ' . $dir . ' not writable, ' .
- 'please chmod to ' . decoct($chmod),
- E_USER_WARNING
- );
- } else {
- // generic error message
- trigger_error(
- 'Directory ' . $dir . ' not writable, ' .
- 'please alter file permissions',
- E_USER_WARNING
- );
- }
- return false;
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/Encoder.php b/library/HTMLPurifier/Encoder.php
deleted file mode 100644
index fef9b5890..000000000
--- a/library/HTMLPurifier/Encoder.php
+++ /dev/null
@@ -1,611 +0,0 @@
-<?php
-
-/**
- * A UTF-8 specific character encoder that handles cleaning and transforming.
- * @note All functions in this class should be static.
- */
-class HTMLPurifier_Encoder
-{
-
- /**
- * Constructor throws fatal error if you attempt to instantiate class
- */
- private function __construct()
- {
- trigger_error('Cannot instantiate encoder, call methods statically', E_USER_ERROR);
- }
-
- /**
- * Error-handler that mutes errors, alternative to shut-up operator.
- */
- public static function muteErrorHandler()
- {
- }
-
- /**
- * iconv wrapper which mutes errors, but doesn't work around bugs.
- * @param string $in Input encoding
- * @param string $out Output encoding
- * @param string $text The text to convert
- * @return string
- */
- public static function unsafeIconv($in, $out, $text)
- {
- set_error_handler(array('HTMLPurifier_Encoder', 'muteErrorHandler'));
- $r = iconv($in, $out, $text);
- restore_error_handler();
- return $r;
- }
-
- /**
- * iconv wrapper which mutes errors and works around bugs.
- * @param string $in Input encoding
- * @param string $out Output encoding
- * @param string $text The text to convert
- * @param int $max_chunk_size
- * @return string
- */
- public static function iconv($in, $out, $text, $max_chunk_size = 8000)
- {
- $code = self::testIconvTruncateBug();
- if ($code == self::ICONV_OK) {
- return self::unsafeIconv($in, $out, $text);
- } elseif ($code == self::ICONV_TRUNCATES) {
- // we can only work around this if the input character set
- // is utf-8
- if ($in == 'utf-8') {
- if ($max_chunk_size < 4) {
- trigger_error('max_chunk_size is too small', E_USER_WARNING);
- return false;
- }
- // split into 8000 byte chunks, but be careful to handle
- // multibyte boundaries properly
- if (($c = strlen($text)) <= $max_chunk_size) {
- return self::unsafeIconv($in, $out, $text);
- }
- $r = '';
- $i = 0;
- while (true) {
- if ($i + $max_chunk_size >= $c) {
- $r .= self::unsafeIconv($in, $out, substr($text, $i));
- break;
- }
- // wibble the boundary
- if (0x80 != (0xC0 & ord($text[$i + $max_chunk_size]))) {
- $chunk_size = $max_chunk_size;
- } elseif (0x80 != (0xC0 & ord($text[$i + $max_chunk_size - 1]))) {
- $chunk_size = $max_chunk_size - 1;
- } elseif (0x80 != (0xC0 & ord($text[$i + $max_chunk_size - 2]))) {
- $chunk_size = $max_chunk_size - 2;
- } elseif (0x80 != (0xC0 & ord($text[$i + $max_chunk_size - 3]))) {
- $chunk_size = $max_chunk_size - 3;
- } else {
- return false; // rather confusing UTF-8...
- }
- $chunk = substr($text, $i, $chunk_size); // substr doesn't mind overlong lengths
- $r .= self::unsafeIconv($in, $out, $chunk);
- $i += $chunk_size;
- }
- return $r;
- } else {
- return false;
- }
- } else {
- return false;
- }
- }
-
- /**
- * Cleans a UTF-8 string for well-formedness and SGML validity
- *
- * It will parse according to UTF-8 and return a valid UTF8 string, with
- * non-SGML codepoints excluded.
- *
- * @param string $str The string to clean
- * @param bool $force_php
- * @return string
- *
- * @note Just for reference, the non-SGML code points are 0 to 31 and
- * 127 to 159, inclusive. However, we allow code points 9, 10
- * and 13, which are the tab, line feed and carriage return
- * respectively. 128 and above the code points map to multibyte
- * UTF-8 representations.
- *
- * @note Fallback code adapted from utf8ToUnicode by Henri Sivonen and
- * hsivonen@iki.fi at <http://iki.fi/hsivonen/php-utf8/> under the
- * LGPL license. Notes on what changed are inside, but in general,
- * the original code transformed UTF-8 text into an array of integer
- * Unicode codepoints. Understandably, transforming that back to
- * a string would be somewhat expensive, so the function was modded to
- * directly operate on the string. However, this discourages code
- * reuse, and the logic enumerated here would be useful for any
- * function that needs to be able to understand UTF-8 characters.
- * As of right now, only smart lossless character encoding converters
- * would need that, and I'm probably not going to implement them.
- * Once again, PHP 6 should solve all our problems.
- */
- public static function cleanUTF8($str, $force_php = false)
- {
- // UTF-8 validity is checked since PHP 4.3.5
- // This is an optimization: if the string is already valid UTF-8, no
- // need to do PHP stuff. 99% of the time, this will be the case.
- // The regexp matches the XML char production, as well as well as excluding
- // non-SGML codepoints U+007F to U+009F
- if (preg_match(
- '/^[\x{9}\x{A}\x{D}\x{20}-\x{7E}\x{A0}-\x{D7FF}\x{E000}-\x{FFFD}\x{10000}-\x{10FFFF}]*$/Du',
- $str
- )) {
- return $str;
- }
-
- $mState = 0; // cached expected number of octets after the current octet
- // until the beginning of the next UTF8 character sequence
- $mUcs4 = 0; // cached Unicode character
- $mBytes = 1; // cached expected number of octets in the current sequence
-
- // original code involved an $out that was an array of Unicode
- // codepoints. Instead of having to convert back into UTF-8, we've
- // decided to directly append valid UTF-8 characters onto a string
- // $out once they're done. $char accumulates raw bytes, while $mUcs4
- // turns into the Unicode code point, so there's some redundancy.
-
- $out = '';
- $char = '';
-
- $len = strlen($str);
- for ($i = 0; $i < $len; $i++) {
- $in = ord($str{$i});
- $char .= $str[$i]; // append byte to char
- if (0 == $mState) {
- // When mState is zero we expect either a US-ASCII character
- // or a multi-octet sequence.
- if (0 == (0x80 & ($in))) {
- // US-ASCII, pass straight through.
- if (($in <= 31 || $in == 127) &&
- !($in == 9 || $in == 13 || $in == 10) // save \r\t\n
- ) {
- // control characters, remove
- } else {
- $out .= $char;
- }
- // reset
- $char = '';
- $mBytes = 1;
- } elseif (0xC0 == (0xE0 & ($in))) {
- // First octet of 2 octet sequence
- $mUcs4 = ($in);
- $mUcs4 = ($mUcs4 & 0x1F) << 6;
- $mState = 1;
- $mBytes = 2;
- } elseif (0xE0 == (0xF0 & ($in))) {
- // First octet of 3 octet sequence
- $mUcs4 = ($in);
- $mUcs4 = ($mUcs4 & 0x0F) << 12;
- $mState = 2;
- $mBytes = 3;
- } elseif (0xF0 == (0xF8 & ($in))) {
- // First octet of 4 octet sequence
- $mUcs4 = ($in);
- $mUcs4 = ($mUcs4 & 0x07) << 18;
- $mState = 3;
- $mBytes = 4;
- } elseif (0xF8 == (0xFC & ($in))) {
- // First octet of 5 octet sequence.
- //
- // This is illegal because the encoded codepoint must be
- // either:
- // (a) not the shortest form or
- // (b) outside the Unicode range of 0-0x10FFFF.
- // Rather than trying to resynchronize, we will carry on
- // until the end of the sequence and let the later error
- // handling code catch it.
- $mUcs4 = ($in);
- $mUcs4 = ($mUcs4 & 0x03) << 24;
- $mState = 4;
- $mBytes = 5;
- } elseif (0xFC == (0xFE & ($in))) {
- // First octet of 6 octet sequence, see comments for 5
- // octet sequence.
- $mUcs4 = ($in);
- $mUcs4 = ($mUcs4 & 1) << 30;
- $mState = 5;
- $mBytes = 6;
- } else {
- // Current octet is neither in the US-ASCII range nor a
- // legal first octet of a multi-octet sequence.
- $mState = 0;
- $mUcs4 = 0;
- $mBytes = 1;
- $char = '';
- }
- } else {
- // When mState is non-zero, we expect a continuation of the
- // multi-octet sequence
- if (0x80 == (0xC0 & ($in))) {
- // Legal continuation.
- $shift = ($mState - 1) * 6;
- $tmp = $in;
- $tmp = ($tmp & 0x0000003F) << $shift;
- $mUcs4 |= $tmp;
-
- if (0 == --$mState) {
- // End of the multi-octet sequence. mUcs4 now contains
- // the final Unicode codepoint to be output
-
- // Check for illegal sequences and codepoints.
-
- // From Unicode 3.1, non-shortest form is illegal
- if (((2 == $mBytes) && ($mUcs4 < 0x0080)) ||
- ((3 == $mBytes) && ($mUcs4 < 0x0800)) ||
- ((4 == $mBytes) && ($mUcs4 < 0x10000)) ||
- (4 < $mBytes) ||
- // From Unicode 3.2, surrogate characters = illegal
- (($mUcs4 & 0xFFFFF800) == 0xD800) ||
- // Codepoints outside the Unicode range are illegal
- ($mUcs4 > 0x10FFFF)
- ) {
-
- } elseif (0xFEFF != $mUcs4 && // omit BOM
- // check for valid Char unicode codepoints
- (
- 0x9 == $mUcs4 ||
- 0xA == $mUcs4 ||
- 0xD == $mUcs4 ||
- (0x20 <= $mUcs4 && 0x7E >= $mUcs4) ||
- // 7F-9F is not strictly prohibited by XML,
- // but it is non-SGML, and thus we don't allow it
- (0xA0 <= $mUcs4 && 0xD7FF >= $mUcs4) ||
- (0x10000 <= $mUcs4 && 0x10FFFF >= $mUcs4)
- )
- ) {
- $out .= $char;
- }
- // initialize UTF8 cache (reset)
- $mState = 0;
- $mUcs4 = 0;
- $mBytes = 1;
- $char = '';
- }
- } else {
- // ((0xC0 & (*in) != 0x80) && (mState != 0))
- // Incomplete multi-octet sequence.
- // used to result in complete fail, but we'll reset
- $mState = 0;
- $mUcs4 = 0;
- $mBytes = 1;
- $char ='';
- }
- }
- }
- return $out;
- }
-
- /**
- * Translates a Unicode codepoint into its corresponding UTF-8 character.
- * @note Based on Feyd's function at
- * <http://forums.devnetwork.net/viewtopic.php?p=191404#191404>,
- * which is in public domain.
- * @note While we're going to do code point parsing anyway, a good
- * optimization would be to refuse to translate code points that
- * are non-SGML characters. However, this could lead to duplication.
- * @note This is very similar to the unichr function in
- * maintenance/generate-entity-file.php (although this is superior,
- * due to its sanity checks).
- */
-
- // +----------+----------+----------+----------+
- // | 33222222 | 22221111 | 111111 | |
- // | 10987654 | 32109876 | 54321098 | 76543210 | bit
- // +----------+----------+----------+----------+
- // | | | | 0xxxxxxx | 1 byte 0x00000000..0x0000007F
- // | | | 110yyyyy | 10xxxxxx | 2 byte 0x00000080..0x000007FF
- // | | 1110zzzz | 10yyyyyy | 10xxxxxx | 3 byte 0x00000800..0x0000FFFF
- // | 11110www | 10wwzzzz | 10yyyyyy | 10xxxxxx | 4 byte 0x00010000..0x0010FFFF
- // +----------+----------+----------+----------+
- // | 00000000 | 00011111 | 11111111 | 11111111 | Theoretical upper limit of legal scalars: 2097151 (0x001FFFFF)
- // | 00000000 | 00010000 | 11111111 | 11111111 | Defined upper limit of legal scalar codes
- // +----------+----------+----------+----------+
-
- public static function unichr($code)
- {
- if ($code > 1114111 or $code < 0 or
- ($code >= 55296 and $code <= 57343) ) {
- // bits are set outside the "valid" range as defined
- // by UNICODE 4.1.0
- return '';
- }
-
- $x = $y = $z = $w = 0;
- if ($code < 128) {
- // regular ASCII character
- $x = $code;
- } else {
- // set up bits for UTF-8
- $x = ($code & 63) | 128;
- if ($code < 2048) {
- $y = (($code & 2047) >> 6) | 192;
- } else {
- $y = (($code & 4032) >> 6) | 128;
- if ($code < 65536) {
- $z = (($code >> 12) & 15) | 224;
- } else {
- $z = (($code >> 12) & 63) | 128;
- $w = (($code >> 18) & 7) | 240;
- }
- }
- }
- // set up the actual character
- $ret = '';
- if ($w) {
- $ret .= chr($w);
- }
- if ($z) {
- $ret .= chr($z);
- }
- if ($y) {
- $ret .= chr($y);
- }
- $ret .= chr($x);
-
- return $ret;
- }
-
- /**
- * @return bool
- */
- public static function iconvAvailable()
- {
- static $iconv = null;
- if ($iconv === null) {
- $iconv = function_exists('iconv') && self::testIconvTruncateBug() != self::ICONV_UNUSABLE;
- }
- return $iconv;
- }
-
- /**
- * Convert a string to UTF-8 based on configuration.
- * @param string $str The string to convert
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return string
- */
- public static function convertToUTF8($str, $config, $context)
- {
- $encoding = $config->get('Core.Encoding');
- if ($encoding === 'utf-8') {
- return $str;
- }
- static $iconv = null;
- if ($iconv === null) {
- $iconv = self::iconvAvailable();
- }
- if ($iconv && !$config->get('Test.ForceNoIconv')) {
- // unaffected by bugs, since UTF-8 support all characters
- $str = self::unsafeIconv($encoding, 'utf-8//IGNORE', $str);
- if ($str === false) {
- // $encoding is not a valid encoding
- trigger_error('Invalid encoding ' . $encoding, E_USER_ERROR);
- return '';
- }
- // If the string is bjorked by Shift_JIS or a similar encoding
- // that doesn't support all of ASCII, convert the naughty
- // characters to their true byte-wise ASCII/UTF-8 equivalents.
- $str = strtr($str, self::testEncodingSupportsASCII($encoding));
- return $str;
- } elseif ($encoding === 'iso-8859-1') {
- $str = utf8_encode($str);
- return $str;
- }
- $bug = HTMLPurifier_Encoder::testIconvTruncateBug();
- if ($bug == self::ICONV_OK) {
- trigger_error('Encoding not supported, please install iconv', E_USER_ERROR);
- } else {
- trigger_error(
- 'You have a buggy version of iconv, see https://bugs.php.net/bug.php?id=48147 ' .
- 'and http://sourceware.org/bugzilla/show_bug.cgi?id=13541',
- E_USER_ERROR
- );
- }
- }
-
- /**
- * Converts a string from UTF-8 based on configuration.
- * @param string $str The string to convert
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return string
- * @note Currently, this is a lossy conversion, with unexpressable
- * characters being omitted.
- */
- public static function convertFromUTF8($str, $config, $context)
- {
- $encoding = $config->get('Core.Encoding');
- if ($escape = $config->get('Core.EscapeNonASCIICharacters')) {
- $str = self::convertToASCIIDumbLossless($str);
- }
- if ($encoding === 'utf-8') {
- return $str;
- }
- static $iconv = null;
- if ($iconv === null) {
- $iconv = self::iconvAvailable();
- }
- if ($iconv && !$config->get('Test.ForceNoIconv')) {
- // Undo our previous fix in convertToUTF8, otherwise iconv will barf
- $ascii_fix = self::testEncodingSupportsASCII($encoding);
- if (!$escape && !empty($ascii_fix)) {
- $clear_fix = array();
- foreach ($ascii_fix as $utf8 => $native) {
- $clear_fix[$utf8] = '';
- }
- $str = strtr($str, $clear_fix);
- }
- $str = strtr($str, array_flip($ascii_fix));
- // Normal stuff
- $str = self::iconv('utf-8', $encoding . '//IGNORE', $str);
- return $str;
- } elseif ($encoding === 'iso-8859-1') {
- $str = utf8_decode($str);
- return $str;
- }
- trigger_error('Encoding not supported', E_USER_ERROR);
- // You might be tempted to assume that the ASCII representation
- // might be OK, however, this is *not* universally true over all
- // encodings. So we take the conservative route here, rather
- // than forcibly turn on %Core.EscapeNonASCIICharacters
- }
-
- /**
- * Lossless (character-wise) conversion of HTML to ASCII
- * @param string $str UTF-8 string to be converted to ASCII
- * @return string ASCII encoded string with non-ASCII character entity-ized
- * @warning Adapted from MediaWiki, claiming fair use: this is a common
- * algorithm. If you disagree with this license fudgery,
- * implement it yourself.
- * @note Uses decimal numeric entities since they are best supported.
- * @note This is a DUMB function: it has no concept of keeping
- * character entities that the projected character encoding
- * can allow. We could possibly implement a smart version
- * but that would require it to also know which Unicode
- * codepoints the charset supported (not an easy task).
- * @note Sort of with cleanUTF8() but it assumes that $str is
- * well-formed UTF-8
- */
- public static function convertToASCIIDumbLossless($str)
- {
- $bytesleft = 0;
- $result = '';
- $working = 0;
- $len = strlen($str);
- for ($i = 0; $i < $len; $i++) {
- $bytevalue = ord($str[$i]);
- if ($bytevalue <= 0x7F) { //0xxx xxxx
- $result .= chr($bytevalue);
- $bytesleft = 0;
- } elseif ($bytevalue <= 0xBF) { //10xx xxxx
- $working = $working << 6;
- $working += ($bytevalue & 0x3F);
- $bytesleft--;
- if ($bytesleft <= 0) {
- $result .= "&#" . $working . ";";
- }
- } elseif ($bytevalue <= 0xDF) { //110x xxxx
- $working = $bytevalue & 0x1F;
- $bytesleft = 1;
- } elseif ($bytevalue <= 0xEF) { //1110 xxxx
- $working = $bytevalue & 0x0F;
- $bytesleft = 2;
- } else { //1111 0xxx
- $working = $bytevalue & 0x07;
- $bytesleft = 3;
- }
- }
- return $result;
- }
-
- /** No bugs detected in iconv. */
- const ICONV_OK = 0;
-
- /** Iconv truncates output if converting from UTF-8 to another
- * character set with //IGNORE, and a non-encodable character is found */
- const ICONV_TRUNCATES = 1;
-
- /** Iconv does not support //IGNORE, making it unusable for
- * transcoding purposes */
- const ICONV_UNUSABLE = 2;
-
- /**
- * glibc iconv has a known bug where it doesn't handle the magic
- * //IGNORE stanza correctly. In particular, rather than ignore
- * characters, it will return an EILSEQ after consuming some number
- * of characters, and expect you to restart iconv as if it were
- * an E2BIG. Old versions of PHP did not respect the errno, and
- * returned the fragment, so as a result you would see iconv
- * mysteriously truncating output. We can work around this by
- * manually chopping our input into segments of about 8000
- * characters, as long as PHP ignores the error code. If PHP starts
- * paying attention to the error code, iconv becomes unusable.
- *
- * @return int Error code indicating severity of bug.
- */
- public static function testIconvTruncateBug()
- {
- static $code = null;
- if ($code === null) {
- // better not use iconv, otherwise infinite loop!
- $r = self::unsafeIconv('utf-8', 'ascii//IGNORE', "\xCE\xB1" . str_repeat('a', 9000));
- if ($r === false) {
- $code = self::ICONV_UNUSABLE;
- } elseif (($c = strlen($r)) < 9000) {
- $code = self::ICONV_TRUNCATES;
- } elseif ($c > 9000) {
- trigger_error(
- 'Your copy of iconv is extremely buggy. Please notify HTML Purifier maintainers: ' .
- 'include your iconv version as per phpversion()',
- E_USER_ERROR
- );
- } else {
- $code = self::ICONV_OK;
- }
- }
- return $code;
- }
-
- /**
- * This expensive function tests whether or not a given character
- * encoding supports ASCII. 7/8-bit encodings like Shift_JIS will
- * fail this test, and require special processing. Variable width
- * encodings shouldn't ever fail.
- *
- * @param string $encoding Encoding name to test, as per iconv format
- * @param bool $bypass Whether or not to bypass the precompiled arrays.
- * @return Array of UTF-8 characters to their corresponding ASCII,
- * which can be used to "undo" any overzealous iconv action.
- */
- public static function testEncodingSupportsASCII($encoding, $bypass = false)
- {
- // All calls to iconv here are unsafe, proof by case analysis:
- // If ICONV_OK, no difference.
- // If ICONV_TRUNCATE, all calls involve one character inputs,
- // so bug is not triggered.
- // If ICONV_UNUSABLE, this call is irrelevant
- static $encodings = array();
- if (!$bypass) {
- if (isset($encodings[$encoding])) {
- return $encodings[$encoding];
- }
- $lenc = strtolower($encoding);
- switch ($lenc) {
- case 'shift_jis':
- return array("\xC2\xA5" => '\\', "\xE2\x80\xBE" => '~');
- case 'johab':
- return array("\xE2\x82\xA9" => '\\');
- }
- if (strpos($lenc, 'iso-8859-') === 0) {
- return array();
- }
- }
- $ret = array();
- if (self::unsafeIconv('UTF-8', $encoding, 'a') === false) {
- return false;
- }
- for ($i = 0x20; $i <= 0x7E; $i++) { // all printable ASCII chars
- $c = chr($i); // UTF-8 char
- $r = self::unsafeIconv('UTF-8', "$encoding//IGNORE", $c); // initial conversion
- if ($r === '' ||
- // This line is needed for iconv implementations that do not
- // omit characters that do not exist in the target character set
- ($r === $c && self::unsafeIconv($encoding, 'UTF-8//IGNORE', $r) !== $c)
- ) {
- // Reverse engineer: what's the UTF-8 equiv of this byte
- // sequence? This assumes that there's no variable width
- // encoding that doesn't support ASCII.
- $ret[self::unsafeIconv($encoding, 'UTF-8//IGNORE', $c)] = $c;
- }
- }
- $encodings[$encoding] = $ret;
- return $ret;
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/EntityParser.php b/library/HTMLPurifier/EntityParser.php
deleted file mode 100644
index 61529dcd9..000000000
--- a/library/HTMLPurifier/EntityParser.php
+++ /dev/null
@@ -1,153 +0,0 @@
-<?php
-
-// if want to implement error collecting here, we'll need to use some sort
-// of global data (probably trigger_error) because it's impossible to pass
-// $config or $context to the callback functions.
-
-/**
- * Handles referencing and derefencing character entities
- */
-class HTMLPurifier_EntityParser
-{
-
- /**
- * Reference to entity lookup table.
- * @type HTMLPurifier_EntityLookup
- */
- protected $_entity_lookup;
-
- /**
- * Callback regex string for parsing entities.
- * @type string
- */
- protected $_substituteEntitiesRegex =
- '/&(?:[#]x([a-fA-F0-9]+)|[#]0*(\d+)|([A-Za-z_:][A-Za-z0-9.\-_:]*));?/';
- // 1. hex 2. dec 3. string (XML style)
-
- /**
- * Decimal to parsed string conversion table for special entities.
- * @type array
- */
- protected $_special_dec2str =
- array(
- 34 => '"',
- 38 => '&',
- 39 => "'",
- 60 => '<',
- 62 => '>'
- );
-
- /**
- * Stripped entity names to decimal conversion table for special entities.
- * @type array
- */
- protected $_special_ent2dec =
- array(
- 'quot' => 34,
- 'amp' => 38,
- 'lt' => 60,
- 'gt' => 62
- );
-
- /**
- * Substitutes non-special entities with their parsed equivalents. Since
- * running this whenever you have parsed character is t3h 5uck, we run
- * it before everything else.
- *
- * @param string $string String to have non-special entities parsed.
- * @return string Parsed string.
- */
- public function substituteNonSpecialEntities($string)
- {
- // it will try to detect missing semicolons, but don't rely on it
- return preg_replace_callback(
- $this->_substituteEntitiesRegex,
- array($this, 'nonSpecialEntityCallback'),
- $string
- );
- }
-
- /**
- * Callback function for substituteNonSpecialEntities() that does the work.
- *
- * @param array $matches PCRE matches array, with 0 the entire match, and
- * either index 1, 2 or 3 set with a hex value, dec value,
- * or string (respectively).
- * @return string Replacement string.
- */
-
- protected function nonSpecialEntityCallback($matches)
- {
- // replaces all but big five
- $entity = $matches[0];
- $is_num = (@$matches[0][1] === '#');
- if ($is_num) {
- $is_hex = (@$entity[2] === 'x');
- $code = $is_hex ? hexdec($matches[1]) : (int) $matches[2];
- // abort for special characters
- if (isset($this->_special_dec2str[$code])) {
- return $entity;
- }
- return HTMLPurifier_Encoder::unichr($code);
- } else {
- if (isset($this->_special_ent2dec[$matches[3]])) {
- return $entity;
- }
- if (!$this->_entity_lookup) {
- $this->_entity_lookup = HTMLPurifier_EntityLookup::instance();
- }
- if (isset($this->_entity_lookup->table[$matches[3]])) {
- return $this->_entity_lookup->table[$matches[3]];
- } else {
- return $entity;
- }
- }
- }
-
- /**
- * Substitutes only special entities with their parsed equivalents.
- *
- * @notice We try to avoid calling this function because otherwise, it
- * would have to be called a lot (for every parsed section).
- *
- * @param string $string String to have non-special entities parsed.
- * @return string Parsed string.
- */
- public function substituteSpecialEntities($string)
- {
- return preg_replace_callback(
- $this->_substituteEntitiesRegex,
- array($this, 'specialEntityCallback'),
- $string
- );
- }
-
- /**
- * Callback function for substituteSpecialEntities() that does the work.
- *
- * This callback has same syntax as nonSpecialEntityCallback().
- *
- * @param array $matches PCRE-style matches array, with 0 the entire match, and
- * either index 1, 2 or 3 set with a hex value, dec value,
- * or string (respectively).
- * @return string Replacement string.
- */
- protected function specialEntityCallback($matches)
- {
- $entity = $matches[0];
- $is_num = (@$matches[0][1] === '#');
- if ($is_num) {
- $is_hex = (@$entity[2] === 'x');
- $int = $is_hex ? hexdec($matches[1]) : (int) $matches[2];
- return isset($this->_special_dec2str[$int]) ?
- $this->_special_dec2str[$int] :
- $entity;
- } else {
- return isset($this->_special_ent2dec[$matches[3]]) ?
- $this->_special_ent2dec[$matches[3]] :
- $entity;
- }
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/Filter/ExtractStyleBlocks.php b/library/HTMLPurifier/Filter/ExtractStyleBlocks.php
deleted file mode 100644
index 08e62c16b..000000000
--- a/library/HTMLPurifier/Filter/ExtractStyleBlocks.php
+++ /dev/null
@@ -1,338 +0,0 @@
-<?php
-
-// why is this a top level function? Because PHP 5.2.0 doesn't seem to
-// understand how to interpret this filter if it's a static method.
-// It's all really silly, but if we go this route it might be reasonable
-// to coalesce all of these methods into one.
-function htmlpurifier_filter_extractstyleblocks_muteerrorhandler()
-{
-}
-
-/**
- * This filter extracts <style> blocks from input HTML, cleans them up
- * using CSSTidy, and then places them in $purifier->context->get('StyleBlocks')
- * so they can be used elsewhere in the document.
- *
- * @note
- * See tests/HTMLPurifier/Filter/ExtractStyleBlocksTest.php for
- * sample usage.
- *
- * @note
- * This filter can also be used on stylesheets not included in the
- * document--something purists would probably prefer. Just directly
- * call HTMLPurifier_Filter_ExtractStyleBlocks->cleanCSS()
- */
-class HTMLPurifier_Filter_ExtractStyleBlocks extends HTMLPurifier_Filter
-{
- /**
- * @type string
- */
- public $name = 'ExtractStyleBlocks';
-
- /**
- * @type array
- */
- private $_styleMatches = array();
-
- /**
- * @type csstidy
- */
- private $_tidy;
-
- /**
- * @type HTMLPurifier_AttrDef_HTML_ID
- */
- private $_id_attrdef;
-
- /**
- * @type HTMLPurifier_AttrDef_CSS_Ident
- */
- private $_class_attrdef;
-
- /**
- * @type HTMLPurifier_AttrDef_Enum
- */
- private $_enum_attrdef;
-
- public function __construct()
- {
- $this->_tidy = new csstidy();
- $this->_tidy->set_cfg('lowercase_s', false);
- $this->_id_attrdef = new HTMLPurifier_AttrDef_HTML_ID(true);
- $this->_class_attrdef = new HTMLPurifier_AttrDef_CSS_Ident();
- $this->_enum_attrdef = new HTMLPurifier_AttrDef_Enum(
- array(
- 'first-child',
- 'link',
- 'visited',
- 'active',
- 'hover',
- 'focus'
- )
- );
- }
-
- /**
- * Save the contents of CSS blocks to style matches
- * @param array $matches preg_replace style $matches array
- */
- protected function styleCallback($matches)
- {
- $this->_styleMatches[] = $matches[1];
- }
-
- /**
- * Removes inline <style> tags from HTML, saves them for later use
- * @param string $html
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return string
- * @todo Extend to indicate non-text/css style blocks
- */
- public function preFilter($html, $config, $context)
- {
- $tidy = $config->get('Filter.ExtractStyleBlocks.TidyImpl');
- if ($tidy !== null) {
- $this->_tidy = $tidy;
- }
- $html = preg_replace_callback('#<style(?:\s.*)?>(.+)</style>#isU', array($this, 'styleCallback'), $html);
- $style_blocks = $this->_styleMatches;
- $this->_styleMatches = array(); // reset
- $context->register('StyleBlocks', $style_blocks); // $context must not be reused
- if ($this->_tidy) {
- foreach ($style_blocks as &$style) {
- $style = $this->cleanCSS($style, $config, $context);
- }
- }
- return $html;
- }
-
- /**
- * Takes CSS (the stuff found in <style>) and cleans it.
- * @warning Requires CSSTidy <http://csstidy.sourceforge.net/>
- * @param string $css CSS styling to clean
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @throws HTMLPurifier_Exception
- * @return string Cleaned CSS
- */
- public function cleanCSS($css, $config, $context)
- {
- // prepare scope
- $scope = $config->get('Filter.ExtractStyleBlocks.Scope');
- if ($scope !== null) {
- $scopes = array_map('trim', explode(',', $scope));
- } else {
- $scopes = array();
- }
- // remove comments from CSS
- $css = trim($css);
- if (strncmp('<!--', $css, 4) === 0) {
- $css = substr($css, 4);
- }
- if (strlen($css) > 3 && substr($css, -3) == '-->') {
- $css = substr($css, 0, -3);
- }
- $css = trim($css);
- set_error_handler('htmlpurifier_filter_extractstyleblocks_muteerrorhandler');
- $this->_tidy->parse($css);
- restore_error_handler();
- $css_definition = $config->getDefinition('CSS');
- $html_definition = $config->getDefinition('HTML');
- $new_css = array();
- foreach ($this->_tidy->css as $k => $decls) {
- // $decls are all CSS declarations inside an @ selector
- $new_decls = array();
- foreach ($decls as $selector => $style) {
- $selector = trim($selector);
- if ($selector === '') {
- continue;
- } // should not happen
- // Parse the selector
- // Here is the relevant part of the CSS grammar:
- //
- // ruleset
- // : selector [ ',' S* selector ]* '{' ...
- // selector
- // : simple_selector [ combinator selector | S+ [ combinator? selector ]? ]?
- // combinator
- // : '+' S*
- // : '>' S*
- // simple_selector
- // : element_name [ HASH | class | attrib | pseudo ]*
- // | [ HASH | class | attrib | pseudo ]+
- // element_name
- // : IDENT | '*'
- // ;
- // class
- // : '.' IDENT
- // ;
- // attrib
- // : '[' S* IDENT S* [ [ '=' | INCLUDES | DASHMATCH ] S*
- // [ IDENT | STRING ] S* ]? ']'
- // ;
- // pseudo
- // : ':' [ IDENT | FUNCTION S* [IDENT S*]? ')' ]
- // ;
- //
- // For reference, here are the relevant tokens:
- //
- // HASH #{name}
- // IDENT {ident}
- // INCLUDES ==
- // DASHMATCH |=
- // STRING {string}
- // FUNCTION {ident}\(
- //
- // And the lexical scanner tokens
- //
- // name {nmchar}+
- // nmchar [_a-z0-9-]|{nonascii}|{escape}
- // nonascii [\240-\377]
- // escape {unicode}|\\[^\r\n\f0-9a-f]
- // unicode \\{h}}{1,6}(\r\n|[ \t\r\n\f])?
- // ident -?{nmstart}{nmchar*}
- // nmstart [_a-z]|{nonascii}|{escape}
- // string {string1}|{string2}
- // string1 \"([^\n\r\f\\"]|\\{nl}|{escape})*\"
- // string2 \'([^\n\r\f\\"]|\\{nl}|{escape})*\'
- //
- // We'll implement a subset (in order to reduce attack
- // surface); in particular:
- //
- // - No Unicode support
- // - No escapes support
- // - No string support (by proxy no attrib support)
- // - element_name is matched against allowed
- // elements (some people might find this
- // annoying...)
- // - Pseudo-elements one of :first-child, :link,
- // :visited, :active, :hover, :focus
-
- // handle ruleset
- $selectors = array_map('trim', explode(',', $selector));
- $new_selectors = array();
- foreach ($selectors as $sel) {
- // split on +, > and spaces
- $basic_selectors = preg_split('/\s*([+> ])\s*/', $sel, -1, PREG_SPLIT_DELIM_CAPTURE);
- // even indices are chunks, odd indices are
- // delimiters
- $nsel = null;
- $delim = null; // guaranteed to be non-null after
- // two loop iterations
- for ($i = 0, $c = count($basic_selectors); $i < $c; $i++) {
- $x = $basic_selectors[$i];
- if ($i % 2) {
- // delimiter
- if ($x === ' ') {
- $delim = ' ';
- } else {
- $delim = ' ' . $x . ' ';
- }
- } else {
- // simple selector
- $components = preg_split('/([#.:])/', $x, -1, PREG_SPLIT_DELIM_CAPTURE);
- $sdelim = null;
- $nx = null;
- for ($j = 0, $cc = count($components); $j < $cc; $j++) {
- $y = $components[$j];
- if ($j === 0) {
- if ($y === '*' || isset($html_definition->info[$y = strtolower($y)])) {
- $nx = $y;
- } else {
- // $nx stays null; this matters
- // if we don't manage to find
- // any valid selector content,
- // in which case we ignore the
- // outer $delim
- }
- } elseif ($j % 2) {
- // set delimiter
- $sdelim = $y;
- } else {
- $attrdef = null;
- if ($sdelim === '#') {
- $attrdef = $this->_id_attrdef;
- } elseif ($sdelim === '.') {
- $attrdef = $this->_class_attrdef;
- } elseif ($sdelim === ':') {
- $attrdef = $this->_enum_attrdef;
- } else {
- throw new HTMLPurifier_Exception('broken invariant sdelim and preg_split');
- }
- $r = $attrdef->validate($y, $config, $context);
- if ($r !== false) {
- if ($r !== true) {
- $y = $r;
- }
- if ($nx === null) {
- $nx = '';
- }
- $nx .= $sdelim . $y;
- }
- }
- }
- if ($nx !== null) {
- if ($nsel === null) {
- $nsel = $nx;
- } else {
- $nsel .= $delim . $nx;
- }
- } else {
- // delimiters to the left of invalid
- // basic selector ignored
- }
- }
- }
- if ($nsel !== null) {
- if (!empty($scopes)) {
- foreach ($scopes as $s) {
- $new_selectors[] = "$s $nsel";
- }
- } else {
- $new_selectors[] = $nsel;
- }
- }
- }
- if (empty($new_selectors)) {
- continue;
- }
- $selector = implode(', ', $new_selectors);
- foreach ($style as $name => $value) {
- if (!isset($css_definition->info[$name])) {
- unset($style[$name]);
- continue;
- }
- $def = $css_definition->info[$name];
- $ret = $def->validate($value, $config, $context);
- if ($ret === false) {
- unset($style[$name]);
- } else {
- $style[$name] = $ret;
- }
- }
- $new_decls[$selector] = $style;
- }
- $new_css[$k] = $new_decls;
- }
- // remove stuff that shouldn't be used, could be reenabled
- // after security risks are analyzed
- $this->_tidy->css = $new_css;
- $this->_tidy->import = array();
- $this->_tidy->charset = null;
- $this->_tidy->namespace = null;
- $css = $this->_tidy->print->plain();
- // we are going to escape any special characters <>& to ensure
- // that no funny business occurs (i.e. </style> in a font-family prop).
- if ($config->get('Filter.ExtractStyleBlocks.Escaping')) {
- $css = str_replace(
- array('<', '>', '&'),
- array('\3C ', '\3E ', '\26 '),
- $css
- );
- }
- return $css;
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/Filter/YouTube.php b/library/HTMLPurifier/Filter/YouTube.php
deleted file mode 100644
index 411519ad6..000000000
--- a/library/HTMLPurifier/Filter/YouTube.php
+++ /dev/null
@@ -1,65 +0,0 @@
-<?php
-
-class HTMLPurifier_Filter_YouTube extends HTMLPurifier_Filter
-{
-
- /**
- * @type string
- */
- public $name = 'YouTube';
-
- /**
- * @param string $html
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return string
- */
- public function preFilter($html, $config, $context)
- {
- $pre_regex = '#<object[^>]+>.+?' .
- 'http://www.youtube.com/((?:v|cp)/[A-Za-z0-9\-_=]+).+?</object>#s';
- $pre_replace = '<span class="youtube-embed">\1</span>';
- return preg_replace($pre_regex, $pre_replace, $html);
- }
-
- /**
- * @param string $html
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return string
- */
- public function postFilter($html, $config, $context)
- {
- $post_regex = '#<span class="youtube-embed">((?:v|cp)/[A-Za-z0-9\-_=]+)</span>#';
- return preg_replace_callback($post_regex, array($this, 'postFilterCallback'), $html);
- }
-
- /**
- * @param $url
- * @return string
- */
- protected function armorUrl($url)
- {
- return str_replace('--', '-&#45;', $url);
- }
-
- /**
- * @param array $matches
- * @return string
- */
- protected function postFilterCallback($matches)
- {
- $url = $this->armorUrl($matches[1]);
- return '<object width="425" height="350" type="application/x-shockwave-flash" ' .
- 'data="http://www.youtube.com/' . $url . '">' .
- '<param name="movie" value="http://www.youtube.com/' . $url . '"></param>' .
- '<!--[if IE]>' .
- '<embed src="http://www.youtube.com/' . $url . '"' .
- 'type="application/x-shockwave-flash"' .
- 'wmode="transparent" width="425" height="350" />' .
- '<![endif]-->' .
- '</object>';
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/Generator.php b/library/HTMLPurifier/Generator.php
deleted file mode 100644
index 6fb568714..000000000
--- a/library/HTMLPurifier/Generator.php
+++ /dev/null
@@ -1,286 +0,0 @@
-<?php
-
-/**
- * Generates HTML from tokens.
- * @todo Refactor interface so that configuration/context is determined
- * upon instantiation, no need for messy generateFromTokens() calls
- * @todo Make some of the more internal functions protected, and have
- * unit tests work around that
- */
-class HTMLPurifier_Generator
-{
-
- /**
- * Whether or not generator should produce XML output.
- * @type bool
- */
- private $_xhtml = true;
-
- /**
- * :HACK: Whether or not generator should comment the insides of <script> tags.
- * @type bool
- */
- private $_scriptFix = false;
-
- /**
- * Cache of HTMLDefinition during HTML output to determine whether or
- * not attributes should be minimized.
- * @type HTMLPurifier_HTMLDefinition
- */
- private $_def;
-
- /**
- * Cache of %Output.SortAttr.
- * @type bool
- */
- private $_sortAttr;
-
- /**
- * Cache of %Output.FlashCompat.
- * @type bool
- */
- private $_flashCompat;
-
- /**
- * Cache of %Output.FixInnerHTML.
- * @type bool
- */
- private $_innerHTMLFix;
-
- /**
- * Stack for keeping track of object information when outputting IE
- * compatibility code.
- * @type array
- */
- private $_flashStack = array();
-
- /**
- * Configuration for the generator
- * @type HTMLPurifier_Config
- */
- protected $config;
-
- /**
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- */
- public function __construct($config, $context)
- {
- $this->config = $config;
- $this->_scriptFix = $config->get('Output.CommentScriptContents');
- $this->_innerHTMLFix = $config->get('Output.FixInnerHTML');
- $this->_sortAttr = $config->get('Output.SortAttr');
- $this->_flashCompat = $config->get('Output.FlashCompat');
- $this->_def = $config->getHTMLDefinition();
- $this->_xhtml = $this->_def->doctype->xml;
- }
-
- /**
- * Generates HTML from an array of tokens.
- * @param HTMLPurifier_Token[] $tokens Array of HTMLPurifier_Token
- * @return string Generated HTML
- */
- public function generateFromTokens($tokens)
- {
- if (!$tokens) {
- return '';
- }
-
- // Basic algorithm
- $html = '';
- for ($i = 0, $size = count($tokens); $i < $size; $i++) {
- if ($this->_scriptFix && $tokens[$i]->name === 'script'
- && $i + 2 < $size && $tokens[$i+2] instanceof HTMLPurifier_Token_End) {
- // script special case
- // the contents of the script block must be ONE token
- // for this to work.
- $html .= $this->generateFromToken($tokens[$i++]);
- $html .= $this->generateScriptFromToken($tokens[$i++]);
- }
- $html .= $this->generateFromToken($tokens[$i]);
- }
-
- // Tidy cleanup
- if (extension_loaded('tidy') && $this->config->get('Output.TidyFormat')) {
- $tidy = new Tidy;
- $tidy->parseString(
- $html,
- array(
- 'indent'=> true,
- 'output-xhtml' => $this->_xhtml,
- 'show-body-only' => true,
- 'indent-spaces' => 2,
- 'wrap' => 68,
- ),
- 'utf8'
- );
- $tidy->cleanRepair();
- $html = (string) $tidy; // explicit cast necessary
- }
-
- // Normalize newlines to system defined value
- if ($this->config->get('Core.NormalizeNewlines')) {
- $nl = $this->config->get('Output.Newline');
- if ($nl === null) {
- $nl = PHP_EOL;
- }
- if ($nl !== "\n") {
- $html = str_replace("\n", $nl, $html);
- }
- }
- return $html;
- }
-
- /**
- * Generates HTML from a single token.
- * @param HTMLPurifier_Token $token HTMLPurifier_Token object.
- * @return string Generated HTML
- */
- public function generateFromToken($token)
- {
- if (!$token instanceof HTMLPurifier_Token) {
- trigger_error('Cannot generate HTML from non-HTMLPurifier_Token object', E_USER_WARNING);
- return '';
-
- } elseif ($token instanceof HTMLPurifier_Token_Start) {
- $attr = $this->generateAttributes($token->attr, $token->name);
- if ($this->_flashCompat) {
- if ($token->name == "object") {
- $flash = new stdclass();
- $flash->attr = $token->attr;
- $flash->param = array();
- $this->_flashStack[] = $flash;
- }
- }
- return '<' . $token->name . ($attr ? ' ' : '') . $attr . '>';
-
- } elseif ($token instanceof HTMLPurifier_Token_End) {
- $_extra = '';
- if ($this->_flashCompat) {
- if ($token->name == "object" && !empty($this->_flashStack)) {
- // doesn't do anything for now
- }
- }
- return $_extra . '</' . $token->name . '>';
-
- } elseif ($token instanceof HTMLPurifier_Token_Empty) {
- if ($this->_flashCompat && $token->name == "param" && !empty($this->_flashStack)) {
- $this->_flashStack[count($this->_flashStack)-1]->param[$token->attr['name']] = $token->attr['value'];
- }
- $attr = $this->generateAttributes($token->attr, $token->name);
- return '<' . $token->name . ($attr ? ' ' : '') . $attr .
- ( $this->_xhtml ? ' /': '' ) // <br /> v. <br>
- . '>';
-
- } elseif ($token instanceof HTMLPurifier_Token_Text) {
- return $this->escape($token->data, ENT_NOQUOTES);
-
- } elseif ($token instanceof HTMLPurifier_Token_Comment) {
- return '<!--' . $token->data . '-->';
- } else {
- return '';
-
- }
- }
-
- /**
- * Special case processor for the contents of script tags
- * @param HTMLPurifier_Token $token HTMLPurifier_Token object.
- * @return string
- * @warning This runs into problems if there's already a literal
- * --> somewhere inside the script contents.
- */
- public function generateScriptFromToken($token)
- {
- if (!$token instanceof HTMLPurifier_Token_Text) {
- return $this->generateFromToken($token);
- }
- // Thanks <http://lachy.id.au/log/2005/05/script-comments>
- $data = preg_replace('#//\s*$#', '', $token->data);
- return '<!--//--><![CDATA[//><!--' . "\n" . trim($data) . "\n" . '//--><!]]>';
- }
-
- /**
- * Generates attribute declarations from attribute array.
- * @note This does not include the leading or trailing space.
- * @param array $assoc_array_of_attributes Attribute array
- * @param string $element Name of element attributes are for, used to check
- * attribute minimization.
- * @return string Generated HTML fragment for insertion.
- */
- public function generateAttributes($assoc_array_of_attributes, $element = '')
- {
- $html = '';
- if ($this->_sortAttr) {
- ksort($assoc_array_of_attributes);
- }
- foreach ($assoc_array_of_attributes as $key => $value) {
- if (!$this->_xhtml) {
- // Remove namespaced attributes
- if (strpos($key, ':') !== false) {
- continue;
- }
- // Check if we should minimize the attribute: val="val" -> val
- if ($element && !empty($this->_def->info[$element]->attr[$key]->minimized)) {
- $html .= $key . ' ';
- continue;
- }
- }
- // Workaround for Internet Explorer innerHTML bug.
- // Essentially, Internet Explorer, when calculating
- // innerHTML, omits quotes if there are no instances of
- // angled brackets, quotes or spaces. However, when parsing
- // HTML (for example, when you assign to innerHTML), it
- // treats backticks as quotes. Thus,
- // <img alt="``" />
- // becomes
- // <img alt=`` />
- // becomes
- // <img alt='' />
- // Fortunately, all we need to do is trigger an appropriate
- // quoting style, which we do by adding an extra space.
- // This also is consistent with the W3C spec, which states
- // that user agents may ignore leading or trailing
- // whitespace (in fact, most don't, at least for attributes
- // like alt, but an extra space at the end is barely
- // noticeable). Still, we have a configuration knob for
- // this, since this transformation is not necesary if you
- // don't process user input with innerHTML or you don't plan
- // on supporting Internet Explorer.
- if ($this->_innerHTMLFix) {
- if (strpos($value, '`') !== false) {
- // check if correct quoting style would not already be
- // triggered
- if (strcspn($value, '"\' <>') === strlen($value)) {
- // protect!
- $value .= ' ';
- }
- }
- }
- $html .= $key.'="'.$this->escape($value).'" ';
- }
- return rtrim($html);
- }
-
- /**
- * Escapes raw text data.
- * @todo This really ought to be protected, but until we have a facility
- * for properly generating HTML here w/o using tokens, it stays
- * public.
- * @param string $string String data to escape for HTML.
- * @param int $quote Quoting style, like htmlspecialchars. ENT_NOQUOTES is
- * permissible for non-attribute output.
- * @return string escaped data.
- */
- public function escape($string, $quote = null)
- {
- // Workaround for APC bug on Mac Leopard reported by sidepodcast
- // http://htmlpurifier.org/phorum/read.php?3,4823,4846
- if ($quote === null) {
- $quote = ENT_COMPAT;
- }
- return htmlspecialchars($string, $quote, 'UTF-8');
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/HTMLModuleManager.php b/library/HTMLPurifier/HTMLModuleManager.php
deleted file mode 100644
index f3a17cb03..000000000
--- a/library/HTMLPurifier/HTMLModuleManager.php
+++ /dev/null
@@ -1,459 +0,0 @@
-<?php
-
-class HTMLPurifier_HTMLModuleManager
-{
-
- /**
- * @type HTMLPurifier_DoctypeRegistry
- */
- public $doctypes;
-
- /**
- * Instance of current doctype.
- * @type string
- */
- public $doctype;
-
- /**
- * @type HTMLPurifier_AttrTypes
- */
- public $attrTypes;
-
- /**
- * Active instances of modules for the specified doctype are
- * indexed, by name, in this array.
- * @type HTMLPurifier_HTMLModule[]
- */
- public $modules = array();
-
- /**
- * Array of recognized HTMLPurifier_HTMLModule instances,
- * indexed by module's class name. This array is usually lazy loaded, but a
- * user can overload a module by pre-emptively registering it.
- * @type HTMLPurifier_HTMLModule[]
- */
- public $registeredModules = array();
-
- /**
- * List of extra modules that were added by the user
- * using addModule(). These get unconditionally merged into the current doctype, whatever
- * it may be.
- * @type HTMLPurifier_HTMLModule[]
- */
- public $userModules = array();
-
- /**
- * Associative array of element name to list of modules that have
- * definitions for the element; this array is dynamically filled.
- * @type array
- */
- public $elementLookup = array();
-
- /**
- * List of prefixes we should use for registering small names.
- * @type array
- */
- public $prefixes = array('HTMLPurifier_HTMLModule_');
-
- /**
- * @type HTMLPurifier_ContentSets
- */
- public $contentSets;
-
- /**
- * @type HTMLPurifier_AttrCollections
- */
- public $attrCollections;
-
- /**
- * If set to true, unsafe elements and attributes will be allowed.
- * @type bool
- */
- public $trusted = false;
-
- public function __construct()
- {
- // editable internal objects
- $this->attrTypes = new HTMLPurifier_AttrTypes();
- $this->doctypes = new HTMLPurifier_DoctypeRegistry();
-
- // setup basic modules
- $common = array(
- 'CommonAttributes', 'Text', 'Hypertext', 'List',
- 'Presentation', 'Edit', 'Bdo', 'Tables', 'Image',
- 'StyleAttribute',
- // Unsafe:
- 'Scripting', 'Object', 'Forms',
- // Sorta legacy, but present in strict:
- 'Name',
- );
- $transitional = array('Legacy', 'Target', 'Iframe');
- $xml = array('XMLCommonAttributes');
- $non_xml = array('NonXMLCommonAttributes');
-
- // setup basic doctypes
- $this->doctypes->register(
- 'HTML 4.01 Transitional',
- false,
- array_merge($common, $transitional, $non_xml),
- array('Tidy_Transitional', 'Tidy_Proprietary'),
- array(),
- '-//W3C//DTD HTML 4.01 Transitional//EN',
- 'http://www.w3.org/TR/html4/loose.dtd'
- );
-
- $this->doctypes->register(
- 'HTML 4.01 Strict',
- false,
- array_merge($common, $non_xml),
- array('Tidy_Strict', 'Tidy_Proprietary', 'Tidy_Name'),
- array(),
- '-//W3C//DTD HTML 4.01//EN',
- 'http://www.w3.org/TR/html4/strict.dtd'
- );
-
- $this->doctypes->register(
- 'XHTML 1.0 Transitional',
- true,
- array_merge($common, $transitional, $xml, $non_xml),
- array('Tidy_Transitional', 'Tidy_XHTML', 'Tidy_Proprietary', 'Tidy_Name'),
- array(),
- '-//W3C//DTD XHTML 1.0 Transitional//EN',
- 'http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd'
- );
-
- $this->doctypes->register(
- 'XHTML 1.0 Strict',
- true,
- array_merge($common, $xml, $non_xml),
- array('Tidy_Strict', 'Tidy_XHTML', 'Tidy_Strict', 'Tidy_Proprietary', 'Tidy_Name'),
- array(),
- '-//W3C//DTD XHTML 1.0 Strict//EN',
- 'http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd'
- );
-
- $this->doctypes->register(
- 'XHTML 1.1',
- true,
- // Iframe is a real XHTML 1.1 module, despite being
- // "transitional"!
- array_merge($common, $xml, array('Ruby', 'Iframe')),
- array('Tidy_Strict', 'Tidy_XHTML', 'Tidy_Proprietary', 'Tidy_Strict', 'Tidy_Name'), // Tidy_XHTML1_1
- array(),
- '-//W3C//DTD XHTML 1.1//EN',
- 'http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd'
- );
-
- }
-
- /**
- * Registers a module to the recognized module list, useful for
- * overloading pre-existing modules.
- * @param $module Mixed: string module name, with or without
- * HTMLPurifier_HTMLModule prefix, or instance of
- * subclass of HTMLPurifier_HTMLModule.
- * @param $overload Boolean whether or not to overload previous modules.
- * If this is not set, and you do overload a module,
- * HTML Purifier will complain with a warning.
- * @note This function will not call autoload, you must instantiate
- * (and thus invoke) autoload outside the method.
- * @note If a string is passed as a module name, different variants
- * will be tested in this order:
- * - Check for HTMLPurifier_HTMLModule_$name
- * - Check all prefixes with $name in order they were added
- * - Check for literal object name
- * - Throw fatal error
- * If your object name collides with an internal class, specify
- * your module manually. All modules must have been included
- * externally: registerModule will not perform inclusions for you!
- */
- public function registerModule($module, $overload = false)
- {
- if (is_string($module)) {
- // attempt to load the module
- $original_module = $module;
- $ok = false;
- foreach ($this->prefixes as $prefix) {
- $module = $prefix . $original_module;
- if (class_exists($module)) {
- $ok = true;
- break;
- }
- }
- if (!$ok) {
- $module = $original_module;
- if (!class_exists($module)) {
- trigger_error(
- $original_module . ' module does not exist',
- E_USER_ERROR
- );
- return;
- }
- }
- $module = new $module();
- }
- if (empty($module->name)) {
- trigger_error('Module instance of ' . get_class($module) . ' must have name');
- return;
- }
- if (!$overload && isset($this->registeredModules[$module->name])) {
- trigger_error('Overloading ' . $module->name . ' without explicit overload parameter', E_USER_WARNING);
- }
- $this->registeredModules[$module->name] = $module;
- }
-
- /**
- * Adds a module to the current doctype by first registering it,
- * and then tacking it on to the active doctype
- */
- public function addModule($module)
- {
- $this->registerModule($module);
- if (is_object($module)) {
- $module = $module->name;
- }
- $this->userModules[] = $module;
- }
-
- /**
- * Adds a class prefix that registerModule() will use to resolve a
- * string name to a concrete class
- */
- public function addPrefix($prefix)
- {
- $this->prefixes[] = $prefix;
- }
-
- /**
- * Performs processing on modules, after being called you may
- * use getElement() and getElements()
- * @param HTMLPurifier_Config $config
- */
- public function setup($config)
- {
- $this->trusted = $config->get('HTML.Trusted');
-
- // generate
- $this->doctype = $this->doctypes->make($config);
- $modules = $this->doctype->modules;
-
- // take out the default modules that aren't allowed
- $lookup = $config->get('HTML.AllowedModules');
- $special_cases = $config->get('HTML.CoreModules');
-
- if (is_array($lookup)) {
- foreach ($modules as $k => $m) {
- if (isset($special_cases[$m])) {
- continue;
- }
- if (!isset($lookup[$m])) {
- unset($modules[$k]);
- }
- }
- }
-
- // custom modules
- if ($config->get('HTML.Proprietary')) {
- $modules[] = 'Proprietary';
- }
- if ($config->get('HTML.SafeObject')) {
- $modules[] = 'SafeObject';
- }
- if ($config->get('HTML.SafeEmbed')) {
- $modules[] = 'SafeEmbed';
- }
- if ($config->get('HTML.SafeScripting') !== array()) {
- $modules[] = 'SafeScripting';
- }
- if ($config->get('HTML.Nofollow')) {
- $modules[] = 'Nofollow';
- }
- if ($config->get('HTML.TargetBlank')) {
- $modules[] = 'TargetBlank';
- }
-
- // merge in custom modules
- $modules = array_merge($modules, $this->userModules);
-
- foreach ($modules as $module) {
- $this->processModule($module);
- $this->modules[$module]->setup($config);
- }
-
- foreach ($this->doctype->tidyModules as $module) {
- $this->processModule($module);
- $this->modules[$module]->setup($config);
- }
-
- // prepare any injectors
- foreach ($this->modules as $module) {
- $n = array();
- foreach ($module->info_injector as $injector) {
- if (!is_object($injector)) {
- $class = "HTMLPurifier_Injector_$injector";
- $injector = new $class;
- }
- $n[$injector->name] = $injector;
- }
- $module->info_injector = $n;
- }
-
- // setup lookup table based on all valid modules
- foreach ($this->modules as $module) {
- foreach ($module->info as $name => $def) {
- if (!isset($this->elementLookup[$name])) {
- $this->elementLookup[$name] = array();
- }
- $this->elementLookup[$name][] = $module->name;
- }
- }
-
- // note the different choice
- $this->contentSets = new HTMLPurifier_ContentSets(
- // content set assembly deals with all possible modules,
- // not just ones deemed to be "safe"
- $this->modules
- );
- $this->attrCollections = new HTMLPurifier_AttrCollections(
- $this->attrTypes,
- // there is no way to directly disable a global attribute,
- // but using AllowedAttributes or simply not including
- // the module in your custom doctype should be sufficient
- $this->modules
- );
- }
-
- /**
- * Takes a module and adds it to the active module collection,
- * registering it if necessary.
- */
- public function processModule($module)
- {
- if (!isset($this->registeredModules[$module]) || is_object($module)) {
- $this->registerModule($module);
- }
- $this->modules[$module] = $this->registeredModules[$module];
- }
-
- /**
- * Retrieves merged element definitions.
- * @return Array of HTMLPurifier_ElementDef
- */
- public function getElements()
- {
- $elements = array();
- foreach ($this->modules as $module) {
- if (!$this->trusted && !$module->safe) {
- continue;
- }
- foreach ($module->info as $name => $v) {
- if (isset($elements[$name])) {
- continue;
- }
- $elements[$name] = $this->getElement($name);
- }
- }
-
- // remove dud elements, this happens when an element that
- // appeared to be safe actually wasn't
- foreach ($elements as $n => $v) {
- if ($v === false) {
- unset($elements[$n]);
- }
- }
-
- return $elements;
-
- }
-
- /**
- * Retrieves a single merged element definition
- * @param string $name Name of element
- * @param bool $trusted Boolean trusted overriding parameter: set to true
- * if you want the full version of an element
- * @return HTMLPurifier_ElementDef Merged HTMLPurifier_ElementDef
- * @note You may notice that modules are getting iterated over twice (once
- * in getElements() and once here). This
- * is because
- */
- public function getElement($name, $trusted = null)
- {
- if (!isset($this->elementLookup[$name])) {
- return false;
- }
-
- // setup global state variables
- $def = false;
- if ($trusted === null) {
- $trusted = $this->trusted;
- }
-
- // iterate through each module that has registered itself to this
- // element
- foreach ($this->elementLookup[$name] as $module_name) {
- $module = $this->modules[$module_name];
-
- // refuse to create/merge from a module that is deemed unsafe--
- // pretend the module doesn't exist--when trusted mode is not on.
- if (!$trusted && !$module->safe) {
- continue;
- }
-
- // clone is used because, ideally speaking, the original
- // definition should not be modified. Usually, this will
- // make no difference, but for consistency's sake
- $new_def = clone $module->info[$name];
-
- if (!$def && $new_def->standalone) {
- $def = $new_def;
- } elseif ($def) {
- // This will occur even if $new_def is standalone. In practice,
- // this will usually result in a full replacement.
- $def->mergeIn($new_def);
- } else {
- // :TODO:
- // non-standalone definitions that don't have a standalone
- // to merge into could be deferred to the end
- // HOWEVER, it is perfectly valid for a non-standalone
- // definition to lack a standalone definition, even
- // after all processing: this allows us to safely
- // specify extra attributes for elements that may not be
- // enabled all in one place. In particular, this might
- // be the case for trusted elements. WARNING: care must
- // be taken that the /extra/ definitions are all safe.
- continue;
- }
-
- // attribute value expansions
- $this->attrCollections->performInclusions($def->attr);
- $this->attrCollections->expandIdentifiers($def->attr, $this->attrTypes);
-
- // descendants_are_inline, for ChildDef_Chameleon
- if (is_string($def->content_model) &&
- strpos($def->content_model, 'Inline') !== false) {
- if ($name != 'del' && $name != 'ins') {
- // this is for you, ins/del
- $def->descendants_are_inline = true;
- }
- }
-
- $this->contentSets->generateChildDef($def, $module);
- }
-
- // This can occur if there is a blank definition, but no base to
- // mix it in with
- if (!$def) {
- return false;
- }
-
- // add information on required attributes
- foreach ($def->attr as $attr_name => $attr_def) {
- if ($attr_def->required) {
- $def->required_attr[] = $attr_name;
- }
- }
- return $def;
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/Injector/Linkify.php b/library/HTMLPurifier/Injector/Linkify.php
deleted file mode 100644
index 069708c25..000000000
--- a/library/HTMLPurifier/Injector/Linkify.php
+++ /dev/null
@@ -1,59 +0,0 @@
-<?php
-
-/**
- * Injector that converts http, https and ftp text URLs to actual links.
- */
-class HTMLPurifier_Injector_Linkify extends HTMLPurifier_Injector
-{
- /**
- * @type string
- */
- public $name = 'Linkify';
-
- /**
- * @type array
- */
- public $needed = array('a' => array('href'));
-
- /**
- * @param HTMLPurifier_Token $token
- */
- public function handleText(&$token)
- {
- if (!$this->allowsElement('a')) {
- return;
- }
-
- if (strpos($token->data, '://') === false) {
- // our really quick heuristic failed, abort
- // this may not work so well if we want to match things like
- // "google.com", but then again, most people don't
- return;
- }
-
- // there is/are URL(s). Let's split the string:
- // Note: this regex is extremely permissive
- $bits = preg_split('#((?:https?|ftp)://[^\s\'",<>()]+)#Su', $token->data, -1, PREG_SPLIT_DELIM_CAPTURE);
-
-
- $token = array();
-
- // $i = index
- // $c = count
- // $l = is link
- for ($i = 0, $c = count($bits), $l = false; $i < $c; $i++, $l = !$l) {
- if (!$l) {
- if ($bits[$i] === '') {
- continue;
- }
- $token[] = new HTMLPurifier_Token_Text($bits[$i]);
- } else {
- $token[] = new HTMLPurifier_Token_Start('a', array('href' => $bits[$i]));
- $token[] = new HTMLPurifier_Token_Text($bits[$i]);
- $token[] = new HTMLPurifier_Token_End('a');
- }
- }
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/Injector/RemoveEmpty.php b/library/HTMLPurifier/Injector/RemoveEmpty.php
deleted file mode 100644
index cd885722e..000000000
--- a/library/HTMLPurifier/Injector/RemoveEmpty.php
+++ /dev/null
@@ -1,101 +0,0 @@
-<?php
-
-class HTMLPurifier_Injector_RemoveEmpty extends HTMLPurifier_Injector
-{
- /**
- * @type HTMLPurifier_Context
- */
- private $context;
-
- /**
- * @type HTMLPurifier_Config
- */
- private $config;
-
- /**
- * @type HTMLPurifier_AttrValidator
- */
- private $attrValidator;
-
- /**
- * @type bool
- */
- private $removeNbsp;
-
- /**
- * @type bool
- */
- private $removeNbspExceptions;
-
- /**
- * @type array
- * TODO: make me configurable
- */
- private $_exclude = array('colgroup' => 1, 'th' => 1, 'td' => 1, 'iframe' => 1);
-
- /**
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return void
- */
- public function prepare($config, $context)
- {
- parent::prepare($config, $context);
- $this->config = $config;
- $this->context = $context;
- $this->removeNbsp = $config->get('AutoFormat.RemoveEmpty.RemoveNbsp');
- $this->removeNbspExceptions = $config->get('AutoFormat.RemoveEmpty.RemoveNbsp.Exceptions');
- $this->attrValidator = new HTMLPurifier_AttrValidator();
- }
-
- /**
- * @param HTMLPurifier_Token $token
- */
- public function handleElement(&$token)
- {
- if (!$token instanceof HTMLPurifier_Token_Start) {
- return;
- }
- $next = false;
- $deleted = 1; // the current tag
- for ($i = count($this->inputZipper->back) - 1; $i >= 0; $i--, $deleted++) {
- $next = $this->inputZipper->back[$i];
- if ($next instanceof HTMLPurifier_Token_Text) {
- if ($next->is_whitespace) {
- continue;
- }
- if ($this->removeNbsp && !isset($this->removeNbspExceptions[$token->name])) {
- $plain = str_replace("\xC2\xA0", "", $next->data);
- $isWsOrNbsp = $plain === '' || ctype_space($plain);
- if ($isWsOrNbsp) {
- continue;
- }
- }
- }
- break;
- }
- if (!$next || ($next instanceof HTMLPurifier_Token_End && $next->name == $token->name)) {
- if (isset($this->_exclude[$token->name])) {
- return;
- }
- $this->attrValidator->validateToken($token, $this->config, $this->context);
- $token->armor['ValidateAttributes'] = true;
- if (isset($token->attr['id']) || isset($token->attr['name'])) {
- return;
- }
- $token = $deleted + 1;
- for ($b = 0, $c = count($this->inputZipper->front); $b < $c; $b++) {
- $prev = $this->inputZipper->front[$b];
- if ($prev instanceof HTMLPurifier_Token_Text && $prev->is_whitespace) {
- continue;
- }
- break;
- }
- // This is safe because we removed the token that triggered this.
- $this->rewindOffset($b+$deleted);
- return;
- }
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/Injector/SafeObject.php b/library/HTMLPurifier/Injector/SafeObject.php
deleted file mode 100644
index 3d17e07af..000000000
--- a/library/HTMLPurifier/Injector/SafeObject.php
+++ /dev/null
@@ -1,121 +0,0 @@
-<?php
-
-/**
- * Adds important param elements to inside of object in order to make
- * things safe.
- */
-class HTMLPurifier_Injector_SafeObject extends HTMLPurifier_Injector
-{
- /**
- * @type string
- */
- public $name = 'SafeObject';
-
- /**
- * @type array
- */
- public $needed = array('object', 'param');
-
- /**
- * @type array
- */
- protected $objectStack = array();
-
- /**
- * @type array
- */
- protected $paramStack = array();
-
- /**
- * Keep this synchronized with AttrTransform/SafeParam.php.
- * @type array
- */
- protected $addParam = array(
- 'allowScriptAccess' => 'never',
- 'allowNetworking' => 'internal',
- );
-
- /**
- * @type array
- */
- protected $allowedParam = array(
- 'wmode' => true,
- 'movie' => true,
- 'flashvars' => true,
- 'src' => true,
- 'allowFullScreen' => true, // if omitted, assume to be 'false'
- );
-
- /**
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return void
- */
- public function prepare($config, $context)
- {
- parent::prepare($config, $context);
- }
-
- /**
- * @param HTMLPurifier_Token $token
- */
- public function handleElement(&$token)
- {
- if ($token->name == 'object') {
- $this->objectStack[] = $token;
- $this->paramStack[] = array();
- $new = array($token);
- foreach ($this->addParam as $name => $value) {
- $new[] = new HTMLPurifier_Token_Empty('param', array('name' => $name, 'value' => $value));
- }
- $token = $new;
- } elseif ($token->name == 'param') {
- $nest = count($this->currentNesting) - 1;
- if ($nest >= 0 && $this->currentNesting[$nest]->name === 'object') {
- $i = count($this->objectStack) - 1;
- if (!isset($token->attr['name'])) {
- $token = false;
- return;
- }
- $n = $token->attr['name'];
- // We need this fix because YouTube doesn't supply a data
- // attribute, which we need if a type is specified. This is
- // *very* Flash specific.
- if (!isset($this->objectStack[$i]->attr['data']) &&
- ($token->attr['name'] == 'movie' || $token->attr['name'] == 'src')
- ) {
- $this->objectStack[$i]->attr['data'] = $token->attr['value'];
- }
- // Check if the parameter is the correct value but has not
- // already been added
- if (!isset($this->paramStack[$i][$n]) &&
- isset($this->addParam[$n]) &&
- $token->attr['name'] === $this->addParam[$n]) {
- // keep token, and add to param stack
- $this->paramStack[$i][$n] = true;
- } elseif (isset($this->allowedParam[$n])) {
- // keep token, don't do anything to it
- // (could possibly check for duplicates here)
- } else {
- $token = false;
- }
- } else {
- // not directly inside an object, DENY!
- $token = false;
- }
- }
- }
-
- public function handleEnd(&$token)
- {
- // This is the WRONG way of handling the object and param stacks;
- // we should be inserting them directly on the relevant object tokens
- // so that the global stack handling handles it.
- if ($token->name == 'object') {
- array_pop($this->objectStack);
- array_pop($this->paramStack);
- }
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/Lexer.php b/library/HTMLPurifier/Lexer.php
deleted file mode 100644
index 43732621d..000000000
--- a/library/HTMLPurifier/Lexer.php
+++ /dev/null
@@ -1,357 +0,0 @@
-<?php
-
-/**
- * Forgivingly lexes HTML (SGML-style) markup into tokens.
- *
- * A lexer parses a string of SGML-style markup and converts them into
- * corresponding tokens. It doesn't check for well-formedness, although its
- * internal mechanism may make this automatic (such as the case of
- * HTMLPurifier_Lexer_DOMLex). There are several implementations to choose
- * from.
- *
- * A lexer is HTML-oriented: it might work with XML, but it's not
- * recommended, as we adhere to a subset of the specification for optimization
- * reasons. This might change in the future. Also, most tokenizers are not
- * expected to handle DTDs or PIs.
- *
- * This class should not be directly instantiated, but you may use create() to
- * retrieve a default copy of the lexer. Being a supertype, this class
- * does not actually define any implementation, but offers commonly used
- * convenience functions for subclasses.
- *
- * @note The unit tests will instantiate this class for testing purposes, as
- * many of the utility functions require a class to be instantiated.
- * This means that, even though this class is not runnable, it will
- * not be declared abstract.
- *
- * @par
- *
- * @note
- * We use tokens rather than create a DOM representation because DOM would:
- *
- * @par
- * -# Require more processing and memory to create,
- * -# Is not streamable, and
- * -# Has the entire document structure (html and body not needed).
- *
- * @par
- * However, DOM is helpful in that it makes it easy to move around nodes
- * without a lot of lookaheads to see when a tag is closed. This is a
- * limitation of the token system and some workarounds would be nice.
- */
-class HTMLPurifier_Lexer
-{
-
- /**
- * Whether or not this lexer implements line-number/column-number tracking.
- * If it does, set to true.
- */
- public $tracksLineNumbers = false;
-
- // -- STATIC ----------------------------------------------------------
-
- /**
- * Retrieves or sets the default Lexer as a Prototype Factory.
- *
- * By default HTMLPurifier_Lexer_DOMLex will be returned. There are
- * a few exceptions involving special features that only DirectLex
- * implements.
- *
- * @note The behavior of this class has changed, rather than accepting
- * a prototype object, it now accepts a configuration object.
- * To specify your own prototype, set %Core.LexerImpl to it.
- * This change in behavior de-singletonizes the lexer object.
- *
- * @param HTMLPurifier_Config $config
- * @return HTMLPurifier_Lexer
- * @throws HTMLPurifier_Exception
- */
- public static function create($config)
- {
- if (!($config instanceof HTMLPurifier_Config)) {
- $lexer = $config;
- trigger_error(
- "Passing a prototype to
- HTMLPurifier_Lexer::create() is deprecated, please instead
- use %Core.LexerImpl",
- E_USER_WARNING
- );
- } else {
- $lexer = $config->get('Core.LexerImpl');
- }
-
- $needs_tracking =
- $config->get('Core.MaintainLineNumbers') ||
- $config->get('Core.CollectErrors');
-
- $inst = null;
- if (is_object($lexer)) {
- $inst = $lexer;
- } else {
- if (is_null($lexer)) {
- do {
- // auto-detection algorithm
- if ($needs_tracking) {
- $lexer = 'DirectLex';
- break;
- }
-
- if (class_exists('DOMDocument') &&
- method_exists('DOMDocument', 'loadHTML') &&
- !extension_loaded('domxml')
- ) {
- // check for DOM support, because while it's part of the
- // core, it can be disabled compile time. Also, the PECL
- // domxml extension overrides the default DOM, and is evil
- // and nasty and we shan't bother to support it
- $lexer = 'DOMLex';
- } else {
- $lexer = 'DirectLex';
- }
- } while (0);
- } // do..while so we can break
-
- // instantiate recognized string names
- switch ($lexer) {
- case 'DOMLex':
- $inst = new HTMLPurifier_Lexer_DOMLex();
- break;
- case 'DirectLex':
- $inst = new HTMLPurifier_Lexer_DirectLex();
- break;
- case 'PH5P':
- $inst = new HTMLPurifier_Lexer_PH5P();
- break;
- default:
- throw new HTMLPurifier_Exception(
- "Cannot instantiate unrecognized Lexer type " .
- htmlspecialchars($lexer)
- );
- }
- }
-
- if (!$inst) {
- throw new HTMLPurifier_Exception('No lexer was instantiated');
- }
-
- // once PHP DOM implements native line numbers, or we
- // hack out something using XSLT, remove this stipulation
- if ($needs_tracking && !$inst->tracksLineNumbers) {
- throw new HTMLPurifier_Exception(
- 'Cannot use lexer that does not support line numbers with ' .
- 'Core.MaintainLineNumbers or Core.CollectErrors (use DirectLex instead)'
- );
- }
-
- return $inst;
-
- }
-
- // -- CONVENIENCE MEMBERS ---------------------------------------------
-
- public function __construct()
- {
- $this->_entity_parser = new HTMLPurifier_EntityParser();
- }
-
- /**
- * Most common entity to raw value conversion table for special entities.
- * @type array
- */
- protected $_special_entity2str =
- array(
- '&quot;' => '"',
- '&amp;' => '&',
- '&lt;' => '<',
- '&gt;' => '>',
- '&#39;' => "'",
- '&#039;' => "'",
- '&#x27;' => "'"
- );
-
- /**
- * Parses special entities into the proper characters.
- *
- * This string will translate escaped versions of the special characters
- * into the correct ones.
- *
- * @warning
- * You should be able to treat the output of this function as
- * completely parsed, but that's only because all other entities should
- * have been handled previously in substituteNonSpecialEntities()
- *
- * @param string $string String character data to be parsed.
- * @return string Parsed character data.
- */
- public function parseData($string)
- {
- // following functions require at least one character
- if ($string === '') {
- return '';
- }
-
- // subtracts amps that cannot possibly be escaped
- $num_amp = substr_count($string, '&') - substr_count($string, '& ') -
- ($string[strlen($string) - 1] === '&' ? 1 : 0);
-
- if (!$num_amp) {
- return $string;
- } // abort if no entities
- $num_esc_amp = substr_count($string, '&amp;');
- $string = strtr($string, $this->_special_entity2str);
-
- // code duplication for sake of optimization, see above
- $num_amp_2 = substr_count($string, '&') - substr_count($string, '& ') -
- ($string[strlen($string) - 1] === '&' ? 1 : 0);
-
- if ($num_amp_2 <= $num_esc_amp) {
- return $string;
- }
-
- // hmm... now we have some uncommon entities. Use the callback.
- $string = $this->_entity_parser->substituteSpecialEntities($string);
- return $string;
- }
-
- /**
- * Lexes an HTML string into tokens.
- * @param $string String HTML.
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return HTMLPurifier_Token[] array representation of HTML.
- */
- public function tokenizeHTML($string, $config, $context)
- {
- trigger_error('Call to abstract class', E_USER_ERROR);
- }
-
- /**
- * Translates CDATA sections into regular sections (through escaping).
- * @param string $string HTML string to process.
- * @return string HTML with CDATA sections escaped.
- */
- protected static function escapeCDATA($string)
- {
- return preg_replace_callback(
- '/<!\[CDATA\[(.+?)\]\]>/s',
- array('HTMLPurifier_Lexer', 'CDATACallback'),
- $string
- );
- }
-
- /**
- * Special CDATA case that is especially convoluted for <script>
- * @param string $string HTML string to process.
- * @return string HTML with CDATA sections escaped.
- */
- protected static function escapeCommentedCDATA($string)
- {
- return preg_replace_callback(
- '#<!--//--><!\[CDATA\[//><!--(.+?)//--><!\]\]>#s',
- array('HTMLPurifier_Lexer', 'CDATACallback'),
- $string
- );
- }
-
- /**
- * Special Internet Explorer conditional comments should be removed.
- * @param string $string HTML string to process.
- * @return string HTML with conditional comments removed.
- */
- protected static function removeIEConditional($string)
- {
- return preg_replace(
- '#<!--\[if [^>]+\]>.*?<!\[endif\]-->#si', // probably should generalize for all strings
- '',
- $string
- );
- }
-
- /**
- * Callback function for escapeCDATA() that does the work.
- *
- * @warning Though this is public in order to let the callback happen,
- * calling it directly is not recommended.
- * @param array $matches PCRE matches array, with index 0 the entire match
- * and 1 the inside of the CDATA section.
- * @return string Escaped internals of the CDATA section.
- */
- protected static function CDATACallback($matches)
- {
- // not exactly sure why the character set is needed, but whatever
- return htmlspecialchars($matches[1], ENT_COMPAT, 'UTF-8');
- }
-
- /**
- * Takes a piece of HTML and normalizes it by converting entities, fixing
- * encoding, extracting bits, and other good stuff.
- * @param string $html HTML.
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return string
- * @todo Consider making protected
- */
- public function normalize($html, $config, $context)
- {
- // normalize newlines to \n
- if ($config->get('Core.NormalizeNewlines')) {
- $html = str_replace("\r\n", "\n", $html);
- $html = str_replace("\r", "\n", $html);
- }
-
- if ($config->get('HTML.Trusted')) {
- // escape convoluted CDATA
- $html = $this->escapeCommentedCDATA($html);
- }
-
- // escape CDATA
- $html = $this->escapeCDATA($html);
-
- $html = $this->removeIEConditional($html);
-
- // extract body from document if applicable
- if ($config->get('Core.ConvertDocumentToFragment')) {
- $e = false;
- if ($config->get('Core.CollectErrors')) {
- $e =& $context->get('ErrorCollector');
- }
- $new_html = $this->extractBody($html);
- if ($e && $new_html != $html) {
- $e->send(E_WARNING, 'Lexer: Extracted body');
- }
- $html = $new_html;
- }
-
- // expand entities that aren't the big five
- $html = $this->_entity_parser->substituteNonSpecialEntities($html);
-
- // clean into wellformed UTF-8 string for an SGML context: this has
- // to be done after entity expansion because the entities sometimes
- // represent non-SGML characters (horror, horror!)
- $html = HTMLPurifier_Encoder::cleanUTF8($html);
-
- // if processing instructions are to removed, remove them now
- if ($config->get('Core.RemoveProcessingInstructions')) {
- $html = preg_replace('#<\?.+?\?>#s', '', $html);
- }
-
- return $html;
- }
-
- /**
- * Takes a string of HTML (fragment or document) and returns the content
- * @todo Consider making protected
- */
- public function extractBody($html)
- {
- $matches = array();
- $result = preg_match('!<body[^>]*>(.*)</body>!is', $html, $matches);
- if ($result) {
- return $matches[1];
- } else {
- return $html;
- }
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/Lexer/DOMLex.php b/library/HTMLPurifier/Lexer/DOMLex.php
deleted file mode 100644
index 720754454..000000000
--- a/library/HTMLPurifier/Lexer/DOMLex.php
+++ /dev/null
@@ -1,280 +0,0 @@
-<?php
-
-/**
- * Parser that uses PHP 5's DOM extension (part of the core).
- *
- * In PHP 5, the DOM XML extension was revamped into DOM and added to the core.
- * It gives us a forgiving HTML parser, which we use to transform the HTML
- * into a DOM, and then into the tokens. It is blazingly fast (for large
- * documents, it performs twenty times faster than
- * HTMLPurifier_Lexer_DirectLex,and is the default choice for PHP 5.
- *
- * @note Any empty elements will have empty tokens associated with them, even if
- * this is prohibited by the spec. This is cannot be fixed until the spec
- * comes into play.
- *
- * @note PHP's DOM extension does not actually parse any entities, we use
- * our own function to do that.
- *
- * @warning DOM tends to drop whitespace, which may wreak havoc on indenting.
- * If this is a huge problem, due to the fact that HTML is hand
- * edited and you are unable to get a parser cache that caches the
- * the output of HTML Purifier while keeping the original HTML lying
- * around, you may want to run Tidy on the resulting output or use
- * HTMLPurifier_DirectLex
- */
-
-class HTMLPurifier_Lexer_DOMLex extends HTMLPurifier_Lexer
-{
-
- /**
- * @type HTMLPurifier_TokenFactory
- */
- private $factory;
-
- public function __construct()
- {
- // setup the factory
- parent::__construct();
- $this->factory = new HTMLPurifier_TokenFactory();
- }
-
- /**
- * @param string $html
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return HTMLPurifier_Token[]
- */
- public function tokenizeHTML($html, $config, $context)
- {
- $html = $this->normalize($html, $config, $context);
-
- // attempt to armor stray angled brackets that cannot possibly
- // form tags and thus are probably being used as emoticons
- if ($config->get('Core.AggressivelyFixLt')) {
- $char = '[^a-z!\/]';
- $comment = "/<!--(.*?)(-->|\z)/is";
- $html = preg_replace_callback($comment, array($this, 'callbackArmorCommentEntities'), $html);
- do {
- $old = $html;
- $html = preg_replace("/<($char)/i", '&lt;\\1', $html);
- } while ($html !== $old);
- $html = preg_replace_callback($comment, array($this, 'callbackUndoCommentSubst'), $html); // fix comments
- }
-
- // preprocess html, essential for UTF-8
- $html = $this->wrapHTML($html, $config, $context);
-
- $doc = new DOMDocument();
- $doc->encoding = 'UTF-8'; // theoretically, the above has this covered
-
- set_error_handler(array($this, 'muteErrorHandler'));
- $doc->loadHTML($html);
- restore_error_handler();
-
- $tokens = array();
- $this->tokenizeDOM(
- $doc->getElementsByTagName('html')->item(0)-> // <html>
- getElementsByTagName('body')->item(0)-> // <body>
- getElementsByTagName('div')->item(0), // <div>
- $tokens
- );
- return $tokens;
- }
-
- /**
- * Iterative function that tokenizes a node, putting it into an accumulator.
- * To iterate is human, to recurse divine - L. Peter Deutsch
- * @param DOMNode $node DOMNode to be tokenized.
- * @param HTMLPurifier_Token[] $tokens Array-list of already tokenized tokens.
- * @return HTMLPurifier_Token of node appended to previously passed tokens.
- */
- protected function tokenizeDOM($node, &$tokens)
- {
- $level = 0;
- $nodes = array($level => new HTMLPurifier_Queue(array($node)));
- $closingNodes = array();
- do {
- while (!$nodes[$level]->isEmpty()) {
- $node = $nodes[$level]->shift(); // FIFO
- $collect = $level > 0 ? true : false;
- $needEndingTag = $this->createStartNode($node, $tokens, $collect);
- if ($needEndingTag) {
- $closingNodes[$level][] = $node;
- }
- if ($node->childNodes && $node->childNodes->length) {
- $level++;
- $nodes[$level] = new HTMLPurifier_Queue();
- foreach ($node->childNodes as $childNode) {
- $nodes[$level]->push($childNode);
- }
- }
- }
- $level--;
- if ($level && isset($closingNodes[$level])) {
- while ($node = array_pop($closingNodes[$level])) {
- $this->createEndNode($node, $tokens);
- }
- }
- } while ($level > 0);
- }
-
- /**
- * @param DOMNode $node DOMNode to be tokenized.
- * @param HTMLPurifier_Token[] $tokens Array-list of already tokenized tokens.
- * @param bool $collect Says whether or start and close are collected, set to
- * false at first recursion because it's the implicit DIV
- * tag you're dealing with.
- * @return bool if the token needs an endtoken
- * @todo data and tagName properties don't seem to exist in DOMNode?
- */
- protected function createStartNode($node, &$tokens, $collect)
- {
- // intercept non element nodes. WE MUST catch all of them,
- // but we're not getting the character reference nodes because
- // those should have been preprocessed
- if ($node->nodeType === XML_TEXT_NODE) {
- $tokens[] = $this->factory->createText($node->data);
- return false;
- } elseif ($node->nodeType === XML_CDATA_SECTION_NODE) {
- // undo libxml's special treatment of <script> and <style> tags
- $last = end($tokens);
- $data = $node->data;
- // (note $node->tagname is already normalized)
- if ($last instanceof HTMLPurifier_Token_Start && ($last->name == 'script' || $last->name == 'style')) {
- $new_data = trim($data);
- if (substr($new_data, 0, 4) === '<!--') {
- $data = substr($new_data, 4);
- if (substr($data, -3) === '-->') {
- $data = substr($data, 0, -3);
- } else {
- // Highly suspicious! Not sure what to do...
- }
- }
- }
- $tokens[] = $this->factory->createText($this->parseData($data));
- return false;
- } elseif ($node->nodeType === XML_COMMENT_NODE) {
- // this is code is only invoked for comments in script/style in versions
- // of libxml pre-2.6.28 (regular comments, of course, are still
- // handled regularly)
- $tokens[] = $this->factory->createComment($node->data);
- return false;
- } elseif ($node->nodeType !== XML_ELEMENT_NODE) {
- // not-well tested: there may be other nodes we have to grab
- return false;
- }
-
- $attr = $node->hasAttributes() ? $this->transformAttrToAssoc($node->attributes) : array();
-
- // We still have to make sure that the element actually IS empty
- if (!$node->childNodes->length) {
- if ($collect) {
- $tokens[] = $this->factory->createEmpty($node->tagName, $attr);
- }
- return false;
- } else {
- if ($collect) {
- $tokens[] = $this->factory->createStart(
- $tag_name = $node->tagName, // somehow, it get's dropped
- $attr
- );
- }
- return true;
- }
- }
-
- /**
- * @param DOMNode $node
- * @param HTMLPurifier_Token[] $tokens
- */
- protected function createEndNode($node, &$tokens)
- {
- $tokens[] = $this->factory->createEnd($node->tagName);
- }
-
-
- /**
- * Converts a DOMNamedNodeMap of DOMAttr objects into an assoc array.
- *
- * @param DOMNamedNodeMap $node_map DOMNamedNodeMap of DOMAttr objects.
- * @return array Associative array of attributes.
- */
- protected function transformAttrToAssoc($node_map)
- {
- // NamedNodeMap is documented very well, so we're using undocumented
- // features, namely, the fact that it implements Iterator and
- // has a ->length attribute
- if ($node_map->length === 0) {
- return array();
- }
- $array = array();
- foreach ($node_map as $attr) {
- $array[$attr->name] = $attr->value;
- }
- return $array;
- }
-
- /**
- * An error handler that mutes all errors
- * @param int $errno
- * @param string $errstr
- */
- public function muteErrorHandler($errno, $errstr)
- {
- }
-
- /**
- * Callback function for undoing escaping of stray angled brackets
- * in comments
- * @param array $matches
- * @return string
- */
- public function callbackUndoCommentSubst($matches)
- {
- return '<!--' . strtr($matches[1], array('&amp;' => '&', '&lt;' => '<')) . $matches[2];
- }
-
- /**
- * Callback function that entity-izes ampersands in comments so that
- * callbackUndoCommentSubst doesn't clobber them
- * @param array $matches
- * @return string
- */
- public function callbackArmorCommentEntities($matches)
- {
- return '<!--' . str_replace('&', '&amp;', $matches[1]) . $matches[2];
- }
-
- /**
- * Wraps an HTML fragment in the necessary HTML
- * @param string $html
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return string
- */
- protected function wrapHTML($html, $config, $context)
- {
- $def = $config->getDefinition('HTML');
- $ret = '';
-
- if (!empty($def->doctype->dtdPublic) || !empty($def->doctype->dtdSystem)) {
- $ret .= '<!DOCTYPE html ';
- if (!empty($def->doctype->dtdPublic)) {
- $ret .= 'PUBLIC "' . $def->doctype->dtdPublic . '" ';
- }
- if (!empty($def->doctype->dtdSystem)) {
- $ret .= '"' . $def->doctype->dtdSystem . '" ';
- }
- $ret .= '>';
- }
-
- $ret .= '<html><head>';
- $ret .= '<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />';
- // No protection if $html contains a stray </div>!
- $ret .= '</head><body><div>' . $html . '</div></body></html>';
- return $ret;
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/Lexer/DirectLex.php b/library/HTMLPurifier/Lexer/DirectLex.php
deleted file mode 100644
index 746b6e315..000000000
--- a/library/HTMLPurifier/Lexer/DirectLex.php
+++ /dev/null
@@ -1,539 +0,0 @@
-<?php
-
-/**
- * Our in-house implementation of a parser.
- *
- * A pure PHP parser, DirectLex has absolutely no dependencies, making
- * it a reasonably good default for PHP4. Written with efficiency in mind,
- * it can be four times faster than HTMLPurifier_Lexer_PEARSax3, although it
- * pales in comparison to HTMLPurifier_Lexer_DOMLex.
- *
- * @todo Reread XML spec and document differences.
- */
-class HTMLPurifier_Lexer_DirectLex extends HTMLPurifier_Lexer
-{
- /**
- * @type bool
- */
- public $tracksLineNumbers = true;
-
- /**
- * Whitespace characters for str(c)spn.
- * @type string
- */
- protected $_whitespace = "\x20\x09\x0D\x0A";
-
- /**
- * Callback function for script CDATA fudge
- * @param array $matches, in form of array(opening tag, contents, closing tag)
- * @return string
- */
- protected function scriptCallback($matches)
- {
- return $matches[1] . htmlspecialchars($matches[2], ENT_COMPAT, 'UTF-8') . $matches[3];
- }
-
- /**
- * @param String $html
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return array|HTMLPurifier_Token[]
- */
- public function tokenizeHTML($html, $config, $context)
- {
- // special normalization for script tags without any armor
- // our "armor" heurstic is a < sign any number of whitespaces after
- // the first script tag
- if ($config->get('HTML.Trusted')) {
- $html = preg_replace_callback(
- '#(<script[^>]*>)(\s*[^<].+?)(</script>)#si',
- array($this, 'scriptCallback'),
- $html
- );
- }
-
- $html = $this->normalize($html, $config, $context);
-
- $cursor = 0; // our location in the text
- $inside_tag = false; // whether or not we're parsing the inside of a tag
- $array = array(); // result array
-
- // This is also treated to mean maintain *column* numbers too
- $maintain_line_numbers = $config->get('Core.MaintainLineNumbers');
-
- if ($maintain_line_numbers === null) {
- // automatically determine line numbering by checking
- // if error collection is on
- $maintain_line_numbers = $config->get('Core.CollectErrors');
- }
-
- if ($maintain_line_numbers) {
- $current_line = 1;
- $current_col = 0;
- $length = strlen($html);
- } else {
- $current_line = false;
- $current_col = false;
- $length = false;
- }
- $context->register('CurrentLine', $current_line);
- $context->register('CurrentCol', $current_col);
- $nl = "\n";
- // how often to manually recalculate. This will ALWAYS be right,
- // but it's pretty wasteful. Set to 0 to turn off
- $synchronize_interval = $config->get('Core.DirectLexLineNumberSyncInterval');
-
- $e = false;
- if ($config->get('Core.CollectErrors')) {
- $e =& $context->get('ErrorCollector');
- }
-
- // for testing synchronization
- $loops = 0;
-
- while (++$loops) {
- // $cursor is either at the start of a token, or inside of
- // a tag (i.e. there was a < immediately before it), as indicated
- // by $inside_tag
-
- if ($maintain_line_numbers) {
- // $rcursor, however, is always at the start of a token.
- $rcursor = $cursor - (int)$inside_tag;
-
- // Column number is cheap, so we calculate it every round.
- // We're interested at the *end* of the newline string, so
- // we need to add strlen($nl) == 1 to $nl_pos before subtracting it
- // from our "rcursor" position.
- $nl_pos = strrpos($html, $nl, $rcursor - $length);
- $current_col = $rcursor - (is_bool($nl_pos) ? 0 : $nl_pos + 1);
-
- // recalculate lines
- if ($synchronize_interval && // synchronization is on
- $cursor > 0 && // cursor is further than zero
- $loops % $synchronize_interval === 0) { // time to synchronize!
- $current_line = 1 + $this->substrCount($html, $nl, 0, $cursor);
- }
- }
-
- $position_next_lt = strpos($html, '<', $cursor);
- $position_next_gt = strpos($html, '>', $cursor);
-
- // triggers on "<b>asdf</b>" but not "asdf <b></b>"
- // special case to set up context
- if ($position_next_lt === $cursor) {
- $inside_tag = true;
- $cursor++;
- }
-
- if (!$inside_tag && $position_next_lt !== false) {
- // We are not inside tag and there still is another tag to parse
- $token = new
- HTMLPurifier_Token_Text(
- $this->parseData(
- substr(
- $html,
- $cursor,
- $position_next_lt - $cursor
- )
- )
- );
- if ($maintain_line_numbers) {
- $token->rawPosition($current_line, $current_col);
- $current_line += $this->substrCount($html, $nl, $cursor, $position_next_lt - $cursor);
- }
- $array[] = $token;
- $cursor = $position_next_lt + 1;
- $inside_tag = true;
- continue;
- } elseif (!$inside_tag) {
- // We are not inside tag but there are no more tags
- // If we're already at the end, break
- if ($cursor === strlen($html)) {
- break;
- }
- // Create Text of rest of string
- $token = new
- HTMLPurifier_Token_Text(
- $this->parseData(
- substr(
- $html,
- $cursor
- )
- )
- );
- if ($maintain_line_numbers) {
- $token->rawPosition($current_line, $current_col);
- }
- $array[] = $token;
- break;
- } elseif ($inside_tag && $position_next_gt !== false) {
- // We are in tag and it is well formed
- // Grab the internals of the tag
- $strlen_segment = $position_next_gt - $cursor;
-
- if ($strlen_segment < 1) {
- // there's nothing to process!
- $token = new HTMLPurifier_Token_Text('<');
- $cursor++;
- continue;
- }
-
- $segment = substr($html, $cursor, $strlen_segment);
-
- if ($segment === false) {
- // somehow, we attempted to access beyond the end of
- // the string, defense-in-depth, reported by Nate Abele
- break;
- }
-
- // Check if it's a comment
- if (substr($segment, 0, 3) === '!--') {
- // re-determine segment length, looking for -->
- $position_comment_end = strpos($html, '-->', $cursor);
- if ($position_comment_end === false) {
- // uh oh, we have a comment that extends to
- // infinity. Can't be helped: set comment
- // end position to end of string
- if ($e) {
- $e->send(E_WARNING, 'Lexer: Unclosed comment');
- }
- $position_comment_end = strlen($html);
- $end = true;
- } else {
- $end = false;
- }
- $strlen_segment = $position_comment_end - $cursor;
- $segment = substr($html, $cursor, $strlen_segment);
- $token = new
- HTMLPurifier_Token_Comment(
- substr(
- $segment,
- 3,
- $strlen_segment - 3
- )
- );
- if ($maintain_line_numbers) {
- $token->rawPosition($current_line, $current_col);
- $current_line += $this->substrCount($html, $nl, $cursor, $strlen_segment);
- }
- $array[] = $token;
- $cursor = $end ? $position_comment_end : $position_comment_end + 3;
- $inside_tag = false;
- continue;
- }
-
- // Check if it's an end tag
- $is_end_tag = (strpos($segment, '/') === 0);
- if ($is_end_tag) {
- $type = substr($segment, 1);
- $token = new HTMLPurifier_Token_End($type);
- if ($maintain_line_numbers) {
- $token->rawPosition($current_line, $current_col);
- $current_line += $this->substrCount($html, $nl, $cursor, $position_next_gt - $cursor);
- }
- $array[] = $token;
- $inside_tag = false;
- $cursor = $position_next_gt + 1;
- continue;
- }
-
- // Check leading character is alnum, if not, we may
- // have accidently grabbed an emoticon. Translate into
- // text and go our merry way
- if (!ctype_alpha($segment[0])) {
- // XML: $segment[0] !== '_' && $segment[0] !== ':'
- if ($e) {
- $e->send(E_NOTICE, 'Lexer: Unescaped lt');
- }
- $token = new HTMLPurifier_Token_Text('<');
- if ($maintain_line_numbers) {
- $token->rawPosition($current_line, $current_col);
- $current_line += $this->substrCount($html, $nl, $cursor, $position_next_gt - $cursor);
- }
- $array[] = $token;
- $inside_tag = false;
- continue;
- }
-
- // Check if it is explicitly self closing, if so, remove
- // trailing slash. Remember, we could have a tag like <br>, so
- // any later token processing scripts must convert improperly
- // classified EmptyTags from StartTags.
- $is_self_closing = (strrpos($segment, '/') === $strlen_segment - 1);
- if ($is_self_closing) {
- $strlen_segment--;
- $segment = substr($segment, 0, $strlen_segment);
- }
-
- // Check if there are any attributes
- $position_first_space = strcspn($segment, $this->_whitespace);
-
- if ($position_first_space >= $strlen_segment) {
- if ($is_self_closing) {
- $token = new HTMLPurifier_Token_Empty($segment);
- } else {
- $token = new HTMLPurifier_Token_Start($segment);
- }
- if ($maintain_line_numbers) {
- $token->rawPosition($current_line, $current_col);
- $current_line += $this->substrCount($html, $nl, $cursor, $position_next_gt - $cursor);
- }
- $array[] = $token;
- $inside_tag = false;
- $cursor = $position_next_gt + 1;
- continue;
- }
-
- // Grab out all the data
- $type = substr($segment, 0, $position_first_space);
- $attribute_string =
- trim(
- substr(
- $segment,
- $position_first_space
- )
- );
- if ($attribute_string) {
- $attr = $this->parseAttributeString(
- $attribute_string,
- $config,
- $context
- );
- } else {
- $attr = array();
- }
-
- if ($is_self_closing) {
- $token = new HTMLPurifier_Token_Empty($type, $attr);
- } else {
- $token = new HTMLPurifier_Token_Start($type, $attr);
- }
- if ($maintain_line_numbers) {
- $token->rawPosition($current_line, $current_col);
- $current_line += $this->substrCount($html, $nl, $cursor, $position_next_gt - $cursor);
- }
- $array[] = $token;
- $cursor = $position_next_gt + 1;
- $inside_tag = false;
- continue;
- } else {
- // inside tag, but there's no ending > sign
- if ($e) {
- $e->send(E_WARNING, 'Lexer: Missing gt');
- }
- $token = new
- HTMLPurifier_Token_Text(
- '<' .
- $this->parseData(
- substr($html, $cursor)
- )
- );
- if ($maintain_line_numbers) {
- $token->rawPosition($current_line, $current_col);
- }
- // no cursor scroll? Hmm...
- $array[] = $token;
- break;
- }
- break;
- }
-
- $context->destroy('CurrentLine');
- $context->destroy('CurrentCol');
- return $array;
- }
-
- /**
- * PHP 5.0.x compatible substr_count that implements offset and length
- * @param string $haystack
- * @param string $needle
- * @param int $offset
- * @param int $length
- * @return int
- */
- protected function substrCount($haystack, $needle, $offset, $length)
- {
- static $oldVersion;
- if ($oldVersion === null) {
- $oldVersion = version_compare(PHP_VERSION, '5.1', '<');
- }
- if ($oldVersion) {
- $haystack = substr($haystack, $offset, $length);
- return substr_count($haystack, $needle);
- } else {
- return substr_count($haystack, $needle, $offset, $length);
- }
- }
-
- /**
- * Takes the inside of an HTML tag and makes an assoc array of attributes.
- *
- * @param string $string Inside of tag excluding name.
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return array Assoc array of attributes.
- */
- public function parseAttributeString($string, $config, $context)
- {
- $string = (string)$string; // quick typecast
-
- if ($string == '') {
- return array();
- } // no attributes
-
- $e = false;
- if ($config->get('Core.CollectErrors')) {
- $e =& $context->get('ErrorCollector');
- }
-
- // let's see if we can abort as quickly as possible
- // one equal sign, no spaces => one attribute
- $num_equal = substr_count($string, '=');
- $has_space = strpos($string, ' ');
- if ($num_equal === 0 && !$has_space) {
- // bool attribute
- return array($string => $string);
- } elseif ($num_equal === 1 && !$has_space) {
- // only one attribute
- list($key, $quoted_value) = explode('=', $string);
- $quoted_value = trim($quoted_value);
- if (!$key) {
- if ($e) {
- $e->send(E_ERROR, 'Lexer: Missing attribute key');
- }
- return array();
- }
- if (!$quoted_value) {
- return array($key => '');
- }
- $first_char = @$quoted_value[0];
- $last_char = @$quoted_value[strlen($quoted_value) - 1];
-
- $same_quote = ($first_char == $last_char);
- $open_quote = ($first_char == '"' || $first_char == "'");
-
- if ($same_quote && $open_quote) {
- // well behaved
- $value = substr($quoted_value, 1, strlen($quoted_value) - 2);
- } else {
- // not well behaved
- if ($open_quote) {
- if ($e) {
- $e->send(E_ERROR, 'Lexer: Missing end quote');
- }
- $value = substr($quoted_value, 1);
- } else {
- $value = $quoted_value;
- }
- }
- if ($value === false) {
- $value = '';
- }
- return array($key => $this->parseData($value));
- }
-
- // setup loop environment
- $array = array(); // return assoc array of attributes
- $cursor = 0; // current position in string (moves forward)
- $size = strlen($string); // size of the string (stays the same)
-
- // if we have unquoted attributes, the parser expects a terminating
- // space, so let's guarantee that there's always a terminating space.
- $string .= ' ';
-
- $old_cursor = -1;
- while ($cursor < $size) {
- if ($old_cursor >= $cursor) {
- throw new Exception("Infinite loop detected");
- }
- $old_cursor = $cursor;
-
- $cursor += ($value = strspn($string, $this->_whitespace, $cursor));
- // grab the key
-
- $key_begin = $cursor; //we're currently at the start of the key
-
- // scroll past all characters that are the key (not whitespace or =)
- $cursor += strcspn($string, $this->_whitespace . '=', $cursor);
-
- $key_end = $cursor; // now at the end of the key
-
- $key = substr($string, $key_begin, $key_end - $key_begin);
-
- if (!$key) {
- if ($e) {
- $e->send(E_ERROR, 'Lexer: Missing attribute key');
- }
- $cursor += 1 + strcspn($string, $this->_whitespace, $cursor + 1); // prevent infinite loop
- continue; // empty key
- }
-
- // scroll past all whitespace
- $cursor += strspn($string, $this->_whitespace, $cursor);
-
- if ($cursor >= $size) {
- $array[$key] = $key;
- break;
- }
-
- // if the next character is an equal sign, we've got a regular
- // pair, otherwise, it's a bool attribute
- $first_char = @$string[$cursor];
-
- if ($first_char == '=') {
- // key="value"
-
- $cursor++;
- $cursor += strspn($string, $this->_whitespace, $cursor);
-
- if ($cursor === false) {
- $array[$key] = '';
- break;
- }
-
- // we might be in front of a quote right now
-
- $char = @$string[$cursor];
-
- if ($char == '"' || $char == "'") {
- // it's quoted, end bound is $char
- $cursor++;
- $value_begin = $cursor;
- $cursor = strpos($string, $char, $cursor);
- $value_end = $cursor;
- } else {
- // it's not quoted, end bound is whitespace
- $value_begin = $cursor;
- $cursor += strcspn($string, $this->_whitespace, $cursor);
- $value_end = $cursor;
- }
-
- // we reached a premature end
- if ($cursor === false) {
- $cursor = $size;
- $value_end = $cursor;
- }
-
- $value = substr($string, $value_begin, $value_end - $value_begin);
- if ($value === false) {
- $value = '';
- }
- $array[$key] = $this->parseData($value);
- $cursor++;
- } else {
- // boolattr
- if ($key !== '') {
- $array[$key] = $key;
- } else {
- // purely theoretical
- if ($e) {
- $e->send(E_ERROR, 'Lexer: Missing attribute key');
- }
- }
- }
- }
- return $array;
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/Lexer/PH5P.php b/library/HTMLPurifier/Lexer/PH5P.php
deleted file mode 100644
index a4587e4cd..000000000
--- a/library/HTMLPurifier/Lexer/PH5P.php
+++ /dev/null
@@ -1,4788 +0,0 @@
-<?php
-
-/**
- * Experimental HTML5-based parser using Jeroen van der Meer's PH5P library.
- * Occupies space in the HTML5 pseudo-namespace, which may cause conflicts.
- *
- * @note
- * Recent changes to PHP's DOM extension have resulted in some fatal
- * error conditions with the original version of PH5P. Pending changes,
- * this lexer will punt to DirectLex if DOM throws an exception.
- */
-
-class HTMLPurifier_Lexer_PH5P extends HTMLPurifier_Lexer_DOMLex
-{
- /**
- * @param string $html
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return HTMLPurifier_Token[]
- */
- public function tokenizeHTML($html, $config, $context)
- {
- $new_html = $this->normalize($html, $config, $context);
- $new_html = $this->wrapHTML($new_html, $config, $context);
- try {
- $parser = new HTML5($new_html);
- $doc = $parser->save();
- } catch (DOMException $e) {
- // Uh oh, it failed. Punt to DirectLex.
- $lexer = new HTMLPurifier_Lexer_DirectLex();
- $context->register('PH5PError', $e); // save the error, so we can detect it
- return $lexer->tokenizeHTML($html, $config, $context); // use original HTML
- }
- $tokens = array();
- $this->tokenizeDOM(
- $doc->getElementsByTagName('html')->item(0)-> // <html>
- getElementsByTagName('body')->item(0)-> // <body>
- getElementsByTagName('div')->item(0) // <div>
- ,
- $tokens
- );
- return $tokens;
- }
-}
-
-/*
-
-Copyright 2007 Jeroen van der Meer <http://jero.net/>
-
-Permission is hereby granted, free of charge, to any person obtaining a
-copy of this software and associated documentation files (the
-"Software"), to deal in the Software without restriction, including
-without limitation the rights to use, copy, modify, merge, publish,
-distribute, sublicense, and/or sell copies of the Software, and to
-permit persons to whom the Software is furnished to do so, subject to
-the following conditions:
-
-The above copyright notice and this permission notice shall be included
-in all copies or substantial portions of the Software.
-
-THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
-OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
-MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
-IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
-CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
-TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
-SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
-
-*/
-
-class HTML5
-{
- private $data;
- private $char;
- private $EOF;
- private $state;
- private $tree;
- private $token;
- private $content_model;
- private $escape = false;
- private $entities = array(
- 'AElig;',
- 'AElig',
- 'AMP;',
- 'AMP',
- 'Aacute;',
- 'Aacute',
- 'Acirc;',
- 'Acirc',
- 'Agrave;',
- 'Agrave',
- 'Alpha;',
- 'Aring;',
- 'Aring',
- 'Atilde;',
- 'Atilde',
- 'Auml;',
- 'Auml',
- 'Beta;',
- 'COPY;',
- 'COPY',
- 'Ccedil;',
- 'Ccedil',
- 'Chi;',
- 'Dagger;',
- 'Delta;',
- 'ETH;',
- 'ETH',
- 'Eacute;',
- 'Eacute',
- 'Ecirc;',
- 'Ecirc',
- 'Egrave;',
- 'Egrave',
- 'Epsilon;',
- 'Eta;',
- 'Euml;',
- 'Euml',
- 'GT;',
- 'GT',
- 'Gamma;',
- 'Iacute;',
- 'Iacute',
- 'Icirc;',
- 'Icirc',
- 'Igrave;',
- 'Igrave',
- 'Iota;',
- 'Iuml;',
- 'Iuml',
- 'Kappa;',
- 'LT;',
- 'LT',
- 'Lambda;',
- 'Mu;',
- 'Ntilde;',
- 'Ntilde',
- 'Nu;',
- 'OElig;',
- 'Oacute;',
- 'Oacute',
- 'Ocirc;',
- 'Ocirc',
- 'Ograve;',
- 'Ograve',
- 'Omega;',
- 'Omicron;',
- 'Oslash;',
- 'Oslash',
- 'Otilde;',
- 'Otilde',
- 'Ouml;',
- 'Ouml',
- 'Phi;',
- 'Pi;',
- 'Prime;',
- 'Psi;',
- 'QUOT;',
- 'QUOT',
- 'REG;',
- 'REG',
- 'Rho;',
- 'Scaron;',
- 'Sigma;',
- 'THORN;',
- 'THORN',
- 'TRADE;',
- 'Tau;',
- 'Theta;',
- 'Uacute;',
- 'Uacute',
- 'Ucirc;',
- 'Ucirc',
- 'Ugrave;',
- 'Ugrave',
- 'Upsilon;',
- 'Uuml;',
- 'Uuml',
- 'Xi;',
- 'Yacute;',
- 'Yacute',
- 'Yuml;',
- 'Zeta;',
- 'aacute;',
- 'aacute',
- 'acirc;',
- 'acirc',
- 'acute;',
- 'acute',
- 'aelig;',
- 'aelig',
- 'agrave;',
- 'agrave',
- 'alefsym;',
- 'alpha;',
- 'amp;',
- 'amp',
- 'and;',
- 'ang;',
- 'apos;',
- 'aring;',
- 'aring',
- 'asymp;',
- 'atilde;',
- 'atilde',
- 'auml;',
- 'auml',
- 'bdquo;',
- 'beta;',
- 'brvbar;',
- 'brvbar',
- 'bull;',
- 'cap;',
- 'ccedil;',
- 'ccedil',
- 'cedil;',
- 'cedil',
- 'cent;',
- 'cent',
- 'chi;',
- 'circ;',
- 'clubs;',
- 'cong;',
- 'copy;',
- 'copy',
- 'crarr;',
- 'cup;',
- 'curren;',
- 'curren',
- 'dArr;',
- 'dagger;',
- 'darr;',
- 'deg;',
- 'deg',
- 'delta;',
- 'diams;',
- 'divide;',
- 'divide',
- 'eacute;',
- 'eacute',
- 'ecirc;',
- 'ecirc',
- 'egrave;',
- 'egrave',
- 'empty;',
- 'emsp;',
- 'ensp;',
- 'epsilon;',
- 'equiv;',
- 'eta;',
- 'eth;',
- 'eth',
- 'euml;',
- 'euml',
- 'euro;',
- 'exist;',
- 'fnof;',
- 'forall;',
- 'frac12;',
- 'frac12',
- 'frac14;',
- 'frac14',
- 'frac34;',
- 'frac34',
- 'frasl;',
- 'gamma;',
- 'ge;',
- 'gt;',
- 'gt',
- 'hArr;',
- 'harr;',
- 'hearts;',
- 'hellip;',
- 'iacute;',
- 'iacute',
- 'icirc;',
- 'icirc',
- 'iexcl;',
- 'iexcl',
- 'igrave;',
- 'igrave',
- 'image;',
- 'infin;',
- 'int;',
- 'iota;',
- 'iquest;',
- 'iquest',
- 'isin;',
- 'iuml;',
- 'iuml',
- 'kappa;',
- 'lArr;',
- 'lambda;',
- 'lang;',
- 'laquo;',
- 'laquo',
- 'larr;',
- 'lceil;',
- 'ldquo;',
- 'le;',
- 'lfloor;',
- 'lowast;',
- 'loz;',
- 'lrm;',
- 'lsaquo;',
- 'lsquo;',
- 'lt;',
- 'lt',
- 'macr;',
- 'macr',
- 'mdash;',
- 'micro;',
- 'micro',
- 'middot;',
- 'middot',
- 'minus;',
- 'mu;',
- 'nabla;',
- 'nbsp;',
- 'nbsp',
- 'ndash;',
- 'ne;',
- 'ni;',
- 'not;',
- 'not',
- 'notin;',
- 'nsub;',
- 'ntilde;',
- 'ntilde',
- 'nu;',
- 'oacute;',
- 'oacute',
- 'ocirc;',
- 'ocirc',
- 'oelig;',
- 'ograve;',
- 'ograve',
- 'oline;',
- 'omega;',
- 'omicron;',
- 'oplus;',
- 'or;',
- 'ordf;',
- 'ordf',
- 'ordm;',
- 'ordm',
- 'oslash;',
- 'oslash',
- 'otilde;',
- 'otilde',
- 'otimes;',
- 'ouml;',
- 'ouml',
- 'para;',
- 'para',
- 'part;',
- 'permil;',
- 'perp;',
- 'phi;',
- 'pi;',
- 'piv;',
- 'plusmn;',
- 'plusmn',
- 'pound;',
- 'pound',
- 'prime;',
- 'prod;',
- 'prop;',
- 'psi;',
- 'quot;',
- 'quot',
- 'rArr;',
- 'radic;',
- 'rang;',
- 'raquo;',
- 'raquo',
- 'rarr;',
- 'rceil;',
- 'rdquo;',
- 'real;',
- 'reg;',
- 'reg',
- 'rfloor;',
- 'rho;',
- 'rlm;',
- 'rsaquo;',
- 'rsquo;',
- 'sbquo;',
- 'scaron;',
- 'sdot;',
- 'sect;',
- 'sect',
- 'shy;',
- 'shy',
- 'sigma;',
- 'sigmaf;',
- 'sim;',
- 'spades;',
- 'sub;',
- 'sube;',
- 'sum;',
- 'sup1;',
- 'sup1',
- 'sup2;',
- 'sup2',
- 'sup3;',
- 'sup3',
- 'sup;',
- 'supe;',
- 'szlig;',
- 'szlig',
- 'tau;',
- 'there4;',
- 'theta;',
- 'thetasym;',
- 'thinsp;',
- 'thorn;',
- 'thorn',
- 'tilde;',
- 'times;',
- 'times',
- 'trade;',
- 'uArr;',
- 'uacute;',
- 'uacute',
- 'uarr;',
- 'ucirc;',
- 'ucirc',
- 'ugrave;',
- 'ugrave',
- 'uml;',
- 'uml',
- 'upsih;',
- 'upsilon;',
- 'uuml;',
- 'uuml',
- 'weierp;',
- 'xi;',
- 'yacute;',
- 'yacute',
- 'yen;',
- 'yen',
- 'yuml;',
- 'yuml',
- 'zeta;',
- 'zwj;',
- 'zwnj;'
- );
-
- const PCDATA = 0;
- const RCDATA = 1;
- const CDATA = 2;
- const PLAINTEXT = 3;
-
- const DOCTYPE = 0;
- const STARTTAG = 1;
- const ENDTAG = 2;
- const COMMENT = 3;
- const CHARACTR = 4;
- const EOF = 5;
-
- public function __construct($data)
- {
- $this->data = $data;
- $this->char = -1;
- $this->EOF = strlen($data);
- $this->tree = new HTML5TreeConstructer;
- $this->content_model = self::PCDATA;
-
- $this->state = 'data';
-
- while ($this->state !== null) {
- $this->{$this->state . 'State'}();
- }
- }
-
- public function save()
- {
- return $this->tree->save();
- }
-
- private function char()
- {
- return ($this->char < $this->EOF)
- ? $this->data[$this->char]
- : false;
- }
-
- private function character($s, $l = 0)
- {
- if ($s + $l < $this->EOF) {
- if ($l === 0) {
- return $this->data[$s];
- } else {
- return substr($this->data, $s, $l);
- }
- }
- }
-
- private function characters($char_class, $start)
- {
- return preg_replace('#^([' . $char_class . ']+).*#s', '\\1', substr($this->data, $start));
- }
-
- private function dataState()
- {
- // Consume the next input character
- $this->char++;
- $char = $this->char();
-
- if ($char === '&' && ($this->content_model === self::PCDATA || $this->content_model === self::RCDATA)) {
- /* U+0026 AMPERSAND (&)
- When the content model flag is set to one of the PCDATA or RCDATA
- states: switch to the entity data state. Otherwise: treat it as per
- the "anything else" entry below. */
- $this->state = 'entityData';
-
- } elseif ($char === '-') {
- /* If the content model flag is set to either the RCDATA state or
- the CDATA state, and the escape flag is false, and there are at
- least three characters before this one in the input stream, and the
- last four characters in the input stream, including this one, are
- U+003C LESS-THAN SIGN, U+0021 EXCLAMATION MARK, U+002D HYPHEN-MINUS,
- and U+002D HYPHEN-MINUS ("<!--"), then set the escape flag to true. */
- if (($this->content_model === self::RCDATA || $this->content_model ===
- self::CDATA) && $this->escape === false &&
- $this->char >= 3 && $this->character($this->char - 4, 4) === '<!--'
- ) {
- $this->escape = true;
- }
-
- /* In any case, emit the input character as a character token. Stay
- in the data state. */
- $this->emitToken(
- array(
- 'type' => self::CHARACTR,
- 'data' => $char
- )
- );
-
- /* U+003C LESS-THAN SIGN (<) */
- } elseif ($char === '<' && ($this->content_model === self::PCDATA ||
- (($this->content_model === self::RCDATA ||
- $this->content_model === self::CDATA) && $this->escape === false))
- ) {
- /* When the content model flag is set to the PCDATA state: switch
- to the tag open state.
-
- When the content model flag is set to either the RCDATA state or
- the CDATA state and the escape flag is false: switch to the tag
- open state.
-
- Otherwise: treat it as per the "anything else" entry below. */
- $this->state = 'tagOpen';
-
- /* U+003E GREATER-THAN SIGN (>) */
- } elseif ($char === '>') {
- /* If the content model flag is set to either the RCDATA state or
- the CDATA state, and the escape flag is true, and the last three
- characters in the input stream including this one are U+002D
- HYPHEN-MINUS, U+002D HYPHEN-MINUS, U+003E GREATER-THAN SIGN ("-->"),
- set the escape flag to false. */
- if (($this->content_model === self::RCDATA ||
- $this->content_model === self::CDATA) && $this->escape === true &&
- $this->character($this->char, 3) === '-->'
- ) {
- $this->escape = false;
- }
-
- /* In any case, emit the input character as a character token.
- Stay in the data state. */
- $this->emitToken(
- array(
- 'type' => self::CHARACTR,
- 'data' => $char
- )
- );
-
- } elseif ($this->char === $this->EOF) {
- /* EOF
- Emit an end-of-file token. */
- $this->EOF();
-
- } elseif ($this->content_model === self::PLAINTEXT) {
- /* When the content model flag is set to the PLAINTEXT state
- THIS DIFFERS GREATLY FROM THE SPEC: Get the remaining characters of
- the text and emit it as a character token. */
- $this->emitToken(
- array(
- 'type' => self::CHARACTR,
- 'data' => substr($this->data, $this->char)
- )
- );
-
- $this->EOF();
-
- } else {
- /* Anything else
- THIS DIFFERS GREATLY FROM THE SPEC: Get as many character that
- otherwise would also be treated as a character token and emit it
- as a single character token. Stay in the data state. */
- $len = strcspn($this->data, '<&', $this->char);
- $char = substr($this->data, $this->char, $len);
- $this->char += $len - 1;
-
- $this->emitToken(
- array(
- 'type' => self::CHARACTR,
- 'data' => $char
- )
- );
-
- $this->state = 'data';
- }
- }
-
- private function entityDataState()
- {
- // Attempt to consume an entity.
- $entity = $this->entity();
-
- // If nothing is returned, emit a U+0026 AMPERSAND character token.
- // Otherwise, emit the character token that was returned.
- $char = (!$entity) ? '&' : $entity;
- $this->emitToken(
- array(
- 'type' => self::CHARACTR,
- 'data' => $char
- )
- );
-
- // Finally, switch to the data state.
- $this->state = 'data';
- }
-
- private function tagOpenState()
- {
- switch ($this->content_model) {
- case self::RCDATA:
- case self::CDATA:
- /* If the next input character is a U+002F SOLIDUS (/) character,
- consume it and switch to the close tag open state. If the next
- input character is not a U+002F SOLIDUS (/) character, emit a
- U+003C LESS-THAN SIGN character token and switch to the data
- state to process the next input character. */
- if ($this->character($this->char + 1) === '/') {
- $this->char++;
- $this->state = 'closeTagOpen';
-
- } else {
- $this->emitToken(
- array(
- 'type' => self::CHARACTR,
- 'data' => '<'
- )
- );
-
- $this->state = 'data';
- }
- break;
-
- case self::PCDATA:
- // If the content model flag is set to the PCDATA state
- // Consume the next input character:
- $this->char++;
- $char = $this->char();
-
- if ($char === '!') {
- /* U+0021 EXCLAMATION MARK (!)
- Switch to the markup declaration open state. */
- $this->state = 'markupDeclarationOpen';
-
- } elseif ($char === '/') {
- /* U+002F SOLIDUS (/)
- Switch to the close tag open state. */
- $this->state = 'closeTagOpen';
-
- } elseif (preg_match('/^[A-Za-z]$/', $char)) {
- /* U+0041 LATIN LETTER A through to U+005A LATIN LETTER Z
- Create a new start tag token, set its tag name to the lowercase
- version of the input character (add 0x0020 to the character's code
- point), then switch to the tag name state. (Don't emit the token
- yet; further details will be filled in before it is emitted.) */
- $this->token = array(
- 'name' => strtolower($char),
- 'type' => self::STARTTAG,
- 'attr' => array()
- );
-
- $this->state = 'tagName';
-
- } elseif ($char === '>') {
- /* U+003E GREATER-THAN SIGN (>)
- Parse error. Emit a U+003C LESS-THAN SIGN character token and a
- U+003E GREATER-THAN SIGN character token. Switch to the data state. */
- $this->emitToken(
- array(
- 'type' => self::CHARACTR,
- 'data' => '<>'
- )
- );
-
- $this->state = 'data';
-
- } elseif ($char === '?') {
- /* U+003F QUESTION MARK (?)
- Parse error. Switch to the bogus comment state. */
- $this->state = 'bogusComment';
-
- } else {
- /* Anything else
- Parse error. Emit a U+003C LESS-THAN SIGN character token and
- reconsume the current input character in the data state. */
- $this->emitToken(
- array(
- 'type' => self::CHARACTR,
- 'data' => '<'
- )
- );
-
- $this->char--;
- $this->state = 'data';
- }
- break;
- }
- }
-
- private function closeTagOpenState()
- {
- $next_node = strtolower($this->characters('A-Za-z', $this->char + 1));
- $the_same = count($this->tree->stack) > 0 && $next_node === end($this->tree->stack)->nodeName;
-
- if (($this->content_model === self::RCDATA || $this->content_model === self::CDATA) &&
- (!$the_same || ($the_same && (!preg_match(
- '/[\t\n\x0b\x0c >\/]/',
- $this->character($this->char + 1 + strlen($next_node))
- ) || $this->EOF === $this->char)))
- ) {
- /* If the content model flag is set to the RCDATA or CDATA states then
- examine the next few characters. If they do not match the tag name of
- the last start tag token emitted (case insensitively), or if they do but
- they are not immediately followed by one of the following characters:
- * U+0009 CHARACTER TABULATION
- * U+000A LINE FEED (LF)
- * U+000B LINE TABULATION
- * U+000C FORM FEED (FF)
- * U+0020 SPACE
- * U+003E GREATER-THAN SIGN (>)
- * U+002F SOLIDUS (/)
- * EOF
- ...then there is a parse error. Emit a U+003C LESS-THAN SIGN character
- token, a U+002F SOLIDUS character token, and switch to the data state
- to process the next input character. */
- $this->emitToken(
- array(
- 'type' => self::CHARACTR,
- 'data' => '</'
- )
- );
-
- $this->state = 'data';
-
- } else {
- /* Otherwise, if the content model flag is set to the PCDATA state,
- or if the next few characters do match that tag name, consume the
- next input character: */
- $this->char++;
- $char = $this->char();
-
- if (preg_match('/^[A-Za-z]$/', $char)) {
- /* U+0041 LATIN LETTER A through to U+005A LATIN LETTER Z
- Create a new end tag token, set its tag name to the lowercase version
- of the input character (add 0x0020 to the character's code point), then
- switch to the tag name state. (Don't emit the token yet; further details
- will be filled in before it is emitted.) */
- $this->token = array(
- 'name' => strtolower($char),
- 'type' => self::ENDTAG
- );
-
- $this->state = 'tagName';
-
- } elseif ($char === '>') {
- /* U+003E GREATER-THAN SIGN (>)
- Parse error. Switch to the data state. */
- $this->state = 'data';
-
- } elseif ($this->char === $this->EOF) {
- /* EOF
- Parse error. Emit a U+003C LESS-THAN SIGN character token and a U+002F
- SOLIDUS character token. Reconsume the EOF character in the data state. */
- $this->emitToken(
- array(
- 'type' => self::CHARACTR,
- 'data' => '</'
- )
- );
-
- $this->char--;
- $this->state = 'data';
-
- } else {
- /* Parse error. Switch to the bogus comment state. */
- $this->state = 'bogusComment';
- }
- }
- }
-
- private function tagNameState()
- {
- // Consume the next input character:
- $this->char++;
- $char = $this->character($this->char);
-
- if (preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
- /* U+0009 CHARACTER TABULATION
- U+000A LINE FEED (LF)
- U+000B LINE TABULATION
- U+000C FORM FEED (FF)
- U+0020 SPACE
- Switch to the before attribute name state. */
- $this->state = 'beforeAttributeName';
-
- } elseif ($char === '>') {
- /* U+003E GREATER-THAN SIGN (>)
- Emit the current tag token. Switch to the data state. */
- $this->emitToken($this->token);
- $this->state = 'data';
-
- } elseif ($this->char === $this->EOF) {
- /* EOF
- Parse error. Emit the current tag token. Reconsume the EOF
- character in the data state. */
- $this->emitToken($this->token);
-
- $this->char--;
- $this->state = 'data';
-
- } elseif ($char === '/') {
- /* U+002F SOLIDUS (/)
- Parse error unless this is a permitted slash. Switch to the before
- attribute name state. */
- $this->state = 'beforeAttributeName';
-
- } else {
- /* Anything else
- Append the current input character to the current tag token's tag name.
- Stay in the tag name state. */
- $this->token['name'] .= strtolower($char);
- $this->state = 'tagName';
- }
- }
-
- private function beforeAttributeNameState()
- {
- // Consume the next input character:
- $this->char++;
- $char = $this->character($this->char);
-
- if (preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
- /* U+0009 CHARACTER TABULATION
- U+000A LINE FEED (LF)
- U+000B LINE TABULATION
- U+000C FORM FEED (FF)
- U+0020 SPACE
- Stay in the before attribute name state. */
- $this->state = 'beforeAttributeName';
-
- } elseif ($char === '>') {
- /* U+003E GREATER-THAN SIGN (>)
- Emit the current tag token. Switch to the data state. */
- $this->emitToken($this->token);
- $this->state = 'data';
-
- } elseif ($char === '/') {
- /* U+002F SOLIDUS (/)
- Parse error unless this is a permitted slash. Stay in the before
- attribute name state. */
- $this->state = 'beforeAttributeName';
-
- } elseif ($this->char === $this->EOF) {
- /* EOF
- Parse error. Emit the current tag token. Reconsume the EOF
- character in the data state. */
- $this->emitToken($this->token);
-
- $this->char--;
- $this->state = 'data';
-
- } else {
- /* Anything else
- Start a new attribute in the current tag token. Set that attribute's
- name to the current input character, and its value to the empty string.
- Switch to the attribute name state. */
- $this->token['attr'][] = array(
- 'name' => strtolower($char),
- 'value' => null
- );
-
- $this->state = 'attributeName';
- }
- }
-
- private function attributeNameState()
- {
- // Consume the next input character:
- $this->char++;
- $char = $this->character($this->char);
-
- if (preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
- /* U+0009 CHARACTER TABULATION
- U+000A LINE FEED (LF)
- U+000B LINE TABULATION
- U+000C FORM FEED (FF)
- U+0020 SPACE
- Stay in the before attribute name state. */
- $this->state = 'afterAttributeName';
-
- } elseif ($char === '=') {
- /* U+003D EQUALS SIGN (=)
- Switch to the before attribute value state. */
- $this->state = 'beforeAttributeValue';
-
- } elseif ($char === '>') {
- /* U+003E GREATER-THAN SIGN (>)
- Emit the current tag token. Switch to the data state. */
- $this->emitToken($this->token);
- $this->state = 'data';
-
- } elseif ($char === '/' && $this->character($this->char + 1) !== '>') {
- /* U+002F SOLIDUS (/)
- Parse error unless this is a permitted slash. Switch to the before
- attribute name state. */
- $this->state = 'beforeAttributeName';
-
- } elseif ($this->char === $this->EOF) {
- /* EOF
- Parse error. Emit the current tag token. Reconsume the EOF
- character in the data state. */
- $this->emitToken($this->token);
-
- $this->char--;
- $this->state = 'data';
-
- } else {
- /* Anything else
- Append the current input character to the current attribute's name.
- Stay in the attribute name state. */
- $last = count($this->token['attr']) - 1;
- $this->token['attr'][$last]['name'] .= strtolower($char);
-
- $this->state = 'attributeName';
- }
- }
-
- private function afterAttributeNameState()
- {
- // Consume the next input character:
- $this->char++;
- $char = $this->character($this->char);
-
- if (preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
- /* U+0009 CHARACTER TABULATION
- U+000A LINE FEED (LF)
- U+000B LINE TABULATION
- U+000C FORM FEED (FF)
- U+0020 SPACE
- Stay in the after attribute name state. */
- $this->state = 'afterAttributeName';
-
- } elseif ($char === '=') {
- /* U+003D EQUALS SIGN (=)
- Switch to the before attribute value state. */
- $this->state = 'beforeAttributeValue';
-
- } elseif ($char === '>') {
- /* U+003E GREATER-THAN SIGN (>)
- Emit the current tag token. Switch to the data state. */
- $this->emitToken($this->token);
- $this->state = 'data';
-
- } elseif ($char === '/' && $this->character($this->char + 1) !== '>') {
- /* U+002F SOLIDUS (/)
- Parse error unless this is a permitted slash. Switch to the
- before attribute name state. */
- $this->state = 'beforeAttributeName';
-
- } elseif ($this->char === $this->EOF) {
- /* EOF
- Parse error. Emit the current tag token. Reconsume the EOF
- character in the data state. */
- $this->emitToken($this->token);
-
- $this->char--;
- $this->state = 'data';
-
- } else {
- /* Anything else
- Start a new attribute in the current tag token. Set that attribute's
- name to the current input character, and its value to the empty string.
- Switch to the attribute name state. */
- $this->token['attr'][] = array(
- 'name' => strtolower($char),
- 'value' => null
- );
-
- $this->state = 'attributeName';
- }
- }
-
- private function beforeAttributeValueState()
- {
- // Consume the next input character:
- $this->char++;
- $char = $this->character($this->char);
-
- if (preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
- /* U+0009 CHARACTER TABULATION
- U+000A LINE FEED (LF)
- U+000B LINE TABULATION
- U+000C FORM FEED (FF)
- U+0020 SPACE
- Stay in the before attribute value state. */
- $this->state = 'beforeAttributeValue';
-
- } elseif ($char === '"') {
- /* U+0022 QUOTATION MARK (")
- Switch to the attribute value (double-quoted) state. */
- $this->state = 'attributeValueDoubleQuoted';
-
- } elseif ($char === '&') {
- /* U+0026 AMPERSAND (&)
- Switch to the attribute value (unquoted) state and reconsume
- this input character. */
- $this->char--;
- $this->state = 'attributeValueUnquoted';
-
- } elseif ($char === '\'') {
- /* U+0027 APOSTROPHE (')
- Switch to the attribute value (single-quoted) state. */
- $this->state = 'attributeValueSingleQuoted';
-
- } elseif ($char === '>') {
- /* U+003E GREATER-THAN SIGN (>)
- Emit the current tag token. Switch to the data state. */
- $this->emitToken($this->token);
- $this->state = 'data';
-
- } else {
- /* Anything else
- Append the current input character to the current attribute's value.
- Switch to the attribute value (unquoted) state. */
- $last = count($this->token['attr']) - 1;
- $this->token['attr'][$last]['value'] .= $char;
-
- $this->state = 'attributeValueUnquoted';
- }
- }
-
- private function attributeValueDoubleQuotedState()
- {
- // Consume the next input character:
- $this->char++;
- $char = $this->character($this->char);
-
- if ($char === '"') {
- /* U+0022 QUOTATION MARK (")
- Switch to the before attribute name state. */
- $this->state = 'beforeAttributeName';
-
- } elseif ($char === '&') {
- /* U+0026 AMPERSAND (&)
- Switch to the entity in attribute value state. */
- $this->entityInAttributeValueState('double');
-
- } elseif ($this->char === $this->EOF) {
- /* EOF
- Parse error. Emit the current tag token. Reconsume the character
- in the data state. */
- $this->emitToken($this->token);
-
- $this->char--;
- $this->state = 'data';
-
- } else {
- /* Anything else
- Append the current input character to the current attribute's value.
- Stay in the attribute value (double-quoted) state. */
- $last = count($this->token['attr']) - 1;
- $this->token['attr'][$last]['value'] .= $char;
-
- $this->state = 'attributeValueDoubleQuoted';
- }
- }
-
- private function attributeValueSingleQuotedState()
- {
- // Consume the next input character:
- $this->char++;
- $char = $this->character($this->char);
-
- if ($char === '\'') {
- /* U+0022 QUOTATION MARK (')
- Switch to the before attribute name state. */
- $this->state = 'beforeAttributeName';
-
- } elseif ($char === '&') {
- /* U+0026 AMPERSAND (&)
- Switch to the entity in attribute value state. */
- $this->entityInAttributeValueState('single');
-
- } elseif ($this->char === $this->EOF) {
- /* EOF
- Parse error. Emit the current tag token. Reconsume the character
- in the data state. */
- $this->emitToken($this->token);
-
- $this->char--;
- $this->state = 'data';
-
- } else {
- /* Anything else
- Append the current input character to the current attribute's value.
- Stay in the attribute value (single-quoted) state. */
- $last = count($this->token['attr']) - 1;
- $this->token['attr'][$last]['value'] .= $char;
-
- $this->state = 'attributeValueSingleQuoted';
- }
- }
-
- private function attributeValueUnquotedState()
- {
- // Consume the next input character:
- $this->char++;
- $char = $this->character($this->char);
-
- if (preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
- /* U+0009 CHARACTER TABULATION
- U+000A LINE FEED (LF)
- U+000B LINE TABULATION
- U+000C FORM FEED (FF)
- U+0020 SPACE
- Switch to the before attribute name state. */
- $this->state = 'beforeAttributeName';
-
- } elseif ($char === '&') {
- /* U+0026 AMPERSAND (&)
- Switch to the entity in attribute value state. */
- $this->entityInAttributeValueState();
-
- } elseif ($char === '>') {
- /* U+003E GREATER-THAN SIGN (>)
- Emit the current tag token. Switch to the data state. */
- $this->emitToken($this->token);
- $this->state = 'data';
-
- } else {
- /* Anything else
- Append the current input character to the current attribute's value.
- Stay in the attribute value (unquoted) state. */
- $last = count($this->token['attr']) - 1;
- $this->token['attr'][$last]['value'] .= $char;
-
- $this->state = 'attributeValueUnquoted';
- }
- }
-
- private function entityInAttributeValueState()
- {
- // Attempt to consume an entity.
- $entity = $this->entity();
-
- // If nothing is returned, append a U+0026 AMPERSAND character to the
- // current attribute's value. Otherwise, emit the character token that
- // was returned.
- $char = (!$entity)
- ? '&'
- : $entity;
-
- $last = count($this->token['attr']) - 1;
- $this->token['attr'][$last]['value'] .= $char;
- }
-
- private function bogusCommentState()
- {
- /* Consume every character up to the first U+003E GREATER-THAN SIGN
- character (>) or the end of the file (EOF), whichever comes first. Emit
- a comment token whose data is the concatenation of all the characters
- starting from and including the character that caused the state machine
- to switch into the bogus comment state, up to and including the last
- consumed character before the U+003E character, if any, or up to the
- end of the file otherwise. (If the comment was started by the end of
- the file (EOF), the token is empty.) */
- $data = $this->characters('^>', $this->char);
- $this->emitToken(
- array(
- 'data' => $data,
- 'type' => self::COMMENT
- )
- );
-
- $this->char += strlen($data);
-
- /* Switch to the data state. */
- $this->state = 'data';
-
- /* If the end of the file was reached, reconsume the EOF character. */
- if ($this->char === $this->EOF) {
- $this->char = $this->EOF - 1;
- }
- }
-
- private function markupDeclarationOpenState()
- {
- /* If the next two characters are both U+002D HYPHEN-MINUS (-)
- characters, consume those two characters, create a comment token whose
- data is the empty string, and switch to the comment state. */
- if ($this->character($this->char + 1, 2) === '--') {
- $this->char += 2;
- $this->state = 'comment';
- $this->token = array(
- 'data' => null,
- 'type' => self::COMMENT
- );
-
- /* Otherwise if the next seven chacacters are a case-insensitive match
- for the word "DOCTYPE", then consume those characters and switch to the
- DOCTYPE state. */
- } elseif (strtolower($this->character($this->char + 1, 7)) === 'doctype') {
- $this->char += 7;
- $this->state = 'doctype';
-
- /* Otherwise, is is a parse error. Switch to the bogus comment state.
- The next character that is consumed, if any, is the first character
- that will be in the comment. */
- } else {
- $this->char++;
- $this->state = 'bogusComment';
- }
- }
-
- private function commentState()
- {
- /* Consume the next input character: */
- $this->char++;
- $char = $this->char();
-
- /* U+002D HYPHEN-MINUS (-) */
- if ($char === '-') {
- /* Switch to the comment dash state */
- $this->state = 'commentDash';
-
- /* EOF */
- } elseif ($this->char === $this->EOF) {
- /* Parse error. Emit the comment token. Reconsume the EOF character
- in the data state. */
- $this->emitToken($this->token);
- $this->char--;
- $this->state = 'data';
-
- /* Anything else */
- } else {
- /* Append the input character to the comment token's data. Stay in
- the comment state. */
- $this->token['data'] .= $char;
- }
- }
-
- private function commentDashState()
- {
- /* Consume the next input character: */
- $this->char++;
- $char = $this->char();
-
- /* U+002D HYPHEN-MINUS (-) */
- if ($char === '-') {
- /* Switch to the comment end state */
- $this->state = 'commentEnd';
-
- /* EOF */
- } elseif ($this->char === $this->EOF) {
- /* Parse error. Emit the comment token. Reconsume the EOF character
- in the data state. */
- $this->emitToken($this->token);
- $this->char--;
- $this->state = 'data';
-
- /* Anything else */
- } else {
- /* Append a U+002D HYPHEN-MINUS (-) character and the input
- character to the comment token's data. Switch to the comment state. */
- $this->token['data'] .= '-' . $char;
- $this->state = 'comment';
- }
- }
-
- private function commentEndState()
- {
- /* Consume the next input character: */
- $this->char++;
- $char = $this->char();
-
- if ($char === '>') {
- $this->emitToken($this->token);
- $this->state = 'data';
-
- } elseif ($char === '-') {
- $this->token['data'] .= '-';
-
- } elseif ($this->char === $this->EOF) {
- $this->emitToken($this->token);
- $this->char--;
- $this->state = 'data';
-
- } else {
- $this->token['data'] .= '--' . $char;
- $this->state = 'comment';
- }
- }
-
- private function doctypeState()
- {
- /* Consume the next input character: */
- $this->char++;
- $char = $this->char();
-
- if (preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
- $this->state = 'beforeDoctypeName';
-
- } else {
- $this->char--;
- $this->state = 'beforeDoctypeName';
- }
- }
-
- private function beforeDoctypeNameState()
- {
- /* Consume the next input character: */
- $this->char++;
- $char = $this->char();
-
- if (preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
- // Stay in the before DOCTYPE name state.
-
- } elseif (preg_match('/^[a-z]$/', $char)) {
- $this->token = array(
- 'name' => strtoupper($char),
- 'type' => self::DOCTYPE,
- 'error' => true
- );
-
- $this->state = 'doctypeName';
-
- } elseif ($char === '>') {
- $this->emitToken(
- array(
- 'name' => null,
- 'type' => self::DOCTYPE,
- 'error' => true
- )
- );
-
- $this->state = 'data';
-
- } elseif ($this->char === $this->EOF) {
- $this->emitToken(
- array(
- 'name' => null,
- 'type' => self::DOCTYPE,
- 'error' => true
- )
- );
-
- $this->char--;
- $this->state = 'data';
-
- } else {
- $this->token = array(
- 'name' => $char,
- 'type' => self::DOCTYPE,
- 'error' => true
- );
-
- $this->state = 'doctypeName';
- }
- }
-
- private function doctypeNameState()
- {
- /* Consume the next input character: */
- $this->char++;
- $char = $this->char();
-
- if (preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
- $this->state = 'AfterDoctypeName';
-
- } elseif ($char === '>') {
- $this->emitToken($this->token);
- $this->state = 'data';
-
- } elseif (preg_match('/^[a-z]$/', $char)) {
- $this->token['name'] .= strtoupper($char);
-
- } elseif ($this->char === $this->EOF) {
- $this->emitToken($this->token);
- $this->char--;
- $this->state = 'data';
-
- } else {
- $this->token['name'] .= $char;
- }
-
- $this->token['error'] = ($this->token['name'] === 'HTML')
- ? false
- : true;
- }
-
- private function afterDoctypeNameState()
- {
- /* Consume the next input character: */
- $this->char++;
- $char = $this->char();
-
- if (preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
- // Stay in the DOCTYPE name state.
-
- } elseif ($char === '>') {
- $this->emitToken($this->token);
- $this->state = 'data';
-
- } elseif ($this->char === $this->EOF) {
- $this->emitToken($this->token);
- $this->char--;
- $this->state = 'data';
-
- } else {
- $this->token['error'] = true;
- $this->state = 'bogusDoctype';
- }
- }
-
- private function bogusDoctypeState()
- {
- /* Consume the next input character: */
- $this->char++;
- $char = $this->char();
-
- if ($char === '>') {
- $this->emitToken($this->token);
- $this->state = 'data';
-
- } elseif ($this->char === $this->EOF) {
- $this->emitToken($this->token);
- $this->char--;
- $this->state = 'data';
-
- } else {
- // Stay in the bogus DOCTYPE state.
- }
- }
-
- private function entity()
- {
- $start = $this->char;
-
- // This section defines how to consume an entity. This definition is
- // used when parsing entities in text and in attributes.
-
- // The behaviour depends on the identity of the next character (the
- // one immediately after the U+0026 AMPERSAND character):
-
- switch ($this->character($this->char + 1)) {
- // U+0023 NUMBER SIGN (#)
- case '#':
-
- // The behaviour further depends on the character after the
- // U+0023 NUMBER SIGN:
- switch ($this->character($this->char + 1)) {
- // U+0078 LATIN SMALL LETTER X
- // U+0058 LATIN CAPITAL LETTER X
- case 'x':
- case 'X':
- // Follow the steps below, but using the range of
- // characters U+0030 DIGIT ZERO through to U+0039 DIGIT
- // NINE, U+0061 LATIN SMALL LETTER A through to U+0066
- // LATIN SMALL LETTER F, and U+0041 LATIN CAPITAL LETTER
- // A, through to U+0046 LATIN CAPITAL LETTER F (in other
- // words, 0-9, A-F, a-f).
- $char = 1;
- $char_class = '0-9A-Fa-f';
- break;
-
- // Anything else
- default:
- // Follow the steps below, but using the range of
- // characters U+0030 DIGIT ZERO through to U+0039 DIGIT
- // NINE (i.e. just 0-9).
- $char = 0;
- $char_class = '0-9';
- break;
- }
-
- // Consume as many characters as match the range of characters
- // given above.
- $this->char++;
- $e_name = $this->characters($char_class, $this->char + $char + 1);
- $entity = $this->character($start, $this->char);
- $cond = strlen($e_name) > 0;
-
- // The rest of the parsing happens bellow.
- break;
-
- // Anything else
- default:
- // Consume the maximum number of characters possible, with the
- // consumed characters case-sensitively matching one of the
- // identifiers in the first column of the entities table.
- $e_name = $this->characters('0-9A-Za-z;', $this->char + 1);
- $len = strlen($e_name);
-
- for ($c = 1; $c <= $len; $c++) {
- $id = substr($e_name, 0, $c);
- $this->char++;
-
- if (in_array($id, $this->entities)) {
- if ($e_name[$c - 1] !== ';') {
- if ($c < $len && $e_name[$c] == ';') {
- $this->char++; // consume extra semicolon
- }
- }
- $entity = $id;
- break;
- }
- }
-
- $cond = isset($entity);
- // The rest of the parsing happens bellow.
- break;
- }
-
- if (!$cond) {
- // If no match can be made, then this is a parse error. No
- // characters are consumed, and nothing is returned.
- $this->char = $start;
- return false;
- }
-
- // Return a character token for the character corresponding to the
- // entity name (as given by the second column of the entities table).
- return html_entity_decode('&' . $entity . ';', ENT_QUOTES, 'UTF-8');
- }
-
- private function emitToken($token)
- {
- $emit = $this->tree->emitToken($token);
-
- if (is_int($emit)) {
- $this->content_model = $emit;
-
- } elseif ($token['type'] === self::ENDTAG) {
- $this->content_model = self::PCDATA;
- }
- }
-
- private function EOF()
- {
- $this->state = null;
- $this->tree->emitToken(
- array(
- 'type' => self::EOF
- )
- );
- }
-}
-
-class HTML5TreeConstructer
-{
- public $stack = array();
-
- private $phase;
- private $mode;
- private $dom;
- private $foster_parent = null;
- private $a_formatting = array();
-
- private $head_pointer = null;
- private $form_pointer = null;
-
- private $scoping = array('button', 'caption', 'html', 'marquee', 'object', 'table', 'td', 'th');
- private $formatting = array(
- 'a',
- 'b',
- 'big',
- 'em',
- 'font',
- 'i',
- 'nobr',
- 's',
- 'small',
- 'strike',
- 'strong',
- 'tt',
- 'u'
- );
- private $special = array(
- 'address',
- 'area',
- 'base',
- 'basefont',
- 'bgsound',
- 'blockquote',
- 'body',
- 'br',
- 'center',
- 'col',
- 'colgroup',
- 'dd',
- 'dir',
- 'div',
- 'dl',
- 'dt',
- 'embed',
- 'fieldset',
- 'form',
- 'frame',
- 'frameset',
- 'h1',
- 'h2',
- 'h3',
- 'h4',
- 'h5',
- 'h6',
- 'head',
- 'hr',
- 'iframe',
- 'image',
- 'img',
- 'input',
- 'isindex',
- 'li',
- 'link',
- 'listing',
- 'menu',
- 'meta',
- 'noembed',
- 'noframes',
- 'noscript',
- 'ol',
- 'optgroup',
- 'option',
- 'p',
- 'param',
- 'plaintext',
- 'pre',
- 'script',
- 'select',
- 'spacer',
- 'style',
- 'tbody',
- 'textarea',
- 'tfoot',
- 'thead',
- 'title',
- 'tr',
- 'ul',
- 'wbr'
- );
-
- // The different phases.
- const INIT_PHASE = 0;
- const ROOT_PHASE = 1;
- const MAIN_PHASE = 2;
- const END_PHASE = 3;
-
- // The different insertion modes for the main phase.
- const BEFOR_HEAD = 0;
- const IN_HEAD = 1;
- const AFTER_HEAD = 2;
- const IN_BODY = 3;
- const IN_TABLE = 4;
- const IN_CAPTION = 5;
- const IN_CGROUP = 6;
- const IN_TBODY = 7;
- const IN_ROW = 8;
- const IN_CELL = 9;
- const IN_SELECT = 10;
- const AFTER_BODY = 11;
- const IN_FRAME = 12;
- const AFTR_FRAME = 13;
-
- // The different types of elements.
- const SPECIAL = 0;
- const SCOPING = 1;
- const FORMATTING = 2;
- const PHRASING = 3;
-
- const MARKER = 0;
-
- public function __construct()
- {
- $this->phase = self::INIT_PHASE;
- $this->mode = self::BEFOR_HEAD;
- $this->dom = new DOMDocument;
-
- $this->dom->encoding = 'UTF-8';
- $this->dom->preserveWhiteSpace = true;
- $this->dom->substituteEntities = true;
- $this->dom->strictErrorChecking = false;
- }
-
- // Process tag tokens
- public function emitToken($token)
- {
- switch ($this->phase) {
- case self::INIT_PHASE:
- return $this->initPhase($token);
- break;
- case self::ROOT_PHASE:
- return $this->rootElementPhase($token);
- break;
- case self::MAIN_PHASE:
- return $this->mainPhase($token);
- break;
- case self::END_PHASE :
- return $this->trailingEndPhase($token);
- break;
- }
- }
-
- private function initPhase($token)
- {
- /* Initially, the tree construction stage must handle each token
- emitted from the tokenisation stage as follows: */
-
- /* A DOCTYPE token that is marked as being in error
- A comment token
- A start tag token
- An end tag token
- A character token that is not one of one of U+0009 CHARACTER TABULATION,
- U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
- or U+0020 SPACE
- An end-of-file token */
- if ((isset($token['error']) && $token['error']) ||
- $token['type'] === HTML5::COMMENT ||
- $token['type'] === HTML5::STARTTAG ||
- $token['type'] === HTML5::ENDTAG ||
- $token['type'] === HTML5::EOF ||
- ($token['type'] === HTML5::CHARACTR && isset($token['data']) &&
- !preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data']))
- ) {
- /* This specification does not define how to handle this case. In
- particular, user agents may ignore the entirety of this specification
- altogether for such documents, and instead invoke special parse modes
- with a greater emphasis on backwards compatibility. */
-
- $this->phase = self::ROOT_PHASE;
- return $this->rootElementPhase($token);
-
- /* A DOCTYPE token marked as being correct */
- } elseif (isset($token['error']) && !$token['error']) {
- /* Append a DocumentType node to the Document node, with the name
- attribute set to the name given in the DOCTYPE token (which will be
- "HTML"), and the other attributes specific to DocumentType objects
- set to null, empty lists, or the empty string as appropriate. */
- $doctype = new DOMDocumentType(null, null, 'HTML');
-
- /* Then, switch to the root element phase of the tree construction
- stage. */
- $this->phase = self::ROOT_PHASE;
-
- /* A character token that is one of one of U+0009 CHARACTER TABULATION,
- U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
- or U+0020 SPACE */
- } elseif (isset($token['data']) && preg_match(
- '/^[\t\n\x0b\x0c ]+$/',
- $token['data']
- )
- ) {
- /* Append that character to the Document node. */
- $text = $this->dom->createTextNode($token['data']);
- $this->dom->appendChild($text);
- }
- }
-
- private function rootElementPhase($token)
- {
- /* After the initial phase, as each token is emitted from the tokenisation
- stage, it must be processed as described in this section. */
-
- /* A DOCTYPE token */
- if ($token['type'] === HTML5::DOCTYPE) {
- // Parse error. Ignore the token.
-
- /* A comment token */
- } elseif ($token['type'] === HTML5::COMMENT) {
- /* Append a Comment node to the Document object with the data
- attribute set to the data given in the comment token. */
- $comment = $this->dom->createComment($token['data']);
- $this->dom->appendChild($comment);
-
- /* A character token that is one of one of U+0009 CHARACTER TABULATION,
- U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
- or U+0020 SPACE */
- } elseif ($token['type'] === HTML5::CHARACTR &&
- preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])
- ) {
- /* Append that character to the Document node. */
- $text = $this->dom->createTextNode($token['data']);
- $this->dom->appendChild($text);
-
- /* A character token that is not one of U+0009 CHARACTER TABULATION,
- U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED
- (FF), or U+0020 SPACE
- A start tag token
- An end tag token
- An end-of-file token */
- } elseif (($token['type'] === HTML5::CHARACTR &&
- !preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])) ||
- $token['type'] === HTML5::STARTTAG ||
- $token['type'] === HTML5::ENDTAG ||
- $token['type'] === HTML5::EOF
- ) {
- /* Create an HTMLElement node with the tag name html, in the HTML
- namespace. Append it to the Document object. Switch to the main
- phase and reprocess the current token. */
- $html = $this->dom->createElement('html');
- $this->dom->appendChild($html);
- $this->stack[] = $html;
-
- $this->phase = self::MAIN_PHASE;
- return $this->mainPhase($token);
- }
- }
-
- private function mainPhase($token)
- {
- /* Tokens in the main phase must be handled as follows: */
-
- /* A DOCTYPE token */
- if ($token['type'] === HTML5::DOCTYPE) {
- // Parse error. Ignore the token.
-
- /* A start tag token with the tag name "html" */
- } elseif ($token['type'] === HTML5::STARTTAG && $token['name'] === 'html') {
- /* If this start tag token was not the first start tag token, then
- it is a parse error. */
-
- /* For each attribute on the token, check to see if the attribute
- is already present on the top element of the stack of open elements.
- If it is not, add the attribute and its corresponding value to that
- element. */
- foreach ($token['attr'] as $attr) {
- if (!$this->stack[0]->hasAttribute($attr['name'])) {
- $this->stack[0]->setAttribute($attr['name'], $attr['value']);
- }
- }
-
- /* An end-of-file token */
- } elseif ($token['type'] === HTML5::EOF) {
- /* Generate implied end tags. */
- $this->generateImpliedEndTags();
-
- /* Anything else. */
- } else {
- /* Depends on the insertion mode: */
- switch ($this->mode) {
- case self::BEFOR_HEAD:
- return $this->beforeHead($token);
- break;
- case self::IN_HEAD:
- return $this->inHead($token);
- break;
- case self::AFTER_HEAD:
- return $this->afterHead($token);
- break;
- case self::IN_BODY:
- return $this->inBody($token);
- break;
- case self::IN_TABLE:
- return $this->inTable($token);
- break;
- case self::IN_CAPTION:
- return $this->inCaption($token);
- break;
- case self::IN_CGROUP:
- return $this->inColumnGroup($token);
- break;
- case self::IN_TBODY:
- return $this->inTableBody($token);
- break;
- case self::IN_ROW:
- return $this->inRow($token);
- break;
- case self::IN_CELL:
- return $this->inCell($token);
- break;
- case self::IN_SELECT:
- return $this->inSelect($token);
- break;
- case self::AFTER_BODY:
- return $this->afterBody($token);
- break;
- case self::IN_FRAME:
- return $this->inFrameset($token);
- break;
- case self::AFTR_FRAME:
- return $this->afterFrameset($token);
- break;
- case self::END_PHASE:
- return $this->trailingEndPhase($token);
- break;
- }
- }
- }
-
- private function beforeHead($token)
- {
- /* Handle the token as follows: */
-
- /* A character token that is one of one of U+0009 CHARACTER TABULATION,
- U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
- or U+0020 SPACE */
- if ($token['type'] === HTML5::CHARACTR &&
- preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])
- ) {
- /* Append the character to the current node. */
- $this->insertText($token['data']);
-
- /* A comment token */
- } elseif ($token['type'] === HTML5::COMMENT) {
- /* Append a Comment node to the current node with the data attribute
- set to the data given in the comment token. */
- $this->insertComment($token['data']);
-
- /* A start tag token with the tag name "head" */
- } elseif ($token['type'] === HTML5::STARTTAG && $token['name'] === 'head') {
- /* Create an element for the token, append the new element to the
- current node and push it onto the stack of open elements. */
- $element = $this->insertElement($token);
-
- /* Set the head element pointer to this new element node. */
- $this->head_pointer = $element;
-
- /* Change the insertion mode to "in head". */
- $this->mode = self::IN_HEAD;
-
- /* A start tag token whose tag name is one of: "base", "link", "meta",
- "script", "style", "title". Or an end tag with the tag name "html".
- Or a character token that is not one of U+0009 CHARACTER TABULATION,
- U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
- or U+0020 SPACE. Or any other start tag token */
- } elseif ($token['type'] === HTML5::STARTTAG ||
- ($token['type'] === HTML5::ENDTAG && $token['name'] === 'html') ||
- ($token['type'] === HTML5::CHARACTR && !preg_match(
- '/^[\t\n\x0b\x0c ]$/',
- $token['data']
- ))
- ) {
- /* Act as if a start tag token with the tag name "head" and no
- attributes had been seen, then reprocess the current token. */
- $this->beforeHead(
- array(
- 'name' => 'head',
- 'type' => HTML5::STARTTAG,
- 'attr' => array()
- )
- );
-
- return $this->inHead($token);
-
- /* Any other end tag */
- } elseif ($token['type'] === HTML5::ENDTAG) {
- /* Parse error. Ignore the token. */
- }
- }
-
- private function inHead($token)
- {
- /* Handle the token as follows: */
-
- /* A character token that is one of one of U+0009 CHARACTER TABULATION,
- U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
- or U+0020 SPACE.
-
- THIS DIFFERS FROM THE SPEC: If the current node is either a title, style
- or script element, append the character to the current node regardless
- of its content. */
- if (($token['type'] === HTML5::CHARACTR &&
- preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])) || (
- $token['type'] === HTML5::CHARACTR && in_array(
- end($this->stack)->nodeName,
- array('title', 'style', 'script')
- ))
- ) {
- /* Append the character to the current node. */
- $this->insertText($token['data']);
-
- /* A comment token */
- } elseif ($token['type'] === HTML5::COMMENT) {
- /* Append a Comment node to the current node with the data attribute
- set to the data given in the comment token. */
- $this->insertComment($token['data']);
-
- } elseif ($token['type'] === HTML5::ENDTAG &&
- in_array($token['name'], array('title', 'style', 'script'))
- ) {
- array_pop($this->stack);
- return HTML5::PCDATA;
-
- /* A start tag with the tag name "title" */
- } elseif ($token['type'] === HTML5::STARTTAG && $token['name'] === 'title') {
- /* Create an element for the token and append the new element to the
- node pointed to by the head element pointer, or, if that is null
- (innerHTML case), to the current node. */
- if ($this->head_pointer !== null) {
- $element = $this->insertElement($token, false);
- $this->head_pointer->appendChild($element);
-
- } else {
- $element = $this->insertElement($token);
- }
-
- /* Switch the tokeniser's content model flag to the RCDATA state. */
- return HTML5::RCDATA;
-
- /* A start tag with the tag name "style" */
- } elseif ($token['type'] === HTML5::STARTTAG && $token['name'] === 'style') {
- /* Create an element for the token and append the new element to the
- node pointed to by the head element pointer, or, if that is null
- (innerHTML case), to the current node. */
- if ($this->head_pointer !== null) {
- $element = $this->insertElement($token, false);
- $this->head_pointer->appendChild($element);
-
- } else {
- $this->insertElement($token);
- }
-
- /* Switch the tokeniser's content model flag to the CDATA state. */
- return HTML5::CDATA;
-
- /* A start tag with the tag name "script" */
- } elseif ($token['type'] === HTML5::STARTTAG && $token['name'] === 'script') {
- /* Create an element for the token. */
- $element = $this->insertElement($token, false);
- $this->head_pointer->appendChild($element);
-
- /* Switch the tokeniser's content model flag to the CDATA state. */
- return HTML5::CDATA;
-
- /* A start tag with the tag name "base", "link", or "meta" */
- } elseif ($token['type'] === HTML5::STARTTAG && in_array(
- $token['name'],
- array('base', 'link', 'meta')
- )
- ) {
- /* Create an element for the token and append the new element to the
- node pointed to by the head element pointer, or, if that is null
- (innerHTML case), to the current node. */
- if ($this->head_pointer !== null) {
- $element = $this->insertElement($token, false);
- $this->head_pointer->appendChild($element);
- array_pop($this->stack);
-
- } else {
- $this->insertElement($token);
- }
-
- /* An end tag with the tag name "head" */
- } elseif ($token['type'] === HTML5::ENDTAG && $token['name'] === 'head') {
- /* If the current node is a head element, pop the current node off
- the stack of open elements. */
- if ($this->head_pointer->isSameNode(end($this->stack))) {
- array_pop($this->stack);
-
- /* Otherwise, this is a parse error. */
- } else {
- // k
- }
-
- /* Change the insertion mode to "after head". */
- $this->mode = self::AFTER_HEAD;
-
- /* A start tag with the tag name "head" or an end tag except "html". */
- } elseif (($token['type'] === HTML5::STARTTAG && $token['name'] === 'head') ||
- ($token['type'] === HTML5::ENDTAG && $token['name'] !== 'html')
- ) {
- // Parse error. Ignore the token.
-
- /* Anything else */
- } else {
- /* If the current node is a head element, act as if an end tag
- token with the tag name "head" had been seen. */
- if ($this->head_pointer->isSameNode(end($this->stack))) {
- $this->inHead(
- array(
- 'name' => 'head',
- 'type' => HTML5::ENDTAG
- )
- );
-
- /* Otherwise, change the insertion mode to "after head". */
- } else {
- $this->mode = self::AFTER_HEAD;
- }
-
- /* Then, reprocess the current token. */
- return $this->afterHead($token);
- }
- }
-
- private function afterHead($token)
- {
- /* Handle the token as follows: */
-
- /* A character token that is one of one of U+0009 CHARACTER TABULATION,
- U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
- or U+0020 SPACE */
- if ($token['type'] === HTML5::CHARACTR &&
- preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])
- ) {
- /* Append the character to the current node. */
- $this->insertText($token['data']);
-
- /* A comment token */
- } elseif ($token['type'] === HTML5::COMMENT) {
- /* Append a Comment node to the current node with the data attribute
- set to the data given in the comment token. */
- $this->insertComment($token['data']);
-
- /* A start tag token with the tag name "body" */
- } elseif ($token['type'] === HTML5::STARTTAG && $token['name'] === 'body') {
- /* Insert a body element for the token. */
- $this->insertElement($token);
-
- /* Change the insertion mode to "in body". */
- $this->mode = self::IN_BODY;
-
- /* A start tag token with the tag name "frameset" */
- } elseif ($token['type'] === HTML5::STARTTAG && $token['name'] === 'frameset') {
- /* Insert a frameset element for the token. */
- $this->insertElement($token);
-
- /* Change the insertion mode to "in frameset". */
- $this->mode = self::IN_FRAME;
-
- /* A start tag token whose tag name is one of: "base", "link", "meta",
- "script", "style", "title" */
- } elseif ($token['type'] === HTML5::STARTTAG && in_array(
- $token['name'],
- array('base', 'link', 'meta', 'script', 'style', 'title')
- )
- ) {
- /* Parse error. Switch the insertion mode back to "in head" and
- reprocess the token. */
- $this->mode = self::IN_HEAD;
- return $this->inHead($token);
-
- /* Anything else */
- } else {
- /* Act as if a start tag token with the tag name "body" and no
- attributes had been seen, and then reprocess the current token. */
- $this->afterHead(
- array(
- 'name' => 'body',
- 'type' => HTML5::STARTTAG,
- 'attr' => array()
- )
- );
-
- return $this->inBody($token);
- }
- }
-
- private function inBody($token)
- {
- /* Handle the token as follows: */
-
- switch ($token['type']) {
- /* A character token */
- case HTML5::CHARACTR:
- /* Reconstruct the active formatting elements, if any. */
- $this->reconstructActiveFormattingElements();
-
- /* Append the token's character to the current node. */
- $this->insertText($token['data']);
- break;
-
- /* A comment token */
- case HTML5::COMMENT:
- /* Append a Comment node to the current node with the data
- attribute set to the data given in the comment token. */
- $this->insertComment($token['data']);
- break;
-
- case HTML5::STARTTAG:
- switch ($token['name']) {
- /* A start tag token whose tag name is one of: "script",
- "style" */
- case 'script':
- case 'style':
- /* Process the token as if the insertion mode had been "in
- head". */
- return $this->inHead($token);
- break;
-
- /* A start tag token whose tag name is one of: "base", "link",
- "meta", "title" */
- case 'base':
- case 'link':
- case 'meta':
- case 'title':
- /* Parse error. Process the token as if the insertion mode
- had been "in head". */
- return $this->inHead($token);
- break;
-
- /* A start tag token with the tag name "body" */
- case 'body':
- /* Parse error. If the second element on the stack of open
- elements is not a body element, or, if the stack of open
- elements has only one node on it, then ignore the token.
- (innerHTML case) */
- if (count($this->stack) === 1 || $this->stack[1]->nodeName !== 'body') {
- // Ignore
-
- /* Otherwise, for each attribute on the token, check to see
- if the attribute is already present on the body element (the
- second element) on the stack of open elements. If it is not,
- add the attribute and its corresponding value to that
- element. */
- } else {
- foreach ($token['attr'] as $attr) {
- if (!$this->stack[1]->hasAttribute($attr['name'])) {
- $this->stack[1]->setAttribute($attr['name'], $attr['value']);
- }
- }
- }
- break;
-
- /* A start tag whose tag name is one of: "address",
- "blockquote", "center", "dir", "div", "dl", "fieldset",
- "listing", "menu", "ol", "p", "ul" */
- case 'address':
- case 'blockquote':
- case 'center':
- case 'dir':
- case 'div':
- case 'dl':
- case 'fieldset':
- case 'listing':
- case 'menu':
- case 'ol':
- case 'p':
- case 'ul':
- /* If the stack of open elements has a p element in scope,
- then act as if an end tag with the tag name p had been
- seen. */
- if ($this->elementInScope('p')) {
- $this->emitToken(
- array(
- 'name' => 'p',
- 'type' => HTML5::ENDTAG
- )
- );
- }
-
- /* Insert an HTML element for the token. */
- $this->insertElement($token);
- break;
-
- /* A start tag whose tag name is "form" */
- case 'form':
- /* If the form element pointer is not null, ignore the
- token with a parse error. */
- if ($this->form_pointer !== null) {
- // Ignore.
-
- /* Otherwise: */
- } else {
- /* If the stack of open elements has a p element in
- scope, then act as if an end tag with the tag name p
- had been seen. */
- if ($this->elementInScope('p')) {
- $this->emitToken(
- array(
- 'name' => 'p',
- 'type' => HTML5::ENDTAG
- )
- );
- }
-
- /* Insert an HTML element for the token, and set the
- form element pointer to point to the element created. */
- $element = $this->insertElement($token);
- $this->form_pointer = $element;
- }
- break;
-
- /* A start tag whose tag name is "li", "dd" or "dt" */
- case 'li':
- case 'dd':
- case 'dt':
- /* If the stack of open elements has a p element in scope,
- then act as if an end tag with the tag name p had been
- seen. */
- if ($this->elementInScope('p')) {
- $this->emitToken(
- array(
- 'name' => 'p',
- 'type' => HTML5::ENDTAG
- )
- );
- }
-
- $stack_length = count($this->stack) - 1;
-
- for ($n = $stack_length; 0 <= $n; $n--) {
- /* 1. Initialise node to be the current node (the
- bottommost node of the stack). */
- $stop = false;
- $node = $this->stack[$n];
- $cat = $this->getElementCategory($node->tagName);
-
- /* 2. If node is an li, dd or dt element, then pop all
- the nodes from the current node up to node, including
- node, then stop this algorithm. */
- if ($token['name'] === $node->tagName || ($token['name'] !== 'li'
- && ($node->tagName === 'dd' || $node->tagName === 'dt'))
- ) {
- for ($x = $stack_length; $x >= $n; $x--) {
- array_pop($this->stack);
- }
-
- break;
- }
-
- /* 3. If node is not in the formatting category, and is
- not in the phrasing category, and is not an address or
- div element, then stop this algorithm. */
- if ($cat !== self::FORMATTING && $cat !== self::PHRASING &&
- $node->tagName !== 'address' && $node->tagName !== 'div'
- ) {
- break;
- }
- }
-
- /* Finally, insert an HTML element with the same tag
- name as the token's. */
- $this->insertElement($token);
- break;
-
- /* A start tag token whose tag name is "plaintext" */
- case 'plaintext':
- /* If the stack of open elements has a p element in scope,
- then act as if an end tag with the tag name p had been
- seen. */
- if ($this->elementInScope('p')) {
- $this->emitToken(
- array(
- 'name' => 'p',
- 'type' => HTML5::ENDTAG
- )
- );
- }
-
- /* Insert an HTML element for the token. */
- $this->insertElement($token);
-
- return HTML5::PLAINTEXT;
- break;
-
- /* A start tag whose tag name is one of: "h1", "h2", "h3", "h4",
- "h5", "h6" */
- case 'h1':
- case 'h2':
- case 'h3':
- case 'h4':
- case 'h5':
- case 'h6':
- /* If the stack of open elements has a p element in scope,
- then act as if an end tag with the tag name p had been seen. */
- if ($this->elementInScope('p')) {
- $this->emitToken(
- array(
- 'name' => 'p',
- 'type' => HTML5::ENDTAG
- )
- );
- }
-
- /* If the stack of open elements has in scope an element whose
- tag name is one of "h1", "h2", "h3", "h4", "h5", or "h6", then
- this is a parse error; pop elements from the stack until an
- element with one of those tag names has been popped from the
- stack. */
- while ($this->elementInScope(array('h1', 'h2', 'h3', 'h4', 'h5', 'h6'))) {
- array_pop($this->stack);
- }
-
- /* Insert an HTML element for the token. */
- $this->insertElement($token);
- break;
-
- /* A start tag whose tag name is "a" */
- case 'a':
- /* If the list of active formatting elements contains
- an element whose tag name is "a" between the end of the
- list and the last marker on the list (or the start of
- the list if there is no marker on the list), then this
- is a parse error; act as if an end tag with the tag name
- "a" had been seen, then remove that element from the list
- of active formatting elements and the stack of open
- elements if the end tag didn't already remove it (it
- might not have if the element is not in table scope). */
- $leng = count($this->a_formatting);
-
- for ($n = $leng - 1; $n >= 0; $n--) {
- if ($this->a_formatting[$n] === self::MARKER) {
- break;
-
- } elseif ($this->a_formatting[$n]->nodeName === 'a') {
- $this->emitToken(
- array(
- 'name' => 'a',
- 'type' => HTML5::ENDTAG
- )
- );
- break;
- }
- }
-
- /* Reconstruct the active formatting elements, if any. */
- $this->reconstructActiveFormattingElements();
-
- /* Insert an HTML element for the token. */
- $el = $this->insertElement($token);
-
- /* Add that element to the list of active formatting
- elements. */
- $this->a_formatting[] = $el;
- break;
-
- /* A start tag whose tag name is one of: "b", "big", "em", "font",
- "i", "nobr", "s", "small", "strike", "strong", "tt", "u" */
- case 'b':
- case 'big':
- case 'em':
- case 'font':
- case 'i':
- case 'nobr':
- case 's':
- case 'small':
- case 'strike':
- case 'strong':
- case 'tt':
- case 'u':
- /* Reconstruct the active formatting elements, if any. */
- $this->reconstructActiveFormattingElements();
-
- /* Insert an HTML element for the token. */
- $el = $this->insertElement($token);
-
- /* Add that element to the list of active formatting
- elements. */
- $this->a_formatting[] = $el;
- break;
-
- /* A start tag token whose tag name is "button" */
- case 'button':
- /* If the stack of open elements has a button element in scope,
- then this is a parse error; act as if an end tag with the tag
- name "button" had been seen, then reprocess the token. (We don't
- do that. Unnecessary.) */
- if ($this->elementInScope('button')) {
- $this->inBody(
- array(
- 'name' => 'button',
- 'type' => HTML5::ENDTAG
- )
- );
- }
-
- /* Reconstruct the active formatting elements, if any. */
- $this->reconstructActiveFormattingElements();
-
- /* Insert an HTML element for the token. */
- $this->insertElement($token);
-
- /* Insert a marker at the end of the list of active
- formatting elements. */
- $this->a_formatting[] = self::MARKER;
- break;
-
- /* A start tag token whose tag name is one of: "marquee", "object" */
- case 'marquee':
- case 'object':
- /* Reconstruct the active formatting elements, if any. */
- $this->reconstructActiveFormattingElements();
-
- /* Insert an HTML element for the token. */
- $this->insertElement($token);
-
- /* Insert a marker at the end of the list of active
- formatting elements. */
- $this->a_formatting[] = self::MARKER;
- break;
-
- /* A start tag token whose tag name is "xmp" */
- case 'xmp':
- /* Reconstruct the active formatting elements, if any. */
- $this->reconstructActiveFormattingElements();
-
- /* Insert an HTML element for the token. */
- $this->insertElement($token);
-
- /* Switch the content model flag to the CDATA state. */
- return HTML5::CDATA;
- break;
-
- /* A start tag whose tag name is "table" */
- case 'table':
- /* If the stack of open elements has a p element in scope,
- then act as if an end tag with the tag name p had been seen. */
- if ($this->elementInScope('p')) {
- $this->emitToken(
- array(
- 'name' => 'p',
- 'type' => HTML5::ENDTAG
- )
- );
- }
-
- /* Insert an HTML element for the token. */
- $this->insertElement($token);
-
- /* Change the insertion mode to "in table". */
- $this->mode = self::IN_TABLE;
- break;
-
- /* A start tag whose tag name is one of: "area", "basefont",
- "bgsound", "br", "embed", "img", "param", "spacer", "wbr" */
- case 'area':
- case 'basefont':
- case 'bgsound':
- case 'br':
- case 'embed':
- case 'img':
- case 'param':
- case 'spacer':
- case 'wbr':
- /* Reconstruct the active formatting elements, if any. */
- $this->reconstructActiveFormattingElements();
-
- /* Insert an HTML element for the token. */
- $this->insertElement($token);
-
- /* Immediately pop the current node off the stack of open elements. */
- array_pop($this->stack);
- break;
-
- /* A start tag whose tag name is "hr" */
- case 'hr':
- /* If the stack of open elements has a p element in scope,
- then act as if an end tag with the tag name p had been seen. */
- if ($this->elementInScope('p')) {
- $this->emitToken(
- array(
- 'name' => 'p',
- 'type' => HTML5::ENDTAG
- )
- );
- }
-
- /* Insert an HTML element for the token. */
- $this->insertElement($token);
-
- /* Immediately pop the current node off the stack of open elements. */
- array_pop($this->stack);
- break;
-
- /* A start tag whose tag name is "image" */
- case 'image':
- /* Parse error. Change the token's tag name to "img" and
- reprocess it. (Don't ask.) */
- $token['name'] = 'img';
- return $this->inBody($token);
- break;
-
- /* A start tag whose tag name is "input" */
- case 'input':
- /* Reconstruct the active formatting elements, if any. */
- $this->reconstructActiveFormattingElements();
-
- /* Insert an input element for the token. */
- $element = $this->insertElement($token, false);
-
- /* If the form element pointer is not null, then associate the
- input element with the form element pointed to by the form
- element pointer. */
- $this->form_pointer !== null
- ? $this->form_pointer->appendChild($element)
- : end($this->stack)->appendChild($element);
-
- /* Pop that input element off the stack of open elements. */
- array_pop($this->stack);
- break;
-
- /* A start tag whose tag name is "isindex" */
- case 'isindex':
- /* Parse error. */
- // w/e
-
- /* If the form element pointer is not null,
- then ignore the token. */
- if ($this->form_pointer === null) {
- /* Act as if a start tag token with the tag name "form" had
- been seen. */
- $this->inBody(
- array(
- 'name' => 'body',
- 'type' => HTML5::STARTTAG,
- 'attr' => array()
- )
- );
-
- /* Act as if a start tag token with the tag name "hr" had
- been seen. */
- $this->inBody(
- array(
- 'name' => 'hr',
- 'type' => HTML5::STARTTAG,
- 'attr' => array()
- )
- );
-
- /* Act as if a start tag token with the tag name "p" had
- been seen. */
- $this->inBody(
- array(
- 'name' => 'p',
- 'type' => HTML5::STARTTAG,
- 'attr' => array()
- )
- );
-
- /* Act as if a start tag token with the tag name "label"
- had been seen. */
- $this->inBody(
- array(
- 'name' => 'label',
- 'type' => HTML5::STARTTAG,
- 'attr' => array()
- )
- );
-
- /* Act as if a stream of character tokens had been seen. */
- $this->insertText(
- 'This is a searchable index. ' .
- 'Insert your search keywords here: '
- );
-
- /* Act as if a start tag token with the tag name "input"
- had been seen, with all the attributes from the "isindex"
- token, except with the "name" attribute set to the value
- "isindex" (ignoring any explicit "name" attribute). */
- $attr = $token['attr'];
- $attr[] = array('name' => 'name', 'value' => 'isindex');
-
- $this->inBody(
- array(
- 'name' => 'input',
- 'type' => HTML5::STARTTAG,
- 'attr' => $attr
- )
- );
-
- /* Act as if a stream of character tokens had been seen
- (see below for what they should say). */
- $this->insertText(
- 'This is a searchable index. ' .
- 'Insert your search keywords here: '
- );
-
- /* Act as if an end tag token with the tag name "label"
- had been seen. */
- $this->inBody(
- array(
- 'name' => 'label',
- 'type' => HTML5::ENDTAG
- )
- );
-
- /* Act as if an end tag token with the tag name "p" had
- been seen. */
- $this->inBody(
- array(
- 'name' => 'p',
- 'type' => HTML5::ENDTAG
- )
- );
-
- /* Act as if a start tag token with the tag name "hr" had
- been seen. */
- $this->inBody(
- array(
- 'name' => 'hr',
- 'type' => HTML5::ENDTAG
- )
- );
-
- /* Act as if an end tag token with the tag name "form" had
- been seen. */
- $this->inBody(
- array(
- 'name' => 'form',
- 'type' => HTML5::ENDTAG
- )
- );
- }
- break;
-
- /* A start tag whose tag name is "textarea" */
- case 'textarea':
- $this->insertElement($token);
-
- /* Switch the tokeniser's content model flag to the
- RCDATA state. */
- return HTML5::RCDATA;
- break;
-
- /* A start tag whose tag name is one of: "iframe", "noembed",
- "noframes" */
- case 'iframe':
- case 'noembed':
- case 'noframes':
- $this->insertElement($token);
-
- /* Switch the tokeniser's content model flag to the CDATA state. */
- return HTML5::CDATA;
- break;
-
- /* A start tag whose tag name is "select" */
- case 'select':
- /* Reconstruct the active formatting elements, if any. */
- $this->reconstructActiveFormattingElements();
-
- /* Insert an HTML element for the token. */
- $this->insertElement($token);
-
- /* Change the insertion mode to "in select". */
- $this->mode = self::IN_SELECT;
- break;
-
- /* A start or end tag whose tag name is one of: "caption", "col",
- "colgroup", "frame", "frameset", "head", "option", "optgroup",
- "tbody", "td", "tfoot", "th", "thead", "tr". */
- case 'caption':
- case 'col':
- case 'colgroup':
- case 'frame':
- case 'frameset':
- case 'head':
- case 'option':
- case 'optgroup':
- case 'tbody':
- case 'td':
- case 'tfoot':
- case 'th':
- case 'thead':
- case 'tr':
- // Parse error. Ignore the token.
- break;
-
- /* A start or end tag whose tag name is one of: "event-source",
- "section", "nav", "article", "aside", "header", "footer",
- "datagrid", "command" */
- case 'event-source':
- case 'section':
- case 'nav':
- case 'article':
- case 'aside':
- case 'header':
- case 'footer':
- case 'datagrid':
- case 'command':
- // Work in progress!
- break;
-
- /* A start tag token not covered by the previous entries */
- default:
- /* Reconstruct the active formatting elements, if any. */
- $this->reconstructActiveFormattingElements();
-
- $this->insertElement($token, true, true);
- break;
- }
- break;
-
- case HTML5::ENDTAG:
- switch ($token['name']) {
- /* An end tag with the tag name "body" */
- case 'body':
- /* If the second element in the stack of open elements is
- not a body element, this is a parse error. Ignore the token.
- (innerHTML case) */
- if (count($this->stack) < 2 || $this->stack[1]->nodeName !== 'body') {
- // Ignore.
-
- /* If the current node is not the body element, then this
- is a parse error. */
- } elseif (end($this->stack)->nodeName !== 'body') {
- // Parse error.
- }
-
- /* Change the insertion mode to "after body". */
- $this->mode = self::AFTER_BODY;
- break;
-
- /* An end tag with the tag name "html" */
- case 'html':
- /* Act as if an end tag with tag name "body" had been seen,
- then, if that token wasn't ignored, reprocess the current
- token. */
- $this->inBody(
- array(
- 'name' => 'body',
- 'type' => HTML5::ENDTAG
- )
- );
-
- return $this->afterBody($token);
- break;
-
- /* An end tag whose tag name is one of: "address", "blockquote",
- "center", "dir", "div", "dl", "fieldset", "listing", "menu",
- "ol", "pre", "ul" */
- case 'address':
- case 'blockquote':
- case 'center':
- case 'dir':
- case 'div':
- case 'dl':
- case 'fieldset':
- case 'listing':
- case 'menu':
- case 'ol':
- case 'pre':
- case 'ul':
- /* If the stack of open elements has an element in scope
- with the same tag name as that of the token, then generate
- implied end tags. */
- if ($this->elementInScope($token['name'])) {
- $this->generateImpliedEndTags();
-
- /* Now, if the current node is not an element with
- the same tag name as that of the token, then this
- is a parse error. */
- // w/e
-
- /* If the stack of open elements has an element in
- scope with the same tag name as that of the token,
- then pop elements from this stack until an element
- with that tag name has been popped from the stack. */
- for ($n = count($this->stack) - 1; $n >= 0; $n--) {
- if ($this->stack[$n]->nodeName === $token['name']) {
- $n = -1;
- }
-
- array_pop($this->stack);
- }
- }
- break;
-
- /* An end tag whose tag name is "form" */
- case 'form':
- /* If the stack of open elements has an element in scope
- with the same tag name as that of the token, then generate
- implied end tags. */
- if ($this->elementInScope($token['name'])) {
- $this->generateImpliedEndTags();
-
- }
-
- if (end($this->stack)->nodeName !== $token['name']) {
- /* Now, if the current node is not an element with the
- same tag name as that of the token, then this is a parse
- error. */
- // w/e
-
- } else {
- /* Otherwise, if the current node is an element with
- the same tag name as that of the token pop that element
- from the stack. */
- array_pop($this->stack);
- }
-
- /* In any case, set the form element pointer to null. */
- $this->form_pointer = null;
- break;
-
- /* An end tag whose tag name is "p" */
- case 'p':
- /* If the stack of open elements has a p element in scope,
- then generate implied end tags, except for p elements. */
- if ($this->elementInScope('p')) {
- $this->generateImpliedEndTags(array('p'));
-
- /* If the current node is not a p element, then this is
- a parse error. */
- // k
-
- /* If the stack of open elements has a p element in
- scope, then pop elements from this stack until the stack
- no longer has a p element in scope. */
- for ($n = count($this->stack) - 1; $n >= 0; $n--) {
- if ($this->elementInScope('p')) {
- array_pop($this->stack);
-
- } else {
- break;
- }
- }
- }
- break;
-
- /* An end tag whose tag name is "dd", "dt", or "li" */
- case 'dd':
- case 'dt':
- case 'li':
- /* If the stack of open elements has an element in scope
- whose tag name matches the tag name of the token, then
- generate implied end tags, except for elements with the
- same tag name as the token. */
- if ($this->elementInScope($token['name'])) {
- $this->generateImpliedEndTags(array($token['name']));
-
- /* If the current node is not an element with the same
- tag name as the token, then this is a parse error. */
- // w/e
-
- /* If the stack of open elements has an element in scope
- whose tag name matches the tag name of the token, then
- pop elements from this stack until an element with that
- tag name has been popped from the stack. */
- for ($n = count($this->stack) - 1; $n >= 0; $n--) {
- if ($this->stack[$n]->nodeName === $token['name']) {
- $n = -1;
- }
-
- array_pop($this->stack);
- }
- }
- break;
-
- /* An end tag whose tag name is one of: "h1", "h2", "h3", "h4",
- "h5", "h6" */
- case 'h1':
- case 'h2':
- case 'h3':
- case 'h4':
- case 'h5':
- case 'h6':
- $elements = array('h1', 'h2', 'h3', 'h4', 'h5', 'h6');
-
- /* If the stack of open elements has in scope an element whose
- tag name is one of "h1", "h2", "h3", "h4", "h5", or "h6", then
- generate implied end tags. */
- if ($this->elementInScope($elements)) {
- $this->generateImpliedEndTags();
-
- /* Now, if the current node is not an element with the same
- tag name as that of the token, then this is a parse error. */
- // w/e
-
- /* If the stack of open elements has in scope an element
- whose tag name is one of "h1", "h2", "h3", "h4", "h5", or
- "h6", then pop elements from the stack until an element
- with one of those tag names has been popped from the stack. */
- while ($this->elementInScope($elements)) {
- array_pop($this->stack);
- }
- }
- break;
-
- /* An end tag whose tag name is one of: "a", "b", "big", "em",
- "font", "i", "nobr", "s", "small", "strike", "strong", "tt", "u" */
- case 'a':
- case 'b':
- case 'big':
- case 'em':
- case 'font':
- case 'i':
- case 'nobr':
- case 's':
- case 'small':
- case 'strike':
- case 'strong':
- case 'tt':
- case 'u':
- /* 1. Let the formatting element be the last element in
- the list of active formatting elements that:
- * is between the end of the list and the last scope
- marker in the list, if any, or the start of the list
- otherwise, and
- * has the same tag name as the token.
- */
- while (true) {
- for ($a = count($this->a_formatting) - 1; $a >= 0; $a--) {
- if ($this->a_formatting[$a] === self::MARKER) {
- break;
-
- } elseif ($this->a_formatting[$a]->tagName === $token['name']) {
- $formatting_element = $this->a_formatting[$a];
- $in_stack = in_array($formatting_element, $this->stack, true);
- $fe_af_pos = $a;
- break;
- }
- }
-
- /* If there is no such node, or, if that node is
- also in the stack of open elements but the element
- is not in scope, then this is a parse error. Abort
- these steps. The token is ignored. */
- if (!isset($formatting_element) || ($in_stack &&
- !$this->elementInScope($token['name']))
- ) {
- break;
-
- /* Otherwise, if there is such a node, but that node
- is not in the stack of open elements, then this is a
- parse error; remove the element from the list, and
- abort these steps. */
- } elseif (isset($formatting_element) && !$in_stack) {
- unset($this->a_formatting[$fe_af_pos]);
- $this->a_formatting = array_merge($this->a_formatting);
- break;
- }
-
- /* 2. Let the furthest block be the topmost node in the
- stack of open elements that is lower in the stack
- than the formatting element, and is not an element in
- the phrasing or formatting categories. There might
- not be one. */
- $fe_s_pos = array_search($formatting_element, $this->stack, true);
- $length = count($this->stack);
-
- for ($s = $fe_s_pos + 1; $s < $length; $s++) {
- $category = $this->getElementCategory($this->stack[$s]->nodeName);
-
- if ($category !== self::PHRASING && $category !== self::FORMATTING) {
- $furthest_block = $this->stack[$s];
- }
- }
-
- /* 3. If there is no furthest block, then the UA must
- skip the subsequent steps and instead just pop all
- the nodes from the bottom of the stack of open
- elements, from the current node up to the formatting
- element, and remove the formatting element from the
- list of active formatting elements. */
- if (!isset($furthest_block)) {
- for ($n = $length - 1; $n >= $fe_s_pos; $n--) {
- array_pop($this->stack);
- }
-
- unset($this->a_formatting[$fe_af_pos]);
- $this->a_formatting = array_merge($this->a_formatting);
- break;
- }
-
- /* 4. Let the common ancestor be the element
- immediately above the formatting element in the stack
- of open elements. */
- $common_ancestor = $this->stack[$fe_s_pos - 1];
-
- /* 5. If the furthest block has a parent node, then
- remove the furthest block from its parent node. */
- if ($furthest_block->parentNode !== null) {
- $furthest_block->parentNode->removeChild($furthest_block);
- }
-
- /* 6. Let a bookmark note the position of the
- formatting element in the list of active formatting
- elements relative to the elements on either side
- of it in the list. */
- $bookmark = $fe_af_pos;
-
- /* 7. Let node and last node be the furthest block.
- Follow these steps: */
- $node = $furthest_block;
- $last_node = $furthest_block;
-
- while (true) {
- for ($n = array_search($node, $this->stack, true) - 1; $n >= 0; $n--) {
- /* 7.1 Let node be the element immediately
- prior to node in the stack of open elements. */
- $node = $this->stack[$n];
-
- /* 7.2 If node is not in the list of active
- formatting elements, then remove node from
- the stack of open elements and then go back
- to step 1. */
- if (!in_array($node, $this->a_formatting, true)) {
- unset($this->stack[$n]);
- $this->stack = array_merge($this->stack);
-
- } else {
- break;
- }
- }
-
- /* 7.3 Otherwise, if node is the formatting
- element, then go to the next step in the overall
- algorithm. */
- if ($node === $formatting_element) {
- break;
-
- /* 7.4 Otherwise, if last node is the furthest
- block, then move the aforementioned bookmark to
- be immediately after the node in the list of
- active formatting elements. */
- } elseif ($last_node === $furthest_block) {
- $bookmark = array_search($node, $this->a_formatting, true) + 1;
- }
-
- /* 7.5 If node has any children, perform a
- shallow clone of node, replace the entry for
- node in the list of active formatting elements
- with an entry for the clone, replace the entry
- for node in the stack of open elements with an
- entry for the clone, and let node be the clone. */
- if ($node->hasChildNodes()) {
- $clone = $node->cloneNode();
- $s_pos = array_search($node, $this->stack, true);
- $a_pos = array_search($node, $this->a_formatting, true);
-
- $this->stack[$s_pos] = $clone;
- $this->a_formatting[$a_pos] = $clone;
- $node = $clone;
- }
-
- /* 7.6 Insert last node into node, first removing
- it from its previous parent node if any. */
- if ($last_node->parentNode !== null) {
- $last_node->parentNode->removeChild($last_node);
- }
-
- $node->appendChild($last_node);
-
- /* 7.7 Let last node be node. */
- $last_node = $node;
- }
-
- /* 8. Insert whatever last node ended up being in
- the previous step into the common ancestor node,
- first removing it from its previous parent node if
- any. */
- if ($last_node->parentNode !== null) {
- $last_node->parentNode->removeChild($last_node);
- }
-
- $common_ancestor->appendChild($last_node);
-
- /* 9. Perform a shallow clone of the formatting
- element. */
- $clone = $formatting_element->cloneNode();
-
- /* 10. Take all of the child nodes of the furthest
- block and append them to the clone created in the
- last step. */
- while ($furthest_block->hasChildNodes()) {
- $child = $furthest_block->firstChild;
- $furthest_block->removeChild($child);
- $clone->appendChild($child);
- }
-
- /* 11. Append that clone to the furthest block. */
- $furthest_block->appendChild($clone);
-
- /* 12. Remove the formatting element from the list
- of active formatting elements, and insert the clone
- into the list of active formatting elements at the
- position of the aforementioned bookmark. */
- $fe_af_pos = array_search($formatting_element, $this->a_formatting, true);
- unset($this->a_formatting[$fe_af_pos]);
- $this->a_formatting = array_merge($this->a_formatting);
-
- $af_part1 = array_slice($this->a_formatting, 0, $bookmark - 1);
- $af_part2 = array_slice($this->a_formatting, $bookmark, count($this->a_formatting));
- $this->a_formatting = array_merge($af_part1, array($clone), $af_part2);
-
- /* 13. Remove the formatting element from the stack
- of open elements, and insert the clone into the stack
- of open elements immediately after (i.e. in a more
- deeply nested position than) the position of the
- furthest block in that stack. */
- $fe_s_pos = array_search($formatting_element, $this->stack, true);
- $fb_s_pos = array_search($furthest_block, $this->stack, true);
- unset($this->stack[$fe_s_pos]);
-
- $s_part1 = array_slice($this->stack, 0, $fb_s_pos);
- $s_part2 = array_slice($this->stack, $fb_s_pos + 1, count($this->stack));
- $this->stack = array_merge($s_part1, array($clone), $s_part2);
-
- /* 14. Jump back to step 1 in this series of steps. */
- unset($formatting_element, $fe_af_pos, $fe_s_pos, $furthest_block);
- }
- break;
-
- /* An end tag token whose tag name is one of: "button",
- "marquee", "object" */
- case 'button':
- case 'marquee':
- case 'object':
- /* If the stack of open elements has an element in scope whose
- tag name matches the tag name of the token, then generate implied
- tags. */
- if ($this->elementInScope($token['name'])) {
- $this->generateImpliedEndTags();
-
- /* Now, if the current node is not an element with the same
- tag name as the token, then this is a parse error. */
- // k
-
- /* Now, if the stack of open elements has an element in scope
- whose tag name matches the tag name of the token, then pop
- elements from the stack until that element has been popped from
- the stack, and clear the list of active formatting elements up
- to the last marker. */
- for ($n = count($this->stack) - 1; $n >= 0; $n--) {
- if ($this->stack[$n]->nodeName === $token['name']) {
- $n = -1;
- }
-
- array_pop($this->stack);
- }
-
- $marker = end(array_keys($this->a_formatting, self::MARKER, true));
-
- for ($n = count($this->a_formatting) - 1; $n > $marker; $n--) {
- array_pop($this->a_formatting);
- }
- }
- break;
-
- /* Or an end tag whose tag name is one of: "area", "basefont",
- "bgsound", "br", "embed", "hr", "iframe", "image", "img",
- "input", "isindex", "noembed", "noframes", "param", "select",
- "spacer", "table", "textarea", "wbr" */
- case 'area':
- case 'basefont':
- case 'bgsound':
- case 'br':
- case 'embed':
- case 'hr':
- case 'iframe':
- case 'image':
- case 'img':
- case 'input':
- case 'isindex':
- case 'noembed':
- case 'noframes':
- case 'param':
- case 'select':
- case 'spacer':
- case 'table':
- case 'textarea':
- case 'wbr':
- // Parse error. Ignore the token.
- break;
-
- /* An end tag token not covered by the previous entries */
- default:
- for ($n = count($this->stack) - 1; $n >= 0; $n--) {
- /* Initialise node to be the current node (the bottommost
- node of the stack). */
- $node = end($this->stack);
-
- /* If node has the same tag name as the end tag token,
- then: */
- if ($token['name'] === $node->nodeName) {
- /* Generate implied end tags. */
- $this->generateImpliedEndTags();
-
- /* If the tag name of the end tag token does not
- match the tag name of the current node, this is a
- parse error. */
- // k
-
- /* Pop all the nodes from the current node up to
- node, including node, then stop this algorithm. */
- for ($x = count($this->stack) - $n; $x >= $n; $x--) {
- array_pop($this->stack);
- }
-
- } else {
- $category = $this->getElementCategory($node);
-
- if ($category !== self::SPECIAL && $category !== self::SCOPING) {
- /* Otherwise, if node is in neither the formatting
- category nor the phrasing category, then this is a
- parse error. Stop this algorithm. The end tag token
- is ignored. */
- return false;
- }
- }
- }
- break;
- }
- break;
- }
- }
-
- private function inTable($token)
- {
- $clear = array('html', 'table');
-
- /* A character token that is one of one of U+0009 CHARACTER TABULATION,
- U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
- or U+0020 SPACE */
- if ($token['type'] === HTML5::CHARACTR &&
- preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])
- ) {
- /* Append the character to the current node. */
- $text = $this->dom->createTextNode($token['data']);
- end($this->stack)->appendChild($text);
-
- /* A comment token */
- } elseif ($token['type'] === HTML5::COMMENT) {
- /* Append a Comment node to the current node with the data
- attribute set to the data given in the comment token. */
- $comment = $this->dom->createComment($token['data']);
- end($this->stack)->appendChild($comment);
-
- /* A start tag whose tag name is "caption" */
- } elseif ($token['type'] === HTML5::STARTTAG &&
- $token['name'] === 'caption'
- ) {
- /* Clear the stack back to a table context. */
- $this->clearStackToTableContext($clear);
-
- /* Insert a marker at the end of the list of active
- formatting elements. */
- $this->a_formatting[] = self::MARKER;
-
- /* Insert an HTML element for the token, then switch the
- insertion mode to "in caption". */
- $this->insertElement($token);
- $this->mode = self::IN_CAPTION;
-
- /* A start tag whose tag name is "colgroup" */
- } elseif ($token['type'] === HTML5::STARTTAG &&
- $token['name'] === 'colgroup'
- ) {
- /* Clear the stack back to a table context. */
- $this->clearStackToTableContext($clear);
-
- /* Insert an HTML element for the token, then switch the
- insertion mode to "in column group". */
- $this->insertElement($token);
- $this->mode = self::IN_CGROUP;
-
- /* A start tag whose tag name is "col" */
- } elseif ($token['type'] === HTML5::STARTTAG &&
- $token['name'] === 'col'
- ) {
- $this->inTable(
- array(
- 'name' => 'colgroup',
- 'type' => HTML5::STARTTAG,
- 'attr' => array()
- )
- );
-
- $this->inColumnGroup($token);
-
- /* A start tag whose tag name is one of: "tbody", "tfoot", "thead" */
- } elseif ($token['type'] === HTML5::STARTTAG && in_array(
- $token['name'],
- array('tbody', 'tfoot', 'thead')
- )
- ) {
- /* Clear the stack back to a table context. */
- $this->clearStackToTableContext($clear);
-
- /* Insert an HTML element for the token, then switch the insertion
- mode to "in table body". */
- $this->insertElement($token);
- $this->mode = self::IN_TBODY;
-
- /* A start tag whose tag name is one of: "td", "th", "tr" */
- } elseif ($token['type'] === HTML5::STARTTAG &&
- in_array($token['name'], array('td', 'th', 'tr'))
- ) {
- /* Act as if a start tag token with the tag name "tbody" had been
- seen, then reprocess the current token. */
- $this->inTable(
- array(
- 'name' => 'tbody',
- 'type' => HTML5::STARTTAG,
- 'attr' => array()
- )
- );
-
- return $this->inTableBody($token);
-
- /* A start tag whose tag name is "table" */
- } elseif ($token['type'] === HTML5::STARTTAG &&
- $token['name'] === 'table'
- ) {
- /* Parse error. Act as if an end tag token with the tag name "table"
- had been seen, then, if that token wasn't ignored, reprocess the
- current token. */
- $this->inTable(
- array(
- 'name' => 'table',
- 'type' => HTML5::ENDTAG
- )
- );
-
- return $this->mainPhase($token);
-
- /* An end tag whose tag name is "table" */
- } elseif ($token['type'] === HTML5::ENDTAG &&
- $token['name'] === 'table'
- ) {
- /* If the stack of open elements does not have an element in table
- scope with the same tag name as the token, this is a parse error.
- Ignore the token. (innerHTML case) */
- if (!$this->elementInScope($token['name'], true)) {
- return false;
-
- /* Otherwise: */
- } else {
- /* Generate implied end tags. */
- $this->generateImpliedEndTags();
-
- /* Now, if the current node is not a table element, then this
- is a parse error. */
- // w/e
-
- /* Pop elements from this stack until a table element has been
- popped from the stack. */
- while (true) {
- $current = end($this->stack)->nodeName;
- array_pop($this->stack);
-
- if ($current === 'table') {
- break;
- }
- }
-
- /* Reset the insertion mode appropriately. */
- $this->resetInsertionMode();
- }
-
- /* An end tag whose tag name is one of: "body", "caption", "col",
- "colgroup", "html", "tbody", "td", "tfoot", "th", "thead", "tr" */
- } elseif ($token['type'] === HTML5::ENDTAG && in_array(
- $token['name'],
- array(
- 'body',
- 'caption',
- 'col',
- 'colgroup',
- 'html',
- 'tbody',
- 'td',
- 'tfoot',
- 'th',
- 'thead',
- 'tr'
- )
- )
- ) {
- // Parse error. Ignore the token.
-
- /* Anything else */
- } else {
- /* Parse error. Process the token as if the insertion mode was "in
- body", with the following exception: */
-
- /* If the current node is a table, tbody, tfoot, thead, or tr
- element, then, whenever a node would be inserted into the current
- node, it must instead be inserted into the foster parent element. */
- if (in_array(
- end($this->stack)->nodeName,
- array('table', 'tbody', 'tfoot', 'thead', 'tr')
- )
- ) {
- /* The foster parent element is the parent element of the last
- table element in the stack of open elements, if there is a
- table element and it has such a parent element. If there is no
- table element in the stack of open elements (innerHTML case),
- then the foster parent element is the first element in the
- stack of open elements (the html element). Otherwise, if there
- is a table element in the stack of open elements, but the last
- table element in the stack of open elements has no parent, or
- its parent node is not an element, then the foster parent
- element is the element before the last table element in the
- stack of open elements. */
- for ($n = count($this->stack) - 1; $n >= 0; $n--) {
- if ($this->stack[$n]->nodeName === 'table') {
- $table = $this->stack[$n];
- break;
- }
- }
-
- if (isset($table) && $table->parentNode !== null) {
- $this->foster_parent = $table->parentNode;
-
- } elseif (!isset($table)) {
- $this->foster_parent = $this->stack[0];
-
- } elseif (isset($table) && ($table->parentNode === null ||
- $table->parentNode->nodeType !== XML_ELEMENT_NODE)
- ) {
- $this->foster_parent = $this->stack[$n - 1];
- }
- }
-
- $this->inBody($token);
- }
- }
-
- private function inCaption($token)
- {
- /* An end tag whose tag name is "caption" */
- if ($token['type'] === HTML5::ENDTAG && $token['name'] === 'caption') {
- /* If the stack of open elements does not have an element in table
- scope with the same tag name as the token, this is a parse error.
- Ignore the token. (innerHTML case) */
- if (!$this->elementInScope($token['name'], true)) {
- // Ignore
-
- /* Otherwise: */
- } else {
- /* Generate implied end tags. */
- $this->generateImpliedEndTags();
-
- /* Now, if the current node is not a caption element, then this
- is a parse error. */
- // w/e
-
- /* Pop elements from this stack until a caption element has
- been popped from the stack. */
- while (true) {
- $node = end($this->stack)->nodeName;
- array_pop($this->stack);
-
- if ($node === 'caption') {
- break;
- }
- }
-
- /* Clear the list of active formatting elements up to the last
- marker. */
- $this->clearTheActiveFormattingElementsUpToTheLastMarker();
-
- /* Switch the insertion mode to "in table". */
- $this->mode = self::IN_TABLE;
- }
-
- /* A start tag whose tag name is one of: "caption", "col", "colgroup",
- "tbody", "td", "tfoot", "th", "thead", "tr", or an end tag whose tag
- name is "table" */
- } elseif (($token['type'] === HTML5::STARTTAG && in_array(
- $token['name'],
- array(
- 'caption',
- 'col',
- 'colgroup',
- 'tbody',
- 'td',
- 'tfoot',
- 'th',
- 'thead',
- 'tr'
- )
- )) || ($token['type'] === HTML5::ENDTAG &&
- $token['name'] === 'table')
- ) {
- /* Parse error. Act as if an end tag with the tag name "caption"
- had been seen, then, if that token wasn't ignored, reprocess the
- current token. */
- $this->inCaption(
- array(
- 'name' => 'caption',
- 'type' => HTML5::ENDTAG
- )
- );
-
- return $this->inTable($token);
-
- /* An end tag whose tag name is one of: "body", "col", "colgroup",
- "html", "tbody", "td", "tfoot", "th", "thead", "tr" */
- } elseif ($token['type'] === HTML5::ENDTAG && in_array(
- $token['name'],
- array(
- 'body',
- 'col',
- 'colgroup',
- 'html',
- 'tbody',
- 'tfoot',
- 'th',
- 'thead',
- 'tr'
- )
- )
- ) {
- // Parse error. Ignore the token.
-
- /* Anything else */
- } else {
- /* Process the token as if the insertion mode was "in body". */
- $this->inBody($token);
- }
- }
-
- private function inColumnGroup($token)
- {
- /* A character token that is one of one of U+0009 CHARACTER TABULATION,
- U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
- or U+0020 SPACE */
- if ($token['type'] === HTML5::CHARACTR &&
- preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])
- ) {
- /* Append the character to the current node. */
- $text = $this->dom->createTextNode($token['data']);
- end($this->stack)->appendChild($text);
-
- /* A comment token */
- } elseif ($token['type'] === HTML5::COMMENT) {
- /* Append a Comment node to the current node with the data
- attribute set to the data given in the comment token. */
- $comment = $this->dom->createComment($token['data']);
- end($this->stack)->appendChild($comment);
-
- /* A start tag whose tag name is "col" */
- } elseif ($token['type'] === HTML5::STARTTAG && $token['name'] === 'col') {
- /* Insert a col element for the token. Immediately pop the current
- node off the stack of open elements. */
- $this->insertElement($token);
- array_pop($this->stack);
-
- /* An end tag whose tag name is "colgroup" */
- } elseif ($token['type'] === HTML5::ENDTAG &&
- $token['name'] === 'colgroup'
- ) {
- /* If the current node is the root html element, then this is a
- parse error, ignore the token. (innerHTML case) */
- if (end($this->stack)->nodeName === 'html') {
- // Ignore
-
- /* Otherwise, pop the current node (which will be a colgroup
- element) from the stack of open elements. Switch the insertion
- mode to "in table". */
- } else {
- array_pop($this->stack);
- $this->mode = self::IN_TABLE;
- }
-
- /* An end tag whose tag name is "col" */
- } elseif ($token['type'] === HTML5::ENDTAG && $token['name'] === 'col') {
- /* Parse error. Ignore the token. */
-
- /* Anything else */
- } else {
- /* Act as if an end tag with the tag name "colgroup" had been seen,
- and then, if that token wasn't ignored, reprocess the current token. */
- $this->inColumnGroup(
- array(
- 'name' => 'colgroup',
- 'type' => HTML5::ENDTAG
- )
- );
-
- return $this->inTable($token);
- }
- }
-
- private function inTableBody($token)
- {
- $clear = array('tbody', 'tfoot', 'thead', 'html');
-
- /* A start tag whose tag name is "tr" */
- if ($token['type'] === HTML5::STARTTAG && $token['name'] === 'tr') {
- /* Clear the stack back to a table body context. */
- $this->clearStackToTableContext($clear);
-
- /* Insert a tr element for the token, then switch the insertion
- mode to "in row". */
- $this->insertElement($token);
- $this->mode = self::IN_ROW;
-
- /* A start tag whose tag name is one of: "th", "td" */
- } elseif ($token['type'] === HTML5::STARTTAG &&
- ($token['name'] === 'th' || $token['name'] === 'td')
- ) {
- /* Parse error. Act as if a start tag with the tag name "tr" had
- been seen, then reprocess the current token. */
- $this->inTableBody(
- array(
- 'name' => 'tr',
- 'type' => HTML5::STARTTAG,
- 'attr' => array()
- )
- );
-
- return $this->inRow($token);
-
- /* An end tag whose tag name is one of: "tbody", "tfoot", "thead" */
- } elseif ($token['type'] === HTML5::ENDTAG &&
- in_array($token['name'], array('tbody', 'tfoot', 'thead'))
- ) {
- /* If the stack of open elements does not have an element in table
- scope with the same tag name as the token, this is a parse error.
- Ignore the token. */
- if (!$this->elementInScope($token['name'], true)) {
- // Ignore
-
- /* Otherwise: */
- } else {
- /* Clear the stack back to a table body context. */
- $this->clearStackToTableContext($clear);
-
- /* Pop the current node from the stack of open elements. Switch
- the insertion mode to "in table". */
- array_pop($this->stack);
- $this->mode = self::IN_TABLE;
- }
-
- /* A start tag whose tag name is one of: "caption", "col", "colgroup",
- "tbody", "tfoot", "thead", or an end tag whose tag name is "table" */
- } elseif (($token['type'] === HTML5::STARTTAG && in_array(
- $token['name'],
- array('caption', 'col', 'colgroup', 'tbody', 'tfoor', 'thead')
- )) ||
- ($token['type'] === HTML5::STARTTAG && $token['name'] === 'table')
- ) {
- /* If the stack of open elements does not have a tbody, thead, or
- tfoot element in table scope, this is a parse error. Ignore the
- token. (innerHTML case) */
- if (!$this->elementInScope(array('tbody', 'thead', 'tfoot'), true)) {
- // Ignore.
-
- /* Otherwise: */
- } else {
- /* Clear the stack back to a table body context. */
- $this->clearStackToTableContext($clear);
-
- /* Act as if an end tag with the same tag name as the current
- node ("tbody", "tfoot", or "thead") had been seen, then
- reprocess the current token. */
- $this->inTableBody(
- array(
- 'name' => end($this->stack)->nodeName,
- 'type' => HTML5::ENDTAG
- )
- );
-
- return $this->mainPhase($token);
- }
-
- /* An end tag whose tag name is one of: "body", "caption", "col",
- "colgroup", "html", "td", "th", "tr" */
- } elseif ($token['type'] === HTML5::ENDTAG && in_array(
- $token['name'],
- array('body', 'caption', 'col', 'colgroup', 'html', 'td', 'th', 'tr')
- )
- ) {
- /* Parse error. Ignore the token. */
-
- /* Anything else */
- } else {
- /* Process the token as if the insertion mode was "in table". */
- $this->inTable($token);
- }
- }
-
- private function inRow($token)
- {
- $clear = array('tr', 'html');
-
- /* A start tag whose tag name is one of: "th", "td" */
- if ($token['type'] === HTML5::STARTTAG &&
- ($token['name'] === 'th' || $token['name'] === 'td')
- ) {
- /* Clear the stack back to a table row context. */
- $this->clearStackToTableContext($clear);
-
- /* Insert an HTML element for the token, then switch the insertion
- mode to "in cell". */
- $this->insertElement($token);
- $this->mode = self::IN_CELL;
-
- /* Insert a marker at the end of the list of active formatting
- elements. */
- $this->a_formatting[] = self::MARKER;
-
- /* An end tag whose tag name is "tr" */
- } elseif ($token['type'] === HTML5::ENDTAG && $token['name'] === 'tr') {
- /* If the stack of open elements does not have an element in table
- scope with the same tag name as the token, this is a parse error.
- Ignore the token. (innerHTML case) */
- if (!$this->elementInScope($token['name'], true)) {
- // Ignore.
-
- /* Otherwise: */
- } else {
- /* Clear the stack back to a table row context. */
- $this->clearStackToTableContext($clear);
-
- /* Pop the current node (which will be a tr element) from the
- stack of open elements. Switch the insertion mode to "in table
- body". */
- array_pop($this->stack);
- $this->mode = self::IN_TBODY;
- }
-
- /* A start tag whose tag name is one of: "caption", "col", "colgroup",
- "tbody", "tfoot", "thead", "tr" or an end tag whose tag name is "table" */
- } elseif ($token['type'] === HTML5::STARTTAG && in_array(
- $token['name'],
- array('caption', 'col', 'colgroup', 'tbody', 'tfoot', 'thead', 'tr')
- )
- ) {
- /* Act as if an end tag with the tag name "tr" had been seen, then,
- if that token wasn't ignored, reprocess the current token. */
- $this->inRow(
- array(
- 'name' => 'tr',
- 'type' => HTML5::ENDTAG
- )
- );
-
- return $this->inCell($token);
-
- /* An end tag whose tag name is one of: "tbody", "tfoot", "thead" */
- } elseif ($token['type'] === HTML5::ENDTAG &&
- in_array($token['name'], array('tbody', 'tfoot', 'thead'))
- ) {
- /* If the stack of open elements does not have an element in table
- scope with the same tag name as the token, this is a parse error.
- Ignore the token. */
- if (!$this->elementInScope($token['name'], true)) {
- // Ignore.
-
- /* Otherwise: */
- } else {
- /* Otherwise, act as if an end tag with the tag name "tr" had
- been seen, then reprocess the current token. */
- $this->inRow(
- array(
- 'name' => 'tr',
- 'type' => HTML5::ENDTAG
- )
- );
-
- return $this->inCell($token);
- }
-
- /* An end tag whose tag name is one of: "body", "caption", "col",
- "colgroup", "html", "td", "th" */
- } elseif ($token['type'] === HTML5::ENDTAG && in_array(
- $token['name'],
- array('body', 'caption', 'col', 'colgroup', 'html', 'td', 'th', 'tr')
- )
- ) {
- /* Parse error. Ignore the token. */
-
- /* Anything else */
- } else {
- /* Process the token as if the insertion mode was "in table". */
- $this->inTable($token);
- }
- }
-
- private function inCell($token)
- {
- /* An end tag whose tag name is one of: "td", "th" */
- if ($token['type'] === HTML5::ENDTAG &&
- ($token['name'] === 'td' || $token['name'] === 'th')
- ) {
- /* If the stack of open elements does not have an element in table
- scope with the same tag name as that of the token, then this is a
- parse error and the token must be ignored. */
- if (!$this->elementInScope($token['name'], true)) {
- // Ignore.
-
- /* Otherwise: */
- } else {
- /* Generate implied end tags, except for elements with the same
- tag name as the token. */
- $this->generateImpliedEndTags(array($token['name']));
-
- /* Now, if the current node is not an element with the same tag
- name as the token, then this is a parse error. */
- // k
-
- /* Pop elements from this stack until an element with the same
- tag name as the token has been popped from the stack. */
- while (true) {
- $node = end($this->stack)->nodeName;
- array_pop($this->stack);
-
- if ($node === $token['name']) {
- break;
- }
- }
-
- /* Clear the list of active formatting elements up to the last
- marker. */
- $this->clearTheActiveFormattingElementsUpToTheLastMarker();
-
- /* Switch the insertion mode to "in row". (The current node
- will be a tr element at this point.) */
- $this->mode = self::IN_ROW;
- }
-
- /* A start tag whose tag name is one of: "caption", "col", "colgroup",
- "tbody", "td", "tfoot", "th", "thead", "tr" */
- } elseif ($token['type'] === HTML5::STARTTAG && in_array(
- $token['name'],
- array(
- 'caption',
- 'col',
- 'colgroup',
- 'tbody',
- 'td',
- 'tfoot',
- 'th',
- 'thead',
- 'tr'
- )
- )
- ) {
- /* If the stack of open elements does not have a td or th element
- in table scope, then this is a parse error; ignore the token.
- (innerHTML case) */
- if (!$this->elementInScope(array('td', 'th'), true)) {
- // Ignore.
-
- /* Otherwise, close the cell (see below) and reprocess the current
- token. */
- } else {
- $this->closeCell();
- return $this->inRow($token);
- }
-
- /* A start tag whose tag name is one of: "caption", "col", "colgroup",
- "tbody", "td", "tfoot", "th", "thead", "tr" */
- } elseif ($token['type'] === HTML5::STARTTAG && in_array(
- $token['name'],
- array(
- 'caption',
- 'col',
- 'colgroup',
- 'tbody',
- 'td',
- 'tfoot',
- 'th',
- 'thead',
- 'tr'
- )
- )
- ) {
- /* If the stack of open elements does not have a td or th element
- in table scope, then this is a parse error; ignore the token.
- (innerHTML case) */
- if (!$this->elementInScope(array('td', 'th'), true)) {
- // Ignore.
-
- /* Otherwise, close the cell (see below) and reprocess the current
- token. */
- } else {
- $this->closeCell();
- return $this->inRow($token);
- }
-
- /* An end tag whose tag name is one of: "body", "caption", "col",
- "colgroup", "html" */
- } elseif ($token['type'] === HTML5::ENDTAG && in_array(
- $token['name'],
- array('body', 'caption', 'col', 'colgroup', 'html')
- )
- ) {
- /* Parse error. Ignore the token. */
-
- /* An end tag whose tag name is one of: "table", "tbody", "tfoot",
- "thead", "tr" */
- } elseif ($token['type'] === HTML5::ENDTAG && in_array(
- $token['name'],
- array('table', 'tbody', 'tfoot', 'thead', 'tr')
- )
- ) {
- /* If the stack of open elements does not have an element in table
- scope with the same tag name as that of the token (which can only
- happen for "tbody", "tfoot" and "thead", or, in the innerHTML case),
- then this is a parse error and the token must be ignored. */
- if (!$this->elementInScope($token['name'], true)) {
- // Ignore.
-
- /* Otherwise, close the cell (see below) and reprocess the current
- token. */
- } else {
- $this->closeCell();
- return $this->inRow($token);
- }
-
- /* Anything else */
- } else {
- /* Process the token as if the insertion mode was "in body". */
- $this->inBody($token);
- }
- }
-
- private function inSelect($token)
- {
- /* Handle the token as follows: */
-
- /* A character token */
- if ($token['type'] === HTML5::CHARACTR) {
- /* Append the token's character to the current node. */
- $this->insertText($token['data']);
-
- /* A comment token */
- } elseif ($token['type'] === HTML5::COMMENT) {
- /* Append a Comment node to the current node with the data
- attribute set to the data given in the comment token. */
- $this->insertComment($token['data']);
-
- /* A start tag token whose tag name is "option" */
- } elseif ($token['type'] === HTML5::STARTTAG &&
- $token['name'] === 'option'
- ) {
- /* If the current node is an option element, act as if an end tag
- with the tag name "option" had been seen. */
- if (end($this->stack)->nodeName === 'option') {
- $this->inSelect(
- array(
- 'name' => 'option',
- 'type' => HTML5::ENDTAG
- )
- );
- }
-
- /* Insert an HTML element for the token. */
- $this->insertElement($token);
-
- /* A start tag token whose tag name is "optgroup" */
- } elseif ($token['type'] === HTML5::STARTTAG &&
- $token['name'] === 'optgroup'
- ) {
- /* If the current node is an option element, act as if an end tag
- with the tag name "option" had been seen. */
- if (end($this->stack)->nodeName === 'option') {
- $this->inSelect(
- array(
- 'name' => 'option',
- 'type' => HTML5::ENDTAG
- )
- );
- }
-
- /* If the current node is an optgroup element, act as if an end tag
- with the tag name "optgroup" had been seen. */
- if (end($this->stack)->nodeName === 'optgroup') {
- $this->inSelect(
- array(
- 'name' => 'optgroup',
- 'type' => HTML5::ENDTAG
- )
- );
- }
-
- /* Insert an HTML element for the token. */
- $this->insertElement($token);
-
- /* An end tag token whose tag name is "optgroup" */
- } elseif ($token['type'] === HTML5::ENDTAG &&
- $token['name'] === 'optgroup'
- ) {
- /* First, if the current node is an option element, and the node
- immediately before it in the stack of open elements is an optgroup
- element, then act as if an end tag with the tag name "option" had
- been seen. */
- $elements_in_stack = count($this->stack);
-
- if ($this->stack[$elements_in_stack - 1]->nodeName === 'option' &&
- $this->stack[$elements_in_stack - 2]->nodeName === 'optgroup'
- ) {
- $this->inSelect(
- array(
- 'name' => 'option',
- 'type' => HTML5::ENDTAG
- )
- );
- }
-
- /* If the current node is an optgroup element, then pop that node
- from the stack of open elements. Otherwise, this is a parse error,
- ignore the token. */
- if ($this->stack[$elements_in_stack - 1] === 'optgroup') {
- array_pop($this->stack);
- }
-
- /* An end tag token whose tag name is "option" */
- } elseif ($token['type'] === HTML5::ENDTAG &&
- $token['name'] === 'option'
- ) {
- /* If the current node is an option element, then pop that node
- from the stack of open elements. Otherwise, this is a parse error,
- ignore the token. */
- if (end($this->stack)->nodeName === 'option') {
- array_pop($this->stack);
- }
-
- /* An end tag whose tag name is "select" */
- } elseif ($token['type'] === HTML5::ENDTAG &&
- $token['name'] === 'select'
- ) {
- /* If the stack of open elements does not have an element in table
- scope with the same tag name as the token, this is a parse error.
- Ignore the token. (innerHTML case) */
- if (!$this->elementInScope($token['name'], true)) {
- // w/e
-
- /* Otherwise: */
- } else {
- /* Pop elements from the stack of open elements until a select
- element has been popped from the stack. */
- while (true) {
- $current = end($this->stack)->nodeName;
- array_pop($this->stack);
-
- if ($current === 'select') {
- break;
- }
- }
-
- /* Reset the insertion mode appropriately. */
- $this->resetInsertionMode();
- }
-
- /* A start tag whose tag name is "select" */
- } elseif ($token['name'] === 'select' &&
- $token['type'] === HTML5::STARTTAG
- ) {
- /* Parse error. Act as if the token had been an end tag with the
- tag name "select" instead. */
- $this->inSelect(
- array(
- 'name' => 'select',
- 'type' => HTML5::ENDTAG
- )
- );
-
- /* An end tag whose tag name is one of: "caption", "table", "tbody",
- "tfoot", "thead", "tr", "td", "th" */
- } elseif (in_array(
- $token['name'],
- array(
- 'caption',
- 'table',
- 'tbody',
- 'tfoot',
- 'thead',
- 'tr',
- 'td',
- 'th'
- )
- ) && $token['type'] === HTML5::ENDTAG
- ) {
- /* Parse error. */
- // w/e
-
- /* If the stack of open elements has an element in table scope with
- the same tag name as that of the token, then act as if an end tag
- with the tag name "select" had been seen, and reprocess the token.
- Otherwise, ignore the token. */
- if ($this->elementInScope($token['name'], true)) {
- $this->inSelect(
- array(
- 'name' => 'select',
- 'type' => HTML5::ENDTAG
- )
- );
-
- $this->mainPhase($token);
- }
-
- /* Anything else */
- } else {
- /* Parse error. Ignore the token. */
- }
- }
-
- private function afterBody($token)
- {
- /* Handle the token as follows: */
-
- /* A character token that is one of one of U+0009 CHARACTER TABULATION,
- U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
- or U+0020 SPACE */
- if ($token['type'] === HTML5::CHARACTR &&
- preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])
- ) {
- /* Process the token as it would be processed if the insertion mode
- was "in body". */
- $this->inBody($token);
-
- /* A comment token */
- } elseif ($token['type'] === HTML5::COMMENT) {
- /* Append a Comment node to the first element in the stack of open
- elements (the html element), with the data attribute set to the
- data given in the comment token. */
- $comment = $this->dom->createComment($token['data']);
- $this->stack[0]->appendChild($comment);
-
- /* An end tag with the tag name "html" */
- } elseif ($token['type'] === HTML5::ENDTAG && $token['name'] === 'html') {
- /* If the parser was originally created in order to handle the
- setting of an element's innerHTML attribute, this is a parse error;
- ignore the token. (The element will be an html element in this
- case.) (innerHTML case) */
-
- /* Otherwise, switch to the trailing end phase. */
- $this->phase = self::END_PHASE;
-
- /* Anything else */
- } else {
- /* Parse error. Set the insertion mode to "in body" and reprocess
- the token. */
- $this->mode = self::IN_BODY;
- return $this->inBody($token);
- }
- }
-
- private function inFrameset($token)
- {
- /* Handle the token as follows: */
-
- /* A character token that is one of one of U+0009 CHARACTER TABULATION,
- U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
- U+000D CARRIAGE RETURN (CR), or U+0020 SPACE */
- if ($token['type'] === HTML5::CHARACTR &&
- preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])
- ) {
- /* Append the character to the current node. */
- $this->insertText($token['data']);
-
- /* A comment token */
- } elseif ($token['type'] === HTML5::COMMENT) {
- /* Append a Comment node to the current node with the data
- attribute set to the data given in the comment token. */
- $this->insertComment($token['data']);
-
- /* A start tag with the tag name "frameset" */
- } elseif ($token['name'] === 'frameset' &&
- $token['type'] === HTML5::STARTTAG
- ) {
- $this->insertElement($token);
-
- /* An end tag with the tag name "frameset" */
- } elseif ($token['name'] === 'frameset' &&
- $token['type'] === HTML5::ENDTAG
- ) {
- /* If the current node is the root html element, then this is a
- parse error; ignore the token. (innerHTML case) */
- if (end($this->stack)->nodeName === 'html') {
- // Ignore
-
- } else {
- /* Otherwise, pop the current node from the stack of open
- elements. */
- array_pop($this->stack);
-
- /* If the parser was not originally created in order to handle
- the setting of an element's innerHTML attribute (innerHTML case),
- and the current node is no longer a frameset element, then change
- the insertion mode to "after frameset". */
- $this->mode = self::AFTR_FRAME;
- }
-
- /* A start tag with the tag name "frame" */
- } elseif ($token['name'] === 'frame' &&
- $token['type'] === HTML5::STARTTAG
- ) {
- /* Insert an HTML element for the token. */
- $this->insertElement($token);
-
- /* Immediately pop the current node off the stack of open elements. */
- array_pop($this->stack);
-
- /* A start tag with the tag name "noframes" */
- } elseif ($token['name'] === 'noframes' &&
- $token['type'] === HTML5::STARTTAG
- ) {
- /* Process the token as if the insertion mode had been "in body". */
- $this->inBody($token);
-
- /* Anything else */
- } else {
- /* Parse error. Ignore the token. */
- }
- }
-
- private function afterFrameset($token)
- {
- /* Handle the token as follows: */
-
- /* A character token that is one of one of U+0009 CHARACTER TABULATION,
- U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
- U+000D CARRIAGE RETURN (CR), or U+0020 SPACE */
- if ($token['type'] === HTML5::CHARACTR &&
- preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])
- ) {
- /* Append the character to the current node. */
- $this->insertText($token['data']);
-
- /* A comment token */
- } elseif ($token['type'] === HTML5::COMMENT) {
- /* Append a Comment node to the current node with the data
- attribute set to the data given in the comment token. */
- $this->insertComment($token['data']);
-
- /* An end tag with the tag name "html" */
- } elseif ($token['name'] === 'html' &&
- $token['type'] === HTML5::ENDTAG
- ) {
- /* Switch to the trailing end phase. */
- $this->phase = self::END_PHASE;
-
- /* A start tag with the tag name "noframes" */
- } elseif ($token['name'] === 'noframes' &&
- $token['type'] === HTML5::STARTTAG
- ) {
- /* Process the token as if the insertion mode had been "in body". */
- $this->inBody($token);
-
- /* Anything else */
- } else {
- /* Parse error. Ignore the token. */
- }
- }
-
- private function trailingEndPhase($token)
- {
- /* After the main phase, as each token is emitted from the tokenisation
- stage, it must be processed as described in this section. */
-
- /* A DOCTYPE token */
- if ($token['type'] === HTML5::DOCTYPE) {
- // Parse error. Ignore the token.
-
- /* A comment token */
- } elseif ($token['type'] === HTML5::COMMENT) {
- /* Append a Comment node to the Document object with the data
- attribute set to the data given in the comment token. */
- $comment = $this->dom->createComment($token['data']);
- $this->dom->appendChild($comment);
-
- /* A character token that is one of one of U+0009 CHARACTER TABULATION,
- U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
- or U+0020 SPACE */
- } elseif ($token['type'] === HTML5::CHARACTR &&
- preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])
- ) {
- /* Process the token as it would be processed in the main phase. */
- $this->mainPhase($token);
-
- /* A character token that is not one of U+0009 CHARACTER TABULATION,
- U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
- or U+0020 SPACE. Or a start tag token. Or an end tag token. */
- } elseif (($token['type'] === HTML5::CHARACTR &&
- preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])) ||
- $token['type'] === HTML5::STARTTAG || $token['type'] === HTML5::ENDTAG
- ) {
- /* Parse error. Switch back to the main phase and reprocess the
- token. */
- $this->phase = self::MAIN_PHASE;
- return $this->mainPhase($token);
-
- /* An end-of-file token */
- } elseif ($token['type'] === HTML5::EOF) {
- /* OMG DONE!! */
- }
- }
-
- private function insertElement($token, $append = true, $check = false)
- {
- // Proprietary workaround for libxml2's limitations with tag names
- if ($check) {
- // Slightly modified HTML5 tag-name modification,
- // removing anything that's not an ASCII letter, digit, or hyphen
- $token['name'] = preg_replace('/[^a-z0-9-]/i', '', $token['name']);
- // Remove leading hyphens and numbers
- $token['name'] = ltrim($token['name'], '-0..9');
- // In theory, this should ever be needed, but just in case
- if ($token['name'] === '') {
- $token['name'] = 'span';
- } // arbitrary generic choice
- }
-
- $el = $this->dom->createElement($token['name']);
-
- foreach ($token['attr'] as $attr) {
- if (!$el->hasAttribute($attr['name'])) {
- $el->setAttribute($attr['name'], $attr['value']);
- }
- }
-
- $this->appendToRealParent($el);
- $this->stack[] = $el;
-
- return $el;
- }
-
- private function insertText($data)
- {
- $text = $this->dom->createTextNode($data);
- $this->appendToRealParent($text);
- }
-
- private function insertComment($data)
- {
- $comment = $this->dom->createComment($data);
- $this->appendToRealParent($comment);
- }
-
- private function appendToRealParent($node)
- {
- if ($this->foster_parent === null) {
- end($this->stack)->appendChild($node);
-
- } elseif ($this->foster_parent !== null) {
- /* If the foster parent element is the parent element of the
- last table element in the stack of open elements, then the new
- node must be inserted immediately before the last table element
- in the stack of open elements in the foster parent element;
- otherwise, the new node must be appended to the foster parent
- element. */
- for ($n = count($this->stack) - 1; $n >= 0; $n--) {
- if ($this->stack[$n]->nodeName === 'table' &&
- $this->stack[$n]->parentNode !== null
- ) {
- $table = $this->stack[$n];
- break;
- }
- }
-
- if (isset($table) && $this->foster_parent->isSameNode($table->parentNode)) {
- $this->foster_parent->insertBefore($node, $table);
- } else {
- $this->foster_parent->appendChild($node);
- }
-
- $this->foster_parent = null;
- }
- }
-
- private function elementInScope($el, $table = false)
- {
- if (is_array($el)) {
- foreach ($el as $element) {
- if ($this->elementInScope($element, $table)) {
- return true;
- }
- }
-
- return false;
- }
-
- $leng = count($this->stack);
-
- for ($n = 0; $n < $leng; $n++) {
- /* 1. Initialise node to be the current node (the bottommost node of
- the stack). */
- $node = $this->stack[$leng - 1 - $n];
-
- if ($node->tagName === $el) {
- /* 2. If node is the target node, terminate in a match state. */
- return true;
-
- } elseif ($node->tagName === 'table') {
- /* 3. Otherwise, if node is a table element, terminate in a failure
- state. */
- return false;
-
- } elseif ($table === true && in_array(
- $node->tagName,
- array(
- 'caption',
- 'td',
- 'th',
- 'button',
- 'marquee',
- 'object'
- )
- )
- ) {
- /* 4. Otherwise, if the algorithm is the "has an element in scope"
- variant (rather than the "has an element in table scope" variant),
- and node is one of the following, terminate in a failure state. */
- return false;
-
- } elseif ($node === $node->ownerDocument->documentElement) {
- /* 5. Otherwise, if node is an html element (root element), terminate
- in a failure state. (This can only happen if the node is the topmost
- node of the stack of open elements, and prevents the next step from
- being invoked if there are no more elements in the stack.) */
- return false;
- }
-
- /* Otherwise, set node to the previous entry in the stack of open
- elements and return to step 2. (This will never fail, since the loop
- will always terminate in the previous step if the top of the stack
- is reached.) */
- }
- }
-
- private function reconstructActiveFormattingElements()
- {
- /* 1. If there are no entries in the list of active formatting elements,
- then there is nothing to reconstruct; stop this algorithm. */
- $formatting_elements = count($this->a_formatting);
-
- if ($formatting_elements === 0) {
- return false;
- }
-
- /* 3. Let entry be the last (most recently added) element in the list
- of active formatting elements. */
- $entry = end($this->a_formatting);
-
- /* 2. If the last (most recently added) entry in the list of active
- formatting elements is a marker, or if it is an element that is in the
- stack of open elements, then there is nothing to reconstruct; stop this
- algorithm. */
- if ($entry === self::MARKER || in_array($entry, $this->stack, true)) {
- return false;
- }
-
- for ($a = $formatting_elements - 1; $a >= 0; true) {
- /* 4. If there are no entries before entry in the list of active
- formatting elements, then jump to step 8. */
- if ($a === 0) {
- $step_seven = false;
- break;
- }
-
- /* 5. Let entry be the entry one earlier than entry in the list of
- active formatting elements. */
- $a--;
- $entry = $this->a_formatting[$a];
-
- /* 6. If entry is neither a marker nor an element that is also in
- thetack of open elements, go to step 4. */
- if ($entry === self::MARKER || in_array($entry, $this->stack, true)) {
- break;
- }
- }
-
- while (true) {
- /* 7. Let entry be the element one later than entry in the list of
- active formatting elements. */
- if (isset($step_seven) && $step_seven === true) {
- $a++;
- $entry = $this->a_formatting[$a];
- }
-
- /* 8. Perform a shallow clone of the element entry to obtain clone. */
- $clone = $entry->cloneNode();
-
- /* 9. Append clone to the current node and push it onto the stack
- of open elements so that it is the new current node. */
- end($this->stack)->appendChild($clone);
- $this->stack[] = $clone;
-
- /* 10. Replace the entry for entry in the list with an entry for
- clone. */
- $this->a_formatting[$a] = $clone;
-
- /* 11. If the entry for clone in the list of active formatting
- elements is not the last entry in the list, return to step 7. */
- if (end($this->a_formatting) !== $clone) {
- $step_seven = true;
- } else {
- break;
- }
- }
- }
-
- private function clearTheActiveFormattingElementsUpToTheLastMarker()
- {
- /* When the steps below require the UA to clear the list of active
- formatting elements up to the last marker, the UA must perform the
- following steps: */
-
- while (true) {
- /* 1. Let entry be the last (most recently added) entry in the list
- of active formatting elements. */
- $entry = end($this->a_formatting);
-
- /* 2. Remove entry from the list of active formatting elements. */
- array_pop($this->a_formatting);
-
- /* 3. If entry was a marker, then stop the algorithm at this point.
- The list has been cleared up to the last marker. */
- if ($entry === self::MARKER) {
- break;
- }
- }
- }
-
- private function generateImpliedEndTags($exclude = array())
- {
- /* When the steps below require the UA to generate implied end tags,
- then, if the current node is a dd element, a dt element, an li element,
- a p element, a td element, a th element, or a tr element, the UA must
- act as if an end tag with the respective tag name had been seen and
- then generate implied end tags again. */
- $node = end($this->stack);
- $elements = array_diff(array('dd', 'dt', 'li', 'p', 'td', 'th', 'tr'), $exclude);
-
- while (in_array(end($this->stack)->nodeName, $elements)) {
- array_pop($this->stack);
- }
- }
-
- private function getElementCategory($node)
- {
- $name = $node->tagName;
- if (in_array($name, $this->special)) {
- return self::SPECIAL;
- } elseif (in_array($name, $this->scoping)) {
- return self::SCOPING;
- } elseif (in_array($name, $this->formatting)) {
- return self::FORMATTING;
- } else {
- return self::PHRASING;
- }
- }
-
- private function clearStackToTableContext($elements)
- {
- /* When the steps above require the UA to clear the stack back to a
- table context, it means that the UA must, while the current node is not
- a table element or an html element, pop elements from the stack of open
- elements. If this causes any elements to be popped from the stack, then
- this is a parse error. */
- while (true) {
- $node = end($this->stack)->nodeName;
-
- if (in_array($node, $elements)) {
- break;
- } else {
- array_pop($this->stack);
- }
- }
- }
-
- private function resetInsertionMode()
- {
- /* 1. Let last be false. */
- $last = false;
- $leng = count($this->stack);
-
- for ($n = $leng - 1; $n >= 0; $n--) {
- /* 2. Let node be the last node in the stack of open elements. */
- $node = $this->stack[$n];
-
- /* 3. If node is the first node in the stack of open elements, then
- set last to true. If the element whose innerHTML attribute is being
- set is neither a td element nor a th element, then set node to the
- element whose innerHTML attribute is being set. (innerHTML case) */
- if ($this->stack[0]->isSameNode($node)) {
- $last = true;
- }
-
- /* 4. If node is a select element, then switch the insertion mode to
- "in select" and abort these steps. (innerHTML case) */
- if ($node->nodeName === 'select') {
- $this->mode = self::IN_SELECT;
- break;
-
- /* 5. If node is a td or th element, then switch the insertion mode
- to "in cell" and abort these steps. */
- } elseif ($node->nodeName === 'td' || $node->nodeName === 'th') {
- $this->mode = self::IN_CELL;
- break;
-
- /* 6. If node is a tr element, then switch the insertion mode to
- "in row" and abort these steps. */
- } elseif ($node->nodeName === 'tr') {
- $this->mode = self::IN_ROW;
- break;
-
- /* 7. If node is a tbody, thead, or tfoot element, then switch the
- insertion mode to "in table body" and abort these steps. */
- } elseif (in_array($node->nodeName, array('tbody', 'thead', 'tfoot'))) {
- $this->mode = self::IN_TBODY;
- break;
-
- /* 8. If node is a caption element, then switch the insertion mode
- to "in caption" and abort these steps. */
- } elseif ($node->nodeName === 'caption') {
- $this->mode = self::IN_CAPTION;
- break;
-
- /* 9. If node is a colgroup element, then switch the insertion mode
- to "in column group" and abort these steps. (innerHTML case) */
- } elseif ($node->nodeName === 'colgroup') {
- $this->mode = self::IN_CGROUP;
- break;
-
- /* 10. If node is a table element, then switch the insertion mode
- to "in table" and abort these steps. */
- } elseif ($node->nodeName === 'table') {
- $this->mode = self::IN_TABLE;
- break;
-
- /* 11. If node is a head element, then switch the insertion mode
- to "in body" ("in body"! not "in head"!) and abort these steps.
- (innerHTML case) */
- } elseif ($node->nodeName === 'head') {
- $this->mode = self::IN_BODY;
- break;
-
- /* 12. If node is a body element, then switch the insertion mode to
- "in body" and abort these steps. */
- } elseif ($node->nodeName === 'body') {
- $this->mode = self::IN_BODY;
- break;
-
- /* 13. If node is a frameset element, then switch the insertion
- mode to "in frameset" and abort these steps. (innerHTML case) */
- } elseif ($node->nodeName === 'frameset') {
- $this->mode = self::IN_FRAME;
- break;
-
- /* 14. If node is an html element, then: if the head element
- pointer is null, switch the insertion mode to "before head",
- otherwise, switch the insertion mode to "after head". In either
- case, abort these steps. (innerHTML case) */
- } elseif ($node->nodeName === 'html') {
- $this->mode = ($this->head_pointer === null)
- ? self::BEFOR_HEAD
- : self::AFTER_HEAD;
-
- break;
-
- /* 15. If last is true, then set the insertion mode to "in body"
- and abort these steps. (innerHTML case) */
- } elseif ($last) {
- $this->mode = self::IN_BODY;
- break;
- }
- }
- }
-
- private function closeCell()
- {
- /* If the stack of open elements has a td or th element in table scope,
- then act as if an end tag token with that tag name had been seen. */
- foreach (array('td', 'th') as $cell) {
- if ($this->elementInScope($cell, true)) {
- $this->inCell(
- array(
- 'name' => $cell,
- 'type' => HTML5::ENDTAG
- )
- );
-
- break;
- }
- }
- }
-
- public function save()
- {
- return $this->dom;
- }
-}
diff --git a/library/HTMLPurifier/Printer/ConfigForm.php b/library/HTMLPurifier/Printer/ConfigForm.php
deleted file mode 100644
index 36100ce73..000000000
--- a/library/HTMLPurifier/Printer/ConfigForm.php
+++ /dev/null
@@ -1,447 +0,0 @@
-<?php
-
-/**
- * @todo Rewrite to use Interchange objects
- */
-class HTMLPurifier_Printer_ConfigForm extends HTMLPurifier_Printer
-{
-
- /**
- * Printers for specific fields.
- * @type HTMLPurifier_Printer[]
- */
- protected $fields = array();
-
- /**
- * Documentation URL, can have fragment tagged on end.
- * @type string
- */
- protected $docURL;
-
- /**
- * Name of form element to stuff config in.
- * @type string
- */
- protected $name;
-
- /**
- * Whether or not to compress directive names, clipping them off
- * after a certain amount of letters. False to disable or integer letters
- * before clipping.
- * @type bool
- */
- protected $compress = false;
-
- /**
- * @param string $name Form element name for directives to be stuffed into
- * @param string $doc_url String documentation URL, will have fragment tagged on
- * @param bool $compress Integer max length before compressing a directive name, set to false to turn off
- */
- public function __construct(
- $name,
- $doc_url = null,
- $compress = false
- ) {
- parent::__construct();
- $this->docURL = $doc_url;
- $this->name = $name;
- $this->compress = $compress;
- // initialize sub-printers
- $this->fields[0] = new HTMLPurifier_Printer_ConfigForm_default();
- $this->fields[HTMLPurifier_VarParser::BOOL] = new HTMLPurifier_Printer_ConfigForm_bool();
- }
-
- /**
- * Sets default column and row size for textareas in sub-printers
- * @param $cols Integer columns of textarea, null to use default
- * @param $rows Integer rows of textarea, null to use default
- */
- public function setTextareaDimensions($cols = null, $rows = null)
- {
- if ($cols) {
- $this->fields['default']->cols = $cols;
- }
- if ($rows) {
- $this->fields['default']->rows = $rows;
- }
- }
-
- /**
- * Retrieves styling, in case it is not accessible by webserver
- */
- public static function getCSS()
- {
- return file_get_contents(HTMLPURIFIER_PREFIX . '/HTMLPurifier/Printer/ConfigForm.css');
- }
-
- /**
- * Retrieves JavaScript, in case it is not accessible by webserver
- */
- public static function getJavaScript()
- {
- return file_get_contents(HTMLPURIFIER_PREFIX . '/HTMLPurifier/Printer/ConfigForm.js');
- }
-
- /**
- * Returns HTML output for a configuration form
- * @param HTMLPurifier_Config|array $config Configuration object of current form state, or an array
- * where [0] has an HTML namespace and [1] is being rendered.
- * @param array|bool $allowed Optional namespace(s) and directives to restrict form to.
- * @param bool $render_controls
- * @return string
- */
- public function render($config, $allowed = true, $render_controls = true)
- {
- if (is_array($config) && isset($config[0])) {
- $gen_config = $config[0];
- $config = $config[1];
- } else {
- $gen_config = $config;
- }
-
- $this->config = $config;
- $this->genConfig = $gen_config;
- $this->prepareGenerator($gen_config);
-
- $allowed = HTMLPurifier_Config::getAllowedDirectivesForForm($allowed, $config->def);
- $all = array();
- foreach ($allowed as $key) {
- list($ns, $directive) = $key;
- $all[$ns][$directive] = $config->get($ns . '.' . $directive);
- }
-
- $ret = '';
- $ret .= $this->start('table', array('class' => 'hp-config'));
- $ret .= $this->start('thead');
- $ret .= $this->start('tr');
- $ret .= $this->element('th', 'Directive', array('class' => 'hp-directive'));
- $ret .= $this->element('th', 'Value', array('class' => 'hp-value'));
- $ret .= $this->end('tr');
- $ret .= $this->end('thead');
- foreach ($all as $ns => $directives) {
- $ret .= $this->renderNamespace($ns, $directives);
- }
- if ($render_controls) {
- $ret .= $this->start('tbody');
- $ret .= $this->start('tr');
- $ret .= $this->start('td', array('colspan' => 2, 'class' => 'controls'));
- $ret .= $this->elementEmpty('input', array('type' => 'submit', 'value' => 'Submit'));
- $ret .= '[<a href="?">Reset</a>]';
- $ret .= $this->end('td');
- $ret .= $this->end('tr');
- $ret .= $this->end('tbody');
- }
- $ret .= $this->end('table');
- return $ret;
- }
-
- /**
- * Renders a single namespace
- * @param $ns String namespace name
- * @param array $directives array of directives to values
- * @return string
- */
- protected function renderNamespace($ns, $directives)
- {
- $ret = '';
- $ret .= $this->start('tbody', array('class' => 'namespace'));
- $ret .= $this->start('tr');
- $ret .= $this->element('th', $ns, array('colspan' => 2));
- $ret .= $this->end('tr');
- $ret .= $this->end('tbody');
- $ret .= $this->start('tbody');
- foreach ($directives as $directive => $value) {
- $ret .= $this->start('tr');
- $ret .= $this->start('th');
- if ($this->docURL) {
- $url = str_replace('%s', urlencode("$ns.$directive"), $this->docURL);
- $ret .= $this->start('a', array('href' => $url));
- }
- $attr = array('for' => "{$this->name}:$ns.$directive");
-
- // crop directive name if it's too long
- if (!$this->compress || (strlen($directive) < $this->compress)) {
- $directive_disp = $directive;
- } else {
- $directive_disp = substr($directive, 0, $this->compress - 2) . '...';
- $attr['title'] = $directive;
- }
-
- $ret .= $this->element(
- 'label',
- $directive_disp,
- // component printers must create an element with this id
- $attr
- );
- if ($this->docURL) {
- $ret .= $this->end('a');
- }
- $ret .= $this->end('th');
-
- $ret .= $this->start('td');
- $def = $this->config->def->info["$ns.$directive"];
- if (is_int($def)) {
- $allow_null = $def < 0;
- $type = abs($def);
- } else {
- $type = $def->type;
- $allow_null = isset($def->allow_null);
- }
- if (!isset($this->fields[$type])) {
- $type = 0;
- } // default
- $type_obj = $this->fields[$type];
- if ($allow_null) {
- $type_obj = new HTMLPurifier_Printer_ConfigForm_NullDecorator($type_obj);
- }
- $ret .= $type_obj->render($ns, $directive, $value, $this->name, array($this->genConfig, $this->config));
- $ret .= $this->end('td');
- $ret .= $this->end('tr');
- }
- $ret .= $this->end('tbody');
- return $ret;
- }
-
-}
-
-/**
- * Printer decorator for directives that accept null
- */
-class HTMLPurifier_Printer_ConfigForm_NullDecorator extends HTMLPurifier_Printer
-{
- /**
- * Printer being decorated
- * @type HTMLPurifier_Printer
- */
- protected $obj;
-
- /**
- * @param HTMLPurifier_Printer $obj Printer to decorate
- */
- public function __construct($obj)
- {
- parent::__construct();
- $this->obj = $obj;
- }
-
- /**
- * @param string $ns
- * @param string $directive
- * @param string $value
- * @param string $name
- * @param HTMLPurifier_Config|array $config
- * @return string
- */
- public function render($ns, $directive, $value, $name, $config)
- {
- if (is_array($config) && isset($config[0])) {
- $gen_config = $config[0];
- $config = $config[1];
- } else {
- $gen_config = $config;
- }
- $this->prepareGenerator($gen_config);
-
- $ret = '';
- $ret .= $this->start('label', array('for' => "$name:Null_$ns.$directive"));
- $ret .= $this->element('span', "$ns.$directive:", array('class' => 'verbose'));
- $ret .= $this->text(' Null/Disabled');
- $ret .= $this->end('label');
- $attr = array(
- 'type' => 'checkbox',
- 'value' => '1',
- 'class' => 'null-toggle',
- 'name' => "$name" . "[Null_$ns.$directive]",
- 'id' => "$name:Null_$ns.$directive",
- 'onclick' => "toggleWriteability('$name:$ns.$directive',checked)" // INLINE JAVASCRIPT!!!!
- );
- if ($this->obj instanceof HTMLPurifier_Printer_ConfigForm_bool) {
- // modify inline javascript slightly
- $attr['onclick'] =
- "toggleWriteability('$name:Yes_$ns.$directive',checked);" .
- "toggleWriteability('$name:No_$ns.$directive',checked)";
- }
- if ($value === null) {
- $attr['checked'] = 'checked';
- }
- $ret .= $this->elementEmpty('input', $attr);
- $ret .= $this->text(' or ');
- $ret .= $this->elementEmpty('br');
- $ret .= $this->obj->render($ns, $directive, $value, $name, array($gen_config, $config));
- return $ret;
- }
-}
-
-/**
- * Swiss-army knife configuration form field printer
- */
-class HTMLPurifier_Printer_ConfigForm_default extends HTMLPurifier_Printer
-{
- /**
- * @type int
- */
- public $cols = 18;
-
- /**
- * @type int
- */
- public $rows = 5;
-
- /**
- * @param string $ns
- * @param string $directive
- * @param string $value
- * @param string $name
- * @param HTMLPurifier_Config|array $config
- * @return string
- */
- public function render($ns, $directive, $value, $name, $config)
- {
- if (is_array($config) && isset($config[0])) {
- $gen_config = $config[0];
- $config = $config[1];
- } else {
- $gen_config = $config;
- }
- $this->prepareGenerator($gen_config);
- // this should probably be split up a little
- $ret = '';
- $def = $config->def->info["$ns.$directive"];
- if (is_int($def)) {
- $type = abs($def);
- } else {
- $type = $def->type;
- }
- if (is_array($value)) {
- switch ($type) {
- case HTMLPurifier_VarParser::LOOKUP:
- $array = $value;
- $value = array();
- foreach ($array as $val => $b) {
- $value[] = $val;
- }
- //TODO does this need a break?
- case HTMLPurifier_VarParser::ALIST:
- $value = implode(PHP_EOL, $value);
- break;
- case HTMLPurifier_VarParser::HASH:
- $nvalue = '';
- foreach ($value as $i => $v) {
- $nvalue .= "$i:$v" . PHP_EOL;
- }
- $value = $nvalue;
- break;
- default:
- $value = '';
- }
- }
- if ($type === HTMLPurifier_VarParser::MIXED) {
- return 'Not supported';
- $value = serialize($value);
- }
- $attr = array(
- 'name' => "$name" . "[$ns.$directive]",
- 'id' => "$name:$ns.$directive"
- );
- if ($value === null) {
- $attr['disabled'] = 'disabled';
- }
- if (isset($def->allowed)) {
- $ret .= $this->start('select', $attr);
- foreach ($def->allowed as $val => $b) {
- $attr = array();
- if ($value == $val) {
- $attr['selected'] = 'selected';
- }
- $ret .= $this->element('option', $val, $attr);
- }
- $ret .= $this->end('select');
- } elseif ($type === HTMLPurifier_VarParser::TEXT ||
- $type === HTMLPurifier_VarParser::ITEXT ||
- $type === HTMLPurifier_VarParser::ALIST ||
- $type === HTMLPurifier_VarParser::HASH ||
- $type === HTMLPurifier_VarParser::LOOKUP) {
- $attr['cols'] = $this->cols;
- $attr['rows'] = $this->rows;
- $ret .= $this->start('textarea', $attr);
- $ret .= $this->text($value);
- $ret .= $this->end('textarea');
- } else {
- $attr['value'] = $value;
- $attr['type'] = 'text';
- $ret .= $this->elementEmpty('input', $attr);
- }
- return $ret;
- }
-}
-
-/**
- * Bool form field printer
- */
-class HTMLPurifier_Printer_ConfigForm_bool extends HTMLPurifier_Printer
-{
- /**
- * @param string $ns
- * @param string $directive
- * @param string $value
- * @param string $name
- * @param HTMLPurifier_Config|array $config
- * @return string
- */
- public function render($ns, $directive, $value, $name, $config)
- {
- if (is_array($config) && isset($config[0])) {
- $gen_config = $config[0];
- $config = $config[1];
- } else {
- $gen_config = $config;
- }
- $this->prepareGenerator($gen_config);
- $ret = '';
- $ret .= $this->start('div', array('id' => "$name:$ns.$directive"));
-
- $ret .= $this->start('label', array('for' => "$name:Yes_$ns.$directive"));
- $ret .= $this->element('span', "$ns.$directive:", array('class' => 'verbose'));
- $ret .= $this->text(' Yes');
- $ret .= $this->end('label');
-
- $attr = array(
- 'type' => 'radio',
- 'name' => "$name" . "[$ns.$directive]",
- 'id' => "$name:Yes_$ns.$directive",
- 'value' => '1'
- );
- if ($value === true) {
- $attr['checked'] = 'checked';
- }
- if ($value === null) {
- $attr['disabled'] = 'disabled';
- }
- $ret .= $this->elementEmpty('input', $attr);
-
- $ret .= $this->start('label', array('for' => "$name:No_$ns.$directive"));
- $ret .= $this->element('span', "$ns.$directive:", array('class' => 'verbose'));
- $ret .= $this->text(' No');
- $ret .= $this->end('label');
-
- $attr = array(
- 'type' => 'radio',
- 'name' => "$name" . "[$ns.$directive]",
- 'id' => "$name:No_$ns.$directive",
- 'value' => '0'
- );
- if ($value === false) {
- $attr['checked'] = 'checked';
- }
- if ($value === null) {
- $attr['disabled'] = 'disabled';
- }
- $ret .= $this->elementEmpty('input', $attr);
-
- $ret .= $this->end('div');
-
- return $ret;
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/Strategy/MakeWellFormed.php b/library/HTMLPurifier/Strategy/MakeWellFormed.php
deleted file mode 100644
index e389e0011..000000000
--- a/library/HTMLPurifier/Strategy/MakeWellFormed.php
+++ /dev/null
@@ -1,600 +0,0 @@
-<?php
-
-/**
- * Takes tokens makes them well-formed (balance end tags, etc.)
- *
- * Specification of the armor attributes this strategy uses:
- *
- * - MakeWellFormed_TagClosedError: This armor field is used to
- * suppress tag closed errors for certain tokens [TagClosedSuppress],
- * in particular, if a tag was generated automatically by HTML
- * Purifier, we may rely on our infrastructure to close it for us
- * and shouldn't report an error to the user [TagClosedAuto].
- */
-class HTMLPurifier_Strategy_MakeWellFormed extends HTMLPurifier_Strategy
-{
-
- /**
- * Array stream of tokens being processed.
- * @type HTMLPurifier_Token[]
- */
- protected $tokens;
-
- /**
- * Current token.
- * @type HTMLPurifier_Token
- */
- protected $token;
-
- /**
- * Zipper managing the true state.
- * @type HTMLPurifier_Zipper
- */
- protected $zipper;
-
- /**
- * Current nesting of elements.
- * @type array
- */
- protected $stack;
-
- /**
- * Injectors active in this stream processing.
- * @type HTMLPurifier_Injector[]
- */
- protected $injectors;
-
- /**
- * Current instance of HTMLPurifier_Config.
- * @type HTMLPurifier_Config
- */
- protected $config;
-
- /**
- * Current instance of HTMLPurifier_Context.
- * @type HTMLPurifier_Context
- */
- protected $context;
-
- /**
- * @param HTMLPurifier_Token[] $tokens
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return HTMLPurifier_Token[]
- * @throws HTMLPurifier_Exception
- */
- public function execute($tokens, $config, $context)
- {
- $definition = $config->getHTMLDefinition();
-
- // local variables
- $generator = new HTMLPurifier_Generator($config, $context);
- $escape_invalid_tags = $config->get('Core.EscapeInvalidTags');
- // used for autoclose early abortion
- $global_parent_allowed_elements = $definition->info_parent_def->child->getAllowedElements($config);
- $e = $context->get('ErrorCollector', true);
- $i = false; // injector index
- list($zipper, $token) = HTMLPurifier_Zipper::fromArray($tokens);
- if ($token === NULL) {
- return array();
- }
- $reprocess = false; // whether or not to reprocess the same token
- $stack = array();
-
- // member variables
- $this->stack =& $stack;
- $this->tokens =& $tokens;
- $this->token =& $token;
- $this->zipper =& $zipper;
- $this->config = $config;
- $this->context = $context;
-
- // context variables
- $context->register('CurrentNesting', $stack);
- $context->register('InputZipper', $zipper);
- $context->register('CurrentToken', $token);
-
- // -- begin INJECTOR --
-
- $this->injectors = array();
-
- $injectors = $config->getBatch('AutoFormat');
- $def_injectors = $definition->info_injector;
- $custom_injectors = $injectors['Custom'];
- unset($injectors['Custom']); // special case
- foreach ($injectors as $injector => $b) {
- // XXX: Fix with a legitimate lookup table of enabled filters
- if (strpos($injector, '.') !== false) {
- continue;
- }
- $injector = "HTMLPurifier_Injector_$injector";
- if (!$b) {
- continue;
- }
- $this->injectors[] = new $injector;
- }
- foreach ($def_injectors as $injector) {
- // assumed to be objects
- $this->injectors[] = $injector;
- }
- foreach ($custom_injectors as $injector) {
- if (!$injector) {
- continue;
- }
- if (is_string($injector)) {
- $injector = "HTMLPurifier_Injector_$injector";
- $injector = new $injector;
- }
- $this->injectors[] = $injector;
- }
-
- // give the injectors references to the definition and context
- // variables for performance reasons
- foreach ($this->injectors as $ix => $injector) {
- $error = $injector->prepare($config, $context);
- if (!$error) {
- continue;
- }
- array_splice($this->injectors, $ix, 1); // rm the injector
- trigger_error("Cannot enable {$injector->name} injector because $error is not allowed", E_USER_WARNING);
- }
-
- // -- end INJECTOR --
-
- // a note on reprocessing:
- // In order to reduce code duplication, whenever some code needs
- // to make HTML changes in order to make things "correct", the
- // new HTML gets sent through the purifier, regardless of its
- // status. This means that if we add a start token, because it
- // was totally necessary, we don't have to update nesting; we just
- // punt ($reprocess = true; continue;) and it does that for us.
-
- // isset is in loop because $tokens size changes during loop exec
- for (;;
- // only increment if we don't need to reprocess
- $reprocess ? $reprocess = false : $token = $zipper->next($token)) {
-
- // check for a rewind
- if (is_int($i)) {
- // possibility: disable rewinding if the current token has a
- // rewind set on it already. This would offer protection from
- // infinite loop, but might hinder some advanced rewinding.
- $rewind_offset = $this->injectors[$i]->getRewindOffset();
- if (is_int($rewind_offset)) {
- for ($j = 0; $j < $rewind_offset; $j++) {
- if (empty($zipper->front)) break;
- $token = $zipper->prev($token);
- // indicate that other injectors should not process this token,
- // but we need to reprocess it
- unset($token->skip[$i]);
- $token->rewind = $i;
- if ($token instanceof HTMLPurifier_Token_Start) {
- array_pop($this->stack);
- } elseif ($token instanceof HTMLPurifier_Token_End) {
- $this->stack[] = $token->start;
- }
- }
- }
- $i = false;
- }
-
- // handle case of document end
- if ($token === NULL) {
- // kill processing if stack is empty
- if (empty($this->stack)) {
- break;
- }
-
- // peek
- $top_nesting = array_pop($this->stack);
- $this->stack[] = $top_nesting;
-
- // send error [TagClosedSuppress]
- if ($e && !isset($top_nesting->armor['MakeWellFormed_TagClosedError'])) {
- $e->send(E_NOTICE, 'Strategy_MakeWellFormed: Tag closed by document end', $top_nesting);
- }
-
- // append, don't splice, since this is the end
- $token = new HTMLPurifier_Token_End($top_nesting->name);
-
- // punt!
- $reprocess = true;
- continue;
- }
-
- //echo '<br>'; printZipper($zipper, $token);//printTokens($this->stack);
- //flush();
-
- // quick-check: if it's not a tag, no need to process
- if (empty($token->is_tag)) {
- if ($token instanceof HTMLPurifier_Token_Text) {
- foreach ($this->injectors as $i => $injector) {
- if (isset($token->skip[$i])) {
- continue;
- }
- if ($token->rewind !== null && $token->rewind !== $i) {
- continue;
- }
- // XXX fuckup
- $r = $token;
- $injector->handleText($r);
- $token = $this->processToken($r, $i);
- $reprocess = true;
- break;
- }
- }
- // another possibility is a comment
- continue;
- }
-
- if (isset($definition->info[$token->name])) {
- $type = $definition->info[$token->name]->child->type;
- } else {
- $type = false; // Type is unknown, treat accordingly
- }
-
- // quick tag checks: anything that's *not* an end tag
- $ok = false;
- if ($type === 'empty' && $token instanceof HTMLPurifier_Token_Start) {
- // claims to be a start tag but is empty
- $token = new HTMLPurifier_Token_Empty(
- $token->name,
- $token->attr,
- $token->line,
- $token->col,
- $token->armor
- );
- $ok = true;
- } elseif ($type && $type !== 'empty' && $token instanceof HTMLPurifier_Token_Empty) {
- // claims to be empty but really is a start tag
- // NB: this assignment is required
- $old_token = $token;
- $token = new HTMLPurifier_Token_End($token->name);
- $token = $this->insertBefore(
- new HTMLPurifier_Token_Start($old_token->name, $old_token->attr, $old_token->line, $old_token->col, $old_token->armor)
- );
- // punt (since we had to modify the input stream in a non-trivial way)
- $reprocess = true;
- continue;
- } elseif ($token instanceof HTMLPurifier_Token_Empty) {
- // real empty token
- $ok = true;
- } elseif ($token instanceof HTMLPurifier_Token_Start) {
- // start tag
-
- // ...unless they also have to close their parent
- if (!empty($this->stack)) {
-
- // Performance note: you might think that it's rather
- // inefficient, recalculating the autoclose information
- // for every tag that a token closes (since when we
- // do an autoclose, we push a new token into the
- // stream and then /process/ that, before
- // re-processing this token.) But this is
- // necessary, because an injector can make an
- // arbitrary transformations to the autoclosing
- // tokens we introduce, so things may have changed
- // in the meantime. Also, doing the inefficient thing is
- // "easy" to reason about (for certain perverse definitions
- // of "easy")
-
- $parent = array_pop($this->stack);
- $this->stack[] = $parent;
-
- $parent_def = null;
- $parent_elements = null;
- $autoclose = false;
- if (isset($definition->info[$parent->name])) {
- $parent_def = $definition->info[$parent->name];
- $parent_elements = $parent_def->child->getAllowedElements($config);
- $autoclose = !isset($parent_elements[$token->name]);
- }
-
- if ($autoclose && $definition->info[$token->name]->wrap) {
- // Check if an element can be wrapped by another
- // element to make it valid in a context (for
- // example, <ul><ul> needs a <li> in between)
- $wrapname = $definition->info[$token->name]->wrap;
- $wrapdef = $definition->info[$wrapname];
- $elements = $wrapdef->child->getAllowedElements($config);
- if (isset($elements[$token->name]) && isset($parent_elements[$wrapname])) {
- $newtoken = new HTMLPurifier_Token_Start($wrapname);
- $token = $this->insertBefore($newtoken);
- $reprocess = true;
- continue;
- }
- }
-
- $carryover = false;
- if ($autoclose && $parent_def->formatting) {
- $carryover = true;
- }
-
- if ($autoclose) {
- // check if this autoclose is doomed to fail
- // (this rechecks $parent, which his harmless)
- $autoclose_ok = isset($global_parent_allowed_elements[$token->name]);
- if (!$autoclose_ok) {
- foreach ($this->stack as $ancestor) {
- $elements = $definition->info[$ancestor->name]->child->getAllowedElements($config);
- if (isset($elements[$token->name])) {
- $autoclose_ok = true;
- break;
- }
- if ($definition->info[$token->name]->wrap) {
- $wrapname = $definition->info[$token->name]->wrap;
- $wrapdef = $definition->info[$wrapname];
- $wrap_elements = $wrapdef->child->getAllowedElements($config);
- if (isset($wrap_elements[$token->name]) && isset($elements[$wrapname])) {
- $autoclose_ok = true;
- break;
- }
- }
- }
- }
- if ($autoclose_ok) {
- // errors need to be updated
- $new_token = new HTMLPurifier_Token_End($parent->name);
- $new_token->start = $parent;
- // [TagClosedSuppress]
- if ($e && !isset($parent->armor['MakeWellFormed_TagClosedError'])) {
- if (!$carryover) {
- $e->send(E_NOTICE, 'Strategy_MakeWellFormed: Tag auto closed', $parent);
- } else {
- $e->send(E_NOTICE, 'Strategy_MakeWellFormed: Tag carryover', $parent);
- }
- }
- if ($carryover) {
- $element = clone $parent;
- // [TagClosedAuto]
- $element->armor['MakeWellFormed_TagClosedError'] = true;
- $element->carryover = true;
- $token = $this->processToken(array($new_token, $token, $element));
- } else {
- $token = $this->insertBefore($new_token);
- }
- } else {
- $token = $this->remove();
- }
- $reprocess = true;
- continue;
- }
-
- }
- $ok = true;
- }
-
- if ($ok) {
- foreach ($this->injectors as $i => $injector) {
- if (isset($token->skip[$i])) {
- continue;
- }
- if ($token->rewind !== null && $token->rewind !== $i) {
- continue;
- }
- $r = $token;
- $injector->handleElement($r);
- $token = $this->processToken($r, $i);
- $reprocess = true;
- break;
- }
- if (!$reprocess) {
- // ah, nothing interesting happened; do normal processing
- if ($token instanceof HTMLPurifier_Token_Start) {
- $this->stack[] = $token;
- } elseif ($token instanceof HTMLPurifier_Token_End) {
- throw new HTMLPurifier_Exception(
- 'Improper handling of end tag in start code; possible error in MakeWellFormed'
- );
- }
- }
- continue;
- }
-
- // sanity check: we should be dealing with a closing tag
- if (!$token instanceof HTMLPurifier_Token_End) {
- throw new HTMLPurifier_Exception('Unaccounted for tag token in input stream, bug in HTML Purifier');
- }
-
- // make sure that we have something open
- if (empty($this->stack)) {
- if ($escape_invalid_tags) {
- if ($e) {
- $e->send(E_WARNING, 'Strategy_MakeWellFormed: Unnecessary end tag to text');
- }
- $token = new HTMLPurifier_Token_Text($generator->generateFromToken($token));
- } else {
- if ($e) {
- $e->send(E_WARNING, 'Strategy_MakeWellFormed: Unnecessary end tag removed');
- }
- $token = $this->remove();
- }
- $reprocess = true;
- continue;
- }
-
- // first, check for the simplest case: everything closes neatly.
- // Eventually, everything passes through here; if there are problems
- // we modify the input stream accordingly and then punt, so that
- // the tokens get processed again.
- $current_parent = array_pop($this->stack);
- if ($current_parent->name == $token->name) {
- $token->start = $current_parent;
- foreach ($this->injectors as $i => $injector) {
- if (isset($token->skip[$i])) {
- continue;
- }
- if ($token->rewind !== null && $token->rewind !== $i) {
- continue;
- }
- $r = $token;
- $injector->handleEnd($r);
- $token = $this->processToken($r, $i);
- $this->stack[] = $current_parent;
- $reprocess = true;
- break;
- }
- continue;
- }
-
- // okay, so we're trying to close the wrong tag
-
- // undo the pop previous pop
- $this->stack[] = $current_parent;
-
- // scroll back the entire nest, trying to find our tag.
- // (feature could be to specify how far you'd like to go)
- $size = count($this->stack);
- // -2 because -1 is the last element, but we already checked that
- $skipped_tags = false;
- for ($j = $size - 2; $j >= 0; $j--) {
- if ($this->stack[$j]->name == $token->name) {
- $skipped_tags = array_slice($this->stack, $j);
- break;
- }
- }
-
- // we didn't find the tag, so remove
- if ($skipped_tags === false) {
- if ($escape_invalid_tags) {
- if ($e) {
- $e->send(E_WARNING, 'Strategy_MakeWellFormed: Stray end tag to text');
- }
- $token = new HTMLPurifier_Token_Text($generator->generateFromToken($token));
- } else {
- if ($e) {
- $e->send(E_WARNING, 'Strategy_MakeWellFormed: Stray end tag removed');
- }
- $token = $this->remove();
- }
- $reprocess = true;
- continue;
- }
-
- // do errors, in REVERSE $j order: a,b,c with </a></b></c>
- $c = count($skipped_tags);
- if ($e) {
- for ($j = $c - 1; $j > 0; $j--) {
- // notice we exclude $j == 0, i.e. the current ending tag, from
- // the errors... [TagClosedSuppress]
- if (!isset($skipped_tags[$j]->armor['MakeWellFormed_TagClosedError'])) {
- $e->send(E_NOTICE, 'Strategy_MakeWellFormed: Tag closed by element end', $skipped_tags[$j]);
- }
- }
- }
-
- // insert tags, in FORWARD $j order: c,b,a with </a></b></c>
- $replace = array($token);
- for ($j = 1; $j < $c; $j++) {
- // ...as well as from the insertions
- $new_token = new HTMLPurifier_Token_End($skipped_tags[$j]->name);
- $new_token->start = $skipped_tags[$j];
- array_unshift($replace, $new_token);
- if (isset($definition->info[$new_token->name]) && $definition->info[$new_token->name]->formatting) {
- // [TagClosedAuto]
- $element = clone $skipped_tags[$j];
- $element->carryover = true;
- $element->armor['MakeWellFormed_TagClosedError'] = true;
- $replace[] = $element;
- }
- }
- $token = $this->processToken($replace);
- $reprocess = true;
- continue;
- }
-
- $context->destroy('CurrentToken');
- $context->destroy('CurrentNesting');
- $context->destroy('InputZipper');
-
- unset($this->injectors, $this->stack, $this->tokens);
- return $zipper->toArray($token);
- }
-
- /**
- * Processes arbitrary token values for complicated substitution patterns.
- * In general:
- *
- * If $token is an array, it is a list of tokens to substitute for the
- * current token. These tokens then get individually processed. If there
- * is a leading integer in the list, that integer determines how many
- * tokens from the stream should be removed.
- *
- * If $token is a regular token, it is swapped with the current token.
- *
- * If $token is false, the current token is deleted.
- *
- * If $token is an integer, that number of tokens (with the first token
- * being the current one) will be deleted.
- *
- * @param HTMLPurifier_Token|array|int|bool $token Token substitution value
- * @param HTMLPurifier_Injector|int $injector Injector that performed the substitution; default is if
- * this is not an injector related operation.
- * @throws HTMLPurifier_Exception
- */
- protected function processToken($token, $injector = -1)
- {
- // normalize forms of token
- if (is_object($token)) {
- $token = array(1, $token);
- }
- if (is_int($token)) {
- $token = array($token);
- }
- if ($token === false) {
- $token = array(1);
- }
- if (!is_array($token)) {
- throw new HTMLPurifier_Exception('Invalid token type from injector');
- }
- if (!is_int($token[0])) {
- array_unshift($token, 1);
- }
- if ($token[0] === 0) {
- throw new HTMLPurifier_Exception('Deleting zero tokens is not valid');
- }
-
- // $token is now an array with the following form:
- // array(number nodes to delete, new node 1, new node 2, ...)
-
- $delete = array_shift($token);
- list($old, $r) = $this->zipper->splice($this->token, $delete, $token);
-
- if ($injector > -1) {
- // determine appropriate skips
- $oldskip = isset($old[0]) ? $old[0]->skip : array();
- foreach ($token as $object) {
- $object->skip = $oldskip;
- $object->skip[$injector] = true;
- }
- }
-
- return $r;
-
- }
-
- /**
- * Inserts a token before the current token. Cursor now points to
- * this token. You must reprocess after this.
- * @param HTMLPurifier_Token $token
- */
- private function insertBefore($token)
- {
- // NB not $this->zipper->insertBefore(), due to positioning
- // differences
- $splice = $this->zipper->splice($this->token, 0, array($token));
-
- return $splice[1];
- }
-
- /**
- * Removes current token. Cursor now points to new token occupying previously
- * occupied space. You must reprocess after this.
- */
- private function remove()
- {
- return $this->zipper->delete();
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/Token.php b/library/HTMLPurifier/Token.php
deleted file mode 100644
index 85b85e072..000000000
--- a/library/HTMLPurifier/Token.php
+++ /dev/null
@@ -1,100 +0,0 @@
-<?php
-
-/**
- * Abstract base token class that all others inherit from.
- */
-abstract class HTMLPurifier_Token
-{
- /**
- * Line number node was on in source document. Null if unknown.
- * @type int
- */
- public $line;
-
- /**
- * Column of line node was on in source document. Null if unknown.
- * @type int
- */
- public $col;
-
- /**
- * Lookup array of processing that this token is exempt from.
- * Currently, valid values are "ValidateAttributes" and
- * "MakeWellFormed_TagClosedError"
- * @type array
- */
- public $armor = array();
-
- /**
- * Used during MakeWellFormed.
- * @type
- */
- public $skip;
-
- /**
- * @type
- */
- public $rewind;
-
- /**
- * @type
- */
- public $carryover;
-
- /**
- * @param string $n
- * @return null|string
- */
- public function __get($n)
- {
- if ($n === 'type') {
- trigger_error('Deprecated type property called; use instanceof', E_USER_NOTICE);
- switch (get_class($this)) {
- case 'HTMLPurifier_Token_Start':
- return 'start';
- case 'HTMLPurifier_Token_Empty':
- return 'empty';
- case 'HTMLPurifier_Token_End':
- return 'end';
- case 'HTMLPurifier_Token_Text':
- return 'text';
- case 'HTMLPurifier_Token_Comment':
- return 'comment';
- default:
- return null;
- }
- }
- }
-
- /**
- * Sets the position of the token in the source document.
- * @param int $l
- * @param int $c
- */
- public function position($l = null, $c = null)
- {
- $this->line = $l;
- $this->col = $c;
- }
-
- /**
- * Convenience function for DirectLex settings line/col position.
- * @param int $l
- * @param int $c
- */
- public function rawPosition($l, $c)
- {
- if ($c === -1) {
- $l++;
- }
- $this->line = $l;
- $this->col = $c;
- }
-
- /**
- * Converts a token into its corresponding node.
- */
- abstract public function toNode();
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/URI.php b/library/HTMLPurifier/URI.php
deleted file mode 100644
index a5e7ae298..000000000
--- a/library/HTMLPurifier/URI.php
+++ /dev/null
@@ -1,314 +0,0 @@
-<?php
-
-/**
- * HTML Purifier's internal representation of a URI.
- * @note
- * Internal data-structures are completely escaped. If the data needs
- * to be used in a non-URI context (which is very unlikely), be sure
- * to decode it first. The URI may not necessarily be well-formed until
- * validate() is called.
- */
-class HTMLPurifier_URI
-{
- /**
- * @type string
- */
- public $scheme;
-
- /**
- * @type string
- */
- public $userinfo;
-
- /**
- * @type string
- */
- public $host;
-
- /**
- * @type int
- */
- public $port;
-
- /**
- * @type string
- */
- public $path;
-
- /**
- * @type string
- */
- public $query;
-
- /**
- * @type string
- */
- public $fragment;
-
- /**
- * @param string $scheme
- * @param string $userinfo
- * @param string $host
- * @param int $port
- * @param string $path
- * @param string $query
- * @param string $fragment
- * @note Automatically normalizes scheme and port
- */
- public function __construct($scheme, $userinfo, $host, $port, $path, $query, $fragment)
- {
- $this->scheme = is_null($scheme) || ctype_lower($scheme) ? $scheme : strtolower($scheme);
- $this->userinfo = $userinfo;
- $this->host = $host;
- $this->port = is_null($port) ? $port : (int)$port;
- $this->path = $path;
- $this->query = $query;
- $this->fragment = $fragment;
- }
-
- /**
- * Retrieves a scheme object corresponding to the URI's scheme/default
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return HTMLPurifier_URIScheme Scheme object appropriate for validating this URI
- */
- public function getSchemeObj($config, $context)
- {
- $registry = HTMLPurifier_URISchemeRegistry::instance();
- if ($this->scheme !== null) {
- $scheme_obj = $registry->getScheme($this->scheme, $config, $context);
- if (!$scheme_obj) {
- return false;
- } // invalid scheme, clean it out
- } else {
- // no scheme: retrieve the default one
- $def = $config->getDefinition('URI');
- $scheme_obj = $def->getDefaultScheme($config, $context);
- if (!$scheme_obj) {
- // something funky happened to the default scheme object
- trigger_error(
- 'Default scheme object "' . $def->defaultScheme . '" was not readable',
- E_USER_WARNING
- );
- return false;
- }
- }
- return $scheme_obj;
- }
-
- /**
- * Generic validation method applicable for all schemes. May modify
- * this URI in order to get it into a compliant form.
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return bool True if validation/filtering succeeds, false if failure
- */
- public function validate($config, $context)
- {
- // ABNF definitions from RFC 3986
- $chars_sub_delims = '!$&\'()*+,;=';
- $chars_gen_delims = ':/?#[]@';
- $chars_pchar = $chars_sub_delims . ':@';
-
- // validate host
- if (!is_null($this->host)) {
- $host_def = new HTMLPurifier_AttrDef_URI_Host();
- $this->host = $host_def->validate($this->host, $config, $context);
- if ($this->host === false) {
- $this->host = null;
- }
- }
-
- // validate scheme
- // NOTE: It's not appropriate to check whether or not this
- // scheme is in our registry, since a URIFilter may convert a
- // URI that we don't allow into one we do. So instead, we just
- // check if the scheme can be dropped because there is no host
- // and it is our default scheme.
- if (!is_null($this->scheme) && is_null($this->host) || $this->host === '') {
- // support for relative paths is pretty abysmal when the
- // scheme is present, so axe it when possible
- $def = $config->getDefinition('URI');
- if ($def->defaultScheme === $this->scheme) {
- $this->scheme = null;
- }
- }
-
- // validate username
- if (!is_null($this->userinfo)) {
- $encoder = new HTMLPurifier_PercentEncoder($chars_sub_delims . ':');
- $this->userinfo = $encoder->encode($this->userinfo);
- }
-
- // validate port
- if (!is_null($this->port)) {
- if ($this->port < 1 || $this->port > 65535) {
- $this->port = null;
- }
- }
-
- // validate path
- $segments_encoder = new HTMLPurifier_PercentEncoder($chars_pchar . '/');
- if (!is_null($this->host)) { // this catches $this->host === ''
- // path-abempty (hier and relative)
- // http://www.example.com/my/path
- // //www.example.com/my/path (looks odd, but works, and
- // recognized by most browsers)
- // (this set is valid or invalid on a scheme by scheme
- // basis, so we'll deal with it later)
- // file:///my/path
- // ///my/path
- $this->path = $segments_encoder->encode($this->path);
- } elseif ($this->path !== '') {
- if ($this->path[0] === '/') {
- // path-absolute (hier and relative)
- // http:/my/path
- // /my/path
- if (strlen($this->path) >= 2 && $this->path[1] === '/') {
- // This could happen if both the host gets stripped
- // out
- // http://my/path
- // //my/path
- $this->path = '';
- } else {
- $this->path = $segments_encoder->encode($this->path);
- }
- } elseif (!is_null($this->scheme)) {
- // path-rootless (hier)
- // http:my/path
- // Short circuit evaluation means we don't need to check nz
- $this->path = $segments_encoder->encode($this->path);
- } else {
- // path-noscheme (relative)
- // my/path
- // (once again, not checking nz)
- $segment_nc_encoder = new HTMLPurifier_PercentEncoder($chars_sub_delims . '@');
- $c = strpos($this->path, '/');
- if ($c !== false) {
- $this->path =
- $segment_nc_encoder->encode(substr($this->path, 0, $c)) .
- $segments_encoder->encode(substr($this->path, $c));
- } else {
- $this->path = $segment_nc_encoder->encode($this->path);
- }
- }
- } else {
- // path-empty (hier and relative)
- $this->path = ''; // just to be safe
- }
-
- // qf = query and fragment
- $qf_encoder = new HTMLPurifier_PercentEncoder($chars_pchar . '/?');
-
- if (!is_null($this->query)) {
- $this->query = $qf_encoder->encode($this->query);
- }
-
- if (!is_null($this->fragment)) {
- $this->fragment = $qf_encoder->encode($this->fragment);
- }
- return true;
- }
-
- /**
- * Convert URI back to string
- * @return string URI appropriate for output
- */
- public function toString()
- {
- // reconstruct authority
- $authority = null;
- // there is a rendering difference between a null authority
- // (http:foo-bar) and an empty string authority
- // (http:///foo-bar).
- if (!is_null($this->host)) {
- $authority = '';
- if (!is_null($this->userinfo)) {
- $authority .= $this->userinfo . '@';
- }
- $authority .= $this->host;
- if (!is_null($this->port)) {
- $authority .= ':' . $this->port;
- }
- }
-
- // Reconstruct the result
- // One might wonder about parsing quirks from browsers after
- // this reconstruction. Unfortunately, parsing behavior depends
- // on what *scheme* was employed (file:///foo is handled *very*
- // differently than http:///foo), so unfortunately we have to
- // defer to the schemes to do the right thing.
- $result = '';
- if (!is_null($this->scheme)) {
- $result .= $this->scheme . ':';
- }
- if (!is_null($authority)) {
- $result .= '//' . $authority;
- }
- $result .= $this->path;
- if (!is_null($this->query)) {
- $result .= '?' . $this->query;
- }
- if (!is_null($this->fragment)) {
- $result .= '#' . $this->fragment;
- }
-
- return $result;
- }
-
- /**
- * Returns true if this URL might be considered a 'local' URL given
- * the current context. This is true when the host is null, or
- * when it matches the host supplied to the configuration.
- *
- * Note that this does not do any scheme checking, so it is mostly
- * only appropriate for metadata that doesn't care about protocol
- * security. isBenign is probably what you actually want.
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return bool
- */
- public function isLocal($config, $context)
- {
- if ($this->host === null) {
- return true;
- }
- $uri_def = $config->getDefinition('URI');
- if ($uri_def->host === $this->host) {
- return true;
- }
- return false;
- }
-
- /**
- * Returns true if this URL should be considered a 'benign' URL,
- * that is:
- *
- * - It is a local URL (isLocal), and
- * - It has a equal or better level of security
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return bool
- */
- public function isBenign($config, $context)
- {
- if (!$this->isLocal($config, $context)) {
- return false;
- }
-
- $scheme_obj = $this->getSchemeObj($config, $context);
- if (!$scheme_obj) {
- return false;
- } // conservative approach
-
- $current_scheme_obj = $config->getDefinition('URI')->getDefaultScheme($config, $context);
- if ($current_scheme_obj->secure) {
- if (!$scheme_obj->secure) {
- return false;
- }
- }
- return true;
- }
-}
-
-// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/URIScheme/data.php b/library/HTMLPurifier/URIScheme/data.php
deleted file mode 100644
index 6ebca4984..000000000
--- a/library/HTMLPurifier/URIScheme/data.php
+++ /dev/null
@@ -1,127 +0,0 @@
-<?php
-
-/**
- * Implements data: URI for base64 encoded images supported by GD.
- */
-class HTMLPurifier_URIScheme_data extends HTMLPurifier_URIScheme
-{
- /**
- * @type bool
- */
- public $browsable = true;
-
- /**
- * @type array
- */
- public $allowed_types = array(
- // you better write validation code for other types if you
- // decide to allow them
- 'image/jpeg' => true,
- 'image/gif' => true,
- 'image/png' => true,
- );
- // this is actually irrelevant since we only write out the path
- // component
- /**
- * @type bool
- */
- public $may_omit_host = true;
-
- /**
- * @param HTMLPurifier_URI $uri
- * @param HTMLPurifier_Config $config
- * @param HTMLPurifier_Context $context
- * @return bool
- */
- public function doValidate(&$uri, $config, $context)
- {
- $result = explode(',', $uri->path, 2);
- $is_base64 = false;
- $charset = null;
- $content_type = null;
- if (count($result) == 2) {
- list($metadata, $data) = $result;
- // do some legwork on the metadata
- $metas = explode(';', $metadata);
- while (!empty($metas)) {
- $cur = array_shift($metas);
- if ($cur == 'base64') {
- $is_base64 = true;
- break;
- }
- if (substr($cur, 0, 8) == 'charset=') {
- // doesn't match if there are arbitrary spaces, but
- // whatever dude
- if ($charset !== null) {
- continue;
- } // garbage
- $charset = substr($cur, 8); // not used
- } else {
- if ($content_type !== null) {
- continue;
- } // garbage
- $content_type = $cur;
- }
- }
- } else {
- $data = $result[0];
- }
- if ($content_type !== null && empty($this->allowed_types[$content_type])) {
- return false;
- }
- if ($charset !== null) {
- // error; we don't allow plaintext stuff
- $charset = null;
- }
- $data = rawurldecode($data);
- if ($is_base64) {
- $raw_data = base64_decode($data);
- } else {
- $raw_data = $data;
- }
- // XXX probably want to refactor this into a general mechanism
- // for filtering arbitrary content types
- $file = tempnam("/tmp", "");
- file_put_contents($file, $raw_data);
- if (function_exists('exif_imagetype')) {
- $image_code = exif_imagetype($file);
- unlink($file);
- } elseif (function_exists('getimagesize')) {
- set_error_handler(array($this, 'muteErrorHandler'));
- $info = getimagesize($file);
- restore_error_handler();
- unlink($file);
- if ($info == false) {
- return false;
- }
- $image_code = $info[2];
- } else {
- trigger_error("could not find exif_imagetype or getimagesize functions", E_USER_ERROR);
- }
- $real_content_type = image_type_to_mime_type($image_code);
- if ($real_content_type != $content_type) {
- // we're nice guys; if the content type is something else we
- // support, change it over
- if (empty($this->allowed_types[$real_content_type])) {
- return false;
- }
- $content_type = $real_content_type;
- }
- // ok, it's kosher, rewrite what we need
- $uri->userinfo = null;
- $uri->host = null;
- $uri->port = null;
- $uri->fragment = null;
- $uri->query = null;
- $uri->path = "$content_type;base64," . base64_encode($raw_data);
- return true;
- }
-
- /**
- * @param int $errno
- * @param string $errstr
- */
- public function muteErrorHandler($errno, $errstr)
- {
- }
-}
diff --git a/library/Text_Highlighter/README b/library/Text_Highlighter/README
deleted file mode 100644
index 88f71aed2..000000000
--- a/library/Text_Highlighter/README
+++ /dev/null
@@ -1,455 +0,0 @@
-# $Id$
-
-Introduction
-============
-
-Text_Highlighter is a class for syntax highlighting. The main idea is to
-simplify creation of subclasses implementing syntax highlighting for
-particular language. Subclasses do not implement any new functioanality, they
-just provide syntax highlighting rules. The rules sources are in XML format.
-To create a highlighter for a language, there is no need to code a new class
-manually. Simply describe the rules in XML file and use Text_Highlighter_Generator
-to create a new class.
-
-
-This document does not contain a formal description of API - it is very
-simple, and I believe providing some examples of code is sufficient.
-
-
-Highlighter XML source
-======================
-
-Basics
-------
-
-Creating a new syntax highlighter begins with describing the highlighting
-rules. There are two basic elements: block and region. A block is just a
-portion of text matching a regular expression and highlighted with a single
-color. Keyword is an example of a block. A region is defined by two regular
-expressions: one for start of region, and another for the end. The main
-difference from a block is that a region can contain blocks and regions
-(including same-named regions). An example of a region is a group of
-statements enclosed in curly brackets (this is used in many languages, for
-example PHP and C). Also, characters matching start and end of a region may be
-highlighted with their own color, and region contents with another.
-
-Blocks and regions may be declared as contained. Contained blocks and regions
-can only appear inside regions. If a region or a block is not declared as
-contained, it can appear both on top level and inside regions. Block or region
-declared as not-contained can only appear on top level.
-
-For any region, a list of blocks and regions that can appear inside this
-region can be specified.
-
-In this document, the term "color group" is used. Chunks of text assigned to
-same color group will be highlighted with same color. Note that in versions
-prior 0.5.0 color goups were refered as CSS classes, but since 0.5.0 not only
-HTML output is supported, so "color group" is more appropriate term.
-
-Elements
---------
-
-The toplevel element is <highlight>. Attribute lang is required and denotes
-the name of the language. Its value is used as a part of generated class name,
-and must only contain letters, digits and underscores. Optional attribute
-case, when given value yes, makes the language case sensitive (default is case
-insensitive). Allowed subelements are:
-
- * <authors>: Information about the authors of the file.
- <author>: Information about a single author of the file. (May be used
- multiple times, one per author.)
- - name="...": Author's name. Required.
- - email="...": Author's email address. Optional.
-
- * <default>: Default color group.
- - innerGroup="...": color group name. Required.
-
- * <region>: Region definition
- - name="...": Region name. Required.
- - innerGroup="...": Default color group of region contents. Required.
- - delimGroup="...": color group of start and end of region. Optional,
- defaults to value of innerGroup attribute.
- - start="...", end="...": Regular expression matching start and end
- of region. Required. Regular expression delimiters are optional, but
- if you need to specify delimiter, use /. The only case when the
- delimiters are needed, is specifying regular expression modifiers,
- such as m or U. Examples: \/\* or /$/m.
- - contained="yes": Marks region as contained.
- - never-contained="yes": Marks region as not-contained.
- - <contains>: Elements allowed inside this region.
- - all="yes" Region can contain any other region or block
- (except not-contained). May be used multiple times.
- - <but> Do not allow certain regions or blocks.
- - region="..." Name of region not allowed within
- current region.
- - block="..." Name of block not allowed within
- current region.
- - region="..." Name of region allowed within current region.
- - block="..." Name of block allowed within current region.
- - <onlyin> Only allow this region within certain regions. May be
- used multiple times.
- - block="..." Name of parent region
-
- * <block>: Block definition
- - name="...": Block name. Required.
- - innerGroup="...": color group of block contents. Optional. If not
- specified, color group of parent region or default color group will be
- used. One would only want to omit this attribute if there are
- keyword groups (see below) inherited from this block, and no special
- highlighting should apply when the block does not match the keyword.
- - match="..." Regular expression matching the block. Required.
- Regular expression delimiters are optional, but if you need to
- specify delimiter, use /. The only case when the delimiters are
- needed, is specifying regular expression modifiers, such as m or U.
- Examples: #|\/\/ or /$/m.
- - contained="yes": Marks block as contained.
- - never-contained="yes": Marks block as not-contained.
- - <onlyin> Only allow this block within certain regions. May be used
- multiple times.
- - block="..." Name of parent region
- - multiline="yes": Marks block as multi-line. By default, whole
- blocks are assumed to reside in a single line. This make the things
- faster. If you need to declare a multi-line block, use this
- attribute.
- - <partgroup>: Assigns another color group to a part of the block that
- matched a subpattern.
- - index="n": Subpattern index. Required.
- - innerGroup="...": color group name. Required.
-
- This is an example from CSS highlighter: the measure is matched as
- a whole, but the measurement units are highlighted with different
- color.
-
- <block name="measure" match="\d*\.?\d+(\%|em|ex|pc|pt|px|in|mm|cm)"
- innerGroup="number" contained="yes">
- <onlyin region="property"/>
- <partGroup index="1" innerGroup="string" />
- </block>
-
- * <keywords>: Keyword group definition. Keyword groups are useful when you
- want to highlight some words that match a condition for a block with a
- different color. Keywords are defined with literal match, not regular
- expressions. For example, you have a block named identifier matching a
- general identifier, and want to highlight reserved words (which match
- this block as well) with different color. You inherit a keyword group
- "reserved" from "identifier" block.
- - name="...": Keyword group. Required.
- - ifdef="...", ifndef="..." : Conditional declaration. See
- "Conditions" below.
- - inherits="...": Inherited block name. Required.
- - innerGroup="...": color group of keyword group. Required.
- - case="yes|no": Overrides case-sensitivity of the language.
- Optional, defaults to global value.
- - <keyword>: Single keyword definition.
- - match="..." The keyword. Note: this is not a regular
- expression, but literal match (possibly case insensitive).
-
-Note that for BC reasons element partClass is alias for partGroup, and
-attributes innerClass and delimClass are aliases of innerGroup and
-delimGroup, respectively.
-
-
-Conditions
-----------
-
-Conditional declarations allow enabling or disabling certain highlighting
-rules at runtime. For example, Java highlighter has a very big list of
-keywords matching Java standard classes. Finding a match in this list can take
-much time. For that reason, corresponding keyword group is declared with
-"ifdef" attribute :
-
- <keywords name="builtin" inherits="identifier" innerClass="builtin"
- case="yes" ifdef="java.builtins">
- <keyword match="AbstractAction" />
- <keyword match="AbstractBorder" />
- <keyword match="AbstractButton" />
- ...
- ...
- <keyword match="_Remote_Stub" />
- <keyword match="_ServantActivatorStub" />
- <keyword match="_ServantLocatorStub" />
- </keywords>
-
-This keyword group will be only enabled when "java.builtins" is passed as an
-element of "defines" option:
-
- $options = array(
- 'defines' => array(
- 'java.builtins',
- ),
- 'numbers' => HL_NUMBERS_TABLE,
- );
- $highlighter = Text_Highlighter::factory('java', $options);
-
-"ifndef" attribute has reverse meaning.
-
-Currently, "ifdef" and "ifndef" attributes are only supported for <keywords>
-tag.
-
-
-
-Class generation
-================
-
-Creating XML description of highlighting rules is the most complicated part of
-the process. To generate the class, you need just few lines of code:
-
- <?php
- require_once 'Text/Highlighter/Generator.php';
- $generator = new Text_Highlighter_Generator('php.xml');
- $generator->generate();
- $generator->saveCode('PHP.php');
- ?>
-
-
-
-Command-line class generation tool
-==================================
-
-Example from previous section looks pretty simple, but it does not handle any
-errors which may occur during parsing of XML source. The package provides a
-command-line script to make generation of classes even more simple, and takes
-care of possible errors. It is called generate (on Unix/Linux) or generate.bat
-(on Windows). This script is able to process multiple files in one run, and
-also to process XML from standard input and write generated code to standard
-output.
-
- Usage:
- generate options
-
- Options:
- -x filename, --xml=filename
- source XML file. Multiple input files can be specified, in which
- case each -x option must be followed by -p unless -d is specified
- Defaults to stdin
- -p filename, --php=filename
- destination PHP file. Defaults to stdout. If specied multiple times,
- each -p must follow -x
- -d dirname, --dir=dirname
- Default destination directory. File names will be taken from XML input
- ("lang" attribute of <highlight> tag)
- -h, --help
- This help
-
-Examples
-
- Read from php.xml, write to PHP.php
-
- generate -x php.xml -p PHP.php
-
- Read from php.xml, write to standard output
-
- generate -x php.xml
-
- Read from php.xml, write to PHP.php, read from xml.xml, write to XML.php
-
- generate -x php.xml -p PHP.php -x xml.xml -p XML.php
-
- Read from php.xml, write to /some/dir/PHP.php, read from xml.xml, write to
- /some/dir/XML.php (assuming that xml.xml contains <highlight lang="xml">, and
- php.xml contains <highlight lang="php">)
-
- generate -x php.xml -x xml.xml -d /some/dir/
-
-
-
-Renderers
-=========
-
-Introduction
-------------
-
-Text_Highlighter supports renderes. Using renderers, you can get output in
-different formats. Two renderers are included in the package:
-
- - HTML renderer. Generates HTML output. A style sheet should be linked to
- the document to display colored text
-
- - Console renderer. Can be used to output highlighted text to
- color-capable terminals, either directly or trough less -r
-
-
-Renderers API
--------------
-
-Renderers are subclasses of Text_Highlighter_Renderer. Renderer should
-override at least two methods - acceptToken and getOutput. Overriding other
-methods is optional, depending on the nature of renderer's output and details
-of implementation.
-
- string reset()
- resets renderer state. This method is called every time before a new
- source file is highlighted.
-
- string preprocess(string $code)
- preprocesses code. Can be used, for example, to normalize whitespace
- before highlighting. Returns preprocessed string.
-
- void acceptToken(string $group, string $content)
- the core method of the renderer. Highlighter passes chunks of text to
- this method in $content, and color group in $group
-
- void finalize()
- signals the renderer that no more tokens are available.
-
- mixed getOutput()
- returns generated output.
-
-
-Setting renderer options
---------------------------------
-
-Renderers accept an optional argument to their constructor - options array.
-Elements of this array are renderer-specific.
-
-HTML renderer
--------------
-
-HTML renderer produces HTML output with optional line numbering. The renderer
-itself does not provide information about actual colors of highlighted text.
-Instead, <span class="hl-XXX"> is used, where XXX is replaced with color group
-name (hl-var, hl-string, etc.). It is up to you to create a CSS stylesheet.
-If 'use_language' option with value evaluating to true was passed, class names
-will be formatted as "LANG-hl-XXX", where LANG is language name as defined in
-highlighter XML source ("lang" attribute of <highlight> tag) in lower case.
-
-There are 3 special CSS classes:
-
- hl-main - this class applies to whole output or right table column,
- depending on 'numbers' option
- hl-gutter - applies to left column in table
- hl-table - applies to whole table
-
-HTML renderer accepts following options (each being optional):
-
- * numbers - line numbering style.
- 0 - no numbering (default)
- HL_NUMBERS_LI - use <ol></ol> for line numbering
- HL_NUMBERS_TABLE - create a 2-column table, with line numbers in left
- column and highlighted text in right column
-
- * tabsize - tabulation size. Defaults to 4
-
- Example:
-
- require_once 'Text/Highlighter/Renderer/Html.php';
- $options = array(
- 'numbers' => HL_NUMBERS_LI,
- 'tabsize' => 8,
- );
- $renderer = new Text_Highlighter_Renderer_HTML($options);
-
-Console renderer
-----------------
-
-Console renderer produces output for displaying on a color-capable terminal,
-either directly or through less -r, using ANSI escape sequences. By default,
-this renderer only highlights most common color groups. Additional colors
-can be specified using 'colors' option. This renderer also accepts 'numbers'
-option - a boolean value, and 'tabsize' option.
-
- Example :
-
- require_once 'Text/Highlighter/Renderer/Console.php';
- $colors = array(
- 'prepro' => "\033[35m",
- 'types' => "\033[32m",
- );
- $options = array(
- 'numbers' => true,
- 'tabsize' => 8,
- 'colors' => $colors,
- );
- $renderer = new Text_Highlighter_Renderer_Console($options);
-
-
-ANSI color escape sequences have the following format:
-
- ESC[#;#;....;#m
-
-where ESC is character with ASCII code 27 (033 octal, 0x1B hexadecimal). # is
-one of the following:
-
- 0 for normal display
- 1 for bold on
- 4 underline (mono only)
- 5 blink on
- 7 reverse video on
- 8 nondisplayed (invisible)
- 30 black foreground
- 31 red foreground
- 32 green foreground
- 33 yellow foreground
- 34 blue foreground
- 35 magenta foreground
- 36 cyan foreground
- 37 white foreground
- 40 black background
- 41 red background
- 42 green background
- 43 yellow background
- 44 blue background
- 45 magenta background
- 46 cyan background
- 47 white background
-
-
-How to use Text_Highlighter class
-=================================
-
-Creating a highlighter object
------------------------------
-
-To create a highlighter for a certain language, use Text_Highlighter::factory()
-static method:
-
- require_once 'Text/Highlighter.php';
- $hl = Text_Highlighter::factory('php');
-
-
-Setting a renderer
-------------------
-
-Actual output is produced by a renderer.
-
- require_once 'Text/Highlighter.php';
- require_once 'Text/Highlighter/Renderer/Html.php';
- $options = array(
- 'numbers' => HL_NUMBERS_LI,
- 'tabsize' => 8,
- );
- $renderer = new Text_Highlighter_Renderer_HTML($options);
- $hl = Text_Highlighter::factory('php');
- $hl->setRenderer($renderer);
-
-Note that for BC reasons, it is possible to use highlighter without setting a
-renderer. If no renderer is set, HTML renderer will be used by default. In
-this case, you should pass options as second parameter to factory method. The
-following example works exactly as previous one:
-
- require_once 'Text/Highlighter.php';
- $options = array(
- 'numbers' => HL_NUMBERS_LI,
- 'tabsize' => 8,
- );
- $hl = Text_Highlighter::factory('php', $options);
-
-
-Getting output
---------------
-
-And finally, do the highlighting and get the output:
-
- require_once 'Text/Highlighter.php';
- require_once 'Text/Highlighter/Renderer/Html.php';
- $options = array(
- 'numbers' => HL_NUMBERS_LI,
- 'tabsize' => 8,
- );
- $renderer = new Text_Highlighter_Renderer_HTML($options);
- $hl = Text_Highlighter::factory('php');
- $hl->setRenderer($renderer);
- $html = $hl->highlight(file_get_contents('example.php'));
-
-# vim: set autoindent tabstop=4 shiftwidth=4 softtabstop=4 tw=78: */
-
diff --git a/library/Text_Highlighter/TODO b/library/Text_Highlighter/TODO
deleted file mode 100644
index 77a148b8a..000000000
--- a/library/Text_Highlighter/TODO
+++ /dev/null
@@ -1,12 +0,0 @@
-# $Id$
-
-Major issues to solve (but I currently have no idea how) :
-
-- speedup highlighting process
-
-- switching between highlighters depending on context, for example :
- PHP code -> HTML -> (JavaScript|CSS)
-
-
-# vim: set autoindent tabstop=4 shiftwidth=4 softtabstop=4 tw=78: */
-
diff --git a/library/Text_Highlighter/Text/Highlighter.php b/library/Text_Highlighter/Text/Highlighter.php
deleted file mode 100644
index 480113c16..000000000
--- a/library/Text_Highlighter/Text/Highlighter.php
+++ /dev/null
@@ -1,398 +0,0 @@
-<?php
-/* vim: set expandtab tabstop=4 shiftwidth=4 softtabstop=4: */
-/**
- * Highlighter base class
- *
- * PHP versions 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @category Text
- * @package Text_Highlighter
- * @author Andrey Demenev <demenev@gmail.com>
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version CVS: $Id$
- * @link http://pear.php.net/package/Text_Highlighter
- */
-
-// require_once 'PEAR.php';
-
-// {{{ BC constants
-
-// BC trick : define constants related to default
-// renderer if needed
-if (!defined('HL_NUMBERS_LI')) {
- /**#@+
- * Constant for use with $options['numbers']
- * @see Text_Highlighter_Renderer_Html::_init()
- */
- /**
- * use numbered list
- */
- define ('HL_NUMBERS_LI' , 1);
- /**
- * Use 2-column table with line numbers in left column and code in right column.
- * Forces $options['tag'] = HL_TAG_PRE
- */
- define ('HL_NUMBERS_TABLE' , 2);
- /**#@-*/
-}
-
-// }}}
-// {{{ constants
-/**
- * for our purpose, it is infinity
- */
-define ('HL_INFINITY', 1000000000);
-
-// }}}
-
-/**
- * Text highlighter base class
- *
- * @author Andrey Demenev <demenev@gmail.com>
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: @package_version@
- * @link http://pear.php.net/package/Text_Highlighter
- */
-
-// {{{ Text_Highlighter
-
-/**
- * Text highlighter base class
- *
- * This class implements all functions necessary for highlighting,
- * but it does not contain highlighting rules. Actual highlighting is
- * done using a descendent of this class.
- *
- * One is not supposed to manually create descendent classes.
- * Instead, describe highlighting rules in XML format and
- * use {@link Text_Highlighter_Generator} to create descendent class.
- * Alternatively, an instance of a descendent class can be created
- * directly.
- *
- * Use {@link Text_Highlighter::factory()} to create an
- * object for particular language highlighter
- *
- * Usage example
- * <code>
- *require_once 'Text/Highlighter.php';
- *$hlSQL = Text_Highlighter::factory('SQL',array('numbers'=>true));
- *echo $hlSQL->highlight('SELECT * FROM table a WHERE id = 12');
- * </code>
- *
- * @author Andrey Demenev <demenev@gmail.com>
- * @package Text_Highlighter
- * @access public
- */
-
-class Text_Highlighter
-{
- // {{{ members
-
- /**
- * Syntax highlighting rules.
- * Auto-generated classes set this var
- *
- * @access protected
- * @see _init
- * @var array
- */
- var $_syntax;
-
- /**
- * Renderer object.
- *
- * @access private
- * @var array
- */
- var $_renderer;
-
- /**
- * Options. Keeped for BC
- *
- * @access protected
- * @var array
- */
- var $_options = array();
-
- /**
- * Conditionds
- *
- * @access protected
- * @var array
- */
- var $_conditions = array();
-
- /**
- * Disabled keywords
- *
- * @access protected
- * @var array
- */
- var $_disabled = array();
-
- /**
- * Language
- *
- * @access protected
- * @var string
- */
- var $_language = '';
-
- // }}}
- // {{{ _checkDefines
-
- /**
- * Called by subclssses' constructors to enable/disable
- * optional highlighter rules
- *
- * @param array $defines Conditional defines
- *
- * @access protected
- */
- function _checkDefines()
- {
- if (isset($this->_options['defines'])) {
- $defines = $this->_options['defines'];
- } else {
- $defines = array();
- }
- foreach ($this->_conditions as $name => $actions) {
- foreach($actions as $action) {
- $present = in_array($name, $defines);
- if (!$action[1]) {
- $present = !$present;
- }
- if ($present) {
- unset($this->_disabled[$action[0]]);
- } else {
- $this->_disabled[$action[0]] = true;
- }
- }
- }
- }
-
- // }}}
- // {{{ factory
-
- /**
- * Create a new Highlighter object for specified language
- *
- * @param string $lang language, for example "SQL"
- * @param array $options Rendering options. This
- * parameter is only keeped for BC reasons, use
- * {@link Text_Highlighter::setRenderer()} instead
- *
- * @return mixed a newly created Highlighter object, or
- * a PEAR error object on error
- *
- * @static
- * @access public
- */
- function &factory($lang, $options = array())
- {
- $lang = strtoupper($lang);
- @include_once 'Text/Highlighter/' . $lang . '.php';
-
- $classname = 'Text_Highlighter_' . $lang;
-
- if (!class_exists($classname)) {
- return PEAR::raiseError('Highlighter for ' . $lang . ' not found');
- }
-
- $obj = new $classname($options);
-
- return $obj;
- }
-
- // }}}
- // {{{ setRenderer
-
- /**
- * Set renderer object
- *
- * @param object $renderer Text_Highlighter_Renderer
- *
- * @access public
- */
- function setRenderer(&$renderer)
- {
- $this->_renderer = $renderer;
- }
-
- // }}}
-
- /**
- * Helper function to find matching brackets
- *
- * @access private
- */
- function _matchingBrackets($str)
- {
- return strtr($str, '()<>[]{}', ')(><][}{');
- }
-
-
-
-
- function _getToken()
- {
- if (!empty($this->_tokenStack)) {
- return array_pop($this->_tokenStack);
- }
- if ($this->_pos >= $this->_len) {
- return NULL;
- }
-
- if ($this->_state != -1 && preg_match($this->_endpattern, $this->_str, $m, PREG_OFFSET_CAPTURE, $this->_pos)) {
- $endpos = $m[0][1];
- $endmatch = $m[0][0];
- } else {
- $endpos = -1;
- }
- preg_match ($this->_regs[$this->_state], $this->_str, $m, PREG_OFFSET_CAPTURE, $this->_pos);
- $n = 1;
-
-
- foreach ($this->_counts[$this->_state] as $i=>$count) {
- if (!isset($m[$n])) {
- break;
- }
- if ($m[$n][1]>-1 && ($endpos == -1 || $m[$n][1] < $endpos)) {
- if ($this->_states[$this->_state][$i] != -1) {
- $this->_tokenStack[] = array($this->_delim[$this->_state][$i], $m[$n][0]);
- } else {
- $inner = $this->_inner[$this->_state][$i];
- if (isset($this->_parts[$this->_state][$i])) {
- $parts = array();
- $partpos = $m[$n][1];
- for ($j=1; $j<=$count; $j++) {
- if ($m[$j+$n][1] < 0) {
- continue;
- }
- if (isset($this->_parts[$this->_state][$i][$j])) {
- if ($m[$j+$n][1] > $partpos) {
- array_unshift($parts, array($inner, substr($this->_str, $partpos, $m[$j+$n][1]-$partpos)));
- }
- array_unshift($parts, array($this->_parts[$this->_state][$i][$j], $m[$j+$n][0]));
- }
- $partpos = $m[$j+$n][1] + strlen($m[$j+$n][0]);
- }
- if ($partpos < $m[$n][1] + strlen($m[$n][0])) {
- array_unshift($parts, array($inner, substr($this->_str, $partpos, $m[$n][1] - $partpos + strlen($m[$n][0]))));
- }
- $this->_tokenStack = array_merge($this->_tokenStack, $parts);
- } else {
- foreach ($this->_keywords[$this->_state][$i] as $g => $re) {
- if (isset($this->_disabled[$g])) {
- continue;
- }
- if (preg_match($re, $m[$n][0])) {
- $inner = $this->_kwmap[$g];
- break;
- }
- }
- $this->_tokenStack[] = array($inner, $m[$n][0]);
- }
- }
- if ($m[$n][1] > $this->_pos) {
- $this->_tokenStack[] = array($this->_lastinner, substr($this->_str, $this->_pos, $m[$n][1]-$this->_pos));
- }
- $this->_pos = $m[$n][1] + strlen($m[$n][0]);
- if ($this->_states[$this->_state][$i] != -1) {
- $this->_stack[] = array($this->_state, $this->_lastdelim, $this->_lastinner, $this->_endpattern);
- $this->_lastinner = $this->_inner[$this->_state][$i];
- $this->_lastdelim = $this->_delim[$this->_state][$i];
- $l = $this->_state;
- $this->_state = $this->_states[$this->_state][$i];
- $this->_endpattern = $this->_end[$this->_state];
- if ($this->_subst[$l][$i]) {
- for ($k=0; $k<=$this->_counts[$l][$i]; $k++) {
- if (!isset($m[$i+$k])) {
- break;
- }
- $quoted = preg_quote($m[$n+$k][0], '/');
- $this->_endpattern = str_replace('%'.$k.'%', $quoted, $this->_endpattern);
- $this->_endpattern = str_replace('%b'.$k.'%', $this->_matchingBrackets($quoted), $this->_endpattern);
- }
- }
- }
- return array_pop($this->_tokenStack);
- }
- $n += $count + 1;
- }
-
- if ($endpos > -1) {
- $this->_tokenStack[] = array($this->_lastdelim, $endmatch);
- if ($endpos > $this->_pos) {
- $this->_tokenStack[] = array($this->_lastinner, substr($this->_str, $this->_pos, $endpos-$this->_pos));
- }
- list($this->_state, $this->_lastdelim, $this->_lastinner, $this->_endpattern) = array_pop($this->_stack);
- $this->_pos = $endpos + strlen($endmatch);
- return array_pop($this->_tokenStack);
- }
- $p = $this->_pos;
- $this->_pos = HL_INFINITY;
- return array($this->_lastinner, substr($this->_str, $p));
- }
-
-
-
-
- // {{{ highlight
-
- /**
- * Highlights code
- *
- * @param string $str Code to highlight
- * @access public
- * @return string Highlighted text
- *
- */
-
- function highlight($str)
- {
- if (!($this->_renderer)) {
- include_once('Text/Highlighter/Renderer/Html.php');
- $this->_renderer = new Text_Highlighter_Renderer_Html($this->_options);
- }
- $this->_state = -1;
- $this->_pos = 0;
- $this->_stack = array();
- $this->_tokenStack = array();
- $this->_lastinner = $this->_defClass;
- $this->_lastdelim = $this->_defClass;
- $this->_endpattern = '';
- $this->_renderer->reset();
- $this->_renderer->setCurrentLanguage($this->_language);
- $this->_str = $this->_renderer->preprocess($str);
- $this->_len = strlen($this->_str);
- while ($token = $this->_getToken()) {
- $this->_renderer->acceptToken($token[0], $token[1]);
- }
- $this->_renderer->finalize();
- return $this->_renderer->getOutput();
- }
-
- // }}}
-
-}
-
-// }}}
-
-/*
- * Local variables:
- * tab-width: 4
- * c-basic-offset: 4
- * c-hanging-comment-ender-p: nil
- * End:
- */
-
-?>
diff --git a/library/Text_Highlighter/Text/Highlighter/ABAP.php b/library/Text_Highlighter/Text/Highlighter/ABAP.php
deleted file mode 100644
index b2f7bda94..000000000
--- a/library/Text_Highlighter/Text/Highlighter/ABAP.php
+++ /dev/null
@@ -1,519 +0,0 @@
-<?php
-/**
- * Auto-generated class. ABAP syntax highlighting
- *
- * PHP version 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @link http://pear.php.net/package/Text_Highlighter
- * @category Text
- * @package Text_Highlighter
- * @version generated from: : abap.xml,v 1.1 2007/06/03 02:35:28 ssttoo Exp
- * @author Stoyan Stefanov <ssttoo@gmail.com>
- *
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter.php';
-
-/**
- * Auto-generated class. ABAP syntax highlighting
- *
- * @author Stoyan Stefanov <ssttoo@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: @package_version@
- * @link http://pear.php.net/package/Text_Highlighter
- */
-class Text_Highlighter_ABAP extends Text_Highlighter
-{
- var $_language = 'abap';
-
- /**
- * PHP4 Compatible Constructor
- *
- * @param array $options
- * @access public
- */
- function Text_Highlighter_ABAP($options=array())
- {
- $this->__construct($options);
- }
-
-
- /**
- * Constructor
- *
- * @param array $options
- * @access public
- */
- function __construct($options=array())
- {
-
- $this->_options = $options;
- $this->_regs = array (
- -1 => '/((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)^\\*|")|((?i)\')|((?i)[a-z_\\-]\\w*)/',
- 0 => '/((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)^\\*|")|((?i)\')|((?i)0[xX][\\da-f]+)|((?i)\\d\\d*|\\b0\\b)|((?i)0[0-7]+)|((?i)(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?i)[a-z_\\-]\\w*)/',
- 1 => '/((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)^\\*|")|((?i)\')|((?i)0[xX][\\da-f]+)|((?i)\\d\\d*|\\b0\\b)|((?i)0[0-7]+)|((?i)(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?i)[a-z_\\-]\\w*)/',
- 2 => '/((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)^\\*|")|((?i)\')|((?i)0[xX][\\da-f]+)|((?i)\\d\\d*|\\b0\\b)|((?i)0[0-7]+)|((?i)(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?i)[a-z_\\-]\\w*)/',
- 3 => '//',
- 4 => '//',
- );
- $this->_counts = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- ),
- 0 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 2,
- 9 => 0,
- ),
- 1 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 2,
- 9 => 0,
- ),
- 2 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 2,
- 9 => 0,
- ),
- 3 =>
- array (
- ),
- 4 =>
- array (
- ),
- );
- $this->_delim = array (
- -1 =>
- array (
- 0 => 'brackets',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'comment',
- 4 => 'quotes',
- 5 => '',
- ),
- 0 =>
- array (
- 0 => 'brackets',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'comment',
- 4 => 'quotes',
- 5 => '',
- 6 => '',
- 7 => '',
- 8 => '',
- 9 => '',
- ),
- 1 =>
- array (
- 0 => 'brackets',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'comment',
- 4 => 'quotes',
- 5 => '',
- 6 => '',
- 7 => '',
- 8 => '',
- 9 => '',
- ),
- 2 =>
- array (
- 0 => 'brackets',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'comment',
- 4 => 'quotes',
- 5 => '',
- 6 => '',
- 7 => '',
- 8 => '',
- 9 => '',
- ),
- 3 =>
- array (
- ),
- 4 =>
- array (
- ),
- );
- $this->_inner = array (
- -1 =>
- array (
- 0 => 'code',
- 1 => 'code',
- 2 => 'code',
- 3 => 'comment',
- 4 => 'string',
- 5 => 'identifier',
- ),
- 0 =>
- array (
- 0 => 'code',
- 1 => 'code',
- 2 => 'code',
- 3 => 'comment',
- 4 => 'string',
- 5 => 'number',
- 6 => 'number',
- 7 => 'number',
- 8 => 'number',
- 9 => 'identifier',
- ),
- 1 =>
- array (
- 0 => 'code',
- 1 => 'code',
- 2 => 'code',
- 3 => 'comment',
- 4 => 'string',
- 5 => 'number',
- 6 => 'number',
- 7 => 'number',
- 8 => 'number',
- 9 => 'identifier',
- ),
- 2 =>
- array (
- 0 => 'code',
- 1 => 'code',
- 2 => 'code',
- 3 => 'comment',
- 4 => 'string',
- 5 => 'number',
- 6 => 'number',
- 7 => 'number',
- 8 => 'number',
- 9 => 'identifier',
- ),
- 3 =>
- array (
- ),
- 4 =>
- array (
- ),
- );
- $this->_end = array (
- 0 => '/(?i)\\}/',
- 1 => '/(?i)\\)/',
- 2 => '/(?i)\\]/',
- 3 => '/(?mi)$/',
- 4 => '/(?i)\'/',
- );
- $this->_states = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => 4,
- 5 => -1,
- ),
- 0 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => 4,
- 5 => -1,
- 6 => -1,
- 7 => -1,
- 8 => -1,
- 9 => -1,
- ),
- 1 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => 4,
- 5 => -1,
- 6 => -1,
- 7 => -1,
- 8 => -1,
- 9 => -1,
- ),
- 2 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => 4,
- 5 => -1,
- 6 => -1,
- 7 => -1,
- 8 => -1,
- 9 => -1,
- ),
- 3 =>
- array (
- ),
- 4 =>
- array (
- ),
- );
- $this->_keywords = array (
- -1 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 =>
- array (
- 'sy' => '/^((?i)screen-name|screen-group1|screen-group2|screen-group3|screen-group4|screen-required|screen-input|screen-output|screen-intensified|screen-invisible|screen-length|screen-active|sy-index|sy-pagno|sy-tabix|sy-tfill|sy-tlopc|sy-tmaxl|sy-toccu|sy-ttabc|sy-tstis|sy-ttabi|sy-dbcnt|sy-fdpos|sy-colno|sy-linct|sy-linno|sy-linsz|sy-pagct|sy-macol|sy-marow|sy-tleng|sy-sfoff|sy-willi|sy-lilli|sy-subrc|sy-fleng|sy-cucol|sy-curow|sy-lsind|sy-listi|sy-stepl|sy-tpagi|sy-winx1|sy-winy1|sy-winx2|sy-winy2|sy-winco|sy-winro|sy-windi|sy-srows|sy-scols|sy-loopc|sy-folen|sy-fodec|sy-tzone|sy-dayst|sy-ftype|sy-appli|sy-fdayw|sy-ccurs|sy-ccurt|sy-debug|sy-ctype|sy-input|sy-langu|sy-modno|sy-batch|sy-binpt|sy-calld|sy-dynnr|sy-dyngr|sy-newpa|sy-pri40|sy-rstrt|sy-wtitl|sy-cpage|sy-dbnam|sy-mandt|sy-prefx|sy-fmkey|sy-pexpi|sy-prini|sy-primm|sy-prrel|sy-playo|sy-prbig|sy-playp|sy-prnew|sy-prlog|sy-pdest|sy-plist|sy-pauth|sy-prdsn|sy-pnwpa|sy-callr|sy-repi2|sy-rtitl|sy-prrec|sy-prtxt|sy-prabt|sy-lpass|sy-nrpag|sy-paart|sy-prcop|sy-batzs|sy-bspld|sy-brep4|sy-batzo|sy-batzd|sy-batzw|sy-batzm|sy-ctabl|sy-dbsys|sy-dcsys|sy-macdb|sy-sysid|sy-opsys|sy-pfkey|sy-saprl|sy-tcode|sy-ucomm|sy-cfwae|sy-chwae|sy-spono|sy-sponr|sy-waers|sy-cdate|sy-datum|sy-slset|sy-subty|sy-subcs|sy-group|sy-ffile|sy-uzeit|sy-dsnam|sy-repid|sy-tabid|sy-tfdsn|sy-uname|sy-lstat|sy-abcde|sy-marky|sy-sfnam|sy-tname|sy-msgli|sy-title|sy-entry|sy-lisel|sy-uline|sy-xcode|sy-cprog|sy-xprog|sy-xform|sy-ldbpg|sy-tvar0|sy-tvar1|sy-tvar2|sy-tvar3|sy-tvar4|sy-tvar5|sy-tvar6|sy-tvar7|sy-tvar8|sy-tvar9|sy-msgid|sy-msgty|sy-msgno|sy-msgv1|sy-msgv2|sy-msgv3|sy-msgv4|sy-oncom|sy-vline|sy-winsl|sy-staco|sy-staro|sy-datar|sy-host|sy-locdb|sy-locop|sy-datlo|sy-timlo|sy-zonlo|syst-index|syst-pagno|syst-tabix|syst-tfill|syst-tlopc|syst-tmaxl|syst-toccu|syst-ttabc|syst-tstis|syst-ttabi|syst-dbcnt|syst-fdpos|syst-colno|syst-linct|syst-linno|syst-linsz|syst-pagct|syst-macol|syst-marow|syst-tleng|syst-sfoff|syst-willi|syst-lilli|syst-subrc|syst-fleng|syst-cucol|syst-curow|syst-lsind|syst-listi|syst-stepl|syst-tpagi|syst-winx1|syst-winy1|syst-winx2|syst-winy2|syst-winco|syst-winro|syst-windi|syst-srows|syst-scols|syst-loopc|syst-folen|syst-fodec|syst-tzone|syst-dayst|syst-ftype|syst-appli|syst-fdayw|syst-ccurs|syst-ccurt|syst-debug|syst-ctype|syst-input|syst-langu|syst-modno|syst-batch|syst-binpt|syst-calld|syst-dynnr|syst-dyngr|syst-newpa|syst-pri40|syst-rstrt|syst-wtitl|syst-cpage|syst-dbnam|syst-mandt|syst-prefx|syst-fmkey|syst-pexpi|syst-prini|syst-primm|syst-prrel|syst-playo|syst-prbig|syst-playp|syst-prnew|syst-prlog|syst-pdest|syst-plist|syst-pauth|syst-prdsn|syst-pnwpa|syst-callr|syst-repi2|syst-rtitl|syst-prrec|syst-prtxt|syst-prabt|syst-lpass|syst-nrpag|syst-paart|syst-prcop|syst-batzs|syst-bspld|syst-brep4|syst-batzo|syst-batzd|syst-batzw|syst-batzm|syst-ctabl|syst-dbsys|syst-dcsys|syst-macdb|syst-sysid|syst-opsys|syst-pfkey|syst-saprl|syst-tcode|syst-ucomm|syst-cfwae|syst-chwae|syst-spono|syst-sponr|syst-waers|syst-cdate|syst-datum|syst-slset|syst-subty|syst-subcs|syst-group|syst-ffile|syst-uzeit|syst-dsnam|syst-repid|syst-tabid|syst-tfdsn|syst-uname|syst-lstat|syst-abcde|syst-marky|syst-sfnam|syst-tname|syst-msgli|syst-title|syst-entry|syst-lisel|syst-uline|syst-xcode|syst-cprog|syst-xprog|syst-xform|syst-ldbpg|syst-tvar0|syst-tvar1|syst-tvar2|syst-tvar3|syst-tvar4|syst-tvar5|syst-tvar6|syst-tvar7|syst-tvar8|syst-tvar9|syst-msgid|syst-msgty|syst-msgno|syst-msgv1|syst-msgv2|syst-msgv3|syst-msgv4|syst-oncom|syst-vline|syst-winsl|syst-staco|syst-staro|syst-datar|syst-host|syst-locdb|syst-locop|syst-datlo|syst-timlo|syst-zonlo)$/',
- 'reserved' => '/^((?i)abs|acos|add|add-corresponding|adjacent|after|aliases|all|analyzer|and|any|append|as|ascending|asin|assign|assigned|assigning|at|atan|authority-check|avg|back|before|begin|binary|bit|bit-and|bit-not|bit-or|bit-xor|blank|block|break-point|buffer|by|c|call|case|catch|ceil|centered|chain|change|changing|check|checkbox|class|class-data|class-events|class-methods|class-pool|clear|client|close|cnt|code|collect|color|comment|commit|communication|compute|concatenate|condense|constants|context|contexts|continue|control|controls|convert|copy|corresponding|cos|cosh|count|country|create|currency|cursor|customer-function|data|database|dataset|delete|decimals|default|define|demand|descending|describe|dialog|distinct|div|divide|divide-corresponding|do|duplicates|dynpro|edit|editor-call|else|elseif|end|end-of-definition|end-of-page|end-of-selection|endat|endcase|endcatch|endchain|endclass|enddo|endexec|endform|endfunction|endif|endinterface|endloop|endmethod|endmodule|endon|endprovide|endselect|endwhile|entries|events|exec|exit|exit-command|exp|exponent|export|exporting|exceptions|extended|extract|fetch|field|field-groups|field-symbols|fields|floor|for|form|format|frac|frame|free|from|function|function-pool|generate|get|group|hashed|header|help-id|help-request|hide|hotspot|icon|id|if|import|importing|include|index|infotypes|initialization|inner|input|insert|intensified|interface|interface-pool|interfaces|into|inverse|join|key|language|last|leave|left|left-justified|like|line|line-count|line-selection|line-size|lines|list-processing|load|load-of-program|local|locale|log|log10|loop|m|margin|mask|matchcode|max|memory|message|message-id|messages|method|methods|min|mod|mode|modif|modify|module|move|move-corresponding|multiply|multiply-corresponding|new|new-line|new-page|next|no|no-gap|no-gaps|no-heading|no-scrolling|no-sign|no-title|no-zero|nodes|non-unique|o|object|obligatory|occurs|of|off|on|open|or|order|others|outer|output|overlay|pack|page|parameter|parameters|perform|pf-status|position|print|print-control|private|process|program|property|protected|provide|public|put|radiobutton|raise|raising|range|ranges|read|receive|refresh|reject|replace|report|requested|reserve|reset|right-justified|rollback|round|rows|rtti|run|scan|screen|search|separated|scroll|scroll-boundary|select|select-options|selection-screen|selection-table|set|shared|shift|sign|sin|single|sinh|size|skip|sort|sorted|split|sql|sqrt|stamp|standard|start-of-selection|statics|stop|string|strlen|structure|submit|subtract|subtract-corresponding|sum|supply|suppress|symbol|syntax-check|syntax-trace|system-call|system-exceptions|table|table_line|tables|tan|tanh|text|textpool|time|times|title|titlebar|to|top-of-page|transaction|transfer|translate|transporting|trunc|type|type-pool|type-pools|types|uline|under|unique|unit|unpack|up|update|user-command|using|value|value-request|values|vary|when|where|while|window|with|with-title|work|write|x|xstring|z|zone)$/',
- 'constants' => '/^((?i)initial|null|space|col_background|col_heading|col_normal|col_total|col_key|col_positive|col_negative|col_group)$/',
- ),
- ),
- 0 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 =>
- array (
- ),
- 6 =>
- array (
- ),
- 7 =>
- array (
- ),
- 8 =>
- array (
- ),
- 9 =>
- array (
- 'sy' => '/^((?i)screen-name|screen-group1|screen-group2|screen-group3|screen-group4|screen-required|screen-input|screen-output|screen-intensified|screen-invisible|screen-length|screen-active|sy-index|sy-pagno|sy-tabix|sy-tfill|sy-tlopc|sy-tmaxl|sy-toccu|sy-ttabc|sy-tstis|sy-ttabi|sy-dbcnt|sy-fdpos|sy-colno|sy-linct|sy-linno|sy-linsz|sy-pagct|sy-macol|sy-marow|sy-tleng|sy-sfoff|sy-willi|sy-lilli|sy-subrc|sy-fleng|sy-cucol|sy-curow|sy-lsind|sy-listi|sy-stepl|sy-tpagi|sy-winx1|sy-winy1|sy-winx2|sy-winy2|sy-winco|sy-winro|sy-windi|sy-srows|sy-scols|sy-loopc|sy-folen|sy-fodec|sy-tzone|sy-dayst|sy-ftype|sy-appli|sy-fdayw|sy-ccurs|sy-ccurt|sy-debug|sy-ctype|sy-input|sy-langu|sy-modno|sy-batch|sy-binpt|sy-calld|sy-dynnr|sy-dyngr|sy-newpa|sy-pri40|sy-rstrt|sy-wtitl|sy-cpage|sy-dbnam|sy-mandt|sy-prefx|sy-fmkey|sy-pexpi|sy-prini|sy-primm|sy-prrel|sy-playo|sy-prbig|sy-playp|sy-prnew|sy-prlog|sy-pdest|sy-plist|sy-pauth|sy-prdsn|sy-pnwpa|sy-callr|sy-repi2|sy-rtitl|sy-prrec|sy-prtxt|sy-prabt|sy-lpass|sy-nrpag|sy-paart|sy-prcop|sy-batzs|sy-bspld|sy-brep4|sy-batzo|sy-batzd|sy-batzw|sy-batzm|sy-ctabl|sy-dbsys|sy-dcsys|sy-macdb|sy-sysid|sy-opsys|sy-pfkey|sy-saprl|sy-tcode|sy-ucomm|sy-cfwae|sy-chwae|sy-spono|sy-sponr|sy-waers|sy-cdate|sy-datum|sy-slset|sy-subty|sy-subcs|sy-group|sy-ffile|sy-uzeit|sy-dsnam|sy-repid|sy-tabid|sy-tfdsn|sy-uname|sy-lstat|sy-abcde|sy-marky|sy-sfnam|sy-tname|sy-msgli|sy-title|sy-entry|sy-lisel|sy-uline|sy-xcode|sy-cprog|sy-xprog|sy-xform|sy-ldbpg|sy-tvar0|sy-tvar1|sy-tvar2|sy-tvar3|sy-tvar4|sy-tvar5|sy-tvar6|sy-tvar7|sy-tvar8|sy-tvar9|sy-msgid|sy-msgty|sy-msgno|sy-msgv1|sy-msgv2|sy-msgv3|sy-msgv4|sy-oncom|sy-vline|sy-winsl|sy-staco|sy-staro|sy-datar|sy-host|sy-locdb|sy-locop|sy-datlo|sy-timlo|sy-zonlo|syst-index|syst-pagno|syst-tabix|syst-tfill|syst-tlopc|syst-tmaxl|syst-toccu|syst-ttabc|syst-tstis|syst-ttabi|syst-dbcnt|syst-fdpos|syst-colno|syst-linct|syst-linno|syst-linsz|syst-pagct|syst-macol|syst-marow|syst-tleng|syst-sfoff|syst-willi|syst-lilli|syst-subrc|syst-fleng|syst-cucol|syst-curow|syst-lsind|syst-listi|syst-stepl|syst-tpagi|syst-winx1|syst-winy1|syst-winx2|syst-winy2|syst-winco|syst-winro|syst-windi|syst-srows|syst-scols|syst-loopc|syst-folen|syst-fodec|syst-tzone|syst-dayst|syst-ftype|syst-appli|syst-fdayw|syst-ccurs|syst-ccurt|syst-debug|syst-ctype|syst-input|syst-langu|syst-modno|syst-batch|syst-binpt|syst-calld|syst-dynnr|syst-dyngr|syst-newpa|syst-pri40|syst-rstrt|syst-wtitl|syst-cpage|syst-dbnam|syst-mandt|syst-prefx|syst-fmkey|syst-pexpi|syst-prini|syst-primm|syst-prrel|syst-playo|syst-prbig|syst-playp|syst-prnew|syst-prlog|syst-pdest|syst-plist|syst-pauth|syst-prdsn|syst-pnwpa|syst-callr|syst-repi2|syst-rtitl|syst-prrec|syst-prtxt|syst-prabt|syst-lpass|syst-nrpag|syst-paart|syst-prcop|syst-batzs|syst-bspld|syst-brep4|syst-batzo|syst-batzd|syst-batzw|syst-batzm|syst-ctabl|syst-dbsys|syst-dcsys|syst-macdb|syst-sysid|syst-opsys|syst-pfkey|syst-saprl|syst-tcode|syst-ucomm|syst-cfwae|syst-chwae|syst-spono|syst-sponr|syst-waers|syst-cdate|syst-datum|syst-slset|syst-subty|syst-subcs|syst-group|syst-ffile|syst-uzeit|syst-dsnam|syst-repid|syst-tabid|syst-tfdsn|syst-uname|syst-lstat|syst-abcde|syst-marky|syst-sfnam|syst-tname|syst-msgli|syst-title|syst-entry|syst-lisel|syst-uline|syst-xcode|syst-cprog|syst-xprog|syst-xform|syst-ldbpg|syst-tvar0|syst-tvar1|syst-tvar2|syst-tvar3|syst-tvar4|syst-tvar5|syst-tvar6|syst-tvar7|syst-tvar8|syst-tvar9|syst-msgid|syst-msgty|syst-msgno|syst-msgv1|syst-msgv2|syst-msgv3|syst-msgv4|syst-oncom|syst-vline|syst-winsl|syst-staco|syst-staro|syst-datar|syst-host|syst-locdb|syst-locop|syst-datlo|syst-timlo|syst-zonlo)$/',
- 'reserved' => '/^((?i)abs|acos|add|add-corresponding|adjacent|after|aliases|all|analyzer|and|any|append|as|ascending|asin|assign|assigned|assigning|at|atan|authority-check|avg|back|before|begin|binary|bit|bit-and|bit-not|bit-or|bit-xor|blank|block|break-point|buffer|by|c|call|case|catch|ceil|centered|chain|change|changing|check|checkbox|class|class-data|class-events|class-methods|class-pool|clear|client|close|cnt|code|collect|color|comment|commit|communication|compute|concatenate|condense|constants|context|contexts|continue|control|controls|convert|copy|corresponding|cos|cosh|count|country|create|currency|cursor|customer-function|data|database|dataset|delete|decimals|default|define|demand|descending|describe|dialog|distinct|div|divide|divide-corresponding|do|duplicates|dynpro|edit|editor-call|else|elseif|end|end-of-definition|end-of-page|end-of-selection|endat|endcase|endcatch|endchain|endclass|enddo|endexec|endform|endfunction|endif|endinterface|endloop|endmethod|endmodule|endon|endprovide|endselect|endwhile|entries|events|exec|exit|exit-command|exp|exponent|export|exporting|exceptions|extended|extract|fetch|field|field-groups|field-symbols|fields|floor|for|form|format|frac|frame|free|from|function|function-pool|generate|get|group|hashed|header|help-id|help-request|hide|hotspot|icon|id|if|import|importing|include|index|infotypes|initialization|inner|input|insert|intensified|interface|interface-pool|interfaces|into|inverse|join|key|language|last|leave|left|left-justified|like|line|line-count|line-selection|line-size|lines|list-processing|load|load-of-program|local|locale|log|log10|loop|m|margin|mask|matchcode|max|memory|message|message-id|messages|method|methods|min|mod|mode|modif|modify|module|move|move-corresponding|multiply|multiply-corresponding|new|new-line|new-page|next|no|no-gap|no-gaps|no-heading|no-scrolling|no-sign|no-title|no-zero|nodes|non-unique|o|object|obligatory|occurs|of|off|on|open|or|order|others|outer|output|overlay|pack|page|parameter|parameters|perform|pf-status|position|print|print-control|private|process|program|property|protected|provide|public|put|radiobutton|raise|raising|range|ranges|read|receive|refresh|reject|replace|report|requested|reserve|reset|right-justified|rollback|round|rows|rtti|run|scan|screen|search|separated|scroll|scroll-boundary|select|select-options|selection-screen|selection-table|set|shared|shift|sign|sin|single|sinh|size|skip|sort|sorted|split|sql|sqrt|stamp|standard|start-of-selection|statics|stop|string|strlen|structure|submit|subtract|subtract-corresponding|sum|supply|suppress|symbol|syntax-check|syntax-trace|system-call|system-exceptions|table|table_line|tables|tan|tanh|text|textpool|time|times|title|titlebar|to|top-of-page|transaction|transfer|translate|transporting|trunc|type|type-pool|type-pools|types|uline|under|unique|unit|unpack|up|update|user-command|using|value|value-request|values|vary|when|where|while|window|with|with-title|work|write|x|xstring|z|zone)$/',
- 'constants' => '/^((?i)initial|null|space|col_background|col_heading|col_normal|col_total|col_key|col_positive|col_negative|col_group)$/',
- ),
- ),
- 1 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 =>
- array (
- ),
- 6 =>
- array (
- ),
- 7 =>
- array (
- ),
- 8 =>
- array (
- ),
- 9 =>
- array (
- 'sy' => '/^((?i)screen-name|screen-group1|screen-group2|screen-group3|screen-group4|screen-required|screen-input|screen-output|screen-intensified|screen-invisible|screen-length|screen-active|sy-index|sy-pagno|sy-tabix|sy-tfill|sy-tlopc|sy-tmaxl|sy-toccu|sy-ttabc|sy-tstis|sy-ttabi|sy-dbcnt|sy-fdpos|sy-colno|sy-linct|sy-linno|sy-linsz|sy-pagct|sy-macol|sy-marow|sy-tleng|sy-sfoff|sy-willi|sy-lilli|sy-subrc|sy-fleng|sy-cucol|sy-curow|sy-lsind|sy-listi|sy-stepl|sy-tpagi|sy-winx1|sy-winy1|sy-winx2|sy-winy2|sy-winco|sy-winro|sy-windi|sy-srows|sy-scols|sy-loopc|sy-folen|sy-fodec|sy-tzone|sy-dayst|sy-ftype|sy-appli|sy-fdayw|sy-ccurs|sy-ccurt|sy-debug|sy-ctype|sy-input|sy-langu|sy-modno|sy-batch|sy-binpt|sy-calld|sy-dynnr|sy-dyngr|sy-newpa|sy-pri40|sy-rstrt|sy-wtitl|sy-cpage|sy-dbnam|sy-mandt|sy-prefx|sy-fmkey|sy-pexpi|sy-prini|sy-primm|sy-prrel|sy-playo|sy-prbig|sy-playp|sy-prnew|sy-prlog|sy-pdest|sy-plist|sy-pauth|sy-prdsn|sy-pnwpa|sy-callr|sy-repi2|sy-rtitl|sy-prrec|sy-prtxt|sy-prabt|sy-lpass|sy-nrpag|sy-paart|sy-prcop|sy-batzs|sy-bspld|sy-brep4|sy-batzo|sy-batzd|sy-batzw|sy-batzm|sy-ctabl|sy-dbsys|sy-dcsys|sy-macdb|sy-sysid|sy-opsys|sy-pfkey|sy-saprl|sy-tcode|sy-ucomm|sy-cfwae|sy-chwae|sy-spono|sy-sponr|sy-waers|sy-cdate|sy-datum|sy-slset|sy-subty|sy-subcs|sy-group|sy-ffile|sy-uzeit|sy-dsnam|sy-repid|sy-tabid|sy-tfdsn|sy-uname|sy-lstat|sy-abcde|sy-marky|sy-sfnam|sy-tname|sy-msgli|sy-title|sy-entry|sy-lisel|sy-uline|sy-xcode|sy-cprog|sy-xprog|sy-xform|sy-ldbpg|sy-tvar0|sy-tvar1|sy-tvar2|sy-tvar3|sy-tvar4|sy-tvar5|sy-tvar6|sy-tvar7|sy-tvar8|sy-tvar9|sy-msgid|sy-msgty|sy-msgno|sy-msgv1|sy-msgv2|sy-msgv3|sy-msgv4|sy-oncom|sy-vline|sy-winsl|sy-staco|sy-staro|sy-datar|sy-host|sy-locdb|sy-locop|sy-datlo|sy-timlo|sy-zonlo|syst-index|syst-pagno|syst-tabix|syst-tfill|syst-tlopc|syst-tmaxl|syst-toccu|syst-ttabc|syst-tstis|syst-ttabi|syst-dbcnt|syst-fdpos|syst-colno|syst-linct|syst-linno|syst-linsz|syst-pagct|syst-macol|syst-marow|syst-tleng|syst-sfoff|syst-willi|syst-lilli|syst-subrc|syst-fleng|syst-cucol|syst-curow|syst-lsind|syst-listi|syst-stepl|syst-tpagi|syst-winx1|syst-winy1|syst-winx2|syst-winy2|syst-winco|syst-winro|syst-windi|syst-srows|syst-scols|syst-loopc|syst-folen|syst-fodec|syst-tzone|syst-dayst|syst-ftype|syst-appli|syst-fdayw|syst-ccurs|syst-ccurt|syst-debug|syst-ctype|syst-input|syst-langu|syst-modno|syst-batch|syst-binpt|syst-calld|syst-dynnr|syst-dyngr|syst-newpa|syst-pri40|syst-rstrt|syst-wtitl|syst-cpage|syst-dbnam|syst-mandt|syst-prefx|syst-fmkey|syst-pexpi|syst-prini|syst-primm|syst-prrel|syst-playo|syst-prbig|syst-playp|syst-prnew|syst-prlog|syst-pdest|syst-plist|syst-pauth|syst-prdsn|syst-pnwpa|syst-callr|syst-repi2|syst-rtitl|syst-prrec|syst-prtxt|syst-prabt|syst-lpass|syst-nrpag|syst-paart|syst-prcop|syst-batzs|syst-bspld|syst-brep4|syst-batzo|syst-batzd|syst-batzw|syst-batzm|syst-ctabl|syst-dbsys|syst-dcsys|syst-macdb|syst-sysid|syst-opsys|syst-pfkey|syst-saprl|syst-tcode|syst-ucomm|syst-cfwae|syst-chwae|syst-spono|syst-sponr|syst-waers|syst-cdate|syst-datum|syst-slset|syst-subty|syst-subcs|syst-group|syst-ffile|syst-uzeit|syst-dsnam|syst-repid|syst-tabid|syst-tfdsn|syst-uname|syst-lstat|syst-abcde|syst-marky|syst-sfnam|syst-tname|syst-msgli|syst-title|syst-entry|syst-lisel|syst-uline|syst-xcode|syst-cprog|syst-xprog|syst-xform|syst-ldbpg|syst-tvar0|syst-tvar1|syst-tvar2|syst-tvar3|syst-tvar4|syst-tvar5|syst-tvar6|syst-tvar7|syst-tvar8|syst-tvar9|syst-msgid|syst-msgty|syst-msgno|syst-msgv1|syst-msgv2|syst-msgv3|syst-msgv4|syst-oncom|syst-vline|syst-winsl|syst-staco|syst-staro|syst-datar|syst-host|syst-locdb|syst-locop|syst-datlo|syst-timlo|syst-zonlo)$/',
- 'reserved' => '/^((?i)abs|acos|add|add-corresponding|adjacent|after|aliases|all|analyzer|and|any|append|as|ascending|asin|assign|assigned|assigning|at|atan|authority-check|avg|back|before|begin|binary|bit|bit-and|bit-not|bit-or|bit-xor|blank|block|break-point|buffer|by|c|call|case|catch|ceil|centered|chain|change|changing|check|checkbox|class|class-data|class-events|class-methods|class-pool|clear|client|close|cnt|code|collect|color|comment|commit|communication|compute|concatenate|condense|constants|context|contexts|continue|control|controls|convert|copy|corresponding|cos|cosh|count|country|create|currency|cursor|customer-function|data|database|dataset|delete|decimals|default|define|demand|descending|describe|dialog|distinct|div|divide|divide-corresponding|do|duplicates|dynpro|edit|editor-call|else|elseif|end|end-of-definition|end-of-page|end-of-selection|endat|endcase|endcatch|endchain|endclass|enddo|endexec|endform|endfunction|endif|endinterface|endloop|endmethod|endmodule|endon|endprovide|endselect|endwhile|entries|events|exec|exit|exit-command|exp|exponent|export|exporting|exceptions|extended|extract|fetch|field|field-groups|field-symbols|fields|floor|for|form|format|frac|frame|free|from|function|function-pool|generate|get|group|hashed|header|help-id|help-request|hide|hotspot|icon|id|if|import|importing|include|index|infotypes|initialization|inner|input|insert|intensified|interface|interface-pool|interfaces|into|inverse|join|key|language|last|leave|left|left-justified|like|line|line-count|line-selection|line-size|lines|list-processing|load|load-of-program|local|locale|log|log10|loop|m|margin|mask|matchcode|max|memory|message|message-id|messages|method|methods|min|mod|mode|modif|modify|module|move|move-corresponding|multiply|multiply-corresponding|new|new-line|new-page|next|no|no-gap|no-gaps|no-heading|no-scrolling|no-sign|no-title|no-zero|nodes|non-unique|o|object|obligatory|occurs|of|off|on|open|or|order|others|outer|output|overlay|pack|page|parameter|parameters|perform|pf-status|position|print|print-control|private|process|program|property|protected|provide|public|put|radiobutton|raise|raising|range|ranges|read|receive|refresh|reject|replace|report|requested|reserve|reset|right-justified|rollback|round|rows|rtti|run|scan|screen|search|separated|scroll|scroll-boundary|select|select-options|selection-screen|selection-table|set|shared|shift|sign|sin|single|sinh|size|skip|sort|sorted|split|sql|sqrt|stamp|standard|start-of-selection|statics|stop|string|strlen|structure|submit|subtract|subtract-corresponding|sum|supply|suppress|symbol|syntax-check|syntax-trace|system-call|system-exceptions|table|table_line|tables|tan|tanh|text|textpool|time|times|title|titlebar|to|top-of-page|transaction|transfer|translate|transporting|trunc|type|type-pool|type-pools|types|uline|under|unique|unit|unpack|up|update|user-command|using|value|value-request|values|vary|when|where|while|window|with|with-title|work|write|x|xstring|z|zone)$/',
- 'constants' => '/^((?i)initial|null|space|col_background|col_heading|col_normal|col_total|col_key|col_positive|col_negative|col_group)$/',
- ),
- ),
- 2 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 =>
- array (
- ),
- 6 =>
- array (
- ),
- 7 =>
- array (
- ),
- 8 =>
- array (
- ),
- 9 =>
- array (
- 'sy' => '/^((?i)screen-name|screen-group1|screen-group2|screen-group3|screen-group4|screen-required|screen-input|screen-output|screen-intensified|screen-invisible|screen-length|screen-active|sy-index|sy-pagno|sy-tabix|sy-tfill|sy-tlopc|sy-tmaxl|sy-toccu|sy-ttabc|sy-tstis|sy-ttabi|sy-dbcnt|sy-fdpos|sy-colno|sy-linct|sy-linno|sy-linsz|sy-pagct|sy-macol|sy-marow|sy-tleng|sy-sfoff|sy-willi|sy-lilli|sy-subrc|sy-fleng|sy-cucol|sy-curow|sy-lsind|sy-listi|sy-stepl|sy-tpagi|sy-winx1|sy-winy1|sy-winx2|sy-winy2|sy-winco|sy-winro|sy-windi|sy-srows|sy-scols|sy-loopc|sy-folen|sy-fodec|sy-tzone|sy-dayst|sy-ftype|sy-appli|sy-fdayw|sy-ccurs|sy-ccurt|sy-debug|sy-ctype|sy-input|sy-langu|sy-modno|sy-batch|sy-binpt|sy-calld|sy-dynnr|sy-dyngr|sy-newpa|sy-pri40|sy-rstrt|sy-wtitl|sy-cpage|sy-dbnam|sy-mandt|sy-prefx|sy-fmkey|sy-pexpi|sy-prini|sy-primm|sy-prrel|sy-playo|sy-prbig|sy-playp|sy-prnew|sy-prlog|sy-pdest|sy-plist|sy-pauth|sy-prdsn|sy-pnwpa|sy-callr|sy-repi2|sy-rtitl|sy-prrec|sy-prtxt|sy-prabt|sy-lpass|sy-nrpag|sy-paart|sy-prcop|sy-batzs|sy-bspld|sy-brep4|sy-batzo|sy-batzd|sy-batzw|sy-batzm|sy-ctabl|sy-dbsys|sy-dcsys|sy-macdb|sy-sysid|sy-opsys|sy-pfkey|sy-saprl|sy-tcode|sy-ucomm|sy-cfwae|sy-chwae|sy-spono|sy-sponr|sy-waers|sy-cdate|sy-datum|sy-slset|sy-subty|sy-subcs|sy-group|sy-ffile|sy-uzeit|sy-dsnam|sy-repid|sy-tabid|sy-tfdsn|sy-uname|sy-lstat|sy-abcde|sy-marky|sy-sfnam|sy-tname|sy-msgli|sy-title|sy-entry|sy-lisel|sy-uline|sy-xcode|sy-cprog|sy-xprog|sy-xform|sy-ldbpg|sy-tvar0|sy-tvar1|sy-tvar2|sy-tvar3|sy-tvar4|sy-tvar5|sy-tvar6|sy-tvar7|sy-tvar8|sy-tvar9|sy-msgid|sy-msgty|sy-msgno|sy-msgv1|sy-msgv2|sy-msgv3|sy-msgv4|sy-oncom|sy-vline|sy-winsl|sy-staco|sy-staro|sy-datar|sy-host|sy-locdb|sy-locop|sy-datlo|sy-timlo|sy-zonlo|syst-index|syst-pagno|syst-tabix|syst-tfill|syst-tlopc|syst-tmaxl|syst-toccu|syst-ttabc|syst-tstis|syst-ttabi|syst-dbcnt|syst-fdpos|syst-colno|syst-linct|syst-linno|syst-linsz|syst-pagct|syst-macol|syst-marow|syst-tleng|syst-sfoff|syst-willi|syst-lilli|syst-subrc|syst-fleng|syst-cucol|syst-curow|syst-lsind|syst-listi|syst-stepl|syst-tpagi|syst-winx1|syst-winy1|syst-winx2|syst-winy2|syst-winco|syst-winro|syst-windi|syst-srows|syst-scols|syst-loopc|syst-folen|syst-fodec|syst-tzone|syst-dayst|syst-ftype|syst-appli|syst-fdayw|syst-ccurs|syst-ccurt|syst-debug|syst-ctype|syst-input|syst-langu|syst-modno|syst-batch|syst-binpt|syst-calld|syst-dynnr|syst-dyngr|syst-newpa|syst-pri40|syst-rstrt|syst-wtitl|syst-cpage|syst-dbnam|syst-mandt|syst-prefx|syst-fmkey|syst-pexpi|syst-prini|syst-primm|syst-prrel|syst-playo|syst-prbig|syst-playp|syst-prnew|syst-prlog|syst-pdest|syst-plist|syst-pauth|syst-prdsn|syst-pnwpa|syst-callr|syst-repi2|syst-rtitl|syst-prrec|syst-prtxt|syst-prabt|syst-lpass|syst-nrpag|syst-paart|syst-prcop|syst-batzs|syst-bspld|syst-brep4|syst-batzo|syst-batzd|syst-batzw|syst-batzm|syst-ctabl|syst-dbsys|syst-dcsys|syst-macdb|syst-sysid|syst-opsys|syst-pfkey|syst-saprl|syst-tcode|syst-ucomm|syst-cfwae|syst-chwae|syst-spono|syst-sponr|syst-waers|syst-cdate|syst-datum|syst-slset|syst-subty|syst-subcs|syst-group|syst-ffile|syst-uzeit|syst-dsnam|syst-repid|syst-tabid|syst-tfdsn|syst-uname|syst-lstat|syst-abcde|syst-marky|syst-sfnam|syst-tname|syst-msgli|syst-title|syst-entry|syst-lisel|syst-uline|syst-xcode|syst-cprog|syst-xprog|syst-xform|syst-ldbpg|syst-tvar0|syst-tvar1|syst-tvar2|syst-tvar3|syst-tvar4|syst-tvar5|syst-tvar6|syst-tvar7|syst-tvar8|syst-tvar9|syst-msgid|syst-msgty|syst-msgno|syst-msgv1|syst-msgv2|syst-msgv3|syst-msgv4|syst-oncom|syst-vline|syst-winsl|syst-staco|syst-staro|syst-datar|syst-host|syst-locdb|syst-locop|syst-datlo|syst-timlo|syst-zonlo)$/',
- 'reserved' => '/^((?i)abs|acos|add|add-corresponding|adjacent|after|aliases|all|analyzer|and|any|append|as|ascending|asin|assign|assigned|assigning|at|atan|authority-check|avg|back|before|begin|binary|bit|bit-and|bit-not|bit-or|bit-xor|blank|block|break-point|buffer|by|c|call|case|catch|ceil|centered|chain|change|changing|check|checkbox|class|class-data|class-events|class-methods|class-pool|clear|client|close|cnt|code|collect|color|comment|commit|communication|compute|concatenate|condense|constants|context|contexts|continue|control|controls|convert|copy|corresponding|cos|cosh|count|country|create|currency|cursor|customer-function|data|database|dataset|delete|decimals|default|define|demand|descending|describe|dialog|distinct|div|divide|divide-corresponding|do|duplicates|dynpro|edit|editor-call|else|elseif|end|end-of-definition|end-of-page|end-of-selection|endat|endcase|endcatch|endchain|endclass|enddo|endexec|endform|endfunction|endif|endinterface|endloop|endmethod|endmodule|endon|endprovide|endselect|endwhile|entries|events|exec|exit|exit-command|exp|exponent|export|exporting|exceptions|extended|extract|fetch|field|field-groups|field-symbols|fields|floor|for|form|format|frac|frame|free|from|function|function-pool|generate|get|group|hashed|header|help-id|help-request|hide|hotspot|icon|id|if|import|importing|include|index|infotypes|initialization|inner|input|insert|intensified|interface|interface-pool|interfaces|into|inverse|join|key|language|last|leave|left|left-justified|like|line|line-count|line-selection|line-size|lines|list-processing|load|load-of-program|local|locale|log|log10|loop|m|margin|mask|matchcode|max|memory|message|message-id|messages|method|methods|min|mod|mode|modif|modify|module|move|move-corresponding|multiply|multiply-corresponding|new|new-line|new-page|next|no|no-gap|no-gaps|no-heading|no-scrolling|no-sign|no-title|no-zero|nodes|non-unique|o|object|obligatory|occurs|of|off|on|open|or|order|others|outer|output|overlay|pack|page|parameter|parameters|perform|pf-status|position|print|print-control|private|process|program|property|protected|provide|public|put|radiobutton|raise|raising|range|ranges|read|receive|refresh|reject|replace|report|requested|reserve|reset|right-justified|rollback|round|rows|rtti|run|scan|screen|search|separated|scroll|scroll-boundary|select|select-options|selection-screen|selection-table|set|shared|shift|sign|sin|single|sinh|size|skip|sort|sorted|split|sql|sqrt|stamp|standard|start-of-selection|statics|stop|string|strlen|structure|submit|subtract|subtract-corresponding|sum|supply|suppress|symbol|syntax-check|syntax-trace|system-call|system-exceptions|table|table_line|tables|tan|tanh|text|textpool|time|times|title|titlebar|to|top-of-page|transaction|transfer|translate|transporting|trunc|type|type-pool|type-pools|types|uline|under|unique|unit|unpack|up|update|user-command|using|value|value-request|values|vary|when|where|while|window|with|with-title|work|write|x|xstring|z|zone)$/',
- 'constants' => '/^((?i)initial|null|space|col_background|col_heading|col_normal|col_total|col_key|col_positive|col_negative|col_group)$/',
- ),
- ),
- 3 =>
- array (
- ),
- 4 =>
- array (
- ),
- );
- $this->_parts = array (
- 0 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- ),
- 1 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- ),
- 2 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- ),
- 3 =>
- array (
- ),
- 4 =>
- array (
- ),
- );
- $this->_subst = array (
- -1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- ),
- 0 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- ),
- 1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- ),
- 2 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- ),
- 3 =>
- array (
- ),
- 4 =>
- array (
- ),
- );
- $this->_conditions = array (
- );
- $this->_kwmap = array (
- 'sy' => 'reserved',
- 'reserved' => 'reserved',
- 'constants' => 'reserved',
- );
- $this->_defClass = 'code';
- $this->_checkDefines();
- }
-
-} \ No newline at end of file
diff --git a/library/Text_Highlighter/Text/Highlighter/AVRC.php b/library/Text_Highlighter/Text/Highlighter/AVRC.php
deleted file mode 100644
index de4b82ccd..000000000
--- a/library/Text_Highlighter/Text/Highlighter/AVRC.php
+++ /dev/null
@@ -1,894 +0,0 @@
-
-<?php
-/**
- * Auto-generated class. AVRC syntax highlighting
- *
- *
- * C/C++ highlighter specific to Atmel AVR microcontrollers
- *
- *
- * PHP version 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @link http://pear.php.net/package/Text_Highlighter
- * @category Text
- * @package Text_Highlighter
- * @version generated from: avrc.xml
- * @author Andrey Demenev <demenev@gmail.com>
- *
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter.php';
-
-/**
- * Auto-generated class. AVRC syntax highlighting
- *
- * @author Andrey Demenev <demenev@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: 0.7.0
- * @link http://pear.php.net/package/Text_Highlighter
- */
-class Text_Highlighter_AVRC extends Text_Highlighter
-{
- var $_language = 'avrc';
-
- /**
- * PHP4 Compatible Constructor
- *
- * @param array $options
- * @access public
- */
- function Text_Highlighter_AVRC($options=array())
- {
- $this->__construct($options);
- }
-
-
- /**
- * Constructor
- *
- * @param array $options
- * @access public
- */
- function __construct($options=array())
- {
-
- $this->_options = $options;
- $this->_regs = array (
- -1 => '/((?i)")|((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)[a-z_]\\w*)|((?i)\\b0[xX][\\da-f]+)|((?i)\\b\\d\\d*|\\b0\\b)|((?i)\\b0[0-7]+)|((?i)\\b(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?mi)^[ \\t]*#include)|((?mii)^[ \\t]*#[ \\t]*[a-z]+)|((?i)\\d*\\.?\\d+)|((?i)\\/\\*)|((?i)\\/\\/.+)/',
- 0 => '/((?i)\\\\)/',
- 1 => '/((?i)")|((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)[a-z_]\\w*)|((?i)\\b0[xX][\\da-f]+)|((?i)\\b\\d\\d*|\\b0\\b)|((?i)\\b0[0-7]+)|((?i)\\b(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?mi)^[ \\t]*#include)|((?mii)^[ \\t]*#[ \\t]*[a-z]+)|((?i)\\d*\\.?\\d+)|((?i)\\/\\*)|((?i)\\/\\/.+)/',
- 2 => '/((?i)")|((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)[a-z_]\\w*)|((?i)\\b0[xX][\\da-f]+)|((?i)\\b\\d\\d*|\\b0\\b)|((?i)\\b0[0-7]+)|((?i)\\b(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?mi)^[ \\t]*#include)|((?mii)^[ \\t]*#[ \\t]*[a-z]+)|((?i)\\d*\\.?\\d+)|((?i)\\/\\*)|((?i)\\/\\/.+)/',
- 3 => '/((?i)")|((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)[a-z_]\\w*)|((?i)\\b0[xX][\\da-f]+)|((?i)\\b\\d\\d*|\\b0\\b)|((?i)\\b0[0-7]+)|((?i)\\b(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?mi)^[ \\t]*#include)|((?mii)^[ \\t]*#[ \\t]*[a-z]+)|((?i)\\d*\\.?\\d+)|((?i)\\/\\*)|((?i)\\/\\/.+)/',
- 4 => '//',
- 5 => '/((?i)")|((?i)<)/',
- 6 => '/((?i)")|((?i)\\{)|((?i)\\()|((?i)[a-z_]\\w*)|((?i)\\b0[xX][\\da-f]+)|((?i)\\b\\d\\d*|\\b0\\b)|((?i)\\b0[0-7]+)|((?i)\\b(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?i)\\/\\*)|((?i)\\/\\/.+)/',
- 7 => '/((?i)\\$\\w+\\s*:.+\\$)/',
- 8 => '/((?i)\\$\\w+\\s*:.+\\$)/',
- );
- $this->_counts = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 2,
- 9 => 0,
- 10 => 0,
- 11 => 0,
- 12 => 0,
- 13 => 0,
- ),
- 0 =>
- array (
- 0 => 0,
- ),
- 1 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 2,
- 9 => 0,
- 10 => 0,
- 11 => 0,
- 12 => 0,
- 13 => 0,
- ),
- 2 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 2,
- 9 => 0,
- 10 => 0,
- 11 => 0,
- 12 => 0,
- 13 => 0,
- ),
- 3 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 2,
- 9 => 0,
- 10 => 0,
- 11 => 0,
- 12 => 0,
- 13 => 0,
- ),
- 4 =>
- array (
- ),
- 5 =>
- array (
- 0 => 0,
- 1 => 0,
- ),
- 6 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 2,
- 8 => 0,
- 9 => 0,
- ),
- 7 =>
- array (
- 0 => 0,
- ),
- 8 =>
- array (
- 0 => 0,
- ),
- );
- $this->_delim = array (
- -1 =>
- array (
- 0 => 'quotes',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'brackets',
- 4 => '',
- 5 => '',
- 6 => '',
- 7 => '',
- 8 => '',
- 9 => 'prepro',
- 10 => 'prepro',
- 11 => '',
- 12 => 'mlcomment',
- 13 => 'comment',
- ),
- 0 =>
- array (
- 0 => '',
- ),
- 1 =>
- array (
- 0 => 'quotes',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'brackets',
- 4 => '',
- 5 => '',
- 6 => '',
- 7 => '',
- 8 => '',
- 9 => 'prepro',
- 10 => 'prepro',
- 11 => '',
- 12 => 'mlcomment',
- 13 => 'comment',
- ),
- 2 =>
- array (
- 0 => 'quotes',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'brackets',
- 4 => '',
- 5 => '',
- 6 => '',
- 7 => '',
- 8 => '',
- 9 => 'prepro',
- 10 => 'prepro',
- 11 => '',
- 12 => 'mlcomment',
- 13 => 'comment',
- ),
- 3 =>
- array (
- 0 => 'quotes',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'brackets',
- 4 => '',
- 5 => '',
- 6 => '',
- 7 => '',
- 8 => '',
- 9 => 'prepro',
- 10 => 'prepro',
- 11 => '',
- 12 => 'mlcomment',
- 13 => 'comment',
- ),
- 4 =>
- array (
- ),
- 5 =>
- array (
- 0 => 'quotes',
- 1 => 'quotes',
- ),
- 6 =>
- array (
- 0 => 'quotes',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => '',
- 4 => '',
- 5 => '',
- 6 => '',
- 7 => '',
- 8 => 'mlcomment',
- 9 => 'comment',
- ),
- 7 =>
- array (
- 0 => '',
- ),
- 8 =>
- array (
- 0 => '',
- ),
- );
- $this->_inner = array (
- -1 =>
- array (
- 0 => 'string',
- 1 => 'code',
- 2 => 'code',
- 3 => 'code',
- 4 => 'identifier',
- 5 => 'number',
- 6 => 'number',
- 7 => 'number',
- 8 => 'number',
- 9 => 'prepro',
- 10 => 'code',
- 11 => 'number',
- 12 => 'mlcomment',
- 13 => 'comment',
- ),
- 0 =>
- array (
- 0 => 'special',
- ),
- 1 =>
- array (
- 0 => 'string',
- 1 => 'code',
- 2 => 'code',
- 3 => 'code',
- 4 => 'identifier',
- 5 => 'number',
- 6 => 'number',
- 7 => 'number',
- 8 => 'number',
- 9 => 'prepro',
- 10 => 'code',
- 11 => 'number',
- 12 => 'mlcomment',
- 13 => 'comment',
- ),
- 2 =>
- array (
- 0 => 'string',
- 1 => 'code',
- 2 => 'code',
- 3 => 'code',
- 4 => 'identifier',
- 5 => 'number',
- 6 => 'number',
- 7 => 'number',
- 8 => 'number',
- 9 => 'prepro',
- 10 => 'code',
- 11 => 'number',
- 12 => 'mlcomment',
- 13 => 'comment',
- ),
- 3 =>
- array (
- 0 => 'string',
- 1 => 'code',
- 2 => 'code',
- 3 => 'code',
- 4 => 'identifier',
- 5 => 'number',
- 6 => 'number',
- 7 => 'number',
- 8 => 'number',
- 9 => 'prepro',
- 10 => 'code',
- 11 => 'number',
- 12 => 'mlcomment',
- 13 => 'comment',
- ),
- 4 =>
- array (
- ),
- 5 =>
- array (
- 0 => 'string',
- 1 => 'string',
- ),
- 6 =>
- array (
- 0 => 'string',
- 1 => 'code',
- 2 => 'code',
- 3 => 'identifier',
- 4 => 'number',
- 5 => 'number',
- 6 => 'number',
- 7 => 'number',
- 8 => 'mlcomment',
- 9 => 'comment',
- ),
- 7 =>
- array (
- 0 => 'inlinedoc',
- ),
- 8 =>
- array (
- 0 => 'inlinedoc',
- ),
- );
- $this->_end = array (
- 0 => '/(?i)"/',
- 1 => '/(?i)\\}/',
- 2 => '/(?i)\\)/',
- 3 => '/(?i)\\]/',
- 4 => '/(?i)>/',
- 5 => '/(?mi)(?<!\\\\)$/',
- 6 => '/(?mi)(?<!\\\\)$/',
- 7 => '/(?i)\\*\\//',
- 8 => '/(?mi)$/',
- );
- $this->_states = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 => -1,
- 8 => -1,
- 9 => 5,
- 10 => 6,
- 11 => -1,
- 12 => 7,
- 13 => 8,
- ),
- 0 =>
- array (
- 0 => -1,
- ),
- 1 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 => -1,
- 8 => -1,
- 9 => 5,
- 10 => 6,
- 11 => -1,
- 12 => 7,
- 13 => 8,
- ),
- 2 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 => -1,
- 8 => -1,
- 9 => 5,
- 10 => 6,
- 11 => -1,
- 12 => 7,
- 13 => 8,
- ),
- 3 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 => -1,
- 8 => -1,
- 9 => 5,
- 10 => 6,
- 11 => -1,
- 12 => 7,
- 13 => 8,
- ),
- 4 =>
- array (
- ),
- 5 =>
- array (
- 0 => 0,
- 1 => 4,
- ),
- 6 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => -1,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 => -1,
- 8 => 7,
- 9 => 8,
- ),
- 7 =>
- array (
- 0 => -1,
- ),
- 8 =>
- array (
- 0 => -1,
- ),
- );
- $this->_keywords = array (
- -1 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 =>
- array (
- 'reserved' => '/^(and|and_eq|asm|bitand|bitor|break|case|catch|compl|const_cast|continue|default|delete|do|dynamic_cast|else|for|fortran|friend|goto|if|new|not|not_eq|operator|or|or_eq|private|protected|public|reinterpret_cast|return|sizeof|static_cast|switch|this|throw|try|typeid|using|while|xor|xor_eq|false|true)$/',
- 'registers' => '/^(ACSR|ADCH|ADCL|ADCSRA|ADMUX|ASSR|DDRA|DDRB|DDRC|DDRD|DDRE|DDRF|DDRG|EEARH|EEARL|EECR|EEDR|EICRA|EICRB|EIFR|EIMSK|ETIFR|ETIMSK|GICR|GIFR|ICR1H|ICR1L|ICR3H|ICR3L|MCUCR|MCUCSR|OCDR|OCR0|OCR1AH|OCR1AL|OCR1BH|OCR1BL|OCR1CH|OCR1CL|OCR2|OCR3AH|OCR3AL|OCR3BH|OCR3BL|OCR3CH|OCR3CL|OSCCAL|PINA|PINB|PINC|PIND|PINE|PINF|PING|PORTA|PORTB|PORTC|PORTD|PORTE|PORTF|PORTG|RAMPZ|SFIOR|SPCR|SPDR|SPH|SPL|SPMCR|SPMCSR|SPSR|SREG|TCCR0|TCCR1A|TCCR1B|TCCR1C|TCCR2|TCCR3A|TCCR3B|TCCR3C|TCNT0|TCNT1H|TCNT1L|TCNT2|TCNT3H|TCNT3L|TIFR|TIMSK|TWAR|TWBR|TWCR|TWDR|TWSR|UBRR0H|UBRR0L|UBRR1H|UBRR1L|UBRRH|UBRRL|UCSR0A|UCSR0B|UCSR0C|UCSR1A|UCSR1B|UCSR1C|UCSRA|UCSRB|UCSRC|UDR|UDR0|UDR1|WDTCR|XDIV|XMCRA|XMCRB)$/',
- 'types' => '/^(auto|bool|char|class|const|double|enum|explicit|export|extern|float|inline|int|long|mutable|namespace|register|short|signed|static|struct|template|typedef|typename|union|unsigned|virtual|void|volatile|wchar_t)$/',
- 'Common Macros' => '/^(NULL|TRUE|FALSE|MAX|MIN|__LINE__|__DATA__|__FILE__|__TIME__|__STDC__)$/',
- ),
- 5 =>
- array (
- ),
- 6 =>
- array (
- ),
- 7 =>
- array (
- ),
- 8 =>
- array (
- ),
- 9 => -1,
- 10 => -1,
- 11 =>
- array (
- ),
- 12 => -1,
- 13 => -1,
- ),
- 0 =>
- array (
- 0 =>
- array (
- ),
- ),
- 1 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 =>
- array (
- 'reserved' => '/^(and|and_eq|asm|bitand|bitor|break|case|catch|compl|const_cast|continue|default|delete|do|dynamic_cast|else|for|fortran|friend|goto|if|new|not|not_eq|operator|or|or_eq|private|protected|public|reinterpret_cast|return|sizeof|static_cast|switch|this|throw|try|typeid|using|while|xor|xor_eq|false|true)$/',
- 'registers' => '/^(ACSR|ADCH|ADCL|ADCSRA|ADMUX|ASSR|DDRA|DDRB|DDRC|DDRD|DDRE|DDRF|DDRG|EEARH|EEARL|EECR|EEDR|EICRA|EICRB|EIFR|EIMSK|ETIFR|ETIMSK|GICR|GIFR|ICR1H|ICR1L|ICR3H|ICR3L|MCUCR|MCUCSR|OCDR|OCR0|OCR1AH|OCR1AL|OCR1BH|OCR1BL|OCR1CH|OCR1CL|OCR2|OCR3AH|OCR3AL|OCR3BH|OCR3BL|OCR3CH|OCR3CL|OSCCAL|PINA|PINB|PINC|PIND|PINE|PINF|PING|PORTA|PORTB|PORTC|PORTD|PORTE|PORTF|PORTG|RAMPZ|SFIOR|SPCR|SPDR|SPH|SPL|SPMCR|SPMCSR|SPSR|SREG|TCCR0|TCCR1A|TCCR1B|TCCR1C|TCCR2|TCCR3A|TCCR3B|TCCR3C|TCNT0|TCNT1H|TCNT1L|TCNT2|TCNT3H|TCNT3L|TIFR|TIMSK|TWAR|TWBR|TWCR|TWDR|TWSR|UBRR0H|UBRR0L|UBRR1H|UBRR1L|UBRRH|UBRRL|UCSR0A|UCSR0B|UCSR0C|UCSR1A|UCSR1B|UCSR1C|UCSRA|UCSRB|UCSRC|UDR|UDR0|UDR1|WDTCR|XDIV|XMCRA|XMCRB)$/',
- 'types' => '/^(auto|bool|char|class|const|double|enum|explicit|export|extern|float|inline|int|long|mutable|namespace|register|short|signed|static|struct|template|typedef|typename|union|unsigned|virtual|void|volatile|wchar_t)$/',
- 'Common Macros' => '/^(NULL|TRUE|FALSE|MAX|MIN|__LINE__|__DATA__|__FILE__|__TIME__|__STDC__)$/',
- ),
- 5 =>
- array (
- ),
- 6 =>
- array (
- ),
- 7 =>
- array (
- ),
- 8 =>
- array (
- ),
- 9 => -1,
- 10 => -1,
- 11 =>
- array (
- ),
- 12 => -1,
- 13 => -1,
- ),
- 2 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 =>
- array (
- 'reserved' => '/^(and|and_eq|asm|bitand|bitor|break|case|catch|compl|const_cast|continue|default|delete|do|dynamic_cast|else|for|fortran|friend|goto|if|new|not|not_eq|operator|or|or_eq|private|protected|public|reinterpret_cast|return|sizeof|static_cast|switch|this|throw|try|typeid|using|while|xor|xor_eq|false|true)$/',
- 'registers' => '/^(ACSR|ADCH|ADCL|ADCSRA|ADMUX|ASSR|DDRA|DDRB|DDRC|DDRD|DDRE|DDRF|DDRG|EEARH|EEARL|EECR|EEDR|EICRA|EICRB|EIFR|EIMSK|ETIFR|ETIMSK|GICR|GIFR|ICR1H|ICR1L|ICR3H|ICR3L|MCUCR|MCUCSR|OCDR|OCR0|OCR1AH|OCR1AL|OCR1BH|OCR1BL|OCR1CH|OCR1CL|OCR2|OCR3AH|OCR3AL|OCR3BH|OCR3BL|OCR3CH|OCR3CL|OSCCAL|PINA|PINB|PINC|PIND|PINE|PINF|PING|PORTA|PORTB|PORTC|PORTD|PORTE|PORTF|PORTG|RAMPZ|SFIOR|SPCR|SPDR|SPH|SPL|SPMCR|SPMCSR|SPSR|SREG|TCCR0|TCCR1A|TCCR1B|TCCR1C|TCCR2|TCCR3A|TCCR3B|TCCR3C|TCNT0|TCNT1H|TCNT1L|TCNT2|TCNT3H|TCNT3L|TIFR|TIMSK|TWAR|TWBR|TWCR|TWDR|TWSR|UBRR0H|UBRR0L|UBRR1H|UBRR1L|UBRRH|UBRRL|UCSR0A|UCSR0B|UCSR0C|UCSR1A|UCSR1B|UCSR1C|UCSRA|UCSRB|UCSRC|UDR|UDR0|UDR1|WDTCR|XDIV|XMCRA|XMCRB)$/',
- 'types' => '/^(auto|bool|char|class|const|double|enum|explicit|export|extern|float|inline|int|long|mutable|namespace|register|short|signed|static|struct|template|typedef|typename|union|unsigned|virtual|void|volatile|wchar_t)$/',
- 'Common Macros' => '/^(NULL|TRUE|FALSE|MAX|MIN|__LINE__|__DATA__|__FILE__|__TIME__|__STDC__)$/',
- ),
- 5 =>
- array (
- ),
- 6 =>
- array (
- ),
- 7 =>
- array (
- ),
- 8 =>
- array (
- ),
- 9 => -1,
- 10 => -1,
- 11 =>
- array (
- ),
- 12 => -1,
- 13 => -1,
- ),
- 3 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 =>
- array (
- 'reserved' => '/^(and|and_eq|asm|bitand|bitor|break|case|catch|compl|const_cast|continue|default|delete|do|dynamic_cast|else|for|fortran|friend|goto|if|new|not|not_eq|operator|or|or_eq|private|protected|public|reinterpret_cast|return|sizeof|static_cast|switch|this|throw|try|typeid|using|while|xor|xor_eq|false|true)$/',
- 'registers' => '/^(ACSR|ADCH|ADCL|ADCSRA|ADMUX|ASSR|DDRA|DDRB|DDRC|DDRD|DDRE|DDRF|DDRG|EEARH|EEARL|EECR|EEDR|EICRA|EICRB|EIFR|EIMSK|ETIFR|ETIMSK|GICR|GIFR|ICR1H|ICR1L|ICR3H|ICR3L|MCUCR|MCUCSR|OCDR|OCR0|OCR1AH|OCR1AL|OCR1BH|OCR1BL|OCR1CH|OCR1CL|OCR2|OCR3AH|OCR3AL|OCR3BH|OCR3BL|OCR3CH|OCR3CL|OSCCAL|PINA|PINB|PINC|PIND|PINE|PINF|PING|PORTA|PORTB|PORTC|PORTD|PORTE|PORTF|PORTG|RAMPZ|SFIOR|SPCR|SPDR|SPH|SPL|SPMCR|SPMCSR|SPSR|SREG|TCCR0|TCCR1A|TCCR1B|TCCR1C|TCCR2|TCCR3A|TCCR3B|TCCR3C|TCNT0|TCNT1H|TCNT1L|TCNT2|TCNT3H|TCNT3L|TIFR|TIMSK|TWAR|TWBR|TWCR|TWDR|TWSR|UBRR0H|UBRR0L|UBRR1H|UBRR1L|UBRRH|UBRRL|UCSR0A|UCSR0B|UCSR0C|UCSR1A|UCSR1B|UCSR1C|UCSRA|UCSRB|UCSRC|UDR|UDR0|UDR1|WDTCR|XDIV|XMCRA|XMCRB)$/',
- 'types' => '/^(auto|bool|char|class|const|double|enum|explicit|export|extern|float|inline|int|long|mutable|namespace|register|short|signed|static|struct|template|typedef|typename|union|unsigned|virtual|void|volatile|wchar_t)$/',
- 'Common Macros' => '/^(NULL|TRUE|FALSE|MAX|MIN|__LINE__|__DATA__|__FILE__|__TIME__|__STDC__)$/',
- ),
- 5 =>
- array (
- ),
- 6 =>
- array (
- ),
- 7 =>
- array (
- ),
- 8 =>
- array (
- ),
- 9 => -1,
- 10 => -1,
- 11 =>
- array (
- ),
- 12 => -1,
- 13 => -1,
- ),
- 4 =>
- array (
- ),
- 5 =>
- array (
- 0 => -1,
- 1 => -1,
- ),
- 6 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 =>
- array (
- 'reserved' => '/^(and|and_eq|asm|bitand|bitor|break|case|catch|compl|const_cast|continue|default|delete|do|dynamic_cast|else|for|fortran|friend|goto|if|new|not|not_eq|operator|or|or_eq|private|protected|public|reinterpret_cast|return|sizeof|static_cast|switch|this|throw|try|typeid|using|while|xor|xor_eq|false|true)$/',
- 'registers' => '/^(ACSR|ADCH|ADCL|ADCSRA|ADMUX|ASSR|DDRA|DDRB|DDRC|DDRD|DDRE|DDRF|DDRG|EEARH|EEARL|EECR|EEDR|EICRA|EICRB|EIFR|EIMSK|ETIFR|ETIMSK|GICR|GIFR|ICR1H|ICR1L|ICR3H|ICR3L|MCUCR|MCUCSR|OCDR|OCR0|OCR1AH|OCR1AL|OCR1BH|OCR1BL|OCR1CH|OCR1CL|OCR2|OCR3AH|OCR3AL|OCR3BH|OCR3BL|OCR3CH|OCR3CL|OSCCAL|PINA|PINB|PINC|PIND|PINE|PINF|PING|PORTA|PORTB|PORTC|PORTD|PORTE|PORTF|PORTG|RAMPZ|SFIOR|SPCR|SPDR|SPH|SPL|SPMCR|SPMCSR|SPSR|SREG|TCCR0|TCCR1A|TCCR1B|TCCR1C|TCCR2|TCCR3A|TCCR3B|TCCR3C|TCNT0|TCNT1H|TCNT1L|TCNT2|TCNT3H|TCNT3L|TIFR|TIMSK|TWAR|TWBR|TWCR|TWDR|TWSR|UBRR0H|UBRR0L|UBRR1H|UBRR1L|UBRRH|UBRRL|UCSR0A|UCSR0B|UCSR0C|UCSR1A|UCSR1B|UCSR1C|UCSRA|UCSRB|UCSRC|UDR|UDR0|UDR1|WDTCR|XDIV|XMCRA|XMCRB)$/',
- 'types' => '/^(auto|bool|char|class|const|double|enum|explicit|export|extern|float|inline|int|long|mutable|namespace|register|short|signed|static|struct|template|typedef|typename|union|unsigned|virtual|void|volatile|wchar_t)$/',
- 'Common Macros' => '/^(NULL|TRUE|FALSE|MAX|MIN|__LINE__|__DATA__|__FILE__|__TIME__|__STDC__)$/',
- ),
- 4 =>
- array (
- ),
- 5 =>
- array (
- ),
- 6 =>
- array (
- ),
- 7 =>
- array (
- ),
- 8 => -1,
- 9 => -1,
- ),
- 7 =>
- array (
- 0 =>
- array (
- ),
- ),
- 8 =>
- array (
- 0 =>
- array (
- ),
- ),
- );
- $this->_parts = array (
- 0 =>
- array (
- 0 => NULL,
- ),
- 1 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- 10 => NULL,
- 11 => NULL,
- 12 => NULL,
- 13 => NULL,
- ),
- 2 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- 10 => NULL,
- 11 => NULL,
- 12 => NULL,
- 13 => NULL,
- ),
- 3 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- 10 => NULL,
- 11 => NULL,
- 12 => NULL,
- 13 => NULL,
- ),
- 4 =>
- array (
- ),
- 5 =>
- array (
- 0 => NULL,
- 1 => NULL,
- ),
- 6 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- ),
- 7 =>
- array (
- 0 => NULL,
- ),
- 8 =>
- array (
- 0 => NULL,
- ),
- );
- $this->_subst = array (
- -1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- ),
- 0 =>
- array (
- 0 => false,
- ),
- 1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- ),
- 2 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- ),
- 3 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- ),
- 4 =>
- array (
- ),
- 5 =>
- array (
- 0 => false,
- 1 => false,
- ),
- 6 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- ),
- 7 =>
- array (
- 0 => false,
- ),
- 8 =>
- array (
- 0 => false,
- ),
- );
- $this->_conditions = array (
- );
- $this->_kwmap = array (
- 'reserved' => 'reserved',
- 'registers' => 'reserved',
- 'types' => 'types',
- 'Common Macros' => 'prepro',
- );
- $this->_defClass = 'code';
- $this->_checkDefines();
- }
-
-} \ No newline at end of file
diff --git a/library/Text_Highlighter/Text/Highlighter/CPP.php b/library/Text_Highlighter/Text/Highlighter/CPP.php
deleted file mode 100644
index eaa47c575..000000000
--- a/library/Text_Highlighter/Text/Highlighter/CPP.php
+++ /dev/null
@@ -1,891 +0,0 @@
-
-<?php
-/**
- * Auto-generated class. CPP syntax highlighting
- *
- *
- * Thanks to Aaron Kalin for initial
- * implementation of this highlighter
- *
- *
- * PHP version 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @link http://pear.php.net/package/Text_Highlighter
- * @category Text
- * @package Text_Highlighter
- * @version generated from: cpp.xml
- * @author Aaron Kalin
- * @author Andrey Demenev <demenev@gmail.com>
- *
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter.php';
-
-/**
- * Auto-generated class. CPP syntax highlighting
- *
- * @author Aaron Kalin
- * @author Andrey Demenev <demenev@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: 0.7.0
- * @link http://pear.php.net/package/Text_Highlighter
- */
-class Text_Highlighter_CPP extends Text_Highlighter
-{
- var $_language = 'cpp';
-
- /**
- * PHP4 Compatible Constructor
- *
- * @param array $options
- * @access public
- */
- function Text_Highlighter_CPP($options=array())
- {
- $this->__construct($options);
- }
-
-
- /**
- * Constructor
- *
- * @param array $options
- * @access public
- */
- function __construct($options=array())
- {
-
- $this->_options = $options;
- $this->_regs = array (
- -1 => '/((?i)")|((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)[a-z_]\\w*)|((?i)\\b0[xX][\\da-f]+)|((?i)\\b\\d\\d*|\\b0\\b)|((?i)\\b0[0-7]+)|((?i)\\b(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?mi)^[ \\t]*#include)|((?mii)^[ \\t]*#[ \\t]*[a-z]+)|((?i)\\d*\\.?\\d+)|((?i)\\/\\*)|((?i)\\/\\/.+)/',
- 0 => '/((?i)\\\\)/',
- 1 => '/((?i)")|((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)[a-z_]\\w*)|((?i)\\b0[xX][\\da-f]+)|((?i)\\b\\d\\d*|\\b0\\b)|((?i)\\b0[0-7]+)|((?i)\\b(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?mi)^[ \\t]*#include)|((?mii)^[ \\t]*#[ \\t]*[a-z]+)|((?i)\\d*\\.?\\d+)|((?i)\\/\\*)|((?i)\\/\\/.+)/',
- 2 => '/((?i)")|((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)[a-z_]\\w*)|((?i)\\b0[xX][\\da-f]+)|((?i)\\b\\d\\d*|\\b0\\b)|((?i)\\b0[0-7]+)|((?i)\\b(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?mi)^[ \\t]*#include)|((?mii)^[ \\t]*#[ \\t]*[a-z]+)|((?i)\\d*\\.?\\d+)|((?i)\\/\\*)|((?i)\\/\\/.+)/',
- 3 => '/((?i)")|((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)[a-z_]\\w*)|((?i)\\b0[xX][\\da-f]+)|((?i)\\b\\d\\d*|\\b0\\b)|((?i)\\b0[0-7]+)|((?i)\\b(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?mi)^[ \\t]*#include)|((?mii)^[ \\t]*#[ \\t]*[a-z]+)|((?i)\\d*\\.?\\d+)|((?i)\\/\\*)|((?i)\\/\\/.+)/',
- 4 => '//',
- 5 => '/((?i)")|((?i)<)/',
- 6 => '/((?i)")|((?i)\\{)|((?i)\\()|((?i)[a-z_]\\w*)|((?i)\\b0[xX][\\da-f]+)|((?i)\\b\\d\\d*|\\b0\\b)|((?i)\\b0[0-7]+)|((?i)\\b(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?i)\\/\\*)|((?i)\\/\\/.+)/',
- 7 => '/((?i)\\$\\w+\\s*:.+\\$)/',
- 8 => '/((?i)\\$\\w+\\s*:.+\\$)/',
- );
- $this->_counts = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 2,
- 9 => 0,
- 10 => 0,
- 11 => 0,
- 12 => 0,
- 13 => 0,
- ),
- 0 =>
- array (
- 0 => 0,
- ),
- 1 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 2,
- 9 => 0,
- 10 => 0,
- 11 => 0,
- 12 => 0,
- 13 => 0,
- ),
- 2 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 2,
- 9 => 0,
- 10 => 0,
- 11 => 0,
- 12 => 0,
- 13 => 0,
- ),
- 3 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 2,
- 9 => 0,
- 10 => 0,
- 11 => 0,
- 12 => 0,
- 13 => 0,
- ),
- 4 =>
- array (
- ),
- 5 =>
- array (
- 0 => 0,
- 1 => 0,
- ),
- 6 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 2,
- 8 => 0,
- 9 => 0,
- ),
- 7 =>
- array (
- 0 => 0,
- ),
- 8 =>
- array (
- 0 => 0,
- ),
- );
- $this->_delim = array (
- -1 =>
- array (
- 0 => 'quotes',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'brackets',
- 4 => '',
- 5 => '',
- 6 => '',
- 7 => '',
- 8 => '',
- 9 => 'prepro',
- 10 => 'prepro',
- 11 => '',
- 12 => 'mlcomment',
- 13 => 'comment',
- ),
- 0 =>
- array (
- 0 => '',
- ),
- 1 =>
- array (
- 0 => 'quotes',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'brackets',
- 4 => '',
- 5 => '',
- 6 => '',
- 7 => '',
- 8 => '',
- 9 => 'prepro',
- 10 => 'prepro',
- 11 => '',
- 12 => 'mlcomment',
- 13 => 'comment',
- ),
- 2 =>
- array (
- 0 => 'quotes',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'brackets',
- 4 => '',
- 5 => '',
- 6 => '',
- 7 => '',
- 8 => '',
- 9 => 'prepro',
- 10 => 'prepro',
- 11 => '',
- 12 => 'mlcomment',
- 13 => 'comment',
- ),
- 3 =>
- array (
- 0 => 'quotes',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'brackets',
- 4 => '',
- 5 => '',
- 6 => '',
- 7 => '',
- 8 => '',
- 9 => 'prepro',
- 10 => 'prepro',
- 11 => '',
- 12 => 'mlcomment',
- 13 => 'comment',
- ),
- 4 =>
- array (
- ),
- 5 =>
- array (
- 0 => 'quotes',
- 1 => 'quotes',
- ),
- 6 =>
- array (
- 0 => 'quotes',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => '',
- 4 => '',
- 5 => '',
- 6 => '',
- 7 => '',
- 8 => 'mlcomment',
- 9 => 'comment',
- ),
- 7 =>
- array (
- 0 => '',
- ),
- 8 =>
- array (
- 0 => '',
- ),
- );
- $this->_inner = array (
- -1 =>
- array (
- 0 => 'string',
- 1 => 'code',
- 2 => 'code',
- 3 => 'code',
- 4 => 'identifier',
- 5 => 'number',
- 6 => 'number',
- 7 => 'number',
- 8 => 'number',
- 9 => 'prepro',
- 10 => 'code',
- 11 => 'number',
- 12 => 'mlcomment',
- 13 => 'comment',
- ),
- 0 =>
- array (
- 0 => 'special',
- ),
- 1 =>
- array (
- 0 => 'string',
- 1 => 'code',
- 2 => 'code',
- 3 => 'code',
- 4 => 'identifier',
- 5 => 'number',
- 6 => 'number',
- 7 => 'number',
- 8 => 'number',
- 9 => 'prepro',
- 10 => 'code',
- 11 => 'number',
- 12 => 'mlcomment',
- 13 => 'comment',
- ),
- 2 =>
- array (
- 0 => 'string',
- 1 => 'code',
- 2 => 'code',
- 3 => 'code',
- 4 => 'identifier',
- 5 => 'number',
- 6 => 'number',
- 7 => 'number',
- 8 => 'number',
- 9 => 'prepro',
- 10 => 'code',
- 11 => 'number',
- 12 => 'mlcomment',
- 13 => 'comment',
- ),
- 3 =>
- array (
- 0 => 'string',
- 1 => 'code',
- 2 => 'code',
- 3 => 'code',
- 4 => 'identifier',
- 5 => 'number',
- 6 => 'number',
- 7 => 'number',
- 8 => 'number',
- 9 => 'prepro',
- 10 => 'code',
- 11 => 'number',
- 12 => 'mlcomment',
- 13 => 'comment',
- ),
- 4 =>
- array (
- ),
- 5 =>
- array (
- 0 => 'string',
- 1 => 'string',
- ),
- 6 =>
- array (
- 0 => 'string',
- 1 => 'code',
- 2 => 'code',
- 3 => 'identifier',
- 4 => 'number',
- 5 => 'number',
- 6 => 'number',
- 7 => 'number',
- 8 => 'mlcomment',
- 9 => 'comment',
- ),
- 7 =>
- array (
- 0 => 'inlinedoc',
- ),
- 8 =>
- array (
- 0 => 'inlinedoc',
- ),
- );
- $this->_end = array (
- 0 => '/(?i)"/',
- 1 => '/(?i)\\}/',
- 2 => '/(?i)\\)/',
- 3 => '/(?i)\\]/',
- 4 => '/(?i)>/',
- 5 => '/(?mi)(?<!\\\\)$/',
- 6 => '/(?mi)(?<!\\\\)$/',
- 7 => '/(?i)\\*\\//',
- 8 => '/(?mi)$/',
- );
- $this->_states = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 => -1,
- 8 => -1,
- 9 => 5,
- 10 => 6,
- 11 => -1,
- 12 => 7,
- 13 => 8,
- ),
- 0 =>
- array (
- 0 => -1,
- ),
- 1 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 => -1,
- 8 => -1,
- 9 => 5,
- 10 => 6,
- 11 => -1,
- 12 => 7,
- 13 => 8,
- ),
- 2 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 => -1,
- 8 => -1,
- 9 => 5,
- 10 => 6,
- 11 => -1,
- 12 => 7,
- 13 => 8,
- ),
- 3 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 => -1,
- 8 => -1,
- 9 => 5,
- 10 => 6,
- 11 => -1,
- 12 => 7,
- 13 => 8,
- ),
- 4 =>
- array (
- ),
- 5 =>
- array (
- 0 => 0,
- 1 => 4,
- ),
- 6 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => -1,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 => -1,
- 8 => 7,
- 9 => 8,
- ),
- 7 =>
- array (
- 0 => -1,
- ),
- 8 =>
- array (
- 0 => -1,
- ),
- );
- $this->_keywords = array (
- -1 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 =>
- array (
- 'reserved' => '/^(and|and_eq|asm|bitand|bitor|break|case|catch|compl|const_cast|continue|default|delete|do|dynamic_cast|else|for|fortran|friend|goto|if|new|not|not_eq|operator|or|or_eq|private|protected|public|reinterpret_cast|return|sizeof|static_cast|switch|this|throw|try|typeid|using|while|xor|xor_eq|false|true)$/',
- 'types' => '/^(auto|bool|char|class|const|double|enum|explicit|export|extern|float|inline|int|long|mutable|namespace|register|short|signed|static|struct|template|typedef|typename|union|unsigned|virtual|void|volatile|wchar_t)$/',
- 'Common Macros' => '/^(NULL|TRUE|FALSE|MAX|MIN|__LINE__|__DATA__|__FILE__|__TIME__|__STDC__)$/',
- ),
- 5 =>
- array (
- ),
- 6 =>
- array (
- ),
- 7 =>
- array (
- ),
- 8 =>
- array (
- ),
- 9 => -1,
- 10 => -1,
- 11 =>
- array (
- ),
- 12 => -1,
- 13 => -1,
- ),
- 0 =>
- array (
- 0 =>
- array (
- ),
- ),
- 1 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 =>
- array (
- 'reserved' => '/^(and|and_eq|asm|bitand|bitor|break|case|catch|compl|const_cast|continue|default|delete|do|dynamic_cast|else|for|fortran|friend|goto|if|new|not|not_eq|operator|or|or_eq|private|protected|public|reinterpret_cast|return|sizeof|static_cast|switch|this|throw|try|typeid|using|while|xor|xor_eq|false|true)$/',
- 'types' => '/^(auto|bool|char|class|const|double|enum|explicit|export|extern|float|inline|int|long|mutable|namespace|register|short|signed|static|struct|template|typedef|typename|union|unsigned|virtual|void|volatile|wchar_t)$/',
- 'Common Macros' => '/^(NULL|TRUE|FALSE|MAX|MIN|__LINE__|__DATA__|__FILE__|__TIME__|__STDC__)$/',
- ),
- 5 =>
- array (
- ),
- 6 =>
- array (
- ),
- 7 =>
- array (
- ),
- 8 =>
- array (
- ),
- 9 => -1,
- 10 => -1,
- 11 =>
- array (
- ),
- 12 => -1,
- 13 => -1,
- ),
- 2 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 =>
- array (
- 'reserved' => '/^(and|and_eq|asm|bitand|bitor|break|case|catch|compl|const_cast|continue|default|delete|do|dynamic_cast|else|for|fortran|friend|goto|if|new|not|not_eq|operator|or|or_eq|private|protected|public|reinterpret_cast|return|sizeof|static_cast|switch|this|throw|try|typeid|using|while|xor|xor_eq|false|true)$/',
- 'types' => '/^(auto|bool|char|class|const|double|enum|explicit|export|extern|float|inline|int|long|mutable|namespace|register|short|signed|static|struct|template|typedef|typename|union|unsigned|virtual|void|volatile|wchar_t)$/',
- 'Common Macros' => '/^(NULL|TRUE|FALSE|MAX|MIN|__LINE__|__DATA__|__FILE__|__TIME__|__STDC__)$/',
- ),
- 5 =>
- array (
- ),
- 6 =>
- array (
- ),
- 7 =>
- array (
- ),
- 8 =>
- array (
- ),
- 9 => -1,
- 10 => -1,
- 11 =>
- array (
- ),
- 12 => -1,
- 13 => -1,
- ),
- 3 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 =>
- array (
- 'reserved' => '/^(and|and_eq|asm|bitand|bitor|break|case|catch|compl|const_cast|continue|default|delete|do|dynamic_cast|else|for|fortran|friend|goto|if|new|not|not_eq|operator|or|or_eq|private|protected|public|reinterpret_cast|return|sizeof|static_cast|switch|this|throw|try|typeid|using|while|xor|xor_eq|false|true)$/',
- 'types' => '/^(auto|bool|char|class|const|double|enum|explicit|export|extern|float|inline|int|long|mutable|namespace|register|short|signed|static|struct|template|typedef|typename|union|unsigned|virtual|void|volatile|wchar_t)$/',
- 'Common Macros' => '/^(NULL|TRUE|FALSE|MAX|MIN|__LINE__|__DATA__|__FILE__|__TIME__|__STDC__)$/',
- ),
- 5 =>
- array (
- ),
- 6 =>
- array (
- ),
- 7 =>
- array (
- ),
- 8 =>
- array (
- ),
- 9 => -1,
- 10 => -1,
- 11 =>
- array (
- ),
- 12 => -1,
- 13 => -1,
- ),
- 4 =>
- array (
- ),
- 5 =>
- array (
- 0 => -1,
- 1 => -1,
- ),
- 6 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 =>
- array (
- 'reserved' => '/^(and|and_eq|asm|bitand|bitor|break|case|catch|compl|const_cast|continue|default|delete|do|dynamic_cast|else|for|fortran|friend|goto|if|new|not|not_eq|operator|or|or_eq|private|protected|public|reinterpret_cast|return|sizeof|static_cast|switch|this|throw|try|typeid|using|while|xor|xor_eq|false|true)$/',
- 'types' => '/^(auto|bool|char|class|const|double|enum|explicit|export|extern|float|inline|int|long|mutable|namespace|register|short|signed|static|struct|template|typedef|typename|union|unsigned|virtual|void|volatile|wchar_t)$/',
- 'Common Macros' => '/^(NULL|TRUE|FALSE|MAX|MIN|__LINE__|__DATA__|__FILE__|__TIME__|__STDC__)$/',
- ),
- 4 =>
- array (
- ),
- 5 =>
- array (
- ),
- 6 =>
- array (
- ),
- 7 =>
- array (
- ),
- 8 => -1,
- 9 => -1,
- ),
- 7 =>
- array (
- 0 =>
- array (
- ),
- ),
- 8 =>
- array (
- 0 =>
- array (
- ),
- ),
- );
- $this->_parts = array (
- 0 =>
- array (
- 0 => NULL,
- ),
- 1 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- 10 => NULL,
- 11 => NULL,
- 12 => NULL,
- 13 => NULL,
- ),
- 2 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- 10 => NULL,
- 11 => NULL,
- 12 => NULL,
- 13 => NULL,
- ),
- 3 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- 10 => NULL,
- 11 => NULL,
- 12 => NULL,
- 13 => NULL,
- ),
- 4 =>
- array (
- ),
- 5 =>
- array (
- 0 => NULL,
- 1 => NULL,
- ),
- 6 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- ),
- 7 =>
- array (
- 0 => NULL,
- ),
- 8 =>
- array (
- 0 => NULL,
- ),
- );
- $this->_subst = array (
- -1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- ),
- 0 =>
- array (
- 0 => false,
- ),
- 1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- ),
- 2 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- ),
- 3 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- ),
- 4 =>
- array (
- ),
- 5 =>
- array (
- 0 => false,
- 1 => false,
- ),
- 6 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- ),
- 7 =>
- array (
- 0 => false,
- ),
- 8 =>
- array (
- 0 => false,
- ),
- );
- $this->_conditions = array (
- );
- $this->_kwmap = array (
- 'reserved' => 'reserved',
- 'types' => 'types',
- 'Common Macros' => 'prepro',
- );
- $this->_defClass = 'code';
- $this->_checkDefines();
- }
-
-} \ No newline at end of file
diff --git a/library/Text_Highlighter/Text/Highlighter/CSS.php b/library/Text_Highlighter/Text/Highlighter/CSS.php
deleted file mode 100644
index 51757c88e..000000000
--- a/library/Text_Highlighter/Text/Highlighter/CSS.php
+++ /dev/null
@@ -1,437 +0,0 @@
-<?php
-/**
- * Auto-generated class. CSS syntax highlighting
- *
- * PHP version 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @link http://pear.php.net/package/Text_Highlighter
- * @category Text
- * @package Text_Highlighter
- * @version generated from: css.xml
- * @author Andrey Demenev <demenev@gmail.com>
- *
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter.php';
-
-/**
- * Auto-generated class. CSS syntax highlighting
- *
- * @author Andrey Demenev <demenev@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: 0.7.0
- * @link http://pear.php.net/package/Text_Highlighter
- */
-class Text_Highlighter_CSS extends Text_Highlighter
-{
- var $_language = 'css';
-
- /**
- * PHP4 Compatible Constructor
- *
- * @param array $options
- * @access public
- */
- function Text_Highlighter_CSS($options=array())
- {
- $this->__construct($options);
- }
-
-
- /**
- * Constructor
- *
- * @param array $options
- * @access public
- */
- function __construct($options=array())
- {
-
- $this->_options = $options;
- $this->_regs = array (
- -1 => '/((?i)\\/\\*)|((?i)(@[a-z\\d]+))|((?i)(((\\.|#)?[a-z]+[a-z\\d\\-]*(?![a-z\\d\\-]))|(\\*))(?!\\s*:\\s*[\\s\\{]))|((?i):[a-z][a-z\\d\\-]*)|((?i)\\[)|((?i)\\{)/',
- 0 => '//',
- 1 => '/((?i)\\d*\\.?\\d+(\\%|em|ex|pc|pt|px|in|mm|cm))|((?i)\\d*\\.?\\d+)|((?i)[a-z][a-z\\d\\-]*)|((?i)#([\\da-f]{6}|[\\da-f]{3})\\b)/',
- 2 => '/((?i)\')|((?i)")|((?i)[\\w\\-\\:]+)/',
- 3 => '/((?i)\\/\\*)|((?i)[a-z][a-z\\d\\-]*\\s*:)|((?i)(((\\.|#)?[a-z]+[a-z\\d\\-]*(?![a-z\\d\\-]))|(\\*))(?!\\s*:\\s*[\\s\\{]))|((?i)\\{)/',
- 4 => '/((?i)\\\\[\\\\(\\\\)\\\\])/',
- 5 => '/((?i)\\\\\\\\|\\\\"|\\\\\'|\\\\`)/',
- 6 => '/((?i)\\\\\\\\|\\\\"|\\\\\'|\\\\`|\\\\t|\\\\n|\\\\r)/',
- );
- $this->_counts = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 4,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => 1,
- 1 => 0,
- 2 => 0,
- 3 => 1,
- ),
- 2 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- ),
- 3 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 4,
- 3 => 0,
- ),
- 4 =>
- array (
- 0 => 0,
- ),
- 5 =>
- array (
- 0 => 0,
- ),
- 6 =>
- array (
- 0 => 0,
- ),
- );
- $this->_delim = array (
- -1 =>
- array (
- 0 => 'comment',
- 1 => '',
- 2 => '',
- 3 => '',
- 4 => 'brackets',
- 5 => 'brackets',
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => '',
- 1 => '',
- 2 => '',
- 3 => '',
- ),
- 2 =>
- array (
- 0 => 'quotes',
- 1 => 'quotes',
- 2 => '',
- ),
- 3 =>
- array (
- 0 => 'comment',
- 1 => 'reserved',
- 2 => '',
- 3 => 'brackets',
- ),
- 4 =>
- array (
- 0 => '',
- ),
- 5 =>
- array (
- 0 => '',
- ),
- 6 =>
- array (
- 0 => '',
- ),
- );
- $this->_inner = array (
- -1 =>
- array (
- 0 => 'comment',
- 1 => 'var',
- 2 => 'identifier',
- 3 => 'special',
- 4 => 'code',
- 5 => 'code',
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => 'number',
- 1 => 'number',
- 2 => 'code',
- 3 => 'var',
- ),
- 2 =>
- array (
- 0 => 'string',
- 1 => 'string',
- 2 => 'var',
- ),
- 3 =>
- array (
- 0 => 'comment',
- 1 => 'code',
- 2 => 'identifier',
- 3 => 'code',
- ),
- 4 =>
- array (
- 0 => 'string',
- ),
- 5 =>
- array (
- 0 => 'special',
- ),
- 6 =>
- array (
- 0 => 'special',
- ),
- );
- $this->_end = array (
- 0 => '/(?i)\\*\\//',
- 1 => '/(?i)(?=;|\\})/',
- 2 => '/(?i)\\]/',
- 3 => '/(?i)\\}/',
- 4 => '/(?i)\\)/',
- 5 => '/(?i)\'/',
- 6 => '/(?i)"/',
- );
- $this->_states = array (
- -1 =>
- array (
- 0 => 0,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => 2,
- 5 => 3,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- ),
- 2 =>
- array (
- 0 => 5,
- 1 => 6,
- 2 => -1,
- ),
- 3 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => -1,
- 3 => 3,
- ),
- 4 =>
- array (
- 0 => -1,
- ),
- 5 =>
- array (
- 0 => -1,
- ),
- 6 =>
- array (
- 0 => -1,
- ),
- );
- $this->_keywords = array (
- -1 =>
- array (
- 0 => -1,
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- 3 =>
- array (
- ),
- 4 => -1,
- 5 => -1,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 'propertyValue' => '/^((?i)far-left|left|center-left|center-right|center|far-right|right-side|right|behind|leftwards|rightwards|inherit|scroll|fixed|transparent|none|repeat-x|repeat-y|repeat|no-repeat|collapse|separate|auto|top|bottom|both|open-quote|close-quote|no-open-quote|no-close-quote|crosshair|default|pointer|move|e-resize|ne-resize|nw-resize|n-resize|se-resize|sw-resize|s-resize|text|wait|help|ltr|rtl|inline|block|list-item|run-in|compact|marker|table|inline-table|table-row-group|table-header-group|table-footer-group|table-row|table-column-group|table-column|table-cell|table-caption|below|level|above|higher|lower|show|hide|caption|icon|menu|message-box|small-caption|status-bar|normal|wider|narrower|ultra-condensed|extra-condensed|condensed|semi-condensed|semi-expanded|expanded|extra-expanded|ultra-expanded|italic|oblique|small-caps|bold|bolder|lighter|inside|outside|disc|circle|square|decimal|decimal-leading-zero|lower-roman|upper-roman|lower-greek|lower-alpha|lower-latin|upper-alpha|upper-latin|hebrew|armenian|georgian|cjk-ideographic|hiragana|katakana|hiragana-iroha|katakana-iroha|crop|cross|invert|visible|hidden|always|avoid|x-low|low|medium|high|x-high|mix?|repeat?|static|relative|absolute|portrait|landscape|spell-out|once|digits|continuous|code|x-slow|slow|fast|x-fast|faster|slower|justify|underline|overline|line-through|blink|capitalize|uppercase|lowercase|embed|bidi-override|baseline|sub|super|text-top|middle|text-bottom|silent|x-soft|soft|loud|x-loud|pre|nowrap|serif|sans-serif|cursive|fantasy|monospace|empty|string|strict|loose|char|true|false|dotted|dashed|solid|double|groove|ridge|inset|outset|larger|smaller|xx-small|x-small|small|large|x-large|xx-large|all|newspaper|distribute|distribute-all-lines|distribute-center-last|inter-word|inter-ideograph|inter-cluster|kashida|ideograph-alpha|ideograph-numeric|ideograph-parenthesis|ideograph-space|keep-all|break-all|break-word|lr-tb|tb-rl|thin|thick|inline-block|w-resize|hand|distribute-letter|distribute-space|whitespace|male|female|child)$/',
- 'namedcolor' => '/^((?i)aqua|black|blue|fuchsia|gray|green|lime|maroon|navy|olive|purple|red|silver|teal|white|yellow|activeborder|activecaption|appworkspace|background|buttonface|buttonhighlight|buttonshadow|buttontext|captiontext|graytext|highlight|highlighttext|inactiveborder|inactivecaption|inactivecaptiontext|infobackground|infotext|menu|menutext|scrollbar|threeddarkshadow|threedface|threedhighlight|threedlightshadow|threedshadow|window|windowframe|windowtext)$/',
- ),
- 3 =>
- array (
- ),
- ),
- 2 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 =>
- array (
- ),
- ),
- 3 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 =>
- array (
- ),
- 3 => -1,
- ),
- 4 =>
- array (
- 0 =>
- array (
- ),
- ),
- 5 =>
- array (
- 0 =>
- array (
- ),
- ),
- 6 =>
- array (
- 0 =>
- array (
- ),
- ),
- );
- $this->_parts = array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 =>
- array (
- 1 => 'string',
- ),
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- ),
- 2 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- ),
- 3 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- ),
- 4 =>
- array (
- 0 => NULL,
- ),
- 5 =>
- array (
- 0 => NULL,
- ),
- 6 =>
- array (
- 0 => NULL,
- ),
- );
- $this->_subst = array (
- -1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- ),
- 2 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- ),
- 3 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- ),
- 4 =>
- array (
- 0 => false,
- ),
- 5 =>
- array (
- 0 => false,
- ),
- 6 =>
- array (
- 0 => false,
- ),
- );
- $this->_conditions = array (
- );
- $this->_kwmap = array (
- 'propertyValue' => 'string',
- 'namedcolor' => 'var',
- );
- $this->_defClass = 'code';
- $this->_checkDefines();
- }
-
-}
diff --git a/library/Text_Highlighter/Text/Highlighter/DIFF.php b/library/Text_Highlighter/Text/Highlighter/DIFF.php
deleted file mode 100644
index 2bb25a453..000000000
--- a/library/Text_Highlighter/Text/Highlighter/DIFF.php
+++ /dev/null
@@ -1,384 +0,0 @@
-<?php
-/**
- * Auto-generated class. DIFF syntax highlighting
- *
- * PHP version 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @link http://pear.php.net/package/Text_Highlighter
- * @category Text
- * @package Text_Highlighter
- * @version generated from: : diff.xml,v 1.1 2007/06/03 02:35:28 ssttoo Exp
- * @author Andrey Demenev <demenev@gmail.com>
- *
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter.php';
-
-/**
- * Auto-generated class. DIFF syntax highlighting
- *
- * @author Andrey Demenev <demenev@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: @package_version@
- * @link http://pear.php.net/package/Text_Highlighter
- */
-class Text_Highlighter_DIFF extends Text_Highlighter
-{
- var $_language = 'diff';
-
- /**
- * PHP4 Compatible Constructor
- *
- * @param array $options
- * @access public
- */
- function Text_Highlighter_DIFF($options=array())
- {
- $this->__construct($options);
- }
-
-
- /**
- * Constructor
- *
- * @param array $options
- * @access public
- */
- function __construct($options=array())
- {
-
- $this->_options = $options;
- $this->_regs = array (
- -1 => '/((?m)^\\\\\\sNo\\snewline.+$)|((?m)^\\-\\-\\-$)|((?m)^(diff\\s+\\-|Only\\s+|Index).*$)|((?m)^(\\-\\-\\-|\\+\\+\\+)\\s.+$)|((?m)^\\*.*$)|((?m)^\\+.*$)|((?m)^!.*$)|((?m)^\\<\\s.*$)|((?m)^\\>\\s.*$)|((?m)^\\d+(\\,\\d+)?[acd]\\d+(,\\d+)?$)|((?m)^\\-.*$)|((?m)^\\+.*$)|((?m)^@@.+@@$)|((?m)^d\\d+\\s\\d+$)|((?m)^a\\d+\\s\\d+$)|((?m)^(\\d+)(,\\d+)?(a)$)|((?m)^(\\d+)(,\\d+)?(c)$)|((?m)^(\\d+)(,\\d+)?(d)$)|((?m)^a(\\d+)(\\s\\d+)?$)|((?m)^c(\\d+)(\\s\\d+)?$)|((?m)^d(\\d+)(\\s\\d+)?$)/',
- 0 => '//',
- 1 => '//',
- 2 => '//',
- 3 => '//',
- 4 => '//',
- );
- $this->_counts = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 1,
- 3 => 1,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 0,
- 9 => 2,
- 10 => 0,
- 11 => 0,
- 12 => 0,
- 13 => 0,
- 14 => 0,
- 15 => 3,
- 16 => 3,
- 17 => 3,
- 18 => 2,
- 19 => 2,
- 20 => 2,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- 3 =>
- array (
- ),
- 4 =>
- array (
- ),
- );
- $this->_delim = array (
- -1 =>
- array (
- 0 => '',
- 1 => '',
- 2 => '',
- 3 => '',
- 4 => '',
- 5 => '',
- 6 => '',
- 7 => '',
- 8 => '',
- 9 => '',
- 10 => '',
- 11 => '',
- 12 => '',
- 13 => '',
- 14 => 'code',
- 15 => 'code',
- 16 => 'code',
- 17 => '',
- 18 => 'code',
- 19 => 'code',
- 20 => '',
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- 3 =>
- array (
- ),
- 4 =>
- array (
- ),
- );
- $this->_inner = array (
- -1 =>
- array (
- 0 => 'special',
- 1 => 'code',
- 2 => 'var',
- 3 => 'reserved',
- 4 => 'quotes',
- 5 => 'string',
- 6 => 'inlinedoc',
- 7 => 'quotes',
- 8 => 'string',
- 9 => 'code',
- 10 => 'quotes',
- 11 => 'string',
- 12 => 'code',
- 13 => 'code',
- 14 => 'var',
- 15 => 'string',
- 16 => 'inlinedoc',
- 17 => 'code',
- 18 => 'string',
- 19 => 'inlinedoc',
- 20 => 'code',
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- 3 =>
- array (
- ),
- 4 =>
- array (
- ),
- );
- $this->_end = array (
- 0 => '/(?m)(?=^[ad]\\d+\\s\\d+)/',
- 1 => '/(?m)^(\\.)$/',
- 2 => '/(?m)^(\\.)$/',
- 3 => '/(?m)^(\\.)$/',
- 4 => '/(?m)^(\\.)$/',
- );
- $this->_states = array (
- -1 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 => -1,
- 8 => -1,
- 9 => -1,
- 10 => -1,
- 11 => -1,
- 12 => -1,
- 13 => -1,
- 14 => 0,
- 15 => 1,
- 16 => 2,
- 17 => -1,
- 18 => 3,
- 19 => 4,
- 20 => -1,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- 3 =>
- array (
- ),
- 4 =>
- array (
- ),
- );
- $this->_keywords = array (
- -1 =>
- array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- 3 =>
- array (
- ),
- 4 =>
- array (
- ),
- 5 =>
- array (
- ),
- 6 =>
- array (
- ),
- 7 =>
- array (
- ),
- 8 =>
- array (
- ),
- 9 =>
- array (
- ),
- 10 =>
- array (
- ),
- 11 =>
- array (
- ),
- 12 =>
- array (
- ),
- 13 =>
- array (
- ),
- 14 => -1,
- 15 => -1,
- 16 => -1,
- 17 =>
- array (
- ),
- 18 => -1,
- 19 => -1,
- 20 =>
- array (
- ),
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- 3 =>
- array (
- ),
- 4 =>
- array (
- ),
- );
- $this->_parts = array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- 3 =>
- array (
- ),
- 4 =>
- array (
- ),
- );
- $this->_subst = array (
- -1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- 14 => false,
- 15 => false,
- 16 => false,
- 17 => false,
- 18 => false,
- 19 => false,
- 20 => false,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- 3 =>
- array (
- ),
- 4 =>
- array (
- ),
- );
- $this->_conditions = array (
- );
- $this->_kwmap = array (
- );
- $this->_defClass = 'default';
- $this->_checkDefines();
- }
-
-} \ No newline at end of file
diff --git a/library/Text_Highlighter/Text/Highlighter/DTD.php b/library/Text_Highlighter/Text/Highlighter/DTD.php
deleted file mode 100644
index 41b0faa78..000000000
--- a/library/Text_Highlighter/Text/Highlighter/DTD.php
+++ /dev/null
@@ -1,426 +0,0 @@
-<?php
-/**
- * Auto-generated class. DTD syntax highlighting
- *
- * PHP version 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @link http://pear.php.net/package/Text_Highlighter
- * @category Text
- * @package Text_Highlighter
- * @version generated from: : dtd.xml,v 1.1 2007/06/03 02:35:28 ssttoo Exp
- * @author Andrey Demenev <demenev@gmail.com>
- *
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter.php';
-
-/**
- * Auto-generated class. DTD syntax highlighting
- *
- * @author Andrey Demenev <demenev@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: @package_version@
- * @link http://pear.php.net/package/Text_Highlighter
- */
-class Text_Highlighter_DTD extends Text_Highlighter
-{
- var $_language = 'dtd';
-
- /**
- * PHP4 Compatible Constructor
- *
- * @param array $options
- * @access public
- */
- function Text_Highlighter_DTD($options=array())
- {
- $this->__construct($options);
- }
-
-
- /**
- * Constructor
- *
- * @param array $options
- * @access public
- */
- function __construct($options=array())
- {
-
- $this->_options = $options;
- $this->_regs = array (
- -1 => '/(\\<!--)|(\\<\\!\\[)|((\\&|\\%)[\\w\\-\\.]+;)/',
- 0 => '//',
- 1 => '/(\\<!--)|(\\<)|(#PCDATA\\b)|((\\&|\\%)[\\w\\-\\.]+;)|((?i)[a-z][a-z\\d\\-\\,:]+)/',
- 2 => '/(\\<!--)|(\\()|(\')|(")|((?<=\\<)!(ENTITY|ATTLIST|ELEMENT|NOTATION)\\b)|(\\s(#(IMPLIED|REQUIRED|FIXED))|CDATA|ENTITY|NOTATION|NMTOKENS?|PUBLIC|SYSTEM\\b)|(#PCDATA\\b)|((\\&|\\%)[\\w\\-\\.]+;)|((?i)[a-z][a-z\\d\\-\\,:]+)/',
- 3 => '/(\\()|((\\&|\\%)[\\w\\-\\.]+;)|((?i)[a-z][a-z\\d\\-\\,:]+)/',
- 4 => '/((\\&|\\%)[\\w\\-\\.]+;)/',
- 5 => '/((\\&|\\%)[\\w\\-\\.]+;)/',
- );
- $this->_counts = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 1,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 1,
- 4 => 0,
- ),
- 2 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 1,
- 5 => 2,
- 6 => 0,
- 7 => 1,
- 8 => 0,
- ),
- 3 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 0,
- ),
- 4 =>
- array (
- 0 => 1,
- ),
- 5 =>
- array (
- 0 => 1,
- ),
- );
- $this->_delim = array (
- -1 =>
- array (
- 0 => 'comment',
- 1 => 'brackets',
- 2 => '',
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => 'comment',
- 1 => 'brackets',
- 2 => '',
- 3 => '',
- 4 => '',
- ),
- 2 =>
- array (
- 0 => 'comment',
- 1 => 'brackets',
- 2 => 'quotes',
- 3 => 'quotes',
- 4 => '',
- 5 => '',
- 6 => '',
- 7 => '',
- 8 => '',
- ),
- 3 =>
- array (
- 0 => 'brackets',
- 1 => '',
- 2 => '',
- ),
- 4 =>
- array (
- 0 => '',
- ),
- 5 =>
- array (
- 0 => '',
- ),
- );
- $this->_inner = array (
- -1 =>
- array (
- 0 => 'comment',
- 1 => 'code',
- 2 => 'special',
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => 'comment',
- 1 => 'code',
- 2 => 'reserved',
- 3 => 'special',
- 4 => 'identifier',
- ),
- 2 =>
- array (
- 0 => 'comment',
- 1 => 'code',
- 2 => 'string',
- 3 => 'string',
- 4 => 'var',
- 5 => 'reserved',
- 6 => 'reserved',
- 7 => 'special',
- 8 => 'identifier',
- ),
- 3 =>
- array (
- 0 => 'code',
- 1 => 'special',
- 2 => 'identifier',
- ),
- 4 =>
- array (
- 0 => 'special',
- ),
- 5 =>
- array (
- 0 => 'special',
- ),
- );
- $this->_end = array (
- 0 => '/--\\>/',
- 1 => '/\\]\\]\\>/',
- 2 => '/\\>/',
- 3 => '/\\)/',
- 4 => '/\'/',
- 5 => '/"/',
- );
- $this->_states = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => -1,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => 0,
- 1 => 2,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- ),
- 2 =>
- array (
- 0 => 0,
- 1 => 3,
- 2 => 4,
- 3 => 5,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 => -1,
- 8 => -1,
- ),
- 3 =>
- array (
- 0 => 3,
- 1 => -1,
- 2 => -1,
- ),
- 4 =>
- array (
- 0 => -1,
- ),
- 5 =>
- array (
- 0 => -1,
- ),
- );
- $this->_keywords = array (
- -1 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 =>
- array (
- ),
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 =>
- array (
- ),
- 3 =>
- array (
- ),
- 4 =>
- array (
- ),
- ),
- 2 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 =>
- array (
- ),
- 5 =>
- array (
- ),
- 6 =>
- array (
- ),
- 7 =>
- array (
- ),
- 8 =>
- array (
- ),
- ),
- 3 =>
- array (
- 0 => -1,
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- ),
- 4 =>
- array (
- 0 =>
- array (
- ),
- ),
- 5 =>
- array (
- 0 =>
- array (
- ),
- ),
- );
- $this->_parts = array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- ),
- 2 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- ),
- 3 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- ),
- 4 =>
- array (
- 0 => NULL,
- ),
- 5 =>
- array (
- 0 => NULL,
- ),
- );
- $this->_subst = array (
- -1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- ),
- 2 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- ),
- 3 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- ),
- 4 =>
- array (
- 0 => false,
- ),
- 5 =>
- array (
- 0 => false,
- ),
- );
- $this->_conditions = array (
- );
- $this->_kwmap = array (
- );
- $this->_defClass = 'code';
- $this->_checkDefines();
- }
-
-} \ No newline at end of file
diff --git a/library/Text_Highlighter/Text/Highlighter/Generator.php b/library/Text_Highlighter/Text/Highlighter/Generator.php
deleted file mode 100644
index 39c4edccb..000000000
--- a/library/Text_Highlighter/Text/Highlighter/Generator.php
+++ /dev/null
@@ -1,1291 +0,0 @@
-<?php
-/* vim: set expandtab tabstop=4 shiftwidth=4 softtabstop=4: */
-/**
-* Syntax highlighter class generator
-*
-* To simplify the process of creating new syntax highlighters
-* for different languages, {@link Text_Highlighter_Generator} class is
-* provided. It takes highlighting rules from XML file and generates
-* a code of a class inherited from {@link Text_Highlighter}.
-*
-* PHP versions 4 and 5
-*
-* LICENSE: This source file is subject to version 3.0 of the PHP license
-* that is available through the world-wide-web at the following URI:
-* http://www.php.net/license/3_0.txt. If you did not receive a copy of
-* the PHP License and are unable to obtain it through the web, please
-* send a note to license@php.net so we can mail you a copy immediately.
-*
-* @category Text
-* @package Text_Highlighter
-* @author Andrey Demenev <demenev@gmail.com>
-* @copyright 2004-2006 Andrey Demenev
-* @license http://www.php.net/license/3_0.txt PHP License
-* @version CVS: $Id$
-* @link http://pear.php.net/package/Text_Highlighter
-*/
-
-/**
-* @ignore
-*/
-require_once 'PEAR.php';
-require_once 'XML/Parser.php';
-
-// {{{ error codes
-
-define ('TEXT_HIGHLIGHTER_EMPTY_RE', 1);
-define ('TEXT_HIGHLIGHTER_INVALID_RE', 2);
-define ('TEXT_HIGHLIGHTER_EMPTY_OR_MISSING', 3);
-define ('TEXT_HIGHLIGHTER_EMPTY', 4);
-define ('TEXT_HIGHLIGHTER_REGION_REGION', 5);
-define ('TEXT_HIGHLIGHTER_REGION_BLOCK', 6);
-define ('TEXT_HIGHLIGHTER_BLOCK_REGION', 7);
-define ('TEXT_HIGHLIGHTER_KEYWORD_BLOCK', 8);
-define ('TEXT_HIGHLIGHTER_KEYWORD_INHERITS', 9);
-define ('TEXT_HIGHLIGHTER_PARSE', 10);
-define ('TEXT_HIGHLIGHTER_FILE_WRITE', 11);
-define ('TEXT_HIGHLIGHTER_FILE_READ', 12);
-// }}}
-
-/**
-* Syntax highliter class generator class
-*
-* This class is used to generate PHP classes
-* from XML files with highlighting rules
-*
-* Usage example
-* <code>
-*require_once 'Text/Highlighter/Generator.php';
-*$generator = new Text_Highlighter_Generator('php.xml');
-*$generator->generate();
-*$generator->saveCode('PHP.php');
-* </code>
-*
-* A command line script <b>generate</b> is provided for
-* class generation (installs in scripts/Text/Highlighter).
-*
-* @author Andrey Demenev <demenev@gmail.com>
-* @copyright 2004-2006 Andrey Demenev
-* @license http://www.php.net/license/3_0.txt PHP License
-* @version Release: @package_version@
-* @link http://pear.php.net/package/Text_Highlighter
-*/
-
-class Text_Highlighter_Generator extends XML_Parser
-{
- // {{{ properties
- /**
- * Whether to do case folding.
- * We have to declare it here, because XML_Parser
- * sets case folding in constructor
- *
- * @var boolean
- */
- var $folding = false;
-
- /**
- * Holds name of file with highlighting rules
- *
- * @var string
- * @access private
- */
- var $_syntaxFile;
-
- /**
- * Current element being processed
- *
- * @var array
- * @access private
- */
- var $_element;
-
- /**
- * List of regions
- *
- * @var array
- * @access private
- */
- var $_regions = array();
-
- /**
- * List of blocks
- *
- * @var array
- * @access private
- */
- var $_blocks = array();
-
- /**
- * List of keyword groups
- *
- * @var array
- * @access private
- */
- var $_keywords = array();
-
- /**
- * List of authors
- *
- * @var array
- * @access private
- */
- var $_authors = array();
-
- /**
- * Name of language
- *
- * @var string
- * @access public
- */
- var $language = '';
-
- /**
- * Generated code
- *
- * @var string
- * @access private
- */
- var $_code = '';
-
- /**
- * Default class
- *
- * @var string
- * @access private
- */
- var $_defClass = 'default';
-
- /**
- * Comment
- *
- * @var string
- * @access private
- */
- var $_comment = '';
-
- /**
- * Flag for comment processing
- *
- * @var boolean
- * @access private
- */
- var $_inComment = false;
-
- /**
- * Sorting order of current block/region
- *
- * @var integer
- * @access private
- */
- var $_blockOrder = 0;
-
- /**
- * Generation errors
- *
- * @var array
- * @access private
- */
- var $_errors;
-
- // }}}
- // {{{ constructor
-
- /**
- * PHP4 compatable constructor
- *
- * @param string $syntaxFile Name of XML file
- * with syntax highlighting rules
- *
- * @access public
- */
-
- function Text_Highlighter_Generator($syntaxFile = '')
- {
- return $this->__construct($syntaxFile);
- }
-
- /**
- * Constructor
- *
- * @param string $syntaxFile Name of XML file
- * with syntax highlighting rules
- *
- * @access public
- */
-
- function __construct($syntaxFile = '')
- {
- XML_Parser::XML_Parser(null, 'func');
- $this->_errors = array();
- $this->_declareErrorMessages();
- if ($syntaxFile) {
- $this->setInputFile($syntaxFile);
- }
- }
-
- // }}}
- // {{{ _formatError
-
- /**
- * Format error message
- *
- * @param int $code error code
- * @param string $params parameters
- * @param string $fileName file name
- * @param int $lineNo line number
- * @return array
- * @access public
- */
- function _formatError($code, $params, $fileName, $lineNo)
- {
- $template = $this->_templates[$code];
- $ret = call_user_func_array('sprintf', array_merge(array($template), $params));
- if ($fileName) {
- $ret = '[' . $fileName . '] ' . $ret;
- }
- if ($lineNo) {
- $ret .= ' (line ' . $lineNo . ')';
- }
- return $ret;
- }
-
- // }}}
- // {{{ declareErrorMessages
-
- /**
- * Set up error message templates
- *
- * @access private
- */
- function _declareErrorMessages()
- {
- $this->_templates = array (
- TEXT_HIGHLIGHTER_EMPTY_RE => 'Empty regular expression',
- TEXT_HIGHLIGHTER_INVALID_RE => 'Invalid regular expression : %s',
- TEXT_HIGHLIGHTER_EMPTY_OR_MISSING => 'Empty or missing %s',
- TEXT_HIGHLIGHTER_EMPTY => 'Empty %s',
- TEXT_HIGHLIGHTER_REGION_REGION => 'Region %s refers undefined region %s',
- TEXT_HIGHLIGHTER_REGION_BLOCK => 'Region %s refers undefined block %s',
- TEXT_HIGHLIGHTER_BLOCK_REGION => 'Block %s refers undefined region %s',
- TEXT_HIGHLIGHTER_KEYWORD_BLOCK => 'Keyword group %s refers undefined block %s',
- TEXT_HIGHLIGHTER_KEYWORD_INHERITS => 'Keyword group %s inherits undefined block %s',
- TEXT_HIGHLIGHTER_PARSE => '%s',
- TEXT_HIGHLIGHTER_FILE_WRITE => 'Error writing file %s',
- TEXT_HIGHLIGHTER_FILE_READ => '%s'
- );
- }
-
- // }}}
- // {{{ setInputFile
-
- /**
- * Sets the input xml file to be parsed
- *
- * @param string Filename (full path)
- * @return boolean
- * @access public
- */
- function setInputFile($file)
- {
- $this->_syntaxFile = $file;
- $ret = parent::setInputFile($file);
- if (PEAR::isError($ret)) {
- $this->_error(TEXT_HIGHLIGHTER_FILE_READ, $ret->message);
- return false;
- }
- return true;
- }
-
- // }}}
- // {{{ generate
-
- /**
- * Generates class code
- *
- * @access public
- */
-
- function generate()
- {
- $this->_regions = array();
- $this->_blocks = array();
- $this->_keywords = array();
- $this->language = '';
- $this->_code = '';
- $this->_defClass = 'default';
- $this->_comment = '';
- $this->_inComment = false;
- $this->_authors = array();
- $this->_blockOrder = 0;
- $this->_errors = array();
-
- $ret = $this->parse();
- if (PEAR::isError($ret)) {
- $this->_error(TEXT_HIGHLIGHTER_PARSE, $ret->message);
- return false;
- }
- return true;
- }
-
- // }}}
- // {{{ getCode
-
- /**
- * Returns generated code as a string.
- *
- * @return string Generated code
- * @access public
- */
-
- function getCode()
- {
- return $this->_code;
- }
-
- // }}}
- // {{{ saveCode
-
- /**
- * Saves generated class to file. Note that {@link Text_Highlighter::factory()}
- * assumes that filename is uppercase (SQL.php, DTD.php, etc), and file
- * is located in Text/Highlighter
- *
- * @param string $filename Name of file to write the code to
- * @return boolean true on success, false on failure
- * @access public
- */
-
- function saveCode($filename)
- {
- $f = @fopen($filename, 'wb');
- if (!$f) {
- $this->_error(TEXT_HIGHLIGHTER_FILE_WRITE, array('outfile'=>$filename));
- return false;
- }
- fwrite ($f, $this->_code);
- fclose($f);
- return true;
- }
-
- // }}}
- // {{{ hasErrors
-
- /**
- * Reports if there were errors
- *
- * @return boolean
- * @access public
- */
-
- function hasErrors()
- {
- return count($this->_errors) > 0;
- }
-
- // }}}
- // {{{ getErrors
-
- /**
- * Returns errors
- *
- * @return array
- * @access public
- */
-
- function getErrors()
- {
- return $this->_errors;
- }
-
- // }}}
- // {{{ _sortBlocks
-
- /**
- * Sorts blocks
- *
- * @access private
- */
-
- function _sortBlocks($b1, $b2) {
- return $b1['order'] - $b2['order'];
- }
-
- // }}}
- // {{{ _sortLookFor
- /**
- * Sort 'look for' list
- * @return int
- * @param string $b1
- * @param string $b2
- */
- function _sortLookFor($b1, $b2) {
- $o1 = isset($this->_blocks[$b1]) ? $this->_blocks[$b1]['order'] : $this->_regions[$b1]['order'];
- $o2 = isset($this->_blocks[$b2]) ? $this->_blocks[$b2]['order'] : $this->_regions[$b2]['order'];
- return $o1 - $o2;
- }
-
- // }}}
- // {{{ _makeRE
-
- /**
- * Adds delimiters and modifiers to regular expression if necessary
- *
- * @param string $text Original RE
- * @return string Final RE
- * @access private
- */
- function _makeRE($text, $case = false)
- {
- if (!strlen($text)) {
- $this->_error(TEXT_HIGHLIGHTER_EMPTY_RE);
- }
- if (!strlen($text) || $text{0} != '/') {
- $text = '/' . $text . '/';
- }
- if (!$case) {
- $text .= 'i';
- }
- $php_errormsg = '';
- @preg_match($text, '');
- if ($php_errormsg) {
- $this->_error(TEXT_HIGHLIGHTER_INVALID_RE, $php_errormsg);
- }
- preg_match ('#^/(.+)/(.*)$#', $text, $m);
- if (@$m[2]) {
- $text = '(?' . $m[2] . ')' . $m[1];
- } else {
- $text = $m[1];
- }
- return $text;
- }
-
- // }}}
- // {{{ _exportArray
-
- /**
- * Exports array as PHP code
- *
- * @param array $array
- * @return string Code
- * @access private
- */
- function _exportArray($array)
- {
- $array = var_export($array, true);
- return trim(preg_replace('~^(\s*)~m',' \1\1',$array));
- }
-
- // }}}
- // {{{ _countSubpatterns
- /**
- * Find number of capturing suppaterns in regular expression
- * @return int
- * @param string $re Regular expression (without delimiters)
- */
- function _countSubpatterns($re)
- {
- preg_match_all('/' . $re . '/', '', $m);
- return count($m)-1;
- }
-
- // }}}
-
- /**#@+
- * @access private
- * @param resource $xp XML parser resource
- * @param string $elem XML element name
- * @param array $attribs XML element attributes
- */
-
- // {{{ xmltag_Default
-
- /**
- * start handler for <default> element
- */
- function xmltag_Default($xp, $elem, $attribs)
- {
- $this->_aliasAttributes($attribs);
- if (!isset($attribs['innerGroup']) || $attribs['innerGroup'] === '') {
- $this->_error(TEXT_HIGHLIGHTER_EMPTY_OR_MISSING, 'innerGroup');
- }
- $this->_defClass = @$attribs['innerGroup'];
- }
-
- // }}}
- // {{{ xmltag_Region
-
- /**
- * start handler for <region> element
- */
- function xmltag_Region($xp, $elem, $attribs)
- {
- $this->_aliasAttributes($attribs);
- if (!isset($attribs['name']) || $attribs['name'] === '') {
- $this->_error(TEXT_HIGHLIGHTER_EMPTY_OR_MISSING, 'region name');
- }
- if (!isset($attribs['innerGroup']) || $attribs['innerGroup'] === '') {
- $this->_error(TEXT_HIGHLIGHTER_EMPTY_OR_MISSING, 'innerGroup');
- }
- $this->_element = array('name' => $attribs['name']);
- $this->_element['line'] = xml_get_current_line_number($this->parser);
- if (isset($attribs['case'])) {
- $this->_element['case'] = $attribs['case'] == 'yes';
- } else {
- $this->_element['case'] = $this->_case;
- }
- $this->_element['innerGroup'] = $attribs['innerGroup'];
- $this->_element['delimGroup'] = isset($attribs['delimGroup']) ?
- $attribs['delimGroup'] :
- $attribs['innerGroup'];
- $this->_element['start'] = $this->_makeRE(@$attribs['start'], $this->_element['case']);
- $this->_element['end'] = $this->_makeRE(@$attribs['end'], $this->_element['case']);
- $this->_element['contained'] = @$attribs['contained'] == 'yes';
- $this->_element['never-contained'] = @$attribs['never-contained'] == 'yes';
- $this->_element['remember'] = @$attribs['remember'] == 'yes';
- if (isset($attribs['startBOL']) && $attribs['startBOL'] == 'yes') {
- $this->_element['startBOL'] = true;
- }
- if (isset($attribs['endBOL']) && $attribs['endBOL'] == 'yes') {
- $this->_element['endBOL'] = true;
- }
- if (isset($attribs['neverAfter'])) {
- $this->_element['neverafter'] = $this->_makeRE($attribs['neverAfter']);
- }
- }
-
- // }}}
- // {{{ xmltag_Block
-
- /**
- * start handler for <block> element
- */
- function xmltag_Block($xp, $elem, $attribs)
- {
- $this->_aliasAttributes($attribs);
- if (!isset($attribs['name']) || $attribs['name'] === '') {
- $this->_error(TEXT_HIGHLIGHTER_EMPTY_OR_MISSING, 'block name');
- }
- if (isset($attribs['innerGroup']) && $attribs['innerGroup'] === '') {
- $this->_error(TEXT_HIGHLIGHTER_EMPTY, 'innerGroup');
- }
- $this->_element = array('name' => $attribs['name']);
- $this->_element['line'] = xml_get_current_line_number($this->parser);
- if (isset($attribs['case'])) {
- $this->_element['case'] = $attribs['case'] == 'yes';
- } else {
- $this->_element['case'] = $this->_case;
- }
- if (isset($attribs['innerGroup'])) {
- $this->_element['innerGroup'] = @$attribs['innerGroup'];
- }
- $this->_element['match'] = $this->_makeRE($attribs['match'], $this->_element['case']);
- $this->_element['contained'] = @$attribs['contained'] == 'yes';
- $this->_element['multiline'] = @$attribs['multiline'] == 'yes';
- if (isset($attribs['BOL']) && $attribs['BOL'] == 'yes') {
- $this->_element['BOL'] = true;
- }
- if (isset($attribs['neverAfter'])) {
- $this->_element['neverafter'] = $this->_makeRE($attribs['neverAfter']);
- }
- }
-
- // }}}
- // {{{ cdataHandler
-
- /**
- * Character data handler. Used for comment
- */
- function cdataHandler($xp, $cdata)
- {
- if ($this->_inComment) {
- $this->_comment .= $cdata;
- }
- }
-
- // }}}
- // {{{ xmltag_Comment
-
- /**
- * start handler for <comment> element
- */
- function xmltag_Comment($xp, $elem, $attribs)
- {
- $this->_comment = '';
- $this->_inComment = true;
- }
-
- // }}}
- // {{{ xmltag_PartGroup
-
- /**
- * start handler for <partgroup> element
- */
- function xmltag_PartGroup($xp, $elem, $attribs)
- {
- $this->_aliasAttributes($attribs);
- if (!isset($attribs['innerGroup']) || $attribs['innerGroup'] === '') {
- $this->_error(TEXT_HIGHLIGHTER_EMPTY_OR_MISSING, 'innerGroup');
- }
- $this->_element['partClass'][$attribs['index']] = @$attribs['innerGroup'];
- }
-
- // }}}
- // {{{ xmltag_PartClass
-
- /**
- * start handler for <partclass> element
- */
- function xmltag_PartClass($xp, $elem, $attribs)
- {
- $this->xmltag_PartGroup($xp, $elem, $attribs);
- }
-
- // }}}
- // {{{ xmltag_Keywords
-
- /**
- * start handler for <keywords> element
- */
- function xmltag_Keywords($xp, $elem, $attribs)
- {
- $this->_aliasAttributes($attribs);
- if (!isset($attribs['name']) || $attribs['name'] === '') {
- $this->_error(TEXT_HIGHLIGHTER_EMPTY_OR_MISSING, 'keyword group name');
- }
- if (!isset($attribs['innerGroup']) || $attribs['innerGroup'] === '') {
- $this->_error(TEXT_HIGHLIGHTER_EMPTY_OR_MISSING, 'innerGroup');
- }
- if (!isset($attribs['inherits']) || $attribs['inherits'] === '') {
- $this->_error(TEXT_HIGHLIGHTER_EMPTY_OR_MISSING, 'inherits');
- }
- $this->_element = array('name'=>@$attribs['name']);
- $this->_element['line'] = xml_get_current_line_number($this->parser);
- $this->_element['innerGroup'] = @$attribs['innerGroup'];
- if (isset($attribs['case'])) {
- $this->_element['case'] = $attribs['case'] == 'yes';
- } else {
- $this->_element['case'] = $this->_case;
- }
- $this->_element['inherits'] = @$attribs['inherits'];
- if (isset($attribs['otherwise'])) {
- $this->_element['otherwise'] = $attribs['otherwise'];
- }
- if (isset($attribs['ifdef'])) {
- $this->_element['ifdef'] = $attribs['ifdef'];
- }
- if (isset($attribs['ifndef'])) {
- $this->_element['ifndef'] = $attribs['ifndef'];
- }
- }
-
- // }}}
- // {{{ xmltag_Keyword
-
- /**
- * start handler for <keyword> element
- */
- function xmltag_Keyword($xp, $elem, $attribs)
- {
- if (!isset($attribs['match']) || $attribs['match'] === '') {
- $this->_error(TEXT_HIGHLIGHTER_EMPTY_OR_MISSING, 'match');
- }
- $keyword = @$attribs['match'];
- if (!$this->_element['case']) {
- $keyword = strtolower($keyword);
- }
- $this->_element['match'][$keyword] = true;
- }
-
- // }}}
- // {{{ xmltag_Contains
-
- /**
- * start handler for <contains> element
- */
- function xmltag_Contains($xp, $elem, $attribs)
- {
- $this->_element['contains-all'] = @$attribs['all'] == 'yes';
- if (isset($attribs['region'])) {
- $this->_element['contains']['region'][$attribs['region']] =
- xml_get_current_line_number($this->parser);
- }
- if (isset($attribs['block'])) {
- $this->_element['contains']['block'][$attribs['block']] =
- xml_get_current_line_number($this->parser);
- }
- }
-
- // }}}
- // {{{ xmltag_But
-
- /**
- * start handler for <but> element
- */
- function xmltag_But($xp, $elem, $attribs)
- {
- if (isset($attribs['region'])) {
- $this->_element['not-contains']['region'][$attribs['region']] = true;
- }
- if (isset($attribs['block'])) {
- $this->_element['not-contains']['block'][$attribs['block']] = true;
- }
- }
-
- // }}}
- // {{{ xmltag_Onlyin
-
- /**
- * start handler for <onlyin> element
- */
- function xmltag_Onlyin($xp, $elem, $attribs)
- {
- if (!isset($attribs['region']) || $attribs['region'] === '') {
- $this->_error(TEXT_HIGHLIGHTER_EMPTY_OR_MISSING, 'region');
- }
- $this->_element['onlyin'][$attribs['region']] = xml_get_current_line_number($this->parser);
- }
-
- // }}}
- // {{{ xmltag_Author
-
- /**
- * start handler for <author> element
- */
- function xmltag_Author($xp, $elem, $attribs)
- {
- if (!isset($attribs['name']) || $attribs['name'] === '') {
- $this->_error(TEXT_HIGHLIGHTER_EMPTY_OR_MISSING, 'author name');
- }
- $this->_authors[] = array(
- 'name' => @$attribs['name'],
- 'email' => (string)@$attribs['email']
- );
- }
-
- // }}}
- // {{{ xmltag_Highlight
-
- /**
- * start handler for <highlight> element
- */
- function xmltag_Highlight($xp, $elem, $attribs)
- {
- if (!isset($attribs['lang']) || $attribs['lang'] === '') {
- $this->_error(TEXT_HIGHLIGHTER_EMPTY_OR_MISSING, 'language name');
- }
- $this->_code = '';
- $this->language = strtoupper(@$attribs['lang']);
- $this->_case = @$attribs['case'] == 'yes';
- }
-
- // }}}
-
- /**#@-*/
-
- // {{{ _error
-
- /**
- * Add an error message
- *
- * @param integer $code Error code
- * @param mixed $message Error message or array with error message parameters
- * @param integer $lineNo Source code line number
- * @access private
- */
- function _error($code, $params = array(), $lineNo = 0)
- {
- if (!$lineNo && !empty($this->parser)) {
- $lineNo = xml_get_current_line_number($this->parser);
- }
- $this->_errors[] = $this->_formatError($code, $params, $this->_syntaxFile, $lineNo);
- }
-
- // }}}
- // {{{ _aliasAttributes
-
- /**
- * BC trick
- *
- * @param array $attrs attributes
- */
- function _aliasAttributes(&$attrs)
- {
- if (isset($attrs['innerClass']) && !isset($attrs['innerGroup'])) {
- $attrs['innerGroup'] = $attrs['innerClass'];
- }
- if (isset($attrs['delimClass']) && !isset($attrs['delimGroup'])) {
- $attrs['delimGroup'] = $attrs['delimClass'];
- }
- if (isset($attrs['partClass']) && !isset($attrs['partGroup'])) {
- $attrs['partGroup'] = $attrs['partClass'];
- }
- }
-
- // }}}
-
- /**#@+
- * @access private
- * @param resource $xp XML parser resource
- * @param string $elem XML element name
- */
-
- // {{{ xmltag_Comment_
-
- /**
- * end handler for <comment> element
- */
- function xmltag_Comment_($xp, $elem)
- {
- $this->_inComment = false;
- }
-
- // }}}
- // {{{ xmltag_Region_
-
- /**
- * end handler for <region> element
- */
- function xmltag_Region_($xp, $elem)
- {
- $this->_element['type'] = 'region';
- $this->_element['order'] = $this->_blockOrder ++;
- $this->_regions[$this->_element['name']] = $this->_element;
- }
-
- // }}}
- // {{{ xmltag_Keywords_
-
- /**
- * end handler for <keywords> element
- */
- function xmltag_Keywords_($xp, $elem)
- {
- $this->_keywords[$this->_element['name']] = $this->_element;
- }
-
- // }}}
- // {{{ xmltag_Block_
-
- /**
- * end handler for <block> element
- */
- function xmltag_Block_($xp, $elem)
- {
- $this->_element['type'] = 'block';
- $this->_element['order'] = $this->_blockOrder ++;
- $this->_blocks[$this->_element['name']] = $this->_element;
- }
-
- // }}}
- // {{{ xmltag_Highlight_
-
- /**
- * end handler for <highlight> element
- */
- function xmltag_Highlight_($xp, $elem)
- {
- $conditions = array();
- $toplevel = array();
- foreach ($this->_blocks as $i => $current) {
- if (!$current['contained'] && !isset($current['onlyin'])) {
- $toplevel[] = $i;
- }
- foreach ((array)@$current['onlyin'] as $region => $lineNo) {
- if (!isset($this->_regions[$region])) {
- $this->_error(TEXT_HIGHLIGHTER_BLOCK_REGION,
- array(
- 'block' => $current['name'],
- 'region' => $region
- ));
- }
- }
- }
- foreach ($this->_regions as $i=>$current) {
- if (!$current['contained'] && !isset($current['onlyin'])) {
- $toplevel[] = $i;
- }
- foreach ((array)@$current['contains']['region'] as $region => $lineNo) {
- if (!isset($this->_regions[$region])) {
- $this->_error(TEXT_HIGHLIGHTER_REGION_REGION,
- array(
- 'region1' => $current['name'],
- 'region2' => $region
- ));
- }
- }
- foreach ((array)@$current['contains']['block'] as $region => $lineNo) {
- if (!isset($this->_blocks[$region])) {
- $this->_error(TEXT_HIGHLIGHTER_REGION_BLOCK,
- array(
- 'block' => $current['name'],
- 'region' => $region
- ));
- }
- }
- foreach ((array)@$current['onlyin'] as $region => $lineNo) {
- if (!isset($this->_regions[$region])) {
- $this->_error(TEXT_HIGHLIGHTER_REGION_REGION,
- array(
- 'region1' => $current['name'],
- 'region2' => $region
- ));
- }
- }
- foreach ($this->_regions as $j => $region) {
- if (isset($region['onlyin'])) {
- $suits = isset($region['onlyin'][$current['name']]);
- } elseif (isset($current['not-contains']['region'][$region['name']])) {
- $suits = false;
- } elseif (isset($current['contains']['region'][$region['name']])) {
- $suits = true;
- } else {
- $suits = @$current['contains-all'] && @!$region['never-contained'];
- }
- if ($suits) {
- $this->_regions[$i]['lookfor'][] = $j;
- }
- }
- foreach ($this->_blocks as $j=>$region) {
- if (isset($region['onlyin'])) {
- $suits = isset($region['onlyin'][$current['name']]);
- } elseif (isset($current['not-contains']['block'][$region['name']])) {
- $suits = false;
- } elseif (isset($current['contains']['block'][$region['name']])) {
- $suits = true;
- } else {
- $suits = @$current['contains-all'] && @!$region['never-contained'];
- }
- if ($suits) {
- $this->_regions[$i]['lookfor'][] = $j;
- }
- }
- }
- foreach ($this->_blocks as $i=>$current) {
- unset ($this->_blocks[$i]['never-contained']);
- unset ($this->_blocks[$i]['contained']);
- unset ($this->_blocks[$i]['contains-all']);
- unset ($this->_blocks[$i]['contains']);
- unset ($this->_blocks[$i]['onlyin']);
- unset ($this->_blocks[$i]['line']);
- }
-
- foreach ($this->_regions as $i=>$current) {
- unset ($this->_regions[$i]['never-contained']);
- unset ($this->_regions[$i]['contained']);
- unset ($this->_regions[$i]['contains-all']);
- unset ($this->_regions[$i]['contains']);
- unset ($this->_regions[$i]['onlyin']);
- unset ($this->_regions[$i]['line']);
- }
-
- foreach ($this->_keywords as $name => $keyword) {
- if (isset($keyword['ifdef'])) {
- $conditions[$keyword['ifdef']][] = array($name, true);
- }
- if (isset($keyword['ifndef'])) {
- $conditions[$keyword['ifndef']][] = array($name, false);
- }
- unset($this->_keywords[$name]['line']);
- if (!isset($this->_blocks[$keyword['inherits']])) {
- $this->_error(TEXT_HIGHLIGHTER_KEYWORD_INHERITS,
- array(
- 'keyword' => $keyword['name'],
- 'block' => $keyword['inherits']
- ));
- }
- if (isset($keyword['otherwise']) && !isset($this->_blocks[$keyword['otherwise']]) ) {
- $this->_error(TEXT_HIGHLIGHTER_KEYWORD_BLOCK,
- array(
- 'keyword' => $keyword['name'],
- 'block' => $keyword['inherits']
- ));
- }
- }
-
- $syntax=array(
- 'keywords' => $this->_keywords,
- 'blocks' => array_merge($this->_blocks, $this->_regions),
- 'toplevel' => $toplevel,
- );
- uasort($syntax['blocks'], array(&$this, '_sortBlocks'));
- foreach ($syntax['blocks'] as $name => $block) {
- if ($block['type'] == 'block') {
- continue;
- }
- if (is_array(@$syntax['blocks'][$name]['lookfor'])) {
- usort($syntax['blocks'][$name]['lookfor'], array(&$this, '_sortLookFor'));
- }
- }
- usort($syntax['toplevel'], array(&$this, '_sortLookFor'));
- $syntax['case'] = $this->_case;
- $this->_code = <<<CODE
-<?php
-/**
- * Auto-generated class. {$this->language} syntax highlighting
-CODE;
-
- if ($this->_comment) {
- $comment = preg_replace('~^~m',' * ',$this->_comment);
- $this->_code .= "\n * \n" . $comment;
- }
-
- $this->_code .= <<<CODE
-
- *
- * PHP version 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @link http://pear.php.net/package/Text_Highlighter
- * @category Text
- * @package Text_Highlighter
- * @version generated from: $this->_syntaxFile
-
-CODE;
-
- foreach ($this->_authors as $author) {
- $this->_code .= ' * @author ' . $author['name'];
- if ($author['email']) {
- $this->_code .= ' <' . $author['email'] . '>';
- }
- $this->_code .= "\n";
- }
-
- $this->_code .= <<<CODE
- *
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter.php';
-
-/**
- * Auto-generated class. {$this->language} syntax highlighting
- *
-
-CODE;
- foreach ($this->_authors as $author) {
- $this->_code .= ' * @author ' . $author['name'];
- if ($author['email']) {
- $this->_code .= ' <' . $author['email']. '>';
- }
- $this->_code .= "\n";
- }
-
-
- $this->_code .= <<<CODE
- * @category Text
- * @package Text_Highlighter
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: @package_version@
- * @link http://pear.php.net/package/Text_Highlighter
- */
-class Text_Highlighter_{$this->language} extends Text_Highlighter
-{
-
-CODE;
- $this->_code .= 'var $_language = \'' . strtolower($this->language) . "';\n\n";
- $array = var_export($syntax, true);
- $array = trim(preg_replace('~^(\s*)~m',' \1\1',$array));
- // \$this->_syntax = $array;
- $this->_code .= <<<CODE
- /**
- * PHP4 Compatible Constructor
- *
- * @param array \$options
- * @access public
- */
- function Text_Highlighter_{$this->language}(\$options=array())
- {
- \$this->__construct(\$options);
- }
-
-
- /**
- * Constructor
- *
- * @param array \$options
- * @access public
- */
- function __construct(\$options=array())
- {
-
-CODE;
- $this->_code .= <<<CODE
-
- \$this->_options = \$options;
-CODE;
- $states = array();
- $i = 0;
- foreach ($syntax['blocks'] as $name => $block) {
- if ($block['type'] == 'region') {
- $states[$name] = $i++;
- }
- }
- $regs = array();
- $counts = array();
- $delim = array();
- $inner = array();
- $end = array();
- $stat = array();
- $keywords = array();
- $parts = array();
- $kwmap = array();
- $subst = array();
- $re = array();
- $ce = array();
- $rd = array();
- $in = array();
- $st = array();
- $kw = array();
- $sb = array();
- foreach ($syntax['toplevel'] as $name) {
- $block = $syntax['blocks'][$name];
- if ($block['type'] == 'block') {
- $kwm = array();
- $re[] = '(' . $block['match'] . ')';
- $ce[] = $this->_countSubpatterns($block['match']);
- $rd[] = '';
- $sb[] = false;;
- $st[] = -1;
- foreach ($syntax['keywords'] as $kwname => $kwgroup) {
- if ($kwgroup['inherits'] != $name) {
- continue;
- }
- $gre = implode('|', array_keys($kwgroup['match']));
- if (!$kwgroup['case']) {
- $gre = '(?i)' . $gre;
- }
- $kwm[$kwname][] = $gre;
- $kwmap[$kwname] = $kwgroup['innerGroup'];
- }
- foreach ($kwm as $g => $ma) {
- $kwm[$g] = '/^(' . implode(')|(', $ma) . ')$/';
- }
- $kw[] = $kwm;
- } else {
- $kw[] = -1;
- $re[] = '(' . $block['start'] . ')';
- $ce[] = $this->_countSubpatterns($block['start']);
- $rd[] = $block['delimGroup'];
- $st[] = $states[$name];
- $sb[] = $block['remember'];
- }
- $in[] = $block['innerGroup'];
- }
- $re = implode('|', $re);
- $regs[-1] = '/' . $re . '/';
- $counts[-1] = $ce;
- $delim[-1] = $rd;
- $inner[-1] = $in;
- $stat[-1] = $st;
- $keywords[-1] = $kw;
- $subst[-1] = $sb;
-
- foreach ($syntax['blocks'] as $ablock) {
- if ($ablock['type'] != 'region') {
- continue;
- }
- $end[] = '/' . $ablock['end'] . '/';
- $re = array();
- $ce = array();
- $rd = array();
- $in = array();
- $st = array();
- $kw = array();
- $pc = array();
- $sb = array();
- foreach ((array)@$ablock['lookfor'] as $name) {
- $block = $syntax['blocks'][$name];
- if (isset($block['partClass'])) {
- $pc[] = $block['partClass'];
- } else {
- $pc[] = null;
- }
- if ($block['type'] == 'block') {
- $kwm = array();;
- $re[] = '(' . $block['match'] . ')';
- $ce[] = $this->_countSubpatterns($block['match']);
- $rd[] = '';
- $sb[] = false;
- $st[] = -1;
- foreach ($syntax['keywords'] as $kwname => $kwgroup) {
- if ($kwgroup['inherits'] != $name) {
- continue;
- }
- $gre = implode('|', array_keys($kwgroup['match']));
- if (!$kwgroup['case']) {
- $gre = '(?i)' . $gre;
- }
- $kwm[$kwname][] = $gre;
- $kwmap[$kwname] = $kwgroup['innerGroup'];
- }
- foreach ($kwm as $g => $ma) {
- $kwm[$g] = '/^(' . implode(')|(', $ma) . ')$/';
- }
- $kw[] = $kwm;
- } else {
- $sb[] = $block['remember'];
- $kw[] = -1;
- $re[] = '(' . $block['start'] . ')';
- $ce[] = $this->_countSubpatterns($block['start']);
- $rd[] = $block['delimGroup'];
- $st[] = $states[$name];
- }
- $in[] = $block['innerGroup'];
- }
- $re = implode('|', $re);
- $regs[] = '/' . $re . '/';
- $counts[] = $ce;
- $delim[] = $rd;
- $inner[] = $in;
- $stat[] = $st;
- $keywords[] = $kw;
- $parts[] = $pc;
- $subst[] = $sb;
- }
-
-
- $this->_code .= "\n \$this->_regs = " . $this->_exportArray($regs);
- $this->_code .= ";\n \$this->_counts = " .$this->_exportArray($counts);
- $this->_code .= ";\n \$this->_delim = " .$this->_exportArray($delim);
- $this->_code .= ";\n \$this->_inner = " .$this->_exportArray($inner);
- $this->_code .= ";\n \$this->_end = " .$this->_exportArray($end);
- $this->_code .= ";\n \$this->_states = " .$this->_exportArray($stat);
- $this->_code .= ";\n \$this->_keywords = " .$this->_exportArray($keywords);
- $this->_code .= ";\n \$this->_parts = " .$this->_exportArray($parts);
- $this->_code .= ";\n \$this->_subst = " .$this->_exportArray($subst);
- $this->_code .= ";\n \$this->_conditions = " .$this->_exportArray($conditions);
- $this->_code .= ";\n \$this->_kwmap = " .$this->_exportArray($kwmap);
- $this->_code .= ";\n \$this->_defClass = '" .$this->_defClass . '\'';
- $this->_code .= <<<CODE
-;
- \$this->_checkDefines();
- }
-
-}
-CODE;
-}
-
-// }}}
-}
-
-
-/*
-* Local variables:
-* tab-width: 4
-* c-basic-offset: 4
-* c-hanging-comment-ender-p: nil
-* End:
-*/
-
-?>
diff --git a/library/Text_Highlighter/Text/Highlighter/HTML.php b/library/Text_Highlighter/Text/Highlighter/HTML.php
deleted file mode 100644
index 14d0a783f..000000000
--- a/library/Text_Highlighter/Text/Highlighter/HTML.php
+++ /dev/null
@@ -1,234 +0,0 @@
-<?php
-/**
- * Auto-generated class. HTML syntax highlighting
- *
- * PHP version 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @link http://pear.php.net/package/Text_Highlighter
- * @category Text
- * @package Text_Highlighter
- * @version generated from: : html.xml,v 1.1 2007/06/03 02:35:28 ssttoo Exp
- * @author Andrey Demenev <demenev@gmail.com>
- *
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter.php';
-
-/**
- * Auto-generated class. HTML syntax highlighting
- *
- * @author Andrey Demenev <demenev@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: @package_version@
- * @link http://pear.php.net/package/Text_Highlighter
- */
-class Text_Highlighter_HTML extends Text_Highlighter
-{
- var $_language = 'html';
-
- /**
- * PHP4 Compatible Constructor
- *
- * @param array $options
- * @access public
- */
- function Text_Highlighter_HTML($options=array())
- {
- $this->__construct($options);
- }
-
-
- /**
- * Constructor
- *
- * @param array $options
- * @access public
- */
- function __construct($options=array())
- {
-
- $this->_options = $options;
- $this->_regs = array (
- -1 => '/((?i)\\<!--)|((?i)\\<[\\?\\/]?)|((?i)(&)[\\w\\-\\.]+;)/',
- 0 => '//',
- 1 => '/((?i)(?<=[\\<\\/?])[\\w\\-\\:]+)|((?i)[\\w\\-\\:]+)|((?i)")/',
- 2 => '/((?i)(&)[\\w\\-\\.]+;)/',
- );
- $this->_counts = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 1,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- ),
- 2 =>
- array (
- 0 => 1,
- ),
- );
- $this->_delim = array (
- -1 =>
- array (
- 0 => 'comment',
- 1 => 'brackets',
- 2 => '',
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => '',
- 1 => '',
- 2 => 'quotes',
- ),
- 2 =>
- array (
- 0 => '',
- ),
- );
- $this->_inner = array (
- -1 =>
- array (
- 0 => 'comment',
- 1 => 'code',
- 2 => 'special',
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => 'reserved',
- 1 => 'var',
- 2 => 'string',
- ),
- 2 =>
- array (
- 0 => 'special',
- ),
- );
- $this->_end = array (
- 0 => '/(?i)--\\>/',
- 1 => '/(?i)[\\/\\?]?\\>/',
- 2 => '/(?i)"/',
- );
- $this->_states = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => -1,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => 2,
- ),
- 2 =>
- array (
- 0 => -1,
- ),
- );
- $this->_keywords = array (
- -1 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 =>
- array (
- ),
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 => -1,
- ),
- 2 =>
- array (
- 0 =>
- array (
- ),
- ),
- );
- $this->_parts = array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- ),
- 2 =>
- array (
- 0 => NULL,
- ),
- );
- $this->_subst = array (
- -1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- ),
- 2 =>
- array (
- 0 => false,
- ),
- );
- $this->_conditions = array (
- );
- $this->_kwmap = array (
- );
- $this->_defClass = 'code';
- $this->_checkDefines();
- }
-
-} \ No newline at end of file
diff --git a/library/Text_Highlighter/Text/Highlighter/JAVA.php b/library/Text_Highlighter/Text/Highlighter/JAVA.php
deleted file mode 100644
index 46c0b8851..000000000
--- a/library/Text_Highlighter/Text/Highlighter/JAVA.php
+++ /dev/null
@@ -1,802 +0,0 @@
-<?php
-/**
- * Auto-generated class. JAVA syntax highlighting
- *
- * PHP version 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @link http://pear.php.net/package/Text_Highlighter
- * @category Text
- * @package Text_Highlighter
- * @version generated from: : java.xml,v 1.1 2007/06/03 02:35:28 ssttoo Exp
- * @author Andrey Demenev <demenev@gmail.com>
- *
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter.php';
-
-/**
- * Auto-generated class. JAVA syntax highlighting
- *
- * @author Andrey Demenev <demenev@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: @package_version@
- * @link http://pear.php.net/package/Text_Highlighter
- */
-class Text_Highlighter_JAVA extends Text_Highlighter
-{
- var $_language = 'java';
-
- /**
- * PHP4 Compatible Constructor
- *
- * @param array $options
- * @access public
- */
- function Text_Highlighter_JAVA($options=array())
- {
- $this->__construct($options);
- }
-
-
- /**
- * Constructor
- *
- * @param array $options
- * @access public
- */
- function __construct($options=array())
- {
-
- $this->_options = $options;
- $this->_regs = array (
- -1 => '/((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)\\/\\*)|((?i)")|((?i)\')|((?i)\\/\\/)|((?i)[a-z_]\\w*)|((?i)0[xX][\\da-f]+)|((?i)\\d\\d*|\\b0\\b)|((?i)0[0-7]+)|((?i)(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?i)((\\d+|((\\d*\\.\\d+)|(\\d+\\.\\d*)))[eE][+-]?\\d+))/',
- 0 => '/((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)\\/\\*)|((?i)")|((?i)\')|((?i)\\/\\/)|((?i)[a-z_]\\w*)|((?i)0[xX][\\da-f]+)|((?i)\\d\\d*|\\b0\\b)|((?i)0[0-7]+)|((?i)(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?i)((\\d+|((\\d*\\.\\d+)|(\\d+\\.\\d*)))[eE][+-]?\\d+))/',
- 1 => '/((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)\\/\\*)|((?i)")|((?i)\')|((?i)\\/\\/)|((?i)[a-z_]\\w*)|((?i)0[xX][\\da-f]+)|((?i)\\d\\d*|\\b0\\b)|((?i)0[0-7]+)|((?i)(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?i)((\\d+|((\\d*\\.\\d+)|(\\d+\\.\\d*)))[eE][+-]?\\d+))/',
- 2 => '/((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)\\/\\*)|((?i)")|((?i)\')|((?i)\\/\\/)|((?i)[a-z_]\\w*)|((?i)0[xX][\\da-f]+)|((?i)\\d\\d*|\\b0\\b)|((?i)0[0-7]+)|((?i)(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?i)((\\d+|((\\d*\\.\\d+)|(\\d+\\.\\d*)))[eE][+-]?\\d+))/',
- 3 => '/((?i)\\s@\\w+\\s)|((?i)((https?|ftp):\\/\\/[\\w\\?\\.\\-\\&=\\/%+]+)|(^|[\\s,!?])www\\.\\w+\\.\\w+[\\w\\?\\.\\&=\\/%+]*)|((?i)\\w+[\\.\\w\\-]+@(\\w+[\\.\\w\\-])+)|((?i)\\bnote:)|((?i)\\$\\w+\\s*:.*\\$)/',
- 4 => '/((?i)\\\\[\\\\"\'`tnr\\$\\{])/',
- 5 => '/((?i)\\\\.)/',
- 6 => '/((?i)\\s@\\w+\\s)|((?i)((https?|ftp):\\/\\/[\\w\\?\\.\\-\\&=\\/%+]+)|(^|[\\s,!?])www\\.\\w+\\.\\w+[\\w\\?\\.\\&=\\/%+]*)|((?i)\\w+[\\.\\w\\-]+@(\\w+[\\.\\w\\-])+)|((?i)\\bnote:)|((?i)\\$\\w+\\s*:.*\\$)/',
- );
- $this->_counts = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 0,
- 9 => 0,
- 10 => 0,
- 11 => 2,
- 12 => 5,
- ),
- 0 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 0,
- 9 => 0,
- 10 => 0,
- 11 => 2,
- 12 => 5,
- ),
- 1 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 0,
- 9 => 0,
- 10 => 0,
- 11 => 2,
- 12 => 5,
- ),
- 2 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 0,
- 9 => 0,
- 10 => 0,
- 11 => 2,
- 12 => 5,
- ),
- 3 =>
- array (
- 0 => 0,
- 1 => 3,
- 2 => 1,
- 3 => 0,
- 4 => 0,
- ),
- 4 =>
- array (
- 0 => 0,
- ),
- 5 =>
- array (
- 0 => 0,
- ),
- 6 =>
- array (
- 0 => 0,
- 1 => 3,
- 2 => 1,
- 3 => 0,
- 4 => 0,
- ),
- );
- $this->_delim = array (
- -1 =>
- array (
- 0 => 'brackets',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'comment',
- 4 => 'quotes',
- 5 => 'quotes',
- 6 => 'comment',
- 7 => '',
- 8 => '',
- 9 => '',
- 10 => '',
- 11 => '',
- 12 => '',
- ),
- 0 =>
- array (
- 0 => 'brackets',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'comment',
- 4 => 'quotes',
- 5 => 'quotes',
- 6 => 'comment',
- 7 => '',
- 8 => '',
- 9 => '',
- 10 => '',
- 11 => '',
- 12 => '',
- ),
- 1 =>
- array (
- 0 => 'brackets',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'comment',
- 4 => 'quotes',
- 5 => 'quotes',
- 6 => 'comment',
- 7 => '',
- 8 => '',
- 9 => '',
- 10 => '',
- 11 => '',
- 12 => '',
- ),
- 2 =>
- array (
- 0 => 'brackets',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'comment',
- 4 => 'quotes',
- 5 => 'quotes',
- 6 => 'comment',
- 7 => '',
- 8 => '',
- 9 => '',
- 10 => '',
- 11 => '',
- 12 => '',
- ),
- 3 =>
- array (
- 0 => '',
- 1 => '',
- 2 => '',
- 3 => '',
- 4 => '',
- ),
- 4 =>
- array (
- 0 => '',
- ),
- 5 =>
- array (
- 0 => '',
- ),
- 6 =>
- array (
- 0 => '',
- 1 => '',
- 2 => '',
- 3 => '',
- 4 => '',
- ),
- );
- $this->_inner = array (
- -1 =>
- array (
- 0 => 'code',
- 1 => 'code',
- 2 => 'code',
- 3 => 'comment',
- 4 => 'string',
- 5 => 'string',
- 6 => 'comment',
- 7 => 'identifier',
- 8 => 'number',
- 9 => 'number',
- 10 => 'number',
- 11 => 'number',
- 12 => 'number',
- ),
- 0 =>
- array (
- 0 => 'code',
- 1 => 'code',
- 2 => 'code',
- 3 => 'comment',
- 4 => 'string',
- 5 => 'string',
- 6 => 'comment',
- 7 => 'identifier',
- 8 => 'number',
- 9 => 'number',
- 10 => 'number',
- 11 => 'number',
- 12 => 'number',
- ),
- 1 =>
- array (
- 0 => 'code',
- 1 => 'code',
- 2 => 'code',
- 3 => 'comment',
- 4 => 'string',
- 5 => 'string',
- 6 => 'comment',
- 7 => 'identifier',
- 8 => 'number',
- 9 => 'number',
- 10 => 'number',
- 11 => 'number',
- 12 => 'number',
- ),
- 2 =>
- array (
- 0 => 'code',
- 1 => 'code',
- 2 => 'code',
- 3 => 'comment',
- 4 => 'string',
- 5 => 'string',
- 6 => 'comment',
- 7 => 'identifier',
- 8 => 'number',
- 9 => 'number',
- 10 => 'number',
- 11 => 'number',
- 12 => 'number',
- ),
- 3 =>
- array (
- 0 => 'inlinedoc',
- 1 => 'url',
- 2 => 'url',
- 3 => 'inlinedoc',
- 4 => 'inlinedoc',
- ),
- 4 =>
- array (
- 0 => 'special',
- ),
- 5 =>
- array (
- 0 => 'special',
- ),
- 6 =>
- array (
- 0 => 'inlinedoc',
- 1 => 'url',
- 2 => 'url',
- 3 => 'inlinedoc',
- 4 => 'inlinedoc',
- ),
- );
- $this->_end = array (
- 0 => '/(?i)\\}/',
- 1 => '/(?i)\\)/',
- 2 => '/(?i)\\]/',
- 3 => '/(?i)\\*\\//',
- 4 => '/(?i)"/',
- 5 => '/(?i)\'/',
- 6 => '/(?mi)$/',
- );
- $this->_states = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => 4,
- 5 => 5,
- 6 => 6,
- 7 => -1,
- 8 => -1,
- 9 => -1,
- 10 => -1,
- 11 => -1,
- 12 => -1,
- ),
- 0 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => 4,
- 5 => 5,
- 6 => 6,
- 7 => -1,
- 8 => -1,
- 9 => -1,
- 10 => -1,
- 11 => -1,
- 12 => -1,
- ),
- 1 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => 4,
- 5 => 5,
- 6 => 6,
- 7 => -1,
- 8 => -1,
- 9 => -1,
- 10 => -1,
- 11 => -1,
- 12 => -1,
- ),
- 2 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => 4,
- 5 => 5,
- 6 => 6,
- 7 => -1,
- 8 => -1,
- 9 => -1,
- 10 => -1,
- 11 => -1,
- 12 => -1,
- ),
- 3 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- ),
- 4 =>
- array (
- 0 => -1,
- ),
- 5 =>
- array (
- 0 => -1,
- ),
- 6 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- ),
- );
- $this->_keywords = array (
- -1 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 =>
- array (
- 'types' => '/^(boolean|byte|char|const|double|final|float|int|long|short|static|void)$/',
- 'reserved' => '/^(import|package|abstract|break|case|catch|class|continue|default|do|else|extends|false|finally|for|goto|if|implements|instanceof|interface|native|new|null|private|protected|public|return|super|strictfp|switch|synchronized|this|throws|throw|transient|true|try|volatile|while)$/',
- 'builtin' => '/^(AbstractAction|AbstractBorder|AbstractButton|AbstractCellEditor|AbstractCollection|AbstractColorChooserPanel|AbstractDocument|AbstractInterruptibleChannel|AbstractLayoutCache|AbstractList|AbstractListModel|AbstractMap|AbstractMethodError|AbstractPreferences|AbstractSelectableChannel|AbstractSelectionKey|AbstractSelector|AbstractSequentialList|AbstractSet|AbstractSpinnerModel|AbstractTableModel|AbstractUndoableEdit|AbstractWriter|AccessControlContext|AccessControlException|AccessController|AccessException|Accessible|AccessibleAction|AccessibleBundle|AccessibleComponent|AccessibleContext|AccessibleEditableText|AccessibleExtendedComponent|AccessibleExtendedTable|AccessibleHyperlink|AccessibleHypertext|AccessibleIcon|AccessibleKeyBinding|AccessibleObject|AccessibleRelation|AccessibleRelationSet|AccessibleResourceBundle|AccessibleRole|AccessibleSelection|AccessibleState|AccessibleStateSet|AccessibleTable|AccessibleTableModelChange|AccessibleText|AccessibleValue|AccountExpiredException|Acl|AclEntry|AclNotFoundException|Action|ActionEvent|ActionListener|ActionMap|ActionMapUIResource|Activatable|ActivateFailedException|ActivationDesc|ActivationException|ActivationGroup|ActivationGroup_Stub|ActivationGroupDesc|ActivationGroupID|ActivationID|ActivationInstantiator|ActivationMonitor|ActivationSystem|Activator|ActiveEvent|AdapterActivator|AdapterActivatorOperations|AdapterAlreadyExists|AdapterAlreadyExistsHelper|AdapterInactive|AdapterInactiveHelper|AdapterNonExistent|AdapterNonExistentHelper|AddressHelper|Adjustable|AdjustmentEvent|AdjustmentListener|Adler32|AffineTransform|AffineTransformOp|AlgorithmParameterGenerator|AlgorithmParameterGeneratorSpi|AlgorithmParameters|AlgorithmParameterSpec|AlgorithmParametersSpi|AllPermission|AlphaComposite|AlreadyBound|AlreadyBoundException|AlreadyBoundHelper|AlreadyBoundHolder|AlreadyConnectedException|AncestorEvent|AncestorListener|Annotation|Any|AnyHolder|AnySeqHelper|AnySeqHolder|AppConfigurationEntry|Applet|AppletContext|AppletInitializer|AppletStub|ApplicationException|Arc2D|Area|AreaAveragingScaleFilter|ARG_IN|ARG_INOUT|ARG_OUT|ArithmeticException|Array|ArrayIndexOutOfBoundsException|ArrayList|Arrays|ArrayStoreException|AssertionError|AsyncBoxView|AsynchronousCloseException|Attr|Attribute|AttributedCharacterIterator|AttributedString|AttributeException|AttributeInUseException|AttributeList|AttributeListImpl|AttributeModificationException|Attributes|AttributeSet|AttributeSetUtilities|AttributesImpl|AudioClip|AudioFileFormat|AudioFileReader|AudioFileWriter|AudioFormat|AudioInputStream|AudioPermission|AudioSystem|AuthenticationException|AuthenticationNotSupportedException|Authenticator|AuthPermission|Autoscroll|AWTError|AWTEvent|AWTEventListener|AWTEventListenerProxy|AWTEventMulticaster|AWTException|AWTKeyStroke|AWTPermission|BackingStoreException|BAD_CONTEXT|BAD_INV_ORDER|BAD_OPERATION|BAD_PARAM|BAD_POLICY|BAD_POLICY_TYPE|BAD_POLICY_VALUE|BAD_TYPECODE|BadKind|BadLocationException|BadPaddingException|BandCombineOp|BandedSampleModel|BasicArrowButton|BasicAttribute|BasicAttributes|BasicBorders|BasicButtonListener|BasicButtonUI|BasicCheckBoxMenuItemUI|BasicCheckBoxUI|BasicColorChooserUI|BasicComboBoxEditor|BasicComboBoxRenderer|BasicComboBoxUI|BasicComboPopup|BasicDesktopIconUI|BasicDesktopPaneUI|BasicDirectoryModel|BasicEditorPaneUI|BasicFileChooserUI|BasicFormattedTextFieldUI|BasicGraphicsUtils|BasicHTML|BasicIconFactory|BasicInternalFrameTitlePane|BasicInternalFrameUI|BasicLabelUI|BasicListUI|BasicLookAndFeel|BasicMenuBarUI|BasicMenuItemUI|BasicMenuUI|BasicOptionPaneUI|BasicPanelUI|BasicPasswordFieldUI|BasicPermission|BasicPopupMenuSeparatorUI|BasicPopupMenuUI|BasicProgressBarUI|BasicRadioButtonMenuItemUI|BasicRadioButtonUI|BasicRootPaneUI|BasicScrollBarUI|BasicScrollPaneUI|BasicSeparatorUI|BasicSliderUI|BasicSpinnerUI|BasicSplitPaneDivider|BasicSplitPaneUI|BasicStroke|BasicTabbedPaneUI|BasicTableHeaderUI|BasicTableUI|BasicTextAreaUI|BasicTextFieldUI|BasicTextPaneUI|BasicTextUI|BasicToggleButtonUI|BasicToolBarSeparatorUI|BasicToolBarUI|BasicToolTipUI|BasicTreeUI|BasicViewportUI|BatchUpdateException|BeanContext|BeanContextChild|BeanContextChildComponentProxy|BeanContextChildSupport|BeanContextContainerProxy|BeanContextEvent|BeanContextMembershipEvent|BeanContextMembershipListener|BeanContextProxy|BeanContextServiceAvailableEvent|BeanContextServiceProvider|BeanContextServiceProviderBeanInfo|BeanContextServiceRevokedEvent|BeanContextServiceRevokedListener|BeanContextServices|BeanContextServicesListener|BeanContextServicesSupport|BeanContextSupport|BeanDescriptor|BeanInfo|Beans|BevelBorder|Bidi|BigDecimal|BigInteger|BinaryRefAddr|BindException|Binding|BindingHelper|BindingHolder|BindingIterator|BindingIteratorHelper|BindingIteratorHolder|BindingIteratorOperations|BindingIteratorPOA|BindingListHelper|BindingListHolder|BindingType|BindingTypeHelper|BindingTypeHolder|BitSet|Blob|BlockView|Book|Boolean|BooleanControl|BooleanHolder|BooleanSeqHelper|BooleanSeqHolder|Border|BorderFactory|BorderLayout|BorderUIResource|BoundedRangeModel|Bounds|Box|BoxedValueHelper|BoxLayout|BoxView|BreakIterator|Buffer|BufferCapabilities|BufferedImage|BufferedImageFilter|BufferedImageOp|BufferedInputStream|BufferedOutputStream|BufferedReader|BufferedWriter|BufferOverflowException|BufferStrategy|BufferUnderflowException|Button|ButtonGroup|ButtonModel|ButtonUI|Byte|ByteArrayInputStream|ByteArrayOutputStream|ByteBuffer|ByteChannel|ByteHolder|ByteLookupTable|ByteOrder|Calendar|CallableStatement|Callback|CallbackHandler|CancelablePrintJob|CancelledKeyException|CannotProceed|CannotProceedException|CannotProceedHelper|CannotProceedHolder|CannotRedoException|CannotUndoException|Canvas|CardLayout|Caret|CaretEvent|CaretListener|CDATASection|CellEditor|CellEditorListener|CellRendererPane|Certificate|CertificateEncodingException|CertificateException|CertificateExpiredException|CertificateFactory|CertificateFactorySpi|CertificateNotYetValidException|CertificateParsingException|CertPath|CertPathBuilder|CertPathBuilderException|CertPathBuilderResult|CertPathBuilderSpi|CertPathParameters|CertPathValidator|CertPathValidatorException|CertPathValidatorResult|CertPathValidatorSpi|CertSelector|CertStore|CertStoreException|CertStoreParameters|CertStoreSpi|ChangedCharSetException|ChangeEvent|ChangeListener|Channel|ChannelBinding|Channels|Character|CharacterCodingException|CharacterData|CharacterIterator|CharArrayReader|CharArrayWriter|CharBuffer|CharConversionException|CharHolder|CharSeqHelper|CharSeqHolder|CharSequence|Charset|CharsetDecoder|CharsetEncoder|CharsetProvider|Checkbox|CheckboxGroup|CheckboxMenuItem|CheckedInputStream|CheckedOutputStream|Checksum|Choice|ChoiceCallback|ChoiceFormat|Chromaticity|Cipher|CipherInputStream|CipherOutputStream|CipherSpi|Class|ClassCastException|ClassCircularityError|ClassDesc|ClassFormatError|ClassLoader|ClassNotFoundException|ClientRequestInfo|ClientRequestInfoOperations|ClientRequestInterceptor|ClientRequestInterceptorOperations|Clip|Clipboard|ClipboardOwner|Clob|Cloneable|CloneNotSupportedException|ClosedByInterruptException|ClosedChannelException|ClosedSelectorException|CMMException|Codec|CodecFactory|CodecFactoryHelper|CodecFactoryOperations|CodecOperations|CoderMalfunctionError|CoderResult|CodeSets|CodeSource|CodingErrorAction|CollationElementIterator|CollationKey|Collator|Collection|CollectionCertStoreParameters|Collections|Color|ColorChooserComponentFactory|ColorChooserUI|ColorConvertOp|ColorModel|ColorSelectionModel|ColorSpace|ColorSupported|ColorUIResource|ComboBoxEditor|ComboBoxModel|ComboBoxUI|ComboPopup|COMM_FAILURE|Comment|CommunicationException|Comparable|Comparator|Compiler|CompletionStatus|CompletionStatusHelper|Component|ComponentAdapter|ComponentColorModel|ComponentEvent|ComponentIdHelper|ComponentInputMap|ComponentInputMapUIResource|ComponentListener|ComponentOrientation|ComponentSampleModel|ComponentUI|ComponentView|Composite|CompositeContext|CompositeName|CompositeView|CompoundBorder|CompoundControl|CompoundEdit|CompoundName|Compression|ConcurrentModificationException|Configuration|ConfigurationException|ConfirmationCallback|ConnectException|ConnectIOException|Connection|ConnectionEvent|ConnectionEventListener|ConnectionPendingException|ConnectionPoolDataSource|ConsoleHandler|Constructor|Container|ContainerAdapter|ContainerEvent|ContainerListener|ContainerOrderFocusTraversalPolicy|ContentHandler|ContentHandlerFactory|ContentModel|Context|ContextList|ContextNotEmptyException|ContextualRenderedImageFactory|Control|ControlFactory|ControllerEventListener|ConvolveOp|CookieHolder|Copies|CopiesSupported|CRC32|CredentialExpiredException|CRL|CRLException|CRLSelector|CropImageFilter|CSS|CTX_RESTRICT_SCOPE|CubicCurve2D|Currency|Current|CurrentHelper|CurrentHolder|CurrentOperations|Cursor|Customizer|CustomMarshal|CustomValue|DATA_CONVERSION|DatabaseMetaData|DataBuffer|DataBufferByte|DataBufferDouble|DataBufferFloat|DataBufferInt|DataBufferShort|DataBufferUShort|DataFlavor|DataFormatException|DatagramChannel|DatagramPacket|DatagramSocket|DatagramSocketImpl|DatagramSocketImplFactory|DataInput|DataInputStream|DataLine|DataOutput|DataOutputStream|DataSource|DataTruncation|Date|DateFormat|DateFormatSymbols|DateFormatter|DateTimeAtCompleted|DateTimeAtCreation|DateTimeAtProcessing|DateTimeSyntax|DebugGraphics|DecimalFormat|DecimalFormatSymbols|DeclHandler|DefaultBoundedRangeModel|DefaultButtonModel|DefaultCaret|DefaultCellEditor|DefaultColorSelectionModel|DefaultComboBoxModel|DefaultDesktopManager|DefaultEditorKit|DefaultFocusManager|DefaultFocusTraversalPolicy|DefaultFormatter|DefaultFormatterFactory|DefaultHandler|DefaultHighlighter|DefaultKeyboardFocusManager|DefaultListCellRenderer|DefaultListModel|DefaultListSelectionModel|DefaultMenuLayout|DefaultMetalTheme|DefaultMutableTreeNode|DefaultPersistenceDelegate|DefaultSingleSelectionModel|DefaultStyledDocument|DefaultTableCellRenderer|DefaultTableColumnModel|DefaultTableModel|DefaultTextUI|DefaultTreeCellEditor|DefaultTreeCellRenderer|DefaultTreeModel|DefaultTreeSelectionModel|DefinitionKind|DefinitionKindHelper|Deflater|DeflaterOutputStream|Delegate|DelegationPermission|DESedeKeySpec|DesignMode|DESKeySpec|DesktopIconUI|DesktopManager|DesktopPaneUI|Destination|Destroyable|DestroyFailedException|DGC|DHGenParameterSpec|DHKey|DHParameterSpec|DHPrivateKey|DHPrivateKeySpec|DHPublicKey|DHPublicKeySpec|Dialog|Dictionary|DigestException|DigestInputStream|DigestOutputStream|Dimension|Dimension2D|DimensionUIResource|DirContext|DirectColorModel|DirectoryManager|DirObjectFactory|DirStateFactory|DisplayMode|DnDConstants|Doc|DocAttribute|DocAttributeSet|DocFlavor|DocPrintJob|Document|DocumentBuilder|DocumentBuilderFactory|DocumentEvent|DocumentFilter|DocumentFragment|DocumentHandler|DocumentListener|DocumentName|DocumentParser|DocumentType|DomainCombiner|DomainManager|DomainManagerOperations|DOMException|DOMImplementation|DOMLocator|DOMResult|DOMSource|Double|DoubleBuffer|DoubleHolder|DoubleSeqHelper|DoubleSeqHolder|DragGestureEvent|DragGestureListener|DragGestureRecognizer|DragSource|DragSourceAdapter|DragSourceContext|DragSourceDragEvent|DragSourceDropEvent|DragSourceEvent|DragSourceListener|DragSourceMotionListener|Driver|DriverManager|DriverPropertyInfo|DropTarget|DropTargetAdapter|DropTargetContext|DropTargetDragEvent|DropTargetDropEvent|DropTargetEvent|DropTargetListener|DSAKey|DSAKeyPairGenerator|DSAParameterSpec|DSAParams|DSAPrivateKey|DSAPrivateKeySpec|DSAPublicKey|DSAPublicKeySpec|DTD|DTDConstants|DTDHandler|DuplicateName|DuplicateNameHelper|DynamicImplementation|DynAny|DynAnyFactory|DynAnyFactoryHelper|DynAnyFactoryOperations|DynAnyHelper|DynAnyOperations|DynAnySeqHelper|DynArray|DynArrayHelper|DynArrayOperations|DynEnum|DynEnumHelper|DynEnumOperations|DynFixed|DynFixedHelper|DynFixedOperations|DynSequence|DynSequenceHelper|DynSequenceOperations|DynStruct|DynStructHelper|DynStructOperations|DynUnion|DynUnionHelper|DynUnionOperations|DynValue|DynValueBox|DynValueBoxOperations|DynValueCommon|DynValueCommonOperations|DynValueHelper|DynValueOperations|EditorKit|Element|ElementIterator|Ellipse2D|EmptyBorder|EmptyStackException|EncodedKeySpec|Encoder|Encoding|ENCODING_CDR_ENCAPS|EncryptedPrivateKeyInfo|Entity|EntityReference|EntityResolver|EnumControl|Enumeration|EnumSyntax|Environment|EOFException|Error|ErrorHandler|ErrorListener|ErrorManager|EtchedBorder|Event|EventContext|EventDirContext|EventHandler|EventListener|EventListenerList|EventListenerProxy|EventObject|EventQueue|EventSetDescriptor|Exception|ExceptionInInitializerError|ExceptionList|ExceptionListener|ExemptionMechanism|ExemptionMechanismException|ExemptionMechanismSpi|ExpandVetoException|ExportException|Expression|ExtendedRequest|ExtendedResponse|Externalizable|FactoryConfigurationError|FailedLoginException|FeatureDescriptor|Fidelity|Field|FieldNameHelper|FieldPosition|FieldView|File|FileCacheImageInputStream|FileCacheImageOutputStream|FileChannel|FileChooserUI|FileDescriptor|FileDialog|FileFilter|FileHandler|FileImageInputStream|FileImageOutputStream|FileInputStream|FileLock|FileLockInterruptionException|FilenameFilter|FileNameMap|FileNotFoundException|FileOutputStream|FilePermission|FileReader|FileSystemView|FileView|FileWriter|Filter|FilteredImageSource|FilterInputStream|FilterOutputStream|FilterReader|FilterWriter|Finishings|FixedHeightLayoutCache|FixedHolder|FlatteningPathIterator|FlavorException|FlavorMap|FlavorTable|Float|FloatBuffer|FloatControl|FloatHolder|FloatSeqHelper|FloatSeqHolder|FlowLayout|FlowView|FocusAdapter|FocusEvent|FocusListener|FocusManager|FocusTraversalPolicy|Font|FontFormatException|FontMetrics|FontRenderContext|FontUIResource|Format|FormatConversionProvider|FormatMismatch|FormatMismatchHelper|Formatter|FormView|ForwardRequest|ForwardRequestHelper|Frame|FREE_MEM|GapContent|GatheringByteChannel|GeneralPath|GeneralSecurityException|GlyphJustificationInfo|GlyphMetrics|GlyphVector|GlyphView|GradientPaint|GraphicAttribute|Graphics|Graphics2D|GraphicsConfigTemplate|GraphicsConfiguration|GraphicsDevice|GraphicsEnvironment|GrayFilter|GregorianCalendar|GridBagConstraints|GridBagLayout|GridLayout|Group|GSSContext|GSSCredential|GSSException|GSSManager|GSSName|Guard|GuardedObject|GZIPInputStream|GZIPOutputStream|Handler|HandlerBase|HandshakeCompletedEvent|HandshakeCompletedListener|HasControls|HashAttributeSet|HashDocAttributeSet|HashMap|HashPrintJobAttributeSet|HashPrintRequestAttributeSet|HashPrintServiceAttributeSet|HashSet|Hashtable|HeadlessException|HierarchyBoundsAdapter|HierarchyBoundsListener|HierarchyEvent|HierarchyListener|Highlighter|HostnameVerifier|HTML|HTMLDocument|HTMLEditorKit|HTMLFrameHyperlinkEvent|HTMLWriter|HttpsURLConnection|HttpURLConnection|HyperlinkEvent|HyperlinkListener|ICC_ColorSpace|ICC_Profile|ICC_ProfileGray|ICC_ProfileRGB|Icon|IconUIResource|IconView|ID_ASSIGNMENT_POLICY_ID|ID_UNIQUENESS_POLICY_ID|IdAssignmentPolicy|IdAssignmentPolicyOperations|IdAssignmentPolicyValue|IdentifierHelper|Identity|IdentityHashMap|IdentityScope|IDLEntity|IDLType|IDLTypeHelper|IDLTypeOperations|IdUniquenessPolicy|IdUniquenessPolicyOperations|IdUniquenessPolicyValue|IIOByteBuffer|IIOException|IIOImage|IIOInvalidTreeException|IIOMetadata|IIOMetadataController|IIOMetadataFormat|IIOMetadataFormatImpl|IIOMetadataNode|IIOParam|IIOParamController|IIOReadProgressListener|IIOReadUpdateListener|IIOReadWarningListener|IIORegistry|IIOServiceProvider|IIOWriteProgressListener|IIOWriteWarningListener|IllegalAccessError|IllegalAccessException|IllegalArgumentException|IllegalBlockingModeException|IllegalBlockSizeException|IllegalCharsetNameException|IllegalComponentStateException|IllegalMonitorStateException|IllegalPathStateException|IllegalSelectorException|IllegalStateException|IllegalThreadStateException|Image|ImageCapabilities|ImageConsumer|ImageFilter|ImageGraphicAttribute|ImageIcon|ImageInputStream|ImageInputStreamImpl|ImageInputStreamSpi|ImageIO|ImageObserver|ImageOutputStream|ImageOutputStreamImpl|ImageOutputStreamSpi|ImageProducer|ImageReader|ImageReaderSpi|ImageReaderWriterSpi|ImageReadParam|ImageTranscoder|ImageTranscoderSpi|ImageTypeSpecifier|ImageView|ImageWriteParam|ImageWriter|ImageWriterSpi|ImagingOpException|IMP_LIMIT|IMPLICIT_ACTIVATION_POLICY_ID|ImplicitActivationPolicy|ImplicitActivationPolicyOperations|ImplicitActivationPolicyValue|IncompatibleClassChangeError|InconsistentTypeCode|InconsistentTypeCodeHelper|IndexColorModel|IndexedPropertyDescriptor|IndexOutOfBoundsException|IndirectionException|Inet4Address|Inet6Address|InetAddress|InetSocketAddress|Inflater|InflaterInputStream|InheritableThreadLocal|InitialContext|InitialContextFactory|InitialContextFactoryBuilder|InitialDirContext|INITIALIZE|InitialLdapContext|InlineView|InputContext|InputEvent|InputMap|InputMapUIResource|InputMethod|InputMethodContext|InputMethodDescriptor|InputMethodEvent|InputMethodHighlight|InputMethodListener|InputMethodRequests|InputSource|InputStream|InputStreamReader|InputSubset|InputVerifier|Insets|InsetsUIResource|InstantiationError|InstantiationException|Instrument|InsufficientResourcesException|IntBuffer|Integer|IntegerSyntax|Interceptor|InterceptorOperations|INTERNAL|InternalError|InternalFrameAdapter|InternalFrameEvent|InternalFrameFocusTraversalPolicy|InternalFrameListener|InternalFrameUI|InternationalFormatter|InterruptedException|InterruptedIOException|InterruptedNamingException|InterruptibleChannel|INTF_REPOS|IntHolder|IntrospectionException|Introspector|INV_FLAG|INV_IDENT|INV_OBJREF|INV_POLICY|Invalid|INVALID_TRANSACTION|InvalidAddress|InvalidAddressHelper|InvalidAddressHolder|InvalidAlgorithmParameterException|InvalidAttributeIdentifierException|InvalidAttributesException|InvalidAttributeValueException|InvalidClassException|InvalidDnDOperationException|InvalidKeyException|InvalidKeySpecException|InvalidMarkException|InvalidMidiDataException|InvalidName|InvalidNameException|InvalidNameHelper|InvalidNameHolder|InvalidObjectException|InvalidParameterException|InvalidParameterSpecException|InvalidPolicy|InvalidPolicyHelper|InvalidPreferencesFormatException|InvalidSearchControlsException|InvalidSearchFilterException|InvalidSeq|InvalidSlot|InvalidSlotHelper|InvalidTransactionException|InvalidTypeForEncoding|InvalidTypeForEncodingHelper|InvalidValue|InvalidValueHelper|InvocationEvent|InvocationHandler|InvocationTargetException|InvokeHandler|IOException|IOR|IORHelper|IORHolder|IORInfo|IORInfoOperations|IORInterceptor|IORInterceptorOperations|IRObject|IRObjectOperations|IstringHelper|ItemEvent|ItemListener|ItemSelectable|Iterator|IvParameterSpec|JApplet|JarEntry|JarException|JarFile|JarInputStream|JarOutputStream|JarURLConnection|JButton|JCheckBox|JCheckBoxMenuItem|JColorChooser|JComboBox|JComponent|JDesktopPane|JDialog|JEditorPane|JFileChooser|JFormattedTextField|JFrame|JInternalFrame|JLabel|JLayeredPane|JList|JMenu|JMenuBar|JMenuItem|JobAttributes|JobHoldUntil|JobImpressions|JobImpressionsCompleted|JobImpressionsSupported|JobKOctets|JobKOctetsProcessed|JobKOctetsSupported|JobMediaSheets|JobMediaSheetsCompleted|JobMediaSheetsSupported|JobMessageFromOperator|JobName|JobOriginatingUserName|JobPriority|JobPrioritySupported|JobSheets|JobState|JobStateReason|JobStateReasons|JOptionPane|JPanel|JPasswordField|JPEGHuffmanTable|JPEGImageReadParam|JPEGImageWriteParam|JPEGQTable|JPopupMenu|JProgressBar|JRadioButton|JRadioButtonMenuItem|JRootPane|JScrollBar|JScrollPane|JSeparator|JSlider|JSpinner|JSplitPane|JTabbedPane|JTable|JTableHeader|JTextArea|JTextComponent|JTextField|JTextPane|JToggleButton|JToolBar|JToolTip|JTree|JViewport|JWindow|KerberosKey|KerberosPrincipal|KerberosTicket|Kernel|Key|KeyAdapter|KeyAgreement|KeyAgreementSpi|KeyboardFocusManager|KeyEvent|KeyEventDispatcher|KeyEventPostProcessor|KeyException|KeyFactory|KeyFactorySpi|KeyGenerator|KeyGeneratorSpi|KeyListener|KeyManagementException|KeyManager|KeyManagerFactory|KeyManagerFactorySpi|Keymap|KeyPair|KeyPairGenerator|KeyPairGeneratorSpi|KeySpec|KeyStore|KeyStoreException|KeyStoreSpi|KeyStroke|Label|LabelUI|LabelView|LanguageCallback|LastOwnerException|LayeredHighlighter|LayoutFocusTraversalPolicy|LayoutManager|LayoutManager2|LayoutQueue|LDAPCertStoreParameters|LdapContext|LdapReferralException|Lease|Level|LexicalHandler|LIFESPAN_POLICY_ID|LifespanPolicy|LifespanPolicyOperations|LifespanPolicyValue|LimitExceededException|Line|Line2D|LineBorder|LineBreakMeasurer|LineEvent|LineListener|LineMetrics|LineNumberInputStream|LineNumberReader|LineUnavailableException|LinkageError|LinkedHashMap|LinkedHashSet|LinkedList|LinkException|LinkLoopException|LinkRef|List|ListCellRenderer|ListDataEvent|ListDataListener|ListIterator|ListModel|ListResourceBundle|ListSelectionEvent|ListSelectionListener|ListSelectionModel|ListUI|ListView|LoaderHandler|Locale|LocalObject|LocateRegistry|LOCATION_FORWARD|Locator|LocatorImpl|Logger|LoggingPermission|LoginContext|LoginException|LoginModule|LogManager|LogRecord|LogStream|Long|LongBuffer|LongHolder|LongLongSeqHelper|LongLongSeqHolder|LongSeqHelper|LongSeqHolder|LookAndFeel|LookupOp|LookupTable|Mac|MacSpi|MalformedInputException|MalformedLinkException|MalformedURLException|ManagerFactoryParameters|Manifest|Map|MappedByteBuffer|MARSHAL|MarshalException|MarshalledObject|MaskFormatter|Matcher|Math|MatteBorder|Media|MediaName|MediaPrintableArea|MediaSize|MediaSizeName|MediaTracker|MediaTray|Member|MemoryCacheImageInputStream|MemoryCacheImageOutputStream|MemoryHandler|MemoryImageSource|Menu|MenuBar|MenuBarUI|MenuComponent|MenuContainer|MenuDragMouseEvent|MenuDragMouseListener|MenuElement|MenuEvent|MenuItem|MenuItemUI|MenuKeyEvent|MenuKeyListener|MenuListener|MenuSelectionManager|MenuShortcut|MessageDigest|MessageDigestSpi|MessageFormat|MessageProp|MetaEventListener|MetalBorders|MetalButtonUI|MetalCheckBoxIcon|MetalCheckBoxUI|MetalComboBoxButton|MetalComboBoxEditor|MetalComboBoxIcon|MetalComboBoxUI|MetalDesktopIconUI|MetalFileChooserUI|MetalIconFactory|MetalInternalFrameTitlePane|MetalInternalFrameUI|MetalLabelUI|MetalLookAndFeel|MetalPopupMenuSeparatorUI|MetalProgressBarUI|MetalRadioButtonUI|MetalRootPaneUI|MetalScrollBarUI|MetalScrollButton|MetalScrollPaneUI|MetalSeparatorUI|MetalSliderUI|MetalSplitPaneUI|MetalTabbedPaneUI|MetalTextFieldUI|MetalTheme|MetalToggleButtonUI|MetalToolBarUI|MetalToolTipUI|MetalTreeUI|MetaMessage|Method|MethodDescriptor|MidiChannel|MidiDevice|MidiDeviceProvider|MidiEvent|MidiFileFormat|MidiFileReader|MidiFileWriter|MidiMessage|MidiSystem|MidiUnavailableException|MimeTypeParseException|MinimalHTMLWriter|MissingResourceException|Mixer|MixerProvider|ModificationItem|Modifier|MouseAdapter|MouseDragGestureRecognizer|MouseEvent|MouseInputAdapter|MouseInputListener|MouseListener|MouseMotionAdapter|MouseMotionListener|MouseWheelEvent|MouseWheelListener|MultiButtonUI|MulticastSocket|MultiColorChooserUI|MultiComboBoxUI|MultiDesktopIconUI|MultiDesktopPaneUI|MultiDoc|MultiDocPrintJob|MultiDocPrintService|MultiFileChooserUI|MultiInternalFrameUI|MultiLabelUI|MultiListUI|MultiLookAndFeel|MultiMenuBarUI|MultiMenuItemUI|MultiOptionPaneUI|MultiPanelUI|MultiPixelPackedSampleModel|MultipleComponentProfileHelper|MultipleComponentProfileHolder|MultipleDocumentHandling|MultipleMaster|MultiPopupMenuUI|MultiProgressBarUI|MultiRootPaneUI|MultiScrollBarUI|MultiScrollPaneUI|MultiSeparatorUI|MultiSliderUI|MultiSpinnerUI|MultiSplitPaneUI|MultiTabbedPaneUI|MultiTableHeaderUI|MultiTableUI|MultiTextUI|MultiToolBarUI|MultiToolTipUI|MultiTreeUI|MultiViewportUI|MutableAttributeSet|MutableComboBoxModel|MutableTreeNode|Name|NameAlreadyBoundException|NameCallback|NameClassPair|NameComponent|NameComponentHelper|NameComponentHolder|NamedNodeMap|NamedValue|NameDynAnyPair|NameDynAnyPairHelper|NameDynAnyPairSeqHelper|NameHelper|NameHolder|NameNotFoundException|NameParser|NamespaceChangeListener|NamespaceSupport|NameValuePair|NameValuePairHelper|NameValuePairSeqHelper|Naming|NamingContext|NamingContextExt|NamingContextExtHelper|NamingContextExtHolder|NamingContextExtOperations|NamingContextExtPOA|NamingContextHelper|NamingContextHolder|NamingContextOperations|NamingContextPOA|NamingEnumeration|NamingEvent|NamingException|NamingExceptionEvent|NamingListener|NamingManager|NamingSecurityException|NavigationFilter|NegativeArraySizeException|NetPermission|NetworkInterface|NO_IMPLEMENT|NO_MEMORY|NO_PERMISSION|NO_RESOURCES|NO_RESPONSE|NoClassDefFoundError|NoConnectionPendingException|NoContext|NoContextHelper|Node|NodeChangeEvent|NodeChangeListener|NodeList|NoInitialContextException|NoninvertibleTransformException|NonReadableChannelException|NonWritableChannelException|NoPermissionException|NoRouteToHostException|NoServant|NoServantHelper|NoSuchAlgorithmException|NoSuchAttributeException|NoSuchElementException|NoSuchFieldError|NoSuchFieldException|NoSuchMethodError|NoSuchMethodException|NoSuchObjectException|NoSuchPaddingException|NoSuchProviderException|NotActiveException|Notation|NotBoundException|NotContextException|NotEmpty|NotEmptyHelper|NotEmptyHolder|NotFound|NotFoundHelper|NotFoundHolder|NotFoundReason|NotFoundReasonHelper|NotFoundReasonHolder|NotOwnerException|NotSerializableException|NotYetBoundException|NotYetConnectedException|NullCipher|NullPointerException|Number|NumberFormat|NumberFormatException|NumberFormatter|NumberOfDocuments|NumberOfInterveningJobs|NumberUp|NumberUpSupported|NumericShaper|NVList|OBJ_ADAPTER|Object|OBJECT_NOT_EXIST|ObjectAlreadyActive|ObjectAlreadyActiveHelper|ObjectChangeListener|ObjectFactory|ObjectFactoryBuilder|ObjectHelper|ObjectHolder|ObjectIdHelper|ObjectImpl|ObjectInput|ObjectInputStream|ObjectInputValidation|ObjectNotActive|ObjectNotActiveHelper|ObjectOutput|ObjectOutputStream|ObjectStreamClass|ObjectStreamConstants|ObjectStreamException|ObjectStreamField|ObjectView|ObjID|Observable|Observer|OctetSeqHelper|OctetSeqHolder|Oid|OMGVMCID|OpenType|Operation|OperationNotSupportedException|Option|OptionalDataException|OptionPaneUI|ORB|ORBInitializer|ORBInitializerOperations|ORBInitInfo|ORBInitInfoOperations|OrientationRequested|OutOfMemoryError|OutputDeviceAssigned|OutputKeys|OutputStream|OutputStreamWriter|OverlappingFileLockException|OverlayLayout|Owner|Package|PackedColorModel|Pageable|PageAttributes|PageFormat|PageRanges|PagesPerMinute|PagesPerMinuteColor|Paint|PaintContext|PaintEvent|Panel|PanelUI|Paper|ParagraphView|Parameter|ParameterBlock|ParameterDescriptor|ParameterMetaData|ParameterMode|ParameterModeHelper|ParameterModeHolder|ParseException|ParsePosition|Parser|ParserAdapter|ParserConfigurationException|ParserDelegator|ParserFactory|PartialResultException|PasswordAuthentication|PasswordCallback|PasswordView|Patch|PathIterator|Pattern|PatternSyntaxException|PBEKey|PBEKeySpec|PBEParameterSpec|PDLOverrideSupported|Permission|PermissionCollection|Permissions|PERSIST_STORE|PersistenceDelegate|PhantomReference|Pipe|PipedInputStream|PipedOutputStream|PipedReader|PipedWriter|PixelGrabber|PixelInterleavedSampleModel|PKCS8EncodedKeySpec|PKIXBuilderParameters|PKIXCertPathBuilderResult|PKIXCertPathChecker|PKIXCertPathValidatorResult|PKIXParameters|PlainDocument|PlainView|POA|POAHelper|POAManager|POAManagerOperations|POAOperations|Point|Point2D|Policy|PolicyError|PolicyErrorCodeHelper|PolicyErrorHelper|PolicyErrorHolder|PolicyFactory|PolicyFactoryOperations|PolicyHelper|PolicyHolder|PolicyListHelper|PolicyListHolder|PolicyNode|PolicyOperations|PolicyQualifierInfo|PolicyTypeHelper|Polygon|PooledConnection|Popup|PopupFactory|PopupMenu|PopupMenuEvent|PopupMenuListener|PopupMenuUI|Port|PortableRemoteObject|PortableRemoteObjectDelegate|PortUnreachableException|Position|PreferenceChangeEvent|PreferenceChangeListener|Preferences|PreferencesFactory|PreparedStatement|PresentationDirection|Principal|PrincipalHolder|Printable|PrinterAbortException|PrinterException|PrinterGraphics|PrinterInfo|PrinterIOException|PrinterIsAcceptingJobs|PrinterJob|PrinterLocation|PrinterMakeAndModel|PrinterMessageFromOperator|PrinterMoreInfo|PrinterMoreInfoManufacturer|PrinterName|PrinterResolution|PrinterState|PrinterStateReason|PrinterStateReasons|PrinterURI|PrintEvent|PrintException|PrintGraphics|PrintJob|PrintJobAdapter|PrintJobAttribute|PrintJobAttributeEvent|PrintJobAttributeListener|PrintJobAttributeSet|PrintJobEvent|PrintJobListener|PrintQuality|PrintRequestAttribute|PrintRequestAttributeSet|PrintService|PrintServiceAttribute|PrintServiceAttributeEvent|PrintServiceAttributeListener|PrintServiceAttributeSet|PrintServiceLookup|PrintStream|PrintWriter|PRIVATE_MEMBER|PrivateCredentialPermission|PrivateKey|PrivilegedAction|PrivilegedActionException|PrivilegedExceptionAction|Process|ProcessingInstruction|ProfileDataException|ProfileIdHelper|ProgressBarUI|ProgressMonitor|ProgressMonitorInputStream|Properties|PropertyChangeEvent|PropertyChangeListener|PropertyChangeListenerProxy|PropertyChangeSupport|PropertyDescriptor|PropertyEditor|PropertyEditorManager|PropertyEditorSupport|PropertyPermission|PropertyResourceBundle|PropertyVetoException|ProtectionDomain|ProtocolException|Provider|ProviderException|Proxy|PSSParameterSpec|PUBLIC_MEMBER|PublicKey|PushbackInputStream|PushbackReader|QuadCurve2D|QueuedJobCount|Random|RandomAccess|RandomAccessFile|Raster|RasterFormatException|RasterOp|RC2ParameterSpec|RC5ParameterSpec|ReadableByteChannel|Reader|ReadOnlyBufferException|Receiver|Rectangle|Rectangle2D|RectangularShape|Ref|RefAddr|Reference|Referenceable|ReferenceQueue|ReferenceUriSchemesSupported|ReferralException|ReflectPermission|Refreshable|RefreshFailedException|RegisterableService|Registry|RegistryHandler|RemarshalException|Remote|RemoteCall|RemoteException|RemoteObject|RemoteRef|RemoteServer|RemoteStub|RenderableImage|RenderableImageOp|RenderableImageProducer|RenderContext|RenderedImage|RenderedImageFactory|Renderer|RenderingHints|RepaintManager|ReplicateScaleFilter|RepositoryIdHelper|Request|REQUEST_PROCESSING_POLICY_ID|RequestInfo|RequestInfoOperations|RequestingUserName|RequestProcessingPolicy|RequestProcessingPolicyOperations|RequestProcessingPolicyValue|RescaleOp|ResolutionSyntax|Resolver|ResolveResult|ResourceBundle|ResponseHandler|Result|ResultSet|ResultSetMetaData|ReverbType|RGBImageFilter|RMIClassLoader|RMIClassLoaderSpi|RMIClientSocketFactory|RMIFailureHandler|RMISecurityException|RMISecurityManager|RMIServerSocketFactory|RMISocketFactory|Robot|RootPaneContainer|RootPaneUI|RoundRectangle2D|RowMapper|RowSet|RowSetEvent|RowSetInternal|RowSetListener|RowSetMetaData|RowSetReader|RowSetWriter|RSAKey|RSAKeyGenParameterSpec|RSAMultiPrimePrivateCrtKey|RSAMultiPrimePrivateCrtKeySpec|RSAOtherPrimeInfo|RSAPrivateCrtKey|RSAPrivateCrtKeySpec|RSAPrivateKey|RSAPrivateKeySpec|RSAPublicKey|RSAPublicKeySpec|RTFEditorKit|RuleBasedCollator|Runnable|Runtime|RunTime|RuntimeException|RunTimeOperations|RuntimePermission|SampleModel|Savepoint|SAXException|SAXNotRecognizedException|SAXNotSupportedException|SAXParseException|SAXParser|SAXParserFactory|SAXResult|SAXSource|SAXTransformerFactory|ScatteringByteChannel|SchemaViolationException|Scrollable|Scrollbar|ScrollBarUI|ScrollPane|ScrollPaneAdjustable|ScrollPaneConstants|ScrollPaneLayout|ScrollPaneUI|SealedObject|SearchControls|SearchResult|SecretKey|SecretKeyFactory|SecretKeyFactorySpi|SecretKeySpec|SecureClassLoader|SecureRandom|SecureRandomSpi|Security|SecurityException|SecurityManager|SecurityPermission|Segment|SelectableChannel|SelectionKey|Selector|SelectorProvider|SeparatorUI|Sequence|SequenceInputStream|Sequencer|Serializable|SerializablePermission|Servant|SERVANT_RETENTION_POLICY_ID|ServantActivator|ServantActivatorHelper|ServantActivatorOperations|ServantActivatorPOA|ServantAlreadyActive|ServantAlreadyActiveHelper|ServantLocator|ServantLocatorHelper|ServantLocatorOperations|ServantLocatorPOA|ServantManager|ServantManagerOperations|ServantNotActive|ServantNotActiveHelper|ServantObject|ServantRetentionPolicy|ServantRetentionPolicyOperations|ServantRetentionPolicyValue|ServerCloneException|ServerError|ServerException|ServerNotActiveException|ServerRef|ServerRequest|ServerRequestInfo|ServerRequestInfoOperations|ServerRequestInterceptor|ServerRequestInterceptorOperations|ServerRuntimeException|ServerSocket|ServerSocketChannel|ServerSocketFactory|ServiceContext|ServiceContextHelper|ServiceContextHolder|ServiceContextListHelper|ServiceContextListHolder|ServiceDetail|ServiceDetailHelper|ServiceIdHelper|ServiceInformation|ServiceInformationHelper|ServiceInformationHolder|ServicePermission|ServiceRegistry|ServiceUI|ServiceUIFactory|ServiceUnavailableException|Set|SetOfIntegerSyntax|SetOverrideType|SetOverrideTypeHelper|Severity|Shape|ShapeGraphicAttribute|SheetCollate|Short|ShortBuffer|ShortBufferException|ShortHolder|ShortLookupTable|ShortMessage|ShortSeqHelper|ShortSeqHolder|Sides|Signature|SignatureException|SignatureSpi|SignedObject|Signer|SimpleAttributeSet|SimpleBeanInfo|SimpleDateFormat|SimpleDoc|SimpleFormatter|SimpleTimeZone|SinglePixelPackedSampleModel|SingleSelectionModel|Size2DSyntax|SizeLimitExceededException|SizeRequirements|SizeSequence|Skeleton|SkeletonMismatchException|SkeletonNotFoundException|SliderUI|Socket|SocketAddress|SocketChannel|SocketException|SocketFactory|SocketHandler|SocketImpl|SocketImplFactory|SocketOptions|SocketPermission|SocketSecurityException|SocketTimeoutException|SoftBevelBorder|SoftReference|SortedMap|SortedSet|SortingFocusTraversalPolicy|Soundbank|SoundbankReader|SoundbankResource|Source|SourceDataLine|SourceLocator|SpinnerDateModel|SpinnerListModel|SpinnerModel|SpinnerNumberModel|SpinnerUI|SplitPaneUI|Spring|SpringLayout|SQLData|SQLException|SQLInput|SQLOutput|SQLPermission|SQLWarning|SSLContext|SSLContextSpi|SSLException|SSLHandshakeException|SSLKeyException|SSLPeerUnverifiedException|SSLPermission|SSLProtocolException|SSLServerSocket|SSLServerSocketFactory|SSLSession|SSLSessionBindingEvent|SSLSessionBindingListener|SSLSessionContext|SSLSocket|SSLSocketFactory|Stack|StackOverflowError|StackTraceElement|StartTlsRequest|StartTlsResponse|State|StateEdit|StateEditable|StateFactory|Statement|Streamable|StreamableValue|StreamCorruptedException|StreamHandler|StreamPrintService|StreamPrintServiceFactory|StreamResult|StreamSource|StreamTokenizer|StrictMath|String|StringBuffer|StringBufferInputStream|StringCharacterIterator|StringContent|StringHolder|StringIndexOutOfBoundsException|StringNameHelper|StringReader|StringRefAddr|StringSelection|StringSeqHelper|StringSeqHolder|StringTokenizer|StringValueHelper|StringWriter|Stroke|Struct|StructMember|StructMemberHelper|Stub|StubDelegate|StubNotFoundException|Style|StyleConstants|StyleContext|StyledDocument|StyledEditorKit|StyleSheet|Subject|SubjectDomainCombiner|SUCCESSFUL|SupportedValuesAttribute|SwingConstants|SwingPropertyChangeSupport|SwingUtilities|SYNC_WITH_TRANSPORT|SyncFailedException|SyncScopeHelper|Synthesizer|SysexMessage|System|SYSTEM_EXCEPTION|SystemColor|SystemException|SystemFlavorMap|TabableView|TabbedPaneUI|TabExpander|TableCellEditor|TableCellRenderer|TableColumn|TableColumnModel|TableColumnModelEvent|TableColumnModelListener|TableHeaderUI|TableModel|TableModelEvent|TableModelListener|TableUI|TableView|TabSet|TabStop|TAG_ALTERNATE_IIOP_ADDRESS|TAG_CODE_SETS|TAG_INTERNET_IOP|TAG_JAVA_CODEBASE|TAG_MULTIPLE_COMPONENTS|TAG_ORB_TYPE|TAG_POLICIES|TagElement|TaggedComponent|TaggedComponentHelper|TaggedComponentHolder|TaggedProfile|TaggedProfileHelper|TaggedProfileHolder|TargetDataLine|TCKind|Templates|TemplatesHandler|Text|TextAction|TextArea|TextAttribute|TextComponent|TextEvent|TextField|TextHitInfo|TextInputCallback|TextLayout|TextListener|TextMeasurer|TextOutputCallback|TextSyntax|TextUI|TexturePaint|Thread|THREAD_POLICY_ID|ThreadDeath|ThreadGroup|ThreadLocal|ThreadPolicy|ThreadPolicyOperations|ThreadPolicyValue|Throwable|Tie|TileObserver|Time|TimeLimitExceededException|Timer|TimerTask|Timestamp|TimeZone|TitledBorder|ToolBarUI|Toolkit|ToolTipManager|ToolTipUI|TooManyListenersException|Track|TRANSACTION_REQUIRED|TRANSACTION_ROLLEDBACK|TransactionRequiredException|TransactionRolledbackException|TransactionService|Transferable|TransferHandler|TransformAttribute|Transformer|TransformerConfigurationException|TransformerException|TransformerFactory|TransformerFactoryConfigurationError|TransformerHandler|TRANSIENT|Transmitter|Transparency|TRANSPORT_RETRY|TreeCellEditor|TreeCellRenderer|TreeExpansionEvent|TreeExpansionListener|TreeMap|TreeModel|TreeModelEvent|TreeModelListener|TreeNode|TreePath|TreeSelectionEvent|TreeSelectionListener|TreeSelectionModel|TreeSet|TreeUI|TreeWillExpandListener|TrustAnchor|TrustManager|TrustManagerFactory|TrustManagerFactorySpi|TypeCode|TypeCodeHolder|TypeMismatch|TypeMismatchHelper|Types|UID|UIDefaults|UIManager|UIResource|ULongLongSeqHelper|ULongLongSeqHolder|ULongSeqHelper|ULongSeqHolder|UndeclaredThrowableException|UndoableEdit|UndoableEditEvent|UndoableEditListener|UndoableEditSupport|UndoManager|UnexpectedException|UnicastRemoteObject|UnionMember|UnionMemberHelper|UNKNOWN|UnknownEncoding|UnknownEncodingHelper|UnknownError|UnknownException|UnknownGroupException|UnknownHostException|UnknownObjectException|UnknownServiceException|UnknownUserException|UnknownUserExceptionHelper|UnknownUserExceptionHolder|UnmappableCharacterException|UnmarshalException|UnmodifiableSetException|UnrecoverableKeyException|Unreferenced|UnresolvedAddressException|UnresolvedPermission|UnsatisfiedLinkError|UnsolicitedNotification|UnsolicitedNotificationEvent|UnsolicitedNotificationListener|UNSUPPORTED_POLICY|UNSUPPORTED_POLICY_VALUE|UnsupportedAddressTypeException|UnsupportedAudioFileException|UnsupportedCallbackException|UnsupportedCharsetException|UnsupportedClassVersionError|UnsupportedEncodingException|UnsupportedFlavorException|UnsupportedLookAndFeelException|UnsupportedOperationException|URI|URIException|URIResolver|URISyntax|URISyntaxException|URL|URLClassLoader|URLConnection|URLDecoder|URLEncoder|URLStreamHandler|URLStreamHandlerFactory|URLStringHelper|USER_EXCEPTION|UserException|UShortSeqHelper|UShortSeqHolder|UTFDataFormatException|Util|UtilDelegate|Utilities|ValueBase|ValueBaseHelper|ValueBaseHolder|ValueFactory|ValueHandler|ValueMember|ValueMemberHelper|VariableHeightLayoutCache|Vector|VerifyError|VersionSpecHelper|VetoableChangeListener|VetoableChangeListenerProxy|VetoableChangeSupport|View|ViewFactory|ViewportLayout|ViewportUI|VirtualMachineError|Visibility|VisibilityHelper|VM_ABSTRACT|VM_CUSTOM|VM_NONE|VM_TRUNCATABLE|VMID|VoiceStatus|Void|VolatileImage|WCharSeqHelper|WCharSeqHolder|WeakHashMap|WeakReference|Window|WindowAdapter|WindowConstants|WindowEvent|WindowFocusListener|WindowListener|WindowStateListener|WrappedPlainView|WritableByteChannel|WritableRaster|WritableRenderedImage|WriteAbortedException|Writer|WrongAdapter|WrongAdapterHelper|WrongPolicy|WrongPolicyHelper|WrongTransaction|WrongTransactionHelper|WrongTransactionHolder|WStringSeqHelper|WStringSeqHolder|WStringValueHelper|X500Principal|X500PrivateCredential|X509Certificate|X509CertSelector|X509CRL|X509CRLEntry|X509CRLSelector|X509EncodedKeySpec|X509Extension|X509KeyManager|X509TrustManager|XAConnection|XADataSource|XAException|XAResource|Xid|XMLDecoder|XMLEncoder|XMLFilter|XMLFilterImpl|XMLFormatter|XMLReader|XMLReaderAdapter|XMLReaderFactory|ZipEntry|ZipException|ZipFile|ZipInputStream|ZipOutputStream|ZoneView|_BindingIteratorImplBase|_BindingIteratorStub|_DynAnyFactoryStub|_DynAnyStub|_DynArrayStub|_DynEnumStub|_DynFixedStub|_DynSequenceStub|_DynStructStub|_DynUnionStub|_DynValueStub|_IDLTypeStub|_NamingContextExtStub|_NamingContextImplBase|_NamingContextStub|_PolicyStub|_Remote_Stub|_ServantActivatorStub|_ServantLocatorStub)$/',
- ),
- 8 =>
- array (
- ),
- 9 =>
- array (
- ),
- 10 =>
- array (
- ),
- 11 =>
- array (
- ),
- 12 =>
- array (
- ),
- ),
- 0 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 =>
- array (
- 'types' => '/^(boolean|byte|char|const|double|final|float|int|long|short|static|void)$/',
- 'reserved' => '/^(import|package|abstract|break|case|catch|class|continue|default|do|else|extends|false|finally|for|goto|if|implements|instanceof|interface|native|new|null|private|protected|public|return|super|strictfp|switch|synchronized|this|throws|throw|transient|true|try|volatile|while)$/',
- 'builtin' => '/^(AbstractAction|AbstractBorder|AbstractButton|AbstractCellEditor|AbstractCollection|AbstractColorChooserPanel|AbstractDocument|AbstractInterruptibleChannel|AbstractLayoutCache|AbstractList|AbstractListModel|AbstractMap|AbstractMethodError|AbstractPreferences|AbstractSelectableChannel|AbstractSelectionKey|AbstractSelector|AbstractSequentialList|AbstractSet|AbstractSpinnerModel|AbstractTableModel|AbstractUndoableEdit|AbstractWriter|AccessControlContext|AccessControlException|AccessController|AccessException|Accessible|AccessibleAction|AccessibleBundle|AccessibleComponent|AccessibleContext|AccessibleEditableText|AccessibleExtendedComponent|AccessibleExtendedTable|AccessibleHyperlink|AccessibleHypertext|AccessibleIcon|AccessibleKeyBinding|AccessibleObject|AccessibleRelation|AccessibleRelationSet|AccessibleResourceBundle|AccessibleRole|AccessibleSelection|AccessibleState|AccessibleStateSet|AccessibleTable|AccessibleTableModelChange|AccessibleText|AccessibleValue|AccountExpiredException|Acl|AclEntry|AclNotFoundException|Action|ActionEvent|ActionListener|ActionMap|ActionMapUIResource|Activatable|ActivateFailedException|ActivationDesc|ActivationException|ActivationGroup|ActivationGroup_Stub|ActivationGroupDesc|ActivationGroupID|ActivationID|ActivationInstantiator|ActivationMonitor|ActivationSystem|Activator|ActiveEvent|AdapterActivator|AdapterActivatorOperations|AdapterAlreadyExists|AdapterAlreadyExistsHelper|AdapterInactive|AdapterInactiveHelper|AdapterNonExistent|AdapterNonExistentHelper|AddressHelper|Adjustable|AdjustmentEvent|AdjustmentListener|Adler32|AffineTransform|AffineTransformOp|AlgorithmParameterGenerator|AlgorithmParameterGeneratorSpi|AlgorithmParameters|AlgorithmParameterSpec|AlgorithmParametersSpi|AllPermission|AlphaComposite|AlreadyBound|AlreadyBoundException|AlreadyBoundHelper|AlreadyBoundHolder|AlreadyConnectedException|AncestorEvent|AncestorListener|Annotation|Any|AnyHolder|AnySeqHelper|AnySeqHolder|AppConfigurationEntry|Applet|AppletContext|AppletInitializer|AppletStub|ApplicationException|Arc2D|Area|AreaAveragingScaleFilter|ARG_IN|ARG_INOUT|ARG_OUT|ArithmeticException|Array|ArrayIndexOutOfBoundsException|ArrayList|Arrays|ArrayStoreException|AssertionError|AsyncBoxView|AsynchronousCloseException|Attr|Attribute|AttributedCharacterIterator|AttributedString|AttributeException|AttributeInUseException|AttributeList|AttributeListImpl|AttributeModificationException|Attributes|AttributeSet|AttributeSetUtilities|AttributesImpl|AudioClip|AudioFileFormat|AudioFileReader|AudioFileWriter|AudioFormat|AudioInputStream|AudioPermission|AudioSystem|AuthenticationException|AuthenticationNotSupportedException|Authenticator|AuthPermission|Autoscroll|AWTError|AWTEvent|AWTEventListener|AWTEventListenerProxy|AWTEventMulticaster|AWTException|AWTKeyStroke|AWTPermission|BackingStoreException|BAD_CONTEXT|BAD_INV_ORDER|BAD_OPERATION|BAD_PARAM|BAD_POLICY|BAD_POLICY_TYPE|BAD_POLICY_VALUE|BAD_TYPECODE|BadKind|BadLocationException|BadPaddingException|BandCombineOp|BandedSampleModel|BasicArrowButton|BasicAttribute|BasicAttributes|BasicBorders|BasicButtonListener|BasicButtonUI|BasicCheckBoxMenuItemUI|BasicCheckBoxUI|BasicColorChooserUI|BasicComboBoxEditor|BasicComboBoxRenderer|BasicComboBoxUI|BasicComboPopup|BasicDesktopIconUI|BasicDesktopPaneUI|BasicDirectoryModel|BasicEditorPaneUI|BasicFileChooserUI|BasicFormattedTextFieldUI|BasicGraphicsUtils|BasicHTML|BasicIconFactory|BasicInternalFrameTitlePane|BasicInternalFrameUI|BasicLabelUI|BasicListUI|BasicLookAndFeel|BasicMenuBarUI|BasicMenuItemUI|BasicMenuUI|BasicOptionPaneUI|BasicPanelUI|BasicPasswordFieldUI|BasicPermission|BasicPopupMenuSeparatorUI|BasicPopupMenuUI|BasicProgressBarUI|BasicRadioButtonMenuItemUI|BasicRadioButtonUI|BasicRootPaneUI|BasicScrollBarUI|BasicScrollPaneUI|BasicSeparatorUI|BasicSliderUI|BasicSpinnerUI|BasicSplitPaneDivider|BasicSplitPaneUI|BasicStroke|BasicTabbedPaneUI|BasicTableHeaderUI|BasicTableUI|BasicTextAreaUI|BasicTextFieldUI|BasicTextPaneUI|BasicTextUI|BasicToggleButtonUI|BasicToolBarSeparatorUI|BasicToolBarUI|BasicToolTipUI|BasicTreeUI|BasicViewportUI|BatchUpdateException|BeanContext|BeanContextChild|BeanContextChildComponentProxy|BeanContextChildSupport|BeanContextContainerProxy|BeanContextEvent|BeanContextMembershipEvent|BeanContextMembershipListener|BeanContextProxy|BeanContextServiceAvailableEvent|BeanContextServiceProvider|BeanContextServiceProviderBeanInfo|BeanContextServiceRevokedEvent|BeanContextServiceRevokedListener|BeanContextServices|BeanContextServicesListener|BeanContextServicesSupport|BeanContextSupport|BeanDescriptor|BeanInfo|Beans|BevelBorder|Bidi|BigDecimal|BigInteger|BinaryRefAddr|BindException|Binding|BindingHelper|BindingHolder|BindingIterator|BindingIteratorHelper|BindingIteratorHolder|BindingIteratorOperations|BindingIteratorPOA|BindingListHelper|BindingListHolder|BindingType|BindingTypeHelper|BindingTypeHolder|BitSet|Blob|BlockView|Book|Boolean|BooleanControl|BooleanHolder|BooleanSeqHelper|BooleanSeqHolder|Border|BorderFactory|BorderLayout|BorderUIResource|BoundedRangeModel|Bounds|Box|BoxedValueHelper|BoxLayout|BoxView|BreakIterator|Buffer|BufferCapabilities|BufferedImage|BufferedImageFilter|BufferedImageOp|BufferedInputStream|BufferedOutputStream|BufferedReader|BufferedWriter|BufferOverflowException|BufferStrategy|BufferUnderflowException|Button|ButtonGroup|ButtonModel|ButtonUI|Byte|ByteArrayInputStream|ByteArrayOutputStream|ByteBuffer|ByteChannel|ByteHolder|ByteLookupTable|ByteOrder|Calendar|CallableStatement|Callback|CallbackHandler|CancelablePrintJob|CancelledKeyException|CannotProceed|CannotProceedException|CannotProceedHelper|CannotProceedHolder|CannotRedoException|CannotUndoException|Canvas|CardLayout|Caret|CaretEvent|CaretListener|CDATASection|CellEditor|CellEditorListener|CellRendererPane|Certificate|CertificateEncodingException|CertificateException|CertificateExpiredException|CertificateFactory|CertificateFactorySpi|CertificateNotYetValidException|CertificateParsingException|CertPath|CertPathBuilder|CertPathBuilderException|CertPathBuilderResult|CertPathBuilderSpi|CertPathParameters|CertPathValidator|CertPathValidatorException|CertPathValidatorResult|CertPathValidatorSpi|CertSelector|CertStore|CertStoreException|CertStoreParameters|CertStoreSpi|ChangedCharSetException|ChangeEvent|ChangeListener|Channel|ChannelBinding|Channels|Character|CharacterCodingException|CharacterData|CharacterIterator|CharArrayReader|CharArrayWriter|CharBuffer|CharConversionException|CharHolder|CharSeqHelper|CharSeqHolder|CharSequence|Charset|CharsetDecoder|CharsetEncoder|CharsetProvider|Checkbox|CheckboxGroup|CheckboxMenuItem|CheckedInputStream|CheckedOutputStream|Checksum|Choice|ChoiceCallback|ChoiceFormat|Chromaticity|Cipher|CipherInputStream|CipherOutputStream|CipherSpi|Class|ClassCastException|ClassCircularityError|ClassDesc|ClassFormatError|ClassLoader|ClassNotFoundException|ClientRequestInfo|ClientRequestInfoOperations|ClientRequestInterceptor|ClientRequestInterceptorOperations|Clip|Clipboard|ClipboardOwner|Clob|Cloneable|CloneNotSupportedException|ClosedByInterruptException|ClosedChannelException|ClosedSelectorException|CMMException|Codec|CodecFactory|CodecFactoryHelper|CodecFactoryOperations|CodecOperations|CoderMalfunctionError|CoderResult|CodeSets|CodeSource|CodingErrorAction|CollationElementIterator|CollationKey|Collator|Collection|CollectionCertStoreParameters|Collections|Color|ColorChooserComponentFactory|ColorChooserUI|ColorConvertOp|ColorModel|ColorSelectionModel|ColorSpace|ColorSupported|ColorUIResource|ComboBoxEditor|ComboBoxModel|ComboBoxUI|ComboPopup|COMM_FAILURE|Comment|CommunicationException|Comparable|Comparator|Compiler|CompletionStatus|CompletionStatusHelper|Component|ComponentAdapter|ComponentColorModel|ComponentEvent|ComponentIdHelper|ComponentInputMap|ComponentInputMapUIResource|ComponentListener|ComponentOrientation|ComponentSampleModel|ComponentUI|ComponentView|Composite|CompositeContext|CompositeName|CompositeView|CompoundBorder|CompoundControl|CompoundEdit|CompoundName|Compression|ConcurrentModificationException|Configuration|ConfigurationException|ConfirmationCallback|ConnectException|ConnectIOException|Connection|ConnectionEvent|ConnectionEventListener|ConnectionPendingException|ConnectionPoolDataSource|ConsoleHandler|Constructor|Container|ContainerAdapter|ContainerEvent|ContainerListener|ContainerOrderFocusTraversalPolicy|ContentHandler|ContentHandlerFactory|ContentModel|Context|ContextList|ContextNotEmptyException|ContextualRenderedImageFactory|Control|ControlFactory|ControllerEventListener|ConvolveOp|CookieHolder|Copies|CopiesSupported|CRC32|CredentialExpiredException|CRL|CRLException|CRLSelector|CropImageFilter|CSS|CTX_RESTRICT_SCOPE|CubicCurve2D|Currency|Current|CurrentHelper|CurrentHolder|CurrentOperations|Cursor|Customizer|CustomMarshal|CustomValue|DATA_CONVERSION|DatabaseMetaData|DataBuffer|DataBufferByte|DataBufferDouble|DataBufferFloat|DataBufferInt|DataBufferShort|DataBufferUShort|DataFlavor|DataFormatException|DatagramChannel|DatagramPacket|DatagramSocket|DatagramSocketImpl|DatagramSocketImplFactory|DataInput|DataInputStream|DataLine|DataOutput|DataOutputStream|DataSource|DataTruncation|Date|DateFormat|DateFormatSymbols|DateFormatter|DateTimeAtCompleted|DateTimeAtCreation|DateTimeAtProcessing|DateTimeSyntax|DebugGraphics|DecimalFormat|DecimalFormatSymbols|DeclHandler|DefaultBoundedRangeModel|DefaultButtonModel|DefaultCaret|DefaultCellEditor|DefaultColorSelectionModel|DefaultComboBoxModel|DefaultDesktopManager|DefaultEditorKit|DefaultFocusManager|DefaultFocusTraversalPolicy|DefaultFormatter|DefaultFormatterFactory|DefaultHandler|DefaultHighlighter|DefaultKeyboardFocusManager|DefaultListCellRenderer|DefaultListModel|DefaultListSelectionModel|DefaultMenuLayout|DefaultMetalTheme|DefaultMutableTreeNode|DefaultPersistenceDelegate|DefaultSingleSelectionModel|DefaultStyledDocument|DefaultTableCellRenderer|DefaultTableColumnModel|DefaultTableModel|DefaultTextUI|DefaultTreeCellEditor|DefaultTreeCellRenderer|DefaultTreeModel|DefaultTreeSelectionModel|DefinitionKind|DefinitionKindHelper|Deflater|DeflaterOutputStream|Delegate|DelegationPermission|DESedeKeySpec|DesignMode|DESKeySpec|DesktopIconUI|DesktopManager|DesktopPaneUI|Destination|Destroyable|DestroyFailedException|DGC|DHGenParameterSpec|DHKey|DHParameterSpec|DHPrivateKey|DHPrivateKeySpec|DHPublicKey|DHPublicKeySpec|Dialog|Dictionary|DigestException|DigestInputStream|DigestOutputStream|Dimension|Dimension2D|DimensionUIResource|DirContext|DirectColorModel|DirectoryManager|DirObjectFactory|DirStateFactory|DisplayMode|DnDConstants|Doc|DocAttribute|DocAttributeSet|DocFlavor|DocPrintJob|Document|DocumentBuilder|DocumentBuilderFactory|DocumentEvent|DocumentFilter|DocumentFragment|DocumentHandler|DocumentListener|DocumentName|DocumentParser|DocumentType|DomainCombiner|DomainManager|DomainManagerOperations|DOMException|DOMImplementation|DOMLocator|DOMResult|DOMSource|Double|DoubleBuffer|DoubleHolder|DoubleSeqHelper|DoubleSeqHolder|DragGestureEvent|DragGestureListener|DragGestureRecognizer|DragSource|DragSourceAdapter|DragSourceContext|DragSourceDragEvent|DragSourceDropEvent|DragSourceEvent|DragSourceListener|DragSourceMotionListener|Driver|DriverManager|DriverPropertyInfo|DropTarget|DropTargetAdapter|DropTargetContext|DropTargetDragEvent|DropTargetDropEvent|DropTargetEvent|DropTargetListener|DSAKey|DSAKeyPairGenerator|DSAParameterSpec|DSAParams|DSAPrivateKey|DSAPrivateKeySpec|DSAPublicKey|DSAPublicKeySpec|DTD|DTDConstants|DTDHandler|DuplicateName|DuplicateNameHelper|DynamicImplementation|DynAny|DynAnyFactory|DynAnyFactoryHelper|DynAnyFactoryOperations|DynAnyHelper|DynAnyOperations|DynAnySeqHelper|DynArray|DynArrayHelper|DynArrayOperations|DynEnum|DynEnumHelper|DynEnumOperations|DynFixed|DynFixedHelper|DynFixedOperations|DynSequence|DynSequenceHelper|DynSequenceOperations|DynStruct|DynStructHelper|DynStructOperations|DynUnion|DynUnionHelper|DynUnionOperations|DynValue|DynValueBox|DynValueBoxOperations|DynValueCommon|DynValueCommonOperations|DynValueHelper|DynValueOperations|EditorKit|Element|ElementIterator|Ellipse2D|EmptyBorder|EmptyStackException|EncodedKeySpec|Encoder|Encoding|ENCODING_CDR_ENCAPS|EncryptedPrivateKeyInfo|Entity|EntityReference|EntityResolver|EnumControl|Enumeration|EnumSyntax|Environment|EOFException|Error|ErrorHandler|ErrorListener|ErrorManager|EtchedBorder|Event|EventContext|EventDirContext|EventHandler|EventListener|EventListenerList|EventListenerProxy|EventObject|EventQueue|EventSetDescriptor|Exception|ExceptionInInitializerError|ExceptionList|ExceptionListener|ExemptionMechanism|ExemptionMechanismException|ExemptionMechanismSpi|ExpandVetoException|ExportException|Expression|ExtendedRequest|ExtendedResponse|Externalizable|FactoryConfigurationError|FailedLoginException|FeatureDescriptor|Fidelity|Field|FieldNameHelper|FieldPosition|FieldView|File|FileCacheImageInputStream|FileCacheImageOutputStream|FileChannel|FileChooserUI|FileDescriptor|FileDialog|FileFilter|FileHandler|FileImageInputStream|FileImageOutputStream|FileInputStream|FileLock|FileLockInterruptionException|FilenameFilter|FileNameMap|FileNotFoundException|FileOutputStream|FilePermission|FileReader|FileSystemView|FileView|FileWriter|Filter|FilteredImageSource|FilterInputStream|FilterOutputStream|FilterReader|FilterWriter|Finishings|FixedHeightLayoutCache|FixedHolder|FlatteningPathIterator|FlavorException|FlavorMap|FlavorTable|Float|FloatBuffer|FloatControl|FloatHolder|FloatSeqHelper|FloatSeqHolder|FlowLayout|FlowView|FocusAdapter|FocusEvent|FocusListener|FocusManager|FocusTraversalPolicy|Font|FontFormatException|FontMetrics|FontRenderContext|FontUIResource|Format|FormatConversionProvider|FormatMismatch|FormatMismatchHelper|Formatter|FormView|ForwardRequest|ForwardRequestHelper|Frame|FREE_MEM|GapContent|GatheringByteChannel|GeneralPath|GeneralSecurityException|GlyphJustificationInfo|GlyphMetrics|GlyphVector|GlyphView|GradientPaint|GraphicAttribute|Graphics|Graphics2D|GraphicsConfigTemplate|GraphicsConfiguration|GraphicsDevice|GraphicsEnvironment|GrayFilter|GregorianCalendar|GridBagConstraints|GridBagLayout|GridLayout|Group|GSSContext|GSSCredential|GSSException|GSSManager|GSSName|Guard|GuardedObject|GZIPInputStream|GZIPOutputStream|Handler|HandlerBase|HandshakeCompletedEvent|HandshakeCompletedListener|HasControls|HashAttributeSet|HashDocAttributeSet|HashMap|HashPrintJobAttributeSet|HashPrintRequestAttributeSet|HashPrintServiceAttributeSet|HashSet|Hashtable|HeadlessException|HierarchyBoundsAdapter|HierarchyBoundsListener|HierarchyEvent|HierarchyListener|Highlighter|HostnameVerifier|HTML|HTMLDocument|HTMLEditorKit|HTMLFrameHyperlinkEvent|HTMLWriter|HttpsURLConnection|HttpURLConnection|HyperlinkEvent|HyperlinkListener|ICC_ColorSpace|ICC_Profile|ICC_ProfileGray|ICC_ProfileRGB|Icon|IconUIResource|IconView|ID_ASSIGNMENT_POLICY_ID|ID_UNIQUENESS_POLICY_ID|IdAssignmentPolicy|IdAssignmentPolicyOperations|IdAssignmentPolicyValue|IdentifierHelper|Identity|IdentityHashMap|IdentityScope|IDLEntity|IDLType|IDLTypeHelper|IDLTypeOperations|IdUniquenessPolicy|IdUniquenessPolicyOperations|IdUniquenessPolicyValue|IIOByteBuffer|IIOException|IIOImage|IIOInvalidTreeException|IIOMetadata|IIOMetadataController|IIOMetadataFormat|IIOMetadataFormatImpl|IIOMetadataNode|IIOParam|IIOParamController|IIOReadProgressListener|IIOReadUpdateListener|IIOReadWarningListener|IIORegistry|IIOServiceProvider|IIOWriteProgressListener|IIOWriteWarningListener|IllegalAccessError|IllegalAccessException|IllegalArgumentException|IllegalBlockingModeException|IllegalBlockSizeException|IllegalCharsetNameException|IllegalComponentStateException|IllegalMonitorStateException|IllegalPathStateException|IllegalSelectorException|IllegalStateException|IllegalThreadStateException|Image|ImageCapabilities|ImageConsumer|ImageFilter|ImageGraphicAttribute|ImageIcon|ImageInputStream|ImageInputStreamImpl|ImageInputStreamSpi|ImageIO|ImageObserver|ImageOutputStream|ImageOutputStreamImpl|ImageOutputStreamSpi|ImageProducer|ImageReader|ImageReaderSpi|ImageReaderWriterSpi|ImageReadParam|ImageTranscoder|ImageTranscoderSpi|ImageTypeSpecifier|ImageView|ImageWriteParam|ImageWriter|ImageWriterSpi|ImagingOpException|IMP_LIMIT|IMPLICIT_ACTIVATION_POLICY_ID|ImplicitActivationPolicy|ImplicitActivationPolicyOperations|ImplicitActivationPolicyValue|IncompatibleClassChangeError|InconsistentTypeCode|InconsistentTypeCodeHelper|IndexColorModel|IndexedPropertyDescriptor|IndexOutOfBoundsException|IndirectionException|Inet4Address|Inet6Address|InetAddress|InetSocketAddress|Inflater|InflaterInputStream|InheritableThreadLocal|InitialContext|InitialContextFactory|InitialContextFactoryBuilder|InitialDirContext|INITIALIZE|InitialLdapContext|InlineView|InputContext|InputEvent|InputMap|InputMapUIResource|InputMethod|InputMethodContext|InputMethodDescriptor|InputMethodEvent|InputMethodHighlight|InputMethodListener|InputMethodRequests|InputSource|InputStream|InputStreamReader|InputSubset|InputVerifier|Insets|InsetsUIResource|InstantiationError|InstantiationException|Instrument|InsufficientResourcesException|IntBuffer|Integer|IntegerSyntax|Interceptor|InterceptorOperations|INTERNAL|InternalError|InternalFrameAdapter|InternalFrameEvent|InternalFrameFocusTraversalPolicy|InternalFrameListener|InternalFrameUI|InternationalFormatter|InterruptedException|InterruptedIOException|InterruptedNamingException|InterruptibleChannel|INTF_REPOS|IntHolder|IntrospectionException|Introspector|INV_FLAG|INV_IDENT|INV_OBJREF|INV_POLICY|Invalid|INVALID_TRANSACTION|InvalidAddress|InvalidAddressHelper|InvalidAddressHolder|InvalidAlgorithmParameterException|InvalidAttributeIdentifierException|InvalidAttributesException|InvalidAttributeValueException|InvalidClassException|InvalidDnDOperationException|InvalidKeyException|InvalidKeySpecException|InvalidMarkException|InvalidMidiDataException|InvalidName|InvalidNameException|InvalidNameHelper|InvalidNameHolder|InvalidObjectException|InvalidParameterException|InvalidParameterSpecException|InvalidPolicy|InvalidPolicyHelper|InvalidPreferencesFormatException|InvalidSearchControlsException|InvalidSearchFilterException|InvalidSeq|InvalidSlot|InvalidSlotHelper|InvalidTransactionException|InvalidTypeForEncoding|InvalidTypeForEncodingHelper|InvalidValue|InvalidValueHelper|InvocationEvent|InvocationHandler|InvocationTargetException|InvokeHandler|IOException|IOR|IORHelper|IORHolder|IORInfo|IORInfoOperations|IORInterceptor|IORInterceptorOperations|IRObject|IRObjectOperations|IstringHelper|ItemEvent|ItemListener|ItemSelectable|Iterator|IvParameterSpec|JApplet|JarEntry|JarException|JarFile|JarInputStream|JarOutputStream|JarURLConnection|JButton|JCheckBox|JCheckBoxMenuItem|JColorChooser|JComboBox|JComponent|JDesktopPane|JDialog|JEditorPane|JFileChooser|JFormattedTextField|JFrame|JInternalFrame|JLabel|JLayeredPane|JList|JMenu|JMenuBar|JMenuItem|JobAttributes|JobHoldUntil|JobImpressions|JobImpressionsCompleted|JobImpressionsSupported|JobKOctets|JobKOctetsProcessed|JobKOctetsSupported|JobMediaSheets|JobMediaSheetsCompleted|JobMediaSheetsSupported|JobMessageFromOperator|JobName|JobOriginatingUserName|JobPriority|JobPrioritySupported|JobSheets|JobState|JobStateReason|JobStateReasons|JOptionPane|JPanel|JPasswordField|JPEGHuffmanTable|JPEGImageReadParam|JPEGImageWriteParam|JPEGQTable|JPopupMenu|JProgressBar|JRadioButton|JRadioButtonMenuItem|JRootPane|JScrollBar|JScrollPane|JSeparator|JSlider|JSpinner|JSplitPane|JTabbedPane|JTable|JTableHeader|JTextArea|JTextComponent|JTextField|JTextPane|JToggleButton|JToolBar|JToolTip|JTree|JViewport|JWindow|KerberosKey|KerberosPrincipal|KerberosTicket|Kernel|Key|KeyAdapter|KeyAgreement|KeyAgreementSpi|KeyboardFocusManager|KeyEvent|KeyEventDispatcher|KeyEventPostProcessor|KeyException|KeyFactory|KeyFactorySpi|KeyGenerator|KeyGeneratorSpi|KeyListener|KeyManagementException|KeyManager|KeyManagerFactory|KeyManagerFactorySpi|Keymap|KeyPair|KeyPairGenerator|KeyPairGeneratorSpi|KeySpec|KeyStore|KeyStoreException|KeyStoreSpi|KeyStroke|Label|LabelUI|LabelView|LanguageCallback|LastOwnerException|LayeredHighlighter|LayoutFocusTraversalPolicy|LayoutManager|LayoutManager2|LayoutQueue|LDAPCertStoreParameters|LdapContext|LdapReferralException|Lease|Level|LexicalHandler|LIFESPAN_POLICY_ID|LifespanPolicy|LifespanPolicyOperations|LifespanPolicyValue|LimitExceededException|Line|Line2D|LineBorder|LineBreakMeasurer|LineEvent|LineListener|LineMetrics|LineNumberInputStream|LineNumberReader|LineUnavailableException|LinkageError|LinkedHashMap|LinkedHashSet|LinkedList|LinkException|LinkLoopException|LinkRef|List|ListCellRenderer|ListDataEvent|ListDataListener|ListIterator|ListModel|ListResourceBundle|ListSelectionEvent|ListSelectionListener|ListSelectionModel|ListUI|ListView|LoaderHandler|Locale|LocalObject|LocateRegistry|LOCATION_FORWARD|Locator|LocatorImpl|Logger|LoggingPermission|LoginContext|LoginException|LoginModule|LogManager|LogRecord|LogStream|Long|LongBuffer|LongHolder|LongLongSeqHelper|LongLongSeqHolder|LongSeqHelper|LongSeqHolder|LookAndFeel|LookupOp|LookupTable|Mac|MacSpi|MalformedInputException|MalformedLinkException|MalformedURLException|ManagerFactoryParameters|Manifest|Map|MappedByteBuffer|MARSHAL|MarshalException|MarshalledObject|MaskFormatter|Matcher|Math|MatteBorder|Media|MediaName|MediaPrintableArea|MediaSize|MediaSizeName|MediaTracker|MediaTray|Member|MemoryCacheImageInputStream|MemoryCacheImageOutputStream|MemoryHandler|MemoryImageSource|Menu|MenuBar|MenuBarUI|MenuComponent|MenuContainer|MenuDragMouseEvent|MenuDragMouseListener|MenuElement|MenuEvent|MenuItem|MenuItemUI|MenuKeyEvent|MenuKeyListener|MenuListener|MenuSelectionManager|MenuShortcut|MessageDigest|MessageDigestSpi|MessageFormat|MessageProp|MetaEventListener|MetalBorders|MetalButtonUI|MetalCheckBoxIcon|MetalCheckBoxUI|MetalComboBoxButton|MetalComboBoxEditor|MetalComboBoxIcon|MetalComboBoxUI|MetalDesktopIconUI|MetalFileChooserUI|MetalIconFactory|MetalInternalFrameTitlePane|MetalInternalFrameUI|MetalLabelUI|MetalLookAndFeel|MetalPopupMenuSeparatorUI|MetalProgressBarUI|MetalRadioButtonUI|MetalRootPaneUI|MetalScrollBarUI|MetalScrollButton|MetalScrollPaneUI|MetalSeparatorUI|MetalSliderUI|MetalSplitPaneUI|MetalTabbedPaneUI|MetalTextFieldUI|MetalTheme|MetalToggleButtonUI|MetalToolBarUI|MetalToolTipUI|MetalTreeUI|MetaMessage|Method|MethodDescriptor|MidiChannel|MidiDevice|MidiDeviceProvider|MidiEvent|MidiFileFormat|MidiFileReader|MidiFileWriter|MidiMessage|MidiSystem|MidiUnavailableException|MimeTypeParseException|MinimalHTMLWriter|MissingResourceException|Mixer|MixerProvider|ModificationItem|Modifier|MouseAdapter|MouseDragGestureRecognizer|MouseEvent|MouseInputAdapter|MouseInputListener|MouseListener|MouseMotionAdapter|MouseMotionListener|MouseWheelEvent|MouseWheelListener|MultiButtonUI|MulticastSocket|MultiColorChooserUI|MultiComboBoxUI|MultiDesktopIconUI|MultiDesktopPaneUI|MultiDoc|MultiDocPrintJob|MultiDocPrintService|MultiFileChooserUI|MultiInternalFrameUI|MultiLabelUI|MultiListUI|MultiLookAndFeel|MultiMenuBarUI|MultiMenuItemUI|MultiOptionPaneUI|MultiPanelUI|MultiPixelPackedSampleModel|MultipleComponentProfileHelper|MultipleComponentProfileHolder|MultipleDocumentHandling|MultipleMaster|MultiPopupMenuUI|MultiProgressBarUI|MultiRootPaneUI|MultiScrollBarUI|MultiScrollPaneUI|MultiSeparatorUI|MultiSliderUI|MultiSpinnerUI|MultiSplitPaneUI|MultiTabbedPaneUI|MultiTableHeaderUI|MultiTableUI|MultiTextUI|MultiToolBarUI|MultiToolTipUI|MultiTreeUI|MultiViewportUI|MutableAttributeSet|MutableComboBoxModel|MutableTreeNode|Name|NameAlreadyBoundException|NameCallback|NameClassPair|NameComponent|NameComponentHelper|NameComponentHolder|NamedNodeMap|NamedValue|NameDynAnyPair|NameDynAnyPairHelper|NameDynAnyPairSeqHelper|NameHelper|NameHolder|NameNotFoundException|NameParser|NamespaceChangeListener|NamespaceSupport|NameValuePair|NameValuePairHelper|NameValuePairSeqHelper|Naming|NamingContext|NamingContextExt|NamingContextExtHelper|NamingContextExtHolder|NamingContextExtOperations|NamingContextExtPOA|NamingContextHelper|NamingContextHolder|NamingContextOperations|NamingContextPOA|NamingEnumeration|NamingEvent|NamingException|NamingExceptionEvent|NamingListener|NamingManager|NamingSecurityException|NavigationFilter|NegativeArraySizeException|NetPermission|NetworkInterface|NO_IMPLEMENT|NO_MEMORY|NO_PERMISSION|NO_RESOURCES|NO_RESPONSE|NoClassDefFoundError|NoConnectionPendingException|NoContext|NoContextHelper|Node|NodeChangeEvent|NodeChangeListener|NodeList|NoInitialContextException|NoninvertibleTransformException|NonReadableChannelException|NonWritableChannelException|NoPermissionException|NoRouteToHostException|NoServant|NoServantHelper|NoSuchAlgorithmException|NoSuchAttributeException|NoSuchElementException|NoSuchFieldError|NoSuchFieldException|NoSuchMethodError|NoSuchMethodException|NoSuchObjectException|NoSuchPaddingException|NoSuchProviderException|NotActiveException|Notation|NotBoundException|NotContextException|NotEmpty|NotEmptyHelper|NotEmptyHolder|NotFound|NotFoundHelper|NotFoundHolder|NotFoundReason|NotFoundReasonHelper|NotFoundReasonHolder|NotOwnerException|NotSerializableException|NotYetBoundException|NotYetConnectedException|NullCipher|NullPointerException|Number|NumberFormat|NumberFormatException|NumberFormatter|NumberOfDocuments|NumberOfInterveningJobs|NumberUp|NumberUpSupported|NumericShaper|NVList|OBJ_ADAPTER|Object|OBJECT_NOT_EXIST|ObjectAlreadyActive|ObjectAlreadyActiveHelper|ObjectChangeListener|ObjectFactory|ObjectFactoryBuilder|ObjectHelper|ObjectHolder|ObjectIdHelper|ObjectImpl|ObjectInput|ObjectInputStream|ObjectInputValidation|ObjectNotActive|ObjectNotActiveHelper|ObjectOutput|ObjectOutputStream|ObjectStreamClass|ObjectStreamConstants|ObjectStreamException|ObjectStreamField|ObjectView|ObjID|Observable|Observer|OctetSeqHelper|OctetSeqHolder|Oid|OMGVMCID|OpenType|Operation|OperationNotSupportedException|Option|OptionalDataException|OptionPaneUI|ORB|ORBInitializer|ORBInitializerOperations|ORBInitInfo|ORBInitInfoOperations|OrientationRequested|OutOfMemoryError|OutputDeviceAssigned|OutputKeys|OutputStream|OutputStreamWriter|OverlappingFileLockException|OverlayLayout|Owner|Package|PackedColorModel|Pageable|PageAttributes|PageFormat|PageRanges|PagesPerMinute|PagesPerMinuteColor|Paint|PaintContext|PaintEvent|Panel|PanelUI|Paper|ParagraphView|Parameter|ParameterBlock|ParameterDescriptor|ParameterMetaData|ParameterMode|ParameterModeHelper|ParameterModeHolder|ParseException|ParsePosition|Parser|ParserAdapter|ParserConfigurationException|ParserDelegator|ParserFactory|PartialResultException|PasswordAuthentication|PasswordCallback|PasswordView|Patch|PathIterator|Pattern|PatternSyntaxException|PBEKey|PBEKeySpec|PBEParameterSpec|PDLOverrideSupported|Permission|PermissionCollection|Permissions|PERSIST_STORE|PersistenceDelegate|PhantomReference|Pipe|PipedInputStream|PipedOutputStream|PipedReader|PipedWriter|PixelGrabber|PixelInterleavedSampleModel|PKCS8EncodedKeySpec|PKIXBuilderParameters|PKIXCertPathBuilderResult|PKIXCertPathChecker|PKIXCertPathValidatorResult|PKIXParameters|PlainDocument|PlainView|POA|POAHelper|POAManager|POAManagerOperations|POAOperations|Point|Point2D|Policy|PolicyError|PolicyErrorCodeHelper|PolicyErrorHelper|PolicyErrorHolder|PolicyFactory|PolicyFactoryOperations|PolicyHelper|PolicyHolder|PolicyListHelper|PolicyListHolder|PolicyNode|PolicyOperations|PolicyQualifierInfo|PolicyTypeHelper|Polygon|PooledConnection|Popup|PopupFactory|PopupMenu|PopupMenuEvent|PopupMenuListener|PopupMenuUI|Port|PortableRemoteObject|PortableRemoteObjectDelegate|PortUnreachableException|Position|PreferenceChangeEvent|PreferenceChangeListener|Preferences|PreferencesFactory|PreparedStatement|PresentationDirection|Principal|PrincipalHolder|Printable|PrinterAbortException|PrinterException|PrinterGraphics|PrinterInfo|PrinterIOException|PrinterIsAcceptingJobs|PrinterJob|PrinterLocation|PrinterMakeAndModel|PrinterMessageFromOperator|PrinterMoreInfo|PrinterMoreInfoManufacturer|PrinterName|PrinterResolution|PrinterState|PrinterStateReason|PrinterStateReasons|PrinterURI|PrintEvent|PrintException|PrintGraphics|PrintJob|PrintJobAdapter|PrintJobAttribute|PrintJobAttributeEvent|PrintJobAttributeListener|PrintJobAttributeSet|PrintJobEvent|PrintJobListener|PrintQuality|PrintRequestAttribute|PrintRequestAttributeSet|PrintService|PrintServiceAttribute|PrintServiceAttributeEvent|PrintServiceAttributeListener|PrintServiceAttributeSet|PrintServiceLookup|PrintStream|PrintWriter|PRIVATE_MEMBER|PrivateCredentialPermission|PrivateKey|PrivilegedAction|PrivilegedActionException|PrivilegedExceptionAction|Process|ProcessingInstruction|ProfileDataException|ProfileIdHelper|ProgressBarUI|ProgressMonitor|ProgressMonitorInputStream|Properties|PropertyChangeEvent|PropertyChangeListener|PropertyChangeListenerProxy|PropertyChangeSupport|PropertyDescriptor|PropertyEditor|PropertyEditorManager|PropertyEditorSupport|PropertyPermission|PropertyResourceBundle|PropertyVetoException|ProtectionDomain|ProtocolException|Provider|ProviderException|Proxy|PSSParameterSpec|PUBLIC_MEMBER|PublicKey|PushbackInputStream|PushbackReader|QuadCurve2D|QueuedJobCount|Random|RandomAccess|RandomAccessFile|Raster|RasterFormatException|RasterOp|RC2ParameterSpec|RC5ParameterSpec|ReadableByteChannel|Reader|ReadOnlyBufferException|Receiver|Rectangle|Rectangle2D|RectangularShape|Ref|RefAddr|Reference|Referenceable|ReferenceQueue|ReferenceUriSchemesSupported|ReferralException|ReflectPermission|Refreshable|RefreshFailedException|RegisterableService|Registry|RegistryHandler|RemarshalException|Remote|RemoteCall|RemoteException|RemoteObject|RemoteRef|RemoteServer|RemoteStub|RenderableImage|RenderableImageOp|RenderableImageProducer|RenderContext|RenderedImage|RenderedImageFactory|Renderer|RenderingHints|RepaintManager|ReplicateScaleFilter|RepositoryIdHelper|Request|REQUEST_PROCESSING_POLICY_ID|RequestInfo|RequestInfoOperations|RequestingUserName|RequestProcessingPolicy|RequestProcessingPolicyOperations|RequestProcessingPolicyValue|RescaleOp|ResolutionSyntax|Resolver|ResolveResult|ResourceBundle|ResponseHandler|Result|ResultSet|ResultSetMetaData|ReverbType|RGBImageFilter|RMIClassLoader|RMIClassLoaderSpi|RMIClientSocketFactory|RMIFailureHandler|RMISecurityException|RMISecurityManager|RMIServerSocketFactory|RMISocketFactory|Robot|RootPaneContainer|RootPaneUI|RoundRectangle2D|RowMapper|RowSet|RowSetEvent|RowSetInternal|RowSetListener|RowSetMetaData|RowSetReader|RowSetWriter|RSAKey|RSAKeyGenParameterSpec|RSAMultiPrimePrivateCrtKey|RSAMultiPrimePrivateCrtKeySpec|RSAOtherPrimeInfo|RSAPrivateCrtKey|RSAPrivateCrtKeySpec|RSAPrivateKey|RSAPrivateKeySpec|RSAPublicKey|RSAPublicKeySpec|RTFEditorKit|RuleBasedCollator|Runnable|Runtime|RunTime|RuntimeException|RunTimeOperations|RuntimePermission|SampleModel|Savepoint|SAXException|SAXNotRecognizedException|SAXNotSupportedException|SAXParseException|SAXParser|SAXParserFactory|SAXResult|SAXSource|SAXTransformerFactory|ScatteringByteChannel|SchemaViolationException|Scrollable|Scrollbar|ScrollBarUI|ScrollPane|ScrollPaneAdjustable|ScrollPaneConstants|ScrollPaneLayout|ScrollPaneUI|SealedObject|SearchControls|SearchResult|SecretKey|SecretKeyFactory|SecretKeyFactorySpi|SecretKeySpec|SecureClassLoader|SecureRandom|SecureRandomSpi|Security|SecurityException|SecurityManager|SecurityPermission|Segment|SelectableChannel|SelectionKey|Selector|SelectorProvider|SeparatorUI|Sequence|SequenceInputStream|Sequencer|Serializable|SerializablePermission|Servant|SERVANT_RETENTION_POLICY_ID|ServantActivator|ServantActivatorHelper|ServantActivatorOperations|ServantActivatorPOA|ServantAlreadyActive|ServantAlreadyActiveHelper|ServantLocator|ServantLocatorHelper|ServantLocatorOperations|ServantLocatorPOA|ServantManager|ServantManagerOperations|ServantNotActive|ServantNotActiveHelper|ServantObject|ServantRetentionPolicy|ServantRetentionPolicyOperations|ServantRetentionPolicyValue|ServerCloneException|ServerError|ServerException|ServerNotActiveException|ServerRef|ServerRequest|ServerRequestInfo|ServerRequestInfoOperations|ServerRequestInterceptor|ServerRequestInterceptorOperations|ServerRuntimeException|ServerSocket|ServerSocketChannel|ServerSocketFactory|ServiceContext|ServiceContextHelper|ServiceContextHolder|ServiceContextListHelper|ServiceContextListHolder|ServiceDetail|ServiceDetailHelper|ServiceIdHelper|ServiceInformation|ServiceInformationHelper|ServiceInformationHolder|ServicePermission|ServiceRegistry|ServiceUI|ServiceUIFactory|ServiceUnavailableException|Set|SetOfIntegerSyntax|SetOverrideType|SetOverrideTypeHelper|Severity|Shape|ShapeGraphicAttribute|SheetCollate|Short|ShortBuffer|ShortBufferException|ShortHolder|ShortLookupTable|ShortMessage|ShortSeqHelper|ShortSeqHolder|Sides|Signature|SignatureException|SignatureSpi|SignedObject|Signer|SimpleAttributeSet|SimpleBeanInfo|SimpleDateFormat|SimpleDoc|SimpleFormatter|SimpleTimeZone|SinglePixelPackedSampleModel|SingleSelectionModel|Size2DSyntax|SizeLimitExceededException|SizeRequirements|SizeSequence|Skeleton|SkeletonMismatchException|SkeletonNotFoundException|SliderUI|Socket|SocketAddress|SocketChannel|SocketException|SocketFactory|SocketHandler|SocketImpl|SocketImplFactory|SocketOptions|SocketPermission|SocketSecurityException|SocketTimeoutException|SoftBevelBorder|SoftReference|SortedMap|SortedSet|SortingFocusTraversalPolicy|Soundbank|SoundbankReader|SoundbankResource|Source|SourceDataLine|SourceLocator|SpinnerDateModel|SpinnerListModel|SpinnerModel|SpinnerNumberModel|SpinnerUI|SplitPaneUI|Spring|SpringLayout|SQLData|SQLException|SQLInput|SQLOutput|SQLPermission|SQLWarning|SSLContext|SSLContextSpi|SSLException|SSLHandshakeException|SSLKeyException|SSLPeerUnverifiedException|SSLPermission|SSLProtocolException|SSLServerSocket|SSLServerSocketFactory|SSLSession|SSLSessionBindingEvent|SSLSessionBindingListener|SSLSessionContext|SSLSocket|SSLSocketFactory|Stack|StackOverflowError|StackTraceElement|StartTlsRequest|StartTlsResponse|State|StateEdit|StateEditable|StateFactory|Statement|Streamable|StreamableValue|StreamCorruptedException|StreamHandler|StreamPrintService|StreamPrintServiceFactory|StreamResult|StreamSource|StreamTokenizer|StrictMath|String|StringBuffer|StringBufferInputStream|StringCharacterIterator|StringContent|StringHolder|StringIndexOutOfBoundsException|StringNameHelper|StringReader|StringRefAddr|StringSelection|StringSeqHelper|StringSeqHolder|StringTokenizer|StringValueHelper|StringWriter|Stroke|Struct|StructMember|StructMemberHelper|Stub|StubDelegate|StubNotFoundException|Style|StyleConstants|StyleContext|StyledDocument|StyledEditorKit|StyleSheet|Subject|SubjectDomainCombiner|SUCCESSFUL|SupportedValuesAttribute|SwingConstants|SwingPropertyChangeSupport|SwingUtilities|SYNC_WITH_TRANSPORT|SyncFailedException|SyncScopeHelper|Synthesizer|SysexMessage|System|SYSTEM_EXCEPTION|SystemColor|SystemException|SystemFlavorMap|TabableView|TabbedPaneUI|TabExpander|TableCellEditor|TableCellRenderer|TableColumn|TableColumnModel|TableColumnModelEvent|TableColumnModelListener|TableHeaderUI|TableModel|TableModelEvent|TableModelListener|TableUI|TableView|TabSet|TabStop|TAG_ALTERNATE_IIOP_ADDRESS|TAG_CODE_SETS|TAG_INTERNET_IOP|TAG_JAVA_CODEBASE|TAG_MULTIPLE_COMPONENTS|TAG_ORB_TYPE|TAG_POLICIES|TagElement|TaggedComponent|TaggedComponentHelper|TaggedComponentHolder|TaggedProfile|TaggedProfileHelper|TaggedProfileHolder|TargetDataLine|TCKind|Templates|TemplatesHandler|Text|TextAction|TextArea|TextAttribute|TextComponent|TextEvent|TextField|TextHitInfo|TextInputCallback|TextLayout|TextListener|TextMeasurer|TextOutputCallback|TextSyntax|TextUI|TexturePaint|Thread|THREAD_POLICY_ID|ThreadDeath|ThreadGroup|ThreadLocal|ThreadPolicy|ThreadPolicyOperations|ThreadPolicyValue|Throwable|Tie|TileObserver|Time|TimeLimitExceededException|Timer|TimerTask|Timestamp|TimeZone|TitledBorder|ToolBarUI|Toolkit|ToolTipManager|ToolTipUI|TooManyListenersException|Track|TRANSACTION_REQUIRED|TRANSACTION_ROLLEDBACK|TransactionRequiredException|TransactionRolledbackException|TransactionService|Transferable|TransferHandler|TransformAttribute|Transformer|TransformerConfigurationException|TransformerException|TransformerFactory|TransformerFactoryConfigurationError|TransformerHandler|TRANSIENT|Transmitter|Transparency|TRANSPORT_RETRY|TreeCellEditor|TreeCellRenderer|TreeExpansionEvent|TreeExpansionListener|TreeMap|TreeModel|TreeModelEvent|TreeModelListener|TreeNode|TreePath|TreeSelectionEvent|TreeSelectionListener|TreeSelectionModel|TreeSet|TreeUI|TreeWillExpandListener|TrustAnchor|TrustManager|TrustManagerFactory|TrustManagerFactorySpi|TypeCode|TypeCodeHolder|TypeMismatch|TypeMismatchHelper|Types|UID|UIDefaults|UIManager|UIResource|ULongLongSeqHelper|ULongLongSeqHolder|ULongSeqHelper|ULongSeqHolder|UndeclaredThrowableException|UndoableEdit|UndoableEditEvent|UndoableEditListener|UndoableEditSupport|UndoManager|UnexpectedException|UnicastRemoteObject|UnionMember|UnionMemberHelper|UNKNOWN|UnknownEncoding|UnknownEncodingHelper|UnknownError|UnknownException|UnknownGroupException|UnknownHostException|UnknownObjectException|UnknownServiceException|UnknownUserException|UnknownUserExceptionHelper|UnknownUserExceptionHolder|UnmappableCharacterException|UnmarshalException|UnmodifiableSetException|UnrecoverableKeyException|Unreferenced|UnresolvedAddressException|UnresolvedPermission|UnsatisfiedLinkError|UnsolicitedNotification|UnsolicitedNotificationEvent|UnsolicitedNotificationListener|UNSUPPORTED_POLICY|UNSUPPORTED_POLICY_VALUE|UnsupportedAddressTypeException|UnsupportedAudioFileException|UnsupportedCallbackException|UnsupportedCharsetException|UnsupportedClassVersionError|UnsupportedEncodingException|UnsupportedFlavorException|UnsupportedLookAndFeelException|UnsupportedOperationException|URI|URIException|URIResolver|URISyntax|URISyntaxException|URL|URLClassLoader|URLConnection|URLDecoder|URLEncoder|URLStreamHandler|URLStreamHandlerFactory|URLStringHelper|USER_EXCEPTION|UserException|UShortSeqHelper|UShortSeqHolder|UTFDataFormatException|Util|UtilDelegate|Utilities|ValueBase|ValueBaseHelper|ValueBaseHolder|ValueFactory|ValueHandler|ValueMember|ValueMemberHelper|VariableHeightLayoutCache|Vector|VerifyError|VersionSpecHelper|VetoableChangeListener|VetoableChangeListenerProxy|VetoableChangeSupport|View|ViewFactory|ViewportLayout|ViewportUI|VirtualMachineError|Visibility|VisibilityHelper|VM_ABSTRACT|VM_CUSTOM|VM_NONE|VM_TRUNCATABLE|VMID|VoiceStatus|Void|VolatileImage|WCharSeqHelper|WCharSeqHolder|WeakHashMap|WeakReference|Window|WindowAdapter|WindowConstants|WindowEvent|WindowFocusListener|WindowListener|WindowStateListener|WrappedPlainView|WritableByteChannel|WritableRaster|WritableRenderedImage|WriteAbortedException|Writer|WrongAdapter|WrongAdapterHelper|WrongPolicy|WrongPolicyHelper|WrongTransaction|WrongTransactionHelper|WrongTransactionHolder|WStringSeqHelper|WStringSeqHolder|WStringValueHelper|X500Principal|X500PrivateCredential|X509Certificate|X509CertSelector|X509CRL|X509CRLEntry|X509CRLSelector|X509EncodedKeySpec|X509Extension|X509KeyManager|X509TrustManager|XAConnection|XADataSource|XAException|XAResource|Xid|XMLDecoder|XMLEncoder|XMLFilter|XMLFilterImpl|XMLFormatter|XMLReader|XMLReaderAdapter|XMLReaderFactory|ZipEntry|ZipException|ZipFile|ZipInputStream|ZipOutputStream|ZoneView|_BindingIteratorImplBase|_BindingIteratorStub|_DynAnyFactoryStub|_DynAnyStub|_DynArrayStub|_DynEnumStub|_DynFixedStub|_DynSequenceStub|_DynStructStub|_DynUnionStub|_DynValueStub|_IDLTypeStub|_NamingContextExtStub|_NamingContextImplBase|_NamingContextStub|_PolicyStub|_Remote_Stub|_ServantActivatorStub|_ServantLocatorStub)$/',
- ),
- 8 =>
- array (
- ),
- 9 =>
- array (
- ),
- 10 =>
- array (
- ),
- 11 =>
- array (
- ),
- 12 =>
- array (
- ),
- ),
- 1 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 =>
- array (
- 'types' => '/^(boolean|byte|char|const|double|final|float|int|long|short|static|void)$/',
- 'reserved' => '/^(import|package|abstract|break|case|catch|class|continue|default|do|else|extends|false|finally|for|goto|if|implements|instanceof|interface|native|new|null|private|protected|public|return|super|strictfp|switch|synchronized|this|throws|throw|transient|true|try|volatile|while)$/',
- 'builtin' => '/^(AbstractAction|AbstractBorder|AbstractButton|AbstractCellEditor|AbstractCollection|AbstractColorChooserPanel|AbstractDocument|AbstractInterruptibleChannel|AbstractLayoutCache|AbstractList|AbstractListModel|AbstractMap|AbstractMethodError|AbstractPreferences|AbstractSelectableChannel|AbstractSelectionKey|AbstractSelector|AbstractSequentialList|AbstractSet|AbstractSpinnerModel|AbstractTableModel|AbstractUndoableEdit|AbstractWriter|AccessControlContext|AccessControlException|AccessController|AccessException|Accessible|AccessibleAction|AccessibleBundle|AccessibleComponent|AccessibleContext|AccessibleEditableText|AccessibleExtendedComponent|AccessibleExtendedTable|AccessibleHyperlink|AccessibleHypertext|AccessibleIcon|AccessibleKeyBinding|AccessibleObject|AccessibleRelation|AccessibleRelationSet|AccessibleResourceBundle|AccessibleRole|AccessibleSelection|AccessibleState|AccessibleStateSet|AccessibleTable|AccessibleTableModelChange|AccessibleText|AccessibleValue|AccountExpiredException|Acl|AclEntry|AclNotFoundException|Action|ActionEvent|ActionListener|ActionMap|ActionMapUIResource|Activatable|ActivateFailedException|ActivationDesc|ActivationException|ActivationGroup|ActivationGroup_Stub|ActivationGroupDesc|ActivationGroupID|ActivationID|ActivationInstantiator|ActivationMonitor|ActivationSystem|Activator|ActiveEvent|AdapterActivator|AdapterActivatorOperations|AdapterAlreadyExists|AdapterAlreadyExistsHelper|AdapterInactive|AdapterInactiveHelper|AdapterNonExistent|AdapterNonExistentHelper|AddressHelper|Adjustable|AdjustmentEvent|AdjustmentListener|Adler32|AffineTransform|AffineTransformOp|AlgorithmParameterGenerator|AlgorithmParameterGeneratorSpi|AlgorithmParameters|AlgorithmParameterSpec|AlgorithmParametersSpi|AllPermission|AlphaComposite|AlreadyBound|AlreadyBoundException|AlreadyBoundHelper|AlreadyBoundHolder|AlreadyConnectedException|AncestorEvent|AncestorListener|Annotation|Any|AnyHolder|AnySeqHelper|AnySeqHolder|AppConfigurationEntry|Applet|AppletContext|AppletInitializer|AppletStub|ApplicationException|Arc2D|Area|AreaAveragingScaleFilter|ARG_IN|ARG_INOUT|ARG_OUT|ArithmeticException|Array|ArrayIndexOutOfBoundsException|ArrayList|Arrays|ArrayStoreException|AssertionError|AsyncBoxView|AsynchronousCloseException|Attr|Attribute|AttributedCharacterIterator|AttributedString|AttributeException|AttributeInUseException|AttributeList|AttributeListImpl|AttributeModificationException|Attributes|AttributeSet|AttributeSetUtilities|AttributesImpl|AudioClip|AudioFileFormat|AudioFileReader|AudioFileWriter|AudioFormat|AudioInputStream|AudioPermission|AudioSystem|AuthenticationException|AuthenticationNotSupportedException|Authenticator|AuthPermission|Autoscroll|AWTError|AWTEvent|AWTEventListener|AWTEventListenerProxy|AWTEventMulticaster|AWTException|AWTKeyStroke|AWTPermission|BackingStoreException|BAD_CONTEXT|BAD_INV_ORDER|BAD_OPERATION|BAD_PARAM|BAD_POLICY|BAD_POLICY_TYPE|BAD_POLICY_VALUE|BAD_TYPECODE|BadKind|BadLocationException|BadPaddingException|BandCombineOp|BandedSampleModel|BasicArrowButton|BasicAttribute|BasicAttributes|BasicBorders|BasicButtonListener|BasicButtonUI|BasicCheckBoxMenuItemUI|BasicCheckBoxUI|BasicColorChooserUI|BasicComboBoxEditor|BasicComboBoxRenderer|BasicComboBoxUI|BasicComboPopup|BasicDesktopIconUI|BasicDesktopPaneUI|BasicDirectoryModel|BasicEditorPaneUI|BasicFileChooserUI|BasicFormattedTextFieldUI|BasicGraphicsUtils|BasicHTML|BasicIconFactory|BasicInternalFrameTitlePane|BasicInternalFrameUI|BasicLabelUI|BasicListUI|BasicLookAndFeel|BasicMenuBarUI|BasicMenuItemUI|BasicMenuUI|BasicOptionPaneUI|BasicPanelUI|BasicPasswordFieldUI|BasicPermission|BasicPopupMenuSeparatorUI|BasicPopupMenuUI|BasicProgressBarUI|BasicRadioButtonMenuItemUI|BasicRadioButtonUI|BasicRootPaneUI|BasicScrollBarUI|BasicScrollPaneUI|BasicSeparatorUI|BasicSliderUI|BasicSpinnerUI|BasicSplitPaneDivider|BasicSplitPaneUI|BasicStroke|BasicTabbedPaneUI|BasicTableHeaderUI|BasicTableUI|BasicTextAreaUI|BasicTextFieldUI|BasicTextPaneUI|BasicTextUI|BasicToggleButtonUI|BasicToolBarSeparatorUI|BasicToolBarUI|BasicToolTipUI|BasicTreeUI|BasicViewportUI|BatchUpdateException|BeanContext|BeanContextChild|BeanContextChildComponentProxy|BeanContextChildSupport|BeanContextContainerProxy|BeanContextEvent|BeanContextMembershipEvent|BeanContextMembershipListener|BeanContextProxy|BeanContextServiceAvailableEvent|BeanContextServiceProvider|BeanContextServiceProviderBeanInfo|BeanContextServiceRevokedEvent|BeanContextServiceRevokedListener|BeanContextServices|BeanContextServicesListener|BeanContextServicesSupport|BeanContextSupport|BeanDescriptor|BeanInfo|Beans|BevelBorder|Bidi|BigDecimal|BigInteger|BinaryRefAddr|BindException|Binding|BindingHelper|BindingHolder|BindingIterator|BindingIteratorHelper|BindingIteratorHolder|BindingIteratorOperations|BindingIteratorPOA|BindingListHelper|BindingListHolder|BindingType|BindingTypeHelper|BindingTypeHolder|BitSet|Blob|BlockView|Book|Boolean|BooleanControl|BooleanHolder|BooleanSeqHelper|BooleanSeqHolder|Border|BorderFactory|BorderLayout|BorderUIResource|BoundedRangeModel|Bounds|Box|BoxedValueHelper|BoxLayout|BoxView|BreakIterator|Buffer|BufferCapabilities|BufferedImage|BufferedImageFilter|BufferedImageOp|BufferedInputStream|BufferedOutputStream|BufferedReader|BufferedWriter|BufferOverflowException|BufferStrategy|BufferUnderflowException|Button|ButtonGroup|ButtonModel|ButtonUI|Byte|ByteArrayInputStream|ByteArrayOutputStream|ByteBuffer|ByteChannel|ByteHolder|ByteLookupTable|ByteOrder|Calendar|CallableStatement|Callback|CallbackHandler|CancelablePrintJob|CancelledKeyException|CannotProceed|CannotProceedException|CannotProceedHelper|CannotProceedHolder|CannotRedoException|CannotUndoException|Canvas|CardLayout|Caret|CaretEvent|CaretListener|CDATASection|CellEditor|CellEditorListener|CellRendererPane|Certificate|CertificateEncodingException|CertificateException|CertificateExpiredException|CertificateFactory|CertificateFactorySpi|CertificateNotYetValidException|CertificateParsingException|CertPath|CertPathBuilder|CertPathBuilderException|CertPathBuilderResult|CertPathBuilderSpi|CertPathParameters|CertPathValidator|CertPathValidatorException|CertPathValidatorResult|CertPathValidatorSpi|CertSelector|CertStore|CertStoreException|CertStoreParameters|CertStoreSpi|ChangedCharSetException|ChangeEvent|ChangeListener|Channel|ChannelBinding|Channels|Character|CharacterCodingException|CharacterData|CharacterIterator|CharArrayReader|CharArrayWriter|CharBuffer|CharConversionException|CharHolder|CharSeqHelper|CharSeqHolder|CharSequence|Charset|CharsetDecoder|CharsetEncoder|CharsetProvider|Checkbox|CheckboxGroup|CheckboxMenuItem|CheckedInputStream|CheckedOutputStream|Checksum|Choice|ChoiceCallback|ChoiceFormat|Chromaticity|Cipher|CipherInputStream|CipherOutputStream|CipherSpi|Class|ClassCastException|ClassCircularityError|ClassDesc|ClassFormatError|ClassLoader|ClassNotFoundException|ClientRequestInfo|ClientRequestInfoOperations|ClientRequestInterceptor|ClientRequestInterceptorOperations|Clip|Clipboard|ClipboardOwner|Clob|Cloneable|CloneNotSupportedException|ClosedByInterruptException|ClosedChannelException|ClosedSelectorException|CMMException|Codec|CodecFactory|CodecFactoryHelper|CodecFactoryOperations|CodecOperations|CoderMalfunctionError|CoderResult|CodeSets|CodeSource|CodingErrorAction|CollationElementIterator|CollationKey|Collator|Collection|CollectionCertStoreParameters|Collections|Color|ColorChooserComponentFactory|ColorChooserUI|ColorConvertOp|ColorModel|ColorSelectionModel|ColorSpace|ColorSupported|ColorUIResource|ComboBoxEditor|ComboBoxModel|ComboBoxUI|ComboPopup|COMM_FAILURE|Comment|CommunicationException|Comparable|Comparator|Compiler|CompletionStatus|CompletionStatusHelper|Component|ComponentAdapter|ComponentColorModel|ComponentEvent|ComponentIdHelper|ComponentInputMap|ComponentInputMapUIResource|ComponentListener|ComponentOrientation|ComponentSampleModel|ComponentUI|ComponentView|Composite|CompositeContext|CompositeName|CompositeView|CompoundBorder|CompoundControl|CompoundEdit|CompoundName|Compression|ConcurrentModificationException|Configuration|ConfigurationException|ConfirmationCallback|ConnectException|ConnectIOException|Connection|ConnectionEvent|ConnectionEventListener|ConnectionPendingException|ConnectionPoolDataSource|ConsoleHandler|Constructor|Container|ContainerAdapter|ContainerEvent|ContainerListener|ContainerOrderFocusTraversalPolicy|ContentHandler|ContentHandlerFactory|ContentModel|Context|ContextList|ContextNotEmptyException|ContextualRenderedImageFactory|Control|ControlFactory|ControllerEventListener|ConvolveOp|CookieHolder|Copies|CopiesSupported|CRC32|CredentialExpiredException|CRL|CRLException|CRLSelector|CropImageFilter|CSS|CTX_RESTRICT_SCOPE|CubicCurve2D|Currency|Current|CurrentHelper|CurrentHolder|CurrentOperations|Cursor|Customizer|CustomMarshal|CustomValue|DATA_CONVERSION|DatabaseMetaData|DataBuffer|DataBufferByte|DataBufferDouble|DataBufferFloat|DataBufferInt|DataBufferShort|DataBufferUShort|DataFlavor|DataFormatException|DatagramChannel|DatagramPacket|DatagramSocket|DatagramSocketImpl|DatagramSocketImplFactory|DataInput|DataInputStream|DataLine|DataOutput|DataOutputStream|DataSource|DataTruncation|Date|DateFormat|DateFormatSymbols|DateFormatter|DateTimeAtCompleted|DateTimeAtCreation|DateTimeAtProcessing|DateTimeSyntax|DebugGraphics|DecimalFormat|DecimalFormatSymbols|DeclHandler|DefaultBoundedRangeModel|DefaultButtonModel|DefaultCaret|DefaultCellEditor|DefaultColorSelectionModel|DefaultComboBoxModel|DefaultDesktopManager|DefaultEditorKit|DefaultFocusManager|DefaultFocusTraversalPolicy|DefaultFormatter|DefaultFormatterFactory|DefaultHandler|DefaultHighlighter|DefaultKeyboardFocusManager|DefaultListCellRenderer|DefaultListModel|DefaultListSelectionModel|DefaultMenuLayout|DefaultMetalTheme|DefaultMutableTreeNode|DefaultPersistenceDelegate|DefaultSingleSelectionModel|DefaultStyledDocument|DefaultTableCellRenderer|DefaultTableColumnModel|DefaultTableModel|DefaultTextUI|DefaultTreeCellEditor|DefaultTreeCellRenderer|DefaultTreeModel|DefaultTreeSelectionModel|DefinitionKind|DefinitionKindHelper|Deflater|DeflaterOutputStream|Delegate|DelegationPermission|DESedeKeySpec|DesignMode|DESKeySpec|DesktopIconUI|DesktopManager|DesktopPaneUI|Destination|Destroyable|DestroyFailedException|DGC|DHGenParameterSpec|DHKey|DHParameterSpec|DHPrivateKey|DHPrivateKeySpec|DHPublicKey|DHPublicKeySpec|Dialog|Dictionary|DigestException|DigestInputStream|DigestOutputStream|Dimension|Dimension2D|DimensionUIResource|DirContext|DirectColorModel|DirectoryManager|DirObjectFactory|DirStateFactory|DisplayMode|DnDConstants|Doc|DocAttribute|DocAttributeSet|DocFlavor|DocPrintJob|Document|DocumentBuilder|DocumentBuilderFactory|DocumentEvent|DocumentFilter|DocumentFragment|DocumentHandler|DocumentListener|DocumentName|DocumentParser|DocumentType|DomainCombiner|DomainManager|DomainManagerOperations|DOMException|DOMImplementation|DOMLocator|DOMResult|DOMSource|Double|DoubleBuffer|DoubleHolder|DoubleSeqHelper|DoubleSeqHolder|DragGestureEvent|DragGestureListener|DragGestureRecognizer|DragSource|DragSourceAdapter|DragSourceContext|DragSourceDragEvent|DragSourceDropEvent|DragSourceEvent|DragSourceListener|DragSourceMotionListener|Driver|DriverManager|DriverPropertyInfo|DropTarget|DropTargetAdapter|DropTargetContext|DropTargetDragEvent|DropTargetDropEvent|DropTargetEvent|DropTargetListener|DSAKey|DSAKeyPairGenerator|DSAParameterSpec|DSAParams|DSAPrivateKey|DSAPrivateKeySpec|DSAPublicKey|DSAPublicKeySpec|DTD|DTDConstants|DTDHandler|DuplicateName|DuplicateNameHelper|DynamicImplementation|DynAny|DynAnyFactory|DynAnyFactoryHelper|DynAnyFactoryOperations|DynAnyHelper|DynAnyOperations|DynAnySeqHelper|DynArray|DynArrayHelper|DynArrayOperations|DynEnum|DynEnumHelper|DynEnumOperations|DynFixed|DynFixedHelper|DynFixedOperations|DynSequence|DynSequenceHelper|DynSequenceOperations|DynStruct|DynStructHelper|DynStructOperations|DynUnion|DynUnionHelper|DynUnionOperations|DynValue|DynValueBox|DynValueBoxOperations|DynValueCommon|DynValueCommonOperations|DynValueHelper|DynValueOperations|EditorKit|Element|ElementIterator|Ellipse2D|EmptyBorder|EmptyStackException|EncodedKeySpec|Encoder|Encoding|ENCODING_CDR_ENCAPS|EncryptedPrivateKeyInfo|Entity|EntityReference|EntityResolver|EnumControl|Enumeration|EnumSyntax|Environment|EOFException|Error|ErrorHandler|ErrorListener|ErrorManager|EtchedBorder|Event|EventContext|EventDirContext|EventHandler|EventListener|EventListenerList|EventListenerProxy|EventObject|EventQueue|EventSetDescriptor|Exception|ExceptionInInitializerError|ExceptionList|ExceptionListener|ExemptionMechanism|ExemptionMechanismException|ExemptionMechanismSpi|ExpandVetoException|ExportException|Expression|ExtendedRequest|ExtendedResponse|Externalizable|FactoryConfigurationError|FailedLoginException|FeatureDescriptor|Fidelity|Field|FieldNameHelper|FieldPosition|FieldView|File|FileCacheImageInputStream|FileCacheImageOutputStream|FileChannel|FileChooserUI|FileDescriptor|FileDialog|FileFilter|FileHandler|FileImageInputStream|FileImageOutputStream|FileInputStream|FileLock|FileLockInterruptionException|FilenameFilter|FileNameMap|FileNotFoundException|FileOutputStream|FilePermission|FileReader|FileSystemView|FileView|FileWriter|Filter|FilteredImageSource|FilterInputStream|FilterOutputStream|FilterReader|FilterWriter|Finishings|FixedHeightLayoutCache|FixedHolder|FlatteningPathIterator|FlavorException|FlavorMap|FlavorTable|Float|FloatBuffer|FloatControl|FloatHolder|FloatSeqHelper|FloatSeqHolder|FlowLayout|FlowView|FocusAdapter|FocusEvent|FocusListener|FocusManager|FocusTraversalPolicy|Font|FontFormatException|FontMetrics|FontRenderContext|FontUIResource|Format|FormatConversionProvider|FormatMismatch|FormatMismatchHelper|Formatter|FormView|ForwardRequest|ForwardRequestHelper|Frame|FREE_MEM|GapContent|GatheringByteChannel|GeneralPath|GeneralSecurityException|GlyphJustificationInfo|GlyphMetrics|GlyphVector|GlyphView|GradientPaint|GraphicAttribute|Graphics|Graphics2D|GraphicsConfigTemplate|GraphicsConfiguration|GraphicsDevice|GraphicsEnvironment|GrayFilter|GregorianCalendar|GridBagConstraints|GridBagLayout|GridLayout|Group|GSSContext|GSSCredential|GSSException|GSSManager|GSSName|Guard|GuardedObject|GZIPInputStream|GZIPOutputStream|Handler|HandlerBase|HandshakeCompletedEvent|HandshakeCompletedListener|HasControls|HashAttributeSet|HashDocAttributeSet|HashMap|HashPrintJobAttributeSet|HashPrintRequestAttributeSet|HashPrintServiceAttributeSet|HashSet|Hashtable|HeadlessException|HierarchyBoundsAdapter|HierarchyBoundsListener|HierarchyEvent|HierarchyListener|Highlighter|HostnameVerifier|HTML|HTMLDocument|HTMLEditorKit|HTMLFrameHyperlinkEvent|HTMLWriter|HttpsURLConnection|HttpURLConnection|HyperlinkEvent|HyperlinkListener|ICC_ColorSpace|ICC_Profile|ICC_ProfileGray|ICC_ProfileRGB|Icon|IconUIResource|IconView|ID_ASSIGNMENT_POLICY_ID|ID_UNIQUENESS_POLICY_ID|IdAssignmentPolicy|IdAssignmentPolicyOperations|IdAssignmentPolicyValue|IdentifierHelper|Identity|IdentityHashMap|IdentityScope|IDLEntity|IDLType|IDLTypeHelper|IDLTypeOperations|IdUniquenessPolicy|IdUniquenessPolicyOperations|IdUniquenessPolicyValue|IIOByteBuffer|IIOException|IIOImage|IIOInvalidTreeException|IIOMetadata|IIOMetadataController|IIOMetadataFormat|IIOMetadataFormatImpl|IIOMetadataNode|IIOParam|IIOParamController|IIOReadProgressListener|IIOReadUpdateListener|IIOReadWarningListener|IIORegistry|IIOServiceProvider|IIOWriteProgressListener|IIOWriteWarningListener|IllegalAccessError|IllegalAccessException|IllegalArgumentException|IllegalBlockingModeException|IllegalBlockSizeException|IllegalCharsetNameException|IllegalComponentStateException|IllegalMonitorStateException|IllegalPathStateException|IllegalSelectorException|IllegalStateException|IllegalThreadStateException|Image|ImageCapabilities|ImageConsumer|ImageFilter|ImageGraphicAttribute|ImageIcon|ImageInputStream|ImageInputStreamImpl|ImageInputStreamSpi|ImageIO|ImageObserver|ImageOutputStream|ImageOutputStreamImpl|ImageOutputStreamSpi|ImageProducer|ImageReader|ImageReaderSpi|ImageReaderWriterSpi|ImageReadParam|ImageTranscoder|ImageTranscoderSpi|ImageTypeSpecifier|ImageView|ImageWriteParam|ImageWriter|ImageWriterSpi|ImagingOpException|IMP_LIMIT|IMPLICIT_ACTIVATION_POLICY_ID|ImplicitActivationPolicy|ImplicitActivationPolicyOperations|ImplicitActivationPolicyValue|IncompatibleClassChangeError|InconsistentTypeCode|InconsistentTypeCodeHelper|IndexColorModel|IndexedPropertyDescriptor|IndexOutOfBoundsException|IndirectionException|Inet4Address|Inet6Address|InetAddress|InetSocketAddress|Inflater|InflaterInputStream|InheritableThreadLocal|InitialContext|InitialContextFactory|InitialContextFactoryBuilder|InitialDirContext|INITIALIZE|InitialLdapContext|InlineView|InputContext|InputEvent|InputMap|InputMapUIResource|InputMethod|InputMethodContext|InputMethodDescriptor|InputMethodEvent|InputMethodHighlight|InputMethodListener|InputMethodRequests|InputSource|InputStream|InputStreamReader|InputSubset|InputVerifier|Insets|InsetsUIResource|InstantiationError|InstantiationException|Instrument|InsufficientResourcesException|IntBuffer|Integer|IntegerSyntax|Interceptor|InterceptorOperations|INTERNAL|InternalError|InternalFrameAdapter|InternalFrameEvent|InternalFrameFocusTraversalPolicy|InternalFrameListener|InternalFrameUI|InternationalFormatter|InterruptedException|InterruptedIOException|InterruptedNamingException|InterruptibleChannel|INTF_REPOS|IntHolder|IntrospectionException|Introspector|INV_FLAG|INV_IDENT|INV_OBJREF|INV_POLICY|Invalid|INVALID_TRANSACTION|InvalidAddress|InvalidAddressHelper|InvalidAddressHolder|InvalidAlgorithmParameterException|InvalidAttributeIdentifierException|InvalidAttributesException|InvalidAttributeValueException|InvalidClassException|InvalidDnDOperationException|InvalidKeyException|InvalidKeySpecException|InvalidMarkException|InvalidMidiDataException|InvalidName|InvalidNameException|InvalidNameHelper|InvalidNameHolder|InvalidObjectException|InvalidParameterException|InvalidParameterSpecException|InvalidPolicy|InvalidPolicyHelper|InvalidPreferencesFormatException|InvalidSearchControlsException|InvalidSearchFilterException|InvalidSeq|InvalidSlot|InvalidSlotHelper|InvalidTransactionException|InvalidTypeForEncoding|InvalidTypeForEncodingHelper|InvalidValue|InvalidValueHelper|InvocationEvent|InvocationHandler|InvocationTargetException|InvokeHandler|IOException|IOR|IORHelper|IORHolder|IORInfo|IORInfoOperations|IORInterceptor|IORInterceptorOperations|IRObject|IRObjectOperations|IstringHelper|ItemEvent|ItemListener|ItemSelectable|Iterator|IvParameterSpec|JApplet|JarEntry|JarException|JarFile|JarInputStream|JarOutputStream|JarURLConnection|JButton|JCheckBox|JCheckBoxMenuItem|JColorChooser|JComboBox|JComponent|JDesktopPane|JDialog|JEditorPane|JFileChooser|JFormattedTextField|JFrame|JInternalFrame|JLabel|JLayeredPane|JList|JMenu|JMenuBar|JMenuItem|JobAttributes|JobHoldUntil|JobImpressions|JobImpressionsCompleted|JobImpressionsSupported|JobKOctets|JobKOctetsProcessed|JobKOctetsSupported|JobMediaSheets|JobMediaSheetsCompleted|JobMediaSheetsSupported|JobMessageFromOperator|JobName|JobOriginatingUserName|JobPriority|JobPrioritySupported|JobSheets|JobState|JobStateReason|JobStateReasons|JOptionPane|JPanel|JPasswordField|JPEGHuffmanTable|JPEGImageReadParam|JPEGImageWriteParam|JPEGQTable|JPopupMenu|JProgressBar|JRadioButton|JRadioButtonMenuItem|JRootPane|JScrollBar|JScrollPane|JSeparator|JSlider|JSpinner|JSplitPane|JTabbedPane|JTable|JTableHeader|JTextArea|JTextComponent|JTextField|JTextPane|JToggleButton|JToolBar|JToolTip|JTree|JViewport|JWindow|KerberosKey|KerberosPrincipal|KerberosTicket|Kernel|Key|KeyAdapter|KeyAgreement|KeyAgreementSpi|KeyboardFocusManager|KeyEvent|KeyEventDispatcher|KeyEventPostProcessor|KeyException|KeyFactory|KeyFactorySpi|KeyGenerator|KeyGeneratorSpi|KeyListener|KeyManagementException|KeyManager|KeyManagerFactory|KeyManagerFactorySpi|Keymap|KeyPair|KeyPairGenerator|KeyPairGeneratorSpi|KeySpec|KeyStore|KeyStoreException|KeyStoreSpi|KeyStroke|Label|LabelUI|LabelView|LanguageCallback|LastOwnerException|LayeredHighlighter|LayoutFocusTraversalPolicy|LayoutManager|LayoutManager2|LayoutQueue|LDAPCertStoreParameters|LdapContext|LdapReferralException|Lease|Level|LexicalHandler|LIFESPAN_POLICY_ID|LifespanPolicy|LifespanPolicyOperations|LifespanPolicyValue|LimitExceededException|Line|Line2D|LineBorder|LineBreakMeasurer|LineEvent|LineListener|LineMetrics|LineNumberInputStream|LineNumberReader|LineUnavailableException|LinkageError|LinkedHashMap|LinkedHashSet|LinkedList|LinkException|LinkLoopException|LinkRef|List|ListCellRenderer|ListDataEvent|ListDataListener|ListIterator|ListModel|ListResourceBundle|ListSelectionEvent|ListSelectionListener|ListSelectionModel|ListUI|ListView|LoaderHandler|Locale|LocalObject|LocateRegistry|LOCATION_FORWARD|Locator|LocatorImpl|Logger|LoggingPermission|LoginContext|LoginException|LoginModule|LogManager|LogRecord|LogStream|Long|LongBuffer|LongHolder|LongLongSeqHelper|LongLongSeqHolder|LongSeqHelper|LongSeqHolder|LookAndFeel|LookupOp|LookupTable|Mac|MacSpi|MalformedInputException|MalformedLinkException|MalformedURLException|ManagerFactoryParameters|Manifest|Map|MappedByteBuffer|MARSHAL|MarshalException|MarshalledObject|MaskFormatter|Matcher|Math|MatteBorder|Media|MediaName|MediaPrintableArea|MediaSize|MediaSizeName|MediaTracker|MediaTray|Member|MemoryCacheImageInputStream|MemoryCacheImageOutputStream|MemoryHandler|MemoryImageSource|Menu|MenuBar|MenuBarUI|MenuComponent|MenuContainer|MenuDragMouseEvent|MenuDragMouseListener|MenuElement|MenuEvent|MenuItem|MenuItemUI|MenuKeyEvent|MenuKeyListener|MenuListener|MenuSelectionManager|MenuShortcut|MessageDigest|MessageDigestSpi|MessageFormat|MessageProp|MetaEventListener|MetalBorders|MetalButtonUI|MetalCheckBoxIcon|MetalCheckBoxUI|MetalComboBoxButton|MetalComboBoxEditor|MetalComboBoxIcon|MetalComboBoxUI|MetalDesktopIconUI|MetalFileChooserUI|MetalIconFactory|MetalInternalFrameTitlePane|MetalInternalFrameUI|MetalLabelUI|MetalLookAndFeel|MetalPopupMenuSeparatorUI|MetalProgressBarUI|MetalRadioButtonUI|MetalRootPaneUI|MetalScrollBarUI|MetalScrollButton|MetalScrollPaneUI|MetalSeparatorUI|MetalSliderUI|MetalSplitPaneUI|MetalTabbedPaneUI|MetalTextFieldUI|MetalTheme|MetalToggleButtonUI|MetalToolBarUI|MetalToolTipUI|MetalTreeUI|MetaMessage|Method|MethodDescriptor|MidiChannel|MidiDevice|MidiDeviceProvider|MidiEvent|MidiFileFormat|MidiFileReader|MidiFileWriter|MidiMessage|MidiSystem|MidiUnavailableException|MimeTypeParseException|MinimalHTMLWriter|MissingResourceException|Mixer|MixerProvider|ModificationItem|Modifier|MouseAdapter|MouseDragGestureRecognizer|MouseEvent|MouseInputAdapter|MouseInputListener|MouseListener|MouseMotionAdapter|MouseMotionListener|MouseWheelEvent|MouseWheelListener|MultiButtonUI|MulticastSocket|MultiColorChooserUI|MultiComboBoxUI|MultiDesktopIconUI|MultiDesktopPaneUI|MultiDoc|MultiDocPrintJob|MultiDocPrintService|MultiFileChooserUI|MultiInternalFrameUI|MultiLabelUI|MultiListUI|MultiLookAndFeel|MultiMenuBarUI|MultiMenuItemUI|MultiOptionPaneUI|MultiPanelUI|MultiPixelPackedSampleModel|MultipleComponentProfileHelper|MultipleComponentProfileHolder|MultipleDocumentHandling|MultipleMaster|MultiPopupMenuUI|MultiProgressBarUI|MultiRootPaneUI|MultiScrollBarUI|MultiScrollPaneUI|MultiSeparatorUI|MultiSliderUI|MultiSpinnerUI|MultiSplitPaneUI|MultiTabbedPaneUI|MultiTableHeaderUI|MultiTableUI|MultiTextUI|MultiToolBarUI|MultiToolTipUI|MultiTreeUI|MultiViewportUI|MutableAttributeSet|MutableComboBoxModel|MutableTreeNode|Name|NameAlreadyBoundException|NameCallback|NameClassPair|NameComponent|NameComponentHelper|NameComponentHolder|NamedNodeMap|NamedValue|NameDynAnyPair|NameDynAnyPairHelper|NameDynAnyPairSeqHelper|NameHelper|NameHolder|NameNotFoundException|NameParser|NamespaceChangeListener|NamespaceSupport|NameValuePair|NameValuePairHelper|NameValuePairSeqHelper|Naming|NamingContext|NamingContextExt|NamingContextExtHelper|NamingContextExtHolder|NamingContextExtOperations|NamingContextExtPOA|NamingContextHelper|NamingContextHolder|NamingContextOperations|NamingContextPOA|NamingEnumeration|NamingEvent|NamingException|NamingExceptionEvent|NamingListener|NamingManager|NamingSecurityException|NavigationFilter|NegativeArraySizeException|NetPermission|NetworkInterface|NO_IMPLEMENT|NO_MEMORY|NO_PERMISSION|NO_RESOURCES|NO_RESPONSE|NoClassDefFoundError|NoConnectionPendingException|NoContext|NoContextHelper|Node|NodeChangeEvent|NodeChangeListener|NodeList|NoInitialContextException|NoninvertibleTransformException|NonReadableChannelException|NonWritableChannelException|NoPermissionException|NoRouteToHostException|NoServant|NoServantHelper|NoSuchAlgorithmException|NoSuchAttributeException|NoSuchElementException|NoSuchFieldError|NoSuchFieldException|NoSuchMethodError|NoSuchMethodException|NoSuchObjectException|NoSuchPaddingException|NoSuchProviderException|NotActiveException|Notation|NotBoundException|NotContextException|NotEmpty|NotEmptyHelper|NotEmptyHolder|NotFound|NotFoundHelper|NotFoundHolder|NotFoundReason|NotFoundReasonHelper|NotFoundReasonHolder|NotOwnerException|NotSerializableException|NotYetBoundException|NotYetConnectedException|NullCipher|NullPointerException|Number|NumberFormat|NumberFormatException|NumberFormatter|NumberOfDocuments|NumberOfInterveningJobs|NumberUp|NumberUpSupported|NumericShaper|NVList|OBJ_ADAPTER|Object|OBJECT_NOT_EXIST|ObjectAlreadyActive|ObjectAlreadyActiveHelper|ObjectChangeListener|ObjectFactory|ObjectFactoryBuilder|ObjectHelper|ObjectHolder|ObjectIdHelper|ObjectImpl|ObjectInput|ObjectInputStream|ObjectInputValidation|ObjectNotActive|ObjectNotActiveHelper|ObjectOutput|ObjectOutputStream|ObjectStreamClass|ObjectStreamConstants|ObjectStreamException|ObjectStreamField|ObjectView|ObjID|Observable|Observer|OctetSeqHelper|OctetSeqHolder|Oid|OMGVMCID|OpenType|Operation|OperationNotSupportedException|Option|OptionalDataException|OptionPaneUI|ORB|ORBInitializer|ORBInitializerOperations|ORBInitInfo|ORBInitInfoOperations|OrientationRequested|OutOfMemoryError|OutputDeviceAssigned|OutputKeys|OutputStream|OutputStreamWriter|OverlappingFileLockException|OverlayLayout|Owner|Package|PackedColorModel|Pageable|PageAttributes|PageFormat|PageRanges|PagesPerMinute|PagesPerMinuteColor|Paint|PaintContext|PaintEvent|Panel|PanelUI|Paper|ParagraphView|Parameter|ParameterBlock|ParameterDescriptor|ParameterMetaData|ParameterMode|ParameterModeHelper|ParameterModeHolder|ParseException|ParsePosition|Parser|ParserAdapter|ParserConfigurationException|ParserDelegator|ParserFactory|PartialResultException|PasswordAuthentication|PasswordCallback|PasswordView|Patch|PathIterator|Pattern|PatternSyntaxException|PBEKey|PBEKeySpec|PBEParameterSpec|PDLOverrideSupported|Permission|PermissionCollection|Permissions|PERSIST_STORE|PersistenceDelegate|PhantomReference|Pipe|PipedInputStream|PipedOutputStream|PipedReader|PipedWriter|PixelGrabber|PixelInterleavedSampleModel|PKCS8EncodedKeySpec|PKIXBuilderParameters|PKIXCertPathBuilderResult|PKIXCertPathChecker|PKIXCertPathValidatorResult|PKIXParameters|PlainDocument|PlainView|POA|POAHelper|POAManager|POAManagerOperations|POAOperations|Point|Point2D|Policy|PolicyError|PolicyErrorCodeHelper|PolicyErrorHelper|PolicyErrorHolder|PolicyFactory|PolicyFactoryOperations|PolicyHelper|PolicyHolder|PolicyListHelper|PolicyListHolder|PolicyNode|PolicyOperations|PolicyQualifierInfo|PolicyTypeHelper|Polygon|PooledConnection|Popup|PopupFactory|PopupMenu|PopupMenuEvent|PopupMenuListener|PopupMenuUI|Port|PortableRemoteObject|PortableRemoteObjectDelegate|PortUnreachableException|Position|PreferenceChangeEvent|PreferenceChangeListener|Preferences|PreferencesFactory|PreparedStatement|PresentationDirection|Principal|PrincipalHolder|Printable|PrinterAbortException|PrinterException|PrinterGraphics|PrinterInfo|PrinterIOException|PrinterIsAcceptingJobs|PrinterJob|PrinterLocation|PrinterMakeAndModel|PrinterMessageFromOperator|PrinterMoreInfo|PrinterMoreInfoManufacturer|PrinterName|PrinterResolution|PrinterState|PrinterStateReason|PrinterStateReasons|PrinterURI|PrintEvent|PrintException|PrintGraphics|PrintJob|PrintJobAdapter|PrintJobAttribute|PrintJobAttributeEvent|PrintJobAttributeListener|PrintJobAttributeSet|PrintJobEvent|PrintJobListener|PrintQuality|PrintRequestAttribute|PrintRequestAttributeSet|PrintService|PrintServiceAttribute|PrintServiceAttributeEvent|PrintServiceAttributeListener|PrintServiceAttributeSet|PrintServiceLookup|PrintStream|PrintWriter|PRIVATE_MEMBER|PrivateCredentialPermission|PrivateKey|PrivilegedAction|PrivilegedActionException|PrivilegedExceptionAction|Process|ProcessingInstruction|ProfileDataException|ProfileIdHelper|ProgressBarUI|ProgressMonitor|ProgressMonitorInputStream|Properties|PropertyChangeEvent|PropertyChangeListener|PropertyChangeListenerProxy|PropertyChangeSupport|PropertyDescriptor|PropertyEditor|PropertyEditorManager|PropertyEditorSupport|PropertyPermission|PropertyResourceBundle|PropertyVetoException|ProtectionDomain|ProtocolException|Provider|ProviderException|Proxy|PSSParameterSpec|PUBLIC_MEMBER|PublicKey|PushbackInputStream|PushbackReader|QuadCurve2D|QueuedJobCount|Random|RandomAccess|RandomAccessFile|Raster|RasterFormatException|RasterOp|RC2ParameterSpec|RC5ParameterSpec|ReadableByteChannel|Reader|ReadOnlyBufferException|Receiver|Rectangle|Rectangle2D|RectangularShape|Ref|RefAddr|Reference|Referenceable|ReferenceQueue|ReferenceUriSchemesSupported|ReferralException|ReflectPermission|Refreshable|RefreshFailedException|RegisterableService|Registry|RegistryHandler|RemarshalException|Remote|RemoteCall|RemoteException|RemoteObject|RemoteRef|RemoteServer|RemoteStub|RenderableImage|RenderableImageOp|RenderableImageProducer|RenderContext|RenderedImage|RenderedImageFactory|Renderer|RenderingHints|RepaintManager|ReplicateScaleFilter|RepositoryIdHelper|Request|REQUEST_PROCESSING_POLICY_ID|RequestInfo|RequestInfoOperations|RequestingUserName|RequestProcessingPolicy|RequestProcessingPolicyOperations|RequestProcessingPolicyValue|RescaleOp|ResolutionSyntax|Resolver|ResolveResult|ResourceBundle|ResponseHandler|Result|ResultSet|ResultSetMetaData|ReverbType|RGBImageFilter|RMIClassLoader|RMIClassLoaderSpi|RMIClientSocketFactory|RMIFailureHandler|RMISecurityException|RMISecurityManager|RMIServerSocketFactory|RMISocketFactory|Robot|RootPaneContainer|RootPaneUI|RoundRectangle2D|RowMapper|RowSet|RowSetEvent|RowSetInternal|RowSetListener|RowSetMetaData|RowSetReader|RowSetWriter|RSAKey|RSAKeyGenParameterSpec|RSAMultiPrimePrivateCrtKey|RSAMultiPrimePrivateCrtKeySpec|RSAOtherPrimeInfo|RSAPrivateCrtKey|RSAPrivateCrtKeySpec|RSAPrivateKey|RSAPrivateKeySpec|RSAPublicKey|RSAPublicKeySpec|RTFEditorKit|RuleBasedCollator|Runnable|Runtime|RunTime|RuntimeException|RunTimeOperations|RuntimePermission|SampleModel|Savepoint|SAXException|SAXNotRecognizedException|SAXNotSupportedException|SAXParseException|SAXParser|SAXParserFactory|SAXResult|SAXSource|SAXTransformerFactory|ScatteringByteChannel|SchemaViolationException|Scrollable|Scrollbar|ScrollBarUI|ScrollPane|ScrollPaneAdjustable|ScrollPaneConstants|ScrollPaneLayout|ScrollPaneUI|SealedObject|SearchControls|SearchResult|SecretKey|SecretKeyFactory|SecretKeyFactorySpi|SecretKeySpec|SecureClassLoader|SecureRandom|SecureRandomSpi|Security|SecurityException|SecurityManager|SecurityPermission|Segment|SelectableChannel|SelectionKey|Selector|SelectorProvider|SeparatorUI|Sequence|SequenceInputStream|Sequencer|Serializable|SerializablePermission|Servant|SERVANT_RETENTION_POLICY_ID|ServantActivator|ServantActivatorHelper|ServantActivatorOperations|ServantActivatorPOA|ServantAlreadyActive|ServantAlreadyActiveHelper|ServantLocator|ServantLocatorHelper|ServantLocatorOperations|ServantLocatorPOA|ServantManager|ServantManagerOperations|ServantNotActive|ServantNotActiveHelper|ServantObject|ServantRetentionPolicy|ServantRetentionPolicyOperations|ServantRetentionPolicyValue|ServerCloneException|ServerError|ServerException|ServerNotActiveException|ServerRef|ServerRequest|ServerRequestInfo|ServerRequestInfoOperations|ServerRequestInterceptor|ServerRequestInterceptorOperations|ServerRuntimeException|ServerSocket|ServerSocketChannel|ServerSocketFactory|ServiceContext|ServiceContextHelper|ServiceContextHolder|ServiceContextListHelper|ServiceContextListHolder|ServiceDetail|ServiceDetailHelper|ServiceIdHelper|ServiceInformation|ServiceInformationHelper|ServiceInformationHolder|ServicePermission|ServiceRegistry|ServiceUI|ServiceUIFactory|ServiceUnavailableException|Set|SetOfIntegerSyntax|SetOverrideType|SetOverrideTypeHelper|Severity|Shape|ShapeGraphicAttribute|SheetCollate|Short|ShortBuffer|ShortBufferException|ShortHolder|ShortLookupTable|ShortMessage|ShortSeqHelper|ShortSeqHolder|Sides|Signature|SignatureException|SignatureSpi|SignedObject|Signer|SimpleAttributeSet|SimpleBeanInfo|SimpleDateFormat|SimpleDoc|SimpleFormatter|SimpleTimeZone|SinglePixelPackedSampleModel|SingleSelectionModel|Size2DSyntax|SizeLimitExceededException|SizeRequirements|SizeSequence|Skeleton|SkeletonMismatchException|SkeletonNotFoundException|SliderUI|Socket|SocketAddress|SocketChannel|SocketException|SocketFactory|SocketHandler|SocketImpl|SocketImplFactory|SocketOptions|SocketPermission|SocketSecurityException|SocketTimeoutException|SoftBevelBorder|SoftReference|SortedMap|SortedSet|SortingFocusTraversalPolicy|Soundbank|SoundbankReader|SoundbankResource|Source|SourceDataLine|SourceLocator|SpinnerDateModel|SpinnerListModel|SpinnerModel|SpinnerNumberModel|SpinnerUI|SplitPaneUI|Spring|SpringLayout|SQLData|SQLException|SQLInput|SQLOutput|SQLPermission|SQLWarning|SSLContext|SSLContextSpi|SSLException|SSLHandshakeException|SSLKeyException|SSLPeerUnverifiedException|SSLPermission|SSLProtocolException|SSLServerSocket|SSLServerSocketFactory|SSLSession|SSLSessionBindingEvent|SSLSessionBindingListener|SSLSessionContext|SSLSocket|SSLSocketFactory|Stack|StackOverflowError|StackTraceElement|StartTlsRequest|StartTlsResponse|State|StateEdit|StateEditable|StateFactory|Statement|Streamable|StreamableValue|StreamCorruptedException|StreamHandler|StreamPrintService|StreamPrintServiceFactory|StreamResult|StreamSource|StreamTokenizer|StrictMath|String|StringBuffer|StringBufferInputStream|StringCharacterIterator|StringContent|StringHolder|StringIndexOutOfBoundsException|StringNameHelper|StringReader|StringRefAddr|StringSelection|StringSeqHelper|StringSeqHolder|StringTokenizer|StringValueHelper|StringWriter|Stroke|Struct|StructMember|StructMemberHelper|Stub|StubDelegate|StubNotFoundException|Style|StyleConstants|StyleContext|StyledDocument|StyledEditorKit|StyleSheet|Subject|SubjectDomainCombiner|SUCCESSFUL|SupportedValuesAttribute|SwingConstants|SwingPropertyChangeSupport|SwingUtilities|SYNC_WITH_TRANSPORT|SyncFailedException|SyncScopeHelper|Synthesizer|SysexMessage|System|SYSTEM_EXCEPTION|SystemColor|SystemException|SystemFlavorMap|TabableView|TabbedPaneUI|TabExpander|TableCellEditor|TableCellRenderer|TableColumn|TableColumnModel|TableColumnModelEvent|TableColumnModelListener|TableHeaderUI|TableModel|TableModelEvent|TableModelListener|TableUI|TableView|TabSet|TabStop|TAG_ALTERNATE_IIOP_ADDRESS|TAG_CODE_SETS|TAG_INTERNET_IOP|TAG_JAVA_CODEBASE|TAG_MULTIPLE_COMPONENTS|TAG_ORB_TYPE|TAG_POLICIES|TagElement|TaggedComponent|TaggedComponentHelper|TaggedComponentHolder|TaggedProfile|TaggedProfileHelper|TaggedProfileHolder|TargetDataLine|TCKind|Templates|TemplatesHandler|Text|TextAction|TextArea|TextAttribute|TextComponent|TextEvent|TextField|TextHitInfo|TextInputCallback|TextLayout|TextListener|TextMeasurer|TextOutputCallback|TextSyntax|TextUI|TexturePaint|Thread|THREAD_POLICY_ID|ThreadDeath|ThreadGroup|ThreadLocal|ThreadPolicy|ThreadPolicyOperations|ThreadPolicyValue|Throwable|Tie|TileObserver|Time|TimeLimitExceededException|Timer|TimerTask|Timestamp|TimeZone|TitledBorder|ToolBarUI|Toolkit|ToolTipManager|ToolTipUI|TooManyListenersException|Track|TRANSACTION_REQUIRED|TRANSACTION_ROLLEDBACK|TransactionRequiredException|TransactionRolledbackException|TransactionService|Transferable|TransferHandler|TransformAttribute|Transformer|TransformerConfigurationException|TransformerException|TransformerFactory|TransformerFactoryConfigurationError|TransformerHandler|TRANSIENT|Transmitter|Transparency|TRANSPORT_RETRY|TreeCellEditor|TreeCellRenderer|TreeExpansionEvent|TreeExpansionListener|TreeMap|TreeModel|TreeModelEvent|TreeModelListener|TreeNode|TreePath|TreeSelectionEvent|TreeSelectionListener|TreeSelectionModel|TreeSet|TreeUI|TreeWillExpandListener|TrustAnchor|TrustManager|TrustManagerFactory|TrustManagerFactorySpi|TypeCode|TypeCodeHolder|TypeMismatch|TypeMismatchHelper|Types|UID|UIDefaults|UIManager|UIResource|ULongLongSeqHelper|ULongLongSeqHolder|ULongSeqHelper|ULongSeqHolder|UndeclaredThrowableException|UndoableEdit|UndoableEditEvent|UndoableEditListener|UndoableEditSupport|UndoManager|UnexpectedException|UnicastRemoteObject|UnionMember|UnionMemberHelper|UNKNOWN|UnknownEncoding|UnknownEncodingHelper|UnknownError|UnknownException|UnknownGroupException|UnknownHostException|UnknownObjectException|UnknownServiceException|UnknownUserException|UnknownUserExceptionHelper|UnknownUserExceptionHolder|UnmappableCharacterException|UnmarshalException|UnmodifiableSetException|UnrecoverableKeyException|Unreferenced|UnresolvedAddressException|UnresolvedPermission|UnsatisfiedLinkError|UnsolicitedNotification|UnsolicitedNotificationEvent|UnsolicitedNotificationListener|UNSUPPORTED_POLICY|UNSUPPORTED_POLICY_VALUE|UnsupportedAddressTypeException|UnsupportedAudioFileException|UnsupportedCallbackException|UnsupportedCharsetException|UnsupportedClassVersionError|UnsupportedEncodingException|UnsupportedFlavorException|UnsupportedLookAndFeelException|UnsupportedOperationException|URI|URIException|URIResolver|URISyntax|URISyntaxException|URL|URLClassLoader|URLConnection|URLDecoder|URLEncoder|URLStreamHandler|URLStreamHandlerFactory|URLStringHelper|USER_EXCEPTION|UserException|UShortSeqHelper|UShortSeqHolder|UTFDataFormatException|Util|UtilDelegate|Utilities|ValueBase|ValueBaseHelper|ValueBaseHolder|ValueFactory|ValueHandler|ValueMember|ValueMemberHelper|VariableHeightLayoutCache|Vector|VerifyError|VersionSpecHelper|VetoableChangeListener|VetoableChangeListenerProxy|VetoableChangeSupport|View|ViewFactory|ViewportLayout|ViewportUI|VirtualMachineError|Visibility|VisibilityHelper|VM_ABSTRACT|VM_CUSTOM|VM_NONE|VM_TRUNCATABLE|VMID|VoiceStatus|Void|VolatileImage|WCharSeqHelper|WCharSeqHolder|WeakHashMap|WeakReference|Window|WindowAdapter|WindowConstants|WindowEvent|WindowFocusListener|WindowListener|WindowStateListener|WrappedPlainView|WritableByteChannel|WritableRaster|WritableRenderedImage|WriteAbortedException|Writer|WrongAdapter|WrongAdapterHelper|WrongPolicy|WrongPolicyHelper|WrongTransaction|WrongTransactionHelper|WrongTransactionHolder|WStringSeqHelper|WStringSeqHolder|WStringValueHelper|X500Principal|X500PrivateCredential|X509Certificate|X509CertSelector|X509CRL|X509CRLEntry|X509CRLSelector|X509EncodedKeySpec|X509Extension|X509KeyManager|X509TrustManager|XAConnection|XADataSource|XAException|XAResource|Xid|XMLDecoder|XMLEncoder|XMLFilter|XMLFilterImpl|XMLFormatter|XMLReader|XMLReaderAdapter|XMLReaderFactory|ZipEntry|ZipException|ZipFile|ZipInputStream|ZipOutputStream|ZoneView|_BindingIteratorImplBase|_BindingIteratorStub|_DynAnyFactoryStub|_DynAnyStub|_DynArrayStub|_DynEnumStub|_DynFixedStub|_DynSequenceStub|_DynStructStub|_DynUnionStub|_DynValueStub|_IDLTypeStub|_NamingContextExtStub|_NamingContextImplBase|_NamingContextStub|_PolicyStub|_Remote_Stub|_ServantActivatorStub|_ServantLocatorStub)$/',
- ),
- 8 =>
- array (
- ),
- 9 =>
- array (
- ),
- 10 =>
- array (
- ),
- 11 =>
- array (
- ),
- 12 =>
- array (
- ),
- ),
- 2 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 =>
- array (
- 'types' => '/^(boolean|byte|char|const|double|final|float|int|long|short|static|void)$/',
- 'reserved' => '/^(import|package|abstract|break|case|catch|class|continue|default|do|else|extends|false|finally|for|goto|if|implements|instanceof|interface|native|new|null|private|protected|public|return|super|strictfp|switch|synchronized|this|throws|throw|transient|true|try|volatile|while)$/',
- 'builtin' => '/^(AbstractAction|AbstractBorder|AbstractButton|AbstractCellEditor|AbstractCollection|AbstractColorChooserPanel|AbstractDocument|AbstractInterruptibleChannel|AbstractLayoutCache|AbstractList|AbstractListModel|AbstractMap|AbstractMethodError|AbstractPreferences|AbstractSelectableChannel|AbstractSelectionKey|AbstractSelector|AbstractSequentialList|AbstractSet|AbstractSpinnerModel|AbstractTableModel|AbstractUndoableEdit|AbstractWriter|AccessControlContext|AccessControlException|AccessController|AccessException|Accessible|AccessibleAction|AccessibleBundle|AccessibleComponent|AccessibleContext|AccessibleEditableText|AccessibleExtendedComponent|AccessibleExtendedTable|AccessibleHyperlink|AccessibleHypertext|AccessibleIcon|AccessibleKeyBinding|AccessibleObject|AccessibleRelation|AccessibleRelationSet|AccessibleResourceBundle|AccessibleRole|AccessibleSelection|AccessibleState|AccessibleStateSet|AccessibleTable|AccessibleTableModelChange|AccessibleText|AccessibleValue|AccountExpiredException|Acl|AclEntry|AclNotFoundException|Action|ActionEvent|ActionListener|ActionMap|ActionMapUIResource|Activatable|ActivateFailedException|ActivationDesc|ActivationException|ActivationGroup|ActivationGroup_Stub|ActivationGroupDesc|ActivationGroupID|ActivationID|ActivationInstantiator|ActivationMonitor|ActivationSystem|Activator|ActiveEvent|AdapterActivator|AdapterActivatorOperations|AdapterAlreadyExists|AdapterAlreadyExistsHelper|AdapterInactive|AdapterInactiveHelper|AdapterNonExistent|AdapterNonExistentHelper|AddressHelper|Adjustable|AdjustmentEvent|AdjustmentListener|Adler32|AffineTransform|AffineTransformOp|AlgorithmParameterGenerator|AlgorithmParameterGeneratorSpi|AlgorithmParameters|AlgorithmParameterSpec|AlgorithmParametersSpi|AllPermission|AlphaComposite|AlreadyBound|AlreadyBoundException|AlreadyBoundHelper|AlreadyBoundHolder|AlreadyConnectedException|AncestorEvent|AncestorListener|Annotation|Any|AnyHolder|AnySeqHelper|AnySeqHolder|AppConfigurationEntry|Applet|AppletContext|AppletInitializer|AppletStub|ApplicationException|Arc2D|Area|AreaAveragingScaleFilter|ARG_IN|ARG_INOUT|ARG_OUT|ArithmeticException|Array|ArrayIndexOutOfBoundsException|ArrayList|Arrays|ArrayStoreException|AssertionError|AsyncBoxView|AsynchronousCloseException|Attr|Attribute|AttributedCharacterIterator|AttributedString|AttributeException|AttributeInUseException|AttributeList|AttributeListImpl|AttributeModificationException|Attributes|AttributeSet|AttributeSetUtilities|AttributesImpl|AudioClip|AudioFileFormat|AudioFileReader|AudioFileWriter|AudioFormat|AudioInputStream|AudioPermission|AudioSystem|AuthenticationException|AuthenticationNotSupportedException|Authenticator|AuthPermission|Autoscroll|AWTError|AWTEvent|AWTEventListener|AWTEventListenerProxy|AWTEventMulticaster|AWTException|AWTKeyStroke|AWTPermission|BackingStoreException|BAD_CONTEXT|BAD_INV_ORDER|BAD_OPERATION|BAD_PARAM|BAD_POLICY|BAD_POLICY_TYPE|BAD_POLICY_VALUE|BAD_TYPECODE|BadKind|BadLocationException|BadPaddingException|BandCombineOp|BandedSampleModel|BasicArrowButton|BasicAttribute|BasicAttributes|BasicBorders|BasicButtonListener|BasicButtonUI|BasicCheckBoxMenuItemUI|BasicCheckBoxUI|BasicColorChooserUI|BasicComboBoxEditor|BasicComboBoxRenderer|BasicComboBoxUI|BasicComboPopup|BasicDesktopIconUI|BasicDesktopPaneUI|BasicDirectoryModel|BasicEditorPaneUI|BasicFileChooserUI|BasicFormattedTextFieldUI|BasicGraphicsUtils|BasicHTML|BasicIconFactory|BasicInternalFrameTitlePane|BasicInternalFrameUI|BasicLabelUI|BasicListUI|BasicLookAndFeel|BasicMenuBarUI|BasicMenuItemUI|BasicMenuUI|BasicOptionPaneUI|BasicPanelUI|BasicPasswordFieldUI|BasicPermission|BasicPopupMenuSeparatorUI|BasicPopupMenuUI|BasicProgressBarUI|BasicRadioButtonMenuItemUI|BasicRadioButtonUI|BasicRootPaneUI|BasicScrollBarUI|BasicScrollPaneUI|BasicSeparatorUI|BasicSliderUI|BasicSpinnerUI|BasicSplitPaneDivider|BasicSplitPaneUI|BasicStroke|BasicTabbedPaneUI|BasicTableHeaderUI|BasicTableUI|BasicTextAreaUI|BasicTextFieldUI|BasicTextPaneUI|BasicTextUI|BasicToggleButtonUI|BasicToolBarSeparatorUI|BasicToolBarUI|BasicToolTipUI|BasicTreeUI|BasicViewportUI|BatchUpdateException|BeanContext|BeanContextChild|BeanContextChildComponentProxy|BeanContextChildSupport|BeanContextContainerProxy|BeanContextEvent|BeanContextMembershipEvent|BeanContextMembershipListener|BeanContextProxy|BeanContextServiceAvailableEvent|BeanContextServiceProvider|BeanContextServiceProviderBeanInfo|BeanContextServiceRevokedEvent|BeanContextServiceRevokedListener|BeanContextServices|BeanContextServicesListener|BeanContextServicesSupport|BeanContextSupport|BeanDescriptor|BeanInfo|Beans|BevelBorder|Bidi|BigDecimal|BigInteger|BinaryRefAddr|BindException|Binding|BindingHelper|BindingHolder|BindingIterator|BindingIteratorHelper|BindingIteratorHolder|BindingIteratorOperations|BindingIteratorPOA|BindingListHelper|BindingListHolder|BindingType|BindingTypeHelper|BindingTypeHolder|BitSet|Blob|BlockView|Book|Boolean|BooleanControl|BooleanHolder|BooleanSeqHelper|BooleanSeqHolder|Border|BorderFactory|BorderLayout|BorderUIResource|BoundedRangeModel|Bounds|Box|BoxedValueHelper|BoxLayout|BoxView|BreakIterator|Buffer|BufferCapabilities|BufferedImage|BufferedImageFilter|BufferedImageOp|BufferedInputStream|BufferedOutputStream|BufferedReader|BufferedWriter|BufferOverflowException|BufferStrategy|BufferUnderflowException|Button|ButtonGroup|ButtonModel|ButtonUI|Byte|ByteArrayInputStream|ByteArrayOutputStream|ByteBuffer|ByteChannel|ByteHolder|ByteLookupTable|ByteOrder|Calendar|CallableStatement|Callback|CallbackHandler|CancelablePrintJob|CancelledKeyException|CannotProceed|CannotProceedException|CannotProceedHelper|CannotProceedHolder|CannotRedoException|CannotUndoException|Canvas|CardLayout|Caret|CaretEvent|CaretListener|CDATASection|CellEditor|CellEditorListener|CellRendererPane|Certificate|CertificateEncodingException|CertificateException|CertificateExpiredException|CertificateFactory|CertificateFactorySpi|CertificateNotYetValidException|CertificateParsingException|CertPath|CertPathBuilder|CertPathBuilderException|CertPathBuilderResult|CertPathBuilderSpi|CertPathParameters|CertPathValidator|CertPathValidatorException|CertPathValidatorResult|CertPathValidatorSpi|CertSelector|CertStore|CertStoreException|CertStoreParameters|CertStoreSpi|ChangedCharSetException|ChangeEvent|ChangeListener|Channel|ChannelBinding|Channels|Character|CharacterCodingException|CharacterData|CharacterIterator|CharArrayReader|CharArrayWriter|CharBuffer|CharConversionException|CharHolder|CharSeqHelper|CharSeqHolder|CharSequence|Charset|CharsetDecoder|CharsetEncoder|CharsetProvider|Checkbox|CheckboxGroup|CheckboxMenuItem|CheckedInputStream|CheckedOutputStream|Checksum|Choice|ChoiceCallback|ChoiceFormat|Chromaticity|Cipher|CipherInputStream|CipherOutputStream|CipherSpi|Class|ClassCastException|ClassCircularityError|ClassDesc|ClassFormatError|ClassLoader|ClassNotFoundException|ClientRequestInfo|ClientRequestInfoOperations|ClientRequestInterceptor|ClientRequestInterceptorOperations|Clip|Clipboard|ClipboardOwner|Clob|Cloneable|CloneNotSupportedException|ClosedByInterruptException|ClosedChannelException|ClosedSelectorException|CMMException|Codec|CodecFactory|CodecFactoryHelper|CodecFactoryOperations|CodecOperations|CoderMalfunctionError|CoderResult|CodeSets|CodeSource|CodingErrorAction|CollationElementIterator|CollationKey|Collator|Collection|CollectionCertStoreParameters|Collections|Color|ColorChooserComponentFactory|ColorChooserUI|ColorConvertOp|ColorModel|ColorSelectionModel|ColorSpace|ColorSupported|ColorUIResource|ComboBoxEditor|ComboBoxModel|ComboBoxUI|ComboPopup|COMM_FAILURE|Comment|CommunicationException|Comparable|Comparator|Compiler|CompletionStatus|CompletionStatusHelper|Component|ComponentAdapter|ComponentColorModel|ComponentEvent|ComponentIdHelper|ComponentInputMap|ComponentInputMapUIResource|ComponentListener|ComponentOrientation|ComponentSampleModel|ComponentUI|ComponentView|Composite|CompositeContext|CompositeName|CompositeView|CompoundBorder|CompoundControl|CompoundEdit|CompoundName|Compression|ConcurrentModificationException|Configuration|ConfigurationException|ConfirmationCallback|ConnectException|ConnectIOException|Connection|ConnectionEvent|ConnectionEventListener|ConnectionPendingException|ConnectionPoolDataSource|ConsoleHandler|Constructor|Container|ContainerAdapter|ContainerEvent|ContainerListener|ContainerOrderFocusTraversalPolicy|ContentHandler|ContentHandlerFactory|ContentModel|Context|ContextList|ContextNotEmptyException|ContextualRenderedImageFactory|Control|ControlFactory|ControllerEventListener|ConvolveOp|CookieHolder|Copies|CopiesSupported|CRC32|CredentialExpiredException|CRL|CRLException|CRLSelector|CropImageFilter|CSS|CTX_RESTRICT_SCOPE|CubicCurve2D|Currency|Current|CurrentHelper|CurrentHolder|CurrentOperations|Cursor|Customizer|CustomMarshal|CustomValue|DATA_CONVERSION|DatabaseMetaData|DataBuffer|DataBufferByte|DataBufferDouble|DataBufferFloat|DataBufferInt|DataBufferShort|DataBufferUShort|DataFlavor|DataFormatException|DatagramChannel|DatagramPacket|DatagramSocket|DatagramSocketImpl|DatagramSocketImplFactory|DataInput|DataInputStream|DataLine|DataOutput|DataOutputStream|DataSource|DataTruncation|Date|DateFormat|DateFormatSymbols|DateFormatter|DateTimeAtCompleted|DateTimeAtCreation|DateTimeAtProcessing|DateTimeSyntax|DebugGraphics|DecimalFormat|DecimalFormatSymbols|DeclHandler|DefaultBoundedRangeModel|DefaultButtonModel|DefaultCaret|DefaultCellEditor|DefaultColorSelectionModel|DefaultComboBoxModel|DefaultDesktopManager|DefaultEditorKit|DefaultFocusManager|DefaultFocusTraversalPolicy|DefaultFormatter|DefaultFormatterFactory|DefaultHandler|DefaultHighlighter|DefaultKeyboardFocusManager|DefaultListCellRenderer|DefaultListModel|DefaultListSelectionModel|DefaultMenuLayout|DefaultMetalTheme|DefaultMutableTreeNode|DefaultPersistenceDelegate|DefaultSingleSelectionModel|DefaultStyledDocument|DefaultTableCellRenderer|DefaultTableColumnModel|DefaultTableModel|DefaultTextUI|DefaultTreeCellEditor|DefaultTreeCellRenderer|DefaultTreeModel|DefaultTreeSelectionModel|DefinitionKind|DefinitionKindHelper|Deflater|DeflaterOutputStream|Delegate|DelegationPermission|DESedeKeySpec|DesignMode|DESKeySpec|DesktopIconUI|DesktopManager|DesktopPaneUI|Destination|Destroyable|DestroyFailedException|DGC|DHGenParameterSpec|DHKey|DHParameterSpec|DHPrivateKey|DHPrivateKeySpec|DHPublicKey|DHPublicKeySpec|Dialog|Dictionary|DigestException|DigestInputStream|DigestOutputStream|Dimension|Dimension2D|DimensionUIResource|DirContext|DirectColorModel|DirectoryManager|DirObjectFactory|DirStateFactory|DisplayMode|DnDConstants|Doc|DocAttribute|DocAttributeSet|DocFlavor|DocPrintJob|Document|DocumentBuilder|DocumentBuilderFactory|DocumentEvent|DocumentFilter|DocumentFragment|DocumentHandler|DocumentListener|DocumentName|DocumentParser|DocumentType|DomainCombiner|DomainManager|DomainManagerOperations|DOMException|DOMImplementation|DOMLocator|DOMResult|DOMSource|Double|DoubleBuffer|DoubleHolder|DoubleSeqHelper|DoubleSeqHolder|DragGestureEvent|DragGestureListener|DragGestureRecognizer|DragSource|DragSourceAdapter|DragSourceContext|DragSourceDragEvent|DragSourceDropEvent|DragSourceEvent|DragSourceListener|DragSourceMotionListener|Driver|DriverManager|DriverPropertyInfo|DropTarget|DropTargetAdapter|DropTargetContext|DropTargetDragEvent|DropTargetDropEvent|DropTargetEvent|DropTargetListener|DSAKey|DSAKeyPairGenerator|DSAParameterSpec|DSAParams|DSAPrivateKey|DSAPrivateKeySpec|DSAPublicKey|DSAPublicKeySpec|DTD|DTDConstants|DTDHandler|DuplicateName|DuplicateNameHelper|DynamicImplementation|DynAny|DynAnyFactory|DynAnyFactoryHelper|DynAnyFactoryOperations|DynAnyHelper|DynAnyOperations|DynAnySeqHelper|DynArray|DynArrayHelper|DynArrayOperations|DynEnum|DynEnumHelper|DynEnumOperations|DynFixed|DynFixedHelper|DynFixedOperations|DynSequence|DynSequenceHelper|DynSequenceOperations|DynStruct|DynStructHelper|DynStructOperations|DynUnion|DynUnionHelper|DynUnionOperations|DynValue|DynValueBox|DynValueBoxOperations|DynValueCommon|DynValueCommonOperations|DynValueHelper|DynValueOperations|EditorKit|Element|ElementIterator|Ellipse2D|EmptyBorder|EmptyStackException|EncodedKeySpec|Encoder|Encoding|ENCODING_CDR_ENCAPS|EncryptedPrivateKeyInfo|Entity|EntityReference|EntityResolver|EnumControl|Enumeration|EnumSyntax|Environment|EOFException|Error|ErrorHandler|ErrorListener|ErrorManager|EtchedBorder|Event|EventContext|EventDirContext|EventHandler|EventListener|EventListenerList|EventListenerProxy|EventObject|EventQueue|EventSetDescriptor|Exception|ExceptionInInitializerError|ExceptionList|ExceptionListener|ExemptionMechanism|ExemptionMechanismException|ExemptionMechanismSpi|ExpandVetoException|ExportException|Expression|ExtendedRequest|ExtendedResponse|Externalizable|FactoryConfigurationError|FailedLoginException|FeatureDescriptor|Fidelity|Field|FieldNameHelper|FieldPosition|FieldView|File|FileCacheImageInputStream|FileCacheImageOutputStream|FileChannel|FileChooserUI|FileDescriptor|FileDialog|FileFilter|FileHandler|FileImageInputStream|FileImageOutputStream|FileInputStream|FileLock|FileLockInterruptionException|FilenameFilter|FileNameMap|FileNotFoundException|FileOutputStream|FilePermission|FileReader|FileSystemView|FileView|FileWriter|Filter|FilteredImageSource|FilterInputStream|FilterOutputStream|FilterReader|FilterWriter|Finishings|FixedHeightLayoutCache|FixedHolder|FlatteningPathIterator|FlavorException|FlavorMap|FlavorTable|Float|FloatBuffer|FloatControl|FloatHolder|FloatSeqHelper|FloatSeqHolder|FlowLayout|FlowView|FocusAdapter|FocusEvent|FocusListener|FocusManager|FocusTraversalPolicy|Font|FontFormatException|FontMetrics|FontRenderContext|FontUIResource|Format|FormatConversionProvider|FormatMismatch|FormatMismatchHelper|Formatter|FormView|ForwardRequest|ForwardRequestHelper|Frame|FREE_MEM|GapContent|GatheringByteChannel|GeneralPath|GeneralSecurityException|GlyphJustificationInfo|GlyphMetrics|GlyphVector|GlyphView|GradientPaint|GraphicAttribute|Graphics|Graphics2D|GraphicsConfigTemplate|GraphicsConfiguration|GraphicsDevice|GraphicsEnvironment|GrayFilter|GregorianCalendar|GridBagConstraints|GridBagLayout|GridLayout|Group|GSSContext|GSSCredential|GSSException|GSSManager|GSSName|Guard|GuardedObject|GZIPInputStream|GZIPOutputStream|Handler|HandlerBase|HandshakeCompletedEvent|HandshakeCompletedListener|HasControls|HashAttributeSet|HashDocAttributeSet|HashMap|HashPrintJobAttributeSet|HashPrintRequestAttributeSet|HashPrintServiceAttributeSet|HashSet|Hashtable|HeadlessException|HierarchyBoundsAdapter|HierarchyBoundsListener|HierarchyEvent|HierarchyListener|Highlighter|HostnameVerifier|HTML|HTMLDocument|HTMLEditorKit|HTMLFrameHyperlinkEvent|HTMLWriter|HttpsURLConnection|HttpURLConnection|HyperlinkEvent|HyperlinkListener|ICC_ColorSpace|ICC_Profile|ICC_ProfileGray|ICC_ProfileRGB|Icon|IconUIResource|IconView|ID_ASSIGNMENT_POLICY_ID|ID_UNIQUENESS_POLICY_ID|IdAssignmentPolicy|IdAssignmentPolicyOperations|IdAssignmentPolicyValue|IdentifierHelper|Identity|IdentityHashMap|IdentityScope|IDLEntity|IDLType|IDLTypeHelper|IDLTypeOperations|IdUniquenessPolicy|IdUniquenessPolicyOperations|IdUniquenessPolicyValue|IIOByteBuffer|IIOException|IIOImage|IIOInvalidTreeException|IIOMetadata|IIOMetadataController|IIOMetadataFormat|IIOMetadataFormatImpl|IIOMetadataNode|IIOParam|IIOParamController|IIOReadProgressListener|IIOReadUpdateListener|IIOReadWarningListener|IIORegistry|IIOServiceProvider|IIOWriteProgressListener|IIOWriteWarningListener|IllegalAccessError|IllegalAccessException|IllegalArgumentException|IllegalBlockingModeException|IllegalBlockSizeException|IllegalCharsetNameException|IllegalComponentStateException|IllegalMonitorStateException|IllegalPathStateException|IllegalSelectorException|IllegalStateException|IllegalThreadStateException|Image|ImageCapabilities|ImageConsumer|ImageFilter|ImageGraphicAttribute|ImageIcon|ImageInputStream|ImageInputStreamImpl|ImageInputStreamSpi|ImageIO|ImageObserver|ImageOutputStream|ImageOutputStreamImpl|ImageOutputStreamSpi|ImageProducer|ImageReader|ImageReaderSpi|ImageReaderWriterSpi|ImageReadParam|ImageTranscoder|ImageTranscoderSpi|ImageTypeSpecifier|ImageView|ImageWriteParam|ImageWriter|ImageWriterSpi|ImagingOpException|IMP_LIMIT|IMPLICIT_ACTIVATION_POLICY_ID|ImplicitActivationPolicy|ImplicitActivationPolicyOperations|ImplicitActivationPolicyValue|IncompatibleClassChangeError|InconsistentTypeCode|InconsistentTypeCodeHelper|IndexColorModel|IndexedPropertyDescriptor|IndexOutOfBoundsException|IndirectionException|Inet4Address|Inet6Address|InetAddress|InetSocketAddress|Inflater|InflaterInputStream|InheritableThreadLocal|InitialContext|InitialContextFactory|InitialContextFactoryBuilder|InitialDirContext|INITIALIZE|InitialLdapContext|InlineView|InputContext|InputEvent|InputMap|InputMapUIResource|InputMethod|InputMethodContext|InputMethodDescriptor|InputMethodEvent|InputMethodHighlight|InputMethodListener|InputMethodRequests|InputSource|InputStream|InputStreamReader|InputSubset|InputVerifier|Insets|InsetsUIResource|InstantiationError|InstantiationException|Instrument|InsufficientResourcesException|IntBuffer|Integer|IntegerSyntax|Interceptor|InterceptorOperations|INTERNAL|InternalError|InternalFrameAdapter|InternalFrameEvent|InternalFrameFocusTraversalPolicy|InternalFrameListener|InternalFrameUI|InternationalFormatter|InterruptedException|InterruptedIOException|InterruptedNamingException|InterruptibleChannel|INTF_REPOS|IntHolder|IntrospectionException|Introspector|INV_FLAG|INV_IDENT|INV_OBJREF|INV_POLICY|Invalid|INVALID_TRANSACTION|InvalidAddress|InvalidAddressHelper|InvalidAddressHolder|InvalidAlgorithmParameterException|InvalidAttributeIdentifierException|InvalidAttributesException|InvalidAttributeValueException|InvalidClassException|InvalidDnDOperationException|InvalidKeyException|InvalidKeySpecException|InvalidMarkException|InvalidMidiDataException|InvalidName|InvalidNameException|InvalidNameHelper|InvalidNameHolder|InvalidObjectException|InvalidParameterException|InvalidParameterSpecException|InvalidPolicy|InvalidPolicyHelper|InvalidPreferencesFormatException|InvalidSearchControlsException|InvalidSearchFilterException|InvalidSeq|InvalidSlot|InvalidSlotHelper|InvalidTransactionException|InvalidTypeForEncoding|InvalidTypeForEncodingHelper|InvalidValue|InvalidValueHelper|InvocationEvent|InvocationHandler|InvocationTargetException|InvokeHandler|IOException|IOR|IORHelper|IORHolder|IORInfo|IORInfoOperations|IORInterceptor|IORInterceptorOperations|IRObject|IRObjectOperations|IstringHelper|ItemEvent|ItemListener|ItemSelectable|Iterator|IvParameterSpec|JApplet|JarEntry|JarException|JarFile|JarInputStream|JarOutputStream|JarURLConnection|JButton|JCheckBox|JCheckBoxMenuItem|JColorChooser|JComboBox|JComponent|JDesktopPane|JDialog|JEditorPane|JFileChooser|JFormattedTextField|JFrame|JInternalFrame|JLabel|JLayeredPane|JList|JMenu|JMenuBar|JMenuItem|JobAttributes|JobHoldUntil|JobImpressions|JobImpressionsCompleted|JobImpressionsSupported|JobKOctets|JobKOctetsProcessed|JobKOctetsSupported|JobMediaSheets|JobMediaSheetsCompleted|JobMediaSheetsSupported|JobMessageFromOperator|JobName|JobOriginatingUserName|JobPriority|JobPrioritySupported|JobSheets|JobState|JobStateReason|JobStateReasons|JOptionPane|JPanel|JPasswordField|JPEGHuffmanTable|JPEGImageReadParam|JPEGImageWriteParam|JPEGQTable|JPopupMenu|JProgressBar|JRadioButton|JRadioButtonMenuItem|JRootPane|JScrollBar|JScrollPane|JSeparator|JSlider|JSpinner|JSplitPane|JTabbedPane|JTable|JTableHeader|JTextArea|JTextComponent|JTextField|JTextPane|JToggleButton|JToolBar|JToolTip|JTree|JViewport|JWindow|KerberosKey|KerberosPrincipal|KerberosTicket|Kernel|Key|KeyAdapter|KeyAgreement|KeyAgreementSpi|KeyboardFocusManager|KeyEvent|KeyEventDispatcher|KeyEventPostProcessor|KeyException|KeyFactory|KeyFactorySpi|KeyGenerator|KeyGeneratorSpi|KeyListener|KeyManagementException|KeyManager|KeyManagerFactory|KeyManagerFactorySpi|Keymap|KeyPair|KeyPairGenerator|KeyPairGeneratorSpi|KeySpec|KeyStore|KeyStoreException|KeyStoreSpi|KeyStroke|Label|LabelUI|LabelView|LanguageCallback|LastOwnerException|LayeredHighlighter|LayoutFocusTraversalPolicy|LayoutManager|LayoutManager2|LayoutQueue|LDAPCertStoreParameters|LdapContext|LdapReferralException|Lease|Level|LexicalHandler|LIFESPAN_POLICY_ID|LifespanPolicy|LifespanPolicyOperations|LifespanPolicyValue|LimitExceededException|Line|Line2D|LineBorder|LineBreakMeasurer|LineEvent|LineListener|LineMetrics|LineNumberInputStream|LineNumberReader|LineUnavailableException|LinkageError|LinkedHashMap|LinkedHashSet|LinkedList|LinkException|LinkLoopException|LinkRef|List|ListCellRenderer|ListDataEvent|ListDataListener|ListIterator|ListModel|ListResourceBundle|ListSelectionEvent|ListSelectionListener|ListSelectionModel|ListUI|ListView|LoaderHandler|Locale|LocalObject|LocateRegistry|LOCATION_FORWARD|Locator|LocatorImpl|Logger|LoggingPermission|LoginContext|LoginException|LoginModule|LogManager|LogRecord|LogStream|Long|LongBuffer|LongHolder|LongLongSeqHelper|LongLongSeqHolder|LongSeqHelper|LongSeqHolder|LookAndFeel|LookupOp|LookupTable|Mac|MacSpi|MalformedInputException|MalformedLinkException|MalformedURLException|ManagerFactoryParameters|Manifest|Map|MappedByteBuffer|MARSHAL|MarshalException|MarshalledObject|MaskFormatter|Matcher|Math|MatteBorder|Media|MediaName|MediaPrintableArea|MediaSize|MediaSizeName|MediaTracker|MediaTray|Member|MemoryCacheImageInputStream|MemoryCacheImageOutputStream|MemoryHandler|MemoryImageSource|Menu|MenuBar|MenuBarUI|MenuComponent|MenuContainer|MenuDragMouseEvent|MenuDragMouseListener|MenuElement|MenuEvent|MenuItem|MenuItemUI|MenuKeyEvent|MenuKeyListener|MenuListener|MenuSelectionManager|MenuShortcut|MessageDigest|MessageDigestSpi|MessageFormat|MessageProp|MetaEventListener|MetalBorders|MetalButtonUI|MetalCheckBoxIcon|MetalCheckBoxUI|MetalComboBoxButton|MetalComboBoxEditor|MetalComboBoxIcon|MetalComboBoxUI|MetalDesktopIconUI|MetalFileChooserUI|MetalIconFactory|MetalInternalFrameTitlePane|MetalInternalFrameUI|MetalLabelUI|MetalLookAndFeel|MetalPopupMenuSeparatorUI|MetalProgressBarUI|MetalRadioButtonUI|MetalRootPaneUI|MetalScrollBarUI|MetalScrollButton|MetalScrollPaneUI|MetalSeparatorUI|MetalSliderUI|MetalSplitPaneUI|MetalTabbedPaneUI|MetalTextFieldUI|MetalTheme|MetalToggleButtonUI|MetalToolBarUI|MetalToolTipUI|MetalTreeUI|MetaMessage|Method|MethodDescriptor|MidiChannel|MidiDevice|MidiDeviceProvider|MidiEvent|MidiFileFormat|MidiFileReader|MidiFileWriter|MidiMessage|MidiSystem|MidiUnavailableException|MimeTypeParseException|MinimalHTMLWriter|MissingResourceException|Mixer|MixerProvider|ModificationItem|Modifier|MouseAdapter|MouseDragGestureRecognizer|MouseEvent|MouseInputAdapter|MouseInputListener|MouseListener|MouseMotionAdapter|MouseMotionListener|MouseWheelEvent|MouseWheelListener|MultiButtonUI|MulticastSocket|MultiColorChooserUI|MultiComboBoxUI|MultiDesktopIconUI|MultiDesktopPaneUI|MultiDoc|MultiDocPrintJob|MultiDocPrintService|MultiFileChooserUI|MultiInternalFrameUI|MultiLabelUI|MultiListUI|MultiLookAndFeel|MultiMenuBarUI|MultiMenuItemUI|MultiOptionPaneUI|MultiPanelUI|MultiPixelPackedSampleModel|MultipleComponentProfileHelper|MultipleComponentProfileHolder|MultipleDocumentHandling|MultipleMaster|MultiPopupMenuUI|MultiProgressBarUI|MultiRootPaneUI|MultiScrollBarUI|MultiScrollPaneUI|MultiSeparatorUI|MultiSliderUI|MultiSpinnerUI|MultiSplitPaneUI|MultiTabbedPaneUI|MultiTableHeaderUI|MultiTableUI|MultiTextUI|MultiToolBarUI|MultiToolTipUI|MultiTreeUI|MultiViewportUI|MutableAttributeSet|MutableComboBoxModel|MutableTreeNode|Name|NameAlreadyBoundException|NameCallback|NameClassPair|NameComponent|NameComponentHelper|NameComponentHolder|NamedNodeMap|NamedValue|NameDynAnyPair|NameDynAnyPairHelper|NameDynAnyPairSeqHelper|NameHelper|NameHolder|NameNotFoundException|NameParser|NamespaceChangeListener|NamespaceSupport|NameValuePair|NameValuePairHelper|NameValuePairSeqHelper|Naming|NamingContext|NamingContextExt|NamingContextExtHelper|NamingContextExtHolder|NamingContextExtOperations|NamingContextExtPOA|NamingContextHelper|NamingContextHolder|NamingContextOperations|NamingContextPOA|NamingEnumeration|NamingEvent|NamingException|NamingExceptionEvent|NamingListener|NamingManager|NamingSecurityException|NavigationFilter|NegativeArraySizeException|NetPermission|NetworkInterface|NO_IMPLEMENT|NO_MEMORY|NO_PERMISSION|NO_RESOURCES|NO_RESPONSE|NoClassDefFoundError|NoConnectionPendingException|NoContext|NoContextHelper|Node|NodeChangeEvent|NodeChangeListener|NodeList|NoInitialContextException|NoninvertibleTransformException|NonReadableChannelException|NonWritableChannelException|NoPermissionException|NoRouteToHostException|NoServant|NoServantHelper|NoSuchAlgorithmException|NoSuchAttributeException|NoSuchElementException|NoSuchFieldError|NoSuchFieldException|NoSuchMethodError|NoSuchMethodException|NoSuchObjectException|NoSuchPaddingException|NoSuchProviderException|NotActiveException|Notation|NotBoundException|NotContextException|NotEmpty|NotEmptyHelper|NotEmptyHolder|NotFound|NotFoundHelper|NotFoundHolder|NotFoundReason|NotFoundReasonHelper|NotFoundReasonHolder|NotOwnerException|NotSerializableException|NotYetBoundException|NotYetConnectedException|NullCipher|NullPointerException|Number|NumberFormat|NumberFormatException|NumberFormatter|NumberOfDocuments|NumberOfInterveningJobs|NumberUp|NumberUpSupported|NumericShaper|NVList|OBJ_ADAPTER|Object|OBJECT_NOT_EXIST|ObjectAlreadyActive|ObjectAlreadyActiveHelper|ObjectChangeListener|ObjectFactory|ObjectFactoryBuilder|ObjectHelper|ObjectHolder|ObjectIdHelper|ObjectImpl|ObjectInput|ObjectInputStream|ObjectInputValidation|ObjectNotActive|ObjectNotActiveHelper|ObjectOutput|ObjectOutputStream|ObjectStreamClass|ObjectStreamConstants|ObjectStreamException|ObjectStreamField|ObjectView|ObjID|Observable|Observer|OctetSeqHelper|OctetSeqHolder|Oid|OMGVMCID|OpenType|Operation|OperationNotSupportedException|Option|OptionalDataException|OptionPaneUI|ORB|ORBInitializer|ORBInitializerOperations|ORBInitInfo|ORBInitInfoOperations|OrientationRequested|OutOfMemoryError|OutputDeviceAssigned|OutputKeys|OutputStream|OutputStreamWriter|OverlappingFileLockException|OverlayLayout|Owner|Package|PackedColorModel|Pageable|PageAttributes|PageFormat|PageRanges|PagesPerMinute|PagesPerMinuteColor|Paint|PaintContext|PaintEvent|Panel|PanelUI|Paper|ParagraphView|Parameter|ParameterBlock|ParameterDescriptor|ParameterMetaData|ParameterMode|ParameterModeHelper|ParameterModeHolder|ParseException|ParsePosition|Parser|ParserAdapter|ParserConfigurationException|ParserDelegator|ParserFactory|PartialResultException|PasswordAuthentication|PasswordCallback|PasswordView|Patch|PathIterator|Pattern|PatternSyntaxException|PBEKey|PBEKeySpec|PBEParameterSpec|PDLOverrideSupported|Permission|PermissionCollection|Permissions|PERSIST_STORE|PersistenceDelegate|PhantomReference|Pipe|PipedInputStream|PipedOutputStream|PipedReader|PipedWriter|PixelGrabber|PixelInterleavedSampleModel|PKCS8EncodedKeySpec|PKIXBuilderParameters|PKIXCertPathBuilderResult|PKIXCertPathChecker|PKIXCertPathValidatorResult|PKIXParameters|PlainDocument|PlainView|POA|POAHelper|POAManager|POAManagerOperations|POAOperations|Point|Point2D|Policy|PolicyError|PolicyErrorCodeHelper|PolicyErrorHelper|PolicyErrorHolder|PolicyFactory|PolicyFactoryOperations|PolicyHelper|PolicyHolder|PolicyListHelper|PolicyListHolder|PolicyNode|PolicyOperations|PolicyQualifierInfo|PolicyTypeHelper|Polygon|PooledConnection|Popup|PopupFactory|PopupMenu|PopupMenuEvent|PopupMenuListener|PopupMenuUI|Port|PortableRemoteObject|PortableRemoteObjectDelegate|PortUnreachableException|Position|PreferenceChangeEvent|PreferenceChangeListener|Preferences|PreferencesFactory|PreparedStatement|PresentationDirection|Principal|PrincipalHolder|Printable|PrinterAbortException|PrinterException|PrinterGraphics|PrinterInfo|PrinterIOException|PrinterIsAcceptingJobs|PrinterJob|PrinterLocation|PrinterMakeAndModel|PrinterMessageFromOperator|PrinterMoreInfo|PrinterMoreInfoManufacturer|PrinterName|PrinterResolution|PrinterState|PrinterStateReason|PrinterStateReasons|PrinterURI|PrintEvent|PrintException|PrintGraphics|PrintJob|PrintJobAdapter|PrintJobAttribute|PrintJobAttributeEvent|PrintJobAttributeListener|PrintJobAttributeSet|PrintJobEvent|PrintJobListener|PrintQuality|PrintRequestAttribute|PrintRequestAttributeSet|PrintService|PrintServiceAttribute|PrintServiceAttributeEvent|PrintServiceAttributeListener|PrintServiceAttributeSet|PrintServiceLookup|PrintStream|PrintWriter|PRIVATE_MEMBER|PrivateCredentialPermission|PrivateKey|PrivilegedAction|PrivilegedActionException|PrivilegedExceptionAction|Process|ProcessingInstruction|ProfileDataException|ProfileIdHelper|ProgressBarUI|ProgressMonitor|ProgressMonitorInputStream|Properties|PropertyChangeEvent|PropertyChangeListener|PropertyChangeListenerProxy|PropertyChangeSupport|PropertyDescriptor|PropertyEditor|PropertyEditorManager|PropertyEditorSupport|PropertyPermission|PropertyResourceBundle|PropertyVetoException|ProtectionDomain|ProtocolException|Provider|ProviderException|Proxy|PSSParameterSpec|PUBLIC_MEMBER|PublicKey|PushbackInputStream|PushbackReader|QuadCurve2D|QueuedJobCount|Random|RandomAccess|RandomAccessFile|Raster|RasterFormatException|RasterOp|RC2ParameterSpec|RC5ParameterSpec|ReadableByteChannel|Reader|ReadOnlyBufferException|Receiver|Rectangle|Rectangle2D|RectangularShape|Ref|RefAddr|Reference|Referenceable|ReferenceQueue|ReferenceUriSchemesSupported|ReferralException|ReflectPermission|Refreshable|RefreshFailedException|RegisterableService|Registry|RegistryHandler|RemarshalException|Remote|RemoteCall|RemoteException|RemoteObject|RemoteRef|RemoteServer|RemoteStub|RenderableImage|RenderableImageOp|RenderableImageProducer|RenderContext|RenderedImage|RenderedImageFactory|Renderer|RenderingHints|RepaintManager|ReplicateScaleFilter|RepositoryIdHelper|Request|REQUEST_PROCESSING_POLICY_ID|RequestInfo|RequestInfoOperations|RequestingUserName|RequestProcessingPolicy|RequestProcessingPolicyOperations|RequestProcessingPolicyValue|RescaleOp|ResolutionSyntax|Resolver|ResolveResult|ResourceBundle|ResponseHandler|Result|ResultSet|ResultSetMetaData|ReverbType|RGBImageFilter|RMIClassLoader|RMIClassLoaderSpi|RMIClientSocketFactory|RMIFailureHandler|RMISecurityException|RMISecurityManager|RMIServerSocketFactory|RMISocketFactory|Robot|RootPaneContainer|RootPaneUI|RoundRectangle2D|RowMapper|RowSet|RowSetEvent|RowSetInternal|RowSetListener|RowSetMetaData|RowSetReader|RowSetWriter|RSAKey|RSAKeyGenParameterSpec|RSAMultiPrimePrivateCrtKey|RSAMultiPrimePrivateCrtKeySpec|RSAOtherPrimeInfo|RSAPrivateCrtKey|RSAPrivateCrtKeySpec|RSAPrivateKey|RSAPrivateKeySpec|RSAPublicKey|RSAPublicKeySpec|RTFEditorKit|RuleBasedCollator|Runnable|Runtime|RunTime|RuntimeException|RunTimeOperations|RuntimePermission|SampleModel|Savepoint|SAXException|SAXNotRecognizedException|SAXNotSupportedException|SAXParseException|SAXParser|SAXParserFactory|SAXResult|SAXSource|SAXTransformerFactory|ScatteringByteChannel|SchemaViolationException|Scrollable|Scrollbar|ScrollBarUI|ScrollPane|ScrollPaneAdjustable|ScrollPaneConstants|ScrollPaneLayout|ScrollPaneUI|SealedObject|SearchControls|SearchResult|SecretKey|SecretKeyFactory|SecretKeyFactorySpi|SecretKeySpec|SecureClassLoader|SecureRandom|SecureRandomSpi|Security|SecurityException|SecurityManager|SecurityPermission|Segment|SelectableChannel|SelectionKey|Selector|SelectorProvider|SeparatorUI|Sequence|SequenceInputStream|Sequencer|Serializable|SerializablePermission|Servant|SERVANT_RETENTION_POLICY_ID|ServantActivator|ServantActivatorHelper|ServantActivatorOperations|ServantActivatorPOA|ServantAlreadyActive|ServantAlreadyActiveHelper|ServantLocator|ServantLocatorHelper|ServantLocatorOperations|ServantLocatorPOA|ServantManager|ServantManagerOperations|ServantNotActive|ServantNotActiveHelper|ServantObject|ServantRetentionPolicy|ServantRetentionPolicyOperations|ServantRetentionPolicyValue|ServerCloneException|ServerError|ServerException|ServerNotActiveException|ServerRef|ServerRequest|ServerRequestInfo|ServerRequestInfoOperations|ServerRequestInterceptor|ServerRequestInterceptorOperations|ServerRuntimeException|ServerSocket|ServerSocketChannel|ServerSocketFactory|ServiceContext|ServiceContextHelper|ServiceContextHolder|ServiceContextListHelper|ServiceContextListHolder|ServiceDetail|ServiceDetailHelper|ServiceIdHelper|ServiceInformation|ServiceInformationHelper|ServiceInformationHolder|ServicePermission|ServiceRegistry|ServiceUI|ServiceUIFactory|ServiceUnavailableException|Set|SetOfIntegerSyntax|SetOverrideType|SetOverrideTypeHelper|Severity|Shape|ShapeGraphicAttribute|SheetCollate|Short|ShortBuffer|ShortBufferException|ShortHolder|ShortLookupTable|ShortMessage|ShortSeqHelper|ShortSeqHolder|Sides|Signature|SignatureException|SignatureSpi|SignedObject|Signer|SimpleAttributeSet|SimpleBeanInfo|SimpleDateFormat|SimpleDoc|SimpleFormatter|SimpleTimeZone|SinglePixelPackedSampleModel|SingleSelectionModel|Size2DSyntax|SizeLimitExceededException|SizeRequirements|SizeSequence|Skeleton|SkeletonMismatchException|SkeletonNotFoundException|SliderUI|Socket|SocketAddress|SocketChannel|SocketException|SocketFactory|SocketHandler|SocketImpl|SocketImplFactory|SocketOptions|SocketPermission|SocketSecurityException|SocketTimeoutException|SoftBevelBorder|SoftReference|SortedMap|SortedSet|SortingFocusTraversalPolicy|Soundbank|SoundbankReader|SoundbankResource|Source|SourceDataLine|SourceLocator|SpinnerDateModel|SpinnerListModel|SpinnerModel|SpinnerNumberModel|SpinnerUI|SplitPaneUI|Spring|SpringLayout|SQLData|SQLException|SQLInput|SQLOutput|SQLPermission|SQLWarning|SSLContext|SSLContextSpi|SSLException|SSLHandshakeException|SSLKeyException|SSLPeerUnverifiedException|SSLPermission|SSLProtocolException|SSLServerSocket|SSLServerSocketFactory|SSLSession|SSLSessionBindingEvent|SSLSessionBindingListener|SSLSessionContext|SSLSocket|SSLSocketFactory|Stack|StackOverflowError|StackTraceElement|StartTlsRequest|StartTlsResponse|State|StateEdit|StateEditable|StateFactory|Statement|Streamable|StreamableValue|StreamCorruptedException|StreamHandler|StreamPrintService|StreamPrintServiceFactory|StreamResult|StreamSource|StreamTokenizer|StrictMath|String|StringBuffer|StringBufferInputStream|StringCharacterIterator|StringContent|StringHolder|StringIndexOutOfBoundsException|StringNameHelper|StringReader|StringRefAddr|StringSelection|StringSeqHelper|StringSeqHolder|StringTokenizer|StringValueHelper|StringWriter|Stroke|Struct|StructMember|StructMemberHelper|Stub|StubDelegate|StubNotFoundException|Style|StyleConstants|StyleContext|StyledDocument|StyledEditorKit|StyleSheet|Subject|SubjectDomainCombiner|SUCCESSFUL|SupportedValuesAttribute|SwingConstants|SwingPropertyChangeSupport|SwingUtilities|SYNC_WITH_TRANSPORT|SyncFailedException|SyncScopeHelper|Synthesizer|SysexMessage|System|SYSTEM_EXCEPTION|SystemColor|SystemException|SystemFlavorMap|TabableView|TabbedPaneUI|TabExpander|TableCellEditor|TableCellRenderer|TableColumn|TableColumnModel|TableColumnModelEvent|TableColumnModelListener|TableHeaderUI|TableModel|TableModelEvent|TableModelListener|TableUI|TableView|TabSet|TabStop|TAG_ALTERNATE_IIOP_ADDRESS|TAG_CODE_SETS|TAG_INTERNET_IOP|TAG_JAVA_CODEBASE|TAG_MULTIPLE_COMPONENTS|TAG_ORB_TYPE|TAG_POLICIES|TagElement|TaggedComponent|TaggedComponentHelper|TaggedComponentHolder|TaggedProfile|TaggedProfileHelper|TaggedProfileHolder|TargetDataLine|TCKind|Templates|TemplatesHandler|Text|TextAction|TextArea|TextAttribute|TextComponent|TextEvent|TextField|TextHitInfo|TextInputCallback|TextLayout|TextListener|TextMeasurer|TextOutputCallback|TextSyntax|TextUI|TexturePaint|Thread|THREAD_POLICY_ID|ThreadDeath|ThreadGroup|ThreadLocal|ThreadPolicy|ThreadPolicyOperations|ThreadPolicyValue|Throwable|Tie|TileObserver|Time|TimeLimitExceededException|Timer|TimerTask|Timestamp|TimeZone|TitledBorder|ToolBarUI|Toolkit|ToolTipManager|ToolTipUI|TooManyListenersException|Track|TRANSACTION_REQUIRED|TRANSACTION_ROLLEDBACK|TransactionRequiredException|TransactionRolledbackException|TransactionService|Transferable|TransferHandler|TransformAttribute|Transformer|TransformerConfigurationException|TransformerException|TransformerFactory|TransformerFactoryConfigurationError|TransformerHandler|TRANSIENT|Transmitter|Transparency|TRANSPORT_RETRY|TreeCellEditor|TreeCellRenderer|TreeExpansionEvent|TreeExpansionListener|TreeMap|TreeModel|TreeModelEvent|TreeModelListener|TreeNode|TreePath|TreeSelectionEvent|TreeSelectionListener|TreeSelectionModel|TreeSet|TreeUI|TreeWillExpandListener|TrustAnchor|TrustManager|TrustManagerFactory|TrustManagerFactorySpi|TypeCode|TypeCodeHolder|TypeMismatch|TypeMismatchHelper|Types|UID|UIDefaults|UIManager|UIResource|ULongLongSeqHelper|ULongLongSeqHolder|ULongSeqHelper|ULongSeqHolder|UndeclaredThrowableException|UndoableEdit|UndoableEditEvent|UndoableEditListener|UndoableEditSupport|UndoManager|UnexpectedException|UnicastRemoteObject|UnionMember|UnionMemberHelper|UNKNOWN|UnknownEncoding|UnknownEncodingHelper|UnknownError|UnknownException|UnknownGroupException|UnknownHostException|UnknownObjectException|UnknownServiceException|UnknownUserException|UnknownUserExceptionHelper|UnknownUserExceptionHolder|UnmappableCharacterException|UnmarshalException|UnmodifiableSetException|UnrecoverableKeyException|Unreferenced|UnresolvedAddressException|UnresolvedPermission|UnsatisfiedLinkError|UnsolicitedNotification|UnsolicitedNotificationEvent|UnsolicitedNotificationListener|UNSUPPORTED_POLICY|UNSUPPORTED_POLICY_VALUE|UnsupportedAddressTypeException|UnsupportedAudioFileException|UnsupportedCallbackException|UnsupportedCharsetException|UnsupportedClassVersionError|UnsupportedEncodingException|UnsupportedFlavorException|UnsupportedLookAndFeelException|UnsupportedOperationException|URI|URIException|URIResolver|URISyntax|URISyntaxException|URL|URLClassLoader|URLConnection|URLDecoder|URLEncoder|URLStreamHandler|URLStreamHandlerFactory|URLStringHelper|USER_EXCEPTION|UserException|UShortSeqHelper|UShortSeqHolder|UTFDataFormatException|Util|UtilDelegate|Utilities|ValueBase|ValueBaseHelper|ValueBaseHolder|ValueFactory|ValueHandler|ValueMember|ValueMemberHelper|VariableHeightLayoutCache|Vector|VerifyError|VersionSpecHelper|VetoableChangeListener|VetoableChangeListenerProxy|VetoableChangeSupport|View|ViewFactory|ViewportLayout|ViewportUI|VirtualMachineError|Visibility|VisibilityHelper|VM_ABSTRACT|VM_CUSTOM|VM_NONE|VM_TRUNCATABLE|VMID|VoiceStatus|Void|VolatileImage|WCharSeqHelper|WCharSeqHolder|WeakHashMap|WeakReference|Window|WindowAdapter|WindowConstants|WindowEvent|WindowFocusListener|WindowListener|WindowStateListener|WrappedPlainView|WritableByteChannel|WritableRaster|WritableRenderedImage|WriteAbortedException|Writer|WrongAdapter|WrongAdapterHelper|WrongPolicy|WrongPolicyHelper|WrongTransaction|WrongTransactionHelper|WrongTransactionHolder|WStringSeqHelper|WStringSeqHolder|WStringValueHelper|X500Principal|X500PrivateCredential|X509Certificate|X509CertSelector|X509CRL|X509CRLEntry|X509CRLSelector|X509EncodedKeySpec|X509Extension|X509KeyManager|X509TrustManager|XAConnection|XADataSource|XAException|XAResource|Xid|XMLDecoder|XMLEncoder|XMLFilter|XMLFilterImpl|XMLFormatter|XMLReader|XMLReaderAdapter|XMLReaderFactory|ZipEntry|ZipException|ZipFile|ZipInputStream|ZipOutputStream|ZoneView|_BindingIteratorImplBase|_BindingIteratorStub|_DynAnyFactoryStub|_DynAnyStub|_DynArrayStub|_DynEnumStub|_DynFixedStub|_DynSequenceStub|_DynStructStub|_DynUnionStub|_DynValueStub|_IDLTypeStub|_NamingContextExtStub|_NamingContextImplBase|_NamingContextStub|_PolicyStub|_Remote_Stub|_ServantActivatorStub|_ServantLocatorStub)$/',
- ),
- 8 =>
- array (
- ),
- 9 =>
- array (
- ),
- 10 =>
- array (
- ),
- 11 =>
- array (
- ),
- 12 =>
- array (
- ),
- ),
- 3 =>
- array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- 3 =>
- array (
- ),
- 4 =>
- array (
- ),
- ),
- 4 =>
- array (
- 0 =>
- array (
- ),
- ),
- 5 =>
- array (
- 0 =>
- array (
- ),
- ),
- 6 =>
- array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- 3 =>
- array (
- ),
- 4 =>
- array (
- ),
- ),
- );
- $this->_parts = array (
- 0 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- 10 => NULL,
- 11 => NULL,
- 12 => NULL,
- ),
- 1 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- 10 => NULL,
- 11 => NULL,
- 12 => NULL,
- ),
- 2 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- 10 => NULL,
- 11 => NULL,
- 12 => NULL,
- ),
- 3 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- ),
- 4 =>
- array (
- 0 => NULL,
- ),
- 5 =>
- array (
- 0 => NULL,
- ),
- 6 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- ),
- );
- $this->_subst = array (
- -1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- ),
- 0 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- ),
- 1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- ),
- 2 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- ),
- 3 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- ),
- 4 =>
- array (
- 0 => false,
- ),
- 5 =>
- array (
- 0 => false,
- ),
- 6 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- ),
- );
- $this->_conditions = array (
- 'java.builtins' =>
- array (
- 0 =>
- array (
- 0 => 'builtin',
- 1 => true,
- ),
- ),
- );
- $this->_kwmap = array (
- 'types' => 'types',
- 'reserved' => 'reserved',
- 'builtin' => 'builtin',
- );
- $this->_defClass = 'code';
- $this->_checkDefines();
- }
-
-} \ No newline at end of file
diff --git a/library/Text_Highlighter/Text/Highlighter/JAVASCRIPT.php b/library/Text_Highlighter/Text/Highlighter/JAVASCRIPT.php
deleted file mode 100644
index 51eae8f62..000000000
--- a/library/Text_Highlighter/Text/Highlighter/JAVASCRIPT.php
+++ /dev/null
@@ -1,631 +0,0 @@
-<?php
-/**
- * Auto-generated class. JAVASCRIPT syntax highlighting
- *
- * PHP version 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @link http://pear.php.net/package/Text_Highlighter
- * @category Text
- * @package Text_Highlighter
- * @version generated from: javascript.xml
- * @author Andrey Demenev <demenev@gmail.com>
- *
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter.php';
-
-/**
- * Auto-generated class. JAVASCRIPT syntax highlighting
- *
- * @author Andrey Demenev <demenev@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: 0.7.0
- * @link http://pear.php.net/package/Text_Highlighter
- */
-class Text_Highlighter_JAVASCRIPT extends Text_Highlighter
-{
- var $_language = 'javascript';
-
- /**
- * PHP4 Compatible Constructor
- *
- * @param array $options
- * @access public
- */
- function Text_Highlighter_JAVASCRIPT($options=array())
- {
- $this->__construct($options);
- }
-
-
- /**
- * Constructor
- *
- * @param array $options
- * @access public
- */
- function __construct($options=array())
- {
-
- $this->_options = $options;
- $this->_regs = array (
- -1 => '/((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)\\/\\*)|((?i)")|((?i)\')|((?i)\\/\\/)|((?i)[a-z_]\\w*)|((?i)0x\\d*|\\d*\\.?\\d+)/',
- 0 => '/((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)\\/\\*)|((?i)")|((?i)\')|((?i)\\/\\/)|((?i)[a-z_]\\w*)|((?i)0x\\d*|\\d*\\.?\\d+)/',
- 1 => '/((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)\\/\\*)|((?i)")|((?i)\')|((?i)\\/\\/)|((?i)[a-z_]\\w*)|((?i)0x\\d*|\\d*\\.?\\d+)/',
- 2 => '/((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)\\/\\*)|((?i)")|((?i)\')|((?i)\\/\\/)|((?i)[a-z_]\\w*)|((?i)0x\\d*|\\d*\\.?\\d+)/',
- 3 => '/((?i)((https?|ftp):\\/\\/[\\w\\?\\.\\-\\&=\\/%+]+)|(^|[\\s,!?])www\\.\\w+\\.\\w+[\\w\\?\\.\\&=\\/%+]*)|((?i)\\w+[\\.\\w\\-]+@(\\w+[\\.\\w\\-])+)|((?i)\\b(note|fixme):)|((?i)\\$\\w+:.+\\$)/',
- 4 => '/((?i)\\\\\\\\|\\\\"|\\\\\'|\\\\`|\\\\t|\\\\n|\\\\r)/',
- 5 => '/((?i)\\\\\\\\|\\\\"|\\\\\'|\\\\`)/',
- 6 => '/((?i)((https?|ftp):\\/\\/[\\w\\?\\.\\-\\&=\\/%+]+)|(^|[\\s,!?])www\\.\\w+\\.\\w+[\\w\\?\\.\\&=\\/%+]*)|((?i)\\w+[\\.\\w\\-]+@(\\w+[\\.\\w\\-])+)|((?i)\\b(note|fixme):)|((?i)\\$\\w+:.+\\$)/',
- );
- $this->_counts = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 0,
- ),
- 0 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 0,
- ),
- 1 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 0,
- ),
- 2 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 0,
- ),
- 3 =>
- array (
- 0 => 3,
- 1 => 1,
- 2 => 1,
- 3 => 0,
- ),
- 4 =>
- array (
- 0 => 0,
- ),
- 5 =>
- array (
- 0 => 0,
- ),
- 6 =>
- array (
- 0 => 3,
- 1 => 1,
- 2 => 1,
- 3 => 0,
- ),
- );
- $this->_delim = array (
- -1 =>
- array (
- 0 => 'brackets',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'comment',
- 4 => 'quotes',
- 5 => 'quotes',
- 6 => 'comment',
- 7 => '',
- 8 => '',
- ),
- 0 =>
- array (
- 0 => 'brackets',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'comment',
- 4 => 'quotes',
- 5 => 'quotes',
- 6 => 'comment',
- 7 => '',
- 8 => '',
- ),
- 1 =>
- array (
- 0 => 'brackets',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'comment',
- 4 => 'quotes',
- 5 => 'quotes',
- 6 => 'comment',
- 7 => '',
- 8 => '',
- ),
- 2 =>
- array (
- 0 => 'brackets',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'comment',
- 4 => 'quotes',
- 5 => 'quotes',
- 6 => 'comment',
- 7 => '',
- 8 => '',
- ),
- 3 =>
- array (
- 0 => '',
- 1 => '',
- 2 => '',
- 3 => '',
- ),
- 4 =>
- array (
- 0 => '',
- ),
- 5 =>
- array (
- 0 => '',
- ),
- 6 =>
- array (
- 0 => '',
- 1 => '',
- 2 => '',
- 3 => '',
- ),
- );
- $this->_inner = array (
- -1 =>
- array (
- 0 => 'code',
- 1 => 'code',
- 2 => 'code',
- 3 => 'comment',
- 4 => 'string',
- 5 => 'string',
- 6 => 'comment',
- 7 => 'identifier',
- 8 => 'number',
- ),
- 0 =>
- array (
- 0 => 'code',
- 1 => 'code',
- 2 => 'code',
- 3 => 'comment',
- 4 => 'string',
- 5 => 'string',
- 6 => 'comment',
- 7 => 'identifier',
- 8 => 'number',
- ),
- 1 =>
- array (
- 0 => 'code',
- 1 => 'code',
- 2 => 'code',
- 3 => 'comment',
- 4 => 'string',
- 5 => 'string',
- 6 => 'comment',
- 7 => 'identifier',
- 8 => 'number',
- ),
- 2 =>
- array (
- 0 => 'code',
- 1 => 'code',
- 2 => 'code',
- 3 => 'comment',
- 4 => 'string',
- 5 => 'string',
- 6 => 'comment',
- 7 => 'identifier',
- 8 => 'number',
- ),
- 3 =>
- array (
- 0 => 'url',
- 1 => 'url',
- 2 => 'inlinedoc',
- 3 => 'inlinedoc',
- ),
- 4 =>
- array (
- 0 => 'special',
- ),
- 5 =>
- array (
- 0 => 'special',
- ),
- 6 =>
- array (
- 0 => 'url',
- 1 => 'url',
- 2 => 'inlinedoc',
- 3 => 'inlinedoc',
- ),
- );
- $this->_end = array (
- 0 => '/(?i)\\}/',
- 1 => '/(?i)\\)/',
- 2 => '/(?i)\\]/',
- 3 => '/(?i)\\*\\//',
- 4 => '/(?i)"/',
- 5 => '/(?i)\'/',
- 6 => '/(?mi)$/',
- );
- $this->_states = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => 4,
- 5 => 5,
- 6 => 6,
- 7 => -1,
- 8 => -1,
- ),
- 0 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => 4,
- 5 => 5,
- 6 => 6,
- 7 => -1,
- 8 => -1,
- ),
- 1 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => 4,
- 5 => 5,
- 6 => 6,
- 7 => -1,
- 8 => -1,
- ),
- 2 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => 4,
- 5 => 5,
- 6 => 6,
- 7 => -1,
- 8 => -1,
- ),
- 3 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- ),
- 4 =>
- array (
- 0 => -1,
- ),
- 5 =>
- array (
- 0 => -1,
- ),
- 6 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- ),
- );
- $this->_keywords = array (
- -1 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 =>
- array (
- 'builtin' => '/^(String|Array|RegExp|Function|Math|Number|Date|Image|window|document|navigator|onAbort|onBlur|onChange|onClick|onDblClick|onDragDrop|onError|onFocus|onKeyDown|onKeyPress|onKeyUp|onLoad|onMouseDown|onMouseOver|onMouseOut|onMouseMove|onMouseUp|onMove|onReset|onResize|onSelect|onSubmit|onUnload)$/',
- 'reserved' => '/^(break|continue|do|while|export|for|in|if|else|import|return|label|switch|case|var|with|delete|new|this|typeof|void|abstract|boolean|byte|catch|char|class|const|debugger|default|double|enum|extends|false|final|finally|float|function|implements|goto|instanceof|int|interface|long|native|null|package|private|protected|public|short|static|super|synchronized|throw|throws|transient|true|try|volatile)$/',
- ),
- 8 =>
- array (
- ),
- ),
- 0 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 =>
- array (
- 'builtin' => '/^(String|Array|RegExp|Function|Math|Number|Date|Image|window|document|navigator|onAbort|onBlur|onChange|onClick|onDblClick|onDragDrop|onError|onFocus|onKeyDown|onKeyPress|onKeyUp|onLoad|onMouseDown|onMouseOver|onMouseOut|onMouseMove|onMouseUp|onMove|onReset|onResize|onSelect|onSubmit|onUnload)$/',
- 'reserved' => '/^(break|continue|do|while|export|for|in|if|else|import|return|label|switch|case|var|with|delete|new|this|typeof|void|abstract|boolean|byte|catch|char|class|const|debugger|default|double|enum|extends|false|final|finally|float|function|implements|goto|instanceof|int|interface|long|native|null|package|private|protected|public|short|static|super|synchronized|throw|throws|transient|true|try|volatile)$/',
- ),
- 8 =>
- array (
- ),
- ),
- 1 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 =>
- array (
- 'builtin' => '/^(String|Array|RegExp|Function|Math|Number|Date|Image|window|document|navigator|onAbort|onBlur|onChange|onClick|onDblClick|onDragDrop|onError|onFocus|onKeyDown|onKeyPress|onKeyUp|onLoad|onMouseDown|onMouseOver|onMouseOut|onMouseMove|onMouseUp|onMove|onReset|onResize|onSelect|onSubmit|onUnload)$/',
- 'reserved' => '/^(break|continue|do|while|export|for|in|if|else|import|return|label|switch|case|var|with|delete|new|this|typeof|void|abstract|boolean|byte|catch|char|class|const|debugger|default|double|enum|extends|false|final|finally|float|function|implements|goto|instanceof|int|interface|long|native|null|package|private|protected|public|short|static|super|synchronized|throw|throws|transient|true|try|volatile)$/',
- ),
- 8 =>
- array (
- ),
- ),
- 2 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 =>
- array (
- 'builtin' => '/^(String|Array|RegExp|Function|Math|Number|Date|Image|window|document|navigator|onAbort|onBlur|onChange|onClick|onDblClick|onDragDrop|onError|onFocus|onKeyDown|onKeyPress|onKeyUp|onLoad|onMouseDown|onMouseOver|onMouseOut|onMouseMove|onMouseUp|onMove|onReset|onResize|onSelect|onSubmit|onUnload)$/',
- 'reserved' => '/^(break|continue|do|while|export|for|in|if|else|import|return|label|switch|case|var|with|delete|new|this|typeof|void|abstract|boolean|byte|catch|char|class|const|debugger|default|double|enum|extends|false|final|finally|float|function|implements|goto|instanceof|int|interface|long|native|null|package|private|protected|public|short|static|super|synchronized|throw|throws|transient|true|try|volatile)$/',
- ),
- 8 =>
- array (
- ),
- ),
- 3 =>
- array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- 3 =>
- array (
- ),
- ),
- 4 =>
- array (
- 0 =>
- array (
- ),
- ),
- 5 =>
- array (
- 0 =>
- array (
- ),
- ),
- 6 =>
- array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- 3 =>
- array (
- ),
- ),
- );
- $this->_parts = array (
- 0 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- ),
- 1 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- ),
- 2 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- ),
- 3 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- ),
- 4 =>
- array (
- 0 => NULL,
- ),
- 5 =>
- array (
- 0 => NULL,
- ),
- 6 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- ),
- );
- $this->_subst = array (
- -1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- ),
- 0 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- ),
- 1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- ),
- 2 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- ),
- 3 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- ),
- 4 =>
- array (
- 0 => false,
- ),
- 5 =>
- array (
- 0 => false,
- ),
- 6 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- ),
- );
- $this->_conditions = array (
- );
- $this->_kwmap = array (
- 'builtin' => 'builtin',
- 'reserved' => 'reserved',
- );
- $this->_defClass = 'code';
- $this->_checkDefines();
- }
-
-}
diff --git a/library/Text_Highlighter/Text/Highlighter/MYSQL.php b/library/Text_Highlighter/Text/Highlighter/MYSQL.php
deleted file mode 100644
index bdd74cc8b..000000000
--- a/library/Text_Highlighter/Text/Highlighter/MYSQL.php
+++ /dev/null
@@ -1,434 +0,0 @@
-<?php
-/**
- * Auto-generated class. MYSQL syntax highlighting
- *
- * PHP version 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @link http://pear.php.net/package/Text_Highlighter
- * @category Text
- * @package Text_Highlighter
- * @version generated from: : mysql.xml,v 1.1 2007/06/03 02:35:28 ssttoo Exp
- * @author Andrey Demenev <demenev@gmail.com>
- *
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter.php';
-
-/**
- * Auto-generated class. MYSQL syntax highlighting
- *
- * @author Andrey Demenev <demenev@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: @package_version@
- * @link http://pear.php.net/package/Text_Highlighter
- */
-class Text_Highlighter_MYSQL extends Text_Highlighter
-{
- var $_language = 'mysql';
-
- /**
- * PHP4 Compatible Constructor
- *
- * @param array $options
- * @access public
- */
- function Text_Highlighter_MYSQL($options=array())
- {
- $this->__construct($options);
- }
-
-
- /**
- * Constructor
- *
- * @param array $options
- * @access public
- */
- function __construct($options=array())
- {
-
- $this->_options = $options;
- $this->_regs = array (
- -1 => '/((?i)`)|((?i)\\/\\*)|((?i)(#|--\\s).*)|((?i)[a-z_]\\w*(?=\\s*\\())|((?i)[a-z_]\\w*)|((?i)")|((?i)\\()|((?i)\')|((?i)((\\d+|((\\d*\\.\\d+)|(\\d+\\.\\d*)))[eE][+-]?\\d+))|((?i)(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?i)\\d+l?|\\b0l?\\b)|((?i)0[xX][\\da-f]+l?)/',
- 0 => '//',
- 1 => '//',
- 2 => '/((?i)\\\\.)/',
- 3 => '/((?i)`)|((?i)\\/\\*)|((?i)(#|--\\s).*)|((?i)[a-z_]\\w*(?=\\s*\\())|((?i)[a-z_]\\w*)|((?i)")|((?i)\\()|((?i)\')|((?i)((\\d+|((\\d*\\.\\d+)|(\\d+\\.\\d*)))[eE][+-]?\\d+))|((?i)(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?i)\\d+l?|\\b0l?\\b)|((?i)0[xX][\\da-f]+l?)/',
- 4 => '/((?i)\\\\.)/',
- );
- $this->_counts = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 1,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 5,
- 9 => 2,
- 10 => 0,
- 11 => 0,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => 0,
- ),
- 3 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 1,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 5,
- 9 => 2,
- 10 => 0,
- 11 => 0,
- ),
- 4 =>
- array (
- 0 => 0,
- ),
- );
- $this->_delim = array (
- -1 =>
- array (
- 0 => 'quotes',
- 1 => 'comment',
- 2 => '',
- 3 => '',
- 4 => '',
- 5 => 'quotes',
- 6 => 'brackets',
- 7 => 'quotes',
- 8 => '',
- 9 => '',
- 10 => '',
- 11 => '',
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => '',
- ),
- 3 =>
- array (
- 0 => 'quotes',
- 1 => 'comment',
- 2 => '',
- 3 => '',
- 4 => '',
- 5 => 'quotes',
- 6 => 'brackets',
- 7 => 'quotes',
- 8 => '',
- 9 => '',
- 10 => '',
- 11 => '',
- ),
- 4 =>
- array (
- 0 => '',
- ),
- );
- $this->_inner = array (
- -1 =>
- array (
- 0 => 'identifier',
- 1 => 'comment',
- 2 => 'comment',
- 3 => 'identifier',
- 4 => 'identifier',
- 5 => 'string',
- 6 => 'code',
- 7 => 'string',
- 8 => 'number',
- 9 => 'number',
- 10 => 'number',
- 11 => 'number',
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => 'special',
- ),
- 3 =>
- array (
- 0 => 'identifier',
- 1 => 'comment',
- 2 => 'comment',
- 3 => 'identifier',
- 4 => 'identifier',
- 5 => 'string',
- 6 => 'code',
- 7 => 'string',
- 8 => 'number',
- 9 => 'number',
- 10 => 'number',
- 11 => 'number',
- ),
- 4 =>
- array (
- 0 => 'special',
- ),
- );
- $this->_end = array (
- 0 => '/(?i)`/',
- 1 => '/(?i)\\*\\//',
- 2 => '/(?i)"/',
- 3 => '/(?i)\\)/',
- 4 => '/(?i)\'/',
- );
- $this->_states = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 => 2,
- 6 => 3,
- 7 => 4,
- 8 => -1,
- 9 => -1,
- 10 => -1,
- 11 => -1,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => -1,
- ),
- 3 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 => 2,
- 6 => 3,
- 7 => 4,
- 8 => -1,
- 9 => -1,
- 10 => -1,
- 11 => -1,
- ),
- 4 =>
- array (
- 0 => -1,
- ),
- );
- $this->_keywords = array (
- -1 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 =>
- array (
- ),
- 3 =>
- array (
- 'function' => '/^((?i)abs|acos|adddate|ascii|asin|atan|atan2|avg|benchmark|bin|ceiling|char|coalesce|concat|conv|cos|cot|count|curdate|curtime|database|dayname|dayofmonth|dayofweek|dayofyear|decode|degrees|elt|encode|encrypt|exp|extract|field|floor|format|greatest|hex|hour|if|ifnull|insert|instr|interval|isnull|lcase|least|left|length|locate|log|log10|lower|lpad|ltrim|max|md5|mid|min|minute|mod|month|monthname|now|nullif|oct|ord|password|pi|position|pow|power|prepare|quarter|radians|rand|repeat|replace|reverse|right|round|rpad|rtrim|second|sign|sin|soundex|space|sqrt|std|stddev|strcmp|subdate|substring|sum|sysdate|tan|trim|truncate|ucase|upper|user|version|week|weekday|year)$/',
- ),
- 4 =>
- array (
- 'reserved' => '/^((?i)action|add|aggregate|all|alter|after|and|as|asc|avg|avg_row_length|auto_increment|between|bigint|bit|binary|blob|bool|both|by|cascade|case|char|character|change|check|checksum|column|columns|comment|constraint|create|cross|current_date|current_time|current_timestamp|data|database|databases|date|datetime|day|day_hour|day_minute|day_second|dayofmonth|dayofweek|dayofyear|dec|decimal|default|delayed|delay_key_write|delete|desc|describe|distinct|distinctrow|double|drop|end|else|escape|escaped|enclosed|enum|explain|exists|fields|file|first|float|float4|float8|flush|foreign|from|for|full|function|global|grant|grants|group|having|heap|high_priority|hour|hour_minute|hour_second|hosts|identified|ignore|in|index|infile|inner|insert|insert_id|int|integer|interval|int1|int2|int3|int4|int8|into|if|is|isam|join|key|keys|kill|last_insert_id|leading|left|length|like|lines|limit|load|local|lock|logs|long|longblob|longtext|low_priority|max|max_rows|match|mediumblob|mediumtext|mediumint|middleint|min_rows|minute|minute_second|modify|month|monthname|myisam|natural|numeric|no|not|null|on|optimize|option|optionally|or|order|outer|outfile|pack_keys|partial|password|precision|primary|procedure|process|processlist|privileges|read|real|references|reload|regexp|rename|replace|restrict|returns|revoke|rlike|row|rows|second|select|set|show|shutdown|smallint|soname|sql_big_tables|sql_big_selects|sql_low_priority_updates|sql_log_off|sql_log_update|sql_select_limit|sql_small_result|sql_big_result|sql_warnings|straight_join|starting|status|string|table|tables|temporary|terminated|text|then|time|timestamp|tinyblob|tinytext|tinyint|trailing|to|type|use|using|unique|unlock|unsigned|update|usage|values|varchar|variables|varying|varbinary|with|write|when|where|year|year_month|zerofill)$/',
- ),
- 5 => -1,
- 6 => -1,
- 7 => -1,
- 8 =>
- array (
- ),
- 9 =>
- array (
- ),
- 10 =>
- array (
- ),
- 11 =>
- array (
- ),
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 =>
- array (
- ),
- ),
- 3 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 =>
- array (
- ),
- 3 =>
- array (
- 'function' => '/^((?i)abs|acos|adddate|ascii|asin|atan|atan2|avg|benchmark|bin|ceiling|char|coalesce|concat|conv|cos|cot|count|curdate|curtime|database|dayname|dayofmonth|dayofweek|dayofyear|decode|degrees|elt|encode|encrypt|exp|extract|field|floor|format|greatest|hex|hour|if|ifnull|insert|instr|interval|isnull|lcase|least|left|length|locate|log|log10|lower|lpad|ltrim|max|md5|mid|min|minute|mod|month|monthname|now|nullif|oct|ord|password|pi|position|pow|power|prepare|quarter|radians|rand|repeat|replace|reverse|right|round|rpad|rtrim|second|sign|sin|soundex|space|sqrt|std|stddev|strcmp|subdate|substring|sum|sysdate|tan|trim|truncate|ucase|upper|user|version|week|weekday|year)$/',
- ),
- 4 =>
- array (
- 'reserved' => '/^((?i)action|add|aggregate|all|alter|after|and|as|asc|avg|avg_row_length|auto_increment|between|bigint|bit|binary|blob|bool|both|by|cascade|case|char|character|change|check|checksum|column|columns|comment|constraint|create|cross|current_date|current_time|current_timestamp|data|database|databases|date|datetime|day|day_hour|day_minute|day_second|dayofmonth|dayofweek|dayofyear|dec|decimal|default|delayed|delay_key_write|delete|desc|describe|distinct|distinctrow|double|drop|end|else|escape|escaped|enclosed|enum|explain|exists|fields|file|first|float|float4|float8|flush|foreign|from|for|full|function|global|grant|grants|group|having|heap|high_priority|hour|hour_minute|hour_second|hosts|identified|ignore|in|index|infile|inner|insert|insert_id|int|integer|interval|int1|int2|int3|int4|int8|into|if|is|isam|join|key|keys|kill|last_insert_id|leading|left|length|like|lines|limit|load|local|lock|logs|long|longblob|longtext|low_priority|max|max_rows|match|mediumblob|mediumtext|mediumint|middleint|min_rows|minute|minute_second|modify|month|monthname|myisam|natural|numeric|no|not|null|on|optimize|option|optionally|or|order|outer|outfile|pack_keys|partial|password|precision|primary|procedure|process|processlist|privileges|read|real|references|reload|regexp|rename|replace|restrict|returns|revoke|rlike|row|rows|second|select|set|show|shutdown|smallint|soname|sql_big_tables|sql_big_selects|sql_low_priority_updates|sql_log_off|sql_log_update|sql_select_limit|sql_small_result|sql_big_result|sql_warnings|straight_join|starting|status|string|table|tables|temporary|terminated|text|then|time|timestamp|tinyblob|tinytext|tinyint|trailing|to|type|use|using|unique|unlock|unsigned|update|usage|values|varchar|variables|varying|varbinary|with|write|when|where|year|year_month|zerofill)$/',
- ),
- 5 => -1,
- 6 => -1,
- 7 => -1,
- 8 =>
- array (
- ),
- 9 =>
- array (
- ),
- 10 =>
- array (
- ),
- 11 =>
- array (
- ),
- ),
- 4 =>
- array (
- 0 =>
- array (
- ),
- ),
- );
- $this->_parts = array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => NULL,
- ),
- 3 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- 10 => NULL,
- 11 => NULL,
- ),
- 4 =>
- array (
- 0 => NULL,
- ),
- );
- $this->_subst = array (
- -1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => false,
- ),
- 3 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- ),
- 4 =>
- array (
- 0 => false,
- ),
- );
- $this->_conditions = array (
- );
- $this->_kwmap = array (
- 'function' => 'reserved',
- 'reserved' => 'reserved',
- );
- $this->_defClass = 'code';
- $this->_checkDefines();
- }
-
-} \ No newline at end of file
diff --git a/library/Text_Highlighter/Text/Highlighter/PERL.php b/library/Text_Highlighter/Text/Highlighter/PERL.php
deleted file mode 100644
index 277a5ba45..000000000
--- a/library/Text_Highlighter/Text/Highlighter/PERL.php
+++ /dev/null
@@ -1,1352 +0,0 @@
-<?php
-/**
- * Auto-generated class. PERL syntax highlighting
- *
- * This highlighter is EXPERIMENTAL, so that it may work incorrectly.
- * Most rules were created by Mariusz Jakubowski, and extended by me.
- * My knowledge of Perl is poor, and Perl syntax seems too
- * complicated to me.
- *
- * PHP version 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @link http://pear.php.net/package/Text_Highlighter
- * @category Text
- * @package Text_Highlighter
- * @version generated from: : perl.xml,v 1.1 2007/06/03 02:35:28 ssttoo Exp
- * @author Mariusz 'kg' Jakubowski <kg@alternatywa.info>
- * @author Andrey Demenev <demenev@gmail.com>
- *
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter.php';
-
-/**
- * Auto-generated class. PERL syntax highlighting
- *
- * @author Mariusz 'kg' Jakubowski <kg@alternatywa.info>
- * @author Andrey Demenev <demenev@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: @package_version@
- * @link http://pear.php.net/package/Text_Highlighter
- */
-class Text_Highlighter_PERL extends Text_Highlighter
-{
- var $_language = 'perl';
-
- /**
- * PHP4 Compatible Constructor
- *
- * @param array $options
- * @access public
- */
- function Text_Highlighter_PERL($options=array())
- {
- $this->__construct($options);
- }
-
-
- /**
- * Constructor
- *
- * @param array $options
- * @access public
- */
- function __construct($options=array())
- {
-
- $this->_options = $options;
- $this->_regs = array (
- -1 => '/((?m)^(#!)(.*))|((?m)^=\\w+)|(\\{)|(\\()|(\\[)|((use)\\s+([\\w:]*))|([& ](\\w{2,}::)+\\w{2,})|((?Us)\\b(q[wq]\\s*((\\{)|(\\()|(\\[)|(\\<)|([\\W\\S])))(?=(.*)((?(3)\\})(?(4)\\))(?(5)\\])(?(6)\\>)(?(7)\\7))))|((?Us)\\b(q\\s*((\\{)|(\\()|(\\[)|(\\<)|([\\W\\S])))(?=(.*)((?(3)\\})(?(4)\\))(?(5)\\])(?(6)\\>)(?(7)\\7))))|(#.*)|((?x)(s|tr) ([|#~`!@$%^&*-+=\\\\;:\'",.\\/?]) ((\\\\.|[^\\\\])*?) (\\2)((\\\\.|[^\\\\])*?)(\\2[ecgimosx]*))|((?x)(m) ([|#~`!@$%^&*-+=\\\\;:\'",.\\/?]) ((\\\\.|[^\\\\])*?) (\\2[ecgimosx]*))|( \\/)|(\\$#?[1-9\'`@!])|((?i)(\\$#?|[@%*])([a-z1-9_]+::)*([a-z1-9_]+|\\^(?-i)[A-Z]?(?i)))|((?i)\\$([a-z1-9_]+|\\^(?-i)[A-Z]?(?i)))|((?i)(&|\\w+)\'[\\w_\']+\\b)|((?i)(\\{)([a-z1-9]+)(\\}))|((?i)[\\$@%]#?\\{[a-z1-9]+\\})|(`)|(\')|(")|((?i)[a-z_]\\w*)|(\\d*\\.?\\d+)/',
- 0 => '//',
- 1 => '/((?m)^(#!)(.*))|((?m)^=\\w+)|(\\{)|(\\()|(\\[)|((use)\\s+([\\w:]*))|([& ](\\w{2,}::)+\\w{2,})|((?Us)\\b(q[wq]\\s*((\\{)|(\\()|(\\[)|(\\<)|([\\W\\S])))(?=(.*)((?(3)\\})(?(4)\\))(?(5)\\])(?(6)\\>)(?(7)\\7))))|((?Us)\\b(q\\s*((\\{)|(\\()|(\\[)|(\\<)|([\\W\\S])))(?=(.*)((?(3)\\})(?(4)\\))(?(5)\\])(?(6)\\>)(?(7)\\7))))|(#.*)|((?x)(s|tr) ([|#~`!@$%^&*-+=\\\\;:\'",.\\/?]) ((\\\\.|[^\\\\])*?) (\\2)((\\\\.|[^\\\\])*?)(\\2[ecgimosx]*))|((?x)(m) ([|#~`!@$%^&*-+=\\\\;:\'",.\\/?]) ((\\\\.|[^\\\\])*?) (\\2[ecgimosx]*))|( \\/)|(\\$#?[1-9\'`@!])|((?i)(\\$#?|[@%*])([a-z1-9_]+::)*([a-z1-9_]+|\\^(?-i)[A-Z]?(?i)))|((?i)\\$([a-z1-9_]+|\\^(?-i)[A-Z]?(?i)))|((?i)(&|\\w+)\'[\\w_\']+\\b)|((?i)(\\{)([a-z1-9]+)(\\}))|((?i)[\\$@%]#?\\{[a-z1-9]+\\})|(`)|(\')|(")|((?i)[a-z_]\\w*)|(\\d*\\.?\\d+)/',
- 2 => '/((?m)^(#!)(.*))|((?m)^=\\w+)|(\\{)|(\\()|(\\[)|((use)\\s+([\\w:]*))|([& ](\\w{2,}::)+\\w{2,})|((?Us)\\b(q[wq]\\s*((\\{)|(\\()|(\\[)|(\\<)|([\\W\\S])))(?=(.*)((?(3)\\})(?(4)\\))(?(5)\\])(?(6)\\>)(?(7)\\7))))|((?Us)\\b(q\\s*((\\{)|(\\()|(\\[)|(\\<)|([\\W\\S])))(?=(.*)((?(3)\\})(?(4)\\))(?(5)\\])(?(6)\\>)(?(7)\\7))))|(#.*)|((?x)(s|tr) ([|#~`!@$%^&*-+=\\\\;:\'",.\\/?]) ((\\\\.|[^\\\\])*?) (\\2)((\\\\.|[^\\\\])*?)(\\2[ecgimosx]*))|((?x)(m) ([|#~`!@$%^&*-+=\\\\;:\'",.\\/?]) ((\\\\.|[^\\\\])*?) (\\2[ecgimosx]*))|( \\/)|((?i)([a-z1-9_]+)(\\s*=>))|(\\$#?[1-9\'`@!])|((?i)(\\$#?|[@%*])([a-z1-9_]+::)*([a-z1-9_]+|\\^(?-i)[A-Z]?(?i)))|((?i)\\$([a-z1-9_]+|\\^(?-i)[A-Z]?(?i)))|((?i)(&|\\w+)\'[\\w_\']+\\b)|((?i)(\\{)([a-z1-9]+)(\\}))|((?i)[\\$@%]#?\\{[a-z1-9]+\\})|(`)|(\')|(")|((?i)[a-z_]\\w*)|(\\d*\\.?\\d+)/',
- 3 => '/((?m)^(#!)(.*))|((?m)^=\\w+)|(\\{)|(\\()|(\\[)|((use)\\s+([\\w:]*))|([& ](\\w{2,}::)+\\w{2,})|((?Us)\\b(q[wq]\\s*((\\{)|(\\()|(\\[)|(\\<)|([\\W\\S])))(?=(.*)((?(3)\\})(?(4)\\))(?(5)\\])(?(6)\\>)(?(7)\\7))))|((?Us)\\b(q\\s*((\\{)|(\\()|(\\[)|(\\<)|([\\W\\S])))(?=(.*)((?(3)\\})(?(4)\\))(?(5)\\])(?(6)\\>)(?(7)\\7))))|(#.*)|((?x)(s|tr) ([|#~`!@$%^&*-+=\\\\;:\'",.\\/?]) ((\\\\.|[^\\\\])*?) (\\2)((\\\\.|[^\\\\])*?)(\\2[ecgimosx]*))|((?x)(m) ([|#~`!@$%^&*-+=\\\\;:\'",.\\/?]) ((\\\\.|[^\\\\])*?) (\\2[ecgimosx]*))|( \\/)|(\\$#?[1-9\'`@!])|((?i)(\\$#?|[@%*])([a-z1-9_]+::)*([a-z1-9_]+|\\^(?-i)[A-Z]?(?i)))|((?i)\\$([a-z1-9_]+|\\^(?-i)[A-Z]?(?i)))|((?i)(&|\\w+)\'[\\w_\']+\\b)|((?i)(\\{)([a-z1-9]+)(\\}))|((?i)[\\$@%]#?\\{[a-z1-9]+\\})|(`)|(\')|(")|((?i)[a-z_]\\w*)|(\\d*\\.?\\d+)/',
- 4 => '/(\\$#?[1-9\'`@!])|((?i)\\$([a-z1-9_]+|\\^(?-i)[A-Z]?(?i)))|((?i)[\\$@%]#?\\{[a-z1-9]+\\})|(\\\\[\\\\"\'`tnr\\$\\{@])/',
- 5 => '/(\\\\\\\\|\\\\"|\\\\\'|\\\\`)/',
- 6 => '/(\\\\\\/)/',
- 7 => '/(\\$#?[1-9\'`@!])|((?i)\\$([a-z1-9_]+|\\^(?-i)[A-Z]?(?i)))|((?i)[\\$@%]#?\\{[a-z1-9]+\\})|(\\\\\\\\|\\\\"|\\\\\'|\\\\`)/',
- 8 => '/(\\\\\\\\|\\\\"|\\\\\'|\\\\`)/',
- 9 => '/(\\$#?[1-9\'`@!])|((?i)\\$([a-z1-9_]+|\\^(?-i)[A-Z]?(?i)))|((?i)[\\$@%]#?\\{[a-z1-9]+\\})|(\\\\[\\\\"\'`tnr\\$\\{@])/',
- );
- $this->_counts = array (
- -1 =>
- array (
- 0 => 2,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 2,
- 6 => 1,
- 7 => 9,
- 8 => 9,
- 9 => 0,
- 10 => 8,
- 11 => 5,
- 12 => 0,
- 13 => 0,
- 14 => 3,
- 15 => 1,
- 16 => 1,
- 17 => 3,
- 18 => 0,
- 19 => 0,
- 20 => 0,
- 21 => 0,
- 22 => 0,
- 23 => 0,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => 2,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 2,
- 6 => 1,
- 7 => 9,
- 8 => 9,
- 9 => 0,
- 10 => 8,
- 11 => 5,
- 12 => 0,
- 13 => 0,
- 14 => 3,
- 15 => 1,
- 16 => 1,
- 17 => 3,
- 18 => 0,
- 19 => 0,
- 20 => 0,
- 21 => 0,
- 22 => 0,
- 23 => 0,
- ),
- 2 =>
- array (
- 0 => 2,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 2,
- 6 => 1,
- 7 => 9,
- 8 => 9,
- 9 => 0,
- 10 => 8,
- 11 => 5,
- 12 => 0,
- 13 => 2,
- 14 => 0,
- 15 => 3,
- 16 => 1,
- 17 => 1,
- 18 => 3,
- 19 => 0,
- 20 => 0,
- 21 => 0,
- 22 => 0,
- 23 => 0,
- 24 => 0,
- ),
- 3 =>
- array (
- 0 => 2,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 2,
- 6 => 1,
- 7 => 9,
- 8 => 9,
- 9 => 0,
- 10 => 8,
- 11 => 5,
- 12 => 0,
- 13 => 0,
- 14 => 3,
- 15 => 1,
- 16 => 1,
- 17 => 3,
- 18 => 0,
- 19 => 0,
- 20 => 0,
- 21 => 0,
- 22 => 0,
- 23 => 0,
- ),
- 4 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 0,
- 3 => 0,
- ),
- 5 =>
- array (
- 0 => 0,
- ),
- 6 =>
- array (
- 0 => 0,
- ),
- 7 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 0,
- 3 => 0,
- ),
- 8 =>
- array (
- 0 => 0,
- ),
- 9 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 0,
- 3 => 0,
- ),
- );
- $this->_delim = array (
- -1 =>
- array (
- 0 => '',
- 1 => 'comment',
- 2 => 'brackets',
- 3 => 'brackets',
- 4 => 'brackets',
- 5 => '',
- 6 => '',
- 7 => 'quotes',
- 8 => 'quotes',
- 9 => '',
- 10 => '',
- 11 => '',
- 12 => 'quotes',
- 13 => '',
- 14 => '',
- 15 => '',
- 16 => '',
- 17 => '',
- 18 => '',
- 19 => 'quotes',
- 20 => 'quotes',
- 21 => 'quotes',
- 22 => '',
- 23 => '',
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => '',
- 1 => 'comment',
- 2 => 'brackets',
- 3 => 'brackets',
- 4 => 'brackets',
- 5 => '',
- 6 => '',
- 7 => 'quotes',
- 8 => 'quotes',
- 9 => '',
- 10 => '',
- 11 => '',
- 12 => 'quotes',
- 13 => '',
- 14 => '',
- 15 => '',
- 16 => '',
- 17 => '',
- 18 => '',
- 19 => 'quotes',
- 20 => 'quotes',
- 21 => 'quotes',
- 22 => '',
- 23 => '',
- ),
- 2 =>
- array (
- 0 => '',
- 1 => 'comment',
- 2 => 'brackets',
- 3 => 'brackets',
- 4 => 'brackets',
- 5 => '',
- 6 => '',
- 7 => 'quotes',
- 8 => 'quotes',
- 9 => '',
- 10 => '',
- 11 => '',
- 12 => 'quotes',
- 13 => '',
- 14 => '',
- 15 => '',
- 16 => '',
- 17 => '',
- 18 => '',
- 19 => '',
- 20 => 'quotes',
- 21 => 'quotes',
- 22 => 'quotes',
- 23 => '',
- 24 => '',
- ),
- 3 =>
- array (
- 0 => '',
- 1 => 'comment',
- 2 => 'brackets',
- 3 => 'brackets',
- 4 => 'brackets',
- 5 => '',
- 6 => '',
- 7 => 'quotes',
- 8 => 'quotes',
- 9 => '',
- 10 => '',
- 11 => '',
- 12 => 'quotes',
- 13 => '',
- 14 => '',
- 15 => '',
- 16 => '',
- 17 => '',
- 18 => '',
- 19 => 'quotes',
- 20 => 'quotes',
- 21 => 'quotes',
- 22 => '',
- 23 => '',
- ),
- 4 =>
- array (
- 0 => '',
- 1 => '',
- 2 => '',
- 3 => '',
- ),
- 5 =>
- array (
- 0 => '',
- ),
- 6 =>
- array (
- 0 => '',
- ),
- 7 =>
- array (
- 0 => '',
- 1 => '',
- 2 => '',
- 3 => '',
- ),
- 8 =>
- array (
- 0 => '',
- ),
- 9 =>
- array (
- 0 => '',
- 1 => '',
- 2 => '',
- 3 => '',
- ),
- );
- $this->_inner = array (
- -1 =>
- array (
- 0 => 'special',
- 1 => 'comment',
- 2 => 'code',
- 3 => 'code',
- 4 => 'code',
- 5 => 'special',
- 6 => 'special',
- 7 => 'string',
- 8 => 'string',
- 9 => 'comment',
- 10 => 'string',
- 11 => 'string',
- 12 => 'string',
- 13 => 'var',
- 14 => 'var',
- 15 => 'var',
- 16 => 'var',
- 17 => 'var',
- 18 => 'var',
- 19 => 'string',
- 20 => 'string',
- 21 => 'string',
- 22 => 'identifier',
- 23 => 'number',
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => 'special',
- 1 => 'comment',
- 2 => 'code',
- 3 => 'code',
- 4 => 'code',
- 5 => 'special',
- 6 => 'special',
- 7 => 'string',
- 8 => 'string',
- 9 => 'comment',
- 10 => 'string',
- 11 => 'string',
- 12 => 'string',
- 13 => 'var',
- 14 => 'var',
- 15 => 'var',
- 16 => 'var',
- 17 => 'var',
- 18 => 'var',
- 19 => 'string',
- 20 => 'string',
- 21 => 'string',
- 22 => 'identifier',
- 23 => 'number',
- ),
- 2 =>
- array (
- 0 => 'special',
- 1 => 'comment',
- 2 => 'code',
- 3 => 'code',
- 4 => 'code',
- 5 => 'special',
- 6 => 'special',
- 7 => 'string',
- 8 => 'string',
- 9 => 'comment',
- 10 => 'string',
- 11 => 'string',
- 12 => 'string',
- 13 => 'string',
- 14 => 'var',
- 15 => 'var',
- 16 => 'var',
- 17 => 'var',
- 18 => 'var',
- 19 => 'var',
- 20 => 'string',
- 21 => 'string',
- 22 => 'string',
- 23 => 'identifier',
- 24 => 'number',
- ),
- 3 =>
- array (
- 0 => 'special',
- 1 => 'comment',
- 2 => 'code',
- 3 => 'code',
- 4 => 'code',
- 5 => 'special',
- 6 => 'special',
- 7 => 'string',
- 8 => 'string',
- 9 => 'comment',
- 10 => 'string',
- 11 => 'string',
- 12 => 'string',
- 13 => 'var',
- 14 => 'var',
- 15 => 'var',
- 16 => 'var',
- 17 => 'var',
- 18 => 'var',
- 19 => 'string',
- 20 => 'string',
- 21 => 'string',
- 22 => 'identifier',
- 23 => 'number',
- ),
- 4 =>
- array (
- 0 => 'var',
- 1 => 'var',
- 2 => 'var',
- 3 => 'special',
- ),
- 5 =>
- array (
- 0 => 'special',
- ),
- 6 =>
- array (
- 0 => 'string',
- ),
- 7 =>
- array (
- 0 => 'var',
- 1 => 'var',
- 2 => 'var',
- 3 => 'special',
- ),
- 8 =>
- array (
- 0 => 'special',
- ),
- 9 =>
- array (
- 0 => 'var',
- 1 => 'var',
- 2 => 'var',
- 3 => 'special',
- ),
- );
- $this->_end = array (
- 0 => '/(?m)^=cut[^\\n]*/',
- 1 => '/\\}/',
- 2 => '/\\)/',
- 3 => '/\\]/',
- 4 => '/%b2%/',
- 5 => '/%b2%/',
- 6 => '/\\/[cgimosx]*/',
- 7 => '/`/',
- 8 => '/\'/',
- 9 => '/"/',
- );
- $this->_states = array (
- -1 =>
- array (
- 0 => -1,
- 1 => 0,
- 2 => 1,
- 3 => 2,
- 4 => 3,
- 5 => -1,
- 6 => -1,
- 7 => 4,
- 8 => 5,
- 9 => -1,
- 10 => -1,
- 11 => -1,
- 12 => 6,
- 13 => -1,
- 14 => -1,
- 15 => -1,
- 16 => -1,
- 17 => -1,
- 18 => -1,
- 19 => 7,
- 20 => 8,
- 21 => 9,
- 22 => -1,
- 23 => -1,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => -1,
- 1 => 0,
- 2 => 1,
- 3 => 2,
- 4 => 3,
- 5 => -1,
- 6 => -1,
- 7 => 4,
- 8 => 5,
- 9 => -1,
- 10 => -1,
- 11 => -1,
- 12 => 6,
- 13 => -1,
- 14 => -1,
- 15 => -1,
- 16 => -1,
- 17 => -1,
- 18 => -1,
- 19 => 7,
- 20 => 8,
- 21 => 9,
- 22 => -1,
- 23 => -1,
- ),
- 2 =>
- array (
- 0 => -1,
- 1 => 0,
- 2 => 1,
- 3 => 2,
- 4 => 3,
- 5 => -1,
- 6 => -1,
- 7 => 4,
- 8 => 5,
- 9 => -1,
- 10 => -1,
- 11 => -1,
- 12 => 6,
- 13 => -1,
- 14 => -1,
- 15 => -1,
- 16 => -1,
- 17 => -1,
- 18 => -1,
- 19 => -1,
- 20 => 7,
- 21 => 8,
- 22 => 9,
- 23 => -1,
- 24 => -1,
- ),
- 3 =>
- array (
- 0 => -1,
- 1 => 0,
- 2 => 1,
- 3 => 2,
- 4 => 3,
- 5 => -1,
- 6 => -1,
- 7 => 4,
- 8 => 5,
- 9 => -1,
- 10 => -1,
- 11 => -1,
- 12 => 6,
- 13 => -1,
- 14 => -1,
- 15 => -1,
- 16 => -1,
- 17 => -1,
- 18 => -1,
- 19 => 7,
- 20 => 8,
- 21 => 9,
- 22 => -1,
- 23 => -1,
- ),
- 4 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- ),
- 5 =>
- array (
- 0 => -1,
- ),
- 6 =>
- array (
- 0 => -1,
- ),
- 7 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- ),
- 8 =>
- array (
- 0 => -1,
- ),
- 9 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- ),
- );
- $this->_keywords = array (
- -1 =>
- array (
- 0 =>
- array (
- ),
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 =>
- array (
- ),
- 6 =>
- array (
- ),
- 7 => -1,
- 8 => -1,
- 9 =>
- array (
- ),
- 10 =>
- array (
- ),
- 11 =>
- array (
- ),
- 12 => -1,
- 13 =>
- array (
- ),
- 14 =>
- array (
- ),
- 15 =>
- array (
- ),
- 16 =>
- array (
- ),
- 17 =>
- array (
- ),
- 18 =>
- array (
- ),
- 19 => -1,
- 20 => -1,
- 21 => -1,
- 22 =>
- array (
- 'reserved' => '/^(abs|accept|alarm|atan2|bind|binmode|bless|caller|chdir|chmod|chomp|chop|chown|chr|chroot|close|closedir|connect|continue|cos|crypt|dbmclose|dbmopen|defined|delete|die|do|dump|each|endgrent|endhostent|endnetent|endprotoent|endpwent|endservent|eof|eval|exec|exists|exit|exp|fcntl|fileno|flock|fork|format|formline|getc|getgrent|getgrgid|getgrnam|gethostbyaddr|gethostbyname|gethostent|getlogin|getnetbyaddr|getnetbyname|getnetent|getpeername|getpgrp|getppid|getpriority|getprotobyname|getprotobynumber|getprotoent|getpwent|getpwnam|getpwuid|getservbyname|getservbyport|getservent|getsockname|getsockopt|glob|gmtime|goto|grep|hex|import|index|int|ioctl|join|keys|kill|last|lc|lcfirst|length|link|listen|local|localtime|lock|log|lstat|map|mkdir|msgctl|msgget|msgrcv|msgsnd|my|next|no|oct|open|opendir|ord|our|pack|package|pipe|pop|pos|print|printf|prototype|push|quotemeta|rand|read|readdir|readline|readlink|readpipe|recv|redo|ref|rename|require|reset|return|reverse|rewinddir|rindex|rmdir|scalar|seek|seekdir|select|semctl|semget|semop|send|setgrent|sethostent|setnetent|setpgrp|setpriority|setprotoent|setpwent|setservent|setsockopt|shift|shmctl|shmget|shmread|shmwrite|shutdown|sin|sleep|socket|socketpair|sort|splice|split|sprintf|sqrt|srand|stat|study|sub|substr|symlink|syscall|sysopen|sysread|sysseek|system|syswrite|tell|telldir|tie|tied|time|times|truncate|uc|ucfirst|umask|undef|unlink|unpack|unshift|untie|use|utime|values|vec|wait|waitpid|wantarray|warn|write|y)$/',
- 'missingreserved' => '/^(new)$/',
- 'flowcontrol' => '/^(if|else|elsif|while|unless|for|foreach|until|do|continue|not|or|and|eq|ne|gt|lt)$/',
- ),
- 23 =>
- array (
- ),
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 =>
- array (
- ),
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 =>
- array (
- ),
- 6 =>
- array (
- ),
- 7 => -1,
- 8 => -1,
- 9 =>
- array (
- ),
- 10 =>
- array (
- ),
- 11 =>
- array (
- ),
- 12 => -1,
- 13 =>
- array (
- ),
- 14 =>
- array (
- ),
- 15 =>
- array (
- ),
- 16 =>
- array (
- ),
- 17 =>
- array (
- ),
- 18 =>
- array (
- ),
- 19 => -1,
- 20 => -1,
- 21 => -1,
- 22 =>
- array (
- 'reserved' => '/^(abs|accept|alarm|atan2|bind|binmode|bless|caller|chdir|chmod|chomp|chop|chown|chr|chroot|close|closedir|connect|continue|cos|crypt|dbmclose|dbmopen|defined|delete|die|do|dump|each|endgrent|endhostent|endnetent|endprotoent|endpwent|endservent|eof|eval|exec|exists|exit|exp|fcntl|fileno|flock|fork|format|formline|getc|getgrent|getgrgid|getgrnam|gethostbyaddr|gethostbyname|gethostent|getlogin|getnetbyaddr|getnetbyname|getnetent|getpeername|getpgrp|getppid|getpriority|getprotobyname|getprotobynumber|getprotoent|getpwent|getpwnam|getpwuid|getservbyname|getservbyport|getservent|getsockname|getsockopt|glob|gmtime|goto|grep|hex|import|index|int|ioctl|join|keys|kill|last|lc|lcfirst|length|link|listen|local|localtime|lock|log|lstat|map|mkdir|msgctl|msgget|msgrcv|msgsnd|my|next|no|oct|open|opendir|ord|our|pack|package|pipe|pop|pos|print|printf|prototype|push|quotemeta|rand|read|readdir|readline|readlink|readpipe|recv|redo|ref|rename|require|reset|return|reverse|rewinddir|rindex|rmdir|scalar|seek|seekdir|select|semctl|semget|semop|send|setgrent|sethostent|setnetent|setpgrp|setpriority|setprotoent|setpwent|setservent|setsockopt|shift|shmctl|shmget|shmread|shmwrite|shutdown|sin|sleep|socket|socketpair|sort|splice|split|sprintf|sqrt|srand|stat|study|sub|substr|symlink|syscall|sysopen|sysread|sysseek|system|syswrite|tell|telldir|tie|tied|time|times|truncate|uc|ucfirst|umask|undef|unlink|unpack|unshift|untie|use|utime|values|vec|wait|waitpid|wantarray|warn|write|y)$/',
- 'missingreserved' => '/^(new)$/',
- 'flowcontrol' => '/^(if|else|elsif|while|unless|for|foreach|until|do|continue|not|or|and|eq|ne|gt|lt)$/',
- ),
- 23 =>
- array (
- ),
- ),
- 2 =>
- array (
- 0 =>
- array (
- ),
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 =>
- array (
- ),
- 6 =>
- array (
- ),
- 7 => -1,
- 8 => -1,
- 9 =>
- array (
- ),
- 10 =>
- array (
- ),
- 11 =>
- array (
- ),
- 12 => -1,
- 13 =>
- array (
- ),
- 14 =>
- array (
- ),
- 15 =>
- array (
- ),
- 16 =>
- array (
- ),
- 17 =>
- array (
- ),
- 18 =>
- array (
- ),
- 19 =>
- array (
- ),
- 20 => -1,
- 21 => -1,
- 22 => -1,
- 23 =>
- array (
- 'reserved' => '/^(abs|accept|alarm|atan2|bind|binmode|bless|caller|chdir|chmod|chomp|chop|chown|chr|chroot|close|closedir|connect|continue|cos|crypt|dbmclose|dbmopen|defined|delete|die|do|dump|each|endgrent|endhostent|endnetent|endprotoent|endpwent|endservent|eof|eval|exec|exists|exit|exp|fcntl|fileno|flock|fork|format|formline|getc|getgrent|getgrgid|getgrnam|gethostbyaddr|gethostbyname|gethostent|getlogin|getnetbyaddr|getnetbyname|getnetent|getpeername|getpgrp|getppid|getpriority|getprotobyname|getprotobynumber|getprotoent|getpwent|getpwnam|getpwuid|getservbyname|getservbyport|getservent|getsockname|getsockopt|glob|gmtime|goto|grep|hex|import|index|int|ioctl|join|keys|kill|last|lc|lcfirst|length|link|listen|local|localtime|lock|log|lstat|map|mkdir|msgctl|msgget|msgrcv|msgsnd|my|next|no|oct|open|opendir|ord|our|pack|package|pipe|pop|pos|print|printf|prototype|push|quotemeta|rand|read|readdir|readline|readlink|readpipe|recv|redo|ref|rename|require|reset|return|reverse|rewinddir|rindex|rmdir|scalar|seek|seekdir|select|semctl|semget|semop|send|setgrent|sethostent|setnetent|setpgrp|setpriority|setprotoent|setpwent|setservent|setsockopt|shift|shmctl|shmget|shmread|shmwrite|shutdown|sin|sleep|socket|socketpair|sort|splice|split|sprintf|sqrt|srand|stat|study|sub|substr|symlink|syscall|sysopen|sysread|sysseek|system|syswrite|tell|telldir|tie|tied|time|times|truncate|uc|ucfirst|umask|undef|unlink|unpack|unshift|untie|use|utime|values|vec|wait|waitpid|wantarray|warn|write|y)$/',
- 'missingreserved' => '/^(new)$/',
- 'flowcontrol' => '/^(if|else|elsif|while|unless|for|foreach|until|do|continue|not|or|and|eq|ne|gt|lt)$/',
- ),
- 24 =>
- array (
- ),
- ),
- 3 =>
- array (
- 0 =>
- array (
- ),
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 =>
- array (
- ),
- 6 =>
- array (
- ),
- 7 => -1,
- 8 => -1,
- 9 =>
- array (
- ),
- 10 =>
- array (
- ),
- 11 =>
- array (
- ),
- 12 => -1,
- 13 =>
- array (
- ),
- 14 =>
- array (
- ),
- 15 =>
- array (
- ),
- 16 =>
- array (
- ),
- 17 =>
- array (
- ),
- 18 =>
- array (
- ),
- 19 => -1,
- 20 => -1,
- 21 => -1,
- 22 =>
- array (
- 'reserved' => '/^(abs|accept|alarm|atan2|bind|binmode|bless|caller|chdir|chmod|chomp|chop|chown|chr|chroot|close|closedir|connect|continue|cos|crypt|dbmclose|dbmopen|defined|delete|die|do|dump|each|endgrent|endhostent|endnetent|endprotoent|endpwent|endservent|eof|eval|exec|exists|exit|exp|fcntl|fileno|flock|fork|format|formline|getc|getgrent|getgrgid|getgrnam|gethostbyaddr|gethostbyname|gethostent|getlogin|getnetbyaddr|getnetbyname|getnetent|getpeername|getpgrp|getppid|getpriority|getprotobyname|getprotobynumber|getprotoent|getpwent|getpwnam|getpwuid|getservbyname|getservbyport|getservent|getsockname|getsockopt|glob|gmtime|goto|grep|hex|import|index|int|ioctl|join|keys|kill|last|lc|lcfirst|length|link|listen|local|localtime|lock|log|lstat|map|mkdir|msgctl|msgget|msgrcv|msgsnd|my|next|no|oct|open|opendir|ord|our|pack|package|pipe|pop|pos|print|printf|prototype|push|quotemeta|rand|read|readdir|readline|readlink|readpipe|recv|redo|ref|rename|require|reset|return|reverse|rewinddir|rindex|rmdir|scalar|seek|seekdir|select|semctl|semget|semop|send|setgrent|sethostent|setnetent|setpgrp|setpriority|setprotoent|setpwent|setservent|setsockopt|shift|shmctl|shmget|shmread|shmwrite|shutdown|sin|sleep|socket|socketpair|sort|splice|split|sprintf|sqrt|srand|stat|study|sub|substr|symlink|syscall|sysopen|sysread|sysseek|system|syswrite|tell|telldir|tie|tied|time|times|truncate|uc|ucfirst|umask|undef|unlink|unpack|unshift|untie|use|utime|values|vec|wait|waitpid|wantarray|warn|write|y)$/',
- 'missingreserved' => '/^(new)$/',
- 'flowcontrol' => '/^(if|else|elsif|while|unless|for|foreach|until|do|continue|not|or|and|eq|ne|gt|lt)$/',
- ),
- 23 =>
- array (
- ),
- ),
- 4 =>
- array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- 3 =>
- array (
- ),
- ),
- 5 =>
- array (
- 0 =>
- array (
- ),
- ),
- 6 =>
- array (
- 0 =>
- array (
- ),
- ),
- 7 =>
- array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- 3 =>
- array (
- ),
- ),
- 8 =>
- array (
- 0 =>
- array (
- ),
- ),
- 9 =>
- array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- 3 =>
- array (
- ),
- ),
- );
- $this->_parts = array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 =>
- array (
- 1 => 'special',
- 2 => 'string',
- ),
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 =>
- array (
- 1 => 'reserved',
- 2 => 'special',
- ),
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- 10 =>
- array (
- 1 => 'quotes',
- 2 => 'quotes',
- 3 => 'string',
- 5 => 'quotes',
- 6 => 'string',
- 8 => 'quotes',
- ),
- 11 =>
- array (
- 1 => 'quotes',
- 2 => 'quotes',
- 3 => 'string',
- 5 => 'quotes',
- ),
- 12 => NULL,
- 13 => NULL,
- 14 => NULL,
- 15 => NULL,
- 16 => NULL,
- 17 =>
- array (
- 1 => 'brackets',
- 2 => 'var',
- 3 => 'brackets',
- ),
- 18 => NULL,
- 19 => NULL,
- 20 => NULL,
- 21 => NULL,
- 22 => NULL,
- 23 => NULL,
- ),
- 2 =>
- array (
- 0 =>
- array (
- 1 => 'special',
- 2 => 'string',
- ),
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 =>
- array (
- 1 => 'reserved',
- 2 => 'special',
- ),
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- 10 =>
- array (
- 1 => 'quotes',
- 2 => 'quotes',
- 3 => 'string',
- 5 => 'quotes',
- 6 => 'string',
- 8 => 'quotes',
- ),
- 11 =>
- array (
- 1 => 'quotes',
- 2 => 'quotes',
- 3 => 'string',
- 5 => 'quotes',
- ),
- 12 => NULL,
- 13 =>
- array (
- 1 => 'string',
- 2 => 'code',
- ),
- 14 => NULL,
- 15 => NULL,
- 16 => NULL,
- 17 => NULL,
- 18 =>
- array (
- 1 => 'brackets',
- 2 => 'var',
- 3 => 'brackets',
- ),
- 19 => NULL,
- 20 => NULL,
- 21 => NULL,
- 22 => NULL,
- 23 => NULL,
- 24 => NULL,
- ),
- 3 =>
- array (
- 0 =>
- array (
- 1 => 'special',
- 2 => 'string',
- ),
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 =>
- array (
- 1 => 'reserved',
- 2 => 'special',
- ),
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- 10 =>
- array (
- 1 => 'quotes',
- 2 => 'quotes',
- 3 => 'string',
- 5 => 'quotes',
- 6 => 'string',
- 8 => 'quotes',
- ),
- 11 =>
- array (
- 1 => 'quotes',
- 2 => 'quotes',
- 3 => 'string',
- 5 => 'quotes',
- ),
- 12 => NULL,
- 13 => NULL,
- 14 => NULL,
- 15 => NULL,
- 16 => NULL,
- 17 =>
- array (
- 1 => 'brackets',
- 2 => 'var',
- 3 => 'brackets',
- ),
- 18 => NULL,
- 19 => NULL,
- 20 => NULL,
- 21 => NULL,
- 22 => NULL,
- 23 => NULL,
- ),
- 4 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- ),
- 5 =>
- array (
- 0 => NULL,
- ),
- 6 =>
- array (
- 0 => NULL,
- ),
- 7 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- ),
- 8 =>
- array (
- 0 => NULL,
- ),
- 9 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- ),
- );
- $this->_subst = array (
- -1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => true,
- 8 => true,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- 14 => false,
- 15 => false,
- 16 => false,
- 17 => false,
- 18 => false,
- 19 => false,
- 20 => false,
- 21 => false,
- 22 => false,
- 23 => false,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => true,
- 8 => true,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- 14 => false,
- 15 => false,
- 16 => false,
- 17 => false,
- 18 => false,
- 19 => false,
- 20 => false,
- 21 => false,
- 22 => false,
- 23 => false,
- ),
- 2 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => true,
- 8 => true,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- 14 => false,
- 15 => false,
- 16 => false,
- 17 => false,
- 18 => false,
- 19 => false,
- 20 => false,
- 21 => false,
- 22 => false,
- 23 => false,
- 24 => false,
- ),
- 3 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => true,
- 8 => true,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- 14 => false,
- 15 => false,
- 16 => false,
- 17 => false,
- 18 => false,
- 19 => false,
- 20 => false,
- 21 => false,
- 22 => false,
- 23 => false,
- ),
- 4 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- ),
- 5 =>
- array (
- 0 => false,
- ),
- 6 =>
- array (
- 0 => false,
- ),
- 7 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- ),
- 8 =>
- array (
- 0 => false,
- ),
- 9 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- ),
- );
- $this->_conditions = array (
- );
- $this->_kwmap = array (
- 'reserved' => 'reserved',
- 'missingreserved' => 'reserved',
- 'flowcontrol' => 'reserved',
- );
- $this->_defClass = 'code';
- $this->_checkDefines();
- }
-
-} \ No newline at end of file
diff --git a/library/Text_Highlighter/Text/Highlighter/PHP.php b/library/Text_Highlighter/Text/Highlighter/PHP.php
deleted file mode 100644
index 1ee2e6b90..000000000
--- a/library/Text_Highlighter/Text/Highlighter/PHP.php
+++ /dev/null
@@ -1,1107 +0,0 @@
-<?php
-/**
- * Auto-generated class. PHP syntax highlighting
- *
- * PHP version 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @link http://pear.php.net/package/Text_Highlighter
- * @category Text
- * @package Text_Highlighter
- * @version generated from: : php.xml,v 1.1 2007/06/03 02:35:28 ssttoo Exp
- * @author Andrey Demenev <demenev@gmail.com>
- *
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter.php';
-
-/**
- * Auto-generated class. PHP syntax highlighting
- *
- * @author Andrey Demenev <demenev@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: @package_version@
- * @link http://pear.php.net/package/Text_Highlighter
- */
-class Text_Highlighter_PHP extends Text_Highlighter
-{
- var $_language = 'php';
-
- /**
- * PHP4 Compatible Constructor
- *
- * @param array $options
- * @access public
- */
- function Text_Highlighter_PHP($options=array())
- {
- $this->__construct($options);
- }
-
-
- /**
- * Constructor
- *
- * @param array $options
- * @access public
- */
- function __construct($options=array())
- {
-
- $this->_options = $options;
- $this->_regs = array (
- -1 => '/((?i)\\<\\?(php|=)?)/',
- 0 => '/((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)\\/\\*)|((?i)")|((?i)`)|((?mi)\\<\\<\\<[\\x20\\x09]*(\\w+)$)|((?i)\')|((?i)(#|\\/\\/))|((?i)[a-z_]\\w*)|((?i)\\((array|int|integer|string|bool|boolean|object|float|double)\\))|((?i)0[xX][\\da-f]+)|((?i)\\$[a-z_]\\w*)|((?i)\\d\\d*|\\b0\\b)|((?i)0[0-7]+)|((?i)(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?i)((\\d+|((\\d*\\.\\d+)|(\\d+\\.\\d*)))[eE][+-]?\\d+))/',
- 1 => '/((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)\\/\\*)|((?i)")|((?i)`)|((?mi)\\<\\<\\<[\\x20\\x09]*(\\w+)$)|((?i)\')|((?i)(#|\\/\\/))|((?i)[a-z_]\\w*)|((?i)\\((array|int|integer|string|bool|boolean|object|float|double)\\))|((?i)\\?\\>)|((?i)0[xX][\\da-f]+)|((?i)\\$[a-z_]\\w*)|((?i)\\d\\d*|\\b0\\b)|((?i)0[0-7]+)|((?i)(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?i)((\\d+|((\\d*\\.\\d+)|(\\d+\\.\\d*)))[eE][+-]?\\d+))/',
- 2 => '/((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)\\/\\*)|((?i)")|((?i)`)|((?mi)\\<\\<\\<[\\x20\\x09]*(\\w+)$)|((?i)\')|((?i)(#|\\/\\/))|((?i)[a-z_]\\w*)|((?i)\\((array|int|integer|string|bool|boolean|object|float|double)\\))|((?i)0[xX][\\da-f]+)|((?i)\\$[a-z_]\\w*)|((?i)\\d\\d*|\\b0\\b)|((?i)0[0-7]+)|((?i)(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?i)((\\d+|((\\d*\\.\\d+)|(\\d+\\.\\d*)))[eE][+-]?\\d+))/',
- 3 => '/((?i)\\{)|((?i)\\()|((?i)\\[)|((?i)\\/\\*)|((?i)")|((?i)`)|((?mi)\\<\\<\\<[\\x20\\x09]*(\\w+)$)|((?i)\')|((?i)(#|\\/\\/))|((?i)[a-z_]\\w*)|((?i)\\((array|int|integer|string|bool|boolean|object|float|double)\\))|((?i)0[xX][\\da-f]+)|((?i)\\$[a-z_]\\w*)|((?i)\\d\\d*|\\b0\\b)|((?i)0[0-7]+)|((?i)(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?i)((\\d+|((\\d*\\.\\d+)|(\\d+\\.\\d*)))[eE][+-]?\\d+))/',
- 4 => '/((?i)\\s@\\w+\\s)|((?i)((https?|ftp):\\/\\/[\\w\\?\\.\\-\\&=\\/%+]+)|(^|[\\s,!?])www\\.\\w+\\.\\w+[\\w\\?\\.\\&=\\/%+]*)|((?i)\\w+[\\.\\w\\-]+@(\\w+[\\.\\w\\-])+)|((?i)\\bnote:)|((?i)\\$\\w+\\s*:.*\\$)/',
- 5 => '/((?i)\\\\[\\\\"\'`tnr\\$\\{])|((?i)\\{\\$[a-z_].*\\})|((?i)\\$[a-z_]\\w*)/',
- 6 => '/((?i)\\\\\\\\|\\\\"|\\\\\'|\\\\`)|((?i)\\{\\$[a-z_].*\\})|((?i)\\$[a-z_]\\w*)/',
- 7 => '/((?i)\\\\[\\\\"\'`tnr\\$\\{])|((?i)\\{\\$[a-z_].*\\})|((?i)\\$[a-z_]\\w*)/',
- 8 => '/((?i)\\\\\\\\|\\\\"|\\\\\'|\\\\`)/',
- 9 => '/((?i)\\s@\\w+\\s)|((?i)((https?|ftp):\\/\\/[\\w\\?\\.\\-\\&=\\/%+]+)|(^|[\\s,!?])www\\.\\w+\\.\\w+[\\w\\?\\.\\&=\\/%+]*)|((?i)\\w+[\\.\\w\\-]+@(\\w+[\\.\\w\\-])+)|((?i)\\bnote:)|((?i)\\$\\w+\\s*:.*\\$)/',
- 10 => '//',
- );
- $this->_counts = array (
- -1 =>
- array (
- 0 => 1,
- ),
- 0 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 1,
- 7 => 0,
- 8 => 1,
- 9 => 0,
- 10 => 1,
- 11 => 0,
- 12 => 0,
- 13 => 0,
- 14 => 0,
- 15 => 2,
- 16 => 5,
- ),
- 1 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 1,
- 7 => 0,
- 8 => 1,
- 9 => 0,
- 10 => 1,
- 11 => 0,
- 12 => 0,
- 13 => 0,
- 14 => 0,
- 15 => 0,
- 16 => 2,
- 17 => 5,
- ),
- 2 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 1,
- 7 => 0,
- 8 => 1,
- 9 => 0,
- 10 => 1,
- 11 => 0,
- 12 => 0,
- 13 => 0,
- 14 => 0,
- 15 => 2,
- 16 => 5,
- ),
- 3 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 1,
- 7 => 0,
- 8 => 1,
- 9 => 0,
- 10 => 1,
- 11 => 0,
- 12 => 0,
- 13 => 0,
- 14 => 0,
- 15 => 2,
- 16 => 5,
- ),
- 4 =>
- array (
- 0 => 0,
- 1 => 3,
- 2 => 1,
- 3 => 0,
- 4 => 0,
- ),
- 5 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- ),
- 6 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- ),
- 7 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- ),
- 8 =>
- array (
- 0 => 0,
- ),
- 9 =>
- array (
- 0 => 0,
- 1 => 3,
- 2 => 1,
- 3 => 0,
- 4 => 0,
- ),
- 10 =>
- array (
- ),
- );
- $this->_delim = array (
- -1 =>
- array (
- 0 => 'inlinetags',
- ),
- 0 =>
- array (
- 0 => 'brackets',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'comment',
- 4 => 'quotes',
- 5 => 'quotes',
- 6 => 'quotes',
- 7 => 'quotes',
- 8 => 'comment',
- 9 => '',
- 10 => '',
- 11 => '',
- 12 => '',
- 13 => '',
- 14 => '',
- 15 => '',
- 16 => '',
- ),
- 1 =>
- array (
- 0 => 'brackets',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'comment',
- 4 => 'quotes',
- 5 => 'quotes',
- 6 => 'quotes',
- 7 => 'quotes',
- 8 => 'comment',
- 9 => '',
- 10 => '',
- 11 => 'inlinetags',
- 12 => '',
- 13 => '',
- 14 => '',
- 15 => '',
- 16 => '',
- 17 => '',
- ),
- 2 =>
- array (
- 0 => 'brackets',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'comment',
- 4 => 'quotes',
- 5 => 'quotes',
- 6 => 'quotes',
- 7 => 'quotes',
- 8 => 'comment',
- 9 => '',
- 10 => '',
- 11 => '',
- 12 => '',
- 13 => '',
- 14 => '',
- 15 => '',
- 16 => '',
- ),
- 3 =>
- array (
- 0 => 'brackets',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'comment',
- 4 => 'quotes',
- 5 => 'quotes',
- 6 => 'quotes',
- 7 => 'quotes',
- 8 => 'comment',
- 9 => '',
- 10 => '',
- 11 => '',
- 12 => '',
- 13 => '',
- 14 => '',
- 15 => '',
- 16 => '',
- ),
- 4 =>
- array (
- 0 => '',
- 1 => '',
- 2 => '',
- 3 => '',
- 4 => '',
- ),
- 5 =>
- array (
- 0 => '',
- 1 => '',
- 2 => '',
- ),
- 6 =>
- array (
- 0 => '',
- 1 => '',
- 2 => '',
- ),
- 7 =>
- array (
- 0 => '',
- 1 => '',
- 2 => '',
- ),
- 8 =>
- array (
- 0 => '',
- ),
- 9 =>
- array (
- 0 => '',
- 1 => '',
- 2 => '',
- 3 => '',
- 4 => '',
- ),
- 10 =>
- array (
- ),
- );
- $this->_inner = array (
- -1 =>
- array (
- 0 => 'code',
- ),
- 0 =>
- array (
- 0 => 'code',
- 1 => 'code',
- 2 => 'code',
- 3 => 'comment',
- 4 => 'string',
- 5 => 'string',
- 6 => 'string',
- 7 => 'string',
- 8 => 'comment',
- 9 => 'identifier',
- 10 => 'reserved',
- 11 => 'number',
- 12 => 'var',
- 13 => 'number',
- 14 => 'number',
- 15 => 'number',
- 16 => 'number',
- ),
- 1 =>
- array (
- 0 => 'code',
- 1 => 'code',
- 2 => 'code',
- 3 => 'comment',
- 4 => 'string',
- 5 => 'string',
- 6 => 'string',
- 7 => 'string',
- 8 => 'comment',
- 9 => 'identifier',
- 10 => 'reserved',
- 11 => 'default',
- 12 => 'number',
- 13 => 'var',
- 14 => 'number',
- 15 => 'number',
- 16 => 'number',
- 17 => 'number',
- ),
- 2 =>
- array (
- 0 => 'code',
- 1 => 'code',
- 2 => 'code',
- 3 => 'comment',
- 4 => 'string',
- 5 => 'string',
- 6 => 'string',
- 7 => 'string',
- 8 => 'comment',
- 9 => 'identifier',
- 10 => 'reserved',
- 11 => 'number',
- 12 => 'var',
- 13 => 'number',
- 14 => 'number',
- 15 => 'number',
- 16 => 'number',
- ),
- 3 =>
- array (
- 0 => 'code',
- 1 => 'code',
- 2 => 'code',
- 3 => 'comment',
- 4 => 'string',
- 5 => 'string',
- 6 => 'string',
- 7 => 'string',
- 8 => 'comment',
- 9 => 'identifier',
- 10 => 'reserved',
- 11 => 'number',
- 12 => 'var',
- 13 => 'number',
- 14 => 'number',
- 15 => 'number',
- 16 => 'number',
- ),
- 4 =>
- array (
- 0 => 'inlinedoc',
- 1 => 'url',
- 2 => 'url',
- 3 => 'inlinedoc',
- 4 => 'inlinedoc',
- ),
- 5 =>
- array (
- 0 => 'special',
- 1 => 'var',
- 2 => 'var',
- ),
- 6 =>
- array (
- 0 => 'special',
- 1 => 'var',
- 2 => 'var',
- ),
- 7 =>
- array (
- 0 => 'special',
- 1 => 'var',
- 2 => 'var',
- ),
- 8 =>
- array (
- 0 => 'special',
- ),
- 9 =>
- array (
- 0 => 'inlinedoc',
- 1 => 'url',
- 2 => 'url',
- 3 => 'inlinedoc',
- 4 => 'inlinedoc',
- ),
- 10 =>
- array (
- ),
- );
- $this->_end = array (
- 0 => '/(?i)\\?\\>/',
- 1 => '/(?i)\\}/',
- 2 => '/(?i)\\)/',
- 3 => '/(?i)\\]/',
- 4 => '/(?i)\\*\\//',
- 5 => '/(?i)"/',
- 6 => '/(?i)`/',
- 7 => '/(?mi)^%1%;?$/',
- 8 => '/(?i)\'/',
- 9 => '/(?mi)$|(?=\\?\\>)/',
- 10 => '/(?i)\\<\\?(php|=)?/',
- );
- $this->_states = array (
- -1 =>
- array (
- 0 => 0,
- ),
- 0 =>
- array (
- 0 => 1,
- 1 => 2,
- 2 => 3,
- 3 => 4,
- 4 => 5,
- 5 => 6,
- 6 => 7,
- 7 => 8,
- 8 => 9,
- 9 => -1,
- 10 => -1,
- 11 => -1,
- 12 => -1,
- 13 => -1,
- 14 => -1,
- 15 => -1,
- 16 => -1,
- ),
- 1 =>
- array (
- 0 => 1,
- 1 => 2,
- 2 => 3,
- 3 => 4,
- 4 => 5,
- 5 => 6,
- 6 => 7,
- 7 => 8,
- 8 => 9,
- 9 => -1,
- 10 => -1,
- 11 => 10,
- 12 => -1,
- 13 => -1,
- 14 => -1,
- 15 => -1,
- 16 => -1,
- 17 => -1,
- ),
- 2 =>
- array (
- 0 => 1,
- 1 => 2,
- 2 => 3,
- 3 => 4,
- 4 => 5,
- 5 => 6,
- 6 => 7,
- 7 => 8,
- 8 => 9,
- 9 => -1,
- 10 => -1,
- 11 => -1,
- 12 => -1,
- 13 => -1,
- 14 => -1,
- 15 => -1,
- 16 => -1,
- ),
- 3 =>
- array (
- 0 => 1,
- 1 => 2,
- 2 => 3,
- 3 => 4,
- 4 => 5,
- 5 => 6,
- 6 => 7,
- 7 => 8,
- 8 => 9,
- 9 => -1,
- 10 => -1,
- 11 => -1,
- 12 => -1,
- 13 => -1,
- 14 => -1,
- 15 => -1,
- 16 => -1,
- ),
- 4 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- ),
- 5 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- ),
- 6 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- ),
- 7 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- ),
- 8 =>
- array (
- 0 => -1,
- ),
- 9 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- ),
- 10 =>
- array (
- ),
- );
- $this->_keywords = array (
- -1 =>
- array (
- 0 => -1,
- ),
- 0 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 => -1,
- 8 => -1,
- 9 =>
- array (
- 'constants' => '/^(DIRECTORY_SEPARATOR|PATH_SEPARATOR)$/',
- 'reserved' => '/^((?i)echo|foreach|else|if|elseif|for|as|while|break|continue|class|const|declare|switch|case|endfor|endswitch|endforeach|endif|array|default|do|enddeclare|eval|exit|die|extends|function|global|include|include_once|require|require_once|isset|empty|list|new|static|unset|var|return|try|catch|final|throw|public|private|protected|abstract|interface|implements|define|__file__|__line__|__class__|__method__|__function__|null|true|false|and|or|xor)$/',
- ),
- 10 =>
- array (
- ),
- 11 =>
- array (
- ),
- 12 =>
- array (
- ),
- 13 =>
- array (
- ),
- 14 =>
- array (
- ),
- 15 =>
- array (
- ),
- 16 =>
- array (
- ),
- ),
- 1 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 => -1,
- 8 => -1,
- 9 =>
- array (
- 'constants' => '/^(DIRECTORY_SEPARATOR|PATH_SEPARATOR)$/',
- 'reserved' => '/^((?i)echo|foreach|else|if|elseif|for|as|while|break|continue|class|const|declare|switch|case|endfor|endswitch|endforeach|endif|array|default|do|enddeclare|eval|exit|die|extends|function|global|include|include_once|require|require_once|isset|empty|list|new|static|unset|var|return|try|catch|final|throw|public|private|protected|abstract|interface|implements|define|__file__|__line__|__class__|__method__|__function__|null|true|false|and|or|xor)$/',
- ),
- 10 =>
- array (
- ),
- 11 => -1,
- 12 =>
- array (
- ),
- 13 =>
- array (
- ),
- 14 =>
- array (
- ),
- 15 =>
- array (
- ),
- 16 =>
- array (
- ),
- 17 =>
- array (
- ),
- ),
- 2 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 => -1,
- 8 => -1,
- 9 =>
- array (
- 'constants' => '/^(DIRECTORY_SEPARATOR|PATH_SEPARATOR)$/',
- 'reserved' => '/^((?i)echo|foreach|else|if|elseif|for|as|while|break|continue|class|const|declare|switch|case|endfor|endswitch|endforeach|endif|array|default|do|enddeclare|eval|exit|die|extends|function|global|include|include_once|require|require_once|isset|empty|list|new|static|unset|var|return|try|catch|final|throw|public|private|protected|abstract|interface|implements|define|__file__|__line__|__class__|__method__|__function__|null|true|false|and|or|xor)$/',
- ),
- 10 =>
- array (
- ),
- 11 =>
- array (
- ),
- 12 =>
- array (
- ),
- 13 =>
- array (
- ),
- 14 =>
- array (
- ),
- 15 =>
- array (
- ),
- 16 =>
- array (
- ),
- ),
- 3 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 => -1,
- 8 => -1,
- 9 =>
- array (
- 'constants' => '/^(DIRECTORY_SEPARATOR|PATH_SEPARATOR)$/',
- 'reserved' => '/^((?i)echo|foreach|else|if|elseif|for|as|while|break|continue|class|const|declare|switch|case|endfor|endswitch|endforeach|endif|array|default|do|enddeclare|eval|exit|die|extends|function|global|include|include_once|require|require_once|isset|empty|list|new|static|unset|var|return|try|catch|final|throw|public|private|protected|abstract|interface|implements|define|__file__|__line__|__class__|__method__|__function__|null|true|false|and|or|xor)$/',
- ),
- 10 =>
- array (
- ),
- 11 =>
- array (
- ),
- 12 =>
- array (
- ),
- 13 =>
- array (
- ),
- 14 =>
- array (
- ),
- 15 =>
- array (
- ),
- 16 =>
- array (
- ),
- ),
- 4 =>
- array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- 3 =>
- array (
- ),
- 4 =>
- array (
- ),
- ),
- 5 =>
- array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- ),
- 6 =>
- array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- ),
- 7 =>
- array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- ),
- 8 =>
- array (
- 0 =>
- array (
- ),
- ),
- 9 =>
- array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- 3 =>
- array (
- ),
- 4 =>
- array (
- ),
- ),
- 10 =>
- array (
- ),
- );
- $this->_parts = array (
- 0 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- 10 => NULL,
- 11 => NULL,
- 12 => NULL,
- 13 => NULL,
- 14 => NULL,
- 15 => NULL,
- 16 => NULL,
- ),
- 1 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- 10 => NULL,
- 11 => NULL,
- 12 => NULL,
- 13 => NULL,
- 14 => NULL,
- 15 => NULL,
- 16 => NULL,
- 17 => NULL,
- ),
- 2 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- 10 => NULL,
- 11 => NULL,
- 12 => NULL,
- 13 => NULL,
- 14 => NULL,
- 15 => NULL,
- 16 => NULL,
- ),
- 3 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- 10 => NULL,
- 11 => NULL,
- 12 => NULL,
- 13 => NULL,
- 14 => NULL,
- 15 => NULL,
- 16 => NULL,
- ),
- 4 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- ),
- 5 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- ),
- 6 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- ),
- 7 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- ),
- 8 =>
- array (
- 0 => NULL,
- ),
- 9 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- ),
- 10 =>
- array (
- ),
- );
- $this->_subst = array (
- -1 =>
- array (
- 0 => false,
- ),
- 0 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => true,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- 14 => false,
- 15 => false,
- 16 => false,
- ),
- 1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => true,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- 14 => false,
- 15 => false,
- 16 => false,
- 17 => false,
- ),
- 2 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => true,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- 14 => false,
- 15 => false,
- 16 => false,
- ),
- 3 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => true,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- 14 => false,
- 15 => false,
- 16 => false,
- ),
- 4 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- ),
- 5 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- ),
- 6 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- ),
- 7 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- ),
- 8 =>
- array (
- 0 => false,
- ),
- 9 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- ),
- 10 =>
- array (
- ),
- );
- $this->_conditions = array (
- );
- $this->_kwmap = array (
- 'constants' => 'reserved',
- 'reserved' => 'reserved',
- );
- $this->_defClass = 'code';
- $this->_checkDefines();
- }
-
-} \ No newline at end of file
diff --git a/library/Text_Highlighter/Text/Highlighter/PYTHON.php b/library/Text_Highlighter/Text/Highlighter/PYTHON.php
deleted file mode 100644
index ed4f59dde..000000000
--- a/library/Text_Highlighter/Text/Highlighter/PYTHON.php
+++ /dev/null
@@ -1,647 +0,0 @@
-<?php
-/**
- * Auto-generated class. PYTHON syntax highlighting
- *
- * PHP version 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @link http://pear.php.net/package/Text_Highlighter
- * @category Text
- * @package Text_Highlighter
- * @version generated from: : python.xml,v 1.1 2007/06/03 02:35:28 ssttoo Exp
- * @author Andrey Demenev <demenev@gmail.com>
- *
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter.php';
-
-/**
- * Auto-generated class. PYTHON syntax highlighting
- *
- * @author Andrey Demenev <demenev@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: @package_version@
- * @link http://pear.php.net/package/Text_Highlighter
- */
-class Text_Highlighter_PYTHON extends Text_Highlighter
-{
- var $_language = 'python';
-
- /**
- * PHP4 Compatible Constructor
- *
- * @param array $options
- * @access public
- */
- function Text_Highlighter_PYTHON($options=array())
- {
- $this->__construct($options);
- }
-
-
- /**
- * Constructor
- *
- * @param array $options
- * @access public
- */
- function __construct($options=array())
- {
-
- $this->_options = $options;
- $this->_regs = array (
- -1 => '/((?i)\'\'\')|((?i)""")|((?i)")|((?i)\')|((?i)\\()|((?i)\\[)|((?i)[a-z_]\\w*(?=\\s*\\())|((?i)[a-z_]\\w*)|((?i)((\\d+|((\\d*\\.\\d+)|(\\d+\\.\\d*)))[eE][+-]?\\d+))|((?i)((\\d*\\.\\d+)|(\\d+\\.\\d*)|(\\d+))j)|((?i)(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?i)\\d+l?|\\b0l?\\b)|((?i)0[xX][\\da-f]+l?)|((?i)0[0-7]+l?)|((?i)#.+)/',
- 0 => '/((?i)\\\\.)/',
- 1 => '/((?i)\\\\.)/',
- 2 => '/((?i)\\\\.)/',
- 3 => '/((?i)\\\\.)/',
- 4 => '/((?i)\'\'\')|((?i)""")|((?i)")|((?i)\')|((?i)\\()|((?i)\\[)|((?i)[a-z_]\\w*(?=\\s*\\())|((?i)[a-z_]\\w*)|((?i)((\\d+|((\\d*\\.\\d+)|(\\d+\\.\\d*)))[eE][+-]?\\d+))|((?i)((\\d*\\.\\d+)|(\\d+\\.\\d*)|(\\d+))j)|((?i)(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?i)\\d+l?|\\b0l?\\b)|((?i)0[xX][\\da-f]+l?)|((?i)0[0-7]+l?)|((?i)#.+)/',
- 5 => '/((?i)\'\'\')|((?i)""")|((?i)")|((?i)\')|((?i)\\()|((?i)\\[)|((?i)[a-z_]\\w*(?=\\s*\\())|((?i)[a-z_]\\w*)|((?i)((\\d+|((\\d*\\.\\d+)|(\\d+\\.\\d*)))[eE][+-]?\\d+))|((?i)((\\d*\\.\\d+)|(\\d+\\.\\d*)|(\\d+))j)|((?i)(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?i)\\d+l?|\\b0l?\\b)|((?i)0[xX][\\da-f]+l?)|((?i)0[0-7]+l?)|((?i)#.+)/',
- );
- $this->_counts = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 5,
- 9 => 4,
- 10 => 2,
- 11 => 0,
- 12 => 0,
- 13 => 0,
- 14 => 0,
- ),
- 0 =>
- array (
- 0 => 0,
- ),
- 1 =>
- array (
- 0 => 0,
- ),
- 2 =>
- array (
- 0 => 0,
- ),
- 3 =>
- array (
- 0 => 0,
- ),
- 4 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 5,
- 9 => 4,
- 10 => 2,
- 11 => 0,
- 12 => 0,
- 13 => 0,
- 14 => 0,
- ),
- 5 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 0,
- 8 => 5,
- 9 => 4,
- 10 => 2,
- 11 => 0,
- 12 => 0,
- 13 => 0,
- 14 => 0,
- ),
- );
- $this->_delim = array (
- -1 =>
- array (
- 0 => 'quotes',
- 1 => 'quotes',
- 2 => 'quotes',
- 3 => 'quotes',
- 4 => 'brackets',
- 5 => 'brackets',
- 6 => '',
- 7 => '',
- 8 => '',
- 9 => '',
- 10 => '',
- 11 => '',
- 12 => '',
- 13 => '',
- 14 => '',
- ),
- 0 =>
- array (
- 0 => '',
- ),
- 1 =>
- array (
- 0 => '',
- ),
- 2 =>
- array (
- 0 => '',
- ),
- 3 =>
- array (
- 0 => '',
- ),
- 4 =>
- array (
- 0 => 'quotes',
- 1 => 'quotes',
- 2 => 'quotes',
- 3 => 'quotes',
- 4 => 'brackets',
- 5 => 'brackets',
- 6 => '',
- 7 => '',
- 8 => '',
- 9 => '',
- 10 => '',
- 11 => '',
- 12 => '',
- 13 => '',
- 14 => '',
- ),
- 5 =>
- array (
- 0 => 'quotes',
- 1 => 'quotes',
- 2 => 'quotes',
- 3 => 'quotes',
- 4 => 'brackets',
- 5 => 'brackets',
- 6 => '',
- 7 => '',
- 8 => '',
- 9 => '',
- 10 => '',
- 11 => '',
- 12 => '',
- 13 => '',
- 14 => '',
- ),
- );
- $this->_inner = array (
- -1 =>
- array (
- 0 => 'string',
- 1 => 'string',
- 2 => 'string',
- 3 => 'string',
- 4 => 'code',
- 5 => 'code',
- 6 => 'identifier',
- 7 => 'identifier',
- 8 => 'number',
- 9 => 'number',
- 10 => 'number',
- 11 => 'number',
- 12 => 'number',
- 13 => 'number',
- 14 => 'comment',
- ),
- 0 =>
- array (
- 0 => 'special',
- ),
- 1 =>
- array (
- 0 => 'special',
- ),
- 2 =>
- array (
- 0 => 'special',
- ),
- 3 =>
- array (
- 0 => 'special',
- ),
- 4 =>
- array (
- 0 => 'string',
- 1 => 'string',
- 2 => 'string',
- 3 => 'string',
- 4 => 'code',
- 5 => 'code',
- 6 => 'identifier',
- 7 => 'identifier',
- 8 => 'number',
- 9 => 'number',
- 10 => 'number',
- 11 => 'number',
- 12 => 'number',
- 13 => 'number',
- 14 => 'comment',
- ),
- 5 =>
- array (
- 0 => 'string',
- 1 => 'string',
- 2 => 'string',
- 3 => 'string',
- 4 => 'code',
- 5 => 'code',
- 6 => 'identifier',
- 7 => 'identifier',
- 8 => 'number',
- 9 => 'number',
- 10 => 'number',
- 11 => 'number',
- 12 => 'number',
- 13 => 'number',
- 14 => 'comment',
- ),
- );
- $this->_end = array (
- 0 => '/(?i)\'\'\'/',
- 1 => '/(?i)"""/',
- 2 => '/(?i)"/',
- 3 => '/(?i)\'/',
- 4 => '/(?i)\\)/',
- 5 => '/(?i)\\]/',
- );
- $this->_states = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => 4,
- 5 => 5,
- 6 => -1,
- 7 => -1,
- 8 => -1,
- 9 => -1,
- 10 => -1,
- 11 => -1,
- 12 => -1,
- 13 => -1,
- 14 => -1,
- ),
- 0 =>
- array (
- 0 => -1,
- ),
- 1 =>
- array (
- 0 => -1,
- ),
- 2 =>
- array (
- 0 => -1,
- ),
- 3 =>
- array (
- 0 => -1,
- ),
- 4 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => 4,
- 5 => 5,
- 6 => -1,
- 7 => -1,
- 8 => -1,
- 9 => -1,
- 10 => -1,
- 11 => -1,
- 12 => -1,
- 13 => -1,
- 14 => -1,
- ),
- 5 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => 4,
- 5 => 5,
- 6 => -1,
- 7 => -1,
- 8 => -1,
- 9 => -1,
- 10 => -1,
- 11 => -1,
- 12 => -1,
- 13 => -1,
- 14 => -1,
- ),
- );
- $this->_keywords = array (
- -1 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 => -1,
- 6 =>
- array (
- 'builtin' => '/^(__import__|abs|apply|basestring|bool|buffer|callable|chr|classmethod|cmp|coerce|compile|complex|delattr|dict|dir|divmod|enumerate|eval|execfile|file|filter|float|getattr|globals|hasattr|hash|help|hex|id|input|int|intern|isinstance|issubclass|iter|len|list|locals|long|map|max|min|object|oct|open|ord|pow|property|range|raw_input|reduce|reload|repr|round|setattr|slice|staticmethod|sum|super|str|tuple|type|unichr|unicode|vars|xrange|zip)$/',
- ),
- 7 =>
- array (
- 'reserved' => '/^(and|del|for|is|raise|assert|elif|from|lambda|return|break|else|global|not|try|class|except|if|or|while|continue|exec|import|pass|yield|def|finally|in|print|False|True|None|NotImplemented|Ellipsis|Exception|SystemExit|StopIteration|StandardError|KeyboardInterrupt|ImportError|EnvironmentError|IOError|OSError|WindowsError|EOFError|RuntimeError|NotImplementedError|NameError|UnboundLocalError|AttributeError|SyntaxError|IndentationError|TabError|TypeError|AssertionError|LookupError|IndexError|KeyError|ArithmeticError|OverflowError|ZeroDivisionError|FloatingPointError|ValueError|UnicodeError|UnicodeEncodeError|UnicodeDecodeError|UnicodeTranslateError|ReferenceError|SystemError|MemoryError|Warning|UserWarning|DeprecationWarning|PendingDeprecationWarning|SyntaxWarning|OverflowWarning|RuntimeWarning|FutureWarning)$/',
- ),
- 8 =>
- array (
- ),
- 9 =>
- array (
- ),
- 10 =>
- array (
- ),
- 11 =>
- array (
- ),
- 12 =>
- array (
- ),
- 13 =>
- array (
- ),
- 14 =>
- array (
- ),
- ),
- 0 =>
- array (
- 0 =>
- array (
- ),
- ),
- 1 =>
- array (
- 0 =>
- array (
- ),
- ),
- 2 =>
- array (
- 0 =>
- array (
- ),
- ),
- 3 =>
- array (
- 0 =>
- array (
- ),
- ),
- 4 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 => -1,
- 6 =>
- array (
- 'builtin' => '/^(__import__|abs|apply|basestring|bool|buffer|callable|chr|classmethod|cmp|coerce|compile|complex|delattr|dict|dir|divmod|enumerate|eval|execfile|file|filter|float|getattr|globals|hasattr|hash|help|hex|id|input|int|intern|isinstance|issubclass|iter|len|list|locals|long|map|max|min|object|oct|open|ord|pow|property|range|raw_input|reduce|reload|repr|round|setattr|slice|staticmethod|sum|super|str|tuple|type|unichr|unicode|vars|xrange|zip)$/',
- ),
- 7 =>
- array (
- 'reserved' => '/^(and|del|for|is|raise|assert|elif|from|lambda|return|break|else|global|not|try|class|except|if|or|while|continue|exec|import|pass|yield|def|finally|in|print|False|True|None|NotImplemented|Ellipsis|Exception|SystemExit|StopIteration|StandardError|KeyboardInterrupt|ImportError|EnvironmentError|IOError|OSError|WindowsError|EOFError|RuntimeError|NotImplementedError|NameError|UnboundLocalError|AttributeError|SyntaxError|IndentationError|TabError|TypeError|AssertionError|LookupError|IndexError|KeyError|ArithmeticError|OverflowError|ZeroDivisionError|FloatingPointError|ValueError|UnicodeError|UnicodeEncodeError|UnicodeDecodeError|UnicodeTranslateError|ReferenceError|SystemError|MemoryError|Warning|UserWarning|DeprecationWarning|PendingDeprecationWarning|SyntaxWarning|OverflowWarning|RuntimeWarning|FutureWarning)$/',
- ),
- 8 =>
- array (
- ),
- 9 =>
- array (
- ),
- 10 =>
- array (
- ),
- 11 =>
- array (
- ),
- 12 =>
- array (
- ),
- 13 =>
- array (
- ),
- 14 =>
- array (
- ),
- ),
- 5 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 => -1,
- 6 =>
- array (
- 'builtin' => '/^(__import__|abs|apply|basestring|bool|buffer|callable|chr|classmethod|cmp|coerce|compile|complex|delattr|dict|dir|divmod|enumerate|eval|execfile|file|filter|float|getattr|globals|hasattr|hash|help|hex|id|input|int|intern|isinstance|issubclass|iter|len|list|locals|long|map|max|min|object|oct|open|ord|pow|property|range|raw_input|reduce|reload|repr|round|setattr|slice|staticmethod|sum|super|str|tuple|type|unichr|unicode|vars|xrange|zip)$/',
- ),
- 7 =>
- array (
- 'reserved' => '/^(and|del|for|is|raise|assert|elif|from|lambda|return|break|else|global|not|try|class|except|if|or|while|continue|exec|import|pass|yield|def|finally|in|print|False|True|None|NotImplemented|Ellipsis|Exception|SystemExit|StopIteration|StandardError|KeyboardInterrupt|ImportError|EnvironmentError|IOError|OSError|WindowsError|EOFError|RuntimeError|NotImplementedError|NameError|UnboundLocalError|AttributeError|SyntaxError|IndentationError|TabError|TypeError|AssertionError|LookupError|IndexError|KeyError|ArithmeticError|OverflowError|ZeroDivisionError|FloatingPointError|ValueError|UnicodeError|UnicodeEncodeError|UnicodeDecodeError|UnicodeTranslateError|ReferenceError|SystemError|MemoryError|Warning|UserWarning|DeprecationWarning|PendingDeprecationWarning|SyntaxWarning|OverflowWarning|RuntimeWarning|FutureWarning)$/',
- ),
- 8 =>
- array (
- ),
- 9 =>
- array (
- ),
- 10 =>
- array (
- ),
- 11 =>
- array (
- ),
- 12 =>
- array (
- ),
- 13 =>
- array (
- ),
- 14 =>
- array (
- ),
- ),
- );
- $this->_parts = array (
- 0 =>
- array (
- 0 => NULL,
- ),
- 1 =>
- array (
- 0 => NULL,
- ),
- 2 =>
- array (
- 0 => NULL,
- ),
- 3 =>
- array (
- 0 => NULL,
- ),
- 4 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- 10 => NULL,
- 11 => NULL,
- 12 => NULL,
- 13 => NULL,
- 14 => NULL,
- ),
- 5 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- 10 => NULL,
- 11 => NULL,
- 12 => NULL,
- 13 => NULL,
- 14 => NULL,
- ),
- );
- $this->_subst = array (
- -1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- 14 => false,
- ),
- 0 =>
- array (
- 0 => false,
- ),
- 1 =>
- array (
- 0 => false,
- ),
- 2 =>
- array (
- 0 => false,
- ),
- 3 =>
- array (
- 0 => false,
- ),
- 4 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- 14 => false,
- ),
- 5 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- 14 => false,
- ),
- );
- $this->_conditions = array (
- );
- $this->_kwmap = array (
- 'builtin' => 'builtin',
- 'reserved' => 'reserved',
- );
- $this->_defClass = 'code';
- $this->_checkDefines();
- }
-
-} \ No newline at end of file
diff --git a/library/Text_Highlighter/Text/Highlighter/RUBY.php b/library/Text_Highlighter/Text/Highlighter/RUBY.php
deleted file mode 100644
index ce20e9f2e..000000000
--- a/library/Text_Highlighter/Text/Highlighter/RUBY.php
+++ /dev/null
@@ -1,825 +0,0 @@
-<?php
-/**
- * Auto-generated class. RUBY syntax highlighting
- *
- *
- * FIXME: While this construction : s.split /z/i
- * is valid, regular expression is not recognized as such
- * (/ folowing an identifier or number is not recognized as
- * start of RE), making highlighting improper
- *
- * %q(a (nested) string) does not get highlighted correctly
- *
- *
- * PHP version 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @link http://pear.php.net/package/Text_Highlighter
- * @category Text
- * @package Text_Highlighter
- * @version generated from: : ruby.xml,v 1.1 2007/06/03 02:35:28 ssttoo Exp
- * @author Andrey Demenev <demenev@gmail.com>
- *
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter.php';
-
-/**
- * Auto-generated class. RUBY syntax highlighting
- *
- * @author Andrey Demenev <demenev@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: @package_version@
- * @link http://pear.php.net/package/Text_Highlighter
- */
-class Text_Highlighter_RUBY extends Text_Highlighter
-{
- var $_language = 'ruby';
-
- /**
- * PHP4 Compatible Constructor
- *
- * @param array $options
- * @access public
- */
- function Text_Highlighter_RUBY($options=array())
- {
- $this->__construct($options);
- }
-
-
- /**
- * Constructor
- *
- * @param array $options
- * @access public
- */
- function __construct($options=array())
- {
-
- $this->_options = $options;
- $this->_regs = array (
- -1 => '/((?mi)^__END__$)|((?i)")|((?i)%[Qx]([!"#\\$%&\'+\\-*.\\/:;=?@^`|~{<\\[(]))|((?i)\')|((?i)%[wq]([!"#\\$%&\'+\\-*.\\/:;=?@^`|~{<\\[(]))|((?i)\\$(\\W|\\w+))|((?ii)@@?[_a-z][\\d_a-z]*)|((?i)\\()|((?i)\\[)|((?i)[a-z_]\\w*)|((?i)((\\d+|((\\d*\\.\\d+)|(\\d+\\.\\d*)))[eE][+-]?\\d+))|((?i)(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?i)0[xX][\\da-f]+l?)|((?i)\\d+l?|\\b0l?\\b)|((?i)0[0-7]+l?)|((?mi)^=begin$)|((?i)#)|((?i)\\s*\\/)/',
- 0 => '//',
- 1 => '/((?i)\\\\.)/',
- 2 => '/((?i)\\\\.)/',
- 3 => '/((?i)\\\\.)/',
- 4 => '/((?i)\\\\.)/',
- 5 => '/((?mi)^__END__$)|((?i)")|((?i)%[Qx]([!"#\\$%&\'+\\-*.\\/:;=?@^`|~{<\\[(]))|((?i)\')|((?i)%[wq]([!"#\\$%&\'+\\-*.\\/:;=?@^`|~{<\\[(]))|((?i)\\$(\\W|\\w+))|((?ii)@@?[_a-z][\\d_a-z]*)|((?i)\\()|((?i)\\[)|((?i)[a-z_]\\w*)|((?i)((\\d+|((\\d*\\.\\d+)|(\\d+\\.\\d*)))[eE][+-]?\\d+))|((?i)(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?i)0[xX][\\da-f]+l?)|((?i)\\d+l?|\\b0l?\\b)|((?i)0[0-7]+l?)|((?mi)^=begin$)|((?i)#)|((?i)\\s*\\/)/',
- 6 => '/((?mi)^__END__$)|((?i)")|((?i)%[Qx]([!"#\\$%&\'+\\-*.\\/:;=?@^`|~{<\\[(]))|((?i)\')|((?i)%[wq]([!"#\\$%&\'+\\-*.\\/:;=?@^`|~{<\\[(]))|((?i)\\$(\\W|\\w+))|((?ii)@@?[_a-z][\\d_a-z]*)|((?i)\\()|((?i)\\[)|((?i)[a-z_]\\w*)|((?i)((\\d+|((\\d*\\.\\d+)|(\\d+\\.\\d*)))[eE][+-]?\\d+))|((?i)(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?i)0[xX][\\da-f]+l?)|((?i)\\d+l?|\\b0l?\\b)|((?i)0[0-7]+l?)|((?mi)^=begin$)|((?i)#)|((?i)\\s*\\/)/',
- 7 => '/((?i)\\$\\w+\\s*:.+\\$)/',
- 8 => '/((?i)\\$\\w+\\s*:.+\\$)/',
- 9 => '/((?i)\\\\.)/',
- );
- $this->_counts = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 1,
- 3 => 0,
- 4 => 1,
- 5 => 1,
- 6 => 0,
- 7 => 0,
- 8 => 0,
- 9 => 0,
- 10 => 5,
- 11 => 2,
- 12 => 0,
- 13 => 0,
- 14 => 0,
- 15 => 0,
- 16 => 0,
- 17 => 0,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => 0,
- ),
- 2 =>
- array (
- 0 => 0,
- ),
- 3 =>
- array (
- 0 => 0,
- ),
- 4 =>
- array (
- 0 => 0,
- ),
- 5 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 1,
- 3 => 0,
- 4 => 1,
- 5 => 1,
- 6 => 0,
- 7 => 0,
- 8 => 0,
- 9 => 0,
- 10 => 5,
- 11 => 2,
- 12 => 0,
- 13 => 0,
- 14 => 0,
- 15 => 0,
- 16 => 0,
- 17 => 0,
- ),
- 6 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 1,
- 3 => 0,
- 4 => 1,
- 5 => 1,
- 6 => 0,
- 7 => 0,
- 8 => 0,
- 9 => 0,
- 10 => 5,
- 11 => 2,
- 12 => 0,
- 13 => 0,
- 14 => 0,
- 15 => 0,
- 16 => 0,
- 17 => 0,
- ),
- 7 =>
- array (
- 0 => 0,
- ),
- 8 =>
- array (
- 0 => 0,
- ),
- 9 =>
- array (
- 0 => 0,
- ),
- );
- $this->_delim = array (
- -1 =>
- array (
- 0 => 'reserved',
- 1 => 'quotes',
- 2 => 'quotes',
- 3 => 'quotes',
- 4 => 'quotes',
- 5 => '',
- 6 => '',
- 7 => 'brackets',
- 8 => 'brackets',
- 9 => '',
- 10 => '',
- 11 => '',
- 12 => '',
- 13 => '',
- 14 => '',
- 15 => 'comment',
- 16 => 'comment',
- 17 => 'quotes',
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => '',
- ),
- 2 =>
- array (
- 0 => '',
- ),
- 3 =>
- array (
- 0 => '',
- ),
- 4 =>
- array (
- 0 => '',
- ),
- 5 =>
- array (
- 0 => 'reserved',
- 1 => 'quotes',
- 2 => 'quotes',
- 3 => 'quotes',
- 4 => 'quotes',
- 5 => '',
- 6 => '',
- 7 => 'brackets',
- 8 => 'brackets',
- 9 => '',
- 10 => '',
- 11 => '',
- 12 => '',
- 13 => '',
- 14 => '',
- 15 => 'comment',
- 16 => 'comment',
- 17 => 'quotes',
- ),
- 6 =>
- array (
- 0 => 'reserved',
- 1 => 'quotes',
- 2 => 'quotes',
- 3 => 'quotes',
- 4 => 'quotes',
- 5 => '',
- 6 => '',
- 7 => 'brackets',
- 8 => 'brackets',
- 9 => '',
- 10 => '',
- 11 => '',
- 12 => '',
- 13 => '',
- 14 => '',
- 15 => 'comment',
- 16 => 'comment',
- 17 => 'quotes',
- ),
- 7 =>
- array (
- 0 => '',
- ),
- 8 =>
- array (
- 0 => '',
- ),
- 9 =>
- array (
- 0 => '',
- ),
- );
- $this->_inner = array (
- -1 =>
- array (
- 0 => 'comment',
- 1 => 'string',
- 2 => 'string',
- 3 => 'string',
- 4 => 'string',
- 5 => 'var',
- 6 => 'var',
- 7 => 'code',
- 8 => 'code',
- 9 => 'identifier',
- 10 => 'number',
- 11 => 'number',
- 12 => 'number',
- 13 => 'number',
- 14 => 'number',
- 15 => 'comment',
- 16 => 'comment',
- 17 => 'string',
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => 'special',
- ),
- 2 =>
- array (
- 0 => 'special',
- ),
- 3 =>
- array (
- 0 => 'special',
- ),
- 4 =>
- array (
- 0 => 'special',
- ),
- 5 =>
- array (
- 0 => 'comment',
- 1 => 'string',
- 2 => 'string',
- 3 => 'string',
- 4 => 'string',
- 5 => 'var',
- 6 => 'var',
- 7 => 'code',
- 8 => 'code',
- 9 => 'identifier',
- 10 => 'number',
- 11 => 'number',
- 12 => 'number',
- 13 => 'number',
- 14 => 'number',
- 15 => 'comment',
- 16 => 'comment',
- 17 => 'string',
- ),
- 6 =>
- array (
- 0 => 'comment',
- 1 => 'string',
- 2 => 'string',
- 3 => 'string',
- 4 => 'string',
- 5 => 'var',
- 6 => 'var',
- 7 => 'code',
- 8 => 'code',
- 9 => 'identifier',
- 10 => 'number',
- 11 => 'number',
- 12 => 'number',
- 13 => 'number',
- 14 => 'number',
- 15 => 'comment',
- 16 => 'comment',
- 17 => 'string',
- ),
- 7 =>
- array (
- 0 => 'inlinedoc',
- ),
- 8 =>
- array (
- 0 => 'inlinedoc',
- ),
- 9 =>
- array (
- 0 => 'special',
- ),
- );
- $this->_end = array (
- 0 => '/(?i)$/',
- 1 => '/(?i)"/',
- 2 => '/(?i)%b1%/',
- 3 => '/(?i)\'/',
- 4 => '/(?i)%b1%/',
- 5 => '/(?i)\\)/',
- 6 => '/(?i)\\]/',
- 7 => '/(?mi)^=end$/',
- 8 => '/(?mi)$/',
- 9 => '/(?i)\\/[iomx]*/',
- );
- $this->_states = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => 4,
- 5 => -1,
- 6 => -1,
- 7 => 5,
- 8 => 6,
- 9 => -1,
- 10 => -1,
- 11 => -1,
- 12 => -1,
- 13 => -1,
- 14 => -1,
- 15 => 7,
- 16 => 8,
- 17 => 9,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => -1,
- ),
- 2 =>
- array (
- 0 => -1,
- ),
- 3 =>
- array (
- 0 => -1,
- ),
- 4 =>
- array (
- 0 => -1,
- ),
- 5 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => 4,
- 5 => -1,
- 6 => -1,
- 7 => 5,
- 8 => 6,
- 9 => -1,
- 10 => -1,
- 11 => -1,
- 12 => -1,
- 13 => -1,
- 14 => -1,
- 15 => 7,
- 16 => 8,
- 17 => 9,
- ),
- 6 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => 3,
- 4 => 4,
- 5 => -1,
- 6 => -1,
- 7 => 5,
- 8 => 6,
- 9 => -1,
- 10 => -1,
- 11 => -1,
- 12 => -1,
- 13 => -1,
- 14 => -1,
- 15 => 7,
- 16 => 8,
- 17 => 9,
- ),
- 7 =>
- array (
- 0 => -1,
- ),
- 8 =>
- array (
- 0 => -1,
- ),
- 9 =>
- array (
- 0 => -1,
- ),
- );
- $this->_keywords = array (
- -1 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 =>
- array (
- ),
- 6 =>
- array (
- ),
- 7 => -1,
- 8 => -1,
- 9 =>
- array (
- 'reserved' => '/^(__FILE__|require|and|def|end|in|or|self|unless|__LINE__|begin|defined?|ensure|module|redo|super|until|BEGIN|break|do|false|next|rescue|then|when|END|case|else|for|nil|retry|true|while|alias|module_function|private|public|protected|attr_reader|attr_writer|attr_accessor|class|elsif|if|not|return|undef|yield)$/',
- ),
- 10 =>
- array (
- ),
- 11 =>
- array (
- ),
- 12 =>
- array (
- ),
- 13 =>
- array (
- ),
- 14 =>
- array (
- ),
- 15 => -1,
- 16 => -1,
- 17 => -1,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 =>
- array (
- ),
- ),
- 2 =>
- array (
- 0 =>
- array (
- ),
- ),
- 3 =>
- array (
- 0 =>
- array (
- ),
- ),
- 4 =>
- array (
- 0 =>
- array (
- ),
- ),
- 5 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 =>
- array (
- ),
- 6 =>
- array (
- ),
- 7 => -1,
- 8 => -1,
- 9 =>
- array (
- 'reserved' => '/^(__FILE__|require|and|def|end|in|or|self|unless|__LINE__|begin|defined?|ensure|module|redo|super|until|BEGIN|break|do|false|next|rescue|then|when|END|case|else|for|nil|retry|true|while|alias|module_function|private|public|protected|attr_reader|attr_writer|attr_accessor|class|elsif|if|not|return|undef|yield)$/',
- ),
- 10 =>
- array (
- ),
- 11 =>
- array (
- ),
- 12 =>
- array (
- ),
- 13 =>
- array (
- ),
- 14 =>
- array (
- ),
- 15 => -1,
- 16 => -1,
- 17 => -1,
- ),
- 6 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 => -1,
- 5 =>
- array (
- ),
- 6 =>
- array (
- ),
- 7 => -1,
- 8 => -1,
- 9 =>
- array (
- 'reserved' => '/^(__FILE__|require|and|def|end|in|or|self|unless|__LINE__|begin|defined?|ensure|module|redo|super|until|BEGIN|break|do|false|next|rescue|then|when|END|case|else|for|nil|retry|true|while|alias|module_function|private|public|protected|attr_reader|attr_writer|attr_accessor|class|elsif|if|not|return|undef|yield)$/',
- ),
- 10 =>
- array (
- ),
- 11 =>
- array (
- ),
- 12 =>
- array (
- ),
- 13 =>
- array (
- ),
- 14 =>
- array (
- ),
- 15 => -1,
- 16 => -1,
- 17 => -1,
- ),
- 7 =>
- array (
- 0 =>
- array (
- ),
- ),
- 8 =>
- array (
- 0 =>
- array (
- ),
- ),
- 9 =>
- array (
- 0 =>
- array (
- ),
- ),
- );
- $this->_parts = array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => NULL,
- ),
- 2 =>
- array (
- 0 => NULL,
- ),
- 3 =>
- array (
- 0 => NULL,
- ),
- 4 =>
- array (
- 0 => NULL,
- ),
- 5 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- 10 => NULL,
- 11 => NULL,
- 12 => NULL,
- 13 => NULL,
- 14 => NULL,
- 15 => NULL,
- 16 => NULL,
- 17 => NULL,
- ),
- 6 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- 10 => NULL,
- 11 => NULL,
- 12 => NULL,
- 13 => NULL,
- 14 => NULL,
- 15 => NULL,
- 16 => NULL,
- 17 => NULL,
- ),
- 7 =>
- array (
- 0 => NULL,
- ),
- 8 =>
- array (
- 0 => NULL,
- ),
- 9 =>
- array (
- 0 => NULL,
- ),
- );
- $this->_subst = array (
- -1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => true,
- 3 => false,
- 4 => true,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- 14 => false,
- 15 => false,
- 16 => false,
- 17 => false,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- 0 => false,
- ),
- 2 =>
- array (
- 0 => false,
- ),
- 3 =>
- array (
- 0 => false,
- ),
- 4 =>
- array (
- 0 => false,
- ),
- 5 =>
- array (
- 0 => false,
- 1 => false,
- 2 => true,
- 3 => false,
- 4 => true,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- 14 => false,
- 15 => false,
- 16 => false,
- 17 => false,
- ),
- 6 =>
- array (
- 0 => false,
- 1 => false,
- 2 => true,
- 3 => false,
- 4 => true,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- 14 => false,
- 15 => false,
- 16 => false,
- 17 => false,
- ),
- 7 =>
- array (
- 0 => false,
- ),
- 8 =>
- array (
- 0 => false,
- ),
- 9 =>
- array (
- 0 => false,
- ),
- );
- $this->_conditions = array (
- );
- $this->_kwmap = array (
- 'reserved' => 'reserved',
- );
- $this->_defClass = 'code';
- $this->_checkDefines();
- }
-
-} \ No newline at end of file
diff --git a/library/Text_Highlighter/Text/Highlighter/Renderer.php b/library/Text_Highlighter/Text/Highlighter/Renderer.php
deleted file mode 100644
index cb8993ff8..000000000
--- a/library/Text_Highlighter/Text/Highlighter/Renderer.php
+++ /dev/null
@@ -1,164 +0,0 @@
-<?php
-/* vim: set expandtab tabstop=4 shiftwidth=4 softtabstop=4: */
-/**
- * Abstract base class for Highlighter renderers
- *
- * PHP versions 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @category Text
- * @package Text_Highlighter
- * @author Andrey Demenev <demenev@gmail.com>
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version CVS: $Id$
- * @link http://pear.php.net/package/Text_Highlighter
- */
-
-/**
- * Abstract base class for Highlighter renderers
- *
- * @author Andrey Demenev <demenev@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: @package_version@
- * @link http://pear.php.net/package/Text_Highlighter
- * @abstract
- */
-
-class Text_Highlighter_Renderer
-{
- /**
- * Renderer options
- *
- * @var array
- * @access protected
- */
- var $_options = array();
-
- /**
- * Current language
- *
- * @var string
- * @access protected
- */
- var $_language = '';
-
- /**
- * Constructor
- *
- * @access public
- *
- * @param array $options Rendering options. Renderer-specific.
- */
- function __construct($options = array())
- {
- $this->_options = $options;
- }
-
- /**
- * PHP4 compatable constructor
- *
- * @access public
- *
- * @param array $options Rendering options. Renderer-specific.
- */
- function Text_Highlighter_Renderer($options = array())
- {
- $this->__construct($options);
- }
-
- /**
- * Resets renderer state
- *
- * @access public
- *
- * @param array $options Rendering options. Renderer-specific.
- */
- function reset()
- {
- return;
- }
-
- /**
- * Preprocesses code
- *
- * @access public
- *
- * @param string $str Code to preprocess
- * @return string Preprocessed code
- */
- function preprocess($str)
- {
- return $str;
- }
-
- /**
- * Accepts next token
- *
- * @abstract
- * @access public
- *
- * @param string $class Token class
- * @param string $content Token content
- */
- function acceptToken($class, $content)
- {
- return;
- }
-
- /**
- * Signals that no more tokens are available
- *
- * @access public
- *
- */
- function finalize()
- {
- return;
- }
-
- /**
- * Get generated output
- *
- * @abstract
- * @return mixed Renderer-specific
- * @access public
- *
- */
- function getOutput()
- {
- return;
- }
-
- /**
- * Set current language
- *
- * @abstract
- * @return void
- * @access public
- *
- */
- function setCurrentLanguage($lang)
- {
- $this->_language = $lang;
- }
-
-}
-
-/*
- * Local variables:
- * tab-width: 4
- * c-basic-offset: 4
- * c-hanging-comment-ender-p: nil
- * End:
- */
-
-?>
diff --git a/library/Text_Highlighter/Text/Highlighter/Renderer/Array.php b/library/Text_Highlighter/Text/Highlighter/Renderer/Array.php
deleted file mode 100644
index edf6290f8..000000000
--- a/library/Text_Highlighter/Text/Highlighter/Renderer/Array.php
+++ /dev/null
@@ -1,202 +0,0 @@
-<?php
-/* vim: set expandtab tabstop=4 shiftwidth=4 softtabstop=4: */
-/**
- * Array renderer.
- *
- * Produces an array that contains class names and content pairs.
- * The array can be enumerated or associative. Associative means
- * <code>class =&gt; content</code> pairs.
- * Based on the HTML renderer by Andrey Demenev.
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @category Text
- * @package Text_Highlighter
- * @author Stoyan Stefanov <ssttoo@gmail.com>
- * @copyright 2006 Stoyan Stefanov
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version CVS: $Id$
- * @link http://pear.php.net/package/Text_Highlighter
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter/Renderer.php';
-
-/**
- * Array renderer, based on Andrey Demenev's HTML renderer.
- *
- * In addition to the options supported by the HTML renderer,
- * the following options were also introduced:
- * <ul><li>htmlspecialchars - whether or not htmlspecialchars() will
- * be called on the content, default TRUE</li>
- * <li>enumerated - type of array produced, default FALSE,
- * meaning associative array</li>
- * </ul>
- *
- *
- * @author Stoyan Stefanov <ssttoo@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2006 Stoyan Stefanov
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: 0.5.0
- * @link http://pear.php.net/package/Text_Highlighter
- */
-
-class Text_Highlighter_Renderer_Array extends Text_Highlighter_Renderer
-{
-
- /**#@+
- * @access private
- */
-
- /**
- * Tab size
- *
- * @var integer
- */
- var $_tabsize = 4;
-
- /**
- * Should htmlentities() will be called
- *
- * @var boolean
- */
- var $_htmlspecialchars = true;
-
- /**
- * Enumerated or associative array
- *
- * @var integer
- */
- var $_enumerated = false;
-
- /**
- * Array containing highlighting rules
- *
- * @var array
- */
- var $_output = array();
-
- /**#@-*/
-
- /**
- * Preprocesses code
- *
- * @access public
- *
- * @param string $str Code to preprocess
- * @return string Preprocessed code
- */
- function preprocess($str)
- {
- // normalize whitespace and tabs
- $str = str_replace("\r\n","\n", $str);
- $str = str_replace("\r","\n", $str);
- // some browsers refuse to display empty lines
- $str = preg_replace('~^$~m'," ", $str);
- $str = str_replace("\t",str_repeat(' ', $this->_tabsize), $str);
- return rtrim($str);
- }
-
-
- /**
- * Resets renderer state
- *
- * Descendents of Text_Highlighter call this method from the constructor,
- * passing $options they get as parameter.
- *
- * @access protected
- */
- function reset()
- {
- $this->_output = array();
- $this->_lastClass = 'default';
- if (isset($this->_options['tabsize'])) {
- $this->_tabsize = $this->_options['tabsize'];
- }
- if (isset($this->_options['htmlspecialchars'])) {
- $this->_htmlspecialchars = $this->_options['htmlspecialchars'];
- }
- if (isset($this->_options['enumerated'])) {
- $this->_enumerated = $this->_options['enumerated'];
- }
- }
-
-
-
- /**
- * Accepts next token
- *
- * @abstract
- * @access public
- * @param string $class Token class
- * @param string $content Token content
- */
- function acceptToken($class, $content)
- {
-
- if(! is_array($this->_output)) {
- $this->_output = array();
- }
- $theClass = $this->_getFullClassName($class);
- if ($this->_htmlspecialchars) {
- $content = htmlspecialchars($content);
- }
- if ($this->_enumerated) {
- $this->_output[] = array($class, $content);
- } else {
- $this->_output[][$class] = $content;
- }
- $this->_lastClass = $class;
-
- }
-
-
- /**
- * Given a CSS class name, returns the class name
- * with language name prepended, if necessary
- *
- * @access private
- *
- * @param string $class Token class
- */
- function _getFullClassName($class)
- {
- if (!empty($this->_options['use_language'])) {
- $theClass = $this->_language . '-' . $class;
- } else {
- $theClass = $class;
- }
- return $theClass;
- }
-
- /**
- * Get generated output
- *
- * @abstract
- * @return array Highlighted code as an array
- * @access public
- */
- function getOutput()
- {
- return $this->_output;
- }
-}
-
-/*
- * Local variables:
- * tab-width: 4
- * c-basic-offset: 4
- * c-hanging-comment-ender-p: nil
- * End:
- */
-
-?>
diff --git a/library/Text_Highlighter/Text/Highlighter/Renderer/BB.php b/library/Text_Highlighter/Text/Highlighter/Renderer/BB.php
deleted file mode 100644
index abd77cfd8..000000000
--- a/library/Text_Highlighter/Text/Highlighter/Renderer/BB.php
+++ /dev/null
@@ -1,238 +0,0 @@
-<?php
-/* vim: set expandtab tabstop=4 shiftwidth=4 softtabstop=4: */
-/**
- * BB code renderer.
- *
- * This BB renderer produces BB code, ready to be pasted in bulletin boards and
- * other applications that accept BB code. Based on the HTML renderer by Andrey Demenev.
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @category Text
- * @package Text_Highlighter
- * @author Stoyan Stefanov <ssttoo@gmail.com>
- * @copyright 2005 Stoyan Stefanov
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version CVS: $Id$
- * @link http://pear.php.net/package/Text_Highlighter
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter/Renderer.php';
-
-/**
- * BB code renderer, based on Andrey Demenev's HTML renderer.
- *
- * Elements of $options argument of constructor (each being optional):
- *
- * - 'numbers' - Line numbering TRUE or FALSE
- * - 'tabsize' - Tab size, default is 4
- * - 'bb_tags' - An array containing three BB tags, see below
- * - 'tag_brackets' - An array that conains opening and closing tags, [ and ]
- * - 'colors' - An array with all the colors to be used for highlighting
- *
- * The default BB tags are:
- * - 'color' => 'color'
- * - 'list' => 'list'
- * - 'list_item' => '*'
- *
- * The default colors for the highlighter are:
- * - 'default' => 'Black',
- * - 'code' => 'Gray',
- * - 'brackets' => 'Olive',
- * - 'comment' => 'Orange',
- * - 'mlcomment' => 'Orange',
- * - 'quotes' => 'Darkred',
- * - 'string' => 'Red',
- * - 'identifier' => 'Blue',
- * - 'builtin' => 'Teal',
- * - 'reserved' => 'Green',
- * - 'inlinedoc' => 'Blue',
- * - 'var' => 'Darkblue',
- * - 'url' => 'Blue',
- * - 'special' => 'Navy',
- * - 'number' => 'Maroon',
- * - 'inlinetags' => 'Blue',
- *
- *
- * @author Stoyan Stefanov <ssttoo@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 20045 Stoyan Stefanov
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: 0.5.0
- * @link http://pear.php.net/package/Text_Highlighter
- */
-
-class Text_Highlighter_Renderer_BB extends Text_Highlighter_Renderer_Array
-{
-
- /**#@+
- * @access private
- */
-
- /**
- * Line numbering - will use the specified BB tag for listings
- *
- * @var boolean
- */
- var $_numbers = false;
-
- /**
- * BB tags to be used
- *
- * @var array
- */
- var $_bb_tags = array (
- 'color' => 'color',
- 'list' => 'list',
- 'list_item' => '*',
- 'code' => 'code',
- );
-
- /**
- * BB brackets - [ and ]
- *
- * @var array
- */
- var $_tag_brackets = array ('start' => '[', 'end' => ']');
-
- /**
- * Colors map
- *
- * @var boolean
- */
- var $_colors = array(
- 'default' => 'Black',
- 'code' => 'Gray',
- 'brackets' => 'Olive',
- 'comment' => 'Orange',
- 'mlcomment' => 'Orange',
- 'quotes' => 'Darkred',
- 'string' => 'Red',
- 'identifier' => 'Blue',
- 'builtin' => 'Teal',
- 'reserved' => 'Green',
- 'inlinedoc' => 'Blue',
- 'var' => 'Darkblue',
- 'url' => 'Blue',
- 'special' => 'Navy',
- 'number' => 'Maroon',
- 'inlinetags' => 'Blue',
- );
-
- /**#@-*/
-
- /**
- * Resets renderer state
- *
- * @access protected
- *
- *
- * Descendents of Text_Highlighter call this method from the constructor,
- * passing $options they get as parameter.
- */
- function reset()
- {
- parent::reset();
- if (isset($this->_options['numbers'])) {
- $this->_numbers = $this->_options['numbers'];
- }
- if (isset($this->_options['bb_tags'])) {
- $this->_bb_tags = array_merge($this->_bb_tags, $this->_options['bb_tags']);
- }
- if (isset($this->_options['tag_brackets'])) {
- $this->_tag_brackets = array_merge($this->_tag_brackets, $this->_options['tag_brackets']);
- }
- if (isset($this->_options['colors'])) {
- $this->_colors = array_merge($this->_colors, $this->_options['colors']);
- }
- }
-
-
- /**
- * Signals that no more tokens are available
- *
- * @abstract
- * @access public
- *
- */
- function finalize()
- {
-
- // get parent's output
- parent::finalize();
- $output = parent::getOutput();
-
- $bb_output = '';
-
- $color_start = $this->_tag_brackets['start'] . $this->_bb_tags['color'] . '=%s' . $this->_tag_brackets['end'];
- $color_end = $this->_tag_brackets['start'] . '/' . $this->_bb_tags['color'] . $this->_tag_brackets['end'];
-
- // loop through each class=>content pair
- foreach ($output AS $token) {
-
- if ($this->_enumerated) {
- $class = $token[0];
- $content = $token[1];
- } else {
- $key = key($token);
- $class = $key;
- $content = $token[$key];
- }
-
- $iswhitespace = ctype_space($content);
- if (!$iswhitespace && !empty($this->_colors[$class])) {
- $bb_output .= sprintf($color_start, $this->_colors[$class]);
- $bb_output .= $content;
- $bb_output .= $color_end;
- } else {
- $bb_output .= $content;
- }
- }
-
- if ($this->_numbers) {
-
- $item_tag = $this->_tag_brackets['start'] .
- $this->_bb_tags['list_item'] .
- $this->_tag_brackets['end'];
- $this->_output = $item_tag . str_replace("\n", "\n". $item_tag .' ', $bb_output);
- $this->_output = $this->_tag_brackets['start'] .
- $this->_bb_tags['list'] .
- $this->_tag_brackets['end'] .
- $this->_output .
- $this->_tag_brackets['start'] .
- '/'.
- $this->_bb_tags['list'] .
- $this->_tag_brackets['end']
- ;
- } else {
- $this->_output = $this->_tag_brackets['start'] .
- $this->_bb_tags['code'] .
- $this->_tag_brackets['end'] .
- $bb_output .
- $this->_tag_brackets['start'] .
- '/' .
- $this->_bb_tags['code'] .
- $this->_tag_brackets['end'];
- }
- }
-
-}
-
-/*
- * Local variables:
- * tab-width: 4
- * c-basic-offset: 4
- * c-hanging-comment-ender-p: nil
- * End:
- */
-
-?>
diff --git a/library/Text_Highlighter/Text/Highlighter/Renderer/Console.php b/library/Text_Highlighter/Text/Highlighter/Renderer/Console.php
deleted file mode 100644
index d7b1fba88..000000000
--- a/library/Text_Highlighter/Text/Highlighter/Renderer/Console.php
+++ /dev/null
@@ -1,208 +0,0 @@
-<?php
-/* vim: set expandtab tabstop=4 shiftwidth=4 softtabstop=4: */
-/**
- * Console renderer
- *
- * PHP versions 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @category Text
- * @package Text_Highlighter
- * @author Andrey Demenev <demenev@gmail.com>
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version CVS: $Id$
- * @link http://pear.php.net/package/Text_Highlighter
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter/Renderer.php';
-
-define ('HL_CONSOLE_DEFCOLOR', "\033[0m");
-
-/**
- * Console renderer
- *
- * Suitable for displaying text on color-capable terminals, directly
- * or trough less -r
- *
- * Elements of $options argument of constructor (each being optional):
- *
- * - 'numbers' - whether to add line numbers
- * - 'tabsize' - Tab size
- * - 'colors' - additional colors
- *
- * @author Andrey Demenev <demenev@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: @package_version@
- * @link http://pear.php.net/package/Text_Highlighter
- */
-
-class Text_Highlighter_Renderer_Console extends Text_Highlighter_Renderer
-{
-
- /**#@+
- * @access private
- */
-
- /**
- * class of last outputted text chunk
- *
- * @var string
- */
- var $_lastClass;
-
- /**
- * Line numbering
- *
- * @var boolean
- */
- var $_numbers = false;
-
- /**
- * Tab size
- *
- * @var integer
- */
- var $_tabsize = 4;
-
- /**
- * Highlighted code
- *
- * @var string
- */
- var $_output = '';
-
- /**#@-*/
-
- var $_colors = array();
-
- var $_defColors = array(
- 'default' => "\033[0m",
- 'inlinetags' => "\033[31m",
- 'brackets' => "\033[36m",
- 'quotes' => "\033[34m",
- 'inlinedoc' => "\033[34m",
- 'var' => "\033[1m",
- 'types' => "\033[32m",
- 'number' => "\033[32m",
- 'string' => "\033[31m",
- 'reserved' => "\033[35m",
- 'comment' => "\033[33m",
- 'mlcomment' => "\033[33m",
- );
-
- function preprocess($str)
- {
- // normalize whitespace and tabs
- $str = str_replace("\r\n","\n", $str);
- $str = str_replace("\t",str_repeat(' ', $this->_tabsize), $str);
- return rtrim($str);
- }
-
-
- /**
- * Resets renderer state
- *
- * @access protected
- *
- *
- * Descendents of Text_Highlighter call this method from the constructor,
- * passing $options they get as parameter.
- */
- function reset()
- {
- $this->_lastClass = '';
- if (isset($this->_options['numbers'])) {
- $this->_numbers = (bool)$this->_options['numbers'];
- } else {
- $this->_numbers = false;
- }
- if (isset($this->_options['tabsize'])) {
- $this->_tabsize = $this->_options['tabsize'];
- } else {
- $this->_tabsize = 4;
- }
- if (isset($this->_options['colors'])) {
- $this->_colors = array_merge($this->_defColors, $this->_options['colors']);
- } else {
- $this->_colors = $this->_defColors;
- }
- $this->_output = '';
- }
-
-
-
- /**
- * Accepts next token
- *
- * @access public
- *
- * @param string $class Token class
- * @param string $content Token content
- */
- function acceptToken($class, $content)
- {
- if (isset($this->_colors[$class])) {
- $color = $this->_colors[$class];
- } else {
- $color = $this->_colors['default'];
- }
- if ($this->_lastClass != $class) {
- $this->_output .= $color;
- }
- $content = str_replace("\n", $this->_colors['default'] . "\n" . $color, $content);
- $content .= $this->_colors['default'];
- $this->_output .= $content;
- }
-
- /**
- * Signals that no more tokens are available
- *
- * @access public
- *
- */
- function finalize()
- {
- if ($this->_numbers) {
- $nlines = substr_count($this->_output, "\n") + 1;
- $len = strlen($nlines);
- $i = 1;
- $this->_output = preg_replace('~^~em', '" " . str_pad($i++, $len, " ", STR_PAD_LEFT) . ": "', $this->_output);
- }
- $this->_output .= HL_CONSOLE_DEFCOLOR . "\n";
- }
-
- /**
- * Get generated output
- *
- * @return string Highlighted code
- * @access public
- *
- */
- function getOutput()
- {
- return $this->_output;
- }
-}
-
-/*
- * Local variables:
- * tab-width: 4
- * c-basic-offset: 4
- * c-hanging-comment-ender-p: nil
- * End:
- */
-
-?>
diff --git a/library/Text_Highlighter/Text/Highlighter/Renderer/Html.php b/library/Text_Highlighter/Text/Highlighter/Renderer/Html.php
deleted file mode 100644
index 5d6e56ae1..000000000
--- a/library/Text_Highlighter/Text/Highlighter/Renderer/Html.php
+++ /dev/null
@@ -1,465 +0,0 @@
-<?php
-/* vim: set expandtab tabstop=4 shiftwidth=4 softtabstop=4: */
-/**
- * HTML renderer
- *
- * PHP versions 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @category Text
- * @package Text_Highlighter
- * @author Andrey Demenev <demenev@gmail.com>
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version CVS: $Id$
- * @link http://pear.php.net/package/Text_Highlighter
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter/Renderer.php';
-require_once 'Text/Highlighter/Renderer/Array.php';
-
-// BC trick : only define constants if Text/Highlighter.php
-// is not yet included
-if (!defined('HL_NUMBERS_LI')) {
- /**#@+
- * Constant for use with $options['numbers']
- */
- /**
- * use numbered list, deprecated, use HL_NUMBERS_OL instaed
- * @deprecated
- */
- define ('HL_NUMBERS_LI' , 1);
- /**
- * Use 2-column table with line numbers in left column and code in right column.
- */
- define ('HL_NUMBERS_TABLE' , 2);
- /**#@-*/
-}
-
-
-/**#@+
- * Constant for use with $options['numbers']
- */
-/**
- * Use numbered list
- */
-define ('HL_NUMBERS_OL', 1);
-/**
- * Use non-numbered list
- */
-define ('HL_NUMBERS_UL', 3);
-/**#@-*/
-
-
-/**
- * HTML renderer
- *
- * Elements of $options argument of constructor (each being optional):
- *
- * - 'numbers' - Line numbering style 0 or {@link HL_NUMBERS_TABLE}
- * or {@link HL_NUMBERS_UL} or {@link HL_NUMBERS_OL}
- * - 'numbers_start' - starting number for numbered lines
- * - 'tabsize' - Tab size
- * - 'style_map' - Mapping of keywords to formatting rules using inline styles
- * - 'class_map' - Mapping of keywords to formatting rules using class names
- * - 'doclinks' - array that has keys "url", "target" and "elements", used for
- * generating links to online documentation
- * - 'use_language' - class names will be prefixed with language, like "php-reserved" or "css-code"
- *
- * Example of setting documentation links:
- * $options['doclinks'] = array(
- * 'url' => 'http://php.net/%s',
- * 'target' => '_blank',
- * 'elements' => array('reserved', 'identifier')
- * );
- *
- * Example of setting class names map:
- * $options['class_map'] = array(
- * 'main' => 'my-main',
- * 'table' => 'my-table',
- * 'gutter' => 'my-gutter',
- * 'brackets' => 'my-brackets',
- * 'builtin' => 'my-builtin',
- * 'code' => 'my-code',
- * 'comment' => 'my-comment',
- * 'default' => 'my-default',
- * 'identifier' => 'my-identifier',
- * 'inlinedoc' => 'my-inlinedoc',
- * 'inlinetags' => 'my-inlinetags',
- * 'mlcomment' => 'my-mlcomment',
- * 'number' => 'my-number',
- * 'quotes' => 'my-quotes',
- * 'reserved' => 'my-reserved',
- * 'special' => 'my-special',
- * 'string' => 'my-string',
- * 'url' => 'my-url',
- * 'var' => 'my-var',
- * );
- *
- * Example of setting styles mapping:
- * $options['style_map'] = array(
- * 'main' => 'color: black',
- * 'table' => 'border: 1px solid black',
- * 'gutter' => 'background-color: yellow',
- * 'brackets' => 'color: blue',
- * 'builtin' => 'color: red',
- * 'code' => 'color: green',
- * 'comment' => 'color: orange',
- * // ....
- * );
- *
- *
- * @author Andrey Demenev <demenev@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: @package_version@
- * @link http://pear.php.net/package/Text_Highlighter
- */
-
-class Text_Highlighter_Renderer_Html extends Text_Highlighter_Renderer_Array
-{
-
- /**#@+
- * @access private
- */
-
- /**
- * Line numbering style
- *
- * @var integer
- */
- var $_numbers = 0;
-
- /**
- * For numberered lines - where to start
- *
- * @var integer
- */
- var $_numbers_start = 0;
-
- /**
- * Tab size
- *
- * @var integer
- */
- var $_tabsize = 4;
-
- /**
- * Highlighted code
- *
- * @var string
- */
- var $_output = '';
-
- /**
- * Mapping of keywords to formatting rules using inline styles
- *
- * @var array
- */
- var $_style_map = array();
-
- /**
- * Mapping of keywords to formatting rules using class names
- *
- * @var array
- */
- var $_class_map = array(
- 'main' => 'hl-main',
- 'table' => 'hl-table',
- 'gutter' => 'hl-gutter',
- 'brackets' => 'hl-brackets',
- 'builtin' => 'hl-builtin',
- 'code' => 'hl-code',
- 'comment' => 'hl-comment',
- 'default' => 'hl-default',
- 'identifier' => 'hl-identifier',
- 'inlinedoc' => 'hl-inlinedoc',
- 'inlinetags' => 'hl-inlinetags',
- 'mlcomment' => 'hl-mlcomment',
- 'number' => 'hl-number',
- 'prepro' => 'hl-prepro',
- 'quotes' => 'hl-quotes',
- 'reserved' => 'hl-reserved',
- 'special' => 'hl-special',
- 'string' => 'hl-string',
- 'types' => 'hl-types',
- 'url' => 'hl-url',
- 'var' => 'hl-var',
- );
-
- /**
- * Setup for links to online documentation
- *
- * This is an array with keys:
- * - url, ex. http://php.net/%s
- * - target, ex. _blank, default - no target
- * - elements, default is <code>array('reserved', 'identifier')</code>
- *
- * @var array
- */
- var $_doclinks = array();
-
- /**#@-*/
-
-
- /**
- * Resets renderer state
- *
- * @access protected
- *
- *
- * Descendents of Text_Highlighter call this method from the constructor,
- * passing $options they get as parameter.
- */
- function reset()
- {
- $this->_output = '';
- if (isset($this->_options['numbers'])) {
- $this->_numbers = (int)$this->_options['numbers'];
- if ($this->_numbers != HL_NUMBERS_LI
- && $this->_numbers != HL_NUMBERS_UL
- && $this->_numbers != HL_NUMBERS_OL
- && $this->_numbers != HL_NUMBERS_TABLE
- ) {
- $this->_numbers = 0;
- }
- }
- if (isset($this->_options['tabsize'])) {
- $this->_tabsize = $this->_options['tabsize'];
- }
- if (isset($this->_options['numbers_start'])) {
- $this->_numbers_start = intval($this->_options['numbers_start']);
- }
- if (isset($this->_options['doclinks']) &&
- is_array($this->_options['doclinks']) &&
- !empty($this->_options['doclinks']['url'])
- ) {
-
- $this->_doclinks = $this->_options['doclinks']; // keys: url, target, elements array
-
- if (empty($this->_options['doclinks']['elements'])) {
- $this->_doclinks['elements'] = array('reserved', 'identifier');
- }
- }
- if (isset($this->_options['style_map'])) {
- $this->_style_map = $this->_options['style_map'];
- }
- if (isset($this->_options['class_map'])) {
- $this->_class_map = array_merge($this->_class_map, $this->_options['class_map']);
- }
- $this->_htmlspecialchars = true;
-
- }
-
-
- /**
- * Given a CSS class name, returns the class name
- * with language name prepended, if necessary
- *
- * @access private
- *
- * @param string $class Token class
- */
- function _getFullClassName($class)
- {
- if (!empty($this->_options['use_language'])) {
- $the_class = $this->_language . '-' . $class;
- } else {
- $the_class = $class;
- }
- return $the_class;
- }
-
- /**
- * Signals that no more tokens are available
- *
- * @access public
- */
- function finalize()
- {
-
- // get parent's output
- parent::finalize();
- $output = parent::getOutput();
-
- $html_output = '';
-
- $numbers_li = false;
-
- if (
- $this->_numbers == HL_NUMBERS_LI ||
- $this->_numbers == HL_NUMBERS_UL ||
- $this->_numbers == HL_NUMBERS_OL
- )
- {
- $numbers_li = true;
- }
-
- // loop through each class=>content pair
- foreach ($output AS $token) {
-
- if ($this->_enumerated) {
- $key = false;
- $the_class = $token[0];
- $content = $token[1];
- } else {
- $key = key($token);
- $the_class = $key;
- $content = $token[$key];
- }
-
- $span = $this->_getStyling($the_class);
- $decorated_output = $this->_decorate($content, $key);
-
-
- if ($numbers_li == true) {
- // end span tags before end of li, and re-open on next line
- $lastSpanTag = str_replace("%s</span>", "", $span);
- $span = sprintf($span, $decorated_output);
- $span = str_replace("\n", "</span></li>\n<li>$lastSpanTag&nbsp;", $span);
- $html_output .= $span;
- } else {
- $html_output .= sprintf($span, $decorated_output);
- }
-
-
- }
-
- // format lists
- if (!empty($this->_numbers) && $numbers_li == true) {
-
-
- // additional whitespace for browsers that do not display
- // empty list items correctly
- $this->_output = '<li>&nbsp;' . $html_output . '</li>';
-
- $start = '';
- if ($this->_numbers == HL_NUMBERS_OL && intval($this->_numbers_start) > 0) {
- $start = ' start="' . $this->_numbers_start . '"';
- }
-
- $list_tag = 'ol';
- if ($this->_numbers == HL_NUMBERS_UL) {
- $list_tag = 'ul';
- }
-
-
- $this->_output = '<' . $list_tag . $start
- . ' ' . $this->_getStyling('main', false) . '>'
- . $this->_output . '</'. $list_tag .'>';
-
- // render a table
- } else if ($this->_numbers == HL_NUMBERS_TABLE) {
-
-
- $start_number = 0;
- if (intval($this->_numbers_start)) {
- $start_number = $this->_numbers_start - 1;
- }
-
- $numbers = '';
-
- $nlines = substr_count($html_output,"\n")+1;
- for ($i=1; $i <= $nlines; $i++) {
- $numbers .= ($start_number + $i) . "\n";
- }
- $this->_output = '<table ' . $this->_getStyling('table', false) . ' width="100%"><tr>' .
- '<td '. $this->_getStyling('gutter', false) .' align="right" valign="top">' .
- '<pre>' . $numbers . '</pre></td><td '. $this->_getStyling('main', false) .
- ' valign="top"><pre>' .
- $html_output . '</pre></td></tr></table>';
- }
- if (!$this->_numbers) {
- $this->_output = '<pre>' . $html_output . '</pre>';
- }
- $this->_output = '<div ' . $this->_getStyling('main', false) . '>' . $this->_output . '</div>';
- }
-
-
- /**
- * Provides additional formatting to a keyword
- *
- * @param string $content Keyword
- * @return string Keyword with additional formatting
- * @access public
- *
- */
- function _decorate($content, $key = false)
- {
- // links to online documentation
- if (!empty($this->_doclinks) &&
- !empty($this->_doclinks['url']) &&
- in_array($key, $this->_doclinks['elements'])
- ) {
-
- $link = '<a href="'. sprintf($this->_doclinks['url'], $content) . '"';
- if (!empty($this->_doclinks['target'])) {
- $link.= ' target="' . $this->_doclinks['target'] . '"';
- }
- $link .= '>';
- $link.= $content;
- $link.= '</a>';
-
- $content = $link;
-
- }
-
- return $content;
- }
-
- /**
- * Returns <code>class</code> and/or <code>style</code> attribute,
- * optionally enclosed in a <code>span</code> tag
- *
- * @param string $class Class name
- * @paran boolean $span_tag Whether or not to return styling attributes in a <code>&gt;span&lt;</code> tag
- * @return string <code>span</code> tag or just a <code>class</code> and/or <code>style</code> attributes
- * @access private
- */
- function _getStyling($class, $span_tag = true)
- {
- $attrib = '';
- if (!empty($this->_style_map) &&
- !empty($this->_style_map[$class])
- ) {
- $attrib = 'style="'. $this->_style_map[$class] .'"';
- }
- if (!empty($this->_class_map) &&
- !empty($this->_class_map[$class])
- ) {
- if ($attrib) {
- $attrib .= ' ';
- }
- $attrib .= 'class="'. $this->_getFullClassName($this->_class_map[$class]) .'"';
- }
-
- if ($span_tag) {
- $span = '<span ' . $attrib . '>%s</span>';
- return $span;
- } else {
- return $attrib;
- }
-
- }
-}
-
-/*
- * Local variables:
- * tab-width: 4
- * c-basic-offset: 4
- * c-hanging-comment-ender-p: nil
- * End:
- */
-
-?>
diff --git a/library/Text_Highlighter/Text/Highlighter/Renderer/HtmlTags.php b/library/Text_Highlighter/Text/Highlighter/Renderer/HtmlTags.php
deleted file mode 100644
index 68e01d3e0..000000000
--- a/library/Text_Highlighter/Text/Highlighter/Renderer/HtmlTags.php
+++ /dev/null
@@ -1,187 +0,0 @@
-<?php
-/* vim: set expandtab tabstop=4 shiftwidth=4 softtabstop=4: */
-/**
- * HTML renderer that uses only basic html tags
- *
- * PHP versions 4 and 5. Based on the "normal" HTML renderer by Andrey Demenev.
- * It's designed to work with user agents that support only a limited number of
- * HTML tags. Like the iPod which supports only b, i, u and a.
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @category Text
- * @package Text_Highlighter
- * @author Stoyan Stefanov <ssttoo@gmail.com>
- * @copyright 2005 Stoyan Stefanov
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version CVS: $Id$
- * @link http://pear.php.net/package/Text_Highlighter
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter/Renderer.php';
-require_once 'Text/Highlighter/Renderer/Array.php';
-
-/**
- * HTML basic tags renderer, based on Andrey Demenev's HTML renderer.
- *
- * Elements of $options argument of constructor (each being optional):
- *
- * - 'numbers' - Line numbering TRUE or FALSE. Default is FALSE.
- * - 'tabsize' - Tab size, default is 4.
- * - 'tags' - Array, containing the tags to be used for highlighting
- *
- * Here's the listing of the default tags:
- * - 'default' => '',
- * - 'code' => '',
- * - 'brackets' => 'b',
- * - 'comment' => 'i',
- * - 'mlcomment' => 'i',
- * - 'quotes' => '',
- * - 'string' => 'i',
- * - 'identifier' => 'b',
- * - 'builtin' => 'b',
- * - 'reserved' => 'u',
- * - 'inlinedoc' => 'i',
- * - 'var' => 'b',
- * - 'url' => 'i',
- * - 'special' => '',
- * - 'number' => '',
- * - 'inlinetags' => ''
- *
- * @author Stoyan Stefanov <ssttoo@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2005 Stoyan Stefanov
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: 0.5.0
- * @link http://pear.php.net/package/Text_Highlighter
- */
-
-class Text_Highlighter_Renderer_HtmlTags extends Text_Highlighter_Renderer_Array
-{
-
- /**#@+
- * @access private
- */
-
- /**
- * Line numbering - will use 'ol' tag
- *
- * @var boolean
- */
- var $_numbers = false;
-
- /**
- * HTML tags map
- *
- * @var array
- */
- var $_hilite_tags = array(
- 'default' => '',
- 'code' => '',
- 'brackets' => 'b',
- 'comment' => 'i',
- 'mlcomment' => 'i',
- 'quotes' => '',
- 'string' => 'i',
- 'identifier' => 'b',
- 'builtin' => 'b',
- 'reserved' => 'u',
- 'inlinedoc' => 'i',
- 'var' => 'b',
- 'url' => 'i',
- 'special' => '',
- 'number' => '',
- 'inlinetags' => '',
- );
-
- /**#@-*/
-
- /**
- * Resets renderer state
- *
- * @access protected
- *
- *
- * Descendents of Text_Highlighter call this method from the constructor,
- * passing $options they get as parameter.
- */
- function reset()
- {
- parent::reset();
- if (isset($this->_options['numbers'])) {
- $this->_numbers = $this->_options['numbers'];
- }
- if (isset($this->_options['tags'])) {
- $this->_hilite_tags = array_merge($this->_tags, $this->_options['tags']);
- }
- }
-
-
- /**
- * Signals that no more tokens are available
- *
- * @abstract
- * @access public
- *
- */
- function finalize()
- {
-
- // get parent's output
- parent::finalize();
- $output = parent::getOutput();
-
- $html_output = '';
-
- // loop through each class=>content pair
- foreach ($output AS $token) {
-
- if ($this->_enumerated) {
- $class = $token[0];
- $content = $token[1];
- } else {
- $key = key($token);
- $class = $key;
- $content = $token[$key];
- }
-
- $iswhitespace = ctype_space($content);
- if (!$iswhitespace && !empty($this->_hilite_tags[$class])) {
- $html_output .= '<'. $this->_hilite_tags[$class] . '>' . $content . '</'. $this->_hilite_tags[$class] . '>';
- } else {
- $html_output .= $content;
- }
- }
-
-
- if ($this->_numbers) {
- /* additional whitespace for browsers that do not display
- empty list items correctly */
- $html_output = '<li>&nbsp;' . str_replace("\n", "</li>\n<li>&nbsp;", $html_output) . '</li>';
- $this->_output = '<ol>' . str_replace(' ', '&nbsp;', $html_output) . '</ol>';
- } else {
- $this->_output = '<pre>' . $html_output . '</pre>';
- }
- }
-
-
-}
-
-/*
- * Local variables:
- * tab-width: 4
- * c-basic-offset: 4
- * c-hanging-comment-ender-p: nil
- * End:
- */
-
-?>
diff --git a/library/Text_Highlighter/Text/Highlighter/Renderer/JSON.php b/library/Text_Highlighter/Text/Highlighter/Renderer/JSON.php
deleted file mode 100644
index d4c926161..000000000
--- a/library/Text_Highlighter/Text/Highlighter/Renderer/JSON.php
+++ /dev/null
@@ -1,86 +0,0 @@
-<?php
-/* vim: set expandtab tabstop=4 shiftwidth=4 softtabstop=4: */
-/**
- * JSON renderer.
- *
- * Based on the HTML renderer by Andrey Demenev.
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @category Text
- * @package Text_Highlighter
- * @author Stoyan Stefanov <ssttoo@gmail.com>
- * @copyright 2006 Stoyan Stefanov
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version CVS: $Id$
- * @link http://pear.php.net/package/Text_Highlighter
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter/Renderer.php';
-require_once 'Text/Highlighter/Renderer/Array.php';
-
-/**
- * JSON renderer, based on Andrey Demenev's HTML renderer.
- *
- * @author Stoyan Stefanov <ssttoo@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2006 Stoyan Stefanov
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: 0.5.0
- * @link http://pear.php.net/package/Text_Highlighter
- */
-
-class Text_Highlighter_Renderer_JSON extends Text_Highlighter_Renderer_Array
-{
-
- /**
- * Signals that no more tokens are available
- *
- * @abstract
- * @access public
- */
- function finalize()
- {
-
- parent::finalize();
- $output = parent::getOutput();
-
- $json_array = array();
-
- foreach ($output AS $token) {
-
- if ($this->_enumerated) {
- $json_array[] = '["' . $token[0] . '","' . $token[1] . '"]';
- } else {
- $key = key($token);
- $json_array[] = '{"class": "' . $key . '","content":"' . $token[$key] . '"}';
- }
-
- }
-
- $this->_output = '['. implode(',', $json_array) .']';
- $this->_output = str_replace("\n", '\n', $this->_output);
-
- }
-
-
-}
-
-/*
- * Local variables:
- * tab-width: 4
- * c-basic-offset: 4
- * c-hanging-comment-ender-p: nil
- * End:
- */
-
-?> \ No newline at end of file
diff --git a/library/Text_Highlighter/Text/Highlighter/Renderer/XML.php b/library/Text_Highlighter/Text/Highlighter/Renderer/XML.php
deleted file mode 100644
index 7b6fb2106..000000000
--- a/library/Text_Highlighter/Text/Highlighter/Renderer/XML.php
+++ /dev/null
@@ -1,104 +0,0 @@
-<?php
-/* vim: set expandtab tabstop=4 shiftwidth=4 softtabstop=4: */
-/**
- * XML renderer.
- *
- * Based on the HTML renderer by Andrey Demenev.
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @category Text
- * @package Text_Highlighter
- * @author Stoyan Stefanov <ssttoo@gmail.com>
- * @copyright 2006 Stoyan Stefanov
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version CVS: $Id$
- * @link http://pear.php.net/package/Text_Highlighter
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter/Renderer.php';
-require_once 'Text/Highlighter/Renderer/Array.php';
-require_once 'XML/Serializer.php';
-
-/**
- * XML renderer, based on Andrey Demenev's HTML renderer.
- *
- * @author Stoyan Stefanov <ssttoo@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2006 Stoyan Stefanov
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: 0.5.0
- * @link http://pear.php.net/package/Text_Highlighter
- */
-
-class Text_Highlighter_Renderer_XML extends Text_Highlighter_Renderer_Array
-{
-
-
- /**
- * Options for XML_Serializer
- *
- * @access private
- * @var array
- */
- var $_serializer_options = array();
-
-
- /**
- * Resets renderer state
- *
- * Descendents of Text_Highlighter call this method from the constructor,
- * passing $options they get as parameter.
- *
- * @access protected
- */
- function reset()
- {
- parent::reset();
- if (isset($this->_options['xml_serializer'])) {
- $this->_serializer_options = $this->_options['xml_serializer'];
- }
- }
-
-
- /**
- * Signals that no more tokens are available
- *
- * @abstract
- * @access public
- */
- function finalize()
- {
-
- // call parent's finalize(), then serialize array into XML
- parent::finalize();
- $output = parent::getOutput();
-
- $serializer = new XML_Serializer($this->_serializer_options);
- $result = $serializer->serialize($output);
- if ($result === true) {
- $this->_output = $serializer->getSerializedData();
- }
- }
-
-
-}
-
-/*
- * Local variables:
- * tab-width: 4
- * c-basic-offset: 4
- * c-hanging-comment-ender-p: nil
- * End:
- */
-
-?>
diff --git a/library/Text_Highlighter/Text/Highlighter/SH.php b/library/Text_Highlighter/Text/Highlighter/SH.php
deleted file mode 100644
index ff779868f..000000000
--- a/library/Text_Highlighter/Text/Highlighter/SH.php
+++ /dev/null
@@ -1,1225 +0,0 @@
-<?php
-/**
- * Auto-generated class. SH syntax highlighting
- *
- * This highlighter is EXPERIMENTAL. It may work incorrectly.
- * It is a crude hack of the perl syntax, which itself wasn't so good.
- * But this seems to work OK.
- *
- *
- * PHP version 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @link http://pear.php.net/package/Text_Highlighter
- * @category Text
- * @package Text_Highlighter
- * @version generated from: : sh.xml,v 1.2 2007/06/14 00:15:50 ssttoo Exp
- * @author Noah Spurrier <noah@noah.org>
- *
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter.php';
-
-/**
- * Auto-generated class. SH syntax highlighting
- *
- * @author Noah Spurrier <noah@noah.org>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: @package_version@
- * @link http://pear.php.net/package/Text_Highlighter
- */
-class Text_Highlighter_SH extends Text_Highlighter
-{
- var $_language = 'sh';
-
- /**
- * PHP4 Compatible Constructor
- *
- * @param array $options
- * @access public
- */
- function Text_Highlighter_SH($options=array())
- {
- $this->__construct($options);
- }
-
-
- /**
- * Constructor
- *
- * @param array $options
- * @access public
- */
- function __construct($options=array())
- {
-
- $this->_options = $options;
- $this->_regs = array (
- -1 => '/((?m)^(#!)(.*))|(\\{)|(\\()|(\\[)|((use)\\s+([\\w:]*))|((?Us)\\b(q[wq]\\s*((\\{)|(\\()|(\\[)|(\\<)|([\\W\\S])))(?=(.*)((?(3)\\})(?(4)\\))(?(5)\\])(?(6)\\>)(?(7)\\7))))|((?Us)\\b(q\\s*((\\{)|(\\()|(\\[)|(\\<)|([\\W\\S])))(?=(.*)((?(3)\\})(?(4)\\))(?(5)\\])(?(6)\\>)(?(7)\\7))))|(#.*)|((?x)(s|tr) ([|#~`!@$%^&*-+=\\\\;:\'",.\\/?]) ((\\\\.|[^\\\\])*?) (\\2)((\\\\.|[^\\\\])*?)(\\2[ecgimosx]*))|((?x)(m) ([|#~`!@$%^&*-+=\\\\;:\'",.\\/?]) ((\\\\.|[^\\\\])*?) (\\2[ecgimosx]*))|( \\/)|(\\$#?[1-9\'`@!])|((?i)(\\$#?|[@%*])([a-z1-9_]+::)*([a-z1-9_]+|\\^(?-i)[A-Z]?(?i)))|((?i)\\$([a-z1-9_]+|\\^(?-i)[A-Z]?(?i)))|((?i)(\\{)([a-z1-9]+)(\\}))|((?i)[\\$@%]#?\\{[a-z1-9]+\\})|(`)|(\')|(")|((?i)[a-z_]\\w*)|(\\d*\\.?\\d+)/',
- 0 => '/((?m)^(#!)(.*))|(\\{)|(\\()|(\\[)|((use)\\s+([\\w:]*))|((?Us)\\b(q[wq]\\s*((\\{)|(\\()|(\\[)|(\\<)|([\\W\\S])))(?=(.*)((?(3)\\})(?(4)\\))(?(5)\\])(?(6)\\>)(?(7)\\7))))|((?Us)\\b(q\\s*((\\{)|(\\()|(\\[)|(\\<)|([\\W\\S])))(?=(.*)((?(3)\\})(?(4)\\))(?(5)\\])(?(6)\\>)(?(7)\\7))))|(#.*)|((?x)(s|tr) ([|#~`!@$%^&*-+=\\\\;:\'",.\\/?]) ((\\\\.|[^\\\\])*?) (\\2)((\\\\.|[^\\\\])*?)(\\2[ecgimosx]*))|((?x)(m) ([|#~`!@$%^&*-+=\\\\;:\'",.\\/?]) ((\\\\.|[^\\\\])*?) (\\2[ecgimosx]*))|( \\/)|(\\$#?[1-9\'`@!])|((?i)(\\$#?|[@%*])([a-z1-9_]+::)*([a-z1-9_]+|\\^(?-i)[A-Z]?(?i)))|((?i)\\$([a-z1-9_]+|\\^(?-i)[A-Z]?(?i)))|((?i)(\\{)([a-z1-9]+)(\\}))|((?i)[\\$@%]#?\\{[a-z1-9]+\\})|(`)|(\')|(")|((?i)[a-z_]\\w*)|(\\d*\\.?\\d+)/',
- 1 => '/((?m)^(#!)(.*))|(\\{)|(\\()|(\\[)|((use)\\s+([\\w:]*))|((?Us)\\b(q[wq]\\s*((\\{)|(\\()|(\\[)|(\\<)|([\\W\\S])))(?=(.*)((?(3)\\})(?(4)\\))(?(5)\\])(?(6)\\>)(?(7)\\7))))|((?Us)\\b(q\\s*((\\{)|(\\()|(\\[)|(\\<)|([\\W\\S])))(?=(.*)((?(3)\\})(?(4)\\))(?(5)\\])(?(6)\\>)(?(7)\\7))))|(#.*)|((?x)(s|tr) ([|#~`!@$%^&*-+=\\\\;:\'",.\\/?]) ((\\\\.|[^\\\\])*?) (\\2)((\\\\.|[^\\\\])*?)(\\2[ecgimosx]*))|((?x)(m) ([|#~`!@$%^&*-+=\\\\;:\'",.\\/?]) ((\\\\.|[^\\\\])*?) (\\2[ecgimosx]*))|( \\/)|((?i)([a-z1-9_]+)(\\s*=>))|(\\$#?[1-9\'`@!])|((?i)(\\$#?|[@%*])([a-z1-9_]+::)*([a-z1-9_]+|\\^(?-i)[A-Z]?(?i)))|((?i)\\$([a-z1-9_]+|\\^(?-i)[A-Z]?(?i)))|((?i)(\\{)([a-z1-9]+)(\\}))|((?i)[\\$@%]#?\\{[a-z1-9]+\\})|(`)|(\')|(")|((?i)[a-z_]\\w*)|(\\d*\\.?\\d+)/',
- 2 => '/((?m)^(#!)(.*))|(\\{)|(\\()|(\\[)|((use)\\s+([\\w:]*))|((?Us)\\b(q[wq]\\s*((\\{)|(\\()|(\\[)|(\\<)|([\\W\\S])))(?=(.*)((?(3)\\})(?(4)\\))(?(5)\\])(?(6)\\>)(?(7)\\7))))|((?Us)\\b(q\\s*((\\{)|(\\()|(\\[)|(\\<)|([\\W\\S])))(?=(.*)((?(3)\\})(?(4)\\))(?(5)\\])(?(6)\\>)(?(7)\\7))))|(#.*)|((?x)(s|tr) ([|#~`!@$%^&*-+=\\\\;:\'",.\\/?]) ((\\\\.|[^\\\\])*?) (\\2)((\\\\.|[^\\\\])*?)(\\2[ecgimosx]*))|((?x)(m) ([|#~`!@$%^&*-+=\\\\;:\'",.\\/?]) ((\\\\.|[^\\\\])*?) (\\2[ecgimosx]*))|( \\/)|(\\$#?[1-9\'`@!])|((?i)(\\$#?|[@%*])([a-z1-9_]+::)*([a-z1-9_]+|\\^(?-i)[A-Z]?(?i)))|((?i)\\$([a-z1-9_]+|\\^(?-i)[A-Z]?(?i)))|((?i)(\\{)([a-z1-9]+)(\\}))|((?i)[\\$@%]#?\\{[a-z1-9]+\\})|(`)|(\')|(")|((?i)[a-z_]\\w*)|(\\d*\\.?\\d+)/',
- 3 => '/(\\$#?[1-9\'`@!])|((?i)\\$([a-z1-9_]+|\\^(?-i)[A-Z]?(?i)))|((?i)[\\$@%]#?\\{[a-z1-9]+\\})|(\\\\[\\\\"\'`tnr\\$\\{@])/',
- 4 => '/(\\\\\\\\|\\\\"|\\\\\'|\\\\`)/',
- 5 => '/(\\\\\\/)/',
- 6 => '/(\\$#?[1-9\'`@!])|((?i)\\$([a-z1-9_]+|\\^(?-i)[A-Z]?(?i)))|((?i)[\\$@%]#?\\{[a-z1-9]+\\})|(\\\\\\\\|\\\\"|\\\\\'|\\\\`)/',
- 7 => '/(\\\\\\\\|\\\\"|\\\\\'|\\\\`)/',
- 8 => '/(\\$#?[1-9\'`@!])|((?i)\\$([a-z1-9_]+|\\^(?-i)[A-Z]?(?i)))|((?i)[\\$@%]#?\\{[a-z1-9]+\\})|(\\\\[\\\\"\'`tnr\\$\\{@])/',
- );
- $this->_counts = array (
- -1 =>
- array (
- 0 => 2,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 2,
- 5 => 9,
- 6 => 9,
- 7 => 0,
- 8 => 8,
- 9 => 5,
- 10 => 0,
- 11 => 0,
- 12 => 3,
- 13 => 1,
- 14 => 3,
- 15 => 0,
- 16 => 0,
- 17 => 0,
- 18 => 0,
- 19 => 0,
- 20 => 0,
- ),
- 0 =>
- array (
- 0 => 2,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 2,
- 5 => 9,
- 6 => 9,
- 7 => 0,
- 8 => 8,
- 9 => 5,
- 10 => 0,
- 11 => 0,
- 12 => 3,
- 13 => 1,
- 14 => 3,
- 15 => 0,
- 16 => 0,
- 17 => 0,
- 18 => 0,
- 19 => 0,
- 20 => 0,
- ),
- 1 =>
- array (
- 0 => 2,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 2,
- 5 => 9,
- 6 => 9,
- 7 => 0,
- 8 => 8,
- 9 => 5,
- 10 => 0,
- 11 => 2,
- 12 => 0,
- 13 => 3,
- 14 => 1,
- 15 => 3,
- 16 => 0,
- 17 => 0,
- 18 => 0,
- 19 => 0,
- 20 => 0,
- 21 => 0,
- ),
- 2 =>
- array (
- 0 => 2,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 2,
- 5 => 9,
- 6 => 9,
- 7 => 0,
- 8 => 8,
- 9 => 5,
- 10 => 0,
- 11 => 0,
- 12 => 3,
- 13 => 1,
- 14 => 3,
- 15 => 0,
- 16 => 0,
- 17 => 0,
- 18 => 0,
- 19 => 0,
- 20 => 0,
- ),
- 3 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 0,
- 3 => 0,
- ),
- 4 =>
- array (
- 0 => 0,
- ),
- 5 =>
- array (
- 0 => 0,
- ),
- 6 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 0,
- 3 => 0,
- ),
- 7 =>
- array (
- 0 => 0,
- ),
- 8 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 0,
- 3 => 0,
- ),
- );
- $this->_delim = array (
- -1 =>
- array (
- 0 => '',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'brackets',
- 4 => '',
- 5 => 'quotes',
- 6 => 'quotes',
- 7 => '',
- 8 => '',
- 9 => '',
- 10 => 'quotes',
- 11 => '',
- 12 => '',
- 13 => '',
- 14 => '',
- 15 => '',
- 16 => 'quotes',
- 17 => 'quotes',
- 18 => 'quotes',
- 19 => '',
- 20 => '',
- ),
- 0 =>
- array (
- 0 => '',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'brackets',
- 4 => '',
- 5 => 'quotes',
- 6 => 'quotes',
- 7 => '',
- 8 => '',
- 9 => '',
- 10 => 'quotes',
- 11 => '',
- 12 => '',
- 13 => '',
- 14 => '',
- 15 => '',
- 16 => 'quotes',
- 17 => 'quotes',
- 18 => 'quotes',
- 19 => '',
- 20 => '',
- ),
- 1 =>
- array (
- 0 => '',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'brackets',
- 4 => '',
- 5 => 'quotes',
- 6 => 'quotes',
- 7 => '',
- 8 => '',
- 9 => '',
- 10 => 'quotes',
- 11 => '',
- 12 => '',
- 13 => '',
- 14 => '',
- 15 => '',
- 16 => '',
- 17 => 'quotes',
- 18 => 'quotes',
- 19 => 'quotes',
- 20 => '',
- 21 => '',
- ),
- 2 =>
- array (
- 0 => '',
- 1 => 'brackets',
- 2 => 'brackets',
- 3 => 'brackets',
- 4 => '',
- 5 => 'quotes',
- 6 => 'quotes',
- 7 => '',
- 8 => '',
- 9 => '',
- 10 => 'quotes',
- 11 => '',
- 12 => '',
- 13 => '',
- 14 => '',
- 15 => '',
- 16 => 'quotes',
- 17 => 'quotes',
- 18 => 'quotes',
- 19 => '',
- 20 => '',
- ),
- 3 =>
- array (
- 0 => '',
- 1 => '',
- 2 => '',
- 3 => '',
- ),
- 4 =>
- array (
- 0 => '',
- ),
- 5 =>
- array (
- 0 => '',
- ),
- 6 =>
- array (
- 0 => '',
- 1 => '',
- 2 => '',
- 3 => '',
- ),
- 7 =>
- array (
- 0 => '',
- ),
- 8 =>
- array (
- 0 => '',
- 1 => '',
- 2 => '',
- 3 => '',
- ),
- );
- $this->_inner = array (
- -1 =>
- array (
- 0 => 'special',
- 1 => 'code',
- 2 => 'code',
- 3 => 'code',
- 4 => 'special',
- 5 => 'string',
- 6 => 'string',
- 7 => 'comment',
- 8 => 'string',
- 9 => 'string',
- 10 => 'string',
- 11 => 'var',
- 12 => 'var',
- 13 => 'var',
- 14 => 'var',
- 15 => 'var',
- 16 => 'string',
- 17 => 'string',
- 18 => 'string',
- 19 => 'identifier',
- 20 => 'number',
- ),
- 0 =>
- array (
- 0 => 'special',
- 1 => 'code',
- 2 => 'code',
- 3 => 'code',
- 4 => 'special',
- 5 => 'string',
- 6 => 'string',
- 7 => 'comment',
- 8 => 'string',
- 9 => 'string',
- 10 => 'string',
- 11 => 'var',
- 12 => 'var',
- 13 => 'var',
- 14 => 'var',
- 15 => 'var',
- 16 => 'string',
- 17 => 'string',
- 18 => 'string',
- 19 => 'identifier',
- 20 => 'number',
- ),
- 1 =>
- array (
- 0 => 'special',
- 1 => 'code',
- 2 => 'code',
- 3 => 'code',
- 4 => 'special',
- 5 => 'string',
- 6 => 'string',
- 7 => 'comment',
- 8 => 'string',
- 9 => 'string',
- 10 => 'string',
- 11 => 'string',
- 12 => 'var',
- 13 => 'var',
- 14 => 'var',
- 15 => 'var',
- 16 => 'var',
- 17 => 'string',
- 18 => 'string',
- 19 => 'string',
- 20 => 'identifier',
- 21 => 'number',
- ),
- 2 =>
- array (
- 0 => 'special',
- 1 => 'code',
- 2 => 'code',
- 3 => 'code',
- 4 => 'special',
- 5 => 'string',
- 6 => 'string',
- 7 => 'comment',
- 8 => 'string',
- 9 => 'string',
- 10 => 'string',
- 11 => 'var',
- 12 => 'var',
- 13 => 'var',
- 14 => 'var',
- 15 => 'var',
- 16 => 'string',
- 17 => 'string',
- 18 => 'string',
- 19 => 'identifier',
- 20 => 'number',
- ),
- 3 =>
- array (
- 0 => 'var',
- 1 => 'var',
- 2 => 'var',
- 3 => 'special',
- ),
- 4 =>
- array (
- 0 => 'special',
- ),
- 5 =>
- array (
- 0 => 'string',
- ),
- 6 =>
- array (
- 0 => 'var',
- 1 => 'var',
- 2 => 'var',
- 3 => 'special',
- ),
- 7 =>
- array (
- 0 => 'special',
- ),
- 8 =>
- array (
- 0 => 'var',
- 1 => 'var',
- 2 => 'var',
- 3 => 'special',
- ),
- );
- $this->_end = array (
- 0 => '/\\}/',
- 1 => '/\\)/',
- 2 => '/\\]/',
- 3 => '/%b2%/',
- 4 => '/%b2%/',
- 5 => '/\\/[cgimosx]*/',
- 6 => '/`/',
- 7 => '/\'/',
- 8 => '/"/',
- );
- $this->_states = array (
- -1 =>
- array (
- 0 => -1,
- 1 => 0,
- 2 => 1,
- 3 => 2,
- 4 => -1,
- 5 => 3,
- 6 => 4,
- 7 => -1,
- 8 => -1,
- 9 => -1,
- 10 => 5,
- 11 => -1,
- 12 => -1,
- 13 => -1,
- 14 => -1,
- 15 => -1,
- 16 => 6,
- 17 => 7,
- 18 => 8,
- 19 => -1,
- 20 => -1,
- ),
- 0 =>
- array (
- 0 => -1,
- 1 => 0,
- 2 => 1,
- 3 => 2,
- 4 => -1,
- 5 => 3,
- 6 => 4,
- 7 => -1,
- 8 => -1,
- 9 => -1,
- 10 => 5,
- 11 => -1,
- 12 => -1,
- 13 => -1,
- 14 => -1,
- 15 => -1,
- 16 => 6,
- 17 => 7,
- 18 => 8,
- 19 => -1,
- 20 => -1,
- ),
- 1 =>
- array (
- 0 => -1,
- 1 => 0,
- 2 => 1,
- 3 => 2,
- 4 => -1,
- 5 => 3,
- 6 => 4,
- 7 => -1,
- 8 => -1,
- 9 => -1,
- 10 => 5,
- 11 => -1,
- 12 => -1,
- 13 => -1,
- 14 => -1,
- 15 => -1,
- 16 => -1,
- 17 => 6,
- 18 => 7,
- 19 => 8,
- 20 => -1,
- 21 => -1,
- ),
- 2 =>
- array (
- 0 => -1,
- 1 => 0,
- 2 => 1,
- 3 => 2,
- 4 => -1,
- 5 => 3,
- 6 => 4,
- 7 => -1,
- 8 => -1,
- 9 => -1,
- 10 => 5,
- 11 => -1,
- 12 => -1,
- 13 => -1,
- 14 => -1,
- 15 => -1,
- 16 => 6,
- 17 => 7,
- 18 => 8,
- 19 => -1,
- 20 => -1,
- ),
- 3 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- ),
- 4 =>
- array (
- 0 => -1,
- ),
- 5 =>
- array (
- 0 => -1,
- ),
- 6 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- ),
- 7 =>
- array (
- 0 => -1,
- ),
- 8 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- ),
- );
- $this->_keywords = array (
- -1 =>
- array (
- 0 =>
- array (
- ),
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 =>
- array (
- ),
- 5 => -1,
- 6 => -1,
- 7 =>
- array (
- ),
- 8 =>
- array (
- ),
- 9 =>
- array (
- ),
- 10 => -1,
- 11 =>
- array (
- ),
- 12 =>
- array (
- ),
- 13 =>
- array (
- ),
- 14 =>
- array (
- ),
- 15 =>
- array (
- ),
- 16 => -1,
- 17 => -1,
- 18 => -1,
- 19 =>
- array (
- 'reserved' => '/^(cd|cp|rm|echo|printf|exit|cut|join|comm|fmt|grep|egrep|fgrep|sed|awk|yes|false|true|test|expr|tee|basename|dirname|pathchk|pwd|stty|tty|env|printenv|id|logname|whoami|groups|users|who|date|uname|hostname|chroot|nice|nohup|sleep|factor|seq|getopt|getopts|options|shift)$/',
- 'flowcontrol' => '/^(if|fi|then|else|elif|case|esac|while|done|for|in|function|until|do|select|time|read|set)$/',
- ),
- 20 =>
- array (
- ),
- ),
- 0 =>
- array (
- 0 =>
- array (
- ),
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 =>
- array (
- ),
- 5 => -1,
- 6 => -1,
- 7 =>
- array (
- ),
- 8 =>
- array (
- ),
- 9 =>
- array (
- ),
- 10 => -1,
- 11 =>
- array (
- ),
- 12 =>
- array (
- ),
- 13 =>
- array (
- ),
- 14 =>
- array (
- ),
- 15 =>
- array (
- ),
- 16 => -1,
- 17 => -1,
- 18 => -1,
- 19 =>
- array (
- 'reserved' => '/^(cd|cp|rm|echo|printf|exit|cut|join|comm|fmt|grep|egrep|fgrep|sed|awk|yes|false|true|test|expr|tee|basename|dirname|pathchk|pwd|stty|tty|env|printenv|id|logname|whoami|groups|users|who|date|uname|hostname|chroot|nice|nohup|sleep|factor|seq|getopt|getopts|options|shift)$/',
- 'flowcontrol' => '/^(if|fi|then|else|elif|case|esac|while|done|for|in|function|until|do|select|time|read|set)$/',
- ),
- 20 =>
- array (
- ),
- ),
- 1 =>
- array (
- 0 =>
- array (
- ),
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 =>
- array (
- ),
- 5 => -1,
- 6 => -1,
- 7 =>
- array (
- ),
- 8 =>
- array (
- ),
- 9 =>
- array (
- ),
- 10 => -1,
- 11 =>
- array (
- ),
- 12 =>
- array (
- ),
- 13 =>
- array (
- ),
- 14 =>
- array (
- ),
- 15 =>
- array (
- ),
- 16 =>
- array (
- ),
- 17 => -1,
- 18 => -1,
- 19 => -1,
- 20 =>
- array (
- 'reserved' => '/^(cd|cp|rm|echo|printf|exit|cut|join|comm|fmt|grep|egrep|fgrep|sed|awk|yes|false|true|test|expr|tee|basename|dirname|pathchk|pwd|stty|tty|env|printenv|id|logname|whoami|groups|users|who|date|uname|hostname|chroot|nice|nohup|sleep|factor|seq|getopt|getopts|options|shift)$/',
- 'flowcontrol' => '/^(if|fi|then|else|elif|case|esac|while|done|for|in|function|until|do|select|time|read|set)$/',
- ),
- 21 =>
- array (
- ),
- ),
- 2 =>
- array (
- 0 =>
- array (
- ),
- 1 => -1,
- 2 => -1,
- 3 => -1,
- 4 =>
- array (
- ),
- 5 => -1,
- 6 => -1,
- 7 =>
- array (
- ),
- 8 =>
- array (
- ),
- 9 =>
- array (
- ),
- 10 => -1,
- 11 =>
- array (
- ),
- 12 =>
- array (
- ),
- 13 =>
- array (
- ),
- 14 =>
- array (
- ),
- 15 =>
- array (
- ),
- 16 => -1,
- 17 => -1,
- 18 => -1,
- 19 =>
- array (
- 'reserved' => '/^(cd|cp|rm|echo|printf|exit|cut|join|comm|fmt|grep|egrep|fgrep|sed|awk|yes|false|true|test|expr|tee|basename|dirname|pathchk|pwd|stty|tty|env|printenv|id|logname|whoami|groups|users|who|date|uname|hostname|chroot|nice|nohup|sleep|factor|seq|getopt|getopts|options|shift)$/',
- 'flowcontrol' => '/^(if|fi|then|else|elif|case|esac|while|done|for|in|function|until|do|select|time|read|set)$/',
- ),
- 20 =>
- array (
- ),
- ),
- 3 =>
- array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- 3 =>
- array (
- ),
- ),
- 4 =>
- array (
- 0 =>
- array (
- ),
- ),
- 5 =>
- array (
- 0 =>
- array (
- ),
- ),
- 6 =>
- array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- 3 =>
- array (
- ),
- ),
- 7 =>
- array (
- 0 =>
- array (
- ),
- ),
- 8 =>
- array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- 3 =>
- array (
- ),
- ),
- );
- $this->_parts = array (
- 0 =>
- array (
- 0 =>
- array (
- 1 => 'special',
- 2 => 'string',
- ),
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 =>
- array (
- 1 => 'reserved',
- 2 => 'special',
- ),
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 =>
- array (
- 1 => 'quotes',
- 2 => 'quotes',
- 3 => 'string',
- 5 => 'quotes',
- 6 => 'string',
- 8 => 'quotes',
- ),
- 9 =>
- array (
- 1 => 'quotes',
- 2 => 'quotes',
- 3 => 'string',
- 5 => 'quotes',
- ),
- 10 => NULL,
- 11 => NULL,
- 12 => NULL,
- 13 => NULL,
- 14 =>
- array (
- 1 => 'brackets',
- 2 => 'var',
- 3 => 'brackets',
- ),
- 15 => NULL,
- 16 => NULL,
- 17 => NULL,
- 18 => NULL,
- 19 => NULL,
- 20 => NULL,
- ),
- 1 =>
- array (
- 0 =>
- array (
- 1 => 'special',
- 2 => 'string',
- ),
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 =>
- array (
- 1 => 'reserved',
- 2 => 'special',
- ),
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 =>
- array (
- 1 => 'quotes',
- 2 => 'quotes',
- 3 => 'string',
- 5 => 'quotes',
- 6 => 'string',
- 8 => 'quotes',
- ),
- 9 =>
- array (
- 1 => 'quotes',
- 2 => 'quotes',
- 3 => 'string',
- 5 => 'quotes',
- ),
- 10 => NULL,
- 11 =>
- array (
- 1 => 'string',
- 2 => 'code',
- ),
- 12 => NULL,
- 13 => NULL,
- 14 => NULL,
- 15 =>
- array (
- 1 => 'brackets',
- 2 => 'var',
- 3 => 'brackets',
- ),
- 16 => NULL,
- 17 => NULL,
- 18 => NULL,
- 19 => NULL,
- 20 => NULL,
- 21 => NULL,
- ),
- 2 =>
- array (
- 0 =>
- array (
- 1 => 'special',
- 2 => 'string',
- ),
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 =>
- array (
- 1 => 'reserved',
- 2 => 'special',
- ),
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 =>
- array (
- 1 => 'quotes',
- 2 => 'quotes',
- 3 => 'string',
- 5 => 'quotes',
- 6 => 'string',
- 8 => 'quotes',
- ),
- 9 =>
- array (
- 1 => 'quotes',
- 2 => 'quotes',
- 3 => 'string',
- 5 => 'quotes',
- ),
- 10 => NULL,
- 11 => NULL,
- 12 => NULL,
- 13 => NULL,
- 14 =>
- array (
- 1 => 'brackets',
- 2 => 'var',
- 3 => 'brackets',
- ),
- 15 => NULL,
- 16 => NULL,
- 17 => NULL,
- 18 => NULL,
- 19 => NULL,
- 20 => NULL,
- ),
- 3 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- ),
- 4 =>
- array (
- 0 => NULL,
- ),
- 5 =>
- array (
- 0 => NULL,
- ),
- 6 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- ),
- 7 =>
- array (
- 0 => NULL,
- ),
- 8 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- ),
- );
- $this->_subst = array (
- -1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => true,
- 6 => true,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- 14 => false,
- 15 => false,
- 16 => false,
- 17 => false,
- 18 => false,
- 19 => false,
- 20 => false,
- ),
- 0 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => true,
- 6 => true,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- 14 => false,
- 15 => false,
- 16 => false,
- 17 => false,
- 18 => false,
- 19 => false,
- 20 => false,
- ),
- 1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => true,
- 6 => true,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- 14 => false,
- 15 => false,
- 16 => false,
- 17 => false,
- 18 => false,
- 19 => false,
- 20 => false,
- 21 => false,
- ),
- 2 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => true,
- 6 => true,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- 11 => false,
- 12 => false,
- 13 => false,
- 14 => false,
- 15 => false,
- 16 => false,
- 17 => false,
- 18 => false,
- 19 => false,
- 20 => false,
- ),
- 3 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- ),
- 4 =>
- array (
- 0 => false,
- ),
- 5 =>
- array (
- 0 => false,
- ),
- 6 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- ),
- 7 =>
- array (
- 0 => false,
- ),
- 8 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- ),
- );
- $this->_conditions = array (
- );
- $this->_kwmap = array (
- 'reserved' => 'reserved',
- 'flowcontrol' => 'reserved',
- );
- $this->_defClass = 'code';
- $this->_checkDefines();
- }
-
-} \ No newline at end of file
diff --git a/library/Text_Highlighter/Text/Highlighter/SQL.php b/library/Text_Highlighter/Text/Highlighter/SQL.php
deleted file mode 100644
index 824864033..000000000
--- a/library/Text_Highlighter/Text/Highlighter/SQL.php
+++ /dev/null
@@ -1,419 +0,0 @@
-<?php
-/**
- * Auto-generated class. SQL syntax highlighting
- *
- * Based on SQL-99
- *
- * PHP version 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @link http://pear.php.net/package/Text_Highlighter
- * @category Text
- * @package Text_Highlighter
- * @version generated from: : sql.xml,v 1.1 2007/06/03 02:35:28 ssttoo Exp
- * @author Andrey Demenev <demenev@gmail.com>
- *
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter.php';
-
-/**
- * Auto-generated class. SQL syntax highlighting
- *
- * @author Andrey Demenev <demenev@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: @package_version@
- * @link http://pear.php.net/package/Text_Highlighter
- */
-class Text_Highlighter_SQL extends Text_Highlighter
-{
- var $_language = 'sql';
-
- /**
- * PHP4 Compatible Constructor
- *
- * @param array $options
- * @access public
- */
- function Text_Highlighter_SQL($options=array())
- {
- $this->__construct($options);
- }
-
-
- /**
- * Constructor
- *
- * @param array $options
- * @access public
- */
- function __construct($options=array())
- {
-
- $this->_options = $options;
- $this->_regs = array (
- -1 => '/((?i)`)|((?i)\\/\\*)|((?i)(#|--\\s).*)|((?i)[a-z_]\\w*)|((?i)")|((?i)\\()|((?i)\')|((?i)((\\d+|((\\d*\\.\\d+)|(\\d+\\.\\d*)))[eE][+-]?\\d+))|((?i)(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?i)\\d+l?|\\b0l?\\b)|((?i)0[xX][\\da-f]+l?)/',
- 0 => '//',
- 1 => '//',
- 2 => '/((?i)\\\\.)/',
- 3 => '/((?i)`)|((?i)\\/\\*)|((?i)(#|--\\s).*)|((?i)[a-z_]\\w*)|((?i)")|((?i)\\()|((?i)\')|((?i)((\\d+|((\\d*\\.\\d+)|(\\d+\\.\\d*)))[eE][+-]?\\d+))|((?i)(\\d*\\.\\d+)|(\\d+\\.\\d*))|((?i)\\d+l?|\\b0l?\\b)|((?i)0[xX][\\da-f]+l?)/',
- 4 => '/((?i)\\\\.)/',
- );
- $this->_counts = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 1,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 5,
- 8 => 2,
- 9 => 0,
- 10 => 0,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => 0,
- ),
- 3 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 1,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- 6 => 0,
- 7 => 5,
- 8 => 2,
- 9 => 0,
- 10 => 0,
- ),
- 4 =>
- array (
- 0 => 0,
- ),
- );
- $this->_delim = array (
- -1 =>
- array (
- 0 => 'quotes',
- 1 => 'comment',
- 2 => '',
- 3 => '',
- 4 => 'quotes',
- 5 => 'brackets',
- 6 => 'quotes',
- 7 => '',
- 8 => '',
- 9 => '',
- 10 => '',
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => '',
- ),
- 3 =>
- array (
- 0 => 'quotes',
- 1 => 'comment',
- 2 => '',
- 3 => '',
- 4 => 'quotes',
- 5 => 'brackets',
- 6 => 'quotes',
- 7 => '',
- 8 => '',
- 9 => '',
- 10 => '',
- ),
- 4 =>
- array (
- 0 => '',
- ),
- );
- $this->_inner = array (
- -1 =>
- array (
- 0 => 'identifier',
- 1 => 'comment',
- 2 => 'comment',
- 3 => 'identifier',
- 4 => 'string',
- 5 => 'code',
- 6 => 'string',
- 7 => 'number',
- 8 => 'number',
- 9 => 'number',
- 10 => 'number',
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => 'special',
- ),
- 3 =>
- array (
- 0 => 'identifier',
- 1 => 'comment',
- 2 => 'comment',
- 3 => 'identifier',
- 4 => 'string',
- 5 => 'code',
- 6 => 'string',
- 7 => 'number',
- 8 => 'number',
- 9 => 'number',
- 10 => 'number',
- ),
- 4 =>
- array (
- 0 => 'special',
- ),
- );
- $this->_end = array (
- 0 => '/(?i)`/',
- 1 => '/(?i)\\*\\//',
- 2 => '/(?i)"/',
- 3 => '/(?i)\\)/',
- 4 => '/(?i)\'/',
- );
- $this->_states = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => -1,
- 3 => -1,
- 4 => 2,
- 5 => 3,
- 6 => 4,
- 7 => -1,
- 8 => -1,
- 9 => -1,
- 10 => -1,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => -1,
- ),
- 3 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => -1,
- 3 => -1,
- 4 => 2,
- 5 => 3,
- 6 => 4,
- 7 => -1,
- 8 => -1,
- 9 => -1,
- 10 => -1,
- ),
- 4 =>
- array (
- 0 => -1,
- ),
- );
- $this->_keywords = array (
- -1 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 =>
- array (
- ),
- 3 =>
- array (
- 'reserved' => '/^((?i)absolute|action|add|admin|after|aggregate|alias|all|allocate|alter|and|any|are|array|as|asc|assertion|at|authorization|before|begin|binary|bit|blob|boolean|both|breadth|by|call|cascade|cascaded|case|cast|catalog|char|character|check|class|clob|close|collate|collation|column|commit|completion|connect|connection|constraint|constraints|constructor|continue|corresponding|create|cross|cube|current|current_date|current_path|current_role|current_time|current_timestamp|current_user|cursor|cycle|data|date|day|deallocate|dec|decimal|declare|default|deferrable|deferred|delete|depth|deref|desc|describe|descriptor|destroy|destructor|deterministic|diagnostics|dictionary|disconnect|distinct|domain|double|drop|dynamic|each|else|end|end-exec|equals|escape|every|except|exception|exec|execute|external|false|fetch|first|float|for|foreign|found|free|from|full|function|general|get|global|go|goto|grant|group|grouping|having|host|hour|identity|ignore|immediate|in|indicator|initialize|initially|inner|inout|input|insert|int|integer|intersect|interval|into|is|isolation|iterate|join|key|language|large|last|lateral|leading|left|less|level|like|limit|local|localtime|localtimestamp|locator|map|match|minute|modifies|modify|module|month|names|national|natural|nchar|nclob|new|next|no|none|not|null|numeric|object|of|off|old|on|only|open|operation|option|or|order|ordinality|out|outer|output|pad|parameter|parameters|partial|path|postfix|precision|prefix|preorder|prepare|preserve|primary|prior|privileges|procedure|public|read|reads|real|recursive|ref|references|referencing|relative|restrict|result|return|returns|revoke|right|role|rollback|rollup|routine|row|rows|savepoint|schema|scope|scroll|search|second|section|select|sequence|session|session_user|set|sets|size|smallint|some|space|specific|specifictype|sql|sqlexception|sqlstate|sqlwarning|start|state|statement|static|structure|system_user|table|temporary|terminate|than|then|time|timestamp|timezone_hour|timezone_minute|to|trailing|transaction|translation|treat|trigger|true|under|union|unique|unknown|unnest|update|usage|user|using|value|values|varchar|variable|varying|view|when|whenever|where|with|without|work|write|year|zone)$/',
- 'keyword' => '/^((?i)abs|ada|asensitive|assignment|asymmetric|atomic|avg|between|bitvar|bit_length|c|called|cardinality|catalog_name|chain|character_length|character_set_catalog|character_set_name|character_set_schema|char_length|checked|class_origin|coalesce|cobol|collation_catalog|collation_name|collation_schema|column_name|command_function|command_function_code|committed|condition_number|connection_name|constraint_catalog|constraint_name|constraint_schema|contains|convert|count|cursor_name|datetime_interval_code|datetime_interval_precision|defined|definer|dispatch|dynamic_function|dynamic_function_code|existing|exists|extract|final|fortran|g|generated|granted|hierarchy|hold|implementation|infix|insensitive|instance|instantiable|invoker|k|key_member|key_type|length|lower|m|max|message_length|message_octet_length|message_text|method|min|mod|more|mumps|name|nullable|nullif|number|octet_length|options|overlaps|overlay|overriding|parameter_mode|parameter_name|parameter_ordinal_position|parameter_specific_catalog|parameter_specific_name|parameter_specific_schema|pascal|pli|position|repeatable|returned_length|returned_octet_length|returned_sqlstate|routine_catalog|routine_name|routine_schema|row_count|scale|schema_name|security|self|sensitive|serializable|server_name|similar|simple|source|specific_name|style|subclass_origin|sublist|substring|sum|symmetric|system|table_name|transactions_committed|transactions_rolled_back|transaction_active|transform|transforms|translate|trigger_catalog|trigger_name|trigger_schema|trim|type|uncommitted|unnamed|upper|user_defined_type_catalog|user_defined_type_name|user_defined_type_schema)$/',
- ),
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 =>
- array (
- ),
- 8 =>
- array (
- ),
- 9 =>
- array (
- ),
- 10 =>
- array (
- ),
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 =>
- array (
- ),
- ),
- 3 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 =>
- array (
- ),
- 3 =>
- array (
- 'reserved' => '/^((?i)absolute|action|add|admin|after|aggregate|alias|all|allocate|alter|and|any|are|array|as|asc|assertion|at|authorization|before|begin|binary|bit|blob|boolean|both|breadth|by|call|cascade|cascaded|case|cast|catalog|char|character|check|class|clob|close|collate|collation|column|commit|completion|connect|connection|constraint|constraints|constructor|continue|corresponding|create|cross|cube|current|current_date|current_path|current_role|current_time|current_timestamp|current_user|cursor|cycle|data|date|day|deallocate|dec|decimal|declare|default|deferrable|deferred|delete|depth|deref|desc|describe|descriptor|destroy|destructor|deterministic|diagnostics|dictionary|disconnect|distinct|domain|double|drop|dynamic|each|else|end|end-exec|equals|escape|every|except|exception|exec|execute|external|false|fetch|first|float|for|foreign|found|free|from|full|function|general|get|global|go|goto|grant|group|grouping|having|host|hour|identity|ignore|immediate|in|indicator|initialize|initially|inner|inout|input|insert|int|integer|intersect|interval|into|is|isolation|iterate|join|key|language|large|last|lateral|leading|left|less|level|like|limit|local|localtime|localtimestamp|locator|map|match|minute|modifies|modify|module|month|names|national|natural|nchar|nclob|new|next|no|none|not|null|numeric|object|of|off|old|on|only|open|operation|option|or|order|ordinality|out|outer|output|pad|parameter|parameters|partial|path|postfix|precision|prefix|preorder|prepare|preserve|primary|prior|privileges|procedure|public|read|reads|real|recursive|ref|references|referencing|relative|restrict|result|return|returns|revoke|right|role|rollback|rollup|routine|row|rows|savepoint|schema|scope|scroll|search|second|section|select|sequence|session|session_user|set|sets|size|smallint|some|space|specific|specifictype|sql|sqlexception|sqlstate|sqlwarning|start|state|statement|static|structure|system_user|table|temporary|terminate|than|then|time|timestamp|timezone_hour|timezone_minute|to|trailing|transaction|translation|treat|trigger|true|under|union|unique|unknown|unnest|update|usage|user|using|value|values|varchar|variable|varying|view|when|whenever|where|with|without|work|write|year|zone)$/',
- 'keyword' => '/^((?i)abs|ada|asensitive|assignment|asymmetric|atomic|avg|between|bitvar|bit_length|c|called|cardinality|catalog_name|chain|character_length|character_set_catalog|character_set_name|character_set_schema|char_length|checked|class_origin|coalesce|cobol|collation_catalog|collation_name|collation_schema|column_name|command_function|command_function_code|committed|condition_number|connection_name|constraint_catalog|constraint_name|constraint_schema|contains|convert|count|cursor_name|datetime_interval_code|datetime_interval_precision|defined|definer|dispatch|dynamic_function|dynamic_function_code|existing|exists|extract|final|fortran|g|generated|granted|hierarchy|hold|implementation|infix|insensitive|instance|instantiable|invoker|k|key_member|key_type|length|lower|m|max|message_length|message_octet_length|message_text|method|min|mod|more|mumps|name|nullable|nullif|number|octet_length|options|overlaps|overlay|overriding|parameter_mode|parameter_name|parameter_ordinal_position|parameter_specific_catalog|parameter_specific_name|parameter_specific_schema|pascal|pli|position|repeatable|returned_length|returned_octet_length|returned_sqlstate|routine_catalog|routine_name|routine_schema|row_count|scale|schema_name|security|self|sensitive|serializable|server_name|similar|simple|source|specific_name|style|subclass_origin|sublist|substring|sum|symmetric|system|table_name|transactions_committed|transactions_rolled_back|transaction_active|transform|transforms|translate|trigger_catalog|trigger_name|trigger_schema|trim|type|uncommitted|unnamed|upper|user_defined_type_catalog|user_defined_type_name|user_defined_type_schema)$/',
- ),
- 4 => -1,
- 5 => -1,
- 6 => -1,
- 7 =>
- array (
- ),
- 8 =>
- array (
- ),
- 9 =>
- array (
- ),
- 10 =>
- array (
- ),
- ),
- 4 =>
- array (
- 0 =>
- array (
- ),
- ),
- );
- $this->_parts = array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => NULL,
- ),
- 3 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- 6 => NULL,
- 7 => NULL,
- 8 => NULL,
- 9 => NULL,
- 10 => NULL,
- ),
- 4 =>
- array (
- 0 => NULL,
- ),
- );
- $this->_subst = array (
- -1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => false,
- ),
- 3 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- 6 => false,
- 7 => false,
- 8 => false,
- 9 => false,
- 10 => false,
- ),
- 4 =>
- array (
- 0 => false,
- ),
- );
- $this->_conditions = array (
- );
- $this->_kwmap = array (
- 'reserved' => 'reserved',
- 'keyword' => 'var',
- );
- $this->_defClass = 'code';
- $this->_checkDefines();
- }
-
-} \ No newline at end of file
diff --git a/library/Text_Highlighter/Text/Highlighter/VBSCRIPT.php b/library/Text_Highlighter/Text/Highlighter/VBSCRIPT.php
deleted file mode 100644
index 31a7c7c9e..000000000
--- a/library/Text_Highlighter/Text/Highlighter/VBSCRIPT.php
+++ /dev/null
@@ -1,318 +0,0 @@
-<?php
-/**
- * Auto-generated class. VBSCRIPT syntax highlighting
- *
- * PHP version 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @link http://pear.php.net/package/Text_Highlighter
- * @category Text
- * @package Text_Highlighter
- * @version generated from: vbscript.xml
- * @author Daniel Fruzynski <daniel-AT-poradnik-webmastera.com>
- *
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter.php';
-
-/**
- * Auto-generated class. VBSCRIPT syntax highlighting
- *
- * @author Daniel Fruzynski <daniel-AT-poradnik-webmastera.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: 0.7.0
- * @link http://pear.php.net/package/Text_Highlighter
- */
-class Text_Highlighter_VBSCRIPT extends Text_Highlighter
-{
- var $_language = 'vbscript';
-
- /**
- * PHP4 Compatible Constructor
- *
- * @param array $options
- * @access public
- */
- function Text_Highlighter_VBSCRIPT($options=array())
- {
- $this->__construct($options);
- }
-
-
- /**
- * Constructor
- *
- * @param array $options
- * @access public
- */
- function __construct($options=array())
- {
-
- $this->_options = $options;
- $this->_regs = array (
- -1 => '/((?i)\\()|((?i)")|((?i)\'|[Rr][Ee][Mm]\\b)|((?i)\\d*\\.?\\d+)|((?i)&H[0-9a-fA-F]+)|((?i)[a-z_]\\w*)/',
- 0 => '/((?i)\\()|((?i)")|((?i)\'|[Rr][Ee][Mm]\\b)|((?i)\\d*\\.?\\d+)|((?i)&H[0-9a-fA-F]+)|((?i)[a-z_]\\w*)/',
- 1 => '//',
- 2 => '/((?i)((https?|ftp):\\/\\/[\\w\\?\\.\\-\\&=\\/%+]+)|(^|[\\s,!?])www\\.\\w+\\.\\w+[\\w\\?\\.\\&=\\/%+]*)|((?i)\\w+[\\.\\w\\-]+@(\\w+[\\.\\w\\-])+)|((?i)\\b(note|fixme):)|((?i)\\$\\w+:.+\\$)/',
- );
- $this->_counts = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- ),
- 0 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 0,
- 4 => 0,
- 5 => 0,
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => 3,
- 1 => 1,
- 2 => 1,
- 3 => 0,
- ),
- );
- $this->_delim = array (
- -1 =>
- array (
- 0 => 'brackets',
- 1 => 'quotes',
- 2 => 'comment',
- 3 => '',
- 4 => '',
- 5 => '',
- ),
- 0 =>
- array (
- 0 => 'brackets',
- 1 => 'quotes',
- 2 => 'comment',
- 3 => '',
- 4 => '',
- 5 => '',
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => '',
- 1 => '',
- 2 => '',
- 3 => '',
- ),
- );
- $this->_inner = array (
- -1 =>
- array (
- 0 => 'code',
- 1 => 'string',
- 2 => 'comment',
- 3 => 'number',
- 4 => 'number',
- 5 => 'identifier',
- ),
- 0 =>
- array (
- 0 => 'code',
- 1 => 'string',
- 2 => 'comment',
- 3 => 'number',
- 4 => 'number',
- 5 => 'identifier',
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => 'url',
- 1 => 'url',
- 2 => 'inlinedoc',
- 3 => 'inlinedoc',
- ),
- );
- $this->_end = array (
- 0 => '/(?i)\\)/',
- 1 => '/(?i)"/',
- 2 => '/(?mi)$/',
- );
- $this->_states = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => -1,
- 4 => -1,
- 5 => -1,
- ),
- 0 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => -1,
- 4 => -1,
- 5 => -1,
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 => -1,
- ),
- );
- $this->_keywords = array (
- -1 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 =>
- array (
- ),
- 4 =>
- array (
- ),
- 5 =>
- array (
- 'constants' => '/^((?i)vbblack|vbred|vbgreen|vbyellow|vbblue|vbmagenta|vbcyan|vbwhite|vbbinarycompare|vbtextcompare|vbsunday|vbmonday|vbtuesday|vbwednesday|vbthursday|vbfriday|vbsaturday|vbusesystemdayofweek|vbfirstjan1|vbfirstfourdays|vbfirstfullweek|vbgeneraldate|vblongdate|vbshortdate|vblongtime|vbshorttime|vbobjecterror|vbokonly|vbokcancel|vbabortretryignore|vbyesnocancel|vbyesno|vbretrycancel|vbcritical|vbquestion|vbexclamation|vbinformation|vbdefaultbutton1|vbdefaultbutton2|vbdefaultbutton3|vbdefaultbutton4|vbapplicationmodal|vbsystemmodal|vbok|vbcancel|vbabort|vbretry|vbignore|vbyes|vbno|vbcr|vbcrlf|vbformfeed|vblf|vbnewline|vbnullchar|vbnullstring|vbtab|vbverticaltab|vbusedefault|vbtrue|vbfalse|vbempty|vbnull|vbinteger|vblong|vbsingle|vbdouble|vbcurrency|vbdate|vbstring|vbobject|vberror|vbboolean|vbvariant|vbdataobject|vbdecimal|vbbyte|vbarray)$/',
- 'functions' => '/^((?i)abs|array|asc|atn|cbool|cbyte|ccur|cdate|cdbl|chr|cint|clng|cos|createobject|csng|cstr|date|dateadd|datediff|datepart|dateserial|datevalue|day|escape|eval|exp|filter|formatcurrency|formatdatetime|formatnumber|formatpercent|getlocale|getobject|getref|hex|hour|inputbox|instr|instrrev|int|fix|isarray|isdate|isempty|isnull|isnumeric|isobject|join|lbound|lcase|left|len|loadpicture|log|ltrim|rtrim|trim|mid|minute|month|monthname|msgbox|now|oct|replace|rgb|right|rnd|round|scriptengine|scriptenginebuildversion|scriptenginemajorversion|scriptengineminorversion|second|setlocale|sgn|sin|space|split|sqr|strcomp|string|strreverse|tan|time|timer|timeserial|timevalue|typename|ubound|ucase|unescape|vartype|weekday|weekdayname|year)$/',
- 'builtin' => '/^((?i)debug|err|match|regexp)$/',
- 'reserved' => '/^((?i)empty|false|nothing|null|true|and|eqv|imp|is|mod|not|or|xor|call|class|end|const|public|private|dim|do|while|until|exit|loop|erase|execute|executeglobal|for|each|in|to|step|next|function|default|if|then|else|elseif|on|error|resume|goto|option|explicit|property|get|let|set|randomize|redim|preserve|select|case|stop|sub|wend|with)$/',
- ),
- ),
- 0 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 =>
- array (
- ),
- 4 =>
- array (
- ),
- 5 =>
- array (
- 'constants' => '/^((?i)vbblack|vbred|vbgreen|vbyellow|vbblue|vbmagenta|vbcyan|vbwhite|vbbinarycompare|vbtextcompare|vbsunday|vbmonday|vbtuesday|vbwednesday|vbthursday|vbfriday|vbsaturday|vbusesystemdayofweek|vbfirstjan1|vbfirstfourdays|vbfirstfullweek|vbgeneraldate|vblongdate|vbshortdate|vblongtime|vbshorttime|vbobjecterror|vbokonly|vbokcancel|vbabortretryignore|vbyesnocancel|vbyesno|vbretrycancel|vbcritical|vbquestion|vbexclamation|vbinformation|vbdefaultbutton1|vbdefaultbutton2|vbdefaultbutton3|vbdefaultbutton4|vbapplicationmodal|vbsystemmodal|vbok|vbcancel|vbabort|vbretry|vbignore|vbyes|vbno|vbcr|vbcrlf|vbformfeed|vblf|vbnewline|vbnullchar|vbnullstring|vbtab|vbverticaltab|vbusedefault|vbtrue|vbfalse|vbempty|vbnull|vbinteger|vblong|vbsingle|vbdouble|vbcurrency|vbdate|vbstring|vbobject|vberror|vbboolean|vbvariant|vbdataobject|vbdecimal|vbbyte|vbarray)$/',
- 'functions' => '/^((?i)abs|array|asc|atn|cbool|cbyte|ccur|cdate|cdbl|chr|cint|clng|cos|createobject|csng|cstr|date|dateadd|datediff|datepart|dateserial|datevalue|day|escape|eval|exp|filter|formatcurrency|formatdatetime|formatnumber|formatpercent|getlocale|getobject|getref|hex|hour|inputbox|instr|instrrev|int|fix|isarray|isdate|isempty|isnull|isnumeric|isobject|join|lbound|lcase|left|len|loadpicture|log|ltrim|rtrim|trim|mid|minute|month|monthname|msgbox|now|oct|replace|rgb|right|rnd|round|scriptengine|scriptenginebuildversion|scriptenginemajorversion|scriptengineminorversion|second|setlocale|sgn|sin|space|split|sqr|strcomp|string|strreverse|tan|time|timer|timeserial|timevalue|typename|ubound|ucase|unescape|vartype|weekday|weekdayname|year)$/',
- 'builtin' => '/^((?i)debug|err|match|regexp)$/',
- 'reserved' => '/^((?i)empty|false|nothing|null|true|and|eqv|imp|is|mod|not|or|xor|call|class|end|const|public|private|dim|do|while|until|exit|loop|erase|execute|executeglobal|for|each|in|to|step|next|function|default|if|then|else|elseif|on|error|resume|goto|option|explicit|property|get|let|set|randomize|redim|preserve|select|case|stop|sub|wend|with)$/',
- ),
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- ),
- 3 =>
- array (
- ),
- ),
- );
- $this->_parts = array (
- 0 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- 4 => NULL,
- 5 => NULL,
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- 3 => NULL,
- ),
- );
- $this->_subst = array (
- -1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- ),
- 0 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- 4 => false,
- 5 => false,
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- ),
- );
- $this->_conditions = array (
- );
- $this->_kwmap = array (
- 'constants' => 'builtin',
- 'functions' => 'builtin',
- 'builtin' => 'builtin',
- 'reserved' => 'reserved',
- );
- $this->_defClass = 'code';
- $this->_checkDefines();
- }
-
-}
diff --git a/library/Text_Highlighter/Text/Highlighter/XML.php b/library/Text_Highlighter/Text/Highlighter/XML.php
deleted file mode 100644
index 2d85db5fd..000000000
--- a/library/Text_Highlighter/Text/Highlighter/XML.php
+++ /dev/null
@@ -1,263 +0,0 @@
-<?php
-/**
- * Auto-generated class. XML syntax highlighting
- *
- * PHP version 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @link http://pear.php.net/package/Text_Highlighter
- * @category Text
- * @package Text_Highlighter
- * @version generated from: : xml.xml,v 1.1 2007/06/03 02:35:28 ssttoo Exp
- * @author Andrey Demenev <demenev@gmail.com>
- *
- */
-
-/**
- * @ignore
- */
-
-require_once 'Text/Highlighter.php';
-
-/**
- * Auto-generated class. XML syntax highlighting
- *
- * @author Andrey Demenev <demenev@gmail.com>
- * @category Text
- * @package Text_Highlighter
- * @copyright 2004-2006 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version Release: @package_version@
- * @link http://pear.php.net/package/Text_Highlighter
- */
-class Text_Highlighter_XML extends Text_Highlighter
-{
- var $_language = 'xml';
-
- /**
- * PHP4 Compatible Constructor
- *
- * @param array $options
- * @access public
- */
- function Text_Highlighter_XML($options=array())
- {
- $this->__construct($options);
- }
-
-
- /**
- * Constructor
- *
- * @param array $options
- * @access public
- */
- function __construct($options=array())
- {
-
- $this->_options = $options;
- $this->_regs = array (
- -1 => '/((?i)\\<\\!\\[CDATA\\[)|((?i)\\<!--)|((?i)\\<[\\?\\/]?)|((?i)(&|%)[\\w\\-\\.]+;)/',
- 0 => '//',
- 1 => '//',
- 2 => '/((?i)(?<=[\\<\\/?])[\\w\\-\\:]+)|((?i)[\\w\\-\\:]+)|((?i)")/',
- 3 => '/((?i)(&|%)[\\w\\-\\.]+;)/',
- );
- $this->_counts = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- 3 => 1,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => 0,
- 1 => 0,
- 2 => 0,
- ),
- 3 =>
- array (
- 0 => 1,
- ),
- );
- $this->_delim = array (
- -1 =>
- array (
- 0 => 'comment',
- 1 => 'comment',
- 2 => 'brackets',
- 3 => '',
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => '',
- 1 => '',
- 2 => 'quotes',
- ),
- 3 =>
- array (
- 0 => '',
- ),
- );
- $this->_inner = array (
- -1 =>
- array (
- 0 => 'comment',
- 1 => 'comment',
- 2 => 'code',
- 3 => 'special',
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => 'reserved',
- 1 => 'var',
- 2 => 'string',
- ),
- 3 =>
- array (
- 0 => 'special',
- ),
- );
- $this->_end = array (
- 0 => '/(?i)\\]\\]\\>/',
- 1 => '/(?i)--\\>/',
- 2 => '/(?i)[\\/\\?]?\\>/',
- 3 => '/(?i)"/',
- );
- $this->_states = array (
- -1 =>
- array (
- 0 => 0,
- 1 => 1,
- 2 => 2,
- 3 => -1,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => 3,
- ),
- 3 =>
- array (
- 0 => -1,
- ),
- );
- $this->_keywords = array (
- -1 =>
- array (
- 0 => -1,
- 1 => -1,
- 2 => -1,
- 3 =>
- array (
- ),
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 => -1,
- ),
- 3 =>
- array (
- 0 =>
- array (
- ),
- ),
- );
- $this->_parts = array (
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => NULL,
- 1 => NULL,
- 2 => NULL,
- ),
- 3 =>
- array (
- 0 => NULL,
- ),
- );
- $this->_subst = array (
- -1 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- 3 => false,
- ),
- 0 =>
- array (
- ),
- 1 =>
- array (
- ),
- 2 =>
- array (
- 0 => false,
- 1 => false,
- 2 => false,
- ),
- 3 =>
- array (
- 0 => false,
- ),
- );
- $this->_conditions = array (
- );
- $this->_kwmap = array (
- );
- $this->_defClass = 'code';
- $this->_checkDefines();
- }
-
-} \ No newline at end of file
diff --git a/library/Text_Highlighter/abap.xml b/library/Text_Highlighter/abap.xml
deleted file mode 100644
index 06d26e507..000000000
--- a/library/Text_Highlighter/abap.xml
+++ /dev/null
@@ -1,802 +0,0 @@
-<?xml version="1.0"?>
-<!-- $Id: abap.xml,v 1.1 2007-06-03 02:35:28 ssttoo Exp $ -->
-
-<highlight lang="abap" case = "no">
-
- <authors>
- <author name="Stoyan Stefanov" email ="ssttoo@gmail.com"/>
- </authors>
-
-
- <default innerClass="code" />
-
-
- <region name="block" delimClass="brackets" innerClass="code" start="\{" end="\}">
- <contains all="yes"/>
- </region>
-
- <region name="brackets" delimClass="brackets" innerClass="code" start="\(" end="\)">
- <contains all="yes"/>
- </region>
-
- <region name="sqbrackets" delimClass="brackets" innerClass="code" start="\[" end="\]">
- <contains all="yes"/>
- </region>
-
- <region name="comment" start="^\*|&quot;" end="/$/m" innerClass="comment">
- <contains all="no"/>
- </region>
-
- <region name="strsingle" delimClass="quotes" innerClass="string" start="'" end="'" />
-
- <block name="identifier" match="[a-zA-Z_]\w*" innerClass="identifier" contained="yes"/>
-
- <block name="hexinteger" match="0[xX][\da-f]+" innerClass="number" contained="yes"/>
-
- <block name="integer" match="\d\d*|\b0\b" innerClass="number" contained="yes"/>
-
- <block name="octinteger" match="0[0-7]+" innerClass="number" contained="yes"/>
-
- <block name="float" match="(\d*\.\d+)|(\d+\.\d*)" innerClass="number" contained="yes"/>
-
-
- <block name="identifier" match="[a-z_\-]\w*" innerClass="identifier" case="no"/>
-
- <keywords name="sy" inherits="identifier" innerClass="reserved">
- <keyword match="SCREEN-NAME"/>
- <keyword match="SCREEN-GROUP1"/>
- <keyword match="SCREEN-GROUP2"/>
- <keyword match="SCREEN-GROUP3"/>
- <keyword match="SCREEN-GROUP4"/>
- <keyword match="SCREEN-REQUIRED"/>
- <keyword match="SCREEN-INPUT"/>
- <keyword match="SCREEN-OUTPUT"/>
- <keyword match="SCREEN-INTENSIFIED"/>
- <keyword match="SCREEN-INVISIBLE"/>
- <keyword match="SCREEN-LENGTH"/>
- <keyword match="SCREEN-ACTIVE"/>
- <keyword match="SY-INDEX"/>
- <keyword match="SY-PAGNO"/>
- <keyword match="SY-TABIX"/>
- <keyword match="SY-TFILL"/>
- <keyword match="SY-TLOPC"/>
- <keyword match="SY-TMAXL"/>
- <keyword match="SY-TOCCU"/>
- <keyword match="SY-TTABC"/>
- <keyword match="SY-TSTIS"/>
- <keyword match="SY-TTABI"/>
- <keyword match="SY-DBCNT"/>
- <keyword match="SY-FDPOS"/>
- <keyword match="SY-COLNO"/>
- <keyword match="SY-LINCT"/>
- <keyword match="SY-LINNO"/>
- <keyword match="SY-LINSZ"/>
- <keyword match="SY-PAGCT"/>
- <keyword match="SY-MACOL"/>
- <keyword match="SY-MAROW"/>
- <keyword match="SY-TLENG"/>
- <keyword match="SY-SFOFF"/>
- <keyword match="SY-WILLI"/>
- <keyword match="SY-LILLI"/>
- <keyword match="SY-SUBRC"/>
- <keyword match="SY-FLENG"/>
- <keyword match="SY-CUCOL"/>
- <keyword match="SY-CUROW"/>
- <keyword match="SY-LSIND"/>
- <keyword match="SY-LISTI"/>
- <keyword match="SY-STEPL"/>
- <keyword match="SY-TPAGI"/>
- <keyword match="SY-WINX1"/>
- <keyword match="SY-WINY1"/>
- <keyword match="SY-WINX2"/>
- <keyword match="SY-WINY2"/>
- <keyword match="SY-WINCO"/>
- <keyword match="SY-WINRO"/>
- <keyword match="SY-WINDI"/>
- <keyword match="SY-SROWS"/>
- <keyword match="SY-SCOLS"/>
- <keyword match="SY-LOOPC"/>
- <keyword match="SY-FOLEN"/>
- <keyword match="SY-FODEC"/>
- <keyword match="SY-TZONE"/>
- <keyword match="SY-DAYST"/>
- <keyword match="SY-FTYPE"/>
- <keyword match="SY-APPLI"/>
- <keyword match="SY-FDAYW"/>
- <keyword match="SY-CCURS"/>
- <keyword match="SY-CCURT"/>
- <keyword match="SY-DEBUG"/>
- <keyword match="SY-CTYPE"/>
- <keyword match="SY-INPUT"/>
- <keyword match="SY-LANGU"/>
- <keyword match="SY-MODNO"/>
- <keyword match="SY-BATCH"/>
- <keyword match="SY-BINPT"/>
- <keyword match="SY-CALLD"/>
- <keyword match="SY-DYNNR"/>
- <keyword match="SY-DYNGR"/>
- <keyword match="SY-NEWPA"/>
- <keyword match="SY-PRI40"/>
- <keyword match="SY-RSTRT"/>
- <keyword match="SY-WTITL"/>
- <keyword match="SY-CPAGE"/>
- <keyword match="SY-DBNAM"/>
- <keyword match="SY-MANDT"/>
- <keyword match="SY-PREFX"/>
- <keyword match="SY-FMKEY"/>
- <keyword match="SY-PEXPI"/>
- <keyword match="SY-PRINI"/>
- <keyword match="SY-PRIMM"/>
- <keyword match="SY-PRREL"/>
- <keyword match="SY-PLAYO"/>
- <keyword match="SY-PRBIG"/>
- <keyword match="SY-PLAYP"/>
- <keyword match="SY-PRNEW"/>
- <keyword match="SY-PRLOG"/>
- <keyword match="SY-PDEST"/>
- <keyword match="SY-PLIST"/>
- <keyword match="SY-PAUTH"/>
- <keyword match="SY-PRDSN"/>
- <keyword match="SY-PNWPA"/>
- <keyword match="SY-CALLR"/>
- <keyword match="SY-REPI2"/>
- <keyword match="SY-RTITL"/>
- <keyword match="SY-PRREC"/>
- <keyword match="SY-PRTXT"/>
- <keyword match="SY-PRABT"/>
- <keyword match="SY-LPASS"/>
- <keyword match="SY-NRPAG"/>
- <keyword match="SY-PAART"/>
- <keyword match="SY-PRCOP"/>
- <keyword match="SY-BATZS"/>
- <keyword match="SY-BSPLD"/>
- <keyword match="SY-BREP4"/>
- <keyword match="SY-BATZO"/>
- <keyword match="SY-BATZD"/>
- <keyword match="SY-BATZW"/>
- <keyword match="SY-BATZM"/>
- <keyword match="SY-CTABL"/>
- <keyword match="SY-DBSYS"/>
- <keyword match="SY-DCSYS"/>
- <keyword match="SY-MACDB"/>
- <keyword match="SY-SYSID"/>
- <keyword match="SY-OPSYS"/>
- <keyword match="SY-PFKEY"/>
- <keyword match="SY-SAPRL"/>
- <keyword match="SY-TCODE"/>
- <keyword match="SY-UCOMM"/>
- <keyword match="SY-CFWAE"/>
- <keyword match="SY-CHWAE"/>
- <keyword match="SY-SPONO"/>
- <keyword match="SY-SPONR"/>
- <keyword match="SY-WAERS"/>
- <keyword match="SY-CDATE"/>
- <keyword match="SY-DATUM"/>
- <keyword match="SY-SLSET"/>
- <keyword match="SY-SUBTY"/>
- <keyword match="SY-SUBCS"/>
- <keyword match="SY-GROUP"/>
- <keyword match="SY-FFILE"/>
- <keyword match="SY-UZEIT"/>
- <keyword match="SY-DSNAM"/>
- <keyword match="SY-REPID"/>
- <keyword match="SY-TABID"/>
- <keyword match="SY-TFDSN"/>
- <keyword match="SY-UNAME"/>
- <keyword match="SY-LSTAT"/>
- <keyword match="SY-ABCDE"/>
- <keyword match="SY-MARKY"/>
- <keyword match="SY-SFNAM"/>
- <keyword match="SY-TNAME"/>
- <keyword match="SY-MSGLI"/>
- <keyword match="SY-TITLE"/>
- <keyword match="SY-ENTRY"/>
- <keyword match="SY-LISEL"/>
- <keyword match="SY-ULINE"/>
- <keyword match="SY-XCODE"/>
- <keyword match="SY-CPROG"/>
- <keyword match="SY-XPROG"/>
- <keyword match="SY-XFORM"/>
- <keyword match="SY-LDBPG"/>
- <keyword match="SY-TVAR0"/>
- <keyword match="SY-TVAR1"/>
- <keyword match="SY-TVAR2"/>
- <keyword match="SY-TVAR3"/>
- <keyword match="SY-TVAR4"/>
- <keyword match="SY-TVAR5"/>
- <keyword match="SY-TVAR6"/>
- <keyword match="SY-TVAR7"/>
- <keyword match="SY-TVAR8"/>
- <keyword match="SY-TVAR9"/>
- <keyword match="SY-MSGID"/>
- <keyword match="SY-MSGTY"/>
- <keyword match="SY-MSGNO"/>
- <keyword match="SY-MSGV1"/>
- <keyword match="SY-MSGV2"/>
- <keyword match="SY-MSGV3"/>
- <keyword match="SY-MSGV4"/>
- <keyword match="SY-ONCOM"/>
- <keyword match="SY-VLINE"/>
- <keyword match="SY-WINSL"/>
- <keyword match="SY-STACO"/>
- <keyword match="SY-STARO"/>
- <keyword match="SY-DATAR"/>
- <keyword match="SY-HOST"/>
- <keyword match="SY-LOCDB"/>
- <keyword match="SY-LOCOP"/>
- <keyword match="SY-DATLO"/>
- <keyword match="SY-TIMLO"/>
- <keyword match="SY-ZONLO"/>
- <keyword match="SYST-INDEX"/>
- <keyword match="SYST-PAGNO"/>
- <keyword match="SYST-TABIX"/>
- <keyword match="SYST-TFILL"/>
- <keyword match="SYST-TLOPC"/>
- <keyword match="SYST-TMAXL"/>
- <keyword match="SYST-TOCCU"/>
- <keyword match="SYST-TTABC"/>
- <keyword match="SYST-TSTIS"/>
- <keyword match="SYST-TTABI"/>
- <keyword match="SYST-DBCNT"/>
- <keyword match="SYST-FDPOS"/>
- <keyword match="SYST-COLNO"/>
- <keyword match="SYST-LINCT"/>
- <keyword match="SYST-LINNO"/>
- <keyword match="SYST-LINSZ"/>
- <keyword match="SYST-PAGCT"/>
- <keyword match="SYST-MACOL"/>
- <keyword match="SYST-MAROW"/>
- <keyword match="SYST-TLENG"/>
- <keyword match="SYST-SFOFF"/>
- <keyword match="SYST-WILLI"/>
- <keyword match="SYST-LILLI"/>
- <keyword match="SYST-SUBRC"/>
- <keyword match="SYST-FLENG"/>
- <keyword match="SYST-CUCOL"/>
- <keyword match="SYST-CUROW"/>
- <keyword match="SYST-LSIND"/>
- <keyword match="SYST-LISTI"/>
- <keyword match="SYST-STEPL"/>
- <keyword match="SYST-TPAGI"/>
- <keyword match="SYST-WINX1"/>
- <keyword match="SYST-WINY1"/>
- <keyword match="SYST-WINX2"/>
- <keyword match="SYST-WINY2"/>
- <keyword match="SYST-WINCO"/>
- <keyword match="SYST-WINRO"/>
- <keyword match="SYST-WINDI"/>
- <keyword match="SYST-SROWS"/>
- <keyword match="SYST-SCOLS"/>
- <keyword match="SYST-LOOPC"/>
- <keyword match="SYST-FOLEN"/>
- <keyword match="SYST-FODEC"/>
- <keyword match="SYST-TZONE"/>
- <keyword match="SYST-DAYST"/>
- <keyword match="SYST-FTYPE"/>
- <keyword match="SYST-APPLI"/>
- <keyword match="SYST-FDAYW"/>
- <keyword match="SYST-CCURS"/>
- <keyword match="SYST-CCURT"/>
- <keyword match="SYST-DEBUG"/>
- <keyword match="SYST-CTYPE"/>
- <keyword match="SYST-INPUT"/>
- <keyword match="SYST-LANGU"/>
- <keyword match="SYST-MODNO"/>
- <keyword match="SYST-BATCH"/>
- <keyword match="SYST-BINPT"/>
- <keyword match="SYST-CALLD"/>
- <keyword match="SYST-DYNNR"/>
- <keyword match="SYST-DYNGR"/>
- <keyword match="SYST-NEWPA"/>
- <keyword match="SYST-PRI40"/>
- <keyword match="SYST-RSTRT"/>
- <keyword match="SYST-WTITL"/>
- <keyword match="SYST-CPAGE"/>
- <keyword match="SYST-DBNAM"/>
- <keyword match="SYST-MANDT"/>
- <keyword match="SYST-PREFX"/>
- <keyword match="SYST-FMKEY"/>
- <keyword match="SYST-PEXPI"/>
- <keyword match="SYST-PRINI"/>
- <keyword match="SYST-PRIMM"/>
- <keyword match="SYST-PRREL"/>
- <keyword match="SYST-PLAYO"/>
- <keyword match="SYST-PRBIG"/>
- <keyword match="SYST-PLAYP"/>
- <keyword match="SYST-PRNEW"/>
- <keyword match="SYST-PRLOG"/>
- <keyword match="SYST-PDEST"/>
- <keyword match="SYST-PLIST"/>
- <keyword match="SYST-PAUTH"/>
- <keyword match="SYST-PRDSN"/>
- <keyword match="SYST-PNWPA"/>
- <keyword match="SYST-CALLR"/>
- <keyword match="SYST-REPI2"/>
- <keyword match="SYST-RTITL"/>
- <keyword match="SYST-PRREC"/>
- <keyword match="SYST-PRTXT"/>
- <keyword match="SYST-PRABT"/>
- <keyword match="SYST-LPASS"/>
- <keyword match="SYST-NRPAG"/>
- <keyword match="SYST-PAART"/>
- <keyword match="SYST-PRCOP"/>
- <keyword match="SYST-BATZS"/>
- <keyword match="SYST-BSPLD"/>
- <keyword match="SYST-BREP4"/>
- <keyword match="SYST-BATZO"/>
- <keyword match="SYST-BATZD"/>
- <keyword match="SYST-BATZW"/>
- <keyword match="SYST-BATZM"/>
- <keyword match="SYST-CTABL"/>
- <keyword match="SYST-DBSYS"/>
- <keyword match="SYST-DCSYS"/>
- <keyword match="SYST-MACDB"/>
- <keyword match="SYST-SYSID"/>
- <keyword match="SYST-OPSYS"/>
- <keyword match="SYST-PFKEY"/>
- <keyword match="SYST-SAPRL"/>
- <keyword match="SYST-TCODE"/>
- <keyword match="SYST-UCOMM"/>
- <keyword match="SYST-CFWAE"/>
- <keyword match="SYST-CHWAE"/>
- <keyword match="SYST-SPONO"/>
- <keyword match="SYST-SPONR"/>
- <keyword match="SYST-WAERS"/>
- <keyword match="SYST-CDATE"/>
- <keyword match="SYST-DATUM"/>
- <keyword match="SYST-SLSET"/>
- <keyword match="SYST-SUBTY"/>
- <keyword match="SYST-SUBCS"/>
- <keyword match="SYST-GROUP"/>
- <keyword match="SYST-FFILE"/>
- <keyword match="SYST-UZEIT"/>
- <keyword match="SYST-DSNAM"/>
- <keyword match="SYST-REPID"/>
- <keyword match="SYST-TABID"/>
- <keyword match="SYST-TFDSN"/>
- <keyword match="SYST-UNAME"/>
- <keyword match="SYST-LSTAT"/>
- <keyword match="SYST-ABCDE"/>
- <keyword match="SYST-MARKY"/>
- <keyword match="SYST-SFNAM"/>
- <keyword match="SYST-TNAME"/>
- <keyword match="SYST-MSGLI"/>
- <keyword match="SYST-TITLE"/>
- <keyword match="SYST-ENTRY"/>
- <keyword match="SYST-LISEL"/>
- <keyword match="SYST-ULINE"/>
- <keyword match="SYST-XCODE"/>
- <keyword match="SYST-CPROG"/>
- <keyword match="SYST-XPROG"/>
- <keyword match="SYST-XFORM"/>
- <keyword match="SYST-LDBPG"/>
- <keyword match="SYST-TVAR0"/>
- <keyword match="SYST-TVAR1"/>
- <keyword match="SYST-TVAR2"/>
- <keyword match="SYST-TVAR3"/>
- <keyword match="SYST-TVAR4"/>
- <keyword match="SYST-TVAR5"/>
- <keyword match="SYST-TVAR6"/>
- <keyword match="SYST-TVAR7"/>
- <keyword match="SYST-TVAR8"/>
- <keyword match="SYST-TVAR9"/>
- <keyword match="SYST-MSGID"/>
- <keyword match="SYST-MSGTY"/>
- <keyword match="SYST-MSGNO"/>
- <keyword match="SYST-MSGV1"/>
- <keyword match="SYST-MSGV2"/>
- <keyword match="SYST-MSGV3"/>
- <keyword match="SYST-MSGV4"/>
- <keyword match="SYST-ONCOM"/>
- <keyword match="SYST-VLINE"/>
- <keyword match="SYST-WINSL"/>
- <keyword match="SYST-STACO"/>
- <keyword match="SYST-STARO"/>
- <keyword match="SYST-DATAR"/>
- <keyword match="SYST-HOST"/>
- <keyword match="SYST-LOCDB"/>
- <keyword match="SYST-LOCOP"/>
- <keyword match="SYST-DATLO"/>
- <keyword match="SYST-TIMLO"/>
- <keyword match="SYST-ZONLO"/>
- </keywords>
-
-
- <keywords name="reserved" inherits="identifier" innerClass="reserved">
- <keyword match="ABS"/>
- <keyword match="ACOS"/>
- <keyword match="ADD"/>
- <keyword match="ADD-CORRESPONDING"/>
- <keyword match="ADJACENT"/>
- <keyword match="AFTER"/>
- <keyword match="ALIASES"/>
- <keyword match="ALL"/>
- <keyword match="ANALYZER"/>
- <keyword match="AND"/>
- <keyword match="ANY"/>
- <keyword match="APPEND"/>
- <keyword match="AS"/>
- <keyword match="ASCENDING"/>
- <keyword match="ASIN"/>
- <keyword match="ASSIGN"/>
- <keyword match="ASSIGNED"/>
- <keyword match="ASSIGNING"/>
- <keyword match="AT"/>
- <keyword match="ATAN"/>
- <keyword match="AUTHORITY-CHECK"/>
- <keyword match="AVG"/>
- <keyword match="BACK"/>
- <keyword match="BEFORE"/>
- <keyword match="BEGIN"/>
- <keyword match="BINARY"/>
- <keyword match="BIT"/>
- <keyword match="BIT-AND"/>
- <keyword match="BIT-NOT"/>
- <keyword match="BIT-OR"/>
- <keyword match="BIT-XOR"/>
- <keyword match="BLANK"/>
- <keyword match="BLOCK"/>
- <keyword match="BREAK-POINT"/>
- <keyword match="BUFFER"/>
- <keyword match="BY"/>
- <keyword match="C"/>
- <keyword match="CALL"/>
- <keyword match="CASE"/>
- <keyword match="CATCH"/>
- <keyword match="CEIL"/>
- <keyword match="CENTERED"/>
- <keyword match="CHAIN"/>
- <keyword match="CHANGE"/>
- <keyword match="CHANGING"/>
- <keyword match="CHECK"/>
- <keyword match="CHECKBOX"/>
- <keyword match="CLASS"/>
- <keyword match="CLASS-DATA"/>
- <keyword match="CLASS-EVENTS"/>
- <keyword match="CLASS-METHODS"/>
- <keyword match="CLASS-POOL"/>
- <keyword match="CLEAR"/>
- <keyword match="CLIENT"/>
- <keyword match="CLOSE"/>
- <keyword match="CNT"/>
- <keyword match="CODE"/>
- <keyword match="COLLECT"/>
- <keyword match="COLOR"/>
- <keyword match="COMMENT"/>
- <keyword match="COMMIT"/>
- <keyword match="COMMUNICATION"/>
- <keyword match="COMPUTE"/>
- <keyword match="CONCATENATE"/>
- <keyword match="CONDENSE"/>
- <keyword match="CONSTANTS"/>
- <keyword match="CONTEXT"/>
- <keyword match="CONTEXTS"/>
- <keyword match="CONTINUE"/>
- <keyword match="CONTROL"/>
- <keyword match="CONTROLS"/>
- <keyword match="CONVERT"/>
- <keyword match="COPY"/>
- <keyword match="CORRESPONDING"/>
- <keyword match="COS"/>
- <keyword match="COSH"/>
- <keyword match="COUNT"/>
- <keyword match="COUNTRY"/>
- <keyword match="CREATE"/>
- <keyword match="CURRENCY"/>
- <keyword match="CURSOR"/>
- <keyword match="CUSTOMER-FUNCTION"/>
- <keyword match="DATA"/>
- <keyword match="DATABASE"/>
- <keyword match="DATASET"/>
- <keyword match="DELETE"/>
- <keyword match="DECIMALS"/>
- <keyword match="DEFAULT"/>
- <keyword match="DEFINE"/>
- <keyword match="DELETE"/>
- <keyword match="DEMAND"/>
- <keyword match="DESCENDING"/>
- <keyword match="DESCRIBE"/>
- <keyword match="DIALOG"/>
- <keyword match="DISTINCT"/>
- <keyword match="DIV"/>
- <keyword match="DIVIDE"/>
- <keyword match="DIVIDE-CORRESPONDING"/>
- <keyword match="DO"/>
- <keyword match="DUPLICATES"/>
- <keyword match="DYNPRO"/>
- <keyword match="EDIT"/>
- <keyword match="EDITOR-CALL"/>
- <keyword match="ELSE"/>
- <keyword match="ELSEIF"/>
- <keyword match="END"/>
- <keyword match="END-OF-DEFINITION"/>
- <keyword match="END-OF-PAGE"/>
- <keyword match="END-OF-SELECTION"/>
- <keyword match="ENDAT"/>
- <keyword match="ENDCASE"/>
- <keyword match="ENDCATCH"/>
- <keyword match="ENDCHAIN"/>
- <keyword match="ENDCLASS"/>
- <keyword match="ENDDO"/>
- <keyword match="ENDEXEC"/>
- <keyword match="ENDFORM"/>
- <keyword match="ENDFUNCTION"/>
- <keyword match="ENDIF"/>
- <keyword match="ENDINTERFACE"/>
- <keyword match="ENDLOOP"/>
- <keyword match="ENDMETHOD"/>
- <keyword match="ENDMODULE"/>
- <keyword match="ENDON"/>
- <keyword match="ENDPROVIDE"/>
- <keyword match="ENDSELECT"/>
- <keyword match="ENDWHILE"/>
- <keyword match="ENTRIES"/>
- <keyword match="EVENTS"/>
- <keyword match="EXEC"/>
- <keyword match="EXIT"/>
- <keyword match="EXIT-COMMAND"/>
- <keyword match="EXP"/>
- <keyword match="EXPONENT"/>
- <keyword match="EXPORT"/>
- <keyword match="EXPORTING"/>
- <keyword match="EXCEPTIONS"/>
- <keyword match="EXTENDED"/>
- <keyword match="EXTRACT"/>
- <keyword match="FETCH"/>
- <keyword match="FIELD"/>
- <keyword match="FIELD-GROUPS"/>
- <keyword match="FIELD-SYMBOLS"/>
- <keyword match="FIELDS"/>
- <keyword match="FLOOR"/>
- <keyword match="FOR"/>
- <keyword match="FORM"/>
- <keyword match="FORMAT"/>
- <keyword match="FRAC"/>
- <keyword match="FRAME"/>
- <keyword match="FREE"/>
- <keyword match="FROM"/>
- <keyword match="FUNCTION"/>
- <keyword match="FUNCTION-POOL"/>
- <keyword match="GENERATE"/>
- <keyword match="GET"/>
- <keyword match="GROUP"/>
- <keyword match="HASHED"/>
- <keyword match="HEADER"/>
- <keyword match="HELP-ID"/>
- <keyword match="HELP-REQUEST"/>
- <keyword match="HIDE"/>
- <keyword match="HOTSPOT"/>
- <keyword match="ICON"/>
- <keyword match="ID"/>
- <keyword match="IF"/>
- <keyword match="IMPORT"/>
- <keyword match="IMPORTING"/>
- <keyword match="INCLUDE"/>
- <keyword match="INDEX"/>
- <keyword match="INFOTYPES"/>
- <keyword match="INITIALIZATION"/>
- <keyword match="INNER"/>
- <keyword match="INPUT"/>
- <keyword match="INSERT"/>
- <keyword match="INTENSIFIED"/>
- <keyword match="INTERFACE"/>
- <keyword match="INTERFACE-POOL"/>
- <keyword match="INTERFACES"/>
- <keyword match="INTO"/>
- <keyword match="INVERSE"/>
- <keyword match="JOIN"/>
- <keyword match="KEY"/>
- <keyword match="LANGUAGE"/>
- <keyword match="LAST"/>
- <keyword match="LEAVE"/>
- <keyword match="LEFT"/>
- <keyword match="LEFT-JUSTIFIED"/>
- <keyword match="LIKE"/>
- <keyword match="LINE"/>
- <keyword match="LINE-COUNT"/>
- <keyword match="LINE-SELECTION"/>
- <keyword match="LINE-SIZE"/>
- <keyword match="LINES"/>
- <keyword match="LIST-PROCESSING"/>
- <keyword match="LOAD"/>
- <keyword match="LOAD-OF-PROGRAM"/>
- <keyword match="LOCAL"/>
- <keyword match="LOCALE"/>
- <keyword match="LOG"/>
- <keyword match="LOG10"/>
- <keyword match="LOOP"/>
- <keyword match="M"/>
- <keyword match="MARGIN"/>
- <keyword match="MASK"/>
- <keyword match="MATCHCODE"/>
- <keyword match="MAX"/>
- <keyword match="MEMORY"/>
- <keyword match="MESSAGE"/>
- <keyword match="MESSAGE-ID"/>
- <keyword match="MESSAGES"/>
- <keyword match="METHOD"/>
- <keyword match="METHODS"/>
- <keyword match="MIN"/>
- <keyword match="MOD"/>
- <keyword match="MODE"/>
- <keyword match="MODIF"/>
- <keyword match="MODIFY"/>
- <keyword match="MODULE"/>
- <keyword match="MOVE"/>
- <keyword match="MOVE-CORRESPONDING"/>
- <keyword match="MULTIPLY"/>
- <keyword match="MULTIPLY-CORRESPONDING"/>
- <keyword match="NEW"/>
- <keyword match="NEW-LINE"/>
- <keyword match="NEW-PAGE"/>
- <keyword match="NEXT"/>
- <keyword match="NO"/>
- <keyword match="NO-GAP"/>
- <keyword match="NO-GAPS"/>
- <keyword match="NO-HEADING"/>
- <keyword match="NO-SCROLLING"/>
- <keyword match="NO-SIGN"/>
- <keyword match="NO-TITLE"/>
- <keyword match="NO-ZERO"/>
- <keyword match="NODES"/>
- <keyword match="NON-UNIQUE"/>
- <keyword match="O"/>
- <keyword match="OBJECT"/>
- <keyword match="OBLIGATORY"/>
- <keyword match="OCCURS"/>
- <keyword match="OF"/>
- <keyword match="OFF"/>
- <keyword match="ON"/>
- <keyword match="OPEN"/>
- <keyword match="OR"/>
- <keyword match="ORDER"/>
- <keyword match="OTHERS"/>
- <keyword match="OUTER"/>
- <keyword match="OUTPUT"/>
- <keyword match="OVERLAY"/>
- <keyword match="PACK"/>
- <keyword match="PAGE"/>
- <keyword match="PARAMETER"/>
- <keyword match="PARAMETERS"/>
- <keyword match="PERFORM"/>
- <keyword match="PF-STATUS"/>
- <keyword match="POSITION"/>
- <keyword match="PRINT"/>
- <keyword match="PRINT-CONTROL"/>
- <keyword match="PRIVATE"/>
- <keyword match="PROCESS"/>
- <keyword match="PROGRAM"/>
- <keyword match="PROPERTY"/>
- <keyword match="PROTECTED"/>
- <keyword match="PROVIDE"/>
- <keyword match="PUBLIC"/>
- <keyword match="PUT"/>
- <keyword match="RADIOBUTTON"/>
- <keyword match="RAISE"/>
- <keyword match="RAISING"/>
- <keyword match="RANGE"/>
- <keyword match="RANGES"/>
- <keyword match="READ"/>
- <keyword match="RECEIVE"/>
- <keyword match="REFRESH"/>
- <keyword match="REJECT"/>
- <keyword match="REPLACE"/>
- <keyword match="REPORT"/>
- <keyword match="REQUESTED"/>
- <keyword match="RESERVE"/>
- <keyword match="RESET"/>
- <keyword match="RIGHT-JUSTIFIED"/>
- <keyword match="ROLLBACK"/>
- <keyword match="ROUND"/>
- <keyword match="ROWS"/>
- <keyword match="RTTI"/>
- <keyword match="RUN"/>
- <keyword match="SCAN"/>
- <keyword match="SCREEN"/>
- <keyword match="SEARCH"/>
- <keyword match="SEPARATED"/>
- <keyword match="SCROLL"/>
- <keyword match="SCROLL-BOUNDARY"/>
- <keyword match="SEARCH"/>
- <keyword match="SELECT"/>
- <keyword match="SELECT-OPTIONS"/>
- <keyword match="SELECTION-SCREEN"/>
- <keyword match="SELECTION-TABLE"/>
- <keyword match="SET"/>
- <keyword match="SHARED"/>
- <keyword match="SHIFT"/>
- <keyword match="SIGN"/>
- <keyword match="SIN"/>
- <keyword match="SINGLE"/>
- <keyword match="SINH"/>
- <keyword match="SIZE"/>
- <keyword match="SKIP"/>
- <keyword match="SORT"/>
- <keyword match="SORTED"/>
- <keyword match="SPLIT"/>
- <keyword match="SQL"/>
- <keyword match="SQRT"/>
- <keyword match="STAMP"/>
- <keyword match="STANDARD"/>
- <keyword match="START-OF-SELECTION"/>
- <keyword match="STATICS"/>
- <keyword match="STOP"/>
- <keyword match="STRING"/>
- <keyword match="STRLEN"/>
- <keyword match="STRUCTURE"/>
- <keyword match="SUBMIT"/>
- <keyword match="SUBTRACT"/>
- <keyword match="SUBTRACT-CORRESPONDING"/>
- <keyword match="SUM"/>
- <keyword match="SUPPLY"/>
- <keyword match="SUPPRESS"/>
- <keyword match="SYMBOL"/>
- <keyword match="SYNTAX-CHECK"/>
- <keyword match="SYNTAX-TRACE"/>
- <keyword match="SYSTEM-CALL"/>
- <keyword match="SYSTEM-EXCEPTIONS"/>
- <keyword match="TABLE"/>
- <keyword match="TABLE_LINE"/>
- <keyword match="TABLES"/>
- <keyword match="TAN"/>
- <keyword match="TANH"/>
- <keyword match="TEXT"/>
- <keyword match="TEXTPOOL"/>
- <keyword match="TIME"/>
- <keyword match="TIMES"/>
- <keyword match="TITLE"/>
- <keyword match="TITLEBAR"/>
- <keyword match="TO"/>
- <keyword match="TOP-OF-PAGE"/>
- <keyword match="TRANSACTION"/>
- <keyword match="TRANSFER"/>
- <keyword match="TRANSLATE"/>
- <keyword match="TRANSPORTING"/>
- <keyword match="TRUNC"/>
- <keyword match="TYPE"/>
- <keyword match="TYPE-POOL"/>
- <keyword match="TYPE-POOLS"/>
- <keyword match="TYPES"/>
- <keyword match="ULINE"/>
- <keyword match="UNDER"/>
- <keyword match="UNIQUE"/>
- <keyword match="UNIT"/>
- <keyword match="UNPACK"/>
- <keyword match="UP"/>
- <keyword match="UPDATE"/>
- <keyword match="USER-COMMAND"/>
- <keyword match="USING"/>
- <keyword match="VALUE"/>
- <keyword match="VALUE-REQUEST"/>
- <keyword match="VALUES"/>
- <keyword match="VARY"/>
- <keyword match="WHEN"/>
- <keyword match="WHERE"/>
- <keyword match="WHILE"/>
- <keyword match="WINDOW"/>
- <keyword match="WITH"/>
- <keyword match="WITH-TITLE"/>
- <keyword match="WORK"/>
- <keyword match="WRITE"/>
- <keyword match="X"/>
- <keyword match="XSTRING"/>
- <keyword match="Z"/>
- <keyword match="ZONE"/>
- </keywords>
-
-
- <keywords name="constants" inherits="identifier" innerClass="reserved">
- <keyword match="INITIAL"/>
- <keyword match="NULL"/>
- <keyword match="SPACE"/>
- <keyword match="COL_BACKGROUND"/>
- <keyword match="COL_HEADING"/>
- <keyword match="COL_NORMAL"/>
- <keyword match="COL_TOTAL"/>
- <keyword match="COL_KEY"/>
- <keyword match="COL_POSITIVE"/>
- <keyword match="COL_NEGATIVE"/>
- <keyword match="COL_GROUP"/>
- </keywords>
-
-</highlight>
diff --git a/library/Text_Highlighter/avrc.xml b/library/Text_Highlighter/avrc.xml
deleted file mode 100644
index dec571e13..000000000
--- a/library/Text_Highlighter/avrc.xml
+++ /dev/null
@@ -1,316 +0,0 @@
-<?xml version="1.0"?>
-<!-- $Id: avrc.xml,v 1.1 2008-07-31 23:05:38 ssttoo Exp $ -->
-
-<highlight lang="AVRC" case="no">
-
- <authors>
- <author name="Andrey Demenev" email="demenev@gmail.com"/>
- </authors>
-
- <comment>
- C/C++ highlighter specific to Atmel AVR microcontrollers
- </comment>
-
- <default innerClass="code" />
-
- <block name="escaped" match="\\" innerClass="special" contained="yes">
- <onlyin region="strdouble"/>
- </block>
-
- <region name="strdouble" delimClass="quotes" innerClass="string" start="&quot;" end="&quot;"/>
-
- <region name="block" delimClass="brackets" innerClass="code" start="\{" end="\}">
- <contains all="yes"/>
- </region>
-
- <region name="brackets" delimClass="brackets" innerClass="code" start="\(" end="\)">
- <contains all="yes"/>
- </region>
-
- <region name="sqbrackets" delimClass="brackets" innerClass="code" start="\[" end="\]">
- <contains all="yes"/>
- </region>
-
- <block name="identifier" match="[a-z_]\w*" innerClass="identifier" case="no"/>
-
- <block name="hexinteger" match="\b0[xX][\da-f]+" innerClass="number"/>
- <block name="integer" match="\b\d\d*|\b0\b" innerClass="number"/>
- <block name="octinteger" match="\b0[0-7]+" innerClass="number"/>
- <block name="float" match="\b(\d*\.\d+)|(\d+\.\d*)" innerClass="number"/>
-
-
- <region name="strincl" delimClass="quotes" innerClass="string" start="&lt;" end="&gt;">
- <onlyin region="include" />
- </region>
-
- <!-- <block name="preprocessor" match="^#[azAZ_]\w*" innerClass="prepro"/> -->
- <region name="include" innerClass="prepro" start="/^[ \t]*#include/m" end="/(?&lt;!\\)$/m">
- <contains region="strdouble"/>
- <contains region="strincl"/>
- </region>
-
- <region name="preprocessor" delimClass="prepro" innerClass="code" start="/^[ \t]*#[ \t]*[a-z]+/mi" end="/(?&lt;!\\)$/m">
- <contains region="comment"/>
- <contains region="mlcomment"/>
- <contains region="strdouble"/>
- <contains region="brackets"/>
- <contains region="block"/>
- <contains block="identifier"/>
- <contains block="integer"/>
- <contains block="hexinteger"/>
- <contains block="octinteger"/>
- <contains block="float"/>
-
- </region>
-
- <block name="number" match="\d*\.?\d+" innerClass="number"/>
-
-
- <region name="mlcomment" innerClass="mlcomment" start="\/\*" end="\*\/" >
- <contains block="cvstag"/>
- </region>
-
- <block name="cvstag" match="\$\w+\s*:.+\$" innerClass="inlinedoc">
-
- <onlyin region="mlcomment"/>
- <onlyin region="comment"/>
- </block>
-
- <region name="comment" start="\/\/.+" end="/$/m" innerClass="comment" delimClass="comment">
- <contains block="cvstag"/>
- </region>
-
- <keywords name="reserved" inherits="identifier" innerClass="reserved" case="yes">
- <keyword match="and" />
- <keyword match="and_eq" />
- <keyword match="asm" />
-
- <keyword match="bitand" />
- <keyword match="bitor" />
- <keyword match="break" />
- <keyword match="case" />
- <keyword match="catch" />
- <keyword match="compl" />
-
- <keyword match="const_cast" />
- <keyword match="continue" />
- <keyword match="default" />
- <keyword match="delete" />
- <keyword match="do" />
- <keyword match="dynamic_cast" />
-
- <keyword match="else" />
- <keyword match="for" />
- <keyword match="fortran" />
- <keyword match="friend" />
- <keyword match="goto" />
- <keyword match="if" />
-
- <keyword match="new" />
- <keyword match="not" />
- <keyword match="not_eq" />
- <keyword match="operator" />
- <keyword match="or" />
- <keyword match="or_eq" />
-
- <keyword match="private" />
- <keyword match="protected" />
- <keyword match="public" />
- <keyword match="reinterpret_cast" />
- <keyword match="return" />
- <keyword match="sizeof" />
-
- <keyword match="static_cast" />
- <keyword match="switch" />
- <keyword match="this" />
- <keyword match="throw" />
- <keyword match="try" />
- <keyword match="typeid" />
-
- <keyword match="using" />
- <keyword match="while" />
- <keyword match="xor" />
- <keyword match="xor_eq" />
-
- <keyword match="false" />
- <keyword match="true" />
- </keywords>
-
- <keywords name="registers" inherits="identifier" innerClass="reserved" case="yes">
- <keyword match="ACSR" />
- <keyword match="ADCH" />
- <keyword match="ADCL" />
- <keyword match="ADCSRA" />
- <keyword match="ADMUX" />
- <keyword match="ASSR" />
- <keyword match="DDRA" />
- <keyword match="DDRB" />
- <keyword match="DDRC" />
- <keyword match="DDRD" />
- <keyword match="DDRE" />
- <keyword match="DDRF" />
- <keyword match="DDRG" />
- <keyword match="EEARH" />
- <keyword match="EEARL" />
- <keyword match="EECR" />
- <keyword match="EEDR" />
- <keyword match="EICRA" />
- <keyword match="EICRB" />
- <keyword match="EIFR" />
- <keyword match="EIMSK" />
- <keyword match="ETIFR" />
- <keyword match="ETIMSK" />
- <keyword match="GICR" />
- <keyword match="GIFR" />
- <keyword match="ICR1H" />
- <keyword match="ICR1L" />
- <keyword match="ICR3H" />
- <keyword match="ICR3L" />
- <keyword match="MCUCR" />
- <keyword match="MCUCSR" />
- <keyword match="OCDR" />
- <keyword match="OCR0" />
- <keyword match="OCR1AH" />
- <keyword match="OCR1AL" />
- <keyword match="OCR1BH" />
- <keyword match="OCR1BL" />
- <keyword match="OCR1CH" />
- <keyword match="OCR1CL" />
- <keyword match="OCR2" />
- <keyword match="OCR3AH" />
- <keyword match="OCR3AL" />
- <keyword match="OCR3BH" />
- <keyword match="OCR3BL" />
- <keyword match="OCR3CH" />
- <keyword match="OCR3CL" />
- <keyword match="OSCCAL" />
- <keyword match="PINA" />
- <keyword match="PINB" />
- <keyword match="PINC" />
- <keyword match="PIND" />
- <keyword match="PINE" />
- <keyword match="PINF" />
- <keyword match="PING" />
- <keyword match="PORTA" />
- <keyword match="PORTB" />
- <keyword match="PORTC" />
- <keyword match="PORTD" />
- <keyword match="PORTE" />
- <keyword match="PORTF" />
- <keyword match="PORTG" />
- <keyword match="RAMPZ" />
- <keyword match="SFIOR" />
- <keyword match="SPCR" />
- <keyword match="SPDR" />
- <keyword match="SPH" />
- <keyword match="SPL" />
- <keyword match="SPMCR" />
- <keyword match="SPMCSR" />
- <keyword match="SPSR" />
- <keyword match="SREG" />
- <keyword match="TCCR0" />
- <keyword match="TCCR1A" />
- <keyword match="TCCR1B" />
- <keyword match="TCCR1C" />
- <keyword match="TCCR2" />
- <keyword match="TCCR3A" />
- <keyword match="TCCR3B" />
- <keyword match="TCCR3C" />
- <keyword match="TCNT0" />
- <keyword match="TCNT1H" />
- <keyword match="TCNT1L" />
- <keyword match="TCNT2" />
- <keyword match="TCNT3H" />
- <keyword match="TCNT3L" />
- <keyword match="TIFR" />
- <keyword match="TIMSK" />
- <keyword match="TWAR" />
- <keyword match="TWBR" />
- <keyword match="TWCR" />
- <keyword match="TWDR" />
- <keyword match="TWSR" />
- <keyword match="UBRR0H" />
- <keyword match="UBRR0L" />
- <keyword match="UBRR1H" />
- <keyword match="UBRR1L" />
- <keyword match="UBRRH" />
- <keyword match="UBRRL" />
- <keyword match="UCSR0A" />
- <keyword match="UCSR0B" />
- <keyword match="UCSR0C" />
- <keyword match="UCSR1A" />
- <keyword match="UCSR1B" />
- <keyword match="UCSR1C" />
- <keyword match="UCSRA" />
- <keyword match="UCSRB" />
- <keyword match="UCSRC" />
- <keyword match="UDR" />
- <keyword match="UDR0" />
- <keyword match="UDR1" />
- <keyword match="WDTCR" />
- <keyword match="XDIV" />
- <keyword match="XMCRA" />
- <keyword match="XMCRB" />
- </keywords>
-
- <keywords name="types" inherits="identifier" innerClass="types" case="yes">
-
- <keyword match="auto" />
- <keyword match="bool" />
- <keyword match="char" />
- <keyword match="class" />
- <keyword match="const" />
- <keyword match="double" />
-
- <keyword match="enum" />
- <keyword match="explicit" />
- <keyword match="export" />
- <keyword match="extern" />
- <keyword match="float" />
- <keyword match="inline" />
-
- <keyword match="int" />
- <keyword match="long" />
- <keyword match="mutable" />
- <keyword match="namespace" />
- <keyword match="register" />
- <keyword match="short" />
-
- <keyword match="signed" />
- <keyword match="static" />
- <keyword match="struct" />
- <keyword match="template" />
- <keyword match="typedef" />
- <keyword match="typename" />
-
- <keyword match="union" />
- <keyword match="unsigned" />
- <keyword match="virtual" />
- <keyword match="void" />
- <keyword match="volatile" />
- <keyword match="wchar_t" />
-
- </keywords>
-
- <keywords name="Common Macros" inherits="identifier" innerClass="prepro" case="yes">
- <keyword match="NULL" />
- <keyword match="TRUE" />
- <keyword match="FALSE" />
- <keyword match="MAX" />
-
- <keyword match="MIN" />
- <keyword match="__LINE__" />
- <keyword match="__DATA__" />
- <keyword match="__FILE__" />
- <keyword match="__TIME__" />
- <keyword match="__STDC__" />
-
- </keywords>
-
-
- <!--
- <keywords name="reserved" inherits="identifier" innerClass="reserved" case="yes">
- -->
-
-</highlight>
-
diff --git a/library/Text_Highlighter/cpp.xml b/library/Text_Highlighter/cpp.xml
deleted file mode 100644
index 2cbaa930f..000000000
--- a/library/Text_Highlighter/cpp.xml
+++ /dev/null
@@ -1,201 +0,0 @@
-<?xml version="1.0"?>
-<!-- $Id: cpp.xml,v 1.2 2008-07-31 23:06:30 ssttoo Exp $ -->
-
-<highlight lang="CPP" case="no">
-
- <authors>
- <author name="Aaron Kalin"/>
- <author name="Andrey Demenev" email="demenev@gmail.com"/>
- </authors>
-
- <comment>
-Thanks to Aaron Kalin for initial
-implementation of this highlighter
- </comment>
-
- <default innerClass="code" />
-
- <block name="escaped" match="\\" innerClass="special" contained="yes">
- <onlyin region="strdouble"/>
- </block>
-
- <region name="strdouble" delimClass="quotes" innerClass="string" start="&quot;" end="&quot;"/>
-
- <region name="block" delimClass="brackets" innerClass="code" start="\{" end="\}">
- <contains all="yes"/>
- </region>
-
- <region name="brackets" delimClass="brackets" innerClass="code" start="\(" end="\)">
- <contains all="yes"/>
- </region>
-
- <region name="sqbrackets" delimClass="brackets" innerClass="code" start="\[" end="\]">
- <contains all="yes"/>
- </region>
-
- <block name="identifier" match="[a-z_]\w*" innerClass="identifier" case="no"/>
-
- <block name="hexinteger" match="\b0[xX][\da-f]+" innerClass="number"/>
- <block name="integer" match="\b\d\d*|\b0\b" innerClass="number"/>
- <block name="octinteger" match="\b0[0-7]+" innerClass="number"/>
- <block name="float" match="\b(\d*\.\d+)|(\d+\.\d*)" innerClass="number"/>
-
-
- <region name="strincl" delimClass="quotes" innerClass="string" start="&lt;" end="&gt;">
- <onlyin region="include" />
- </region>
-
- <!-- <block name="preprocessor" match="^#[azAZ_]\w*" innerClass="prepro"/> -->
- <region name="include" innerClass="prepro" start="/^[ \t]*#include/m" end="/(?&lt;!\\)$/m">
- <contains region="strdouble"/>
- <contains region="strincl"/>
- </region>
-
- <region name="preprocessor" delimClass="prepro" innerClass="code" start="/^[ \t]*#[ \t]*[a-z]+/mi" end="/(?&lt;!\\)$/m">
- <contains region="comment"/>
- <contains region="mlcomment"/>
- <contains region="strdouble"/>
- <contains region="brackets"/>
- <contains region="block"/>
- <contains block="identifier"/>
- <contains block="integer"/>
- <contains block="hexinteger"/>
- <contains block="octinteger"/>
- <contains block="float"/>
-
- </region>
-
- <block name="number" match="\d*\.?\d+" innerClass="number"/>
-
-
- <region name="mlcomment" innerClass="mlcomment" start="\/\*" end="\*\/" >
- <contains block="cvstag"/>
- </region>
-
- <block name="cvstag" match="\$\w+\s*:.+\$" innerClass="inlinedoc">
-
- <onlyin region="mlcomment"/>
- <onlyin region="comment"/>
- </block>
-
- <region name="comment" start="\/\/.+" end="/$/m" innerClass="comment" delimClass="comment">
- <contains block="cvstag"/>
- </region>
-
- <keywords name="reserved" inherits="identifier" innerClass="reserved" case="yes">
- <keyword match="and" />
- <keyword match="and_eq" />
- <keyword match="asm" />
-
- <keyword match="bitand" />
- <keyword match="bitor" />
- <keyword match="break" />
- <keyword match="case" />
- <keyword match="catch" />
- <keyword match="compl" />
-
- <keyword match="const_cast" />
- <keyword match="continue" />
- <keyword match="default" />
- <keyword match="delete" />
- <keyword match="do" />
- <keyword match="dynamic_cast" />
-
- <keyword match="else" />
- <keyword match="for" />
- <keyword match="fortran" />
- <keyword match="friend" />
- <keyword match="goto" />
- <keyword match="if" />
-
- <keyword match="new" />
- <keyword match="not" />
- <keyword match="not_eq" />
- <keyword match="operator" />
- <keyword match="or" />
- <keyword match="or_eq" />
-
- <keyword match="private" />
- <keyword match="protected" />
- <keyword match="public" />
- <keyword match="reinterpret_cast" />
- <keyword match="return" />
- <keyword match="sizeof" />
-
- <keyword match="static_cast" />
- <keyword match="switch" />
- <keyword match="this" />
- <keyword match="throw" />
- <keyword match="try" />
- <keyword match="typeid" />
-
- <keyword match="using" />
- <keyword match="while" />
- <keyword match="xor" />
- <keyword match="xor_eq" />
-
- <keyword match="false" />
- <keyword match="true" />
- </keywords>
-
- <keywords name="types" inherits="identifier" innerClass="types" case="yes">
-
- <keyword match="auto" />
- <keyword match="bool" />
- <keyword match="char" />
- <keyword match="class" />
- <keyword match="const" />
- <keyword match="double" />
-
- <keyword match="enum" />
- <keyword match="explicit" />
- <keyword match="export" />
- <keyword match="extern" />
- <keyword match="float" />
- <keyword match="inline" />
-
- <keyword match="int" />
- <keyword match="long" />
- <keyword match="mutable" />
- <keyword match="namespace" />
- <keyword match="register" />
- <keyword match="short" />
-
- <keyword match="signed" />
- <keyword match="static" />
- <keyword match="struct" />
- <keyword match="template" />
- <keyword match="typedef" />
- <keyword match="typename" />
-
- <keyword match="union" />
- <keyword match="unsigned" />
- <keyword match="virtual" />
- <keyword match="void" />
- <keyword match="volatile" />
- <keyword match="wchar_t" />
-
- </keywords>
-
- <keywords name="Common Macros" inherits="identifier" innerClass="prepro" case="yes">
- <keyword match="NULL" />
- <keyword match="TRUE" />
- <keyword match="FALSE" />
- <keyword match="MAX" />
-
- <keyword match="MIN" />
- <keyword match="__LINE__" />
- <keyword match="__DATA__" />
- <keyword match="__FILE__" />
- <keyword match="__TIME__" />
- <keyword match="__STDC__" />
-
- </keywords>
-
-
- <!--
- <keywords name="reserved" inherits="identifier" innerClass="reserved" case="yes">
- -->
-
-</highlight>
-
diff --git a/library/Text_Highlighter/css.xml b/library/Text_Highlighter/css.xml
deleted file mode 100644
index 2473bcfb7..000000000
--- a/library/Text_Highlighter/css.xml
+++ /dev/null
@@ -1,368 +0,0 @@
-<?xml version="1.0"?>
-<!-- $Id: css.xml,v 1.2 2008-01-01 23:45:07 ssttoo Exp $ -->
-
-<highlight lang="css" case="no">
-
- <authors>
- <author name="Andrey Demenev" email="demenev@gmail.com"/>
- </authors>
-
-
- <default innerClass="code" />
-
-
- <region name="mlcomment" innerClass="comment" start="\/\*" end="\*\/" >
-
- </region>
-
-
- <block name="atrule" match="(@[a-z\d]+)"
- innerClass="var" never-contained="yes"/>
-
- <region name="property" start="[a-z][a-z\d\-]*\s*:" end="(?=;|\})"
- innerClass="code" delimClass="reserved" contained="yes"/>
-
- <block name="selector" match="(((\.|#)?[a-z]+[a-z\d\-]*(?![a-z\d\-]))|(\*))(?!\s*:\s*[\s\{])"
- innerClass="identifier" >
- </block>
-
- <block name="pseudo" match=":[a-z][a-z\d\-]*"
- innerClass="special" />
-
- <block name="bescaped" match="\\[\\(\\)\\]"
- innerClass="string" contained="yes"/>
-
-
- <region name="paramselector" start="\[" end="\]" innerClass="code"
- delimClass="brackets" >
- <contains block="paramname" />
- <not-contains block="identifier" />
- <contains region="strdouble" />
- <contains region="strsingle" />
- </region>
-
- <region name="block" start="\{" end="\}" innerClass="code"
- delimClass="brackets" >
- <contains region="block" />
- <contains region="property" />
- <contains block="selector" />
- <contains region="mlcomment" />
- </region>
-
- <region name="brackets" start="\(" end="\)" innerClass="string"
- delimClass="brackets" contained="yes">
- <contains block="bescaped"/>
- </region>
-
- <region name="strsingle" delimClass="quotes" innerClass="string" start="'" end="'" contained="yes"/>
-
- <block name="escaped" match="\\\\|\\&quot;|\\'|\\`" innerClass="special" contained="yes">
- <onlyin region="strsingle"/>
- </block>
-
- <block name="descaped" match="\\\\|\\&quot;|\\'|\\`|\\t|\\n|\\r" innerClass="special" contained="yes">
- <onlyin region="strdouble"/>
- </block>
-
- <region name="strdouble" delimClass="quotes" innerClass="string"
- start="&quot;" end="&quot;" contained="yes" />
-
- <block name="measure" match="\d*\.?\d+(\%|em|ex|pc|pt|px|in|mm|cm)"
- innerClass="number" contained="yes">
- <onlyin region="property"/>
- <partClass index="1" innerClass="string" />
- </block>
-
- <block name="number" match="\d*\.?\d+" innerClass="number" contained="yes" >
- <onlyin region="property"/>
- </block>
-
- <block name="identifier" match="[a-z][a-z\d\-]*"
- innerClass="code" contained="yes">
- <onlyin region="property"/>
- </block>
-
- <block name="hexcolor" match="#([\da-f]{6}|[\da-f]{3})\b" innerClass="var" contained="yes">
- <onlyin region="property"/>
- </block>
-
- <block name="paramname" match="[\w\-\:]+" innerClass="var" contained="yes">
- <onlyin region="paramselector"/>
- </block>
-
- <keywords name="propertyValue" inherits="identifier" innerClass="string" case = "no">
- <word name="left-side"/>
- <keyword match="far-left"/>
- <keyword match="left"/>
- <keyword match="center-left"/>
- <keyword match="center-right"/>
- <keyword match="center"/>
- <keyword match="far-right"/>
- <keyword match="right-side"/>
- <keyword match="right"/>
- <keyword match="behind"/>
- <keyword match="leftwards"/>
- <keyword match="rightwards"/>
- <keyword match="inherit"/>
- <keyword match="scroll"/>
- <keyword match="fixed"/>
- <keyword match="transparent"/>
- <keyword match="none"/>
- <keyword match="repeat-x"/>
- <keyword match="repeat-y"/>
- <keyword match="repeat"/>
- <keyword match="no-repeat"/>
- <keyword match="collapse"/>
- <keyword match="separate"/>
- <keyword match="auto"/>
- <keyword match="top"/>
- <keyword match="bottom"/>
- <keyword match="both"/>
- <keyword match="open-quote"/>
- <keyword match="close-quote"/>
- <keyword match="no-open-quote"/>
- <keyword match="no-close-quote"/>
- <keyword match="crosshair"/>
- <keyword match="default"/>
- <keyword match="pointer"/>
- <keyword match="move"/>
- <keyword match="e-resize"/>
- <keyword match="ne-resize"/>
- <keyword match="nw-resize"/>
- <keyword match="n-resize"/>
- <keyword match="se-resize"/>
- <keyword match="sw-resize"/>
- <keyword match="s-resize"/>
- <keyword match="text"/>
- <keyword match="wait"/>
- <keyword match="help"/>
- <keyword match="ltr"/>
- <keyword match="rtl"/>
- <keyword match="inline"/>
- <keyword match="block"/>
- <keyword match="list-item"/>
- <keyword match="run-in"/>
- <keyword match="compact"/>
- <keyword match="marker"/>
- <keyword match="table"/>
- <keyword match="inline-table"/>
- <keyword match="table-row-group"/>
- <keyword match="table-header-group"/>
- <keyword match="table-footer-group"/>
- <keyword match="table-row"/>
- <keyword match="table-column-group"/>
- <keyword match="table-column"/>
- <keyword match="table-cell"/>
- <keyword match="table-caption"/>
- <keyword match="below"/>
- <keyword match="level"/>
- <keyword match="above"/>
- <keyword match="higher"/>
- <keyword match="lower"/>
- <keyword match="show"/>
- <keyword match="hide"/>
- <keyword match="caption"/>
- <keyword match="icon"/>
- <keyword match="menu"/>
- <keyword match="message-box"/>
- <keyword match="small-caption"/>
- <keyword match="status-bar"/>
- <keyword match="normal"/>
- <keyword match="wider"/>
- <keyword match="narrower"/>
- <keyword match="ultra-condensed"/>
- <keyword match="extra-condensed"/>
- <keyword match="condensed"/>
- <keyword match="semi-condensed"/>
- <keyword match="semi-expanded"/>
- <keyword match="expanded"/>
- <keyword match="extra-expanded"/>
- <keyword match="ultra-expanded"/>
- <keyword match="italic"/>
- <keyword match="oblique"/>
- <keyword match="small-caps"/>
- <keyword match="bold"/>
- <keyword match="bolder"/>
- <keyword match="lighter"/>
- <keyword match="inside"/>
- <keyword match="outside"/>
- <keyword match="disc"/>
- <keyword match="circle"/>
- <keyword match="square"/>
- <keyword match="decimal"/>
- <keyword match="decimal-leading-zero"/>
- <keyword match="lower-roman"/>
- <keyword match="upper-roman"/>
- <keyword match="lower-greek"/>
- <keyword match="lower-alpha"/>
- <keyword match="lower-latin"/>
- <keyword match="upper-alpha"/>
- <keyword match="upper-latin"/>
- <keyword match="hebrew"/>
- <keyword match="armenian"/>
- <keyword match="georgian"/>
- <keyword match="cjk-ideographic"/>
- <keyword match="hiragana"/>
- <keyword match="katakana"/>
- <keyword match="hiragana-iroha"/>
- <keyword match="katakana-iroha"/>
- <keyword match="crop"/>
- <keyword match="cross"/>
- <keyword match="invert"/>
- <keyword match="visible"/>
- <keyword match="hidden"/>
- <keyword match="always"/>
- <keyword match="avoid"/>
- <keyword match="x-low"/>
- <keyword match="low"/>
- <keyword match="medium"/>
- <keyword match="high"/>
- <keyword match="x-high"/>
- <keyword match="mix?"/>
- <keyword match="repeat?"/>
- <keyword match="static"/>
- <keyword match="relative"/>
- <keyword match="absolute"/>
- <keyword match="portrait"/>
- <keyword match="landscape"/>
- <keyword match="spell-out"/>
- <keyword match="once"/>
- <keyword match="digits"/>
- <keyword match="continuous"/>
- <keyword match="code"/>
- <keyword match="x-slow"/>
- <keyword match="slow"/>
- <keyword match="fast"/>
- <keyword match="x-fast"/>
- <keyword match="faster"/>
- <keyword match="slower"/>
- <keyword match="justify"/>
- <keyword match="underline"/>
- <keyword match="overline"/>
- <keyword match="line-through"/>
- <keyword match="blink"/>
- <keyword match="capitalize"/>
- <keyword match="uppercase"/>
- <keyword match="lowercase"/>
- <keyword match="embed"/>
- <keyword match="bidi-override"/>
- <keyword match="baseline"/>
- <keyword match="sub"/>
- <keyword match="super"/>
- <keyword match="text-top"/>
- <keyword match="middle"/>
- <keyword match="text-bottom"/>
- <keyword match="silent"/>
- <keyword match="x-soft"/>
- <keyword match="soft"/>
- <keyword match="loud"/>
- <keyword match="x-loud"/>
- <keyword match="pre"/>
- <keyword match="nowrap"/>
- <keyword match="serif"/>
- <keyword match="sans-serif"/>
- <keyword match="cursive"/>
- <keyword match="fantasy"/>
- <keyword match="monospace"/>
- <keyword match="empty"/>
- <keyword match="string"/>
- <keyword match="strict"/>
- <keyword match="loose"/>
- <keyword match="char"/>
- <keyword match="true"/>
- <keyword match="false"/>
- <keyword match="dotted"/>
- <keyword match="dashed"/>
- <keyword match="solid"/>
- <keyword match="double"/>
- <keyword match="groove"/>
- <keyword match="ridge"/>
- <keyword match="inset"/>
- <keyword match="outset"/>
- <keyword match="larger"/>
- <keyword match="smaller"/>
- <keyword match="xx-small"/>
- <keyword match="x-small"/>
- <keyword match="small"/>
- <keyword match="large"/>
- <keyword match="x-large"/>
- <keyword match="xx-large"/>
- <keyword match="all"/>
- <keyword match="newspaper"/>
- <keyword match="distribute"/>
- <keyword match="distribute-all-lines"/>
- <keyword match="distribute-center-last"/>
- <keyword match="inter-word"/>
- <keyword match="inter-ideograph"/>
- <keyword match="inter-cluster"/>
- <keyword match="kashida"/>
- <keyword match="ideograph-alpha"/>
- <keyword match="ideograph-numeric"/>
- <keyword match="ideograph-parenthesis"/>
- <keyword match="ideograph-space"/>
- <keyword match="keep-all"/>
- <keyword match="break-all"/>
- <keyword match="break-word"/>
- <keyword match="lr-tb"/>
- <keyword match="tb-rl"/>
- <keyword match="thin"/>
- <keyword match="thick"/>
- <keyword match="inline-block"/>
- <keyword match="w-resize"/>
- <keyword match="hand"/>
- <keyword match="distribute-letter"/>
- <keyword match="distribute-space"/>
- <keyword match="whitespace"/>
- <keyword match="male"/>
- <keyword match="female"/>
- <keyword match="child"/>
- </keywords>
-
-
- <keywords name="namedcolor" inherits="identifier" innerClass="var" case = "no">
- <keyword match="aqua"/>
- <keyword match="black"/>
- <keyword match="blue"/>
- <keyword match="fuchsia"/>
- <keyword match="gray"/>
- <keyword match="green"/>
- <keyword match="lime"/>
- <keyword match="maroon"/>
- <keyword match="navy"/>
- <keyword match="olive"/>
- <keyword match="purple"/>
- <keyword match="red"/>
- <keyword match="silver"/>
- <keyword match="teal"/>
- <keyword match="white"/>
- <keyword match="yellow"/>
- <keyword match="ActiveBorder"/>
- <keyword match="ActiveCaption"/>
- <keyword match="AppWorkspace"/>
- <keyword match="Background"/>
- <keyword match="ButtonFace"/>
- <keyword match="ButtonHighlight"/>
- <keyword match="ButtonShadow"/>
- <keyword match="ButtonText"/>
- <keyword match="CaptionText"/>
- <keyword match="GrayText"/>
- <keyword match="Highlight"/>
- <keyword match="HighlightText"/>
- <keyword match="InactiveBorder"/>
- <keyword match="InactiveCaption"/>
- <keyword match="InactiveCaptionText"/>
- <keyword match="InfoBackground"/>
- <keyword match="InfoText"/>
- <keyword match="Menu"/>
- <keyword match="MenuText"/>
- <keyword match="Scrollbar"/>
- <keyword match="ThreeDDarkShadow"/>
- <keyword match="ThreeDFace"/>
- <keyword match="ThreeDHighlight"/>
- <keyword match="ThreeDLightShadow"/>
- <keyword match="ThreeDShadow"/>
- <keyword match="Window"/>
- <keyword match="WindowFrame"/>
- <keyword match="WindowText"/>
- </keywords>
-</highlight>
diff --git a/library/Text_Highlighter/diff.xml b/library/Text_Highlighter/diff.xml
deleted file mode 100644
index d088f9257..000000000
--- a/library/Text_Highlighter/diff.xml
+++ /dev/null
@@ -1,45 +0,0 @@
-<?xml version="1.0"?>
-<!-- $Id: diff.xml,v 1.1 2007-06-03 02:35:28 ssttoo Exp $ -->
-
-<highlight lang="diff" case="yes">
-
- <authors>
- <author name="Andrey Demenev" email="demenev@gmail.com"/>
- </authors>
-
-
- <default innerClass="default" />
-
- <block name="noNewLine" match="/^\\\sNo\snewline.+$/m" innerClass="special"/>
-
- <block name="diffSeparator" match="/^\-\-\-$/m" innerClass="code"/>
-
- <block name="diffCmdLine" match="/^(diff\s+\-|Only\s+|Index).*$/m" innerClass="var"/>
- <block name="diffFiles" match="/^(\-\-\-|\+\+\+)\s.+$/m" innerClass="reserved"/>
-
- <block name="contextOrg" match="/^\*.*$/m" innerClass="quotes"/>
- <block name="contextNew" match="/^\+.*$/m" innerClass="string"/>
- <block name="contextChg" match="/^!.*$/m" innerClass="inlinedoc"/>
-
- <block name="defOrg" match="/^\&lt;\s.*$/m" innerClass="quotes"/>
- <block name="defNew" match="/^\&gt;\s.*$/m" innerClass="string"/>
- <block name="defChg" match="/^\d+(\,\d+)?[acd]\d+(,\d+)?$/m" innerClass="code"/>
-
- <block name="uniOrg" match="/^\-.*$/m" innerClass="quotes"/>
- <block name="uniNew" match="/^\+.*$/m" innerClass="string"/>
- <block name="uniChg" match="/^@@.+@@$/m" innerClass="code"/>
-
- <block name="normOrg" match="/^d\d+\s\d+$/m" innerClass="code"/>
- <region name="normNew" start="/^a\d+\s\d+$/m" end="/(?=^[ad]\d+\s\d+)/m" innerClass="var" delimClass="code"/>
-
- <region name="edNew" start="/^(\d+)(,\d+)?(a)$/m" end="/^(\.)$/m" innerClass="string" delimClass="code"/>
- <region name="edChg" start="/^(\d+)(,\d+)?(c)$/m" end="/^(\.)$/m" innerClass="inlinedoc" delimClass="code"/>
- <block name="edDel" match="/^(\d+)(,\d+)?(d)$/m" innerClass="code"/>
-
- <region name="fedNew" start="/^a(\d+)(\s\d+)?$/m" end="/^(\.)$/m" innerClass="string" delimClass="code"/>
- <region name="fedChg" start="/^c(\d+)(\s\d+)?$/m" end="/^(\.)$/m" innerClass="inlinedoc" delimClass="code"/>
- <block name="fedDel" match="/^d(\d+)(\s\d+)?$/m"
- innerClass="code"/>
-
-
-</highlight>
diff --git a/library/Text_Highlighter/dtd.xml b/library/Text_Highlighter/dtd.xml
deleted file mode 100644
index 18fa07db7..000000000
--- a/library/Text_Highlighter/dtd.xml
+++ /dev/null
@@ -1,66 +0,0 @@
-<?xml version="1.0"?>
-<!-- $Id: dtd.xml,v 1.1 2007-06-03 02:35:28 ssttoo Exp $ -->
-
-<highlight lang="dtd" case="yes">
-
- <authors>
- <author name="Andrey Demenev" email="demenev@gmail.com"/>
- </authors>
-
-
- <default innerClass="code" />
-
- <region name="comment" delimClass="comment" innerClass="comment"
- start="\&lt;!--" end="--\&gt;">
- </region>
-
- <region name="redecl" start="\&lt;\!\[" end="\]\]\&gt;" delimClass="brackets"
- innerClass="code" never-contained="yes">
- <contains all="yes" />
- </region>
-
- <region name="tag" start="\&lt;" end="\&gt;" delimClass="brackets"
- innerClass="code" >
- <contains all="yes" />
- <onlyin region="redecl"/>
- </region>
-
- <region name="brackets" start="\(" end="\)" delimClass="brackets"
- innerClass="code" contained="yes">
- <onlyin region="tag"/>
- <onlyin region="brackets"/>
- <contains block="entity" />
- <contains block="identifier" />
- </region>
-
- <region name="strsingle" start="'" end="'" delimClass="quotes"
- innerClass="string" contained="yes">
- <onlyin region="tag"/>
- <contains block="entity" />
- </region>
-
- <region name="strdouble" start="&quot;" end="&quot;" delimClass="quotes"
- innerClass="string" contained="yes">
- <onlyin region="tag"/>
- <contains block="entity" />
- </region>
-
- <block name="tagname" match="(?&lt;=\&lt;)!(ENTITY|ATTLIST|ELEMENT|NOTATION)\b"
- innerClass="var" contained="yes">
- <onlyin region="tag"/>
- </block>
-
- <block name="reserved" match="\s(#(IMPLIED|REQUIRED|FIXED))|CDATA|ENTITY|NOTATION|NMTOKENS?|PUBLIC|SYSTEM\b"
- innerClass="reserved" contained="yes">
- <onlyin region="tag"/>
- </block>
-
- <block name="pcdata" match="#PCDATA\b"
- innerClass="reserved" contained="yes" />
-
- <block name="entity" match="(\&amp;|\%)[\w\-\.]+;" innerClass="special" />
-
- <block name="identifier" match="[a-z][a-z\d\-\,:]+"
- innerClass="identifier" contained="yes" case="no"/>
-
-</highlight>
diff --git a/library/Text_Highlighter/generate b/library/Text_Highlighter/generate
deleted file mode 100644
index 4e22e82fd..000000000
--- a/library/Text_Highlighter/generate
+++ /dev/null
@@ -1,171 +0,0 @@
-#!@php_bin@
-<?php
-/* vim: set expandtab tabstop=4 shiftwidth=4 softtabstop=4: */
-/**
- * Console highlighter class generator
- *
- * PHP versions 4 and 5
- *
- * LICENSE: This source file is subject to version 3.0 of the PHP license
- * that is available through the world-wide-web at the following URI:
- * http://www.php.net/license/3_0.txt. If you did not receive a copy of
- * the PHP License and are unable to obtain it through the web, please
- * send a note to license@php.net so we can mail you a copy immediately.
- *
- * @category Text
- * @package Text_Highlighter
- * @author Andrey Demenev <demenev@gmail.com>
- * @copyright 2004 Andrey Demenev
- * @license http://www.php.net/license/3_0.txt PHP License
- * @version CVS: $Id$
- * @link http://pear.php.net/package/Text_Highlighter
- */
-
-require_once 'Text/Highlighter/Generator.php';
-require_once 'Console/Getopt.php';
-
-$options = Console_Getopt::getopt($argv, 'x:p:d:h', array('xml=', 'php=','dir=', 'help'));
-
-if (PEAR::isError($options)) {
- $message = str_replace('Console_Getopt: ','',$options->message);
- usage($message);
-}
-
-$source = array();
-$dest = array();
-$dir = '';
-
-$expectp = false;
-$expectx = false;
-$unexpectedx = false;
-$unexpectedp = false;
-$si = $di = 0;
-
-foreach ($options[0] as $option) {
- switch ($option[0]) {
- case 'x':
- case '--xml':
- $source[$si] = $option[1];
- if ($si) {
- $di++;
- }
- $si++;
- if ($expectp) {
- $unexpectedx = true;
- }
- $expectp = true;
- $expectx = false;
- break;
-
- case 'p':
- case '--php':
- if ($expectx) {
- $unexpectedp = true;
- }
- $dest[$di] = $option[1];
- $expectp = false;
- $expectx = true;
- break;
-
- case 'd':
- case '--dir':
- $dir = $option[1];
- break;
-
- case 'h':
- case '--help':
- usage();
- break;
- }
-}
-
-
-if ($unexpectedx && !$dir) {
- usage('Unexpected -x or --xml', STDERR);
-}
-
-if ($unexpectedp) {
- usage('Unexpected -p or --php', STDERR);
-}
-
-$nsource = count($source);
-$ndest = count($dest);
-
-if (!$nsource && !$ndest) {
- $source[]='php://stdin';
- if (!$dir) {
- $dest[]='php://stdout';
- } else {
- $dest[] = null;
- }
-} elseif ($expectp && !$dir && $nsource > 1) {
- usage('-x or --xml without following -p or --php', STDERR);
-} elseif ($nsource == 1 && !$ndest && !$dir) {
- $dest[]='php://stdout';
-}
-
-if ($dir && substr($dir,-1)!='/' && substr($dir,-1)!=='\\' ) {
- $dir .= DIRECTORY_SEPARATOR;
-}
-
-
-foreach ($source as $i => $xmlfile)
-{
- $gen = new Text_Highlighter_Generator;
- $gen->setInputFile($xmlfile);
- if ($gen->hasErrors()) {
- break;
- }
- $gen->generate();
- if ($gen->hasErrors()) {
- break;
- }
- if (isset($dest[$i])) {
- $phpfile = $dest[$i];
- } else {
- $phpfile = $dir . $gen->language . '.php';
- }
- $gen->saveCode($phpfile);
- if ($gen->hasErrors()) {
- break;
- }
-}
-if ($gen->hasErrors()) {
- $errors = $gen->getErrors();
- foreach ($errors as $error) {
- fwrite (STDERR, $error . "\n");
- }
- exit(1);
-}
-
-function usage($message='', $file=STDOUT)
-{
- $code = 0;
- if ($message) {
- $message .= "\n\n";
- $code = 1;
- }
- $message .= <<<MSG
-Generates a highlighter class from XML source
-Usage:
-generate options
-
-Options:
- -x filename, --xml=filename
- source XML file. Multiple input files can be specified, in which
- case each -x option must be followed by -p unless -d is specified
- Defaults to stdin
- -p filename, --php=filename
- destination PHP file. Defaults to stdout. If specied multiple times,
- each -p must follow -x
- -d dirname, --dir=dirname
- Default destination directory. File names will be taken from XML input
- ("lang" attribute of <highlight> tag)
- -h, --help
- This help
-MSG;
- fwrite ($file, $message);
- exit($code);
-}
-?>
-
diff --git a/library/Text_Highlighter/generate.bat b/library/Text_Highlighter/generate.bat
deleted file mode 100644
index 3960486c1..000000000
--- a/library/Text_Highlighter/generate.bat
+++ /dev/null
@@ -1,188 +0,0 @@
-@echo off
-rem vim: set expandtab tabstop=4 shiftwidth=4 softtabstop=4:
-
-rem Console highlighter class generator
-
-rem PHP versions 4 and 5
-
-rem LICENSE: This source file is subject to version 3.0 of the PHP license
-rem that is available through the world-wide-web at the following URI:
-rem http://www.php.net/license/3_0.txt. If you did not receive a copy of
-rem the PHP License and are unable to obtain it through the web, please
-rem send a note to license@php.net so we can mail you a copy immediately.
-
-rem @category Text
-rem @package Text_Highlighter
-rem @author Andrey Demenev <demenev@gmail.com>
-rem @copyright 2004 Andrey Demenev
-rem @license http://www.php.net/license/3_0.txt PHP License
-rem @version CVS: $Id: generate.bat,v 1.1 2007-06-03 02:35:28 ssttoo Exp $
-rem @link http://pear.php.net/package/Text_Highlighter
-
-set "MHL_PARAMS="
-:doshift
-set "MHL_PARAMS=%MHL_PARAMS% %1"
-shift
-if -%1- == -- GOTO noshift
-GOTO doshift
-:noshift
-@php_bin@ -q -d output_buffering=1 -d include_path="@php_dir@" @bin_dir@/Text/Highlighter/generate.bat %MHL_PARAMS%
-
-GOTO finish
-<?php
-ob_end_clean();
-
-if (!defined('STDOUT')) {
- define('STDOUT', fopen('php://stdout', 'wb'));
- define('STDERR', fopen('php://stderr', 'wb'));
-}
-require_once 'Text/Highlighter/Generator.php';
-require_once 'Console/Getopt.php';
-
-$options = Console_Getopt::getopt($argv, 'x:p:d:h', array('xml=', 'php=','dir=', 'help'));
-
-if (PEAR::isError($options)) {
- $message = str_replace('Console_Getopt: ','',$options->message);
- usage($message);
-}
-
-$source = array();
-$dest = array();
-$dir = '';
-
-$expectp = false;
-$expectx = false;
-$unexpectedx = false;
-$unexpectedp = false;
-$si = $di = 0;
-
-foreach ($options[0] as $option) {
- switch ($option[0]) {
- case 'x':
- case '--xml':
- $source[$si] = $option[1];
- if ($si) {
- $di++;
- }
- $si++;
- if ($expectp) {
- $unexpectedx = true;
- }
- $expectp = true;
- $expectx = false;
- break;
-
- case 'p':
- case '--php':
- if ($expectx) {
- $unexpectedp = true;
- }
- $dest[$di] = $option[1];
- $expectp = false;
- $expectx = true;
- break;
-
- case 'd':
- case '--dir':
- $dir = $option[1];
- break;
-
- case 'h':
- case '--help':
- usage();
- break;
- }
-}
-
-
-if ($unexpectedx && !$dir) {
- usage('Unexpected -x or --xml', STDERR);
-}
-
-if ($unexpectedp) {
- usage('Unexpected -p or --php', STDERR);
-}
-
-$nsource = count($source);
-$ndest = count($dest);
-
-if (!$nsource && !$ndest) {
- $source[]='php://stdin';
- if (!$dir) {
- $dest[]='php://stdout';
- } else {
- $dest[] = null;
- }
-} elseif ($expectp && !$dir && $nsource > 1) {
- usage('-x or --xml without following -p or --php', STDERR);
-} elseif ($nsource == 1 && !$ndest && !$dir) {
- $dest[]='php://stdout';
-}
-
-if ($dir && substr($dir,-1)!='/' && substr($dir,-1)!=='\\' ) {
- $dir .= DIRECTORY_SEPARATOR;
-}
-
-
-foreach ($source as $i => $xmlfile)
-{
- $gen = new Text_Highlighter_Generator;
- $gen->setInputFile($xmlfile);
- if ($gen->hasErrors()) {
- break;
- }
- $gen->generate();
- if ($gen->hasErrors()) {
- break;
- }
- if (isset($dest[$i])) {
- $phpfile = $dest[$i];
- } else {
- $phpfile = $dir . $gen->language . '.php';
- }
- $gen->saveCode($phpfile);
- if ($gen->hasErrors()) {
- break;
- }
-}
-if ($gen->hasErrors()) {
- $errors = $gen->getErrors();
- foreach ($errors as $error) {
- fwrite (STDERR, $error . "\n");
- }
- exit(1);
-}
-
-exit(0);
-
-function usage($message='', $file=STDOUT)
-{
- $code = 0;
- if ($message) {
- $message .= "\n\n";
- $code = 1;
- }
- $message .= <<<MSG
-Generates a highlighter class from XML source
-Usage:
-generate options
-
-Options:
- -x filename, --xml=filename
- source XML file. Multiple input files can be specified, in which
- case each -x option must be followed by -p unless -d is specified
- Defaults to stdin
- -p filename, --php=filename
- destination PHP file. Defaults to stdout. If specied multiple times,
- each -p must follow -x
- -d dirname, --dir=dirname
- Default destination directory. File names will be taken from XML input
- ("lang" attribute of <highlight> tag)
- -h, --help
- This help
-MSG;
- fwrite ($file, $message);
- exit($code);
-}
-?>
-:finish
diff --git a/library/Text_Highlighter/html.xml b/library/Text_Highlighter/html.xml
deleted file mode 100644
index 58d51fc5b..000000000
--- a/library/Text_Highlighter/html.xml
+++ /dev/null
@@ -1,33 +0,0 @@
-<?xml version="1.0"?>
-<!-- $Id: html.xml,v 1.1 2007-06-03 02:35:28 ssttoo Exp $ -->
-
-<highlight lang="html" case="no">
-
- <authors>
- <author name="Andrey Demenev" email="demenev@gmail.com"/>
- </authors>
-
-
- <default innerClass="code" />
-
- <region name="comment" delimClass="comment" innerClass="comment"
- start="\&lt;!--" end="--\&gt;">
- </region>
-
- <region name="tag" delimClass="brackets" innerClass="code" start="\&lt;[\?\/]?" end="[\/\?]?\&gt;">
- <contains block="tagname"/>
- <contains region="param"/>
- <contains block="paramname"/>
- </region>
-
- <block name="tagname" match="(?&lt;=[\&lt;\/?])[\w\-\:]+" innerClass="reserved" contained="yes"/>
-
- <block name="paramname" match="[\w\-\:]+" innerClass="var" contained="yes"/>
-
- <block name="entity" match="(&amp;)[\w\-\.]+;" innerClass="special" />
-
- <region name="param" start="&quot;" end="&quot;" delimClass="quotes" innerClass="string" contained="yes">
- <contains block="entity"/>
- </region>
-
-</highlight>
diff --git a/library/Text_Highlighter/java.xml b/library/Text_Highlighter/java.xml
deleted file mode 100644
index 12052b5db..000000000
--- a/library/Text_Highlighter/java.xml
+++ /dev/null
@@ -1,2824 +0,0 @@
-<?xml version="1.0"?>
-<!-- $Id: java.xml,v 1.1 2007-06-03 02:35:28 ssttoo Exp $ -->
-
-<highlight lang="java">
-
- <authors>
- <author name="Andrey Demenev" email ="demenev@gmail.com"/>
- </authors>
-
- <default innerClass="code" />
-
- <region name="block" delimClass="brackets" innerClass="code" start="\{" end="\}">
- <contains all="yes"/>
- </region>
-
- <region name="brackets" delimClass="brackets" innerClass="code" start="\(" end="\)" >
- <contains all="yes"/>
- </region>
-
- <region name="sqbrackets" delimClass="brackets" innerClass="code" start="\[" end="\]">
- <contains all="yes"/>
- </region>
-
-
- <region name="mlcomment" innerClass="comment" start="\/\*" end="\*\/">
- <contains block="javadoc"/>
- <contains block="cvstag"/>
- </region>
-
- <region name="strdouble" delimClass="quotes" innerClass="string" start="&quot;" end="&quot;" />
-
- <region name="strsingle" delimClass="quotes" innerClass="string" start="'" end="'"/>
-
- <block name="escaped" match="\\." innerClass="special" contained="yes">
- <onlyin region="strsingle"/>
- </block>
-
- <block name="descaped" match="\\[\\&quot;'`tnr\$\{]" innerClass="special" contained="yes">
- <onlyin region="strdouble"/>
- </block>
-
-
- <region name="comment" start="\/\/" end="/$/m" innerClass="comment">
- <contains block="cvstag"/>
- </region>
-
- <block name="identifier" match="[a-z_]\w*" innerClass="identifier" />
-
- <block name="hexinteger" match="0[xX][\da-f]+" innerClass="number" />
- <block name="integer" match="\d\d*|\b0\b" innerClass="number" />
- <block name="octinteger" match="0[0-7]+" innerClass="number" />
- <block name="float" match="(\d*\.\d+)|(\d+\.\d*)" innerClass="number" />
- <block name="exponent"
- match="((\d+|((\d*\.\d+)|(\d+\.\d*)))[eE][+-]?\d+)"
- innerClass="number" />
-
- <block name="javadoc" match="\s@\w+\s" innerClass="inlinedoc" contained="yes">
- <onlyin region="mlcomment"/>
- <onlyin region="comment"/>
- </block>
-
- <block name="url" match="((https?|ftp):\/\/[\w\?\.\-\&amp;=\/%+]+)|(^|[\s,!?])www\.\w+\.\w+[\w\?\.\&amp;=\/%+]*" innerClass="url" contained="yes">
- <onlyin region="mlcomment"/>
- <onlyin region="comment"/>
- </block>
-
- <block name="email" match="\w+[\.\w\-]+@(\w+[\.\w\-])+" innerClass="url" contained="yes">
- <onlyin region="mlcomment"/>
- <onlyin region="comment"/>
- </block>
-
- <block name="note" match="\bnote:" innerClass="inlinedoc" contained="yes">
- <onlyin region="mlcomment"/>
- <onlyin region="comment"/>
- </block>
-
-
- <block name="cvstag" match="\$\w+\s*:.*\$" innerClass="inlinedoc" contained="yes">
- <onlyin region="mlcomment"/>
- <onlyin region="comment"/>
- </block>
-
- <keywords name="types" inherits="identifier" innerClass="types" case = "yes">
- <keyword match="boolean" />
- <keyword match="byte" />
- <keyword match="char" />
- <keyword match="const" />
- <keyword match="double" />
- <keyword match="final" />
- <keyword match="float" />
- <keyword match="int" />
- <keyword match="long" />
- <keyword match="short" />
- <keyword match="static" />
- <keyword match="void" />
- </keywords>
-
- <keywords name="reserved" inherits="identifier" innerClass="reserved" case="yes">
- <keyword match="import"/>
- <keyword match="package"/>
- <keyword match="abstract" />
- <keyword match="break" />
- <keyword match="case" />
- <keyword match="catch" />
- <keyword match="class" />
- <keyword match="continue" />
- <keyword match="default" />
- <keyword match="do" />
- <keyword match="else" />
- <keyword match="extends" />
- <keyword match="false" />
- <keyword match="finally" />
- <keyword match="for" />
- <keyword match="goto" />
- <keyword match="if" />
- <keyword match="implements" />
- <keyword match="instanceof" />
- <keyword match="interface" />
- <keyword match="native" />
- <keyword match="new" />
- <keyword match="null" />
- <keyword match="private" />
- <keyword match="protected" />
- <keyword match="public" />
- <keyword match="return" />
- <keyword match="super" />
- <keyword match="strictfp" />
- <keyword match="switch" />
- <keyword match="synchronized" />
- <keyword match="this" />
- <keyword match="throws" />
- <keyword match="throw" />
- <keyword match="transient" />
- <keyword match="true" />
- <keyword match="try" />
- <keyword match="volatile" />
- <keyword match="while" />
- </keywords>
-
- <keywords name="builtin" inherits="identifier" innerClass="builtin" case = "yes" ifdef="java.builtins">
- <keyword match="AbstractAction" />
- <keyword match="AbstractBorder" />
- <keyword match="AbstractButton" />
- <keyword match="AbstractCellEditor" />
- <keyword match="AbstractCollection" />
- <keyword match="AbstractColorChooserPanel" />
- <keyword match="AbstractDocument" />
- <keyword match="AbstractInterruptibleChannel" />
- <keyword match="AbstractLayoutCache" />
- <keyword match="AbstractList" />
- <keyword match="AbstractListModel" />
- <keyword match="AbstractMap" />
- <keyword match="AbstractMethodError" />
- <keyword match="AbstractPreferences" />
- <keyword match="AbstractSelectableChannel" />
- <keyword match="AbstractSelectionKey" />
- <keyword match="AbstractSelector" />
- <keyword match="AbstractSequentialList" />
- <keyword match="AbstractSet" />
- <keyword match="AbstractSpinnerModel" />
- <keyword match="AbstractTableModel" />
- <keyword match="AbstractUndoableEdit" />
- <keyword match="AbstractWriter" />
- <keyword match="AccessControlContext" />
- <keyword match="AccessControlException" />
- <keyword match="AccessController" />
- <keyword match="AccessException" />
- <keyword match="Accessible" />
- <keyword match="AccessibleAction" />
- <keyword match="AccessibleBundle" />
- <keyword match="AccessibleComponent" />
- <keyword match="AccessibleContext" />
- <keyword match="AccessibleEditableText" />
- <keyword match="AccessibleExtendedComponent" />
- <keyword match="AccessibleExtendedTable" />
- <keyword match="AccessibleHyperlink" />
- <keyword match="AccessibleHypertext" />
- <keyword match="AccessibleIcon" />
- <keyword match="AccessibleKeyBinding" />
- <keyword match="AccessibleObject" />
- <keyword match="AccessibleRelation" />
- <keyword match="AccessibleRelationSet" />
- <keyword match="AccessibleResourceBundle" />
- <keyword match="AccessibleRole" />
- <keyword match="AccessibleSelection" />
- <keyword match="AccessibleState" />
- <keyword match="AccessibleStateSet" />
- <keyword match="AccessibleTable" />
- <keyword match="AccessibleTableModelChange" />
- <keyword match="AccessibleText" />
- <keyword match="AccessibleValue" />
- <keyword match="AccountExpiredException" />
- <keyword match="Acl" />
- <keyword match="AclEntry" />
- <keyword match="AclNotFoundException" />
- <keyword match="Action" />
- <keyword match="ActionEvent" />
- <keyword match="ActionListener" />
- <keyword match="ActionMap" />
- <keyword match="ActionMapUIResource" />
- <keyword match="Activatable" />
- <keyword match="ActivateFailedException" />
- <keyword match="ActivationDesc" />
- <keyword match="ActivationException" />
- <keyword match="ActivationGroup" />
- <keyword match="ActivationGroup_Stub" />
- <keyword match="ActivationGroupDesc" />
- <keyword match="ActivationGroupID" />
- <keyword match="ActivationID" />
- <keyword match="ActivationInstantiator" />
- <keyword match="ActivationMonitor" />
- <keyword match="ActivationSystem" />
- <keyword match="Activator" />
- <keyword match="ActiveEvent" />
- <keyword match="AdapterActivator" />
- <keyword match="AdapterActivatorOperations" />
- <keyword match="AdapterAlreadyExists" />
- <keyword match="AdapterAlreadyExistsHelper" />
- <keyword match="AdapterInactive" />
- <keyword match="AdapterInactiveHelper" />
- <keyword match="AdapterNonExistent" />
- <keyword match="AdapterNonExistentHelper" />
- <keyword match="AddressHelper" />
- <keyword match="Adjustable" />
- <keyword match="AdjustmentEvent" />
- <keyword match="AdjustmentListener" />
- <keyword match="Adler32" />
- <keyword match="AffineTransform" />
- <keyword match="AffineTransformOp" />
- <keyword match="AlgorithmParameterGenerator" />
- <keyword match="AlgorithmParameterGeneratorSpi" />
- <keyword match="AlgorithmParameters" />
- <keyword match="AlgorithmParameterSpec" />
- <keyword match="AlgorithmParametersSpi" />
- <keyword match="AllPermission" />
- <keyword match="AlphaComposite" />
- <keyword match="AlreadyBound" />
- <keyword match="AlreadyBoundException" />
- <keyword match="AlreadyBoundHelper" />
- <keyword match="AlreadyBoundHolder" />
- <keyword match="AlreadyConnectedException" />
- <keyword match="AncestorEvent" />
- <keyword match="AncestorListener" />
- <keyword match="Annotation" />
- <keyword match="Any" />
- <keyword match="AnyHolder" />
- <keyword match="AnySeqHelper" />
- <keyword match="AnySeqHelper" />
- <keyword match="AnySeqHolder" />
- <keyword match="AppConfigurationEntry" />
- <keyword match="Applet" />
- <keyword match="AppletContext" />
- <keyword match="AppletInitializer" />
- <keyword match="AppletStub" />
- <keyword match="ApplicationException" />
- <keyword match="Arc2D" />
- <keyword match="Area" />
- <keyword match="AreaAveragingScaleFilter" />
- <keyword match="ARG_IN" />
- <keyword match="ARG_INOUT" />
- <keyword match="ARG_OUT" />
- <keyword match="ArithmeticException" />
- <keyword match="Array" />
- <keyword match="Array" />
- <keyword match="ArrayIndexOutOfBoundsException" />
- <keyword match="ArrayList" />
- <keyword match="Arrays" />
- <keyword match="ArrayStoreException" />
- <keyword match="AssertionError" />
- <keyword match="AsyncBoxView" />
- <keyword match="AsynchronousCloseException" />
- <keyword match="Attr" />
- <keyword match="Attribute" />
- <keyword match="Attribute" />
- <keyword match="AttributedCharacterIterator" />
- <keyword match="AttributedString" />
- <keyword match="AttributeException" />
- <keyword match="AttributeInUseException" />
- <keyword match="AttributeList" />
- <keyword match="AttributeList" />
- <keyword match="AttributeListImpl" />
- <keyword match="AttributeModificationException" />
- <keyword match="Attributes" />
- <keyword match="Attributes" />
- <keyword match="Attributes" />
- <keyword match="AttributeSet" />
- <keyword match="AttributeSet" />
- <keyword match="AttributeSetUtilities" />
- <keyword match="AttributesImpl" />
- <keyword match="AudioClip" />
- <keyword match="AudioFileFormat" />
- <keyword match="AudioFileReader" />
- <keyword match="AudioFileWriter" />
- <keyword match="AudioFormat" />
- <keyword match="AudioInputStream" />
- <keyword match="AudioPermission" />
- <keyword match="AudioSystem" />
- <keyword match="AuthenticationException" />
- <keyword match="AuthenticationNotSupportedException" />
- <keyword match="Authenticator" />
- <keyword match="AuthPermission" />
- <keyword match="Autoscroll" />
- <keyword match="AWTError" />
- <keyword match="AWTEvent" />
- <keyword match="AWTEventListener" />
- <keyword match="AWTEventListenerProxy" />
- <keyword match="AWTEventMulticaster" />
- <keyword match="AWTException" />
- <keyword match="AWTKeyStroke" />
- <keyword match="AWTPermission" />
- <keyword match="BackingStoreException" />
- <keyword match="BAD_CONTEXT" />
- <keyword match="BAD_INV_ORDER" />
- <keyword match="BAD_OPERATION" />
- <keyword match="BAD_PARAM" />
- <keyword match="BAD_POLICY" />
- <keyword match="BAD_POLICY_TYPE" />
- <keyword match="BAD_POLICY_VALUE" />
- <keyword match="BAD_TYPECODE" />
- <keyword match="BadKind" />
- <keyword match="BadLocationException" />
- <keyword match="BadPaddingException" />
- <keyword match="BandCombineOp" />
- <keyword match="BandedSampleModel" />
- <keyword match="BasicArrowButton" />
- <keyword match="BasicAttribute" />
- <keyword match="BasicAttributes" />
- <keyword match="BasicBorders" />
- <keyword match="BasicButtonListener" />
- <keyword match="BasicButtonUI" />
- <keyword match="BasicCheckBoxMenuItemUI" />
- <keyword match="BasicCheckBoxUI" />
- <keyword match="BasicColorChooserUI" />
- <keyword match="BasicComboBoxEditor" />
- <keyword match="BasicComboBoxRenderer" />
- <keyword match="BasicComboBoxUI" />
- <keyword match="BasicComboPopup" />
- <keyword match="BasicDesktopIconUI" />
- <keyword match="BasicDesktopPaneUI" />
- <keyword match="BasicDirectoryModel" />
- <keyword match="BasicEditorPaneUI" />
- <keyword match="BasicFileChooserUI" />
- <keyword match="BasicFormattedTextFieldUI" />
- <keyword match="BasicGraphicsUtils" />
- <keyword match="BasicHTML" />
- <keyword match="BasicIconFactory" />
- <keyword match="BasicInternalFrameTitlePane" />
- <keyword match="BasicInternalFrameUI" />
- <keyword match="BasicLabelUI" />
- <keyword match="BasicListUI" />
- <keyword match="BasicLookAndFeel" />
- <keyword match="BasicMenuBarUI" />
- <keyword match="BasicMenuItemUI" />
- <keyword match="BasicMenuUI" />
- <keyword match="BasicOptionPaneUI" />
- <keyword match="BasicPanelUI" />
- <keyword match="BasicPasswordFieldUI" />
- <keyword match="BasicPermission" />
- <keyword match="BasicPopupMenuSeparatorUI" />
- <keyword match="BasicPopupMenuUI" />
- <keyword match="BasicProgressBarUI" />
- <keyword match="BasicRadioButtonMenuItemUI" />
- <keyword match="BasicRadioButtonUI" />
- <keyword match="BasicRootPaneUI" />
- <keyword match="BasicScrollBarUI" />
- <keyword match="BasicScrollPaneUI" />
- <keyword match="BasicSeparatorUI" />
- <keyword match="BasicSliderUI" />
- <keyword match="BasicSpinnerUI" />
- <keyword match="BasicSplitPaneDivider" />
- <keyword match="BasicSplitPaneUI" />
- <keyword match="BasicStroke" />
- <keyword match="BasicTabbedPaneUI" />
- <keyword match="BasicTableHeaderUI" />
- <keyword match="BasicTableUI" />
- <keyword match="BasicTextAreaUI" />
- <keyword match="BasicTextFieldUI" />
- <keyword match="BasicTextPaneUI" />
- <keyword match="BasicTextUI" />
- <keyword match="BasicToggleButtonUI" />
- <keyword match="BasicToolBarSeparatorUI" />
- <keyword match="BasicToolBarUI" />
- <keyword match="BasicToolTipUI" />
- <keyword match="BasicTreeUI" />
- <keyword match="BasicViewportUI" />
- <keyword match="BatchUpdateException" />
- <keyword match="BeanContext" />
- <keyword match="BeanContextChild" />
- <keyword match="BeanContextChildComponentProxy" />
- <keyword match="BeanContextChildSupport" />
- <keyword match="BeanContextContainerProxy" />
- <keyword match="BeanContextEvent" />
- <keyword match="BeanContextMembershipEvent" />
- <keyword match="BeanContextMembershipListener" />
- <keyword match="BeanContextProxy" />
- <keyword match="BeanContextServiceAvailableEvent" />
- <keyword match="BeanContextServiceProvider" />
- <keyword match="BeanContextServiceProviderBeanInfo" />
- <keyword match="BeanContextServiceRevokedEvent" />
- <keyword match="BeanContextServiceRevokedListener" />
- <keyword match="BeanContextServices" />
- <keyword match="BeanContextServicesListener" />
- <keyword match="BeanContextServicesSupport" />
- <keyword match="BeanContextSupport" />
- <keyword match="BeanDescriptor" />
- <keyword match="BeanInfo" />
- <keyword match="Beans" />
- <keyword match="BevelBorder" />
- <keyword match="Bidi" />
- <keyword match="BigDecimal" />
- <keyword match="BigInteger" />
- <keyword match="BinaryRefAddr" />
- <keyword match="BindException" />
- <keyword match="Binding" />
- <keyword match="Binding" />
- <keyword match="BindingHelper" />
- <keyword match="BindingHolder" />
- <keyword match="BindingIterator" />
- <keyword match="BindingIteratorHelper" />
- <keyword match="BindingIteratorHolder" />
- <keyword match="BindingIteratorOperations" />
- <keyword match="BindingIteratorPOA" />
- <keyword match="BindingListHelper" />
- <keyword match="BindingListHolder" />
- <keyword match="BindingType" />
- <keyword match="BindingTypeHelper" />
- <keyword match="BindingTypeHolder" />
- <keyword match="BitSet" />
- <keyword match="Blob" />
- <keyword match="BlockView" />
- <keyword match="Book" />
- <keyword match="Boolean" />
- <keyword match="BooleanControl" />
- <keyword match="BooleanHolder" />
- <keyword match="BooleanSeqHelper" />
- <keyword match="BooleanSeqHolder" />
- <keyword match="Border" />
- <keyword match="BorderFactory" />
- <keyword match="BorderLayout" />
- <keyword match="BorderUIResource" />
- <keyword match="BoundedRangeModel" />
- <keyword match="Bounds" />
- <keyword match="Bounds" />
- <keyword match="Box" />
- <keyword match="BoxedValueHelper" />
- <keyword match="BoxLayout" />
- <keyword match="BoxView" />
- <keyword match="BreakIterator" />
- <keyword match="Buffer" />
- <keyword match="BufferCapabilities" />
- <keyword match="BufferedImage" />
- <keyword match="BufferedImageFilter" />
- <keyword match="BufferedImageOp" />
- <keyword match="BufferedInputStream" />
- <keyword match="BufferedOutputStream" />
- <keyword match="BufferedReader" />
- <keyword match="BufferedWriter" />
- <keyword match="BufferOverflowException" />
- <keyword match="BufferStrategy" />
- <keyword match="BufferUnderflowException" />
- <keyword match="Button" />
- <keyword match="ButtonGroup" />
- <keyword match="ButtonModel" />
- <keyword match="ButtonUI" />
- <keyword match="Byte" />
- <keyword match="ByteArrayInputStream" />
- <keyword match="ByteArrayOutputStream" />
- <keyword match="ByteBuffer" />
- <keyword match="ByteChannel" />
- <keyword match="ByteHolder" />
- <keyword match="ByteLookupTable" />
- <keyword match="ByteOrder" />
- <keyword match="Calendar" />
- <keyword match="CallableStatement" />
- <keyword match="Callback" />
- <keyword match="CallbackHandler" />
- <keyword match="CancelablePrintJob" />
- <keyword match="CancelledKeyException" />
- <keyword match="CannotProceed" />
- <keyword match="CannotProceedException" />
- <keyword match="CannotProceedHelper" />
- <keyword match="CannotProceedHolder" />
- <keyword match="CannotRedoException" />
- <keyword match="CannotUndoException" />
- <keyword match="Canvas" />
- <keyword match="CardLayout" />
- <keyword match="Caret" />
- <keyword match="CaretEvent" />
- <keyword match="CaretListener" />
- <keyword match="CDATASection" />
- <keyword match="CellEditor" />
- <keyword match="CellEditorListener" />
- <keyword match="CellRendererPane" />
- <keyword match="Certificate" />
- <keyword match="Certificate" />
- <keyword match="Certificate" />
-
- <keyword match="CertificateEncodingException" />
- <keyword match="CertificateEncodingException" />
- <keyword match="CertificateException" />
- <keyword match="CertificateException" />
- <keyword match="CertificateExpiredException" />
- <keyword match="CertificateExpiredException" />
- <keyword match="CertificateFactory" />
- <keyword match="CertificateFactorySpi" />
- <keyword match="CertificateNotYetValidException" />
- <keyword match="CertificateNotYetValidException" />
- <keyword match="CertificateParsingException" />
- <keyword match="CertificateParsingException" />
- <keyword match="CertPath" />
-
- <keyword match="CertPathBuilder" />
- <keyword match="CertPathBuilderException" />
- <keyword match="CertPathBuilderResult" />
- <keyword match="CertPathBuilderSpi" />
- <keyword match="CertPathParameters" />
- <keyword match="CertPathValidator" />
- <keyword match="CertPathValidatorException" />
- <keyword match="CertPathValidatorResult" />
- <keyword match="CertPathValidatorSpi" />
- <keyword match="CertSelector" />
- <keyword match="CertStore" />
- <keyword match="CertStoreException" />
- <keyword match="CertStoreParameters" />
- <keyword match="CertStoreSpi" />
- <keyword match="ChangedCharSetException" />
- <keyword match="ChangeEvent" />
- <keyword match="ChangeListener" />
- <keyword match="Channel" />
- <keyword match="ChannelBinding" />
- <keyword match="Channels" />
- <keyword match="Character" />
-
-
- <keyword match="CharacterCodingException" />
- <keyword match="CharacterData" />
- <keyword match="CharacterIterator" />
- <keyword match="CharArrayReader" />
- <keyword match="CharArrayWriter" />
- <keyword match="CharBuffer" />
- <keyword match="CharConversionException" />
- <keyword match="CharHolder" />
- <keyword match="CharSeqHelper" />
- <keyword match="CharSeqHolder" />
- <keyword match="CharSequence" />
- <keyword match="Charset" />
- <keyword match="CharsetDecoder" />
- <keyword match="CharsetEncoder" />
- <keyword match="CharsetProvider" />
- <keyword match="Checkbox" />
- <keyword match="CheckboxGroup" />
- <keyword match="CheckboxMenuItem" />
- <keyword match="CheckedInputStream" />
- <keyword match="CheckedOutputStream" />
- <keyword match="Checksum" />
- <keyword match="Choice" />
- <keyword match="ChoiceCallback" />
- <keyword match="ChoiceFormat" />
- <keyword match="Chromaticity" />
- <keyword match="Cipher" />
- <keyword match="CipherInputStream" />
- <keyword match="CipherOutputStream" />
- <keyword match="CipherSpi" />
- <keyword match="Class" />
- <keyword match="ClassCastException" />
- <keyword match="ClassCircularityError" />
- <keyword match="ClassDesc" />
- <keyword match="ClassFormatError" />
- <keyword match="ClassLoader" />
- <keyword match="ClassNotFoundException" />
- <keyword match="ClientRequestInfo" />
- <keyword match="ClientRequestInfoOperations" />
- <keyword match="ClientRequestInterceptor" />
- <keyword match="ClientRequestInterceptorOperations" />
- <keyword match="Clip" />
- <keyword match="Clipboard" />
- <keyword match="ClipboardOwner" />
- <keyword match="Clob" />
- <keyword match="Cloneable" />
- <keyword match="CloneNotSupportedException" />
- <keyword match="ClosedByInterruptException" />
- <keyword match="ClosedChannelException" />
- <keyword match="ClosedSelectorException" />
- <keyword match="CMMException" />
- <keyword match="Codec" />
- <keyword match="CodecFactory" />
- <keyword match="CodecFactoryHelper" />
- <keyword match="CodecFactoryOperations" />
- <keyword match="CodecOperations" />
- <keyword match="CoderMalfunctionError" />
- <keyword match="CoderResult" />
- <keyword match="CodeSets" />
- <keyword match="CodeSource" />
- <keyword match="CodingErrorAction" />
- <keyword match="CollationElementIterator" />
- <keyword match="CollationKey" />
- <keyword match="Collator" />
- <keyword match="Collection" />
- <keyword match="CollectionCertStoreParameters" />
- <keyword match="Collections" />
- <keyword match="Color" />
- <keyword match="ColorChooserComponentFactory" />
- <keyword match="ColorChooserUI" />
- <keyword match="ColorConvertOp" />
- <keyword match="ColorModel" />
- <keyword match="ColorSelectionModel" />
- <keyword match="ColorSpace" />
- <keyword match="ColorSupported" />
- <keyword match="ColorUIResource" />
- <keyword match="ComboBoxEditor" />
- <keyword match="ComboBoxModel" />
- <keyword match="ComboBoxUI" />
- <keyword match="ComboPopup" />
- <keyword match="COMM_FAILURE" />
- <keyword match="Comment" />
- <keyword match="CommunicationException" />
- <keyword match="Comparable" />
- <keyword match="Comparator" />
- <keyword match="Compiler" />
- <keyword match="CompletionStatus" />
- <keyword match="CompletionStatusHelper" />
- <keyword match="Component" />
- <keyword match="ComponentAdapter" />
- <keyword match="ComponentColorModel" />
- <keyword match="ComponentEvent" />
- <keyword match="ComponentIdHelper" />
- <keyword match="ComponentInputMap" />
- <keyword match="ComponentInputMapUIResource" />
- <keyword match="ComponentListener" />
- <keyword match="ComponentOrientation" />
- <keyword match="ComponentSampleModel" />
- <keyword match="ComponentUI" />
- <keyword match="ComponentView" />
- <keyword match="Composite" />
- <keyword match="CompositeContext" />
- <keyword match="CompositeName" />
- <keyword match="CompositeView" />
- <keyword match="CompoundBorder" />
- <keyword match="CompoundControl" />
-
- <keyword match="CompoundEdit" />
- <keyword match="CompoundName" />
- <keyword match="Compression" />
- <keyword match="ConcurrentModificationException" />
- <keyword match="Configuration" />
- <keyword match="ConfigurationException" />
- <keyword match="ConfirmationCallback" />
- <keyword match="ConnectException" />
- <keyword match="ConnectException" />
- <keyword match="ConnectIOException" />
- <keyword match="Connection" />
- <keyword match="ConnectionEvent" />
- <keyword match="ConnectionEventListener" />
- <keyword match="ConnectionPendingException" />
- <keyword match="ConnectionPoolDataSource" />
- <keyword match="ConsoleHandler" />
- <keyword match="Constructor" />
- <keyword match="Container" />
- <keyword match="ContainerAdapter" />
- <keyword match="ContainerEvent" />
- <keyword match="ContainerListener" />
- <keyword match="ContainerOrderFocusTraversalPolicy" />
- <keyword match="ContentHandler" />
- <keyword match="ContentHandler" />
- <keyword match="ContentHandlerFactory" />
- <keyword match="ContentModel" />
- <keyword match="Context" />
- <keyword match="Context" />
- <keyword match="ContextList" />
- <keyword match="ContextNotEmptyException" />
- <keyword match="ContextualRenderedImageFactory" />
- <keyword match="Control" />
- <keyword match="Control" />
-
- <keyword match="ControlFactory" />
- <keyword match="ControllerEventListener" />
- <keyword match="ConvolveOp" />
- <keyword match="CookieHolder" />
- <keyword match="Copies" />
- <keyword match="CopiesSupported" />
- <keyword match="CRC32" />
- <keyword match="CredentialExpiredException" />
- <keyword match="CRL" />
- <keyword match="CRLException" />
- <keyword match="CRLSelector" />
- <keyword match="CropImageFilter" />
- <keyword match="CSS" />
-
- <keyword match="CTX_RESTRICT_SCOPE" />
- <keyword match="CubicCurve2D" />
-
-
- <keyword match="Currency" />
- <keyword match="Current" />
- <keyword match="Current" />
- <keyword match="Current" />
- <keyword match="CurrentHelper" />
- <keyword match="CurrentHelper" />
- <keyword match="CurrentHelper" />
- <keyword match="CurrentHolder" />
- <keyword match="CurrentOperations" />
- <keyword match="CurrentOperations" />
- <keyword match="CurrentOperations" />
- <keyword match="Cursor" />
- <keyword match="Customizer" />
- <keyword match="CustomMarshal" />
- <keyword match="CustomValue" />
- <keyword match="DATA_CONVERSION" />
- <keyword match="DatabaseMetaData" />
- <keyword match="DataBuffer" />
- <keyword match="DataBufferByte" />
- <keyword match="DataBufferDouble" />
- <keyword match="DataBufferFloat" />
- <keyword match="DataBufferInt" />
- <keyword match="DataBufferShort" />
- <keyword match="DataBufferUShort" />
- <keyword match="DataFlavor" />
- <keyword match="DataFormatException" />
- <keyword match="DatagramChannel" />
- <keyword match="DatagramPacket" />
- <keyword match="DatagramSocket" />
- <keyword match="DatagramSocketImpl" />
- <keyword match="DatagramSocketImplFactory" />
- <keyword match="DataInput" />
- <keyword match="DataInputStream" />
- <keyword match="DataInputStream" />
- <keyword match="DataLine" />
-
- <keyword match="DataOutput" />
- <keyword match="DataOutputStream" />
- <keyword match="DataOutputStream" />
- <keyword match="DataSource" />
- <keyword match="DataTruncation" />
- <keyword match="Date" />
- <keyword match="Date" />
- <keyword match="DateFormat" />
-
- <keyword match="DateFormatSymbols" />
- <keyword match="DateFormatter" />
- <keyword match="DateTimeAtCompleted" />
- <keyword match="DateTimeAtCreation" />
- <keyword match="DateTimeAtProcessing" />
- <keyword match="DateTimeSyntax" />
- <keyword match="DebugGraphics" />
- <keyword match="DecimalFormat" />
- <keyword match="DecimalFormatSymbols" />
- <keyword match="DeclHandler" />
- <keyword match="DefaultBoundedRangeModel" />
- <keyword match="DefaultButtonModel" />
- <keyword match="DefaultCaret" />
- <keyword match="DefaultCellEditor" />
- <keyword match="DefaultColorSelectionModel" />
- <keyword match="DefaultComboBoxModel" />
- <keyword match="DefaultDesktopManager" />
- <keyword match="DefaultEditorKit" />
-
-
-
-
-
-
-
-
- <keyword match="DefaultFocusManager" />
- <keyword match="DefaultFocusTraversalPolicy" />
- <keyword match="DefaultFormatter" />
- <keyword match="DefaultFormatterFactory" />
- <keyword match="DefaultHandler" />
- <keyword match="DefaultHighlighter" />
-
- <keyword match="DefaultKeyboardFocusManager" />
- <keyword match="DefaultListCellRenderer" />
-
- <keyword match="DefaultListModel" />
- <keyword match="DefaultListSelectionModel" />
- <keyword match="DefaultMenuLayout" />
- <keyword match="DefaultMetalTheme" />
- <keyword match="DefaultMutableTreeNode" />
- <keyword match="DefaultPersistenceDelegate" />
- <keyword match="DefaultSingleSelectionModel" />
- <keyword match="DefaultStyledDocument" />
-
-
- <keyword match="DefaultTableCellRenderer" />
-
- <keyword match="DefaultTableColumnModel" />
- <keyword match="DefaultTableModel" />
- <keyword match="DefaultTextUI" />
- <keyword match="DefaultTreeCellEditor" />
- <keyword match="DefaultTreeCellRenderer" />
- <keyword match="DefaultTreeModel" />
- <keyword match="DefaultTreeSelectionModel" />
- <keyword match="DefinitionKind" />
- <keyword match="DefinitionKindHelper" />
- <keyword match="Deflater" />
- <keyword match="DeflaterOutputStream" />
- <keyword match="Delegate" />
- <keyword match="Delegate" />
- <keyword match="Delegate" />
- <keyword match="DelegationPermission" />
- <keyword match="DESedeKeySpec" />
- <keyword match="DesignMode" />
- <keyword match="DESKeySpec" />
- <keyword match="DesktopIconUI" />
- <keyword match="DesktopManager" />
- <keyword match="DesktopPaneUI" />
- <keyword match="Destination" />
- <keyword match="Destroyable" />
- <keyword match="DestroyFailedException" />
- <keyword match="DGC" />
- <keyword match="DHGenParameterSpec" />
- <keyword match="DHKey" />
- <keyword match="DHParameterSpec" />
- <keyword match="DHPrivateKey" />
- <keyword match="DHPrivateKeySpec" />
- <keyword match="DHPublicKey" />
- <keyword match="DHPublicKeySpec" />
- <keyword match="Dialog" />
- <keyword match="Dictionary" />
- <keyword match="DigestException" />
- <keyword match="DigestInputStream" />
- <keyword match="DigestOutputStream" />
- <keyword match="Dimension" />
- <keyword match="Dimension2D" />
- <keyword match="DimensionUIResource" />
- <keyword match="DirContext" />
- <keyword match="DirectColorModel" />
- <keyword match="DirectoryManager" />
- <keyword match="DirObjectFactory" />
- <keyword match="DirStateFactory" />
-
- <keyword match="DisplayMode" />
- <keyword match="DnDConstants" />
- <keyword match="Doc" />
- <keyword match="DocAttribute" />
- <keyword match="DocAttributeSet" />
- <keyword match="DocFlavor" />
-
-
-
-
-
-
-
- <keyword match="DocPrintJob" />
- <keyword match="Document" />
- <keyword match="Document" />
- <keyword match="DocumentBuilder" />
- <keyword match="DocumentBuilderFactory" />
- <keyword match="DocumentEvent" />
-
-
- <keyword match="DocumentFilter" />
-
- <keyword match="DocumentFragment" />
- <keyword match="DocumentHandler" />
- <keyword match="DocumentListener" />
- <keyword match="DocumentName" />
- <keyword match="DocumentParser" />
- <keyword match="DocumentType" />
- <keyword match="DomainCombiner" />
- <keyword match="DomainManager" />
- <keyword match="DomainManagerOperations" />
- <keyword match="DOMException" />
- <keyword match="DOMImplementation" />
- <keyword match="DOMLocator" />
- <keyword match="DOMResult" />
- <keyword match="DOMSource" />
- <keyword match="Double" />
- <keyword match="DoubleBuffer" />
- <keyword match="DoubleHolder" />
- <keyword match="DoubleSeqHelper" />
- <keyword match="DoubleSeqHolder" />
- <keyword match="DragGestureEvent" />
- <keyword match="DragGestureListener" />
- <keyword match="DragGestureRecognizer" />
- <keyword match="DragSource" />
- <keyword match="DragSourceAdapter" />
- <keyword match="DragSourceContext" />
- <keyword match="DragSourceDragEvent" />
- <keyword match="DragSourceDropEvent" />
- <keyword match="DragSourceEvent" />
- <keyword match="DragSourceListener" />
- <keyword match="DragSourceMotionListener" />
- <keyword match="Driver" />
- <keyword match="DriverManager" />
- <keyword match="DriverPropertyInfo" />
- <keyword match="DropTarget" />
-
- <keyword match="DropTargetAdapter" />
- <keyword match="DropTargetContext" />
- <keyword match="DropTargetDragEvent" />
- <keyword match="DropTargetDropEvent" />
- <keyword match="DropTargetEvent" />
- <keyword match="DropTargetListener" />
- <keyword match="DSAKey" />
- <keyword match="DSAKeyPairGenerator" />
- <keyword match="DSAParameterSpec" />
- <keyword match="DSAParams" />
- <keyword match="DSAPrivateKey" />
- <keyword match="DSAPrivateKeySpec" />
- <keyword match="DSAPublicKey" />
- <keyword match="DSAPublicKeySpec" />
- <keyword match="DTD" />
- <keyword match="DTDConstants" />
- <keyword match="DTDHandler" />
- <keyword match="DuplicateName" />
- <keyword match="DuplicateNameHelper" />
- <keyword match="DynamicImplementation" />
- <keyword match="DynamicImplementation" />
- <keyword match="DynAny" />
- <keyword match="DynAny" />
- <keyword match="DynAnyFactory" />
- <keyword match="DynAnyFactoryHelper" />
- <keyword match="DynAnyFactoryOperations" />
- <keyword match="DynAnyHelper" />
- <keyword match="DynAnyOperations" />
- <keyword match="DynAnySeqHelper" />
- <keyword match="DynArray" />
- <keyword match="DynArray" />
- <keyword match="DynArrayHelper" />
- <keyword match="DynArrayOperations" />
- <keyword match="DynEnum" />
- <keyword match="DynEnum" />
- <keyword match="DynEnumHelper" />
- <keyword match="DynEnumOperations" />
- <keyword match="DynFixed" />
- <keyword match="DynFixed" />
- <keyword match="DynFixedHelper" />
- <keyword match="DynFixedOperations" />
- <keyword match="DynSequence" />
- <keyword match="DynSequence" />
- <keyword match="DynSequenceHelper" />
- <keyword match="DynSequenceOperations" />
- <keyword match="DynStruct" />
- <keyword match="DynStruct" />
- <keyword match="DynStructHelper" />
- <keyword match="DynStructOperations" />
- <keyword match="DynUnion" />
- <keyword match="DynUnion" />
- <keyword match="DynUnionHelper" />
- <keyword match="DynUnionOperations" />
- <keyword match="DynValue" />
- <keyword match="DynValue" />
- <keyword match="DynValueBox" />
- <keyword match="DynValueBoxOperations" />
- <keyword match="DynValueCommon" />
- <keyword match="DynValueCommonOperations" />
- <keyword match="DynValueHelper" />
- <keyword match="DynValueOperations" />
- <keyword match="EditorKit" />
- <keyword match="Element" />
- <keyword match="Element" />
- <keyword match="Element" />
- <keyword match="ElementIterator" />
- <keyword match="Ellipse2D" />
-
-
- <keyword match="EmptyBorder" />
- <keyword match="EmptyStackException" />
- <keyword match="EncodedKeySpec" />
- <keyword match="Encoder" />
- <keyword match="Encoding" />
- <keyword match="ENCODING_CDR_ENCAPS" />
- <keyword match="EncryptedPrivateKeyInfo" />
- <keyword match="Entity" />
- <keyword match="Entity" />
- <keyword match="EntityReference" />
- <keyword match="EntityResolver" />
- <keyword match="EnumControl" />
-
- <keyword match="Enumeration" />
- <keyword match="EnumSyntax" />
- <keyword match="Environment" />
- <keyword match="EOFException" />
- <keyword match="Error" />
- <keyword match="ErrorHandler" />
- <keyword match="ErrorListener" />
- <keyword match="ErrorManager" />
- <keyword match="EtchedBorder" />
- <keyword match="Event" />
- <keyword match="EventContext" />
- <keyword match="EventDirContext" />
- <keyword match="EventHandler" />
- <keyword match="EventListener" />
- <keyword match="EventListenerList" />
- <keyword match="EventListenerProxy" />
- <keyword match="EventObject" />
- <keyword match="EventQueue" />
- <keyword match="EventSetDescriptor" />
- <keyword match="Exception" />
- <keyword match="ExceptionInInitializerError" />
- <keyword match="ExceptionList" />
- <keyword match="ExceptionListener" />
- <keyword match="ExemptionMechanism" />
- <keyword match="ExemptionMechanismException" />
- <keyword match="ExemptionMechanismSpi" />
- <keyword match="ExpandVetoException" />
- <keyword match="ExportException" />
- <keyword match="Expression" />
- <keyword match="ExtendedRequest" />
- <keyword match="ExtendedResponse" />
- <keyword match="Externalizable" />
- <keyword match="FactoryConfigurationError" />
- <keyword match="FailedLoginException" />
- <keyword match="FeatureDescriptor" />
- <keyword match="Fidelity" />
- <keyword match="Field" />
- <keyword match="FieldNameHelper" />
- <keyword match="FieldNameHelper" />
- <keyword match="FieldPosition" />
- <keyword match="FieldView" />
- <keyword match="File" />
- <keyword match="FileCacheImageInputStream" />
- <keyword match="FileCacheImageOutputStream" />
- <keyword match="FileChannel" />
-
- <keyword match="FileChooserUI" />
- <keyword match="FileDescriptor" />
- <keyword match="FileDialog" />
- <keyword match="FileFilter" />
- <keyword match="FileFilter" />
- <keyword match="FileHandler" />
- <keyword match="FileImageInputStream" />
- <keyword match="FileImageOutputStream" />
- <keyword match="FileInputStream" />
- <keyword match="FileLock" />
- <keyword match="FileLockInterruptionException" />
- <keyword match="FilenameFilter" />
- <keyword match="FileNameMap" />
- <keyword match="FileNotFoundException" />
- <keyword match="FileOutputStream" />
- <keyword match="FilePermission" />
- <keyword match="FileReader" />
- <keyword match="FileSystemView" />
- <keyword match="FileView" />
- <keyword match="FileWriter" />
- <keyword match="Filter" />
- <keyword match="FilteredImageSource" />
- <keyword match="FilterInputStream" />
- <keyword match="FilterOutputStream" />
- <keyword match="FilterReader" />
- <keyword match="FilterWriter" />
- <keyword match="Finishings" />
- <keyword match="FixedHeightLayoutCache" />
- <keyword match="FixedHolder" />
- <keyword match="FlatteningPathIterator" />
- <keyword match="FlavorException" />
- <keyword match="FlavorMap" />
- <keyword match="FlavorTable" />
- <keyword match="Float" />
- <keyword match="FloatBuffer" />
- <keyword match="FloatControl" />
-
- <keyword match="FloatHolder" />
- <keyword match="FloatSeqHelper" />
- <keyword match="FloatSeqHolder" />
- <keyword match="FlowLayout" />
- <keyword match="FlowView" />
-
- <keyword match="FocusAdapter" />
- <keyword match="FocusEvent" />
- <keyword match="FocusListener" />
- <keyword match="FocusManager" />
- <keyword match="FocusTraversalPolicy" />
- <keyword match="Font" />
- <keyword match="FontFormatException" />
- <keyword match="FontMetrics" />
- <keyword match="FontRenderContext" />
- <keyword match="FontUIResource" />
- <keyword match="Format" />
-
- <keyword match="FormatConversionProvider" />
- <keyword match="FormatMismatch" />
- <keyword match="FormatMismatchHelper" />
- <keyword match="Formatter" />
- <keyword match="FormView" />
- <keyword match="ForwardRequest" />
- <keyword match="ForwardRequest" />
- <keyword match="ForwardRequestHelper" />
- <keyword match="ForwardRequestHelper" />
- <keyword match="Frame" />
- <keyword match="FREE_MEM" />
- <keyword match="GapContent" />
- <keyword match="GatheringByteChannel" />
- <keyword match="GeneralPath" />
- <keyword match="GeneralSecurityException" />
- <keyword match="GlyphJustificationInfo" />
- <keyword match="GlyphMetrics" />
- <keyword match="GlyphVector" />
- <keyword match="GlyphView" />
-
- <keyword match="GradientPaint" />
- <keyword match="GraphicAttribute" />
- <keyword match="Graphics" />
- <keyword match="Graphics2D" />
- <keyword match="GraphicsConfigTemplate" />
- <keyword match="GraphicsConfiguration" />
- <keyword match="GraphicsDevice" />
- <keyword match="GraphicsEnvironment" />
- <keyword match="GrayFilter" />
- <keyword match="GregorianCalendar" />
- <keyword match="GridBagConstraints" />
- <keyword match="GridBagLayout" />
- <keyword match="GridLayout" />
- <keyword match="Group" />
- <keyword match="GSSContext" />
- <keyword match="GSSCredential" />
- <keyword match="GSSException" />
- <keyword match="GSSManager" />
- <keyword match="GSSName" />
- <keyword match="Guard" />
- <keyword match="GuardedObject" />
- <keyword match="GZIPInputStream" />
- <keyword match="GZIPOutputStream" />
- <keyword match="Handler" />
- <keyword match="HandlerBase" />
- <keyword match="HandshakeCompletedEvent" />
- <keyword match="HandshakeCompletedListener" />
- <keyword match="HasControls" />
- <keyword match="HashAttributeSet" />
- <keyword match="HashDocAttributeSet" />
- <keyword match="HashMap" />
- <keyword match="HashPrintJobAttributeSet" />
- <keyword match="HashPrintRequestAttributeSet" />
- <keyword match="HashPrintServiceAttributeSet" />
- <keyword match="HashSet" />
- <keyword match="Hashtable" />
- <keyword match="HeadlessException" />
- <keyword match="HierarchyBoundsAdapter" />
- <keyword match="HierarchyBoundsListener" />
- <keyword match="HierarchyEvent" />
- <keyword match="HierarchyListener" />
- <keyword match="Highlighter" />
-
-
- <keyword match="HostnameVerifier" />
- <keyword match="HTML" />
-
-
-
- <keyword match="HTMLDocument" />
-
- <keyword match="HTMLEditorKit" />
-
-
-
-
-
-
- <keyword match="HTMLFrameHyperlinkEvent" />
- <keyword match="HTMLWriter" />
- <keyword match="HttpsURLConnection" />
- <keyword match="HttpURLConnection" />
- <keyword match="HyperlinkEvent" />
-
- <keyword match="HyperlinkListener" />
- <keyword match="ICC_ColorSpace" />
- <keyword match="ICC_Profile" />
- <keyword match="ICC_ProfileGray" />
- <keyword match="ICC_ProfileRGB" />
- <keyword match="Icon" />
- <keyword match="IconUIResource" />
- <keyword match="IconView" />
- <keyword match="ID_ASSIGNMENT_POLICY_ID" />
- <keyword match="ID_UNIQUENESS_POLICY_ID" />
- <keyword match="IdAssignmentPolicy" />
- <keyword match="IdAssignmentPolicyOperations" />
- <keyword match="IdAssignmentPolicyValue" />
- <keyword match="IdentifierHelper" />
- <keyword match="Identity" />
- <keyword match="IdentityHashMap" />
- <keyword match="IdentityScope" />
- <keyword match="IDLEntity" />
- <keyword match="IDLType" />
- <keyword match="IDLTypeHelper" />
- <keyword match="IDLTypeOperations" />
- <keyword match="IdUniquenessPolicy" />
- <keyword match="IdUniquenessPolicyOperations" />
- <keyword match="IdUniquenessPolicyValue" />
- <keyword match="IIOByteBuffer" />
- <keyword match="IIOException" />
- <keyword match="IIOImage" />
- <keyword match="IIOInvalidTreeException" />
- <keyword match="IIOMetadata" />
- <keyword match="IIOMetadataController" />
- <keyword match="IIOMetadataFormat" />
- <keyword match="IIOMetadataFormatImpl" />
- <keyword match="IIOMetadataNode" />
- <keyword match="IIOParam" />
- <keyword match="IIOParamController" />
- <keyword match="IIOReadProgressListener" />
- <keyword match="IIOReadUpdateListener" />
- <keyword match="IIOReadWarningListener" />
- <keyword match="IIORegistry" />
- <keyword match="IIOServiceProvider" />
- <keyword match="IIOWriteProgressListener" />
- <keyword match="IIOWriteWarningListener" />
- <keyword match="IllegalAccessError" />
- <keyword match="IllegalAccessException" />
- <keyword match="IllegalArgumentException" />
- <keyword match="IllegalBlockingModeException" />
- <keyword match="IllegalBlockSizeException" />
- <keyword match="IllegalCharsetNameException" />
- <keyword match="IllegalComponentStateException" />
- <keyword match="IllegalMonitorStateException" />
- <keyword match="IllegalPathStateException" />
- <keyword match="IllegalSelectorException" />
- <keyword match="IllegalStateException" />
- <keyword match="IllegalThreadStateException" />
- <keyword match="Image" />
- <keyword match="ImageCapabilities" />
- <keyword match="ImageConsumer" />
- <keyword match="ImageFilter" />
- <keyword match="ImageGraphicAttribute" />
- <keyword match="ImageIcon" />
- <keyword match="ImageInputStream" />
- <keyword match="ImageInputStreamImpl" />
- <keyword match="ImageInputStreamSpi" />
- <keyword match="ImageIO" />
- <keyword match="ImageObserver" />
- <keyword match="ImageOutputStream" />
- <keyword match="ImageOutputStreamImpl" />
- <keyword match="ImageOutputStreamSpi" />
- <keyword match="ImageProducer" />
- <keyword match="ImageReader" />
- <keyword match="ImageReaderSpi" />
- <keyword match="ImageReaderWriterSpi" />
- <keyword match="ImageReadParam" />
- <keyword match="ImageTranscoder" />
- <keyword match="ImageTranscoderSpi" />
- <keyword match="ImageTypeSpecifier" />
- <keyword match="ImageView" />
- <keyword match="ImageWriteParam" />
- <keyword match="ImageWriter" />
- <keyword match="ImageWriterSpi" />
- <keyword match="ImagingOpException" />
- <keyword match="IMP_LIMIT" />
- <keyword match="IMPLICIT_ACTIVATION_POLICY_ID" />
- <keyword match="ImplicitActivationPolicy" />
- <keyword match="ImplicitActivationPolicyOperations" />
- <keyword match="ImplicitActivationPolicyValue" />
- <keyword match="IncompatibleClassChangeError" />
- <keyword match="InconsistentTypeCode" />
- <keyword match="InconsistentTypeCode" />
- <keyword match="InconsistentTypeCodeHelper" />
- <keyword match="IndexColorModel" />
- <keyword match="IndexedPropertyDescriptor" />
- <keyword match="IndexOutOfBoundsException" />
- <keyword match="IndirectionException" />
- <keyword match="Inet4Address" />
- <keyword match="Inet6Address" />
- <keyword match="InetAddress" />
- <keyword match="InetSocketAddress" />
- <keyword match="Inflater" />
- <keyword match="InflaterInputStream" />
- <keyword match="InheritableThreadLocal" />
- <keyword match="InitialContext" />
- <keyword match="InitialContextFactory" />
- <keyword match="InitialContextFactoryBuilder" />
- <keyword match="InitialDirContext" />
- <keyword match="INITIALIZE" />
- <keyword match="InitialLdapContext" />
- <keyword match="InlineView" />
- <keyword match="InputContext" />
- <keyword match="InputEvent" />
- <keyword match="InputMap" />
- <keyword match="InputMapUIResource" />
- <keyword match="InputMethod" />
- <keyword match="InputMethodContext" />
- <keyword match="InputMethodDescriptor" />
- <keyword match="InputMethodEvent" />
- <keyword match="InputMethodHighlight" />
- <keyword match="InputMethodListener" />
- <keyword match="InputMethodRequests" />
- <keyword match="InputSource" />
- <keyword match="InputStream" />
- <keyword match="InputStream" />
- <keyword match="InputStream" />
- <keyword match="InputStreamReader" />
- <keyword match="InputSubset" />
- <keyword match="InputVerifier" />
- <keyword match="Insets" />
- <keyword match="InsetsUIResource" />
- <keyword match="InstantiationError" />
- <keyword match="InstantiationException" />
- <keyword match="Instrument" />
- <keyword match="InsufficientResourcesException" />
- <keyword match="IntBuffer" />
- <keyword match="Integer" />
- <keyword match="IntegerSyntax" />
- <keyword match="Interceptor" />
- <keyword match="InterceptorOperations" />
- <keyword match="INTERNAL" />
- <keyword match="InternalError" />
- <keyword match="InternalFrameAdapter" />
- <keyword match="InternalFrameEvent" />
- <keyword match="InternalFrameFocusTraversalPolicy" />
- <keyword match="InternalFrameListener" />
- <keyword match="InternalFrameUI" />
- <keyword match="InternationalFormatter" />
- <keyword match="InterruptedException" />
- <keyword match="InterruptedIOException" />
- <keyword match="InterruptedNamingException" />
- <keyword match="InterruptibleChannel" />
- <keyword match="INTF_REPOS" />
- <keyword match="IntHolder" />
- <keyword match="IntrospectionException" />
- <keyword match="Introspector" />
- <keyword match="INV_FLAG" />
- <keyword match="INV_IDENT" />
- <keyword match="INV_OBJREF" />
- <keyword match="INV_POLICY" />
- <keyword match="Invalid" />
- <keyword match="INVALID_TRANSACTION" />
- <keyword match="InvalidAddress" />
- <keyword match="InvalidAddressHelper" />
- <keyword match="InvalidAddressHolder" />
- <keyword match="InvalidAlgorithmParameterException" />
- <keyword match="InvalidAttributeIdentifierException" />
- <keyword match="InvalidAttributesException" />
- <keyword match="InvalidAttributeValueException" />
- <keyword match="InvalidClassException" />
- <keyword match="InvalidDnDOperationException" />
- <keyword match="InvalidKeyException" />
- <keyword match="InvalidKeySpecException" />
- <keyword match="InvalidMarkException" />
- <keyword match="InvalidMidiDataException" />
- <keyword match="InvalidName" />
- <keyword match="InvalidName" />
- <keyword match="InvalidName" />
- <keyword match="InvalidNameException" />
- <keyword match="InvalidNameHelper" />
- <keyword match="InvalidNameHelper" />
- <keyword match="InvalidNameHolder" />
- <keyword match="InvalidObjectException" />
- <keyword match="InvalidParameterException" />
- <keyword match="InvalidParameterSpecException" />
- <keyword match="InvalidPolicy" />
- <keyword match="InvalidPolicyHelper" />
- <keyword match="InvalidPreferencesFormatException" />
- <keyword match="InvalidSearchControlsException" />
- <keyword match="InvalidSearchFilterException" />
- <keyword match="InvalidSeq" />
- <keyword match="InvalidSlot" />
- <keyword match="InvalidSlotHelper" />
- <keyword match="InvalidTransactionException" />
- <keyword match="InvalidTypeForEncoding" />
- <keyword match="InvalidTypeForEncodingHelper" />
- <keyword match="InvalidValue" />
- <keyword match="InvalidValue" />
- <keyword match="InvalidValueHelper" />
- <keyword match="InvocationEvent" />
- <keyword match="InvocationHandler" />
- <keyword match="InvocationTargetException" />
- <keyword match="InvokeHandler" />
- <keyword match="IOException" />
- <keyword match="IOR" />
- <keyword match="IORHelper" />
- <keyword match="IORHolder" />
- <keyword match="IORInfo" />
- <keyword match="IORInfoOperations" />
- <keyword match="IORInterceptor" />
- <keyword match="IORInterceptorOperations" />
- <keyword match="IRObject" />
- <keyword match="IRObjectOperations" />
- <keyword match="IstringHelper" />
- <keyword match="ItemEvent" />
- <keyword match="ItemListener" />
- <keyword match="ItemSelectable" />
- <keyword match="Iterator" />
- <keyword match="IvParameterSpec" />
- <keyword match="JApplet" />
- <keyword match="JarEntry" />
- <keyword match="JarException" />
- <keyword match="JarFile" />
- <keyword match="JarInputStream" />
- <keyword match="JarOutputStream" />
- <keyword match="JarURLConnection" />
- <keyword match="JButton" />
- <keyword match="JCheckBox" />
- <keyword match="JCheckBoxMenuItem" />
- <keyword match="JColorChooser" />
- <keyword match="JComboBox" />
-
- <keyword match="JComponent" />
- <keyword match="JDesktopPane" />
- <keyword match="JDialog" />
- <keyword match="JEditorPane" />
- <keyword match="JFileChooser" />
- <keyword match="JFormattedTextField" />
-
-
- <keyword match="JFrame" />
- <keyword match="JInternalFrame" />
-
- <keyword match="JLabel" />
- <keyword match="JLayeredPane" />
- <keyword match="JList" />
- <keyword match="JMenu" />
- <keyword match="JMenuBar" />
- <keyword match="JMenuItem" />
- <keyword match="JobAttributes" />
-
-
-
-
-
- <keyword match="JobHoldUntil" />
- <keyword match="JobImpressions" />
- <keyword match="JobImpressionsCompleted" />
- <keyword match="JobImpressionsSupported" />
- <keyword match="JobKOctets" />
- <keyword match="JobKOctetsProcessed" />
- <keyword match="JobKOctetsSupported" />
- <keyword match="JobMediaSheets" />
- <keyword match="JobMediaSheetsCompleted" />
- <keyword match="JobMediaSheetsSupported" />
- <keyword match="JobMessageFromOperator" />
- <keyword match="JobName" />
- <keyword match="JobOriginatingUserName" />
- <keyword match="JobPriority" />
- <keyword match="JobPrioritySupported" />
- <keyword match="JobSheets" />
- <keyword match="JobState" />
- <keyword match="JobStateReason" />
- <keyword match="JobStateReasons" />
- <keyword match="JOptionPane" />
- <keyword match="JPanel" />
- <keyword match="JPasswordField" />
- <keyword match="JPEGHuffmanTable" />
- <keyword match="JPEGImageReadParam" />
- <keyword match="JPEGImageWriteParam" />
- <keyword match="JPEGQTable" />
- <keyword match="JPopupMenu" />
-
- <keyword match="JProgressBar" />
- <keyword match="JRadioButton" />
- <keyword match="JRadioButtonMenuItem" />
- <keyword match="JRootPane" />
- <keyword match="JScrollBar" />
- <keyword match="JScrollPane" />
- <keyword match="JSeparator" />
- <keyword match="JSlider" />
- <keyword match="JSpinner" />
-
-
-
-
- <keyword match="JSplitPane" />
- <keyword match="JTabbedPane" />
- <keyword match="JTable" />
- <keyword match="JTableHeader" />
- <keyword match="JTextArea" />
- <keyword match="JTextComponent" />
-
- <keyword match="JTextField" />
- <keyword match="JTextPane" />
- <keyword match="JToggleButton" />
-
- <keyword match="JToolBar" />
-
- <keyword match="JToolTip" />
- <keyword match="JTree" />
-
-
- <keyword match="JViewport" />
- <keyword match="JWindow" />
- <keyword match="KerberosKey" />
- <keyword match="KerberosPrincipal" />
- <keyword match="KerberosTicket" />
- <keyword match="Kernel" />
- <keyword match="Key" />
- <keyword match="KeyAdapter" />
- <keyword match="KeyAgreement" />
- <keyword match="KeyAgreementSpi" />
- <keyword match="KeyboardFocusManager" />
- <keyword match="KeyEvent" />
- <keyword match="KeyEventDispatcher" />
- <keyword match="KeyEventPostProcessor" />
- <keyword match="KeyException" />
- <keyword match="KeyFactory" />
- <keyword match="KeyFactorySpi" />
- <keyword match="KeyGenerator" />
- <keyword match="KeyGeneratorSpi" />
- <keyword match="KeyListener" />
- <keyword match="KeyManagementException" />
- <keyword match="KeyManager" />
- <keyword match="KeyManagerFactory" />
- <keyword match="KeyManagerFactorySpi" />
- <keyword match="Keymap" />
- <keyword match="KeyPair" />
- <keyword match="KeyPairGenerator" />
- <keyword match="KeyPairGeneratorSpi" />
- <keyword match="KeySpec" />
- <keyword match="KeyStore" />
- <keyword match="KeyStoreException" />
- <keyword match="KeyStoreSpi" />
- <keyword match="KeyStroke" />
- <keyword match="Label" />
- <keyword match="LabelUI" />
- <keyword match="LabelView" />
- <keyword match="LanguageCallback" />
- <keyword match="LastOwnerException" />
- <keyword match="LayeredHighlighter" />
-
- <keyword match="LayoutFocusTraversalPolicy" />
- <keyword match="LayoutManager" />
- <keyword match="LayoutManager2" />
- <keyword match="LayoutQueue" />
- <keyword match="LDAPCertStoreParameters" />
- <keyword match="LdapContext" />
- <keyword match="LdapReferralException" />
- <keyword match="Lease" />
- <keyword match="Level" />
- <keyword match="LexicalHandler" />
- <keyword match="LIFESPAN_POLICY_ID" />
- <keyword match="LifespanPolicy" />
- <keyword match="LifespanPolicyOperations" />
- <keyword match="LifespanPolicyValue" />
- <keyword match="LimitExceededException" />
- <keyword match="Line" />
-
- <keyword match="Line2D" />
-
-
- <keyword match="LineBorder" />
- <keyword match="LineBreakMeasurer" />
- <keyword match="LineEvent" />
-
- <keyword match="LineListener" />
- <keyword match="LineMetrics" />
- <keyword match="LineNumberInputStream" />
- <keyword match="LineNumberReader" />
- <keyword match="LineUnavailableException" />
- <keyword match="LinkageError" />
- <keyword match="LinkedHashMap" />
- <keyword match="LinkedHashSet" />
- <keyword match="LinkedList" />
- <keyword match="LinkException" />
- <keyword match="LinkLoopException" />
- <keyword match="LinkRef" />
- <keyword match="List" />
- <keyword match="List" />
- <keyword match="ListCellRenderer" />
- <keyword match="ListDataEvent" />
- <keyword match="ListDataListener" />
- <keyword match="ListIterator" />
- <keyword match="ListModel" />
- <keyword match="ListResourceBundle" />
- <keyword match="ListSelectionEvent" />
- <keyword match="ListSelectionListener" />
- <keyword match="ListSelectionModel" />
- <keyword match="ListUI" />
- <keyword match="ListView" />
- <keyword match="LoaderHandler" />
- <keyword match="Locale" />
- <keyword match="LocalObject" />
- <keyword match="LocateRegistry" />
- <keyword match="LOCATION_FORWARD" />
- <keyword match="Locator" />
- <keyword match="LocatorImpl" />
- <keyword match="Logger" />
- <keyword match="LoggingPermission" />
- <keyword match="LoginContext" />
- <keyword match="LoginException" />
- <keyword match="LoginModule" />
- <keyword match="LogManager" />
- <keyword match="LogRecord" />
- <keyword match="LogStream" />
- <keyword match="Long" />
- <keyword match="LongBuffer" />
- <keyword match="LongHolder" />
- <keyword match="LongLongSeqHelper" />
- <keyword match="LongLongSeqHolder" />
- <keyword match="LongSeqHelper" />
- <keyword match="LongSeqHolder" />
- <keyword match="LookAndFeel" />
- <keyword match="LookupOp" />
- <keyword match="LookupTable" />
- <keyword match="Mac" />
- <keyword match="MacSpi" />
- <keyword match="MalformedInputException" />
- <keyword match="MalformedLinkException" />
- <keyword match="MalformedURLException" />
- <keyword match="ManagerFactoryParameters" />
- <keyword match="Manifest" />
- <keyword match="Map" />
-
- <keyword match="MappedByteBuffer" />
- <keyword match="MARSHAL" />
- <keyword match="MarshalException" />
- <keyword match="MarshalledObject" />
- <keyword match="MaskFormatter" />
- <keyword match="Matcher" />
- <keyword match="Math" />
- <keyword match="MatteBorder" />
- <keyword match="Media" />
- <keyword match="MediaName" />
- <keyword match="MediaPrintableArea" />
- <keyword match="MediaSize" />
-
-
-
-
-
- <keyword match="MediaSizeName" />
- <keyword match="MediaTracker" />
- <keyword match="MediaTray" />
- <keyword match="Member" />
- <keyword match="MemoryCacheImageInputStream" />
- <keyword match="MemoryCacheImageOutputStream" />
- <keyword match="MemoryHandler" />
- <keyword match="MemoryImageSource" />
- <keyword match="Menu" />
- <keyword match="MenuBar" />
- <keyword match="MenuBarUI" />
- <keyword match="MenuComponent" />
- <keyword match="MenuContainer" />
- <keyword match="MenuDragMouseEvent" />
- <keyword match="MenuDragMouseListener" />
- <keyword match="MenuElement" />
- <keyword match="MenuEvent" />
- <keyword match="MenuItem" />
- <keyword match="MenuItemUI" />
- <keyword match="MenuKeyEvent" />
- <keyword match="MenuKeyListener" />
- <keyword match="MenuListener" />
- <keyword match="MenuSelectionManager" />
- <keyword match="MenuShortcut" />
- <keyword match="MessageDigest" />
- <keyword match="MessageDigestSpi" />
- <keyword match="MessageFormat" />
-
- <keyword match="MessageProp" />
- <keyword match="MetaEventListener" />
- <keyword match="MetalBorders" />
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- <keyword match="MetalButtonUI" />
- <keyword match="MetalCheckBoxIcon" />
- <keyword match="MetalCheckBoxUI" />
- <keyword match="MetalComboBoxButton" />
- <keyword match="MetalComboBoxEditor" />
-
- <keyword match="MetalComboBoxIcon" />
- <keyword match="MetalComboBoxUI" />
- <keyword match="MetalDesktopIconUI" />
- <keyword match="MetalFileChooserUI" />
- <keyword match="MetalIconFactory" />
-
-
-
-
-
-
- <keyword match="MetalInternalFrameTitlePane" />
- <keyword match="MetalInternalFrameUI" />
- <keyword match="MetalLabelUI" />
- <keyword match="MetalLookAndFeel" />
- <keyword match="MetalPopupMenuSeparatorUI" />
- <keyword match="MetalProgressBarUI" />
- <keyword match="MetalRadioButtonUI" />
- <keyword match="MetalRootPaneUI" />
- <keyword match="MetalScrollBarUI" />
- <keyword match="MetalScrollButton" />
- <keyword match="MetalScrollPaneUI" />
- <keyword match="MetalSeparatorUI" />
- <keyword match="MetalSliderUI" />
- <keyword match="MetalSplitPaneUI" />
- <keyword match="MetalTabbedPaneUI" />
- <keyword match="MetalTextFieldUI" />
- <keyword match="MetalTheme" />
- <keyword match="MetalToggleButtonUI" />
- <keyword match="MetalToolBarUI" />
- <keyword match="MetalToolTipUI" />
- <keyword match="MetalTreeUI" />
- <keyword match="MetaMessage" />
- <keyword match="Method" />
- <keyword match="MethodDescriptor" />
- <keyword match="MidiChannel" />
- <keyword match="MidiDevice" />
-
- <keyword match="MidiDeviceProvider" />
- <keyword match="MidiEvent" />
- <keyword match="MidiFileFormat" />
- <keyword match="MidiFileReader" />
- <keyword match="MidiFileWriter" />
- <keyword match="MidiMessage" />
- <keyword match="MidiSystem" />
- <keyword match="MidiUnavailableException" />
- <keyword match="MimeTypeParseException" />
- <keyword match="MinimalHTMLWriter" />
- <keyword match="MissingResourceException" />
- <keyword match="Mixer" />
-
- <keyword match="MixerProvider" />
- <keyword match="ModificationItem" />
- <keyword match="Modifier" />
- <keyword match="MouseAdapter" />
- <keyword match="MouseDragGestureRecognizer" />
- <keyword match="MouseEvent" />
- <keyword match="MouseInputAdapter" />
- <keyword match="MouseInputListener" />
- <keyword match="MouseListener" />
- <keyword match="MouseMotionAdapter" />
- <keyword match="MouseMotionListener" />
- <keyword match="MouseWheelEvent" />
- <keyword match="MouseWheelListener" />
- <keyword match="MultiButtonUI" />
- <keyword match="MulticastSocket" />
- <keyword match="MultiColorChooserUI" />
- <keyword match="MultiComboBoxUI" />
- <keyword match="MultiDesktopIconUI" />
- <keyword match="MultiDesktopPaneUI" />
- <keyword match="MultiDoc" />
- <keyword match="MultiDocPrintJob" />
- <keyword match="MultiDocPrintService" />
- <keyword match="MultiFileChooserUI" />
- <keyword match="MultiInternalFrameUI" />
- <keyword match="MultiLabelUI" />
- <keyword match="MultiListUI" />
- <keyword match="MultiLookAndFeel" />
- <keyword match="MultiMenuBarUI" />
- <keyword match="MultiMenuItemUI" />
- <keyword match="MultiOptionPaneUI" />
- <keyword match="MultiPanelUI" />
- <keyword match="MultiPixelPackedSampleModel" />
- <keyword match="MultipleComponentProfileHelper" />
- <keyword match="MultipleComponentProfileHolder" />
- <keyword match="MultipleDocumentHandling" />
- <keyword match="MultipleMaster" />
- <keyword match="MultiPopupMenuUI" />
- <keyword match="MultiProgressBarUI" />
- <keyword match="MultiRootPaneUI" />
- <keyword match="MultiScrollBarUI" />
- <keyword match="MultiScrollPaneUI" />
- <keyword match="MultiSeparatorUI" />
- <keyword match="MultiSliderUI" />
- <keyword match="MultiSpinnerUI" />
- <keyword match="MultiSplitPaneUI" />
- <keyword match="MultiTabbedPaneUI" />
- <keyword match="MultiTableHeaderUI" />
- <keyword match="MultiTableUI" />
- <keyword match="MultiTextUI" />
- <keyword match="MultiToolBarUI" />
- <keyword match="MultiToolTipUI" />
- <keyword match="MultiTreeUI" />
- <keyword match="MultiViewportUI" />
- <keyword match="MutableAttributeSet" />
- <keyword match="MutableComboBoxModel" />
- <keyword match="MutableTreeNode" />
- <keyword match="Name" />
- <keyword match="NameAlreadyBoundException" />
- <keyword match="NameCallback" />
- <keyword match="NameClassPair" />
- <keyword match="NameComponent" />
- <keyword match="NameComponentHelper" />
- <keyword match="NameComponentHolder" />
- <keyword match="NamedNodeMap" />
- <keyword match="NamedValue" />
- <keyword match="NameDynAnyPair" />
- <keyword match="NameDynAnyPairHelper" />
- <keyword match="NameDynAnyPairSeqHelper" />
- <keyword match="NameHelper" />
- <keyword match="NameHolder" />
- <keyword match="NameNotFoundException" />
- <keyword match="NameParser" />
- <keyword match="NamespaceChangeListener" />
- <keyword match="NamespaceSupport" />
- <keyword match="NameValuePair" />
- <keyword match="NameValuePair" />
- <keyword match="NameValuePairHelper" />
- <keyword match="NameValuePairHelper" />
- <keyword match="NameValuePairSeqHelper" />
- <keyword match="Naming" />
- <keyword match="NamingContext" />
- <keyword match="NamingContextExt" />
- <keyword match="NamingContextExtHelper" />
- <keyword match="NamingContextExtHolder" />
- <keyword match="NamingContextExtOperations" />
- <keyword match="NamingContextExtPOA" />
- <keyword match="NamingContextHelper" />
- <keyword match="NamingContextHolder" />
- <keyword match="NamingContextOperations" />
- <keyword match="NamingContextPOA" />
- <keyword match="NamingEnumeration" />
- <keyword match="NamingEvent" />
- <keyword match="NamingException" />
- <keyword match="NamingExceptionEvent" />
- <keyword match="NamingListener" />
- <keyword match="NamingManager" />
- <keyword match="NamingSecurityException" />
- <keyword match="NavigationFilter" />
-
- <keyword match="NegativeArraySizeException" />
- <keyword match="NetPermission" />
- <keyword match="NetworkInterface" />
- <keyword match="NO_IMPLEMENT" />
- <keyword match="NO_MEMORY" />
- <keyword match="NO_PERMISSION" />
- <keyword match="NO_RESOURCES" />
- <keyword match="NO_RESPONSE" />
- <keyword match="NoClassDefFoundError" />
- <keyword match="NoConnectionPendingException" />
- <keyword match="NoContext" />
- <keyword match="NoContextHelper" />
- <keyword match="Node" />
- <keyword match="NodeChangeEvent" />
- <keyword match="NodeChangeListener" />
- <keyword match="NodeList" />
- <keyword match="NoInitialContextException" />
- <keyword match="NoninvertibleTransformException" />
- <keyword match="NonReadableChannelException" />
- <keyword match="NonWritableChannelException" />
- <keyword match="NoPermissionException" />
- <keyword match="NoRouteToHostException" />
- <keyword match="NoServant" />
- <keyword match="NoServantHelper" />
- <keyword match="NoSuchAlgorithmException" />
- <keyword match="NoSuchAttributeException" />
- <keyword match="NoSuchElementException" />
- <keyword match="NoSuchFieldError" />
- <keyword match="NoSuchFieldException" />
- <keyword match="NoSuchMethodError" />
- <keyword match="NoSuchMethodException" />
- <keyword match="NoSuchObjectException" />
- <keyword match="NoSuchPaddingException" />
- <keyword match="NoSuchProviderException" />
- <keyword match="NotActiveException" />
- <keyword match="Notation" />
- <keyword match="NotBoundException" />
- <keyword match="NotContextException" />
- <keyword match="NotEmpty" />
- <keyword match="NotEmptyHelper" />
- <keyword match="NotEmptyHolder" />
- <keyword match="NotFound" />
- <keyword match="NotFoundHelper" />
- <keyword match="NotFoundHolder" />
- <keyword match="NotFoundReason" />
- <keyword match="NotFoundReasonHelper" />
- <keyword match="NotFoundReasonHolder" />
- <keyword match="NotOwnerException" />
- <keyword match="NotSerializableException" />
- <keyword match="NotYetBoundException" />
- <keyword match="NotYetConnectedException" />
- <keyword match="NullCipher" />
- <keyword match="NullPointerException" />
- <keyword match="Number" />
- <keyword match="NumberFormat" />
-
- <keyword match="NumberFormatException" />
- <keyword match="NumberFormatter" />
- <keyword match="NumberOfDocuments" />
- <keyword match="NumberOfInterveningJobs" />
- <keyword match="NumberUp" />
- <keyword match="NumberUpSupported" />
- <keyword match="NumericShaper" />
- <keyword match="NVList" />
- <keyword match="OBJ_ADAPTER" />
- <keyword match="Object" />
- <keyword match="OBJECT_NOT_EXIST" />
- <keyword match="ObjectAlreadyActive" />
- <keyword match="ObjectAlreadyActiveHelper" />
- <keyword match="ObjectChangeListener" />
- <keyword match="ObjectFactory" />
- <keyword match="ObjectFactoryBuilder" />
- <keyword match="ObjectHelper" />
- <keyword match="ObjectHolder" />
- <keyword match="ObjectIdHelper" />
- <keyword match="ObjectImpl" />
- <keyword match="ObjectImpl" />
- <keyword match="ObjectInput" />
- <keyword match="ObjectInputStream" />
-
- <keyword match="ObjectInputValidation" />
- <keyword match="ObjectNotActive" />
- <keyword match="ObjectNotActiveHelper" />
- <keyword match="ObjectOutput" />
- <keyword match="ObjectOutputStream" />
-
- <keyword match="ObjectStreamClass" />
- <keyword match="ObjectStreamConstants" />
- <keyword match="ObjectStreamException" />
- <keyword match="ObjectStreamField" />
- <keyword match="ObjectView" />
- <keyword match="ObjID" />
- <keyword match="Observable" />
- <keyword match="Observer" />
- <keyword match="OctetSeqHelper" />
- <keyword match="OctetSeqHolder" />
- <keyword match="Oid" />
- <keyword match="OMGVMCID" />
- <keyword match="OpenType" />
- <keyword match="Operation" />
- <keyword match="OperationNotSupportedException" />
- <keyword match="Option" />
- <keyword match="OptionalDataException" />
- <keyword match="OptionPaneUI" />
- <keyword match="ORB" />
- <keyword match="ORB" />
- <keyword match="ORBInitializer" />
- <keyword match="ORBInitializerOperations" />
- <keyword match="ORBInitInfo" />
- <keyword match="ORBInitInfoOperations" />
- <keyword match="OrientationRequested" />
- <keyword match="OutOfMemoryError" />
- <keyword match="OutputDeviceAssigned" />
- <keyword match="OutputKeys" />
- <keyword match="OutputStream" />
- <keyword match="OutputStream" />
- <keyword match="OutputStream" />
- <keyword match="OutputStreamWriter" />
- <keyword match="OverlappingFileLockException" />
- <keyword match="OverlayLayout" />
- <keyword match="Owner" />
- <keyword match="Package" />
- <keyword match="PackedColorModel" />
- <keyword match="Pageable" />
- <keyword match="PageAttributes" />
-
-
-
-
-
- <keyword match="PageFormat" />
- <keyword match="PageRanges" />
- <keyword match="PagesPerMinute" />
- <keyword match="PagesPerMinuteColor" />
- <keyword match="Paint" />
- <keyword match="PaintContext" />
- <keyword match="PaintEvent" />
- <keyword match="Panel" />
- <keyword match="PanelUI" />
- <keyword match="Paper" />
- <keyword match="ParagraphView" />
- <keyword match="ParagraphView" />
- <keyword match="Parameter" />
- <keyword match="ParameterBlock" />
- <keyword match="ParameterDescriptor" />
- <keyword match="ParameterMetaData" />
- <keyword match="ParameterMode" />
- <keyword match="ParameterModeHelper" />
- <keyword match="ParameterModeHolder" />
- <keyword match="ParseException" />
- <keyword match="ParsePosition" />
- <keyword match="Parser" />
- <keyword match="Parser" />
- <keyword match="ParserAdapter" />
- <keyword match="ParserConfigurationException" />
- <keyword match="ParserDelegator" />
- <keyword match="ParserFactory" />
- <keyword match="PartialResultException" />
- <keyword match="PasswordAuthentication" />
- <keyword match="PasswordCallback" />
- <keyword match="PasswordView" />
- <keyword match="Patch" />
- <keyword match="PathIterator" />
- <keyword match="Pattern" />
- <keyword match="PatternSyntaxException" />
- <keyword match="PBEKey" />
- <keyword match="PBEKeySpec" />
- <keyword match="PBEParameterSpec" />
- <keyword match="PDLOverrideSupported" />
- <keyword match="Permission" />
- <keyword match="Permission" />
- <keyword match="PermissionCollection" />
- <keyword match="Permissions" />
- <keyword match="PERSIST_STORE" />
- <keyword match="PersistenceDelegate" />
- <keyword match="PhantomReference" />
- <keyword match="Pipe" />
-
-
- <keyword match="PipedInputStream" />
- <keyword match="PipedOutputStream" />
- <keyword match="PipedReader" />
- <keyword match="PipedWriter" />
- <keyword match="PixelGrabber" />
- <keyword match="PixelInterleavedSampleModel" />
- <keyword match="PKCS8EncodedKeySpec" />
- <keyword match="PKIXBuilderParameters" />
- <keyword match="PKIXCertPathBuilderResult" />
- <keyword match="PKIXCertPathChecker" />
- <keyword match="PKIXCertPathValidatorResult" />
- <keyword match="PKIXParameters" />
- <keyword match="PlainDocument" />
- <keyword match="PlainView" />
- <keyword match="POA" />
- <keyword match="POAHelper" />
- <keyword match="POAManager" />
- <keyword match="POAManagerOperations" />
- <keyword match="POAOperations" />
- <keyword match="Point" />
- <keyword match="Point2D" />
-
-
- <keyword match="Policy" />
- <keyword match="Policy" />
- <keyword match="Policy" />
- <keyword match="PolicyError" />
- <keyword match="PolicyErrorCodeHelper" />
- <keyword match="PolicyErrorHelper" />
- <keyword match="PolicyErrorHolder" />
- <keyword match="PolicyFactory" />
- <keyword match="PolicyFactoryOperations" />
- <keyword match="PolicyHelper" />
- <keyword match="PolicyHolder" />
- <keyword match="PolicyListHelper" />
- <keyword match="PolicyListHolder" />
- <keyword match="PolicyNode" />
- <keyword match="PolicyOperations" />
- <keyword match="PolicyQualifierInfo" />
- <keyword match="PolicyTypeHelper" />
- <keyword match="Polygon" />
- <keyword match="PooledConnection" />
- <keyword match="Popup" />
- <keyword match="PopupFactory" />
- <keyword match="PopupMenu" />
- <keyword match="PopupMenuEvent" />
- <keyword match="PopupMenuListener" />
- <keyword match="PopupMenuUI" />
- <keyword match="Port" />
-
- <keyword match="PortableRemoteObject" />
- <keyword match="PortableRemoteObjectDelegate" />
- <keyword match="PortUnreachableException" />
- <keyword match="Position" />
-
- <keyword match="PreferenceChangeEvent" />
- <keyword match="PreferenceChangeListener" />
- <keyword match="Preferences" />
- <keyword match="PreferencesFactory" />
- <keyword match="PreparedStatement" />
- <keyword match="PresentationDirection" />
- <keyword match="Principal" />
- <keyword match="Principal" />
- <keyword match="PrincipalHolder" />
- <keyword match="Printable" />
- <keyword match="PrinterAbortException" />
- <keyword match="PrinterException" />
- <keyword match="PrinterGraphics" />
- <keyword match="PrinterInfo" />
- <keyword match="PrinterIOException" />
- <keyword match="PrinterIsAcceptingJobs" />
- <keyword match="PrinterJob" />
- <keyword match="PrinterLocation" />
- <keyword match="PrinterMakeAndModel" />
- <keyword match="PrinterMessageFromOperator" />
- <keyword match="PrinterMoreInfo" />
- <keyword match="PrinterMoreInfoManufacturer" />
- <keyword match="PrinterName" />
- <keyword match="PrinterResolution" />
- <keyword match="PrinterState" />
- <keyword match="PrinterStateReason" />
- <keyword match="PrinterStateReasons" />
- <keyword match="PrinterURI" />
- <keyword match="PrintEvent" />
- <keyword match="PrintException" />
- <keyword match="PrintGraphics" />
- <keyword match="PrintJob" />
- <keyword match="PrintJobAdapter" />
- <keyword match="PrintJobAttribute" />
- <keyword match="PrintJobAttributeEvent" />
- <keyword match="PrintJobAttributeListener" />
- <keyword match="PrintJobAttributeSet" />
- <keyword match="PrintJobEvent" />
- <keyword match="PrintJobListener" />
- <keyword match="PrintQuality" />
- <keyword match="PrintRequestAttribute" />
- <keyword match="PrintRequestAttributeSet" />
- <keyword match="PrintService" />
- <keyword match="PrintServiceAttribute" />
- <keyword match="PrintServiceAttributeEvent" />
- <keyword match="PrintServiceAttributeListener" />
- <keyword match="PrintServiceAttributeSet" />
- <keyword match="PrintServiceLookup" />
- <keyword match="PrintStream" />
- <keyword match="PrintWriter" />
- <keyword match="PRIVATE_MEMBER" />
- <keyword match="PrivateCredentialPermission" />
- <keyword match="PrivateKey" />
- <keyword match="PrivilegedAction" />
- <keyword match="PrivilegedActionException" />
- <keyword match="PrivilegedExceptionAction" />
- <keyword match="Process" />
- <keyword match="ProcessingInstruction" />
- <keyword match="ProfileDataException" />
- <keyword match="ProfileIdHelper" />
- <keyword match="ProgressBarUI" />
- <keyword match="ProgressMonitor" />
- <keyword match="ProgressMonitorInputStream" />
- <keyword match="Properties" />
- <keyword match="PropertyChangeEvent" />
- <keyword match="PropertyChangeListener" />
- <keyword match="PropertyChangeListenerProxy" />
- <keyword match="PropertyChangeSupport" />
- <keyword match="PropertyDescriptor" />
- <keyword match="PropertyEditor" />
- <keyword match="PropertyEditorManager" />
- <keyword match="PropertyEditorSupport" />
- <keyword match="PropertyPermission" />
- <keyword match="PropertyResourceBundle" />
- <keyword match="PropertyVetoException" />
- <keyword match="ProtectionDomain" />
- <keyword match="ProtocolException" />
- <keyword match="Provider" />
- <keyword match="ProviderException" />
- <keyword match="Proxy" />
- <keyword match="PSSParameterSpec" />
- <keyword match="PUBLIC_MEMBER" />
- <keyword match="PublicKey" />
- <keyword match="PushbackInputStream" />
- <keyword match="PushbackReader" />
- <keyword match="QuadCurve2D" />
-
-
- <keyword match="QueuedJobCount" />
- <keyword match="Random" />
- <keyword match="RandomAccess" />
- <keyword match="RandomAccessFile" />
- <keyword match="Raster" />
- <keyword match="RasterFormatException" />
- <keyword match="RasterOp" />
- <keyword match="RC2ParameterSpec" />
- <keyword match="RC5ParameterSpec" />
- <keyword match="ReadableByteChannel" />
- <keyword match="Reader" />
- <keyword match="ReadOnlyBufferException" />
- <keyword match="Receiver" />
- <keyword match="Rectangle" />
- <keyword match="Rectangle2D" />
-
-
- <keyword match="RectangularShape" />
- <keyword match="Ref" />
- <keyword match="RefAddr" />
- <keyword match="Reference" />
- <keyword match="Reference" />
- <keyword match="Referenceable" />
- <keyword match="ReferenceQueue" />
- <keyword match="ReferenceUriSchemesSupported" />
- <keyword match="ReferralException" />
- <keyword match="ReflectPermission" />
- <keyword match="Refreshable" />
- <keyword match="RefreshFailedException" />
- <keyword match="RegisterableService" />
- <keyword match="Registry" />
- <keyword match="RegistryHandler" />
- <keyword match="RemarshalException" />
- <keyword match="Remote" />
- <keyword match="RemoteCall" />
- <keyword match="RemoteException" />
- <keyword match="RemoteObject" />
- <keyword match="RemoteRef" />
- <keyword match="RemoteServer" />
- <keyword match="RemoteStub" />
- <keyword match="RenderableImage" />
- <keyword match="RenderableImageOp" />
- <keyword match="RenderableImageProducer" />
- <keyword match="RenderContext" />
- <keyword match="RenderedImage" />
- <keyword match="RenderedImageFactory" />
- <keyword match="Renderer" />
- <keyword match="RenderingHints" />
-
- <keyword match="RepaintManager" />
- <keyword match="ReplicateScaleFilter" />
- <keyword match="RepositoryIdHelper" />
- <keyword match="Request" />
- <keyword match="REQUEST_PROCESSING_POLICY_ID" />
- <keyword match="RequestInfo" />
- <keyword match="RequestInfoOperations" />
- <keyword match="RequestingUserName" />
- <keyword match="RequestProcessingPolicy" />
- <keyword match="RequestProcessingPolicyOperations" />
- <keyword match="RequestProcessingPolicyValue" />
- <keyword match="RescaleOp" />
- <keyword match="ResolutionSyntax" />
- <keyword match="Resolver" />
- <keyword match="ResolveResult" />
- <keyword match="ResourceBundle" />
- <keyword match="ResponseHandler" />
- <keyword match="Result" />
- <keyword match="ResultSet" />
- <keyword match="ResultSetMetaData" />
- <keyword match="ReverbType" />
- <keyword match="RGBImageFilter" />
- <keyword match="RMIClassLoader" />
- <keyword match="RMIClassLoaderSpi" />
- <keyword match="RMIClientSocketFactory" />
- <keyword match="RMIFailureHandler" />
- <keyword match="RMISecurityException" />
- <keyword match="RMISecurityManager" />
- <keyword match="RMIServerSocketFactory" />
- <keyword match="RMISocketFactory" />
- <keyword match="Robot" />
- <keyword match="RootPaneContainer" />
- <keyword match="RootPaneUI" />
- <keyword match="RoundRectangle2D" />
-
-
- <keyword match="RowMapper" />
- <keyword match="RowSet" />
- <keyword match="RowSetEvent" />
- <keyword match="RowSetInternal" />
- <keyword match="RowSetListener" />
- <keyword match="RowSetMetaData" />
- <keyword match="RowSetReader" />
- <keyword match="RowSetWriter" />
- <keyword match="RSAKey" />
- <keyword match="RSAKeyGenParameterSpec" />
- <keyword match="RSAMultiPrimePrivateCrtKey" />
- <keyword match="RSAMultiPrimePrivateCrtKeySpec" />
- <keyword match="RSAOtherPrimeInfo" />
- <keyword match="RSAPrivateCrtKey" />
- <keyword match="RSAPrivateCrtKeySpec" />
- <keyword match="RSAPrivateKey" />
- <keyword match="RSAPrivateKeySpec" />
- <keyword match="RSAPublicKey" />
- <keyword match="RSAPublicKeySpec" />
- <keyword match="RTFEditorKit" />
- <keyword match="RuleBasedCollator" />
- <keyword match="Runnable" />
- <keyword match="Runtime" />
- <keyword match="RunTime" />
- <keyword match="RuntimeException" />
- <keyword match="RunTimeOperations" />
- <keyword match="RuntimePermission" />
- <keyword match="SampleModel" />
- <keyword match="Savepoint" />
- <keyword match="SAXException" />
- <keyword match="SAXNotRecognizedException" />
- <keyword match="SAXNotSupportedException" />
- <keyword match="SAXParseException" />
- <keyword match="SAXParser" />
- <keyword match="SAXParserFactory" />
- <keyword match="SAXResult" />
- <keyword match="SAXSource" />
- <keyword match="SAXTransformerFactory" />
- <keyword match="ScatteringByteChannel" />
- <keyword match="SchemaViolationException" />
- <keyword match="Scrollable" />
- <keyword match="Scrollbar" />
- <keyword match="ScrollBarUI" />
- <keyword match="ScrollPane" />
- <keyword match="ScrollPaneAdjustable" />
- <keyword match="ScrollPaneConstants" />
- <keyword match="ScrollPaneLayout" />
-
- <keyword match="ScrollPaneUI" />
- <keyword match="SealedObject" />
- <keyword match="SearchControls" />
- <keyword match="SearchResult" />
- <keyword match="SecretKey" />
- <keyword match="SecretKeyFactory" />
- <keyword match="SecretKeyFactorySpi" />
- <keyword match="SecretKeySpec" />
- <keyword match="SecureClassLoader" />
- <keyword match="SecureRandom" />
- <keyword match="SecureRandomSpi" />
- <keyword match="Security" />
- <keyword match="SecurityException" />
- <keyword match="SecurityManager" />
- <keyword match="SecurityPermission" />
- <keyword match="Segment" />
- <keyword match="SelectableChannel" />
- <keyword match="SelectionKey" />
- <keyword match="Selector" />
- <keyword match="SelectorProvider" />
- <keyword match="SeparatorUI" />
- <keyword match="Sequence" />
- <keyword match="SequenceInputStream" />
- <keyword match="Sequencer" />
-
- <keyword match="Serializable" />
- <keyword match="SerializablePermission" />
- <keyword match="Servant" />
- <keyword match="SERVANT_RETENTION_POLICY_ID" />
- <keyword match="ServantActivator" />
- <keyword match="ServantActivatorHelper" />
- <keyword match="ServantActivatorOperations" />
- <keyword match="ServantActivatorPOA" />
- <keyword match="ServantAlreadyActive" />
- <keyword match="ServantAlreadyActiveHelper" />
- <keyword match="ServantLocator" />
- <keyword match="ServantLocatorHelper" />
- <keyword match="ServantLocatorOperations" />
- <keyword match="ServantLocatorPOA" />
- <keyword match="ServantManager" />
- <keyword match="ServantManagerOperations" />
- <keyword match="ServantNotActive" />
- <keyword match="ServantNotActiveHelper" />
- <keyword match="ServantObject" />
- <keyword match="ServantRetentionPolicy" />
- <keyword match="ServantRetentionPolicyOperations" />
- <keyword match="ServantRetentionPolicyValue" />
- <keyword match="ServerCloneException" />
- <keyword match="ServerError" />
- <keyword match="ServerException" />
- <keyword match="ServerNotActiveException" />
- <keyword match="ServerRef" />
- <keyword match="ServerRequest" />
- <keyword match="ServerRequestInfo" />
- <keyword match="ServerRequestInfoOperations" />
- <keyword match="ServerRequestInterceptor" />
- <keyword match="ServerRequestInterceptorOperations" />
- <keyword match="ServerRuntimeException" />
- <keyword match="ServerSocket" />
- <keyword match="ServerSocketChannel" />
- <keyword match="ServerSocketFactory" />
- <keyword match="ServiceContext" />
- <keyword match="ServiceContextHelper" />
- <keyword match="ServiceContextHolder" />
- <keyword match="ServiceContextListHelper" />
- <keyword match="ServiceContextListHolder" />
- <keyword match="ServiceDetail" />
- <keyword match="ServiceDetailHelper" />
- <keyword match="ServiceIdHelper" />
- <keyword match="ServiceInformation" />
- <keyword match="ServiceInformationHelper" />
- <keyword match="ServiceInformationHolder" />
- <keyword match="ServicePermission" />
- <keyword match="ServiceRegistry" />
-
- <keyword match="ServiceUI" />
- <keyword match="ServiceUIFactory" />
- <keyword match="ServiceUnavailableException" />
- <keyword match="Set" />
- <keyword match="SetOfIntegerSyntax" />
- <keyword match="SetOverrideType" />
- <keyword match="SetOverrideTypeHelper" />
- <keyword match="Severity" />
- <keyword match="Shape" />
- <keyword match="ShapeGraphicAttribute" />
- <keyword match="SheetCollate" />
- <keyword match="Short" />
- <keyword match="ShortBuffer" />
- <keyword match="ShortBufferException" />
- <keyword match="ShortHolder" />
- <keyword match="ShortLookupTable" />
- <keyword match="ShortMessage" />
- <keyword match="ShortSeqHelper" />
- <keyword match="ShortSeqHolder" />
- <keyword match="Sides" />
- <keyword match="Signature" />
- <keyword match="SignatureException" />
- <keyword match="SignatureSpi" />
- <keyword match="SignedObject" />
- <keyword match="Signer" />
- <keyword match="SimpleAttributeSet" />
- <keyword match="SimpleBeanInfo" />
- <keyword match="SimpleDateFormat" />
- <keyword match="SimpleDoc" />
- <keyword match="SimpleFormatter" />
- <keyword match="SimpleTimeZone" />
- <keyword match="SinglePixelPackedSampleModel" />
- <keyword match="SingleSelectionModel" />
- <keyword match="Size2DSyntax" />
- <keyword match="SizeLimitExceededException" />
- <keyword match="SizeRequirements" />
- <keyword match="SizeSequence" />
- <keyword match="Skeleton" />
- <keyword match="SkeletonMismatchException" />
- <keyword match="SkeletonNotFoundException" />
- <keyword match="SliderUI" />
- <keyword match="Socket" />
- <keyword match="SocketAddress" />
- <keyword match="SocketChannel" />
- <keyword match="SocketException" />
- <keyword match="SocketFactory" />
- <keyword match="SocketHandler" />
- <keyword match="SocketImpl" />
- <keyword match="SocketImplFactory" />
- <keyword match="SocketOptions" />
- <keyword match="SocketPermission" />
- <keyword match="SocketSecurityException" />
- <keyword match="SocketTimeoutException" />
- <keyword match="SoftBevelBorder" />
- <keyword match="SoftReference" />
- <keyword match="SortedMap" />
- <keyword match="SortedSet" />
- <keyword match="SortingFocusTraversalPolicy" />
- <keyword match="Soundbank" />
- <keyword match="SoundbankReader" />
- <keyword match="SoundbankResource" />
- <keyword match="Source" />
- <keyword match="SourceDataLine" />
- <keyword match="SourceLocator" />
- <keyword match="SpinnerDateModel" />
- <keyword match="SpinnerListModel" />
- <keyword match="SpinnerModel" />
- <keyword match="SpinnerNumberModel" />
- <keyword match="SpinnerUI" />
- <keyword match="SplitPaneUI" />
- <keyword match="Spring" />
- <keyword match="SpringLayout" />
-
- <keyword match="SQLData" />
- <keyword match="SQLException" />
- <keyword match="SQLInput" />
- <keyword match="SQLOutput" />
- <keyword match="SQLPermission" />
- <keyword match="SQLWarning" />
- <keyword match="SSLContext" />
- <keyword match="SSLContextSpi" />
- <keyword match="SSLException" />
- <keyword match="SSLHandshakeException" />
- <keyword match="SSLKeyException" />
- <keyword match="SSLPeerUnverifiedException" />
- <keyword match="SSLPermission" />
- <keyword match="SSLProtocolException" />
- <keyword match="SSLServerSocket" />
- <keyword match="SSLServerSocketFactory" />
- <keyword match="SSLSession" />
- <keyword match="SSLSessionBindingEvent" />
- <keyword match="SSLSessionBindingListener" />
- <keyword match="SSLSessionContext" />
- <keyword match="SSLSocket" />
- <keyword match="SSLSocketFactory" />
- <keyword match="Stack" />
- <keyword match="StackOverflowError" />
- <keyword match="StackTraceElement" />
- <keyword match="StartTlsRequest" />
- <keyword match="StartTlsResponse" />
- <keyword match="State" />
- <keyword match="StateEdit" />
- <keyword match="StateEditable" />
- <keyword match="StateFactory" />
- <keyword match="Statement" />
- <keyword match="Statement" />
- <keyword match="Streamable" />
- <keyword match="StreamableValue" />
- <keyword match="StreamCorruptedException" />
- <keyword match="StreamHandler" />
- <keyword match="StreamPrintService" />
- <keyword match="StreamPrintServiceFactory" />
- <keyword match="StreamResult" />
- <keyword match="StreamSource" />
- <keyword match="StreamTokenizer" />
- <keyword match="StrictMath" />
- <keyword match="String" />
- <keyword match="StringBuffer" />
- <keyword match="StringBufferInputStream" />
- <keyword match="StringCharacterIterator" />
- <keyword match="StringContent" />
- <keyword match="StringHolder" />
- <keyword match="StringIndexOutOfBoundsException" />
- <keyword match="StringNameHelper" />
- <keyword match="StringReader" />
- <keyword match="StringRefAddr" />
- <keyword match="StringSelection" />
- <keyword match="StringSeqHelper" />
- <keyword match="StringSeqHolder" />
- <keyword match="StringTokenizer" />
- <keyword match="StringValueHelper" />
- <keyword match="StringWriter" />
- <keyword match="Stroke" />
- <keyword match="Struct" />
- <keyword match="StructMember" />
- <keyword match="StructMemberHelper" />
- <keyword match="Stub" />
- <keyword match="StubDelegate" />
- <keyword match="StubNotFoundException" />
- <keyword match="Style" />
- <keyword match="StyleConstants" />
-
-
-
-
- <keyword match="StyleContext" />
- <keyword match="StyledDocument" />
- <keyword match="StyledEditorKit" />
-
-
-
-
-
-
-
-
- <keyword match="StyleSheet" />
-
-
- <keyword match="Subject" />
- <keyword match="SubjectDomainCombiner" />
- <keyword match="SUCCESSFUL" />
- <keyword match="SupportedValuesAttribute" />
- <keyword match="SwingConstants" />
- <keyword match="SwingPropertyChangeSupport" />
- <keyword match="SwingUtilities" />
- <keyword match="SYNC_WITH_TRANSPORT" />
- <keyword match="SyncFailedException" />
- <keyword match="SyncScopeHelper" />
- <keyword match="Synthesizer" />
- <keyword match="SysexMessage" />
- <keyword match="System" />
- <keyword match="SYSTEM_EXCEPTION" />
- <keyword match="SystemColor" />
- <keyword match="SystemException" />
- <keyword match="SystemFlavorMap" />
- <keyword match="TabableView" />
- <keyword match="TabbedPaneUI" />
- <keyword match="TabExpander" />
- <keyword match="TableCellEditor" />
- <keyword match="TableCellRenderer" />
- <keyword match="TableColumn" />
- <keyword match="TableColumnModel" />
- <keyword match="TableColumnModelEvent" />
- <keyword match="TableColumnModelListener" />
- <keyword match="TableHeaderUI" />
- <keyword match="TableModel" />
- <keyword match="TableModelEvent" />
- <keyword match="TableModelListener" />
- <keyword match="TableUI" />
- <keyword match="TableView" />
- <keyword match="TabSet" />
- <keyword match="TabStop" />
- <keyword match="TAG_ALTERNATE_IIOP_ADDRESS" />
- <keyword match="TAG_CODE_SETS" />
- <keyword match="TAG_INTERNET_IOP" />
- <keyword match="TAG_JAVA_CODEBASE" />
- <keyword match="TAG_MULTIPLE_COMPONENTS" />
- <keyword match="TAG_ORB_TYPE" />
- <keyword match="TAG_POLICIES" />
- <keyword match="TagElement" />
- <keyword match="TaggedComponent" />
- <keyword match="TaggedComponentHelper" />
- <keyword match="TaggedComponentHolder" />
- <keyword match="TaggedProfile" />
- <keyword match="TaggedProfileHelper" />
- <keyword match="TaggedProfileHolder" />
- <keyword match="TargetDataLine" />
- <keyword match="TCKind" />
- <keyword match="Templates" />
- <keyword match="TemplatesHandler" />
- <keyword match="Text" />
- <keyword match="TextAction" />
- <keyword match="TextArea" />
- <keyword match="TextAttribute" />
- <keyword match="TextComponent" />
- <keyword match="TextEvent" />
- <keyword match="TextField" />
- <keyword match="TextHitInfo" />
- <keyword match="TextInputCallback" />
- <keyword match="TextLayout" />
-
- <keyword match="TextListener" />
- <keyword match="TextMeasurer" />
- <keyword match="TextOutputCallback" />
- <keyword match="TextSyntax" />
- <keyword match="TextUI" />
- <keyword match="TexturePaint" />
- <keyword match="Thread" />
- <keyword match="THREAD_POLICY_ID" />
- <keyword match="ThreadDeath" />
- <keyword match="ThreadGroup" />
- <keyword match="ThreadLocal" />
- <keyword match="ThreadPolicy" />
- <keyword match="ThreadPolicyOperations" />
- <keyword match="ThreadPolicyValue" />
- <keyword match="Throwable" />
- <keyword match="Tie" />
- <keyword match="TileObserver" />
- <keyword match="Time" />
- <keyword match="TimeLimitExceededException" />
- <keyword match="Timer" />
- <keyword match="Timer" />
- <keyword match="TimerTask" />
- <keyword match="Timestamp" />
- <keyword match="TimeZone" />
- <keyword match="TitledBorder" />
- <keyword match="ToolBarUI" />
- <keyword match="Toolkit" />
- <keyword match="ToolTipManager" />
- <keyword match="ToolTipUI" />
- <keyword match="TooManyListenersException" />
- <keyword match="Track" />
- <keyword match="TRANSACTION_REQUIRED" />
- <keyword match="TRANSACTION_ROLLEDBACK" />
- <keyword match="TransactionRequiredException" />
- <keyword match="TransactionRolledbackException" />
- <keyword match="TransactionService" />
- <keyword match="Transferable" />
- <keyword match="TransferHandler" />
- <keyword match="TransformAttribute" />
- <keyword match="Transformer" />
- <keyword match="TransformerConfigurationException" />
- <keyword match="TransformerException" />
- <keyword match="TransformerFactory" />
- <keyword match="TransformerFactoryConfigurationError" />
- <keyword match="TransformerHandler" />
- <keyword match="TRANSIENT" />
- <keyword match="Transmitter" />
- <keyword match="Transparency" />
- <keyword match="TRANSPORT_RETRY" />
- <keyword match="TreeCellEditor" />
- <keyword match="TreeCellRenderer" />
- <keyword match="TreeExpansionEvent" />
- <keyword match="TreeExpansionListener" />
- <keyword match="TreeMap" />
- <keyword match="TreeModel" />
- <keyword match="TreeModelEvent" />
- <keyword match="TreeModelListener" />
- <keyword match="TreeNode" />
- <keyword match="TreePath" />
- <keyword match="TreeSelectionEvent" />
- <keyword match="TreeSelectionListener" />
- <keyword match="TreeSelectionModel" />
- <keyword match="TreeSet" />
- <keyword match="TreeUI" />
- <keyword match="TreeWillExpandListener" />
- <keyword match="TrustAnchor" />
- <keyword match="TrustManager" />
- <keyword match="TrustManagerFactory" />
- <keyword match="TrustManagerFactorySpi" />
- <keyword match="TypeCode" />
- <keyword match="TypeCodeHolder" />
- <keyword match="TypeMismatch" />
- <keyword match="TypeMismatch" />
- <keyword match="TypeMismatch" />
- <keyword match="TypeMismatchHelper" />
- <keyword match="TypeMismatchHelper" />
- <keyword match="Types" />
- <keyword match="UID" />
- <keyword match="UIDefaults" />
-
-
-
-
- <keyword match="UIManager" />
-
- <keyword match="UIResource" />
- <keyword match="ULongLongSeqHelper" />
- <keyword match="ULongLongSeqHolder" />
- <keyword match="ULongSeqHelper" />
- <keyword match="ULongSeqHolder" />
- <keyword match="UndeclaredThrowableException" />
- <keyword match="UndoableEdit" />
- <keyword match="UndoableEditEvent" />
- <keyword match="UndoableEditListener" />
- <keyword match="UndoableEditSupport" />
- <keyword match="UndoManager" />
- <keyword match="UnexpectedException" />
- <keyword match="UnicastRemoteObject" />
- <keyword match="UnionMember" />
- <keyword match="UnionMemberHelper" />
- <keyword match="UNKNOWN" />
- <keyword match="UnknownEncoding" />
- <keyword match="UnknownEncodingHelper" />
- <keyword match="UnknownError" />
- <keyword match="UnknownException" />
- <keyword match="UnknownGroupException" />
- <keyword match="UnknownHostException" />
- <keyword match="UnknownHostException" />
- <keyword match="UnknownObjectException" />
- <keyword match="UnknownServiceException" />
- <keyword match="UnknownUserException" />
- <keyword match="UnknownUserExceptionHelper" />
- <keyword match="UnknownUserExceptionHolder" />
- <keyword match="UnmappableCharacterException" />
- <keyword match="UnmarshalException" />
- <keyword match="UnmodifiableSetException" />
- <keyword match="UnrecoverableKeyException" />
- <keyword match="Unreferenced" />
- <keyword match="UnresolvedAddressException" />
- <keyword match="UnresolvedPermission" />
- <keyword match="UnsatisfiedLinkError" />
- <keyword match="UnsolicitedNotification" />
- <keyword match="UnsolicitedNotificationEvent" />
- <keyword match="UnsolicitedNotificationListener" />
- <keyword match="UNSUPPORTED_POLICY" />
- <keyword match="UNSUPPORTED_POLICY_VALUE" />
- <keyword match="UnsupportedAddressTypeException" />
- <keyword match="UnsupportedAudioFileException" />
- <keyword match="UnsupportedCallbackException" />
- <keyword match="UnsupportedCharsetException" />
- <keyword match="UnsupportedClassVersionError" />
- <keyword match="UnsupportedEncodingException" />
- <keyword match="UnsupportedFlavorException" />
- <keyword match="UnsupportedLookAndFeelException" />
- <keyword match="UnsupportedOperationException" />
- <keyword match="URI" />
- <keyword match="URIException" />
- <keyword match="URIResolver" />
- <keyword match="URISyntax" />
- <keyword match="URISyntaxException" />
- <keyword match="URL" />
- <keyword match="URLClassLoader" />
- <keyword match="URLConnection" />
- <keyword match="URLDecoder" />
- <keyword match="URLEncoder" />
- <keyword match="URLStreamHandler" />
- <keyword match="URLStreamHandlerFactory" />
- <keyword match="URLStringHelper" />
- <keyword match="USER_EXCEPTION" />
- <keyword match="UserException" />
- <keyword match="UShortSeqHelper" />
- <keyword match="UShortSeqHolder" />
- <keyword match="UTFDataFormatException" />
- <keyword match="Util" />
- <keyword match="UtilDelegate" />
- <keyword match="Utilities" />
- <keyword match="ValueBase" />
- <keyword match="ValueBaseHelper" />
- <keyword match="ValueBaseHolder" />
- <keyword match="ValueFactory" />
- <keyword match="ValueHandler" />
- <keyword match="ValueMember" />
- <keyword match="ValueMemberHelper" />
- <keyword match="VariableHeightLayoutCache" />
- <keyword match="Vector" />
- <keyword match="VerifyError" />
- <keyword match="VersionSpecHelper" />
- <keyword match="VetoableChangeListener" />
- <keyword match="VetoableChangeListenerProxy" />
- <keyword match="VetoableChangeSupport" />
- <keyword match="View" />
- <keyword match="ViewFactory" />
- <keyword match="ViewportLayout" />
- <keyword match="ViewportUI" />
- <keyword match="VirtualMachineError" />
- <keyword match="Visibility" />
- <keyword match="VisibilityHelper" />
- <keyword match="VM_ABSTRACT" />
- <keyword match="VM_CUSTOM" />
- <keyword match="VM_NONE" />
- <keyword match="VM_TRUNCATABLE" />
- <keyword match="VMID" />
- <keyword match="VoiceStatus" />
- <keyword match="Void" />
- <keyword match="VolatileImage" />
- <keyword match="WCharSeqHelper" />
- <keyword match="WCharSeqHolder" />
- <keyword match="WeakHashMap" />
- <keyword match="WeakReference" />
- <keyword match="Window" />
- <keyword match="WindowAdapter" />
- <keyword match="WindowConstants" />
- <keyword match="WindowEvent" />
- <keyword match="WindowFocusListener" />
- <keyword match="WindowListener" />
- <keyword match="WindowStateListener" />
- <keyword match="WrappedPlainView" />
- <keyword match="WritableByteChannel" />
- <keyword match="WritableRaster" />
- <keyword match="WritableRenderedImage" />
- <keyword match="WriteAbortedException" />
- <keyword match="Writer" />
- <keyword match="WrongAdapter" />
- <keyword match="WrongAdapterHelper" />
- <keyword match="WrongPolicy" />
- <keyword match="WrongPolicyHelper" />
- <keyword match="WrongTransaction" />
- <keyword match="WrongTransactionHelper" />
- <keyword match="WrongTransactionHolder" />
- <keyword match="WStringSeqHelper" />
- <keyword match="WStringSeqHolder" />
- <keyword match="WStringValueHelper" />
- <keyword match="X500Principal" />
- <keyword match="X500PrivateCredential" />
- <keyword match="X509Certificate" />
- <keyword match="X509Certificate" />
- <keyword match="X509CertSelector" />
- <keyword match="X509CRL" />
- <keyword match="X509CRLEntry" />
- <keyword match="X509CRLSelector" />
- <keyword match="X509EncodedKeySpec" />
- <keyword match="X509Extension" />
- <keyword match="X509KeyManager" />
- <keyword match="X509TrustManager" />
- <keyword match="XAConnection" />
- <keyword match="XADataSource" />
- <keyword match="XAException" />
- <keyword match="XAResource" />
- <keyword match="Xid" />
- <keyword match="XMLDecoder" />
- <keyword match="XMLEncoder" />
- <keyword match="XMLFilter" />
- <keyword match="XMLFilterImpl" />
- <keyword match="XMLFormatter" />
- <keyword match="XMLReader" />
- <keyword match="XMLReaderAdapter" />
- <keyword match="XMLReaderFactory" />
- <keyword match="ZipEntry" />
- <keyword match="ZipException" />
- <keyword match="ZipFile" />
- <keyword match="ZipInputStream" />
- <keyword match="ZipOutputStream" />
- <keyword match="ZoneView" />
- <keyword match="_BindingIteratorImplBase" />
- <keyword match="_BindingIteratorStub" />
- <keyword match="_DynAnyFactoryStub" />
- <keyword match="_DynAnyStub" />
- <keyword match="_DynArrayStub" />
- <keyword match="_DynEnumStub" />
- <keyword match="_DynFixedStub" />
- <keyword match="_DynSequenceStub" />
- <keyword match="_DynStructStub" />
- <keyword match="_DynUnionStub" />
- <keyword match="_DynValueStub" />
- <keyword match="_IDLTypeStub" />
- <keyword match="_NamingContextExtStub" />
- <keyword match="_NamingContextImplBase" />
- <keyword match="_NamingContextStub" />
- <keyword match="_PolicyStub" />
- <keyword match="_Remote_Stub" />
- <keyword match="_ServantActivatorStub" />
- <keyword match="_ServantLocatorStub" />
- </keywords>
-
-</highlight>
diff --git a/library/Text_Highlighter/javascript.xml b/library/Text_Highlighter/javascript.xml
deleted file mode 100644
index e478515a7..000000000
--- a/library/Text_Highlighter/javascript.xml
+++ /dev/null
@@ -1,174 +0,0 @@
-<?xml version="1.0"?>
-<!-- $Id: javascript.xml,v 1.3 2008-01-01 23:43:36 ssttoo Exp $ -->
-
-<highlight lang="javascript" case = "no">
-
- <authors>
- <author name="Andrey Demenev" email ="demenev@gmail.com"/>
- </authors>
-
- <default innerClass="code" />
-
- <region name="block" delimClass="brackets" innerClass="code" start="\{" end="\}">
- <contains all="yes"/>
- </region>
-
- <region name="brackets" delimClass="brackets" innerClass="code" start="\(" end="\)">
- <contains all="yes"/>
- </region>
-
- <region name="sqbrackets" delimClass="brackets" innerClass="code" start="\[" end="\]">
- <contains all="yes"/>
- </region>
-
-
- <region name="mlcomment" innerClass="comment" start="\/\*" end="\*\/" >
- <contains block="cvstag"/>
- </region>
-
- <region name="strdouble" delimClass="quotes" innerClass="string" start="&quot;" end="&quot;"/>
-
- <region name="strsingle" delimClass="quotes" innerClass="string" start="'" end="'" />
-
- <block name="escaped" match="\\\\|\\&quot;|\\'|\\`" innerClass="special" contained="yes">
- <onlyin region="strsingle"/>
- </block>
-
- <block name="descaped" match="\\\\|\\&quot;|\\'|\\`|\\t|\\n|\\r" innerClass="special" contained="yes">
- <onlyin region="strdouble"/>
- </block>
-
- <region name="comment" start="\/\/" end="/$/m" innerClass="comment">
- <contains block="cvstag"/>
- </region>
-
- <block name="identifier" match="[a-z_]\w*" innerClass="identifier" case="no"/>
-
- <block name="number" match="0x\d*|\d*\.?\d+" innerClass="number"/>
-
-
- <block name="url" match="((https?|ftp):\/\/[\w\?\.\-\&amp;=\/%+]+)|(^|[\s,!?])www\.\w+\.\w+[\w\?\.\&amp;=\/%+]*" innerClass="url" contained="yes">
- <onlyin region="mlcomment"/>
- <onlyin region="comment"/>
- </block>
-
- <block name="email" match="\w+[\.\w\-]+@(\w+[\.\w\-])+" innerClass="url" contained="yes">
- <onlyin region="mlcomment"/>
- <onlyin region="comment"/>
- </block>
-
- <block name="note" match="\b(note|fixme):" innerClass="inlinedoc" contained="yes" case="no">
- <onlyin region="mlcomment"/>
- <onlyin region="comment"/>
- </block>
-
-
- <block name="cvstag" match="\$\w+:.+\$" innerClass="inlinedoc" contained="yes">
- <onlyin region="mlcomment"/>
- <onlyin region="comment"/>
- </block>
-
- <keywords name="builtin" inherits="identifier" innerClass="builtin" case = "yes">
- <keyword match="String"/>
- <keyword match="Array"/>
- <keyword match="RegExp"/>
- <keyword match="Function"/>
- <keyword match="Math"/>
- <keyword match="Number"/>
- <keyword match="Date"/>
- <keyword match="Image"/>
- <keyword match="window"/>
- <keyword match="document"/>
- <keyword match="navigator"/>
- <keyword match="onAbort"/>
- <keyword match="onBlur"/>
- <keyword match="onChange"/>
- <keyword match="onClick"/>
- <keyword match="onDblClick"/>
- <keyword match="onDragDrop"/>
- <keyword match="onError"/>
- <keyword match="onFocus"/>
- <keyword match="onKeyDown"/>
- <keyword match="onKeyPress"/>
- <keyword match="onKeyUp"/>
- <keyword match="onLoad"/>
- <keyword match="onMouseDown"/>
- <keyword match="onMouseOver"/>
- <keyword match="onMouseOut"/>
- <keyword match="onMouseMove"/>
- <keyword match="onMouseUp"/>
- <keyword match="onMove"/>
- <keyword match="onReset"/>
- <keyword match="onResize"/>
- <keyword match="onSelect"/>
- <keyword match="onSubmit"/>
- <keyword match="onUnload"/>
- </keywords>
-
- <keywords name="reserved" inherits="identifier" innerClass="reserved" case = "yes">
- <keyword match="break"/>
- <keyword match="continue"/>
- <keyword match="do"/>
- <keyword match="while"/>
- <keyword match="do"/>
- <keyword match="export"/>
- <keyword match="for"/>
- <keyword match="in"/>
- <keyword match="if"/>
- <keyword match="else"/>
- <keyword match="import"/>
- <keyword match="return"/>
- <keyword match="label"/>
- <keyword match="switch"/>
- <keyword match="case"/>
- <keyword match="var"/>
- <keyword match="with"/>
- <keyword match="delete"/>
- <keyword match="new"/>
- <keyword match="this"/>
- <keyword match="typeof"/>
- <keyword match="void"/>
- <keyword match="abstract"/>
- <keyword match="boolean"/>
- <keyword match="byte"/>
- <keyword match="catch"/>
- <keyword match="char"/>
- <keyword match="class"/>
- <keyword match="const"/>
- <keyword match="continue"/>
- <keyword match="debugger"/>
- <keyword match="default"/>
- <keyword match="double"/>
- <keyword match="enum"/>
- <keyword match="extends"/>
- <keyword match="false"/>
- <keyword match="final"/>
- <keyword match="finally"/>
- <keyword match="float"/>
- <keyword match="function"/>
- <keyword match="implements"/>
- <keyword match="goto"/>
- <keyword match="in"/>
- <keyword match="instanceof"/>
- <keyword match="int"/>
- <keyword match="interface"/>
- <keyword match="long"/>
- <keyword match="native"/>
- <keyword match="null"/>
- <keyword match="package"/>
- <keyword match="private"/>
- <keyword match="protected"/>
- <keyword match="public"/>
- <keyword match="short"/>
- <keyword match="static"/>
- <keyword match="super"/>
- <keyword match="synchronized"/>
- <keyword match="throw"/>
- <keyword match="throws"/>
- <keyword match="transient"/>
- <keyword match="true"/>
- <keyword match="try"/>
- <keyword match="volatile"/>
- </keywords>
-
-</highlight>
diff --git a/library/Text_Highlighter/mysql.xml b/library/Text_Highlighter/mysql.xml
deleted file mode 100644
index 082b62795..000000000
--- a/library/Text_Highlighter/mysql.xml
+++ /dev/null
@@ -1,424 +0,0 @@
-<?xml version="1.0"?>
-<!-- $Id: mysql.xml,v 1.1 2007-06-03 02:35:28 ssttoo Exp $ -->
-
-<highlight lang="mysql" case="no">
-
- <authors>
- <author name="Andrey Demenev" email="demenev@gmail.com"/>
- </authors>
-
-
- <default innerClass="code" />
-
- <region name="qidentifier" delimClass="quotes" innerClass="identifier"
- start="`" end="`" />
-
- <region name="mlcomment" delimClass="comment" innerClass="comment"
- start="\/\*" end="\*\/" />
-
- <block name="comment" match="(#|--\s).*" innerClass="comment" />
-
- <block name="possiblefunction" match="[a-z_]\w*(?=\s*\()" innerClass="identifier" />
-
- <block name="identifier" match="[a-z_]\w*" innerClass="identifier" />
-
- <region name="strdouble" delimClass="quotes" innerClass="string"
- start="&quot;" end="&quot;" >
- </region>
-
- <region name="brackets" delimClass="brackets" innerClass="code"
- start="\(" end="\)" >
- <contains all="yes"/>
- </region>
-
- <region name="strsingle" delimClass="quotes" innerClass="string"
- start="'" end="'" />
-
- <block name="escaped" match="\\." innerClass="special" contained="yes">
- <onlyin region="strsingle"/>
- <onlyin region="strdouble"/>
- </block>
-
- <block name="exponent"
- match="((\d+|((\d*\.\d+)|(\d+\.\d*)))[eE][+-]?\d+)"
- innerClass="number" />
-
- <block name="float" match="(\d*\.\d+)|(\d+\.\d*)" innerClass="number"/>
-
- <block name="integer" match="\d+l?|\b0l?\b" innerClass="number" />
-
- <block name="hexinteger" match="0[xX][\da-f]+l?" innerClass="number" />
-
- <keywords name="reserved" inherits="identifier" innerClass="reserved"
- case="no">
- <keyword match="action" />
- <keyword match="add" />
- <keyword match="aggregate" />
- <keyword match="all" />
- <keyword match="alter" />
- <keyword match="after" />
- <keyword match="and" />
- <keyword match="as" />
- <keyword match="asc" />
- <keyword match="avg" />
- <keyword match="avg_row_length" />
- <keyword match="auto_increment" />
- <keyword match="between" />
- <keyword match="bigint" />
- <keyword match="bit" />
-
- <keyword match="binary" />
- <keyword match="blob" />
- <keyword match="bool" />
- <keyword match="both" />
- <keyword match="by" />
- <keyword match="cascade" />
- <keyword match="case" />
- <keyword match="char" />
- <keyword match="character" />
- <keyword match="change" />
- <keyword match="check" />
- <keyword match="checksum" />
- <keyword match="column" />
- <keyword match="columns" />
- <keyword match="comment" />
- <keyword match="constraint" />
- <keyword match="create" />
-
- <keyword match="cross" />
- <keyword match="current_date" />
- <keyword match="current_time" />
- <keyword match="current_timestamp" />
- <keyword match="data" />
- <keyword match="database" />
- <keyword match="databases" />
- <keyword match="date" />
- <keyword match="datetime" />
- <keyword match="day" />
- <keyword match="day_hour" />
- <keyword match="day_minute" />
- <keyword match="day_second" />
- <keyword match="dayofmonth" />
- <keyword match="dayofweek" />
- <keyword match="dayofyear" />
- <keyword match="dec" />
-
- <keyword match="decimal" />
- <keyword match="default" />
- <keyword match="delayed" />
- <keyword match="delay_key_write" />
- <keyword match="delete" />
- <keyword match="desc" />
- <keyword match="describe" />
- <keyword match="distinct" />
- <keyword match="distinctrow" />
- <keyword match="double" />
- <keyword match="drop" />
- <keyword match="end" />
- <keyword match="else" />
- <keyword match="escape" />
- <keyword match="escaped" />
- <keyword match="enclosed" />
- <keyword match="enum" />
-
- <keyword match="explain" />
- <keyword match="exists" />
- <keyword match="fields" />
- <keyword match="file" />
- <keyword match="first" />
- <keyword match="float" />
- <keyword match="float4" />
- <keyword match="float8" />
- <keyword match="flush" />
- <keyword match="foreign" />
- <keyword match="from" />
- <keyword match="for" />
- <keyword match="full" />
- <keyword match="function" />
- <keyword match="global" />
- <keyword match="grant" />
- <keyword match="grants" />
-
- <keyword match="group" />
- <keyword match="having" />
- <keyword match="heap" />
- <keyword match="high_priority" />
- <keyword match="hour" />
- <keyword match="hour_minute" />
- <keyword match="hour_second" />
- <keyword match="hosts" />
- <keyword match="identified" />
- <keyword match="ignore" />
- <keyword match="in" />
- <keyword match="index" />
- <keyword match="infile" />
- <keyword match="inner" />
- <keyword match="insert" />
- <keyword match="insert_id" />
- <keyword match="int" />
-
- <keyword match="integer" />
- <keyword match="interval" />
- <keyword match="int1" />
- <keyword match="int2" />
- <keyword match="int3" />
- <keyword match="int4" />
- <keyword match="int8" />
- <keyword match="into" />
- <keyword match="if" />
- <keyword match="is" />
- <keyword match="isam" />
- <keyword match="join" />
- <keyword match="key" />
- <keyword match="keys" />
- <keyword match="kill" />
- <keyword match="last_insert_id" />
- <keyword match="leading" />
-
- <keyword match="left" />
- <keyword match="length" />
- <keyword match="like" />
- <keyword match="lines" />
- <keyword match="limit" />
- <keyword match="load" />
- <keyword match="local" />
- <keyword match="lock" />
- <keyword match="logs" />
- <keyword match="long" />
- <keyword match="longblob" />
- <keyword match="longtext" />
- <keyword match="low_priority" />
- <keyword match="max" />
- <keyword match="max_rows" />
- <keyword match="match" />
- <keyword match="mediumblob" />
-
- <keyword match="mediumtext" />
- <keyword match="mediumint" />
- <keyword match="middleint" />
- <keyword match="min_rows" />
- <keyword match="minute" />
- <keyword match="minute_second" />
- <keyword match="modify" />
- <keyword match="month" />
- <keyword match="monthname" />
- <keyword match="myisam" />
- <keyword match="natural" />
- <keyword match="numeric" />
- <keyword match="no" />
- <keyword match="not" />
- <keyword match="null" />
- <keyword match="on" />
- <keyword match="optimize" />
-
- <keyword match="option" />
- <keyword match="optionally" />
- <keyword match="or" />
- <keyword match="order" />
- <keyword match="outer" />
- <keyword match="outfile" />
- <keyword match="pack_keys" />
- <keyword match="partial" />
- <keyword match="password" />
- <keyword match="precision" />
- <keyword match="primary" />
- <keyword match="procedure" />
- <keyword match="process" />
- <keyword match="processlist" />
- <keyword match="privileges" />
- <keyword match="read" />
- <keyword match="real" />
-
- <keyword match="references" />
- <keyword match="reload" />
- <keyword match="regexp" />
- <keyword match="rename" />
- <keyword match="replace" />
- <keyword match="restrict" />
- <keyword match="returns" />
- <keyword match="revoke" />
- <keyword match="rlike" />
- <keyword match="row" />
- <keyword match="rows" />
- <keyword match="second" />
- <keyword match="select" />
- <keyword match="set" />
- <keyword match="show" />
- <keyword match="shutdown" />
- <keyword match="smallint" />
-
- <keyword match="soname" />
- <keyword match="sql_big_tables" />
- <keyword match="sql_big_selects" />
- <keyword match="sql_low_priority_updates" />
- <keyword match="sql_log_off" />
- <keyword match="sql_log_update" />
- <keyword match="sql_select_limit" />
- <keyword match="sql_small_result" />
- <keyword match="sql_big_result" />
- <keyword match="sql_warnings" />
- <keyword match="straight_join" />
- <keyword match="starting" />
- <keyword match="status" />
- <keyword match="string" />
- <keyword match="table" />
- <keyword match="tables" />
- <keyword match="temporary" />
-
- <keyword match="terminated" />
- <keyword match="text" />
- <keyword match="then" />
- <keyword match="time" />
- <keyword match="timestamp" />
- <keyword match="tinyblob" />
- <keyword match="tinytext" />
- <keyword match="tinyint" />
- <keyword match="trailing" />
- <keyword match="to" />
- <keyword match="type" />
- <keyword match="use" />
- <keyword match="using" />
- <keyword match="unique" />
- <keyword match="unlock" />
- <keyword match="unsigned" />
- <keyword match="update" />
-
- <keyword match="usage" />
- <keyword match="values" />
- <keyword match="varchar" />
- <keyword match="variables" />
- <keyword match="varying" />
- <keyword match="varbinary" />
- <keyword match="with" />
- <keyword match="write" />
- <keyword match="when" />
- <keyword match="where" />
- <keyword match="year" />
- <keyword match="year_month" />
- <keyword match="zerofill" />
- </keywords>
-
- <keywords name="function" inherits="possiblefunction" innerClass="reserved"
- case="no" otherwise="identifier">
- <keyword match="ABS" />
- <keyword match="ACOS" />
- <keyword match="ADDDATE" />
- <keyword match="ASCII" />
- <keyword match="ASIN" />
- <keyword match="ATAN" />
- <keyword match="ATAN2" />
- <keyword match="AVG" />
- <keyword match="BENCHMARK" />
- <keyword match="BIN" />
- <keyword match="CEILING" />
- <keyword match="CHAR" />
- <keyword match="COALESCE" />
- <keyword match="CONCAT" />
- <keyword match="CONV" />
- <keyword match="COS" />
- <keyword match="COT" />
- <keyword match="COUNT" />
- <keyword match="CURDATE" />
- <keyword match="CURTIME" />
- <keyword match="DATABASE" />
- <keyword match="DAYNAME" />
- <keyword match="DAYOFMONTH" />
- <keyword match="DAYOFWEEK" />
- <keyword match="DAYOFYEAR" />
- <keyword match="DECODE" />
- <keyword match="DEGREES" />
- <keyword match="ELT" />
-
- <keyword match="ENCODE" />
- <keyword match="ENCRYPT" />
- <keyword match="EXP" />
- <keyword match="EXTRACT" />
-
- <keyword match="EXTRACT" />
- <keyword match="FIELD" />
- <keyword match="FLOOR" />
- <keyword match="FORMAT" />
- <keyword match="GREATEST" />
- <keyword match="HEX" />
- <keyword match="HOUR" />
- <keyword match="IF" />
- <keyword match="IFNULL" />
- <keyword match="INSERT" />
- <keyword match="INSTR" />
- <keyword match="INTERVAL" />
-
- <keyword match="ISNULL" />
- <keyword match="LCASE" />
- <keyword match="LEAST" />
- <keyword match="LEFT" />
- <keyword match="LENGTH" />
- <keyword match="LOCATE" />
-
- <keyword match="LOCATE" />
- <keyword match="LOG" />
- <keyword match="LOG10" />
- <keyword match="LOWER" />
- <keyword match="LPAD" />
- <keyword match="LTRIM" />
- <keyword match="MAX" />
- <keyword match="MD5" />
- <keyword match="MID" />
- <keyword match="MIN" />
-
- <keyword match="MINUTE" />
- <keyword match="MOD" />
- <keyword match="MONTH" />
- <keyword match="MONTHNAME" />
- <keyword match="NOW" />
- <keyword match="NULLIF" />
- <keyword match="OCT" />
- <keyword match="ORD" />
- <keyword match="PASSWORD" />
- <keyword match="PI" />
- <keyword match="POSITION" />
-
- <keyword match="POW" />
- <keyword match="POWER" />
- <keyword match="prepare" />
- <keyword match="QUARTER" />
- <keyword match="RADIANS" />
- <keyword match="RAND" />
- <keyword match="REPEAT" />
- <keyword match="REPLACE" />
- <keyword match="REVERSE" />
- <keyword match="RIGHT" />
- <keyword match="ROUND" />
-
- <keyword match="ROUND" />
- <keyword match="RPAD" />
-
- <keyword match="RTRIM" />
- <keyword match="SECOND" />
- <keyword match="SIGN" />
- <keyword match="SIN" />
- <keyword match="SOUNDEX" />
- <keyword match="SPACE" />
- <keyword match="SQRT" />
- <keyword match="STD" />
- <keyword match="STDDEV" />
- <keyword match="STRCMP" />
- <keyword match="SUBDATE" />
- <keyword match="SUBSTRING" />
-
- <keyword match="SUBSTRING" />
- <keyword match="SUM" />
- <keyword match="SYSDATE" />
- <keyword match="TAN" />
-
- <keyword match="TRIM" />
- <keyword match="TRUNCATE" />
- <keyword match="UCASE" />
- <keyword match="UPPER" />
- <keyword match="USER" />
- <keyword match="VERSION" />
- <keyword match="WEEK" />
- <keyword match="WEEKDAY" />
- <keyword match="YEAR" />
- </keywords>
-
-</highlight>
diff --git a/library/Text_Highlighter/perl.xml b/library/Text_Highlighter/perl.xml
deleted file mode 100644
index 54f8835ea..000000000
--- a/library/Text_Highlighter/perl.xml
+++ /dev/null
@@ -1,439 +0,0 @@
-<?xml version="1.0"?>
-<!-- $Id: perl.xml,v 1.1 2007-06-03 02:35:28 ssttoo Exp $ -->
-
-<highlight lang="perl" case = "yes">
-
- <authors>
- <author name="Mariusz 'kg' Jakubowski" email="kg@alternatywa.info" jid="kg@chrome.pl"/>
- <author name="Andrey Demenev" email="demenev@gmail.com"/>
- </authors>
-
- <comment>This highlighter is EXPERIMENTAL, so that it may work incorrectly.
-Most rules were created by Mariusz Jakubowski, and extended by me.
-My knowledge of Perl is poor, and Perl syntax seems too
-complicated to me.</comment>
-
- <default innerClass="code"/>
-
- <block name="interpreter" match="/^(#!)(.*)/m" innerClass="special">
- <partClass index="1" innerClass="special" />
- <partClass index="2" innerClass="string" />
- </block>
-
- <region name="pod" innerClass="comment" start="/^=\w+/m" end="/^=cut[^\n]*/m" startBOL="yes" endBOL="yes"/>
-
- <!--
- brackets
- -->
- <region name="block" delimClass="brackets" innerClass="code" start="\{" end="\}">
- <contains all="yes"/>
- </region>
-
- <region name="brackets" delimClass="brackets" innerClass="code" start="\(" end="\)">
- <contains all="yes"/>
- </region>
-
- <region name="sqbrackets" delimClass="brackets" innerClass="code" start="\[" end="\]">
- <contains all="yes"/>
- </region>
-
- <!--
- use smth
- -->
- <block name="usestatement" match="(use)\s+([\w:]*)" innerClass="special">
- <partClass index="1" innerClass="reserved" />
- <partClass index="2" innerClass="special" />
- </block>
-
- <block name="packagereference" match="[&amp; ](\w{2,}::)+\w{2,}" innerClass="special"/>
-
- <region name="q-w-q-statement"
- start="/\b(q[wq]\s*((\{)|(\()|(\[)|(\&lt;)|([\W\S])))(?=(.*)((?(3)\})(?(4)\))(?(5)\])(?(6)\&gt;)(?(7)\7)))/Us"
- end="%b2%"
- innerClass="string" delimClass="quotes" remember="yes">
-
- <contains block="containedvar"/>
- <contains block="specialvar"/>
- <contains block="curlyvar"/>
-
- </region>
-
- <region name="qstatement"
- start="/\b(q\s*((\{)|(\()|(\[)|(\&lt;)|([\W\S])))(?=(.*)((?(3)\})(?(4)\))(?(5)\])(?(6)\&gt;)(?(7)\7)))/Us"
- end="%b2%"
- innerClass="string" delimClass="quotes" remember="yes">
-
- </region>
-
- <!--
- comments
- -->
- <block name="comment" match="#.*" innerClass="comment" />
-
-
- <!--
- regexpr
- FIXME: this should be rewrited
- -->
- <block name="dblregexprver1" match="/(s|tr) ([|#~`!@$%^&amp;*-+=\\;:'&quot;,.\/?]) ((\\.|[^\\])*?) (\2)((\\.|[^\\])*?)(\2[ecgimosx]*)/x" innerClass="string">
- <partClass index="1" innerClass="quotes" />
- <partClass index="2" innerClass="quotes" />
- <partClass index="3" innerClass="string" />
- <partClass index="5" innerClass="quotes" />
- <partClass index="6" innerClass="string" />
- <partClass index="8" innerClass="quotes" />
- </block>
-
- <block name="dblregexprver2" match="/(m) ([|#~`!@$%^&amp;*-+=\\;:'&quot;,.\/?]) ((\\.|[^\\])*?) (\2[ecgimosx]*)/x" innerClass="string">
- <partClass index="1" innerClass="quotes" />
- <partClass index="2" innerClass="quotes" />
- <partClass index="3" innerClass="string" />
- <partClass index="5" innerClass="quotes" />
- </block>
-
-
- <region name="regexp" start=" \/" end="\/[cgimosx]*" innerClass="string" delimClass="quotes" case="yes">
- <contains block="reescaped"/>
- </region>
-
- <block name="reescaped" match="\\\/" innerClass="string" contained="yes">
- <onlyin region="regexp"/>
- </block>
-
- <!--
- variables
- FIXME: @{...}
- -->
- <block name="bracketsvars" match="([a-z1-9_]+)(\s*=>)" innerClass="string" contained="yes" case="no">
- <partClass index="1" innerClass="string" />
- <partClass index="2" innerClass="code" />
- <onlyin region="brackets"/>
- </block>
-
- <block name="specialvar" match="\$#?[1-9'`@!]" innerClass="var"/>
-
- <block name="var" match="(\$#?|[@%*])([a-z1-9_]+::)*([a-z1-9_]+|\^(?-i)[A-Z]?(?i))" innerClass="var" case="no"/>
- <block name="containedvar" match="\$([a-z1-9_]+|\^(?-i)[A-Z]?(?i))" innerClass="var" case="no"/>
-
- <!-- not shure what is this, but the Perlers do it :) -->
- <block name="var2" match="(&amp;|\w+)'[\w_']+\b" innerClass="var" case="no"/>
-
- <block name="classvar" match="(\{)([a-z1-9]+)(\})" innerClass="var" case="no">
- <partClass index="1" innerClass="brackets" />
- <partClass index="2" innerClass="var" />
- <partClass index="3" innerClass="brackets" />
- </block>
-
- <block name="curlyvar" match="[\$@%]#?\{[a-z1-9]+\}" innerClass="var" case="no"/>
-
- <!--
- quotes
- -->
- <region name="exec" delimClass="quotes" innerClass="string" start="`" end="`">
- <contains block="containedvar"/>
- <contains block="specialvar"/>
- <contains block="curlyvar"/>
- </region>
-
- <region name="strsingle" delimClass="quotes" innerClass="string" start="'" end="'"/>
-
- <block name="escaped" match="\\\\|\\&quot;|\\'|\\`" innerClass="special" contained="yes">
- <onlyin region="qstatement"/>
- <onlyin region="strsingle"/>
- <onlyin region="exec"/>
- </block>
-
- <region name="strdouble" delimClass="quotes" innerClass="string" start="&quot;" end="&quot;">
- <contains block="containedvar"/>
- <contains block="specialvar"/>
- <contains block="curlyvar"/>
- </region>
-
- <block name="descaped" match="\\[\\&quot;'`tnr\$\{@]" innerClass="special" contained="yes">
- <onlyin region="strdouble"/>
- <onlyin region="q-w-q-statement"/>
- </block>
-
- <!-- logical op.
- <block name="logic" match="\|\||&amp;&amp;" innerClass="reserved" contained="yes"/>-->
-
- <!--
- identifiers
- -->
- <block name="identifier" match="[a-z_]\w*" innerClass="identifier" case="no"/>
-
- <!--
- numbers
- -->
- <block name="number" match="\d*\.?\d+" innerClass="number"/>
-
- <!--
- http://www.perldoc.com/perl5.6/pod/perlfunc.html
- Alphabetical Listing of Perl Functions
- -->
- <keywords name="reserved" inherits="identifier" innerClass="reserved" case = "yes">
- <keyword match="abs"/>
- <keyword match="accept"/>
- <keyword match="alarm"/>
- <keyword match="atan2"/>
-
- <keyword match="bind"/>
- <keyword match="binmode"/>
- <keyword match="bless"/>
-
- <keyword match="caller"/>
- <keyword match="chdir"/>
- <keyword match="chmod"/>
- <keyword match="chomp"/>
- <keyword match="chop"/>
- <keyword match="chown"/>
- <keyword match="chr"/>
- <keyword match="chroot"/>
- <keyword match="close"/>
- <keyword match="closedir"/>
- <keyword match="connect"/>
- <keyword match="continue"/>
- <keyword match="cos"/>
- <keyword match="crypt"/>
-
- <keyword match="dbmclose"/>
- <keyword match="dbmopen"/>
- <keyword match="defined"/>
- <keyword match="delete"/>
- <keyword match="die"/>
- <keyword match="do"/>
- <keyword match="dump"/>
-
- <keyword match="each"/>
- <keyword match="endgrent"/>
- <keyword match="endhostent"/>
- <keyword match="endnetent"/>
- <keyword match="endprotoent"/>
- <keyword match="endpwent"/>
- <keyword match="endservent"/>
- <keyword match="eof"/>
- <keyword match="eval"/>
- <keyword match="exec"/>
- <keyword match="exists"/>
- <keyword match="exit"/>
- <keyword match="exp"/>
-
- <keyword match="fcntl"/>
- <keyword match="fileno"/>
- <keyword match="flock"/>
- <keyword match="fork"/>
- <keyword match="format"/>
- <keyword match="formline"/>
-
- <keyword match="getc"/>
- <keyword match="getgrent"/>
- <keyword match="getgrgid"/>
- <keyword match="getgrnam"/>
- <keyword match="gethostbyaddr"/>
- <keyword match="gethostbyname"/>
- <keyword match="gethostent"/>
- <keyword match="getlogin"/>
- <keyword match="getnetbyaddr"/>
- <keyword match="getnetbyname"/>
- <keyword match="getnetent"/>
- <keyword match="getpeername"/>
- <keyword match="getpgrp"/>
- <keyword match="getppid"/>
- <keyword match="getpriority"/>
- <keyword match="getprotobyname"/>
- <keyword match="getprotobynumber"/>
- <keyword match="getprotoent"/>
- <keyword match="getpwent"/>
- <keyword match="getpwnam"/>
- <keyword match="getpwuid"/>
- <keyword match="getservbyname"/>
- <keyword match="getservbyport"/>
- <keyword match="getservent"/>
- <keyword match="getsockname"/>
- <keyword match="getsockopt"/>
- <keyword match="glob"/>
- <keyword match="gmtime"/>
- <keyword match="goto"/>
- <keyword match="grep"/>
-
- <keyword match="hex"/>
-
- <keyword match="import"/>
- <keyword match="index"/>
- <keyword match="int"/>
- <keyword match="ioctl"/>
-
- <keyword match="join"/>
-
- <keyword match="keys"/>
- <keyword match="kill"/>
-
- <keyword match="last"/>
- <keyword match="lc"/>
- <keyword match="lcfirst"/>
- <keyword match="length"/>
- <keyword match="link"/>
- <keyword match="listen"/>
- <keyword match="local"/>
- <keyword match="localtime"/>
- <keyword match="lock"/>
- <keyword match="log"/>
- <keyword match="lstat"/>
-
- <!--<keyword match="m"/>-->
- <keyword match="map"/>
- <keyword match="mkdir"/>
- <keyword match="msgctl"/>
- <keyword match="msgget"/>
- <keyword match="msgrcv"/>
- <keyword match="msgsnd"/>
- <keyword match="my"/>
-
- <keyword match="next"/>
- <keyword match="no"/>
-
- <keyword match="oct"/>
- <keyword match="open"/>
- <keyword match="opendir"/>
- <keyword match="ord"/>
- <keyword match="our"/>
-
- <keyword match="pack"/>
- <keyword match="package"/>
- <keyword match="pipe"/>
- <keyword match="pop"/>
- <keyword match="pos"/>
- <keyword match="print"/>
- <keyword match="printf"/>
- <keyword match="prototype"/>
- <keyword match="push"/>
-
- <!--<keyword match="q"/>
- <keyword match="qq"/>
- <keyword match="qr"/>-->
- <keyword match="quotemeta"/>
- <!--<keyword match="qw"/>
- <keyword match="qx"/>-->
-
- <keyword match="rand"/>
- <keyword match="read"/>
- <keyword match="readdir"/>
- <keyword match="readline"/>
- <keyword match="readlink"/>
- <keyword match="readpipe"/>
- <keyword match="recv"/>
- <keyword match="redo"/>
- <keyword match="ref"/>
- <keyword match="rename"/>
- <keyword match="require"/>
- <keyword match="reset"/>
- <keyword match="return"/>
- <keyword match="reverse"/>
- <keyword match="rewinddir"/>
- <keyword match="rindex"/>
- <keyword match="rmdir"/>
-
- <!--<keyword match="s"/>-->
- <keyword match="scalar"/>
- <keyword match="seek"/>
- <keyword match="seekdir"/>
- <keyword match="select"/>
- <keyword match="semctl"/>
- <keyword match="semget"/>
- <keyword match="semop"/>
- <keyword match="send"/>
- <keyword match="setgrent"/>
- <keyword match="sethostent"/>
- <keyword match="setnetent"/>
- <keyword match="setpgrp"/>
- <keyword match="setpriority"/>
- <keyword match="setprotoent"/>
- <keyword match="setpwent"/>
- <keyword match="setservent"/>
- <keyword match="setsockopt"/>
- <keyword match="shift"/>
- <keyword match="shmctl"/>
- <keyword match="shmget"/>
- <keyword match="shmread"/>
- <keyword match="shmwrite"/>
- <keyword match="shutdown"/>
- <keyword match="sin"/>
- <keyword match="sleep"/>
- <keyword match="socket"/>
- <keyword match="socketpair"/>
- <keyword match="sort"/>
- <keyword match="splice"/>
- <keyword match="split"/>
- <keyword match="sprintf"/>
- <keyword match="sqrt"/>
- <keyword match="srand"/>
- <keyword match="stat"/>
- <keyword match="study"/>
- <keyword match="sub"/>
- <keyword match="substr"/>
- <keyword match="symlink"/>
- <keyword match="syscall"/>
- <keyword match="sysopen"/>
- <keyword match="sysread"/>
- <keyword match="sysseek"/>
- <keyword match="system"/>
- <keyword match="syswrite"/>
-
- <keyword match="tell"/>
- <keyword match="telldir"/>
- <keyword match="tie"/>
- <keyword match="tied"/>
- <keyword match="time"/>
- <keyword match="times"/>
- <!--<keyword match="tr"/>-->
- <keyword match="truncate"/>
-
- <keyword match="uc"/>
- <keyword match="ucfirst"/>
- <keyword match="umask"/>
- <keyword match="undef"/>
- <keyword match="unlink"/>
- <keyword match="unpack"/>
- <keyword match="unshift"/>
- <keyword match="untie"/>
- <keyword match="use"/>
- <keyword match="utime"/>
-
- <keyword match="values"/>
- <keyword match="vec"/>
-
- <keyword match="wait"/>
- <keyword match="waitpid"/>
- <keyword match="wantarray"/>
- <keyword match="warn"/>
- <keyword match="write"/>
-
- <keyword match="y"/>
- </keywords>
-
- <keywords name="missingreserved" inherits="identifier" innerClass="reserved" case = "yes">
- <keyword match="new"/>
- </keywords>
-
-
- <keywords name="flowcontrol" inherits="identifier" innerClass="reserved" case = "yes">
- <keyword match="if"/>
- <keyword match="else"/>
- <keyword match="elsif"/>
- <keyword match="while"/>
- <keyword match="unless"/>
- <keyword match="for"/>
- <keyword match="foreach"/>
- <keyword match="until"/>
- <keyword match="do"/>
- <keyword match="continue"/>
- <keyword match="not"/>
- <keyword match="or"/>
- <keyword match="and"/>
- <keyword match="eq"/>
- <keyword match="ne"/>
- <keyword match="gt"/>
- <keyword match="lt"/>
- </keywords>
-
-</highlight>
diff --git a/library/Text_Highlighter/php.xml b/library/Text_Highlighter/php.xml
deleted file mode 100644
index 1b08ea203..000000000
--- a/library/Text_Highlighter/php.xml
+++ /dev/null
@@ -1,194 +0,0 @@
-<?xml version="1.0"?>
-<!-- $Id: php.xml,v 1.1 2007-06-03 02:35:28 ssttoo Exp $ -->
-
-<highlight lang="php">
-
- <authors>
- <author name="Andrey Demenev" email ="demenev@gmail.com"/>
- </authors>
-
-
- <default innerClass="code" />
-
- <region name="phpCode" delimClass="inlinetags" innerClass="code"
- start="\&lt;\?(php|=)?" end="\?\>" never-contained="yes">
- <contains all="yes"/>
- </region>
-
- <region name="block" delimClass="brackets" innerClass="code" start="\{" end="\}" contained="yes">
- <contains all="yes"/>
- </region>
-
- <region name="brackets" delimClass="brackets" innerClass="code" start="\(" end="\)" contained="yes" >
- <contains all="yes"/>
- </region>
-
- <region name="sqbrackets" delimClass="brackets" innerClass="code" start="\[" end="\]" contained="yes">
- <contains all="yes"/>
- </region>
-
-
- <region name="mlcomment" innerClass="comment" start="\/\*" end="\*\/" contained="yes">
- <contains block="phpdoc"/>
- <contains block="cvstag"/>
- </region>
-
- <region name="strdouble" delimClass="quotes" innerClass="string" start="&quot;" end="&quot;" contained="yes">
- <contains block="var"/>
- </region>
-
- <region name="exec" delimClass="quotes" innerClass="string" start="`" end="`" contained="yes">
- <contains block="var"/>
- </region>
-
- <region name="heredoc" delimClass="quotes" innerClass="string" start="/\&lt;\&lt;\&lt;[\x20\x09]*(\w+)$/m" end="/^%1%;?$/m" contained="yes" remember="yes">
- <contains block="var"/>
- </region>
-
- <region name="strsingle" delimClass="quotes" innerClass="string" start="'" end="'" contained="yes"/>
-
- <block name="escaped" match="\\\\|\\&quot;|\\'|\\`" innerClass="special" contained="yes">
- <onlyin region="strsingle"/>
- <onlyin region="exec"/>
- </block>
-
- <block name="descaped" match="\\[\\&quot;'`tnr\$\{]" innerClass="special" contained="yes">
- <onlyin region="strdouble"/>
- <onlyin region="heredoc"/>
- </block>
-
-
- <region name="comment" start="(#|\/\/)" end="/$|(?=\?\>)/m" innerClass="comment" contained="yes">
- <contains block="cvstag"/>
- </region>
-
-
- <block name="identifier" match="[a-z_]\w*" innerClass="identifier" contained="yes"/>
-
- <block name="typecast" match="\((array|int|integer|string|bool|boolean|object|float|double)\)" innerClass="reserved" contained="yes"/>
-
- <block name="curlyvar" match="\{\$[a-z_].*\}" innerClass="var" contained="yes">
- <onlyin region="strdouble"/>
- <onlyin region="heredoc"/>
- <onlyin region="exec"/>
- </block>
-
- <region name="codeescape" delimClass="inlinetags" innerClass="default" end="\&lt;\?(php|=)?" start="\?\>" contained="yes">
- <onlyin region="block"/>
- </region>
-
- <block name="hexinteger" match="0[xX][\da-f]+" innerClass="number" contained="yes"/>
- <block name="var" match="\$[a-z_]\w*" innerClass="var" contained="yes"/>
-
- <block name="integer" match="\d\d*|\b0\b" innerClass="number" contained="yes"/>
-
-
- <block name="octinteger" match="0[0-7]+" innerClass="number" contained="yes"/>
-
- <block name="float" match="(\d*\.\d+)|(\d+\.\d*)" innerClass="number" contained="yes"/>
-
- <block name="exponent"
- match="((\d+|((\d*\.\d+)|(\d+\.\d*)))[eE][+-]?\d+)"
- innerClass="number" contained="yes"/>
-
- <block name="phpdoc" match="\s@\w+\s" innerClass="inlinedoc" contained="yes">
- <onlyin region="mlcomment"/>
- <onlyin region="comment"/>
- </block>
-
- <block name="url" match="((https?|ftp):\/\/[\w\?\.\-\&amp;=\/%+]+)|(^|[\s,!?])www\.\w+\.\w+[\w\?\.\&amp;=\/%+]*" innerClass="url" contained="yes">
- <onlyin region="mlcomment"/>
- <onlyin region="comment"/>
- </block>
-
- <block name="email" match="\w+[\.\w\-]+@(\w+[\.\w\-])+" innerClass="url" contained="yes">
- <onlyin region="mlcomment"/>
- <onlyin region="comment"/>
- </block>
-
- <block name="note" match="\bnote:" innerClass="inlinedoc" contained="yes">
- <onlyin region="mlcomment"/>
- <onlyin region="comment"/>
- </block>
-
-
- <block name="cvstag" match="\$\w+\s*:.*\$" innerClass="inlinedoc" contained="yes">
- <onlyin region="mlcomment"/>
- <onlyin region="comment"/>
- </block>
-
- <keywords name="constants" inherits="identifier" innerClass="reserved" case = "yes">
- <keyword match="DIRECTORY_SEPARATOR"/>
- <keyword match="PATH_SEPARATOR"/>
- </keywords>
-
- <keywords name="reserved" inherits="identifier" innerClass="reserved">
- <keyword match="echo"/>
- <keyword match="foreach"/>
- <keyword match="else"/>
- <keyword match="if"/>
- <keyword match="elseif"/>
- <keyword match="for"/>
- <keyword match="as"/>
- <keyword match="while"/>
- <keyword match="foreach"/>
- <keyword match="break"/>
- <keyword match="continue"/>
- <keyword match="class"/>
- <keyword match="const"/>
- <keyword match="declare"/>
- <keyword match="switch"/>
- <keyword match="case"/>
- <keyword match="endfor"/>
- <keyword match="endswitch"/>
- <keyword match="endforeach"/>
- <keyword match="endswitch"/>
- <keyword match="endif"/>
- <keyword match="array"/>
- <keyword match="default"/>
- <keyword match="do"/>
- <keyword match="enddeclare"/>
- <keyword match="eval"/>
- <keyword match="exit"/>
- <keyword match="die"/>
- <keyword match="extends"/>
- <keyword match="function"/>
- <keyword match="global"/>
- <keyword match="include"/>
- <keyword match="include_once"/>
- <keyword match="require"/>
- <keyword match="require_once"/>
- <keyword match="isset"/>
- <keyword match="empty"/>
- <keyword match="list"/>
- <keyword match="new"/>
- <keyword match="static"/>
- <keyword match="unset"/>
- <keyword match="var"/>
- <keyword match="return"/>
- <keyword match="try"/>
- <keyword match="catch"/>
- <keyword match="final"/>
- <keyword match="throw"/>
- <keyword match="public"/>
- <keyword match="private"/>
- <keyword match="protected"/>
- <keyword match="abstract"/>
- <keyword match="interface"/>
- <keyword match="implements"/>
- <keyword match="const"/>
- <keyword match="define"/>
- <keyword match="__FILE__"/>
- <keyword match="__LINE__"/>
- <keyword match="__CLASS__"/>
- <keyword match="__METHOD__"/>
- <keyword match="__FUNCTION__"/>
- <keyword match="NULL"/>
- <keyword match="true"/>
- <keyword match="false"/>
- <keyword match="and"/>
- <keyword match="or"/>
- <keyword match="xor"/>
- </keywords>
-
-</highlight>
diff --git a/library/Text_Highlighter/python.xml b/library/Text_Highlighter/python.xml
deleted file mode 100644
index 29e77203c..000000000
--- a/library/Text_Highlighter/python.xml
+++ /dev/null
@@ -1,229 +0,0 @@
-<?xml version="1.0"?>
-<!-- $Id: python.xml,v 1.1 2007-06-03 02:35:28 ssttoo Exp $ -->
-
-<highlight lang="python" case="no">
-
- <authors>
- <author name="Andrey Demenev" email="demenev@gmail.com"/>
- </authors>
-
- <default innerClass="code" />
-
- <region name="strsingle3" delimClass="quotes" innerClass="string"
- start="'''" end="'''" />
-
- <region name="strdouble3" delimClass="quotes" innerClass="string"
- start="&quot;&quot;&quot;" end="&quot;&quot;&quot;">
- </region>
-
- <region name="strdouble" delimClass="quotes" innerClass="string"
- start="&quot;" end="&quot;" >
- </region>
-
- <region name="strsingle" delimClass="quotes" innerClass="string"
- start="'" end="'" />
-
- <region name="brackets" delimClass="brackets" innerClass="code" start="\(" end="\)" >
- <contains all="yes"/>
- </region>
-
- <region name="sqbrackets" delimClass="brackets" innerClass="code" start="\[" end="\]" >
- <contains all="yes"/>
- </region>
-
- <block name="escaped" match="\\." innerClass="special" contained="yes">
- <onlyin region="strsingle"/>
- <onlyin region="strsingle3"/>
- <onlyin region="strdouble"/>
- <onlyin region="strdouble3"/>
- </block>
-
- <block name="possiblefunction" match="[a-z_]\w*(?=\s*\()" innerClass="identifier" />
-
- <block name="identifier" match="[a-z_]\w*" innerClass="identifier" />
-
- <block name="exponent"
- match="((\d+|((\d*\.\d+)|(\d+\.\d*)))[eE][+-]?\d+)"
- innerClass="number" />
-
- <block name="imaginary" match="((\d*\.\d+)|(\d+\.\d*)|(\d+))j" innerClass="number"/>
-
- <block name="float" match="(\d*\.\d+)|(\d+\.\d*)" innerClass="number"/>
-
- <block name="integer" match="\d+l?|\b0l?\b" innerClass="number" />
-
- <block name="hexinteger" match="0[xX][\da-f]+l?" innerClass="number" />
-
- <block name="octinteger" match="0[0-7]+l?" innerClass="number" />
-
- <block name="comment" innerClass="comment"
- match="#.+" />
-
- <keywords name="reserved" inherits="identifier" innerClass="reserved" case = "yes">
- <keyword match="and"/>
- <keyword match="del"/>
- <keyword match="for"/>
- <keyword match="is"/>
- <keyword match="raise"/>
- <keyword match="assert"/>
- <keyword match="elif"/>
- <keyword match="from"/>
- <keyword match="lambda"/>
- <keyword match="return"/>
- <keyword match="break"/>
- <keyword match="else"/>
- <keyword match="global"/>
- <keyword match="not"/>
- <keyword match="try"/>
- <keyword match="class"/>
- <keyword match="except"/>
- <keyword match="if"/>
- <keyword match="or"/>
- <keyword match="while"/>
- <keyword match="continue"/>
- <keyword match="exec"/>
- <keyword match="import"/>
- <keyword match="pass"/>
- <keyword match="yield"/>
- <keyword match="def"/>
- <keyword match="finally"/>
- <keyword match="in"/>
- <keyword match="print"/>
- <keyword match="False"/>
- <keyword match="True"/>
- <keyword match="None"/>
- <keyword match="NotImplemented"/>
- <keyword match="Ellipsis"/>
-
- <keyword match="Exception" />
- <keyword match="SystemExit" />
- <keyword match="StopIteration" />
- <keyword match="StandardError" />
- <keyword match="KeyboardInterrupt" />
- <keyword match="ImportError" />
- <keyword match="EnvironmentError" />
- <keyword match="IOError" />
- <keyword match="OSError" />
- <keyword match="WindowsError" />
- <keyword match="EOFError" />
- <keyword match="RuntimeError" />
- <keyword match="NotImplementedError" />
- <keyword match="NameError" />
- <keyword match="UnboundLocalError" />
-
- <keyword match="AttributeError" />
- <keyword match="SyntaxError" />
- <keyword match="IndentationError" />
- <keyword match="TabError" />
- <keyword match="TypeError" />
- <keyword match="AssertionError" />
- <keyword match="LookupError" />
- <keyword match="IndexError" />
- <keyword match="KeyError" />
- <keyword match="ArithmeticError" />
- <keyword match="OverflowError" />
- <keyword match="ZeroDivisionError" />
- <keyword match="FloatingPointError" />
- <keyword match="ValueError" />
- <keyword match="UnicodeError" />
- <keyword match="UnicodeEncodeError" />
- <keyword match="UnicodeDecodeError" />
-
- <keyword match="UnicodeTranslateError" />
- <keyword match="ReferenceError" />
- <keyword match="SystemError" />
- <keyword match="MemoryError" />
- <keyword match="Warning" />
- <keyword match="UserWarning" />
- <keyword match="DeprecationWarning" />
- <keyword match="PendingDeprecationWarning" />
- <keyword match="SyntaxWarning" />
- <keyword match="OverflowWarning" />
- <keyword match="RuntimeWarning" />
- <keyword match="FutureWarning" />
-
- </keywords>
-
- <keywords name="builtin" inherits="possiblefunction"
- innerClass="builtin" otherwise="identifier" case = "yes">
- <keyword match="__import__"/>
-
- <keyword match="abs"/>
- <keyword match="apply"/>
- <keyword match="basestring"/>
- <keyword match="bool"/>
- <keyword match="buffer"/>
- <keyword match="callable"/>
- <keyword match="chr"/>
- <keyword match="classmethod"/>
- <keyword match="cmp"/>
-
- <keyword match="coerce"/>
- <keyword match="compile"/>
- <keyword match="complex"/>
- <keyword match="delattr"/>
- <keyword match="dict"/>
- <keyword match="dir"/>
- <keyword match="divmod"/>
- <keyword match="enumerate"/>
- <keyword match="eval"/>
-
- <keyword match="execfile"/>
- <keyword match="file"/>
- <keyword match="filter"/>
- <keyword match="float"/>
- <keyword match="getattr"/>
- <keyword match="globals"/>
- <keyword match="hasattr"/>
- <keyword match="hash"/>
- <keyword match="help"/>
-
- <keyword match="hex"/>
- <keyword match="id"/>
- <keyword match="input"/>
- <keyword match="int"/>
- <keyword match="intern"/>
- <keyword match="isinstance"/>
- <keyword match="issubclass"/>
- <keyword match="iter"/>
- <keyword match="len"/>
-
- <keyword match="list"/>
- <keyword match="locals"/>
- <keyword match="long"/>
- <keyword match="map"/>
- <keyword match="max"/>
- <keyword match="min"/>
- <keyword match="object"/>
- <keyword match="oct"/>
- <keyword match="open"/>
-
- <keyword match="ord"/>
- <keyword match="pow"/>
- <keyword match="property"/>
- <keyword match="range"/>
- <keyword match="raw_input"/>
- <keyword match="reduce"/>
- <keyword match="reload"/>
- <keyword match="repr"/>
- <keyword match="round"/>
-
- <keyword match="setattr"/>
- <keyword match="slice"/>
- <keyword match="staticmethod"/>
- <keyword match="sum"/>
- <keyword match="super"/>
- <keyword match="str"/>
- <keyword match="tuple"/>
- <keyword match="type"/>
- <keyword match="unichr"/>
-
- <keyword match="unicode"/>
- <keyword match="vars"/>
- <keyword match="xrange"/>
- <keyword match="zip"/>
-
- </keywords>
-
-</highlight>
-
diff --git a/library/Text_Highlighter/release b/library/Text_Highlighter/release
deleted file mode 100644
index 66f1fa603..000000000
--- a/library/Text_Highlighter/release
+++ /dev/null
@@ -1,4 +0,0 @@
-#!/bin/sh
-
-/usr/local/bin/php package.php make
-/usr/local/bin/pear package
diff --git a/library/Text_Highlighter/ruby.xml b/library/Text_Highlighter/ruby.xml
deleted file mode 100644
index 599f5af17..000000000
--- a/library/Text_Highlighter/ruby.xml
+++ /dev/null
@@ -1,141 +0,0 @@
-<?xml version="1.0"?>
-<!-- $Id: ruby.xml,v 1.1 2007-06-03 02:35:28 ssttoo Exp $ -->
-
-<highlight lang="ruby" case="no">
-
- <authors>
- <author name="Andrey Demenev" email="demenev@gmail.com"/>
- </authors>
-
- <comment>
-FIXME: While this construction : s.split /z/i
-is valid, regular expression is not recognized as such
-(/ folowing an identifier or number is not recognized as
-start of RE), making highlighting improper
-
-%q(a (nested) string) does not get highlighted correctly
- </comment>
-
- <default innerClass="code" />
-
- <region name="data" start="/^__END__$/m" end="$" delimClass="reserved" innerClass="comment" never-conteined="yes" />
-
- <region name="strdouble" delimClass="quotes" innerClass="string"
- start="&quot;" end="&quot;" >
- </region>
-
- <region name="qstrdouble" delimClass="quotes" innerClass="string"
- start="%[Qx]([!&quot;#\$%&amp;'+\-*.\/:;=?@^`|~{&lt;\[(])" end="%b1%" remember="yes" />
-
- <region name="strsingle" delimClass="quotes" innerClass="string"
- start="'" end="'" />
-
- <region name="qstrsingle" delimClass="quotes" innerClass="string"
- start="%[wq]([!&quot;#\$%&amp;'+\-*.\/:;=?@^`|~{&lt;\[(])" end="%b1%" remember="yes" />
-
- <block name="global" match="\$(\W|\w+)" innerClass="var" />
-
- <block name="classvar" match="/@@?[_a-z][\d_a-z]*/i" innerClass="var" />
-
- <region name="brackets" delimClass="brackets" innerClass="code" start="\(" end="\)" >
- <contains all="yes"/>
- </region>
-
- <region name="sqbrackets" delimClass="brackets" innerClass="code" start="\[" end="\]" >
- <contains all="yes"/>
- </region>
-
- <block name="escaped" match="\\." innerClass="special" contained="yes">
- <onlyin region="qstrsingle"/>
- <onlyin region="strsingle"/>
- <onlyin region="qstrdouble"/>
- <onlyin region="strdouble"/>
- <onlyin region="regexp"/>
- </block>
-
- <block name="identifier" match="[a-z_]\w*" innerClass="identifier" />
-
- <block name="exponent"
- match="((\d+|((\d*\.\d+)|(\d+\.\d*)))[eE][+-]?\d+)"
- innerClass="number" />
-
- <block name="float" match="(\d*\.\d+)|(\d+\.\d*)" innerClass="number"/>
-
- <block name="hexinteger" match="0[xX][\da-f]+l?" innerClass="number" />
-
- <block name="integer" match="\d+l?|\b0l?\b" innerClass="number" />
-
- <block name="octinteger" match="0[0-7]+l?" innerClass="number" />
-
-
- <region name="rubydoc" start="/^=begin$/m" end="/^=end$/m" delimClass="comment" innerClass="comment">
- <contains block="cvstag" />
- </region>
-
- <block name="cvstag" match="\$\w+\s*:.+\$" innerClass="inlinedoc" contained="yes">
- <onlyin region="comment"/>
- <onlyin region="rubydoc"/>
- </block>
-
- <region name="comment" innerClass="comment" start="#" end="/$/m" delimClass="comment" >
- <contains block="cvstag" />
- </region>
-
- <region name="regexp" delimClass="quotes" innerClass="string" start="\s*\/" end="\/[iomx]*"
- neverAfter="(?&lt;!\band|\bor|\bwhile|\buntil|\bunless|\bif|\belsif|\bwhen|[~=!|&amp;(,\[])$">
- </region>
-
- <keywords name="reserved" inherits="identifier" innerClass="reserved" case = "yes">
- <keyword match="__FILE__" />
- <keyword match="require" />
- <keyword match="and" />
- <keyword match="def" />
- <keyword match="end" />
- <keyword match="in" />
- <keyword match="or" />
- <keyword match="self" />
- <keyword match="unless" />
- <keyword match="__LINE__" />
- <keyword match="begin" />
- <keyword match="defined?" />
- <keyword match="ensure" />
- <keyword match="module" />
- <keyword match="redo" />
- <keyword match="super" />
- <keyword match="until" />
- <keyword match="BEGIN" />
- <keyword match="break" />
- <keyword match="do" />
- <keyword match="false" />
- <keyword match="next" />
- <keyword match="rescue" />
- <keyword match="then" />
- <keyword match="when" />
- <keyword match="END" />
- <keyword match="case" />
- <keyword match="else" />
- <keyword match="for" />
- <keyword match="nil" />
- <keyword match="retry" />
- <keyword match="true" />
- <keyword match="while" />
- <keyword match="alias" />
- <keyword match="module_function" />
- <keyword match="private" />
- <keyword match="public" />
- <keyword match="protected" />
- <keyword match="attr_reader" />
- <keyword match="attr_writer" />
- <keyword match="attr_accessor" />
- <keyword match="class" />
- <keyword match="elsif" />
- <keyword match="if" />
- <keyword match="not" />
- <keyword match="return" />
- <keyword match="undef" />
- <keyword match="yield" />
- </keywords>
-
-
-</highlight>
-
diff --git a/library/Text_Highlighter/sample.css b/library/Text_Highlighter/sample.css
deleted file mode 100644
index b4b38c5fc..000000000
--- a/library/Text_Highlighter/sample.css
+++ /dev/null
@@ -1,62 +0,0 @@
-.hl-main ol {
- line-height: 1.0;
-}
-.hl-default {
- color: Black;
-}
-.hl-code {
- color: Black;
-}
-.hl-brackets {
- color: Olive;
-}
-.hl-comment {
- color: Purple;
-}
-.hl-quotes {
- color: Darkred;
-}
-.hl-string {
- color: Red;
-}
-.hl-identifier {
- color: Blue;
-}
-.hl-builtin {
- color: Teal;
-}
-.hl-reserved {
- color: Green;
-}
-.hl-inlinedoc {
- color: Blue;
-}
-.hl-var {
- color: Darkblue;
-}
-.hl-url {
- color: Blue;
-}
-.hl-special {
- color: Navy;
-}
-.hl-number {
- color: Maroon;
-}
-.hl-inlinetags {
- color: Blue;
-}
-.hl-main {
- background: #ccc none repeat scroll 0 0;
- color: #000;
-/* background-color: White; */
-}
-.hl-gutter {
- background-color: #999999;
- color: White
-}
-.hl-table {
- font-family: courier;
- font-size: 12px;
- border: solid 1px Lightgrey;
-}
diff --git a/library/Text_Highlighter/sh.xml b/library/Text_Highlighter/sh.xml
deleted file mode 100644
index 1250de3bc..000000000
--- a/library/Text_Highlighter/sh.xml
+++ /dev/null
@@ -1,242 +0,0 @@
-<?xml version="1.0"?>
-<!-- $Id: sh.xml,v 1.2 2007-06-14 00:15:50 ssttoo Exp $ -->
-
-<highlight lang="sh" case = "yes">
-
- <authors>
- <author name="Noah Spurrier" email="noah@noah.org" />
- </authors>
-
- <comment>This highlighter is EXPERIMENTAL. It may work incorrectly.
- It is a crude hack of the perl syntax, which itself wasn't so good.
- But this seems to work OK.
- </comment>
-
- <default innerClass="code"/>
-
- <block name="interpreter" match="/^(#!)(.*)/m" innerClass="special">
- <partClass index="1" innerClass="special" />
- <partClass index="2" innerClass="string" />
- </block>
-
- <!--
- brackets
- -->
- <region name="block" delimClass="brackets" innerClass="code" start="\{" end="\}">
- <contains all="yes"/>
- </region>
-
- <region name="brackets" delimClass="brackets" innerClass="code" start="\(" end="\)">
- <contains all="yes"/>
- </region>
-
- <region name="sqbrackets" delimClass="brackets" innerClass="code" start="\[" end="\]">
- <contains all="yes"/>
- </region>
-
- <!--
- use smth
- -->
- <block name="usestatement" match="(use)\s+([\w:]*)" innerClass="special">
- <partClass index="1" innerClass="reserved" />
- <partClass index="2" innerClass="special" />
- </block>
-
-
- <region name="q-w-q-statement"
- start="/\b(q[wq]\s*((\{)|(\()|(\[)|(\&lt;)|([\W\S])))(?=(.*)((?(3)\})(?(4)\))(?(5)\])(?(6)\&gt;)(?(7)\7)))/Us"
- end="%b2%"
- innerClass="string" delimClass="quotes" remember="yes">
-
- <contains block="containedvar"/>
- <contains block="specialvar"/>
- <contains block="curlyvar"/>
-
- </region>
-
- <region name="qstatement"
- start="/\b(q\s*((\{)|(\()|(\[)|(\&lt;)|([\W\S])))(?=(.*)((?(3)\})(?(4)\))(?(5)\])(?(6)\&gt;)(?(7)\7)))/Us"
- end="%b2%"
- innerClass="string" delimClass="quotes" remember="yes">
-
- </region>
-
- <!--
- comments
- -->
- <block name="comment" match="#.*" innerClass="comment" />
-
-
- <!--
- regexpr
- FIXME: this should be rewritten
- -->
- <block name="dblregexprver1" match="/(s|tr) ([|#~`!@$%^&amp;*-+=\\;:'&quot;,.\/?]) ((\\.|[^\\])*?) (\2)((\\.|[^\\])*?)(\2[ecgimosx]*)/x" innerClass="string">
- <partClass index="1" innerClass="quotes" />
- <partClass index="2" innerClass="quotes" />
- <partClass index="3" innerClass="string" />
- <partClass index="5" innerClass="quotes" />
- <partClass index="6" innerClass="string" />
- <partClass index="8" innerClass="quotes" />
- </block>
-
- <block name="dblregexprver2" match="/(m) ([|#~`!@$%^&amp;*-+=\\;:'&quot;,.\/?]) ((\\.|[^\\])*?) (\2[ecgimosx]*)/x" innerClass="string">
- <partClass index="1" innerClass="quotes" />
- <partClass index="2" innerClass="quotes" />
- <partClass index="3" innerClass="string" />
- <partClass index="5" innerClass="quotes" />
- </block>
-
-
- <region name="regexp" start=" \/" end="\/[cgimosx]*" innerClass="string" delimClass="quotes" case="yes">
- <contains block="reescaped"/>
- </region>
-
- <block name="reescaped" match="\\\/" innerClass="string" contained="yes">
- <onlyin region="regexp"/>
- </block>
-
- <!--
- variables
- FIXME: @{...}
- -->
- <block name="bracketsvars" match="([a-z1-9_]+)(\s*=>)" innerClass="string" contained="yes" case="no">
- <partClass index="1" innerClass="string" />
- <partClass index="2" innerClass="code" />
- <onlyin region="brackets"/>
- </block>
-
- <block name="specialvar" match="\$#?[1-9'`@!]" innerClass="var"/>
-
- <block name="var" match="(\$#?|[@%*])([a-z1-9_]+::)*([a-z1-9_]+|\^(?-i)[A-Z]?(?i))" innerClass="var" case="no"/>
- <block name="containedvar" match="\$([a-z1-9_]+|\^(?-i)[A-Z]?(?i))" innerClass="var" case="no"/>
-
- <block name="classvar" match="(\{)([a-z1-9]+)(\})" innerClass="var" case="no">
- <partClass index="1" innerClass="brackets" />
- <partClass index="2" innerClass="var" />
- <partClass index="3" innerClass="brackets" />
- </block>
-
- <block name="curlyvar" match="[\$@%]#?\{[a-z1-9]+\}" innerClass="var" case="no"/>
-
- <!--
- quotes
- -->
- <region name="exec" delimClass="quotes" innerClass="string" start="`" end="`">
- <contains block="containedvar"/>
- <contains block="specialvar"/>
- <contains block="curlyvar"/>
- </region>
-
- <region name="strsingle" delimClass="quotes" innerClass="string" start="'" end="'"/>
-
- <block name="escaped" match="\\\\|\\&quot;|\\'|\\`" innerClass="special" contained="yes">
- <onlyin region="qstatement"/>
- <onlyin region="strsingle"/>
- <onlyin region="exec"/>
- </block>
-
- <region name="strdouble" delimClass="quotes" innerClass="string" start="&quot;" end="&quot;">
- <contains block="containedvar"/>
- <contains block="specialvar"/>
- <contains block="curlyvar"/>
- </region>
-
- <block name="descaped" match="\\[\\&quot;'`tnr\$\{@]" innerClass="special" contained="yes">
- <onlyin region="strdouble"/>
- <onlyin region="q-w-q-statement"/>
- </block>
-
- <!-- logical op.
- <block name="logic" match="\|\||&amp;&amp;" innerClass="reserved" contained="yes"/>-->
-
- <!--
- identifiers
- -->
- <block name="identifier" match="[a-z_]\w*" innerClass="identifier" case="no"/>
-
- <!--
- numbers
- -->
- <block name="number" match="\d*\.?\d+" innerClass="number"/>
-
- <!--
- GNU and posix standard shell utilities here.
- -->
- <keywords name="reserved" inherits="identifier" innerClass="reserved" case = "yes">
- <keyword match="cd"/>
- <keyword match="cp"/>
- <keyword match="rm"/>
- <keyword match="echo"/>
- <keyword match="printf"/>
- <keyword match="exit"/>
- <keyword match="cut"/>
- <keyword match="join"/>
- <keyword match="comm"/>
- <keyword match="fmt"/>
- <keyword match="grep"/>
- <keyword match="egrep"/>
- <keyword match="fgrep"/>
- <keyword match="sed"/>
- <keyword match="awk"/>
- <keyword match="yes"/>
- <keyword match="false"/>
- <keyword match="true"/>
- <keyword match="test"/>
- <keyword match="expr"/>
- <keyword match="tee"/>
- <keyword match="basename"/>
- <keyword match="dirname"/>
- <keyword match="pathchk"/>
- <keyword match="pwd"/>
- <keyword match="stty"/>
- <keyword match="tty"/>
- <keyword match="env"/>
- <keyword match="printenv"/>
- <keyword match="id"/>
- <keyword match="logname"/>
- <keyword match="whoami"/>
- <keyword match="groups"/>
- <keyword match="users"/>
- <keyword match="who"/>
- <keyword match="date"/>
- <keyword match="uname"/>
- <keyword match="hostname"/>
- <keyword match="chroot"/>
- <keyword match="nice"/>
- <keyword match="nohup"/>
- <keyword match="sleep"/>
- <keyword match="factor"/>
- <keyword match="seq"/>
- <keyword match="getopt"/>
- <keyword match="getopts"/>
- <keyword match="options"/>
- <keyword match="shift"/>
- </keywords>
-
- <keywords name="flowcontrol" inherits="identifier" innerClass="reserved" case = "yes">
- <keyword match="if"/>
- <keyword match="fi"/>
- <keyword match="then"/>
- <keyword match="else"/>
- <keyword match="elif"/>
- <keyword match="case"/>
- <keyword match="esac"/>
- <keyword match="while"/>
- <keyword match="done"/>
- <keyword match="for"/>
- <keyword match="in"/>
- <keyword match="function"/>
- <keyword match="until"/>
- <keyword match="do"/>
- <keyword match="select"/>
- <keyword match="time"/>
- <!--
- <keyword match="[["/>
- <keyword match="]]"/>
- -->
- <keyword match="read"/>
- <keyword match="set"/>
- </keywords>
-
-</highlight>
diff --git a/library/Text_Highlighter/sql.xml b/library/Text_Highlighter/sql.xml
deleted file mode 100644
index 19cae49a0..000000000
--- a/library/Text_Highlighter/sql.xml
+++ /dev/null
@@ -1,496 +0,0 @@
-<?xml version="1.0"?>
-<!-- $Id: sql.xml,v 1.1 2007-06-03 02:35:28 ssttoo Exp $ -->
-
-<highlight lang="sql" case="no">
-
- <authors>
- <author name="Andrey Demenev" email="demenev@gmail.com"/>
- </authors>
-
-
- <comment>Based on SQL-99</comment>
-
- <default innerClass="code" />
-
- <region name="qidentifier" delimClass="quotes" innerClass="identifier"
- start="`" end="`" />
-
- <region name="mlcomment" delimClass="comment" innerClass="comment"
- start="\/\*" end="\*\/" />
-
- <block name="comment" match="(#|--\s).*" innerClass="comment" />
-
- <block name="identifier" match="[a-z_]\w*" innerClass="identifier" />
-
- <region name="strdouble" delimClass="quotes" innerClass="string"
- start="&quot;" end="&quot;" >
- </region>
-
- <region name="brackets" delimClass="brackets" innerClass="code"
- start="\(" end="\)" >
- <contains all="yes"/>
- </region>
-
- <region name="strsingle" delimClass="quotes" innerClass="string"
- start="'" end="'" />
-
- <block name="escaped" match="\\." innerClass="special" contained="yes">
- <onlyin region="strsingle"/>
- <onlyin region="strdouble"/>
- </block>
-
- <block name="exponent"
- match="((\d+|((\d*\.\d+)|(\d+\.\d*)))[eE][+-]?\d+)"
- innerClass="number" />
-
- <block name="float" match="(\d*\.\d+)|(\d+\.\d*)" innerClass="number"/>
-
- <block name="integer" match="\d+l?|\b0l?\b" innerClass="number" />
-
- <block name="hexinteger" match="0[xX][\da-f]+l?" innerClass="number" />
-
- <keywords name="reserved" inherits="identifier" innerClass="reserved" case = "no">
- <keyword match="ABSOLUTE" />
- <keyword match="ACTION" />
- <keyword match="ADD" />
- <keyword match="ADMIN" />
- <keyword match="AFTER" />
- <keyword match="AGGREGATE" />
- <keyword match="ALIAS" />
- <keyword match="ALL" />
- <keyword match="ALLOCATE" />
- <keyword match="ALTER" />
- <keyword match="AND" />
- <keyword match="ANY" />
- <keyword match="ARE" />
- <keyword match="ARRAY" />
- <keyword match="AS" />
- <keyword match="ASC" />
- <keyword match="ASSERTION" />
- <keyword match="AT" />
- <keyword match="AUTHORIZATION" />
- <keyword match="BEFORE" />
- <keyword match="BEGIN" />
- <keyword match="BINARY" />
- <keyword match="BIT" />
- <keyword match="BLOB" />
- <keyword match="BOOLEAN" />
- <keyword match="BOTH" />
- <keyword match="BREADTH" />
- <keyword match="BY" />
- <keyword match="CALL" />
- <keyword match="CASCADE" />
- <keyword match="CASCADED" />
- <keyword match="CASE" />
- <keyword match="CAST" />
- <keyword match="CATALOG" />
- <keyword match="CHAR" />
- <keyword match="CHARACTER" />
- <keyword match="CHECK" />
- <keyword match="CLASS" />
- <keyword match="CLOB" />
- <keyword match="CLOSE" />
- <keyword match="COLLATE" />
- <keyword match="COLLATION" />
- <keyword match="COLUMN" />
- <keyword match="COMMIT" />
- <keyword match="COMPLETION" />
- <keyword match="CONNECT" />
- <keyword match="CONNECTION" />
- <keyword match="CONSTRAINT" />
- <keyword match="CONSTRAINTS" />
- <keyword match="CONSTRUCTOR" />
- <keyword match="CONTINUE" />
- <keyword match="CORRESPONDING" />
- <keyword match="CREATE" />
- <keyword match="CROSS" />
- <keyword match="CUBE" />
- <keyword match="CURRENT" />
- <keyword match="CURRENT_DATE" />
- <keyword match="CURRENT_PATH" />
- <keyword match="CURRENT_ROLE" />
- <keyword match="CURRENT_TIME" />
- <keyword match="CURRENT_TIMESTAMP" />
- <keyword match="CURRENT_USER" />
- <keyword match="CURSOR" />
- <keyword match="CYCLE" />
- <keyword match="DATA" />
- <keyword match="DATE" />
- <keyword match="DAY" />
- <keyword match="DEALLOCATE" />
- <keyword match="DEC" />
- <keyword match="DECIMAL" />
- <keyword match="DECLARE" />
- <keyword match="DEFAULT" />
- <keyword match="DEFERRABLE" />
- <keyword match="DEFERRED" />
- <keyword match="DELETE" />
- <keyword match="DEPTH" />
- <keyword match="DEREF" />
- <keyword match="DESC" />
- <keyword match="DESCRIBE" />
- <keyword match="DESCRIPTOR" />
- <keyword match="DESTROY" />
- <keyword match="DESTRUCTOR" />
- <keyword match="DETERMINISTIC" />
- <keyword match="DIAGNOSTICS" />
- <keyword match="DICTIONARY" />
- <keyword match="DISCONNECT" />
- <keyword match="DISTINCT" />
- <keyword match="DOMAIN" />
- <keyword match="DOUBLE" />
- <keyword match="DROP" />
- <keyword match="DYNAMIC" />
- <keyword match="EACH" />
- <keyword match="ELSE" />
- <keyword match="END" />
- <keyword match="END-EXEC" />
- <keyword match="EQUALS" />
- <keyword match="ESCAPE" />
- <keyword match="EVERY" />
- <keyword match="EXCEPT" />
- <keyword match="EXCEPTION" />
- <keyword match="EXEC" />
- <keyword match="EXECUTE" />
- <keyword match="EXTERNAL" />
- <keyword match="FALSE" />
- <keyword match="FETCH" />
- <keyword match="FIRST" />
- <keyword match="FLOAT" />
- <keyword match="FOR" />
- <keyword match="FOREIGN" />
- <keyword match="FOUND" />
- <keyword match="FREE" />
- <keyword match="FROM" />
- <keyword match="FULL" />
- <keyword match="FUNCTION" />
- <keyword match="GENERAL" />
- <keyword match="GET" />
- <keyword match="GLOBAL" />
- <keyword match="GO" />
- <keyword match="GOTO" />
- <keyword match="GRANT" />
- <keyword match="GROUP" />
- <keyword match="GROUPING" />
- <keyword match="HAVING" />
- <keyword match="HOST" />
- <keyword match="HOUR" />
- <keyword match="IDENTITY" />
- <keyword match="IGNORE" />
- <keyword match="IMMEDIATE" />
- <keyword match="IN" />
- <keyword match="INDICATOR" />
- <keyword match="INITIALIZE" />
- <keyword match="INITIALLY" />
- <keyword match="INNER" />
- <keyword match="INOUT" />
- <keyword match="INPUT" />
- <keyword match="INSERT" />
- <keyword match="INT" />
- <keyword match="INTEGER" />
- <keyword match="INTERSECT" />
- <keyword match="INTERVAL" />
- <keyword match="INTO" />
- <keyword match="IS" />
- <keyword match="ISOLATION" />
- <keyword match="ITERATE" />
- <keyword match="JOIN" />
- <keyword match="KEY" />
- <keyword match="LANGUAGE" />
- <keyword match="LARGE" />
- <keyword match="LAST" />
- <keyword match="LATERAL" />
- <keyword match="LEADING" />
- <keyword match="LEFT" />
- <keyword match="LESS" />
- <keyword match="LEVEL" />
- <keyword match="LIKE" />
- <keyword match="LIMIT" />
- <keyword match="LOCAL" />
- <keyword match="LOCALTIME" />
- <keyword match="LOCALTIMESTAMP" />
- <keyword match="LOCATOR" />
- <keyword match="MAP" />
- <keyword match="MATCH" />
- <keyword match="MINUTE" />
- <keyword match="MODIFIES" />
- <keyword match="MODIFY" />
- <keyword match="MODULE" />
- <keyword match="MONTH" />
- <keyword match="NAMES" />
- <keyword match="NATIONAL" />
- <keyword match="NATURAL" />
- <keyword match="NCHAR" />
- <keyword match="NCLOB" />
- <keyword match="NEW" />
- <keyword match="NEXT" />
- <keyword match="NO" />
- <keyword match="NONE" />
- <keyword match="NOT" />
- <keyword match="NULL" />
- <keyword match="NUMERIC" />
- <keyword match="OBJECT" />
- <keyword match="OF" />
- <keyword match="OFF" />
- <keyword match="OLD" />
- <keyword match="ON" />
- <keyword match="ONLY" />
- <keyword match="OPEN" />
- <keyword match="OPERATION" />
- <keyword match="OPTION" />
- <keyword match="OR" />
- <keyword match="ORDER" />
- <keyword match="ORDINALITY" />
- <keyword match="OUT" />
- <keyword match="OUTER" />
- <keyword match="OUTPUT" />
- <keyword match="PAD" />
- <keyword match="PARAMETER" />
- <keyword match="PARAMETERS" />
- <keyword match="PARTIAL" />
- <keyword match="PATH" />
- <keyword match="POSTFIX" />
- <keyword match="PRECISION" />
- <keyword match="PREFIX" />
- <keyword match="PREORDER" />
- <keyword match="PREPARE" />
- <keyword match="PRESERVE" />
- <keyword match="PRIMARY" />
- <keyword match="PRIOR" />
- <keyword match="PRIVILEGES" />
- <keyword match="PROCEDURE" />
- <keyword match="PUBLIC" />
- <keyword match="READ" />
- <keyword match="READS" />
- <keyword match="REAL" />
- <keyword match="RECURSIVE" />
- <keyword match="REF" />
- <keyword match="REFERENCES" />
- <keyword match="REFERENCING" />
- <keyword match="RELATIVE" />
- <keyword match="RESTRICT" />
- <keyword match="RESULT" />
- <keyword match="RETURN" />
- <keyword match="RETURNS" />
- <keyword match="REVOKE" />
- <keyword match="RIGHT" />
- <keyword match="ROLE" />
- <keyword match="ROLLBACK" />
- <keyword match="ROLLUP" />
- <keyword match="ROUTINE" />
- <keyword match="ROW" />
- <keyword match="ROWS" />
- <keyword match="SAVEPOINT" />
- <keyword match="SCHEMA" />
- <keyword match="SCOPE" />
- <keyword match="SCROLL" />
- <keyword match="SEARCH" />
- <keyword match="SECOND" />
- <keyword match="SECTION" />
- <keyword match="SELECT" />
- <keyword match="SEQUENCE" />
- <keyword match="SESSION" />
- <keyword match="SESSION_USER" />
- <keyword match="SET" />
- <keyword match="SETS" />
- <keyword match="SIZE" />
- <keyword match="SMALLINT" />
- <keyword match="SOME" />
- <keyword match="SPACE" />
- <keyword match="SPECIFIC" />
- <keyword match="SPECIFICTYPE" />
- <keyword match="SQL" />
- <keyword match="SQLEXCEPTION" />
- <keyword match="SQLSTATE" />
- <keyword match="SQLWARNING" />
- <keyword match="START" />
- <keyword match="STATE" />
- <keyword match="STATEMENT" />
- <keyword match="STATIC" />
- <keyword match="STRUCTURE" />
- <keyword match="SYSTEM_USER" />
- <keyword match="TABLE" />
- <keyword match="TEMPORARY" />
- <keyword match="TERMINATE" />
- <keyword match="THAN" />
- <keyword match="THEN" />
- <keyword match="TIME" />
- <keyword match="TIMESTAMP" />
- <keyword match="TIMEZONE_HOUR" />
- <keyword match="TIMEZONE_MINUTE" />
- <keyword match="TO" />
- <keyword match="TRAILING" />
- <keyword match="TRANSACTION" />
- <keyword match="TRANSLATION" />
- <keyword match="TREAT" />
- <keyword match="TRIGGER" />
- <keyword match="TRUE" />
- <keyword match="UNDER" />
- <keyword match="UNION" />
- <keyword match="UNIQUE" />
- <keyword match="UNKNOWN" />
- <keyword match="UNNEST" />
- <keyword match="UPDATE" />
- <keyword match="USAGE" />
- <keyword match="USER" />
- <keyword match="USING" />
- <keyword match="VALUE" />
- <keyword match="VALUES" />
- <keyword match="VARCHAR" />
- <keyword match="VARIABLE" />
- <keyword match="VARYING" />
- <keyword match="VIEW" />
- <keyword match="WHEN" />
- <keyword match="WHENEVER" />
- <keyword match="WHERE" />
- <keyword match="WITH" />
- <keyword match="WITHOUT" />
- <keyword match="WORK" />
- <keyword match="WRITE" />
- <keyword match="YEAR" />
- <keyword match="ZONE" />
- </keywords>
- <keywords name="keyword" inherits="identifier" innerClass="var" case = "no">
- <keyword match="ABS" />
- <keyword match="ADA" />
- <keyword match="ASENSITIVE" />
- <keyword match="ASSIGNMENT" />
- <keyword match="ASYMMETRIC" />
- <keyword match="ATOMIC" />
- <keyword match="AVG" />
- <keyword match="BETWEEN" />
- <keyword match="BITVAR" />
- <keyword match="BIT_LENGTH" />
- <keyword match="C" />
- <keyword match="CALLED" />
- <keyword match="CARDINALITY" />
- <keyword match="CATALOG_NAME" />
- <keyword match="CHAIN" />
- <keyword match="CHARACTER_LENGTH" />
- <keyword match="CHARACTER_SET_CATALOG" />
- <keyword match="CHARACTER_SET_NAME" />
- <keyword match="CHARACTER_SET_SCHEMA" />
- <keyword match="CHAR_LENGTH" />
- <keyword match="CHECKED" />
- <keyword match="CLASS_ORIGIN" />
- <keyword match="COALESCE" />
- <keyword match="COBOL" />
- <keyword match="COLLATION_CATALOG" />
- <keyword match="COLLATION_NAME" />
- <keyword match="COLLATION_SCHEMA" />
- <keyword match="COLUMN_NAME" />
- <keyword match="COMMAND_FUNCTION" />
- <keyword match="COMMAND_FUNCTION_CODE" />
- <keyword match="COMMITTED" />
- <keyword match="CONDITION_NUMBER" />
- <keyword match="CONNECTION_NAME" />
- <keyword match="CONSTRAINT_CATALOG" />
- <keyword match="CONSTRAINT_NAME" />
- <keyword match="CONSTRAINT_SCHEMA" />
- <keyword match="CONTAINS" />
- <keyword match="CONVERT" />
- <keyword match="COUNT" />
- <keyword match="CURSOR_NAME" />
- <keyword match="DATETIME_INTERVAL_CODE" />
- <keyword match="DATETIME_INTERVAL_PRECISION" />
- <keyword match="DEFINED" />
- <keyword match="DEFINER" />
- <keyword match="DISPATCH" />
- <keyword match="DYNAMIC_FUNCTION" />
- <keyword match="DYNAMIC_FUNCTION_CODE" />
- <keyword match="EXISTING" />
- <keyword match="EXISTS" />
- <keyword match="EXTRACT" />
- <keyword match="FINAL" />
- <keyword match="FORTRAN" />
- <keyword match="G" />
- <keyword match="GENERATED" />
- <keyword match="GRANTED" />
- <keyword match="HIERARCHY" />
- <keyword match="HOLD" />
- <keyword match="IMPLEMENTATION" />
- <keyword match="INFIX" />
- <keyword match="INSENSITIVE" />
- <keyword match="INSTANCE" />
- <keyword match="INSTANTIABLE" />
- <keyword match="INVOKER" />
- <keyword match="K" />
- <keyword match="KEY_MEMBER" />
- <keyword match="KEY_TYPE" />
- <keyword match="LENGTH" />
- <keyword match="LOWER" />
- <keyword match="M" />
- <keyword match="MAX" />
- <keyword match="MESSAGE_LENGTH" />
- <keyword match="MESSAGE_OCTET_LENGTH" />
- <keyword match="MESSAGE_TEXT" />
- <keyword match="METHOD" />
- <keyword match="MIN" />
- <keyword match="MOD" />
- <keyword match="MORE" />
- <keyword match="MUMPS" />
- <keyword match="NAME" />
- <keyword match="NULLABLE" />
- <keyword match="NULLIF" />
- <keyword match="NUMBER" />
- <keyword match="OCTET_LENGTH" />
- <keyword match="OPTIONS" />
- <keyword match="OVERLAPS" />
- <keyword match="OVERLAY" />
- <keyword match="OVERRIDING" />
- <keyword match="PARAMETER_MODE" />
- <keyword match="PARAMETER_NAME" />
- <keyword match="PARAMETER_ORDINAL_POSITION" />
- <keyword match="PARAMETER_SPECIFIC_CATALOG" />
- <keyword match="PARAMETER_SPECIFIC_NAME" />
- <keyword match="PARAMETER_SPECIFIC_SCHEMA" />
- <keyword match="PASCAL" />
- <keyword match="PLI" />
- <keyword match="POSITION" />
- <keyword match="REPEATABLE" />
- <keyword match="RETURNED_LENGTH" />
- <keyword match="RETURNED_OCTET_LENGTH" />
- <keyword match="RETURNED_SQLSTATE" />
- <keyword match="ROUTINE_CATALOG" />
- <keyword match="ROUTINE_NAME" />
- <keyword match="ROUTINE_SCHEMA" />
- <keyword match="ROW_COUNT" />
- <keyword match="SCALE" />
- <keyword match="SCHEMA_NAME" />
- <keyword match="SECURITY" />
- <keyword match="SELF" />
- <keyword match="SENSITIVE" />
- <keyword match="SERIALIZABLE" />
- <keyword match="SERVER_NAME" />
- <keyword match="SIMILAR" />
- <keyword match="SIMPLE" />
- <keyword match="SOURCE" />
- <keyword match="SPECIFIC_NAME" />
- <keyword match="STYLE" />
- <keyword match="SUBCLASS_ORIGIN" />
- <keyword match="SUBLIST" />
- <keyword match="SUBSTRING" />
- <keyword match="SUM" />
- <keyword match="SYMMETRIC" />
- <keyword match="SYSTEM" />
- <keyword match="TABLE_NAME" />
- <keyword match="TRANSACTIONS_COMMITTED" />
- <keyword match="TRANSACTIONS_ROLLED_BACK" />
- <keyword match="TRANSACTION_ACTIVE" />
- <keyword match="TRANSFORM" />
- <keyword match="TRANSFORMS" />
- <keyword match="TRANSLATE" />
- <keyword match="TRIGGER_CATALOG" />
- <keyword match="TRIGGER_NAME" />
- <keyword match="TRIGGER_SCHEMA" />
- <keyword match="TRIM" />
- <keyword match="TYPE" />
- <keyword match="UNCOMMITTED" />
- <keyword match="UNNAMED" />
- <keyword match="UPPER" />
- <keyword match="USER_DEFINED_TYPE_CATALOG" />
- <keyword match="USER_DEFINED_TYPE_NAME" />
- <keyword match="USER_DEFINED_TYPE_SCHEMA" />
- </keywords>
-
-</highlight>
diff --git a/library/Text_Highlighter/vbscript.xml b/library/Text_Highlighter/vbscript.xml
deleted file mode 100644
index 09c37ffde..000000000
--- a/library/Text_Highlighter/vbscript.xml
+++ /dev/null
@@ -1,305 +0,0 @@
-<?xml version="1.0"?>
-<!-- $Id: vbscript.xml,v 1.2 2008-01-02 00:05:52 ssttoo Exp $ -->
-
-<highlight lang="vbscript" case="no">
-
- <authors>
- <author name="Daniel Fruzynski" email="daniel-AT-poradnik-webmastera.com" />
- </authors>
-
- <default innerClass="code" />
-
- <region name="brackets" delimClass="brackets" innerClass="code" start="\(" end="\)">
- <contains all="yes"/>
- </region>
-
-
- <region name="strdouble" delimClass="quotes" innerClass="string" start="&quot;" end="&quot;"/>
-
- <region name="comment" start="'|[Rr][Ee][Mm]\b" end="/$/m" innerClass="comment">
- <contains block="cvstag"/>
- </region>
-
- <block name="number" match="\d*\.?\d+" innerClass="number"/>
- <block name="hexnumber" match="&amp;H[0-9a-fA-F]+" innerClass="number"/>
-
- <block name="identifier" match="[a-z_]\w*" innerClass="identifier" case="no"/>
-
- <block name="url" match="((https?|ftp):\/\/[\w\?\.\-\&amp;=\/%+]+)|(^|[\s,!?])www\.\w+\.\w+[\w\?\.\&amp;=\/%+]*" innerClass="url" contained="yes">
- <onlyin region="comment"/>
- </block>
-
- <block name="email" match="\w+[\.\w\-]+@(\w+[\.\w\-])+" innerClass="url" contained="yes">
- <onlyin region="comment"/>
- </block>
-
- <block name="note" match="\b(note|fixme):" innerClass="inlinedoc" contained="yes" case="no">
- <onlyin region="comment"/>
- </block>
-
-
- <block name="cvstag" match="\$\w+:.+\$" innerClass="inlinedoc" contained="yes">
- <onlyin region="comment"/>
- </block>
-
- <keywords name="constants" inherits="identifier" innerClass="builtin" case="no">
- <!-- Color Constants -->
- <keyword match="vbBlack" />
- <keyword match="vbRed" />
- <keyword match="vbGreen" />
- <keyword match="vbYellow" />
- <keyword match="vbBlue" />
- <keyword match="vbMagenta" />
- <keyword match="vbCyan" />
- <keyword match="vbWhite" />
- <!-- Comparison Constants -->
- <keyword match="vbBinaryCompare" />
- <keyword match="vbTextCompare" />
- <!-- Date and Time Constants -->
- <keyword match="vbSunday" />
- <keyword match="vbMonday" />
- <keyword match="vbTuesday" />
- <keyword match="vbWednesday" />
- <keyword match="vbThursday" />
- <keyword match="vbFriday" />
- <keyword match="vbSaturday" />
- <keyword match="vbUseSystemDayOfWeek" />
- <keyword match="vbFirstJan1" />
- <keyword match="vbFirstFourDays" />
- <keyword match="vbFirstFullWeek" />
- <!-- Date Format Constants -->
- <keyword match="vbGeneralDate" />
- <keyword match="vbLongDate" />
- <keyword match="vbShortDate" />
- <keyword match="vbLongTime" />
- <keyword match="vbShortTime" />
- <!-- Miscellaneous Constants -->
- <keyword match="vbObjectError" />
- <!-- MsgBox Constants -->
- <keyword match="vbOKOnly" />
- <keyword match="vbOKCancel" />
- <keyword match="vbAbortRetryIgnore" />
- <keyword match="vbYesNoCancel" />
- <keyword match="vbYesNo" />
- <keyword match="vbRetryCancel" />
- <keyword match="vbCritical" />
- <keyword match="vbQuestion" />
- <keyword match="vbExclamation" />
- <keyword match="vbInformation" />
- <keyword match="vbDefaultButton1" />
- <keyword match="vbDefaultButton2" />
- <keyword match="vbDefaultButton3" />
- <keyword match="vbDefaultButton4" />
- <keyword match="vbApplicationModal" />
- <keyword match="vbSystemModal" />
- <keyword match="vbOK" />
- <keyword match="vbCancel" />
- <keyword match="vbAbort" />
- <keyword match="vbRetry" />
- <keyword match="vbIgnore" />
- <keyword match="vbYes" />
- <keyword match="vbNo" />
- <!-- String Constants -->
- <keyword match="vbCr" />
- <keyword match="VbCrLf" />
- <keyword match="vbFormFeed" />
- <keyword match="vbLf" />
- <keyword match="vbNewLine" />
- <keyword match="vbNullChar" />
- <keyword match="vbNullString" />
- <keyword match="vbTab" />
- <keyword match="vbVerticalTab" />
- <!-- Tristate Constants -->
- <keyword match="vbUseDefault" />
- <keyword match="vbTrue" />
- <keyword match="vbFalse" />
- <!-- VarType Constants -->
- <keyword match="vbEmpty" />
- <keyword match="vbNull" />
- <keyword match="vbInteger" />
- <keyword match="vbLong" />
- <keyword match="vbSingle" />
- <keyword match="vbDouble" />
- <keyword match="vbCurrency" />
- <keyword match="vbDate" />
- <keyword match="vbString" />
- <keyword match="vbObject" />
- <keyword match="vbError" />
- <keyword match="vbBoolean" />
- <keyword match="vbVariant" />
- <keyword match="vbDataObject" />
- <keyword match="vbDecimal" />
- <keyword match="vbByte" />
- <keyword match="vbArray" />
- </keywords>
-
- <keywords name="functions" inherits="identifier" innerClass="builtin" case="no">
- <keyword match="Abs" />
- <keyword match="Array" />
- <keyword match="Asc" />
- <keyword match="Atn" />
- <keyword match="CBool" />
- <keyword match="CByte" />
- <keyword match="CCur" />
- <keyword match="CDate" />
- <keyword match="CDbl" />
- <keyword match="Chr" />
- <keyword match="CInt" />
- <keyword match="CLng" />
- <keyword match="Cos" />
- <keyword match="CreateObject" />
- <keyword match="CSng" />
- <keyword match="CStr" />
- <keyword match="Date" />
- <keyword match="DateAdd" />
- <keyword match="DateDiff" />
- <keyword match="DatePart" />
- <keyword match="DateSerial" />
- <keyword match="DateValue" />
- <keyword match="Day" />
- <keyword match="Escape" />
- <keyword match="Eval" />
- <keyword match="Exp" />
- <keyword match="Filter" />
- <keyword match="FormatCurrency" />
- <keyword match="FormatDateTime" />
- <keyword match="FormatNumber" />
- <keyword match="FormatPercent" />
- <keyword match="GetLocale" />
- <keyword match="GetObject" />
- <keyword match="GetRef" />
- <keyword match="Hex" />
- <keyword match="Hour" />
- <keyword match="InputBox" />
- <keyword match="InStr" />
- <keyword match="InStrRev" />
- <keyword match="Int" />
- <keyword match="Fix" />
- <keyword match="IsArray" />
- <keyword match="IsDate" />
- <keyword match="IsEmpty" />
- <keyword match="IsNull" />
- <keyword match="IsNumeric" />
- <keyword match="IsObject" />
- <keyword match="Join" />
- <keyword match="LBound" />
- <keyword match="LCase" />
- <keyword match="Left" />
- <keyword match="Len" />
- <keyword match="LoadPicture" />
- <keyword match="Log" />
- <keyword match="LTrim" />
- <keyword match="RTrim" />
- <keyword match="Trim" />
- <keyword match="Mid" />
- <keyword match="Minute" />
- <keyword match="Month" />
- <keyword match="MonthName" />
- <keyword match="MsgBox" />
- <keyword match="Now" />
- <keyword match="Oct" />
- <keyword match="Replace" />
- <keyword match="RGB" />
- <keyword match="Right" />
- <keyword match="Rnd" />
- <keyword match="Round" />
- <keyword match="ScriptEngine" />
- <keyword match="ScriptEngineBuildVersion" />
- <keyword match="ScriptEngineMajorVersion" />
- <keyword match="ScriptEngineMinorVersion" />
- <keyword match="Second" />
- <keyword match="SetLocale" />
- <keyword match="Sgn" />
- <keyword match="Sin" />
- <keyword match="Space" />
- <keyword match="Split" />
- <keyword match="Sqr" />
- <keyword match="StrComp" />
- <keyword match="String" />
- <keyword match="StrReverse" />
- <keyword match="Tan" />
- <keyword match="Time" />
- <keyword match="Timer" />
- <keyword match="TimeSerial" />
- <keyword match="TimeValue" />
- <keyword match="TypeName" />
- <keyword match="UBound" />
- <keyword match="UCase" />
- <keyword match="Unescape" />
- <keyword match="VarType" />
- <keyword match="Weekday" />
- <keyword match="WeekdayName" />
- <keyword match="Year" />
- </keywords>
-
- <keywords name="builtin" inherits="identifier" innerClass="builtin" case="no">
- <!--<keyword match="Class" />-->
- <keyword match="Debug" />
- <keyword match="Err" />
- <keyword match="Match" />
- <keyword match="RegExp" />
- </keywords>
-
- <keywords name="reserved" inherits="identifier" innerClass="reserved" case="no">
- <keyword match="Empty" />
- <keyword match="False" />
- <keyword match="Nothing" />
- <keyword match="Null" />
- <keyword match="True" />
- <keyword match="And" />
- <keyword match="Eqv" />
- <keyword match="Imp" />
- <keyword match="Is" />
- <keyword match="Mod" />
- <keyword match="Not" />
- <keyword match="Or" />
- <keyword match="Xor" />
- <keyword match="Call" />
- <keyword match="Class" />
- <keyword match="End" />
- <keyword match="Const" />
- <keyword match="Public" />
- <keyword match="Private" />
- <keyword match="Dim" />
- <keyword match="Do" />
- <keyword match="While" />
- <keyword match="Until" />
- <keyword match="Exit" />
- <keyword match="Loop" />
- <keyword match="Erase" />
- <keyword match="Execute" />
- <keyword match="ExecuteGlobal" />
- <keyword match="For" />
- <keyword match="Each" />
- <keyword match="In" />
- <keyword match="To" />
- <keyword match="Step" />
- <keyword match="Next" />
- <keyword match="Function" />
- <keyword match="Default" />
- <keyword match="If" />
- <keyword match="Then" />
- <keyword match="Else" />
- <keyword match="ElseIf" />
- <keyword match="On" />
- <keyword match="Error" />
- <keyword match="Resume" />
- <keyword match="Goto" />
- <keyword match="Option" />
- <keyword match="Explicit" />
- <keyword match="Property" />
- <keyword match="Get" />
- <keyword match="Let" />
- <keyword match="Set" />
- <keyword match="Randomize" />
- <keyword match="ReDim" />
- <keyword match="Preserve" />
- <keyword match="Select" />
- <keyword match="Case" />
- <keyword match="Stop" />
- <keyword match="Sub" />
- <keyword match="Wend" />
- <keyword match="With" />
- </keywords>
-
-</highlight>
diff --git a/library/Text_Highlighter/xml.xml b/library/Text_Highlighter/xml.xml
deleted file mode 100644
index 2271ff3ae..000000000
--- a/library/Text_Highlighter/xml.xml
+++ /dev/null
@@ -1,37 +0,0 @@
-<?xml version="1.0"?>
-<!-- $Id: xml.xml,v 1.1 2007-06-03 02:35:28 ssttoo Exp $ -->
-
-<highlight lang="xml" case="no">
-
- <authors>
- <author name="Andrey Demenev" email="demenev@gmail.com"/>
- </authors>
-
-
- <default innerClass="code" />
-
- <region name="cdata" delimClass="comment" innerClass="comment"
- start="\&lt;\!\[CDATA\[" end="\]\]\&gt;">
- </region>
-
- <region name="comment" delimClass="comment" innerClass="comment"
- start="\&lt;!--" end="--\&gt;">
- </region>
-
- <region name="tag" delimClass="brackets" innerClass="code" start="\&lt;[\?\/]?" end="[\/\?]?\&gt;">
- <contains block="tagname"/>
- <contains region="param"/>
- <contains block="paramname"/>
- </region>
-
- <block name="tagname" match="(?&lt;=[\&lt;\/?])[\w\-\:]+" innerClass="reserved" contained="yes"/>
-
- <block name="paramname" match="[\w\-\:]+" innerClass="var" contained="yes"/>
-
- <block name="entity" match="(&amp;|%)[\w\-\.]+;" innerClass="special" />
-
- <region name="param" start="&quot;" end="&quot;" delimClass="quotes" innerClass="string" contained="yes">
- <contains block="entity"/>
- </region>
-
-</highlight>
diff --git a/library/blueimp_upload/.gitignore b/library/blueimp_upload/.gitignore
deleted file mode 100644
index 29a41a8c4..000000000
--- a/library/blueimp_upload/.gitignore
+++ /dev/null
@@ -1,3 +0,0 @@
-.DS_Store
-*.pyc
-node_modules
diff --git a/library/blueimp_upload/.jshintrc b/library/blueimp_upload/.jshintrc
deleted file mode 100644
index 4ad82e664..000000000
--- a/library/blueimp_upload/.jshintrc
+++ /dev/null
@@ -1,81 +0,0 @@
-{
- "bitwise" : true, // true: Prohibit bitwise operators (&, |, ^, etc.)
- "camelcase" : true, // true: Identifiers must be in camelCase
- "curly" : true, // true: Require {} for every new block or scope
- "eqeqeq" : true, // true: Require triple equals (===) for comparison
- "forin" : true, // true: Require filtering for..in loops with obj.hasOwnProperty()
- "immed" : true, // true: Require immediate invocations to be wrapped in parens
- // e.g. `(function () { } ());`
- "indent" : 4, // {int} Number of spaces to use for indentation
- "latedef" : true, // true: Require variables/functions to be defined before being used
- "newcap" : true, // true: Require capitalization of all constructor functions e.g. `new F()`
- "noarg" : true, // true: Prohibit use of `arguments.caller` and `arguments.callee`
- "noempty" : true, // true: Prohibit use of empty blocks
- "nonew" : true, // true: Prohibit use of constructors for side-effects (without assignment)
- "plusplus" : false, // true: Prohibit use of `++` & `--`
- "quotmark" : "single", // Quotation mark consistency:
- // false : do nothing (default)
- // true : ensure whatever is used is consistent
- // "single" : require single quotes
- // "double" : require double quotes
- "undef" : true, // true: Require all non-global variables to be declared (prevents global leaks)
- "unused" : true, // true: Require all defined variables be used
- "strict" : true, // true: Requires all functions run in ES5 Strict Mode
- "trailing" : true, // true: Prohibit trailing whitespaces
- "maxparams" : false, // {int} Max number of formal params allowed per function
- "maxdepth" : false, // {int} Max depth of nested blocks (within functions)
- "maxstatements" : false, // {int} Max number statements per function
- "maxcomplexity" : false, // {int} Max cyclomatic complexity per function
- "maxlen" : false, // {int} Max number of characters per line
-
- // Relaxing
- "asi" : false, // true: Tolerate Automatic Semicolon Insertion (no semicolons)
- "boss" : false, // true: Tolerate assignments where comparisons would be expected
- "debug" : false, // true: Allow debugger statements e.g. browser breakpoints.
- "eqnull" : false, // true: Tolerate use of `== null`
- "es5" : false, // true: Allow ES5 syntax (ex: getters and setters)
- "esnext" : false, // true: Allow ES.next (ES6) syntax (ex: `const`)
- "moz" : false, // true: Allow Mozilla specific syntax (extends and overrides esnext features)
- // (ex: `for each`, multiple try/catch, function expression…)
- "evil" : false, // true: Tolerate use of `eval` and `new Function()`
- "expr" : false, // true: Tolerate `ExpressionStatement` as Programs
- "funcscope" : false, // true: Tolerate defining variables inside control statements"
- "globalstrict" : false, // true: Allow global "use strict" (also enables 'strict')
- "iterator" : false, // true: Tolerate using the `__iterator__` property
- "lastsemic" : false, // true: Tolerate omitting a semicolon for the last statement of a 1-line block
- "laxbreak" : false, // true: Tolerate possibly unsafe line breakings
- "laxcomma" : false, // true: Tolerate comma-first style coding
- "loopfunc" : false, // true: Tolerate functions being defined in loops
- "multistr" : false, // true: Tolerate multi-line strings
- "proto" : false, // true: Tolerate using the `__proto__` property
- "scripturl" : false, // true: Tolerate script-targeted URLs
- "smarttabs" : false, // true: Tolerate mixed tabs/spaces when used for alignment
- "shadow" : false, // true: Allows re-define variables later in code e.g. `var x=1; x=2;`
- "sub" : false, // true: Tolerate using `[]` notation when it can still be expressed in dot notation
- "supernew" : false, // true: Tolerate `new function () { ... };` and `new Object;`
- "validthis" : false, // true: Tolerate using this in a non-constructor function
-
- // Environments
- "browser" : false, // Web Browser (window, document, etc)
- "couch" : false, // CouchDB
- "devel" : false, // Development/debugging (alert, confirm, etc)
- "dojo" : false, // Dojo Toolkit
- "jquery" : false, // jQuery
- "mootools" : false, // MooTools
- "node" : false, // Node.js
- "nonstandard" : false, // Widely adopted globals (escape, unescape, etc)
- "prototypejs" : false, // Prototype and Scriptaculous
- "rhino" : false, // Rhino
- "worker" : false, // Web Workers
- "wsh" : false, // Windows Scripting Host
- "yui" : false, // Yahoo User Interface
-
- // Legacy
- "nomen" : true, // true: Prohibit dangling `_` in variables
- "onevar" : true, // true: Allow only one `var` statement per function
- "passfail" : false, // true: Stop on first error
- "white" : true, // true: Check against strict whitespace and indentation rules
-
- // Custom Globals
- "globals" : {} // additional predefined global variables
-}
diff --git a/library/blueimp_upload/CONTRIBUTING.md b/library/blueimp_upload/CONTRIBUTING.md
index b8708f8b6..e182f9b37 100644
--- a/library/blueimp_upload/CONTRIBUTING.md
+++ b/library/blueimp_upload/CONTRIBUTING.md
@@ -1,42 +1,15 @@
-# Issue Guidelines
+Please follow these pull request guidelines:
-The issues tracker should only be used for **bugs** or **feature requests**.
-
-Please post **support requests** and **general discussions** about this project to the [support forum](https://groups.google.com/d/forum/jquery-fileupload).
-
-## Bugs
-
-Please follow these guidelines before reporting a bug:
-
-1. **Update to the latest version** &mdash; Check if you can reproduce the issue with the latest version from the `master` branch.
-
-2. **Use the GitHub issue search** &mdash; check if the issue has already been reported. If it has been, please comment on the existing issue.
-
-3. **Isolate the demonstrable problem** &mdash; Try to reproduce the problem with the [Demo](https://blueimp.github.io/jQuery-File-Upload/) or with a reduced test case that includes the least amount of code necessary to reproduce the problem.
-
-4. **Provide a means to reproduce the problem** &mdash; Please provide as much details as possible, e.g. server information, browser and operating system versions, steps to reproduce the problem. If possible, provide a link to your reduced test case, e.g. via [JSFiddle](http://jsfiddle.net/).
-
-
-## Feature requests
-
-Please follow the bug guidelines above for feature requests, i.e. update to the latest version and search for exising issues before posting a new request.
-
-Generally, feature requests might be accepted if the implementation would benefit a broader use case or the project could be considered incomplete without that feature.
-
-If you need help integrating this project into another framework, please post your request to the [support forum](https://groups.google.com/d/forum/jquery-fileupload).
-
-## Pull requests
-
-[Pull requests](https://help.github.com/articles/using-pull-requests) are welcome and the preferred way of accepting code contributions.
+1. Update your fork to the latest upstream version.
-However, if you add a server-side upload handler implementation for another framework, please continue to maintain this version in your own fork without sending a pull request. You are welcome to add a link and possibly documentation about your implementation to the [Wiki](https://github.com/blueimp/jQuery-File-Upload/wiki).
+2. Follow the coding conventions of the original source files (indentation, spaces, brackets layout).
-Please follow these guidelines before sending a pull request:
+3. Code changes must pass JSHint validation with the `.jshintrc` settings of this project.
-1. Update your fork to the latest upstream version.
+4. Code changes must pass the QUnit tests defined in the `test` folder.
-2. Follow the coding conventions of the original repository. Changes to one of the JavaScript source files are required to pass the [JSHint](http://www.jshint.com/) validation tool.
+5. New features should be covered by accompanying QUnit tests.
-3. Keep your commits as atomar as possible, i.e. create a new commit for every single bug fix or feature added.
+6. Keep your commits as atomic as possible, i.e. create a new commit for every single bug fix or feature added.
-4. Always add meaningfull commit messages.
+7. Always add meaningful commit messages.
diff --git a/library/blueimp_upload/Gruntfile.js b/library/blueimp_upload/Gruntfile.js
deleted file mode 100644
index dcdb5d57a..000000000
--- a/library/blueimp_upload/Gruntfile.js
+++ /dev/null
@@ -1,37 +0,0 @@
-/*
- * jQuery File Upload Gruntfile
- * https://github.com/blueimp/jQuery-File-Upload
- *
- * Copyright 2013, Sebastian Tschan
- * https://blueimp.net
- *
- * Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
- */
-
-/*global module */
-
-module.exports = function (grunt) {
- 'use strict';
-
- grunt.initConfig({
- jshint: {
- options: {
- jshintrc: '.jshintrc'
- },
- all: [
- 'Gruntfile.js',
- 'js/cors/*.js',
- 'js/*.js',
- 'server/node/server.js',
- 'test/test.js'
- ]
- }
- });
-
- grunt.loadNpmTasks('grunt-contrib-jshint');
- grunt.loadNpmTasks('grunt-bump-build-git');
- grunt.registerTask('test', ['jshint']);
- grunt.registerTask('default', ['test']);
-
-};
diff --git a/library/blueimp_upload/LICENSE b/library/blueimp_upload/LICENSE
new file mode 100644
index 000000000..0ecca3e8c
--- /dev/null
+++ b/library/blueimp_upload/LICENSE
@@ -0,0 +1,20 @@
+The MIT License (MIT)
+
+Copyright (c) 2017 jQuery-File-Upload Authors
+
+Permission is hereby granted, free of charge, to any person obtaining a copy of
+this software and associated documentation files (the "Software"), to deal in
+the Software without restriction, including without limitation the rights to
+use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
+the Software, and to permit persons to whom the Software is furnished to do so,
+subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in all
+copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
+FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
diff --git a/library/blueimp_upload/README.md b/library/blueimp_upload/README.md
index 3aa33de42..56785b847 100644
--- a/library/blueimp_upload/README.md
+++ b/library/blueimp_upload/README.md
@@ -11,17 +11,6 @@ Supports cross-domain, chunked and resumable file uploads and client-side image
* [How to setup the plugin on your website](https://github.com/blueimp/jQuery-File-Upload/wiki/Setup)
* [How to use only the basic plugin (minimal setup guide).](https://github.com/blueimp/jQuery-File-Upload/wiki/Basic-plugin)
-## Support
-
-* **[Support Forum](https://groups.google.com/d/forum/jquery-fileupload)**
-**Support requests** and **general discussions** about the File Upload plugin can be posted to the official
-[Support Forum](https://groups.google.com/d/forum/jquery-fileupload).
-If your question is not directly related to the File Upload plugin, you might have a better chance to get a reply by posting to [Stack Overflow](http://stackoverflow.com/questions/tagged/blueimp+jquery+file-upload).
-
-* Bugs and Feature requests
-**Bugs** and **Feature requests** can be reported using the [issues tracker](https://github.com/blueimp/jQuery-File-Upload/issues).
-Please read the [issue guidelines](https://github.com/blueimp/jQuery-File-Upload/blob/master/CONTRIBUTING.md) before posting.
-
## Features
* **Multiple file upload:**
Allows to select multiple files at once and upload them simultaneously.
@@ -60,28 +49,18 @@ Please read the [issue guidelines](https://github.com/blueimp/jQuery-File-Upload
### Mandatory requirements
* [jQuery](https://jquery.com/) v. 1.6+
-* [jQuery UI widget factory](https://api.jqueryui.com/jQuery.widget/) v. 1.9+ (included)
-* [jQuery Iframe Transport plugin](https://github.com/blueimp/jQuery-File-Upload/blob/master/js/jquery.iframe-transport.js) (included)
-
-The jQuery UI widget factory is a requirement for the basic File Upload plugin, but very lightweight without any other dependencies from the jQuery UI suite.
-
-The jQuery Iframe Transport is required for [browsers without XHR file upload support](https://github.com/blueimp/jQuery-File-Upload/wiki/Browser-support).
+* [jQuery UI widget factory](https://api.jqueryui.com/jQuery.widget/) v. 1.9+ (included): Required for the basic File Upload plugin, but very lightweight without any other dependencies from the jQuery UI suite.
+* [jQuery Iframe Transport plugin](https://github.com/blueimp/jQuery-File-Upload/blob/master/js/jquery.iframe-transport.js) (included): Required for [browsers without XHR file upload support](https://github.com/blueimp/jQuery-File-Upload/wiki/Browser-support).
### Optional requirements
-* [JavaScript Templates engine](https://github.com/blueimp/JavaScript-Templates) v. 2.5.4+
-* [JavaScript Load Image library](https://github.com/blueimp/JavaScript-Load-Image) v. 1.13.0+
-* [JavaScript Canvas to Blob polyfill](https://github.com/blueimp/JavaScript-Canvas-to-Blob) v. 2.1.1+
-* [blueimp Gallery](https://github.com/blueimp/Gallery) v. 2.15.1+
-* [Bootstrap CSS framework](http://getbootstrap.com/) v. 3.2.0+
+* [JavaScript Templates engine](https://github.com/blueimp/JavaScript-Templates) v. 2.5.4+: Used to render the selected and uploaded files for the Basic Plus UI and jQuery UI versions.
+* [JavaScript Load Image library](https://github.com/blueimp/JavaScript-Load-Image) v. 1.13.0+: Required for the image previews and resizing functionality.
+* [JavaScript Canvas to Blob polyfill](https://github.com/blueimp/JavaScript-Canvas-to-Blob) v. 2.1.1+:Required for the image previews and resizing functionality.
+* [blueimp Gallery](https://github.com/blueimp/Gallery) v. 2.15.1+: Used to display the uploaded images in a lightbox.
+* [Bootstrap](http://getbootstrap.com/) v. 3.2.0+
* [Glyphicons](http://glyphicons.com/)
-The JavaScript Templates engine is used to render the selected and uploaded files for the Basic Plus UI and jQuery UI versions.
-
-The JavaScript Load Image library and JavaScript Canvas to Blob polyfill are required for the image previews and resizing functionality.
-
-The blueimp Gallery is used to display the uploaded images in a lightbox.
-
-The user interface of all versions except the jQuery UI version is built with Twitter's [Bootstrap](http://getbootstrap.com/) framework and icons from [Glyphicons](http://glyphicons.com/).
+The user interface of all versions except the jQuery UI version is built with [Bootstrap](http://getbootstrap.com/) and icons from [Glyphicons](http://glyphicons.com/).
### Cross-domain requirements
[Cross-domain File Uploads](https://github.com/blueimp/jQuery-File-Upload/wiki/Cross-domain-uploads) using the [Iframe Transport plugin](https://github.com/blueimp/jQuery-File-Upload/blob/master/js/jquery.iframe-transport.js) require a redirect back to the origin server to retrieve the upload results. The [example implementation](https://github.com/blueimp/jQuery-File-Upload/blob/master/js/main.js) makes use of [result.html](https://github.com/blueimp/jQuery-File-Upload/blob/master/cors/result.html) as a static redirect page for the origin server.
@@ -89,6 +68,10 @@ The user interface of all versions except the jQuery UI version is built with Tw
The repository also includes the [jQuery XDomainRequest Transport plugin](https://github.com/blueimp/jQuery-File-Upload/blob/master/js/cors/jquery.xdr-transport.js), which enables limited cross-domain AJAX requests in Microsoft Internet Explorer 8 and 9 (IE 10 supports cross-domain XHR requests).
The XDomainRequest object allows GET and POST requests only and doesn't support file uploads. It is used on the [Demo](https://blueimp.github.io/jQuery-File-Upload/) to delete uploaded files from the cross-domain demo file upload service.
+### Custom Backends
+
+You can add support for various backends by adhering to the specification [outlined here](https://github.com/blueimp/jQuery-File-Upload/wiki/JSON-Response).
+
## Browsers
### Desktop browsers
@@ -110,14 +93,15 @@ The File Upload plugin has been tested with and supports the following mobile br
* Opera Mobile 12.0+
### Supported features
-For a detailed overview of the features supported by each browser version please have a look at the [Extended browser support information](https://github.com/blueimp/jQuery-File-Upload/wiki/Browser-support).
+For a detailed overview of the features supported by each browser version, please have a look at the [Extended browser support information](https://github.com/blueimp/jQuery-File-Upload/wiki/Browser-support).
-## License
-Released under the [MIT license](http://www.opensource.org/licenses/MIT).
+## Contributing
+**Bug fixes** and **new features** can be proposed using [pull requests](https://github.com/blueimp/jQuery-File-Upload/pulls).
+Please read the [contribution guidelines](https://github.com/blueimp/jQuery-File-Upload/blob/master/CONTRIBUTING.md) before submitting a pull request.
-## Donations
-jQuery File Upload is free software, but you can donate to support the developer, Sebastian Tschan:
-
-Flattr: [![Flattr](https://api.flattr.com/button/flattr-badge-large.png)](https://flattr.com/thing/286433/jQuery-File-Upload-Plugin)
+## Support
+This project is actively maintained, but there is no official support channel.
+If you have a question that another developer might help you with, please post to [Stack Overflow](http://stackoverflow.com/questions/tagged/blueimp+jquery+file-upload) and tag your question with `blueimp jquery file upload`.
-PayPal: [![PayPal](https://www.paypalobjects.com/WEBSCR-640-20110429-1/en_US/i/btn/btn_donateCC_LG.gif)](https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&hosted_button_id=PYWYSYP77KL54)
+## License
+Released under the [MIT license](https://opensource.org/licenses/MIT).
diff --git a/library/blueimp_upload/angularjs.html b/library/blueimp_upload/angularjs.html
index 2a3ca2007..4858c8600 100644
--- a/library/blueimp_upload/angularjs.html
+++ b/library/blueimp_upload/angularjs.html
@@ -1,14 +1,14 @@
<!DOCTYPE HTML>
<!--
/*
- * jQuery File Upload Plugin AngularJS Demo 2.2.0
+ * jQuery File Upload Plugin AngularJS Demo
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2013, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
-->
<html lang="en">
@@ -157,9 +157,9 @@
</div>
<div class="panel-body">
<ul>
- <li>The maximum file size for uploads in this demo is <strong>5 MB</strong> (default file size is unlimited).</li>
+ <li>The maximum file size for uploads in this demo is <strong>999 KB</strong> (default file size is unlimited).</li>
<li>Only image files (<strong>JPG, GIF, PNG</strong>) are allowed in this demo (by default there is no file type restriction).</li>
- <li>Uploaded files will be deleted automatically after <strong>5 minutes</strong> (demo setting).</li>
+ <li>Uploaded files will be deleted automatically after <strong>5 minutes or less</strong> (demo files are stored in memory).</li>
<li>You can <strong>drag &amp; drop</strong> files from your desktop on this webpage (see <a href="https://github.com/blueimp/jQuery-File-Upload/wiki/Browser-support">Browser support</a>).</li>
<li>Please refer to the <a href="https://github.com/blueimp/jQuery-File-Upload">project website</a> and <a href="https://github.com/blueimp/jQuery-File-Upload/wiki">documentation</a> for more information.</li>
<li>Built with the <a href="http://getbootstrap.com/">Bootstrap</a> CSS framework and Icons from <a href="http://glyphicons.com/">Glyphicons</a>.</li>
@@ -177,8 +177,8 @@
<a class="play-pause"></a>
<ol class="indicator"></ol>
</div>
-<script src="//ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
-<script src="//ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
+<script src="//ajax.googleapis.com/ajax/libs/jquery/1.11.3/jquery.min.js"></script>
+<script src="//ajax.googleapis.com/ajax/libs/angularjs/1.3.15/angular.min.js"></script>
<!-- The jQuery UI widget factory, can be omitted if jQuery UI is already included -->
<script src="js/vendor/jquery.ui.widget.js"></script>
<!-- The Load Image plugin is included for the preview images and image resizing functionality -->
@@ -207,5 +207,5 @@
<script src="js/jquery.fileupload-angular.js"></script>
<!-- The main application script -->
<script src="js/app.js"></script>
-</body>
+</body>
</html>
diff --git a/library/blueimp_upload/basic-plus.html b/library/blueimp_upload/basic-plus.html
index 59b73b60c..9e5c2321f 100644
--- a/library/blueimp_upload/basic-plus.html
+++ b/library/blueimp_upload/basic-plus.html
@@ -1,14 +1,14 @@
<!DOCTYPE HTML>
<!--
/*
- * jQuery File Upload Plugin Basic Plus Demo 1.4.0
+ * jQuery File Upload Plugin Basic Plus Demo
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2013, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
-->
<html lang="en">
@@ -86,9 +86,9 @@
</div>
<div class="panel-body">
<ul>
- <li>The maximum file size for uploads in this demo is <strong>5 MB</strong> (default file size is unlimited).</li>
+ <li>The maximum file size for uploads in this demo is <strong>999 KB</strong> (default file size is unlimited).</li>
<li>Only image files (<strong>JPG, GIF, PNG</strong>) are allowed in this demo (by default there is no file type restriction).</li>
- <li>Uploaded files will be deleted automatically after <strong>5 minutes</strong> (demo setting).</li>
+ <li>Uploaded files will be deleted automatically after <strong>5 minutes or less</strong> (demo files are stored in memory).</li>
<li>You can <strong>drag &amp; drop</strong> files from your desktop on this webpage (see <a href="https://github.com/blueimp/jQuery-File-Upload/wiki/Browser-support">Browser support</a>).</li>
<li>Please refer to the <a href="https://github.com/blueimp/jQuery-File-Upload">project website</a> and <a href="https://github.com/blueimp/jQuery-File-Upload/wiki">documentation</a> for more information.</li>
<li>Built with the <a href="http://getbootstrap.com/">Bootstrap</a> CSS framework and Icons from <a href="http://glyphicons.com/">Glyphicons</a>.</li>
@@ -96,7 +96,7 @@
</div>
</div>
</div>
-<script src="//ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
+<script src="//ajax.googleapis.com/ajax/libs/jquery/1.11.3/jquery.min.js"></script>
<!-- The jQuery UI widget factory, can be omitted if jQuery UI is already included -->
<script src="js/vendor/jquery.ui.widget.js"></script>
<!-- The Load Image plugin is included for the preview images and image resizing functionality -->
@@ -150,7 +150,7 @@ $(function () {
dataType: 'json',
autoUpload: false,
acceptFileTypes: /(\.|\/)(gif|jpe?g|png)$/i,
- maxFileSize: 5000000, // 5 MB
+ maxFileSize: 999000,
// Enable image resizing, except for Android and Opera,
// which actually support image resizing, but fail to
// send Blob objects via XHR requests:
@@ -222,5 +222,5 @@ $(function () {
.parent().addClass($.support.fileInput ? undefined : 'disabled');
});
</script>
-</body>
+</body>
</html>
diff --git a/library/blueimp_upload/basic.html b/library/blueimp_upload/basic.html
index f248f4d80..c0df639b4 100644
--- a/library/blueimp_upload/basic.html
+++ b/library/blueimp_upload/basic.html
@@ -1,14 +1,14 @@
<!DOCTYPE HTML>
<!--
/*
- * jQuery File Upload Plugin Basic Demo 1.3.0
+ * jQuery File Upload Plugin Basic Demo
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2013, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
-->
<html lang="en">
@@ -86,17 +86,17 @@
</div>
<div class="panel-body">
<ul>
- <li>The maximum file size for uploads in this demo is <strong>5 MB</strong> (default file size is unlimited).</li>
+ <li>The maximum file size for uploads in this demo is <strong>999 KB</strong> (default file size is unlimited).</li>
<li>Only image files (<strong>JPG, GIF, PNG</strong>) are allowed in this demo (by default there is no file type restriction).</li>
- <li>Uploaded files will be deleted automatically after <strong>5 minutes</strong> (demo setting).</li>
+ <li>Uploaded files will be deleted automatically after <strong>5 minutes or less</strong> (demo files are stored in memory).</li>
<li>You can <strong>drag &amp; drop</strong> files from your desktop on this webpage (see <a href="https://github.com/blueimp/jQuery-File-Upload/wiki/Browser-support">Browser support</a>).</li>
<li>Please refer to the <a href="https://github.com/blueimp/jQuery-File-Upload">project website</a> and <a href="https://github.com/blueimp/jQuery-File-Upload/wiki">documentation</a> for more information.</li>
- <li>Built with Twitter's <a href="http://twitter.github.com/bootstrap/">Bootstrap</a> CSS framework and Icons from <a href="http://glyphicons.com/">Glyphicons</a>.</li>
+ <li>Built with the <a href="http://getbootstrap.com/">Bootstrap</a> CSS framework and Icons from <a href="http://glyphicons.com/">Glyphicons</a>.</li>
</ul>
</div>
</div>
</div>
-<script src="//ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
+<script src="//ajax.googleapis.com/ajax/libs/jquery/1.11.3/jquery.min.js"></script>
<!-- The jQuery UI widget factory, can be omitted if jQuery UI is already included -->
<script src="js/vendor/jquery.ui.widget.js"></script>
<!-- The Iframe Transport is required for browsers without support for XHR file uploads -->
@@ -132,5 +132,5 @@ $(function () {
.parent().addClass($.support.fileInput ? undefined : 'disabled');
});
</script>
-</body>
+</body>
</html>
diff --git a/library/blueimp_upload/blueimp-file-upload.jquery.json b/library/blueimp_upload/blueimp-file-upload.jquery.json
deleted file mode 100644
index d6d8c911c..000000000
--- a/library/blueimp_upload/blueimp-file-upload.jquery.json
+++ /dev/null
@@ -1,50 +0,0 @@
-{
- "name": "blueimp-file-upload",
- "version": "9.8.0",
- "title": "jQuery File Upload",
- "author": {
- "name": "Sebastian Tschan",
- "url": "https://blueimp.net"
- },
- "licenses": [
- {
- "type": "MIT",
- "url": "http://www.opensource.org/licenses/MIT"
- }
- ],
- "dependencies": {
- "jquery": ">=1.6"
- },
- "description": "File Upload widget with multiple file selection, drag&amp;drop support, progress bar, validation and preview images, audio and video for jQuery. Supports cross-domain, chunked and resumable file uploads. Works with any server-side platform (Google App Engine, PHP, Python, Ruby on Rails, Java, etc.) that supports standard HTML form file uploads.",
- "keywords": [
- "jquery",
- "file",
- "upload",
- "widget",
- "multiple",
- "selection",
- "drag",
- "drop",
- "progress",
- "preview",
- "cross-domain",
- "cross-site",
- "chunk",
- "resume",
- "gae",
- "go",
- "python",
- "php",
- "bootstrap"
- ],
- "homepage": "https://github.com/blueimp/jQuery-File-Upload",
- "docs": "https://github.com/blueimp/jQuery-File-Upload/wiki",
- "demo": "https://blueimp.github.io/jQuery-File-Upload/",
- "bugs": "https://github.com/blueimp/jQuery-File-Upload/issues",
- "maintainers": [
- {
- "name": "Sebastian Tschan",
- "url": "https://blueimp.net"
- }
- ]
-}
diff --git a/library/blueimp_upload/bower-version-update.js b/library/blueimp_upload/bower-version-update.js
new file mode 100755
index 000000000..09ce3927e
--- /dev/null
+++ b/library/blueimp_upload/bower-version-update.js
@@ -0,0 +1,16 @@
+#!/usr/bin/env node
+
+'use strict';
+
+var path = require('path');
+var packageJSON = require(path.join(__dirname, 'package.json'));
+var bowerFile = path.join(__dirname, 'bower.json');
+var bowerJSON = require('bower-json').parse(
+ require(bowerFile),
+ {normalize: true}
+);
+bowerJSON.version = packageJSON.version;
+require('fs').writeFileSync(
+ bowerFile,
+ JSON.stringify(bowerJSON, null, 2) + '\n'
+);
diff --git a/library/blueimp_upload/bower.json b/library/blueimp_upload/bower.json
index c0d3d3259..90c74c792 100644
--- a/library/blueimp_upload/bower.json
+++ b/library/blueimp_upload/bower.json
@@ -1,8 +1,8 @@
{
"name": "blueimp-file-upload",
- "version": "9.8.0",
+ "version": "9.18.0",
"title": "jQuery File Upload",
- "description": "File Upload widget with multiple file selection, drag&amp;drop support, progress bar, validation and preview images, audio and video for jQuery. Supports cross-domain, chunked and resumable file uploads. Works with any server-side platform (Google App Engine, PHP, Python, Ruby on Rails, Java, etc.) that supports standard HTML form file uploads.",
+ "description": "File Upload widget with multiple file selection, drag&amp;drop support, progress bar, validation and preview images.",
"keywords": [
"jquery",
"file",
@@ -40,12 +40,7 @@
"url": "git://github.com/blueimp/jQuery-File-Upload.git"
},
"bugs": "https://github.com/blueimp/jQuery-File-Upload/issues",
- "licenses": [
- {
- "type": "MIT",
- "url": "http://www.opensource.org/licenses/MIT"
- }
- ],
+ "license": "MIT",
"dependencies": {
"jquery": ">=1.6",
"blueimp-tmpl": ">=2.5.4",
@@ -53,23 +48,7 @@
"blueimp-canvas-to-blob": ">=2.1.1"
},
"main": [
- "css/jquery.fileupload.css",
- "css/jquery.fileupload-ui.css",
- "css/jquery.fileupload-noscript.css",
- "css/jquery.fileupload-ui-noscript.css",
- "js/cors/jquery.postmessage-transport.js",
- "js/cors/jquery.xdr-transport.js",
- "js/vendor/jquery.ui.widget.js",
- "js/jquery.fileupload.js",
- "js/jquery.fileupload-process.js",
- "js/jquery.fileupload-validate.js",
- "js/jquery.fileupload-image.js",
- "js/jquery.fileupload-audio.js",
- "js/jquery.fileupload-video.js",
- "js/jquery.fileupload-ui.js",
- "js/jquery.fileupload-jquery-ui.js",
- "js/jquery.fileupload-angular.js",
- "js/jquery.iframe-transport.js"
+ "js/jquery.fileupload.js"
],
"ignore": [
"/*.*",
diff --git a/library/blueimp_upload/cors/postmessage.html b/library/blueimp_upload/cors/postmessage.html
index 3d1448f08..6db288cf9 100644
--- a/library/blueimp_upload/cors/postmessage.html
+++ b/library/blueimp_upload/cors/postmessage.html
@@ -1,14 +1,14 @@
<!DOCTYPE HTML>
<!--
/*
- * jQuery File Upload Plugin postMessage API 1.2.1
+ * jQuery File Upload Plugin postMessage API
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2011, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
-->
<html lang="en">
@@ -72,4 +72,4 @@ $(window).on('message', function (e) {
});
</script>
</body>
-</html> \ No newline at end of file
+</html>
diff --git a/library/blueimp_upload/cors/result.html b/library/blueimp_upload/cors/result.html
index 225131495..e3d629814 100644
--- a/library/blueimp_upload/cors/result.html
+++ b/library/blueimp_upload/cors/result.html
@@ -1,14 +1,14 @@
<!DOCTYPE HTML>
<!--
/*
- * jQuery Iframe Transport Plugin Redirect Page 2.0.1
+ * jQuery Iframe Transport Plugin Redirect Page
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2010, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
-->
<html lang="en">
diff --git a/library/blueimp_upload/css/demo-ie8.css b/library/blueimp_upload/css/demo-ie8.css
index 262493d08..e0e8ea9b0 100644
--- a/library/blueimp_upload/css/demo-ie8.css
+++ b/library/blueimp_upload/css/demo-ie8.css
@@ -1,13 +1,13 @@
@charset "UTF-8";
/*
- * jQuery File Upload Demo CSS Fixes for IE<9 1.0.0
+ * jQuery File Upload Demo CSS Fixes for IE<9
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2013, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
.navigation {
diff --git a/library/blueimp_upload/css/demo.css b/library/blueimp_upload/css/demo.css
index 2b4d43934..d7d524df5 100644
--- a/library/blueimp_upload/css/demo.css
+++ b/library/blueimp_upload/css/demo.css
@@ -1,13 +1,13 @@
@charset "UTF-8";
/*
- * jQuery File Upload Demo CSS 1.1.0
+ * jQuery File Upload Demo CSS
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2013, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
body {
diff --git a/library/blueimp_upload/css/jquery.fileupload-noscript.css b/library/blueimp_upload/css/jquery.fileupload-noscript.css
index 64d728fc3..2409bfb0a 100644
--- a/library/blueimp_upload/css/jquery.fileupload-noscript.css
+++ b/library/blueimp_upload/css/jquery.fileupload-noscript.css
@@ -1,20 +1,20 @@
@charset "UTF-8";
/*
- * jQuery File Upload Plugin NoScript CSS 1.2.0
+ * jQuery File Upload Plugin NoScript CSS
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2013, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
.fileinput-button input {
position: static;
opacity: 1;
filter: none;
- font-size: inherit;
+ font-size: inherit !important;
direction: inherit;
}
.fileinput-button span {
diff --git a/library/blueimp_upload/css/jquery.fileupload-ui-noscript.css b/library/blueimp_upload/css/jquery.fileupload-ui-noscript.css
index 87f110cdb..30651acf0 100644
--- a/library/blueimp_upload/css/jquery.fileupload-ui-noscript.css
+++ b/library/blueimp_upload/css/jquery.fileupload-ui-noscript.css
@@ -1,13 +1,13 @@
@charset "UTF-8";
/*
- * jQuery File Upload UI Plugin NoScript CSS 8.8.5
+ * jQuery File Upload UI Plugin NoScript CSS
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2012, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
.fileinput-button i,
diff --git a/library/blueimp_upload/css/jquery.fileupload-ui.css b/library/blueimp_upload/css/jquery.fileupload-ui.css
index 76fb376de..9e36c42c5 100644
--- a/library/blueimp_upload/css/jquery.fileupload-ui.css
+++ b/library/blueimp_upload/css/jquery.fileupload-ui.css
@@ -1,13 +1,13 @@
@charset "UTF-8";
/*
- * jQuery File Upload UI Plugin CSS 9.0.0
+ * jQuery File Upload UI Plugin CSS
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2010, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
.fileupload-buttonbar .btn,
diff --git a/library/blueimp_upload/css/jquery.fileupload.css b/library/blueimp_upload/css/jquery.fileupload.css
index fb6044d34..8ae3b09d4 100644
--- a/library/blueimp_upload/css/jquery.fileupload.css
+++ b/library/blueimp_upload/css/jquery.fileupload.css
@@ -1,18 +1,19 @@
@charset "UTF-8";
/*
- * jQuery File Upload Plugin CSS 1.3.0
+ * jQuery File Upload Plugin CSS
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2013, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
.fileinput-button {
position: relative;
overflow: hidden;
+ display: inline-block;
}
.fileinput-button input {
position: absolute;
@@ -21,7 +22,7 @@
margin: 0;
opacity: 0;
-ms-filter: 'alpha(opacity=0)';
- font-size: 200px;
+ font-size: 200px !important;
direction: ltr;
cursor: pointer;
}
diff --git a/library/blueimp_upload/css/style.css b/library/blueimp_upload/css/style.css
index b2c60a6f1..3aee25689 100644
--- a/library/blueimp_upload/css/style.css
+++ b/library/blueimp_upload/css/style.css
@@ -1,13 +1,13 @@
@charset "UTF-8";
/*
- * jQuery File Upload Plugin CSS Example 8.8.2
+ * jQuery File Upload Plugin CSS Example
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2013, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
body {
diff --git a/library/blueimp_upload/index.html b/library/blueimp_upload/index.html
index f92f04aab..2a8dc1521 100644
--- a/library/blueimp_upload/index.html
+++ b/library/blueimp_upload/index.html
@@ -1,14 +1,14 @@
<!DOCTYPE HTML>
<!--
/*
- * jQuery File Upload Plugin Demo 9.1.0
+ * jQuery File Upload Plugin Demo
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2010, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
-->
<html lang="en">
@@ -121,9 +121,9 @@
</div>
<div class="panel-body">
<ul>
- <li>The maximum file size for uploads in this demo is <strong>5 MB</strong> (default file size is unlimited).</li>
+ <li>The maximum file size for uploads in this demo is <strong>999 KB</strong> (default file size is unlimited).</li>
<li>Only image files (<strong>JPG, GIF, PNG</strong>) are allowed in this demo (by default there is no file type restriction).</li>
- <li>Uploaded files will be deleted automatically after <strong>5 minutes</strong> (demo setting).</li>
+ <li>Uploaded files will be deleted automatically after <strong>5 minutes or less</strong> (demo files are stored in memory).</li>
<li>You can <strong>drag &amp; drop</strong> files from your desktop on this webpage (see <a href="https://github.com/blueimp/jQuery-File-Upload/wiki/Browser-support">Browser support</a>).</li>
<li>Please refer to the <a href="https://github.com/blueimp/jQuery-File-Upload">project website</a> and <a href="https://github.com/blueimp/jQuery-File-Upload/wiki">documentation</a> for more information.</li>
<li>Built with the <a href="http://getbootstrap.com/">Bootstrap</a> CSS framework and Icons from <a href="http://glyphicons.com/">Glyphicons</a>.</li>
@@ -216,7 +216,7 @@
</tr>
{% } %}
</script>
-<script src="//ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
+<script src="//ajax.googleapis.com/ajax/libs/jquery/1.11.3/jquery.min.js"></script>
<!-- The jQuery UI widget factory, can be omitted if jQuery UI is already included -->
<script src="js/vendor/jquery.ui.widget.js"></script>
<!-- The Templates plugin is included to render the upload/download listings -->
@@ -251,5 +251,5 @@
<!--[if (gte IE 8)&(lt IE 10)]>
<script src="js/cors/jquery.xdr-transport.js"></script>
<![endif]-->
-</body>
+</body>
</html>
diff --git a/library/blueimp_upload/jquery-ui.html b/library/blueimp_upload/jquery-ui.html
index d61ee5233..83fe9acd1 100644
--- a/library/blueimp_upload/jquery-ui.html
+++ b/library/blueimp_upload/jquery-ui.html
@@ -1,14 +1,14 @@
<!DOCTYPE HTML>
<!--
/*
- * jQuery File Upload Plugin jQuery UI Demo 9.1.0
+ * jQuery File Upload Plugin jQuery UI Demo
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2013, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
-->
<html lang="en">
@@ -127,9 +127,9 @@
<br>
<h3>Demo Notes</h3>
<ul>
- <li>The maximum file size for uploads in this demo is <strong>5 MB</strong> (default file size is unlimited).</li>
+ <li>The maximum file size for uploads in this demo is <strong>999 KB</strong> (default file size is unlimited).</li>
<li>Only image files (<strong>JPG, GIF, PNG</strong>) are allowed in this demo (by default there is no file type restriction).</li>
- <li>Uploaded files will be deleted automatically after <strong>5 minutes</strong> (demo setting).</li>
+ <li>Uploaded files will be deleted automatically after <strong>5 minutes or less</strong> (demo files are stored in memory).</li>
<li>You can <strong>drag &amp; drop</strong> files from your desktop on this webpage (see <a href="https://github.com/blueimp/jQuery-File-Upload/wiki/Browser-support">Browser support</a>).</li>
<li>Please refer to the <a href="https://github.com/blueimp/jQuery-File-Upload">project website</a> and <a href="https://github.com/blueimp/jQuery-File-Upload/wiki">documentation</a> for more information.</li>
<li>Built with <a href="https://jqueryui.com">jQuery UI</a>.</li>
@@ -199,8 +199,8 @@
</tr>
{% } %}
</script>
-<script src="//ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
-<script src="//ajax.googleapis.com/ajax/libs/jqueryui/1.11.1/jquery-ui.min.js"></script>
+<script src="//ajax.googleapis.com/ajax/libs/jquery/1.11.3/jquery.min.js"></script>
+<script src="//ajax.googleapis.com/ajax/libs/jqueryui/1.11.4/jquery-ui.min.js"></script>
<!-- The Templates plugin is included to render the upload/download listings -->
<script src="//blueimp.github.io/JavaScript-Templates/js/tmpl.min.js"></script>
<!-- The Load Image plugin is included for the preview images and image resizing functionality -->
@@ -246,5 +246,5 @@ $('#theme-switcher').change(function () {
<!--[if (gte IE 8)&(lt IE 10)]>
<script src="js/cors/jquery.xdr-transport.js"></script>
<![endif]-->
-</body>
+</body>
</html>
diff --git a/library/blueimp_upload/js/app.js b/library/blueimp_upload/js/app.js
index 47b4f923b..e6b7bce3e 100644
--- a/library/blueimp_upload/js/app.js
+++ b/library/blueimp_upload/js/app.js
@@ -1,18 +1,18 @@
/*
- * jQuery File Upload Plugin Angular JS Example 1.2.1
+ * jQuery File Upload Plugin Angular JS Example
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2013, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
/* jshint nomen:false */
/* global window, angular */
-(function () {
+;(function () {
'use strict';
var isOnGitHub = window.location.hostname === 'blueimp.github.io',
@@ -37,7 +37,7 @@
// send Blob objects via XHR requests:
disableImageResize: /Android(?!.*Chrome)|Opera/
.test(window.navigator.userAgent),
- maxFileSize: 5000000,
+ maxFileSize: 999000,
acceptFileTypes: /(\.|\/)(gif|jpe?g|png)$/i
});
}
diff --git a/library/blueimp_upload/js/cors/jquery.postmessage-transport.js b/library/blueimp_upload/js/cors/jquery.postmessage-transport.js
index 2b4851e67..2a0c38cb6 100644
--- a/library/blueimp_upload/js/cors/jquery.postmessage-transport.js
+++ b/library/blueimp_upload/js/cors/jquery.postmessage-transport.js
@@ -1,21 +1,24 @@
/*
- * jQuery postMessage Transport Plugin 1.1.1
+ * jQuery postMessage Transport Plugin
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2011, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
-/* global define, window, document */
+/* global define, require, window, document */
-(function (factory) {
+;(function (factory) {
'use strict';
if (typeof define === 'function' && define.amd) {
// Register as an anonymous AMD module:
define(['jquery'], factory);
+ } else if (typeof exports === 'object') {
+ // Node/CommonJS:
+ factory(require('jquery'));
} else {
// Browser globals:
factory(window.jQuery);
@@ -61,6 +64,12 @@
loc = $('<a>').prop('href', options.postMessage)[0],
target = loc.protocol + '//' + loc.host,
xhrUpload = options.xhr().upload;
+ // IE always includes the port for the host property of a link
+ // element, but not in the location.host or origin property for the
+ // default http port 80 and https port 443, so we strip it:
+ if (/^(http:\/\/.+:80)|(https:\/\/.+:443)$/.test(target)) {
+ target = target.replace(/:(80|443)$/, '');
+ }
return {
send: function (_, completeCallback) {
counter += 1;
diff --git a/library/blueimp_upload/js/cors/jquery.xdr-transport.js b/library/blueimp_upload/js/cors/jquery.xdr-transport.js
index 0044cc2d5..a4e2699c6 100644
--- a/library/blueimp_upload/js/cors/jquery.xdr-transport.js
+++ b/library/blueimp_upload/js/cors/jquery.xdr-transport.js
@@ -1,24 +1,27 @@
/*
- * jQuery XDomainRequest Transport Plugin 1.1.3
+ * jQuery XDomainRequest Transport Plugin
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2011, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*
* Based on Julian Aubourg's ajaxHooks xdr.js:
* https://github.com/jaubourg/ajaxHooks/
*/
-/* global define, window, XDomainRequest */
+/* global define, require, window, XDomainRequest */
-(function (factory) {
+;(function (factory) {
'use strict';
if (typeof define === 'function' && define.amd) {
// Register as an anonymous AMD module:
define(['jquery'], factory);
+ } else if (typeof exports === 'object') {
+ // Node/CommonJS:
+ factory(require('jquery'));
} else {
// Browser globals:
factory(window.jQuery);
diff --git a/library/blueimp_upload/js/jquery.fileupload-angular.js b/library/blueimp_upload/js/jquery.fileupload-angular.js
index e4ef3926b..1c2055276 100644
--- a/library/blueimp_upload/js/jquery.fileupload-angular.js
+++ b/library/blueimp_upload/js/jquery.fileupload-angular.js
@@ -1,18 +1,18 @@
/*
- * jQuery File Upload AngularJS Plugin 2.2.0
+ * jQuery File Upload AngularJS Plugin
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2013, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
/* jshint nomen:false */
-/* global define, angular */
+/* global define, angular, require */
-(function (factory) {
+;(function (factory) {
'use strict';
if (typeof define === 'function' && define.amd) {
// Register as an anonymous AMD module:
@@ -24,6 +24,16 @@
'./jquery.fileupload-video',
'./jquery.fileupload-validate'
], factory);
+ } else if (typeof exports === 'object') {
+ // Node/CommonJS:
+ factory(
+ require('jquery'),
+ require('angular'),
+ require('./jquery.fileupload-image'),
+ require('./jquery.fileupload-audio'),
+ require('./jquery.fileupload-video'),
+ require('./jquery.fileupload-validate')
+ );
} else {
factory();
}
@@ -91,7 +101,7 @@
angular.forEach(data.files, function (file) {
filesCopy.push(file);
});
- scope.$apply(function () {
+ scope.$parent.$applyAsync(function () {
addFileMethods(scope, data);
var method = scope.option('prependFiles') ?
'unshift' : 'push';
@@ -100,7 +110,7 @@
data.process(function () {
return scope.process(data);
}).always(function () {
- scope.$apply(function () {
+ scope.$parent.$applyAsync(function () {
addFileMethods(scope, data);
scope.replace(filesCopy, data.files);
});
@@ -112,12 +122,6 @@
}
});
},
- progress: function (e, data) {
- if (e.isDefaultPrevented()) {
- return false;
- }
- data.scope.$apply();
- },
done: function (e, data) {
if (e.isDefaultPrevented()) {
return false;
@@ -197,8 +201,8 @@
// The FileUploadController initializes the fileupload widget and
// provides scope methods to control the File Upload functionality:
.controller('FileUploadController', [
- '$scope', '$element', '$attrs', '$window', 'fileUpload',
- function ($scope, $element, $attrs, $window, fileUpload) {
+ '$scope', '$element', '$attrs', '$window', 'fileUpload','$q',
+ function ($scope, $element, $attrs, $window, fileUpload, $q) {
var uploadMethods = {
progress: function () {
return $element.fileupload('progress');
@@ -260,19 +264,21 @@
$scope.applyOnQueue = function (method) {
var list = this.queue.slice(0),
i,
- file;
+ file,
+ promises = [];
for (i = 0; i < list.length; i += 1) {
file = list[i];
if (file[method]) {
- file[method]();
+ promises.push(file[method]());
}
}
+ return $q.all(promises);
};
$scope.submit = function () {
- this.applyOnQueue('$submit');
+ return this.applyOnQueue('$submit');
};
$scope.cancel = function () {
- this.applyOnQueue('$cancel');
+ return this.applyOnQueue('$cancel');
};
// Add upload methods to the scope:
angular.extend($scope, uploadMethods);
@@ -320,9 +326,11 @@
'fileuploadprocessalways',
'fileuploadprocessstop'
].join(' '), function (e, data) {
- if ($scope.$emit(e.type, data).defaultPrevented) {
- e.preventDefault();
- }
+ $scope.$parent.$applyAsync(function () {
+ if ($scope.$emit(e.type, data).defaultPrevented) {
+ e.preventDefault();
+ }
+ });
}).on('remove', function () {
// Remove upload methods from the scope,
// when the widget is removed:
diff --git a/library/blueimp_upload/js/jquery.fileupload-audio.js b/library/blueimp_upload/js/jquery.fileupload-audio.js
index 575800e82..a25377619 100644
--- a/library/blueimp_upload/js/jquery.fileupload-audio.js
+++ b/library/blueimp_upload/js/jquery.fileupload-audio.js
@@ -1,18 +1,18 @@
/*
- * jQuery File Upload Audio Preview Plugin 1.0.3
+ * jQuery File Upload Audio Preview Plugin
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2013, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
/* jshint nomen:false */
-/* global define, window, document */
+/* global define, require, window, document */
-(function (factory) {
+;(function (factory) {
'use strict';
if (typeof define === 'function' && define.amd) {
// Register as an anonymous AMD module:
@@ -21,6 +21,13 @@
'load-image',
'./jquery.fileupload-process'
], factory);
+ } else if (typeof exports === 'object') {
+ // Node/CommonJS:
+ factory(
+ require('jquery'),
+ require('blueimp-load-image/js/load-image'),
+ require('./jquery.fileupload-process')
+ );
} else {
// Browser globals:
factory(
diff --git a/library/blueimp_upload/js/jquery.fileupload-image.js b/library/blueimp_upload/js/jquery.fileupload-image.js
index 5bb7026ae..65fc6d7b8 100644
--- a/library/blueimp_upload/js/jquery.fileupload-image.js
+++ b/library/blueimp_upload/js/jquery.fileupload-image.js
@@ -1,18 +1,18 @@
/*
- * jQuery File Upload Image Preview & Resize Plugin 1.7.2
+ * jQuery File Upload Image Preview & Resize Plugin
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2013, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
/* jshint nomen:false */
-/* global define, window, Blob */
+/* global define, require, window, Blob */
-(function (factory) {
+;(function (factory) {
'use strict';
if (typeof define === 'function' && define.amd) {
// Register as an anonymous AMD module:
@@ -20,11 +20,22 @@
'jquery',
'load-image',
'load-image-meta',
+ 'load-image-scale',
'load-image-exif',
- 'load-image-ios',
'canvas-to-blob',
'./jquery.fileupload-process'
], factory);
+ } else if (typeof exports === 'object') {
+ // Node/CommonJS:
+ factory(
+ require('jquery'),
+ require('blueimp-load-image/js/load-image'),
+ require('blueimp-load-image/js/load-image-meta'),
+ require('blueimp-load-image/js/load-image-scale'),
+ require('blueimp-load-image/js/load-image-exif'),
+ require('blueimp-canvas-to-blob'),
+ require('./jquery.fileupload-process')
+ );
} else {
// Browser globals:
factory(
@@ -236,7 +247,7 @@
blob.name = file.name;
} else if (file.name) {
blob.name = file.name.replace(
- /\..+$/,
+ /\.\w+$/,
'.' + blob.type.substr(6)
);
}
diff --git a/library/blueimp_upload/js/jquery.fileupload-jquery-ui.js b/library/blueimp_upload/js/jquery.fileupload-jquery-ui.js
index af0a00b1e..7b136b379 100755..100644
--- a/library/blueimp_upload/js/jquery.fileupload-jquery-ui.js
+++ b/library/blueimp_upload/js/jquery.fileupload-jquery-ui.js
@@ -1,22 +1,31 @@
/*
- * jQuery File Upload jQuery UI Plugin 8.7.1
+ * jQuery File Upload jQuery UI Plugin
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2013, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
/* jshint nomen:false */
-/* global define, window */
+/* global define, require, window */
-(function (factory) {
+;(function (factory) {
'use strict';
if (typeof define === 'function' && define.amd) {
// Register as an anonymous AMD module:
- define(['jquery', './jquery.fileupload-ui'], factory);
+ define([
+ 'jquery',
+ './jquery.fileupload-ui'
+ ], factory);
+ } else if (typeof exports === 'object') {
+ // Node/CommonJS:
+ factory(
+ require('jquery'),
+ require('./jquery.fileupload-ui')
+ );
} else {
// Browser globals:
factory(window.jQuery);
diff --git a/library/blueimp_upload/js/jquery.fileupload-process.js b/library/blueimp_upload/js/jquery.fileupload-process.js
index 8a6b929a6..638f0d26b 100644
--- a/library/blueimp_upload/js/jquery.fileupload-process.js
+++ b/library/blueimp_upload/js/jquery.fileupload-process.js
@@ -1,18 +1,18 @@
/*
- * jQuery File Upload Processing Plugin 1.3.0
+ * jQuery File Upload Processing Plugin
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2012, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
/* jshint nomen:false */
-/* global define, window */
+/* global define, require, window */
-(function (factory) {
+;(function (factory) {
'use strict';
if (typeof define === 'function' && define.amd) {
// Register as an anonymous AMD module:
@@ -20,6 +20,12 @@
'jquery',
'./jquery.fileupload'
], factory);
+ } else if (typeof exports === 'object') {
+ // Node/CommonJS:
+ factory(
+ require('jquery'),
+ require('./jquery.fileupload')
+ );
} else {
// Browser globals:
factory(
@@ -81,7 +87,7 @@
settings
);
};
- chain = chain.pipe(func, settings.always && func);
+ chain = chain.then(func, settings.always && func);
});
chain
.done(function () {
@@ -148,7 +154,7 @@
};
opts.index = index;
that._processing += 1;
- that._processingQueue = that._processingQueue.pipe(func, func)
+ that._processingQueue = that._processingQueue.then(func, func)
.always(function () {
that._processing -= 1;
if (that._processing === 0) {
diff --git a/library/blueimp_upload/js/jquery.fileupload-ui.js b/library/blueimp_upload/js/jquery.fileupload-ui.js
index 62cf9aa38..83e7449e6 100644
--- a/library/blueimp_upload/js/jquery.fileupload-ui.js
+++ b/library/blueimp_upload/js/jquery.fileupload-ui.js
@@ -1,29 +1,38 @@
/*
- * jQuery File Upload User Interface Plugin 9.6.0
+ * jQuery File Upload User Interface Plugin
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2010, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
/* jshint nomen:false */
-/* global define, window */
+/* global define, require, window */
-(function (factory) {
+;(function (factory) {
'use strict';
if (typeof define === 'function' && define.amd) {
// Register as an anonymous AMD module:
define([
'jquery',
- 'tmpl',
+ 'blueimp-tmpl',
'./jquery.fileupload-image',
'./jquery.fileupload-audio',
'./jquery.fileupload-video',
'./jquery.fileupload-validate'
], factory);
+ } else if (typeof exports === 'object') {
+ // Node/CommonJS:
+ factory(
+ require('jquery'),
+ require('blueimp-tmpl'),
+ require('./jquery.fileupload-image'),
+ require('./jquery.fileupload-video'),
+ require('./jquery.fileupload-validate')
+ );
} else {
// Browser globals:
factory(
@@ -62,10 +71,10 @@
// The expected data type of the upload response, sets the dataType
// option of the $.ajax upload requests:
dataType: 'json',
-
+
// Error and info messages:
messages: {
- unknownError: 'Unknown error'
+ unknownError: 'Unknown error'
},
// Function returning the current number of files,
diff --git a/library/blueimp_upload/js/jquery.fileupload-validate.js b/library/blueimp_upload/js/jquery.fileupload-validate.js
index f93a18fa2..eebeb3733 100644
--- a/library/blueimp_upload/js/jquery.fileupload-validate.js
+++ b/library/blueimp_upload/js/jquery.fileupload-validate.js
@@ -1,17 +1,17 @@
/*
- * jQuery File Upload Validation Plugin 1.1.2
+ * jQuery File Upload Validation Plugin
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2013, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
-/* global define, window */
+/* global define, require, window */
-(function (factory) {
+;(function (factory) {
'use strict';
if (typeof define === 'function' && define.amd) {
// Register as an anonymous AMD module:
@@ -19,6 +19,12 @@
'jquery',
'./jquery.fileupload-process'
], factory);
+ } else if (typeof exports === 'object') {
+ // Node/CommonJS:
+ factory(
+ require('jquery'),
+ require('./jquery.fileupload-process')
+ );
} else {
// Browser globals:
factory(
@@ -33,7 +39,7 @@
{
action: 'validate',
// Always trigger this action,
- // even if the previous action was rejected:
+ // even if the previous action was rejected:
always: true,
// Options taken from the global options map:
acceptFileTypes: '@',
diff --git a/library/blueimp_upload/js/jquery.fileupload-video.js b/library/blueimp_upload/js/jquery.fileupload-video.js
index 3764b27a2..aedcec2ba 100644
--- a/library/blueimp_upload/js/jquery.fileupload-video.js
+++ b/library/blueimp_upload/js/jquery.fileupload-video.js
@@ -1,18 +1,18 @@
/*
- * jQuery File Upload Video Preview Plugin 1.0.3
+ * jQuery File Upload Video Preview Plugin
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2013, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
/* jshint nomen:false */
-/* global define, window, document */
+/* global define, require, window, document */
-(function (factory) {
+;(function (factory) {
'use strict';
if (typeof define === 'function' && define.amd) {
// Register as an anonymous AMD module:
@@ -21,6 +21,13 @@
'load-image',
'./jquery.fileupload-process'
], factory);
+ } else if (typeof exports === 'object') {
+ // Node/CommonJS:
+ factory(
+ require('jquery'),
+ require('blueimp-load-image/js/load-image'),
+ require('./jquery.fileupload-process')
+ );
} else {
// Browser globals:
factory(
diff --git a/library/blueimp_upload/js/jquery.fileupload.js b/library/blueimp_upload/js/jquery.fileupload.js
index a4cfdc0ac..5ff151b53 100644
--- a/library/blueimp_upload/js/jquery.fileupload.js
+++ b/library/blueimp_upload/js/jquery.fileupload.js
@@ -1,25 +1,31 @@
/*
- * jQuery File Upload Plugin 5.42.0
+ * jQuery File Upload Plugin
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2010, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
/* jshint nomen:false */
-/* global define, window, document, location, Blob, FormData */
+/* global define, require, window, document, location, Blob, FormData */
-(function (factory) {
+;(function (factory) {
'use strict';
if (typeof define === 'function' && define.amd) {
// Register as an anonymous AMD module:
define([
'jquery',
- 'jquery.ui.widget'
+ 'jquery-ui/ui/widget'
], factory);
+ } else if (typeof exports === 'object') {
+ // Node/CommonJS:
+ factory(
+ require('jquery'),
+ require('./vendor/jquery.ui.widget')
+ );
} else {
// Browser globals:
factory(window.jQuery);
@@ -271,7 +277,8 @@
// The following are jQuery ajax settings required for the file uploads:
processData: false,
contentType: false,
- cache: false
+ cache: false,
+ timeout: 0
},
// A list of options that require reinitializing event listeners and/or
@@ -645,7 +652,7 @@
data.process = function (resolveFunc, rejectFunc) {
if (resolveFunc || rejectFunc) {
data._processQueue = this._processQueue =
- (this._processQueue || getPromise([this])).pipe(
+ (this._processQueue || getPromise([this])).then(
function () {
if (data.errorThrown) {
return $.Deferred()
@@ -653,7 +660,7 @@
}
return getPromise(arguments);
}
- ).pipe(resolveFunc, rejectFunc);
+ ).then(resolveFunc, rejectFunc);
}
return this._processQueue || getPromise([this]);
};
@@ -938,9 +945,9 @@
if (this.options.limitConcurrentUploads > 1) {
slot = $.Deferred();
this._slots.push(slot);
- pipe = slot.pipe(send);
+ pipe = slot.then(send);
} else {
- this._sequence = this._sequence.pipe(send, send);
+ this._sequence = this._sequence.then(send, send);
pipe = this._sequence;
}
// Return the piped Promise object, enhanced with an abort method,
@@ -977,7 +984,10 @@
fileSet,
i,
j = 0;
- if (limitSize && (!filesLength || files[0].size === undefined)) {
+ if (!filesLength) {
+ return false;
+ }
+ if (limitSize && files[0].size === undefined) {
limitSize = undefined;
}
if (!(options.singleFileUploads || limit || limitSize) ||
@@ -1036,13 +1046,19 @@
_replaceFileInput: function (data) {
var input = data.fileInput,
- inputClone = input.clone(true);
+ inputClone = input.clone(true),
+ restoreFocus = input.is(document.activeElement);
// Add a reference for the new cloned file input to the data argument:
data.fileInputClone = inputClone;
$('<form></form>').append(inputClone)[0].reset();
// Detaching allows to insert the fileInput on another form
// without loosing the file input value:
input.after(inputClone).detach();
+ // If the fileInput had focus before it was detached,
+ // restore focus to the inputClone.
+ if (restoreFocus) {
+ inputClone.focus();
+ }
// Avoid memory leaks with the detached file input:
$.cleanData(input.unbind('remove'));
// Replace the original file input element in the fileInput
@@ -1064,6 +1080,8 @@
_handleFileTreeEntry: function (entry, path) {
var that = this,
dfd = $.Deferred(),
+ entries = [],
+ dirReader,
errorHandler = function (e) {
if (e && !e.entry) {
e.entry = entry;
@@ -1091,8 +1109,7 @@
readEntries();
}
}, errorHandler);
- },
- dirReader, entries = [];
+ };
path = path || '';
if (entry.isFile) {
if (entry._file) {
@@ -1123,7 +1140,7 @@
$.map(entries, function (entry) {
return that._handleFileTreeEntry(entry, path);
})
- ).pipe(function () {
+ ).then(function () {
return Array.prototype.concat.apply(
[],
arguments
@@ -1192,7 +1209,7 @@
return $.when.apply(
$,
$.map(fileInput, this._getSingleFileInputFiles)
- ).pipe(function () {
+ ).then(function () {
return Array.prototype.concat.apply(
[],
arguments
@@ -1295,6 +1312,10 @@
this._off(this.options.fileInput, 'change');
},
+ _destroy: function () {
+ this._destroyEventHandlers();
+ },
+
_setOption: function (key, value) {
var reinit = $.inArray(key, this._specialOptions) !== -1;
if (reinit) {
@@ -1338,15 +1359,19 @@
_initDataAttributes: function () {
var that = this,
options = this.options,
- clone = $(this.element[0].cloneNode(false));
+ data = this.element.data();
// Initialize options set via HTML5 data-attributes:
$.each(
- clone.data(),
- function (key, value) {
- var dataAttributeName = 'data-' +
- // Convert camelCase to hyphen-ated key:
- key.replace(/([a-z])([A-Z])/g, '$1-$2').toLowerCase();
- if (clone.attr(dataAttributeName)) {
+ this.element[0].attributes,
+ function (index, attr) {
+ var key = attr.name.toLowerCase(),
+ value;
+ if (/^data-/.test(key)) {
+ // Convert hyphen-ated key to camelCase:
+ key = key.slice(5).replace(/-[a-z]/g, function (str) {
+ return str.charAt(1).toUpperCase();
+ });
+ value = data[key];
if (that._isRegExpOption(key, value)) {
value = that._getRegExp(value);
}
diff --git a/library/blueimp_upload/js/jquery.iframe-transport.js b/library/blueimp_upload/js/jquery.iframe-transport.js
index 8d64b591b..8d25c4641 100644
--- a/library/blueimp_upload/js/jquery.iframe-transport.js
+++ b/library/blueimp_upload/js/jquery.iframe-transport.js
@@ -1,21 +1,24 @@
/*
- * jQuery Iframe Transport Plugin 1.8.2
+ * jQuery Iframe Transport Plugin
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2011, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
-/* global define, window, document */
+/* global define, require, window, document, JSON */
-(function (factory) {
+;(function (factory) {
'use strict';
if (typeof define === 'function' && define.amd) {
// Register as an anonymous AMD module:
define(['jquery'], factory);
+ } else if (typeof exports === 'object') {
+ // Node/CommonJS:
+ factory(require('jquery'));
} else {
// Browser globals:
factory(window.jQuery);
@@ -24,7 +27,14 @@
'use strict';
// Helper variable to create unique names for the transport iframes:
- var counter = 0;
+ var counter = 0,
+ jsonAPI = $,
+ jsonParse = 'parseJSON';
+
+ if ('JSON' in window && 'parse' in JSON) {
+ jsonAPI = JSON;
+ jsonParse = 'parse';
+ }
// The iframe transport accepts four additional options:
// options.fileInput: a jQuery collection of file input fields
@@ -194,7 +204,7 @@
return iframe && $(iframe[0].body).text();
},
'iframe json': function (iframe) {
- return iframe && $.parseJSON($(iframe[0].body).text());
+ return iframe && jsonAPI[jsonParse]($(iframe[0].body).text());
},
'iframe html': function (iframe) {
return iframe && $(iframe[0].body).html();
diff --git a/library/blueimp_upload/js/main.js b/library/blueimp_upload/js/main.js
index 8f57967a3..0403682e7 100644
--- a/library/blueimp_upload/js/main.js
+++ b/library/blueimp_upload/js/main.js
@@ -1,12 +1,12 @@
/*
- * jQuery File Upload Plugin JS Example 8.9.1
+ * jQuery File Upload Plugin JS Example
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2010, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
/* global $, window */
@@ -40,7 +40,7 @@ $(function () {
// send Blob objects via XHR requests:
disableImageResize: /Android(?!.*Chrome)|Opera/
.test(window.navigator.userAgent),
- maxFileSize: 5000000,
+ maxFileSize: 999000,
acceptFileTypes: /(\.|\/)(gif|jpe?g|png)$/i
});
// Upload server status check for browsers with CORS support:
diff --git a/library/blueimp_upload/js/vendor/jquery.ui.widget.js b/library/blueimp_upload/js/vendor/jquery.ui.widget.js
index 7899e6bb3..e08df3fd0 100644
--- a/library/blueimp_upload/js/vendor/jquery.ui.widget.js
+++ b/library/blueimp_upload/js/vendor/jquery.ui.widget.js
@@ -1,13 +1,19 @@
-/*! jQuery UI - v1.11.1 - 2014-09-17
+/*! jQuery UI - v1.11.4+CommonJS - 2015-08-28
* http://jqueryui.com
* Includes: widget.js
-* Copyright 2014 jQuery Foundation and other contributors; Licensed MIT */
+* Copyright 2015 jQuery Foundation and other contributors; Licensed MIT */
(function( factory ) {
if ( typeof define === "function" && define.amd ) {
// AMD. Register as an anonymous module.
define([ "jquery" ], factory );
+
+ } else if ( typeof exports === "object" ) {
+
+ // Node/CommonJS
+ factory( require( "jquery" ) );
+
} else {
// Browser globals
@@ -15,10 +21,10 @@
}
}(function( $ ) {
/*!
- * jQuery UI Widget 1.11.1
+ * jQuery UI Widget 1.11.4
* http://jqueryui.com
*
- * Copyright 2014 jQuery Foundation and other contributors
+ * Copyright jQuery Foundation and other contributors
* Released under the MIT license.
* http://jquery.org/license
*
@@ -42,7 +48,7 @@ $.cleanData = (function( orig ) {
}
// http://bugs.jquery.com/ticket/8235
- } catch( e ) {}
+ } catch ( e ) {}
}
orig( elems );
};
@@ -196,11 +202,6 @@ $.widget.bridge = function( name, object ) {
args = widget_slice.call( arguments, 1 ),
returnValue = this;
- // allow multiple hashes to be passed on init
- options = !isMethodCall && args.length ?
- $.widget.extend.apply( null, [ options ].concat(args) ) :
- options;
-
if ( isMethodCall ) {
this.each(function() {
var methodValue,
@@ -225,6 +226,12 @@ $.widget.bridge = function( name, object ) {
}
});
} else {
+
+ // Allow multiple hashes to be passed on init
+ if ( args.length ) {
+ options = $.widget.extend.apply( null, [ options ].concat(args) );
+ }
+
this.each(function() {
var instance = $.data( this, fullName );
if ( instance ) {
@@ -260,10 +267,6 @@ $.Widget.prototype = {
this.element = $( element );
this.uuid = widget_uuid++;
this.eventNamespace = "." + this.widgetName + this.uuid;
- this.options = $.widget.extend( {},
- this.options,
- this._getCreateOptions(),
- options );
this.bindings = $();
this.hoverable = $();
@@ -286,6 +289,11 @@ $.Widget.prototype = {
this.window = $( this.document[0].defaultView || this.document[0].parentWindow );
}
+ this.options = $.widget.extend( {},
+ this.options,
+ this._getCreateOptions(),
+ options );
+
this._create();
this._trigger( "create", null, this._getCreateEventData() );
this._init();
@@ -448,8 +456,14 @@ $.Widget.prototype = {
},
_off: function( element, eventName ) {
- eventName = (eventName || "").split( " " ).join( this.eventNamespace + " " ) + this.eventNamespace;
+ eventName = (eventName || "").split( " " ).join( this.eventNamespace + " " ) +
+ this.eventNamespace;
element.unbind( eventName ).undelegate( eventName );
+
+ // Clear the stack to avoid memory leaks (#10056)
+ this.bindings = $( this.bindings.not( element ).get() );
+ this.focusable = $( this.focusable.not( element ).get() );
+ this.hoverable = $( this.hoverable.not( element ).get() );
},
_delay: function( handler, delay ) {
diff --git a/library/blueimp_upload/package.json b/library/blueimp_upload/package.json
index 880574aa7..ed4d33681 100644
--- a/library/blueimp_upload/package.json
+++ b/library/blueimp_upload/package.json
@@ -1,8 +1,8 @@
{
"name": "blueimp-file-upload",
- "version": "9.8.0",
+ "version": "9.18.0",
"title": "jQuery File Upload",
- "description": "File Upload widget with multiple file selection, drag&amp;drop support, progress bar, validation and preview images, audio and video for jQuery. Supports cross-domain, chunked and resumable file uploads. Works with any server-side platform (Google App Engine, PHP, Python, Ruby on Rails, Java, etc.) that supports standard HTML form file uploads.",
+ "description": "File Upload widget with multiple file selection, drag&drop support, progress bar, validation and preview images, audio and video for jQuery. Supports cross-domain, chunked and resumable file uploads. Works with any server-side platform (Google App Engine, PHP, Python, Ruby on Rails, Java, etc.) that supports standard HTML form file uploads.",
"keywords": [
"jquery",
"file",
@@ -29,26 +29,27 @@
"name": "Sebastian Tschan",
"url": "https://blueimp.net"
},
- "maintainers": [
- {
- "name": "Sebastian Tschan",
- "url": "https://blueimp.net"
- }
- ],
"repository": {
"type": "git",
"url": "git://github.com/blueimp/jQuery-File-Upload.git"
},
- "bugs": "https://github.com/blueimp/jQuery-File-Upload/issues",
- "licenses": [
- {
- "type": "MIT",
- "url": "http://www.opensource.org/licenses/MIT"
- }
- ],
+ "license": "MIT",
+ "optionalDependencies": {
+ "blueimp-canvas-to-blob": "3.5.0",
+ "blueimp-load-image": "2.12.2",
+ "blueimp-tmpl": "3.6.0"
+ },
"devDependencies": {
- "grunt": "~0.4.5",
- "grunt-bump-build-git": "~1.1.1",
- "grunt-contrib-jshint": "~0.10.0"
- }
+ "bower-json": "0.8.1",
+ "jshint": "2.9.3"
+ },
+ "scripts": {
+ "bower-version-update": "./bower-version-update.js",
+ "lint": "jshint *.js js/*.js js/cors/*.js",
+ "test": "npm run lint",
+ "preversion": "npm test",
+ "version": "npm run bower-version-update && git add bower.json",
+ "postversion": "git push --tags origin master && npm publish"
+ },
+ "main": "js/jquery.fileupload.js"
}
diff --git a/library/blueimp_upload/server/gae-go/app/main.go b/library/blueimp_upload/server/gae-go/app/main.go
index 03af0b1d2..a92d128c0 100644
--- a/library/blueimp_upload/server/gae-go/app/main.go
+++ b/library/blueimp_upload/server/gae-go/app/main.go
@@ -1,59 +1,90 @@
/*
- * jQuery File Upload Plugin GAE Go Example 3.2.0
+ * jQuery File Upload Plugin GAE Go Example
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2011, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
package app
import (
- "appengine"
- "appengine/blobstore"
- "appengine/image"
- "appengine/taskqueue"
+ "bufio"
"bytes"
"encoding/json"
"fmt"
+ "github.com/disintegration/gift"
+ "golang.org/x/net/context"
+ "google.golang.org/appengine"
+ "google.golang.org/appengine/memcache"
+ "hash/crc32"
+ "image"
+ "image/gif"
+ "image/jpeg"
+ "image/png"
"io"
"log"
"mime/multipart"
"net/http"
"net/url"
+ "path/filepath"
"regexp"
"strings"
- "time"
)
const (
- WEBSITE = "https://blueimp.github.io/jQuery-File-Upload/"
- MIN_FILE_SIZE = 1 // bytes
- MAX_FILE_SIZE = 5000000 // bytes
+ WEBSITE = "https://blueimp.github.io/jQuery-File-Upload/"
+ MIN_FILE_SIZE = 1 // bytes
+ // Max file size is memcache limit (1MB) minus key size minus overhead:
+ MAX_FILE_SIZE = 999000 // bytes
IMAGE_TYPES = "image/(gif|p?jpeg|(x-)?png)"
ACCEPT_FILE_TYPES = IMAGE_TYPES
+ THUMB_MAX_WIDTH = 80
+ THUMB_MAX_HEIGHT = 80
EXPIRATION_TIME = 300 // seconds
- THUMBNAIL_PARAM = "=s80"
+ // If empty, only allow redirects to the referer protocol+host.
+ // Set to a regexp string for custom pattern matching:
+ REDIRECT_ALLOW_TARGET = ""
)
var (
imageTypes = regexp.MustCompile(IMAGE_TYPES)
acceptFileTypes = regexp.MustCompile(ACCEPT_FILE_TYPES)
+ thumbSuffix = "." + fmt.Sprint(THUMB_MAX_WIDTH) + "x" +
+ fmt.Sprint(THUMB_MAX_HEIGHT)
)
+func escape(s string) string {
+ return strings.Replace(url.QueryEscape(s), "+", "%20", -1)
+}
+
+func extractKey(r *http.Request) string {
+ // Use RequestURI instead of r.URL.Path, as we need the encoded form:
+ path := strings.Split(r.RequestURI, "?")[0]
+ // Also adjust double encoded slashes:
+ return strings.Replace(path[1:], "%252F", "%2F", -1)
+}
+
+func check(err error) {
+ if err != nil {
+ panic(err)
+ }
+}
+
type FileInfo struct {
- Key appengine.BlobKey `json:"-"`
- Url string `json:"url,omitempty"`
- ThumbnailUrl string `json:"thumbnailUrl,omitempty"`
- Name string `json:"name"`
- Type string `json:"type"`
- Size int64 `json:"size"`
- Error string `json:"error,omitempty"`
- DeleteUrl string `json:"deleteUrl,omitempty"`
- DeleteType string `json:"deleteType,omitempty"`
+ Key string `json:"-"`
+ ThumbnailKey string `json:"-"`
+ Url string `json:"url,omitempty"`
+ ThumbnailUrl string `json:"thumbnailUrl,omitempty"`
+ Name string `json:"name"`
+ Type string `json:"type"`
+ Size int64 `json:"size"`
+ Error string `json:"error,omitempty"`
+ DeleteUrl string `json:"deleteUrl,omitempty"`
+ DeleteType string `json:"deleteType,omitempty"`
}
func (fi *FileInfo) ValidateType() (valid bool) {
@@ -75,50 +106,58 @@ func (fi *FileInfo) ValidateSize() (valid bool) {
return false
}
-func (fi *FileInfo) CreateUrls(r *http.Request, c appengine.Context) {
+func (fi *FileInfo) CreateUrls(r *http.Request, c context.Context) {
u := &url.URL{
Scheme: r.URL.Scheme,
Host: appengine.DefaultVersionHostname(c),
Path: "/",
}
uString := u.String()
- fi.Url = uString + escape(string(fi.Key)) + "/" +
- escape(string(fi.Name))
- fi.DeleteUrl = fi.Url + "?delete=true"
+ fi.Url = uString + fi.Key
+ fi.DeleteUrl = fi.Url
fi.DeleteType = "DELETE"
- if imageTypes.MatchString(fi.Type) {
- servingUrl, err := image.ServingURL(
- c,
- fi.Key,
- &image.ServingURLOptions{
- Secure: strings.HasSuffix(u.Scheme, "s"),
- Size: 0,
- Crop: false,
- },
- )
- check(err)
- fi.ThumbnailUrl = servingUrl.String() + THUMBNAIL_PARAM
+ if fi.ThumbnailKey != "" {
+ fi.ThumbnailUrl = uString + fi.ThumbnailKey
}
}
-func check(err error) {
- if err != nil {
- panic(err)
- }
-}
-
-func escape(s string) string {
- return strings.Replace(url.QueryEscape(s), "+", "%20", -1)
+func (fi *FileInfo) SetKey(checksum uint32) {
+ fi.Key = escape(string(fi.Type)) + "/" +
+ escape(fmt.Sprint(checksum)) + "/" +
+ escape(string(fi.Name))
}
-func delayedDelete(c appengine.Context, fi *FileInfo) {
- if key := string(fi.Key); key != "" {
- task := &taskqueue.Task{
- Path: "/" + escape(key) + "/-",
- Method: "DELETE",
- Delay: time.Duration(EXPIRATION_TIME) * time.Second,
+func (fi *FileInfo) createThumb(buffer *bytes.Buffer, c context.Context) {
+ if imageTypes.MatchString(fi.Type) {
+ src, _, err := image.Decode(bytes.NewReader(buffer.Bytes()))
+ check(err)
+ filter := gift.New(gift.ResizeToFit(
+ THUMB_MAX_WIDTH,
+ THUMB_MAX_HEIGHT,
+ gift.LanczosResampling,
+ ))
+ dst := image.NewNRGBA(filter.Bounds(src.Bounds()))
+ filter.Draw(dst, src)
+ buffer.Reset()
+ bWriter := bufio.NewWriter(buffer)
+ switch fi.Type {
+ case "image/jpeg", "image/pjpeg":
+ err = jpeg.Encode(bWriter, dst, nil)
+ case "image/gif":
+ err = gif.Encode(bWriter, dst, nil)
+ default:
+ err = png.Encode(bWriter, dst)
+ }
+ check(err)
+ bWriter.Flush()
+ thumbnailKey := fi.Key + thumbSuffix + filepath.Ext(fi.Name)
+ item := &memcache.Item{
+ Key: thumbnailKey,
+ Value: buffer.Bytes(),
}
- taskqueue.Add(c, task, "")
+ err = memcache.Set(c, item)
+ check(err)
+ fi.ThumbnailKey = thumbnailKey
}
}
@@ -136,24 +175,26 @@ func handleUpload(r *http.Request, p *multipart.Part) (fi *FileInfo) {
fi.Error = rec.(error).Error()
}
}()
+ var buffer bytes.Buffer
+ hash := crc32.NewIEEE()
+ mw := io.MultiWriter(&buffer, hash)
lr := &io.LimitedReader{R: p, N: MAX_FILE_SIZE + 1}
+ _, err := io.Copy(mw, lr)
+ check(err)
+ fi.Size = MAX_FILE_SIZE + 1 - lr.N
+ if !fi.ValidateSize() {
+ return
+ }
+ fi.SetKey(hash.Sum32())
+ item := &memcache.Item{
+ Key: fi.Key,
+ Value: buffer.Bytes(),
+ }
context := appengine.NewContext(r)
- w, err := blobstore.Create(context, fi.Type)
- defer func() {
- w.Close()
- fi.Size = MAX_FILE_SIZE + 1 - lr.N
- fi.Key, err = w.Key()
- check(err)
- if !fi.ValidateSize() {
- err := blobstore.Delete(context, fi.Key)
- check(err)
- return
- }
- delayedDelete(context, fi)
- fi.CreateUrls(r, context)
- }()
+ err = memcache.Set(context, item)
check(err)
- _, err = io.Copy(w, lr)
+ fi.createThumb(&buffer, context)
+ fi.CreateUrls(r, context)
return
}
@@ -183,49 +224,70 @@ func handleUploads(r *http.Request) (fileInfos []*FileInfo) {
return
}
+func validateRedirect(r *http.Request, redirect string) bool {
+ if redirect != "" {
+ var redirectAllowTarget *regexp.Regexp
+ if REDIRECT_ALLOW_TARGET != "" {
+ redirectAllowTarget = regexp.MustCompile(REDIRECT_ALLOW_TARGET)
+ } else {
+ referer := r.Referer()
+ if referer == "" {
+ return false
+ }
+ refererUrl, err := url.Parse(referer)
+ if err != nil {
+ return false
+ }
+ redirectAllowTarget = regexp.MustCompile("^" + regexp.QuoteMeta(
+ refererUrl.Scheme+"://"+refererUrl.Host+"/",
+ ))
+ }
+ return redirectAllowTarget.MatchString(redirect)
+ }
+ return false
+}
+
func get(w http.ResponseWriter, r *http.Request) {
if r.URL.Path == "/" {
http.Redirect(w, r, WEBSITE, http.StatusFound)
return
}
- parts := strings.Split(r.URL.Path, "/")
+ // Use RequestURI instead of r.URL.Path, as we need the encoded form:
+ key := extractKey(r)
+ parts := strings.Split(key, "/")
if len(parts) == 3 {
- if key := parts[1]; key != "" {
- blobKey := appengine.BlobKey(key)
- bi, err := blobstore.Stat(appengine.NewContext(r), blobKey)
- if err == nil {
- w.Header().Add("X-Content-Type-Options", "nosniff")
- if !imageTypes.MatchString(bi.ContentType) {
- w.Header().Add("Content-Type", "application/octet-stream")
- w.Header().Add(
- "Content-Disposition",
- fmt.Sprintf("attachment; filename=\"%s\"", parts[2]),
- )
- }
- w.Header().Add(
- "Cache-Control",
- fmt.Sprintf("public,max-age=%d", EXPIRATION_TIME),
- )
- blobstore.Send(w, blobKey)
- return
+ context := appengine.NewContext(r)
+ item, err := memcache.Get(context, key)
+ if err == nil {
+ w.Header().Add("X-Content-Type-Options", "nosniff")
+ contentType, _ := url.QueryUnescape(parts[0])
+ if !imageTypes.MatchString(contentType) {
+ contentType = "application/octet-stream"
}
+ w.Header().Add("Content-Type", contentType)
+ w.Header().Add(
+ "Cache-Control",
+ fmt.Sprintf("public,max-age=%d", EXPIRATION_TIME),
+ )
+ w.Write(item.Value)
+ return
}
}
http.Error(w, "404 Not Found", http.StatusNotFound)
}
func post(w http.ResponseWriter, r *http.Request) {
- result := make(map[string][]*FileInfo, 1)
- result["files"] = handleUploads(r)
+ result := make(map[string][]*FileInfo, 1)
+ result["files"] = handleUploads(r)
b, err := json.Marshal(result)
check(err)
- if redirect := r.FormValue("redirect"); redirect != "" {
- if strings.Contains(redirect, "%s") {
- redirect = fmt.Sprintf(
- redirect,
- escape(string(b)),
- )
- }
+ if redirect := r.FormValue("redirect"); validateRedirect(r, redirect) {
+ if strings.Contains(redirect, "%s") {
+ redirect = fmt.Sprintf(
+ redirect,
+ escape(string(b)),
+ )
+ }
http.Redirect(w, r, redirect, http.StatusFound)
return
}
@@ -238,27 +300,30 @@ func post(w http.ResponseWriter, r *http.Request) {
}
func delete(w http.ResponseWriter, r *http.Request) {
- parts := strings.Split(r.URL.Path, "/")
- if len(parts) != 3 {
- return
- }
- result := make(map[string]bool, 1)
- if key := parts[1]; key != "" {
- c := appengine.NewContext(r)
- blobKey := appengine.BlobKey(key)
- err := blobstore.Delete(c, blobKey)
- check(err)
- err = image.DeleteServingURL(c, blobKey)
+ key := extractKey(r)
+ parts := strings.Split(key, "/")
+ if len(parts) == 3 {
+ result := make(map[string]bool, 1)
+ context := appengine.NewContext(r)
+ err := memcache.Delete(context, key)
+ if err == nil {
+ result[key] = true
+ contentType, _ := url.QueryUnescape(parts[0])
+ if imageTypes.MatchString(contentType) {
+ thumbnailKey := key + thumbSuffix + filepath.Ext(parts[2])
+ err := memcache.Delete(context, thumbnailKey)
+ if err == nil {
+ result[thumbnailKey] = true
+ }
+ }
+ }
+ w.Header().Set("Content-Type", "application/json")
+ b, err := json.Marshal(result)
check(err)
- result[key] = true
- }
- jsonType := "application/json"
- if strings.Index(r.Header.Get("Accept"), jsonType) != -1 {
- w.Header().Set("Content-Type", jsonType)
+ fmt.Fprintln(w, string(b))
+ } else {
+ http.Error(w, "405 Method not allowed", http.StatusMethodNotAllowed)
}
- b, err := json.Marshal(result)
- check(err)
- fmt.Fprintln(w, string(b))
}
func handle(w http.ResponseWriter, r *http.Request) {
@@ -267,15 +332,15 @@ func handle(w http.ResponseWriter, r *http.Request) {
w.Header().Add("Access-Control-Allow-Origin", "*")
w.Header().Add(
"Access-Control-Allow-Methods",
- "OPTIONS, HEAD, GET, POST, PUT, DELETE",
+ "OPTIONS, HEAD, GET, POST, DELETE",
)
w.Header().Add(
"Access-Control-Allow-Headers",
"Content-Type, Content-Range, Content-Disposition",
)
switch r.Method {
- case "OPTIONS":
- case "HEAD":
+ case "OPTIONS", "HEAD":
+ return
case "GET":
get(w, r)
case "POST":
diff --git a/library/blueimp_upload/server/gae-python/app.yaml b/library/blueimp_upload/server/gae-python/app.yaml
index 5fe123f59..764449b74 100644
--- a/library/blueimp_upload/server/gae-python/app.yaml
+++ b/library/blueimp_upload/server/gae-python/app.yaml
@@ -4,8 +4,9 @@ runtime: python27
api_version: 1
threadsafe: true
-builtins:
-- deferred: on
+libraries:
+- name: PIL
+ version: latest
handlers:
- url: /(favicon\.ico|robots\.txt)
diff --git a/library/blueimp_upload/server/gae-python/main.py b/library/blueimp_upload/server/gae-python/main.py
index 6276be6a0..1955ac00a 100644
--- a/library/blueimp_upload/server/gae-python/main.py
+++ b/library/blueimp_upload/server/gae-python/main.py
@@ -1,49 +1,57 @@
# -*- coding: utf-8 -*-
#
-# jQuery File Upload Plugin GAE Python Example 2.2.0
+# jQuery File Upload Plugin GAE Python Example
# https://github.com/blueimp/jQuery-File-Upload
#
# Copyright 2011, Sebastian Tschan
# https://blueimp.net
#
# Licensed under the MIT license:
-# http://www.opensource.org/licenses/MIT
+# https://opensource.org/licenses/MIT
#
-from __future__ import with_statement
-from google.appengine.api import files, images
-from google.appengine.ext import blobstore, deferred
-from google.appengine.ext.webapp import blobstore_handlers
+from google.appengine.api import memcache, images
import json
+import os
import re
import urllib
import webapp2
+DEBUG=os.environ.get('SERVER_SOFTWARE', '').startswith('Dev')
WEBSITE = 'https://blueimp.github.io/jQuery-File-Upload/'
MIN_FILE_SIZE = 1 # bytes
-MAX_FILE_SIZE = 5000000 # bytes
+# Max file size is memcache limit (1MB) minus key size minus overhead:
+MAX_FILE_SIZE = 999000 # bytes
IMAGE_TYPES = re.compile('image/(gif|p?jpeg|(x-)?png)')
ACCEPT_FILE_TYPES = IMAGE_TYPES
-THUMBNAIL_MODIFICATOR = '=s80' # max width / height
+THUMB_MAX_WIDTH = 80
+THUMB_MAX_HEIGHT = 80
+THUMB_SUFFIX = '.'+str(THUMB_MAX_WIDTH)+'x'+str(THUMB_MAX_HEIGHT)+'.png'
EXPIRATION_TIME = 300 # seconds
+# If set to None, only allow redirects to the referer protocol+host.
+# Set to a regexp for custom pattern matching against the redirect value:
+REDIRECT_ALLOW_TARGET = None
+
+class CORSHandler(webapp2.RequestHandler):
+ def cors(self):
+ headers = self.response.headers
+ headers['Access-Control-Allow-Origin'] = '*'
+ headers['Access-Control-Allow-Methods'] =\
+ 'OPTIONS, HEAD, GET, POST, DELETE'
+ headers['Access-Control-Allow-Headers'] =\
+ 'Content-Type, Content-Range, Content-Disposition'
+ def initialize(self, request, response):
+ super(CORSHandler, self).initialize(request, response)
+ self.cors()
-def cleanup(blob_keys):
- blobstore.delete(blob_keys)
-
-
-class UploadHandler(webapp2.RequestHandler):
+ def json_stringify(self, obj):
+ return json.dumps(obj, separators=(',', ':'))
- def initialize(self, request, response):
- super(UploadHandler, self).initialize(request, response)
- self.response.headers['Access-Control-Allow-Origin'] = '*'
- self.response.headers[
- 'Access-Control-Allow-Methods'
- ] = 'OPTIONS, HEAD, GET, POST, PUT, DELETE'
- self.response.headers[
- 'Access-Control-Allow-Headers'
- ] = 'Content-Type, Content-Range, Content-Disposition'
+ def options(self, *args, **kwargs):
+ pass
+class UploadHandler(CORSHandler):
def validate(self, file):
if file['size'] < MIN_FILE_SIZE:
file['error'] = 'File is too small'
@@ -55,6 +63,20 @@ class UploadHandler(webapp2.RequestHandler):
return True
return False
+ def validate_redirect(self, redirect):
+ if redirect:
+ if REDIRECT_ALLOW_TARGET:
+ return REDIRECT_ALLOW_TARGET.match(redirect)
+ referer = self.request.headers['referer']
+ if referer:
+ from urlparse import urlparse
+ parts = urlparse(referer)
+ redirect_allow_target = '^' + re.escape(
+ parts.scheme + '://' + parts.netloc + '/'
+ )
+ return re.match(redirect_allow_target, redirect)
+ return False
+
def get_file_size(self, file):
file.seek(0, 2) # Seek to the end of the file
size = file.tell() # Get the position of EOF
@@ -62,64 +84,58 @@ class UploadHandler(webapp2.RequestHandler):
return size
def write_blob(self, data, info):
- blob = files.blobstore.create(
- mime_type=info['type'],
- _blobinfo_uploaded_filename=info['name']
- )
- with files.open(blob, 'a') as f:
- f.write(data)
- files.finalize(blob)
- return files.blobstore.get_blob_key(blob)
+ key = urllib.quote(info['type'].encode('utf-8'), '') +\
+ '/' + str(hash(data)) +\
+ '/' + urllib.quote(info['name'].encode('utf-8'), '')
+ try:
+ memcache.set(key, data, time=EXPIRATION_TIME)
+ except: #Failed to add to memcache
+ return (None, None)
+ thumbnail_key = None
+ if IMAGE_TYPES.match(info['type']):
+ try:
+ img = images.Image(image_data=data)
+ img.resize(
+ width=THUMB_MAX_WIDTH,
+ height=THUMB_MAX_HEIGHT
+ )
+ thumbnail_data = img.execute_transforms()
+ thumbnail_key = key + THUMB_SUFFIX
+ memcache.set(
+ thumbnail_key,
+ thumbnail_data,
+ time=EXPIRATION_TIME
+ )
+ except: #Failed to resize Image or add to memcache
+ thumbnail_key = None
+ return (key, thumbnail_key)
def handle_upload(self):
results = []
- blob_keys = []
for name, fieldStorage in self.request.POST.items():
if type(fieldStorage) is unicode:
continue
result = {}
- result['name'] = re.sub(
- r'^.*\\',
- '',
- fieldStorage.filename
- )
+ result['name'] = urllib.unquote(fieldStorage.filename)
result['type'] = fieldStorage.type
result['size'] = self.get_file_size(fieldStorage.file)
if self.validate(result):
- blob_key = str(
- self.write_blob(fieldStorage.value, result)
+ key, thumbnail_key = self.write_blob(
+ fieldStorage.value,
+ result
)
- blob_keys.append(blob_key)
- result['deleteType'] = 'DELETE'
- result['deleteUrl'] = self.request.host_url +\
- '/?key=' + urllib.quote(blob_key, '')
- if (IMAGE_TYPES.match(result['type'])):
- try:
- result['url'] = images.get_serving_url(
- blob_key,
- secure_url=self.request.host_url.startswith(
- 'https'
- )
- )
- result['thumbnailUrl'] = result['url'] +\
- THUMBNAIL_MODIFICATOR
- except: # Could not get an image serving url
- pass
- if not 'url' in result:
- result['url'] = self.request.host_url +\
- '/' + blob_key + '/' + urllib.quote(
- result['name'].encode('utf-8'), '')
+ if key is not None:
+ result['url'] = self.request.host_url + '/' + key
+ result['deleteUrl'] = result['url']
+ result['deleteType'] = 'DELETE'
+ if thumbnail_key is not None:
+ result['thumbnailUrl'] = self.request.host_url +\
+ '/' + thumbnail_key
+ else:
+ result['error'] = 'Failed to store uploaded file.'
results.append(result)
- deferred.defer(
- cleanup,
- blob_keys,
- _countdown=EXPIRATION_TIME
- )
return results
- def options(self):
- pass
-
def head(self):
pass
@@ -130,9 +146,9 @@ class UploadHandler(webapp2.RequestHandler):
if (self.request.get('_method') == 'DELETE'):
return self.delete()
result = {'files': self.handle_upload()}
- s = json.dumps(result, separators=(',', ':'))
+ s = self.json_stringify(result)
redirect = self.request.get('redirect')
- if redirect:
+ if self.validate_redirect(redirect):
return self.redirect(str(
redirect.replace('%s', urllib.quote(s, ''), 1)
))
@@ -140,31 +156,49 @@ class UploadHandler(webapp2.RequestHandler):
self.response.headers['Content-Type'] = 'application/json'
self.response.write(s)
- def delete(self):
- key = self.request.get('key') or ''
- blobstore.delete(key)
- s = json.dumps({key: True}, separators=(',', ':'))
+class FileHandler(CORSHandler):
+ def normalize(self, str):
+ return urllib.quote(urllib.unquote(str), '')
+
+ def get(self, content_type, data_hash, file_name):
+ content_type = self.normalize(content_type)
+ file_name = self.normalize(file_name)
+ key = content_type + '/' + data_hash + '/' + file_name
+ data = memcache.get(key)
+ if data is None:
+ return self.error(404)
+ # Prevent browsers from MIME-sniffing the content-type:
+ self.response.headers['X-Content-Type-Options'] = 'nosniff'
+ content_type = urllib.unquote(content_type)
+ if not IMAGE_TYPES.match(content_type):
+ # Force a download dialog for non-image types:
+ content_type = 'application/octet-stream'
+ elif file_name.endswith(THUMB_SUFFIX):
+ content_type = 'image/png'
+ self.response.headers['Content-Type'] = content_type
+ # Cache for the expiration time:
+ self.response.headers['Cache-Control'] = 'public,max-age=%d' \
+ % EXPIRATION_TIME
+ self.response.write(data)
+
+ def delete(self, content_type, data_hash, file_name):
+ content_type = self.normalize(content_type)
+ file_name = self.normalize(file_name)
+ key = content_type + '/' + data_hash + '/' + file_name
+ result = {key: memcache.delete(key)}
+ content_type = urllib.unquote(content_type)
+ if IMAGE_TYPES.match(content_type):
+ thumbnail_key = key + THUMB_SUFFIX
+ result[thumbnail_key] = memcache.delete(thumbnail_key)
if 'application/json' in self.request.headers.get('Accept'):
self.response.headers['Content-Type'] = 'application/json'
+ s = self.json_stringify(result)
self.response.write(s)
-
-class DownloadHandler(blobstore_handlers.BlobstoreDownloadHandler):
- def get(self, key, filename):
- if not blobstore.get(key):
- self.error(404)
- else:
- # Prevent browsers from MIME-sniffing the content-type:
- self.response.headers['X-Content-Type-Options'] = 'nosniff'
- # Cache for the expiration time:
- self.response.headers['Cache-Control'] = 'public,max-age=%d' % EXPIRATION_TIME
- # Send the file forcing a download dialog:
- self.send_blob(key, save_as=filename, content_type='application/octet-stream')
-
app = webapp2.WSGIApplication(
[
('/', UploadHandler),
- ('/([^/]+)/([^/]+)', DownloadHandler)
+ ('/(.+)/([^/]+)/([^/]+)', FileHandler)
],
- debug=True
+ debug=DEBUG
)
diff --git a/library/blueimp_upload/server/node/.gitignore b/library/blueimp_upload/server/node/.gitignore
deleted file mode 100644
index 9daa8247d..000000000
--- a/library/blueimp_upload/server/node/.gitignore
+++ /dev/null
@@ -1,2 +0,0 @@
-.DS_Store
-node_modules
diff --git a/library/blueimp_upload/server/node/package.json b/library/blueimp_upload/server/node/package.json
deleted file mode 100644
index dd38c50ca..000000000
--- a/library/blueimp_upload/server/node/package.json
+++ /dev/null
@@ -1,41 +0,0 @@
-{
- "name": "blueimp-file-upload-node",
- "version": "2.1.0",
- "title": "jQuery File Upload Node.js example",
- "description": "Node.js implementation example of a file upload handler for jQuery File Upload.",
- "keywords": [
- "file",
- "upload",
- "cross-domain",
- "cross-site",
- "node"
- ],
- "homepage": "https://github.com/blueimp/jQuery-File-Upload",
- "author": {
- "name": "Sebastian Tschan",
- "url": "https://blueimp.net"
- },
- "maintainers": [
- {
- "name": "Sebastian Tschan",
- "url": "https://blueimp.net"
- }
- ],
- "repository": {
- "type": "git",
- "url": "git://github.com/blueimp/jQuery-File-Upload.git"
- },
- "bugs": "https://github.com/blueimp/jQuery-File-Upload/issues",
- "licenses": [
- {
- "type": "MIT",
- "url": "http://www.opensource.org/licenses/MIT"
- }
- ],
- "dependencies": {
- "formidable": ">=1.0.11",
- "node-static": ">=0.6.5",
- "imagemagick": ">=0.1.3"
- },
- "main": "server.js"
-}
diff --git a/library/blueimp_upload/server/node/public/files/.gitignore b/library/blueimp_upload/server/node/public/files/.gitignore
deleted file mode 100644
index d6b7ef32c..000000000
--- a/library/blueimp_upload/server/node/public/files/.gitignore
+++ /dev/null
@@ -1,2 +0,0 @@
-*
-!.gitignore
diff --git a/library/blueimp_upload/server/node/server.js b/library/blueimp_upload/server/node/server.js
deleted file mode 100755
index 808d6ffe1..000000000
--- a/library/blueimp_upload/server/node/server.js
+++ /dev/null
@@ -1,292 +0,0 @@
-#!/usr/bin/nodejs
-/*
- * jQuery File Upload Plugin Node.js Example 2.1.2
- * https://github.com/blueimp/jQuery-File-Upload
- *
- * Copyright 2012, Sebastian Tschan
- * https://blueimp.net
- *
- * Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
- */
-
-/* jshint nomen:false */
-/* global require, __dirname, unescape, console */
-
-(function (port) {
- 'use strict';
- var path = require('path'),
- fs = require('fs'),
- // Since Node 0.8, .existsSync() moved from path to fs:
- _existsSync = fs.existsSync || path.existsSync,
- formidable = require('formidable'),
- nodeStatic = require('node-static'),
- imageMagick = require('imagemagick'),
- options = {
- tmpDir: __dirname + '/tmp',
- publicDir: __dirname + '/public',
- uploadDir: __dirname + '/public/files',
- uploadUrl: '/files/',
- maxPostSize: 11000000000, // 11 GB
- minFileSize: 1,
- maxFileSize: 10000000000, // 10 GB
- acceptFileTypes: /.+/i,
- // Files not matched by this regular expression force a download dialog,
- // to prevent executing any scripts in the context of the service domain:
- inlineFileTypes: /\.(gif|jpe?g|png)$/i,
- imageTypes: /\.(gif|jpe?g|png)$/i,
- imageVersions: {
- 'thumbnail': {
- width: 80,
- height: 80
- }
- },
- accessControl: {
- allowOrigin: '*',
- allowMethods: 'OPTIONS, HEAD, GET, POST, PUT, DELETE',
- allowHeaders: 'Content-Type, Content-Range, Content-Disposition'
- },
- /* Uncomment and edit this section to provide the service via HTTPS:
- ssl: {
- key: fs.readFileSync('/Applications/XAMPP/etc/ssl.key/server.key'),
- cert: fs.readFileSync('/Applications/XAMPP/etc/ssl.crt/server.crt')
- },
- */
- nodeStatic: {
- cache: 3600 // seconds to cache served files
- }
- },
- utf8encode = function (str) {
- return unescape(encodeURIComponent(str));
- },
- fileServer = new nodeStatic.Server(options.publicDir, options.nodeStatic),
- nameCountRegexp = /(?:(?: \(([\d]+)\))?(\.[^.]+))?$/,
- nameCountFunc = function (s, index, ext) {
- return ' (' + ((parseInt(index, 10) || 0) + 1) + ')' + (ext || '');
- },
- FileInfo = function (file) {
- this.name = file.name;
- this.size = file.size;
- this.type = file.type;
- this.deleteType = 'DELETE';
- },
- UploadHandler = function (req, res, callback) {
- this.req = req;
- this.res = res;
- this.callback = callback;
- },
- serve = function (req, res) {
- res.setHeader(
- 'Access-Control-Allow-Origin',
- options.accessControl.allowOrigin
- );
- res.setHeader(
- 'Access-Control-Allow-Methods',
- options.accessControl.allowMethods
- );
- res.setHeader(
- 'Access-Control-Allow-Headers',
- options.accessControl.allowHeaders
- );
- var handleResult = function (result, redirect) {
- if (redirect) {
- res.writeHead(302, {
- 'Location': redirect.replace(
- /%s/,
- encodeURIComponent(JSON.stringify(result))
- )
- });
- res.end();
- } else {
- res.writeHead(200, {
- 'Content-Type': req.headers.accept
- .indexOf('application/json') !== -1 ?
- 'application/json' : 'text/plain'
- });
- res.end(JSON.stringify(result));
- }
- },
- setNoCacheHeaders = function () {
- res.setHeader('Pragma', 'no-cache');
- res.setHeader('Cache-Control', 'no-store, no-cache, must-revalidate');
- res.setHeader('Content-Disposition', 'inline; filename="files.json"');
- },
- handler = new UploadHandler(req, res, handleResult);
- switch (req.method) {
- case 'OPTIONS':
- res.end();
- break;
- case 'HEAD':
- case 'GET':
- if (req.url === '/') {
- setNoCacheHeaders();
- if (req.method === 'GET') {
- handler.get();
- } else {
- res.end();
- }
- } else {
- fileServer.serve(req, res);
- }
- break;
- case 'POST':
- setNoCacheHeaders();
- handler.post();
- break;
- case 'DELETE':
- handler.destroy();
- break;
- default:
- res.statusCode = 405;
- res.end();
- }
- };
- fileServer.respond = function (pathname, status, _headers, files, stat, req, res, finish) {
- // Prevent browsers from MIME-sniffing the content-type:
- _headers['X-Content-Type-Options'] = 'nosniff';
- if (!options.inlineFileTypes.test(files[0])) {
- // Force a download dialog for unsafe file extensions:
- _headers['Content-Type'] = 'application/octet-stream';
- _headers['Content-Disposition'] = 'attachment; filename="' +
- utf8encode(path.basename(files[0])) + '"';
- }
- nodeStatic.Server.prototype.respond
- .call(this, pathname, status, _headers, files, stat, req, res, finish);
- };
- FileInfo.prototype.validate = function () {
- if (options.minFileSize && options.minFileSize > this.size) {
- this.error = 'File is too small';
- } else if (options.maxFileSize && options.maxFileSize < this.size) {
- this.error = 'File is too big';
- } else if (!options.acceptFileTypes.test(this.name)) {
- this.error = 'Filetype not allowed';
- }
- return !this.error;
- };
- FileInfo.prototype.safeName = function () {
- // Prevent directory traversal and creating hidden system files:
- this.name = path.basename(this.name).replace(/^\.+/, '');
- // Prevent overwriting existing files:
- while (_existsSync(options.uploadDir + '/' + this.name)) {
- this.name = this.name.replace(nameCountRegexp, nameCountFunc);
- }
- };
- FileInfo.prototype.initUrls = function (req) {
- if (!this.error) {
- var that = this,
- baseUrl = (options.ssl ? 'https:' : 'http:') +
- '//' + req.headers.host + options.uploadUrl;
- this.url = this.deleteUrl = baseUrl + encodeURIComponent(this.name);
- Object.keys(options.imageVersions).forEach(function (version) {
- if (_existsSync(
- options.uploadDir + '/' + version + '/' + that.name
- )) {
- that[version + 'Url'] = baseUrl + version + '/' +
- encodeURIComponent(that.name);
- }
- });
- }
- };
- UploadHandler.prototype.get = function () {
- var handler = this,
- files = [];
- fs.readdir(options.uploadDir, function (err, list) {
- list.forEach(function (name) {
- var stats = fs.statSync(options.uploadDir + '/' + name),
- fileInfo;
- if (stats.isFile() && name[0] !== '.') {
- fileInfo = new FileInfo({
- name: name,
- size: stats.size
- });
- fileInfo.initUrls(handler.req);
- files.push(fileInfo);
- }
- });
- handler.callback({files: files});
- });
- };
- UploadHandler.prototype.post = function () {
- var handler = this,
- form = new formidable.IncomingForm(),
- tmpFiles = [],
- files = [],
- map = {},
- counter = 1,
- redirect,
- finish = function () {
- counter -= 1;
- if (!counter) {
- files.forEach(function (fileInfo) {
- fileInfo.initUrls(handler.req);
- });
- handler.callback({files: files}, redirect);
- }
- };
- form.uploadDir = options.tmpDir;
- form.on('fileBegin', function (name, file) {
- tmpFiles.push(file.path);
- var fileInfo = new FileInfo(file);
- fileInfo.safeName();
- map[path.basename(file.path)] = fileInfo;
- files.push(fileInfo);
- }).on('field', function (name, value) {
- if (name === 'redirect') {
- redirect = value;
- }
- }).on('file', function (name, file) {
- var fileInfo = map[path.basename(file.path)];
- fileInfo.size = file.size;
- if (!fileInfo.validate()) {
- fs.unlink(file.path);
- return;
- }
- fs.renameSync(file.path, options.uploadDir + '/' + fileInfo.name);
- if (options.imageTypes.test(fileInfo.name)) {
- Object.keys(options.imageVersions).forEach(function (version) {
- counter += 1;
- var opts = options.imageVersions[version];
- imageMagick.resize({
- width: opts.width,
- height: opts.height,
- srcPath: options.uploadDir + '/' + fileInfo.name,
- dstPath: options.uploadDir + '/' + version + '/' +
- fileInfo.name
- }, finish);
- });
- }
- }).on('aborted', function () {
- tmpFiles.forEach(function (file) {
- fs.unlink(file);
- });
- }).on('error', function (e) {
- console.log(e);
- }).on('progress', function (bytesReceived) {
- if (bytesReceived > options.maxPostSize) {
- handler.req.connection.destroy();
- }
- }).on('end', finish).parse(handler.req);
- };
- UploadHandler.prototype.destroy = function () {
- var handler = this,
- fileName;
- if (handler.req.url.slice(0, options.uploadUrl.length) === options.uploadUrl) {
- fileName = path.basename(decodeURIComponent(handler.req.url));
- if (fileName[0] !== '.') {
- fs.unlink(options.uploadDir + '/' + fileName, function (ex) {
- Object.keys(options.imageVersions).forEach(function (version) {
- fs.unlink(options.uploadDir + '/' + version + '/' + fileName);
- });
- handler.callback({success: !ex});
- });
- return;
- }
- }
- handler.callback({success: false});
- };
- if (options.ssl) {
- require('https').createServer(options.ssl, serve).listen(port);
- } else {
- require('http').createServer(serve).listen(port);
- }
-}(8888));
diff --git a/library/blueimp_upload/server/node/tmp/.gitignore b/library/blueimp_upload/server/node/tmp/.gitignore
deleted file mode 100644
index e69de29bb..000000000
--- a/library/blueimp_upload/server/node/tmp/.gitignore
+++ /dev/null
diff --git a/library/blueimp_upload/server/php/Dockerfile b/library/blueimp_upload/server/php/Dockerfile
new file mode 100644
index 000000000..ca88d3d0d
--- /dev/null
+++ b/library/blueimp_upload/server/php/Dockerfile
@@ -0,0 +1,38 @@
+FROM php:7.0-apache
+
+# Enable the Apache Headers module:
+RUN ln -s /etc/apache2/mods-available/headers.load \
+ /etc/apache2/mods-enabled/headers.load
+
+# Enable the Apache Rewrite module:
+RUN ln -s /etc/apache2/mods-available/rewrite.load \
+ /etc/apache2/mods-enabled/rewrite.load
+
+# Install GD, Imagick and ImageMagick as image conversion options:
+RUN DEBIAN_FRONTEND=noninteractive \
+ apt-get update && apt-get install -y --no-install-recommends \
+ libpng-dev \
+ libjpeg-dev \
+ libmagickwand-dev \
+ imagemagick \
+ && pecl install \
+ imagick \
+ && docker-php-ext-enable \
+ imagick \
+ && docker-php-ext-configure \
+ gd --with-jpeg-dir=/usr/include/ \
+ && docker-php-ext-install \
+ gd \
+ # Uninstall obsolete packages:
+ && apt-get autoremove -y \
+ libpng-dev \
+ libjpeg-dev \
+ libmagickwand-dev \
+ # Remove obsolete files:
+ && apt-get clean \
+ && rm -rf \
+ /tmp/* \
+ /usr/share/doc/* \
+ /var/cache/* \
+ /var/lib/apt/lists/* \
+ /var/tmp/*
diff --git a/library/blueimp_upload/server/php/UploadHandler.php b/library/blueimp_upload/server/php/UploadHandler.php
index fb77be1d0..1380d4739 100755
--- a/library/blueimp_upload/server/php/UploadHandler.php
+++ b/library/blueimp_upload/server/php/UploadHandler.php
@@ -1,13 +1,13 @@
<?php
/*
- * jQuery File Upload Plugin PHP Class 8.1.0
+ * jQuery File Upload Plugin PHP Class
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2010, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
class UploadHandler
@@ -40,11 +40,13 @@ class UploadHandler
protected $image_objects = array();
- function __construct($options = null, $initialize = true, $error_messages = null) {
+ public function __construct($options = null, $initialize = true, $error_messages = null) {
+ $this->response = array();
$this->options = array(
- 'script_url' => $this->get_full_url().'/',
+ 'script_url' => $this->get_full_url().'/'.$this->basename($this->get_server_var('SCRIPT_NAME')),
'upload_dir' => dirname($this->get_server_var('SCRIPT_FILENAME')).'/files/',
'upload_url' => $this->get_full_url().'/files/',
+ 'input_stream' => 'php://input',
'user_dirs' => false,
'mkdir_mode' => 0755,
'param_name' => 'files',
@@ -67,6 +69,14 @@ class UploadHandler
'Content-Range',
'Content-Disposition'
),
+ // By default, allow redirects to the referer protocol+host:
+ 'redirect_allow_target' => '/^'.preg_quote(
+ parse_url($this->get_server_var('HTTP_REFERER'), PHP_URL_SCHEME)
+ .'://'
+ .parse_url($this->get_server_var('HTTP_REFERER'), PHP_URL_HOST)
+ .'/', // Trailing slash to not match subdomains by mistake
+ '/' // preg_quote delimiter param
+ ).'/',
// Enable to provide file downloads via GET requests to the PHP script:
// 1. Set to 1 to download files via readfile method through PHP
// 2. Set to 2 to send a X-Sendfile header for lighttpd/Apache
@@ -147,7 +157,8 @@ class UploadHandler
'max_width' => 80,
'max_height' => 80
)
- )
+ ),
+ 'print_response' => true
);
if ($options) {
$this->options = $options + $this->options;
@@ -167,15 +178,15 @@ class UploadHandler
$this->head();
break;
case 'GET':
- $this->get();
+ $this->get($this->options['print_response']);
break;
case 'PATCH':
case 'PUT':
case 'POST':
- $this->post();
+ $this->post($this->options['print_response']);
break;
case 'DELETE':
- $this->delete();
+ $this->delete($this->options['print_response']);
break;
default:
$this->header('HTTP/1.1 405 Method Not Allowed');
@@ -300,7 +311,7 @@ class UploadHandler
$this->get_upload_path($file_name)
);
$file->url = $this->get_download_url($file->name);
- foreach($this->options['image_versions'] as $version => $options) {
+ foreach ($this->options['image_versions'] as $version => $options) {
if (!empty($version)) {
if (is_file($this->get_upload_path($file_name, $version))) {
$file->{$version.'Url'} = $this->get_download_url(
@@ -332,14 +343,15 @@ class UploadHandler
}
protected function get_error_message($error) {
- return array_key_exists($error, $this->error_messages) ?
+ return isset($this->error_messages[$error]) ?
$this->error_messages[$error] : $error;
}
- function get_config_bytes($val) {
+ public function get_config_bytes($val) {
$val = trim($val);
$last = strtolower($val[strlen($val)-1]);
- switch($last) {
+ $val = (int)$val;
+ switch ($last) {
case 'g':
$val *= 1024;
case 'm':
@@ -355,9 +367,9 @@ class UploadHandler
$file->error = $this->get_error_message($error);
return false;
}
- $content_length = $this->fix_integer_overflow(intval(
- $this->get_server_var('CONTENT_LENGTH')
- ));
+ $content_length = $this->fix_integer_overflow(
+ (int)$this->get_server_var('CONTENT_LENGTH')
+ );
$post_max_size = $this->get_config_bytes(ini_get('post_max_size'));
if ($post_max_size && ($content_length > $post_max_size)) {
$file->error = $this->get_error_message('post_max_size');
@@ -398,6 +410,21 @@ class UploadHandler
if (($max_width || $max_height || $min_width || $min_height)
&& preg_match($this->options['image_file_types'], $file->name)) {
list($img_width, $img_height) = $this->get_image_size($uploaded_file);
+
+ // If we are auto rotating the image by default, do the checks on
+ // the correct orientation
+ if (
+ @$this->options['image_versions']['']['auto_orient'] &&
+ function_exists('exif_read_data') &&
+ ($exif = @exif_read_data($uploaded_file)) &&
+ (((int) @$exif['Orientation']) >= 5)
+ ) {
+ $tmp = $img_width;
+ $img_width = $img_height;
+ $img_height = $tmp;
+ unset($tmp);
+ }
+
}
if (!empty($img_width)) {
if ($max_width && $img_width > $max_width) {
@@ -421,7 +448,7 @@ class UploadHandler
}
protected function upcount_name_callback($matches) {
- $index = isset($matches[1]) ? intval($matches[1]) + 1 : 1;
+ $index = isset($matches[1]) ? ((int)$matches[1]) + 1 : 1;
$ext = isset($matches[2]) ? $matches[2] : '';
return ' ('.$index.')'.$ext;
}
@@ -441,8 +468,8 @@ class UploadHandler
$name = $this->upcount_name($name);
}
// Keep an existing filename if this is part of a chunked upload:
- $uploaded_bytes = $this->fix_integer_overflow(intval($content_range[1]));
- while(is_file($this->get_upload_path($name))) {
+ $uploaded_bytes = $this->fix_integer_overflow((int)$content_range[1]);
+ while (is_file($this->get_upload_path($name))) {
if ($uploaded_bytes === $this->get_file_size(
$this->get_upload_path($name))) {
break;
@@ -461,7 +488,7 @@ class UploadHandler
}
if ($this->options['correct_image_extensions'] &&
function_exists('exif_imagetype')) {
- switch(@exif_imagetype($file_path)){
+ switch (@exif_imagetype($file_path)){
case IMAGETYPE_JPEG:
$extensions = array('jpg', 'jpeg');
break;
@@ -491,7 +518,7 @@ class UploadHandler
// Remove path information and dots around the filename, to prevent uploading
// into different directories or replacing hidden system files.
// Also remove control characters and spaces (\x00..\x20) around the filename:
- $name = trim(basename(stripslashes($name)), ".\x00..\x20");
+ $name = trim($this->basename(stripslashes($name)), ".\x00..\x20");
// Use a timestamp for empty filenames:
if (!$name) {
$name = str_replace('.', '-', microtime(true));
@@ -515,10 +542,6 @@ class UploadHandler
);
}
- protected function handle_form_data($file, $index) {
- // Handle form data, e.g. $_REQUEST['description'][$index]
- }
-
protected function get_scaled_image_file_paths($file_name, $version) {
$file_path = $this->get_upload_path($file_name);
if (!empty($version)) {
@@ -601,7 +624,7 @@ class UploadHandler
if ($exif === false) {
return false;
}
- $orientation = intval(@$exif['Orientation']);
+ $orientation = (int)@$exif['Orientation'];
if ($orientation < 2 || $orientation > 8) {
return false;
}
@@ -825,7 +848,7 @@ class UploadHandler
$this->get_scaled_image_file_paths($file_name, $version);
$image = $this->imagick_get_image_object(
$file_path,
- !empty($options['no_cache'])
+ !empty($options['crop']) || !empty($options['no_cache'])
);
if ($image->getImageFormat() === 'GIF') {
// Handle animated GIFs:
@@ -955,7 +978,7 @@ class UploadHandler
return $dimensions;
}
return false;
- } catch (Exception $e) {
+ } catch (\Exception $e) {
error_log($e->getMessage());
}
}
@@ -965,7 +988,7 @@ class UploadHandler
exec($cmd, $output, $error);
if (!$error && !empty($output)) {
// image.jpg JPEG 1920x1080 1920x1080+0+0 8-bit sRGB 465KB 0.000u 0:00.000
- $infos = preg_split('/\s+/', $output[0]);
+ $infos = preg_split('/\s+/', substr($output[0], strlen($file_path)));
$dimensions = preg_split('/x/', $infos[2]);
return $dimensions;
}
@@ -1008,7 +1031,7 @@ class UploadHandler
protected function handle_image_file($file_path, $file) {
$failed_versions = array();
- foreach($this->options['image_versions'] as $version => $options) {
+ foreach ($this->options['image_versions'] as $version => $options) {
if ($this->create_scaled_image($file->name, $version, $options)) {
if (!empty($version)) {
$file->{$version.'Url'} = $this->get_download_url(
@@ -1024,7 +1047,7 @@ class UploadHandler
}
if (count($failed_versions)) {
$file->error = $this->get_error_message('image_resize')
- .' ('.implode($failed_versions,', ').')';
+ .' ('.implode($failed_versions, ', ').')';
}
// Free memory:
$this->destroy_image_object($file_path);
@@ -1035,7 +1058,7 @@ class UploadHandler
$file = new \stdClass();
$file->name = $this->get_file_name($uploaded_file, $name, $size, $type, $error,
$index, $content_range);
- $file->size = $this->fix_integer_overflow(intval($size));
+ $file->size = $this->fix_integer_overflow((int)$size);
$file->type = $type;
if ($this->validate($uploaded_file, $file, $error, $index)) {
$this->handle_form_data($file, $index);
@@ -1061,7 +1084,7 @@ class UploadHandler
// Non-multipart uploads (PUT method support)
file_put_contents(
$file_path,
- fopen('php://input', 'r'),
+ fopen($this->options['input_stream'], 'r'),
$append_file ? FILE_APPEND : 0
);
}
@@ -1102,41 +1125,33 @@ class UploadHandler
protected function body($str) {
echo $str;
}
-
+
protected function header($str) {
header($str);
}
+ protected function get_upload_data($id) {
+ return @$_FILES[$id];
+ }
+
+ protected function get_post_param($id) {
+ return @$_POST[$id];
+ }
+
+ protected function get_query_param($id) {
+ return @$_GET[$id];
+ }
+
protected function get_server_var($id) {
- return isset($_SERVER[$id]) ? $_SERVER[$id] : '';
+ return @$_SERVER[$id];
}
- protected function generate_response($content, $print_response = true) {
- if ($print_response) {
- $json = json_encode($content);
- $redirect = isset($_REQUEST['redirect']) ?
- stripslashes($_REQUEST['redirect']) : null;
- if ($redirect) {
- $this->header('Location: '.sprintf($redirect, rawurlencode($json)));
- return;
- }
- $this->head();
- if ($this->get_server_var('HTTP_CONTENT_RANGE')) {
- $files = isset($content[$this->options['param_name']]) ?
- $content[$this->options['param_name']] : null;
- if ($files && is_array($files) && is_object($files[0]) && $files[0]->size) {
- $this->header('Range: 0-'.(
- $this->fix_integer_overflow(intval($files[0]->size)) - 1
- ));
- }
- }
- $this->body($json);
- }
- return $content;
+ protected function handle_form_data($file, $index) {
+ // Handle form data, e.g. $_POST['description'][$index]
}
protected function get_version_param() {
- return isset($_GET['version']) ? basename(stripslashes($_GET['version'])) : null;
+ return $this->basename(stripslashes($this->get_query_param('version')));
}
protected function get_singular_param_name() {
@@ -1145,14 +1160,16 @@ class UploadHandler
protected function get_file_name_param() {
$name = $this->get_singular_param_name();
- return isset($_REQUEST[$name]) ? basename(stripslashes($_REQUEST[$name])) : null;
+ return $this->basename(stripslashes($this->get_query_param($name)));
}
protected function get_file_names_params() {
- $params = isset($_REQUEST[$this->options['param_name']]) ?
- $_REQUEST[$this->options['param_name']] : array();
+ $params = $this->get_query_param($this->options['param_name']);
+ if (!$params) {
+ return null;
+ }
foreach ($params as $key => $value) {
- $params[$key] = basename(stripslashes($value));
+ $params[$key] = $this->basename(stripslashes($value));
}
return $params;
}
@@ -1232,6 +1249,34 @@ class UploadHandler
.implode(', ', $this->options['access_control_allow_headers']));
}
+ public function generate_response($content, $print_response = true) {
+ $this->response = $content;
+ if ($print_response) {
+ $json = json_encode($content);
+ $redirect = stripslashes($this->get_post_param('redirect'));
+ if ($redirect && preg_match($this->options['redirect_allow_target'], $redirect)) {
+ $this->header('Location: '.sprintf($redirect, rawurlencode($json)));
+ return;
+ }
+ $this->head();
+ if ($this->get_server_var('HTTP_CONTENT_RANGE')) {
+ $files = isset($content[$this->options['param_name']]) ?
+ $content[$this->options['param_name']] : null;
+ if ($files && is_array($files) && is_object($files[0]) && $files[0]->size) {
+ $this->header('Range: 0-'.(
+ $this->fix_integer_overflow((int)$files[0]->size) - 1
+ ));
+ }
+ }
+ $this->body($json);
+ }
+ return $content;
+ }
+
+ public function get_response () {
+ return $this->response;
+ }
+
public function head() {
$this->header('Pragma: no-cache');
$this->header('Cache-Control: no-store, no-cache, must-revalidate');
@@ -1245,7 +1290,7 @@ class UploadHandler
}
public function get($print_response = true) {
- if ($print_response && isset($_GET['download'])) {
+ if ($print_response && $this->get_query_param('download')) {
return $this->download();
}
$file_name = $this->get_file_name_param();
@@ -1262,58 +1307,59 @@ class UploadHandler
}
public function post($print_response = true) {
- if (isset($_REQUEST['_method']) && $_REQUEST['_method'] === 'DELETE') {
+ if ($this->get_query_param('_method') === 'DELETE') {
return $this->delete($print_response);
}
- $upload = isset($_FILES[$this->options['param_name']]) ?
- $_FILES[$this->options['param_name']] : null;
+ $upload = $this->get_upload_data($this->options['param_name']);
// Parse the Content-Disposition header, if available:
- $file_name = $this->get_server_var('HTTP_CONTENT_DISPOSITION') ?
+ $content_disposition_header = $this->get_server_var('HTTP_CONTENT_DISPOSITION');
+ $file_name = $content_disposition_header ?
rawurldecode(preg_replace(
'/(^[^"]+")|("$)/',
'',
- $this->get_server_var('HTTP_CONTENT_DISPOSITION')
+ $content_disposition_header
)) : null;
// Parse the Content-Range header, which has the following form:
// Content-Range: bytes 0-524287/2000000
- $content_range = $this->get_server_var('HTTP_CONTENT_RANGE') ?
- preg_split('/[^0-9]+/', $this->get_server_var('HTTP_CONTENT_RANGE')) : null;
+ $content_range_header = $this->get_server_var('HTTP_CONTENT_RANGE');
+ $content_range = $content_range_header ?
+ preg_split('/[^0-9]+/', $content_range_header) : null;
$size = $content_range ? $content_range[3] : null;
$files = array();
- if ($upload && is_array($upload['tmp_name'])) {
- // param_name is an array identifier like "files[]",
- // $_FILES is a multi-dimensional array:
- foreach ($upload['tmp_name'] as $index => $value) {
+ if ($upload) {
+ if (is_array($upload['tmp_name'])) {
+ // param_name is an array identifier like "files[]",
+ // $upload is a multi-dimensional array:
+ foreach ($upload['tmp_name'] as $index => $value) {
+ $files[] = $this->handle_file_upload(
+ $upload['tmp_name'][$index],
+ $file_name ? $file_name : $upload['name'][$index],
+ $size ? $size : $upload['size'][$index],
+ $upload['type'][$index],
+ $upload['error'][$index],
+ $index,
+ $content_range
+ );
+ }
+ } else {
+ // param_name is a single object identifier like "file",
+ // $upload is a one-dimensional array:
$files[] = $this->handle_file_upload(
- $upload['tmp_name'][$index],
- $file_name ? $file_name : $upload['name'][$index],
- $size ? $size : $upload['size'][$index],
- $upload['type'][$index],
- $upload['error'][$index],
- $index,
+ isset($upload['tmp_name']) ? $upload['tmp_name'] : null,
+ $file_name ? $file_name : (isset($upload['name']) ?
+ $upload['name'] : null),
+ $size ? $size : (isset($upload['size']) ?
+ $upload['size'] : $this->get_server_var('CONTENT_LENGTH')),
+ isset($upload['type']) ?
+ $upload['type'] : $this->get_server_var('CONTENT_TYPE'),
+ isset($upload['error']) ? $upload['error'] : null,
+ null,
$content_range
);
}
- } else {
- // param_name is a single object identifier like "file",
- // $_FILES is a one-dimensional array:
- $files[] = $this->handle_file_upload(
- isset($upload['tmp_name']) ? $upload['tmp_name'] : null,
- $file_name ? $file_name : (isset($upload['name']) ?
- $upload['name'] : null),
- $size ? $size : (isset($upload['size']) ?
- $upload['size'] : $this->get_server_var('CONTENT_LENGTH')),
- isset($upload['type']) ?
- $upload['type'] : $this->get_server_var('CONTENT_TYPE'),
- isset($upload['error']) ? $upload['error'] : null,
- null,
- $content_range
- );
}
- return $this->generate_response(
- array($this->options['param_name'] => $files),
- $print_response
- );
+ $response = array($this->options['param_name'] => $files);
+ return $this->generate_response($response, $print_response);
}
public function delete($print_response = true) {
@@ -1322,11 +1368,11 @@ class UploadHandler
$file_names = array($this->get_file_name_param());
}
$response = array();
- foreach($file_names as $file_name) {
+ foreach ($file_names as $file_name) {
$file_path = $this->get_upload_path($file_name);
$success = is_file($file_path) && $file_name[0] !== '.' && unlink($file_path);
if ($success) {
- foreach($this->options['image_versions'] as $version => $options) {
+ foreach ($this->options['image_versions'] as $version => $options) {
if (!empty($version)) {
$file = $this->get_upload_path($file_name, $version);
if (is_file($file)) {
@@ -1340,4 +1386,8 @@ class UploadHandler
return $this->generate_response($response, $print_response);
}
+ protected function basename($filepath, $suffix = null) {
+ $splited = preg_split('/\//', rtrim ($filepath, '/ '));
+ return substr(basename('X'.$splited[count($splited)-1], $suffix), 1);
+ }
}
diff --git a/library/blueimp_upload/server/php/docker-compose.yml b/library/blueimp_upload/server/php/docker-compose.yml
new file mode 100644
index 000000000..691ea9caa
--- /dev/null
+++ b/library/blueimp_upload/server/php/docker-compose.yml
@@ -0,0 +1,6 @@
+apache:
+ build: ./
+ ports:
+ - "80:80"
+ volumes:
+ - "../../:/var/www/html"
diff --git a/library/blueimp_upload/server/php/files/.htaccess b/library/blueimp_upload/server/php/files/.htaccess
index 56689f0bb..6f454afb9 100644
--- a/library/blueimp_upload/server/php/files/.htaccess
+++ b/library/blueimp_upload/server/php/files/.htaccess
@@ -1,8 +1,16 @@
-# The following directives force the content-type application/octet-stream
-# and force browsers to display a download dialog for non-image files.
-# This prevents the execution of script files in the context of the website:
+# To enable the Headers module, execute the following command and reload Apache:
+# sudo a2enmod headers
+
+# The following directives prevent the execution of script files
+# in the context of the website.
+# They also force the content-type application/octet-stream and
+# force browsers to display a download dialog for non-image files.
+SetHandler default-handler
ForceType application/octet-stream
Header set Content-Disposition attachment
+
+# The following unsets the forced type and Content-Disposition headers
+# for known image files:
<FilesMatch "(?i)\.(gif|jpe?g|png)$">
ForceType none
Header unset Content-Disposition
diff --git a/library/blueimp_upload/server/php/index.php b/library/blueimp_upload/server/php/index.php
index 3ae1295ef..6caabb710 100644
--- a/library/blueimp_upload/server/php/index.php
+++ b/library/blueimp_upload/server/php/index.php
@@ -1,13 +1,13 @@
<?php
/*
- * jQuery File Upload Plugin PHP Example 5.14
+ * jQuery File Upload Plugin PHP Example
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2010, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
error_reporting(E_ALL | E_STRICT);
diff --git a/library/blueimp_upload/test/index.html b/library/blueimp_upload/test/index.html
index a04e53433..4a9a6f328 100644
--- a/library/blueimp_upload/test/index.html
+++ b/library/blueimp_upload/test/index.html
@@ -1,14 +1,14 @@
<!DOCTYPE HTML>
<!--
/*
- * jQuery File Upload Plugin Test 9.1.0
+ * jQuery File Upload Plugin Test
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2010, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
-->
<html lang="en">
@@ -20,7 +20,7 @@
<meta charset="utf-8">
<title>jQuery File Upload Plugin Test</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
-<link rel="stylesheet" href="http://codeorigin.jquery.com/qunit/qunit-1.14.0.css">
+<link rel="stylesheet" href="//codeorigin.jquery.com/qunit/qunit-1.14.0.css">
</head>
<body>
<h1 id="qunit-header">jQuery File Upload Plugin Test</h1>
@@ -36,20 +36,20 @@
<div class="col-lg-7">
<!-- The fileinput-button span is used to style the file input field as button -->
<span class="btn btn-success fileinput-button">
- <i class="fa-plus fa fa-inverse"></i>
+ <i class="icon-plus icon-white"></i>
<span>Add files...</span>
<input type="file" name="files[]" multiple>
</span>
<button type="submit" class="btn btn-primary start">
- <i class="fa-arrow-circle-o-up fa fa-inverse"></i>
+ <i class="icon-upload icon-white"></i>
<span>Start upload</span>
</button>
<button type="reset" class="btn btn-warning cancel">
- <i class="fa-ban fa fa-inverse"></i>
+ <i class="icon-ban-circle icon-white"></i>
<span>Cancel upload</span>
</button>
<button type="button" class="btn btn-danger delete">
- <i class="fa-trash-o fa fa-inverse"></i>
+ <i class="icon-trash icon-white"></i>
<span>Delete</span>
</button>
<input type="checkbox" class="toggle">
@@ -168,5 +168,5 @@ window.testUIWidget = $.blueimp.fileupload;
</script>
<script src="//code.jquery.com/qunit/qunit-1.15.0.js"></script>
<script src="test.js"></script>
-</body>
+</body>
</html>
diff --git a/library/blueimp_upload/test/test.js b/library/blueimp_upload/test/test.js
index 72d08d99e..452127567 100644
--- a/library/blueimp_upload/test/test.js
+++ b/library/blueimp_upload/test/test.js
@@ -1,12 +1,12 @@
/*
- * jQuery File Upload Plugin Test 9.4.0
+ * jQuery File Upload Plugin Test
* https://github.com/blueimp/jQuery-File-Upload
*
* Copyright 2010, Sebastian Tschan
* https://blueimp.net
*
* Licensed under the MIT license:
- * http://www.opensource.org/licenses/MIT
+ * https://opensource.org/licenses/MIT
*/
/* global $, QUnit, window, document, expect, module, test, asyncTest, start, ok, strictEqual, notStrictEqual */
@@ -83,7 +83,7 @@ $(function () {
});
test('Paste zone initialization', function () {
- ok($('#fileupload').fileupload()
+ ok($('#fileupload').fileupload({pasteZone: document})
.fileupload('option', 'pasteZone').length);
});
@@ -98,6 +98,7 @@ $(function () {
}
},
fu = $('#fileupload').fileupload({
+ pasteZone: document,
dragover: function () {
ok(true, 'Triggers dragover callback');
return false;
@@ -135,6 +136,7 @@ $(function () {
}
},
options = {
+ pasteZone: document,
dragover: function () {
ok(true, 'Triggers dragover callback');
return false;
@@ -178,6 +180,7 @@ $(function () {
}
},
fu = $('#fileupload').fileupload({
+ pasteZone: document,
dragover: function () {
ok(true, 'Triggers dragover callback');
return false;
@@ -221,6 +224,7 @@ $(function () {
}
},
fu = $('#fileupload').fileupload({
+ pasteZone: document,
dragover: function () {
ok(true, 'Triggers dragover callback');
return false;
diff --git a/library/bootstrap/css/bootstrap-grid.css b/library/bootstrap/css/bootstrap-grid.css
new file mode 100644
index 000000000..b5f77b27c
--- /dev/null
+++ b/library/bootstrap/css/bootstrap-grid.css
@@ -0,0 +1,1353 @@
+@-ms-viewport {
+ width: device-width;
+}
+
+html {
+ box-sizing: border-box;
+ -ms-overflow-style: scrollbar;
+}
+
+*,
+*::before,
+*::after {
+ box-sizing: inherit;
+}
+
+.container {
+ margin-right: auto;
+ margin-left: auto;
+ padding-right: 15px;
+ padding-left: 15px;
+ width: 100%;
+}
+
+@media (min-width: 576px) {
+ .container {
+ max-width: 540px;
+ }
+}
+
+@media (min-width: 768px) {
+ .container {
+ max-width: 720px;
+ }
+}
+
+@media (min-width: 992px) {
+ .container {
+ max-width: 960px;
+ }
+}
+
+@media (min-width: 1200px) {
+ .container {
+ max-width: 1140px;
+ }
+}
+
+.container-fluid {
+ width: 100%;
+ margin-right: auto;
+ margin-left: auto;
+ padding-right: 15px;
+ padding-left: 15px;
+ width: 100%;
+}
+
+.row {
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-wrap: wrap;
+ flex-wrap: wrap;
+ margin-right: -15px;
+ margin-left: -15px;
+}
+
+.no-gutters {
+ margin-right: 0;
+ margin-left: 0;
+}
+
+.no-gutters > .col,
+.no-gutters > [class*="col-"] {
+ padding-right: 0;
+ padding-left: 0;
+}
+
+.col-1, .col-2, .col-3, .col-4, .col-5, .col-6, .col-7, .col-8, .col-9, .col-10, .col-11, .col-12, .col,
+.col-auto, .col-sm-1, .col-sm-2, .col-sm-3, .col-sm-4, .col-sm-5, .col-sm-6, .col-sm-7, .col-sm-8, .col-sm-9, .col-sm-10, .col-sm-11, .col-sm-12, .col-sm,
+.col-sm-auto, .col-md-1, .col-md-2, .col-md-3, .col-md-4, .col-md-5, .col-md-6, .col-md-7, .col-md-8, .col-md-9, .col-md-10, .col-md-11, .col-md-12, .col-md,
+.col-md-auto, .col-lg-1, .col-lg-2, .col-lg-3, .col-lg-4, .col-lg-5, .col-lg-6, .col-lg-7, .col-lg-8, .col-lg-9, .col-lg-10, .col-lg-11, .col-lg-12, .col-lg,
+.col-lg-auto, .col-xl-1, .col-xl-2, .col-xl-3, .col-xl-4, .col-xl-5, .col-xl-6, .col-xl-7, .col-xl-8, .col-xl-9, .col-xl-10, .col-xl-11, .col-xl-12, .col-xl,
+.col-xl-auto {
+ position: relative;
+ width: 100%;
+ min-height: 1px;
+ padding-right: 15px;
+ padding-left: 15px;
+}
+
+.col {
+ -ms-flex-preferred-size: 0;
+ flex-basis: 0;
+ -ms-flex-positive: 1;
+ flex-grow: 1;
+ max-width: 100%;
+}
+
+.col-auto {
+ -ms-flex: 0 0 auto;
+ flex: 0 0 auto;
+ width: auto;
+ max-width: none;
+}
+
+.col-1 {
+ -ms-flex: 0 0 8.333333%;
+ flex: 0 0 8.333333%;
+ max-width: 8.333333%;
+}
+
+.col-2 {
+ -ms-flex: 0 0 16.666667%;
+ flex: 0 0 16.666667%;
+ max-width: 16.666667%;
+}
+
+.col-3 {
+ -ms-flex: 0 0 25%;
+ flex: 0 0 25%;
+ max-width: 25%;
+}
+
+.col-4 {
+ -ms-flex: 0 0 33.333333%;
+ flex: 0 0 33.333333%;
+ max-width: 33.333333%;
+}
+
+.col-5 {
+ -ms-flex: 0 0 41.666667%;
+ flex: 0 0 41.666667%;
+ max-width: 41.666667%;
+}
+
+.col-6 {
+ -ms-flex: 0 0 50%;
+ flex: 0 0 50%;
+ max-width: 50%;
+}
+
+.col-7 {
+ -ms-flex: 0 0 58.333333%;
+ flex: 0 0 58.333333%;
+ max-width: 58.333333%;
+}
+
+.col-8 {
+ -ms-flex: 0 0 66.666667%;
+ flex: 0 0 66.666667%;
+ max-width: 66.666667%;
+}
+
+.col-9 {
+ -ms-flex: 0 0 75%;
+ flex: 0 0 75%;
+ max-width: 75%;
+}
+
+.col-10 {
+ -ms-flex: 0 0 83.333333%;
+ flex: 0 0 83.333333%;
+ max-width: 83.333333%;
+}
+
+.col-11 {
+ -ms-flex: 0 0 91.666667%;
+ flex: 0 0 91.666667%;
+ max-width: 91.666667%;
+}
+
+.col-12 {
+ -ms-flex: 0 0 100%;
+ flex: 0 0 100%;
+ max-width: 100%;
+}
+
+.order-1 {
+ -ms-flex-order: 1;
+ order: 1;
+}
+
+.order-2 {
+ -ms-flex-order: 2;
+ order: 2;
+}
+
+.order-3 {
+ -ms-flex-order: 3;
+ order: 3;
+}
+
+.order-4 {
+ -ms-flex-order: 4;
+ order: 4;
+}
+
+.order-5 {
+ -ms-flex-order: 5;
+ order: 5;
+}
+
+.order-6 {
+ -ms-flex-order: 6;
+ order: 6;
+}
+
+.order-7 {
+ -ms-flex-order: 7;
+ order: 7;
+}
+
+.order-8 {
+ -ms-flex-order: 8;
+ order: 8;
+}
+
+.order-9 {
+ -ms-flex-order: 9;
+ order: 9;
+}
+
+.order-10 {
+ -ms-flex-order: 10;
+ order: 10;
+}
+
+.order-11 {
+ -ms-flex-order: 11;
+ order: 11;
+}
+
+.order-12 {
+ -ms-flex-order: 12;
+ order: 12;
+}
+
+@media (min-width: 576px) {
+ .col-sm {
+ -ms-flex-preferred-size: 0;
+ flex-basis: 0;
+ -ms-flex-positive: 1;
+ flex-grow: 1;
+ max-width: 100%;
+ }
+ .col-sm-auto {
+ -ms-flex: 0 0 auto;
+ flex: 0 0 auto;
+ width: auto;
+ max-width: none;
+ }
+ .col-sm-1 {
+ -ms-flex: 0 0 8.333333%;
+ flex: 0 0 8.333333%;
+ max-width: 8.333333%;
+ }
+ .col-sm-2 {
+ -ms-flex: 0 0 16.666667%;
+ flex: 0 0 16.666667%;
+ max-width: 16.666667%;
+ }
+ .col-sm-3 {
+ -ms-flex: 0 0 25%;
+ flex: 0 0 25%;
+ max-width: 25%;
+ }
+ .col-sm-4 {
+ -ms-flex: 0 0 33.333333%;
+ flex: 0 0 33.333333%;
+ max-width: 33.333333%;
+ }
+ .col-sm-5 {
+ -ms-flex: 0 0 41.666667%;
+ flex: 0 0 41.666667%;
+ max-width: 41.666667%;
+ }
+ .col-sm-6 {
+ -ms-flex: 0 0 50%;
+ flex: 0 0 50%;
+ max-width: 50%;
+ }
+ .col-sm-7 {
+ -ms-flex: 0 0 58.333333%;
+ flex: 0 0 58.333333%;
+ max-width: 58.333333%;
+ }
+ .col-sm-8 {
+ -ms-flex: 0 0 66.666667%;
+ flex: 0 0 66.666667%;
+ max-width: 66.666667%;
+ }
+ .col-sm-9 {
+ -ms-flex: 0 0 75%;
+ flex: 0 0 75%;
+ max-width: 75%;
+ }
+ .col-sm-10 {
+ -ms-flex: 0 0 83.333333%;
+ flex: 0 0 83.333333%;
+ max-width: 83.333333%;
+ }
+ .col-sm-11 {
+ -ms-flex: 0 0 91.666667%;
+ flex: 0 0 91.666667%;
+ max-width: 91.666667%;
+ }
+ .col-sm-12 {
+ -ms-flex: 0 0 100%;
+ flex: 0 0 100%;
+ max-width: 100%;
+ }
+ .order-sm-1 {
+ -ms-flex-order: 1;
+ order: 1;
+ }
+ .order-sm-2 {
+ -ms-flex-order: 2;
+ order: 2;
+ }
+ .order-sm-3 {
+ -ms-flex-order: 3;
+ order: 3;
+ }
+ .order-sm-4 {
+ -ms-flex-order: 4;
+ order: 4;
+ }
+ .order-sm-5 {
+ -ms-flex-order: 5;
+ order: 5;
+ }
+ .order-sm-6 {
+ -ms-flex-order: 6;
+ order: 6;
+ }
+ .order-sm-7 {
+ -ms-flex-order: 7;
+ order: 7;
+ }
+ .order-sm-8 {
+ -ms-flex-order: 8;
+ order: 8;
+ }
+ .order-sm-9 {
+ -ms-flex-order: 9;
+ order: 9;
+ }
+ .order-sm-10 {
+ -ms-flex-order: 10;
+ order: 10;
+ }
+ .order-sm-11 {
+ -ms-flex-order: 11;
+ order: 11;
+ }
+ .order-sm-12 {
+ -ms-flex-order: 12;
+ order: 12;
+ }
+}
+
+@media (min-width: 768px) {
+ .col-md {
+ -ms-flex-preferred-size: 0;
+ flex-basis: 0;
+ -ms-flex-positive: 1;
+ flex-grow: 1;
+ max-width: 100%;
+ }
+ .col-md-auto {
+ -ms-flex: 0 0 auto;
+ flex: 0 0 auto;
+ width: auto;
+ max-width: none;
+ }
+ .col-md-1 {
+ -ms-flex: 0 0 8.333333%;
+ flex: 0 0 8.333333%;
+ max-width: 8.333333%;
+ }
+ .col-md-2 {
+ -ms-flex: 0 0 16.666667%;
+ flex: 0 0 16.666667%;
+ max-width: 16.666667%;
+ }
+ .col-md-3 {
+ -ms-flex: 0 0 25%;
+ flex: 0 0 25%;
+ max-width: 25%;
+ }
+ .col-md-4 {
+ -ms-flex: 0 0 33.333333%;
+ flex: 0 0 33.333333%;
+ max-width: 33.333333%;
+ }
+ .col-md-5 {
+ -ms-flex: 0 0 41.666667%;
+ flex: 0 0 41.666667%;
+ max-width: 41.666667%;
+ }
+ .col-md-6 {
+ -ms-flex: 0 0 50%;
+ flex: 0 0 50%;
+ max-width: 50%;
+ }
+ .col-md-7 {
+ -ms-flex: 0 0 58.333333%;
+ flex: 0 0 58.333333%;
+ max-width: 58.333333%;
+ }
+ .col-md-8 {
+ -ms-flex: 0 0 66.666667%;
+ flex: 0 0 66.666667%;
+ max-width: 66.666667%;
+ }
+ .col-md-9 {
+ -ms-flex: 0 0 75%;
+ flex: 0 0 75%;
+ max-width: 75%;
+ }
+ .col-md-10 {
+ -ms-flex: 0 0 83.333333%;
+ flex: 0 0 83.333333%;
+ max-width: 83.333333%;
+ }
+ .col-md-11 {
+ -ms-flex: 0 0 91.666667%;
+ flex: 0 0 91.666667%;
+ max-width: 91.666667%;
+ }
+ .col-md-12 {
+ -ms-flex: 0 0 100%;
+ flex: 0 0 100%;
+ max-width: 100%;
+ }
+ .order-md-1 {
+ -ms-flex-order: 1;
+ order: 1;
+ }
+ .order-md-2 {
+ -ms-flex-order: 2;
+ order: 2;
+ }
+ .order-md-3 {
+ -ms-flex-order: 3;
+ order: 3;
+ }
+ .order-md-4 {
+ -ms-flex-order: 4;
+ order: 4;
+ }
+ .order-md-5 {
+ -ms-flex-order: 5;
+ order: 5;
+ }
+ .order-md-6 {
+ -ms-flex-order: 6;
+ order: 6;
+ }
+ .order-md-7 {
+ -ms-flex-order: 7;
+ order: 7;
+ }
+ .order-md-8 {
+ -ms-flex-order: 8;
+ order: 8;
+ }
+ .order-md-9 {
+ -ms-flex-order: 9;
+ order: 9;
+ }
+ .order-md-10 {
+ -ms-flex-order: 10;
+ order: 10;
+ }
+ .order-md-11 {
+ -ms-flex-order: 11;
+ order: 11;
+ }
+ .order-md-12 {
+ -ms-flex-order: 12;
+ order: 12;
+ }
+}
+
+@media (min-width: 992px) {
+ .col-lg {
+ -ms-flex-preferred-size: 0;
+ flex-basis: 0;
+ -ms-flex-positive: 1;
+ flex-grow: 1;
+ max-width: 100%;
+ }
+ .col-lg-auto {
+ -ms-flex: 0 0 auto;
+ flex: 0 0 auto;
+ width: auto;
+ max-width: none;
+ }
+ .col-lg-1 {
+ -ms-flex: 0 0 8.333333%;
+ flex: 0 0 8.333333%;
+ max-width: 8.333333%;
+ }
+ .col-lg-2 {
+ -ms-flex: 0 0 16.666667%;
+ flex: 0 0 16.666667%;
+ max-width: 16.666667%;
+ }
+ .col-lg-3 {
+ -ms-flex: 0 0 25%;
+ flex: 0 0 25%;
+ max-width: 25%;
+ }
+ .col-lg-4 {
+ -ms-flex: 0 0 33.333333%;
+ flex: 0 0 33.333333%;
+ max-width: 33.333333%;
+ }
+ .col-lg-5 {
+ -ms-flex: 0 0 41.666667%;
+ flex: 0 0 41.666667%;
+ max-width: 41.666667%;
+ }
+ .col-lg-6 {
+ -ms-flex: 0 0 50%;
+ flex: 0 0 50%;
+ max-width: 50%;
+ }
+ .col-lg-7 {
+ -ms-flex: 0 0 58.333333%;
+ flex: 0 0 58.333333%;
+ max-width: 58.333333%;
+ }
+ .col-lg-8 {
+ -ms-flex: 0 0 66.666667%;
+ flex: 0 0 66.666667%;
+ max-width: 66.666667%;
+ }
+ .col-lg-9 {
+ -ms-flex: 0 0 75%;
+ flex: 0 0 75%;
+ max-width: 75%;
+ }
+ .col-lg-10 {
+ -ms-flex: 0 0 83.333333%;
+ flex: 0 0 83.333333%;
+ max-width: 83.333333%;
+ }
+ .col-lg-11 {
+ -ms-flex: 0 0 91.666667%;
+ flex: 0 0 91.666667%;
+ max-width: 91.666667%;
+ }
+ .col-lg-12 {
+ -ms-flex: 0 0 100%;
+ flex: 0 0 100%;
+ max-width: 100%;
+ }
+ .order-lg-1 {
+ -ms-flex-order: 1;
+ order: 1;
+ }
+ .order-lg-2 {
+ -ms-flex-order: 2;
+ order: 2;
+ }
+ .order-lg-3 {
+ -ms-flex-order: 3;
+ order: 3;
+ }
+ .order-lg-4 {
+ -ms-flex-order: 4;
+ order: 4;
+ }
+ .order-lg-5 {
+ -ms-flex-order: 5;
+ order: 5;
+ }
+ .order-lg-6 {
+ -ms-flex-order: 6;
+ order: 6;
+ }
+ .order-lg-7 {
+ -ms-flex-order: 7;
+ order: 7;
+ }
+ .order-lg-8 {
+ -ms-flex-order: 8;
+ order: 8;
+ }
+ .order-lg-9 {
+ -ms-flex-order: 9;
+ order: 9;
+ }
+ .order-lg-10 {
+ -ms-flex-order: 10;
+ order: 10;
+ }
+ .order-lg-11 {
+ -ms-flex-order: 11;
+ order: 11;
+ }
+ .order-lg-12 {
+ -ms-flex-order: 12;
+ order: 12;
+ }
+}
+
+@media (min-width: 1200px) {
+ .col-xl {
+ -ms-flex-preferred-size: 0;
+ flex-basis: 0;
+ -ms-flex-positive: 1;
+ flex-grow: 1;
+ max-width: 100%;
+ }
+ .col-xl-auto {
+ -ms-flex: 0 0 auto;
+ flex: 0 0 auto;
+ width: auto;
+ max-width: none;
+ }
+ .col-xl-1 {
+ -ms-flex: 0 0 8.333333%;
+ flex: 0 0 8.333333%;
+ max-width: 8.333333%;
+ }
+ .col-xl-2 {
+ -ms-flex: 0 0 16.666667%;
+ flex: 0 0 16.666667%;
+ max-width: 16.666667%;
+ }
+ .col-xl-3 {
+ -ms-flex: 0 0 25%;
+ flex: 0 0 25%;
+ max-width: 25%;
+ }
+ .col-xl-4 {
+ -ms-flex: 0 0 33.333333%;
+ flex: 0 0 33.333333%;
+ max-width: 33.333333%;
+ }
+ .col-xl-5 {
+ -ms-flex: 0 0 41.666667%;
+ flex: 0 0 41.666667%;
+ max-width: 41.666667%;
+ }
+ .col-xl-6 {
+ -ms-flex: 0 0 50%;
+ flex: 0 0 50%;
+ max-width: 50%;
+ }
+ .col-xl-7 {
+ -ms-flex: 0 0 58.333333%;
+ flex: 0 0 58.333333%;
+ max-width: 58.333333%;
+ }
+ .col-xl-8 {
+ -ms-flex: 0 0 66.666667%;
+ flex: 0 0 66.666667%;
+ max-width: 66.666667%;
+ }
+ .col-xl-9 {
+ -ms-flex: 0 0 75%;
+ flex: 0 0 75%;
+ max-width: 75%;
+ }
+ .col-xl-10 {
+ -ms-flex: 0 0 83.333333%;
+ flex: 0 0 83.333333%;
+ max-width: 83.333333%;
+ }
+ .col-xl-11 {
+ -ms-flex: 0 0 91.666667%;
+ flex: 0 0 91.666667%;
+ max-width: 91.666667%;
+ }
+ .col-xl-12 {
+ -ms-flex: 0 0 100%;
+ flex: 0 0 100%;
+ max-width: 100%;
+ }
+ .order-xl-1 {
+ -ms-flex-order: 1;
+ order: 1;
+ }
+ .order-xl-2 {
+ -ms-flex-order: 2;
+ order: 2;
+ }
+ .order-xl-3 {
+ -ms-flex-order: 3;
+ order: 3;
+ }
+ .order-xl-4 {
+ -ms-flex-order: 4;
+ order: 4;
+ }
+ .order-xl-5 {
+ -ms-flex-order: 5;
+ order: 5;
+ }
+ .order-xl-6 {
+ -ms-flex-order: 6;
+ order: 6;
+ }
+ .order-xl-7 {
+ -ms-flex-order: 7;
+ order: 7;
+ }
+ .order-xl-8 {
+ -ms-flex-order: 8;
+ order: 8;
+ }
+ .order-xl-9 {
+ -ms-flex-order: 9;
+ order: 9;
+ }
+ .order-xl-10 {
+ -ms-flex-order: 10;
+ order: 10;
+ }
+ .order-xl-11 {
+ -ms-flex-order: 11;
+ order: 11;
+ }
+ .order-xl-12 {
+ -ms-flex-order: 12;
+ order: 12;
+ }
+}
+
+.flex-row {
+ -ms-flex-direction: row !important;
+ flex-direction: row !important;
+}
+
+.flex-column {
+ -ms-flex-direction: column !important;
+ flex-direction: column !important;
+}
+
+.flex-row-reverse {
+ -ms-flex-direction: row-reverse !important;
+ flex-direction: row-reverse !important;
+}
+
+.flex-column-reverse {
+ -ms-flex-direction: column-reverse !important;
+ flex-direction: column-reverse !important;
+}
+
+.flex-wrap {
+ -ms-flex-wrap: wrap !important;
+ flex-wrap: wrap !important;
+}
+
+.flex-nowrap {
+ -ms-flex-wrap: nowrap !important;
+ flex-wrap: nowrap !important;
+}
+
+.flex-wrap-reverse {
+ -ms-flex-wrap: wrap-reverse !important;
+ flex-wrap: wrap-reverse !important;
+}
+
+.justify-content-start {
+ -ms-flex-pack: start !important;
+ justify-content: flex-start !important;
+}
+
+.justify-content-end {
+ -ms-flex-pack: end !important;
+ justify-content: flex-end !important;
+}
+
+.justify-content-center {
+ -ms-flex-pack: center !important;
+ justify-content: center !important;
+}
+
+.justify-content-between {
+ -ms-flex-pack: justify !important;
+ justify-content: space-between !important;
+}
+
+.justify-content-around {
+ -ms-flex-pack: distribute !important;
+ justify-content: space-around !important;
+}
+
+.align-items-start {
+ -ms-flex-align: start !important;
+ align-items: flex-start !important;
+}
+
+.align-items-end {
+ -ms-flex-align: end !important;
+ align-items: flex-end !important;
+}
+
+.align-items-center {
+ -ms-flex-align: center !important;
+ align-items: center !important;
+}
+
+.align-items-baseline {
+ -ms-flex-align: baseline !important;
+ align-items: baseline !important;
+}
+
+.align-items-stretch {
+ -ms-flex-align: stretch !important;
+ align-items: stretch !important;
+}
+
+.align-content-start {
+ -ms-flex-line-pack: start !important;
+ align-content: flex-start !important;
+}
+
+.align-content-end {
+ -ms-flex-line-pack: end !important;
+ align-content: flex-end !important;
+}
+
+.align-content-center {
+ -ms-flex-line-pack: center !important;
+ align-content: center !important;
+}
+
+.align-content-between {
+ -ms-flex-line-pack: justify !important;
+ align-content: space-between !important;
+}
+
+.align-content-around {
+ -ms-flex-line-pack: distribute !important;
+ align-content: space-around !important;
+}
+
+.align-content-stretch {
+ -ms-flex-line-pack: stretch !important;
+ align-content: stretch !important;
+}
+
+.align-self-auto {
+ -ms-flex-item-align: auto !important;
+ align-self: auto !important;
+}
+
+.align-self-start {
+ -ms-flex-item-align: start !important;
+ align-self: flex-start !important;
+}
+
+.align-self-end {
+ -ms-flex-item-align: end !important;
+ align-self: flex-end !important;
+}
+
+.align-self-center {
+ -ms-flex-item-align: center !important;
+ align-self: center !important;
+}
+
+.align-self-baseline {
+ -ms-flex-item-align: baseline !important;
+ align-self: baseline !important;
+}
+
+.align-self-stretch {
+ -ms-flex-item-align: stretch !important;
+ align-self: stretch !important;
+}
+
+@media (min-width: 576px) {
+ .flex-sm-row {
+ -ms-flex-direction: row !important;
+ flex-direction: row !important;
+ }
+ .flex-sm-column {
+ -ms-flex-direction: column !important;
+ flex-direction: column !important;
+ }
+ .flex-sm-row-reverse {
+ -ms-flex-direction: row-reverse !important;
+ flex-direction: row-reverse !important;
+ }
+ .flex-sm-column-reverse {
+ -ms-flex-direction: column-reverse !important;
+ flex-direction: column-reverse !important;
+ }
+ .flex-sm-wrap {
+ -ms-flex-wrap: wrap !important;
+ flex-wrap: wrap !important;
+ }
+ .flex-sm-nowrap {
+ -ms-flex-wrap: nowrap !important;
+ flex-wrap: nowrap !important;
+ }
+ .flex-sm-wrap-reverse {
+ -ms-flex-wrap: wrap-reverse !important;
+ flex-wrap: wrap-reverse !important;
+ }
+ .justify-content-sm-start {
+ -ms-flex-pack: start !important;
+ justify-content: flex-start !important;
+ }
+ .justify-content-sm-end {
+ -ms-flex-pack: end !important;
+ justify-content: flex-end !important;
+ }
+ .justify-content-sm-center {
+ -ms-flex-pack: center !important;
+ justify-content: center !important;
+ }
+ .justify-content-sm-between {
+ -ms-flex-pack: justify !important;
+ justify-content: space-between !important;
+ }
+ .justify-content-sm-around {
+ -ms-flex-pack: distribute !important;
+ justify-content: space-around !important;
+ }
+ .align-items-sm-start {
+ -ms-flex-align: start !important;
+ align-items: flex-start !important;
+ }
+ .align-items-sm-end {
+ -ms-flex-align: end !important;
+ align-items: flex-end !important;
+ }
+ .align-items-sm-center {
+ -ms-flex-align: center !important;
+ align-items: center !important;
+ }
+ .align-items-sm-baseline {
+ -ms-flex-align: baseline !important;
+ align-items: baseline !important;
+ }
+ .align-items-sm-stretch {
+ -ms-flex-align: stretch !important;
+ align-items: stretch !important;
+ }
+ .align-content-sm-start {
+ -ms-flex-line-pack: start !important;
+ align-content: flex-start !important;
+ }
+ .align-content-sm-end {
+ -ms-flex-line-pack: end !important;
+ align-content: flex-end !important;
+ }
+ .align-content-sm-center {
+ -ms-flex-line-pack: center !important;
+ align-content: center !important;
+ }
+ .align-content-sm-between {
+ -ms-flex-line-pack: justify !important;
+ align-content: space-between !important;
+ }
+ .align-content-sm-around {
+ -ms-flex-line-pack: distribute !important;
+ align-content: space-around !important;
+ }
+ .align-content-sm-stretch {
+ -ms-flex-line-pack: stretch !important;
+ align-content: stretch !important;
+ }
+ .align-self-sm-auto {
+ -ms-flex-item-align: auto !important;
+ align-self: auto !important;
+ }
+ .align-self-sm-start {
+ -ms-flex-item-align: start !important;
+ align-self: flex-start !important;
+ }
+ .align-self-sm-end {
+ -ms-flex-item-align: end !important;
+ align-self: flex-end !important;
+ }
+ .align-self-sm-center {
+ -ms-flex-item-align: center !important;
+ align-self: center !important;
+ }
+ .align-self-sm-baseline {
+ -ms-flex-item-align: baseline !important;
+ align-self: baseline !important;
+ }
+ .align-self-sm-stretch {
+ -ms-flex-item-align: stretch !important;
+ align-self: stretch !important;
+ }
+}
+
+@media (min-width: 768px) {
+ .flex-md-row {
+ -ms-flex-direction: row !important;
+ flex-direction: row !important;
+ }
+ .flex-md-column {
+ -ms-flex-direction: column !important;
+ flex-direction: column !important;
+ }
+ .flex-md-row-reverse {
+ -ms-flex-direction: row-reverse !important;
+ flex-direction: row-reverse !important;
+ }
+ .flex-md-column-reverse {
+ -ms-flex-direction: column-reverse !important;
+ flex-direction: column-reverse !important;
+ }
+ .flex-md-wrap {
+ -ms-flex-wrap: wrap !important;
+ flex-wrap: wrap !important;
+ }
+ .flex-md-nowrap {
+ -ms-flex-wrap: nowrap !important;
+ flex-wrap: nowrap !important;
+ }
+ .flex-md-wrap-reverse {
+ -ms-flex-wrap: wrap-reverse !important;
+ flex-wrap: wrap-reverse !important;
+ }
+ .justify-content-md-start {
+ -ms-flex-pack: start !important;
+ justify-content: flex-start !important;
+ }
+ .justify-content-md-end {
+ -ms-flex-pack: end !important;
+ justify-content: flex-end !important;
+ }
+ .justify-content-md-center {
+ -ms-flex-pack: center !important;
+ justify-content: center !important;
+ }
+ .justify-content-md-between {
+ -ms-flex-pack: justify !important;
+ justify-content: space-between !important;
+ }
+ .justify-content-md-around {
+ -ms-flex-pack: distribute !important;
+ justify-content: space-around !important;
+ }
+ .align-items-md-start {
+ -ms-flex-align: start !important;
+ align-items: flex-start !important;
+ }
+ .align-items-md-end {
+ -ms-flex-align: end !important;
+ align-items: flex-end !important;
+ }
+ .align-items-md-center {
+ -ms-flex-align: center !important;
+ align-items: center !important;
+ }
+ .align-items-md-baseline {
+ -ms-flex-align: baseline !important;
+ align-items: baseline !important;
+ }
+ .align-items-md-stretch {
+ -ms-flex-align: stretch !important;
+ align-items: stretch !important;
+ }
+ .align-content-md-start {
+ -ms-flex-line-pack: start !important;
+ align-content: flex-start !important;
+ }
+ .align-content-md-end {
+ -ms-flex-line-pack: end !important;
+ align-content: flex-end !important;
+ }
+ .align-content-md-center {
+ -ms-flex-line-pack: center !important;
+ align-content: center !important;
+ }
+ .align-content-md-between {
+ -ms-flex-line-pack: justify !important;
+ align-content: space-between !important;
+ }
+ .align-content-md-around {
+ -ms-flex-line-pack: distribute !important;
+ align-content: space-around !important;
+ }
+ .align-content-md-stretch {
+ -ms-flex-line-pack: stretch !important;
+ align-content: stretch !important;
+ }
+ .align-self-md-auto {
+ -ms-flex-item-align: auto !important;
+ align-self: auto !important;
+ }
+ .align-self-md-start {
+ -ms-flex-item-align: start !important;
+ align-self: flex-start !important;
+ }
+ .align-self-md-end {
+ -ms-flex-item-align: end !important;
+ align-self: flex-end !important;
+ }
+ .align-self-md-center {
+ -ms-flex-item-align: center !important;
+ align-self: center !important;
+ }
+ .align-self-md-baseline {
+ -ms-flex-item-align: baseline !important;
+ align-self: baseline !important;
+ }
+ .align-self-md-stretch {
+ -ms-flex-item-align: stretch !important;
+ align-self: stretch !important;
+ }
+}
+
+@media (min-width: 992px) {
+ .flex-lg-row {
+ -ms-flex-direction: row !important;
+ flex-direction: row !important;
+ }
+ .flex-lg-column {
+ -ms-flex-direction: column !important;
+ flex-direction: column !important;
+ }
+ .flex-lg-row-reverse {
+ -ms-flex-direction: row-reverse !important;
+ flex-direction: row-reverse !important;
+ }
+ .flex-lg-column-reverse {
+ -ms-flex-direction: column-reverse !important;
+ flex-direction: column-reverse !important;
+ }
+ .flex-lg-wrap {
+ -ms-flex-wrap: wrap !important;
+ flex-wrap: wrap !important;
+ }
+ .flex-lg-nowrap {
+ -ms-flex-wrap: nowrap !important;
+ flex-wrap: nowrap !important;
+ }
+ .flex-lg-wrap-reverse {
+ -ms-flex-wrap: wrap-reverse !important;
+ flex-wrap: wrap-reverse !important;
+ }
+ .justify-content-lg-start {
+ -ms-flex-pack: start !important;
+ justify-content: flex-start !important;
+ }
+ .justify-content-lg-end {
+ -ms-flex-pack: end !important;
+ justify-content: flex-end !important;
+ }
+ .justify-content-lg-center {
+ -ms-flex-pack: center !important;
+ justify-content: center !important;
+ }
+ .justify-content-lg-between {
+ -ms-flex-pack: justify !important;
+ justify-content: space-between !important;
+ }
+ .justify-content-lg-around {
+ -ms-flex-pack: distribute !important;
+ justify-content: space-around !important;
+ }
+ .align-items-lg-start {
+ -ms-flex-align: start !important;
+ align-items: flex-start !important;
+ }
+ .align-items-lg-end {
+ -ms-flex-align: end !important;
+ align-items: flex-end !important;
+ }
+ .align-items-lg-center {
+ -ms-flex-align: center !important;
+ align-items: center !important;
+ }
+ .align-items-lg-baseline {
+ -ms-flex-align: baseline !important;
+ align-items: baseline !important;
+ }
+ .align-items-lg-stretch {
+ -ms-flex-align: stretch !important;
+ align-items: stretch !important;
+ }
+ .align-content-lg-start {
+ -ms-flex-line-pack: start !important;
+ align-content: flex-start !important;
+ }
+ .align-content-lg-end {
+ -ms-flex-line-pack: end !important;
+ align-content: flex-end !important;
+ }
+ .align-content-lg-center {
+ -ms-flex-line-pack: center !important;
+ align-content: center !important;
+ }
+ .align-content-lg-between {
+ -ms-flex-line-pack: justify !important;
+ align-content: space-between !important;
+ }
+ .align-content-lg-around {
+ -ms-flex-line-pack: distribute !important;
+ align-content: space-around !important;
+ }
+ .align-content-lg-stretch {
+ -ms-flex-line-pack: stretch !important;
+ align-content: stretch !important;
+ }
+ .align-self-lg-auto {
+ -ms-flex-item-align: auto !important;
+ align-self: auto !important;
+ }
+ .align-self-lg-start {
+ -ms-flex-item-align: start !important;
+ align-self: flex-start !important;
+ }
+ .align-self-lg-end {
+ -ms-flex-item-align: end !important;
+ align-self: flex-end !important;
+ }
+ .align-self-lg-center {
+ -ms-flex-item-align: center !important;
+ align-self: center !important;
+ }
+ .align-self-lg-baseline {
+ -ms-flex-item-align: baseline !important;
+ align-self: baseline !important;
+ }
+ .align-self-lg-stretch {
+ -ms-flex-item-align: stretch !important;
+ align-self: stretch !important;
+ }
+}
+
+@media (min-width: 1200px) {
+ .flex-xl-row {
+ -ms-flex-direction: row !important;
+ flex-direction: row !important;
+ }
+ .flex-xl-column {
+ -ms-flex-direction: column !important;
+ flex-direction: column !important;
+ }
+ .flex-xl-row-reverse {
+ -ms-flex-direction: row-reverse !important;
+ flex-direction: row-reverse !important;
+ }
+ .flex-xl-column-reverse {
+ -ms-flex-direction: column-reverse !important;
+ flex-direction: column-reverse !important;
+ }
+ .flex-xl-wrap {
+ -ms-flex-wrap: wrap !important;
+ flex-wrap: wrap !important;
+ }
+ .flex-xl-nowrap {
+ -ms-flex-wrap: nowrap !important;
+ flex-wrap: nowrap !important;
+ }
+ .flex-xl-wrap-reverse {
+ -ms-flex-wrap: wrap-reverse !important;
+ flex-wrap: wrap-reverse !important;
+ }
+ .justify-content-xl-start {
+ -ms-flex-pack: start !important;
+ justify-content: flex-start !important;
+ }
+ .justify-content-xl-end {
+ -ms-flex-pack: end !important;
+ justify-content: flex-end !important;
+ }
+ .justify-content-xl-center {
+ -ms-flex-pack: center !important;
+ justify-content: center !important;
+ }
+ .justify-content-xl-between {
+ -ms-flex-pack: justify !important;
+ justify-content: space-between !important;
+ }
+ .justify-content-xl-around {
+ -ms-flex-pack: distribute !important;
+ justify-content: space-around !important;
+ }
+ .align-items-xl-start {
+ -ms-flex-align: start !important;
+ align-items: flex-start !important;
+ }
+ .align-items-xl-end {
+ -ms-flex-align: end !important;
+ align-items: flex-end !important;
+ }
+ .align-items-xl-center {
+ -ms-flex-align: center !important;
+ align-items: center !important;
+ }
+ .align-items-xl-baseline {
+ -ms-flex-align: baseline !important;
+ align-items: baseline !important;
+ }
+ .align-items-xl-stretch {
+ -ms-flex-align: stretch !important;
+ align-items: stretch !important;
+ }
+ .align-content-xl-start {
+ -ms-flex-line-pack: start !important;
+ align-content: flex-start !important;
+ }
+ .align-content-xl-end {
+ -ms-flex-line-pack: end !important;
+ align-content: flex-end !important;
+ }
+ .align-content-xl-center {
+ -ms-flex-line-pack: center !important;
+ align-content: center !important;
+ }
+ .align-content-xl-between {
+ -ms-flex-line-pack: justify !important;
+ align-content: space-between !important;
+ }
+ .align-content-xl-around {
+ -ms-flex-line-pack: distribute !important;
+ align-content: space-around !important;
+ }
+ .align-content-xl-stretch {
+ -ms-flex-line-pack: stretch !important;
+ align-content: stretch !important;
+ }
+ .align-self-xl-auto {
+ -ms-flex-item-align: auto !important;
+ align-self: auto !important;
+ }
+ .align-self-xl-start {
+ -ms-flex-item-align: start !important;
+ align-self: flex-start !important;
+ }
+ .align-self-xl-end {
+ -ms-flex-item-align: end !important;
+ align-self: flex-end !important;
+ }
+ .align-self-xl-center {
+ -ms-flex-item-align: center !important;
+ align-self: center !important;
+ }
+ .align-self-xl-baseline {
+ -ms-flex-item-align: baseline !important;
+ align-self: baseline !important;
+ }
+ .align-self-xl-stretch {
+ -ms-flex-item-align: stretch !important;
+ align-self: stretch !important;
+ }
+}
+/*# sourceMappingURL=bootstrap-grid.css.map */ \ No newline at end of file
diff --git a/library/bootstrap/css/bootstrap-grid.css.map b/library/bootstrap/css/bootstrap-grid.css.map
new file mode 100644
index 000000000..a5145bdb0
--- /dev/null
+++ b/library/bootstrap/css/bootstrap-grid.css.map
@@ -0,0 +1 @@
+{"version":3,"sources":["../../scss/bootstrap-grid.scss","bootstrap-grid.css","../../scss/_grid.scss","../../scss/mixins/_grid.scss","../../scss/mixins/_breakpoints.scss","../../scss/_variables.scss","../../scss/mixins/_grid-framework.scss","../../scss/utilities/_flex.scss"],"names":[],"mappings":"AAUE;EAAgB,oBAAmB;CCRpC;;ADWD;EACE,uBAAsB;EACtB,8BAA6B;CAC9B;;AAED;;;EAGE,oBAAmB;CACpB;;AEjBC;ECAA,mBAAkB;EAClB,kBAAiB;EACjB,oBAAuC;EACvC,mBAAuC;EACvC,YAAW;CDDV;;AEgDC;EFnDF;ICYI,iBE8KK;GHvLR;CDmBF;;AG6BG;EFnDF;ICYI,iBE+KK;GHxLR;CDyBF;;AGuBG;EFnDF;ICYI,iBEgLK;GHzLR;CD+BF;;AGiBG;EFnDF;ICYI,kBEiLM;GH1LT;CDqCF;;AC5BC;EACE,YAAW;ECbb,mBAAkB;EAClB,kBAAiB;EACjB,oBAAuC;EACvC,mBAAuC;EACvC,YAAW;CDWV;;AAQD;ECLA,qBAAa;EAAb,cAAa;EACb,oBAAe;MAAf,gBAAe;EACf,oBAAuC;EACvC,mBAAuC;CDItC;;AAID;EACE,gBAAe;EACf,eAAc;CAOf;;AATD;;EAMI,iBAAgB;EAChB,gBAAe;CAChB;;AInCH;;;;;;EACE,mBAAkB;EAClB,YAAW;EACX,gBAAe;EACf,oBAA4B;EAC5B,mBAA4B;CAC7B;;AAkBG;EACE,2BAAa;MAAb,cAAa;EACb,qBAAY;MAAZ,aAAY;EACZ,gBAAe;CAChB;;AACD;EACE,mBAAc;MAAd,eAAc;EACd,YAAW;EACX,gBAAe;CAChB;;AAGC;EHFN,wBAAsC;MAAtC,oBAAsC;EAItC,qBAAuC;CGAhC;;AAFD;EHFN,yBAAsC;MAAtC,qBAAsC;EAItC,sBAAuC;CGAhC;;AAFD;EHFN,kBAAsC;MAAtC,cAAsC;EAItC,eAAuC;CGAhC;;AAFD;EHFN,yBAAsC;MAAtC,qBAAsC;EAItC,sBAAuC;CGAhC;;AAFD;EHFN,yBAAsC;MAAtC,qBAAsC;EAItC,sBAAuC;CGAhC;;AAFD;EHFN,kBAAsC;MAAtC,cAAsC;EAItC,eAAuC;CGAhC;;AAFD;EHFN,yBAAsC;MAAtC,qBAAsC;EAItC,sBAAuC;CGAhC;;AAFD;EHFN,yBAAsC;MAAtC,qBAAsC;EAItC,sBAAuC;CGAhC;;AAFD;EHFN,kBAAsC;MAAtC,cAAsC;EAItC,eAAuC;CGAhC;;AAFD;EHFN,yBAAsC;MAAtC,qBAAsC;EAItC,sBAAuC;CGAhC;;AAFD;EHFN,yBAAsC;MAAtC,qBAAsC;EAItC,sBAAuC;CGAhC;;AAFD;EHFN,mBAAsC;MAAtC,eAAsC;EAItC,gBAAuC;CGAhC;;AAID;EACE,kBAFU;MAEV,SAFU;CAGX;;AAFD;EACE,kBAFU;MAEV,SAFU;CAGX;;AAFD;EACE,kBAFU;MAEV,SAFU;CAGX;;AAFD;EACE,kBAFU;MAEV,SAFU;CAGX;;AAFD;EACE,kBAFU;MAEV,SAFU;CAGX;;AAFD;EACE,kBAFU;MAEV,SAFU;CAGX;;AAFD;EACE,kBAFU;MAEV,SAFU;CAGX;;AAFD;EACE,kBAFU;MAEV,SAFU;CAGX;;AAFD;EACE,kBAFU;MAEV,SAFU;CAGX;;AAFD;EACE,mBAFU;MAEV,UAFU;CAGX;;AAFD;EACE,mBAFU;MAEV,UAFU;CAGX;;AAFD;EACE,mBAFU;MAEV,UAFU;CAGX;;AFKL;EEzBE;IACE,2BAAa;QAAb,cAAa;IACb,qBAAY;QAAZ,aAAY;IACZ,gBAAe;GAChB;EACD;IACE,mBAAc;QAAd,eAAc;IACd,YAAW;IACX,gBAAe;GAChB;EAGC;IHFN,wBAAsC;QAAtC,oBAAsC;IAItC,qBAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,mBAAsC;QAAtC,eAAsC;IAItC,gBAAuC;GGAhC;EAID;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;CL2PR;;AGtPG;EEzBE;IACE,2BAAa;QAAb,cAAa;IACb,qBAAY;QAAZ,aAAY;IACZ,gBAAe;GAChB;EACD;IACE,mBAAc;QAAd,eAAc;IACd,YAAW;IACX,gBAAe;GAChB;EAGC;IHFN,wBAAsC;QAAtC,oBAAsC;IAItC,qBAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,mBAAsC;QAAtC,eAAsC;IAItC,gBAAuC;GGAhC;EAID;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;CL4VR;;AGvVG;EEzBE;IACE,2BAAa;QAAb,cAAa;IACb,qBAAY;QAAZ,aAAY;IACZ,gBAAe;GAChB;EACD;IACE,mBAAc;QAAd,eAAc;IACd,YAAW;IACX,gBAAe;GAChB;EAGC;IHFN,wBAAsC;QAAtC,oBAAsC;IAItC,qBAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,mBAAsC;QAAtC,eAAsC;IAItC,gBAAuC;GGAhC;EAID;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;CL6bR;;AGxbG;EEzBE;IACE,2BAAa;QAAb,cAAa;IACb,qBAAY;QAAZ,aAAY;IACZ,gBAAe;GAChB;EACD;IACE,mBAAc;QAAd,eAAc;IACd,YAAW;IACX,gBAAe;GAChB;EAGC;IHFN,wBAAsC;QAAtC,oBAAsC;IAItC,qBAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GGAhC;EAFD;IHFN,mBAAsC;QAAtC,eAAsC;IAItC,gBAAuC;GGAhC;EAID;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;CL8hBR;;AMzkBG;EAAgC,mCAA8B;MAA9B,+BAA8B;CAAK;;AACnE;EAAgC,sCAAiC;MAAjC,kCAAiC;CAAK;;AACtE;EAAgC,2CAAsC;MAAtC,uCAAsC;CAAK;;AAC3E;EAAgC,8CAAyC;MAAzC,0CAAyC;CAAK;;AAE9E;EAA8B,+BAA0B;MAA1B,2BAA0B;CAAK;;AAC7D;EAA8B,iCAA4B;MAA5B,6BAA4B;CAAK;;AAC/D;EAA8B,uCAAkC;MAAlC,mCAAkC;CAAK;;AAErE;EAAoC,gCAAsC;MAAtC,uCAAsC;CAAK;;AAC/E;EAAoC,8BAAoC;MAApC,qCAAoC;CAAK;;AAC7E;EAAoC,iCAAkC;MAAlC,mCAAkC;CAAK;;AAC3E;EAAoC,kCAAyC;MAAzC,0CAAyC;CAAK;;AAClF;EAAoC,qCAAwC;MAAxC,yCAAwC;CAAK;;AAEjF;EAAiC,iCAAkC;MAAlC,mCAAkC;CAAK;;AACxE;EAAiC,+BAAgC;MAAhC,iCAAgC;CAAK;;AACtE;EAAiC,kCAA8B;MAA9B,+BAA8B;CAAK;;AACpE;EAAiC,oCAAgC;MAAhC,iCAAgC;CAAK;;AACtE;EAAiC,mCAA+B;MAA/B,gCAA+B;CAAK;;AAErE;EAAkC,qCAAoC;MAApC,qCAAoC;CAAK;;AAC3E;EAAkC,mCAAkC;MAAlC,mCAAkC;CAAK;;AACzE;EAAkC,sCAAgC;MAAhC,iCAAgC;CAAK;;AACvE;EAAkC,uCAAuC;MAAvC,wCAAuC;CAAK;;AAC9E;EAAkC,0CAAsC;MAAtC,uCAAsC;CAAK;;AAC7E;EAAkC,uCAAiC;MAAjC,kCAAiC;CAAK;;AAExE;EAAgC,qCAA2B;MAA3B,4BAA2B;CAAK;;AAChE;EAAgC,sCAAiC;MAAjC,kCAAiC;CAAK;;AACtE;EAAgC,oCAA+B;MAA/B,gCAA+B;CAAK;;AACpE;EAAgC,uCAA6B;MAA7B,8BAA6B;CAAK;;AAClE;EAAgC,yCAA+B;MAA/B,gCAA+B;CAAK;;AACpE;EAAgC,wCAA8B;MAA9B,+BAA8B;CAAK;;AHenE;EGhDA;IAAgC,mCAA8B;QAA9B,+BAA8B;GAAK;EACnE;IAAgC,sCAAiC;QAAjC,kCAAiC;GAAK;EACtE;IAAgC,2CAAsC;QAAtC,uCAAsC;GAAK;EAC3E;IAAgC,8CAAyC;QAAzC,0CAAyC;GAAK;EAE9E;IAA8B,+BAA0B;QAA1B,2BAA0B;GAAK;EAC7D;IAA8B,iCAA4B;QAA5B,6BAA4B;GAAK;EAC/D;IAA8B,uCAAkC;QAAlC,mCAAkC;GAAK;EAErE;IAAoC,gCAAsC;QAAtC,uCAAsC;GAAK;EAC/E;IAAoC,8BAAoC;QAApC,qCAAoC;GAAK;EAC7E;IAAoC,iCAAkC;QAAlC,mCAAkC;GAAK;EAC3E;IAAoC,kCAAyC;QAAzC,0CAAyC;GAAK;EAClF;IAAoC,qCAAwC;QAAxC,yCAAwC;GAAK;EAEjF;IAAiC,iCAAkC;QAAlC,mCAAkC;GAAK;EACxE;IAAiC,+BAAgC;QAAhC,iCAAgC;GAAK;EACtE;IAAiC,kCAA8B;QAA9B,+BAA8B;GAAK;EACpE;IAAiC,oCAAgC;QAAhC,iCAAgC;GAAK;EACtE;IAAiC,mCAA+B;QAA/B,gCAA+B;GAAK;EAErE;IAAkC,qCAAoC;QAApC,qCAAoC;GAAK;EAC3E;IAAkC,mCAAkC;QAAlC,mCAAkC;GAAK;EACzE;IAAkC,sCAAgC;QAAhC,iCAAgC;GAAK;EACvE;IAAkC,uCAAuC;QAAvC,wCAAuC;GAAK;EAC9E;IAAkC,0CAAsC;QAAtC,uCAAsC;GAAK;EAC7E;IAAkC,uCAAiC;QAAjC,kCAAiC;GAAK;EAExE;IAAgC,qCAA2B;QAA3B,4BAA2B;GAAK;EAChE;IAAgC,sCAAiC;QAAjC,kCAAiC;GAAK;EACtE;IAAgC,oCAA+B;QAA/B,gCAA+B;GAAK;EACpE;IAAgC,uCAA6B;QAA7B,8BAA6B;GAAK;EAClE;IAAgC,yCAA+B;QAA/B,gCAA+B;GAAK;EACpE;IAAgC,wCAA8B;QAA9B,+BAA8B;GAAK;CNsvBtE;;AGvuBG;EGhDA;IAAgC,mCAA8B;QAA9B,+BAA8B;GAAK;EACnE;IAAgC,sCAAiC;QAAjC,kCAAiC;GAAK;EACtE;IAAgC,2CAAsC;QAAtC,uCAAsC;GAAK;EAC3E;IAAgC,8CAAyC;QAAzC,0CAAyC;GAAK;EAE9E;IAA8B,+BAA0B;QAA1B,2BAA0B;GAAK;EAC7D;IAA8B,iCAA4B;QAA5B,6BAA4B;GAAK;EAC/D;IAA8B,uCAAkC;QAAlC,mCAAkC;GAAK;EAErE;IAAoC,gCAAsC;QAAtC,uCAAsC;GAAK;EAC/E;IAAoC,8BAAoC;QAApC,qCAAoC;GAAK;EAC7E;IAAoC,iCAAkC;QAAlC,mCAAkC;GAAK;EAC3E;IAAoC,kCAAyC;QAAzC,0CAAyC;GAAK;EAClF;IAAoC,qCAAwC;QAAxC,yCAAwC;GAAK;EAEjF;IAAiC,iCAAkC;QAAlC,mCAAkC;GAAK;EACxE;IAAiC,+BAAgC;QAAhC,iCAAgC;GAAK;EACtE;IAAiC,kCAA8B;QAA9B,+BAA8B;GAAK;EACpE;IAAiC,oCAAgC;QAAhC,iCAAgC;GAAK;EACtE;IAAiC,mCAA+B;QAA/B,gCAA+B;GAAK;EAErE;IAAkC,qCAAoC;QAApC,qCAAoC;GAAK;EAC3E;IAAkC,mCAAkC;QAAlC,mCAAkC;GAAK;EACzE;IAAkC,sCAAgC;QAAhC,iCAAgC;GAAK;EACvE;IAAkC,uCAAuC;QAAvC,wCAAuC;GAAK;EAC9E;IAAkC,0CAAsC;QAAtC,uCAAsC;GAAK;EAC7E;IAAkC,uCAAiC;QAAjC,kCAAiC;GAAK;EAExE;IAAgC,qCAA2B;QAA3B,4BAA2B;GAAK;EAChE;IAAgC,sCAAiC;QAAjC,kCAAiC;GAAK;EACtE;IAAgC,oCAA+B;QAA/B,gCAA+B;GAAK;EACpE;IAAgC,uCAA6B;QAA7B,8BAA6B;GAAK;EAClE;IAAgC,yCAA+B;QAA/B,gCAA+B;GAAK;EACpE;IAAgC,wCAA8B;QAA9B,+BAA8B;GAAK;CNg1BtE;;AGj0BG;EGhDA;IAAgC,mCAA8B;QAA9B,+BAA8B;GAAK;EACnE;IAAgC,sCAAiC;QAAjC,kCAAiC;GAAK;EACtE;IAAgC,2CAAsC;QAAtC,uCAAsC;GAAK;EAC3E;IAAgC,8CAAyC;QAAzC,0CAAyC;GAAK;EAE9E;IAA8B,+BAA0B;QAA1B,2BAA0B;GAAK;EAC7D;IAA8B,iCAA4B;QAA5B,6BAA4B;GAAK;EAC/D;IAA8B,uCAAkC;QAAlC,mCAAkC;GAAK;EAErE;IAAoC,gCAAsC;QAAtC,uCAAsC;GAAK;EAC/E;IAAoC,8BAAoC;QAApC,qCAAoC;GAAK;EAC7E;IAAoC,iCAAkC;QAAlC,mCAAkC;GAAK;EAC3E;IAAoC,kCAAyC;QAAzC,0CAAyC;GAAK;EAClF;IAAoC,qCAAwC;QAAxC,yCAAwC;GAAK;EAEjF;IAAiC,iCAAkC;QAAlC,mCAAkC;GAAK;EACxE;IAAiC,+BAAgC;QAAhC,iCAAgC;GAAK;EACtE;IAAiC,kCAA8B;QAA9B,+BAA8B;GAAK;EACpE;IAAiC,oCAAgC;QAAhC,iCAAgC;GAAK;EACtE;IAAiC,mCAA+B;QAA/B,gCAA+B;GAAK;EAErE;IAAkC,qCAAoC;QAApC,qCAAoC;GAAK;EAC3E;IAAkC,mCAAkC;QAAlC,mCAAkC;GAAK;EACzE;IAAkC,sCAAgC;QAAhC,iCAAgC;GAAK;EACvE;IAAkC,uCAAuC;QAAvC,wCAAuC;GAAK;EAC9E;IAAkC,0CAAsC;QAAtC,uCAAsC;GAAK;EAC7E;IAAkC,uCAAiC;QAAjC,kCAAiC;GAAK;EAExE;IAAgC,qCAA2B;QAA3B,4BAA2B;GAAK;EAChE;IAAgC,sCAAiC;QAAjC,kCAAiC;GAAK;EACtE;IAAgC,oCAA+B;QAA/B,gCAA+B;GAAK;EACpE;IAAgC,uCAA6B;QAA7B,8BAA6B;GAAK;EAClE;IAAgC,yCAA+B;QAA/B,gCAA+B;GAAK;EACpE;IAAgC,wCAA8B;QAA9B,+BAA8B;GAAK;CN06BtE;;AG35BG;EGhDA;IAAgC,mCAA8B;QAA9B,+BAA8B;GAAK;EACnE;IAAgC,sCAAiC;QAAjC,kCAAiC;GAAK;EACtE;IAAgC,2CAAsC;QAAtC,uCAAsC;GAAK;EAC3E;IAAgC,8CAAyC;QAAzC,0CAAyC;GAAK;EAE9E;IAA8B,+BAA0B;QAA1B,2BAA0B;GAAK;EAC7D;IAA8B,iCAA4B;QAA5B,6BAA4B;GAAK;EAC/D;IAA8B,uCAAkC;QAAlC,mCAAkC;GAAK;EAErE;IAAoC,gCAAsC;QAAtC,uCAAsC;GAAK;EAC/E;IAAoC,8BAAoC;QAApC,qCAAoC;GAAK;EAC7E;IAAoC,iCAAkC;QAAlC,mCAAkC;GAAK;EAC3E;IAAoC,kCAAyC;QAAzC,0CAAyC;GAAK;EAClF;IAAoC,qCAAwC;QAAxC,yCAAwC;GAAK;EAEjF;IAAiC,iCAAkC;QAAlC,mCAAkC;GAAK;EACxE;IAAiC,+BAAgC;QAAhC,iCAAgC;GAAK;EACtE;IAAiC,kCAA8B;QAA9B,+BAA8B;GAAK;EACpE;IAAiC,oCAAgC;QAAhC,iCAAgC;GAAK;EACtE;IAAiC,mCAA+B;QAA/B,gCAA+B;GAAK;EAErE;IAAkC,qCAAoC;QAApC,qCAAoC;GAAK;EAC3E;IAAkC,mCAAkC;QAAlC,mCAAkC;GAAK;EACzE;IAAkC,sCAAgC;QAAhC,iCAAgC;GAAK;EACvE;IAAkC,uCAAuC;QAAvC,wCAAuC;GAAK;EAC9E;IAAkC,0CAAsC;QAAtC,uCAAsC;GAAK;EAC7E;IAAkC,uCAAiC;QAAjC,kCAAiC;GAAK;EAExE;IAAgC,qCAA2B;QAA3B,4BAA2B;GAAK;EAChE;IAAgC,sCAAiC;QAAjC,kCAAiC;GAAK;EACtE;IAAgC,oCAA+B;QAA/B,gCAA+B;GAAK;EACpE;IAAgC,uCAA6B;QAA7B,8BAA6B;GAAK;EAClE;IAAgC,yCAA+B;QAA/B,gCAA+B;GAAK;EACpE;IAAgC,wCAA8B;QAA9B,+BAA8B;GAAK;CNogCtE","file":"bootstrap-grid.css","sourcesContent":["// Bootstrap Grid only\n//\n// Includes relevant variables and mixins for the flexbox grid\n// system, as well as the generated predefined classes (e.g., `.col-sm-4`).\n\n//\n// Box sizing, responsive, and more\n//\n\n@at-root {\n @-ms-viewport { width: device-width; }\n}\n\nhtml {\n box-sizing: border-box;\n -ms-overflow-style: scrollbar;\n}\n\n*,\n*::before,\n*::after {\n box-sizing: inherit;\n}\n\n@import \"functions\";\n@import \"variables\";\n\n//\n// Grid mixins\n//\n\n@import \"mixins/breakpoints\";\n@import \"mixins/grid-framework\";\n@import \"mixins/grid\";\n\n@import \"grid\";\n@import \"utilities/flex\";\n","@-ms-viewport {\n width: device-width;\n}\n\nhtml {\n box-sizing: border-box;\n -ms-overflow-style: scrollbar;\n}\n\n*,\n*::before,\n*::after {\n box-sizing: inherit;\n}\n\n.container {\n margin-right: auto;\n margin-left: auto;\n padding-right: 15px;\n padding-left: 15px;\n width: 100%;\n}\n\n@media (min-width: 576px) {\n .container {\n max-width: 540px;\n }\n}\n\n@media (min-width: 768px) {\n .container {\n max-width: 720px;\n }\n}\n\n@media (min-width: 992px) {\n .container {\n max-width: 960px;\n }\n}\n\n@media (min-width: 1200px) {\n .container {\n max-width: 1140px;\n }\n}\n\n.container-fluid {\n width: 100%;\n margin-right: auto;\n margin-left: auto;\n padding-right: 15px;\n padding-left: 15px;\n width: 100%;\n}\n\n.row {\n display: flex;\n flex-wrap: wrap;\n margin-right: -15px;\n margin-left: -15px;\n}\n\n.no-gutters {\n margin-right: 0;\n margin-left: 0;\n}\n\n.no-gutters > .col,\n.no-gutters > [class*=\"col-\"] {\n padding-right: 0;\n padding-left: 0;\n}\n\n.col-1, .col-2, .col-3, .col-4, .col-5, .col-6, .col-7, .col-8, .col-9, .col-10, .col-11, .col-12, .col,\n.col-auto, .col-sm-1, .col-sm-2, .col-sm-3, .col-sm-4, .col-sm-5, .col-sm-6, .col-sm-7, .col-sm-8, .col-sm-9, .col-sm-10, .col-sm-11, .col-sm-12, .col-sm,\n.col-sm-auto, .col-md-1, .col-md-2, .col-md-3, .col-md-4, .col-md-5, .col-md-6, .col-md-7, .col-md-8, .col-md-9, .col-md-10, .col-md-11, .col-md-12, .col-md,\n.col-md-auto, .col-lg-1, .col-lg-2, .col-lg-3, .col-lg-4, .col-lg-5, .col-lg-6, .col-lg-7, .col-lg-8, .col-lg-9, .col-lg-10, .col-lg-11, .col-lg-12, .col-lg,\n.col-lg-auto, .col-xl-1, .col-xl-2, .col-xl-3, .col-xl-4, .col-xl-5, .col-xl-6, .col-xl-7, .col-xl-8, .col-xl-9, .col-xl-10, .col-xl-11, .col-xl-12, .col-xl,\n.col-xl-auto {\n position: relative;\n width: 100%;\n min-height: 1px;\n padding-right: 15px;\n padding-left: 15px;\n}\n\n.col {\n flex-basis: 0;\n flex-grow: 1;\n max-width: 100%;\n}\n\n.col-auto {\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n}\n\n.col-1 {\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n}\n\n.col-2 {\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n}\n\n.col-3 {\n flex: 0 0 25%;\n max-width: 25%;\n}\n\n.col-4 {\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n}\n\n.col-5 {\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n}\n\n.col-6 {\n flex: 0 0 50%;\n max-width: 50%;\n}\n\n.col-7 {\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n}\n\n.col-8 {\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n}\n\n.col-9 {\n flex: 0 0 75%;\n max-width: 75%;\n}\n\n.col-10 {\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n}\n\n.col-11 {\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n}\n\n.col-12 {\n flex: 0 0 100%;\n max-width: 100%;\n}\n\n.order-1 {\n order: 1;\n}\n\n.order-2 {\n order: 2;\n}\n\n.order-3 {\n order: 3;\n}\n\n.order-4 {\n order: 4;\n}\n\n.order-5 {\n order: 5;\n}\n\n.order-6 {\n order: 6;\n}\n\n.order-7 {\n order: 7;\n}\n\n.order-8 {\n order: 8;\n}\n\n.order-9 {\n order: 9;\n}\n\n.order-10 {\n order: 10;\n}\n\n.order-11 {\n order: 11;\n}\n\n.order-12 {\n order: 12;\n}\n\n@media (min-width: 576px) {\n .col-sm {\n flex-basis: 0;\n flex-grow: 1;\n max-width: 100%;\n }\n .col-sm-auto {\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n }\n .col-sm-1 {\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n }\n .col-sm-2 {\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n }\n .col-sm-3 {\n flex: 0 0 25%;\n max-width: 25%;\n }\n .col-sm-4 {\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n }\n .col-sm-5 {\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n }\n .col-sm-6 {\n flex: 0 0 50%;\n max-width: 50%;\n }\n .col-sm-7 {\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n }\n .col-sm-8 {\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n }\n .col-sm-9 {\n flex: 0 0 75%;\n max-width: 75%;\n }\n .col-sm-10 {\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n }\n .col-sm-11 {\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n }\n .col-sm-12 {\n flex: 0 0 100%;\n max-width: 100%;\n }\n .order-sm-1 {\n order: 1;\n }\n .order-sm-2 {\n order: 2;\n }\n .order-sm-3 {\n order: 3;\n }\n .order-sm-4 {\n order: 4;\n }\n .order-sm-5 {\n order: 5;\n }\n .order-sm-6 {\n order: 6;\n }\n .order-sm-7 {\n order: 7;\n }\n .order-sm-8 {\n order: 8;\n }\n .order-sm-9 {\n order: 9;\n }\n .order-sm-10 {\n order: 10;\n }\n .order-sm-11 {\n order: 11;\n }\n .order-sm-12 {\n order: 12;\n }\n}\n\n@media (min-width: 768px) {\n .col-md {\n flex-basis: 0;\n flex-grow: 1;\n max-width: 100%;\n }\n .col-md-auto {\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n }\n .col-md-1 {\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n }\n .col-md-2 {\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n }\n .col-md-3 {\n flex: 0 0 25%;\n max-width: 25%;\n }\n .col-md-4 {\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n }\n .col-md-5 {\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n }\n .col-md-6 {\n flex: 0 0 50%;\n max-width: 50%;\n }\n .col-md-7 {\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n }\n .col-md-8 {\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n }\n .col-md-9 {\n flex: 0 0 75%;\n max-width: 75%;\n }\n .col-md-10 {\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n }\n .col-md-11 {\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n }\n .col-md-12 {\n flex: 0 0 100%;\n max-width: 100%;\n }\n .order-md-1 {\n order: 1;\n }\n .order-md-2 {\n order: 2;\n }\n .order-md-3 {\n order: 3;\n }\n .order-md-4 {\n order: 4;\n }\n .order-md-5 {\n order: 5;\n }\n .order-md-6 {\n order: 6;\n }\n .order-md-7 {\n order: 7;\n }\n .order-md-8 {\n order: 8;\n }\n .order-md-9 {\n order: 9;\n }\n .order-md-10 {\n order: 10;\n }\n .order-md-11 {\n order: 11;\n }\n .order-md-12 {\n order: 12;\n }\n}\n\n@media (min-width: 992px) {\n .col-lg {\n flex-basis: 0;\n flex-grow: 1;\n max-width: 100%;\n }\n .col-lg-auto {\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n }\n .col-lg-1 {\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n }\n .col-lg-2 {\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n }\n .col-lg-3 {\n flex: 0 0 25%;\n max-width: 25%;\n }\n .col-lg-4 {\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n }\n .col-lg-5 {\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n }\n .col-lg-6 {\n flex: 0 0 50%;\n max-width: 50%;\n }\n .col-lg-7 {\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n }\n .col-lg-8 {\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n }\n .col-lg-9 {\n flex: 0 0 75%;\n max-width: 75%;\n }\n .col-lg-10 {\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n }\n .col-lg-11 {\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n }\n .col-lg-12 {\n flex: 0 0 100%;\n max-width: 100%;\n }\n .order-lg-1 {\n order: 1;\n }\n .order-lg-2 {\n order: 2;\n }\n .order-lg-3 {\n order: 3;\n }\n .order-lg-4 {\n order: 4;\n }\n .order-lg-5 {\n order: 5;\n }\n .order-lg-6 {\n order: 6;\n }\n .order-lg-7 {\n order: 7;\n }\n .order-lg-8 {\n order: 8;\n }\n .order-lg-9 {\n order: 9;\n }\n .order-lg-10 {\n order: 10;\n }\n .order-lg-11 {\n order: 11;\n }\n .order-lg-12 {\n order: 12;\n }\n}\n\n@media (min-width: 1200px) {\n .col-xl {\n flex-basis: 0;\n flex-grow: 1;\n max-width: 100%;\n }\n .col-xl-auto {\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n }\n .col-xl-1 {\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n }\n .col-xl-2 {\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n }\n .col-xl-3 {\n flex: 0 0 25%;\n max-width: 25%;\n }\n .col-xl-4 {\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n }\n .col-xl-5 {\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n }\n .col-xl-6 {\n flex: 0 0 50%;\n max-width: 50%;\n }\n .col-xl-7 {\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n }\n .col-xl-8 {\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n }\n .col-xl-9 {\n flex: 0 0 75%;\n max-width: 75%;\n }\n .col-xl-10 {\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n }\n .col-xl-11 {\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n }\n .col-xl-12 {\n flex: 0 0 100%;\n max-width: 100%;\n }\n .order-xl-1 {\n order: 1;\n }\n .order-xl-2 {\n order: 2;\n }\n .order-xl-3 {\n order: 3;\n }\n .order-xl-4 {\n order: 4;\n }\n .order-xl-5 {\n order: 5;\n }\n .order-xl-6 {\n order: 6;\n }\n .order-xl-7 {\n order: 7;\n }\n .order-xl-8 {\n order: 8;\n }\n .order-xl-9 {\n order: 9;\n }\n .order-xl-10 {\n order: 10;\n }\n .order-xl-11 {\n order: 11;\n }\n .order-xl-12 {\n order: 12;\n }\n}\n\n.flex-row {\n flex-direction: row !important;\n}\n\n.flex-column {\n flex-direction: column !important;\n}\n\n.flex-row-reverse {\n flex-direction: row-reverse !important;\n}\n\n.flex-column-reverse {\n flex-direction: column-reverse !important;\n}\n\n.flex-wrap {\n flex-wrap: wrap !important;\n}\n\n.flex-nowrap {\n flex-wrap: nowrap !important;\n}\n\n.flex-wrap-reverse {\n flex-wrap: wrap-reverse !important;\n}\n\n.justify-content-start {\n justify-content: flex-start !important;\n}\n\n.justify-content-end {\n justify-content: flex-end !important;\n}\n\n.justify-content-center {\n justify-content: center !important;\n}\n\n.justify-content-between {\n justify-content: space-between !important;\n}\n\n.justify-content-around {\n justify-content: space-around !important;\n}\n\n.align-items-start {\n align-items: flex-start !important;\n}\n\n.align-items-end {\n align-items: flex-end !important;\n}\n\n.align-items-center {\n align-items: center !important;\n}\n\n.align-items-baseline {\n align-items: baseline !important;\n}\n\n.align-items-stretch {\n align-items: stretch !important;\n}\n\n.align-content-start {\n align-content: flex-start !important;\n}\n\n.align-content-end {\n align-content: flex-end !important;\n}\n\n.align-content-center {\n align-content: center !important;\n}\n\n.align-content-between {\n align-content: space-between !important;\n}\n\n.align-content-around {\n align-content: space-around !important;\n}\n\n.align-content-stretch {\n align-content: stretch !important;\n}\n\n.align-self-auto {\n align-self: auto !important;\n}\n\n.align-self-start {\n align-self: flex-start !important;\n}\n\n.align-self-end {\n align-self: flex-end !important;\n}\n\n.align-self-center {\n align-self: center !important;\n}\n\n.align-self-baseline {\n align-self: baseline !important;\n}\n\n.align-self-stretch {\n align-self: stretch !important;\n}\n\n@media (min-width: 576px) {\n .flex-sm-row {\n flex-direction: row !important;\n }\n .flex-sm-column {\n flex-direction: column !important;\n }\n .flex-sm-row-reverse {\n flex-direction: row-reverse !important;\n }\n .flex-sm-column-reverse {\n flex-direction: column-reverse !important;\n }\n .flex-sm-wrap {\n flex-wrap: wrap !important;\n }\n .flex-sm-nowrap {\n flex-wrap: nowrap !important;\n }\n .flex-sm-wrap-reverse {\n flex-wrap: wrap-reverse !important;\n }\n .justify-content-sm-start {\n justify-content: flex-start !important;\n }\n .justify-content-sm-end {\n justify-content: flex-end !important;\n }\n .justify-content-sm-center {\n justify-content: center !important;\n }\n .justify-content-sm-between {\n justify-content: space-between !important;\n }\n .justify-content-sm-around {\n justify-content: space-around !important;\n }\n .align-items-sm-start {\n align-items: flex-start !important;\n }\n .align-items-sm-end {\n align-items: flex-end !important;\n }\n .align-items-sm-center {\n align-items: center !important;\n }\n .align-items-sm-baseline {\n align-items: baseline !important;\n }\n .align-items-sm-stretch {\n align-items: stretch !important;\n }\n .align-content-sm-start {\n align-content: flex-start !important;\n }\n .align-content-sm-end {\n align-content: flex-end !important;\n }\n .align-content-sm-center {\n align-content: center !important;\n }\n .align-content-sm-between {\n align-content: space-between !important;\n }\n .align-content-sm-around {\n align-content: space-around !important;\n }\n .align-content-sm-stretch {\n align-content: stretch !important;\n }\n .align-self-sm-auto {\n align-self: auto !important;\n }\n .align-self-sm-start {\n align-self: flex-start !important;\n }\n .align-self-sm-end {\n align-self: flex-end !important;\n }\n .align-self-sm-center {\n align-self: center !important;\n }\n .align-self-sm-baseline {\n align-self: baseline !important;\n }\n .align-self-sm-stretch {\n align-self: stretch !important;\n }\n}\n\n@media (min-width: 768px) {\n .flex-md-row {\n flex-direction: row !important;\n }\n .flex-md-column {\n flex-direction: column !important;\n }\n .flex-md-row-reverse {\n flex-direction: row-reverse !important;\n }\n .flex-md-column-reverse {\n flex-direction: column-reverse !important;\n }\n .flex-md-wrap {\n flex-wrap: wrap !important;\n }\n .flex-md-nowrap {\n flex-wrap: nowrap !important;\n }\n .flex-md-wrap-reverse {\n flex-wrap: wrap-reverse !important;\n }\n .justify-content-md-start {\n justify-content: flex-start !important;\n }\n .justify-content-md-end {\n justify-content: flex-end !important;\n }\n .justify-content-md-center {\n justify-content: center !important;\n }\n .justify-content-md-between {\n justify-content: space-between !important;\n }\n .justify-content-md-around {\n justify-content: space-around !important;\n }\n .align-items-md-start {\n align-items: flex-start !important;\n }\n .align-items-md-end {\n align-items: flex-end !important;\n }\n .align-items-md-center {\n align-items: center !important;\n }\n .align-items-md-baseline {\n align-items: baseline !important;\n }\n .align-items-md-stretch {\n align-items: stretch !important;\n }\n .align-content-md-start {\n align-content: flex-start !important;\n }\n .align-content-md-end {\n align-content: flex-end !important;\n }\n .align-content-md-center {\n align-content: center !important;\n }\n .align-content-md-between {\n align-content: space-between !important;\n }\n .align-content-md-around {\n align-content: space-around !important;\n }\n .align-content-md-stretch {\n align-content: stretch !important;\n }\n .align-self-md-auto {\n align-self: auto !important;\n }\n .align-self-md-start {\n align-self: flex-start !important;\n }\n .align-self-md-end {\n align-self: flex-end !important;\n }\n .align-self-md-center {\n align-self: center !important;\n }\n .align-self-md-baseline {\n align-self: baseline !important;\n }\n .align-self-md-stretch {\n align-self: stretch !important;\n }\n}\n\n@media (min-width: 992px) {\n .flex-lg-row {\n flex-direction: row !important;\n }\n .flex-lg-column {\n flex-direction: column !important;\n }\n .flex-lg-row-reverse {\n flex-direction: row-reverse !important;\n }\n .flex-lg-column-reverse {\n flex-direction: column-reverse !important;\n }\n .flex-lg-wrap {\n flex-wrap: wrap !important;\n }\n .flex-lg-nowrap {\n flex-wrap: nowrap !important;\n }\n .flex-lg-wrap-reverse {\n flex-wrap: wrap-reverse !important;\n }\n .justify-content-lg-start {\n justify-content: flex-start !important;\n }\n .justify-content-lg-end {\n justify-content: flex-end !important;\n }\n .justify-content-lg-center {\n justify-content: center !important;\n }\n .justify-content-lg-between {\n justify-content: space-between !important;\n }\n .justify-content-lg-around {\n justify-content: space-around !important;\n }\n .align-items-lg-start {\n align-items: flex-start !important;\n }\n .align-items-lg-end {\n align-items: flex-end !important;\n }\n .align-items-lg-center {\n align-items: center !important;\n }\n .align-items-lg-baseline {\n align-items: baseline !important;\n }\n .align-items-lg-stretch {\n align-items: stretch !important;\n }\n .align-content-lg-start {\n align-content: flex-start !important;\n }\n .align-content-lg-end {\n align-content: flex-end !important;\n }\n .align-content-lg-center {\n align-content: center !important;\n }\n .align-content-lg-between {\n align-content: space-between !important;\n }\n .align-content-lg-around {\n align-content: space-around !important;\n }\n .align-content-lg-stretch {\n align-content: stretch !important;\n }\n .align-self-lg-auto {\n align-self: auto !important;\n }\n .align-self-lg-start {\n align-self: flex-start !important;\n }\n .align-self-lg-end {\n align-self: flex-end !important;\n }\n .align-self-lg-center {\n align-self: center !important;\n }\n .align-self-lg-baseline {\n align-self: baseline !important;\n }\n .align-self-lg-stretch {\n align-self: stretch !important;\n }\n}\n\n@media (min-width: 1200px) {\n .flex-xl-row {\n flex-direction: row !important;\n }\n .flex-xl-column {\n flex-direction: column !important;\n }\n .flex-xl-row-reverse {\n flex-direction: row-reverse !important;\n }\n .flex-xl-column-reverse {\n flex-direction: column-reverse !important;\n }\n .flex-xl-wrap {\n flex-wrap: wrap !important;\n }\n .flex-xl-nowrap {\n flex-wrap: nowrap !important;\n }\n .flex-xl-wrap-reverse {\n flex-wrap: wrap-reverse !important;\n }\n .justify-content-xl-start {\n justify-content: flex-start !important;\n }\n .justify-content-xl-end {\n justify-content: flex-end !important;\n }\n .justify-content-xl-center {\n justify-content: center !important;\n }\n .justify-content-xl-between {\n justify-content: space-between !important;\n }\n .justify-content-xl-around {\n justify-content: space-around !important;\n }\n .align-items-xl-start {\n align-items: flex-start !important;\n }\n .align-items-xl-end {\n align-items: flex-end !important;\n }\n .align-items-xl-center {\n align-items: center !important;\n }\n .align-items-xl-baseline {\n align-items: baseline !important;\n }\n .align-items-xl-stretch {\n align-items: stretch !important;\n }\n .align-content-xl-start {\n align-content: flex-start !important;\n }\n .align-content-xl-end {\n align-content: flex-end !important;\n }\n .align-content-xl-center {\n align-content: center !important;\n }\n .align-content-xl-between {\n align-content: space-between !important;\n }\n .align-content-xl-around {\n align-content: space-around !important;\n }\n .align-content-xl-stretch {\n align-content: stretch !important;\n }\n .align-self-xl-auto {\n align-self: auto !important;\n }\n .align-self-xl-start {\n align-self: flex-start !important;\n }\n .align-self-xl-end {\n align-self: flex-end !important;\n }\n .align-self-xl-center {\n align-self: center !important;\n }\n .align-self-xl-baseline {\n align-self: baseline !important;\n }\n .align-self-xl-stretch {\n align-self: stretch !important;\n }\n}\n\n/*# sourceMappingURL=bootstrap-grid.css.map */","// Container widths\n//\n// Set the container width, and override it for fixed navbars in media queries.\n\n@if $enable-grid-classes {\n .container {\n @include make-container();\n @include make-container-max-widths();\n }\n}\n\n// Fluid container\n//\n// Utilizes the mixin meant for fixed width containers, but with 100% width for\n// fluid, full width layouts.\n\n@if $enable-grid-classes {\n .container-fluid {\n width: 100%;\n @include make-container();\n }\n}\n\n// Row\n//\n// Rows contain and clear the floats of your columns.\n\n@if $enable-grid-classes {\n .row {\n @include make-row();\n }\n\n // Remove the negative margin from default .row, then the horizontal padding\n // from all immediate children columns (to prevent runaway style inheritance).\n .no-gutters {\n margin-right: 0;\n margin-left: 0;\n\n > .col,\n > [class*=\"col-\"] {\n padding-right: 0;\n padding-left: 0;\n }\n }\n}\n\n// Columns\n//\n// Common styles for small and large grid columns\n\n@if $enable-grid-classes {\n @include make-grid-columns();\n}\n","/// Grid system\n//\n// Generate semantic grid columns with these mixins.\n\n@mixin make-container() {\n margin-right: auto;\n margin-left: auto;\n padding-right: ($grid-gutter-width / 2);\n padding-left: ($grid-gutter-width / 2);\n width: 100%;\n}\n\n\n// For each breakpoint, define the maximum width of the container in a media query\n@mixin make-container-max-widths($max-widths: $container-max-widths, $breakpoints: $grid-breakpoints) {\n @each $breakpoint, $container-max-width in $max-widths {\n @include media-breakpoint-up($breakpoint, $breakpoints) {\n max-width: $container-max-width;\n }\n }\n}\n\n@mixin make-row() {\n display: flex;\n flex-wrap: wrap;\n margin-right: ($grid-gutter-width / -2);\n margin-left: ($grid-gutter-width / -2);\n}\n\n@mixin make-col-ready() {\n position: relative;\n // Prevent columns from becoming too narrow when at smaller grid tiers by\n // always setting `width: 100%;`. This works because we use `flex` values\n // later on to override this initial width.\n width: 100%;\n min-height: 1px; // Prevent collapsing\n padding-right: ($grid-gutter-width / 2);\n padding-left: ($grid-gutter-width / 2);\n}\n\n@mixin make-col($size, $columns: $grid-columns) {\n flex: 0 0 percentage($size / $columns);\n // Add a `max-width` to ensure content within each column does not blow out\n // the width of the column. Applies to IE10+ and Firefox. Chrome and Safari\n // do not appear to require this.\n max-width: percentage($size / $columns);\n}\n","// Breakpoint viewport sizes and media queries.\n//\n// Breakpoints are defined as a map of (name: minimum width), order from small to large:\n//\n// (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px)\n//\n// The map defined in the `$grid-breakpoints` global variable is used as the `$breakpoints` argument by default.\n\n// Name of the next breakpoint, or null for the last breakpoint.\n//\n// >> breakpoint-next(sm)\n// md\n// >> breakpoint-next(sm, (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px))\n// md\n// >> breakpoint-next(sm, $breakpoint-names: (xs sm md lg xl))\n// md\n@function breakpoint-next($name, $breakpoints: $grid-breakpoints, $breakpoint-names: map-keys($breakpoints)) {\n $n: index($breakpoint-names, $name);\n @return if($n < length($breakpoint-names), nth($breakpoint-names, $n + 1), null);\n}\n\n// Minimum breakpoint width. Null for the smallest (first) breakpoint.\n//\n// >> breakpoint-min(sm, (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px))\n// 576px\n@function breakpoint-min($name, $breakpoints: $grid-breakpoints) {\n $min: map-get($breakpoints, $name);\n @return if($min != 0, $min, null);\n}\n\n// Maximum breakpoint width. Null for the largest (last) breakpoint.\n// The maximum value is calculated as the minimum of the next one less 0.1.\n//\n// >> breakpoint-max(sm, (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px))\n// 767px\n@function breakpoint-max($name, $breakpoints: $grid-breakpoints) {\n $next: breakpoint-next($name, $breakpoints);\n @return if($next, breakpoint-min($next, $breakpoints) - 1px, null);\n}\n\n// Returns a blank string if smallest breakpoint, otherwise returns the name with a dash infront.\n// Useful for making responsive utilities.\n//\n// >> breakpoint-infix(xs, (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px))\n// \"\" (Returns a blank string)\n// >> breakpoint-infix(sm, (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px))\n// \"-sm\"\n@function breakpoint-infix($name, $breakpoints: $grid-breakpoints) {\n @return if(breakpoint-min($name, $breakpoints) == null, \"\", \"-#{$name}\");\n}\n\n// Media of at least the minimum breakpoint width. No query for the smallest breakpoint.\n// Makes the @content apply to the given breakpoint and wider.\n@mixin media-breakpoint-up($name, $breakpoints: $grid-breakpoints) {\n $min: breakpoint-min($name, $breakpoints);\n @if $min {\n @media (min-width: $min) {\n @content;\n }\n } @else {\n @content;\n }\n}\n\n// Media of at most the maximum breakpoint width. No query for the largest breakpoint.\n// Makes the @content apply to the given breakpoint and narrower.\n@mixin media-breakpoint-down($name, $breakpoints: $grid-breakpoints) {\n $max: breakpoint-max($name, $breakpoints);\n @if $max {\n @media (max-width: $max) {\n @content;\n }\n } @else {\n @content;\n }\n}\n\n// Media that spans multiple breakpoint widths.\n// Makes the @content apply between the min and max breakpoints\n@mixin media-breakpoint-between($lower, $upper, $breakpoints: $grid-breakpoints) {\n $min: breakpoint-min($lower, $breakpoints);\n $max: breakpoint-max($upper, $breakpoints);\n\n @media (min-width: $min) and (max-width: $max) {\n @content;\n }\n}\n\n// Media between the breakpoint's minimum and maximum widths.\n// No minimum for the smallest breakpoint, and no maximum for the largest one.\n// Makes the @content apply only to the given breakpoint, not viewports any wider or narrower.\n@mixin media-breakpoint-only($name, $breakpoints: $grid-breakpoints) {\n $min: breakpoint-min($name, $breakpoints);\n $max: breakpoint-max($name, $breakpoints);\n\n @if $min != null and $max != null {\n @media (min-width: $min) and (max-width: $max) {\n @content;\n }\n } @else if $max == null {\n @include media-breakpoint-up($name)\n } @else if $min == null {\n @include media-breakpoint-down($name)\n }\n}\n","// Variables\n//\n// Copy settings from this file into the provided `_custom.scss` to override\n// the Bootstrap defaults without modifying key, versioned files.\n//\n// Variables should follow the `$component-state-property-size` formula for\n// consistent naming. Ex: $nav-link-disabled-color and $modal-content-box-shadow-xs.\n\n// Table of Contents\n//\n// Color system\n// Options\n// Spacing\n// Body\n// Links\n// Grid breakpoints\n// Grid containers\n// Grid columns\n// Fonts\n// Components\n// Tables\n// Buttons\n// Forms\n// Dropdowns\n// Z-index master list\n// Navs\n// Navbar\n// Pagination\n// Jumbotron\n// Form states and alerts\n// Cards\n// Tooltips\n// Popovers\n// Badges\n// Modals\n// Alerts\n// Progress bars\n// List group\n// Image thumbnails\n// Figures\n// Breadcrumbs\n// Carousel\n// Close\n// Code\n\n\n//\n// Color system\n//\n\n$white: #fff !default;\n$gray-100: #f8f9fa !default;\n$gray-200: #e9ecef !default;\n$gray-300: #dee2e6 !default;\n$gray-400: #ced4da !default;\n$gray-500: #adb5bd !default;\n$gray-600: #868e96 !default;\n$gray-700: #495057 !default;\n$gray-800: #343a40 !default;\n$gray-900: #212529 !default;\n$black: #000 !default;\n\n$grays: (\n 100: $gray-100,\n 200: $gray-200,\n 300: $gray-300,\n 400: $gray-400,\n 500: $gray-500,\n 600: $gray-600,\n 700: $gray-700,\n 800: $gray-800,\n 900: $gray-900\n) !default;\n\n$blue: #007bff !default;\n$indigo: #6610f2 !default;\n$purple: #6f42c1 !default;\n$pink: #e83e8c !default;\n$red: #dc3545 !default;\n$orange: #fd7e14 !default;\n$yellow: #ffc107 !default;\n$green: #28a745 !default;\n$teal: #20c997 !default;\n$cyan: #17a2b8 !default;\n\n$colors: (\n blue: $blue,\n indigo: $indigo,\n purple: $purple,\n pink: $pink,\n red: $red,\n orange: $orange,\n yellow: $yellow,\n green: $green,\n teal: $teal,\n cyan: $cyan,\n white: $white,\n gray: $gray-600,\n gray-dark: $gray-800\n) !default;\n\n$theme-colors: (\n primary: $blue,\n secondary: $gray-600,\n success: $green,\n info: $cyan,\n warning: $yellow,\n danger: $red,\n light: $gray-100,\n dark: $gray-800\n) !default;\n\n// Set a specific jump point for requesting color jumps\n$theme-color-interval: 8% !default;\n\n\n// Options\n//\n// Quickly modify global styling by enabling or disabling optional features.\n\n$enable-rounded: true !default;\n$enable-shadows: false !default;\n$enable-gradients: false !default;\n$enable-transitions: true !default;\n$enable-hover-media-query: false !default;\n$enable-grid-classes: true !default;\n$enable-print-styles: true !default;\n\n\n// Spacing\n//\n// Control the default styling of most Bootstrap elements by modifying these\n// variables. Mostly focused on spacing.\n// You can add more entries to the $spacers map, should you need more variation.\n\n$spacer: 1rem !default;\n$spacers: (\n 0: 0,\n 1: ($spacer * .25),\n 2: ($spacer * .5),\n 3: $spacer,\n 4: ($spacer * 1.5),\n 5: ($spacer * 3)\n) !default;\n\n// This variable affects the `.h-*` and `.w-*` classes.\n$sizes: (\n 25: 25%,\n 50: 50%,\n 75: 75%,\n 100: 100%\n) !default;\n\n// Body\n//\n// Settings for the `<body>` element.\n\n$body-bg: $white !default;\n$body-color: $gray-900 !default;\n\n// Links\n//\n// Style anchor elements.\n\n$link-color: theme-color(\"primary\") !default;\n$link-decoration: none !default;\n$link-hover-color: darken($link-color, 15%) !default;\n$link-hover-decoration: underline !default;\n\n\n// Grid breakpoints\n//\n// Define the minimum dimensions at which your layout will change,\n// adapting to different screen sizes, for use in media queries.\n\n$grid-breakpoints: (\n xs: 0,\n sm: 576px,\n md: 768px,\n lg: 992px,\n xl: 1200px\n) !default;\n@include _assert-ascending($grid-breakpoints, \"$grid-breakpoints\");\n@include _assert-starts-at-zero($grid-breakpoints);\n\n\n// Grid containers\n//\n// Define the maximum width of `.container` for different screen sizes.\n\n$container-max-widths: (\n sm: 540px,\n md: 720px,\n lg: 960px,\n xl: 1140px\n) !default;\n@include _assert-ascending($container-max-widths, \"$container-max-widths\");\n\n\n// Grid columns\n//\n// Set the number of columns and specify the width of the gutters.\n\n$grid-columns: 12 !default;\n$grid-gutter-width: 30px !default;\n\n// Components\n//\n// Define common padding and border radius sizes and more.\n\n$line-height-lg: 1.5 !default;\n$line-height-sm: 1.5 !default;\n\n$border-width: 1px !default;\n\n$border-radius: .25rem !default;\n$border-radius-lg: .3rem !default;\n$border-radius-sm: .2rem !default;\n\n$component-active-color: $white !default;\n$component-active-bg: theme-color(\"primary\") !default;\n\n$caret-width: .3em !default;\n\n$transition-base: all .2s ease-in-out !default;\n$transition-fade: opacity .15s linear !default;\n$transition-collapse: height .35s ease !default;\n\n\n// Fonts\n//\n// Font, line-height, and color for body text, headings, and more.\n\n$font-family-sans-serif: -apple-system, BlinkMacSystemFont, \"Segoe UI\", Roboto, \"Helvetica Neue\", Arial, sans-serif !default;\n$font-family-monospace: Menlo, Monaco, Consolas, \"Liberation Mono\", \"Courier New\", monospace !default;\n$font-family-base: $font-family-sans-serif !default;\n\n$font-size-base: 1rem !default; // Assumes the browser default, typically `16px`\n$font-size-lg: 1.25rem !default;\n$font-size-sm: .875rem !default;\n\n$font-weight-normal: normal !default;\n$font-weight-bold: bold !default;\n\n$font-weight-base: $font-weight-normal !default;\n$line-height-base: 1.5 !default;\n\n$h1-font-size: 2.5rem !default;\n$h2-font-size: 2rem !default;\n$h3-font-size: 1.75rem !default;\n$h4-font-size: 1.5rem !default;\n$h5-font-size: 1.25rem !default;\n$h6-font-size: 1rem !default;\n\n$headings-margin-bottom: ($spacer / 2) !default;\n$headings-font-family: inherit !default;\n$headings-font-weight: 500 !default;\n$headings-line-height: 1.1 !default;\n$headings-color: inherit !default;\n\n$display1-size: 6rem !default;\n$display2-size: 5.5rem !default;\n$display3-size: 4.5rem !default;\n$display4-size: 3.5rem !default;\n\n$display1-weight: 300 !default;\n$display2-weight: 300 !default;\n$display3-weight: 300 !default;\n$display4-weight: 300 !default;\n$display-line-height: $headings-line-height !default;\n\n$lead-font-size: 1.25rem !default;\n$lead-font-weight: 300 !default;\n\n$small-font-size: 80% !default;\n\n$text-muted: $gray-600 !default;\n\n$blockquote-small-color: $gray-600 !default;\n$blockquote-font-size: ($font-size-base * 1.25) !default;\n\n$hr-border-color: rgba($black,.1) !default;\n$hr-border-width: $border-width !default;\n\n$mark-padding: .2em !default;\n\n$dt-font-weight: $font-weight-bold !default;\n\n$kbd-box-shadow: inset 0 -.1rem 0 rgba($black,.25) !default;\n$nested-kbd-font-weight: $font-weight-bold !default;\n\n$list-inline-padding: 5px !default;\n\n$mark-bg: #fcf8e3 !default;\n\n\n// Tables\n//\n// Customizes the `.table` component with basic values, each used across all table variations.\n\n$table-cell-padding: .75rem !default;\n$table-cell-padding-sm: .3rem !default;\n\n$table-bg: transparent !default;\n$table-accent-bg: rgba($black,.05) !default;\n$table-hover-bg: rgba($black,.075) !default;\n$table-active-bg: $table-hover-bg !default;\n\n$table-border-width: $border-width !default;\n$table-border-color: $gray-200 !default;\n\n$table-head-bg: $gray-200 !default;\n$table-head-color: $gray-700 !default;\n\n$table-inverse-bg: $gray-900 !default;\n$table-inverse-accent-bg: rgba($white, .05) !default;\n$table-inverse-hover-bg: rgba($white, .075) !default;\n$table-inverse-border-color: lighten($gray-900, 7.5%) !default;\n$table-inverse-color: $body-bg !default;\n\n\n// Buttons\n//\n// For each of Bootstrap's buttons, define text, background and border color.\n\n$input-btn-padding-y: .5rem !default;\n$input-btn-padding-x: .75rem !default;\n$input-btn-line-height: 1.25 !default;\n\n$input-btn-padding-y-sm: .25rem !default;\n$input-btn-padding-x-sm: .5rem !default;\n$input-btn-line-height-sm: 1.5 !default;\n\n$input-btn-padding-y-lg: .5rem !default;\n$input-btn-padding-x-lg: 1rem !default;\n$input-btn-line-height-lg: 1.5 !default;\n\n$btn-font-weight: $font-weight-normal !default;\n$btn-box-shadow: inset 0 1px 0 rgba($white,.15), 0 1px 1px rgba($black,.075) !default;\n$btn-focus-box-shadow: 0 0 0 3px rgba(theme-color(\"primary\"), .25) !default;\n$btn-active-box-shadow: inset 0 3px 5px rgba($black,.125) !default;\n\n$btn-link-disabled-color: $gray-600 !default;\n\n$btn-block-spacing-y: .5rem !default;\n\n// Allows for customizing button radius independently from global border radius\n$btn-border-radius: $border-radius !default;\n$btn-border-radius-lg: $border-radius-lg !default;\n$btn-border-radius-sm: $border-radius-sm !default;\n\n$btn-transition: all .15s ease-in-out !default;\n\n\n// Forms\n\n$input-bg: $white !default;\n$input-disabled-bg: $gray-200 !default;\n\n$input-color: $gray-700 !default;\n$input-border-color: rgba($black,.15) !default;\n$input-btn-border-width: $border-width !default; // For form controls and buttons\n$input-box-shadow: inset 0 1px 1px rgba($black,.075) !default;\n\n$input-border-radius: $border-radius !default;\n$input-border-radius-lg: $border-radius-lg !default;\n$input-border-radius-sm: $border-radius-sm !default;\n\n$input-focus-bg: $input-bg !default;\n$input-focus-border-color: lighten(theme-color(\"primary\"), 25%) !default;\n$input-focus-box-shadow: $input-box-shadow, $btn-focus-box-shadow !default;\n$input-focus-color: $input-color !default;\n\n$input-placeholder-color: $gray-600 !default;\n\n$input-height-border: $input-btn-border-width * 2 !default;\n\n$input-height-inner: ($font-size-base * $input-btn-line-height) + ($input-btn-padding-y * 2) !default;\n$input-height: calc(#{$input-height-inner} + #{$input-height-border}) !default;\n\n$input-height-inner-sm: ($font-size-sm * $input-btn-line-height-sm) + ($input-btn-padding-y-sm * 2) !default;\n$input-height-sm: calc(#{$input-height-inner-sm} + #{$input-height-border}) !default;\n\n$input-height-inner-lg: ($font-size-sm * $input-btn-line-height-lg) + ($input-btn-padding-y-lg * 2) !default;\n$input-height-lg: calc(#{$input-height-inner-lg} + #{$input-height-border}) !default;\n\n$input-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s !default;\n\n$form-text-margin-top: .25rem !default;\n\n$form-check-margin-bottom: .5rem !default;\n$form-check-input-gutter: 1.25rem !default;\n$form-check-input-margin-y: .25rem !default;\n$form-check-input-margin-x: .25rem !default;\n\n$form-check-inline-margin-x: .75rem !default;\n\n$form-group-margin-bottom: 1rem !default;\n\n$input-group-addon-bg: $gray-200 !default;\n$input-group-addon-border-color: $input-border-color !default;\n\n$custom-control-gutter: 1.5rem !default;\n$custom-control-spacer-y: .25rem !default;\n$custom-control-spacer-x: 1rem !default;\n\n$custom-control-indicator-size: 1rem !default;\n$custom-control-indicator-bg: #ddd !default;\n$custom-control-indicator-bg-size: 50% 50% !default;\n$custom-control-indicator-box-shadow: inset 0 .25rem .25rem rgba($black,.1) !default;\n\n$custom-control-indicator-disabled-bg: $gray-200 !default;\n$custom-control-description-disabled-color: $gray-600 !default;\n\n$custom-control-indicator-checked-color: $white !default;\n$custom-control-indicator-checked-bg: theme-color(\"primary\") !default;\n$custom-control-indicator-checked-box-shadow: none !default;\n\n$custom-control-indicator-focus-box-shadow: 0 0 0 1px $body-bg, 0 0 0 3px theme-color(\"primary\") !default;\n\n$custom-control-indicator-active-color: $white !default;\n$custom-control-indicator-active-bg: lighten(theme-color(\"primary\"), 35%) !default;\n$custom-control-indicator-active-box-shadow: none !default;\n\n$custom-checkbox-indicator-border-radius: $border-radius !default;\n$custom-checkbox-indicator-icon-checked: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 8 8'%3E%3Cpath fill='#{$custom-control-indicator-checked-color}' d='M6.564.75l-3.59 3.612-1.538-1.55L0 4.26 2.974 7.25 8 2.193z'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n\n$custom-checkbox-indicator-indeterminate-bg: theme-color(\"primary\") !default;\n$custom-checkbox-indicator-indeterminate-color: $custom-control-indicator-checked-color !default;\n$custom-checkbox-indicator-icon-indeterminate: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 4 4'%3E%3Cpath stroke='#{$custom-checkbox-indicator-indeterminate-color}' d='M0 2h4'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n$custom-checkbox-indicator-indeterminate-box-shadow: none !default;\n\n$custom-radio-indicator-border-radius: 50% !default;\n$custom-radio-indicator-icon-checked: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='-4 -4 8 8'%3E%3Ccircle r='3' fill='#{$custom-control-indicator-checked-color}'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n\n$custom-select-padding-y: .375rem !default;\n$custom-select-padding-x: .75rem !default;\n$custom-select-height: $input-height !default;\n$custom-select-indicator-padding: 1rem !default; // Extra padding to account for the presence of the background-image based indicator\n$custom-select-line-height: $input-btn-line-height !default;\n$custom-select-color: $input-color !default;\n$custom-select-disabled-color: $gray-600 !default;\n$custom-select-bg: $white !default;\n$custom-select-disabled-bg: $gray-200 !default;\n$custom-select-bg-size: 8px 10px !default; // In pixels because image dimensions\n$custom-select-indicator-color: #333 !default;\n$custom-select-indicator: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 4 5'%3E%3Cpath fill='#{$custom-select-indicator-color}' d='M2 0L0 2h4zm0 5L0 3h4z'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n$custom-select-border-width: $input-btn-border-width !default;\n$custom-select-border-color: $input-border-color !default;\n$custom-select-border-radius: $border-radius !default;\n\n$custom-select-focus-border-color: lighten(theme-color(\"primary\"), 25%) !default;\n$custom-select-focus-box-shadow: inset 0 1px 2px rgba($black, .075), 0 0 5px rgba($custom-select-focus-border-color, .5) !default;\n\n$custom-select-font-size-sm: 75% !default;\n$custom-select-height-sm: $input-height-sm !default;\n\n$custom-file-height: 2.5rem !default;\n$custom-file-width: 14rem !default;\n$custom-file-focus-box-shadow: 0 0 0 .075rem $white, 0 0 0 .2rem theme-color(\"primary\") !default;\n\n$custom-file-padding-y: 1rem !default;\n$custom-file-padding-x: .5rem !default;\n$custom-file-line-height: 1.5 !default;\n$custom-file-color: $gray-700 !default;\n$custom-file-bg: $white !default;\n$custom-file-border-width: $border-width !default;\n$custom-file-border-color: $input-border-color !default;\n$custom-file-border-radius: $border-radius !default;\n$custom-file-box-shadow: inset 0 .2rem .4rem rgba($black,.05) !default;\n$custom-file-button-color: $custom-file-color !default;\n$custom-file-button-bg: $gray-200 !default;\n$custom-file-text: (\n placeholder: (\n en: \"Choose file...\"\n ),\n button-label: (\n en: \"Browse\"\n )\n) !default;\n\n\n// Form validation\n$form-feedback-valid-color: theme-color(\"success\") !default;\n$form-feedback-invalid-color: theme-color(\"danger\") !default;\n\n\n// Dropdowns\n//\n// Dropdown menu container and contents.\n\n$dropdown-min-width: 10rem !default;\n$dropdown-padding-y: .5rem !default;\n$dropdown-spacer: .125rem !default;\n$dropdown-bg: $white !default;\n$dropdown-border-color: rgba($black,.15) !default;\n$dropdown-border-width: $border-width !default;\n$dropdown-divider-bg: $gray-200 !default;\n$dropdown-box-shadow: 0 .5rem 1rem rgba($black,.175) !default;\n\n$dropdown-link-color: $gray-900 !default;\n$dropdown-link-hover-color: darken($gray-900, 5%) !default;\n$dropdown-link-hover-bg: $gray-100 !default;\n\n$dropdown-link-active-color: $component-active-color !default;\n$dropdown-link-active-bg: $component-active-bg !default;\n\n$dropdown-link-disabled-color: $gray-600 !default;\n\n$dropdown-item-padding-y: .25rem !default;\n$dropdown-item-padding-x: 1.5rem !default;\n\n$dropdown-header-color: $gray-600 !default;\n\n\n// Z-index master list\n//\n// Warning: Avoid customizing these values. They're used for a bird's eye view\n// of components dependent on the z-axis and are designed to all work together.\n\n$zindex-dropdown: 1000 !default;\n$zindex-sticky: 1020 !default;\n$zindex-fixed: 1030 !default;\n$zindex-modal-backdrop: 1040 !default;\n$zindex-modal: 1050 !default;\n$zindex-popover: 1060 !default;\n$zindex-tooltip: 1070 !default;\n\n// Navs\n\n$nav-link-padding-y: .5rem !default;\n$nav-link-padding-x: 1rem !default;\n$nav-link-disabled-color: $gray-600 !default;\n\n$nav-tabs-border-color: #ddd !default;\n$nav-tabs-border-width: $border-width !default;\n$nav-tabs-border-radius: $border-radius !default;\n$nav-tabs-link-hover-border-color: $gray-200 !default;\n$nav-tabs-link-active-color: $gray-700 !default;\n$nav-tabs-link-active-bg: $body-bg !default;\n$nav-tabs-link-active-border-color: #ddd !default;\n\n$nav-pills-border-radius: $border-radius !default;\n$nav-pills-link-active-color: $component-active-color !default;\n$nav-pills-link-active-bg: $component-active-bg !default;\n\n// Navbar\n\n$navbar-padding-y: ($spacer / 2) !default;\n$navbar-padding-x: $spacer !default;\n\n$navbar-brand-font-size: $font-size-lg !default;\n// Compute the navbar-brand padding-y so the navbar-brand will have the same height as navbar-text and nav-link\n$nav-link-height: $navbar-brand-font-size * $line-height-base !default;\n$navbar-brand-height: ($font-size-base * $line-height-base + $nav-link-padding-y * 2) !default;\n$navbar-brand-padding-y: ($navbar-brand-height - $nav-link-height) / 2 !default;\n\n$navbar-toggler-padding-y: .25rem !default;\n$navbar-toggler-padding-x: .75rem !default;\n$navbar-toggler-font-size: $font-size-lg !default;\n$navbar-toggler-border-radius: $btn-border-radius !default;\n\n$navbar-dark-color: rgba($white,.5) !default;\n$navbar-dark-hover-color: rgba($white,.75) !default;\n$navbar-dark-active-color: rgba($white,1) !default;\n$navbar-dark-disabled-color: rgba($white,.25) !default;\n$navbar-dark-toggler-icon-bg: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg viewBox='0 0 30 30' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath stroke='#{$navbar-dark-color}' stroke-width='2' stroke-linecap='round' stroke-miterlimit='10' d='M4 7h22M4 15h22M4 23h22'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n$navbar-dark-toggler-border-color: rgba($white,.1) !default;\n\n$navbar-light-color: rgba($black,.5) !default;\n$navbar-light-hover-color: rgba($black,.7) !default;\n$navbar-light-active-color: rgba($black,.9) !default;\n$navbar-light-disabled-color: rgba($black,.3) !default;\n$navbar-light-toggler-icon-bg: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg viewBox='0 0 30 30' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath stroke='#{$navbar-light-color}' stroke-width='2' stroke-linecap='round' stroke-miterlimit='10' d='M4 7h22M4 15h22M4 23h22'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n$navbar-light-toggler-border-color: rgba($black,.1) !default;\n\n// Pagination\n\n$pagination-padding-y: .5rem !default;\n$pagination-padding-x: .75rem !default;\n$pagination-padding-y-sm: .25rem !default;\n$pagination-padding-x-sm: .5rem !default;\n$pagination-padding-y-lg: .75rem !default;\n$pagination-padding-x-lg: 1.5rem !default;\n$pagination-line-height: 1.25 !default;\n\n$pagination-color: $link-color !default;\n$pagination-bg: $white !default;\n$pagination-border-width: $border-width !default;\n$pagination-border-color: #ddd !default;\n\n$pagination-hover-color: $link-hover-color !default;\n$pagination-hover-bg: $gray-200 !default;\n$pagination-hover-border-color: #ddd !default;\n\n$pagination-active-color: $white !default;\n$pagination-active-bg: theme-color(\"primary\") !default;\n$pagination-active-border-color: theme-color(\"primary\") !default;\n\n$pagination-disabled-color: $gray-600 !default;\n$pagination-disabled-bg: $white !default;\n$pagination-disabled-border-color: #ddd !default;\n\n\n// Jumbotron\n\n$jumbotron-padding: 2rem !default;\n$jumbotron-bg: $gray-200 !default;\n\n\n// Cards\n\n$card-spacer-y: .75rem !default;\n$card-spacer-x: 1.25rem !default;\n$card-border-width: 1px !default;\n$card-border-radius: $border-radius !default;\n$card-border-color: rgba($black,.125) !default;\n$card-inner-border-radius: calc(#{$card-border-radius} - #{$card-border-width}) !default;\n$card-cap-bg: rgba($black, .03) !default;\n$card-bg: $white !default;\n\n$card-img-overlay-padding: 1.25rem !default;\n\n$card-deck-margin: ($grid-gutter-width / 2) !default;\n\n$card-columns-count: 3 !default;\n$card-columns-gap: 1.25rem !default;\n$card-columns-margin: $card-spacer-y !default;\n\n\n// Tooltips\n\n$tooltip-max-width: 200px !default;\n$tooltip-color: $white !default;\n$tooltip-bg: $black !default;\n$tooltip-opacity: .9 !default;\n$tooltip-padding-y: 3px !default;\n$tooltip-padding-x: 8px !default;\n$tooltip-margin: 0 !default;\n\n\n$tooltip-arrow-width: 5px !default;\n$tooltip-arrow-height: 5px !default;\n$tooltip-arrow-color: $tooltip-bg !default;\n\n\n// Popovers\n\n$popover-inner-padding: 1px !default;\n$popover-bg: $white !default;\n$popover-max-width: 276px !default;\n$popover-border-width: $border-width !default;\n$popover-border-color: rgba($black,.2) !default;\n$popover-box-shadow: 0 5px 10px rgba($black,.2) !default;\n\n$popover-header-bg: darken($popover-bg, 3%) !default;\n$popover-header-color: $headings-color !default;\n$popover-header-padding-y: 8px !default;\n$popover-header-padding-x: 14px !default;\n\n$popover-body-color: $body-color !default;\n$popover-body-padding-y: 9px !default;\n$popover-body-padding-x: 14px !default;\n\n$popover-arrow-width: 10px !default;\n$popover-arrow-height: 5px !default;\n$popover-arrow-color: $popover-bg !default;\n\n$popover-arrow-outer-width: ($popover-arrow-width + 1px) !default;\n$popover-arrow-outer-color: fade-in($popover-border-color, .05) !default;\n\n\n// Badges\n\n$badge-color: $white !default;\n$badge-font-size: 75% !default;\n$badge-font-weight: $font-weight-bold !default;\n$badge-padding-y: .25em !default;\n$badge-padding-x: .4em !default;\n\n$badge-pill-padding-x: .6em !default;\n// Use a higher than normal value to ensure completely rounded edges when\n// customizing padding or font-size on labels.\n$badge-pill-border-radius: 10rem !default;\n\n\n// Modals\n\n// Padding applied to the modal body\n$modal-inner-padding: 15px !default;\n\n$modal-dialog-margin: 10px !default;\n$modal-dialog-margin-y-sm-up: 30px !default;\n\n$modal-title-line-height: $line-height-base !default;\n\n$modal-content-bg: $white !default;\n$modal-content-border-color: rgba($black,.2) !default;\n$modal-content-border-width: $border-width !default;\n$modal-content-box-shadow-xs: 0 3px 9px rgba($black,.5) !default;\n$modal-content-box-shadow-sm-up: 0 5px 15px rgba($black,.5) !default;\n\n$modal-backdrop-bg: $black !default;\n$modal-backdrop-opacity: .5 !default;\n$modal-header-border-color: $gray-200 !default;\n$modal-footer-border-color: $modal-header-border-color !default;\n$modal-header-border-width: $modal-content-border-width !default;\n$modal-footer-border-width: $modal-header-border-width !default;\n$modal-header-padding: 15px !default;\n\n$modal-lg: 800px !default;\n$modal-md: 500px !default;\n$modal-sm: 300px !default;\n\n$modal-transition: transform .3s ease-out !default;\n\n\n// Alerts\n//\n// Define alert colors, border radius, and padding.\n\n$alert-padding-y: .75rem !default;\n$alert-padding-x: 1.25rem !default;\n$alert-margin-bottom: 1rem !default;\n$alert-border-radius: $border-radius !default;\n$alert-link-font-weight: $font-weight-bold !default;\n$alert-border-width: $border-width !default;\n\n\n// Progress bars\n\n$progress-height: 1rem !default;\n$progress-font-size: .75rem !default;\n$progress-bg: $gray-200 !default;\n$progress-border-radius: $border-radius !default;\n$progress-box-shadow: inset 0 .1rem .1rem rgba($black,.1) !default;\n$progress-bar-color: $white !default;\n$progress-bar-bg: theme-color(\"primary\") !default;\n$progress-bar-animation-timing: 1s linear infinite !default;\n$progress-bar-transition: width .6s ease !default;\n\n// List group\n\n$list-group-bg: $white !default;\n$list-group-border-color: rgba($black,.125) !default;\n$list-group-border-width: $border-width !default;\n$list-group-border-radius: $border-radius !default;\n\n$list-group-item-padding-y: .75rem !default;\n$list-group-item-padding-x: 1.25rem !default;\n\n$list-group-hover-bg: $gray-100 !default;\n$list-group-active-color: $component-active-color !default;\n$list-group-active-bg: $component-active-bg !default;\n$list-group-active-border-color: $list-group-active-bg !default;\n\n$list-group-disabled-color: $gray-600 !default;\n$list-group-disabled-bg: $list-group-bg !default;\n\n$list-group-action-color: $gray-700 !default;\n$list-group-action-hover-color: $list-group-action-color !default;\n\n$list-group-action-active-color: $body-color !default;\n$list-group-action-active-bg: $gray-200 !default;\n\n\n// Image thumbnails\n\n$thumbnail-padding: .25rem !default;\n$thumbnail-bg: $body-bg !default;\n$thumbnail-border-width: $border-width !default;\n$thumbnail-border-color: #ddd !default;\n$thumbnail-border-radius: $border-radius !default;\n$thumbnail-box-shadow: 0 1px 2px rgba($black,.075) !default;\n$thumbnail-transition: all .2s ease-in-out !default;\n\n\n// Figures\n\n$figure-caption-font-size: 90% !default;\n$figure-caption-color: $gray-600 !default;\n\n\n// Breadcrumbs\n\n$breadcrumb-padding-y: .75rem !default;\n$breadcrumb-padding-x: 1rem !default;\n$breadcrumb-item-padding: .5rem !default;\n\n$breadcrumb-bg: $gray-200 !default;\n$breadcrumb-divider-color: $gray-600 !default;\n$breadcrumb-active-color: $gray-600 !default;\n$breadcrumb-divider: \"/\" !default;\n\n\n// Carousel\n\n$carousel-control-color: $white !default;\n$carousel-control-width: 15% !default;\n$carousel-control-opacity: .5 !default;\n\n$carousel-indicator-width: 30px !default;\n$carousel-indicator-height: 3px !default;\n$carousel-indicator-spacer: 3px !default;\n$carousel-indicator-active-bg: $white !default;\n\n$carousel-caption-width: 70% !default;\n$carousel-caption-color: $white !default;\n\n$carousel-control-icon-width: 20px !default;\n\n$carousel-control-prev-icon-bg: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' fill='#{$carousel-control-color}' viewBox='0 0 8 8'%3E%3Cpath d='M4 0l-4 4 4 4 1.5-1.5-2.5-2.5 2.5-2.5-1.5-1.5z'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n$carousel-control-next-icon-bg: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' fill='#{$carousel-control-color}' viewBox='0 0 8 8'%3E%3Cpath d='M1.5 0l-1.5 1.5 2.5 2.5-2.5 2.5 1.5 1.5 4-4-4-4z'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n\n$carousel-transition: transform .6s ease !default;\n\n\n// Close\n\n$close-font-size: $font-size-base * 1.5 !default;\n$close-font-weight: $font-weight-bold !default;\n$close-color: $black !default;\n$close-text-shadow: 0 1px 0 $white !default;\n\n// Code\n\n$code-font-size: 90% !default;\n$code-padding-y: .2rem !default;\n$code-padding-x: .4rem !default;\n$code-color: #bd4147 !default;\n$code-bg: $gray-100 !default;\n\n$kbd-color: $white !default;\n$kbd-bg: $gray-900 !default;\n\n$pre-color: $gray-900 !default;\n$pre-scrollable-max-height: 340px !default;\n","// Framework grid generation\n//\n// Used only by Bootstrap to generate the correct number of grid classes given\n// any value of `$grid-columns`.\n\n@mixin make-grid-columns($columns: $grid-columns, $gutter: $grid-gutter-width, $breakpoints: $grid-breakpoints) {\n // Common properties for all breakpoints\n %grid-column {\n position: relative;\n width: 100%;\n min-height: 1px; // Prevent columns from collapsing when empty\n padding-right: ($gutter / 2);\n padding-left: ($gutter / 2);\n }\n\n @each $breakpoint in map-keys($breakpoints) {\n $infix: breakpoint-infix($breakpoint, $breakpoints);\n\n // Allow columns to stretch full width below their breakpoints\n @for $i from 1 through $columns {\n .col#{$infix}-#{$i} {\n @extend %grid-column;\n }\n }\n .col#{$infix},\n .col#{$infix}-auto {\n @extend %grid-column;\n }\n\n @include media-breakpoint-up($breakpoint, $breakpoints) {\n // Provide basic `.col-{bp}` classes for equal-width flexbox columns\n .col#{$infix} {\n flex-basis: 0;\n flex-grow: 1;\n max-width: 100%;\n }\n .col#{$infix}-auto {\n flex: 0 0 auto;\n width: auto;\n max-width: none; // Reset earlier grid tiers\n }\n\n @for $i from 1 through $columns {\n .col#{$infix}-#{$i} {\n @include make-col($i, $columns);\n }\n }\n\n @for $i from 1 through $columns {\n .order#{$infix}-#{$i} {\n order: $i;\n }\n }\n }\n }\n}\n","// Flex variation\n//\n// Custom styles for additional flex alignment options.\n\n@each $breakpoint in map-keys($grid-breakpoints) {\n @include media-breakpoint-up($breakpoint) {\n $infix: breakpoint-infix($breakpoint, $grid-breakpoints);\n\n .flex#{$infix}-row { flex-direction: row !important; }\n .flex#{$infix}-column { flex-direction: column !important; }\n .flex#{$infix}-row-reverse { flex-direction: row-reverse !important; }\n .flex#{$infix}-column-reverse { flex-direction: column-reverse !important; }\n\n .flex#{$infix}-wrap { flex-wrap: wrap !important; }\n .flex#{$infix}-nowrap { flex-wrap: nowrap !important; }\n .flex#{$infix}-wrap-reverse { flex-wrap: wrap-reverse !important; }\n\n .justify-content#{$infix}-start { justify-content: flex-start !important; }\n .justify-content#{$infix}-end { justify-content: flex-end !important; }\n .justify-content#{$infix}-center { justify-content: center !important; }\n .justify-content#{$infix}-between { justify-content: space-between !important; }\n .justify-content#{$infix}-around { justify-content: space-around !important; }\n\n .align-items#{$infix}-start { align-items: flex-start !important; }\n .align-items#{$infix}-end { align-items: flex-end !important; }\n .align-items#{$infix}-center { align-items: center !important; }\n .align-items#{$infix}-baseline { align-items: baseline !important; }\n .align-items#{$infix}-stretch { align-items: stretch !important; }\n\n .align-content#{$infix}-start { align-content: flex-start !important; }\n .align-content#{$infix}-end { align-content: flex-end !important; }\n .align-content#{$infix}-center { align-content: center !important; }\n .align-content#{$infix}-between { align-content: space-between !important; }\n .align-content#{$infix}-around { align-content: space-around !important; }\n .align-content#{$infix}-stretch { align-content: stretch !important; }\n\n .align-self#{$infix}-auto { align-self: auto !important; }\n .align-self#{$infix}-start { align-self: flex-start !important; }\n .align-self#{$infix}-end { align-self: flex-end !important; }\n .align-self#{$infix}-center { align-self: center !important; }\n .align-self#{$infix}-baseline { align-self: baseline !important; }\n .align-self#{$infix}-stretch { align-self: stretch !important; }\n }\n}\n"]} \ No newline at end of file
diff --git a/library/bootstrap/css/bootstrap-grid.min.css b/library/bootstrap/css/bootstrap-grid.min.css
new file mode 100644
index 000000000..b775555cc
--- /dev/null
+++ b/library/bootstrap/css/bootstrap-grid.min.css
@@ -0,0 +1,2 @@
+@-ms-viewport{width:device-width}html{box-sizing:border-box;-ms-overflow-style:scrollbar}*,::after,::before{box-sizing:inherit}.container{margin-right:auto;margin-left:auto;padding-right:15px;padding-left:15px;width:100%}@media (min-width:576px){.container{max-width:540px}}@media (min-width:768px){.container{max-width:720px}}@media (min-width:992px){.container{max-width:960px}}@media (min-width:1200px){.container{max-width:1140px}}.container-fluid{width:100%;margin-right:auto;margin-left:auto;padding-right:15px;padding-left:15px;width:100%}.row{display:-ms-flexbox;display:flex;-ms-flex-wrap:wrap;flex-wrap:wrap;margin-right:-15px;margin-left:-15px}.no-gutters{margin-right:0;margin-left:0}.no-gutters>.col,.no-gutters>[class*=col-]{padding-right:0;padding-left:0}.col,.col-1,.col-10,.col-11,.col-12,.col-2,.col-3,.col-4,.col-5,.col-6,.col-7,.col-8,.col-9,.col-auto,.col-lg,.col-lg-1,.col-lg-10,.col-lg-11,.col-lg-12,.col-lg-2,.col-lg-3,.col-lg-4,.col-lg-5,.col-lg-6,.col-lg-7,.col-lg-8,.col-lg-9,.col-lg-auto,.col-md,.col-md-1,.col-md-10,.col-md-11,.col-md-12,.col-md-2,.col-md-3,.col-md-4,.col-md-5,.col-md-6,.col-md-7,.col-md-8,.col-md-9,.col-md-auto,.col-sm,.col-sm-1,.col-sm-10,.col-sm-11,.col-sm-12,.col-sm-2,.col-sm-3,.col-sm-4,.col-sm-5,.col-sm-6,.col-sm-7,.col-sm-8,.col-sm-9,.col-sm-auto,.col-xl,.col-xl-1,.col-xl-10,.col-xl-11,.col-xl-12,.col-xl-2,.col-xl-3,.col-xl-4,.col-xl-5,.col-xl-6,.col-xl-7,.col-xl-8,.col-xl-9,.col-xl-auto{position:relative;width:100%;min-height:1px;padding-right:15px;padding-left:15px}.col{-ms-flex-preferred-size:0;flex-basis:0;-ms-flex-positive:1;flex-grow:1;max-width:100%}.col-auto{-ms-flex:0 0 auto;flex:0 0 auto;width:auto;max-width:none}.col-1{-ms-flex:0 0 8.333333%;flex:0 0 8.333333%;max-width:8.333333%}.col-2{-ms-flex:0 0 16.666667%;flex:0 0 16.666667%;max-width:16.666667%}.col-3{-ms-flex:0 0 25%;flex:0 0 25%;max-width:25%}.col-4{-ms-flex:0 0 33.333333%;flex:0 0 33.333333%;max-width:33.333333%}.col-5{-ms-flex:0 0 41.666667%;flex:0 0 41.666667%;max-width:41.666667%}.col-6{-ms-flex:0 0 50%;flex:0 0 50%;max-width:50%}.col-7{-ms-flex:0 0 58.333333%;flex:0 0 58.333333%;max-width:58.333333%}.col-8{-ms-flex:0 0 66.666667%;flex:0 0 66.666667%;max-width:66.666667%}.col-9{-ms-flex:0 0 75%;flex:0 0 75%;max-width:75%}.col-10{-ms-flex:0 0 83.333333%;flex:0 0 83.333333%;max-width:83.333333%}.col-11{-ms-flex:0 0 91.666667%;flex:0 0 91.666667%;max-width:91.666667%}.col-12{-ms-flex:0 0 100%;flex:0 0 100%;max-width:100%}.order-1{-ms-flex-order:1;order:1}.order-2{-ms-flex-order:2;order:2}.order-3{-ms-flex-order:3;order:3}.order-4{-ms-flex-order:4;order:4}.order-5{-ms-flex-order:5;order:5}.order-6{-ms-flex-order:6;order:6}.order-7{-ms-flex-order:7;order:7}.order-8{-ms-flex-order:8;order:8}.order-9{-ms-flex-order:9;order:9}.order-10{-ms-flex-order:10;order:10}.order-11{-ms-flex-order:11;order:11}.order-12{-ms-flex-order:12;order:12}@media (min-width:576px){.col-sm{-ms-flex-preferred-size:0;flex-basis:0;-ms-flex-positive:1;flex-grow:1;max-width:100%}.col-sm-auto{-ms-flex:0 0 auto;flex:0 0 auto;width:auto;max-width:none}.col-sm-1{-ms-flex:0 0 8.333333%;flex:0 0 8.333333%;max-width:8.333333%}.col-sm-2{-ms-flex:0 0 16.666667%;flex:0 0 16.666667%;max-width:16.666667%}.col-sm-3{-ms-flex:0 0 25%;flex:0 0 25%;max-width:25%}.col-sm-4{-ms-flex:0 0 33.333333%;flex:0 0 33.333333%;max-width:33.333333%}.col-sm-5{-ms-flex:0 0 41.666667%;flex:0 0 41.666667%;max-width:41.666667%}.col-sm-6{-ms-flex:0 0 50%;flex:0 0 50%;max-width:50%}.col-sm-7{-ms-flex:0 0 58.333333%;flex:0 0 58.333333%;max-width:58.333333%}.col-sm-8{-ms-flex:0 0 66.666667%;flex:0 0 66.666667%;max-width:66.666667%}.col-sm-9{-ms-flex:0 0 75%;flex:0 0 75%;max-width:75%}.col-sm-10{-ms-flex:0 0 83.333333%;flex:0 0 83.333333%;max-width:83.333333%}.col-sm-11{-ms-flex:0 0 91.666667%;flex:0 0 91.666667%;max-width:91.666667%}.col-sm-12{-ms-flex:0 0 100%;flex:0 0 100%;max-width:100%}.order-sm-1{-ms-flex-order:1;order:1}.order-sm-2{-ms-flex-order:2;order:2}.order-sm-3{-ms-flex-order:3;order:3}.order-sm-4{-ms-flex-order:4;order:4}.order-sm-5{-ms-flex-order:5;order:5}.order-sm-6{-ms-flex-order:6;order:6}.order-sm-7{-ms-flex-order:7;order:7}.order-sm-8{-ms-flex-order:8;order:8}.order-sm-9{-ms-flex-order:9;order:9}.order-sm-10{-ms-flex-order:10;order:10}.order-sm-11{-ms-flex-order:11;order:11}.order-sm-12{-ms-flex-order:12;order:12}}@media (min-width:768px){.col-md{-ms-flex-preferred-size:0;flex-basis:0;-ms-flex-positive:1;flex-grow:1;max-width:100%}.col-md-auto{-ms-flex:0 0 auto;flex:0 0 auto;width:auto;max-width:none}.col-md-1{-ms-flex:0 0 8.333333%;flex:0 0 8.333333%;max-width:8.333333%}.col-md-2{-ms-flex:0 0 16.666667%;flex:0 0 16.666667%;max-width:16.666667%}.col-md-3{-ms-flex:0 0 25%;flex:0 0 25%;max-width:25%}.col-md-4{-ms-flex:0 0 33.333333%;flex:0 0 33.333333%;max-width:33.333333%}.col-md-5{-ms-flex:0 0 41.666667%;flex:0 0 41.666667%;max-width:41.666667%}.col-md-6{-ms-flex:0 0 50%;flex:0 0 50%;max-width:50%}.col-md-7{-ms-flex:0 0 58.333333%;flex:0 0 58.333333%;max-width:58.333333%}.col-md-8{-ms-flex:0 0 66.666667%;flex:0 0 66.666667%;max-width:66.666667%}.col-md-9{-ms-flex:0 0 75%;flex:0 0 75%;max-width:75%}.col-md-10{-ms-flex:0 0 83.333333%;flex:0 0 83.333333%;max-width:83.333333%}.col-md-11{-ms-flex:0 0 91.666667%;flex:0 0 91.666667%;max-width:91.666667%}.col-md-12{-ms-flex:0 0 100%;flex:0 0 100%;max-width:100%}.order-md-1{-ms-flex-order:1;order:1}.order-md-2{-ms-flex-order:2;order:2}.order-md-3{-ms-flex-order:3;order:3}.order-md-4{-ms-flex-order:4;order:4}.order-md-5{-ms-flex-order:5;order:5}.order-md-6{-ms-flex-order:6;order:6}.order-md-7{-ms-flex-order:7;order:7}.order-md-8{-ms-flex-order:8;order:8}.order-md-9{-ms-flex-order:9;order:9}.order-md-10{-ms-flex-order:10;order:10}.order-md-11{-ms-flex-order:11;order:11}.order-md-12{-ms-flex-order:12;order:12}}@media (min-width:992px){.col-lg{-ms-flex-preferred-size:0;flex-basis:0;-ms-flex-positive:1;flex-grow:1;max-width:100%}.col-lg-auto{-ms-flex:0 0 auto;flex:0 0 auto;width:auto;max-width:none}.col-lg-1{-ms-flex:0 0 8.333333%;flex:0 0 8.333333%;max-width:8.333333%}.col-lg-2{-ms-flex:0 0 16.666667%;flex:0 0 16.666667%;max-width:16.666667%}.col-lg-3{-ms-flex:0 0 25%;flex:0 0 25%;max-width:25%}.col-lg-4{-ms-flex:0 0 33.333333%;flex:0 0 33.333333%;max-width:33.333333%}.col-lg-5{-ms-flex:0 0 41.666667%;flex:0 0 41.666667%;max-width:41.666667%}.col-lg-6{-ms-flex:0 0 50%;flex:0 0 50%;max-width:50%}.col-lg-7{-ms-flex:0 0 58.333333%;flex:0 0 58.333333%;max-width:58.333333%}.col-lg-8{-ms-flex:0 0 66.666667%;flex:0 0 66.666667%;max-width:66.666667%}.col-lg-9{-ms-flex:0 0 75%;flex:0 0 75%;max-width:75%}.col-lg-10{-ms-flex:0 0 83.333333%;flex:0 0 83.333333%;max-width:83.333333%}.col-lg-11{-ms-flex:0 0 91.666667%;flex:0 0 91.666667%;max-width:91.666667%}.col-lg-12{-ms-flex:0 0 100%;flex:0 0 100%;max-width:100%}.order-lg-1{-ms-flex-order:1;order:1}.order-lg-2{-ms-flex-order:2;order:2}.order-lg-3{-ms-flex-order:3;order:3}.order-lg-4{-ms-flex-order:4;order:4}.order-lg-5{-ms-flex-order:5;order:5}.order-lg-6{-ms-flex-order:6;order:6}.order-lg-7{-ms-flex-order:7;order:7}.order-lg-8{-ms-flex-order:8;order:8}.order-lg-9{-ms-flex-order:9;order:9}.order-lg-10{-ms-flex-order:10;order:10}.order-lg-11{-ms-flex-order:11;order:11}.order-lg-12{-ms-flex-order:12;order:12}}@media (min-width:1200px){.col-xl{-ms-flex-preferred-size:0;flex-basis:0;-ms-flex-positive:1;flex-grow:1;max-width:100%}.col-xl-auto{-ms-flex:0 0 auto;flex:0 0 auto;width:auto;max-width:none}.col-xl-1{-ms-flex:0 0 8.333333%;flex:0 0 8.333333%;max-width:8.333333%}.col-xl-2{-ms-flex:0 0 16.666667%;flex:0 0 16.666667%;max-width:16.666667%}.col-xl-3{-ms-flex:0 0 25%;flex:0 0 25%;max-width:25%}.col-xl-4{-ms-flex:0 0 33.333333%;flex:0 0 33.333333%;max-width:33.333333%}.col-xl-5{-ms-flex:0 0 41.666667%;flex:0 0 41.666667%;max-width:41.666667%}.col-xl-6{-ms-flex:0 0 50%;flex:0 0 50%;max-width:50%}.col-xl-7{-ms-flex:0 0 58.333333%;flex:0 0 58.333333%;max-width:58.333333%}.col-xl-8{-ms-flex:0 0 66.666667%;flex:0 0 66.666667%;max-width:66.666667%}.col-xl-9{-ms-flex:0 0 75%;flex:0 0 75%;max-width:75%}.col-xl-10{-ms-flex:0 0 83.333333%;flex:0 0 83.333333%;max-width:83.333333%}.col-xl-11{-ms-flex:0 0 91.666667%;flex:0 0 91.666667%;max-width:91.666667%}.col-xl-12{-ms-flex:0 0 100%;flex:0 0 100%;max-width:100%}.order-xl-1{-ms-flex-order:1;order:1}.order-xl-2{-ms-flex-order:2;order:2}.order-xl-3{-ms-flex-order:3;order:3}.order-xl-4{-ms-flex-order:4;order:4}.order-xl-5{-ms-flex-order:5;order:5}.order-xl-6{-ms-flex-order:6;order:6}.order-xl-7{-ms-flex-order:7;order:7}.order-xl-8{-ms-flex-order:8;order:8}.order-xl-9{-ms-flex-order:9;order:9}.order-xl-10{-ms-flex-order:10;order:10}.order-xl-11{-ms-flex-order:11;order:11}.order-xl-12{-ms-flex-order:12;order:12}}.flex-row{-ms-flex-direction:row!important;flex-direction:row!important}.flex-column{-ms-flex-direction:column!important;flex-direction:column!important}.flex-row-reverse{-ms-flex-direction:row-reverse!important;flex-direction:row-reverse!important}.flex-column-reverse{-ms-flex-direction:column-reverse!important;flex-direction:column-reverse!important}.flex-wrap{-ms-flex-wrap:wrap!important;flex-wrap:wrap!important}.flex-nowrap{-ms-flex-wrap:nowrap!important;flex-wrap:nowrap!important}.flex-wrap-reverse{-ms-flex-wrap:wrap-reverse!important;flex-wrap:wrap-reverse!important}.justify-content-start{-ms-flex-pack:start!important;justify-content:flex-start!important}.justify-content-end{-ms-flex-pack:end!important;justify-content:flex-end!important}.justify-content-center{-ms-flex-pack:center!important;justify-content:center!important}.justify-content-between{-ms-flex-pack:justify!important;justify-content:space-between!important}.justify-content-around{-ms-flex-pack:distribute!important;justify-content:space-around!important}.align-items-start{-ms-flex-align:start!important;align-items:flex-start!important}.align-items-end{-ms-flex-align:end!important;align-items:flex-end!important}.align-items-center{-ms-flex-align:center!important;align-items:center!important}.align-items-baseline{-ms-flex-align:baseline!important;align-items:baseline!important}.align-items-stretch{-ms-flex-align:stretch!important;align-items:stretch!important}.align-content-start{-ms-flex-line-pack:start!important;align-content:flex-start!important}.align-content-end{-ms-flex-line-pack:end!important;align-content:flex-end!important}.align-content-center{-ms-flex-line-pack:center!important;align-content:center!important}.align-content-between{-ms-flex-line-pack:justify!important;align-content:space-between!important}.align-content-around{-ms-flex-line-pack:distribute!important;align-content:space-around!important}.align-content-stretch{-ms-flex-line-pack:stretch!important;align-content:stretch!important}.align-self-auto{-ms-flex-item-align:auto!important;align-self:auto!important}.align-self-start{-ms-flex-item-align:start!important;align-self:flex-start!important}.align-self-end{-ms-flex-item-align:end!important;align-self:flex-end!important}.align-self-center{-ms-flex-item-align:center!important;align-self:center!important}.align-self-baseline{-ms-flex-item-align:baseline!important;align-self:baseline!important}.align-self-stretch{-ms-flex-item-align:stretch!important;align-self:stretch!important}@media (min-width:576px){.flex-sm-row{-ms-flex-direction:row!important;flex-direction:row!important}.flex-sm-column{-ms-flex-direction:column!important;flex-direction:column!important}.flex-sm-row-reverse{-ms-flex-direction:row-reverse!important;flex-direction:row-reverse!important}.flex-sm-column-reverse{-ms-flex-direction:column-reverse!important;flex-direction:column-reverse!important}.flex-sm-wrap{-ms-flex-wrap:wrap!important;flex-wrap:wrap!important}.flex-sm-nowrap{-ms-flex-wrap:nowrap!important;flex-wrap:nowrap!important}.flex-sm-wrap-reverse{-ms-flex-wrap:wrap-reverse!important;flex-wrap:wrap-reverse!important}.justify-content-sm-start{-ms-flex-pack:start!important;justify-content:flex-start!important}.justify-content-sm-end{-ms-flex-pack:end!important;justify-content:flex-end!important}.justify-content-sm-center{-ms-flex-pack:center!important;justify-content:center!important}.justify-content-sm-between{-ms-flex-pack:justify!important;justify-content:space-between!important}.justify-content-sm-around{-ms-flex-pack:distribute!important;justify-content:space-around!important}.align-items-sm-start{-ms-flex-align:start!important;align-items:flex-start!important}.align-items-sm-end{-ms-flex-align:end!important;align-items:flex-end!important}.align-items-sm-center{-ms-flex-align:center!important;align-items:center!important}.align-items-sm-baseline{-ms-flex-align:baseline!important;align-items:baseline!important}.align-items-sm-stretch{-ms-flex-align:stretch!important;align-items:stretch!important}.align-content-sm-start{-ms-flex-line-pack:start!important;align-content:flex-start!important}.align-content-sm-end{-ms-flex-line-pack:end!important;align-content:flex-end!important}.align-content-sm-center{-ms-flex-line-pack:center!important;align-content:center!important}.align-content-sm-between{-ms-flex-line-pack:justify!important;align-content:space-between!important}.align-content-sm-around{-ms-flex-line-pack:distribute!important;align-content:space-around!important}.align-content-sm-stretch{-ms-flex-line-pack:stretch!important;align-content:stretch!important}.align-self-sm-auto{-ms-flex-item-align:auto!important;align-self:auto!important}.align-self-sm-start{-ms-flex-item-align:start!important;align-self:flex-start!important}.align-self-sm-end{-ms-flex-item-align:end!important;align-self:flex-end!important}.align-self-sm-center{-ms-flex-item-align:center!important;align-self:center!important}.align-self-sm-baseline{-ms-flex-item-align:baseline!important;align-self:baseline!important}.align-self-sm-stretch{-ms-flex-item-align:stretch!important;align-self:stretch!important}}@media (min-width:768px){.flex-md-row{-ms-flex-direction:row!important;flex-direction:row!important}.flex-md-column{-ms-flex-direction:column!important;flex-direction:column!important}.flex-md-row-reverse{-ms-flex-direction:row-reverse!important;flex-direction:row-reverse!important}.flex-md-column-reverse{-ms-flex-direction:column-reverse!important;flex-direction:column-reverse!important}.flex-md-wrap{-ms-flex-wrap:wrap!important;flex-wrap:wrap!important}.flex-md-nowrap{-ms-flex-wrap:nowrap!important;flex-wrap:nowrap!important}.flex-md-wrap-reverse{-ms-flex-wrap:wrap-reverse!important;flex-wrap:wrap-reverse!important}.justify-content-md-start{-ms-flex-pack:start!important;justify-content:flex-start!important}.justify-content-md-end{-ms-flex-pack:end!important;justify-content:flex-end!important}.justify-content-md-center{-ms-flex-pack:center!important;justify-content:center!important}.justify-content-md-between{-ms-flex-pack:justify!important;justify-content:space-between!important}.justify-content-md-around{-ms-flex-pack:distribute!important;justify-content:space-around!important}.align-items-md-start{-ms-flex-align:start!important;align-items:flex-start!important}.align-items-md-end{-ms-flex-align:end!important;align-items:flex-end!important}.align-items-md-center{-ms-flex-align:center!important;align-items:center!important}.align-items-md-baseline{-ms-flex-align:baseline!important;align-items:baseline!important}.align-items-md-stretch{-ms-flex-align:stretch!important;align-items:stretch!important}.align-content-md-start{-ms-flex-line-pack:start!important;align-content:flex-start!important}.align-content-md-end{-ms-flex-line-pack:end!important;align-content:flex-end!important}.align-content-md-center{-ms-flex-line-pack:center!important;align-content:center!important}.align-content-md-between{-ms-flex-line-pack:justify!important;align-content:space-between!important}.align-content-md-around{-ms-flex-line-pack:distribute!important;align-content:space-around!important}.align-content-md-stretch{-ms-flex-line-pack:stretch!important;align-content:stretch!important}.align-self-md-auto{-ms-flex-item-align:auto!important;align-self:auto!important}.align-self-md-start{-ms-flex-item-align:start!important;align-self:flex-start!important}.align-self-md-end{-ms-flex-item-align:end!important;align-self:flex-end!important}.align-self-md-center{-ms-flex-item-align:center!important;align-self:center!important}.align-self-md-baseline{-ms-flex-item-align:baseline!important;align-self:baseline!important}.align-self-md-stretch{-ms-flex-item-align:stretch!important;align-self:stretch!important}}@media (min-width:992px){.flex-lg-row{-ms-flex-direction:row!important;flex-direction:row!important}.flex-lg-column{-ms-flex-direction:column!important;flex-direction:column!important}.flex-lg-row-reverse{-ms-flex-direction:row-reverse!important;flex-direction:row-reverse!important}.flex-lg-column-reverse{-ms-flex-direction:column-reverse!important;flex-direction:column-reverse!important}.flex-lg-wrap{-ms-flex-wrap:wrap!important;flex-wrap:wrap!important}.flex-lg-nowrap{-ms-flex-wrap:nowrap!important;flex-wrap:nowrap!important}.flex-lg-wrap-reverse{-ms-flex-wrap:wrap-reverse!important;flex-wrap:wrap-reverse!important}.justify-content-lg-start{-ms-flex-pack:start!important;justify-content:flex-start!important}.justify-content-lg-end{-ms-flex-pack:end!important;justify-content:flex-end!important}.justify-content-lg-center{-ms-flex-pack:center!important;justify-content:center!important}.justify-content-lg-between{-ms-flex-pack:justify!important;justify-content:space-between!important}.justify-content-lg-around{-ms-flex-pack:distribute!important;justify-content:space-around!important}.align-items-lg-start{-ms-flex-align:start!important;align-items:flex-start!important}.align-items-lg-end{-ms-flex-align:end!important;align-items:flex-end!important}.align-items-lg-center{-ms-flex-align:center!important;align-items:center!important}.align-items-lg-baseline{-ms-flex-align:baseline!important;align-items:baseline!important}.align-items-lg-stretch{-ms-flex-align:stretch!important;align-items:stretch!important}.align-content-lg-start{-ms-flex-line-pack:start!important;align-content:flex-start!important}.align-content-lg-end{-ms-flex-line-pack:end!important;align-content:flex-end!important}.align-content-lg-center{-ms-flex-line-pack:center!important;align-content:center!important}.align-content-lg-between{-ms-flex-line-pack:justify!important;align-content:space-between!important}.align-content-lg-around{-ms-flex-line-pack:distribute!important;align-content:space-around!important}.align-content-lg-stretch{-ms-flex-line-pack:stretch!important;align-content:stretch!important}.align-self-lg-auto{-ms-flex-item-align:auto!important;align-self:auto!important}.align-self-lg-start{-ms-flex-item-align:start!important;align-self:flex-start!important}.align-self-lg-end{-ms-flex-item-align:end!important;align-self:flex-end!important}.align-self-lg-center{-ms-flex-item-align:center!important;align-self:center!important}.align-self-lg-baseline{-ms-flex-item-align:baseline!important;align-self:baseline!important}.align-self-lg-stretch{-ms-flex-item-align:stretch!important;align-self:stretch!important}}@media (min-width:1200px){.flex-xl-row{-ms-flex-direction:row!important;flex-direction:row!important}.flex-xl-column{-ms-flex-direction:column!important;flex-direction:column!important}.flex-xl-row-reverse{-ms-flex-direction:row-reverse!important;flex-direction:row-reverse!important}.flex-xl-column-reverse{-ms-flex-direction:column-reverse!important;flex-direction:column-reverse!important}.flex-xl-wrap{-ms-flex-wrap:wrap!important;flex-wrap:wrap!important}.flex-xl-nowrap{-ms-flex-wrap:nowrap!important;flex-wrap:nowrap!important}.flex-xl-wrap-reverse{-ms-flex-wrap:wrap-reverse!important;flex-wrap:wrap-reverse!important}.justify-content-xl-start{-ms-flex-pack:start!important;justify-content:flex-start!important}.justify-content-xl-end{-ms-flex-pack:end!important;justify-content:flex-end!important}.justify-content-xl-center{-ms-flex-pack:center!important;justify-content:center!important}.justify-content-xl-between{-ms-flex-pack:justify!important;justify-content:space-between!important}.justify-content-xl-around{-ms-flex-pack:distribute!important;justify-content:space-around!important}.align-items-xl-start{-ms-flex-align:start!important;align-items:flex-start!important}.align-items-xl-end{-ms-flex-align:end!important;align-items:flex-end!important}.align-items-xl-center{-ms-flex-align:center!important;align-items:center!important}.align-items-xl-baseline{-ms-flex-align:baseline!important;align-items:baseline!important}.align-items-xl-stretch{-ms-flex-align:stretch!important;align-items:stretch!important}.align-content-xl-start{-ms-flex-line-pack:start!important;align-content:flex-start!important}.align-content-xl-end{-ms-flex-line-pack:end!important;align-content:flex-end!important}.align-content-xl-center{-ms-flex-line-pack:center!important;align-content:center!important}.align-content-xl-between{-ms-flex-line-pack:justify!important;align-content:space-between!important}.align-content-xl-around{-ms-flex-line-pack:distribute!important;align-content:space-around!important}.align-content-xl-stretch{-ms-flex-line-pack:stretch!important;align-content:stretch!important}.align-self-xl-auto{-ms-flex-item-align:auto!important;align-self:auto!important}.align-self-xl-start{-ms-flex-item-align:start!important;align-self:flex-start!important}.align-self-xl-end{-ms-flex-item-align:end!important;align-self:flex-end!important}.align-self-xl-center{-ms-flex-item-align:center!important;align-self:center!important}.align-self-xl-baseline{-ms-flex-item-align:baseline!important;align-self:baseline!important}.align-self-xl-stretch{-ms-flex-item-align:stretch!important;align-self:stretch!important}}
+/*# sourceMappingURL=bootstrap-grid.min.css.map */ \ No newline at end of file
diff --git a/library/bootstrap/css/bootstrap-grid.min.css.map b/library/bootstrap/css/bootstrap-grid.min.css.map
new file mode 100644
index 000000000..5e16e09e5
--- /dev/null
+++ b/library/bootstrap/css/bootstrap-grid.min.css.map
@@ -0,0 +1 @@
+{"version":3,"sources":["../../scss/bootstrap-grid.scss","dist/css/bootstrap-grid.css","../../scss/_grid.scss","../../scss/mixins/_grid.scss","../../scss/mixins/_breakpoints.scss","../../scss/mixins/_grid-framework.scss","../../scss/utilities/_flex.scss"],"names":[],"mappings":"AAUE,cAAgB,MAAA,aAGlB,KACE,WAAA,WACA,mBAAA,UAGF,ECPA,QADA,SDWE,WAAA,QEhBA,WCAA,aAAA,KACA,YAAA,KACA,cAAA,KACA,aAAA,KACA,MAAA,KC+CE,yBFnDF,WCYI,UAAA,OCuCF,yBFnDF,WCYI,UAAA,OCuCF,yBFnDF,WCYI,UAAA,OCuCF,0BFnDF,WCYI,UAAA,QDAJ,iBACE,MAAA,KCbF,aAAA,KACA,YAAA,KACA,cAAA,KACA,aAAA,KACA,MAAA,KDmBA,KCLA,QAAA,YAAA,QAAA,KACA,cAAA,KAAA,UAAA,KACA,aAAA,MACA,YAAA,MDQA,YACE,aAAA,EACA,YAAA,EAFF,iBDqCF,0BC/BM,cAAA,EACA,aAAA,EGlCJ,KAAA,OAAA,QAAA,QAAA,QAAA,OAAA,OAAA,OAAA,OAAA,OAAA,OAAA,OAAA,OJsEF,UAEqJ,QAAvI,UAAmG,WAAY,WAAY,WAAhH,UAAW,UAAW,UAAW,UAAW,UAAW,UAAW,UAAW,UACtG,aAFqJ,QAAvI,UAAmG,WAAY,WAAY,WAAhH,UAAW,UAAW,UAAW,UAAW,UAAW,UAAW,UAAW,UACtG,aAFkJ,QAAvI,UAAmG,WAAY,WAAY,WAAhH,UAAW,UAAW,UAAW,UAAW,UAAW,UAAW,UAAW,UACnG,aAEqJ,QAAvI,UAAmG,WAAY,WAAY,WAAhH,UAAW,UAAW,UAAW,UAAW,UAAW,UAAW,UAAW,UACtG,aIzEI,SAAA,SACA,MAAA,KACA,WAAA,IACA,cAAA,KACA,aAAA,KAmBE,KACE,wBAAA,EAAA,WAAA,EACA,kBAAA,EAAA,UAAA,EACA,UAAA,KAEF,UACE,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KACA,MAAA,KACA,UAAA,KAIA,OFFN,SAAA,EAAA,EAAA,UAAA,KAAA,EAAA,EAAA,UAIA,UAAA,UEFM,OFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,OFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,OFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,OFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,OFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,OFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,OFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,OFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,QFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,QFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,QFFN,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KAIA,UAAA,KEIM,SACE,eAAA,EAAA,MAAA,EADF,SACE,eAAA,EAAA,MAAA,EADF,SACE,eAAA,EAAA,MAAA,EADF,SACE,eAAA,EAAA,MAAA,EADF,SACE,eAAA,EAAA,MAAA,EADF,SACE,eAAA,EAAA,MAAA,EADF,SACE,eAAA,EAAA,MAAA,EADF,SACE,eAAA,EAAA,MAAA,EADF,SACE,eAAA,EAAA,MAAA,EADF,UACE,eAAA,GAAA,MAAA,GADF,UACE,eAAA,GAAA,MAAA,GADF,UACE,eAAA,GAAA,MAAA,GDMN,yBCzBE,QACE,wBAAA,EAAA,WAAA,EACA,kBAAA,EAAA,UAAA,EACA,UAAA,KAEF,aACE,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KACA,MAAA,KACA,UAAA,KAIA,UFFN,SAAA,EAAA,EAAA,UAAA,KAAA,EAAA,EAAA,UAIA,UAAA,UEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,WFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,WFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,WFFN,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KAIA,UAAA,KEIM,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,aACE,eAAA,GAAA,MAAA,GADF,aACE,eAAA,GAAA,MAAA,GADF,aACE,eAAA,GAAA,MAAA,IDMN,yBCzBE,QACE,wBAAA,EAAA,WAAA,EACA,kBAAA,EAAA,UAAA,EACA,UAAA,KAEF,aACE,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KACA,MAAA,KACA,UAAA,KAIA,UFFN,SAAA,EAAA,EAAA,UAAA,KAAA,EAAA,EAAA,UAIA,UAAA,UEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,WFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,WFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,WFFN,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KAIA,UAAA,KEIM,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,aACE,eAAA,GAAA,MAAA,GADF,aACE,eAAA,GAAA,MAAA,GADF,aACE,eAAA,GAAA,MAAA,IDMN,yBCzBE,QACE,wBAAA,EAAA,WAAA,EACA,kBAAA,EAAA,UAAA,EACA,UAAA,KAEF,aACE,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KACA,MAAA,KACA,UAAA,KAIA,UFFN,SAAA,EAAA,EAAA,UAAA,KAAA,EAAA,EAAA,UAIA,UAAA,UEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,WFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,WFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,WFFN,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KAIA,UAAA,KEIM,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,aACE,eAAA,GAAA,MAAA,GADF,aACE,eAAA,GAAA,MAAA,GADF,aACE,eAAA,GAAA,MAAA,IDMN,0BCzBE,QACE,wBAAA,EAAA,WAAA,EACA,kBAAA,EAAA,UAAA,EACA,UAAA,KAEF,aACE,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KACA,MAAA,KACA,UAAA,KAIA,UFFN,SAAA,EAAA,EAAA,UAAA,KAAA,EAAA,EAAA,UAIA,UAAA,UEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,WFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,WFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,WFFN,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KAIA,UAAA,KEIM,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,aACE,eAAA,GAAA,MAAA,GADF,aACE,eAAA,GAAA,MAAA,GADF,aACE,eAAA,GAAA,MAAA,IC1CN,UAAgC,mBAAA,cAAA,eAAA,cAChC,aAAgC,mBAAA,iBAAA,eAAA,iBAChC,kBAAgC,mBAAA,sBAAA,eAAA,sBAChC,qBAAgC,mBAAA,yBAAA,eAAA,yBAEhC,WAA8B,cAAA,eAAA,UAAA,eAC9B,aAA8B,cAAA,iBAAA,UAAA,iBAC9B,mBAA8B,cAAA,uBAAA,UAAA,uBAE9B,uBAAoC,cAAA,gBAAA,gBAAA,qBACpC,qBAAoC,cAAA,cAAA,gBAAA,mBACpC,wBAAoC,cAAA,iBAAA,gBAAA,iBACpC,yBAAoC,cAAA,kBAAA,gBAAA,wBACpC,wBAAoC,cAAA,qBAAA,gBAAA,uBAEpC,mBAAiC,eAAA,gBAAA,YAAA,qBACjC,iBAAiC,eAAA,cAAA,YAAA,mBACjC,oBAAiC,eAAA,iBAAA,YAAA,iBACjC,sBAAiC,eAAA,mBAAA,YAAA,mBACjC,qBAAiC,eAAA,kBAAA,YAAA,kBAEjC,qBAAkC,mBAAA,gBAAA,cAAA,qBAClC,mBAAkC,mBAAA,cAAA,cAAA,mBAClC,sBAAkC,mBAAA,iBAAA,cAAA,iBAClC,uBAAkC,mBAAA,kBAAA,cAAA,wBAClC,sBAAkC,mBAAA,qBAAA,cAAA,uBAClC,uBAAkC,mBAAA,kBAAA,cAAA,kBAElC,iBAAgC,oBAAA,eAAA,WAAA,eAChC,kBAAgC,oBAAA,gBAAA,WAAA,qBAChC,gBAAgC,oBAAA,cAAA,WAAA,mBAChC,mBAAgC,oBAAA,iBAAA,WAAA,iBAChC,qBAAgC,oBAAA,mBAAA,WAAA,mBAChC,oBAAgC,oBAAA,kBAAA,WAAA,kBFehC,yBEhDA,aAAgC,mBAAA,cAAA,eAAA,cAChC,gBAAgC,mBAAA,iBAAA,eAAA,iBAChC,qBAAgC,mBAAA,sBAAA,eAAA,sBAChC,wBAAgC,mBAAA,yBAAA,eAAA,yBAEhC,cAA8B,cAAA,eAAA,UAAA,eAC9B,gBAA8B,cAAA,iBAAA,UAAA,iBAC9B,sBAA8B,cAAA,uBAAA,UAAA,uBAE9B,0BAAoC,cAAA,gBAAA,gBAAA,qBACpC,wBAAoC,cAAA,cAAA,gBAAA,mBACpC,2BAAoC,cAAA,iBAAA,gBAAA,iBACpC,4BAAoC,cAAA,kBAAA,gBAAA,wBACpC,2BAAoC,cAAA,qBAAA,gBAAA,uBAEpC,sBAAiC,eAAA,gBAAA,YAAA,qBACjC,oBAAiC,eAAA,cAAA,YAAA,mBACjC,uBAAiC,eAAA,iBAAA,YAAA,iBACjC,yBAAiC,eAAA,mBAAA,YAAA,mBACjC,wBAAiC,eAAA,kBAAA,YAAA,kBAEjC,wBAAkC,mBAAA,gBAAA,cAAA,qBAClC,sBAAkC,mBAAA,cAAA,cAAA,mBAClC,yBAAkC,mBAAA,iBAAA,cAAA,iBAClC,0BAAkC,mBAAA,kBAAA,cAAA,wBAClC,yBAAkC,mBAAA,qBAAA,cAAA,uBAClC,0BAAkC,mBAAA,kBAAA,cAAA,kBAElC,oBAAgC,oBAAA,eAAA,WAAA,eAChC,qBAAgC,oBAAA,gBAAA,WAAA,qBAChC,mBAAgC,oBAAA,cAAA,WAAA,mBAChC,sBAAgC,oBAAA,iBAAA,WAAA,iBAChC,wBAAgC,oBAAA,mBAAA,WAAA,mBAChC,uBAAgC,oBAAA,kBAAA,WAAA,mBFehC,yBEhDA,aAAgC,mBAAA,cAAA,eAAA,cAChC,gBAAgC,mBAAA,iBAAA,eAAA,iBAChC,qBAAgC,mBAAA,sBAAA,eAAA,sBAChC,wBAAgC,mBAAA,yBAAA,eAAA,yBAEhC,cAA8B,cAAA,eAAA,UAAA,eAC9B,gBAA8B,cAAA,iBAAA,UAAA,iBAC9B,sBAA8B,cAAA,uBAAA,UAAA,uBAE9B,0BAAoC,cAAA,gBAAA,gBAAA,qBACpC,wBAAoC,cAAA,cAAA,gBAAA,mBACpC,2BAAoC,cAAA,iBAAA,gBAAA,iBACpC,4BAAoC,cAAA,kBAAA,gBAAA,wBACpC,2BAAoC,cAAA,qBAAA,gBAAA,uBAEpC,sBAAiC,eAAA,gBAAA,YAAA,qBACjC,oBAAiC,eAAA,cAAA,YAAA,mBACjC,uBAAiC,eAAA,iBAAA,YAAA,iBACjC,yBAAiC,eAAA,mBAAA,YAAA,mBACjC,wBAAiC,eAAA,kBAAA,YAAA,kBAEjC,wBAAkC,mBAAA,gBAAA,cAAA,qBAClC,sBAAkC,mBAAA,cAAA,cAAA,mBAClC,yBAAkC,mBAAA,iBAAA,cAAA,iBAClC,0BAAkC,mBAAA,kBAAA,cAAA,wBAClC,yBAAkC,mBAAA,qBAAA,cAAA,uBAClC,0BAAkC,mBAAA,kBAAA,cAAA,kBAElC,oBAAgC,oBAAA,eAAA,WAAA,eAChC,qBAAgC,oBAAA,gBAAA,WAAA,qBAChC,mBAAgC,oBAAA,cAAA,WAAA,mBAChC,sBAAgC,oBAAA,iBAAA,WAAA,iBAChC,wBAAgC,oBAAA,mBAAA,WAAA,mBAChC,uBAAgC,oBAAA,kBAAA,WAAA,mBFehC,yBEhDA,aAAgC,mBAAA,cAAA,eAAA,cAChC,gBAAgC,mBAAA,iBAAA,eAAA,iBAChC,qBAAgC,mBAAA,sBAAA,eAAA,sBAChC,wBAAgC,mBAAA,yBAAA,eAAA,yBAEhC,cAA8B,cAAA,eAAA,UAAA,eAC9B,gBAA8B,cAAA,iBAAA,UAAA,iBAC9B,sBAA8B,cAAA,uBAAA,UAAA,uBAE9B,0BAAoC,cAAA,gBAAA,gBAAA,qBACpC,wBAAoC,cAAA,cAAA,gBAAA,mBACpC,2BAAoC,cAAA,iBAAA,gBAAA,iBACpC,4BAAoC,cAAA,kBAAA,gBAAA,wBACpC,2BAAoC,cAAA,qBAAA,gBAAA,uBAEpC,sBAAiC,eAAA,gBAAA,YAAA,qBACjC,oBAAiC,eAAA,cAAA,YAAA,mBACjC,uBAAiC,eAAA,iBAAA,YAAA,iBACjC,yBAAiC,eAAA,mBAAA,YAAA,mBACjC,wBAAiC,eAAA,kBAAA,YAAA,kBAEjC,wBAAkC,mBAAA,gBAAA,cAAA,qBAClC,sBAAkC,mBAAA,cAAA,cAAA,mBAClC,yBAAkC,mBAAA,iBAAA,cAAA,iBAClC,0BAAkC,mBAAA,kBAAA,cAAA,wBAClC,yBAAkC,mBAAA,qBAAA,cAAA,uBAClC,0BAAkC,mBAAA,kBAAA,cAAA,kBAElC,oBAAgC,oBAAA,eAAA,WAAA,eAChC,qBAAgC,oBAAA,gBAAA,WAAA,qBAChC,mBAAgC,oBAAA,cAAA,WAAA,mBAChC,sBAAgC,oBAAA,iBAAA,WAAA,iBAChC,wBAAgC,oBAAA,mBAAA,WAAA,mBAChC,uBAAgC,oBAAA,kBAAA,WAAA,mBFehC,0BEhDA,aAAgC,mBAAA,cAAA,eAAA,cAChC,gBAAgC,mBAAA,iBAAA,eAAA,iBAChC,qBAAgC,mBAAA,sBAAA,eAAA,sBAChC,wBAAgC,mBAAA,yBAAA,eAAA,yBAEhC,cAA8B,cAAA,eAAA,UAAA,eAC9B,gBAA8B,cAAA,iBAAA,UAAA,iBAC9B,sBAA8B,cAAA,uBAAA,UAAA,uBAE9B,0BAAoC,cAAA,gBAAA,gBAAA,qBACpC,wBAAoC,cAAA,cAAA,gBAAA,mBACpC,2BAAoC,cAAA,iBAAA,gBAAA,iBACpC,4BAAoC,cAAA,kBAAA,gBAAA,wBACpC,2BAAoC,cAAA,qBAAA,gBAAA,uBAEpC,sBAAiC,eAAA,gBAAA,YAAA,qBACjC,oBAAiC,eAAA,cAAA,YAAA,mBACjC,uBAAiC,eAAA,iBAAA,YAAA,iBACjC,yBAAiC,eAAA,mBAAA,YAAA,mBACjC,wBAAiC,eAAA,kBAAA,YAAA,kBAEjC,wBAAkC,mBAAA,gBAAA,cAAA,qBAClC,sBAAkC,mBAAA,cAAA,cAAA,mBAClC,yBAAkC,mBAAA,iBAAA,cAAA,iBAClC,0BAAkC,mBAAA,kBAAA,cAAA,wBAClC,yBAAkC,mBAAA,qBAAA,cAAA,uBAClC,0BAAkC,mBAAA,kBAAA,cAAA,kBAElC,oBAAgC,oBAAA,eAAA,WAAA,eAChC,qBAAgC,oBAAA,gBAAA,WAAA,qBAChC,mBAAgC,oBAAA,cAAA,WAAA,mBAChC,sBAAgC,oBAAA,iBAAA,WAAA,iBAChC,wBAAgC,oBAAA,mBAAA,WAAA,mBAChC,uBAAgC,oBAAA,kBAAA,WAAA","sourcesContent":["// Bootstrap Grid only\n//\n// Includes relevant variables and mixins for the flexbox grid\n// system, as well as the generated predefined classes (e.g., `.col-sm-4`).\n\n//\n// Box sizing, responsive, and more\n//\n\n@at-root {\n @-ms-viewport { width: device-width; }\n}\n\nhtml {\n box-sizing: border-box;\n -ms-overflow-style: scrollbar;\n}\n\n*,\n*::before,\n*::after {\n box-sizing: inherit;\n}\n\n@import \"functions\";\n@import \"variables\";\n\n//\n// Grid mixins\n//\n\n@import \"mixins/breakpoints\";\n@import \"mixins/grid-framework\";\n@import \"mixins/grid\";\n\n@import \"grid\";\n@import \"utilities/flex\";\n","@-ms-viewport {\n width: device-width;\n}\n\nhtml {\n box-sizing: border-box;\n -ms-overflow-style: scrollbar;\n}\n\n*,\n*::before,\n*::after {\n box-sizing: inherit;\n}\n\n.container {\n margin-right: auto;\n margin-left: auto;\n padding-right: 15px;\n padding-left: 15px;\n width: 100%;\n}\n\n@media (min-width: 576px) {\n .container {\n max-width: 540px;\n }\n}\n\n@media (min-width: 768px) {\n .container {\n max-width: 720px;\n }\n}\n\n@media (min-width: 992px) {\n .container {\n max-width: 960px;\n }\n}\n\n@media (min-width: 1200px) {\n .container {\n max-width: 1140px;\n }\n}\n\n.container-fluid {\n width: 100%;\n margin-right: auto;\n margin-left: auto;\n padding-right: 15px;\n padding-left: 15px;\n width: 100%;\n}\n\n.row {\n display: -ms-flexbox;\n display: flex;\n -ms-flex-wrap: wrap;\n flex-wrap: wrap;\n margin-right: -15px;\n margin-left: -15px;\n}\n\n.no-gutters {\n margin-right: 0;\n margin-left: 0;\n}\n\n.no-gutters > .col,\n.no-gutters > [class*=\"col-\"] {\n padding-right: 0;\n padding-left: 0;\n}\n\n.col-1, .col-2, .col-3, .col-4, .col-5, .col-6, .col-7, .col-8, .col-9, .col-10, .col-11, .col-12, .col,\n.col-auto, .col-sm-1, .col-sm-2, .col-sm-3, .col-sm-4, .col-sm-5, .col-sm-6, .col-sm-7, .col-sm-8, .col-sm-9, .col-sm-10, .col-sm-11, .col-sm-12, .col-sm,\n.col-sm-auto, .col-md-1, .col-md-2, .col-md-3, .col-md-4, .col-md-5, .col-md-6, .col-md-7, .col-md-8, .col-md-9, .col-md-10, .col-md-11, .col-md-12, .col-md,\n.col-md-auto, .col-lg-1, .col-lg-2, .col-lg-3, .col-lg-4, .col-lg-5, .col-lg-6, .col-lg-7, .col-lg-8, .col-lg-9, .col-lg-10, .col-lg-11, .col-lg-12, .col-lg,\n.col-lg-auto, .col-xl-1, .col-xl-2, .col-xl-3, .col-xl-4, .col-xl-5, .col-xl-6, .col-xl-7, .col-xl-8, .col-xl-9, .col-xl-10, .col-xl-11, .col-xl-12, .col-xl,\n.col-xl-auto {\n position: relative;\n width: 100%;\n min-height: 1px;\n padding-right: 15px;\n padding-left: 15px;\n}\n\n.col {\n -ms-flex-preferred-size: 0;\n flex-basis: 0;\n -ms-flex-positive: 1;\n flex-grow: 1;\n max-width: 100%;\n}\n\n.col-auto {\n -ms-flex: 0 0 auto;\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n}\n\n.col-1 {\n -ms-flex: 0 0 8.333333%;\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n}\n\n.col-2 {\n -ms-flex: 0 0 16.666667%;\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n}\n\n.col-3 {\n -ms-flex: 0 0 25%;\n flex: 0 0 25%;\n max-width: 25%;\n}\n\n.col-4 {\n -ms-flex: 0 0 33.333333%;\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n}\n\n.col-5 {\n -ms-flex: 0 0 41.666667%;\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n}\n\n.col-6 {\n -ms-flex: 0 0 50%;\n flex: 0 0 50%;\n max-width: 50%;\n}\n\n.col-7 {\n -ms-flex: 0 0 58.333333%;\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n}\n\n.col-8 {\n -ms-flex: 0 0 66.666667%;\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n}\n\n.col-9 {\n -ms-flex: 0 0 75%;\n flex: 0 0 75%;\n max-width: 75%;\n}\n\n.col-10 {\n -ms-flex: 0 0 83.333333%;\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n}\n\n.col-11 {\n -ms-flex: 0 0 91.666667%;\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n}\n\n.col-12 {\n -ms-flex: 0 0 100%;\n flex: 0 0 100%;\n max-width: 100%;\n}\n\n.order-1 {\n -ms-flex-order: 1;\n order: 1;\n}\n\n.order-2 {\n -ms-flex-order: 2;\n order: 2;\n}\n\n.order-3 {\n -ms-flex-order: 3;\n order: 3;\n}\n\n.order-4 {\n -ms-flex-order: 4;\n order: 4;\n}\n\n.order-5 {\n -ms-flex-order: 5;\n order: 5;\n}\n\n.order-6 {\n -ms-flex-order: 6;\n order: 6;\n}\n\n.order-7 {\n -ms-flex-order: 7;\n order: 7;\n}\n\n.order-8 {\n -ms-flex-order: 8;\n order: 8;\n}\n\n.order-9 {\n -ms-flex-order: 9;\n order: 9;\n}\n\n.order-10 {\n -ms-flex-order: 10;\n order: 10;\n}\n\n.order-11 {\n -ms-flex-order: 11;\n order: 11;\n}\n\n.order-12 {\n -ms-flex-order: 12;\n order: 12;\n}\n\n@media (min-width: 576px) {\n .col-sm {\n -ms-flex-preferred-size: 0;\n flex-basis: 0;\n -ms-flex-positive: 1;\n flex-grow: 1;\n max-width: 100%;\n }\n .col-sm-auto {\n -ms-flex: 0 0 auto;\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n }\n .col-sm-1 {\n -ms-flex: 0 0 8.333333%;\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n }\n .col-sm-2 {\n -ms-flex: 0 0 16.666667%;\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n }\n .col-sm-3 {\n -ms-flex: 0 0 25%;\n flex: 0 0 25%;\n max-width: 25%;\n }\n .col-sm-4 {\n -ms-flex: 0 0 33.333333%;\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n }\n .col-sm-5 {\n -ms-flex: 0 0 41.666667%;\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n }\n .col-sm-6 {\n -ms-flex: 0 0 50%;\n flex: 0 0 50%;\n max-width: 50%;\n }\n .col-sm-7 {\n -ms-flex: 0 0 58.333333%;\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n }\n .col-sm-8 {\n -ms-flex: 0 0 66.666667%;\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n }\n .col-sm-9 {\n -ms-flex: 0 0 75%;\n flex: 0 0 75%;\n max-width: 75%;\n }\n .col-sm-10 {\n -ms-flex: 0 0 83.333333%;\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n }\n .col-sm-11 {\n -ms-flex: 0 0 91.666667%;\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n }\n .col-sm-12 {\n -ms-flex: 0 0 100%;\n flex: 0 0 100%;\n max-width: 100%;\n }\n .order-sm-1 {\n -ms-flex-order: 1;\n order: 1;\n }\n .order-sm-2 {\n -ms-flex-order: 2;\n order: 2;\n }\n .order-sm-3 {\n -ms-flex-order: 3;\n order: 3;\n }\n .order-sm-4 {\n -ms-flex-order: 4;\n order: 4;\n }\n .order-sm-5 {\n -ms-flex-order: 5;\n order: 5;\n }\n .order-sm-6 {\n -ms-flex-order: 6;\n order: 6;\n }\n .order-sm-7 {\n -ms-flex-order: 7;\n order: 7;\n }\n .order-sm-8 {\n -ms-flex-order: 8;\n order: 8;\n }\n .order-sm-9 {\n -ms-flex-order: 9;\n order: 9;\n }\n .order-sm-10 {\n -ms-flex-order: 10;\n order: 10;\n }\n .order-sm-11 {\n -ms-flex-order: 11;\n order: 11;\n }\n .order-sm-12 {\n -ms-flex-order: 12;\n order: 12;\n }\n}\n\n@media (min-width: 768px) {\n .col-md {\n -ms-flex-preferred-size: 0;\n flex-basis: 0;\n -ms-flex-positive: 1;\n flex-grow: 1;\n max-width: 100%;\n }\n .col-md-auto {\n -ms-flex: 0 0 auto;\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n }\n .col-md-1 {\n -ms-flex: 0 0 8.333333%;\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n }\n .col-md-2 {\n -ms-flex: 0 0 16.666667%;\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n }\n .col-md-3 {\n -ms-flex: 0 0 25%;\n flex: 0 0 25%;\n max-width: 25%;\n }\n .col-md-4 {\n -ms-flex: 0 0 33.333333%;\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n }\n .col-md-5 {\n -ms-flex: 0 0 41.666667%;\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n }\n .col-md-6 {\n -ms-flex: 0 0 50%;\n flex: 0 0 50%;\n max-width: 50%;\n }\n .col-md-7 {\n -ms-flex: 0 0 58.333333%;\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n }\n .col-md-8 {\n -ms-flex: 0 0 66.666667%;\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n }\n .col-md-9 {\n -ms-flex: 0 0 75%;\n flex: 0 0 75%;\n max-width: 75%;\n }\n .col-md-10 {\n -ms-flex: 0 0 83.333333%;\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n }\n .col-md-11 {\n -ms-flex: 0 0 91.666667%;\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n }\n .col-md-12 {\n -ms-flex: 0 0 100%;\n flex: 0 0 100%;\n max-width: 100%;\n }\n .order-md-1 {\n -ms-flex-order: 1;\n order: 1;\n }\n .order-md-2 {\n -ms-flex-order: 2;\n order: 2;\n }\n .order-md-3 {\n -ms-flex-order: 3;\n order: 3;\n }\n .order-md-4 {\n -ms-flex-order: 4;\n order: 4;\n }\n .order-md-5 {\n -ms-flex-order: 5;\n order: 5;\n }\n .order-md-6 {\n -ms-flex-order: 6;\n order: 6;\n }\n .order-md-7 {\n -ms-flex-order: 7;\n order: 7;\n }\n .order-md-8 {\n -ms-flex-order: 8;\n order: 8;\n }\n .order-md-9 {\n -ms-flex-order: 9;\n order: 9;\n }\n .order-md-10 {\n -ms-flex-order: 10;\n order: 10;\n }\n .order-md-11 {\n -ms-flex-order: 11;\n order: 11;\n }\n .order-md-12 {\n -ms-flex-order: 12;\n order: 12;\n }\n}\n\n@media (min-width: 992px) {\n .col-lg {\n -ms-flex-preferred-size: 0;\n flex-basis: 0;\n -ms-flex-positive: 1;\n flex-grow: 1;\n max-width: 100%;\n }\n .col-lg-auto {\n -ms-flex: 0 0 auto;\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n }\n .col-lg-1 {\n -ms-flex: 0 0 8.333333%;\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n }\n .col-lg-2 {\n -ms-flex: 0 0 16.666667%;\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n }\n .col-lg-3 {\n -ms-flex: 0 0 25%;\n flex: 0 0 25%;\n max-width: 25%;\n }\n .col-lg-4 {\n -ms-flex: 0 0 33.333333%;\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n }\n .col-lg-5 {\n -ms-flex: 0 0 41.666667%;\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n }\n .col-lg-6 {\n -ms-flex: 0 0 50%;\n flex: 0 0 50%;\n max-width: 50%;\n }\n .col-lg-7 {\n -ms-flex: 0 0 58.333333%;\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n }\n .col-lg-8 {\n -ms-flex: 0 0 66.666667%;\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n }\n .col-lg-9 {\n -ms-flex: 0 0 75%;\n flex: 0 0 75%;\n max-width: 75%;\n }\n .col-lg-10 {\n -ms-flex: 0 0 83.333333%;\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n }\n .col-lg-11 {\n -ms-flex: 0 0 91.666667%;\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n }\n .col-lg-12 {\n -ms-flex: 0 0 100%;\n flex: 0 0 100%;\n max-width: 100%;\n }\n .order-lg-1 {\n -ms-flex-order: 1;\n order: 1;\n }\n .order-lg-2 {\n -ms-flex-order: 2;\n order: 2;\n }\n .order-lg-3 {\n -ms-flex-order: 3;\n order: 3;\n }\n .order-lg-4 {\n -ms-flex-order: 4;\n order: 4;\n }\n .order-lg-5 {\n -ms-flex-order: 5;\n order: 5;\n }\n .order-lg-6 {\n -ms-flex-order: 6;\n order: 6;\n }\n .order-lg-7 {\n -ms-flex-order: 7;\n order: 7;\n }\n .order-lg-8 {\n -ms-flex-order: 8;\n order: 8;\n }\n .order-lg-9 {\n -ms-flex-order: 9;\n order: 9;\n }\n .order-lg-10 {\n -ms-flex-order: 10;\n order: 10;\n }\n .order-lg-11 {\n -ms-flex-order: 11;\n order: 11;\n }\n .order-lg-12 {\n -ms-flex-order: 12;\n order: 12;\n }\n}\n\n@media (min-width: 1200px) {\n .col-xl {\n -ms-flex-preferred-size: 0;\n flex-basis: 0;\n -ms-flex-positive: 1;\n flex-grow: 1;\n max-width: 100%;\n }\n .col-xl-auto {\n -ms-flex: 0 0 auto;\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n }\n .col-xl-1 {\n -ms-flex: 0 0 8.333333%;\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n }\n .col-xl-2 {\n -ms-flex: 0 0 16.666667%;\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n }\n .col-xl-3 {\n -ms-flex: 0 0 25%;\n flex: 0 0 25%;\n max-width: 25%;\n }\n .col-xl-4 {\n -ms-flex: 0 0 33.333333%;\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n }\n .col-xl-5 {\n -ms-flex: 0 0 41.666667%;\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n }\n .col-xl-6 {\n -ms-flex: 0 0 50%;\n flex: 0 0 50%;\n max-width: 50%;\n }\n .col-xl-7 {\n -ms-flex: 0 0 58.333333%;\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n }\n .col-xl-8 {\n -ms-flex: 0 0 66.666667%;\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n }\n .col-xl-9 {\n -ms-flex: 0 0 75%;\n flex: 0 0 75%;\n max-width: 75%;\n }\n .col-xl-10 {\n -ms-flex: 0 0 83.333333%;\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n }\n .col-xl-11 {\n -ms-flex: 0 0 91.666667%;\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n }\n .col-xl-12 {\n -ms-flex: 0 0 100%;\n flex: 0 0 100%;\n max-width: 100%;\n }\n .order-xl-1 {\n -ms-flex-order: 1;\n order: 1;\n }\n .order-xl-2 {\n -ms-flex-order: 2;\n order: 2;\n }\n .order-xl-3 {\n -ms-flex-order: 3;\n order: 3;\n }\n .order-xl-4 {\n -ms-flex-order: 4;\n order: 4;\n }\n .order-xl-5 {\n -ms-flex-order: 5;\n order: 5;\n }\n .order-xl-6 {\n -ms-flex-order: 6;\n order: 6;\n }\n .order-xl-7 {\n -ms-flex-order: 7;\n order: 7;\n }\n .order-xl-8 {\n -ms-flex-order: 8;\n order: 8;\n }\n .order-xl-9 {\n -ms-flex-order: 9;\n order: 9;\n }\n .order-xl-10 {\n -ms-flex-order: 10;\n order: 10;\n }\n .order-xl-11 {\n -ms-flex-order: 11;\n order: 11;\n }\n .order-xl-12 {\n -ms-flex-order: 12;\n order: 12;\n }\n}\n\n.flex-row {\n -ms-flex-direction: row !important;\n flex-direction: row !important;\n}\n\n.flex-column {\n -ms-flex-direction: column !important;\n flex-direction: column !important;\n}\n\n.flex-row-reverse {\n -ms-flex-direction: row-reverse !important;\n flex-direction: row-reverse !important;\n}\n\n.flex-column-reverse {\n -ms-flex-direction: column-reverse !important;\n flex-direction: column-reverse !important;\n}\n\n.flex-wrap {\n -ms-flex-wrap: wrap !important;\n flex-wrap: wrap !important;\n}\n\n.flex-nowrap {\n -ms-flex-wrap: nowrap !important;\n flex-wrap: nowrap !important;\n}\n\n.flex-wrap-reverse {\n -ms-flex-wrap: wrap-reverse !important;\n flex-wrap: wrap-reverse !important;\n}\n\n.justify-content-start {\n -ms-flex-pack: start !important;\n justify-content: flex-start !important;\n}\n\n.justify-content-end {\n -ms-flex-pack: end !important;\n justify-content: flex-end !important;\n}\n\n.justify-content-center {\n -ms-flex-pack: center !important;\n justify-content: center !important;\n}\n\n.justify-content-between {\n -ms-flex-pack: justify !important;\n justify-content: space-between !important;\n}\n\n.justify-content-around {\n -ms-flex-pack: distribute !important;\n justify-content: space-around !important;\n}\n\n.align-items-start {\n -ms-flex-align: start !important;\n align-items: flex-start !important;\n}\n\n.align-items-end {\n -ms-flex-align: end !important;\n align-items: flex-end !important;\n}\n\n.align-items-center {\n -ms-flex-align: center !important;\n align-items: center !important;\n}\n\n.align-items-baseline {\n -ms-flex-align: baseline !important;\n align-items: baseline !important;\n}\n\n.align-items-stretch {\n -ms-flex-align: stretch !important;\n align-items: stretch !important;\n}\n\n.align-content-start {\n -ms-flex-line-pack: start !important;\n align-content: flex-start !important;\n}\n\n.align-content-end {\n -ms-flex-line-pack: end !important;\n align-content: flex-end !important;\n}\n\n.align-content-center {\n -ms-flex-line-pack: center !important;\n align-content: center !important;\n}\n\n.align-content-between {\n -ms-flex-line-pack: justify !important;\n align-content: space-between !important;\n}\n\n.align-content-around {\n -ms-flex-line-pack: distribute !important;\n align-content: space-around !important;\n}\n\n.align-content-stretch {\n -ms-flex-line-pack: stretch !important;\n align-content: stretch !important;\n}\n\n.align-self-auto {\n -ms-flex-item-align: auto !important;\n align-self: auto !important;\n}\n\n.align-self-start {\n -ms-flex-item-align: start !important;\n align-self: flex-start !important;\n}\n\n.align-self-end {\n -ms-flex-item-align: end !important;\n align-self: flex-end !important;\n}\n\n.align-self-center {\n -ms-flex-item-align: center !important;\n align-self: center !important;\n}\n\n.align-self-baseline {\n -ms-flex-item-align: baseline !important;\n align-self: baseline !important;\n}\n\n.align-self-stretch {\n -ms-flex-item-align: stretch !important;\n align-self: stretch !important;\n}\n\n@media (min-width: 576px) {\n .flex-sm-row {\n -ms-flex-direction: row !important;\n flex-direction: row !important;\n }\n .flex-sm-column {\n -ms-flex-direction: column !important;\n flex-direction: column !important;\n }\n .flex-sm-row-reverse {\n -ms-flex-direction: row-reverse !important;\n flex-direction: row-reverse !important;\n }\n .flex-sm-column-reverse {\n -ms-flex-direction: column-reverse !important;\n flex-direction: column-reverse !important;\n }\n .flex-sm-wrap {\n -ms-flex-wrap: wrap !important;\n flex-wrap: wrap !important;\n }\n .flex-sm-nowrap {\n -ms-flex-wrap: nowrap !important;\n flex-wrap: nowrap !important;\n }\n .flex-sm-wrap-reverse {\n -ms-flex-wrap: wrap-reverse !important;\n flex-wrap: wrap-reverse !important;\n }\n .justify-content-sm-start {\n -ms-flex-pack: start !important;\n justify-content: flex-start !important;\n }\n .justify-content-sm-end {\n -ms-flex-pack: end !important;\n justify-content: flex-end !important;\n }\n .justify-content-sm-center {\n -ms-flex-pack: center !important;\n justify-content: center !important;\n }\n .justify-content-sm-between {\n -ms-flex-pack: justify !important;\n justify-content: space-between !important;\n }\n .justify-content-sm-around {\n -ms-flex-pack: distribute !important;\n justify-content: space-around !important;\n }\n .align-items-sm-start {\n -ms-flex-align: start !important;\n align-items: flex-start !important;\n }\n .align-items-sm-end {\n -ms-flex-align: end !important;\n align-items: flex-end !important;\n }\n .align-items-sm-center {\n -ms-flex-align: center !important;\n align-items: center !important;\n }\n .align-items-sm-baseline {\n -ms-flex-align: baseline !important;\n align-items: baseline !important;\n }\n .align-items-sm-stretch {\n -ms-flex-align: stretch !important;\n align-items: stretch !important;\n }\n .align-content-sm-start {\n -ms-flex-line-pack: start !important;\n align-content: flex-start !important;\n }\n .align-content-sm-end {\n -ms-flex-line-pack: end !important;\n align-content: flex-end !important;\n }\n .align-content-sm-center {\n -ms-flex-line-pack: center !important;\n align-content: center !important;\n }\n .align-content-sm-between {\n -ms-flex-line-pack: justify !important;\n align-content: space-between !important;\n }\n .align-content-sm-around {\n -ms-flex-line-pack: distribute !important;\n align-content: space-around !important;\n }\n .align-content-sm-stretch {\n -ms-flex-line-pack: stretch !important;\n align-content: stretch !important;\n }\n .align-self-sm-auto {\n -ms-flex-item-align: auto !important;\n align-self: auto !important;\n }\n .align-self-sm-start {\n -ms-flex-item-align: start !important;\n align-self: flex-start !important;\n }\n .align-self-sm-end {\n -ms-flex-item-align: end !important;\n align-self: flex-end !important;\n }\n .align-self-sm-center {\n -ms-flex-item-align: center !important;\n align-self: center !important;\n }\n .align-self-sm-baseline {\n -ms-flex-item-align: baseline !important;\n align-self: baseline !important;\n }\n .align-self-sm-stretch {\n -ms-flex-item-align: stretch !important;\n align-self: stretch !important;\n }\n}\n\n@media (min-width: 768px) {\n .flex-md-row {\n -ms-flex-direction: row !important;\n flex-direction: row !important;\n }\n .flex-md-column {\n -ms-flex-direction: column !important;\n flex-direction: column !important;\n }\n .flex-md-row-reverse {\n -ms-flex-direction: row-reverse !important;\n flex-direction: row-reverse !important;\n }\n .flex-md-column-reverse {\n -ms-flex-direction: column-reverse !important;\n flex-direction: column-reverse !important;\n }\n .flex-md-wrap {\n -ms-flex-wrap: wrap !important;\n flex-wrap: wrap !important;\n }\n .flex-md-nowrap {\n -ms-flex-wrap: nowrap !important;\n flex-wrap: nowrap !important;\n }\n .flex-md-wrap-reverse {\n -ms-flex-wrap: wrap-reverse !important;\n flex-wrap: wrap-reverse !important;\n }\n .justify-content-md-start {\n -ms-flex-pack: start !important;\n justify-content: flex-start !important;\n }\n .justify-content-md-end {\n -ms-flex-pack: end !important;\n justify-content: flex-end !important;\n }\n .justify-content-md-center {\n -ms-flex-pack: center !important;\n justify-content: center !important;\n }\n .justify-content-md-between {\n -ms-flex-pack: justify !important;\n justify-content: space-between !important;\n }\n .justify-content-md-around {\n -ms-flex-pack: distribute !important;\n justify-content: space-around !important;\n }\n .align-items-md-start {\n -ms-flex-align: start !important;\n align-items: flex-start !important;\n }\n .align-items-md-end {\n -ms-flex-align: end !important;\n align-items: flex-end !important;\n }\n .align-items-md-center {\n -ms-flex-align: center !important;\n align-items: center !important;\n }\n .align-items-md-baseline {\n -ms-flex-align: baseline !important;\n align-items: baseline !important;\n }\n .align-items-md-stretch {\n -ms-flex-align: stretch !important;\n align-items: stretch !important;\n }\n .align-content-md-start {\n -ms-flex-line-pack: start !important;\n align-content: flex-start !important;\n }\n .align-content-md-end {\n -ms-flex-line-pack: end !important;\n align-content: flex-end !important;\n }\n .align-content-md-center {\n -ms-flex-line-pack: center !important;\n align-content: center !important;\n }\n .align-content-md-between {\n -ms-flex-line-pack: justify !important;\n align-content: space-between !important;\n }\n .align-content-md-around {\n -ms-flex-line-pack: distribute !important;\n align-content: space-around !important;\n }\n .align-content-md-stretch {\n -ms-flex-line-pack: stretch !important;\n align-content: stretch !important;\n }\n .align-self-md-auto {\n -ms-flex-item-align: auto !important;\n align-self: auto !important;\n }\n .align-self-md-start {\n -ms-flex-item-align: start !important;\n align-self: flex-start !important;\n }\n .align-self-md-end {\n -ms-flex-item-align: end !important;\n align-self: flex-end !important;\n }\n .align-self-md-center {\n -ms-flex-item-align: center !important;\n align-self: center !important;\n }\n .align-self-md-baseline {\n -ms-flex-item-align: baseline !important;\n align-self: baseline !important;\n }\n .align-self-md-stretch {\n -ms-flex-item-align: stretch !important;\n align-self: stretch !important;\n }\n}\n\n@media (min-width: 992px) {\n .flex-lg-row {\n -ms-flex-direction: row !important;\n flex-direction: row !important;\n }\n .flex-lg-column {\n -ms-flex-direction: column !important;\n flex-direction: column !important;\n }\n .flex-lg-row-reverse {\n -ms-flex-direction: row-reverse !important;\n flex-direction: row-reverse !important;\n }\n .flex-lg-column-reverse {\n -ms-flex-direction: column-reverse !important;\n flex-direction: column-reverse !important;\n }\n .flex-lg-wrap {\n -ms-flex-wrap: wrap !important;\n flex-wrap: wrap !important;\n }\n .flex-lg-nowrap {\n -ms-flex-wrap: nowrap !important;\n flex-wrap: nowrap !important;\n }\n .flex-lg-wrap-reverse {\n -ms-flex-wrap: wrap-reverse !important;\n flex-wrap: wrap-reverse !important;\n }\n .justify-content-lg-start {\n -ms-flex-pack: start !important;\n justify-content: flex-start !important;\n }\n .justify-content-lg-end {\n -ms-flex-pack: end !important;\n justify-content: flex-end !important;\n }\n .justify-content-lg-center {\n -ms-flex-pack: center !important;\n justify-content: center !important;\n }\n .justify-content-lg-between {\n -ms-flex-pack: justify !important;\n justify-content: space-between !important;\n }\n .justify-content-lg-around {\n -ms-flex-pack: distribute !important;\n justify-content: space-around !important;\n }\n .align-items-lg-start {\n -ms-flex-align: start !important;\n align-items: flex-start !important;\n }\n .align-items-lg-end {\n -ms-flex-align: end !important;\n align-items: flex-end !important;\n }\n .align-items-lg-center {\n -ms-flex-align: center !important;\n align-items: center !important;\n }\n .align-items-lg-baseline {\n -ms-flex-align: baseline !important;\n align-items: baseline !important;\n }\n .align-items-lg-stretch {\n -ms-flex-align: stretch !important;\n align-items: stretch !important;\n }\n .align-content-lg-start {\n -ms-flex-line-pack: start !important;\n align-content: flex-start !important;\n }\n .align-content-lg-end {\n -ms-flex-line-pack: end !important;\n align-content: flex-end !important;\n }\n .align-content-lg-center {\n -ms-flex-line-pack: center !important;\n align-content: center !important;\n }\n .align-content-lg-between {\n -ms-flex-line-pack: justify !important;\n align-content: space-between !important;\n }\n .align-content-lg-around {\n -ms-flex-line-pack: distribute !important;\n align-content: space-around !important;\n }\n .align-content-lg-stretch {\n -ms-flex-line-pack: stretch !important;\n align-content: stretch !important;\n }\n .align-self-lg-auto {\n -ms-flex-item-align: auto !important;\n align-self: auto !important;\n }\n .align-self-lg-start {\n -ms-flex-item-align: start !important;\n align-self: flex-start !important;\n }\n .align-self-lg-end {\n -ms-flex-item-align: end !important;\n align-self: flex-end !important;\n }\n .align-self-lg-center {\n -ms-flex-item-align: center !important;\n align-self: center !important;\n }\n .align-self-lg-baseline {\n -ms-flex-item-align: baseline !important;\n align-self: baseline !important;\n }\n .align-self-lg-stretch {\n -ms-flex-item-align: stretch !important;\n align-self: stretch !important;\n }\n}\n\n@media (min-width: 1200px) {\n .flex-xl-row {\n -ms-flex-direction: row !important;\n flex-direction: row !important;\n }\n .flex-xl-column {\n -ms-flex-direction: column !important;\n flex-direction: column !important;\n }\n .flex-xl-row-reverse {\n -ms-flex-direction: row-reverse !important;\n flex-direction: row-reverse !important;\n }\n .flex-xl-column-reverse {\n -ms-flex-direction: column-reverse !important;\n flex-direction: column-reverse !important;\n }\n .flex-xl-wrap {\n -ms-flex-wrap: wrap !important;\n flex-wrap: wrap !important;\n }\n .flex-xl-nowrap {\n -ms-flex-wrap: nowrap !important;\n flex-wrap: nowrap !important;\n }\n .flex-xl-wrap-reverse {\n -ms-flex-wrap: wrap-reverse !important;\n flex-wrap: wrap-reverse !important;\n }\n .justify-content-xl-start {\n -ms-flex-pack: start !important;\n justify-content: flex-start !important;\n }\n .justify-content-xl-end {\n -ms-flex-pack: end !important;\n justify-content: flex-end !important;\n }\n .justify-content-xl-center {\n -ms-flex-pack: center !important;\n justify-content: center !important;\n }\n .justify-content-xl-between {\n -ms-flex-pack: justify !important;\n justify-content: space-between !important;\n }\n .justify-content-xl-around {\n -ms-flex-pack: distribute !important;\n justify-content: space-around !important;\n }\n .align-items-xl-start {\n -ms-flex-align: start !important;\n align-items: flex-start !important;\n }\n .align-items-xl-end {\n -ms-flex-align: end !important;\n align-items: flex-end !important;\n }\n .align-items-xl-center {\n -ms-flex-align: center !important;\n align-items: center !important;\n }\n .align-items-xl-baseline {\n -ms-flex-align: baseline !important;\n align-items: baseline !important;\n }\n .align-items-xl-stretch {\n -ms-flex-align: stretch !important;\n align-items: stretch !important;\n }\n .align-content-xl-start {\n -ms-flex-line-pack: start !important;\n align-content: flex-start !important;\n }\n .align-content-xl-end {\n -ms-flex-line-pack: end !important;\n align-content: flex-end !important;\n }\n .align-content-xl-center {\n -ms-flex-line-pack: center !important;\n align-content: center !important;\n }\n .align-content-xl-between {\n -ms-flex-line-pack: justify !important;\n align-content: space-between !important;\n }\n .align-content-xl-around {\n -ms-flex-line-pack: distribute !important;\n align-content: space-around !important;\n }\n .align-content-xl-stretch {\n -ms-flex-line-pack: stretch !important;\n align-content: stretch !important;\n }\n .align-self-xl-auto {\n -ms-flex-item-align: auto !important;\n align-self: auto !important;\n }\n .align-self-xl-start {\n -ms-flex-item-align: start !important;\n align-self: flex-start !important;\n }\n .align-self-xl-end {\n -ms-flex-item-align: end !important;\n align-self: flex-end !important;\n }\n .align-self-xl-center {\n -ms-flex-item-align: center !important;\n align-self: center !important;\n }\n .align-self-xl-baseline {\n -ms-flex-item-align: baseline !important;\n align-self: baseline !important;\n }\n .align-self-xl-stretch {\n -ms-flex-item-align: stretch !important;\n align-self: stretch !important;\n }\n}\n/*# sourceMappingURL=bootstrap-grid.css.map */","// Container widths\n//\n// Set the container width, and override it for fixed navbars in media queries.\n\n@if $enable-grid-classes {\n .container {\n @include make-container();\n @include make-container-max-widths();\n }\n}\n\n// Fluid container\n//\n// Utilizes the mixin meant for fixed width containers, but with 100% width for\n// fluid, full width layouts.\n\n@if $enable-grid-classes {\n .container-fluid {\n width: 100%;\n @include make-container();\n }\n}\n\n// Row\n//\n// Rows contain and clear the floats of your columns.\n\n@if $enable-grid-classes {\n .row {\n @include make-row();\n }\n\n // Remove the negative margin from default .row, then the horizontal padding\n // from all immediate children columns (to prevent runaway style inheritance).\n .no-gutters {\n margin-right: 0;\n margin-left: 0;\n\n > .col,\n > [class*=\"col-\"] {\n padding-right: 0;\n padding-left: 0;\n }\n }\n}\n\n// Columns\n//\n// Common styles for small and large grid columns\n\n@if $enable-grid-classes {\n @include make-grid-columns();\n}\n","/// Grid system\n//\n// Generate semantic grid columns with these mixins.\n\n@mixin make-container() {\n margin-right: auto;\n margin-left: auto;\n padding-right: ($grid-gutter-width / 2);\n padding-left: ($grid-gutter-width / 2);\n width: 100%;\n}\n\n\n// For each breakpoint, define the maximum width of the container in a media query\n@mixin make-container-max-widths($max-widths: $container-max-widths, $breakpoints: $grid-breakpoints) {\n @each $breakpoint, $container-max-width in $max-widths {\n @include media-breakpoint-up($breakpoint, $breakpoints) {\n max-width: $container-max-width;\n }\n }\n}\n\n@mixin make-row() {\n display: flex;\n flex-wrap: wrap;\n margin-right: ($grid-gutter-width / -2);\n margin-left: ($grid-gutter-width / -2);\n}\n\n@mixin make-col-ready() {\n position: relative;\n // Prevent columns from becoming too narrow when at smaller grid tiers by\n // always setting `width: 100%;`. This works because we use `flex` values\n // later on to override this initial width.\n width: 100%;\n min-height: 1px; // Prevent collapsing\n padding-right: ($grid-gutter-width / 2);\n padding-left: ($grid-gutter-width / 2);\n}\n\n@mixin make-col($size, $columns: $grid-columns) {\n flex: 0 0 percentage($size / $columns);\n // Add a `max-width` to ensure content within each column does not blow out\n // the width of the column. Applies to IE10+ and Firefox. Chrome and Safari\n // do not appear to require this.\n max-width: percentage($size / $columns);\n}\n","// Breakpoint viewport sizes and media queries.\n//\n// Breakpoints are defined as a map of (name: minimum width), order from small to large:\n//\n// (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px)\n//\n// The map defined in the `$grid-breakpoints` global variable is used as the `$breakpoints` argument by default.\n\n// Name of the next breakpoint, or null for the last breakpoint.\n//\n// >> breakpoint-next(sm)\n// md\n// >> breakpoint-next(sm, (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px))\n// md\n// >> breakpoint-next(sm, $breakpoint-names: (xs sm md lg xl))\n// md\n@function breakpoint-next($name, $breakpoints: $grid-breakpoints, $breakpoint-names: map-keys($breakpoints)) {\n $n: index($breakpoint-names, $name);\n @return if($n < length($breakpoint-names), nth($breakpoint-names, $n + 1), null);\n}\n\n// Minimum breakpoint width. Null for the smallest (first) breakpoint.\n//\n// >> breakpoint-min(sm, (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px))\n// 576px\n@function breakpoint-min($name, $breakpoints: $grid-breakpoints) {\n $min: map-get($breakpoints, $name);\n @return if($min != 0, $min, null);\n}\n\n// Maximum breakpoint width. Null for the largest (last) breakpoint.\n// The maximum value is calculated as the minimum of the next one less 0.1.\n//\n// >> breakpoint-max(sm, (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px))\n// 767px\n@function breakpoint-max($name, $breakpoints: $grid-breakpoints) {\n $next: breakpoint-next($name, $breakpoints);\n @return if($next, breakpoint-min($next, $breakpoints) - 1px, null);\n}\n\n// Returns a blank string if smallest breakpoint, otherwise returns the name with a dash infront.\n// Useful for making responsive utilities.\n//\n// >> breakpoint-infix(xs, (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px))\n// \"\" (Returns a blank string)\n// >> breakpoint-infix(sm, (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px))\n// \"-sm\"\n@function breakpoint-infix($name, $breakpoints: $grid-breakpoints) {\n @return if(breakpoint-min($name, $breakpoints) == null, \"\", \"-#{$name}\");\n}\n\n// Media of at least the minimum breakpoint width. No query for the smallest breakpoint.\n// Makes the @content apply to the given breakpoint and wider.\n@mixin media-breakpoint-up($name, $breakpoints: $grid-breakpoints) {\n $min: breakpoint-min($name, $breakpoints);\n @if $min {\n @media (min-width: $min) {\n @content;\n }\n } @else {\n @content;\n }\n}\n\n// Media of at most the maximum breakpoint width. No query for the largest breakpoint.\n// Makes the @content apply to the given breakpoint and narrower.\n@mixin media-breakpoint-down($name, $breakpoints: $grid-breakpoints) {\n $max: breakpoint-max($name, $breakpoints);\n @if $max {\n @media (max-width: $max) {\n @content;\n }\n } @else {\n @content;\n }\n}\n\n// Media that spans multiple breakpoint widths.\n// Makes the @content apply between the min and max breakpoints\n@mixin media-breakpoint-between($lower, $upper, $breakpoints: $grid-breakpoints) {\n $min: breakpoint-min($lower, $breakpoints);\n $max: breakpoint-max($upper, $breakpoints);\n\n @media (min-width: $min) and (max-width: $max) {\n @content;\n }\n}\n\n// Media between the breakpoint's minimum and maximum widths.\n// No minimum for the smallest breakpoint, and no maximum for the largest one.\n// Makes the @content apply only to the given breakpoint, not viewports any wider or narrower.\n@mixin media-breakpoint-only($name, $breakpoints: $grid-breakpoints) {\n $min: breakpoint-min($name, $breakpoints);\n $max: breakpoint-max($name, $breakpoints);\n\n @if $min != null and $max != null {\n @media (min-width: $min) and (max-width: $max) {\n @content;\n }\n } @else if $max == null {\n @include media-breakpoint-up($name)\n } @else if $min == null {\n @include media-breakpoint-down($name)\n }\n}\n","// Framework grid generation\n//\n// Used only by Bootstrap to generate the correct number of grid classes given\n// any value of `$grid-columns`.\n\n@mixin make-grid-columns($columns: $grid-columns, $gutter: $grid-gutter-width, $breakpoints: $grid-breakpoints) {\n // Common properties for all breakpoints\n %grid-column {\n position: relative;\n width: 100%;\n min-height: 1px; // Prevent columns from collapsing when empty\n padding-right: ($gutter / 2);\n padding-left: ($gutter / 2);\n }\n\n @each $breakpoint in map-keys($breakpoints) {\n $infix: breakpoint-infix($breakpoint, $breakpoints);\n\n // Allow columns to stretch full width below their breakpoints\n @for $i from 1 through $columns {\n .col#{$infix}-#{$i} {\n @extend %grid-column;\n }\n }\n .col#{$infix},\n .col#{$infix}-auto {\n @extend %grid-column;\n }\n\n @include media-breakpoint-up($breakpoint, $breakpoints) {\n // Provide basic `.col-{bp}` classes for equal-width flexbox columns\n .col#{$infix} {\n flex-basis: 0;\n flex-grow: 1;\n max-width: 100%;\n }\n .col#{$infix}-auto {\n flex: 0 0 auto;\n width: auto;\n max-width: none; // Reset earlier grid tiers\n }\n\n @for $i from 1 through $columns {\n .col#{$infix}-#{$i} {\n @include make-col($i, $columns);\n }\n }\n\n @for $i from 1 through $columns {\n .order#{$infix}-#{$i} {\n order: $i;\n }\n }\n }\n }\n}\n","// Flex variation\n//\n// Custom styles for additional flex alignment options.\n\n@each $breakpoint in map-keys($grid-breakpoints) {\n @include media-breakpoint-up($breakpoint) {\n $infix: breakpoint-infix($breakpoint, $grid-breakpoints);\n\n .flex#{$infix}-row { flex-direction: row !important; }\n .flex#{$infix}-column { flex-direction: column !important; }\n .flex#{$infix}-row-reverse { flex-direction: row-reverse !important; }\n .flex#{$infix}-column-reverse { flex-direction: column-reverse !important; }\n\n .flex#{$infix}-wrap { flex-wrap: wrap !important; }\n .flex#{$infix}-nowrap { flex-wrap: nowrap !important; }\n .flex#{$infix}-wrap-reverse { flex-wrap: wrap-reverse !important; }\n\n .justify-content#{$infix}-start { justify-content: flex-start !important; }\n .justify-content#{$infix}-end { justify-content: flex-end !important; }\n .justify-content#{$infix}-center { justify-content: center !important; }\n .justify-content#{$infix}-between { justify-content: space-between !important; }\n .justify-content#{$infix}-around { justify-content: space-around !important; }\n\n .align-items#{$infix}-start { align-items: flex-start !important; }\n .align-items#{$infix}-end { align-items: flex-end !important; }\n .align-items#{$infix}-center { align-items: center !important; }\n .align-items#{$infix}-baseline { align-items: baseline !important; }\n .align-items#{$infix}-stretch { align-items: stretch !important; }\n\n .align-content#{$infix}-start { align-content: flex-start !important; }\n .align-content#{$infix}-end { align-content: flex-end !important; }\n .align-content#{$infix}-center { align-content: center !important; }\n .align-content#{$infix}-between { align-content: space-between !important; }\n .align-content#{$infix}-around { align-content: space-around !important; }\n .align-content#{$infix}-stretch { align-content: stretch !important; }\n\n .align-self#{$infix}-auto { align-self: auto !important; }\n .align-self#{$infix}-start { align-self: flex-start !important; }\n .align-self#{$infix}-end { align-self: flex-end !important; }\n .align-self#{$infix}-center { align-self: center !important; }\n .align-self#{$infix}-baseline { align-self: baseline !important; }\n .align-self#{$infix}-stretch { align-self: stretch !important; }\n }\n}\n"]} \ No newline at end of file
diff --git a/library/bootstrap/css/bootstrap-reboot.css b/library/bootstrap/css/bootstrap-reboot.css
new file mode 100644
index 000000000..867ee1771
--- /dev/null
+++ b/library/bootstrap/css/bootstrap-reboot.css
@@ -0,0 +1,330 @@
+html {
+ box-sizing: border-box;
+ font-family: sans-serif;
+ line-height: 1.15;
+ -webkit-text-size-adjust: 100%;
+ -ms-text-size-adjust: 100%;
+ -ms-overflow-style: scrollbar;
+ -webkit-tap-highlight-color: transparent;
+}
+
+*,
+*::before,
+*::after {
+ box-sizing: inherit;
+}
+
+@-ms-viewport {
+ width: device-width;
+}
+
+article, aside, dialog, figcaption, figure, footer, header, hgroup, main, nav, section {
+ display: block;
+}
+
+body {
+ margin: 0;
+ font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, "Helvetica Neue", Arial, sans-serif;
+ font-size: 1rem;
+ font-weight: normal;
+ line-height: 1.5;
+ color: #212529;
+ background-color: #fff;
+}
+
+[tabindex="-1"]:focus {
+ outline: none !important;
+}
+
+hr {
+ box-sizing: content-box;
+ height: 0;
+ overflow: visible;
+}
+
+h1, h2, h3, h4, h5, h6 {
+ margin-top: 0;
+ margin-bottom: .5rem;
+}
+
+p {
+ margin-top: 0;
+ margin-bottom: 1rem;
+}
+
+abbr[title],
+abbr[data-original-title] {
+ text-decoration: underline;
+ -webkit-text-decoration: underline dotted;
+ text-decoration: underline dotted;
+ cursor: help;
+ border-bottom: 0;
+}
+
+address {
+ margin-bottom: 1rem;
+ font-style: normal;
+ line-height: inherit;
+}
+
+ol,
+ul,
+dl {
+ margin-top: 0;
+ margin-bottom: 1rem;
+}
+
+ol ol,
+ul ul,
+ol ul,
+ul ol {
+ margin-bottom: 0;
+}
+
+dt {
+ font-weight: bold;
+}
+
+dd {
+ margin-bottom: .5rem;
+ margin-left: 0;
+}
+
+blockquote {
+ margin: 0 0 1rem;
+}
+
+dfn {
+ font-style: italic;
+}
+
+b,
+strong {
+ font-weight: bolder;
+}
+
+small {
+ font-size: 80%;
+}
+
+sub,
+sup {
+ position: relative;
+ font-size: 75%;
+ line-height: 0;
+ vertical-align: baseline;
+}
+
+sub {
+ bottom: -.25em;
+}
+
+sup {
+ top: -.5em;
+}
+
+a {
+ color: #007bff;
+ text-decoration: none;
+ background-color: transparent;
+ -webkit-text-decoration-skip: objects;
+}
+
+a:hover {
+ color: #0056b3;
+ text-decoration: underline;
+}
+
+a:not([href]):not([tabindex]) {
+ color: inherit;
+ text-decoration: none;
+}
+
+a:not([href]):not([tabindex]):focus, a:not([href]):not([tabindex]):hover {
+ color: inherit;
+ text-decoration: none;
+}
+
+a:not([href]):not([tabindex]):focus {
+ outline: 0;
+}
+
+pre,
+code,
+kbd,
+samp {
+ font-family: monospace, monospace;
+ font-size: 1em;
+}
+
+pre {
+ margin-top: 0;
+ margin-bottom: 1rem;
+ overflow: auto;
+}
+
+figure {
+ margin: 0 0 1rem;
+}
+
+img {
+ vertical-align: middle;
+ border-style: none;
+}
+
+svg:not(:root) {
+ overflow: hidden;
+}
+
+a,
+area,
+button,
+[role="button"],
+input,
+label,
+select,
+summary,
+textarea {
+ -ms-touch-action: manipulation;
+ touch-action: manipulation;
+}
+
+table {
+ border-collapse: collapse;
+}
+
+caption {
+ padding-top: 0.75rem;
+ padding-bottom: 0.75rem;
+ color: #868e96;
+ text-align: left;
+ caption-side: bottom;
+}
+
+th {
+ text-align: left;
+}
+
+label {
+ display: inline-block;
+ margin-bottom: .5rem;
+}
+
+button:focus {
+ outline: 1px dotted;
+ outline: 5px auto -webkit-focus-ring-color;
+}
+
+input,
+button,
+select,
+optgroup,
+textarea {
+ margin: 0;
+ font-family: inherit;
+ font-size: inherit;
+ line-height: inherit;
+}
+
+button,
+input {
+ overflow: visible;
+}
+
+button,
+select {
+ text-transform: none;
+}
+
+button,
+html [type="button"],
+[type="reset"],
+[type="submit"] {
+ -webkit-appearance: button;
+}
+
+button::-moz-focus-inner,
+[type="button"]::-moz-focus-inner,
+[type="reset"]::-moz-focus-inner,
+[type="submit"]::-moz-focus-inner {
+ padding: 0;
+ border-style: none;
+}
+
+input[type="radio"],
+input[type="checkbox"] {
+ box-sizing: border-box;
+ padding: 0;
+}
+
+input[type="date"],
+input[type="time"],
+input[type="datetime-local"],
+input[type="month"] {
+ -webkit-appearance: listbox;
+}
+
+textarea {
+ overflow: auto;
+ resize: vertical;
+}
+
+fieldset {
+ min-width: 0;
+ padding: 0;
+ margin: 0;
+ border: 0;
+}
+
+legend {
+ display: block;
+ width: 100%;
+ max-width: 100%;
+ padding: 0;
+ margin-bottom: .5rem;
+ font-size: 1.5rem;
+ line-height: inherit;
+ color: inherit;
+ white-space: normal;
+}
+
+progress {
+ vertical-align: baseline;
+}
+
+[type="number"]::-webkit-inner-spin-button,
+[type="number"]::-webkit-outer-spin-button {
+ height: auto;
+}
+
+[type="search"] {
+ outline-offset: -2px;
+ -webkit-appearance: none;
+}
+
+[type="search"]::-webkit-search-cancel-button,
+[type="search"]::-webkit-search-decoration {
+ -webkit-appearance: none;
+}
+
+::-webkit-file-upload-button {
+ font: inherit;
+ -webkit-appearance: button;
+}
+
+output {
+ display: inline-block;
+}
+
+summary {
+ display: list-item;
+}
+
+template {
+ display: none;
+}
+
+[hidden] {
+ display: none !important;
+}
+/*# sourceMappingURL=bootstrap-reboot.css.map */ \ No newline at end of file
diff --git a/library/bootstrap/css/bootstrap-reboot.css.map b/library/bootstrap/css/bootstrap-reboot.css.map
new file mode 100644
index 000000000..425ac48c7
--- /dev/null
+++ b/library/bootstrap/css/bootstrap-reboot.css.map
@@ -0,0 +1 @@
+{"version":3,"sources":["../../scss/_reboot.scss","bootstrap-reboot.css","../../scss/_variables.scss","../../scss/mixins/_hover.scss"],"names":[],"mappings":"AAoBA;EACE,uBAAsB;EACtB,wBAAuB;EACvB,kBAAiB;EACjB,+BAA8B;EAC9B,2BAA0B;EAC1B,8BAA6B;EAC7B,yCAA0C;CAC3C;;AAED;;;EAGE,oBAAmB;CACpB;;AAIC;EAAgB,oBAAmB;CCpBpC;;ADwBD;EACE,eAAc;CACf;;AAOD;EACE,UAAS;EACT,wGEoLiH;EFnLjH,gBEuLmB;EFtLnB,oBE0LyB;EFzLzB,iBE6LoB;EF5LpB,eEEgB;EFDhB,uBERW;CFSZ;;ACzBD;EDiCE,yBAAwB;CACzB;;AAQD;EACE,wBAAuB;EACvB,UAAS;EACT,kBAAiB;CAClB;;AAWD;EACE,cAAa;EACb,qBAAoB;CACrB;;AAMD;EACE,cAAa;EACb,oBAAmB;CACpB;;AASD;;EAEE,2BAA0B;EAC1B,0CAAiC;UAAjC,kCAAiC;EACjC,aAAY;EACZ,iBAAgB;CACjB;;AAED;EACE,oBAAmB;EACnB,mBAAkB;EAClB,qBAAoB;CACrB;;AAED;;;EAGE,cAAa;EACb,oBAAmB;CACpB;;AAED;;;;EAIE,iBAAgB;CACjB;;AAED;EACE,kBEqGqB;CFpGtB;;AAED;EACE,qBAAoB;EACpB,eAAc;CACf;;AAED;EACE,iBAAgB;CACjB;;AAED;EACE,mBAAkB;CACnB;;AAED;;EAEE,oBAAmB;CACpB;;AAED;EACE,eAAc;CACf;;AAOD;;EAEE,mBAAkB;EAClB,eAAc;EACd,eAAc;EACd,yBAAwB;CACzB;;AAED;EAAM,eAAc;CAAK;;AACzB;EAAM,WAAU;CAAK;;AAOrB;EACE,eElHe;EFmHf,sBExB0B;EFyB1B,8BAA6B;EAC7B,sCAAqC;CAMtC;;AG1LG;EHuLA,eE5B4C;EF6B5C,2BE5B6B;CC5JR;;AHkMzB;EACE,eAAc;EACd,sBAAqB;CAUtB;;AGnMG;EH4LA,eAAc;EACd,sBAAqB;CG1LpB;;AHoLL;EAUI,WAAU;CACX;;AAQH;;;;EAIE,kCAAiC;EACjC,eAAc;CACf;;AAED;EAEE,cAAa;EAEb,oBAAmB;EAEnB,eAAc;CACf;;AAOD;EAEE,iBAAgB;CACjB;;AAOD;EACE,uBAAsB;EACtB,mBAAkB;CACnB;;AAED;EACE,iBAAgB;CACjB;;AAaD;;;;;;;;;EASE,+BAA0B;MAA1B,2BAA0B;CAC3B;;AAOD;EACE,0BAAyB;CAC1B;;AAED;EACE,qBEEoC;EFDpC,wBECoC;EFApC,eEpPgB;EFqPhB,iBAAgB;EAChB,qBAAoB;CACrB;;AAED;EAEE,iBAAgB;CACjB;;AAOD;EAEE,sBAAqB;EACrB,qBAAoB;CACrB;;AAMD;EACE,oBAAmB;EACnB,2CAA0C;CAC3C;;AAED;;;;;EAKE,UAAS;EACT,qBAAoB;EACpB,mBAAkB;EAClB,qBAAoB;CACrB;;AAED;;EAEE,kBAAiB;CAClB;;AAED;;EAEE,qBAAoB;CACrB;;AAKD;;;;EAIE,2BAA0B;CAC3B;;AAGD;;;;EAIE,WAAU;EACV,mBAAkB;CACnB;;AAED;;EAEE,uBAAsB;EACtB,WAAU;CACX;;AAGD;;;;EASE,4BAA2B;CAC5B;;AAED;EACE,eAAc;EAEd,iBAAgB;CACjB;;AAED;EAME,aAAY;EAEZ,WAAU;EACV,UAAS;EACT,UAAS;CACV;;AAID;EACE,eAAc;EACd,YAAW;EACX,gBAAe;EACf,WAAU;EACV,qBAAoB;EACpB,kBAAiB;EACjB,qBAAoB;EACpB,eAAc;EACd,oBAAmB;CACpB;;AAED;EACE,yBAAwB;CACzB;;ACpID;;EDyIE,aAAY;CACb;;ACrID;ED4IE,qBAAoB;EACpB,yBAAwB;CACzB;;ACzID;;EDiJE,yBAAwB;CACzB;;AAOD;EACE,cAAa;EACb,2BAA0B;CAC3B;;AAMD;EACE,sBAAqB;CACtB;;AAED;EACE,mBAAkB;CACnB;;AAED;EACE,cAAa;CACd;;ACtJD;ED2JE,yBAAwB;CACzB","file":"bootstrap-reboot.css","sourcesContent":["// scss-lint:disable QualifyingElement, DuplicateProperty, VendorPrefix\n\n// Reboot\n//\n// Normalization of HTML elements, manually forked from Normalize.css to remove\n// styles targeting irrelevant browsers while applying new styles.\n//\n// Normalize is licensed MIT. https://github.com/necolas/normalize.css\n\n\n// Document\n//\n// 1. Change from `box-sizing: content-box` so that `width` is not affected by `padding` or `border`.\n// 2. Change the default font family in all browsers.\n// 3. Correct the line height in all browsers.\n// 4. Prevent adjustments of font size after orientation changes in IE on Windows Phone and in iOS.\n// 5. Setting @viewport causes scrollbars to overlap content in IE11 and Edge, so\n// we force a non-overlapping, non-auto-hiding scrollbar to counteract.\n// 6. Change the default tap highlight to be completely transparent in iOS.\n\nhtml {\n box-sizing: border-box; // 1\n font-family: sans-serif; // 2\n line-height: 1.15; // 3\n -webkit-text-size-adjust: 100%; // 4\n -ms-text-size-adjust: 100%; // 4\n -ms-overflow-style: scrollbar; // 5\n -webkit-tap-highlight-color: rgba(0,0,0,0); // 6\n}\n\n*,\n*::before,\n*::after {\n box-sizing: inherit; // 1\n}\n\n// IE10+ doesn't honor `<meta name=\"viewport\">` in some cases.\n@at-root {\n @-ms-viewport { width: device-width; }\n}\n\n// Shim for \"new\" HTML5 structural elements to display correctly (IE10, older browsers)\narticle, aside, dialog, figcaption, figure, footer, header, hgroup, main, nav, section {\n display: block;\n}\n\n// Body\n//\n// 1. Remove the margin in all browsers.\n// 2. As a best practice, apply a default `background-color`.\n\nbody {\n margin: 0; // 1\n font-family: $font-family-base;\n font-size: $font-size-base;\n font-weight: $font-weight-base;\n line-height: $line-height-base;\n color: $body-color;\n background-color: $body-bg; // 2\n}\n\n// Suppress the focus outline on elements that cannot be accessed via keyboard.\n// This prevents an unwanted focus outline from appearing around elements that\n// might still respond to pointer events.\n//\n// Credit: https://github.com/suitcss/base\n[tabindex=\"-1\"]:focus {\n outline: none !important;\n}\n\n\n// Content grouping\n//\n// 1. Add the correct box sizing in Firefox.\n// 2. Show the overflow in Edge and IE.\n\nhr {\n box-sizing: content-box; // 1\n height: 0; // 1\n overflow: visible; // 2\n}\n\n\n//\n// Typography\n//\n\n// Remove top margins from headings\n//\n// By default, `<h1>`-`<h6>` all receive top and bottom margins. We nuke the top\n// margin for easier control within type scales as it avoids margin collapsing.\nh1, h2, h3, h4, h5, h6 {\n margin-top: 0;\n margin-bottom: .5rem;\n}\n\n// Reset margins on paragraphs\n//\n// Similarly, the top margin on `<p>`s get reset. However, we also reset the\n// bottom margin to use `rem` units instead of `em`.\np {\n margin-top: 0;\n margin-bottom: 1rem;\n}\n\n// Abbreviations\n//\n// 1. Remove the bottom border in Firefox 39-.\n// 2. Add the correct text decoration in Chrome, Edge, IE, Opera, and Safari.\n// 3. Add explicit cursor to indicate changed behavior.\n// 4. Duplicate behavior to the data-* attribute for our tooltip plugin\n\nabbr[title],\nabbr[data-original-title] { // 4\n text-decoration: underline; // 2\n text-decoration: underline dotted; // 2\n cursor: help; // 3\n border-bottom: 0; // 1\n}\n\naddress {\n margin-bottom: 1rem;\n font-style: normal;\n line-height: inherit;\n}\n\nol,\nul,\ndl {\n margin-top: 0;\n margin-bottom: 1rem;\n}\n\nol ol,\nul ul,\nol ul,\nul ol {\n margin-bottom: 0;\n}\n\ndt {\n font-weight: $dt-font-weight;\n}\n\ndd {\n margin-bottom: .5rem;\n margin-left: 0; // Undo browser default\n}\n\nblockquote {\n margin: 0 0 1rem;\n}\n\ndfn {\n font-style: italic; // Add the correct font style in Android 4.3-\n}\n\nb,\nstrong {\n font-weight: bolder; // Add the correct font weight in Chrome, Edge, and Safari\n}\n\nsmall {\n font-size: 80%; // Add the correct font size in all browsers\n}\n\n//\n// Prevent `sub` and `sup` elements from affecting the line height in\n// all browsers.\n//\n\nsub,\nsup {\n position: relative;\n font-size: 75%;\n line-height: 0;\n vertical-align: baseline;\n}\n\nsub { bottom: -.25em; }\nsup { top: -.5em; }\n\n\n//\n// Links\n//\n\na {\n color: $link-color;\n text-decoration: $link-decoration;\n background-color: transparent; // Remove the gray background on active links in IE 10.\n -webkit-text-decoration-skip: objects; // Remove gaps in links underline in iOS 8+ and Safari 8+.\n\n @include hover {\n color: $link-hover-color;\n text-decoration: $link-hover-decoration;\n }\n}\n\n// And undo these styles for placeholder links/named anchors (without href)\n// which have not been made explicitly keyboard-focusable (without tabindex).\n// It would be more straightforward to just use a[href] in previous block, but that\n// causes specificity issues in many other styles that are too complex to fix.\n// See https://github.com/twbs/bootstrap/issues/19402\n\na:not([href]):not([tabindex]) {\n color: inherit;\n text-decoration: none;\n\n @include hover-focus {\n color: inherit;\n text-decoration: none;\n }\n\n &:focus {\n outline: 0;\n }\n}\n\n\n//\n// Code\n//\n\npre,\ncode,\nkbd,\nsamp {\n font-family: monospace, monospace; // Correct the inheritance and scaling of font size in all browsers.\n font-size: 1em; // Correct the odd `em` font sizing in all browsers.\n}\n\npre {\n // Remove browser default top margin\n margin-top: 0;\n // Reset browser default of `1em` to use `rem`s\n margin-bottom: 1rem;\n // Don't allow content to break outside\n overflow: auto;\n}\n\n\n//\n// Figures\n//\n\nfigure {\n // Apply a consistent margin strategy (matches our type styles).\n margin: 0 0 1rem;\n}\n\n\n//\n// Images and content\n//\n\nimg {\n vertical-align: middle;\n border-style: none; // Remove the border on images inside links in IE 10-.\n}\n\nsvg:not(:root) {\n overflow: hidden; // Hide the overflow in IE\n}\n\n\n// Avoid 300ms click delay on touch devices that support the `touch-action` CSS property.\n//\n// In particular, unlike most other browsers, IE11+Edge on Windows 10 on touch devices and IE Mobile 10-11\n// DON'T remove the click delay when `<meta name=\"viewport\" content=\"width=device-width\">` is present.\n// However, they DO support removing the click delay via `touch-action: manipulation`.\n// See:\n// * https://v4-alpha.getbootstrap.com/content/reboot/#click-delay-optimization-for-touch\n// * http://caniuse.com/#feat=css-touch-action\n// * https://patrickhlauke.github.io/touch/tests/results/#suppressing-300ms-delay\n\na,\narea,\nbutton,\n[role=\"button\"],\ninput,\nlabel,\nselect,\nsummary,\ntextarea {\n touch-action: manipulation;\n}\n\n\n//\n// Tables\n//\n\ntable {\n border-collapse: collapse; // Prevent double borders\n}\n\ncaption {\n padding-top: $table-cell-padding;\n padding-bottom: $table-cell-padding;\n color: $text-muted;\n text-align: left;\n caption-side: bottom;\n}\n\nth {\n // Matches default `<td>` alignment\n text-align: left;\n}\n\n\n//\n// Forms\n//\n\nlabel {\n // Allow labels to use `margin` for spacing.\n display: inline-block;\n margin-bottom: .5rem;\n}\n\n// Work around a Firefox/IE bug where the transparent `button` background\n// results in a loss of the default `button` focus styles.\n//\n// Credit: https://github.com/suitcss/base/\nbutton:focus {\n outline: 1px dotted;\n outline: 5px auto -webkit-focus-ring-color;\n}\n\ninput,\nbutton,\nselect,\noptgroup,\ntextarea {\n margin: 0; // Remove the margin in Firefox and Safari\n font-family: inherit;\n font-size: inherit;\n line-height: inherit;\n}\n\nbutton,\ninput {\n overflow: visible; // Show the overflow in Edge\n}\n\nbutton,\nselect {\n text-transform: none; // Remove the inheritance of text transform in Firefox\n}\n\n// 1. Prevent a WebKit bug where (2) destroys native `audio` and `video`\n// controls in Android 4.\n// 2. Correct the inability to style clickable types in iOS and Safari.\nbutton,\nhtml [type=\"button\"], // 1\n[type=\"reset\"],\n[type=\"submit\"] {\n -webkit-appearance: button; // 2\n}\n\n// Remove inner border and padding from Firefox, but don't restore the outline like Normalize.\nbutton::-moz-focus-inner,\n[type=\"button\"]::-moz-focus-inner,\n[type=\"reset\"]::-moz-focus-inner,\n[type=\"submit\"]::-moz-focus-inner {\n padding: 0;\n border-style: none;\n}\n\ninput[type=\"radio\"],\ninput[type=\"checkbox\"] {\n box-sizing: border-box; // 1. Add the correct box sizing in IE 10-\n padding: 0; // 2. Remove the padding in IE 10-\n}\n\n\ninput[type=\"date\"],\ninput[type=\"time\"],\ninput[type=\"datetime-local\"],\ninput[type=\"month\"] {\n // Remove the default appearance of temporal inputs to avoid a Mobile Safari\n // bug where setting a custom line-height prevents text from being vertically\n // centered within the input.\n // See https://bugs.webkit.org/show_bug.cgi?id=139848\n // and https://github.com/twbs/bootstrap/issues/11266\n -webkit-appearance: listbox;\n}\n\ntextarea {\n overflow: auto; // Remove the default vertical scrollbar in IE.\n // Textareas should really only resize vertically so they don't break their (horizontal) containers.\n resize: vertical;\n}\n\nfieldset {\n // Browsers set a default `min-width: min-content;` on fieldsets,\n // unlike e.g. `<div>`s, which have `min-width: 0;` by default.\n // So we reset that to ensure fieldsets behave more like a standard block element.\n // See https://github.com/twbs/bootstrap/issues/12359\n // and https://html.spec.whatwg.org/multipage/#the-fieldset-and-legend-elements\n min-width: 0;\n // Reset the default outline behavior of fieldsets so they don't affect page layout.\n padding: 0;\n margin: 0;\n border: 0;\n}\n\n// 1. Correct the text wrapping in Edge and IE.\n// 2. Correct the color inheritance from `fieldset` elements in IE.\nlegend {\n display: block;\n width: 100%;\n max-width: 100%; // 1\n padding: 0;\n margin-bottom: .5rem;\n font-size: 1.5rem;\n line-height: inherit;\n color: inherit; // 2\n white-space: normal; // 1\n}\n\nprogress {\n vertical-align: baseline; // Add the correct vertical alignment in Chrome, Firefox, and Opera.\n}\n\n// Correct the cursor style of increment and decrement buttons in Chrome.\n[type=\"number\"]::-webkit-inner-spin-button,\n[type=\"number\"]::-webkit-outer-spin-button {\n height: auto;\n}\n\n[type=\"search\"] {\n // This overrides the extra rounded corners on search inputs in iOS so that our\n // `.form-control` class can properly style them. Note that this cannot simply\n // be added to `.form-control` as it's not specific enough. For details, see\n // https://github.com/twbs/bootstrap/issues/11586.\n outline-offset: -2px; // 2. Correct the outline style in Safari.\n -webkit-appearance: none;\n}\n\n//\n// Remove the inner padding and cancel buttons in Chrome and Safari on macOS.\n//\n\n[type=\"search\"]::-webkit-search-cancel-button,\n[type=\"search\"]::-webkit-search-decoration {\n -webkit-appearance: none;\n}\n\n//\n// 1. Correct the inability to style clickable types in iOS and Safari.\n// 2. Change font properties to `inherit` in Safari.\n//\n\n::-webkit-file-upload-button {\n font: inherit; // 2\n -webkit-appearance: button; // 1\n}\n\n//\n// Correct element displays\n//\n\noutput {\n display: inline-block;\n}\n\nsummary {\n display: list-item; // Add the correct display in all browsers\n}\n\ntemplate {\n display: none; // Add the correct display in IE\n}\n\n// Always hide an element with the `hidden` HTML attribute (from PureCSS).\n// Needed for proper display in IE 10-.\n[hidden] {\n display: none !important;\n}\n","html {\n box-sizing: border-box;\n font-family: sans-serif;\n line-height: 1.15;\n -webkit-text-size-adjust: 100%;\n -ms-text-size-adjust: 100%;\n -ms-overflow-style: scrollbar;\n -webkit-tap-highlight-color: transparent;\n}\n\n*,\n*::before,\n*::after {\n box-sizing: inherit;\n}\n\n@-ms-viewport {\n width: device-width;\n}\n\narticle, aside, dialog, figcaption, figure, footer, header, hgroup, main, nav, section {\n display: block;\n}\n\nbody {\n margin: 0;\n font-family: -apple-system, BlinkMacSystemFont, \"Segoe UI\", Roboto, \"Helvetica Neue\", Arial, sans-serif;\n font-size: 1rem;\n font-weight: normal;\n line-height: 1.5;\n color: #212529;\n background-color: #fff;\n}\n\n[tabindex=\"-1\"]:focus {\n outline: none !important;\n}\n\nhr {\n box-sizing: content-box;\n height: 0;\n overflow: visible;\n}\n\nh1, h2, h3, h4, h5, h6 {\n margin-top: 0;\n margin-bottom: .5rem;\n}\n\np {\n margin-top: 0;\n margin-bottom: 1rem;\n}\n\nabbr[title],\nabbr[data-original-title] {\n text-decoration: underline;\n text-decoration: underline dotted;\n cursor: help;\n border-bottom: 0;\n}\n\naddress {\n margin-bottom: 1rem;\n font-style: normal;\n line-height: inherit;\n}\n\nol,\nul,\ndl {\n margin-top: 0;\n margin-bottom: 1rem;\n}\n\nol ol,\nul ul,\nol ul,\nul ol {\n margin-bottom: 0;\n}\n\ndt {\n font-weight: bold;\n}\n\ndd {\n margin-bottom: .5rem;\n margin-left: 0;\n}\n\nblockquote {\n margin: 0 0 1rem;\n}\n\ndfn {\n font-style: italic;\n}\n\nb,\nstrong {\n font-weight: bolder;\n}\n\nsmall {\n font-size: 80%;\n}\n\nsub,\nsup {\n position: relative;\n font-size: 75%;\n line-height: 0;\n vertical-align: baseline;\n}\n\nsub {\n bottom: -.25em;\n}\n\nsup {\n top: -.5em;\n}\n\na {\n color: #007bff;\n text-decoration: none;\n background-color: transparent;\n -webkit-text-decoration-skip: objects;\n}\n\na:hover {\n color: #0056b3;\n text-decoration: underline;\n}\n\na:not([href]):not([tabindex]) {\n color: inherit;\n text-decoration: none;\n}\n\na:not([href]):not([tabindex]):focus, a:not([href]):not([tabindex]):hover {\n color: inherit;\n text-decoration: none;\n}\n\na:not([href]):not([tabindex]):focus {\n outline: 0;\n}\n\npre,\ncode,\nkbd,\nsamp {\n font-family: monospace, monospace;\n font-size: 1em;\n}\n\npre {\n margin-top: 0;\n margin-bottom: 1rem;\n overflow: auto;\n}\n\nfigure {\n margin: 0 0 1rem;\n}\n\nimg {\n vertical-align: middle;\n border-style: none;\n}\n\nsvg:not(:root) {\n overflow: hidden;\n}\n\na,\narea,\nbutton,\n[role=\"button\"],\ninput,\nlabel,\nselect,\nsummary,\ntextarea {\n touch-action: manipulation;\n}\n\ntable {\n border-collapse: collapse;\n}\n\ncaption {\n padding-top: 0.75rem;\n padding-bottom: 0.75rem;\n color: #868e96;\n text-align: left;\n caption-side: bottom;\n}\n\nth {\n text-align: left;\n}\n\nlabel {\n display: inline-block;\n margin-bottom: .5rem;\n}\n\nbutton:focus {\n outline: 1px dotted;\n outline: 5px auto -webkit-focus-ring-color;\n}\n\ninput,\nbutton,\nselect,\noptgroup,\ntextarea {\n margin: 0;\n font-family: inherit;\n font-size: inherit;\n line-height: inherit;\n}\n\nbutton,\ninput {\n overflow: visible;\n}\n\nbutton,\nselect {\n text-transform: none;\n}\n\nbutton,\nhtml [type=\"button\"],\n[type=\"reset\"],\n[type=\"submit\"] {\n -webkit-appearance: button;\n}\n\nbutton::-moz-focus-inner,\n[type=\"button\"]::-moz-focus-inner,\n[type=\"reset\"]::-moz-focus-inner,\n[type=\"submit\"]::-moz-focus-inner {\n padding: 0;\n border-style: none;\n}\n\ninput[type=\"radio\"],\ninput[type=\"checkbox\"] {\n box-sizing: border-box;\n padding: 0;\n}\n\ninput[type=\"date\"],\ninput[type=\"time\"],\ninput[type=\"datetime-local\"],\ninput[type=\"month\"] {\n -webkit-appearance: listbox;\n}\n\ntextarea {\n overflow: auto;\n resize: vertical;\n}\n\nfieldset {\n min-width: 0;\n padding: 0;\n margin: 0;\n border: 0;\n}\n\nlegend {\n display: block;\n width: 100%;\n max-width: 100%;\n padding: 0;\n margin-bottom: .5rem;\n font-size: 1.5rem;\n line-height: inherit;\n color: inherit;\n white-space: normal;\n}\n\nprogress {\n vertical-align: baseline;\n}\n\n[type=\"number\"]::-webkit-inner-spin-button,\n[type=\"number\"]::-webkit-outer-spin-button {\n height: auto;\n}\n\n[type=\"search\"] {\n outline-offset: -2px;\n -webkit-appearance: none;\n}\n\n[type=\"search\"]::-webkit-search-cancel-button,\n[type=\"search\"]::-webkit-search-decoration {\n -webkit-appearance: none;\n}\n\n::-webkit-file-upload-button {\n font: inherit;\n -webkit-appearance: button;\n}\n\noutput {\n display: inline-block;\n}\n\nsummary {\n display: list-item;\n}\n\ntemplate {\n display: none;\n}\n\n[hidden] {\n display: none !important;\n}\n\n/*# sourceMappingURL=bootstrap-reboot.css.map */","// Variables\n//\n// Copy settings from this file into the provided `_custom.scss` to override\n// the Bootstrap defaults without modifying key, versioned files.\n//\n// Variables should follow the `$component-state-property-size` formula for\n// consistent naming. Ex: $nav-link-disabled-color and $modal-content-box-shadow-xs.\n\n// Table of Contents\n//\n// Color system\n// Options\n// Spacing\n// Body\n// Links\n// Grid breakpoints\n// Grid containers\n// Grid columns\n// Fonts\n// Components\n// Tables\n// Buttons\n// Forms\n// Dropdowns\n// Z-index master list\n// Navs\n// Navbar\n// Pagination\n// Jumbotron\n// Form states and alerts\n// Cards\n// Tooltips\n// Popovers\n// Badges\n// Modals\n// Alerts\n// Progress bars\n// List group\n// Image thumbnails\n// Figures\n// Breadcrumbs\n// Carousel\n// Close\n// Code\n\n\n//\n// Color system\n//\n\n$white: #fff !default;\n$gray-100: #f8f9fa !default;\n$gray-200: #e9ecef !default;\n$gray-300: #dee2e6 !default;\n$gray-400: #ced4da !default;\n$gray-500: #adb5bd !default;\n$gray-600: #868e96 !default;\n$gray-700: #495057 !default;\n$gray-800: #343a40 !default;\n$gray-900: #212529 !default;\n$black: #000 !default;\n\n$grays: (\n 100: $gray-100,\n 200: $gray-200,\n 300: $gray-300,\n 400: $gray-400,\n 500: $gray-500,\n 600: $gray-600,\n 700: $gray-700,\n 800: $gray-800,\n 900: $gray-900\n) !default;\n\n$blue: #007bff !default;\n$indigo: #6610f2 !default;\n$purple: #6f42c1 !default;\n$pink: #e83e8c !default;\n$red: #dc3545 !default;\n$orange: #fd7e14 !default;\n$yellow: #ffc107 !default;\n$green: #28a745 !default;\n$teal: #20c997 !default;\n$cyan: #17a2b8 !default;\n\n$colors: (\n blue: $blue,\n indigo: $indigo,\n purple: $purple,\n pink: $pink,\n red: $red,\n orange: $orange,\n yellow: $yellow,\n green: $green,\n teal: $teal,\n cyan: $cyan,\n white: $white,\n gray: $gray-600,\n gray-dark: $gray-800\n) !default;\n\n$theme-colors: (\n primary: $blue,\n secondary: $gray-600,\n success: $green,\n info: $cyan,\n warning: $yellow,\n danger: $red,\n light: $gray-100,\n dark: $gray-800\n) !default;\n\n// Set a specific jump point for requesting color jumps\n$theme-color-interval: 8% !default;\n\n\n// Options\n//\n// Quickly modify global styling by enabling or disabling optional features.\n\n$enable-rounded: true !default;\n$enable-shadows: false !default;\n$enable-gradients: false !default;\n$enable-transitions: true !default;\n$enable-hover-media-query: false !default;\n$enable-grid-classes: true !default;\n$enable-print-styles: true !default;\n\n\n// Spacing\n//\n// Control the default styling of most Bootstrap elements by modifying these\n// variables. Mostly focused on spacing.\n// You can add more entries to the $spacers map, should you need more variation.\n\n$spacer: 1rem !default;\n$spacers: (\n 0: 0,\n 1: ($spacer * .25),\n 2: ($spacer * .5),\n 3: $spacer,\n 4: ($spacer * 1.5),\n 5: ($spacer * 3)\n) !default;\n\n// This variable affects the `.h-*` and `.w-*` classes.\n$sizes: (\n 25: 25%,\n 50: 50%,\n 75: 75%,\n 100: 100%\n) !default;\n\n// Body\n//\n// Settings for the `<body>` element.\n\n$body-bg: $white !default;\n$body-color: $gray-900 !default;\n\n// Links\n//\n// Style anchor elements.\n\n$link-color: theme-color(\"primary\") !default;\n$link-decoration: none !default;\n$link-hover-color: darken($link-color, 15%) !default;\n$link-hover-decoration: underline !default;\n\n\n// Grid breakpoints\n//\n// Define the minimum dimensions at which your layout will change,\n// adapting to different screen sizes, for use in media queries.\n\n$grid-breakpoints: (\n xs: 0,\n sm: 576px,\n md: 768px,\n lg: 992px,\n xl: 1200px\n) !default;\n@include _assert-ascending($grid-breakpoints, \"$grid-breakpoints\");\n@include _assert-starts-at-zero($grid-breakpoints);\n\n\n// Grid containers\n//\n// Define the maximum width of `.container` for different screen sizes.\n\n$container-max-widths: (\n sm: 540px,\n md: 720px,\n lg: 960px,\n xl: 1140px\n) !default;\n@include _assert-ascending($container-max-widths, \"$container-max-widths\");\n\n\n// Grid columns\n//\n// Set the number of columns and specify the width of the gutters.\n\n$grid-columns: 12 !default;\n$grid-gutter-width: 30px !default;\n\n// Components\n//\n// Define common padding and border radius sizes and more.\n\n$line-height-lg: 1.5 !default;\n$line-height-sm: 1.5 !default;\n\n$border-width: 1px !default;\n\n$border-radius: .25rem !default;\n$border-radius-lg: .3rem !default;\n$border-radius-sm: .2rem !default;\n\n$component-active-color: $white !default;\n$component-active-bg: theme-color(\"primary\") !default;\n\n$caret-width: .3em !default;\n\n$transition-base: all .2s ease-in-out !default;\n$transition-fade: opacity .15s linear !default;\n$transition-collapse: height .35s ease !default;\n\n\n// Fonts\n//\n// Font, line-height, and color for body text, headings, and more.\n\n$font-family-sans-serif: -apple-system, BlinkMacSystemFont, \"Segoe UI\", Roboto, \"Helvetica Neue\", Arial, sans-serif !default;\n$font-family-monospace: Menlo, Monaco, Consolas, \"Liberation Mono\", \"Courier New\", monospace !default;\n$font-family-base: $font-family-sans-serif !default;\n\n$font-size-base: 1rem !default; // Assumes the browser default, typically `16px`\n$font-size-lg: 1.25rem !default;\n$font-size-sm: .875rem !default;\n\n$font-weight-normal: normal !default;\n$font-weight-bold: bold !default;\n\n$font-weight-base: $font-weight-normal !default;\n$line-height-base: 1.5 !default;\n\n$h1-font-size: 2.5rem !default;\n$h2-font-size: 2rem !default;\n$h3-font-size: 1.75rem !default;\n$h4-font-size: 1.5rem !default;\n$h5-font-size: 1.25rem !default;\n$h6-font-size: 1rem !default;\n\n$headings-margin-bottom: ($spacer / 2) !default;\n$headings-font-family: inherit !default;\n$headings-font-weight: 500 !default;\n$headings-line-height: 1.1 !default;\n$headings-color: inherit !default;\n\n$display1-size: 6rem !default;\n$display2-size: 5.5rem !default;\n$display3-size: 4.5rem !default;\n$display4-size: 3.5rem !default;\n\n$display1-weight: 300 !default;\n$display2-weight: 300 !default;\n$display3-weight: 300 !default;\n$display4-weight: 300 !default;\n$display-line-height: $headings-line-height !default;\n\n$lead-font-size: 1.25rem !default;\n$lead-font-weight: 300 !default;\n\n$small-font-size: 80% !default;\n\n$text-muted: $gray-600 !default;\n\n$blockquote-small-color: $gray-600 !default;\n$blockquote-font-size: ($font-size-base * 1.25) !default;\n\n$hr-border-color: rgba($black,.1) !default;\n$hr-border-width: $border-width !default;\n\n$mark-padding: .2em !default;\n\n$dt-font-weight: $font-weight-bold !default;\n\n$kbd-box-shadow: inset 0 -.1rem 0 rgba($black,.25) !default;\n$nested-kbd-font-weight: $font-weight-bold !default;\n\n$list-inline-padding: 5px !default;\n\n$mark-bg: #fcf8e3 !default;\n\n\n// Tables\n//\n// Customizes the `.table` component with basic values, each used across all table variations.\n\n$table-cell-padding: .75rem !default;\n$table-cell-padding-sm: .3rem !default;\n\n$table-bg: transparent !default;\n$table-accent-bg: rgba($black,.05) !default;\n$table-hover-bg: rgba($black,.075) !default;\n$table-active-bg: $table-hover-bg !default;\n\n$table-border-width: $border-width !default;\n$table-border-color: $gray-200 !default;\n\n$table-head-bg: $gray-200 !default;\n$table-head-color: $gray-700 !default;\n\n$table-inverse-bg: $gray-900 !default;\n$table-inverse-accent-bg: rgba($white, .05) !default;\n$table-inverse-hover-bg: rgba($white, .075) !default;\n$table-inverse-border-color: lighten($gray-900, 7.5%) !default;\n$table-inverse-color: $body-bg !default;\n\n\n// Buttons\n//\n// For each of Bootstrap's buttons, define text, background and border color.\n\n$input-btn-padding-y: .5rem !default;\n$input-btn-padding-x: .75rem !default;\n$input-btn-line-height: 1.25 !default;\n\n$input-btn-padding-y-sm: .25rem !default;\n$input-btn-padding-x-sm: .5rem !default;\n$input-btn-line-height-sm: 1.5 !default;\n\n$input-btn-padding-y-lg: .5rem !default;\n$input-btn-padding-x-lg: 1rem !default;\n$input-btn-line-height-lg: 1.5 !default;\n\n$btn-font-weight: $font-weight-normal !default;\n$btn-box-shadow: inset 0 1px 0 rgba($white,.15), 0 1px 1px rgba($black,.075) !default;\n$btn-focus-box-shadow: 0 0 0 3px rgba(theme-color(\"primary\"), .25) !default;\n$btn-active-box-shadow: inset 0 3px 5px rgba($black,.125) !default;\n\n$btn-link-disabled-color: $gray-600 !default;\n\n$btn-block-spacing-y: .5rem !default;\n\n// Allows for customizing button radius independently from global border radius\n$btn-border-radius: $border-radius !default;\n$btn-border-radius-lg: $border-radius-lg !default;\n$btn-border-radius-sm: $border-radius-sm !default;\n\n$btn-transition: all .15s ease-in-out !default;\n\n\n// Forms\n\n$input-bg: $white !default;\n$input-disabled-bg: $gray-200 !default;\n\n$input-color: $gray-700 !default;\n$input-border-color: rgba($black,.15) !default;\n$input-btn-border-width: $border-width !default; // For form controls and buttons\n$input-box-shadow: inset 0 1px 1px rgba($black,.075) !default;\n\n$input-border-radius: $border-radius !default;\n$input-border-radius-lg: $border-radius-lg !default;\n$input-border-radius-sm: $border-radius-sm !default;\n\n$input-focus-bg: $input-bg !default;\n$input-focus-border-color: lighten(theme-color(\"primary\"), 25%) !default;\n$input-focus-box-shadow: $input-box-shadow, $btn-focus-box-shadow !default;\n$input-focus-color: $input-color !default;\n\n$input-placeholder-color: $gray-600 !default;\n\n$input-height-border: $input-btn-border-width * 2 !default;\n\n$input-height-inner: ($font-size-base * $input-btn-line-height) + ($input-btn-padding-y * 2) !default;\n$input-height: calc(#{$input-height-inner} + #{$input-height-border}) !default;\n\n$input-height-inner-sm: ($font-size-sm * $input-btn-line-height-sm) + ($input-btn-padding-y-sm * 2) !default;\n$input-height-sm: calc(#{$input-height-inner-sm} + #{$input-height-border}) !default;\n\n$input-height-inner-lg: ($font-size-sm * $input-btn-line-height-lg) + ($input-btn-padding-y-lg * 2) !default;\n$input-height-lg: calc(#{$input-height-inner-lg} + #{$input-height-border}) !default;\n\n$input-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s !default;\n\n$form-text-margin-top: .25rem !default;\n\n$form-check-margin-bottom: .5rem !default;\n$form-check-input-gutter: 1.25rem !default;\n$form-check-input-margin-y: .25rem !default;\n$form-check-input-margin-x: .25rem !default;\n\n$form-check-inline-margin-x: .75rem !default;\n\n$form-group-margin-bottom: 1rem !default;\n\n$input-group-addon-bg: $gray-200 !default;\n$input-group-addon-border-color: $input-border-color !default;\n\n$custom-control-gutter: 1.5rem !default;\n$custom-control-spacer-y: .25rem !default;\n$custom-control-spacer-x: 1rem !default;\n\n$custom-control-indicator-size: 1rem !default;\n$custom-control-indicator-bg: #ddd !default;\n$custom-control-indicator-bg-size: 50% 50% !default;\n$custom-control-indicator-box-shadow: inset 0 .25rem .25rem rgba($black,.1) !default;\n\n$custom-control-indicator-disabled-bg: $gray-200 !default;\n$custom-control-description-disabled-color: $gray-600 !default;\n\n$custom-control-indicator-checked-color: $white !default;\n$custom-control-indicator-checked-bg: theme-color(\"primary\") !default;\n$custom-control-indicator-checked-box-shadow: none !default;\n\n$custom-control-indicator-focus-box-shadow: 0 0 0 1px $body-bg, 0 0 0 3px theme-color(\"primary\") !default;\n\n$custom-control-indicator-active-color: $white !default;\n$custom-control-indicator-active-bg: lighten(theme-color(\"primary\"), 35%) !default;\n$custom-control-indicator-active-box-shadow: none !default;\n\n$custom-checkbox-indicator-border-radius: $border-radius !default;\n$custom-checkbox-indicator-icon-checked: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 8 8'%3E%3Cpath fill='#{$custom-control-indicator-checked-color}' d='M6.564.75l-3.59 3.612-1.538-1.55L0 4.26 2.974 7.25 8 2.193z'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n\n$custom-checkbox-indicator-indeterminate-bg: theme-color(\"primary\") !default;\n$custom-checkbox-indicator-indeterminate-color: $custom-control-indicator-checked-color !default;\n$custom-checkbox-indicator-icon-indeterminate: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 4 4'%3E%3Cpath stroke='#{$custom-checkbox-indicator-indeterminate-color}' d='M0 2h4'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n$custom-checkbox-indicator-indeterminate-box-shadow: none !default;\n\n$custom-radio-indicator-border-radius: 50% !default;\n$custom-radio-indicator-icon-checked: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='-4 -4 8 8'%3E%3Ccircle r='3' fill='#{$custom-control-indicator-checked-color}'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n\n$custom-select-padding-y: .375rem !default;\n$custom-select-padding-x: .75rem !default;\n$custom-select-height: $input-height !default;\n$custom-select-indicator-padding: 1rem !default; // Extra padding to account for the presence of the background-image based indicator\n$custom-select-line-height: $input-btn-line-height !default;\n$custom-select-color: $input-color !default;\n$custom-select-disabled-color: $gray-600 !default;\n$custom-select-bg: $white !default;\n$custom-select-disabled-bg: $gray-200 !default;\n$custom-select-bg-size: 8px 10px !default; // In pixels because image dimensions\n$custom-select-indicator-color: #333 !default;\n$custom-select-indicator: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 4 5'%3E%3Cpath fill='#{$custom-select-indicator-color}' d='M2 0L0 2h4zm0 5L0 3h4z'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n$custom-select-border-width: $input-btn-border-width !default;\n$custom-select-border-color: $input-border-color !default;\n$custom-select-border-radius: $border-radius !default;\n\n$custom-select-focus-border-color: lighten(theme-color(\"primary\"), 25%) !default;\n$custom-select-focus-box-shadow: inset 0 1px 2px rgba($black, .075), 0 0 5px rgba($custom-select-focus-border-color, .5) !default;\n\n$custom-select-font-size-sm: 75% !default;\n$custom-select-height-sm: $input-height-sm !default;\n\n$custom-file-height: 2.5rem !default;\n$custom-file-width: 14rem !default;\n$custom-file-focus-box-shadow: 0 0 0 .075rem $white, 0 0 0 .2rem theme-color(\"primary\") !default;\n\n$custom-file-padding-y: 1rem !default;\n$custom-file-padding-x: .5rem !default;\n$custom-file-line-height: 1.5 !default;\n$custom-file-color: $gray-700 !default;\n$custom-file-bg: $white !default;\n$custom-file-border-width: $border-width !default;\n$custom-file-border-color: $input-border-color !default;\n$custom-file-border-radius: $border-radius !default;\n$custom-file-box-shadow: inset 0 .2rem .4rem rgba($black,.05) !default;\n$custom-file-button-color: $custom-file-color !default;\n$custom-file-button-bg: $gray-200 !default;\n$custom-file-text: (\n placeholder: (\n en: \"Choose file...\"\n ),\n button-label: (\n en: \"Browse\"\n )\n) !default;\n\n\n// Form validation\n$form-feedback-valid-color: theme-color(\"success\") !default;\n$form-feedback-invalid-color: theme-color(\"danger\") !default;\n\n\n// Dropdowns\n//\n// Dropdown menu container and contents.\n\n$dropdown-min-width: 10rem !default;\n$dropdown-padding-y: .5rem !default;\n$dropdown-spacer: .125rem !default;\n$dropdown-bg: $white !default;\n$dropdown-border-color: rgba($black,.15) !default;\n$dropdown-border-width: $border-width !default;\n$dropdown-divider-bg: $gray-200 !default;\n$dropdown-box-shadow: 0 .5rem 1rem rgba($black,.175) !default;\n\n$dropdown-link-color: $gray-900 !default;\n$dropdown-link-hover-color: darken($gray-900, 5%) !default;\n$dropdown-link-hover-bg: $gray-100 !default;\n\n$dropdown-link-active-color: $component-active-color !default;\n$dropdown-link-active-bg: $component-active-bg !default;\n\n$dropdown-link-disabled-color: $gray-600 !default;\n\n$dropdown-item-padding-y: .25rem !default;\n$dropdown-item-padding-x: 1.5rem !default;\n\n$dropdown-header-color: $gray-600 !default;\n\n\n// Z-index master list\n//\n// Warning: Avoid customizing these values. They're used for a bird's eye view\n// of components dependent on the z-axis and are designed to all work together.\n\n$zindex-dropdown: 1000 !default;\n$zindex-sticky: 1020 !default;\n$zindex-fixed: 1030 !default;\n$zindex-modal-backdrop: 1040 !default;\n$zindex-modal: 1050 !default;\n$zindex-popover: 1060 !default;\n$zindex-tooltip: 1070 !default;\n\n// Navs\n\n$nav-link-padding-y: .5rem !default;\n$nav-link-padding-x: 1rem !default;\n$nav-link-disabled-color: $gray-600 !default;\n\n$nav-tabs-border-color: #ddd !default;\n$nav-tabs-border-width: $border-width !default;\n$nav-tabs-border-radius: $border-radius !default;\n$nav-tabs-link-hover-border-color: $gray-200 !default;\n$nav-tabs-link-active-color: $gray-700 !default;\n$nav-tabs-link-active-bg: $body-bg !default;\n$nav-tabs-link-active-border-color: #ddd !default;\n\n$nav-pills-border-radius: $border-radius !default;\n$nav-pills-link-active-color: $component-active-color !default;\n$nav-pills-link-active-bg: $component-active-bg !default;\n\n// Navbar\n\n$navbar-padding-y: ($spacer / 2) !default;\n$navbar-padding-x: $spacer !default;\n\n$navbar-brand-font-size: $font-size-lg !default;\n// Compute the navbar-brand padding-y so the navbar-brand will have the same height as navbar-text and nav-link\n$nav-link-height: $navbar-brand-font-size * $line-height-base !default;\n$navbar-brand-height: ($font-size-base * $line-height-base + $nav-link-padding-y * 2) !default;\n$navbar-brand-padding-y: ($navbar-brand-height - $nav-link-height) / 2 !default;\n\n$navbar-toggler-padding-y: .25rem !default;\n$navbar-toggler-padding-x: .75rem !default;\n$navbar-toggler-font-size: $font-size-lg !default;\n$navbar-toggler-border-radius: $btn-border-radius !default;\n\n$navbar-dark-color: rgba($white,.5) !default;\n$navbar-dark-hover-color: rgba($white,.75) !default;\n$navbar-dark-active-color: rgba($white,1) !default;\n$navbar-dark-disabled-color: rgba($white,.25) !default;\n$navbar-dark-toggler-icon-bg: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg viewBox='0 0 30 30' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath stroke='#{$navbar-dark-color}' stroke-width='2' stroke-linecap='round' stroke-miterlimit='10' d='M4 7h22M4 15h22M4 23h22'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n$navbar-dark-toggler-border-color: rgba($white,.1) !default;\n\n$navbar-light-color: rgba($black,.5) !default;\n$navbar-light-hover-color: rgba($black,.7) !default;\n$navbar-light-active-color: rgba($black,.9) !default;\n$navbar-light-disabled-color: rgba($black,.3) !default;\n$navbar-light-toggler-icon-bg: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg viewBox='0 0 30 30' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath stroke='#{$navbar-light-color}' stroke-width='2' stroke-linecap='round' stroke-miterlimit='10' d='M4 7h22M4 15h22M4 23h22'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n$navbar-light-toggler-border-color: rgba($black,.1) !default;\n\n// Pagination\n\n$pagination-padding-y: .5rem !default;\n$pagination-padding-x: .75rem !default;\n$pagination-padding-y-sm: .25rem !default;\n$pagination-padding-x-sm: .5rem !default;\n$pagination-padding-y-lg: .75rem !default;\n$pagination-padding-x-lg: 1.5rem !default;\n$pagination-line-height: 1.25 !default;\n\n$pagination-color: $link-color !default;\n$pagination-bg: $white !default;\n$pagination-border-width: $border-width !default;\n$pagination-border-color: #ddd !default;\n\n$pagination-hover-color: $link-hover-color !default;\n$pagination-hover-bg: $gray-200 !default;\n$pagination-hover-border-color: #ddd !default;\n\n$pagination-active-color: $white !default;\n$pagination-active-bg: theme-color(\"primary\") !default;\n$pagination-active-border-color: theme-color(\"primary\") !default;\n\n$pagination-disabled-color: $gray-600 !default;\n$pagination-disabled-bg: $white !default;\n$pagination-disabled-border-color: #ddd !default;\n\n\n// Jumbotron\n\n$jumbotron-padding: 2rem !default;\n$jumbotron-bg: $gray-200 !default;\n\n\n// Cards\n\n$card-spacer-y: .75rem !default;\n$card-spacer-x: 1.25rem !default;\n$card-border-width: 1px !default;\n$card-border-radius: $border-radius !default;\n$card-border-color: rgba($black,.125) !default;\n$card-inner-border-radius: calc(#{$card-border-radius} - #{$card-border-width}) !default;\n$card-cap-bg: rgba($black, .03) !default;\n$card-bg: $white !default;\n\n$card-img-overlay-padding: 1.25rem !default;\n\n$card-deck-margin: ($grid-gutter-width / 2) !default;\n\n$card-columns-count: 3 !default;\n$card-columns-gap: 1.25rem !default;\n$card-columns-margin: $card-spacer-y !default;\n\n\n// Tooltips\n\n$tooltip-max-width: 200px !default;\n$tooltip-color: $white !default;\n$tooltip-bg: $black !default;\n$tooltip-opacity: .9 !default;\n$tooltip-padding-y: 3px !default;\n$tooltip-padding-x: 8px !default;\n$tooltip-margin: 0 !default;\n\n\n$tooltip-arrow-width: 5px !default;\n$tooltip-arrow-height: 5px !default;\n$tooltip-arrow-color: $tooltip-bg !default;\n\n\n// Popovers\n\n$popover-inner-padding: 1px !default;\n$popover-bg: $white !default;\n$popover-max-width: 276px !default;\n$popover-border-width: $border-width !default;\n$popover-border-color: rgba($black,.2) !default;\n$popover-box-shadow: 0 5px 10px rgba($black,.2) !default;\n\n$popover-header-bg: darken($popover-bg, 3%) !default;\n$popover-header-color: $headings-color !default;\n$popover-header-padding-y: 8px !default;\n$popover-header-padding-x: 14px !default;\n\n$popover-body-color: $body-color !default;\n$popover-body-padding-y: 9px !default;\n$popover-body-padding-x: 14px !default;\n\n$popover-arrow-width: 10px !default;\n$popover-arrow-height: 5px !default;\n$popover-arrow-color: $popover-bg !default;\n\n$popover-arrow-outer-width: ($popover-arrow-width + 1px) !default;\n$popover-arrow-outer-color: fade-in($popover-border-color, .05) !default;\n\n\n// Badges\n\n$badge-color: $white !default;\n$badge-font-size: 75% !default;\n$badge-font-weight: $font-weight-bold !default;\n$badge-padding-y: .25em !default;\n$badge-padding-x: .4em !default;\n\n$badge-pill-padding-x: .6em !default;\n// Use a higher than normal value to ensure completely rounded edges when\n// customizing padding or font-size on labels.\n$badge-pill-border-radius: 10rem !default;\n\n\n// Modals\n\n// Padding applied to the modal body\n$modal-inner-padding: 15px !default;\n\n$modal-dialog-margin: 10px !default;\n$modal-dialog-margin-y-sm-up: 30px !default;\n\n$modal-title-line-height: $line-height-base !default;\n\n$modal-content-bg: $white !default;\n$modal-content-border-color: rgba($black,.2) !default;\n$modal-content-border-width: $border-width !default;\n$modal-content-box-shadow-xs: 0 3px 9px rgba($black,.5) !default;\n$modal-content-box-shadow-sm-up: 0 5px 15px rgba($black,.5) !default;\n\n$modal-backdrop-bg: $black !default;\n$modal-backdrop-opacity: .5 !default;\n$modal-header-border-color: $gray-200 !default;\n$modal-footer-border-color: $modal-header-border-color !default;\n$modal-header-border-width: $modal-content-border-width !default;\n$modal-footer-border-width: $modal-header-border-width !default;\n$modal-header-padding: 15px !default;\n\n$modal-lg: 800px !default;\n$modal-md: 500px !default;\n$modal-sm: 300px !default;\n\n$modal-transition: transform .3s ease-out !default;\n\n\n// Alerts\n//\n// Define alert colors, border radius, and padding.\n\n$alert-padding-y: .75rem !default;\n$alert-padding-x: 1.25rem !default;\n$alert-margin-bottom: 1rem !default;\n$alert-border-radius: $border-radius !default;\n$alert-link-font-weight: $font-weight-bold !default;\n$alert-border-width: $border-width !default;\n\n\n// Progress bars\n\n$progress-height: 1rem !default;\n$progress-font-size: .75rem !default;\n$progress-bg: $gray-200 !default;\n$progress-border-radius: $border-radius !default;\n$progress-box-shadow: inset 0 .1rem .1rem rgba($black,.1) !default;\n$progress-bar-color: $white !default;\n$progress-bar-bg: theme-color(\"primary\") !default;\n$progress-bar-animation-timing: 1s linear infinite !default;\n$progress-bar-transition: width .6s ease !default;\n\n// List group\n\n$list-group-bg: $white !default;\n$list-group-border-color: rgba($black,.125) !default;\n$list-group-border-width: $border-width !default;\n$list-group-border-radius: $border-radius !default;\n\n$list-group-item-padding-y: .75rem !default;\n$list-group-item-padding-x: 1.25rem !default;\n\n$list-group-hover-bg: $gray-100 !default;\n$list-group-active-color: $component-active-color !default;\n$list-group-active-bg: $component-active-bg !default;\n$list-group-active-border-color: $list-group-active-bg !default;\n\n$list-group-disabled-color: $gray-600 !default;\n$list-group-disabled-bg: $list-group-bg !default;\n\n$list-group-action-color: $gray-700 !default;\n$list-group-action-hover-color: $list-group-action-color !default;\n\n$list-group-action-active-color: $body-color !default;\n$list-group-action-active-bg: $gray-200 !default;\n\n\n// Image thumbnails\n\n$thumbnail-padding: .25rem !default;\n$thumbnail-bg: $body-bg !default;\n$thumbnail-border-width: $border-width !default;\n$thumbnail-border-color: #ddd !default;\n$thumbnail-border-radius: $border-radius !default;\n$thumbnail-box-shadow: 0 1px 2px rgba($black,.075) !default;\n$thumbnail-transition: all .2s ease-in-out !default;\n\n\n// Figures\n\n$figure-caption-font-size: 90% !default;\n$figure-caption-color: $gray-600 !default;\n\n\n// Breadcrumbs\n\n$breadcrumb-padding-y: .75rem !default;\n$breadcrumb-padding-x: 1rem !default;\n$breadcrumb-item-padding: .5rem !default;\n\n$breadcrumb-bg: $gray-200 !default;\n$breadcrumb-divider-color: $gray-600 !default;\n$breadcrumb-active-color: $gray-600 !default;\n$breadcrumb-divider: \"/\" !default;\n\n\n// Carousel\n\n$carousel-control-color: $white !default;\n$carousel-control-width: 15% !default;\n$carousel-control-opacity: .5 !default;\n\n$carousel-indicator-width: 30px !default;\n$carousel-indicator-height: 3px !default;\n$carousel-indicator-spacer: 3px !default;\n$carousel-indicator-active-bg: $white !default;\n\n$carousel-caption-width: 70% !default;\n$carousel-caption-color: $white !default;\n\n$carousel-control-icon-width: 20px !default;\n\n$carousel-control-prev-icon-bg: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' fill='#{$carousel-control-color}' viewBox='0 0 8 8'%3E%3Cpath d='M4 0l-4 4 4 4 1.5-1.5-2.5-2.5 2.5-2.5-1.5-1.5z'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n$carousel-control-next-icon-bg: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' fill='#{$carousel-control-color}' viewBox='0 0 8 8'%3E%3Cpath d='M1.5 0l-1.5 1.5 2.5 2.5-2.5 2.5 1.5 1.5 4-4-4-4z'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n\n$carousel-transition: transform .6s ease !default;\n\n\n// Close\n\n$close-font-size: $font-size-base * 1.5 !default;\n$close-font-weight: $font-weight-bold !default;\n$close-color: $black !default;\n$close-text-shadow: 0 1px 0 $white !default;\n\n// Code\n\n$code-font-size: 90% !default;\n$code-padding-y: .2rem !default;\n$code-padding-x: .4rem !default;\n$code-color: #bd4147 !default;\n$code-bg: $gray-100 !default;\n\n$kbd-color: $white !default;\n$kbd-bg: $gray-900 !default;\n\n$pre-color: $gray-900 !default;\n$pre-scrollable-max-height: 340px !default;\n","@mixin hover {\n // TODO: re-enable along with mq4-hover-shim\n// @if $enable-hover-media-query {\n// // See Media Queries Level 4: https://drafts.csswg.org/mediaqueries/#hover\n// // Currently shimmed by https://github.com/twbs/mq4-hover-shim\n// @media (hover: hover) {\n// &:hover { @content }\n// }\n// }\n// @else {\n// scss-lint:disable Indentation\n &:hover { @content }\n// scss-lint:enable Indentation\n// }\n}\n\n\n@mixin hover-focus {\n @if $enable-hover-media-query {\n &:focus { @content }\n @include hover { @content }\n } @else {\n &:focus,\n &:hover {\n @content\n }\n }\n}\n\n@mixin plain-hover-focus {\n @if $enable-hover-media-query {\n &,\n &:focus {\n @content\n }\n @include hover { @content }\n } @else {\n &,\n &:focus,\n &:hover {\n @content\n }\n }\n}\n\n@mixin hover-focus-active {\n @if $enable-hover-media-query {\n &:focus,\n &:active {\n @content\n }\n @include hover { @content }\n } @else {\n &:focus,\n &:active,\n &:hover {\n @content\n }\n }\n}\n"]} \ No newline at end of file
diff --git a/library/bootstrap/css/bootstrap-reboot.min.css b/library/bootstrap/css/bootstrap-reboot.min.css
new file mode 100644
index 000000000..4ee4a4069
--- /dev/null
+++ b/library/bootstrap/css/bootstrap-reboot.min.css
@@ -0,0 +1,2 @@
+html{box-sizing:border-box;font-family:sans-serif;line-height:1.15;-webkit-text-size-adjust:100%;-ms-text-size-adjust:100%;-ms-overflow-style:scrollbar;-webkit-tap-highlight-color:transparent}*,::after,::before{box-sizing:inherit}@-ms-viewport{width:device-width}article,aside,dialog,figcaption,figure,footer,header,hgroup,main,nav,section{display:block}body{margin:0;font-family:-apple-system,BlinkMacSystemFont,"Segoe UI",Roboto,"Helvetica Neue",Arial,sans-serif;font-size:1rem;font-weight:400;line-height:1.5;color:#212529;background-color:#fff}[tabindex="-1"]:focus{outline:0!important}hr{box-sizing:content-box;height:0;overflow:visible}h1,h2,h3,h4,h5,h6{margin-top:0;margin-bottom:.5rem}p{margin-top:0;margin-bottom:1rem}abbr[data-original-title],abbr[title]{text-decoration:underline;-webkit-text-decoration:underline dotted;text-decoration:underline dotted;cursor:help;border-bottom:0}address{margin-bottom:1rem;font-style:normal;line-height:inherit}dl,ol,ul{margin-top:0;margin-bottom:1rem}ol ol,ol ul,ul ol,ul ul{margin-bottom:0}dt{font-weight:700}dd{margin-bottom:.5rem;margin-left:0}blockquote{margin:0 0 1rem}dfn{font-style:italic}b,strong{font-weight:bolder}small{font-size:80%}sub,sup{position:relative;font-size:75%;line-height:0;vertical-align:baseline}sub{bottom:-.25em}sup{top:-.5em}a{color:#007bff;text-decoration:none;background-color:transparent;-webkit-text-decoration-skip:objects}a:hover{color:#0056b3;text-decoration:underline}a:not([href]):not([tabindex]){color:inherit;text-decoration:none}a:not([href]):not([tabindex]):focus,a:not([href]):not([tabindex]):hover{color:inherit;text-decoration:none}a:not([href]):not([tabindex]):focus{outline:0}code,kbd,pre,samp{font-family:monospace,monospace;font-size:1em}pre{margin-top:0;margin-bottom:1rem;overflow:auto}figure{margin:0 0 1rem}img{vertical-align:middle;border-style:none}svg:not(:root){overflow:hidden}[role=button],a,area,button,input,label,select,summary,textarea{-ms-touch-action:manipulation;touch-action:manipulation}table{border-collapse:collapse}caption{padding-top:.75rem;padding-bottom:.75rem;color:#868e96;text-align:left;caption-side:bottom}th{text-align:left}label{display:inline-block;margin-bottom:.5rem}button:focus{outline:1px dotted;outline:5px auto -webkit-focus-ring-color}button,input,optgroup,select,textarea{margin:0;font-family:inherit;font-size:inherit;line-height:inherit}button,input{overflow:visible}button,select{text-transform:none}[type=reset],[type=submit],button,html [type=button]{-webkit-appearance:button}[type=button]::-moz-focus-inner,[type=reset]::-moz-focus-inner,[type=submit]::-moz-focus-inner,button::-moz-focus-inner{padding:0;border-style:none}input[type=checkbox],input[type=radio]{box-sizing:border-box;padding:0}input[type=date],input[type=datetime-local],input[type=month],input[type=time]{-webkit-appearance:listbox}textarea{overflow:auto;resize:vertical}fieldset{min-width:0;padding:0;margin:0;border:0}legend{display:block;width:100%;max-width:100%;padding:0;margin-bottom:.5rem;font-size:1.5rem;line-height:inherit;color:inherit;white-space:normal}progress{vertical-align:baseline}[type=number]::-webkit-inner-spin-button,[type=number]::-webkit-outer-spin-button{height:auto}[type=search]{outline-offset:-2px;-webkit-appearance:none}[type=search]::-webkit-search-cancel-button,[type=search]::-webkit-search-decoration{-webkit-appearance:none}::-webkit-file-upload-button{font:inherit;-webkit-appearance:button}output{display:inline-block}summary{display:list-item}template{display:none}[hidden]{display:none!important}
+/*# sourceMappingURL=bootstrap-reboot.min.css.map */ \ No newline at end of file
diff --git a/library/bootstrap/css/bootstrap-reboot.min.css.map b/library/bootstrap/css/bootstrap-reboot.min.css.map
new file mode 100644
index 000000000..d461cb58f
--- /dev/null
+++ b/library/bootstrap/css/bootstrap-reboot.min.css.map
@@ -0,0 +1 @@
+{"version":3,"sources":["../../scss/_reboot.scss","dist/css/bootstrap-reboot.css","bootstrap-reboot.css","../../scss/mixins/_hover.scss"],"names":[],"mappings":"AAoBA,KACE,WAAA,WACA,YAAA,WACA,YAAA,KACA,yBAAA,KACA,qBAAA,KACA,mBAAA,UACA,4BAAA,YAGF,EClBA,QADA,SDsBE,WAAA,QAKA,cAAgB,MAAA,aAIlB,QAAA,MAAA,OAAA,WAAA,OAAA,OAAA,OAAA,OAAA,KAAA,IAAA,QACE,QAAA,MAQF,KACE,OAAA,EACA,YAAA,aAAA,CAAA,kBAAA,CAAA,UAAA,CAAA,MAAA,CAAA,gBAAA,CAAA,KAAA,CAAA,WACA,UAAA,KACA,YAAA,IACA,YAAA,IACA,MAAA,QACA,iBAAA,KExBF,sBFiCE,QAAA,YASF,GACE,WAAA,YACA,OAAA,EACA,SAAA,QAYF,GAAA,GAAA,GAAA,GAAA,GAAA,GACE,WAAA,EACA,cAAA,MAOF,EACE,WAAA,EACA,cAAA,KC/CF,0BDyDA,YAEE,gBAAA,UACA,wBAAA,UAAA,OAAA,gBAAA,UAAA,OACA,OAAA,KACA,cAAA,EAGF,QACE,cAAA,KACA,WAAA,OACA,YAAA,QCpDF,GDuDA,GCxDA,GD2DE,WAAA,EACA,cAAA,KAGF,MCvDA,MACA,MAFA,MD4DE,cAAA,EAGF,GACE,YAAA,IAGF,GACE,cAAA,MACA,YAAA,EAGF,WACE,OAAA,EAAA,EAAA,KAGF,IACE,WAAA,OAGF,ECxDA,OD0DE,YAAA,OAGF,MACE,UAAA,IAQF,IC7DA,ID+DE,SAAA,SACA,UAAA,IACA,YAAA,EACA,eAAA,SAGF,IAAM,OAAA,OACN,IAAM,IAAA,MAON,EACE,MAAA,QACA,gBAAA,KACA,iBAAA,YACA,6BAAA,QGpLE,QHuLA,MAAA,QACA,gBAAA,UAUJ,8BACE,MAAA,QACA,gBAAA,KGzLE,oCAAA,oCH4LA,MAAA,QACA,gBAAA,KANJ,oCAUI,QAAA,EC/DJ,KACA,IDuEA,ICtEA,KD0EE,YAAA,SAAA,CAAA,UACA,UAAA,IAGF,IAEE,WAAA,EAEA,cAAA,KAEA,SAAA,KAQF,OAEE,OAAA,EAAA,EAAA,KAQF,IACE,eAAA,OACA,aAAA,KAGF,eACE,SAAA,OCjFF,cD+FA,ECjGA,KACA,OAEA,MACA,MACA,OACA,QACA,SDmGE,iBAAA,aAAA,aAAA,aAQF,MACE,gBAAA,SAGF,QACE,YAAA,OACA,eAAA,OACA,MAAA,QACA,WAAA,KACA,aAAA,OAGF,GAEE,WAAA,KAQF,MAEE,QAAA,aACA,cAAA,MAOF,aACE,QAAA,IAAA,OACA,QAAA,IAAA,KAAA,yBC7GF,ODgHA,MC9GA,SADA,OAEA,SDkHE,OAAA,EACA,YAAA,QACA,UAAA,QACA,YAAA,QAGF,OChHA,MDkHE,SAAA,QAGF,OChHA,ODkHE,eAAA,KC5GF,aACA,cDiHA,OCnHA,mBDuHE,mBAAA,OChHF,gCACA,+BACA,gCDkHA,yBAIE,QAAA,EACA,aAAA,KCjHF,qBDoHA,kBAEE,WAAA,WACA,QAAA,EAIF,iBCpHA,2BACA,kBAFA,iBD8HE,mBAAA,QAGF,SACE,SAAA,KAEA,OAAA,SAGF,SAME,UAAA,EAEA,QAAA,EACA,OAAA,EACA,OAAA,EAKF,OACE,QAAA,MACA,MAAA,KACA,UAAA,KACA,QAAA,EACA,cAAA,MACA,UAAA,OACA,YAAA,QACA,MAAA,QACA,YAAA,OAGF,SACE,eAAA,SEnIF,yCDGA,yCDsIE,OAAA,KEpIF,cF4IE,eAAA,KACA,mBAAA,KExIF,4CDGA,yCD8IE,mBAAA,KAQF,6BACE,KAAA,QACA,mBAAA,OAOF,OACE,QAAA,aAGF,QACE,QAAA,UAGF,SACE,QAAA,KErJF,SF2JE,QAAA","sourcesContent":["// scss-lint:disable QualifyingElement, DuplicateProperty, VendorPrefix\n\n// Reboot\n//\n// Normalization of HTML elements, manually forked from Normalize.css to remove\n// styles targeting irrelevant browsers while applying new styles.\n//\n// Normalize is licensed MIT. https://github.com/necolas/normalize.css\n\n\n// Document\n//\n// 1. Change from `box-sizing: content-box` so that `width` is not affected by `padding` or `border`.\n// 2. Change the default font family in all browsers.\n// 3. Correct the line height in all browsers.\n// 4. Prevent adjustments of font size after orientation changes in IE on Windows Phone and in iOS.\n// 5. Setting @viewport causes scrollbars to overlap content in IE11 and Edge, so\n// we force a non-overlapping, non-auto-hiding scrollbar to counteract.\n// 6. Change the default tap highlight to be completely transparent in iOS.\n\nhtml {\n box-sizing: border-box; // 1\n font-family: sans-serif; // 2\n line-height: 1.15; // 3\n -webkit-text-size-adjust: 100%; // 4\n -ms-text-size-adjust: 100%; // 4\n -ms-overflow-style: scrollbar; // 5\n -webkit-tap-highlight-color: rgba(0,0,0,0); // 6\n}\n\n*,\n*::before,\n*::after {\n box-sizing: inherit; // 1\n}\n\n// IE10+ doesn't honor `<meta name=\"viewport\">` in some cases.\n@at-root {\n @-ms-viewport { width: device-width; }\n}\n\n// Shim for \"new\" HTML5 structural elements to display correctly (IE10, older browsers)\narticle, aside, dialog, figcaption, figure, footer, header, hgroup, main, nav, section {\n display: block;\n}\n\n// Body\n//\n// 1. Remove the margin in all browsers.\n// 2. As a best practice, apply a default `background-color`.\n\nbody {\n margin: 0; // 1\n font-family: $font-family-base;\n font-size: $font-size-base;\n font-weight: $font-weight-base;\n line-height: $line-height-base;\n color: $body-color;\n background-color: $body-bg; // 2\n}\n\n// Suppress the focus outline on elements that cannot be accessed via keyboard.\n// This prevents an unwanted focus outline from appearing around elements that\n// might still respond to pointer events.\n//\n// Credit: https://github.com/suitcss/base\n[tabindex=\"-1\"]:focus {\n outline: none !important;\n}\n\n\n// Content grouping\n//\n// 1. Add the correct box sizing in Firefox.\n// 2. Show the overflow in Edge and IE.\n\nhr {\n box-sizing: content-box; // 1\n height: 0; // 1\n overflow: visible; // 2\n}\n\n\n//\n// Typography\n//\n\n// Remove top margins from headings\n//\n// By default, `<h1>`-`<h6>` all receive top and bottom margins. We nuke the top\n// margin for easier control within type scales as it avoids margin collapsing.\nh1, h2, h3, h4, h5, h6 {\n margin-top: 0;\n margin-bottom: .5rem;\n}\n\n// Reset margins on paragraphs\n//\n// Similarly, the top margin on `<p>`s get reset. However, we also reset the\n// bottom margin to use `rem` units instead of `em`.\np {\n margin-top: 0;\n margin-bottom: 1rem;\n}\n\n// Abbreviations\n//\n// 1. Remove the bottom border in Firefox 39-.\n// 2. Add the correct text decoration in Chrome, Edge, IE, Opera, and Safari.\n// 3. Add explicit cursor to indicate changed behavior.\n// 4. Duplicate behavior to the data-* attribute for our tooltip plugin\n\nabbr[title],\nabbr[data-original-title] { // 4\n text-decoration: underline; // 2\n text-decoration: underline dotted; // 2\n cursor: help; // 3\n border-bottom: 0; // 1\n}\n\naddress {\n margin-bottom: 1rem;\n font-style: normal;\n line-height: inherit;\n}\n\nol,\nul,\ndl {\n margin-top: 0;\n margin-bottom: 1rem;\n}\n\nol ol,\nul ul,\nol ul,\nul ol {\n margin-bottom: 0;\n}\n\ndt {\n font-weight: $dt-font-weight;\n}\n\ndd {\n margin-bottom: .5rem;\n margin-left: 0; // Undo browser default\n}\n\nblockquote {\n margin: 0 0 1rem;\n}\n\ndfn {\n font-style: italic; // Add the correct font style in Android 4.3-\n}\n\nb,\nstrong {\n font-weight: bolder; // Add the correct font weight in Chrome, Edge, and Safari\n}\n\nsmall {\n font-size: 80%; // Add the correct font size in all browsers\n}\n\n//\n// Prevent `sub` and `sup` elements from affecting the line height in\n// all browsers.\n//\n\nsub,\nsup {\n position: relative;\n font-size: 75%;\n line-height: 0;\n vertical-align: baseline;\n}\n\nsub { bottom: -.25em; }\nsup { top: -.5em; }\n\n\n//\n// Links\n//\n\na {\n color: $link-color;\n text-decoration: $link-decoration;\n background-color: transparent; // Remove the gray background on active links in IE 10.\n -webkit-text-decoration-skip: objects; // Remove gaps in links underline in iOS 8+ and Safari 8+.\n\n @include hover {\n color: $link-hover-color;\n text-decoration: $link-hover-decoration;\n }\n}\n\n// And undo these styles for placeholder links/named anchors (without href)\n// which have not been made explicitly keyboard-focusable (without tabindex).\n// It would be more straightforward to just use a[href] in previous block, but that\n// causes specificity issues in many other styles that are too complex to fix.\n// See https://github.com/twbs/bootstrap/issues/19402\n\na:not([href]):not([tabindex]) {\n color: inherit;\n text-decoration: none;\n\n @include hover-focus {\n color: inherit;\n text-decoration: none;\n }\n\n &:focus {\n outline: 0;\n }\n}\n\n\n//\n// Code\n//\n\npre,\ncode,\nkbd,\nsamp {\n font-family: monospace, monospace; // Correct the inheritance and scaling of font size in all browsers.\n font-size: 1em; // Correct the odd `em` font sizing in all browsers.\n}\n\npre {\n // Remove browser default top margin\n margin-top: 0;\n // Reset browser default of `1em` to use `rem`s\n margin-bottom: 1rem;\n // Don't allow content to break outside\n overflow: auto;\n}\n\n\n//\n// Figures\n//\n\nfigure {\n // Apply a consistent margin strategy (matches our type styles).\n margin: 0 0 1rem;\n}\n\n\n//\n// Images and content\n//\n\nimg {\n vertical-align: middle;\n border-style: none; // Remove the border on images inside links in IE 10-.\n}\n\nsvg:not(:root) {\n overflow: hidden; // Hide the overflow in IE\n}\n\n\n// Avoid 300ms click delay on touch devices that support the `touch-action` CSS property.\n//\n// In particular, unlike most other browsers, IE11+Edge on Windows 10 on touch devices and IE Mobile 10-11\n// DON'T remove the click delay when `<meta name=\"viewport\" content=\"width=device-width\">` is present.\n// However, they DO support removing the click delay via `touch-action: manipulation`.\n// See:\n// * https://v4-alpha.getbootstrap.com/content/reboot/#click-delay-optimization-for-touch\n// * http://caniuse.com/#feat=css-touch-action\n// * https://patrickhlauke.github.io/touch/tests/results/#suppressing-300ms-delay\n\na,\narea,\nbutton,\n[role=\"button\"],\ninput,\nlabel,\nselect,\nsummary,\ntextarea {\n touch-action: manipulation;\n}\n\n\n//\n// Tables\n//\n\ntable {\n border-collapse: collapse; // Prevent double borders\n}\n\ncaption {\n padding-top: $table-cell-padding;\n padding-bottom: $table-cell-padding;\n color: $text-muted;\n text-align: left;\n caption-side: bottom;\n}\n\nth {\n // Matches default `<td>` alignment\n text-align: left;\n}\n\n\n//\n// Forms\n//\n\nlabel {\n // Allow labels to use `margin` for spacing.\n display: inline-block;\n margin-bottom: .5rem;\n}\n\n// Work around a Firefox/IE bug where the transparent `button` background\n// results in a loss of the default `button` focus styles.\n//\n// Credit: https://github.com/suitcss/base/\nbutton:focus {\n outline: 1px dotted;\n outline: 5px auto -webkit-focus-ring-color;\n}\n\ninput,\nbutton,\nselect,\noptgroup,\ntextarea {\n margin: 0; // Remove the margin in Firefox and Safari\n font-family: inherit;\n font-size: inherit;\n line-height: inherit;\n}\n\nbutton,\ninput {\n overflow: visible; // Show the overflow in Edge\n}\n\nbutton,\nselect {\n text-transform: none; // Remove the inheritance of text transform in Firefox\n}\n\n// 1. Prevent a WebKit bug where (2) destroys native `audio` and `video`\n// controls in Android 4.\n// 2. Correct the inability to style clickable types in iOS and Safari.\nbutton,\nhtml [type=\"button\"], // 1\n[type=\"reset\"],\n[type=\"submit\"] {\n -webkit-appearance: button; // 2\n}\n\n// Remove inner border and padding from Firefox, but don't restore the outline like Normalize.\nbutton::-moz-focus-inner,\n[type=\"button\"]::-moz-focus-inner,\n[type=\"reset\"]::-moz-focus-inner,\n[type=\"submit\"]::-moz-focus-inner {\n padding: 0;\n border-style: none;\n}\n\ninput[type=\"radio\"],\ninput[type=\"checkbox\"] {\n box-sizing: border-box; // 1. Add the correct box sizing in IE 10-\n padding: 0; // 2. Remove the padding in IE 10-\n}\n\n\ninput[type=\"date\"],\ninput[type=\"time\"],\ninput[type=\"datetime-local\"],\ninput[type=\"month\"] {\n // Remove the default appearance of temporal inputs to avoid a Mobile Safari\n // bug where setting a custom line-height prevents text from being vertically\n // centered within the input.\n // See https://bugs.webkit.org/show_bug.cgi?id=139848\n // and https://github.com/twbs/bootstrap/issues/11266\n -webkit-appearance: listbox;\n}\n\ntextarea {\n overflow: auto; // Remove the default vertical scrollbar in IE.\n // Textareas should really only resize vertically so they don't break their (horizontal) containers.\n resize: vertical;\n}\n\nfieldset {\n // Browsers set a default `min-width: min-content;` on fieldsets,\n // unlike e.g. `<div>`s, which have `min-width: 0;` by default.\n // So we reset that to ensure fieldsets behave more like a standard block element.\n // See https://github.com/twbs/bootstrap/issues/12359\n // and https://html.spec.whatwg.org/multipage/#the-fieldset-and-legend-elements\n min-width: 0;\n // Reset the default outline behavior of fieldsets so they don't affect page layout.\n padding: 0;\n margin: 0;\n border: 0;\n}\n\n// 1. Correct the text wrapping in Edge and IE.\n// 2. Correct the color inheritance from `fieldset` elements in IE.\nlegend {\n display: block;\n width: 100%;\n max-width: 100%; // 1\n padding: 0;\n margin-bottom: .5rem;\n font-size: 1.5rem;\n line-height: inherit;\n color: inherit; // 2\n white-space: normal; // 1\n}\n\nprogress {\n vertical-align: baseline; // Add the correct vertical alignment in Chrome, Firefox, and Opera.\n}\n\n// Correct the cursor style of increment and decrement buttons in Chrome.\n[type=\"number\"]::-webkit-inner-spin-button,\n[type=\"number\"]::-webkit-outer-spin-button {\n height: auto;\n}\n\n[type=\"search\"] {\n // This overrides the extra rounded corners on search inputs in iOS so that our\n // `.form-control` class can properly style them. Note that this cannot simply\n // be added to `.form-control` as it's not specific enough. For details, see\n // https://github.com/twbs/bootstrap/issues/11586.\n outline-offset: -2px; // 2. Correct the outline style in Safari.\n -webkit-appearance: none;\n}\n\n//\n// Remove the inner padding and cancel buttons in Chrome and Safari on macOS.\n//\n\n[type=\"search\"]::-webkit-search-cancel-button,\n[type=\"search\"]::-webkit-search-decoration {\n -webkit-appearance: none;\n}\n\n//\n// 1. Correct the inability to style clickable types in iOS and Safari.\n// 2. Change font properties to `inherit` in Safari.\n//\n\n::-webkit-file-upload-button {\n font: inherit; // 2\n -webkit-appearance: button; // 1\n}\n\n//\n// Correct element displays\n//\n\noutput {\n display: inline-block;\n}\n\nsummary {\n display: list-item; // Add the correct display in all browsers\n}\n\ntemplate {\n display: none; // Add the correct display in IE\n}\n\n// Always hide an element with the `hidden` HTML attribute (from PureCSS).\n// Needed for proper display in IE 10-.\n[hidden] {\n display: none !important;\n}\n","html {\n box-sizing: border-box;\n font-family: sans-serif;\n line-height: 1.15;\n -webkit-text-size-adjust: 100%;\n -ms-text-size-adjust: 100%;\n -ms-overflow-style: scrollbar;\n -webkit-tap-highlight-color: transparent;\n}\n\n*,\n*::before,\n*::after {\n box-sizing: inherit;\n}\n\n@-ms-viewport {\n width: device-width;\n}\n\narticle, aside, dialog, figcaption, figure, footer, header, hgroup, main, nav, section {\n display: block;\n}\n\nbody {\n margin: 0;\n font-family: -apple-system, BlinkMacSystemFont, \"Segoe UI\", Roboto, \"Helvetica Neue\", Arial, sans-serif;\n font-size: 1rem;\n font-weight: normal;\n line-height: 1.5;\n color: #212529;\n background-color: #fff;\n}\n\n[tabindex=\"-1\"]:focus {\n outline: none !important;\n}\n\nhr {\n box-sizing: content-box;\n height: 0;\n overflow: visible;\n}\n\nh1, h2, h3, h4, h5, h6 {\n margin-top: 0;\n margin-bottom: .5rem;\n}\n\np {\n margin-top: 0;\n margin-bottom: 1rem;\n}\n\nabbr[title],\nabbr[data-original-title] {\n text-decoration: underline;\n -webkit-text-decoration: underline dotted;\n text-decoration: underline dotted;\n cursor: help;\n border-bottom: 0;\n}\n\naddress {\n margin-bottom: 1rem;\n font-style: normal;\n line-height: inherit;\n}\n\nol,\nul,\ndl {\n margin-top: 0;\n margin-bottom: 1rem;\n}\n\nol ol,\nul ul,\nol ul,\nul ol {\n margin-bottom: 0;\n}\n\ndt {\n font-weight: bold;\n}\n\ndd {\n margin-bottom: .5rem;\n margin-left: 0;\n}\n\nblockquote {\n margin: 0 0 1rem;\n}\n\ndfn {\n font-style: italic;\n}\n\nb,\nstrong {\n font-weight: bolder;\n}\n\nsmall {\n font-size: 80%;\n}\n\nsub,\nsup {\n position: relative;\n font-size: 75%;\n line-height: 0;\n vertical-align: baseline;\n}\n\nsub {\n bottom: -.25em;\n}\n\nsup {\n top: -.5em;\n}\n\na {\n color: #007bff;\n text-decoration: none;\n background-color: transparent;\n -webkit-text-decoration-skip: objects;\n}\n\na:hover {\n color: #0056b3;\n text-decoration: underline;\n}\n\na:not([href]):not([tabindex]) {\n color: inherit;\n text-decoration: none;\n}\n\na:not([href]):not([tabindex]):focus, a:not([href]):not([tabindex]):hover {\n color: inherit;\n text-decoration: none;\n}\n\na:not([href]):not([tabindex]):focus {\n outline: 0;\n}\n\npre,\ncode,\nkbd,\nsamp {\n font-family: monospace, monospace;\n font-size: 1em;\n}\n\npre {\n margin-top: 0;\n margin-bottom: 1rem;\n overflow: auto;\n}\n\nfigure {\n margin: 0 0 1rem;\n}\n\nimg {\n vertical-align: middle;\n border-style: none;\n}\n\nsvg:not(:root) {\n overflow: hidden;\n}\n\na,\narea,\nbutton,\n[role=\"button\"],\ninput,\nlabel,\nselect,\nsummary,\ntextarea {\n -ms-touch-action: manipulation;\n touch-action: manipulation;\n}\n\ntable {\n border-collapse: collapse;\n}\n\ncaption {\n padding-top: 0.75rem;\n padding-bottom: 0.75rem;\n color: #868e96;\n text-align: left;\n caption-side: bottom;\n}\n\nth {\n text-align: left;\n}\n\nlabel {\n display: inline-block;\n margin-bottom: .5rem;\n}\n\nbutton:focus {\n outline: 1px dotted;\n outline: 5px auto -webkit-focus-ring-color;\n}\n\ninput,\nbutton,\nselect,\noptgroup,\ntextarea {\n margin: 0;\n font-family: inherit;\n font-size: inherit;\n line-height: inherit;\n}\n\nbutton,\ninput {\n overflow: visible;\n}\n\nbutton,\nselect {\n text-transform: none;\n}\n\nbutton,\nhtml [type=\"button\"],\n[type=\"reset\"],\n[type=\"submit\"] {\n -webkit-appearance: button;\n}\n\nbutton::-moz-focus-inner,\n[type=\"button\"]::-moz-focus-inner,\n[type=\"reset\"]::-moz-focus-inner,\n[type=\"submit\"]::-moz-focus-inner {\n padding: 0;\n border-style: none;\n}\n\ninput[type=\"radio\"],\ninput[type=\"checkbox\"] {\n box-sizing: border-box;\n padding: 0;\n}\n\ninput[type=\"date\"],\ninput[type=\"time\"],\ninput[type=\"datetime-local\"],\ninput[type=\"month\"] {\n -webkit-appearance: listbox;\n}\n\ntextarea {\n overflow: auto;\n resize: vertical;\n}\n\nfieldset {\n min-width: 0;\n padding: 0;\n margin: 0;\n border: 0;\n}\n\nlegend {\n display: block;\n width: 100%;\n max-width: 100%;\n padding: 0;\n margin-bottom: .5rem;\n font-size: 1.5rem;\n line-height: inherit;\n color: inherit;\n white-space: normal;\n}\n\nprogress {\n vertical-align: baseline;\n}\n\n[type=\"number\"]::-webkit-inner-spin-button,\n[type=\"number\"]::-webkit-outer-spin-button {\n height: auto;\n}\n\n[type=\"search\"] {\n outline-offset: -2px;\n -webkit-appearance: none;\n}\n\n[type=\"search\"]::-webkit-search-cancel-button,\n[type=\"search\"]::-webkit-search-decoration {\n -webkit-appearance: none;\n}\n\n::-webkit-file-upload-button {\n font: inherit;\n -webkit-appearance: button;\n}\n\noutput {\n display: inline-block;\n}\n\nsummary {\n display: list-item;\n}\n\ntemplate {\n display: none;\n}\n\n[hidden] {\n display: none !important;\n}\n/*# sourceMappingURL=bootstrap-reboot.css.map */","html {\n box-sizing: border-box;\n font-family: sans-serif;\n line-height: 1.15;\n -webkit-text-size-adjust: 100%;\n -ms-text-size-adjust: 100%;\n -ms-overflow-style: scrollbar;\n -webkit-tap-highlight-color: transparent;\n}\n\n*,\n*::before,\n*::after {\n box-sizing: inherit;\n}\n\n@-ms-viewport {\n width: device-width;\n}\n\narticle, aside, dialog, figcaption, figure, footer, header, hgroup, main, nav, section {\n display: block;\n}\n\nbody {\n margin: 0;\n font-family: -apple-system, BlinkMacSystemFont, \"Segoe UI\", Roboto, \"Helvetica Neue\", Arial, sans-serif;\n font-size: 1rem;\n font-weight: normal;\n line-height: 1.5;\n color: #212529;\n background-color: #fff;\n}\n\n[tabindex=\"-1\"]:focus {\n outline: none !important;\n}\n\nhr {\n box-sizing: content-box;\n height: 0;\n overflow: visible;\n}\n\nh1, h2, h3, h4, h5, h6 {\n margin-top: 0;\n margin-bottom: .5rem;\n}\n\np {\n margin-top: 0;\n margin-bottom: 1rem;\n}\n\nabbr[title],\nabbr[data-original-title] {\n text-decoration: underline;\n text-decoration: underline dotted;\n cursor: help;\n border-bottom: 0;\n}\n\naddress {\n margin-bottom: 1rem;\n font-style: normal;\n line-height: inherit;\n}\n\nol,\nul,\ndl {\n margin-top: 0;\n margin-bottom: 1rem;\n}\n\nol ol,\nul ul,\nol ul,\nul ol {\n margin-bottom: 0;\n}\n\ndt {\n font-weight: bold;\n}\n\ndd {\n margin-bottom: .5rem;\n margin-left: 0;\n}\n\nblockquote {\n margin: 0 0 1rem;\n}\n\ndfn {\n font-style: italic;\n}\n\nb,\nstrong {\n font-weight: bolder;\n}\n\nsmall {\n font-size: 80%;\n}\n\nsub,\nsup {\n position: relative;\n font-size: 75%;\n line-height: 0;\n vertical-align: baseline;\n}\n\nsub {\n bottom: -.25em;\n}\n\nsup {\n top: -.5em;\n}\n\na {\n color: #007bff;\n text-decoration: none;\n background-color: transparent;\n -webkit-text-decoration-skip: objects;\n}\n\na:hover {\n color: #0056b3;\n text-decoration: underline;\n}\n\na:not([href]):not([tabindex]) {\n color: inherit;\n text-decoration: none;\n}\n\na:not([href]):not([tabindex]):focus, a:not([href]):not([tabindex]):hover {\n color: inherit;\n text-decoration: none;\n}\n\na:not([href]):not([tabindex]):focus {\n outline: 0;\n}\n\npre,\ncode,\nkbd,\nsamp {\n font-family: monospace, monospace;\n font-size: 1em;\n}\n\npre {\n margin-top: 0;\n margin-bottom: 1rem;\n overflow: auto;\n}\n\nfigure {\n margin: 0 0 1rem;\n}\n\nimg {\n vertical-align: middle;\n border-style: none;\n}\n\nsvg:not(:root) {\n overflow: hidden;\n}\n\na,\narea,\nbutton,\n[role=\"button\"],\ninput,\nlabel,\nselect,\nsummary,\ntextarea {\n touch-action: manipulation;\n}\n\ntable {\n border-collapse: collapse;\n}\n\ncaption {\n padding-top: 0.75rem;\n padding-bottom: 0.75rem;\n color: #868e96;\n text-align: left;\n caption-side: bottom;\n}\n\nth {\n text-align: left;\n}\n\nlabel {\n display: inline-block;\n margin-bottom: .5rem;\n}\n\nbutton:focus {\n outline: 1px dotted;\n outline: 5px auto -webkit-focus-ring-color;\n}\n\ninput,\nbutton,\nselect,\noptgroup,\ntextarea {\n margin: 0;\n font-family: inherit;\n font-size: inherit;\n line-height: inherit;\n}\n\nbutton,\ninput {\n overflow: visible;\n}\n\nbutton,\nselect {\n text-transform: none;\n}\n\nbutton,\nhtml [type=\"button\"],\n[type=\"reset\"],\n[type=\"submit\"] {\n -webkit-appearance: button;\n}\n\nbutton::-moz-focus-inner,\n[type=\"button\"]::-moz-focus-inner,\n[type=\"reset\"]::-moz-focus-inner,\n[type=\"submit\"]::-moz-focus-inner {\n padding: 0;\n border-style: none;\n}\n\ninput[type=\"radio\"],\ninput[type=\"checkbox\"] {\n box-sizing: border-box;\n padding: 0;\n}\n\ninput[type=\"date\"],\ninput[type=\"time\"],\ninput[type=\"datetime-local\"],\ninput[type=\"month\"] {\n -webkit-appearance: listbox;\n}\n\ntextarea {\n overflow: auto;\n resize: vertical;\n}\n\nfieldset {\n min-width: 0;\n padding: 0;\n margin: 0;\n border: 0;\n}\n\nlegend {\n display: block;\n width: 100%;\n max-width: 100%;\n padding: 0;\n margin-bottom: .5rem;\n font-size: 1.5rem;\n line-height: inherit;\n color: inherit;\n white-space: normal;\n}\n\nprogress {\n vertical-align: baseline;\n}\n\n[type=\"number\"]::-webkit-inner-spin-button,\n[type=\"number\"]::-webkit-outer-spin-button {\n height: auto;\n}\n\n[type=\"search\"] {\n outline-offset: -2px;\n -webkit-appearance: none;\n}\n\n[type=\"search\"]::-webkit-search-cancel-button,\n[type=\"search\"]::-webkit-search-decoration {\n -webkit-appearance: none;\n}\n\n::-webkit-file-upload-button {\n font: inherit;\n -webkit-appearance: button;\n}\n\noutput {\n display: inline-block;\n}\n\nsummary {\n display: list-item;\n}\n\ntemplate {\n display: none;\n}\n\n[hidden] {\n display: none !important;\n}\n\n/*# sourceMappingURL=bootstrap-reboot.css.map */","@mixin hover {\n // TODO: re-enable along with mq4-hover-shim\n// @if $enable-hover-media-query {\n// // See Media Queries Level 4: https://drafts.csswg.org/mediaqueries/#hover\n// // Currently shimmed by https://github.com/twbs/mq4-hover-shim\n// @media (hover: hover) {\n// &:hover { @content }\n// }\n// }\n// @else {\n// scss-lint:disable Indentation\n &:hover { @content }\n// scss-lint:enable Indentation\n// }\n}\n\n\n@mixin hover-focus {\n @if $enable-hover-media-query {\n &:focus { @content }\n @include hover { @content }\n } @else {\n &:focus,\n &:hover {\n @content\n }\n }\n}\n\n@mixin plain-hover-focus {\n @if $enable-hover-media-query {\n &,\n &:focus {\n @content\n }\n @include hover { @content }\n } @else {\n &,\n &:focus,\n &:hover {\n @content\n }\n }\n}\n\n@mixin hover-focus-active {\n @if $enable-hover-media-query {\n &:focus,\n &:active {\n @content\n }\n @include hover { @content }\n } @else {\n &:focus,\n &:active,\n &:hover {\n @content\n }\n }\n}\n"]} \ No newline at end of file
diff --git a/library/bootstrap/css/bootstrap-theme.css b/library/bootstrap/css/bootstrap-theme.css
deleted file mode 100644
index 31d888266..000000000
--- a/library/bootstrap/css/bootstrap-theme.css
+++ /dev/null
@@ -1,587 +0,0 @@
-/*!
- * Bootstrap v3.3.7 (http://getbootstrap.com)
- * Copyright 2011-2016 Twitter, Inc.
- * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
- */
-.btn-default,
-.btn-primary,
-.btn-success,
-.btn-info,
-.btn-warning,
-.btn-danger {
- text-shadow: 0 -1px 0 rgba(0, 0, 0, .2);
- -webkit-box-shadow: inset 0 1px 0 rgba(255, 255, 255, .15), 0 1px 1px rgba(0, 0, 0, .075);
- box-shadow: inset 0 1px 0 rgba(255, 255, 255, .15), 0 1px 1px rgba(0, 0, 0, .075);
-}
-.btn-default:active,
-.btn-primary:active,
-.btn-success:active,
-.btn-info:active,
-.btn-warning:active,
-.btn-danger:active,
-.btn-default.active,
-.btn-primary.active,
-.btn-success.active,
-.btn-info.active,
-.btn-warning.active,
-.btn-danger.active {
- -webkit-box-shadow: inset 0 3px 5px rgba(0, 0, 0, .125);
- box-shadow: inset 0 3px 5px rgba(0, 0, 0, .125);
-}
-.btn-default.disabled,
-.btn-primary.disabled,
-.btn-success.disabled,
-.btn-info.disabled,
-.btn-warning.disabled,
-.btn-danger.disabled,
-.btn-default[disabled],
-.btn-primary[disabled],
-.btn-success[disabled],
-.btn-info[disabled],
-.btn-warning[disabled],
-.btn-danger[disabled],
-fieldset[disabled] .btn-default,
-fieldset[disabled] .btn-primary,
-fieldset[disabled] .btn-success,
-fieldset[disabled] .btn-info,
-fieldset[disabled] .btn-warning,
-fieldset[disabled] .btn-danger {
- -webkit-box-shadow: none;
- box-shadow: none;
-}
-.btn-default .badge,
-.btn-primary .badge,
-.btn-success .badge,
-.btn-info .badge,
-.btn-warning .badge,
-.btn-danger .badge {
- text-shadow: none;
-}
-.btn:active,
-.btn.active {
- background-image: none;
-}
-.btn-default {
- text-shadow: 0 1px 0 #fff;
- background-image: -webkit-linear-gradient(top, #fff 0%, #e0e0e0 100%);
- background-image: -o-linear-gradient(top, #fff 0%, #e0e0e0 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#fff), to(#e0e0e0));
- background-image: linear-gradient(to bottom, #fff 0%, #e0e0e0 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffffffff', endColorstr='#ffe0e0e0', GradientType=0);
- filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);
- background-repeat: repeat-x;
- border-color: #dbdbdb;
- border-color: #ccc;
-}
-.btn-default:hover,
-.btn-default:focus {
- background-color: #e0e0e0;
- background-position: 0 -15px;
-}
-.btn-default:active,
-.btn-default.active {
- background-color: #e0e0e0;
- border-color: #dbdbdb;
-}
-.btn-default.disabled,
-.btn-default[disabled],
-fieldset[disabled] .btn-default,
-.btn-default.disabled:hover,
-.btn-default[disabled]:hover,
-fieldset[disabled] .btn-default:hover,
-.btn-default.disabled:focus,
-.btn-default[disabled]:focus,
-fieldset[disabled] .btn-default:focus,
-.btn-default.disabled.focus,
-.btn-default[disabled].focus,
-fieldset[disabled] .btn-default.focus,
-.btn-default.disabled:active,
-.btn-default[disabled]:active,
-fieldset[disabled] .btn-default:active,
-.btn-default.disabled.active,
-.btn-default[disabled].active,
-fieldset[disabled] .btn-default.active {
- background-color: #e0e0e0;
- background-image: none;
-}
-.btn-primary {
- background-image: -webkit-linear-gradient(top, #337ab7 0%, #265a88 100%);
- background-image: -o-linear-gradient(top, #337ab7 0%, #265a88 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#337ab7), to(#265a88));
- background-image: linear-gradient(to bottom, #337ab7 0%, #265a88 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff337ab7', endColorstr='#ff265a88', GradientType=0);
- filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);
- background-repeat: repeat-x;
- border-color: #245580;
-}
-.btn-primary:hover,
-.btn-primary:focus {
- background-color: #265a88;
- background-position: 0 -15px;
-}
-.btn-primary:active,
-.btn-primary.active {
- background-color: #265a88;
- border-color: #245580;
-}
-.btn-primary.disabled,
-.btn-primary[disabled],
-fieldset[disabled] .btn-primary,
-.btn-primary.disabled:hover,
-.btn-primary[disabled]:hover,
-fieldset[disabled] .btn-primary:hover,
-.btn-primary.disabled:focus,
-.btn-primary[disabled]:focus,
-fieldset[disabled] .btn-primary:focus,
-.btn-primary.disabled.focus,
-.btn-primary[disabled].focus,
-fieldset[disabled] .btn-primary.focus,
-.btn-primary.disabled:active,
-.btn-primary[disabled]:active,
-fieldset[disabled] .btn-primary:active,
-.btn-primary.disabled.active,
-.btn-primary[disabled].active,
-fieldset[disabled] .btn-primary.active {
- background-color: #265a88;
- background-image: none;
-}
-.btn-success {
- background-image: -webkit-linear-gradient(top, #5cb85c 0%, #419641 100%);
- background-image: -o-linear-gradient(top, #5cb85c 0%, #419641 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#5cb85c), to(#419641));
- background-image: linear-gradient(to bottom, #5cb85c 0%, #419641 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff5cb85c', endColorstr='#ff419641', GradientType=0);
- filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);
- background-repeat: repeat-x;
- border-color: #3e8f3e;
-}
-.btn-success:hover,
-.btn-success:focus {
- background-color: #419641;
- background-position: 0 -15px;
-}
-.btn-success:active,
-.btn-success.active {
- background-color: #419641;
- border-color: #3e8f3e;
-}
-.btn-success.disabled,
-.btn-success[disabled],
-fieldset[disabled] .btn-success,
-.btn-success.disabled:hover,
-.btn-success[disabled]:hover,
-fieldset[disabled] .btn-success:hover,
-.btn-success.disabled:focus,
-.btn-success[disabled]:focus,
-fieldset[disabled] .btn-success:focus,
-.btn-success.disabled.focus,
-.btn-success[disabled].focus,
-fieldset[disabled] .btn-success.focus,
-.btn-success.disabled:active,
-.btn-success[disabled]:active,
-fieldset[disabled] .btn-success:active,
-.btn-success.disabled.active,
-.btn-success[disabled].active,
-fieldset[disabled] .btn-success.active {
- background-color: #419641;
- background-image: none;
-}
-.btn-info {
- background-image: -webkit-linear-gradient(top, #5bc0de 0%, #2aabd2 100%);
- background-image: -o-linear-gradient(top, #5bc0de 0%, #2aabd2 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#5bc0de), to(#2aabd2));
- background-image: linear-gradient(to bottom, #5bc0de 0%, #2aabd2 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff5bc0de', endColorstr='#ff2aabd2', GradientType=0);
- filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);
- background-repeat: repeat-x;
- border-color: #28a4c9;
-}
-.btn-info:hover,
-.btn-info:focus {
- background-color: #2aabd2;
- background-position: 0 -15px;
-}
-.btn-info:active,
-.btn-info.active {
- background-color: #2aabd2;
- border-color: #28a4c9;
-}
-.btn-info.disabled,
-.btn-info[disabled],
-fieldset[disabled] .btn-info,
-.btn-info.disabled:hover,
-.btn-info[disabled]:hover,
-fieldset[disabled] .btn-info:hover,
-.btn-info.disabled:focus,
-.btn-info[disabled]:focus,
-fieldset[disabled] .btn-info:focus,
-.btn-info.disabled.focus,
-.btn-info[disabled].focus,
-fieldset[disabled] .btn-info.focus,
-.btn-info.disabled:active,
-.btn-info[disabled]:active,
-fieldset[disabled] .btn-info:active,
-.btn-info.disabled.active,
-.btn-info[disabled].active,
-fieldset[disabled] .btn-info.active {
- background-color: #2aabd2;
- background-image: none;
-}
-.btn-warning {
- background-image: -webkit-linear-gradient(top, #f0ad4e 0%, #eb9316 100%);
- background-image: -o-linear-gradient(top, #f0ad4e 0%, #eb9316 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#f0ad4e), to(#eb9316));
- background-image: linear-gradient(to bottom, #f0ad4e 0%, #eb9316 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#fff0ad4e', endColorstr='#ffeb9316', GradientType=0);
- filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);
- background-repeat: repeat-x;
- border-color: #e38d13;
-}
-.btn-warning:hover,
-.btn-warning:focus {
- background-color: #eb9316;
- background-position: 0 -15px;
-}
-.btn-warning:active,
-.btn-warning.active {
- background-color: #eb9316;
- border-color: #e38d13;
-}
-.btn-warning.disabled,
-.btn-warning[disabled],
-fieldset[disabled] .btn-warning,
-.btn-warning.disabled:hover,
-.btn-warning[disabled]:hover,
-fieldset[disabled] .btn-warning:hover,
-.btn-warning.disabled:focus,
-.btn-warning[disabled]:focus,
-fieldset[disabled] .btn-warning:focus,
-.btn-warning.disabled.focus,
-.btn-warning[disabled].focus,
-fieldset[disabled] .btn-warning.focus,
-.btn-warning.disabled:active,
-.btn-warning[disabled]:active,
-fieldset[disabled] .btn-warning:active,
-.btn-warning.disabled.active,
-.btn-warning[disabled].active,
-fieldset[disabled] .btn-warning.active {
- background-color: #eb9316;
- background-image: none;
-}
-.btn-danger {
- background-image: -webkit-linear-gradient(top, #d9534f 0%, #c12e2a 100%);
- background-image: -o-linear-gradient(top, #d9534f 0%, #c12e2a 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#d9534f), to(#c12e2a));
- background-image: linear-gradient(to bottom, #d9534f 0%, #c12e2a 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffd9534f', endColorstr='#ffc12e2a', GradientType=0);
- filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);
- background-repeat: repeat-x;
- border-color: #b92c28;
-}
-.btn-danger:hover,
-.btn-danger:focus {
- background-color: #c12e2a;
- background-position: 0 -15px;
-}
-.btn-danger:active,
-.btn-danger.active {
- background-color: #c12e2a;
- border-color: #b92c28;
-}
-.btn-danger.disabled,
-.btn-danger[disabled],
-fieldset[disabled] .btn-danger,
-.btn-danger.disabled:hover,
-.btn-danger[disabled]:hover,
-fieldset[disabled] .btn-danger:hover,
-.btn-danger.disabled:focus,
-.btn-danger[disabled]:focus,
-fieldset[disabled] .btn-danger:focus,
-.btn-danger.disabled.focus,
-.btn-danger[disabled].focus,
-fieldset[disabled] .btn-danger.focus,
-.btn-danger.disabled:active,
-.btn-danger[disabled]:active,
-fieldset[disabled] .btn-danger:active,
-.btn-danger.disabled.active,
-.btn-danger[disabled].active,
-fieldset[disabled] .btn-danger.active {
- background-color: #c12e2a;
- background-image: none;
-}
-.thumbnail,
-.img-thumbnail {
- -webkit-box-shadow: 0 1px 2px rgba(0, 0, 0, .075);
- box-shadow: 0 1px 2px rgba(0, 0, 0, .075);
-}
-.dropdown-menu > li > a:hover,
-.dropdown-menu > li > a:focus {
- background-color: #e8e8e8;
- background-image: -webkit-linear-gradient(top, #f5f5f5 0%, #e8e8e8 100%);
- background-image: -o-linear-gradient(top, #f5f5f5 0%, #e8e8e8 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#f5f5f5), to(#e8e8e8));
- background-image: linear-gradient(to bottom, #f5f5f5 0%, #e8e8e8 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#fff5f5f5', endColorstr='#ffe8e8e8', GradientType=0);
- background-repeat: repeat-x;
-}
-.dropdown-menu > .active > a,
-.dropdown-menu > .active > a:hover,
-.dropdown-menu > .active > a:focus {
- background-color: #2e6da4;
- background-image: -webkit-linear-gradient(top, #337ab7 0%, #2e6da4 100%);
- background-image: -o-linear-gradient(top, #337ab7 0%, #2e6da4 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#337ab7), to(#2e6da4));
- background-image: linear-gradient(to bottom, #337ab7 0%, #2e6da4 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff337ab7', endColorstr='#ff2e6da4', GradientType=0);
- background-repeat: repeat-x;
-}
-.navbar-default {
- background-image: -webkit-linear-gradient(top, #fff 0%, #f8f8f8 100%);
- background-image: -o-linear-gradient(top, #fff 0%, #f8f8f8 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#fff), to(#f8f8f8));
- background-image: linear-gradient(to bottom, #fff 0%, #f8f8f8 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffffffff', endColorstr='#fff8f8f8', GradientType=0);
- filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);
- background-repeat: repeat-x;
- border-radius: 4px;
- -webkit-box-shadow: inset 0 1px 0 rgba(255, 255, 255, .15), 0 1px 5px rgba(0, 0, 0, .075);
- box-shadow: inset 0 1px 0 rgba(255, 255, 255, .15), 0 1px 5px rgba(0, 0, 0, .075);
-}
-.navbar-default .navbar-nav > .open > a,
-.navbar-default .navbar-nav > .active > a {
- background-image: -webkit-linear-gradient(top, #dbdbdb 0%, #e2e2e2 100%);
- background-image: -o-linear-gradient(top, #dbdbdb 0%, #e2e2e2 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#dbdbdb), to(#e2e2e2));
- background-image: linear-gradient(to bottom, #dbdbdb 0%, #e2e2e2 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffdbdbdb', endColorstr='#ffe2e2e2', GradientType=0);
- background-repeat: repeat-x;
- -webkit-box-shadow: inset 0 3px 9px rgba(0, 0, 0, .075);
- box-shadow: inset 0 3px 9px rgba(0, 0, 0, .075);
-}
-.navbar-brand,
-.navbar-nav > li > a {
- text-shadow: 0 1px 0 rgba(255, 255, 255, .25);
-}
-.navbar-inverse {
- background-image: -webkit-linear-gradient(top, #3c3c3c 0%, #222 100%);
- background-image: -o-linear-gradient(top, #3c3c3c 0%, #222 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#3c3c3c), to(#222));
- background-image: linear-gradient(to bottom, #3c3c3c 0%, #222 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff3c3c3c', endColorstr='#ff222222', GradientType=0);
- filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);
- background-repeat: repeat-x;
- border-radius: 4px;
-}
-.navbar-inverse .navbar-nav > .open > a,
-.navbar-inverse .navbar-nav > .active > a {
- background-image: -webkit-linear-gradient(top, #080808 0%, #0f0f0f 100%);
- background-image: -o-linear-gradient(top, #080808 0%, #0f0f0f 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#080808), to(#0f0f0f));
- background-image: linear-gradient(to bottom, #080808 0%, #0f0f0f 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff080808', endColorstr='#ff0f0f0f', GradientType=0);
- background-repeat: repeat-x;
- -webkit-box-shadow: inset 0 3px 9px rgba(0, 0, 0, .25);
- box-shadow: inset 0 3px 9px rgba(0, 0, 0, .25);
-}
-.navbar-inverse .navbar-brand,
-.navbar-inverse .navbar-nav > li > a {
- text-shadow: 0 -1px 0 rgba(0, 0, 0, .25);
-}
-.navbar-static-top,
-.navbar-fixed-top,
-.navbar-fixed-bottom {
- border-radius: 0;
-}
-@media (max-width: 767px) {
- .navbar .navbar-nav .open .dropdown-menu > .active > a,
- .navbar .navbar-nav .open .dropdown-menu > .active > a:hover,
- .navbar .navbar-nav .open .dropdown-menu > .active > a:focus {
- color: #fff;
- background-image: -webkit-linear-gradient(top, #337ab7 0%, #2e6da4 100%);
- background-image: -o-linear-gradient(top, #337ab7 0%, #2e6da4 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#337ab7), to(#2e6da4));
- background-image: linear-gradient(to bottom, #337ab7 0%, #2e6da4 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff337ab7', endColorstr='#ff2e6da4', GradientType=0);
- background-repeat: repeat-x;
- }
-}
-.alert {
- text-shadow: 0 1px 0 rgba(255, 255, 255, .2);
- -webkit-box-shadow: inset 0 1px 0 rgba(255, 255, 255, .25), 0 1px 2px rgba(0, 0, 0, .05);
- box-shadow: inset 0 1px 0 rgba(255, 255, 255, .25), 0 1px 2px rgba(0, 0, 0, .05);
-}
-.alert-success {
- background-image: -webkit-linear-gradient(top, #dff0d8 0%, #c8e5bc 100%);
- background-image: -o-linear-gradient(top, #dff0d8 0%, #c8e5bc 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#dff0d8), to(#c8e5bc));
- background-image: linear-gradient(to bottom, #dff0d8 0%, #c8e5bc 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffdff0d8', endColorstr='#ffc8e5bc', GradientType=0);
- background-repeat: repeat-x;
- border-color: #b2dba1;
-}
-.alert-info {
- background-image: -webkit-linear-gradient(top, #d9edf7 0%, #b9def0 100%);
- background-image: -o-linear-gradient(top, #d9edf7 0%, #b9def0 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#d9edf7), to(#b9def0));
- background-image: linear-gradient(to bottom, #d9edf7 0%, #b9def0 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffd9edf7', endColorstr='#ffb9def0', GradientType=0);
- background-repeat: repeat-x;
- border-color: #9acfea;
-}
-.alert-warning {
- background-image: -webkit-linear-gradient(top, #fcf8e3 0%, #f8efc0 100%);
- background-image: -o-linear-gradient(top, #fcf8e3 0%, #f8efc0 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#fcf8e3), to(#f8efc0));
- background-image: linear-gradient(to bottom, #fcf8e3 0%, #f8efc0 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#fffcf8e3', endColorstr='#fff8efc0', GradientType=0);
- background-repeat: repeat-x;
- border-color: #f5e79e;
-}
-.alert-danger {
- background-image: -webkit-linear-gradient(top, #f2dede 0%, #e7c3c3 100%);
- background-image: -o-linear-gradient(top, #f2dede 0%, #e7c3c3 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#f2dede), to(#e7c3c3));
- background-image: linear-gradient(to bottom, #f2dede 0%, #e7c3c3 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#fff2dede', endColorstr='#ffe7c3c3', GradientType=0);
- background-repeat: repeat-x;
- border-color: #dca7a7;
-}
-.progress {
- background-image: -webkit-linear-gradient(top, #ebebeb 0%, #f5f5f5 100%);
- background-image: -o-linear-gradient(top, #ebebeb 0%, #f5f5f5 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#ebebeb), to(#f5f5f5));
- background-image: linear-gradient(to bottom, #ebebeb 0%, #f5f5f5 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffebebeb', endColorstr='#fff5f5f5', GradientType=0);
- background-repeat: repeat-x;
-}
-.progress-bar {
- background-image: -webkit-linear-gradient(top, #337ab7 0%, #286090 100%);
- background-image: -o-linear-gradient(top, #337ab7 0%, #286090 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#337ab7), to(#286090));
- background-image: linear-gradient(to bottom, #337ab7 0%, #286090 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff337ab7', endColorstr='#ff286090', GradientType=0);
- background-repeat: repeat-x;
-}
-.progress-bar-success {
- background-image: -webkit-linear-gradient(top, #5cb85c 0%, #449d44 100%);
- background-image: -o-linear-gradient(top, #5cb85c 0%, #449d44 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#5cb85c), to(#449d44));
- background-image: linear-gradient(to bottom, #5cb85c 0%, #449d44 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff5cb85c', endColorstr='#ff449d44', GradientType=0);
- background-repeat: repeat-x;
-}
-.progress-bar-info {
- background-image: -webkit-linear-gradient(top, #5bc0de 0%, #31b0d5 100%);
- background-image: -o-linear-gradient(top, #5bc0de 0%, #31b0d5 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#5bc0de), to(#31b0d5));
- background-image: linear-gradient(to bottom, #5bc0de 0%, #31b0d5 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff5bc0de', endColorstr='#ff31b0d5', GradientType=0);
- background-repeat: repeat-x;
-}
-.progress-bar-warning {
- background-image: -webkit-linear-gradient(top, #f0ad4e 0%, #ec971f 100%);
- background-image: -o-linear-gradient(top, #f0ad4e 0%, #ec971f 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#f0ad4e), to(#ec971f));
- background-image: linear-gradient(to bottom, #f0ad4e 0%, #ec971f 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#fff0ad4e', endColorstr='#ffec971f', GradientType=0);
- background-repeat: repeat-x;
-}
-.progress-bar-danger {
- background-image: -webkit-linear-gradient(top, #d9534f 0%, #c9302c 100%);
- background-image: -o-linear-gradient(top, #d9534f 0%, #c9302c 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#d9534f), to(#c9302c));
- background-image: linear-gradient(to bottom, #d9534f 0%, #c9302c 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffd9534f', endColorstr='#ffc9302c', GradientType=0);
- background-repeat: repeat-x;
-}
-.progress-bar-striped {
- background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);
- background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);
- background-image: linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);
-}
-.list-group {
- border-radius: 4px;
- -webkit-box-shadow: 0 1px 2px rgba(0, 0, 0, .075);
- box-shadow: 0 1px 2px rgba(0, 0, 0, .075);
-}
-.list-group-item.active,
-.list-group-item.active:hover,
-.list-group-item.active:focus {
- text-shadow: 0 -1px 0 #286090;
- background-image: -webkit-linear-gradient(top, #337ab7 0%, #2b669a 100%);
- background-image: -o-linear-gradient(top, #337ab7 0%, #2b669a 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#337ab7), to(#2b669a));
- background-image: linear-gradient(to bottom, #337ab7 0%, #2b669a 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff337ab7', endColorstr='#ff2b669a', GradientType=0);
- background-repeat: repeat-x;
- border-color: #2b669a;
-}
-.list-group-item.active .badge,
-.list-group-item.active:hover .badge,
-.list-group-item.active:focus .badge {
- text-shadow: none;
-}
-.panel {
- -webkit-box-shadow: 0 1px 2px rgba(0, 0, 0, .05);
- box-shadow: 0 1px 2px rgba(0, 0, 0, .05);
-}
-.panel-default > .panel-heading {
- background-image: -webkit-linear-gradient(top, #f5f5f5 0%, #e8e8e8 100%);
- background-image: -o-linear-gradient(top, #f5f5f5 0%, #e8e8e8 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#f5f5f5), to(#e8e8e8));
- background-image: linear-gradient(to bottom, #f5f5f5 0%, #e8e8e8 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#fff5f5f5', endColorstr='#ffe8e8e8', GradientType=0);
- background-repeat: repeat-x;
-}
-.panel-primary > .panel-heading {
- background-image: -webkit-linear-gradient(top, #337ab7 0%, #2e6da4 100%);
- background-image: -o-linear-gradient(top, #337ab7 0%, #2e6da4 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#337ab7), to(#2e6da4));
- background-image: linear-gradient(to bottom, #337ab7 0%, #2e6da4 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff337ab7', endColorstr='#ff2e6da4', GradientType=0);
- background-repeat: repeat-x;
-}
-.panel-success > .panel-heading {
- background-image: -webkit-linear-gradient(top, #dff0d8 0%, #d0e9c6 100%);
- background-image: -o-linear-gradient(top, #dff0d8 0%, #d0e9c6 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#dff0d8), to(#d0e9c6));
- background-image: linear-gradient(to bottom, #dff0d8 0%, #d0e9c6 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffdff0d8', endColorstr='#ffd0e9c6', GradientType=0);
- background-repeat: repeat-x;
-}
-.panel-info > .panel-heading {
- background-image: -webkit-linear-gradient(top, #d9edf7 0%, #c4e3f3 100%);
- background-image: -o-linear-gradient(top, #d9edf7 0%, #c4e3f3 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#d9edf7), to(#c4e3f3));
- background-image: linear-gradient(to bottom, #d9edf7 0%, #c4e3f3 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffd9edf7', endColorstr='#ffc4e3f3', GradientType=0);
- background-repeat: repeat-x;
-}
-.panel-warning > .panel-heading {
- background-image: -webkit-linear-gradient(top, #fcf8e3 0%, #faf2cc 100%);
- background-image: -o-linear-gradient(top, #fcf8e3 0%, #faf2cc 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#fcf8e3), to(#faf2cc));
- background-image: linear-gradient(to bottom, #fcf8e3 0%, #faf2cc 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#fffcf8e3', endColorstr='#fffaf2cc', GradientType=0);
- background-repeat: repeat-x;
-}
-.panel-danger > .panel-heading {
- background-image: -webkit-linear-gradient(top, #f2dede 0%, #ebcccc 100%);
- background-image: -o-linear-gradient(top, #f2dede 0%, #ebcccc 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#f2dede), to(#ebcccc));
- background-image: linear-gradient(to bottom, #f2dede 0%, #ebcccc 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#fff2dede', endColorstr='#ffebcccc', GradientType=0);
- background-repeat: repeat-x;
-}
-.well {
- background-image: -webkit-linear-gradient(top, #e8e8e8 0%, #f5f5f5 100%);
- background-image: -o-linear-gradient(top, #e8e8e8 0%, #f5f5f5 100%);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#e8e8e8), to(#f5f5f5));
- background-image: linear-gradient(to bottom, #e8e8e8 0%, #f5f5f5 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffe8e8e8', endColorstr='#fff5f5f5', GradientType=0);
- background-repeat: repeat-x;
- border-color: #dcdcdc;
- -webkit-box-shadow: inset 0 1px 3px rgba(0, 0, 0, .05), 0 1px 0 rgba(255, 255, 255, .1);
- box-shadow: inset 0 1px 3px rgba(0, 0, 0, .05), 0 1px 0 rgba(255, 255, 255, .1);
-}
-/*# sourceMappingURL=bootstrap-theme.css.map */
diff --git a/library/bootstrap/css/bootstrap-theme.css.map b/library/bootstrap/css/bootstrap-theme.css.map
deleted file mode 100644
index d876f60fb..000000000
--- a/library/bootstrap/css/bootstrap-theme.css.map
+++ /dev/null
@@ -1 +0,0 @@
-{"version":3,"sources":["bootstrap-theme.css","less/theme.less","less/mixins/vendor-prefixes.less","less/mixins/gradients.less","less/mixins/reset-filter.less"],"names":[],"mappings":"AAAA;;;;GAIG;ACeH;;;;;;EAME,yCAAA;EC2CA,4FAAA;EACQ,oFAAA;CFvDT;ACgBC;;;;;;;;;;;;ECsCA,yDAAA;EACQ,iDAAA;CFxCT;ACMC;;;;;;;;;;;;;;;;;;ECiCA,yBAAA;EACQ,iBAAA;CFnBT;AC/BD;;;;;;EAuBI,kBAAA;CDgBH;ACyBC;;EAEE,uBAAA;CDvBH;AC4BD;EErEI,sEAAA;EACA,iEAAA;EACA,2FAAA;EAAA,oEAAA;EAEA,uHAAA;ECnBF,oEAAA;EH4CA,4BAAA;EACA,sBAAA;EAuC2C,0BAAA;EAA2B,mBAAA;CDjBvE;ACpBC;;EAEE,0BAAA;EACA,6BAAA;CDsBH;ACnBC;;EAEE,0BAAA;EACA,sBAAA;CDqBH;ACfG;;;;;;;;;;;;;;;;;;EAME,0BAAA;EACA,uBAAA;CD6BL;ACbD;EEtEI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EAEA,uHAAA;ECnBF,oEAAA;EH4CA,4BAAA;EACA,sBAAA;CD8DD;AC5DC;;EAEE,0BAAA;EACA,6BAAA;CD8DH;AC3DC;;EAEE,0BAAA;EACA,sBAAA;CD6DH;ACvDG;;;;;;;;;;;;;;;;;;EAME,0BAAA;EACA,uBAAA;CDqEL;ACpDD;EEvEI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EAEA,uHAAA;ECnBF,oEAAA;EH4CA,4BAAA;EACA,sBAAA;CDsGD;ACpGC;;EAEE,0BAAA;EACA,6BAAA;CDsGH;ACnGC;;EAEE,0BAAA;EACA,sBAAA;CDqGH;AC/FG;;;;;;;;;;;;;;;;;;EAME,0BAAA;EACA,uBAAA;CD6GL;AC3FD;EExEI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EAEA,uHAAA;ECnBF,oEAAA;EH4CA,4BAAA;EACA,sBAAA;CD8ID;AC5IC;;EAEE,0BAAA;EACA,6BAAA;CD8IH;AC3IC;;EAEE,0BAAA;EACA,sBAAA;CD6IH;ACvIG;;;;;;;;;;;;;;;;;;EAME,0BAAA;EACA,uBAAA;CDqJL;AClID;EEzEI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EAEA,uHAAA;ECnBF,oEAAA;EH4CA,4BAAA;EACA,sBAAA;CDsLD;ACpLC;;EAEE,0BAAA;EACA,6BAAA;CDsLH;ACnLC;;EAEE,0BAAA;EACA,sBAAA;CDqLH;AC/KG;;;;;;;;;;;;;;;;;;EAME,0BAAA;EACA,uBAAA;CD6LL;ACzKD;EE1EI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EAEA,uHAAA;ECnBF,oEAAA;EH4CA,4BAAA;EACA,sBAAA;CD8ND;AC5NC;;EAEE,0BAAA;EACA,6BAAA;CD8NH;AC3NC;;EAEE,0BAAA;EACA,sBAAA;CD6NH;ACvNG;;;;;;;;;;;;;;;;;;EAME,0BAAA;EACA,uBAAA;CDqOL;AC1MD;;EClCE,mDAAA;EACQ,2CAAA;CFgPT;ACrMD;;EE3FI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EACA,4BAAA;EACA,uHAAA;EF0FF,0BAAA;CD2MD;ACzMD;;;EEhGI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EACA,4BAAA;EACA,uHAAA;EFgGF,0BAAA;CD+MD;ACtMD;EE7GI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EACA,4BAAA;EACA,uHAAA;ECnBF,oEAAA;EH+HA,mBAAA;ECjEA,4FAAA;EACQ,oFAAA;CF8QT;ACjND;;EE7GI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EACA,4BAAA;EACA,uHAAA;ED2CF,yDAAA;EACQ,iDAAA;CFwRT;AC9MD;;EAEE,+CAAA;CDgND;AC5MD;EEhII,sEAAA;EACA,iEAAA;EACA,2FAAA;EAAA,oEAAA;EACA,4BAAA;EACA,uHAAA;ECnBF,oEAAA;EHkJA,mBAAA;CDkND;ACrND;;EEhII,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EACA,4BAAA;EACA,uHAAA;ED2CF,wDAAA;EACQ,gDAAA;CF+ST;AC/ND;;EAYI,0CAAA;CDuNH;AClND;;;EAGE,iBAAA;CDoND;AC/LD;EAfI;;;IAGE,YAAA;IE7JF,yEAAA;IACA,oEAAA;IACA,8FAAA;IAAA,uEAAA;IACA,4BAAA;IACA,uHAAA;GH+WD;CACF;AC3MD;EACE,8CAAA;EC3HA,2FAAA;EACQ,mFAAA;CFyUT;ACnMD;EEtLI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EACA,4BAAA;EACA,uHAAA;EF8KF,sBAAA;CD+MD;AC1MD;EEvLI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EACA,4BAAA;EACA,uHAAA;EF8KF,sBAAA;CDuND;ACjND;EExLI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EACA,4BAAA;EACA,uHAAA;EF8KF,sBAAA;CD+ND;ACxND;EEzLI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EACA,4BAAA;EACA,uHAAA;EF8KF,sBAAA;CDuOD;ACxND;EEjMI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EACA,4BAAA;EACA,uHAAA;CH4ZH;ACrND;EE3MI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EACA,4BAAA;EACA,uHAAA;CHmaH;AC3ND;EE5MI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EACA,4BAAA;EACA,uHAAA;CH0aH;ACjOD;EE7MI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EACA,4BAAA;EACA,uHAAA;CHibH;ACvOD;EE9MI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EACA,4BAAA;EACA,uHAAA;CHwbH;AC7OD;EE/MI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EACA,4BAAA;EACA,uHAAA;CH+bH;AChPD;EElLI,8MAAA;EACA,yMAAA;EACA,sMAAA;CHqaH;AC5OD;EACE,mBAAA;EC9KA,mDAAA;EACQ,2CAAA;CF6ZT;AC7OD;;;EAGE,8BAAA;EEnOE,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EACA,4BAAA;EACA,uHAAA;EFiOF,sBAAA;CDmPD;ACxPD;;;EAQI,kBAAA;CDqPH;AC3OD;ECnME,kDAAA;EACQ,0CAAA;CFibT;ACrOD;EE5PI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EACA,4BAAA;EACA,uHAAA;CHoeH;AC3OD;EE7PI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EACA,4BAAA;EACA,uHAAA;CH2eH;ACjPD;EE9PI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EACA,4BAAA;EACA,uHAAA;CHkfH;ACvPD;EE/PI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EACA,4BAAA;EACA,uHAAA;CHyfH;AC7PD;EEhQI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EACA,4BAAA;EACA,uHAAA;CHggBH;ACnQD;EEjQI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EACA,4BAAA;EACA,uHAAA;CHugBH;ACnQD;EExQI,yEAAA;EACA,oEAAA;EACA,8FAAA;EAAA,uEAAA;EACA,4BAAA;EACA,uHAAA;EFsQF,sBAAA;EC3NA,0FAAA;EACQ,kFAAA;CFqeT","file":"bootstrap-theme.css","sourcesContent":["/*!\n * Bootstrap v3.3.7 (http://getbootstrap.com)\n * Copyright 2011-2016 Twitter, Inc.\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)\n */\n.btn-default,\n.btn-primary,\n.btn-success,\n.btn-info,\n.btn-warning,\n.btn-danger {\n text-shadow: 0 -1px 0 rgba(0, 0, 0, 0.2);\n -webkit-box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.15), 0 1px 1px rgba(0, 0, 0, 0.075);\n box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.15), 0 1px 1px rgba(0, 0, 0, 0.075);\n}\n.btn-default:active,\n.btn-primary:active,\n.btn-success:active,\n.btn-info:active,\n.btn-warning:active,\n.btn-danger:active,\n.btn-default.active,\n.btn-primary.active,\n.btn-success.active,\n.btn-info.active,\n.btn-warning.active,\n.btn-danger.active {\n -webkit-box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);\n box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);\n}\n.btn-default.disabled,\n.btn-primary.disabled,\n.btn-success.disabled,\n.btn-info.disabled,\n.btn-warning.disabled,\n.btn-danger.disabled,\n.btn-default[disabled],\n.btn-primary[disabled],\n.btn-success[disabled],\n.btn-info[disabled],\n.btn-warning[disabled],\n.btn-danger[disabled],\nfieldset[disabled] .btn-default,\nfieldset[disabled] .btn-primary,\nfieldset[disabled] .btn-success,\nfieldset[disabled] .btn-info,\nfieldset[disabled] .btn-warning,\nfieldset[disabled] .btn-danger {\n -webkit-box-shadow: none;\n box-shadow: none;\n}\n.btn-default .badge,\n.btn-primary .badge,\n.btn-success .badge,\n.btn-info .badge,\n.btn-warning .badge,\n.btn-danger .badge {\n text-shadow: none;\n}\n.btn:active,\n.btn.active {\n background-image: none;\n}\n.btn-default {\n background-image: -webkit-linear-gradient(top, #fff 0%, #e0e0e0 100%);\n background-image: -o-linear-gradient(top, #fff 0%, #e0e0e0 100%);\n background-image: linear-gradient(to bottom, #fff 0%, #e0e0e0 100%);\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffffffff', endColorstr='#ffe0e0e0', GradientType=0);\n filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);\n background-repeat: repeat-x;\n border-color: #dbdbdb;\n text-shadow: 0 1px 0 #fff;\n border-color: #ccc;\n}\n.btn-default:hover,\n.btn-default:focus {\n background-color: #e0e0e0;\n background-position: 0 -15px;\n}\n.btn-default:active,\n.btn-default.active {\n background-color: #e0e0e0;\n border-color: #dbdbdb;\n}\n.btn-default.disabled,\n.btn-default[disabled],\nfieldset[disabled] .btn-default,\n.btn-default.disabled:hover,\n.btn-default[disabled]:hover,\nfieldset[disabled] .btn-default:hover,\n.btn-default.disabled:focus,\n.btn-default[disabled]:focus,\nfieldset[disabled] .btn-default:focus,\n.btn-default.disabled.focus,\n.btn-default[disabled].focus,\nfieldset[disabled] .btn-default.focus,\n.btn-default.disabled:active,\n.btn-default[disabled]:active,\nfieldset[disabled] .btn-default:active,\n.btn-default.disabled.active,\n.btn-default[disabled].active,\nfieldset[disabled] .btn-default.active {\n background-color: #e0e0e0;\n background-image: none;\n}\n.btn-primary {\n background-image: -webkit-linear-gradient(top, #337ab7 0%, #265a88 100%);\n background-image: -o-linear-gradient(top, #337ab7 0%, #265a88 100%);\n background-image: linear-gradient(to bottom, #337ab7 0%, #265a88 100%);\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff337ab7', endColorstr='#ff265a88', GradientType=0);\n filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);\n background-repeat: repeat-x;\n border-color: #245580;\n}\n.btn-primary:hover,\n.btn-primary:focus {\n background-color: #265a88;\n background-position: 0 -15px;\n}\n.btn-primary:active,\n.btn-primary.active {\n background-color: #265a88;\n border-color: #245580;\n}\n.btn-primary.disabled,\n.btn-primary[disabled],\nfieldset[disabled] .btn-primary,\n.btn-primary.disabled:hover,\n.btn-primary[disabled]:hover,\nfieldset[disabled] .btn-primary:hover,\n.btn-primary.disabled:focus,\n.btn-primary[disabled]:focus,\nfieldset[disabled] .btn-primary:focus,\n.btn-primary.disabled.focus,\n.btn-primary[disabled].focus,\nfieldset[disabled] .btn-primary.focus,\n.btn-primary.disabled:active,\n.btn-primary[disabled]:active,\nfieldset[disabled] .btn-primary:active,\n.btn-primary.disabled.active,\n.btn-primary[disabled].active,\nfieldset[disabled] .btn-primary.active {\n background-color: #265a88;\n background-image: none;\n}\n.btn-success {\n background-image: -webkit-linear-gradient(top, #5cb85c 0%, #419641 100%);\n background-image: -o-linear-gradient(top, #5cb85c 0%, #419641 100%);\n background-image: linear-gradient(to bottom, #5cb85c 0%, #419641 100%);\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff5cb85c', endColorstr='#ff419641', GradientType=0);\n filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);\n background-repeat: repeat-x;\n border-color: #3e8f3e;\n}\n.btn-success:hover,\n.btn-success:focus {\n background-color: #419641;\n background-position: 0 -15px;\n}\n.btn-success:active,\n.btn-success.active {\n background-color: #419641;\n border-color: #3e8f3e;\n}\n.btn-success.disabled,\n.btn-success[disabled],\nfieldset[disabled] .btn-success,\n.btn-success.disabled:hover,\n.btn-success[disabled]:hover,\nfieldset[disabled] .btn-success:hover,\n.btn-success.disabled:focus,\n.btn-success[disabled]:focus,\nfieldset[disabled] .btn-success:focus,\n.btn-success.disabled.focus,\n.btn-success[disabled].focus,\nfieldset[disabled] .btn-success.focus,\n.btn-success.disabled:active,\n.btn-success[disabled]:active,\nfieldset[disabled] .btn-success:active,\n.btn-success.disabled.active,\n.btn-success[disabled].active,\nfieldset[disabled] .btn-success.active {\n background-color: #419641;\n background-image: none;\n}\n.btn-info {\n background-image: -webkit-linear-gradient(top, #5bc0de 0%, #2aabd2 100%);\n background-image: -o-linear-gradient(top, #5bc0de 0%, #2aabd2 100%);\n background-image: linear-gradient(to bottom, #5bc0de 0%, #2aabd2 100%);\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff5bc0de', endColorstr='#ff2aabd2', GradientType=0);\n filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);\n background-repeat: repeat-x;\n border-color: #28a4c9;\n}\n.btn-info:hover,\n.btn-info:focus {\n background-color: #2aabd2;\n background-position: 0 -15px;\n}\n.btn-info:active,\n.btn-info.active {\n background-color: #2aabd2;\n border-color: #28a4c9;\n}\n.btn-info.disabled,\n.btn-info[disabled],\nfieldset[disabled] .btn-info,\n.btn-info.disabled:hover,\n.btn-info[disabled]:hover,\nfieldset[disabled] .btn-info:hover,\n.btn-info.disabled:focus,\n.btn-info[disabled]:focus,\nfieldset[disabled] .btn-info:focus,\n.btn-info.disabled.focus,\n.btn-info[disabled].focus,\nfieldset[disabled] .btn-info.focus,\n.btn-info.disabled:active,\n.btn-info[disabled]:active,\nfieldset[disabled] .btn-info:active,\n.btn-info.disabled.active,\n.btn-info[disabled].active,\nfieldset[disabled] .btn-info.active {\n background-color: #2aabd2;\n background-image: none;\n}\n.btn-warning {\n background-image: -webkit-linear-gradient(top, #f0ad4e 0%, #eb9316 100%);\n background-image: -o-linear-gradient(top, #f0ad4e 0%, #eb9316 100%);\n background-image: linear-gradient(to bottom, #f0ad4e 0%, #eb9316 100%);\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#fff0ad4e', endColorstr='#ffeb9316', GradientType=0);\n filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);\n background-repeat: repeat-x;\n border-color: #e38d13;\n}\n.btn-warning:hover,\n.btn-warning:focus {\n background-color: #eb9316;\n background-position: 0 -15px;\n}\n.btn-warning:active,\n.btn-warning.active {\n background-color: #eb9316;\n border-color: #e38d13;\n}\n.btn-warning.disabled,\n.btn-warning[disabled],\nfieldset[disabled] .btn-warning,\n.btn-warning.disabled:hover,\n.btn-warning[disabled]:hover,\nfieldset[disabled] .btn-warning:hover,\n.btn-warning.disabled:focus,\n.btn-warning[disabled]:focus,\nfieldset[disabled] .btn-warning:focus,\n.btn-warning.disabled.focus,\n.btn-warning[disabled].focus,\nfieldset[disabled] .btn-warning.focus,\n.btn-warning.disabled:active,\n.btn-warning[disabled]:active,\nfieldset[disabled] .btn-warning:active,\n.btn-warning.disabled.active,\n.btn-warning[disabled].active,\nfieldset[disabled] .btn-warning.active {\n background-color: #eb9316;\n background-image: none;\n}\n.btn-danger {\n background-image: -webkit-linear-gradient(top, #d9534f 0%, #c12e2a 100%);\n background-image: -o-linear-gradient(top, #d9534f 0%, #c12e2a 100%);\n background-image: linear-gradient(to bottom, #d9534f 0%, #c12e2a 100%);\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffd9534f', endColorstr='#ffc12e2a', GradientType=0);\n filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);\n background-repeat: repeat-x;\n border-color: #b92c28;\n}\n.btn-danger:hover,\n.btn-danger:focus {\n background-color: #c12e2a;\n background-position: 0 -15px;\n}\n.btn-danger:active,\n.btn-danger.active {\n background-color: #c12e2a;\n border-color: #b92c28;\n}\n.btn-danger.disabled,\n.btn-danger[disabled],\nfieldset[disabled] .btn-danger,\n.btn-danger.disabled:hover,\n.btn-danger[disabled]:hover,\nfieldset[disabled] .btn-danger:hover,\n.btn-danger.disabled:focus,\n.btn-danger[disabled]:focus,\nfieldset[disabled] .btn-danger:focus,\n.btn-danger.disabled.focus,\n.btn-danger[disabled].focus,\nfieldset[disabled] .btn-danger.focus,\n.btn-danger.disabled:active,\n.btn-danger[disabled]:active,\nfieldset[disabled] .btn-danger:active,\n.btn-danger.disabled.active,\n.btn-danger[disabled].active,\nfieldset[disabled] .btn-danger.active {\n background-color: #c12e2a;\n background-image: none;\n}\n.thumbnail,\n.img-thumbnail {\n -webkit-box-shadow: 0 1px 2px rgba(0, 0, 0, 0.075);\n box-shadow: 0 1px 2px rgba(0, 0, 0, 0.075);\n}\n.dropdown-menu > li > a:hover,\n.dropdown-menu > li > a:focus {\n background-image: -webkit-linear-gradient(top, #f5f5f5 0%, #e8e8e8 100%);\n background-image: -o-linear-gradient(top, #f5f5f5 0%, #e8e8e8 100%);\n background-image: linear-gradient(to bottom, #f5f5f5 0%, #e8e8e8 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#fff5f5f5', endColorstr='#ffe8e8e8', GradientType=0);\n background-color: #e8e8e8;\n}\n.dropdown-menu > .active > a,\n.dropdown-menu > .active > a:hover,\n.dropdown-menu > .active > a:focus {\n background-image: -webkit-linear-gradient(top, #337ab7 0%, #2e6da4 100%);\n background-image: -o-linear-gradient(top, #337ab7 0%, #2e6da4 100%);\n background-image: linear-gradient(to bottom, #337ab7 0%, #2e6da4 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff337ab7', endColorstr='#ff2e6da4', GradientType=0);\n background-color: #2e6da4;\n}\n.navbar-default {\n background-image: -webkit-linear-gradient(top, #ffffff 0%, #f8f8f8 100%);\n background-image: -o-linear-gradient(top, #ffffff 0%, #f8f8f8 100%);\n background-image: linear-gradient(to bottom, #ffffff 0%, #f8f8f8 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffffffff', endColorstr='#fff8f8f8', GradientType=0);\n filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);\n border-radius: 4px;\n -webkit-box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.15), 0 1px 5px rgba(0, 0, 0, 0.075);\n box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.15), 0 1px 5px rgba(0, 0, 0, 0.075);\n}\n.navbar-default .navbar-nav > .open > a,\n.navbar-default .navbar-nav > .active > a {\n background-image: -webkit-linear-gradient(top, #dbdbdb 0%, #e2e2e2 100%);\n background-image: -o-linear-gradient(top, #dbdbdb 0%, #e2e2e2 100%);\n background-image: linear-gradient(to bottom, #dbdbdb 0%, #e2e2e2 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffdbdbdb', endColorstr='#ffe2e2e2', GradientType=0);\n -webkit-box-shadow: inset 0 3px 9px rgba(0, 0, 0, 0.075);\n box-shadow: inset 0 3px 9px rgba(0, 0, 0, 0.075);\n}\n.navbar-brand,\n.navbar-nav > li > a {\n text-shadow: 0 1px 0 rgba(255, 255, 255, 0.25);\n}\n.navbar-inverse {\n background-image: -webkit-linear-gradient(top, #3c3c3c 0%, #222 100%);\n background-image: -o-linear-gradient(top, #3c3c3c 0%, #222 100%);\n background-image: linear-gradient(to bottom, #3c3c3c 0%, #222 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff3c3c3c', endColorstr='#ff222222', GradientType=0);\n filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);\n border-radius: 4px;\n}\n.navbar-inverse .navbar-nav > .open > a,\n.navbar-inverse .navbar-nav > .active > a {\n background-image: -webkit-linear-gradient(top, #080808 0%, #0f0f0f 100%);\n background-image: -o-linear-gradient(top, #080808 0%, #0f0f0f 100%);\n background-image: linear-gradient(to bottom, #080808 0%, #0f0f0f 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff080808', endColorstr='#ff0f0f0f', GradientType=0);\n -webkit-box-shadow: inset 0 3px 9px rgba(0, 0, 0, 0.25);\n box-shadow: inset 0 3px 9px rgba(0, 0, 0, 0.25);\n}\n.navbar-inverse .navbar-brand,\n.navbar-inverse .navbar-nav > li > a {\n text-shadow: 0 -1px 0 rgba(0, 0, 0, 0.25);\n}\n.navbar-static-top,\n.navbar-fixed-top,\n.navbar-fixed-bottom {\n border-radius: 0;\n}\n@media (max-width: 767px) {\n .navbar .navbar-nav .open .dropdown-menu > .active > a,\n .navbar .navbar-nav .open .dropdown-menu > .active > a:hover,\n .navbar .navbar-nav .open .dropdown-menu > .active > a:focus {\n color: #fff;\n background-image: -webkit-linear-gradient(top, #337ab7 0%, #2e6da4 100%);\n background-image: -o-linear-gradient(top, #337ab7 0%, #2e6da4 100%);\n background-image: linear-gradient(to bottom, #337ab7 0%, #2e6da4 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff337ab7', endColorstr='#ff2e6da4', GradientType=0);\n }\n}\n.alert {\n text-shadow: 0 1px 0 rgba(255, 255, 255, 0.2);\n -webkit-box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.25), 0 1px 2px rgba(0, 0, 0, 0.05);\n box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.25), 0 1px 2px rgba(0, 0, 0, 0.05);\n}\n.alert-success {\n background-image: -webkit-linear-gradient(top, #dff0d8 0%, #c8e5bc 100%);\n background-image: -o-linear-gradient(top, #dff0d8 0%, #c8e5bc 100%);\n background-image: linear-gradient(to bottom, #dff0d8 0%, #c8e5bc 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffdff0d8', endColorstr='#ffc8e5bc', GradientType=0);\n border-color: #b2dba1;\n}\n.alert-info {\n background-image: -webkit-linear-gradient(top, #d9edf7 0%, #b9def0 100%);\n background-image: -o-linear-gradient(top, #d9edf7 0%, #b9def0 100%);\n background-image: linear-gradient(to bottom, #d9edf7 0%, #b9def0 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffd9edf7', endColorstr='#ffb9def0', GradientType=0);\n border-color: #9acfea;\n}\n.alert-warning {\n background-image: -webkit-linear-gradient(top, #fcf8e3 0%, #f8efc0 100%);\n background-image: -o-linear-gradient(top, #fcf8e3 0%, #f8efc0 100%);\n background-image: linear-gradient(to bottom, #fcf8e3 0%, #f8efc0 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#fffcf8e3', endColorstr='#fff8efc0', GradientType=0);\n border-color: #f5e79e;\n}\n.alert-danger {\n background-image: -webkit-linear-gradient(top, #f2dede 0%, #e7c3c3 100%);\n background-image: -o-linear-gradient(top, #f2dede 0%, #e7c3c3 100%);\n background-image: linear-gradient(to bottom, #f2dede 0%, #e7c3c3 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#fff2dede', endColorstr='#ffe7c3c3', GradientType=0);\n border-color: #dca7a7;\n}\n.progress {\n background-image: -webkit-linear-gradient(top, #ebebeb 0%, #f5f5f5 100%);\n background-image: -o-linear-gradient(top, #ebebeb 0%, #f5f5f5 100%);\n background-image: linear-gradient(to bottom, #ebebeb 0%, #f5f5f5 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffebebeb', endColorstr='#fff5f5f5', GradientType=0);\n}\n.progress-bar {\n background-image: -webkit-linear-gradient(top, #337ab7 0%, #286090 100%);\n background-image: -o-linear-gradient(top, #337ab7 0%, #286090 100%);\n background-image: linear-gradient(to bottom, #337ab7 0%, #286090 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff337ab7', endColorstr='#ff286090', GradientType=0);\n}\n.progress-bar-success {\n background-image: -webkit-linear-gradient(top, #5cb85c 0%, #449d44 100%);\n background-image: -o-linear-gradient(top, #5cb85c 0%, #449d44 100%);\n background-image: linear-gradient(to bottom, #5cb85c 0%, #449d44 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff5cb85c', endColorstr='#ff449d44', GradientType=0);\n}\n.progress-bar-info {\n background-image: -webkit-linear-gradient(top, #5bc0de 0%, #31b0d5 100%);\n background-image: -o-linear-gradient(top, #5bc0de 0%, #31b0d5 100%);\n background-image: linear-gradient(to bottom, #5bc0de 0%, #31b0d5 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff5bc0de', endColorstr='#ff31b0d5', GradientType=0);\n}\n.progress-bar-warning {\n background-image: -webkit-linear-gradient(top, #f0ad4e 0%, #ec971f 100%);\n background-image: -o-linear-gradient(top, #f0ad4e 0%, #ec971f 100%);\n background-image: linear-gradient(to bottom, #f0ad4e 0%, #ec971f 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#fff0ad4e', endColorstr='#ffec971f', GradientType=0);\n}\n.progress-bar-danger {\n background-image: -webkit-linear-gradient(top, #d9534f 0%, #c9302c 100%);\n background-image: -o-linear-gradient(top, #d9534f 0%, #c9302c 100%);\n background-image: linear-gradient(to bottom, #d9534f 0%, #c9302c 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffd9534f', endColorstr='#ffc9302c', GradientType=0);\n}\n.progress-bar-striped {\n background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n}\n.list-group {\n border-radius: 4px;\n -webkit-box-shadow: 0 1px 2px rgba(0, 0, 0, 0.075);\n box-shadow: 0 1px 2px rgba(0, 0, 0, 0.075);\n}\n.list-group-item.active,\n.list-group-item.active:hover,\n.list-group-item.active:focus {\n text-shadow: 0 -1px 0 #286090;\n background-image: -webkit-linear-gradient(top, #337ab7 0%, #2b669a 100%);\n background-image: -o-linear-gradient(top, #337ab7 0%, #2b669a 100%);\n background-image: linear-gradient(to bottom, #337ab7 0%, #2b669a 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff337ab7', endColorstr='#ff2b669a', GradientType=0);\n border-color: #2b669a;\n}\n.list-group-item.active .badge,\n.list-group-item.active:hover .badge,\n.list-group-item.active:focus .badge {\n text-shadow: none;\n}\n.panel {\n -webkit-box-shadow: 0 1px 2px rgba(0, 0, 0, 0.05);\n box-shadow: 0 1px 2px rgba(0, 0, 0, 0.05);\n}\n.panel-default > .panel-heading {\n background-image: -webkit-linear-gradient(top, #f5f5f5 0%, #e8e8e8 100%);\n background-image: -o-linear-gradient(top, #f5f5f5 0%, #e8e8e8 100%);\n background-image: linear-gradient(to bottom, #f5f5f5 0%, #e8e8e8 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#fff5f5f5', endColorstr='#ffe8e8e8', GradientType=0);\n}\n.panel-primary > .panel-heading {\n background-image: -webkit-linear-gradient(top, #337ab7 0%, #2e6da4 100%);\n background-image: -o-linear-gradient(top, #337ab7 0%, #2e6da4 100%);\n background-image: linear-gradient(to bottom, #337ab7 0%, #2e6da4 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff337ab7', endColorstr='#ff2e6da4', GradientType=0);\n}\n.panel-success > .panel-heading {\n background-image: -webkit-linear-gradient(top, #dff0d8 0%, #d0e9c6 100%);\n background-image: -o-linear-gradient(top, #dff0d8 0%, #d0e9c6 100%);\n background-image: linear-gradient(to bottom, #dff0d8 0%, #d0e9c6 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffdff0d8', endColorstr='#ffd0e9c6', GradientType=0);\n}\n.panel-info > .panel-heading {\n background-image: -webkit-linear-gradient(top, #d9edf7 0%, #c4e3f3 100%);\n background-image: -o-linear-gradient(top, #d9edf7 0%, #c4e3f3 100%);\n background-image: linear-gradient(to bottom, #d9edf7 0%, #c4e3f3 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffd9edf7', endColorstr='#ffc4e3f3', GradientType=0);\n}\n.panel-warning > .panel-heading {\n background-image: -webkit-linear-gradient(top, #fcf8e3 0%, #faf2cc 100%);\n background-image: -o-linear-gradient(top, #fcf8e3 0%, #faf2cc 100%);\n background-image: linear-gradient(to bottom, #fcf8e3 0%, #faf2cc 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#fffcf8e3', endColorstr='#fffaf2cc', GradientType=0);\n}\n.panel-danger > .panel-heading {\n background-image: -webkit-linear-gradient(top, #f2dede 0%, #ebcccc 100%);\n background-image: -o-linear-gradient(top, #f2dede 0%, #ebcccc 100%);\n background-image: linear-gradient(to bottom, #f2dede 0%, #ebcccc 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#fff2dede', endColorstr='#ffebcccc', GradientType=0);\n}\n.well {\n background-image: -webkit-linear-gradient(top, #e8e8e8 0%, #f5f5f5 100%);\n background-image: -o-linear-gradient(top, #e8e8e8 0%, #f5f5f5 100%);\n background-image: linear-gradient(to bottom, #e8e8e8 0%, #f5f5f5 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffe8e8e8', endColorstr='#fff5f5f5', GradientType=0);\n border-color: #dcdcdc;\n -webkit-box-shadow: inset 0 1px 3px rgba(0, 0, 0, 0.05), 0 1px 0 rgba(255, 255, 255, 0.1);\n box-shadow: inset 0 1px 3px rgba(0, 0, 0, 0.05), 0 1px 0 rgba(255, 255, 255, 0.1);\n}\n/*# sourceMappingURL=bootstrap-theme.css.map */","/*!\n * Bootstrap v3.3.7 (http://getbootstrap.com)\n * Copyright 2011-2016 Twitter, Inc.\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)\n */\n\n//\n// Load core variables and mixins\n// --------------------------------------------------\n\n@import \"variables.less\";\n@import \"mixins.less\";\n\n\n//\n// Buttons\n// --------------------------------------------------\n\n// Common styles\n.btn-default,\n.btn-primary,\n.btn-success,\n.btn-info,\n.btn-warning,\n.btn-danger {\n text-shadow: 0 -1px 0 rgba(0,0,0,.2);\n @shadow: inset 0 1px 0 rgba(255,255,255,.15), 0 1px 1px rgba(0,0,0,.075);\n .box-shadow(@shadow);\n\n // Reset the shadow\n &:active,\n &.active {\n .box-shadow(inset 0 3px 5px rgba(0,0,0,.125));\n }\n\n &.disabled,\n &[disabled],\n fieldset[disabled] & {\n .box-shadow(none);\n }\n\n .badge {\n text-shadow: none;\n }\n}\n\n// Mixin for generating new styles\n.btn-styles(@btn-color: #555) {\n #gradient > .vertical(@start-color: @btn-color; @end-color: darken(@btn-color, 12%));\n .reset-filter(); // Disable gradients for IE9 because filter bleeds through rounded corners; see https://github.com/twbs/bootstrap/issues/10620\n background-repeat: repeat-x;\n border-color: darken(@btn-color, 14%);\n\n &:hover,\n &:focus {\n background-color: darken(@btn-color, 12%);\n background-position: 0 -15px;\n }\n\n &:active,\n &.active {\n background-color: darken(@btn-color, 12%);\n border-color: darken(@btn-color, 14%);\n }\n\n &.disabled,\n &[disabled],\n fieldset[disabled] & {\n &,\n &:hover,\n &:focus,\n &.focus,\n &:active,\n &.active {\n background-color: darken(@btn-color, 12%);\n background-image: none;\n }\n }\n}\n\n// Common styles\n.btn {\n // Remove the gradient for the pressed/active state\n &:active,\n &.active {\n background-image: none;\n }\n}\n\n// Apply the mixin to the buttons\n.btn-default { .btn-styles(@btn-default-bg); text-shadow: 0 1px 0 #fff; border-color: #ccc; }\n.btn-primary { .btn-styles(@btn-primary-bg); }\n.btn-success { .btn-styles(@btn-success-bg); }\n.btn-info { .btn-styles(@btn-info-bg); }\n.btn-warning { .btn-styles(@btn-warning-bg); }\n.btn-danger { .btn-styles(@btn-danger-bg); }\n\n\n//\n// Images\n// --------------------------------------------------\n\n.thumbnail,\n.img-thumbnail {\n .box-shadow(0 1px 2px rgba(0,0,0,.075));\n}\n\n\n//\n// Dropdowns\n// --------------------------------------------------\n\n.dropdown-menu > li > a:hover,\n.dropdown-menu > li > a:focus {\n #gradient > .vertical(@start-color: @dropdown-link-hover-bg; @end-color: darken(@dropdown-link-hover-bg, 5%));\n background-color: darken(@dropdown-link-hover-bg, 5%);\n}\n.dropdown-menu > .active > a,\n.dropdown-menu > .active > a:hover,\n.dropdown-menu > .active > a:focus {\n #gradient > .vertical(@start-color: @dropdown-link-active-bg; @end-color: darken(@dropdown-link-active-bg, 5%));\n background-color: darken(@dropdown-link-active-bg, 5%);\n}\n\n\n//\n// Navbar\n// --------------------------------------------------\n\n// Default navbar\n.navbar-default {\n #gradient > .vertical(@start-color: lighten(@navbar-default-bg, 10%); @end-color: @navbar-default-bg);\n .reset-filter(); // Remove gradient in IE<10 to fix bug where dropdowns don't get triggered\n border-radius: @navbar-border-radius;\n @shadow: inset 0 1px 0 rgba(255,255,255,.15), 0 1px 5px rgba(0,0,0,.075);\n .box-shadow(@shadow);\n\n .navbar-nav > .open > a,\n .navbar-nav > .active > a {\n #gradient > .vertical(@start-color: darken(@navbar-default-link-active-bg, 5%); @end-color: darken(@navbar-default-link-active-bg, 2%));\n .box-shadow(inset 0 3px 9px rgba(0,0,0,.075));\n }\n}\n.navbar-brand,\n.navbar-nav > li > a {\n text-shadow: 0 1px 0 rgba(255,255,255,.25);\n}\n\n// Inverted navbar\n.navbar-inverse {\n #gradient > .vertical(@start-color: lighten(@navbar-inverse-bg, 10%); @end-color: @navbar-inverse-bg);\n .reset-filter(); // Remove gradient in IE<10 to fix bug where dropdowns don't get triggered; see https://github.com/twbs/bootstrap/issues/10257\n border-radius: @navbar-border-radius;\n .navbar-nav > .open > a,\n .navbar-nav > .active > a {\n #gradient > .vertical(@start-color: @navbar-inverse-link-active-bg; @end-color: lighten(@navbar-inverse-link-active-bg, 2.5%));\n .box-shadow(inset 0 3px 9px rgba(0,0,0,.25));\n }\n\n .navbar-brand,\n .navbar-nav > li > a {\n text-shadow: 0 -1px 0 rgba(0,0,0,.25);\n }\n}\n\n// Undo rounded corners in static and fixed navbars\n.navbar-static-top,\n.navbar-fixed-top,\n.navbar-fixed-bottom {\n border-radius: 0;\n}\n\n// Fix active state of dropdown items in collapsed mode\n@media (max-width: @grid-float-breakpoint-max) {\n .navbar .navbar-nav .open .dropdown-menu > .active > a {\n &,\n &:hover,\n &:focus {\n color: #fff;\n #gradient > .vertical(@start-color: @dropdown-link-active-bg; @end-color: darken(@dropdown-link-active-bg, 5%));\n }\n }\n}\n\n\n//\n// Alerts\n// --------------------------------------------------\n\n// Common styles\n.alert {\n text-shadow: 0 1px 0 rgba(255,255,255,.2);\n @shadow: inset 0 1px 0 rgba(255,255,255,.25), 0 1px 2px rgba(0,0,0,.05);\n .box-shadow(@shadow);\n}\n\n// Mixin for generating new styles\n.alert-styles(@color) {\n #gradient > .vertical(@start-color: @color; @end-color: darken(@color, 7.5%));\n border-color: darken(@color, 15%);\n}\n\n// Apply the mixin to the alerts\n.alert-success { .alert-styles(@alert-success-bg); }\n.alert-info { .alert-styles(@alert-info-bg); }\n.alert-warning { .alert-styles(@alert-warning-bg); }\n.alert-danger { .alert-styles(@alert-danger-bg); }\n\n\n//\n// Progress bars\n// --------------------------------------------------\n\n// Give the progress background some depth\n.progress {\n #gradient > .vertical(@start-color: darken(@progress-bg, 4%); @end-color: @progress-bg)\n}\n\n// Mixin for generating new styles\n.progress-bar-styles(@color) {\n #gradient > .vertical(@start-color: @color; @end-color: darken(@color, 10%));\n}\n\n// Apply the mixin to the progress bars\n.progress-bar { .progress-bar-styles(@progress-bar-bg); }\n.progress-bar-success { .progress-bar-styles(@progress-bar-success-bg); }\n.progress-bar-info { .progress-bar-styles(@progress-bar-info-bg); }\n.progress-bar-warning { .progress-bar-styles(@progress-bar-warning-bg); }\n.progress-bar-danger { .progress-bar-styles(@progress-bar-danger-bg); }\n\n// Reset the striped class because our mixins don't do multiple gradients and\n// the above custom styles override the new `.progress-bar-striped` in v3.2.0.\n.progress-bar-striped {\n #gradient > .striped();\n}\n\n\n//\n// List groups\n// --------------------------------------------------\n\n.list-group {\n border-radius: @border-radius-base;\n .box-shadow(0 1px 2px rgba(0,0,0,.075));\n}\n.list-group-item.active,\n.list-group-item.active:hover,\n.list-group-item.active:focus {\n text-shadow: 0 -1px 0 darken(@list-group-active-bg, 10%);\n #gradient > .vertical(@start-color: @list-group-active-bg; @end-color: darken(@list-group-active-bg, 7.5%));\n border-color: darken(@list-group-active-border, 7.5%);\n\n .badge {\n text-shadow: none;\n }\n}\n\n\n//\n// Panels\n// --------------------------------------------------\n\n// Common styles\n.panel {\n .box-shadow(0 1px 2px rgba(0,0,0,.05));\n}\n\n// Mixin for generating new styles\n.panel-heading-styles(@color) {\n #gradient > .vertical(@start-color: @color; @end-color: darken(@color, 5%));\n}\n\n// Apply the mixin to the panel headings only\n.panel-default > .panel-heading { .panel-heading-styles(@panel-default-heading-bg); }\n.panel-primary > .panel-heading { .panel-heading-styles(@panel-primary-heading-bg); }\n.panel-success > .panel-heading { .panel-heading-styles(@panel-success-heading-bg); }\n.panel-info > .panel-heading { .panel-heading-styles(@panel-info-heading-bg); }\n.panel-warning > .panel-heading { .panel-heading-styles(@panel-warning-heading-bg); }\n.panel-danger > .panel-heading { .panel-heading-styles(@panel-danger-heading-bg); }\n\n\n//\n// Wells\n// --------------------------------------------------\n\n.well {\n #gradient > .vertical(@start-color: darken(@well-bg, 5%); @end-color: @well-bg);\n border-color: darken(@well-bg, 10%);\n @shadow: inset 0 1px 3px rgba(0,0,0,.05), 0 1px 0 rgba(255,255,255,.1);\n .box-shadow(@shadow);\n}\n","// Vendor Prefixes\n//\n// All vendor mixins are deprecated as of v3.2.0 due to the introduction of\n// Autoprefixer in our Gruntfile. They have been removed in v4.\n\n// - Animations\n// - Backface visibility\n// - Box shadow\n// - Box sizing\n// - Content columns\n// - Hyphens\n// - Placeholder text\n// - Transformations\n// - Transitions\n// - User Select\n\n\n// Animations\n.animation(@animation) {\n -webkit-animation: @animation;\n -o-animation: @animation;\n animation: @animation;\n}\n.animation-name(@name) {\n -webkit-animation-name: @name;\n animation-name: @name;\n}\n.animation-duration(@duration) {\n -webkit-animation-duration: @duration;\n animation-duration: @duration;\n}\n.animation-timing-function(@timing-function) {\n -webkit-animation-timing-function: @timing-function;\n animation-timing-function: @timing-function;\n}\n.animation-delay(@delay) {\n -webkit-animation-delay: @delay;\n animation-delay: @delay;\n}\n.animation-iteration-count(@iteration-count) {\n -webkit-animation-iteration-count: @iteration-count;\n animation-iteration-count: @iteration-count;\n}\n.animation-direction(@direction) {\n -webkit-animation-direction: @direction;\n animation-direction: @direction;\n}\n.animation-fill-mode(@fill-mode) {\n -webkit-animation-fill-mode: @fill-mode;\n animation-fill-mode: @fill-mode;\n}\n\n// Backface visibility\n// Prevent browsers from flickering when using CSS 3D transforms.\n// Default value is `visible`, but can be changed to `hidden`\n\n.backface-visibility(@visibility) {\n -webkit-backface-visibility: @visibility;\n -moz-backface-visibility: @visibility;\n backface-visibility: @visibility;\n}\n\n// Drop shadows\n//\n// Note: Deprecated `.box-shadow()` as of v3.1.0 since all of Bootstrap's\n// supported browsers that have box shadow capabilities now support it.\n\n.box-shadow(@shadow) {\n -webkit-box-shadow: @shadow; // iOS <4.3 & Android <4.1\n box-shadow: @shadow;\n}\n\n// Box sizing\n.box-sizing(@boxmodel) {\n -webkit-box-sizing: @boxmodel;\n -moz-box-sizing: @boxmodel;\n box-sizing: @boxmodel;\n}\n\n// CSS3 Content Columns\n.content-columns(@column-count; @column-gap: @grid-gutter-width) {\n -webkit-column-count: @column-count;\n -moz-column-count: @column-count;\n column-count: @column-count;\n -webkit-column-gap: @column-gap;\n -moz-column-gap: @column-gap;\n column-gap: @column-gap;\n}\n\n// Optional hyphenation\n.hyphens(@mode: auto) {\n word-wrap: break-word;\n -webkit-hyphens: @mode;\n -moz-hyphens: @mode;\n -ms-hyphens: @mode; // IE10+\n -o-hyphens: @mode;\n hyphens: @mode;\n}\n\n// Placeholder text\n.placeholder(@color: @input-color-placeholder) {\n // Firefox\n &::-moz-placeholder {\n color: @color;\n opacity: 1; // Override Firefox's unusual default opacity; see https://github.com/twbs/bootstrap/pull/11526\n }\n &:-ms-input-placeholder { color: @color; } // Internet Explorer 10+\n &::-webkit-input-placeholder { color: @color; } // Safari and Chrome\n}\n\n// Transformations\n.scale(@ratio) {\n -webkit-transform: scale(@ratio);\n -ms-transform: scale(@ratio); // IE9 only\n -o-transform: scale(@ratio);\n transform: scale(@ratio);\n}\n.scale(@ratioX; @ratioY) {\n -webkit-transform: scale(@ratioX, @ratioY);\n -ms-transform: scale(@ratioX, @ratioY); // IE9 only\n -o-transform: scale(@ratioX, @ratioY);\n transform: scale(@ratioX, @ratioY);\n}\n.scaleX(@ratio) {\n -webkit-transform: scaleX(@ratio);\n -ms-transform: scaleX(@ratio); // IE9 only\n -o-transform: scaleX(@ratio);\n transform: scaleX(@ratio);\n}\n.scaleY(@ratio) {\n -webkit-transform: scaleY(@ratio);\n -ms-transform: scaleY(@ratio); // IE9 only\n -o-transform: scaleY(@ratio);\n transform: scaleY(@ratio);\n}\n.skew(@x; @y) {\n -webkit-transform: skewX(@x) skewY(@y);\n -ms-transform: skewX(@x) skewY(@y); // See https://github.com/twbs/bootstrap/issues/4885; IE9+\n -o-transform: skewX(@x) skewY(@y);\n transform: skewX(@x) skewY(@y);\n}\n.translate(@x; @y) {\n -webkit-transform: translate(@x, @y);\n -ms-transform: translate(@x, @y); // IE9 only\n -o-transform: translate(@x, @y);\n transform: translate(@x, @y);\n}\n.translate3d(@x; @y; @z) {\n -webkit-transform: translate3d(@x, @y, @z);\n transform: translate3d(@x, @y, @z);\n}\n.rotate(@degrees) {\n -webkit-transform: rotate(@degrees);\n -ms-transform: rotate(@degrees); // IE9 only\n -o-transform: rotate(@degrees);\n transform: rotate(@degrees);\n}\n.rotateX(@degrees) {\n -webkit-transform: rotateX(@degrees);\n -ms-transform: rotateX(@degrees); // IE9 only\n -o-transform: rotateX(@degrees);\n transform: rotateX(@degrees);\n}\n.rotateY(@degrees) {\n -webkit-transform: rotateY(@degrees);\n -ms-transform: rotateY(@degrees); // IE9 only\n -o-transform: rotateY(@degrees);\n transform: rotateY(@degrees);\n}\n.perspective(@perspective) {\n -webkit-perspective: @perspective;\n -moz-perspective: @perspective;\n perspective: @perspective;\n}\n.perspective-origin(@perspective) {\n -webkit-perspective-origin: @perspective;\n -moz-perspective-origin: @perspective;\n perspective-origin: @perspective;\n}\n.transform-origin(@origin) {\n -webkit-transform-origin: @origin;\n -moz-transform-origin: @origin;\n -ms-transform-origin: @origin; // IE9 only\n transform-origin: @origin;\n}\n\n\n// Transitions\n\n.transition(@transition) {\n -webkit-transition: @transition;\n -o-transition: @transition;\n transition: @transition;\n}\n.transition-property(@transition-property) {\n -webkit-transition-property: @transition-property;\n transition-property: @transition-property;\n}\n.transition-delay(@transition-delay) {\n -webkit-transition-delay: @transition-delay;\n transition-delay: @transition-delay;\n}\n.transition-duration(@transition-duration) {\n -webkit-transition-duration: @transition-duration;\n transition-duration: @transition-duration;\n}\n.transition-timing-function(@timing-function) {\n -webkit-transition-timing-function: @timing-function;\n transition-timing-function: @timing-function;\n}\n.transition-transform(@transition) {\n -webkit-transition: -webkit-transform @transition;\n -moz-transition: -moz-transform @transition;\n -o-transition: -o-transform @transition;\n transition: transform @transition;\n}\n\n\n// User select\n// For selecting text on the page\n\n.user-select(@select) {\n -webkit-user-select: @select;\n -moz-user-select: @select;\n -ms-user-select: @select; // IE10+\n user-select: @select;\n}\n","// Gradients\n\n#gradient {\n\n // Horizontal gradient, from left to right\n //\n // Creates two color stops, start and end, by specifying a color and position for each color stop.\n // Color stops are not available in IE9 and below.\n .horizontal(@start-color: #555; @end-color: #333; @start-percent: 0%; @end-percent: 100%) {\n background-image: -webkit-linear-gradient(left, @start-color @start-percent, @end-color @end-percent); // Safari 5.1-6, Chrome 10+\n background-image: -o-linear-gradient(left, @start-color @start-percent, @end-color @end-percent); // Opera 12\n background-image: linear-gradient(to right, @start-color @start-percent, @end-color @end-percent); // Standard, IE10, Firefox 16+, Opera 12.10+, Safari 7+, Chrome 26+\n background-repeat: repeat-x;\n filter: e(%(\"progid:DXImageTransform.Microsoft.gradient(startColorstr='%d', endColorstr='%d', GradientType=1)\",argb(@start-color),argb(@end-color))); // IE9 and down\n }\n\n // Vertical gradient, from top to bottom\n //\n // Creates two color stops, start and end, by specifying a color and position for each color stop.\n // Color stops are not available in IE9 and below.\n .vertical(@start-color: #555; @end-color: #333; @start-percent: 0%; @end-percent: 100%) {\n background-image: -webkit-linear-gradient(top, @start-color @start-percent, @end-color @end-percent); // Safari 5.1-6, Chrome 10+\n background-image: -o-linear-gradient(top, @start-color @start-percent, @end-color @end-percent); // Opera 12\n background-image: linear-gradient(to bottom, @start-color @start-percent, @end-color @end-percent); // Standard, IE10, Firefox 16+, Opera 12.10+, Safari 7+, Chrome 26+\n background-repeat: repeat-x;\n filter: e(%(\"progid:DXImageTransform.Microsoft.gradient(startColorstr='%d', endColorstr='%d', GradientType=0)\",argb(@start-color),argb(@end-color))); // IE9 and down\n }\n\n .directional(@start-color: #555; @end-color: #333; @deg: 45deg) {\n background-repeat: repeat-x;\n background-image: -webkit-linear-gradient(@deg, @start-color, @end-color); // Safari 5.1-6, Chrome 10+\n background-image: -o-linear-gradient(@deg, @start-color, @end-color); // Opera 12\n background-image: linear-gradient(@deg, @start-color, @end-color); // Standard, IE10, Firefox 16+, Opera 12.10+, Safari 7+, Chrome 26+\n }\n .horizontal-three-colors(@start-color: #00b3ee; @mid-color: #7a43b6; @color-stop: 50%; @end-color: #c3325f) {\n background-image: -webkit-linear-gradient(left, @start-color, @mid-color @color-stop, @end-color);\n background-image: -o-linear-gradient(left, @start-color, @mid-color @color-stop, @end-color);\n background-image: linear-gradient(to right, @start-color, @mid-color @color-stop, @end-color);\n background-repeat: no-repeat;\n filter: e(%(\"progid:DXImageTransform.Microsoft.gradient(startColorstr='%d', endColorstr='%d', GradientType=1)\",argb(@start-color),argb(@end-color))); // IE9 and down, gets no color-stop at all for proper fallback\n }\n .vertical-three-colors(@start-color: #00b3ee; @mid-color: #7a43b6; @color-stop: 50%; @end-color: #c3325f) {\n background-image: -webkit-linear-gradient(@start-color, @mid-color @color-stop, @end-color);\n background-image: -o-linear-gradient(@start-color, @mid-color @color-stop, @end-color);\n background-image: linear-gradient(@start-color, @mid-color @color-stop, @end-color);\n background-repeat: no-repeat;\n filter: e(%(\"progid:DXImageTransform.Microsoft.gradient(startColorstr='%d', endColorstr='%d', GradientType=0)\",argb(@start-color),argb(@end-color))); // IE9 and down, gets no color-stop at all for proper fallback\n }\n .radial(@inner-color: #555; @outer-color: #333) {\n background-image: -webkit-radial-gradient(circle, @inner-color, @outer-color);\n background-image: radial-gradient(circle, @inner-color, @outer-color);\n background-repeat: no-repeat;\n }\n .striped(@color: rgba(255,255,255,.15); @angle: 45deg) {\n background-image: -webkit-linear-gradient(@angle, @color 25%, transparent 25%, transparent 50%, @color 50%, @color 75%, transparent 75%, transparent);\n background-image: -o-linear-gradient(@angle, @color 25%, transparent 25%, transparent 50%, @color 50%, @color 75%, transparent 75%, transparent);\n background-image: linear-gradient(@angle, @color 25%, transparent 25%, transparent 50%, @color 50%, @color 75%, transparent 75%, transparent);\n }\n}\n","// Reset filters for IE\n//\n// When you need to remove a gradient background, do not forget to use this to reset\n// the IE filter for IE9 and below.\n\n.reset-filter() {\n filter: e(%(\"progid:DXImageTransform.Microsoft.gradient(enabled = false)\"));\n}\n"]} \ No newline at end of file
diff --git a/library/bootstrap/css/bootstrap-theme.min.css b/library/bootstrap/css/bootstrap-theme.min.css
deleted file mode 100644
index 5e3940195..000000000
--- a/library/bootstrap/css/bootstrap-theme.min.css
+++ /dev/null
@@ -1,6 +0,0 @@
-/*!
- * Bootstrap v3.3.7 (http://getbootstrap.com)
- * Copyright 2011-2016 Twitter, Inc.
- * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
- */.btn-danger,.btn-default,.btn-info,.btn-primary,.btn-success,.btn-warning{text-shadow:0 -1px 0 rgba(0,0,0,.2);-webkit-box-shadow:inset 0 1px 0 rgba(255,255,255,.15),0 1px 1px rgba(0,0,0,.075);box-shadow:inset 0 1px 0 rgba(255,255,255,.15),0 1px 1px rgba(0,0,0,.075)}.btn-danger.active,.btn-danger:active,.btn-default.active,.btn-default:active,.btn-info.active,.btn-info:active,.btn-primary.active,.btn-primary:active,.btn-success.active,.btn-success:active,.btn-warning.active,.btn-warning:active{-webkit-box-shadow:inset 0 3px 5px rgba(0,0,0,.125);box-shadow:inset 0 3px 5px rgba(0,0,0,.125)}.btn-danger.disabled,.btn-danger[disabled],.btn-default.disabled,.btn-default[disabled],.btn-info.disabled,.btn-info[disabled],.btn-primary.disabled,.btn-primary[disabled],.btn-success.disabled,.btn-success[disabled],.btn-warning.disabled,.btn-warning[disabled],fieldset[disabled] .btn-danger,fieldset[disabled] .btn-default,fieldset[disabled] .btn-info,fieldset[disabled] .btn-primary,fieldset[disabled] .btn-success,fieldset[disabled] .btn-warning{-webkit-box-shadow:none;box-shadow:none}.btn-danger .badge,.btn-default .badge,.btn-info .badge,.btn-primary .badge,.btn-success .badge,.btn-warning .badge{text-shadow:none}.btn.active,.btn:active{background-image:none}.btn-default{text-shadow:0 1px 0 #fff;background-image:-webkit-linear-gradient(top,#fff 0,#e0e0e0 100%);background-image:-o-linear-gradient(top,#fff 0,#e0e0e0 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#fff),to(#e0e0e0));background-image:linear-gradient(to bottom,#fff 0,#e0e0e0 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffffffff', endColorstr='#ffe0e0e0', GradientType=0);filter:progid:DXImageTransform.Microsoft.gradient(enabled=false);background-repeat:repeat-x;border-color:#dbdbdb;border-color:#ccc}.btn-default:focus,.btn-default:hover{background-color:#e0e0e0;background-position:0 -15px}.btn-default.active,.btn-default:active{background-color:#e0e0e0;border-color:#dbdbdb}.btn-default.disabled,.btn-default.disabled.active,.btn-default.disabled.focus,.btn-default.disabled:active,.btn-default.disabled:focus,.btn-default.disabled:hover,.btn-default[disabled],.btn-default[disabled].active,.btn-default[disabled].focus,.btn-default[disabled]:active,.btn-default[disabled]:focus,.btn-default[disabled]:hover,fieldset[disabled] .btn-default,fieldset[disabled] .btn-default.active,fieldset[disabled] .btn-default.focus,fieldset[disabled] .btn-default:active,fieldset[disabled] .btn-default:focus,fieldset[disabled] .btn-default:hover{background-color:#e0e0e0;background-image:none}.btn-primary{background-image:-webkit-linear-gradient(top,#337ab7 0,#265a88 100%);background-image:-o-linear-gradient(top,#337ab7 0,#265a88 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#337ab7),to(#265a88));background-image:linear-gradient(to bottom,#337ab7 0,#265a88 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff337ab7', endColorstr='#ff265a88', GradientType=0);filter:progid:DXImageTransform.Microsoft.gradient(enabled=false);background-repeat:repeat-x;border-color:#245580}.btn-primary:focus,.btn-primary:hover{background-color:#265a88;background-position:0 -15px}.btn-primary.active,.btn-primary:active{background-color:#265a88;border-color:#245580}.btn-primary.disabled,.btn-primary.disabled.active,.btn-primary.disabled.focus,.btn-primary.disabled:active,.btn-primary.disabled:focus,.btn-primary.disabled:hover,.btn-primary[disabled],.btn-primary[disabled].active,.btn-primary[disabled].focus,.btn-primary[disabled]:active,.btn-primary[disabled]:focus,.btn-primary[disabled]:hover,fieldset[disabled] .btn-primary,fieldset[disabled] .btn-primary.active,fieldset[disabled] .btn-primary.focus,fieldset[disabled] .btn-primary:active,fieldset[disabled] .btn-primary:focus,fieldset[disabled] .btn-primary:hover{background-color:#265a88;background-image:none}.btn-success{background-image:-webkit-linear-gradient(top,#5cb85c 0,#419641 100%);background-image:-o-linear-gradient(top,#5cb85c 0,#419641 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#5cb85c),to(#419641));background-image:linear-gradient(to bottom,#5cb85c 0,#419641 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff5cb85c', endColorstr='#ff419641', GradientType=0);filter:progid:DXImageTransform.Microsoft.gradient(enabled=false);background-repeat:repeat-x;border-color:#3e8f3e}.btn-success:focus,.btn-success:hover{background-color:#419641;background-position:0 -15px}.btn-success.active,.btn-success:active{background-color:#419641;border-color:#3e8f3e}.btn-success.disabled,.btn-success.disabled.active,.btn-success.disabled.focus,.btn-success.disabled:active,.btn-success.disabled:focus,.btn-success.disabled:hover,.btn-success[disabled],.btn-success[disabled].active,.btn-success[disabled].focus,.btn-success[disabled]:active,.btn-success[disabled]:focus,.btn-success[disabled]:hover,fieldset[disabled] .btn-success,fieldset[disabled] .btn-success.active,fieldset[disabled] .btn-success.focus,fieldset[disabled] .btn-success:active,fieldset[disabled] .btn-success:focus,fieldset[disabled] .btn-success:hover{background-color:#419641;background-image:none}.btn-info{background-image:-webkit-linear-gradient(top,#5bc0de 0,#2aabd2 100%);background-image:-o-linear-gradient(top,#5bc0de 0,#2aabd2 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#5bc0de),to(#2aabd2));background-image:linear-gradient(to bottom,#5bc0de 0,#2aabd2 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff5bc0de', endColorstr='#ff2aabd2', GradientType=0);filter:progid:DXImageTransform.Microsoft.gradient(enabled=false);background-repeat:repeat-x;border-color:#28a4c9}.btn-info:focus,.btn-info:hover{background-color:#2aabd2;background-position:0 -15px}.btn-info.active,.btn-info:active{background-color:#2aabd2;border-color:#28a4c9}.btn-info.disabled,.btn-info.disabled.active,.btn-info.disabled.focus,.btn-info.disabled:active,.btn-info.disabled:focus,.btn-info.disabled:hover,.btn-info[disabled],.btn-info[disabled].active,.btn-info[disabled].focus,.btn-info[disabled]:active,.btn-info[disabled]:focus,.btn-info[disabled]:hover,fieldset[disabled] .btn-info,fieldset[disabled] .btn-info.active,fieldset[disabled] .btn-info.focus,fieldset[disabled] .btn-info:active,fieldset[disabled] .btn-info:focus,fieldset[disabled] .btn-info:hover{background-color:#2aabd2;background-image:none}.btn-warning{background-image:-webkit-linear-gradient(top,#f0ad4e 0,#eb9316 100%);background-image:-o-linear-gradient(top,#f0ad4e 0,#eb9316 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#f0ad4e),to(#eb9316));background-image:linear-gradient(to bottom,#f0ad4e 0,#eb9316 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#fff0ad4e', endColorstr='#ffeb9316', GradientType=0);filter:progid:DXImageTransform.Microsoft.gradient(enabled=false);background-repeat:repeat-x;border-color:#e38d13}.btn-warning:focus,.btn-warning:hover{background-color:#eb9316;background-position:0 -15px}.btn-warning.active,.btn-warning:active{background-color:#eb9316;border-color:#e38d13}.btn-warning.disabled,.btn-warning.disabled.active,.btn-warning.disabled.focus,.btn-warning.disabled:active,.btn-warning.disabled:focus,.btn-warning.disabled:hover,.btn-warning[disabled],.btn-warning[disabled].active,.btn-warning[disabled].focus,.btn-warning[disabled]:active,.btn-warning[disabled]:focus,.btn-warning[disabled]:hover,fieldset[disabled] .btn-warning,fieldset[disabled] .btn-warning.active,fieldset[disabled] .btn-warning.focus,fieldset[disabled] .btn-warning:active,fieldset[disabled] .btn-warning:focus,fieldset[disabled] .btn-warning:hover{background-color:#eb9316;background-image:none}.btn-danger{background-image:-webkit-linear-gradient(top,#d9534f 0,#c12e2a 100%);background-image:-o-linear-gradient(top,#d9534f 0,#c12e2a 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#d9534f),to(#c12e2a));background-image:linear-gradient(to bottom,#d9534f 0,#c12e2a 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffd9534f', endColorstr='#ffc12e2a', GradientType=0);filter:progid:DXImageTransform.Microsoft.gradient(enabled=false);background-repeat:repeat-x;border-color:#b92c28}.btn-danger:focus,.btn-danger:hover{background-color:#c12e2a;background-position:0 -15px}.btn-danger.active,.btn-danger:active{background-color:#c12e2a;border-color:#b92c28}.btn-danger.disabled,.btn-danger.disabled.active,.btn-danger.disabled.focus,.btn-danger.disabled:active,.btn-danger.disabled:focus,.btn-danger.disabled:hover,.btn-danger[disabled],.btn-danger[disabled].active,.btn-danger[disabled].focus,.btn-danger[disabled]:active,.btn-danger[disabled]:focus,.btn-danger[disabled]:hover,fieldset[disabled] .btn-danger,fieldset[disabled] .btn-danger.active,fieldset[disabled] .btn-danger.focus,fieldset[disabled] .btn-danger:active,fieldset[disabled] .btn-danger:focus,fieldset[disabled] .btn-danger:hover{background-color:#c12e2a;background-image:none}.img-thumbnail,.thumbnail{-webkit-box-shadow:0 1px 2px rgba(0,0,0,.075);box-shadow:0 1px 2px rgba(0,0,0,.075)}.dropdown-menu>li>a:focus,.dropdown-menu>li>a:hover{background-color:#e8e8e8;background-image:-webkit-linear-gradient(top,#f5f5f5 0,#e8e8e8 100%);background-image:-o-linear-gradient(top,#f5f5f5 0,#e8e8e8 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#f5f5f5),to(#e8e8e8));background-image:linear-gradient(to bottom,#f5f5f5 0,#e8e8e8 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#fff5f5f5', endColorstr='#ffe8e8e8', GradientType=0);background-repeat:repeat-x}.dropdown-menu>.active>a,.dropdown-menu>.active>a:focus,.dropdown-menu>.active>a:hover{background-color:#2e6da4;background-image:-webkit-linear-gradient(top,#337ab7 0,#2e6da4 100%);background-image:-o-linear-gradient(top,#337ab7 0,#2e6da4 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#337ab7),to(#2e6da4));background-image:linear-gradient(to bottom,#337ab7 0,#2e6da4 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff337ab7', endColorstr='#ff2e6da4', GradientType=0);background-repeat:repeat-x}.navbar-default{background-image:-webkit-linear-gradient(top,#fff 0,#f8f8f8 100%);background-image:-o-linear-gradient(top,#fff 0,#f8f8f8 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#fff),to(#f8f8f8));background-image:linear-gradient(to bottom,#fff 0,#f8f8f8 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffffffff', endColorstr='#fff8f8f8', GradientType=0);filter:progid:DXImageTransform.Microsoft.gradient(enabled=false);background-repeat:repeat-x;border-radius:4px;-webkit-box-shadow:inset 0 1px 0 rgba(255,255,255,.15),0 1px 5px rgba(0,0,0,.075);box-shadow:inset 0 1px 0 rgba(255,255,255,.15),0 1px 5px rgba(0,0,0,.075)}.navbar-default .navbar-nav>.active>a,.navbar-default .navbar-nav>.open>a{background-image:-webkit-linear-gradient(top,#dbdbdb 0,#e2e2e2 100%);background-image:-o-linear-gradient(top,#dbdbdb 0,#e2e2e2 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#dbdbdb),to(#e2e2e2));background-image:linear-gradient(to bottom,#dbdbdb 0,#e2e2e2 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffdbdbdb', endColorstr='#ffe2e2e2', GradientType=0);background-repeat:repeat-x;-webkit-box-shadow:inset 0 3px 9px rgba(0,0,0,.075);box-shadow:inset 0 3px 9px rgba(0,0,0,.075)}.navbar-brand,.navbar-nav>li>a{text-shadow:0 1px 0 rgba(255,255,255,.25)}.navbar-inverse{background-image:-webkit-linear-gradient(top,#3c3c3c 0,#222 100%);background-image:-o-linear-gradient(top,#3c3c3c 0,#222 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#3c3c3c),to(#222));background-image:linear-gradient(to bottom,#3c3c3c 0,#222 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff3c3c3c', endColorstr='#ff222222', GradientType=0);filter:progid:DXImageTransform.Microsoft.gradient(enabled=false);background-repeat:repeat-x;border-radius:4px}.navbar-inverse .navbar-nav>.active>a,.navbar-inverse .navbar-nav>.open>a{background-image:-webkit-linear-gradient(top,#080808 0,#0f0f0f 100%);background-image:-o-linear-gradient(top,#080808 0,#0f0f0f 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#080808),to(#0f0f0f));background-image:linear-gradient(to bottom,#080808 0,#0f0f0f 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff080808', endColorstr='#ff0f0f0f', GradientType=0);background-repeat:repeat-x;-webkit-box-shadow:inset 0 3px 9px rgba(0,0,0,.25);box-shadow:inset 0 3px 9px rgba(0,0,0,.25)}.navbar-inverse .navbar-brand,.navbar-inverse .navbar-nav>li>a{text-shadow:0 -1px 0 rgba(0,0,0,.25)}.navbar-fixed-bottom,.navbar-fixed-top,.navbar-static-top{border-radius:0}@media (max-width:767px){.navbar .navbar-nav .open .dropdown-menu>.active>a,.navbar .navbar-nav .open .dropdown-menu>.active>a:focus,.navbar .navbar-nav .open .dropdown-menu>.active>a:hover{color:#fff;background-image:-webkit-linear-gradient(top,#337ab7 0,#2e6da4 100%);background-image:-o-linear-gradient(top,#337ab7 0,#2e6da4 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#337ab7),to(#2e6da4));background-image:linear-gradient(to bottom,#337ab7 0,#2e6da4 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff337ab7', endColorstr='#ff2e6da4', GradientType=0);background-repeat:repeat-x}}.alert{text-shadow:0 1px 0 rgba(255,255,255,.2);-webkit-box-shadow:inset 0 1px 0 rgba(255,255,255,.25),0 1px 2px rgba(0,0,0,.05);box-shadow:inset 0 1px 0 rgba(255,255,255,.25),0 1px 2px rgba(0,0,0,.05)}.alert-success{background-image:-webkit-linear-gradient(top,#dff0d8 0,#c8e5bc 100%);background-image:-o-linear-gradient(top,#dff0d8 0,#c8e5bc 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#dff0d8),to(#c8e5bc));background-image:linear-gradient(to bottom,#dff0d8 0,#c8e5bc 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffdff0d8', endColorstr='#ffc8e5bc', GradientType=0);background-repeat:repeat-x;border-color:#b2dba1}.alert-info{background-image:-webkit-linear-gradient(top,#d9edf7 0,#b9def0 100%);background-image:-o-linear-gradient(top,#d9edf7 0,#b9def0 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#d9edf7),to(#b9def0));background-image:linear-gradient(to bottom,#d9edf7 0,#b9def0 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffd9edf7', endColorstr='#ffb9def0', GradientType=0);background-repeat:repeat-x;border-color:#9acfea}.alert-warning{background-image:-webkit-linear-gradient(top,#fcf8e3 0,#f8efc0 100%);background-image:-o-linear-gradient(top,#fcf8e3 0,#f8efc0 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#fcf8e3),to(#f8efc0));background-image:linear-gradient(to bottom,#fcf8e3 0,#f8efc0 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#fffcf8e3', endColorstr='#fff8efc0', GradientType=0);background-repeat:repeat-x;border-color:#f5e79e}.alert-danger{background-image:-webkit-linear-gradient(top,#f2dede 0,#e7c3c3 100%);background-image:-o-linear-gradient(top,#f2dede 0,#e7c3c3 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#f2dede),to(#e7c3c3));background-image:linear-gradient(to bottom,#f2dede 0,#e7c3c3 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#fff2dede', endColorstr='#ffe7c3c3', GradientType=0);background-repeat:repeat-x;border-color:#dca7a7}.progress{background-image:-webkit-linear-gradient(top,#ebebeb 0,#f5f5f5 100%);background-image:-o-linear-gradient(top,#ebebeb 0,#f5f5f5 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#ebebeb),to(#f5f5f5));background-image:linear-gradient(to bottom,#ebebeb 0,#f5f5f5 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffebebeb', endColorstr='#fff5f5f5', GradientType=0);background-repeat:repeat-x}.progress-bar{background-image:-webkit-linear-gradient(top,#337ab7 0,#286090 100%);background-image:-o-linear-gradient(top,#337ab7 0,#286090 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#337ab7),to(#286090));background-image:linear-gradient(to bottom,#337ab7 0,#286090 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff337ab7', endColorstr='#ff286090', GradientType=0);background-repeat:repeat-x}.progress-bar-success{background-image:-webkit-linear-gradient(top,#5cb85c 0,#449d44 100%);background-image:-o-linear-gradient(top,#5cb85c 0,#449d44 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#5cb85c),to(#449d44));background-image:linear-gradient(to bottom,#5cb85c 0,#449d44 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff5cb85c', endColorstr='#ff449d44', GradientType=0);background-repeat:repeat-x}.progress-bar-info{background-image:-webkit-linear-gradient(top,#5bc0de 0,#31b0d5 100%);background-image:-o-linear-gradient(top,#5bc0de 0,#31b0d5 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#5bc0de),to(#31b0d5));background-image:linear-gradient(to bottom,#5bc0de 0,#31b0d5 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff5bc0de', endColorstr='#ff31b0d5', GradientType=0);background-repeat:repeat-x}.progress-bar-warning{background-image:-webkit-linear-gradient(top,#f0ad4e 0,#ec971f 100%);background-image:-o-linear-gradient(top,#f0ad4e 0,#ec971f 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#f0ad4e),to(#ec971f));background-image:linear-gradient(to bottom,#f0ad4e 0,#ec971f 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#fff0ad4e', endColorstr='#ffec971f', GradientType=0);background-repeat:repeat-x}.progress-bar-danger{background-image:-webkit-linear-gradient(top,#d9534f 0,#c9302c 100%);background-image:-o-linear-gradient(top,#d9534f 0,#c9302c 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#d9534f),to(#c9302c));background-image:linear-gradient(to bottom,#d9534f 0,#c9302c 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffd9534f', endColorstr='#ffc9302c', GradientType=0);background-repeat:repeat-x}.progress-bar-striped{background-image:-webkit-linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);background-image:-o-linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);background-image:linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent)}.list-group{border-radius:4px;-webkit-box-shadow:0 1px 2px rgba(0,0,0,.075);box-shadow:0 1px 2px rgba(0,0,0,.075)}.list-group-item.active,.list-group-item.active:focus,.list-group-item.active:hover{text-shadow:0 -1px 0 #286090;background-image:-webkit-linear-gradient(top,#337ab7 0,#2b669a 100%);background-image:-o-linear-gradient(top,#337ab7 0,#2b669a 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#337ab7),to(#2b669a));background-image:linear-gradient(to bottom,#337ab7 0,#2b669a 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff337ab7', endColorstr='#ff2b669a', GradientType=0);background-repeat:repeat-x;border-color:#2b669a}.list-group-item.active .badge,.list-group-item.active:focus .badge,.list-group-item.active:hover .badge{text-shadow:none}.panel{-webkit-box-shadow:0 1px 2px rgba(0,0,0,.05);box-shadow:0 1px 2px rgba(0,0,0,.05)}.panel-default>.panel-heading{background-image:-webkit-linear-gradient(top,#f5f5f5 0,#e8e8e8 100%);background-image:-o-linear-gradient(top,#f5f5f5 0,#e8e8e8 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#f5f5f5),to(#e8e8e8));background-image:linear-gradient(to bottom,#f5f5f5 0,#e8e8e8 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#fff5f5f5', endColorstr='#ffe8e8e8', GradientType=0);background-repeat:repeat-x}.panel-primary>.panel-heading{background-image:-webkit-linear-gradient(top,#337ab7 0,#2e6da4 100%);background-image:-o-linear-gradient(top,#337ab7 0,#2e6da4 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#337ab7),to(#2e6da4));background-image:linear-gradient(to bottom,#337ab7 0,#2e6da4 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff337ab7', endColorstr='#ff2e6da4', GradientType=0);background-repeat:repeat-x}.panel-success>.panel-heading{background-image:-webkit-linear-gradient(top,#dff0d8 0,#d0e9c6 100%);background-image:-o-linear-gradient(top,#dff0d8 0,#d0e9c6 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#dff0d8),to(#d0e9c6));background-image:linear-gradient(to bottom,#dff0d8 0,#d0e9c6 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffdff0d8', endColorstr='#ffd0e9c6', GradientType=0);background-repeat:repeat-x}.panel-info>.panel-heading{background-image:-webkit-linear-gradient(top,#d9edf7 0,#c4e3f3 100%);background-image:-o-linear-gradient(top,#d9edf7 0,#c4e3f3 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#d9edf7),to(#c4e3f3));background-image:linear-gradient(to bottom,#d9edf7 0,#c4e3f3 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffd9edf7', endColorstr='#ffc4e3f3', GradientType=0);background-repeat:repeat-x}.panel-warning>.panel-heading{background-image:-webkit-linear-gradient(top,#fcf8e3 0,#faf2cc 100%);background-image:-o-linear-gradient(top,#fcf8e3 0,#faf2cc 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#fcf8e3),to(#faf2cc));background-image:linear-gradient(to bottom,#fcf8e3 0,#faf2cc 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#fffcf8e3', endColorstr='#fffaf2cc', GradientType=0);background-repeat:repeat-x}.panel-danger>.panel-heading{background-image:-webkit-linear-gradient(top,#f2dede 0,#ebcccc 100%);background-image:-o-linear-gradient(top,#f2dede 0,#ebcccc 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#f2dede),to(#ebcccc));background-image:linear-gradient(to bottom,#f2dede 0,#ebcccc 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#fff2dede', endColorstr='#ffebcccc', GradientType=0);background-repeat:repeat-x}.well{background-image:-webkit-linear-gradient(top,#e8e8e8 0,#f5f5f5 100%);background-image:-o-linear-gradient(top,#e8e8e8 0,#f5f5f5 100%);background-image:-webkit-gradient(linear,left top,left bottom,from(#e8e8e8),to(#f5f5f5));background-image:linear-gradient(to bottom,#e8e8e8 0,#f5f5f5 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffe8e8e8', endColorstr='#fff5f5f5', GradientType=0);background-repeat:repeat-x;border-color:#dcdcdc;-webkit-box-shadow:inset 0 1px 3px rgba(0,0,0,.05),0 1px 0 rgba(255,255,255,.1);box-shadow:inset 0 1px 3px rgba(0,0,0,.05),0 1px 0 rgba(255,255,255,.1)}
-/*# sourceMappingURL=bootstrap-theme.min.css.map */ \ No newline at end of file
diff --git a/library/bootstrap/css/bootstrap-theme.min.css.map b/library/bootstrap/css/bootstrap-theme.min.css.map
deleted file mode 100644
index 94813e900..000000000
--- a/library/bootstrap/css/bootstrap-theme.min.css.map
+++ /dev/null
@@ -1 +0,0 @@
-{"version":3,"sources":["less/theme.less","less/mixins/vendor-prefixes.less","less/mixins/gradients.less","less/mixins/reset-filter.less"],"names":[],"mappings":";;;;AAmBA,YAAA,aAAA,UAAA,aAAA,aAAA,aAME,YAAA,EAAA,KAAA,EAAA,eC2CA,mBAAA,MAAA,EAAA,IAAA,EAAA,sBAAA,EAAA,IAAA,IAAA,iBACQ,WAAA,MAAA,EAAA,IAAA,EAAA,sBAAA,EAAA,IAAA,IAAA,iBDvCR,mBAAA,mBAAA,oBAAA,oBAAA,iBAAA,iBAAA,oBAAA,oBAAA,oBAAA,oBAAA,oBAAA,oBCsCA,mBAAA,MAAA,EAAA,IAAA,IAAA,iBACQ,WAAA,MAAA,EAAA,IAAA,IAAA,iBDlCR,qBAAA,sBAAA,sBAAA,uBAAA,mBAAA,oBAAA,sBAAA,uBAAA,sBAAA,uBAAA,sBAAA,uBAAA,+BAAA,gCAAA,6BAAA,gCAAA,gCAAA,gCCiCA,mBAAA,KACQ,WAAA,KDlDV,mBAAA,oBAAA,iBAAA,oBAAA,oBAAA,oBAuBI,YAAA,KAyCF,YAAA,YAEE,iBAAA,KAKJ,aErEI,YAAA,EAAA,IAAA,EAAA,KACA,iBAAA,iDACA,iBAAA,4CAAA,iBAAA,qEAEA,iBAAA,+CCnBF,OAAA,+GH4CA,OAAA,0DACA,kBAAA,SAuC2C,aAAA,QAA2B,aAAA,KArCtE,mBAAA,mBAEE,iBAAA,QACA,oBAAA,EAAA,MAGF,oBAAA,oBAEE,iBAAA,QACA,aAAA,QAMA,sBAAA,6BAAA,4BAAA,6BAAA,4BAAA,4BAAA,uBAAA,8BAAA,6BAAA,8BAAA,6BAAA,6BAAA,gCAAA,uCAAA,sCAAA,uCAAA,sCAAA,sCAME,iBAAA,QACA,iBAAA,KAgBN,aEtEI,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDAEA,OAAA,+GCnBF,OAAA,0DH4CA,kBAAA,SACA,aAAA,QAEA,mBAAA,mBAEE,iBAAA,QACA,oBAAA,EAAA,MAGF,oBAAA,oBAEE,iBAAA,QACA,aAAA,QAMA,sBAAA,6BAAA,4BAAA,6BAAA,4BAAA,4BAAA,uBAAA,8BAAA,6BAAA,8BAAA,6BAAA,6BAAA,gCAAA,uCAAA,sCAAA,uCAAA,sCAAA,sCAME,iBAAA,QACA,iBAAA,KAiBN,aEvEI,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDAEA,OAAA,+GCnBF,OAAA,0DH4CA,kBAAA,SACA,aAAA,QAEA,mBAAA,mBAEE,iBAAA,QACA,oBAAA,EAAA,MAGF,oBAAA,oBAEE,iBAAA,QACA,aAAA,QAMA,sBAAA,6BAAA,4BAAA,6BAAA,4BAAA,4BAAA,uBAAA,8BAAA,6BAAA,8BAAA,6BAAA,6BAAA,gCAAA,uCAAA,sCAAA,uCAAA,sCAAA,sCAME,iBAAA,QACA,iBAAA,KAkBN,UExEI,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDAEA,OAAA,+GCnBF,OAAA,0DH4CA,kBAAA,SACA,aAAA,QAEA,gBAAA,gBAEE,iBAAA,QACA,oBAAA,EAAA,MAGF,iBAAA,iBAEE,iBAAA,QACA,aAAA,QAMA,mBAAA,0BAAA,yBAAA,0BAAA,yBAAA,yBAAA,oBAAA,2BAAA,0BAAA,2BAAA,0BAAA,0BAAA,6BAAA,oCAAA,mCAAA,oCAAA,mCAAA,mCAME,iBAAA,QACA,iBAAA,KAmBN,aEzEI,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDAEA,OAAA,+GCnBF,OAAA,0DH4CA,kBAAA,SACA,aAAA,QAEA,mBAAA,mBAEE,iBAAA,QACA,oBAAA,EAAA,MAGF,oBAAA,oBAEE,iBAAA,QACA,aAAA,QAMA,sBAAA,6BAAA,4BAAA,6BAAA,4BAAA,4BAAA,uBAAA,8BAAA,6BAAA,8BAAA,6BAAA,6BAAA,gCAAA,uCAAA,sCAAA,uCAAA,sCAAA,sCAME,iBAAA,QACA,iBAAA,KAoBN,YE1EI,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDAEA,OAAA,+GCnBF,OAAA,0DH4CA,kBAAA,SACA,aAAA,QAEA,kBAAA,kBAEE,iBAAA,QACA,oBAAA,EAAA,MAGF,mBAAA,mBAEE,iBAAA,QACA,aAAA,QAMA,qBAAA,4BAAA,2BAAA,4BAAA,2BAAA,2BAAA,sBAAA,6BAAA,4BAAA,6BAAA,4BAAA,4BAAA,+BAAA,sCAAA,qCAAA,sCAAA,qCAAA,qCAME,iBAAA,QACA,iBAAA,KA2BN,eAAA,WClCE,mBAAA,EAAA,IAAA,IAAA,iBACQ,WAAA,EAAA,IAAA,IAAA,iBD2CV,0BAAA,0BE3FI,iBAAA,QACA,iBAAA,oDACA,iBAAA,+CAAA,iBAAA,wEACA,iBAAA,kDACA,OAAA,+GF0FF,kBAAA,SAEF,yBAAA,+BAAA,+BEhGI,iBAAA,QACA,iBAAA,oDACA,iBAAA,+CAAA,iBAAA,wEACA,iBAAA,kDACA,OAAA,+GFgGF,kBAAA,SASF,gBE7GI,iBAAA,iDACA,iBAAA,4CACA,iBAAA,qEAAA,iBAAA,+CACA,OAAA,+GACA,OAAA,0DCnBF,kBAAA,SH+HA,cAAA,ICjEA,mBAAA,MAAA,EAAA,IAAA,EAAA,sBAAA,EAAA,IAAA,IAAA,iBACQ,WAAA,MAAA,EAAA,IAAA,EAAA,sBAAA,EAAA,IAAA,IAAA,iBD6DV,sCAAA,oCE7GI,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDACA,OAAA,+GACA,kBAAA,SD2CF,mBAAA,MAAA,EAAA,IAAA,IAAA,iBACQ,WAAA,MAAA,EAAA,IAAA,IAAA,iBD0EV,cAAA,iBAEE,YAAA,EAAA,IAAA,EAAA,sBAIF,gBEhII,iBAAA,iDACA,iBAAA,4CACA,iBAAA,qEAAA,iBAAA,+CACA,OAAA,+GACA,OAAA,0DCnBF,kBAAA,SHkJA,cAAA,IAHF,sCAAA,oCEhII,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDACA,OAAA,+GACA,kBAAA,SD2CF,mBAAA,MAAA,EAAA,IAAA,IAAA,gBACQ,WAAA,MAAA,EAAA,IAAA,IAAA,gBDgFV,8BAAA,iCAYI,YAAA,EAAA,KAAA,EAAA,gBAKJ,qBAAA,kBAAA,mBAGE,cAAA,EAqBF,yBAfI,mDAAA,yDAAA,yDAGE,MAAA,KE7JF,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDACA,OAAA,+GACA,kBAAA,UFqKJ,OACE,YAAA,EAAA,IAAA,EAAA,qBC3HA,mBAAA,MAAA,EAAA,IAAA,EAAA,sBAAA,EAAA,IAAA,IAAA,gBACQ,WAAA,MAAA,EAAA,IAAA,EAAA,sBAAA,EAAA,IAAA,IAAA,gBDsIV,eEtLI,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDACA,OAAA,+GACA,kBAAA,SF8KF,aAAA,QAKF,YEvLI,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDACA,OAAA,+GACA,kBAAA,SF8KF,aAAA,QAMF,eExLI,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDACA,OAAA,+GACA,kBAAA,SF8KF,aAAA,QAOF,cEzLI,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDACA,OAAA,+GACA,kBAAA,SF8KF,aAAA,QAeF,UEjMI,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDACA,OAAA,+GACA,kBAAA,SFuMJ,cE3MI,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDACA,OAAA,+GACA,kBAAA,SFwMJ,sBE5MI,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDACA,OAAA,+GACA,kBAAA,SFyMJ,mBE7MI,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDACA,OAAA,+GACA,kBAAA,SF0MJ,sBE9MI,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDACA,OAAA,+GACA,kBAAA,SF2MJ,qBE/MI,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDACA,OAAA,+GACA,kBAAA,SF+MJ,sBElLI,iBAAA,yKACA,iBAAA,oKACA,iBAAA,iKFyLJ,YACE,cAAA,IC9KA,mBAAA,EAAA,IAAA,IAAA,iBACQ,WAAA,EAAA,IAAA,IAAA,iBDgLV,wBAAA,8BAAA,8BAGE,YAAA,EAAA,KAAA,EAAA,QEnOE,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDACA,OAAA,+GACA,kBAAA,SFiOF,aAAA,QALF,+BAAA,qCAAA,qCAQI,YAAA,KAUJ,OCnME,mBAAA,EAAA,IAAA,IAAA,gBACQ,WAAA,EAAA,IAAA,IAAA,gBD4MV,8BE5PI,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDACA,OAAA,+GACA,kBAAA,SFyPJ,8BE7PI,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDACA,OAAA,+GACA,kBAAA,SF0PJ,8BE9PI,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDACA,OAAA,+GACA,kBAAA,SF2PJ,2BE/PI,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDACA,OAAA,+GACA,kBAAA,SF4PJ,8BEhQI,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDACA,OAAA,+GACA,kBAAA,SF6PJ,6BEjQI,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDACA,OAAA,+GACA,kBAAA,SFoQJ,MExQI,iBAAA,oDACA,iBAAA,+CACA,iBAAA,wEAAA,iBAAA,kDACA,OAAA,+GACA,kBAAA,SFsQF,aAAA,QC3NA,mBAAA,MAAA,EAAA,IAAA,IAAA,gBAAA,EAAA,IAAA,EAAA,qBACQ,WAAA,MAAA,EAAA,IAAA,IAAA,gBAAA,EAAA,IAAA,EAAA","sourcesContent":["/*!\n * Bootstrap v3.3.7 (http://getbootstrap.com)\n * Copyright 2011-2016 Twitter, Inc.\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)\n */\n\n//\n// Load core variables and mixins\n// --------------------------------------------------\n\n@import \"variables.less\";\n@import \"mixins.less\";\n\n\n//\n// Buttons\n// --------------------------------------------------\n\n// Common styles\n.btn-default,\n.btn-primary,\n.btn-success,\n.btn-info,\n.btn-warning,\n.btn-danger {\n text-shadow: 0 -1px 0 rgba(0,0,0,.2);\n @shadow: inset 0 1px 0 rgba(255,255,255,.15), 0 1px 1px rgba(0,0,0,.075);\n .box-shadow(@shadow);\n\n // Reset the shadow\n &:active,\n &.active {\n .box-shadow(inset 0 3px 5px rgba(0,0,0,.125));\n }\n\n &.disabled,\n &[disabled],\n fieldset[disabled] & {\n .box-shadow(none);\n }\n\n .badge {\n text-shadow: none;\n }\n}\n\n// Mixin for generating new styles\n.btn-styles(@btn-color: #555) {\n #gradient > .vertical(@start-color: @btn-color; @end-color: darken(@btn-color, 12%));\n .reset-filter(); // Disable gradients for IE9 because filter bleeds through rounded corners; see https://github.com/twbs/bootstrap/issues/10620\n background-repeat: repeat-x;\n border-color: darken(@btn-color, 14%);\n\n &:hover,\n &:focus {\n background-color: darken(@btn-color, 12%);\n background-position: 0 -15px;\n }\n\n &:active,\n &.active {\n background-color: darken(@btn-color, 12%);\n border-color: darken(@btn-color, 14%);\n }\n\n &.disabled,\n &[disabled],\n fieldset[disabled] & {\n &,\n &:hover,\n &:focus,\n &.focus,\n &:active,\n &.active {\n background-color: darken(@btn-color, 12%);\n background-image: none;\n }\n }\n}\n\n// Common styles\n.btn {\n // Remove the gradient for the pressed/active state\n &:active,\n &.active {\n background-image: none;\n }\n}\n\n// Apply the mixin to the buttons\n.btn-default { .btn-styles(@btn-default-bg); text-shadow: 0 1px 0 #fff; border-color: #ccc; }\n.btn-primary { .btn-styles(@btn-primary-bg); }\n.btn-success { .btn-styles(@btn-success-bg); }\n.btn-info { .btn-styles(@btn-info-bg); }\n.btn-warning { .btn-styles(@btn-warning-bg); }\n.btn-danger { .btn-styles(@btn-danger-bg); }\n\n\n//\n// Images\n// --------------------------------------------------\n\n.thumbnail,\n.img-thumbnail {\n .box-shadow(0 1px 2px rgba(0,0,0,.075));\n}\n\n\n//\n// Dropdowns\n// --------------------------------------------------\n\n.dropdown-menu > li > a:hover,\n.dropdown-menu > li > a:focus {\n #gradient > .vertical(@start-color: @dropdown-link-hover-bg; @end-color: darken(@dropdown-link-hover-bg, 5%));\n background-color: darken(@dropdown-link-hover-bg, 5%);\n}\n.dropdown-menu > .active > a,\n.dropdown-menu > .active > a:hover,\n.dropdown-menu > .active > a:focus {\n #gradient > .vertical(@start-color: @dropdown-link-active-bg; @end-color: darken(@dropdown-link-active-bg, 5%));\n background-color: darken(@dropdown-link-active-bg, 5%);\n}\n\n\n//\n// Navbar\n// --------------------------------------------------\n\n// Default navbar\n.navbar-default {\n #gradient > .vertical(@start-color: lighten(@navbar-default-bg, 10%); @end-color: @navbar-default-bg);\n .reset-filter(); // Remove gradient in IE<10 to fix bug where dropdowns don't get triggered\n border-radius: @navbar-border-radius;\n @shadow: inset 0 1px 0 rgba(255,255,255,.15), 0 1px 5px rgba(0,0,0,.075);\n .box-shadow(@shadow);\n\n .navbar-nav > .open > a,\n .navbar-nav > .active > a {\n #gradient > .vertical(@start-color: darken(@navbar-default-link-active-bg, 5%); @end-color: darken(@navbar-default-link-active-bg, 2%));\n .box-shadow(inset 0 3px 9px rgba(0,0,0,.075));\n }\n}\n.navbar-brand,\n.navbar-nav > li > a {\n text-shadow: 0 1px 0 rgba(255,255,255,.25);\n}\n\n// Inverted navbar\n.navbar-inverse {\n #gradient > .vertical(@start-color: lighten(@navbar-inverse-bg, 10%); @end-color: @navbar-inverse-bg);\n .reset-filter(); // Remove gradient in IE<10 to fix bug where dropdowns don't get triggered; see https://github.com/twbs/bootstrap/issues/10257\n border-radius: @navbar-border-radius;\n .navbar-nav > .open > a,\n .navbar-nav > .active > a {\n #gradient > .vertical(@start-color: @navbar-inverse-link-active-bg; @end-color: lighten(@navbar-inverse-link-active-bg, 2.5%));\n .box-shadow(inset 0 3px 9px rgba(0,0,0,.25));\n }\n\n .navbar-brand,\n .navbar-nav > li > a {\n text-shadow: 0 -1px 0 rgba(0,0,0,.25);\n }\n}\n\n// Undo rounded corners in static and fixed navbars\n.navbar-static-top,\n.navbar-fixed-top,\n.navbar-fixed-bottom {\n border-radius: 0;\n}\n\n// Fix active state of dropdown items in collapsed mode\n@media (max-width: @grid-float-breakpoint-max) {\n .navbar .navbar-nav .open .dropdown-menu > .active > a {\n &,\n &:hover,\n &:focus {\n color: #fff;\n #gradient > .vertical(@start-color: @dropdown-link-active-bg; @end-color: darken(@dropdown-link-active-bg, 5%));\n }\n }\n}\n\n\n//\n// Alerts\n// --------------------------------------------------\n\n// Common styles\n.alert {\n text-shadow: 0 1px 0 rgba(255,255,255,.2);\n @shadow: inset 0 1px 0 rgba(255,255,255,.25), 0 1px 2px rgba(0,0,0,.05);\n .box-shadow(@shadow);\n}\n\n// Mixin for generating new styles\n.alert-styles(@color) {\n #gradient > .vertical(@start-color: @color; @end-color: darken(@color, 7.5%));\n border-color: darken(@color, 15%);\n}\n\n// Apply the mixin to the alerts\n.alert-success { .alert-styles(@alert-success-bg); }\n.alert-info { .alert-styles(@alert-info-bg); }\n.alert-warning { .alert-styles(@alert-warning-bg); }\n.alert-danger { .alert-styles(@alert-danger-bg); }\n\n\n//\n// Progress bars\n// --------------------------------------------------\n\n// Give the progress background some depth\n.progress {\n #gradient > .vertical(@start-color: darken(@progress-bg, 4%); @end-color: @progress-bg)\n}\n\n// Mixin for generating new styles\n.progress-bar-styles(@color) {\n #gradient > .vertical(@start-color: @color; @end-color: darken(@color, 10%));\n}\n\n// Apply the mixin to the progress bars\n.progress-bar { .progress-bar-styles(@progress-bar-bg); }\n.progress-bar-success { .progress-bar-styles(@progress-bar-success-bg); }\n.progress-bar-info { .progress-bar-styles(@progress-bar-info-bg); }\n.progress-bar-warning { .progress-bar-styles(@progress-bar-warning-bg); }\n.progress-bar-danger { .progress-bar-styles(@progress-bar-danger-bg); }\n\n// Reset the striped class because our mixins don't do multiple gradients and\n// the above custom styles override the new `.progress-bar-striped` in v3.2.0.\n.progress-bar-striped {\n #gradient > .striped();\n}\n\n\n//\n// List groups\n// --------------------------------------------------\n\n.list-group {\n border-radius: @border-radius-base;\n .box-shadow(0 1px 2px rgba(0,0,0,.075));\n}\n.list-group-item.active,\n.list-group-item.active:hover,\n.list-group-item.active:focus {\n text-shadow: 0 -1px 0 darken(@list-group-active-bg, 10%);\n #gradient > .vertical(@start-color: @list-group-active-bg; @end-color: darken(@list-group-active-bg, 7.5%));\n border-color: darken(@list-group-active-border, 7.5%);\n\n .badge {\n text-shadow: none;\n }\n}\n\n\n//\n// Panels\n// --------------------------------------------------\n\n// Common styles\n.panel {\n .box-shadow(0 1px 2px rgba(0,0,0,.05));\n}\n\n// Mixin for generating new styles\n.panel-heading-styles(@color) {\n #gradient > .vertical(@start-color: @color; @end-color: darken(@color, 5%));\n}\n\n// Apply the mixin to the panel headings only\n.panel-default > .panel-heading { .panel-heading-styles(@panel-default-heading-bg); }\n.panel-primary > .panel-heading { .panel-heading-styles(@panel-primary-heading-bg); }\n.panel-success > .panel-heading { .panel-heading-styles(@panel-success-heading-bg); }\n.panel-info > .panel-heading { .panel-heading-styles(@panel-info-heading-bg); }\n.panel-warning > .panel-heading { .panel-heading-styles(@panel-warning-heading-bg); }\n.panel-danger > .panel-heading { .panel-heading-styles(@panel-danger-heading-bg); }\n\n\n//\n// Wells\n// --------------------------------------------------\n\n.well {\n #gradient > .vertical(@start-color: darken(@well-bg, 5%); @end-color: @well-bg);\n border-color: darken(@well-bg, 10%);\n @shadow: inset 0 1px 3px rgba(0,0,0,.05), 0 1px 0 rgba(255,255,255,.1);\n .box-shadow(@shadow);\n}\n","// Vendor Prefixes\n//\n// All vendor mixins are deprecated as of v3.2.0 due to the introduction of\n// Autoprefixer in our Gruntfile. They have been removed in v4.\n\n// - Animations\n// - Backface visibility\n// - Box shadow\n// - Box sizing\n// - Content columns\n// - Hyphens\n// - Placeholder text\n// - Transformations\n// - Transitions\n// - User Select\n\n\n// Animations\n.animation(@animation) {\n -webkit-animation: @animation;\n -o-animation: @animation;\n animation: @animation;\n}\n.animation-name(@name) {\n -webkit-animation-name: @name;\n animation-name: @name;\n}\n.animation-duration(@duration) {\n -webkit-animation-duration: @duration;\n animation-duration: @duration;\n}\n.animation-timing-function(@timing-function) {\n -webkit-animation-timing-function: @timing-function;\n animation-timing-function: @timing-function;\n}\n.animation-delay(@delay) {\n -webkit-animation-delay: @delay;\n animation-delay: @delay;\n}\n.animation-iteration-count(@iteration-count) {\n -webkit-animation-iteration-count: @iteration-count;\n animation-iteration-count: @iteration-count;\n}\n.animation-direction(@direction) {\n -webkit-animation-direction: @direction;\n animation-direction: @direction;\n}\n.animation-fill-mode(@fill-mode) {\n -webkit-animation-fill-mode: @fill-mode;\n animation-fill-mode: @fill-mode;\n}\n\n// Backface visibility\n// Prevent browsers from flickering when using CSS 3D transforms.\n// Default value is `visible`, but can be changed to `hidden`\n\n.backface-visibility(@visibility) {\n -webkit-backface-visibility: @visibility;\n -moz-backface-visibility: @visibility;\n backface-visibility: @visibility;\n}\n\n// Drop shadows\n//\n// Note: Deprecated `.box-shadow()` as of v3.1.0 since all of Bootstrap's\n// supported browsers that have box shadow capabilities now support it.\n\n.box-shadow(@shadow) {\n -webkit-box-shadow: @shadow; // iOS <4.3 & Android <4.1\n box-shadow: @shadow;\n}\n\n// Box sizing\n.box-sizing(@boxmodel) {\n -webkit-box-sizing: @boxmodel;\n -moz-box-sizing: @boxmodel;\n box-sizing: @boxmodel;\n}\n\n// CSS3 Content Columns\n.content-columns(@column-count; @column-gap: @grid-gutter-width) {\n -webkit-column-count: @column-count;\n -moz-column-count: @column-count;\n column-count: @column-count;\n -webkit-column-gap: @column-gap;\n -moz-column-gap: @column-gap;\n column-gap: @column-gap;\n}\n\n// Optional hyphenation\n.hyphens(@mode: auto) {\n word-wrap: break-word;\n -webkit-hyphens: @mode;\n -moz-hyphens: @mode;\n -ms-hyphens: @mode; // IE10+\n -o-hyphens: @mode;\n hyphens: @mode;\n}\n\n// Placeholder text\n.placeholder(@color: @input-color-placeholder) {\n // Firefox\n &::-moz-placeholder {\n color: @color;\n opacity: 1; // Override Firefox's unusual default opacity; see https://github.com/twbs/bootstrap/pull/11526\n }\n &:-ms-input-placeholder { color: @color; } // Internet Explorer 10+\n &::-webkit-input-placeholder { color: @color; } // Safari and Chrome\n}\n\n// Transformations\n.scale(@ratio) {\n -webkit-transform: scale(@ratio);\n -ms-transform: scale(@ratio); // IE9 only\n -o-transform: scale(@ratio);\n transform: scale(@ratio);\n}\n.scale(@ratioX; @ratioY) {\n -webkit-transform: scale(@ratioX, @ratioY);\n -ms-transform: scale(@ratioX, @ratioY); // IE9 only\n -o-transform: scale(@ratioX, @ratioY);\n transform: scale(@ratioX, @ratioY);\n}\n.scaleX(@ratio) {\n -webkit-transform: scaleX(@ratio);\n -ms-transform: scaleX(@ratio); // IE9 only\n -o-transform: scaleX(@ratio);\n transform: scaleX(@ratio);\n}\n.scaleY(@ratio) {\n -webkit-transform: scaleY(@ratio);\n -ms-transform: scaleY(@ratio); // IE9 only\n -o-transform: scaleY(@ratio);\n transform: scaleY(@ratio);\n}\n.skew(@x; @y) {\n -webkit-transform: skewX(@x) skewY(@y);\n -ms-transform: skewX(@x) skewY(@y); // See https://github.com/twbs/bootstrap/issues/4885; IE9+\n -o-transform: skewX(@x) skewY(@y);\n transform: skewX(@x) skewY(@y);\n}\n.translate(@x; @y) {\n -webkit-transform: translate(@x, @y);\n -ms-transform: translate(@x, @y); // IE9 only\n -o-transform: translate(@x, @y);\n transform: translate(@x, @y);\n}\n.translate3d(@x; @y; @z) {\n -webkit-transform: translate3d(@x, @y, @z);\n transform: translate3d(@x, @y, @z);\n}\n.rotate(@degrees) {\n -webkit-transform: rotate(@degrees);\n -ms-transform: rotate(@degrees); // IE9 only\n -o-transform: rotate(@degrees);\n transform: rotate(@degrees);\n}\n.rotateX(@degrees) {\n -webkit-transform: rotateX(@degrees);\n -ms-transform: rotateX(@degrees); // IE9 only\n -o-transform: rotateX(@degrees);\n transform: rotateX(@degrees);\n}\n.rotateY(@degrees) {\n -webkit-transform: rotateY(@degrees);\n -ms-transform: rotateY(@degrees); // IE9 only\n -o-transform: rotateY(@degrees);\n transform: rotateY(@degrees);\n}\n.perspective(@perspective) {\n -webkit-perspective: @perspective;\n -moz-perspective: @perspective;\n perspective: @perspective;\n}\n.perspective-origin(@perspective) {\n -webkit-perspective-origin: @perspective;\n -moz-perspective-origin: @perspective;\n perspective-origin: @perspective;\n}\n.transform-origin(@origin) {\n -webkit-transform-origin: @origin;\n -moz-transform-origin: @origin;\n -ms-transform-origin: @origin; // IE9 only\n transform-origin: @origin;\n}\n\n\n// Transitions\n\n.transition(@transition) {\n -webkit-transition: @transition;\n -o-transition: @transition;\n transition: @transition;\n}\n.transition-property(@transition-property) {\n -webkit-transition-property: @transition-property;\n transition-property: @transition-property;\n}\n.transition-delay(@transition-delay) {\n -webkit-transition-delay: @transition-delay;\n transition-delay: @transition-delay;\n}\n.transition-duration(@transition-duration) {\n -webkit-transition-duration: @transition-duration;\n transition-duration: @transition-duration;\n}\n.transition-timing-function(@timing-function) {\n -webkit-transition-timing-function: @timing-function;\n transition-timing-function: @timing-function;\n}\n.transition-transform(@transition) {\n -webkit-transition: -webkit-transform @transition;\n -moz-transition: -moz-transform @transition;\n -o-transition: -o-transform @transition;\n transition: transform @transition;\n}\n\n\n// User select\n// For selecting text on the page\n\n.user-select(@select) {\n -webkit-user-select: @select;\n -moz-user-select: @select;\n -ms-user-select: @select; // IE10+\n user-select: @select;\n}\n","// Gradients\n\n#gradient {\n\n // Horizontal gradient, from left to right\n //\n // Creates two color stops, start and end, by specifying a color and position for each color stop.\n // Color stops are not available in IE9 and below.\n .horizontal(@start-color: #555; @end-color: #333; @start-percent: 0%; @end-percent: 100%) {\n background-image: -webkit-linear-gradient(left, @start-color @start-percent, @end-color @end-percent); // Safari 5.1-6, Chrome 10+\n background-image: -o-linear-gradient(left, @start-color @start-percent, @end-color @end-percent); // Opera 12\n background-image: linear-gradient(to right, @start-color @start-percent, @end-color @end-percent); // Standard, IE10, Firefox 16+, Opera 12.10+, Safari 7+, Chrome 26+\n background-repeat: repeat-x;\n filter: e(%(\"progid:DXImageTransform.Microsoft.gradient(startColorstr='%d', endColorstr='%d', GradientType=1)\",argb(@start-color),argb(@end-color))); // IE9 and down\n }\n\n // Vertical gradient, from top to bottom\n //\n // Creates two color stops, start and end, by specifying a color and position for each color stop.\n // Color stops are not available in IE9 and below.\n .vertical(@start-color: #555; @end-color: #333; @start-percent: 0%; @end-percent: 100%) {\n background-image: -webkit-linear-gradient(top, @start-color @start-percent, @end-color @end-percent); // Safari 5.1-6, Chrome 10+\n background-image: -o-linear-gradient(top, @start-color @start-percent, @end-color @end-percent); // Opera 12\n background-image: linear-gradient(to bottom, @start-color @start-percent, @end-color @end-percent); // Standard, IE10, Firefox 16+, Opera 12.10+, Safari 7+, Chrome 26+\n background-repeat: repeat-x;\n filter: e(%(\"progid:DXImageTransform.Microsoft.gradient(startColorstr='%d', endColorstr='%d', GradientType=0)\",argb(@start-color),argb(@end-color))); // IE9 and down\n }\n\n .directional(@start-color: #555; @end-color: #333; @deg: 45deg) {\n background-repeat: repeat-x;\n background-image: -webkit-linear-gradient(@deg, @start-color, @end-color); // Safari 5.1-6, Chrome 10+\n background-image: -o-linear-gradient(@deg, @start-color, @end-color); // Opera 12\n background-image: linear-gradient(@deg, @start-color, @end-color); // Standard, IE10, Firefox 16+, Opera 12.10+, Safari 7+, Chrome 26+\n }\n .horizontal-three-colors(@start-color: #00b3ee; @mid-color: #7a43b6; @color-stop: 50%; @end-color: #c3325f) {\n background-image: -webkit-linear-gradient(left, @start-color, @mid-color @color-stop, @end-color);\n background-image: -o-linear-gradient(left, @start-color, @mid-color @color-stop, @end-color);\n background-image: linear-gradient(to right, @start-color, @mid-color @color-stop, @end-color);\n background-repeat: no-repeat;\n filter: e(%(\"progid:DXImageTransform.Microsoft.gradient(startColorstr='%d', endColorstr='%d', GradientType=1)\",argb(@start-color),argb(@end-color))); // IE9 and down, gets no color-stop at all for proper fallback\n }\n .vertical-three-colors(@start-color: #00b3ee; @mid-color: #7a43b6; @color-stop: 50%; @end-color: #c3325f) {\n background-image: -webkit-linear-gradient(@start-color, @mid-color @color-stop, @end-color);\n background-image: -o-linear-gradient(@start-color, @mid-color @color-stop, @end-color);\n background-image: linear-gradient(@start-color, @mid-color @color-stop, @end-color);\n background-repeat: no-repeat;\n filter: e(%(\"progid:DXImageTransform.Microsoft.gradient(startColorstr='%d', endColorstr='%d', GradientType=0)\",argb(@start-color),argb(@end-color))); // IE9 and down, gets no color-stop at all for proper fallback\n }\n .radial(@inner-color: #555; @outer-color: #333) {\n background-image: -webkit-radial-gradient(circle, @inner-color, @outer-color);\n background-image: radial-gradient(circle, @inner-color, @outer-color);\n background-repeat: no-repeat;\n }\n .striped(@color: rgba(255,255,255,.15); @angle: 45deg) {\n background-image: -webkit-linear-gradient(@angle, @color 25%, transparent 25%, transparent 50%, @color 50%, @color 75%, transparent 75%, transparent);\n background-image: -o-linear-gradient(@angle, @color 25%, transparent 25%, transparent 50%, @color 50%, @color 75%, transparent 75%, transparent);\n background-image: linear-gradient(@angle, @color 25%, transparent 25%, transparent 50%, @color 50%, @color 75%, transparent 75%, transparent);\n }\n}\n","// Reset filters for IE\n//\n// When you need to remove a gradient background, do not forget to use this to reset\n// the IE filter for IE9 and below.\n\n.reset-filter() {\n filter: e(%(\"progid:DXImageTransform.Microsoft.gradient(enabled = false)\"));\n}\n"]} \ No newline at end of file
diff --git a/library/bootstrap/css/bootstrap.css b/library/bootstrap/css/bootstrap.css
index 6167622ce..b39107f6f 100644
--- a/library/bootstrap/css/bootstrap.css
+++ b/library/bootstrap/css/bootstrap.css
@@ -1,221 +1,29 @@
/*!
- * Bootstrap v3.3.7 (http://getbootstrap.com)
- * Copyright 2011-2016 Twitter, Inc.
+ * Bootstrap v4.0.0-beta (https://getbootstrap.com)
+ * Copyright 2011-2017 The Bootstrap Authors
+ * Copyright 2011-2017 Twitter, Inc.
* Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
*/
-/*! normalize.css v3.0.3 | MIT License | github.com/necolas/normalize.css */
-html {
- font-family: sans-serif;
- -webkit-text-size-adjust: 100%;
- -ms-text-size-adjust: 100%;
-}
-body {
- margin: 0;
-}
-article,
-aside,
-details,
-figcaption,
-figure,
-footer,
-header,
-hgroup,
-main,
-menu,
-nav,
-section,
-summary {
- display: block;
-}
-audio,
-canvas,
-progress,
-video {
- display: inline-block;
- vertical-align: baseline;
-}
-audio:not([controls]) {
- display: none;
- height: 0;
-}
-[hidden],
-template {
- display: none;
-}
-a {
- background-color: transparent;
-}
-a:active,
-a:hover {
- outline: 0;
-}
-abbr[title] {
- border-bottom: 1px dotted;
-}
-b,
-strong {
- font-weight: bold;
-}
-dfn {
- font-style: italic;
-}
-h1 {
- margin: .67em 0;
- font-size: 2em;
-}
-mark {
- color: #000;
- background: #ff0;
-}
-small {
- font-size: 80%;
-}
-sub,
-sup {
- position: relative;
- font-size: 75%;
- line-height: 0;
- vertical-align: baseline;
-}
-sup {
- top: -.5em;
-}
-sub {
- bottom: -.25em;
-}
-img {
- border: 0;
-}
-svg:not(:root) {
- overflow: hidden;
-}
-figure {
- margin: 1em 40px;
-}
-hr {
- height: 0;
- -webkit-box-sizing: content-box;
- -moz-box-sizing: content-box;
- box-sizing: content-box;
-}
-pre {
- overflow: auto;
-}
-code,
-kbd,
-pre,
-samp {
- font-family: monospace, monospace;
- font-size: 1em;
-}
-button,
-input,
-optgroup,
-select,
-textarea {
- margin: 0;
- font: inherit;
- color: inherit;
-}
-button {
- overflow: visible;
-}
-button,
-select {
- text-transform: none;
-}
-button,
-html input[type="button"],
-input[type="reset"],
-input[type="submit"] {
- -webkit-appearance: button;
- cursor: pointer;
-}
-button[disabled],
-html input[disabled] {
- cursor: default;
-}
-button::-moz-focus-inner,
-input::-moz-focus-inner {
- padding: 0;
- border: 0;
-}
-input {
- line-height: normal;
-}
-input[type="checkbox"],
-input[type="radio"] {
- -webkit-box-sizing: border-box;
- -moz-box-sizing: border-box;
- box-sizing: border-box;
- padding: 0;
-}
-input[type="number"]::-webkit-inner-spin-button,
-input[type="number"]::-webkit-outer-spin-button {
- height: auto;
-}
-input[type="search"] {
- -webkit-box-sizing: content-box;
- -moz-box-sizing: content-box;
- box-sizing: content-box;
- -webkit-appearance: textfield;
-}
-input[type="search"]::-webkit-search-cancel-button,
-input[type="search"]::-webkit-search-decoration {
- -webkit-appearance: none;
-}
-fieldset {
- padding: .35em .625em .75em;
- margin: 0 2px;
- border: 1px solid #c0c0c0;
-}
-legend {
- padding: 0;
- border: 0;
-}
-textarea {
- overflow: auto;
-}
-optgroup {
- font-weight: bold;
-}
-table {
- border-spacing: 0;
- border-collapse: collapse;
-}
-td,
-th {
- padding: 0;
-}
-/*! Source: https://github.com/h5bp/html5-boilerplate/blob/master/src/css/main.css */
@media print {
*,
- *:before,
- *:after {
- color: #000 !important;
+ *::before,
+ *::after {
text-shadow: none !important;
- background: transparent !important;
- -webkit-box-shadow: none !important;
- box-shadow: none !important;
+ box-shadow: none !important;
}
a,
a:visited {
text-decoration: underline;
}
- a[href]:after {
- content: " (" attr(href) ")";
- }
- abbr[title]:after {
+ abbr[title]::after {
content: " (" attr(title) ")";
}
- a[href^="#"]:after,
- a[href^="javascript:"]:after {
- content: "";
+ pre {
+ white-space: pre-wrap !important;
}
pre,
blockquote {
border: 1px solid #999;
-
page-break-inside: avoid;
}
thead {
@@ -225,9 +33,6 @@ th {
img {
page-break-inside: avoid;
}
- img {
- max-width: 100% !important;
- }
p,
h2,
h3 {
@@ -241,11 +46,7 @@ th {
.navbar {
display: none;
}
- .btn > .caret,
- .dropup > .btn > .caret {
- border-top-color: #000 !important;
- }
- .label {
+ .badge {
border: 1px solid #000;
}
.table {
@@ -260,3263 +61,2513 @@ th {
border: 1px solid #ddd !important;
}
}
-@font-face {
- font-family: 'Glyphicons Halflings';
- src: url('../fonts/glyphicons-halflings-regular.eot');
- src: url('../fonts/glyphicons-halflings-regular.eot?#iefix') format('embedded-opentype'), url('../fonts/glyphicons-halflings-regular.woff2') format('woff2'), url('../fonts/glyphicons-halflings-regular.woff') format('woff'), url('../fonts/glyphicons-halflings-regular.ttf') format('truetype'), url('../fonts/glyphicons-halflings-regular.svg#glyphicons_halflingsregular') format('svg');
+html {
+ box-sizing: border-box;
+ font-family: sans-serif;
+ line-height: 1.15;
+ -webkit-text-size-adjust: 100%;
+ -ms-text-size-adjust: 100%;
+ -ms-overflow-style: scrollbar;
+ -webkit-tap-highlight-color: transparent;
}
-.glyphicon {
- position: relative;
- top: 1px;
- display: inline-block;
- font-family: 'Glyphicons Halflings';
- font-style: normal;
- font-weight: normal;
- line-height: 1;
- -webkit-font-smoothing: antialiased;
- -moz-osx-font-smoothing: grayscale;
-}
-.glyphicon-asterisk:before {
- content: "\002a";
-}
-.glyphicon-plus:before {
- content: "\002b";
-}
-.glyphicon-euro:before,
-.glyphicon-eur:before {
- content: "\20ac";
-}
-.glyphicon-minus:before {
- content: "\2212";
-}
-.glyphicon-cloud:before {
- content: "\2601";
-}
-.glyphicon-envelope:before {
- content: "\2709";
-}
-.glyphicon-pencil:before {
- content: "\270f";
-}
-.glyphicon-glass:before {
- content: "\e001";
-}
-.glyphicon-music:before {
- content: "\e002";
-}
-.glyphicon-search:before {
- content: "\e003";
-}
-.glyphicon-heart:before {
- content: "\e005";
-}
-.glyphicon-star:before {
- content: "\e006";
-}
-.glyphicon-star-empty:before {
- content: "\e007";
-}
-.glyphicon-user:before {
- content: "\e008";
-}
-.glyphicon-film:before {
- content: "\e009";
-}
-.glyphicon-th-large:before {
- content: "\e010";
-}
-.glyphicon-th:before {
- content: "\e011";
-}
-.glyphicon-th-list:before {
- content: "\e012";
-}
-.glyphicon-ok:before {
- content: "\e013";
-}
-.glyphicon-remove:before {
- content: "\e014";
-}
-.glyphicon-zoom-in:before {
- content: "\e015";
-}
-.glyphicon-zoom-out:before {
- content: "\e016";
-}
-.glyphicon-off:before {
- content: "\e017";
-}
-.glyphicon-signal:before {
- content: "\e018";
-}
-.glyphicon-cog:before {
- content: "\e019";
-}
-.glyphicon-trash:before {
- content: "\e020";
-}
-.glyphicon-home:before {
- content: "\e021";
-}
-.glyphicon-file:before {
- content: "\e022";
-}
-.glyphicon-time:before {
- content: "\e023";
-}
-.glyphicon-road:before {
- content: "\e024";
-}
-.glyphicon-download-alt:before {
- content: "\e025";
-}
-.glyphicon-download:before {
- content: "\e026";
-}
-.glyphicon-upload:before {
- content: "\e027";
-}
-.glyphicon-inbox:before {
- content: "\e028";
-}
-.glyphicon-play-circle:before {
- content: "\e029";
-}
-.glyphicon-repeat:before {
- content: "\e030";
-}
-.glyphicon-refresh:before {
- content: "\e031";
-}
-.glyphicon-list-alt:before {
- content: "\e032";
-}
-.glyphicon-lock:before {
- content: "\e033";
-}
-.glyphicon-flag:before {
- content: "\e034";
-}
-.glyphicon-headphones:before {
- content: "\e035";
-}
-.glyphicon-volume-off:before {
- content: "\e036";
-}
-.glyphicon-volume-down:before {
- content: "\e037";
-}
-.glyphicon-volume-up:before {
- content: "\e038";
-}
-.glyphicon-qrcode:before {
- content: "\e039";
-}
-.glyphicon-barcode:before {
- content: "\e040";
-}
-.glyphicon-tag:before {
- content: "\e041";
-}
-.glyphicon-tags:before {
- content: "\e042";
-}
-.glyphicon-book:before {
- content: "\e043";
-}
-.glyphicon-bookmark:before {
- content: "\e044";
-}
-.glyphicon-print:before {
- content: "\e045";
-}
-.glyphicon-camera:before {
- content: "\e046";
-}
-.glyphicon-font:before {
- content: "\e047";
-}
-.glyphicon-bold:before {
- content: "\e048";
-}
-.glyphicon-italic:before {
- content: "\e049";
-}
-.glyphicon-text-height:before {
- content: "\e050";
-}
-.glyphicon-text-width:before {
- content: "\e051";
-}
-.glyphicon-align-left:before {
- content: "\e052";
-}
-.glyphicon-align-center:before {
- content: "\e053";
-}
-.glyphicon-align-right:before {
- content: "\e054";
-}
-.glyphicon-align-justify:before {
- content: "\e055";
-}
-.glyphicon-list:before {
- content: "\e056";
-}
-.glyphicon-indent-left:before {
- content: "\e057";
-}
-.glyphicon-indent-right:before {
- content: "\e058";
-}
-.glyphicon-facetime-video:before {
- content: "\e059";
-}
-.glyphicon-picture:before {
- content: "\e060";
-}
-.glyphicon-map-marker:before {
- content: "\e062";
-}
-.glyphicon-adjust:before {
- content: "\e063";
-}
-.glyphicon-tint:before {
- content: "\e064";
-}
-.glyphicon-edit:before {
- content: "\e065";
-}
-.glyphicon-share:before {
- content: "\e066";
-}
-.glyphicon-check:before {
- content: "\e067";
-}
-.glyphicon-move:before {
- content: "\e068";
-}
-.glyphicon-step-backward:before {
- content: "\e069";
-}
-.glyphicon-fast-backward:before {
- content: "\e070";
-}
-.glyphicon-backward:before {
- content: "\e071";
-}
-.glyphicon-play:before {
- content: "\e072";
-}
-.glyphicon-pause:before {
- content: "\e073";
-}
-.glyphicon-stop:before {
- content: "\e074";
-}
-.glyphicon-forward:before {
- content: "\e075";
-}
-.glyphicon-fast-forward:before {
- content: "\e076";
-}
-.glyphicon-step-forward:before {
- content: "\e077";
-}
-.glyphicon-eject:before {
- content: "\e078";
-}
-.glyphicon-chevron-left:before {
- content: "\e079";
-}
-.glyphicon-chevron-right:before {
- content: "\e080";
-}
-.glyphicon-plus-sign:before {
- content: "\e081";
-}
-.glyphicon-minus-sign:before {
- content: "\e082";
-}
-.glyphicon-remove-sign:before {
- content: "\e083";
-}
-.glyphicon-ok-sign:before {
- content: "\e084";
-}
-.glyphicon-question-sign:before {
- content: "\e085";
-}
-.glyphicon-info-sign:before {
- content: "\e086";
-}
-.glyphicon-screenshot:before {
- content: "\e087";
-}
-.glyphicon-remove-circle:before {
- content: "\e088";
-}
-.glyphicon-ok-circle:before {
- content: "\e089";
-}
-.glyphicon-ban-circle:before {
- content: "\e090";
-}
-.glyphicon-arrow-left:before {
- content: "\e091";
-}
-.glyphicon-arrow-right:before {
- content: "\e092";
-}
-.glyphicon-arrow-up:before {
- content: "\e093";
-}
-.glyphicon-arrow-down:before {
- content: "\e094";
-}
-.glyphicon-share-alt:before {
- content: "\e095";
-}
-.glyphicon-resize-full:before {
- content: "\e096";
-}
-.glyphicon-resize-small:before {
- content: "\e097";
-}
-.glyphicon-exclamation-sign:before {
- content: "\e101";
-}
-.glyphicon-gift:before {
- content: "\e102";
-}
-.glyphicon-leaf:before {
- content: "\e103";
-}
-.glyphicon-fire:before {
- content: "\e104";
-}
-.glyphicon-eye-open:before {
- content: "\e105";
-}
-.glyphicon-eye-close:before {
- content: "\e106";
-}
-.glyphicon-warning-sign:before {
- content: "\e107";
-}
-.glyphicon-plane:before {
- content: "\e108";
-}
-.glyphicon-calendar:before {
- content: "\e109";
-}
-.glyphicon-random:before {
- content: "\e110";
-}
-.glyphicon-comment:before {
- content: "\e111";
-}
-.glyphicon-magnet:before {
- content: "\e112";
-}
-.glyphicon-chevron-up:before {
- content: "\e113";
-}
-.glyphicon-chevron-down:before {
- content: "\e114";
-}
-.glyphicon-retweet:before {
- content: "\e115";
-}
-.glyphicon-shopping-cart:before {
- content: "\e116";
-}
-.glyphicon-folder-close:before {
- content: "\e117";
-}
-.glyphicon-folder-open:before {
- content: "\e118";
-}
-.glyphicon-resize-vertical:before {
- content: "\e119";
-}
-.glyphicon-resize-horizontal:before {
- content: "\e120";
-}
-.glyphicon-hdd:before {
- content: "\e121";
-}
-.glyphicon-bullhorn:before {
- content: "\e122";
-}
-.glyphicon-bell:before {
- content: "\e123";
-}
-.glyphicon-certificate:before {
- content: "\e124";
-}
-.glyphicon-thumbs-up:before {
- content: "\e125";
+*,
+*::before,
+*::after {
+ box-sizing: inherit;
}
-.glyphicon-thumbs-down:before {
- content: "\e126";
-}
-.glyphicon-hand-right:before {
- content: "\e127";
-}
-.glyphicon-hand-left:before {
- content: "\e128";
-}
-.glyphicon-hand-up:before {
- content: "\e129";
-}
-.glyphicon-hand-down:before {
- content: "\e130";
-}
-.glyphicon-circle-arrow-right:before {
- content: "\e131";
-}
-.glyphicon-circle-arrow-left:before {
- content: "\e132";
-}
-.glyphicon-circle-arrow-up:before {
- content: "\e133";
-}
-.glyphicon-circle-arrow-down:before {
- content: "\e134";
-}
-.glyphicon-globe:before {
- content: "\e135";
-}
-.glyphicon-wrench:before {
- content: "\e136";
-}
-.glyphicon-tasks:before {
- content: "\e137";
-}
-.glyphicon-filter:before {
- content: "\e138";
-}
-.glyphicon-briefcase:before {
- content: "\e139";
-}
-.glyphicon-fullscreen:before {
- content: "\e140";
-}
-.glyphicon-dashboard:before {
- content: "\e141";
-}
-.glyphicon-paperclip:before {
- content: "\e142";
-}
-.glyphicon-heart-empty:before {
- content: "\e143";
-}
-.glyphicon-link:before {
- content: "\e144";
-}
-.glyphicon-phone:before {
- content: "\e145";
-}
-.glyphicon-pushpin:before {
- content: "\e146";
-}
-.glyphicon-usd:before {
- content: "\e148";
-}
-.glyphicon-gbp:before {
- content: "\e149";
-}
-.glyphicon-sort:before {
- content: "\e150";
-}
-.glyphicon-sort-by-alphabet:before {
- content: "\e151";
-}
-.glyphicon-sort-by-alphabet-alt:before {
- content: "\e152";
-}
-.glyphicon-sort-by-order:before {
- content: "\e153";
-}
-.glyphicon-sort-by-order-alt:before {
- content: "\e154";
-}
-.glyphicon-sort-by-attributes:before {
- content: "\e155";
-}
-.glyphicon-sort-by-attributes-alt:before {
- content: "\e156";
-}
-.glyphicon-unchecked:before {
- content: "\e157";
-}
-.glyphicon-expand:before {
- content: "\e158";
-}
-.glyphicon-collapse-down:before {
- content: "\e159";
-}
-.glyphicon-collapse-up:before {
- content: "\e160";
-}
-.glyphicon-log-in:before {
- content: "\e161";
-}
-.glyphicon-flash:before {
- content: "\e162";
-}
-.glyphicon-log-out:before {
- content: "\e163";
-}
-.glyphicon-new-window:before {
- content: "\e164";
-}
-.glyphicon-record:before {
- content: "\e165";
-}
-.glyphicon-save:before {
- content: "\e166";
-}
-.glyphicon-open:before {
- content: "\e167";
-}
-.glyphicon-saved:before {
- content: "\e168";
-}
-.glyphicon-import:before {
- content: "\e169";
-}
-.glyphicon-export:before {
- content: "\e170";
-}
-.glyphicon-send:before {
- content: "\e171";
-}
-.glyphicon-floppy-disk:before {
- content: "\e172";
-}
-.glyphicon-floppy-saved:before {
- content: "\e173";
-}
-.glyphicon-floppy-remove:before {
- content: "\e174";
-}
-.glyphicon-floppy-save:before {
- content: "\e175";
-}
-.glyphicon-floppy-open:before {
- content: "\e176";
-}
-.glyphicon-credit-card:before {
- content: "\e177";
-}
-.glyphicon-transfer:before {
- content: "\e178";
-}
-.glyphicon-cutlery:before {
- content: "\e179";
-}
-.glyphicon-header:before {
- content: "\e180";
-}
-.glyphicon-compressed:before {
- content: "\e181";
-}
-.glyphicon-earphone:before {
- content: "\e182";
-}
-.glyphicon-phone-alt:before {
- content: "\e183";
-}
-.glyphicon-tower:before {
- content: "\e184";
-}
-.glyphicon-stats:before {
- content: "\e185";
-}
-.glyphicon-sd-video:before {
- content: "\e186";
-}
-.glyphicon-hd-video:before {
- content: "\e187";
-}
-.glyphicon-subtitles:before {
- content: "\e188";
-}
-.glyphicon-sound-stereo:before {
- content: "\e189";
-}
-.glyphicon-sound-dolby:before {
- content: "\e190";
-}
-.glyphicon-sound-5-1:before {
- content: "\e191";
-}
-.glyphicon-sound-6-1:before {
- content: "\e192";
-}
-.glyphicon-sound-7-1:before {
- content: "\e193";
-}
-.glyphicon-copyright-mark:before {
- content: "\e194";
-}
-.glyphicon-registration-mark:before {
- content: "\e195";
-}
-.glyphicon-cloud-download:before {
- content: "\e197";
-}
-.glyphicon-cloud-upload:before {
- content: "\e198";
-}
-.glyphicon-tree-conifer:before {
- content: "\e199";
-}
-.glyphicon-tree-deciduous:before {
- content: "\e200";
-}
-.glyphicon-cd:before {
- content: "\e201";
-}
-.glyphicon-save-file:before {
- content: "\e202";
-}
-.glyphicon-open-file:before {
- content: "\e203";
-}
-.glyphicon-level-up:before {
- content: "\e204";
-}
-.glyphicon-copy:before {
- content: "\e205";
-}
-.glyphicon-paste:before {
- content: "\e206";
-}
-.glyphicon-alert:before {
- content: "\e209";
-}
-.glyphicon-equalizer:before {
- content: "\e210";
-}
-.glyphicon-king:before {
- content: "\e211";
-}
-.glyphicon-queen:before {
- content: "\e212";
-}
-.glyphicon-pawn:before {
- content: "\e213";
-}
-.glyphicon-bishop:before {
- content: "\e214";
-}
-.glyphicon-knight:before {
- content: "\e215";
-}
-.glyphicon-baby-formula:before {
- content: "\e216";
-}
-.glyphicon-tent:before {
- content: "\26fa";
-}
-.glyphicon-blackboard:before {
- content: "\e218";
-}
-.glyphicon-bed:before {
- content: "\e219";
-}
-.glyphicon-apple:before {
- content: "\f8ff";
-}
-.glyphicon-erase:before {
- content: "\e221";
-}
-.glyphicon-hourglass:before {
- content: "\231b";
-}
-.glyphicon-lamp:before {
- content: "\e223";
-}
-.glyphicon-duplicate:before {
- content: "\e224";
-}
-.glyphicon-piggy-bank:before {
- content: "\e225";
-}
-.glyphicon-scissors:before {
- content: "\e226";
-}
-.glyphicon-bitcoin:before {
- content: "\e227";
-}
-.glyphicon-btc:before {
- content: "\e227";
-}
-.glyphicon-xbt:before {
- content: "\e227";
-}
-.glyphicon-yen:before {
- content: "\00a5";
-}
-.glyphicon-jpy:before {
- content: "\00a5";
-}
-.glyphicon-ruble:before {
- content: "\20bd";
-}
-.glyphicon-rub:before {
- content: "\20bd";
+
+@-ms-viewport {
+ width: device-width;
}
-.glyphicon-scale:before {
- content: "\e230";
+
+article, aside, dialog, figcaption, figure, footer, header, hgroup, main, nav, section {
+ display: block;
}
-.glyphicon-ice-lolly:before {
- content: "\e231";
+
+body {
+ margin: 0;
+ font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, "Helvetica Neue", Arial, sans-serif;
+ font-size: 1rem;
+ font-weight: normal;
+ line-height: 1.5;
+ color: #212529;
+ background-color: #fff;
}
-.glyphicon-ice-lolly-tasted:before {
- content: "\e232";
+
+[tabindex="-1"]:focus {
+ outline: none !important;
}
-.glyphicon-education:before {
- content: "\e233";
+
+hr {
+ box-sizing: content-box;
+ height: 0;
+ overflow: visible;
}
-.glyphicon-option-horizontal:before {
- content: "\e234";
+
+h1, h2, h3, h4, h5, h6 {
+ margin-top: 0;
+ margin-bottom: .5rem;
}
-.glyphicon-option-vertical:before {
- content: "\e235";
+
+p {
+ margin-top: 0;
+ margin-bottom: 1rem;
}
-.glyphicon-menu-hamburger:before {
- content: "\e236";
+
+abbr[title],
+abbr[data-original-title] {
+ text-decoration: underline;
+ -webkit-text-decoration: underline dotted;
+ text-decoration: underline dotted;
+ cursor: help;
+ border-bottom: 0;
}
-.glyphicon-modal-window:before {
- content: "\e237";
+
+address {
+ margin-bottom: 1rem;
+ font-style: normal;
+ line-height: inherit;
}
-.glyphicon-oil:before {
- content: "\e238";
+
+ol,
+ul,
+dl {
+ margin-top: 0;
+ margin-bottom: 1rem;
}
-.glyphicon-grain:before {
- content: "\e239";
+
+ol ol,
+ul ul,
+ol ul,
+ul ol {
+ margin-bottom: 0;
}
-.glyphicon-sunglasses:before {
- content: "\e240";
+
+dt {
+ font-weight: bold;
}
-.glyphicon-text-size:before {
- content: "\e241";
+
+dd {
+ margin-bottom: .5rem;
+ margin-left: 0;
}
-.glyphicon-text-color:before {
- content: "\e242";
+
+blockquote {
+ margin: 0 0 1rem;
}
-.glyphicon-text-background:before {
- content: "\e243";
+
+dfn {
+ font-style: italic;
}
-.glyphicon-object-align-top:before {
- content: "\e244";
+
+b,
+strong {
+ font-weight: bolder;
}
-.glyphicon-object-align-bottom:before {
- content: "\e245";
+
+small {
+ font-size: 80%;
}
-.glyphicon-object-align-horizontal:before {
- content: "\e246";
+
+sub,
+sup {
+ position: relative;
+ font-size: 75%;
+ line-height: 0;
+ vertical-align: baseline;
}
-.glyphicon-object-align-left:before {
- content: "\e247";
+
+sub {
+ bottom: -.25em;
}
-.glyphicon-object-align-vertical:before {
- content: "\e248";
+
+sup {
+ top: -.5em;
}
-.glyphicon-object-align-right:before {
- content: "\e249";
+
+a {
+ color: #007bff;
+ text-decoration: none;
+ background-color: transparent;
+ -webkit-text-decoration-skip: objects;
}
-.glyphicon-triangle-right:before {
- content: "\e250";
+
+a:hover {
+ color: #0056b3;
+ text-decoration: underline;
}
-.glyphicon-triangle-left:before {
- content: "\e251";
+
+a:not([href]):not([tabindex]) {
+ color: inherit;
+ text-decoration: none;
}
-.glyphicon-triangle-bottom:before {
- content: "\e252";
+
+a:not([href]):not([tabindex]):focus, a:not([href]):not([tabindex]):hover {
+ color: inherit;
+ text-decoration: none;
}
-.glyphicon-triangle-top:before {
- content: "\e253";
+
+a:not([href]):not([tabindex]):focus {
+ outline: 0;
}
-.glyphicon-console:before {
- content: "\e254";
+
+pre,
+code,
+kbd,
+samp {
+ font-family: monospace, monospace;
+ font-size: 1em;
}
-.glyphicon-superscript:before {
- content: "\e255";
+
+pre {
+ margin-top: 0;
+ margin-bottom: 1rem;
+ overflow: auto;
}
-.glyphicon-subscript:before {
- content: "\e256";
+
+figure {
+ margin: 0 0 1rem;
}
-.glyphicon-menu-left:before {
- content: "\e257";
+
+img {
+ vertical-align: middle;
+ border-style: none;
}
-.glyphicon-menu-right:before {
- content: "\e258";
+
+svg:not(:root) {
+ overflow: hidden;
}
-.glyphicon-menu-down:before {
- content: "\e259";
+
+a,
+area,
+button,
+[role="button"],
+input,
+label,
+select,
+summary,
+textarea {
+ -ms-touch-action: manipulation;
+ touch-action: manipulation;
}
-.glyphicon-menu-up:before {
- content: "\e260";
+
+table {
+ border-collapse: collapse;
}
-* {
- -webkit-box-sizing: border-box;
- -moz-box-sizing: border-box;
- box-sizing: border-box;
+
+caption {
+ padding-top: 0.75rem;
+ padding-bottom: 0.75rem;
+ color: #868e96;
+ text-align: left;
+ caption-side: bottom;
}
-*:before,
-*:after {
- -webkit-box-sizing: border-box;
- -moz-box-sizing: border-box;
- box-sizing: border-box;
+
+th {
+ text-align: left;
}
-html {
- font-size: 10px;
- -webkit-tap-highlight-color: rgba(0, 0, 0, 0);
+label {
+ display: inline-block;
+ margin-bottom: .5rem;
}
-body {
- font-family: "Helvetica Neue", Helvetica, Arial, sans-serif;
- font-size: 14px;
- line-height: 1.42857143;
- color: #333;
- background-color: #fff;
+
+button:focus {
+ outline: 1px dotted;
+ outline: 5px auto -webkit-focus-ring-color;
}
+
input,
button,
select,
+optgroup,
textarea {
+ margin: 0;
font-family: inherit;
font-size: inherit;
line-height: inherit;
}
-a {
- color: #337ab7;
- text-decoration: none;
+
+button,
+input {
+ overflow: visible;
}
-a:hover,
-a:focus {
- color: #23527c;
- text-decoration: underline;
+
+button,
+select {
+ text-transform: none;
}
-a:focus {
- outline: 5px auto -webkit-focus-ring-color;
- outline-offset: -2px;
+
+button,
+html [type="button"],
+[type="reset"],
+[type="submit"] {
+ -webkit-appearance: button;
}
-figure {
- margin: 0;
+
+button::-moz-focus-inner,
+[type="button"]::-moz-focus-inner,
+[type="reset"]::-moz-focus-inner,
+[type="submit"]::-moz-focus-inner {
+ padding: 0;
+ border-style: none;
}
-img {
- vertical-align: middle;
+
+input[type="radio"],
+input[type="checkbox"] {
+ box-sizing: border-box;
+ padding: 0;
+}
+
+input[type="date"],
+input[type="time"],
+input[type="datetime-local"],
+input[type="month"] {
+ -webkit-appearance: listbox;
}
-.img-responsive,
-.thumbnail > img,
-.thumbnail a > img,
-.carousel-inner > .item > img,
-.carousel-inner > .item > a > img {
+
+textarea {
+ overflow: auto;
+ resize: vertical;
+}
+
+fieldset {
+ min-width: 0;
+ padding: 0;
+ margin: 0;
+ border: 0;
+}
+
+legend {
display: block;
+ width: 100%;
max-width: 100%;
- height: auto;
+ padding: 0;
+ margin-bottom: .5rem;
+ font-size: 1.5rem;
+ line-height: inherit;
+ color: inherit;
+ white-space: normal;
}
-.img-rounded {
- border-radius: 6px;
+
+progress {
+ vertical-align: baseline;
}
-.img-thumbnail {
- display: inline-block;
- max-width: 100%;
+
+[type="number"]::-webkit-inner-spin-button,
+[type="number"]::-webkit-outer-spin-button {
height: auto;
- padding: 4px;
- line-height: 1.42857143;
- background-color: #fff;
- border: 1px solid #ddd;
- border-radius: 4px;
- -webkit-transition: all .2s ease-in-out;
- -o-transition: all .2s ease-in-out;
- transition: all .2s ease-in-out;
}
-.img-circle {
- border-radius: 50%;
+
+[type="search"] {
+ outline-offset: -2px;
+ -webkit-appearance: none;
}
-hr {
- margin-top: 20px;
- margin-bottom: 20px;
- border: 0;
- border-top: 1px solid #eee;
+
+[type="search"]::-webkit-search-cancel-button,
+[type="search"]::-webkit-search-decoration {
+ -webkit-appearance: none;
}
-.sr-only {
- position: absolute;
- width: 1px;
- height: 1px;
- padding: 0;
- margin: -1px;
- overflow: hidden;
- clip: rect(0, 0, 0, 0);
- border: 0;
+
+::-webkit-file-upload-button {
+ font: inherit;
+ -webkit-appearance: button;
}
-.sr-only-focusable:active,
-.sr-only-focusable:focus {
- position: static;
- width: auto;
- height: auto;
- margin: 0;
- overflow: visible;
- clip: auto;
+
+output {
+ display: inline-block;
+}
+
+summary {
+ display: list-item;
}
-[role="button"] {
- cursor: pointer;
-}
-h1,
-h2,
-h3,
-h4,
-h5,
-h6,
-.h1,
-.h2,
-.h3,
-.h4,
-.h5,
-.h6 {
+
+template {
+ display: none;
+}
+
+[hidden] {
+ display: none !important;
+}
+
+h1, h2, h3, h4, h5, h6,
+.h1, .h2, .h3, .h4, .h5, .h6 {
+ margin-bottom: 0.5rem;
font-family: inherit;
font-weight: 500;
line-height: 1.1;
color: inherit;
}
-h1 small,
-h2 small,
-h3 small,
-h4 small,
-h5 small,
-h6 small,
-.h1 small,
-.h2 small,
-.h3 small,
-.h4 small,
-.h5 small,
-.h6 small,
-h1 .small,
-h2 .small,
-h3 .small,
-h4 .small,
-h5 .small,
-h6 .small,
-.h1 .small,
-.h2 .small,
-.h3 .small,
-.h4 .small,
-.h5 .small,
-.h6 .small {
- font-weight: normal;
- line-height: 1;
- color: #777;
-}
-h1,
-.h1,
-h2,
-.h2,
-h3,
-.h3 {
- margin-top: 20px;
- margin-bottom: 10px;
+
+h1, .h1 {
+ font-size: 2.5rem;
}
-h1 small,
-.h1 small,
-h2 small,
-.h2 small,
-h3 small,
-.h3 small,
-h1 .small,
-.h1 .small,
-h2 .small,
-.h2 .small,
-h3 .small,
-.h3 .small {
- font-size: 65%;
-}
-h4,
-.h4,
-h5,
-.h5,
-h6,
-.h6 {
- margin-top: 10px;
- margin-bottom: 10px;
+
+h2, .h2 {
+ font-size: 2rem;
}
-h4 small,
-.h4 small,
-h5 small,
-.h5 small,
-h6 small,
-.h6 small,
-h4 .small,
-.h4 .small,
-h5 .small,
-.h5 .small,
-h6 .small,
-.h6 .small {
- font-size: 75%;
+
+h3, .h3 {
+ font-size: 1.75rem;
}
-h1,
-.h1 {
- font-size: 36px;
+
+h4, .h4 {
+ font-size: 1.5rem;
}
-h2,
-.h2 {
- font-size: 30px;
+
+h5, .h5 {
+ font-size: 1.25rem;
}
-h3,
-.h3 {
- font-size: 24px;
+
+h6, .h6 {
+ font-size: 1rem;
}
-h4,
-.h4 {
- font-size: 18px;
+
+.lead {
+ font-size: 1.25rem;
+ font-weight: 300;
}
-h5,
-.h5 {
- font-size: 14px;
+
+.display-1 {
+ font-size: 6rem;
+ font-weight: 300;
+ line-height: 1.1;
}
-h6,
-.h6 {
- font-size: 12px;
+
+.display-2 {
+ font-size: 5.5rem;
+ font-weight: 300;
+ line-height: 1.1;
}
-p {
- margin: 0 0 10px;
+
+.display-3 {
+ font-size: 4.5rem;
+ font-weight: 300;
+ line-height: 1.1;
}
-.lead {
- margin-bottom: 20px;
- font-size: 16px;
+
+.display-4 {
+ font-size: 3.5rem;
font-weight: 300;
- line-height: 1.4;
+ line-height: 1.1;
}
-@media (min-width: 768px) {
- .lead {
- font-size: 21px;
- }
+
+hr {
+ margin-top: 1rem;
+ margin-bottom: 1rem;
+ border: 0;
+ border-top: 1px solid rgba(0, 0, 0, 0.1);
}
+
small,
.small {
- font-size: 85%;
+ font-size: 80%;
+ font-weight: normal;
}
+
mark,
.mark {
- padding: .2em;
- background-color: #fcf8e3;
-}
-.text-left {
- text-align: left;
-}
-.text-right {
- text-align: right;
-}
-.text-center {
- text-align: center;
-}
-.text-justify {
- text-align: justify;
-}
-.text-nowrap {
- white-space: nowrap;
-}
-.text-lowercase {
- text-transform: lowercase;
-}
-.text-uppercase {
- text-transform: uppercase;
-}
-.text-capitalize {
- text-transform: capitalize;
-}
-.text-muted {
- color: #777;
-}
-.text-primary {
- color: #337ab7;
-}
-a.text-primary:hover,
-a.text-primary:focus {
- color: #286090;
-}
-.text-success {
- color: #3c763d;
-}
-a.text-success:hover,
-a.text-success:focus {
- color: #2b542c;
-}
-.text-info {
- color: #31708f;
-}
-a.text-info:hover,
-a.text-info:focus {
- color: #245269;
-}
-.text-warning {
- color: #8a6d3b;
-}
-a.text-warning:hover,
-a.text-warning:focus {
- color: #66512c;
-}
-.text-danger {
- color: #a94442;
-}
-a.text-danger:hover,
-a.text-danger:focus {
- color: #843534;
-}
-.bg-primary {
- color: #fff;
- background-color: #337ab7;
-}
-a.bg-primary:hover,
-a.bg-primary:focus {
- background-color: #286090;
-}
-.bg-success {
- background-color: #dff0d8;
-}
-a.bg-success:hover,
-a.bg-success:focus {
- background-color: #c1e2b3;
-}
-.bg-info {
- background-color: #d9edf7;
-}
-a.bg-info:hover,
-a.bg-info:focus {
- background-color: #afd9ee;
-}
-.bg-warning {
+ padding: 0.2em;
background-color: #fcf8e3;
}
-a.bg-warning:hover,
-a.bg-warning:focus {
- background-color: #f7ecb5;
-}
-.bg-danger {
- background-color: #f2dede;
-}
-a.bg-danger:hover,
-a.bg-danger:focus {
- background-color: #e4b9b9;
-}
-.page-header {
- padding-bottom: 9px;
- margin: 40px 0 20px;
- border-bottom: 1px solid #eee;
-}
-ul,
-ol {
- margin-top: 0;
- margin-bottom: 10px;
-}
-ul ul,
-ol ul,
-ul ol,
-ol ol {
- margin-bottom: 0;
-}
+
.list-unstyled {
padding-left: 0;
list-style: none;
}
+
.list-inline {
padding-left: 0;
- margin-left: -5px;
list-style: none;
}
-.list-inline > li {
+
+.list-inline-item {
display: inline-block;
- padding-right: 5px;
- padding-left: 5px;
}
-dl {
- margin-top: 0;
- margin-bottom: 20px;
-}
-dt,
-dd {
- line-height: 1.42857143;
-}
-dt {
- font-weight: bold;
-}
-dd {
- margin-left: 0;
-}
-@media (min-width: 768px) {
- .dl-horizontal dt {
- float: left;
- width: 160px;
- overflow: hidden;
- clear: left;
- text-align: right;
- text-overflow: ellipsis;
- white-space: nowrap;
- }
- .dl-horizontal dd {
- margin-left: 180px;
- }
-}
-abbr[title],
-abbr[data-original-title] {
- cursor: help;
- border-bottom: 1px dotted #777;
+
+.list-inline-item:not(:last-child) {
+ margin-right: 5px;
}
+
.initialism {
font-size: 90%;
text-transform: uppercase;
}
-blockquote {
- padding: 10px 20px;
- margin: 0 0 20px;
- font-size: 17.5px;
- border-left: 5px solid #eee;
-}
-blockquote p:last-child,
-blockquote ul:last-child,
-blockquote ol:last-child {
- margin-bottom: 0;
+
+.blockquote {
+ margin-bottom: 1rem;
+ font-size: 1.25rem;
}
-blockquote footer,
-blockquote small,
-blockquote .small {
+
+.blockquote-footer {
display: block;
font-size: 80%;
- line-height: 1.42857143;
- color: #777;
+ color: #868e96;
}
-blockquote footer:before,
-blockquote small:before,
-blockquote .small:before {
- content: '\2014 \00A0';
+
+.blockquote-footer::before {
+ content: "\2014 \00A0";
}
-.blockquote-reverse,
-blockquote.pull-right {
- padding-right: 15px;
- padding-left: 0;
- text-align: right;
- border-right: 5px solid #eee;
- border-left: 0;
+
+.img-fluid {
+ max-width: 100%;
+ height: auto;
}
-.blockquote-reverse footer:before,
-blockquote.pull-right footer:before,
-.blockquote-reverse small:before,
-blockquote.pull-right small:before,
-.blockquote-reverse .small:before,
-blockquote.pull-right .small:before {
- content: '';
-}
-.blockquote-reverse footer:after,
-blockquote.pull-right footer:after,
-.blockquote-reverse small:after,
-blockquote.pull-right small:after,
-.blockquote-reverse .small:after,
-blockquote.pull-right .small:after {
- content: '\00A0 \2014';
+
+.img-thumbnail {
+ padding: 0.25rem;
+ background-color: #fff;
+ border: 1px solid #ddd;
+ border-radius: 0.25rem;
+ transition: all 0.2s ease-in-out;
+ max-width: 100%;
+ height: auto;
}
-address {
- margin-bottom: 20px;
- font-style: normal;
- line-height: 1.42857143;
+
+.figure {
+ display: inline-block;
}
+
+.figure-img {
+ margin-bottom: 0.5rem;
+ line-height: 1;
+}
+
+.figure-caption {
+ font-size: 90%;
+ color: #868e96;
+}
+
code,
kbd,
pre,
samp {
- font-family: Menlo, Monaco, Consolas, "Courier New", monospace;
+ font-family: Menlo, Monaco, Consolas, "Liberation Mono", "Courier New", monospace;
}
+
code {
- padding: 2px 4px;
+ padding: 0.2rem 0.4rem;
font-size: 90%;
- color: #c7254e;
- background-color: #f9f2f4;
- border-radius: 4px;
+ color: #bd4147;
+ background-color: #f8f9fa;
+ border-radius: 0.25rem;
}
+
+a > code {
+ padding: 0;
+ color: inherit;
+ background-color: inherit;
+}
+
kbd {
- padding: 2px 4px;
+ padding: 0.2rem 0.4rem;
font-size: 90%;
color: #fff;
- background-color: #333;
- border-radius: 3px;
- -webkit-box-shadow: inset 0 -1px 0 rgba(0, 0, 0, .25);
- box-shadow: inset 0 -1px 0 rgba(0, 0, 0, .25);
+ background-color: #212529;
+ border-radius: 0.2rem;
}
+
kbd kbd {
padding: 0;
font-size: 100%;
font-weight: bold;
- -webkit-box-shadow: none;
- box-shadow: none;
}
+
pre {
display: block;
- padding: 9.5px;
- margin: 0 0 10px;
- font-size: 13px;
- line-height: 1.42857143;
- color: #333;
- word-break: break-all;
- word-wrap: break-word;
- background-color: #f5f5f5;
- border: 1px solid #ccc;
- border-radius: 4px;
+ margin-top: 0;
+ margin-bottom: 1rem;
+ font-size: 90%;
+ color: #212529;
}
+
pre code {
padding: 0;
font-size: inherit;
color: inherit;
- white-space: pre-wrap;
background-color: transparent;
border-radius: 0;
}
+
.pre-scrollable {
max-height: 340px;
overflow-y: scroll;
}
+
.container {
- padding-right: 15px;
- padding-left: 15px;
margin-right: auto;
margin-left: auto;
+ padding-right: 15px;
+ padding-left: 15px;
+ width: 100%;
+}
+
+@media (min-width: 576px) {
+ .container {
+ max-width: 540px;
+ }
}
+
@media (min-width: 768px) {
.container {
- width: 750px;
+ max-width: 720px;
}
}
+
@media (min-width: 992px) {
.container {
- width: 970px;
+ max-width: 960px;
}
}
+
@media (min-width: 1200px) {
.container {
- width: 1170px;
+ max-width: 1140px;
}
}
+
.container-fluid {
- padding-right: 15px;
- padding-left: 15px;
+ width: 100%;
margin-right: auto;
margin-left: auto;
+ padding-right: 15px;
+ padding-left: 15px;
+ width: 100%;
}
+
.row {
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-wrap: wrap;
+ flex-wrap: wrap;
margin-right: -15px;
margin-left: -15px;
}
-.col-xs-1, .col-sm-1, .col-md-1, .col-lg-1, .col-xs-2, .col-sm-2, .col-md-2, .col-lg-2, .col-xs-3, .col-sm-3, .col-md-3, .col-lg-3, .col-xs-4, .col-sm-4, .col-md-4, .col-lg-4, .col-xs-5, .col-sm-5, .col-md-5, .col-lg-5, .col-xs-6, .col-sm-6, .col-md-6, .col-lg-6, .col-xs-7, .col-sm-7, .col-md-7, .col-lg-7, .col-xs-8, .col-sm-8, .col-md-8, .col-lg-8, .col-xs-9, .col-sm-9, .col-md-9, .col-lg-9, .col-xs-10, .col-sm-10, .col-md-10, .col-lg-10, .col-xs-11, .col-sm-11, .col-md-11, .col-lg-11, .col-xs-12, .col-sm-12, .col-md-12, .col-lg-12 {
+
+.no-gutters {
+ margin-right: 0;
+ margin-left: 0;
+}
+
+.no-gutters > .col,
+.no-gutters > [class*="col-"] {
+ padding-right: 0;
+ padding-left: 0;
+}
+
+.col-1, .col-2, .col-3, .col-4, .col-5, .col-6, .col-7, .col-8, .col-9, .col-10, .col-11, .col-12, .col,
+.col-auto, .col-sm-1, .col-sm-2, .col-sm-3, .col-sm-4, .col-sm-5, .col-sm-6, .col-sm-7, .col-sm-8, .col-sm-9, .col-sm-10, .col-sm-11, .col-sm-12, .col-sm,
+.col-sm-auto, .col-md-1, .col-md-2, .col-md-3, .col-md-4, .col-md-5, .col-md-6, .col-md-7, .col-md-8, .col-md-9, .col-md-10, .col-md-11, .col-md-12, .col-md,
+.col-md-auto, .col-lg-1, .col-lg-2, .col-lg-3, .col-lg-4, .col-lg-5, .col-lg-6, .col-lg-7, .col-lg-8, .col-lg-9, .col-lg-10, .col-lg-11, .col-lg-12, .col-lg,
+.col-lg-auto, .col-xl-1, .col-xl-2, .col-xl-3, .col-xl-4, .col-xl-5, .col-xl-6, .col-xl-7, .col-xl-8, .col-xl-9, .col-xl-10, .col-xl-11, .col-xl-12, .col-xl,
+.col-xl-auto {
position: relative;
+ width: 100%;
min-height: 1px;
padding-right: 15px;
padding-left: 15px;
}
-.col-xs-1, .col-xs-2, .col-xs-3, .col-xs-4, .col-xs-5, .col-xs-6, .col-xs-7, .col-xs-8, .col-xs-9, .col-xs-10, .col-xs-11, .col-xs-12 {
- float: left;
-}
-.col-xs-12 {
- width: 100%;
-}
-.col-xs-11 {
- width: 91.66666667%;
-}
-.col-xs-10 {
- width: 83.33333333%;
-}
-.col-xs-9 {
- width: 75%;
-}
-.col-xs-8 {
- width: 66.66666667%;
-}
-.col-xs-7 {
- width: 58.33333333%;
-}
-.col-xs-6 {
- width: 50%;
-}
-.col-xs-5 {
- width: 41.66666667%;
-}
-.col-xs-4 {
- width: 33.33333333%;
-}
-.col-xs-3 {
- width: 25%;
-}
-.col-xs-2 {
- width: 16.66666667%;
-}
-.col-xs-1 {
- width: 8.33333333%;
-}
-.col-xs-pull-12 {
- right: 100%;
-}
-.col-xs-pull-11 {
- right: 91.66666667%;
-}
-.col-xs-pull-10 {
- right: 83.33333333%;
-}
-.col-xs-pull-9 {
- right: 75%;
-}
-.col-xs-pull-8 {
- right: 66.66666667%;
-}
-.col-xs-pull-7 {
- right: 58.33333333%;
-}
-.col-xs-pull-6 {
- right: 50%;
-}
-.col-xs-pull-5 {
- right: 41.66666667%;
-}
-.col-xs-pull-4 {
- right: 33.33333333%;
-}
-.col-xs-pull-3 {
- right: 25%;
-}
-.col-xs-pull-2 {
- right: 16.66666667%;
-}
-.col-xs-pull-1 {
- right: 8.33333333%;
-}
-.col-xs-pull-0 {
- right: auto;
-}
-.col-xs-push-12 {
- left: 100%;
+
+.col {
+ -ms-flex-preferred-size: 0;
+ flex-basis: 0;
+ -ms-flex-positive: 1;
+ flex-grow: 1;
+ max-width: 100%;
}
-.col-xs-push-11 {
- left: 91.66666667%;
+
+.col-auto {
+ -ms-flex: 0 0 auto;
+ flex: 0 0 auto;
+ width: auto;
+ max-width: none;
}
-.col-xs-push-10 {
- left: 83.33333333%;
+
+.col-1 {
+ -ms-flex: 0 0 8.333333%;
+ flex: 0 0 8.333333%;
+ max-width: 8.333333%;
}
-.col-xs-push-9 {
- left: 75%;
+
+.col-2 {
+ -ms-flex: 0 0 16.666667%;
+ flex: 0 0 16.666667%;
+ max-width: 16.666667%;
}
-.col-xs-push-8 {
- left: 66.66666667%;
+
+.col-3 {
+ -ms-flex: 0 0 25%;
+ flex: 0 0 25%;
+ max-width: 25%;
}
-.col-xs-push-7 {
- left: 58.33333333%;
+
+.col-4 {
+ -ms-flex: 0 0 33.333333%;
+ flex: 0 0 33.333333%;
+ max-width: 33.333333%;
}
-.col-xs-push-6 {
- left: 50%;
+
+.col-5 {
+ -ms-flex: 0 0 41.666667%;
+ flex: 0 0 41.666667%;
+ max-width: 41.666667%;
}
-.col-xs-push-5 {
- left: 41.66666667%;
+
+.col-6 {
+ -ms-flex: 0 0 50%;
+ flex: 0 0 50%;
+ max-width: 50%;
}
-.col-xs-push-4 {
- left: 33.33333333%;
+
+.col-7 {
+ -ms-flex: 0 0 58.333333%;
+ flex: 0 0 58.333333%;
+ max-width: 58.333333%;
}
-.col-xs-push-3 {
- left: 25%;
+
+.col-8 {
+ -ms-flex: 0 0 66.666667%;
+ flex: 0 0 66.666667%;
+ max-width: 66.666667%;
}
-.col-xs-push-2 {
- left: 16.66666667%;
+
+.col-9 {
+ -ms-flex: 0 0 75%;
+ flex: 0 0 75%;
+ max-width: 75%;
}
-.col-xs-push-1 {
- left: 8.33333333%;
+
+.col-10 {
+ -ms-flex: 0 0 83.333333%;
+ flex: 0 0 83.333333%;
+ max-width: 83.333333%;
}
-.col-xs-push-0 {
- left: auto;
+
+.col-11 {
+ -ms-flex: 0 0 91.666667%;
+ flex: 0 0 91.666667%;
+ max-width: 91.666667%;
}
-.col-xs-offset-12 {
- margin-left: 100%;
+
+.col-12 {
+ -ms-flex: 0 0 100%;
+ flex: 0 0 100%;
+ max-width: 100%;
}
-.col-xs-offset-11 {
- margin-left: 91.66666667%;
+
+.order-1 {
+ -ms-flex-order: 1;
+ order: 1;
}
-.col-xs-offset-10 {
- margin-left: 83.33333333%;
+
+.order-2 {
+ -ms-flex-order: 2;
+ order: 2;
}
-.col-xs-offset-9 {
- margin-left: 75%;
+
+.order-3 {
+ -ms-flex-order: 3;
+ order: 3;
}
-.col-xs-offset-8 {
- margin-left: 66.66666667%;
+
+.order-4 {
+ -ms-flex-order: 4;
+ order: 4;
}
-.col-xs-offset-7 {
- margin-left: 58.33333333%;
+
+.order-5 {
+ -ms-flex-order: 5;
+ order: 5;
}
-.col-xs-offset-6 {
- margin-left: 50%;
+
+.order-6 {
+ -ms-flex-order: 6;
+ order: 6;
}
-.col-xs-offset-5 {
- margin-left: 41.66666667%;
+
+.order-7 {
+ -ms-flex-order: 7;
+ order: 7;
}
-.col-xs-offset-4 {
- margin-left: 33.33333333%;
+
+.order-8 {
+ -ms-flex-order: 8;
+ order: 8;
}
-.col-xs-offset-3 {
- margin-left: 25%;
+
+.order-9 {
+ -ms-flex-order: 9;
+ order: 9;
}
-.col-xs-offset-2 {
- margin-left: 16.66666667%;
+
+.order-10 {
+ -ms-flex-order: 10;
+ order: 10;
}
-.col-xs-offset-1 {
- margin-left: 8.33333333%;
+
+.order-11 {
+ -ms-flex-order: 11;
+ order: 11;
}
-.col-xs-offset-0 {
- margin-left: 0;
+
+.order-12 {
+ -ms-flex-order: 12;
+ order: 12;
}
-@media (min-width: 768px) {
- .col-sm-1, .col-sm-2, .col-sm-3, .col-sm-4, .col-sm-5, .col-sm-6, .col-sm-7, .col-sm-8, .col-sm-9, .col-sm-10, .col-sm-11, .col-sm-12 {
- float: left;
- }
- .col-sm-12 {
- width: 100%;
- }
- .col-sm-11 {
- width: 91.66666667%;
- }
- .col-sm-10 {
- width: 83.33333333%;
- }
- .col-sm-9 {
- width: 75%;
- }
- .col-sm-8 {
- width: 66.66666667%;
- }
- .col-sm-7 {
- width: 58.33333333%;
- }
- .col-sm-6 {
- width: 50%;
- }
- .col-sm-5 {
- width: 41.66666667%;
- }
- .col-sm-4 {
- width: 33.33333333%;
- }
- .col-sm-3 {
- width: 25%;
- }
- .col-sm-2 {
- width: 16.66666667%;
+
+@media (min-width: 576px) {
+ .col-sm {
+ -ms-flex-preferred-size: 0;
+ flex-basis: 0;
+ -ms-flex-positive: 1;
+ flex-grow: 1;
+ max-width: 100%;
+ }
+ .col-sm-auto {
+ -ms-flex: 0 0 auto;
+ flex: 0 0 auto;
+ width: auto;
+ max-width: none;
}
.col-sm-1 {
- width: 8.33333333%;
- }
- .col-sm-pull-12 {
- right: 100%;
- }
- .col-sm-pull-11 {
- right: 91.66666667%;
- }
- .col-sm-pull-10 {
- right: 83.33333333%;
- }
- .col-sm-pull-9 {
- right: 75%;
- }
- .col-sm-pull-8 {
- right: 66.66666667%;
- }
- .col-sm-pull-7 {
- right: 58.33333333%;
- }
- .col-sm-pull-6 {
- right: 50%;
- }
- .col-sm-pull-5 {
- right: 41.66666667%;
- }
- .col-sm-pull-4 {
- right: 33.33333333%;
+ -ms-flex: 0 0 8.333333%;
+ flex: 0 0 8.333333%;
+ max-width: 8.333333%;
}
- .col-sm-pull-3 {
- right: 25%;
- }
- .col-sm-pull-2 {
- right: 16.66666667%;
- }
- .col-sm-pull-1 {
- right: 8.33333333%;
- }
- .col-sm-pull-0 {
- right: auto;
- }
- .col-sm-push-12 {
- left: 100%;
- }
- .col-sm-push-11 {
- left: 91.66666667%;
- }
- .col-sm-push-10 {
- left: 83.33333333%;
- }
- .col-sm-push-9 {
- left: 75%;
+ .col-sm-2 {
+ -ms-flex: 0 0 16.666667%;
+ flex: 0 0 16.666667%;
+ max-width: 16.666667%;
}
- .col-sm-push-8 {
- left: 66.66666667%;
+ .col-sm-3 {
+ -ms-flex: 0 0 25%;
+ flex: 0 0 25%;
+ max-width: 25%;
}
- .col-sm-push-7 {
- left: 58.33333333%;
+ .col-sm-4 {
+ -ms-flex: 0 0 33.333333%;
+ flex: 0 0 33.333333%;
+ max-width: 33.333333%;
}
- .col-sm-push-6 {
- left: 50%;
+ .col-sm-5 {
+ -ms-flex: 0 0 41.666667%;
+ flex: 0 0 41.666667%;
+ max-width: 41.666667%;
}
- .col-sm-push-5 {
- left: 41.66666667%;
+ .col-sm-6 {
+ -ms-flex: 0 0 50%;
+ flex: 0 0 50%;
+ max-width: 50%;
}
- .col-sm-push-4 {
- left: 33.33333333%;
+ .col-sm-7 {
+ -ms-flex: 0 0 58.333333%;
+ flex: 0 0 58.333333%;
+ max-width: 58.333333%;
}
- .col-sm-push-3 {
- left: 25%;
+ .col-sm-8 {
+ -ms-flex: 0 0 66.666667%;
+ flex: 0 0 66.666667%;
+ max-width: 66.666667%;
}
- .col-sm-push-2 {
- left: 16.66666667%;
+ .col-sm-9 {
+ -ms-flex: 0 0 75%;
+ flex: 0 0 75%;
+ max-width: 75%;
}
- .col-sm-push-1 {
- left: 8.33333333%;
+ .col-sm-10 {
+ -ms-flex: 0 0 83.333333%;
+ flex: 0 0 83.333333%;
+ max-width: 83.333333%;
}
- .col-sm-push-0 {
- left: auto;
+ .col-sm-11 {
+ -ms-flex: 0 0 91.666667%;
+ flex: 0 0 91.666667%;
+ max-width: 91.666667%;
}
- .col-sm-offset-12 {
- margin-left: 100%;
+ .col-sm-12 {
+ -ms-flex: 0 0 100%;
+ flex: 0 0 100%;
+ max-width: 100%;
}
- .col-sm-offset-11 {
- margin-left: 91.66666667%;
+ .order-sm-1 {
+ -ms-flex-order: 1;
+ order: 1;
}
- .col-sm-offset-10 {
- margin-left: 83.33333333%;
+ .order-sm-2 {
+ -ms-flex-order: 2;
+ order: 2;
}
- .col-sm-offset-9 {
- margin-left: 75%;
+ .order-sm-3 {
+ -ms-flex-order: 3;
+ order: 3;
}
- .col-sm-offset-8 {
- margin-left: 66.66666667%;
+ .order-sm-4 {
+ -ms-flex-order: 4;
+ order: 4;
}
- .col-sm-offset-7 {
- margin-left: 58.33333333%;
+ .order-sm-5 {
+ -ms-flex-order: 5;
+ order: 5;
}
- .col-sm-offset-6 {
- margin-left: 50%;
+ .order-sm-6 {
+ -ms-flex-order: 6;
+ order: 6;
}
- .col-sm-offset-5 {
- margin-left: 41.66666667%;
+ .order-sm-7 {
+ -ms-flex-order: 7;
+ order: 7;
}
- .col-sm-offset-4 {
- margin-left: 33.33333333%;
+ .order-sm-8 {
+ -ms-flex-order: 8;
+ order: 8;
}
- .col-sm-offset-3 {
- margin-left: 25%;
+ .order-sm-9 {
+ -ms-flex-order: 9;
+ order: 9;
}
- .col-sm-offset-2 {
- margin-left: 16.66666667%;
+ .order-sm-10 {
+ -ms-flex-order: 10;
+ order: 10;
}
- .col-sm-offset-1 {
- margin-left: 8.33333333%;
+ .order-sm-11 {
+ -ms-flex-order: 11;
+ order: 11;
}
- .col-sm-offset-0 {
- margin-left: 0;
+ .order-sm-12 {
+ -ms-flex-order: 12;
+ order: 12;
}
}
-@media (min-width: 992px) {
- .col-md-1, .col-md-2, .col-md-3, .col-md-4, .col-md-5, .col-md-6, .col-md-7, .col-md-8, .col-md-9, .col-md-10, .col-md-11, .col-md-12 {
- float: left;
- }
- .col-md-12 {
- width: 100%;
- }
- .col-md-11 {
- width: 91.66666667%;
- }
- .col-md-10 {
- width: 83.33333333%;
- }
- .col-md-9 {
- width: 75%;
- }
- .col-md-8 {
- width: 66.66666667%;
- }
- .col-md-7 {
- width: 58.33333333%;
- }
- .col-md-6 {
- width: 50%;
- }
- .col-md-5 {
- width: 41.66666667%;
- }
- .col-md-4 {
- width: 33.33333333%;
- }
- .col-md-3 {
- width: 25%;
- }
- .col-md-2 {
- width: 16.66666667%;
+
+@media (min-width: 768px) {
+ .col-md {
+ -ms-flex-preferred-size: 0;
+ flex-basis: 0;
+ -ms-flex-positive: 1;
+ flex-grow: 1;
+ max-width: 100%;
+ }
+ .col-md-auto {
+ -ms-flex: 0 0 auto;
+ flex: 0 0 auto;
+ width: auto;
+ max-width: none;
}
.col-md-1 {
- width: 8.33333333%;
- }
- .col-md-pull-12 {
- right: 100%;
- }
- .col-md-pull-11 {
- right: 91.66666667%;
+ -ms-flex: 0 0 8.333333%;
+ flex: 0 0 8.333333%;
+ max-width: 8.333333%;
}
- .col-md-pull-10 {
- right: 83.33333333%;
- }
- .col-md-pull-9 {
- right: 75%;
- }
- .col-md-pull-8 {
- right: 66.66666667%;
- }
- .col-md-pull-7 {
- right: 58.33333333%;
- }
- .col-md-pull-6 {
- right: 50%;
- }
- .col-md-pull-5 {
- right: 41.66666667%;
- }
- .col-md-pull-4 {
- right: 33.33333333%;
- }
- .col-md-pull-3 {
- right: 25%;
- }
- .col-md-pull-2 {
- right: 16.66666667%;
- }
- .col-md-pull-1 {
- right: 8.33333333%;
- }
- .col-md-pull-0 {
- right: auto;
- }
- .col-md-push-12 {
- left: 100%;
- }
- .col-md-push-11 {
- left: 91.66666667%;
- }
- .col-md-push-10 {
- left: 83.33333333%;
- }
- .col-md-push-9 {
- left: 75%;
+ .col-md-2 {
+ -ms-flex: 0 0 16.666667%;
+ flex: 0 0 16.666667%;
+ max-width: 16.666667%;
}
- .col-md-push-8 {
- left: 66.66666667%;
+ .col-md-3 {
+ -ms-flex: 0 0 25%;
+ flex: 0 0 25%;
+ max-width: 25%;
}
- .col-md-push-7 {
- left: 58.33333333%;
+ .col-md-4 {
+ -ms-flex: 0 0 33.333333%;
+ flex: 0 0 33.333333%;
+ max-width: 33.333333%;
}
- .col-md-push-6 {
- left: 50%;
+ .col-md-5 {
+ -ms-flex: 0 0 41.666667%;
+ flex: 0 0 41.666667%;
+ max-width: 41.666667%;
}
- .col-md-push-5 {
- left: 41.66666667%;
+ .col-md-6 {
+ -ms-flex: 0 0 50%;
+ flex: 0 0 50%;
+ max-width: 50%;
}
- .col-md-push-4 {
- left: 33.33333333%;
+ .col-md-7 {
+ -ms-flex: 0 0 58.333333%;
+ flex: 0 0 58.333333%;
+ max-width: 58.333333%;
}
- .col-md-push-3 {
- left: 25%;
+ .col-md-8 {
+ -ms-flex: 0 0 66.666667%;
+ flex: 0 0 66.666667%;
+ max-width: 66.666667%;
}
- .col-md-push-2 {
- left: 16.66666667%;
+ .col-md-9 {
+ -ms-flex: 0 0 75%;
+ flex: 0 0 75%;
+ max-width: 75%;
}
- .col-md-push-1 {
- left: 8.33333333%;
+ .col-md-10 {
+ -ms-flex: 0 0 83.333333%;
+ flex: 0 0 83.333333%;
+ max-width: 83.333333%;
}
- .col-md-push-0 {
- left: auto;
+ .col-md-11 {
+ -ms-flex: 0 0 91.666667%;
+ flex: 0 0 91.666667%;
+ max-width: 91.666667%;
}
- .col-md-offset-12 {
- margin-left: 100%;
+ .col-md-12 {
+ -ms-flex: 0 0 100%;
+ flex: 0 0 100%;
+ max-width: 100%;
}
- .col-md-offset-11 {
- margin-left: 91.66666667%;
+ .order-md-1 {
+ -ms-flex-order: 1;
+ order: 1;
}
- .col-md-offset-10 {
- margin-left: 83.33333333%;
+ .order-md-2 {
+ -ms-flex-order: 2;
+ order: 2;
}
- .col-md-offset-9 {
- margin-left: 75%;
+ .order-md-3 {
+ -ms-flex-order: 3;
+ order: 3;
}
- .col-md-offset-8 {
- margin-left: 66.66666667%;
+ .order-md-4 {
+ -ms-flex-order: 4;
+ order: 4;
}
- .col-md-offset-7 {
- margin-left: 58.33333333%;
+ .order-md-5 {
+ -ms-flex-order: 5;
+ order: 5;
}
- .col-md-offset-6 {
- margin-left: 50%;
+ .order-md-6 {
+ -ms-flex-order: 6;
+ order: 6;
}
- .col-md-offset-5 {
- margin-left: 41.66666667%;
+ .order-md-7 {
+ -ms-flex-order: 7;
+ order: 7;
}
- .col-md-offset-4 {
- margin-left: 33.33333333%;
+ .order-md-8 {
+ -ms-flex-order: 8;
+ order: 8;
}
- .col-md-offset-3 {
- margin-left: 25%;
+ .order-md-9 {
+ -ms-flex-order: 9;
+ order: 9;
}
- .col-md-offset-2 {
- margin-left: 16.66666667%;
+ .order-md-10 {
+ -ms-flex-order: 10;
+ order: 10;
}
- .col-md-offset-1 {
- margin-left: 8.33333333%;
+ .order-md-11 {
+ -ms-flex-order: 11;
+ order: 11;
}
- .col-md-offset-0 {
- margin-left: 0;
+ .order-md-12 {
+ -ms-flex-order: 12;
+ order: 12;
}
}
-@media (min-width: 1200px) {
- .col-lg-1, .col-lg-2, .col-lg-3, .col-lg-4, .col-lg-5, .col-lg-6, .col-lg-7, .col-lg-8, .col-lg-9, .col-lg-10, .col-lg-11, .col-lg-12 {
- float: left;
- }
- .col-lg-12 {
- width: 100%;
- }
- .col-lg-11 {
- width: 91.66666667%;
- }
- .col-lg-10 {
- width: 83.33333333%;
- }
- .col-lg-9 {
- width: 75%;
- }
- .col-lg-8 {
- width: 66.66666667%;
- }
- .col-lg-7 {
- width: 58.33333333%;
- }
- .col-lg-6 {
- width: 50%;
- }
- .col-lg-5 {
- width: 41.66666667%;
- }
- .col-lg-4 {
- width: 33.33333333%;
- }
- .col-lg-3 {
- width: 25%;
- }
- .col-lg-2 {
- width: 16.66666667%;
+
+@media (min-width: 992px) {
+ .col-lg {
+ -ms-flex-preferred-size: 0;
+ flex-basis: 0;
+ -ms-flex-positive: 1;
+ flex-grow: 1;
+ max-width: 100%;
+ }
+ .col-lg-auto {
+ -ms-flex: 0 0 auto;
+ flex: 0 0 auto;
+ width: auto;
+ max-width: none;
}
.col-lg-1 {
- width: 8.33333333%;
- }
- .col-lg-pull-12 {
- right: 100%;
- }
- .col-lg-pull-11 {
- right: 91.66666667%;
- }
- .col-lg-pull-10 {
- right: 83.33333333%;
- }
- .col-lg-pull-9 {
- right: 75%;
- }
- .col-lg-pull-8 {
- right: 66.66666667%;
- }
- .col-lg-pull-7 {
- right: 58.33333333%;
- }
- .col-lg-pull-6 {
- right: 50%;
- }
- .col-lg-pull-5 {
- right: 41.66666667%;
- }
- .col-lg-pull-4 {
- right: 33.33333333%;
- }
- .col-lg-pull-3 {
- right: 25%;
- }
- .col-lg-pull-2 {
- right: 16.66666667%;
+ -ms-flex: 0 0 8.333333%;
+ flex: 0 0 8.333333%;
+ max-width: 8.333333%;
}
- .col-lg-pull-1 {
- right: 8.33333333%;
- }
- .col-lg-pull-0 {
- right: auto;
- }
- .col-lg-push-12 {
- left: 100%;
- }
- .col-lg-push-11 {
- left: 91.66666667%;
- }
- .col-lg-push-10 {
- left: 83.33333333%;
- }
- .col-lg-push-9 {
- left: 75%;
+ .col-lg-2 {
+ -ms-flex: 0 0 16.666667%;
+ flex: 0 0 16.666667%;
+ max-width: 16.666667%;
}
- .col-lg-push-8 {
- left: 66.66666667%;
+ .col-lg-3 {
+ -ms-flex: 0 0 25%;
+ flex: 0 0 25%;
+ max-width: 25%;
}
- .col-lg-push-7 {
- left: 58.33333333%;
+ .col-lg-4 {
+ -ms-flex: 0 0 33.333333%;
+ flex: 0 0 33.333333%;
+ max-width: 33.333333%;
}
- .col-lg-push-6 {
- left: 50%;
+ .col-lg-5 {
+ -ms-flex: 0 0 41.666667%;
+ flex: 0 0 41.666667%;
+ max-width: 41.666667%;
}
- .col-lg-push-5 {
- left: 41.66666667%;
+ .col-lg-6 {
+ -ms-flex: 0 0 50%;
+ flex: 0 0 50%;
+ max-width: 50%;
}
- .col-lg-push-4 {
- left: 33.33333333%;
+ .col-lg-7 {
+ -ms-flex: 0 0 58.333333%;
+ flex: 0 0 58.333333%;
+ max-width: 58.333333%;
}
- .col-lg-push-3 {
- left: 25%;
+ .col-lg-8 {
+ -ms-flex: 0 0 66.666667%;
+ flex: 0 0 66.666667%;
+ max-width: 66.666667%;
}
- .col-lg-push-2 {
- left: 16.66666667%;
+ .col-lg-9 {
+ -ms-flex: 0 0 75%;
+ flex: 0 0 75%;
+ max-width: 75%;
}
- .col-lg-push-1 {
- left: 8.33333333%;
+ .col-lg-10 {
+ -ms-flex: 0 0 83.333333%;
+ flex: 0 0 83.333333%;
+ max-width: 83.333333%;
}
- .col-lg-push-0 {
- left: auto;
+ .col-lg-11 {
+ -ms-flex: 0 0 91.666667%;
+ flex: 0 0 91.666667%;
+ max-width: 91.666667%;
}
- .col-lg-offset-12 {
- margin-left: 100%;
+ .col-lg-12 {
+ -ms-flex: 0 0 100%;
+ flex: 0 0 100%;
+ max-width: 100%;
}
- .col-lg-offset-11 {
- margin-left: 91.66666667%;
+ .order-lg-1 {
+ -ms-flex-order: 1;
+ order: 1;
}
- .col-lg-offset-10 {
- margin-left: 83.33333333%;
+ .order-lg-2 {
+ -ms-flex-order: 2;
+ order: 2;
}
- .col-lg-offset-9 {
- margin-left: 75%;
+ .order-lg-3 {
+ -ms-flex-order: 3;
+ order: 3;
}
- .col-lg-offset-8 {
- margin-left: 66.66666667%;
+ .order-lg-4 {
+ -ms-flex-order: 4;
+ order: 4;
}
- .col-lg-offset-7 {
- margin-left: 58.33333333%;
+ .order-lg-5 {
+ -ms-flex-order: 5;
+ order: 5;
}
- .col-lg-offset-6 {
- margin-left: 50%;
+ .order-lg-6 {
+ -ms-flex-order: 6;
+ order: 6;
}
- .col-lg-offset-5 {
- margin-left: 41.66666667%;
+ .order-lg-7 {
+ -ms-flex-order: 7;
+ order: 7;
}
- .col-lg-offset-4 {
- margin-left: 33.33333333%;
+ .order-lg-8 {
+ -ms-flex-order: 8;
+ order: 8;
}
- .col-lg-offset-3 {
- margin-left: 25%;
+ .order-lg-9 {
+ -ms-flex-order: 9;
+ order: 9;
}
- .col-lg-offset-2 {
- margin-left: 16.66666667%;
+ .order-lg-10 {
+ -ms-flex-order: 10;
+ order: 10;
}
- .col-lg-offset-1 {
- margin-left: 8.33333333%;
+ .order-lg-11 {
+ -ms-flex-order: 11;
+ order: 11;
}
- .col-lg-offset-0 {
- margin-left: 0;
+ .order-lg-12 {
+ -ms-flex-order: 12;
+ order: 12;
}
}
-table {
- background-color: transparent;
-}
-caption {
- padding-top: 8px;
- padding-bottom: 8px;
- color: #777;
- text-align: left;
-}
-th {
- text-align: left;
+
+@media (min-width: 1200px) {
+ .col-xl {
+ -ms-flex-preferred-size: 0;
+ flex-basis: 0;
+ -ms-flex-positive: 1;
+ flex-grow: 1;
+ max-width: 100%;
+ }
+ .col-xl-auto {
+ -ms-flex: 0 0 auto;
+ flex: 0 0 auto;
+ width: auto;
+ max-width: none;
+ }
+ .col-xl-1 {
+ -ms-flex: 0 0 8.333333%;
+ flex: 0 0 8.333333%;
+ max-width: 8.333333%;
+ }
+ .col-xl-2 {
+ -ms-flex: 0 0 16.666667%;
+ flex: 0 0 16.666667%;
+ max-width: 16.666667%;
+ }
+ .col-xl-3 {
+ -ms-flex: 0 0 25%;
+ flex: 0 0 25%;
+ max-width: 25%;
+ }
+ .col-xl-4 {
+ -ms-flex: 0 0 33.333333%;
+ flex: 0 0 33.333333%;
+ max-width: 33.333333%;
+ }
+ .col-xl-5 {
+ -ms-flex: 0 0 41.666667%;
+ flex: 0 0 41.666667%;
+ max-width: 41.666667%;
+ }
+ .col-xl-6 {
+ -ms-flex: 0 0 50%;
+ flex: 0 0 50%;
+ max-width: 50%;
+ }
+ .col-xl-7 {
+ -ms-flex: 0 0 58.333333%;
+ flex: 0 0 58.333333%;
+ max-width: 58.333333%;
+ }
+ .col-xl-8 {
+ -ms-flex: 0 0 66.666667%;
+ flex: 0 0 66.666667%;
+ max-width: 66.666667%;
+ }
+ .col-xl-9 {
+ -ms-flex: 0 0 75%;
+ flex: 0 0 75%;
+ max-width: 75%;
+ }
+ .col-xl-10 {
+ -ms-flex: 0 0 83.333333%;
+ flex: 0 0 83.333333%;
+ max-width: 83.333333%;
+ }
+ .col-xl-11 {
+ -ms-flex: 0 0 91.666667%;
+ flex: 0 0 91.666667%;
+ max-width: 91.666667%;
+ }
+ .col-xl-12 {
+ -ms-flex: 0 0 100%;
+ flex: 0 0 100%;
+ max-width: 100%;
+ }
+ .order-xl-1 {
+ -ms-flex-order: 1;
+ order: 1;
+ }
+ .order-xl-2 {
+ -ms-flex-order: 2;
+ order: 2;
+ }
+ .order-xl-3 {
+ -ms-flex-order: 3;
+ order: 3;
+ }
+ .order-xl-4 {
+ -ms-flex-order: 4;
+ order: 4;
+ }
+ .order-xl-5 {
+ -ms-flex-order: 5;
+ order: 5;
+ }
+ .order-xl-6 {
+ -ms-flex-order: 6;
+ order: 6;
+ }
+ .order-xl-7 {
+ -ms-flex-order: 7;
+ order: 7;
+ }
+ .order-xl-8 {
+ -ms-flex-order: 8;
+ order: 8;
+ }
+ .order-xl-9 {
+ -ms-flex-order: 9;
+ order: 9;
+ }
+ .order-xl-10 {
+ -ms-flex-order: 10;
+ order: 10;
+ }
+ .order-xl-11 {
+ -ms-flex-order: 11;
+ order: 11;
+ }
+ .order-xl-12 {
+ -ms-flex-order: 12;
+ order: 12;
+ }
}
+
.table {
width: 100%;
max-width: 100%;
- margin-bottom: 20px;
-}
-.table > thead > tr > th,
-.table > tbody > tr > th,
-.table > tfoot > tr > th,
-.table > thead > tr > td,
-.table > tbody > tr > td,
-.table > tfoot > tr > td {
- padding: 8px;
- line-height: 1.42857143;
+ margin-bottom: 1rem;
+ background-color: transparent;
+}
+
+.table th,
+.table td {
+ padding: 0.75rem;
vertical-align: top;
- border-top: 1px solid #ddd;
+ border-top: 1px solid #e9ecef;
}
-.table > thead > tr > th {
+
+.table thead th {
vertical-align: bottom;
- border-bottom: 2px solid #ddd;
-}
-.table > caption + thead > tr:first-child > th,
-.table > colgroup + thead > tr:first-child > th,
-.table > thead:first-child > tr:first-child > th,
-.table > caption + thead > tr:first-child > td,
-.table > colgroup + thead > tr:first-child > td,
-.table > thead:first-child > tr:first-child > td {
- border-top: 0;
+ border-bottom: 2px solid #e9ecef;
}
-.table > tbody + tbody {
- border-top: 2px solid #ddd;
+
+.table tbody + tbody {
+ border-top: 2px solid #e9ecef;
}
+
.table .table {
background-color: #fff;
}
-.table-condensed > thead > tr > th,
-.table-condensed > tbody > tr > th,
-.table-condensed > tfoot > tr > th,
-.table-condensed > thead > tr > td,
-.table-condensed > tbody > tr > td,
-.table-condensed > tfoot > tr > td {
- padding: 5px;
+
+.table-sm th,
+.table-sm td {
+ padding: 0.3rem;
}
+
.table-bordered {
- border: 1px solid #ddd;
+ border: 1px solid #e9ecef;
}
-.table-bordered > thead > tr > th,
-.table-bordered > tbody > tr > th,
-.table-bordered > tfoot > tr > th,
-.table-bordered > thead > tr > td,
-.table-bordered > tbody > tr > td,
-.table-bordered > tfoot > tr > td {
- border: 1px solid #ddd;
+
+.table-bordered th,
+.table-bordered td {
+ border: 1px solid #e9ecef;
}
-.table-bordered > thead > tr > th,
-.table-bordered > thead > tr > td {
+
+.table-bordered thead th,
+.table-bordered thead td {
border-bottom-width: 2px;
}
-.table-striped > tbody > tr:nth-of-type(odd) {
- background-color: #f9f9f9;
+
+.table-striped tbody tr:nth-of-type(odd) {
+ background-color: rgba(0, 0, 0, 0.05);
}
-.table-hover > tbody > tr:hover {
- background-color: #f5f5f5;
+
+.table-hover tbody tr:hover {
+ background-color: rgba(0, 0, 0, 0.075);
}
-table col[class*="col-"] {
- position: static;
- display: table-column;
- float: none;
+
+.table-primary,
+.table-primary > th,
+.table-primary > td {
+ background-color: #b8daff;
}
-table td[class*="col-"],
-table th[class*="col-"] {
- position: static;
- display: table-cell;
- float: none;
+
+.table-hover .table-primary:hover {
+ background-color: #9fcdff;
}
-.table > thead > tr > td.active,
-.table > tbody > tr > td.active,
-.table > tfoot > tr > td.active,
-.table > thead > tr > th.active,
-.table > tbody > tr > th.active,
-.table > tfoot > tr > th.active,
-.table > thead > tr.active > td,
-.table > tbody > tr.active > td,
-.table > tfoot > tr.active > td,
-.table > thead > tr.active > th,
-.table > tbody > tr.active > th,
-.table > tfoot > tr.active > th {
- background-color: #f5f5f5;
-}
-.table-hover > tbody > tr > td.active:hover,
-.table-hover > tbody > tr > th.active:hover,
-.table-hover > tbody > tr.active:hover > td,
-.table-hover > tbody > tr:hover > .active,
-.table-hover > tbody > tr.active:hover > th {
- background-color: #e8e8e8;
-}
-.table > thead > tr > td.success,
-.table > tbody > tr > td.success,
-.table > tfoot > tr > td.success,
-.table > thead > tr > th.success,
-.table > tbody > tr > th.success,
-.table > tfoot > tr > th.success,
-.table > thead > tr.success > td,
-.table > tbody > tr.success > td,
-.table > tfoot > tr.success > td,
-.table > thead > tr.success > th,
-.table > tbody > tr.success > th,
-.table > tfoot > tr.success > th {
- background-color: #dff0d8;
-}
-.table-hover > tbody > tr > td.success:hover,
-.table-hover > tbody > tr > th.success:hover,
-.table-hover > tbody > tr.success:hover > td,
-.table-hover > tbody > tr:hover > .success,
-.table-hover > tbody > tr.success:hover > th {
- background-color: #d0e9c6;
-}
-.table > thead > tr > td.info,
-.table > tbody > tr > td.info,
-.table > tfoot > tr > td.info,
-.table > thead > tr > th.info,
-.table > tbody > tr > th.info,
-.table > tfoot > tr > th.info,
-.table > thead > tr.info > td,
-.table > tbody > tr.info > td,
-.table > tfoot > tr.info > td,
-.table > thead > tr.info > th,
-.table > tbody > tr.info > th,
-.table > tfoot > tr.info > th {
- background-color: #d9edf7;
-}
-.table-hover > tbody > tr > td.info:hover,
-.table-hover > tbody > tr > th.info:hover,
-.table-hover > tbody > tr.info:hover > td,
-.table-hover > tbody > tr:hover > .info,
-.table-hover > tbody > tr.info:hover > th {
- background-color: #c4e3f3;
-}
-.table > thead > tr > td.warning,
-.table > tbody > tr > td.warning,
-.table > tfoot > tr > td.warning,
-.table > thead > tr > th.warning,
-.table > tbody > tr > th.warning,
-.table > tfoot > tr > th.warning,
-.table > thead > tr.warning > td,
-.table > tbody > tr.warning > td,
-.table > tfoot > tr.warning > td,
-.table > thead > tr.warning > th,
-.table > tbody > tr.warning > th,
-.table > tfoot > tr.warning > th {
- background-color: #fcf8e3;
+
+.table-hover .table-primary:hover > td,
+.table-hover .table-primary:hover > th {
+ background-color: #9fcdff;
}
-.table-hover > tbody > tr > td.warning:hover,
-.table-hover > tbody > tr > th.warning:hover,
-.table-hover > tbody > tr.warning:hover > td,
-.table-hover > tbody > tr:hover > .warning,
-.table-hover > tbody > tr.warning:hover > th {
- background-color: #faf2cc;
-}
-.table > thead > tr > td.danger,
-.table > tbody > tr > td.danger,
-.table > tfoot > tr > td.danger,
-.table > thead > tr > th.danger,
-.table > tbody > tr > th.danger,
-.table > tfoot > tr > th.danger,
-.table > thead > tr.danger > td,
-.table > tbody > tr.danger > td,
-.table > tfoot > tr.danger > td,
-.table > thead > tr.danger > th,
-.table > tbody > tr.danger > th,
-.table > tfoot > tr.danger > th {
- background-color: #f2dede;
-}
-.table-hover > tbody > tr > td.danger:hover,
-.table-hover > tbody > tr > th.danger:hover,
-.table-hover > tbody > tr.danger:hover > td,
-.table-hover > tbody > tr:hover > .danger,
-.table-hover > tbody > tr.danger:hover > th {
- background-color: #ebcccc;
-}
-.table-responsive {
- min-height: .01%;
- overflow-x: auto;
-}
-@media screen and (max-width: 767px) {
- .table-responsive {
- width: 100%;
- margin-bottom: 15px;
- overflow-y: hidden;
- -ms-overflow-style: -ms-autohiding-scrollbar;
- border: 1px solid #ddd;
- }
- .table-responsive > .table {
- margin-bottom: 0;
- }
- .table-responsive > .table > thead > tr > th,
- .table-responsive > .table > tbody > tr > th,
- .table-responsive > .table > tfoot > tr > th,
- .table-responsive > .table > thead > tr > td,
- .table-responsive > .table > tbody > tr > td,
- .table-responsive > .table > tfoot > tr > td {
- white-space: nowrap;
- }
- .table-responsive > .table-bordered {
- border: 0;
- }
- .table-responsive > .table-bordered > thead > tr > th:first-child,
- .table-responsive > .table-bordered > tbody > tr > th:first-child,
- .table-responsive > .table-bordered > tfoot > tr > th:first-child,
- .table-responsive > .table-bordered > thead > tr > td:first-child,
- .table-responsive > .table-bordered > tbody > tr > td:first-child,
- .table-responsive > .table-bordered > tfoot > tr > td:first-child {
- border-left: 0;
- }
- .table-responsive > .table-bordered > thead > tr > th:last-child,
- .table-responsive > .table-bordered > tbody > tr > th:last-child,
- .table-responsive > .table-bordered > tfoot > tr > th:last-child,
- .table-responsive > .table-bordered > thead > tr > td:last-child,
- .table-responsive > .table-bordered > tbody > tr > td:last-child,
- .table-responsive > .table-bordered > tfoot > tr > td:last-child {
- border-right: 0;
- }
- .table-responsive > .table-bordered > tbody > tr:last-child > th,
- .table-responsive > .table-bordered > tfoot > tr:last-child > th,
- .table-responsive > .table-bordered > tbody > tr:last-child > td,
- .table-responsive > .table-bordered > tfoot > tr:last-child > td {
- border-bottom: 0;
- }
+
+.table-secondary,
+.table-secondary > th,
+.table-secondary > td {
+ background-color: #dddfe2;
}
-fieldset {
- min-width: 0;
- padding: 0;
- margin: 0;
- border: 0;
+
+.table-hover .table-secondary:hover {
+ background-color: #cfd2d6;
}
-legend {
- display: block;
- width: 100%;
- padding: 0;
- margin-bottom: 20px;
- font-size: 21px;
- line-height: inherit;
- color: #333;
- border: 0;
- border-bottom: 1px solid #e5e5e5;
+
+.table-hover .table-secondary:hover > td,
+.table-hover .table-secondary:hover > th {
+ background-color: #cfd2d6;
}
-label {
- display: inline-block;
- max-width: 100%;
- margin-bottom: 5px;
- font-weight: bold;
+
+.table-success,
+.table-success > th,
+.table-success > td {
+ background-color: #c3e6cb;
}
-input[type="search"] {
- -webkit-box-sizing: border-box;
- -moz-box-sizing: border-box;
- box-sizing: border-box;
+
+.table-hover .table-success:hover {
+ background-color: #b1dfbb;
}
-input[type="radio"],
-input[type="checkbox"] {
- margin: 4px 0 0;
- margin-top: 1px \9;
- line-height: normal;
+
+.table-hover .table-success:hover > td,
+.table-hover .table-success:hover > th {
+ background-color: #b1dfbb;
}
-input[type="file"] {
- display: block;
+
+.table-info,
+.table-info > th,
+.table-info > td {
+ background-color: #bee5eb;
}
-input[type="range"] {
- display: block;
- width: 100%;
+
+.table-hover .table-info:hover {
+ background-color: #abdde5;
}
-select[multiple],
-select[size] {
- height: auto;
+
+.table-hover .table-info:hover > td,
+.table-hover .table-info:hover > th {
+ background-color: #abdde5;
}
-input[type="file"]:focus,
-input[type="radio"]:focus,
-input[type="checkbox"]:focus {
- outline: 5px auto -webkit-focus-ring-color;
- outline-offset: -2px;
+
+.table-warning,
+.table-warning > th,
+.table-warning > td {
+ background-color: #ffeeba;
}
-output {
- display: block;
- padding-top: 7px;
- font-size: 14px;
- line-height: 1.42857143;
- color: #555;
+
+.table-hover .table-warning:hover {
+ background-color: #ffe8a1;
+}
+
+.table-hover .table-warning:hover > td,
+.table-hover .table-warning:hover > th {
+ background-color: #ffe8a1;
+}
+
+.table-danger,
+.table-danger > th,
+.table-danger > td {
+ background-color: #f5c6cb;
+}
+
+.table-hover .table-danger:hover {
+ background-color: #f1b0b7;
+}
+
+.table-hover .table-danger:hover > td,
+.table-hover .table-danger:hover > th {
+ background-color: #f1b0b7;
+}
+
+.table-light,
+.table-light > th,
+.table-light > td {
+ background-color: #fdfdfe;
}
+
+.table-hover .table-light:hover {
+ background-color: #ececf6;
+}
+
+.table-hover .table-light:hover > td,
+.table-hover .table-light:hover > th {
+ background-color: #ececf6;
+}
+
+.table-dark,
+.table-dark > th,
+.table-dark > td {
+ background-color: #c6c8ca;
+}
+
+.table-hover .table-dark:hover {
+ background-color: #b9bbbe;
+}
+
+.table-hover .table-dark:hover > td,
+.table-hover .table-dark:hover > th {
+ background-color: #b9bbbe;
+}
+
+.table-active,
+.table-active > th,
+.table-active > td {
+ background-color: rgba(0, 0, 0, 0.075);
+}
+
+.table-hover .table-active:hover {
+ background-color: rgba(0, 0, 0, 0.075);
+}
+
+.table-hover .table-active:hover > td,
+.table-hover .table-active:hover > th {
+ background-color: rgba(0, 0, 0, 0.075);
+}
+
+.thead-inverse th {
+ color: #fff;
+ background-color: #212529;
+}
+
+.thead-default th {
+ color: #495057;
+ background-color: #e9ecef;
+}
+
+.table-inverse {
+ color: #fff;
+ background-color: #212529;
+}
+
+.table-inverse th,
+.table-inverse td,
+.table-inverse thead th {
+ border-color: #32383e;
+}
+
+.table-inverse.table-bordered {
+ border: 0;
+}
+
+.table-inverse.table-striped tbody tr:nth-of-type(odd) {
+ background-color: rgba(255, 255, 255, 0.05);
+}
+
+.table-inverse.table-hover tbody tr:hover {
+ background-color: rgba(255, 255, 255, 0.075);
+}
+
+@media (max-width: 991px) {
+ .table-responsive {
+ display: block;
+ width: 100%;
+ overflow-x: auto;
+ -ms-overflow-style: -ms-autohiding-scrollbar;
+ }
+ .table-responsive.table-bordered {
+ border: 0;
+ }
+}
+
.form-control {
display: block;
width: 100%;
- height: 34px;
- padding: 6px 12px;
- font-size: 14px;
- line-height: 1.42857143;
- color: #555;
+ padding: 0.5rem 0.75rem;
+ font-size: 1rem;
+ line-height: 1.25;
+ color: #495057;
background-color: #fff;
background-image: none;
- border: 1px solid #ccc;
- border-radius: 4px;
- -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075);
- box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075);
- -webkit-transition: border-color ease-in-out .15s, -webkit-box-shadow ease-in-out .15s;
- -o-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
- transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
+ background-clip: padding-box;
+ border: 1px solid rgba(0, 0, 0, 0.15);
+ border-radius: 0.25rem;
+ transition: border-color ease-in-out 0.15s, box-shadow ease-in-out 0.15s;
}
+
+.form-control::-ms-expand {
+ background-color: transparent;
+ border: 0;
+}
+
.form-control:focus {
- border-color: #66afe9;
- outline: 0;
- -webkit-box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(102, 175, 233, .6);
- box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(102, 175, 233, .6);
+ color: #495057;
+ background-color: #fff;
+ border-color: #80bdff;
+ outline: none;
}
-.form-control::-moz-placeholder {
- color: #999;
+
+.form-control::-webkit-input-placeholder {
+ color: #868e96;
opacity: 1;
}
+
.form-control:-ms-input-placeholder {
- color: #999;
-}
-.form-control::-webkit-input-placeholder {
- color: #999;
+ color: #868e96;
+ opacity: 1;
}
-.form-control::-ms-expand {
- background-color: transparent;
- border: 0;
+
+.form-control::placeholder {
+ color: #868e96;
+ opacity: 1;
}
-.form-control[disabled],
-.form-control[readonly],
-fieldset[disabled] .form-control {
- background-color: #eee;
+
+.form-control:disabled, .form-control[readonly] {
+ background-color: #e9ecef;
opacity: 1;
}
-.form-control[disabled],
-fieldset[disabled] .form-control {
- cursor: not-allowed;
+
+select.form-control:not([size]):not([multiple]) {
+ height: calc(2.25rem + 2px);
}
-textarea.form-control {
- height: auto;
+
+select.form-control:focus::-ms-value {
+ color: #495057;
+ background-color: #fff;
}
-input[type="search"] {
- -webkit-appearance: none;
+
+.form-control-file,
+.form-control-range {
+ display: block;
}
-@media screen and (-webkit-min-device-pixel-ratio: 0) {
- input[type="date"].form-control,
- input[type="time"].form-control,
- input[type="datetime-local"].form-control,
- input[type="month"].form-control {
- line-height: 34px;
- }
- input[type="date"].input-sm,
- input[type="time"].input-sm,
- input[type="datetime-local"].input-sm,
- input[type="month"].input-sm,
- .input-group-sm input[type="date"],
- .input-group-sm input[type="time"],
- .input-group-sm input[type="datetime-local"],
- .input-group-sm input[type="month"] {
- line-height: 30px;
- }
- input[type="date"].input-lg,
- input[type="time"].input-lg,
- input[type="datetime-local"].input-lg,
- input[type="month"].input-lg,
- .input-group-lg input[type="date"],
- .input-group-lg input[type="time"],
- .input-group-lg input[type="datetime-local"],
- .input-group-lg input[type="month"] {
- line-height: 46px;
- }
+
+.col-form-label {
+ padding-top: calc(0.5rem - 1px * 2);
+ padding-bottom: calc(0.5rem - 1px * 2);
+ margin-bottom: 0;
+}
+
+.col-form-label-lg {
+ padding-top: calc(0.5rem - 1px * 2);
+ padding-bottom: calc(0.5rem - 1px * 2);
+ font-size: 1.25rem;
+}
+
+.col-form-label-sm {
+ padding-top: calc(0.25rem - 1px * 2);
+ padding-bottom: calc(0.25rem - 1px * 2);
+ font-size: 0.875rem;
+}
+
+.col-form-legend {
+ padding-top: 0.5rem;
+ padding-bottom: 0.5rem;
+ margin-bottom: 0;
+ font-size: 1rem;
+}
+
+.form-control-plaintext {
+ padding-top: 0.5rem;
+ padding-bottom: 0.5rem;
+ margin-bottom: 0;
+ line-height: 1.25;
+ border: solid transparent;
+ border-width: 1px 0;
+}
+
+.form-control-plaintext.form-control-sm, .input-group-sm > .form-control-plaintext.form-control,
+.input-group-sm > .form-control-plaintext.input-group-addon,
+.input-group-sm > .input-group-btn > .form-control-plaintext.btn, .form-control-plaintext.form-control-lg, .input-group-lg > .form-control-plaintext.form-control,
+.input-group-lg > .form-control-plaintext.input-group-addon,
+.input-group-lg > .input-group-btn > .form-control-plaintext.btn {
+ padding-right: 0;
+ padding-left: 0;
+}
+
+.form-control-sm, .input-group-sm > .form-control,
+.input-group-sm > .input-group-addon,
+.input-group-sm > .input-group-btn > .btn {
+ padding: 0.25rem 0.5rem;
+ font-size: 0.875rem;
+ line-height: 1.5;
+ border-radius: 0.2rem;
+}
+
+select.form-control-sm:not([size]):not([multiple]), .input-group-sm > select.form-control:not([size]):not([multiple]),
+.input-group-sm > select.input-group-addon:not([size]):not([multiple]),
+.input-group-sm > .input-group-btn > select.btn:not([size]):not([multiple]) {
+ height: calc(1.8125rem + 2px);
+}
+
+.form-control-lg, .input-group-lg > .form-control,
+.input-group-lg > .input-group-addon,
+.input-group-lg > .input-group-btn > .btn {
+ padding: 0.5rem 1rem;
+ font-size: 1.25rem;
+ line-height: 1.5;
+ border-radius: 0.3rem;
}
+
+select.form-control-lg:not([size]):not([multiple]), .input-group-lg > select.form-control:not([size]):not([multiple]),
+.input-group-lg > select.input-group-addon:not([size]):not([multiple]),
+.input-group-lg > .input-group-btn > select.btn:not([size]):not([multiple]) {
+ height: calc(2.3125rem + 2px);
+}
+
.form-group {
- margin-bottom: 15px;
+ margin-bottom: 1rem;
+}
+
+.form-text {
+ display: block;
+ margin-top: 0.25rem;
+}
+
+.form-row {
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-wrap: wrap;
+ flex-wrap: wrap;
+ margin-right: -5px;
+ margin-left: -5px;
}
-.radio,
-.checkbox {
+
+.form-row > .col,
+.form-row > [class*="col-"] {
+ padding-right: 5px;
+ padding-left: 5px;
+}
+
+.form-check {
position: relative;
display: block;
- margin-top: 10px;
- margin-bottom: 10px;
+ margin-bottom: 0.5rem;
}
-.radio label,
-.checkbox label {
- min-height: 20px;
- padding-left: 20px;
+
+.form-check.disabled .form-check-label {
+ color: #868e96;
+}
+
+.form-check-label {
+ padding-left: 1.25rem;
margin-bottom: 0;
- font-weight: normal;
- cursor: pointer;
}
-.radio input[type="radio"],
-.radio-inline input[type="radio"],
-.checkbox input[type="checkbox"],
-.checkbox-inline input[type="checkbox"] {
+
+.form-check-input {
position: absolute;
- margin-top: 4px \9;
- margin-left: -20px;
+ margin-top: 0.25rem;
+ margin-left: -1.25rem;
}
-.radio + .radio,
-.checkbox + .checkbox {
- margin-top: -5px;
+
+.form-check-input:only-child {
+ position: static;
}
-.radio-inline,
-.checkbox-inline {
- position: relative;
+
+.form-check-inline {
display: inline-block;
- padding-left: 20px;
- margin-bottom: 0;
- font-weight: normal;
+}
+
+.form-check-inline .form-check-label {
vertical-align: middle;
- cursor: pointer;
}
-.radio-inline + .radio-inline,
-.checkbox-inline + .checkbox-inline {
- margin-top: 0;
- margin-left: 10px;
+
+.form-check-inline + .form-check-inline {
+ margin-left: 0.75rem;
}
-input[type="radio"][disabled],
-input[type="checkbox"][disabled],
-input[type="radio"].disabled,
-input[type="checkbox"].disabled,
-fieldset[disabled] input[type="radio"],
-fieldset[disabled] input[type="checkbox"] {
- cursor: not-allowed;
-}
-.radio-inline.disabled,
-.checkbox-inline.disabled,
-fieldset[disabled] .radio-inline,
-fieldset[disabled] .checkbox-inline {
- cursor: not-allowed;
-}
-.radio.disabled label,
-.checkbox.disabled label,
-fieldset[disabled] .radio label,
-fieldset[disabled] .checkbox label {
- cursor: not-allowed;
-}
-.form-control-static {
- min-height: 34px;
- padding-top: 7px;
- padding-bottom: 7px;
- margin-bottom: 0;
+
+.invalid-feedback {
+ display: none;
+ margin-top: .25rem;
+ font-size: .875rem;
+ color: #dc3545;
}
-.form-control-static.input-lg,
-.form-control-static.input-sm {
- padding-right: 0;
- padding-left: 0;
+
+.invalid-tooltip {
+ position: absolute;
+ top: 100%;
+ z-index: 5;
+ display: none;
+ width: 250px;
+ padding: .5rem;
+ margin-top: .1rem;
+ font-size: .875rem;
+ line-height: 1;
+ color: #fff;
+ background-color: rgba(220, 53, 69, 0.8);
+ border-radius: .2rem;
}
-.input-sm {
- height: 30px;
- padding: 5px 10px;
- font-size: 12px;
- line-height: 1.5;
- border-radius: 3px;
+
+.was-validated .form-control:valid, .form-control.is-valid, .was-validated
+.custom-select:valid,
+.custom-select.is-valid {
+ border-color: #28a745;
}
-select.input-sm {
- height: 30px;
- line-height: 30px;
+
+.was-validated .form-control:valid:focus, .form-control.is-valid:focus, .was-validated
+.custom-select:valid:focus,
+.custom-select.is-valid:focus {
+ box-shadow: 0 0 0 0.2rem rgba(40, 167, 69, 0.25);
}
-textarea.input-sm,
-select[multiple].input-sm {
- height: auto;
+
+.was-validated .form-control:valid ~ .invalid-feedback,
+.was-validated .form-control:valid ~ .invalid-tooltip, .form-control.is-valid ~ .invalid-feedback,
+.form-control.is-valid ~ .invalid-tooltip, .was-validated
+.custom-select:valid ~ .invalid-feedback,
+.was-validated
+.custom-select:valid ~ .invalid-tooltip,
+.custom-select.is-valid ~ .invalid-feedback,
+.custom-select.is-valid ~ .invalid-tooltip {
+ display: block;
}
-.form-group-sm .form-control {
- height: 30px;
- padding: 5px 10px;
- font-size: 12px;
- line-height: 1.5;
- border-radius: 3px;
+
+.was-validated .form-check-input:valid + .form-check-label, .form-check-input.is-valid + .form-check-label {
+ color: #28a745;
}
-.form-group-sm select.form-control {
- height: 30px;
- line-height: 30px;
+
+.was-validated .custom-control-input:valid ~ .custom-control-indicator, .custom-control-input.is-valid ~ .custom-control-indicator {
+ background-color: rgba(40, 167, 69, 0.25);
}
-.form-group-sm textarea.form-control,
-.form-group-sm select[multiple].form-control {
- height: auto;
+
+.was-validated .custom-control-input:valid ~ .custom-control-description, .custom-control-input.is-valid ~ .custom-control-description {
+ color: #28a745;
}
-.form-group-sm .form-control-static {
- height: 30px;
- min-height: 32px;
- padding: 6px 10px;
- font-size: 12px;
- line-height: 1.5;
+
+.was-validated .custom-file-input:valid ~ .custom-file-control, .custom-file-input.is-valid ~ .custom-file-control {
+ border-color: #28a745;
}
-.input-lg {
- height: 46px;
- padding: 10px 16px;
- font-size: 18px;
- line-height: 1.3333333;
- border-radius: 6px;
+
+.was-validated .custom-file-input:valid ~ .custom-file-control::before, .custom-file-input.is-valid ~ .custom-file-control::before {
+ border-color: inherit;
}
-select.input-lg {
- height: 46px;
- line-height: 46px;
+
+.was-validated .custom-file-input:valid:focus, .custom-file-input.is-valid:focus {
+ box-shadow: 0 0 0 0.2rem rgba(40, 167, 69, 0.25);
}
-textarea.input-lg,
-select[multiple].input-lg {
- height: auto;
+
+.was-validated .form-control:invalid, .form-control.is-invalid, .was-validated
+.custom-select:invalid,
+.custom-select.is-invalid {
+ border-color: #dc3545;
}
-.form-group-lg .form-control {
- height: 46px;
- padding: 10px 16px;
- font-size: 18px;
- line-height: 1.3333333;
- border-radius: 6px;
+
+.was-validated .form-control:invalid:focus, .form-control.is-invalid:focus, .was-validated
+.custom-select:invalid:focus,
+.custom-select.is-invalid:focus {
+ box-shadow: 0 0 0 0.2rem rgba(220, 53, 69, 0.25);
}
-.form-group-lg select.form-control {
- height: 46px;
- line-height: 46px;
+
+.was-validated .form-control:invalid ~ .invalid-feedback,
+.was-validated .form-control:invalid ~ .invalid-tooltip, .form-control.is-invalid ~ .invalid-feedback,
+.form-control.is-invalid ~ .invalid-tooltip, .was-validated
+.custom-select:invalid ~ .invalid-feedback,
+.was-validated
+.custom-select:invalid ~ .invalid-tooltip,
+.custom-select.is-invalid ~ .invalid-feedback,
+.custom-select.is-invalid ~ .invalid-tooltip {
+ display: block;
}
-.form-group-lg textarea.form-control,
-.form-group-lg select[multiple].form-control {
- height: auto;
+
+.was-validated .form-check-input:invalid + .form-check-label, .form-check-input.is-invalid + .form-check-label {
+ color: #dc3545;
}
-.form-group-lg .form-control-static {
- height: 46px;
- min-height: 38px;
- padding: 11px 16px;
- font-size: 18px;
- line-height: 1.3333333;
+
+.was-validated .custom-control-input:invalid ~ .custom-control-indicator, .custom-control-input.is-invalid ~ .custom-control-indicator {
+ background-color: rgba(220, 53, 69, 0.25);
}
-.has-feedback {
- position: relative;
+
+.was-validated .custom-control-input:invalid ~ .custom-control-description, .custom-control-input.is-invalid ~ .custom-control-description {
+ color: #dc3545;
}
-.has-feedback .form-control {
- padding-right: 42.5px;
+
+.was-validated .custom-file-input:invalid ~ .custom-file-control, .custom-file-input.is-invalid ~ .custom-file-control {
+ border-color: #dc3545;
}
-.form-control-feedback {
- position: absolute;
- top: 0;
- right: 0;
- z-index: 2;
- display: block;
- width: 34px;
- height: 34px;
- line-height: 34px;
- text-align: center;
- pointer-events: none;
+
+.was-validated .custom-file-input:invalid ~ .custom-file-control::before, .custom-file-input.is-invalid ~ .custom-file-control::before {
+ border-color: inherit;
}
-.input-lg + .form-control-feedback,
-.input-group-lg + .form-control-feedback,
-.form-group-lg .form-control + .form-control-feedback {
- width: 46px;
- height: 46px;
- line-height: 46px;
+
+.was-validated .custom-file-input:invalid:focus, .custom-file-input.is-invalid:focus {
+ box-shadow: 0 0 0 0.2rem rgba(220, 53, 69, 0.25);
}
-.input-sm + .form-control-feedback,
-.input-group-sm + .form-control-feedback,
-.form-group-sm .form-control + .form-control-feedback {
- width: 30px;
- height: 30px;
- line-height: 30px;
-}
-.has-success .help-block,
-.has-success .control-label,
-.has-success .radio,
-.has-success .checkbox,
-.has-success .radio-inline,
-.has-success .checkbox-inline,
-.has-success.radio label,
-.has-success.checkbox label,
-.has-success.radio-inline label,
-.has-success.checkbox-inline label {
- color: #3c763d;
-}
-.has-success .form-control {
- border-color: #3c763d;
- -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075);
- box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075);
-}
-.has-success .form-control:focus {
- border-color: #2b542c;
- -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075), 0 0 6px #67b168;
- box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075), 0 0 6px #67b168;
-}
-.has-success .input-group-addon {
- color: #3c763d;
- background-color: #dff0d8;
- border-color: #3c763d;
-}
-.has-success .form-control-feedback {
- color: #3c763d;
-}
-.has-warning .help-block,
-.has-warning .control-label,
-.has-warning .radio,
-.has-warning .checkbox,
-.has-warning .radio-inline,
-.has-warning .checkbox-inline,
-.has-warning.radio label,
-.has-warning.checkbox label,
-.has-warning.radio-inline label,
-.has-warning.checkbox-inline label {
- color: #8a6d3b;
-}
-.has-warning .form-control {
- border-color: #8a6d3b;
- -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075);
- box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075);
-}
-.has-warning .form-control:focus {
- border-color: #66512c;
- -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075), 0 0 6px #c0a16b;
- box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075), 0 0 6px #c0a16b;
-}
-.has-warning .input-group-addon {
- color: #8a6d3b;
- background-color: #fcf8e3;
- border-color: #8a6d3b;
-}
-.has-warning .form-control-feedback {
- color: #8a6d3b;
-}
-.has-error .help-block,
-.has-error .control-label,
-.has-error .radio,
-.has-error .checkbox,
-.has-error .radio-inline,
-.has-error .checkbox-inline,
-.has-error.radio label,
-.has-error.checkbox label,
-.has-error.radio-inline label,
-.has-error.checkbox-inline label {
- color: #a94442;
-}
-.has-error .form-control {
- border-color: #a94442;
- -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075);
- box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075);
-}
-.has-error .form-control:focus {
- border-color: #843534;
- -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075), 0 0 6px #ce8483;
- box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075), 0 0 6px #ce8483;
-}
-.has-error .input-group-addon {
- color: #a94442;
- background-color: #f2dede;
- border-color: #a94442;
-}
-.has-error .form-control-feedback {
- color: #a94442;
-}
-.has-feedback label ~ .form-control-feedback {
- top: 25px;
-}
-.has-feedback label.sr-only ~ .form-control-feedback {
- top: 0;
+
+.form-inline {
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-flow: row wrap;
+ flex-flow: row wrap;
+ -ms-flex-align: center;
+ align-items: center;
}
-.help-block {
- display: block;
- margin-top: 5px;
- margin-bottom: 10px;
- color: #737373;
+
+.form-inline .form-check {
+ width: 100%;
}
-@media (min-width: 768px) {
+
+@media (min-width: 576px) {
+ .form-inline label {
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-align: center;
+ align-items: center;
+ -ms-flex-pack: center;
+ justify-content: center;
+ margin-bottom: 0;
+ }
.form-inline .form-group {
- display: inline-block;
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex: 0 0 auto;
+ flex: 0 0 auto;
+ -ms-flex-flow: row wrap;
+ flex-flow: row wrap;
+ -ms-flex-align: center;
+ align-items: center;
margin-bottom: 0;
- vertical-align: middle;
}
.form-inline .form-control {
display: inline-block;
width: auto;
vertical-align: middle;
}
- .form-inline .form-control-static {
+ .form-inline .form-control-plaintext {
display: inline-block;
}
.form-inline .input-group {
- display: inline-table;
- vertical-align: middle;
- }
- .form-inline .input-group .input-group-addon,
- .form-inline .input-group .input-group-btn,
- .form-inline .input-group .form-control {
width: auto;
}
- .form-inline .input-group > .form-control {
- width: 100%;
- }
- .form-inline .control-label {
+ .form-inline .form-control-label {
margin-bottom: 0;
vertical-align: middle;
}
- .form-inline .radio,
- .form-inline .checkbox {
- display: inline-block;
+ .form-inline .form-check {
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-align: center;
+ align-items: center;
+ -ms-flex-pack: center;
+ justify-content: center;
+ width: auto;
margin-top: 0;
margin-bottom: 0;
- vertical-align: middle;
}
- .form-inline .radio label,
- .form-inline .checkbox label {
+ .form-inline .form-check-label {
padding-left: 0;
}
- .form-inline .radio input[type="radio"],
- .form-inline .checkbox input[type="checkbox"] {
+ .form-inline .form-check-input {
position: relative;
+ margin-top: 0;
+ margin-right: 0.25rem;
margin-left: 0;
}
- .form-inline .has-feedback .form-control-feedback {
- top: 0;
- }
-}
-.form-horizontal .radio,
-.form-horizontal .checkbox,
-.form-horizontal .radio-inline,
-.form-horizontal .checkbox-inline {
- padding-top: 7px;
- margin-top: 0;
- margin-bottom: 0;
-}
-.form-horizontal .radio,
-.form-horizontal .checkbox {
- min-height: 27px;
-}
-.form-horizontal .form-group {
- margin-right: -15px;
- margin-left: -15px;
-}
-@media (min-width: 768px) {
- .form-horizontal .control-label {
- padding-top: 7px;
- margin-bottom: 0;
- text-align: right;
+ .form-inline .custom-control {
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-align: center;
+ align-items: center;
+ -ms-flex-pack: center;
+ justify-content: center;
+ padding-left: 0;
}
-}
-.form-horizontal .has-feedback .form-control-feedback {
- right: 15px;
-}
-@media (min-width: 768px) {
- .form-horizontal .form-group-lg .control-label {
- padding-top: 11px;
- font-size: 18px;
+ .form-inline .custom-control-indicator {
+ position: static;
+ display: inline-block;
+ margin-right: 0.25rem;
+ vertical-align: text-bottom;
}
-}
-@media (min-width: 768px) {
- .form-horizontal .form-group-sm .control-label {
- padding-top: 6px;
- font-size: 12px;
+ .form-inline .has-feedback .form-control-feedback {
+ top: 0;
}
}
+
.btn {
display: inline-block;
- padding: 6px 12px;
- margin-bottom: 0;
- font-size: 14px;
font-weight: normal;
- line-height: 1.42857143;
text-align: center;
white-space: nowrap;
vertical-align: middle;
- -ms-touch-action: manipulation;
- touch-action: manipulation;
- cursor: pointer;
-webkit-user-select: none;
-moz-user-select: none;
-ms-user-select: none;
user-select: none;
- background-image: none;
border: 1px solid transparent;
- border-radius: 4px;
-}
-.btn:focus,
-.btn:active:focus,
-.btn.active:focus,
-.btn.focus,
-.btn:active.focus,
-.btn.active.focus {
- outline: 5px auto -webkit-focus-ring-color;
- outline-offset: -2px;
+ padding: 0.5rem 0.75rem;
+ font-size: 1rem;
+ line-height: 1.25;
+ border-radius: 0.25rem;
+ transition: all 0.15s ease-in-out;
}
-.btn:hover,
-.btn:focus,
-.btn.focus {
- color: #333;
+
+.btn:focus, .btn:hover {
text-decoration: none;
}
-.btn:active,
-.btn.active {
- background-image: none;
+
+.btn:focus, .btn.focus {
outline: 0;
- -webkit-box-shadow: inset 0 3px 5px rgba(0, 0, 0, .125);
- box-shadow: inset 0 3px 5px rgba(0, 0, 0, .125);
-}
-.btn.disabled,
-.btn[disabled],
-fieldset[disabled] .btn {
- cursor: not-allowed;
- filter: alpha(opacity=65);
- -webkit-box-shadow: none;
- box-shadow: none;
+ box-shadow: 0 0 0 3px rgba(0, 123, 255, 0.25);
+}
+
+.btn.disabled, .btn:disabled {
opacity: .65;
}
+
+.btn:active, .btn.active {
+ background-image: none;
+}
+
a.btn.disabled,
fieldset[disabled] a.btn {
pointer-events: none;
}
-.btn-default {
- color: #333;
- background-color: #fff;
- border-color: #ccc;
-}
-.btn-default:focus,
-.btn-default.focus {
- color: #333;
- background-color: #e6e6e6;
- border-color: #8c8c8c;
-}
-.btn-default:hover {
- color: #333;
- background-color: #e6e6e6;
- border-color: #adadad;
-}
-.btn-default:active,
-.btn-default.active,
-.open > .dropdown-toggle.btn-default {
- color: #333;
- background-color: #e6e6e6;
- border-color: #adadad;
-}
-.btn-default:active:hover,
-.btn-default.active:hover,
-.open > .dropdown-toggle.btn-default:hover,
-.btn-default:active:focus,
-.btn-default.active:focus,
-.open > .dropdown-toggle.btn-default:focus,
-.btn-default:active.focus,
-.btn-default.active.focus,
-.open > .dropdown-toggle.btn-default.focus {
- color: #333;
- background-color: #d4d4d4;
- border-color: #8c8c8c;
-}
-.btn-default:active,
-.btn-default.active,
-.open > .dropdown-toggle.btn-default {
- background-image: none;
+
+.btn-primary {
+ color: #fff;
+ background-color: #007bff;
+ border-color: #007bff;
}
-.btn-default.disabled:hover,
-.btn-default[disabled]:hover,
-fieldset[disabled] .btn-default:hover,
-.btn-default.disabled:focus,
-.btn-default[disabled]:focus,
-fieldset[disabled] .btn-default:focus,
-.btn-default.disabled.focus,
-.btn-default[disabled].focus,
-fieldset[disabled] .btn-default.focus {
- background-color: #fff;
- border-color: #ccc;
+
+.btn-primary:hover {
+ color: #fff;
+ background-color: #0069d9;
+ border-color: #0062cc;
+}
+
+.btn-primary:focus, .btn-primary.focus {
+ box-shadow: 0 0 0 3px rgba(0, 123, 255, 0.5);
+}
+
+.btn-primary.disabled, .btn-primary:disabled {
+ background-color: #007bff;
+ border-color: #007bff;
+}
+
+.btn-primary:active, .btn-primary.active,
+.show > .btn-primary.dropdown-toggle {
+ background-color: #0069d9;
+ background-image: none;
+ border-color: #0062cc;
}
-.btn-default .badge {
+
+.btn-secondary {
color: #fff;
- background-color: #333;
+ background-color: #868e96;
+ border-color: #868e96;
}
-.btn-primary {
+
+.btn-secondary:hover {
color: #fff;
- background-color: #337ab7;
- border-color: #2e6da4;
+ background-color: #727b84;
+ border-color: #6c757d;
+}
+
+.btn-secondary:focus, .btn-secondary.focus {
+ box-shadow: 0 0 0 3px rgba(134, 142, 150, 0.5);
+}
+
+.btn-secondary.disabled, .btn-secondary:disabled {
+ background-color: #868e96;
+ border-color: #868e96;
}
-.btn-primary:focus,
-.btn-primary.focus {
+
+.btn-secondary:active, .btn-secondary.active,
+.show > .btn-secondary.dropdown-toggle {
+ background-color: #727b84;
+ background-image: none;
+ border-color: #6c757d;
+}
+
+.btn-success {
color: #fff;
- background-color: #286090;
- border-color: #122b40;
+ background-color: #28a745;
+ border-color: #28a745;
}
-.btn-primary:hover {
+
+.btn-success:hover {
color: #fff;
- background-color: #286090;
- border-color: #204d74;
+ background-color: #218838;
+ border-color: #1e7e34;
+}
+
+.btn-success:focus, .btn-success.focus {
+ box-shadow: 0 0 0 3px rgba(40, 167, 69, 0.5);
}
-.btn-primary:active,
-.btn-primary.active,
-.open > .dropdown-toggle.btn-primary {
+
+.btn-success.disabled, .btn-success:disabled {
+ background-color: #28a745;
+ border-color: #28a745;
+}
+
+.btn-success:active, .btn-success.active,
+.show > .btn-success.dropdown-toggle {
+ background-color: #218838;
+ background-image: none;
+ border-color: #1e7e34;
+}
+
+.btn-info {
color: #fff;
- background-color: #286090;
- border-color: #204d74;
-}
-.btn-primary:active:hover,
-.btn-primary.active:hover,
-.open > .dropdown-toggle.btn-primary:hover,
-.btn-primary:active:focus,
-.btn-primary.active:focus,
-.open > .dropdown-toggle.btn-primary:focus,
-.btn-primary:active.focus,
-.btn-primary.active.focus,
-.open > .dropdown-toggle.btn-primary.focus {
+ background-color: #17a2b8;
+ border-color: #17a2b8;
+}
+
+.btn-info:hover {
color: #fff;
- background-color: #204d74;
- border-color: #122b40;
+ background-color: #138496;
+ border-color: #117a8b;
+}
+
+.btn-info:focus, .btn-info.focus {
+ box-shadow: 0 0 0 3px rgba(23, 162, 184, 0.5);
}
-.btn-primary:active,
-.btn-primary.active,
-.open > .dropdown-toggle.btn-primary {
+
+.btn-info.disabled, .btn-info:disabled {
+ background-color: #17a2b8;
+ border-color: #17a2b8;
+}
+
+.btn-info:active, .btn-info.active,
+.show > .btn-info.dropdown-toggle {
+ background-color: #138496;
background-image: none;
+ border-color: #117a8b;
}
-.btn-primary.disabled:hover,
-.btn-primary[disabled]:hover,
-fieldset[disabled] .btn-primary:hover,
-.btn-primary.disabled:focus,
-.btn-primary[disabled]:focus,
-fieldset[disabled] .btn-primary:focus,
-.btn-primary.disabled.focus,
-.btn-primary[disabled].focus,
-fieldset[disabled] .btn-primary.focus {
- background-color: #337ab7;
- border-color: #2e6da4;
-}
-.btn-primary .badge {
- color: #337ab7;
- background-color: #fff;
+
+.btn-warning {
+ color: #111;
+ background-color: #ffc107;
+ border-color: #ffc107;
}
-.btn-success {
- color: #fff;
- background-color: #5cb85c;
- border-color: #4cae4c;
+
+.btn-warning:hover {
+ color: #111;
+ background-color: #e0a800;
+ border-color: #d39e00;
}
-.btn-success:focus,
-.btn-success.focus {
- color: #fff;
- background-color: #449d44;
- border-color: #255625;
+
+.btn-warning:focus, .btn-warning.focus {
+ box-shadow: 0 0 0 3px rgba(255, 193, 7, 0.5);
}
-.btn-success:hover {
- color: #fff;
- background-color: #449d44;
- border-color: #398439;
+
+.btn-warning.disabled, .btn-warning:disabled {
+ background-color: #ffc107;
+ border-color: #ffc107;
+}
+
+.btn-warning:active, .btn-warning.active,
+.show > .btn-warning.dropdown-toggle {
+ background-color: #e0a800;
+ background-image: none;
+ border-color: #d39e00;
}
-.btn-success:active,
-.btn-success.active,
-.open > .dropdown-toggle.btn-success {
+
+.btn-danger {
color: #fff;
- background-color: #449d44;
- border-color: #398439;
-}
-.btn-success:active:hover,
-.btn-success.active:hover,
-.open > .dropdown-toggle.btn-success:hover,
-.btn-success:active:focus,
-.btn-success.active:focus,
-.open > .dropdown-toggle.btn-success:focus,
-.btn-success:active.focus,
-.btn-success.active.focus,
-.open > .dropdown-toggle.btn-success.focus {
+ background-color: #dc3545;
+ border-color: #dc3545;
+}
+
+.btn-danger:hover {
color: #fff;
- background-color: #398439;
- border-color: #255625;
+ background-color: #c82333;
+ border-color: #bd2130;
+}
+
+.btn-danger:focus, .btn-danger.focus {
+ box-shadow: 0 0 0 3px rgba(220, 53, 69, 0.5);
+}
+
+.btn-danger.disabled, .btn-danger:disabled {
+ background-color: #dc3545;
+ border-color: #dc3545;
}
-.btn-success:active,
-.btn-success.active,
-.open > .dropdown-toggle.btn-success {
+
+.btn-danger:active, .btn-danger.active,
+.show > .btn-danger.dropdown-toggle {
+ background-color: #c82333;
background-image: none;
+ border-color: #bd2130;
}
-.btn-success.disabled:hover,
-.btn-success[disabled]:hover,
-fieldset[disabled] .btn-success:hover,
-.btn-success.disabled:focus,
-.btn-success[disabled]:focus,
-fieldset[disabled] .btn-success:focus,
-.btn-success.disabled.focus,
-.btn-success[disabled].focus,
-fieldset[disabled] .btn-success.focus {
- background-color: #5cb85c;
- border-color: #4cae4c;
-}
-.btn-success .badge {
- color: #5cb85c;
- background-color: #fff;
+
+.btn-light {
+ color: #111;
+ background-color: #f8f9fa;
+ border-color: #f8f9fa;
}
-.btn-info {
- color: #fff;
- background-color: #5bc0de;
- border-color: #46b8da;
+
+.btn-light:hover {
+ color: #111;
+ background-color: #e2e6ea;
+ border-color: #dae0e5;
+}
+
+.btn-light:focus, .btn-light.focus {
+ box-shadow: 0 0 0 3px rgba(248, 249, 250, 0.5);
+}
+
+.btn-light.disabled, .btn-light:disabled {
+ background-color: #f8f9fa;
+ border-color: #f8f9fa;
+}
+
+.btn-light:active, .btn-light.active,
+.show > .btn-light.dropdown-toggle {
+ background-color: #e2e6ea;
+ background-image: none;
+ border-color: #dae0e5;
}
-.btn-info:focus,
-.btn-info.focus {
+
+.btn-dark {
color: #fff;
- background-color: #31b0d5;
- border-color: #1b6d85;
+ background-color: #343a40;
+ border-color: #343a40;
}
-.btn-info:hover {
+
+.btn-dark:hover {
color: #fff;
- background-color: #31b0d5;
- border-color: #269abc;
+ background-color: #23272b;
+ border-color: #1d2124;
}
-.btn-info:active,
-.btn-info.active,
-.open > .dropdown-toggle.btn-info {
+
+.btn-dark:focus, .btn-dark.focus {
+ box-shadow: 0 0 0 3px rgba(52, 58, 64, 0.5);
+}
+
+.btn-dark.disabled, .btn-dark:disabled {
+ background-color: #343a40;
+ border-color: #343a40;
+}
+
+.btn-dark:active, .btn-dark.active,
+.show > .btn-dark.dropdown-toggle {
+ background-color: #23272b;
+ background-image: none;
+ border-color: #1d2124;
+}
+
+.btn-outline-primary {
+ color: #007bff;
+ background-color: transparent;
+ background-image: none;
+ border-color: #007bff;
+}
+
+.btn-outline-primary:hover {
color: #fff;
- background-color: #31b0d5;
- border-color: #269abc;
-}
-.btn-info:active:hover,
-.btn-info.active:hover,
-.open > .dropdown-toggle.btn-info:hover,
-.btn-info:active:focus,
-.btn-info.active:focus,
-.open > .dropdown-toggle.btn-info:focus,
-.btn-info:active.focus,
-.btn-info.active.focus,
-.open > .dropdown-toggle.btn-info.focus {
+ background-color: #007bff;
+ border-color: #007bff;
+}
+
+.btn-outline-primary:focus, .btn-outline-primary.focus {
+ box-shadow: 0 0 0 3px rgba(0, 123, 255, 0.5);
+}
+
+.btn-outline-primary.disabled, .btn-outline-primary:disabled {
+ color: #007bff;
+ background-color: transparent;
+}
+
+.btn-outline-primary:active, .btn-outline-primary.active,
+.show > .btn-outline-primary.dropdown-toggle {
color: #fff;
- background-color: #269abc;
- border-color: #1b6d85;
+ background-color: #007bff;
+ border-color: #007bff;
}
-.btn-info:active,
-.btn-info.active,
-.open > .dropdown-toggle.btn-info {
+
+.btn-outline-secondary {
+ color: #868e96;
+ background-color: transparent;
background-image: none;
+ border-color: #868e96;
}
-.btn-info.disabled:hover,
-.btn-info[disabled]:hover,
-fieldset[disabled] .btn-info:hover,
-.btn-info.disabled:focus,
-.btn-info[disabled]:focus,
-fieldset[disabled] .btn-info:focus,
-.btn-info.disabled.focus,
-.btn-info[disabled].focus,
-fieldset[disabled] .btn-info.focus {
- background-color: #5bc0de;
- border-color: #46b8da;
-}
-.btn-info .badge {
- color: #5bc0de;
- background-color: #fff;
+
+.btn-outline-secondary:hover {
+ color: #fff;
+ background-color: #868e96;
+ border-color: #868e96;
}
-.btn-warning {
+
+.btn-outline-secondary:focus, .btn-outline-secondary.focus {
+ box-shadow: 0 0 0 3px rgba(134, 142, 150, 0.5);
+}
+
+.btn-outline-secondary.disabled, .btn-outline-secondary:disabled {
+ color: #868e96;
+ background-color: transparent;
+}
+
+.btn-outline-secondary:active, .btn-outline-secondary.active,
+.show > .btn-outline-secondary.dropdown-toggle {
color: #fff;
- background-color: #f0ad4e;
- border-color: #eea236;
+ background-color: #868e96;
+ border-color: #868e96;
}
-.btn-warning:focus,
-.btn-warning.focus {
+
+.btn-outline-success {
+ color: #28a745;
+ background-color: transparent;
+ background-image: none;
+ border-color: #28a745;
+}
+
+.btn-outline-success:hover {
color: #fff;
- background-color: #ec971f;
- border-color: #985f0d;
+ background-color: #28a745;
+ border-color: #28a745;
}
-.btn-warning:hover {
+
+.btn-outline-success:focus, .btn-outline-success.focus {
+ box-shadow: 0 0 0 3px rgba(40, 167, 69, 0.5);
+}
+
+.btn-outline-success.disabled, .btn-outline-success:disabled {
+ color: #28a745;
+ background-color: transparent;
+}
+
+.btn-outline-success:active, .btn-outline-success.active,
+.show > .btn-outline-success.dropdown-toggle {
color: #fff;
- background-color: #ec971f;
- border-color: #d58512;
+ background-color: #28a745;
+ border-color: #28a745;
+}
+
+.btn-outline-info {
+ color: #17a2b8;
+ background-color: transparent;
+ background-image: none;
+ border-color: #17a2b8;
}
-.btn-warning:active,
-.btn-warning.active,
-.open > .dropdown-toggle.btn-warning {
+
+.btn-outline-info:hover {
color: #fff;
- background-color: #ec971f;
- border-color: #d58512;
-}
-.btn-warning:active:hover,
-.btn-warning.active:hover,
-.open > .dropdown-toggle.btn-warning:hover,
-.btn-warning:active:focus,
-.btn-warning.active:focus,
-.open > .dropdown-toggle.btn-warning:focus,
-.btn-warning:active.focus,
-.btn-warning.active.focus,
-.open > .dropdown-toggle.btn-warning.focus {
+ background-color: #17a2b8;
+ border-color: #17a2b8;
+}
+
+.btn-outline-info:focus, .btn-outline-info.focus {
+ box-shadow: 0 0 0 3px rgba(23, 162, 184, 0.5);
+}
+
+.btn-outline-info.disabled, .btn-outline-info:disabled {
+ color: #17a2b8;
+ background-color: transparent;
+}
+
+.btn-outline-info:active, .btn-outline-info.active,
+.show > .btn-outline-info.dropdown-toggle {
color: #fff;
- background-color: #d58512;
- border-color: #985f0d;
+ background-color: #17a2b8;
+ border-color: #17a2b8;
}
-.btn-warning:active,
-.btn-warning.active,
-.open > .dropdown-toggle.btn-warning {
+
+.btn-outline-warning {
+ color: #ffc107;
+ background-color: transparent;
background-image: none;
+ border-color: #ffc107;
}
-.btn-warning.disabled:hover,
-.btn-warning[disabled]:hover,
-fieldset[disabled] .btn-warning:hover,
-.btn-warning.disabled:focus,
-.btn-warning[disabled]:focus,
-fieldset[disabled] .btn-warning:focus,
-.btn-warning.disabled.focus,
-.btn-warning[disabled].focus,
-fieldset[disabled] .btn-warning.focus {
- background-color: #f0ad4e;
- border-color: #eea236;
-}
-.btn-warning .badge {
- color: #f0ad4e;
- background-color: #fff;
+
+.btn-outline-warning:hover {
+ color: #fff;
+ background-color: #ffc107;
+ border-color: #ffc107;
}
-.btn-danger {
+
+.btn-outline-warning:focus, .btn-outline-warning.focus {
+ box-shadow: 0 0 0 3px rgba(255, 193, 7, 0.5);
+}
+
+.btn-outline-warning.disabled, .btn-outline-warning:disabled {
+ color: #ffc107;
+ background-color: transparent;
+}
+
+.btn-outline-warning:active, .btn-outline-warning.active,
+.show > .btn-outline-warning.dropdown-toggle {
color: #fff;
- background-color: #d9534f;
- border-color: #d43f3a;
+ background-color: #ffc107;
+ border-color: #ffc107;
+}
+
+.btn-outline-danger {
+ color: #dc3545;
+ background-color: transparent;
+ background-image: none;
+ border-color: #dc3545;
}
-.btn-danger:focus,
-.btn-danger.focus {
+
+.btn-outline-danger:hover {
color: #fff;
- background-color: #c9302c;
- border-color: #761c19;
+ background-color: #dc3545;
+ border-color: #dc3545;
}
-.btn-danger:hover {
+
+.btn-outline-danger:focus, .btn-outline-danger.focus {
+ box-shadow: 0 0 0 3px rgba(220, 53, 69, 0.5);
+}
+
+.btn-outline-danger.disabled, .btn-outline-danger:disabled {
+ color: #dc3545;
+ background-color: transparent;
+}
+
+.btn-outline-danger:active, .btn-outline-danger.active,
+.show > .btn-outline-danger.dropdown-toggle {
color: #fff;
- background-color: #c9302c;
- border-color: #ac2925;
+ background-color: #dc3545;
+ border-color: #dc3545;
+}
+
+.btn-outline-light {
+ color: #f8f9fa;
+ background-color: transparent;
+ background-image: none;
+ border-color: #f8f9fa;
}
-.btn-danger:active,
-.btn-danger.active,
-.open > .dropdown-toggle.btn-danger {
+
+.btn-outline-light:hover {
color: #fff;
- background-color: #c9302c;
- border-color: #ac2925;
-}
-.btn-danger:active:hover,
-.btn-danger.active:hover,
-.open > .dropdown-toggle.btn-danger:hover,
-.btn-danger:active:focus,
-.btn-danger.active:focus,
-.open > .dropdown-toggle.btn-danger:focus,
-.btn-danger:active.focus,
-.btn-danger.active.focus,
-.open > .dropdown-toggle.btn-danger.focus {
+ background-color: #f8f9fa;
+ border-color: #f8f9fa;
+}
+
+.btn-outline-light:focus, .btn-outline-light.focus {
+ box-shadow: 0 0 0 3px rgba(248, 249, 250, 0.5);
+}
+
+.btn-outline-light.disabled, .btn-outline-light:disabled {
+ color: #f8f9fa;
+ background-color: transparent;
+}
+
+.btn-outline-light:active, .btn-outline-light.active,
+.show > .btn-outline-light.dropdown-toggle {
color: #fff;
- background-color: #ac2925;
- border-color: #761c19;
+ background-color: #f8f9fa;
+ border-color: #f8f9fa;
}
-.btn-danger:active,
-.btn-danger.active,
-.open > .dropdown-toggle.btn-danger {
+
+.btn-outline-dark {
+ color: #343a40;
+ background-color: transparent;
background-image: none;
+ border-color: #343a40;
}
-.btn-danger.disabled:hover,
-.btn-danger[disabled]:hover,
-fieldset[disabled] .btn-danger:hover,
-.btn-danger.disabled:focus,
-.btn-danger[disabled]:focus,
-fieldset[disabled] .btn-danger:focus,
-.btn-danger.disabled.focus,
-.btn-danger[disabled].focus,
-fieldset[disabled] .btn-danger.focus {
- background-color: #d9534f;
- border-color: #d43f3a;
-}
-.btn-danger .badge {
- color: #d9534f;
- background-color: #fff;
+
+.btn-outline-dark:hover {
+ color: #fff;
+ background-color: #343a40;
+ border-color: #343a40;
+}
+
+.btn-outline-dark:focus, .btn-outline-dark.focus {
+ box-shadow: 0 0 0 3px rgba(52, 58, 64, 0.5);
}
+
+.btn-outline-dark.disabled, .btn-outline-dark:disabled {
+ color: #343a40;
+ background-color: transparent;
+}
+
+.btn-outline-dark:active, .btn-outline-dark.active,
+.show > .btn-outline-dark.dropdown-toggle {
+ color: #fff;
+ background-color: #343a40;
+ border-color: #343a40;
+}
+
.btn-link {
font-weight: normal;
- color: #337ab7;
+ color: #007bff;
border-radius: 0;
}
-.btn-link,
-.btn-link:active,
-.btn-link.active,
-.btn-link[disabled],
-fieldset[disabled] .btn-link {
+
+.btn-link, .btn-link:active, .btn-link.active, .btn-link:disabled {
background-color: transparent;
- -webkit-box-shadow: none;
- box-shadow: none;
}
-.btn-link,
-.btn-link:hover,
-.btn-link:focus,
-.btn-link:active {
+
+.btn-link, .btn-link:focus, .btn-link:active {
+ border-color: transparent;
+ box-shadow: none;
+}
+
+.btn-link:hover {
border-color: transparent;
}
-.btn-link:hover,
-.btn-link:focus {
- color: #23527c;
+
+.btn-link:focus, .btn-link:hover {
+ color: #0056b3;
text-decoration: underline;
background-color: transparent;
}
-.btn-link[disabled]:hover,
-fieldset[disabled] .btn-link:hover,
-.btn-link[disabled]:focus,
-fieldset[disabled] .btn-link:focus {
- color: #777;
+
+.btn-link:disabled {
+ color: #868e96;
+}
+
+.btn-link:disabled:focus, .btn-link:disabled:hover {
text-decoration: none;
}
-.btn-lg,
-.btn-group-lg > .btn {
- padding: 10px 16px;
- font-size: 18px;
- line-height: 1.3333333;
- border-radius: 6px;
-}
-.btn-sm,
-.btn-group-sm > .btn {
- padding: 5px 10px;
- font-size: 12px;
+
+.btn-lg, .btn-group-lg > .btn {
+ padding: 0.5rem 1rem;
+ font-size: 1.25rem;
line-height: 1.5;
- border-radius: 3px;
+ border-radius: 0.3rem;
}
-.btn-xs,
-.btn-group-xs > .btn {
- padding: 1px 5px;
- font-size: 12px;
+
+.btn-sm, .btn-group-sm > .btn {
+ padding: 0.25rem 0.5rem;
+ font-size: 0.875rem;
line-height: 1.5;
- border-radius: 3px;
+ border-radius: 0.2rem;
}
+
.btn-block {
display: block;
width: 100%;
}
+
.btn-block + .btn-block {
- margin-top: 5px;
+ margin-top: 0.5rem;
}
+
input[type="submit"].btn-block,
input[type="reset"].btn-block,
input[type="button"].btn-block {
width: 100%;
}
+
.fade {
opacity: 0;
- -webkit-transition: opacity .15s linear;
- -o-transition: opacity .15s linear;
- transition: opacity .15s linear;
+ transition: opacity 0.15s linear;
}
-.fade.in {
+
+.fade.show {
opacity: 1;
}
+
.collapse {
display: none;
}
-.collapse.in {
+
+.collapse.show {
display: block;
}
-tr.collapse.in {
+
+tr.collapse.show {
display: table-row;
}
-tbody.collapse.in {
+
+tbody.collapse.show {
display: table-row-group;
}
+
.collapsing {
position: relative;
height: 0;
overflow: hidden;
- -webkit-transition-timing-function: ease;
- -o-transition-timing-function: ease;
- transition-timing-function: ease;
- -webkit-transition-duration: .35s;
- -o-transition-duration: .35s;
- transition-duration: .35s;
- -webkit-transition-property: height, visibility;
- -o-transition-property: height, visibility;
- transition-property: height, visibility;
-}
-.caret {
- display: inline-block;
- width: 0;
- height: 0;
- margin-left: 2px;
- vertical-align: middle;
- border-top: 4px dashed;
- border-top: 4px solid \9;
- border-right: 4px solid transparent;
- border-left: 4px solid transparent;
+ transition: height 0.35s ease;
}
+
.dropup,
.dropdown {
position: relative;
}
-.dropdown-toggle:focus {
- outline: 0;
+
+.dropdown-toggle::after {
+ display: inline-block;
+ width: 0;
+ height: 0;
+ margin-left: 0.255em;
+ vertical-align: 0.255em;
+ content: "";
+ border-top: 0.3em solid;
+ border-right: 0.3em solid transparent;
+ border-left: 0.3em solid transparent;
+}
+
+.dropdown-toggle:empty::after {
+ margin-left: 0;
}
+
+.dropup .dropdown-menu {
+ margin-top: 0;
+ margin-bottom: 0.125rem;
+}
+
+.dropup .dropdown-toggle::after {
+ border-top: 0;
+ border-bottom: 0.3em solid;
+}
+
.dropdown-menu {
position: absolute;
top: 100%;
@@ -3524,235 +2575,198 @@ tbody.collapse.in {
z-index: 1000;
display: none;
float: left;
- min-width: 160px;
- padding: 5px 0;
- margin: 2px 0 0;
- font-size: 14px;
+ min-width: 10rem;
+ padding: 0.5rem 0;
+ margin: 0.125rem 0 0;
+ font-size: 1rem;
+ color: #212529;
text-align: left;
list-style: none;
background-color: #fff;
- -webkit-background-clip: padding-box;
- background-clip: padding-box;
- border: 1px solid #ccc;
- border: 1px solid rgba(0, 0, 0, .15);
- border-radius: 4px;
- -webkit-box-shadow: 0 6px 12px rgba(0, 0, 0, .175);
- box-shadow: 0 6px 12px rgba(0, 0, 0, .175);
-}
-.dropdown-menu.pull-right {
- right: 0;
- left: auto;
+ background-clip: padding-box;
+ border: 1px solid rgba(0, 0, 0, 0.15);
+ border-radius: 0.25rem;
}
-.dropdown-menu .divider {
- height: 1px;
- margin: 9px 0;
+
+.dropdown-divider {
+ height: 0;
+ margin: 0.5rem 0;
overflow: hidden;
- background-color: #e5e5e5;
+ border-top: 1px solid #e9ecef;
}
-.dropdown-menu > li > a {
+
+.dropdown-item {
display: block;
- padding: 3px 20px;
+ width: 100%;
+ padding: 0.25rem 1.5rem;
clear: both;
font-weight: normal;
- line-height: 1.42857143;
- color: #333;
+ color: #212529;
+ text-align: inherit;
white-space: nowrap;
+ background: none;
+ border: 0;
}
-.dropdown-menu > li > a:hover,
-.dropdown-menu > li > a:focus {
- color: #262626;
+
+.dropdown-item:focus, .dropdown-item:hover {
+ color: #16181b;
text-decoration: none;
- background-color: #f5f5f5;
+ background-color: #f8f9fa;
}
-.dropdown-menu > .active > a,
-.dropdown-menu > .active > a:hover,
-.dropdown-menu > .active > a:focus {
+
+.dropdown-item.active, .dropdown-item:active {
color: #fff;
text-decoration: none;
- background-color: #337ab7;
- outline: 0;
-}
-.dropdown-menu > .disabled > a,
-.dropdown-menu > .disabled > a:hover,
-.dropdown-menu > .disabled > a:focus {
- color: #777;
+ background-color: #007bff;
}
-.dropdown-menu > .disabled > a:hover,
-.dropdown-menu > .disabled > a:focus {
- text-decoration: none;
- cursor: not-allowed;
+
+.dropdown-item.disabled, .dropdown-item:disabled {
+ color: #868e96;
background-color: transparent;
- background-image: none;
- filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);
-}
-.open > .dropdown-menu {
- display: block;
}
-.open > a {
+
+.show > a {
outline: 0;
}
-.dropdown-menu-right {
- right: 0;
- left: auto;
-}
-.dropdown-menu-left {
- right: auto;
- left: 0;
+
+.dropdown-menu.show {
+ display: block;
}
+
.dropdown-header {
display: block;
- padding: 3px 20px;
- font-size: 12px;
- line-height: 1.42857143;
- color: #777;
+ padding: 0.5rem 1.5rem;
+ margin-bottom: 0;
+ font-size: 0.875rem;
+ color: #868e96;
white-space: nowrap;
}
-.dropdown-backdrop {
- position: fixed;
- top: 0;
- right: 0;
- bottom: 0;
- left: 0;
- z-index: 990;
-}
-.pull-right > .dropdown-menu {
- right: 0;
- left: auto;
-}
-.dropup .caret,
-.navbar-fixed-bottom .dropdown .caret {
- content: "";
- border-top: 0;
- border-bottom: 4px dashed;
- border-bottom: 4px solid \9;
-}
-.dropup .dropdown-menu,
-.navbar-fixed-bottom .dropdown .dropdown-menu {
- top: auto;
- bottom: 100%;
- margin-bottom: 2px;
-}
-@media (min-width: 768px) {
- .navbar-right .dropdown-menu {
- right: 0;
- left: auto;
- }
- .navbar-right .dropdown-menu-left {
- right: auto;
- left: 0;
- }
-}
+
.btn-group,
.btn-group-vertical {
position: relative;
- display: inline-block;
+ display: -ms-inline-flexbox;
+ display: inline-flex;
vertical-align: middle;
}
+
.btn-group > .btn,
.btn-group-vertical > .btn {
position: relative;
- float: left;
+ -ms-flex: 0 1 auto;
+ flex: 0 1 auto;
+ margin-bottom: 0;
}
+
.btn-group > .btn:hover,
-.btn-group-vertical > .btn:hover,
-.btn-group > .btn:focus,
+.btn-group-vertical > .btn:hover {
+ z-index: 2;
+}
+
+.btn-group > .btn:focus, .btn-group > .btn:active, .btn-group > .btn.active,
.btn-group-vertical > .btn:focus,
-.btn-group > .btn:active,
.btn-group-vertical > .btn:active,
-.btn-group > .btn.active,
.btn-group-vertical > .btn.active {
z-index: 2;
}
+
.btn-group .btn + .btn,
.btn-group .btn + .btn-group,
.btn-group .btn-group + .btn,
-.btn-group .btn-group + .btn-group {
+.btn-group .btn-group + .btn-group,
+.btn-group-vertical .btn + .btn,
+.btn-group-vertical .btn + .btn-group,
+.btn-group-vertical .btn-group + .btn,
+.btn-group-vertical .btn-group + .btn-group {
margin-left: -1px;
}
+
.btn-toolbar {
- margin-left: -5px;
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-wrap: wrap;
+ flex-wrap: wrap;
+ -ms-flex-pack: start;
+ justify-content: flex-start;
}
-.btn-toolbar .btn,
-.btn-toolbar .btn-group,
+
.btn-toolbar .input-group {
- float: left;
-}
-.btn-toolbar > .btn,
-.btn-toolbar > .btn-group,
-.btn-toolbar > .input-group {
- margin-left: 5px;
+ width: auto;
}
+
.btn-group > .btn:not(:first-child):not(:last-child):not(.dropdown-toggle) {
border-radius: 0;
}
+
.btn-group > .btn:first-child {
margin-left: 0;
}
+
.btn-group > .btn:first-child:not(:last-child):not(.dropdown-toggle) {
border-top-right-radius: 0;
border-bottom-right-radius: 0;
}
+
.btn-group > .btn:last-child:not(:first-child),
.btn-group > .dropdown-toggle:not(:first-child) {
border-top-left-radius: 0;
border-bottom-left-radius: 0;
}
+
.btn-group > .btn-group {
float: left;
}
+
.btn-group > .btn-group:not(:first-child):not(:last-child) > .btn {
border-radius: 0;
}
+
.btn-group > .btn-group:first-child:not(:last-child) > .btn:last-child,
.btn-group > .btn-group:first-child:not(:last-child) > .dropdown-toggle {
border-top-right-radius: 0;
border-bottom-right-radius: 0;
}
+
.btn-group > .btn-group:last-child:not(:first-child) > .btn:first-child {
border-top-left-radius: 0;
border-bottom-left-radius: 0;
}
-.btn-group .dropdown-toggle:active,
-.btn-group.open .dropdown-toggle {
- outline: 0;
-}
-.btn-group > .btn + .dropdown-toggle {
- padding-right: 8px;
- padding-left: 8px;
-}
-.btn-group > .btn-lg + .dropdown-toggle {
- padding-right: 12px;
- padding-left: 12px;
-}
-.btn-group.open .dropdown-toggle {
- -webkit-box-shadow: inset 0 3px 5px rgba(0, 0, 0, .125);
- box-shadow: inset 0 3px 5px rgba(0, 0, 0, .125);
-}
-.btn-group.open .dropdown-toggle.btn-link {
- -webkit-box-shadow: none;
- box-shadow: none;
+
+.btn + .dropdown-toggle-split {
+ padding-right: 0.5625rem;
+ padding-left: 0.5625rem;
}
-.btn .caret {
+
+.btn + .dropdown-toggle-split::after {
margin-left: 0;
}
-.btn-lg .caret {
- border-width: 5px 5px 0;
- border-bottom-width: 0;
+
+.btn-sm + .dropdown-toggle-split, .btn-group-sm > .btn + .dropdown-toggle-split {
+ padding-right: 0.375rem;
+ padding-left: 0.375rem;
}
-.dropup .btn-lg .caret {
- border-width: 0 5px 5px;
+
+.btn-lg + .dropdown-toggle-split, .btn-group-lg > .btn + .dropdown-toggle-split {
+ padding-right: 0.75rem;
+ padding-left: 0.75rem;
}
-.btn-group-vertical > .btn,
-.btn-group-vertical > .btn-group,
-.btn-group-vertical > .btn-group > .btn {
- display: block;
- float: none;
- width: 100%;
- max-width: 100%;
+
+.btn-group-vertical {
+ display: -ms-inline-flexbox;
+ display: inline-flex;
+ -ms-flex-direction: column;
+ flex-direction: column;
+ -ms-flex-align: start;
+ align-items: flex-start;
+ -ms-flex-pack: center;
+ justify-content: center;
}
-.btn-group-vertical > .btn-group > .btn {
- float: none;
+
+.btn-group-vertical .btn,
+.btn-group-vertical .btn-group {
+ width: 100%;
}
+
.btn-group-vertical > .btn + .btn,
.btn-group-vertical > .btn + .btn-group,
.btn-group-vertical > .btn-group + .btn,
@@ -3760,1091 +2774,1196 @@ tbody.collapse.in {
margin-top: -1px;
margin-left: 0;
}
+
.btn-group-vertical > .btn:not(:first-child):not(:last-child) {
border-radius: 0;
}
+
.btn-group-vertical > .btn:first-child:not(:last-child) {
- border-top-left-radius: 4px;
- border-top-right-radius: 4px;
border-bottom-right-radius: 0;
border-bottom-left-radius: 0;
}
+
.btn-group-vertical > .btn:last-child:not(:first-child) {
border-top-left-radius: 0;
border-top-right-radius: 0;
- border-bottom-right-radius: 4px;
- border-bottom-left-radius: 4px;
}
+
.btn-group-vertical > .btn-group:not(:first-child):not(:last-child) > .btn {
border-radius: 0;
}
+
.btn-group-vertical > .btn-group:first-child:not(:last-child) > .btn:last-child,
.btn-group-vertical > .btn-group:first-child:not(:last-child) > .dropdown-toggle {
border-bottom-right-radius: 0;
border-bottom-left-radius: 0;
}
+
.btn-group-vertical > .btn-group:last-child:not(:first-child) > .btn:first-child {
border-top-left-radius: 0;
border-top-right-radius: 0;
}
-.btn-group-justified {
- display: table;
- width: 100%;
- table-layout: fixed;
- border-collapse: separate;
-}
-.btn-group-justified > .btn,
-.btn-group-justified > .btn-group {
- display: table-cell;
- float: none;
- width: 1%;
-}
-.btn-group-justified > .btn-group .btn {
- width: 100%;
-}
-.btn-group-justified > .btn-group .dropdown-menu {
- left: auto;
-}
+
[data-toggle="buttons"] > .btn input[type="radio"],
-[data-toggle="buttons"] > .btn-group > .btn input[type="radio"],
[data-toggle="buttons"] > .btn input[type="checkbox"],
+[data-toggle="buttons"] > .btn-group > .btn input[type="radio"],
[data-toggle="buttons"] > .btn-group > .btn input[type="checkbox"] {
position: absolute;
clip: rect(0, 0, 0, 0);
pointer-events: none;
}
+
.input-group {
position: relative;
- display: table;
- border-collapse: separate;
-}
-.input-group[class*="col-"] {
- float: none;
- padding-right: 0;
- padding-left: 0;
+ display: -ms-flexbox;
+ display: flex;
+ width: 100%;
}
+
.input-group .form-control {
position: relative;
z-index: 2;
- float: left;
- width: 100%;
+ -ms-flex: 1 1 auto;
+ flex: 1 1 auto;
+ width: 1%;
margin-bottom: 0;
}
-.input-group .form-control:focus {
+
+.input-group .form-control:focus, .input-group .form-control:active, .input-group .form-control:hover {
z-index: 3;
}
-.input-group-lg > .form-control,
-.input-group-lg > .input-group-addon,
-.input-group-lg > .input-group-btn > .btn {
- height: 46px;
- padding: 10px 16px;
- font-size: 18px;
- line-height: 1.3333333;
- border-radius: 6px;
-}
-select.input-group-lg > .form-control,
-select.input-group-lg > .input-group-addon,
-select.input-group-lg > .input-group-btn > .btn {
- height: 46px;
- line-height: 46px;
-}
-textarea.input-group-lg > .form-control,
-textarea.input-group-lg > .input-group-addon,
-textarea.input-group-lg > .input-group-btn > .btn,
-select[multiple].input-group-lg > .form-control,
-select[multiple].input-group-lg > .input-group-addon,
-select[multiple].input-group-lg > .input-group-btn > .btn {
- height: auto;
-}
-.input-group-sm > .form-control,
-.input-group-sm > .input-group-addon,
-.input-group-sm > .input-group-btn > .btn {
- height: 30px;
- padding: 5px 10px;
- font-size: 12px;
- line-height: 1.5;
- border-radius: 3px;
-}
-select.input-group-sm > .form-control,
-select.input-group-sm > .input-group-addon,
-select.input-group-sm > .input-group-btn > .btn {
- height: 30px;
- line-height: 30px;
-}
-textarea.input-group-sm > .form-control,
-textarea.input-group-sm > .input-group-addon,
-textarea.input-group-sm > .input-group-btn > .btn,
-select[multiple].input-group-sm > .form-control,
-select[multiple].input-group-sm > .input-group-addon,
-select[multiple].input-group-sm > .input-group-btn > .btn {
- height: auto;
-}
+
.input-group-addon,
.input-group-btn,
.input-group .form-control {
- display: table-cell;
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-align: center;
+ align-items: center;
}
+
.input-group-addon:not(:first-child):not(:last-child),
.input-group-btn:not(:first-child):not(:last-child),
.input-group .form-control:not(:first-child):not(:last-child) {
border-radius: 0;
}
+
.input-group-addon,
.input-group-btn {
- width: 1%;
white-space: nowrap;
vertical-align: middle;
}
+
.input-group-addon {
- padding: 6px 12px;
- font-size: 14px;
+ padding: 0.5rem 0.75rem;
+ margin-bottom: 0;
+ font-size: 1rem;
font-weight: normal;
- line-height: 1;
- color: #555;
+ line-height: 1.25;
+ color: #495057;
text-align: center;
- background-color: #eee;
- border: 1px solid #ccc;
- border-radius: 4px;
+ background-color: #e9ecef;
+ border: 1px solid rgba(0, 0, 0, 0.15);
+ border-radius: 0.25rem;
}
-.input-group-addon.input-sm {
- padding: 5px 10px;
- font-size: 12px;
- border-radius: 3px;
+
+.input-group-addon.form-control-sm,
+.input-group-sm > .input-group-addon,
+.input-group-sm > .input-group-btn > .input-group-addon.btn {
+ padding: 0.25rem 0.5rem;
+ font-size: 0.875rem;
+ border-radius: 0.2rem;
}
-.input-group-addon.input-lg {
- padding: 10px 16px;
- font-size: 18px;
- border-radius: 6px;
+
+.input-group-addon.form-control-lg,
+.input-group-lg > .input-group-addon,
+.input-group-lg > .input-group-btn > .input-group-addon.btn {
+ padding: 0.5rem 1rem;
+ font-size: 1.25rem;
+ border-radius: 0.3rem;
}
+
.input-group-addon input[type="radio"],
.input-group-addon input[type="checkbox"] {
margin-top: 0;
}
-.input-group .form-control:first-child,
-.input-group-addon:first-child,
-.input-group-btn:first-child > .btn,
-.input-group-btn:first-child > .btn-group > .btn,
-.input-group-btn:first-child > .dropdown-toggle,
-.input-group-btn:last-child > .btn:not(:last-child):not(.dropdown-toggle),
-.input-group-btn:last-child > .btn-group:not(:last-child) > .btn {
+
+.input-group .form-control:not(:last-child),
+.input-group-addon:not(:last-child),
+.input-group-btn:not(:last-child) > .btn,
+.input-group-btn:not(:last-child) > .btn-group > .btn,
+.input-group-btn:not(:last-child) > .dropdown-toggle,
+.input-group-btn:not(:first-child) > .btn:not(:last-child):not(.dropdown-toggle),
+.input-group-btn:not(:first-child) > .btn-group:not(:last-child) > .btn {
border-top-right-radius: 0;
border-bottom-right-radius: 0;
}
-.input-group-addon:first-child {
+
+.input-group-addon:not(:last-child) {
border-right: 0;
}
-.input-group .form-control:last-child,
-.input-group-addon:last-child,
-.input-group-btn:last-child > .btn,
-.input-group-btn:last-child > .btn-group > .btn,
-.input-group-btn:last-child > .dropdown-toggle,
-.input-group-btn:first-child > .btn:not(:first-child),
-.input-group-btn:first-child > .btn-group:not(:first-child) > .btn {
+
+.input-group .form-control:not(:first-child),
+.input-group-addon:not(:first-child),
+.input-group-btn:not(:first-child) > .btn,
+.input-group-btn:not(:first-child) > .btn-group > .btn,
+.input-group-btn:not(:first-child) > .dropdown-toggle,
+.input-group-btn:not(:last-child) > .btn:not(:first-child),
+.input-group-btn:not(:last-child) > .btn-group:not(:first-child) > .btn {
border-top-left-radius: 0;
border-bottom-left-radius: 0;
}
-.input-group-addon:last-child {
+
+.form-control + .input-group-addon:not(:first-child) {
border-left: 0;
}
+
.input-group-btn {
position: relative;
font-size: 0;
white-space: nowrap;
}
+
.input-group-btn > .btn {
position: relative;
}
+
.input-group-btn > .btn + .btn {
margin-left: -1px;
}
-.input-group-btn > .btn:hover,
-.input-group-btn > .btn:focus,
-.input-group-btn > .btn:active {
- z-index: 2;
+
+.input-group-btn > .btn:focus, .input-group-btn > .btn:active, .input-group-btn > .btn:hover {
+ z-index: 3;
}
-.input-group-btn:first-child > .btn,
-.input-group-btn:first-child > .btn-group {
+
+.input-group-btn:not(:last-child) > .btn,
+.input-group-btn:not(:last-child) > .btn-group {
margin-right: -1px;
}
-.input-group-btn:last-child > .btn,
-.input-group-btn:last-child > .btn-group {
+
+.input-group-btn:not(:first-child) > .btn,
+.input-group-btn:not(:first-child) > .btn-group {
z-index: 2;
margin-left: -1px;
}
-.nav {
- padding-left: 0;
- margin-bottom: 0;
- list-style: none;
+
+.input-group-btn:not(:first-child) > .btn:focus, .input-group-btn:not(:first-child) > .btn:active, .input-group-btn:not(:first-child) > .btn:hover,
+.input-group-btn:not(:first-child) > .btn-group:focus,
+.input-group-btn:not(:first-child) > .btn-group:active,
+.input-group-btn:not(:first-child) > .btn-group:hover {
+ z-index: 3;
}
-.nav > li {
+
+.custom-control {
position: relative;
- display: block;
+ display: -ms-inline-flexbox;
+ display: inline-flex;
+ min-height: 1.5rem;
+ padding-left: 1.5rem;
+ margin-right: 1rem;
}
-.nav > li > a {
- position: relative;
- display: block;
- padding: 10px 15px;
+
+.custom-control-input {
+ position: absolute;
+ z-index: -1;
+ opacity: 0;
}
-.nav > li > a:hover,
-.nav > li > a:focus {
- text-decoration: none;
- background-color: #eee;
+
+.custom-control-input:checked ~ .custom-control-indicator {
+ color: #fff;
+ background-color: #007bff;
}
-.nav > li.disabled > a {
- color: #777;
+
+.custom-control-input:focus ~ .custom-control-indicator {
+ box-shadow: 0 0 0 1px #fff, 0 0 0 3px #007bff;
}
-.nav > li.disabled > a:hover,
-.nav > li.disabled > a:focus {
- color: #777;
- text-decoration: none;
- cursor: not-allowed;
- background-color: transparent;
+
+.custom-control-input:active ~ .custom-control-indicator {
+ color: #fff;
+ background-color: #b3d7ff;
}
-.nav .open > a,
-.nav .open > a:hover,
-.nav .open > a:focus {
- background-color: #eee;
- border-color: #337ab7;
+
+.custom-control-input:disabled ~ .custom-control-indicator {
+ background-color: #e9ecef;
}
-.nav .nav-divider {
- height: 1px;
- margin: 9px 0;
- overflow: hidden;
- background-color: #e5e5e5;
+
+.custom-control-input:disabled ~ .custom-control-description {
+ color: #868e96;
}
-.nav > li > a > img {
- max-width: none;
+
+.custom-control-indicator {
+ position: absolute;
+ top: 0.25rem;
+ left: 0;
+ display: block;
+ width: 1rem;
+ height: 1rem;
+ pointer-events: none;
+ -webkit-user-select: none;
+ -moz-user-select: none;
+ -ms-user-select: none;
+ user-select: none;
+ background-color: #ddd;
+ background-repeat: no-repeat;
+ background-position: center center;
+ background-size: 50% 50%;
}
-.nav-tabs {
- border-bottom: 1px solid #ddd;
+
+.custom-checkbox .custom-control-indicator {
+ border-radius: 0.25rem;
}
-.nav-tabs > li {
- float: left;
- margin-bottom: -1px;
+
+.custom-checkbox .custom-control-input:checked ~ .custom-control-indicator {
+ background-image: url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 8 8'%3E%3Cpath fill='%23fff' d='M6.564.75l-3.59 3.612-1.538-1.55L0 4.26 2.974 7.25 8 2.193z'/%3E%3C/svg%3E");
}
-.nav-tabs > li > a {
- margin-right: 2px;
- line-height: 1.42857143;
- border: 1px solid transparent;
- border-radius: 4px 4px 0 0;
+
+.custom-checkbox .custom-control-input:indeterminate ~ .custom-control-indicator {
+ background-color: #007bff;
+ background-image: url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 4 4'%3E%3Cpath stroke='%23fff' d='M0 2h4'/%3E%3C/svg%3E");
}
-.nav-tabs > li > a:hover {
- border-color: #eee #eee #ddd;
+
+.custom-radio .custom-control-indicator {
+ border-radius: 50%;
}
-.nav-tabs > li.active > a,
-.nav-tabs > li.active > a:hover,
-.nav-tabs > li.active > a:focus {
- color: #555;
- cursor: default;
- background-color: #fff;
- border: 1px solid #ddd;
- border-bottom-color: transparent;
+
+.custom-radio .custom-control-input:checked ~ .custom-control-indicator {
+ background-image: url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='-4 -4 8 8'%3E%3Ccircle r='3' fill='%23fff'/%3E%3C/svg%3E");
}
-.nav-tabs.nav-justified {
- width: 100%;
- border-bottom: 0;
+
+.custom-controls-stacked {
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-direction: column;
+ flex-direction: column;
}
-.nav-tabs.nav-justified > li {
- float: none;
+
+.custom-controls-stacked .custom-control {
+ margin-bottom: 0.25rem;
}
-.nav-tabs.nav-justified > li > a {
- margin-bottom: 5px;
- text-align: center;
+
+.custom-controls-stacked .custom-control + .custom-control {
+ margin-left: 0;
}
-.nav-tabs.nav-justified > .dropdown .dropdown-menu {
- top: auto;
- left: auto;
+
+.custom-select {
+ display: inline-block;
+ max-width: 100%;
+ height: calc(2.25rem + 2px);
+ padding: 0.375rem 1.75rem 0.375rem 0.75rem;
+ line-height: 1.25;
+ color: #495057;
+ vertical-align: middle;
+ background: #fff url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 4 5'%3E%3Cpath fill='%23333' d='M2 0L0 2h4zm0 5L0 3h4z'/%3E%3C/svg%3E") no-repeat right 0.75rem center;
+ background-size: 8px 10px;
+ border: 1px solid rgba(0, 0, 0, 0.15);
+ border-radius: 0.25rem;
+ -webkit-appearance: none;
+ -moz-appearance: none;
+ appearance: none;
}
-@media (min-width: 768px) {
- .nav-tabs.nav-justified > li {
- display: table-cell;
- width: 1%;
- }
- .nav-tabs.nav-justified > li > a {
- margin-bottom: 0;
- }
+
+.custom-select:focus {
+ border-color: #80bdff;
+ outline: none;
}
-.nav-tabs.nav-justified > li > a {
- margin-right: 0;
- border-radius: 4px;
+
+.custom-select:focus::-ms-value {
+ color: #495057;
+ background-color: #fff;
}
-.nav-tabs.nav-justified > .active > a,
-.nav-tabs.nav-justified > .active > a:hover,
-.nav-tabs.nav-justified > .active > a:focus {
- border: 1px solid #ddd;
+
+.custom-select:disabled {
+ color: #868e96;
+ background-color: #e9ecef;
}
-@media (min-width: 768px) {
- .nav-tabs.nav-justified > li > a {
- border-bottom: 1px solid #ddd;
- border-radius: 4px 4px 0 0;
- }
- .nav-tabs.nav-justified > .active > a,
- .nav-tabs.nav-justified > .active > a:hover,
- .nav-tabs.nav-justified > .active > a:focus {
- border-bottom-color: #fff;
- }
+
+.custom-select::-ms-expand {
+ opacity: 0;
}
-.nav-pills > li {
- float: left;
+
+.custom-select-sm {
+ height: calc(1.8125rem + 2px);
+ padding-top: 0.375rem;
+ padding-bottom: 0.375rem;
+ font-size: 75%;
}
-.nav-pills > li > a {
- border-radius: 4px;
+
+.custom-file {
+ position: relative;
+ display: inline-block;
+ max-width: 100%;
+ height: 2.5rem;
+ margin-bottom: 0;
}
-.nav-pills > li + li {
- margin-left: 2px;
+
+.custom-file-input {
+ min-width: 14rem;
+ max-width: 100%;
+ height: 2.5rem;
+ margin: 0;
+ opacity: 0;
}
-.nav-pills > li.active > a,
-.nav-pills > li.active > a:hover,
-.nav-pills > li.active > a:focus {
- color: #fff;
- background-color: #337ab7;
+
+.custom-file-control {
+ position: absolute;
+ top: 0;
+ right: 0;
+ left: 0;
+ z-index: 5;
+ height: 2.5rem;
+ padding: 0.5rem 1rem;
+ line-height: 1.5;
+ color: #495057;
+ pointer-events: none;
+ -webkit-user-select: none;
+ -moz-user-select: none;
+ -ms-user-select: none;
+ user-select: none;
+ background-color: #fff;
+ border: 1px solid rgba(0, 0, 0, 0.15);
+ border-radius: 0.25rem;
}
-.nav-stacked > li {
- float: none;
+
+.custom-file-control:lang(en):empty::after {
+ content: "Choose file...";
}
-.nav-stacked > li + li {
- margin-top: 2px;
- margin-left: 0;
+
+.custom-file-control::before {
+ position: absolute;
+ top: -1px;
+ right: -1px;
+ bottom: -1px;
+ z-index: 6;
+ display: block;
+ height: 2.5rem;
+ padding: 0.5rem 1rem;
+ line-height: 1.5;
+ color: #495057;
+ background-color: #e9ecef;
+ border: 1px solid rgba(0, 0, 0, 0.15);
+ border-radius: 0 0.25rem 0.25rem 0;
}
-.nav-justified {
- width: 100%;
+
+.custom-file-control:lang(en)::before {
+ content: "Browse";
}
-.nav-justified > li {
- float: none;
+
+.nav {
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-wrap: wrap;
+ flex-wrap: wrap;
+ padding-left: 0;
+ margin-bottom: 0;
+ list-style: none;
}
-.nav-justified > li > a {
- margin-bottom: 5px;
- text-align: center;
+
+.nav-link {
+ display: block;
+ padding: 0.5rem 1rem;
}
-.nav-justified > .dropdown .dropdown-menu {
- top: auto;
- left: auto;
+
+.nav-link:focus, .nav-link:hover {
+ text-decoration: none;
}
-@media (min-width: 768px) {
- .nav-justified > li {
- display: table-cell;
- width: 1%;
- }
- .nav-justified > li > a {
- margin-bottom: 0;
- }
+
+.nav-link.disabled {
+ color: #868e96;
}
-.nav-tabs-justified {
- border-bottom: 0;
+
+.nav-tabs {
+ border-bottom: 1px solid #ddd;
}
-.nav-tabs-justified > li > a {
- margin-right: 0;
- border-radius: 4px;
+
+.nav-tabs .nav-item {
+ margin-bottom: -1px;
}
-.nav-tabs-justified > .active > a,
-.nav-tabs-justified > .active > a:hover,
-.nav-tabs-justified > .active > a:focus {
- border: 1px solid #ddd;
+
+.nav-tabs .nav-link {
+ border: 1px solid transparent;
+ border-top-left-radius: 0.25rem;
+ border-top-right-radius: 0.25rem;
}
-@media (min-width: 768px) {
- .nav-tabs-justified > li > a {
- border-bottom: 1px solid #ddd;
- border-radius: 4px 4px 0 0;
- }
- .nav-tabs-justified > .active > a,
- .nav-tabs-justified > .active > a:hover,
- .nav-tabs-justified > .active > a:focus {
- border-bottom-color: #fff;
- }
+
+.nav-tabs .nav-link:focus, .nav-tabs .nav-link:hover {
+ border-color: #e9ecef #e9ecef #ddd;
}
-.tab-content > .tab-pane {
- display: none;
+
+.nav-tabs .nav-link.disabled {
+ color: #868e96;
+ background-color: transparent;
+ border-color: transparent;
}
-.tab-content > .active {
- display: block;
+
+.nav-tabs .nav-link.active,
+.nav-tabs .nav-item.show .nav-link {
+ color: #495057;
+ background-color: #fff;
+ border-color: #ddd #ddd #fff;
}
+
.nav-tabs .dropdown-menu {
margin-top: -1px;
border-top-left-radius: 0;
border-top-right-radius: 0;
}
-.navbar {
- position: relative;
- min-height: 50px;
- margin-bottom: 20px;
- border: 1px solid transparent;
-}
-@media (min-width: 768px) {
- .navbar {
- border-radius: 4px;
- }
-}
-@media (min-width: 768px) {
- .navbar-header {
- float: left;
- }
-}
-.navbar-collapse {
- padding-right: 15px;
- padding-left: 15px;
- overflow-x: visible;
- -webkit-overflow-scrolling: touch;
- border-top: 1px solid transparent;
- -webkit-box-shadow: inset 0 1px 0 rgba(255, 255, 255, .1);
- box-shadow: inset 0 1px 0 rgba(255, 255, 255, .1);
-}
-.navbar-collapse.in {
- overflow-y: auto;
-}
-@media (min-width: 768px) {
- .navbar-collapse {
- width: auto;
- border-top: 0;
- -webkit-box-shadow: none;
- box-shadow: none;
- }
- .navbar-collapse.collapse {
- display: block !important;
- height: auto !important;
- padding-bottom: 0;
- overflow: visible !important;
- }
- .navbar-collapse.in {
- overflow-y: visible;
- }
- .navbar-fixed-top .navbar-collapse,
- .navbar-static-top .navbar-collapse,
- .navbar-fixed-bottom .navbar-collapse {
- padding-right: 0;
- padding-left: 0;
- }
+
+.nav-pills .nav-link {
+ border-radius: 0.25rem;
}
-.navbar-fixed-top .navbar-collapse,
-.navbar-fixed-bottom .navbar-collapse {
- max-height: 340px;
+
+.nav-pills .nav-link.active,
+.show > .nav-pills .nav-link {
+ color: #fff;
+ background-color: #007bff;
}
-@media (max-device-width: 480px) and (orientation: landscape) {
- .navbar-fixed-top .navbar-collapse,
- .navbar-fixed-bottom .navbar-collapse {
- max-height: 200px;
- }
+
+.nav-fill .nav-item {
+ -ms-flex: 1 1 auto;
+ flex: 1 1 auto;
+ text-align: center;
}
-.container > .navbar-header,
-.container-fluid > .navbar-header,
-.container > .navbar-collapse,
-.container-fluid > .navbar-collapse {
- margin-right: -15px;
- margin-left: -15px;
+
+.nav-justified .nav-item {
+ -ms-flex-preferred-size: 0;
+ flex-basis: 0;
+ -ms-flex-positive: 1;
+ flex-grow: 1;
+ text-align: center;
}
-@media (min-width: 768px) {
- .container > .navbar-header,
- .container-fluid > .navbar-header,
- .container > .navbar-collapse,
- .container-fluid > .navbar-collapse {
- margin-right: 0;
- margin-left: 0;
- }
+
+.tab-content > .tab-pane {
+ display: none;
}
-.navbar-static-top {
- z-index: 1000;
- border-width: 0 0 1px;
+
+.tab-content > .active {
+ display: block;
}
-@media (min-width: 768px) {
- .navbar-static-top {
- border-radius: 0;
- }
+
+.navbar {
+ position: relative;
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-wrap: wrap;
+ flex-wrap: wrap;
+ -ms-flex-align: center;
+ align-items: center;
+ -ms-flex-pack: justify;
+ justify-content: space-between;
+ padding: 0.5rem 1rem;
}
-.navbar-fixed-top,
-.navbar-fixed-bottom {
- position: fixed;
- right: 0;
- left: 0;
- z-index: 1030;
+
+.navbar > .container,
+.navbar > .container-fluid {
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-wrap: wrap;
+ flex-wrap: wrap;
+ -ms-flex-align: center;
+ align-items: center;
+ -ms-flex-pack: justify;
+ justify-content: space-between;
}
-@media (min-width: 768px) {
- .navbar-fixed-top,
- .navbar-fixed-bottom {
- border-radius: 0;
- }
+
+.navbar-brand {
+ display: inline-block;
+ padding-top: 0.3125rem;
+ padding-bottom: 0.3125rem;
+ margin-right: 1rem;
+ font-size: 1.25rem;
+ line-height: inherit;
+ white-space: nowrap;
}
-.navbar-fixed-top {
- top: 0;
- border-width: 0 0 1px;
+
+.navbar-brand:focus, .navbar-brand:hover {
+ text-decoration: none;
}
-.navbar-fixed-bottom {
- bottom: 0;
+
+.navbar-nav {
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-direction: column;
+ flex-direction: column;
+ padding-left: 0;
margin-bottom: 0;
- border-width: 1px 0 0;
+ list-style: none;
}
-.navbar-brand {
- float: left;
- height: 50px;
- padding: 15px 15px;
- font-size: 18px;
- line-height: 20px;
+
+.navbar-nav .nav-link {
+ padding-right: 0;
+ padding-left: 0;
}
-.navbar-brand:hover,
-.navbar-brand:focus {
- text-decoration: none;
+
+.navbar-nav .dropdown-menu {
+ position: static;
+ float: none;
}
-.navbar-brand > img {
- display: block;
+
+.navbar-text {
+ display: inline-block;
+ padding-top: 0.5rem;
+ padding-bottom: 0.5rem;
}
-@media (min-width: 768px) {
- .navbar > .container .navbar-brand,
- .navbar > .container-fluid .navbar-brand {
- margin-left: -15px;
- }
+
+.navbar-collapse {
+ -ms-flex-preferred-size: 100%;
+ flex-basis: 100%;
+ -ms-flex-align: center;
+ align-items: center;
}
-.navbar-toggle {
- position: relative;
- float: right;
- padding: 9px 10px;
- margin-top: 8px;
- margin-right: 15px;
- margin-bottom: 8px;
- background-color: transparent;
- background-image: none;
+
+.navbar-toggler {
+ padding: 0.25rem 0.75rem;
+ font-size: 1.25rem;
+ line-height: 1;
+ background: transparent;
border: 1px solid transparent;
- border-radius: 4px;
+ border-radius: 0.25rem;
}
-.navbar-toggle:focus {
- outline: 0;
-}
-.navbar-toggle .icon-bar {
- display: block;
- width: 22px;
- height: 2px;
- border-radius: 1px;
+
+.navbar-toggler:focus, .navbar-toggler:hover {
+ text-decoration: none;
}
-.navbar-toggle .icon-bar + .icon-bar {
- margin-top: 4px;
+
+.navbar-toggler-icon {
+ display: inline-block;
+ width: 1.5em;
+ height: 1.5em;
+ vertical-align: middle;
+ content: "";
+ background: no-repeat center center;
+ background-size: 100% 100%;
}
-@media (min-width: 768px) {
- .navbar-toggle {
- display: none;
+
+@media (max-width: 575px) {
+ .navbar-expand-sm > .container,
+ .navbar-expand-sm > .container-fluid {
+ padding-right: 0;
+ padding-left: 0;
}
}
-.navbar-nav {
- margin: 7.5px -15px;
-}
-.navbar-nav > li > a {
- padding-top: 10px;
- padding-bottom: 10px;
- line-height: 20px;
-}
-@media (max-width: 767px) {
- .navbar-nav .open .dropdown-menu {
- position: static;
- float: none;
- width: auto;
- margin-top: 0;
- background-color: transparent;
- border: 0;
- -webkit-box-shadow: none;
- box-shadow: none;
+
+@media (min-width: 576px) {
+ .navbar-expand-sm {
+ -ms-flex-direction: row;
+ flex-direction: row;
+ -ms-flex-wrap: nowrap;
+ flex-wrap: nowrap;
+ -ms-flex-pack: start;
+ justify-content: flex-start;
+ }
+ .navbar-expand-sm .navbar-nav {
+ -ms-flex-direction: row;
+ flex-direction: row;
+ }
+ .navbar-expand-sm .navbar-nav .dropdown-menu {
+ position: absolute;
+ }
+ .navbar-expand-sm .navbar-nav .dropdown-menu-right {
+ right: 0;
+ left: auto;
+ }
+ .navbar-expand-sm .navbar-nav .nav-link {
+ padding-right: .5rem;
+ padding-left: .5rem;
}
- .navbar-nav .open .dropdown-menu > li > a,
- .navbar-nav .open .dropdown-menu .dropdown-header {
- padding: 5px 15px 5px 25px;
+ .navbar-expand-sm > .container,
+ .navbar-expand-sm > .container-fluid {
+ -ms-flex-wrap: nowrap;
+ flex-wrap: nowrap;
}
- .navbar-nav .open .dropdown-menu > li > a {
- line-height: 20px;
+ .navbar-expand-sm .navbar-collapse {
+ display: -ms-flexbox !important;
+ display: flex !important;
+ }
+ .navbar-expand-sm .navbar-toggler {
+ display: none;
}
- .navbar-nav .open .dropdown-menu > li > a:hover,
- .navbar-nav .open .dropdown-menu > li > a:focus {
- background-image: none;
+}
+
+@media (max-width: 767px) {
+ .navbar-expand-md > .container,
+ .navbar-expand-md > .container-fluid {
+ padding-right: 0;
+ padding-left: 0;
}
}
+
@media (min-width: 768px) {
- .navbar-nav {
- float: left;
- margin: 0;
+ .navbar-expand-md {
+ -ms-flex-direction: row;
+ flex-direction: row;
+ -ms-flex-wrap: nowrap;
+ flex-wrap: nowrap;
+ -ms-flex-pack: start;
+ justify-content: flex-start;
+ }
+ .navbar-expand-md .navbar-nav {
+ -ms-flex-direction: row;
+ flex-direction: row;
+ }
+ .navbar-expand-md .navbar-nav .dropdown-menu {
+ position: absolute;
+ }
+ .navbar-expand-md .navbar-nav .dropdown-menu-right {
+ right: 0;
+ left: auto;
}
- .navbar-nav > li {
- float: left;
+ .navbar-expand-md .navbar-nav .nav-link {
+ padding-right: .5rem;
+ padding-left: .5rem;
}
- .navbar-nav > li > a {
- padding-top: 15px;
- padding-bottom: 15px;
+ .navbar-expand-md > .container,
+ .navbar-expand-md > .container-fluid {
+ -ms-flex-wrap: nowrap;
+ flex-wrap: nowrap;
}
-}
-.navbar-form {
- padding: 10px 15px;
- margin-top: 8px;
- margin-right: -15px;
- margin-bottom: 8px;
- margin-left: -15px;
- border-top: 1px solid transparent;
- border-bottom: 1px solid transparent;
- -webkit-box-shadow: inset 0 1px 0 rgba(255, 255, 255, .1), 0 1px 0 rgba(255, 255, 255, .1);
- box-shadow: inset 0 1px 0 rgba(255, 255, 255, .1), 0 1px 0 rgba(255, 255, 255, .1);
-}
-@media (min-width: 768px) {
- .navbar-form .form-group {
- display: inline-block;
- margin-bottom: 0;
- vertical-align: middle;
+ .navbar-expand-md .navbar-collapse {
+ display: -ms-flexbox !important;
+ display: flex !important;
}
- .navbar-form .form-control {
- display: inline-block;
- width: auto;
- vertical-align: middle;
+ .navbar-expand-md .navbar-toggler {
+ display: none;
}
- .navbar-form .form-control-static {
- display: inline-block;
+}
+
+@media (max-width: 991px) {
+ .navbar-expand-lg > .container,
+ .navbar-expand-lg > .container-fluid {
+ padding-right: 0;
+ padding-left: 0;
}
- .navbar-form .input-group {
- display: inline-table;
- vertical-align: middle;
+}
+
+@media (min-width: 992px) {
+ .navbar-expand-lg {
+ -ms-flex-direction: row;
+ flex-direction: row;
+ -ms-flex-wrap: nowrap;
+ flex-wrap: nowrap;
+ -ms-flex-pack: start;
+ justify-content: flex-start;
+ }
+ .navbar-expand-lg .navbar-nav {
+ -ms-flex-direction: row;
+ flex-direction: row;
+ }
+ .navbar-expand-lg .navbar-nav .dropdown-menu {
+ position: absolute;
+ }
+ .navbar-expand-lg .navbar-nav .dropdown-menu-right {
+ right: 0;
+ left: auto;
}
- .navbar-form .input-group .input-group-addon,
- .navbar-form .input-group .input-group-btn,
- .navbar-form .input-group .form-control {
- width: auto;
+ .navbar-expand-lg .navbar-nav .nav-link {
+ padding-right: .5rem;
+ padding-left: .5rem;
}
- .navbar-form .input-group > .form-control {
- width: 100%;
+ .navbar-expand-lg > .container,
+ .navbar-expand-lg > .container-fluid {
+ -ms-flex-wrap: nowrap;
+ flex-wrap: nowrap;
}
- .navbar-form .control-label {
- margin-bottom: 0;
- vertical-align: middle;
+ .navbar-expand-lg .navbar-collapse {
+ display: -ms-flexbox !important;
+ display: flex !important;
}
- .navbar-form .radio,
- .navbar-form .checkbox {
- display: inline-block;
- margin-top: 0;
- margin-bottom: 0;
- vertical-align: middle;
+ .navbar-expand-lg .navbar-toggler {
+ display: none;
}
- .navbar-form .radio label,
- .navbar-form .checkbox label {
+}
+
+@media (max-width: 1199px) {
+ .navbar-expand-xl > .container,
+ .navbar-expand-xl > .container-fluid {
+ padding-right: 0;
padding-left: 0;
}
- .navbar-form .radio input[type="radio"],
- .navbar-form .checkbox input[type="checkbox"] {
- position: relative;
- margin-left: 0;
+}
+
+@media (min-width: 1200px) {
+ .navbar-expand-xl {
+ -ms-flex-direction: row;
+ flex-direction: row;
+ -ms-flex-wrap: nowrap;
+ flex-wrap: nowrap;
+ -ms-flex-pack: start;
+ justify-content: flex-start;
+ }
+ .navbar-expand-xl .navbar-nav {
+ -ms-flex-direction: row;
+ flex-direction: row;
+ }
+ .navbar-expand-xl .navbar-nav .dropdown-menu {
+ position: absolute;
+ }
+ .navbar-expand-xl .navbar-nav .dropdown-menu-right {
+ right: 0;
+ left: auto;
}
- .navbar-form .has-feedback .form-control-feedback {
- top: 0;
+ .navbar-expand-xl .navbar-nav .nav-link {
+ padding-right: .5rem;
+ padding-left: .5rem;
}
-}
-@media (max-width: 767px) {
- .navbar-form .form-group {
- margin-bottom: 5px;
+ .navbar-expand-xl > .container,
+ .navbar-expand-xl > .container-fluid {
+ -ms-flex-wrap: nowrap;
+ flex-wrap: nowrap;
}
- .navbar-form .form-group:last-child {
- margin-bottom: 0;
+ .navbar-expand-xl .navbar-collapse {
+ display: -ms-flexbox !important;
+ display: flex !important;
}
-}
-@media (min-width: 768px) {
- .navbar-form {
- width: auto;
- padding-top: 0;
- padding-bottom: 0;
- margin-right: 0;
- margin-left: 0;
- border: 0;
- -webkit-box-shadow: none;
- box-shadow: none;
+ .navbar-expand-xl .navbar-toggler {
+ display: none;
}
}
-.navbar-nav > li > .dropdown-menu {
- margin-top: 0;
- border-top-left-radius: 0;
- border-top-right-radius: 0;
+
+.navbar-expand {
+ -ms-flex-direction: row;
+ flex-direction: row;
+ -ms-flex-wrap: nowrap;
+ flex-wrap: nowrap;
+ -ms-flex-pack: start;
+ justify-content: flex-start;
}
-.navbar-fixed-bottom .navbar-nav > li > .dropdown-menu {
- margin-bottom: 0;
- border-top-left-radius: 4px;
- border-top-right-radius: 4px;
- border-bottom-right-radius: 0;
- border-bottom-left-radius: 0;
+
+.navbar-expand > .container,
+.navbar-expand > .container-fluid {
+ padding-right: 0;
+ padding-left: 0;
}
-.navbar-btn {
- margin-top: 8px;
- margin-bottom: 8px;
+
+.navbar-expand .navbar-nav {
+ -ms-flex-direction: row;
+ flex-direction: row;
}
-.navbar-btn.btn-sm {
- margin-top: 10px;
- margin-bottom: 10px;
+
+.navbar-expand .navbar-nav .dropdown-menu {
+ position: absolute;
}
-.navbar-btn.btn-xs {
- margin-top: 14px;
- margin-bottom: 14px;
+
+.navbar-expand .navbar-nav .dropdown-menu-right {
+ right: 0;
+ left: auto;
}
-.navbar-text {
- margin-top: 15px;
- margin-bottom: 15px;
+
+.navbar-expand .navbar-nav .nav-link {
+ padding-right: .5rem;
+ padding-left: .5rem;
}
-@media (min-width: 768px) {
- .navbar-text {
- float: left;
- margin-right: 15px;
- margin-left: 15px;
- }
+
+.navbar-expand > .container,
+.navbar-expand > .container-fluid {
+ -ms-flex-wrap: nowrap;
+ flex-wrap: nowrap;
}
-@media (min-width: 768px) {
- .navbar-left {
- float: left !important;
- }
- .navbar-right {
- float: right !important;
- margin-right: -15px;
- }
- .navbar-right ~ .navbar-right {
- margin-right: 0;
- }
+
+.navbar-expand .navbar-collapse {
+ display: -ms-flexbox !important;
+ display: flex !important;
}
-.navbar-default {
- background-color: #f8f8f8;
- border-color: #e7e7e7;
+
+.navbar-expand .navbar-toggler {
+ display: none;
}
-.navbar-default .navbar-brand {
- color: #777;
+
+.navbar-light .navbar-brand {
+ color: rgba(0, 0, 0, 0.9);
}
-.navbar-default .navbar-brand:hover,
-.navbar-default .navbar-brand:focus {
- color: #5e5e5e;
- background-color: transparent;
+
+.navbar-light .navbar-brand:focus, .navbar-light .navbar-brand:hover {
+ color: rgba(0, 0, 0, 0.9);
}
-.navbar-default .navbar-text {
- color: #777;
+
+.navbar-light .navbar-nav .nav-link {
+ color: rgba(0, 0, 0, 0.5);
}
-.navbar-default .navbar-nav > li > a {
- color: #777;
+
+.navbar-light .navbar-nav .nav-link:focus, .navbar-light .navbar-nav .nav-link:hover {
+ color: rgba(0, 0, 0, 0.7);
}
-.navbar-default .navbar-nav > li > a:hover,
-.navbar-default .navbar-nav > li > a:focus {
- color: #333;
- background-color: transparent;
+
+.navbar-light .navbar-nav .nav-link.disabled {
+ color: rgba(0, 0, 0, 0.3);
}
-.navbar-default .navbar-nav > .active > a,
-.navbar-default .navbar-nav > .active > a:hover,
-.navbar-default .navbar-nav > .active > a:focus {
- color: #555;
- background-color: #e7e7e7;
+
+.navbar-light .navbar-nav .show > .nav-link,
+.navbar-light .navbar-nav .active > .nav-link,
+.navbar-light .navbar-nav .nav-link.show,
+.navbar-light .navbar-nav .nav-link.active {
+ color: rgba(0, 0, 0, 0.9);
}
-.navbar-default .navbar-nav > .disabled > a,
-.navbar-default .navbar-nav > .disabled > a:hover,
-.navbar-default .navbar-nav > .disabled > a:focus {
- color: #ccc;
- background-color: transparent;
+
+.navbar-light .navbar-toggler {
+ color: rgba(0, 0, 0, 0.5);
+ border-color: rgba(0, 0, 0, 0.1);
}
-.navbar-default .navbar-toggle {
- border-color: #ddd;
+
+.navbar-light .navbar-toggler-icon {
+ background-image: url("data:image/svg+xml;charset=utf8,%3Csvg viewBox='0 0 30 30' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath stroke='rgba(0, 0, 0, 0.5)' stroke-width='2' stroke-linecap='round' stroke-miterlimit='10' d='M4 7h22M4 15h22M4 23h22'/%3E%3C/svg%3E");
}
-.navbar-default .navbar-toggle:hover,
-.navbar-default .navbar-toggle:focus {
- background-color: #ddd;
+
+.navbar-light .navbar-text {
+ color: rgba(0, 0, 0, 0.5);
}
-.navbar-default .navbar-toggle .icon-bar {
- background-color: #888;
+
+.navbar-dark .navbar-brand {
+ color: white;
}
-.navbar-default .navbar-collapse,
-.navbar-default .navbar-form {
- border-color: #e7e7e7;
+
+.navbar-dark .navbar-brand:focus, .navbar-dark .navbar-brand:hover {
+ color: white;
}
-.navbar-default .navbar-nav > .open > a,
-.navbar-default .navbar-nav > .open > a:hover,
-.navbar-default .navbar-nav > .open > a:focus {
- color: #555;
- background-color: #e7e7e7;
+
+.navbar-dark .navbar-nav .nav-link {
+ color: rgba(255, 255, 255, 0.5);
}
-@media (max-width: 767px) {
- .navbar-default .navbar-nav .open .dropdown-menu > li > a {
- color: #777;
- }
- .navbar-default .navbar-nav .open .dropdown-menu > li > a:hover,
- .navbar-default .navbar-nav .open .dropdown-menu > li > a:focus {
- color: #333;
- background-color: transparent;
- }
- .navbar-default .navbar-nav .open .dropdown-menu > .active > a,
- .navbar-default .navbar-nav .open .dropdown-menu > .active > a:hover,
- .navbar-default .navbar-nav .open .dropdown-menu > .active > a:focus {
- color: #555;
- background-color: #e7e7e7;
- }
- .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a,
- .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a:hover,
- .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a:focus {
- color: #ccc;
- background-color: transparent;
- }
+
+.navbar-dark .navbar-nav .nav-link:focus, .navbar-dark .navbar-nav .nav-link:hover {
+ color: rgba(255, 255, 255, 0.75);
}
-.navbar-default .navbar-link {
- color: #777;
+
+.navbar-dark .navbar-nav .nav-link.disabled {
+ color: rgba(255, 255, 255, 0.25);
}
-.navbar-default .navbar-link:hover {
- color: #333;
+
+.navbar-dark .navbar-nav .show > .nav-link,
+.navbar-dark .navbar-nav .active > .nav-link,
+.navbar-dark .navbar-nav .nav-link.show,
+.navbar-dark .navbar-nav .nav-link.active {
+ color: white;
}
-.navbar-default .btn-link {
- color: #777;
+
+.navbar-dark .navbar-toggler {
+ color: rgba(255, 255, 255, 0.5);
+ border-color: rgba(255, 255, 255, 0.1);
}
-.navbar-default .btn-link:hover,
-.navbar-default .btn-link:focus {
- color: #333;
+
+.navbar-dark .navbar-toggler-icon {
+ background-image: url("data:image/svg+xml;charset=utf8,%3Csvg viewBox='0 0 30 30' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath stroke='rgba(255, 255, 255, 0.5)' stroke-width='2' stroke-linecap='round' stroke-miterlimit='10' d='M4 7h22M4 15h22M4 23h22'/%3E%3C/svg%3E");
}
-.navbar-default .btn-link[disabled]:hover,
-fieldset[disabled] .navbar-default .btn-link:hover,
-.navbar-default .btn-link[disabled]:focus,
-fieldset[disabled] .navbar-default .btn-link:focus {
- color: #ccc;
+
+.navbar-dark .navbar-text {
+ color: rgba(255, 255, 255, 0.5);
}
-.navbar-inverse {
- background-color: #222;
- border-color: #080808;
+
+.card {
+ position: relative;
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-direction: column;
+ flex-direction: column;
+ min-width: 0;
+ word-wrap: break-word;
+ background-color: #fff;
+ background-clip: border-box;
+ border: 1px solid rgba(0, 0, 0, 0.125);
+ border-radius: 0.25rem;
}
-.navbar-inverse .navbar-brand {
- color: #9d9d9d;
+
+.card-body {
+ -ms-flex: 1 1 auto;
+ flex: 1 1 auto;
+ padding: 1.25rem;
}
-.navbar-inverse .navbar-brand:hover,
-.navbar-inverse .navbar-brand:focus {
- color: #fff;
- background-color: transparent;
+
+.card-title {
+ margin-bottom: 0.75rem;
}
-.navbar-inverse .navbar-text {
- color: #9d9d9d;
+
+.card-subtitle {
+ margin-top: -0.375rem;
+ margin-bottom: 0;
}
-.navbar-inverse .navbar-nav > li > a {
- color: #9d9d9d;
+
+.card-text:last-child {
+ margin-bottom: 0;
}
-.navbar-inverse .navbar-nav > li > a:hover,
-.navbar-inverse .navbar-nav > li > a:focus {
- color: #fff;
- background-color: transparent;
+
+.card-link:hover {
+ text-decoration: none;
}
-.navbar-inverse .navbar-nav > .active > a,
-.navbar-inverse .navbar-nav > .active > a:hover,
-.navbar-inverse .navbar-nav > .active > a:focus {
- color: #fff;
- background-color: #080808;
+
+.card-link + .card-link {
+ margin-left: 1.25rem;
}
-.navbar-inverse .navbar-nav > .disabled > a,
-.navbar-inverse .navbar-nav > .disabled > a:hover,
-.navbar-inverse .navbar-nav > .disabled > a:focus {
- color: #444;
- background-color: transparent;
+
+.card > .list-group:first-child .list-group-item:first-child {
+ border-top-left-radius: 0.25rem;
+ border-top-right-radius: 0.25rem;
}
-.navbar-inverse .navbar-toggle {
- border-color: #333;
+
+.card > .list-group:last-child .list-group-item:last-child {
+ border-bottom-right-radius: 0.25rem;
+ border-bottom-left-radius: 0.25rem;
}
-.navbar-inverse .navbar-toggle:hover,
-.navbar-inverse .navbar-toggle:focus {
- background-color: #333;
+
+.card-header {
+ padding: 0.75rem 1.25rem;
+ margin-bottom: 0;
+ background-color: rgba(0, 0, 0, 0.03);
+ border-bottom: 1px solid rgba(0, 0, 0, 0.125);
}
-.navbar-inverse .navbar-toggle .icon-bar {
- background-color: #fff;
+
+.card-header:first-child {
+ border-radius: calc(0.25rem - 1px) calc(0.25rem - 1px) 0 0;
}
-.navbar-inverse .navbar-collapse,
-.navbar-inverse .navbar-form {
- border-color: #101010;
+
+.card-footer {
+ padding: 0.75rem 1.25rem;
+ background-color: rgba(0, 0, 0, 0.03);
+ border-top: 1px solid rgba(0, 0, 0, 0.125);
}
-.navbar-inverse .navbar-nav > .open > a,
-.navbar-inverse .navbar-nav > .open > a:hover,
-.navbar-inverse .navbar-nav > .open > a:focus {
- color: #fff;
- background-color: #080808;
+
+.card-footer:last-child {
+ border-radius: 0 0 calc(0.25rem - 1px) calc(0.25rem - 1px);
}
-@media (max-width: 767px) {
- .navbar-inverse .navbar-nav .open .dropdown-menu > .dropdown-header {
- border-color: #080808;
+
+.card-header-tabs {
+ margin-right: -0.625rem;
+ margin-bottom: -0.75rem;
+ margin-left: -0.625rem;
+ border-bottom: 0;
+}
+
+.card-header-pills {
+ margin-right: -0.625rem;
+ margin-left: -0.625rem;
+}
+
+.card-img-overlay {
+ position: absolute;
+ top: 0;
+ right: 0;
+ bottom: 0;
+ left: 0;
+ padding: 1.25rem;
+}
+
+.card-img {
+ width: 100%;
+ border-radius: calc(0.25rem - 1px);
+}
+
+.card-img-top {
+ width: 100%;
+ border-top-left-radius: calc(0.25rem - 1px);
+ border-top-right-radius: calc(0.25rem - 1px);
+}
+
+.card-img-bottom {
+ width: 100%;
+ border-bottom-right-radius: calc(0.25rem - 1px);
+ border-bottom-left-radius: calc(0.25rem - 1px);
+}
+
+@media (min-width: 576px) {
+ .card-deck {
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-flow: row wrap;
+ flex-flow: row wrap;
+ margin-right: -15px;
+ margin-left: -15px;
}
- .navbar-inverse .navbar-nav .open .dropdown-menu .divider {
- background-color: #080808;
+ .card-deck .card {
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex: 1 0 0%;
+ flex: 1 0 0%;
+ -ms-flex-direction: column;
+ flex-direction: column;
+ margin-right: 15px;
+ margin-left: 15px;
}
- .navbar-inverse .navbar-nav .open .dropdown-menu > li > a {
- color: #9d9d9d;
+}
+
+@media (min-width: 576px) {
+ .card-group {
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-flow: row wrap;
+ flex-flow: row wrap;
+ }
+ .card-group .card {
+ -ms-flex: 1 0 0%;
+ flex: 1 0 0%;
+ }
+ .card-group .card + .card {
+ margin-left: 0;
+ border-left: 0;
}
- .navbar-inverse .navbar-nav .open .dropdown-menu > li > a:hover,
- .navbar-inverse .navbar-nav .open .dropdown-menu > li > a:focus {
- color: #fff;
- background-color: transparent;
+ .card-group .card:first-child {
+ border-top-right-radius: 0;
+ border-bottom-right-radius: 0;
}
- .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a,
- .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a:hover,
- .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a:focus {
- color: #fff;
- background-color: #080808;
+ .card-group .card:first-child .card-img-top {
+ border-top-right-radius: 0;
}
- .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a,
- .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a:hover,
- .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a:focus {
- color: #444;
- background-color: transparent;
+ .card-group .card:first-child .card-img-bottom {
+ border-bottom-right-radius: 0;
+ }
+ .card-group .card:last-child {
+ border-top-left-radius: 0;
+ border-bottom-left-radius: 0;
+ }
+ .card-group .card:last-child .card-img-top {
+ border-top-left-radius: 0;
+ }
+ .card-group .card:last-child .card-img-bottom {
+ border-bottom-left-radius: 0;
+ }
+ .card-group .card:not(:first-child):not(:last-child) {
+ border-radius: 0;
+ }
+ .card-group .card:not(:first-child):not(:last-child) .card-img-top,
+ .card-group .card:not(:first-child):not(:last-child) .card-img-bottom {
+ border-radius: 0;
}
}
-.navbar-inverse .navbar-link {
- color: #9d9d9d;
-}
-.navbar-inverse .navbar-link:hover {
- color: #fff;
-}
-.navbar-inverse .btn-link {
- color: #9d9d9d;
-}
-.navbar-inverse .btn-link:hover,
-.navbar-inverse .btn-link:focus {
- color: #fff;
+
+.card-columns .card {
+ margin-bottom: 0.75rem;
}
-.navbar-inverse .btn-link[disabled]:hover,
-fieldset[disabled] .navbar-inverse .btn-link:hover,
-.navbar-inverse .btn-link[disabled]:focus,
-fieldset[disabled] .navbar-inverse .btn-link:focus {
- color: #444;
+
+@media (min-width: 576px) {
+ .card-columns {
+ -webkit-column-count: 3;
+ column-count: 3;
+ -webkit-column-gap: 1.25rem;
+ column-gap: 1.25rem;
+ }
+ .card-columns .card {
+ display: inline-block;
+ width: 100%;
+ }
}
+
.breadcrumb {
- padding: 8px 15px;
- margin-bottom: 20px;
+ padding: 0.75rem 1rem;
+ margin-bottom: 1rem;
list-style: none;
- background-color: #f5f5f5;
- border-radius: 4px;
+ background-color: #e9ecef;
+ border-radius: 0.25rem;
+}
+
+.breadcrumb::after {
+ display: block;
+ clear: both;
+ content: "";
+}
+
+.breadcrumb-item {
+ float: left;
}
-.breadcrumb > li {
+
+.breadcrumb-item + .breadcrumb-item::before {
display: inline-block;
+ padding-right: 0.5rem;
+ padding-left: 0.5rem;
+ color: #868e96;
+ content: "/";
}
-.breadcrumb > li + li:before {
- padding: 0 5px;
- color: #ccc;
- content: "/\00a0";
+
+.breadcrumb-item + .breadcrumb-item:hover::before {
+ text-decoration: underline;
}
-.breadcrumb > .active {
- color: #777;
+
+.breadcrumb-item + .breadcrumb-item:hover::before {
+ text-decoration: none;
+}
+
+.breadcrumb-item.active {
+ color: #868e96;
}
+
.pagination {
- display: inline-block;
+ display: -ms-flexbox;
+ display: flex;
padding-left: 0;
- margin: 20px 0;
- border-radius: 4px;
+ list-style: none;
+ border-radius: 0.25rem;
}
-.pagination > li {
- display: inline;
+
+.page-item:first-child .page-link {
+ margin-left: 0;
+ border-top-left-radius: 0.25rem;
+ border-bottom-left-radius: 0.25rem;
}
-.pagination > li > a,
-.pagination > li > span {
- position: relative;
- float: left;
- padding: 6px 12px;
- margin-left: -1px;
- line-height: 1.42857143;
- color: #337ab7;
- text-decoration: none;
- background-color: #fff;
- border: 1px solid #ddd;
+
+.page-item:last-child .page-link {
+ border-top-right-radius: 0.25rem;
+ border-bottom-right-radius: 0.25rem;
}
-.pagination > li:first-child > a,
-.pagination > li:first-child > span {
- margin-left: 0;
- border-top-left-radius: 4px;
- border-bottom-left-radius: 4px;
-}
-.pagination > li:last-child > a,
-.pagination > li:last-child > span {
- border-top-right-radius: 4px;
- border-bottom-right-radius: 4px;
-}
-.pagination > li > a:hover,
-.pagination > li > span:hover,
-.pagination > li > a:focus,
-.pagination > li > span:focus {
+
+.page-item.active .page-link {
z-index: 2;
- color: #23527c;
- background-color: #eee;
- border-color: #ddd;
-}
-.pagination > .active > a,
-.pagination > .active > span,
-.pagination > .active > a:hover,
-.pagination > .active > span:hover,
-.pagination > .active > a:focus,
-.pagination > .active > span:focus {
- z-index: 3;
color: #fff;
- cursor: default;
- background-color: #337ab7;
- border-color: #337ab7;
-}
-.pagination > .disabled > span,
-.pagination > .disabled > span:hover,
-.pagination > .disabled > span:focus,
-.pagination > .disabled > a,
-.pagination > .disabled > a:hover,
-.pagination > .disabled > a:focus {
- color: #777;
- cursor: not-allowed;
+ background-color: #007bff;
+ border-color: #007bff;
+}
+
+.page-item.disabled .page-link {
+ color: #868e96;
+ pointer-events: none;
background-color: #fff;
border-color: #ddd;
}
-.pagination-lg > li > a,
-.pagination-lg > li > span {
- padding: 10px 16px;
- font-size: 18px;
- line-height: 1.3333333;
-}
-.pagination-lg > li:first-child > a,
-.pagination-lg > li:first-child > span {
- border-top-left-radius: 6px;
- border-bottom-left-radius: 6px;
-}
-.pagination-lg > li:last-child > a,
-.pagination-lg > li:last-child > span {
- border-top-right-radius: 6px;
- border-bottom-right-radius: 6px;
-}
-.pagination-sm > li > a,
-.pagination-sm > li > span {
- padding: 5px 10px;
- font-size: 12px;
- line-height: 1.5;
-}
-.pagination-sm > li:first-child > a,
-.pagination-sm > li:first-child > span {
- border-top-left-radius: 3px;
- border-bottom-left-radius: 3px;
-}
-.pagination-sm > li:last-child > a,
-.pagination-sm > li:last-child > span {
- border-top-right-radius: 3px;
- border-bottom-right-radius: 3px;
-}
-.pager {
- padding-left: 0;
- margin: 20px 0;
- text-align: center;
- list-style: none;
-}
-.pager li {
- display: inline;
-}
-.pager li > a,
-.pager li > span {
- display: inline-block;
- padding: 5px 14px;
+
+.page-link {
+ position: relative;
+ display: block;
+ padding: 0.5rem 0.75rem;
+ margin-left: -1px;
+ line-height: 1.25;
+ color: #007bff;
background-color: #fff;
border: 1px solid #ddd;
- border-radius: 15px;
}
-.pager li > a:hover,
-.pager li > a:focus {
+
+.page-link:focus, .page-link:hover {
+ color: #0056b3;
text-decoration: none;
- background-color: #eee;
+ background-color: #e9ecef;
+ border-color: #ddd;
}
-.pager .next > a,
-.pager .next > span {
- float: right;
+
+.pagination-lg .page-link {
+ padding: 0.75rem 1.5rem;
+ font-size: 1.25rem;
+ line-height: 1.5;
}
-.pager .previous > a,
-.pager .previous > span {
- float: left;
+
+.pagination-lg .page-item:first-child .page-link {
+ border-top-left-radius: 0.3rem;
+ border-bottom-left-radius: 0.3rem;
}
-.pager .disabled > a,
-.pager .disabled > a:hover,
-.pager .disabled > a:focus,
-.pager .disabled > span {
- color: #777;
- cursor: not-allowed;
- background-color: #fff;
+
+.pagination-lg .page-item:last-child .page-link {
+ border-top-right-radius: 0.3rem;
+ border-bottom-right-radius: 0.3rem;
+}
+
+.pagination-sm .page-link {
+ padding: 0.25rem 0.5rem;
+ font-size: 0.875rem;
+ line-height: 1.5;
+}
+
+.pagination-sm .page-item:first-child .page-link {
+ border-top-left-radius: 0.2rem;
+ border-bottom-left-radius: 0.2rem;
}
-.label {
- display: inline;
- padding: .2em .6em .3em;
+
+.pagination-sm .page-item:last-child .page-link {
+ border-top-right-radius: 0.2rem;
+ border-bottom-right-radius: 0.2rem;
+}
+
+.badge {
+ display: inline-block;
+ padding: 0.25em 0.4em;
font-size: 75%;
font-weight: bold;
line-height: 1;
@@ -4852,1020 +3971,620 @@ fieldset[disabled] .navbar-inverse .btn-link:focus {
text-align: center;
white-space: nowrap;
vertical-align: baseline;
- border-radius: .25em;
+ border-radius: 0.25rem;
}
-a.label:hover,
-a.label:focus {
- color: #fff;
- text-decoration: none;
- cursor: pointer;
-}
-.label:empty {
+
+.badge:empty {
display: none;
}
-.btn .label {
+
+.btn .badge {
position: relative;
top: -1px;
}
-.label-default {
- background-color: #777;
-}
-.label-default[href]:hover,
-.label-default[href]:focus {
- background-color: #5e5e5e;
-}
-.label-primary {
- background-color: #337ab7;
-}
-.label-primary[href]:hover,
-.label-primary[href]:focus {
- background-color: #286090;
-}
-.label-success {
- background-color: #5cb85c;
+
+.badge-pill {
+ padding-right: 0.6em;
+ padding-left: 0.6em;
+ border-radius: 10rem;
}
-.label-success[href]:hover,
-.label-success[href]:focus {
- background-color: #449d44;
+
+.badge-primary {
+ color: #fff;
+ background-color: #007bff;
}
-.label-info {
- background-color: #5bc0de;
+
+.badge-primary[href]:focus, .badge-primary[href]:hover {
+ color: #fff;
+ text-decoration: none;
+ background-color: #0062cc;
}
-.label-info[href]:hover,
-.label-info[href]:focus {
- background-color: #31b0d5;
+
+.badge-secondary {
+ color: #fff;
+ background-color: #868e96;
}
-.label-warning {
- background-color: #f0ad4e;
+
+.badge-secondary[href]:focus, .badge-secondary[href]:hover {
+ color: #fff;
+ text-decoration: none;
+ background-color: #6c757d;
}
-.label-warning[href]:hover,
-.label-warning[href]:focus {
- background-color: #ec971f;
+
+.badge-success {
+ color: #fff;
+ background-color: #28a745;
}
-.label-danger {
- background-color: #d9534f;
+
+.badge-success[href]:focus, .badge-success[href]:hover {
+ color: #fff;
+ text-decoration: none;
+ background-color: #1e7e34;
}
-.label-danger[href]:hover,
-.label-danger[href]:focus {
- background-color: #c9302c;
+
+.badge-info {
+ color: #fff;
+ background-color: #17a2b8;
}
-.badge {
- display: inline-block;
- min-width: 10px;
- padding: 3px 7px;
- font-size: 12px;
- font-weight: bold;
- line-height: 1;
+
+.badge-info[href]:focus, .badge-info[href]:hover {
color: #fff;
- text-align: center;
- white-space: nowrap;
- vertical-align: middle;
- background-color: #777;
- border-radius: 10px;
+ text-decoration: none;
+ background-color: #117a8b;
}
-.badge:empty {
- display: none;
+
+.badge-warning {
+ color: #111;
+ background-color: #ffc107;
}
-.btn .badge {
- position: relative;
- top: -1px;
+
+.badge-warning[href]:focus, .badge-warning[href]:hover {
+ color: #111;
+ text-decoration: none;
+ background-color: #d39e00;
}
-.btn-xs .badge,
-.btn-group-xs > .btn .badge {
- top: 0;
- padding: 1px 5px;
+
+.badge-danger {
+ color: #fff;
+ background-color: #dc3545;
}
-a.badge:hover,
-a.badge:focus {
+
+.badge-danger[href]:focus, .badge-danger[href]:hover {
color: #fff;
text-decoration: none;
- cursor: pointer;
+ background-color: #bd2130;
}
-.list-group-item.active > .badge,
-.nav-pills > .active > a > .badge {
- color: #337ab7;
- background-color: #fff;
+
+.badge-light {
+ color: #111;
+ background-color: #f8f9fa;
}
-.list-group-item > .badge {
- float: right;
+
+.badge-light[href]:focus, .badge-light[href]:hover {
+ color: #111;
+ text-decoration: none;
+ background-color: #dae0e5;
}
-.list-group-item > .badge + .badge {
- margin-right: 5px;
+
+.badge-dark {
+ color: #fff;
+ background-color: #343a40;
}
-.nav-pills > li > a > .badge {
- margin-left: 3px;
+
+.badge-dark[href]:focus, .badge-dark[href]:hover {
+ color: #fff;
+ text-decoration: none;
+ background-color: #1d2124;
}
+
.jumbotron {
- padding-top: 30px;
- padding-bottom: 30px;
- margin-bottom: 30px;
- color: inherit;
- background-color: #eee;
-}
-.jumbotron h1,
-.jumbotron .h1 {
- color: inherit;
+ padding: 2rem 1rem;
+ margin-bottom: 2rem;
+ background-color: #e9ecef;
+ border-radius: 0.3rem;
}
-.jumbotron p {
- margin-bottom: 15px;
- font-size: 21px;
- font-weight: 200;
-}
-.jumbotron > hr {
- border-top-color: #d5d5d5;
-}
-.container .jumbotron,
-.container-fluid .jumbotron {
- padding-right: 15px;
- padding-left: 15px;
- border-radius: 6px;
-}
-.jumbotron .container {
- max-width: 100%;
-}
-@media screen and (min-width: 768px) {
+
+@media (min-width: 576px) {
.jumbotron {
- padding-top: 48px;
- padding-bottom: 48px;
- }
- .container .jumbotron,
- .container-fluid .jumbotron {
- padding-right: 60px;
- padding-left: 60px;
- }
- .jumbotron h1,
- .jumbotron .h1 {
- font-size: 63px;
+ padding: 4rem 2rem;
}
}
-.thumbnail {
- display: block;
- padding: 4px;
- margin-bottom: 20px;
- line-height: 1.42857143;
- background-color: #fff;
- border: 1px solid #ddd;
- border-radius: 4px;
- -webkit-transition: border .2s ease-in-out;
- -o-transition: border .2s ease-in-out;
- transition: border .2s ease-in-out;
-}
-.thumbnail > img,
-.thumbnail a > img {
- margin-right: auto;
- margin-left: auto;
-}
-a.thumbnail:hover,
-a.thumbnail:focus,
-a.thumbnail.active {
- border-color: #337ab7;
-}
-.thumbnail .caption {
- padding: 9px;
- color: #333;
+
+.jumbotron-fluid {
+ padding-right: 0;
+ padding-left: 0;
+ border-radius: 0;
}
+
.alert {
- padding: 15px;
- margin-bottom: 20px;
+ padding: 0.75rem 1.25rem;
+ margin-bottom: 1rem;
border: 1px solid transparent;
- border-radius: 4px;
+ border-radius: 0.25rem;
}
-.alert h4 {
- margin-top: 0;
+
+.alert-heading {
color: inherit;
}
-.alert .alert-link {
+
+.alert-link {
font-weight: bold;
}
-.alert > p,
-.alert > ul {
- margin-bottom: 0;
-}
-.alert > p + p {
- margin-top: 5px;
-}
-.alert-dismissable,
-.alert-dismissible {
- padding-right: 35px;
-}
-.alert-dismissable .close,
+
.alert-dismissible .close {
position: relative;
- top: -2px;
- right: -21px;
+ top: -0.75rem;
+ right: -1.25rem;
+ padding: 0.75rem 1.25rem;
color: inherit;
}
+
+.alert-primary {
+ color: #004085;
+ background-color: #cce5ff;
+ border-color: #b8daff;
+}
+
+.alert-primary hr {
+ border-top-color: #9fcdff;
+}
+
+.alert-primary .alert-link {
+ color: #002752;
+}
+
+.alert-secondary {
+ color: #464a4e;
+ background-color: #e7e8ea;
+ border-color: #dddfe2;
+}
+
+.alert-secondary hr {
+ border-top-color: #cfd2d6;
+}
+
+.alert-secondary .alert-link {
+ color: #2e3133;
+}
+
.alert-success {
- color: #3c763d;
- background-color: #dff0d8;
- border-color: #d6e9c6;
+ color: #155724;
+ background-color: #d4edda;
+ border-color: #c3e6cb;
}
+
.alert-success hr {
- border-top-color: #c9e2b3;
+ border-top-color: #b1dfbb;
}
+
.alert-success .alert-link {
- color: #2b542c;
+ color: #0b2e13;
}
+
.alert-info {
- color: #31708f;
- background-color: #d9edf7;
- border-color: #bce8f1;
+ color: #0c5460;
+ background-color: #d1ecf1;
+ border-color: #bee5eb;
}
+
.alert-info hr {
- border-top-color: #a6e1ec;
+ border-top-color: #abdde5;
}
+
.alert-info .alert-link {
- color: #245269;
+ color: #062c33;
}
+
.alert-warning {
- color: #8a6d3b;
- background-color: #fcf8e3;
- border-color: #faebcc;
+ color: #856404;
+ background-color: #fff3cd;
+ border-color: #ffeeba;
}
+
.alert-warning hr {
- border-top-color: #f7e1b5;
+ border-top-color: #ffe8a1;
}
+
.alert-warning .alert-link {
- color: #66512c;
+ color: #533f03;
}
+
.alert-danger {
- color: #a94442;
- background-color: #f2dede;
- border-color: #ebccd1;
+ color: #721c24;
+ background-color: #f8d7da;
+ border-color: #f5c6cb;
}
+
.alert-danger hr {
- border-top-color: #e4b9c0;
+ border-top-color: #f1b0b7;
}
+
.alert-danger .alert-link {
- color: #843534;
+ color: #491217;
}
-@-webkit-keyframes progress-bar-stripes {
- from {
- background-position: 40px 0;
- }
- to {
- background-position: 0 0;
- }
+
+.alert-light {
+ color: #818182;
+ background-color: #fefefe;
+ border-color: #fdfdfe;
+}
+
+.alert-light hr {
+ border-top-color: #ececf6;
+}
+
+.alert-light .alert-link {
+ color: #686868;
+}
+
+.alert-dark {
+ color: #1b1e21;
+ background-color: #d6d8d9;
+ border-color: #c6c8ca;
}
-@-o-keyframes progress-bar-stripes {
+
+.alert-dark hr {
+ border-top-color: #b9bbbe;
+}
+
+.alert-dark .alert-link {
+ color: #040505;
+}
+
+@-webkit-keyframes progress-bar-stripes {
from {
- background-position: 40px 0;
+ background-position: 1rem 0;
}
to {
background-position: 0 0;
}
}
+
@keyframes progress-bar-stripes {
from {
- background-position: 40px 0;
+ background-position: 1rem 0;
}
to {
background-position: 0 0;
}
}
+
.progress {
- height: 20px;
- margin-bottom: 20px;
+ display: -ms-flexbox;
+ display: flex;
overflow: hidden;
- background-color: #f5f5f5;
- border-radius: 4px;
- -webkit-box-shadow: inset 0 1px 2px rgba(0, 0, 0, .1);
- box-shadow: inset 0 1px 2px rgba(0, 0, 0, .1);
+ font-size: 0.75rem;
+ line-height: 1rem;
+ text-align: center;
+ background-color: #e9ecef;
+ border-radius: 0.25rem;
}
+
.progress-bar {
- float: left;
- width: 0;
- height: 100%;
- font-size: 12px;
- line-height: 20px;
+ height: 1rem;
+ line-height: 1rem;
color: #fff;
- text-align: center;
- background-color: #337ab7;
- -webkit-box-shadow: inset 0 -1px 0 rgba(0, 0, 0, .15);
- box-shadow: inset 0 -1px 0 rgba(0, 0, 0, .15);
- -webkit-transition: width .6s ease;
- -o-transition: width .6s ease;
- transition: width .6s ease;
-}
-.progress-striped .progress-bar,
-.progress-bar-striped {
- background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);
- background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);
- background-image: linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);
- -webkit-background-size: 40px 40px;
- background-size: 40px 40px;
-}
-.progress.active .progress-bar,
-.progress-bar.active {
- -webkit-animation: progress-bar-stripes 2s linear infinite;
- -o-animation: progress-bar-stripes 2s linear infinite;
- animation: progress-bar-stripes 2s linear infinite;
-}
-.progress-bar-success {
- background-color: #5cb85c;
-}
-.progress-striped .progress-bar-success {
- background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);
- background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);
- background-image: linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);
-}
-.progress-bar-info {
- background-color: #5bc0de;
-}
-.progress-striped .progress-bar-info {
- background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);
- background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);
- background-image: linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);
-}
-.progress-bar-warning {
- background-color: #f0ad4e;
-}
-.progress-striped .progress-bar-warning {
- background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);
- background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);
- background-image: linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);
-}
-.progress-bar-danger {
- background-color: #d9534f;
-}
-.progress-striped .progress-bar-danger {
- background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);
- background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);
- background-image: linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);
+ background-color: #007bff;
+ transition: width 0.6s ease;
}
-.media {
- margin-top: 15px;
-}
-.media:first-child {
- margin-top: 0;
-}
-.media,
-.media-body {
- overflow: hidden;
- zoom: 1;
-}
-.media-body {
- width: 10000px;
-}
-.media-object {
- display: block;
-}
-.media-object.img-thumbnail {
- max-width: none;
+
+.progress-bar-striped {
+ background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
+ background-size: 1rem 1rem;
}
-.media-right,
-.media > .pull-right {
- padding-left: 10px;
+
+.progress-bar-animated {
+ -webkit-animation: progress-bar-stripes 1s linear infinite;
+ animation: progress-bar-stripes 1s linear infinite;
}
-.media-left,
-.media > .pull-left {
- padding-right: 10px;
+
+.media {
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-align: start;
+ align-items: flex-start;
}
-.media-left,
-.media-right,
+
.media-body {
- display: table-cell;
- vertical-align: top;
-}
-.media-middle {
- vertical-align: middle;
+ -ms-flex: 1;
+ flex: 1;
}
-.media-bottom {
- vertical-align: bottom;
+
+.list-group {
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-direction: column;
+ flex-direction: column;
+ padding-left: 0;
+ margin-bottom: 0;
}
-.media-heading {
- margin-top: 0;
- margin-bottom: 5px;
+
+.list-group-item-action {
+ width: 100%;
+ color: #495057;
+ text-align: inherit;
}
-.media-list {
- padding-left: 0;
- list-style: none;
+
+.list-group-item-action:focus, .list-group-item-action:hover {
+ color: #495057;
+ text-decoration: none;
+ background-color: #f8f9fa;
}
-.list-group {
- padding-left: 0;
- margin-bottom: 20px;
+
+.list-group-item-action:active {
+ color: #212529;
+ background-color: #e9ecef;
}
+
.list-group-item {
position: relative;
display: block;
- padding: 10px 15px;
+ padding: 0.75rem 1.25rem;
margin-bottom: -1px;
background-color: #fff;
- border: 1px solid #ddd;
+ border: 1px solid rgba(0, 0, 0, 0.125);
}
+
.list-group-item:first-child {
- border-top-left-radius: 4px;
- border-top-right-radius: 4px;
+ border-top-left-radius: 0.25rem;
+ border-top-right-radius: 0.25rem;
}
+
.list-group-item:last-child {
margin-bottom: 0;
- border-bottom-right-radius: 4px;
- border-bottom-left-radius: 4px;
-}
-a.list-group-item,
-button.list-group-item {
- color: #555;
-}
-a.list-group-item .list-group-item-heading,
-button.list-group-item .list-group-item-heading {
- color: #333;
-}
-a.list-group-item:hover,
-button.list-group-item:hover,
-a.list-group-item:focus,
-button.list-group-item:focus {
- color: #555;
+ border-bottom-right-radius: 0.25rem;
+ border-bottom-left-radius: 0.25rem;
+}
+
+.list-group-item:focus, .list-group-item:hover {
text-decoration: none;
- background-color: #f5f5f5;
}
-button.list-group-item {
- width: 100%;
- text-align: left;
+
+.list-group-item.disabled, .list-group-item:disabled {
+ color: #868e96;
+ background-color: #fff;
}
-.list-group-item.disabled,
-.list-group-item.disabled:hover,
-.list-group-item.disabled:focus {
- color: #777;
- cursor: not-allowed;
- background-color: #eee;
+
+.list-group-item.active {
+ z-index: 2;
+ color: #fff;
+ background-color: #007bff;
+ border-color: #007bff;
}
-.list-group-item.disabled .list-group-item-heading,
-.list-group-item.disabled:hover .list-group-item-heading,
-.list-group-item.disabled:focus .list-group-item-heading {
- color: inherit;
+
+.list-group-flush .list-group-item {
+ border-right: 0;
+ border-left: 0;
+ border-radius: 0;
}
-.list-group-item.disabled .list-group-item-text,
-.list-group-item.disabled:hover .list-group-item-text,
-.list-group-item.disabled:focus .list-group-item-text {
- color: #777;
+
+.list-group-flush:first-child .list-group-item:first-child {
+ border-top: 0;
}
-.list-group-item.active,
-.list-group-item.active:hover,
-.list-group-item.active:focus {
- z-index: 2;
+
+.list-group-flush:last-child .list-group-item:last-child {
+ border-bottom: 0;
+}
+
+.list-group-item-primary {
+ color: #004085;
+ background-color: #b8daff;
+}
+
+a.list-group-item-primary,
+button.list-group-item-primary {
+ color: #004085;
+}
+
+a.list-group-item-primary:focus, a.list-group-item-primary:hover,
+button.list-group-item-primary:focus,
+button.list-group-item-primary:hover {
+ color: #004085;
+ background-color: #9fcdff;
+}
+
+a.list-group-item-primary.active,
+button.list-group-item-primary.active {
color: #fff;
- background-color: #337ab7;
- border-color: #337ab7;
-}
-.list-group-item.active .list-group-item-heading,
-.list-group-item.active:hover .list-group-item-heading,
-.list-group-item.active:focus .list-group-item-heading,
-.list-group-item.active .list-group-item-heading > small,
-.list-group-item.active:hover .list-group-item-heading > small,
-.list-group-item.active:focus .list-group-item-heading > small,
-.list-group-item.active .list-group-item-heading > .small,
-.list-group-item.active:hover .list-group-item-heading > .small,
-.list-group-item.active:focus .list-group-item-heading > .small {
- color: inherit;
+ background-color: #004085;
+ border-color: #004085;
+}
+
+.list-group-item-secondary {
+ color: #464a4e;
+ background-color: #dddfe2;
+}
+
+a.list-group-item-secondary,
+button.list-group-item-secondary {
+ color: #464a4e;
}
-.list-group-item.active .list-group-item-text,
-.list-group-item.active:hover .list-group-item-text,
-.list-group-item.active:focus .list-group-item-text {
- color: #c7ddef;
+
+a.list-group-item-secondary:focus, a.list-group-item-secondary:hover,
+button.list-group-item-secondary:focus,
+button.list-group-item-secondary:hover {
+ color: #464a4e;
+ background-color: #cfd2d6;
}
+
+a.list-group-item-secondary.active,
+button.list-group-item-secondary.active {
+ color: #fff;
+ background-color: #464a4e;
+ border-color: #464a4e;
+}
+
.list-group-item-success {
- color: #3c763d;
- background-color: #dff0d8;
+ color: #155724;
+ background-color: #c3e6cb;
}
+
a.list-group-item-success,
button.list-group-item-success {
- color: #3c763d;
-}
-a.list-group-item-success .list-group-item-heading,
-button.list-group-item-success .list-group-item-heading {
- color: inherit;
+ color: #155724;
}
-a.list-group-item-success:hover,
-button.list-group-item-success:hover,
-a.list-group-item-success:focus,
-button.list-group-item-success:focus {
- color: #3c763d;
- background-color: #d0e9c6;
+
+a.list-group-item-success:focus, a.list-group-item-success:hover,
+button.list-group-item-success:focus,
+button.list-group-item-success:hover {
+ color: #155724;
+ background-color: #b1dfbb;
}
+
a.list-group-item-success.active,
-button.list-group-item-success.active,
-a.list-group-item-success.active:hover,
-button.list-group-item-success.active:hover,
-a.list-group-item-success.active:focus,
-button.list-group-item-success.active:focus {
+button.list-group-item-success.active {
color: #fff;
- background-color: #3c763d;
- border-color: #3c763d;
+ background-color: #155724;
+ border-color: #155724;
}
+
.list-group-item-info {
- color: #31708f;
- background-color: #d9edf7;
+ color: #0c5460;
+ background-color: #bee5eb;
}
+
a.list-group-item-info,
button.list-group-item-info {
- color: #31708f;
-}
-a.list-group-item-info .list-group-item-heading,
-button.list-group-item-info .list-group-item-heading {
- color: inherit;
+ color: #0c5460;
}
-a.list-group-item-info:hover,
-button.list-group-item-info:hover,
-a.list-group-item-info:focus,
-button.list-group-item-info:focus {
- color: #31708f;
- background-color: #c4e3f3;
+
+a.list-group-item-info:focus, a.list-group-item-info:hover,
+button.list-group-item-info:focus,
+button.list-group-item-info:hover {
+ color: #0c5460;
+ background-color: #abdde5;
}
+
a.list-group-item-info.active,
-button.list-group-item-info.active,
-a.list-group-item-info.active:hover,
-button.list-group-item-info.active:hover,
-a.list-group-item-info.active:focus,
-button.list-group-item-info.active:focus {
+button.list-group-item-info.active {
color: #fff;
- background-color: #31708f;
- border-color: #31708f;
+ background-color: #0c5460;
+ border-color: #0c5460;
}
+
.list-group-item-warning {
- color: #8a6d3b;
- background-color: #fcf8e3;
+ color: #856404;
+ background-color: #ffeeba;
}
+
a.list-group-item-warning,
button.list-group-item-warning {
- color: #8a6d3b;
-}
-a.list-group-item-warning .list-group-item-heading,
-button.list-group-item-warning .list-group-item-heading {
- color: inherit;
+ color: #856404;
}
-a.list-group-item-warning:hover,
-button.list-group-item-warning:hover,
-a.list-group-item-warning:focus,
-button.list-group-item-warning:focus {
- color: #8a6d3b;
- background-color: #faf2cc;
+
+a.list-group-item-warning:focus, a.list-group-item-warning:hover,
+button.list-group-item-warning:focus,
+button.list-group-item-warning:hover {
+ color: #856404;
+ background-color: #ffe8a1;
}
+
a.list-group-item-warning.active,
-button.list-group-item-warning.active,
-a.list-group-item-warning.active:hover,
-button.list-group-item-warning.active:hover,
-a.list-group-item-warning.active:focus,
-button.list-group-item-warning.active:focus {
+button.list-group-item-warning.active {
color: #fff;
- background-color: #8a6d3b;
- border-color: #8a6d3b;
+ background-color: #856404;
+ border-color: #856404;
}
+
.list-group-item-danger {
- color: #a94442;
- background-color: #f2dede;
+ color: #721c24;
+ background-color: #f5c6cb;
}
+
a.list-group-item-danger,
button.list-group-item-danger {
- color: #a94442;
+ color: #721c24;
}
-a.list-group-item-danger .list-group-item-heading,
-button.list-group-item-danger .list-group-item-heading {
- color: inherit;
-}
-a.list-group-item-danger:hover,
-button.list-group-item-danger:hover,
-a.list-group-item-danger:focus,
-button.list-group-item-danger:focus {
- color: #a94442;
- background-color: #ebcccc;
+
+a.list-group-item-danger:focus, a.list-group-item-danger:hover,
+button.list-group-item-danger:focus,
+button.list-group-item-danger:hover {
+ color: #721c24;
+ background-color: #f1b0b7;
}
+
a.list-group-item-danger.active,
-button.list-group-item-danger.active,
-a.list-group-item-danger.active:hover,
-button.list-group-item-danger.active:hover,
-a.list-group-item-danger.active:focus,
-button.list-group-item-danger.active:focus {
+button.list-group-item-danger.active {
color: #fff;
- background-color: #a94442;
- border-color: #a94442;
-}
-.list-group-item-heading {
- margin-top: 0;
- margin-bottom: 5px;
-}
-.list-group-item-text {
- margin-bottom: 0;
- line-height: 1.3;
+ background-color: #721c24;
+ border-color: #721c24;
}
-.panel {
- margin-bottom: 20px;
- background-color: #fff;
- border: 1px solid transparent;
- border-radius: 4px;
- -webkit-box-shadow: 0 1px 1px rgba(0, 0, 0, .05);
- box-shadow: 0 1px 1px rgba(0, 0, 0, .05);
-}
-.panel-body {
- padding: 15px;
-}
-.panel-heading {
- padding: 10px 15px;
- border-bottom: 1px solid transparent;
- border-top-left-radius: 3px;
- border-top-right-radius: 3px;
-}
-.panel-heading > .dropdown .dropdown-toggle {
- color: inherit;
-}
-.panel-title {
- margin-top: 0;
- margin-bottom: 0;
- font-size: 16px;
- color: inherit;
-}
-.panel-title > a,
-.panel-title > small,
-.panel-title > .small,
-.panel-title > small > a,
-.panel-title > .small > a {
- color: inherit;
-}
-.panel-footer {
- padding: 10px 15px;
- background-color: #f5f5f5;
- border-top: 1px solid #ddd;
- border-bottom-right-radius: 3px;
- border-bottom-left-radius: 3px;
-}
-.panel > .list-group,
-.panel > .panel-collapse > .list-group {
- margin-bottom: 0;
-}
-.panel > .list-group .list-group-item,
-.panel > .panel-collapse > .list-group .list-group-item {
- border-width: 1px 0;
- border-radius: 0;
-}
-.panel > .list-group:first-child .list-group-item:first-child,
-.panel > .panel-collapse > .list-group:first-child .list-group-item:first-child {
- border-top: 0;
- border-top-left-radius: 3px;
- border-top-right-radius: 3px;
-}
-.panel > .list-group:last-child .list-group-item:last-child,
-.panel > .panel-collapse > .list-group:last-child .list-group-item:last-child {
- border-bottom: 0;
- border-bottom-right-radius: 3px;
- border-bottom-left-radius: 3px;
-}
-.panel > .panel-heading + .panel-collapse > .list-group .list-group-item:first-child {
- border-top-left-radius: 0;
- border-top-right-radius: 0;
-}
-.panel-heading + .list-group .list-group-item:first-child {
- border-top-width: 0;
-}
-.list-group + .panel-footer {
- border-top-width: 0;
-}
-.panel > .table,
-.panel > .table-responsive > .table,
-.panel > .panel-collapse > .table {
- margin-bottom: 0;
-}
-.panel > .table caption,
-.panel > .table-responsive > .table caption,
-.panel > .panel-collapse > .table caption {
- padding-right: 15px;
- padding-left: 15px;
-}
-.panel > .table:first-child,
-.panel > .table-responsive:first-child > .table:first-child {
- border-top-left-radius: 3px;
- border-top-right-radius: 3px;
-}
-.panel > .table:first-child > thead:first-child > tr:first-child,
-.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child,
-.panel > .table:first-child > tbody:first-child > tr:first-child,
-.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child {
- border-top-left-radius: 3px;
- border-top-right-radius: 3px;
-}
-.panel > .table:first-child > thead:first-child > tr:first-child td:first-child,
-.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child td:first-child,
-.panel > .table:first-child > tbody:first-child > tr:first-child td:first-child,
-.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child td:first-child,
-.panel > .table:first-child > thead:first-child > tr:first-child th:first-child,
-.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child th:first-child,
-.panel > .table:first-child > tbody:first-child > tr:first-child th:first-child,
-.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child th:first-child {
- border-top-left-radius: 3px;
-}
-.panel > .table:first-child > thead:first-child > tr:first-child td:last-child,
-.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child td:last-child,
-.panel > .table:first-child > tbody:first-child > tr:first-child td:last-child,
-.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child td:last-child,
-.panel > .table:first-child > thead:first-child > tr:first-child th:last-child,
-.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child th:last-child,
-.panel > .table:first-child > tbody:first-child > tr:first-child th:last-child,
-.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child th:last-child {
- border-top-right-radius: 3px;
-}
-.panel > .table:last-child,
-.panel > .table-responsive:last-child > .table:last-child {
- border-bottom-right-radius: 3px;
- border-bottom-left-radius: 3px;
-}
-.panel > .table:last-child > tbody:last-child > tr:last-child,
-.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child,
-.panel > .table:last-child > tfoot:last-child > tr:last-child,
-.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child {
- border-bottom-right-radius: 3px;
- border-bottom-left-radius: 3px;
-}
-.panel > .table:last-child > tbody:last-child > tr:last-child td:first-child,
-.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child td:first-child,
-.panel > .table:last-child > tfoot:last-child > tr:last-child td:first-child,
-.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child td:first-child,
-.panel > .table:last-child > tbody:last-child > tr:last-child th:first-child,
-.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child th:first-child,
-.panel > .table:last-child > tfoot:last-child > tr:last-child th:first-child,
-.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child th:first-child {
- border-bottom-left-radius: 3px;
-}
-.panel > .table:last-child > tbody:last-child > tr:last-child td:last-child,
-.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child td:last-child,
-.panel > .table:last-child > tfoot:last-child > tr:last-child td:last-child,
-.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child td:last-child,
-.panel > .table:last-child > tbody:last-child > tr:last-child th:last-child,
-.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child th:last-child,
-.panel > .table:last-child > tfoot:last-child > tr:last-child th:last-child,
-.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child th:last-child {
- border-bottom-right-radius: 3px;
-}
-.panel > .panel-body + .table,
-.panel > .panel-body + .table-responsive,
-.panel > .table + .panel-body,
-.panel > .table-responsive + .panel-body {
- border-top: 1px solid #ddd;
-}
-.panel > .table > tbody:first-child > tr:first-child th,
-.panel > .table > tbody:first-child > tr:first-child td {
- border-top: 0;
-}
-.panel > .table-bordered,
-.panel > .table-responsive > .table-bordered {
- border: 0;
-}
-.panel > .table-bordered > thead > tr > th:first-child,
-.panel > .table-responsive > .table-bordered > thead > tr > th:first-child,
-.panel > .table-bordered > tbody > tr > th:first-child,
-.panel > .table-responsive > .table-bordered > tbody > tr > th:first-child,
-.panel > .table-bordered > tfoot > tr > th:first-child,
-.panel > .table-responsive > .table-bordered > tfoot > tr > th:first-child,
-.panel > .table-bordered > thead > tr > td:first-child,
-.panel > .table-responsive > .table-bordered > thead > tr > td:first-child,
-.panel > .table-bordered > tbody > tr > td:first-child,
-.panel > .table-responsive > .table-bordered > tbody > tr > td:first-child,
-.panel > .table-bordered > tfoot > tr > td:first-child,
-.panel > .table-responsive > .table-bordered > tfoot > tr > td:first-child {
- border-left: 0;
-}
-.panel > .table-bordered > thead > tr > th:last-child,
-.panel > .table-responsive > .table-bordered > thead > tr > th:last-child,
-.panel > .table-bordered > tbody > tr > th:last-child,
-.panel > .table-responsive > .table-bordered > tbody > tr > th:last-child,
-.panel > .table-bordered > tfoot > tr > th:last-child,
-.panel > .table-responsive > .table-bordered > tfoot > tr > th:last-child,
-.panel > .table-bordered > thead > tr > td:last-child,
-.panel > .table-responsive > .table-bordered > thead > tr > td:last-child,
-.panel > .table-bordered > tbody > tr > td:last-child,
-.panel > .table-responsive > .table-bordered > tbody > tr > td:last-child,
-.panel > .table-bordered > tfoot > tr > td:last-child,
-.panel > .table-responsive > .table-bordered > tfoot > tr > td:last-child {
- border-right: 0;
-}
-.panel > .table-bordered > thead > tr:first-child > td,
-.panel > .table-responsive > .table-bordered > thead > tr:first-child > td,
-.panel > .table-bordered > tbody > tr:first-child > td,
-.panel > .table-responsive > .table-bordered > tbody > tr:first-child > td,
-.panel > .table-bordered > thead > tr:first-child > th,
-.panel > .table-responsive > .table-bordered > thead > tr:first-child > th,
-.panel > .table-bordered > tbody > tr:first-child > th,
-.panel > .table-responsive > .table-bordered > tbody > tr:first-child > th {
- border-bottom: 0;
-}
-.panel > .table-bordered > tbody > tr:last-child > td,
-.panel > .table-responsive > .table-bordered > tbody > tr:last-child > td,
-.panel > .table-bordered > tfoot > tr:last-child > td,
-.panel > .table-responsive > .table-bordered > tfoot > tr:last-child > td,
-.panel > .table-bordered > tbody > tr:last-child > th,
-.panel > .table-responsive > .table-bordered > tbody > tr:last-child > th,
-.panel > .table-bordered > tfoot > tr:last-child > th,
-.panel > .table-responsive > .table-bordered > tfoot > tr:last-child > th {
- border-bottom: 0;
-}
-.panel > .table-responsive {
- margin-bottom: 0;
- border: 0;
-}
-.panel-group {
- margin-bottom: 20px;
-}
-.panel-group .panel {
- margin-bottom: 0;
- border-radius: 4px;
-}
-.panel-group .panel + .panel {
- margin-top: 5px;
-}
-.panel-group .panel-heading {
- border-bottom: 0;
-}
-.panel-group .panel-heading + .panel-collapse > .panel-body,
-.panel-group .panel-heading + .panel-collapse > .list-group {
- border-top: 1px solid #ddd;
-}
-.panel-group .panel-footer {
- border-top: 0;
-}
-.panel-group .panel-footer + .panel-collapse .panel-body {
- border-bottom: 1px solid #ddd;
-}
-.panel-default {
- border-color: #ddd;
-}
-.panel-default > .panel-heading {
- color: #333;
- background-color: #f5f5f5;
- border-color: #ddd;
-}
-.panel-default > .panel-heading + .panel-collapse > .panel-body {
- border-top-color: #ddd;
-}
-.panel-default > .panel-heading .badge {
- color: #f5f5f5;
- background-color: #333;
+
+.list-group-item-light {
+ color: #818182;
+ background-color: #fdfdfe;
}
-.panel-default > .panel-footer + .panel-collapse > .panel-body {
- border-bottom-color: #ddd;
+
+a.list-group-item-light,
+button.list-group-item-light {
+ color: #818182;
}
-.panel-primary {
- border-color: #337ab7;
+
+a.list-group-item-light:focus, a.list-group-item-light:hover,
+button.list-group-item-light:focus,
+button.list-group-item-light:hover {
+ color: #818182;
+ background-color: #ececf6;
}
-.panel-primary > .panel-heading {
+
+a.list-group-item-light.active,
+button.list-group-item-light.active {
color: #fff;
- background-color: #337ab7;
- border-color: #337ab7;
-}
-.panel-primary > .panel-heading + .panel-collapse > .panel-body {
- border-top-color: #337ab7;
-}
-.panel-primary > .panel-heading .badge {
- color: #337ab7;
- background-color: #fff;
-}
-.panel-primary > .panel-footer + .panel-collapse > .panel-body {
- border-bottom-color: #337ab7;
-}
-.panel-success {
- border-color: #d6e9c6;
-}
-.panel-success > .panel-heading {
- color: #3c763d;
- background-color: #dff0d8;
- border-color: #d6e9c6;
-}
-.panel-success > .panel-heading + .panel-collapse > .panel-body {
- border-top-color: #d6e9c6;
-}
-.panel-success > .panel-heading .badge {
- color: #dff0d8;
- background-color: #3c763d;
-}
-.panel-success > .panel-footer + .panel-collapse > .panel-body {
- border-bottom-color: #d6e9c6;
-}
-.panel-info {
- border-color: #bce8f1;
-}
-.panel-info > .panel-heading {
- color: #31708f;
- background-color: #d9edf7;
- border-color: #bce8f1;
-}
-.panel-info > .panel-heading + .panel-collapse > .panel-body {
- border-top-color: #bce8f1;
-}
-.panel-info > .panel-heading .badge {
- color: #d9edf7;
- background-color: #31708f;
-}
-.panel-info > .panel-footer + .panel-collapse > .panel-body {
- border-bottom-color: #bce8f1;
-}
-.panel-warning {
- border-color: #faebcc;
-}
-.panel-warning > .panel-heading {
- color: #8a6d3b;
- background-color: #fcf8e3;
- border-color: #faebcc;
-}
-.panel-warning > .panel-heading + .panel-collapse > .panel-body {
- border-top-color: #faebcc;
-}
-.panel-warning > .panel-heading .badge {
- color: #fcf8e3;
- background-color: #8a6d3b;
-}
-.panel-warning > .panel-footer + .panel-collapse > .panel-body {
- border-bottom-color: #faebcc;
-}
-.panel-danger {
- border-color: #ebccd1;
-}
-.panel-danger > .panel-heading {
- color: #a94442;
- background-color: #f2dede;
- border-color: #ebccd1;
-}
-.panel-danger > .panel-heading + .panel-collapse > .panel-body {
- border-top-color: #ebccd1;
-}
-.panel-danger > .panel-heading .badge {
- color: #f2dede;
- background-color: #a94442;
-}
-.panel-danger > .panel-footer + .panel-collapse > .panel-body {
- border-bottom-color: #ebccd1;
-}
-.embed-responsive {
- position: relative;
- display: block;
- height: 0;
- padding: 0;
- overflow: hidden;
+ background-color: #818182;
+ border-color: #818182;
}
-.embed-responsive .embed-responsive-item,
-.embed-responsive iframe,
-.embed-responsive embed,
-.embed-responsive object,
-.embed-responsive video {
- position: absolute;
- top: 0;
- bottom: 0;
- left: 0;
- width: 100%;
- height: 100%;
- border: 0;
-}
-.embed-responsive-16by9 {
- padding-bottom: 56.25%;
-}
-.embed-responsive-4by3 {
- padding-bottom: 75%;
-}
-.well {
- min-height: 20px;
- padding: 19px;
- margin-bottom: 20px;
- background-color: #f5f5f5;
- border: 1px solid #e3e3e3;
- border-radius: 4px;
- -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, .05);
- box-shadow: inset 0 1px 1px rgba(0, 0, 0, .05);
+
+.list-group-item-dark {
+ color: #1b1e21;
+ background-color: #c6c8ca;
}
-.well blockquote {
- border-color: #ddd;
- border-color: rgba(0, 0, 0, .15);
+
+a.list-group-item-dark,
+button.list-group-item-dark {
+ color: #1b1e21;
}
-.well-lg {
- padding: 24px;
- border-radius: 6px;
+
+a.list-group-item-dark:focus, a.list-group-item-dark:hover,
+button.list-group-item-dark:focus,
+button.list-group-item-dark:hover {
+ color: #1b1e21;
+ background-color: #b9bbbe;
}
-.well-sm {
- padding: 9px;
- border-radius: 3px;
+
+a.list-group-item-dark.active,
+button.list-group-item-dark.active {
+ color: #fff;
+ background-color: #1b1e21;
+ border-color: #1b1e21;
}
+
.close {
float: right;
- font-size: 21px;
+ font-size: 1.5rem;
font-weight: bold;
line-height: 1;
color: #000;
text-shadow: 0 1px 0 #fff;
- filter: alpha(opacity=20);
- opacity: .2;
+ opacity: .5;
}
-.close:hover,
-.close:focus {
+
+.close:focus, .close:hover {
color: #000;
text-decoration: none;
- cursor: pointer;
- filter: alpha(opacity=50);
- opacity: .5;
+ opacity: .75;
}
+
button.close {
- -webkit-appearance: none;
padding: 0;
- cursor: pointer;
background: transparent;
border: 0;
+ -webkit-appearance: none;
}
+
.modal-open {
overflow: hidden;
}
+
.modal {
position: fixed;
top: 0;
@@ -5875,45 +4594,46 @@ button.close {
z-index: 1050;
display: none;
overflow: hidden;
- -webkit-overflow-scrolling: touch;
outline: 0;
}
+
.modal.fade .modal-dialog {
- -webkit-transition: -webkit-transform .3s ease-out;
- -o-transition: -o-transform .3s ease-out;
- transition: transform .3s ease-out;
+ transition: -webkit-transform 0.3s ease-out;
+ transition: transform 0.3s ease-out;
+ transition: transform 0.3s ease-out, -webkit-transform 0.3s ease-out;
-webkit-transform: translate(0, -25%);
- -ms-transform: translate(0, -25%);
- -o-transform: translate(0, -25%);
transform: translate(0, -25%);
}
-.modal.in .modal-dialog {
+
+.modal.show .modal-dialog {
-webkit-transform: translate(0, 0);
- -ms-transform: translate(0, 0);
- -o-transform: translate(0, 0);
transform: translate(0, 0);
}
+
.modal-open .modal {
overflow-x: hidden;
overflow-y: auto;
}
+
.modal-dialog {
position: relative;
width: auto;
margin: 10px;
}
+
.modal-content {
position: relative;
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-direction: column;
+ flex-direction: column;
background-color: #fff;
- -webkit-background-clip: padding-box;
- background-clip: padding-box;
- border: 1px solid #999;
- border: 1px solid rgba(0, 0, 0, .2);
- border-radius: 6px;
+ background-clip: padding-box;
+ border: 1px solid rgba(0, 0, 0, 0.2);
+ border-radius: 0.3rem;
outline: 0;
- -webkit-box-shadow: 0 3px 9px rgba(0, 0, 0, .5);
- box-shadow: 0 3px 9px rgba(0, 0, 0, .5);
}
+
.modal-backdrop {
position: fixed;
top: 0;
@@ -5923,44 +4643,57 @@ button.close {
z-index: 1040;
background-color: #000;
}
+
.modal-backdrop.fade {
- filter: alpha(opacity=0);
opacity: 0;
}
-.modal-backdrop.in {
- filter: alpha(opacity=50);
- opacity: .5;
+
+.modal-backdrop.show {
+ opacity: 0.5;
}
+
.modal-header {
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-align: center;
+ align-items: center;
+ -ms-flex-pack: justify;
+ justify-content: space-between;
padding: 15px;
- border-bottom: 1px solid #e5e5e5;
-}
-.modal-header .close {
- margin-top: -2px;
+ border-bottom: 1px solid #e9ecef;
}
+
.modal-title {
- margin: 0;
- line-height: 1.42857143;
+ margin-bottom: 0;
+ line-height: 1.5;
}
+
.modal-body {
position: relative;
+ -ms-flex: 1 1 auto;
+ flex: 1 1 auto;
padding: 15px;
}
+
.modal-footer {
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-align: center;
+ align-items: center;
+ -ms-flex-pack: end;
+ justify-content: flex-end;
padding: 15px;
- text-align: right;
- border-top: 1px solid #e5e5e5;
-}
-.modal-footer .btn + .btn {
- margin-bottom: 0;
- margin-left: 5px;
+ border-top: 1px solid #e9ecef;
}
-.modal-footer .btn-group .btn + .btn {
- margin-left: -1px;
+
+.modal-footer > :not(:first-child) {
+ margin-left: .25rem;
}
-.modal-footer .btn-block + .btn-block {
- margin-left: 0;
+
+.modal-footer > :not(:last-child) {
+ margin-right: .25rem;
}
+
.modal-scrollbar-measure {
position: absolute;
top: -9999px;
@@ -5968,33 +4701,32 @@ button.close {
height: 50px;
overflow: scroll;
}
-@media (min-width: 768px) {
+
+@media (min-width: 576px) {
.modal-dialog {
- width: 600px;
+ max-width: 500px;
margin: 30px auto;
}
- .modal-content {
- -webkit-box-shadow: 0 5px 15px rgba(0, 0, 0, .5);
- box-shadow: 0 5px 15px rgba(0, 0, 0, .5);
- }
.modal-sm {
- width: 300px;
+ max-width: 300px;
}
}
+
@media (min-width: 992px) {
.modal-lg {
- width: 900px;
+ max-width: 800px;
}
}
+
.tooltip {
position: absolute;
z-index: 1070;
display: block;
- font-family: "Helvetica Neue", Helvetica, Arial, sans-serif;
- font-size: 12px;
+ margin: 0;
+ font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, "Helvetica Neue", Arial, sans-serif;
font-style: normal;
font-weight: normal;
- line-height: 1.42857143;
+ line-height: 1.5;
text-align: left;
text-align: start;
text-decoration: none;
@@ -6003,117 +4735,112 @@ button.close {
letter-spacing: normal;
word-break: normal;
word-spacing: normal;
- word-wrap: normal;
white-space: normal;
- filter: alpha(opacity=0);
- opacity: 0;
-
line-break: auto;
+ font-size: 0.875rem;
+ word-wrap: break-word;
+ opacity: 0;
}
-.tooltip.in {
- filter: alpha(opacity=90);
- opacity: .9;
-}
-.tooltip.top {
- padding: 5px 0;
- margin-top: -3px;
+
+.tooltip.show {
+ opacity: 0.9;
}
-.tooltip.right {
- padding: 0 5px;
- margin-left: 3px;
+
+.tooltip .arrow {
+ position: absolute;
+ display: block;
+ width: 5px;
+ height: 5px;
}
-.tooltip.bottom {
+
+.tooltip.bs-tooltip-top, .tooltip.bs-tooltip-auto[x-placement^="top"] {
padding: 5px 0;
- margin-top: 3px;
-}
-.tooltip.left {
- padding: 0 5px;
- margin-left: -3px;
-}
-.tooltip-inner {
- max-width: 200px;
- padding: 3px 8px;
- color: #fff;
- text-align: center;
- background-color: #000;
- border-radius: 4px;
-}
-.tooltip-arrow {
- position: absolute;
- width: 0;
- height: 0;
- border-color: transparent;
- border-style: solid;
}
-.tooltip.top .tooltip-arrow {
+
+.tooltip.bs-tooltip-top .arrow, .tooltip.bs-tooltip-auto[x-placement^="top"] .arrow {
bottom: 0;
- left: 50%;
- margin-left: -5px;
- border-width: 5px 5px 0;
- border-top-color: #000;
}
-.tooltip.top-left .tooltip-arrow {
- right: 5px;
- bottom: 0;
- margin-bottom: -5px;
+
+.tooltip.bs-tooltip-top .arrow::before, .tooltip.bs-tooltip-auto[x-placement^="top"] .arrow::before {
+ margin-left: -3px;
+ content: "";
border-width: 5px 5px 0;
border-top-color: #000;
}
-.tooltip.top-right .tooltip-arrow {
- bottom: 0;
- left: 5px;
- margin-bottom: -5px;
- border-width: 5px 5px 0;
- border-top-color: #000;
+
+.tooltip.bs-tooltip-right, .tooltip.bs-tooltip-auto[x-placement^="right"] {
+ padding: 0 5px;
}
-.tooltip.right .tooltip-arrow {
- top: 50%;
+
+.tooltip.bs-tooltip-right .arrow, .tooltip.bs-tooltip-auto[x-placement^="right"] .arrow {
left: 0;
- margin-top: -5px;
+}
+
+.tooltip.bs-tooltip-right .arrow::before, .tooltip.bs-tooltip-auto[x-placement^="right"] .arrow::before {
+ margin-top: -3px;
+ content: "";
border-width: 5px 5px 5px 0;
border-right-color: #000;
}
-.tooltip.left .tooltip-arrow {
- top: 50%;
- right: 0;
- margin-top: -5px;
- border-width: 5px 0 5px 5px;
- border-left-color: #000;
+
+.tooltip.bs-tooltip-bottom, .tooltip.bs-tooltip-auto[x-placement^="bottom"] {
+ padding: 5px 0;
}
-.tooltip.bottom .tooltip-arrow {
+
+.tooltip.bs-tooltip-bottom .arrow, .tooltip.bs-tooltip-auto[x-placement^="bottom"] .arrow {
top: 0;
- left: 50%;
- margin-left: -5px;
- border-width: 0 5px 5px;
- border-bottom-color: #000;
}
-.tooltip.bottom-left .tooltip-arrow {
- top: 0;
- right: 5px;
- margin-top: -5px;
+
+.tooltip.bs-tooltip-bottom .arrow::before, .tooltip.bs-tooltip-auto[x-placement^="bottom"] .arrow::before {
+ margin-left: -3px;
+ content: "";
border-width: 0 5px 5px;
border-bottom-color: #000;
}
-.tooltip.bottom-right .tooltip-arrow {
- top: 0;
- left: 5px;
- margin-top: -5px;
- border-width: 0 5px 5px;
- border-bottom-color: #000;
+
+.tooltip.bs-tooltip-left, .tooltip.bs-tooltip-auto[x-placement^="left"] {
+ padding: 0 5px;
+}
+
+.tooltip.bs-tooltip-left .arrow, .tooltip.bs-tooltip-auto[x-placement^="left"] .arrow {
+ right: 0;
+}
+
+.tooltip.bs-tooltip-left .arrow::before, .tooltip.bs-tooltip-auto[x-placement^="left"] .arrow::before {
+ right: 0;
+ margin-top: -3px;
+ content: "";
+ border-width: 5px 0 5px 5px;
+ border-left-color: #000;
+}
+
+.tooltip .arrow::before {
+ position: absolute;
+ border-color: transparent;
+ border-style: solid;
+}
+
+.tooltip-inner {
+ max-width: 200px;
+ padding: 3px 8px;
+ color: #fff;
+ text-align: center;
+ background-color: #000;
+ border-radius: 0.25rem;
}
+
.popover {
position: absolute;
top: 0;
left: 0;
z-index: 1060;
- display: none;
+ display: block;
max-width: 276px;
padding: 1px;
- font-family: "Helvetica Neue", Helvetica, Arial, sans-serif;
- font-size: 14px;
+ font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, "Helvetica Neue", Arial, sans-serif;
font-style: normal;
font-weight: normal;
- line-height: 1.42857143;
+ line-height: 1.5;
text-align: left;
text-align: start;
text-decoration: none;
@@ -6122,300 +4849,351 @@ button.close {
letter-spacing: normal;
word-break: normal;
word-spacing: normal;
- word-wrap: normal;
white-space: normal;
- background-color: #fff;
- -webkit-background-clip: padding-box;
- background-clip: padding-box;
- border: 1px solid #ccc;
- border: 1px solid rgba(0, 0, 0, .2);
- border-radius: 6px;
- -webkit-box-shadow: 0 5px 10px rgba(0, 0, 0, .2);
- box-shadow: 0 5px 10px rgba(0, 0, 0, .2);
-
line-break: auto;
+ font-size: 0.875rem;
+ word-wrap: break-word;
+ background-color: #fff;
+ background-clip: padding-box;
+ border: 1px solid rgba(0, 0, 0, 0.2);
+ border-radius: 0.3rem;
}
-.popover.top {
- margin-top: -10px;
-}
-.popover.right {
- margin-left: 10px;
-}
-.popover.bottom {
- margin-top: 10px;
-}
-.popover.left {
- margin-left: -10px;
-}
-.popover-title {
- padding: 8px 14px;
- margin: 0;
- font-size: 14px;
- background-color: #f7f7f7;
- border-bottom: 1px solid #ebebeb;
- border-radius: 5px 5px 0 0;
-}
-.popover-content {
- padding: 9px 14px;
+
+.popover .arrow {
+ position: absolute;
+ display: block;
+ width: 10px;
+ height: 5px;
}
-.popover > .arrow,
-.popover > .arrow:after {
+
+.popover .arrow::before,
+.popover .arrow::after {
position: absolute;
display: block;
- width: 0;
- height: 0;
border-color: transparent;
border-style: solid;
}
-.popover > .arrow {
+
+.popover .arrow::before {
+ content: "";
border-width: 11px;
}
-.popover > .arrow:after {
+
+.popover .arrow::after {
content: "";
- border-width: 10px;
+ border-width: 11px;
}
-.popover.top > .arrow {
- bottom: -11px;
- left: 50%;
- margin-left: -11px;
- border-top-color: #999;
- border-top-color: rgba(0, 0, 0, .25);
+
+.popover.bs-popover-top, .popover.bs-popover-auto[x-placement^="top"] {
+ margin-bottom: 10px;
+}
+
+.popover.bs-popover-top .arrow, .popover.bs-popover-auto[x-placement^="top"] .arrow {
+ bottom: 0;
+}
+
+.popover.bs-popover-top .arrow::before, .popover.bs-popover-auto[x-placement^="top"] .arrow::before,
+.popover.bs-popover-top .arrow::after, .popover.bs-popover-auto[x-placement^="top"] .arrow::after {
border-bottom-width: 0;
}
-.popover.top > .arrow:after {
- bottom: 1px;
- margin-left: -10px;
- content: " ";
+
+.popover.bs-popover-top .arrow::before, .popover.bs-popover-auto[x-placement^="top"] .arrow::before {
+ bottom: -11px;
+ margin-left: -6px;
+ border-top-color: rgba(0, 0, 0, 0.25);
+}
+
+.popover.bs-popover-top .arrow::after, .popover.bs-popover-auto[x-placement^="top"] .arrow::after {
+ bottom: -10px;
+ margin-left: -6px;
border-top-color: #fff;
- border-bottom-width: 0;
}
-.popover.right > .arrow {
- top: 50%;
- left: -11px;
- margin-top: -11px;
- border-right-color: #999;
- border-right-color: rgba(0, 0, 0, .25);
+
+.popover.bs-popover-right, .popover.bs-popover-auto[x-placement^="right"] {
+ margin-left: 10px;
+}
+
+.popover.bs-popover-right .arrow, .popover.bs-popover-auto[x-placement^="right"] .arrow {
+ left: 0;
+}
+
+.popover.bs-popover-right .arrow::before, .popover.bs-popover-auto[x-placement^="right"] .arrow::before,
+.popover.bs-popover-right .arrow::after, .popover.bs-popover-auto[x-placement^="right"] .arrow::after {
+ margin-top: -8px;
border-left-width: 0;
}
-.popover.right > .arrow:after {
- bottom: -10px;
- left: 1px;
- content: " ";
+
+.popover.bs-popover-right .arrow::before, .popover.bs-popover-auto[x-placement^="right"] .arrow::before {
+ left: -11px;
+ border-right-color: rgba(0, 0, 0, 0.25);
+}
+
+.popover.bs-popover-right .arrow::after, .popover.bs-popover-auto[x-placement^="right"] .arrow::after {
+ left: -10px;
border-right-color: #fff;
- border-left-width: 0;
}
-.popover.bottom > .arrow {
- top: -11px;
- left: 50%;
- margin-left: -11px;
- border-top-width: 0;
- border-bottom-color: #999;
- border-bottom-color: rgba(0, 0, 0, .25);
+
+.popover.bs-popover-bottom, .popover.bs-popover-auto[x-placement^="bottom"] {
+ margin-top: 10px;
}
-.popover.bottom > .arrow:after {
- top: 1px;
- margin-left: -10px;
- content: " ";
+
+.popover.bs-popover-bottom .arrow, .popover.bs-popover-auto[x-placement^="bottom"] .arrow {
+ top: 0;
+}
+
+.popover.bs-popover-bottom .arrow::before, .popover.bs-popover-auto[x-placement^="bottom"] .arrow::before,
+.popover.bs-popover-bottom .arrow::after, .popover.bs-popover-auto[x-placement^="bottom"] .arrow::after {
+ margin-left: -7px;
border-top-width: 0;
+}
+
+.popover.bs-popover-bottom .arrow::before, .popover.bs-popover-auto[x-placement^="bottom"] .arrow::before {
+ top: -11px;
+ border-bottom-color: rgba(0, 0, 0, 0.25);
+}
+
+.popover.bs-popover-bottom .arrow::after, .popover.bs-popover-auto[x-placement^="bottom"] .arrow::after {
+ top: -10px;
border-bottom-color: #fff;
}
-.popover.left > .arrow {
- top: 50%;
- right: -11px;
- margin-top: -11px;
- border-right-width: 0;
- border-left-color: #999;
- border-left-color: rgba(0, 0, 0, .25);
+
+.popover.bs-popover-bottom .popover-header::before, .popover.bs-popover-auto[x-placement^="bottom"] .popover-header::before {
+ position: absolute;
+ top: 0;
+ left: 50%;
+ display: block;
+ width: 20px;
+ margin-left: -10px;
+ content: "";
+ border-bottom: 1px solid #f7f7f7;
}
-.popover.left > .arrow:after {
- right: 1px;
- bottom: -10px;
- content: " ";
+
+.popover.bs-popover-left, .popover.bs-popover-auto[x-placement^="left"] {
+ margin-right: 10px;
+}
+
+.popover.bs-popover-left .arrow, .popover.bs-popover-auto[x-placement^="left"] .arrow {
+ right: 0;
+}
+
+.popover.bs-popover-left .arrow::before, .popover.bs-popover-auto[x-placement^="left"] .arrow::before,
+.popover.bs-popover-left .arrow::after, .popover.bs-popover-auto[x-placement^="left"] .arrow::after {
+ margin-top: -8px;
border-right-width: 0;
+}
+
+.popover.bs-popover-left .arrow::before, .popover.bs-popover-auto[x-placement^="left"] .arrow::before {
+ right: -11px;
+ border-left-color: rgba(0, 0, 0, 0.25);
+}
+
+.popover.bs-popover-left .arrow::after, .popover.bs-popover-auto[x-placement^="left"] .arrow::after {
+ right: -10px;
border-left-color: #fff;
}
+
+.popover-header {
+ padding: 8px 14px;
+ margin-bottom: 0;
+ font-size: 1rem;
+ color: inherit;
+ background-color: #f7f7f7;
+ border-bottom: 1px solid #ebebeb;
+ border-top-left-radius: calc(0.3rem - 1px);
+ border-top-right-radius: calc(0.3rem - 1px);
+}
+
+.popover-header:empty {
+ display: none;
+}
+
+.popover-body {
+ padding: 9px 14px;
+ color: #212529;
+}
+
.carousel {
position: relative;
}
+
.carousel-inner {
position: relative;
width: 100%;
overflow: hidden;
}
-.carousel-inner > .item {
+
+.carousel-item {
position: relative;
display: none;
- -webkit-transition: .6s ease-in-out left;
- -o-transition: .6s ease-in-out left;
- transition: .6s ease-in-out left;
-}
-.carousel-inner > .item > img,
-.carousel-inner > .item > a > img {
- line-height: 1;
+ -ms-flex-align: center;
+ align-items: center;
+ width: 100%;
+ transition: -webkit-transform 0.6s ease;
+ transition: transform 0.6s ease;
+ transition: transform 0.6s ease, -webkit-transform 0.6s ease;
+ -webkit-backface-visibility: hidden;
+ backface-visibility: hidden;
+ -webkit-perspective: 1000px;
+ perspective: 1000px;
}
-@media all and (transform-3d), (-webkit-transform-3d) {
- .carousel-inner > .item {
- -webkit-transition: -webkit-transform .6s ease-in-out;
- -o-transition: -o-transform .6s ease-in-out;
- transition: transform .6s ease-in-out;
- -webkit-backface-visibility: hidden;
- backface-visibility: hidden;
- -webkit-perspective: 1000px;
- perspective: 1000px;
- }
- .carousel-inner > .item.next,
- .carousel-inner > .item.active.right {
- left: 0;
- -webkit-transform: translate3d(100%, 0, 0);
- transform: translate3d(100%, 0, 0);
- }
- .carousel-inner > .item.prev,
- .carousel-inner > .item.active.left {
- left: 0;
- -webkit-transform: translate3d(-100%, 0, 0);
- transform: translate3d(-100%, 0, 0);
- }
- .carousel-inner > .item.next.left,
- .carousel-inner > .item.prev.right,
- .carousel-inner > .item.active {
- left: 0;
- -webkit-transform: translate3d(0, 0, 0);
- transform: translate3d(0, 0, 0);
- }
-}
-.carousel-inner > .active,
-.carousel-inner > .next,
-.carousel-inner > .prev {
+.carousel-item.active,
+.carousel-item-next,
+.carousel-item-prev {
display: block;
}
-.carousel-inner > .active {
- left: 0;
-}
-.carousel-inner > .next,
-.carousel-inner > .prev {
+
+.carousel-item-next,
+.carousel-item-prev {
position: absolute;
top: 0;
- width: 100%;
}
-.carousel-inner > .next {
- left: 100%;
+
+.carousel-item-next.carousel-item-left,
+.carousel-item-prev.carousel-item-right {
+ -webkit-transform: translateX(0);
+ transform: translateX(0);
}
-.carousel-inner > .prev {
- left: -100%;
+
+@supports ((-webkit-transform-style: preserve-3d) or (transform-style: preserve-3d)) {
+ .carousel-item-next.carousel-item-left,
+ .carousel-item-prev.carousel-item-right {
+ -webkit-transform: translate3d(0, 0, 0);
+ transform: translate3d(0, 0, 0);
+ }
}
-.carousel-inner > .next.left,
-.carousel-inner > .prev.right {
- left: 0;
+
+.carousel-item-next,
+.active.carousel-item-right {
+ -webkit-transform: translateX(100%);
+ transform: translateX(100%);
}
-.carousel-inner > .active.left {
- left: -100%;
+
+@supports ((-webkit-transform-style: preserve-3d) or (transform-style: preserve-3d)) {
+ .carousel-item-next,
+ .active.carousel-item-right {
+ -webkit-transform: translate3d(100%, 0, 0);
+ transform: translate3d(100%, 0, 0);
+ }
}
-.carousel-inner > .active.right {
- left: 100%;
+
+.carousel-item-prev,
+.active.carousel-item-left {
+ -webkit-transform: translateX(-100%);
+ transform: translateX(-100%);
}
-.carousel-control {
+
+@supports ((-webkit-transform-style: preserve-3d) or (transform-style: preserve-3d)) {
+ .carousel-item-prev,
+ .active.carousel-item-left {
+ -webkit-transform: translate3d(-100%, 0, 0);
+ transform: translate3d(-100%, 0, 0);
+ }
+}
+
+.carousel-control-prev,
+.carousel-control-next {
position: absolute;
top: 0;
bottom: 0;
- left: 0;
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-align: center;
+ align-items: center;
+ -ms-flex-pack: center;
+ justify-content: center;
width: 15%;
- font-size: 20px;
color: #fff;
text-align: center;
- text-shadow: 0 1px 2px rgba(0, 0, 0, .6);
- background-color: rgba(0, 0, 0, 0);
- filter: alpha(opacity=50);
- opacity: .5;
+ opacity: 0.5;
}
-.carousel-control.left {
- background-image: -webkit-linear-gradient(left, rgba(0, 0, 0, .5) 0%, rgba(0, 0, 0, .0001) 100%);
- background-image: -o-linear-gradient(left, rgba(0, 0, 0, .5) 0%, rgba(0, 0, 0, .0001) 100%);
- background-image: -webkit-gradient(linear, left top, right top, from(rgba(0, 0, 0, .5)), to(rgba(0, 0, 0, .0001)));
- background-image: linear-gradient(to right, rgba(0, 0, 0, .5) 0%, rgba(0, 0, 0, .0001) 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#80000000', endColorstr='#00000000', GradientType=1);
- background-repeat: repeat-x;
-}
-.carousel-control.right {
- right: 0;
- left: auto;
- background-image: -webkit-linear-gradient(left, rgba(0, 0, 0, .0001) 0%, rgba(0, 0, 0, .5) 100%);
- background-image: -o-linear-gradient(left, rgba(0, 0, 0, .0001) 0%, rgba(0, 0, 0, .5) 100%);
- background-image: -webkit-gradient(linear, left top, right top, from(rgba(0, 0, 0, .0001)), to(rgba(0, 0, 0, .5)));
- background-image: linear-gradient(to right, rgba(0, 0, 0, .0001) 0%, rgba(0, 0, 0, .5) 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#00000000', endColorstr='#80000000', GradientType=1);
- background-repeat: repeat-x;
-}
-.carousel-control:hover,
-.carousel-control:focus {
+
+.carousel-control-prev:focus, .carousel-control-prev:hover,
+.carousel-control-next:focus,
+.carousel-control-next:hover {
color: #fff;
text-decoration: none;
- filter: alpha(opacity=90);
outline: 0;
opacity: .9;
}
-.carousel-control .icon-prev,
-.carousel-control .icon-next,
-.carousel-control .glyphicon-chevron-left,
-.carousel-control .glyphicon-chevron-right {
- position: absolute;
- top: 50%;
- z-index: 5;
- display: inline-block;
- margin-top: -10px;
-}
-.carousel-control .icon-prev,
-.carousel-control .glyphicon-chevron-left {
- left: 50%;
- margin-left: -10px;
+
+.carousel-control-prev {
+ left: 0;
}
-.carousel-control .icon-next,
-.carousel-control .glyphicon-chevron-right {
- right: 50%;
- margin-right: -10px;
+
+.carousel-control-next {
+ right: 0;
}
-.carousel-control .icon-prev,
-.carousel-control .icon-next {
+
+.carousel-control-prev-icon,
+.carousel-control-next-icon {
+ display: inline-block;
width: 20px;
height: 20px;
- font-family: serif;
- line-height: 1;
+ background: transparent no-repeat center center;
+ background-size: 100% 100%;
}
-.carousel-control .icon-prev:before {
- content: '\2039';
+
+.carousel-control-prev-icon {
+ background-image: url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' fill='%23fff' viewBox='0 0 8 8'%3E%3Cpath d='M4 0l-4 4 4 4 1.5-1.5-2.5-2.5 2.5-2.5-1.5-1.5z'/%3E%3C/svg%3E");
}
-.carousel-control .icon-next:before {
- content: '\203a';
+
+.carousel-control-next-icon {
+ background-image: url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' fill='%23fff' viewBox='0 0 8 8'%3E%3Cpath d='M1.5 0l-1.5 1.5 2.5 2.5-2.5 2.5 1.5 1.5 4-4-4-4z'/%3E%3C/svg%3E");
}
+
.carousel-indicators {
position: absolute;
+ right: 0;
bottom: 10px;
- left: 50%;
+ left: 0;
z-index: 15;
- width: 60%;
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-pack: center;
+ justify-content: center;
padding-left: 0;
- margin-left: -30%;
- text-align: center;
+ margin-right: 15%;
+ margin-left: 15%;
list-style: none;
}
+
.carousel-indicators li {
+ position: relative;
+ -ms-flex: 0 1 auto;
+ flex: 0 1 auto;
+ width: 30px;
+ height: 3px;
+ margin-right: 3px;
+ margin-left: 3px;
+ text-indent: -999px;
+ background-color: rgba(255, 255, 255, 0.5);
+}
+
+.carousel-indicators li::before {
+ position: absolute;
+ top: -10px;
+ left: 0;
display: inline-block;
- width: 10px;
+ width: 100%;
height: 10px;
- margin: 1px;
- text-indent: -999px;
- cursor: pointer;
- background-color: #000 \9;
- background-color: rgba(0, 0, 0, 0);
- border: 1px solid #fff;
- border-radius: 10px;
+ content: "";
+}
+
+.carousel-indicators li::after {
+ position: absolute;
+ bottom: -10px;
+ left: 0;
+ display: inline-block;
+ width: 100%;
+ height: 10px;
+ content: "";
}
+
.carousel-indicators .active {
- width: 12px;
- height: 12px;
- margin: 0;
background-color: #fff;
}
+
.carousel-caption {
position: absolute;
right: 15%;
@@ -6426,332 +5204,2982 @@ button.close {
padding-bottom: 20px;
color: #fff;
text-align: center;
- text-shadow: 0 1px 2px rgba(0, 0, 0, .6);
}
-.carousel-caption .btn {
- text-shadow: none;
+
+.align-baseline {
+ vertical-align: baseline !important;
}
-@media screen and (min-width: 768px) {
- .carousel-control .glyphicon-chevron-left,
- .carousel-control .glyphicon-chevron-right,
- .carousel-control .icon-prev,
- .carousel-control .icon-next {
- width: 30px;
- height: 30px;
- margin-top: -10px;
- font-size: 30px;
- }
- .carousel-control .glyphicon-chevron-left,
- .carousel-control .icon-prev {
- margin-left: -10px;
- }
- .carousel-control .glyphicon-chevron-right,
- .carousel-control .icon-next {
- margin-right: -10px;
- }
- .carousel-caption {
- right: 20%;
- left: 20%;
- padding-bottom: 30px;
- }
- .carousel-indicators {
- bottom: 20px;
- }
-}
-.clearfix:before,
-.clearfix:after,
-.dl-horizontal dd:before,
-.dl-horizontal dd:after,
-.container:before,
-.container:after,
-.container-fluid:before,
-.container-fluid:after,
-.row:before,
-.row:after,
-.form-horizontal .form-group:before,
-.form-horizontal .form-group:after,
-.btn-toolbar:before,
-.btn-toolbar:after,
-.btn-group-vertical > .btn-group:before,
-.btn-group-vertical > .btn-group:after,
-.nav:before,
-.nav:after,
-.navbar:before,
-.navbar:after,
-.navbar-header:before,
-.navbar-header:after,
-.navbar-collapse:before,
-.navbar-collapse:after,
-.pager:before,
-.pager:after,
-.panel-body:before,
-.panel-body:after,
-.modal-header:before,
-.modal-header:after,
-.modal-footer:before,
-.modal-footer:after {
- display: table;
- content: " ";
-}
-.clearfix:after,
-.dl-horizontal dd:after,
-.container:after,
-.container-fluid:after,
-.row:after,
-.form-horizontal .form-group:after,
-.btn-toolbar:after,
-.btn-group-vertical > .btn-group:after,
-.nav:after,
-.navbar:after,
-.navbar-header:after,
-.navbar-collapse:after,
-.pager:after,
-.panel-body:after,
-.modal-header:after,
-.modal-footer:after {
- clear: both;
+
+.align-top {
+ vertical-align: top !important;
}
-.center-block {
- display: block;
- margin-right: auto;
- margin-left: auto;
+
+.align-middle {
+ vertical-align: middle !important;
}
-.pull-right {
- float: right !important;
+
+.align-bottom {
+ vertical-align: bottom !important;
}
-.pull-left {
- float: left !important;
+
+.align-text-bottom {
+ vertical-align: text-bottom !important;
}
-.hide {
- display: none !important;
+
+.align-text-top {
+ vertical-align: text-top !important;
}
-.show {
- display: block !important;
+
+.bg-primary {
+ background-color: #007bff !important;
}
-.invisible {
- visibility: hidden;
+
+a.bg-primary:focus, a.bg-primary:hover {
+ background-color: #0062cc !important;
}
-.text-hide {
- font: 0/0 a;
- color: transparent;
- text-shadow: none;
- background-color: transparent;
- border: 0;
+
+.bg-secondary {
+ background-color: #868e96 !important;
}
-.hidden {
- display: none !important;
+
+a.bg-secondary:focus, a.bg-secondary:hover {
+ background-color: #6c757d !important;
}
-.affix {
- position: fixed;
+
+.bg-success {
+ background-color: #28a745 !important;
}
-@-ms-viewport {
- width: device-width;
+
+a.bg-success:focus, a.bg-success:hover {
+ background-color: #1e7e34 !important;
}
-.visible-xs,
-.visible-sm,
-.visible-md,
-.visible-lg {
- display: none !important;
+
+.bg-info {
+ background-color: #17a2b8 !important;
+}
+
+a.bg-info:focus, a.bg-info:hover {
+ background-color: #117a8b !important;
+}
+
+.bg-warning {
+ background-color: #ffc107 !important;
+}
+
+a.bg-warning:focus, a.bg-warning:hover {
+ background-color: #d39e00 !important;
+}
+
+.bg-danger {
+ background-color: #dc3545 !important;
+}
+
+a.bg-danger:focus, a.bg-danger:hover {
+ background-color: #bd2130 !important;
+}
+
+.bg-light {
+ background-color: #f8f9fa !important;
+}
+
+a.bg-light:focus, a.bg-light:hover {
+ background-color: #dae0e5 !important;
+}
+
+.bg-dark {
+ background-color: #343a40 !important;
+}
+
+a.bg-dark:focus, a.bg-dark:hover {
+ background-color: #1d2124 !important;
+}
+
+.bg-white {
+ background-color: #fff !important;
+}
+
+.bg-transparent {
+ background-color: transparent !important;
+}
+
+.border {
+ border: 1px solid #e9ecef !important;
+}
+
+.border-0 {
+ border: 0 !important;
+}
+
+.border-top-0 {
+ border-top: 0 !important;
+}
+
+.border-right-0 {
+ border-right: 0 !important;
+}
+
+.border-bottom-0 {
+ border-bottom: 0 !important;
+}
+
+.border-left-0 {
+ border-left: 0 !important;
+}
+
+.border-primary {
+ border-color: #007bff !important;
+}
+
+.border-secondary {
+ border-color: #868e96 !important;
+}
+
+.border-success {
+ border-color: #28a745 !important;
+}
+
+.border-info {
+ border-color: #17a2b8 !important;
+}
+
+.border-warning {
+ border-color: #ffc107 !important;
+}
+
+.border-danger {
+ border-color: #dc3545 !important;
+}
+
+.border-light {
+ border-color: #f8f9fa !important;
+}
+
+.border-dark {
+ border-color: #343a40 !important;
+}
+
+.border-white {
+ border-color: #fff !important;
+}
+
+.rounded {
+ border-radius: 0.25rem !important;
+}
+
+.rounded-top {
+ border-top-left-radius: 0.25rem !important;
+ border-top-right-radius: 0.25rem !important;
+}
+
+.rounded-right {
+ border-top-right-radius: 0.25rem !important;
+ border-bottom-right-radius: 0.25rem !important;
}
-.visible-xs-block,
-.visible-xs-inline,
-.visible-xs-inline-block,
-.visible-sm-block,
-.visible-sm-inline,
-.visible-sm-inline-block,
-.visible-md-block,
-.visible-md-inline,
-.visible-md-inline-block,
-.visible-lg-block,
-.visible-lg-inline,
-.visible-lg-inline-block {
+
+.rounded-bottom {
+ border-bottom-right-radius: 0.25rem !important;
+ border-bottom-left-radius: 0.25rem !important;
+}
+
+.rounded-left {
+ border-top-left-radius: 0.25rem !important;
+ border-bottom-left-radius: 0.25rem !important;
+}
+
+.rounded-circle {
+ border-radius: 50%;
+}
+
+.rounded-0 {
+ border-radius: 0;
+}
+
+.clearfix::after {
+ display: block;
+ clear: both;
+ content: "";
+}
+
+.d-none {
display: none !important;
}
-@media (max-width: 767px) {
- .visible-xs {
+
+.d-inline {
+ display: inline !important;
+}
+
+.d-inline-block {
+ display: inline-block !important;
+}
+
+.d-block {
+ display: block !important;
+}
+
+.d-table {
+ display: table !important;
+}
+
+.d-table-cell {
+ display: table-cell !important;
+}
+
+.d-flex {
+ display: -ms-flexbox !important;
+ display: flex !important;
+}
+
+.d-inline-flex {
+ display: -ms-inline-flexbox !important;
+ display: inline-flex !important;
+}
+
+@media (min-width: 576px) {
+ .d-sm-none {
+ display: none !important;
+ }
+ .d-sm-inline {
+ display: inline !important;
+ }
+ .d-sm-inline-block {
+ display: inline-block !important;
+ }
+ .d-sm-block {
display: block !important;
}
- table.visible-xs {
+ .d-sm-table {
display: table !important;
}
- tr.visible-xs {
- display: table-row !important;
- }
- th.visible-xs,
- td.visible-xs {
+ .d-sm-table-cell {
display: table-cell !important;
}
-}
-@media (max-width: 767px) {
- .visible-xs-block {
- display: block !important;
+ .d-sm-flex {
+ display: -ms-flexbox !important;
+ display: flex !important;
+ }
+ .d-sm-inline-flex {
+ display: -ms-inline-flexbox !important;
+ display: inline-flex !important;
}
}
-@media (max-width: 767px) {
- .visible-xs-inline {
+
+@media (min-width: 768px) {
+ .d-md-none {
+ display: none !important;
+ }
+ .d-md-inline {
display: inline !important;
}
-}
-@media (max-width: 767px) {
- .visible-xs-inline-block {
+ .d-md-inline-block {
display: inline-block !important;
}
-}
-@media (min-width: 768px) and (max-width: 991px) {
- .visible-sm {
+ .d-md-block {
display: block !important;
}
- table.visible-sm {
+ .d-md-table {
display: table !important;
}
- tr.visible-sm {
- display: table-row !important;
- }
- th.visible-sm,
- td.visible-sm {
+ .d-md-table-cell {
display: table-cell !important;
}
+ .d-md-flex {
+ display: -ms-flexbox !important;
+ display: flex !important;
+ }
+ .d-md-inline-flex {
+ display: -ms-inline-flexbox !important;
+ display: inline-flex !important;
+ }
}
-@media (min-width: 768px) and (max-width: 991px) {
- .visible-sm-block {
+
+@media (min-width: 992px) {
+ .d-lg-none {
+ display: none !important;
+ }
+ .d-lg-inline {
+ display: inline !important;
+ }
+ .d-lg-inline-block {
+ display: inline-block !important;
+ }
+ .d-lg-block {
display: block !important;
}
+ .d-lg-table {
+ display: table !important;
+ }
+ .d-lg-table-cell {
+ display: table-cell !important;
+ }
+ .d-lg-flex {
+ display: -ms-flexbox !important;
+ display: flex !important;
+ }
+ .d-lg-inline-flex {
+ display: -ms-inline-flexbox !important;
+ display: inline-flex !important;
+ }
}
-@media (min-width: 768px) and (max-width: 991px) {
- .visible-sm-inline {
+
+@media (min-width: 1200px) {
+ .d-xl-none {
+ display: none !important;
+ }
+ .d-xl-inline {
display: inline !important;
}
-}
-@media (min-width: 768px) and (max-width: 991px) {
- .visible-sm-inline-block {
+ .d-xl-inline-block {
display: inline-block !important;
}
-}
-@media (min-width: 992px) and (max-width: 1199px) {
- .visible-md {
+ .d-xl-block {
display: block !important;
}
- table.visible-md {
+ .d-xl-table {
display: table !important;
}
- tr.visible-md {
- display: table-row !important;
- }
- th.visible-md,
- td.visible-md {
+ .d-xl-table-cell {
display: table-cell !important;
}
+ .d-xl-flex {
+ display: -ms-flexbox !important;
+ display: flex !important;
+ }
+ .d-xl-inline-flex {
+ display: -ms-inline-flexbox !important;
+ display: inline-flex !important;
+ }
}
-@media (min-width: 992px) and (max-width: 1199px) {
- .visible-md-block {
+
+.d-print-block {
+ display: none !important;
+}
+
+@media print {
+ .d-print-block {
display: block !important;
}
}
-@media (min-width: 992px) and (max-width: 1199px) {
- .visible-md-inline {
+
+.d-print-inline {
+ display: none !important;
+}
+
+@media print {
+ .d-print-inline {
display: inline !important;
}
}
-@media (min-width: 992px) and (max-width: 1199px) {
- .visible-md-inline-block {
+
+.d-print-inline-block {
+ display: none !important;
+}
+
+@media print {
+ .d-print-inline-block {
display: inline-block !important;
}
}
-@media (min-width: 1200px) {
- .visible-lg {
- display: block !important;
+
+@media print {
+ .d-print-none {
+ display: none !important;
}
- table.visible-lg {
- display: table !important;
+}
+
+.embed-responsive {
+ position: relative;
+ display: block;
+ width: 100%;
+ padding: 0;
+ overflow: hidden;
+}
+
+.embed-responsive::before {
+ display: block;
+ content: "";
+}
+
+.embed-responsive .embed-responsive-item,
+.embed-responsive iframe,
+.embed-responsive embed,
+.embed-responsive object,
+.embed-responsive video {
+ position: absolute;
+ top: 0;
+ bottom: 0;
+ left: 0;
+ width: 100%;
+ height: 100%;
+ border: 0;
+}
+
+.embed-responsive-21by9::before {
+ padding-top: 42.857143%;
+}
+
+.embed-responsive-16by9::before {
+ padding-top: 56.25%;
+}
+
+.embed-responsive-4by3::before {
+ padding-top: 75%;
+}
+
+.embed-responsive-1by1::before {
+ padding-top: 100%;
+}
+
+.flex-row {
+ -ms-flex-direction: row !important;
+ flex-direction: row !important;
+}
+
+.flex-column {
+ -ms-flex-direction: column !important;
+ flex-direction: column !important;
+}
+
+.flex-row-reverse {
+ -ms-flex-direction: row-reverse !important;
+ flex-direction: row-reverse !important;
+}
+
+.flex-column-reverse {
+ -ms-flex-direction: column-reverse !important;
+ flex-direction: column-reverse !important;
+}
+
+.flex-wrap {
+ -ms-flex-wrap: wrap !important;
+ flex-wrap: wrap !important;
+}
+
+.flex-nowrap {
+ -ms-flex-wrap: nowrap !important;
+ flex-wrap: nowrap !important;
+}
+
+.flex-wrap-reverse {
+ -ms-flex-wrap: wrap-reverse !important;
+ flex-wrap: wrap-reverse !important;
+}
+
+.justify-content-start {
+ -ms-flex-pack: start !important;
+ justify-content: flex-start !important;
+}
+
+.justify-content-end {
+ -ms-flex-pack: end !important;
+ justify-content: flex-end !important;
+}
+
+.justify-content-center {
+ -ms-flex-pack: center !important;
+ justify-content: center !important;
+}
+
+.justify-content-between {
+ -ms-flex-pack: justify !important;
+ justify-content: space-between !important;
+}
+
+.justify-content-around {
+ -ms-flex-pack: distribute !important;
+ justify-content: space-around !important;
+}
+
+.align-items-start {
+ -ms-flex-align: start !important;
+ align-items: flex-start !important;
+}
+
+.align-items-end {
+ -ms-flex-align: end !important;
+ align-items: flex-end !important;
+}
+
+.align-items-center {
+ -ms-flex-align: center !important;
+ align-items: center !important;
+}
+
+.align-items-baseline {
+ -ms-flex-align: baseline !important;
+ align-items: baseline !important;
+}
+
+.align-items-stretch {
+ -ms-flex-align: stretch !important;
+ align-items: stretch !important;
+}
+
+.align-content-start {
+ -ms-flex-line-pack: start !important;
+ align-content: flex-start !important;
+}
+
+.align-content-end {
+ -ms-flex-line-pack: end !important;
+ align-content: flex-end !important;
+}
+
+.align-content-center {
+ -ms-flex-line-pack: center !important;
+ align-content: center !important;
+}
+
+.align-content-between {
+ -ms-flex-line-pack: justify !important;
+ align-content: space-between !important;
+}
+
+.align-content-around {
+ -ms-flex-line-pack: distribute !important;
+ align-content: space-around !important;
+}
+
+.align-content-stretch {
+ -ms-flex-line-pack: stretch !important;
+ align-content: stretch !important;
+}
+
+.align-self-auto {
+ -ms-flex-item-align: auto !important;
+ align-self: auto !important;
+}
+
+.align-self-start {
+ -ms-flex-item-align: start !important;
+ align-self: flex-start !important;
+}
+
+.align-self-end {
+ -ms-flex-item-align: end !important;
+ align-self: flex-end !important;
+}
+
+.align-self-center {
+ -ms-flex-item-align: center !important;
+ align-self: center !important;
+}
+
+.align-self-baseline {
+ -ms-flex-item-align: baseline !important;
+ align-self: baseline !important;
+}
+
+.align-self-stretch {
+ -ms-flex-item-align: stretch !important;
+ align-self: stretch !important;
+}
+
+@media (min-width: 576px) {
+ .flex-sm-row {
+ -ms-flex-direction: row !important;
+ flex-direction: row !important;
}
- tr.visible-lg {
- display: table-row !important;
+ .flex-sm-column {
+ -ms-flex-direction: column !important;
+ flex-direction: column !important;
}
- th.visible-lg,
- td.visible-lg {
- display: table-cell !important;
+ .flex-sm-row-reverse {
+ -ms-flex-direction: row-reverse !important;
+ flex-direction: row-reverse !important;
+ }
+ .flex-sm-column-reverse {
+ -ms-flex-direction: column-reverse !important;
+ flex-direction: column-reverse !important;
+ }
+ .flex-sm-wrap {
+ -ms-flex-wrap: wrap !important;
+ flex-wrap: wrap !important;
+ }
+ .flex-sm-nowrap {
+ -ms-flex-wrap: nowrap !important;
+ flex-wrap: nowrap !important;
+ }
+ .flex-sm-wrap-reverse {
+ -ms-flex-wrap: wrap-reverse !important;
+ flex-wrap: wrap-reverse !important;
+ }
+ .justify-content-sm-start {
+ -ms-flex-pack: start !important;
+ justify-content: flex-start !important;
+ }
+ .justify-content-sm-end {
+ -ms-flex-pack: end !important;
+ justify-content: flex-end !important;
+ }
+ .justify-content-sm-center {
+ -ms-flex-pack: center !important;
+ justify-content: center !important;
+ }
+ .justify-content-sm-between {
+ -ms-flex-pack: justify !important;
+ justify-content: space-between !important;
+ }
+ .justify-content-sm-around {
+ -ms-flex-pack: distribute !important;
+ justify-content: space-around !important;
+ }
+ .align-items-sm-start {
+ -ms-flex-align: start !important;
+ align-items: flex-start !important;
+ }
+ .align-items-sm-end {
+ -ms-flex-align: end !important;
+ align-items: flex-end !important;
+ }
+ .align-items-sm-center {
+ -ms-flex-align: center !important;
+ align-items: center !important;
+ }
+ .align-items-sm-baseline {
+ -ms-flex-align: baseline !important;
+ align-items: baseline !important;
+ }
+ .align-items-sm-stretch {
+ -ms-flex-align: stretch !important;
+ align-items: stretch !important;
+ }
+ .align-content-sm-start {
+ -ms-flex-line-pack: start !important;
+ align-content: flex-start !important;
+ }
+ .align-content-sm-end {
+ -ms-flex-line-pack: end !important;
+ align-content: flex-end !important;
+ }
+ .align-content-sm-center {
+ -ms-flex-line-pack: center !important;
+ align-content: center !important;
+ }
+ .align-content-sm-between {
+ -ms-flex-line-pack: justify !important;
+ align-content: space-between !important;
+ }
+ .align-content-sm-around {
+ -ms-flex-line-pack: distribute !important;
+ align-content: space-around !important;
+ }
+ .align-content-sm-stretch {
+ -ms-flex-line-pack: stretch !important;
+ align-content: stretch !important;
+ }
+ .align-self-sm-auto {
+ -ms-flex-item-align: auto !important;
+ align-self: auto !important;
+ }
+ .align-self-sm-start {
+ -ms-flex-item-align: start !important;
+ align-self: flex-start !important;
+ }
+ .align-self-sm-end {
+ -ms-flex-item-align: end !important;
+ align-self: flex-end !important;
+ }
+ .align-self-sm-center {
+ -ms-flex-item-align: center !important;
+ align-self: center !important;
+ }
+ .align-self-sm-baseline {
+ -ms-flex-item-align: baseline !important;
+ align-self: baseline !important;
+ }
+ .align-self-sm-stretch {
+ -ms-flex-item-align: stretch !important;
+ align-self: stretch !important;
}
}
-@media (min-width: 1200px) {
- .visible-lg-block {
- display: block !important;
+
+@media (min-width: 768px) {
+ .flex-md-row {
+ -ms-flex-direction: row !important;
+ flex-direction: row !important;
+ }
+ .flex-md-column {
+ -ms-flex-direction: column !important;
+ flex-direction: column !important;
+ }
+ .flex-md-row-reverse {
+ -ms-flex-direction: row-reverse !important;
+ flex-direction: row-reverse !important;
+ }
+ .flex-md-column-reverse {
+ -ms-flex-direction: column-reverse !important;
+ flex-direction: column-reverse !important;
+ }
+ .flex-md-wrap {
+ -ms-flex-wrap: wrap !important;
+ flex-wrap: wrap !important;
+ }
+ .flex-md-nowrap {
+ -ms-flex-wrap: nowrap !important;
+ flex-wrap: nowrap !important;
+ }
+ .flex-md-wrap-reverse {
+ -ms-flex-wrap: wrap-reverse !important;
+ flex-wrap: wrap-reverse !important;
+ }
+ .justify-content-md-start {
+ -ms-flex-pack: start !important;
+ justify-content: flex-start !important;
+ }
+ .justify-content-md-end {
+ -ms-flex-pack: end !important;
+ justify-content: flex-end !important;
+ }
+ .justify-content-md-center {
+ -ms-flex-pack: center !important;
+ justify-content: center !important;
+ }
+ .justify-content-md-between {
+ -ms-flex-pack: justify !important;
+ justify-content: space-between !important;
+ }
+ .justify-content-md-around {
+ -ms-flex-pack: distribute !important;
+ justify-content: space-around !important;
+ }
+ .align-items-md-start {
+ -ms-flex-align: start !important;
+ align-items: flex-start !important;
+ }
+ .align-items-md-end {
+ -ms-flex-align: end !important;
+ align-items: flex-end !important;
+ }
+ .align-items-md-center {
+ -ms-flex-align: center !important;
+ align-items: center !important;
+ }
+ .align-items-md-baseline {
+ -ms-flex-align: baseline !important;
+ align-items: baseline !important;
+ }
+ .align-items-md-stretch {
+ -ms-flex-align: stretch !important;
+ align-items: stretch !important;
+ }
+ .align-content-md-start {
+ -ms-flex-line-pack: start !important;
+ align-content: flex-start !important;
+ }
+ .align-content-md-end {
+ -ms-flex-line-pack: end !important;
+ align-content: flex-end !important;
+ }
+ .align-content-md-center {
+ -ms-flex-line-pack: center !important;
+ align-content: center !important;
+ }
+ .align-content-md-between {
+ -ms-flex-line-pack: justify !important;
+ align-content: space-between !important;
+ }
+ .align-content-md-around {
+ -ms-flex-line-pack: distribute !important;
+ align-content: space-around !important;
+ }
+ .align-content-md-stretch {
+ -ms-flex-line-pack: stretch !important;
+ align-content: stretch !important;
+ }
+ .align-self-md-auto {
+ -ms-flex-item-align: auto !important;
+ align-self: auto !important;
+ }
+ .align-self-md-start {
+ -ms-flex-item-align: start !important;
+ align-self: flex-start !important;
+ }
+ .align-self-md-end {
+ -ms-flex-item-align: end !important;
+ align-self: flex-end !important;
+ }
+ .align-self-md-center {
+ -ms-flex-item-align: center !important;
+ align-self: center !important;
+ }
+ .align-self-md-baseline {
+ -ms-flex-item-align: baseline !important;
+ align-self: baseline !important;
+ }
+ .align-self-md-stretch {
+ -ms-flex-item-align: stretch !important;
+ align-self: stretch !important;
}
}
-@media (min-width: 1200px) {
- .visible-lg-inline {
- display: inline !important;
+
+@media (min-width: 992px) {
+ .flex-lg-row {
+ -ms-flex-direction: row !important;
+ flex-direction: row !important;
+ }
+ .flex-lg-column {
+ -ms-flex-direction: column !important;
+ flex-direction: column !important;
+ }
+ .flex-lg-row-reverse {
+ -ms-flex-direction: row-reverse !important;
+ flex-direction: row-reverse !important;
+ }
+ .flex-lg-column-reverse {
+ -ms-flex-direction: column-reverse !important;
+ flex-direction: column-reverse !important;
+ }
+ .flex-lg-wrap {
+ -ms-flex-wrap: wrap !important;
+ flex-wrap: wrap !important;
+ }
+ .flex-lg-nowrap {
+ -ms-flex-wrap: nowrap !important;
+ flex-wrap: nowrap !important;
+ }
+ .flex-lg-wrap-reverse {
+ -ms-flex-wrap: wrap-reverse !important;
+ flex-wrap: wrap-reverse !important;
+ }
+ .justify-content-lg-start {
+ -ms-flex-pack: start !important;
+ justify-content: flex-start !important;
+ }
+ .justify-content-lg-end {
+ -ms-flex-pack: end !important;
+ justify-content: flex-end !important;
+ }
+ .justify-content-lg-center {
+ -ms-flex-pack: center !important;
+ justify-content: center !important;
+ }
+ .justify-content-lg-between {
+ -ms-flex-pack: justify !important;
+ justify-content: space-between !important;
+ }
+ .justify-content-lg-around {
+ -ms-flex-pack: distribute !important;
+ justify-content: space-around !important;
+ }
+ .align-items-lg-start {
+ -ms-flex-align: start !important;
+ align-items: flex-start !important;
+ }
+ .align-items-lg-end {
+ -ms-flex-align: end !important;
+ align-items: flex-end !important;
+ }
+ .align-items-lg-center {
+ -ms-flex-align: center !important;
+ align-items: center !important;
+ }
+ .align-items-lg-baseline {
+ -ms-flex-align: baseline !important;
+ align-items: baseline !important;
+ }
+ .align-items-lg-stretch {
+ -ms-flex-align: stretch !important;
+ align-items: stretch !important;
+ }
+ .align-content-lg-start {
+ -ms-flex-line-pack: start !important;
+ align-content: flex-start !important;
+ }
+ .align-content-lg-end {
+ -ms-flex-line-pack: end !important;
+ align-content: flex-end !important;
+ }
+ .align-content-lg-center {
+ -ms-flex-line-pack: center !important;
+ align-content: center !important;
+ }
+ .align-content-lg-between {
+ -ms-flex-line-pack: justify !important;
+ align-content: space-between !important;
+ }
+ .align-content-lg-around {
+ -ms-flex-line-pack: distribute !important;
+ align-content: space-around !important;
+ }
+ .align-content-lg-stretch {
+ -ms-flex-line-pack: stretch !important;
+ align-content: stretch !important;
+ }
+ .align-self-lg-auto {
+ -ms-flex-item-align: auto !important;
+ align-self: auto !important;
+ }
+ .align-self-lg-start {
+ -ms-flex-item-align: start !important;
+ align-self: flex-start !important;
+ }
+ .align-self-lg-end {
+ -ms-flex-item-align: end !important;
+ align-self: flex-end !important;
+ }
+ .align-self-lg-center {
+ -ms-flex-item-align: center !important;
+ align-self: center !important;
+ }
+ .align-self-lg-baseline {
+ -ms-flex-item-align: baseline !important;
+ align-self: baseline !important;
+ }
+ .align-self-lg-stretch {
+ -ms-flex-item-align: stretch !important;
+ align-self: stretch !important;
}
}
+
@media (min-width: 1200px) {
- .visible-lg-inline-block {
- display: inline-block !important;
+ .flex-xl-row {
+ -ms-flex-direction: row !important;
+ flex-direction: row !important;
+ }
+ .flex-xl-column {
+ -ms-flex-direction: column !important;
+ flex-direction: column !important;
+ }
+ .flex-xl-row-reverse {
+ -ms-flex-direction: row-reverse !important;
+ flex-direction: row-reverse !important;
+ }
+ .flex-xl-column-reverse {
+ -ms-flex-direction: column-reverse !important;
+ flex-direction: column-reverse !important;
+ }
+ .flex-xl-wrap {
+ -ms-flex-wrap: wrap !important;
+ flex-wrap: wrap !important;
+ }
+ .flex-xl-nowrap {
+ -ms-flex-wrap: nowrap !important;
+ flex-wrap: nowrap !important;
+ }
+ .flex-xl-wrap-reverse {
+ -ms-flex-wrap: wrap-reverse !important;
+ flex-wrap: wrap-reverse !important;
+ }
+ .justify-content-xl-start {
+ -ms-flex-pack: start !important;
+ justify-content: flex-start !important;
+ }
+ .justify-content-xl-end {
+ -ms-flex-pack: end !important;
+ justify-content: flex-end !important;
+ }
+ .justify-content-xl-center {
+ -ms-flex-pack: center !important;
+ justify-content: center !important;
+ }
+ .justify-content-xl-between {
+ -ms-flex-pack: justify !important;
+ justify-content: space-between !important;
+ }
+ .justify-content-xl-around {
+ -ms-flex-pack: distribute !important;
+ justify-content: space-around !important;
+ }
+ .align-items-xl-start {
+ -ms-flex-align: start !important;
+ align-items: flex-start !important;
+ }
+ .align-items-xl-end {
+ -ms-flex-align: end !important;
+ align-items: flex-end !important;
+ }
+ .align-items-xl-center {
+ -ms-flex-align: center !important;
+ align-items: center !important;
+ }
+ .align-items-xl-baseline {
+ -ms-flex-align: baseline !important;
+ align-items: baseline !important;
+ }
+ .align-items-xl-stretch {
+ -ms-flex-align: stretch !important;
+ align-items: stretch !important;
+ }
+ .align-content-xl-start {
+ -ms-flex-line-pack: start !important;
+ align-content: flex-start !important;
+ }
+ .align-content-xl-end {
+ -ms-flex-line-pack: end !important;
+ align-content: flex-end !important;
+ }
+ .align-content-xl-center {
+ -ms-flex-line-pack: center !important;
+ align-content: center !important;
+ }
+ .align-content-xl-between {
+ -ms-flex-line-pack: justify !important;
+ align-content: space-between !important;
+ }
+ .align-content-xl-around {
+ -ms-flex-line-pack: distribute !important;
+ align-content: space-around !important;
+ }
+ .align-content-xl-stretch {
+ -ms-flex-line-pack: stretch !important;
+ align-content: stretch !important;
+ }
+ .align-self-xl-auto {
+ -ms-flex-item-align: auto !important;
+ align-self: auto !important;
+ }
+ .align-self-xl-start {
+ -ms-flex-item-align: start !important;
+ align-self: flex-start !important;
+ }
+ .align-self-xl-end {
+ -ms-flex-item-align: end !important;
+ align-self: flex-end !important;
+ }
+ .align-self-xl-center {
+ -ms-flex-item-align: center !important;
+ align-self: center !important;
+ }
+ .align-self-xl-baseline {
+ -ms-flex-item-align: baseline !important;
+ align-self: baseline !important;
+ }
+ .align-self-xl-stretch {
+ -ms-flex-item-align: stretch !important;
+ align-self: stretch !important;
}
}
-@media (max-width: 767px) {
- .hidden-xs {
- display: none !important;
+
+.float-left {
+ float: left !important;
+}
+
+.float-right {
+ float: right !important;
+}
+
+.float-none {
+ float: none !important;
+}
+
+@media (min-width: 576px) {
+ .float-sm-left {
+ float: left !important;
+ }
+ .float-sm-right {
+ float: right !important;
+ }
+ .float-sm-none {
+ float: none !important;
}
}
-@media (min-width: 768px) and (max-width: 991px) {
- .hidden-sm {
- display: none !important;
+
+@media (min-width: 768px) {
+ .float-md-left {
+ float: left !important;
+ }
+ .float-md-right {
+ float: right !important;
+ }
+ .float-md-none {
+ float: none !important;
}
}
-@media (min-width: 992px) and (max-width: 1199px) {
- .hidden-md {
- display: none !important;
+
+@media (min-width: 992px) {
+ .float-lg-left {
+ float: left !important;
+ }
+ .float-lg-right {
+ float: right !important;
+ }
+ .float-lg-none {
+ float: none !important;
}
}
+
@media (min-width: 1200px) {
- .hidden-lg {
- display: none !important;
+ .float-xl-left {
+ float: left !important;
+ }
+ .float-xl-right {
+ float: right !important;
+ }
+ .float-xl-none {
+ float: none !important;
}
}
-.visible-print {
- display: none !important;
+
+.fixed-top {
+ position: fixed;
+ top: 0;
+ right: 0;
+ left: 0;
+ z-index: 1030;
}
-@media print {
- .visible-print {
- display: block !important;
+
+.fixed-bottom {
+ position: fixed;
+ right: 0;
+ bottom: 0;
+ left: 0;
+ z-index: 1030;
+}
+
+@supports ((position: -webkit-sticky) or (position: sticky)) {
+ .sticky-top {
+ position: -webkit-sticky;
+ position: sticky;
+ top: 0;
+ z-index: 1020;
}
- table.visible-print {
- display: table !important;
+}
+
+.sr-only {
+ position: absolute;
+ width: 1px;
+ height: 1px;
+ padding: 0;
+ overflow: hidden;
+ clip: rect(0, 0, 0, 0);
+ white-space: nowrap;
+ -webkit-clip-path: inset(50%);
+ clip-path: inset(50%);
+ border: 0;
+}
+
+.sr-only-focusable:active, .sr-only-focusable:focus {
+ position: static;
+ width: auto;
+ height: auto;
+ overflow: visible;
+ clip: auto;
+ white-space: normal;
+ -webkit-clip-path: none;
+ clip-path: none;
+}
+
+.w-25 {
+ width: 25% !important;
+}
+
+.w-50 {
+ width: 50% !important;
+}
+
+.w-75 {
+ width: 75% !important;
+}
+
+.w-100 {
+ width: 100% !important;
+}
+
+.h-25 {
+ height: 25% !important;
+}
+
+.h-50 {
+ height: 50% !important;
+}
+
+.h-75 {
+ height: 75% !important;
+}
+
+.h-100 {
+ height: 100% !important;
+}
+
+.mw-100 {
+ max-width: 100% !important;
+}
+
+.mh-100 {
+ max-height: 100% !important;
+}
+
+.m-0 {
+ margin: 0 !important;
+}
+
+.mt-0 {
+ margin-top: 0 !important;
+}
+
+.mr-0 {
+ margin-right: 0 !important;
+}
+
+.mb-0 {
+ margin-bottom: 0 !important;
+}
+
+.ml-0 {
+ margin-left: 0 !important;
+}
+
+.mx-0 {
+ margin-right: 0 !important;
+ margin-left: 0 !important;
+}
+
+.my-0 {
+ margin-top: 0 !important;
+ margin-bottom: 0 !important;
+}
+
+.m-1 {
+ margin: 0.25rem !important;
+}
+
+.mt-1 {
+ margin-top: 0.25rem !important;
+}
+
+.mr-1 {
+ margin-right: 0.25rem !important;
+}
+
+.mb-1 {
+ margin-bottom: 0.25rem !important;
+}
+
+.ml-1 {
+ margin-left: 0.25rem !important;
+}
+
+.mx-1 {
+ margin-right: 0.25rem !important;
+ margin-left: 0.25rem !important;
+}
+
+.my-1 {
+ margin-top: 0.25rem !important;
+ margin-bottom: 0.25rem !important;
+}
+
+.m-2 {
+ margin: 0.5rem !important;
+}
+
+.mt-2 {
+ margin-top: 0.5rem !important;
+}
+
+.mr-2 {
+ margin-right: 0.5rem !important;
+}
+
+.mb-2 {
+ margin-bottom: 0.5rem !important;
+}
+
+.ml-2 {
+ margin-left: 0.5rem !important;
+}
+
+.mx-2 {
+ margin-right: 0.5rem !important;
+ margin-left: 0.5rem !important;
+}
+
+.my-2 {
+ margin-top: 0.5rem !important;
+ margin-bottom: 0.5rem !important;
+}
+
+.m-3 {
+ margin: 1rem !important;
+}
+
+.mt-3 {
+ margin-top: 1rem !important;
+}
+
+.mr-3 {
+ margin-right: 1rem !important;
+}
+
+.mb-3 {
+ margin-bottom: 1rem !important;
+}
+
+.ml-3 {
+ margin-left: 1rem !important;
+}
+
+.mx-3 {
+ margin-right: 1rem !important;
+ margin-left: 1rem !important;
+}
+
+.my-3 {
+ margin-top: 1rem !important;
+ margin-bottom: 1rem !important;
+}
+
+.m-4 {
+ margin: 1.5rem !important;
+}
+
+.mt-4 {
+ margin-top: 1.5rem !important;
+}
+
+.mr-4 {
+ margin-right: 1.5rem !important;
+}
+
+.mb-4 {
+ margin-bottom: 1.5rem !important;
+}
+
+.ml-4 {
+ margin-left: 1.5rem !important;
+}
+
+.mx-4 {
+ margin-right: 1.5rem !important;
+ margin-left: 1.5rem !important;
+}
+
+.my-4 {
+ margin-top: 1.5rem !important;
+ margin-bottom: 1.5rem !important;
+}
+
+.m-5 {
+ margin: 3rem !important;
+}
+
+.mt-5 {
+ margin-top: 3rem !important;
+}
+
+.mr-5 {
+ margin-right: 3rem !important;
+}
+
+.mb-5 {
+ margin-bottom: 3rem !important;
+}
+
+.ml-5 {
+ margin-left: 3rem !important;
+}
+
+.mx-5 {
+ margin-right: 3rem !important;
+ margin-left: 3rem !important;
+}
+
+.my-5 {
+ margin-top: 3rem !important;
+ margin-bottom: 3rem !important;
+}
+
+.p-0 {
+ padding: 0 !important;
+}
+
+.pt-0 {
+ padding-top: 0 !important;
+}
+
+.pr-0 {
+ padding-right: 0 !important;
+}
+
+.pb-0 {
+ padding-bottom: 0 !important;
+}
+
+.pl-0 {
+ padding-left: 0 !important;
+}
+
+.px-0 {
+ padding-right: 0 !important;
+ padding-left: 0 !important;
+}
+
+.py-0 {
+ padding-top: 0 !important;
+ padding-bottom: 0 !important;
+}
+
+.p-1 {
+ padding: 0.25rem !important;
+}
+
+.pt-1 {
+ padding-top: 0.25rem !important;
+}
+
+.pr-1 {
+ padding-right: 0.25rem !important;
+}
+
+.pb-1 {
+ padding-bottom: 0.25rem !important;
+}
+
+.pl-1 {
+ padding-left: 0.25rem !important;
+}
+
+.px-1 {
+ padding-right: 0.25rem !important;
+ padding-left: 0.25rem !important;
+}
+
+.py-1 {
+ padding-top: 0.25rem !important;
+ padding-bottom: 0.25rem !important;
+}
+
+.p-2 {
+ padding: 0.5rem !important;
+}
+
+.pt-2 {
+ padding-top: 0.5rem !important;
+}
+
+.pr-2 {
+ padding-right: 0.5rem !important;
+}
+
+.pb-2 {
+ padding-bottom: 0.5rem !important;
+}
+
+.pl-2 {
+ padding-left: 0.5rem !important;
+}
+
+.px-2 {
+ padding-right: 0.5rem !important;
+ padding-left: 0.5rem !important;
+}
+
+.py-2 {
+ padding-top: 0.5rem !important;
+ padding-bottom: 0.5rem !important;
+}
+
+.p-3 {
+ padding: 1rem !important;
+}
+
+.pt-3 {
+ padding-top: 1rem !important;
+}
+
+.pr-3 {
+ padding-right: 1rem !important;
+}
+
+.pb-3 {
+ padding-bottom: 1rem !important;
+}
+
+.pl-3 {
+ padding-left: 1rem !important;
+}
+
+.px-3 {
+ padding-right: 1rem !important;
+ padding-left: 1rem !important;
+}
+
+.py-3 {
+ padding-top: 1rem !important;
+ padding-bottom: 1rem !important;
+}
+
+.p-4 {
+ padding: 1.5rem !important;
+}
+
+.pt-4 {
+ padding-top: 1.5rem !important;
+}
+
+.pr-4 {
+ padding-right: 1.5rem !important;
+}
+
+.pb-4 {
+ padding-bottom: 1.5rem !important;
+}
+
+.pl-4 {
+ padding-left: 1.5rem !important;
+}
+
+.px-4 {
+ padding-right: 1.5rem !important;
+ padding-left: 1.5rem !important;
+}
+
+.py-4 {
+ padding-top: 1.5rem !important;
+ padding-bottom: 1.5rem !important;
+}
+
+.p-5 {
+ padding: 3rem !important;
+}
+
+.pt-5 {
+ padding-top: 3rem !important;
+}
+
+.pr-5 {
+ padding-right: 3rem !important;
+}
+
+.pb-5 {
+ padding-bottom: 3rem !important;
+}
+
+.pl-5 {
+ padding-left: 3rem !important;
+}
+
+.px-5 {
+ padding-right: 3rem !important;
+ padding-left: 3rem !important;
+}
+
+.py-5 {
+ padding-top: 3rem !important;
+ padding-bottom: 3rem !important;
+}
+
+.m-auto {
+ margin: auto !important;
+}
+
+.mt-auto {
+ margin-top: auto !important;
+}
+
+.mr-auto {
+ margin-right: auto !important;
+}
+
+.mb-auto {
+ margin-bottom: auto !important;
+}
+
+.ml-auto {
+ margin-left: auto !important;
+}
+
+.mx-auto {
+ margin-right: auto !important;
+ margin-left: auto !important;
+}
+
+.my-auto {
+ margin-top: auto !important;
+ margin-bottom: auto !important;
+}
+
+@media (min-width: 576px) {
+ .m-sm-0 {
+ margin: 0 !important;
}
- tr.visible-print {
- display: table-row !important;
+ .mt-sm-0 {
+ margin-top: 0 !important;
}
- th.visible-print,
- td.visible-print {
- display: table-cell !important;
+ .mr-sm-0 {
+ margin-right: 0 !important;
+ }
+ .mb-sm-0 {
+ margin-bottom: 0 !important;
+ }
+ .ml-sm-0 {
+ margin-left: 0 !important;
+ }
+ .mx-sm-0 {
+ margin-right: 0 !important;
+ margin-left: 0 !important;
+ }
+ .my-sm-0 {
+ margin-top: 0 !important;
+ margin-bottom: 0 !important;
+ }
+ .m-sm-1 {
+ margin: 0.25rem !important;
+ }
+ .mt-sm-1 {
+ margin-top: 0.25rem !important;
+ }
+ .mr-sm-1 {
+ margin-right: 0.25rem !important;
+ }
+ .mb-sm-1 {
+ margin-bottom: 0.25rem !important;
+ }
+ .ml-sm-1 {
+ margin-left: 0.25rem !important;
+ }
+ .mx-sm-1 {
+ margin-right: 0.25rem !important;
+ margin-left: 0.25rem !important;
+ }
+ .my-sm-1 {
+ margin-top: 0.25rem !important;
+ margin-bottom: 0.25rem !important;
+ }
+ .m-sm-2 {
+ margin: 0.5rem !important;
+ }
+ .mt-sm-2 {
+ margin-top: 0.5rem !important;
+ }
+ .mr-sm-2 {
+ margin-right: 0.5rem !important;
+ }
+ .mb-sm-2 {
+ margin-bottom: 0.5rem !important;
+ }
+ .ml-sm-2 {
+ margin-left: 0.5rem !important;
+ }
+ .mx-sm-2 {
+ margin-right: 0.5rem !important;
+ margin-left: 0.5rem !important;
+ }
+ .my-sm-2 {
+ margin-top: 0.5rem !important;
+ margin-bottom: 0.5rem !important;
+ }
+ .m-sm-3 {
+ margin: 1rem !important;
+ }
+ .mt-sm-3 {
+ margin-top: 1rem !important;
+ }
+ .mr-sm-3 {
+ margin-right: 1rem !important;
+ }
+ .mb-sm-3 {
+ margin-bottom: 1rem !important;
+ }
+ .ml-sm-3 {
+ margin-left: 1rem !important;
+ }
+ .mx-sm-3 {
+ margin-right: 1rem !important;
+ margin-left: 1rem !important;
+ }
+ .my-sm-3 {
+ margin-top: 1rem !important;
+ margin-bottom: 1rem !important;
+ }
+ .m-sm-4 {
+ margin: 1.5rem !important;
+ }
+ .mt-sm-4 {
+ margin-top: 1.5rem !important;
+ }
+ .mr-sm-4 {
+ margin-right: 1.5rem !important;
+ }
+ .mb-sm-4 {
+ margin-bottom: 1.5rem !important;
+ }
+ .ml-sm-4 {
+ margin-left: 1.5rem !important;
+ }
+ .mx-sm-4 {
+ margin-right: 1.5rem !important;
+ margin-left: 1.5rem !important;
+ }
+ .my-sm-4 {
+ margin-top: 1.5rem !important;
+ margin-bottom: 1.5rem !important;
+ }
+ .m-sm-5 {
+ margin: 3rem !important;
+ }
+ .mt-sm-5 {
+ margin-top: 3rem !important;
+ }
+ .mr-sm-5 {
+ margin-right: 3rem !important;
+ }
+ .mb-sm-5 {
+ margin-bottom: 3rem !important;
+ }
+ .ml-sm-5 {
+ margin-left: 3rem !important;
+ }
+ .mx-sm-5 {
+ margin-right: 3rem !important;
+ margin-left: 3rem !important;
+ }
+ .my-sm-5 {
+ margin-top: 3rem !important;
+ margin-bottom: 3rem !important;
+ }
+ .p-sm-0 {
+ padding: 0 !important;
+ }
+ .pt-sm-0 {
+ padding-top: 0 !important;
+ }
+ .pr-sm-0 {
+ padding-right: 0 !important;
+ }
+ .pb-sm-0 {
+ padding-bottom: 0 !important;
+ }
+ .pl-sm-0 {
+ padding-left: 0 !important;
+ }
+ .px-sm-0 {
+ padding-right: 0 !important;
+ padding-left: 0 !important;
+ }
+ .py-sm-0 {
+ padding-top: 0 !important;
+ padding-bottom: 0 !important;
+ }
+ .p-sm-1 {
+ padding: 0.25rem !important;
+ }
+ .pt-sm-1 {
+ padding-top: 0.25rem !important;
+ }
+ .pr-sm-1 {
+ padding-right: 0.25rem !important;
+ }
+ .pb-sm-1 {
+ padding-bottom: 0.25rem !important;
+ }
+ .pl-sm-1 {
+ padding-left: 0.25rem !important;
+ }
+ .px-sm-1 {
+ padding-right: 0.25rem !important;
+ padding-left: 0.25rem !important;
+ }
+ .py-sm-1 {
+ padding-top: 0.25rem !important;
+ padding-bottom: 0.25rem !important;
+ }
+ .p-sm-2 {
+ padding: 0.5rem !important;
+ }
+ .pt-sm-2 {
+ padding-top: 0.5rem !important;
+ }
+ .pr-sm-2 {
+ padding-right: 0.5rem !important;
+ }
+ .pb-sm-2 {
+ padding-bottom: 0.5rem !important;
+ }
+ .pl-sm-2 {
+ padding-left: 0.5rem !important;
+ }
+ .px-sm-2 {
+ padding-right: 0.5rem !important;
+ padding-left: 0.5rem !important;
+ }
+ .py-sm-2 {
+ padding-top: 0.5rem !important;
+ padding-bottom: 0.5rem !important;
+ }
+ .p-sm-3 {
+ padding: 1rem !important;
+ }
+ .pt-sm-3 {
+ padding-top: 1rem !important;
+ }
+ .pr-sm-3 {
+ padding-right: 1rem !important;
+ }
+ .pb-sm-3 {
+ padding-bottom: 1rem !important;
+ }
+ .pl-sm-3 {
+ padding-left: 1rem !important;
+ }
+ .px-sm-3 {
+ padding-right: 1rem !important;
+ padding-left: 1rem !important;
+ }
+ .py-sm-3 {
+ padding-top: 1rem !important;
+ padding-bottom: 1rem !important;
+ }
+ .p-sm-4 {
+ padding: 1.5rem !important;
+ }
+ .pt-sm-4 {
+ padding-top: 1.5rem !important;
+ }
+ .pr-sm-4 {
+ padding-right: 1.5rem !important;
+ }
+ .pb-sm-4 {
+ padding-bottom: 1.5rem !important;
+ }
+ .pl-sm-4 {
+ padding-left: 1.5rem !important;
+ }
+ .px-sm-4 {
+ padding-right: 1.5rem !important;
+ padding-left: 1.5rem !important;
+ }
+ .py-sm-4 {
+ padding-top: 1.5rem !important;
+ padding-bottom: 1.5rem !important;
+ }
+ .p-sm-5 {
+ padding: 3rem !important;
+ }
+ .pt-sm-5 {
+ padding-top: 3rem !important;
+ }
+ .pr-sm-5 {
+ padding-right: 3rem !important;
+ }
+ .pb-sm-5 {
+ padding-bottom: 3rem !important;
+ }
+ .pl-sm-5 {
+ padding-left: 3rem !important;
+ }
+ .px-sm-5 {
+ padding-right: 3rem !important;
+ padding-left: 3rem !important;
+ }
+ .py-sm-5 {
+ padding-top: 3rem !important;
+ padding-bottom: 3rem !important;
+ }
+ .m-sm-auto {
+ margin: auto !important;
+ }
+ .mt-sm-auto {
+ margin-top: auto !important;
+ }
+ .mr-sm-auto {
+ margin-right: auto !important;
+ }
+ .mb-sm-auto {
+ margin-bottom: auto !important;
+ }
+ .ml-sm-auto {
+ margin-left: auto !important;
+ }
+ .mx-sm-auto {
+ margin-right: auto !important;
+ margin-left: auto !important;
+ }
+ .my-sm-auto {
+ margin-top: auto !important;
+ margin-bottom: auto !important;
}
}
-.visible-print-block {
- display: none !important;
+
+@media (min-width: 768px) {
+ .m-md-0 {
+ margin: 0 !important;
+ }
+ .mt-md-0 {
+ margin-top: 0 !important;
+ }
+ .mr-md-0 {
+ margin-right: 0 !important;
+ }
+ .mb-md-0 {
+ margin-bottom: 0 !important;
+ }
+ .ml-md-0 {
+ margin-left: 0 !important;
+ }
+ .mx-md-0 {
+ margin-right: 0 !important;
+ margin-left: 0 !important;
+ }
+ .my-md-0 {
+ margin-top: 0 !important;
+ margin-bottom: 0 !important;
+ }
+ .m-md-1 {
+ margin: 0.25rem !important;
+ }
+ .mt-md-1 {
+ margin-top: 0.25rem !important;
+ }
+ .mr-md-1 {
+ margin-right: 0.25rem !important;
+ }
+ .mb-md-1 {
+ margin-bottom: 0.25rem !important;
+ }
+ .ml-md-1 {
+ margin-left: 0.25rem !important;
+ }
+ .mx-md-1 {
+ margin-right: 0.25rem !important;
+ margin-left: 0.25rem !important;
+ }
+ .my-md-1 {
+ margin-top: 0.25rem !important;
+ margin-bottom: 0.25rem !important;
+ }
+ .m-md-2 {
+ margin: 0.5rem !important;
+ }
+ .mt-md-2 {
+ margin-top: 0.5rem !important;
+ }
+ .mr-md-2 {
+ margin-right: 0.5rem !important;
+ }
+ .mb-md-2 {
+ margin-bottom: 0.5rem !important;
+ }
+ .ml-md-2 {
+ margin-left: 0.5rem !important;
+ }
+ .mx-md-2 {
+ margin-right: 0.5rem !important;
+ margin-left: 0.5rem !important;
+ }
+ .my-md-2 {
+ margin-top: 0.5rem !important;
+ margin-bottom: 0.5rem !important;
+ }
+ .m-md-3 {
+ margin: 1rem !important;
+ }
+ .mt-md-3 {
+ margin-top: 1rem !important;
+ }
+ .mr-md-3 {
+ margin-right: 1rem !important;
+ }
+ .mb-md-3 {
+ margin-bottom: 1rem !important;
+ }
+ .ml-md-3 {
+ margin-left: 1rem !important;
+ }
+ .mx-md-3 {
+ margin-right: 1rem !important;
+ margin-left: 1rem !important;
+ }
+ .my-md-3 {
+ margin-top: 1rem !important;
+ margin-bottom: 1rem !important;
+ }
+ .m-md-4 {
+ margin: 1.5rem !important;
+ }
+ .mt-md-4 {
+ margin-top: 1.5rem !important;
+ }
+ .mr-md-4 {
+ margin-right: 1.5rem !important;
+ }
+ .mb-md-4 {
+ margin-bottom: 1.5rem !important;
+ }
+ .ml-md-4 {
+ margin-left: 1.5rem !important;
+ }
+ .mx-md-4 {
+ margin-right: 1.5rem !important;
+ margin-left: 1.5rem !important;
+ }
+ .my-md-4 {
+ margin-top: 1.5rem !important;
+ margin-bottom: 1.5rem !important;
+ }
+ .m-md-5 {
+ margin: 3rem !important;
+ }
+ .mt-md-5 {
+ margin-top: 3rem !important;
+ }
+ .mr-md-5 {
+ margin-right: 3rem !important;
+ }
+ .mb-md-5 {
+ margin-bottom: 3rem !important;
+ }
+ .ml-md-5 {
+ margin-left: 3rem !important;
+ }
+ .mx-md-5 {
+ margin-right: 3rem !important;
+ margin-left: 3rem !important;
+ }
+ .my-md-5 {
+ margin-top: 3rem !important;
+ margin-bottom: 3rem !important;
+ }
+ .p-md-0 {
+ padding: 0 !important;
+ }
+ .pt-md-0 {
+ padding-top: 0 !important;
+ }
+ .pr-md-0 {
+ padding-right: 0 !important;
+ }
+ .pb-md-0 {
+ padding-bottom: 0 !important;
+ }
+ .pl-md-0 {
+ padding-left: 0 !important;
+ }
+ .px-md-0 {
+ padding-right: 0 !important;
+ padding-left: 0 !important;
+ }
+ .py-md-0 {
+ padding-top: 0 !important;
+ padding-bottom: 0 !important;
+ }
+ .p-md-1 {
+ padding: 0.25rem !important;
+ }
+ .pt-md-1 {
+ padding-top: 0.25rem !important;
+ }
+ .pr-md-1 {
+ padding-right: 0.25rem !important;
+ }
+ .pb-md-1 {
+ padding-bottom: 0.25rem !important;
+ }
+ .pl-md-1 {
+ padding-left: 0.25rem !important;
+ }
+ .px-md-1 {
+ padding-right: 0.25rem !important;
+ padding-left: 0.25rem !important;
+ }
+ .py-md-1 {
+ padding-top: 0.25rem !important;
+ padding-bottom: 0.25rem !important;
+ }
+ .p-md-2 {
+ padding: 0.5rem !important;
+ }
+ .pt-md-2 {
+ padding-top: 0.5rem !important;
+ }
+ .pr-md-2 {
+ padding-right: 0.5rem !important;
+ }
+ .pb-md-2 {
+ padding-bottom: 0.5rem !important;
+ }
+ .pl-md-2 {
+ padding-left: 0.5rem !important;
+ }
+ .px-md-2 {
+ padding-right: 0.5rem !important;
+ padding-left: 0.5rem !important;
+ }
+ .py-md-2 {
+ padding-top: 0.5rem !important;
+ padding-bottom: 0.5rem !important;
+ }
+ .p-md-3 {
+ padding: 1rem !important;
+ }
+ .pt-md-3 {
+ padding-top: 1rem !important;
+ }
+ .pr-md-3 {
+ padding-right: 1rem !important;
+ }
+ .pb-md-3 {
+ padding-bottom: 1rem !important;
+ }
+ .pl-md-3 {
+ padding-left: 1rem !important;
+ }
+ .px-md-3 {
+ padding-right: 1rem !important;
+ padding-left: 1rem !important;
+ }
+ .py-md-3 {
+ padding-top: 1rem !important;
+ padding-bottom: 1rem !important;
+ }
+ .p-md-4 {
+ padding: 1.5rem !important;
+ }
+ .pt-md-4 {
+ padding-top: 1.5rem !important;
+ }
+ .pr-md-4 {
+ padding-right: 1.5rem !important;
+ }
+ .pb-md-4 {
+ padding-bottom: 1.5rem !important;
+ }
+ .pl-md-4 {
+ padding-left: 1.5rem !important;
+ }
+ .px-md-4 {
+ padding-right: 1.5rem !important;
+ padding-left: 1.5rem !important;
+ }
+ .py-md-4 {
+ padding-top: 1.5rem !important;
+ padding-bottom: 1.5rem !important;
+ }
+ .p-md-5 {
+ padding: 3rem !important;
+ }
+ .pt-md-5 {
+ padding-top: 3rem !important;
+ }
+ .pr-md-5 {
+ padding-right: 3rem !important;
+ }
+ .pb-md-5 {
+ padding-bottom: 3rem !important;
+ }
+ .pl-md-5 {
+ padding-left: 3rem !important;
+ }
+ .px-md-5 {
+ padding-right: 3rem !important;
+ padding-left: 3rem !important;
+ }
+ .py-md-5 {
+ padding-top: 3rem !important;
+ padding-bottom: 3rem !important;
+ }
+ .m-md-auto {
+ margin: auto !important;
+ }
+ .mt-md-auto {
+ margin-top: auto !important;
+ }
+ .mr-md-auto {
+ margin-right: auto !important;
+ }
+ .mb-md-auto {
+ margin-bottom: auto !important;
+ }
+ .ml-md-auto {
+ margin-left: auto !important;
+ }
+ .mx-md-auto {
+ margin-right: auto !important;
+ margin-left: auto !important;
+ }
+ .my-md-auto {
+ margin-top: auto !important;
+ margin-bottom: auto !important;
+ }
}
-@media print {
- .visible-print-block {
- display: block !important;
+
+@media (min-width: 992px) {
+ .m-lg-0 {
+ margin: 0 !important;
+ }
+ .mt-lg-0 {
+ margin-top: 0 !important;
+ }
+ .mr-lg-0 {
+ margin-right: 0 !important;
+ }
+ .mb-lg-0 {
+ margin-bottom: 0 !important;
+ }
+ .ml-lg-0 {
+ margin-left: 0 !important;
+ }
+ .mx-lg-0 {
+ margin-right: 0 !important;
+ margin-left: 0 !important;
+ }
+ .my-lg-0 {
+ margin-top: 0 !important;
+ margin-bottom: 0 !important;
+ }
+ .m-lg-1 {
+ margin: 0.25rem !important;
+ }
+ .mt-lg-1 {
+ margin-top: 0.25rem !important;
+ }
+ .mr-lg-1 {
+ margin-right: 0.25rem !important;
+ }
+ .mb-lg-1 {
+ margin-bottom: 0.25rem !important;
+ }
+ .ml-lg-1 {
+ margin-left: 0.25rem !important;
+ }
+ .mx-lg-1 {
+ margin-right: 0.25rem !important;
+ margin-left: 0.25rem !important;
+ }
+ .my-lg-1 {
+ margin-top: 0.25rem !important;
+ margin-bottom: 0.25rem !important;
+ }
+ .m-lg-2 {
+ margin: 0.5rem !important;
+ }
+ .mt-lg-2 {
+ margin-top: 0.5rem !important;
+ }
+ .mr-lg-2 {
+ margin-right: 0.5rem !important;
+ }
+ .mb-lg-2 {
+ margin-bottom: 0.5rem !important;
+ }
+ .ml-lg-2 {
+ margin-left: 0.5rem !important;
+ }
+ .mx-lg-2 {
+ margin-right: 0.5rem !important;
+ margin-left: 0.5rem !important;
+ }
+ .my-lg-2 {
+ margin-top: 0.5rem !important;
+ margin-bottom: 0.5rem !important;
+ }
+ .m-lg-3 {
+ margin: 1rem !important;
+ }
+ .mt-lg-3 {
+ margin-top: 1rem !important;
+ }
+ .mr-lg-3 {
+ margin-right: 1rem !important;
+ }
+ .mb-lg-3 {
+ margin-bottom: 1rem !important;
+ }
+ .ml-lg-3 {
+ margin-left: 1rem !important;
+ }
+ .mx-lg-3 {
+ margin-right: 1rem !important;
+ margin-left: 1rem !important;
+ }
+ .my-lg-3 {
+ margin-top: 1rem !important;
+ margin-bottom: 1rem !important;
+ }
+ .m-lg-4 {
+ margin: 1.5rem !important;
+ }
+ .mt-lg-4 {
+ margin-top: 1.5rem !important;
+ }
+ .mr-lg-4 {
+ margin-right: 1.5rem !important;
+ }
+ .mb-lg-4 {
+ margin-bottom: 1.5rem !important;
+ }
+ .ml-lg-4 {
+ margin-left: 1.5rem !important;
+ }
+ .mx-lg-4 {
+ margin-right: 1.5rem !important;
+ margin-left: 1.5rem !important;
+ }
+ .my-lg-4 {
+ margin-top: 1.5rem !important;
+ margin-bottom: 1.5rem !important;
+ }
+ .m-lg-5 {
+ margin: 3rem !important;
+ }
+ .mt-lg-5 {
+ margin-top: 3rem !important;
+ }
+ .mr-lg-5 {
+ margin-right: 3rem !important;
+ }
+ .mb-lg-5 {
+ margin-bottom: 3rem !important;
+ }
+ .ml-lg-5 {
+ margin-left: 3rem !important;
+ }
+ .mx-lg-5 {
+ margin-right: 3rem !important;
+ margin-left: 3rem !important;
+ }
+ .my-lg-5 {
+ margin-top: 3rem !important;
+ margin-bottom: 3rem !important;
+ }
+ .p-lg-0 {
+ padding: 0 !important;
+ }
+ .pt-lg-0 {
+ padding-top: 0 !important;
+ }
+ .pr-lg-0 {
+ padding-right: 0 !important;
+ }
+ .pb-lg-0 {
+ padding-bottom: 0 !important;
+ }
+ .pl-lg-0 {
+ padding-left: 0 !important;
+ }
+ .px-lg-0 {
+ padding-right: 0 !important;
+ padding-left: 0 !important;
+ }
+ .py-lg-0 {
+ padding-top: 0 !important;
+ padding-bottom: 0 !important;
+ }
+ .p-lg-1 {
+ padding: 0.25rem !important;
+ }
+ .pt-lg-1 {
+ padding-top: 0.25rem !important;
+ }
+ .pr-lg-1 {
+ padding-right: 0.25rem !important;
+ }
+ .pb-lg-1 {
+ padding-bottom: 0.25rem !important;
+ }
+ .pl-lg-1 {
+ padding-left: 0.25rem !important;
+ }
+ .px-lg-1 {
+ padding-right: 0.25rem !important;
+ padding-left: 0.25rem !important;
+ }
+ .py-lg-1 {
+ padding-top: 0.25rem !important;
+ padding-bottom: 0.25rem !important;
+ }
+ .p-lg-2 {
+ padding: 0.5rem !important;
+ }
+ .pt-lg-2 {
+ padding-top: 0.5rem !important;
+ }
+ .pr-lg-2 {
+ padding-right: 0.5rem !important;
+ }
+ .pb-lg-2 {
+ padding-bottom: 0.5rem !important;
+ }
+ .pl-lg-2 {
+ padding-left: 0.5rem !important;
+ }
+ .px-lg-2 {
+ padding-right: 0.5rem !important;
+ padding-left: 0.5rem !important;
+ }
+ .py-lg-2 {
+ padding-top: 0.5rem !important;
+ padding-bottom: 0.5rem !important;
+ }
+ .p-lg-3 {
+ padding: 1rem !important;
+ }
+ .pt-lg-3 {
+ padding-top: 1rem !important;
+ }
+ .pr-lg-3 {
+ padding-right: 1rem !important;
+ }
+ .pb-lg-3 {
+ padding-bottom: 1rem !important;
+ }
+ .pl-lg-3 {
+ padding-left: 1rem !important;
+ }
+ .px-lg-3 {
+ padding-right: 1rem !important;
+ padding-left: 1rem !important;
+ }
+ .py-lg-3 {
+ padding-top: 1rem !important;
+ padding-bottom: 1rem !important;
+ }
+ .p-lg-4 {
+ padding: 1.5rem !important;
+ }
+ .pt-lg-4 {
+ padding-top: 1.5rem !important;
+ }
+ .pr-lg-4 {
+ padding-right: 1.5rem !important;
+ }
+ .pb-lg-4 {
+ padding-bottom: 1.5rem !important;
+ }
+ .pl-lg-4 {
+ padding-left: 1.5rem !important;
+ }
+ .px-lg-4 {
+ padding-right: 1.5rem !important;
+ padding-left: 1.5rem !important;
+ }
+ .py-lg-4 {
+ padding-top: 1.5rem !important;
+ padding-bottom: 1.5rem !important;
+ }
+ .p-lg-5 {
+ padding: 3rem !important;
+ }
+ .pt-lg-5 {
+ padding-top: 3rem !important;
+ }
+ .pr-lg-5 {
+ padding-right: 3rem !important;
+ }
+ .pb-lg-5 {
+ padding-bottom: 3rem !important;
+ }
+ .pl-lg-5 {
+ padding-left: 3rem !important;
+ }
+ .px-lg-5 {
+ padding-right: 3rem !important;
+ padding-left: 3rem !important;
+ }
+ .py-lg-5 {
+ padding-top: 3rem !important;
+ padding-bottom: 3rem !important;
+ }
+ .m-lg-auto {
+ margin: auto !important;
+ }
+ .mt-lg-auto {
+ margin-top: auto !important;
+ }
+ .mr-lg-auto {
+ margin-right: auto !important;
+ }
+ .mb-lg-auto {
+ margin-bottom: auto !important;
+ }
+ .ml-lg-auto {
+ margin-left: auto !important;
+ }
+ .mx-lg-auto {
+ margin-right: auto !important;
+ margin-left: auto !important;
+ }
+ .my-lg-auto {
+ margin-top: auto !important;
+ margin-bottom: auto !important;
}
}
-.visible-print-inline {
- display: none !important;
+
+@media (min-width: 1200px) {
+ .m-xl-0 {
+ margin: 0 !important;
+ }
+ .mt-xl-0 {
+ margin-top: 0 !important;
+ }
+ .mr-xl-0 {
+ margin-right: 0 !important;
+ }
+ .mb-xl-0 {
+ margin-bottom: 0 !important;
+ }
+ .ml-xl-0 {
+ margin-left: 0 !important;
+ }
+ .mx-xl-0 {
+ margin-right: 0 !important;
+ margin-left: 0 !important;
+ }
+ .my-xl-0 {
+ margin-top: 0 !important;
+ margin-bottom: 0 !important;
+ }
+ .m-xl-1 {
+ margin: 0.25rem !important;
+ }
+ .mt-xl-1 {
+ margin-top: 0.25rem !important;
+ }
+ .mr-xl-1 {
+ margin-right: 0.25rem !important;
+ }
+ .mb-xl-1 {
+ margin-bottom: 0.25rem !important;
+ }
+ .ml-xl-1 {
+ margin-left: 0.25rem !important;
+ }
+ .mx-xl-1 {
+ margin-right: 0.25rem !important;
+ margin-left: 0.25rem !important;
+ }
+ .my-xl-1 {
+ margin-top: 0.25rem !important;
+ margin-bottom: 0.25rem !important;
+ }
+ .m-xl-2 {
+ margin: 0.5rem !important;
+ }
+ .mt-xl-2 {
+ margin-top: 0.5rem !important;
+ }
+ .mr-xl-2 {
+ margin-right: 0.5rem !important;
+ }
+ .mb-xl-2 {
+ margin-bottom: 0.5rem !important;
+ }
+ .ml-xl-2 {
+ margin-left: 0.5rem !important;
+ }
+ .mx-xl-2 {
+ margin-right: 0.5rem !important;
+ margin-left: 0.5rem !important;
+ }
+ .my-xl-2 {
+ margin-top: 0.5rem !important;
+ margin-bottom: 0.5rem !important;
+ }
+ .m-xl-3 {
+ margin: 1rem !important;
+ }
+ .mt-xl-3 {
+ margin-top: 1rem !important;
+ }
+ .mr-xl-3 {
+ margin-right: 1rem !important;
+ }
+ .mb-xl-3 {
+ margin-bottom: 1rem !important;
+ }
+ .ml-xl-3 {
+ margin-left: 1rem !important;
+ }
+ .mx-xl-3 {
+ margin-right: 1rem !important;
+ margin-left: 1rem !important;
+ }
+ .my-xl-3 {
+ margin-top: 1rem !important;
+ margin-bottom: 1rem !important;
+ }
+ .m-xl-4 {
+ margin: 1.5rem !important;
+ }
+ .mt-xl-4 {
+ margin-top: 1.5rem !important;
+ }
+ .mr-xl-4 {
+ margin-right: 1.5rem !important;
+ }
+ .mb-xl-4 {
+ margin-bottom: 1.5rem !important;
+ }
+ .ml-xl-4 {
+ margin-left: 1.5rem !important;
+ }
+ .mx-xl-4 {
+ margin-right: 1.5rem !important;
+ margin-left: 1.5rem !important;
+ }
+ .my-xl-4 {
+ margin-top: 1.5rem !important;
+ margin-bottom: 1.5rem !important;
+ }
+ .m-xl-5 {
+ margin: 3rem !important;
+ }
+ .mt-xl-5 {
+ margin-top: 3rem !important;
+ }
+ .mr-xl-5 {
+ margin-right: 3rem !important;
+ }
+ .mb-xl-5 {
+ margin-bottom: 3rem !important;
+ }
+ .ml-xl-5 {
+ margin-left: 3rem !important;
+ }
+ .mx-xl-5 {
+ margin-right: 3rem !important;
+ margin-left: 3rem !important;
+ }
+ .my-xl-5 {
+ margin-top: 3rem !important;
+ margin-bottom: 3rem !important;
+ }
+ .p-xl-0 {
+ padding: 0 !important;
+ }
+ .pt-xl-0 {
+ padding-top: 0 !important;
+ }
+ .pr-xl-0 {
+ padding-right: 0 !important;
+ }
+ .pb-xl-0 {
+ padding-bottom: 0 !important;
+ }
+ .pl-xl-0 {
+ padding-left: 0 !important;
+ }
+ .px-xl-0 {
+ padding-right: 0 !important;
+ padding-left: 0 !important;
+ }
+ .py-xl-0 {
+ padding-top: 0 !important;
+ padding-bottom: 0 !important;
+ }
+ .p-xl-1 {
+ padding: 0.25rem !important;
+ }
+ .pt-xl-1 {
+ padding-top: 0.25rem !important;
+ }
+ .pr-xl-1 {
+ padding-right: 0.25rem !important;
+ }
+ .pb-xl-1 {
+ padding-bottom: 0.25rem !important;
+ }
+ .pl-xl-1 {
+ padding-left: 0.25rem !important;
+ }
+ .px-xl-1 {
+ padding-right: 0.25rem !important;
+ padding-left: 0.25rem !important;
+ }
+ .py-xl-1 {
+ padding-top: 0.25rem !important;
+ padding-bottom: 0.25rem !important;
+ }
+ .p-xl-2 {
+ padding: 0.5rem !important;
+ }
+ .pt-xl-2 {
+ padding-top: 0.5rem !important;
+ }
+ .pr-xl-2 {
+ padding-right: 0.5rem !important;
+ }
+ .pb-xl-2 {
+ padding-bottom: 0.5rem !important;
+ }
+ .pl-xl-2 {
+ padding-left: 0.5rem !important;
+ }
+ .px-xl-2 {
+ padding-right: 0.5rem !important;
+ padding-left: 0.5rem !important;
+ }
+ .py-xl-2 {
+ padding-top: 0.5rem !important;
+ padding-bottom: 0.5rem !important;
+ }
+ .p-xl-3 {
+ padding: 1rem !important;
+ }
+ .pt-xl-3 {
+ padding-top: 1rem !important;
+ }
+ .pr-xl-3 {
+ padding-right: 1rem !important;
+ }
+ .pb-xl-3 {
+ padding-bottom: 1rem !important;
+ }
+ .pl-xl-3 {
+ padding-left: 1rem !important;
+ }
+ .px-xl-3 {
+ padding-right: 1rem !important;
+ padding-left: 1rem !important;
+ }
+ .py-xl-3 {
+ padding-top: 1rem !important;
+ padding-bottom: 1rem !important;
+ }
+ .p-xl-4 {
+ padding: 1.5rem !important;
+ }
+ .pt-xl-4 {
+ padding-top: 1.5rem !important;
+ }
+ .pr-xl-4 {
+ padding-right: 1.5rem !important;
+ }
+ .pb-xl-4 {
+ padding-bottom: 1.5rem !important;
+ }
+ .pl-xl-4 {
+ padding-left: 1.5rem !important;
+ }
+ .px-xl-4 {
+ padding-right: 1.5rem !important;
+ padding-left: 1.5rem !important;
+ }
+ .py-xl-4 {
+ padding-top: 1.5rem !important;
+ padding-bottom: 1.5rem !important;
+ }
+ .p-xl-5 {
+ padding: 3rem !important;
+ }
+ .pt-xl-5 {
+ padding-top: 3rem !important;
+ }
+ .pr-xl-5 {
+ padding-right: 3rem !important;
+ }
+ .pb-xl-5 {
+ padding-bottom: 3rem !important;
+ }
+ .pl-xl-5 {
+ padding-left: 3rem !important;
+ }
+ .px-xl-5 {
+ padding-right: 3rem !important;
+ padding-left: 3rem !important;
+ }
+ .py-xl-5 {
+ padding-top: 3rem !important;
+ padding-bottom: 3rem !important;
+ }
+ .m-xl-auto {
+ margin: auto !important;
+ }
+ .mt-xl-auto {
+ margin-top: auto !important;
+ }
+ .mr-xl-auto {
+ margin-right: auto !important;
+ }
+ .mb-xl-auto {
+ margin-bottom: auto !important;
+ }
+ .ml-xl-auto {
+ margin-left: auto !important;
+ }
+ .mx-xl-auto {
+ margin-right: auto !important;
+ margin-left: auto !important;
+ }
+ .my-xl-auto {
+ margin-top: auto !important;
+ margin-bottom: auto !important;
+ }
}
-@media print {
- .visible-print-inline {
- display: inline !important;
+
+.text-justify {
+ text-align: justify !important;
+}
+
+.text-nowrap {
+ white-space: nowrap !important;
+}
+
+.text-truncate {
+ overflow: hidden;
+ text-overflow: ellipsis;
+ white-space: nowrap;
+}
+
+.text-left {
+ text-align: left !important;
+}
+
+.text-right {
+ text-align: right !important;
+}
+
+.text-center {
+ text-align: center !important;
+}
+
+@media (min-width: 576px) {
+ .text-sm-left {
+ text-align: left !important;
+ }
+ .text-sm-right {
+ text-align: right !important;
+ }
+ .text-sm-center {
+ text-align: center !important;
}
}
-.visible-print-inline-block {
- display: none !important;
+
+@media (min-width: 768px) {
+ .text-md-left {
+ text-align: left !important;
+ }
+ .text-md-right {
+ text-align: right !important;
+ }
+ .text-md-center {
+ text-align: center !important;
+ }
}
-@media print {
- .visible-print-inline-block {
- display: inline-block !important;
+
+@media (min-width: 992px) {
+ .text-lg-left {
+ text-align: left !important;
+ }
+ .text-lg-right {
+ text-align: right !important;
+ }
+ .text-lg-center {
+ text-align: center !important;
}
}
-@media print {
- .hidden-print {
- display: none !important;
+
+@media (min-width: 1200px) {
+ .text-xl-left {
+ text-align: left !important;
+ }
+ .text-xl-right {
+ text-align: right !important;
+ }
+ .text-xl-center {
+ text-align: center !important;
}
}
-/*# sourceMappingURL=bootstrap.css.map */
+
+.text-lowercase {
+ text-transform: lowercase !important;
+}
+
+.text-uppercase {
+ text-transform: uppercase !important;
+}
+
+.text-capitalize {
+ text-transform: capitalize !important;
+}
+
+.font-weight-normal {
+ font-weight: normal;
+}
+
+.font-weight-bold {
+ font-weight: bold;
+}
+
+.font-italic {
+ font-style: italic;
+}
+
+.text-white {
+ color: #fff !important;
+}
+
+.text-primary {
+ color: #007bff !important;
+}
+
+a.text-primary:focus, a.text-primary:hover {
+ color: #0062cc !important;
+}
+
+.text-secondary {
+ color: #868e96 !important;
+}
+
+a.text-secondary:focus, a.text-secondary:hover {
+ color: #6c757d !important;
+}
+
+.text-success {
+ color: #28a745 !important;
+}
+
+a.text-success:focus, a.text-success:hover {
+ color: #1e7e34 !important;
+}
+
+.text-info {
+ color: #17a2b8 !important;
+}
+
+a.text-info:focus, a.text-info:hover {
+ color: #117a8b !important;
+}
+
+.text-warning {
+ color: #ffc107 !important;
+}
+
+a.text-warning:focus, a.text-warning:hover {
+ color: #d39e00 !important;
+}
+
+.text-danger {
+ color: #dc3545 !important;
+}
+
+a.text-danger:focus, a.text-danger:hover {
+ color: #bd2130 !important;
+}
+
+.text-light {
+ color: #f8f9fa !important;
+}
+
+a.text-light:focus, a.text-light:hover {
+ color: #dae0e5 !important;
+}
+
+.text-dark {
+ color: #343a40 !important;
+}
+
+a.text-dark:focus, a.text-dark:hover {
+ color: #1d2124 !important;
+}
+
+.text-muted {
+ color: #868e96 !important;
+}
+
+.text-hide {
+ font: 0/0 a;
+ color: transparent;
+ text-shadow: none;
+ background-color: transparent;
+ border: 0;
+}
+
+.visible {
+ visibility: visible !important;
+}
+
+.invisible {
+ visibility: hidden !important;
+}
+/*# sourceMappingURL=bootstrap.css.map */ \ No newline at end of file
diff --git a/library/bootstrap/css/bootstrap.css.map b/library/bootstrap/css/bootstrap.css.map
index f010c82d1..14530357a 100644
--- a/library/bootstrap/css/bootstrap.css.map
+++ b/library/bootstrap/css/bootstrap.css.map
@@ -1 +1 @@
-{"version":3,"sources":["bootstrap.css","less/normalize.less","less/print.less","less/glyphicons.less","less/scaffolding.less","less/mixins/vendor-prefixes.less","less/mixins/tab-focus.less","less/mixins/image.less","less/type.less","less/mixins/text-emphasis.less","less/mixins/background-variant.less","less/mixins/text-overflow.less","less/code.less","less/grid.less","less/mixins/grid.less","less/mixins/grid-framework.less","less/tables.less","less/mixins/table-row.less","less/forms.less","less/mixins/forms.less","less/buttons.less","less/mixins/buttons.less","less/mixins/opacity.less","less/component-animations.less","less/dropdowns.less","less/mixins/nav-divider.less","less/mixins/reset-filter.less","less/button-groups.less","less/mixins/border-radius.less","less/input-groups.less","less/navs.less","less/navbar.less","less/mixins/nav-vertical-align.less","less/utilities.less","less/breadcrumbs.less","less/pagination.less","less/mixins/pagination.less","less/pager.less","less/labels.less","less/mixins/labels.less","less/badges.less","less/jumbotron.less","less/thumbnails.less","less/alerts.less","less/mixins/alerts.less","less/progress-bars.less","less/mixins/gradients.less","less/mixins/progress-bar.less","less/media.less","less/list-group.less","less/mixins/list-group.less","less/panels.less","less/mixins/panels.less","less/responsive-embed.less","less/wells.less","less/close.less","less/modals.less","less/tooltip.less","less/mixins/reset-text.less","less/popovers.less","less/carousel.less","less/mixins/clearfix.less","less/mixins/center-block.less","less/mixins/hide-text.less","less/responsive-utilities.less","less/mixins/responsive-visibility.less"],"names":[],"mappings":"AAAA;;;;GAIG;AACH,4EAA4E;ACG5E;EACE,wBAAA;EACA,2BAAA;EACA,+BAAA;CDDD;ACQD;EACE,UAAA;CDND;ACmBD;;;;;;;;;;;;;EAaE,eAAA;CDjBD;ACyBD;;;;EAIE,sBAAA;EACA,yBAAA;CDvBD;AC+BD;EACE,cAAA;EACA,UAAA;CD7BD;ACqCD;;EAEE,cAAA;CDnCD;AC6CD;EACE,8BAAA;CD3CD;ACmDD;;EAEE,WAAA;CDjDD;AC2DD;EACE,0BAAA;CDzDD;ACgED;;EAEE,kBAAA;CD9DD;ACqED;EACE,mBAAA;CDnED;AC2ED;EACE,eAAA;EACA,iBAAA;CDzED;ACgFD;EACE,iBAAA;EACA,YAAA;CD9ED;ACqFD;EACE,eAAA;CDnFD;AC0FD;;EAEE,eAAA;EACA,eAAA;EACA,mBAAA;EACA,yBAAA;CDxFD;AC2FD;EACE,YAAA;CDzFD;AC4FD;EACE,gBAAA;CD1FD;ACoGD;EACE,UAAA;CDlGD;ACyGD;EACE,iBAAA;CDvGD;ACiHD;EACE,iBAAA;CD/GD;ACsHD;EACE,gCAAA;KAAA,6BAAA;UAAA,wBAAA;EACA,UAAA;CDpHD;AC2HD;EACE,eAAA;CDzHD;ACgID;;;;EAIE,kCAAA;EACA,eAAA;CD9HD;ACgJD;;;;;EAKE,eAAA;EACA,cAAA;EACA,UAAA;CD9ID;ACqJD;EACE,kBAAA;CDnJD;AC6JD;;EAEE,qBAAA;CD3JD;ACsKD;;;;EAIE,2BAAA;EACA,gBAAA;CDpKD;AC2KD;;EAEE,gBAAA;CDzKD;ACgLD;;EAEE,UAAA;EACA,WAAA;CD9KD;ACsLD;EACE,oBAAA;CDpLD;AC+LD;;EAEE,+BAAA;KAAA,4BAAA;UAAA,uBAAA;EACA,WAAA;CD7LD;ACsMD;;EAEE,aAAA;CDpMD;AC4MD;EACE,8BAAA;EACA,gCAAA;KAAA,6BAAA;UAAA,wBAAA;CD1MD;ACmND;;EAEE,yBAAA;CDjND;ACwND;EACE,0BAAA;EACA,cAAA;EACA,+BAAA;CDtND;AC8ND;EACE,UAAA;EACA,WAAA;CD5ND;ACmOD;EACE,eAAA;CDjOD;ACyOD;EACE,kBAAA;CDvOD;ACiPD;EACE,0BAAA;EACA,kBAAA;CD/OD;ACkPD;;EAEE,WAAA;CDhPD;AACD,qFAAqF;AElFrF;EA7FI;;;IAGI,mCAAA;IACA,uBAAA;IACA,oCAAA;YAAA,4BAAA;IACA,6BAAA;GFkLL;EE/KC;;IAEI,2BAAA;GFiLL;EE9KC;IACI,6BAAA;GFgLL;EE7KC;IACI,8BAAA;GF+KL;EE1KC;;IAEI,YAAA;GF4KL;EEzKC;;IAEI,uBAAA;IACA,yBAAA;GF2KL;EExKC;IACI,4BAAA;GF0KL;EEvKC;;IAEI,yBAAA;GFyKL;EEtKC;IACI,2BAAA;GFwKL;EErKC;;;IAGI,WAAA;IACA,UAAA;GFuKL;EEpKC;;IAEI,wBAAA;GFsKL;EEhKC;IACI,cAAA;GFkKL;EEhKC;;IAGQ,kCAAA;GFiKT;EE9JC;IACI,uBAAA;GFgKL;EE7JC;IACI,qCAAA;GF+JL;EEhKC;;IAKQ,kCAAA;GF+JT;EE5JC;;IAGQ,kCAAA;GF6JT;CACF;AGnPD;EACE,oCAAA;EACA,sDAAA;EACA,gYAAA;CHqPD;AG7OD;EACE,mBAAA;EACA,SAAA;EACA,sBAAA;EACA,oCAAA;EACA,mBAAA;EACA,oBAAA;EACA,eAAA;EACA,oCAAA;EACA,mCAAA;CH+OD;AG3OmC;EAAW,iBAAA;CH8O9C;AG7OmC;EAAW,iBAAA;CHgP9C;AG9OmC;;EAAW,iBAAA;CHkP9C;AGjPmC;EAAW,iBAAA;CHoP9C;AGnPmC;EAAW,iBAAA;CHsP9C;AGrPmC;EAAW,iBAAA;CHwP9C;AGvPmC;EAAW,iBAAA;CH0P9C;AGzPmC;EAAW,iBAAA;CH4P9C;AG3PmC;EAAW,iBAAA;CH8P9C;AG7PmC;EAAW,iBAAA;CHgQ9C;AG/PmC;EAAW,iBAAA;CHkQ9C;AGjQmC;EAAW,iBAAA;CHoQ9C;AGnQmC;EAAW,iBAAA;CHsQ9C;AGrQmC;EAAW,iBAAA;CHwQ9C;AGvQmC;EAAW,iBAAA;CH0Q9C;AGzQmC;EAAW,iBAAA;CH4Q9C;AG3QmC;EAAW,iBAAA;CH8Q9C;AG7QmC;EAAW,iBAAA;CHgR9C;AG/QmC;EAAW,iBAAA;CHkR9C;AGjRmC;EAAW,iBAAA;CHoR9C;AGnRmC;EAAW,iBAAA;CHsR9C;AGrRmC;EAAW,iBAAA;CHwR9C;AGvRmC;EAAW,iBAAA;CH0R9C;AGzRmC;EAAW,iBAAA;CH4R9C;AG3RmC;EAAW,iBAAA;CH8R9C;AG7RmC;EAAW,iBAAA;CHgS9C;AG/RmC;EAAW,iBAAA;CHkS9C;AGjSmC;EAAW,iBAAA;CHoS9C;AGnSmC;EAAW,iBAAA;CHsS9C;AGrSmC;EAAW,iBAAA;CHwS9C;AGvSmC;EAAW,iBAAA;CH0S9C;AGzSmC;EAAW,iBAAA;CH4S9C;AG3SmC;EAAW,iBAAA;CH8S9C;AG7SmC;EAAW,iBAAA;CHgT9C;AG/SmC;EAAW,iBAAA;CHkT9C;AGjTmC;EAAW,iBAAA;CHoT9C;AGnTmC;EAAW,iBAAA;CHsT9C;AGrTmC;EAAW,iBAAA;CHwT9C;AGvTmC;EAAW,iBAAA;CH0T9C;AGzTmC;EAAW,iBAAA;CH4T9C;AG3TmC;EAAW,iBAAA;CH8T9C;AG7TmC;EAAW,iBAAA;CHgU9C;AG/TmC;EAAW,iBAAA;CHkU9C;AGjUmC;EAAW,iBAAA;CHoU9C;AGnUmC;EAAW,iBAAA;CHsU9C;AGrUmC;EAAW,iBAAA;CHwU9C;AGvUmC;EAAW,iBAAA;CH0U9C;AGzUmC;EAAW,iBAAA;CH4U9C;AG3UmC;EAAW,iBAAA;CH8U9C;AG7UmC;EAAW,iBAAA;CHgV9C;AG/UmC;EAAW,iBAAA;CHkV9C;AGjVmC;EAAW,iBAAA;CHoV9C;AGnVmC;EAAW,iBAAA;CHsV9C;AGrVmC;EAAW,iBAAA;CHwV9C;AGvVmC;EAAW,iBAAA;CH0V9C;AGzVmC;EAAW,iBAAA;CH4V9C;AG3VmC;EAAW,iBAAA;CH8V9C;AG7VmC;EAAW,iBAAA;CHgW9C;AG/VmC;EAAW,iBAAA;CHkW9C;AGjWmC;EAAW,iBAAA;CHoW9C;AGnWmC;EAAW,iBAAA;CHsW9C;AGrWmC;EAAW,iBAAA;CHwW9C;AGvWmC;EAAW,iBAAA;CH0W9C;AGzWmC;EAAW,iBAAA;CH4W9C;AG3WmC;EAAW,iBAAA;CH8W9C;AG7WmC;EAAW,iBAAA;CHgX9C;AG/WmC;EAAW,iBAAA;CHkX9C;AGjXmC;EAAW,iBAAA;CHoX9C;AGnXmC;EAAW,iBAAA;CHsX9C;AGrXmC;EAAW,iBAAA;CHwX9C;AGvXmC;EAAW,iBAAA;CH0X9C;AGzXmC;EAAW,iBAAA;CH4X9C;AG3XmC;EAAW,iBAAA;CH8X9C;AG7XmC;EAAW,iBAAA;CHgY9C;AG/XmC;EAAW,iBAAA;CHkY9C;AGjYmC;EAAW,iBAAA;CHoY9C;AGnYmC;EAAW,iBAAA;CHsY9C;AGrYmC;EAAW,iBAAA;CHwY9C;AGvYmC;EAAW,iBAAA;CH0Y9C;AGzYmC;EAAW,iBAAA;CH4Y9C;AG3YmC;EAAW,iBAAA;CH8Y9C;AG7YmC;EAAW,iBAAA;CHgZ9C;AG/YmC;EAAW,iBAAA;CHkZ9C;AGjZmC;EAAW,iBAAA;CHoZ9C;AGnZmC;EAAW,iBAAA;CHsZ9C;AGrZmC;EAAW,iBAAA;CHwZ9C;AGvZmC;EAAW,iBAAA;CH0Z9C;AGzZmC;EAAW,iBAAA;CH4Z9C;AG3ZmC;EAAW,iBAAA;CH8Z9C;AG7ZmC;EAAW,iBAAA;CHga9C;AG/ZmC;EAAW,iBAAA;CHka9C;AGjamC;EAAW,iBAAA;CHoa9C;AGnamC;EAAW,iBAAA;CHsa9C;AGramC;EAAW,iBAAA;CHwa9C;AGvamC;EAAW,iBAAA;CH0a9C;AGzamC;EAAW,iBAAA;CH4a9C;AG3amC;EAAW,iBAAA;CH8a9C;AG7amC;EAAW,iBAAA;CHgb9C;AG/amC;EAAW,iBAAA;CHkb9C;AGjbmC;EAAW,iBAAA;CHob9C;AGnbmC;EAAW,iBAAA;CHsb9C;AGrbmC;EAAW,iBAAA;CHwb9C;AGvbmC;EAAW,iBAAA;CH0b9C;AGzbmC;EAAW,iBAAA;CH4b9C;AG3bmC;EAAW,iBAAA;CH8b9C;AG7bmC;EAAW,iBAAA;CHgc9C;AG/bmC;EAAW,iBAAA;CHkc9C;AGjcmC;EAAW,iBAAA;CHoc9C;AGncmC;EAAW,iBAAA;CHsc9C;AGrcmC;EAAW,iBAAA;CHwc9C;AGvcmC;EAAW,iBAAA;CH0c9C;AGzcmC;EAAW,iBAAA;CH4c9C;AG3cmC;EAAW,iBAAA;CH8c9C;AG7cmC;EAAW,iBAAA;CHgd9C;AG/cmC;EAAW,iBAAA;CHkd9C;AGjdmC;EAAW,iBAAA;CHod9C;AGndmC;EAAW,iBAAA;CHsd9C;AGrdmC;EAAW,iBAAA;CHwd9C;AGvdmC;EAAW,iBAAA;CH0d9C;AGzdmC;EAAW,iBAAA;CH4d9C;AG3dmC;EAAW,iBAAA;CH8d9C;AG7dmC;EAAW,iBAAA;CHge9C;AG/dmC;EAAW,iBAAA;CHke9C;AGjemC;EAAW,iBAAA;CHoe9C;AGnemC;EAAW,iBAAA;CHse9C;AGremC;EAAW,iBAAA;CHwe9C;AGvemC;EAAW,iBAAA;CH0e9C;AGzemC;EAAW,iBAAA;CH4e9C;AG3emC;EAAW,iBAAA;CH8e9C;AG7emC;EAAW,iBAAA;CHgf9C;AG/emC;EAAW,iBAAA;CHkf9C;AGjfmC;EAAW,iBAAA;CHof9C;AGnfmC;EAAW,iBAAA;CHsf9C;AGrfmC;EAAW,iBAAA;CHwf9C;AGvfmC;EAAW,iBAAA;CH0f9C;AGzfmC;EAAW,iBAAA;CH4f9C;AG3fmC;EAAW,iBAAA;CH8f9C;AG7fmC;EAAW,iBAAA;CHggB9C;AG/fmC;EAAW,iBAAA;CHkgB9C;AGjgBmC;EAAW,iBAAA;CHogB9C;AGngBmC;EAAW,iBAAA;CHsgB9C;AGrgBmC;EAAW,iBAAA;CHwgB9C;AGvgBmC;EAAW,iBAAA;CH0gB9C;AGzgBmC;EAAW,iBAAA;CH4gB9C;AG3gBmC;EAAW,iBAAA;CH8gB9C;AG7gBmC;EAAW,iBAAA;CHghB9C;AG/gBmC;EAAW,iBAAA;CHkhB9C;AGjhBmC;EAAW,iBAAA;CHohB9C;AGnhBmC;EAAW,iBAAA;CHshB9C;AGrhBmC;EAAW,iBAAA;CHwhB9C;AGvhBmC;EAAW,iBAAA;CH0hB9C;AGzhBmC;EAAW,iBAAA;CH4hB9C;AG3hBmC;EAAW,iBAAA;CH8hB9C;AG7hBmC;EAAW,iBAAA;CHgiB9C;AG/hBmC;EAAW,iBAAA;CHkiB9C;AGjiBmC;EAAW,iBAAA;CHoiB9C;AGniBmC;EAAW,iBAAA;CHsiB9C;AGriBmC;EAAW,iBAAA;CHwiB9C;AGviBmC;EAAW,iBAAA;CH0iB9C;AGziBmC;EAAW,iBAAA;CH4iB9C;AG3iBmC;EAAW,iBAAA;CH8iB9C;AG7iBmC;EAAW,iBAAA;CHgjB9C;AG/iBmC;EAAW,iBAAA;CHkjB9C;AGjjBmC;EAAW,iBAAA;CHojB9C;AGnjBmC;EAAW,iBAAA;CHsjB9C;AGrjBmC;EAAW,iBAAA;CHwjB9C;AGvjBmC;EAAW,iBAAA;CH0jB9C;AGzjBmC;EAAW,iBAAA;CH4jB9C;AG3jBmC;EAAW,iBAAA;CH8jB9C;AG7jBmC;EAAW,iBAAA;CHgkB9C;AG/jBmC;EAAW,iBAAA;CHkkB9C;AGjkBmC;EAAW,iBAAA;CHokB9C;AGnkBmC;EAAW,iBAAA;CHskB9C;AGrkBmC;EAAW,iBAAA;CHwkB9C;AGvkBmC;EAAW,iBAAA;CH0kB9C;AGzkBmC;EAAW,iBAAA;CH4kB9C;AG3kBmC;EAAW,iBAAA;CH8kB9C;AG7kBmC;EAAW,iBAAA;CHglB9C;AG/kBmC;EAAW,iBAAA;CHklB9C;AGjlBmC;EAAW,iBAAA;CHolB9C;AGnlBmC;EAAW,iBAAA;CHslB9C;AGrlBmC;EAAW,iBAAA;CHwlB9C;AGvlBmC;EAAW,iBAAA;CH0lB9C;AGzlBmC;EAAW,iBAAA;CH4lB9C;AG3lBmC;EAAW,iBAAA;CH8lB9C;AG7lBmC;EAAW,iBAAA;CHgmB9C;AG/lBmC;EAAW,iBAAA;CHkmB9C;AGjmBmC;EAAW,iBAAA;CHomB9C;AGnmBmC;EAAW,iBAAA;CHsmB9C;AGrmBmC;EAAW,iBAAA;CHwmB9C;AGvmBmC;EAAW,iBAAA;CH0mB9C;AGzmBmC;EAAW,iBAAA;CH4mB9C;AG3mBmC;EAAW,iBAAA;CH8mB9C;AG7mBmC;EAAW,iBAAA;CHgnB9C;AG/mBmC;EAAW,iBAAA;CHknB9C;AGjnBmC;EAAW,iBAAA;CHonB9C;AGnnBmC;EAAW,iBAAA;CHsnB9C;AGrnBmC;EAAW,iBAAA;CHwnB9C;AGvnBmC;EAAW,iBAAA;CH0nB9C;AGznBmC;EAAW,iBAAA;CH4nB9C;AG3nBmC;EAAW,iBAAA;CH8nB9C;AG7nBmC;EAAW,iBAAA;CHgoB9C;AG/nBmC;EAAW,iBAAA;CHkoB9C;AGjoBmC;EAAW,iBAAA;CHooB9C;AGnoBmC;EAAW,iBAAA;CHsoB9C;AGroBmC;EAAW,iBAAA;CHwoB9C;AG/nBmC;EAAW,iBAAA;CHkoB9C;AGjoBmC;EAAW,iBAAA;CHooB9C;AGnoBmC;EAAW,iBAAA;CHsoB9C;AGroBmC;EAAW,iBAAA;CHwoB9C;AGvoBmC;EAAW,iBAAA;CH0oB9C;AGzoBmC;EAAW,iBAAA;CH4oB9C;AG3oBmC;EAAW,iBAAA;CH8oB9C;AG7oBmC;EAAW,iBAAA;CHgpB9C;AG/oBmC;EAAW,iBAAA;CHkpB9C;AGjpBmC;EAAW,iBAAA;CHopB9C;AGnpBmC;EAAW,iBAAA;CHspB9C;AGrpBmC;EAAW,iBAAA;CHwpB9C;AGvpBmC;EAAW,iBAAA;CH0pB9C;AGzpBmC;EAAW,iBAAA;CH4pB9C;AG3pBmC;EAAW,iBAAA;CH8pB9C;AG7pBmC;EAAW,iBAAA;CHgqB9C;AG/pBmC;EAAW,iBAAA;CHkqB9C;AGjqBmC;EAAW,iBAAA;CHoqB9C;AGnqBmC;EAAW,iBAAA;CHsqB9C;AGrqBmC;EAAW,iBAAA;CHwqB9C;AGvqBmC;EAAW,iBAAA;CH0qB9C;AGzqBmC;EAAW,iBAAA;CH4qB9C;AG3qBmC;EAAW,iBAAA;CH8qB9C;AG7qBmC;EAAW,iBAAA;CHgrB9C;AG/qBmC;EAAW,iBAAA;CHkrB9C;AGjrBmC;EAAW,iBAAA;CHorB9C;AGnrBmC;EAAW,iBAAA;CHsrB9C;AGrrBmC;EAAW,iBAAA;CHwrB9C;AGvrBmC;EAAW,iBAAA;CH0rB9C;AGzrBmC;EAAW,iBAAA;CH4rB9C;AG3rBmC;EAAW,iBAAA;CH8rB9C;AG7rBmC;EAAW,iBAAA;CHgsB9C;AG/rBmC;EAAW,iBAAA;CHksB9C;AGjsBmC;EAAW,iBAAA;CHosB9C;AGnsBmC;EAAW,iBAAA;CHssB9C;AGrsBmC;EAAW,iBAAA;CHwsB9C;AGvsBmC;EAAW,iBAAA;CH0sB9C;AGzsBmC;EAAW,iBAAA;CH4sB9C;AG3sBmC;EAAW,iBAAA;CH8sB9C;AG7sBmC;EAAW,iBAAA;CHgtB9C;AG/sBmC;EAAW,iBAAA;CHktB9C;AGjtBmC;EAAW,iBAAA;CHotB9C;AGntBmC;EAAW,iBAAA;CHstB9C;AGrtBmC;EAAW,iBAAA;CHwtB9C;AGvtBmC;EAAW,iBAAA;CH0tB9C;AGztBmC;EAAW,iBAAA;CH4tB9C;AG3tBmC;EAAW,iBAAA;CH8tB9C;AG7tBmC;EAAW,iBAAA;CHguB9C;AG/tBmC;EAAW,iBAAA;CHkuB9C;AGjuBmC;EAAW,iBAAA;CHouB9C;AGnuBmC;EAAW,iBAAA;CHsuB9C;AGruBmC;EAAW,iBAAA;CHwuB9C;AGvuBmC;EAAW,iBAAA;CH0uB9C;AGzuBmC;EAAW,iBAAA;CH4uB9C;AG3uBmC;EAAW,iBAAA;CH8uB9C;AG7uBmC;EAAW,iBAAA;CHgvB9C;AIthCD;ECgEE,+BAAA;EACG,4BAAA;EACK,uBAAA;CLy9BT;AIxhCD;;EC6DE,+BAAA;EACG,4BAAA;EACK,uBAAA;CL+9BT;AIthCD;EACE,gBAAA;EACA,8CAAA;CJwhCD;AIrhCD;EACE,4DAAA;EACA,gBAAA;EACA,wBAAA;EACA,eAAA;EACA,uBAAA;CJuhCD;AInhCD;;;;EAIE,qBAAA;EACA,mBAAA;EACA,qBAAA;CJqhCD;AI/gCD;EACE,eAAA;EACA,sBAAA;CJihCD;AI/gCC;;EAEE,eAAA;EACA,2BAAA;CJihCH;AI9gCC;EEnDA,2CAAA;EACA,qBAAA;CNokCD;AIvgCD;EACE,UAAA;CJygCD;AIngCD;EACE,uBAAA;CJqgCD;AIjgCD;;;;;EGvEE,eAAA;EACA,gBAAA;EACA,aAAA;CP+kCD;AIrgCD;EACE,mBAAA;CJugCD;AIjgCD;EACE,aAAA;EACA,wBAAA;EACA,uBAAA;EACA,uBAAA;EACA,mBAAA;EC6FA,yCAAA;EACK,oCAAA;EACG,iCAAA;EEvLR,sBAAA;EACA,gBAAA;EACA,aAAA;CP+lCD;AIjgCD;EACE,mBAAA;CJmgCD;AI7/BD;EACE,iBAAA;EACA,oBAAA;EACA,UAAA;EACA,8BAAA;CJ+/BD;AIv/BD;EACE,mBAAA;EACA,WAAA;EACA,YAAA;EACA,aAAA;EACA,WAAA;EACA,iBAAA;EACA,uBAAA;EACA,UAAA;CJy/BD;AIj/BC;;EAEE,iBAAA;EACA,YAAA;EACA,aAAA;EACA,UAAA;EACA,kBAAA;EACA,WAAA;CJm/BH;AIx+BD;EACE,gBAAA;CJ0+BD;AQjoCD;;;;;;;;;;;;EAEE,qBAAA;EACA,iBAAA;EACA,iBAAA;EACA,eAAA;CR6oCD;AQlpCD;;;;;;;;;;;;;;;;;;;;;;;;EASI,oBAAA;EACA,eAAA;EACA,eAAA;CRmqCH;AQ/pCD;;;;;;EAGE,iBAAA;EACA,oBAAA;CRoqCD;AQxqCD;;;;;;;;;;;;EAQI,eAAA;CR8qCH;AQ3qCD;;;;;;EAGE,iBAAA;EACA,oBAAA;CRgrCD;AQprCD;;;;;;;;;;;;EAQI,eAAA;CR0rCH;AQtrCD;;EAAU,gBAAA;CR0rCT;AQzrCD;;EAAU,gBAAA;CR6rCT;AQ5rCD;;EAAU,gBAAA;CRgsCT;AQ/rCD;;EAAU,gBAAA;CRmsCT;AQlsCD;;EAAU,gBAAA;CRssCT;AQrsCD;;EAAU,gBAAA;CRysCT;AQnsCD;EACE,iBAAA;CRqsCD;AQlsCD;EACE,oBAAA;EACA,gBAAA;EACA,iBAAA;EACA,iBAAA;CRosCD;AQ/rCD;EAwOA;IA1OI,gBAAA;GRqsCD;CACF;AQ7rCD;;EAEE,eAAA;CR+rCD;AQ5rCD;;EAEE,0BAAA;EACA,cAAA;CR8rCD;AQ1rCD;EAAuB,iBAAA;CR6rCtB;AQ5rCD;EAAuB,kBAAA;CR+rCtB;AQ9rCD;EAAuB,mBAAA;CRisCtB;AQhsCD;EAAuB,oBAAA;CRmsCtB;AQlsCD;EAAuB,oBAAA;CRqsCtB;AQlsCD;EAAuB,0BAAA;CRqsCtB;AQpsCD;EAAuB,0BAAA;CRusCtB;AQtsCD;EAAuB,2BAAA;CRysCtB;AQtsCD;EACE,eAAA;CRwsCD;AQtsCD;ECrGE,eAAA;CT8yCD;AS7yCC;;EAEE,eAAA;CT+yCH;AQ1sCD;ECxGE,eAAA;CTqzCD;ASpzCC;;EAEE,eAAA;CTszCH;AQ9sCD;EC3GE,eAAA;CT4zCD;AS3zCC;;EAEE,eAAA;CT6zCH;AQltCD;EC9GE,eAAA;CTm0CD;ASl0CC;;EAEE,eAAA;CTo0CH;AQttCD;ECjHE,eAAA;CT00CD;ASz0CC;;EAEE,eAAA;CT20CH;AQttCD;EAGE,YAAA;EE3HA,0BAAA;CVk1CD;AUj1CC;;EAEE,0BAAA;CVm1CH;AQxtCD;EE9HE,0BAAA;CVy1CD;AUx1CC;;EAEE,0BAAA;CV01CH;AQ5tCD;EEjIE,0BAAA;CVg2CD;AU/1CC;;EAEE,0BAAA;CVi2CH;AQhuCD;EEpIE,0BAAA;CVu2CD;AUt2CC;;EAEE,0BAAA;CVw2CH;AQpuCD;EEvIE,0BAAA;CV82CD;AU72CC;;EAEE,0BAAA;CV+2CH;AQnuCD;EACE,oBAAA;EACA,oBAAA;EACA,iCAAA;CRquCD;AQ7tCD;;EAEE,cAAA;EACA,oBAAA;CR+tCD;AQluCD;;;;EAMI,iBAAA;CRkuCH;AQ3tCD;EACE,gBAAA;EACA,iBAAA;CR6tCD;AQztCD;EALE,gBAAA;EACA,iBAAA;EAMA,kBAAA;CR4tCD;AQ9tCD;EAKI,sBAAA;EACA,kBAAA;EACA,mBAAA;CR4tCH;AQvtCD;EACE,cAAA;EACA,oBAAA;CRytCD;AQvtCD;;EAEE,wBAAA;CRytCD;AQvtCD;EACE,kBAAA;CRytCD;AQvtCD;EACE,eAAA;CRytCD;AQhsCD;EA6EA;IAvFM,YAAA;IACA,aAAA;IACA,YAAA;IACA,kBAAA;IGtNJ,iBAAA;IACA,wBAAA;IACA,oBAAA;GXq6CC;EQ7nCH;IAhFM,mBAAA;GRgtCH;CACF;AQvsCD;;EAGE,aAAA;EACA,kCAAA;CRwsCD;AQtsCD;EACE,eAAA;EA9IqB,0BAAA;CRu1CtB;AQpsCD;EACE,mBAAA;EACA,iBAAA;EACA,kBAAA;EACA,+BAAA;CRssCD;AQjsCG;;;EACE,iBAAA;CRqsCL;AQ/sCD;;;EAmBI,eAAA;EACA,eAAA;EACA,wBAAA;EACA,eAAA;CRisCH;AQ/rCG;;;EACE,uBAAA;CRmsCL;AQ3rCD;;EAEE,oBAAA;EACA,gBAAA;EACA,gCAAA;EACA,eAAA;EACA,kBAAA;CR6rCD;AQvrCG;;;;;;EAAW,YAAA;CR+rCd;AQ9rCG;;;;;;EACE,uBAAA;CRqsCL;AQ/rCD;EACE,oBAAA;EACA,mBAAA;EACA,wBAAA;CRisCD;AYv+CD;;;;EAIE,+DAAA;CZy+CD;AYr+CD;EACE,iBAAA;EACA,eAAA;EACA,eAAA;EACA,0BAAA;EACA,mBAAA;CZu+CD;AYn+CD;EACE,iBAAA;EACA,eAAA;EACA,YAAA;EACA,uBAAA;EACA,mBAAA;EACA,uDAAA;UAAA,+CAAA;CZq+CD;AY3+CD;EASI,WAAA;EACA,gBAAA;EACA,kBAAA;EACA,yBAAA;UAAA,iBAAA;CZq+CH;AYh+CD;EACE,eAAA;EACA,eAAA;EACA,iBAAA;EACA,gBAAA;EACA,wBAAA;EACA,sBAAA;EACA,sBAAA;EACA,eAAA;EACA,0BAAA;EACA,uBAAA;EACA,mBAAA;CZk+CD;AY7+CD;EAeI,WAAA;EACA,mBAAA;EACA,eAAA;EACA,sBAAA;EACA,8BAAA;EACA,iBAAA;CZi+CH;AY59CD;EACE,kBAAA;EACA,mBAAA;CZ89CD;AaxhDD;ECHE,mBAAA;EACA,kBAAA;EACA,mBAAA;EACA,oBAAA;Cd8hDD;AaxhDC;EAqEF;IAvEI,aAAA;Gb8hDD;CACF;Aa1hDC;EAkEF;IApEI,aAAA;GbgiDD;CACF;Aa5hDD;EA+DA;IAjEI,cAAA;GbkiDD;CACF;AazhDD;ECvBE,mBAAA;EACA,kBAAA;EACA,mBAAA;EACA,oBAAA;CdmjDD;AathDD;ECvBE,mBAAA;EACA,oBAAA;CdgjDD;AehjDG;EACE,mBAAA;EAEA,gBAAA;EAEA,mBAAA;EACA,oBAAA;CfgjDL;AehiDG;EACE,YAAA;CfkiDL;Ae3hDC;EACE,YAAA;Cf6hDH;Ae9hDC;EACE,oBAAA;CfgiDH;AejiDC;EACE,oBAAA;CfmiDH;AepiDC;EACE,WAAA;CfsiDH;AeviDC;EACE,oBAAA;CfyiDH;Ae1iDC;EACE,oBAAA;Cf4iDH;Ae7iDC;EACE,WAAA;Cf+iDH;AehjDC;EACE,oBAAA;CfkjDH;AenjDC;EACE,oBAAA;CfqjDH;AetjDC;EACE,WAAA;CfwjDH;AezjDC;EACE,oBAAA;Cf2jDH;Ae5jDC;EACE,mBAAA;Cf8jDH;AehjDC;EACE,YAAA;CfkjDH;AenjDC;EACE,oBAAA;CfqjDH;AetjDC;EACE,oBAAA;CfwjDH;AezjDC;EACE,WAAA;Cf2jDH;Ae5jDC;EACE,oBAAA;Cf8jDH;Ae/jDC;EACE,oBAAA;CfikDH;AelkDC;EACE,WAAA;CfokDH;AerkDC;EACE,oBAAA;CfukDH;AexkDC;EACE,oBAAA;Cf0kDH;Ae3kDC;EACE,WAAA;Cf6kDH;Ae9kDC;EACE,oBAAA;CfglDH;AejlDC;EACE,mBAAA;CfmlDH;Ae/kDC;EACE,YAAA;CfilDH;AejmDC;EACE,WAAA;CfmmDH;AepmDC;EACE,mBAAA;CfsmDH;AevmDC;EACE,mBAAA;CfymDH;Ae1mDC;EACE,UAAA;Cf4mDH;Ae7mDC;EACE,mBAAA;Cf+mDH;AehnDC;EACE,mBAAA;CfknDH;AennDC;EACE,UAAA;CfqnDH;AetnDC;EACE,mBAAA;CfwnDH;AeznDC;EACE,mBAAA;Cf2nDH;Ae5nDC;EACE,UAAA;Cf8nDH;Ae/nDC;EACE,mBAAA;CfioDH;AeloDC;EACE,kBAAA;CfooDH;AehoDC;EACE,WAAA;CfkoDH;AepnDC;EACE,kBAAA;CfsnDH;AevnDC;EACE,0BAAA;CfynDH;Ae1nDC;EACE,0BAAA;Cf4nDH;Ae7nDC;EACE,iBAAA;Cf+nDH;AehoDC;EACE,0BAAA;CfkoDH;AenoDC;EACE,0BAAA;CfqoDH;AetoDC;EACE,iBAAA;CfwoDH;AezoDC;EACE,0BAAA;Cf2oDH;Ae5oDC;EACE,0BAAA;Cf8oDH;Ae/oDC;EACE,iBAAA;CfipDH;AelpDC;EACE,0BAAA;CfopDH;AerpDC;EACE,yBAAA;CfupDH;AexpDC;EACE,gBAAA;Cf0pDH;Aa1pDD;EElCI;IACE,YAAA;Gf+rDH;EexrDD;IACE,YAAA;Gf0rDD;Ee3rDD;IACE,oBAAA;Gf6rDD;Ee9rDD;IACE,oBAAA;GfgsDD;EejsDD;IACE,WAAA;GfmsDD;EepsDD;IACE,oBAAA;GfssDD;EevsDD;IACE,oBAAA;GfysDD;Ee1sDD;IACE,WAAA;Gf4sDD;Ee7sDD;IACE,oBAAA;Gf+sDD;EehtDD;IACE,oBAAA;GfktDD;EentDD;IACE,WAAA;GfqtDD;EettDD;IACE,oBAAA;GfwtDD;EeztDD;IACE,mBAAA;Gf2tDD;Ee7sDD;IACE,YAAA;Gf+sDD;EehtDD;IACE,oBAAA;GfktDD;EentDD;IACE,oBAAA;GfqtDD;EettDD;IACE,WAAA;GfwtDD;EeztDD;IACE,oBAAA;Gf2tDD;Ee5tDD;IACE,oBAAA;Gf8tDD;Ee/tDD;IACE,WAAA;GfiuDD;EeluDD;IACE,oBAAA;GfouDD;EeruDD;IACE,oBAAA;GfuuDD;EexuDD;IACE,WAAA;Gf0uDD;Ee3uDD;IACE,oBAAA;Gf6uDD;Ee9uDD;IACE,mBAAA;GfgvDD;Ee5uDD;IACE,YAAA;Gf8uDD;Ee9vDD;IACE,WAAA;GfgwDD;EejwDD;IACE,mBAAA;GfmwDD;EepwDD;IACE,mBAAA;GfswDD;EevwDD;IACE,UAAA;GfywDD;Ee1wDD;IACE,mBAAA;Gf4wDD;Ee7wDD;IACE,mBAAA;Gf+wDD;EehxDD;IACE,UAAA;GfkxDD;EenxDD;IACE,mBAAA;GfqxDD;EetxDD;IACE,mBAAA;GfwxDD;EezxDD;IACE,UAAA;Gf2xDD;Ee5xDD;IACE,mBAAA;Gf8xDD;Ee/xDD;IACE,kBAAA;GfiyDD;Ee7xDD;IACE,WAAA;Gf+xDD;EejxDD;IACE,kBAAA;GfmxDD;EepxDD;IACE,0BAAA;GfsxDD;EevxDD;IACE,0BAAA;GfyxDD;Ee1xDD;IACE,iBAAA;Gf4xDD;Ee7xDD;IACE,0BAAA;Gf+xDD;EehyDD;IACE,0BAAA;GfkyDD;EenyDD;IACE,iBAAA;GfqyDD;EetyDD;IACE,0BAAA;GfwyDD;EezyDD;IACE,0BAAA;Gf2yDD;Ee5yDD;IACE,iBAAA;Gf8yDD;Ee/yDD;IACE,0BAAA;GfizDD;EelzDD;IACE,yBAAA;GfozDD;EerzDD;IACE,gBAAA;GfuzDD;CACF;Aa/yDD;EE3CI;IACE,YAAA;Gf61DH;Eet1DD;IACE,YAAA;Gfw1DD;Eez1DD;IACE,oBAAA;Gf21DD;Ee51DD;IACE,oBAAA;Gf81DD;Ee/1DD;IACE,WAAA;Gfi2DD;Eel2DD;IACE,oBAAA;Gfo2DD;Eer2DD;IACE,oBAAA;Gfu2DD;Eex2DD;IACE,WAAA;Gf02DD;Ee32DD;IACE,oBAAA;Gf62DD;Ee92DD;IACE,oBAAA;Gfg3DD;Eej3DD;IACE,WAAA;Gfm3DD;Eep3DD;IACE,oBAAA;Gfs3DD;Eev3DD;IACE,mBAAA;Gfy3DD;Ee32DD;IACE,YAAA;Gf62DD;Ee92DD;IACE,oBAAA;Gfg3DD;Eej3DD;IACE,oBAAA;Gfm3DD;Eep3DD;IACE,WAAA;Gfs3DD;Eev3DD;IACE,oBAAA;Gfy3DD;Ee13DD;IACE,oBAAA;Gf43DD;Ee73DD;IACE,WAAA;Gf+3DD;Eeh4DD;IACE,oBAAA;Gfk4DD;Een4DD;IACE,oBAAA;Gfq4DD;Eet4DD;IACE,WAAA;Gfw4DD;Eez4DD;IACE,oBAAA;Gf24DD;Ee54DD;IACE,mBAAA;Gf84DD;Ee14DD;IACE,YAAA;Gf44DD;Ee55DD;IACE,WAAA;Gf85DD;Ee/5DD;IACE,mBAAA;Gfi6DD;Eel6DD;IACE,mBAAA;Gfo6DD;Eer6DD;IACE,UAAA;Gfu6DD;Eex6DD;IACE,mBAAA;Gf06DD;Ee36DD;IACE,mBAAA;Gf66DD;Ee96DD;IACE,UAAA;Gfg7DD;Eej7DD;IACE,mBAAA;Gfm7DD;Eep7DD;IACE,mBAAA;Gfs7DD;Eev7DD;IACE,UAAA;Gfy7DD;Ee17DD;IACE,mBAAA;Gf47DD;Ee77DD;IACE,kBAAA;Gf+7DD;Ee37DD;IACE,WAAA;Gf67DD;Ee/6DD;IACE,kBAAA;Gfi7DD;Eel7DD;IACE,0BAAA;Gfo7DD;Eer7DD;IACE,0BAAA;Gfu7DD;Eex7DD;IACE,iBAAA;Gf07DD;Ee37DD;IACE,0BAAA;Gf67DD;Ee97DD;IACE,0BAAA;Gfg8DD;Eej8DD;IACE,iBAAA;Gfm8DD;Eep8DD;IACE,0BAAA;Gfs8DD;Eev8DD;IACE,0BAAA;Gfy8DD;Ee18DD;IACE,iBAAA;Gf48DD;Ee78DD;IACE,0BAAA;Gf+8DD;Eeh9DD;IACE,yBAAA;Gfk9DD;Een9DD;IACE,gBAAA;Gfq9DD;CACF;Aa18DD;EE9CI;IACE,YAAA;Gf2/DH;Eep/DD;IACE,YAAA;Gfs/DD;Eev/DD;IACE,oBAAA;Gfy/DD;Ee1/DD;IACE,oBAAA;Gf4/DD;Ee7/DD;IACE,WAAA;Gf+/DD;EehgED;IACE,oBAAA;GfkgED;EengED;IACE,oBAAA;GfqgED;EetgED;IACE,WAAA;GfwgED;EezgED;IACE,oBAAA;Gf2gED;Ee5gED;IACE,oBAAA;Gf8gED;Ee/gED;IACE,WAAA;GfihED;EelhED;IACE,oBAAA;GfohED;EerhED;IACE,mBAAA;GfuhED;EezgED;IACE,YAAA;Gf2gED;Ee5gED;IACE,oBAAA;Gf8gED;Ee/gED;IACE,oBAAA;GfihED;EelhED;IACE,WAAA;GfohED;EerhED;IACE,oBAAA;GfuhED;EexhED;IACE,oBAAA;Gf0hED;Ee3hED;IACE,WAAA;Gf6hED;Ee9hED;IACE,oBAAA;GfgiED;EejiED;IACE,oBAAA;GfmiED;EepiED;IACE,WAAA;GfsiED;EeviED;IACE,oBAAA;GfyiED;Ee1iED;IACE,mBAAA;Gf4iED;EexiED;IACE,YAAA;Gf0iED;Ee1jED;IACE,WAAA;Gf4jED;Ee7jED;IACE,mBAAA;Gf+jED;EehkED;IACE,mBAAA;GfkkED;EenkED;IACE,UAAA;GfqkED;EetkED;IACE,mBAAA;GfwkED;EezkED;IACE,mBAAA;Gf2kED;Ee5kED;IACE,UAAA;Gf8kED;Ee/kED;IACE,mBAAA;GfilED;EellED;IACE,mBAAA;GfolED;EerlED;IACE,UAAA;GfulED;EexlED;IACE,mBAAA;Gf0lED;Ee3lED;IACE,kBAAA;Gf6lED;EezlED;IACE,WAAA;Gf2lED;Ee7kED;IACE,kBAAA;Gf+kED;EehlED;IACE,0BAAA;GfklED;EenlED;IACE,0BAAA;GfqlED;EetlED;IACE,iBAAA;GfwlED;EezlED;IACE,0BAAA;Gf2lED;Ee5lED;IACE,0BAAA;Gf8lED;Ee/lED;IACE,iBAAA;GfimED;EelmED;IACE,0BAAA;GfomED;EermED;IACE,0BAAA;GfumED;EexmED;IACE,iBAAA;Gf0mED;Ee3mED;IACE,0BAAA;Gf6mED;Ee9mED;IACE,yBAAA;GfgnED;EejnED;IACE,gBAAA;GfmnED;CACF;AgBvrED;EACE,8BAAA;ChByrED;AgBvrED;EACE,iBAAA;EACA,oBAAA;EACA,eAAA;EACA,iBAAA;ChByrED;AgBvrED;EACE,iBAAA;ChByrED;AgBnrED;EACE,YAAA;EACA,gBAAA;EACA,oBAAA;ChBqrED;AgBxrED;;;;;;EAWQ,aAAA;EACA,wBAAA;EACA,oBAAA;EACA,2BAAA;ChBqrEP;AgBnsED;EAoBI,uBAAA;EACA,8BAAA;ChBkrEH;AgBvsED;;;;;;EA8BQ,cAAA;ChBirEP;AgB/sED;EAoCI,2BAAA;ChB8qEH;AgBltED;EAyCI,uBAAA;ChB4qEH;AgBrqED;;;;;;EAOQ,aAAA;ChBsqEP;AgB3pED;EACE,uBAAA;ChB6pED;AgB9pED;;;;;;EAQQ,uBAAA;ChB8pEP;AgBtqED;;EAeM,yBAAA;ChB2pEL;AgBjpED;EAEI,0BAAA;ChBkpEH;AgBzoED;EAEI,0BAAA;ChB0oEH;AgBjoED;EACE,iBAAA;EACA,YAAA;EACA,sBAAA;ChBmoED;AgB9nEG;;EACE,iBAAA;EACA,YAAA;EACA,oBAAA;ChBioEL;AiB7wEC;;;;;;;;;;;;EAOI,0BAAA;CjBoxEL;AiB9wEC;;;;;EAMI,0BAAA;CjB+wEL;AiBlyEC;;;;;;;;;;;;EAOI,0BAAA;CjByyEL;AiBnyEC;;;;;EAMI,0BAAA;CjBoyEL;AiBvzEC;;;;;;;;;;;;EAOI,0BAAA;CjB8zEL;AiBxzEC;;;;;EAMI,0BAAA;CjByzEL;AiB50EC;;;;;;;;;;;;EAOI,0BAAA;CjBm1EL;AiB70EC;;;;;EAMI,0BAAA;CjB80EL;AiBj2EC;;;;;;;;;;;;EAOI,0BAAA;CjBw2EL;AiBl2EC;;;;;EAMI,0BAAA;CjBm2EL;AgBjtED;EACE,iBAAA;EACA,kBAAA;ChBmtED;AgBtpED;EACA;IA3DI,YAAA;IACA,oBAAA;IACA,mBAAA;IACA,6CAAA;IACA,uBAAA;GhBotED;EgB7pEH;IAnDM,iBAAA;GhBmtEH;EgBhqEH;;;;;;IA1CY,oBAAA;GhBktET;EgBxqEH;IAlCM,UAAA;GhB6sEH;EgB3qEH;;;;;;IAzBY,eAAA;GhB4sET;EgBnrEH;;;;;;IArBY,gBAAA;GhBgtET;EgB3rEH;;;;IARY,iBAAA;GhBysET;CACF;AkBn6ED;EACE,WAAA;EACA,UAAA;EACA,UAAA;EAIA,aAAA;ClBk6ED;AkB/5ED;EACE,eAAA;EACA,YAAA;EACA,WAAA;EACA,oBAAA;EACA,gBAAA;EACA,qBAAA;EACA,eAAA;EACA,UAAA;EACA,iCAAA;ClBi6ED;AkB95ED;EACE,sBAAA;EACA,gBAAA;EACA,mBAAA;EACA,kBAAA;ClBg6ED;AkBr5ED;Eb4BE,+BAAA;EACG,4BAAA;EACK,uBAAA;CL43ET;AkBr5ED;;EAEE,gBAAA;EACA,mBAAA;EACA,oBAAA;ClBu5ED;AkBp5ED;EACE,eAAA;ClBs5ED;AkBl5ED;EACE,eAAA;EACA,YAAA;ClBo5ED;AkBh5ED;;EAEE,aAAA;ClBk5ED;AkB94ED;;;EZrEE,2CAAA;EACA,qBAAA;CNw9ED;AkB74ED;EACE,eAAA;EACA,iBAAA;EACA,gBAAA;EACA,wBAAA;EACA,eAAA;ClB+4ED;AkBr3ED;EACE,eAAA;EACA,YAAA;EACA,aAAA;EACA,kBAAA;EACA,gBAAA;EACA,wBAAA;EACA,eAAA;EACA,uBAAA;EACA,uBAAA;EACA,uBAAA;EACA,mBAAA;EbxDA,yDAAA;EACQ,iDAAA;EAyHR,uFAAA;EACK,0EAAA;EACG,uEAAA;CLwzET;AmBh8EC;EACE,sBAAA;EACA,WAAA;EdUF,uFAAA;EACQ,+EAAA;CLy7ET;AKx5EC;EACE,YAAA;EACA,WAAA;CL05EH;AKx5EC;EAA0B,YAAA;CL25E3B;AK15EC;EAAgC,YAAA;CL65EjC;AkBj4EC;EACE,UAAA;EACA,8BAAA;ClBm4EH;AkB33EC;;;EAGE,0BAAA;EACA,WAAA;ClB63EH;AkB13EC;;EAEE,oBAAA;ClB43EH;AkBx3EC;EACE,aAAA;ClB03EH;AkB92ED;EACE,yBAAA;ClBg3ED;AkBx0ED;EAtBI;;;;IACE,kBAAA;GlBo2EH;EkBj2EC;;;;;;;;IAEE,kBAAA;GlBy2EH;EkBt2EC;;;;;;;;IAEE,kBAAA;GlB82EH;CACF;AkBp2ED;EACE,oBAAA;ClBs2ED;AkB91ED;;EAEE,mBAAA;EACA,eAAA;EACA,iBAAA;EACA,oBAAA;ClBg2ED;AkBr2ED;;EAQI,iBAAA;EACA,mBAAA;EACA,iBAAA;EACA,oBAAA;EACA,gBAAA;ClBi2EH;AkB91ED;;;;EAIE,mBAAA;EACA,mBAAA;EACA,mBAAA;ClBg2ED;AkB71ED;;EAEE,iBAAA;ClB+1ED;AkB31ED;;EAEE,mBAAA;EACA,sBAAA;EACA,mBAAA;EACA,iBAAA;EACA,uBAAA;EACA,oBAAA;EACA,gBAAA;ClB61ED;AkB31ED;;EAEE,cAAA;EACA,kBAAA;ClB61ED;AkBp1EC;;;;;;EAGE,oBAAA;ClBy1EH;AkBn1EC;;;;EAEE,oBAAA;ClBu1EH;AkBj1EC;;;;EAGI,oBAAA;ClBo1EL;AkBz0ED;EAEE,iBAAA;EACA,oBAAA;EAEA,iBAAA;EACA,iBAAA;ClBy0ED;AkBv0EC;;EAEE,gBAAA;EACA,iBAAA;ClBy0EH;AkB5zED;ECnQE,aAAA;EACA,kBAAA;EACA,gBAAA;EACA,iBAAA;EACA,mBAAA;CnBkkFD;AmBhkFC;EACE,aAAA;EACA,kBAAA;CnBkkFH;AmB/jFC;;EAEE,aAAA;CnBikFH;AkBx0ED;EAEI,aAAA;EACA,kBAAA;EACA,gBAAA;EACA,iBAAA;EACA,mBAAA;ClBy0EH;AkB/0ED;EASI,aAAA;EACA,kBAAA;ClBy0EH;AkBn1ED;;EAcI,aAAA;ClBy0EH;AkBv1ED;EAiBI,aAAA;EACA,iBAAA;EACA,kBAAA;EACA,gBAAA;EACA,iBAAA;ClBy0EH;AkBr0ED;EC/RE,aAAA;EACA,mBAAA;EACA,gBAAA;EACA,uBAAA;EACA,mBAAA;CnBumFD;AmBrmFC;EACE,aAAA;EACA,kBAAA;CnBumFH;AmBpmFC;;EAEE,aAAA;CnBsmFH;AkBj1ED;EAEI,aAAA;EACA,mBAAA;EACA,gBAAA;EACA,uBAAA;EACA,mBAAA;ClBk1EH;AkBx1ED;EASI,aAAA;EACA,kBAAA;ClBk1EH;AkB51ED;;EAcI,aAAA;ClBk1EH;AkBh2ED;EAiBI,aAAA;EACA,iBAAA;EACA,mBAAA;EACA,gBAAA;EACA,uBAAA;ClBk1EH;AkBz0ED;EAEE,mBAAA;ClB00ED;AkB50ED;EAMI,sBAAA;ClBy0EH;AkBr0ED;EACE,mBAAA;EACA,OAAA;EACA,SAAA;EACA,WAAA;EACA,eAAA;EACA,YAAA;EACA,aAAA;EACA,kBAAA;EACA,mBAAA;EACA,qBAAA;ClBu0ED;AkBr0ED;;;EAGE,YAAA;EACA,aAAA;EACA,kBAAA;ClBu0ED;AkBr0ED;;;EAGE,YAAA;EACA,aAAA;EACA,kBAAA;ClBu0ED;AkBn0ED;;;;;;;;;;EC1ZI,eAAA;CnByuFH;AkB/0ED;ECtZI,sBAAA;Ed+CF,yDAAA;EACQ,iDAAA;CL0rFT;AmBxuFG;EACE,sBAAA;Ed4CJ,0EAAA;EACQ,kEAAA;CL+rFT;AkBz1ED;EC5YI,eAAA;EACA,sBAAA;EACA,0BAAA;CnBwuFH;AkB91ED;ECtYI,eAAA;CnBuuFH;AkB91ED;;;;;;;;;;EC7ZI,eAAA;CnBuwFH;AkB12ED;ECzZI,sBAAA;Ed+CF,yDAAA;EACQ,iDAAA;CLwtFT;AmBtwFG;EACE,sBAAA;Ed4CJ,0EAAA;EACQ,kEAAA;CL6tFT;AkBp3ED;EC/YI,eAAA;EACA,sBAAA;EACA,0BAAA;CnBswFH;AkBz3ED;ECzYI,eAAA;CnBqwFH;AkBz3ED;;;;;;;;;;EChaI,eAAA;CnBqyFH;AkBr4ED;EC5ZI,sBAAA;Ed+CF,yDAAA;EACQ,iDAAA;CLsvFT;AmBpyFG;EACE,sBAAA;Ed4CJ,0EAAA;EACQ,kEAAA;CL2vFT;AkB/4ED;EClZI,eAAA;EACA,sBAAA;EACA,0BAAA;CnBoyFH;AkBp5ED;EC5YI,eAAA;CnBmyFH;AkBh5EC;EACE,UAAA;ClBk5EH;AkBh5EC;EACE,OAAA;ClBk5EH;AkBx4ED;EACE,eAAA;EACA,gBAAA;EACA,oBAAA;EACA,eAAA;ClB04ED;AkBvzED;EAwEA;IAtIM,sBAAA;IACA,iBAAA;IACA,uBAAA;GlBy3EH;EkBrvEH;IA/HM,sBAAA;IACA,YAAA;IACA,uBAAA;GlBu3EH;EkB1vEH;IAxHM,sBAAA;GlBq3EH;EkB7vEH;IApHM,sBAAA;IACA,uBAAA;GlBo3EH;EkBjwEH;;;IA9GQ,YAAA;GlBo3EL;EkBtwEH;IAxGM,YAAA;GlBi3EH;EkBzwEH;IApGM,iBAAA;IACA,uBAAA;GlBg3EH;EkB7wEH;;IA5FM,sBAAA;IACA,cAAA;IACA,iBAAA;IACA,uBAAA;GlB62EH;EkBpxEH;;IAtFQ,gBAAA;GlB82EL;EkBxxEH;;IAjFM,mBAAA;IACA,eAAA;GlB62EH;EkB7xEH;IA3EM,OAAA;GlB22EH;CACF;AkBj2ED;;;;EASI,cAAA;EACA,iBAAA;EACA,iBAAA;ClB81EH;AkBz2ED;;EAiBI,iBAAA;ClB41EH;AkB72ED;EJthBE,mBAAA;EACA,oBAAA;Cds4FD;AkB10EC;EAyBF;IAnCM,kBAAA;IACA,iBAAA;IACA,iBAAA;GlBw1EH;CACF;AkBx3ED;EAwCI,YAAA;ClBm1EH;AkBr0EC;EAUF;IAdQ,kBAAA;IACA,gBAAA;GlB60EL;CACF;AkBn0EC;EAEF;IANQ,iBAAA;IACA,gBAAA;GlB20EL;CACF;AoBp6FD;EACE,sBAAA;EACA,iBAAA;EACA,oBAAA;EACA,mBAAA;EACA,uBAAA;EACA,+BAAA;MAAA,2BAAA;EACA,gBAAA;EACA,uBAAA;EACA,8BAAA;EACA,oBAAA;EC0CA,kBAAA;EACA,gBAAA;EACA,wBAAA;EACA,mBAAA;EhB+JA,0BAAA;EACG,uBAAA;EACC,sBAAA;EACI,kBAAA;CL+tFT;AoBv6FG;;;;;;EdnBF,2CAAA;EACA,qBAAA;CNk8FD;AoB16FC;;;EAGE,YAAA;EACA,sBAAA;CpB46FH;AoBz6FC;;EAEE,WAAA;EACA,uBAAA;Ef2BF,yDAAA;EACQ,iDAAA;CLi5FT;AoBz6FC;;;EAGE,oBAAA;EE7CF,cAAA;EAGA,0BAAA;EjB8DA,yBAAA;EACQ,iBAAA;CL05FT;AoBz6FG;;EAEE,qBAAA;CpB26FL;AoBl6FD;EC3DE,YAAA;EACA,uBAAA;EACA,mBAAA;CrBg+FD;AqB99FC;;EAEE,YAAA;EACA,0BAAA;EACI,sBAAA;CrBg+FP;AqB99FC;EACE,YAAA;EACA,0BAAA;EACI,sBAAA;CrBg+FP;AqB99FC;;;EAGE,YAAA;EACA,0BAAA;EACI,sBAAA;CrBg+FP;AqB99FG;;;;;;;;;EAGE,YAAA;EACA,0BAAA;EACI,sBAAA;CrBs+FT;AqBn+FC;;;EAGE,uBAAA;CrBq+FH;AqBh+FG;;;;;;;;;EAGE,uBAAA;EACI,mBAAA;CrBw+FT;AoBv9FD;ECZI,YAAA;EACA,uBAAA;CrBs+FH;AoBx9FD;EC9DE,YAAA;EACA,0BAAA;EACA,sBAAA;CrByhGD;AqBvhGC;;EAEE,YAAA;EACA,0BAAA;EACI,sBAAA;CrByhGP;AqBvhGC;EACE,YAAA;EACA,0BAAA;EACI,sBAAA;CrByhGP;AqBvhGC;;;EAGE,YAAA;EACA,0BAAA;EACI,sBAAA;CrByhGP;AqBvhGG;;;;;;;;;EAGE,YAAA;EACA,0BAAA;EACI,sBAAA;CrB+hGT;AqB5hGC;;;EAGE,uBAAA;CrB8hGH;AqBzhGG;;;;;;;;;EAGE,0BAAA;EACI,sBAAA;CrBiiGT;AoB7gGD;ECfI,eAAA;EACA,uBAAA;CrB+hGH;AoB7gGD;EClEE,YAAA;EACA,0BAAA;EACA,sBAAA;CrBklGD;AqBhlGC;;EAEE,YAAA;EACA,0BAAA;EACI,sBAAA;CrBklGP;AqBhlGC;EACE,YAAA;EACA,0BAAA;EACI,sBAAA;CrBklGP;AqBhlGC;;;EAGE,YAAA;EACA,0BAAA;EACI,sBAAA;CrBklGP;AqBhlGG;;;;;;;;;EAGE,YAAA;EACA,0BAAA;EACI,sBAAA;CrBwlGT;AqBrlGC;;;EAGE,uBAAA;CrBulGH;AqBllGG;;;;;;;;;EAGE,0BAAA;EACI,sBAAA;CrB0lGT;AoBlkGD;ECnBI,eAAA;EACA,uBAAA;CrBwlGH;AoBlkGD;ECtEE,YAAA;EACA,0BAAA;EACA,sBAAA;CrB2oGD;AqBzoGC;;EAEE,YAAA;EACA,0BAAA;EACI,sBAAA;CrB2oGP;AqBzoGC;EACE,YAAA;EACA,0BAAA;EACI,sBAAA;CrB2oGP;AqBzoGC;;;EAGE,YAAA;EACA,0BAAA;EACI,sBAAA;CrB2oGP;AqBzoGG;;;;;;;;;EAGE,YAAA;EACA,0BAAA;EACI,sBAAA;CrBipGT;AqB9oGC;;;EAGE,uBAAA;CrBgpGH;AqB3oGG;;;;;;;;;EAGE,0BAAA;EACI,sBAAA;CrBmpGT;AoBvnGD;ECvBI,eAAA;EACA,uBAAA;CrBipGH;AoBvnGD;EC1EE,YAAA;EACA,0BAAA;EACA,sBAAA;CrBosGD;AqBlsGC;;EAEE,YAAA;EACA,0BAAA;EACI,sBAAA;CrBosGP;AqBlsGC;EACE,YAAA;EACA,0BAAA;EACI,sBAAA;CrBosGP;AqBlsGC;;;EAGE,YAAA;EACA,0BAAA;EACI,sBAAA;CrBosGP;AqBlsGG;;;;;;;;;EAGE,YAAA;EACA,0BAAA;EACI,sBAAA;CrB0sGT;AqBvsGC;;;EAGE,uBAAA;CrBysGH;AqBpsGG;;;;;;;;;EAGE,0BAAA;EACI,sBAAA;CrB4sGT;AoB5qGD;EC3BI,eAAA;EACA,uBAAA;CrB0sGH;AoB5qGD;EC9EE,YAAA;EACA,0BAAA;EACA,sBAAA;CrB6vGD;AqB3vGC;;EAEE,YAAA;EACA,0BAAA;EACI,sBAAA;CrB6vGP;AqB3vGC;EACE,YAAA;EACA,0BAAA;EACI,sBAAA;CrB6vGP;AqB3vGC;;;EAGE,YAAA;EACA,0BAAA;EACI,sBAAA;CrB6vGP;AqB3vGG;;;;;;;;;EAGE,YAAA;EACA,0BAAA;EACI,sBAAA;CrBmwGT;AqBhwGC;;;EAGE,uBAAA;CrBkwGH;AqB7vGG;;;;;;;;;EAGE,0BAAA;EACI,sBAAA;CrBqwGT;AoBjuGD;EC/BI,eAAA;EACA,uBAAA;CrBmwGH;AoB5tGD;EACE,eAAA;EACA,oBAAA;EACA,iBAAA;CpB8tGD;AoB5tGC;;;;;EAKE,8BAAA;EfnCF,yBAAA;EACQ,iBAAA;CLkwGT;AoB7tGC;;;;EAIE,0BAAA;CpB+tGH;AoB7tGC;;EAEE,eAAA;EACA,2BAAA;EACA,8BAAA;CpB+tGH;AoB3tGG;;;;EAEE,eAAA;EACA,sBAAA;CpB+tGL;AoBttGD;;ECxEE,mBAAA;EACA,gBAAA;EACA,uBAAA;EACA,mBAAA;CrBkyGD;AoBztGD;;EC5EE,kBAAA;EACA,gBAAA;EACA,iBAAA;EACA,mBAAA;CrByyGD;AoB5tGD;;EChFE,iBAAA;EACA,gBAAA;EACA,iBAAA;EACA,mBAAA;CrBgzGD;AoB3tGD;EACE,eAAA;EACA,YAAA;CpB6tGD;AoBztGD;EACE,gBAAA;CpB2tGD;AoBptGC;;;EACE,YAAA;CpBwtGH;AuBl3GD;EACE,WAAA;ElBoLA,yCAAA;EACK,oCAAA;EACG,iCAAA;CLisGT;AuBr3GC;EACE,WAAA;CvBu3GH;AuBn3GD;EACE,cAAA;CvBq3GD;AuBn3GC;EAAY,eAAA;CvBs3Gb;AuBr3GC;EAAY,mBAAA;CvBw3Gb;AuBv3GC;EAAY,yBAAA;CvB03Gb;AuBv3GD;EACE,mBAAA;EACA,UAAA;EACA,iBAAA;ElBuKA,gDAAA;EACQ,2CAAA;KAAA,wCAAA;EAOR,mCAAA;EACQ,8BAAA;KAAA,2BAAA;EAGR,yCAAA;EACQ,oCAAA;KAAA,iCAAA;CL2sGT;AwBr5GD;EACE,sBAAA;EACA,SAAA;EACA,UAAA;EACA,iBAAA;EACA,uBAAA;EACA,uBAAA;EACA,yBAAA;EACA,oCAAA;EACA,mCAAA;CxBu5GD;AwBn5GD;;EAEE,mBAAA;CxBq5GD;AwBj5GD;EACE,WAAA;CxBm5GD;AwB/4GD;EACE,mBAAA;EACA,UAAA;EACA,QAAA;EACA,cAAA;EACA,cAAA;EACA,YAAA;EACA,iBAAA;EACA,eAAA;EACA,gBAAA;EACA,iBAAA;EACA,gBAAA;EACA,iBAAA;EACA,uBAAA;EACA,uBAAA;EACA,sCAAA;EACA,mBAAA;EnBsBA,oDAAA;EACQ,4CAAA;EmBrBR,qCAAA;UAAA,6BAAA;CxBk5GD;AwB74GC;EACE,SAAA;EACA,WAAA;CxB+4GH;AwBx6GD;ECzBE,YAAA;EACA,cAAA;EACA,iBAAA;EACA,0BAAA;CzBo8GD;AwB96GD;EAmCI,eAAA;EACA,kBAAA;EACA,YAAA;EACA,oBAAA;EACA,wBAAA;EACA,eAAA;EACA,oBAAA;CxB84GH;AwBx4GC;;EAEE,sBAAA;EACA,eAAA;EACA,0BAAA;CxB04GH;AwBp4GC;;;EAGE,YAAA;EACA,sBAAA;EACA,WAAA;EACA,0BAAA;CxBs4GH;AwB73GC;;;EAGE,eAAA;CxB+3GH;AwB33GC;;EAEE,sBAAA;EACA,8BAAA;EACA,uBAAA;EE3GF,oEAAA;EF6GE,oBAAA;CxB63GH;AwBx3GD;EAGI,eAAA;CxBw3GH;AwB33GD;EAQI,WAAA;CxBs3GH;AwB92GD;EACE,WAAA;EACA,SAAA;CxBg3GD;AwBx2GD;EACE,QAAA;EACA,YAAA;CxB02GD;AwBt2GD;EACE,eAAA;EACA,kBAAA;EACA,gBAAA;EACA,wBAAA;EACA,eAAA;EACA,oBAAA;CxBw2GD;AwBp2GD;EACE,gBAAA;EACA,QAAA;EACA,SAAA;EACA,UAAA;EACA,OAAA;EACA,aAAA;CxBs2GD;AwBl2GD;EACE,SAAA;EACA,WAAA;CxBo2GD;AwB51GD;;EAII,cAAA;EACA,0BAAA;EACA,4BAAA;EACA,YAAA;CxB41GH;AwBn2GD;;EAWI,UAAA;EACA,aAAA;EACA,mBAAA;CxB41GH;AwBv0GD;EAXE;IApEA,WAAA;IACA,SAAA;GxB05GC;EwBv1GD;IA1DA,QAAA;IACA,YAAA;GxBo5GC;CACF;A2BpiHD;;EAEE,mBAAA;EACA,sBAAA;EACA,uBAAA;C3BsiHD;A2B1iHD;;EAMI,mBAAA;EACA,YAAA;C3BwiHH;A2BtiHG;;;;;;;;EAIE,WAAA;C3B4iHL;A2BtiHD;;;;EAKI,kBAAA;C3BuiHH;A2BliHD;EACE,kBAAA;C3BoiHD;A2BriHD;;;EAOI,YAAA;C3BmiHH;A2B1iHD;;;EAYI,iBAAA;C3BmiHH;A2B/hHD;EACE,iBAAA;C3BiiHD;A2B7hHD;EACE,eAAA;C3B+hHD;A2B9hHC;EClDA,8BAAA;EACG,2BAAA;C5BmlHJ;A2B7hHD;;EC/CE,6BAAA;EACG,0BAAA;C5BglHJ;A2B5hHD;EACE,YAAA;C3B8hHD;A2B5hHD;EACE,iBAAA;C3B8hHD;A2B5hHD;;ECnEE,8BAAA;EACG,2BAAA;C5BmmHJ;A2B3hHD;ECjEE,6BAAA;EACG,0BAAA;C5B+lHJ;A2B1hHD;;EAEE,WAAA;C3B4hHD;A2B3gHD;EACE,kBAAA;EACA,mBAAA;C3B6gHD;A2B3gHD;EACE,mBAAA;EACA,oBAAA;C3B6gHD;A2BxgHD;EtB/CE,yDAAA;EACQ,iDAAA;CL0jHT;A2BxgHC;EtBnDA,yBAAA;EACQ,iBAAA;CL8jHT;A2BrgHD;EACE,eAAA;C3BugHD;A2BpgHD;EACE,wBAAA;EACA,uBAAA;C3BsgHD;A2BngHD;EACE,wBAAA;C3BqgHD;A2B9/GD;;;EAII,eAAA;EACA,YAAA;EACA,YAAA;EACA,gBAAA;C3B+/GH;A2BtgHD;EAcM,YAAA;C3B2/GL;A2BzgHD;;;;EAsBI,iBAAA;EACA,eAAA;C3By/GH;A2Bp/GC;EACE,iBAAA;C3Bs/GH;A2Bp/GC;EC3KA,6BAAA;EACC,4BAAA;EAOD,8BAAA;EACC,6BAAA;C5B4pHF;A2Bt/GC;EC/KA,2BAAA;EACC,0BAAA;EAOD,gCAAA;EACC,+BAAA;C5BkqHF;A2Bv/GD;EACE,iBAAA;C3By/GD;A2Bv/GD;;EC/KE,8BAAA;EACC,6BAAA;C5B0qHF;A2Bt/GD;EC7LE,2BAAA;EACC,0BAAA;C5BsrHF;A2Bl/GD;EACE,eAAA;EACA,YAAA;EACA,oBAAA;EACA,0BAAA;C3Bo/GD;A2Bx/GD;;EAOI,YAAA;EACA,oBAAA;EACA,UAAA;C3Bq/GH;A2B9/GD;EAYI,YAAA;C3Bq/GH;A2BjgHD;EAgBI,WAAA;C3Bo/GH;A2Bn+GD;;;;EAKM,mBAAA;EACA,uBAAA;EACA,qBAAA;C3Bo+GL;A6B9sHD;EACE,mBAAA;EACA,eAAA;EACA,0BAAA;C7BgtHD;A6B7sHC;EACE,YAAA;EACA,gBAAA;EACA,iBAAA;C7B+sHH;A6BxtHD;EAeI,mBAAA;EACA,WAAA;EAKA,YAAA;EAEA,YAAA;EACA,iBAAA;C7BusHH;A6BrsHG;EACE,WAAA;C7BusHL;A6B7rHD;;;EV0BE,aAAA;EACA,mBAAA;EACA,gBAAA;EACA,uBAAA;EACA,mBAAA;CnBwqHD;AmBtqHC;;;EACE,aAAA;EACA,kBAAA;CnB0qHH;AmBvqHC;;;;;;EAEE,aAAA;CnB6qHH;A6B/sHD;;;EVqBE,aAAA;EACA,kBAAA;EACA,gBAAA;EACA,iBAAA;EACA,mBAAA;CnB+rHD;AmB7rHC;;;EACE,aAAA;EACA,kBAAA;CnBisHH;AmB9rHC;;;;;;EAEE,aAAA;CnBosHH;A6B7tHD;;;EAGE,oBAAA;C7B+tHD;A6B7tHC;;;EACE,iBAAA;C7BiuHH;A6B7tHD;;EAEE,UAAA;EACA,oBAAA;EACA,uBAAA;C7B+tHD;A6B1tHD;EACE,kBAAA;EACA,gBAAA;EACA,oBAAA;EACA,eAAA;EACA,eAAA;EACA,mBAAA;EACA,0BAAA;EACA,uBAAA;EACA,mBAAA;C7B4tHD;A6BztHC;EACE,kBAAA;EACA,gBAAA;EACA,mBAAA;C7B2tHH;A6BztHC;EACE,mBAAA;EACA,gBAAA;EACA,mBAAA;C7B2tHH;A6B/uHD;;EA0BI,cAAA;C7BytHH;A6BptHD;;;;;;;EDpGE,8BAAA;EACG,2BAAA;C5Bi0HJ;A6BrtHD;EACE,gBAAA;C7ButHD;A6BrtHD;;;;;;;EDxGE,6BAAA;EACG,0BAAA;C5Bs0HJ;A6BttHD;EACE,eAAA;C7BwtHD;A6BntHD;EACE,mBAAA;EAGA,aAAA;EACA,oBAAA;C7BmtHD;A6BxtHD;EAUI,mBAAA;C7BitHH;A6B3tHD;EAYM,kBAAA;C7BktHL;A6B/sHG;;;EAGE,WAAA;C7BitHL;A6B5sHC;;EAGI,mBAAA;C7B6sHL;A6B1sHC;;EAGI,WAAA;EACA,kBAAA;C7B2sHL;A8B12HD;EACE,iBAAA;EACA,gBAAA;EACA,iBAAA;C9B42HD;A8B/2HD;EAOI,mBAAA;EACA,eAAA;C9B22HH;A8Bn3HD;EAWM,mBAAA;EACA,eAAA;EACA,mBAAA;C9B22HL;A8B12HK;;EAEE,sBAAA;EACA,0BAAA;C9B42HP;A8Bv2HG;EACE,eAAA;C9By2HL;A8Bv2HK;;EAEE,eAAA;EACA,sBAAA;EACA,8BAAA;EACA,oBAAA;C9By2HP;A8Bl2HG;;;EAGE,0BAAA;EACA,sBAAA;C9Bo2HL;A8B74HD;ELHE,YAAA;EACA,cAAA;EACA,iBAAA;EACA,0BAAA;CzBm5HD;A8Bn5HD;EA0DI,gBAAA;C9B41HH;A8Bn1HD;EACE,8BAAA;C9Bq1HD;A8Bt1HD;EAGI,YAAA;EAEA,oBAAA;C9Bq1HH;A8B11HD;EASM,kBAAA;EACA,wBAAA;EACA,8BAAA;EACA,2BAAA;C9Bo1HL;A8Bn1HK;EACE,mCAAA;C9Bq1HP;A8B/0HK;;;EAGE,eAAA;EACA,uBAAA;EACA,uBAAA;EACA,iCAAA;EACA,gBAAA;C9Bi1HP;A8B50HC;EAqDA,YAAA;EA8BA,iBAAA;C9B6vHD;A8Bh1HC;EAwDE,YAAA;C9B2xHH;A8Bn1HC;EA0DI,mBAAA;EACA,mBAAA;C9B4xHL;A8Bv1HC;EAgEE,UAAA;EACA,WAAA;C9B0xHH;A8B9wHD;EA0DA;IAjEM,oBAAA;IACA,UAAA;G9ByxHH;E8BztHH;IA9DQ,iBAAA;G9B0xHL;CACF;A8Bp2HC;EAuFE,gBAAA;EACA,mBAAA;C9BgxHH;A8Bx2HC;;;EA8FE,uBAAA;C9B+wHH;A8BjwHD;EA2BA;IApCM,8BAAA;IACA,2BAAA;G9B8wHH;E8B3uHH;;;IA9BM,0BAAA;G9B8wHH;CACF;A8B/2HD;EAEI,YAAA;C9Bg3HH;A8Bl3HD;EAMM,mBAAA;C9B+2HL;A8Br3HD;EASM,iBAAA;C9B+2HL;A8B12HK;;;EAGE,YAAA;EACA,0BAAA;C9B42HP;A8Bp2HD;EAEI,YAAA;C9Bq2HH;A8Bv2HD;EAIM,gBAAA;EACA,eAAA;C9Bs2HL;A8B11HD;EACE,YAAA;C9B41HD;A8B71HD;EAII,YAAA;C9B41HH;A8Bh2HD;EAMM,mBAAA;EACA,mBAAA;C9B61HL;A8Bp2HD;EAYI,UAAA;EACA,WAAA;C9B21HH;A8B/0HD;EA0DA;IAjEM,oBAAA;IACA,UAAA;G9B01HH;E8B1xHH;IA9DQ,iBAAA;G9B21HL;CACF;A8Bn1HD;EACE,iBAAA;C9Bq1HD;A8Bt1HD;EAKI,gBAAA;EACA,mBAAA;C9Bo1HH;A8B11HD;;;EAYI,uBAAA;C9Bm1HH;A8Br0HD;EA2BA;IApCM,8BAAA;IACA,2BAAA;G9Bk1HH;E8B/yHH;;;IA9BM,0BAAA;G9Bk1HH;CACF;A8Bz0HD;EAEI,cAAA;C9B00HH;A8B50HD;EAKI,eAAA;C9B00HH;A8Bj0HD;EAEE,iBAAA;EF3OA,2BAAA;EACC,0BAAA;C5B8iIF;A+BxiID;EACE,mBAAA;EACA,iBAAA;EACA,oBAAA;EACA,8BAAA;C/B0iID;A+BliID;EA8nBA;IAhoBI,mBAAA;G/BwiID;CACF;A+BzhID;EAgnBA;IAlnBI,YAAA;G/B+hID;CACF;A+BjhID;EACE,oBAAA;EACA,oBAAA;EACA,mBAAA;EACA,kCAAA;EACA,2DAAA;UAAA,mDAAA;EAEA,kCAAA;C/BkhID;A+BhhIC;EACE,iBAAA;C/BkhIH;A+Bt/HD;EA6jBA;IArlBI,YAAA;IACA,cAAA;IACA,yBAAA;YAAA,iBAAA;G/BkhID;E+BhhIC;IACE,0BAAA;IACA,wBAAA;IACA,kBAAA;IACA,6BAAA;G/BkhIH;E+B/gIC;IACE,oBAAA;G/BihIH;E+B5gIC;;;IAGE,gBAAA;IACA,iBAAA;G/B8gIH;CACF;A+B1gID;;EAGI,kBAAA;C/B2gIH;A+BtgIC;EAmjBF;;IArjBM,kBAAA;G/B6gIH;CACF;A+BpgID;;;;EAII,oBAAA;EACA,mBAAA;C/BsgIH;A+BhgIC;EAgiBF;;;;IAniBM,gBAAA;IACA,eAAA;G/B0gIH;CACF;A+B9/HD;EACE,cAAA;EACA,sBAAA;C/BggID;A+B3/HD;EA8gBA;IAhhBI,iBAAA;G/BigID;CACF;A+B7/HD;;EAEE,gBAAA;EACA,SAAA;EACA,QAAA;EACA,cAAA;C/B+/HD;A+Bz/HD;EAggBA;;IAlgBI,iBAAA;G/BggID;CACF;A+B9/HD;EACE,OAAA;EACA,sBAAA;C/BggID;A+B9/HD;EACE,UAAA;EACA,iBAAA;EACA,sBAAA;C/BggID;A+B1/HD;EACE,YAAA;EACA,mBAAA;EACA,gBAAA;EACA,kBAAA;EACA,aAAA;C/B4/HD;A+B1/HC;;EAEE,sBAAA;C/B4/HH;A+BrgID;EAaI,eAAA;C/B2/HH;A+Bl/HD;EALI;;IAEE,mBAAA;G/B0/HH;CACF;A+Bh/HD;EACE,mBAAA;EACA,aAAA;EACA,mBAAA;EACA,kBAAA;EC9LA,gBAAA;EACA,mBAAA;ED+LA,8BAAA;EACA,uBAAA;EACA,8BAAA;EACA,mBAAA;C/Bm/HD;A+B/+HC;EACE,WAAA;C/Bi/HH;A+B//HD;EAmBI,eAAA;EACA,YAAA;EACA,YAAA;EACA,mBAAA;C/B++HH;A+BrgID;EAyBI,gBAAA;C/B++HH;A+Bz+HD;EAqbA;IAvbI,cAAA;G/B++HD;CACF;A+Bt+HD;EACE,oBAAA;C/Bw+HD;A+Bz+HD;EAII,kBAAA;EACA,qBAAA;EACA,kBAAA;C/Bw+HH;A+B58HC;EA2YF;IAjaM,iBAAA;IACA,YAAA;IACA,YAAA;IACA,cAAA;IACA,8BAAA;IACA,UAAA;IACA,yBAAA;YAAA,iBAAA;G/Bs+HH;E+B3kHH;;IAxZQ,2BAAA;G/Bu+HL;E+B/kHH;IArZQ,kBAAA;G/Bu+HL;E+Bt+HK;;IAEE,uBAAA;G/Bw+HP;CACF;A+Bt9HD;EA+XA;IA1YI,YAAA;IACA,UAAA;G/Bq+HD;E+B5lHH;IAtYM,YAAA;G/Bq+HH;E+B/lHH;IApYQ,kBAAA;IACA,qBAAA;G/Bs+HL;CACF;A+B39HD;EACE,mBAAA;EACA,oBAAA;EACA,mBAAA;EACA,kCAAA;EACA,qCAAA;E1B9NA,6FAAA;EACQ,qFAAA;E2B/DR,gBAAA;EACA,mBAAA;ChC4vID;AkBtuHD;EAwEA;IAtIM,sBAAA;IACA,iBAAA;IACA,uBAAA;GlBwyHH;EkBpqHH;IA/HM,sBAAA;IACA,YAAA;IACA,uBAAA;GlBsyHH;EkBzqHH;IAxHM,sBAAA;GlBoyHH;EkB5qHH;IApHM,sBAAA;IACA,uBAAA;GlBmyHH;EkBhrHH;;;IA9GQ,YAAA;GlBmyHL;EkBrrHH;IAxGM,YAAA;GlBgyHH;EkBxrHH;IApGM,iBAAA;IACA,uBAAA;GlB+xHH;EkB5rHH;;IA5FM,sBAAA;IACA,cAAA;IACA,iBAAA;IACA,uBAAA;GlB4xHH;EkBnsHH;;IAtFQ,gBAAA;GlB6xHL;EkBvsHH;;IAjFM,mBAAA;IACA,eAAA;GlB4xHH;EkB5sHH;IA3EM,OAAA;GlB0xHH;CACF;A+BpgIC;EAmWF;IAzWM,mBAAA;G/B8gIH;E+B5gIG;IACE,iBAAA;G/B8gIL;CACF;A+B7/HD;EAoVA;IA5VI,YAAA;IACA,UAAA;IACA,eAAA;IACA,gBAAA;IACA,eAAA;IACA,kBAAA;I1BzPF,yBAAA;IACQ,iBAAA;GLmwIP;CACF;A+BngID;EACE,cAAA;EHpUA,2BAAA;EACC,0BAAA;C5B00IF;A+BngID;EACE,iBAAA;EHzUA,6BAAA;EACC,4BAAA;EAOD,8BAAA;EACC,6BAAA;C5By0IF;A+B//HD;EChVE,gBAAA;EACA,mBAAA;ChCk1ID;A+BhgIC;ECnVA,iBAAA;EACA,oBAAA;ChCs1ID;A+BjgIC;ECtVA,iBAAA;EACA,oBAAA;ChC01ID;A+B3/HD;EChWE,iBAAA;EACA,oBAAA;ChC81ID;A+Bv/HD;EAsSA;IA1SI,YAAA;IACA,kBAAA;IACA,mBAAA;G/B+/HD;CACF;A+Bl+HD;EAhBE;IExWA,uBAAA;GjC81IC;E+Br/HD;IE5WA,wBAAA;IF8WE,oBAAA;G/Bu/HD;E+Bz/HD;IAKI,gBAAA;G/Bu/HH;CACF;A+B9+HD;EACE,0BAAA;EACA,sBAAA;C/Bg/HD;A+Bl/HD;EAKI,YAAA;C/Bg/HH;A+B/+HG;;EAEE,eAAA;EACA,8BAAA;C/Bi/HL;A+B1/HD;EAcI,YAAA;C/B++HH;A+B7/HD;EAmBM,YAAA;C/B6+HL;A+B3+HK;;EAEE,YAAA;EACA,8BAAA;C/B6+HP;A+Bz+HK;;;EAGE,YAAA;EACA,0BAAA;C/B2+HP;A+Bv+HK;;;EAGE,YAAA;EACA,8BAAA;C/By+HP;A+BjhID;EA8CI,mBAAA;C/Bs+HH;A+Br+HG;;EAEE,uBAAA;C/Bu+HL;A+BxhID;EAoDM,uBAAA;C/Bu+HL;A+B3hID;;EA0DI,sBAAA;C/Bq+HH;A+B99HK;;;EAGE,0BAAA;EACA,YAAA;C/Bg+HP;A+B/7HC;EAoKF;IA7LU,YAAA;G/B49HP;E+B39HO;;IAEE,YAAA;IACA,8BAAA;G/B69HT;E+Bz9HO;;;IAGE,YAAA;IACA,0BAAA;G/B29HT;E+Bv9HO;;;IAGE,YAAA;IACA,8BAAA;G/By9HT;CACF;A+B3jID;EA8GI,YAAA;C/Bg9HH;A+B/8HG;EACE,YAAA;C/Bi9HL;A+BjkID;EAqHI,YAAA;C/B+8HH;A+B98HG;;EAEE,YAAA;C/Bg9HL;A+B58HK;;;;EAEE,YAAA;C/Bg9HP;A+Bx8HD;EACE,uBAAA;EACA,sBAAA;C/B08HD;A+B58HD;EAKI,eAAA;C/B08HH;A+Bz8HG;;EAEE,YAAA;EACA,8BAAA;C/B28HL;A+Bp9HD;EAcI,eAAA;C/By8HH;A+Bv9HD;EAmBM,eAAA;C/Bu8HL;A+Br8HK;;EAEE,YAAA;EACA,8BAAA;C/Bu8HP;A+Bn8HK;;;EAGE,YAAA;EACA,0BAAA;C/Bq8HP;A+Bj8HK;;;EAGE,YAAA;EACA,8BAAA;C/Bm8HP;A+B3+HD;EA+CI,mBAAA;C/B+7HH;A+B97HG;;EAEE,uBAAA;C/Bg8HL;A+Bl/HD;EAqDM,uBAAA;C/Bg8HL;A+Br/HD;;EA2DI,sBAAA;C/B87HH;A+Bx7HK;;;EAGE,0BAAA;EACA,YAAA;C/B07HP;A+Bn5HC;EAwBF;IAvDU,sBAAA;G/Bs7HP;E+B/3HH;IApDU,0BAAA;G/Bs7HP;E+Bl4HH;IAjDU,eAAA;G/Bs7HP;E+Br7HO;;IAEE,YAAA;IACA,8BAAA;G/Bu7HT;E+Bn7HO;;;IAGE,YAAA;IACA,0BAAA;G/Bq7HT;E+Bj7HO;;;IAGE,YAAA;IACA,8BAAA;G/Bm7HT;CACF;A+B3hID;EA+GI,eAAA;C/B+6HH;A+B96HG;EACE,YAAA;C/Bg7HL;A+BjiID;EAsHI,eAAA;C/B86HH;A+B76HG;;EAEE,YAAA;C/B+6HL;A+B36HK;;;;EAEE,YAAA;C/B+6HP;AkCzjJD;EACE,kBAAA;EACA,oBAAA;EACA,iBAAA;EACA,0BAAA;EACA,mBAAA;ClC2jJD;AkChkJD;EAQI,sBAAA;ClC2jJH;AkCnkJD;EAWM,kBAAA;EACA,eAAA;EACA,YAAA;ClC2jJL;AkCxkJD;EAkBI,eAAA;ClCyjJH;AmC7kJD;EACE,sBAAA;EACA,gBAAA;EACA,eAAA;EACA,mBAAA;CnC+kJD;AmCnlJD;EAOI,gBAAA;CnC+kJH;AmCtlJD;;EAUM,mBAAA;EACA,YAAA;EACA,kBAAA;EACA,wBAAA;EACA,sBAAA;EACA,eAAA;EACA,uBAAA;EACA,uBAAA;EACA,kBAAA;CnCglJL;AmC9kJG;;EAGI,eAAA;EPXN,+BAAA;EACG,4BAAA;C5B2lJJ;AmC7kJG;;EPvBF,gCAAA;EACG,6BAAA;C5BwmJJ;AmCxkJG;;;;EAEE,WAAA;EACA,eAAA;EACA,0BAAA;EACA,mBAAA;CnC4kJL;AmCtkJG;;;;;;EAGE,WAAA;EACA,YAAA;EACA,0BAAA;EACA,sBAAA;EACA,gBAAA;CnC2kJL;AmCloJD;;;;;;EAkEM,eAAA;EACA,uBAAA;EACA,mBAAA;EACA,oBAAA;CnCwkJL;AmC/jJD;;EC3EM,mBAAA;EACA,gBAAA;EACA,uBAAA;CpC8oJL;AoC5oJG;;ERKF,+BAAA;EACG,4BAAA;C5B2oJJ;AoC3oJG;;ERTF,gCAAA;EACG,6BAAA;C5BwpJJ;AmC1kJD;;EChFM,kBAAA;EACA,gBAAA;EACA,iBAAA;CpC8pJL;AoC5pJG;;ERKF,+BAAA;EACG,4BAAA;C5B2pJJ;AoC3pJG;;ERTF,gCAAA;EACG,6BAAA;C5BwqJJ;AqC3qJD;EACE,gBAAA;EACA,eAAA;EACA,iBAAA;EACA,mBAAA;CrC6qJD;AqCjrJD;EAOI,gBAAA;CrC6qJH;AqCprJD;;EAUM,sBAAA;EACA,kBAAA;EACA,uBAAA;EACA,uBAAA;EACA,oBAAA;CrC8qJL;AqC5rJD;;EAmBM,sBAAA;EACA,0BAAA;CrC6qJL;AqCjsJD;;EA2BM,aAAA;CrC0qJL;AqCrsJD;;EAkCM,YAAA;CrCuqJL;AqCzsJD;;;;EA2CM,eAAA;EACA,uBAAA;EACA,oBAAA;CrCoqJL;AsCltJD;EACE,gBAAA;EACA,wBAAA;EACA,eAAA;EACA,kBAAA;EACA,eAAA;EACA,YAAA;EACA,mBAAA;EACA,oBAAA;EACA,yBAAA;EACA,qBAAA;CtCotJD;AsChtJG;;EAEE,YAAA;EACA,sBAAA;EACA,gBAAA;CtCktJL;AsC7sJC;EACE,cAAA;CtC+sJH;AsC3sJC;EACE,mBAAA;EACA,UAAA;CtC6sJH;AsCtsJD;ECtCE,0BAAA;CvC+uJD;AuC5uJG;;EAEE,0BAAA;CvC8uJL;AsCzsJD;EC1CE,0BAAA;CvCsvJD;AuCnvJG;;EAEE,0BAAA;CvCqvJL;AsC5sJD;EC9CE,0BAAA;CvC6vJD;AuC1vJG;;EAEE,0BAAA;CvC4vJL;AsC/sJD;EClDE,0BAAA;CvCowJD;AuCjwJG;;EAEE,0BAAA;CvCmwJL;AsCltJD;ECtDE,0BAAA;CvC2wJD;AuCxwJG;;EAEE,0BAAA;CvC0wJL;AsCrtJD;EC1DE,0BAAA;CvCkxJD;AuC/wJG;;EAEE,0BAAA;CvCixJL;AwCnxJD;EACE,sBAAA;EACA,gBAAA;EACA,iBAAA;EACA,gBAAA;EACA,kBAAA;EACA,YAAA;EACA,eAAA;EACA,uBAAA;EACA,oBAAA;EACA,mBAAA;EACA,0BAAA;EACA,oBAAA;CxCqxJD;AwClxJC;EACE,cAAA;CxCoxJH;AwChxJC;EACE,mBAAA;EACA,UAAA;CxCkxJH;AwC/wJC;;EAEE,OAAA;EACA,iBAAA;CxCixJH;AwC5wJG;;EAEE,YAAA;EACA,sBAAA;EACA,gBAAA;CxC8wJL;AwCzwJC;;EAEE,eAAA;EACA,uBAAA;CxC2wJH;AwCxwJC;EACE,aAAA;CxC0wJH;AwCvwJC;EACE,kBAAA;CxCywJH;AwCtwJC;EACE,iBAAA;CxCwwJH;AyCl0JD;EACE,kBAAA;EACA,qBAAA;EACA,oBAAA;EACA,eAAA;EACA,0BAAA;CzCo0JD;AyCz0JD;;EASI,eAAA;CzCo0JH;AyC70JD;EAaI,oBAAA;EACA,gBAAA;EACA,iBAAA;CzCm0JH;AyCl1JD;EAmBI,0BAAA;CzCk0JH;AyC/zJC;;EAEE,mBAAA;EACA,mBAAA;EACA,oBAAA;CzCi0JH;AyC31JD;EA8BI,gBAAA;CzCg0JH;AyC9yJD;EACA;IAfI,kBAAA;IACA,qBAAA;GzCg0JD;EyC9zJC;;IAEE,mBAAA;IACA,oBAAA;GzCg0JH;EyCvzJH;;IAJM,gBAAA;GzC+zJH;CACF;A0C52JD;EACE,eAAA;EACA,aAAA;EACA,oBAAA;EACA,wBAAA;EACA,uBAAA;EACA,uBAAA;EACA,mBAAA;ErCiLA,4CAAA;EACK,uCAAA;EACG,oCAAA;CL8rJT;A0Cx3JD;;EAaI,kBAAA;EACA,mBAAA;C1C+2JH;A0C32JC;;;EAGE,sBAAA;C1C62JH;A0Cl4JD;EA0BI,aAAA;EACA,eAAA;C1C22JH;A2Cp4JD;EACE,cAAA;EACA,oBAAA;EACA,8BAAA;EACA,mBAAA;C3Cs4JD;A2C14JD;EAQI,cAAA;EAEA,eAAA;C3Co4JH;A2C94JD;EAeI,kBAAA;C3Ck4JH;A2Cj5JD;;EAqBI,iBAAA;C3Cg4JH;A2Cr5JD;EAyBI,gBAAA;C3C+3JH;A2Cv3JD;;EAEE,oBAAA;C3Cy3JD;A2C33JD;;EAMI,mBAAA;EACA,UAAA;EACA,aAAA;EACA,eAAA;C3Cy3JH;A2Cj3JD;ECvDE,0BAAA;EACA,sBAAA;EACA,eAAA;C5C26JD;A2Ct3JD;EClDI,0BAAA;C5C26JH;A2Cz3JD;EC/CI,eAAA;C5C26JH;A2Cx3JD;EC3DE,0BAAA;EACA,sBAAA;EACA,eAAA;C5Cs7JD;A2C73JD;ECtDI,0BAAA;C5Cs7JH;A2Ch4JD;ECnDI,eAAA;C5Cs7JH;A2C/3JD;EC/DE,0BAAA;EACA,sBAAA;EACA,eAAA;C5Ci8JD;A2Cp4JD;EC1DI,0BAAA;C5Ci8JH;A2Cv4JD;ECvDI,eAAA;C5Ci8JH;A2Ct4JD;ECnEE,0BAAA;EACA,sBAAA;EACA,eAAA;C5C48JD;A2C34JD;EC9DI,0BAAA;C5C48JH;A2C94JD;EC3DI,eAAA;C5C48JH;A6C98JD;EACE;IAAQ,4BAAA;G7Ci9JP;E6Ch9JD;IAAQ,yBAAA;G7Cm9JP;CACF;A6Ch9JD;EACE;IAAQ,4BAAA;G7Cm9JP;E6Cl9JD;IAAQ,yBAAA;G7Cq9JP;CACF;A6Cx9JD;EACE;IAAQ,4BAAA;G7Cm9JP;E6Cl9JD;IAAQ,yBAAA;G7Cq9JP;CACF;A6C98JD;EACE,iBAAA;EACA,aAAA;EACA,oBAAA;EACA,0BAAA;EACA,mBAAA;ExCsCA,uDAAA;EACQ,+CAAA;CL26JT;A6C78JD;EACE,YAAA;EACA,UAAA;EACA,aAAA;EACA,gBAAA;EACA,kBAAA;EACA,YAAA;EACA,mBAAA;EACA,0BAAA;ExCyBA,uDAAA;EACQ,+CAAA;EAyHR,oCAAA;EACK,+BAAA;EACG,4BAAA;CL+zJT;A6C18JD;;ECCI,8MAAA;EACA,yMAAA;EACA,sMAAA;EDAF,mCAAA;UAAA,2BAAA;C7C88JD;A6Cv8JD;;ExC5CE,2DAAA;EACK,sDAAA;EACG,mDAAA;CLu/JT;A6Cp8JD;EErEE,0BAAA;C/C4gKD;A+CzgKC;EDgDE,8MAAA;EACA,yMAAA;EACA,sMAAA;C9C49JH;A6Cx8JD;EEzEE,0BAAA;C/CohKD;A+CjhKC;EDgDE,8MAAA;EACA,yMAAA;EACA,sMAAA;C9Co+JH;A6C58JD;EE7EE,0BAAA;C/C4hKD;A+CzhKC;EDgDE,8MAAA;EACA,yMAAA;EACA,sMAAA;C9C4+JH;A6Ch9JD;EEjFE,0BAAA;C/CoiKD;A+CjiKC;EDgDE,8MAAA;EACA,yMAAA;EACA,sMAAA;C9Co/JH;AgD5iKD;EAEE,iBAAA;ChD6iKD;AgD3iKC;EACE,cAAA;ChD6iKH;AgDziKD;;EAEE,QAAA;EACA,iBAAA;ChD2iKD;AgDxiKD;EACE,eAAA;ChD0iKD;AgDviKD;EACE,eAAA;ChDyiKD;AgDtiKC;EACE,gBAAA;ChDwiKH;AgDpiKD;;EAEE,mBAAA;ChDsiKD;AgDniKD;;EAEE,oBAAA;ChDqiKD;AgDliKD;;;EAGE,oBAAA;EACA,oBAAA;ChDoiKD;AgDjiKD;EACE,uBAAA;ChDmiKD;AgDhiKD;EACE,uBAAA;ChDkiKD;AgD9hKD;EACE,cAAA;EACA,mBAAA;ChDgiKD;AgD1hKD;EACE,gBAAA;EACA,iBAAA;ChD4hKD;AiDnlKD;EAEE,oBAAA;EACA,gBAAA;CjDolKD;AiD5kKD;EACE,mBAAA;EACA,eAAA;EACA,mBAAA;EAEA,oBAAA;EACA,uBAAA;EACA,uBAAA;CjD6kKD;AiD1kKC;ErB3BA,6BAAA;EACC,4BAAA;C5BwmKF;AiD3kKC;EACE,iBAAA;ErBvBF,gCAAA;EACC,+BAAA;C5BqmKF;AiDpkKD;;EAEE,YAAA;CjDskKD;AiDxkKD;;EAKI,YAAA;CjDukKH;AiDnkKC;;;;EAEE,sBAAA;EACA,YAAA;EACA,0BAAA;CjDukKH;AiDnkKD;EACE,YAAA;EACA,iBAAA;CjDqkKD;AiDhkKC;;;EAGE,0BAAA;EACA,eAAA;EACA,oBAAA;CjDkkKH;AiDvkKC;;;EASI,eAAA;CjDmkKL;AiD5kKC;;;EAYI,eAAA;CjDqkKL;AiDhkKC;;;EAGE,WAAA;EACA,YAAA;EACA,0BAAA;EACA,sBAAA;CjDkkKH;AiDxkKC;;;;;;;;;EAYI,eAAA;CjDukKL;AiDnlKC;;;EAeI,eAAA;CjDykKL;AkD3qKC;EACE,eAAA;EACA,0BAAA;ClD6qKH;AkD3qKG;;EAEE,eAAA;ClD6qKL;AkD/qKG;;EAKI,eAAA;ClD8qKP;AkD3qKK;;;;EAEE,eAAA;EACA,0BAAA;ClD+qKP;AkD7qKK;;;;;;EAGE,YAAA;EACA,0BAAA;EACA,sBAAA;ClDkrKP;AkDxsKC;EACE,eAAA;EACA,0BAAA;ClD0sKH;AkDxsKG;;EAEE,eAAA;ClD0sKL;AkD5sKG;;EAKI,eAAA;ClD2sKP;AkDxsKK;;;;EAEE,eAAA;EACA,0BAAA;ClD4sKP;AkD1sKK;;;;;;EAGE,YAAA;EACA,0BAAA;EACA,sBAAA;ClD+sKP;AkDruKC;EACE,eAAA;EACA,0BAAA;ClDuuKH;AkDruKG;;EAEE,eAAA;ClDuuKL;AkDzuKG;;EAKI,eAAA;ClDwuKP;AkDruKK;;;;EAEE,eAAA;EACA,0BAAA;ClDyuKP;AkDvuKK;;;;;;EAGE,YAAA;EACA,0BAAA;EACA,sBAAA;ClD4uKP;AkDlwKC;EACE,eAAA;EACA,0BAAA;ClDowKH;AkDlwKG;;EAEE,eAAA;ClDowKL;AkDtwKG;;EAKI,eAAA;ClDqwKP;AkDlwKK;;;;EAEE,eAAA;EACA,0BAAA;ClDswKP;AkDpwKK;;;;;;EAGE,YAAA;EACA,0BAAA;EACA,sBAAA;ClDywKP;AiDxqKD;EACE,cAAA;EACA,mBAAA;CjD0qKD;AiDxqKD;EACE,iBAAA;EACA,iBAAA;CjD0qKD;AmDpyKD;EACE,oBAAA;EACA,uBAAA;EACA,8BAAA;EACA,mBAAA;E9C0DA,kDAAA;EACQ,0CAAA;CL6uKT;AmDnyKD;EACE,cAAA;CnDqyKD;AmDhyKD;EACE,mBAAA;EACA,qCAAA;EvBpBA,6BAAA;EACC,4BAAA;C5BuzKF;AmDtyKD;EAMI,eAAA;CnDmyKH;AmD9xKD;EACE,cAAA;EACA,iBAAA;EACA,gBAAA;EACA,eAAA;CnDgyKD;AmDpyKD;;;;;EAWI,eAAA;CnDgyKH;AmD3xKD;EACE,mBAAA;EACA,0BAAA;EACA,2BAAA;EvBxCA,gCAAA;EACC,+BAAA;C5Bs0KF;AmDrxKD;;EAGI,iBAAA;CnDsxKH;AmDzxKD;;EAMM,oBAAA;EACA,iBAAA;CnDuxKL;AmDnxKG;;EAEI,cAAA;EvBvEN,6BAAA;EACC,4BAAA;C5B61KF;AmDjxKG;;EAEI,iBAAA;EvBvEN,gCAAA;EACC,+BAAA;C5B21KF;AmD1yKD;EvB1DE,2BAAA;EACC,0BAAA;C5Bu2KF;AmD7wKD;EAEI,oBAAA;CnD8wKH;AmD3wKD;EACE,oBAAA;CnD6wKD;AmDrwKD;;;EAII,iBAAA;CnDswKH;AmD1wKD;;;EAOM,mBAAA;EACA,oBAAA;CnDwwKL;AmDhxKD;;EvBzGE,6BAAA;EACC,4BAAA;C5B63KF;AmDrxKD;;;;EAmBQ,4BAAA;EACA,6BAAA;CnDwwKP;AmD5xKD;;;;;;;;EAwBU,4BAAA;CnD8wKT;AmDtyKD;;;;;;;;EA4BU,6BAAA;CnDoxKT;AmDhzKD;;EvBjGE,gCAAA;EACC,+BAAA;C5Bq5KF;AmDrzKD;;;;EAyCQ,+BAAA;EACA,gCAAA;CnDkxKP;AmD5zKD;;;;;;;;EA8CU,+BAAA;CnDwxKT;AmDt0KD;;;;;;;;EAkDU,gCAAA;CnD8xKT;AmDh1KD;;;;EA2DI,2BAAA;CnD2xKH;AmDt1KD;;EA+DI,cAAA;CnD2xKH;AmD11KD;;EAmEI,UAAA;CnD2xKH;AmD91KD;;;;;;;;;;;;EA0EU,eAAA;CnDkyKT;AmD52KD;;;;;;;;;;;;EA8EU,gBAAA;CnD4yKT;AmD13KD;;;;;;;;EAuFU,iBAAA;CnD6yKT;AmDp4KD;;;;;;;;EAgGU,iBAAA;CnD8yKT;AmD94KD;EAsGI,UAAA;EACA,iBAAA;CnD2yKH;AmDjyKD;EACE,oBAAA;CnDmyKD;AmDpyKD;EAKI,iBAAA;EACA,mBAAA;CnDkyKH;AmDxyKD;EASM,gBAAA;CnDkyKL;AmD3yKD;EAcI,iBAAA;CnDgyKH;AmD9yKD;;EAkBM,2BAAA;CnDgyKL;AmDlzKD;EAuBI,cAAA;CnD8xKH;AmDrzKD;EAyBM,8BAAA;CnD+xKL;AmDxxKD;EC1PE,mBAAA;CpDqhLD;AoDnhLC;EACE,eAAA;EACA,0BAAA;EACA,mBAAA;CpDqhLH;AoDxhLC;EAMI,uBAAA;CpDqhLL;AoD3hLC;EASI,eAAA;EACA,0BAAA;CpDqhLL;AoDlhLC;EAEI,0BAAA;CpDmhLL;AmDvyKD;EC7PE,sBAAA;CpDuiLD;AoDriLC;EACE,YAAA;EACA,0BAAA;EACA,sBAAA;CpDuiLH;AoD1iLC;EAMI,0BAAA;CpDuiLL;AoD7iLC;EASI,eAAA;EACA,uBAAA;CpDuiLL;AoDpiLC;EAEI,6BAAA;CpDqiLL;AmDtzKD;EChQE,sBAAA;CpDyjLD;AoDvjLC;EACE,eAAA;EACA,0BAAA;EACA,sBAAA;CpDyjLH;AoD5jLC;EAMI,0BAAA;CpDyjLL;AoD/jLC;EASI,eAAA;EACA,0BAAA;CpDyjLL;AoDtjLC;EAEI,6BAAA;CpDujLL;AmDr0KD;ECnQE,sBAAA;CpD2kLD;AoDzkLC;EACE,eAAA;EACA,0BAAA;EACA,sBAAA;CpD2kLH;AoD9kLC;EAMI,0BAAA;CpD2kLL;AoDjlLC;EASI,eAAA;EACA,0BAAA;CpD2kLL;AoDxkLC;EAEI,6BAAA;CpDykLL;AmDp1KD;ECtQE,sBAAA;CpD6lLD;AoD3lLC;EACE,eAAA;EACA,0BAAA;EACA,sBAAA;CpD6lLH;AoDhmLC;EAMI,0BAAA;CpD6lLL;AoDnmLC;EASI,eAAA;EACA,0BAAA;CpD6lLL;AoD1lLC;EAEI,6BAAA;CpD2lLL;AmDn2KD;ECzQE,sBAAA;CpD+mLD;AoD7mLC;EACE,eAAA;EACA,0BAAA;EACA,sBAAA;CpD+mLH;AoDlnLC;EAMI,0BAAA;CpD+mLL;AoDrnLC;EASI,eAAA;EACA,0BAAA;CpD+mLL;AoD5mLC;EAEI,6BAAA;CpD6mLL;AqD7nLD;EACE,mBAAA;EACA,eAAA;EACA,UAAA;EACA,WAAA;EACA,iBAAA;CrD+nLD;AqDpoLD;;;;;EAYI,mBAAA;EACA,OAAA;EACA,QAAA;EACA,UAAA;EACA,aAAA;EACA,YAAA;EACA,UAAA;CrD+nLH;AqD1nLD;EACE,uBAAA;CrD4nLD;AqDxnLD;EACE,oBAAA;CrD0nLD;AsDrpLD;EACE,iBAAA;EACA,cAAA;EACA,oBAAA;EACA,0BAAA;EACA,0BAAA;EACA,mBAAA;EjDwDA,wDAAA;EACQ,gDAAA;CLgmLT;AsD/pLD;EASI,mBAAA;EACA,kCAAA;CtDypLH;AsDppLD;EACE,cAAA;EACA,mBAAA;CtDspLD;AsDppLD;EACE,aAAA;EACA,mBAAA;CtDspLD;AuD5qLD;EACE,aAAA;EACA,gBAAA;EACA,kBAAA;EACA,eAAA;EACA,YAAA;EACA,0BAAA;EjCRA,aAAA;EAGA,0BAAA;CtBqrLD;AuD7qLC;;EAEE,YAAA;EACA,sBAAA;EACA,gBAAA;EjCfF,aAAA;EAGA,0BAAA;CtB6rLD;AuDzqLC;EACE,WAAA;EACA,gBAAA;EACA,wBAAA;EACA,UAAA;EACA,yBAAA;CvD2qLH;AwDhsLD;EACE,iBAAA;CxDksLD;AwD9rLD;EACE,cAAA;EACA,iBAAA;EACA,gBAAA;EACA,OAAA;EACA,SAAA;EACA,UAAA;EACA,QAAA;EACA,cAAA;EACA,kCAAA;EAIA,WAAA;CxD6rLD;AwD1rLC;EnD+GA,sCAAA;EACI,kCAAA;EACC,iCAAA;EACG,8BAAA;EAkER,oDAAA;EAEK,0CAAA;EACG,oCAAA;CL6gLT;AwDhsLC;EnD2GA,mCAAA;EACI,+BAAA;EACC,8BAAA;EACG,2BAAA;CLwlLT;AwDpsLD;EACE,mBAAA;EACA,iBAAA;CxDssLD;AwDlsLD;EACE,mBAAA;EACA,YAAA;EACA,aAAA;CxDosLD;AwDhsLD;EACE,mBAAA;EACA,uBAAA;EACA,uBAAA;EACA,qCAAA;EACA,mBAAA;EnDaA,iDAAA;EACQ,yCAAA;EmDZR,qCAAA;UAAA,6BAAA;EAEA,WAAA;CxDksLD;AwD9rLD;EACE,gBAAA;EACA,OAAA;EACA,SAAA;EACA,UAAA;EACA,QAAA;EACA,cAAA;EACA,uBAAA;CxDgsLD;AwD9rLC;ElCrEA,WAAA;EAGA,yBAAA;CtBowLD;AwDjsLC;ElCtEA,aAAA;EAGA,0BAAA;CtBwwLD;AwDhsLD;EACE,cAAA;EACA,iCAAA;CxDksLD;AwD9rLD;EACE,iBAAA;CxDgsLD;AwD5rLD;EACE,UAAA;EACA,wBAAA;CxD8rLD;AwDzrLD;EACE,mBAAA;EACA,cAAA;CxD2rLD;AwDvrLD;EACE,cAAA;EACA,kBAAA;EACA,8BAAA;CxDyrLD;AwD5rLD;EAQI,iBAAA;EACA,iBAAA;CxDurLH;AwDhsLD;EAaI,kBAAA;CxDsrLH;AwDnsLD;EAiBI,eAAA;CxDqrLH;AwDhrLD;EACE,mBAAA;EACA,aAAA;EACA,YAAA;EACA,aAAA;EACA,iBAAA;CxDkrLD;AwDhqLD;EAZE;IACE,aAAA;IACA,kBAAA;GxD+qLD;EwD7qLD;InDvEA,kDAAA;IACQ,0CAAA;GLuvLP;EwD5qLD;IAAY,aAAA;GxD+qLX;CACF;AwD1qLD;EAFE;IAAY,aAAA;GxDgrLX;CACF;AyD/zLD;EACE,mBAAA;EACA,cAAA;EACA,eAAA;ECRA,4DAAA;EAEA,mBAAA;EACA,oBAAA;EACA,uBAAA;EACA,iBAAA;EACA,wBAAA;EACA,iBAAA;EACA,kBAAA;EACA,sBAAA;EACA,kBAAA;EACA,qBAAA;EACA,oBAAA;EACA,mBAAA;EACA,qBAAA;EACA,kBAAA;EDHA,gBAAA;EnCVA,WAAA;EAGA,yBAAA;CtBs1LD;AyD30LC;EnCdA,aAAA;EAGA,0BAAA;CtB01LD;AyD90LC;EAAW,iBAAA;EAAmB,eAAA;CzDk1L/B;AyDj1LC;EAAW,iBAAA;EAAmB,eAAA;CzDq1L/B;AyDp1LC;EAAW,gBAAA;EAAmB,eAAA;CzDw1L/B;AyDv1LC;EAAW,kBAAA;EAAmB,eAAA;CzD21L/B;AyDv1LD;EACE,iBAAA;EACA,iBAAA;EACA,YAAA;EACA,mBAAA;EACA,uBAAA;EACA,mBAAA;CzDy1LD;AyDr1LD;EACE,mBAAA;EACA,SAAA;EACA,UAAA;EACA,0BAAA;EACA,oBAAA;CzDu1LD;AyDn1LC;EACE,UAAA;EACA,UAAA;EACA,kBAAA;EACA,wBAAA;EACA,uBAAA;CzDq1LH;AyDn1LC;EACE,UAAA;EACA,WAAA;EACA,oBAAA;EACA,wBAAA;EACA,uBAAA;CzDq1LH;AyDn1LC;EACE,UAAA;EACA,UAAA;EACA,oBAAA;EACA,wBAAA;EACA,uBAAA;CzDq1LH;AyDn1LC;EACE,SAAA;EACA,QAAA;EACA,iBAAA;EACA,4BAAA;EACA,yBAAA;CzDq1LH;AyDn1LC;EACE,SAAA;EACA,SAAA;EACA,iBAAA;EACA,4BAAA;EACA,wBAAA;CzDq1LH;AyDn1LC;EACE,OAAA;EACA,UAAA;EACA,kBAAA;EACA,wBAAA;EACA,0BAAA;CzDq1LH;AyDn1LC;EACE,OAAA;EACA,WAAA;EACA,iBAAA;EACA,wBAAA;EACA,0BAAA;CzDq1LH;AyDn1LC;EACE,OAAA;EACA,UAAA;EACA,iBAAA;EACA,wBAAA;EACA,0BAAA;CzDq1LH;A2Dl7LD;EACE,mBAAA;EACA,OAAA;EACA,QAAA;EACA,cAAA;EACA,cAAA;EACA,iBAAA;EACA,aAAA;EDXA,4DAAA;EAEA,mBAAA;EACA,oBAAA;EACA,uBAAA;EACA,iBAAA;EACA,wBAAA;EACA,iBAAA;EACA,kBAAA;EACA,sBAAA;EACA,kBAAA;EACA,qBAAA;EACA,oBAAA;EACA,mBAAA;EACA,qBAAA;EACA,kBAAA;ECAA,gBAAA;EAEA,uBAAA;EACA,qCAAA;UAAA,6BAAA;EACA,uBAAA;EACA,qCAAA;EACA,mBAAA;EtD8CA,kDAAA;EACQ,0CAAA;CLk5LT;A2D77LC;EAAY,kBAAA;C3Dg8Lb;A2D/7LC;EAAY,kBAAA;C3Dk8Lb;A2Dj8LC;EAAY,iBAAA;C3Do8Lb;A2Dn8LC;EAAY,mBAAA;C3Ds8Lb;A2Dn8LD;EACE,UAAA;EACA,kBAAA;EACA,gBAAA;EACA,0BAAA;EACA,iCAAA;EACA,2BAAA;C3Dq8LD;A2Dl8LD;EACE,kBAAA;C3Do8LD;A2D57LC;;EAEE,mBAAA;EACA,eAAA;EACA,SAAA;EACA,UAAA;EACA,0BAAA;EACA,oBAAA;C3D87LH;A2D37LD;EACE,mBAAA;C3D67LD;A2D37LD;EACE,mBAAA;EACA,YAAA;C3D67LD;A2Dz7LC;EACE,UAAA;EACA,mBAAA;EACA,uBAAA;EACA,0BAAA;EACA,sCAAA;EACA,cAAA;C3D27LH;A2D17LG;EACE,aAAA;EACA,YAAA;EACA,mBAAA;EACA,uBAAA;EACA,uBAAA;C3D47LL;A2Dz7LC;EACE,SAAA;EACA,YAAA;EACA,kBAAA;EACA,qBAAA;EACA,4BAAA;EACA,wCAAA;C3D27LH;A2D17LG;EACE,aAAA;EACA,UAAA;EACA,cAAA;EACA,qBAAA;EACA,yBAAA;C3D47LL;A2Dz7LC;EACE,UAAA;EACA,mBAAA;EACA,oBAAA;EACA,6BAAA;EACA,yCAAA;EACA,WAAA;C3D27LH;A2D17LG;EACE,aAAA;EACA,SAAA;EACA,mBAAA;EACA,oBAAA;EACA,0BAAA;C3D47LL;A2Dx7LC;EACE,SAAA;EACA,aAAA;EACA,kBAAA;EACA,sBAAA;EACA,2BAAA;EACA,uCAAA;C3D07LH;A2Dz7LG;EACE,aAAA;EACA,WAAA;EACA,sBAAA;EACA,wBAAA;EACA,cAAA;C3D27LL;A4DpjMD;EACE,mBAAA;C5DsjMD;A4DnjMD;EACE,mBAAA;EACA,iBAAA;EACA,YAAA;C5DqjMD;A4DxjMD;EAMI,cAAA;EACA,mBAAA;EvD6KF,0CAAA;EACK,qCAAA;EACG,kCAAA;CLy4LT;A4D/jMD;;EAcM,eAAA;C5DqjML;A4D3hMC;EA4NF;IvD3DE,uDAAA;IAEK,6CAAA;IACG,uCAAA;IA7JR,oCAAA;IAEQ,4BAAA;IA+GR,4BAAA;IAEQ,oBAAA;GL86LP;E4DzjMG;;IvDmHJ,2CAAA;IACQ,mCAAA;IuDjHF,QAAA;G5D4jML;E4D1jMG;;IvD8GJ,4CAAA;IACQ,oCAAA;IuD5GF,QAAA;G5D6jML;E4D3jMG;;;IvDyGJ,wCAAA;IACQ,gCAAA;IuDtGF,QAAA;G5D8jML;CACF;A4DpmMD;;;EA6CI,eAAA;C5D4jMH;A4DzmMD;EAiDI,QAAA;C5D2jMH;A4D5mMD;;EAsDI,mBAAA;EACA,OAAA;EACA,YAAA;C5D0jMH;A4DlnMD;EA4DI,WAAA;C5DyjMH;A4DrnMD;EA+DI,YAAA;C5DyjMH;A4DxnMD;;EAmEI,QAAA;C5DyjMH;A4D5nMD;EAuEI,YAAA;C5DwjMH;A4D/nMD;EA0EI,WAAA;C5DwjMH;A4DhjMD;EACE,mBAAA;EACA,OAAA;EACA,QAAA;EACA,UAAA;EACA,WAAA;EtC9FA,aAAA;EAGA,0BAAA;EsC6FA,gBAAA;EACA,YAAA;EACA,mBAAA;EACA,0CAAA;EACA,mCAAA;C5DmjMD;A4D9iMC;EdnGE,mGAAA;EACA,8FAAA;EACA,qHAAA;EAAA,+FAAA;EACA,4BAAA;EACA,uHAAA;C9CopMH;A4DljMC;EACE,WAAA;EACA,SAAA;EdxGA,mGAAA;EACA,8FAAA;EACA,qHAAA;EAAA,+FAAA;EACA,4BAAA;EACA,uHAAA;C9C6pMH;A4DpjMC;;EAEE,WAAA;EACA,YAAA;EACA,sBAAA;EtCvHF,aAAA;EAGA,0BAAA;CtB4qMD;A4DtlMD;;;;EAuCI,mBAAA;EACA,SAAA;EACA,kBAAA;EACA,WAAA;EACA,sBAAA;C5DqjMH;A4DhmMD;;EA+CI,UAAA;EACA,mBAAA;C5DqjMH;A4DrmMD;;EAoDI,WAAA;EACA,oBAAA;C5DqjMH;A4D1mMD;;EAyDI,YAAA;EACA,aAAA;EACA,eAAA;EACA,mBAAA;C5DqjMH;A4DhjMG;EACE,iBAAA;C5DkjML;A4D9iMG;EACE,iBAAA;C5DgjML;A4DtiMD;EACE,mBAAA;EACA,aAAA;EACA,UAAA;EACA,YAAA;EACA,WAAA;EACA,kBAAA;EACA,gBAAA;EACA,iBAAA;EACA,mBAAA;C5DwiMD;A4DjjMD;EAYI,sBAAA;EACA,YAAA;EACA,aAAA;EACA,YAAA;EACA,oBAAA;EACA,uBAAA;EACA,oBAAA;EACA,gBAAA;EAWA,0BAAA;EACA,mCAAA;C5D8hMH;A4D7jMD;EAkCI,UAAA;EACA,YAAA;EACA,aAAA;EACA,uBAAA;C5D8hMH;A4DvhMD;EACE,mBAAA;EACA,UAAA;EACA,WAAA;EACA,aAAA;EACA,YAAA;EACA,kBAAA;EACA,qBAAA;EACA,YAAA;EACA,mBAAA;EACA,0CAAA;C5DyhMD;A4DxhMC;EACE,kBAAA;C5D0hMH;A4Dj/LD;EAhCE;;;;IAKI,YAAA;IACA,aAAA;IACA,kBAAA;IACA,gBAAA;G5DmhMH;E4D3hMD;;IAYI,mBAAA;G5DmhMH;E4D/hMD;;IAgBI,oBAAA;G5DmhMH;E4D9gMD;IACE,UAAA;IACA,WAAA;IACA,qBAAA;G5DghMD;E4D5gMD;IACE,aAAA;G5D8gMD;CACF;A6D7wMC;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;EAEE,aAAA;EACA,eAAA;C7D6yMH;A6D3yMC;;;;;;;;;;;;;;;;EACE,YAAA;C7D4zMH;AiCp0MD;E6BRE,eAAA;EACA,kBAAA;EACA,mBAAA;C9D+0MD;AiCt0MD;EACE,wBAAA;CjCw0MD;AiCt0MD;EACE,uBAAA;CjCw0MD;AiCh0MD;EACE,yBAAA;CjCk0MD;AiCh0MD;EACE,0BAAA;CjCk0MD;AiCh0MD;EACE,mBAAA;CjCk0MD;AiCh0MD;E8BzBE,YAAA;EACA,mBAAA;EACA,kBAAA;EACA,8BAAA;EACA,UAAA;C/D41MD;AiC9zMD;EACE,yBAAA;CjCg0MD;AiCzzMD;EACE,gBAAA;CjC2zMD;AgE51MD;EACE,oBAAA;ChE81MD;AgEx1MD;;;;ECdE,yBAAA;CjE42MD;AgEv1MD;;;;;;;;;;;;EAYE,yBAAA;ChEy1MD;AgEl1MD;EA6IA;IC7LE,0BAAA;GjEs4MC;EiEr4MD;IAAU,0BAAA;GjEw4MT;EiEv4MD;IAAU,8BAAA;GjE04MT;EiEz4MD;;IACU,+BAAA;GjE44MT;CACF;AgE51MD;EAwIA;IA1II,0BAAA;GhEk2MD;CACF;AgE51MD;EAmIA;IArII,2BAAA;GhEk2MD;CACF;AgE51MD;EA8HA;IAhII,iCAAA;GhEk2MD;CACF;AgE31MD;EAwHA;IC7LE,0BAAA;GjEo6MC;EiEn6MD;IAAU,0BAAA;GjEs6MT;EiEr6MD;IAAU,8BAAA;GjEw6MT;EiEv6MD;;IACU,+BAAA;GjE06MT;CACF;AgEr2MD;EAmHA;IArHI,0BAAA;GhE22MD;CACF;AgEr2MD;EA8GA;IAhHI,2BAAA;GhE22MD;CACF;AgEr2MD;EAyGA;IA3GI,iCAAA;GhE22MD;CACF;AgEp2MD;EAmGA;IC7LE,0BAAA;GjEk8MC;EiEj8MD;IAAU,0BAAA;GjEo8MT;EiEn8MD;IAAU,8BAAA;GjEs8MT;EiEr8MD;;IACU,+BAAA;GjEw8MT;CACF;AgE92MD;EA8FA;IAhGI,0BAAA;GhEo3MD;CACF;AgE92MD;EAyFA;IA3FI,2BAAA;GhEo3MD;CACF;AgE92MD;EAoFA;IAtFI,iCAAA;GhEo3MD;CACF;AgE72MD;EA8EA;IC7LE,0BAAA;GjEg+MC;EiE/9MD;IAAU,0BAAA;GjEk+MT;EiEj+MD;IAAU,8BAAA;GjEo+MT;EiEn+MD;;IACU,+BAAA;GjEs+MT;CACF;AgEv3MD;EAyEA;IA3EI,0BAAA;GhE63MD;CACF;AgEv3MD;EAoEA;IAtEI,2BAAA;GhE63MD;CACF;AgEv3MD;EA+DA;IAjEI,iCAAA;GhE63MD;CACF;AgEt3MD;EAyDA;ICrLE,yBAAA;GjEs/MC;CACF;AgEt3MD;EAoDA;ICrLE,yBAAA;GjE2/MC;CACF;AgEt3MD;EA+CA;ICrLE,yBAAA;GjEggNC;CACF;AgEt3MD;EA0CA;ICrLE,yBAAA;GjEqgNC;CACF;AgEn3MD;ECnJE,yBAAA;CjEygND;AgEh3MD;EA4BA;IC7LE,0BAAA;GjEqhNC;EiEphND;IAAU,0BAAA;GjEuhNT;EiEthND;IAAU,8BAAA;GjEyhNT;EiExhND;;IACU,+BAAA;GjE2hNT;CACF;AgE93MD;EACE,yBAAA;ChEg4MD;AgE33MD;EAqBA;IAvBI,0BAAA;GhEi4MD;CACF;AgE/3MD;EACE,yBAAA;ChEi4MD;AgE53MD;EAcA;IAhBI,2BAAA;GhEk4MD;CACF;AgEh4MD;EACE,yBAAA;ChEk4MD;AgE73MD;EAOA;IATI,iCAAA;GhEm4MD;CACF;AgE53MD;EACA;ICrLE,yBAAA;GjEojNC;CACF","file":"bootstrap.css","sourcesContent":["/*!\n * Bootstrap v3.3.7 (http://getbootstrap.com)\n * Copyright 2011-2016 Twitter, Inc.\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)\n */\n/*! normalize.css v3.0.3 | MIT License | github.com/necolas/normalize.css */\nhtml {\n font-family: sans-serif;\n -ms-text-size-adjust: 100%;\n -webkit-text-size-adjust: 100%;\n}\nbody {\n margin: 0;\n}\narticle,\naside,\ndetails,\nfigcaption,\nfigure,\nfooter,\nheader,\nhgroup,\nmain,\nmenu,\nnav,\nsection,\nsummary {\n display: block;\n}\naudio,\ncanvas,\nprogress,\nvideo {\n display: inline-block;\n vertical-align: baseline;\n}\naudio:not([controls]) {\n display: none;\n height: 0;\n}\n[hidden],\ntemplate {\n display: none;\n}\na {\n background-color: transparent;\n}\na:active,\na:hover {\n outline: 0;\n}\nabbr[title] {\n border-bottom: 1px dotted;\n}\nb,\nstrong {\n font-weight: bold;\n}\ndfn {\n font-style: italic;\n}\nh1 {\n font-size: 2em;\n margin: 0.67em 0;\n}\nmark {\n background: #ff0;\n color: #000;\n}\nsmall {\n font-size: 80%;\n}\nsub,\nsup {\n font-size: 75%;\n line-height: 0;\n position: relative;\n vertical-align: baseline;\n}\nsup {\n top: -0.5em;\n}\nsub {\n bottom: -0.25em;\n}\nimg {\n border: 0;\n}\nsvg:not(:root) {\n overflow: hidden;\n}\nfigure {\n margin: 1em 40px;\n}\nhr {\n box-sizing: content-box;\n height: 0;\n}\npre {\n overflow: auto;\n}\ncode,\nkbd,\npre,\nsamp {\n font-family: monospace, monospace;\n font-size: 1em;\n}\nbutton,\ninput,\noptgroup,\nselect,\ntextarea {\n color: inherit;\n font: inherit;\n margin: 0;\n}\nbutton {\n overflow: visible;\n}\nbutton,\nselect {\n text-transform: none;\n}\nbutton,\nhtml input[type=\"button\"],\ninput[type=\"reset\"],\ninput[type=\"submit\"] {\n -webkit-appearance: button;\n cursor: pointer;\n}\nbutton[disabled],\nhtml input[disabled] {\n cursor: default;\n}\nbutton::-moz-focus-inner,\ninput::-moz-focus-inner {\n border: 0;\n padding: 0;\n}\ninput {\n line-height: normal;\n}\ninput[type=\"checkbox\"],\ninput[type=\"radio\"] {\n box-sizing: border-box;\n padding: 0;\n}\ninput[type=\"number\"]::-webkit-inner-spin-button,\ninput[type=\"number\"]::-webkit-outer-spin-button {\n height: auto;\n}\ninput[type=\"search\"] {\n -webkit-appearance: textfield;\n box-sizing: content-box;\n}\ninput[type=\"search\"]::-webkit-search-cancel-button,\ninput[type=\"search\"]::-webkit-search-decoration {\n -webkit-appearance: none;\n}\nfieldset {\n border: 1px solid #c0c0c0;\n margin: 0 2px;\n padding: 0.35em 0.625em 0.75em;\n}\nlegend {\n border: 0;\n padding: 0;\n}\ntextarea {\n overflow: auto;\n}\noptgroup {\n font-weight: bold;\n}\ntable {\n border-collapse: collapse;\n border-spacing: 0;\n}\ntd,\nth {\n padding: 0;\n}\n/*! Source: https://github.com/h5bp/html5-boilerplate/blob/master/src/css/main.css */\n@media print {\n *,\n *:before,\n *:after {\n background: transparent !important;\n color: #000 !important;\n box-shadow: none !important;\n text-shadow: none !important;\n }\n a,\n a:visited {\n text-decoration: underline;\n }\n a[href]:after {\n content: \" (\" attr(href) \")\";\n }\n abbr[title]:after {\n content: \" (\" attr(title) \")\";\n }\n a[href^=\"#\"]:after,\n a[href^=\"javascript:\"]:after {\n content: \"\";\n }\n pre,\n blockquote {\n border: 1px solid #999;\n page-break-inside: avoid;\n }\n thead {\n display: table-header-group;\n }\n tr,\n img {\n page-break-inside: avoid;\n }\n img {\n max-width: 100% !important;\n }\n p,\n h2,\n h3 {\n orphans: 3;\n widows: 3;\n }\n h2,\n h3 {\n page-break-after: avoid;\n }\n .navbar {\n display: none;\n }\n .btn > .caret,\n .dropup > .btn > .caret {\n border-top-color: #000 !important;\n }\n .label {\n border: 1px solid #000;\n }\n .table {\n border-collapse: collapse !important;\n }\n .table td,\n .table th {\n background-color: #fff !important;\n }\n .table-bordered th,\n .table-bordered td {\n border: 1px solid #ddd !important;\n }\n}\n@font-face {\n font-family: 'Glyphicons Halflings';\n src: url('../fonts/glyphicons-halflings-regular.eot');\n src: url('../fonts/glyphicons-halflings-regular.eot?#iefix') format('embedded-opentype'), url('../fonts/glyphicons-halflings-regular.woff2') format('woff2'), url('../fonts/glyphicons-halflings-regular.woff') format('woff'), url('../fonts/glyphicons-halflings-regular.ttf') format('truetype'), url('../fonts/glyphicons-halflings-regular.svg#glyphicons_halflingsregular') format('svg');\n}\n.glyphicon {\n position: relative;\n top: 1px;\n display: inline-block;\n font-family: 'Glyphicons Halflings';\n font-style: normal;\n font-weight: normal;\n line-height: 1;\n -webkit-font-smoothing: antialiased;\n -moz-osx-font-smoothing: grayscale;\n}\n.glyphicon-asterisk:before {\n content: \"\\002a\";\n}\n.glyphicon-plus:before {\n content: \"\\002b\";\n}\n.glyphicon-euro:before,\n.glyphicon-eur:before {\n content: \"\\20ac\";\n}\n.glyphicon-minus:before {\n content: \"\\2212\";\n}\n.glyphicon-cloud:before {\n content: \"\\2601\";\n}\n.glyphicon-envelope:before {\n content: \"\\2709\";\n}\n.glyphicon-pencil:before {\n content: \"\\270f\";\n}\n.glyphicon-glass:before {\n content: \"\\e001\";\n}\n.glyphicon-music:before {\n content: \"\\e002\";\n}\n.glyphicon-search:before {\n content: \"\\e003\";\n}\n.glyphicon-heart:before {\n content: \"\\e005\";\n}\n.glyphicon-star:before {\n content: \"\\e006\";\n}\n.glyphicon-star-empty:before {\n content: \"\\e007\";\n}\n.glyphicon-user:before {\n content: \"\\e008\";\n}\n.glyphicon-film:before {\n content: \"\\e009\";\n}\n.glyphicon-th-large:before {\n content: \"\\e010\";\n}\n.glyphicon-th:before {\n content: \"\\e011\";\n}\n.glyphicon-th-list:before {\n content: \"\\e012\";\n}\n.glyphicon-ok:before {\n content: \"\\e013\";\n}\n.glyphicon-remove:before {\n content: \"\\e014\";\n}\n.glyphicon-zoom-in:before {\n content: \"\\e015\";\n}\n.glyphicon-zoom-out:before {\n content: \"\\e016\";\n}\n.glyphicon-off:before {\n content: \"\\e017\";\n}\n.glyphicon-signal:before {\n content: \"\\e018\";\n}\n.glyphicon-cog:before {\n content: \"\\e019\";\n}\n.glyphicon-trash:before {\n content: \"\\e020\";\n}\n.glyphicon-home:before {\n content: \"\\e021\";\n}\n.glyphicon-file:before {\n content: \"\\e022\";\n}\n.glyphicon-time:before {\n content: \"\\e023\";\n}\n.glyphicon-road:before {\n content: \"\\e024\";\n}\n.glyphicon-download-alt:before {\n content: \"\\e025\";\n}\n.glyphicon-download:before {\n content: \"\\e026\";\n}\n.glyphicon-upload:before {\n content: \"\\e027\";\n}\n.glyphicon-inbox:before {\n content: \"\\e028\";\n}\n.glyphicon-play-circle:before {\n content: \"\\e029\";\n}\n.glyphicon-repeat:before {\n content: \"\\e030\";\n}\n.glyphicon-refresh:before {\n content: \"\\e031\";\n}\n.glyphicon-list-alt:before {\n content: \"\\e032\";\n}\n.glyphicon-lock:before {\n content: \"\\e033\";\n}\n.glyphicon-flag:before {\n content: \"\\e034\";\n}\n.glyphicon-headphones:before {\n content: \"\\e035\";\n}\n.glyphicon-volume-off:before {\n content: \"\\e036\";\n}\n.glyphicon-volume-down:before {\n content: \"\\e037\";\n}\n.glyphicon-volume-up:before {\n content: \"\\e038\";\n}\n.glyphicon-qrcode:before {\n content: \"\\e039\";\n}\n.glyphicon-barcode:before {\n content: \"\\e040\";\n}\n.glyphicon-tag:before {\n content: \"\\e041\";\n}\n.glyphicon-tags:before {\n content: \"\\e042\";\n}\n.glyphicon-book:before {\n content: \"\\e043\";\n}\n.glyphicon-bookmark:before {\n content: \"\\e044\";\n}\n.glyphicon-print:before {\n content: \"\\e045\";\n}\n.glyphicon-camera:before {\n content: \"\\e046\";\n}\n.glyphicon-font:before {\n content: \"\\e047\";\n}\n.glyphicon-bold:before {\n content: \"\\e048\";\n}\n.glyphicon-italic:before {\n content: \"\\e049\";\n}\n.glyphicon-text-height:before {\n content: \"\\e050\";\n}\n.glyphicon-text-width:before {\n content: \"\\e051\";\n}\n.glyphicon-align-left:before {\n content: \"\\e052\";\n}\n.glyphicon-align-center:before {\n content: \"\\e053\";\n}\n.glyphicon-align-right:before {\n content: \"\\e054\";\n}\n.glyphicon-align-justify:before {\n content: \"\\e055\";\n}\n.glyphicon-list:before {\n content: \"\\e056\";\n}\n.glyphicon-indent-left:before {\n content: \"\\e057\";\n}\n.glyphicon-indent-right:before {\n content: \"\\e058\";\n}\n.glyphicon-facetime-video:before {\n content: \"\\e059\";\n}\n.glyphicon-picture:before {\n content: \"\\e060\";\n}\n.glyphicon-map-marker:before {\n content: \"\\e062\";\n}\n.glyphicon-adjust:before {\n content: \"\\e063\";\n}\n.glyphicon-tint:before {\n content: \"\\e064\";\n}\n.glyphicon-edit:before {\n content: \"\\e065\";\n}\n.glyphicon-share:before {\n content: \"\\e066\";\n}\n.glyphicon-check:before {\n content: \"\\e067\";\n}\n.glyphicon-move:before {\n content: \"\\e068\";\n}\n.glyphicon-step-backward:before {\n content: \"\\e069\";\n}\n.glyphicon-fast-backward:before {\n content: \"\\e070\";\n}\n.glyphicon-backward:before {\n content: \"\\e071\";\n}\n.glyphicon-play:before {\n content: \"\\e072\";\n}\n.glyphicon-pause:before {\n content: \"\\e073\";\n}\n.glyphicon-stop:before {\n content: \"\\e074\";\n}\n.glyphicon-forward:before {\n content: \"\\e075\";\n}\n.glyphicon-fast-forward:before {\n content: \"\\e076\";\n}\n.glyphicon-step-forward:before {\n content: \"\\e077\";\n}\n.glyphicon-eject:before {\n content: \"\\e078\";\n}\n.glyphicon-chevron-left:before {\n content: \"\\e079\";\n}\n.glyphicon-chevron-right:before {\n content: \"\\e080\";\n}\n.glyphicon-plus-sign:before {\n content: \"\\e081\";\n}\n.glyphicon-minus-sign:before {\n content: \"\\e082\";\n}\n.glyphicon-remove-sign:before {\n content: \"\\e083\";\n}\n.glyphicon-ok-sign:before {\n content: \"\\e084\";\n}\n.glyphicon-question-sign:before {\n content: \"\\e085\";\n}\n.glyphicon-info-sign:before {\n content: \"\\e086\";\n}\n.glyphicon-screenshot:before {\n content: \"\\e087\";\n}\n.glyphicon-remove-circle:before {\n content: \"\\e088\";\n}\n.glyphicon-ok-circle:before {\n content: \"\\e089\";\n}\n.glyphicon-ban-circle:before {\n content: \"\\e090\";\n}\n.glyphicon-arrow-left:before {\n content: \"\\e091\";\n}\n.glyphicon-arrow-right:before {\n content: \"\\e092\";\n}\n.glyphicon-arrow-up:before {\n content: \"\\e093\";\n}\n.glyphicon-arrow-down:before {\n content: \"\\e094\";\n}\n.glyphicon-share-alt:before {\n content: \"\\e095\";\n}\n.glyphicon-resize-full:before {\n content: \"\\e096\";\n}\n.glyphicon-resize-small:before {\n content: \"\\e097\";\n}\n.glyphicon-exclamation-sign:before {\n content: \"\\e101\";\n}\n.glyphicon-gift:before {\n content: \"\\e102\";\n}\n.glyphicon-leaf:before {\n content: \"\\e103\";\n}\n.glyphicon-fire:before {\n content: \"\\e104\";\n}\n.glyphicon-eye-open:before {\n content: \"\\e105\";\n}\n.glyphicon-eye-close:before {\n content: \"\\e106\";\n}\n.glyphicon-warning-sign:before {\n content: \"\\e107\";\n}\n.glyphicon-plane:before {\n content: \"\\e108\";\n}\n.glyphicon-calendar:before {\n content: \"\\e109\";\n}\n.glyphicon-random:before {\n content: \"\\e110\";\n}\n.glyphicon-comment:before {\n content: \"\\e111\";\n}\n.glyphicon-magnet:before {\n content: \"\\e112\";\n}\n.glyphicon-chevron-up:before {\n content: \"\\e113\";\n}\n.glyphicon-chevron-down:before {\n content: \"\\e114\";\n}\n.glyphicon-retweet:before {\n content: \"\\e115\";\n}\n.glyphicon-shopping-cart:before {\n content: \"\\e116\";\n}\n.glyphicon-folder-close:before {\n content: \"\\e117\";\n}\n.glyphicon-folder-open:before {\n content: \"\\e118\";\n}\n.glyphicon-resize-vertical:before {\n content: \"\\e119\";\n}\n.glyphicon-resize-horizontal:before {\n content: \"\\e120\";\n}\n.glyphicon-hdd:before {\n content: \"\\e121\";\n}\n.glyphicon-bullhorn:before {\n content: \"\\e122\";\n}\n.glyphicon-bell:before {\n content: \"\\e123\";\n}\n.glyphicon-certificate:before {\n content: \"\\e124\";\n}\n.glyphicon-thumbs-up:before {\n content: \"\\e125\";\n}\n.glyphicon-thumbs-down:before {\n content: \"\\e126\";\n}\n.glyphicon-hand-right:before {\n content: \"\\e127\";\n}\n.glyphicon-hand-left:before {\n content: \"\\e128\";\n}\n.glyphicon-hand-up:before {\n content: \"\\e129\";\n}\n.glyphicon-hand-down:before {\n content: \"\\e130\";\n}\n.glyphicon-circle-arrow-right:before {\n content: \"\\e131\";\n}\n.glyphicon-circle-arrow-left:before {\n content: \"\\e132\";\n}\n.glyphicon-circle-arrow-up:before {\n content: \"\\e133\";\n}\n.glyphicon-circle-arrow-down:before {\n content: \"\\e134\";\n}\n.glyphicon-globe:before {\n content: \"\\e135\";\n}\n.glyphicon-wrench:before {\n content: \"\\e136\";\n}\n.glyphicon-tasks:before {\n content: \"\\e137\";\n}\n.glyphicon-filter:before {\n content: \"\\e138\";\n}\n.glyphicon-briefcase:before {\n content: \"\\e139\";\n}\n.glyphicon-fullscreen:before {\n content: \"\\e140\";\n}\n.glyphicon-dashboard:before {\n content: \"\\e141\";\n}\n.glyphicon-paperclip:before {\n content: \"\\e142\";\n}\n.glyphicon-heart-empty:before {\n content: \"\\e143\";\n}\n.glyphicon-link:before {\n content: \"\\e144\";\n}\n.glyphicon-phone:before {\n content: \"\\e145\";\n}\n.glyphicon-pushpin:before {\n content: \"\\e146\";\n}\n.glyphicon-usd:before {\n content: \"\\e148\";\n}\n.glyphicon-gbp:before {\n content: \"\\e149\";\n}\n.glyphicon-sort:before {\n content: \"\\e150\";\n}\n.glyphicon-sort-by-alphabet:before {\n content: \"\\e151\";\n}\n.glyphicon-sort-by-alphabet-alt:before {\n content: \"\\e152\";\n}\n.glyphicon-sort-by-order:before {\n content: \"\\e153\";\n}\n.glyphicon-sort-by-order-alt:before {\n content: \"\\e154\";\n}\n.glyphicon-sort-by-attributes:before {\n content: \"\\e155\";\n}\n.glyphicon-sort-by-attributes-alt:before {\n content: \"\\e156\";\n}\n.glyphicon-unchecked:before {\n content: \"\\e157\";\n}\n.glyphicon-expand:before {\n content: \"\\e158\";\n}\n.glyphicon-collapse-down:before {\n content: \"\\e159\";\n}\n.glyphicon-collapse-up:before {\n content: \"\\e160\";\n}\n.glyphicon-log-in:before {\n content: \"\\e161\";\n}\n.glyphicon-flash:before {\n content: \"\\e162\";\n}\n.glyphicon-log-out:before {\n content: \"\\e163\";\n}\n.glyphicon-new-window:before {\n content: \"\\e164\";\n}\n.glyphicon-record:before {\n content: \"\\e165\";\n}\n.glyphicon-save:before {\n content: \"\\e166\";\n}\n.glyphicon-open:before {\n content: \"\\e167\";\n}\n.glyphicon-saved:before {\n content: \"\\e168\";\n}\n.glyphicon-import:before {\n content: \"\\e169\";\n}\n.glyphicon-export:before {\n content: \"\\e170\";\n}\n.glyphicon-send:before {\n content: \"\\e171\";\n}\n.glyphicon-floppy-disk:before {\n content: \"\\e172\";\n}\n.glyphicon-floppy-saved:before {\n content: \"\\e173\";\n}\n.glyphicon-floppy-remove:before {\n content: \"\\e174\";\n}\n.glyphicon-floppy-save:before {\n content: \"\\e175\";\n}\n.glyphicon-floppy-open:before {\n content: \"\\e176\";\n}\n.glyphicon-credit-card:before {\n content: \"\\e177\";\n}\n.glyphicon-transfer:before {\n content: \"\\e178\";\n}\n.glyphicon-cutlery:before {\n content: \"\\e179\";\n}\n.glyphicon-header:before {\n content: \"\\e180\";\n}\n.glyphicon-compressed:before {\n content: \"\\e181\";\n}\n.glyphicon-earphone:before {\n content: \"\\e182\";\n}\n.glyphicon-phone-alt:before {\n content: \"\\e183\";\n}\n.glyphicon-tower:before {\n content: \"\\e184\";\n}\n.glyphicon-stats:before {\n content: \"\\e185\";\n}\n.glyphicon-sd-video:before {\n content: \"\\e186\";\n}\n.glyphicon-hd-video:before {\n content: \"\\e187\";\n}\n.glyphicon-subtitles:before {\n content: \"\\e188\";\n}\n.glyphicon-sound-stereo:before {\n content: \"\\e189\";\n}\n.glyphicon-sound-dolby:before {\n content: \"\\e190\";\n}\n.glyphicon-sound-5-1:before {\n content: \"\\e191\";\n}\n.glyphicon-sound-6-1:before {\n content: \"\\e192\";\n}\n.glyphicon-sound-7-1:before {\n content: \"\\e193\";\n}\n.glyphicon-copyright-mark:before {\n content: \"\\e194\";\n}\n.glyphicon-registration-mark:before {\n content: \"\\e195\";\n}\n.glyphicon-cloud-download:before {\n content: \"\\e197\";\n}\n.glyphicon-cloud-upload:before {\n content: \"\\e198\";\n}\n.glyphicon-tree-conifer:before {\n content: \"\\e199\";\n}\n.glyphicon-tree-deciduous:before {\n content: \"\\e200\";\n}\n.glyphicon-cd:before {\n content: \"\\e201\";\n}\n.glyphicon-save-file:before {\n content: \"\\e202\";\n}\n.glyphicon-open-file:before {\n content: \"\\e203\";\n}\n.glyphicon-level-up:before {\n content: \"\\e204\";\n}\n.glyphicon-copy:before {\n content: \"\\e205\";\n}\n.glyphicon-paste:before {\n content: \"\\e206\";\n}\n.glyphicon-alert:before {\n content: \"\\e209\";\n}\n.glyphicon-equalizer:before {\n content: \"\\e210\";\n}\n.glyphicon-king:before {\n content: \"\\e211\";\n}\n.glyphicon-queen:before {\n content: \"\\e212\";\n}\n.glyphicon-pawn:before {\n content: \"\\e213\";\n}\n.glyphicon-bishop:before {\n content: \"\\e214\";\n}\n.glyphicon-knight:before {\n content: \"\\e215\";\n}\n.glyphicon-baby-formula:before {\n content: \"\\e216\";\n}\n.glyphicon-tent:before {\n content: \"\\26fa\";\n}\n.glyphicon-blackboard:before {\n content: \"\\e218\";\n}\n.glyphicon-bed:before {\n content: \"\\e219\";\n}\n.glyphicon-apple:before {\n content: \"\\f8ff\";\n}\n.glyphicon-erase:before {\n content: \"\\e221\";\n}\n.glyphicon-hourglass:before {\n content: \"\\231b\";\n}\n.glyphicon-lamp:before {\n content: \"\\e223\";\n}\n.glyphicon-duplicate:before {\n content: \"\\e224\";\n}\n.glyphicon-piggy-bank:before {\n content: \"\\e225\";\n}\n.glyphicon-scissors:before {\n content: \"\\e226\";\n}\n.glyphicon-bitcoin:before {\n content: \"\\e227\";\n}\n.glyphicon-btc:before {\n content: \"\\e227\";\n}\n.glyphicon-xbt:before {\n content: \"\\e227\";\n}\n.glyphicon-yen:before {\n content: \"\\00a5\";\n}\n.glyphicon-jpy:before {\n content: \"\\00a5\";\n}\n.glyphicon-ruble:before {\n content: \"\\20bd\";\n}\n.glyphicon-rub:before {\n content: \"\\20bd\";\n}\n.glyphicon-scale:before {\n content: \"\\e230\";\n}\n.glyphicon-ice-lolly:before {\n content: \"\\e231\";\n}\n.glyphicon-ice-lolly-tasted:before {\n content: \"\\e232\";\n}\n.glyphicon-education:before {\n content: \"\\e233\";\n}\n.glyphicon-option-horizontal:before {\n content: \"\\e234\";\n}\n.glyphicon-option-vertical:before {\n content: \"\\e235\";\n}\n.glyphicon-menu-hamburger:before {\n content: \"\\e236\";\n}\n.glyphicon-modal-window:before {\n content: \"\\e237\";\n}\n.glyphicon-oil:before {\n content: \"\\e238\";\n}\n.glyphicon-grain:before {\n content: \"\\e239\";\n}\n.glyphicon-sunglasses:before {\n content: \"\\e240\";\n}\n.glyphicon-text-size:before {\n content: \"\\e241\";\n}\n.glyphicon-text-color:before {\n content: \"\\e242\";\n}\n.glyphicon-text-background:before {\n content: \"\\e243\";\n}\n.glyphicon-object-align-top:before {\n content: \"\\e244\";\n}\n.glyphicon-object-align-bottom:before {\n content: \"\\e245\";\n}\n.glyphicon-object-align-horizontal:before {\n content: \"\\e246\";\n}\n.glyphicon-object-align-left:before {\n content: \"\\e247\";\n}\n.glyphicon-object-align-vertical:before {\n content: \"\\e248\";\n}\n.glyphicon-object-align-right:before {\n content: \"\\e249\";\n}\n.glyphicon-triangle-right:before {\n content: \"\\e250\";\n}\n.glyphicon-triangle-left:before {\n content: \"\\e251\";\n}\n.glyphicon-triangle-bottom:before {\n content: \"\\e252\";\n}\n.glyphicon-triangle-top:before {\n content: \"\\e253\";\n}\n.glyphicon-console:before {\n content: \"\\e254\";\n}\n.glyphicon-superscript:before {\n content: \"\\e255\";\n}\n.glyphicon-subscript:before {\n content: \"\\e256\";\n}\n.glyphicon-menu-left:before {\n content: \"\\e257\";\n}\n.glyphicon-menu-right:before {\n content: \"\\e258\";\n}\n.glyphicon-menu-down:before {\n content: \"\\e259\";\n}\n.glyphicon-menu-up:before {\n content: \"\\e260\";\n}\n* {\n -webkit-box-sizing: border-box;\n -moz-box-sizing: border-box;\n box-sizing: border-box;\n}\n*:before,\n*:after {\n -webkit-box-sizing: border-box;\n -moz-box-sizing: border-box;\n box-sizing: border-box;\n}\nhtml {\n font-size: 10px;\n -webkit-tap-highlight-color: rgba(0, 0, 0, 0);\n}\nbody {\n font-family: \"Helvetica Neue\", Helvetica, Arial, sans-serif;\n font-size: 14px;\n line-height: 1.42857143;\n color: #333333;\n background-color: #fff;\n}\ninput,\nbutton,\nselect,\ntextarea {\n font-family: inherit;\n font-size: inherit;\n line-height: inherit;\n}\na {\n color: #337ab7;\n text-decoration: none;\n}\na:hover,\na:focus {\n color: #23527c;\n text-decoration: underline;\n}\na:focus {\n outline: 5px auto -webkit-focus-ring-color;\n outline-offset: -2px;\n}\nfigure {\n margin: 0;\n}\nimg {\n vertical-align: middle;\n}\n.img-responsive,\n.thumbnail > img,\n.thumbnail a > img,\n.carousel-inner > .item > img,\n.carousel-inner > .item > a > img {\n display: block;\n max-width: 100%;\n height: auto;\n}\n.img-rounded {\n border-radius: 6px;\n}\n.img-thumbnail {\n padding: 4px;\n line-height: 1.42857143;\n background-color: #fff;\n border: 1px solid #ddd;\n border-radius: 4px;\n -webkit-transition: all 0.2s ease-in-out;\n -o-transition: all 0.2s ease-in-out;\n transition: all 0.2s ease-in-out;\n display: inline-block;\n max-width: 100%;\n height: auto;\n}\n.img-circle {\n border-radius: 50%;\n}\nhr {\n margin-top: 20px;\n margin-bottom: 20px;\n border: 0;\n border-top: 1px solid #eeeeee;\n}\n.sr-only {\n position: absolute;\n width: 1px;\n height: 1px;\n margin: -1px;\n padding: 0;\n overflow: hidden;\n clip: rect(0, 0, 0, 0);\n border: 0;\n}\n.sr-only-focusable:active,\n.sr-only-focusable:focus {\n position: static;\n width: auto;\n height: auto;\n margin: 0;\n overflow: visible;\n clip: auto;\n}\n[role=\"button\"] {\n cursor: pointer;\n}\nh1,\nh2,\nh3,\nh4,\nh5,\nh6,\n.h1,\n.h2,\n.h3,\n.h4,\n.h5,\n.h6 {\n font-family: inherit;\n font-weight: 500;\n line-height: 1.1;\n color: inherit;\n}\nh1 small,\nh2 small,\nh3 small,\nh4 small,\nh5 small,\nh6 small,\n.h1 small,\n.h2 small,\n.h3 small,\n.h4 small,\n.h5 small,\n.h6 small,\nh1 .small,\nh2 .small,\nh3 .small,\nh4 .small,\nh5 .small,\nh6 .small,\n.h1 .small,\n.h2 .small,\n.h3 .small,\n.h4 .small,\n.h5 .small,\n.h6 .small {\n font-weight: normal;\n line-height: 1;\n color: #777777;\n}\nh1,\n.h1,\nh2,\n.h2,\nh3,\n.h3 {\n margin-top: 20px;\n margin-bottom: 10px;\n}\nh1 small,\n.h1 small,\nh2 small,\n.h2 small,\nh3 small,\n.h3 small,\nh1 .small,\n.h1 .small,\nh2 .small,\n.h2 .small,\nh3 .small,\n.h3 .small {\n font-size: 65%;\n}\nh4,\n.h4,\nh5,\n.h5,\nh6,\n.h6 {\n margin-top: 10px;\n margin-bottom: 10px;\n}\nh4 small,\n.h4 small,\nh5 small,\n.h5 small,\nh6 small,\n.h6 small,\nh4 .small,\n.h4 .small,\nh5 .small,\n.h5 .small,\nh6 .small,\n.h6 .small {\n font-size: 75%;\n}\nh1,\n.h1 {\n font-size: 36px;\n}\nh2,\n.h2 {\n font-size: 30px;\n}\nh3,\n.h3 {\n font-size: 24px;\n}\nh4,\n.h4 {\n font-size: 18px;\n}\nh5,\n.h5 {\n font-size: 14px;\n}\nh6,\n.h6 {\n font-size: 12px;\n}\np {\n margin: 0 0 10px;\n}\n.lead {\n margin-bottom: 20px;\n font-size: 16px;\n font-weight: 300;\n line-height: 1.4;\n}\n@media (min-width: 768px) {\n .lead {\n font-size: 21px;\n }\n}\nsmall,\n.small {\n font-size: 85%;\n}\nmark,\n.mark {\n background-color: #fcf8e3;\n padding: .2em;\n}\n.text-left {\n text-align: left;\n}\n.text-right {\n text-align: right;\n}\n.text-center {\n text-align: center;\n}\n.text-justify {\n text-align: justify;\n}\n.text-nowrap {\n white-space: nowrap;\n}\n.text-lowercase {\n text-transform: lowercase;\n}\n.text-uppercase {\n text-transform: uppercase;\n}\n.text-capitalize {\n text-transform: capitalize;\n}\n.text-muted {\n color: #777777;\n}\n.text-primary {\n color: #337ab7;\n}\na.text-primary:hover,\na.text-primary:focus {\n color: #286090;\n}\n.text-success {\n color: #3c763d;\n}\na.text-success:hover,\na.text-success:focus {\n color: #2b542c;\n}\n.text-info {\n color: #31708f;\n}\na.text-info:hover,\na.text-info:focus {\n color: #245269;\n}\n.text-warning {\n color: #8a6d3b;\n}\na.text-warning:hover,\na.text-warning:focus {\n color: #66512c;\n}\n.text-danger {\n color: #a94442;\n}\na.text-danger:hover,\na.text-danger:focus {\n color: #843534;\n}\n.bg-primary {\n color: #fff;\n background-color: #337ab7;\n}\na.bg-primary:hover,\na.bg-primary:focus {\n background-color: #286090;\n}\n.bg-success {\n background-color: #dff0d8;\n}\na.bg-success:hover,\na.bg-success:focus {\n background-color: #c1e2b3;\n}\n.bg-info {\n background-color: #d9edf7;\n}\na.bg-info:hover,\na.bg-info:focus {\n background-color: #afd9ee;\n}\n.bg-warning {\n background-color: #fcf8e3;\n}\na.bg-warning:hover,\na.bg-warning:focus {\n background-color: #f7ecb5;\n}\n.bg-danger {\n background-color: #f2dede;\n}\na.bg-danger:hover,\na.bg-danger:focus {\n background-color: #e4b9b9;\n}\n.page-header {\n padding-bottom: 9px;\n margin: 40px 0 20px;\n border-bottom: 1px solid #eeeeee;\n}\nul,\nol {\n margin-top: 0;\n margin-bottom: 10px;\n}\nul ul,\nol ul,\nul ol,\nol ol {\n margin-bottom: 0;\n}\n.list-unstyled {\n padding-left: 0;\n list-style: none;\n}\n.list-inline {\n padding-left: 0;\n list-style: none;\n margin-left: -5px;\n}\n.list-inline > li {\n display: inline-block;\n padding-left: 5px;\n padding-right: 5px;\n}\ndl {\n margin-top: 0;\n margin-bottom: 20px;\n}\ndt,\ndd {\n line-height: 1.42857143;\n}\ndt {\n font-weight: bold;\n}\ndd {\n margin-left: 0;\n}\n@media (min-width: 768px) {\n .dl-horizontal dt {\n float: left;\n width: 160px;\n clear: left;\n text-align: right;\n overflow: hidden;\n text-overflow: ellipsis;\n white-space: nowrap;\n }\n .dl-horizontal dd {\n margin-left: 180px;\n }\n}\nabbr[title],\nabbr[data-original-title] {\n cursor: help;\n border-bottom: 1px dotted #777777;\n}\n.initialism {\n font-size: 90%;\n text-transform: uppercase;\n}\nblockquote {\n padding: 10px 20px;\n margin: 0 0 20px;\n font-size: 17.5px;\n border-left: 5px solid #eeeeee;\n}\nblockquote p:last-child,\nblockquote ul:last-child,\nblockquote ol:last-child {\n margin-bottom: 0;\n}\nblockquote footer,\nblockquote small,\nblockquote .small {\n display: block;\n font-size: 80%;\n line-height: 1.42857143;\n color: #777777;\n}\nblockquote footer:before,\nblockquote small:before,\nblockquote .small:before {\n content: '\\2014 \\00A0';\n}\n.blockquote-reverse,\nblockquote.pull-right {\n padding-right: 15px;\n padding-left: 0;\n border-right: 5px solid #eeeeee;\n border-left: 0;\n text-align: right;\n}\n.blockquote-reverse footer:before,\nblockquote.pull-right footer:before,\n.blockquote-reverse small:before,\nblockquote.pull-right small:before,\n.blockquote-reverse .small:before,\nblockquote.pull-right .small:before {\n content: '';\n}\n.blockquote-reverse footer:after,\nblockquote.pull-right footer:after,\n.blockquote-reverse small:after,\nblockquote.pull-right small:after,\n.blockquote-reverse .small:after,\nblockquote.pull-right .small:after {\n content: '\\00A0 \\2014';\n}\naddress {\n margin-bottom: 20px;\n font-style: normal;\n line-height: 1.42857143;\n}\ncode,\nkbd,\npre,\nsamp {\n font-family: Menlo, Monaco, Consolas, \"Courier New\", monospace;\n}\ncode {\n padding: 2px 4px;\n font-size: 90%;\n color: #c7254e;\n background-color: #f9f2f4;\n border-radius: 4px;\n}\nkbd {\n padding: 2px 4px;\n font-size: 90%;\n color: #fff;\n background-color: #333;\n border-radius: 3px;\n box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.25);\n}\nkbd kbd {\n padding: 0;\n font-size: 100%;\n font-weight: bold;\n box-shadow: none;\n}\npre {\n display: block;\n padding: 9.5px;\n margin: 0 0 10px;\n font-size: 13px;\n line-height: 1.42857143;\n word-break: break-all;\n word-wrap: break-word;\n color: #333333;\n background-color: #f5f5f5;\n border: 1px solid #ccc;\n border-radius: 4px;\n}\npre code {\n padding: 0;\n font-size: inherit;\n color: inherit;\n white-space: pre-wrap;\n background-color: transparent;\n border-radius: 0;\n}\n.pre-scrollable {\n max-height: 340px;\n overflow-y: scroll;\n}\n.container {\n margin-right: auto;\n margin-left: auto;\n padding-left: 15px;\n padding-right: 15px;\n}\n@media (min-width: 768px) {\n .container {\n width: 750px;\n }\n}\n@media (min-width: 992px) {\n .container {\n width: 970px;\n }\n}\n@media (min-width: 1200px) {\n .container {\n width: 1170px;\n }\n}\n.container-fluid {\n margin-right: auto;\n margin-left: auto;\n padding-left: 15px;\n padding-right: 15px;\n}\n.row {\n margin-left: -15px;\n margin-right: -15px;\n}\n.col-xs-1, .col-sm-1, .col-md-1, .col-lg-1, .col-xs-2, .col-sm-2, .col-md-2, .col-lg-2, .col-xs-3, .col-sm-3, .col-md-3, .col-lg-3, .col-xs-4, .col-sm-4, .col-md-4, .col-lg-4, .col-xs-5, .col-sm-5, .col-md-5, .col-lg-5, .col-xs-6, .col-sm-6, .col-md-6, .col-lg-6, .col-xs-7, .col-sm-7, .col-md-7, .col-lg-7, .col-xs-8, .col-sm-8, .col-md-8, .col-lg-8, .col-xs-9, .col-sm-9, .col-md-9, .col-lg-9, .col-xs-10, .col-sm-10, .col-md-10, .col-lg-10, .col-xs-11, .col-sm-11, .col-md-11, .col-lg-11, .col-xs-12, .col-sm-12, .col-md-12, .col-lg-12 {\n position: relative;\n min-height: 1px;\n padding-left: 15px;\n padding-right: 15px;\n}\n.col-xs-1, .col-xs-2, .col-xs-3, .col-xs-4, .col-xs-5, .col-xs-6, .col-xs-7, .col-xs-8, .col-xs-9, .col-xs-10, .col-xs-11, .col-xs-12 {\n float: left;\n}\n.col-xs-12 {\n width: 100%;\n}\n.col-xs-11 {\n width: 91.66666667%;\n}\n.col-xs-10 {\n width: 83.33333333%;\n}\n.col-xs-9 {\n width: 75%;\n}\n.col-xs-8 {\n width: 66.66666667%;\n}\n.col-xs-7 {\n width: 58.33333333%;\n}\n.col-xs-6 {\n width: 50%;\n}\n.col-xs-5 {\n width: 41.66666667%;\n}\n.col-xs-4 {\n width: 33.33333333%;\n}\n.col-xs-3 {\n width: 25%;\n}\n.col-xs-2 {\n width: 16.66666667%;\n}\n.col-xs-1 {\n width: 8.33333333%;\n}\n.col-xs-pull-12 {\n right: 100%;\n}\n.col-xs-pull-11 {\n right: 91.66666667%;\n}\n.col-xs-pull-10 {\n right: 83.33333333%;\n}\n.col-xs-pull-9 {\n right: 75%;\n}\n.col-xs-pull-8 {\n right: 66.66666667%;\n}\n.col-xs-pull-7 {\n right: 58.33333333%;\n}\n.col-xs-pull-6 {\n right: 50%;\n}\n.col-xs-pull-5 {\n right: 41.66666667%;\n}\n.col-xs-pull-4 {\n right: 33.33333333%;\n}\n.col-xs-pull-3 {\n right: 25%;\n}\n.col-xs-pull-2 {\n right: 16.66666667%;\n}\n.col-xs-pull-1 {\n right: 8.33333333%;\n}\n.col-xs-pull-0 {\n right: auto;\n}\n.col-xs-push-12 {\n left: 100%;\n}\n.col-xs-push-11 {\n left: 91.66666667%;\n}\n.col-xs-push-10 {\n left: 83.33333333%;\n}\n.col-xs-push-9 {\n left: 75%;\n}\n.col-xs-push-8 {\n left: 66.66666667%;\n}\n.col-xs-push-7 {\n left: 58.33333333%;\n}\n.col-xs-push-6 {\n left: 50%;\n}\n.col-xs-push-5 {\n left: 41.66666667%;\n}\n.col-xs-push-4 {\n left: 33.33333333%;\n}\n.col-xs-push-3 {\n left: 25%;\n}\n.col-xs-push-2 {\n left: 16.66666667%;\n}\n.col-xs-push-1 {\n left: 8.33333333%;\n}\n.col-xs-push-0 {\n left: auto;\n}\n.col-xs-offset-12 {\n margin-left: 100%;\n}\n.col-xs-offset-11 {\n margin-left: 91.66666667%;\n}\n.col-xs-offset-10 {\n margin-left: 83.33333333%;\n}\n.col-xs-offset-9 {\n margin-left: 75%;\n}\n.col-xs-offset-8 {\n margin-left: 66.66666667%;\n}\n.col-xs-offset-7 {\n margin-left: 58.33333333%;\n}\n.col-xs-offset-6 {\n margin-left: 50%;\n}\n.col-xs-offset-5 {\n margin-left: 41.66666667%;\n}\n.col-xs-offset-4 {\n margin-left: 33.33333333%;\n}\n.col-xs-offset-3 {\n margin-left: 25%;\n}\n.col-xs-offset-2 {\n margin-left: 16.66666667%;\n}\n.col-xs-offset-1 {\n margin-left: 8.33333333%;\n}\n.col-xs-offset-0 {\n margin-left: 0%;\n}\n@media (min-width: 768px) {\n .col-sm-1, .col-sm-2, .col-sm-3, .col-sm-4, .col-sm-5, .col-sm-6, .col-sm-7, .col-sm-8, .col-sm-9, .col-sm-10, .col-sm-11, .col-sm-12 {\n float: left;\n }\n .col-sm-12 {\n width: 100%;\n }\n .col-sm-11 {\n width: 91.66666667%;\n }\n .col-sm-10 {\n width: 83.33333333%;\n }\n .col-sm-9 {\n width: 75%;\n }\n .col-sm-8 {\n width: 66.66666667%;\n }\n .col-sm-7 {\n width: 58.33333333%;\n }\n .col-sm-6 {\n width: 50%;\n }\n .col-sm-5 {\n width: 41.66666667%;\n }\n .col-sm-4 {\n width: 33.33333333%;\n }\n .col-sm-3 {\n width: 25%;\n }\n .col-sm-2 {\n width: 16.66666667%;\n }\n .col-sm-1 {\n width: 8.33333333%;\n }\n .col-sm-pull-12 {\n right: 100%;\n }\n .col-sm-pull-11 {\n right: 91.66666667%;\n }\n .col-sm-pull-10 {\n right: 83.33333333%;\n }\n .col-sm-pull-9 {\n right: 75%;\n }\n .col-sm-pull-8 {\n right: 66.66666667%;\n }\n .col-sm-pull-7 {\n right: 58.33333333%;\n }\n .col-sm-pull-6 {\n right: 50%;\n }\n .col-sm-pull-5 {\n right: 41.66666667%;\n }\n .col-sm-pull-4 {\n right: 33.33333333%;\n }\n .col-sm-pull-3 {\n right: 25%;\n }\n .col-sm-pull-2 {\n right: 16.66666667%;\n }\n .col-sm-pull-1 {\n right: 8.33333333%;\n }\n .col-sm-pull-0 {\n right: auto;\n }\n .col-sm-push-12 {\n left: 100%;\n }\n .col-sm-push-11 {\n left: 91.66666667%;\n }\n .col-sm-push-10 {\n left: 83.33333333%;\n }\n .col-sm-push-9 {\n left: 75%;\n }\n .col-sm-push-8 {\n left: 66.66666667%;\n }\n .col-sm-push-7 {\n left: 58.33333333%;\n }\n .col-sm-push-6 {\n left: 50%;\n }\n .col-sm-push-5 {\n left: 41.66666667%;\n }\n .col-sm-push-4 {\n left: 33.33333333%;\n }\n .col-sm-push-3 {\n left: 25%;\n }\n .col-sm-push-2 {\n left: 16.66666667%;\n }\n .col-sm-push-1 {\n left: 8.33333333%;\n }\n .col-sm-push-0 {\n left: auto;\n }\n .col-sm-offset-12 {\n margin-left: 100%;\n }\n .col-sm-offset-11 {\n margin-left: 91.66666667%;\n }\n .col-sm-offset-10 {\n margin-left: 83.33333333%;\n }\n .col-sm-offset-9 {\n margin-left: 75%;\n }\n .col-sm-offset-8 {\n margin-left: 66.66666667%;\n }\n .col-sm-offset-7 {\n margin-left: 58.33333333%;\n }\n .col-sm-offset-6 {\n margin-left: 50%;\n }\n .col-sm-offset-5 {\n margin-left: 41.66666667%;\n }\n .col-sm-offset-4 {\n margin-left: 33.33333333%;\n }\n .col-sm-offset-3 {\n margin-left: 25%;\n }\n .col-sm-offset-2 {\n margin-left: 16.66666667%;\n }\n .col-sm-offset-1 {\n margin-left: 8.33333333%;\n }\n .col-sm-offset-0 {\n margin-left: 0%;\n }\n}\n@media (min-width: 992px) {\n .col-md-1, .col-md-2, .col-md-3, .col-md-4, .col-md-5, .col-md-6, .col-md-7, .col-md-8, .col-md-9, .col-md-10, .col-md-11, .col-md-12 {\n float: left;\n }\n .col-md-12 {\n width: 100%;\n }\n .col-md-11 {\n width: 91.66666667%;\n }\n .col-md-10 {\n width: 83.33333333%;\n }\n .col-md-9 {\n width: 75%;\n }\n .col-md-8 {\n width: 66.66666667%;\n }\n .col-md-7 {\n width: 58.33333333%;\n }\n .col-md-6 {\n width: 50%;\n }\n .col-md-5 {\n width: 41.66666667%;\n }\n .col-md-4 {\n width: 33.33333333%;\n }\n .col-md-3 {\n width: 25%;\n }\n .col-md-2 {\n width: 16.66666667%;\n }\n .col-md-1 {\n width: 8.33333333%;\n }\n .col-md-pull-12 {\n right: 100%;\n }\n .col-md-pull-11 {\n right: 91.66666667%;\n }\n .col-md-pull-10 {\n right: 83.33333333%;\n }\n .col-md-pull-9 {\n right: 75%;\n }\n .col-md-pull-8 {\n right: 66.66666667%;\n }\n .col-md-pull-7 {\n right: 58.33333333%;\n }\n .col-md-pull-6 {\n right: 50%;\n }\n .col-md-pull-5 {\n right: 41.66666667%;\n }\n .col-md-pull-4 {\n right: 33.33333333%;\n }\n .col-md-pull-3 {\n right: 25%;\n }\n .col-md-pull-2 {\n right: 16.66666667%;\n }\n .col-md-pull-1 {\n right: 8.33333333%;\n }\n .col-md-pull-0 {\n right: auto;\n }\n .col-md-push-12 {\n left: 100%;\n }\n .col-md-push-11 {\n left: 91.66666667%;\n }\n .col-md-push-10 {\n left: 83.33333333%;\n }\n .col-md-push-9 {\n left: 75%;\n }\n .col-md-push-8 {\n left: 66.66666667%;\n }\n .col-md-push-7 {\n left: 58.33333333%;\n }\n .col-md-push-6 {\n left: 50%;\n }\n .col-md-push-5 {\n left: 41.66666667%;\n }\n .col-md-push-4 {\n left: 33.33333333%;\n }\n .col-md-push-3 {\n left: 25%;\n }\n .col-md-push-2 {\n left: 16.66666667%;\n }\n .col-md-push-1 {\n left: 8.33333333%;\n }\n .col-md-push-0 {\n left: auto;\n }\n .col-md-offset-12 {\n margin-left: 100%;\n }\n .col-md-offset-11 {\n margin-left: 91.66666667%;\n }\n .col-md-offset-10 {\n margin-left: 83.33333333%;\n }\n .col-md-offset-9 {\n margin-left: 75%;\n }\n .col-md-offset-8 {\n margin-left: 66.66666667%;\n }\n .col-md-offset-7 {\n margin-left: 58.33333333%;\n }\n .col-md-offset-6 {\n margin-left: 50%;\n }\n .col-md-offset-5 {\n margin-left: 41.66666667%;\n }\n .col-md-offset-4 {\n margin-left: 33.33333333%;\n }\n .col-md-offset-3 {\n margin-left: 25%;\n }\n .col-md-offset-2 {\n margin-left: 16.66666667%;\n }\n .col-md-offset-1 {\n margin-left: 8.33333333%;\n }\n .col-md-offset-0 {\n margin-left: 0%;\n }\n}\n@media (min-width: 1200px) {\n .col-lg-1, .col-lg-2, .col-lg-3, .col-lg-4, .col-lg-5, .col-lg-6, .col-lg-7, .col-lg-8, .col-lg-9, .col-lg-10, .col-lg-11, .col-lg-12 {\n float: left;\n }\n .col-lg-12 {\n width: 100%;\n }\n .col-lg-11 {\n width: 91.66666667%;\n }\n .col-lg-10 {\n width: 83.33333333%;\n }\n .col-lg-9 {\n width: 75%;\n }\n .col-lg-8 {\n width: 66.66666667%;\n }\n .col-lg-7 {\n width: 58.33333333%;\n }\n .col-lg-6 {\n width: 50%;\n }\n .col-lg-5 {\n width: 41.66666667%;\n }\n .col-lg-4 {\n width: 33.33333333%;\n }\n .col-lg-3 {\n width: 25%;\n }\n .col-lg-2 {\n width: 16.66666667%;\n }\n .col-lg-1 {\n width: 8.33333333%;\n }\n .col-lg-pull-12 {\n right: 100%;\n }\n .col-lg-pull-11 {\n right: 91.66666667%;\n }\n .col-lg-pull-10 {\n right: 83.33333333%;\n }\n .col-lg-pull-9 {\n right: 75%;\n }\n .col-lg-pull-8 {\n right: 66.66666667%;\n }\n .col-lg-pull-7 {\n right: 58.33333333%;\n }\n .col-lg-pull-6 {\n right: 50%;\n }\n .col-lg-pull-5 {\n right: 41.66666667%;\n }\n .col-lg-pull-4 {\n right: 33.33333333%;\n }\n .col-lg-pull-3 {\n right: 25%;\n }\n .col-lg-pull-2 {\n right: 16.66666667%;\n }\n .col-lg-pull-1 {\n right: 8.33333333%;\n }\n .col-lg-pull-0 {\n right: auto;\n }\n .col-lg-push-12 {\n left: 100%;\n }\n .col-lg-push-11 {\n left: 91.66666667%;\n }\n .col-lg-push-10 {\n left: 83.33333333%;\n }\n .col-lg-push-9 {\n left: 75%;\n }\n .col-lg-push-8 {\n left: 66.66666667%;\n }\n .col-lg-push-7 {\n left: 58.33333333%;\n }\n .col-lg-push-6 {\n left: 50%;\n }\n .col-lg-push-5 {\n left: 41.66666667%;\n }\n .col-lg-push-4 {\n left: 33.33333333%;\n }\n .col-lg-push-3 {\n left: 25%;\n }\n .col-lg-push-2 {\n left: 16.66666667%;\n }\n .col-lg-push-1 {\n left: 8.33333333%;\n }\n .col-lg-push-0 {\n left: auto;\n }\n .col-lg-offset-12 {\n margin-left: 100%;\n }\n .col-lg-offset-11 {\n margin-left: 91.66666667%;\n }\n .col-lg-offset-10 {\n margin-left: 83.33333333%;\n }\n .col-lg-offset-9 {\n margin-left: 75%;\n }\n .col-lg-offset-8 {\n margin-left: 66.66666667%;\n }\n .col-lg-offset-7 {\n margin-left: 58.33333333%;\n }\n .col-lg-offset-6 {\n margin-left: 50%;\n }\n .col-lg-offset-5 {\n margin-left: 41.66666667%;\n }\n .col-lg-offset-4 {\n margin-left: 33.33333333%;\n }\n .col-lg-offset-3 {\n margin-left: 25%;\n }\n .col-lg-offset-2 {\n margin-left: 16.66666667%;\n }\n .col-lg-offset-1 {\n margin-left: 8.33333333%;\n }\n .col-lg-offset-0 {\n margin-left: 0%;\n }\n}\ntable {\n background-color: transparent;\n}\ncaption {\n padding-top: 8px;\n padding-bottom: 8px;\n color: #777777;\n text-align: left;\n}\nth {\n text-align: left;\n}\n.table {\n width: 100%;\n max-width: 100%;\n margin-bottom: 20px;\n}\n.table > thead > tr > th,\n.table > tbody > tr > th,\n.table > tfoot > tr > th,\n.table > thead > tr > td,\n.table > tbody > tr > td,\n.table > tfoot > tr > td {\n padding: 8px;\n line-height: 1.42857143;\n vertical-align: top;\n border-top: 1px solid #ddd;\n}\n.table > thead > tr > th {\n vertical-align: bottom;\n border-bottom: 2px solid #ddd;\n}\n.table > caption + thead > tr:first-child > th,\n.table > colgroup + thead > tr:first-child > th,\n.table > thead:first-child > tr:first-child > th,\n.table > caption + thead > tr:first-child > td,\n.table > colgroup + thead > tr:first-child > td,\n.table > thead:first-child > tr:first-child > td {\n border-top: 0;\n}\n.table > tbody + tbody {\n border-top: 2px solid #ddd;\n}\n.table .table {\n background-color: #fff;\n}\n.table-condensed > thead > tr > th,\n.table-condensed > tbody > tr > th,\n.table-condensed > tfoot > tr > th,\n.table-condensed > thead > tr > td,\n.table-condensed > tbody > tr > td,\n.table-condensed > tfoot > tr > td {\n padding: 5px;\n}\n.table-bordered {\n border: 1px solid #ddd;\n}\n.table-bordered > thead > tr > th,\n.table-bordered > tbody > tr > th,\n.table-bordered > tfoot > tr > th,\n.table-bordered > thead > tr > td,\n.table-bordered > tbody > tr > td,\n.table-bordered > tfoot > tr > td {\n border: 1px solid #ddd;\n}\n.table-bordered > thead > tr > th,\n.table-bordered > thead > tr > td {\n border-bottom-width: 2px;\n}\n.table-striped > tbody > tr:nth-of-type(odd) {\n background-color: #f9f9f9;\n}\n.table-hover > tbody > tr:hover {\n background-color: #f5f5f5;\n}\ntable col[class*=\"col-\"] {\n position: static;\n float: none;\n display: table-column;\n}\ntable td[class*=\"col-\"],\ntable th[class*=\"col-\"] {\n position: static;\n float: none;\n display: table-cell;\n}\n.table > thead > tr > td.active,\n.table > tbody > tr > td.active,\n.table > tfoot > tr > td.active,\n.table > thead > tr > th.active,\n.table > tbody > tr > th.active,\n.table > tfoot > tr > th.active,\n.table > thead > tr.active > td,\n.table > tbody > tr.active > td,\n.table > tfoot > tr.active > td,\n.table > thead > tr.active > th,\n.table > tbody > tr.active > th,\n.table > tfoot > tr.active > th {\n background-color: #f5f5f5;\n}\n.table-hover > tbody > tr > td.active:hover,\n.table-hover > tbody > tr > th.active:hover,\n.table-hover > tbody > tr.active:hover > td,\n.table-hover > tbody > tr:hover > .active,\n.table-hover > tbody > tr.active:hover > th {\n background-color: #e8e8e8;\n}\n.table > thead > tr > td.success,\n.table > tbody > tr > td.success,\n.table > tfoot > tr > td.success,\n.table > thead > tr > th.success,\n.table > tbody > tr > th.success,\n.table > tfoot > tr > th.success,\n.table > thead > tr.success > td,\n.table > tbody > tr.success > td,\n.table > tfoot > tr.success > td,\n.table > thead > tr.success > th,\n.table > tbody > tr.success > th,\n.table > tfoot > tr.success > th {\n background-color: #dff0d8;\n}\n.table-hover > tbody > tr > td.success:hover,\n.table-hover > tbody > tr > th.success:hover,\n.table-hover > tbody > tr.success:hover > td,\n.table-hover > tbody > tr:hover > .success,\n.table-hover > tbody > tr.success:hover > th {\n background-color: #d0e9c6;\n}\n.table > thead > tr > td.info,\n.table > tbody > tr > td.info,\n.table > tfoot > tr > td.info,\n.table > thead > tr > th.info,\n.table > tbody > tr > th.info,\n.table > tfoot > tr > th.info,\n.table > thead > tr.info > td,\n.table > tbody > tr.info > td,\n.table > tfoot > tr.info > td,\n.table > thead > tr.info > th,\n.table > tbody > tr.info > th,\n.table > tfoot > tr.info > th {\n background-color: #d9edf7;\n}\n.table-hover > tbody > tr > td.info:hover,\n.table-hover > tbody > tr > th.info:hover,\n.table-hover > tbody > tr.info:hover > td,\n.table-hover > tbody > tr:hover > .info,\n.table-hover > tbody > tr.info:hover > th {\n background-color: #c4e3f3;\n}\n.table > thead > tr > td.warning,\n.table > tbody > tr > td.warning,\n.table > tfoot > tr > td.warning,\n.table > thead > tr > th.warning,\n.table > tbody > tr > th.warning,\n.table > tfoot > tr > th.warning,\n.table > thead > tr.warning > td,\n.table > tbody > tr.warning > td,\n.table > tfoot > tr.warning > td,\n.table > thead > tr.warning > th,\n.table > tbody > tr.warning > th,\n.table > tfoot > tr.warning > th {\n background-color: #fcf8e3;\n}\n.table-hover > tbody > tr > td.warning:hover,\n.table-hover > tbody > tr > th.warning:hover,\n.table-hover > tbody > tr.warning:hover > td,\n.table-hover > tbody > tr:hover > .warning,\n.table-hover > tbody > tr.warning:hover > th {\n background-color: #faf2cc;\n}\n.table > thead > tr > td.danger,\n.table > tbody > tr > td.danger,\n.table > tfoot > tr > td.danger,\n.table > thead > tr > th.danger,\n.table > tbody > tr > th.danger,\n.table > tfoot > tr > th.danger,\n.table > thead > tr.danger > td,\n.table > tbody > tr.danger > td,\n.table > tfoot > tr.danger > td,\n.table > thead > tr.danger > th,\n.table > tbody > tr.danger > th,\n.table > tfoot > tr.danger > th {\n background-color: #f2dede;\n}\n.table-hover > tbody > tr > td.danger:hover,\n.table-hover > tbody > tr > th.danger:hover,\n.table-hover > tbody > tr.danger:hover > td,\n.table-hover > tbody > tr:hover > .danger,\n.table-hover > tbody > tr.danger:hover > th {\n background-color: #ebcccc;\n}\n.table-responsive {\n overflow-x: auto;\n min-height: 0.01%;\n}\n@media screen and (max-width: 767px) {\n .table-responsive {\n width: 100%;\n margin-bottom: 15px;\n overflow-y: hidden;\n -ms-overflow-style: -ms-autohiding-scrollbar;\n border: 1px solid #ddd;\n }\n .table-responsive > .table {\n margin-bottom: 0;\n }\n .table-responsive > .table > thead > tr > th,\n .table-responsive > .table > tbody > tr > th,\n .table-responsive > .table > tfoot > tr > th,\n .table-responsive > .table > thead > tr > td,\n .table-responsive > .table > tbody > tr > td,\n .table-responsive > .table > tfoot > tr > td {\n white-space: nowrap;\n }\n .table-responsive > .table-bordered {\n border: 0;\n }\n .table-responsive > .table-bordered > thead > tr > th:first-child,\n .table-responsive > .table-bordered > tbody > tr > th:first-child,\n .table-responsive > .table-bordered > tfoot > tr > th:first-child,\n .table-responsive > .table-bordered > thead > tr > td:first-child,\n .table-responsive > .table-bordered > tbody > tr > td:first-child,\n .table-responsive > .table-bordered > tfoot > tr > td:first-child {\n border-left: 0;\n }\n .table-responsive > .table-bordered > thead > tr > th:last-child,\n .table-responsive > .table-bordered > tbody > tr > th:last-child,\n .table-responsive > .table-bordered > tfoot > tr > th:last-child,\n .table-responsive > .table-bordered > thead > tr > td:last-child,\n .table-responsive > .table-bordered > tbody > tr > td:last-child,\n .table-responsive > .table-bordered > tfoot > tr > td:last-child {\n border-right: 0;\n }\n .table-responsive > .table-bordered > tbody > tr:last-child > th,\n .table-responsive > .table-bordered > tfoot > tr:last-child > th,\n .table-responsive > .table-bordered > tbody > tr:last-child > td,\n .table-responsive > .table-bordered > tfoot > tr:last-child > td {\n border-bottom: 0;\n }\n}\nfieldset {\n padding: 0;\n margin: 0;\n border: 0;\n min-width: 0;\n}\nlegend {\n display: block;\n width: 100%;\n padding: 0;\n margin-bottom: 20px;\n font-size: 21px;\n line-height: inherit;\n color: #333333;\n border: 0;\n border-bottom: 1px solid #e5e5e5;\n}\nlabel {\n display: inline-block;\n max-width: 100%;\n margin-bottom: 5px;\n font-weight: bold;\n}\ninput[type=\"search\"] {\n -webkit-box-sizing: border-box;\n -moz-box-sizing: border-box;\n box-sizing: border-box;\n}\ninput[type=\"radio\"],\ninput[type=\"checkbox\"] {\n margin: 4px 0 0;\n margin-top: 1px \\9;\n line-height: normal;\n}\ninput[type=\"file\"] {\n display: block;\n}\ninput[type=\"range\"] {\n display: block;\n width: 100%;\n}\nselect[multiple],\nselect[size] {\n height: auto;\n}\ninput[type=\"file\"]:focus,\ninput[type=\"radio\"]:focus,\ninput[type=\"checkbox\"]:focus {\n outline: 5px auto -webkit-focus-ring-color;\n outline-offset: -2px;\n}\noutput {\n display: block;\n padding-top: 7px;\n font-size: 14px;\n line-height: 1.42857143;\n color: #555555;\n}\n.form-control {\n display: block;\n width: 100%;\n height: 34px;\n padding: 6px 12px;\n font-size: 14px;\n line-height: 1.42857143;\n color: #555555;\n background-color: #fff;\n background-image: none;\n border: 1px solid #ccc;\n border-radius: 4px;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\n -webkit-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;\n -o-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;\n transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;\n}\n.form-control:focus {\n border-color: #66afe9;\n outline: 0;\n -webkit-box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(102, 175, 233, 0.6);\n box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(102, 175, 233, 0.6);\n}\n.form-control::-moz-placeholder {\n color: #999;\n opacity: 1;\n}\n.form-control:-ms-input-placeholder {\n color: #999;\n}\n.form-control::-webkit-input-placeholder {\n color: #999;\n}\n.form-control::-ms-expand {\n border: 0;\n background-color: transparent;\n}\n.form-control[disabled],\n.form-control[readonly],\nfieldset[disabled] .form-control {\n background-color: #eeeeee;\n opacity: 1;\n}\n.form-control[disabled],\nfieldset[disabled] .form-control {\n cursor: not-allowed;\n}\ntextarea.form-control {\n height: auto;\n}\ninput[type=\"search\"] {\n -webkit-appearance: none;\n}\n@media screen and (-webkit-min-device-pixel-ratio: 0) {\n input[type=\"date\"].form-control,\n input[type=\"time\"].form-control,\n input[type=\"datetime-local\"].form-control,\n input[type=\"month\"].form-control {\n line-height: 34px;\n }\n input[type=\"date\"].input-sm,\n input[type=\"time\"].input-sm,\n input[type=\"datetime-local\"].input-sm,\n input[type=\"month\"].input-sm,\n .input-group-sm input[type=\"date\"],\n .input-group-sm input[type=\"time\"],\n .input-group-sm input[type=\"datetime-local\"],\n .input-group-sm input[type=\"month\"] {\n line-height: 30px;\n }\n input[type=\"date\"].input-lg,\n input[type=\"time\"].input-lg,\n input[type=\"datetime-local\"].input-lg,\n input[type=\"month\"].input-lg,\n .input-group-lg input[type=\"date\"],\n .input-group-lg input[type=\"time\"],\n .input-group-lg input[type=\"datetime-local\"],\n .input-group-lg input[type=\"month\"] {\n line-height: 46px;\n }\n}\n.form-group {\n margin-bottom: 15px;\n}\n.radio,\n.checkbox {\n position: relative;\n display: block;\n margin-top: 10px;\n margin-bottom: 10px;\n}\n.radio label,\n.checkbox label {\n min-height: 20px;\n padding-left: 20px;\n margin-bottom: 0;\n font-weight: normal;\n cursor: pointer;\n}\n.radio input[type=\"radio\"],\n.radio-inline input[type=\"radio\"],\n.checkbox input[type=\"checkbox\"],\n.checkbox-inline input[type=\"checkbox\"] {\n position: absolute;\n margin-left: -20px;\n margin-top: 4px \\9;\n}\n.radio + .radio,\n.checkbox + .checkbox {\n margin-top: -5px;\n}\n.radio-inline,\n.checkbox-inline {\n position: relative;\n display: inline-block;\n padding-left: 20px;\n margin-bottom: 0;\n vertical-align: middle;\n font-weight: normal;\n cursor: pointer;\n}\n.radio-inline + .radio-inline,\n.checkbox-inline + .checkbox-inline {\n margin-top: 0;\n margin-left: 10px;\n}\ninput[type=\"radio\"][disabled],\ninput[type=\"checkbox\"][disabled],\ninput[type=\"radio\"].disabled,\ninput[type=\"checkbox\"].disabled,\nfieldset[disabled] input[type=\"radio\"],\nfieldset[disabled] input[type=\"checkbox\"] {\n cursor: not-allowed;\n}\n.radio-inline.disabled,\n.checkbox-inline.disabled,\nfieldset[disabled] .radio-inline,\nfieldset[disabled] .checkbox-inline {\n cursor: not-allowed;\n}\n.radio.disabled label,\n.checkbox.disabled label,\nfieldset[disabled] .radio label,\nfieldset[disabled] .checkbox label {\n cursor: not-allowed;\n}\n.form-control-static {\n padding-top: 7px;\n padding-bottom: 7px;\n margin-bottom: 0;\n min-height: 34px;\n}\n.form-control-static.input-lg,\n.form-control-static.input-sm {\n padding-left: 0;\n padding-right: 0;\n}\n.input-sm {\n height: 30px;\n padding: 5px 10px;\n font-size: 12px;\n line-height: 1.5;\n border-radius: 3px;\n}\nselect.input-sm {\n height: 30px;\n line-height: 30px;\n}\ntextarea.input-sm,\nselect[multiple].input-sm {\n height: auto;\n}\n.form-group-sm .form-control {\n height: 30px;\n padding: 5px 10px;\n font-size: 12px;\n line-height: 1.5;\n border-radius: 3px;\n}\n.form-group-sm select.form-control {\n height: 30px;\n line-height: 30px;\n}\n.form-group-sm textarea.form-control,\n.form-group-sm select[multiple].form-control {\n height: auto;\n}\n.form-group-sm .form-control-static {\n height: 30px;\n min-height: 32px;\n padding: 6px 10px;\n font-size: 12px;\n line-height: 1.5;\n}\n.input-lg {\n height: 46px;\n padding: 10px 16px;\n font-size: 18px;\n line-height: 1.3333333;\n border-radius: 6px;\n}\nselect.input-lg {\n height: 46px;\n line-height: 46px;\n}\ntextarea.input-lg,\nselect[multiple].input-lg {\n height: auto;\n}\n.form-group-lg .form-control {\n height: 46px;\n padding: 10px 16px;\n font-size: 18px;\n line-height: 1.3333333;\n border-radius: 6px;\n}\n.form-group-lg select.form-control {\n height: 46px;\n line-height: 46px;\n}\n.form-group-lg textarea.form-control,\n.form-group-lg select[multiple].form-control {\n height: auto;\n}\n.form-group-lg .form-control-static {\n height: 46px;\n min-height: 38px;\n padding: 11px 16px;\n font-size: 18px;\n line-height: 1.3333333;\n}\n.has-feedback {\n position: relative;\n}\n.has-feedback .form-control {\n padding-right: 42.5px;\n}\n.form-control-feedback {\n position: absolute;\n top: 0;\n right: 0;\n z-index: 2;\n display: block;\n width: 34px;\n height: 34px;\n line-height: 34px;\n text-align: center;\n pointer-events: none;\n}\n.input-lg + .form-control-feedback,\n.input-group-lg + .form-control-feedback,\n.form-group-lg .form-control + .form-control-feedback {\n width: 46px;\n height: 46px;\n line-height: 46px;\n}\n.input-sm + .form-control-feedback,\n.input-group-sm + .form-control-feedback,\n.form-group-sm .form-control + .form-control-feedback {\n width: 30px;\n height: 30px;\n line-height: 30px;\n}\n.has-success .help-block,\n.has-success .control-label,\n.has-success .radio,\n.has-success .checkbox,\n.has-success .radio-inline,\n.has-success .checkbox-inline,\n.has-success.radio label,\n.has-success.checkbox label,\n.has-success.radio-inline label,\n.has-success.checkbox-inline label {\n color: #3c763d;\n}\n.has-success .form-control {\n border-color: #3c763d;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\n}\n.has-success .form-control:focus {\n border-color: #2b542c;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #67b168;\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #67b168;\n}\n.has-success .input-group-addon {\n color: #3c763d;\n border-color: #3c763d;\n background-color: #dff0d8;\n}\n.has-success .form-control-feedback {\n color: #3c763d;\n}\n.has-warning .help-block,\n.has-warning .control-label,\n.has-warning .radio,\n.has-warning .checkbox,\n.has-warning .radio-inline,\n.has-warning .checkbox-inline,\n.has-warning.radio label,\n.has-warning.checkbox label,\n.has-warning.radio-inline label,\n.has-warning.checkbox-inline label {\n color: #8a6d3b;\n}\n.has-warning .form-control {\n border-color: #8a6d3b;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\n}\n.has-warning .form-control:focus {\n border-color: #66512c;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #c0a16b;\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #c0a16b;\n}\n.has-warning .input-group-addon {\n color: #8a6d3b;\n border-color: #8a6d3b;\n background-color: #fcf8e3;\n}\n.has-warning .form-control-feedback {\n color: #8a6d3b;\n}\n.has-error .help-block,\n.has-error .control-label,\n.has-error .radio,\n.has-error .checkbox,\n.has-error .radio-inline,\n.has-error .checkbox-inline,\n.has-error.radio label,\n.has-error.checkbox label,\n.has-error.radio-inline label,\n.has-error.checkbox-inline label {\n color: #a94442;\n}\n.has-error .form-control {\n border-color: #a94442;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\n}\n.has-error .form-control:focus {\n border-color: #843534;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #ce8483;\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #ce8483;\n}\n.has-error .input-group-addon {\n color: #a94442;\n border-color: #a94442;\n background-color: #f2dede;\n}\n.has-error .form-control-feedback {\n color: #a94442;\n}\n.has-feedback label ~ .form-control-feedback {\n top: 25px;\n}\n.has-feedback label.sr-only ~ .form-control-feedback {\n top: 0;\n}\n.help-block {\n display: block;\n margin-top: 5px;\n margin-bottom: 10px;\n color: #737373;\n}\n@media (min-width: 768px) {\n .form-inline .form-group {\n display: inline-block;\n margin-bottom: 0;\n vertical-align: middle;\n }\n .form-inline .form-control {\n display: inline-block;\n width: auto;\n vertical-align: middle;\n }\n .form-inline .form-control-static {\n display: inline-block;\n }\n .form-inline .input-group {\n display: inline-table;\n vertical-align: middle;\n }\n .form-inline .input-group .input-group-addon,\n .form-inline .input-group .input-group-btn,\n .form-inline .input-group .form-control {\n width: auto;\n }\n .form-inline .input-group > .form-control {\n width: 100%;\n }\n .form-inline .control-label {\n margin-bottom: 0;\n vertical-align: middle;\n }\n .form-inline .radio,\n .form-inline .checkbox {\n display: inline-block;\n margin-top: 0;\n margin-bottom: 0;\n vertical-align: middle;\n }\n .form-inline .radio label,\n .form-inline .checkbox label {\n padding-left: 0;\n }\n .form-inline .radio input[type=\"radio\"],\n .form-inline .checkbox input[type=\"checkbox\"] {\n position: relative;\n margin-left: 0;\n }\n .form-inline .has-feedback .form-control-feedback {\n top: 0;\n }\n}\n.form-horizontal .radio,\n.form-horizontal .checkbox,\n.form-horizontal .radio-inline,\n.form-horizontal .checkbox-inline {\n margin-top: 0;\n margin-bottom: 0;\n padding-top: 7px;\n}\n.form-horizontal .radio,\n.form-horizontal .checkbox {\n min-height: 27px;\n}\n.form-horizontal .form-group {\n margin-left: -15px;\n margin-right: -15px;\n}\n@media (min-width: 768px) {\n .form-horizontal .control-label {\n text-align: right;\n margin-bottom: 0;\n padding-top: 7px;\n }\n}\n.form-horizontal .has-feedback .form-control-feedback {\n right: 15px;\n}\n@media (min-width: 768px) {\n .form-horizontal .form-group-lg .control-label {\n padding-top: 11px;\n font-size: 18px;\n }\n}\n@media (min-width: 768px) {\n .form-horizontal .form-group-sm .control-label {\n padding-top: 6px;\n font-size: 12px;\n }\n}\n.btn {\n display: inline-block;\n margin-bottom: 0;\n font-weight: normal;\n text-align: center;\n vertical-align: middle;\n touch-action: manipulation;\n cursor: pointer;\n background-image: none;\n border: 1px solid transparent;\n white-space: nowrap;\n padding: 6px 12px;\n font-size: 14px;\n line-height: 1.42857143;\n border-radius: 4px;\n -webkit-user-select: none;\n -moz-user-select: none;\n -ms-user-select: none;\n user-select: none;\n}\n.btn:focus,\n.btn:active:focus,\n.btn.active:focus,\n.btn.focus,\n.btn:active.focus,\n.btn.active.focus {\n outline: 5px auto -webkit-focus-ring-color;\n outline-offset: -2px;\n}\n.btn:hover,\n.btn:focus,\n.btn.focus {\n color: #333;\n text-decoration: none;\n}\n.btn:active,\n.btn.active {\n outline: 0;\n background-image: none;\n -webkit-box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);\n box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);\n}\n.btn.disabled,\n.btn[disabled],\nfieldset[disabled] .btn {\n cursor: not-allowed;\n opacity: 0.65;\n filter: alpha(opacity=65);\n -webkit-box-shadow: none;\n box-shadow: none;\n}\na.btn.disabled,\nfieldset[disabled] a.btn {\n pointer-events: none;\n}\n.btn-default {\n color: #333;\n background-color: #fff;\n border-color: #ccc;\n}\n.btn-default:focus,\n.btn-default.focus {\n color: #333;\n background-color: #e6e6e6;\n border-color: #8c8c8c;\n}\n.btn-default:hover {\n color: #333;\n background-color: #e6e6e6;\n border-color: #adadad;\n}\n.btn-default:active,\n.btn-default.active,\n.open > .dropdown-toggle.btn-default {\n color: #333;\n background-color: #e6e6e6;\n border-color: #adadad;\n}\n.btn-default:active:hover,\n.btn-default.active:hover,\n.open > .dropdown-toggle.btn-default:hover,\n.btn-default:active:focus,\n.btn-default.active:focus,\n.open > .dropdown-toggle.btn-default:focus,\n.btn-default:active.focus,\n.btn-default.active.focus,\n.open > .dropdown-toggle.btn-default.focus {\n color: #333;\n background-color: #d4d4d4;\n border-color: #8c8c8c;\n}\n.btn-default:active,\n.btn-default.active,\n.open > .dropdown-toggle.btn-default {\n background-image: none;\n}\n.btn-default.disabled:hover,\n.btn-default[disabled]:hover,\nfieldset[disabled] .btn-default:hover,\n.btn-default.disabled:focus,\n.btn-default[disabled]:focus,\nfieldset[disabled] .btn-default:focus,\n.btn-default.disabled.focus,\n.btn-default[disabled].focus,\nfieldset[disabled] .btn-default.focus {\n background-color: #fff;\n border-color: #ccc;\n}\n.btn-default .badge {\n color: #fff;\n background-color: #333;\n}\n.btn-primary {\n color: #fff;\n background-color: #337ab7;\n border-color: #2e6da4;\n}\n.btn-primary:focus,\n.btn-primary.focus {\n color: #fff;\n background-color: #286090;\n border-color: #122b40;\n}\n.btn-primary:hover {\n color: #fff;\n background-color: #286090;\n border-color: #204d74;\n}\n.btn-primary:active,\n.btn-primary.active,\n.open > .dropdown-toggle.btn-primary {\n color: #fff;\n background-color: #286090;\n border-color: #204d74;\n}\n.btn-primary:active:hover,\n.btn-primary.active:hover,\n.open > .dropdown-toggle.btn-primary:hover,\n.btn-primary:active:focus,\n.btn-primary.active:focus,\n.open > .dropdown-toggle.btn-primary:focus,\n.btn-primary:active.focus,\n.btn-primary.active.focus,\n.open > .dropdown-toggle.btn-primary.focus {\n color: #fff;\n background-color: #204d74;\n border-color: #122b40;\n}\n.btn-primary:active,\n.btn-primary.active,\n.open > .dropdown-toggle.btn-primary {\n background-image: none;\n}\n.btn-primary.disabled:hover,\n.btn-primary[disabled]:hover,\nfieldset[disabled] .btn-primary:hover,\n.btn-primary.disabled:focus,\n.btn-primary[disabled]:focus,\nfieldset[disabled] .btn-primary:focus,\n.btn-primary.disabled.focus,\n.btn-primary[disabled].focus,\nfieldset[disabled] .btn-primary.focus {\n background-color: #337ab7;\n border-color: #2e6da4;\n}\n.btn-primary .badge {\n color: #337ab7;\n background-color: #fff;\n}\n.btn-success {\n color: #fff;\n background-color: #5cb85c;\n border-color: #4cae4c;\n}\n.btn-success:focus,\n.btn-success.focus {\n color: #fff;\n background-color: #449d44;\n border-color: #255625;\n}\n.btn-success:hover {\n color: #fff;\n background-color: #449d44;\n border-color: #398439;\n}\n.btn-success:active,\n.btn-success.active,\n.open > .dropdown-toggle.btn-success {\n color: #fff;\n background-color: #449d44;\n border-color: #398439;\n}\n.btn-success:active:hover,\n.btn-success.active:hover,\n.open > .dropdown-toggle.btn-success:hover,\n.btn-success:active:focus,\n.btn-success.active:focus,\n.open > .dropdown-toggle.btn-success:focus,\n.btn-success:active.focus,\n.btn-success.active.focus,\n.open > .dropdown-toggle.btn-success.focus {\n color: #fff;\n background-color: #398439;\n border-color: #255625;\n}\n.btn-success:active,\n.btn-success.active,\n.open > .dropdown-toggle.btn-success {\n background-image: none;\n}\n.btn-success.disabled:hover,\n.btn-success[disabled]:hover,\nfieldset[disabled] .btn-success:hover,\n.btn-success.disabled:focus,\n.btn-success[disabled]:focus,\nfieldset[disabled] .btn-success:focus,\n.btn-success.disabled.focus,\n.btn-success[disabled].focus,\nfieldset[disabled] .btn-success.focus {\n background-color: #5cb85c;\n border-color: #4cae4c;\n}\n.btn-success .badge {\n color: #5cb85c;\n background-color: #fff;\n}\n.btn-info {\n color: #fff;\n background-color: #5bc0de;\n border-color: #46b8da;\n}\n.btn-info:focus,\n.btn-info.focus {\n color: #fff;\n background-color: #31b0d5;\n border-color: #1b6d85;\n}\n.btn-info:hover {\n color: #fff;\n background-color: #31b0d5;\n border-color: #269abc;\n}\n.btn-info:active,\n.btn-info.active,\n.open > .dropdown-toggle.btn-info {\n color: #fff;\n background-color: #31b0d5;\n border-color: #269abc;\n}\n.btn-info:active:hover,\n.btn-info.active:hover,\n.open > .dropdown-toggle.btn-info:hover,\n.btn-info:active:focus,\n.btn-info.active:focus,\n.open > .dropdown-toggle.btn-info:focus,\n.btn-info:active.focus,\n.btn-info.active.focus,\n.open > .dropdown-toggle.btn-info.focus {\n color: #fff;\n background-color: #269abc;\n border-color: #1b6d85;\n}\n.btn-info:active,\n.btn-info.active,\n.open > .dropdown-toggle.btn-info {\n background-image: none;\n}\n.btn-info.disabled:hover,\n.btn-info[disabled]:hover,\nfieldset[disabled] .btn-info:hover,\n.btn-info.disabled:focus,\n.btn-info[disabled]:focus,\nfieldset[disabled] .btn-info:focus,\n.btn-info.disabled.focus,\n.btn-info[disabled].focus,\nfieldset[disabled] .btn-info.focus {\n background-color: #5bc0de;\n border-color: #46b8da;\n}\n.btn-info .badge {\n color: #5bc0de;\n background-color: #fff;\n}\n.btn-warning {\n color: #fff;\n background-color: #f0ad4e;\n border-color: #eea236;\n}\n.btn-warning:focus,\n.btn-warning.focus {\n color: #fff;\n background-color: #ec971f;\n border-color: #985f0d;\n}\n.btn-warning:hover {\n color: #fff;\n background-color: #ec971f;\n border-color: #d58512;\n}\n.btn-warning:active,\n.btn-warning.active,\n.open > .dropdown-toggle.btn-warning {\n color: #fff;\n background-color: #ec971f;\n border-color: #d58512;\n}\n.btn-warning:active:hover,\n.btn-warning.active:hover,\n.open > .dropdown-toggle.btn-warning:hover,\n.btn-warning:active:focus,\n.btn-warning.active:focus,\n.open > .dropdown-toggle.btn-warning:focus,\n.btn-warning:active.focus,\n.btn-warning.active.focus,\n.open > .dropdown-toggle.btn-warning.focus {\n color: #fff;\n background-color: #d58512;\n border-color: #985f0d;\n}\n.btn-warning:active,\n.btn-warning.active,\n.open > .dropdown-toggle.btn-warning {\n background-image: none;\n}\n.btn-warning.disabled:hover,\n.btn-warning[disabled]:hover,\nfieldset[disabled] .btn-warning:hover,\n.btn-warning.disabled:focus,\n.btn-warning[disabled]:focus,\nfieldset[disabled] .btn-warning:focus,\n.btn-warning.disabled.focus,\n.btn-warning[disabled].focus,\nfieldset[disabled] .btn-warning.focus {\n background-color: #f0ad4e;\n border-color: #eea236;\n}\n.btn-warning .badge {\n color: #f0ad4e;\n background-color: #fff;\n}\n.btn-danger {\n color: #fff;\n background-color: #d9534f;\n border-color: #d43f3a;\n}\n.btn-danger:focus,\n.btn-danger.focus {\n color: #fff;\n background-color: #c9302c;\n border-color: #761c19;\n}\n.btn-danger:hover {\n color: #fff;\n background-color: #c9302c;\n border-color: #ac2925;\n}\n.btn-danger:active,\n.btn-danger.active,\n.open > .dropdown-toggle.btn-danger {\n color: #fff;\n background-color: #c9302c;\n border-color: #ac2925;\n}\n.btn-danger:active:hover,\n.btn-danger.active:hover,\n.open > .dropdown-toggle.btn-danger:hover,\n.btn-danger:active:focus,\n.btn-danger.active:focus,\n.open > .dropdown-toggle.btn-danger:focus,\n.btn-danger:active.focus,\n.btn-danger.active.focus,\n.open > .dropdown-toggle.btn-danger.focus {\n color: #fff;\n background-color: #ac2925;\n border-color: #761c19;\n}\n.btn-danger:active,\n.btn-danger.active,\n.open > .dropdown-toggle.btn-danger {\n background-image: none;\n}\n.btn-danger.disabled:hover,\n.btn-danger[disabled]:hover,\nfieldset[disabled] .btn-danger:hover,\n.btn-danger.disabled:focus,\n.btn-danger[disabled]:focus,\nfieldset[disabled] .btn-danger:focus,\n.btn-danger.disabled.focus,\n.btn-danger[disabled].focus,\nfieldset[disabled] .btn-danger.focus {\n background-color: #d9534f;\n border-color: #d43f3a;\n}\n.btn-danger .badge {\n color: #d9534f;\n background-color: #fff;\n}\n.btn-link {\n color: #337ab7;\n font-weight: normal;\n border-radius: 0;\n}\n.btn-link,\n.btn-link:active,\n.btn-link.active,\n.btn-link[disabled],\nfieldset[disabled] .btn-link {\n background-color: transparent;\n -webkit-box-shadow: none;\n box-shadow: none;\n}\n.btn-link,\n.btn-link:hover,\n.btn-link:focus,\n.btn-link:active {\n border-color: transparent;\n}\n.btn-link:hover,\n.btn-link:focus {\n color: #23527c;\n text-decoration: underline;\n background-color: transparent;\n}\n.btn-link[disabled]:hover,\nfieldset[disabled] .btn-link:hover,\n.btn-link[disabled]:focus,\nfieldset[disabled] .btn-link:focus {\n color: #777777;\n text-decoration: none;\n}\n.btn-lg,\n.btn-group-lg > .btn {\n padding: 10px 16px;\n font-size: 18px;\n line-height: 1.3333333;\n border-radius: 6px;\n}\n.btn-sm,\n.btn-group-sm > .btn {\n padding: 5px 10px;\n font-size: 12px;\n line-height: 1.5;\n border-radius: 3px;\n}\n.btn-xs,\n.btn-group-xs > .btn {\n padding: 1px 5px;\n font-size: 12px;\n line-height: 1.5;\n border-radius: 3px;\n}\n.btn-block {\n display: block;\n width: 100%;\n}\n.btn-block + .btn-block {\n margin-top: 5px;\n}\ninput[type=\"submit\"].btn-block,\ninput[type=\"reset\"].btn-block,\ninput[type=\"button\"].btn-block {\n width: 100%;\n}\n.fade {\n opacity: 0;\n -webkit-transition: opacity 0.15s linear;\n -o-transition: opacity 0.15s linear;\n transition: opacity 0.15s linear;\n}\n.fade.in {\n opacity: 1;\n}\n.collapse {\n display: none;\n}\n.collapse.in {\n display: block;\n}\ntr.collapse.in {\n display: table-row;\n}\ntbody.collapse.in {\n display: table-row-group;\n}\n.collapsing {\n position: relative;\n height: 0;\n overflow: hidden;\n -webkit-transition-property: height, visibility;\n transition-property: height, visibility;\n -webkit-transition-duration: 0.35s;\n transition-duration: 0.35s;\n -webkit-transition-timing-function: ease;\n transition-timing-function: ease;\n}\n.caret {\n display: inline-block;\n width: 0;\n height: 0;\n margin-left: 2px;\n vertical-align: middle;\n border-top: 4px dashed;\n border-top: 4px solid \\9;\n border-right: 4px solid transparent;\n border-left: 4px solid transparent;\n}\n.dropup,\n.dropdown {\n position: relative;\n}\n.dropdown-toggle:focus {\n outline: 0;\n}\n.dropdown-menu {\n position: absolute;\n top: 100%;\n left: 0;\n z-index: 1000;\n display: none;\n float: left;\n min-width: 160px;\n padding: 5px 0;\n margin: 2px 0 0;\n list-style: none;\n font-size: 14px;\n text-align: left;\n background-color: #fff;\n border: 1px solid #ccc;\n border: 1px solid rgba(0, 0, 0, 0.15);\n border-radius: 4px;\n -webkit-box-shadow: 0 6px 12px rgba(0, 0, 0, 0.175);\n box-shadow: 0 6px 12px rgba(0, 0, 0, 0.175);\n background-clip: padding-box;\n}\n.dropdown-menu.pull-right {\n right: 0;\n left: auto;\n}\n.dropdown-menu .divider {\n height: 1px;\n margin: 9px 0;\n overflow: hidden;\n background-color: #e5e5e5;\n}\n.dropdown-menu > li > a {\n display: block;\n padding: 3px 20px;\n clear: both;\n font-weight: normal;\n line-height: 1.42857143;\n color: #333333;\n white-space: nowrap;\n}\n.dropdown-menu > li > a:hover,\n.dropdown-menu > li > a:focus {\n text-decoration: none;\n color: #262626;\n background-color: #f5f5f5;\n}\n.dropdown-menu > .active > a,\n.dropdown-menu > .active > a:hover,\n.dropdown-menu > .active > a:focus {\n color: #fff;\n text-decoration: none;\n outline: 0;\n background-color: #337ab7;\n}\n.dropdown-menu > .disabled > a,\n.dropdown-menu > .disabled > a:hover,\n.dropdown-menu > .disabled > a:focus {\n color: #777777;\n}\n.dropdown-menu > .disabled > a:hover,\n.dropdown-menu > .disabled > a:focus {\n text-decoration: none;\n background-color: transparent;\n background-image: none;\n filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);\n cursor: not-allowed;\n}\n.open > .dropdown-menu {\n display: block;\n}\n.open > a {\n outline: 0;\n}\n.dropdown-menu-right {\n left: auto;\n right: 0;\n}\n.dropdown-menu-left {\n left: 0;\n right: auto;\n}\n.dropdown-header {\n display: block;\n padding: 3px 20px;\n font-size: 12px;\n line-height: 1.42857143;\n color: #777777;\n white-space: nowrap;\n}\n.dropdown-backdrop {\n position: fixed;\n left: 0;\n right: 0;\n bottom: 0;\n top: 0;\n z-index: 990;\n}\n.pull-right > .dropdown-menu {\n right: 0;\n left: auto;\n}\n.dropup .caret,\n.navbar-fixed-bottom .dropdown .caret {\n border-top: 0;\n border-bottom: 4px dashed;\n border-bottom: 4px solid \\9;\n content: \"\";\n}\n.dropup .dropdown-menu,\n.navbar-fixed-bottom .dropdown .dropdown-menu {\n top: auto;\n bottom: 100%;\n margin-bottom: 2px;\n}\n@media (min-width: 768px) {\n .navbar-right .dropdown-menu {\n left: auto;\n right: 0;\n }\n .navbar-right .dropdown-menu-left {\n left: 0;\n right: auto;\n }\n}\n.btn-group,\n.btn-group-vertical {\n position: relative;\n display: inline-block;\n vertical-align: middle;\n}\n.btn-group > .btn,\n.btn-group-vertical > .btn {\n position: relative;\n float: left;\n}\n.btn-group > .btn:hover,\n.btn-group-vertical > .btn:hover,\n.btn-group > .btn:focus,\n.btn-group-vertical > .btn:focus,\n.btn-group > .btn:active,\n.btn-group-vertical > .btn:active,\n.btn-group > .btn.active,\n.btn-group-vertical > .btn.active {\n z-index: 2;\n}\n.btn-group .btn + .btn,\n.btn-group .btn + .btn-group,\n.btn-group .btn-group + .btn,\n.btn-group .btn-group + .btn-group {\n margin-left: -1px;\n}\n.btn-toolbar {\n margin-left: -5px;\n}\n.btn-toolbar .btn,\n.btn-toolbar .btn-group,\n.btn-toolbar .input-group {\n float: left;\n}\n.btn-toolbar > .btn,\n.btn-toolbar > .btn-group,\n.btn-toolbar > .input-group {\n margin-left: 5px;\n}\n.btn-group > .btn:not(:first-child):not(:last-child):not(.dropdown-toggle) {\n border-radius: 0;\n}\n.btn-group > .btn:first-child {\n margin-left: 0;\n}\n.btn-group > .btn:first-child:not(:last-child):not(.dropdown-toggle) {\n border-bottom-right-radius: 0;\n border-top-right-radius: 0;\n}\n.btn-group > .btn:last-child:not(:first-child),\n.btn-group > .dropdown-toggle:not(:first-child) {\n border-bottom-left-radius: 0;\n border-top-left-radius: 0;\n}\n.btn-group > .btn-group {\n float: left;\n}\n.btn-group > .btn-group:not(:first-child):not(:last-child) > .btn {\n border-radius: 0;\n}\n.btn-group > .btn-group:first-child:not(:last-child) > .btn:last-child,\n.btn-group > .btn-group:first-child:not(:last-child) > .dropdown-toggle {\n border-bottom-right-radius: 0;\n border-top-right-radius: 0;\n}\n.btn-group > .btn-group:last-child:not(:first-child) > .btn:first-child {\n border-bottom-left-radius: 0;\n border-top-left-radius: 0;\n}\n.btn-group .dropdown-toggle:active,\n.btn-group.open .dropdown-toggle {\n outline: 0;\n}\n.btn-group > .btn + .dropdown-toggle {\n padding-left: 8px;\n padding-right: 8px;\n}\n.btn-group > .btn-lg + .dropdown-toggle {\n padding-left: 12px;\n padding-right: 12px;\n}\n.btn-group.open .dropdown-toggle {\n -webkit-box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);\n box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);\n}\n.btn-group.open .dropdown-toggle.btn-link {\n -webkit-box-shadow: none;\n box-shadow: none;\n}\n.btn .caret {\n margin-left: 0;\n}\n.btn-lg .caret {\n border-width: 5px 5px 0;\n border-bottom-width: 0;\n}\n.dropup .btn-lg .caret {\n border-width: 0 5px 5px;\n}\n.btn-group-vertical > .btn,\n.btn-group-vertical > .btn-group,\n.btn-group-vertical > .btn-group > .btn {\n display: block;\n float: none;\n width: 100%;\n max-width: 100%;\n}\n.btn-group-vertical > .btn-group > .btn {\n float: none;\n}\n.btn-group-vertical > .btn + .btn,\n.btn-group-vertical > .btn + .btn-group,\n.btn-group-vertical > .btn-group + .btn,\n.btn-group-vertical > .btn-group + .btn-group {\n margin-top: -1px;\n margin-left: 0;\n}\n.btn-group-vertical > .btn:not(:first-child):not(:last-child) {\n border-radius: 0;\n}\n.btn-group-vertical > .btn:first-child:not(:last-child) {\n border-top-right-radius: 4px;\n border-top-left-radius: 4px;\n border-bottom-right-radius: 0;\n border-bottom-left-radius: 0;\n}\n.btn-group-vertical > .btn:last-child:not(:first-child) {\n border-top-right-radius: 0;\n border-top-left-radius: 0;\n border-bottom-right-radius: 4px;\n border-bottom-left-radius: 4px;\n}\n.btn-group-vertical > .btn-group:not(:first-child):not(:last-child) > .btn {\n border-radius: 0;\n}\n.btn-group-vertical > .btn-group:first-child:not(:last-child) > .btn:last-child,\n.btn-group-vertical > .btn-group:first-child:not(:last-child) > .dropdown-toggle {\n border-bottom-right-radius: 0;\n border-bottom-left-radius: 0;\n}\n.btn-group-vertical > .btn-group:last-child:not(:first-child) > .btn:first-child {\n border-top-right-radius: 0;\n border-top-left-radius: 0;\n}\n.btn-group-justified {\n display: table;\n width: 100%;\n table-layout: fixed;\n border-collapse: separate;\n}\n.btn-group-justified > .btn,\n.btn-group-justified > .btn-group {\n float: none;\n display: table-cell;\n width: 1%;\n}\n.btn-group-justified > .btn-group .btn {\n width: 100%;\n}\n.btn-group-justified > .btn-group .dropdown-menu {\n left: auto;\n}\n[data-toggle=\"buttons\"] > .btn input[type=\"radio\"],\n[data-toggle=\"buttons\"] > .btn-group > .btn input[type=\"radio\"],\n[data-toggle=\"buttons\"] > .btn input[type=\"checkbox\"],\n[data-toggle=\"buttons\"] > .btn-group > .btn input[type=\"checkbox\"] {\n position: absolute;\n clip: rect(0, 0, 0, 0);\n pointer-events: none;\n}\n.input-group {\n position: relative;\n display: table;\n border-collapse: separate;\n}\n.input-group[class*=\"col-\"] {\n float: none;\n padding-left: 0;\n padding-right: 0;\n}\n.input-group .form-control {\n position: relative;\n z-index: 2;\n float: left;\n width: 100%;\n margin-bottom: 0;\n}\n.input-group .form-control:focus {\n z-index: 3;\n}\n.input-group-lg > .form-control,\n.input-group-lg > .input-group-addon,\n.input-group-lg > .input-group-btn > .btn {\n height: 46px;\n padding: 10px 16px;\n font-size: 18px;\n line-height: 1.3333333;\n border-radius: 6px;\n}\nselect.input-group-lg > .form-control,\nselect.input-group-lg > .input-group-addon,\nselect.input-group-lg > .input-group-btn > .btn {\n height: 46px;\n line-height: 46px;\n}\ntextarea.input-group-lg > .form-control,\ntextarea.input-group-lg > .input-group-addon,\ntextarea.input-group-lg > .input-group-btn > .btn,\nselect[multiple].input-group-lg > .form-control,\nselect[multiple].input-group-lg > .input-group-addon,\nselect[multiple].input-group-lg > .input-group-btn > .btn {\n height: auto;\n}\n.input-group-sm > .form-control,\n.input-group-sm > .input-group-addon,\n.input-group-sm > .input-group-btn > .btn {\n height: 30px;\n padding: 5px 10px;\n font-size: 12px;\n line-height: 1.5;\n border-radius: 3px;\n}\nselect.input-group-sm > .form-control,\nselect.input-group-sm > .input-group-addon,\nselect.input-group-sm > .input-group-btn > .btn {\n height: 30px;\n line-height: 30px;\n}\ntextarea.input-group-sm > .form-control,\ntextarea.input-group-sm > .input-group-addon,\ntextarea.input-group-sm > .input-group-btn > .btn,\nselect[multiple].input-group-sm > .form-control,\nselect[multiple].input-group-sm > .input-group-addon,\nselect[multiple].input-group-sm > .input-group-btn > .btn {\n height: auto;\n}\n.input-group-addon,\n.input-group-btn,\n.input-group .form-control {\n display: table-cell;\n}\n.input-group-addon:not(:first-child):not(:last-child),\n.input-group-btn:not(:first-child):not(:last-child),\n.input-group .form-control:not(:first-child):not(:last-child) {\n border-radius: 0;\n}\n.input-group-addon,\n.input-group-btn {\n width: 1%;\n white-space: nowrap;\n vertical-align: middle;\n}\n.input-group-addon {\n padding: 6px 12px;\n font-size: 14px;\n font-weight: normal;\n line-height: 1;\n color: #555555;\n text-align: center;\n background-color: #eeeeee;\n border: 1px solid #ccc;\n border-radius: 4px;\n}\n.input-group-addon.input-sm {\n padding: 5px 10px;\n font-size: 12px;\n border-radius: 3px;\n}\n.input-group-addon.input-lg {\n padding: 10px 16px;\n font-size: 18px;\n border-radius: 6px;\n}\n.input-group-addon input[type=\"radio\"],\n.input-group-addon input[type=\"checkbox\"] {\n margin-top: 0;\n}\n.input-group .form-control:first-child,\n.input-group-addon:first-child,\n.input-group-btn:first-child > .btn,\n.input-group-btn:first-child > .btn-group > .btn,\n.input-group-btn:first-child > .dropdown-toggle,\n.input-group-btn:last-child > .btn:not(:last-child):not(.dropdown-toggle),\n.input-group-btn:last-child > .btn-group:not(:last-child) > .btn {\n border-bottom-right-radius: 0;\n border-top-right-radius: 0;\n}\n.input-group-addon:first-child {\n border-right: 0;\n}\n.input-group .form-control:last-child,\n.input-group-addon:last-child,\n.input-group-btn:last-child > .btn,\n.input-group-btn:last-child > .btn-group > .btn,\n.input-group-btn:last-child > .dropdown-toggle,\n.input-group-btn:first-child > .btn:not(:first-child),\n.input-group-btn:first-child > .btn-group:not(:first-child) > .btn {\n border-bottom-left-radius: 0;\n border-top-left-radius: 0;\n}\n.input-group-addon:last-child {\n border-left: 0;\n}\n.input-group-btn {\n position: relative;\n font-size: 0;\n white-space: nowrap;\n}\n.input-group-btn > .btn {\n position: relative;\n}\n.input-group-btn > .btn + .btn {\n margin-left: -1px;\n}\n.input-group-btn > .btn:hover,\n.input-group-btn > .btn:focus,\n.input-group-btn > .btn:active {\n z-index: 2;\n}\n.input-group-btn:first-child > .btn,\n.input-group-btn:first-child > .btn-group {\n margin-right: -1px;\n}\n.input-group-btn:last-child > .btn,\n.input-group-btn:last-child > .btn-group {\n z-index: 2;\n margin-left: -1px;\n}\n.nav {\n margin-bottom: 0;\n padding-left: 0;\n list-style: none;\n}\n.nav > li {\n position: relative;\n display: block;\n}\n.nav > li > a {\n position: relative;\n display: block;\n padding: 10px 15px;\n}\n.nav > li > a:hover,\n.nav > li > a:focus {\n text-decoration: none;\n background-color: #eeeeee;\n}\n.nav > li.disabled > a {\n color: #777777;\n}\n.nav > li.disabled > a:hover,\n.nav > li.disabled > a:focus {\n color: #777777;\n text-decoration: none;\n background-color: transparent;\n cursor: not-allowed;\n}\n.nav .open > a,\n.nav .open > a:hover,\n.nav .open > a:focus {\n background-color: #eeeeee;\n border-color: #337ab7;\n}\n.nav .nav-divider {\n height: 1px;\n margin: 9px 0;\n overflow: hidden;\n background-color: #e5e5e5;\n}\n.nav > li > a > img {\n max-width: none;\n}\n.nav-tabs {\n border-bottom: 1px solid #ddd;\n}\n.nav-tabs > li {\n float: left;\n margin-bottom: -1px;\n}\n.nav-tabs > li > a {\n margin-right: 2px;\n line-height: 1.42857143;\n border: 1px solid transparent;\n border-radius: 4px 4px 0 0;\n}\n.nav-tabs > li > a:hover {\n border-color: #eeeeee #eeeeee #ddd;\n}\n.nav-tabs > li.active > a,\n.nav-tabs > li.active > a:hover,\n.nav-tabs > li.active > a:focus {\n color: #555555;\n background-color: #fff;\n border: 1px solid #ddd;\n border-bottom-color: transparent;\n cursor: default;\n}\n.nav-tabs.nav-justified {\n width: 100%;\n border-bottom: 0;\n}\n.nav-tabs.nav-justified > li {\n float: none;\n}\n.nav-tabs.nav-justified > li > a {\n text-align: center;\n margin-bottom: 5px;\n}\n.nav-tabs.nav-justified > .dropdown .dropdown-menu {\n top: auto;\n left: auto;\n}\n@media (min-width: 768px) {\n .nav-tabs.nav-justified > li {\n display: table-cell;\n width: 1%;\n }\n .nav-tabs.nav-justified > li > a {\n margin-bottom: 0;\n }\n}\n.nav-tabs.nav-justified > li > a {\n margin-right: 0;\n border-radius: 4px;\n}\n.nav-tabs.nav-justified > .active > a,\n.nav-tabs.nav-justified > .active > a:hover,\n.nav-tabs.nav-justified > .active > a:focus {\n border: 1px solid #ddd;\n}\n@media (min-width: 768px) {\n .nav-tabs.nav-justified > li > a {\n border-bottom: 1px solid #ddd;\n border-radius: 4px 4px 0 0;\n }\n .nav-tabs.nav-justified > .active > a,\n .nav-tabs.nav-justified > .active > a:hover,\n .nav-tabs.nav-justified > .active > a:focus {\n border-bottom-color: #fff;\n }\n}\n.nav-pills > li {\n float: left;\n}\n.nav-pills > li > a {\n border-radius: 4px;\n}\n.nav-pills > li + li {\n margin-left: 2px;\n}\n.nav-pills > li.active > a,\n.nav-pills > li.active > a:hover,\n.nav-pills > li.active > a:focus {\n color: #fff;\n background-color: #337ab7;\n}\n.nav-stacked > li {\n float: none;\n}\n.nav-stacked > li + li {\n margin-top: 2px;\n margin-left: 0;\n}\n.nav-justified {\n width: 100%;\n}\n.nav-justified > li {\n float: none;\n}\n.nav-justified > li > a {\n text-align: center;\n margin-bottom: 5px;\n}\n.nav-justified > .dropdown .dropdown-menu {\n top: auto;\n left: auto;\n}\n@media (min-width: 768px) {\n .nav-justified > li {\n display: table-cell;\n width: 1%;\n }\n .nav-justified > li > a {\n margin-bottom: 0;\n }\n}\n.nav-tabs-justified {\n border-bottom: 0;\n}\n.nav-tabs-justified > li > a {\n margin-right: 0;\n border-radius: 4px;\n}\n.nav-tabs-justified > .active > a,\n.nav-tabs-justified > .active > a:hover,\n.nav-tabs-justified > .active > a:focus {\n border: 1px solid #ddd;\n}\n@media (min-width: 768px) {\n .nav-tabs-justified > li > a {\n border-bottom: 1px solid #ddd;\n border-radius: 4px 4px 0 0;\n }\n .nav-tabs-justified > .active > a,\n .nav-tabs-justified > .active > a:hover,\n .nav-tabs-justified > .active > a:focus {\n border-bottom-color: #fff;\n }\n}\n.tab-content > .tab-pane {\n display: none;\n}\n.tab-content > .active {\n display: block;\n}\n.nav-tabs .dropdown-menu {\n margin-top: -1px;\n border-top-right-radius: 0;\n border-top-left-radius: 0;\n}\n.navbar {\n position: relative;\n min-height: 50px;\n margin-bottom: 20px;\n border: 1px solid transparent;\n}\n@media (min-width: 768px) {\n .navbar {\n border-radius: 4px;\n }\n}\n@media (min-width: 768px) {\n .navbar-header {\n float: left;\n }\n}\n.navbar-collapse {\n overflow-x: visible;\n padding-right: 15px;\n padding-left: 15px;\n border-top: 1px solid transparent;\n box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1);\n -webkit-overflow-scrolling: touch;\n}\n.navbar-collapse.in {\n overflow-y: auto;\n}\n@media (min-width: 768px) {\n .navbar-collapse {\n width: auto;\n border-top: 0;\n box-shadow: none;\n }\n .navbar-collapse.collapse {\n display: block !important;\n height: auto !important;\n padding-bottom: 0;\n overflow: visible !important;\n }\n .navbar-collapse.in {\n overflow-y: visible;\n }\n .navbar-fixed-top .navbar-collapse,\n .navbar-static-top .navbar-collapse,\n .navbar-fixed-bottom .navbar-collapse {\n padding-left: 0;\n padding-right: 0;\n }\n}\n.navbar-fixed-top .navbar-collapse,\n.navbar-fixed-bottom .navbar-collapse {\n max-height: 340px;\n}\n@media (max-device-width: 480px) and (orientation: landscape) {\n .navbar-fixed-top .navbar-collapse,\n .navbar-fixed-bottom .navbar-collapse {\n max-height: 200px;\n }\n}\n.container > .navbar-header,\n.container-fluid > .navbar-header,\n.container > .navbar-collapse,\n.container-fluid > .navbar-collapse {\n margin-right: -15px;\n margin-left: -15px;\n}\n@media (min-width: 768px) {\n .container > .navbar-header,\n .container-fluid > .navbar-header,\n .container > .navbar-collapse,\n .container-fluid > .navbar-collapse {\n margin-right: 0;\n margin-left: 0;\n }\n}\n.navbar-static-top {\n z-index: 1000;\n border-width: 0 0 1px;\n}\n@media (min-width: 768px) {\n .navbar-static-top {\n border-radius: 0;\n }\n}\n.navbar-fixed-top,\n.navbar-fixed-bottom {\n position: fixed;\n right: 0;\n left: 0;\n z-index: 1030;\n}\n@media (min-width: 768px) {\n .navbar-fixed-top,\n .navbar-fixed-bottom {\n border-radius: 0;\n }\n}\n.navbar-fixed-top {\n top: 0;\n border-width: 0 0 1px;\n}\n.navbar-fixed-bottom {\n bottom: 0;\n margin-bottom: 0;\n border-width: 1px 0 0;\n}\n.navbar-brand {\n float: left;\n padding: 15px 15px;\n font-size: 18px;\n line-height: 20px;\n height: 50px;\n}\n.navbar-brand:hover,\n.navbar-brand:focus {\n text-decoration: none;\n}\n.navbar-brand > img {\n display: block;\n}\n@media (min-width: 768px) {\n .navbar > .container .navbar-brand,\n .navbar > .container-fluid .navbar-brand {\n margin-left: -15px;\n }\n}\n.navbar-toggle {\n position: relative;\n float: right;\n margin-right: 15px;\n padding: 9px 10px;\n margin-top: 8px;\n margin-bottom: 8px;\n background-color: transparent;\n background-image: none;\n border: 1px solid transparent;\n border-radius: 4px;\n}\n.navbar-toggle:focus {\n outline: 0;\n}\n.navbar-toggle .icon-bar {\n display: block;\n width: 22px;\n height: 2px;\n border-radius: 1px;\n}\n.navbar-toggle .icon-bar + .icon-bar {\n margin-top: 4px;\n}\n@media (min-width: 768px) {\n .navbar-toggle {\n display: none;\n }\n}\n.navbar-nav {\n margin: 7.5px -15px;\n}\n.navbar-nav > li > a {\n padding-top: 10px;\n padding-bottom: 10px;\n line-height: 20px;\n}\n@media (max-width: 767px) {\n .navbar-nav .open .dropdown-menu {\n position: static;\n float: none;\n width: auto;\n margin-top: 0;\n background-color: transparent;\n border: 0;\n box-shadow: none;\n }\n .navbar-nav .open .dropdown-menu > li > a,\n .navbar-nav .open .dropdown-menu .dropdown-header {\n padding: 5px 15px 5px 25px;\n }\n .navbar-nav .open .dropdown-menu > li > a {\n line-height: 20px;\n }\n .navbar-nav .open .dropdown-menu > li > a:hover,\n .navbar-nav .open .dropdown-menu > li > a:focus {\n background-image: none;\n }\n}\n@media (min-width: 768px) {\n .navbar-nav {\n float: left;\n margin: 0;\n }\n .navbar-nav > li {\n float: left;\n }\n .navbar-nav > li > a {\n padding-top: 15px;\n padding-bottom: 15px;\n }\n}\n.navbar-form {\n margin-left: -15px;\n margin-right: -15px;\n padding: 10px 15px;\n border-top: 1px solid transparent;\n border-bottom: 1px solid transparent;\n -webkit-box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1), 0 1px 0 rgba(255, 255, 255, 0.1);\n box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1), 0 1px 0 rgba(255, 255, 255, 0.1);\n margin-top: 8px;\n margin-bottom: 8px;\n}\n@media (min-width: 768px) {\n .navbar-form .form-group {\n display: inline-block;\n margin-bottom: 0;\n vertical-align: middle;\n }\n .navbar-form .form-control {\n display: inline-block;\n width: auto;\n vertical-align: middle;\n }\n .navbar-form .form-control-static {\n display: inline-block;\n }\n .navbar-form .input-group {\n display: inline-table;\n vertical-align: middle;\n }\n .navbar-form .input-group .input-group-addon,\n .navbar-form .input-group .input-group-btn,\n .navbar-form .input-group .form-control {\n width: auto;\n }\n .navbar-form .input-group > .form-control {\n width: 100%;\n }\n .navbar-form .control-label {\n margin-bottom: 0;\n vertical-align: middle;\n }\n .navbar-form .radio,\n .navbar-form .checkbox {\n display: inline-block;\n margin-top: 0;\n margin-bottom: 0;\n vertical-align: middle;\n }\n .navbar-form .radio label,\n .navbar-form .checkbox label {\n padding-left: 0;\n }\n .navbar-form .radio input[type=\"radio\"],\n .navbar-form .checkbox input[type=\"checkbox\"] {\n position: relative;\n margin-left: 0;\n }\n .navbar-form .has-feedback .form-control-feedback {\n top: 0;\n }\n}\n@media (max-width: 767px) {\n .navbar-form .form-group {\n margin-bottom: 5px;\n }\n .navbar-form .form-group:last-child {\n margin-bottom: 0;\n }\n}\n@media (min-width: 768px) {\n .navbar-form {\n width: auto;\n border: 0;\n margin-left: 0;\n margin-right: 0;\n padding-top: 0;\n padding-bottom: 0;\n -webkit-box-shadow: none;\n box-shadow: none;\n }\n}\n.navbar-nav > li > .dropdown-menu {\n margin-top: 0;\n border-top-right-radius: 0;\n border-top-left-radius: 0;\n}\n.navbar-fixed-bottom .navbar-nav > li > .dropdown-menu {\n margin-bottom: 0;\n border-top-right-radius: 4px;\n border-top-left-radius: 4px;\n border-bottom-right-radius: 0;\n border-bottom-left-radius: 0;\n}\n.navbar-btn {\n margin-top: 8px;\n margin-bottom: 8px;\n}\n.navbar-btn.btn-sm {\n margin-top: 10px;\n margin-bottom: 10px;\n}\n.navbar-btn.btn-xs {\n margin-top: 14px;\n margin-bottom: 14px;\n}\n.navbar-text {\n margin-top: 15px;\n margin-bottom: 15px;\n}\n@media (min-width: 768px) {\n .navbar-text {\n float: left;\n margin-left: 15px;\n margin-right: 15px;\n }\n}\n@media (min-width: 768px) {\n .navbar-left {\n float: left !important;\n }\n .navbar-right {\n float: right !important;\n margin-right: -15px;\n }\n .navbar-right ~ .navbar-right {\n margin-right: 0;\n }\n}\n.navbar-default {\n background-color: #f8f8f8;\n border-color: #e7e7e7;\n}\n.navbar-default .navbar-brand {\n color: #777;\n}\n.navbar-default .navbar-brand:hover,\n.navbar-default .navbar-brand:focus {\n color: #5e5e5e;\n background-color: transparent;\n}\n.navbar-default .navbar-text {\n color: #777;\n}\n.navbar-default .navbar-nav > li > a {\n color: #777;\n}\n.navbar-default .navbar-nav > li > a:hover,\n.navbar-default .navbar-nav > li > a:focus {\n color: #333;\n background-color: transparent;\n}\n.navbar-default .navbar-nav > .active > a,\n.navbar-default .navbar-nav > .active > a:hover,\n.navbar-default .navbar-nav > .active > a:focus {\n color: #555;\n background-color: #e7e7e7;\n}\n.navbar-default .navbar-nav > .disabled > a,\n.navbar-default .navbar-nav > .disabled > a:hover,\n.navbar-default .navbar-nav > .disabled > a:focus {\n color: #ccc;\n background-color: transparent;\n}\n.navbar-default .navbar-toggle {\n border-color: #ddd;\n}\n.navbar-default .navbar-toggle:hover,\n.navbar-default .navbar-toggle:focus {\n background-color: #ddd;\n}\n.navbar-default .navbar-toggle .icon-bar {\n background-color: #888;\n}\n.navbar-default .navbar-collapse,\n.navbar-default .navbar-form {\n border-color: #e7e7e7;\n}\n.navbar-default .navbar-nav > .open > a,\n.navbar-default .navbar-nav > .open > a:hover,\n.navbar-default .navbar-nav > .open > a:focus {\n background-color: #e7e7e7;\n color: #555;\n}\n@media (max-width: 767px) {\n .navbar-default .navbar-nav .open .dropdown-menu > li > a {\n color: #777;\n }\n .navbar-default .navbar-nav .open .dropdown-menu > li > a:hover,\n .navbar-default .navbar-nav .open .dropdown-menu > li > a:focus {\n color: #333;\n background-color: transparent;\n }\n .navbar-default .navbar-nav .open .dropdown-menu > .active > a,\n .navbar-default .navbar-nav .open .dropdown-menu > .active > a:hover,\n .navbar-default .navbar-nav .open .dropdown-menu > .active > a:focus {\n color: #555;\n background-color: #e7e7e7;\n }\n .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a,\n .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a:hover,\n .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a:focus {\n color: #ccc;\n background-color: transparent;\n }\n}\n.navbar-default .navbar-link {\n color: #777;\n}\n.navbar-default .navbar-link:hover {\n color: #333;\n}\n.navbar-default .btn-link {\n color: #777;\n}\n.navbar-default .btn-link:hover,\n.navbar-default .btn-link:focus {\n color: #333;\n}\n.navbar-default .btn-link[disabled]:hover,\nfieldset[disabled] .navbar-default .btn-link:hover,\n.navbar-default .btn-link[disabled]:focus,\nfieldset[disabled] .navbar-default .btn-link:focus {\n color: #ccc;\n}\n.navbar-inverse {\n background-color: #222;\n border-color: #080808;\n}\n.navbar-inverse .navbar-brand {\n color: #9d9d9d;\n}\n.navbar-inverse .navbar-brand:hover,\n.navbar-inverse .navbar-brand:focus {\n color: #fff;\n background-color: transparent;\n}\n.navbar-inverse .navbar-text {\n color: #9d9d9d;\n}\n.navbar-inverse .navbar-nav > li > a {\n color: #9d9d9d;\n}\n.navbar-inverse .navbar-nav > li > a:hover,\n.navbar-inverse .navbar-nav > li > a:focus {\n color: #fff;\n background-color: transparent;\n}\n.navbar-inverse .navbar-nav > .active > a,\n.navbar-inverse .navbar-nav > .active > a:hover,\n.navbar-inverse .navbar-nav > .active > a:focus {\n color: #fff;\n background-color: #080808;\n}\n.navbar-inverse .navbar-nav > .disabled > a,\n.navbar-inverse .navbar-nav > .disabled > a:hover,\n.navbar-inverse .navbar-nav > .disabled > a:focus {\n color: #444;\n background-color: transparent;\n}\n.navbar-inverse .navbar-toggle {\n border-color: #333;\n}\n.navbar-inverse .navbar-toggle:hover,\n.navbar-inverse .navbar-toggle:focus {\n background-color: #333;\n}\n.navbar-inverse .navbar-toggle .icon-bar {\n background-color: #fff;\n}\n.navbar-inverse .navbar-collapse,\n.navbar-inverse .navbar-form {\n border-color: #101010;\n}\n.navbar-inverse .navbar-nav > .open > a,\n.navbar-inverse .navbar-nav > .open > a:hover,\n.navbar-inverse .navbar-nav > .open > a:focus {\n background-color: #080808;\n color: #fff;\n}\n@media (max-width: 767px) {\n .navbar-inverse .navbar-nav .open .dropdown-menu > .dropdown-header {\n border-color: #080808;\n }\n .navbar-inverse .navbar-nav .open .dropdown-menu .divider {\n background-color: #080808;\n }\n .navbar-inverse .navbar-nav .open .dropdown-menu > li > a {\n color: #9d9d9d;\n }\n .navbar-inverse .navbar-nav .open .dropdown-menu > li > a:hover,\n .navbar-inverse .navbar-nav .open .dropdown-menu > li > a:focus {\n color: #fff;\n background-color: transparent;\n }\n .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a,\n .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a:hover,\n .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a:focus {\n color: #fff;\n background-color: #080808;\n }\n .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a,\n .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a:hover,\n .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a:focus {\n color: #444;\n background-color: transparent;\n }\n}\n.navbar-inverse .navbar-link {\n color: #9d9d9d;\n}\n.navbar-inverse .navbar-link:hover {\n color: #fff;\n}\n.navbar-inverse .btn-link {\n color: #9d9d9d;\n}\n.navbar-inverse .btn-link:hover,\n.navbar-inverse .btn-link:focus {\n color: #fff;\n}\n.navbar-inverse .btn-link[disabled]:hover,\nfieldset[disabled] .navbar-inverse .btn-link:hover,\n.navbar-inverse .btn-link[disabled]:focus,\nfieldset[disabled] .navbar-inverse .btn-link:focus {\n color: #444;\n}\n.breadcrumb {\n padding: 8px 15px;\n margin-bottom: 20px;\n list-style: none;\n background-color: #f5f5f5;\n border-radius: 4px;\n}\n.breadcrumb > li {\n display: inline-block;\n}\n.breadcrumb > li + li:before {\n content: \"/\\00a0\";\n padding: 0 5px;\n color: #ccc;\n}\n.breadcrumb > .active {\n color: #777777;\n}\n.pagination {\n display: inline-block;\n padding-left: 0;\n margin: 20px 0;\n border-radius: 4px;\n}\n.pagination > li {\n display: inline;\n}\n.pagination > li > a,\n.pagination > li > span {\n position: relative;\n float: left;\n padding: 6px 12px;\n line-height: 1.42857143;\n text-decoration: none;\n color: #337ab7;\n background-color: #fff;\n border: 1px solid #ddd;\n margin-left: -1px;\n}\n.pagination > li:first-child > a,\n.pagination > li:first-child > span {\n margin-left: 0;\n border-bottom-left-radius: 4px;\n border-top-left-radius: 4px;\n}\n.pagination > li:last-child > a,\n.pagination > li:last-child > span {\n border-bottom-right-radius: 4px;\n border-top-right-radius: 4px;\n}\n.pagination > li > a:hover,\n.pagination > li > span:hover,\n.pagination > li > a:focus,\n.pagination > li > span:focus {\n z-index: 2;\n color: #23527c;\n background-color: #eeeeee;\n border-color: #ddd;\n}\n.pagination > .active > a,\n.pagination > .active > span,\n.pagination > .active > a:hover,\n.pagination > .active > span:hover,\n.pagination > .active > a:focus,\n.pagination > .active > span:focus {\n z-index: 3;\n color: #fff;\n background-color: #337ab7;\n border-color: #337ab7;\n cursor: default;\n}\n.pagination > .disabled > span,\n.pagination > .disabled > span:hover,\n.pagination > .disabled > span:focus,\n.pagination > .disabled > a,\n.pagination > .disabled > a:hover,\n.pagination > .disabled > a:focus {\n color: #777777;\n background-color: #fff;\n border-color: #ddd;\n cursor: not-allowed;\n}\n.pagination-lg > li > a,\n.pagination-lg > li > span {\n padding: 10px 16px;\n font-size: 18px;\n line-height: 1.3333333;\n}\n.pagination-lg > li:first-child > a,\n.pagination-lg > li:first-child > span {\n border-bottom-left-radius: 6px;\n border-top-left-radius: 6px;\n}\n.pagination-lg > li:last-child > a,\n.pagination-lg > li:last-child > span {\n border-bottom-right-radius: 6px;\n border-top-right-radius: 6px;\n}\n.pagination-sm > li > a,\n.pagination-sm > li > span {\n padding: 5px 10px;\n font-size: 12px;\n line-height: 1.5;\n}\n.pagination-sm > li:first-child > a,\n.pagination-sm > li:first-child > span {\n border-bottom-left-radius: 3px;\n border-top-left-radius: 3px;\n}\n.pagination-sm > li:last-child > a,\n.pagination-sm > li:last-child > span {\n border-bottom-right-radius: 3px;\n border-top-right-radius: 3px;\n}\n.pager {\n padding-left: 0;\n margin: 20px 0;\n list-style: none;\n text-align: center;\n}\n.pager li {\n display: inline;\n}\n.pager li > a,\n.pager li > span {\n display: inline-block;\n padding: 5px 14px;\n background-color: #fff;\n border: 1px solid #ddd;\n border-radius: 15px;\n}\n.pager li > a:hover,\n.pager li > a:focus {\n text-decoration: none;\n background-color: #eeeeee;\n}\n.pager .next > a,\n.pager .next > span {\n float: right;\n}\n.pager .previous > a,\n.pager .previous > span {\n float: left;\n}\n.pager .disabled > a,\n.pager .disabled > a:hover,\n.pager .disabled > a:focus,\n.pager .disabled > span {\n color: #777777;\n background-color: #fff;\n cursor: not-allowed;\n}\n.label {\n display: inline;\n padding: .2em .6em .3em;\n font-size: 75%;\n font-weight: bold;\n line-height: 1;\n color: #fff;\n text-align: center;\n white-space: nowrap;\n vertical-align: baseline;\n border-radius: .25em;\n}\na.label:hover,\na.label:focus {\n color: #fff;\n text-decoration: none;\n cursor: pointer;\n}\n.label:empty {\n display: none;\n}\n.btn .label {\n position: relative;\n top: -1px;\n}\n.label-default {\n background-color: #777777;\n}\n.label-default[href]:hover,\n.label-default[href]:focus {\n background-color: #5e5e5e;\n}\n.label-primary {\n background-color: #337ab7;\n}\n.label-primary[href]:hover,\n.label-primary[href]:focus {\n background-color: #286090;\n}\n.label-success {\n background-color: #5cb85c;\n}\n.label-success[href]:hover,\n.label-success[href]:focus {\n background-color: #449d44;\n}\n.label-info {\n background-color: #5bc0de;\n}\n.label-info[href]:hover,\n.label-info[href]:focus {\n background-color: #31b0d5;\n}\n.label-warning {\n background-color: #f0ad4e;\n}\n.label-warning[href]:hover,\n.label-warning[href]:focus {\n background-color: #ec971f;\n}\n.label-danger {\n background-color: #d9534f;\n}\n.label-danger[href]:hover,\n.label-danger[href]:focus {\n background-color: #c9302c;\n}\n.badge {\n display: inline-block;\n min-width: 10px;\n padding: 3px 7px;\n font-size: 12px;\n font-weight: bold;\n color: #fff;\n line-height: 1;\n vertical-align: middle;\n white-space: nowrap;\n text-align: center;\n background-color: #777777;\n border-radius: 10px;\n}\n.badge:empty {\n display: none;\n}\n.btn .badge {\n position: relative;\n top: -1px;\n}\n.btn-xs .badge,\n.btn-group-xs > .btn .badge {\n top: 0;\n padding: 1px 5px;\n}\na.badge:hover,\na.badge:focus {\n color: #fff;\n text-decoration: none;\n cursor: pointer;\n}\n.list-group-item.active > .badge,\n.nav-pills > .active > a > .badge {\n color: #337ab7;\n background-color: #fff;\n}\n.list-group-item > .badge {\n float: right;\n}\n.list-group-item > .badge + .badge {\n margin-right: 5px;\n}\n.nav-pills > li > a > .badge {\n margin-left: 3px;\n}\n.jumbotron {\n padding-top: 30px;\n padding-bottom: 30px;\n margin-bottom: 30px;\n color: inherit;\n background-color: #eeeeee;\n}\n.jumbotron h1,\n.jumbotron .h1 {\n color: inherit;\n}\n.jumbotron p {\n margin-bottom: 15px;\n font-size: 21px;\n font-weight: 200;\n}\n.jumbotron > hr {\n border-top-color: #d5d5d5;\n}\n.container .jumbotron,\n.container-fluid .jumbotron {\n border-radius: 6px;\n padding-left: 15px;\n padding-right: 15px;\n}\n.jumbotron .container {\n max-width: 100%;\n}\n@media screen and (min-width: 768px) {\n .jumbotron {\n padding-top: 48px;\n padding-bottom: 48px;\n }\n .container .jumbotron,\n .container-fluid .jumbotron {\n padding-left: 60px;\n padding-right: 60px;\n }\n .jumbotron h1,\n .jumbotron .h1 {\n font-size: 63px;\n }\n}\n.thumbnail {\n display: block;\n padding: 4px;\n margin-bottom: 20px;\n line-height: 1.42857143;\n background-color: #fff;\n border: 1px solid #ddd;\n border-radius: 4px;\n -webkit-transition: border 0.2s ease-in-out;\n -o-transition: border 0.2s ease-in-out;\n transition: border 0.2s ease-in-out;\n}\n.thumbnail > img,\n.thumbnail a > img {\n margin-left: auto;\n margin-right: auto;\n}\na.thumbnail:hover,\na.thumbnail:focus,\na.thumbnail.active {\n border-color: #337ab7;\n}\n.thumbnail .caption {\n padding: 9px;\n color: #333333;\n}\n.alert {\n padding: 15px;\n margin-bottom: 20px;\n border: 1px solid transparent;\n border-radius: 4px;\n}\n.alert h4 {\n margin-top: 0;\n color: inherit;\n}\n.alert .alert-link {\n font-weight: bold;\n}\n.alert > p,\n.alert > ul {\n margin-bottom: 0;\n}\n.alert > p + p {\n margin-top: 5px;\n}\n.alert-dismissable,\n.alert-dismissible {\n padding-right: 35px;\n}\n.alert-dismissable .close,\n.alert-dismissible .close {\n position: relative;\n top: -2px;\n right: -21px;\n color: inherit;\n}\n.alert-success {\n background-color: #dff0d8;\n border-color: #d6e9c6;\n color: #3c763d;\n}\n.alert-success hr {\n border-top-color: #c9e2b3;\n}\n.alert-success .alert-link {\n color: #2b542c;\n}\n.alert-info {\n background-color: #d9edf7;\n border-color: #bce8f1;\n color: #31708f;\n}\n.alert-info hr {\n border-top-color: #a6e1ec;\n}\n.alert-info .alert-link {\n color: #245269;\n}\n.alert-warning {\n background-color: #fcf8e3;\n border-color: #faebcc;\n color: #8a6d3b;\n}\n.alert-warning hr {\n border-top-color: #f7e1b5;\n}\n.alert-warning .alert-link {\n color: #66512c;\n}\n.alert-danger {\n background-color: #f2dede;\n border-color: #ebccd1;\n color: #a94442;\n}\n.alert-danger hr {\n border-top-color: #e4b9c0;\n}\n.alert-danger .alert-link {\n color: #843534;\n}\n@-webkit-keyframes progress-bar-stripes {\n from {\n background-position: 40px 0;\n }\n to {\n background-position: 0 0;\n }\n}\n@keyframes progress-bar-stripes {\n from {\n background-position: 40px 0;\n }\n to {\n background-position: 0 0;\n }\n}\n.progress {\n overflow: hidden;\n height: 20px;\n margin-bottom: 20px;\n background-color: #f5f5f5;\n border-radius: 4px;\n -webkit-box-shadow: inset 0 1px 2px rgba(0, 0, 0, 0.1);\n box-shadow: inset 0 1px 2px rgba(0, 0, 0, 0.1);\n}\n.progress-bar {\n float: left;\n width: 0%;\n height: 100%;\n font-size: 12px;\n line-height: 20px;\n color: #fff;\n text-align: center;\n background-color: #337ab7;\n -webkit-box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.15);\n box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.15);\n -webkit-transition: width 0.6s ease;\n -o-transition: width 0.6s ease;\n transition: width 0.6s ease;\n}\n.progress-striped .progress-bar,\n.progress-bar-striped {\n background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-size: 40px 40px;\n}\n.progress.active .progress-bar,\n.progress-bar.active {\n -webkit-animation: progress-bar-stripes 2s linear infinite;\n -o-animation: progress-bar-stripes 2s linear infinite;\n animation: progress-bar-stripes 2s linear infinite;\n}\n.progress-bar-success {\n background-color: #5cb85c;\n}\n.progress-striped .progress-bar-success {\n background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n}\n.progress-bar-info {\n background-color: #5bc0de;\n}\n.progress-striped .progress-bar-info {\n background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n}\n.progress-bar-warning {\n background-color: #f0ad4e;\n}\n.progress-striped .progress-bar-warning {\n background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n}\n.progress-bar-danger {\n background-color: #d9534f;\n}\n.progress-striped .progress-bar-danger {\n background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n}\n.media {\n margin-top: 15px;\n}\n.media:first-child {\n margin-top: 0;\n}\n.media,\n.media-body {\n zoom: 1;\n overflow: hidden;\n}\n.media-body {\n width: 10000px;\n}\n.media-object {\n display: block;\n}\n.media-object.img-thumbnail {\n max-width: none;\n}\n.media-right,\n.media > .pull-right {\n padding-left: 10px;\n}\n.media-left,\n.media > .pull-left {\n padding-right: 10px;\n}\n.media-left,\n.media-right,\n.media-body {\n display: table-cell;\n vertical-align: top;\n}\n.media-middle {\n vertical-align: middle;\n}\n.media-bottom {\n vertical-align: bottom;\n}\n.media-heading {\n margin-top: 0;\n margin-bottom: 5px;\n}\n.media-list {\n padding-left: 0;\n list-style: none;\n}\n.list-group {\n margin-bottom: 20px;\n padding-left: 0;\n}\n.list-group-item {\n position: relative;\n display: block;\n padding: 10px 15px;\n margin-bottom: -1px;\n background-color: #fff;\n border: 1px solid #ddd;\n}\n.list-group-item:first-child {\n border-top-right-radius: 4px;\n border-top-left-radius: 4px;\n}\n.list-group-item:last-child {\n margin-bottom: 0;\n border-bottom-right-radius: 4px;\n border-bottom-left-radius: 4px;\n}\na.list-group-item,\nbutton.list-group-item {\n color: #555;\n}\na.list-group-item .list-group-item-heading,\nbutton.list-group-item .list-group-item-heading {\n color: #333;\n}\na.list-group-item:hover,\nbutton.list-group-item:hover,\na.list-group-item:focus,\nbutton.list-group-item:focus {\n text-decoration: none;\n color: #555;\n background-color: #f5f5f5;\n}\nbutton.list-group-item {\n width: 100%;\n text-align: left;\n}\n.list-group-item.disabled,\n.list-group-item.disabled:hover,\n.list-group-item.disabled:focus {\n background-color: #eeeeee;\n color: #777777;\n cursor: not-allowed;\n}\n.list-group-item.disabled .list-group-item-heading,\n.list-group-item.disabled:hover .list-group-item-heading,\n.list-group-item.disabled:focus .list-group-item-heading {\n color: inherit;\n}\n.list-group-item.disabled .list-group-item-text,\n.list-group-item.disabled:hover .list-group-item-text,\n.list-group-item.disabled:focus .list-group-item-text {\n color: #777777;\n}\n.list-group-item.active,\n.list-group-item.active:hover,\n.list-group-item.active:focus {\n z-index: 2;\n color: #fff;\n background-color: #337ab7;\n border-color: #337ab7;\n}\n.list-group-item.active .list-group-item-heading,\n.list-group-item.active:hover .list-group-item-heading,\n.list-group-item.active:focus .list-group-item-heading,\n.list-group-item.active .list-group-item-heading > small,\n.list-group-item.active:hover .list-group-item-heading > small,\n.list-group-item.active:focus .list-group-item-heading > small,\n.list-group-item.active .list-group-item-heading > .small,\n.list-group-item.active:hover .list-group-item-heading > .small,\n.list-group-item.active:focus .list-group-item-heading > .small {\n color: inherit;\n}\n.list-group-item.active .list-group-item-text,\n.list-group-item.active:hover .list-group-item-text,\n.list-group-item.active:focus .list-group-item-text {\n color: #c7ddef;\n}\n.list-group-item-success {\n color: #3c763d;\n background-color: #dff0d8;\n}\na.list-group-item-success,\nbutton.list-group-item-success {\n color: #3c763d;\n}\na.list-group-item-success .list-group-item-heading,\nbutton.list-group-item-success .list-group-item-heading {\n color: inherit;\n}\na.list-group-item-success:hover,\nbutton.list-group-item-success:hover,\na.list-group-item-success:focus,\nbutton.list-group-item-success:focus {\n color: #3c763d;\n background-color: #d0e9c6;\n}\na.list-group-item-success.active,\nbutton.list-group-item-success.active,\na.list-group-item-success.active:hover,\nbutton.list-group-item-success.active:hover,\na.list-group-item-success.active:focus,\nbutton.list-group-item-success.active:focus {\n color: #fff;\n background-color: #3c763d;\n border-color: #3c763d;\n}\n.list-group-item-info {\n color: #31708f;\n background-color: #d9edf7;\n}\na.list-group-item-info,\nbutton.list-group-item-info {\n color: #31708f;\n}\na.list-group-item-info .list-group-item-heading,\nbutton.list-group-item-info .list-group-item-heading {\n color: inherit;\n}\na.list-group-item-info:hover,\nbutton.list-group-item-info:hover,\na.list-group-item-info:focus,\nbutton.list-group-item-info:focus {\n color: #31708f;\n background-color: #c4e3f3;\n}\na.list-group-item-info.active,\nbutton.list-group-item-info.active,\na.list-group-item-info.active:hover,\nbutton.list-group-item-info.active:hover,\na.list-group-item-info.active:focus,\nbutton.list-group-item-info.active:focus {\n color: #fff;\n background-color: #31708f;\n border-color: #31708f;\n}\n.list-group-item-warning {\n color: #8a6d3b;\n background-color: #fcf8e3;\n}\na.list-group-item-warning,\nbutton.list-group-item-warning {\n color: #8a6d3b;\n}\na.list-group-item-warning .list-group-item-heading,\nbutton.list-group-item-warning .list-group-item-heading {\n color: inherit;\n}\na.list-group-item-warning:hover,\nbutton.list-group-item-warning:hover,\na.list-group-item-warning:focus,\nbutton.list-group-item-warning:focus {\n color: #8a6d3b;\n background-color: #faf2cc;\n}\na.list-group-item-warning.active,\nbutton.list-group-item-warning.active,\na.list-group-item-warning.active:hover,\nbutton.list-group-item-warning.active:hover,\na.list-group-item-warning.active:focus,\nbutton.list-group-item-warning.active:focus {\n color: #fff;\n background-color: #8a6d3b;\n border-color: #8a6d3b;\n}\n.list-group-item-danger {\n color: #a94442;\n background-color: #f2dede;\n}\na.list-group-item-danger,\nbutton.list-group-item-danger {\n color: #a94442;\n}\na.list-group-item-danger .list-group-item-heading,\nbutton.list-group-item-danger .list-group-item-heading {\n color: inherit;\n}\na.list-group-item-danger:hover,\nbutton.list-group-item-danger:hover,\na.list-group-item-danger:focus,\nbutton.list-group-item-danger:focus {\n color: #a94442;\n background-color: #ebcccc;\n}\na.list-group-item-danger.active,\nbutton.list-group-item-danger.active,\na.list-group-item-danger.active:hover,\nbutton.list-group-item-danger.active:hover,\na.list-group-item-danger.active:focus,\nbutton.list-group-item-danger.active:focus {\n color: #fff;\n background-color: #a94442;\n border-color: #a94442;\n}\n.list-group-item-heading {\n margin-top: 0;\n margin-bottom: 5px;\n}\n.list-group-item-text {\n margin-bottom: 0;\n line-height: 1.3;\n}\n.panel {\n margin-bottom: 20px;\n background-color: #fff;\n border: 1px solid transparent;\n border-radius: 4px;\n -webkit-box-shadow: 0 1px 1px rgba(0, 0, 0, 0.05);\n box-shadow: 0 1px 1px rgba(0, 0, 0, 0.05);\n}\n.panel-body {\n padding: 15px;\n}\n.panel-heading {\n padding: 10px 15px;\n border-bottom: 1px solid transparent;\n border-top-right-radius: 3px;\n border-top-left-radius: 3px;\n}\n.panel-heading > .dropdown .dropdown-toggle {\n color: inherit;\n}\n.panel-title {\n margin-top: 0;\n margin-bottom: 0;\n font-size: 16px;\n color: inherit;\n}\n.panel-title > a,\n.panel-title > small,\n.panel-title > .small,\n.panel-title > small > a,\n.panel-title > .small > a {\n color: inherit;\n}\n.panel-footer {\n padding: 10px 15px;\n background-color: #f5f5f5;\n border-top: 1px solid #ddd;\n border-bottom-right-radius: 3px;\n border-bottom-left-radius: 3px;\n}\n.panel > .list-group,\n.panel > .panel-collapse > .list-group {\n margin-bottom: 0;\n}\n.panel > .list-group .list-group-item,\n.panel > .panel-collapse > .list-group .list-group-item {\n border-width: 1px 0;\n border-radius: 0;\n}\n.panel > .list-group:first-child .list-group-item:first-child,\n.panel > .panel-collapse > .list-group:first-child .list-group-item:first-child {\n border-top: 0;\n border-top-right-radius: 3px;\n border-top-left-radius: 3px;\n}\n.panel > .list-group:last-child .list-group-item:last-child,\n.panel > .panel-collapse > .list-group:last-child .list-group-item:last-child {\n border-bottom: 0;\n border-bottom-right-radius: 3px;\n border-bottom-left-radius: 3px;\n}\n.panel > .panel-heading + .panel-collapse > .list-group .list-group-item:first-child {\n border-top-right-radius: 0;\n border-top-left-radius: 0;\n}\n.panel-heading + .list-group .list-group-item:first-child {\n border-top-width: 0;\n}\n.list-group + .panel-footer {\n border-top-width: 0;\n}\n.panel > .table,\n.panel > .table-responsive > .table,\n.panel > .panel-collapse > .table {\n margin-bottom: 0;\n}\n.panel > .table caption,\n.panel > .table-responsive > .table caption,\n.panel > .panel-collapse > .table caption {\n padding-left: 15px;\n padding-right: 15px;\n}\n.panel > .table:first-child,\n.panel > .table-responsive:first-child > .table:first-child {\n border-top-right-radius: 3px;\n border-top-left-radius: 3px;\n}\n.panel > .table:first-child > thead:first-child > tr:first-child,\n.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child,\n.panel > .table:first-child > tbody:first-child > tr:first-child,\n.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child {\n border-top-left-radius: 3px;\n border-top-right-radius: 3px;\n}\n.panel > .table:first-child > thead:first-child > tr:first-child td:first-child,\n.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child td:first-child,\n.panel > .table:first-child > tbody:first-child > tr:first-child td:first-child,\n.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child td:first-child,\n.panel > .table:first-child > thead:first-child > tr:first-child th:first-child,\n.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child th:first-child,\n.panel > .table:first-child > tbody:first-child > tr:first-child th:first-child,\n.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child th:first-child {\n border-top-left-radius: 3px;\n}\n.panel > .table:first-child > thead:first-child > tr:first-child td:last-child,\n.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child td:last-child,\n.panel > .table:first-child > tbody:first-child > tr:first-child td:last-child,\n.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child td:last-child,\n.panel > .table:first-child > thead:first-child > tr:first-child th:last-child,\n.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child th:last-child,\n.panel > .table:first-child > tbody:first-child > tr:first-child th:last-child,\n.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child th:last-child {\n border-top-right-radius: 3px;\n}\n.panel > .table:last-child,\n.panel > .table-responsive:last-child > .table:last-child {\n border-bottom-right-radius: 3px;\n border-bottom-left-radius: 3px;\n}\n.panel > .table:last-child > tbody:last-child > tr:last-child,\n.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child,\n.panel > .table:last-child > tfoot:last-child > tr:last-child,\n.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child {\n border-bottom-left-radius: 3px;\n border-bottom-right-radius: 3px;\n}\n.panel > .table:last-child > tbody:last-child > tr:last-child td:first-child,\n.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child td:first-child,\n.panel > .table:last-child > tfoot:last-child > tr:last-child td:first-child,\n.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child td:first-child,\n.panel > .table:last-child > tbody:last-child > tr:last-child th:first-child,\n.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child th:first-child,\n.panel > .table:last-child > tfoot:last-child > tr:last-child th:first-child,\n.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child th:first-child {\n border-bottom-left-radius: 3px;\n}\n.panel > .table:last-child > tbody:last-child > tr:last-child td:last-child,\n.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child td:last-child,\n.panel > .table:last-child > tfoot:last-child > tr:last-child td:last-child,\n.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child td:last-child,\n.panel > .table:last-child > tbody:last-child > tr:last-child th:last-child,\n.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child th:last-child,\n.panel > .table:last-child > tfoot:last-child > tr:last-child th:last-child,\n.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child th:last-child {\n border-bottom-right-radius: 3px;\n}\n.panel > .panel-body + .table,\n.panel > .panel-body + .table-responsive,\n.panel > .table + .panel-body,\n.panel > .table-responsive + .panel-body {\n border-top: 1px solid #ddd;\n}\n.panel > .table > tbody:first-child > tr:first-child th,\n.panel > .table > tbody:first-child > tr:first-child td {\n border-top: 0;\n}\n.panel > .table-bordered,\n.panel > .table-responsive > .table-bordered {\n border: 0;\n}\n.panel > .table-bordered > thead > tr > th:first-child,\n.panel > .table-responsive > .table-bordered > thead > tr > th:first-child,\n.panel > .table-bordered > tbody > tr > th:first-child,\n.panel > .table-responsive > .table-bordered > tbody > tr > th:first-child,\n.panel > .table-bordered > tfoot > tr > th:first-child,\n.panel > .table-responsive > .table-bordered > tfoot > tr > th:first-child,\n.panel > .table-bordered > thead > tr > td:first-child,\n.panel > .table-responsive > .table-bordered > thead > tr > td:first-child,\n.panel > .table-bordered > tbody > tr > td:first-child,\n.panel > .table-responsive > .table-bordered > tbody > tr > td:first-child,\n.panel > .table-bordered > tfoot > tr > td:first-child,\n.panel > .table-responsive > .table-bordered > tfoot > tr > td:first-child {\n border-left: 0;\n}\n.panel > .table-bordered > thead > tr > th:last-child,\n.panel > .table-responsive > .table-bordered > thead > tr > th:last-child,\n.panel > .table-bordered > tbody > tr > th:last-child,\n.panel > .table-responsive > .table-bordered > tbody > tr > th:last-child,\n.panel > .table-bordered > tfoot > tr > th:last-child,\n.panel > .table-responsive > .table-bordered > tfoot > tr > th:last-child,\n.panel > .table-bordered > thead > tr > td:last-child,\n.panel > .table-responsive > .table-bordered > thead > tr > td:last-child,\n.panel > .table-bordered > tbody > tr > td:last-child,\n.panel > .table-responsive > .table-bordered > tbody > tr > td:last-child,\n.panel > .table-bordered > tfoot > tr > td:last-child,\n.panel > .table-responsive > .table-bordered > tfoot > tr > td:last-child {\n border-right: 0;\n}\n.panel > .table-bordered > thead > tr:first-child > td,\n.panel > .table-responsive > .table-bordered > thead > tr:first-child > td,\n.panel > .table-bordered > tbody > tr:first-child > td,\n.panel > .table-responsive > .table-bordered > tbody > tr:first-child > td,\n.panel > .table-bordered > thead > tr:first-child > th,\n.panel > .table-responsive > .table-bordered > thead > tr:first-child > th,\n.panel > .table-bordered > tbody > tr:first-child > th,\n.panel > .table-responsive > .table-bordered > tbody > tr:first-child > th {\n border-bottom: 0;\n}\n.panel > .table-bordered > tbody > tr:last-child > td,\n.panel > .table-responsive > .table-bordered > tbody > tr:last-child > td,\n.panel > .table-bordered > tfoot > tr:last-child > td,\n.panel > .table-responsive > .table-bordered > tfoot > tr:last-child > td,\n.panel > .table-bordered > tbody > tr:last-child > th,\n.panel > .table-responsive > .table-bordered > tbody > tr:last-child > th,\n.panel > .table-bordered > tfoot > tr:last-child > th,\n.panel > .table-responsive > .table-bordered > tfoot > tr:last-child > th {\n border-bottom: 0;\n}\n.panel > .table-responsive {\n border: 0;\n margin-bottom: 0;\n}\n.panel-group {\n margin-bottom: 20px;\n}\n.panel-group .panel {\n margin-bottom: 0;\n border-radius: 4px;\n}\n.panel-group .panel + .panel {\n margin-top: 5px;\n}\n.panel-group .panel-heading {\n border-bottom: 0;\n}\n.panel-group .panel-heading + .panel-collapse > .panel-body,\n.panel-group .panel-heading + .panel-collapse > .list-group {\n border-top: 1px solid #ddd;\n}\n.panel-group .panel-footer {\n border-top: 0;\n}\n.panel-group .panel-footer + .panel-collapse .panel-body {\n border-bottom: 1px solid #ddd;\n}\n.panel-default {\n border-color: #ddd;\n}\n.panel-default > .panel-heading {\n color: #333333;\n background-color: #f5f5f5;\n border-color: #ddd;\n}\n.panel-default > .panel-heading + .panel-collapse > .panel-body {\n border-top-color: #ddd;\n}\n.panel-default > .panel-heading .badge {\n color: #f5f5f5;\n background-color: #333333;\n}\n.panel-default > .panel-footer + .panel-collapse > .panel-body {\n border-bottom-color: #ddd;\n}\n.panel-primary {\n border-color: #337ab7;\n}\n.panel-primary > .panel-heading {\n color: #fff;\n background-color: #337ab7;\n border-color: #337ab7;\n}\n.panel-primary > .panel-heading + .panel-collapse > .panel-body {\n border-top-color: #337ab7;\n}\n.panel-primary > .panel-heading .badge {\n color: #337ab7;\n background-color: #fff;\n}\n.panel-primary > .panel-footer + .panel-collapse > .panel-body {\n border-bottom-color: #337ab7;\n}\n.panel-success {\n border-color: #d6e9c6;\n}\n.panel-success > .panel-heading {\n color: #3c763d;\n background-color: #dff0d8;\n border-color: #d6e9c6;\n}\n.panel-success > .panel-heading + .panel-collapse > .panel-body {\n border-top-color: #d6e9c6;\n}\n.panel-success > .panel-heading .badge {\n color: #dff0d8;\n background-color: #3c763d;\n}\n.panel-success > .panel-footer + .panel-collapse > .panel-body {\n border-bottom-color: #d6e9c6;\n}\n.panel-info {\n border-color: #bce8f1;\n}\n.panel-info > .panel-heading {\n color: #31708f;\n background-color: #d9edf7;\n border-color: #bce8f1;\n}\n.panel-info > .panel-heading + .panel-collapse > .panel-body {\n border-top-color: #bce8f1;\n}\n.panel-info > .panel-heading .badge {\n color: #d9edf7;\n background-color: #31708f;\n}\n.panel-info > .panel-footer + .panel-collapse > .panel-body {\n border-bottom-color: #bce8f1;\n}\n.panel-warning {\n border-color: #faebcc;\n}\n.panel-warning > .panel-heading {\n color: #8a6d3b;\n background-color: #fcf8e3;\n border-color: #faebcc;\n}\n.panel-warning > .panel-heading + .panel-collapse > .panel-body {\n border-top-color: #faebcc;\n}\n.panel-warning > .panel-heading .badge {\n color: #fcf8e3;\n background-color: #8a6d3b;\n}\n.panel-warning > .panel-footer + .panel-collapse > .panel-body {\n border-bottom-color: #faebcc;\n}\n.panel-danger {\n border-color: #ebccd1;\n}\n.panel-danger > .panel-heading {\n color: #a94442;\n background-color: #f2dede;\n border-color: #ebccd1;\n}\n.panel-danger > .panel-heading + .panel-collapse > .panel-body {\n border-top-color: #ebccd1;\n}\n.panel-danger > .panel-heading .badge {\n color: #f2dede;\n background-color: #a94442;\n}\n.panel-danger > .panel-footer + .panel-collapse > .panel-body {\n border-bottom-color: #ebccd1;\n}\n.embed-responsive {\n position: relative;\n display: block;\n height: 0;\n padding: 0;\n overflow: hidden;\n}\n.embed-responsive .embed-responsive-item,\n.embed-responsive iframe,\n.embed-responsive embed,\n.embed-responsive object,\n.embed-responsive video {\n position: absolute;\n top: 0;\n left: 0;\n bottom: 0;\n height: 100%;\n width: 100%;\n border: 0;\n}\n.embed-responsive-16by9 {\n padding-bottom: 56.25%;\n}\n.embed-responsive-4by3 {\n padding-bottom: 75%;\n}\n.well {\n min-height: 20px;\n padding: 19px;\n margin-bottom: 20px;\n background-color: #f5f5f5;\n border: 1px solid #e3e3e3;\n border-radius: 4px;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.05);\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.05);\n}\n.well blockquote {\n border-color: #ddd;\n border-color: rgba(0, 0, 0, 0.15);\n}\n.well-lg {\n padding: 24px;\n border-radius: 6px;\n}\n.well-sm {\n padding: 9px;\n border-radius: 3px;\n}\n.close {\n float: right;\n font-size: 21px;\n font-weight: bold;\n line-height: 1;\n color: #000;\n text-shadow: 0 1px 0 #fff;\n opacity: 0.2;\n filter: alpha(opacity=20);\n}\n.close:hover,\n.close:focus {\n color: #000;\n text-decoration: none;\n cursor: pointer;\n opacity: 0.5;\n filter: alpha(opacity=50);\n}\nbutton.close {\n padding: 0;\n cursor: pointer;\n background: transparent;\n border: 0;\n -webkit-appearance: none;\n}\n.modal-open {\n overflow: hidden;\n}\n.modal {\n display: none;\n overflow: hidden;\n position: fixed;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: 1050;\n -webkit-overflow-scrolling: touch;\n outline: 0;\n}\n.modal.fade .modal-dialog {\n -webkit-transform: translate(0, -25%);\n -ms-transform: translate(0, -25%);\n -o-transform: translate(0, -25%);\n transform: translate(0, -25%);\n -webkit-transition: -webkit-transform 0.3s ease-out;\n -moz-transition: -moz-transform 0.3s ease-out;\n -o-transition: -o-transform 0.3s ease-out;\n transition: transform 0.3s ease-out;\n}\n.modal.in .modal-dialog {\n -webkit-transform: translate(0, 0);\n -ms-transform: translate(0, 0);\n -o-transform: translate(0, 0);\n transform: translate(0, 0);\n}\n.modal-open .modal {\n overflow-x: hidden;\n overflow-y: auto;\n}\n.modal-dialog {\n position: relative;\n width: auto;\n margin: 10px;\n}\n.modal-content {\n position: relative;\n background-color: #fff;\n border: 1px solid #999;\n border: 1px solid rgba(0, 0, 0, 0.2);\n border-radius: 6px;\n -webkit-box-shadow: 0 3px 9px rgba(0, 0, 0, 0.5);\n box-shadow: 0 3px 9px rgba(0, 0, 0, 0.5);\n background-clip: padding-box;\n outline: 0;\n}\n.modal-backdrop {\n position: fixed;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: 1040;\n background-color: #000;\n}\n.modal-backdrop.fade {\n opacity: 0;\n filter: alpha(opacity=0);\n}\n.modal-backdrop.in {\n opacity: 0.5;\n filter: alpha(opacity=50);\n}\n.modal-header {\n padding: 15px;\n border-bottom: 1px solid #e5e5e5;\n}\n.modal-header .close {\n margin-top: -2px;\n}\n.modal-title {\n margin: 0;\n line-height: 1.42857143;\n}\n.modal-body {\n position: relative;\n padding: 15px;\n}\n.modal-footer {\n padding: 15px;\n text-align: right;\n border-top: 1px solid #e5e5e5;\n}\n.modal-footer .btn + .btn {\n margin-left: 5px;\n margin-bottom: 0;\n}\n.modal-footer .btn-group .btn + .btn {\n margin-left: -1px;\n}\n.modal-footer .btn-block + .btn-block {\n margin-left: 0;\n}\n.modal-scrollbar-measure {\n position: absolute;\n top: -9999px;\n width: 50px;\n height: 50px;\n overflow: scroll;\n}\n@media (min-width: 768px) {\n .modal-dialog {\n width: 600px;\n margin: 30px auto;\n }\n .modal-content {\n -webkit-box-shadow: 0 5px 15px rgba(0, 0, 0, 0.5);\n box-shadow: 0 5px 15px rgba(0, 0, 0, 0.5);\n }\n .modal-sm {\n width: 300px;\n }\n}\n@media (min-width: 992px) {\n .modal-lg {\n width: 900px;\n }\n}\n.tooltip {\n position: absolute;\n z-index: 1070;\n display: block;\n font-family: \"Helvetica Neue\", Helvetica, Arial, sans-serif;\n font-style: normal;\n font-weight: normal;\n letter-spacing: normal;\n line-break: auto;\n line-height: 1.42857143;\n text-align: left;\n text-align: start;\n text-decoration: none;\n text-shadow: none;\n text-transform: none;\n white-space: normal;\n word-break: normal;\n word-spacing: normal;\n word-wrap: normal;\n font-size: 12px;\n opacity: 0;\n filter: alpha(opacity=0);\n}\n.tooltip.in {\n opacity: 0.9;\n filter: alpha(opacity=90);\n}\n.tooltip.top {\n margin-top: -3px;\n padding: 5px 0;\n}\n.tooltip.right {\n margin-left: 3px;\n padding: 0 5px;\n}\n.tooltip.bottom {\n margin-top: 3px;\n padding: 5px 0;\n}\n.tooltip.left {\n margin-left: -3px;\n padding: 0 5px;\n}\n.tooltip-inner {\n max-width: 200px;\n padding: 3px 8px;\n color: #fff;\n text-align: center;\n background-color: #000;\n border-radius: 4px;\n}\n.tooltip-arrow {\n position: absolute;\n width: 0;\n height: 0;\n border-color: transparent;\n border-style: solid;\n}\n.tooltip.top .tooltip-arrow {\n bottom: 0;\n left: 50%;\n margin-left: -5px;\n border-width: 5px 5px 0;\n border-top-color: #000;\n}\n.tooltip.top-left .tooltip-arrow {\n bottom: 0;\n right: 5px;\n margin-bottom: -5px;\n border-width: 5px 5px 0;\n border-top-color: #000;\n}\n.tooltip.top-right .tooltip-arrow {\n bottom: 0;\n left: 5px;\n margin-bottom: -5px;\n border-width: 5px 5px 0;\n border-top-color: #000;\n}\n.tooltip.right .tooltip-arrow {\n top: 50%;\n left: 0;\n margin-top: -5px;\n border-width: 5px 5px 5px 0;\n border-right-color: #000;\n}\n.tooltip.left .tooltip-arrow {\n top: 50%;\n right: 0;\n margin-top: -5px;\n border-width: 5px 0 5px 5px;\n border-left-color: #000;\n}\n.tooltip.bottom .tooltip-arrow {\n top: 0;\n left: 50%;\n margin-left: -5px;\n border-width: 0 5px 5px;\n border-bottom-color: #000;\n}\n.tooltip.bottom-left .tooltip-arrow {\n top: 0;\n right: 5px;\n margin-top: -5px;\n border-width: 0 5px 5px;\n border-bottom-color: #000;\n}\n.tooltip.bottom-right .tooltip-arrow {\n top: 0;\n left: 5px;\n margin-top: -5px;\n border-width: 0 5px 5px;\n border-bottom-color: #000;\n}\n.popover {\n position: absolute;\n top: 0;\n left: 0;\n z-index: 1060;\n display: none;\n max-width: 276px;\n padding: 1px;\n font-family: \"Helvetica Neue\", Helvetica, Arial, sans-serif;\n font-style: normal;\n font-weight: normal;\n letter-spacing: normal;\n line-break: auto;\n line-height: 1.42857143;\n text-align: left;\n text-align: start;\n text-decoration: none;\n text-shadow: none;\n text-transform: none;\n white-space: normal;\n word-break: normal;\n word-spacing: normal;\n word-wrap: normal;\n font-size: 14px;\n background-color: #fff;\n background-clip: padding-box;\n border: 1px solid #ccc;\n border: 1px solid rgba(0, 0, 0, 0.2);\n border-radius: 6px;\n -webkit-box-shadow: 0 5px 10px rgba(0, 0, 0, 0.2);\n box-shadow: 0 5px 10px rgba(0, 0, 0, 0.2);\n}\n.popover.top {\n margin-top: -10px;\n}\n.popover.right {\n margin-left: 10px;\n}\n.popover.bottom {\n margin-top: 10px;\n}\n.popover.left {\n margin-left: -10px;\n}\n.popover-title {\n margin: 0;\n padding: 8px 14px;\n font-size: 14px;\n background-color: #f7f7f7;\n border-bottom: 1px solid #ebebeb;\n border-radius: 5px 5px 0 0;\n}\n.popover-content {\n padding: 9px 14px;\n}\n.popover > .arrow,\n.popover > .arrow:after {\n position: absolute;\n display: block;\n width: 0;\n height: 0;\n border-color: transparent;\n border-style: solid;\n}\n.popover > .arrow {\n border-width: 11px;\n}\n.popover > .arrow:after {\n border-width: 10px;\n content: \"\";\n}\n.popover.top > .arrow {\n left: 50%;\n margin-left: -11px;\n border-bottom-width: 0;\n border-top-color: #999999;\n border-top-color: rgba(0, 0, 0, 0.25);\n bottom: -11px;\n}\n.popover.top > .arrow:after {\n content: \" \";\n bottom: 1px;\n margin-left: -10px;\n border-bottom-width: 0;\n border-top-color: #fff;\n}\n.popover.right > .arrow {\n top: 50%;\n left: -11px;\n margin-top: -11px;\n border-left-width: 0;\n border-right-color: #999999;\n border-right-color: rgba(0, 0, 0, 0.25);\n}\n.popover.right > .arrow:after {\n content: \" \";\n left: 1px;\n bottom: -10px;\n border-left-width: 0;\n border-right-color: #fff;\n}\n.popover.bottom > .arrow {\n left: 50%;\n margin-left: -11px;\n border-top-width: 0;\n border-bottom-color: #999999;\n border-bottom-color: rgba(0, 0, 0, 0.25);\n top: -11px;\n}\n.popover.bottom > .arrow:after {\n content: \" \";\n top: 1px;\n margin-left: -10px;\n border-top-width: 0;\n border-bottom-color: #fff;\n}\n.popover.left > .arrow {\n top: 50%;\n right: -11px;\n margin-top: -11px;\n border-right-width: 0;\n border-left-color: #999999;\n border-left-color: rgba(0, 0, 0, 0.25);\n}\n.popover.left > .arrow:after {\n content: \" \";\n right: 1px;\n border-right-width: 0;\n border-left-color: #fff;\n bottom: -10px;\n}\n.carousel {\n position: relative;\n}\n.carousel-inner {\n position: relative;\n overflow: hidden;\n width: 100%;\n}\n.carousel-inner > .item {\n display: none;\n position: relative;\n -webkit-transition: 0.6s ease-in-out left;\n -o-transition: 0.6s ease-in-out left;\n transition: 0.6s ease-in-out left;\n}\n.carousel-inner > .item > img,\n.carousel-inner > .item > a > img {\n line-height: 1;\n}\n@media all and (transform-3d), (-webkit-transform-3d) {\n .carousel-inner > .item {\n -webkit-transition: -webkit-transform 0.6s ease-in-out;\n -moz-transition: -moz-transform 0.6s ease-in-out;\n -o-transition: -o-transform 0.6s ease-in-out;\n transition: transform 0.6s ease-in-out;\n -webkit-backface-visibility: hidden;\n -moz-backface-visibility: hidden;\n backface-visibility: hidden;\n -webkit-perspective: 1000px;\n -moz-perspective: 1000px;\n perspective: 1000px;\n }\n .carousel-inner > .item.next,\n .carousel-inner > .item.active.right {\n -webkit-transform: translate3d(100%, 0, 0);\n transform: translate3d(100%, 0, 0);\n left: 0;\n }\n .carousel-inner > .item.prev,\n .carousel-inner > .item.active.left {\n -webkit-transform: translate3d(-100%, 0, 0);\n transform: translate3d(-100%, 0, 0);\n left: 0;\n }\n .carousel-inner > .item.next.left,\n .carousel-inner > .item.prev.right,\n .carousel-inner > .item.active {\n -webkit-transform: translate3d(0, 0, 0);\n transform: translate3d(0, 0, 0);\n left: 0;\n }\n}\n.carousel-inner > .active,\n.carousel-inner > .next,\n.carousel-inner > .prev {\n display: block;\n}\n.carousel-inner > .active {\n left: 0;\n}\n.carousel-inner > .next,\n.carousel-inner > .prev {\n position: absolute;\n top: 0;\n width: 100%;\n}\n.carousel-inner > .next {\n left: 100%;\n}\n.carousel-inner > .prev {\n left: -100%;\n}\n.carousel-inner > .next.left,\n.carousel-inner > .prev.right {\n left: 0;\n}\n.carousel-inner > .active.left {\n left: -100%;\n}\n.carousel-inner > .active.right {\n left: 100%;\n}\n.carousel-control {\n position: absolute;\n top: 0;\n left: 0;\n bottom: 0;\n width: 15%;\n opacity: 0.5;\n filter: alpha(opacity=50);\n font-size: 20px;\n color: #fff;\n text-align: center;\n text-shadow: 0 1px 2px rgba(0, 0, 0, 0.6);\n background-color: rgba(0, 0, 0, 0);\n}\n.carousel-control.left {\n background-image: -webkit-linear-gradient(left, rgba(0, 0, 0, 0.5) 0%, rgba(0, 0, 0, 0.0001) 100%);\n background-image: -o-linear-gradient(left, rgba(0, 0, 0, 0.5) 0%, rgba(0, 0, 0, 0.0001) 100%);\n background-image: linear-gradient(to right, rgba(0, 0, 0, 0.5) 0%, rgba(0, 0, 0, 0.0001) 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#80000000', endColorstr='#00000000', GradientType=1);\n}\n.carousel-control.right {\n left: auto;\n right: 0;\n background-image: -webkit-linear-gradient(left, rgba(0, 0, 0, 0.0001) 0%, rgba(0, 0, 0, 0.5) 100%);\n background-image: -o-linear-gradient(left, rgba(0, 0, 0, 0.0001) 0%, rgba(0, 0, 0, 0.5) 100%);\n background-image: linear-gradient(to right, rgba(0, 0, 0, 0.0001) 0%, rgba(0, 0, 0, 0.5) 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#00000000', endColorstr='#80000000', GradientType=1);\n}\n.carousel-control:hover,\n.carousel-control:focus {\n outline: 0;\n color: #fff;\n text-decoration: none;\n opacity: 0.9;\n filter: alpha(opacity=90);\n}\n.carousel-control .icon-prev,\n.carousel-control .icon-next,\n.carousel-control .glyphicon-chevron-left,\n.carousel-control .glyphicon-chevron-right {\n position: absolute;\n top: 50%;\n margin-top: -10px;\n z-index: 5;\n display: inline-block;\n}\n.carousel-control .icon-prev,\n.carousel-control .glyphicon-chevron-left {\n left: 50%;\n margin-left: -10px;\n}\n.carousel-control .icon-next,\n.carousel-control .glyphicon-chevron-right {\n right: 50%;\n margin-right: -10px;\n}\n.carousel-control .icon-prev,\n.carousel-control .icon-next {\n width: 20px;\n height: 20px;\n line-height: 1;\n font-family: serif;\n}\n.carousel-control .icon-prev:before {\n content: '\\2039';\n}\n.carousel-control .icon-next:before {\n content: '\\203a';\n}\n.carousel-indicators {\n position: absolute;\n bottom: 10px;\n left: 50%;\n z-index: 15;\n width: 60%;\n margin-left: -30%;\n padding-left: 0;\n list-style: none;\n text-align: center;\n}\n.carousel-indicators li {\n display: inline-block;\n width: 10px;\n height: 10px;\n margin: 1px;\n text-indent: -999px;\n border: 1px solid #fff;\n border-radius: 10px;\n cursor: pointer;\n background-color: #000 \\9;\n background-color: rgba(0, 0, 0, 0);\n}\n.carousel-indicators .active {\n margin: 0;\n width: 12px;\n height: 12px;\n background-color: #fff;\n}\n.carousel-caption {\n position: absolute;\n left: 15%;\n right: 15%;\n bottom: 20px;\n z-index: 10;\n padding-top: 20px;\n padding-bottom: 20px;\n color: #fff;\n text-align: center;\n text-shadow: 0 1px 2px rgba(0, 0, 0, 0.6);\n}\n.carousel-caption .btn {\n text-shadow: none;\n}\n@media screen and (min-width: 768px) {\n .carousel-control .glyphicon-chevron-left,\n .carousel-control .glyphicon-chevron-right,\n .carousel-control .icon-prev,\n .carousel-control .icon-next {\n width: 30px;\n height: 30px;\n margin-top: -10px;\n font-size: 30px;\n }\n .carousel-control .glyphicon-chevron-left,\n .carousel-control .icon-prev {\n margin-left: -10px;\n }\n .carousel-control .glyphicon-chevron-right,\n .carousel-control .icon-next {\n margin-right: -10px;\n }\n .carousel-caption {\n left: 20%;\n right: 20%;\n padding-bottom: 30px;\n }\n .carousel-indicators {\n bottom: 20px;\n }\n}\n.clearfix:before,\n.clearfix:after,\n.dl-horizontal dd:before,\n.dl-horizontal dd:after,\n.container:before,\n.container:after,\n.container-fluid:before,\n.container-fluid:after,\n.row:before,\n.row:after,\n.form-horizontal .form-group:before,\n.form-horizontal .form-group:after,\n.btn-toolbar:before,\n.btn-toolbar:after,\n.btn-group-vertical > .btn-group:before,\n.btn-group-vertical > .btn-group:after,\n.nav:before,\n.nav:after,\n.navbar:before,\n.navbar:after,\n.navbar-header:before,\n.navbar-header:after,\n.navbar-collapse:before,\n.navbar-collapse:after,\n.pager:before,\n.pager:after,\n.panel-body:before,\n.panel-body:after,\n.modal-header:before,\n.modal-header:after,\n.modal-footer:before,\n.modal-footer:after {\n content: \" \";\n display: table;\n}\n.clearfix:after,\n.dl-horizontal dd:after,\n.container:after,\n.container-fluid:after,\n.row:after,\n.form-horizontal .form-group:after,\n.btn-toolbar:after,\n.btn-group-vertical > .btn-group:after,\n.nav:after,\n.navbar:after,\n.navbar-header:after,\n.navbar-collapse:after,\n.pager:after,\n.panel-body:after,\n.modal-header:after,\n.modal-footer:after {\n clear: both;\n}\n.center-block {\n display: block;\n margin-left: auto;\n margin-right: auto;\n}\n.pull-right {\n float: right !important;\n}\n.pull-left {\n float: left !important;\n}\n.hide {\n display: none !important;\n}\n.show {\n display: block !important;\n}\n.invisible {\n visibility: hidden;\n}\n.text-hide {\n font: 0/0 a;\n color: transparent;\n text-shadow: none;\n background-color: transparent;\n border: 0;\n}\n.hidden {\n display: none !important;\n}\n.affix {\n position: fixed;\n}\n@-ms-viewport {\n width: device-width;\n}\n.visible-xs,\n.visible-sm,\n.visible-md,\n.visible-lg {\n display: none !important;\n}\n.visible-xs-block,\n.visible-xs-inline,\n.visible-xs-inline-block,\n.visible-sm-block,\n.visible-sm-inline,\n.visible-sm-inline-block,\n.visible-md-block,\n.visible-md-inline,\n.visible-md-inline-block,\n.visible-lg-block,\n.visible-lg-inline,\n.visible-lg-inline-block {\n display: none !important;\n}\n@media (max-width: 767px) {\n .visible-xs {\n display: block !important;\n }\n table.visible-xs {\n display: table !important;\n }\n tr.visible-xs {\n display: table-row !important;\n }\n th.visible-xs,\n td.visible-xs {\n display: table-cell !important;\n }\n}\n@media (max-width: 767px) {\n .visible-xs-block {\n display: block !important;\n }\n}\n@media (max-width: 767px) {\n .visible-xs-inline {\n display: inline !important;\n }\n}\n@media (max-width: 767px) {\n .visible-xs-inline-block {\n display: inline-block !important;\n }\n}\n@media (min-width: 768px) and (max-width: 991px) {\n .visible-sm {\n display: block !important;\n }\n table.visible-sm {\n display: table !important;\n }\n tr.visible-sm {\n display: table-row !important;\n }\n th.visible-sm,\n td.visible-sm {\n display: table-cell !important;\n }\n}\n@media (min-width: 768px) and (max-width: 991px) {\n .visible-sm-block {\n display: block !important;\n }\n}\n@media (min-width: 768px) and (max-width: 991px) {\n .visible-sm-inline {\n display: inline !important;\n }\n}\n@media (min-width: 768px) and (max-width: 991px) {\n .visible-sm-inline-block {\n display: inline-block !important;\n }\n}\n@media (min-width: 992px) and (max-width: 1199px) {\n .visible-md {\n display: block !important;\n }\n table.visible-md {\n display: table !important;\n }\n tr.visible-md {\n display: table-row !important;\n }\n th.visible-md,\n td.visible-md {\n display: table-cell !important;\n }\n}\n@media (min-width: 992px) and (max-width: 1199px) {\n .visible-md-block {\n display: block !important;\n }\n}\n@media (min-width: 992px) and (max-width: 1199px) {\n .visible-md-inline {\n display: inline !important;\n }\n}\n@media (min-width: 992px) and (max-width: 1199px) {\n .visible-md-inline-block {\n display: inline-block !important;\n }\n}\n@media (min-width: 1200px) {\n .visible-lg {\n display: block !important;\n }\n table.visible-lg {\n display: table !important;\n }\n tr.visible-lg {\n display: table-row !important;\n }\n th.visible-lg,\n td.visible-lg {\n display: table-cell !important;\n }\n}\n@media (min-width: 1200px) {\n .visible-lg-block {\n display: block !important;\n }\n}\n@media (min-width: 1200px) {\n .visible-lg-inline {\n display: inline !important;\n }\n}\n@media (min-width: 1200px) {\n .visible-lg-inline-block {\n display: inline-block !important;\n }\n}\n@media (max-width: 767px) {\n .hidden-xs {\n display: none !important;\n }\n}\n@media (min-width: 768px) and (max-width: 991px) {\n .hidden-sm {\n display: none !important;\n }\n}\n@media (min-width: 992px) and (max-width: 1199px) {\n .hidden-md {\n display: none !important;\n }\n}\n@media (min-width: 1200px) {\n .hidden-lg {\n display: none !important;\n }\n}\n.visible-print {\n display: none !important;\n}\n@media print {\n .visible-print {\n display: block !important;\n }\n table.visible-print {\n display: table !important;\n }\n tr.visible-print {\n display: table-row !important;\n }\n th.visible-print,\n td.visible-print {\n display: table-cell !important;\n }\n}\n.visible-print-block {\n display: none !important;\n}\n@media print {\n .visible-print-block {\n display: block !important;\n }\n}\n.visible-print-inline {\n display: none !important;\n}\n@media print {\n .visible-print-inline {\n display: inline !important;\n }\n}\n.visible-print-inline-block {\n display: none !important;\n}\n@media print {\n .visible-print-inline-block {\n display: inline-block !important;\n }\n}\n@media print {\n .hidden-print {\n display: none !important;\n }\n}\n/*# sourceMappingURL=bootstrap.css.map */","/*! normalize.css v3.0.3 | MIT License | github.com/necolas/normalize.css */\n\n//\n// 1. Set default font family to sans-serif.\n// 2. Prevent iOS and IE text size adjust after device orientation change,\n// without disabling user zoom.\n//\n\nhtml {\n font-family: sans-serif; // 1\n -ms-text-size-adjust: 100%; // 2\n -webkit-text-size-adjust: 100%; // 2\n}\n\n//\n// Remove default margin.\n//\n\nbody {\n margin: 0;\n}\n\n// HTML5 display definitions\n// ==========================================================================\n\n//\n// Correct `block` display not defined for any HTML5 element in IE 8/9.\n// Correct `block` display not defined for `details` or `summary` in IE 10/11\n// and Firefox.\n// Correct `block` display not defined for `main` in IE 11.\n//\n\narticle,\naside,\ndetails,\nfigcaption,\nfigure,\nfooter,\nheader,\nhgroup,\nmain,\nmenu,\nnav,\nsection,\nsummary {\n display: block;\n}\n\n//\n// 1. Correct `inline-block` display not defined in IE 8/9.\n// 2. Normalize vertical alignment of `progress` in Chrome, Firefox, and Opera.\n//\n\naudio,\ncanvas,\nprogress,\nvideo {\n display: inline-block; // 1\n vertical-align: baseline; // 2\n}\n\n//\n// Prevent modern browsers from displaying `audio` without controls.\n// Remove excess height in iOS 5 devices.\n//\n\naudio:not([controls]) {\n display: none;\n height: 0;\n}\n\n//\n// Address `[hidden]` styling not present in IE 8/9/10.\n// Hide the `template` element in IE 8/9/10/11, Safari, and Firefox < 22.\n//\n\n[hidden],\ntemplate {\n display: none;\n}\n\n// Links\n// ==========================================================================\n\n//\n// Remove the gray background color from active links in IE 10.\n//\n\na {\n background-color: transparent;\n}\n\n//\n// Improve readability of focused elements when they are also in an\n// active/hover state.\n//\n\na:active,\na:hover {\n outline: 0;\n}\n\n// Text-level semantics\n// ==========================================================================\n\n//\n// Address styling not present in IE 8/9/10/11, Safari, and Chrome.\n//\n\nabbr[title] {\n border-bottom: 1px dotted;\n}\n\n//\n// Address style set to `bolder` in Firefox 4+, Safari, and Chrome.\n//\n\nb,\nstrong {\n font-weight: bold;\n}\n\n//\n// Address styling not present in Safari and Chrome.\n//\n\ndfn {\n font-style: italic;\n}\n\n//\n// Address variable `h1` font-size and margin within `section` and `article`\n// contexts in Firefox 4+, Safari, and Chrome.\n//\n\nh1 {\n font-size: 2em;\n margin: 0.67em 0;\n}\n\n//\n// Address styling not present in IE 8/9.\n//\n\nmark {\n background: #ff0;\n color: #000;\n}\n\n//\n// Address inconsistent and variable font size in all browsers.\n//\n\nsmall {\n font-size: 80%;\n}\n\n//\n// Prevent `sub` and `sup` affecting `line-height` in all browsers.\n//\n\nsub,\nsup {\n font-size: 75%;\n line-height: 0;\n position: relative;\n vertical-align: baseline;\n}\n\nsup {\n top: -0.5em;\n}\n\nsub {\n bottom: -0.25em;\n}\n\n// Embedded content\n// ==========================================================================\n\n//\n// Remove border when inside `a` element in IE 8/9/10.\n//\n\nimg {\n border: 0;\n}\n\n//\n// Correct overflow not hidden in IE 9/10/11.\n//\n\nsvg:not(:root) {\n overflow: hidden;\n}\n\n// Grouping content\n// ==========================================================================\n\n//\n// Address margin not present in IE 8/9 and Safari.\n//\n\nfigure {\n margin: 1em 40px;\n}\n\n//\n// Address differences between Firefox and other browsers.\n//\n\nhr {\n box-sizing: content-box;\n height: 0;\n}\n\n//\n// Contain overflow in all browsers.\n//\n\npre {\n overflow: auto;\n}\n\n//\n// Address odd `em`-unit font size rendering in all browsers.\n//\n\ncode,\nkbd,\npre,\nsamp {\n font-family: monospace, monospace;\n font-size: 1em;\n}\n\n// Forms\n// ==========================================================================\n\n//\n// Known limitation: by default, Chrome and Safari on OS X allow very limited\n// styling of `select`, unless a `border` property is set.\n//\n\n//\n// 1. Correct color not being inherited.\n// Known issue: affects color of disabled elements.\n// 2. Correct font properties not being inherited.\n// 3. Address margins set differently in Firefox 4+, Safari, and Chrome.\n//\n\nbutton,\ninput,\noptgroup,\nselect,\ntextarea {\n color: inherit; // 1\n font: inherit; // 2\n margin: 0; // 3\n}\n\n//\n// Address `overflow` set to `hidden` in IE 8/9/10/11.\n//\n\nbutton {\n overflow: visible;\n}\n\n//\n// Address inconsistent `text-transform` inheritance for `button` and `select`.\n// All other form control elements do not inherit `text-transform` values.\n// Correct `button` style inheritance in Firefox, IE 8/9/10/11, and Opera.\n// Correct `select` style inheritance in Firefox.\n//\n\nbutton,\nselect {\n text-transform: none;\n}\n\n//\n// 1. Avoid the WebKit bug in Android 4.0.* where (2) destroys native `audio`\n// and `video` controls.\n// 2. Correct inability to style clickable `input` types in iOS.\n// 3. Improve usability and consistency of cursor style between image-type\n// `input` and others.\n//\n\nbutton,\nhtml input[type=\"button\"], // 1\ninput[type=\"reset\"],\ninput[type=\"submit\"] {\n -webkit-appearance: button; // 2\n cursor: pointer; // 3\n}\n\n//\n// Re-set default cursor for disabled elements.\n//\n\nbutton[disabled],\nhtml input[disabled] {\n cursor: default;\n}\n\n//\n// Remove inner padding and border in Firefox 4+.\n//\n\nbutton::-moz-focus-inner,\ninput::-moz-focus-inner {\n border: 0;\n padding: 0;\n}\n\n//\n// Address Firefox 4+ setting `line-height` on `input` using `!important` in\n// the UA stylesheet.\n//\n\ninput {\n line-height: normal;\n}\n\n//\n// It's recommended that you don't attempt to style these elements.\n// Firefox's implementation doesn't respect box-sizing, padding, or width.\n//\n// 1. Address box sizing set to `content-box` in IE 8/9/10.\n// 2. Remove excess padding in IE 8/9/10.\n//\n\ninput[type=\"checkbox\"],\ninput[type=\"radio\"] {\n box-sizing: border-box; // 1\n padding: 0; // 2\n}\n\n//\n// Fix the cursor style for Chrome's increment/decrement buttons. For certain\n// `font-size` values of the `input`, it causes the cursor style of the\n// decrement button to change from `default` to `text`.\n//\n\ninput[type=\"number\"]::-webkit-inner-spin-button,\ninput[type=\"number\"]::-webkit-outer-spin-button {\n height: auto;\n}\n\n//\n// 1. Address `appearance` set to `searchfield` in Safari and Chrome.\n// 2. Address `box-sizing` set to `border-box` in Safari and Chrome.\n//\n\ninput[type=\"search\"] {\n -webkit-appearance: textfield; // 1\n box-sizing: content-box; //2\n}\n\n//\n// Remove inner padding and search cancel button in Safari and Chrome on OS X.\n// Safari (but not Chrome) clips the cancel button when the search input has\n// padding (and `textfield` appearance).\n//\n\ninput[type=\"search\"]::-webkit-search-cancel-button,\ninput[type=\"search\"]::-webkit-search-decoration {\n -webkit-appearance: none;\n}\n\n//\n// Define consistent border, margin, and padding.\n//\n\nfieldset {\n border: 1px solid #c0c0c0;\n margin: 0 2px;\n padding: 0.35em 0.625em 0.75em;\n}\n\n//\n// 1. Correct `color` not being inherited in IE 8/9/10/11.\n// 2. Remove padding so people aren't caught out if they zero out fieldsets.\n//\n\nlegend {\n border: 0; // 1\n padding: 0; // 2\n}\n\n//\n// Remove default vertical scrollbar in IE 8/9/10/11.\n//\n\ntextarea {\n overflow: auto;\n}\n\n//\n// Don't inherit the `font-weight` (applied by a rule above).\n// NOTE: the default cannot safely be changed in Chrome and Safari on OS X.\n//\n\noptgroup {\n font-weight: bold;\n}\n\n// Tables\n// ==========================================================================\n\n//\n// Remove most spacing between table cells.\n//\n\ntable {\n border-collapse: collapse;\n border-spacing: 0;\n}\n\ntd,\nth {\n padding: 0;\n}\n","/*! Source: https://github.com/h5bp/html5-boilerplate/blob/master/src/css/main.css */\n\n// ==========================================================================\n// Print styles.\n// Inlined to avoid the additional HTTP request: h5bp.com/r\n// ==========================================================================\n\n@media print {\n *,\n *:before,\n *:after {\n background: transparent !important;\n color: #000 !important; // Black prints faster: h5bp.com/s\n box-shadow: none !important;\n text-shadow: none !important;\n }\n\n a,\n a:visited {\n text-decoration: underline;\n }\n\n a[href]:after {\n content: \" (\" attr(href) \")\";\n }\n\n abbr[title]:after {\n content: \" (\" attr(title) \")\";\n }\n\n // Don't show links that are fragment identifiers,\n // or use the `javascript:` pseudo protocol\n a[href^=\"#\"]:after,\n a[href^=\"javascript:\"]:after {\n content: \"\";\n }\n\n pre,\n blockquote {\n border: 1px solid #999;\n page-break-inside: avoid;\n }\n\n thead {\n display: table-header-group; // h5bp.com/t\n }\n\n tr,\n img {\n page-break-inside: avoid;\n }\n\n img {\n max-width: 100% !important;\n }\n\n p,\n h2,\n h3 {\n orphans: 3;\n widows: 3;\n }\n\n h2,\n h3 {\n page-break-after: avoid;\n }\n\n // Bootstrap specific changes start\n\n // Bootstrap components\n .navbar {\n display: none;\n }\n .btn,\n .dropup > .btn {\n > .caret {\n border-top-color: #000 !important;\n }\n }\n .label {\n border: 1px solid #000;\n }\n\n .table {\n border-collapse: collapse !important;\n\n td,\n th {\n background-color: #fff !important;\n }\n }\n .table-bordered {\n th,\n td {\n border: 1px solid #ddd !important;\n }\n }\n\n // Bootstrap specific changes end\n}\n","//\n// Glyphicons for Bootstrap\n//\n// Since icons are fonts, they can be placed anywhere text is placed and are\n// thus automatically sized to match the surrounding child. To use, create an\n// inline element with the appropriate classes, like so:\n//\n// <a href=\"#\"><span class=\"glyphicon glyphicon-star\"></span> Star</a>\n\n// Import the fonts\n@font-face {\n font-family: 'Glyphicons Halflings';\n src: url('@{icon-font-path}@{icon-font-name}.eot');\n src: url('@{icon-font-path}@{icon-font-name}.eot?#iefix') format('embedded-opentype'),\n url('@{icon-font-path}@{icon-font-name}.woff2') format('woff2'),\n url('@{icon-font-path}@{icon-font-name}.woff') format('woff'),\n url('@{icon-font-path}@{icon-font-name}.ttf') format('truetype'),\n url('@{icon-font-path}@{icon-font-name}.svg#@{icon-font-svg-id}') format('svg');\n}\n\n// Catchall baseclass\n.glyphicon {\n position: relative;\n top: 1px;\n display: inline-block;\n font-family: 'Glyphicons Halflings';\n font-style: normal;\n font-weight: normal;\n line-height: 1;\n -webkit-font-smoothing: antialiased;\n -moz-osx-font-smoothing: grayscale;\n}\n\n// Individual icons\n.glyphicon-asterisk { &:before { content: \"\\002a\"; } }\n.glyphicon-plus { &:before { content: \"\\002b\"; } }\n.glyphicon-euro,\n.glyphicon-eur { &:before { content: \"\\20ac\"; } }\n.glyphicon-minus { &:before { content: \"\\2212\"; } }\n.glyphicon-cloud { &:before { content: \"\\2601\"; } }\n.glyphicon-envelope { &:before { content: \"\\2709\"; } }\n.glyphicon-pencil { &:before { content: \"\\270f\"; } }\n.glyphicon-glass { &:before { content: \"\\e001\"; } }\n.glyphicon-music { &:before { content: \"\\e002\"; } }\n.glyphicon-search { &:before { content: \"\\e003\"; } }\n.glyphicon-heart { &:before { content: \"\\e005\"; } }\n.glyphicon-star { &:before { content: \"\\e006\"; } }\n.glyphicon-star-empty { &:before { content: \"\\e007\"; } }\n.glyphicon-user { &:before { content: \"\\e008\"; } }\n.glyphicon-film { &:before { content: \"\\e009\"; } }\n.glyphicon-th-large { &:before { content: \"\\e010\"; } }\n.glyphicon-th { &:before { content: \"\\e011\"; } }\n.glyphicon-th-list { &:before { content: \"\\e012\"; } }\n.glyphicon-ok { &:before { content: \"\\e013\"; } }\n.glyphicon-remove { &:before { content: \"\\e014\"; } }\n.glyphicon-zoom-in { &:before { content: \"\\e015\"; } }\n.glyphicon-zoom-out { &:before { content: \"\\e016\"; } }\n.glyphicon-off { &:before { content: \"\\e017\"; } }\n.glyphicon-signal { &:before { content: \"\\e018\"; } }\n.glyphicon-cog { &:before { content: \"\\e019\"; } }\n.glyphicon-trash { &:before { content: \"\\e020\"; } }\n.glyphicon-home { &:before { content: \"\\e021\"; } }\n.glyphicon-file { &:before { content: \"\\e022\"; } }\n.glyphicon-time { &:before { content: \"\\e023\"; } }\n.glyphicon-road { &:before { content: \"\\e024\"; } }\n.glyphicon-download-alt { &:before { content: \"\\e025\"; } }\n.glyphicon-download { &:before { content: \"\\e026\"; } }\n.glyphicon-upload { &:before { content: \"\\e027\"; } }\n.glyphicon-inbox { &:before { content: \"\\e028\"; } }\n.glyphicon-play-circle { &:before { content: \"\\e029\"; } }\n.glyphicon-repeat { &:before { content: \"\\e030\"; } }\n.glyphicon-refresh { &:before { content: \"\\e031\"; } }\n.glyphicon-list-alt { &:before { content: \"\\e032\"; } }\n.glyphicon-lock { &:before { content: \"\\e033\"; } }\n.glyphicon-flag { &:before { content: \"\\e034\"; } }\n.glyphicon-headphones { &:before { content: \"\\e035\"; } }\n.glyphicon-volume-off { &:before { content: \"\\e036\"; } }\n.glyphicon-volume-down { &:before { content: \"\\e037\"; } }\n.glyphicon-volume-up { &:before { content: \"\\e038\"; } }\n.glyphicon-qrcode { &:before { content: \"\\e039\"; } }\n.glyphicon-barcode { &:before { content: \"\\e040\"; } }\n.glyphicon-tag { &:before { content: \"\\e041\"; } }\n.glyphicon-tags { &:before { content: \"\\e042\"; } }\n.glyphicon-book { &:before { content: \"\\e043\"; } }\n.glyphicon-bookmark { &:before { content: \"\\e044\"; } }\n.glyphicon-print { &:before { content: \"\\e045\"; } }\n.glyphicon-camera { &:before { content: \"\\e046\"; } }\n.glyphicon-font { &:before { content: \"\\e047\"; } }\n.glyphicon-bold { &:before { content: \"\\e048\"; } }\n.glyphicon-italic { &:before { content: \"\\e049\"; } }\n.glyphicon-text-height { &:before { content: \"\\e050\"; } }\n.glyphicon-text-width { &:before { content: \"\\e051\"; } }\n.glyphicon-align-left { &:before { content: \"\\e052\"; } }\n.glyphicon-align-center { &:before { content: \"\\e053\"; } }\n.glyphicon-align-right { &:before { content: \"\\e054\"; } }\n.glyphicon-align-justify { &:before { content: \"\\e055\"; } }\n.glyphicon-list { &:before { content: \"\\e056\"; } }\n.glyphicon-indent-left { &:before { content: \"\\e057\"; } }\n.glyphicon-indent-right { &:before { content: \"\\e058\"; } }\n.glyphicon-facetime-video { &:before { content: \"\\e059\"; } }\n.glyphicon-picture { &:before { content: \"\\e060\"; } }\n.glyphicon-map-marker { &:before { content: \"\\e062\"; } }\n.glyphicon-adjust { &:before { content: \"\\e063\"; } }\n.glyphicon-tint { &:before { content: \"\\e064\"; } }\n.glyphicon-edit { &:before { content: \"\\e065\"; } }\n.glyphicon-share { &:before { content: \"\\e066\"; } }\n.glyphicon-check { &:before { content: \"\\e067\"; } }\n.glyphicon-move { &:before { content: \"\\e068\"; } }\n.glyphicon-step-backward { &:before { content: \"\\e069\"; } }\n.glyphicon-fast-backward { &:before { content: \"\\e070\"; } }\n.glyphicon-backward { &:before { content: \"\\e071\"; } }\n.glyphicon-play { &:before { content: \"\\e072\"; } }\n.glyphicon-pause { &:before { content: \"\\e073\"; } }\n.glyphicon-stop { &:before { content: \"\\e074\"; } }\n.glyphicon-forward { &:before { content: \"\\e075\"; } }\n.glyphicon-fast-forward { &:before { content: \"\\e076\"; } }\n.glyphicon-step-forward { &:before { content: \"\\e077\"; } }\n.glyphicon-eject { &:before { content: \"\\e078\"; } }\n.glyphicon-chevron-left { &:before { content: \"\\e079\"; } }\n.glyphicon-chevron-right { &:before { content: \"\\e080\"; } }\n.glyphicon-plus-sign { &:before { content: \"\\e081\"; } }\n.glyphicon-minus-sign { &:before { content: \"\\e082\"; } }\n.glyphicon-remove-sign { &:before { content: \"\\e083\"; } }\n.glyphicon-ok-sign { &:before { content: \"\\e084\"; } }\n.glyphicon-question-sign { &:before { content: \"\\e085\"; } }\n.glyphicon-info-sign { &:before { content: \"\\e086\"; } }\n.glyphicon-screenshot { &:before { content: \"\\e087\"; } }\n.glyphicon-remove-circle { &:before { content: \"\\e088\"; } }\n.glyphicon-ok-circle { &:before { content: \"\\e089\"; } }\n.glyphicon-ban-circle { &:before { content: \"\\e090\"; } }\n.glyphicon-arrow-left { &:before { content: \"\\e091\"; } }\n.glyphicon-arrow-right { &:before { content: \"\\e092\"; } }\n.glyphicon-arrow-up { &:before { content: \"\\e093\"; } }\n.glyphicon-arrow-down { &:before { content: \"\\e094\"; } }\n.glyphicon-share-alt { &:before { content: \"\\e095\"; } }\n.glyphicon-resize-full { &:before { content: \"\\e096\"; } }\n.glyphicon-resize-small { &:before { content: \"\\e097\"; } }\n.glyphicon-exclamation-sign { &:before { content: \"\\e101\"; } }\n.glyphicon-gift { &:before { content: \"\\e102\"; } }\n.glyphicon-leaf { &:before { content: \"\\e103\"; } }\n.glyphicon-fire { &:before { content: \"\\e104\"; } }\n.glyphicon-eye-open { &:before { content: \"\\e105\"; } }\n.glyphicon-eye-close { &:before { content: \"\\e106\"; } }\n.glyphicon-warning-sign { &:before { content: \"\\e107\"; } }\n.glyphicon-plane { &:before { content: \"\\e108\"; } }\n.glyphicon-calendar { &:before { content: \"\\e109\"; } }\n.glyphicon-random { &:before { content: \"\\e110\"; } }\n.glyphicon-comment { &:before { content: \"\\e111\"; } }\n.glyphicon-magnet { &:before { content: \"\\e112\"; } }\n.glyphicon-chevron-up { &:before { content: \"\\e113\"; } }\n.glyphicon-chevron-down { &:before { content: \"\\e114\"; } }\n.glyphicon-retweet { &:before { content: \"\\e115\"; } }\n.glyphicon-shopping-cart { &:before { content: \"\\e116\"; } }\n.glyphicon-folder-close { &:before { content: \"\\e117\"; } }\n.glyphicon-folder-open { &:before { content: \"\\e118\"; } }\n.glyphicon-resize-vertical { &:before { content: \"\\e119\"; } }\n.glyphicon-resize-horizontal { &:before { content: \"\\e120\"; } }\n.glyphicon-hdd { &:before { content: \"\\e121\"; } }\n.glyphicon-bullhorn { &:before { content: \"\\e122\"; } }\n.glyphicon-bell { &:before { content: \"\\e123\"; } }\n.glyphicon-certificate { &:before { content: \"\\e124\"; } }\n.glyphicon-thumbs-up { &:before { content: \"\\e125\"; } }\n.glyphicon-thumbs-down { &:before { content: \"\\e126\"; } }\n.glyphicon-hand-right { &:before { content: \"\\e127\"; } }\n.glyphicon-hand-left { &:before { content: \"\\e128\"; } }\n.glyphicon-hand-up { &:before { content: \"\\e129\"; } }\n.glyphicon-hand-down { &:before { content: \"\\e130\"; } }\n.glyphicon-circle-arrow-right { &:before { content: \"\\e131\"; } }\n.glyphicon-circle-arrow-left { &:before { content: \"\\e132\"; } }\n.glyphicon-circle-arrow-up { &:before { content: \"\\e133\"; } }\n.glyphicon-circle-arrow-down { &:before { content: \"\\e134\"; } }\n.glyphicon-globe { &:before { content: \"\\e135\"; } }\n.glyphicon-wrench { &:before { content: \"\\e136\"; } }\n.glyphicon-tasks { &:before { content: \"\\e137\"; } }\n.glyphicon-filter { &:before { content: \"\\e138\"; } }\n.glyphicon-briefcase { &:before { content: \"\\e139\"; } }\n.glyphicon-fullscreen { &:before { content: \"\\e140\"; } }\n.glyphicon-dashboard { &:before { content: \"\\e141\"; } }\n.glyphicon-paperclip { &:before { content: \"\\e142\"; } }\n.glyphicon-heart-empty { &:before { content: \"\\e143\"; } }\n.glyphicon-link { &:before { content: \"\\e144\"; } }\n.glyphicon-phone { &:before { content: \"\\e145\"; } }\n.glyphicon-pushpin { &:before { content: \"\\e146\"; } }\n.glyphicon-usd { &:before { content: \"\\e148\"; } }\n.glyphicon-gbp { &:before { content: \"\\e149\"; } }\n.glyphicon-sort { &:before { content: \"\\e150\"; } }\n.glyphicon-sort-by-alphabet { &:before { content: \"\\e151\"; } }\n.glyphicon-sort-by-alphabet-alt { &:before { content: \"\\e152\"; } }\n.glyphicon-sort-by-order { &:before { content: \"\\e153\"; } }\n.glyphicon-sort-by-order-alt { &:before { content: \"\\e154\"; } }\n.glyphicon-sort-by-attributes { &:before { content: \"\\e155\"; } }\n.glyphicon-sort-by-attributes-alt { &:before { content: \"\\e156\"; } }\n.glyphicon-unchecked { &:before { content: \"\\e157\"; } }\n.glyphicon-expand { &:before { content: \"\\e158\"; } }\n.glyphicon-collapse-down { &:before { content: \"\\e159\"; } }\n.glyphicon-collapse-up { &:before { content: \"\\e160\"; } }\n.glyphicon-log-in { &:before { content: \"\\e161\"; } }\n.glyphicon-flash { &:before { content: \"\\e162\"; } }\n.glyphicon-log-out { &:before { content: \"\\e163\"; } }\n.glyphicon-new-window { &:before { content: \"\\e164\"; } }\n.glyphicon-record { &:before { content: \"\\e165\"; } }\n.glyphicon-save { &:before { content: \"\\e166\"; } }\n.glyphicon-open { &:before { content: \"\\e167\"; } }\n.glyphicon-saved { &:before { content: \"\\e168\"; } }\n.glyphicon-import { &:before { content: \"\\e169\"; } }\n.glyphicon-export { &:before { content: \"\\e170\"; } }\n.glyphicon-send { &:before { content: \"\\e171\"; } }\n.glyphicon-floppy-disk { &:before { content: \"\\e172\"; } }\n.glyphicon-floppy-saved { &:before { content: \"\\e173\"; } }\n.glyphicon-floppy-remove { &:before { content: \"\\e174\"; } }\n.glyphicon-floppy-save { &:before { content: \"\\e175\"; } }\n.glyphicon-floppy-open { &:before { content: \"\\e176\"; } }\n.glyphicon-credit-card { &:before { content: \"\\e177\"; } }\n.glyphicon-transfer { &:before { content: \"\\e178\"; } }\n.glyphicon-cutlery { &:before { content: \"\\e179\"; } }\n.glyphicon-header { &:before { content: \"\\e180\"; } }\n.glyphicon-compressed { &:before { content: \"\\e181\"; } }\n.glyphicon-earphone { &:before { content: \"\\e182\"; } }\n.glyphicon-phone-alt { &:before { content: \"\\e183\"; } }\n.glyphicon-tower { &:before { content: \"\\e184\"; } }\n.glyphicon-stats { &:before { content: \"\\e185\"; } }\n.glyphicon-sd-video { &:before { content: \"\\e186\"; } }\n.glyphicon-hd-video { &:before { content: \"\\e187\"; } }\n.glyphicon-subtitles { &:before { content: \"\\e188\"; } }\n.glyphicon-sound-stereo { &:before { content: \"\\e189\"; } }\n.glyphicon-sound-dolby { &:before { content: \"\\e190\"; } }\n.glyphicon-sound-5-1 { &:before { content: \"\\e191\"; } }\n.glyphicon-sound-6-1 { &:before { content: \"\\e192\"; } }\n.glyphicon-sound-7-1 { &:before { content: \"\\e193\"; } }\n.glyphicon-copyright-mark { &:before { content: \"\\e194\"; } }\n.glyphicon-registration-mark { &:before { content: \"\\e195\"; } }\n.glyphicon-cloud-download { &:before { content: \"\\e197\"; } }\n.glyphicon-cloud-upload { &:before { content: \"\\e198\"; } }\n.glyphicon-tree-conifer { &:before { content: \"\\e199\"; } }\n.glyphicon-tree-deciduous { &:before { content: \"\\e200\"; } }\n.glyphicon-cd { &:before { content: \"\\e201\"; } }\n.glyphicon-save-file { &:before { content: \"\\e202\"; } }\n.glyphicon-open-file { &:before { content: \"\\e203\"; } }\n.glyphicon-level-up { &:before { content: \"\\e204\"; } }\n.glyphicon-copy { &:before { content: \"\\e205\"; } }\n.glyphicon-paste { &:before { content: \"\\e206\"; } }\n// The following 2 Glyphicons are omitted for the time being because\n// they currently use Unicode codepoints that are outside the\n// Basic Multilingual Plane (BMP). Older buggy versions of WebKit can't handle\n// non-BMP codepoints in CSS string escapes, and thus can't display these two icons.\n// Notably, the bug affects some older versions of the Android Browser.\n// More info: https://github.com/twbs/bootstrap/issues/10106\n// .glyphicon-door { &:before { content: \"\\1f6aa\"; } }\n// .glyphicon-key { &:before { content: \"\\1f511\"; } }\n.glyphicon-alert { &:before { content: \"\\e209\"; } }\n.glyphicon-equalizer { &:before { content: \"\\e210\"; } }\n.glyphicon-king { &:before { content: \"\\e211\"; } }\n.glyphicon-queen { &:before { content: \"\\e212\"; } }\n.glyphicon-pawn { &:before { content: \"\\e213\"; } }\n.glyphicon-bishop { &:before { content: \"\\e214\"; } }\n.glyphicon-knight { &:before { content: \"\\e215\"; } }\n.glyphicon-baby-formula { &:before { content: \"\\e216\"; } }\n.glyphicon-tent { &:before { content: \"\\26fa\"; } }\n.glyphicon-blackboard { &:before { content: \"\\e218\"; } }\n.glyphicon-bed { &:before { content: \"\\e219\"; } }\n.glyphicon-apple { &:before { content: \"\\f8ff\"; } }\n.glyphicon-erase { &:before { content: \"\\e221\"; } }\n.glyphicon-hourglass { &:before { content: \"\\231b\"; } }\n.glyphicon-lamp { &:before { content: \"\\e223\"; } }\n.glyphicon-duplicate { &:before { content: \"\\e224\"; } }\n.glyphicon-piggy-bank { &:before { content: \"\\e225\"; } }\n.glyphicon-scissors { &:before { content: \"\\e226\"; } }\n.glyphicon-bitcoin { &:before { content: \"\\e227\"; } }\n.glyphicon-btc { &:before { content: \"\\e227\"; } }\n.glyphicon-xbt { &:before { content: \"\\e227\"; } }\n.glyphicon-yen { &:before { content: \"\\00a5\"; } }\n.glyphicon-jpy { &:before { content: \"\\00a5\"; } }\n.glyphicon-ruble { &:before { content: \"\\20bd\"; } }\n.glyphicon-rub { &:before { content: \"\\20bd\"; } }\n.glyphicon-scale { &:before { content: \"\\e230\"; } }\n.glyphicon-ice-lolly { &:before { content: \"\\e231\"; } }\n.glyphicon-ice-lolly-tasted { &:before { content: \"\\e232\"; } }\n.glyphicon-education { &:before { content: \"\\e233\"; } }\n.glyphicon-option-horizontal { &:before { content: \"\\e234\"; } }\n.glyphicon-option-vertical { &:before { content: \"\\e235\"; } }\n.glyphicon-menu-hamburger { &:before { content: \"\\e236\"; } }\n.glyphicon-modal-window { &:before { content: \"\\e237\"; } }\n.glyphicon-oil { &:before { content: \"\\e238\"; } }\n.glyphicon-grain { &:before { content: \"\\e239\"; } }\n.glyphicon-sunglasses { &:before { content: \"\\e240\"; } }\n.glyphicon-text-size { &:before { content: \"\\e241\"; } }\n.glyphicon-text-color { &:before { content: \"\\e242\"; } }\n.glyphicon-text-background { &:before { content: \"\\e243\"; } }\n.glyphicon-object-align-top { &:before { content: \"\\e244\"; } }\n.glyphicon-object-align-bottom { &:before { content: \"\\e245\"; } }\n.glyphicon-object-align-horizontal{ &:before { content: \"\\e246\"; } }\n.glyphicon-object-align-left { &:before { content: \"\\e247\"; } }\n.glyphicon-object-align-vertical { &:before { content: \"\\e248\"; } }\n.glyphicon-object-align-right { &:before { content: \"\\e249\"; } }\n.glyphicon-triangle-right { &:before { content: \"\\e250\"; } }\n.glyphicon-triangle-left { &:before { content: \"\\e251\"; } }\n.glyphicon-triangle-bottom { &:before { content: \"\\e252\"; } }\n.glyphicon-triangle-top { &:before { content: \"\\e253\"; } }\n.glyphicon-console { &:before { content: \"\\e254\"; } }\n.glyphicon-superscript { &:before { content: \"\\e255\"; } }\n.glyphicon-subscript { &:before { content: \"\\e256\"; } }\n.glyphicon-menu-left { &:before { content: \"\\e257\"; } }\n.glyphicon-menu-right { &:before { content: \"\\e258\"; } }\n.glyphicon-menu-down { &:before { content: \"\\e259\"; } }\n.glyphicon-menu-up { &:before { content: \"\\e260\"; } }\n","//\n// Scaffolding\n// --------------------------------------------------\n\n\n// Reset the box-sizing\n//\n// Heads up! This reset may cause conflicts with some third-party widgets.\n// For recommendations on resolving such conflicts, see\n// http://getbootstrap.com/getting-started/#third-box-sizing\n* {\n .box-sizing(border-box);\n}\n*:before,\n*:after {\n .box-sizing(border-box);\n}\n\n\n// Body reset\n\nhtml {\n font-size: 10px;\n -webkit-tap-highlight-color: rgba(0,0,0,0);\n}\n\nbody {\n font-family: @font-family-base;\n font-size: @font-size-base;\n line-height: @line-height-base;\n color: @text-color;\n background-color: @body-bg;\n}\n\n// Reset fonts for relevant elements\ninput,\nbutton,\nselect,\ntextarea {\n font-family: inherit;\n font-size: inherit;\n line-height: inherit;\n}\n\n\n// Links\n\na {\n color: @link-color;\n text-decoration: none;\n\n &:hover,\n &:focus {\n color: @link-hover-color;\n text-decoration: @link-hover-decoration;\n }\n\n &:focus {\n .tab-focus();\n }\n}\n\n\n// Figures\n//\n// We reset this here because previously Normalize had no `figure` margins. This\n// ensures we don't break anyone's use of the element.\n\nfigure {\n margin: 0;\n}\n\n\n// Images\n\nimg {\n vertical-align: middle;\n}\n\n// Responsive images (ensure images don't scale beyond their parents)\n.img-responsive {\n .img-responsive();\n}\n\n// Rounded corners\n.img-rounded {\n border-radius: @border-radius-large;\n}\n\n// Image thumbnails\n//\n// Heads up! This is mixin-ed into thumbnails.less for `.thumbnail`.\n.img-thumbnail {\n padding: @thumbnail-padding;\n line-height: @line-height-base;\n background-color: @thumbnail-bg;\n border: 1px solid @thumbnail-border;\n border-radius: @thumbnail-border-radius;\n .transition(all .2s ease-in-out);\n\n // Keep them at most 100% wide\n .img-responsive(inline-block);\n}\n\n// Perfect circle\n.img-circle {\n border-radius: 50%; // set radius in percents\n}\n\n\n// Horizontal rules\n\nhr {\n margin-top: @line-height-computed;\n margin-bottom: @line-height-computed;\n border: 0;\n border-top: 1px solid @hr-border;\n}\n\n\n// Only display content to screen readers\n//\n// See: http://a11yproject.com/posts/how-to-hide-content\n\n.sr-only {\n position: absolute;\n width: 1px;\n height: 1px;\n margin: -1px;\n padding: 0;\n overflow: hidden;\n clip: rect(0,0,0,0);\n border: 0;\n}\n\n// Use in conjunction with .sr-only to only display content when it's focused.\n// Useful for \"Skip to main content\" links; see http://www.w3.org/TR/2013/NOTE-WCAG20-TECHS-20130905/G1\n// Credit: HTML5 Boilerplate\n\n.sr-only-focusable {\n &:active,\n &:focus {\n position: static;\n width: auto;\n height: auto;\n margin: 0;\n overflow: visible;\n clip: auto;\n }\n}\n\n\n// iOS \"clickable elements\" fix for role=\"button\"\n//\n// Fixes \"clickability\" issue (and more generally, the firing of events such as focus as well)\n// for traditionally non-focusable elements with role=\"button\"\n// see https://developer.mozilla.org/en-US/docs/Web/Events/click#Safari_Mobile\n\n[role=\"button\"] {\n cursor: pointer;\n}\n","// Vendor Prefixes\n//\n// All vendor mixins are deprecated as of v3.2.0 due to the introduction of\n// Autoprefixer in our Gruntfile. They have been removed in v4.\n\n// - Animations\n// - Backface visibility\n// - Box shadow\n// - Box sizing\n// - Content columns\n// - Hyphens\n// - Placeholder text\n// - Transformations\n// - Transitions\n// - User Select\n\n\n// Animations\n.animation(@animation) {\n -webkit-animation: @animation;\n -o-animation: @animation;\n animation: @animation;\n}\n.animation-name(@name) {\n -webkit-animation-name: @name;\n animation-name: @name;\n}\n.animation-duration(@duration) {\n -webkit-animation-duration: @duration;\n animation-duration: @duration;\n}\n.animation-timing-function(@timing-function) {\n -webkit-animation-timing-function: @timing-function;\n animation-timing-function: @timing-function;\n}\n.animation-delay(@delay) {\n -webkit-animation-delay: @delay;\n animation-delay: @delay;\n}\n.animation-iteration-count(@iteration-count) {\n -webkit-animation-iteration-count: @iteration-count;\n animation-iteration-count: @iteration-count;\n}\n.animation-direction(@direction) {\n -webkit-animation-direction: @direction;\n animation-direction: @direction;\n}\n.animation-fill-mode(@fill-mode) {\n -webkit-animation-fill-mode: @fill-mode;\n animation-fill-mode: @fill-mode;\n}\n\n// Backface visibility\n// Prevent browsers from flickering when using CSS 3D transforms.\n// Default value is `visible`, but can be changed to `hidden`\n\n.backface-visibility(@visibility) {\n -webkit-backface-visibility: @visibility;\n -moz-backface-visibility: @visibility;\n backface-visibility: @visibility;\n}\n\n// Drop shadows\n//\n// Note: Deprecated `.box-shadow()` as of v3.1.0 since all of Bootstrap's\n// supported browsers that have box shadow capabilities now support it.\n\n.box-shadow(@shadow) {\n -webkit-box-shadow: @shadow; // iOS <4.3 & Android <4.1\n box-shadow: @shadow;\n}\n\n// Box sizing\n.box-sizing(@boxmodel) {\n -webkit-box-sizing: @boxmodel;\n -moz-box-sizing: @boxmodel;\n box-sizing: @boxmodel;\n}\n\n// CSS3 Content Columns\n.content-columns(@column-count; @column-gap: @grid-gutter-width) {\n -webkit-column-count: @column-count;\n -moz-column-count: @column-count;\n column-count: @column-count;\n -webkit-column-gap: @column-gap;\n -moz-column-gap: @column-gap;\n column-gap: @column-gap;\n}\n\n// Optional hyphenation\n.hyphens(@mode: auto) {\n word-wrap: break-word;\n -webkit-hyphens: @mode;\n -moz-hyphens: @mode;\n -ms-hyphens: @mode; // IE10+\n -o-hyphens: @mode;\n hyphens: @mode;\n}\n\n// Placeholder text\n.placeholder(@color: @input-color-placeholder) {\n // Firefox\n &::-moz-placeholder {\n color: @color;\n opacity: 1; // Override Firefox's unusual default opacity; see https://github.com/twbs/bootstrap/pull/11526\n }\n &:-ms-input-placeholder { color: @color; } // Internet Explorer 10+\n &::-webkit-input-placeholder { color: @color; } // Safari and Chrome\n}\n\n// Transformations\n.scale(@ratio) {\n -webkit-transform: scale(@ratio);\n -ms-transform: scale(@ratio); // IE9 only\n -o-transform: scale(@ratio);\n transform: scale(@ratio);\n}\n.scale(@ratioX; @ratioY) {\n -webkit-transform: scale(@ratioX, @ratioY);\n -ms-transform: scale(@ratioX, @ratioY); // IE9 only\n -o-transform: scale(@ratioX, @ratioY);\n transform: scale(@ratioX, @ratioY);\n}\n.scaleX(@ratio) {\n -webkit-transform: scaleX(@ratio);\n -ms-transform: scaleX(@ratio); // IE9 only\n -o-transform: scaleX(@ratio);\n transform: scaleX(@ratio);\n}\n.scaleY(@ratio) {\n -webkit-transform: scaleY(@ratio);\n -ms-transform: scaleY(@ratio); // IE9 only\n -o-transform: scaleY(@ratio);\n transform: scaleY(@ratio);\n}\n.skew(@x; @y) {\n -webkit-transform: skewX(@x) skewY(@y);\n -ms-transform: skewX(@x) skewY(@y); // See https://github.com/twbs/bootstrap/issues/4885; IE9+\n -o-transform: skewX(@x) skewY(@y);\n transform: skewX(@x) skewY(@y);\n}\n.translate(@x; @y) {\n -webkit-transform: translate(@x, @y);\n -ms-transform: translate(@x, @y); // IE9 only\n -o-transform: translate(@x, @y);\n transform: translate(@x, @y);\n}\n.translate3d(@x; @y; @z) {\n -webkit-transform: translate3d(@x, @y, @z);\n transform: translate3d(@x, @y, @z);\n}\n.rotate(@degrees) {\n -webkit-transform: rotate(@degrees);\n -ms-transform: rotate(@degrees); // IE9 only\n -o-transform: rotate(@degrees);\n transform: rotate(@degrees);\n}\n.rotateX(@degrees) {\n -webkit-transform: rotateX(@degrees);\n -ms-transform: rotateX(@degrees); // IE9 only\n -o-transform: rotateX(@degrees);\n transform: rotateX(@degrees);\n}\n.rotateY(@degrees) {\n -webkit-transform: rotateY(@degrees);\n -ms-transform: rotateY(@degrees); // IE9 only\n -o-transform: rotateY(@degrees);\n transform: rotateY(@degrees);\n}\n.perspective(@perspective) {\n -webkit-perspective: @perspective;\n -moz-perspective: @perspective;\n perspective: @perspective;\n}\n.perspective-origin(@perspective) {\n -webkit-perspective-origin: @perspective;\n -moz-perspective-origin: @perspective;\n perspective-origin: @perspective;\n}\n.transform-origin(@origin) {\n -webkit-transform-origin: @origin;\n -moz-transform-origin: @origin;\n -ms-transform-origin: @origin; // IE9 only\n transform-origin: @origin;\n}\n\n\n// Transitions\n\n.transition(@transition) {\n -webkit-transition: @transition;\n -o-transition: @transition;\n transition: @transition;\n}\n.transition-property(@transition-property) {\n -webkit-transition-property: @transition-property;\n transition-property: @transition-property;\n}\n.transition-delay(@transition-delay) {\n -webkit-transition-delay: @transition-delay;\n transition-delay: @transition-delay;\n}\n.transition-duration(@transition-duration) {\n -webkit-transition-duration: @transition-duration;\n transition-duration: @transition-duration;\n}\n.transition-timing-function(@timing-function) {\n -webkit-transition-timing-function: @timing-function;\n transition-timing-function: @timing-function;\n}\n.transition-transform(@transition) {\n -webkit-transition: -webkit-transform @transition;\n -moz-transition: -moz-transform @transition;\n -o-transition: -o-transform @transition;\n transition: transform @transition;\n}\n\n\n// User select\n// For selecting text on the page\n\n.user-select(@select) {\n -webkit-user-select: @select;\n -moz-user-select: @select;\n -ms-user-select: @select; // IE10+\n user-select: @select;\n}\n","// WebKit-style focus\n\n.tab-focus() {\n // WebKit-specific. Other browsers will keep their default outline style.\n // (Initially tried to also force default via `outline: initial`,\n // but that seems to erroneously remove the outline in Firefox altogether.)\n outline: 5px auto -webkit-focus-ring-color;\n outline-offset: -2px;\n}\n","// Image Mixins\n// - Responsive image\n// - Retina image\n\n\n// Responsive image\n//\n// Keep images from scaling beyond the width of their parents.\n.img-responsive(@display: block) {\n display: @display;\n max-width: 100%; // Part 1: Set a maximum relative to the parent\n height: auto; // Part 2: Scale the height according to the width, otherwise you get stretching\n}\n\n\n// Retina image\n//\n// Short retina mixin for setting background-image and -size. Note that the\n// spelling of `min--moz-device-pixel-ratio` is intentional.\n.img-retina(@file-1x; @file-2x; @width-1x; @height-1x) {\n background-image: url(\"@{file-1x}\");\n\n @media\n only screen and (-webkit-min-device-pixel-ratio: 2),\n only screen and ( min--moz-device-pixel-ratio: 2),\n only screen and ( -o-min-device-pixel-ratio: 2/1),\n only screen and ( min-device-pixel-ratio: 2),\n only screen and ( min-resolution: 192dpi),\n only screen and ( min-resolution: 2dppx) {\n background-image: url(\"@{file-2x}\");\n background-size: @width-1x @height-1x;\n }\n}\n","//\n// Typography\n// --------------------------------------------------\n\n\n// Headings\n// -------------------------\n\nh1, h2, h3, h4, h5, h6,\n.h1, .h2, .h3, .h4, .h5, .h6 {\n font-family: @headings-font-family;\n font-weight: @headings-font-weight;\n line-height: @headings-line-height;\n color: @headings-color;\n\n small,\n .small {\n font-weight: normal;\n line-height: 1;\n color: @headings-small-color;\n }\n}\n\nh1, .h1,\nh2, .h2,\nh3, .h3 {\n margin-top: @line-height-computed;\n margin-bottom: (@line-height-computed / 2);\n\n small,\n .small {\n font-size: 65%;\n }\n}\nh4, .h4,\nh5, .h5,\nh6, .h6 {\n margin-top: (@line-height-computed / 2);\n margin-bottom: (@line-height-computed / 2);\n\n small,\n .small {\n font-size: 75%;\n }\n}\n\nh1, .h1 { font-size: @font-size-h1; }\nh2, .h2 { font-size: @font-size-h2; }\nh3, .h3 { font-size: @font-size-h3; }\nh4, .h4 { font-size: @font-size-h4; }\nh5, .h5 { font-size: @font-size-h5; }\nh6, .h6 { font-size: @font-size-h6; }\n\n\n// Body text\n// -------------------------\n\np {\n margin: 0 0 (@line-height-computed / 2);\n}\n\n.lead {\n margin-bottom: @line-height-computed;\n font-size: floor((@font-size-base * 1.15));\n font-weight: 300;\n line-height: 1.4;\n\n @media (min-width: @screen-sm-min) {\n font-size: (@font-size-base * 1.5);\n }\n}\n\n\n// Emphasis & misc\n// -------------------------\n\n// Ex: (12px small font / 14px base font) * 100% = about 85%\nsmall,\n.small {\n font-size: floor((100% * @font-size-small / @font-size-base));\n}\n\nmark,\n.mark {\n background-color: @state-warning-bg;\n padding: .2em;\n}\n\n// Alignment\n.text-left { text-align: left; }\n.text-right { text-align: right; }\n.text-center { text-align: center; }\n.text-justify { text-align: justify; }\n.text-nowrap { white-space: nowrap; }\n\n// Transformation\n.text-lowercase { text-transform: lowercase; }\n.text-uppercase { text-transform: uppercase; }\n.text-capitalize { text-transform: capitalize; }\n\n// Contextual colors\n.text-muted {\n color: @text-muted;\n}\n.text-primary {\n .text-emphasis-variant(@brand-primary);\n}\n.text-success {\n .text-emphasis-variant(@state-success-text);\n}\n.text-info {\n .text-emphasis-variant(@state-info-text);\n}\n.text-warning {\n .text-emphasis-variant(@state-warning-text);\n}\n.text-danger {\n .text-emphasis-variant(@state-danger-text);\n}\n\n// Contextual backgrounds\n// For now we'll leave these alongside the text classes until v4 when we can\n// safely shift things around (per SemVer rules).\n.bg-primary {\n // Given the contrast here, this is the only class to have its color inverted\n // automatically.\n color: #fff;\n .bg-variant(@brand-primary);\n}\n.bg-success {\n .bg-variant(@state-success-bg);\n}\n.bg-info {\n .bg-variant(@state-info-bg);\n}\n.bg-warning {\n .bg-variant(@state-warning-bg);\n}\n.bg-danger {\n .bg-variant(@state-danger-bg);\n}\n\n\n// Page header\n// -------------------------\n\n.page-header {\n padding-bottom: ((@line-height-computed / 2) - 1);\n margin: (@line-height-computed * 2) 0 @line-height-computed;\n border-bottom: 1px solid @page-header-border-color;\n}\n\n\n// Lists\n// -------------------------\n\n// Unordered and Ordered lists\nul,\nol {\n margin-top: 0;\n margin-bottom: (@line-height-computed / 2);\n ul,\n ol {\n margin-bottom: 0;\n }\n}\n\n// List options\n\n// Unstyled keeps list items block level, just removes default browser padding and list-style\n.list-unstyled {\n padding-left: 0;\n list-style: none;\n}\n\n// Inline turns list items into inline-block\n.list-inline {\n .list-unstyled();\n margin-left: -5px;\n\n > li {\n display: inline-block;\n padding-left: 5px;\n padding-right: 5px;\n }\n}\n\n// Description Lists\ndl {\n margin-top: 0; // Remove browser default\n margin-bottom: @line-height-computed;\n}\ndt,\ndd {\n line-height: @line-height-base;\n}\ndt {\n font-weight: bold;\n}\ndd {\n margin-left: 0; // Undo browser default\n}\n\n// Horizontal description lists\n//\n// Defaults to being stacked without any of the below styles applied, until the\n// grid breakpoint is reached (default of ~768px).\n\n.dl-horizontal {\n dd {\n &:extend(.clearfix all); // Clear the floated `dt` if an empty `dd` is present\n }\n\n @media (min-width: @dl-horizontal-breakpoint) {\n dt {\n float: left;\n width: (@dl-horizontal-offset - 20);\n clear: left;\n text-align: right;\n .text-overflow();\n }\n dd {\n margin-left: @dl-horizontal-offset;\n }\n }\n}\n\n\n// Misc\n// -------------------------\n\n// Abbreviations and acronyms\nabbr[title],\n// Add data-* attribute to help out our tooltip plugin, per https://github.com/twbs/bootstrap/issues/5257\nabbr[data-original-title] {\n cursor: help;\n border-bottom: 1px dotted @abbr-border-color;\n}\n.initialism {\n font-size: 90%;\n .text-uppercase();\n}\n\n// Blockquotes\nblockquote {\n padding: (@line-height-computed / 2) @line-height-computed;\n margin: 0 0 @line-height-computed;\n font-size: @blockquote-font-size;\n border-left: 5px solid @blockquote-border-color;\n\n p,\n ul,\n ol {\n &:last-child {\n margin-bottom: 0;\n }\n }\n\n // Note: Deprecated small and .small as of v3.1.0\n // Context: https://github.com/twbs/bootstrap/issues/11660\n footer,\n small,\n .small {\n display: block;\n font-size: 80%; // back to default font-size\n line-height: @line-height-base;\n color: @blockquote-small-color;\n\n &:before {\n content: '\\2014 \\00A0'; // em dash, nbsp\n }\n }\n}\n\n// Opposite alignment of blockquote\n//\n// Heads up: `blockquote.pull-right` has been deprecated as of v3.1.0.\n.blockquote-reverse,\nblockquote.pull-right {\n padding-right: 15px;\n padding-left: 0;\n border-right: 5px solid @blockquote-border-color;\n border-left: 0;\n text-align: right;\n\n // Account for citation\n footer,\n small,\n .small {\n &:before { content: ''; }\n &:after {\n content: '\\00A0 \\2014'; // nbsp, em dash\n }\n }\n}\n\n// Addresses\naddress {\n margin-bottom: @line-height-computed;\n font-style: normal;\n line-height: @line-height-base;\n}\n","// Typography\n\n.text-emphasis-variant(@color) {\n color: @color;\n a&:hover,\n a&:focus {\n color: darken(@color, 10%);\n }\n}\n","// Contextual backgrounds\n\n.bg-variant(@color) {\n background-color: @color;\n a&:hover,\n a&:focus {\n background-color: darken(@color, 10%);\n }\n}\n","// Text overflow\n// Requires inline-block or block for proper styling\n\n.text-overflow() {\n overflow: hidden;\n text-overflow: ellipsis;\n white-space: nowrap;\n}\n","//\n// Code (inline and block)\n// --------------------------------------------------\n\n\n// Inline and block code styles\ncode,\nkbd,\npre,\nsamp {\n font-family: @font-family-monospace;\n}\n\n// Inline code\ncode {\n padding: 2px 4px;\n font-size: 90%;\n color: @code-color;\n background-color: @code-bg;\n border-radius: @border-radius-base;\n}\n\n// User input typically entered via keyboard\nkbd {\n padding: 2px 4px;\n font-size: 90%;\n color: @kbd-color;\n background-color: @kbd-bg;\n border-radius: @border-radius-small;\n box-shadow: inset 0 -1px 0 rgba(0,0,0,.25);\n\n kbd {\n padding: 0;\n font-size: 100%;\n font-weight: bold;\n box-shadow: none;\n }\n}\n\n// Blocks of code\npre {\n display: block;\n padding: ((@line-height-computed - 1) / 2);\n margin: 0 0 (@line-height-computed / 2);\n font-size: (@font-size-base - 1); // 14px to 13px\n line-height: @line-height-base;\n word-break: break-all;\n word-wrap: break-word;\n color: @pre-color;\n background-color: @pre-bg;\n border: 1px solid @pre-border-color;\n border-radius: @border-radius-base;\n\n // Account for some code outputs that place code tags in pre tags\n code {\n padding: 0;\n font-size: inherit;\n color: inherit;\n white-space: pre-wrap;\n background-color: transparent;\n border-radius: 0;\n }\n}\n\n// Enable scrollable blocks of code\n.pre-scrollable {\n max-height: @pre-scrollable-max-height;\n overflow-y: scroll;\n}\n","//\n// Grid system\n// --------------------------------------------------\n\n\n// Container widths\n//\n// Set the container width, and override it for fixed navbars in media queries.\n\n.container {\n .container-fixed();\n\n @media (min-width: @screen-sm-min) {\n width: @container-sm;\n }\n @media (min-width: @screen-md-min) {\n width: @container-md;\n }\n @media (min-width: @screen-lg-min) {\n width: @container-lg;\n }\n}\n\n\n// Fluid container\n//\n// Utilizes the mixin meant for fixed width containers, but without any defined\n// width for fluid, full width layouts.\n\n.container-fluid {\n .container-fixed();\n}\n\n\n// Row\n//\n// Rows contain and clear the floats of your columns.\n\n.row {\n .make-row();\n}\n\n\n// Columns\n//\n// Common styles for small and large grid columns\n\n.make-grid-columns();\n\n\n// Extra small grid\n//\n// Columns, offsets, pushes, and pulls for extra small devices like\n// smartphones.\n\n.make-grid(xs);\n\n\n// Small grid\n//\n// Columns, offsets, pushes, and pulls for the small device range, from phones\n// to tablets.\n\n@media (min-width: @screen-sm-min) {\n .make-grid(sm);\n}\n\n\n// Medium grid\n//\n// Columns, offsets, pushes, and pulls for the desktop device range.\n\n@media (min-width: @screen-md-min) {\n .make-grid(md);\n}\n\n\n// Large grid\n//\n// Columns, offsets, pushes, and pulls for the large desktop device range.\n\n@media (min-width: @screen-lg-min) {\n .make-grid(lg);\n}\n","// Grid system\n//\n// Generate semantic grid columns with these mixins.\n\n// Centered container element\n.container-fixed(@gutter: @grid-gutter-width) {\n margin-right: auto;\n margin-left: auto;\n padding-left: floor((@gutter / 2));\n padding-right: ceil((@gutter / 2));\n &:extend(.clearfix all);\n}\n\n// Creates a wrapper for a series of columns\n.make-row(@gutter: @grid-gutter-width) {\n margin-left: ceil((@gutter / -2));\n margin-right: floor((@gutter / -2));\n &:extend(.clearfix all);\n}\n\n// Generate the extra small columns\n.make-xs-column(@columns; @gutter: @grid-gutter-width) {\n position: relative;\n float: left;\n width: percentage((@columns / @grid-columns));\n min-height: 1px;\n padding-left: (@gutter / 2);\n padding-right: (@gutter / 2);\n}\n.make-xs-column-offset(@columns) {\n margin-left: percentage((@columns / @grid-columns));\n}\n.make-xs-column-push(@columns) {\n left: percentage((@columns / @grid-columns));\n}\n.make-xs-column-pull(@columns) {\n right: percentage((@columns / @grid-columns));\n}\n\n// Generate the small columns\n.make-sm-column(@columns; @gutter: @grid-gutter-width) {\n position: relative;\n min-height: 1px;\n padding-left: (@gutter / 2);\n padding-right: (@gutter / 2);\n\n @media (min-width: @screen-sm-min) {\n float: left;\n width: percentage((@columns / @grid-columns));\n }\n}\n.make-sm-column-offset(@columns) {\n @media (min-width: @screen-sm-min) {\n margin-left: percentage((@columns / @grid-columns));\n }\n}\n.make-sm-column-push(@columns) {\n @media (min-width: @screen-sm-min) {\n left: percentage((@columns / @grid-columns));\n }\n}\n.make-sm-column-pull(@columns) {\n @media (min-width: @screen-sm-min) {\n right: percentage((@columns / @grid-columns));\n }\n}\n\n// Generate the medium columns\n.make-md-column(@columns; @gutter: @grid-gutter-width) {\n position: relative;\n min-height: 1px;\n padding-left: (@gutter / 2);\n padding-right: (@gutter / 2);\n\n @media (min-width: @screen-md-min) {\n float: left;\n width: percentage((@columns / @grid-columns));\n }\n}\n.make-md-column-offset(@columns) {\n @media (min-width: @screen-md-min) {\n margin-left: percentage((@columns / @grid-columns));\n }\n}\n.make-md-column-push(@columns) {\n @media (min-width: @screen-md-min) {\n left: percentage((@columns / @grid-columns));\n }\n}\n.make-md-column-pull(@columns) {\n @media (min-width: @screen-md-min) {\n right: percentage((@columns / @grid-columns));\n }\n}\n\n// Generate the large columns\n.make-lg-column(@columns; @gutter: @grid-gutter-width) {\n position: relative;\n min-height: 1px;\n padding-left: (@gutter / 2);\n padding-right: (@gutter / 2);\n\n @media (min-width: @screen-lg-min) {\n float: left;\n width: percentage((@columns / @grid-columns));\n }\n}\n.make-lg-column-offset(@columns) {\n @media (min-width: @screen-lg-min) {\n margin-left: percentage((@columns / @grid-columns));\n }\n}\n.make-lg-column-push(@columns) {\n @media (min-width: @screen-lg-min) {\n left: percentage((@columns / @grid-columns));\n }\n}\n.make-lg-column-pull(@columns) {\n @media (min-width: @screen-lg-min) {\n right: percentage((@columns / @grid-columns));\n }\n}\n","// Framework grid generation\n//\n// Used only by Bootstrap to generate the correct number of grid classes given\n// any value of `@grid-columns`.\n\n.make-grid-columns() {\n // Common styles for all sizes of grid columns, widths 1-12\n .col(@index) { // initial\n @item: ~\".col-xs-@{index}, .col-sm-@{index}, .col-md-@{index}, .col-lg-@{index}\";\n .col((@index + 1), @item);\n }\n .col(@index, @list) when (@index =< @grid-columns) { // general; \"=<\" isn't a typo\n @item: ~\".col-xs-@{index}, .col-sm-@{index}, .col-md-@{index}, .col-lg-@{index}\";\n .col((@index + 1), ~\"@{list}, @{item}\");\n }\n .col(@index, @list) when (@index > @grid-columns) { // terminal\n @{list} {\n position: relative;\n // Prevent columns from collapsing when empty\n min-height: 1px;\n // Inner gutter via padding\n padding-left: ceil((@grid-gutter-width / 2));\n padding-right: floor((@grid-gutter-width / 2));\n }\n }\n .col(1); // kickstart it\n}\n\n.float-grid-columns(@class) {\n .col(@index) { // initial\n @item: ~\".col-@{class}-@{index}\";\n .col((@index + 1), @item);\n }\n .col(@index, @list) when (@index =< @grid-columns) { // general\n @item: ~\".col-@{class}-@{index}\";\n .col((@index + 1), ~\"@{list}, @{item}\");\n }\n .col(@index, @list) when (@index > @grid-columns) { // terminal\n @{list} {\n float: left;\n }\n }\n .col(1); // kickstart it\n}\n\n.calc-grid-column(@index, @class, @type) when (@type = width) and (@index > 0) {\n .col-@{class}-@{index} {\n width: percentage((@index / @grid-columns));\n }\n}\n.calc-grid-column(@index, @class, @type) when (@type = push) and (@index > 0) {\n .col-@{class}-push-@{index} {\n left: percentage((@index / @grid-columns));\n }\n}\n.calc-grid-column(@index, @class, @type) when (@type = push) and (@index = 0) {\n .col-@{class}-push-0 {\n left: auto;\n }\n}\n.calc-grid-column(@index, @class, @type) when (@type = pull) and (@index > 0) {\n .col-@{class}-pull-@{index} {\n right: percentage((@index / @grid-columns));\n }\n}\n.calc-grid-column(@index, @class, @type) when (@type = pull) and (@index = 0) {\n .col-@{class}-pull-0 {\n right: auto;\n }\n}\n.calc-grid-column(@index, @class, @type) when (@type = offset) {\n .col-@{class}-offset-@{index} {\n margin-left: percentage((@index / @grid-columns));\n }\n}\n\n// Basic looping in LESS\n.loop-grid-columns(@index, @class, @type) when (@index >= 0) {\n .calc-grid-column(@index, @class, @type);\n // next iteration\n .loop-grid-columns((@index - 1), @class, @type);\n}\n\n// Create grid for specific class\n.make-grid(@class) {\n .float-grid-columns(@class);\n .loop-grid-columns(@grid-columns, @class, width);\n .loop-grid-columns(@grid-columns, @class, pull);\n .loop-grid-columns(@grid-columns, @class, push);\n .loop-grid-columns(@grid-columns, @class, offset);\n}\n","//\n// Tables\n// --------------------------------------------------\n\n\ntable {\n background-color: @table-bg;\n}\ncaption {\n padding-top: @table-cell-padding;\n padding-bottom: @table-cell-padding;\n color: @text-muted;\n text-align: left;\n}\nth {\n text-align: left;\n}\n\n\n// Baseline styles\n\n.table {\n width: 100%;\n max-width: 100%;\n margin-bottom: @line-height-computed;\n // Cells\n > thead,\n > tbody,\n > tfoot {\n > tr {\n > th,\n > td {\n padding: @table-cell-padding;\n line-height: @line-height-base;\n vertical-align: top;\n border-top: 1px solid @table-border-color;\n }\n }\n }\n // Bottom align for column headings\n > thead > tr > th {\n vertical-align: bottom;\n border-bottom: 2px solid @table-border-color;\n }\n // Remove top border from thead by default\n > caption + thead,\n > colgroup + thead,\n > thead:first-child {\n > tr:first-child {\n > th,\n > td {\n border-top: 0;\n }\n }\n }\n // Account for multiple tbody instances\n > tbody + tbody {\n border-top: 2px solid @table-border-color;\n }\n\n // Nesting\n .table {\n background-color: @body-bg;\n }\n}\n\n\n// Condensed table w/ half padding\n\n.table-condensed {\n > thead,\n > tbody,\n > tfoot {\n > tr {\n > th,\n > td {\n padding: @table-condensed-cell-padding;\n }\n }\n }\n}\n\n\n// Bordered version\n//\n// Add borders all around the table and between all the columns.\n\n.table-bordered {\n border: 1px solid @table-border-color;\n > thead,\n > tbody,\n > tfoot {\n > tr {\n > th,\n > td {\n border: 1px solid @table-border-color;\n }\n }\n }\n > thead > tr {\n > th,\n > td {\n border-bottom-width: 2px;\n }\n }\n}\n\n\n// Zebra-striping\n//\n// Default zebra-stripe styles (alternating gray and transparent backgrounds)\n\n.table-striped {\n > tbody > tr:nth-of-type(odd) {\n background-color: @table-bg-accent;\n }\n}\n\n\n// Hover effect\n//\n// Placed here since it has to come after the potential zebra striping\n\n.table-hover {\n > tbody > tr:hover {\n background-color: @table-bg-hover;\n }\n}\n\n\n// Table cell sizing\n//\n// Reset default table behavior\n\ntable col[class*=\"col-\"] {\n position: static; // Prevent border hiding in Firefox and IE9-11 (see https://github.com/twbs/bootstrap/issues/11623)\n float: none;\n display: table-column;\n}\ntable {\n td,\n th {\n &[class*=\"col-\"] {\n position: static; // Prevent border hiding in Firefox and IE9-11 (see https://github.com/twbs/bootstrap/issues/11623)\n float: none;\n display: table-cell;\n }\n }\n}\n\n\n// Table backgrounds\n//\n// Exact selectors below required to override `.table-striped` and prevent\n// inheritance to nested tables.\n\n// Generate the contextual variants\n.table-row-variant(active; @table-bg-active);\n.table-row-variant(success; @state-success-bg);\n.table-row-variant(info; @state-info-bg);\n.table-row-variant(warning; @state-warning-bg);\n.table-row-variant(danger; @state-danger-bg);\n\n\n// Responsive tables\n//\n// Wrap your tables in `.table-responsive` and we'll make them mobile friendly\n// by enabling horizontal scrolling. Only applies <768px. Everything above that\n// will display normally.\n\n.table-responsive {\n overflow-x: auto;\n min-height: 0.01%; // Workaround for IE9 bug (see https://github.com/twbs/bootstrap/issues/14837)\n\n @media screen and (max-width: @screen-xs-max) {\n width: 100%;\n margin-bottom: (@line-height-computed * 0.75);\n overflow-y: hidden;\n -ms-overflow-style: -ms-autohiding-scrollbar;\n border: 1px solid @table-border-color;\n\n // Tighten up spacing\n > .table {\n margin-bottom: 0;\n\n // Ensure the content doesn't wrap\n > thead,\n > tbody,\n > tfoot {\n > tr {\n > th,\n > td {\n white-space: nowrap;\n }\n }\n }\n }\n\n // Special overrides for the bordered tables\n > .table-bordered {\n border: 0;\n\n // Nuke the appropriate borders so that the parent can handle them\n > thead,\n > tbody,\n > tfoot {\n > tr {\n > th:first-child,\n > td:first-child {\n border-left: 0;\n }\n > th:last-child,\n > td:last-child {\n border-right: 0;\n }\n }\n }\n\n // Only nuke the last row's bottom-border in `tbody` and `tfoot` since\n // chances are there will be only one `tr` in a `thead` and that would\n // remove the border altogether.\n > tbody,\n > tfoot {\n > tr:last-child {\n > th,\n > td {\n border-bottom: 0;\n }\n }\n }\n\n }\n }\n}\n","// Tables\n\n.table-row-variant(@state; @background) {\n // Exact selectors below required to override `.table-striped` and prevent\n // inheritance to nested tables.\n .table > thead > tr,\n .table > tbody > tr,\n .table > tfoot > tr {\n > td.@{state},\n > th.@{state},\n &.@{state} > td,\n &.@{state} > th {\n background-color: @background;\n }\n }\n\n // Hover states for `.table-hover`\n // Note: this is not available for cells or rows within `thead` or `tfoot`.\n .table-hover > tbody > tr {\n > td.@{state}:hover,\n > th.@{state}:hover,\n &.@{state}:hover > td,\n &:hover > .@{state},\n &.@{state}:hover > th {\n background-color: darken(@background, 5%);\n }\n }\n}\n","//\n// Forms\n// --------------------------------------------------\n\n\n// Normalize non-controls\n//\n// Restyle and baseline non-control form elements.\n\nfieldset {\n padding: 0;\n margin: 0;\n border: 0;\n // Chrome and Firefox set a `min-width: min-content;` on fieldsets,\n // so we reset that to ensure it behaves more like a standard block element.\n // See https://github.com/twbs/bootstrap/issues/12359.\n min-width: 0;\n}\n\nlegend {\n display: block;\n width: 100%;\n padding: 0;\n margin-bottom: @line-height-computed;\n font-size: (@font-size-base * 1.5);\n line-height: inherit;\n color: @legend-color;\n border: 0;\n border-bottom: 1px solid @legend-border-color;\n}\n\nlabel {\n display: inline-block;\n max-width: 100%; // Force IE8 to wrap long content (see https://github.com/twbs/bootstrap/issues/13141)\n margin-bottom: 5px;\n font-weight: bold;\n}\n\n\n// Normalize form controls\n//\n// While most of our form styles require extra classes, some basic normalization\n// is required to ensure optimum display with or without those classes to better\n// address browser inconsistencies.\n\n// Override content-box in Normalize (* isn't specific enough)\ninput[type=\"search\"] {\n .box-sizing(border-box);\n}\n\n// Position radios and checkboxes better\ninput[type=\"radio\"],\ninput[type=\"checkbox\"] {\n margin: 4px 0 0;\n margin-top: 1px \\9; // IE8-9\n line-height: normal;\n}\n\ninput[type=\"file\"] {\n display: block;\n}\n\n// Make range inputs behave like textual form controls\ninput[type=\"range\"] {\n display: block;\n width: 100%;\n}\n\n// Make multiple select elements height not fixed\nselect[multiple],\nselect[size] {\n height: auto;\n}\n\n// Focus for file, radio, and checkbox\ninput[type=\"file\"]:focus,\ninput[type=\"radio\"]:focus,\ninput[type=\"checkbox\"]:focus {\n .tab-focus();\n}\n\n// Adjust output element\noutput {\n display: block;\n padding-top: (@padding-base-vertical + 1);\n font-size: @font-size-base;\n line-height: @line-height-base;\n color: @input-color;\n}\n\n\n// Common form controls\n//\n// Shared size and type resets for form controls. Apply `.form-control` to any\n// of the following form controls:\n//\n// select\n// textarea\n// input[type=\"text\"]\n// input[type=\"password\"]\n// input[type=\"datetime\"]\n// input[type=\"datetime-local\"]\n// input[type=\"date\"]\n// input[type=\"month\"]\n// input[type=\"time\"]\n// input[type=\"week\"]\n// input[type=\"number\"]\n// input[type=\"email\"]\n// input[type=\"url\"]\n// input[type=\"search\"]\n// input[type=\"tel\"]\n// input[type=\"color\"]\n\n.form-control {\n display: block;\n width: 100%;\n height: @input-height-base; // Make inputs at least the height of their button counterpart (base line-height + padding + border)\n padding: @padding-base-vertical @padding-base-horizontal;\n font-size: @font-size-base;\n line-height: @line-height-base;\n color: @input-color;\n background-color: @input-bg;\n background-image: none; // Reset unusual Firefox-on-Android default style; see https://github.com/necolas/normalize.css/issues/214\n border: 1px solid @input-border;\n border-radius: @input-border-radius; // Note: This has no effect on <select>s in some browsers, due to the limited stylability of <select>s in CSS.\n .box-shadow(inset 0 1px 1px rgba(0,0,0,.075));\n .transition(~\"border-color ease-in-out .15s, box-shadow ease-in-out .15s\");\n\n // Customize the `:focus` state to imitate native WebKit styles.\n .form-control-focus();\n\n // Placeholder\n .placeholder();\n\n // Unstyle the caret on `<select>`s in IE10+.\n &::-ms-expand {\n border: 0;\n background-color: transparent;\n }\n\n // Disabled and read-only inputs\n //\n // HTML5 says that controls under a fieldset > legend:first-child won't be\n // disabled if the fieldset is disabled. Due to implementation difficulty, we\n // don't honor that edge case; we style them as disabled anyway.\n &[disabled],\n &[readonly],\n fieldset[disabled] & {\n background-color: @input-bg-disabled;\n opacity: 1; // iOS fix for unreadable disabled content; see https://github.com/twbs/bootstrap/issues/11655\n }\n\n &[disabled],\n fieldset[disabled] & {\n cursor: @cursor-disabled;\n }\n\n // Reset height for `textarea`s\n textarea& {\n height: auto;\n }\n}\n\n\n// Search inputs in iOS\n//\n// This overrides the extra rounded corners on search inputs in iOS so that our\n// `.form-control` class can properly style them. Note that this cannot simply\n// be added to `.form-control` as it's not specific enough. For details, see\n// https://github.com/twbs/bootstrap/issues/11586.\n\ninput[type=\"search\"] {\n -webkit-appearance: none;\n}\n\n\n// Special styles for iOS temporal inputs\n//\n// In Mobile Safari, setting `display: block` on temporal inputs causes the\n// text within the input to become vertically misaligned. As a workaround, we\n// set a pixel line-height that matches the given height of the input, but only\n// for Safari. See https://bugs.webkit.org/show_bug.cgi?id=139848\n//\n// Note that as of 9.3, iOS doesn't support `week`.\n\n@media screen and (-webkit-min-device-pixel-ratio: 0) {\n input[type=\"date\"],\n input[type=\"time\"],\n input[type=\"datetime-local\"],\n input[type=\"month\"] {\n &.form-control {\n line-height: @input-height-base;\n }\n\n &.input-sm,\n .input-group-sm & {\n line-height: @input-height-small;\n }\n\n &.input-lg,\n .input-group-lg & {\n line-height: @input-height-large;\n }\n }\n}\n\n\n// Form groups\n//\n// Designed to help with the organization and spacing of vertical forms. For\n// horizontal forms, use the predefined grid classes.\n\n.form-group {\n margin-bottom: @form-group-margin-bottom;\n}\n\n\n// Checkboxes and radios\n//\n// Indent the labels to position radios/checkboxes as hanging controls.\n\n.radio,\n.checkbox {\n position: relative;\n display: block;\n margin-top: 10px;\n margin-bottom: 10px;\n\n label {\n min-height: @line-height-computed; // Ensure the input doesn't jump when there is no text\n padding-left: 20px;\n margin-bottom: 0;\n font-weight: normal;\n cursor: pointer;\n }\n}\n.radio input[type=\"radio\"],\n.radio-inline input[type=\"radio\"],\n.checkbox input[type=\"checkbox\"],\n.checkbox-inline input[type=\"checkbox\"] {\n position: absolute;\n margin-left: -20px;\n margin-top: 4px \\9;\n}\n\n.radio + .radio,\n.checkbox + .checkbox {\n margin-top: -5px; // Move up sibling radios or checkboxes for tighter spacing\n}\n\n// Radios and checkboxes on same line\n.radio-inline,\n.checkbox-inline {\n position: relative;\n display: inline-block;\n padding-left: 20px;\n margin-bottom: 0;\n vertical-align: middle;\n font-weight: normal;\n cursor: pointer;\n}\n.radio-inline + .radio-inline,\n.checkbox-inline + .checkbox-inline {\n margin-top: 0;\n margin-left: 10px; // space out consecutive inline controls\n}\n\n// Apply same disabled cursor tweak as for inputs\n// Some special care is needed because <label>s don't inherit their parent's `cursor`.\n//\n// Note: Neither radios nor checkboxes can be readonly.\ninput[type=\"radio\"],\ninput[type=\"checkbox\"] {\n &[disabled],\n &.disabled,\n fieldset[disabled] & {\n cursor: @cursor-disabled;\n }\n}\n// These classes are used directly on <label>s\n.radio-inline,\n.checkbox-inline {\n &.disabled,\n fieldset[disabled] & {\n cursor: @cursor-disabled;\n }\n}\n// These classes are used on elements with <label> descendants\n.radio,\n.checkbox {\n &.disabled,\n fieldset[disabled] & {\n label {\n cursor: @cursor-disabled;\n }\n }\n}\n\n\n// Static form control text\n//\n// Apply class to a `p` element to make any string of text align with labels in\n// a horizontal form layout.\n\n.form-control-static {\n // Size it appropriately next to real form controls\n padding-top: (@padding-base-vertical + 1);\n padding-bottom: (@padding-base-vertical + 1);\n // Remove default margin from `p`\n margin-bottom: 0;\n min-height: (@line-height-computed + @font-size-base);\n\n &.input-lg,\n &.input-sm {\n padding-left: 0;\n padding-right: 0;\n }\n}\n\n\n// Form control sizing\n//\n// Build on `.form-control` with modifier classes to decrease or increase the\n// height and font-size of form controls.\n//\n// The `.form-group-* form-control` variations are sadly duplicated to avoid the\n// issue documented in https://github.com/twbs/bootstrap/issues/15074.\n\n.input-sm {\n .input-size(@input-height-small; @padding-small-vertical; @padding-small-horizontal; @font-size-small; @line-height-small; @input-border-radius-small);\n}\n.form-group-sm {\n .form-control {\n height: @input-height-small;\n padding: @padding-small-vertical @padding-small-horizontal;\n font-size: @font-size-small;\n line-height: @line-height-small;\n border-radius: @input-border-radius-small;\n }\n select.form-control {\n height: @input-height-small;\n line-height: @input-height-small;\n }\n textarea.form-control,\n select[multiple].form-control {\n height: auto;\n }\n .form-control-static {\n height: @input-height-small;\n min-height: (@line-height-computed + @font-size-small);\n padding: (@padding-small-vertical + 1) @padding-small-horizontal;\n font-size: @font-size-small;\n line-height: @line-height-small;\n }\n}\n\n.input-lg {\n .input-size(@input-height-large; @padding-large-vertical; @padding-large-horizontal; @font-size-large; @line-height-large; @input-border-radius-large);\n}\n.form-group-lg {\n .form-control {\n height: @input-height-large;\n padding: @padding-large-vertical @padding-large-horizontal;\n font-size: @font-size-large;\n line-height: @line-height-large;\n border-radius: @input-border-radius-large;\n }\n select.form-control {\n height: @input-height-large;\n line-height: @input-height-large;\n }\n textarea.form-control,\n select[multiple].form-control {\n height: auto;\n }\n .form-control-static {\n height: @input-height-large;\n min-height: (@line-height-computed + @font-size-large);\n padding: (@padding-large-vertical + 1) @padding-large-horizontal;\n font-size: @font-size-large;\n line-height: @line-height-large;\n }\n}\n\n\n// Form control feedback states\n//\n// Apply contextual and semantic states to individual form controls.\n\n.has-feedback {\n // Enable absolute positioning\n position: relative;\n\n // Ensure icons don't overlap text\n .form-control {\n padding-right: (@input-height-base * 1.25);\n }\n}\n// Feedback icon (requires .glyphicon classes)\n.form-control-feedback {\n position: absolute;\n top: 0;\n right: 0;\n z-index: 2; // Ensure icon is above input groups\n display: block;\n width: @input-height-base;\n height: @input-height-base;\n line-height: @input-height-base;\n text-align: center;\n pointer-events: none;\n}\n.input-lg + .form-control-feedback,\n.input-group-lg + .form-control-feedback,\n.form-group-lg .form-control + .form-control-feedback {\n width: @input-height-large;\n height: @input-height-large;\n line-height: @input-height-large;\n}\n.input-sm + .form-control-feedback,\n.input-group-sm + .form-control-feedback,\n.form-group-sm .form-control + .form-control-feedback {\n width: @input-height-small;\n height: @input-height-small;\n line-height: @input-height-small;\n}\n\n// Feedback states\n.has-success {\n .form-control-validation(@state-success-text; @state-success-text; @state-success-bg);\n}\n.has-warning {\n .form-control-validation(@state-warning-text; @state-warning-text; @state-warning-bg);\n}\n.has-error {\n .form-control-validation(@state-danger-text; @state-danger-text; @state-danger-bg);\n}\n\n// Reposition feedback icon if input has visible label above\n.has-feedback label {\n\n & ~ .form-control-feedback {\n top: (@line-height-computed + 5); // Height of the `label` and its margin\n }\n &.sr-only ~ .form-control-feedback {\n top: 0;\n }\n}\n\n\n// Help text\n//\n// Apply to any element you wish to create light text for placement immediately\n// below a form control. Use for general help, formatting, or instructional text.\n\n.help-block {\n display: block; // account for any element using help-block\n margin-top: 5px;\n margin-bottom: 10px;\n color: lighten(@text-color, 25%); // lighten the text some for contrast\n}\n\n\n// Inline forms\n//\n// Make forms appear inline(-block) by adding the `.form-inline` class. Inline\n// forms begin stacked on extra small (mobile) devices and then go inline when\n// viewports reach <768px.\n//\n// Requires wrapping inputs and labels with `.form-group` for proper display of\n// default HTML form controls and our custom form controls (e.g., input groups).\n//\n// Heads up! This is mixin-ed into `.navbar-form` in navbars.less.\n\n.form-inline {\n\n // Kick in the inline\n @media (min-width: @screen-sm-min) {\n // Inline-block all the things for \"inline\"\n .form-group {\n display: inline-block;\n margin-bottom: 0;\n vertical-align: middle;\n }\n\n // In navbar-form, allow folks to *not* use `.form-group`\n .form-control {\n display: inline-block;\n width: auto; // Prevent labels from stacking above inputs in `.form-group`\n vertical-align: middle;\n }\n\n // Make static controls behave like regular ones\n .form-control-static {\n display: inline-block;\n }\n\n .input-group {\n display: inline-table;\n vertical-align: middle;\n\n .input-group-addon,\n .input-group-btn,\n .form-control {\n width: auto;\n }\n }\n\n // Input groups need that 100% width though\n .input-group > .form-control {\n width: 100%;\n }\n\n .control-label {\n margin-bottom: 0;\n vertical-align: middle;\n }\n\n // Remove default margin on radios/checkboxes that were used for stacking, and\n // then undo the floating of radios and checkboxes to match.\n .radio,\n .checkbox {\n display: inline-block;\n margin-top: 0;\n margin-bottom: 0;\n vertical-align: middle;\n\n label {\n padding-left: 0;\n }\n }\n .radio input[type=\"radio\"],\n .checkbox input[type=\"checkbox\"] {\n position: relative;\n margin-left: 0;\n }\n\n // Re-override the feedback icon.\n .has-feedback .form-control-feedback {\n top: 0;\n }\n }\n}\n\n\n// Horizontal forms\n//\n// Horizontal forms are built on grid classes and allow you to create forms with\n// labels on the left and inputs on the right.\n\n.form-horizontal {\n\n // Consistent vertical alignment of radios and checkboxes\n //\n // Labels also get some reset styles, but that is scoped to a media query below.\n .radio,\n .checkbox,\n .radio-inline,\n .checkbox-inline {\n margin-top: 0;\n margin-bottom: 0;\n padding-top: (@padding-base-vertical + 1); // Default padding plus a border\n }\n // Account for padding we're adding to ensure the alignment and of help text\n // and other content below items\n .radio,\n .checkbox {\n min-height: (@line-height-computed + (@padding-base-vertical + 1));\n }\n\n // Make form groups behave like rows\n .form-group {\n .make-row();\n }\n\n // Reset spacing and right align labels, but scope to media queries so that\n // labels on narrow viewports stack the same as a default form example.\n @media (min-width: @screen-sm-min) {\n .control-label {\n text-align: right;\n margin-bottom: 0;\n padding-top: (@padding-base-vertical + 1); // Default padding plus a border\n }\n }\n\n // Validation states\n //\n // Reposition the icon because it's now within a grid column and columns have\n // `position: relative;` on them. Also accounts for the grid gutter padding.\n .has-feedback .form-control-feedback {\n right: floor((@grid-gutter-width / 2));\n }\n\n // Form group sizes\n //\n // Quick utility class for applying `.input-lg` and `.input-sm` styles to the\n // inputs and labels within a `.form-group`.\n .form-group-lg {\n @media (min-width: @screen-sm-min) {\n .control-label {\n padding-top: (@padding-large-vertical + 1);\n font-size: @font-size-large;\n }\n }\n }\n .form-group-sm {\n @media (min-width: @screen-sm-min) {\n .control-label {\n padding-top: (@padding-small-vertical + 1);\n font-size: @font-size-small;\n }\n }\n }\n}\n","// Form validation states\n//\n// Used in forms.less to generate the form validation CSS for warnings, errors,\n// and successes.\n\n.form-control-validation(@text-color: #555; @border-color: #ccc; @background-color: #f5f5f5) {\n // Color the label and help text\n .help-block,\n .control-label,\n .radio,\n .checkbox,\n .radio-inline,\n .checkbox-inline,\n &.radio label,\n &.checkbox label,\n &.radio-inline label,\n &.checkbox-inline label {\n color: @text-color;\n }\n // Set the border and box shadow on specific inputs to match\n .form-control {\n border-color: @border-color;\n .box-shadow(inset 0 1px 1px rgba(0,0,0,.075)); // Redeclare so transitions work\n &:focus {\n border-color: darken(@border-color, 10%);\n @shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 6px lighten(@border-color, 20%);\n .box-shadow(@shadow);\n }\n }\n // Set validation states also for addons\n .input-group-addon {\n color: @text-color;\n border-color: @border-color;\n background-color: @background-color;\n }\n // Optional feedback icon\n .form-control-feedback {\n color: @text-color;\n }\n}\n\n\n// Form control focus state\n//\n// Generate a customized focus state and for any input with the specified color,\n// which defaults to the `@input-border-focus` variable.\n//\n// We highly encourage you to not customize the default value, but instead use\n// this to tweak colors on an as-needed basis. This aesthetic change is based on\n// WebKit's default styles, but applicable to a wider range of browsers. Its\n// usability and accessibility should be taken into account with any change.\n//\n// Example usage: change the default blue border and shadow to white for better\n// contrast against a dark gray background.\n.form-control-focus(@color: @input-border-focus) {\n @color-rgba: rgba(red(@color), green(@color), blue(@color), .6);\n &:focus {\n border-color: @color;\n outline: 0;\n .box-shadow(~\"inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px @{color-rgba}\");\n }\n}\n\n// Form control sizing\n//\n// Relative text size, padding, and border-radii changes for form controls. For\n// horizontal sizing, wrap controls in the predefined grid classes. `<select>`\n// element gets special love because it's special, and that's a fact!\n.input-size(@input-height; @padding-vertical; @padding-horizontal; @font-size; @line-height; @border-radius) {\n height: @input-height;\n padding: @padding-vertical @padding-horizontal;\n font-size: @font-size;\n line-height: @line-height;\n border-radius: @border-radius;\n\n select& {\n height: @input-height;\n line-height: @input-height;\n }\n\n textarea&,\n select[multiple]& {\n height: auto;\n }\n}\n","//\n// Buttons\n// --------------------------------------------------\n\n\n// Base styles\n// --------------------------------------------------\n\n.btn {\n display: inline-block;\n margin-bottom: 0; // For input.btn\n font-weight: @btn-font-weight;\n text-align: center;\n vertical-align: middle;\n touch-action: manipulation;\n cursor: pointer;\n background-image: none; // Reset unusual Firefox-on-Android default style; see https://github.com/necolas/normalize.css/issues/214\n border: 1px solid transparent;\n white-space: nowrap;\n .button-size(@padding-base-vertical; @padding-base-horizontal; @font-size-base; @line-height-base; @btn-border-radius-base);\n .user-select(none);\n\n &,\n &:active,\n &.active {\n &:focus,\n &.focus {\n .tab-focus();\n }\n }\n\n &:hover,\n &:focus,\n &.focus {\n color: @btn-default-color;\n text-decoration: none;\n }\n\n &:active,\n &.active {\n outline: 0;\n background-image: none;\n .box-shadow(inset 0 3px 5px rgba(0,0,0,.125));\n }\n\n &.disabled,\n &[disabled],\n fieldset[disabled] & {\n cursor: @cursor-disabled;\n .opacity(.65);\n .box-shadow(none);\n }\n\n a& {\n &.disabled,\n fieldset[disabled] & {\n pointer-events: none; // Future-proof disabling of clicks on `<a>` elements\n }\n }\n}\n\n\n// Alternate buttons\n// --------------------------------------------------\n\n.btn-default {\n .button-variant(@btn-default-color; @btn-default-bg; @btn-default-border);\n}\n.btn-primary {\n .button-variant(@btn-primary-color; @btn-primary-bg; @btn-primary-border);\n}\n// Success appears as green\n.btn-success {\n .button-variant(@btn-success-color; @btn-success-bg; @btn-success-border);\n}\n// Info appears as blue-green\n.btn-info {\n .button-variant(@btn-info-color; @btn-info-bg; @btn-info-border);\n}\n// Warning appears as orange\n.btn-warning {\n .button-variant(@btn-warning-color; @btn-warning-bg; @btn-warning-border);\n}\n// Danger and error appear as red\n.btn-danger {\n .button-variant(@btn-danger-color; @btn-danger-bg; @btn-danger-border);\n}\n\n\n// Link buttons\n// -------------------------\n\n// Make a button look and behave like a link\n.btn-link {\n color: @link-color;\n font-weight: normal;\n border-radius: 0;\n\n &,\n &:active,\n &.active,\n &[disabled],\n fieldset[disabled] & {\n background-color: transparent;\n .box-shadow(none);\n }\n &,\n &:hover,\n &:focus,\n &:active {\n border-color: transparent;\n }\n &:hover,\n &:focus {\n color: @link-hover-color;\n text-decoration: @link-hover-decoration;\n background-color: transparent;\n }\n &[disabled],\n fieldset[disabled] & {\n &:hover,\n &:focus {\n color: @btn-link-disabled-color;\n text-decoration: none;\n }\n }\n}\n\n\n// Button Sizes\n// --------------------------------------------------\n\n.btn-lg {\n // line-height: ensure even-numbered height of button next to large input\n .button-size(@padding-large-vertical; @padding-large-horizontal; @font-size-large; @line-height-large; @btn-border-radius-large);\n}\n.btn-sm {\n // line-height: ensure proper height of button next to small input\n .button-size(@padding-small-vertical; @padding-small-horizontal; @font-size-small; @line-height-small; @btn-border-radius-small);\n}\n.btn-xs {\n .button-size(@padding-xs-vertical; @padding-xs-horizontal; @font-size-small; @line-height-small; @btn-border-radius-small);\n}\n\n\n// Block button\n// --------------------------------------------------\n\n.btn-block {\n display: block;\n width: 100%;\n}\n\n// Vertically space out multiple block buttons\n.btn-block + .btn-block {\n margin-top: 5px;\n}\n\n// Specificity overrides\ninput[type=\"submit\"],\ninput[type=\"reset\"],\ninput[type=\"button\"] {\n &.btn-block {\n width: 100%;\n }\n}\n","// Button variants\n//\n// Easily pump out default styles, as well as :hover, :focus, :active,\n// and disabled options for all buttons\n\n.button-variant(@color; @background; @border) {\n color: @color;\n background-color: @background;\n border-color: @border;\n\n &:focus,\n &.focus {\n color: @color;\n background-color: darken(@background, 10%);\n border-color: darken(@border, 25%);\n }\n &:hover {\n color: @color;\n background-color: darken(@background, 10%);\n border-color: darken(@border, 12%);\n }\n &:active,\n &.active,\n .open > .dropdown-toggle& {\n color: @color;\n background-color: darken(@background, 10%);\n border-color: darken(@border, 12%);\n\n &:hover,\n &:focus,\n &.focus {\n color: @color;\n background-color: darken(@background, 17%);\n border-color: darken(@border, 25%);\n }\n }\n &:active,\n &.active,\n .open > .dropdown-toggle& {\n background-image: none;\n }\n &.disabled,\n &[disabled],\n fieldset[disabled] & {\n &:hover,\n &:focus,\n &.focus {\n background-color: @background;\n border-color: @border;\n }\n }\n\n .badge {\n color: @background;\n background-color: @color;\n }\n}\n\n// Button sizes\n.button-size(@padding-vertical; @padding-horizontal; @font-size; @line-height; @border-radius) {\n padding: @padding-vertical @padding-horizontal;\n font-size: @font-size;\n line-height: @line-height;\n border-radius: @border-radius;\n}\n","// Opacity\n\n.opacity(@opacity) {\n opacity: @opacity;\n // IE8 filter\n @opacity-ie: (@opacity * 100);\n filter: ~\"alpha(opacity=@{opacity-ie})\";\n}\n","//\n// Component animations\n// --------------------------------------------------\n\n// Heads up!\n//\n// We don't use the `.opacity()` mixin here since it causes a bug with text\n// fields in IE7-8. Source: https://github.com/twbs/bootstrap/pull/3552.\n\n.fade {\n opacity: 0;\n .transition(opacity .15s linear);\n &.in {\n opacity: 1;\n }\n}\n\n.collapse {\n display: none;\n\n &.in { display: block; }\n tr&.in { display: table-row; }\n tbody&.in { display: table-row-group; }\n}\n\n.collapsing {\n position: relative;\n height: 0;\n overflow: hidden;\n .transition-property(~\"height, visibility\");\n .transition-duration(.35s);\n .transition-timing-function(ease);\n}\n","//\n// Dropdown menus\n// --------------------------------------------------\n\n\n// Dropdown arrow/caret\n.caret {\n display: inline-block;\n width: 0;\n height: 0;\n margin-left: 2px;\n vertical-align: middle;\n border-top: @caret-width-base dashed;\n border-top: @caret-width-base solid ~\"\\9\"; // IE8\n border-right: @caret-width-base solid transparent;\n border-left: @caret-width-base solid transparent;\n}\n\n// The dropdown wrapper (div)\n.dropup,\n.dropdown {\n position: relative;\n}\n\n// Prevent the focus on the dropdown toggle when closing dropdowns\n.dropdown-toggle:focus {\n outline: 0;\n}\n\n// The dropdown menu (ul)\n.dropdown-menu {\n position: absolute;\n top: 100%;\n left: 0;\n z-index: @zindex-dropdown;\n display: none; // none by default, but block on \"open\" of the menu\n float: left;\n min-width: 160px;\n padding: 5px 0;\n margin: 2px 0 0; // override default ul\n list-style: none;\n font-size: @font-size-base;\n text-align: left; // Ensures proper alignment if parent has it changed (e.g., modal footer)\n background-color: @dropdown-bg;\n border: 1px solid @dropdown-fallback-border; // IE8 fallback\n border: 1px solid @dropdown-border;\n border-radius: @border-radius-base;\n .box-shadow(0 6px 12px rgba(0,0,0,.175));\n background-clip: padding-box;\n\n // Aligns the dropdown menu to right\n //\n // Deprecated as of 3.1.0 in favor of `.dropdown-menu-[dir]`\n &.pull-right {\n right: 0;\n left: auto;\n }\n\n // Dividers (basically an hr) within the dropdown\n .divider {\n .nav-divider(@dropdown-divider-bg);\n }\n\n // Links within the dropdown menu\n > li > a {\n display: block;\n padding: 3px 20px;\n clear: both;\n font-weight: normal;\n line-height: @line-height-base;\n color: @dropdown-link-color;\n white-space: nowrap; // prevent links from randomly breaking onto new lines\n }\n}\n\n// Hover/Focus state\n.dropdown-menu > li > a {\n &:hover,\n &:focus {\n text-decoration: none;\n color: @dropdown-link-hover-color;\n background-color: @dropdown-link-hover-bg;\n }\n}\n\n// Active state\n.dropdown-menu > .active > a {\n &,\n &:hover,\n &:focus {\n color: @dropdown-link-active-color;\n text-decoration: none;\n outline: 0;\n background-color: @dropdown-link-active-bg;\n }\n}\n\n// Disabled state\n//\n// Gray out text and ensure the hover/focus state remains gray\n\n.dropdown-menu > .disabled > a {\n &,\n &:hover,\n &:focus {\n color: @dropdown-link-disabled-color;\n }\n\n // Nuke hover/focus effects\n &:hover,\n &:focus {\n text-decoration: none;\n background-color: transparent;\n background-image: none; // Remove CSS gradient\n .reset-filter();\n cursor: @cursor-disabled;\n }\n}\n\n// Open state for the dropdown\n.open {\n // Show the menu\n > .dropdown-menu {\n display: block;\n }\n\n // Remove the outline when :focus is triggered\n > a {\n outline: 0;\n }\n}\n\n// Menu positioning\n//\n// Add extra class to `.dropdown-menu` to flip the alignment of the dropdown\n// menu with the parent.\n.dropdown-menu-right {\n left: auto; // Reset the default from `.dropdown-menu`\n right: 0;\n}\n// With v3, we enabled auto-flipping if you have a dropdown within a right\n// aligned nav component. To enable the undoing of that, we provide an override\n// to restore the default dropdown menu alignment.\n//\n// This is only for left-aligning a dropdown menu within a `.navbar-right` or\n// `.pull-right` nav component.\n.dropdown-menu-left {\n left: 0;\n right: auto;\n}\n\n// Dropdown section headers\n.dropdown-header {\n display: block;\n padding: 3px 20px;\n font-size: @font-size-small;\n line-height: @line-height-base;\n color: @dropdown-header-color;\n white-space: nowrap; // as with > li > a\n}\n\n// Backdrop to catch body clicks on mobile, etc.\n.dropdown-backdrop {\n position: fixed;\n left: 0;\n right: 0;\n bottom: 0;\n top: 0;\n z-index: (@zindex-dropdown - 10);\n}\n\n// Right aligned dropdowns\n.pull-right > .dropdown-menu {\n right: 0;\n left: auto;\n}\n\n// Allow for dropdowns to go bottom up (aka, dropup-menu)\n//\n// Just add .dropup after the standard .dropdown class and you're set, bro.\n// TODO: abstract this so that the navbar fixed styles are not placed here?\n\n.dropup,\n.navbar-fixed-bottom .dropdown {\n // Reverse the caret\n .caret {\n border-top: 0;\n border-bottom: @caret-width-base dashed;\n border-bottom: @caret-width-base solid ~\"\\9\"; // IE8\n content: \"\";\n }\n // Different positioning for bottom up menu\n .dropdown-menu {\n top: auto;\n bottom: 100%;\n margin-bottom: 2px;\n }\n}\n\n\n// Component alignment\n//\n// Reiterate per navbar.less and the modified component alignment there.\n\n@media (min-width: @grid-float-breakpoint) {\n .navbar-right {\n .dropdown-menu {\n .dropdown-menu-right();\n }\n // Necessary for overrides of the default right aligned menu.\n // Will remove come v4 in all likelihood.\n .dropdown-menu-left {\n .dropdown-menu-left();\n }\n }\n}\n","// Horizontal dividers\n//\n// Dividers (basically an hr) within dropdowns and nav lists\n\n.nav-divider(@color: #e5e5e5) {\n height: 1px;\n margin: ((@line-height-computed / 2) - 1) 0;\n overflow: hidden;\n background-color: @color;\n}\n","// Reset filters for IE\n//\n// When you need to remove a gradient background, do not forget to use this to reset\n// the IE filter for IE9 and below.\n\n.reset-filter() {\n filter: e(%(\"progid:DXImageTransform.Microsoft.gradient(enabled = false)\"));\n}\n","//\n// Button groups\n// --------------------------------------------------\n\n// Make the div behave like a button\n.btn-group,\n.btn-group-vertical {\n position: relative;\n display: inline-block;\n vertical-align: middle; // match .btn alignment given font-size hack above\n > .btn {\n position: relative;\n float: left;\n // Bring the \"active\" button to the front\n &:hover,\n &:focus,\n &:active,\n &.active {\n z-index: 2;\n }\n }\n}\n\n// Prevent double borders when buttons are next to each other\n.btn-group {\n .btn + .btn,\n .btn + .btn-group,\n .btn-group + .btn,\n .btn-group + .btn-group {\n margin-left: -1px;\n }\n}\n\n// Optional: Group multiple button groups together for a toolbar\n.btn-toolbar {\n margin-left: -5px; // Offset the first child's margin\n &:extend(.clearfix all);\n\n .btn,\n .btn-group,\n .input-group {\n float: left;\n }\n > .btn,\n > .btn-group,\n > .input-group {\n margin-left: 5px;\n }\n}\n\n.btn-group > .btn:not(:first-child):not(:last-child):not(.dropdown-toggle) {\n border-radius: 0;\n}\n\n// Set corners individual because sometimes a single button can be in a .btn-group and we need :first-child and :last-child to both match\n.btn-group > .btn:first-child {\n margin-left: 0;\n &:not(:last-child):not(.dropdown-toggle) {\n .border-right-radius(0);\n }\n}\n// Need .dropdown-toggle since :last-child doesn't apply, given that a .dropdown-menu is used immediately after it\n.btn-group > .btn:last-child:not(:first-child),\n.btn-group > .dropdown-toggle:not(:first-child) {\n .border-left-radius(0);\n}\n\n// Custom edits for including btn-groups within btn-groups (useful for including dropdown buttons within a btn-group)\n.btn-group > .btn-group {\n float: left;\n}\n.btn-group > .btn-group:not(:first-child):not(:last-child) > .btn {\n border-radius: 0;\n}\n.btn-group > .btn-group:first-child:not(:last-child) {\n > .btn:last-child,\n > .dropdown-toggle {\n .border-right-radius(0);\n }\n}\n.btn-group > .btn-group:last-child:not(:first-child) > .btn:first-child {\n .border-left-radius(0);\n}\n\n// On active and open, don't show outline\n.btn-group .dropdown-toggle:active,\n.btn-group.open .dropdown-toggle {\n outline: 0;\n}\n\n\n// Sizing\n//\n// Remix the default button sizing classes into new ones for easier manipulation.\n\n.btn-group-xs > .btn { &:extend(.btn-xs); }\n.btn-group-sm > .btn { &:extend(.btn-sm); }\n.btn-group-lg > .btn { &:extend(.btn-lg); }\n\n\n// Split button dropdowns\n// ----------------------\n\n// Give the line between buttons some depth\n.btn-group > .btn + .dropdown-toggle {\n padding-left: 8px;\n padding-right: 8px;\n}\n.btn-group > .btn-lg + .dropdown-toggle {\n padding-left: 12px;\n padding-right: 12px;\n}\n\n// The clickable button for toggling the menu\n// Remove the gradient and set the same inset shadow as the :active state\n.btn-group.open .dropdown-toggle {\n .box-shadow(inset 0 3px 5px rgba(0,0,0,.125));\n\n // Show no shadow for `.btn-link` since it has no other button styles.\n &.btn-link {\n .box-shadow(none);\n }\n}\n\n\n// Reposition the caret\n.btn .caret {\n margin-left: 0;\n}\n// Carets in other button sizes\n.btn-lg .caret {\n border-width: @caret-width-large @caret-width-large 0;\n border-bottom-width: 0;\n}\n// Upside down carets for .dropup\n.dropup .btn-lg .caret {\n border-width: 0 @caret-width-large @caret-width-large;\n}\n\n\n// Vertical button groups\n// ----------------------\n\n.btn-group-vertical {\n > .btn,\n > .btn-group,\n > .btn-group > .btn {\n display: block;\n float: none;\n width: 100%;\n max-width: 100%;\n }\n\n // Clear floats so dropdown menus can be properly placed\n > .btn-group {\n &:extend(.clearfix all);\n > .btn {\n float: none;\n }\n }\n\n > .btn + .btn,\n > .btn + .btn-group,\n > .btn-group + .btn,\n > .btn-group + .btn-group {\n margin-top: -1px;\n margin-left: 0;\n }\n}\n\n.btn-group-vertical > .btn {\n &:not(:first-child):not(:last-child) {\n border-radius: 0;\n }\n &:first-child:not(:last-child) {\n .border-top-radius(@btn-border-radius-base);\n .border-bottom-radius(0);\n }\n &:last-child:not(:first-child) {\n .border-top-radius(0);\n .border-bottom-radius(@btn-border-radius-base);\n }\n}\n.btn-group-vertical > .btn-group:not(:first-child):not(:last-child) > .btn {\n border-radius: 0;\n}\n.btn-group-vertical > .btn-group:first-child:not(:last-child) {\n > .btn:last-child,\n > .dropdown-toggle {\n .border-bottom-radius(0);\n }\n}\n.btn-group-vertical > .btn-group:last-child:not(:first-child) > .btn:first-child {\n .border-top-radius(0);\n}\n\n\n// Justified button groups\n// ----------------------\n\n.btn-group-justified {\n display: table;\n width: 100%;\n table-layout: fixed;\n border-collapse: separate;\n > .btn,\n > .btn-group {\n float: none;\n display: table-cell;\n width: 1%;\n }\n > .btn-group .btn {\n width: 100%;\n }\n\n > .btn-group .dropdown-menu {\n left: auto;\n }\n}\n\n\n// Checkbox and radio options\n//\n// In order to support the browser's form validation feedback, powered by the\n// `required` attribute, we have to \"hide\" the inputs via `clip`. We cannot use\n// `display: none;` or `visibility: hidden;` as that also hides the popover.\n// Simply visually hiding the inputs via `opacity` would leave them clickable in\n// certain cases which is prevented by using `clip` and `pointer-events`.\n// This way, we ensure a DOM element is visible to position the popover from.\n//\n// See https://github.com/twbs/bootstrap/pull/12794 and\n// https://github.com/twbs/bootstrap/pull/14559 for more information.\n\n[data-toggle=\"buttons\"] {\n > .btn,\n > .btn-group > .btn {\n input[type=\"radio\"],\n input[type=\"checkbox\"] {\n position: absolute;\n clip: rect(0,0,0,0);\n pointer-events: none;\n }\n }\n}\n","// Single side border-radius\n\n.border-top-radius(@radius) {\n border-top-right-radius: @radius;\n border-top-left-radius: @radius;\n}\n.border-right-radius(@radius) {\n border-bottom-right-radius: @radius;\n border-top-right-radius: @radius;\n}\n.border-bottom-radius(@radius) {\n border-bottom-right-radius: @radius;\n border-bottom-left-radius: @radius;\n}\n.border-left-radius(@radius) {\n border-bottom-left-radius: @radius;\n border-top-left-radius: @radius;\n}\n","//\n// Input groups\n// --------------------------------------------------\n\n// Base styles\n// -------------------------\n.input-group {\n position: relative; // For dropdowns\n display: table;\n border-collapse: separate; // prevent input groups from inheriting border styles from table cells when placed within a table\n\n // Undo padding and float of grid classes\n &[class*=\"col-\"] {\n float: none;\n padding-left: 0;\n padding-right: 0;\n }\n\n .form-control {\n // Ensure that the input is always above the *appended* addon button for\n // proper border colors.\n position: relative;\n z-index: 2;\n\n // IE9 fubars the placeholder attribute in text inputs and the arrows on\n // select elements in input groups. To fix it, we float the input. Details:\n // https://github.com/twbs/bootstrap/issues/11561#issuecomment-28936855\n float: left;\n\n width: 100%;\n margin-bottom: 0;\n\n &:focus {\n z-index: 3;\n }\n }\n}\n\n// Sizing options\n//\n// Remix the default form control sizing classes into new ones for easier\n// manipulation.\n\n.input-group-lg > .form-control,\n.input-group-lg > .input-group-addon,\n.input-group-lg > .input-group-btn > .btn {\n .input-lg();\n}\n.input-group-sm > .form-control,\n.input-group-sm > .input-group-addon,\n.input-group-sm > .input-group-btn > .btn {\n .input-sm();\n}\n\n\n// Display as table-cell\n// -------------------------\n.input-group-addon,\n.input-group-btn,\n.input-group .form-control {\n display: table-cell;\n\n &:not(:first-child):not(:last-child) {\n border-radius: 0;\n }\n}\n// Addon and addon wrapper for buttons\n.input-group-addon,\n.input-group-btn {\n width: 1%;\n white-space: nowrap;\n vertical-align: middle; // Match the inputs\n}\n\n// Text input groups\n// -------------------------\n.input-group-addon {\n padding: @padding-base-vertical @padding-base-horizontal;\n font-size: @font-size-base;\n font-weight: normal;\n line-height: 1;\n color: @input-color;\n text-align: center;\n background-color: @input-group-addon-bg;\n border: 1px solid @input-group-addon-border-color;\n border-radius: @input-border-radius;\n\n // Sizing\n &.input-sm {\n padding: @padding-small-vertical @padding-small-horizontal;\n font-size: @font-size-small;\n border-radius: @input-border-radius-small;\n }\n &.input-lg {\n padding: @padding-large-vertical @padding-large-horizontal;\n font-size: @font-size-large;\n border-radius: @input-border-radius-large;\n }\n\n // Nuke default margins from checkboxes and radios to vertically center within.\n input[type=\"radio\"],\n input[type=\"checkbox\"] {\n margin-top: 0;\n }\n}\n\n// Reset rounded corners\n.input-group .form-control:first-child,\n.input-group-addon:first-child,\n.input-group-btn:first-child > .btn,\n.input-group-btn:first-child > .btn-group > .btn,\n.input-group-btn:first-child > .dropdown-toggle,\n.input-group-btn:last-child > .btn:not(:last-child):not(.dropdown-toggle),\n.input-group-btn:last-child > .btn-group:not(:last-child) > .btn {\n .border-right-radius(0);\n}\n.input-group-addon:first-child {\n border-right: 0;\n}\n.input-group .form-control:last-child,\n.input-group-addon:last-child,\n.input-group-btn:last-child > .btn,\n.input-group-btn:last-child > .btn-group > .btn,\n.input-group-btn:last-child > .dropdown-toggle,\n.input-group-btn:first-child > .btn:not(:first-child),\n.input-group-btn:first-child > .btn-group:not(:first-child) > .btn {\n .border-left-radius(0);\n}\n.input-group-addon:last-child {\n border-left: 0;\n}\n\n// Button input groups\n// -------------------------\n.input-group-btn {\n position: relative;\n // Jankily prevent input button groups from wrapping with `white-space` and\n // `font-size` in combination with `inline-block` on buttons.\n font-size: 0;\n white-space: nowrap;\n\n // Negative margin for spacing, position for bringing hovered/focused/actived\n // element above the siblings.\n > .btn {\n position: relative;\n + .btn {\n margin-left: -1px;\n }\n // Bring the \"active\" button to the front\n &:hover,\n &:focus,\n &:active {\n z-index: 2;\n }\n }\n\n // Negative margin to only have a 1px border between the two\n &:first-child {\n > .btn,\n > .btn-group {\n margin-right: -1px;\n }\n }\n &:last-child {\n > .btn,\n > .btn-group {\n z-index: 2;\n margin-left: -1px;\n }\n }\n}\n","//\n// Navs\n// --------------------------------------------------\n\n\n// Base class\n// --------------------------------------------------\n\n.nav {\n margin-bottom: 0;\n padding-left: 0; // Override default ul/ol\n list-style: none;\n &:extend(.clearfix all);\n\n > li {\n position: relative;\n display: block;\n\n > a {\n position: relative;\n display: block;\n padding: @nav-link-padding;\n &:hover,\n &:focus {\n text-decoration: none;\n background-color: @nav-link-hover-bg;\n }\n }\n\n // Disabled state sets text to gray and nukes hover/tab effects\n &.disabled > a {\n color: @nav-disabled-link-color;\n\n &:hover,\n &:focus {\n color: @nav-disabled-link-hover-color;\n text-decoration: none;\n background-color: transparent;\n cursor: @cursor-disabled;\n }\n }\n }\n\n // Open dropdowns\n .open > a {\n &,\n &:hover,\n &:focus {\n background-color: @nav-link-hover-bg;\n border-color: @link-color;\n }\n }\n\n // Nav dividers (deprecated with v3.0.1)\n //\n // This should have been removed in v3 with the dropping of `.nav-list`, but\n // we missed it. We don't currently support this anywhere, but in the interest\n // of maintaining backward compatibility in case you use it, it's deprecated.\n .nav-divider {\n .nav-divider();\n }\n\n // Prevent IE8 from misplacing imgs\n //\n // See https://github.com/h5bp/html5-boilerplate/issues/984#issuecomment-3985989\n > li > a > img {\n max-width: none;\n }\n}\n\n\n// Tabs\n// -------------------------\n\n// Give the tabs something to sit on\n.nav-tabs {\n border-bottom: 1px solid @nav-tabs-border-color;\n > li {\n float: left;\n // Make the list-items overlay the bottom border\n margin-bottom: -1px;\n\n // Actual tabs (as links)\n > a {\n margin-right: 2px;\n line-height: @line-height-base;\n border: 1px solid transparent;\n border-radius: @border-radius-base @border-radius-base 0 0;\n &:hover {\n border-color: @nav-tabs-link-hover-border-color @nav-tabs-link-hover-border-color @nav-tabs-border-color;\n }\n }\n\n // Active state, and its :hover to override normal :hover\n &.active > a {\n &,\n &:hover,\n &:focus {\n color: @nav-tabs-active-link-hover-color;\n background-color: @nav-tabs-active-link-hover-bg;\n border: 1px solid @nav-tabs-active-link-hover-border-color;\n border-bottom-color: transparent;\n cursor: default;\n }\n }\n }\n // pulling this in mainly for less shorthand\n &.nav-justified {\n .nav-justified();\n .nav-tabs-justified();\n }\n}\n\n\n// Pills\n// -------------------------\n.nav-pills {\n > li {\n float: left;\n\n // Links rendered as pills\n > a {\n border-radius: @nav-pills-border-radius;\n }\n + li {\n margin-left: 2px;\n }\n\n // Active state\n &.active > a {\n &,\n &:hover,\n &:focus {\n color: @nav-pills-active-link-hover-color;\n background-color: @nav-pills-active-link-hover-bg;\n }\n }\n }\n}\n\n\n// Stacked pills\n.nav-stacked {\n > li {\n float: none;\n + li {\n margin-top: 2px;\n margin-left: 0; // no need for this gap between nav items\n }\n }\n}\n\n\n// Nav variations\n// --------------------------------------------------\n\n// Justified nav links\n// -------------------------\n\n.nav-justified {\n width: 100%;\n\n > li {\n float: none;\n > a {\n text-align: center;\n margin-bottom: 5px;\n }\n }\n\n > .dropdown .dropdown-menu {\n top: auto;\n left: auto;\n }\n\n @media (min-width: @screen-sm-min) {\n > li {\n display: table-cell;\n width: 1%;\n > a {\n margin-bottom: 0;\n }\n }\n }\n}\n\n// Move borders to anchors instead of bottom of list\n//\n// Mixin for adding on top the shared `.nav-justified` styles for our tabs\n.nav-tabs-justified {\n border-bottom: 0;\n\n > li > a {\n // Override margin from .nav-tabs\n margin-right: 0;\n border-radius: @border-radius-base;\n }\n\n > .active > a,\n > .active > a:hover,\n > .active > a:focus {\n border: 1px solid @nav-tabs-justified-link-border-color;\n }\n\n @media (min-width: @screen-sm-min) {\n > li > a {\n border-bottom: 1px solid @nav-tabs-justified-link-border-color;\n border-radius: @border-radius-base @border-radius-base 0 0;\n }\n > .active > a,\n > .active > a:hover,\n > .active > a:focus {\n border-bottom-color: @nav-tabs-justified-active-link-border-color;\n }\n }\n}\n\n\n// Tabbable tabs\n// -------------------------\n\n// Hide tabbable panes to start, show them when `.active`\n.tab-content {\n > .tab-pane {\n display: none;\n }\n > .active {\n display: block;\n }\n}\n\n\n// Dropdowns\n// -------------------------\n\n// Specific dropdowns\n.nav-tabs .dropdown-menu {\n // make dropdown border overlap tab border\n margin-top: -1px;\n // Remove the top rounded corners here since there is a hard edge above the menu\n .border-top-radius(0);\n}\n","//\n// Navbars\n// --------------------------------------------------\n\n\n// Wrapper and base class\n//\n// Provide a static navbar from which we expand to create full-width, fixed, and\n// other navbar variations.\n\n.navbar {\n position: relative;\n min-height: @navbar-height; // Ensure a navbar always shows (e.g., without a .navbar-brand in collapsed mode)\n margin-bottom: @navbar-margin-bottom;\n border: 1px solid transparent;\n\n // Prevent floats from breaking the navbar\n &:extend(.clearfix all);\n\n @media (min-width: @grid-float-breakpoint) {\n border-radius: @navbar-border-radius;\n }\n}\n\n\n// Navbar heading\n//\n// Groups `.navbar-brand` and `.navbar-toggle` into a single component for easy\n// styling of responsive aspects.\n\n.navbar-header {\n &:extend(.clearfix all);\n\n @media (min-width: @grid-float-breakpoint) {\n float: left;\n }\n}\n\n\n// Navbar collapse (body)\n//\n// Group your navbar content into this for easy collapsing and expanding across\n// various device sizes. By default, this content is collapsed when <768px, but\n// will expand past that for a horizontal display.\n//\n// To start (on mobile devices) the navbar links, forms, and buttons are stacked\n// vertically and include a `max-height` to overflow in case you have too much\n// content for the user's viewport.\n\n.navbar-collapse {\n overflow-x: visible;\n padding-right: @navbar-padding-horizontal;\n padding-left: @navbar-padding-horizontal;\n border-top: 1px solid transparent;\n box-shadow: inset 0 1px 0 rgba(255,255,255,.1);\n &:extend(.clearfix all);\n -webkit-overflow-scrolling: touch;\n\n &.in {\n overflow-y: auto;\n }\n\n @media (min-width: @grid-float-breakpoint) {\n width: auto;\n border-top: 0;\n box-shadow: none;\n\n &.collapse {\n display: block !important;\n height: auto !important;\n padding-bottom: 0; // Override default setting\n overflow: visible !important;\n }\n\n &.in {\n overflow-y: visible;\n }\n\n // Undo the collapse side padding for navbars with containers to ensure\n // alignment of right-aligned contents.\n .navbar-fixed-top &,\n .navbar-static-top &,\n .navbar-fixed-bottom & {\n padding-left: 0;\n padding-right: 0;\n }\n }\n}\n\n.navbar-fixed-top,\n.navbar-fixed-bottom {\n .navbar-collapse {\n max-height: @navbar-collapse-max-height;\n\n @media (max-device-width: @screen-xs-min) and (orientation: landscape) {\n max-height: 200px;\n }\n }\n}\n\n\n// Both navbar header and collapse\n//\n// When a container is present, change the behavior of the header and collapse.\n\n.container,\n.container-fluid {\n > .navbar-header,\n > .navbar-collapse {\n margin-right: -@navbar-padding-horizontal;\n margin-left: -@navbar-padding-horizontal;\n\n @media (min-width: @grid-float-breakpoint) {\n margin-right: 0;\n margin-left: 0;\n }\n }\n}\n\n\n//\n// Navbar alignment options\n//\n// Display the navbar across the entirety of the page or fixed it to the top or\n// bottom of the page.\n\n// Static top (unfixed, but 100% wide) navbar\n.navbar-static-top {\n z-index: @zindex-navbar;\n border-width: 0 0 1px;\n\n @media (min-width: @grid-float-breakpoint) {\n border-radius: 0;\n }\n}\n\n// Fix the top/bottom navbars when screen real estate supports it\n.navbar-fixed-top,\n.navbar-fixed-bottom {\n position: fixed;\n right: 0;\n left: 0;\n z-index: @zindex-navbar-fixed;\n\n // Undo the rounded corners\n @media (min-width: @grid-float-breakpoint) {\n border-radius: 0;\n }\n}\n.navbar-fixed-top {\n top: 0;\n border-width: 0 0 1px;\n}\n.navbar-fixed-bottom {\n bottom: 0;\n margin-bottom: 0; // override .navbar defaults\n border-width: 1px 0 0;\n}\n\n\n// Brand/project name\n\n.navbar-brand {\n float: left;\n padding: @navbar-padding-vertical @navbar-padding-horizontal;\n font-size: @font-size-large;\n line-height: @line-height-computed;\n height: @navbar-height;\n\n &:hover,\n &:focus {\n text-decoration: none;\n }\n\n > img {\n display: block;\n }\n\n @media (min-width: @grid-float-breakpoint) {\n .navbar > .container &,\n .navbar > .container-fluid & {\n margin-left: -@navbar-padding-horizontal;\n }\n }\n}\n\n\n// Navbar toggle\n//\n// Custom button for toggling the `.navbar-collapse`, powered by the collapse\n// JavaScript plugin.\n\n.navbar-toggle {\n position: relative;\n float: right;\n margin-right: @navbar-padding-horizontal;\n padding: 9px 10px;\n .navbar-vertical-align(34px);\n background-color: transparent;\n background-image: none; // Reset unusual Firefox-on-Android default style; see https://github.com/necolas/normalize.css/issues/214\n border: 1px solid transparent;\n border-radius: @border-radius-base;\n\n // We remove the `outline` here, but later compensate by attaching `:hover`\n // styles to `:focus`.\n &:focus {\n outline: 0;\n }\n\n // Bars\n .icon-bar {\n display: block;\n width: 22px;\n height: 2px;\n border-radius: 1px;\n }\n .icon-bar + .icon-bar {\n margin-top: 4px;\n }\n\n @media (min-width: @grid-float-breakpoint) {\n display: none;\n }\n}\n\n\n// Navbar nav links\n//\n// Builds on top of the `.nav` components with its own modifier class to make\n// the nav the full height of the horizontal nav (above 768px).\n\n.navbar-nav {\n margin: (@navbar-padding-vertical / 2) -@navbar-padding-horizontal;\n\n > li > a {\n padding-top: 10px;\n padding-bottom: 10px;\n line-height: @line-height-computed;\n }\n\n @media (max-width: @grid-float-breakpoint-max) {\n // Dropdowns get custom display when collapsed\n .open .dropdown-menu {\n position: static;\n float: none;\n width: auto;\n margin-top: 0;\n background-color: transparent;\n border: 0;\n box-shadow: none;\n > li > a,\n .dropdown-header {\n padding: 5px 15px 5px 25px;\n }\n > li > a {\n line-height: @line-height-computed;\n &:hover,\n &:focus {\n background-image: none;\n }\n }\n }\n }\n\n // Uncollapse the nav\n @media (min-width: @grid-float-breakpoint) {\n float: left;\n margin: 0;\n\n > li {\n float: left;\n > a {\n padding-top: @navbar-padding-vertical;\n padding-bottom: @navbar-padding-vertical;\n }\n }\n }\n}\n\n\n// Navbar form\n//\n// Extension of the `.form-inline` with some extra flavor for optimum display in\n// our navbars.\n\n.navbar-form {\n margin-left: -@navbar-padding-horizontal;\n margin-right: -@navbar-padding-horizontal;\n padding: 10px @navbar-padding-horizontal;\n border-top: 1px solid transparent;\n border-bottom: 1px solid transparent;\n @shadow: inset 0 1px 0 rgba(255,255,255,.1), 0 1px 0 rgba(255,255,255,.1);\n .box-shadow(@shadow);\n\n // Mixin behavior for optimum display\n .form-inline();\n\n .form-group {\n @media (max-width: @grid-float-breakpoint-max) {\n margin-bottom: 5px;\n\n &:last-child {\n margin-bottom: 0;\n }\n }\n }\n\n // Vertically center in expanded, horizontal navbar\n .navbar-vertical-align(@input-height-base);\n\n // Undo 100% width for pull classes\n @media (min-width: @grid-float-breakpoint) {\n width: auto;\n border: 0;\n margin-left: 0;\n margin-right: 0;\n padding-top: 0;\n padding-bottom: 0;\n .box-shadow(none);\n }\n}\n\n\n// Dropdown menus\n\n// Menu position and menu carets\n.navbar-nav > li > .dropdown-menu {\n margin-top: 0;\n .border-top-radius(0);\n}\n// Menu position and menu caret support for dropups via extra dropup class\n.navbar-fixed-bottom .navbar-nav > li > .dropdown-menu {\n margin-bottom: 0;\n .border-top-radius(@navbar-border-radius);\n .border-bottom-radius(0);\n}\n\n\n// Buttons in navbars\n//\n// Vertically center a button within a navbar (when *not* in a form).\n\n.navbar-btn {\n .navbar-vertical-align(@input-height-base);\n\n &.btn-sm {\n .navbar-vertical-align(@input-height-small);\n }\n &.btn-xs {\n .navbar-vertical-align(22);\n }\n}\n\n\n// Text in navbars\n//\n// Add a class to make any element properly align itself vertically within the navbars.\n\n.navbar-text {\n .navbar-vertical-align(@line-height-computed);\n\n @media (min-width: @grid-float-breakpoint) {\n float: left;\n margin-left: @navbar-padding-horizontal;\n margin-right: @navbar-padding-horizontal;\n }\n}\n\n\n// Component alignment\n//\n// Repurpose the pull utilities as their own navbar utilities to avoid specificity\n// issues with parents and chaining. Only do this when the navbar is uncollapsed\n// though so that navbar contents properly stack and align in mobile.\n//\n// Declared after the navbar components to ensure more specificity on the margins.\n\n@media (min-width: @grid-float-breakpoint) {\n .navbar-left { .pull-left(); }\n .navbar-right {\n .pull-right();\n margin-right: -@navbar-padding-horizontal;\n\n ~ .navbar-right {\n margin-right: 0;\n }\n }\n}\n\n\n// Alternate navbars\n// --------------------------------------------------\n\n// Default navbar\n.navbar-default {\n background-color: @navbar-default-bg;\n border-color: @navbar-default-border;\n\n .navbar-brand {\n color: @navbar-default-brand-color;\n &:hover,\n &:focus {\n color: @navbar-default-brand-hover-color;\n background-color: @navbar-default-brand-hover-bg;\n }\n }\n\n .navbar-text {\n color: @navbar-default-color;\n }\n\n .navbar-nav {\n > li > a {\n color: @navbar-default-link-color;\n\n &:hover,\n &:focus {\n color: @navbar-default-link-hover-color;\n background-color: @navbar-default-link-hover-bg;\n }\n }\n > .active > a {\n &,\n &:hover,\n &:focus {\n color: @navbar-default-link-active-color;\n background-color: @navbar-default-link-active-bg;\n }\n }\n > .disabled > a {\n &,\n &:hover,\n &:focus {\n color: @navbar-default-link-disabled-color;\n background-color: @navbar-default-link-disabled-bg;\n }\n }\n }\n\n .navbar-toggle {\n border-color: @navbar-default-toggle-border-color;\n &:hover,\n &:focus {\n background-color: @navbar-default-toggle-hover-bg;\n }\n .icon-bar {\n background-color: @navbar-default-toggle-icon-bar-bg;\n }\n }\n\n .navbar-collapse,\n .navbar-form {\n border-color: @navbar-default-border;\n }\n\n // Dropdown menu items\n .navbar-nav {\n // Remove background color from open dropdown\n > .open > a {\n &,\n &:hover,\n &:focus {\n background-color: @navbar-default-link-active-bg;\n color: @navbar-default-link-active-color;\n }\n }\n\n @media (max-width: @grid-float-breakpoint-max) {\n // Dropdowns get custom display when collapsed\n .open .dropdown-menu {\n > li > a {\n color: @navbar-default-link-color;\n &:hover,\n &:focus {\n color: @navbar-default-link-hover-color;\n background-color: @navbar-default-link-hover-bg;\n }\n }\n > .active > a {\n &,\n &:hover,\n &:focus {\n color: @navbar-default-link-active-color;\n background-color: @navbar-default-link-active-bg;\n }\n }\n > .disabled > a {\n &,\n &:hover,\n &:focus {\n color: @navbar-default-link-disabled-color;\n background-color: @navbar-default-link-disabled-bg;\n }\n }\n }\n }\n }\n\n\n // Links in navbars\n //\n // Add a class to ensure links outside the navbar nav are colored correctly.\n\n .navbar-link {\n color: @navbar-default-link-color;\n &:hover {\n color: @navbar-default-link-hover-color;\n }\n }\n\n .btn-link {\n color: @navbar-default-link-color;\n &:hover,\n &:focus {\n color: @navbar-default-link-hover-color;\n }\n &[disabled],\n fieldset[disabled] & {\n &:hover,\n &:focus {\n color: @navbar-default-link-disabled-color;\n }\n }\n }\n}\n\n// Inverse navbar\n\n.navbar-inverse {\n background-color: @navbar-inverse-bg;\n border-color: @navbar-inverse-border;\n\n .navbar-brand {\n color: @navbar-inverse-brand-color;\n &:hover,\n &:focus {\n color: @navbar-inverse-brand-hover-color;\n background-color: @navbar-inverse-brand-hover-bg;\n }\n }\n\n .navbar-text {\n color: @navbar-inverse-color;\n }\n\n .navbar-nav {\n > li > a {\n color: @navbar-inverse-link-color;\n\n &:hover,\n &:focus {\n color: @navbar-inverse-link-hover-color;\n background-color: @navbar-inverse-link-hover-bg;\n }\n }\n > .active > a {\n &,\n &:hover,\n &:focus {\n color: @navbar-inverse-link-active-color;\n background-color: @navbar-inverse-link-active-bg;\n }\n }\n > .disabled > a {\n &,\n &:hover,\n &:focus {\n color: @navbar-inverse-link-disabled-color;\n background-color: @navbar-inverse-link-disabled-bg;\n }\n }\n }\n\n // Darken the responsive nav toggle\n .navbar-toggle {\n border-color: @navbar-inverse-toggle-border-color;\n &:hover,\n &:focus {\n background-color: @navbar-inverse-toggle-hover-bg;\n }\n .icon-bar {\n background-color: @navbar-inverse-toggle-icon-bar-bg;\n }\n }\n\n .navbar-collapse,\n .navbar-form {\n border-color: darken(@navbar-inverse-bg, 7%);\n }\n\n // Dropdowns\n .navbar-nav {\n > .open > a {\n &,\n &:hover,\n &:focus {\n background-color: @navbar-inverse-link-active-bg;\n color: @navbar-inverse-link-active-color;\n }\n }\n\n @media (max-width: @grid-float-breakpoint-max) {\n // Dropdowns get custom display\n .open .dropdown-menu {\n > .dropdown-header {\n border-color: @navbar-inverse-border;\n }\n .divider {\n background-color: @navbar-inverse-border;\n }\n > li > a {\n color: @navbar-inverse-link-color;\n &:hover,\n &:focus {\n color: @navbar-inverse-link-hover-color;\n background-color: @navbar-inverse-link-hover-bg;\n }\n }\n > .active > a {\n &,\n &:hover,\n &:focus {\n color: @navbar-inverse-link-active-color;\n background-color: @navbar-inverse-link-active-bg;\n }\n }\n > .disabled > a {\n &,\n &:hover,\n &:focus {\n color: @navbar-inverse-link-disabled-color;\n background-color: @navbar-inverse-link-disabled-bg;\n }\n }\n }\n }\n }\n\n .navbar-link {\n color: @navbar-inverse-link-color;\n &:hover {\n color: @navbar-inverse-link-hover-color;\n }\n }\n\n .btn-link {\n color: @navbar-inverse-link-color;\n &:hover,\n &:focus {\n color: @navbar-inverse-link-hover-color;\n }\n &[disabled],\n fieldset[disabled] & {\n &:hover,\n &:focus {\n color: @navbar-inverse-link-disabled-color;\n }\n }\n }\n}\n","// Navbar vertical align\n//\n// Vertically center elements in the navbar.\n// Example: an element has a height of 30px, so write out `.navbar-vertical-align(30px);` to calculate the appropriate top margin.\n\n.navbar-vertical-align(@element-height) {\n margin-top: ((@navbar-height - @element-height) / 2);\n margin-bottom: ((@navbar-height - @element-height) / 2);\n}\n","//\n// Utility classes\n// --------------------------------------------------\n\n\n// Floats\n// -------------------------\n\n.clearfix {\n .clearfix();\n}\n.center-block {\n .center-block();\n}\n.pull-right {\n float: right !important;\n}\n.pull-left {\n float: left !important;\n}\n\n\n// Toggling content\n// -------------------------\n\n// Note: Deprecated .hide in favor of .hidden or .sr-only (as appropriate) in v3.0.1\n.hide {\n display: none !important;\n}\n.show {\n display: block !important;\n}\n.invisible {\n visibility: hidden;\n}\n.text-hide {\n .text-hide();\n}\n\n\n// Hide from screenreaders and browsers\n//\n// Credit: HTML5 Boilerplate\n\n.hidden {\n display: none !important;\n}\n\n\n// For Affix plugin\n// -------------------------\n\n.affix {\n position: fixed;\n}\n","//\n// Breadcrumbs\n// --------------------------------------------------\n\n\n.breadcrumb {\n padding: @breadcrumb-padding-vertical @breadcrumb-padding-horizontal;\n margin-bottom: @line-height-computed;\n list-style: none;\n background-color: @breadcrumb-bg;\n border-radius: @border-radius-base;\n\n > li {\n display: inline-block;\n\n + li:before {\n content: \"@{breadcrumb-separator}\\00a0\"; // Unicode space added since inline-block means non-collapsing white-space\n padding: 0 5px;\n color: @breadcrumb-color;\n }\n }\n\n > .active {\n color: @breadcrumb-active-color;\n }\n}\n","//\n// Pagination (multiple pages)\n// --------------------------------------------------\n.pagination {\n display: inline-block;\n padding-left: 0;\n margin: @line-height-computed 0;\n border-radius: @border-radius-base;\n\n > li {\n display: inline; // Remove list-style and block-level defaults\n > a,\n > span {\n position: relative;\n float: left; // Collapse white-space\n padding: @padding-base-vertical @padding-base-horizontal;\n line-height: @line-height-base;\n text-decoration: none;\n color: @pagination-color;\n background-color: @pagination-bg;\n border: 1px solid @pagination-border;\n margin-left: -1px;\n }\n &:first-child {\n > a,\n > span {\n margin-left: 0;\n .border-left-radius(@border-radius-base);\n }\n }\n &:last-child {\n > a,\n > span {\n .border-right-radius(@border-radius-base);\n }\n }\n }\n\n > li > a,\n > li > span {\n &:hover,\n &:focus {\n z-index: 2;\n color: @pagination-hover-color;\n background-color: @pagination-hover-bg;\n border-color: @pagination-hover-border;\n }\n }\n\n > .active > a,\n > .active > span {\n &,\n &:hover,\n &:focus {\n z-index: 3;\n color: @pagination-active-color;\n background-color: @pagination-active-bg;\n border-color: @pagination-active-border;\n cursor: default;\n }\n }\n\n > .disabled {\n > span,\n > span:hover,\n > span:focus,\n > a,\n > a:hover,\n > a:focus {\n color: @pagination-disabled-color;\n background-color: @pagination-disabled-bg;\n border-color: @pagination-disabled-border;\n cursor: @cursor-disabled;\n }\n }\n}\n\n// Sizing\n// --------------------------------------------------\n\n// Large\n.pagination-lg {\n .pagination-size(@padding-large-vertical; @padding-large-horizontal; @font-size-large; @line-height-large; @border-radius-large);\n}\n\n// Small\n.pagination-sm {\n .pagination-size(@padding-small-vertical; @padding-small-horizontal; @font-size-small; @line-height-small; @border-radius-small);\n}\n","// Pagination\n\n.pagination-size(@padding-vertical; @padding-horizontal; @font-size; @line-height; @border-radius) {\n > li {\n > a,\n > span {\n padding: @padding-vertical @padding-horizontal;\n font-size: @font-size;\n line-height: @line-height;\n }\n &:first-child {\n > a,\n > span {\n .border-left-radius(@border-radius);\n }\n }\n &:last-child {\n > a,\n > span {\n .border-right-radius(@border-radius);\n }\n }\n }\n}\n","//\n// Pager pagination\n// --------------------------------------------------\n\n\n.pager {\n padding-left: 0;\n margin: @line-height-computed 0;\n list-style: none;\n text-align: center;\n &:extend(.clearfix all);\n li {\n display: inline;\n > a,\n > span {\n display: inline-block;\n padding: 5px 14px;\n background-color: @pager-bg;\n border: 1px solid @pager-border;\n border-radius: @pager-border-radius;\n }\n\n > a:hover,\n > a:focus {\n text-decoration: none;\n background-color: @pager-hover-bg;\n }\n }\n\n .next {\n > a,\n > span {\n float: right;\n }\n }\n\n .previous {\n > a,\n > span {\n float: left;\n }\n }\n\n .disabled {\n > a,\n > a:hover,\n > a:focus,\n > span {\n color: @pager-disabled-color;\n background-color: @pager-bg;\n cursor: @cursor-disabled;\n }\n }\n}\n","//\n// Labels\n// --------------------------------------------------\n\n.label {\n display: inline;\n padding: .2em .6em .3em;\n font-size: 75%;\n font-weight: bold;\n line-height: 1;\n color: @label-color;\n text-align: center;\n white-space: nowrap;\n vertical-align: baseline;\n border-radius: .25em;\n\n // Add hover effects, but only for links\n a& {\n &:hover,\n &:focus {\n color: @label-link-hover-color;\n text-decoration: none;\n cursor: pointer;\n }\n }\n\n // Empty labels collapse automatically (not available in IE8)\n &:empty {\n display: none;\n }\n\n // Quick fix for labels in buttons\n .btn & {\n position: relative;\n top: -1px;\n }\n}\n\n// Colors\n// Contextual variations (linked labels get darker on :hover)\n\n.label-default {\n .label-variant(@label-default-bg);\n}\n\n.label-primary {\n .label-variant(@label-primary-bg);\n}\n\n.label-success {\n .label-variant(@label-success-bg);\n}\n\n.label-info {\n .label-variant(@label-info-bg);\n}\n\n.label-warning {\n .label-variant(@label-warning-bg);\n}\n\n.label-danger {\n .label-variant(@label-danger-bg);\n}\n","// Labels\n\n.label-variant(@color) {\n background-color: @color;\n\n &[href] {\n &:hover,\n &:focus {\n background-color: darken(@color, 10%);\n }\n }\n}\n","//\n// Badges\n// --------------------------------------------------\n\n\n// Base class\n.badge {\n display: inline-block;\n min-width: 10px;\n padding: 3px 7px;\n font-size: @font-size-small;\n font-weight: @badge-font-weight;\n color: @badge-color;\n line-height: @badge-line-height;\n vertical-align: middle;\n white-space: nowrap;\n text-align: center;\n background-color: @badge-bg;\n border-radius: @badge-border-radius;\n\n // Empty badges collapse automatically (not available in IE8)\n &:empty {\n display: none;\n }\n\n // Quick fix for badges in buttons\n .btn & {\n position: relative;\n top: -1px;\n }\n\n .btn-xs &,\n .btn-group-xs > .btn & {\n top: 0;\n padding: 1px 5px;\n }\n\n // Hover state, but only for links\n a& {\n &:hover,\n &:focus {\n color: @badge-link-hover-color;\n text-decoration: none;\n cursor: pointer;\n }\n }\n\n // Account for badges in navs\n .list-group-item.active > &,\n .nav-pills > .active > a > & {\n color: @badge-active-color;\n background-color: @badge-active-bg;\n }\n\n .list-group-item > & {\n float: right;\n }\n\n .list-group-item > & + & {\n margin-right: 5px;\n }\n\n .nav-pills > li > a > & {\n margin-left: 3px;\n }\n}\n","//\n// Jumbotron\n// --------------------------------------------------\n\n\n.jumbotron {\n padding-top: @jumbotron-padding;\n padding-bottom: @jumbotron-padding;\n margin-bottom: @jumbotron-padding;\n color: @jumbotron-color;\n background-color: @jumbotron-bg;\n\n h1,\n .h1 {\n color: @jumbotron-heading-color;\n }\n\n p {\n margin-bottom: (@jumbotron-padding / 2);\n font-size: @jumbotron-font-size;\n font-weight: 200;\n }\n\n > hr {\n border-top-color: darken(@jumbotron-bg, 10%);\n }\n\n .container &,\n .container-fluid & {\n border-radius: @border-radius-large; // Only round corners at higher resolutions if contained in a container\n padding-left: (@grid-gutter-width / 2);\n padding-right: (@grid-gutter-width / 2);\n }\n\n .container {\n max-width: 100%;\n }\n\n @media screen and (min-width: @screen-sm-min) {\n padding-top: (@jumbotron-padding * 1.6);\n padding-bottom: (@jumbotron-padding * 1.6);\n\n .container &,\n .container-fluid & {\n padding-left: (@jumbotron-padding * 2);\n padding-right: (@jumbotron-padding * 2);\n }\n\n h1,\n .h1 {\n font-size: @jumbotron-heading-font-size;\n }\n }\n}\n","//\n// Thumbnails\n// --------------------------------------------------\n\n\n// Mixin and adjust the regular image class\n.thumbnail {\n display: block;\n padding: @thumbnail-padding;\n margin-bottom: @line-height-computed;\n line-height: @line-height-base;\n background-color: @thumbnail-bg;\n border: 1px solid @thumbnail-border;\n border-radius: @thumbnail-border-radius;\n .transition(border .2s ease-in-out);\n\n > img,\n a > img {\n &:extend(.img-responsive);\n margin-left: auto;\n margin-right: auto;\n }\n\n // Add a hover state for linked versions only\n a&:hover,\n a&:focus,\n a&.active {\n border-color: @link-color;\n }\n\n // Image captions\n .caption {\n padding: @thumbnail-caption-padding;\n color: @thumbnail-caption-color;\n }\n}\n","//\n// Alerts\n// --------------------------------------------------\n\n\n// Base styles\n// -------------------------\n\n.alert {\n padding: @alert-padding;\n margin-bottom: @line-height-computed;\n border: 1px solid transparent;\n border-radius: @alert-border-radius;\n\n // Headings for larger alerts\n h4 {\n margin-top: 0;\n // Specified for the h4 to prevent conflicts of changing @headings-color\n color: inherit;\n }\n\n // Provide class for links that match alerts\n .alert-link {\n font-weight: @alert-link-font-weight;\n }\n\n // Improve alignment and spacing of inner content\n > p,\n > ul {\n margin-bottom: 0;\n }\n\n > p + p {\n margin-top: 5px;\n }\n}\n\n// Dismissible alerts\n//\n// Expand the right padding and account for the close button's positioning.\n\n.alert-dismissable, // The misspelled .alert-dismissable was deprecated in 3.2.0.\n.alert-dismissible {\n padding-right: (@alert-padding + 20);\n\n // Adjust close link position\n .close {\n position: relative;\n top: -2px;\n right: -21px;\n color: inherit;\n }\n}\n\n// Alternate styles\n//\n// Generate contextual modifier classes for colorizing the alert.\n\n.alert-success {\n .alert-variant(@alert-success-bg; @alert-success-border; @alert-success-text);\n}\n\n.alert-info {\n .alert-variant(@alert-info-bg; @alert-info-border; @alert-info-text);\n}\n\n.alert-warning {\n .alert-variant(@alert-warning-bg; @alert-warning-border; @alert-warning-text);\n}\n\n.alert-danger {\n .alert-variant(@alert-danger-bg; @alert-danger-border; @alert-danger-text);\n}\n","// Alerts\n\n.alert-variant(@background; @border; @text-color) {\n background-color: @background;\n border-color: @border;\n color: @text-color;\n\n hr {\n border-top-color: darken(@border, 5%);\n }\n .alert-link {\n color: darken(@text-color, 10%);\n }\n}\n","//\n// Progress bars\n// --------------------------------------------------\n\n\n// Bar animations\n// -------------------------\n\n// WebKit\n@-webkit-keyframes progress-bar-stripes {\n from { background-position: 40px 0; }\n to { background-position: 0 0; }\n}\n\n// Spec and IE10+\n@keyframes progress-bar-stripes {\n from { background-position: 40px 0; }\n to { background-position: 0 0; }\n}\n\n\n// Bar itself\n// -------------------------\n\n// Outer container\n.progress {\n overflow: hidden;\n height: @line-height-computed;\n margin-bottom: @line-height-computed;\n background-color: @progress-bg;\n border-radius: @progress-border-radius;\n .box-shadow(inset 0 1px 2px rgba(0,0,0,.1));\n}\n\n// Bar of progress\n.progress-bar {\n float: left;\n width: 0%;\n height: 100%;\n font-size: @font-size-small;\n line-height: @line-height-computed;\n color: @progress-bar-color;\n text-align: center;\n background-color: @progress-bar-bg;\n .box-shadow(inset 0 -1px 0 rgba(0,0,0,.15));\n .transition(width .6s ease);\n}\n\n// Striped bars\n//\n// `.progress-striped .progress-bar` is deprecated as of v3.2.0 in favor of the\n// `.progress-bar-striped` class, which you just add to an existing\n// `.progress-bar`.\n.progress-striped .progress-bar,\n.progress-bar-striped {\n #gradient > .striped();\n background-size: 40px 40px;\n}\n\n// Call animation for the active one\n//\n// `.progress.active .progress-bar` is deprecated as of v3.2.0 in favor of the\n// `.progress-bar.active` approach.\n.progress.active .progress-bar,\n.progress-bar.active {\n .animation(progress-bar-stripes 2s linear infinite);\n}\n\n\n// Variations\n// -------------------------\n\n.progress-bar-success {\n .progress-bar-variant(@progress-bar-success-bg);\n}\n\n.progress-bar-info {\n .progress-bar-variant(@progress-bar-info-bg);\n}\n\n.progress-bar-warning {\n .progress-bar-variant(@progress-bar-warning-bg);\n}\n\n.progress-bar-danger {\n .progress-bar-variant(@progress-bar-danger-bg);\n}\n","// Gradients\n\n#gradient {\n\n // Horizontal gradient, from left to right\n //\n // Creates two color stops, start and end, by specifying a color and position for each color stop.\n // Color stops are not available in IE9 and below.\n .horizontal(@start-color: #555; @end-color: #333; @start-percent: 0%; @end-percent: 100%) {\n background-image: -webkit-linear-gradient(left, @start-color @start-percent, @end-color @end-percent); // Safari 5.1-6, Chrome 10+\n background-image: -o-linear-gradient(left, @start-color @start-percent, @end-color @end-percent); // Opera 12\n background-image: linear-gradient(to right, @start-color @start-percent, @end-color @end-percent); // Standard, IE10, Firefox 16+, Opera 12.10+, Safari 7+, Chrome 26+\n background-repeat: repeat-x;\n filter: e(%(\"progid:DXImageTransform.Microsoft.gradient(startColorstr='%d', endColorstr='%d', GradientType=1)\",argb(@start-color),argb(@end-color))); // IE9 and down\n }\n\n // Vertical gradient, from top to bottom\n //\n // Creates two color stops, start and end, by specifying a color and position for each color stop.\n // Color stops are not available in IE9 and below.\n .vertical(@start-color: #555; @end-color: #333; @start-percent: 0%; @end-percent: 100%) {\n background-image: -webkit-linear-gradient(top, @start-color @start-percent, @end-color @end-percent); // Safari 5.1-6, Chrome 10+\n background-image: -o-linear-gradient(top, @start-color @start-percent, @end-color @end-percent); // Opera 12\n background-image: linear-gradient(to bottom, @start-color @start-percent, @end-color @end-percent); // Standard, IE10, Firefox 16+, Opera 12.10+, Safari 7+, Chrome 26+\n background-repeat: repeat-x;\n filter: e(%(\"progid:DXImageTransform.Microsoft.gradient(startColorstr='%d', endColorstr='%d', GradientType=0)\",argb(@start-color),argb(@end-color))); // IE9 and down\n }\n\n .directional(@start-color: #555; @end-color: #333; @deg: 45deg) {\n background-repeat: repeat-x;\n background-image: -webkit-linear-gradient(@deg, @start-color, @end-color); // Safari 5.1-6, Chrome 10+\n background-image: -o-linear-gradient(@deg, @start-color, @end-color); // Opera 12\n background-image: linear-gradient(@deg, @start-color, @end-color); // Standard, IE10, Firefox 16+, Opera 12.10+, Safari 7+, Chrome 26+\n }\n .horizontal-three-colors(@start-color: #00b3ee; @mid-color: #7a43b6; @color-stop: 50%; @end-color: #c3325f) {\n background-image: -webkit-linear-gradient(left, @start-color, @mid-color @color-stop, @end-color);\n background-image: -o-linear-gradient(left, @start-color, @mid-color @color-stop, @end-color);\n background-image: linear-gradient(to right, @start-color, @mid-color @color-stop, @end-color);\n background-repeat: no-repeat;\n filter: e(%(\"progid:DXImageTransform.Microsoft.gradient(startColorstr='%d', endColorstr='%d', GradientType=1)\",argb(@start-color),argb(@end-color))); // IE9 and down, gets no color-stop at all for proper fallback\n }\n .vertical-three-colors(@start-color: #00b3ee; @mid-color: #7a43b6; @color-stop: 50%; @end-color: #c3325f) {\n background-image: -webkit-linear-gradient(@start-color, @mid-color @color-stop, @end-color);\n background-image: -o-linear-gradient(@start-color, @mid-color @color-stop, @end-color);\n background-image: linear-gradient(@start-color, @mid-color @color-stop, @end-color);\n background-repeat: no-repeat;\n filter: e(%(\"progid:DXImageTransform.Microsoft.gradient(startColorstr='%d', endColorstr='%d', GradientType=0)\",argb(@start-color),argb(@end-color))); // IE9 and down, gets no color-stop at all for proper fallback\n }\n .radial(@inner-color: #555; @outer-color: #333) {\n background-image: -webkit-radial-gradient(circle, @inner-color, @outer-color);\n background-image: radial-gradient(circle, @inner-color, @outer-color);\n background-repeat: no-repeat;\n }\n .striped(@color: rgba(255,255,255,.15); @angle: 45deg) {\n background-image: -webkit-linear-gradient(@angle, @color 25%, transparent 25%, transparent 50%, @color 50%, @color 75%, transparent 75%, transparent);\n background-image: -o-linear-gradient(@angle, @color 25%, transparent 25%, transparent 50%, @color 50%, @color 75%, transparent 75%, transparent);\n background-image: linear-gradient(@angle, @color 25%, transparent 25%, transparent 50%, @color 50%, @color 75%, transparent 75%, transparent);\n }\n}\n","// Progress bars\n\n.progress-bar-variant(@color) {\n background-color: @color;\n\n // Deprecated parent class requirement as of v3.2.0\n .progress-striped & {\n #gradient > .striped();\n }\n}\n",".media {\n // Proper spacing between instances of .media\n margin-top: 15px;\n\n &:first-child {\n margin-top: 0;\n }\n}\n\n.media,\n.media-body {\n zoom: 1;\n overflow: hidden;\n}\n\n.media-body {\n width: 10000px;\n}\n\n.media-object {\n display: block;\n\n // Fix collapse in webkit from max-width: 100% and display: table-cell.\n &.img-thumbnail {\n max-width: none;\n }\n}\n\n.media-right,\n.media > .pull-right {\n padding-left: 10px;\n}\n\n.media-left,\n.media > .pull-left {\n padding-right: 10px;\n}\n\n.media-left,\n.media-right,\n.media-body {\n display: table-cell;\n vertical-align: top;\n}\n\n.media-middle {\n vertical-align: middle;\n}\n\n.media-bottom {\n vertical-align: bottom;\n}\n\n// Reset margins on headings for tighter default spacing\n.media-heading {\n margin-top: 0;\n margin-bottom: 5px;\n}\n\n// Media list variation\n//\n// Undo default ul/ol styles\n.media-list {\n padding-left: 0;\n list-style: none;\n}\n","//\n// List groups\n// --------------------------------------------------\n\n\n// Base class\n//\n// Easily usable on <ul>, <ol>, or <div>.\n\n.list-group {\n // No need to set list-style: none; since .list-group-item is block level\n margin-bottom: 20px;\n padding-left: 0; // reset padding because ul and ol\n}\n\n\n// Individual list items\n//\n// Use on `li`s or `div`s within the `.list-group` parent.\n\n.list-group-item {\n position: relative;\n display: block;\n padding: 10px 15px;\n // Place the border on the list items and negative margin up for better styling\n margin-bottom: -1px;\n background-color: @list-group-bg;\n border: 1px solid @list-group-border;\n\n // Round the first and last items\n &:first-child {\n .border-top-radius(@list-group-border-radius);\n }\n &:last-child {\n margin-bottom: 0;\n .border-bottom-radius(@list-group-border-radius);\n }\n}\n\n\n// Interactive list items\n//\n// Use anchor or button elements instead of `li`s or `div`s to create interactive items.\n// Includes an extra `.active` modifier class for showing selected items.\n\na.list-group-item,\nbutton.list-group-item {\n color: @list-group-link-color;\n\n .list-group-item-heading {\n color: @list-group-link-heading-color;\n }\n\n // Hover state\n &:hover,\n &:focus {\n text-decoration: none;\n color: @list-group-link-hover-color;\n background-color: @list-group-hover-bg;\n }\n}\n\nbutton.list-group-item {\n width: 100%;\n text-align: left;\n}\n\n.list-group-item {\n // Disabled state\n &.disabled,\n &.disabled:hover,\n &.disabled:focus {\n background-color: @list-group-disabled-bg;\n color: @list-group-disabled-color;\n cursor: @cursor-disabled;\n\n // Force color to inherit for custom content\n .list-group-item-heading {\n color: inherit;\n }\n .list-group-item-text {\n color: @list-group-disabled-text-color;\n }\n }\n\n // Active class on item itself, not parent\n &.active,\n &.active:hover,\n &.active:focus {\n z-index: 2; // Place active items above their siblings for proper border styling\n color: @list-group-active-color;\n background-color: @list-group-active-bg;\n border-color: @list-group-active-border;\n\n // Force color to inherit for custom content\n .list-group-item-heading,\n .list-group-item-heading > small,\n .list-group-item-heading > .small {\n color: inherit;\n }\n .list-group-item-text {\n color: @list-group-active-text-color;\n }\n }\n}\n\n\n// Contextual variants\n//\n// Add modifier classes to change text and background color on individual items.\n// Organizationally, this must come after the `:hover` states.\n\n.list-group-item-variant(success; @state-success-bg; @state-success-text);\n.list-group-item-variant(info; @state-info-bg; @state-info-text);\n.list-group-item-variant(warning; @state-warning-bg; @state-warning-text);\n.list-group-item-variant(danger; @state-danger-bg; @state-danger-text);\n\n\n// Custom content options\n//\n// Extra classes for creating well-formatted content within `.list-group-item`s.\n\n.list-group-item-heading {\n margin-top: 0;\n margin-bottom: 5px;\n}\n.list-group-item-text {\n margin-bottom: 0;\n line-height: 1.3;\n}\n","// List Groups\n\n.list-group-item-variant(@state; @background; @color) {\n .list-group-item-@{state} {\n color: @color;\n background-color: @background;\n\n a&,\n button& {\n color: @color;\n\n .list-group-item-heading {\n color: inherit;\n }\n\n &:hover,\n &:focus {\n color: @color;\n background-color: darken(@background, 5%);\n }\n &.active,\n &.active:hover,\n &.active:focus {\n color: #fff;\n background-color: @color;\n border-color: @color;\n }\n }\n }\n}\n","//\n// Panels\n// --------------------------------------------------\n\n\n// Base class\n.panel {\n margin-bottom: @line-height-computed;\n background-color: @panel-bg;\n border: 1px solid transparent;\n border-radius: @panel-border-radius;\n .box-shadow(0 1px 1px rgba(0,0,0,.05));\n}\n\n// Panel contents\n.panel-body {\n padding: @panel-body-padding;\n &:extend(.clearfix all);\n}\n\n// Optional heading\n.panel-heading {\n padding: @panel-heading-padding;\n border-bottom: 1px solid transparent;\n .border-top-radius((@panel-border-radius - 1));\n\n > .dropdown .dropdown-toggle {\n color: inherit;\n }\n}\n\n// Within heading, strip any `h*` tag of its default margins for spacing.\n.panel-title {\n margin-top: 0;\n margin-bottom: 0;\n font-size: ceil((@font-size-base * 1.125));\n color: inherit;\n\n > a,\n > small,\n > .small,\n > small > a,\n > .small > a {\n color: inherit;\n }\n}\n\n// Optional footer (stays gray in every modifier class)\n.panel-footer {\n padding: @panel-footer-padding;\n background-color: @panel-footer-bg;\n border-top: 1px solid @panel-inner-border;\n .border-bottom-radius((@panel-border-radius - 1));\n}\n\n\n// List groups in panels\n//\n// By default, space out list group content from panel headings to account for\n// any kind of custom content between the two.\n\n.panel {\n > .list-group,\n > .panel-collapse > .list-group {\n margin-bottom: 0;\n\n .list-group-item {\n border-width: 1px 0;\n border-radius: 0;\n }\n\n // Add border top radius for first one\n &:first-child {\n .list-group-item:first-child {\n border-top: 0;\n .border-top-radius((@panel-border-radius - 1));\n }\n }\n\n // Add border bottom radius for last one\n &:last-child {\n .list-group-item:last-child {\n border-bottom: 0;\n .border-bottom-radius((@panel-border-radius - 1));\n }\n }\n }\n > .panel-heading + .panel-collapse > .list-group {\n .list-group-item:first-child {\n .border-top-radius(0);\n }\n }\n}\n// Collapse space between when there's no additional content.\n.panel-heading + .list-group {\n .list-group-item:first-child {\n border-top-width: 0;\n }\n}\n.list-group + .panel-footer {\n border-top-width: 0;\n}\n\n// Tables in panels\n//\n// Place a non-bordered `.table` within a panel (not within a `.panel-body`) and\n// watch it go full width.\n\n.panel {\n > .table,\n > .table-responsive > .table,\n > .panel-collapse > .table {\n margin-bottom: 0;\n\n caption {\n padding-left: @panel-body-padding;\n padding-right: @panel-body-padding;\n }\n }\n // Add border top radius for first one\n > .table:first-child,\n > .table-responsive:first-child > .table:first-child {\n .border-top-radius((@panel-border-radius - 1));\n\n > thead:first-child,\n > tbody:first-child {\n > tr:first-child {\n border-top-left-radius: (@panel-border-radius - 1);\n border-top-right-radius: (@panel-border-radius - 1);\n\n td:first-child,\n th:first-child {\n border-top-left-radius: (@panel-border-radius - 1);\n }\n td:last-child,\n th:last-child {\n border-top-right-radius: (@panel-border-radius - 1);\n }\n }\n }\n }\n // Add border bottom radius for last one\n > .table:last-child,\n > .table-responsive:last-child > .table:last-child {\n .border-bottom-radius((@panel-border-radius - 1));\n\n > tbody:last-child,\n > tfoot:last-child {\n > tr:last-child {\n border-bottom-left-radius: (@panel-border-radius - 1);\n border-bottom-right-radius: (@panel-border-radius - 1);\n\n td:first-child,\n th:first-child {\n border-bottom-left-radius: (@panel-border-radius - 1);\n }\n td:last-child,\n th:last-child {\n border-bottom-right-radius: (@panel-border-radius - 1);\n }\n }\n }\n }\n > .panel-body + .table,\n > .panel-body + .table-responsive,\n > .table + .panel-body,\n > .table-responsive + .panel-body {\n border-top: 1px solid @table-border-color;\n }\n > .table > tbody:first-child > tr:first-child th,\n > .table > tbody:first-child > tr:first-child td {\n border-top: 0;\n }\n > .table-bordered,\n > .table-responsive > .table-bordered {\n border: 0;\n > thead,\n > tbody,\n > tfoot {\n > tr {\n > th:first-child,\n > td:first-child {\n border-left: 0;\n }\n > th:last-child,\n > td:last-child {\n border-right: 0;\n }\n }\n }\n > thead,\n > tbody {\n > tr:first-child {\n > td,\n > th {\n border-bottom: 0;\n }\n }\n }\n > tbody,\n > tfoot {\n > tr:last-child {\n > td,\n > th {\n border-bottom: 0;\n }\n }\n }\n }\n > .table-responsive {\n border: 0;\n margin-bottom: 0;\n }\n}\n\n\n// Collapsible panels (aka, accordion)\n//\n// Wrap a series of panels in `.panel-group` to turn them into an accordion with\n// the help of our collapse JavaScript plugin.\n\n.panel-group {\n margin-bottom: @line-height-computed;\n\n // Tighten up margin so it's only between panels\n .panel {\n margin-bottom: 0;\n border-radius: @panel-border-radius;\n\n + .panel {\n margin-top: 5px;\n }\n }\n\n .panel-heading {\n border-bottom: 0;\n\n + .panel-collapse > .panel-body,\n + .panel-collapse > .list-group {\n border-top: 1px solid @panel-inner-border;\n }\n }\n\n .panel-footer {\n border-top: 0;\n + .panel-collapse .panel-body {\n border-bottom: 1px solid @panel-inner-border;\n }\n }\n}\n\n\n// Contextual variations\n.panel-default {\n .panel-variant(@panel-default-border; @panel-default-text; @panel-default-heading-bg; @panel-default-border);\n}\n.panel-primary {\n .panel-variant(@panel-primary-border; @panel-primary-text; @panel-primary-heading-bg; @panel-primary-border);\n}\n.panel-success {\n .panel-variant(@panel-success-border; @panel-success-text; @panel-success-heading-bg; @panel-success-border);\n}\n.panel-info {\n .panel-variant(@panel-info-border; @panel-info-text; @panel-info-heading-bg; @panel-info-border);\n}\n.panel-warning {\n .panel-variant(@panel-warning-border; @panel-warning-text; @panel-warning-heading-bg; @panel-warning-border);\n}\n.panel-danger {\n .panel-variant(@panel-danger-border; @panel-danger-text; @panel-danger-heading-bg; @panel-danger-border);\n}\n","// Panels\n\n.panel-variant(@border; @heading-text-color; @heading-bg-color; @heading-border) {\n border-color: @border;\n\n & > .panel-heading {\n color: @heading-text-color;\n background-color: @heading-bg-color;\n border-color: @heading-border;\n\n + .panel-collapse > .panel-body {\n border-top-color: @border;\n }\n .badge {\n color: @heading-bg-color;\n background-color: @heading-text-color;\n }\n }\n & > .panel-footer {\n + .panel-collapse > .panel-body {\n border-bottom-color: @border;\n }\n }\n}\n","// Embeds responsive\n//\n// Credit: Nicolas Gallagher and SUIT CSS.\n\n.embed-responsive {\n position: relative;\n display: block;\n height: 0;\n padding: 0;\n overflow: hidden;\n\n .embed-responsive-item,\n iframe,\n embed,\n object,\n video {\n position: absolute;\n top: 0;\n left: 0;\n bottom: 0;\n height: 100%;\n width: 100%;\n border: 0;\n }\n}\n\n// Modifier class for 16:9 aspect ratio\n.embed-responsive-16by9 {\n padding-bottom: 56.25%;\n}\n\n// Modifier class for 4:3 aspect ratio\n.embed-responsive-4by3 {\n padding-bottom: 75%;\n}\n","//\n// Wells\n// --------------------------------------------------\n\n\n// Base class\n.well {\n min-height: 20px;\n padding: 19px;\n margin-bottom: 20px;\n background-color: @well-bg;\n border: 1px solid @well-border;\n border-radius: @border-radius-base;\n .box-shadow(inset 0 1px 1px rgba(0,0,0,.05));\n blockquote {\n border-color: #ddd;\n border-color: rgba(0,0,0,.15);\n }\n}\n\n// Sizes\n.well-lg {\n padding: 24px;\n border-radius: @border-radius-large;\n}\n.well-sm {\n padding: 9px;\n border-radius: @border-radius-small;\n}\n","//\n// Close icons\n// --------------------------------------------------\n\n\n.close {\n float: right;\n font-size: (@font-size-base * 1.5);\n font-weight: @close-font-weight;\n line-height: 1;\n color: @close-color;\n text-shadow: @close-text-shadow;\n .opacity(.2);\n\n &:hover,\n &:focus {\n color: @close-color;\n text-decoration: none;\n cursor: pointer;\n .opacity(.5);\n }\n\n // Additional properties for button version\n // iOS requires the button element instead of an anchor tag.\n // If you want the anchor version, it requires `href=\"#\"`.\n // See https://developer.mozilla.org/en-US/docs/Web/Events/click#Safari_Mobile\n button& {\n padding: 0;\n cursor: pointer;\n background: transparent;\n border: 0;\n -webkit-appearance: none;\n }\n}\n","//\n// Modals\n// --------------------------------------------------\n\n// .modal-open - body class for killing the scroll\n// .modal - container to scroll within\n// .modal-dialog - positioning shell for the actual modal\n// .modal-content - actual modal w/ bg and corners and shit\n\n// Kill the scroll on the body\n.modal-open {\n overflow: hidden;\n}\n\n// Container that the modal scrolls within\n.modal {\n display: none;\n overflow: hidden;\n position: fixed;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: @zindex-modal;\n -webkit-overflow-scrolling: touch;\n\n // Prevent Chrome on Windows from adding a focus outline. For details, see\n // https://github.com/twbs/bootstrap/pull/10951.\n outline: 0;\n\n // When fading in the modal, animate it to slide down\n &.fade .modal-dialog {\n .translate(0, -25%);\n .transition-transform(~\"0.3s ease-out\");\n }\n &.in .modal-dialog { .translate(0, 0) }\n}\n.modal-open .modal {\n overflow-x: hidden;\n overflow-y: auto;\n}\n\n// Shell div to position the modal with bottom padding\n.modal-dialog {\n position: relative;\n width: auto;\n margin: 10px;\n}\n\n// Actual modal\n.modal-content {\n position: relative;\n background-color: @modal-content-bg;\n border: 1px solid @modal-content-fallback-border-color; //old browsers fallback (ie8 etc)\n border: 1px solid @modal-content-border-color;\n border-radius: @border-radius-large;\n .box-shadow(0 3px 9px rgba(0,0,0,.5));\n background-clip: padding-box;\n // Remove focus outline from opened modal\n outline: 0;\n}\n\n// Modal background\n.modal-backdrop {\n position: fixed;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: @zindex-modal-background;\n background-color: @modal-backdrop-bg;\n // Fade for backdrop\n &.fade { .opacity(0); }\n &.in { .opacity(@modal-backdrop-opacity); }\n}\n\n// Modal header\n// Top section of the modal w/ title and dismiss\n.modal-header {\n padding: @modal-title-padding;\n border-bottom: 1px solid @modal-header-border-color;\n &:extend(.clearfix all);\n}\n// Close icon\n.modal-header .close {\n margin-top: -2px;\n}\n\n// Title text within header\n.modal-title {\n margin: 0;\n line-height: @modal-title-line-height;\n}\n\n// Modal body\n// Where all modal content resides (sibling of .modal-header and .modal-footer)\n.modal-body {\n position: relative;\n padding: @modal-inner-padding;\n}\n\n// Footer (for actions)\n.modal-footer {\n padding: @modal-inner-padding;\n text-align: right; // right align buttons\n border-top: 1px solid @modal-footer-border-color;\n &:extend(.clearfix all); // clear it in case folks use .pull-* classes on buttons\n\n // Properly space out buttons\n .btn + .btn {\n margin-left: 5px;\n margin-bottom: 0; // account for input[type=\"submit\"] which gets the bottom margin like all other inputs\n }\n // but override that for button groups\n .btn-group .btn + .btn {\n margin-left: -1px;\n }\n // and override it for block buttons as well\n .btn-block + .btn-block {\n margin-left: 0;\n }\n}\n\n// Measure scrollbar width for padding body during modal show/hide\n.modal-scrollbar-measure {\n position: absolute;\n top: -9999px;\n width: 50px;\n height: 50px;\n overflow: scroll;\n}\n\n// Scale up the modal\n@media (min-width: @screen-sm-min) {\n // Automatically set modal's width for larger viewports\n .modal-dialog {\n width: @modal-md;\n margin: 30px auto;\n }\n .modal-content {\n .box-shadow(0 5px 15px rgba(0,0,0,.5));\n }\n\n // Modal sizes\n .modal-sm { width: @modal-sm; }\n}\n\n@media (min-width: @screen-md-min) {\n .modal-lg { width: @modal-lg; }\n}\n","//\n// Tooltips\n// --------------------------------------------------\n\n\n// Base class\n.tooltip {\n position: absolute;\n z-index: @zindex-tooltip;\n display: block;\n // Our parent element can be arbitrary since tooltips are by default inserted as a sibling of their target element.\n // So reset our font and text properties to avoid inheriting weird values.\n .reset-text();\n font-size: @font-size-small;\n\n .opacity(0);\n\n &.in { .opacity(@tooltip-opacity); }\n &.top { margin-top: -3px; padding: @tooltip-arrow-width 0; }\n &.right { margin-left: 3px; padding: 0 @tooltip-arrow-width; }\n &.bottom { margin-top: 3px; padding: @tooltip-arrow-width 0; }\n &.left { margin-left: -3px; padding: 0 @tooltip-arrow-width; }\n}\n\n// Wrapper for the tooltip content\n.tooltip-inner {\n max-width: @tooltip-max-width;\n padding: 3px 8px;\n color: @tooltip-color;\n text-align: center;\n background-color: @tooltip-bg;\n border-radius: @border-radius-base;\n}\n\n// Arrows\n.tooltip-arrow {\n position: absolute;\n width: 0;\n height: 0;\n border-color: transparent;\n border-style: solid;\n}\n// Note: Deprecated .top-left, .top-right, .bottom-left, and .bottom-right as of v3.3.1\n.tooltip {\n &.top .tooltip-arrow {\n bottom: 0;\n left: 50%;\n margin-left: -@tooltip-arrow-width;\n border-width: @tooltip-arrow-width @tooltip-arrow-width 0;\n border-top-color: @tooltip-arrow-color;\n }\n &.top-left .tooltip-arrow {\n bottom: 0;\n right: @tooltip-arrow-width;\n margin-bottom: -@tooltip-arrow-width;\n border-width: @tooltip-arrow-width @tooltip-arrow-width 0;\n border-top-color: @tooltip-arrow-color;\n }\n &.top-right .tooltip-arrow {\n bottom: 0;\n left: @tooltip-arrow-width;\n margin-bottom: -@tooltip-arrow-width;\n border-width: @tooltip-arrow-width @tooltip-arrow-width 0;\n border-top-color: @tooltip-arrow-color;\n }\n &.right .tooltip-arrow {\n top: 50%;\n left: 0;\n margin-top: -@tooltip-arrow-width;\n border-width: @tooltip-arrow-width @tooltip-arrow-width @tooltip-arrow-width 0;\n border-right-color: @tooltip-arrow-color;\n }\n &.left .tooltip-arrow {\n top: 50%;\n right: 0;\n margin-top: -@tooltip-arrow-width;\n border-width: @tooltip-arrow-width 0 @tooltip-arrow-width @tooltip-arrow-width;\n border-left-color: @tooltip-arrow-color;\n }\n &.bottom .tooltip-arrow {\n top: 0;\n left: 50%;\n margin-left: -@tooltip-arrow-width;\n border-width: 0 @tooltip-arrow-width @tooltip-arrow-width;\n border-bottom-color: @tooltip-arrow-color;\n }\n &.bottom-left .tooltip-arrow {\n top: 0;\n right: @tooltip-arrow-width;\n margin-top: -@tooltip-arrow-width;\n border-width: 0 @tooltip-arrow-width @tooltip-arrow-width;\n border-bottom-color: @tooltip-arrow-color;\n }\n &.bottom-right .tooltip-arrow {\n top: 0;\n left: @tooltip-arrow-width;\n margin-top: -@tooltip-arrow-width;\n border-width: 0 @tooltip-arrow-width @tooltip-arrow-width;\n border-bottom-color: @tooltip-arrow-color;\n }\n}\n",".reset-text() {\n font-family: @font-family-base;\n // We deliberately do NOT reset font-size.\n font-style: normal;\n font-weight: normal;\n letter-spacing: normal;\n line-break: auto;\n line-height: @line-height-base;\n text-align: left; // Fallback for where `start` is not supported\n text-align: start;\n text-decoration: none;\n text-shadow: none;\n text-transform: none;\n white-space: normal;\n word-break: normal;\n word-spacing: normal;\n word-wrap: normal;\n}\n","//\n// Popovers\n// --------------------------------------------------\n\n\n.popover {\n position: absolute;\n top: 0;\n left: 0;\n z-index: @zindex-popover;\n display: none;\n max-width: @popover-max-width;\n padding: 1px;\n // Our parent element can be arbitrary since popovers are by default inserted as a sibling of their target element.\n // So reset our font and text properties to avoid inheriting weird values.\n .reset-text();\n font-size: @font-size-base;\n\n background-color: @popover-bg;\n background-clip: padding-box;\n border: 1px solid @popover-fallback-border-color;\n border: 1px solid @popover-border-color;\n border-radius: @border-radius-large;\n .box-shadow(0 5px 10px rgba(0,0,0,.2));\n\n // Offset the popover to account for the popover arrow\n &.top { margin-top: -@popover-arrow-width; }\n &.right { margin-left: @popover-arrow-width; }\n &.bottom { margin-top: @popover-arrow-width; }\n &.left { margin-left: -@popover-arrow-width; }\n}\n\n.popover-title {\n margin: 0; // reset heading margin\n padding: 8px 14px;\n font-size: @font-size-base;\n background-color: @popover-title-bg;\n border-bottom: 1px solid darken(@popover-title-bg, 5%);\n border-radius: (@border-radius-large - 1) (@border-radius-large - 1) 0 0;\n}\n\n.popover-content {\n padding: 9px 14px;\n}\n\n// Arrows\n//\n// .arrow is outer, .arrow:after is inner\n\n.popover > .arrow {\n &,\n &:after {\n position: absolute;\n display: block;\n width: 0;\n height: 0;\n border-color: transparent;\n border-style: solid;\n }\n}\n.popover > .arrow {\n border-width: @popover-arrow-outer-width;\n}\n.popover > .arrow:after {\n border-width: @popover-arrow-width;\n content: \"\";\n}\n\n.popover {\n &.top > .arrow {\n left: 50%;\n margin-left: -@popover-arrow-outer-width;\n border-bottom-width: 0;\n border-top-color: @popover-arrow-outer-fallback-color; // IE8 fallback\n border-top-color: @popover-arrow-outer-color;\n bottom: -@popover-arrow-outer-width;\n &:after {\n content: \" \";\n bottom: 1px;\n margin-left: -@popover-arrow-width;\n border-bottom-width: 0;\n border-top-color: @popover-arrow-color;\n }\n }\n &.right > .arrow {\n top: 50%;\n left: -@popover-arrow-outer-width;\n margin-top: -@popover-arrow-outer-width;\n border-left-width: 0;\n border-right-color: @popover-arrow-outer-fallback-color; // IE8 fallback\n border-right-color: @popover-arrow-outer-color;\n &:after {\n content: \" \";\n left: 1px;\n bottom: -@popover-arrow-width;\n border-left-width: 0;\n border-right-color: @popover-arrow-color;\n }\n }\n &.bottom > .arrow {\n left: 50%;\n margin-left: -@popover-arrow-outer-width;\n border-top-width: 0;\n border-bottom-color: @popover-arrow-outer-fallback-color; // IE8 fallback\n border-bottom-color: @popover-arrow-outer-color;\n top: -@popover-arrow-outer-width;\n &:after {\n content: \" \";\n top: 1px;\n margin-left: -@popover-arrow-width;\n border-top-width: 0;\n border-bottom-color: @popover-arrow-color;\n }\n }\n\n &.left > .arrow {\n top: 50%;\n right: -@popover-arrow-outer-width;\n margin-top: -@popover-arrow-outer-width;\n border-right-width: 0;\n border-left-color: @popover-arrow-outer-fallback-color; // IE8 fallback\n border-left-color: @popover-arrow-outer-color;\n &:after {\n content: \" \";\n right: 1px;\n border-right-width: 0;\n border-left-color: @popover-arrow-color;\n bottom: -@popover-arrow-width;\n }\n }\n}\n","//\n// Carousel\n// --------------------------------------------------\n\n\n// Wrapper for the slide container and indicators\n.carousel {\n position: relative;\n}\n\n.carousel-inner {\n position: relative;\n overflow: hidden;\n width: 100%;\n\n > .item {\n display: none;\n position: relative;\n .transition(.6s ease-in-out left);\n\n // Account for jankitude on images\n > img,\n > a > img {\n &:extend(.img-responsive);\n line-height: 1;\n }\n\n // WebKit CSS3 transforms for supported devices\n @media all and (transform-3d), (-webkit-transform-3d) {\n .transition-transform(~'0.6s ease-in-out');\n .backface-visibility(~'hidden');\n .perspective(1000px);\n\n &.next,\n &.active.right {\n .translate3d(100%, 0, 0);\n left: 0;\n }\n &.prev,\n &.active.left {\n .translate3d(-100%, 0, 0);\n left: 0;\n }\n &.next.left,\n &.prev.right,\n &.active {\n .translate3d(0, 0, 0);\n left: 0;\n }\n }\n }\n\n > .active,\n > .next,\n > .prev {\n display: block;\n }\n\n > .active {\n left: 0;\n }\n\n > .next,\n > .prev {\n position: absolute;\n top: 0;\n width: 100%;\n }\n\n > .next {\n left: 100%;\n }\n > .prev {\n left: -100%;\n }\n > .next.left,\n > .prev.right {\n left: 0;\n }\n\n > .active.left {\n left: -100%;\n }\n > .active.right {\n left: 100%;\n }\n\n}\n\n// Left/right controls for nav\n// ---------------------------\n\n.carousel-control {\n position: absolute;\n top: 0;\n left: 0;\n bottom: 0;\n width: @carousel-control-width;\n .opacity(@carousel-control-opacity);\n font-size: @carousel-control-font-size;\n color: @carousel-control-color;\n text-align: center;\n text-shadow: @carousel-text-shadow;\n background-color: rgba(0, 0, 0, 0); // Fix IE9 click-thru bug\n // We can't have this transition here because WebKit cancels the carousel\n // animation if you trip this while in the middle of another animation.\n\n // Set gradients for backgrounds\n &.left {\n #gradient > .horizontal(@start-color: rgba(0,0,0,.5); @end-color: rgba(0,0,0,.0001));\n }\n &.right {\n left: auto;\n right: 0;\n #gradient > .horizontal(@start-color: rgba(0,0,0,.0001); @end-color: rgba(0,0,0,.5));\n }\n\n // Hover/focus state\n &:hover,\n &:focus {\n outline: 0;\n color: @carousel-control-color;\n text-decoration: none;\n .opacity(.9);\n }\n\n // Toggles\n .icon-prev,\n .icon-next,\n .glyphicon-chevron-left,\n .glyphicon-chevron-right {\n position: absolute;\n top: 50%;\n margin-top: -10px;\n z-index: 5;\n display: inline-block;\n }\n .icon-prev,\n .glyphicon-chevron-left {\n left: 50%;\n margin-left: -10px;\n }\n .icon-next,\n .glyphicon-chevron-right {\n right: 50%;\n margin-right: -10px;\n }\n .icon-prev,\n .icon-next {\n width: 20px;\n height: 20px;\n line-height: 1;\n font-family: serif;\n }\n\n\n .icon-prev {\n &:before {\n content: '\\2039';// SINGLE LEFT-POINTING ANGLE QUOTATION MARK (U+2039)\n }\n }\n .icon-next {\n &:before {\n content: '\\203a';// SINGLE RIGHT-POINTING ANGLE QUOTATION MARK (U+203A)\n }\n }\n}\n\n// Optional indicator pips\n//\n// Add an unordered list with the following class and add a list item for each\n// slide your carousel holds.\n\n.carousel-indicators {\n position: absolute;\n bottom: 10px;\n left: 50%;\n z-index: 15;\n width: 60%;\n margin-left: -30%;\n padding-left: 0;\n list-style: none;\n text-align: center;\n\n li {\n display: inline-block;\n width: 10px;\n height: 10px;\n margin: 1px;\n text-indent: -999px;\n border: 1px solid @carousel-indicator-border-color;\n border-radius: 10px;\n cursor: pointer;\n\n // IE8-9 hack for event handling\n //\n // Internet Explorer 8-9 does not support clicks on elements without a set\n // `background-color`. We cannot use `filter` since that's not viewed as a\n // background color by the browser. Thus, a hack is needed.\n // See https://developer.mozilla.org/en-US/docs/Web/Events/click#Internet_Explorer\n //\n // For IE8, we set solid black as it doesn't support `rgba()`. For IE9, we\n // set alpha transparency for the best results possible.\n background-color: #000 \\9; // IE8\n background-color: rgba(0,0,0,0); // IE9\n }\n .active {\n margin: 0;\n width: 12px;\n height: 12px;\n background-color: @carousel-indicator-active-bg;\n }\n}\n\n// Optional captions\n// -----------------------------\n// Hidden by default for smaller viewports\n.carousel-caption {\n position: absolute;\n left: 15%;\n right: 15%;\n bottom: 20px;\n z-index: 10;\n padding-top: 20px;\n padding-bottom: 20px;\n color: @carousel-caption-color;\n text-align: center;\n text-shadow: @carousel-text-shadow;\n & .btn {\n text-shadow: none; // No shadow for button elements in carousel-caption\n }\n}\n\n\n// Scale up controls for tablets and up\n@media screen and (min-width: @screen-sm-min) {\n\n // Scale up the controls a smidge\n .carousel-control {\n .glyphicon-chevron-left,\n .glyphicon-chevron-right,\n .icon-prev,\n .icon-next {\n width: (@carousel-control-font-size * 1.5);\n height: (@carousel-control-font-size * 1.5);\n margin-top: (@carousel-control-font-size / -2);\n font-size: (@carousel-control-font-size * 1.5);\n }\n .glyphicon-chevron-left,\n .icon-prev {\n margin-left: (@carousel-control-font-size / -2);\n }\n .glyphicon-chevron-right,\n .icon-next {\n margin-right: (@carousel-control-font-size / -2);\n }\n }\n\n // Show and left align the captions\n .carousel-caption {\n left: 20%;\n right: 20%;\n padding-bottom: 30px;\n }\n\n // Move up the indicators\n .carousel-indicators {\n bottom: 20px;\n }\n}\n","// Clearfix\n//\n// For modern browsers\n// 1. The space content is one way to avoid an Opera bug when the\n// contenteditable attribute is included anywhere else in the document.\n// Otherwise it causes space to appear at the top and bottom of elements\n// that are clearfixed.\n// 2. The use of `table` rather than `block` is only necessary if using\n// `:before` to contain the top-margins of child elements.\n//\n// Source: http://nicolasgallagher.com/micro-clearfix-hack/\n\n.clearfix() {\n &:before,\n &:after {\n content: \" \"; // 1\n display: table; // 2\n }\n &:after {\n clear: both;\n }\n}\n","// Center-align a block level element\n\n.center-block() {\n display: block;\n margin-left: auto;\n margin-right: auto;\n}\n","// CSS image replacement\n//\n// Heads up! v3 launched with only `.hide-text()`, but per our pattern for\n// mixins being reused as classes with the same name, this doesn't hold up. As\n// of v3.0.1 we have added `.text-hide()` and deprecated `.hide-text()`.\n//\n// Source: https://github.com/h5bp/html5-boilerplate/commit/aa0396eae757\n\n// Deprecated as of v3.0.1 (has been removed in v4)\n.hide-text() {\n font: ~\"0/0\" a;\n color: transparent;\n text-shadow: none;\n background-color: transparent;\n border: 0;\n}\n\n// New mixin to use as of v3.0.1\n.text-hide() {\n .hide-text();\n}\n","//\n// Responsive: Utility classes\n// --------------------------------------------------\n\n\n// IE10 in Windows (Phone) 8\n//\n// Support for responsive views via media queries is kind of borked in IE10, for\n// Surface/desktop in split view and for Windows Phone 8. This particular fix\n// must be accompanied by a snippet of JavaScript to sniff the user agent and\n// apply some conditional CSS to *only* the Surface/desktop Windows 8. Look at\n// our Getting Started page for more information on this bug.\n//\n// For more information, see the following:\n//\n// Issue: https://github.com/twbs/bootstrap/issues/10497\n// Docs: http://getbootstrap.com/getting-started/#support-ie10-width\n// Source: http://timkadlec.com/2013/01/windows-phone-8-and-device-width/\n// Source: http://timkadlec.com/2012/10/ie10-snap-mode-and-responsive-design/\n\n@-ms-viewport {\n width: device-width;\n}\n\n\n// Visibility utilities\n// Note: Deprecated .visible-xs, .visible-sm, .visible-md, and .visible-lg as of v3.2.0\n.visible-xs,\n.visible-sm,\n.visible-md,\n.visible-lg {\n .responsive-invisibility();\n}\n\n.visible-xs-block,\n.visible-xs-inline,\n.visible-xs-inline-block,\n.visible-sm-block,\n.visible-sm-inline,\n.visible-sm-inline-block,\n.visible-md-block,\n.visible-md-inline,\n.visible-md-inline-block,\n.visible-lg-block,\n.visible-lg-inline,\n.visible-lg-inline-block {\n display: none !important;\n}\n\n.visible-xs {\n @media (max-width: @screen-xs-max) {\n .responsive-visibility();\n }\n}\n.visible-xs-block {\n @media (max-width: @screen-xs-max) {\n display: block !important;\n }\n}\n.visible-xs-inline {\n @media (max-width: @screen-xs-max) {\n display: inline !important;\n }\n}\n.visible-xs-inline-block {\n @media (max-width: @screen-xs-max) {\n display: inline-block !important;\n }\n}\n\n.visible-sm {\n @media (min-width: @screen-sm-min) and (max-width: @screen-sm-max) {\n .responsive-visibility();\n }\n}\n.visible-sm-block {\n @media (min-width: @screen-sm-min) and (max-width: @screen-sm-max) {\n display: block !important;\n }\n}\n.visible-sm-inline {\n @media (min-width: @screen-sm-min) and (max-width: @screen-sm-max) {\n display: inline !important;\n }\n}\n.visible-sm-inline-block {\n @media (min-width: @screen-sm-min) and (max-width: @screen-sm-max) {\n display: inline-block !important;\n }\n}\n\n.visible-md {\n @media (min-width: @screen-md-min) and (max-width: @screen-md-max) {\n .responsive-visibility();\n }\n}\n.visible-md-block {\n @media (min-width: @screen-md-min) and (max-width: @screen-md-max) {\n display: block !important;\n }\n}\n.visible-md-inline {\n @media (min-width: @screen-md-min) and (max-width: @screen-md-max) {\n display: inline !important;\n }\n}\n.visible-md-inline-block {\n @media (min-width: @screen-md-min) and (max-width: @screen-md-max) {\n display: inline-block !important;\n }\n}\n\n.visible-lg {\n @media (min-width: @screen-lg-min) {\n .responsive-visibility();\n }\n}\n.visible-lg-block {\n @media (min-width: @screen-lg-min) {\n display: block !important;\n }\n}\n.visible-lg-inline {\n @media (min-width: @screen-lg-min) {\n display: inline !important;\n }\n}\n.visible-lg-inline-block {\n @media (min-width: @screen-lg-min) {\n display: inline-block !important;\n }\n}\n\n.hidden-xs {\n @media (max-width: @screen-xs-max) {\n .responsive-invisibility();\n }\n}\n.hidden-sm {\n @media (min-width: @screen-sm-min) and (max-width: @screen-sm-max) {\n .responsive-invisibility();\n }\n}\n.hidden-md {\n @media (min-width: @screen-md-min) and (max-width: @screen-md-max) {\n .responsive-invisibility();\n }\n}\n.hidden-lg {\n @media (min-width: @screen-lg-min) {\n .responsive-invisibility();\n }\n}\n\n\n// Print utilities\n//\n// Media queries are placed on the inside to be mixin-friendly.\n\n// Note: Deprecated .visible-print as of v3.2.0\n.visible-print {\n .responsive-invisibility();\n\n @media print {\n .responsive-visibility();\n }\n}\n.visible-print-block {\n display: none !important;\n\n @media print {\n display: block !important;\n }\n}\n.visible-print-inline {\n display: none !important;\n\n @media print {\n display: inline !important;\n }\n}\n.visible-print-inline-block {\n display: none !important;\n\n @media print {\n display: inline-block !important;\n }\n}\n\n.hidden-print {\n @media print {\n .responsive-invisibility();\n }\n}\n","// Responsive utilities\n\n//\n// More easily include all the states for responsive-utilities.less.\n.responsive-visibility() {\n display: block !important;\n table& { display: table !important; }\n tr& { display: table-row !important; }\n th&,\n td& { display: table-cell !important; }\n}\n\n.responsive-invisibility() {\n display: none !important;\n}\n"]} \ No newline at end of file
+{"version":3,"sources":["../../scss/bootstrap.scss","../../scss/_print.scss","bootstrap.css","../../scss/_reboot.scss","../../scss/_variables.scss","../../scss/mixins/_hover.scss","../../scss/_type.scss","../../scss/mixins/_lists.scss","../../scss/_images.scss","../../scss/mixins/_image.scss","../../scss/mixins/_border-radius.scss","../../scss/mixins/_transition.scss","../../scss/_code.scss","../../scss/_grid.scss","../../scss/mixins/_grid.scss","../../scss/mixins/_breakpoints.scss","../../scss/mixins/_grid-framework.scss","../../scss/_tables.scss","../../scss/mixins/_table-row.scss","../../scss/_functions.scss","../../scss/_forms.scss","../../scss/mixins/_forms.scss","../../scss/_buttons.scss","../../scss/mixins/_buttons.scss","../../scss/_transitions.scss","../../scss/_dropdown.scss","../../scss/mixins/_nav-divider.scss","../../scss/_button-group.scss","../../scss/_input-group.scss","../../scss/_custom-forms.scss","../../scss/_nav.scss","../../scss/_navbar.scss","../../scss/_card.scss","../../scss/_breadcrumb.scss","../../scss/mixins/_clearfix.scss","../../scss/_pagination.scss","../../scss/mixins/_pagination.scss","../../scss/_badge.scss","../../scss/mixins/_badge.scss","../../scss/_jumbotron.scss","../../scss/_alert.scss","../../scss/mixins/_alert.scss","../../scss/_progress.scss","../../scss/mixins/_gradients.scss","../../scss/_media.scss","../../scss/_list-group.scss","../../scss/mixins/_list-group.scss","../../scss/_close.scss","../../scss/_modal.scss","../../scss/_tooltip.scss","../../scss/mixins/_reset-text.scss","../../scss/_popover.scss","../../scss/_carousel.scss","../../scss/utilities/_align.scss","../../scss/mixins/_background-variant.scss","../../scss/utilities/_background.scss","../../scss/utilities/_borders.scss","../../scss/utilities/_display.scss","../../scss/utilities/_embed.scss","../../scss/utilities/_flex.scss","../../scss/utilities/_float.scss","../../scss/mixins/_float.scss","../../scss/utilities/_position.scss","../../scss/utilities/_screenreaders.scss","../../scss/mixins/_screen-reader.scss","../../scss/utilities/_sizing.scss","../../scss/utilities/_spacing.scss","../../scss/utilities/_text.scss","../../scss/mixins/_text-truncate.scss","../../scss/mixins/_text-emphasis.scss","../../scss/mixins/_text-hide.scss","../../scss/utilities/_visibility.scss","../../scss/mixins/_visibility.scss"],"names":[],"mappings":"AAAA;;;;;GAKG;ACMD;EACE;;;IAME,6BAA4B;IAE5B,4BAA2B;GAC5B;EAED;;IAEE,2BAA0B;GAC3B;EAOD;IACE,8BAA6B;GAC9B;EAaD;IACE,iCAAgC;GACjC;EACD;;IAEE,uBAAgC;IAChC,yBAAwB;GACzB;EAOD;IACE,4BAA2B;GAC5B;EAED;;IAEE,yBAAwB;GACzB;EAED;;;IAGE,WAAU;IACV,UAAS;GACV;EAED;;IAEE,wBAAuB;GACxB;EAKD;IACE,cAAa;GACd;EACD;IACE,uBAAgC;GACjC;EAED;IACE,qCAAoC;GAMrC;EAPD;;IAKI,kCAAiC;GAClC;EAEH;;IAGI,kCAAiC;GAClC;CC3CN;;AC1CD;EACE,uBAAsB;EACtB,wBAAuB;EACvB,kBAAiB;EACjB,+BAA8B;EAC9B,2BAA0B;EAC1B,8BAA6B;EAC7B,yCAA0C;CAC3C;;AAED;;;EAGE,oBAAmB;CACpB;;AAIC;EAAgB,oBAAmB;CD4CpC;;ACxCD;EACE,eAAc;CACf;;AAOD;EACE,UAAS;EACT,wGCoLiH;EDnLjH,gBCuLmB;EDtLnB,oBC0LyB;EDzLzB,iBC6LoB;ED5LpB,eCEgB;EDDhB,uBCRW;CDSZ;;ADuCD;EC/BE,yBAAwB;CACzB;;AAQD;EACE,wBAAuB;EACvB,UAAS;EACT,kBAAiB;CAClB;;AAWD;EACE,cAAa;EACb,qBAAoB;CACrB;;AAMD;EACE,cAAa;EACb,oBAAmB;CACpB;;AASD;;EAEE,2BAA0B;EAC1B,0CAAiC;UAAjC,kCAAiC;EACjC,aAAY;EACZ,iBAAgB;CACjB;;AAED;EACE,oBAAmB;EACnB,mBAAkB;EAClB,qBAAoB;CACrB;;AAED;;;EAGE,cAAa;EACb,oBAAmB;CACpB;;AAED;;;;EAIE,iBAAgB;CACjB;;AAED;EACE,kBCqGqB;CDpGtB;;AAED;EACE,qBAAoB;EACpB,eAAc;CACf;;AAED;EACE,iBAAgB;CACjB;;AAED;EACE,mBAAkB;CACnB;;AAED;;EAEE,oBAAmB;CACpB;;AAED;EACE,eAAc;CACf;;AAOD;;EAEE,mBAAkB;EAClB,eAAc;EACd,eAAc;EACd,yBAAwB;CACzB;;AAED;EAAM,eAAc;CAAK;;AACzB;EAAM,WAAU;CAAK;;AAOrB;EACE,eClHe;EDmHf,sBCxB0B;EDyB1B,8BAA6B;EAC7B,sCAAqC;CAMtC;;AE1LG;EFuLA,eC5B4C;ED6B5C,2BC5B6B;CC5JR;;AFkMzB;EACE,eAAc;EACd,sBAAqB;CAUtB;;AEnMG;EF4LA,eAAc;EACd,sBAAqB;CE1LpB;;AFoLL;EAUI,WAAU;CACX;;AAQH;;;;EAIE,kCAAiC;EACjC,eAAc;CACf;;AAED;EAEE,cAAa;EAEb,oBAAmB;EAEnB,eAAc;CACf;;AAOD;EAEE,iBAAgB;CACjB;;AAOD;EACE,uBAAsB;EACtB,mBAAkB;CACnB;;AAED;EACE,iBAAgB;CACjB;;AAaD;;;;;;;;;EASE,+BAA0B;MAA1B,2BAA0B;CAC3B;;AAOD;EACE,0BAAyB;CAC1B;;AAED;EACE,qBCEoC;EDDpC,wBCCoC;EDApC,eCpPgB;EDqPhB,iBAAgB;EAChB,qBAAoB;CACrB;;AAED;EAEE,iBAAgB;CACjB;;AAOD;EAEE,sBAAqB;EACrB,qBAAoB;CACrB;;AAMD;EACE,oBAAmB;EACnB,2CAA0C;CAC3C;;AAED;;;;;EAKE,UAAS;EACT,qBAAoB;EACpB,mBAAkB;EAClB,qBAAoB;CACrB;;AAED;;EAEE,kBAAiB;CAClB;;AAED;;EAEE,qBAAoB;CACrB;;AAKD;;;;EAIE,2BAA0B;CAC3B;;AAGD;;;;EAIE,WAAU;EACV,mBAAkB;CACnB;;AAED;;EAEE,uBAAsB;EACtB,WAAU;CACX;;AAGD;;;;EASE,4BAA2B;CAC5B;;AAED;EACE,eAAc;EAEd,iBAAgB;CACjB;;AAED;EAME,aAAY;EAEZ,WAAU;EACV,UAAS;EACT,UAAS;CACV;;AAID;EACE,eAAc;EACd,YAAW;EACX,gBAAe;EACf,WAAU;EACV,qBAAoB;EACpB,kBAAiB;EACjB,qBAAoB;EACpB,eAAc;EACd,oBAAmB;CACpB;;AAED;EACE,yBAAwB;CACzB;;ADpED;;ECyEE,aAAY;CACb;;ADrED;EC4EE,qBAAoB;EACpB,yBAAwB;CACzB;;ADzED;;ECiFE,yBAAwB;CACzB;;AAOD;EACE,cAAa;EACb,2BAA0B;CAC3B;;AAMD;EACE,sBAAqB;CACtB;;AAED;EACE,mBAAkB;CACnB;;AAED;EACE,cAAa;CACd;;ADtFD;EC2FE,yBAAwB;CACzB;;AG5dD;;EAEE,sBFwPoC;EEvPpC,qBFwP8B;EEvP9B,iBFwP0B;EEvP1B,iBFwP0B;EEvP1B,eFwP8B;CEvP/B;;AAED;EAAU,kBF0OW;CE1OiB;;AACtC;EAAU,gBF0OS;CE1OmB;;AACtC;EAAU,mBF0OY;CE1OgB;;AACtC;EAAU,kBF0OW;CE1OiB;;AACtC;EAAU,mBF0OY;CE1OgB;;AACtC;EAAU,gBF0OS;CE1OmB;;AAEtC;EACE,mBF0PwB;EEzPxB,iBF0PoB;CEzPrB;;AAGD;EACE,gBFyOkB;EExOlB,iBF6OuB;EE5OvB,iBFoO0B;CEnO3B;;AACD;EACE,kBFqOoB;EEpOpB,iBFyOuB;EExOvB,iBF+N0B;CE9N3B;;AACD;EACE,kBFiOoB;EEhOpB,iBFqOuB;EEpOvB,iBF0N0B;CEzN3B;;AACD;EACE,kBF6NoB;EE5NpB,iBFiOuB;EEhOvB,iBFqN0B;CEpN3B;;AAOD;EACE,iBAAgB;EAChB,oBAAmB;EACnB,UAAS;EACT,yCFIW;CEHZ;;AAOD;;EAEE,eFgNmB;EE/MnB,oBF8KyB;CE7K1B;;AAED;;EAEE,eFoNiB;EEnNjB,0BF4Ne;CE3NhB;;AAOD;EC7EE,gBAAe;EACf,iBAAgB;CD8EjB;;AAGD;EClFE,gBAAe;EACf,iBAAgB;CDmFjB;;AACD;EACE,sBAAqB;CAKtB;;AAND;EAII,kBFsMqB;CErMtB;;AASH;EACE,eAAc;EACd,0BAAyB;CAC1B;;AAGD;EACE,oBFyBW;EExBX,mBFwKgD;CEvKjD;;AAED;EACE,eAAc;EACd,eAAc;EACd,eF7DgB;CEkEjB;;AARD;EAMI,uBAAsB;CACvB;;AElHH;ECIE,gBAAe;EAGf,aAAY;CDLb;;AAID;EACE,iBJkvBkC;EIjvBlC,uBJmCW;EIlCX,uBJmvBgC;EM/vB9B,uBNmN2B;EOlNzB,iCPiwB2C;EK3vB/C,gBAAe;EAGf,aAAY;CDSb;;AAMD;EAEE,sBAAqB;CACtB;;AAED;EACE,sBAA4B;EAC5B,eAAc;CACf;;AAED;EACE,eJmuB4B;EIluB5B,eJegB;CIdjB;;AIzCD;;;;EAIE,kFRqO2F;CQpO5F;;AAGD;EACE,uBRkzBiC;EQjzBjC,eR+yB+B;EQ9yB/B,eRizBmC;EQhzBnC,0BRsCgB;EM/Cd,uBNmN2B;CQjM9B;;AALC;EACE,WAAU;EACV,eAAc;EACd,0BAAyB;CAC1B;;AAIH;EACE,uBRkyBiC;EQjyBjC,eR+xB+B;EQ9xB/B,YRsBW;EQrBX,0BR8BgB;EMvDd,sBNqN0B;CQlL7B;;AAdD;EASI,WAAU;EACV,gBAAe;EACf,kBR8MmB;CQ5MpB;;AAIH;EACE,eAAc;EACd,cAAa;EACb,oBAAmB;EACnB,eR4wB+B;EQ3wB/B,eRYgB;CQFjB;;AAfD;EASI,WAAU;EACV,mBAAkB;EAClB,eAAc;EACd,8BAA6B;EAC7B,iBAAgB;CACjB;;AAIH;EACE,kBRuwBiC;EQtwBjC,mBAAkB;CACnB;;AC1DC;ECAA,mBAAkB;EAClB,kBAAiB;EACjB,oBAAuC;EACvC,mBAAuC;EACvC,YAAW;CDDV;;AEgDC;EFnDF;ICYI,iBV8KK;GSvLR;CXwlBF;;AaxiBG;EFnDF;ICYI,iBV+KK;GSxLR;CX8lBF;;Aa9iBG;EFnDF;ICYI,iBVgLK;GSzLR;CXomBF;;AapjBG;EFnDF;ICYI,kBViLM;GS1LT;CX0mBF;;AWjmBC;EACE,YAAW;ECbb,mBAAkB;EAClB,kBAAiB;EACjB,oBAAuC;EACvC,mBAAuC;EACvC,YAAW;CDWV;;AAQD;ECLA,qBAAa;EAAb,cAAa;EACb,oBAAe;MAAf,gBAAe;EACf,oBAAuC;EACvC,mBAAuC;CDItC;;AAID;EACE,gBAAe;EACf,eAAc;CAOf;;AATD;;EAMI,iBAAgB;EAChB,gBAAe;CAChB;;AGnCH;;;;;;EACE,mBAAkB;EAClB,YAAW;EACX,gBAAe;EACf,oBAA4B;EAC5B,mBAA4B;CAC7B;;AAkBG;EACE,2BAAa;MAAb,cAAa;EACb,qBAAY;MAAZ,aAAY;EACZ,gBAAe;CAChB;;AACD;EACE,mBAAc;MAAd,eAAc;EACd,YAAW;EACX,gBAAe;CAChB;;AAGC;EFFN,wBAAsC;MAAtC,oBAAsC;EAItC,qBAAuC;CEAhC;;AAFD;EFFN,yBAAsC;MAAtC,qBAAsC;EAItC,sBAAuC;CEAhC;;AAFD;EFFN,kBAAsC;MAAtC,cAAsC;EAItC,eAAuC;CEAhC;;AAFD;EFFN,yBAAsC;MAAtC,qBAAsC;EAItC,sBAAuC;CEAhC;;AAFD;EFFN,yBAAsC;MAAtC,qBAAsC;EAItC,sBAAuC;CEAhC;;AAFD;EFFN,kBAAsC;MAAtC,cAAsC;EAItC,eAAuC;CEAhC;;AAFD;EFFN,yBAAsC;MAAtC,qBAAsC;EAItC,sBAAuC;CEAhC;;AAFD;EFFN,yBAAsC;MAAtC,qBAAsC;EAItC,sBAAuC;CEAhC;;AAFD;EFFN,kBAAsC;MAAtC,cAAsC;EAItC,eAAuC;CEAhC;;AAFD;EFFN,yBAAsC;MAAtC,qBAAsC;EAItC,sBAAuC;CEAhC;;AAFD;EFFN,yBAAsC;MAAtC,qBAAsC;EAItC,sBAAuC;CEAhC;;AAFD;EFFN,mBAAsC;MAAtC,eAAsC;EAItC,gBAAuC;CEAhC;;AAID;EACE,kBAFU;MAEV,SAFU;CAGX;;AAFD;EACE,kBAFU;MAEV,SAFU;CAGX;;AAFD;EACE,kBAFU;MAEV,SAFU;CAGX;;AAFD;EACE,kBAFU;MAEV,SAFU;CAGX;;AAFD;EACE,kBAFU;MAEV,SAFU;CAGX;;AAFD;EACE,kBAFU;MAEV,SAFU;CAGX;;AAFD;EACE,kBAFU;MAEV,SAFU;CAGX;;AAFD;EACE,kBAFU;MAEV,SAFU;CAGX;;AAFD;EACE,kBAFU;MAEV,SAFU;CAGX;;AAFD;EACE,mBAFU;MAEV,UAFU;CAGX;;AAFD;EACE,mBAFU;MAEV,UAFU;CAGX;;AAFD;EACE,mBAFU;MAEV,UAFU;CAGX;;ADKL;ECzBE;IACE,2BAAa;QAAb,cAAa;IACb,qBAAY;QAAZ,aAAY;IACZ,gBAAe;GAChB;EACD;IACE,mBAAc;QAAd,eAAc;IACd,YAAW;IACX,gBAAe;GAChB;EAGC;IFFN,wBAAsC;QAAtC,oBAAsC;IAItC,qBAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,mBAAsC;QAAtC,eAAsC;IAItC,gBAAuC;GEAhC;EAID;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;Cdg0BR;;Aa3zBG;ECzBE;IACE,2BAAa;QAAb,cAAa;IACb,qBAAY;QAAZ,aAAY;IACZ,gBAAe;GAChB;EACD;IACE,mBAAc;QAAd,eAAc;IACd,YAAW;IACX,gBAAe;GAChB;EAGC;IFFN,wBAAsC;QAAtC,oBAAsC;IAItC,qBAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,mBAAsC;QAAtC,eAAsC;IAItC,gBAAuC;GEAhC;EAID;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;Cdi6BR;;Aa55BG;ECzBE;IACE,2BAAa;QAAb,cAAa;IACb,qBAAY;QAAZ,aAAY;IACZ,gBAAe;GAChB;EACD;IACE,mBAAc;QAAd,eAAc;IACd,YAAW;IACX,gBAAe;GAChB;EAGC;IFFN,wBAAsC;QAAtC,oBAAsC;IAItC,qBAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,mBAAsC;QAAtC,eAAsC;IAItC,gBAAuC;GEAhC;EAID;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;CdkgCR;;Aa7/BG;ECzBE;IACE,2BAAa;QAAb,cAAa;IACb,qBAAY;QAAZ,aAAY;IACZ,gBAAe;GAChB;EACD;IACE,mBAAc;QAAd,eAAc;IACd,YAAW;IACX,gBAAe;GAChB;EAGC;IFFN,wBAAsC;QAAtC,oBAAsC;IAItC,qBAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,kBAAsC;QAAtC,cAAsC;IAItC,eAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,yBAAsC;QAAtC,qBAAsC;IAItC,sBAAuC;GEAhC;EAFD;IFFN,mBAAsC;QAAtC,eAAsC;IAItC,gBAAuC;GEAhC;EAID;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,kBAFU;QAEV,SAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;EAFD;IACE,mBAFU;QAEV,UAFU;GAGX;CdmmCR;;AelpCD;EACE,YAAW;EACX,gBAAe;EACf,oBbgIW;Ea/HX,8BbuSyC;CalR1C;;AAzBD;;EAQI,iBbgSkC;Ea/RlC,oBAAmB;EACnB,8BbsCc;CarCf;;AAXH;EAcI,uBAAsB;EACtB,iCbiCc;CahCf;;AAhBH;EAmBI,8Bb6Bc;Ca5Bf;;AApBH;EAuBI,uBbuBS;CatBV;;AAQH;;EAGI,gBbsQiC;CarQlC;;AAQH;EACE,0BbGgB;CaUjB;;AAdD;;EAKI,0BbDc;CaEf;;AANH;;EAWM,yBAA8C;CAC/C;;AASL;EAEI,sCbXS;CaYV;;AAQH;EAGM,uCbvBO;CCjDY;;AaNvB;;;EAII,0BC4EmE;CD3EpE;;AAKH;EAKM,0BAJsC;CbLrB;;AaIvB;;EASQ,0BARoC;CASrC;;AApBP;;;EAII,0BC4EmE;CD3EpE;;AAKH;EAKM,0BAJsC;CbLrB;;AaIvB;;EASQ,0BARoC;CASrC;;AApBP;;;EAII,0BC4EmE;CD3EpE;;AAKH;EAKM,0BAJsC;CbLrB;;AaIvB;;EASQ,0BARoC;CASrC;;AApBP;;;EAII,0BC4EmE;CD3EpE;;AAKH;EAKM,0BAJsC;CbLrB;;AaIvB;;EASQ,0BARoC;CASrC;;AApBP;;;EAII,0BC4EmE;CD3EpE;;AAKH;EAKM,0BAJsC;CbLrB;;AaIvB;;EASQ,0BARoC;CASrC;;AApBP;;;EAII,0BC4EmE;CD3EpE;;AAKH;EAKM,0BAJsC;CbLrB;;AaIvB;;EASQ,0BARoC;CASrC;;AApBP;;;EAII,0BC4EmE;CD3EpE;;AAKH;EAKM,0BAJsC;CbLrB;;AaIvB;;EASQ,0BARoC;CASrC;;AApBP;;;EAII,0BC4EmE;CD3EpE;;AAKH;EAKM,0BAJsC;CbLrB;;AaIvB;;EASQ,0BARoC;CASrC;;AApBP;;;EAII,uCdmDO;CclDR;;AAKH;EAKM,uCAJsC;CbLrB;;AaIvB;;EASQ,uCARoC;CASrC;;ADgFT;EAEI,YbzDS;Ea0DT,0BbjDc;CakDf;;AAGH;EAEI,ebzDc;Ea0Dd,0Bb/Dc;CagEf;;AAGH;EACE,YbtEW;EauEX,0Bb9DgB;CauFjB;;AA3BD;;;EAOI,sBb+LoD;Ca9LrD;;AARH;EAWI,UAAS;CACV;;AAZH;EAgBM,4CbrFO;CasFR;;AAjBL;EAuBQ,6Cb5FK;CCvCY;;AU0DrB;EEsFJ;IAEI,eAAc;IACd,YAAW;IACX,iBAAgB;IAChB,6CAA4C;GAO/C;EAZD;IASM,UAAS;GACV;Cf2tCJ;;AkB13CD;EACE,eAAc;EACd,YAAW;EAGX,wBhB2TgC;EgB1ThC,gBhBiOmB;EgBhOnB,kBhB0T8B;EgBzT9B,ehB2CgB;EgB1ChB,uBhBmCW;EgBjCX,uBAAsB;EACtB,6BAA4B;EAC5B,sChByCW;EgBpCT,uBhB+L2B;EOlNzB,yEP6XqF;CgBtU1F;;AAtDD;EA6BI,8BAA6B;EAC7B,UAAS;CACV;;ACxBD;EACE,ejB2Cc;EiB1Cd,uBjBmCS;EiBlCT,sBjBiWiE;EiBhWjE,cAAa;CAEd;;ADbH;EAsCI,ehBYc;EgBVd,WAAU;CACX;;AAzCH;EAsCI,ehBYc;EgBVd,WAAU;CACX;;AAzCH;EAsCI,ehBYc;EgBVd,WAAU;CACX;;AAzCH;EAkDI,0BhBJc;EgBMd,WAAU;CACX;;AAGH;EAEI,4BhB0TkF;CgBzTnF;;AAHH;EAWI,ehBhBc;EgBiBd,uBhBxBS;CgByBV;;AAIH;;EAEE,eAAc;CACf;;AASD;EACE,oCAA2E;EAC3E,uCAA8E;EAC9E,iBAAgB;CACjB;;AAED;EACE,oCAA8E;EAC9E,uCAAiF;EACjF,mBhB0IsB;CgBzIvB;;AAED;EACE,qCAA8E;EAC9E,wCAAiF;EACjF,oBhBqIsB;CgBpIvB;;AASD;EACE,oBhBgN+B;EgB/M/B,uBhB+M+B;EgB9M/B,iBAAgB;EAChB,gBhBqHmB;CgBpHpB;;AAQD;EACE,oBhBmM+B;EgBlM/B,uBhBkM+B;EgBjM/B,iBAAgB;EAChB,kBhBkM8B;EgBjM9B,0BAAyB;EACzB,oBAAuC;CAOxC;;AAbD;;;;;EAUI,iBAAgB;EAChB,gBAAe;CAChB;;AAYH;;;EACE,wBhBgL+B;EgB/K/B,oBhBoFsB;EgBnFtB,iBhB+K6B;EMvU3B,sBNqN0B;CgB3D7B;;AAED;;;EAEI,8BhB2NqF;CgB1NtF;;AAGH;;;EACE,qBhBuK8B;EgBtK9B,mBhBsEsB;EgBrEtB,iBhBsK6B;EM3U3B,sBNoN0B;CgB7C7B;;AAED;;;EAEI,8BhBiNqF;CgBhNtF;;AASH;EACE,oBhBmNmC;CgBlNpC;;AAED;EACE,eAAc;EACd,oBhBqM+B;CgBpMhC;;AAOD;EACE,qBAAa;EAAb,cAAa;EACb,oBAAe;MAAf,gBAAe;EACf,mBAAkB;EAClB,kBAAiB;CAOlB;;AAXD;;EAQI,mBAAkB;EAClB,kBAAiB;CAClB;;AAQH;EACE,mBAAkB;EAClB,eAAc;EACd,sBhB0K+B;CgBnKhC;;AAVD;EAOM,ehBxKY;CgByKb;;AAIL;EACE,sBhBiKiC;EgBhKjC,iBAAgB;CACjB;;AAED;EACE,mBAAkB;EAClB,oBhB4JgC;EgB3JhC,sBhB0JiC;CgBrJlC;;AARD;EAMI,iBAAgB;CACjB;;AAIH;EACE,sBAAqB;CAStB;;AAVD;EAII,uBAAsB;CACvB;;AALH;EAQI,qBhB8I+B;CgB7IhC;;AAWH;EACE,cAAa;EACb,mBAAkB;EAClB,mBAAkB;EAClB,ehB/Le;CgBgMhB;;AAED;EACE,mBAAkB;EAClB,UAAS;EACT,WAAU;EACV,cAAa;EACb,aAAY;EACZ,eAAc;EACd,kBAAiB;EACjB,mBAAkB;EAClB,eAAc;EACd,YAAW;EACX,yChB7Me;EgB8Mf,qBAAoB;CACrB;;AClQG;;;EAEE,sBjBoDW;CiB1CZ;;AAZD;;;EAKI,iDjBiDS;CiBhDV;;AANH;;;;;;;;EAUI,eAAc;CACf;;AAOH;EAGI,ejBiCS;CiBhCV;;AAMH;EAGI,0CjBuBS;CiBtBV;;AAJH;EAMI,ejBoBS;CiBnBV;;AAMH;EAGI,sBjBUS;CiBPV;;AANH;EAKgB,sBAAqB;CAAK;;AAL1C;EAQI,iDjBKS;CiBJV;;AAlDH;;;EAEE,sBjBiDW;CiBvCZ;;AAZD;;;EAKI,iDjB8CS;CiB7CV;;AANH;;;;;;;;EAUI,eAAc;CACf;;AAOH;EAGI,ejB8BS;CiB7BV;;AAMH;EAGI,0CjBoBS;CiBnBV;;AAJH;EAMI,ejBiBS;CiBhBV;;AAMH;EAGI,sBjBOS;CiBJV;;AANH;EAKgB,sBAAqB;CAAK;;AAL1C;EAQI,iDjBES;CiBDV;;AD8NP;EACE,qBAAa;EAAb,cAAa;EACb,wBAAmB;MAAnB,oBAAmB;EACnB,uBAAmB;MAAnB,oBAAmB;CAuFpB;;AA1FD;EASI,YAAW;CACZ;;AL7PC;EKmPJ;IAeM,qBAAa;IAAb,cAAa;IACb,uBAAmB;QAAnB,oBAAmB;IACnB,sBAAuB;QAAvB,wBAAuB;IACvB,iBAAgB;GACjB;EAnBL;IAuBM,qBAAa;IAAb,cAAa;IACb,mBAAc;QAAd,eAAc;IACd,wBAAmB;QAAnB,oBAAmB;IACnB,uBAAmB;QAAnB,oBAAmB;IACnB,iBAAgB;GACjB;EA5BL;IAgCM,sBAAqB;IACrB,YAAW;IACX,uBAAsB;GACvB;EAnCL;IAuCM,sBAAqB;GACtB;EAxCL;IA2CM,YAAW;GACZ;EA5CL;IA+CM,iBAAgB;IAChB,uBAAsB;GACvB;EAjDL;IAsDM,qBAAa;IAAb,cAAa;IACb,uBAAmB;QAAnB,oBAAmB;IACnB,sBAAuB;QAAvB,wBAAuB;IACvB,YAAW;IACX,cAAa;IACb,iBAAgB;GACjB;EA5DL;IA8DM,gBAAe;GAChB;EA/DL;IAiEM,mBAAkB;IAClB,cAAa;IACb,sBhB2B4B;IgB1B5B,eAAc;GACf;EArEL;IAyEM,qBAAa;IAAb,cAAa;IACb,uBAAmB;QAAnB,oBAAmB;IACnB,sBAAuB;QAAvB,wBAAuB;IACvB,gBAAe;GAChB;EA7EL;IA+EM,iBAAgB;IAChB,sBAAqB;IACrB,sBhBa4B;IgBZ5B,4BAA2B;GAC5B;EAnFL;IAuFM,OAAM;GACP;ClBi3CJ;;AoB9uDD;EACE,sBAAqB;EACrB,oBlByOyB;EkBxOzB,mBAAkB;EAClB,oBAAmB;EACnB,uBAAsB;EACtB,0BAAiB;KAAjB,uBAAiB;MAAjB,sBAAiB;UAAjB,kBAAiB;EACjB,8BAAiD;ECiEjD,wBnBwPgC;EmBvPhC,gBnB8JmB;EmB7JnB,kBnBuP8B;EMnU5B,uBNmN2B;EOlNzB,kCP0V+C;CkBxTpD;;AjBjBG;EiBHA,sBAAqB;CjBMpB;;AiBnBL;EAiBI,WAAU;EACV,8ClBkDa;CkBjDd;;AAnBH;EAwBI,aAAY;CAEb;;AA1BH;EA8BI,uBAAsB;CAEvB;;AAIH;;EAEE,qBAAoB;CACrB;;AAQC;EHQE,YAAW;EItDb,0BnBmEe;EmBlEf,sBnBkEe;CkBnBd;;AC5CD;EJkDE,YAAW;EIhDX,0BARqF;EASrF,sBAT2H;CAU5H;;AAED;EAMI,6CnBmDW;CmBjDd;;AAGD;EAEE,0BnB4Ca;EmB3Cb,sBnB2Ca;CmB1Cd;;AAED;;EAGE,0BAhCqF;EAiCrF,uBAAsB;EACtB,sBAlC2H;CAoC5H;;ADYD;EHQE,YAAW;EItDb,0BnBiDgB;EmBhDhB,sBnBgDgB;CkBDf;;AC5CD;EJkDE,YAAW;EIhDX,0BARqF;EASrF,sBAT2H;CAU5H;;AAED;EAMI,+CnBiCY;CmB/Bf;;AAGD;EAEE,0BnB0Bc;EmBzBd,sBnByBc;CmBxBf;;AAED;;EAGE,0BAhCqF;EAiCrF,uBAAsB;EACtB,sBAlC2H;CAoC5H;;ADYD;EHQE,YAAW;EItDb,0BnB0Ee;EmBzEf,sBnByEe;CkB1Bd;;AC5CD;EJkDE,YAAW;EIhDX,0BARqF;EASrF,sBAT2H;CAU5H;;AAED;EAMI,6CnB0DW;CmBxDd;;AAGD;EAEE,0BnBmDa;EmBlDb,sBnBkDa;CmBjDd;;AAED;;EAGE,0BAhCqF;EAiCrF,uBAAsB;EACtB,sBAlC2H;CAoC5H;;ADYD;EHQE,YAAW;EItDb,0BnB4Ee;EmB3Ef,sBnB2Ee;CkB5Bd;;AC5CD;EJkDE,YAAW;EIhDX,0BARqF;EASrF,sBAT2H;CAU5H;;AAED;EAMI,8CnB4DW;CmB1Dd;;AAGD;EAEE,0BnBqDa;EmBpDb,sBnBoDa;CmBnDd;;AAED;;EAGE,0BAhCqF;EAiCrF,uBAAsB;EACtB,sBAlC2H;CAoC5H;;ADYD;EHME,YAAW;EIpDb,0BnByEe;EmBxEf,sBnBwEe;CkBzBd;;AC5CD;EJgDE,YAAW;EI9CX,0BARqF;EASrF,sBAT2H;CAU5H;;AAED;EAMI,6CnByDW;CmBvDd;;AAGD;EAEE,0BnBkDa;EmBjDb,sBnBiDa;CmBhDd;;AAED;;EAGE,0BAhCqF;EAiCrF,uBAAsB;EACtB,sBAlC2H;CAoC5H;;ADYD;EHQE,YAAW;EItDb,0BnBuEe;EmBtEf,sBnBsEe;CkBvBd;;AC5CD;EJkDE,YAAW;EIhDX,0BARqF;EASrF,sBAT2H;CAU5H;;AAED;EAMI,6CnBuDW;CmBrDd;;AAGD;EAEE,0BnBgDa;EmB/Cb,sBnB+Ca;CmB9Cd;;AAED;;EAGE,0BAhCqF;EAiCrF,uBAAsB;EACtB,sBAlC2H;CAoC5H;;ADYD;EHME,YAAW;EIpDb,0BnB4CgB;EmB3ChB,sBnB2CgB;CkBIf;;AC5CD;EJgDE,YAAW;EI9CX,0BARqF;EASrF,sBAT2H;CAU5H;;AAED;EAMI,+CnB4BY;CmB1Bf;;AAGD;EAEE,0BnBqBc;EmBpBd,sBnBoBc;CmBnBf;;AAED;;EAGE,0BAhCqF;EAiCrF,uBAAsB;EACtB,sBAlC2H;CAoC5H;;ADYD;EHQE,YAAW;EItDb,0BnBmDgB;EmBlDhB,sBnBkDgB;CkBHf;;AC5CD;EJkDE,YAAW;EIhDX,0BARqF;EASrF,sBAT2H;CAU5H;;AAED;EAMI,4CnBmCY;CmBjCf;;AAGD;EAEE,0BnB4Bc;EmB3Bd,sBnB2Bc;CmB1Bf;;AAED;;EAGE,0BAhCqF;EAiCrF,uBAAsB;EACtB,sBAlC2H;CAoC5H;;ADkBD;ECdA,enB6Be;EmB5Bf,8BAA6B;EAC7B,uBAAsB;EACtB,sBnB0Be;CkBbd;;AjBlDC;EkBwCA,YDS4C;ECR5C,0BnBsBa;EmBrBb,sBnBqBa;CC/DQ;;AkB6CvB;EAEE,6CnBgBa;CmBfd;;AAED;EAEE,enBWa;EmBVb,8BAA6B;CAC9B;;AAED;;EAGE,YDV4C;ECW5C,0BnBGa;EmBFb,sBnBEa;CmBDd;;ADdD;ECdA,enBWgB;EmBVhB,8BAA6B;EAC7B,uBAAsB;EACtB,sBnBQgB;CkBKf;;AjBlDC;EkBwCA,YDS4C;ECR5C,0BnBIc;EmBHd,sBnBGc;CC7CO;;AkB6CvB;EAEE,+CnBFc;CmBGf;;AAED;EAEE,enBPc;EmBQd,8BAA6B;CAC9B;;AAED;;EAGE,YDV4C;ECW5C,0BnBfc;EmBgBd,sBnBhBc;CmBiBf;;ADdD;ECdA,enBoCe;EmBnCf,8BAA6B;EAC7B,uBAAsB;EACtB,sBnBiCe;CkBpBd;;AjBlDC;EkBwCA,YDS4C;ECR5C,0BnB6Ba;EmB5Bb,sBnB4Ba;CCtEQ;;AkB6CvB;EAEE,6CnBuBa;CmBtBd;;AAED;EAEE,enBkBa;EmBjBb,8BAA6B;CAC9B;;AAED;;EAGE,YDV4C;ECW5C,0BnBUa;EmBTb,sBnBSa;CmBRd;;ADdD;ECdA,enBsCe;EmBrCf,8BAA6B;EAC7B,uBAAsB;EACtB,sBnBmCe;CkBtBd;;AjBlDC;EkBwCA,YDS4C;ECR5C,0BnB+Ba;EmB9Bb,sBnB8Ba;CCxEQ;;AkB6CvB;EAEE,8CnByBa;CmBxBd;;AAED;EAEE,enBoBa;EmBnBb,8BAA6B;CAC9B;;AAED;;EAGE,YDV4C;ECW5C,0BnBYa;EmBXb,sBnBWa;CmBVd;;ADdD;ECdA,enBmCe;EmBlCf,8BAA6B;EAC7B,uBAAsB;EACtB,sBnBgCe;CkBnBd;;AjBlDC;EkBwCA,YDS4C;ECR5C,0BnB4Ba;EmB3Bb,sBnB2Ba;CCrEQ;;AkB6CvB;EAEE,6CnBsBa;CmBrBd;;AAED;EAEE,enBiBa;EmBhBb,8BAA6B;CAC9B;;AAED;;EAGE,YDV4C;ECW5C,0BnBSa;EmBRb,sBnBQa;CmBPd;;ADdD;ECdA,enBiCe;EmBhCf,8BAA6B;EAC7B,uBAAsB;EACtB,sBnB8Be;CkBjBd;;AjBlDC;EkBwCA,YDS4C;ECR5C,0BnB0Ba;EmBzBb,sBnByBa;CCnEQ;;AkB6CvB;EAEE,6CnBoBa;CmBnBd;;AAED;EAEE,enBea;EmBdb,8BAA6B;CAC9B;;AAED;;EAGE,YDV4C;ECW5C,0BnBOa;EmBNb,sBnBMa;CmBLd;;ADdD;ECdA,enBMgB;EmBLhB,8BAA6B;EAC7B,uBAAsB;EACtB,sBnBGgB;CkBUf;;AjBlDC;EkBwCA,YDS4C;ECR5C,0BnBDc;EmBEd,sBnBFc;CCxCO;;AkB6CvB;EAEE,+CnBPc;CmBQf;;AAED;EAEE,enBZc;EmBad,8BAA6B;CAC9B;;AAED;;EAGE,YDV4C;ECW5C,0BnBpBc;EmBqBd,sBnBrBc;CmBsBf;;ADdD;ECdA,enBagB;EmBZhB,8BAA6B;EAC7B,uBAAsB;EACtB,sBnBUgB;CkBGf;;AjBlDC;EkBwCA,YDS4C;ECR5C,0BnBMc;EmBLd,sBnBKc;CC/CO;;AkB6CvB;EAEE,4CnBAc;CmBCf;;AAED;EAEE,enBLc;EmBMd,8BAA6B;CAC9B;;AAED;;EAGE,YDV4C;ECW5C,0BnBbc;EmBcd,sBnBdc;CmBef;;ADHH;EACE,oBlB0KyB;EkBzKzB,elBEe;EkBDf,iBAAgB;CA8BjB;;AAjCD;EASI,8BAA6B;CAE9B;;AAXH;EAeI,0BAAyB;EACzB,iBAAgB;CACjB;;AjB5EC;EiB8EA,0BAAyB;CjB9EJ;;AAWrB;EiBsEA,elB0E4C;EkBzE5C,2BlB0E6B;EkBzE7B,8BAA6B;CjBrE5B;;AiB6CL;EA2BI,elBzCc;CkB8Cf;;AjBhFC;EiB8EE,sBAAqB;CjB3EtB;;AiBqFL;EChCE,qBnBgQ8B;EmB/P9B,mBnB+JsB;EmB9JtB,iBnBkI0B;EM9MxB,sBNoN0B;CkBxG7B;;AAED;ECpCE,wBnB4P+B;EmB3P/B,oBnBgKsB;EmB/JtB,iBnBmI0B;EM/MxB,sBNqN0B;CkBrG7B;;AAOD;EACE,eAAc;EACd,YAAW;CACZ;;AAGD;EACE,mBlBsNoC;CkBrNrC;;AAGD;;;EAII,YAAW;CACZ;;AE3IH;EACE,WAAU;EbIN,iCP4NsC;CoB1N3C;;AAPD;EAKI,WAAU;CACX;;AAGH;EACE,cAAa;CAId;;AALD;EAGI,eAAc;CACf;;AAGH;EAEI,mBAAkB;CACnB;;AAGH;EAEI,yBAAwB;CACzB;;AAGH;EACE,mBAAkB;EAClB,UAAS;EACT,iBAAgB;Eb1BZ,8BP6NmC;CoBjMxC;;AChCD;;EAEE,mBAAkB;CACnB;;AAED;EAGI,sBAAqB;EACrB,SAAQ;EACR,UAAS;EACT,qBAA+B;EAC/B,wBAAkC;EAClC,YAAW;EACX,wBAA8B;EAC9B,sCAA4C;EAC5C,qCAA2C;CAC5C;;AAZH;EAeI,eAAc;CACf;;AAKH;EAEI,cAAa;EACb,wBrB+coC;CqB9crC;;AAJH;EAQM,cAAa;EACb,2BAAiC;CAClC;;AAKL;EACE,mBAAkB;EAClB,UAAS;EACT,QAAO;EACP,crB0d8B;EqBzd9B,cAAa;EACb,YAAW;EACX,iBrB0boC;EqBzbpC,kBAA8B;EAC9B,qBAA4B;EAC5B,gBrByLmB;EqBxLnB,erBMgB;EqBLhB,iBAAgB;EAChB,iBAAgB;EAChB,uBrBNW;EqBOX,6BAA4B;EAC5B,sCrBEW;EMxDT,uBNmN2B;CqB1J9B;;AAGD;EC3DE,UAAS;EACT,iBAAuB;EACvB,iBAAgB;EAChB,8BtB4CgB;CqBcjB;;AAKD;EACE,eAAc;EACd,YAAW;EACX,wBrBobqC;EqBnbrC,YAAW;EACX,oBrBqKyB;EqBpKzB,erBlBgB;EqBmBhB,oBAAmB;EACnB,oBAAmB;EACnB,iBAAgB;EAChB,UAAS;CAwBV;;ApBnFG;EoB8DA,erBiakD;EqBhalD,sBAAqB;EACrB,0BrBnCc;CC1Bb;;AoB8CL;EAoBI,YrBzCS;EqB0CT,sBAAqB;EACrB,0BrBnBa;CqBoBd;;AAvBH;EA2BI,erB1Cc;EqB2Cd,8BAA6B;CAK9B;;AAIH;EAGI,WAAU;CACX;;AAGH;EACE,eAAc;CACf;;AAGD;EACE,eAAc;EACd,uBrBoYqC;EqBnYrC,iBAAgB;EAChB,oBrBmHsB;EqBlHtB,erBrEgB;EqBsEhB,oBAAmB;CACpB;;AE5HD;;EAEE,mBAAkB;EAClB,4BAAoB;EAApB,qBAAoB;EACpB,uBAAsB;CA0BvB;;AA9BD;;EAOI,mBAAkB;EAClB,mBAAc;MAAd,eAAc;EACd,iBAAgB;CAYjB;;AArBH;;EAcM,WAAU;CtBNS;;AsBRzB;;;;EAmBM,WAAU;CACX;;AApBL;;;;;;;;EA4BI,kBvBsLc;CuBrLf;;AAIH;EACE,qBAAa;EAAb,cAAa;EACb,oBAAe;MAAf,gBAAe;EACf,qBAA2B;MAA3B,4BAA2B;CAK5B;;AARD;EAMI,YAAW;CACZ;;AAGH;EACE,iBAAgB;CACjB;;AAGD;EACE,eAAc;CAKf;;AAND;EjBlCI,2BiBsC8B;EjBrC9B,8BiBqC8B;CAC/B;;AAGH;;EjB5BI,0BiB8B2B;EjB7B3B,6BiB6B2B;CAC9B;;AAGD;EACE,YAAW;CACZ;;AACD;EACE,iBAAgB;CACjB;;AACD;;EjBtDI,2BiByD8B;EjBxD9B,8BiBwD8B;CAC/B;;AAEH;EjB9CI,0BiB+C2B;EjB9C3B,6BiB8C2B;CAC9B;;AAeD;EACE,yBAAyC;EACzC,wBAAwC;CAKzC;;AAPD;EAKI,eAAc;CACf;;AAGH;EACE,wBAA4C;EAC5C,uBAA2C;CAC5C;;AAED;EACE,uBAA4C;EAC5C,sBAA2C;CAC5C;;AAmBD;EACE,4BAAoB;EAApB,qBAAoB;EACpB,2BAAsB;MAAtB,uBAAsB;EACtB,sBAAuB;MAAvB,wBAAuB;EACvB,sBAAuB;MAAvB,wBAAuB;CAcxB;;AAlBD;;EAQI,YAAW;CACZ;;AATH;;;;EAeI,iBvBoEc;EuBnEd,eAAc;CACf;;AAGH;EAEI,iBAAgB;CACjB;;AAHH;EjB9HI,8BiBmI+B;EjBlI/B,6BiBkI+B;CAChC;;AANH;EjB5II,0BiBoJ4B;EjBnJ5B,2BiBmJ4B;CAC7B;;AAEH;EACE,iBAAgB;CACjB;;AACD;;EjB5II,8BiB+I+B;EjB9I/B,6BiB8I+B;CAChC;;AAEH;EjBhKI,0BiBiK0B;EjBhK1B,2BiBgK0B;CAC7B;;AzBu5ED;;;;EyBn4EM,mBAAkB;EAClB,uBAAmB;EACnB,qBAAoB;CACrB;;AC/LL;EACE,mBAAkB;EAClB,qBAAa;EAAb,cAAa;EACb,YAAW;CAkBZ;;AArBD;EAQI,mBAAkB;EAClB,WAAU;EACV,mBAAc;MAAd,eAAc;EAGd,UAAS;EACT,iBAAgB;CAMjB;;AApBH;EAkBM,WAAU;CvBmCX;;AuB9BL;;;EAIE,qBAAa;EAAb,cAAa;EACb,uBAAmB;MAAnB,oBAAmB;CAKpB;;AAVD;;;ElBvBI,iBkB+BwB;CACzB;;AAGH;;EAEE,oBAAmB;EACnB,uBAAsB;CACvB;;AAwBD;EACE,wBxBkQgC;EwBjQhC,iBAAgB;EAChB,gBxBuKmB;EwBtKnB,oBxB0KyB;EwBzKzB,kBxB+P8B;EwB9P9B,exBhBgB;EwBiBhB,mBAAkB;EAClB,0BxBvBgB;EwBwBhB,sCxBhBW;EMxDT,uBNmN2B;CwBpH9B;;AAhCD;;;EAcI,wBxByP6B;EwBxP7B,oBxB6JoB;EM3OpB,sBNqN0B;CwBrI3B;;AAjBH;;;EAoBI,qBxBuP4B;EwBtP5B,mBxBsJoB;EM1OpB,sBNoN0B;CwB9H3B;;AAvBH;;EA6BI,cAAa;CACd;;AASH;;;;;;;ElBzFI,2BkBgG4B;ElB/F5B,8BkB+F4B;CAC/B;;AACD;EACE,gBAAe;CAChB;;AACD;;;;;;;ElBvFI,0BkB8F2B;ElB7F3B,6BkB6F2B;CAC9B;;AACD;EACE,eAAc;CACf;;AAMD;EACE,mBAAkB;EAGlB,aAAY;EACZ,oBAAmB;CAmCpB;;AAxCD;EAUI,mBAAkB;CAUnB;;AApBH;EAaM,kBxBiEY;CwBhEb;;AAdL;EAkBM,WAAU;CvBhGX;;AuB8EL;;EA0BM,mBxBoDY;CwBnDb;;AA3BL;;EAgCM,WAAU;EACV,kBxB6CY;CwBxCb;;AAtCL;;;;EAoCQ,WAAU;CvBlHb;;AwB9CL;EACE,mBAAkB;EAClB,4BAAoB;EAApB,qBAAoB;EACpB,mBAAsC;EACtC,qBzBmY8B;EyBlY9B,mBzBoY4B;CyBnY7B;;AAED;EACE,mBAAkB;EAClB,YAAW;EACX,WAAU;CA4BX;;AA/BD;EAMI,YzByBS;EyBxBT,0BzBgDa;CyB9Cd;;AATH;EAaI,8CzB0Ca;CyBzCd;;AAdH;EAiBI,YzBcS;EyBbT,0BzBgY6E;CyB9X9E;;AApBH;EAwBM,0BzBSY;CyBRb;;AAzBL;EA4BM,ezBSY;CyBRb;;AAQL;EACE,mBAAkB;EAClB,aAA+D;EAC/D,QAAO;EACP,eAAc;EACd,YzByVwC;EyBxVxC,azBwVwC;EyBvVxC,qBAAoB;EACpB,0BAAiB;KAAjB,uBAAiB;MAAjB,sBAAiB;UAAjB,kBAAiB;EACjB,uBzBsVwC;EyBrVxC,6BAA4B;EAC5B,mCAAkC;EAClC,yBzBoV2C;CyBlV5C;;AAMD;EnBxEI,uBNmN2B;CyBxI5B;;AAHH;EAMI,2NVtCuI;CUuCxI;;AAPH;EAUI,0BzBZa;EyBab,wKV3CuI;CU6CxI;;AAOH;EAEI,mBzB8UsC;CyB7UvC;;AAHH;EAMI,qKV1DuI;CU2DxI;;AASH;EACE,qBAAa;EAAb,cAAa;EACb,2BAAsB;MAAtB,uBAAsB;CASvB;;AAXD;EAKI,uBzB8R4B;CyBzR7B;;AAVH;EAQM,eAAc;CACf;;AAWL;EACE,sBAAqB;EACrB,gBAAe;EACf,4BzBmPoF;EyBlPpF,2CzB4SuC;EyB3SvC,kBzB8L8B;EyB7L9B,ezBjFgB;EyBkFhB,uBAAsB;EACtB,oNAAsG;EACtG,0BzB+SoC;EyB9SpC,sCzBlFW;EyBoFT,uBzBuE2B;EyBnE7B,yBAAgB;KAAhB,sBAAgB;UAAhB,iBAAgB;CA2BjB;;AA3CD;EAmBI,sBzB4SmE;EyB3SnE,cAAa;CAYd;;AAhCH;EA6BM,ezBxGY;EyByGZ,uBzBhHO;CyBiHR;;AA/BL;EAmCI,ezB/Gc;EyBgHd,0BzBpHc;CyBqHf;;AArCH;EAyCI,WAAU;CACX;;AAGH;EACE,8BzB2MuF;EyB1MvF,sBzBgQwC;EyB/PxC,yBzB+PwC;EyB9PxC,ezBiR+B;CyBhRhC;;AAOD;EACE,mBAAkB;EAClB,sBAAqB;EACrB,gBAAe;EACf,ezBwQmC;EyBvQnC,iBAAgB;CACjB;;AAED;EACE,iBzBoQkC;EyBnQlC,gBAAe;EACf,ezBiQmC;EyBhQnC,UAAS;EACT,WAAU;CAKX;;AAED;EACE,mBAAkB;EAClB,OAAM;EACN,SAAQ;EACR,QAAO;EACP,WAAU;EACV,ezBkPmC;EyBjPnC,qBzBqP8B;EyBpP9B,iBzBsP6B;EyBrP7B,ezBjKgB;EyBkKhB,qBAAoB;EACpB,0BAAiB;KAAjB,uBAAiB;MAAjB,sBAAiB;UAAjB,kBAAiB;EACjB,uBzB3KW;EyB4KX,sCzBlKW;EMxDT,uBNmN2B;CyBsC9B;;AA5CD;EAmBM,0BzBsPkB;CyBrPnB;;AApBL;EAwBI,mBAAkB;EAClB,UzBrBc;EyBsBd,YzBtBc;EyBuBd,azBvBc;EyBwBd,WAAU;EACV,eAAc;EACd,ezB0NiC;EyBzNjC,qBzB6N4B;EyB5N5B,iBzB8N2B;EyB7N3B,ezBzLc;EyB0Ld,0BzB/Lc;EyBgMd,sCzBxLS;EMxDT,mCmBiPgF;CACjF;;AArCH;EAyCM,kBzBmOU;CyBlOX;;ACtPL;EACE,qBAAa;EAAb,cAAa;EACb,oBAAe;MAAf,gBAAe;EACf,gBAAe;EACf,iBAAgB;EAChB,iBAAgB;CACjB;;AAED;EACE,eAAc;EACd,qB1BogBkC;C0B1fnC;;AzBHG;EyBJA,sBAAqB;CzBOpB;;AyBZL;EAUI,e1BiCc;C0BhCf;;AAOH;EACE,8B1BsfgD;C0BpdjD;;AAnCD;EAII,oB1BkLc;C0BjLf;;AALH;EAQI,8BAAgD;EpB7BhD,gCN6M2B;EM5M3B,iCN4M2B;C0BpK5B;;AApBH;EAYM,mC1B2e4C;CC7f7C;;AyBML;EAgBM,e1BSY;E0BRZ,8BAA6B;EAC7B,0BAAyB;CAC1B;;AAnBL;;EAwBI,e1BEc;E0BDd,uB1BNS;E0BOT,6B1BPS;C0BQV;;AA3BH;EA+BI,iB1BuJc;EM3Md,0BoBsD4B;EpBrD5B,2BoBqD4B;CAC7B;;AAQH;EpBrEI,uBNmN2B;C0BrI5B;;AATH;;EAMM,Y1B7BO;E0B8BP,0B1BNW;C0BOZ;;AASL;EAEI,mBAAc;MAAd,eAAc;EACd,mBAAkB;CACnB;;AAGH;EAEI,2BAAa;MAAb,cAAa;EACb,qBAAY;MAAZ,aAAY;EACZ,mBAAkB;CACnB;;AAQH;EAEI,cAAa;CACd;;AAHH;EAKI,eAAc;CACf;;ACnGH;EACE,mBAAkB;EAClB,qBAAa;EAAb,cAAa;EACb,oBAAe;MAAf,gBAAe;EACf,uBAAmB;MAAnB,oBAAmB;EACnB,uBAA8B;MAA9B,+BAA8B;EAC9B,qB3BgHW;C2BrGZ;;AAjBD;;EAYI,qBAAa;EAAb,cAAa;EACb,oBAAe;MAAf,gBAAe;EACf,uBAAmB;MAAnB,oBAAmB;EACnB,uBAA8B;MAA9B,+BAA8B;CAC/B;;AAQH;EACE,sBAAqB;EACrB,uB3BggB+E;E2B/f/E,0B3B+f+E;E2B9f/E,mB3B0FW;E2BzFX,mB3BgMsB;E2B/LtB,qBAAoB;EACpB,oBAAmB;CAKpB;;A1B/BG;E0B6BA,sBAAqB;C1B1BpB;;A0BmCL;EACE,qBAAa;EAAb,cAAa;EACb,2BAAsB;MAAtB,uBAAsB;EACtB,gBAAe;EACf,iBAAgB;EAChB,iBAAgB;CAWjB;;AAhBD;EAQI,iBAAgB;EAChB,gBAAe;CAChB;;AAVH;EAaI,iBAAgB;EAChB,YAAW;CACZ;;AAQH;EACE,sBAAqB;EACrB,oB3B6bmC;E2B5bnC,uB3B4bmC;C2B3bpC;;AAWD;EACE,8BAAgB;MAAhB,iBAAgB;EAGhB,uBAAmB;MAAnB,oBAAmB;CACpB;;AAGD;EACE,yB3BmcyC;E2BlczC,mB3BkIsB;E2BjItB,eAAc;EACd,wBAAuB;EACvB,8BAAuC;ErB3GrC,uBNmN2B;C2BlG9B;;A1B/FG;E0B6FA,sBAAqB;C1B1FpB;;A0BgGL;EACE,sBAAqB;EACrB,aAAY;EACZ,cAAa;EACb,uBAAsB;EACtB,YAAW;EACX,oCAAmC;EACnC,2BAA0B;CAC3B;;AhB5DG;EgBqEA;;IAIM,iBAAgB;IAChB,gBAAe;GAChB;C7B46FR;;AapgGG;EgBkFA;IAUI,wBAAmB;QAAnB,oBAAmB;IACnB,sBAAiB;QAAjB,kBAAiB;IACjB,qBAA2B;QAA3B,4BAA2B;GAoC9B;EAhDD;IAeM,wBAAmB;QAAnB,oBAAmB;GAepB;EA9BL;IAkBQ,mBAAkB;GACnB;EAnBP;IAsBQ,SAAQ;IACR,WAAU;GACX;EAxBP;IA2BQ,qBAAoB;IACpB,oBAAmB;GACpB;EA7BP;;IAmCM,sBAAiB;QAAjB,kBAAiB;GAClB;EApCL;IAwCM,gCAAwB;IAAxB,yBAAwB;GACzB;EAzCL;IA6CM,cAAa;GACd;C7Bo6FR;;AavhGG;EgBqEA;;IAIM,iBAAgB;IAChB,gBAAe;GAChB;C7Bo9FR;;Aa5iGG;EgBkFA;IAUI,wBAAmB;QAAnB,oBAAmB;IACnB,sBAAiB;QAAjB,kBAAiB;IACjB,qBAA2B;QAA3B,4BAA2B;GAoC9B;EAhDD;IAeM,wBAAmB;QAAnB,oBAAmB;GAepB;EA9BL;IAkBQ,mBAAkB;GACnB;EAnBP;IAsBQ,SAAQ;IACR,WAAU;GACX;EAxBP;IA2BQ,qBAAoB;IACpB,oBAAmB;GACpB;EA7BP;;IAmCM,sBAAiB;QAAjB,kBAAiB;GAClB;EApCL;IAwCM,gCAAwB;IAAxB,yBAAwB;GACzB;EAzCL;IA6CM,cAAa;GACd;C7B48FR;;Aa/jGG;EgBqEA;;IAIM,iBAAgB;IAChB,gBAAe;GAChB;C7B4/FR;;AaplGG;EgBkFA;IAUI,wBAAmB;QAAnB,oBAAmB;IACnB,sBAAiB;QAAjB,kBAAiB;IACjB,qBAA2B;QAA3B,4BAA2B;GAoC9B;EAhDD;IAeM,wBAAmB;QAAnB,oBAAmB;GAepB;EA9BL;IAkBQ,mBAAkB;GACnB;EAnBP;IAsBQ,SAAQ;IACR,WAAU;GACX;EAxBP;IA2BQ,qBAAoB;IACpB,oBAAmB;GACpB;EA7BP;;IAmCM,sBAAiB;QAAjB,kBAAiB;GAClB;EApCL;IAwCM,gCAAwB;IAAxB,yBAAwB;GACzB;EAzCL;IA6CM,cAAa;GACd;C7Bo/FR;;AavmGG;EgBqEA;;IAIM,iBAAgB;IAChB,gBAAe;GAChB;C7BoiGR;;Aa5nGG;EgBkFA;IAUI,wBAAmB;QAAnB,oBAAmB;IACnB,sBAAiB;QAAjB,kBAAiB;IACjB,qBAA2B;QAA3B,4BAA2B;GAoC9B;EAhDD;IAeM,wBAAmB;QAAnB,oBAAmB;GAepB;EA9BL;IAkBQ,mBAAkB;GACnB;EAnBP;IAsBQ,SAAQ;IACR,WAAU;GACX;EAxBP;IA2BQ,qBAAoB;IACpB,oBAAmB;GACpB;EA7BP;;IAmCM,sBAAiB;QAAjB,kBAAiB;GAClB;EApCL;IAwCM,gCAAwB;IAAxB,yBAAwB;GACzB;EAzCL;IA6CM,cAAa;GACd;C7B4hGR;;A6B/kGD;EAeQ,wBAAmB;MAAnB,oBAAmB;EACnB,sBAAiB;MAAjB,kBAAiB;EACjB,qBAA2B;MAA3B,4BAA2B;CAoC9B;;AArDL;;EASU,iBAAgB;EAChB,gBAAe;CAChB;;AAXT;EAoBU,wBAAmB;MAAnB,oBAAmB;CAepB;;AAnCT;EAuBY,mBAAkB;CACnB;;AAxBX;EA2BY,SAAQ;EACR,WAAU;CACX;;AA7BX;EAgCY,qBAAoB;EACpB,oBAAmB;CACpB;;AAlCX;;EAwCU,sBAAiB;MAAjB,kBAAiB;CAClB;;AAzCT;EA6CU,gCAAwB;EAAxB,yBAAwB;CACzB;;AA9CT;EAkDU,cAAa;CACd;;AAYT;EAEI,0B3B1IS;C2B+IV;;AAPH;EAKM,0B3B7IO;CCnCR;;A0B2KL;EAWM,0B3BnJO;C2B4JR;;AApBL;EAcQ,0B3BtJK;CCnCR;;A0B2KL;EAkBQ,0B3B1JK;C2B2JN;;AAnBP;;;;EA0BM,0B3BlKO;C2BmKR;;AA3BL;EA+BI,0B3BvKS;E2BwKT,iC3BxKS;C2ByKV;;AAjCH;EAoCI,sQ3BqV8R;C2BpV/R;;AArCH;EAwCI,0B3BhLS;C2BiLV;;AAIH;EAEI,a3BjMS;C2BsMV;;AAPH;EAKM,a3BpMO;CCzBR;;A0BwNL;EAWM,gC3B1MO;C2BmNR;;AApBL;EAcQ,iC3B7MK;CCzBR;;A0BwNL;EAkBQ,iC3BjNK;C2BkNN;;AAnBP;;;;EA0BM,a3BzNO;C2B0NR;;AA3BL;EA+BI,gC3B9NS;E2B+NT,uC3B/NS;C2BgOV;;AAjCH;EAoCI,4Q3BiS4R;C2BhS7R;;AArCH;EAwCI,gC3BvOS;C2BwOV;;ACtRH;EACE,mBAAkB;EAClB,qBAAa;EAAb,cAAa;EACb,2BAAsB;MAAtB,uBAAsB;EACtB,aAAY;EACZ,sBAAqB;EACrB,uB5BwCW;E4BvCX,4BAA2B;EAC3B,uC5BgDW;EMxDT,uBNmN2B;C4BzM9B;;AAED;EAGE,mBAAc;MAAd,eAAc;EACd,iB5BilBgC;C4BhlBjC;;AAED;EACE,uB5B4kB+B;C4B3kBhC;;AAED;EACE,sBAAgC;EAChC,iBAAgB;CACjB;;AAED;EACE,iBAAgB;CACjB;;A3BvBG;E2B2BA,sBAAqB;C3B3BA;;A2ByBzB;EAMI,qB5B2jB8B;C4B1jB/B;;AAGH;EtBpCI,gCN6M2B;EM5M3B,iCN4M2B;C4BrK1B;;AAJL;EtBtBI,oCN+L2B;EM9L3B,mCN8L2B;C4B/J1B;;AASL;EACE,yB5BmiBgC;E4BliBhC,iBAAgB;EAChB,sC5BRW;E4BSX,8C5BTW;C4BcZ;;AATD;EtB7DI,2DsBoE8E;CAC/E;;AAGH;EACE,yB5BwhBgC;E4BvhBhC,sC5BlBW;E4BmBX,2C5BnBW;C4BwBZ;;AARD;EtBxEI,2DNqmB2E;C4BthB5E;;AAQH;EACE,wBAAkC;EAClC,wB5BugB+B;E4BtgB/B,uBAAiC;EACjC,iBAAgB;CACjB;;AAED;EACE,wBAAkC;EAClC,uBAAiC;CAClC;;AAGD;EACE,mBAAkB;EAClB,OAAM;EACN,SAAQ;EACR,UAAS;EACT,QAAO;EACP,iB5B+fgC;C4B9fjC;;AAED;EACE,YAAW;EtB9GT,mCNqmB2E;C4Brf9E;;AAGD;EACE,YAAW;EtB9GT,4CN+lB2E;EM9lB3E,6CN8lB2E;C4B/e9E;;AAED;EACE,YAAW;EtBrGT,gDNilB2E;EMhlB3E,+CNglB2E;C4B1e9E;;AjBvEG;EiB6EF;IACE,qBAAa;IAAb,cAAa;IACb,wBAAmB;QAAnB,oBAAmB;IACnB,oB5BuegD;I4BtehD,mB5BsegD;G4B7djD;EAbD;IAOI,qBAAa;IAAb,cAAa;IACb,iBAAY;QAAZ,aAAY;IACZ,2BAAsB;QAAtB,uBAAsB;IACtB,mB5Bge8C;I4B/d9C,kB5B+d8C;G4B9d/C;C9ByzGJ;;Aal5GG;EiBmGF;IACE,qBAAa;IAAb,cAAa;IACb,wBAAmB;QAAnB,oBAAmB;GA2CpB;EA7CD;IAKI,iBAAY;QAAZ,aAAY;GAuCb;EA5CH;IAQM,eAAc;IACd,eAAc;GACf;EAVL;ItB1IE,2BsByJoC;ItBxJpC,8BsBwJoC;GAQ/B;EAvBP;IAkBU,2BAA0B;GAC3B;EAnBT;IAqBU,8BAA6B;GAC9B;EAtBT;ItB5HE,0BsBqJmC;ItBpJnC,6BsBoJmC;GAQ9B;EAjCP;IA4BU,0BAAyB;GAC1B;EA7BT;IA+BU,6BAA4B;GAC7B;EAhCT;IAoCQ,iBAAgB;GAMjB;EA1CP;;IAwCU,iBAAgB;GACjB;C9B+yGV;;A8BnyGD;EAEI,uB5BkZ6B;C4BjZ9B;;AjB3JC;EiBwJJ;IAMI,wB5B2ZyB;Y4B3ZzB,gB5B2ZyB;I4B1ZzB,4B5B2Z+B;Y4B3Z/B,oB5B2Z+B;G4BpZlC;EAdD;IAUM,sBAAqB;IACrB,YAAW;GACZ;C9BsyGJ;;A+BlgHD;EACE,sB7BixBkC;E6BhxBlC,oBAAmB;EACnB,iBAAgB;EAChB,0B7BgDgB;EMhDd,uBNmN2B;C6BhN9B;;ACNC;EACE,eAAc;EACd,YAAW;EACX,YAAW;CACZ;;ADIH;EACE,YAAW;CA2BZ;;AA5BD;EAKI,sBAAqB;EACrB,sB7BowBiC;E6BnwBjC,qB7BmwBiC;E6BlwBjC,e7BuCc;E6BtCd,aAAiC;CAClC;;AAVH;EAmBI,2BAA0B;CAC3B;;AApBH;EAsBI,sBAAqB;CACtB;;AAvBH;EA0BI,e7BqBc;C6BpBf;;AEpCH;EACE,qBAAa;EAAb,cAAa;EAEb,gBAAe;EACf,iBAAgB;EzBAd,uBNmN2B;C+BjN9B;;AAED;EAGM,eAAc;EzBoBhB,gCNwL2B;EMvL3B,mCNuL2B;C+B1M1B;;AALL;EzBSI,iCNsM2B;EMrM3B,oCNqM2B;C+BrM1B;;AAVL;EAcI,WAAU;EACV,Y/B2BS;E+B1BT,0B/BkDa;E+BjDb,sB/BiDa;C+BhDd;;AAlBH;EAqBI,e/B2Bc;E+B1Bd,qBAAoB;EACpB,uB/BmBS;E+BlBT,mB/ByjBuC;C+BxjBxC;;AAGH;EACE,mBAAkB;EAClB,eAAc;EACd,wB/B4hB0C;E+B3hB1C,kBAAiB;EACjB,kB/B+hBwC;E+B9hBxC,e/BgCe;E+B/Bf,uB/BOW;E+BNX,uB/BiiByC;C+BzhB1C;;A9B9BG;E8ByBA,e/BuH4C;E+BtH5C,sBAAqB;EACrB,0B/BGc;E+BFd,mB/B+hBuC;CCxjBtC;;A+BtBH;EACE,wBhCmkBwC;EgClkBxC,mBhCyOoB;EgCxOpB,iBhC4MwB;CgC3MzB;;AAIG;E1BoBF,+BNyL0B;EMxL1B,kCNwL0B;CgC3MvB;;AAGD;E1BCF,gCNuM0B;EMtM1B,mCNsM0B;CgCtMvB;;AAfL;EACE,wBhCikBuC;EgChkBvC,oBhC0OoB;EgCzOpB,iBhC6MwB;CgC5MzB;;AAIG;E1BoBF,+BN0L0B;EMzL1B,kCNyL0B;CgC5MvB;;AAGD;E1BCF,gCNwM0B;EMvM1B,mCNuM0B;CgCvMvB;;ACbP;EACE,sBAAqB;EACrB,sBjC+pBgC;EiC9pBhC,ejC2pB+B;EiC1pB/B,kBjCyOqB;EiCxOrB,eAAc;EACd,YjCuCW;EiCtCX,mBAAkB;EAClB,oBAAmB;EACnB,yBAAwB;E3BVtB,uBNmN2B;CiClM9B;;AAhBD;EAcI,cAAa;CACd;;AAIH;EACE,mBAAkB;EAClB,UAAS;CACV;;AAMD;EACE,qBjCsoBgC;EiCroBhC,oBjCqoBgC;EMpqB9B,qBNuqB+B;CiCtoBlC;;AAOC;ElBiBE,YAAW;EmB3Db,0BlCwEe;CiC5Bd;;AhCxBC;EcuCA,YAAW;EmBtDT,sBAAqB;EACrB,0BAAkC;CjCiBnC;;AgCmBH;ElBiBE,YAAW;EmB3Db,0BlCsDgB;CiCVf;;AhCxBC;EcuCA,YAAW;EmBtDT,sBAAqB;EACrB,0BAAkC;CjCiBnC;;AgCmBH;ElBiBE,YAAW;EmB3Db,0BlC+Ee;CiCnCd;;AhCxBC;EcuCA,YAAW;EmBtDT,sBAAqB;EACrB,0BAAkC;CjCiBnC;;AgCmBH;ElBiBE,YAAW;EmB3Db,0BlCiFe;CiCrCd;;AhCxBC;EcuCA,YAAW;EmBtDT,sBAAqB;EACrB,0BAAkC;CjCiBnC;;AgCmBH;ElBeE,YAAW;EmBzDb,0BlC8Ee;CiClCd;;AhCxBC;EcqCA,YAAW;EmBpDT,sBAAqB;EACrB,0BAAkC;CjCiBnC;;AgCmBH;ElBiBE,YAAW;EmB3Db,0BlC4Ee;CiChCd;;AhCxBC;EcuCA,YAAW;EmBtDT,sBAAqB;EACrB,0BAAkC;CjCiBnC;;AgCmBH;ElBeE,YAAW;EmBzDb,0BlCiDgB;CiCLf;;AhCxBC;EcqCA,YAAW;EmBpDT,sBAAqB;EACrB,0BAAkC;CjCiBnC;;AgCmBH;ElBiBE,YAAW;EmB3Db,0BlCwDgB;CiCZf;;AhCxBC;EcuCA,YAAW;EmBtDT,sBAAqB;EACrB,0BAAkC;CjCiBnC;;AkCzBL;EACE,mBAAoD;EACpD,oBnC4lBmC;EmC3lBnC,0BnCiDgB;EMhDd,sBNoN0B;CmC/M7B;;AxB+CG;EwBxDJ;IAOI,mBnCulBiC;GmCrlBpC;CrCkvHA;;AqChvHD;EACE,iBAAgB;EAChB,gBAAe;E7BTb,iB6BUsB;CACzB;;ACXD;EACE,yBpC6sBmC;EoC5sBnC,oBpC6sBgC;EoC5sBhC,8BAA6C;E9BH3C,uBNmN2B;CoC9M9B;;AAGD;EAEE,eAAc;CACf;;AAGD;EACE,kBpC+NqB;CoC9NtB;;AAOD;EAGI,mBAAkB;EAClB,cpCkrBgC;EoCjrBhC,gBpCkrBiC;EoCjrBjC,yBpCirBiC;EoChrBjC,eAAc;CACf;;AASD;EC3CA,etBsFkE;EsBrFlE,0BtBmFuE;EsBlFvE,sBtBkFuE;CqBvCtE;;ACzCD;EACE,0BAAqC;CACtC;;AAED;EACE,eAA0B;CAC3B;;ADiCD;EC3CA,etBsFkE;EsBrFlE,0BtBmFuE;EsBlFvE,sBtBkFuE;CqBvCtE;;ACzCD;EACE,0BAAqC;CACtC;;AAED;EACE,eAA0B;CAC3B;;ADiCD;EC3CA,etBsFkE;EsBrFlE,0BtBmFuE;EsBlFvE,sBtBkFuE;CqBvCtE;;ACzCD;EACE,0BAAqC;CACtC;;AAED;EACE,eAA0B;CAC3B;;ADiCD;EC3CA,etBsFkE;EsBrFlE,0BtBmFuE;EsBlFvE,sBtBkFuE;CqBvCtE;;ACzCD;EACE,0BAAqC;CACtC;;AAED;EACE,eAA0B;CAC3B;;ADiCD;EC3CA,etBsFkE;EsBrFlE,0BtBmFuE;EsBlFvE,sBtBkFuE;CqBvCtE;;ACzCD;EACE,0BAAqC;CACtC;;AAED;EACE,eAA0B;CAC3B;;ADiCD;EC3CA,etBsFkE;EsBrFlE,0BtBmFuE;EsBlFvE,sBtBkFuE;CqBvCtE;;ACzCD;EACE,0BAAqC;CACtC;;AAED;EACE,eAA0B;CAC3B;;ADiCD;EC3CA,etBsFkE;EsBrFlE,0BtBmFuE;EsBlFvE,sBtBkFuE;CqBvCtE;;ACzCD;EACE,0BAAqC;CACtC;;AAED;EACE,eAA0B;CAC3B;;ADiCD;EC3CA,etBsFkE;EsBrFlE,0BtBmFuE;EsBlFvE,sBtBkFuE;CqBvCtE;;ACzCD;EACE,0BAAqC;CACtC;;AAED;EACE,eAA0B;CAC3B;;ACXH;EACE;IAAO,4BAAuC;GxC44H7C;EwC34HD;IAAK,yBAAwB;GxC84H5B;CACF;;AwCj5HD;EACE;IAAO,4BAAuC;GxC44H7C;EwC34HD;IAAK,yBAAwB;GxC84H5B;CACF;;AwC54HD;EACE,qBAAa;EAAb,cAAa;EACb,iBAAgB;EAChB,mBtCotBoC;EsCntBpC,kBtCktBkC;EsCjtBlC,mBAAkB;EAClB,0BtCyCgB;EMhDd,uBNmN2B;CsCzM9B;;AAED;EACE,atC0sBkC;EsCzsBlC,kBtCysBkC;EsCxsBlC,YtC+BW;EsC9BX,0BtCsDe;EOrEX,4BP8tBwC;CsC7sB7C;;AAED;ECWE,sMAA6I;EDT7I,2BtCisBkC;CsChsBnC;;AAED;EACE,2DtCosBgD;UsCpsBhD,mDtCosBgD;CsCnsBjD;;AE/BD;EACE,qBAAa;EAAb,cAAa;EACb,sBAAuB;MAAvB,wBAAuB;CACxB;;AAED;EACE,YAAO;MAAP,QAAO;CACR;;ACHD;EACE,qBAAa;EAAb,cAAa;EACb,2BAAsB;MAAtB,uBAAsB;EAGtB,gBAAe;EACf,iBAAgB;CACjB;;AAQD;EACE,YAAW;EACX,ezCoCgB;EyCnChB,oBAAmB;CAapB;;AxCbG;EwCIA,ezC+Bc;EyC9Bd,sBAAqB;EACrB,0BzCuBc;CC1Bb;;AwCNL;EAaI,ezC2Bc;EyC1Bd,0BzCmBc;CyClBf;;AAQH;EACE,mBAAkB;EAClB,eAAc;EACd,yBzCgsBsC;EyC9rBtC,oBzCsKgB;EyCrKhB,uBzCEW;EyCDX,uCzCWW;CyCiBZ;;AAnCD;EnChCI,gCN6M2B;EM5M3B,iCN4M2B;CyClK5B;;AAXH;EAcI,iBAAgB;EnChChB,oCN+L2B;EM9L3B,mCN8L2B;CyC7J5B;;AxCpCC;EwCuCA,sBAAqB;CxCpCpB;;AwCiBL;EAwBI,ezCVc;EyCWd,uBzCjBS;CyCkBV;;AA1BH;EA8BI,WAAU;EACV,YzCvBS;EyCwBT,0BzCAa;EyCCb,sBzCDa;CyCEd;;AASH;EAEI,gBAAe;EACf,eAAc;EACd,iBAAgB;CACjB;;AALH;EASM,cAAa;CACd;;AAVL;EAeM,iBAAgB;CACjB;;AClGH;EACE,e3BmFgE;E2BlFhE,0B3BgFqE;C2B/EtE;;AAGD;;EAEE,e3B4EgE;C2BhEjE;;AzCDC;;;EyCRE,e3ByE8D;E2BxE9D,0BAAyC;CzCU1C;;AyChBH;;EAUI,YAAW;EACX,0B3BmE8D;E2BlE9D,sB3BkE8D;C2BjE/D;;AAnBH;EACE,e3BmFgE;E2BlFhE,0B3BgFqE;C2B/EtE;;AAGD;;EAEE,e3B4EgE;C2BhEjE;;AzCDC;;;EyCRE,e3ByE8D;E2BxE9D,0BAAyC;CzCU1C;;AyChBH;;EAUI,YAAW;EACX,0B3BmE8D;E2BlE9D,sB3BkE8D;C2BjE/D;;AAnBH;EACE,e3BmFgE;E2BlFhE,0B3BgFqE;C2B/EtE;;AAGD;;EAEE,e3B4EgE;C2BhEjE;;AzCDC;;;EyCRE,e3ByE8D;E2BxE9D,0BAAyC;CzCU1C;;AyChBH;;EAUI,YAAW;EACX,0B3BmE8D;E2BlE9D,sB3BkE8D;C2BjE/D;;AAnBH;EACE,e3BmFgE;E2BlFhE,0B3BgFqE;C2B/EtE;;AAGD;;EAEE,e3B4EgE;C2BhEjE;;AzCDC;;;EyCRE,e3ByE8D;E2BxE9D,0BAAyC;CzCU1C;;AyChBH;;EAUI,YAAW;EACX,0B3BmE8D;E2BlE9D,sB3BkE8D;C2BjE/D;;AAnBH;EACE,e3BmFgE;E2BlFhE,0B3BgFqE;C2B/EtE;;AAGD;;EAEE,e3B4EgE;C2BhEjE;;AzCDC;;;EyCRE,e3ByE8D;E2BxE9D,0BAAyC;CzCU1C;;AyChBH;;EAUI,YAAW;EACX,0B3BmE8D;E2BlE9D,sB3BkE8D;C2BjE/D;;AAnBH;EACE,e3BmFgE;E2BlFhE,0B3BgFqE;C2B/EtE;;AAGD;;EAEE,e3B4EgE;C2BhEjE;;AzCDC;;;EyCRE,e3ByE8D;E2BxE9D,0BAAyC;CzCU1C;;AyChBH;;EAUI,YAAW;EACX,0B3BmE8D;E2BlE9D,sB3BkE8D;C2BjE/D;;AAnBH;EACE,e3BmFgE;E2BlFhE,0B3BgFqE;C2B/EtE;;AAGD;;EAEE,e3B4EgE;C2BhEjE;;AzCDC;;;EyCRE,e3ByE8D;E2BxE9D,0BAAyC;CzCU1C;;AyChBH;;EAUI,YAAW;EACX,0B3BmE8D;E2BlE9D,sB3BkE8D;C2BjE/D;;AAnBH;EACE,e3BmFgE;E2BlFhE,0B3BgFqE;C2B/EtE;;AAGD;;EAEE,e3B4EgE;C2BhEjE;;AzCDC;;;EyCRE,e3ByE8D;E2BxE9D,0BAAyC;CzCU1C;;AyChBH;;EAUI,YAAW;EACX,0B3BmE8D;E2BlE9D,sB3BkE8D;C2BjE/D;;ACtBL;EACE,aAAY;EACZ,kB3CizBiD;E2ChzBjD,kB3C+OqB;E2C9OrB,eAAc;EACd,Y3CuDW;E2CtDX,0B3C4CW;E2C3CX,YAAW;CAOZ;;A1CQG;E0CZA,Y3CkDS;E2CjDT,sBAAqB;EACrB,aAAY;C1CaX;;A0CHL;EACE,WAAU;EACV,wBAAuB;EACvB,UAAS;EACT,yBAAwB;CACzB;;ACpBD;EACE,iBAAgB;CACjB;;AAGD;EACE,gBAAe;EACf,OAAM;EACN,SAAQ;EACR,UAAS;EACT,QAAO;EACP,c5C0f8B;E4Czf9B,cAAa;EACb,iBAAgB;EAGhB,WAAU;CAWX;;AAtBD;ErCPM,4CPqsB8C;EOrsB9C,oCPqsB8C;EOrsB9C,qEPqsB8C;E4C3qBhD,sCAA6B;UAA7B,8BAA6B;CAC9B;;AApBH;EAqByB,mCAA0B;UAA1B,2BAA0B;CAAI;;AAEvD;EACE,mBAAkB;EAClB,iBAAgB;CACjB;;AAGD;EACE,mBAAkB;EAClB,YAAW;EACX,a5CuoBgC;C4CtoBjC;;AAGD;EACE,mBAAkB;EAClB,qBAAa;EAAb,cAAa;EACb,2BAAsB;MAAtB,uBAAsB;EACtB,uB5CFW;E4CGX,6BAA4B;EAC5B,qC5CMW;EMxDT,sBNoN0B;E4C9J5B,WAAU;CACX;;AAGD;EACE,gBAAe;EACf,OAAM;EACN,SAAQ;EACR,UAAS;EACT,QAAO;EACP,c5Cuc8B;E4Ctc9B,uB5CTW;C4CcZ;;AAZD;EAUW,WAAU;CAAK;;AAV1B;EAWW,a5CsnBqB;C4CtnBe;;AAK/C;EACE,qBAAa;EAAb,cAAa;EACb,uBAAmB;MAAnB,oBAAmB;EACnB,uBAA8B;MAA9B,+BAA8B;EAC9B,c5CknBgC;E4CjnBhC,iC5C/BgB;C4CgCjB;;AAGD;EACE,iBAAgB;EAChB,iB5C4JoB;C4C3JrB;;AAID;EACE,mBAAkB;EAGlB,mBAAc;MAAd,eAAc;EACd,c5C8kBgC;C4C7kBjC;;AAGD;EACE,qBAAa;EAAb,cAAa;EACb,uBAAmB;MAAnB,oBAAmB;EACnB,mBAAyB;MAAzB,0BAAyB;EACzB,c5CskBgC;E4CrkBhC,8B5CxDgB;C4C6DjB;;AAVD;EAQyB,oBAAmB;CAAK;;AARjD;EASwB,qBAAoB;CAAK;;AAIjD;EACE,mBAAkB;EAClB,aAAY;EACZ,YAAW;EACX,aAAY;EACZ,iBAAgB;CACjB;;AjClEG;EiCuEF;IACE,iB5CukB+B;I4CtkB/B,kBAAyC;GAC1C;EAMD;IAAY,iB5CgkBqB;G4ChkBG;C9CosIrC;;AapxIG;EiCoFF;IAAY,iB5C0jBqB;G4C1jBG;C9CssIrC;;A+Cj1ID;EACE,mBAAkB;EAClB,c7C2gB8B;E6C1gB9B,eAAc;EACd,U7CynB6B;E8C5nB7B,wG9CuOiH;E8CrOjH,mBAAkB;EAClB,oB9C4OyB;E8C3OzB,iB9C+OoB;E8C9OpB,iBAAgB;EAChB,kBAAiB;EACjB,sBAAqB;EACrB,kBAAiB;EACjB,qBAAoB;EACpB,uBAAsB;EACtB,mBAAkB;EAClB,qBAAoB;EACpB,oBAAmB;EACnB,iBAAgB;EDPhB,oB7CsOsB;E6CpOtB,sBAAqB;EACrB,WAAU;CAoFX;;AA/FD;EAaW,a7C6mBqB;C6C7mBQ;;AAbxC;EAgBI,mBAAkB;EAClB,eAAc;EACd,W7C8mB6B;E6C7mB7B,Y7C8mB6B;C6C7mB9B;;AApBH;EAuBI,eAA+B;CAWhC;;AAlCH;EAyBM,UAAS;CACV;;AA1BL;EA6BM,kBAAuC;EACvC,YAAW;EACX,wBAAyD;EACzD,uB7C2BO;C6C1BR;;AAjCL;EAoCI,e7C4lB6B;C6CjlB9B;;AA/CH;EAsCM,QAAO;CACR;;AAvCL;EA0CM,iBAAsC;EACtC,YAAW;EACX,4BAA8E;EAC9E,yB7CcO;C6CbR;;AA9CL;EAiDI,eAA+B;CAWhC;;AA5DH;EAmDM,OAAM;CACP;;AApDL;EAuDM,kBAAuC;EACvC,YAAW;EACX,wB7CukB2B;E6CtkB3B,0B7CCO;C6CAR;;AA3DL;EA8DI,e7CkkB6B;C6CtjB9B;;AA1EH;EAgEM,SAAQ;CACT;;AAjEL;EAoEM,SAAQ;EACR,iBAAsC;EACtC,YAAW;EACX,4B7CyjB2B;E6CxjB3B,wB7CbO;C6CcR;;AAzEL;EA2FI,mBAAkB;EAClB,0BAAyB;EACzB,oBAAmB;CACpB;;AAIH;EACE,iB7CohBiC;E6CnhBjC,iB7CwhB+B;E6CvhB/B,Y7CpDW;E6CqDX,mBAAkB;EAClB,uB7C5CW;EMxDT,uBNmN2B;C6C7G9B;;AE1GD;EACE,mBAAkB;EAClB,OAAM;EACN,QAAO;EACP,c/CygB8B;E+CxgB9B,eAAc;EACd,iB/CooByC;E+CnoBzC,a/CioBuC;E8CtoBvC,wG9CuOiH;E8CrOjH,mBAAkB;EAClB,oB9C4OyB;E8C3OzB,iB9C+OoB;E8C9OpB,iBAAgB;EAChB,kBAAiB;EACjB,sBAAqB;EACrB,kBAAiB;EACjB,qBAAoB;EACpB,uBAAsB;EACtB,mBAAkB;EAClB,qBAAoB;EACpB,oBAAmB;EACnB,iBAAgB;ECLhB,oB/CoOsB;E+ClOtB,sBAAqB;EACrB,uB/CoCW;E+CnCX,6BAA4B;EAC5B,qC/C4CW;EMxDT,sBNoN0B;C+C5C7B;;AA5KD;EAyBI,mBAAkB;EAClB,eAAc;EACd,Y/C6nBsC;E+C5nBtC,Y/C6nBqC;C+C5nBtC;;AA7BH;;EAiCI,mBAAkB;EAClB,eAAc;EACd,0BAAyB;EACzB,oBAAmB;CACpB;;AArCH;EAwCI,YAAW;EACX,mB/CmnB8D;C+ClnB/D;;AA1CH;EA4CI,YAAW;EACX,mB/C+mB8D;C+C9mB/D;;AA9CH;EAmDI,oB/CqmBsC;C+C/kBvC;;AAzEH;EAsDM,UAAS;CACV;;AAvDL;;EA2DM,uBAAsB;CACvB;;AA5DL;EA+DM,c/C6lB4D;E+C5lB5D,kBAA6C;EAC7C,sC/C4lBmE;C+C3lBpE;;AAlEL;EAqEM,cAAwC;EACxC,kBAA6C;EAC7C,uB/CrBO;C+CsBR;;AAxEL;EA4EI,kB/C4kBsC;C+CvjBvC;;AAjGH;EA+EM,QAAO;CACR;;AAhFL;;EAoFM,iBAA4C;EAC5C,qBAAoB;CACrB;;AAtFL;EAyFM,Y/CmkB4D;E+ClkB5D,wC/CmkBmE;C+ClkBpE;;AA3FL;EA8FM,YAAsC;EACtC,yB/C7CO;C+C8CR;;AAhGL;EAoGI,iB/CojBsC;C+CnhBvC;;AArIH;EAuGM,OAAM;CACP;;AAxGL;;EA4GM,kBAAuC;EACvC,oBAAmB;CACpB;;AA9GL;EAiHM,W/C2iB4D;E+C1iB5D,yC/C2iBmE;C+C1iBpE;;AAnHL;EAsHM,WAAqC;EACrC,0B/CrEO;C+CsER;;AAxHL;EA4HM,mBAAkB;EAClB,OAAM;EACN,UAAS;EACT,eAAc;EACd,YAAW;EACX,mBAAkB;EAClB,YAAW;EACX,iC/C4gBwD;C+C3gBzD;;AApIL;EAwII,mB/CghBsC;C+C3fvC;;AA7JH;EA2IM,SAAQ;CACT;;AA5IL;;EAgJM,iBAA4C;EAC5C,sBAAqB;CACtB;;AAlJL;EAqJM,a/CugB4D;E+CtgB5D,uC/CugBmE;C+CtgBpE;;AAvJL;EA0JM,aAAuC;EACvC,wB/CzGO;C+C0GR;;AAoBL;EACE,kB/CieyC;E+ChezC,iBAAgB;EAChB,gB/C0DmB;E+CzDnB,e/C8E8B;E+C7E9B,0B/C0d4D;E+Czd5D,iCAAyE;EzC5KvE,2CyC6KyE;EzC5KzE,4CyC4KyE;CAM5E;;AAbD;EAWI,cAAa;CACd;;AAGH;EACE,kB/CsdqC;E+CrdrC,e/CtIgB;C+CuIjB;;ACjMD;EACE,mBAAkB;CACnB;;AAED;EACE,mBAAkB;EAClB,YAAW;EACX,iBAAgB;CACjB;;AAED;EACE,mBAAkB;EAClB,cAAa;EACb,uBAAmB;MAAnB,oBAAmB;EACnB,YAAW;EzCVP,wCPyyB4C;EOzyB5C,gCPyyB4C;EOzyB5C,6DPyyB4C;EgD7xBhD,oCAA2B;UAA3B,4BAA2B;EAC3B,4BAAmB;UAAnB,oBAAmB;CACpB;;AAED;;;EAGE,eAAc;CACf;;AAED;;EAEE,mBAAkB;EAClB,OAAM;CACP;;AAGD;;EAEE,iCAAwB;UAAxB,yBAAwB;CAKzB;;AAHyC;EAJ1C;;IAKI,wCAA+B;YAA/B,gCAA+B;GAElC;ClD2nJA;;AkDznJD;;EAEE,oCAA2B;UAA3B,4BAA2B;CAK5B;;AAHyC;EAJ1C;;IAKI,2CAAkC;YAAlC,mCAAkC;GAErC;ClD8nJA;;AkD5nJD;;EAEE,qCAA4B;UAA5B,6BAA4B;CAK7B;;AAHyC;EAJ1C;;IAKI,4CAAmC;YAAnC,oCAAmC;GAEtC;ClDioJA;;AkD1nJD;;EAEE,mBAAkB;EAClB,OAAM;EACN,UAAS;EAET,qBAAa;EAAb,cAAa;EACb,uBAAmB;MAAnB,oBAAmB;EACnB,sBAAuB;MAAvB,wBAAuB;EACvB,WhDmtB+C;EgDltB/C,YhD1BW;EgD2BX,mBAAkB;EAClB,ahDitB8C;CgDtsB/C;;A/CnEG;;;E+C8DA,YhDlCS;EgDmCT,sBAAqB;EACrB,WAAU;EACV,YAAW;C/C9DV;;A+CiEL;EACE,QAAO;CACR;;AACD;EACE,SAAQ;CACT;;AAGD;;EAEE,sBAAqB;EACrB,YhDosBgD;EgDnsBhD,ahDmsBgD;EgDlsBhD,gDAA+C;EAC/C,2BAA0B;CAC3B;;AACD;EACE,8MjC/DyI;CiCgE1I;;AACD;EACE,gNjClEyI;CiCmE1I;;AAQD;EACE,mBAAkB;EAClB,SAAQ;EACR,aAAY;EACZ,QAAO;EACP,YAAW;EACX,qBAAa;EAAb,cAAa;EACb,sBAAuB;MAAvB,wBAAuB;EACvB,gBAAe;EAEf,kBhD6pB+C;EgD5pB/C,iBhD4pB+C;EgD3pB/C,iBAAgB;CAoCjB;;AAhDD;EAeI,mBAAkB;EAClB,mBAAc;MAAd,eAAc;EACd,YhDypB8C;EgDxpB9C,YhDypB6C;EgDxpB7C,kBhDypB6C;EgDxpB7C,iBhDwpB6C;EgDvpB7C,oBAAmB;EACnB,2ChD3FS;CgDgHV;;AA3CH;EA0BM,mBAAkB;EAClB,WAAU;EACV,QAAO;EACP,sBAAqB;EACrB,YAAW;EACX,aAAY;EACZ,YAAW;CACZ;;AAjCL;EAmCM,mBAAkB;EAClB,cAAa;EACb,QAAO;EACP,sBAAqB;EACrB,YAAW;EACX,aAAY;EACZ,YAAW;CACZ;;AA1CL;EA8CI,uBhDnHS;CgDoHV;;AAQH;EACE,mBAAkB;EAClB,WAA6C;EAC7C,aAAY;EACZ,UAA4C;EAC5C,YAAW;EACX,kBAAiB;EACjB,qBAAoB;EACpB,YhDpIW;EgDqIX,mBAAkB;CACnB;;ACxLD;EAAqB,oCAAmC;CAAK;;AAC7D;EAAqB,+BAA8B;CAAK;;AACxD;EAAqB,kCAAiC;CAAK;;AAC3D;EAAqB,kCAAiC;CAAK;;AAC3D;EAAqB,uCAAsC;CAAK;;AAChE;EAAqB,oCAAmC;CAAK;;ACF3D;EACE,qCAAmC;CACpC;;AjDiBC;EiDdE,qCAAgD;CjDiBjD;;AiDtBH;EACE,qCAAmC;CACpC;;AjDiBC;EiDdE,qCAAgD;CjDiBjD;;AiDtBH;EACE,qCAAmC;CACpC;;AjDiBC;EiDdE,qCAAgD;CjDiBjD;;AiDtBH;EACE,qCAAmC;CACpC;;AjDiBC;EiDdE,qCAAgD;CjDiBjD;;AiDtBH;EACE,qCAAmC;CACpC;;AjDiBC;EiDdE,qCAAgD;CjDiBjD;;AiDtBH;EACE,qCAAmC;CACpC;;AjDiBC;EiDdE,qCAAgD;CjDiBjD;;AiDtBH;EACE,qCAAmC;CACpC;;AjDiBC;EiDdE,qCAAgD;CjDiBjD;;AiDtBH;EACE,qCAAmC;CACpC;;AjDiBC;EiDdE,qCAAgD;CjDiBjD;;AkDrBL;EAAY,kCAAmC;CAAI;;AACnD;EAAkB,yCAAwC;CAAK;;ACD/D;EAAmB,qCAAsC;CAAI;;AAC7D;EAAmB,qBAAoB;CAAK;;AAC5C;EAAmB,yBAAwB;CAAK;;AAChD;EAAmB,2BAA0B;CAAK;;AAClD;EAAmB,4BAA2B;CAAK;;AACnD;EAAmB,0BAAyB;CAAK;;AAG/C;EACE,iCAA+B;CAChC;;AAFD;EACE,iCAA+B;CAChC;;AAFD;EACE,iCAA+B;CAChC;;AAFD;EACE,iCAA+B;CAChC;;AAFD;EACE,iCAA+B;CAChC;;AAFD;EACE,iCAA+B;CAChC;;AAFD;EACE,iCAA+B;CAChC;;AAFD;EACE,iCAA+B;CAChC;;AAGH;EACE,8BAA+B;CAChC;;AAMD;EACE,kCAAwC;CACzC;;AACD;EACE,2CAAiD;EACjD,4CAAkD;CACnD;;AACD;EACE,4CAAkD;EAClD,+CAAqD;CACtD;;AACD;EACE,+CAAqD;EACrD,8CAAoD;CACrD;;AACD;EACE,2CAAiD;EACjD,8CAAoD;CACrD;;AAED;EACE,mBAAkB;CACnB;;AAED;EACE,iBAAgB;CACjB;;AtBlDC;EACE,eAAc;EACd,YAAW;EACX,YAAW;CACZ;;AuBGC;EAA2B,yBAAwB;CAAK;;AACxD;EAA2B,2BAA0B;CAAK;;AAC1D;EAA2B,iCAAgC;CAAK;;AAChE;EAA2B,0BAAyB;CAAK;;AACzD;EAA2B,0BAAyB;CAAK;;AACzD;EAA2B,+BAA8B;CAAK;;AAC9D;EAA2B,gCAAwB;EAAxB,yBAAwB;CAAK;;AACxD;EAA2B,uCAA+B;EAA/B,gCAA+B;CAAK;;A1CyC/D;E0ChDA;IAA2B,yBAAwB;GAAK;EACxD;IAA2B,2BAA0B;GAAK;EAC1D;IAA2B,iCAAgC;GAAK;EAChE;IAA2B,0BAAyB;GAAK;EACzD;IAA2B,0BAAyB;GAAK;EACzD;IAA2B,+BAA8B;GAAK;EAC9D;IAA2B,gCAAwB;IAAxB,yBAAwB;GAAK;EACxD;IAA2B,uCAA+B;IAA/B,gCAA+B;GAAK;CvDuhKlE;;Aa9+JG;E0ChDA;IAA2B,yBAAwB;GAAK;EACxD;IAA2B,2BAA0B;GAAK;EAC1D;IAA2B,iCAAgC;GAAK;EAChE;IAA2B,0BAAyB;GAAK;EACzD;IAA2B,0BAAyB;GAAK;EACzD;IAA2B,+BAA8B;GAAK;EAC9D;IAA2B,gCAAwB;IAAxB,yBAAwB;GAAK;EACxD;IAA2B,uCAA+B;IAA/B,gCAA+B;GAAK;CvDkjKlE;;AazgKG;E0ChDA;IAA2B,yBAAwB;GAAK;EACxD;IAA2B,2BAA0B;GAAK;EAC1D;IAA2B,iCAAgC;GAAK;EAChE;IAA2B,0BAAyB;GAAK;EACzD;IAA2B,0BAAyB;GAAK;EACzD;IAA2B,+BAA8B;GAAK;EAC9D;IAA2B,gCAAwB;IAAxB,yBAAwB;GAAK;EACxD;IAA2B,uCAA+B;IAA/B,gCAA+B;GAAK;CvD6kKlE;;AapiKG;E0ChDA;IAA2B,yBAAwB;GAAK;EACxD;IAA2B,2BAA0B;GAAK;EAC1D;IAA2B,iCAAgC;GAAK;EAChE;IAA2B,0BAAyB;GAAK;EACzD;IAA2B,0BAAyB;GAAK;EACzD;IAA2B,+BAA8B;GAAK;EAC9D;IAA2B,gCAAwB;IAAxB,yBAAwB;GAAK;EACxD;IAA2B,uCAA+B;IAA/B,gCAA+B;GAAK;CvDwmKlE;;AuD/lKD;EACE,yBAAwB;CAKzB;;AAHC;EAHF;IAII,0BAAyB;GAE5B;CvDmmKA;;AuDjmKD;EACE,yBAAwB;CAKzB;;AAHC;EAHF;IAII,2BAA0B;GAE7B;CvDqmKA;;AuDnmKD;EACE,yBAAwB;CAKzB;;AAHC;EAHF;IAII,iCAAgC;GAEnC;CvDumKA;;AuDpmKC;EADF;IAEI,yBAAwB;GAE3B;CvDumKA;;AwDzpKD;EACE,mBAAkB;EAClB,eAAc;EACd,YAAW;EACX,WAAU;EACV,iBAAgB;CAoBjB;;AAzBD;EAQI,eAAc;EACd,YAAW;CACZ;;AAVH;;;;;EAiBI,mBAAkB;EAClB,OAAM;EACN,UAAS;EACT,QAAO;EACP,YAAW;EACX,aAAY;EACZ,UAAS;CACV;;AAGH;EAEI,wBAA+B;CAChC;;AAGH;EAEI,oBAA+B;CAChC;;AAGH;EAEI,iBAA8B;CAC/B;;AAGH;EAEI,kBAA8B;CAC/B;;AC1CC;EAAgC,mCAA8B;MAA9B,+BAA8B;CAAK;;AACnE;EAAgC,sCAAiC;MAAjC,kCAAiC;CAAK;;AACtE;EAAgC,2CAAsC;MAAtC,uCAAsC;CAAK;;AAC3E;EAAgC,8CAAyC;MAAzC,0CAAyC;CAAK;;AAE9E;EAA8B,+BAA0B;MAA1B,2BAA0B;CAAK;;AAC7D;EAA8B,iCAA4B;MAA5B,6BAA4B;CAAK;;AAC/D;EAA8B,uCAAkC;MAAlC,mCAAkC;CAAK;;AAErE;EAAoC,gCAAsC;MAAtC,uCAAsC;CAAK;;AAC/E;EAAoC,8BAAoC;MAApC,qCAAoC;CAAK;;AAC7E;EAAoC,iCAAkC;MAAlC,mCAAkC;CAAK;;AAC3E;EAAoC,kCAAyC;MAAzC,0CAAyC;CAAK;;AAClF;EAAoC,qCAAwC;MAAxC,yCAAwC;CAAK;;AAEjF;EAAiC,iCAAkC;MAAlC,mCAAkC;CAAK;;AACxE;EAAiC,+BAAgC;MAAhC,iCAAgC;CAAK;;AACtE;EAAiC,kCAA8B;MAA9B,+BAA8B;CAAK;;AACpE;EAAiC,oCAAgC;MAAhC,iCAAgC;CAAK;;AACtE;EAAiC,mCAA+B;MAA/B,gCAA+B;CAAK;;AAErE;EAAkC,qCAAoC;MAApC,qCAAoC;CAAK;;AAC3E;EAAkC,mCAAkC;MAAlC,mCAAkC;CAAK;;AACzE;EAAkC,sCAAgC;MAAhC,iCAAgC;CAAK;;AACvE;EAAkC,uCAAuC;MAAvC,wCAAuC;CAAK;;AAC9E;EAAkC,0CAAsC;MAAtC,uCAAsC;CAAK;;AAC7E;EAAkC,uCAAiC;MAAjC,kCAAiC;CAAK;;AAExE;EAAgC,qCAA2B;MAA3B,4BAA2B;CAAK;;AAChE;EAAgC,sCAAiC;MAAjC,kCAAiC;CAAK;;AACtE;EAAgC,oCAA+B;MAA/B,gCAA+B;CAAK;;AACpE;EAAgC,uCAA6B;MAA7B,8BAA6B;CAAK;;AAClE;EAAgC,yCAA+B;MAA/B,gCAA+B;CAAK;;AACpE;EAAgC,wCAA8B;MAA9B,+BAA8B;CAAK;;A5CenE;E4ChDA;IAAgC,mCAA8B;QAA9B,+BAA8B;GAAK;EACnE;IAAgC,sCAAiC;QAAjC,kCAAiC;GAAK;EACtE;IAAgC,2CAAsC;QAAtC,uCAAsC;GAAK;EAC3E;IAAgC,8CAAyC;QAAzC,0CAAyC;GAAK;EAE9E;IAA8B,+BAA0B;QAA1B,2BAA0B;GAAK;EAC7D;IAA8B,iCAA4B;QAA5B,6BAA4B;GAAK;EAC/D;IAA8B,uCAAkC;QAAlC,mCAAkC;GAAK;EAErE;IAAoC,gCAAsC;QAAtC,uCAAsC;GAAK;EAC/E;IAAoC,8BAAoC;QAApC,qCAAoC;GAAK;EAC7E;IAAoC,iCAAkC;QAAlC,mCAAkC;GAAK;EAC3E;IAAoC,kCAAyC;QAAzC,0CAAyC;GAAK;EAClF;IAAoC,qCAAwC;QAAxC,yCAAwC;GAAK;EAEjF;IAAiC,iCAAkC;QAAlC,mCAAkC;GAAK;EACxE;IAAiC,+BAAgC;QAAhC,iCAAgC;GAAK;EACtE;IAAiC,kCAA8B;QAA9B,+BAA8B;GAAK;EACpE;IAAiC,oCAAgC;QAAhC,iCAAgC;GAAK;EACtE;IAAiC,mCAA+B;QAA/B,gCAA+B;GAAK;EAErE;IAAkC,qCAAoC;QAApC,qCAAoC;GAAK;EAC3E;IAAkC,mCAAkC;QAAlC,mCAAkC;GAAK;EACzE;IAAkC,sCAAgC;QAAhC,iCAAgC;GAAK;EACvE;IAAkC,uCAAuC;QAAvC,wCAAuC;GAAK;EAC9E;IAAkC,0CAAsC;QAAtC,uCAAsC;GAAK;EAC7E;IAAkC,uCAAiC;QAAjC,kCAAiC;GAAK;EAExE;IAAgC,qCAA2B;QAA3B,4BAA2B;GAAK;EAChE;IAAgC,sCAAiC;QAAjC,kCAAiC;GAAK;EACtE;IAAgC,oCAA+B;QAA/B,gCAA+B;GAAK;EACpE;IAAgC,uCAA6B;QAA7B,8BAA6B;GAAK;EAClE;IAAgC,yCAA+B;QAA/B,gCAA+B;GAAK;EACpE;IAAgC,wCAA8B;QAA9B,+BAA8B;GAAK;CzD22KtE;;Aa51KG;E4ChDA;IAAgC,mCAA8B;QAA9B,+BAA8B;GAAK;EACnE;IAAgC,sCAAiC;QAAjC,kCAAiC;GAAK;EACtE;IAAgC,2CAAsC;QAAtC,uCAAsC;GAAK;EAC3E;IAAgC,8CAAyC;QAAzC,0CAAyC;GAAK;EAE9E;IAA8B,+BAA0B;QAA1B,2BAA0B;GAAK;EAC7D;IAA8B,iCAA4B;QAA5B,6BAA4B;GAAK;EAC/D;IAA8B,uCAAkC;QAAlC,mCAAkC;GAAK;EAErE;IAAoC,gCAAsC;QAAtC,uCAAsC;GAAK;EAC/E;IAAoC,8BAAoC;QAApC,qCAAoC;GAAK;EAC7E;IAAoC,iCAAkC;QAAlC,mCAAkC;GAAK;EAC3E;IAAoC,kCAAyC;QAAzC,0CAAyC;GAAK;EAClF;IAAoC,qCAAwC;QAAxC,yCAAwC;GAAK;EAEjF;IAAiC,iCAAkC;QAAlC,mCAAkC;GAAK;EACxE;IAAiC,+BAAgC;QAAhC,iCAAgC;GAAK;EACtE;IAAiC,kCAA8B;QAA9B,+BAA8B;GAAK;EACpE;IAAiC,oCAAgC;QAAhC,iCAAgC;GAAK;EACtE;IAAiC,mCAA+B;QAA/B,gCAA+B;GAAK;EAErE;IAAkC,qCAAoC;QAApC,qCAAoC;GAAK;EAC3E;IAAkC,mCAAkC;QAAlC,mCAAkC;GAAK;EACzE;IAAkC,sCAAgC;QAAhC,iCAAgC;GAAK;EACvE;IAAkC,uCAAuC;QAAvC,wCAAuC;GAAK;EAC9E;IAAkC,0CAAsC;QAAtC,uCAAsC;GAAK;EAC7E;IAAkC,uCAAiC;QAAjC,kCAAiC;GAAK;EAExE;IAAgC,qCAA2B;QAA3B,4BAA2B;GAAK;EAChE;IAAgC,sCAAiC;QAAjC,kCAAiC;GAAK;EACtE;IAAgC,oCAA+B;QAA/B,gCAA+B;GAAK;EACpE;IAAgC,uCAA6B;QAA7B,8BAA6B;GAAK;EAClE;IAAgC,yCAA+B;QAA/B,gCAA+B;GAAK;EACpE;IAAgC,wCAA8B;QAA9B,+BAA8B;GAAK;CzDq8KtE;;Aat7KG;E4ChDA;IAAgC,mCAA8B;QAA9B,+BAA8B;GAAK;EACnE;IAAgC,sCAAiC;QAAjC,kCAAiC;GAAK;EACtE;IAAgC,2CAAsC;QAAtC,uCAAsC;GAAK;EAC3E;IAAgC,8CAAyC;QAAzC,0CAAyC;GAAK;EAE9E;IAA8B,+BAA0B;QAA1B,2BAA0B;GAAK;EAC7D;IAA8B,iCAA4B;QAA5B,6BAA4B;GAAK;EAC/D;IAA8B,uCAAkC;QAAlC,mCAAkC;GAAK;EAErE;IAAoC,gCAAsC;QAAtC,uCAAsC;GAAK;EAC/E;IAAoC,8BAAoC;QAApC,qCAAoC;GAAK;EAC7E;IAAoC,iCAAkC;QAAlC,mCAAkC;GAAK;EAC3E;IAAoC,kCAAyC;QAAzC,0CAAyC;GAAK;EAClF;IAAoC,qCAAwC;QAAxC,yCAAwC;GAAK;EAEjF;IAAiC,iCAAkC;QAAlC,mCAAkC;GAAK;EACxE;IAAiC,+BAAgC;QAAhC,iCAAgC;GAAK;EACtE;IAAiC,kCAA8B;QAA9B,+BAA8B;GAAK;EACpE;IAAiC,oCAAgC;QAAhC,iCAAgC;GAAK;EACtE;IAAiC,mCAA+B;QAA/B,gCAA+B;GAAK;EAErE;IAAkC,qCAAoC;QAApC,qCAAoC;GAAK;EAC3E;IAAkC,mCAAkC;QAAlC,mCAAkC;GAAK;EACzE;IAAkC,sCAAgC;QAAhC,iCAAgC;GAAK;EACvE;IAAkC,uCAAuC;QAAvC,wCAAuC;GAAK;EAC9E;IAAkC,0CAAsC;QAAtC,uCAAsC;GAAK;EAC7E;IAAkC,uCAAiC;QAAjC,kCAAiC;GAAK;EAExE;IAAgC,qCAA2B;QAA3B,4BAA2B;GAAK;EAChE;IAAgC,sCAAiC;QAAjC,kCAAiC;GAAK;EACtE;IAAgC,oCAA+B;QAA/B,gCAA+B;GAAK;EACpE;IAAgC,uCAA6B;QAA7B,8BAA6B;GAAK;EAClE;IAAgC,yCAA+B;QAA/B,gCAA+B;GAAK;EACpE;IAAgC,wCAA8B;QAA9B,+BAA8B;GAAK;CzD+hLtE;;AahhLG;E4ChDA;IAAgC,mCAA8B;QAA9B,+BAA8B;GAAK;EACnE;IAAgC,sCAAiC;QAAjC,kCAAiC;GAAK;EACtE;IAAgC,2CAAsC;QAAtC,uCAAsC;GAAK;EAC3E;IAAgC,8CAAyC;QAAzC,0CAAyC;GAAK;EAE9E;IAA8B,+BAA0B;QAA1B,2BAA0B;GAAK;EAC7D;IAA8B,iCAA4B;QAA5B,6BAA4B;GAAK;EAC/D;IAA8B,uCAAkC;QAAlC,mCAAkC;GAAK;EAErE;IAAoC,gCAAsC;QAAtC,uCAAsC;GAAK;EAC/E;IAAoC,8BAAoC;QAApC,qCAAoC;GAAK;EAC7E;IAAoC,iCAAkC;QAAlC,mCAAkC;GAAK;EAC3E;IAAoC,kCAAyC;QAAzC,0CAAyC;GAAK;EAClF;IAAoC,qCAAwC;QAAxC,yCAAwC;GAAK;EAEjF;IAAiC,iCAAkC;QAAlC,mCAAkC;GAAK;EACxE;IAAiC,+BAAgC;QAAhC,iCAAgC;GAAK;EACtE;IAAiC,kCAA8B;QAA9B,+BAA8B;GAAK;EACpE;IAAiC,oCAAgC;QAAhC,iCAAgC;GAAK;EACtE;IAAiC,mCAA+B;QAA/B,gCAA+B;GAAK;EAErE;IAAkC,qCAAoC;QAApC,qCAAoC;GAAK;EAC3E;IAAkC,mCAAkC;QAAlC,mCAAkC;GAAK;EACzE;IAAkC,sCAAgC;QAAhC,iCAAgC;GAAK;EACvE;IAAkC,uCAAuC;QAAvC,wCAAuC;GAAK;EAC9E;IAAkC,0CAAsC;QAAtC,uCAAsC;GAAK;EAC7E;IAAkC,uCAAiC;QAAjC,kCAAiC;GAAK;EAExE;IAAgC,qCAA2B;QAA3B,4BAA2B;GAAK;EAChE;IAAgC,sCAAiC;QAAjC,kCAAiC;GAAK;EACtE;IAAgC,oCAA+B;QAA/B,gCAA+B;GAAK;EACpE;IAAgC,uCAA6B;QAA7B,8BAA6B;GAAK;EAClE;IAAgC,yCAA+B;QAA/B,gCAA+B;GAAK;EACpE;IAAgC,wCAA8B;QAA9B,+BAA8B;GAAK;CzDynLtE;;A0D9pLG;ECHF,uBAAsB;CDG2B;;AAC/C;ECDF,wBAAuB;CDC2B;;AAChD;ECCF,uBAAsB;CDD2B;;A7CkD/C;E6CpDA;ICHF,uBAAsB;GDG2B;EAC/C;ICDF,wBAAuB;GDC2B;EAChD;ICCF,uBAAsB;GDD2B;C1DorLlD;;AaloLG;E6CpDA;ICHF,uBAAsB;GDG2B;EAC/C;ICDF,wBAAuB;GDC2B;EAChD;ICCF,uBAAsB;GDD2B;C1DgsLlD;;Aa9oLG;E6CpDA;ICHF,uBAAsB;GDG2B;EAC/C;ICDF,wBAAuB;GDC2B;EAChD;ICCF,uBAAsB;GDD2B;C1D4sLlD;;Aa1pLG;E6CpDA;ICHF,uBAAsB;GDG2B;EAC/C;ICDF,wBAAuB;GDC2B;EAChD;ICCF,uBAAsB;GDD2B;C1DwtLlD;;A4D5tLD;EACE,gBAAe;EACf,OAAM;EACN,SAAQ;EACR,QAAO;EACP,c1DmgB8B;C0DlgB/B;;AAED;EACE,gBAAe;EACf,SAAQ;EACR,UAAS;EACT,QAAO;EACP,c1D2f8B;C0D1f/B;;AAG6B;EAD9B;IAEI,yBAAgB;IAAhB,iBAAgB;IAChB,OAAM;IACN,c1Dmf4B;G0Djf/B;C5D8tLA;;A6DlvLD;ECEE,mBAAkB;EAClB,WAAU;EACV,YAAW;EACX,WAAU;EACV,iBAAgB;EAChB,uBAAmB;EACnB,oBAAmB;EACnB,8BAAqB;UAArB,sBAAqB;EACrB,UAAS;CDRV;;ACkBC;EAEE,iBAAgB;EAChB,YAAW;EACX,aAAY;EACZ,kBAAiB;EACjB,WAAU;EACV,oBAAmB;EACnB,wBAAe;UAAf,gBAAe;CAChB;;AC7BC;EAAuB,sBAA4B;CAAI;;AAAvD;EAAuB,sBAA4B;CAAI;;AAAvD;EAAuB,sBAA4B;CAAI;;AAAvD;EAAuB,uBAA4B;CAAI;;AAAvD;EAAuB,uBAA4B;CAAI;;AAAvD;EAAuB,uBAA4B;CAAI;;AAAvD;EAAuB,uBAA4B;CAAI;;AAAvD;EAAuB,wBAA4B;CAAI;;AAI3D;EAAU,2BAA0B;CAAK;;AACzC;EAAU,4BAA2B;CAAK;;ACAlC;EAAiC,qBAAmC;CAAI;;AACxE;EAAiC,yBAAuC;CAAI;;AAC5E;EAAiC,2BAAyC;CAAI;;AAC9E;EAAiC,4BAA0C;CAAI;;AAC/E;EAAiC,0BAAwC;CAAI;;AAC7E;EACE,2BAAwC;EACxC,0BAAuC;CACxC;;AACD;EACE,yBAAuC;EACvC,4BAA0C;CAC3C;;AAZD;EAAiC,2BAAmC;CAAI;;AACxE;EAAiC,+BAAuC;CAAI;;AAC5E;EAAiC,iCAAyC;CAAI;;AAC9E;EAAiC,kCAA0C;CAAI;;AAC/E;EAAiC,gCAAwC;CAAI;;AAC7E;EACE,iCAAwC;EACxC,gCAAuC;CACxC;;AACD;EACE,+BAAuC;EACvC,kCAA0C;CAC3C;;AAZD;EAAiC,0BAAmC;CAAI;;AACxE;EAAiC,8BAAuC;CAAI;;AAC5E;EAAiC,gCAAyC;CAAI;;AAC9E;EAAiC,iCAA0C;CAAI;;AAC/E;EAAiC,+BAAwC;CAAI;;AAC7E;EACE,gCAAwC;EACxC,+BAAuC;CACxC;;AACD;EACE,8BAAuC;EACvC,iCAA0C;CAC3C;;AAZD;EAAiC,wBAAmC;CAAI;;AACxE;EAAiC,4BAAuC;CAAI;;AAC5E;EAAiC,8BAAyC;CAAI;;AAC9E;EAAiC,+BAA0C;CAAI;;AAC/E;EAAiC,6BAAwC;CAAI;;AAC7E;EACE,8BAAwC;EACxC,6BAAuC;CACxC;;AACD;EACE,4BAAuC;EACvC,+BAA0C;CAC3C;;AAZD;EAAiC,0BAAmC;CAAI;;AACxE;EAAiC,8BAAuC;CAAI;;AAC5E;EAAiC,gCAAyC;CAAI;;AAC9E;EAAiC,iCAA0C;CAAI;;AAC/E;EAAiC,+BAAwC;CAAI;;AAC7E;EACE,gCAAwC;EACxC,+BAAuC;CACxC;;AACD;EACE,8BAAuC;EACvC,iCAA0C;CAC3C;;AAZD;EAAiC,wBAAmC;CAAI;;AACxE;EAAiC,4BAAuC;CAAI;;AAC5E;EAAiC,8BAAyC;CAAI;;AAC9E;EAAiC,+BAA0C;CAAI;;AAC/E;EAAiC,6BAAwC;CAAI;;AAC7E;EACE,8BAAwC;EACxC,6BAAuC;CACxC;;AACD;EACE,4BAAuC;EACvC,+BAA0C;CAC3C;;AAZD;EAAiC,sBAAmC;CAAI;;AACxE;EAAiC,0BAAuC;CAAI;;AAC5E;EAAiC,4BAAyC;CAAI;;AAC9E;EAAiC,6BAA0C;CAAI;;AAC/E;EAAiC,2BAAwC;CAAI;;AAC7E;EACE,4BAAwC;EACxC,2BAAuC;CACxC;;AACD;EACE,0BAAuC;EACvC,6BAA0C;CAC3C;;AAZD;EAAiC,4BAAmC;CAAI;;AACxE;EAAiC,gCAAuC;CAAI;;AAC5E;EAAiC,kCAAyC;CAAI;;AAC9E;EAAiC,mCAA0C;CAAI;;AAC/E;EAAiC,iCAAwC;CAAI;;AAC7E;EACE,kCAAwC;EACxC,iCAAuC;CACxC;;AACD;EACE,gCAAuC;EACvC,mCAA0C;CAC3C;;AAZD;EAAiC,2BAAmC;CAAI;;AACxE;EAAiC,+BAAuC;CAAI;;AAC5E;EAAiC,iCAAyC;CAAI;;AAC9E;EAAiC,kCAA0C;CAAI;;AAC/E;EAAiC,gCAAwC;CAAI;;AAC7E;EACE,iCAAwC;EACxC,gCAAuC;CACxC;;AACD;EACE,+BAAuC;EACvC,kCAA0C;CAC3C;;AAZD;EAAiC,yBAAmC;CAAI;;AACxE;EAAiC,6BAAuC;CAAI;;AAC5E;EAAiC,+BAAyC;CAAI;;AAC9E;EAAiC,gCAA0C;CAAI;;AAC/E;EAAiC,8BAAwC;CAAI;;AAC7E;EACE,+BAAwC;EACxC,8BAAuC;CACxC;;AACD;EACE,6BAAuC;EACvC,gCAA0C;CAC3C;;AAZD;EAAiC,2BAAmC;CAAI;;AACxE;EAAiC,+BAAuC;CAAI;;AAC5E;EAAiC,iCAAyC;CAAI;;AAC9E;EAAiC,kCAA0C;CAAI;;AAC/E;EAAiC,gCAAwC;CAAI;;AAC7E;EACE,iCAAwC;EACxC,gCAAuC;CACxC;;AACD;EACE,+BAAuC;EACvC,kCAA0C;CAC3C;;AAZD;EAAiC,yBAAmC;CAAI;;AACxE;EAAiC,6BAAuC;CAAI;;AAC5E;EAAiC,+BAAyC;CAAI;;AAC9E;EAAiC,gCAA0C;CAAI;;AAC/E;EAAiC,8BAAwC;CAAI;;AAC7E;EACE,+BAAwC;EACxC,8BAAuC;CACxC;;AACD;EACE,6BAAuC;EACvC,gCAA0C;CAC3C;;AAKL;EAAoB,wBAA8B;CAAK;;AACvD;EAAoB,4BAA8B;CAAK;;AACvD;EAAoB,8BAA8B;CAAK;;AACvD;EAAoB,+BAA8B;CAAK;;AACvD;EAAoB,6BAA8B;CAAK;;AACvD;EACE,8BAA6B;EAC7B,6BAA6B;CAC9B;;AACD;EACE,4BAA8B;EAC9B,+BAA8B;CAC/B;;AnDkBD;EmD/CI;IAAiC,qBAAmC;GAAI;EACxE;IAAiC,yBAAuC;GAAI;EAC5E;IAAiC,2BAAyC;GAAI;EAC9E;IAAiC,4BAA0C;GAAI;EAC/E;IAAiC,0BAAwC;GAAI;EAC7E;IACE,2BAAwC;IACxC,0BAAuC;GACxC;EACD;IACE,yBAAuC;IACvC,4BAA0C;GAC3C;EAZD;IAAiC,2BAAmC;GAAI;EACxE;IAAiC,+BAAuC;GAAI;EAC5E;IAAiC,iCAAyC;GAAI;EAC9E;IAAiC,kCAA0C;GAAI;EAC/E;IAAiC,gCAAwC;GAAI;EAC7E;IACE,iCAAwC;IACxC,gCAAuC;GACxC;EACD;IACE,+BAAuC;IACvC,kCAA0C;GAC3C;EAZD;IAAiC,0BAAmC;GAAI;EACxE;IAAiC,8BAAuC;GAAI;EAC5E;IAAiC,gCAAyC;GAAI;EAC9E;IAAiC,iCAA0C;GAAI;EAC/E;IAAiC,+BAAwC;GAAI;EAC7E;IACE,gCAAwC;IACxC,+BAAuC;GACxC;EACD;IACE,8BAAuC;IACvC,iCAA0C;GAC3C;EAZD;IAAiC,wBAAmC;GAAI;EACxE;IAAiC,4BAAuC;GAAI;EAC5E;IAAiC,8BAAyC;GAAI;EAC9E;IAAiC,+BAA0C;GAAI;EAC/E;IAAiC,6BAAwC;GAAI;EAC7E;IACE,8BAAwC;IACxC,6BAAuC;GACxC;EACD;IACE,4BAAuC;IACvC,+BAA0C;GAC3C;EAZD;IAAiC,0BAAmC;GAAI;EACxE;IAAiC,8BAAuC;GAAI;EAC5E;IAAiC,gCAAyC;GAAI;EAC9E;IAAiC,iCAA0C;GAAI;EAC/E;IAAiC,+BAAwC;GAAI;EAC7E;IACE,gCAAwC;IACxC,+BAAuC;GACxC;EACD;IACE,8BAAuC;IACvC,iCAA0C;GAC3C;EAZD;IAAiC,wBAAmC;GAAI;EACxE;IAAiC,4BAAuC;GAAI;EAC5E;IAAiC,8BAAyC;GAAI;EAC9E;IAAiC,+BAA0C;GAAI;EAC/E;IAAiC,6BAAwC;GAAI;EAC7E;IACE,8BAAwC;IACxC,6BAAuC;GACxC;EACD;IACE,4BAAuC;IACvC,+BAA0C;GAC3C;EAZD;IAAiC,sBAAmC;GAAI;EACxE;IAAiC,0BAAuC;GAAI;EAC5E;IAAiC,4BAAyC;GAAI;EAC9E;IAAiC,6BAA0C;GAAI;EAC/E;IAAiC,2BAAwC;GAAI;EAC7E;IACE,4BAAwC;IACxC,2BAAuC;GACxC;EACD;IACE,0BAAuC;IACvC,6BAA0C;GAC3C;EAZD;IAAiC,4BAAmC;GAAI;EACxE;IAAiC,gCAAuC;GAAI;EAC5E;IAAiC,kCAAyC;GAAI;EAC9E;IAAiC,mCAA0C;GAAI;EAC/E;IAAiC,iCAAwC;GAAI;EAC7E;IACE,kCAAwC;IACxC,iCAAuC;GACxC;EACD;IACE,gCAAuC;IACvC,mCAA0C;GAC3C;EAZD;IAAiC,2BAAmC;GAAI;EACxE;IAAiC,+BAAuC;GAAI;EAC5E;IAAiC,iCAAyC;GAAI;EAC9E;IAAiC,kCAA0C;GAAI;EAC/E;IAAiC,gCAAwC;GAAI;EAC7E;IACE,iCAAwC;IACxC,gCAAuC;GACxC;EACD;IACE,+BAAuC;IACvC,kCAA0C;GAC3C;EAZD;IAAiC,yBAAmC;GAAI;EACxE;IAAiC,6BAAuC;GAAI;EAC5E;IAAiC,+BAAyC;GAAI;EAC9E;IAAiC,gCAA0C;GAAI;EAC/E;IAAiC,8BAAwC;GAAI;EAC7E;IACE,+BAAwC;IACxC,8BAAuC;GACxC;EACD;IACE,6BAAuC;IACvC,gCAA0C;GAC3C;EAZD;IAAiC,2BAAmC;GAAI;EACxE;IAAiC,+BAAuC;GAAI;EAC5E;IAAiC,iCAAyC;GAAI;EAC9E;IAAiC,kCAA0C;GAAI;EAC/E;IAAiC,gCAAwC;GAAI;EAC7E;IACE,iCAAwC;IACxC,gCAAuC;GACxC;EACD;IACE,+BAAuC;IACvC,kCAA0C;GAC3C;EAZD;IAAiC,yBAAmC;GAAI;EACxE;IAAiC,6BAAuC;GAAI;EAC5E;IAAiC,+BAAyC;GAAI;EAC9E;IAAiC,gCAA0C;GAAI;EAC/E;IAAiC,8BAAwC;GAAI;EAC7E;IACE,+BAAwC;IACxC,8BAAuC;GACxC;EACD;IACE,6BAAuC;IACvC,gCAA0C;GAC3C;EAKL;IAAoB,wBAA8B;GAAK;EACvD;IAAoB,4BAA8B;GAAK;EACvD;IAAoB,8BAA8B;GAAK;EACvD;IAAoB,+BAA8B;GAAK;EACvD;IAAoB,6BAA8B;GAAK;EACvD;IACE,8BAA6B;IAC7B,6BAA6B;GAC9B;EACD;IACE,4BAA8B;IAC9B,+BAA8B;GAC/B;ChEk8MJ;;Aah7MG;EmD/CI;IAAiC,qBAAmC;GAAI;EACxE;IAAiC,yBAAuC;GAAI;EAC5E;IAAiC,2BAAyC;GAAI;EAC9E;IAAiC,4BAA0C;GAAI;EAC/E;IAAiC,0BAAwC;GAAI;EAC7E;IACE,2BAAwC;IACxC,0BAAuC;GACxC;EACD;IACE,yBAAuC;IACvC,4BAA0C;GAC3C;EAZD;IAAiC,2BAAmC;GAAI;EACxE;IAAiC,+BAAuC;GAAI;EAC5E;IAAiC,iCAAyC;GAAI;EAC9E;IAAiC,kCAA0C;GAAI;EAC/E;IAAiC,gCAAwC;GAAI;EAC7E;IACE,iCAAwC;IACxC,gCAAuC;GACxC;EACD;IACE,+BAAuC;IACvC,kCAA0C;GAC3C;EAZD;IAAiC,0BAAmC;GAAI;EACxE;IAAiC,8BAAuC;GAAI;EAC5E;IAAiC,gCAAyC;GAAI;EAC9E;IAAiC,iCAA0C;GAAI;EAC/E;IAAiC,+BAAwC;GAAI;EAC7E;IACE,gCAAwC;IACxC,+BAAuC;GACxC;EACD;IACE,8BAAuC;IACvC,iCAA0C;GAC3C;EAZD;IAAiC,wBAAmC;GAAI;EACxE;IAAiC,4BAAuC;GAAI;EAC5E;IAAiC,8BAAyC;GAAI;EAC9E;IAAiC,+BAA0C;GAAI;EAC/E;IAAiC,6BAAwC;GAAI;EAC7E;IACE,8BAAwC;IACxC,6BAAuC;GACxC;EACD;IACE,4BAAuC;IACvC,+BAA0C;GAC3C;EAZD;IAAiC,0BAAmC;GAAI;EACxE;IAAiC,8BAAuC;GAAI;EAC5E;IAAiC,gCAAyC;GAAI;EAC9E;IAAiC,iCAA0C;GAAI;EAC/E;IAAiC,+BAAwC;GAAI;EAC7E;IACE,gCAAwC;IACxC,+BAAuC;GACxC;EACD;IACE,8BAAuC;IACvC,iCAA0C;GAC3C;EAZD;IAAiC,wBAAmC;GAAI;EACxE;IAAiC,4BAAuC;GAAI;EAC5E;IAAiC,8BAAyC;GAAI;EAC9E;IAAiC,+BAA0C;GAAI;EAC/E;IAAiC,6BAAwC;GAAI;EAC7E;IACE,8BAAwC;IACxC,6BAAuC;GACxC;EACD;IACE,4BAAuC;IACvC,+BAA0C;GAC3C;EAZD;IAAiC,sBAAmC;GAAI;EACxE;IAAiC,0BAAuC;GAAI;EAC5E;IAAiC,4BAAyC;GAAI;EAC9E;IAAiC,6BAA0C;GAAI;EAC/E;IAAiC,2BAAwC;GAAI;EAC7E;IACE,4BAAwC;IACxC,2BAAuC;GACxC;EACD;IACE,0BAAuC;IACvC,6BAA0C;GAC3C;EAZD;IAAiC,4BAAmC;GAAI;EACxE;IAAiC,gCAAuC;GAAI;EAC5E;IAAiC,kCAAyC;GAAI;EAC9E;IAAiC,mCAA0C;GAAI;EAC/E;IAAiC,iCAAwC;GAAI;EAC7E;IACE,kCAAwC;IACxC,iCAAuC;GACxC;EACD;IACE,gCAAuC;IACvC,mCAA0C;GAC3C;EAZD;IAAiC,2BAAmC;GAAI;EACxE;IAAiC,+BAAuC;GAAI;EAC5E;IAAiC,iCAAyC;GAAI;EAC9E;IAAiC,kCAA0C;GAAI;EAC/E;IAAiC,gCAAwC;GAAI;EAC7E;IACE,iCAAwC;IACxC,gCAAuC;GACxC;EACD;IACE,+BAAuC;IACvC,kCAA0C;GAC3C;EAZD;IAAiC,yBAAmC;GAAI;EACxE;IAAiC,6BAAuC;GAAI;EAC5E;IAAiC,+BAAyC;GAAI;EAC9E;IAAiC,gCAA0C;GAAI;EAC/E;IAAiC,8BAAwC;GAAI;EAC7E;IACE,+BAAwC;IACxC,8BAAuC;GACxC;EACD;IACE,6BAAuC;IACvC,gCAA0C;GAC3C;EAZD;IAAiC,2BAAmC;GAAI;EACxE;IAAiC,+BAAuC;GAAI;EAC5E;IAAiC,iCAAyC;GAAI;EAC9E;IAAiC,kCAA0C;GAAI;EAC/E;IAAiC,gCAAwC;GAAI;EAC7E;IACE,iCAAwC;IACxC,gCAAuC;GACxC;EACD;IACE,+BAAuC;IACvC,kCAA0C;GAC3C;EAZD;IAAiC,yBAAmC;GAAI;EACxE;IAAiC,6BAAuC;GAAI;EAC5E;IAAiC,+BAAyC;GAAI;EAC9E;IAAiC,gCAA0C;GAAI;EAC/E;IAAiC,8BAAwC;GAAI;EAC7E;IACE,+BAAwC;IACxC,8BAAuC;GACxC;EACD;IACE,6BAAuC;IACvC,gCAA0C;GAC3C;EAKL;IAAoB,wBAA8B;GAAK;EACvD;IAAoB,4BAA8B;GAAK;EACvD;IAAoB,8BAA8B;GAAK;EACvD;IAAoB,+BAA8B;GAAK;EACvD;IAAoB,6BAA8B;GAAK;EACvD;IACE,8BAA6B;IAC7B,6BAA6B;GAC9B;EACD;IACE,4BAA8B;IAC9B,+BAA8B;GAC/B;ChEgvNJ;;Aa9tNG;EmD/CI;IAAiC,qBAAmC;GAAI;EACxE;IAAiC,yBAAuC;GAAI;EAC5E;IAAiC,2BAAyC;GAAI;EAC9E;IAAiC,4BAA0C;GAAI;EAC/E;IAAiC,0BAAwC;GAAI;EAC7E;IACE,2BAAwC;IACxC,0BAAuC;GACxC;EACD;IACE,yBAAuC;IACvC,4BAA0C;GAC3C;EAZD;IAAiC,2BAAmC;GAAI;EACxE;IAAiC,+BAAuC;GAAI;EAC5E;IAAiC,iCAAyC;GAAI;EAC9E;IAAiC,kCAA0C;GAAI;EAC/E;IAAiC,gCAAwC;GAAI;EAC7E;IACE,iCAAwC;IACxC,gCAAuC;GACxC;EACD;IACE,+BAAuC;IACvC,kCAA0C;GAC3C;EAZD;IAAiC,0BAAmC;GAAI;EACxE;IAAiC,8BAAuC;GAAI;EAC5E;IAAiC,gCAAyC;GAAI;EAC9E;IAAiC,iCAA0C;GAAI;EAC/E;IAAiC,+BAAwC;GAAI;EAC7E;IACE,gCAAwC;IACxC,+BAAuC;GACxC;EACD;IACE,8BAAuC;IACvC,iCAA0C;GAC3C;EAZD;IAAiC,wBAAmC;GAAI;EACxE;IAAiC,4BAAuC;GAAI;EAC5E;IAAiC,8BAAyC;GAAI;EAC9E;IAAiC,+BAA0C;GAAI;EAC/E;IAAiC,6BAAwC;GAAI;EAC7E;IACE,8BAAwC;IACxC,6BAAuC;GACxC;EACD;IACE,4BAAuC;IACvC,+BAA0C;GAC3C;EAZD;IAAiC,0BAAmC;GAAI;EACxE;IAAiC,8BAAuC;GAAI;EAC5E;IAAiC,gCAAyC;GAAI;EAC9E;IAAiC,iCAA0C;GAAI;EAC/E;IAAiC,+BAAwC;GAAI;EAC7E;IACE,gCAAwC;IACxC,+BAAuC;GACxC;EACD;IACE,8BAAuC;IACvC,iCAA0C;GAC3C;EAZD;IAAiC,wBAAmC;GAAI;EACxE;IAAiC,4BAAuC;GAAI;EAC5E;IAAiC,8BAAyC;GAAI;EAC9E;IAAiC,+BAA0C;GAAI;EAC/E;IAAiC,6BAAwC;GAAI;EAC7E;IACE,8BAAwC;IACxC,6BAAuC;GACxC;EACD;IACE,4BAAuC;IACvC,+BAA0C;GAC3C;EAZD;IAAiC,sBAAmC;GAAI;EACxE;IAAiC,0BAAuC;GAAI;EAC5E;IAAiC,4BAAyC;GAAI;EAC9E;IAAiC,6BAA0C;GAAI;EAC/E;IAAiC,2BAAwC;GAAI;EAC7E;IACE,4BAAwC;IACxC,2BAAuC;GACxC;EACD;IACE,0BAAuC;IACvC,6BAA0C;GAC3C;EAZD;IAAiC,4BAAmC;GAAI;EACxE;IAAiC,gCAAuC;GAAI;EAC5E;IAAiC,kCAAyC;GAAI;EAC9E;IAAiC,mCAA0C;GAAI;EAC/E;IAAiC,iCAAwC;GAAI;EAC7E;IACE,kCAAwC;IACxC,iCAAuC;GACxC;EACD;IACE,gCAAuC;IACvC,mCAA0C;GAC3C;EAZD;IAAiC,2BAAmC;GAAI;EACxE;IAAiC,+BAAuC;GAAI;EAC5E;IAAiC,iCAAyC;GAAI;EAC9E;IAAiC,kCAA0C;GAAI;EAC/E;IAAiC,gCAAwC;GAAI;EAC7E;IACE,iCAAwC;IACxC,gCAAuC;GACxC;EACD;IACE,+BAAuC;IACvC,kCAA0C;GAC3C;EAZD;IAAiC,yBAAmC;GAAI;EACxE;IAAiC,6BAAuC;GAAI;EAC5E;IAAiC,+BAAyC;GAAI;EAC9E;IAAiC,gCAA0C;GAAI;EAC/E;IAAiC,8BAAwC;GAAI;EAC7E;IACE,+BAAwC;IACxC,8BAAuC;GACxC;EACD;IACE,6BAAuC;IACvC,gCAA0C;GAC3C;EAZD;IAAiC,2BAAmC;GAAI;EACxE;IAAiC,+BAAuC;GAAI;EAC5E;IAAiC,iCAAyC;GAAI;EAC9E;IAAiC,kCAA0C;GAAI;EAC/E;IAAiC,gCAAwC;GAAI;EAC7E;IACE,iCAAwC;IACxC,gCAAuC;GACxC;EACD;IACE,+BAAuC;IACvC,kCAA0C;GAC3C;EAZD;IAAiC,yBAAmC;GAAI;EACxE;IAAiC,6BAAuC;GAAI;EAC5E;IAAiC,+BAAyC;GAAI;EAC9E;IAAiC,gCAA0C;GAAI;EAC/E;IAAiC,8BAAwC;GAAI;EAC7E;IACE,+BAAwC;IACxC,8BAAuC;GACxC;EACD;IACE,6BAAuC;IACvC,gCAA0C;GAC3C;EAKL;IAAoB,wBAA8B;GAAK;EACvD;IAAoB,4BAA8B;GAAK;EACvD;IAAoB,8BAA8B;GAAK;EACvD;IAAoB,+BAA8B;GAAK;EACvD;IAAoB,6BAA8B;GAAK;EACvD;IACE,8BAA6B;IAC7B,6BAA6B;GAC9B;EACD;IACE,4BAA8B;IAC9B,+BAA8B;GAC/B;ChE8hOJ;;Aa5gOG;EmD/CI;IAAiC,qBAAmC;GAAI;EACxE;IAAiC,yBAAuC;GAAI;EAC5E;IAAiC,2BAAyC;GAAI;EAC9E;IAAiC,4BAA0C;GAAI;EAC/E;IAAiC,0BAAwC;GAAI;EAC7E;IACE,2BAAwC;IACxC,0BAAuC;GACxC;EACD;IACE,yBAAuC;IACvC,4BAA0C;GAC3C;EAZD;IAAiC,2BAAmC;GAAI;EACxE;IAAiC,+BAAuC;GAAI;EAC5E;IAAiC,iCAAyC;GAAI;EAC9E;IAAiC,kCAA0C;GAAI;EAC/E;IAAiC,gCAAwC;GAAI;EAC7E;IACE,iCAAwC;IACxC,gCAAuC;GACxC;EACD;IACE,+BAAuC;IACvC,kCAA0C;GAC3C;EAZD;IAAiC,0BAAmC;GAAI;EACxE;IAAiC,8BAAuC;GAAI;EAC5E;IAAiC,gCAAyC;GAAI;EAC9E;IAAiC,iCAA0C;GAAI;EAC/E;IAAiC,+BAAwC;GAAI;EAC7E;IACE,gCAAwC;IACxC,+BAAuC;GACxC;EACD;IACE,8BAAuC;IACvC,iCAA0C;GAC3C;EAZD;IAAiC,wBAAmC;GAAI;EACxE;IAAiC,4BAAuC;GAAI;EAC5E;IAAiC,8BAAyC;GAAI;EAC9E;IAAiC,+BAA0C;GAAI;EAC/E;IAAiC,6BAAwC;GAAI;EAC7E;IACE,8BAAwC;IACxC,6BAAuC;GACxC;EACD;IACE,4BAAuC;IACvC,+BAA0C;GAC3C;EAZD;IAAiC,0BAAmC;GAAI;EACxE;IAAiC,8BAAuC;GAAI;EAC5E;IAAiC,gCAAyC;GAAI;EAC9E;IAAiC,iCAA0C;GAAI;EAC/E;IAAiC,+BAAwC;GAAI;EAC7E;IACE,gCAAwC;IACxC,+BAAuC;GACxC;EACD;IACE,8BAAuC;IACvC,iCAA0C;GAC3C;EAZD;IAAiC,wBAAmC;GAAI;EACxE;IAAiC,4BAAuC;GAAI;EAC5E;IAAiC,8BAAyC;GAAI;EAC9E;IAAiC,+BAA0C;GAAI;EAC/E;IAAiC,6BAAwC;GAAI;EAC7E;IACE,8BAAwC;IACxC,6BAAuC;GACxC;EACD;IACE,4BAAuC;IACvC,+BAA0C;GAC3C;EAZD;IAAiC,sBAAmC;GAAI;EACxE;IAAiC,0BAAuC;GAAI;EAC5E;IAAiC,4BAAyC;GAAI;EAC9E;IAAiC,6BAA0C;GAAI;EAC/E;IAAiC,2BAAwC;GAAI;EAC7E;IACE,4BAAwC;IACxC,2BAAuC;GACxC;EACD;IACE,0BAAuC;IACvC,6BAA0C;GAC3C;EAZD;IAAiC,4BAAmC;GAAI;EACxE;IAAiC,gCAAuC;GAAI;EAC5E;IAAiC,kCAAyC;GAAI;EAC9E;IAAiC,mCAA0C;GAAI;EAC/E;IAAiC,iCAAwC;GAAI;EAC7E;IACE,kCAAwC;IACxC,iCAAuC;GACxC;EACD;IACE,gCAAuC;IACvC,mCAA0C;GAC3C;EAZD;IAAiC,2BAAmC;GAAI;EACxE;IAAiC,+BAAuC;GAAI;EAC5E;IAAiC,iCAAyC;GAAI;EAC9E;IAAiC,kCAA0C;GAAI;EAC/E;IAAiC,gCAAwC;GAAI;EAC7E;IACE,iCAAwC;IACxC,gCAAuC;GACxC;EACD;IACE,+BAAuC;IACvC,kCAA0C;GAC3C;EAZD;IAAiC,yBAAmC;GAAI;EACxE;IAAiC,6BAAuC;GAAI;EAC5E;IAAiC,+BAAyC;GAAI;EAC9E;IAAiC,gCAA0C;GAAI;EAC/E;IAAiC,8BAAwC;GAAI;EAC7E;IACE,+BAAwC;IACxC,8BAAuC;GACxC;EACD;IACE,6BAAuC;IACvC,gCAA0C;GAC3C;EAZD;IAAiC,2BAAmC;GAAI;EACxE;IAAiC,+BAAuC;GAAI;EAC5E;IAAiC,iCAAyC;GAAI;EAC9E;IAAiC,kCAA0C;GAAI;EAC/E;IAAiC,gCAAwC;GAAI;EAC7E;IACE,iCAAwC;IACxC,gCAAuC;GACxC;EACD;IACE,+BAAuC;IACvC,kCAA0C;GAC3C;EAZD;IAAiC,yBAAmC;GAAI;EACxE;IAAiC,6BAAuC;GAAI;EAC5E;IAAiC,+BAAyC;GAAI;EAC9E;IAAiC,gCAA0C;GAAI;EAC/E;IAAiC,8BAAwC;GAAI;EAC7E;IACE,+BAAwC;IACxC,8BAAuC;GACxC;EACD;IACE,6BAAuC;IACvC,gCAA0C;GAC3C;EAKL;IAAoB,wBAA8B;GAAK;EACvD;IAAoB,4BAA8B;GAAK;EACvD;IAAoB,8BAA8B;GAAK;EACvD;IAAoB,+BAA8B;GAAK;EACvD;IAAoB,6BAA8B;GAAK;EACvD;IACE,8BAA6B;IAC7B,6BAA6B;GAC9B;EACD;IACE,4BAA8B;IAC9B,+BAA8B;GAC/B;ChE40OJ;;AiE52OD;EAAiB,+BAA8B;CAAK;;AACpD;EAAiB,+BAA8B;CAAK;;AACpD;ECJE,iBAAgB;EAChB,wBAAuB;EACvB,oBAAmB;CDEsB;;AAQvC;EAAwB,4BAA2B;CAAK;;AACxD;EAAwB,6BAA4B;CAAK;;AACzD;EAAwB,8BAA6B;CAAK;;ApDsC1D;EoDxCA;IAAwB,4BAA2B;GAAK;EACxD;IAAwB,6BAA4B;GAAK;EACzD;IAAwB,8BAA6B;GAAK;CjEs4O7D;;Aah2OG;EoDxCA;IAAwB,4BAA2B;GAAK;EACxD;IAAwB,6BAA4B;GAAK;EACzD;IAAwB,8BAA6B;GAAK;CjEk5O7D;;Aa52OG;EoDxCA;IAAwB,4BAA2B;GAAK;EACxD;IAAwB,6BAA4B;GAAK;EACzD;IAAwB,8BAA6B;GAAK;CjE85O7D;;Aax3OG;EoDxCA;IAAwB,4BAA2B;GAAK;EACxD;IAAwB,6BAA4B;GAAK;EACzD;IAAwB,8BAA6B;GAAK;CjE06O7D;;AiEp6OD;EAAmB,qCAAoC;CAAK;;AAC5D;EAAmB,qCAAoC;CAAK;;AAC5D;EAAmB,sCAAqC;CAAK;;AAI7D;EAAsB,oB/DmNK;C+DnN+B;;AAC1D;EAAsB,kB/DmNC;C+DnNiC;;AACxD;EAAsB,mBAAkB;CAAK;;AAI7C;EAAc,uBAAsB;CAAK;;AEjCvC;EACE,0BAAwB;CACzB;;AhEiBC;EgEdE,0BAAqC;ChEiBtC;;AgEtBH;EACE,0BAAwB;CACzB;;AhEiBC;EgEdE,0BAAqC;ChEiBtC;;AgEtBH;EACE,0BAAwB;CACzB;;AhEiBC;EgEdE,0BAAqC;ChEiBtC;;AgEtBH;EACE,0BAAwB;CACzB;;AhEiBC;EgEdE,0BAAqC;ChEiBtC;;AgEtBH;EACE,0BAAwB;CACzB;;AhEiBC;EgEdE,0BAAqC;ChEiBtC;;AgEtBH;EACE,0BAAwB;CACzB;;AhEiBC;EgEdE,0BAAqC;ChEiBtC;;AgEtBH;EACE,0BAAwB;CACzB;;AhEiBC;EgEdE,0BAAqC;ChEiBtC;;AgEtBH;EACE,0BAAwB;CACzB;;AhEiBC;EgEdE,0BAAqC;ChEiBtC;;A8DiBL;EAAc,0BAA6B;CAAI;;AAI/C;EG5CE,YAAW;EACX,mBAAkB;EAClB,kBAAiB;EACjB,8BAA6B;EAC7B,UAAS;CH0CV;;AI5CD;ECDE,+BAAkC;CDGnC;;AAED;ECLE,8BAAkC;CDOnC","file":"bootstrap.css","sourcesContent":["/*!\n * Bootstrap v4.0.0-beta (https://getbootstrap.com)\n * Copyright 2011-2017 The Bootstrap Authors\n * Copyright 2011-2017 Twitter, Inc.\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)\n */\n\n@import \"functions\";\n@import \"variables\";\n@import \"mixins\";\n@import \"print\";\n@import \"reboot\";\n@import \"type\";\n@import \"images\";\n@import \"code\";\n@import \"grid\";\n@import \"tables\";\n@import \"forms\";\n@import \"buttons\";\n@import \"transitions\";\n@import \"dropdown\";\n@import \"button-group\";\n@import \"input-group\";\n@import \"custom-forms\";\n@import \"nav\";\n@import \"navbar\";\n@import \"card\";\n@import \"breadcrumb\";\n@import \"pagination\";\n@import \"badge\";\n@import \"jumbotron\";\n@import \"alert\";\n@import \"progress\";\n@import \"media\";\n@import \"list-group\";\n@import \"close\";\n@import \"modal\";\n@import \"tooltip\";\n@import \"popover\";\n@import \"carousel\";\n@import \"utilities\";\n","// scss-lint:disable QualifyingElement\n\n// Source: https://github.com/h5bp/html5-boilerplate/blob/master/src/css/main.css\n\n// ==========================================================================\n// Print styles.\n// Inlined to avoid the additional HTTP request:\n// http://www.phpied.com/delay-loading-your-print-css/\n// ==========================================================================\n\n@if $enable-print-styles {\n @media print {\n *,\n *::before,\n *::after {\n // Bootstrap specific; comment out `color` and `background`\n //color: #000 !important; // Black prints faster:\n // http://www.sanbeiji.com/archives/953\n text-shadow: none !important;\n //background: transparent !important;\n box-shadow: none !important;\n }\n\n a,\n a:visited {\n text-decoration: underline;\n }\n\n // Bootstrap specific; comment the following selector out\n //a[href]::after {\n // content: \" (\" attr(href) \")\";\n //}\n\n abbr[title]::after {\n content: \" (\" attr(title) \")\";\n }\n\n // Bootstrap specific; comment the following selector out\n //\n // Don't show links that are fragment identifiers,\n // or use the `javascript:` pseudo protocol\n //\n\n //a[href^=\"#\"]::after,\n //a[href^=\"javascript:\"]::after {\n // content: \"\";\n //}\n\n pre {\n white-space: pre-wrap !important;\n }\n pre,\n blockquote {\n border: $border-width solid #999; // Bootstrap custom code; using `$border-width` instead of 1px\n page-break-inside: avoid;\n }\n\n //\n // Printing Tables:\n // http://css-discuss.incutio.com/wiki/Printing_Tables\n //\n\n thead {\n display: table-header-group;\n }\n\n tr,\n img {\n page-break-inside: avoid;\n }\n\n p,\n h2,\n h3 {\n orphans: 3;\n widows: 3;\n }\n\n h2,\n h3 {\n page-break-after: avoid;\n }\n\n // Bootstrap specific changes start\n\n // Bootstrap components\n .navbar {\n display: none;\n }\n .badge {\n border: $border-width solid #000;\n }\n\n .table {\n border-collapse: collapse !important;\n\n td,\n th {\n background-color: #fff !important;\n }\n }\n .table-bordered {\n th,\n td {\n border: 1px solid #ddd !important;\n }\n }\n\n // Bootstrap specific changes end\n }\n}\n","/*!\n * Bootstrap v4.0.0-beta (https://getbootstrap.com)\n * Copyright 2011-2017 The Bootstrap Authors\n * Copyright 2011-2017 Twitter, Inc.\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)\n */\n@media print {\n *,\n *::before,\n *::after {\n text-shadow: none !important;\n box-shadow: none !important;\n }\n a,\n a:visited {\n text-decoration: underline;\n }\n abbr[title]::after {\n content: \" (\" attr(title) \")\";\n }\n pre {\n white-space: pre-wrap !important;\n }\n pre,\n blockquote {\n border: 1px solid #999;\n page-break-inside: avoid;\n }\n thead {\n display: table-header-group;\n }\n tr,\n img {\n page-break-inside: avoid;\n }\n p,\n h2,\n h3 {\n orphans: 3;\n widows: 3;\n }\n h2,\n h3 {\n page-break-after: avoid;\n }\n .navbar {\n display: none;\n }\n .badge {\n border: 1px solid #000;\n }\n .table {\n border-collapse: collapse !important;\n }\n .table td,\n .table th {\n background-color: #fff !important;\n }\n .table-bordered th,\n .table-bordered td {\n border: 1px solid #ddd !important;\n }\n}\n\nhtml {\n box-sizing: border-box;\n font-family: sans-serif;\n line-height: 1.15;\n -webkit-text-size-adjust: 100%;\n -ms-text-size-adjust: 100%;\n -ms-overflow-style: scrollbar;\n -webkit-tap-highlight-color: transparent;\n}\n\n*,\n*::before,\n*::after {\n box-sizing: inherit;\n}\n\n@-ms-viewport {\n width: device-width;\n}\n\narticle, aside, dialog, figcaption, figure, footer, header, hgroup, main, nav, section {\n display: block;\n}\n\nbody {\n margin: 0;\n font-family: -apple-system, BlinkMacSystemFont, \"Segoe UI\", Roboto, \"Helvetica Neue\", Arial, sans-serif;\n font-size: 1rem;\n font-weight: normal;\n line-height: 1.5;\n color: #212529;\n background-color: #fff;\n}\n\n[tabindex=\"-1\"]:focus {\n outline: none !important;\n}\n\nhr {\n box-sizing: content-box;\n height: 0;\n overflow: visible;\n}\n\nh1, h2, h3, h4, h5, h6 {\n margin-top: 0;\n margin-bottom: .5rem;\n}\n\np {\n margin-top: 0;\n margin-bottom: 1rem;\n}\n\nabbr[title],\nabbr[data-original-title] {\n text-decoration: underline;\n text-decoration: underline dotted;\n cursor: help;\n border-bottom: 0;\n}\n\naddress {\n margin-bottom: 1rem;\n font-style: normal;\n line-height: inherit;\n}\n\nol,\nul,\ndl {\n margin-top: 0;\n margin-bottom: 1rem;\n}\n\nol ol,\nul ul,\nol ul,\nul ol {\n margin-bottom: 0;\n}\n\ndt {\n font-weight: bold;\n}\n\ndd {\n margin-bottom: .5rem;\n margin-left: 0;\n}\n\nblockquote {\n margin: 0 0 1rem;\n}\n\ndfn {\n font-style: italic;\n}\n\nb,\nstrong {\n font-weight: bolder;\n}\n\nsmall {\n font-size: 80%;\n}\n\nsub,\nsup {\n position: relative;\n font-size: 75%;\n line-height: 0;\n vertical-align: baseline;\n}\n\nsub {\n bottom: -.25em;\n}\n\nsup {\n top: -.5em;\n}\n\na {\n color: #007bff;\n text-decoration: none;\n background-color: transparent;\n -webkit-text-decoration-skip: objects;\n}\n\na:hover {\n color: #0056b3;\n text-decoration: underline;\n}\n\na:not([href]):not([tabindex]) {\n color: inherit;\n text-decoration: none;\n}\n\na:not([href]):not([tabindex]):focus, a:not([href]):not([tabindex]):hover {\n color: inherit;\n text-decoration: none;\n}\n\na:not([href]):not([tabindex]):focus {\n outline: 0;\n}\n\npre,\ncode,\nkbd,\nsamp {\n font-family: monospace, monospace;\n font-size: 1em;\n}\n\npre {\n margin-top: 0;\n margin-bottom: 1rem;\n overflow: auto;\n}\n\nfigure {\n margin: 0 0 1rem;\n}\n\nimg {\n vertical-align: middle;\n border-style: none;\n}\n\nsvg:not(:root) {\n overflow: hidden;\n}\n\na,\narea,\nbutton,\n[role=\"button\"],\ninput,\nlabel,\nselect,\nsummary,\ntextarea {\n touch-action: manipulation;\n}\n\ntable {\n border-collapse: collapse;\n}\n\ncaption {\n padding-top: 0.75rem;\n padding-bottom: 0.75rem;\n color: #868e96;\n text-align: left;\n caption-side: bottom;\n}\n\nth {\n text-align: left;\n}\n\nlabel {\n display: inline-block;\n margin-bottom: .5rem;\n}\n\nbutton:focus {\n outline: 1px dotted;\n outline: 5px auto -webkit-focus-ring-color;\n}\n\ninput,\nbutton,\nselect,\noptgroup,\ntextarea {\n margin: 0;\n font-family: inherit;\n font-size: inherit;\n line-height: inherit;\n}\n\nbutton,\ninput {\n overflow: visible;\n}\n\nbutton,\nselect {\n text-transform: none;\n}\n\nbutton,\nhtml [type=\"button\"],\n[type=\"reset\"],\n[type=\"submit\"] {\n -webkit-appearance: button;\n}\n\nbutton::-moz-focus-inner,\n[type=\"button\"]::-moz-focus-inner,\n[type=\"reset\"]::-moz-focus-inner,\n[type=\"submit\"]::-moz-focus-inner {\n padding: 0;\n border-style: none;\n}\n\ninput[type=\"radio\"],\ninput[type=\"checkbox\"] {\n box-sizing: border-box;\n padding: 0;\n}\n\ninput[type=\"date\"],\ninput[type=\"time\"],\ninput[type=\"datetime-local\"],\ninput[type=\"month\"] {\n -webkit-appearance: listbox;\n}\n\ntextarea {\n overflow: auto;\n resize: vertical;\n}\n\nfieldset {\n min-width: 0;\n padding: 0;\n margin: 0;\n border: 0;\n}\n\nlegend {\n display: block;\n width: 100%;\n max-width: 100%;\n padding: 0;\n margin-bottom: .5rem;\n font-size: 1.5rem;\n line-height: inherit;\n color: inherit;\n white-space: normal;\n}\n\nprogress {\n vertical-align: baseline;\n}\n\n[type=\"number\"]::-webkit-inner-spin-button,\n[type=\"number\"]::-webkit-outer-spin-button {\n height: auto;\n}\n\n[type=\"search\"] {\n outline-offset: -2px;\n -webkit-appearance: none;\n}\n\n[type=\"search\"]::-webkit-search-cancel-button,\n[type=\"search\"]::-webkit-search-decoration {\n -webkit-appearance: none;\n}\n\n::-webkit-file-upload-button {\n font: inherit;\n -webkit-appearance: button;\n}\n\noutput {\n display: inline-block;\n}\n\nsummary {\n display: list-item;\n}\n\ntemplate {\n display: none;\n}\n\n[hidden] {\n display: none !important;\n}\n\nh1, h2, h3, h4, h5, h6,\n.h1, .h2, .h3, .h4, .h5, .h6 {\n margin-bottom: 0.5rem;\n font-family: inherit;\n font-weight: 500;\n line-height: 1.1;\n color: inherit;\n}\n\nh1, .h1 {\n font-size: 2.5rem;\n}\n\nh2, .h2 {\n font-size: 2rem;\n}\n\nh3, .h3 {\n font-size: 1.75rem;\n}\n\nh4, .h4 {\n font-size: 1.5rem;\n}\n\nh5, .h5 {\n font-size: 1.25rem;\n}\n\nh6, .h6 {\n font-size: 1rem;\n}\n\n.lead {\n font-size: 1.25rem;\n font-weight: 300;\n}\n\n.display-1 {\n font-size: 6rem;\n font-weight: 300;\n line-height: 1.1;\n}\n\n.display-2 {\n font-size: 5.5rem;\n font-weight: 300;\n line-height: 1.1;\n}\n\n.display-3 {\n font-size: 4.5rem;\n font-weight: 300;\n line-height: 1.1;\n}\n\n.display-4 {\n font-size: 3.5rem;\n font-weight: 300;\n line-height: 1.1;\n}\n\nhr {\n margin-top: 1rem;\n margin-bottom: 1rem;\n border: 0;\n border-top: 1px solid rgba(0, 0, 0, 0.1);\n}\n\nsmall,\n.small {\n font-size: 80%;\n font-weight: normal;\n}\n\nmark,\n.mark {\n padding: 0.2em;\n background-color: #fcf8e3;\n}\n\n.list-unstyled {\n padding-left: 0;\n list-style: none;\n}\n\n.list-inline {\n padding-left: 0;\n list-style: none;\n}\n\n.list-inline-item {\n display: inline-block;\n}\n\n.list-inline-item:not(:last-child) {\n margin-right: 5px;\n}\n\n.initialism {\n font-size: 90%;\n text-transform: uppercase;\n}\n\n.blockquote {\n margin-bottom: 1rem;\n font-size: 1.25rem;\n}\n\n.blockquote-footer {\n display: block;\n font-size: 80%;\n color: #868e96;\n}\n\n.blockquote-footer::before {\n content: \"\\2014 \\00A0\";\n}\n\n.img-fluid {\n max-width: 100%;\n height: auto;\n}\n\n.img-thumbnail {\n padding: 0.25rem;\n background-color: #fff;\n border: 1px solid #ddd;\n border-radius: 0.25rem;\n transition: all 0.2s ease-in-out;\n max-width: 100%;\n height: auto;\n}\n\n.figure {\n display: inline-block;\n}\n\n.figure-img {\n margin-bottom: 0.5rem;\n line-height: 1;\n}\n\n.figure-caption {\n font-size: 90%;\n color: #868e96;\n}\n\ncode,\nkbd,\npre,\nsamp {\n font-family: Menlo, Monaco, Consolas, \"Liberation Mono\", \"Courier New\", monospace;\n}\n\ncode {\n padding: 0.2rem 0.4rem;\n font-size: 90%;\n color: #bd4147;\n background-color: #f8f9fa;\n border-radius: 0.25rem;\n}\n\na > code {\n padding: 0;\n color: inherit;\n background-color: inherit;\n}\n\nkbd {\n padding: 0.2rem 0.4rem;\n font-size: 90%;\n color: #fff;\n background-color: #212529;\n border-radius: 0.2rem;\n}\n\nkbd kbd {\n padding: 0;\n font-size: 100%;\n font-weight: bold;\n}\n\npre {\n display: block;\n margin-top: 0;\n margin-bottom: 1rem;\n font-size: 90%;\n color: #212529;\n}\n\npre code {\n padding: 0;\n font-size: inherit;\n color: inherit;\n background-color: transparent;\n border-radius: 0;\n}\n\n.pre-scrollable {\n max-height: 340px;\n overflow-y: scroll;\n}\n\n.container {\n margin-right: auto;\n margin-left: auto;\n padding-right: 15px;\n padding-left: 15px;\n width: 100%;\n}\n\n@media (min-width: 576px) {\n .container {\n max-width: 540px;\n }\n}\n\n@media (min-width: 768px) {\n .container {\n max-width: 720px;\n }\n}\n\n@media (min-width: 992px) {\n .container {\n max-width: 960px;\n }\n}\n\n@media (min-width: 1200px) {\n .container {\n max-width: 1140px;\n }\n}\n\n.container-fluid {\n width: 100%;\n margin-right: auto;\n margin-left: auto;\n padding-right: 15px;\n padding-left: 15px;\n width: 100%;\n}\n\n.row {\n display: flex;\n flex-wrap: wrap;\n margin-right: -15px;\n margin-left: -15px;\n}\n\n.no-gutters {\n margin-right: 0;\n margin-left: 0;\n}\n\n.no-gutters > .col,\n.no-gutters > [class*=\"col-\"] {\n padding-right: 0;\n padding-left: 0;\n}\n\n.col-1, .col-2, .col-3, .col-4, .col-5, .col-6, .col-7, .col-8, .col-9, .col-10, .col-11, .col-12, .col,\n.col-auto, .col-sm-1, .col-sm-2, .col-sm-3, .col-sm-4, .col-sm-5, .col-sm-6, .col-sm-7, .col-sm-8, .col-sm-9, .col-sm-10, .col-sm-11, .col-sm-12, .col-sm,\n.col-sm-auto, .col-md-1, .col-md-2, .col-md-3, .col-md-4, .col-md-5, .col-md-6, .col-md-7, .col-md-8, .col-md-9, .col-md-10, .col-md-11, .col-md-12, .col-md,\n.col-md-auto, .col-lg-1, .col-lg-2, .col-lg-3, .col-lg-4, .col-lg-5, .col-lg-6, .col-lg-7, .col-lg-8, .col-lg-9, .col-lg-10, .col-lg-11, .col-lg-12, .col-lg,\n.col-lg-auto, .col-xl-1, .col-xl-2, .col-xl-3, .col-xl-4, .col-xl-5, .col-xl-6, .col-xl-7, .col-xl-8, .col-xl-9, .col-xl-10, .col-xl-11, .col-xl-12, .col-xl,\n.col-xl-auto {\n position: relative;\n width: 100%;\n min-height: 1px;\n padding-right: 15px;\n padding-left: 15px;\n}\n\n.col {\n flex-basis: 0;\n flex-grow: 1;\n max-width: 100%;\n}\n\n.col-auto {\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n}\n\n.col-1 {\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n}\n\n.col-2 {\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n}\n\n.col-3 {\n flex: 0 0 25%;\n max-width: 25%;\n}\n\n.col-4 {\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n}\n\n.col-5 {\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n}\n\n.col-6 {\n flex: 0 0 50%;\n max-width: 50%;\n}\n\n.col-7 {\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n}\n\n.col-8 {\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n}\n\n.col-9 {\n flex: 0 0 75%;\n max-width: 75%;\n}\n\n.col-10 {\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n}\n\n.col-11 {\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n}\n\n.col-12 {\n flex: 0 0 100%;\n max-width: 100%;\n}\n\n.order-1 {\n order: 1;\n}\n\n.order-2 {\n order: 2;\n}\n\n.order-3 {\n order: 3;\n}\n\n.order-4 {\n order: 4;\n}\n\n.order-5 {\n order: 5;\n}\n\n.order-6 {\n order: 6;\n}\n\n.order-7 {\n order: 7;\n}\n\n.order-8 {\n order: 8;\n}\n\n.order-9 {\n order: 9;\n}\n\n.order-10 {\n order: 10;\n}\n\n.order-11 {\n order: 11;\n}\n\n.order-12 {\n order: 12;\n}\n\n@media (min-width: 576px) {\n .col-sm {\n flex-basis: 0;\n flex-grow: 1;\n max-width: 100%;\n }\n .col-sm-auto {\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n }\n .col-sm-1 {\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n }\n .col-sm-2 {\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n }\n .col-sm-3 {\n flex: 0 0 25%;\n max-width: 25%;\n }\n .col-sm-4 {\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n }\n .col-sm-5 {\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n }\n .col-sm-6 {\n flex: 0 0 50%;\n max-width: 50%;\n }\n .col-sm-7 {\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n }\n .col-sm-8 {\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n }\n .col-sm-9 {\n flex: 0 0 75%;\n max-width: 75%;\n }\n .col-sm-10 {\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n }\n .col-sm-11 {\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n }\n .col-sm-12 {\n flex: 0 0 100%;\n max-width: 100%;\n }\n .order-sm-1 {\n order: 1;\n }\n .order-sm-2 {\n order: 2;\n }\n .order-sm-3 {\n order: 3;\n }\n .order-sm-4 {\n order: 4;\n }\n .order-sm-5 {\n order: 5;\n }\n .order-sm-6 {\n order: 6;\n }\n .order-sm-7 {\n order: 7;\n }\n .order-sm-8 {\n order: 8;\n }\n .order-sm-9 {\n order: 9;\n }\n .order-sm-10 {\n order: 10;\n }\n .order-sm-11 {\n order: 11;\n }\n .order-sm-12 {\n order: 12;\n }\n}\n\n@media (min-width: 768px) {\n .col-md {\n flex-basis: 0;\n flex-grow: 1;\n max-width: 100%;\n }\n .col-md-auto {\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n }\n .col-md-1 {\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n }\n .col-md-2 {\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n }\n .col-md-3 {\n flex: 0 0 25%;\n max-width: 25%;\n }\n .col-md-4 {\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n }\n .col-md-5 {\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n }\n .col-md-6 {\n flex: 0 0 50%;\n max-width: 50%;\n }\n .col-md-7 {\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n }\n .col-md-8 {\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n }\n .col-md-9 {\n flex: 0 0 75%;\n max-width: 75%;\n }\n .col-md-10 {\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n }\n .col-md-11 {\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n }\n .col-md-12 {\n flex: 0 0 100%;\n max-width: 100%;\n }\n .order-md-1 {\n order: 1;\n }\n .order-md-2 {\n order: 2;\n }\n .order-md-3 {\n order: 3;\n }\n .order-md-4 {\n order: 4;\n }\n .order-md-5 {\n order: 5;\n }\n .order-md-6 {\n order: 6;\n }\n .order-md-7 {\n order: 7;\n }\n .order-md-8 {\n order: 8;\n }\n .order-md-9 {\n order: 9;\n }\n .order-md-10 {\n order: 10;\n }\n .order-md-11 {\n order: 11;\n }\n .order-md-12 {\n order: 12;\n }\n}\n\n@media (min-width: 992px) {\n .col-lg {\n flex-basis: 0;\n flex-grow: 1;\n max-width: 100%;\n }\n .col-lg-auto {\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n }\n .col-lg-1 {\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n }\n .col-lg-2 {\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n }\n .col-lg-3 {\n flex: 0 0 25%;\n max-width: 25%;\n }\n .col-lg-4 {\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n }\n .col-lg-5 {\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n }\n .col-lg-6 {\n flex: 0 0 50%;\n max-width: 50%;\n }\n .col-lg-7 {\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n }\n .col-lg-8 {\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n }\n .col-lg-9 {\n flex: 0 0 75%;\n max-width: 75%;\n }\n .col-lg-10 {\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n }\n .col-lg-11 {\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n }\n .col-lg-12 {\n flex: 0 0 100%;\n max-width: 100%;\n }\n .order-lg-1 {\n order: 1;\n }\n .order-lg-2 {\n order: 2;\n }\n .order-lg-3 {\n order: 3;\n }\n .order-lg-4 {\n order: 4;\n }\n .order-lg-5 {\n order: 5;\n }\n .order-lg-6 {\n order: 6;\n }\n .order-lg-7 {\n order: 7;\n }\n .order-lg-8 {\n order: 8;\n }\n .order-lg-9 {\n order: 9;\n }\n .order-lg-10 {\n order: 10;\n }\n .order-lg-11 {\n order: 11;\n }\n .order-lg-12 {\n order: 12;\n }\n}\n\n@media (min-width: 1200px) {\n .col-xl {\n flex-basis: 0;\n flex-grow: 1;\n max-width: 100%;\n }\n .col-xl-auto {\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n }\n .col-xl-1 {\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n }\n .col-xl-2 {\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n }\n .col-xl-3 {\n flex: 0 0 25%;\n max-width: 25%;\n }\n .col-xl-4 {\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n }\n .col-xl-5 {\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n }\n .col-xl-6 {\n flex: 0 0 50%;\n max-width: 50%;\n }\n .col-xl-7 {\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n }\n .col-xl-8 {\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n }\n .col-xl-9 {\n flex: 0 0 75%;\n max-width: 75%;\n }\n .col-xl-10 {\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n }\n .col-xl-11 {\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n }\n .col-xl-12 {\n flex: 0 0 100%;\n max-width: 100%;\n }\n .order-xl-1 {\n order: 1;\n }\n .order-xl-2 {\n order: 2;\n }\n .order-xl-3 {\n order: 3;\n }\n .order-xl-4 {\n order: 4;\n }\n .order-xl-5 {\n order: 5;\n }\n .order-xl-6 {\n order: 6;\n }\n .order-xl-7 {\n order: 7;\n }\n .order-xl-8 {\n order: 8;\n }\n .order-xl-9 {\n order: 9;\n }\n .order-xl-10 {\n order: 10;\n }\n .order-xl-11 {\n order: 11;\n }\n .order-xl-12 {\n order: 12;\n }\n}\n\n.table {\n width: 100%;\n max-width: 100%;\n margin-bottom: 1rem;\n background-color: transparent;\n}\n\n.table th,\n.table td {\n padding: 0.75rem;\n vertical-align: top;\n border-top: 1px solid #e9ecef;\n}\n\n.table thead th {\n vertical-align: bottom;\n border-bottom: 2px solid #e9ecef;\n}\n\n.table tbody + tbody {\n border-top: 2px solid #e9ecef;\n}\n\n.table .table {\n background-color: #fff;\n}\n\n.table-sm th,\n.table-sm td {\n padding: 0.3rem;\n}\n\n.table-bordered {\n border: 1px solid #e9ecef;\n}\n\n.table-bordered th,\n.table-bordered td {\n border: 1px solid #e9ecef;\n}\n\n.table-bordered thead th,\n.table-bordered thead td {\n border-bottom-width: 2px;\n}\n\n.table-striped tbody tr:nth-of-type(odd) {\n background-color: rgba(0, 0, 0, 0.05);\n}\n\n.table-hover tbody tr:hover {\n background-color: rgba(0, 0, 0, 0.075);\n}\n\n.table-primary,\n.table-primary > th,\n.table-primary > td {\n background-color: #b8daff;\n}\n\n.table-hover .table-primary:hover {\n background-color: #9fcdff;\n}\n\n.table-hover .table-primary:hover > td,\n.table-hover .table-primary:hover > th {\n background-color: #9fcdff;\n}\n\n.table-secondary,\n.table-secondary > th,\n.table-secondary > td {\n background-color: #dddfe2;\n}\n\n.table-hover .table-secondary:hover {\n background-color: #cfd2d6;\n}\n\n.table-hover .table-secondary:hover > td,\n.table-hover .table-secondary:hover > th {\n background-color: #cfd2d6;\n}\n\n.table-success,\n.table-success > th,\n.table-success > td {\n background-color: #c3e6cb;\n}\n\n.table-hover .table-success:hover {\n background-color: #b1dfbb;\n}\n\n.table-hover .table-success:hover > td,\n.table-hover .table-success:hover > th {\n background-color: #b1dfbb;\n}\n\n.table-info,\n.table-info > th,\n.table-info > td {\n background-color: #bee5eb;\n}\n\n.table-hover .table-info:hover {\n background-color: #abdde5;\n}\n\n.table-hover .table-info:hover > td,\n.table-hover .table-info:hover > th {\n background-color: #abdde5;\n}\n\n.table-warning,\n.table-warning > th,\n.table-warning > td {\n background-color: #ffeeba;\n}\n\n.table-hover .table-warning:hover {\n background-color: #ffe8a1;\n}\n\n.table-hover .table-warning:hover > td,\n.table-hover .table-warning:hover > th {\n background-color: #ffe8a1;\n}\n\n.table-danger,\n.table-danger > th,\n.table-danger > td {\n background-color: #f5c6cb;\n}\n\n.table-hover .table-danger:hover {\n background-color: #f1b0b7;\n}\n\n.table-hover .table-danger:hover > td,\n.table-hover .table-danger:hover > th {\n background-color: #f1b0b7;\n}\n\n.table-light,\n.table-light > th,\n.table-light > td {\n background-color: #fdfdfe;\n}\n\n.table-hover .table-light:hover {\n background-color: #ececf6;\n}\n\n.table-hover .table-light:hover > td,\n.table-hover .table-light:hover > th {\n background-color: #ececf6;\n}\n\n.table-dark,\n.table-dark > th,\n.table-dark > td {\n background-color: #c6c8ca;\n}\n\n.table-hover .table-dark:hover {\n background-color: #b9bbbe;\n}\n\n.table-hover .table-dark:hover > td,\n.table-hover .table-dark:hover > th {\n background-color: #b9bbbe;\n}\n\n.table-active,\n.table-active > th,\n.table-active > td {\n background-color: rgba(0, 0, 0, 0.075);\n}\n\n.table-hover .table-active:hover {\n background-color: rgba(0, 0, 0, 0.075);\n}\n\n.table-hover .table-active:hover > td,\n.table-hover .table-active:hover > th {\n background-color: rgba(0, 0, 0, 0.075);\n}\n\n.thead-inverse th {\n color: #fff;\n background-color: #212529;\n}\n\n.thead-default th {\n color: #495057;\n background-color: #e9ecef;\n}\n\n.table-inverse {\n color: #fff;\n background-color: #212529;\n}\n\n.table-inverse th,\n.table-inverse td,\n.table-inverse thead th {\n border-color: #32383e;\n}\n\n.table-inverse.table-bordered {\n border: 0;\n}\n\n.table-inverse.table-striped tbody tr:nth-of-type(odd) {\n background-color: rgba(255, 255, 255, 0.05);\n}\n\n.table-inverse.table-hover tbody tr:hover {\n background-color: rgba(255, 255, 255, 0.075);\n}\n\n@media (max-width: 991px) {\n .table-responsive {\n display: block;\n width: 100%;\n overflow-x: auto;\n -ms-overflow-style: -ms-autohiding-scrollbar;\n }\n .table-responsive.table-bordered {\n border: 0;\n }\n}\n\n.form-control {\n display: block;\n width: 100%;\n padding: 0.5rem 0.75rem;\n font-size: 1rem;\n line-height: 1.25;\n color: #495057;\n background-color: #fff;\n background-image: none;\n background-clip: padding-box;\n border: 1px solid rgba(0, 0, 0, 0.15);\n border-radius: 0.25rem;\n transition: border-color ease-in-out 0.15s, box-shadow ease-in-out 0.15s;\n}\n\n.form-control::-ms-expand {\n background-color: transparent;\n border: 0;\n}\n\n.form-control:focus {\n color: #495057;\n background-color: #fff;\n border-color: #80bdff;\n outline: none;\n}\n\n.form-control::placeholder {\n color: #868e96;\n opacity: 1;\n}\n\n.form-control:disabled, .form-control[readonly] {\n background-color: #e9ecef;\n opacity: 1;\n}\n\nselect.form-control:not([size]):not([multiple]) {\n height: calc(2.25rem + 2px);\n}\n\nselect.form-control:focus::-ms-value {\n color: #495057;\n background-color: #fff;\n}\n\n.form-control-file,\n.form-control-range {\n display: block;\n}\n\n.col-form-label {\n padding-top: calc(0.5rem - 1px * 2);\n padding-bottom: calc(0.5rem - 1px * 2);\n margin-bottom: 0;\n}\n\n.col-form-label-lg {\n padding-top: calc(0.5rem - 1px * 2);\n padding-bottom: calc(0.5rem - 1px * 2);\n font-size: 1.25rem;\n}\n\n.col-form-label-sm {\n padding-top: calc(0.25rem - 1px * 2);\n padding-bottom: calc(0.25rem - 1px * 2);\n font-size: 0.875rem;\n}\n\n.col-form-legend {\n padding-top: 0.5rem;\n padding-bottom: 0.5rem;\n margin-bottom: 0;\n font-size: 1rem;\n}\n\n.form-control-plaintext {\n padding-top: 0.5rem;\n padding-bottom: 0.5rem;\n margin-bottom: 0;\n line-height: 1.25;\n border: solid transparent;\n border-width: 1px 0;\n}\n\n.form-control-plaintext.form-control-sm, .input-group-sm > .form-control-plaintext.form-control,\n.input-group-sm > .form-control-plaintext.input-group-addon,\n.input-group-sm > .input-group-btn > .form-control-plaintext.btn, .form-control-plaintext.form-control-lg, .input-group-lg > .form-control-plaintext.form-control,\n.input-group-lg > .form-control-plaintext.input-group-addon,\n.input-group-lg > .input-group-btn > .form-control-plaintext.btn {\n padding-right: 0;\n padding-left: 0;\n}\n\n.form-control-sm, .input-group-sm > .form-control,\n.input-group-sm > .input-group-addon,\n.input-group-sm > .input-group-btn > .btn {\n padding: 0.25rem 0.5rem;\n font-size: 0.875rem;\n line-height: 1.5;\n border-radius: 0.2rem;\n}\n\nselect.form-control-sm:not([size]):not([multiple]), .input-group-sm > select.form-control:not([size]):not([multiple]),\n.input-group-sm > select.input-group-addon:not([size]):not([multiple]),\n.input-group-sm > .input-group-btn > select.btn:not([size]):not([multiple]) {\n height: calc(1.8125rem + 2px);\n}\n\n.form-control-lg, .input-group-lg > .form-control,\n.input-group-lg > .input-group-addon,\n.input-group-lg > .input-group-btn > .btn {\n padding: 0.5rem 1rem;\n font-size: 1.25rem;\n line-height: 1.5;\n border-radius: 0.3rem;\n}\n\nselect.form-control-lg:not([size]):not([multiple]), .input-group-lg > select.form-control:not([size]):not([multiple]),\n.input-group-lg > select.input-group-addon:not([size]):not([multiple]),\n.input-group-lg > .input-group-btn > select.btn:not([size]):not([multiple]) {\n height: calc(2.3125rem + 2px);\n}\n\n.form-group {\n margin-bottom: 1rem;\n}\n\n.form-text {\n display: block;\n margin-top: 0.25rem;\n}\n\n.form-row {\n display: flex;\n flex-wrap: wrap;\n margin-right: -5px;\n margin-left: -5px;\n}\n\n.form-row > .col,\n.form-row > [class*=\"col-\"] {\n padding-right: 5px;\n padding-left: 5px;\n}\n\n.form-check {\n position: relative;\n display: block;\n margin-bottom: 0.5rem;\n}\n\n.form-check.disabled .form-check-label {\n color: #868e96;\n}\n\n.form-check-label {\n padding-left: 1.25rem;\n margin-bottom: 0;\n}\n\n.form-check-input {\n position: absolute;\n margin-top: 0.25rem;\n margin-left: -1.25rem;\n}\n\n.form-check-input:only-child {\n position: static;\n}\n\n.form-check-inline {\n display: inline-block;\n}\n\n.form-check-inline .form-check-label {\n vertical-align: middle;\n}\n\n.form-check-inline + .form-check-inline {\n margin-left: 0.75rem;\n}\n\n.invalid-feedback {\n display: none;\n margin-top: .25rem;\n font-size: .875rem;\n color: #dc3545;\n}\n\n.invalid-tooltip {\n position: absolute;\n top: 100%;\n z-index: 5;\n display: none;\n width: 250px;\n padding: .5rem;\n margin-top: .1rem;\n font-size: .875rem;\n line-height: 1;\n color: #fff;\n background-color: rgba(220, 53, 69, 0.8);\n border-radius: .2rem;\n}\n\n.was-validated .form-control:valid, .form-control.is-valid, .was-validated\n.custom-select:valid,\n.custom-select.is-valid {\n border-color: #28a745;\n}\n\n.was-validated .form-control:valid:focus, .form-control.is-valid:focus, .was-validated\n.custom-select:valid:focus,\n.custom-select.is-valid:focus {\n box-shadow: 0 0 0 0.2rem rgba(40, 167, 69, 0.25);\n}\n\n.was-validated .form-control:valid ~ .invalid-feedback,\n.was-validated .form-control:valid ~ .invalid-tooltip, .form-control.is-valid ~ .invalid-feedback,\n.form-control.is-valid ~ .invalid-tooltip, .was-validated\n.custom-select:valid ~ .invalid-feedback,\n.was-validated\n.custom-select:valid ~ .invalid-tooltip,\n.custom-select.is-valid ~ .invalid-feedback,\n.custom-select.is-valid ~ .invalid-tooltip {\n display: block;\n}\n\n.was-validated .form-check-input:valid + .form-check-label, .form-check-input.is-valid + .form-check-label {\n color: #28a745;\n}\n\n.was-validated .custom-control-input:valid ~ .custom-control-indicator, .custom-control-input.is-valid ~ .custom-control-indicator {\n background-color: rgba(40, 167, 69, 0.25);\n}\n\n.was-validated .custom-control-input:valid ~ .custom-control-description, .custom-control-input.is-valid ~ .custom-control-description {\n color: #28a745;\n}\n\n.was-validated .custom-file-input:valid ~ .custom-file-control, .custom-file-input.is-valid ~ .custom-file-control {\n border-color: #28a745;\n}\n\n.was-validated .custom-file-input:valid ~ .custom-file-control::before, .custom-file-input.is-valid ~ .custom-file-control::before {\n border-color: inherit;\n}\n\n.was-validated .custom-file-input:valid:focus, .custom-file-input.is-valid:focus {\n box-shadow: 0 0 0 0.2rem rgba(40, 167, 69, 0.25);\n}\n\n.was-validated .form-control:invalid, .form-control.is-invalid, .was-validated\n.custom-select:invalid,\n.custom-select.is-invalid {\n border-color: #dc3545;\n}\n\n.was-validated .form-control:invalid:focus, .form-control.is-invalid:focus, .was-validated\n.custom-select:invalid:focus,\n.custom-select.is-invalid:focus {\n box-shadow: 0 0 0 0.2rem rgba(220, 53, 69, 0.25);\n}\n\n.was-validated .form-control:invalid ~ .invalid-feedback,\n.was-validated .form-control:invalid ~ .invalid-tooltip, .form-control.is-invalid ~ .invalid-feedback,\n.form-control.is-invalid ~ .invalid-tooltip, .was-validated\n.custom-select:invalid ~ .invalid-feedback,\n.was-validated\n.custom-select:invalid ~ .invalid-tooltip,\n.custom-select.is-invalid ~ .invalid-feedback,\n.custom-select.is-invalid ~ .invalid-tooltip {\n display: block;\n}\n\n.was-validated .form-check-input:invalid + .form-check-label, .form-check-input.is-invalid + .form-check-label {\n color: #dc3545;\n}\n\n.was-validated .custom-control-input:invalid ~ .custom-control-indicator, .custom-control-input.is-invalid ~ .custom-control-indicator {\n background-color: rgba(220, 53, 69, 0.25);\n}\n\n.was-validated .custom-control-input:invalid ~ .custom-control-description, .custom-control-input.is-invalid ~ .custom-control-description {\n color: #dc3545;\n}\n\n.was-validated .custom-file-input:invalid ~ .custom-file-control, .custom-file-input.is-invalid ~ .custom-file-control {\n border-color: #dc3545;\n}\n\n.was-validated .custom-file-input:invalid ~ .custom-file-control::before, .custom-file-input.is-invalid ~ .custom-file-control::before {\n border-color: inherit;\n}\n\n.was-validated .custom-file-input:invalid:focus, .custom-file-input.is-invalid:focus {\n box-shadow: 0 0 0 0.2rem rgba(220, 53, 69, 0.25);\n}\n\n.form-inline {\n display: flex;\n flex-flow: row wrap;\n align-items: center;\n}\n\n.form-inline .form-check {\n width: 100%;\n}\n\n@media (min-width: 576px) {\n .form-inline label {\n display: flex;\n align-items: center;\n justify-content: center;\n margin-bottom: 0;\n }\n .form-inline .form-group {\n display: flex;\n flex: 0 0 auto;\n flex-flow: row wrap;\n align-items: center;\n margin-bottom: 0;\n }\n .form-inline .form-control {\n display: inline-block;\n width: auto;\n vertical-align: middle;\n }\n .form-inline .form-control-plaintext {\n display: inline-block;\n }\n .form-inline .input-group {\n width: auto;\n }\n .form-inline .form-control-label {\n margin-bottom: 0;\n vertical-align: middle;\n }\n .form-inline .form-check {\n display: flex;\n align-items: center;\n justify-content: center;\n width: auto;\n margin-top: 0;\n margin-bottom: 0;\n }\n .form-inline .form-check-label {\n padding-left: 0;\n }\n .form-inline .form-check-input {\n position: relative;\n margin-top: 0;\n margin-right: 0.25rem;\n margin-left: 0;\n }\n .form-inline .custom-control {\n display: flex;\n align-items: center;\n justify-content: center;\n padding-left: 0;\n }\n .form-inline .custom-control-indicator {\n position: static;\n display: inline-block;\n margin-right: 0.25rem;\n vertical-align: text-bottom;\n }\n .form-inline .has-feedback .form-control-feedback {\n top: 0;\n }\n}\n\n.btn {\n display: inline-block;\n font-weight: normal;\n text-align: center;\n white-space: nowrap;\n vertical-align: middle;\n user-select: none;\n border: 1px solid transparent;\n padding: 0.5rem 0.75rem;\n font-size: 1rem;\n line-height: 1.25;\n border-radius: 0.25rem;\n transition: all 0.15s ease-in-out;\n}\n\n.btn:focus, .btn:hover {\n text-decoration: none;\n}\n\n.btn:focus, .btn.focus {\n outline: 0;\n box-shadow: 0 0 0 3px rgba(0, 123, 255, 0.25);\n}\n\n.btn.disabled, .btn:disabled {\n opacity: .65;\n}\n\n.btn:active, .btn.active {\n background-image: none;\n}\n\na.btn.disabled,\nfieldset[disabled] a.btn {\n pointer-events: none;\n}\n\n.btn-primary {\n color: #fff;\n background-color: #007bff;\n border-color: #007bff;\n}\n\n.btn-primary:hover {\n color: #fff;\n background-color: #0069d9;\n border-color: #0062cc;\n}\n\n.btn-primary:focus, .btn-primary.focus {\n box-shadow: 0 0 0 3px rgba(0, 123, 255, 0.5);\n}\n\n.btn-primary.disabled, .btn-primary:disabled {\n background-color: #007bff;\n border-color: #007bff;\n}\n\n.btn-primary:active, .btn-primary.active,\n.show > .btn-primary.dropdown-toggle {\n background-color: #0069d9;\n background-image: none;\n border-color: #0062cc;\n}\n\n.btn-secondary {\n color: #fff;\n background-color: #868e96;\n border-color: #868e96;\n}\n\n.btn-secondary:hover {\n color: #fff;\n background-color: #727b84;\n border-color: #6c757d;\n}\n\n.btn-secondary:focus, .btn-secondary.focus {\n box-shadow: 0 0 0 3px rgba(134, 142, 150, 0.5);\n}\n\n.btn-secondary.disabled, .btn-secondary:disabled {\n background-color: #868e96;\n border-color: #868e96;\n}\n\n.btn-secondary:active, .btn-secondary.active,\n.show > .btn-secondary.dropdown-toggle {\n background-color: #727b84;\n background-image: none;\n border-color: #6c757d;\n}\n\n.btn-success {\n color: #fff;\n background-color: #28a745;\n border-color: #28a745;\n}\n\n.btn-success:hover {\n color: #fff;\n background-color: #218838;\n border-color: #1e7e34;\n}\n\n.btn-success:focus, .btn-success.focus {\n box-shadow: 0 0 0 3px rgba(40, 167, 69, 0.5);\n}\n\n.btn-success.disabled, .btn-success:disabled {\n background-color: #28a745;\n border-color: #28a745;\n}\n\n.btn-success:active, .btn-success.active,\n.show > .btn-success.dropdown-toggle {\n background-color: #218838;\n background-image: none;\n border-color: #1e7e34;\n}\n\n.btn-info {\n color: #fff;\n background-color: #17a2b8;\n border-color: #17a2b8;\n}\n\n.btn-info:hover {\n color: #fff;\n background-color: #138496;\n border-color: #117a8b;\n}\n\n.btn-info:focus, .btn-info.focus {\n box-shadow: 0 0 0 3px rgba(23, 162, 184, 0.5);\n}\n\n.btn-info.disabled, .btn-info:disabled {\n background-color: #17a2b8;\n border-color: #17a2b8;\n}\n\n.btn-info:active, .btn-info.active,\n.show > .btn-info.dropdown-toggle {\n background-color: #138496;\n background-image: none;\n border-color: #117a8b;\n}\n\n.btn-warning {\n color: #111;\n background-color: #ffc107;\n border-color: #ffc107;\n}\n\n.btn-warning:hover {\n color: #111;\n background-color: #e0a800;\n border-color: #d39e00;\n}\n\n.btn-warning:focus, .btn-warning.focus {\n box-shadow: 0 0 0 3px rgba(255, 193, 7, 0.5);\n}\n\n.btn-warning.disabled, .btn-warning:disabled {\n background-color: #ffc107;\n border-color: #ffc107;\n}\n\n.btn-warning:active, .btn-warning.active,\n.show > .btn-warning.dropdown-toggle {\n background-color: #e0a800;\n background-image: none;\n border-color: #d39e00;\n}\n\n.btn-danger {\n color: #fff;\n background-color: #dc3545;\n border-color: #dc3545;\n}\n\n.btn-danger:hover {\n color: #fff;\n background-color: #c82333;\n border-color: #bd2130;\n}\n\n.btn-danger:focus, .btn-danger.focus {\n box-shadow: 0 0 0 3px rgba(220, 53, 69, 0.5);\n}\n\n.btn-danger.disabled, .btn-danger:disabled {\n background-color: #dc3545;\n border-color: #dc3545;\n}\n\n.btn-danger:active, .btn-danger.active,\n.show > .btn-danger.dropdown-toggle {\n background-color: #c82333;\n background-image: none;\n border-color: #bd2130;\n}\n\n.btn-light {\n color: #111;\n background-color: #f8f9fa;\n border-color: #f8f9fa;\n}\n\n.btn-light:hover {\n color: #111;\n background-color: #e2e6ea;\n border-color: #dae0e5;\n}\n\n.btn-light:focus, .btn-light.focus {\n box-shadow: 0 0 0 3px rgba(248, 249, 250, 0.5);\n}\n\n.btn-light.disabled, .btn-light:disabled {\n background-color: #f8f9fa;\n border-color: #f8f9fa;\n}\n\n.btn-light:active, .btn-light.active,\n.show > .btn-light.dropdown-toggle {\n background-color: #e2e6ea;\n background-image: none;\n border-color: #dae0e5;\n}\n\n.btn-dark {\n color: #fff;\n background-color: #343a40;\n border-color: #343a40;\n}\n\n.btn-dark:hover {\n color: #fff;\n background-color: #23272b;\n border-color: #1d2124;\n}\n\n.btn-dark:focus, .btn-dark.focus {\n box-shadow: 0 0 0 3px rgba(52, 58, 64, 0.5);\n}\n\n.btn-dark.disabled, .btn-dark:disabled {\n background-color: #343a40;\n border-color: #343a40;\n}\n\n.btn-dark:active, .btn-dark.active,\n.show > .btn-dark.dropdown-toggle {\n background-color: #23272b;\n background-image: none;\n border-color: #1d2124;\n}\n\n.btn-outline-primary {\n color: #007bff;\n background-color: transparent;\n background-image: none;\n border-color: #007bff;\n}\n\n.btn-outline-primary:hover {\n color: #fff;\n background-color: #007bff;\n border-color: #007bff;\n}\n\n.btn-outline-primary:focus, .btn-outline-primary.focus {\n box-shadow: 0 0 0 3px rgba(0, 123, 255, 0.5);\n}\n\n.btn-outline-primary.disabled, .btn-outline-primary:disabled {\n color: #007bff;\n background-color: transparent;\n}\n\n.btn-outline-primary:active, .btn-outline-primary.active,\n.show > .btn-outline-primary.dropdown-toggle {\n color: #fff;\n background-color: #007bff;\n border-color: #007bff;\n}\n\n.btn-outline-secondary {\n color: #868e96;\n background-color: transparent;\n background-image: none;\n border-color: #868e96;\n}\n\n.btn-outline-secondary:hover {\n color: #fff;\n background-color: #868e96;\n border-color: #868e96;\n}\n\n.btn-outline-secondary:focus, .btn-outline-secondary.focus {\n box-shadow: 0 0 0 3px rgba(134, 142, 150, 0.5);\n}\n\n.btn-outline-secondary.disabled, .btn-outline-secondary:disabled {\n color: #868e96;\n background-color: transparent;\n}\n\n.btn-outline-secondary:active, .btn-outline-secondary.active,\n.show > .btn-outline-secondary.dropdown-toggle {\n color: #fff;\n background-color: #868e96;\n border-color: #868e96;\n}\n\n.btn-outline-success {\n color: #28a745;\n background-color: transparent;\n background-image: none;\n border-color: #28a745;\n}\n\n.btn-outline-success:hover {\n color: #fff;\n background-color: #28a745;\n border-color: #28a745;\n}\n\n.btn-outline-success:focus, .btn-outline-success.focus {\n box-shadow: 0 0 0 3px rgba(40, 167, 69, 0.5);\n}\n\n.btn-outline-success.disabled, .btn-outline-success:disabled {\n color: #28a745;\n background-color: transparent;\n}\n\n.btn-outline-success:active, .btn-outline-success.active,\n.show > .btn-outline-success.dropdown-toggle {\n color: #fff;\n background-color: #28a745;\n border-color: #28a745;\n}\n\n.btn-outline-info {\n color: #17a2b8;\n background-color: transparent;\n background-image: none;\n border-color: #17a2b8;\n}\n\n.btn-outline-info:hover {\n color: #fff;\n background-color: #17a2b8;\n border-color: #17a2b8;\n}\n\n.btn-outline-info:focus, .btn-outline-info.focus {\n box-shadow: 0 0 0 3px rgba(23, 162, 184, 0.5);\n}\n\n.btn-outline-info.disabled, .btn-outline-info:disabled {\n color: #17a2b8;\n background-color: transparent;\n}\n\n.btn-outline-info:active, .btn-outline-info.active,\n.show > .btn-outline-info.dropdown-toggle {\n color: #fff;\n background-color: #17a2b8;\n border-color: #17a2b8;\n}\n\n.btn-outline-warning {\n color: #ffc107;\n background-color: transparent;\n background-image: none;\n border-color: #ffc107;\n}\n\n.btn-outline-warning:hover {\n color: #fff;\n background-color: #ffc107;\n border-color: #ffc107;\n}\n\n.btn-outline-warning:focus, .btn-outline-warning.focus {\n box-shadow: 0 0 0 3px rgba(255, 193, 7, 0.5);\n}\n\n.btn-outline-warning.disabled, .btn-outline-warning:disabled {\n color: #ffc107;\n background-color: transparent;\n}\n\n.btn-outline-warning:active, .btn-outline-warning.active,\n.show > .btn-outline-warning.dropdown-toggle {\n color: #fff;\n background-color: #ffc107;\n border-color: #ffc107;\n}\n\n.btn-outline-danger {\n color: #dc3545;\n background-color: transparent;\n background-image: none;\n border-color: #dc3545;\n}\n\n.btn-outline-danger:hover {\n color: #fff;\n background-color: #dc3545;\n border-color: #dc3545;\n}\n\n.btn-outline-danger:focus, .btn-outline-danger.focus {\n box-shadow: 0 0 0 3px rgba(220, 53, 69, 0.5);\n}\n\n.btn-outline-danger.disabled, .btn-outline-danger:disabled {\n color: #dc3545;\n background-color: transparent;\n}\n\n.btn-outline-danger:active, .btn-outline-danger.active,\n.show > .btn-outline-danger.dropdown-toggle {\n color: #fff;\n background-color: #dc3545;\n border-color: #dc3545;\n}\n\n.btn-outline-light {\n color: #f8f9fa;\n background-color: transparent;\n background-image: none;\n border-color: #f8f9fa;\n}\n\n.btn-outline-light:hover {\n color: #fff;\n background-color: #f8f9fa;\n border-color: #f8f9fa;\n}\n\n.btn-outline-light:focus, .btn-outline-light.focus {\n box-shadow: 0 0 0 3px rgba(248, 249, 250, 0.5);\n}\n\n.btn-outline-light.disabled, .btn-outline-light:disabled {\n color: #f8f9fa;\n background-color: transparent;\n}\n\n.btn-outline-light:active, .btn-outline-light.active,\n.show > .btn-outline-light.dropdown-toggle {\n color: #fff;\n background-color: #f8f9fa;\n border-color: #f8f9fa;\n}\n\n.btn-outline-dark {\n color: #343a40;\n background-color: transparent;\n background-image: none;\n border-color: #343a40;\n}\n\n.btn-outline-dark:hover {\n color: #fff;\n background-color: #343a40;\n border-color: #343a40;\n}\n\n.btn-outline-dark:focus, .btn-outline-dark.focus {\n box-shadow: 0 0 0 3px rgba(52, 58, 64, 0.5);\n}\n\n.btn-outline-dark.disabled, .btn-outline-dark:disabled {\n color: #343a40;\n background-color: transparent;\n}\n\n.btn-outline-dark:active, .btn-outline-dark.active,\n.show > .btn-outline-dark.dropdown-toggle {\n color: #fff;\n background-color: #343a40;\n border-color: #343a40;\n}\n\n.btn-link {\n font-weight: normal;\n color: #007bff;\n border-radius: 0;\n}\n\n.btn-link, .btn-link:active, .btn-link.active, .btn-link:disabled {\n background-color: transparent;\n}\n\n.btn-link, .btn-link:focus, .btn-link:active {\n border-color: transparent;\n box-shadow: none;\n}\n\n.btn-link:hover {\n border-color: transparent;\n}\n\n.btn-link:focus, .btn-link:hover {\n color: #0056b3;\n text-decoration: underline;\n background-color: transparent;\n}\n\n.btn-link:disabled {\n color: #868e96;\n}\n\n.btn-link:disabled:focus, .btn-link:disabled:hover {\n text-decoration: none;\n}\n\n.btn-lg, .btn-group-lg > .btn {\n padding: 0.5rem 1rem;\n font-size: 1.25rem;\n line-height: 1.5;\n border-radius: 0.3rem;\n}\n\n.btn-sm, .btn-group-sm > .btn {\n padding: 0.25rem 0.5rem;\n font-size: 0.875rem;\n line-height: 1.5;\n border-radius: 0.2rem;\n}\n\n.btn-block {\n display: block;\n width: 100%;\n}\n\n.btn-block + .btn-block {\n margin-top: 0.5rem;\n}\n\ninput[type=\"submit\"].btn-block,\ninput[type=\"reset\"].btn-block,\ninput[type=\"button\"].btn-block {\n width: 100%;\n}\n\n.fade {\n opacity: 0;\n transition: opacity 0.15s linear;\n}\n\n.fade.show {\n opacity: 1;\n}\n\n.collapse {\n display: none;\n}\n\n.collapse.show {\n display: block;\n}\n\ntr.collapse.show {\n display: table-row;\n}\n\ntbody.collapse.show {\n display: table-row-group;\n}\n\n.collapsing {\n position: relative;\n height: 0;\n overflow: hidden;\n transition: height 0.35s ease;\n}\n\n.dropup,\n.dropdown {\n position: relative;\n}\n\n.dropdown-toggle::after {\n display: inline-block;\n width: 0;\n height: 0;\n margin-left: 0.255em;\n vertical-align: 0.255em;\n content: \"\";\n border-top: 0.3em solid;\n border-right: 0.3em solid transparent;\n border-left: 0.3em solid transparent;\n}\n\n.dropdown-toggle:empty::after {\n margin-left: 0;\n}\n\n.dropup .dropdown-menu {\n margin-top: 0;\n margin-bottom: 0.125rem;\n}\n\n.dropup .dropdown-toggle::after {\n border-top: 0;\n border-bottom: 0.3em solid;\n}\n\n.dropdown-menu {\n position: absolute;\n top: 100%;\n left: 0;\n z-index: 1000;\n display: none;\n float: left;\n min-width: 10rem;\n padding: 0.5rem 0;\n margin: 0.125rem 0 0;\n font-size: 1rem;\n color: #212529;\n text-align: left;\n list-style: none;\n background-color: #fff;\n background-clip: padding-box;\n border: 1px solid rgba(0, 0, 0, 0.15);\n border-radius: 0.25rem;\n}\n\n.dropdown-divider {\n height: 0;\n margin: 0.5rem 0;\n overflow: hidden;\n border-top: 1px solid #e9ecef;\n}\n\n.dropdown-item {\n display: block;\n width: 100%;\n padding: 0.25rem 1.5rem;\n clear: both;\n font-weight: normal;\n color: #212529;\n text-align: inherit;\n white-space: nowrap;\n background: none;\n border: 0;\n}\n\n.dropdown-item:focus, .dropdown-item:hover {\n color: #16181b;\n text-decoration: none;\n background-color: #f8f9fa;\n}\n\n.dropdown-item.active, .dropdown-item:active {\n color: #fff;\n text-decoration: none;\n background-color: #007bff;\n}\n\n.dropdown-item.disabled, .dropdown-item:disabled {\n color: #868e96;\n background-color: transparent;\n}\n\n.show > a {\n outline: 0;\n}\n\n.dropdown-menu.show {\n display: block;\n}\n\n.dropdown-header {\n display: block;\n padding: 0.5rem 1.5rem;\n margin-bottom: 0;\n font-size: 0.875rem;\n color: #868e96;\n white-space: nowrap;\n}\n\n.btn-group,\n.btn-group-vertical {\n position: relative;\n display: inline-flex;\n vertical-align: middle;\n}\n\n.btn-group > .btn,\n.btn-group-vertical > .btn {\n position: relative;\n flex: 0 1 auto;\n margin-bottom: 0;\n}\n\n.btn-group > .btn:hover,\n.btn-group-vertical > .btn:hover {\n z-index: 2;\n}\n\n.btn-group > .btn:focus, .btn-group > .btn:active, .btn-group > .btn.active,\n.btn-group-vertical > .btn:focus,\n.btn-group-vertical > .btn:active,\n.btn-group-vertical > .btn.active {\n z-index: 2;\n}\n\n.btn-group .btn + .btn,\n.btn-group .btn + .btn-group,\n.btn-group .btn-group + .btn,\n.btn-group .btn-group + .btn-group,\n.btn-group-vertical .btn + .btn,\n.btn-group-vertical .btn + .btn-group,\n.btn-group-vertical .btn-group + .btn,\n.btn-group-vertical .btn-group + .btn-group {\n margin-left: -1px;\n}\n\n.btn-toolbar {\n display: flex;\n flex-wrap: wrap;\n justify-content: flex-start;\n}\n\n.btn-toolbar .input-group {\n width: auto;\n}\n\n.btn-group > .btn:not(:first-child):not(:last-child):not(.dropdown-toggle) {\n border-radius: 0;\n}\n\n.btn-group > .btn:first-child {\n margin-left: 0;\n}\n\n.btn-group > .btn:first-child:not(:last-child):not(.dropdown-toggle) {\n border-top-right-radius: 0;\n border-bottom-right-radius: 0;\n}\n\n.btn-group > .btn:last-child:not(:first-child),\n.btn-group > .dropdown-toggle:not(:first-child) {\n border-top-left-radius: 0;\n border-bottom-left-radius: 0;\n}\n\n.btn-group > .btn-group {\n float: left;\n}\n\n.btn-group > .btn-group:not(:first-child):not(:last-child) > .btn {\n border-radius: 0;\n}\n\n.btn-group > .btn-group:first-child:not(:last-child) > .btn:last-child,\n.btn-group > .btn-group:first-child:not(:last-child) > .dropdown-toggle {\n border-top-right-radius: 0;\n border-bottom-right-radius: 0;\n}\n\n.btn-group > .btn-group:last-child:not(:first-child) > .btn:first-child {\n border-top-left-radius: 0;\n border-bottom-left-radius: 0;\n}\n\n.btn + .dropdown-toggle-split {\n padding-right: 0.5625rem;\n padding-left: 0.5625rem;\n}\n\n.btn + .dropdown-toggle-split::after {\n margin-left: 0;\n}\n\n.btn-sm + .dropdown-toggle-split, .btn-group-sm > .btn + .dropdown-toggle-split {\n padding-right: 0.375rem;\n padding-left: 0.375rem;\n}\n\n.btn-lg + .dropdown-toggle-split, .btn-group-lg > .btn + .dropdown-toggle-split {\n padding-right: 0.75rem;\n padding-left: 0.75rem;\n}\n\n.btn-group-vertical {\n display: inline-flex;\n flex-direction: column;\n align-items: flex-start;\n justify-content: center;\n}\n\n.btn-group-vertical .btn,\n.btn-group-vertical .btn-group {\n width: 100%;\n}\n\n.btn-group-vertical > .btn + .btn,\n.btn-group-vertical > .btn + .btn-group,\n.btn-group-vertical > .btn-group + .btn,\n.btn-group-vertical > .btn-group + .btn-group {\n margin-top: -1px;\n margin-left: 0;\n}\n\n.btn-group-vertical > .btn:not(:first-child):not(:last-child) {\n border-radius: 0;\n}\n\n.btn-group-vertical > .btn:first-child:not(:last-child) {\n border-bottom-right-radius: 0;\n border-bottom-left-radius: 0;\n}\n\n.btn-group-vertical > .btn:last-child:not(:first-child) {\n border-top-left-radius: 0;\n border-top-right-radius: 0;\n}\n\n.btn-group-vertical > .btn-group:not(:first-child):not(:last-child) > .btn {\n border-radius: 0;\n}\n\n.btn-group-vertical > .btn-group:first-child:not(:last-child) > .btn:last-child,\n.btn-group-vertical > .btn-group:first-child:not(:last-child) > .dropdown-toggle {\n border-bottom-right-radius: 0;\n border-bottom-left-radius: 0;\n}\n\n.btn-group-vertical > .btn-group:last-child:not(:first-child) > .btn:first-child {\n border-top-left-radius: 0;\n border-top-right-radius: 0;\n}\n\n[data-toggle=\"buttons\"] > .btn input[type=\"radio\"],\n[data-toggle=\"buttons\"] > .btn input[type=\"checkbox\"],\n[data-toggle=\"buttons\"] > .btn-group > .btn input[type=\"radio\"],\n[data-toggle=\"buttons\"] > .btn-group > .btn input[type=\"checkbox\"] {\n position: absolute;\n clip: rect(0, 0, 0, 0);\n pointer-events: none;\n}\n\n.input-group {\n position: relative;\n display: flex;\n width: 100%;\n}\n\n.input-group .form-control {\n position: relative;\n z-index: 2;\n flex: 1 1 auto;\n width: 1%;\n margin-bottom: 0;\n}\n\n.input-group .form-control:focus, .input-group .form-control:active, .input-group .form-control:hover {\n z-index: 3;\n}\n\n.input-group-addon,\n.input-group-btn,\n.input-group .form-control {\n display: flex;\n align-items: center;\n}\n\n.input-group-addon:not(:first-child):not(:last-child),\n.input-group-btn:not(:first-child):not(:last-child),\n.input-group .form-control:not(:first-child):not(:last-child) {\n border-radius: 0;\n}\n\n.input-group-addon,\n.input-group-btn {\n white-space: nowrap;\n vertical-align: middle;\n}\n\n.input-group-addon {\n padding: 0.5rem 0.75rem;\n margin-bottom: 0;\n font-size: 1rem;\n font-weight: normal;\n line-height: 1.25;\n color: #495057;\n text-align: center;\n background-color: #e9ecef;\n border: 1px solid rgba(0, 0, 0, 0.15);\n border-radius: 0.25rem;\n}\n\n.input-group-addon.form-control-sm,\n.input-group-sm > .input-group-addon,\n.input-group-sm > .input-group-btn > .input-group-addon.btn {\n padding: 0.25rem 0.5rem;\n font-size: 0.875rem;\n border-radius: 0.2rem;\n}\n\n.input-group-addon.form-control-lg,\n.input-group-lg > .input-group-addon,\n.input-group-lg > .input-group-btn > .input-group-addon.btn {\n padding: 0.5rem 1rem;\n font-size: 1.25rem;\n border-radius: 0.3rem;\n}\n\n.input-group-addon input[type=\"radio\"],\n.input-group-addon input[type=\"checkbox\"] {\n margin-top: 0;\n}\n\n.input-group .form-control:not(:last-child),\n.input-group-addon:not(:last-child),\n.input-group-btn:not(:last-child) > .btn,\n.input-group-btn:not(:last-child) > .btn-group > .btn,\n.input-group-btn:not(:last-child) > .dropdown-toggle,\n.input-group-btn:not(:first-child) > .btn:not(:last-child):not(.dropdown-toggle),\n.input-group-btn:not(:first-child) > .btn-group:not(:last-child) > .btn {\n border-top-right-radius: 0;\n border-bottom-right-radius: 0;\n}\n\n.input-group-addon:not(:last-child) {\n border-right: 0;\n}\n\n.input-group .form-control:not(:first-child),\n.input-group-addon:not(:first-child),\n.input-group-btn:not(:first-child) > .btn,\n.input-group-btn:not(:first-child) > .btn-group > .btn,\n.input-group-btn:not(:first-child) > .dropdown-toggle,\n.input-group-btn:not(:last-child) > .btn:not(:first-child),\n.input-group-btn:not(:last-child) > .btn-group:not(:first-child) > .btn {\n border-top-left-radius: 0;\n border-bottom-left-radius: 0;\n}\n\n.form-control + .input-group-addon:not(:first-child) {\n border-left: 0;\n}\n\n.input-group-btn {\n position: relative;\n font-size: 0;\n white-space: nowrap;\n}\n\n.input-group-btn > .btn {\n position: relative;\n}\n\n.input-group-btn > .btn + .btn {\n margin-left: -1px;\n}\n\n.input-group-btn > .btn:focus, .input-group-btn > .btn:active, .input-group-btn > .btn:hover {\n z-index: 3;\n}\n\n.input-group-btn:not(:last-child) > .btn,\n.input-group-btn:not(:last-child) > .btn-group {\n margin-right: -1px;\n}\n\n.input-group-btn:not(:first-child) > .btn,\n.input-group-btn:not(:first-child) > .btn-group {\n z-index: 2;\n margin-left: -1px;\n}\n\n.input-group-btn:not(:first-child) > .btn:focus, .input-group-btn:not(:first-child) > .btn:active, .input-group-btn:not(:first-child) > .btn:hover,\n.input-group-btn:not(:first-child) > .btn-group:focus,\n.input-group-btn:not(:first-child) > .btn-group:active,\n.input-group-btn:not(:first-child) > .btn-group:hover {\n z-index: 3;\n}\n\n.custom-control {\n position: relative;\n display: inline-flex;\n min-height: 1.5rem;\n padding-left: 1.5rem;\n margin-right: 1rem;\n}\n\n.custom-control-input {\n position: absolute;\n z-index: -1;\n opacity: 0;\n}\n\n.custom-control-input:checked ~ .custom-control-indicator {\n color: #fff;\n background-color: #007bff;\n}\n\n.custom-control-input:focus ~ .custom-control-indicator {\n box-shadow: 0 0 0 1px #fff, 0 0 0 3px #007bff;\n}\n\n.custom-control-input:active ~ .custom-control-indicator {\n color: #fff;\n background-color: #b3d7ff;\n}\n\n.custom-control-input:disabled ~ .custom-control-indicator {\n background-color: #e9ecef;\n}\n\n.custom-control-input:disabled ~ .custom-control-description {\n color: #868e96;\n}\n\n.custom-control-indicator {\n position: absolute;\n top: 0.25rem;\n left: 0;\n display: block;\n width: 1rem;\n height: 1rem;\n pointer-events: none;\n user-select: none;\n background-color: #ddd;\n background-repeat: no-repeat;\n background-position: center center;\n background-size: 50% 50%;\n}\n\n.custom-checkbox .custom-control-indicator {\n border-radius: 0.25rem;\n}\n\n.custom-checkbox .custom-control-input:checked ~ .custom-control-indicator {\n background-image: url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 8 8'%3E%3Cpath fill='%23fff' d='M6.564.75l-3.59 3.612-1.538-1.55L0 4.26 2.974 7.25 8 2.193z'/%3E%3C/svg%3E\");\n}\n\n.custom-checkbox .custom-control-input:indeterminate ~ .custom-control-indicator {\n background-color: #007bff;\n background-image: url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 4 4'%3E%3Cpath stroke='%23fff' d='M0 2h4'/%3E%3C/svg%3E\");\n}\n\n.custom-radio .custom-control-indicator {\n border-radius: 50%;\n}\n\n.custom-radio .custom-control-input:checked ~ .custom-control-indicator {\n background-image: url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='-4 -4 8 8'%3E%3Ccircle r='3' fill='%23fff'/%3E%3C/svg%3E\");\n}\n\n.custom-controls-stacked {\n display: flex;\n flex-direction: column;\n}\n\n.custom-controls-stacked .custom-control {\n margin-bottom: 0.25rem;\n}\n\n.custom-controls-stacked .custom-control + .custom-control {\n margin-left: 0;\n}\n\n.custom-select {\n display: inline-block;\n max-width: 100%;\n height: calc(2.25rem + 2px);\n padding: 0.375rem 1.75rem 0.375rem 0.75rem;\n line-height: 1.25;\n color: #495057;\n vertical-align: middle;\n background: #fff url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 4 5'%3E%3Cpath fill='%23333' d='M2 0L0 2h4zm0 5L0 3h4z'/%3E%3C/svg%3E\") no-repeat right 0.75rem center;\n background-size: 8px 10px;\n border: 1px solid rgba(0, 0, 0, 0.15);\n border-radius: 0.25rem;\n appearance: none;\n}\n\n.custom-select:focus {\n border-color: #80bdff;\n outline: none;\n}\n\n.custom-select:focus::-ms-value {\n color: #495057;\n background-color: #fff;\n}\n\n.custom-select:disabled {\n color: #868e96;\n background-color: #e9ecef;\n}\n\n.custom-select::-ms-expand {\n opacity: 0;\n}\n\n.custom-select-sm {\n height: calc(1.8125rem + 2px);\n padding-top: 0.375rem;\n padding-bottom: 0.375rem;\n font-size: 75%;\n}\n\n.custom-file {\n position: relative;\n display: inline-block;\n max-width: 100%;\n height: 2.5rem;\n margin-bottom: 0;\n}\n\n.custom-file-input {\n min-width: 14rem;\n max-width: 100%;\n height: 2.5rem;\n margin: 0;\n opacity: 0;\n}\n\n.custom-file-control {\n position: absolute;\n top: 0;\n right: 0;\n left: 0;\n z-index: 5;\n height: 2.5rem;\n padding: 0.5rem 1rem;\n line-height: 1.5;\n color: #495057;\n pointer-events: none;\n user-select: none;\n background-color: #fff;\n border: 1px solid rgba(0, 0, 0, 0.15);\n border-radius: 0.25rem;\n}\n\n.custom-file-control:lang(en):empty::after {\n content: \"Choose file...\";\n}\n\n.custom-file-control::before {\n position: absolute;\n top: -1px;\n right: -1px;\n bottom: -1px;\n z-index: 6;\n display: block;\n height: 2.5rem;\n padding: 0.5rem 1rem;\n line-height: 1.5;\n color: #495057;\n background-color: #e9ecef;\n border: 1px solid rgba(0, 0, 0, 0.15);\n border-radius: 0 0.25rem 0.25rem 0;\n}\n\n.custom-file-control:lang(en)::before {\n content: \"Browse\";\n}\n\n.nav {\n display: flex;\n flex-wrap: wrap;\n padding-left: 0;\n margin-bottom: 0;\n list-style: none;\n}\n\n.nav-link {\n display: block;\n padding: 0.5rem 1rem;\n}\n\n.nav-link:focus, .nav-link:hover {\n text-decoration: none;\n}\n\n.nav-link.disabled {\n color: #868e96;\n}\n\n.nav-tabs {\n border-bottom: 1px solid #ddd;\n}\n\n.nav-tabs .nav-item {\n margin-bottom: -1px;\n}\n\n.nav-tabs .nav-link {\n border: 1px solid transparent;\n border-top-left-radius: 0.25rem;\n border-top-right-radius: 0.25rem;\n}\n\n.nav-tabs .nav-link:focus, .nav-tabs .nav-link:hover {\n border-color: #e9ecef #e9ecef #ddd;\n}\n\n.nav-tabs .nav-link.disabled {\n color: #868e96;\n background-color: transparent;\n border-color: transparent;\n}\n\n.nav-tabs .nav-link.active,\n.nav-tabs .nav-item.show .nav-link {\n color: #495057;\n background-color: #fff;\n border-color: #ddd #ddd #fff;\n}\n\n.nav-tabs .dropdown-menu {\n margin-top: -1px;\n border-top-left-radius: 0;\n border-top-right-radius: 0;\n}\n\n.nav-pills .nav-link {\n border-radius: 0.25rem;\n}\n\n.nav-pills .nav-link.active,\n.show > .nav-pills .nav-link {\n color: #fff;\n background-color: #007bff;\n}\n\n.nav-fill .nav-item {\n flex: 1 1 auto;\n text-align: center;\n}\n\n.nav-justified .nav-item {\n flex-basis: 0;\n flex-grow: 1;\n text-align: center;\n}\n\n.tab-content > .tab-pane {\n display: none;\n}\n\n.tab-content > .active {\n display: block;\n}\n\n.navbar {\n position: relative;\n display: flex;\n flex-wrap: wrap;\n align-items: center;\n justify-content: space-between;\n padding: 0.5rem 1rem;\n}\n\n.navbar > .container,\n.navbar > .container-fluid {\n display: flex;\n flex-wrap: wrap;\n align-items: center;\n justify-content: space-between;\n}\n\n.navbar-brand {\n display: inline-block;\n padding-top: 0.3125rem;\n padding-bottom: 0.3125rem;\n margin-right: 1rem;\n font-size: 1.25rem;\n line-height: inherit;\n white-space: nowrap;\n}\n\n.navbar-brand:focus, .navbar-brand:hover {\n text-decoration: none;\n}\n\n.navbar-nav {\n display: flex;\n flex-direction: column;\n padding-left: 0;\n margin-bottom: 0;\n list-style: none;\n}\n\n.navbar-nav .nav-link {\n padding-right: 0;\n padding-left: 0;\n}\n\n.navbar-nav .dropdown-menu {\n position: static;\n float: none;\n}\n\n.navbar-text {\n display: inline-block;\n padding-top: 0.5rem;\n padding-bottom: 0.5rem;\n}\n\n.navbar-collapse {\n flex-basis: 100%;\n align-items: center;\n}\n\n.navbar-toggler {\n padding: 0.25rem 0.75rem;\n font-size: 1.25rem;\n line-height: 1;\n background: transparent;\n border: 1px solid transparent;\n border-radius: 0.25rem;\n}\n\n.navbar-toggler:focus, .navbar-toggler:hover {\n text-decoration: none;\n}\n\n.navbar-toggler-icon {\n display: inline-block;\n width: 1.5em;\n height: 1.5em;\n vertical-align: middle;\n content: \"\";\n background: no-repeat center center;\n background-size: 100% 100%;\n}\n\n@media (max-width: 575px) {\n .navbar-expand-sm > .container,\n .navbar-expand-sm > .container-fluid {\n padding-right: 0;\n padding-left: 0;\n }\n}\n\n@media (min-width: 576px) {\n .navbar-expand-sm {\n flex-direction: row;\n flex-wrap: nowrap;\n justify-content: flex-start;\n }\n .navbar-expand-sm .navbar-nav {\n flex-direction: row;\n }\n .navbar-expand-sm .navbar-nav .dropdown-menu {\n position: absolute;\n }\n .navbar-expand-sm .navbar-nav .dropdown-menu-right {\n right: 0;\n left: auto;\n }\n .navbar-expand-sm .navbar-nav .nav-link {\n padding-right: .5rem;\n padding-left: .5rem;\n }\n .navbar-expand-sm > .container,\n .navbar-expand-sm > .container-fluid {\n flex-wrap: nowrap;\n }\n .navbar-expand-sm .navbar-collapse {\n display: flex !important;\n }\n .navbar-expand-sm .navbar-toggler {\n display: none;\n }\n}\n\n@media (max-width: 767px) {\n .navbar-expand-md > .container,\n .navbar-expand-md > .container-fluid {\n padding-right: 0;\n padding-left: 0;\n }\n}\n\n@media (min-width: 768px) {\n .navbar-expand-md {\n flex-direction: row;\n flex-wrap: nowrap;\n justify-content: flex-start;\n }\n .navbar-expand-md .navbar-nav {\n flex-direction: row;\n }\n .navbar-expand-md .navbar-nav .dropdown-menu {\n position: absolute;\n }\n .navbar-expand-md .navbar-nav .dropdown-menu-right {\n right: 0;\n left: auto;\n }\n .navbar-expand-md .navbar-nav .nav-link {\n padding-right: .5rem;\n padding-left: .5rem;\n }\n .navbar-expand-md > .container,\n .navbar-expand-md > .container-fluid {\n flex-wrap: nowrap;\n }\n .navbar-expand-md .navbar-collapse {\n display: flex !important;\n }\n .navbar-expand-md .navbar-toggler {\n display: none;\n }\n}\n\n@media (max-width: 991px) {\n .navbar-expand-lg > .container,\n .navbar-expand-lg > .container-fluid {\n padding-right: 0;\n padding-left: 0;\n }\n}\n\n@media (min-width: 992px) {\n .navbar-expand-lg {\n flex-direction: row;\n flex-wrap: nowrap;\n justify-content: flex-start;\n }\n .navbar-expand-lg .navbar-nav {\n flex-direction: row;\n }\n .navbar-expand-lg .navbar-nav .dropdown-menu {\n position: absolute;\n }\n .navbar-expand-lg .navbar-nav .dropdown-menu-right {\n right: 0;\n left: auto;\n }\n .navbar-expand-lg .navbar-nav .nav-link {\n padding-right: .5rem;\n padding-left: .5rem;\n }\n .navbar-expand-lg > .container,\n .navbar-expand-lg > .container-fluid {\n flex-wrap: nowrap;\n }\n .navbar-expand-lg .navbar-collapse {\n display: flex !important;\n }\n .navbar-expand-lg .navbar-toggler {\n display: none;\n }\n}\n\n@media (max-width: 1199px) {\n .navbar-expand-xl > .container,\n .navbar-expand-xl > .container-fluid {\n padding-right: 0;\n padding-left: 0;\n }\n}\n\n@media (min-width: 1200px) {\n .navbar-expand-xl {\n flex-direction: row;\n flex-wrap: nowrap;\n justify-content: flex-start;\n }\n .navbar-expand-xl .navbar-nav {\n flex-direction: row;\n }\n .navbar-expand-xl .navbar-nav .dropdown-menu {\n position: absolute;\n }\n .navbar-expand-xl .navbar-nav .dropdown-menu-right {\n right: 0;\n left: auto;\n }\n .navbar-expand-xl .navbar-nav .nav-link {\n padding-right: .5rem;\n padding-left: .5rem;\n }\n .navbar-expand-xl > .container,\n .navbar-expand-xl > .container-fluid {\n flex-wrap: nowrap;\n }\n .navbar-expand-xl .navbar-collapse {\n display: flex !important;\n }\n .navbar-expand-xl .navbar-toggler {\n display: none;\n }\n}\n\n.navbar-expand {\n flex-direction: row;\n flex-wrap: nowrap;\n justify-content: flex-start;\n}\n\n.navbar-expand > .container,\n.navbar-expand > .container-fluid {\n padding-right: 0;\n padding-left: 0;\n}\n\n.navbar-expand .navbar-nav {\n flex-direction: row;\n}\n\n.navbar-expand .navbar-nav .dropdown-menu {\n position: absolute;\n}\n\n.navbar-expand .navbar-nav .dropdown-menu-right {\n right: 0;\n left: auto;\n}\n\n.navbar-expand .navbar-nav .nav-link {\n padding-right: .5rem;\n padding-left: .5rem;\n}\n\n.navbar-expand > .container,\n.navbar-expand > .container-fluid {\n flex-wrap: nowrap;\n}\n\n.navbar-expand .navbar-collapse {\n display: flex !important;\n}\n\n.navbar-expand .navbar-toggler {\n display: none;\n}\n\n.navbar-light .navbar-brand {\n color: rgba(0, 0, 0, 0.9);\n}\n\n.navbar-light .navbar-brand:focus, .navbar-light .navbar-brand:hover {\n color: rgba(0, 0, 0, 0.9);\n}\n\n.navbar-light .navbar-nav .nav-link {\n color: rgba(0, 0, 0, 0.5);\n}\n\n.navbar-light .navbar-nav .nav-link:focus, .navbar-light .navbar-nav .nav-link:hover {\n color: rgba(0, 0, 0, 0.7);\n}\n\n.navbar-light .navbar-nav .nav-link.disabled {\n color: rgba(0, 0, 0, 0.3);\n}\n\n.navbar-light .navbar-nav .show > .nav-link,\n.navbar-light .navbar-nav .active > .nav-link,\n.navbar-light .navbar-nav .nav-link.show,\n.navbar-light .navbar-nav .nav-link.active {\n color: rgba(0, 0, 0, 0.9);\n}\n\n.navbar-light .navbar-toggler {\n color: rgba(0, 0, 0, 0.5);\n border-color: rgba(0, 0, 0, 0.1);\n}\n\n.navbar-light .navbar-toggler-icon {\n background-image: url(\"data:image/svg+xml;charset=utf8,%3Csvg viewBox='0 0 30 30' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath stroke='rgba(0, 0, 0, 0.5)' stroke-width='2' stroke-linecap='round' stroke-miterlimit='10' d='M4 7h22M4 15h22M4 23h22'/%3E%3C/svg%3E\");\n}\n\n.navbar-light .navbar-text {\n color: rgba(0, 0, 0, 0.5);\n}\n\n.navbar-dark .navbar-brand {\n color: white;\n}\n\n.navbar-dark .navbar-brand:focus, .navbar-dark .navbar-brand:hover {\n color: white;\n}\n\n.navbar-dark .navbar-nav .nav-link {\n color: rgba(255, 255, 255, 0.5);\n}\n\n.navbar-dark .navbar-nav .nav-link:focus, .navbar-dark .navbar-nav .nav-link:hover {\n color: rgba(255, 255, 255, 0.75);\n}\n\n.navbar-dark .navbar-nav .nav-link.disabled {\n color: rgba(255, 255, 255, 0.25);\n}\n\n.navbar-dark .navbar-nav .show > .nav-link,\n.navbar-dark .navbar-nav .active > .nav-link,\n.navbar-dark .navbar-nav .nav-link.show,\n.navbar-dark .navbar-nav .nav-link.active {\n color: white;\n}\n\n.navbar-dark .navbar-toggler {\n color: rgba(255, 255, 255, 0.5);\n border-color: rgba(255, 255, 255, 0.1);\n}\n\n.navbar-dark .navbar-toggler-icon {\n background-image: url(\"data:image/svg+xml;charset=utf8,%3Csvg viewBox='0 0 30 30' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath stroke='rgba(255, 255, 255, 0.5)' stroke-width='2' stroke-linecap='round' stroke-miterlimit='10' d='M4 7h22M4 15h22M4 23h22'/%3E%3C/svg%3E\");\n}\n\n.navbar-dark .navbar-text {\n color: rgba(255, 255, 255, 0.5);\n}\n\n.card {\n position: relative;\n display: flex;\n flex-direction: column;\n min-width: 0;\n word-wrap: break-word;\n background-color: #fff;\n background-clip: border-box;\n border: 1px solid rgba(0, 0, 0, 0.125);\n border-radius: 0.25rem;\n}\n\n.card-body {\n flex: 1 1 auto;\n padding: 1.25rem;\n}\n\n.card-title {\n margin-bottom: 0.75rem;\n}\n\n.card-subtitle {\n margin-top: -0.375rem;\n margin-bottom: 0;\n}\n\n.card-text:last-child {\n margin-bottom: 0;\n}\n\n.card-link:hover {\n text-decoration: none;\n}\n\n.card-link + .card-link {\n margin-left: 1.25rem;\n}\n\n.card > .list-group:first-child .list-group-item:first-child {\n border-top-left-radius: 0.25rem;\n border-top-right-radius: 0.25rem;\n}\n\n.card > .list-group:last-child .list-group-item:last-child {\n border-bottom-right-radius: 0.25rem;\n border-bottom-left-radius: 0.25rem;\n}\n\n.card-header {\n padding: 0.75rem 1.25rem;\n margin-bottom: 0;\n background-color: rgba(0, 0, 0, 0.03);\n border-bottom: 1px solid rgba(0, 0, 0, 0.125);\n}\n\n.card-header:first-child {\n border-radius: calc(0.25rem - 1px) calc(0.25rem - 1px) 0 0;\n}\n\n.card-footer {\n padding: 0.75rem 1.25rem;\n background-color: rgba(0, 0, 0, 0.03);\n border-top: 1px solid rgba(0, 0, 0, 0.125);\n}\n\n.card-footer:last-child {\n border-radius: 0 0 calc(0.25rem - 1px) calc(0.25rem - 1px);\n}\n\n.card-header-tabs {\n margin-right: -0.625rem;\n margin-bottom: -0.75rem;\n margin-left: -0.625rem;\n border-bottom: 0;\n}\n\n.card-header-pills {\n margin-right: -0.625rem;\n margin-left: -0.625rem;\n}\n\n.card-img-overlay {\n position: absolute;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n padding: 1.25rem;\n}\n\n.card-img {\n width: 100%;\n border-radius: calc(0.25rem - 1px);\n}\n\n.card-img-top {\n width: 100%;\n border-top-left-radius: calc(0.25rem - 1px);\n border-top-right-radius: calc(0.25rem - 1px);\n}\n\n.card-img-bottom {\n width: 100%;\n border-bottom-right-radius: calc(0.25rem - 1px);\n border-bottom-left-radius: calc(0.25rem - 1px);\n}\n\n@media (min-width: 576px) {\n .card-deck {\n display: flex;\n flex-flow: row wrap;\n margin-right: -15px;\n margin-left: -15px;\n }\n .card-deck .card {\n display: flex;\n flex: 1 0 0%;\n flex-direction: column;\n margin-right: 15px;\n margin-left: 15px;\n }\n}\n\n@media (min-width: 576px) {\n .card-group {\n display: flex;\n flex-flow: row wrap;\n }\n .card-group .card {\n flex: 1 0 0%;\n }\n .card-group .card + .card {\n margin-left: 0;\n border-left: 0;\n }\n .card-group .card:first-child {\n border-top-right-radius: 0;\n border-bottom-right-radius: 0;\n }\n .card-group .card:first-child .card-img-top {\n border-top-right-radius: 0;\n }\n .card-group .card:first-child .card-img-bottom {\n border-bottom-right-radius: 0;\n }\n .card-group .card:last-child {\n border-top-left-radius: 0;\n border-bottom-left-radius: 0;\n }\n .card-group .card:last-child .card-img-top {\n border-top-left-radius: 0;\n }\n .card-group .card:last-child .card-img-bottom {\n border-bottom-left-radius: 0;\n }\n .card-group .card:not(:first-child):not(:last-child) {\n border-radius: 0;\n }\n .card-group .card:not(:first-child):not(:last-child) .card-img-top,\n .card-group .card:not(:first-child):not(:last-child) .card-img-bottom {\n border-radius: 0;\n }\n}\n\n.card-columns .card {\n margin-bottom: 0.75rem;\n}\n\n@media (min-width: 576px) {\n .card-columns {\n column-count: 3;\n column-gap: 1.25rem;\n }\n .card-columns .card {\n display: inline-block;\n width: 100%;\n }\n}\n\n.breadcrumb {\n padding: 0.75rem 1rem;\n margin-bottom: 1rem;\n list-style: none;\n background-color: #e9ecef;\n border-radius: 0.25rem;\n}\n\n.breadcrumb::after {\n display: block;\n clear: both;\n content: \"\";\n}\n\n.breadcrumb-item {\n float: left;\n}\n\n.breadcrumb-item + .breadcrumb-item::before {\n display: inline-block;\n padding-right: 0.5rem;\n padding-left: 0.5rem;\n color: #868e96;\n content: \"/\";\n}\n\n.breadcrumb-item + .breadcrumb-item:hover::before {\n text-decoration: underline;\n}\n\n.breadcrumb-item + .breadcrumb-item:hover::before {\n text-decoration: none;\n}\n\n.breadcrumb-item.active {\n color: #868e96;\n}\n\n.pagination {\n display: flex;\n padding-left: 0;\n list-style: none;\n border-radius: 0.25rem;\n}\n\n.page-item:first-child .page-link {\n margin-left: 0;\n border-top-left-radius: 0.25rem;\n border-bottom-left-radius: 0.25rem;\n}\n\n.page-item:last-child .page-link {\n border-top-right-radius: 0.25rem;\n border-bottom-right-radius: 0.25rem;\n}\n\n.page-item.active .page-link {\n z-index: 2;\n color: #fff;\n background-color: #007bff;\n border-color: #007bff;\n}\n\n.page-item.disabled .page-link {\n color: #868e96;\n pointer-events: none;\n background-color: #fff;\n border-color: #ddd;\n}\n\n.page-link {\n position: relative;\n display: block;\n padding: 0.5rem 0.75rem;\n margin-left: -1px;\n line-height: 1.25;\n color: #007bff;\n background-color: #fff;\n border: 1px solid #ddd;\n}\n\n.page-link:focus, .page-link:hover {\n color: #0056b3;\n text-decoration: none;\n background-color: #e9ecef;\n border-color: #ddd;\n}\n\n.pagination-lg .page-link {\n padding: 0.75rem 1.5rem;\n font-size: 1.25rem;\n line-height: 1.5;\n}\n\n.pagination-lg .page-item:first-child .page-link {\n border-top-left-radius: 0.3rem;\n border-bottom-left-radius: 0.3rem;\n}\n\n.pagination-lg .page-item:last-child .page-link {\n border-top-right-radius: 0.3rem;\n border-bottom-right-radius: 0.3rem;\n}\n\n.pagination-sm .page-link {\n padding: 0.25rem 0.5rem;\n font-size: 0.875rem;\n line-height: 1.5;\n}\n\n.pagination-sm .page-item:first-child .page-link {\n border-top-left-radius: 0.2rem;\n border-bottom-left-radius: 0.2rem;\n}\n\n.pagination-sm .page-item:last-child .page-link {\n border-top-right-radius: 0.2rem;\n border-bottom-right-radius: 0.2rem;\n}\n\n.badge {\n display: inline-block;\n padding: 0.25em 0.4em;\n font-size: 75%;\n font-weight: bold;\n line-height: 1;\n color: #fff;\n text-align: center;\n white-space: nowrap;\n vertical-align: baseline;\n border-radius: 0.25rem;\n}\n\n.badge:empty {\n display: none;\n}\n\n.btn .badge {\n position: relative;\n top: -1px;\n}\n\n.badge-pill {\n padding-right: 0.6em;\n padding-left: 0.6em;\n border-radius: 10rem;\n}\n\n.badge-primary {\n color: #fff;\n background-color: #007bff;\n}\n\n.badge-primary[href]:focus, .badge-primary[href]:hover {\n color: #fff;\n text-decoration: none;\n background-color: #0062cc;\n}\n\n.badge-secondary {\n color: #fff;\n background-color: #868e96;\n}\n\n.badge-secondary[href]:focus, .badge-secondary[href]:hover {\n color: #fff;\n text-decoration: none;\n background-color: #6c757d;\n}\n\n.badge-success {\n color: #fff;\n background-color: #28a745;\n}\n\n.badge-success[href]:focus, .badge-success[href]:hover {\n color: #fff;\n text-decoration: none;\n background-color: #1e7e34;\n}\n\n.badge-info {\n color: #fff;\n background-color: #17a2b8;\n}\n\n.badge-info[href]:focus, .badge-info[href]:hover {\n color: #fff;\n text-decoration: none;\n background-color: #117a8b;\n}\n\n.badge-warning {\n color: #111;\n background-color: #ffc107;\n}\n\n.badge-warning[href]:focus, .badge-warning[href]:hover {\n color: #111;\n text-decoration: none;\n background-color: #d39e00;\n}\n\n.badge-danger {\n color: #fff;\n background-color: #dc3545;\n}\n\n.badge-danger[href]:focus, .badge-danger[href]:hover {\n color: #fff;\n text-decoration: none;\n background-color: #bd2130;\n}\n\n.badge-light {\n color: #111;\n background-color: #f8f9fa;\n}\n\n.badge-light[href]:focus, .badge-light[href]:hover {\n color: #111;\n text-decoration: none;\n background-color: #dae0e5;\n}\n\n.badge-dark {\n color: #fff;\n background-color: #343a40;\n}\n\n.badge-dark[href]:focus, .badge-dark[href]:hover {\n color: #fff;\n text-decoration: none;\n background-color: #1d2124;\n}\n\n.jumbotron {\n padding: 2rem 1rem;\n margin-bottom: 2rem;\n background-color: #e9ecef;\n border-radius: 0.3rem;\n}\n\n@media (min-width: 576px) {\n .jumbotron {\n padding: 4rem 2rem;\n }\n}\n\n.jumbotron-fluid {\n padding-right: 0;\n padding-left: 0;\n border-radius: 0;\n}\n\n.alert {\n padding: 0.75rem 1.25rem;\n margin-bottom: 1rem;\n border: 1px solid transparent;\n border-radius: 0.25rem;\n}\n\n.alert-heading {\n color: inherit;\n}\n\n.alert-link {\n font-weight: bold;\n}\n\n.alert-dismissible .close {\n position: relative;\n top: -0.75rem;\n right: -1.25rem;\n padding: 0.75rem 1.25rem;\n color: inherit;\n}\n\n.alert-primary {\n color: #004085;\n background-color: #cce5ff;\n border-color: #b8daff;\n}\n\n.alert-primary hr {\n border-top-color: #9fcdff;\n}\n\n.alert-primary .alert-link {\n color: #002752;\n}\n\n.alert-secondary {\n color: #464a4e;\n background-color: #e7e8ea;\n border-color: #dddfe2;\n}\n\n.alert-secondary hr {\n border-top-color: #cfd2d6;\n}\n\n.alert-secondary .alert-link {\n color: #2e3133;\n}\n\n.alert-success {\n color: #155724;\n background-color: #d4edda;\n border-color: #c3e6cb;\n}\n\n.alert-success hr {\n border-top-color: #b1dfbb;\n}\n\n.alert-success .alert-link {\n color: #0b2e13;\n}\n\n.alert-info {\n color: #0c5460;\n background-color: #d1ecf1;\n border-color: #bee5eb;\n}\n\n.alert-info hr {\n border-top-color: #abdde5;\n}\n\n.alert-info .alert-link {\n color: #062c33;\n}\n\n.alert-warning {\n color: #856404;\n background-color: #fff3cd;\n border-color: #ffeeba;\n}\n\n.alert-warning hr {\n border-top-color: #ffe8a1;\n}\n\n.alert-warning .alert-link {\n color: #533f03;\n}\n\n.alert-danger {\n color: #721c24;\n background-color: #f8d7da;\n border-color: #f5c6cb;\n}\n\n.alert-danger hr {\n border-top-color: #f1b0b7;\n}\n\n.alert-danger .alert-link {\n color: #491217;\n}\n\n.alert-light {\n color: #818182;\n background-color: #fefefe;\n border-color: #fdfdfe;\n}\n\n.alert-light hr {\n border-top-color: #ececf6;\n}\n\n.alert-light .alert-link {\n color: #686868;\n}\n\n.alert-dark {\n color: #1b1e21;\n background-color: #d6d8d9;\n border-color: #c6c8ca;\n}\n\n.alert-dark hr {\n border-top-color: #b9bbbe;\n}\n\n.alert-dark .alert-link {\n color: #040505;\n}\n\n@keyframes progress-bar-stripes {\n from {\n background-position: 1rem 0;\n }\n to {\n background-position: 0 0;\n }\n}\n\n.progress {\n display: flex;\n overflow: hidden;\n font-size: 0.75rem;\n line-height: 1rem;\n text-align: center;\n background-color: #e9ecef;\n border-radius: 0.25rem;\n}\n\n.progress-bar {\n height: 1rem;\n line-height: 1rem;\n color: #fff;\n background-color: #007bff;\n transition: width 0.6s ease;\n}\n\n.progress-bar-striped {\n background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-size: 1rem 1rem;\n}\n\n.progress-bar-animated {\n animation: progress-bar-stripes 1s linear infinite;\n}\n\n.media {\n display: flex;\n align-items: flex-start;\n}\n\n.media-body {\n flex: 1;\n}\n\n.list-group {\n display: flex;\n flex-direction: column;\n padding-left: 0;\n margin-bottom: 0;\n}\n\n.list-group-item-action {\n width: 100%;\n color: #495057;\n text-align: inherit;\n}\n\n.list-group-item-action:focus, .list-group-item-action:hover {\n color: #495057;\n text-decoration: none;\n background-color: #f8f9fa;\n}\n\n.list-group-item-action:active {\n color: #212529;\n background-color: #e9ecef;\n}\n\n.list-group-item {\n position: relative;\n display: block;\n padding: 0.75rem 1.25rem;\n margin-bottom: -1px;\n background-color: #fff;\n border: 1px solid rgba(0, 0, 0, 0.125);\n}\n\n.list-group-item:first-child {\n border-top-left-radius: 0.25rem;\n border-top-right-radius: 0.25rem;\n}\n\n.list-group-item:last-child {\n margin-bottom: 0;\n border-bottom-right-radius: 0.25rem;\n border-bottom-left-radius: 0.25rem;\n}\n\n.list-group-item:focus, .list-group-item:hover {\n text-decoration: none;\n}\n\n.list-group-item.disabled, .list-group-item:disabled {\n color: #868e96;\n background-color: #fff;\n}\n\n.list-group-item.active {\n z-index: 2;\n color: #fff;\n background-color: #007bff;\n border-color: #007bff;\n}\n\n.list-group-flush .list-group-item {\n border-right: 0;\n border-left: 0;\n border-radius: 0;\n}\n\n.list-group-flush:first-child .list-group-item:first-child {\n border-top: 0;\n}\n\n.list-group-flush:last-child .list-group-item:last-child {\n border-bottom: 0;\n}\n\n.list-group-item-primary {\n color: #004085;\n background-color: #b8daff;\n}\n\na.list-group-item-primary,\nbutton.list-group-item-primary {\n color: #004085;\n}\n\na.list-group-item-primary:focus, a.list-group-item-primary:hover,\nbutton.list-group-item-primary:focus,\nbutton.list-group-item-primary:hover {\n color: #004085;\n background-color: #9fcdff;\n}\n\na.list-group-item-primary.active,\nbutton.list-group-item-primary.active {\n color: #fff;\n background-color: #004085;\n border-color: #004085;\n}\n\n.list-group-item-secondary {\n color: #464a4e;\n background-color: #dddfe2;\n}\n\na.list-group-item-secondary,\nbutton.list-group-item-secondary {\n color: #464a4e;\n}\n\na.list-group-item-secondary:focus, a.list-group-item-secondary:hover,\nbutton.list-group-item-secondary:focus,\nbutton.list-group-item-secondary:hover {\n color: #464a4e;\n background-color: #cfd2d6;\n}\n\na.list-group-item-secondary.active,\nbutton.list-group-item-secondary.active {\n color: #fff;\n background-color: #464a4e;\n border-color: #464a4e;\n}\n\n.list-group-item-success {\n color: #155724;\n background-color: #c3e6cb;\n}\n\na.list-group-item-success,\nbutton.list-group-item-success {\n color: #155724;\n}\n\na.list-group-item-success:focus, a.list-group-item-success:hover,\nbutton.list-group-item-success:focus,\nbutton.list-group-item-success:hover {\n color: #155724;\n background-color: #b1dfbb;\n}\n\na.list-group-item-success.active,\nbutton.list-group-item-success.active {\n color: #fff;\n background-color: #155724;\n border-color: #155724;\n}\n\n.list-group-item-info {\n color: #0c5460;\n background-color: #bee5eb;\n}\n\na.list-group-item-info,\nbutton.list-group-item-info {\n color: #0c5460;\n}\n\na.list-group-item-info:focus, a.list-group-item-info:hover,\nbutton.list-group-item-info:focus,\nbutton.list-group-item-info:hover {\n color: #0c5460;\n background-color: #abdde5;\n}\n\na.list-group-item-info.active,\nbutton.list-group-item-info.active {\n color: #fff;\n background-color: #0c5460;\n border-color: #0c5460;\n}\n\n.list-group-item-warning {\n color: #856404;\n background-color: #ffeeba;\n}\n\na.list-group-item-warning,\nbutton.list-group-item-warning {\n color: #856404;\n}\n\na.list-group-item-warning:focus, a.list-group-item-warning:hover,\nbutton.list-group-item-warning:focus,\nbutton.list-group-item-warning:hover {\n color: #856404;\n background-color: #ffe8a1;\n}\n\na.list-group-item-warning.active,\nbutton.list-group-item-warning.active {\n color: #fff;\n background-color: #856404;\n border-color: #856404;\n}\n\n.list-group-item-danger {\n color: #721c24;\n background-color: #f5c6cb;\n}\n\na.list-group-item-danger,\nbutton.list-group-item-danger {\n color: #721c24;\n}\n\na.list-group-item-danger:focus, a.list-group-item-danger:hover,\nbutton.list-group-item-danger:focus,\nbutton.list-group-item-danger:hover {\n color: #721c24;\n background-color: #f1b0b7;\n}\n\na.list-group-item-danger.active,\nbutton.list-group-item-danger.active {\n color: #fff;\n background-color: #721c24;\n border-color: #721c24;\n}\n\n.list-group-item-light {\n color: #818182;\n background-color: #fdfdfe;\n}\n\na.list-group-item-light,\nbutton.list-group-item-light {\n color: #818182;\n}\n\na.list-group-item-light:focus, a.list-group-item-light:hover,\nbutton.list-group-item-light:focus,\nbutton.list-group-item-light:hover {\n color: #818182;\n background-color: #ececf6;\n}\n\na.list-group-item-light.active,\nbutton.list-group-item-light.active {\n color: #fff;\n background-color: #818182;\n border-color: #818182;\n}\n\n.list-group-item-dark {\n color: #1b1e21;\n background-color: #c6c8ca;\n}\n\na.list-group-item-dark,\nbutton.list-group-item-dark {\n color: #1b1e21;\n}\n\na.list-group-item-dark:focus, a.list-group-item-dark:hover,\nbutton.list-group-item-dark:focus,\nbutton.list-group-item-dark:hover {\n color: #1b1e21;\n background-color: #b9bbbe;\n}\n\na.list-group-item-dark.active,\nbutton.list-group-item-dark.active {\n color: #fff;\n background-color: #1b1e21;\n border-color: #1b1e21;\n}\n\n.close {\n float: right;\n font-size: 1.5rem;\n font-weight: bold;\n line-height: 1;\n color: #000;\n text-shadow: 0 1px 0 #fff;\n opacity: .5;\n}\n\n.close:focus, .close:hover {\n color: #000;\n text-decoration: none;\n opacity: .75;\n}\n\nbutton.close {\n padding: 0;\n background: transparent;\n border: 0;\n -webkit-appearance: none;\n}\n\n.modal-open {\n overflow: hidden;\n}\n\n.modal {\n position: fixed;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: 1050;\n display: none;\n overflow: hidden;\n outline: 0;\n}\n\n.modal.fade .modal-dialog {\n transition: transform 0.3s ease-out;\n transform: translate(0, -25%);\n}\n\n.modal.show .modal-dialog {\n transform: translate(0, 0);\n}\n\n.modal-open .modal {\n overflow-x: hidden;\n overflow-y: auto;\n}\n\n.modal-dialog {\n position: relative;\n width: auto;\n margin: 10px;\n}\n\n.modal-content {\n position: relative;\n display: flex;\n flex-direction: column;\n background-color: #fff;\n background-clip: padding-box;\n border: 1px solid rgba(0, 0, 0, 0.2);\n border-radius: 0.3rem;\n outline: 0;\n}\n\n.modal-backdrop {\n position: fixed;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: 1040;\n background-color: #000;\n}\n\n.modal-backdrop.fade {\n opacity: 0;\n}\n\n.modal-backdrop.show {\n opacity: 0.5;\n}\n\n.modal-header {\n display: flex;\n align-items: center;\n justify-content: space-between;\n padding: 15px;\n border-bottom: 1px solid #e9ecef;\n}\n\n.modal-title {\n margin-bottom: 0;\n line-height: 1.5;\n}\n\n.modal-body {\n position: relative;\n flex: 1 1 auto;\n padding: 15px;\n}\n\n.modal-footer {\n display: flex;\n align-items: center;\n justify-content: flex-end;\n padding: 15px;\n border-top: 1px solid #e9ecef;\n}\n\n.modal-footer > :not(:first-child) {\n margin-left: .25rem;\n}\n\n.modal-footer > :not(:last-child) {\n margin-right: .25rem;\n}\n\n.modal-scrollbar-measure {\n position: absolute;\n top: -9999px;\n width: 50px;\n height: 50px;\n overflow: scroll;\n}\n\n@media (min-width: 576px) {\n .modal-dialog {\n max-width: 500px;\n margin: 30px auto;\n }\n .modal-sm {\n max-width: 300px;\n }\n}\n\n@media (min-width: 992px) {\n .modal-lg {\n max-width: 800px;\n }\n}\n\n.tooltip {\n position: absolute;\n z-index: 1070;\n display: block;\n margin: 0;\n font-family: -apple-system, BlinkMacSystemFont, \"Segoe UI\", Roboto, \"Helvetica Neue\", Arial, sans-serif;\n font-style: normal;\n font-weight: normal;\n line-height: 1.5;\n text-align: left;\n text-align: start;\n text-decoration: none;\n text-shadow: none;\n text-transform: none;\n letter-spacing: normal;\n word-break: normal;\n word-spacing: normal;\n white-space: normal;\n line-break: auto;\n font-size: 0.875rem;\n word-wrap: break-word;\n opacity: 0;\n}\n\n.tooltip.show {\n opacity: 0.9;\n}\n\n.tooltip .arrow {\n position: absolute;\n display: block;\n width: 5px;\n height: 5px;\n}\n\n.tooltip.bs-tooltip-top, .tooltip.bs-tooltip-auto[x-placement^=\"top\"] {\n padding: 5px 0;\n}\n\n.tooltip.bs-tooltip-top .arrow, .tooltip.bs-tooltip-auto[x-placement^=\"top\"] .arrow {\n bottom: 0;\n}\n\n.tooltip.bs-tooltip-top .arrow::before, .tooltip.bs-tooltip-auto[x-placement^=\"top\"] .arrow::before {\n margin-left: -3px;\n content: \"\";\n border-width: 5px 5px 0;\n border-top-color: #000;\n}\n\n.tooltip.bs-tooltip-right, .tooltip.bs-tooltip-auto[x-placement^=\"right\"] {\n padding: 0 5px;\n}\n\n.tooltip.bs-tooltip-right .arrow, .tooltip.bs-tooltip-auto[x-placement^=\"right\"] .arrow {\n left: 0;\n}\n\n.tooltip.bs-tooltip-right .arrow::before, .tooltip.bs-tooltip-auto[x-placement^=\"right\"] .arrow::before {\n margin-top: -3px;\n content: \"\";\n border-width: 5px 5px 5px 0;\n border-right-color: #000;\n}\n\n.tooltip.bs-tooltip-bottom, .tooltip.bs-tooltip-auto[x-placement^=\"bottom\"] {\n padding: 5px 0;\n}\n\n.tooltip.bs-tooltip-bottom .arrow, .tooltip.bs-tooltip-auto[x-placement^=\"bottom\"] .arrow {\n top: 0;\n}\n\n.tooltip.bs-tooltip-bottom .arrow::before, .tooltip.bs-tooltip-auto[x-placement^=\"bottom\"] .arrow::before {\n margin-left: -3px;\n content: \"\";\n border-width: 0 5px 5px;\n border-bottom-color: #000;\n}\n\n.tooltip.bs-tooltip-left, .tooltip.bs-tooltip-auto[x-placement^=\"left\"] {\n padding: 0 5px;\n}\n\n.tooltip.bs-tooltip-left .arrow, .tooltip.bs-tooltip-auto[x-placement^=\"left\"] .arrow {\n right: 0;\n}\n\n.tooltip.bs-tooltip-left .arrow::before, .tooltip.bs-tooltip-auto[x-placement^=\"left\"] .arrow::before {\n right: 0;\n margin-top: -3px;\n content: \"\";\n border-width: 5px 0 5px 5px;\n border-left-color: #000;\n}\n\n.tooltip .arrow::before {\n position: absolute;\n border-color: transparent;\n border-style: solid;\n}\n\n.tooltip-inner {\n max-width: 200px;\n padding: 3px 8px;\n color: #fff;\n text-align: center;\n background-color: #000;\n border-radius: 0.25rem;\n}\n\n.popover {\n position: absolute;\n top: 0;\n left: 0;\n z-index: 1060;\n display: block;\n max-width: 276px;\n padding: 1px;\n font-family: -apple-system, BlinkMacSystemFont, \"Segoe UI\", Roboto, \"Helvetica Neue\", Arial, sans-serif;\n font-style: normal;\n font-weight: normal;\n line-height: 1.5;\n text-align: left;\n text-align: start;\n text-decoration: none;\n text-shadow: none;\n text-transform: none;\n letter-spacing: normal;\n word-break: normal;\n word-spacing: normal;\n white-space: normal;\n line-break: auto;\n font-size: 0.875rem;\n word-wrap: break-word;\n background-color: #fff;\n background-clip: padding-box;\n border: 1px solid rgba(0, 0, 0, 0.2);\n border-radius: 0.3rem;\n}\n\n.popover .arrow {\n position: absolute;\n display: block;\n width: 10px;\n height: 5px;\n}\n\n.popover .arrow::before,\n.popover .arrow::after {\n position: absolute;\n display: block;\n border-color: transparent;\n border-style: solid;\n}\n\n.popover .arrow::before {\n content: \"\";\n border-width: 11px;\n}\n\n.popover .arrow::after {\n content: \"\";\n border-width: 11px;\n}\n\n.popover.bs-popover-top, .popover.bs-popover-auto[x-placement^=\"top\"] {\n margin-bottom: 10px;\n}\n\n.popover.bs-popover-top .arrow, .popover.bs-popover-auto[x-placement^=\"top\"] .arrow {\n bottom: 0;\n}\n\n.popover.bs-popover-top .arrow::before, .popover.bs-popover-auto[x-placement^=\"top\"] .arrow::before,\n.popover.bs-popover-top .arrow::after, .popover.bs-popover-auto[x-placement^=\"top\"] .arrow::after {\n border-bottom-width: 0;\n}\n\n.popover.bs-popover-top .arrow::before, .popover.bs-popover-auto[x-placement^=\"top\"] .arrow::before {\n bottom: -11px;\n margin-left: -6px;\n border-top-color: rgba(0, 0, 0, 0.25);\n}\n\n.popover.bs-popover-top .arrow::after, .popover.bs-popover-auto[x-placement^=\"top\"] .arrow::after {\n bottom: -10px;\n margin-left: -6px;\n border-top-color: #fff;\n}\n\n.popover.bs-popover-right, .popover.bs-popover-auto[x-placement^=\"right\"] {\n margin-left: 10px;\n}\n\n.popover.bs-popover-right .arrow, .popover.bs-popover-auto[x-placement^=\"right\"] .arrow {\n left: 0;\n}\n\n.popover.bs-popover-right .arrow::before, .popover.bs-popover-auto[x-placement^=\"right\"] .arrow::before,\n.popover.bs-popover-right .arrow::after, .popover.bs-popover-auto[x-placement^=\"right\"] .arrow::after {\n margin-top: -8px;\n border-left-width: 0;\n}\n\n.popover.bs-popover-right .arrow::before, .popover.bs-popover-auto[x-placement^=\"right\"] .arrow::before {\n left: -11px;\n border-right-color: rgba(0, 0, 0, 0.25);\n}\n\n.popover.bs-popover-right .arrow::after, .popover.bs-popover-auto[x-placement^=\"right\"] .arrow::after {\n left: -10px;\n border-right-color: #fff;\n}\n\n.popover.bs-popover-bottom, .popover.bs-popover-auto[x-placement^=\"bottom\"] {\n margin-top: 10px;\n}\n\n.popover.bs-popover-bottom .arrow, .popover.bs-popover-auto[x-placement^=\"bottom\"] .arrow {\n top: 0;\n}\n\n.popover.bs-popover-bottom .arrow::before, .popover.bs-popover-auto[x-placement^=\"bottom\"] .arrow::before,\n.popover.bs-popover-bottom .arrow::after, .popover.bs-popover-auto[x-placement^=\"bottom\"] .arrow::after {\n margin-left: -7px;\n border-top-width: 0;\n}\n\n.popover.bs-popover-bottom .arrow::before, .popover.bs-popover-auto[x-placement^=\"bottom\"] .arrow::before {\n top: -11px;\n border-bottom-color: rgba(0, 0, 0, 0.25);\n}\n\n.popover.bs-popover-bottom .arrow::after, .popover.bs-popover-auto[x-placement^=\"bottom\"] .arrow::after {\n top: -10px;\n border-bottom-color: #fff;\n}\n\n.popover.bs-popover-bottom .popover-header::before, .popover.bs-popover-auto[x-placement^=\"bottom\"] .popover-header::before {\n position: absolute;\n top: 0;\n left: 50%;\n display: block;\n width: 20px;\n margin-left: -10px;\n content: \"\";\n border-bottom: 1px solid #f7f7f7;\n}\n\n.popover.bs-popover-left, .popover.bs-popover-auto[x-placement^=\"left\"] {\n margin-right: 10px;\n}\n\n.popover.bs-popover-left .arrow, .popover.bs-popover-auto[x-placement^=\"left\"] .arrow {\n right: 0;\n}\n\n.popover.bs-popover-left .arrow::before, .popover.bs-popover-auto[x-placement^=\"left\"] .arrow::before,\n.popover.bs-popover-left .arrow::after, .popover.bs-popover-auto[x-placement^=\"left\"] .arrow::after {\n margin-top: -8px;\n border-right-width: 0;\n}\n\n.popover.bs-popover-left .arrow::before, .popover.bs-popover-auto[x-placement^=\"left\"] .arrow::before {\n right: -11px;\n border-left-color: rgba(0, 0, 0, 0.25);\n}\n\n.popover.bs-popover-left .arrow::after, .popover.bs-popover-auto[x-placement^=\"left\"] .arrow::after {\n right: -10px;\n border-left-color: #fff;\n}\n\n.popover-header {\n padding: 8px 14px;\n margin-bottom: 0;\n font-size: 1rem;\n color: inherit;\n background-color: #f7f7f7;\n border-bottom: 1px solid #ebebeb;\n border-top-left-radius: calc(0.3rem - 1px);\n border-top-right-radius: calc(0.3rem - 1px);\n}\n\n.popover-header:empty {\n display: none;\n}\n\n.popover-body {\n padding: 9px 14px;\n color: #212529;\n}\n\n.carousel {\n position: relative;\n}\n\n.carousel-inner {\n position: relative;\n width: 100%;\n overflow: hidden;\n}\n\n.carousel-item {\n position: relative;\n display: none;\n align-items: center;\n width: 100%;\n transition: transform 0.6s ease;\n backface-visibility: hidden;\n perspective: 1000px;\n}\n\n.carousel-item.active,\n.carousel-item-next,\n.carousel-item-prev {\n display: block;\n}\n\n.carousel-item-next,\n.carousel-item-prev {\n position: absolute;\n top: 0;\n}\n\n.carousel-item-next.carousel-item-left,\n.carousel-item-prev.carousel-item-right {\n transform: translateX(0);\n}\n\n@supports (transform-style: preserve-3d) {\n .carousel-item-next.carousel-item-left,\n .carousel-item-prev.carousel-item-right {\n transform: translate3d(0, 0, 0);\n }\n}\n\n.carousel-item-next,\n.active.carousel-item-right {\n transform: translateX(100%);\n}\n\n@supports (transform-style: preserve-3d) {\n .carousel-item-next,\n .active.carousel-item-right {\n transform: translate3d(100%, 0, 0);\n }\n}\n\n.carousel-item-prev,\n.active.carousel-item-left {\n transform: translateX(-100%);\n}\n\n@supports (transform-style: preserve-3d) {\n .carousel-item-prev,\n .active.carousel-item-left {\n transform: translate3d(-100%, 0, 0);\n }\n}\n\n.carousel-control-prev,\n.carousel-control-next {\n position: absolute;\n top: 0;\n bottom: 0;\n display: flex;\n align-items: center;\n justify-content: center;\n width: 15%;\n color: #fff;\n text-align: center;\n opacity: 0.5;\n}\n\n.carousel-control-prev:focus, .carousel-control-prev:hover,\n.carousel-control-next:focus,\n.carousel-control-next:hover {\n color: #fff;\n text-decoration: none;\n outline: 0;\n opacity: .9;\n}\n\n.carousel-control-prev {\n left: 0;\n}\n\n.carousel-control-next {\n right: 0;\n}\n\n.carousel-control-prev-icon,\n.carousel-control-next-icon {\n display: inline-block;\n width: 20px;\n height: 20px;\n background: transparent no-repeat center center;\n background-size: 100% 100%;\n}\n\n.carousel-control-prev-icon {\n background-image: url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' fill='%23fff' viewBox='0 0 8 8'%3E%3Cpath d='M4 0l-4 4 4 4 1.5-1.5-2.5-2.5 2.5-2.5-1.5-1.5z'/%3E%3C/svg%3E\");\n}\n\n.carousel-control-next-icon {\n background-image: url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' fill='%23fff' viewBox='0 0 8 8'%3E%3Cpath d='M1.5 0l-1.5 1.5 2.5 2.5-2.5 2.5 1.5 1.5 4-4-4-4z'/%3E%3C/svg%3E\");\n}\n\n.carousel-indicators {\n position: absolute;\n right: 0;\n bottom: 10px;\n left: 0;\n z-index: 15;\n display: flex;\n justify-content: center;\n padding-left: 0;\n margin-right: 15%;\n margin-left: 15%;\n list-style: none;\n}\n\n.carousel-indicators li {\n position: relative;\n flex: 0 1 auto;\n width: 30px;\n height: 3px;\n margin-right: 3px;\n margin-left: 3px;\n text-indent: -999px;\n background-color: rgba(255, 255, 255, 0.5);\n}\n\n.carousel-indicators li::before {\n position: absolute;\n top: -10px;\n left: 0;\n display: inline-block;\n width: 100%;\n height: 10px;\n content: \"\";\n}\n\n.carousel-indicators li::after {\n position: absolute;\n bottom: -10px;\n left: 0;\n display: inline-block;\n width: 100%;\n height: 10px;\n content: \"\";\n}\n\n.carousel-indicators .active {\n background-color: #fff;\n}\n\n.carousel-caption {\n position: absolute;\n right: 15%;\n bottom: 20px;\n left: 15%;\n z-index: 10;\n padding-top: 20px;\n padding-bottom: 20px;\n color: #fff;\n text-align: center;\n}\n\n.align-baseline {\n vertical-align: baseline !important;\n}\n\n.align-top {\n vertical-align: top !important;\n}\n\n.align-middle {\n vertical-align: middle !important;\n}\n\n.align-bottom {\n vertical-align: bottom !important;\n}\n\n.align-text-bottom {\n vertical-align: text-bottom !important;\n}\n\n.align-text-top {\n vertical-align: text-top !important;\n}\n\n.bg-primary {\n background-color: #007bff !important;\n}\n\na.bg-primary:focus, a.bg-primary:hover {\n background-color: #0062cc !important;\n}\n\n.bg-secondary {\n background-color: #868e96 !important;\n}\n\na.bg-secondary:focus, a.bg-secondary:hover {\n background-color: #6c757d !important;\n}\n\n.bg-success {\n background-color: #28a745 !important;\n}\n\na.bg-success:focus, a.bg-success:hover {\n background-color: #1e7e34 !important;\n}\n\n.bg-info {\n background-color: #17a2b8 !important;\n}\n\na.bg-info:focus, a.bg-info:hover {\n background-color: #117a8b !important;\n}\n\n.bg-warning {\n background-color: #ffc107 !important;\n}\n\na.bg-warning:focus, a.bg-warning:hover {\n background-color: #d39e00 !important;\n}\n\n.bg-danger {\n background-color: #dc3545 !important;\n}\n\na.bg-danger:focus, a.bg-danger:hover {\n background-color: #bd2130 !important;\n}\n\n.bg-light {\n background-color: #f8f9fa !important;\n}\n\na.bg-light:focus, a.bg-light:hover {\n background-color: #dae0e5 !important;\n}\n\n.bg-dark {\n background-color: #343a40 !important;\n}\n\na.bg-dark:focus, a.bg-dark:hover {\n background-color: #1d2124 !important;\n}\n\n.bg-white {\n background-color: #fff !important;\n}\n\n.bg-transparent {\n background-color: transparent !important;\n}\n\n.border {\n border: 1px solid #e9ecef !important;\n}\n\n.border-0 {\n border: 0 !important;\n}\n\n.border-top-0 {\n border-top: 0 !important;\n}\n\n.border-right-0 {\n border-right: 0 !important;\n}\n\n.border-bottom-0 {\n border-bottom: 0 !important;\n}\n\n.border-left-0 {\n border-left: 0 !important;\n}\n\n.border-primary {\n border-color: #007bff !important;\n}\n\n.border-secondary {\n border-color: #868e96 !important;\n}\n\n.border-success {\n border-color: #28a745 !important;\n}\n\n.border-info {\n border-color: #17a2b8 !important;\n}\n\n.border-warning {\n border-color: #ffc107 !important;\n}\n\n.border-danger {\n border-color: #dc3545 !important;\n}\n\n.border-light {\n border-color: #f8f9fa !important;\n}\n\n.border-dark {\n border-color: #343a40 !important;\n}\n\n.border-white {\n border-color: #fff !important;\n}\n\n.rounded {\n border-radius: 0.25rem !important;\n}\n\n.rounded-top {\n border-top-left-radius: 0.25rem !important;\n border-top-right-radius: 0.25rem !important;\n}\n\n.rounded-right {\n border-top-right-radius: 0.25rem !important;\n border-bottom-right-radius: 0.25rem !important;\n}\n\n.rounded-bottom {\n border-bottom-right-radius: 0.25rem !important;\n border-bottom-left-radius: 0.25rem !important;\n}\n\n.rounded-left {\n border-top-left-radius: 0.25rem !important;\n border-bottom-left-radius: 0.25rem !important;\n}\n\n.rounded-circle {\n border-radius: 50%;\n}\n\n.rounded-0 {\n border-radius: 0;\n}\n\n.clearfix::after {\n display: block;\n clear: both;\n content: \"\";\n}\n\n.d-none {\n display: none !important;\n}\n\n.d-inline {\n display: inline !important;\n}\n\n.d-inline-block {\n display: inline-block !important;\n}\n\n.d-block {\n display: block !important;\n}\n\n.d-table {\n display: table !important;\n}\n\n.d-table-cell {\n display: table-cell !important;\n}\n\n.d-flex {\n display: flex !important;\n}\n\n.d-inline-flex {\n display: inline-flex !important;\n}\n\n@media (min-width: 576px) {\n .d-sm-none {\n display: none !important;\n }\n .d-sm-inline {\n display: inline !important;\n }\n .d-sm-inline-block {\n display: inline-block !important;\n }\n .d-sm-block {\n display: block !important;\n }\n .d-sm-table {\n display: table !important;\n }\n .d-sm-table-cell {\n display: table-cell !important;\n }\n .d-sm-flex {\n display: flex !important;\n }\n .d-sm-inline-flex {\n display: inline-flex !important;\n }\n}\n\n@media (min-width: 768px) {\n .d-md-none {\n display: none !important;\n }\n .d-md-inline {\n display: inline !important;\n }\n .d-md-inline-block {\n display: inline-block !important;\n }\n .d-md-block {\n display: block !important;\n }\n .d-md-table {\n display: table !important;\n }\n .d-md-table-cell {\n display: table-cell !important;\n }\n .d-md-flex {\n display: flex !important;\n }\n .d-md-inline-flex {\n display: inline-flex !important;\n }\n}\n\n@media (min-width: 992px) {\n .d-lg-none {\n display: none !important;\n }\n .d-lg-inline {\n display: inline !important;\n }\n .d-lg-inline-block {\n display: inline-block !important;\n }\n .d-lg-block {\n display: block !important;\n }\n .d-lg-table {\n display: table !important;\n }\n .d-lg-table-cell {\n display: table-cell !important;\n }\n .d-lg-flex {\n display: flex !important;\n }\n .d-lg-inline-flex {\n display: inline-flex !important;\n }\n}\n\n@media (min-width: 1200px) {\n .d-xl-none {\n display: none !important;\n }\n .d-xl-inline {\n display: inline !important;\n }\n .d-xl-inline-block {\n display: inline-block !important;\n }\n .d-xl-block {\n display: block !important;\n }\n .d-xl-table {\n display: table !important;\n }\n .d-xl-table-cell {\n display: table-cell !important;\n }\n .d-xl-flex {\n display: flex !important;\n }\n .d-xl-inline-flex {\n display: inline-flex !important;\n }\n}\n\n.d-print-block {\n display: none !important;\n}\n\n@media print {\n .d-print-block {\n display: block !important;\n }\n}\n\n.d-print-inline {\n display: none !important;\n}\n\n@media print {\n .d-print-inline {\n display: inline !important;\n }\n}\n\n.d-print-inline-block {\n display: none !important;\n}\n\n@media print {\n .d-print-inline-block {\n display: inline-block !important;\n }\n}\n\n@media print {\n .d-print-none {\n display: none !important;\n }\n}\n\n.embed-responsive {\n position: relative;\n display: block;\n width: 100%;\n padding: 0;\n overflow: hidden;\n}\n\n.embed-responsive::before {\n display: block;\n content: \"\";\n}\n\n.embed-responsive .embed-responsive-item,\n.embed-responsive iframe,\n.embed-responsive embed,\n.embed-responsive object,\n.embed-responsive video {\n position: absolute;\n top: 0;\n bottom: 0;\n left: 0;\n width: 100%;\n height: 100%;\n border: 0;\n}\n\n.embed-responsive-21by9::before {\n padding-top: 42.857143%;\n}\n\n.embed-responsive-16by9::before {\n padding-top: 56.25%;\n}\n\n.embed-responsive-4by3::before {\n padding-top: 75%;\n}\n\n.embed-responsive-1by1::before {\n padding-top: 100%;\n}\n\n.flex-row {\n flex-direction: row !important;\n}\n\n.flex-column {\n flex-direction: column !important;\n}\n\n.flex-row-reverse {\n flex-direction: row-reverse !important;\n}\n\n.flex-column-reverse {\n flex-direction: column-reverse !important;\n}\n\n.flex-wrap {\n flex-wrap: wrap !important;\n}\n\n.flex-nowrap {\n flex-wrap: nowrap !important;\n}\n\n.flex-wrap-reverse {\n flex-wrap: wrap-reverse !important;\n}\n\n.justify-content-start {\n justify-content: flex-start !important;\n}\n\n.justify-content-end {\n justify-content: flex-end !important;\n}\n\n.justify-content-center {\n justify-content: center !important;\n}\n\n.justify-content-between {\n justify-content: space-between !important;\n}\n\n.justify-content-around {\n justify-content: space-around !important;\n}\n\n.align-items-start {\n align-items: flex-start !important;\n}\n\n.align-items-end {\n align-items: flex-end !important;\n}\n\n.align-items-center {\n align-items: center !important;\n}\n\n.align-items-baseline {\n align-items: baseline !important;\n}\n\n.align-items-stretch {\n align-items: stretch !important;\n}\n\n.align-content-start {\n align-content: flex-start !important;\n}\n\n.align-content-end {\n align-content: flex-end !important;\n}\n\n.align-content-center {\n align-content: center !important;\n}\n\n.align-content-between {\n align-content: space-between !important;\n}\n\n.align-content-around {\n align-content: space-around !important;\n}\n\n.align-content-stretch {\n align-content: stretch !important;\n}\n\n.align-self-auto {\n align-self: auto !important;\n}\n\n.align-self-start {\n align-self: flex-start !important;\n}\n\n.align-self-end {\n align-self: flex-end !important;\n}\n\n.align-self-center {\n align-self: center !important;\n}\n\n.align-self-baseline {\n align-self: baseline !important;\n}\n\n.align-self-stretch {\n align-self: stretch !important;\n}\n\n@media (min-width: 576px) {\n .flex-sm-row {\n flex-direction: row !important;\n }\n .flex-sm-column {\n flex-direction: column !important;\n }\n .flex-sm-row-reverse {\n flex-direction: row-reverse !important;\n }\n .flex-sm-column-reverse {\n flex-direction: column-reverse !important;\n }\n .flex-sm-wrap {\n flex-wrap: wrap !important;\n }\n .flex-sm-nowrap {\n flex-wrap: nowrap !important;\n }\n .flex-sm-wrap-reverse {\n flex-wrap: wrap-reverse !important;\n }\n .justify-content-sm-start {\n justify-content: flex-start !important;\n }\n .justify-content-sm-end {\n justify-content: flex-end !important;\n }\n .justify-content-sm-center {\n justify-content: center !important;\n }\n .justify-content-sm-between {\n justify-content: space-between !important;\n }\n .justify-content-sm-around {\n justify-content: space-around !important;\n }\n .align-items-sm-start {\n align-items: flex-start !important;\n }\n .align-items-sm-end {\n align-items: flex-end !important;\n }\n .align-items-sm-center {\n align-items: center !important;\n }\n .align-items-sm-baseline {\n align-items: baseline !important;\n }\n .align-items-sm-stretch {\n align-items: stretch !important;\n }\n .align-content-sm-start {\n align-content: flex-start !important;\n }\n .align-content-sm-end {\n align-content: flex-end !important;\n }\n .align-content-sm-center {\n align-content: center !important;\n }\n .align-content-sm-between {\n align-content: space-between !important;\n }\n .align-content-sm-around {\n align-content: space-around !important;\n }\n .align-content-sm-stretch {\n align-content: stretch !important;\n }\n .align-self-sm-auto {\n align-self: auto !important;\n }\n .align-self-sm-start {\n align-self: flex-start !important;\n }\n .align-self-sm-end {\n align-self: flex-end !important;\n }\n .align-self-sm-center {\n align-self: center !important;\n }\n .align-self-sm-baseline {\n align-self: baseline !important;\n }\n .align-self-sm-stretch {\n align-self: stretch !important;\n }\n}\n\n@media (min-width: 768px) {\n .flex-md-row {\n flex-direction: row !important;\n }\n .flex-md-column {\n flex-direction: column !important;\n }\n .flex-md-row-reverse {\n flex-direction: row-reverse !important;\n }\n .flex-md-column-reverse {\n flex-direction: column-reverse !important;\n }\n .flex-md-wrap {\n flex-wrap: wrap !important;\n }\n .flex-md-nowrap {\n flex-wrap: nowrap !important;\n }\n .flex-md-wrap-reverse {\n flex-wrap: wrap-reverse !important;\n }\n .justify-content-md-start {\n justify-content: flex-start !important;\n }\n .justify-content-md-end {\n justify-content: flex-end !important;\n }\n .justify-content-md-center {\n justify-content: center !important;\n }\n .justify-content-md-between {\n justify-content: space-between !important;\n }\n .justify-content-md-around {\n justify-content: space-around !important;\n }\n .align-items-md-start {\n align-items: flex-start !important;\n }\n .align-items-md-end {\n align-items: flex-end !important;\n }\n .align-items-md-center {\n align-items: center !important;\n }\n .align-items-md-baseline {\n align-items: baseline !important;\n }\n .align-items-md-stretch {\n align-items: stretch !important;\n }\n .align-content-md-start {\n align-content: flex-start !important;\n }\n .align-content-md-end {\n align-content: flex-end !important;\n }\n .align-content-md-center {\n align-content: center !important;\n }\n .align-content-md-between {\n align-content: space-between !important;\n }\n .align-content-md-around {\n align-content: space-around !important;\n }\n .align-content-md-stretch {\n align-content: stretch !important;\n }\n .align-self-md-auto {\n align-self: auto !important;\n }\n .align-self-md-start {\n align-self: flex-start !important;\n }\n .align-self-md-end {\n align-self: flex-end !important;\n }\n .align-self-md-center {\n align-self: center !important;\n }\n .align-self-md-baseline {\n align-self: baseline !important;\n }\n .align-self-md-stretch {\n align-self: stretch !important;\n }\n}\n\n@media (min-width: 992px) {\n .flex-lg-row {\n flex-direction: row !important;\n }\n .flex-lg-column {\n flex-direction: column !important;\n }\n .flex-lg-row-reverse {\n flex-direction: row-reverse !important;\n }\n .flex-lg-column-reverse {\n flex-direction: column-reverse !important;\n }\n .flex-lg-wrap {\n flex-wrap: wrap !important;\n }\n .flex-lg-nowrap {\n flex-wrap: nowrap !important;\n }\n .flex-lg-wrap-reverse {\n flex-wrap: wrap-reverse !important;\n }\n .justify-content-lg-start {\n justify-content: flex-start !important;\n }\n .justify-content-lg-end {\n justify-content: flex-end !important;\n }\n .justify-content-lg-center {\n justify-content: center !important;\n }\n .justify-content-lg-between {\n justify-content: space-between !important;\n }\n .justify-content-lg-around {\n justify-content: space-around !important;\n }\n .align-items-lg-start {\n align-items: flex-start !important;\n }\n .align-items-lg-end {\n align-items: flex-end !important;\n }\n .align-items-lg-center {\n align-items: center !important;\n }\n .align-items-lg-baseline {\n align-items: baseline !important;\n }\n .align-items-lg-stretch {\n align-items: stretch !important;\n }\n .align-content-lg-start {\n align-content: flex-start !important;\n }\n .align-content-lg-end {\n align-content: flex-end !important;\n }\n .align-content-lg-center {\n align-content: center !important;\n }\n .align-content-lg-between {\n align-content: space-between !important;\n }\n .align-content-lg-around {\n align-content: space-around !important;\n }\n .align-content-lg-stretch {\n align-content: stretch !important;\n }\n .align-self-lg-auto {\n align-self: auto !important;\n }\n .align-self-lg-start {\n align-self: flex-start !important;\n }\n .align-self-lg-end {\n align-self: flex-end !important;\n }\n .align-self-lg-center {\n align-self: center !important;\n }\n .align-self-lg-baseline {\n align-self: baseline !important;\n }\n .align-self-lg-stretch {\n align-self: stretch !important;\n }\n}\n\n@media (min-width: 1200px) {\n .flex-xl-row {\n flex-direction: row !important;\n }\n .flex-xl-column {\n flex-direction: column !important;\n }\n .flex-xl-row-reverse {\n flex-direction: row-reverse !important;\n }\n .flex-xl-column-reverse {\n flex-direction: column-reverse !important;\n }\n .flex-xl-wrap {\n flex-wrap: wrap !important;\n }\n .flex-xl-nowrap {\n flex-wrap: nowrap !important;\n }\n .flex-xl-wrap-reverse {\n flex-wrap: wrap-reverse !important;\n }\n .justify-content-xl-start {\n justify-content: flex-start !important;\n }\n .justify-content-xl-end {\n justify-content: flex-end !important;\n }\n .justify-content-xl-center {\n justify-content: center !important;\n }\n .justify-content-xl-between {\n justify-content: space-between !important;\n }\n .justify-content-xl-around {\n justify-content: space-around !important;\n }\n .align-items-xl-start {\n align-items: flex-start !important;\n }\n .align-items-xl-end {\n align-items: flex-end !important;\n }\n .align-items-xl-center {\n align-items: center !important;\n }\n .align-items-xl-baseline {\n align-items: baseline !important;\n }\n .align-items-xl-stretch {\n align-items: stretch !important;\n }\n .align-content-xl-start {\n align-content: flex-start !important;\n }\n .align-content-xl-end {\n align-content: flex-end !important;\n }\n .align-content-xl-center {\n align-content: center !important;\n }\n .align-content-xl-between {\n align-content: space-between !important;\n }\n .align-content-xl-around {\n align-content: space-around !important;\n }\n .align-content-xl-stretch {\n align-content: stretch !important;\n }\n .align-self-xl-auto {\n align-self: auto !important;\n }\n .align-self-xl-start {\n align-self: flex-start !important;\n }\n .align-self-xl-end {\n align-self: flex-end !important;\n }\n .align-self-xl-center {\n align-self: center !important;\n }\n .align-self-xl-baseline {\n align-self: baseline !important;\n }\n .align-self-xl-stretch {\n align-self: stretch !important;\n }\n}\n\n.float-left {\n float: left !important;\n}\n\n.float-right {\n float: right !important;\n}\n\n.float-none {\n float: none !important;\n}\n\n@media (min-width: 576px) {\n .float-sm-left {\n float: left !important;\n }\n .float-sm-right {\n float: right !important;\n }\n .float-sm-none {\n float: none !important;\n }\n}\n\n@media (min-width: 768px) {\n .float-md-left {\n float: left !important;\n }\n .float-md-right {\n float: right !important;\n }\n .float-md-none {\n float: none !important;\n }\n}\n\n@media (min-width: 992px) {\n .float-lg-left {\n float: left !important;\n }\n .float-lg-right {\n float: right !important;\n }\n .float-lg-none {\n float: none !important;\n }\n}\n\n@media (min-width: 1200px) {\n .float-xl-left {\n float: left !important;\n }\n .float-xl-right {\n float: right !important;\n }\n .float-xl-none {\n float: none !important;\n }\n}\n\n.fixed-top {\n position: fixed;\n top: 0;\n right: 0;\n left: 0;\n z-index: 1030;\n}\n\n.fixed-bottom {\n position: fixed;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: 1030;\n}\n\n@supports (position: sticky) {\n .sticky-top {\n position: sticky;\n top: 0;\n z-index: 1020;\n }\n}\n\n.sr-only {\n position: absolute;\n width: 1px;\n height: 1px;\n padding: 0;\n overflow: hidden;\n clip: rect(0, 0, 0, 0);\n white-space: nowrap;\n clip-path: inset(50%);\n border: 0;\n}\n\n.sr-only-focusable:active, .sr-only-focusable:focus {\n position: static;\n width: auto;\n height: auto;\n overflow: visible;\n clip: auto;\n white-space: normal;\n clip-path: none;\n}\n\n.w-25 {\n width: 25% !important;\n}\n\n.w-50 {\n width: 50% !important;\n}\n\n.w-75 {\n width: 75% !important;\n}\n\n.w-100 {\n width: 100% !important;\n}\n\n.h-25 {\n height: 25% !important;\n}\n\n.h-50 {\n height: 50% !important;\n}\n\n.h-75 {\n height: 75% !important;\n}\n\n.h-100 {\n height: 100% !important;\n}\n\n.mw-100 {\n max-width: 100% !important;\n}\n\n.mh-100 {\n max-height: 100% !important;\n}\n\n.m-0 {\n margin: 0 !important;\n}\n\n.mt-0 {\n margin-top: 0 !important;\n}\n\n.mr-0 {\n margin-right: 0 !important;\n}\n\n.mb-0 {\n margin-bottom: 0 !important;\n}\n\n.ml-0 {\n margin-left: 0 !important;\n}\n\n.mx-0 {\n margin-right: 0 !important;\n margin-left: 0 !important;\n}\n\n.my-0 {\n margin-top: 0 !important;\n margin-bottom: 0 !important;\n}\n\n.m-1 {\n margin: 0.25rem !important;\n}\n\n.mt-1 {\n margin-top: 0.25rem !important;\n}\n\n.mr-1 {\n margin-right: 0.25rem !important;\n}\n\n.mb-1 {\n margin-bottom: 0.25rem !important;\n}\n\n.ml-1 {\n margin-left: 0.25rem !important;\n}\n\n.mx-1 {\n margin-right: 0.25rem !important;\n margin-left: 0.25rem !important;\n}\n\n.my-1 {\n margin-top: 0.25rem !important;\n margin-bottom: 0.25rem !important;\n}\n\n.m-2 {\n margin: 0.5rem !important;\n}\n\n.mt-2 {\n margin-top: 0.5rem !important;\n}\n\n.mr-2 {\n margin-right: 0.5rem !important;\n}\n\n.mb-2 {\n margin-bottom: 0.5rem !important;\n}\n\n.ml-2 {\n margin-left: 0.5rem !important;\n}\n\n.mx-2 {\n margin-right: 0.5rem !important;\n margin-left: 0.5rem !important;\n}\n\n.my-2 {\n margin-top: 0.5rem !important;\n margin-bottom: 0.5rem !important;\n}\n\n.m-3 {\n margin: 1rem !important;\n}\n\n.mt-3 {\n margin-top: 1rem !important;\n}\n\n.mr-3 {\n margin-right: 1rem !important;\n}\n\n.mb-3 {\n margin-bottom: 1rem !important;\n}\n\n.ml-3 {\n margin-left: 1rem !important;\n}\n\n.mx-3 {\n margin-right: 1rem !important;\n margin-left: 1rem !important;\n}\n\n.my-3 {\n margin-top: 1rem !important;\n margin-bottom: 1rem !important;\n}\n\n.m-4 {\n margin: 1.5rem !important;\n}\n\n.mt-4 {\n margin-top: 1.5rem !important;\n}\n\n.mr-4 {\n margin-right: 1.5rem !important;\n}\n\n.mb-4 {\n margin-bottom: 1.5rem !important;\n}\n\n.ml-4 {\n margin-left: 1.5rem !important;\n}\n\n.mx-4 {\n margin-right: 1.5rem !important;\n margin-left: 1.5rem !important;\n}\n\n.my-4 {\n margin-top: 1.5rem !important;\n margin-bottom: 1.5rem !important;\n}\n\n.m-5 {\n margin: 3rem !important;\n}\n\n.mt-5 {\n margin-top: 3rem !important;\n}\n\n.mr-5 {\n margin-right: 3rem !important;\n}\n\n.mb-5 {\n margin-bottom: 3rem !important;\n}\n\n.ml-5 {\n margin-left: 3rem !important;\n}\n\n.mx-5 {\n margin-right: 3rem !important;\n margin-left: 3rem !important;\n}\n\n.my-5 {\n margin-top: 3rem !important;\n margin-bottom: 3rem !important;\n}\n\n.p-0 {\n padding: 0 !important;\n}\n\n.pt-0 {\n padding-top: 0 !important;\n}\n\n.pr-0 {\n padding-right: 0 !important;\n}\n\n.pb-0 {\n padding-bottom: 0 !important;\n}\n\n.pl-0 {\n padding-left: 0 !important;\n}\n\n.px-0 {\n padding-right: 0 !important;\n padding-left: 0 !important;\n}\n\n.py-0 {\n padding-top: 0 !important;\n padding-bottom: 0 !important;\n}\n\n.p-1 {\n padding: 0.25rem !important;\n}\n\n.pt-1 {\n padding-top: 0.25rem !important;\n}\n\n.pr-1 {\n padding-right: 0.25rem !important;\n}\n\n.pb-1 {\n padding-bottom: 0.25rem !important;\n}\n\n.pl-1 {\n padding-left: 0.25rem !important;\n}\n\n.px-1 {\n padding-right: 0.25rem !important;\n padding-left: 0.25rem !important;\n}\n\n.py-1 {\n padding-top: 0.25rem !important;\n padding-bottom: 0.25rem !important;\n}\n\n.p-2 {\n padding: 0.5rem !important;\n}\n\n.pt-2 {\n padding-top: 0.5rem !important;\n}\n\n.pr-2 {\n padding-right: 0.5rem !important;\n}\n\n.pb-2 {\n padding-bottom: 0.5rem !important;\n}\n\n.pl-2 {\n padding-left: 0.5rem !important;\n}\n\n.px-2 {\n padding-right: 0.5rem !important;\n padding-left: 0.5rem !important;\n}\n\n.py-2 {\n padding-top: 0.5rem !important;\n padding-bottom: 0.5rem !important;\n}\n\n.p-3 {\n padding: 1rem !important;\n}\n\n.pt-3 {\n padding-top: 1rem !important;\n}\n\n.pr-3 {\n padding-right: 1rem !important;\n}\n\n.pb-3 {\n padding-bottom: 1rem !important;\n}\n\n.pl-3 {\n padding-left: 1rem !important;\n}\n\n.px-3 {\n padding-right: 1rem !important;\n padding-left: 1rem !important;\n}\n\n.py-3 {\n padding-top: 1rem !important;\n padding-bottom: 1rem !important;\n}\n\n.p-4 {\n padding: 1.5rem !important;\n}\n\n.pt-4 {\n padding-top: 1.5rem !important;\n}\n\n.pr-4 {\n padding-right: 1.5rem !important;\n}\n\n.pb-4 {\n padding-bottom: 1.5rem !important;\n}\n\n.pl-4 {\n padding-left: 1.5rem !important;\n}\n\n.px-4 {\n padding-right: 1.5rem !important;\n padding-left: 1.5rem !important;\n}\n\n.py-4 {\n padding-top: 1.5rem !important;\n padding-bottom: 1.5rem !important;\n}\n\n.p-5 {\n padding: 3rem !important;\n}\n\n.pt-5 {\n padding-top: 3rem !important;\n}\n\n.pr-5 {\n padding-right: 3rem !important;\n}\n\n.pb-5 {\n padding-bottom: 3rem !important;\n}\n\n.pl-5 {\n padding-left: 3rem !important;\n}\n\n.px-5 {\n padding-right: 3rem !important;\n padding-left: 3rem !important;\n}\n\n.py-5 {\n padding-top: 3rem !important;\n padding-bottom: 3rem !important;\n}\n\n.m-auto {\n margin: auto !important;\n}\n\n.mt-auto {\n margin-top: auto !important;\n}\n\n.mr-auto {\n margin-right: auto !important;\n}\n\n.mb-auto {\n margin-bottom: auto !important;\n}\n\n.ml-auto {\n margin-left: auto !important;\n}\n\n.mx-auto {\n margin-right: auto !important;\n margin-left: auto !important;\n}\n\n.my-auto {\n margin-top: auto !important;\n margin-bottom: auto !important;\n}\n\n@media (min-width: 576px) {\n .m-sm-0 {\n margin: 0 !important;\n }\n .mt-sm-0 {\n margin-top: 0 !important;\n }\n .mr-sm-0 {\n margin-right: 0 !important;\n }\n .mb-sm-0 {\n margin-bottom: 0 !important;\n }\n .ml-sm-0 {\n margin-left: 0 !important;\n }\n .mx-sm-0 {\n margin-right: 0 !important;\n margin-left: 0 !important;\n }\n .my-sm-0 {\n margin-top: 0 !important;\n margin-bottom: 0 !important;\n }\n .m-sm-1 {\n margin: 0.25rem !important;\n }\n .mt-sm-1 {\n margin-top: 0.25rem !important;\n }\n .mr-sm-1 {\n margin-right: 0.25rem !important;\n }\n .mb-sm-1 {\n margin-bottom: 0.25rem !important;\n }\n .ml-sm-1 {\n margin-left: 0.25rem !important;\n }\n .mx-sm-1 {\n margin-right: 0.25rem !important;\n margin-left: 0.25rem !important;\n }\n .my-sm-1 {\n margin-top: 0.25rem !important;\n margin-bottom: 0.25rem !important;\n }\n .m-sm-2 {\n margin: 0.5rem !important;\n }\n .mt-sm-2 {\n margin-top: 0.5rem !important;\n }\n .mr-sm-2 {\n margin-right: 0.5rem !important;\n }\n .mb-sm-2 {\n margin-bottom: 0.5rem !important;\n }\n .ml-sm-2 {\n margin-left: 0.5rem !important;\n }\n .mx-sm-2 {\n margin-right: 0.5rem !important;\n margin-left: 0.5rem !important;\n }\n .my-sm-2 {\n margin-top: 0.5rem !important;\n margin-bottom: 0.5rem !important;\n }\n .m-sm-3 {\n margin: 1rem !important;\n }\n .mt-sm-3 {\n margin-top: 1rem !important;\n }\n .mr-sm-3 {\n margin-right: 1rem !important;\n }\n .mb-sm-3 {\n margin-bottom: 1rem !important;\n }\n .ml-sm-3 {\n margin-left: 1rem !important;\n }\n .mx-sm-3 {\n margin-right: 1rem !important;\n margin-left: 1rem !important;\n }\n .my-sm-3 {\n margin-top: 1rem !important;\n margin-bottom: 1rem !important;\n }\n .m-sm-4 {\n margin: 1.5rem !important;\n }\n .mt-sm-4 {\n margin-top: 1.5rem !important;\n }\n .mr-sm-4 {\n margin-right: 1.5rem !important;\n }\n .mb-sm-4 {\n margin-bottom: 1.5rem !important;\n }\n .ml-sm-4 {\n margin-left: 1.5rem !important;\n }\n .mx-sm-4 {\n margin-right: 1.5rem !important;\n margin-left: 1.5rem !important;\n }\n .my-sm-4 {\n margin-top: 1.5rem !important;\n margin-bottom: 1.5rem !important;\n }\n .m-sm-5 {\n margin: 3rem !important;\n }\n .mt-sm-5 {\n margin-top: 3rem !important;\n }\n .mr-sm-5 {\n margin-right: 3rem !important;\n }\n .mb-sm-5 {\n margin-bottom: 3rem !important;\n }\n .ml-sm-5 {\n margin-left: 3rem !important;\n }\n .mx-sm-5 {\n margin-right: 3rem !important;\n margin-left: 3rem !important;\n }\n .my-sm-5 {\n margin-top: 3rem !important;\n margin-bottom: 3rem !important;\n }\n .p-sm-0 {\n padding: 0 !important;\n }\n .pt-sm-0 {\n padding-top: 0 !important;\n }\n .pr-sm-0 {\n padding-right: 0 !important;\n }\n .pb-sm-0 {\n padding-bottom: 0 !important;\n }\n .pl-sm-0 {\n padding-left: 0 !important;\n }\n .px-sm-0 {\n padding-right: 0 !important;\n padding-left: 0 !important;\n }\n .py-sm-0 {\n padding-top: 0 !important;\n padding-bottom: 0 !important;\n }\n .p-sm-1 {\n padding: 0.25rem !important;\n }\n .pt-sm-1 {\n padding-top: 0.25rem !important;\n }\n .pr-sm-1 {\n padding-right: 0.25rem !important;\n }\n .pb-sm-1 {\n padding-bottom: 0.25rem !important;\n }\n .pl-sm-1 {\n padding-left: 0.25rem !important;\n }\n .px-sm-1 {\n padding-right: 0.25rem !important;\n padding-left: 0.25rem !important;\n }\n .py-sm-1 {\n padding-top: 0.25rem !important;\n padding-bottom: 0.25rem !important;\n }\n .p-sm-2 {\n padding: 0.5rem !important;\n }\n .pt-sm-2 {\n padding-top: 0.5rem !important;\n }\n .pr-sm-2 {\n padding-right: 0.5rem !important;\n }\n .pb-sm-2 {\n padding-bottom: 0.5rem !important;\n }\n .pl-sm-2 {\n padding-left: 0.5rem !important;\n }\n .px-sm-2 {\n padding-right: 0.5rem !important;\n padding-left: 0.5rem !important;\n }\n .py-sm-2 {\n padding-top: 0.5rem !important;\n padding-bottom: 0.5rem !important;\n }\n .p-sm-3 {\n padding: 1rem !important;\n }\n .pt-sm-3 {\n padding-top: 1rem !important;\n }\n .pr-sm-3 {\n padding-right: 1rem !important;\n }\n .pb-sm-3 {\n padding-bottom: 1rem !important;\n }\n .pl-sm-3 {\n padding-left: 1rem !important;\n }\n .px-sm-3 {\n padding-right: 1rem !important;\n padding-left: 1rem !important;\n }\n .py-sm-3 {\n padding-top: 1rem !important;\n padding-bottom: 1rem !important;\n }\n .p-sm-4 {\n padding: 1.5rem !important;\n }\n .pt-sm-4 {\n padding-top: 1.5rem !important;\n }\n .pr-sm-4 {\n padding-right: 1.5rem !important;\n }\n .pb-sm-4 {\n padding-bottom: 1.5rem !important;\n }\n .pl-sm-4 {\n padding-left: 1.5rem !important;\n }\n .px-sm-4 {\n padding-right: 1.5rem !important;\n padding-left: 1.5rem !important;\n }\n .py-sm-4 {\n padding-top: 1.5rem !important;\n padding-bottom: 1.5rem !important;\n }\n .p-sm-5 {\n padding: 3rem !important;\n }\n .pt-sm-5 {\n padding-top: 3rem !important;\n }\n .pr-sm-5 {\n padding-right: 3rem !important;\n }\n .pb-sm-5 {\n padding-bottom: 3rem !important;\n }\n .pl-sm-5 {\n padding-left: 3rem !important;\n }\n .px-sm-5 {\n padding-right: 3rem !important;\n padding-left: 3rem !important;\n }\n .py-sm-5 {\n padding-top: 3rem !important;\n padding-bottom: 3rem !important;\n }\n .m-sm-auto {\n margin: auto !important;\n }\n .mt-sm-auto {\n margin-top: auto !important;\n }\n .mr-sm-auto {\n margin-right: auto !important;\n }\n .mb-sm-auto {\n margin-bottom: auto !important;\n }\n .ml-sm-auto {\n margin-left: auto !important;\n }\n .mx-sm-auto {\n margin-right: auto !important;\n margin-left: auto !important;\n }\n .my-sm-auto {\n margin-top: auto !important;\n margin-bottom: auto !important;\n }\n}\n\n@media (min-width: 768px) {\n .m-md-0 {\n margin: 0 !important;\n }\n .mt-md-0 {\n margin-top: 0 !important;\n }\n .mr-md-0 {\n margin-right: 0 !important;\n }\n .mb-md-0 {\n margin-bottom: 0 !important;\n }\n .ml-md-0 {\n margin-left: 0 !important;\n }\n .mx-md-0 {\n margin-right: 0 !important;\n margin-left: 0 !important;\n }\n .my-md-0 {\n margin-top: 0 !important;\n margin-bottom: 0 !important;\n }\n .m-md-1 {\n margin: 0.25rem !important;\n }\n .mt-md-1 {\n margin-top: 0.25rem !important;\n }\n .mr-md-1 {\n margin-right: 0.25rem !important;\n }\n .mb-md-1 {\n margin-bottom: 0.25rem !important;\n }\n .ml-md-1 {\n margin-left: 0.25rem !important;\n }\n .mx-md-1 {\n margin-right: 0.25rem !important;\n margin-left: 0.25rem !important;\n }\n .my-md-1 {\n margin-top: 0.25rem !important;\n margin-bottom: 0.25rem !important;\n }\n .m-md-2 {\n margin: 0.5rem !important;\n }\n .mt-md-2 {\n margin-top: 0.5rem !important;\n }\n .mr-md-2 {\n margin-right: 0.5rem !important;\n }\n .mb-md-2 {\n margin-bottom: 0.5rem !important;\n }\n .ml-md-2 {\n margin-left: 0.5rem !important;\n }\n .mx-md-2 {\n margin-right: 0.5rem !important;\n margin-left: 0.5rem !important;\n }\n .my-md-2 {\n margin-top: 0.5rem !important;\n margin-bottom: 0.5rem !important;\n }\n .m-md-3 {\n margin: 1rem !important;\n }\n .mt-md-3 {\n margin-top: 1rem !important;\n }\n .mr-md-3 {\n margin-right: 1rem !important;\n }\n .mb-md-3 {\n margin-bottom: 1rem !important;\n }\n .ml-md-3 {\n margin-left: 1rem !important;\n }\n .mx-md-3 {\n margin-right: 1rem !important;\n margin-left: 1rem !important;\n }\n .my-md-3 {\n margin-top: 1rem !important;\n margin-bottom: 1rem !important;\n }\n .m-md-4 {\n margin: 1.5rem !important;\n }\n .mt-md-4 {\n margin-top: 1.5rem !important;\n }\n .mr-md-4 {\n margin-right: 1.5rem !important;\n }\n .mb-md-4 {\n margin-bottom: 1.5rem !important;\n }\n .ml-md-4 {\n margin-left: 1.5rem !important;\n }\n .mx-md-4 {\n margin-right: 1.5rem !important;\n margin-left: 1.5rem !important;\n }\n .my-md-4 {\n margin-top: 1.5rem !important;\n margin-bottom: 1.5rem !important;\n }\n .m-md-5 {\n margin: 3rem !important;\n }\n .mt-md-5 {\n margin-top: 3rem !important;\n }\n .mr-md-5 {\n margin-right: 3rem !important;\n }\n .mb-md-5 {\n margin-bottom: 3rem !important;\n }\n .ml-md-5 {\n margin-left: 3rem !important;\n }\n .mx-md-5 {\n margin-right: 3rem !important;\n margin-left: 3rem !important;\n }\n .my-md-5 {\n margin-top: 3rem !important;\n margin-bottom: 3rem !important;\n }\n .p-md-0 {\n padding: 0 !important;\n }\n .pt-md-0 {\n padding-top: 0 !important;\n }\n .pr-md-0 {\n padding-right: 0 !important;\n }\n .pb-md-0 {\n padding-bottom: 0 !important;\n }\n .pl-md-0 {\n padding-left: 0 !important;\n }\n .px-md-0 {\n padding-right: 0 !important;\n padding-left: 0 !important;\n }\n .py-md-0 {\n padding-top: 0 !important;\n padding-bottom: 0 !important;\n }\n .p-md-1 {\n padding: 0.25rem !important;\n }\n .pt-md-1 {\n padding-top: 0.25rem !important;\n }\n .pr-md-1 {\n padding-right: 0.25rem !important;\n }\n .pb-md-1 {\n padding-bottom: 0.25rem !important;\n }\n .pl-md-1 {\n padding-left: 0.25rem !important;\n }\n .px-md-1 {\n padding-right: 0.25rem !important;\n padding-left: 0.25rem !important;\n }\n .py-md-1 {\n padding-top: 0.25rem !important;\n padding-bottom: 0.25rem !important;\n }\n .p-md-2 {\n padding: 0.5rem !important;\n }\n .pt-md-2 {\n padding-top: 0.5rem !important;\n }\n .pr-md-2 {\n padding-right: 0.5rem !important;\n }\n .pb-md-2 {\n padding-bottom: 0.5rem !important;\n }\n .pl-md-2 {\n padding-left: 0.5rem !important;\n }\n .px-md-2 {\n padding-right: 0.5rem !important;\n padding-left: 0.5rem !important;\n }\n .py-md-2 {\n padding-top: 0.5rem !important;\n padding-bottom: 0.5rem !important;\n }\n .p-md-3 {\n padding: 1rem !important;\n }\n .pt-md-3 {\n padding-top: 1rem !important;\n }\n .pr-md-3 {\n padding-right: 1rem !important;\n }\n .pb-md-3 {\n padding-bottom: 1rem !important;\n }\n .pl-md-3 {\n padding-left: 1rem !important;\n }\n .px-md-3 {\n padding-right: 1rem !important;\n padding-left: 1rem !important;\n }\n .py-md-3 {\n padding-top: 1rem !important;\n padding-bottom: 1rem !important;\n }\n .p-md-4 {\n padding: 1.5rem !important;\n }\n .pt-md-4 {\n padding-top: 1.5rem !important;\n }\n .pr-md-4 {\n padding-right: 1.5rem !important;\n }\n .pb-md-4 {\n padding-bottom: 1.5rem !important;\n }\n .pl-md-4 {\n padding-left: 1.5rem !important;\n }\n .px-md-4 {\n padding-right: 1.5rem !important;\n padding-left: 1.5rem !important;\n }\n .py-md-4 {\n padding-top: 1.5rem !important;\n padding-bottom: 1.5rem !important;\n }\n .p-md-5 {\n padding: 3rem !important;\n }\n .pt-md-5 {\n padding-top: 3rem !important;\n }\n .pr-md-5 {\n padding-right: 3rem !important;\n }\n .pb-md-5 {\n padding-bottom: 3rem !important;\n }\n .pl-md-5 {\n padding-left: 3rem !important;\n }\n .px-md-5 {\n padding-right: 3rem !important;\n padding-left: 3rem !important;\n }\n .py-md-5 {\n padding-top: 3rem !important;\n padding-bottom: 3rem !important;\n }\n .m-md-auto {\n margin: auto !important;\n }\n .mt-md-auto {\n margin-top: auto !important;\n }\n .mr-md-auto {\n margin-right: auto !important;\n }\n .mb-md-auto {\n margin-bottom: auto !important;\n }\n .ml-md-auto {\n margin-left: auto !important;\n }\n .mx-md-auto {\n margin-right: auto !important;\n margin-left: auto !important;\n }\n .my-md-auto {\n margin-top: auto !important;\n margin-bottom: auto !important;\n }\n}\n\n@media (min-width: 992px) {\n .m-lg-0 {\n margin: 0 !important;\n }\n .mt-lg-0 {\n margin-top: 0 !important;\n }\n .mr-lg-0 {\n margin-right: 0 !important;\n }\n .mb-lg-0 {\n margin-bottom: 0 !important;\n }\n .ml-lg-0 {\n margin-left: 0 !important;\n }\n .mx-lg-0 {\n margin-right: 0 !important;\n margin-left: 0 !important;\n }\n .my-lg-0 {\n margin-top: 0 !important;\n margin-bottom: 0 !important;\n }\n .m-lg-1 {\n margin: 0.25rem !important;\n }\n .mt-lg-1 {\n margin-top: 0.25rem !important;\n }\n .mr-lg-1 {\n margin-right: 0.25rem !important;\n }\n .mb-lg-1 {\n margin-bottom: 0.25rem !important;\n }\n .ml-lg-1 {\n margin-left: 0.25rem !important;\n }\n .mx-lg-1 {\n margin-right: 0.25rem !important;\n margin-left: 0.25rem !important;\n }\n .my-lg-1 {\n margin-top: 0.25rem !important;\n margin-bottom: 0.25rem !important;\n }\n .m-lg-2 {\n margin: 0.5rem !important;\n }\n .mt-lg-2 {\n margin-top: 0.5rem !important;\n }\n .mr-lg-2 {\n margin-right: 0.5rem !important;\n }\n .mb-lg-2 {\n margin-bottom: 0.5rem !important;\n }\n .ml-lg-2 {\n margin-left: 0.5rem !important;\n }\n .mx-lg-2 {\n margin-right: 0.5rem !important;\n margin-left: 0.5rem !important;\n }\n .my-lg-2 {\n margin-top: 0.5rem !important;\n margin-bottom: 0.5rem !important;\n }\n .m-lg-3 {\n margin: 1rem !important;\n }\n .mt-lg-3 {\n margin-top: 1rem !important;\n }\n .mr-lg-3 {\n margin-right: 1rem !important;\n }\n .mb-lg-3 {\n margin-bottom: 1rem !important;\n }\n .ml-lg-3 {\n margin-left: 1rem !important;\n }\n .mx-lg-3 {\n margin-right: 1rem !important;\n margin-left: 1rem !important;\n }\n .my-lg-3 {\n margin-top: 1rem !important;\n margin-bottom: 1rem !important;\n }\n .m-lg-4 {\n margin: 1.5rem !important;\n }\n .mt-lg-4 {\n margin-top: 1.5rem !important;\n }\n .mr-lg-4 {\n margin-right: 1.5rem !important;\n }\n .mb-lg-4 {\n margin-bottom: 1.5rem !important;\n }\n .ml-lg-4 {\n margin-left: 1.5rem !important;\n }\n .mx-lg-4 {\n margin-right: 1.5rem !important;\n margin-left: 1.5rem !important;\n }\n .my-lg-4 {\n margin-top: 1.5rem !important;\n margin-bottom: 1.5rem !important;\n }\n .m-lg-5 {\n margin: 3rem !important;\n }\n .mt-lg-5 {\n margin-top: 3rem !important;\n }\n .mr-lg-5 {\n margin-right: 3rem !important;\n }\n .mb-lg-5 {\n margin-bottom: 3rem !important;\n }\n .ml-lg-5 {\n margin-left: 3rem !important;\n }\n .mx-lg-5 {\n margin-right: 3rem !important;\n margin-left: 3rem !important;\n }\n .my-lg-5 {\n margin-top: 3rem !important;\n margin-bottom: 3rem !important;\n }\n .p-lg-0 {\n padding: 0 !important;\n }\n .pt-lg-0 {\n padding-top: 0 !important;\n }\n .pr-lg-0 {\n padding-right: 0 !important;\n }\n .pb-lg-0 {\n padding-bottom: 0 !important;\n }\n .pl-lg-0 {\n padding-left: 0 !important;\n }\n .px-lg-0 {\n padding-right: 0 !important;\n padding-left: 0 !important;\n }\n .py-lg-0 {\n padding-top: 0 !important;\n padding-bottom: 0 !important;\n }\n .p-lg-1 {\n padding: 0.25rem !important;\n }\n .pt-lg-1 {\n padding-top: 0.25rem !important;\n }\n .pr-lg-1 {\n padding-right: 0.25rem !important;\n }\n .pb-lg-1 {\n padding-bottom: 0.25rem !important;\n }\n .pl-lg-1 {\n padding-left: 0.25rem !important;\n }\n .px-lg-1 {\n padding-right: 0.25rem !important;\n padding-left: 0.25rem !important;\n }\n .py-lg-1 {\n padding-top: 0.25rem !important;\n padding-bottom: 0.25rem !important;\n }\n .p-lg-2 {\n padding: 0.5rem !important;\n }\n .pt-lg-2 {\n padding-top: 0.5rem !important;\n }\n .pr-lg-2 {\n padding-right: 0.5rem !important;\n }\n .pb-lg-2 {\n padding-bottom: 0.5rem !important;\n }\n .pl-lg-2 {\n padding-left: 0.5rem !important;\n }\n .px-lg-2 {\n padding-right: 0.5rem !important;\n padding-left: 0.5rem !important;\n }\n .py-lg-2 {\n padding-top: 0.5rem !important;\n padding-bottom: 0.5rem !important;\n }\n .p-lg-3 {\n padding: 1rem !important;\n }\n .pt-lg-3 {\n padding-top: 1rem !important;\n }\n .pr-lg-3 {\n padding-right: 1rem !important;\n }\n .pb-lg-3 {\n padding-bottom: 1rem !important;\n }\n .pl-lg-3 {\n padding-left: 1rem !important;\n }\n .px-lg-3 {\n padding-right: 1rem !important;\n padding-left: 1rem !important;\n }\n .py-lg-3 {\n padding-top: 1rem !important;\n padding-bottom: 1rem !important;\n }\n .p-lg-4 {\n padding: 1.5rem !important;\n }\n .pt-lg-4 {\n padding-top: 1.5rem !important;\n }\n .pr-lg-4 {\n padding-right: 1.5rem !important;\n }\n .pb-lg-4 {\n padding-bottom: 1.5rem !important;\n }\n .pl-lg-4 {\n padding-left: 1.5rem !important;\n }\n .px-lg-4 {\n padding-right: 1.5rem !important;\n padding-left: 1.5rem !important;\n }\n .py-lg-4 {\n padding-top: 1.5rem !important;\n padding-bottom: 1.5rem !important;\n }\n .p-lg-5 {\n padding: 3rem !important;\n }\n .pt-lg-5 {\n padding-top: 3rem !important;\n }\n .pr-lg-5 {\n padding-right: 3rem !important;\n }\n .pb-lg-5 {\n padding-bottom: 3rem !important;\n }\n .pl-lg-5 {\n padding-left: 3rem !important;\n }\n .px-lg-5 {\n padding-right: 3rem !important;\n padding-left: 3rem !important;\n }\n .py-lg-5 {\n padding-top: 3rem !important;\n padding-bottom: 3rem !important;\n }\n .m-lg-auto {\n margin: auto !important;\n }\n .mt-lg-auto {\n margin-top: auto !important;\n }\n .mr-lg-auto {\n margin-right: auto !important;\n }\n .mb-lg-auto {\n margin-bottom: auto !important;\n }\n .ml-lg-auto {\n margin-left: auto !important;\n }\n .mx-lg-auto {\n margin-right: auto !important;\n margin-left: auto !important;\n }\n .my-lg-auto {\n margin-top: auto !important;\n margin-bottom: auto !important;\n }\n}\n\n@media (min-width: 1200px) {\n .m-xl-0 {\n margin: 0 !important;\n }\n .mt-xl-0 {\n margin-top: 0 !important;\n }\n .mr-xl-0 {\n margin-right: 0 !important;\n }\n .mb-xl-0 {\n margin-bottom: 0 !important;\n }\n .ml-xl-0 {\n margin-left: 0 !important;\n }\n .mx-xl-0 {\n margin-right: 0 !important;\n margin-left: 0 !important;\n }\n .my-xl-0 {\n margin-top: 0 !important;\n margin-bottom: 0 !important;\n }\n .m-xl-1 {\n margin: 0.25rem !important;\n }\n .mt-xl-1 {\n margin-top: 0.25rem !important;\n }\n .mr-xl-1 {\n margin-right: 0.25rem !important;\n }\n .mb-xl-1 {\n margin-bottom: 0.25rem !important;\n }\n .ml-xl-1 {\n margin-left: 0.25rem !important;\n }\n .mx-xl-1 {\n margin-right: 0.25rem !important;\n margin-left: 0.25rem !important;\n }\n .my-xl-1 {\n margin-top: 0.25rem !important;\n margin-bottom: 0.25rem !important;\n }\n .m-xl-2 {\n margin: 0.5rem !important;\n }\n .mt-xl-2 {\n margin-top: 0.5rem !important;\n }\n .mr-xl-2 {\n margin-right: 0.5rem !important;\n }\n .mb-xl-2 {\n margin-bottom: 0.5rem !important;\n }\n .ml-xl-2 {\n margin-left: 0.5rem !important;\n }\n .mx-xl-2 {\n margin-right: 0.5rem !important;\n margin-left: 0.5rem !important;\n }\n .my-xl-2 {\n margin-top: 0.5rem !important;\n margin-bottom: 0.5rem !important;\n }\n .m-xl-3 {\n margin: 1rem !important;\n }\n .mt-xl-3 {\n margin-top: 1rem !important;\n }\n .mr-xl-3 {\n margin-right: 1rem !important;\n }\n .mb-xl-3 {\n margin-bottom: 1rem !important;\n }\n .ml-xl-3 {\n margin-left: 1rem !important;\n }\n .mx-xl-3 {\n margin-right: 1rem !important;\n margin-left: 1rem !important;\n }\n .my-xl-3 {\n margin-top: 1rem !important;\n margin-bottom: 1rem !important;\n }\n .m-xl-4 {\n margin: 1.5rem !important;\n }\n .mt-xl-4 {\n margin-top: 1.5rem !important;\n }\n .mr-xl-4 {\n margin-right: 1.5rem !important;\n }\n .mb-xl-4 {\n margin-bottom: 1.5rem !important;\n }\n .ml-xl-4 {\n margin-left: 1.5rem !important;\n }\n .mx-xl-4 {\n margin-right: 1.5rem !important;\n margin-left: 1.5rem !important;\n }\n .my-xl-4 {\n margin-top: 1.5rem !important;\n margin-bottom: 1.5rem !important;\n }\n .m-xl-5 {\n margin: 3rem !important;\n }\n .mt-xl-5 {\n margin-top: 3rem !important;\n }\n .mr-xl-5 {\n margin-right: 3rem !important;\n }\n .mb-xl-5 {\n margin-bottom: 3rem !important;\n }\n .ml-xl-5 {\n margin-left: 3rem !important;\n }\n .mx-xl-5 {\n margin-right: 3rem !important;\n margin-left: 3rem !important;\n }\n .my-xl-5 {\n margin-top: 3rem !important;\n margin-bottom: 3rem !important;\n }\n .p-xl-0 {\n padding: 0 !important;\n }\n .pt-xl-0 {\n padding-top: 0 !important;\n }\n .pr-xl-0 {\n padding-right: 0 !important;\n }\n .pb-xl-0 {\n padding-bottom: 0 !important;\n }\n .pl-xl-0 {\n padding-left: 0 !important;\n }\n .px-xl-0 {\n padding-right: 0 !important;\n padding-left: 0 !important;\n }\n .py-xl-0 {\n padding-top: 0 !important;\n padding-bottom: 0 !important;\n }\n .p-xl-1 {\n padding: 0.25rem !important;\n }\n .pt-xl-1 {\n padding-top: 0.25rem !important;\n }\n .pr-xl-1 {\n padding-right: 0.25rem !important;\n }\n .pb-xl-1 {\n padding-bottom: 0.25rem !important;\n }\n .pl-xl-1 {\n padding-left: 0.25rem !important;\n }\n .px-xl-1 {\n padding-right: 0.25rem !important;\n padding-left: 0.25rem !important;\n }\n .py-xl-1 {\n padding-top: 0.25rem !important;\n padding-bottom: 0.25rem !important;\n }\n .p-xl-2 {\n padding: 0.5rem !important;\n }\n .pt-xl-2 {\n padding-top: 0.5rem !important;\n }\n .pr-xl-2 {\n padding-right: 0.5rem !important;\n }\n .pb-xl-2 {\n padding-bottom: 0.5rem !important;\n }\n .pl-xl-2 {\n padding-left: 0.5rem !important;\n }\n .px-xl-2 {\n padding-right: 0.5rem !important;\n padding-left: 0.5rem !important;\n }\n .py-xl-2 {\n padding-top: 0.5rem !important;\n padding-bottom: 0.5rem !important;\n }\n .p-xl-3 {\n padding: 1rem !important;\n }\n .pt-xl-3 {\n padding-top: 1rem !important;\n }\n .pr-xl-3 {\n padding-right: 1rem !important;\n }\n .pb-xl-3 {\n padding-bottom: 1rem !important;\n }\n .pl-xl-3 {\n padding-left: 1rem !important;\n }\n .px-xl-3 {\n padding-right: 1rem !important;\n padding-left: 1rem !important;\n }\n .py-xl-3 {\n padding-top: 1rem !important;\n padding-bottom: 1rem !important;\n }\n .p-xl-4 {\n padding: 1.5rem !important;\n }\n .pt-xl-4 {\n padding-top: 1.5rem !important;\n }\n .pr-xl-4 {\n padding-right: 1.5rem !important;\n }\n .pb-xl-4 {\n padding-bottom: 1.5rem !important;\n }\n .pl-xl-4 {\n padding-left: 1.5rem !important;\n }\n .px-xl-4 {\n padding-right: 1.5rem !important;\n padding-left: 1.5rem !important;\n }\n .py-xl-4 {\n padding-top: 1.5rem !important;\n padding-bottom: 1.5rem !important;\n }\n .p-xl-5 {\n padding: 3rem !important;\n }\n .pt-xl-5 {\n padding-top: 3rem !important;\n }\n .pr-xl-5 {\n padding-right: 3rem !important;\n }\n .pb-xl-5 {\n padding-bottom: 3rem !important;\n }\n .pl-xl-5 {\n padding-left: 3rem !important;\n }\n .px-xl-5 {\n padding-right: 3rem !important;\n padding-left: 3rem !important;\n }\n .py-xl-5 {\n padding-top: 3rem !important;\n padding-bottom: 3rem !important;\n }\n .m-xl-auto {\n margin: auto !important;\n }\n .mt-xl-auto {\n margin-top: auto !important;\n }\n .mr-xl-auto {\n margin-right: auto !important;\n }\n .mb-xl-auto {\n margin-bottom: auto !important;\n }\n .ml-xl-auto {\n margin-left: auto !important;\n }\n .mx-xl-auto {\n margin-right: auto !important;\n margin-left: auto !important;\n }\n .my-xl-auto {\n margin-top: auto !important;\n margin-bottom: auto !important;\n }\n}\n\n.text-justify {\n text-align: justify !important;\n}\n\n.text-nowrap {\n white-space: nowrap !important;\n}\n\n.text-truncate {\n overflow: hidden;\n text-overflow: ellipsis;\n white-space: nowrap;\n}\n\n.text-left {\n text-align: left !important;\n}\n\n.text-right {\n text-align: right !important;\n}\n\n.text-center {\n text-align: center !important;\n}\n\n@media (min-width: 576px) {\n .text-sm-left {\n text-align: left !important;\n }\n .text-sm-right {\n text-align: right !important;\n }\n .text-sm-center {\n text-align: center !important;\n }\n}\n\n@media (min-width: 768px) {\n .text-md-left {\n text-align: left !important;\n }\n .text-md-right {\n text-align: right !important;\n }\n .text-md-center {\n text-align: center !important;\n }\n}\n\n@media (min-width: 992px) {\n .text-lg-left {\n text-align: left !important;\n }\n .text-lg-right {\n text-align: right !important;\n }\n .text-lg-center {\n text-align: center !important;\n }\n}\n\n@media (min-width: 1200px) {\n .text-xl-left {\n text-align: left !important;\n }\n .text-xl-right {\n text-align: right !important;\n }\n .text-xl-center {\n text-align: center !important;\n }\n}\n\n.text-lowercase {\n text-transform: lowercase !important;\n}\n\n.text-uppercase {\n text-transform: uppercase !important;\n}\n\n.text-capitalize {\n text-transform: capitalize !important;\n}\n\n.font-weight-normal {\n font-weight: normal;\n}\n\n.font-weight-bold {\n font-weight: bold;\n}\n\n.font-italic {\n font-style: italic;\n}\n\n.text-white {\n color: #fff !important;\n}\n\n.text-primary {\n color: #007bff !important;\n}\n\na.text-primary:focus, a.text-primary:hover {\n color: #0062cc !important;\n}\n\n.text-secondary {\n color: #868e96 !important;\n}\n\na.text-secondary:focus, a.text-secondary:hover {\n color: #6c757d !important;\n}\n\n.text-success {\n color: #28a745 !important;\n}\n\na.text-success:focus, a.text-success:hover {\n color: #1e7e34 !important;\n}\n\n.text-info {\n color: #17a2b8 !important;\n}\n\na.text-info:focus, a.text-info:hover {\n color: #117a8b !important;\n}\n\n.text-warning {\n color: #ffc107 !important;\n}\n\na.text-warning:focus, a.text-warning:hover {\n color: #d39e00 !important;\n}\n\n.text-danger {\n color: #dc3545 !important;\n}\n\na.text-danger:focus, a.text-danger:hover {\n color: #bd2130 !important;\n}\n\n.text-light {\n color: #f8f9fa !important;\n}\n\na.text-light:focus, a.text-light:hover {\n color: #dae0e5 !important;\n}\n\n.text-dark {\n color: #343a40 !important;\n}\n\na.text-dark:focus, a.text-dark:hover {\n color: #1d2124 !important;\n}\n\n.text-muted {\n color: #868e96 !important;\n}\n\n.text-hide {\n font: 0/0 a;\n color: transparent;\n text-shadow: none;\n background-color: transparent;\n border: 0;\n}\n\n.visible {\n visibility: visible !important;\n}\n\n.invisible {\n visibility: hidden !important;\n}\n\n/*# sourceMappingURL=bootstrap.css.map */","// scss-lint:disable QualifyingElement, DuplicateProperty, VendorPrefix\n\n// Reboot\n//\n// Normalization of HTML elements, manually forked from Normalize.css to remove\n// styles targeting irrelevant browsers while applying new styles.\n//\n// Normalize is licensed MIT. https://github.com/necolas/normalize.css\n\n\n// Document\n//\n// 1. Change from `box-sizing: content-box` so that `width` is not affected by `padding` or `border`.\n// 2. Change the default font family in all browsers.\n// 3. Correct the line height in all browsers.\n// 4. Prevent adjustments of font size after orientation changes in IE on Windows Phone and in iOS.\n// 5. Setting @viewport causes scrollbars to overlap content in IE11 and Edge, so\n// we force a non-overlapping, non-auto-hiding scrollbar to counteract.\n// 6. Change the default tap highlight to be completely transparent in iOS.\n\nhtml {\n box-sizing: border-box; // 1\n font-family: sans-serif; // 2\n line-height: 1.15; // 3\n -webkit-text-size-adjust: 100%; // 4\n -ms-text-size-adjust: 100%; // 4\n -ms-overflow-style: scrollbar; // 5\n -webkit-tap-highlight-color: rgba(0,0,0,0); // 6\n}\n\n*,\n*::before,\n*::after {\n box-sizing: inherit; // 1\n}\n\n// IE10+ doesn't honor `<meta name=\"viewport\">` in some cases.\n@at-root {\n @-ms-viewport { width: device-width; }\n}\n\n// Shim for \"new\" HTML5 structural elements to display correctly (IE10, older browsers)\narticle, aside, dialog, figcaption, figure, footer, header, hgroup, main, nav, section {\n display: block;\n}\n\n// Body\n//\n// 1. Remove the margin in all browsers.\n// 2. As a best practice, apply a default `background-color`.\n\nbody {\n margin: 0; // 1\n font-family: $font-family-base;\n font-size: $font-size-base;\n font-weight: $font-weight-base;\n line-height: $line-height-base;\n color: $body-color;\n background-color: $body-bg; // 2\n}\n\n// Suppress the focus outline on elements that cannot be accessed via keyboard.\n// This prevents an unwanted focus outline from appearing around elements that\n// might still respond to pointer events.\n//\n// Credit: https://github.com/suitcss/base\n[tabindex=\"-1\"]:focus {\n outline: none !important;\n}\n\n\n// Content grouping\n//\n// 1. Add the correct box sizing in Firefox.\n// 2. Show the overflow in Edge and IE.\n\nhr {\n box-sizing: content-box; // 1\n height: 0; // 1\n overflow: visible; // 2\n}\n\n\n//\n// Typography\n//\n\n// Remove top margins from headings\n//\n// By default, `<h1>`-`<h6>` all receive top and bottom margins. We nuke the top\n// margin for easier control within type scales as it avoids margin collapsing.\nh1, h2, h3, h4, h5, h6 {\n margin-top: 0;\n margin-bottom: .5rem;\n}\n\n// Reset margins on paragraphs\n//\n// Similarly, the top margin on `<p>`s get reset. However, we also reset the\n// bottom margin to use `rem` units instead of `em`.\np {\n margin-top: 0;\n margin-bottom: 1rem;\n}\n\n// Abbreviations\n//\n// 1. Remove the bottom border in Firefox 39-.\n// 2. Add the correct text decoration in Chrome, Edge, IE, Opera, and Safari.\n// 3. Add explicit cursor to indicate changed behavior.\n// 4. Duplicate behavior to the data-* attribute for our tooltip plugin\n\nabbr[title],\nabbr[data-original-title] { // 4\n text-decoration: underline; // 2\n text-decoration: underline dotted; // 2\n cursor: help; // 3\n border-bottom: 0; // 1\n}\n\naddress {\n margin-bottom: 1rem;\n font-style: normal;\n line-height: inherit;\n}\n\nol,\nul,\ndl {\n margin-top: 0;\n margin-bottom: 1rem;\n}\n\nol ol,\nul ul,\nol ul,\nul ol {\n margin-bottom: 0;\n}\n\ndt {\n font-weight: $dt-font-weight;\n}\n\ndd {\n margin-bottom: .5rem;\n margin-left: 0; // Undo browser default\n}\n\nblockquote {\n margin: 0 0 1rem;\n}\n\ndfn {\n font-style: italic; // Add the correct font style in Android 4.3-\n}\n\nb,\nstrong {\n font-weight: bolder; // Add the correct font weight in Chrome, Edge, and Safari\n}\n\nsmall {\n font-size: 80%; // Add the correct font size in all browsers\n}\n\n//\n// Prevent `sub` and `sup` elements from affecting the line height in\n// all browsers.\n//\n\nsub,\nsup {\n position: relative;\n font-size: 75%;\n line-height: 0;\n vertical-align: baseline;\n}\n\nsub { bottom: -.25em; }\nsup { top: -.5em; }\n\n\n//\n// Links\n//\n\na {\n color: $link-color;\n text-decoration: $link-decoration;\n background-color: transparent; // Remove the gray background on active links in IE 10.\n -webkit-text-decoration-skip: objects; // Remove gaps in links underline in iOS 8+ and Safari 8+.\n\n @include hover {\n color: $link-hover-color;\n text-decoration: $link-hover-decoration;\n }\n}\n\n// And undo these styles for placeholder links/named anchors (without href)\n// which have not been made explicitly keyboard-focusable (without tabindex).\n// It would be more straightforward to just use a[href] in previous block, but that\n// causes specificity issues in many other styles that are too complex to fix.\n// See https://github.com/twbs/bootstrap/issues/19402\n\na:not([href]):not([tabindex]) {\n color: inherit;\n text-decoration: none;\n\n @include hover-focus {\n color: inherit;\n text-decoration: none;\n }\n\n &:focus {\n outline: 0;\n }\n}\n\n\n//\n// Code\n//\n\npre,\ncode,\nkbd,\nsamp {\n font-family: monospace, monospace; // Correct the inheritance and scaling of font size in all browsers.\n font-size: 1em; // Correct the odd `em` font sizing in all browsers.\n}\n\npre {\n // Remove browser default top margin\n margin-top: 0;\n // Reset browser default of `1em` to use `rem`s\n margin-bottom: 1rem;\n // Don't allow content to break outside\n overflow: auto;\n}\n\n\n//\n// Figures\n//\n\nfigure {\n // Apply a consistent margin strategy (matches our type styles).\n margin: 0 0 1rem;\n}\n\n\n//\n// Images and content\n//\n\nimg {\n vertical-align: middle;\n border-style: none; // Remove the border on images inside links in IE 10-.\n}\n\nsvg:not(:root) {\n overflow: hidden; // Hide the overflow in IE\n}\n\n\n// Avoid 300ms click delay on touch devices that support the `touch-action` CSS property.\n//\n// In particular, unlike most other browsers, IE11+Edge on Windows 10 on touch devices and IE Mobile 10-11\n// DON'T remove the click delay when `<meta name=\"viewport\" content=\"width=device-width\">` is present.\n// However, they DO support removing the click delay via `touch-action: manipulation`.\n// See:\n// * https://v4-alpha.getbootstrap.com/content/reboot/#click-delay-optimization-for-touch\n// * http://caniuse.com/#feat=css-touch-action\n// * https://patrickhlauke.github.io/touch/tests/results/#suppressing-300ms-delay\n\na,\narea,\nbutton,\n[role=\"button\"],\ninput,\nlabel,\nselect,\nsummary,\ntextarea {\n touch-action: manipulation;\n}\n\n\n//\n// Tables\n//\n\ntable {\n border-collapse: collapse; // Prevent double borders\n}\n\ncaption {\n padding-top: $table-cell-padding;\n padding-bottom: $table-cell-padding;\n color: $text-muted;\n text-align: left;\n caption-side: bottom;\n}\n\nth {\n // Matches default `<td>` alignment\n text-align: left;\n}\n\n\n//\n// Forms\n//\n\nlabel {\n // Allow labels to use `margin` for spacing.\n display: inline-block;\n margin-bottom: .5rem;\n}\n\n// Work around a Firefox/IE bug where the transparent `button` background\n// results in a loss of the default `button` focus styles.\n//\n// Credit: https://github.com/suitcss/base/\nbutton:focus {\n outline: 1px dotted;\n outline: 5px auto -webkit-focus-ring-color;\n}\n\ninput,\nbutton,\nselect,\noptgroup,\ntextarea {\n margin: 0; // Remove the margin in Firefox and Safari\n font-family: inherit;\n font-size: inherit;\n line-height: inherit;\n}\n\nbutton,\ninput {\n overflow: visible; // Show the overflow in Edge\n}\n\nbutton,\nselect {\n text-transform: none; // Remove the inheritance of text transform in Firefox\n}\n\n// 1. Prevent a WebKit bug where (2) destroys native `audio` and `video`\n// controls in Android 4.\n// 2. Correct the inability to style clickable types in iOS and Safari.\nbutton,\nhtml [type=\"button\"], // 1\n[type=\"reset\"],\n[type=\"submit\"] {\n -webkit-appearance: button; // 2\n}\n\n// Remove inner border and padding from Firefox, but don't restore the outline like Normalize.\nbutton::-moz-focus-inner,\n[type=\"button\"]::-moz-focus-inner,\n[type=\"reset\"]::-moz-focus-inner,\n[type=\"submit\"]::-moz-focus-inner {\n padding: 0;\n border-style: none;\n}\n\ninput[type=\"radio\"],\ninput[type=\"checkbox\"] {\n box-sizing: border-box; // 1. Add the correct box sizing in IE 10-\n padding: 0; // 2. Remove the padding in IE 10-\n}\n\n\ninput[type=\"date\"],\ninput[type=\"time\"],\ninput[type=\"datetime-local\"],\ninput[type=\"month\"] {\n // Remove the default appearance of temporal inputs to avoid a Mobile Safari\n // bug where setting a custom line-height prevents text from being vertically\n // centered within the input.\n // See https://bugs.webkit.org/show_bug.cgi?id=139848\n // and https://github.com/twbs/bootstrap/issues/11266\n -webkit-appearance: listbox;\n}\n\ntextarea {\n overflow: auto; // Remove the default vertical scrollbar in IE.\n // Textareas should really only resize vertically so they don't break their (horizontal) containers.\n resize: vertical;\n}\n\nfieldset {\n // Browsers set a default `min-width: min-content;` on fieldsets,\n // unlike e.g. `<div>`s, which have `min-width: 0;` by default.\n // So we reset that to ensure fieldsets behave more like a standard block element.\n // See https://github.com/twbs/bootstrap/issues/12359\n // and https://html.spec.whatwg.org/multipage/#the-fieldset-and-legend-elements\n min-width: 0;\n // Reset the default outline behavior of fieldsets so they don't affect page layout.\n padding: 0;\n margin: 0;\n border: 0;\n}\n\n// 1. Correct the text wrapping in Edge and IE.\n// 2. Correct the color inheritance from `fieldset` elements in IE.\nlegend {\n display: block;\n width: 100%;\n max-width: 100%; // 1\n padding: 0;\n margin-bottom: .5rem;\n font-size: 1.5rem;\n line-height: inherit;\n color: inherit; // 2\n white-space: normal; // 1\n}\n\nprogress {\n vertical-align: baseline; // Add the correct vertical alignment in Chrome, Firefox, and Opera.\n}\n\n// Correct the cursor style of increment and decrement buttons in Chrome.\n[type=\"number\"]::-webkit-inner-spin-button,\n[type=\"number\"]::-webkit-outer-spin-button {\n height: auto;\n}\n\n[type=\"search\"] {\n // This overrides the extra rounded corners on search inputs in iOS so that our\n // `.form-control` class can properly style them. Note that this cannot simply\n // be added to `.form-control` as it's not specific enough. For details, see\n // https://github.com/twbs/bootstrap/issues/11586.\n outline-offset: -2px; // 2. Correct the outline style in Safari.\n -webkit-appearance: none;\n}\n\n//\n// Remove the inner padding and cancel buttons in Chrome and Safari on macOS.\n//\n\n[type=\"search\"]::-webkit-search-cancel-button,\n[type=\"search\"]::-webkit-search-decoration {\n -webkit-appearance: none;\n}\n\n//\n// 1. Correct the inability to style clickable types in iOS and Safari.\n// 2. Change font properties to `inherit` in Safari.\n//\n\n::-webkit-file-upload-button {\n font: inherit; // 2\n -webkit-appearance: button; // 1\n}\n\n//\n// Correct element displays\n//\n\noutput {\n display: inline-block;\n}\n\nsummary {\n display: list-item; // Add the correct display in all browsers\n}\n\ntemplate {\n display: none; // Add the correct display in IE\n}\n\n// Always hide an element with the `hidden` HTML attribute (from PureCSS).\n// Needed for proper display in IE 10-.\n[hidden] {\n display: none !important;\n}\n","// Variables\n//\n// Copy settings from this file into the provided `_custom.scss` to override\n// the Bootstrap defaults without modifying key, versioned files.\n//\n// Variables should follow the `$component-state-property-size` formula for\n// consistent naming. Ex: $nav-link-disabled-color and $modal-content-box-shadow-xs.\n\n// Table of Contents\n//\n// Color system\n// Options\n// Spacing\n// Body\n// Links\n// Grid breakpoints\n// Grid containers\n// Grid columns\n// Fonts\n// Components\n// Tables\n// Buttons\n// Forms\n// Dropdowns\n// Z-index master list\n// Navs\n// Navbar\n// Pagination\n// Jumbotron\n// Form states and alerts\n// Cards\n// Tooltips\n// Popovers\n// Badges\n// Modals\n// Alerts\n// Progress bars\n// List group\n// Image thumbnails\n// Figures\n// Breadcrumbs\n// Carousel\n// Close\n// Code\n\n\n//\n// Color system\n//\n\n$white: #fff !default;\n$gray-100: #f8f9fa !default;\n$gray-200: #e9ecef !default;\n$gray-300: #dee2e6 !default;\n$gray-400: #ced4da !default;\n$gray-500: #adb5bd !default;\n$gray-600: #868e96 !default;\n$gray-700: #495057 !default;\n$gray-800: #343a40 !default;\n$gray-900: #212529 !default;\n$black: #000 !default;\n\n$grays: (\n 100: $gray-100,\n 200: $gray-200,\n 300: $gray-300,\n 400: $gray-400,\n 500: $gray-500,\n 600: $gray-600,\n 700: $gray-700,\n 800: $gray-800,\n 900: $gray-900\n) !default;\n\n$blue: #007bff !default;\n$indigo: #6610f2 !default;\n$purple: #6f42c1 !default;\n$pink: #e83e8c !default;\n$red: #dc3545 !default;\n$orange: #fd7e14 !default;\n$yellow: #ffc107 !default;\n$green: #28a745 !default;\n$teal: #20c997 !default;\n$cyan: #17a2b8 !default;\n\n$colors: (\n blue: $blue,\n indigo: $indigo,\n purple: $purple,\n pink: $pink,\n red: $red,\n orange: $orange,\n yellow: $yellow,\n green: $green,\n teal: $teal,\n cyan: $cyan,\n white: $white,\n gray: $gray-600,\n gray-dark: $gray-800\n) !default;\n\n$theme-colors: (\n primary: $blue,\n secondary: $gray-600,\n success: $green,\n info: $cyan,\n warning: $yellow,\n danger: $red,\n light: $gray-100,\n dark: $gray-800\n) !default;\n\n// Set a specific jump point for requesting color jumps\n$theme-color-interval: 8% !default;\n\n\n// Options\n//\n// Quickly modify global styling by enabling or disabling optional features.\n\n$enable-rounded: true !default;\n$enable-shadows: false !default;\n$enable-gradients: false !default;\n$enable-transitions: true !default;\n$enable-hover-media-query: false !default;\n$enable-grid-classes: true !default;\n$enable-print-styles: true !default;\n\n\n// Spacing\n//\n// Control the default styling of most Bootstrap elements by modifying these\n// variables. Mostly focused on spacing.\n// You can add more entries to the $spacers map, should you need more variation.\n\n$spacer: 1rem !default;\n$spacers: (\n 0: 0,\n 1: ($spacer * .25),\n 2: ($spacer * .5),\n 3: $spacer,\n 4: ($spacer * 1.5),\n 5: ($spacer * 3)\n) !default;\n\n// This variable affects the `.h-*` and `.w-*` classes.\n$sizes: (\n 25: 25%,\n 50: 50%,\n 75: 75%,\n 100: 100%\n) !default;\n\n// Body\n//\n// Settings for the `<body>` element.\n\n$body-bg: $white !default;\n$body-color: $gray-900 !default;\n\n// Links\n//\n// Style anchor elements.\n\n$link-color: theme-color(\"primary\") !default;\n$link-decoration: none !default;\n$link-hover-color: darken($link-color, 15%) !default;\n$link-hover-decoration: underline !default;\n\n\n// Grid breakpoints\n//\n// Define the minimum dimensions at which your layout will change,\n// adapting to different screen sizes, for use in media queries.\n\n$grid-breakpoints: (\n xs: 0,\n sm: 576px,\n md: 768px,\n lg: 992px,\n xl: 1200px\n) !default;\n@include _assert-ascending($grid-breakpoints, \"$grid-breakpoints\");\n@include _assert-starts-at-zero($grid-breakpoints);\n\n\n// Grid containers\n//\n// Define the maximum width of `.container` for different screen sizes.\n\n$container-max-widths: (\n sm: 540px,\n md: 720px,\n lg: 960px,\n xl: 1140px\n) !default;\n@include _assert-ascending($container-max-widths, \"$container-max-widths\");\n\n\n// Grid columns\n//\n// Set the number of columns and specify the width of the gutters.\n\n$grid-columns: 12 !default;\n$grid-gutter-width: 30px !default;\n\n// Components\n//\n// Define common padding and border radius sizes and more.\n\n$line-height-lg: 1.5 !default;\n$line-height-sm: 1.5 !default;\n\n$border-width: 1px !default;\n\n$border-radius: .25rem !default;\n$border-radius-lg: .3rem !default;\n$border-radius-sm: .2rem !default;\n\n$component-active-color: $white !default;\n$component-active-bg: theme-color(\"primary\") !default;\n\n$caret-width: .3em !default;\n\n$transition-base: all .2s ease-in-out !default;\n$transition-fade: opacity .15s linear !default;\n$transition-collapse: height .35s ease !default;\n\n\n// Fonts\n//\n// Font, line-height, and color for body text, headings, and more.\n\n$font-family-sans-serif: -apple-system, BlinkMacSystemFont, \"Segoe UI\", Roboto, \"Helvetica Neue\", Arial, sans-serif !default;\n$font-family-monospace: Menlo, Monaco, Consolas, \"Liberation Mono\", \"Courier New\", monospace !default;\n$font-family-base: $font-family-sans-serif !default;\n\n$font-size-base: 1rem !default; // Assumes the browser default, typically `16px`\n$font-size-lg: 1.25rem !default;\n$font-size-sm: .875rem !default;\n\n$font-weight-normal: normal !default;\n$font-weight-bold: bold !default;\n\n$font-weight-base: $font-weight-normal !default;\n$line-height-base: 1.5 !default;\n\n$h1-font-size: 2.5rem !default;\n$h2-font-size: 2rem !default;\n$h3-font-size: 1.75rem !default;\n$h4-font-size: 1.5rem !default;\n$h5-font-size: 1.25rem !default;\n$h6-font-size: 1rem !default;\n\n$headings-margin-bottom: ($spacer / 2) !default;\n$headings-font-family: inherit !default;\n$headings-font-weight: 500 !default;\n$headings-line-height: 1.1 !default;\n$headings-color: inherit !default;\n\n$display1-size: 6rem !default;\n$display2-size: 5.5rem !default;\n$display3-size: 4.5rem !default;\n$display4-size: 3.5rem !default;\n\n$display1-weight: 300 !default;\n$display2-weight: 300 !default;\n$display3-weight: 300 !default;\n$display4-weight: 300 !default;\n$display-line-height: $headings-line-height !default;\n\n$lead-font-size: 1.25rem !default;\n$lead-font-weight: 300 !default;\n\n$small-font-size: 80% !default;\n\n$text-muted: $gray-600 !default;\n\n$blockquote-small-color: $gray-600 !default;\n$blockquote-font-size: ($font-size-base * 1.25) !default;\n\n$hr-border-color: rgba($black,.1) !default;\n$hr-border-width: $border-width !default;\n\n$mark-padding: .2em !default;\n\n$dt-font-weight: $font-weight-bold !default;\n\n$kbd-box-shadow: inset 0 -.1rem 0 rgba($black,.25) !default;\n$nested-kbd-font-weight: $font-weight-bold !default;\n\n$list-inline-padding: 5px !default;\n\n$mark-bg: #fcf8e3 !default;\n\n\n// Tables\n//\n// Customizes the `.table` component with basic values, each used across all table variations.\n\n$table-cell-padding: .75rem !default;\n$table-cell-padding-sm: .3rem !default;\n\n$table-bg: transparent !default;\n$table-accent-bg: rgba($black,.05) !default;\n$table-hover-bg: rgba($black,.075) !default;\n$table-active-bg: $table-hover-bg !default;\n\n$table-border-width: $border-width !default;\n$table-border-color: $gray-200 !default;\n\n$table-head-bg: $gray-200 !default;\n$table-head-color: $gray-700 !default;\n\n$table-inverse-bg: $gray-900 !default;\n$table-inverse-accent-bg: rgba($white, .05) !default;\n$table-inverse-hover-bg: rgba($white, .075) !default;\n$table-inverse-border-color: lighten($gray-900, 7.5%) !default;\n$table-inverse-color: $body-bg !default;\n\n\n// Buttons\n//\n// For each of Bootstrap's buttons, define text, background and border color.\n\n$input-btn-padding-y: .5rem !default;\n$input-btn-padding-x: .75rem !default;\n$input-btn-line-height: 1.25 !default;\n\n$input-btn-padding-y-sm: .25rem !default;\n$input-btn-padding-x-sm: .5rem !default;\n$input-btn-line-height-sm: 1.5 !default;\n\n$input-btn-padding-y-lg: .5rem !default;\n$input-btn-padding-x-lg: 1rem !default;\n$input-btn-line-height-lg: 1.5 !default;\n\n$btn-font-weight: $font-weight-normal !default;\n$btn-box-shadow: inset 0 1px 0 rgba($white,.15), 0 1px 1px rgba($black,.075) !default;\n$btn-focus-box-shadow: 0 0 0 3px rgba(theme-color(\"primary\"), .25) !default;\n$btn-active-box-shadow: inset 0 3px 5px rgba($black,.125) !default;\n\n$btn-link-disabled-color: $gray-600 !default;\n\n$btn-block-spacing-y: .5rem !default;\n\n// Allows for customizing button radius independently from global border radius\n$btn-border-radius: $border-radius !default;\n$btn-border-radius-lg: $border-radius-lg !default;\n$btn-border-radius-sm: $border-radius-sm !default;\n\n$btn-transition: all .15s ease-in-out !default;\n\n\n// Forms\n\n$input-bg: $white !default;\n$input-disabled-bg: $gray-200 !default;\n\n$input-color: $gray-700 !default;\n$input-border-color: rgba($black,.15) !default;\n$input-btn-border-width: $border-width !default; // For form controls and buttons\n$input-box-shadow: inset 0 1px 1px rgba($black,.075) !default;\n\n$input-border-radius: $border-radius !default;\n$input-border-radius-lg: $border-radius-lg !default;\n$input-border-radius-sm: $border-radius-sm !default;\n\n$input-focus-bg: $input-bg !default;\n$input-focus-border-color: lighten(theme-color(\"primary\"), 25%) !default;\n$input-focus-box-shadow: $input-box-shadow, $btn-focus-box-shadow !default;\n$input-focus-color: $input-color !default;\n\n$input-placeholder-color: $gray-600 !default;\n\n$input-height-border: $input-btn-border-width * 2 !default;\n\n$input-height-inner: ($font-size-base * $input-btn-line-height) + ($input-btn-padding-y * 2) !default;\n$input-height: calc(#{$input-height-inner} + #{$input-height-border}) !default;\n\n$input-height-inner-sm: ($font-size-sm * $input-btn-line-height-sm) + ($input-btn-padding-y-sm * 2) !default;\n$input-height-sm: calc(#{$input-height-inner-sm} + #{$input-height-border}) !default;\n\n$input-height-inner-lg: ($font-size-sm * $input-btn-line-height-lg) + ($input-btn-padding-y-lg * 2) !default;\n$input-height-lg: calc(#{$input-height-inner-lg} + #{$input-height-border}) !default;\n\n$input-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s !default;\n\n$form-text-margin-top: .25rem !default;\n\n$form-check-margin-bottom: .5rem !default;\n$form-check-input-gutter: 1.25rem !default;\n$form-check-input-margin-y: .25rem !default;\n$form-check-input-margin-x: .25rem !default;\n\n$form-check-inline-margin-x: .75rem !default;\n\n$form-group-margin-bottom: 1rem !default;\n\n$input-group-addon-bg: $gray-200 !default;\n$input-group-addon-border-color: $input-border-color !default;\n\n$custom-control-gutter: 1.5rem !default;\n$custom-control-spacer-y: .25rem !default;\n$custom-control-spacer-x: 1rem !default;\n\n$custom-control-indicator-size: 1rem !default;\n$custom-control-indicator-bg: #ddd !default;\n$custom-control-indicator-bg-size: 50% 50% !default;\n$custom-control-indicator-box-shadow: inset 0 .25rem .25rem rgba($black,.1) !default;\n\n$custom-control-indicator-disabled-bg: $gray-200 !default;\n$custom-control-description-disabled-color: $gray-600 !default;\n\n$custom-control-indicator-checked-color: $white !default;\n$custom-control-indicator-checked-bg: theme-color(\"primary\") !default;\n$custom-control-indicator-checked-box-shadow: none !default;\n\n$custom-control-indicator-focus-box-shadow: 0 0 0 1px $body-bg, 0 0 0 3px theme-color(\"primary\") !default;\n\n$custom-control-indicator-active-color: $white !default;\n$custom-control-indicator-active-bg: lighten(theme-color(\"primary\"), 35%) !default;\n$custom-control-indicator-active-box-shadow: none !default;\n\n$custom-checkbox-indicator-border-radius: $border-radius !default;\n$custom-checkbox-indicator-icon-checked: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 8 8'%3E%3Cpath fill='#{$custom-control-indicator-checked-color}' d='M6.564.75l-3.59 3.612-1.538-1.55L0 4.26 2.974 7.25 8 2.193z'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n\n$custom-checkbox-indicator-indeterminate-bg: theme-color(\"primary\") !default;\n$custom-checkbox-indicator-indeterminate-color: $custom-control-indicator-checked-color !default;\n$custom-checkbox-indicator-icon-indeterminate: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 4 4'%3E%3Cpath stroke='#{$custom-checkbox-indicator-indeterminate-color}' d='M0 2h4'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n$custom-checkbox-indicator-indeterminate-box-shadow: none !default;\n\n$custom-radio-indicator-border-radius: 50% !default;\n$custom-radio-indicator-icon-checked: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='-4 -4 8 8'%3E%3Ccircle r='3' fill='#{$custom-control-indicator-checked-color}'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n\n$custom-select-padding-y: .375rem !default;\n$custom-select-padding-x: .75rem !default;\n$custom-select-height: $input-height !default;\n$custom-select-indicator-padding: 1rem !default; // Extra padding to account for the presence of the background-image based indicator\n$custom-select-line-height: $input-btn-line-height !default;\n$custom-select-color: $input-color !default;\n$custom-select-disabled-color: $gray-600 !default;\n$custom-select-bg: $white !default;\n$custom-select-disabled-bg: $gray-200 !default;\n$custom-select-bg-size: 8px 10px !default; // In pixels because image dimensions\n$custom-select-indicator-color: #333 !default;\n$custom-select-indicator: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 4 5'%3E%3Cpath fill='#{$custom-select-indicator-color}' d='M2 0L0 2h4zm0 5L0 3h4z'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n$custom-select-border-width: $input-btn-border-width !default;\n$custom-select-border-color: $input-border-color !default;\n$custom-select-border-radius: $border-radius !default;\n\n$custom-select-focus-border-color: lighten(theme-color(\"primary\"), 25%) !default;\n$custom-select-focus-box-shadow: inset 0 1px 2px rgba($black, .075), 0 0 5px rgba($custom-select-focus-border-color, .5) !default;\n\n$custom-select-font-size-sm: 75% !default;\n$custom-select-height-sm: $input-height-sm !default;\n\n$custom-file-height: 2.5rem !default;\n$custom-file-width: 14rem !default;\n$custom-file-focus-box-shadow: 0 0 0 .075rem $white, 0 0 0 .2rem theme-color(\"primary\") !default;\n\n$custom-file-padding-y: 1rem !default;\n$custom-file-padding-x: .5rem !default;\n$custom-file-line-height: 1.5 !default;\n$custom-file-color: $gray-700 !default;\n$custom-file-bg: $white !default;\n$custom-file-border-width: $border-width !default;\n$custom-file-border-color: $input-border-color !default;\n$custom-file-border-radius: $border-radius !default;\n$custom-file-box-shadow: inset 0 .2rem .4rem rgba($black,.05) !default;\n$custom-file-button-color: $custom-file-color !default;\n$custom-file-button-bg: $gray-200 !default;\n$custom-file-text: (\n placeholder: (\n en: \"Choose file...\"\n ),\n button-label: (\n en: \"Browse\"\n )\n) !default;\n\n\n// Form validation\n$form-feedback-valid-color: theme-color(\"success\") !default;\n$form-feedback-invalid-color: theme-color(\"danger\") !default;\n\n\n// Dropdowns\n//\n// Dropdown menu container and contents.\n\n$dropdown-min-width: 10rem !default;\n$dropdown-padding-y: .5rem !default;\n$dropdown-spacer: .125rem !default;\n$dropdown-bg: $white !default;\n$dropdown-border-color: rgba($black,.15) !default;\n$dropdown-border-width: $border-width !default;\n$dropdown-divider-bg: $gray-200 !default;\n$dropdown-box-shadow: 0 .5rem 1rem rgba($black,.175) !default;\n\n$dropdown-link-color: $gray-900 !default;\n$dropdown-link-hover-color: darken($gray-900, 5%) !default;\n$dropdown-link-hover-bg: $gray-100 !default;\n\n$dropdown-link-active-color: $component-active-color !default;\n$dropdown-link-active-bg: $component-active-bg !default;\n\n$dropdown-link-disabled-color: $gray-600 !default;\n\n$dropdown-item-padding-y: .25rem !default;\n$dropdown-item-padding-x: 1.5rem !default;\n\n$dropdown-header-color: $gray-600 !default;\n\n\n// Z-index master list\n//\n// Warning: Avoid customizing these values. They're used for a bird's eye view\n// of components dependent on the z-axis and are designed to all work together.\n\n$zindex-dropdown: 1000 !default;\n$zindex-sticky: 1020 !default;\n$zindex-fixed: 1030 !default;\n$zindex-modal-backdrop: 1040 !default;\n$zindex-modal: 1050 !default;\n$zindex-popover: 1060 !default;\n$zindex-tooltip: 1070 !default;\n\n// Navs\n\n$nav-link-padding-y: .5rem !default;\n$nav-link-padding-x: 1rem !default;\n$nav-link-disabled-color: $gray-600 !default;\n\n$nav-tabs-border-color: #ddd !default;\n$nav-tabs-border-width: $border-width !default;\n$nav-tabs-border-radius: $border-radius !default;\n$nav-tabs-link-hover-border-color: $gray-200 !default;\n$nav-tabs-link-active-color: $gray-700 !default;\n$nav-tabs-link-active-bg: $body-bg !default;\n$nav-tabs-link-active-border-color: #ddd !default;\n\n$nav-pills-border-radius: $border-radius !default;\n$nav-pills-link-active-color: $component-active-color !default;\n$nav-pills-link-active-bg: $component-active-bg !default;\n\n// Navbar\n\n$navbar-padding-y: ($spacer / 2) !default;\n$navbar-padding-x: $spacer !default;\n\n$navbar-brand-font-size: $font-size-lg !default;\n// Compute the navbar-brand padding-y so the navbar-brand will have the same height as navbar-text and nav-link\n$nav-link-height: $navbar-brand-font-size * $line-height-base !default;\n$navbar-brand-height: ($font-size-base * $line-height-base + $nav-link-padding-y * 2) !default;\n$navbar-brand-padding-y: ($navbar-brand-height - $nav-link-height) / 2 !default;\n\n$navbar-toggler-padding-y: .25rem !default;\n$navbar-toggler-padding-x: .75rem !default;\n$navbar-toggler-font-size: $font-size-lg !default;\n$navbar-toggler-border-radius: $btn-border-radius !default;\n\n$navbar-dark-color: rgba($white,.5) !default;\n$navbar-dark-hover-color: rgba($white,.75) !default;\n$navbar-dark-active-color: rgba($white,1) !default;\n$navbar-dark-disabled-color: rgba($white,.25) !default;\n$navbar-dark-toggler-icon-bg: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg viewBox='0 0 30 30' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath stroke='#{$navbar-dark-color}' stroke-width='2' stroke-linecap='round' stroke-miterlimit='10' d='M4 7h22M4 15h22M4 23h22'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n$navbar-dark-toggler-border-color: rgba($white,.1) !default;\n\n$navbar-light-color: rgba($black,.5) !default;\n$navbar-light-hover-color: rgba($black,.7) !default;\n$navbar-light-active-color: rgba($black,.9) !default;\n$navbar-light-disabled-color: rgba($black,.3) !default;\n$navbar-light-toggler-icon-bg: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg viewBox='0 0 30 30' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath stroke='#{$navbar-light-color}' stroke-width='2' stroke-linecap='round' stroke-miterlimit='10' d='M4 7h22M4 15h22M4 23h22'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n$navbar-light-toggler-border-color: rgba($black,.1) !default;\n\n// Pagination\n\n$pagination-padding-y: .5rem !default;\n$pagination-padding-x: .75rem !default;\n$pagination-padding-y-sm: .25rem !default;\n$pagination-padding-x-sm: .5rem !default;\n$pagination-padding-y-lg: .75rem !default;\n$pagination-padding-x-lg: 1.5rem !default;\n$pagination-line-height: 1.25 !default;\n\n$pagination-color: $link-color !default;\n$pagination-bg: $white !default;\n$pagination-border-width: $border-width !default;\n$pagination-border-color: #ddd !default;\n\n$pagination-hover-color: $link-hover-color !default;\n$pagination-hover-bg: $gray-200 !default;\n$pagination-hover-border-color: #ddd !default;\n\n$pagination-active-color: $white !default;\n$pagination-active-bg: theme-color(\"primary\") !default;\n$pagination-active-border-color: theme-color(\"primary\") !default;\n\n$pagination-disabled-color: $gray-600 !default;\n$pagination-disabled-bg: $white !default;\n$pagination-disabled-border-color: #ddd !default;\n\n\n// Jumbotron\n\n$jumbotron-padding: 2rem !default;\n$jumbotron-bg: $gray-200 !default;\n\n\n// Cards\n\n$card-spacer-y: .75rem !default;\n$card-spacer-x: 1.25rem !default;\n$card-border-width: 1px !default;\n$card-border-radius: $border-radius !default;\n$card-border-color: rgba($black,.125) !default;\n$card-inner-border-radius: calc(#{$card-border-radius} - #{$card-border-width}) !default;\n$card-cap-bg: rgba($black, .03) !default;\n$card-bg: $white !default;\n\n$card-img-overlay-padding: 1.25rem !default;\n\n$card-deck-margin: ($grid-gutter-width / 2) !default;\n\n$card-columns-count: 3 !default;\n$card-columns-gap: 1.25rem !default;\n$card-columns-margin: $card-spacer-y !default;\n\n\n// Tooltips\n\n$tooltip-max-width: 200px !default;\n$tooltip-color: $white !default;\n$tooltip-bg: $black !default;\n$tooltip-opacity: .9 !default;\n$tooltip-padding-y: 3px !default;\n$tooltip-padding-x: 8px !default;\n$tooltip-margin: 0 !default;\n\n\n$tooltip-arrow-width: 5px !default;\n$tooltip-arrow-height: 5px !default;\n$tooltip-arrow-color: $tooltip-bg !default;\n\n\n// Popovers\n\n$popover-inner-padding: 1px !default;\n$popover-bg: $white !default;\n$popover-max-width: 276px !default;\n$popover-border-width: $border-width !default;\n$popover-border-color: rgba($black,.2) !default;\n$popover-box-shadow: 0 5px 10px rgba($black,.2) !default;\n\n$popover-header-bg: darken($popover-bg, 3%) !default;\n$popover-header-color: $headings-color !default;\n$popover-header-padding-y: 8px !default;\n$popover-header-padding-x: 14px !default;\n\n$popover-body-color: $body-color !default;\n$popover-body-padding-y: 9px !default;\n$popover-body-padding-x: 14px !default;\n\n$popover-arrow-width: 10px !default;\n$popover-arrow-height: 5px !default;\n$popover-arrow-color: $popover-bg !default;\n\n$popover-arrow-outer-width: ($popover-arrow-width + 1px) !default;\n$popover-arrow-outer-color: fade-in($popover-border-color, .05) !default;\n\n\n// Badges\n\n$badge-color: $white !default;\n$badge-font-size: 75% !default;\n$badge-font-weight: $font-weight-bold !default;\n$badge-padding-y: .25em !default;\n$badge-padding-x: .4em !default;\n\n$badge-pill-padding-x: .6em !default;\n// Use a higher than normal value to ensure completely rounded edges when\n// customizing padding or font-size on labels.\n$badge-pill-border-radius: 10rem !default;\n\n\n// Modals\n\n// Padding applied to the modal body\n$modal-inner-padding: 15px !default;\n\n$modal-dialog-margin: 10px !default;\n$modal-dialog-margin-y-sm-up: 30px !default;\n\n$modal-title-line-height: $line-height-base !default;\n\n$modal-content-bg: $white !default;\n$modal-content-border-color: rgba($black,.2) !default;\n$modal-content-border-width: $border-width !default;\n$modal-content-box-shadow-xs: 0 3px 9px rgba($black,.5) !default;\n$modal-content-box-shadow-sm-up: 0 5px 15px rgba($black,.5) !default;\n\n$modal-backdrop-bg: $black !default;\n$modal-backdrop-opacity: .5 !default;\n$modal-header-border-color: $gray-200 !default;\n$modal-footer-border-color: $modal-header-border-color !default;\n$modal-header-border-width: $modal-content-border-width !default;\n$modal-footer-border-width: $modal-header-border-width !default;\n$modal-header-padding: 15px !default;\n\n$modal-lg: 800px !default;\n$modal-md: 500px !default;\n$modal-sm: 300px !default;\n\n$modal-transition: transform .3s ease-out !default;\n\n\n// Alerts\n//\n// Define alert colors, border radius, and padding.\n\n$alert-padding-y: .75rem !default;\n$alert-padding-x: 1.25rem !default;\n$alert-margin-bottom: 1rem !default;\n$alert-border-radius: $border-radius !default;\n$alert-link-font-weight: $font-weight-bold !default;\n$alert-border-width: $border-width !default;\n\n\n// Progress bars\n\n$progress-height: 1rem !default;\n$progress-font-size: .75rem !default;\n$progress-bg: $gray-200 !default;\n$progress-border-radius: $border-radius !default;\n$progress-box-shadow: inset 0 .1rem .1rem rgba($black,.1) !default;\n$progress-bar-color: $white !default;\n$progress-bar-bg: theme-color(\"primary\") !default;\n$progress-bar-animation-timing: 1s linear infinite !default;\n$progress-bar-transition: width .6s ease !default;\n\n// List group\n\n$list-group-bg: $white !default;\n$list-group-border-color: rgba($black,.125) !default;\n$list-group-border-width: $border-width !default;\n$list-group-border-radius: $border-radius !default;\n\n$list-group-item-padding-y: .75rem !default;\n$list-group-item-padding-x: 1.25rem !default;\n\n$list-group-hover-bg: $gray-100 !default;\n$list-group-active-color: $component-active-color !default;\n$list-group-active-bg: $component-active-bg !default;\n$list-group-active-border-color: $list-group-active-bg !default;\n\n$list-group-disabled-color: $gray-600 !default;\n$list-group-disabled-bg: $list-group-bg !default;\n\n$list-group-action-color: $gray-700 !default;\n$list-group-action-hover-color: $list-group-action-color !default;\n\n$list-group-action-active-color: $body-color !default;\n$list-group-action-active-bg: $gray-200 !default;\n\n\n// Image thumbnails\n\n$thumbnail-padding: .25rem !default;\n$thumbnail-bg: $body-bg !default;\n$thumbnail-border-width: $border-width !default;\n$thumbnail-border-color: #ddd !default;\n$thumbnail-border-radius: $border-radius !default;\n$thumbnail-box-shadow: 0 1px 2px rgba($black,.075) !default;\n$thumbnail-transition: all .2s ease-in-out !default;\n\n\n// Figures\n\n$figure-caption-font-size: 90% !default;\n$figure-caption-color: $gray-600 !default;\n\n\n// Breadcrumbs\n\n$breadcrumb-padding-y: .75rem !default;\n$breadcrumb-padding-x: 1rem !default;\n$breadcrumb-item-padding: .5rem !default;\n\n$breadcrumb-bg: $gray-200 !default;\n$breadcrumb-divider-color: $gray-600 !default;\n$breadcrumb-active-color: $gray-600 !default;\n$breadcrumb-divider: \"/\" !default;\n\n\n// Carousel\n\n$carousel-control-color: $white !default;\n$carousel-control-width: 15% !default;\n$carousel-control-opacity: .5 !default;\n\n$carousel-indicator-width: 30px !default;\n$carousel-indicator-height: 3px !default;\n$carousel-indicator-spacer: 3px !default;\n$carousel-indicator-active-bg: $white !default;\n\n$carousel-caption-width: 70% !default;\n$carousel-caption-color: $white !default;\n\n$carousel-control-icon-width: 20px !default;\n\n$carousel-control-prev-icon-bg: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' fill='#{$carousel-control-color}' viewBox='0 0 8 8'%3E%3Cpath d='M4 0l-4 4 4 4 1.5-1.5-2.5-2.5 2.5-2.5-1.5-1.5z'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n$carousel-control-next-icon-bg: str-replace(url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' fill='#{$carousel-control-color}' viewBox='0 0 8 8'%3E%3Cpath d='M1.5 0l-1.5 1.5 2.5 2.5-2.5 2.5 1.5 1.5 4-4-4-4z'/%3E%3C/svg%3E\"), \"#\", \"%23\") !default;\n\n$carousel-transition: transform .6s ease !default;\n\n\n// Close\n\n$close-font-size: $font-size-base * 1.5 !default;\n$close-font-weight: $font-weight-bold !default;\n$close-color: $black !default;\n$close-text-shadow: 0 1px 0 $white !default;\n\n// Code\n\n$code-font-size: 90% !default;\n$code-padding-y: .2rem !default;\n$code-padding-x: .4rem !default;\n$code-color: #bd4147 !default;\n$code-bg: $gray-100 !default;\n\n$kbd-color: $white !default;\n$kbd-bg: $gray-900 !default;\n\n$pre-color: $gray-900 !default;\n$pre-scrollable-max-height: 340px !default;\n","@mixin hover {\n // TODO: re-enable along with mq4-hover-shim\n// @if $enable-hover-media-query {\n// // See Media Queries Level 4: https://drafts.csswg.org/mediaqueries/#hover\n// // Currently shimmed by https://github.com/twbs/mq4-hover-shim\n// @media (hover: hover) {\n// &:hover { @content }\n// }\n// }\n// @else {\n// scss-lint:disable Indentation\n &:hover { @content }\n// scss-lint:enable Indentation\n// }\n}\n\n\n@mixin hover-focus {\n @if $enable-hover-media-query {\n &:focus { @content }\n @include hover { @content }\n } @else {\n &:focus,\n &:hover {\n @content\n }\n }\n}\n\n@mixin plain-hover-focus {\n @if $enable-hover-media-query {\n &,\n &:focus {\n @content\n }\n @include hover { @content }\n } @else {\n &,\n &:focus,\n &:hover {\n @content\n }\n }\n}\n\n@mixin hover-focus-active {\n @if $enable-hover-media-query {\n &:focus,\n &:active {\n @content\n }\n @include hover { @content }\n } @else {\n &:focus,\n &:active,\n &:hover {\n @content\n }\n }\n}\n","//\n// Headings\n//\n\nh1, h2, h3, h4, h5, h6,\n.h1, .h2, .h3, .h4, .h5, .h6 {\n margin-bottom: $headings-margin-bottom;\n font-family: $headings-font-family;\n font-weight: $headings-font-weight;\n line-height: $headings-line-height;\n color: $headings-color;\n}\n\nh1, .h1 { font-size: $h1-font-size; }\nh2, .h2 { font-size: $h2-font-size; }\nh3, .h3 { font-size: $h3-font-size; }\nh4, .h4 { font-size: $h4-font-size; }\nh5, .h5 { font-size: $h5-font-size; }\nh6, .h6 { font-size: $h6-font-size; }\n\n.lead {\n font-size: $lead-font-size;\n font-weight: $lead-font-weight;\n}\n\n// Type display classes\n.display-1 {\n font-size: $display1-size;\n font-weight: $display1-weight;\n line-height: $display-line-height;\n}\n.display-2 {\n font-size: $display2-size;\n font-weight: $display2-weight;\n line-height: $display-line-height;\n}\n.display-3 {\n font-size: $display3-size;\n font-weight: $display3-weight;\n line-height: $display-line-height;\n}\n.display-4 {\n font-size: $display4-size;\n font-weight: $display4-weight;\n line-height: $display-line-height;\n}\n\n\n//\n// Horizontal rules\n//\n\nhr {\n margin-top: 1rem;\n margin-bottom: 1rem;\n border: 0;\n border-top: $hr-border-width solid $hr-border-color;\n}\n\n\n//\n// Emphasis\n//\n\nsmall,\n.small {\n font-size: $small-font-size;\n font-weight: $font-weight-normal;\n}\n\nmark,\n.mark {\n padding: $mark-padding;\n background-color: $mark-bg;\n}\n\n\n//\n// Lists\n//\n\n.list-unstyled {\n @include list-unstyled;\n}\n\n// Inline turns list items into inline-block\n.list-inline {\n @include list-unstyled;\n}\n.list-inline-item {\n display: inline-block;\n\n &:not(:last-child) {\n margin-right: $list-inline-padding;\n }\n}\n\n\n//\n// Misc\n//\n\n// Builds on `abbr`\n.initialism {\n font-size: 90%;\n text-transform: uppercase;\n}\n\n// Blockquotes\n.blockquote {\n margin-bottom: $spacer;\n font-size: $blockquote-font-size;\n}\n\n.blockquote-footer {\n display: block;\n font-size: 80%; // back to default font-size\n color: $blockquote-small-color;\n\n &::before {\n content: \"\\2014 \\00A0\"; // em dash, nbsp\n }\n}\n","// Lists\n\n// Unstyled keeps list items block level, just removes default browser padding and list-style\n@mixin list-unstyled {\n padding-left: 0;\n list-style: none;\n}\n","// Responsive images (ensure images don't scale beyond their parents)\n//\n// This is purposefully opt-in via an explicit class rather than being the default for all `<img>`s.\n// We previously tried the \"images are responsive by default\" approach in Bootstrap v2,\n// and abandoned it in Bootstrap v3 because it breaks lots of third-party widgets (including Google Maps)\n// which weren't expecting the images within themselves to be involuntarily resized.\n// See also https://github.com/twbs/bootstrap/issues/18178\n.img-fluid {\n @include img-fluid;\n}\n\n\n// Image thumbnails\n.img-thumbnail {\n padding: $thumbnail-padding;\n background-color: $thumbnail-bg;\n border: $thumbnail-border-width solid $thumbnail-border-color;\n @include border-radius($thumbnail-border-radius);\n @include transition($thumbnail-transition);\n @include box-shadow($thumbnail-box-shadow);\n\n // Keep them at most 100% wide\n @include img-fluid;\n}\n\n//\n// Figures\n//\n\n.figure {\n // Ensures the caption's text aligns with the image.\n display: inline-block;\n}\n\n.figure-img {\n margin-bottom: ($spacer / 2);\n line-height: 1;\n}\n\n.figure-caption {\n font-size: $figure-caption-font-size;\n color: $figure-caption-color;\n}\n","// Image Mixins\n// - Responsive image\n// - Retina image\n\n\n// Responsive image\n//\n// Keep images from scaling beyond the width of their parents.\n\n@mixin img-fluid {\n // Part 1: Set a maximum relative to the parent\n max-width: 100%;\n // Part 2: Override the height to auto, otherwise images will be stretched\n // when setting a width and height attribute on the img element.\n height: auto;\n}\n\n\n// Retina image\n//\n// Short retina mixin for setting background-image and -size.\n\n@mixin img-retina($file-1x, $file-2x, $width-1x, $height-1x) {\n background-image: url($file-1x);\n\n // Autoprefixer takes care of adding -webkit-min-device-pixel-ratio and -o-min-device-pixel-ratio,\n // but doesn't convert dppx=>dpi.\n // There's no such thing as unprefixed min-device-pixel-ratio since it's nonstandard.\n // Compatibility info: http://caniuse.com/#feat=css-media-resolution\n @media\n only screen and (min-resolution: 192dpi), // IE9-11 don't support dppx\n only screen and (min-resolution: 2dppx) { // Standardized\n background-image: url($file-2x);\n background-size: $width-1x $height-1x;\n }\n}\n","// Single side border-radius\n\n@mixin border-radius($radius: $border-radius) {\n @if $enable-rounded {\n border-radius: $radius;\n }\n}\n\n@mixin border-top-radius($radius) {\n @if $enable-rounded {\n border-top-left-radius: $radius;\n border-top-right-radius: $radius;\n }\n}\n\n@mixin border-right-radius($radius) {\n @if $enable-rounded {\n border-top-right-radius: $radius;\n border-bottom-right-radius: $radius;\n }\n}\n\n@mixin border-bottom-radius($radius) {\n @if $enable-rounded {\n border-bottom-right-radius: $radius;\n border-bottom-left-radius: $radius;\n }\n}\n\n@mixin border-left-radius($radius) {\n @if $enable-rounded {\n border-top-left-radius: $radius;\n border-bottom-left-radius: $radius;\n }\n}\n","@mixin transition($transition...) {\n @if $enable-transitions {\n @if length($transition) == 0 {\n transition: $transition-base;\n } @else {\n transition: $transition;\n }\n }\n}\n","// Inline and block code styles\ncode,\nkbd,\npre,\nsamp {\n font-family: $font-family-monospace;\n}\n\n// Inline code\ncode {\n padding: $code-padding-y $code-padding-x;\n font-size: $code-font-size;\n color: $code-color;\n background-color: $code-bg;\n @include border-radius($border-radius);\n\n // Streamline the style when inside anchors to avoid broken underline and more\n a > & {\n padding: 0;\n color: inherit;\n background-color: inherit;\n }\n}\n\n// User input typically entered via keyboard\nkbd {\n padding: $code-padding-y $code-padding-x;\n font-size: $code-font-size;\n color: $kbd-color;\n background-color: $kbd-bg;\n @include border-radius($border-radius-sm);\n @include box-shadow($kbd-box-shadow);\n\n kbd {\n padding: 0;\n font-size: 100%;\n font-weight: $nested-kbd-font-weight;\n @include box-shadow(none);\n }\n}\n\n// Blocks of code\npre {\n display: block;\n margin-top: 0;\n margin-bottom: 1rem;\n font-size: $code-font-size;\n color: $pre-color;\n\n // Account for some code outputs that place code tags in pre tags\n code {\n padding: 0;\n font-size: inherit;\n color: inherit;\n background-color: transparent;\n border-radius: 0;\n }\n}\n\n// Enable scrollable blocks of code\n.pre-scrollable {\n max-height: $pre-scrollable-max-height;\n overflow-y: scroll;\n}\n","// Container widths\n//\n// Set the container width, and override it for fixed navbars in media queries.\n\n@if $enable-grid-classes {\n .container {\n @include make-container();\n @include make-container-max-widths();\n }\n}\n\n// Fluid container\n//\n// Utilizes the mixin meant for fixed width containers, but with 100% width for\n// fluid, full width layouts.\n\n@if $enable-grid-classes {\n .container-fluid {\n width: 100%;\n @include make-container();\n }\n}\n\n// Row\n//\n// Rows contain and clear the floats of your columns.\n\n@if $enable-grid-classes {\n .row {\n @include make-row();\n }\n\n // Remove the negative margin from default .row, then the horizontal padding\n // from all immediate children columns (to prevent runaway style inheritance).\n .no-gutters {\n margin-right: 0;\n margin-left: 0;\n\n > .col,\n > [class*=\"col-\"] {\n padding-right: 0;\n padding-left: 0;\n }\n }\n}\n\n// Columns\n//\n// Common styles for small and large grid columns\n\n@if $enable-grid-classes {\n @include make-grid-columns();\n}\n","/// Grid system\n//\n// Generate semantic grid columns with these mixins.\n\n@mixin make-container() {\n margin-right: auto;\n margin-left: auto;\n padding-right: ($grid-gutter-width / 2);\n padding-left: ($grid-gutter-width / 2);\n width: 100%;\n}\n\n\n// For each breakpoint, define the maximum width of the container in a media query\n@mixin make-container-max-widths($max-widths: $container-max-widths, $breakpoints: $grid-breakpoints) {\n @each $breakpoint, $container-max-width in $max-widths {\n @include media-breakpoint-up($breakpoint, $breakpoints) {\n max-width: $container-max-width;\n }\n }\n}\n\n@mixin make-row() {\n display: flex;\n flex-wrap: wrap;\n margin-right: ($grid-gutter-width / -2);\n margin-left: ($grid-gutter-width / -2);\n}\n\n@mixin make-col-ready() {\n position: relative;\n // Prevent columns from becoming too narrow when at smaller grid tiers by\n // always setting `width: 100%;`. This works because we use `flex` values\n // later on to override this initial width.\n width: 100%;\n min-height: 1px; // Prevent collapsing\n padding-right: ($grid-gutter-width / 2);\n padding-left: ($grid-gutter-width / 2);\n}\n\n@mixin make-col($size, $columns: $grid-columns) {\n flex: 0 0 percentage($size / $columns);\n // Add a `max-width` to ensure content within each column does not blow out\n // the width of the column. Applies to IE10+ and Firefox. Chrome and Safari\n // do not appear to require this.\n max-width: percentage($size / $columns);\n}\n","// Breakpoint viewport sizes and media queries.\n//\n// Breakpoints are defined as a map of (name: minimum width), order from small to large:\n//\n// (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px)\n//\n// The map defined in the `$grid-breakpoints` global variable is used as the `$breakpoints` argument by default.\n\n// Name of the next breakpoint, or null for the last breakpoint.\n//\n// >> breakpoint-next(sm)\n// md\n// >> breakpoint-next(sm, (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px))\n// md\n// >> breakpoint-next(sm, $breakpoint-names: (xs sm md lg xl))\n// md\n@function breakpoint-next($name, $breakpoints: $grid-breakpoints, $breakpoint-names: map-keys($breakpoints)) {\n $n: index($breakpoint-names, $name);\n @return if($n < length($breakpoint-names), nth($breakpoint-names, $n + 1), null);\n}\n\n// Minimum breakpoint width. Null for the smallest (first) breakpoint.\n//\n// >> breakpoint-min(sm, (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px))\n// 576px\n@function breakpoint-min($name, $breakpoints: $grid-breakpoints) {\n $min: map-get($breakpoints, $name);\n @return if($min != 0, $min, null);\n}\n\n// Maximum breakpoint width. Null for the largest (last) breakpoint.\n// The maximum value is calculated as the minimum of the next one less 0.1.\n//\n// >> breakpoint-max(sm, (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px))\n// 767px\n@function breakpoint-max($name, $breakpoints: $grid-breakpoints) {\n $next: breakpoint-next($name, $breakpoints);\n @return if($next, breakpoint-min($next, $breakpoints) - 1px, null);\n}\n\n// Returns a blank string if smallest breakpoint, otherwise returns the name with a dash infront.\n// Useful for making responsive utilities.\n//\n// >> breakpoint-infix(xs, (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px))\n// \"\" (Returns a blank string)\n// >> breakpoint-infix(sm, (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px))\n// \"-sm\"\n@function breakpoint-infix($name, $breakpoints: $grid-breakpoints) {\n @return if(breakpoint-min($name, $breakpoints) == null, \"\", \"-#{$name}\");\n}\n\n// Media of at least the minimum breakpoint width. No query for the smallest breakpoint.\n// Makes the @content apply to the given breakpoint and wider.\n@mixin media-breakpoint-up($name, $breakpoints: $grid-breakpoints) {\n $min: breakpoint-min($name, $breakpoints);\n @if $min {\n @media (min-width: $min) {\n @content;\n }\n } @else {\n @content;\n }\n}\n\n// Media of at most the maximum breakpoint width. No query for the largest breakpoint.\n// Makes the @content apply to the given breakpoint and narrower.\n@mixin media-breakpoint-down($name, $breakpoints: $grid-breakpoints) {\n $max: breakpoint-max($name, $breakpoints);\n @if $max {\n @media (max-width: $max) {\n @content;\n }\n } @else {\n @content;\n }\n}\n\n// Media that spans multiple breakpoint widths.\n// Makes the @content apply between the min and max breakpoints\n@mixin media-breakpoint-between($lower, $upper, $breakpoints: $grid-breakpoints) {\n $min: breakpoint-min($lower, $breakpoints);\n $max: breakpoint-max($upper, $breakpoints);\n\n @media (min-width: $min) and (max-width: $max) {\n @content;\n }\n}\n\n// Media between the breakpoint's minimum and maximum widths.\n// No minimum for the smallest breakpoint, and no maximum for the largest one.\n// Makes the @content apply only to the given breakpoint, not viewports any wider or narrower.\n@mixin media-breakpoint-only($name, $breakpoints: $grid-breakpoints) {\n $min: breakpoint-min($name, $breakpoints);\n $max: breakpoint-max($name, $breakpoints);\n\n @if $min != null and $max != null {\n @media (min-width: $min) and (max-width: $max) {\n @content;\n }\n } @else if $max == null {\n @include media-breakpoint-up($name)\n } @else if $min == null {\n @include media-breakpoint-down($name)\n }\n}\n","// Framework grid generation\n//\n// Used only by Bootstrap to generate the correct number of grid classes given\n// any value of `$grid-columns`.\n\n@mixin make-grid-columns($columns: $grid-columns, $gutter: $grid-gutter-width, $breakpoints: $grid-breakpoints) {\n // Common properties for all breakpoints\n %grid-column {\n position: relative;\n width: 100%;\n min-height: 1px; // Prevent columns from collapsing when empty\n padding-right: ($gutter / 2);\n padding-left: ($gutter / 2);\n }\n\n @each $breakpoint in map-keys($breakpoints) {\n $infix: breakpoint-infix($breakpoint, $breakpoints);\n\n // Allow columns to stretch full width below their breakpoints\n @for $i from 1 through $columns {\n .col#{$infix}-#{$i} {\n @extend %grid-column;\n }\n }\n .col#{$infix},\n .col#{$infix}-auto {\n @extend %grid-column;\n }\n\n @include media-breakpoint-up($breakpoint, $breakpoints) {\n // Provide basic `.col-{bp}` classes for equal-width flexbox columns\n .col#{$infix} {\n flex-basis: 0;\n flex-grow: 1;\n max-width: 100%;\n }\n .col#{$infix}-auto {\n flex: 0 0 auto;\n width: auto;\n max-width: none; // Reset earlier grid tiers\n }\n\n @for $i from 1 through $columns {\n .col#{$infix}-#{$i} {\n @include make-col($i, $columns);\n }\n }\n\n @for $i from 1 through $columns {\n .order#{$infix}-#{$i} {\n order: $i;\n }\n }\n }\n }\n}\n","//\n// Basic Bootstrap table\n//\n\n.table {\n width: 100%;\n max-width: 100%;\n margin-bottom: $spacer;\n background-color: $table-bg; // Reset for nesting within parents with `background-color`.\n\n th,\n td {\n padding: $table-cell-padding;\n vertical-align: top;\n border-top: $table-border-width solid $table-border-color;\n }\n\n thead th {\n vertical-align: bottom;\n border-bottom: (2 * $table-border-width) solid $table-border-color;\n }\n\n tbody + tbody {\n border-top: (2 * $table-border-width) solid $table-border-color;\n }\n\n .table {\n background-color: $body-bg;\n }\n}\n\n\n//\n// Condensed table w/ half padding\n//\n\n.table-sm {\n th,\n td {\n padding: $table-cell-padding-sm;\n }\n}\n\n\n// Bordered version\n//\n// Add borders all around the table and between all the columns.\n\n.table-bordered {\n border: $table-border-width solid $table-border-color;\n\n th,\n td {\n border: $table-border-width solid $table-border-color;\n }\n\n thead {\n th,\n td {\n border-bottom-width: (2 * $table-border-width);\n }\n }\n}\n\n\n// Zebra-striping\n//\n// Default zebra-stripe styles (alternating gray and transparent backgrounds)\n\n.table-striped {\n tbody tr:nth-of-type(odd) {\n background-color: $table-accent-bg;\n }\n}\n\n\n// Hover effect\n//\n// Placed here since it has to come after the potential zebra striping\n\n.table-hover {\n tbody tr {\n @include hover {\n background-color: $table-hover-bg;\n }\n }\n}\n\n\n// Table backgrounds\n//\n// Exact selectors below required to override `.table-striped` and prevent\n// inheritance to nested tables.\n\n@each $color, $value in $theme-colors {\n @include table-row-variant($color, theme-color-level($color, -9));\n}\n\n@include table-row-variant(active, $table-active-bg);\n\n\n// Inverse styles\n//\n// Same table markup, but inverted color scheme: dark background and light text.\n\n.thead-inverse {\n th {\n color: $table-inverse-color;\n background-color: $table-inverse-bg;\n }\n}\n\n.thead-default {\n th {\n color: $table-head-color;\n background-color: $table-head-bg;\n }\n}\n\n.table-inverse {\n color: $table-inverse-color;\n background-color: $table-inverse-bg;\n\n th,\n td,\n thead th {\n border-color: $table-inverse-border-color;\n }\n\n &.table-bordered {\n border: 0;\n }\n\n &.table-striped {\n tbody tr:nth-of-type(odd) {\n background-color: $table-inverse-accent-bg;\n }\n }\n\n &.table-hover {\n tbody tr {\n @include hover {\n background-color: $table-inverse-hover-bg;\n }\n }\n }\n}\n\n\n// Responsive tables\n//\n// Add `.table-responsive` to `.table`s and we'll make them mobile friendly by\n// enabling horizontal scrolling. Only applies <768px. Everything above that\n// will display normally.\n\n.table-responsive {\n @include media-breakpoint-down(md) {\n display: block;\n width: 100%;\n overflow-x: auto;\n -ms-overflow-style: -ms-autohiding-scrollbar; // See https://github.com/twbs/bootstrap/pull/10057\n\n // Prevent double border on horizontal scroll due to use of `display: block;`\n &.table-bordered {\n border: 0;\n }\n }\n}\n","// Tables\n\n@mixin table-row-variant($state, $background) {\n // Exact selectors below required to override `.table-striped` and prevent\n // inheritance to nested tables.\n .table-#{$state} {\n &,\n > th,\n > td {\n background-color: $background;\n }\n }\n\n // Hover states for `.table-hover`\n // Note: this is not available for cells or rows within `thead` or `tfoot`.\n .table-hover {\n $hover-background: darken($background, 5%);\n\n .table-#{$state} {\n @include hover {\n background-color: $hover-background;\n\n > td,\n > th {\n background-color: $hover-background;\n }\n }\n }\n }\n}\n","// Bootstrap functions\n//\n// Utility mixins and functions for evalutating source code across our variables, maps, and mixins.\n\n// Ascending\n// Used to evaluate Sass maps like our grid breakpoints.\n@mixin _assert-ascending($map, $map-name) {\n $prev-key: null;\n $prev-num: null;\n @each $key, $num in $map {\n @if $prev-num == null {\n // Do nothing\n } @else if not comparable($prev-num, $num) {\n @warn \"Potentially invalid value for #{$map-name}: This map must be in ascending order, but key '#{$key}' has value #{$num} whose unit makes it incomparable to #{$prev-num}, the value of the previous key '#{$prev-key}' !\";\n } @else if $prev-num >= $num {\n @warn \"Invalid value for #{$map-name}: This map must be in ascending order, but key '#{$key}' has value #{$num} which isn't greater than #{$prev-num}, the value of the previous key '#{$prev-key}' !\";\n }\n $prev-key: $key;\n $prev-num: $num;\n }\n}\n\n// Starts at zero\n// Another grid mixin that ensures the min-width of the lowest breakpoint starts at 0.\n@mixin _assert-starts-at-zero($map) {\n $values: map-values($map);\n $first-value: nth($values, 1);\n @if $first-value != 0 {\n @warn \"First breakpoint in `$grid-breakpoints` must start at 0, but starts at #{$first-value}.\";\n }\n}\n\n// Replace `$search` with `$replace` in `$string`\n// Used on our SVG icon backgrounds for custom forms.\n//\n// @author Hugo Giraudel\n// @param {String} $string - Initial string\n// @param {String} $search - Substring to replace\n// @param {String} $replace ('') - New value\n// @return {String} - Updated string\n@function str-replace($string, $search, $replace: \"\") {\n $index: str-index($string, $search);\n\n @if $index {\n @return str-slice($string, 1, $index - 1) + $replace + str-replace(str-slice($string, $index + str-length($search)), $search, $replace);\n }\n\n @return $string;\n}\n\n// Color contrast\n@mixin color-yiq($color) {\n $r: red($color);\n $g: green($color);\n $b: blue($color);\n\n $yiq: (($r * 299) + ($g * 587) + ($b * 114)) / 1000;\n\n @if ($yiq >= 150) {\n color: #111;\n } @else {\n color: #fff;\n }\n}\n\n// Retreive color Sass maps\n@function color($key: \"blue\") {\n @return map-get($colors, $key);\n}\n\n@function theme-color($key: \"primary\") {\n @return map-get($theme-colors, $key);\n}\n\n@function grayscale($key: \"100\") {\n @return map-get($grays, $key);\n}\n\n// Request a theme color level\n@function theme-color-level($color-name: \"primary\", $level: 0) {\n $color: theme-color($color-name);\n $color-base: if($level > 0, #000, #fff);\n\n @if $level < 0 {\n // Lighter values need a quick double negative for the Sass math to work\n @return mix($color-base, $color, $level * -1 * $theme-color-interval);\n } @else {\n @return mix($color-base, $color, $level * $theme-color-interval);\n }\n}\n","// scss-lint:disable QualifyingElement, VendorPrefix\n\n//\n// Textual form controls\n//\n\n.form-control {\n display: block;\n width: 100%;\n // // Make inputs at least the height of their button counterpart (base line-height + padding + border)\n // height: $input-height;\n padding: $input-btn-padding-y $input-btn-padding-x;\n font-size: $font-size-base;\n line-height: $input-btn-line-height;\n color: $input-color;\n background-color: $input-bg;\n // Reset unusual Firefox-on-Android default style; see https://github.com/necolas/normalize.css/issues/214.\n background-image: none;\n background-clip: padding-box;\n border: $input-btn-border-width solid $input-border-color;\n\n // Note: This has no effect on <select>s in some browsers, due to the limited stylability of `<select>`s in CSS.\n @if $enable-rounded {\n // Manually use the if/else instead of the mixin to account for iOS override\n border-radius: $input-border-radius;\n } @else {\n // Otherwise undo the iOS default\n border-radius: 0;\n }\n\n @include box-shadow($input-box-shadow);\n @include transition($input-transition);\n\n // Unstyle the caret on `<select>`s in IE10+.\n &::-ms-expand {\n background-color: transparent;\n border: 0;\n }\n\n // Customize the `:focus` state to imitate native WebKit styles.\n @include form-control-focus();\n\n // Placeholder\n &::placeholder {\n color: $input-placeholder-color;\n // Override Firefox's unusual default opacity; see https://github.com/twbs/bootstrap/pull/11526.\n opacity: 1;\n }\n\n // Disabled and read-only inputs\n //\n // HTML5 says that controls under a fieldset > legend:first-child won't be\n // disabled if the fieldset is disabled. Due to implementation difficulty, we\n // don't honor that edge case; we style them as disabled anyway.\n &:disabled,\n &[readonly] {\n background-color: $input-disabled-bg;\n // iOS fix for unreadable disabled content; see https://github.com/twbs/bootstrap/issues/11655.\n opacity: 1;\n }\n}\n\nselect.form-control {\n &:not([size]):not([multiple]) {\n height: $input-height;\n }\n\n &:focus::-ms-value {\n // Suppress the nested default white text on blue background highlight given to\n // the selected option text when the (still closed) <select> receives focus\n // in IE and (under certain conditions) Edge, as it looks bad and cannot be made to\n // match the appearance of the native widget.\n // See https://github.com/twbs/bootstrap/issues/19398.\n color: $input-color;\n background-color: $input-bg;\n }\n}\n\n// Make file inputs better match text inputs by forcing them to new lines.\n.form-control-file,\n.form-control-range {\n display: block;\n}\n\n\n//\n// Labels\n//\n\n// For use with horizontal and inline forms, when you need the label text to\n// align with the form controls.\n.col-form-label {\n padding-top: calc(#{$input-btn-padding-y} - #{$input-btn-border-width} * 2);\n padding-bottom: calc(#{$input-btn-padding-y} - #{$input-btn-border-width} * 2);\n margin-bottom: 0; // Override the `<label>` default\n}\n\n.col-form-label-lg {\n padding-top: calc(#{$input-btn-padding-y-lg} - #{$input-btn-border-width} * 2);\n padding-bottom: calc(#{$input-btn-padding-y-lg} - #{$input-btn-border-width} * 2);\n font-size: $font-size-lg;\n}\n\n.col-form-label-sm {\n padding-top: calc(#{$input-btn-padding-y-sm} - #{$input-btn-border-width} * 2);\n padding-bottom: calc(#{$input-btn-padding-y-sm} - #{$input-btn-border-width} * 2);\n font-size: $font-size-sm;\n}\n\n\n//\n// Legends\n//\n\n// For use with horizontal and inline forms, when you need the legend text to\n// be the same size as regular labels, and to align with the form controls.\n.col-form-legend {\n padding-top: $input-btn-padding-y;\n padding-bottom: $input-btn-padding-y;\n margin-bottom: 0;\n font-size: $font-size-base;\n}\n\n\n// Readonly controls as plain text\n//\n// Apply class to a readonly input to make it appear like regular plain\n// text (without any border, background color, focus indicator)\n\n.form-control-plaintext {\n padding-top: $input-btn-padding-y;\n padding-bottom: $input-btn-padding-y;\n margin-bottom: 0; // match inputs if this class comes on inputs with default margins\n line-height: $input-btn-line-height;\n border: solid transparent;\n border-width: $input-btn-border-width 0;\n\n &.form-control-sm,\n &.form-control-lg {\n padding-right: 0;\n padding-left: 0;\n }\n}\n\n\n// Form control sizing\n//\n// Build on `.form-control` with modifier classes to decrease or increase the\n// height and font-size of form controls.\n//\n// The `.form-group-* form-control` variations are sadly duplicated to avoid the\n// issue documented in https://github.com/twbs/bootstrap/issues/15074.\n\n.form-control-sm {\n padding: $input-btn-padding-y-sm $input-btn-padding-x-sm;\n font-size: $font-size-sm;\n line-height: $input-btn-line-height-sm;\n @include border-radius($input-border-radius-sm);\n}\n\nselect.form-control-sm {\n &:not([size]):not([multiple]) {\n height: $input-height-sm;\n }\n}\n\n.form-control-lg {\n padding: $input-btn-padding-y-lg $input-btn-padding-x-lg;\n font-size: $font-size-lg;\n line-height: $input-btn-line-height-lg;\n @include border-radius($input-border-radius-lg);\n}\n\nselect.form-control-lg {\n &:not([size]):not([multiple]) {\n height: $input-height-lg;\n }\n}\n\n\n// Form groups\n//\n// Designed to help with the organization and spacing of vertical forms. For\n// horizontal forms, use the predefined grid classes.\n\n.form-group {\n margin-bottom: $form-group-margin-bottom;\n}\n\n.form-text {\n display: block;\n margin-top: $form-text-margin-top;\n}\n\n\n// Form grid\n//\n// Special replacement for our grid system's `.row` for tighter form layouts.\n\n.form-row {\n display: flex;\n flex-wrap: wrap;\n margin-right: -5px;\n margin-left: -5px;\n\n > .col,\n > [class*=\"col-\"] {\n padding-right: 5px;\n padding-left: 5px;\n }\n}\n\n\n// Checkboxes and radios\n//\n// Indent the labels to position radios/checkboxes as hanging controls.\n\n.form-check {\n position: relative;\n display: block;\n margin-bottom: $form-check-margin-bottom;\n\n &.disabled {\n .form-check-label {\n color: $text-muted;\n }\n }\n}\n\n.form-check-label {\n padding-left: $form-check-input-gutter;\n margin-bottom: 0; // Override default `<label>` bottom margin\n}\n\n.form-check-input {\n position: absolute;\n margin-top: $form-check-input-margin-y;\n margin-left: -$form-check-input-gutter;\n\n &:only-child {\n position: static;\n }\n}\n\n// Radios and checkboxes on same line\n.form-check-inline {\n display: inline-block;\n\n .form-check-label {\n vertical-align: middle;\n }\n\n + .form-check-inline {\n margin-left: $form-check-inline-margin-x;\n }\n}\n\n\n// Form validation\n//\n// Provide feedback to users when form field values are valid or invalid. Works\n// primarily for client-side validation via scoped `:invalid` and `:valid`\n// pseudo-classes but also includes `.is-invalid` and `.is-valid` classes for\n// server side validation.\n\n.invalid-feedback {\n display: none;\n margin-top: .25rem;\n font-size: .875rem;\n color: $form-feedback-invalid-color;\n}\n\n.invalid-tooltip {\n position: absolute;\n top: 100%;\n z-index: 5;\n display: none;\n width: 250px;\n padding: .5rem;\n margin-top: .1rem;\n font-size: .875rem;\n line-height: 1;\n color: #fff;\n background-color: rgba($form-feedback-invalid-color,.8);\n border-radius: .2rem;\n}\n\n@include form-validation-state(\"valid\", $form-feedback-valid-color);\n@include form-validation-state(\"invalid\", $form-feedback-invalid-color);\n\n// Inline forms\n//\n// Make forms appear inline(-block) by adding the `.form-inline` class. Inline\n// forms begin stacked on extra small (mobile) devices and then go inline when\n// viewports reach <768px.\n//\n// Requires wrapping inputs and labels with `.form-group` for proper display of\n// default HTML form controls and our custom form controls (e.g., input groups).\n\n.form-inline {\n display: flex;\n flex-flow: row wrap;\n align-items: center; // Prevent shorter elements from growing to same height as others (e.g., small buttons growing to normal sized button height)\n\n // Because we use flex, the initial sizing of checkboxes is collapsed and\n // doesn't occupy the full-width (which is what we want for xs grid tier),\n // so we force that here.\n .form-check {\n width: 100%;\n }\n\n // Kick in the inline\n @include media-breakpoint-up(sm) {\n label {\n display: flex;\n align-items: center;\n justify-content: center;\n margin-bottom: 0;\n }\n\n // Inline-block all the things for \"inline\"\n .form-group {\n display: flex;\n flex: 0 0 auto;\n flex-flow: row wrap;\n align-items: center;\n margin-bottom: 0;\n }\n\n // Allow folks to *not* use `.form-group`\n .form-control {\n display: inline-block;\n width: auto; // Prevent labels from stacking above inputs in `.form-group`\n vertical-align: middle;\n }\n\n // Make static controls behave like regular ones\n .form-control-plaintext {\n display: inline-block;\n }\n\n .input-group {\n width: auto;\n }\n\n .form-control-label {\n margin-bottom: 0;\n vertical-align: middle;\n }\n\n // Remove default margin on radios/checkboxes that were used for stacking, and\n // then undo the floating of radios and checkboxes to match.\n .form-check {\n display: flex;\n align-items: center;\n justify-content: center;\n width: auto;\n margin-top: 0;\n margin-bottom: 0;\n }\n .form-check-label {\n padding-left: 0;\n }\n .form-check-input {\n position: relative;\n margin-top: 0;\n margin-right: $form-check-input-margin-x;\n margin-left: 0;\n }\n\n // Custom form controls\n .custom-control {\n display: flex;\n align-items: center;\n justify-content: center;\n padding-left: 0;\n }\n .custom-control-indicator {\n position: static;\n display: inline-block;\n margin-right: $form-check-input-margin-x; // Flexbox alignment means we lose our HTML space here, so we compensate.\n vertical-align: text-bottom;\n }\n\n // Re-override the feedback icon.\n .has-feedback .form-control-feedback {\n top: 0;\n }\n }\n}\n","// Form control focus state\n//\n// Generate a customized focus state and for any input with the specified color,\n// which defaults to the `@input-border-color-focus` variable.\n//\n// We highly encourage you to not customize the default value, but instead use\n// this to tweak colors on an as-needed basis. This aesthetic change is based on\n// WebKit's default styles, but applicable to a wider range of browsers. Its\n// usability and accessibility should be taken into account with any change.\n//\n// Example usage: change the default blue border and shadow to white for better\n// contrast against a dark gray background.\n@mixin form-control-focus() {\n &:focus {\n color: $input-focus-color;\n background-color: $input-focus-bg;\n border-color: $input-focus-border-color;\n outline: none;\n @include box-shadow($input-focus-box-shadow);\n }\n}\n\n\n@mixin form-validation-state($state, $color) {\n\n .form-control,\n .custom-select {\n .was-validated &:#{$state},\n &.is-#{$state} {\n border-color: $color;\n\n &:focus {\n box-shadow: 0 0 0 .2rem rgba($color,.25);\n }\n\n ~ .invalid-feedback,\n ~ .invalid-tooltip {\n display: block;\n }\n }\n }\n\n\n // TODO: redo check markup lol crap\n .form-check-input {\n .was-validated &:#{$state},\n &.is-#{$state} {\n + .form-check-label {\n color: $color;\n }\n }\n }\n\n // custom radios and checks\n .custom-control-input {\n .was-validated &:#{$state},\n &.is-#{$state} {\n ~ .custom-control-indicator {\n background-color: rgba($color, .25);\n }\n ~ .custom-control-description {\n color: $color;\n }\n }\n }\n\n // custom file\n .custom-file-input {\n .was-validated &:#{$state},\n &.is-#{$state} {\n ~ .custom-file-control {\n border-color: $color;\n\n &::before { border-color: inherit; }\n }\n &:focus {\n box-shadow: 0 0 0 .2rem rgba($color,.25);\n }\n }\n }\n}\n","// scss-lint:disable QualifyingElement\n\n//\n// Base styles\n//\n\n.btn {\n display: inline-block;\n font-weight: $btn-font-weight;\n text-align: center;\n white-space: nowrap;\n vertical-align: middle;\n user-select: none;\n border: $input-btn-border-width solid transparent;\n @include button-size($input-btn-padding-y, $input-btn-padding-x, $font-size-base, $input-btn-line-height, $btn-border-radius);\n @include transition($btn-transition);\n\n // Share hover and focus styles\n @include hover-focus {\n text-decoration: none;\n }\n &:focus,\n &.focus {\n outline: 0;\n box-shadow: $btn-focus-box-shadow;\n }\n\n // Disabled comes first so active can properly restyle\n &.disabled,\n &:disabled {\n opacity: .65;\n @include box-shadow(none);\n }\n\n &:active,\n &.active {\n background-image: none;\n @include box-shadow($btn-focus-box-shadow, $btn-active-box-shadow);\n }\n}\n\n// Future-proof disabling of clicks on `<a>` elements\na.btn.disabled,\nfieldset[disabled] a.btn {\n pointer-events: none;\n}\n\n\n//\n// Alternate buttons\n//\n\n@each $color, $value in $theme-colors {\n .btn-#{$color} {\n @include button-variant($value, $value);\n }\n}\n\n@each $color, $value in $theme-colors {\n .btn-outline-#{$color} {\n @include button-outline-variant($value, #fff);\n }\n}\n\n\n//\n// Link buttons\n//\n\n// Make a button look and behave like a link\n.btn-link {\n font-weight: $font-weight-normal;\n color: $link-color;\n border-radius: 0;\n\n &,\n &:active,\n &.active,\n &:disabled {\n background-color: transparent;\n @include box-shadow(none);\n }\n &,\n &:focus,\n &:active {\n border-color: transparent;\n box-shadow: none;\n }\n @include hover {\n border-color: transparent;\n }\n @include hover-focus {\n color: $link-hover-color;\n text-decoration: $link-hover-decoration;\n background-color: transparent;\n }\n &:disabled {\n color: $btn-link-disabled-color;\n\n @include hover-focus {\n text-decoration: none;\n }\n }\n}\n\n\n//\n// Button Sizes\n//\n\n.btn-lg {\n @include button-size($input-btn-padding-y-lg, $input-btn-padding-x-lg, $font-size-lg, $line-height-lg, $btn-border-radius-lg);\n}\n\n.btn-sm {\n @include button-size($input-btn-padding-y-sm, $input-btn-padding-x-sm, $font-size-sm, $line-height-sm, $btn-border-radius-sm);\n}\n\n\n//\n// Block button\n//\n\n.btn-block {\n display: block;\n width: 100%;\n}\n\n// Vertically space out multiple block buttons\n.btn-block + .btn-block {\n margin-top: $btn-block-spacing-y;\n}\n\n// Specificity overrides\ninput[type=\"submit\"],\ninput[type=\"reset\"],\ninput[type=\"button\"] {\n &.btn-block {\n width: 100%;\n }\n}\n","// Button variants\n//\n// Easily pump out default styles, as well as :hover, :focus, :active,\n// and disabled options for all buttons\n\n@mixin button-variant($background, $border, $active-background: darken($background, 7.5%), $active-border: darken($border, 10%)) {\n @include color-yiq($background);\n background-color: $background;\n border-color: $border;\n @include box-shadow($btn-box-shadow);\n\n &:hover {\n @include color-yiq($background);\n background-color: $active-background;\n border-color: $active-border;\n }\n\n &:focus,\n &.focus {\n // Avoid using mixin so we can pass custom focus shadow properly\n @if $enable-shadows {\n box-shadow: $btn-box-shadow, 0 0 0 3px rgba($border, .5);\n } @else {\n box-shadow: 0 0 0 3px rgba($border, .5);\n }\n }\n\n // Disabled comes first so active can properly restyle\n &.disabled,\n &:disabled {\n background-color: $background;\n border-color: $border;\n }\n\n &:active,\n &.active,\n .show > &.dropdown-toggle {\n background-color: $active-background;\n background-image: none; // Remove the gradient for the pressed/active state\n border-color: $active-border;\n @include box-shadow($btn-active-box-shadow);\n }\n}\n\n@mixin button-outline-variant($color, $color-hover: #fff) {\n color: $color;\n background-color: transparent;\n background-image: none;\n border-color: $color;\n\n @include hover {\n color: $color-hover;\n background-color: $color;\n border-color: $color;\n }\n\n &:focus,\n &.focus {\n box-shadow: 0 0 0 3px rgba($color, .5);\n }\n\n &.disabled,\n &:disabled {\n color: $color;\n background-color: transparent;\n }\n\n &:active,\n &.active,\n .show > &.dropdown-toggle {\n color: $color-hover;\n background-color: $color;\n border-color: $color;\n }\n}\n\n// Button sizes\n@mixin button-size($padding-y, $padding-x, $font-size, $line-height, $border-radius) {\n padding: $padding-y $padding-x;\n font-size: $font-size;\n line-height: $line-height;\n @include border-radius($border-radius);\n}\n",".fade {\n opacity: 0;\n @include transition($transition-fade);\n\n &.show {\n opacity: 1;\n }\n}\n\n.collapse {\n display: none;\n &.show {\n display: block;\n }\n}\n\ntr {\n &.collapse.show {\n display: table-row;\n }\n}\n\ntbody {\n &.collapse.show {\n display: table-row-group;\n }\n}\n\n.collapsing {\n position: relative;\n height: 0;\n overflow: hidden;\n @include transition($transition-collapse);\n}\n","// The dropdown wrapper (`<div>`)\n.dropup,\n.dropdown {\n position: relative;\n}\n\n.dropdown-toggle {\n // Generate the caret automatically\n &::after {\n display: inline-block;\n width: 0;\n height: 0;\n margin-left: $caret-width * .85;\n vertical-align: $caret-width * .85;\n content: \"\";\n border-top: $caret-width solid;\n border-right: $caret-width solid transparent;\n border-left: $caret-width solid transparent;\n }\n\n &:empty::after {\n margin-left: 0;\n }\n}\n\n// Allow for dropdowns to go bottom up (aka, dropup-menu)\n// Just add .dropup after the standard .dropdown class and you're set.\n.dropup {\n .dropdown-menu {\n margin-top: 0;\n margin-bottom: $dropdown-spacer;\n }\n\n .dropdown-toggle {\n &::after {\n border-top: 0;\n border-bottom: $caret-width solid;\n }\n }\n}\n\n// The dropdown menu\n.dropdown-menu {\n position: absolute;\n top: 100%;\n left: 0;\n z-index: $zindex-dropdown;\n display: none; // none by default, but block on \"open\" of the menu\n float: left;\n min-width: $dropdown-min-width;\n padding: $dropdown-padding-y 0;\n margin: $dropdown-spacer 0 0; // override default ul\n font-size: $font-size-base; // Redeclare because nesting can cause inheritance issues\n color: $body-color;\n text-align: left; // Ensures proper alignment if parent has it changed (e.g., modal footer)\n list-style: none;\n background-color: $dropdown-bg;\n background-clip: padding-box;\n border: $dropdown-border-width solid $dropdown-border-color;\n @include border-radius($border-radius);\n @include box-shadow($dropdown-box-shadow);\n}\n\n// Dividers (basically an `<hr>`) within the dropdown\n.dropdown-divider {\n @include nav-divider($dropdown-divider-bg);\n}\n\n// Links, buttons, and more within the dropdown menu\n//\n// `<button>`-specific styles are denoted with `// For <button>s`\n.dropdown-item {\n display: block;\n width: 100%; // For `<button>`s\n padding: $dropdown-item-padding-y $dropdown-item-padding-x;\n clear: both;\n font-weight: $font-weight-normal;\n color: $dropdown-link-color;\n text-align: inherit; // For `<button>`s\n white-space: nowrap; // prevent links from randomly breaking onto new lines\n background: none; // For `<button>`s\n border: 0; // For `<button>`s\n\n @include hover-focus {\n color: $dropdown-link-hover-color;\n text-decoration: none;\n background-color: $dropdown-link-hover-bg;\n }\n\n &.active,\n &:active {\n color: $dropdown-link-active-color;\n text-decoration: none;\n background-color: $dropdown-link-active-bg;\n }\n\n &.disabled,\n &:disabled {\n color: $dropdown-link-disabled-color;\n background-color: transparent;\n // Remove CSS gradients if they're enabled\n @if $enable-gradients {\n background-image: none;\n }\n }\n}\n\n// Open state for the dropdown\n.show {\n // Remove the outline when :focus is triggered\n > a {\n outline: 0;\n }\n}\n\n.dropdown-menu.show {\n display: block;\n}\n\n// Dropdown section headers\n.dropdown-header {\n display: block;\n padding: $dropdown-padding-y $dropdown-item-padding-x;\n margin-bottom: 0; // for use with heading elements\n font-size: $font-size-sm;\n color: $dropdown-header-color;\n white-space: nowrap; // as with > li > a\n}\n","// Horizontal dividers\n//\n// Dividers (basically an hr) within dropdowns and nav lists\n\n@mixin nav-divider($color: #e5e5e5) {\n height: 0;\n margin: ($spacer / 2) 0;\n overflow: hidden;\n border-top: 1px solid $color;\n}\n","// scss-lint:disable QualifyingElement\n\n// Make the div behave like a button\n.btn-group,\n.btn-group-vertical {\n position: relative;\n display: inline-flex;\n vertical-align: middle; // match .btn alignment given font-size hack above\n\n > .btn {\n position: relative;\n flex: 0 1 auto;\n margin-bottom: 0;\n\n // Bring the hover, focused, and \"active\" buttons to the front to overlay\n // the borders properly\n @include hover {\n z-index: 2;\n }\n &:focus,\n &:active,\n &.active {\n z-index: 2;\n }\n }\n\n // Prevent double borders when buttons are next to each other\n .btn + .btn,\n .btn + .btn-group,\n .btn-group + .btn,\n .btn-group + .btn-group {\n margin-left: -$input-btn-border-width;\n }\n}\n\n// Optional: Group multiple button groups together for a toolbar\n.btn-toolbar {\n display: flex;\n flex-wrap: wrap;\n justify-content: flex-start;\n\n .input-group {\n width: auto;\n }\n}\n\n.btn-group > .btn:not(:first-child):not(:last-child):not(.dropdown-toggle) {\n border-radius: 0;\n}\n\n// Set corners individual because sometimes a single button can be in a .btn-group and we need :first-child and :last-child to both match\n.btn-group > .btn:first-child {\n margin-left: 0;\n\n &:not(:last-child):not(.dropdown-toggle) {\n @include border-right-radius(0);\n }\n}\n// Need .dropdown-toggle since :last-child doesn't apply given a .dropdown-menu immediately after it\n.btn-group > .btn:last-child:not(:first-child),\n.btn-group > .dropdown-toggle:not(:first-child) {\n @include border-left-radius(0);\n}\n\n// Custom edits for including btn-groups within btn-groups (useful for including dropdown buttons within a btn-group)\n.btn-group > .btn-group {\n float: left;\n}\n.btn-group > .btn-group:not(:first-child):not(:last-child) > .btn {\n border-radius: 0;\n}\n.btn-group > .btn-group:first-child:not(:last-child) {\n > .btn:last-child,\n > .dropdown-toggle {\n @include border-right-radius(0);\n }\n}\n.btn-group > .btn-group:last-child:not(:first-child) > .btn:first-child {\n @include border-left-radius(0);\n}\n\n\n// Sizing\n//\n// Remix the default button sizing classes into new ones for easier manipulation.\n\n.btn-group-sm > .btn { @extend .btn-sm; }\n.btn-group-lg > .btn { @extend .btn-lg; }\n\n\n//\n// Split button dropdowns\n//\n\n.btn + .dropdown-toggle-split {\n padding-right: $input-btn-padding-x * .75;\n padding-left: $input-btn-padding-x * .75;\n\n &::after {\n margin-left: 0;\n }\n}\n\n.btn-sm + .dropdown-toggle-split {\n padding-right: $input-btn-padding-x-sm * .75;\n padding-left: $input-btn-padding-x-sm * .75;\n}\n\n.btn-lg + .dropdown-toggle-split {\n padding-right: $input-btn-padding-x-lg * .75;\n padding-left: $input-btn-padding-x-lg * .75;\n}\n\n\n// The clickable button for toggling the menu\n// Set the same inset shadow as the :active state\n.btn-group.show .dropdown-toggle {\n @include box-shadow($btn-active-box-shadow);\n\n // Show no shadow for `.btn-link` since it has no other button styles.\n &.btn-link {\n @include box-shadow(none);\n }\n}\n\n\n//\n// Vertical button groups\n//\n\n.btn-group-vertical {\n display: inline-flex;\n flex-direction: column;\n align-items: flex-start;\n justify-content: center;\n\n .btn,\n .btn-group {\n width: 100%;\n }\n\n > .btn + .btn,\n > .btn + .btn-group,\n > .btn-group + .btn,\n > .btn-group + .btn-group {\n margin-top: -$input-btn-border-width;\n margin-left: 0;\n }\n}\n\n.btn-group-vertical > .btn {\n &:not(:first-child):not(:last-child) {\n border-radius: 0;\n }\n &:first-child:not(:last-child) {\n @include border-bottom-radius(0);\n }\n &:last-child:not(:first-child) {\n @include border-top-radius(0);\n }\n}\n.btn-group-vertical > .btn-group:not(:first-child):not(:last-child) > .btn {\n border-radius: 0;\n}\n.btn-group-vertical > .btn-group:first-child:not(:last-child) {\n > .btn:last-child,\n > .dropdown-toggle {\n @include border-bottom-radius(0);\n }\n}\n.btn-group-vertical > .btn-group:last-child:not(:first-child) > .btn:first-child {\n @include border-top-radius(0);\n}\n\n\n// Checkbox and radio options\n//\n// In order to support the browser's form validation feedback, powered by the\n// `required` attribute, we have to \"hide\" the inputs via `clip`. We cannot use\n// `display: none;` or `visibility: hidden;` as that also hides the popover.\n// Simply visually hiding the inputs via `opacity` would leave them clickable in\n// certain cases which is prevented by using `clip` and `pointer-events`.\n// This way, we ensure a DOM element is visible to position the popover from.\n//\n// See https://github.com/twbs/bootstrap/pull/12794 and\n// https://github.com/twbs/bootstrap/pull/14559 for more information.\n\n[data-toggle=\"buttons\"] {\n > .btn,\n > .btn-group > .btn {\n input[type=\"radio\"],\n input[type=\"checkbox\"] {\n position: absolute;\n clip: rect(0,0,0,0);\n pointer-events: none;\n }\n }\n}\n","//\n// Base styles\n//\n\n.input-group {\n position: relative;\n display: flex;\n width: 100%;\n\n .form-control {\n // Ensure that the input is always above the *appended* addon button for\n // proper border colors.\n position: relative;\n z-index: 2;\n flex: 1 1 auto;\n // Add width 1% and flex-basis auto to ensure that button will not wrap out\n // the column. Applies to IE Edge+ and Firefox. Chrome does not require this.\n width: 1%;\n margin-bottom: 0;\n\n // Bring the \"active\" form control to the front\n @include hover-focus-active {\n z-index: 3;\n }\n }\n}\n\n.input-group-addon,\n.input-group-btn,\n.input-group .form-control {\n // Vertically centers the content of the addons within the input group\n display: flex;\n align-items: center;\n\n &:not(:first-child):not(:last-child) {\n @include border-radius(0);\n }\n}\n\n.input-group-addon,\n.input-group-btn {\n white-space: nowrap;\n vertical-align: middle; // Match the inputs\n}\n\n\n// Sizing options\n//\n// Remix the default form control sizing classes into new ones for easier\n// manipulation.\n\n.input-group-lg > .form-control,\n.input-group-lg > .input-group-addon,\n.input-group-lg > .input-group-btn > .btn {\n @extend .form-control-lg;\n}\n.input-group-sm > .form-control,\n.input-group-sm > .input-group-addon,\n.input-group-sm > .input-group-btn > .btn {\n @extend .form-control-sm;\n}\n\n\n//\n// Text input groups\n//\n\n.input-group-addon {\n padding: $input-btn-padding-y $input-btn-padding-x;\n margin-bottom: 0; // Allow use of <label> elements by overriding our default margin-bottom\n font-size: $font-size-base; // Match inputs\n font-weight: $font-weight-normal;\n line-height: $input-btn-line-height;\n color: $input-color;\n text-align: center;\n background-color: $input-group-addon-bg;\n border: $input-btn-border-width solid $input-group-addon-border-color;\n @include border-radius($input-border-radius);\n\n // Sizing\n &.form-control-sm {\n padding: $input-btn-padding-y-sm $input-btn-padding-x-sm;\n font-size: $font-size-sm;\n @include border-radius($input-border-radius-sm);\n }\n\n &.form-control-lg {\n padding: $input-btn-padding-y-lg $input-btn-padding-x-lg;\n font-size: $font-size-lg;\n @include border-radius($input-border-radius-lg);\n }\n\n // scss-lint:disable QualifyingElement\n // Nuke default margins from checkboxes and radios to vertically center within.\n input[type=\"radio\"],\n input[type=\"checkbox\"] {\n margin-top: 0;\n }\n // scss-lint:enable QualifyingElement\n}\n\n\n//\n// Reset rounded corners\n//\n\n.input-group .form-control:not(:last-child),\n.input-group-addon:not(:last-child),\n.input-group-btn:not(:last-child) > .btn,\n.input-group-btn:not(:last-child) > .btn-group > .btn,\n.input-group-btn:not(:last-child) > .dropdown-toggle,\n.input-group-btn:not(:first-child) > .btn:not(:last-child):not(.dropdown-toggle),\n.input-group-btn:not(:first-child) > .btn-group:not(:last-child) > .btn {\n @include border-right-radius(0);\n}\n.input-group-addon:not(:last-child) {\n border-right: 0;\n}\n.input-group .form-control:not(:first-child),\n.input-group-addon:not(:first-child),\n.input-group-btn:not(:first-child) > .btn,\n.input-group-btn:not(:first-child) > .btn-group > .btn,\n.input-group-btn:not(:first-child) > .dropdown-toggle,\n.input-group-btn:not(:last-child) > .btn:not(:first-child),\n.input-group-btn:not(:last-child) > .btn-group:not(:first-child) > .btn {\n @include border-left-radius(0);\n}\n.form-control + .input-group-addon:not(:first-child) {\n border-left: 0;\n}\n\n//\n// Button input groups\n//\n\n.input-group-btn {\n position: relative;\n // Jankily prevent input button groups from wrapping with `white-space` and\n // `font-size` in combination with `inline-block` on buttons.\n font-size: 0;\n white-space: nowrap;\n\n // Negative margin for spacing, position for bringing hovered/focused/actived\n // element above the siblings.\n > .btn {\n position: relative;\n\n + .btn {\n margin-left: (-$input-btn-border-width);\n }\n\n // Bring the \"active\" button to the front\n @include hover-focus-active {\n z-index: 3;\n }\n }\n\n // Negative margin to only have a single, shared border between the two\n &:not(:last-child) {\n > .btn,\n > .btn-group {\n margin-right: (-$input-btn-border-width);\n }\n }\n &:not(:first-child) {\n > .btn,\n > .btn-group {\n z-index: 2;\n margin-left: (-$input-btn-border-width);\n // Because specificity\n @include hover-focus-active {\n z-index: 3;\n }\n }\n }\n}\n","// scss-lint:disable PropertyCount, VendorPrefix\n\n// Embedded icons from Open Iconic.\n// Released under MIT and copyright 2014 Waybury.\n// https://useiconic.com/open\n\n\n// Checkboxes and radios\n//\n// Base class takes care of all the key behavioral aspects.\n\n.custom-control {\n position: relative;\n display: inline-flex;\n min-height: (1rem * $line-height-base);\n padding-left: $custom-control-gutter;\n margin-right: $custom-control-spacer-x;\n}\n\n.custom-control-input {\n position: absolute;\n z-index: -1; // Put the input behind the label so it doesn't overlay text\n opacity: 0;\n\n &:checked ~ .custom-control-indicator {\n color: $custom-control-indicator-checked-color;\n background-color: $custom-control-indicator-checked-bg;\n @include box-shadow($custom-control-indicator-checked-box-shadow);\n }\n\n &:focus ~ .custom-control-indicator {\n // the mixin is not used here to make sure there is feedback\n box-shadow: $custom-control-indicator-focus-box-shadow;\n }\n\n &:active ~ .custom-control-indicator {\n color: $custom-control-indicator-active-color;\n background-color: $custom-control-indicator-active-bg;\n @include box-shadow($custom-control-indicator-active-box-shadow);\n }\n\n &:disabled {\n ~ .custom-control-indicator {\n background-color: $custom-control-indicator-disabled-bg;\n }\n\n ~ .custom-control-description {\n color: $custom-control-description-disabled-color;\n }\n }\n}\n\n// Custom indicator\n//\n// Generates a shadow element to create our makeshift checkbox/radio background.\n\n.custom-control-indicator {\n position: absolute;\n top: (($line-height-base - $custom-control-indicator-size) / 2);\n left: 0;\n display: block;\n width: $custom-control-indicator-size;\n height: $custom-control-indicator-size;\n pointer-events: none;\n user-select: none;\n background-color: $custom-control-indicator-bg;\n background-repeat: no-repeat;\n background-position: center center;\n background-size: $custom-control-indicator-bg-size;\n @include box-shadow($custom-control-indicator-box-shadow);\n}\n\n// Checkboxes\n//\n// Tweak just a few things for checkboxes.\n\n.custom-checkbox {\n .custom-control-indicator {\n @include border-radius($custom-checkbox-indicator-border-radius);\n }\n\n .custom-control-input:checked ~ .custom-control-indicator {\n background-image: $custom-checkbox-indicator-icon-checked;\n }\n\n .custom-control-input:indeterminate ~ .custom-control-indicator {\n background-color: $custom-checkbox-indicator-indeterminate-bg;\n background-image: $custom-checkbox-indicator-icon-indeterminate;\n @include box-shadow($custom-checkbox-indicator-indeterminate-box-shadow);\n }\n}\n\n// Radios\n//\n// Tweak just a few things for radios.\n\n.custom-radio {\n .custom-control-indicator {\n border-radius: $custom-radio-indicator-border-radius;\n }\n\n .custom-control-input:checked ~ .custom-control-indicator {\n background-image: $custom-radio-indicator-icon-checked;\n }\n}\n\n\n// Layout options\n//\n// By default radios and checkboxes are `inline-block` with no additional spacing\n// set. Use these optional classes to tweak the layout.\n\n.custom-controls-stacked {\n display: flex;\n flex-direction: column;\n\n .custom-control {\n margin-bottom: $custom-control-spacer-y;\n\n + .custom-control {\n margin-left: 0;\n }\n }\n}\n\n\n// Select\n//\n// Replaces the browser default select with a custom one, mostly pulled from\n// http://primercss.io.\n//\n\n.custom-select {\n display: inline-block;\n max-width: 100%;\n height: $input-height;\n padding: $custom-select-padding-y ($custom-select-padding-x + $custom-select-indicator-padding) $custom-select-padding-y $custom-select-padding-x;\n line-height: $custom-select-line-height;\n color: $custom-select-color;\n vertical-align: middle;\n background: $custom-select-bg $custom-select-indicator no-repeat right $custom-select-padding-x center;\n background-size: $custom-select-bg-size;\n border: $custom-select-border-width solid $custom-select-border-color;\n @if $enable-rounded {\n border-radius: $custom-select-border-radius;\n } @else {\n border-radius: 0;\n }\n appearance: none;\n\n &:focus {\n border-color: $custom-select-focus-border-color;\n outline: none;\n @include box-shadow($custom-select-focus-box-shadow);\n\n &::-ms-value {\n // For visual consistency with other platforms/browsers,\n // supress the default white text on blue background highlight given to\n // the selected option text when the (still closed) <select> receives focus\n // in IE and (under certain conditions) Edge.\n // See https://github.com/twbs/bootstrap/issues/19398.\n color: $input-color;\n background-color: $input-bg;\n }\n }\n\n &:disabled {\n color: $custom-select-disabled-color;\n background-color: $custom-select-disabled-bg;\n }\n\n // Hides the default caret in IE11\n &::-ms-expand {\n opacity: 0;\n }\n}\n\n.custom-select-sm {\n height: $custom-select-height-sm;\n padding-top: $custom-select-padding-y;\n padding-bottom: $custom-select-padding-y;\n font-size: $custom-select-font-size-sm;\n}\n\n\n// File\n//\n// Custom file input.\n\n.custom-file {\n position: relative;\n display: inline-block;\n max-width: 100%;\n height: $custom-file-height;\n margin-bottom: 0;\n}\n\n.custom-file-input {\n min-width: $custom-file-width;\n max-width: 100%;\n height: $custom-file-height;\n margin: 0;\n opacity: 0;\n\n &:focus ~ .custom-file-control {\n @include box-shadow($custom-file-focus-box-shadow);\n }\n}\n\n.custom-file-control {\n position: absolute;\n top: 0;\n right: 0;\n left: 0;\n z-index: 5;\n height: $custom-file-height;\n padding: $custom-file-padding-x $custom-file-padding-y;\n line-height: $custom-file-line-height;\n color: $custom-file-color;\n pointer-events: none;\n user-select: none;\n background-color: $custom-file-bg;\n border: $custom-file-border-width solid $custom-file-border-color;\n @include border-radius($custom-file-border-radius);\n @include box-shadow($custom-file-box-shadow);\n\n @each $lang, $text in map-get($custom-file-text, placeholder) {\n &:lang(#{$lang}):empty::after {\n content: $text;\n }\n }\n\n &::before {\n position: absolute;\n top: -$custom-file-border-width;\n right: -$custom-file-border-width;\n bottom: -$custom-file-border-width;\n z-index: 6;\n display: block;\n height: $custom-file-height;\n padding: $custom-file-padding-x $custom-file-padding-y;\n line-height: $custom-file-line-height;\n color: $custom-file-button-color;\n background-color: $custom-file-button-bg;\n border: $custom-file-border-width solid $custom-file-border-color;\n @include border-radius(0 $custom-file-border-radius $custom-file-border-radius 0);\n }\n\n @each $lang, $text in map-get($custom-file-text, button-label) {\n &:lang(#{$lang})::before {\n content: $text;\n }\n }\n}\n","// Base class\n//\n// Kickstart any navigation component with a set of style resets. Works with\n// `<nav>`s or `<ul>`s.\n\n.nav {\n display: flex;\n flex-wrap: wrap;\n padding-left: 0;\n margin-bottom: 0;\n list-style: none;\n}\n\n.nav-link {\n display: block;\n padding: $nav-link-padding-y $nav-link-padding-x;\n\n @include hover-focus {\n text-decoration: none;\n }\n\n // Disabled state lightens text\n &.disabled {\n color: $nav-link-disabled-color;\n }\n}\n\n//\n// Tabs\n//\n\n.nav-tabs {\n border-bottom: $nav-tabs-border-width solid $nav-tabs-border-color;\n\n .nav-item {\n margin-bottom: -$nav-tabs-border-width;\n }\n\n .nav-link {\n border: $nav-tabs-border-width solid transparent;\n @include border-top-radius($nav-tabs-border-radius);\n\n @include hover-focus {\n border-color: $nav-tabs-link-hover-border-color $nav-tabs-link-hover-border-color $nav-tabs-border-color;\n }\n\n &.disabled {\n color: $nav-link-disabled-color;\n background-color: transparent;\n border-color: transparent;\n }\n }\n\n .nav-link.active,\n .nav-item.show .nav-link {\n color: $nav-tabs-link-active-color;\n background-color: $nav-tabs-link-active-bg;\n border-color: $nav-tabs-link-active-border-color $nav-tabs-link-active-border-color $nav-tabs-link-active-bg;\n }\n\n .dropdown-menu {\n // Make dropdown border overlap tab border\n margin-top: -$nav-tabs-border-width;\n // Remove the top rounded corners here since there is a hard edge above the menu\n @include border-top-radius(0);\n }\n}\n\n\n//\n// Pills\n//\n\n.nav-pills {\n .nav-link {\n @include border-radius($nav-pills-border-radius);\n\n &.active,\n .show > & {\n color: $nav-pills-link-active-color;\n background-color: $nav-pills-link-active-bg;\n }\n }\n}\n\n\n//\n// Justified variants\n//\n\n.nav-fill {\n .nav-item {\n flex: 1 1 auto;\n text-align: center;\n }\n}\n\n.nav-justified {\n .nav-item {\n flex-basis: 0;\n flex-grow: 1;\n text-align: center;\n }\n}\n\n\n// Tabbable tabs\n//\n// Hide tabbable panes to start, show them when `.active`\n\n.tab-content {\n > .tab-pane {\n display: none;\n }\n > .active {\n display: block;\n }\n}\n","// Contents\n//\n// Navbar\n// Navbar brand\n// Navbar nav\n// Navbar text\n// Navbar divider\n// Responsive navbar\n// Navbar position\n// Navbar themes\n\n\n// Navbar\n//\n// Provide a static navbar from which we expand to create full-width, fixed, and\n// other navbar variations.\n\n.navbar {\n position: relative;\n display: flex;\n flex-wrap: wrap; // allow us to do the line break for collapsing content\n align-items: center;\n justify-content: space-between; // space out brand from logo\n padding: $navbar-padding-y $navbar-padding-x;\n\n // Because flex properties aren't inherited, we need to redeclare these first\n // few properities so that content nested within behave properly.\n > .container,\n > .container-fluid {\n display: flex;\n flex-wrap: wrap;\n align-items: center;\n justify-content: space-between;\n }\n}\n\n\n// Navbar brand\n//\n// Used for brand, project, or site names.\n\n.navbar-brand {\n display: inline-block;\n padding-top: $navbar-brand-padding-y;\n padding-bottom: $navbar-brand-padding-y;\n margin-right: $navbar-padding-x;\n font-size: $navbar-brand-font-size;\n line-height: inherit;\n white-space: nowrap;\n\n @include hover-focus {\n text-decoration: none;\n }\n}\n\n\n// Navbar nav\n//\n// Custom navbar navigation (doesn't require `.nav`, but does make use of `.nav-link`).\n\n.navbar-nav {\n display: flex;\n flex-direction: column; // cannot use `inherit` to get the `.navbar`s value\n padding-left: 0;\n margin-bottom: 0;\n list-style: none;\n\n .nav-link {\n padding-right: 0;\n padding-left: 0;\n }\n\n .dropdown-menu {\n position: static;\n float: none;\n }\n}\n\n\n// Navbar text\n//\n//\n\n.navbar-text {\n display: inline-block;\n padding-top: $nav-link-padding-y;\n padding-bottom: $nav-link-padding-y;\n}\n\n\n// Responsive navbar\n//\n// Custom styles for responsive collapsing and toggling of navbar contents.\n// Powered by the collapse Bootstrap JavaScript plugin.\n\n// When collapsed, prevent the toggleable navbar contents from appearing in\n// the default flexbox row orienation. Requires the use of `flex-wrap: wrap`\n// on the `.navbar` parent.\n.navbar-collapse {\n flex-basis: 100%;\n // For always expanded or extra full navbars, ensure content aligns itself\n // properly vertically. Can be easily overridden with flex utilities.\n align-items: center;\n}\n\n// Button for toggling the navbar when in its collapsed state\n.navbar-toggler {\n padding: $navbar-toggler-padding-y $navbar-toggler-padding-x;\n font-size: $navbar-toggler-font-size;\n line-height: 1;\n background: transparent; // remove default button style\n border: $border-width solid transparent; // remove default button style\n @include border-radius($navbar-toggler-border-radius);\n\n @include hover-focus {\n text-decoration: none;\n }\n}\n\n// Keep as a separate element so folks can easily override it with another icon\n// or image file as needed.\n.navbar-toggler-icon {\n display: inline-block;\n width: 1.5em;\n height: 1.5em;\n vertical-align: middle;\n content: \"\";\n background: no-repeat center center;\n background-size: 100% 100%;\n}\n\n// Generate series of `.navbar-expand-*` responsive classes for configuring\n// where your navbar collapses.\n.navbar-expand {\n @each $breakpoint in map-keys($grid-breakpoints) {\n $next: breakpoint-next($breakpoint, $grid-breakpoints);\n $infix: breakpoint-infix($next, $grid-breakpoints);\n\n &#{$infix} {\n @include media-breakpoint-down($breakpoint) {\n > .container,\n > .container-fluid {\n padding-right: 0;\n padding-left: 0;\n }\n }\n\n @include media-breakpoint-up($next) {\n flex-direction: row;\n flex-wrap: nowrap;\n justify-content: flex-start;\n\n .navbar-nav {\n flex-direction: row;\n\n .dropdown-menu {\n position: absolute;\n }\n\n .dropdown-menu-right {\n right: 0;\n left: auto; // Reset the default from `.dropdown-menu`\n }\n\n .nav-link {\n padding-right: .5rem;\n padding-left: .5rem;\n }\n }\n\n // For nesting containers, have to redeclare for alignment purposes\n > .container,\n > .container-fluid {\n flex-wrap: nowrap;\n }\n\n // scss-lint:disable ImportantRule\n .navbar-collapse {\n display: flex !important;\n }\n // scss-lint:enable ImportantRule\n\n .navbar-toggler {\n display: none;\n }\n }\n }\n }\n}\n\n\n// Navbar themes\n//\n// Styles for switching between navbars with light or dark background.\n\n// Dark links against a light background\n.navbar-light {\n .navbar-brand {\n color: $navbar-light-active-color;\n\n @include hover-focus {\n color: $navbar-light-active-color;\n }\n }\n\n .navbar-nav {\n .nav-link {\n color: $navbar-light-color;\n\n @include hover-focus {\n color: $navbar-light-hover-color;\n }\n\n &.disabled {\n color: $navbar-light-disabled-color;\n }\n }\n\n .show > .nav-link,\n .active > .nav-link,\n .nav-link.show,\n .nav-link.active {\n color: $navbar-light-active-color;\n }\n }\n\n .navbar-toggler {\n color: $navbar-light-color;\n border-color: $navbar-light-toggler-border-color;\n }\n\n .navbar-toggler-icon {\n background-image: $navbar-light-toggler-icon-bg;\n }\n\n .navbar-text {\n color: $navbar-light-color;\n }\n}\n\n// White links against a dark background\n.navbar-dark {\n .navbar-brand {\n color: $navbar-dark-active-color;\n\n @include hover-focus {\n color: $navbar-dark-active-color;\n }\n }\n\n .navbar-nav {\n .nav-link {\n color: $navbar-dark-color;\n\n @include hover-focus {\n color: $navbar-dark-hover-color;\n }\n\n &.disabled {\n color: $navbar-dark-disabled-color;\n }\n }\n\n .show > .nav-link,\n .active > .nav-link,\n .nav-link.show,\n .nav-link.active {\n color: $navbar-dark-active-color;\n }\n }\n\n .navbar-toggler {\n color: $navbar-dark-color;\n border-color: $navbar-dark-toggler-border-color;\n }\n\n .navbar-toggler-icon {\n background-image: $navbar-dark-toggler-icon-bg;\n }\n\n .navbar-text {\n color: $navbar-dark-color;\n }\n}\n","//\n// Base styles\n//\n\n.card {\n position: relative;\n display: flex;\n flex-direction: column;\n min-width: 0;\n word-wrap: break-word;\n background-color: $card-bg;\n background-clip: border-box;\n border: $card-border-width solid $card-border-color;\n @include border-radius($card-border-radius);\n}\n\n.card-body {\n // Enable `flex-grow: 1` for decks and groups so that card blocks take up\n // as much space as possible, ensuring footers are aligned to the bottom.\n flex: 1 1 auto;\n padding: $card-spacer-x;\n}\n\n.card-title {\n margin-bottom: $card-spacer-y;\n}\n\n.card-subtitle {\n margin-top: -($card-spacer-y / 2);\n margin-bottom: 0;\n}\n\n.card-text:last-child {\n margin-bottom: 0;\n}\n\n.card-link {\n @include hover {\n text-decoration: none;\n }\n\n + .card-link {\n margin-left: $card-spacer-x;\n }\n}\n\n.card {\n > .list-group:first-child {\n .list-group-item:first-child {\n @include border-top-radius($card-border-radius);\n }\n }\n\n > .list-group:last-child {\n .list-group-item:last-child {\n @include border-bottom-radius($card-border-radius);\n }\n }\n}\n\n\n//\n// Optional textual caps\n//\n\n.card-header {\n padding: $card-spacer-y $card-spacer-x;\n margin-bottom: 0; // Removes the default margin-bottom of <hN>\n background-color: $card-cap-bg;\n border-bottom: $card-border-width solid $card-border-color;\n\n &:first-child {\n @include border-radius($card-inner-border-radius $card-inner-border-radius 0 0);\n }\n}\n\n.card-footer {\n padding: $card-spacer-y $card-spacer-x;\n background-color: $card-cap-bg;\n border-top: $card-border-width solid $card-border-color;\n\n &:last-child {\n @include border-radius(0 0 $card-inner-border-radius $card-inner-border-radius);\n }\n}\n\n\n//\n// Header navs\n//\n\n.card-header-tabs {\n margin-right: -($card-spacer-x / 2);\n margin-bottom: -$card-spacer-y;\n margin-left: -($card-spacer-x / 2);\n border-bottom: 0;\n}\n\n.card-header-pills {\n margin-right: -($card-spacer-x / 2);\n margin-left: -($card-spacer-x / 2);\n}\n\n// Card image\n.card-img-overlay {\n position: absolute;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n padding: $card-img-overlay-padding;\n}\n\n.card-img {\n width: 100%; // Required because we use flexbox and this inherently applies align-self: stretch\n @include border-radius($card-inner-border-radius);\n}\n\n// Card image caps\n.card-img-top {\n width: 100%; // Required because we use flexbox and this inherently applies align-self: stretch\n @include border-top-radius($card-inner-border-radius);\n}\n\n.card-img-bottom {\n width: 100%; // Required because we use flexbox and this inherently applies align-self: stretch\n @include border-bottom-radius($card-inner-border-radius);\n}\n\n\n// Card deck\n\n@include media-breakpoint-up(sm) {\n .card-deck {\n display: flex;\n flex-flow: row wrap;\n margin-right: -$card-deck-margin;\n margin-left: -$card-deck-margin;\n\n .card {\n display: flex;\n flex: 1 0 0%;\n flex-direction: column;\n margin-right: $card-deck-margin;\n margin-left: $card-deck-margin;\n }\n }\n}\n\n\n//\n// Card groups\n//\n\n@include media-breakpoint-up(sm) {\n .card-group {\n display: flex;\n flex-flow: row wrap;\n\n .card {\n flex: 1 0 0%;\n\n + .card {\n margin-left: 0;\n border-left: 0;\n }\n\n // Handle rounded corners\n @if $enable-rounded {\n &:first-child {\n @include border-right-radius(0);\n\n .card-img-top {\n border-top-right-radius: 0;\n }\n .card-img-bottom {\n border-bottom-right-radius: 0;\n }\n }\n &:last-child {\n @include border-left-radius(0);\n\n .card-img-top {\n border-top-left-radius: 0;\n }\n .card-img-bottom {\n border-bottom-left-radius: 0;\n }\n }\n\n &:not(:first-child):not(:last-child) {\n border-radius: 0;\n\n .card-img-top,\n .card-img-bottom {\n border-radius: 0;\n }\n }\n }\n }\n }\n}\n\n\n//\n// Columns\n//\n\n.card-columns {\n .card {\n margin-bottom: $card-columns-margin;\n }\n\n @include media-breakpoint-up(sm) {\n column-count: $card-columns-count;\n column-gap: $card-columns-gap;\n\n .card {\n display: inline-block; // Don't let them vertically span multiple columns\n width: 100%; // Don't let their width change\n }\n }\n}\n",".breadcrumb {\n padding: $breadcrumb-padding-y $breadcrumb-padding-x;\n margin-bottom: 1rem;\n list-style: none;\n background-color: $breadcrumb-bg;\n @include border-radius($border-radius);\n @include clearfix;\n}\n\n.breadcrumb-item {\n float: left;\n\n // The separator between breadcrumbs (by default, a forward-slash: \"/\")\n + .breadcrumb-item::before {\n display: inline-block; // Suppress underlining of the separator in modern browsers\n padding-right: $breadcrumb-item-padding;\n padding-left: $breadcrumb-item-padding;\n color: $breadcrumb-divider-color;\n content: \"#{$breadcrumb-divider}\";\n }\n\n // IE9-11 hack to properly handle hyperlink underlines for breadcrumbs built\n // without `<ul>`s. The `::before` pseudo-element generates an element\n // *within* the .breadcrumb-item and thereby inherits the `text-decoration`.\n //\n // To trick IE into suppressing the underline, we give the pseudo-element an\n // underline and then immediately remove it.\n + .breadcrumb-item:hover::before {\n text-decoration: underline;\n }\n + .breadcrumb-item:hover::before {\n text-decoration: none;\n }\n\n &.active {\n color: $breadcrumb-active-color;\n }\n}\n","@mixin clearfix() {\n &::after {\n display: block;\n clear: both;\n content: \"\";\n }\n}\n",".pagination {\n display: flex;\n // 1-2: Disable browser default list styles\n padding-left: 0; // 1\n list-style: none; // 2\n @include border-radius();\n}\n\n.page-item {\n &:first-child {\n .page-link {\n margin-left: 0;\n @include border-left-radius($border-radius);\n }\n }\n &:last-child {\n .page-link {\n @include border-right-radius($border-radius);\n }\n }\n\n &.active .page-link {\n z-index: 2;\n color: $pagination-active-color;\n background-color: $pagination-active-bg;\n border-color: $pagination-active-border-color;\n }\n\n &.disabled .page-link {\n color: $pagination-disabled-color;\n pointer-events: none;\n background-color: $pagination-disabled-bg;\n border-color: $pagination-disabled-border-color;\n }\n}\n\n.page-link {\n position: relative;\n display: block;\n padding: $pagination-padding-y $pagination-padding-x;\n margin-left: -1px;\n line-height: $pagination-line-height;\n color: $pagination-color;\n background-color: $pagination-bg;\n border: $pagination-border-width solid $pagination-border-color;\n\n @include hover-focus {\n color: $pagination-hover-color;\n text-decoration: none;\n background-color: $pagination-hover-bg;\n border-color: $pagination-hover-border-color;\n }\n}\n\n\n//\n// Sizing\n//\n\n.pagination-lg {\n @include pagination-size($pagination-padding-y-lg, $pagination-padding-x-lg, $font-size-lg, $line-height-lg, $border-radius-lg);\n}\n\n.pagination-sm {\n @include pagination-size($pagination-padding-y-sm, $pagination-padding-x-sm, $font-size-sm, $line-height-sm, $border-radius-sm);\n}\n","// Pagination\n\n@mixin pagination-size($padding-y, $padding-x, $font-size, $line-height, $border-radius) {\n .page-link {\n padding: $padding-y $padding-x;\n font-size: $font-size;\n line-height: $line-height;\n }\n\n .page-item {\n &:first-child {\n .page-link {\n @include border-left-radius($border-radius);\n }\n }\n &:last-child {\n .page-link {\n @include border-right-radius($border-radius);\n }\n }\n }\n}\n","// Base class\n//\n// Requires one of the contextual, color modifier classes for `color` and\n// `background-color`.\n\n.badge {\n display: inline-block;\n padding: $badge-padding-y $badge-padding-x;\n font-size: $badge-font-size;\n font-weight: $badge-font-weight;\n line-height: 1;\n color: $badge-color;\n text-align: center;\n white-space: nowrap;\n vertical-align: baseline;\n @include border-radius();\n\n // Empty badges collapse automatically\n &:empty {\n display: none;\n }\n}\n\n// Quick fix for badges in buttons\n.btn .badge {\n position: relative;\n top: -1px;\n}\n\n// Pill badges\n//\n// Make them extra rounded with a modifier to replace v3's badges.\n\n.badge-pill {\n padding-right: $badge-pill-padding-x;\n padding-left: $badge-pill-padding-x;\n @include border-radius($badge-pill-border-radius);\n}\n\n// Colors\n//\n// Contextual variations (linked badges get darker on :hover).\n\n@each $color, $value in $theme-colors {\n .badge-#{$color} {\n @include badge-variant($value);\n }\n}\n","@mixin badge-variant($bg) {\n @include color-yiq($bg);\n background-color: $bg;\n\n &[href] {\n @include hover-focus {\n @include color-yiq($bg);\n text-decoration: none;\n background-color: darken($bg, 10%);\n }\n }\n}\n",".jumbotron {\n padding: $jumbotron-padding ($jumbotron-padding / 2);\n margin-bottom: $jumbotron-padding;\n background-color: $jumbotron-bg;\n @include border-radius($border-radius-lg);\n\n @include media-breakpoint-up(sm) {\n padding: ($jumbotron-padding * 2) $jumbotron-padding;\n }\n}\n\n.jumbotron-fluid {\n padding-right: 0;\n padding-left: 0;\n @include border-radius(0);\n}\n","//\n// Base styles\n//\n\n.alert {\n padding: $alert-padding-y $alert-padding-x;\n margin-bottom: $alert-margin-bottom;\n border: $alert-border-width solid transparent;\n @include border-radius($alert-border-radius);\n}\n\n// Headings for larger alerts\n.alert-heading {\n // Specified to prevent conflicts of changing $headings-color\n color: inherit;\n}\n\n// Provide class for links that match alerts\n.alert-link {\n font-weight: $alert-link-font-weight;\n}\n\n\n// Dismissible alerts\n//\n// Expand the right padding and account for the close button's positioning.\n\n.alert-dismissible {\n // Adjust close link position\n .close {\n position: relative;\n top: -$alert-padding-y;\n right: -$alert-padding-x;\n padding: $alert-padding-y $alert-padding-x;\n color: inherit;\n }\n}\n\n\n// Alternate styles\n//\n// Generate contextual modifier classes for colorizing the alert.\n\n@each $color, $value in $theme-colors {\n .alert-#{$color} {\n @include alert-variant(theme-color-level($color, -10), theme-color-level($color, -9), theme-color-level($color, 6));\n }\n}\n","@mixin alert-variant($background, $border, $color) {\n color: $color;\n background-color: $background;\n border-color: $border;\n\n hr {\n border-top-color: darken($border, 5%);\n }\n\n .alert-link {\n color: darken($color, 10%);\n }\n}\n","@keyframes progress-bar-stripes {\n from { background-position: $progress-height 0; }\n to { background-position: 0 0; }\n}\n\n.progress {\n display: flex;\n overflow: hidden; // force rounded corners by cropping it\n font-size: $progress-font-size;\n line-height: $progress-height;\n text-align: center;\n background-color: $progress-bg;\n @include border-radius($progress-border-radius);\n @include box-shadow($progress-box-shadow);\n}\n\n.progress-bar {\n height: $progress-height;\n line-height: $progress-height;\n color: $progress-bar-color;\n background-color: $progress-bar-bg;\n @include transition($progress-bar-transition);\n}\n\n.progress-bar-striped {\n @include gradient-striped();\n background-size: $progress-height $progress-height;\n}\n\n.progress-bar-animated {\n animation: progress-bar-stripes $progress-bar-animation-timing;\n}\n","// Gradients\n\n// Horizontal gradient, from left to right\n//\n// Creates two color stops, start and end, by specifying a color and position for each color stop.\n@mixin gradient-x($start-color: #555, $end-color: #333, $start-percent: 0%, $end-percent: 100%) {\n background-image: linear-gradient(to right, $start-color $start-percent, $end-color $end-percent);\n background-repeat: repeat-x;\n}\n\n// Vertical gradient, from top to bottom\n//\n// Creates two color stops, start and end, by specifying a color and position for each color stop.\n@mixin gradient-y($start-color: #555, $end-color: #333, $start-percent: 0%, $end-percent: 100%) {\n background-image: linear-gradient(to bottom, $start-color $start-percent, $end-color $end-percent);\n background-repeat: repeat-x;\n}\n\n@mixin gradient-directional($start-color: #555, $end-color: #333, $deg: 45deg) {\n background-image: linear-gradient($deg, $start-color, $end-color);\n background-repeat: repeat-x;\n}\n@mixin gradient-x-three-colors($start-color: #00b3ee, $mid-color: #7a43b6, $color-stop: 50%, $end-color: #c3325f) {\n background-image: linear-gradient(to right, $start-color, $mid-color $color-stop, $end-color);\n background-repeat: no-repeat;\n}\n@mixin gradient-y-three-colors($start-color: #00b3ee, $mid-color: #7a43b6, $color-stop: 50%, $end-color: #c3325f) {\n background-image: linear-gradient($start-color, $mid-color $color-stop, $end-color);\n background-repeat: no-repeat;\n}\n@mixin gradient-radial($inner-color: #555, $outer-color: #333) {\n background-image: radial-gradient(circle, $inner-color, $outer-color);\n background-repeat: no-repeat;\n}\n@mixin gradient-striped($color: rgba(255,255,255,.15), $angle: 45deg) {\n background-image: linear-gradient($angle, $color 25%, transparent 25%, transparent 50%, $color 50%, $color 75%, transparent 75%, transparent);\n}\n",".media {\n display: flex;\n align-items: flex-start;\n}\n\n.media-body {\n flex: 1;\n}\n","// Base class\n//\n// Easily usable on <ul>, <ol>, or <div>.\n\n.list-group {\n display: flex;\n flex-direction: column;\n\n // No need to set list-style: none; since .list-group-item is block level\n padding-left: 0; // reset padding because ul and ol\n margin-bottom: 0;\n}\n\n\n// Interactive list items\n//\n// Use anchor or button elements instead of `li`s or `div`s to create interactive\n// list items. Includes an extra `.active` modifier class for selected items.\n\n.list-group-item-action {\n width: 100%; // For `<button>`s (anchors become 100% by default though)\n color: $list-group-action-color;\n text-align: inherit; // For `<button>`s (anchors inherit)\n\n // Hover state\n @include hover-focus {\n color: $list-group-action-hover-color;\n text-decoration: none;\n background-color: $list-group-hover-bg;\n }\n\n &:active {\n color: $list-group-action-active-color;\n background-color: $list-group-action-active-bg;\n }\n}\n\n\n// Individual list items\n//\n// Use on `li`s or `div`s within the `.list-group` parent.\n\n.list-group-item {\n position: relative;\n display: block;\n padding: $list-group-item-padding-y $list-group-item-padding-x;\n // Place the border on the list items and negative margin up for better styling\n margin-bottom: -$list-group-border-width;\n background-color: $list-group-bg;\n border: $list-group-border-width solid $list-group-border-color;\n\n &:first-child {\n @include border-top-radius($list-group-border-radius);\n }\n\n &:last-child {\n margin-bottom: 0;\n @include border-bottom-radius($list-group-border-radius);\n }\n\n @include hover-focus {\n text-decoration: none;\n }\n\n &.disabled,\n &:disabled {\n color: $list-group-disabled-color;\n background-color: $list-group-disabled-bg;\n }\n\n // Include both here for `<a>`s and `<button>`s\n &.active {\n z-index: 2; // Place active items above their siblings for proper border styling\n color: $list-group-active-color;\n background-color: $list-group-active-bg;\n border-color: $list-group-active-border-color;\n }\n}\n\n\n// Flush list items\n//\n// Remove borders and border-radius to keep list group items edge-to-edge. Most\n// useful within other components (e.g., cards).\n\n.list-group-flush {\n .list-group-item {\n border-right: 0;\n border-left: 0;\n border-radius: 0;\n }\n\n &:first-child {\n .list-group-item:first-child {\n border-top: 0;\n }\n }\n\n &:last-child {\n .list-group-item:last-child {\n border-bottom: 0;\n }\n }\n}\n\n\n// Contextual variants\n//\n// Add modifier classes to change text and background color on individual items.\n// Organizationally, this must come after the `:hover` states.\n\n@each $color, $value in $theme-colors {\n @include list-group-item-variant($color, theme-color-level($color, -9), theme-color-level($color, 6));\n}\n","// List Groups\n\n@mixin list-group-item-variant($state, $background, $color) {\n .list-group-item-#{$state} {\n color: $color;\n background-color: $background;\n }\n\n //scss-lint:disable QualifyingElement\n a.list-group-item-#{$state},\n button.list-group-item-#{$state} {\n color: $color;\n\n @include hover-focus {\n color: $color;\n background-color: darken($background, 5%);\n }\n\n &.active {\n color: #fff;\n background-color: $color;\n border-color: $color;\n }\n }\n // scss-lint:enable QualifyingElement\n}\n",".close {\n float: right;\n font-size: $close-font-size;\n font-weight: $close-font-weight;\n line-height: 1;\n color: $close-color;\n text-shadow: $close-text-shadow;\n opacity: .5;\n\n @include hover-focus {\n color: $close-color;\n text-decoration: none;\n opacity: .75;\n }\n}\n\n// Additional properties for button version\n// iOS requires the button element instead of an anchor tag.\n// If you want the anchor version, it requires `href=\"#\"`.\n// See https://developer.mozilla.org/en-US/docs/Web/Events/click#Safari_Mobile\n\n// scss-lint:disable QualifyingElement\nbutton.close {\n padding: 0;\n background: transparent;\n border: 0;\n -webkit-appearance: none;\n}\n// scss-lint:enable QualifyingElement\n","// .modal-open - body class for killing the scroll\n// .modal - container to scroll within\n// .modal-dialog - positioning shell for the actual modal\n// .modal-content - actual modal w/ bg and corners and stuff\n\n\n// Kill the scroll on the body\n.modal-open {\n overflow: hidden;\n}\n\n// Container that the modal scrolls within\n.modal {\n position: fixed;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: $zindex-modal;\n display: none;\n overflow: hidden;\n // Prevent Chrome on Windows from adding a focus outline. For details, see\n // https://github.com/twbs/bootstrap/pull/10951.\n outline: 0;\n // We deliberately don't use `-webkit-overflow-scrolling: touch;` due to a\n // gnarly iOS Safari bug: https://bugs.webkit.org/show_bug.cgi?id=158342\n // See also https://github.com/twbs/bootstrap/issues/17695\n\n // When fading in the modal, animate it to slide down\n &.fade .modal-dialog {\n @include transition($modal-transition);\n transform: translate(0, -25%);\n }\n &.show .modal-dialog { transform: translate(0, 0); }\n}\n.modal-open .modal {\n overflow-x: hidden;\n overflow-y: auto;\n}\n\n// Shell div to position the modal with bottom padding\n.modal-dialog {\n position: relative;\n width: auto;\n margin: $modal-dialog-margin;\n}\n\n// Actual modal\n.modal-content {\n position: relative;\n display: flex;\n flex-direction: column;\n background-color: $modal-content-bg;\n background-clip: padding-box;\n border: $modal-content-border-width solid $modal-content-border-color;\n @include border-radius($border-radius-lg);\n @include box-shadow($modal-content-box-shadow-xs);\n // Remove focus outline from opened modal\n outline: 0;\n}\n\n// Modal background\n.modal-backdrop {\n position: fixed;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: $zindex-modal-backdrop;\n background-color: $modal-backdrop-bg;\n\n // Fade for backdrop\n &.fade { opacity: 0; }\n &.show { opacity: $modal-backdrop-opacity; }\n}\n\n// Modal header\n// Top section of the modal w/ title and dismiss\n.modal-header {\n display: flex;\n align-items: center; // vertically center it\n justify-content: space-between; // Put modal header elements (title and dismiss) on opposite ends\n padding: $modal-header-padding;\n border-bottom: $modal-header-border-width solid $modal-header-border-color;\n}\n\n// Title text within header\n.modal-title {\n margin-bottom: 0;\n line-height: $modal-title-line-height;\n}\n\n// Modal body\n// Where all modal content resides (sibling of .modal-header and .modal-footer)\n.modal-body {\n position: relative;\n // Enable `flex-grow: 1` so that the body take up as much space as possible\n // when should there be a fixed height on `.modal-dialog`.\n flex: 1 1 auto;\n padding: $modal-inner-padding;\n}\n\n// Footer (for actions)\n.modal-footer {\n display: flex;\n align-items: center; // vertically center\n justify-content: flex-end; // Right align buttons with flex property because text-align doesn't work on flex items\n padding: $modal-inner-padding;\n border-top: $modal-footer-border-width solid $modal-footer-border-color;\n\n // Easily place margin between footer elements\n > :not(:first-child) { margin-left: .25rem; }\n > :not(:last-child) { margin-right: .25rem; }\n}\n\n// Measure scrollbar width for padding body during modal show/hide\n.modal-scrollbar-measure {\n position: absolute;\n top: -9999px;\n width: 50px;\n height: 50px;\n overflow: scroll;\n}\n\n// Scale up the modal\n@include media-breakpoint-up(sm) {\n // Automatically set modal's width for larger viewports\n .modal-dialog {\n max-width: $modal-md;\n margin: $modal-dialog-margin-y-sm-up auto;\n }\n\n .modal-content {\n @include box-shadow($modal-content-box-shadow-sm-up);\n }\n\n .modal-sm { max-width: $modal-sm; }\n}\n\n@include media-breakpoint-up(lg) {\n .modal-lg { max-width: $modal-lg; }\n}\n","// Base class\n.tooltip {\n position: absolute;\n z-index: $zindex-tooltip;\n display: block;\n margin: $tooltip-margin;\n // Our parent element can be arbitrary since tooltips are by default inserted as a sibling of their target element.\n // So reset our font and text properties to avoid inheriting weird values.\n @include reset-text();\n font-size: $font-size-sm;\n // Allow breaking very long words so they don't overflow the tooltip's bounds\n word-wrap: break-word;\n opacity: 0;\n\n &.show { opacity: $tooltip-opacity; }\n\n .arrow {\n position: absolute;\n display: block;\n width: $tooltip-arrow-width;\n height: $tooltip-arrow-height;\n }\n\n &.bs-tooltip-top {\n padding: $tooltip-arrow-width 0;\n .arrow {\n bottom: 0;\n }\n\n .arrow::before {\n margin-left: -($tooltip-arrow-width - 2);\n content: \"\";\n border-width: $tooltip-arrow-width $tooltip-arrow-width 0;\n border-top-color: $tooltip-arrow-color;\n }\n }\n &.bs-tooltip-right {\n padding: 0 $tooltip-arrow-width;\n .arrow {\n left: 0;\n }\n\n .arrow::before {\n margin-top: -($tooltip-arrow-width - 2);\n content: \"\";\n border-width: $tooltip-arrow-width $tooltip-arrow-width $tooltip-arrow-width 0;\n border-right-color: $tooltip-arrow-color;\n }\n }\n &.bs-tooltip-bottom {\n padding: $tooltip-arrow-width 0;\n .arrow {\n top: 0;\n }\n\n .arrow::before {\n margin-left: -($tooltip-arrow-width - 2);\n content: \"\";\n border-width: 0 $tooltip-arrow-width $tooltip-arrow-width;\n border-bottom-color: $tooltip-arrow-color;\n }\n }\n &.bs-tooltip-left {\n padding: 0 $tooltip-arrow-width;\n .arrow {\n right: 0;\n }\n\n .arrow::before {\n right: 0;\n margin-top: -($tooltip-arrow-width - 2);\n content: \"\";\n border-width: $tooltip-arrow-width 0 $tooltip-arrow-width $tooltip-arrow-width;\n border-left-color: $tooltip-arrow-color;\n }\n }\n &.bs-tooltip-auto {\n &[x-placement^=\"top\"] {\n @extend .bs-tooltip-top;\n }\n &[x-placement^=\"right\"] {\n @extend .bs-tooltip-right;\n }\n &[x-placement^=\"bottom\"] {\n @extend .bs-tooltip-bottom;\n }\n &[x-placement^=\"left\"] {\n @extend .bs-tooltip-left;\n }\n }\n\n .arrow::before {\n position: absolute;\n border-color: transparent;\n border-style: solid;\n }\n}\n\n// Wrapper for the tooltip content\n.tooltip-inner {\n max-width: $tooltip-max-width;\n padding: $tooltip-padding-y $tooltip-padding-x;\n color: $tooltip-color;\n text-align: center;\n background-color: $tooltip-bg;\n @include border-radius($border-radius);\n}\n","// scss-lint:disable DuplicateProperty\n@mixin reset-text {\n font-family: $font-family-base;\n // We deliberately do NOT reset font-size or word-wrap.\n font-style: normal;\n font-weight: $font-weight-normal;\n line-height: $line-height-base;\n text-align: left; // Fallback for where `start` is not supported\n text-align: start;\n text-decoration: none;\n text-shadow: none;\n text-transform: none;\n letter-spacing: normal;\n word-break: normal;\n word-spacing: normal;\n white-space: normal;\n line-break: auto;\n}\n",".popover {\n position: absolute;\n top: 0;\n left: 0;\n z-index: $zindex-popover;\n display: block;\n max-width: $popover-max-width;\n padding: $popover-inner-padding;\n // Our parent element can be arbitrary since tooltips are by default inserted as a sibling of their target element.\n // So reset our font and text properties to avoid inheriting weird values.\n @include reset-text();\n font-size: $font-size-sm;\n // Allow breaking very long words so they don't overflow the popover's bounds\n word-wrap: break-word;\n background-color: $popover-bg;\n background-clip: padding-box;\n border: $popover-border-width solid $popover-border-color;\n @include border-radius($border-radius-lg);\n @include box-shadow($popover-box-shadow);\n\n // Arrows\n //\n // .arrow is outer, .arrow::after is inner\n\n .arrow {\n position: absolute;\n display: block;\n width: $popover-arrow-width;\n height: $popover-arrow-height;\n }\n\n .arrow::before,\n .arrow::after {\n position: absolute;\n display: block;\n border-color: transparent;\n border-style: solid;\n }\n\n .arrow::before {\n content: \"\";\n border-width: $popover-arrow-outer-width;\n }\n .arrow::after {\n content: \"\";\n border-width: $popover-arrow-outer-width;\n }\n\n // Popover directions\n\n &.bs-popover-top {\n margin-bottom: $popover-arrow-width;\n\n .arrow {\n bottom: 0;\n }\n\n .arrow::before,\n .arrow::after {\n border-bottom-width: 0;\n }\n\n .arrow::before {\n bottom: -$popover-arrow-outer-width;\n margin-left: -($popover-arrow-outer-width - 5);\n border-top-color: $popover-arrow-outer-color;\n }\n\n .arrow::after {\n bottom: -($popover-arrow-outer-width - 1);\n margin-left: -($popover-arrow-outer-width - 5);\n border-top-color: $popover-arrow-color;\n }\n }\n\n &.bs-popover-right {\n margin-left: $popover-arrow-width;\n\n .arrow {\n left: 0;\n }\n\n .arrow::before,\n .arrow::after {\n margin-top: -($popover-arrow-outer-width - 3);\n border-left-width: 0;\n }\n\n .arrow::before {\n left: -$popover-arrow-outer-width;\n border-right-color: $popover-arrow-outer-color;\n }\n\n .arrow::after {\n left: -($popover-arrow-outer-width - 1);\n border-right-color: $popover-arrow-color;\n }\n }\n\n &.bs-popover-bottom {\n margin-top: $popover-arrow-width;\n\n .arrow {\n top: 0;\n }\n\n .arrow::before,\n .arrow::after {\n margin-left: -($popover-arrow-width - 3);\n border-top-width: 0;\n }\n\n .arrow::before {\n top: -$popover-arrow-outer-width;\n border-bottom-color: $popover-arrow-outer-color;\n }\n\n .arrow::after {\n top: -($popover-arrow-outer-width - 1);\n border-bottom-color: $popover-arrow-color;\n }\n\n // This will remove the popover-header's border just below the arrow\n .popover-header::before {\n position: absolute;\n top: 0;\n left: 50%;\n display: block;\n width: 20px;\n margin-left: -10px;\n content: \"\";\n border-bottom: 1px solid $popover-header-bg;\n }\n }\n\n &.bs-popover-left {\n margin-right: $popover-arrow-width;\n\n .arrow {\n right: 0;\n }\n\n .arrow::before,\n .arrow::after {\n margin-top: -($popover-arrow-outer-width - 3);\n border-right-width: 0;\n }\n\n .arrow::before {\n right: -$popover-arrow-outer-width;\n border-left-color: $popover-arrow-outer-color;\n }\n\n .arrow::after {\n right: -($popover-arrow-outer-width - 1);\n border-left-color: $popover-arrow-color;\n }\n }\n &.bs-popover-auto {\n &[x-placement^=\"top\"] {\n @extend .bs-popover-top;\n }\n &[x-placement^=\"right\"] {\n @extend .bs-popover-right;\n }\n &[x-placement^=\"bottom\"] {\n @extend .bs-popover-bottom;\n }\n &[x-placement^=\"left\"] {\n @extend .bs-popover-left;\n }\n }\n}\n\n\n// Offset the popover to account for the popover arrow\n.popover-header {\n padding: $popover-header-padding-y $popover-header-padding-x;\n margin-bottom: 0; // Reset the default from Reboot\n font-size: $font-size-base;\n color: $popover-header-color;\n background-color: $popover-header-bg;\n border-bottom: $popover-border-width solid darken($popover-header-bg, 5%);\n $offset-border-width: calc(#{$border-radius-lg} - #{$popover-border-width});\n @include border-top-radius($offset-border-width);\n\n &:empty {\n display: none;\n }\n}\n\n.popover-body {\n padding: $popover-body-padding-y $popover-body-padding-x;\n color: $popover-body-color;\n}\n","// Wrapper for the slide container and indicators\n.carousel {\n position: relative;\n}\n\n.carousel-inner {\n position: relative;\n width: 100%;\n overflow: hidden;\n}\n\n.carousel-item {\n position: relative;\n display: none;\n align-items: center;\n width: 100%;\n @include transition($carousel-transition);\n backface-visibility: hidden;\n perspective: 1000px;\n}\n\n.carousel-item.active,\n.carousel-item-next,\n.carousel-item-prev {\n display: block;\n}\n\n.carousel-item-next,\n.carousel-item-prev {\n position: absolute;\n top: 0;\n}\n\n// CSS3 transforms when supported by the browser\n.carousel-item-next.carousel-item-left,\n.carousel-item-prev.carousel-item-right {\n transform: translateX(0);\n\n @supports (transform-style: preserve-3d) {\n transform: translate3d(0, 0, 0);\n }\n}\n\n.carousel-item-next,\n.active.carousel-item-right {\n transform: translateX(100%);\n\n @supports (transform-style: preserve-3d) {\n transform: translate3d(100%, 0, 0);\n }\n}\n\n.carousel-item-prev,\n.active.carousel-item-left {\n transform: translateX(-100%);\n\n @supports (transform-style: preserve-3d) {\n transform: translate3d(-100%, 0, 0);\n }\n}\n\n\n//\n// Left/right controls for nav\n//\n\n.carousel-control-prev,\n.carousel-control-next {\n position: absolute;\n top: 0;\n bottom: 0;\n // Use flex for alignment (1-3)\n display: flex; // 1. allow flex styles\n align-items: center; // 2. vertically center contents\n justify-content: center; // 3. horizontally center contents\n width: $carousel-control-width;\n color: $carousel-control-color;\n text-align: center;\n opacity: $carousel-control-opacity;\n // We can't have a transition here because WebKit cancels the carousel\n // animation if you trip this while in the middle of another animation.\n\n // Hover/focus state\n @include hover-focus {\n color: $carousel-control-color;\n text-decoration: none;\n outline: 0;\n opacity: .9;\n }\n}\n.carousel-control-prev {\n left: 0;\n}\n.carousel-control-next {\n right: 0;\n}\n\n// Icons for within\n.carousel-control-prev-icon,\n.carousel-control-next-icon {\n display: inline-block;\n width: $carousel-control-icon-width;\n height: $carousel-control-icon-width;\n background: transparent no-repeat center center;\n background-size: 100% 100%;\n}\n.carousel-control-prev-icon {\n background-image: $carousel-control-prev-icon-bg;\n}\n.carousel-control-next-icon {\n background-image: $carousel-control-next-icon-bg;\n}\n\n\n// Optional indicator pips\n//\n// Add an ordered list with the following class and add a list item for each\n// slide your carousel holds.\n\n.carousel-indicators {\n position: absolute;\n right: 0;\n bottom: 10px;\n left: 0;\n z-index: 15;\n display: flex;\n justify-content: center;\n padding-left: 0; // override <ol> default\n // Use the .carousel-control's width as margin so we don't overlay those\n margin-right: $carousel-control-width;\n margin-left: $carousel-control-width;\n list-style: none;\n\n li {\n position: relative;\n flex: 0 1 auto;\n width: $carousel-indicator-width;\n height: $carousel-indicator-height;\n margin-right: $carousel-indicator-spacer;\n margin-left: $carousel-indicator-spacer;\n text-indent: -999px;\n background-color: rgba($carousel-indicator-active-bg, .5);\n\n // Use pseudo classes to increase the hit area by 10px on top and bottom.\n &::before {\n position: absolute;\n top: -10px;\n left: 0;\n display: inline-block;\n width: 100%;\n height: 10px;\n content: \"\";\n }\n &::after {\n position: absolute;\n bottom: -10px;\n left: 0;\n display: inline-block;\n width: 100%;\n height: 10px;\n content: \"\";\n }\n }\n\n .active {\n background-color: $carousel-indicator-active-bg;\n }\n}\n\n\n// Optional captions\n//\n//\n\n.carousel-caption {\n position: absolute;\n right: ((100% - $carousel-caption-width) / 2);\n bottom: 20px;\n left: ((100% - $carousel-caption-width) / 2);\n z-index: 10;\n padding-top: 20px;\n padding-bottom: 20px;\n color: $carousel-caption-color;\n text-align: center;\n}\n",".align-baseline { vertical-align: baseline !important; } // Browser default\n.align-top { vertical-align: top !important; }\n.align-middle { vertical-align: middle !important; }\n.align-bottom { vertical-align: bottom !important; }\n.align-text-bottom { vertical-align: text-bottom !important; }\n.align-text-top { vertical-align: text-top !important; }\n","// Contextual backgrounds\n\n@mixin bg-variant($parent, $color) {\n #{$parent} {\n background-color: $color !important;\n }\n a#{$parent} {\n @include hover-focus {\n background-color: darken($color, 10%) !important;\n }\n }\n}\n","@each $color, $value in $theme-colors {\n @include bg-variant('.bg-#{$color}', $value);\n}\n\n.bg-white { background-color: $white !important; }\n.bg-transparent { background-color: transparent !important; }\n","//\n// Border\n//\n\n.border { border: 1px solid $gray-200 !important; }\n.border-0 { border: 0 !important; }\n.border-top-0 { border-top: 0 !important; }\n.border-right-0 { border-right: 0 !important; }\n.border-bottom-0 { border-bottom: 0 !important; }\n.border-left-0 { border-left: 0 !important; }\n\n@each $color, $value in $theme-colors {\n .border-#{$color} {\n border-color: $value !important;\n }\n}\n\n.border-white {\n border-color: $white !important;\n}\n\n//\n// Border-radius\n//\n\n.rounded {\n border-radius: $border-radius !important;\n}\n.rounded-top {\n border-top-left-radius: $border-radius !important;\n border-top-right-radius: $border-radius !important;\n}\n.rounded-right {\n border-top-right-radius: $border-radius !important;\n border-bottom-right-radius: $border-radius !important;\n}\n.rounded-bottom {\n border-bottom-right-radius: $border-radius !important;\n border-bottom-left-radius: $border-radius !important;\n}\n.rounded-left {\n border-top-left-radius: $border-radius !important;\n border-bottom-left-radius: $border-radius !important;\n}\n\n.rounded-circle {\n border-radius: 50%;\n}\n\n.rounded-0 {\n border-radius: 0;\n}\n","//\n// Utilities for common `display` values\n//\n\n@each $breakpoint in map-keys($grid-breakpoints) {\n @include media-breakpoint-up($breakpoint) {\n $infix: breakpoint-infix($breakpoint, $grid-breakpoints);\n\n .d#{$infix}-none { display: none !important; }\n .d#{$infix}-inline { display: inline !important; }\n .d#{$infix}-inline-block { display: inline-block !important; }\n .d#{$infix}-block { display: block !important; }\n .d#{$infix}-table { display: table !important; }\n .d#{$infix}-table-cell { display: table-cell !important; }\n .d#{$infix}-flex { display: flex !important; }\n .d#{$infix}-inline-flex { display: inline-flex !important; }\n }\n}\n\n\n//\n// Utilities for toggling `display` in print\n//\n\n.d-print-block {\n display: none !important;\n\n @media print {\n display: block !important;\n }\n}\n\n.d-print-inline {\n display: none !important;\n\n @media print {\n display: inline !important;\n }\n}\n\n.d-print-inline-block {\n display: none !important;\n\n @media print {\n display: inline-block !important;\n }\n}\n\n.d-print-none {\n @media print {\n display: none !important;\n }\n}\n","// Credit: Nicolas Gallagher and SUIT CSS.\n\n.embed-responsive {\n position: relative;\n display: block;\n width: 100%;\n padding: 0;\n overflow: hidden;\n\n &::before {\n display: block;\n content: \"\";\n }\n\n .embed-responsive-item,\n iframe,\n embed,\n object,\n video {\n position: absolute;\n top: 0;\n bottom: 0;\n left: 0;\n width: 100%;\n height: 100%;\n border: 0;\n }\n}\n\n.embed-responsive-21by9 {\n &::before {\n padding-top: percentage(9 / 21);\n }\n}\n\n.embed-responsive-16by9 {\n &::before {\n padding-top: percentage(9 / 16);\n }\n}\n\n.embed-responsive-4by3 {\n &::before {\n padding-top: percentage(3 / 4);\n }\n}\n\n.embed-responsive-1by1 {\n &::before {\n padding-top: percentage(1 / 1);\n }\n}\n","// Flex variation\n//\n// Custom styles for additional flex alignment options.\n\n@each $breakpoint in map-keys($grid-breakpoints) {\n @include media-breakpoint-up($breakpoint) {\n $infix: breakpoint-infix($breakpoint, $grid-breakpoints);\n\n .flex#{$infix}-row { flex-direction: row !important; }\n .flex#{$infix}-column { flex-direction: column !important; }\n .flex#{$infix}-row-reverse { flex-direction: row-reverse !important; }\n .flex#{$infix}-column-reverse { flex-direction: column-reverse !important; }\n\n .flex#{$infix}-wrap { flex-wrap: wrap !important; }\n .flex#{$infix}-nowrap { flex-wrap: nowrap !important; }\n .flex#{$infix}-wrap-reverse { flex-wrap: wrap-reverse !important; }\n\n .justify-content#{$infix}-start { justify-content: flex-start !important; }\n .justify-content#{$infix}-end { justify-content: flex-end !important; }\n .justify-content#{$infix}-center { justify-content: center !important; }\n .justify-content#{$infix}-between { justify-content: space-between !important; }\n .justify-content#{$infix}-around { justify-content: space-around !important; }\n\n .align-items#{$infix}-start { align-items: flex-start !important; }\n .align-items#{$infix}-end { align-items: flex-end !important; }\n .align-items#{$infix}-center { align-items: center !important; }\n .align-items#{$infix}-baseline { align-items: baseline !important; }\n .align-items#{$infix}-stretch { align-items: stretch !important; }\n\n .align-content#{$infix}-start { align-content: flex-start !important; }\n .align-content#{$infix}-end { align-content: flex-end !important; }\n .align-content#{$infix}-center { align-content: center !important; }\n .align-content#{$infix}-between { align-content: space-between !important; }\n .align-content#{$infix}-around { align-content: space-around !important; }\n .align-content#{$infix}-stretch { align-content: stretch !important; }\n\n .align-self#{$infix}-auto { align-self: auto !important; }\n .align-self#{$infix}-start { align-self: flex-start !important; }\n .align-self#{$infix}-end { align-self: flex-end !important; }\n .align-self#{$infix}-center { align-self: center !important; }\n .align-self#{$infix}-baseline { align-self: baseline !important; }\n .align-self#{$infix}-stretch { align-self: stretch !important; }\n }\n}\n","@each $breakpoint in map-keys($grid-breakpoints) {\n @include media-breakpoint-up($breakpoint) {\n $infix: breakpoint-infix($breakpoint, $grid-breakpoints);\n\n .float#{$infix}-left { @include float-left; }\n .float#{$infix}-right { @include float-right; }\n .float#{$infix}-none { @include float-none; }\n }\n}\n","@mixin float-left {\n float: left !important;\n}\n@mixin float-right {\n float: right !important;\n}\n@mixin float-none {\n float: none !important;\n}\n","// Positioning\n\n.fixed-top {\n position: fixed;\n top: 0;\n right: 0;\n left: 0;\n z-index: $zindex-fixed;\n}\n\n.fixed-bottom {\n position: fixed;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: $zindex-fixed;\n}\n\n.sticky-top {\n @supports (position: sticky) {\n position: sticky;\n top: 0;\n z-index: $zindex-sticky;\n }\n}\n","//\n// Screenreaders\n//\n\n.sr-only {\n @include sr-only();\n}\n\n.sr-only-focusable {\n @include sr-only-focusable();\n}\n","// Only display content to screen readers\n//\n// See: http://a11yproject.com/posts/how-to-hide-content\n// See: http://hugogiraudel.com/2016/10/13/css-hide-and-seek/\n\n@mixin sr-only {\n position: absolute;\n width: 1px;\n height: 1px;\n padding: 0;\n overflow: hidden;\n clip: rect(0,0,0,0);\n white-space: nowrap;\n clip-path: inset(50%);\n border: 0;\n}\n\n// Use in conjunction with .sr-only to only display content when it's focused.\n//\n// Useful for \"Skip to main content\" links; see https://www.w3.org/TR/2013/NOTE-WCAG20-TECHS-20130905/G1\n//\n// Credit: HTML5 Boilerplate\n\n@mixin sr-only-focusable {\n &:active,\n &:focus {\n position: static;\n width: auto;\n height: auto;\n overflow: visible;\n clip: auto;\n white-space: normal;\n clip-path: none;\n }\n}\n","// Width and height\n\n@each $prop, $abbrev in (width: w, height: h) {\n @each $size, $length in $sizes {\n .#{$abbrev}-#{$size} { #{$prop}: $length !important; }\n }\n}\n\n.mw-100 { max-width: 100% !important; }\n.mh-100 { max-height: 100% !important; }\n","// Margin and Padding\n\n@each $breakpoint in map-keys($grid-breakpoints) {\n @include media-breakpoint-up($breakpoint) {\n $infix: breakpoint-infix($breakpoint, $grid-breakpoints);\n\n @each $prop, $abbrev in (margin: m, padding: p) {\n @each $size, $length in $spacers {\n\n .#{$abbrev}#{$infix}-#{$size} { #{$prop}: $length !important; }\n .#{$abbrev}t#{$infix}-#{$size} { #{$prop}-top: $length !important; }\n .#{$abbrev}r#{$infix}-#{$size} { #{$prop}-right: $length !important; }\n .#{$abbrev}b#{$infix}-#{$size} { #{$prop}-bottom: $length !important; }\n .#{$abbrev}l#{$infix}-#{$size} { #{$prop}-left: $length !important; }\n .#{$abbrev}x#{$infix}-#{$size} {\n #{$prop}-right: $length !important;\n #{$prop}-left: $length !important;\n }\n .#{$abbrev}y#{$infix}-#{$size} {\n #{$prop}-top: $length !important;\n #{$prop}-bottom: $length !important;\n }\n }\n }\n\n // Some special margin utils\n .m#{$infix}-auto { margin: auto !important; }\n .mt#{$infix}-auto { margin-top: auto !important; }\n .mr#{$infix}-auto { margin-right: auto !important; }\n .mb#{$infix}-auto { margin-bottom: auto !important; }\n .ml#{$infix}-auto { margin-left: auto !important; }\n .mx#{$infix}-auto {\n margin-right: auto !important;\n margin-left: auto !important;\n }\n .my#{$infix}-auto {\n margin-top: auto !important;\n margin-bottom: auto !important;\n }\n }\n}\n","//\n// Text\n//\n\n// Alignment\n\n.text-justify { text-align: justify !important; }\n.text-nowrap { white-space: nowrap !important; }\n.text-truncate { @include text-truncate; }\n\n// Responsive alignment\n\n@each $breakpoint in map-keys($grid-breakpoints) {\n @include media-breakpoint-up($breakpoint) {\n $infix: breakpoint-infix($breakpoint, $grid-breakpoints);\n\n .text#{$infix}-left { text-align: left !important; }\n .text#{$infix}-right { text-align: right !important; }\n .text#{$infix}-center { text-align: center !important; }\n }\n}\n\n// Transformation\n\n.text-lowercase { text-transform: lowercase !important; }\n.text-uppercase { text-transform: uppercase !important; }\n.text-capitalize { text-transform: capitalize !important; }\n\n// Weight and italics\n\n.font-weight-normal { font-weight: $font-weight-normal; }\n.font-weight-bold { font-weight: $font-weight-bold; }\n.font-italic { font-style: italic; }\n\n// Contextual colors\n\n.text-white { color: #fff !important; }\n\n@each $color, $value in $theme-colors {\n @include text-emphasis-variant('.text-#{$color}', $value);\n}\n\n.text-muted { color: $text-muted !important; }\n\n// Misc\n\n.text-hide {\n @include text-hide();\n}\n","// Text truncate\n// Requires inline-block or block for proper styling\n\n@mixin text-truncate() {\n overflow: hidden;\n text-overflow: ellipsis;\n white-space: nowrap;\n}\n","// Typography\n\n@mixin text-emphasis-variant($parent, $color) {\n #{$parent} {\n color: $color !important;\n }\n a#{$parent} {\n @include hover-focus {\n color: darken($color, 10%) !important;\n }\n }\n}\n","// CSS image replacement\n@mixin text-hide() {\n font: 0/0 a;\n color: transparent;\n text-shadow: none;\n background-color: transparent;\n border: 0;\n}\n","//\n// Visibility utilities\n//\n\n.visible {\n @include invisible(visible);\n}\n\n.invisible {\n @include invisible(hidden);\n}\n","// Visibility\n\n@mixin invisible($visibility) {\n visibility: $visibility !important;\n}\n"]} \ No newline at end of file
diff --git a/library/bootstrap/css/bootstrap.min.css b/library/bootstrap/css/bootstrap.min.css
index ed3905e0e..622b5a94d 100644
--- a/library/bootstrap/css/bootstrap.min.css
+++ b/library/bootstrap/css/bootstrap.min.css
@@ -1,6 +1,7 @@
/*!
- * Bootstrap v3.3.7 (http://getbootstrap.com)
- * Copyright 2011-2016 Twitter, Inc.
+ * Bootstrap v4.0.0-beta (https://getbootstrap.com)
+ * Copyright 2011-2017 The Bootstrap Authors
+ * Copyright 2011-2017 Twitter, Inc.
* Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
- *//*! normalize.css v3.0.3 | MIT License | github.com/necolas/normalize.css */html{font-family:sans-serif;-webkit-text-size-adjust:100%;-ms-text-size-adjust:100%}body{margin:0}article,aside,details,figcaption,figure,footer,header,hgroup,main,menu,nav,section,summary{display:block}audio,canvas,progress,video{display:inline-block;vertical-align:baseline}audio:not([controls]){display:none;height:0}[hidden],template{display:none}a{background-color:transparent}a:active,a:hover{outline:0}abbr[title]{border-bottom:1px dotted}b,strong{font-weight:700}dfn{font-style:italic}h1{margin:.67em 0;font-size:2em}mark{color:#000;background:#ff0}small{font-size:80%}sub,sup{position:relative;font-size:75%;line-height:0;vertical-align:baseline}sup{top:-.5em}sub{bottom:-.25em}img{border:0}svg:not(:root){overflow:hidden}figure{margin:1em 40px}hr{height:0;-webkit-box-sizing:content-box;-moz-box-sizing:content-box;box-sizing:content-box}pre{overflow:auto}code,kbd,pre,samp{font-family:monospace,monospace;font-size:1em}button,input,optgroup,select,textarea{margin:0;font:inherit;color:inherit}button{overflow:visible}button,select{text-transform:none}button,html input[type=button],input[type=reset],input[type=submit]{-webkit-appearance:button;cursor:pointer}button[disabled],html input[disabled]{cursor:default}button::-moz-focus-inner,input::-moz-focus-inner{padding:0;border:0}input{line-height:normal}input[type=checkbox],input[type=radio]{-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box;padding:0}input[type=number]::-webkit-inner-spin-button,input[type=number]::-webkit-outer-spin-button{height:auto}input[type=search]{-webkit-box-sizing:content-box;-moz-box-sizing:content-box;box-sizing:content-box;-webkit-appearance:textfield}input[type=search]::-webkit-search-cancel-button,input[type=search]::-webkit-search-decoration{-webkit-appearance:none}fieldset{padding:.35em .625em .75em;margin:0 2px;border:1px solid silver}legend{padding:0;border:0}textarea{overflow:auto}optgroup{font-weight:700}table{border-spacing:0;border-collapse:collapse}td,th{padding:0}/*! Source: https://github.com/h5bp/html5-boilerplate/blob/master/src/css/main.css */@media print{*,:after,:before{color:#000!important;text-shadow:none!important;background:0 0!important;-webkit-box-shadow:none!important;box-shadow:none!important}a,a:visited{text-decoration:underline}a[href]:after{content:" (" attr(href) ")"}abbr[title]:after{content:" (" attr(title) ")"}a[href^="javascript:"]:after,a[href^="#"]:after{content:""}blockquote,pre{border:1px solid #999;page-break-inside:avoid}thead{display:table-header-group}img,tr{page-break-inside:avoid}img{max-width:100%!important}h2,h3,p{orphans:3;widows:3}h2,h3{page-break-after:avoid}.navbar{display:none}.btn>.caret,.dropup>.btn>.caret{border-top-color:#000!important}.label{border:1px solid #000}.table{border-collapse:collapse!important}.table td,.table th{background-color:#fff!important}.table-bordered td,.table-bordered th{border:1px solid #ddd!important}}@font-face{font-family:'Glyphicons Halflings';src:url(../fonts/glyphicons-halflings-regular.eot);src:url(../fonts/glyphicons-halflings-regular.eot?#iefix) format('embedded-opentype'),url(../fonts/glyphicons-halflings-regular.woff2) format('woff2'),url(../fonts/glyphicons-halflings-regular.woff) format('woff'),url(../fonts/glyphicons-halflings-regular.ttf) format('truetype'),url(../fonts/glyphicons-halflings-regular.svg#glyphicons_halflingsregular) format('svg')}.glyphicon{position:relative;top:1px;display:inline-block;font-family:'Glyphicons Halflings';font-style:normal;font-weight:400;line-height:1;-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale}.glyphicon-asterisk:before{content:"\002a"}.glyphicon-plus:before{content:"\002b"}.glyphicon-eur:before,.glyphicon-euro:before{content:"\20ac"}.glyphicon-minus:before{content:"\2212"}.glyphicon-cloud:before{content:"\2601"}.glyphicon-envelope:before{content:"\2709"}.glyphicon-pencil:before{content:"\270f"}.glyphicon-glass:before{content:"\e001"}.glyphicon-music:before{content:"\e002"}.glyphicon-search:before{content:"\e003"}.glyphicon-heart:before{content:"\e005"}.glyphicon-star:before{content:"\e006"}.glyphicon-star-empty:before{content:"\e007"}.glyphicon-user:before{content:"\e008"}.glyphicon-film:before{content:"\e009"}.glyphicon-th-large:before{content:"\e010"}.glyphicon-th:before{content:"\e011"}.glyphicon-th-list:before{content:"\e012"}.glyphicon-ok:before{content:"\e013"}.glyphicon-remove:before{content:"\e014"}.glyphicon-zoom-in:before{content:"\e015"}.glyphicon-zoom-out:before{content:"\e016"}.glyphicon-off:before{content:"\e017"}.glyphicon-signal:before{content:"\e018"}.glyphicon-cog:before{content:"\e019"}.glyphicon-trash:before{content:"\e020"}.glyphicon-home:before{content:"\e021"}.glyphicon-file:before{content:"\e022"}.glyphicon-time:before{content:"\e023"}.glyphicon-road:before{content:"\e024"}.glyphicon-download-alt:before{content:"\e025"}.glyphicon-download:before{content:"\e026"}.glyphicon-upload:before{content:"\e027"}.glyphicon-inbox:before{content:"\e028"}.glyphicon-play-circle:before{content:"\e029"}.glyphicon-repeat:before{content:"\e030"}.glyphicon-refresh:before{content:"\e031"}.glyphicon-list-alt:before{content:"\e032"}.glyphicon-lock:before{content:"\e033"}.glyphicon-flag:before{content:"\e034"}.glyphicon-headphones:before{content:"\e035"}.glyphicon-volume-off:before{content:"\e036"}.glyphicon-volume-down:before{content:"\e037"}.glyphicon-volume-up:before{content:"\e038"}.glyphicon-qrcode:before{content:"\e039"}.glyphicon-barcode:before{content:"\e040"}.glyphicon-tag:before{content:"\e041"}.glyphicon-tags:before{content:"\e042"}.glyphicon-book:before{content:"\e043"}.glyphicon-bookmark:before{content:"\e044"}.glyphicon-print:before{content:"\e045"}.glyphicon-camera:before{content:"\e046"}.glyphicon-font:before{content:"\e047"}.glyphicon-bold:before{content:"\e048"}.glyphicon-italic:before{content:"\e049"}.glyphicon-text-height:before{content:"\e050"}.glyphicon-text-width:before{content:"\e051"}.glyphicon-align-left:before{content:"\e052"}.glyphicon-align-center:before{content:"\e053"}.glyphicon-align-right:before{content:"\e054"}.glyphicon-align-justify:before{content:"\e055"}.glyphicon-list:before{content:"\e056"}.glyphicon-indent-left:before{content:"\e057"}.glyphicon-indent-right:before{content:"\e058"}.glyphicon-facetime-video:before{content:"\e059"}.glyphicon-picture:before{content:"\e060"}.glyphicon-map-marker:before{content:"\e062"}.glyphicon-adjust:before{content:"\e063"}.glyphicon-tint:before{content:"\e064"}.glyphicon-edit:before{content:"\e065"}.glyphicon-share:before{content:"\e066"}.glyphicon-check:before{content:"\e067"}.glyphicon-move:before{content:"\e068"}.glyphicon-step-backward:before{content:"\e069"}.glyphicon-fast-backward:before{content:"\e070"}.glyphicon-backward:before{content:"\e071"}.glyphicon-play:before{content:"\e072"}.glyphicon-pause:before{content:"\e073"}.glyphicon-stop:before{content:"\e074"}.glyphicon-forward:before{content:"\e075"}.glyphicon-fast-forward:before{content:"\e076"}.glyphicon-step-forward:before{content:"\e077"}.glyphicon-eject:before{content:"\e078"}.glyphicon-chevron-left:before{content:"\e079"}.glyphicon-chevron-right:before{content:"\e080"}.glyphicon-plus-sign:before{content:"\e081"}.glyphicon-minus-sign:before{content:"\e082"}.glyphicon-remove-sign:before{content:"\e083"}.glyphicon-ok-sign:before{content:"\e084"}.glyphicon-question-sign:before{content:"\e085"}.glyphicon-info-sign:before{content:"\e086"}.glyphicon-screenshot:before{content:"\e087"}.glyphicon-remove-circle:before{content:"\e088"}.glyphicon-ok-circle:before{content:"\e089"}.glyphicon-ban-circle:before{content:"\e090"}.glyphicon-arrow-left:before{content:"\e091"}.glyphicon-arrow-right:before{content:"\e092"}.glyphicon-arrow-up:before{content:"\e093"}.glyphicon-arrow-down:before{content:"\e094"}.glyphicon-share-alt:before{content:"\e095"}.glyphicon-resize-full:before{content:"\e096"}.glyphicon-resize-small:before{content:"\e097"}.glyphicon-exclamation-sign:before{content:"\e101"}.glyphicon-gift:before{content:"\e102"}.glyphicon-leaf:before{content:"\e103"}.glyphicon-fire:before{content:"\e104"}.glyphicon-eye-open:before{content:"\e105"}.glyphicon-eye-close:before{content:"\e106"}.glyphicon-warning-sign:before{content:"\e107"}.glyphicon-plane:before{content:"\e108"}.glyphicon-calendar:before{content:"\e109"}.glyphicon-random:before{content:"\e110"}.glyphicon-comment:before{content:"\e111"}.glyphicon-magnet:before{content:"\e112"}.glyphicon-chevron-up:before{content:"\e113"}.glyphicon-chevron-down:before{content:"\e114"}.glyphicon-retweet:before{content:"\e115"}.glyphicon-shopping-cart:before{content:"\e116"}.glyphicon-folder-close:before{content:"\e117"}.glyphicon-folder-open:before{content:"\e118"}.glyphicon-resize-vertical:before{content:"\e119"}.glyphicon-resize-horizontal:before{content:"\e120"}.glyphicon-hdd:before{content:"\e121"}.glyphicon-bullhorn:before{content:"\e122"}.glyphicon-bell:before{content:"\e123"}.glyphicon-certificate:before{content:"\e124"}.glyphicon-thumbs-up:before{content:"\e125"}.glyphicon-thumbs-down:before{content:"\e126"}.glyphicon-hand-right:before{content:"\e127"}.glyphicon-hand-left:before{content:"\e128"}.glyphicon-hand-up:before{content:"\e129"}.glyphicon-hand-down:before{content:"\e130"}.glyphicon-circle-arrow-right:before{content:"\e131"}.glyphicon-circle-arrow-left:before{content:"\e132"}.glyphicon-circle-arrow-up:before{content:"\e133"}.glyphicon-circle-arrow-down:before{content:"\e134"}.glyphicon-globe:before{content:"\e135"}.glyphicon-wrench:before{content:"\e136"}.glyphicon-tasks:before{content:"\e137"}.glyphicon-filter:before{content:"\e138"}.glyphicon-briefcase:before{content:"\e139"}.glyphicon-fullscreen:before{content:"\e140"}.glyphicon-dashboard:before{content:"\e141"}.glyphicon-paperclip:before{content:"\e142"}.glyphicon-heart-empty:before{content:"\e143"}.glyphicon-link:before{content:"\e144"}.glyphicon-phone:before{content:"\e145"}.glyphicon-pushpin:before{content:"\e146"}.glyphicon-usd:before{content:"\e148"}.glyphicon-gbp:before{content:"\e149"}.glyphicon-sort:before{content:"\e150"}.glyphicon-sort-by-alphabet:before{content:"\e151"}.glyphicon-sort-by-alphabet-alt:before{content:"\e152"}.glyphicon-sort-by-order:before{content:"\e153"}.glyphicon-sort-by-order-alt:before{content:"\e154"}.glyphicon-sort-by-attributes:before{content:"\e155"}.glyphicon-sort-by-attributes-alt:before{content:"\e156"}.glyphicon-unchecked:before{content:"\e157"}.glyphicon-expand:before{content:"\e158"}.glyphicon-collapse-down:before{content:"\e159"}.glyphicon-collapse-up:before{content:"\e160"}.glyphicon-log-in:before{content:"\e161"}.glyphicon-flash:before{content:"\e162"}.glyphicon-log-out:before{content:"\e163"}.glyphicon-new-window:before{content:"\e164"}.glyphicon-record:before{content:"\e165"}.glyphicon-save:before{content:"\e166"}.glyphicon-open:before{content:"\e167"}.glyphicon-saved:before{content:"\e168"}.glyphicon-import:before{content:"\e169"}.glyphicon-export:before{content:"\e170"}.glyphicon-send:before{content:"\e171"}.glyphicon-floppy-disk:before{content:"\e172"}.glyphicon-floppy-saved:before{content:"\e173"}.glyphicon-floppy-remove:before{content:"\e174"}.glyphicon-floppy-save:before{content:"\e175"}.glyphicon-floppy-open:before{content:"\e176"}.glyphicon-credit-card:before{content:"\e177"}.glyphicon-transfer:before{content:"\e178"}.glyphicon-cutlery:before{content:"\e179"}.glyphicon-header:before{content:"\e180"}.glyphicon-compressed:before{content:"\e181"}.glyphicon-earphone:before{content:"\e182"}.glyphicon-phone-alt:before{content:"\e183"}.glyphicon-tower:before{content:"\e184"}.glyphicon-stats:before{content:"\e185"}.glyphicon-sd-video:before{content:"\e186"}.glyphicon-hd-video:before{content:"\e187"}.glyphicon-subtitles:before{content:"\e188"}.glyphicon-sound-stereo:before{content:"\e189"}.glyphicon-sound-dolby:before{content:"\e190"}.glyphicon-sound-5-1:before{content:"\e191"}.glyphicon-sound-6-1:before{content:"\e192"}.glyphicon-sound-7-1:before{content:"\e193"}.glyphicon-copyright-mark:before{content:"\e194"}.glyphicon-registration-mark:before{content:"\e195"}.glyphicon-cloud-download:before{content:"\e197"}.glyphicon-cloud-upload:before{content:"\e198"}.glyphicon-tree-conifer:before{content:"\e199"}.glyphicon-tree-deciduous:before{content:"\e200"}.glyphicon-cd:before{content:"\e201"}.glyphicon-save-file:before{content:"\e202"}.glyphicon-open-file:before{content:"\e203"}.glyphicon-level-up:before{content:"\e204"}.glyphicon-copy:before{content:"\e205"}.glyphicon-paste:before{content:"\e206"}.glyphicon-alert:before{content:"\e209"}.glyphicon-equalizer:before{content:"\e210"}.glyphicon-king:before{content:"\e211"}.glyphicon-queen:before{content:"\e212"}.glyphicon-pawn:before{content:"\e213"}.glyphicon-bishop:before{content:"\e214"}.glyphicon-knight:before{content:"\e215"}.glyphicon-baby-formula:before{content:"\e216"}.glyphicon-tent:before{content:"\26fa"}.glyphicon-blackboard:before{content:"\e218"}.glyphicon-bed:before{content:"\e219"}.glyphicon-apple:before{content:"\f8ff"}.glyphicon-erase:before{content:"\e221"}.glyphicon-hourglass:before{content:"\231b"}.glyphicon-lamp:before{content:"\e223"}.glyphicon-duplicate:before{content:"\e224"}.glyphicon-piggy-bank:before{content:"\e225"}.glyphicon-scissors:before{content:"\e226"}.glyphicon-bitcoin:before{content:"\e227"}.glyphicon-btc:before{content:"\e227"}.glyphicon-xbt:before{content:"\e227"}.glyphicon-yen:before{content:"\00a5"}.glyphicon-jpy:before{content:"\00a5"}.glyphicon-ruble:before{content:"\20bd"}.glyphicon-rub:before{content:"\20bd"}.glyphicon-scale:before{content:"\e230"}.glyphicon-ice-lolly:before{content:"\e231"}.glyphicon-ice-lolly-tasted:before{content:"\e232"}.glyphicon-education:before{content:"\e233"}.glyphicon-option-horizontal:before{content:"\e234"}.glyphicon-option-vertical:before{content:"\e235"}.glyphicon-menu-hamburger:before{content:"\e236"}.glyphicon-modal-window:before{content:"\e237"}.glyphicon-oil:before{content:"\e238"}.glyphicon-grain:before{content:"\e239"}.glyphicon-sunglasses:before{content:"\e240"}.glyphicon-text-size:before{content:"\e241"}.glyphicon-text-color:before{content:"\e242"}.glyphicon-text-background:before{content:"\e243"}.glyphicon-object-align-top:before{content:"\e244"}.glyphicon-object-align-bottom:before{content:"\e245"}.glyphicon-object-align-horizontal:before{content:"\e246"}.glyphicon-object-align-left:before{content:"\e247"}.glyphicon-object-align-vertical:before{content:"\e248"}.glyphicon-object-align-right:before{content:"\e249"}.glyphicon-triangle-right:before{content:"\e250"}.glyphicon-triangle-left:before{content:"\e251"}.glyphicon-triangle-bottom:before{content:"\e252"}.glyphicon-triangle-top:before{content:"\e253"}.glyphicon-console:before{content:"\e254"}.glyphicon-superscript:before{content:"\e255"}.glyphicon-subscript:before{content:"\e256"}.glyphicon-menu-left:before{content:"\e257"}.glyphicon-menu-right:before{content:"\e258"}.glyphicon-menu-down:before{content:"\e259"}.glyphicon-menu-up:before{content:"\e260"}*{-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}:after,:before{-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}html{font-size:10px;-webkit-tap-highlight-color:rgba(0,0,0,0)}body{font-family:"Helvetica Neue",Helvetica,Arial,sans-serif;font-size:14px;line-height:1.42857143;color:#333;background-color:#fff}button,input,select,textarea{font-family:inherit;font-size:inherit;line-height:inherit}a{color:#337ab7;text-decoration:none}a:focus,a:hover{color:#23527c;text-decoration:underline}a:focus{outline:5px auto -webkit-focus-ring-color;outline-offset:-2px}figure{margin:0}img{vertical-align:middle}.carousel-inner>.item>a>img,.carousel-inner>.item>img,.img-responsive,.thumbnail a>img,.thumbnail>img{display:block;max-width:100%;height:auto}.img-rounded{border-radius:6px}.img-thumbnail{display:inline-block;max-width:100%;height:auto;padding:4px;line-height:1.42857143;background-color:#fff;border:1px solid #ddd;border-radius:4px;-webkit-transition:all .2s ease-in-out;-o-transition:all .2s ease-in-out;transition:all .2s ease-in-out}.img-circle{border-radius:50%}hr{margin-top:20px;margin-bottom:20px;border:0;border-top:1px solid #eee}.sr-only{position:absolute;width:1px;height:1px;padding:0;margin:-1px;overflow:hidden;clip:rect(0,0,0,0);border:0}.sr-only-focusable:active,.sr-only-focusable:focus{position:static;width:auto;height:auto;margin:0;overflow:visible;clip:auto}[role=button]{cursor:pointer}.h1,.h2,.h3,.h4,.h5,.h6,h1,h2,h3,h4,h5,h6{font-family:inherit;font-weight:500;line-height:1.1;color:inherit}.h1 .small,.h1 small,.h2 .small,.h2 small,.h3 .small,.h3 small,.h4 .small,.h4 small,.h5 .small,.h5 small,.h6 .small,.h6 small,h1 .small,h1 small,h2 .small,h2 small,h3 .small,h3 small,h4 .small,h4 small,h5 .small,h5 small,h6 .small,h6 small{font-weight:400;line-height:1;color:#777}.h1,.h2,.h3,h1,h2,h3{margin-top:20px;margin-bottom:10px}.h1 .small,.h1 small,.h2 .small,.h2 small,.h3 .small,.h3 small,h1 .small,h1 small,h2 .small,h2 small,h3 .small,h3 small{font-size:65%}.h4,.h5,.h6,h4,h5,h6{margin-top:10px;margin-bottom:10px}.h4 .small,.h4 small,.h5 .small,.h5 small,.h6 .small,.h6 small,h4 .small,h4 small,h5 .small,h5 small,h6 .small,h6 small{font-size:75%}.h1,h1{font-size:36px}.h2,h2{font-size:30px}.h3,h3{font-size:24px}.h4,h4{font-size:18px}.h5,h5{font-size:14px}.h6,h6{font-size:12px}p{margin:0 0 10px}.lead{margin-bottom:20px;font-size:16px;font-weight:300;line-height:1.4}@media (min-width:768px){.lead{font-size:21px}}.small,small{font-size:85%}.mark,mark{padding:.2em;background-color:#fcf8e3}.text-left{text-align:left}.text-right{text-align:right}.text-center{text-align:center}.text-justify{text-align:justify}.text-nowrap{white-space:nowrap}.text-lowercase{text-transform:lowercase}.text-uppercase{text-transform:uppercase}.text-capitalize{text-transform:capitalize}.text-muted{color:#777}.text-primary{color:#337ab7}a.text-primary:focus,a.text-primary:hover{color:#286090}.text-success{color:#3c763d}a.text-success:focus,a.text-success:hover{color:#2b542c}.text-info{color:#31708f}a.text-info:focus,a.text-info:hover{color:#245269}.text-warning{color:#8a6d3b}a.text-warning:focus,a.text-warning:hover{color:#66512c}.text-danger{color:#a94442}a.text-danger:focus,a.text-danger:hover{color:#843534}.bg-primary{color:#fff;background-color:#337ab7}a.bg-primary:focus,a.bg-primary:hover{background-color:#286090}.bg-success{background-color:#dff0d8}a.bg-success:focus,a.bg-success:hover{background-color:#c1e2b3}.bg-info{background-color:#d9edf7}a.bg-info:focus,a.bg-info:hover{background-color:#afd9ee}.bg-warning{background-color:#fcf8e3}a.bg-warning:focus,a.bg-warning:hover{background-color:#f7ecb5}.bg-danger{background-color:#f2dede}a.bg-danger:focus,a.bg-danger:hover{background-color:#e4b9b9}.page-header{padding-bottom:9px;margin:40px 0 20px;border-bottom:1px solid #eee}ol,ul{margin-top:0;margin-bottom:10px}ol ol,ol ul,ul ol,ul ul{margin-bottom:0}.list-unstyled{padding-left:0;list-style:none}.list-inline{padding-left:0;margin-left:-5px;list-style:none}.list-inline>li{display:inline-block;padding-right:5px;padding-left:5px}dl{margin-top:0;margin-bottom:20px}dd,dt{line-height:1.42857143}dt{font-weight:700}dd{margin-left:0}@media (min-width:768px){.dl-horizontal dt{float:left;width:160px;overflow:hidden;clear:left;text-align:right;text-overflow:ellipsis;white-space:nowrap}.dl-horizontal dd{margin-left:180px}}abbr[data-original-title],abbr[title]{cursor:help;border-bottom:1px dotted #777}.initialism{font-size:90%;text-transform:uppercase}blockquote{padding:10px 20px;margin:0 0 20px;font-size:17.5px;border-left:5px solid #eee}blockquote ol:last-child,blockquote p:last-child,blockquote ul:last-child{margin-bottom:0}blockquote .small,blockquote footer,blockquote small{display:block;font-size:80%;line-height:1.42857143;color:#777}blockquote .small:before,blockquote footer:before,blockquote small:before{content:'\2014 \00A0'}.blockquote-reverse,blockquote.pull-right{padding-right:15px;padding-left:0;text-align:right;border-right:5px solid #eee;border-left:0}.blockquote-reverse .small:before,.blockquote-reverse footer:before,.blockquote-reverse small:before,blockquote.pull-right .small:before,blockquote.pull-right footer:before,blockquote.pull-right small:before{content:''}.blockquote-reverse .small:after,.blockquote-reverse footer:after,.blockquote-reverse small:after,blockquote.pull-right .small:after,blockquote.pull-right footer:after,blockquote.pull-right small:after{content:'\00A0 \2014'}address{margin-bottom:20px;font-style:normal;line-height:1.42857143}code,kbd,pre,samp{font-family:Menlo,Monaco,Consolas,"Courier New",monospace}code{padding:2px 4px;font-size:90%;color:#c7254e;background-color:#f9f2f4;border-radius:4px}kbd{padding:2px 4px;font-size:90%;color:#fff;background-color:#333;border-radius:3px;-webkit-box-shadow:inset 0 -1px 0 rgba(0,0,0,.25);box-shadow:inset 0 -1px 0 rgba(0,0,0,.25)}kbd kbd{padding:0;font-size:100%;font-weight:700;-webkit-box-shadow:none;box-shadow:none}pre{display:block;padding:9.5px;margin:0 0 10px;font-size:13px;line-height:1.42857143;color:#333;word-break:break-all;word-wrap:break-word;background-color:#f5f5f5;border:1px solid #ccc;border-radius:4px}pre code{padding:0;font-size:inherit;color:inherit;white-space:pre-wrap;background-color:transparent;border-radius:0}.pre-scrollable{max-height:340px;overflow-y:scroll}.container{padding-right:15px;padding-left:15px;margin-right:auto;margin-left:auto}@media (min-width:768px){.container{width:750px}}@media (min-width:992px){.container{width:970px}}@media (min-width:1200px){.container{width:1170px}}.container-fluid{padding-right:15px;padding-left:15px;margin-right:auto;margin-left:auto}.row{margin-right:-15px;margin-left:-15px}.col-lg-1,.col-lg-10,.col-lg-11,.col-lg-12,.col-lg-2,.col-lg-3,.col-lg-4,.col-lg-5,.col-lg-6,.col-lg-7,.col-lg-8,.col-lg-9,.col-md-1,.col-md-10,.col-md-11,.col-md-12,.col-md-2,.col-md-3,.col-md-4,.col-md-5,.col-md-6,.col-md-7,.col-md-8,.col-md-9,.col-sm-1,.col-sm-10,.col-sm-11,.col-sm-12,.col-sm-2,.col-sm-3,.col-sm-4,.col-sm-5,.col-sm-6,.col-sm-7,.col-sm-8,.col-sm-9,.col-xs-1,.col-xs-10,.col-xs-11,.col-xs-12,.col-xs-2,.col-xs-3,.col-xs-4,.col-xs-5,.col-xs-6,.col-xs-7,.col-xs-8,.col-xs-9{position:relative;min-height:1px;padding-right:15px;padding-left:15px}.col-xs-1,.col-xs-10,.col-xs-11,.col-xs-12,.col-xs-2,.col-xs-3,.col-xs-4,.col-xs-5,.col-xs-6,.col-xs-7,.col-xs-8,.col-xs-9{float:left}.col-xs-12{width:100%}.col-xs-11{width:91.66666667%}.col-xs-10{width:83.33333333%}.col-xs-9{width:75%}.col-xs-8{width:66.66666667%}.col-xs-7{width:58.33333333%}.col-xs-6{width:50%}.col-xs-5{width:41.66666667%}.col-xs-4{width:33.33333333%}.col-xs-3{width:25%}.col-xs-2{width:16.66666667%}.col-xs-1{width:8.33333333%}.col-xs-pull-12{right:100%}.col-xs-pull-11{right:91.66666667%}.col-xs-pull-10{right:83.33333333%}.col-xs-pull-9{right:75%}.col-xs-pull-8{right:66.66666667%}.col-xs-pull-7{right:58.33333333%}.col-xs-pull-6{right:50%}.col-xs-pull-5{right:41.66666667%}.col-xs-pull-4{right:33.33333333%}.col-xs-pull-3{right:25%}.col-xs-pull-2{right:16.66666667%}.col-xs-pull-1{right:8.33333333%}.col-xs-pull-0{right:auto}.col-xs-push-12{left:100%}.col-xs-push-11{left:91.66666667%}.col-xs-push-10{left:83.33333333%}.col-xs-push-9{left:75%}.col-xs-push-8{left:66.66666667%}.col-xs-push-7{left:58.33333333%}.col-xs-push-6{left:50%}.col-xs-push-5{left:41.66666667%}.col-xs-push-4{left:33.33333333%}.col-xs-push-3{left:25%}.col-xs-push-2{left:16.66666667%}.col-xs-push-1{left:8.33333333%}.col-xs-push-0{left:auto}.col-xs-offset-12{margin-left:100%}.col-xs-offset-11{margin-left:91.66666667%}.col-xs-offset-10{margin-left:83.33333333%}.col-xs-offset-9{margin-left:75%}.col-xs-offset-8{margin-left:66.66666667%}.col-xs-offset-7{margin-left:58.33333333%}.col-xs-offset-6{margin-left:50%}.col-xs-offset-5{margin-left:41.66666667%}.col-xs-offset-4{margin-left:33.33333333%}.col-xs-offset-3{margin-left:25%}.col-xs-offset-2{margin-left:16.66666667%}.col-xs-offset-1{margin-left:8.33333333%}.col-xs-offset-0{margin-left:0}@media (min-width:768px){.col-sm-1,.col-sm-10,.col-sm-11,.col-sm-12,.col-sm-2,.col-sm-3,.col-sm-4,.col-sm-5,.col-sm-6,.col-sm-7,.col-sm-8,.col-sm-9{float:left}.col-sm-12{width:100%}.col-sm-11{width:91.66666667%}.col-sm-10{width:83.33333333%}.col-sm-9{width:75%}.col-sm-8{width:66.66666667%}.col-sm-7{width:58.33333333%}.col-sm-6{width:50%}.col-sm-5{width:41.66666667%}.col-sm-4{width:33.33333333%}.col-sm-3{width:25%}.col-sm-2{width:16.66666667%}.col-sm-1{width:8.33333333%}.col-sm-pull-12{right:100%}.col-sm-pull-11{right:91.66666667%}.col-sm-pull-10{right:83.33333333%}.col-sm-pull-9{right:75%}.col-sm-pull-8{right:66.66666667%}.col-sm-pull-7{right:58.33333333%}.col-sm-pull-6{right:50%}.col-sm-pull-5{right:41.66666667%}.col-sm-pull-4{right:33.33333333%}.col-sm-pull-3{right:25%}.col-sm-pull-2{right:16.66666667%}.col-sm-pull-1{right:8.33333333%}.col-sm-pull-0{right:auto}.col-sm-push-12{left:100%}.col-sm-push-11{left:91.66666667%}.col-sm-push-10{left:83.33333333%}.col-sm-push-9{left:75%}.col-sm-push-8{left:66.66666667%}.col-sm-push-7{left:58.33333333%}.col-sm-push-6{left:50%}.col-sm-push-5{left:41.66666667%}.col-sm-push-4{left:33.33333333%}.col-sm-push-3{left:25%}.col-sm-push-2{left:16.66666667%}.col-sm-push-1{left:8.33333333%}.col-sm-push-0{left:auto}.col-sm-offset-12{margin-left:100%}.col-sm-offset-11{margin-left:91.66666667%}.col-sm-offset-10{margin-left:83.33333333%}.col-sm-offset-9{margin-left:75%}.col-sm-offset-8{margin-left:66.66666667%}.col-sm-offset-7{margin-left:58.33333333%}.col-sm-offset-6{margin-left:50%}.col-sm-offset-5{margin-left:41.66666667%}.col-sm-offset-4{margin-left:33.33333333%}.col-sm-offset-3{margin-left:25%}.col-sm-offset-2{margin-left:16.66666667%}.col-sm-offset-1{margin-left:8.33333333%}.col-sm-offset-0{margin-left:0}}@media (min-width:992px){.col-md-1,.col-md-10,.col-md-11,.col-md-12,.col-md-2,.col-md-3,.col-md-4,.col-md-5,.col-md-6,.col-md-7,.col-md-8,.col-md-9{float:left}.col-md-12{width:100%}.col-md-11{width:91.66666667%}.col-md-10{width:83.33333333%}.col-md-9{width:75%}.col-md-8{width:66.66666667%}.col-md-7{width:58.33333333%}.col-md-6{width:50%}.col-md-5{width:41.66666667%}.col-md-4{width:33.33333333%}.col-md-3{width:25%}.col-md-2{width:16.66666667%}.col-md-1{width:8.33333333%}.col-md-pull-12{right:100%}.col-md-pull-11{right:91.66666667%}.col-md-pull-10{right:83.33333333%}.col-md-pull-9{right:75%}.col-md-pull-8{right:66.66666667%}.col-md-pull-7{right:58.33333333%}.col-md-pull-6{right:50%}.col-md-pull-5{right:41.66666667%}.col-md-pull-4{right:33.33333333%}.col-md-pull-3{right:25%}.col-md-pull-2{right:16.66666667%}.col-md-pull-1{right:8.33333333%}.col-md-pull-0{right:auto}.col-md-push-12{left:100%}.col-md-push-11{left:91.66666667%}.col-md-push-10{left:83.33333333%}.col-md-push-9{left:75%}.col-md-push-8{left:66.66666667%}.col-md-push-7{left:58.33333333%}.col-md-push-6{left:50%}.col-md-push-5{left:41.66666667%}.col-md-push-4{left:33.33333333%}.col-md-push-3{left:25%}.col-md-push-2{left:16.66666667%}.col-md-push-1{left:8.33333333%}.col-md-push-0{left:auto}.col-md-offset-12{margin-left:100%}.col-md-offset-11{margin-left:91.66666667%}.col-md-offset-10{margin-left:83.33333333%}.col-md-offset-9{margin-left:75%}.col-md-offset-8{margin-left:66.66666667%}.col-md-offset-7{margin-left:58.33333333%}.col-md-offset-6{margin-left:50%}.col-md-offset-5{margin-left:41.66666667%}.col-md-offset-4{margin-left:33.33333333%}.col-md-offset-3{margin-left:25%}.col-md-offset-2{margin-left:16.66666667%}.col-md-offset-1{margin-left:8.33333333%}.col-md-offset-0{margin-left:0}}@media (min-width:1200px){.col-lg-1,.col-lg-10,.col-lg-11,.col-lg-12,.col-lg-2,.col-lg-3,.col-lg-4,.col-lg-5,.col-lg-6,.col-lg-7,.col-lg-8,.col-lg-9{float:left}.col-lg-12{width:100%}.col-lg-11{width:91.66666667%}.col-lg-10{width:83.33333333%}.col-lg-9{width:75%}.col-lg-8{width:66.66666667%}.col-lg-7{width:58.33333333%}.col-lg-6{width:50%}.col-lg-5{width:41.66666667%}.col-lg-4{width:33.33333333%}.col-lg-3{width:25%}.col-lg-2{width:16.66666667%}.col-lg-1{width:8.33333333%}.col-lg-pull-12{right:100%}.col-lg-pull-11{right:91.66666667%}.col-lg-pull-10{right:83.33333333%}.col-lg-pull-9{right:75%}.col-lg-pull-8{right:66.66666667%}.col-lg-pull-7{right:58.33333333%}.col-lg-pull-6{right:50%}.col-lg-pull-5{right:41.66666667%}.col-lg-pull-4{right:33.33333333%}.col-lg-pull-3{right:25%}.col-lg-pull-2{right:16.66666667%}.col-lg-pull-1{right:8.33333333%}.col-lg-pull-0{right:auto}.col-lg-push-12{left:100%}.col-lg-push-11{left:91.66666667%}.col-lg-push-10{left:83.33333333%}.col-lg-push-9{left:75%}.col-lg-push-8{left:66.66666667%}.col-lg-push-7{left:58.33333333%}.col-lg-push-6{left:50%}.col-lg-push-5{left:41.66666667%}.col-lg-push-4{left:33.33333333%}.col-lg-push-3{left:25%}.col-lg-push-2{left:16.66666667%}.col-lg-push-1{left:8.33333333%}.col-lg-push-0{left:auto}.col-lg-offset-12{margin-left:100%}.col-lg-offset-11{margin-left:91.66666667%}.col-lg-offset-10{margin-left:83.33333333%}.col-lg-offset-9{margin-left:75%}.col-lg-offset-8{margin-left:66.66666667%}.col-lg-offset-7{margin-left:58.33333333%}.col-lg-offset-6{margin-left:50%}.col-lg-offset-5{margin-left:41.66666667%}.col-lg-offset-4{margin-left:33.33333333%}.col-lg-offset-3{margin-left:25%}.col-lg-offset-2{margin-left:16.66666667%}.col-lg-offset-1{margin-left:8.33333333%}.col-lg-offset-0{margin-left:0}}table{background-color:transparent}caption{padding-top:8px;padding-bottom:8px;color:#777;text-align:left}th{text-align:left}.table{width:100%;max-width:100%;margin-bottom:20px}.table>tbody>tr>td,.table>tbody>tr>th,.table>tfoot>tr>td,.table>tfoot>tr>th,.table>thead>tr>td,.table>thead>tr>th{padding:8px;line-height:1.42857143;vertical-align:top;border-top:1px solid #ddd}.table>thead>tr>th{vertical-align:bottom;border-bottom:2px solid #ddd}.table>caption+thead>tr:first-child>td,.table>caption+thead>tr:first-child>th,.table>colgroup+thead>tr:first-child>td,.table>colgroup+thead>tr:first-child>th,.table>thead:first-child>tr:first-child>td,.table>thead:first-child>tr:first-child>th{border-top:0}.table>tbody+tbody{border-top:2px solid #ddd}.table .table{background-color:#fff}.table-condensed>tbody>tr>td,.table-condensed>tbody>tr>th,.table-condensed>tfoot>tr>td,.table-condensed>tfoot>tr>th,.table-condensed>thead>tr>td,.table-condensed>thead>tr>th{padding:5px}.table-bordered{border:1px solid #ddd}.table-bordered>tbody>tr>td,.table-bordered>tbody>tr>th,.table-bordered>tfoot>tr>td,.table-bordered>tfoot>tr>th,.table-bordered>thead>tr>td,.table-bordered>thead>tr>th{border:1px solid #ddd}.table-bordered>thead>tr>td,.table-bordered>thead>tr>th{border-bottom-width:2px}.table-striped>tbody>tr:nth-of-type(odd){background-color:#f9f9f9}.table-hover>tbody>tr:hover{background-color:#f5f5f5}table col[class*=col-]{position:static;display:table-column;float:none}table td[class*=col-],table th[class*=col-]{position:static;display:table-cell;float:none}.table>tbody>tr.active>td,.table>tbody>tr.active>th,.table>tbody>tr>td.active,.table>tbody>tr>th.active,.table>tfoot>tr.active>td,.table>tfoot>tr.active>th,.table>tfoot>tr>td.active,.table>tfoot>tr>th.active,.table>thead>tr.active>td,.table>thead>tr.active>th,.table>thead>tr>td.active,.table>thead>tr>th.active{background-color:#f5f5f5}.table-hover>tbody>tr.active:hover>td,.table-hover>tbody>tr.active:hover>th,.table-hover>tbody>tr:hover>.active,.table-hover>tbody>tr>td.active:hover,.table-hover>tbody>tr>th.active:hover{background-color:#e8e8e8}.table>tbody>tr.success>td,.table>tbody>tr.success>th,.table>tbody>tr>td.success,.table>tbody>tr>th.success,.table>tfoot>tr.success>td,.table>tfoot>tr.success>th,.table>tfoot>tr>td.success,.table>tfoot>tr>th.success,.table>thead>tr.success>td,.table>thead>tr.success>th,.table>thead>tr>td.success,.table>thead>tr>th.success{background-color:#dff0d8}.table-hover>tbody>tr.success:hover>td,.table-hover>tbody>tr.success:hover>th,.table-hover>tbody>tr:hover>.success,.table-hover>tbody>tr>td.success:hover,.table-hover>tbody>tr>th.success:hover{background-color:#d0e9c6}.table>tbody>tr.info>td,.table>tbody>tr.info>th,.table>tbody>tr>td.info,.table>tbody>tr>th.info,.table>tfoot>tr.info>td,.table>tfoot>tr.info>th,.table>tfoot>tr>td.info,.table>tfoot>tr>th.info,.table>thead>tr.info>td,.table>thead>tr.info>th,.table>thead>tr>td.info,.table>thead>tr>th.info{background-color:#d9edf7}.table-hover>tbody>tr.info:hover>td,.table-hover>tbody>tr.info:hover>th,.table-hover>tbody>tr:hover>.info,.table-hover>tbody>tr>td.info:hover,.table-hover>tbody>tr>th.info:hover{background-color:#c4e3f3}.table>tbody>tr.warning>td,.table>tbody>tr.warning>th,.table>tbody>tr>td.warning,.table>tbody>tr>th.warning,.table>tfoot>tr.warning>td,.table>tfoot>tr.warning>th,.table>tfoot>tr>td.warning,.table>tfoot>tr>th.warning,.table>thead>tr.warning>td,.table>thead>tr.warning>th,.table>thead>tr>td.warning,.table>thead>tr>th.warning{background-color:#fcf8e3}.table-hover>tbody>tr.warning:hover>td,.table-hover>tbody>tr.warning:hover>th,.table-hover>tbody>tr:hover>.warning,.table-hover>tbody>tr>td.warning:hover,.table-hover>tbody>tr>th.warning:hover{background-color:#faf2cc}.table>tbody>tr.danger>td,.table>tbody>tr.danger>th,.table>tbody>tr>td.danger,.table>tbody>tr>th.danger,.table>tfoot>tr.danger>td,.table>tfoot>tr.danger>th,.table>tfoot>tr>td.danger,.table>tfoot>tr>th.danger,.table>thead>tr.danger>td,.table>thead>tr.danger>th,.table>thead>tr>td.danger,.table>thead>tr>th.danger{background-color:#f2dede}.table-hover>tbody>tr.danger:hover>td,.table-hover>tbody>tr.danger:hover>th,.table-hover>tbody>tr:hover>.danger,.table-hover>tbody>tr>td.danger:hover,.table-hover>tbody>tr>th.danger:hover{background-color:#ebcccc}.table-responsive{min-height:.01%;overflow-x:auto}@media screen and (max-width:767px){.table-responsive{width:100%;margin-bottom:15px;overflow-y:hidden;-ms-overflow-style:-ms-autohiding-scrollbar;border:1px solid #ddd}.table-responsive>.table{margin-bottom:0}.table-responsive>.table>tbody>tr>td,.table-responsive>.table>tbody>tr>th,.table-responsive>.table>tfoot>tr>td,.table-responsive>.table>tfoot>tr>th,.table-responsive>.table>thead>tr>td,.table-responsive>.table>thead>tr>th{white-space:nowrap}.table-responsive>.table-bordered{border:0}.table-responsive>.table-bordered>tbody>tr>td:first-child,.table-responsive>.table-bordered>tbody>tr>th:first-child,.table-responsive>.table-bordered>tfoot>tr>td:first-child,.table-responsive>.table-bordered>tfoot>tr>th:first-child,.table-responsive>.table-bordered>thead>tr>td:first-child,.table-responsive>.table-bordered>thead>tr>th:first-child{border-left:0}.table-responsive>.table-bordered>tbody>tr>td:last-child,.table-responsive>.table-bordered>tbody>tr>th:last-child,.table-responsive>.table-bordered>tfoot>tr>td:last-child,.table-responsive>.table-bordered>tfoot>tr>th:last-child,.table-responsive>.table-bordered>thead>tr>td:last-child,.table-responsive>.table-bordered>thead>tr>th:last-child{border-right:0}.table-responsive>.table-bordered>tbody>tr:last-child>td,.table-responsive>.table-bordered>tbody>tr:last-child>th,.table-responsive>.table-bordered>tfoot>tr:last-child>td,.table-responsive>.table-bordered>tfoot>tr:last-child>th{border-bottom:0}}fieldset{min-width:0;padding:0;margin:0;border:0}legend{display:block;width:100%;padding:0;margin-bottom:20px;font-size:21px;line-height:inherit;color:#333;border:0;border-bottom:1px solid #e5e5e5}label{display:inline-block;max-width:100%;margin-bottom:5px;font-weight:700}input[type=search]{-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}input[type=checkbox],input[type=radio]{margin:4px 0 0;margin-top:1px\9;line-height:normal}input[type=file]{display:block}input[type=range]{display:block;width:100%}select[multiple],select[size]{height:auto}input[type=file]:focus,input[type=checkbox]:focus,input[type=radio]:focus{outline:5px auto -webkit-focus-ring-color;outline-offset:-2px}output{display:block;padding-top:7px;font-size:14px;line-height:1.42857143;color:#555}.form-control{display:block;width:100%;height:34px;padding:6px 12px;font-size:14px;line-height:1.42857143;color:#555;background-color:#fff;background-image:none;border:1px solid #ccc;border-radius:4px;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,.075);box-shadow:inset 0 1px 1px rgba(0,0,0,.075);-webkit-transition:border-color ease-in-out .15s,-webkit-box-shadow ease-in-out .15s;-o-transition:border-color ease-in-out .15s,box-shadow ease-in-out .15s;transition:border-color ease-in-out .15s,box-shadow ease-in-out .15s}.form-control:focus{border-color:#66afe9;outline:0;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,.075),0 0 8px rgba(102,175,233,.6);box-shadow:inset 0 1px 1px rgba(0,0,0,.075),0 0 8px rgba(102,175,233,.6)}.form-control::-moz-placeholder{color:#999;opacity:1}.form-control:-ms-input-placeholder{color:#999}.form-control::-webkit-input-placeholder{color:#999}.form-control::-ms-expand{background-color:transparent;border:0}.form-control[disabled],.form-control[readonly],fieldset[disabled] .form-control{background-color:#eee;opacity:1}.form-control[disabled],fieldset[disabled] .form-control{cursor:not-allowed}textarea.form-control{height:auto}input[type=search]{-webkit-appearance:none}@media screen and (-webkit-min-device-pixel-ratio:0){input[type=date].form-control,input[type=time].form-control,input[type=datetime-local].form-control,input[type=month].form-control{line-height:34px}.input-group-sm input[type=date],.input-group-sm input[type=time],.input-group-sm input[type=datetime-local],.input-group-sm input[type=month],input[type=date].input-sm,input[type=time].input-sm,input[type=datetime-local].input-sm,input[type=month].input-sm{line-height:30px}.input-group-lg input[type=date],.input-group-lg input[type=time],.input-group-lg input[type=datetime-local],.input-group-lg input[type=month],input[type=date].input-lg,input[type=time].input-lg,input[type=datetime-local].input-lg,input[type=month].input-lg{line-height:46px}}.form-group{margin-bottom:15px}.checkbox,.radio{position:relative;display:block;margin-top:10px;margin-bottom:10px}.checkbox label,.radio label{min-height:20px;padding-left:20px;margin-bottom:0;font-weight:400;cursor:pointer}.checkbox input[type=checkbox],.checkbox-inline input[type=checkbox],.radio input[type=radio],.radio-inline input[type=radio]{position:absolute;margin-top:4px\9;margin-left:-20px}.checkbox+.checkbox,.radio+.radio{margin-top:-5px}.checkbox-inline,.radio-inline{position:relative;display:inline-block;padding-left:20px;margin-bottom:0;font-weight:400;vertical-align:middle;cursor:pointer}.checkbox-inline+.checkbox-inline,.radio-inline+.radio-inline{margin-top:0;margin-left:10px}fieldset[disabled] input[type=checkbox],fieldset[disabled] input[type=radio],input[type=checkbox].disabled,input[type=checkbox][disabled],input[type=radio].disabled,input[type=radio][disabled]{cursor:not-allowed}.checkbox-inline.disabled,.radio-inline.disabled,fieldset[disabled] .checkbox-inline,fieldset[disabled] .radio-inline{cursor:not-allowed}.checkbox.disabled label,.radio.disabled label,fieldset[disabled] .checkbox label,fieldset[disabled] .radio label{cursor:not-allowed}.form-control-static{min-height:34px;padding-top:7px;padding-bottom:7px;margin-bottom:0}.form-control-static.input-lg,.form-control-static.input-sm{padding-right:0;padding-left:0}.input-sm{height:30px;padding:5px 10px;font-size:12px;line-height:1.5;border-radius:3px}select.input-sm{height:30px;line-height:30px}select[multiple].input-sm,textarea.input-sm{height:auto}.form-group-sm .form-control{height:30px;padding:5px 10px;font-size:12px;line-height:1.5;border-radius:3px}.form-group-sm select.form-control{height:30px;line-height:30px}.form-group-sm select[multiple].form-control,.form-group-sm textarea.form-control{height:auto}.form-group-sm .form-control-static{height:30px;min-height:32px;padding:6px 10px;font-size:12px;line-height:1.5}.input-lg{height:46px;padding:10px 16px;font-size:18px;line-height:1.3333333;border-radius:6px}select.input-lg{height:46px;line-height:46px}select[multiple].input-lg,textarea.input-lg{height:auto}.form-group-lg .form-control{height:46px;padding:10px 16px;font-size:18px;line-height:1.3333333;border-radius:6px}.form-group-lg select.form-control{height:46px;line-height:46px}.form-group-lg select[multiple].form-control,.form-group-lg textarea.form-control{height:auto}.form-group-lg .form-control-static{height:46px;min-height:38px;padding:11px 16px;font-size:18px;line-height:1.3333333}.has-feedback{position:relative}.has-feedback .form-control{padding-right:42.5px}.form-control-feedback{position:absolute;top:0;right:0;z-index:2;display:block;width:34px;height:34px;line-height:34px;text-align:center;pointer-events:none}.form-group-lg .form-control+.form-control-feedback,.input-group-lg+.form-control-feedback,.input-lg+.form-control-feedback{width:46px;height:46px;line-height:46px}.form-group-sm .form-control+.form-control-feedback,.input-group-sm+.form-control-feedback,.input-sm+.form-control-feedback{width:30px;height:30px;line-height:30px}.has-success .checkbox,.has-success .checkbox-inline,.has-success .control-label,.has-success .help-block,.has-success .radio,.has-success .radio-inline,.has-success.checkbox label,.has-success.checkbox-inline label,.has-success.radio label,.has-success.radio-inline label{color:#3c763d}.has-success .form-control{border-color:#3c763d;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,.075);box-shadow:inset 0 1px 1px rgba(0,0,0,.075)}.has-success .form-control:focus{border-color:#2b542c;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,.075),0 0 6px #67b168;box-shadow:inset 0 1px 1px rgba(0,0,0,.075),0 0 6px #67b168}.has-success .input-group-addon{color:#3c763d;background-color:#dff0d8;border-color:#3c763d}.has-success .form-control-feedback{color:#3c763d}.has-warning .checkbox,.has-warning .checkbox-inline,.has-warning .control-label,.has-warning .help-block,.has-warning .radio,.has-warning .radio-inline,.has-warning.checkbox label,.has-warning.checkbox-inline label,.has-warning.radio label,.has-warning.radio-inline label{color:#8a6d3b}.has-warning .form-control{border-color:#8a6d3b;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,.075);box-shadow:inset 0 1px 1px rgba(0,0,0,.075)}.has-warning .form-control:focus{border-color:#66512c;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,.075),0 0 6px #c0a16b;box-shadow:inset 0 1px 1px rgba(0,0,0,.075),0 0 6px #c0a16b}.has-warning .input-group-addon{color:#8a6d3b;background-color:#fcf8e3;border-color:#8a6d3b}.has-warning .form-control-feedback{color:#8a6d3b}.has-error .checkbox,.has-error .checkbox-inline,.has-error .control-label,.has-error .help-block,.has-error .radio,.has-error .radio-inline,.has-error.checkbox label,.has-error.checkbox-inline label,.has-error.radio label,.has-error.radio-inline label{color:#a94442}.has-error .form-control{border-color:#a94442;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,.075);box-shadow:inset 0 1px 1px rgba(0,0,0,.075)}.has-error .form-control:focus{border-color:#843534;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,.075),0 0 6px #ce8483;box-shadow:inset 0 1px 1px rgba(0,0,0,.075),0 0 6px #ce8483}.has-error .input-group-addon{color:#a94442;background-color:#f2dede;border-color:#a94442}.has-error .form-control-feedback{color:#a94442}.has-feedback label~.form-control-feedback{top:25px}.has-feedback label.sr-only~.form-control-feedback{top:0}.help-block{display:block;margin-top:5px;margin-bottom:10px;color:#737373}@media (min-width:768px){.form-inline .form-group{display:inline-block;margin-bottom:0;vertical-align:middle}.form-inline .form-control{display:inline-block;width:auto;vertical-align:middle}.form-inline .form-control-static{display:inline-block}.form-inline .input-group{display:inline-table;vertical-align:middle}.form-inline .input-group .form-control,.form-inline .input-group .input-group-addon,.form-inline .input-group .input-group-btn{width:auto}.form-inline .input-group>.form-control{width:100%}.form-inline .control-label{margin-bottom:0;vertical-align:middle}.form-inline .checkbox,.form-inline .radio{display:inline-block;margin-top:0;margin-bottom:0;vertical-align:middle}.form-inline .checkbox label,.form-inline .radio label{padding-left:0}.form-inline .checkbox input[type=checkbox],.form-inline .radio input[type=radio]{position:relative;margin-left:0}.form-inline .has-feedback .form-control-feedback{top:0}}.form-horizontal .checkbox,.form-horizontal .checkbox-inline,.form-horizontal .radio,.form-horizontal .radio-inline{padding-top:7px;margin-top:0;margin-bottom:0}.form-horizontal .checkbox,.form-horizontal .radio{min-height:27px}.form-horizontal .form-group{margin-right:-15px;margin-left:-15px}@media (min-width:768px){.form-horizontal .control-label{padding-top:7px;margin-bottom:0;text-align:right}}.form-horizontal .has-feedback .form-control-feedback{right:15px}@media (min-width:768px){.form-horizontal .form-group-lg .control-label{padding-top:11px;font-size:18px}}@media (min-width:768px){.form-horizontal .form-group-sm .control-label{padding-top:6px;font-size:12px}}.btn{display:inline-block;padding:6px 12px;margin-bottom:0;font-size:14px;font-weight:400;line-height:1.42857143;text-align:center;white-space:nowrap;vertical-align:middle;-ms-touch-action:manipulation;touch-action:manipulation;cursor:pointer;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;background-image:none;border:1px solid transparent;border-radius:4px}.btn.active.focus,.btn.active:focus,.btn.focus,.btn:active.focus,.btn:active:focus,.btn:focus{outline:5px auto -webkit-focus-ring-color;outline-offset:-2px}.btn.focus,.btn:focus,.btn:hover{color:#333;text-decoration:none}.btn.active,.btn:active{background-image:none;outline:0;-webkit-box-shadow:inset 0 3px 5px rgba(0,0,0,.125);box-shadow:inset 0 3px 5px rgba(0,0,0,.125)}.btn.disabled,.btn[disabled],fieldset[disabled] .btn{cursor:not-allowed;filter:alpha(opacity=65);-webkit-box-shadow:none;box-shadow:none;opacity:.65}a.btn.disabled,fieldset[disabled] a.btn{pointer-events:none}.btn-default{color:#333;background-color:#fff;border-color:#ccc}.btn-default.focus,.btn-default:focus{color:#333;background-color:#e6e6e6;border-color:#8c8c8c}.btn-default:hover{color:#333;background-color:#e6e6e6;border-color:#adadad}.btn-default.active,.btn-default:active,.open>.dropdown-toggle.btn-default{color:#333;background-color:#e6e6e6;border-color:#adadad}.btn-default.active.focus,.btn-default.active:focus,.btn-default.active:hover,.btn-default:active.focus,.btn-default:active:focus,.btn-default:active:hover,.open>.dropdown-toggle.btn-default.focus,.open>.dropdown-toggle.btn-default:focus,.open>.dropdown-toggle.btn-default:hover{color:#333;background-color:#d4d4d4;border-color:#8c8c8c}.btn-default.active,.btn-default:active,.open>.dropdown-toggle.btn-default{background-image:none}.btn-default.disabled.focus,.btn-default.disabled:focus,.btn-default.disabled:hover,.btn-default[disabled].focus,.btn-default[disabled]:focus,.btn-default[disabled]:hover,fieldset[disabled] .btn-default.focus,fieldset[disabled] .btn-default:focus,fieldset[disabled] .btn-default:hover{background-color:#fff;border-color:#ccc}.btn-default .badge{color:#fff;background-color:#333}.btn-primary{color:#fff;background-color:#337ab7;border-color:#2e6da4}.btn-primary.focus,.btn-primary:focus{color:#fff;background-color:#286090;border-color:#122b40}.btn-primary:hover{color:#fff;background-color:#286090;border-color:#204d74}.btn-primary.active,.btn-primary:active,.open>.dropdown-toggle.btn-primary{color:#fff;background-color:#286090;border-color:#204d74}.btn-primary.active.focus,.btn-primary.active:focus,.btn-primary.active:hover,.btn-primary:active.focus,.btn-primary:active:focus,.btn-primary:active:hover,.open>.dropdown-toggle.btn-primary.focus,.open>.dropdown-toggle.btn-primary:focus,.open>.dropdown-toggle.btn-primary:hover{color:#fff;background-color:#204d74;border-color:#122b40}.btn-primary.active,.btn-primary:active,.open>.dropdown-toggle.btn-primary{background-image:none}.btn-primary.disabled.focus,.btn-primary.disabled:focus,.btn-primary.disabled:hover,.btn-primary[disabled].focus,.btn-primary[disabled]:focus,.btn-primary[disabled]:hover,fieldset[disabled] .btn-primary.focus,fieldset[disabled] .btn-primary:focus,fieldset[disabled] .btn-primary:hover{background-color:#337ab7;border-color:#2e6da4}.btn-primary .badge{color:#337ab7;background-color:#fff}.btn-success{color:#fff;background-color:#5cb85c;border-color:#4cae4c}.btn-success.focus,.btn-success:focus{color:#fff;background-color:#449d44;border-color:#255625}.btn-success:hover{color:#fff;background-color:#449d44;border-color:#398439}.btn-success.active,.btn-success:active,.open>.dropdown-toggle.btn-success{color:#fff;background-color:#449d44;border-color:#398439}.btn-success.active.focus,.btn-success.active:focus,.btn-success.active:hover,.btn-success:active.focus,.btn-success:active:focus,.btn-success:active:hover,.open>.dropdown-toggle.btn-success.focus,.open>.dropdown-toggle.btn-success:focus,.open>.dropdown-toggle.btn-success:hover{color:#fff;background-color:#398439;border-color:#255625}.btn-success.active,.btn-success:active,.open>.dropdown-toggle.btn-success{background-image:none}.btn-success.disabled.focus,.btn-success.disabled:focus,.btn-success.disabled:hover,.btn-success[disabled].focus,.btn-success[disabled]:focus,.btn-success[disabled]:hover,fieldset[disabled] .btn-success.focus,fieldset[disabled] .btn-success:focus,fieldset[disabled] .btn-success:hover{background-color:#5cb85c;border-color:#4cae4c}.btn-success .badge{color:#5cb85c;background-color:#fff}.btn-info{color:#fff;background-color:#5bc0de;border-color:#46b8da}.btn-info.focus,.btn-info:focus{color:#fff;background-color:#31b0d5;border-color:#1b6d85}.btn-info:hover{color:#fff;background-color:#31b0d5;border-color:#269abc}.btn-info.active,.btn-info:active,.open>.dropdown-toggle.btn-info{color:#fff;background-color:#31b0d5;border-color:#269abc}.btn-info.active.focus,.btn-info.active:focus,.btn-info.active:hover,.btn-info:active.focus,.btn-info:active:focus,.btn-info:active:hover,.open>.dropdown-toggle.btn-info.focus,.open>.dropdown-toggle.btn-info:focus,.open>.dropdown-toggle.btn-info:hover{color:#fff;background-color:#269abc;border-color:#1b6d85}.btn-info.active,.btn-info:active,.open>.dropdown-toggle.btn-info{background-image:none}.btn-info.disabled.focus,.btn-info.disabled:focus,.btn-info.disabled:hover,.btn-info[disabled].focus,.btn-info[disabled]:focus,.btn-info[disabled]:hover,fieldset[disabled] .btn-info.focus,fieldset[disabled] .btn-info:focus,fieldset[disabled] .btn-info:hover{background-color:#5bc0de;border-color:#46b8da}.btn-info .badge{color:#5bc0de;background-color:#fff}.btn-warning{color:#fff;background-color:#f0ad4e;border-color:#eea236}.btn-warning.focus,.btn-warning:focus{color:#fff;background-color:#ec971f;border-color:#985f0d}.btn-warning:hover{color:#fff;background-color:#ec971f;border-color:#d58512}.btn-warning.active,.btn-warning:active,.open>.dropdown-toggle.btn-warning{color:#fff;background-color:#ec971f;border-color:#d58512}.btn-warning.active.focus,.btn-warning.active:focus,.btn-warning.active:hover,.btn-warning:active.focus,.btn-warning:active:focus,.btn-warning:active:hover,.open>.dropdown-toggle.btn-warning.focus,.open>.dropdown-toggle.btn-warning:focus,.open>.dropdown-toggle.btn-warning:hover{color:#fff;background-color:#d58512;border-color:#985f0d}.btn-warning.active,.btn-warning:active,.open>.dropdown-toggle.btn-warning{background-image:none}.btn-warning.disabled.focus,.btn-warning.disabled:focus,.btn-warning.disabled:hover,.btn-warning[disabled].focus,.btn-warning[disabled]:focus,.btn-warning[disabled]:hover,fieldset[disabled] .btn-warning.focus,fieldset[disabled] .btn-warning:focus,fieldset[disabled] .btn-warning:hover{background-color:#f0ad4e;border-color:#eea236}.btn-warning .badge{color:#f0ad4e;background-color:#fff}.btn-danger{color:#fff;background-color:#d9534f;border-color:#d43f3a}.btn-danger.focus,.btn-danger:focus{color:#fff;background-color:#c9302c;border-color:#761c19}.btn-danger:hover{color:#fff;background-color:#c9302c;border-color:#ac2925}.btn-danger.active,.btn-danger:active,.open>.dropdown-toggle.btn-danger{color:#fff;background-color:#c9302c;border-color:#ac2925}.btn-danger.active.focus,.btn-danger.active:focus,.btn-danger.active:hover,.btn-danger:active.focus,.btn-danger:active:focus,.btn-danger:active:hover,.open>.dropdown-toggle.btn-danger.focus,.open>.dropdown-toggle.btn-danger:focus,.open>.dropdown-toggle.btn-danger:hover{color:#fff;background-color:#ac2925;border-color:#761c19}.btn-danger.active,.btn-danger:active,.open>.dropdown-toggle.btn-danger{background-image:none}.btn-danger.disabled.focus,.btn-danger.disabled:focus,.btn-danger.disabled:hover,.btn-danger[disabled].focus,.btn-danger[disabled]:focus,.btn-danger[disabled]:hover,fieldset[disabled] .btn-danger.focus,fieldset[disabled] .btn-danger:focus,fieldset[disabled] .btn-danger:hover{background-color:#d9534f;border-color:#d43f3a}.btn-danger .badge{color:#d9534f;background-color:#fff}.btn-link{font-weight:400;color:#337ab7;border-radius:0}.btn-link,.btn-link.active,.btn-link:active,.btn-link[disabled],fieldset[disabled] .btn-link{background-color:transparent;-webkit-box-shadow:none;box-shadow:none}.btn-link,.btn-link:active,.btn-link:focus,.btn-link:hover{border-color:transparent}.btn-link:focus,.btn-link:hover{color:#23527c;text-decoration:underline;background-color:transparent}.btn-link[disabled]:focus,.btn-link[disabled]:hover,fieldset[disabled] .btn-link:focus,fieldset[disabled] .btn-link:hover{color:#777;text-decoration:none}.btn-group-lg>.btn,.btn-lg{padding:10px 16px;font-size:18px;line-height:1.3333333;border-radius:6px}.btn-group-sm>.btn,.btn-sm{padding:5px 10px;font-size:12px;line-height:1.5;border-radius:3px}.btn-group-xs>.btn,.btn-xs{padding:1px 5px;font-size:12px;line-height:1.5;border-radius:3px}.btn-block{display:block;width:100%}.btn-block+.btn-block{margin-top:5px}input[type=button].btn-block,input[type=reset].btn-block,input[type=submit].btn-block{width:100%}.fade{opacity:0;-webkit-transition:opacity .15s linear;-o-transition:opacity .15s linear;transition:opacity .15s linear}.fade.in{opacity:1}.collapse{display:none}.collapse.in{display:block}tr.collapse.in{display:table-row}tbody.collapse.in{display:table-row-group}.collapsing{position:relative;height:0;overflow:hidden;-webkit-transition-timing-function:ease;-o-transition-timing-function:ease;transition-timing-function:ease;-webkit-transition-duration:.35s;-o-transition-duration:.35s;transition-duration:.35s;-webkit-transition-property:height,visibility;-o-transition-property:height,visibility;transition-property:height,visibility}.caret{display:inline-block;width:0;height:0;margin-left:2px;vertical-align:middle;border-top:4px dashed;border-top:4px solid\9;border-right:4px solid transparent;border-left:4px solid transparent}.dropdown,.dropup{position:relative}.dropdown-toggle:focus{outline:0}.dropdown-menu{position:absolute;top:100%;left:0;z-index:1000;display:none;float:left;min-width:160px;padding:5px 0;margin:2px 0 0;font-size:14px;text-align:left;list-style:none;background-color:#fff;-webkit-background-clip:padding-box;background-clip:padding-box;border:1px solid #ccc;border:1px solid rgba(0,0,0,.15);border-radius:4px;-webkit-box-shadow:0 6px 12px rgba(0,0,0,.175);box-shadow:0 6px 12px rgba(0,0,0,.175)}.dropdown-menu.pull-right{right:0;left:auto}.dropdown-menu .divider{height:1px;margin:9px 0;overflow:hidden;background-color:#e5e5e5}.dropdown-menu>li>a{display:block;padding:3px 20px;clear:both;font-weight:400;line-height:1.42857143;color:#333;white-space:nowrap}.dropdown-menu>li>a:focus,.dropdown-menu>li>a:hover{color:#262626;text-decoration:none;background-color:#f5f5f5}.dropdown-menu>.active>a,.dropdown-menu>.active>a:focus,.dropdown-menu>.active>a:hover{color:#fff;text-decoration:none;background-color:#337ab7;outline:0}.dropdown-menu>.disabled>a,.dropdown-menu>.disabled>a:focus,.dropdown-menu>.disabled>a:hover{color:#777}.dropdown-menu>.disabled>a:focus,.dropdown-menu>.disabled>a:hover{text-decoration:none;cursor:not-allowed;background-color:transparent;background-image:none;filter:progid:DXImageTransform.Microsoft.gradient(enabled=false)}.open>.dropdown-menu{display:block}.open>a{outline:0}.dropdown-menu-right{right:0;left:auto}.dropdown-menu-left{right:auto;left:0}.dropdown-header{display:block;padding:3px 20px;font-size:12px;line-height:1.42857143;color:#777;white-space:nowrap}.dropdown-backdrop{position:fixed;top:0;right:0;bottom:0;left:0;z-index:990}.pull-right>.dropdown-menu{right:0;left:auto}.dropup .caret,.navbar-fixed-bottom .dropdown .caret{content:"";border-top:0;border-bottom:4px dashed;border-bottom:4px solid\9}.dropup .dropdown-menu,.navbar-fixed-bottom .dropdown .dropdown-menu{top:auto;bottom:100%;margin-bottom:2px}@media (min-width:768px){.navbar-right .dropdown-menu{right:0;left:auto}.navbar-right .dropdown-menu-left{right:auto;left:0}}.btn-group,.btn-group-vertical{position:relative;display:inline-block;vertical-align:middle}.btn-group-vertical>.btn,.btn-group>.btn{position:relative;float:left}.btn-group-vertical>.btn.active,.btn-group-vertical>.btn:active,.btn-group-vertical>.btn:focus,.btn-group-vertical>.btn:hover,.btn-group>.btn.active,.btn-group>.btn:active,.btn-group>.btn:focus,.btn-group>.btn:hover{z-index:2}.btn-group .btn+.btn,.btn-group .btn+.btn-group,.btn-group .btn-group+.btn,.btn-group .btn-group+.btn-group{margin-left:-1px}.btn-toolbar{margin-left:-5px}.btn-toolbar .btn,.btn-toolbar .btn-group,.btn-toolbar .input-group{float:left}.btn-toolbar>.btn,.btn-toolbar>.btn-group,.btn-toolbar>.input-group{margin-left:5px}.btn-group>.btn:not(:first-child):not(:last-child):not(.dropdown-toggle){border-radius:0}.btn-group>.btn:first-child{margin-left:0}.btn-group>.btn:first-child:not(:last-child):not(.dropdown-toggle){border-top-right-radius:0;border-bottom-right-radius:0}.btn-group>.btn:last-child:not(:first-child),.btn-group>.dropdown-toggle:not(:first-child){border-top-left-radius:0;border-bottom-left-radius:0}.btn-group>.btn-group{float:left}.btn-group>.btn-group:not(:first-child):not(:last-child)>.btn{border-radius:0}.btn-group>.btn-group:first-child:not(:last-child)>.btn:last-child,.btn-group>.btn-group:first-child:not(:last-child)>.dropdown-toggle{border-top-right-radius:0;border-bottom-right-radius:0}.btn-group>.btn-group:last-child:not(:first-child)>.btn:first-child{border-top-left-radius:0;border-bottom-left-radius:0}.btn-group .dropdown-toggle:active,.btn-group.open .dropdown-toggle{outline:0}.btn-group>.btn+.dropdown-toggle{padding-right:8px;padding-left:8px}.btn-group>.btn-lg+.dropdown-toggle{padding-right:12px;padding-left:12px}.btn-group.open .dropdown-toggle{-webkit-box-shadow:inset 0 3px 5px rgba(0,0,0,.125);box-shadow:inset 0 3px 5px rgba(0,0,0,.125)}.btn-group.open .dropdown-toggle.btn-link{-webkit-box-shadow:none;box-shadow:none}.btn .caret{margin-left:0}.btn-lg .caret{border-width:5px 5px 0;border-bottom-width:0}.dropup .btn-lg .caret{border-width:0 5px 5px}.btn-group-vertical>.btn,.btn-group-vertical>.btn-group,.btn-group-vertical>.btn-group>.btn{display:block;float:none;width:100%;max-width:100%}.btn-group-vertical>.btn-group>.btn{float:none}.btn-group-vertical>.btn+.btn,.btn-group-vertical>.btn+.btn-group,.btn-group-vertical>.btn-group+.btn,.btn-group-vertical>.btn-group+.btn-group{margin-top:-1px;margin-left:0}.btn-group-vertical>.btn:not(:first-child):not(:last-child){border-radius:0}.btn-group-vertical>.btn:first-child:not(:last-child){border-top-left-radius:4px;border-top-right-radius:4px;border-bottom-right-radius:0;border-bottom-left-radius:0}.btn-group-vertical>.btn:last-child:not(:first-child){border-top-left-radius:0;border-top-right-radius:0;border-bottom-right-radius:4px;border-bottom-left-radius:4px}.btn-group-vertical>.btn-group:not(:first-child):not(:last-child)>.btn{border-radius:0}.btn-group-vertical>.btn-group:first-child:not(:last-child)>.btn:last-child,.btn-group-vertical>.btn-group:first-child:not(:last-child)>.dropdown-toggle{border-bottom-right-radius:0;border-bottom-left-radius:0}.btn-group-vertical>.btn-group:last-child:not(:first-child)>.btn:first-child{border-top-left-radius:0;border-top-right-radius:0}.btn-group-justified{display:table;width:100%;table-layout:fixed;border-collapse:separate}.btn-group-justified>.btn,.btn-group-justified>.btn-group{display:table-cell;float:none;width:1%}.btn-group-justified>.btn-group .btn{width:100%}.btn-group-justified>.btn-group .dropdown-menu{left:auto}[data-toggle=buttons]>.btn input[type=checkbox],[data-toggle=buttons]>.btn input[type=radio],[data-toggle=buttons]>.btn-group>.btn input[type=checkbox],[data-toggle=buttons]>.btn-group>.btn input[type=radio]{position:absolute;clip:rect(0,0,0,0);pointer-events:none}.input-group{position:relative;display:table;border-collapse:separate}.input-group[class*=col-]{float:none;padding-right:0;padding-left:0}.input-group .form-control{position:relative;z-index:2;float:left;width:100%;margin-bottom:0}.input-group .form-control:focus{z-index:3}.input-group-lg>.form-control,.input-group-lg>.input-group-addon,.input-group-lg>.input-group-btn>.btn{height:46px;padding:10px 16px;font-size:18px;line-height:1.3333333;border-radius:6px}select.input-group-lg>.form-control,select.input-group-lg>.input-group-addon,select.input-group-lg>.input-group-btn>.btn{height:46px;line-height:46px}select[multiple].input-group-lg>.form-control,select[multiple].input-group-lg>.input-group-addon,select[multiple].input-group-lg>.input-group-btn>.btn,textarea.input-group-lg>.form-control,textarea.input-group-lg>.input-group-addon,textarea.input-group-lg>.input-group-btn>.btn{height:auto}.input-group-sm>.form-control,.input-group-sm>.input-group-addon,.input-group-sm>.input-group-btn>.btn{height:30px;padding:5px 10px;font-size:12px;line-height:1.5;border-radius:3px}select.input-group-sm>.form-control,select.input-group-sm>.input-group-addon,select.input-group-sm>.input-group-btn>.btn{height:30px;line-height:30px}select[multiple].input-group-sm>.form-control,select[multiple].input-group-sm>.input-group-addon,select[multiple].input-group-sm>.input-group-btn>.btn,textarea.input-group-sm>.form-control,textarea.input-group-sm>.input-group-addon,textarea.input-group-sm>.input-group-btn>.btn{height:auto}.input-group .form-control,.input-group-addon,.input-group-btn{display:table-cell}.input-group .form-control:not(:first-child):not(:last-child),.input-group-addon:not(:first-child):not(:last-child),.input-group-btn:not(:first-child):not(:last-child){border-radius:0}.input-group-addon,.input-group-btn{width:1%;white-space:nowrap;vertical-align:middle}.input-group-addon{padding:6px 12px;font-size:14px;font-weight:400;line-height:1;color:#555;text-align:center;background-color:#eee;border:1px solid #ccc;border-radius:4px}.input-group-addon.input-sm{padding:5px 10px;font-size:12px;border-radius:3px}.input-group-addon.input-lg{padding:10px 16px;font-size:18px;border-radius:6px}.input-group-addon input[type=checkbox],.input-group-addon input[type=radio]{margin-top:0}.input-group .form-control:first-child,.input-group-addon:first-child,.input-group-btn:first-child>.btn,.input-group-btn:first-child>.btn-group>.btn,.input-group-btn:first-child>.dropdown-toggle,.input-group-btn:last-child>.btn-group:not(:last-child)>.btn,.input-group-btn:last-child>.btn:not(:last-child):not(.dropdown-toggle){border-top-right-radius:0;border-bottom-right-radius:0}.input-group-addon:first-child{border-right:0}.input-group .form-control:last-child,.input-group-addon:last-child,.input-group-btn:first-child>.btn-group:not(:first-child)>.btn,.input-group-btn:first-child>.btn:not(:first-child),.input-group-btn:last-child>.btn,.input-group-btn:last-child>.btn-group>.btn,.input-group-btn:last-child>.dropdown-toggle{border-top-left-radius:0;border-bottom-left-radius:0}.input-group-addon:last-child{border-left:0}.input-group-btn{position:relative;font-size:0;white-space:nowrap}.input-group-btn>.btn{position:relative}.input-group-btn>.btn+.btn{margin-left:-1px}.input-group-btn>.btn:active,.input-group-btn>.btn:focus,.input-group-btn>.btn:hover{z-index:2}.input-group-btn:first-child>.btn,.input-group-btn:first-child>.btn-group{margin-right:-1px}.input-group-btn:last-child>.btn,.input-group-btn:last-child>.btn-group{z-index:2;margin-left:-1px}.nav{padding-left:0;margin-bottom:0;list-style:none}.nav>li{position:relative;display:block}.nav>li>a{position:relative;display:block;padding:10px 15px}.nav>li>a:focus,.nav>li>a:hover{text-decoration:none;background-color:#eee}.nav>li.disabled>a{color:#777}.nav>li.disabled>a:focus,.nav>li.disabled>a:hover{color:#777;text-decoration:none;cursor:not-allowed;background-color:transparent}.nav .open>a,.nav .open>a:focus,.nav .open>a:hover{background-color:#eee;border-color:#337ab7}.nav .nav-divider{height:1px;margin:9px 0;overflow:hidden;background-color:#e5e5e5}.nav>li>a>img{max-width:none}.nav-tabs{border-bottom:1px solid #ddd}.nav-tabs>li{float:left;margin-bottom:-1px}.nav-tabs>li>a{margin-right:2px;line-height:1.42857143;border:1px solid transparent;border-radius:4px 4px 0 0}.nav-tabs>li>a:hover{border-color:#eee #eee #ddd}.nav-tabs>li.active>a,.nav-tabs>li.active>a:focus,.nav-tabs>li.active>a:hover{color:#555;cursor:default;background-color:#fff;border:1px solid #ddd;border-bottom-color:transparent}.nav-tabs.nav-justified{width:100%;border-bottom:0}.nav-tabs.nav-justified>li{float:none}.nav-tabs.nav-justified>li>a{margin-bottom:5px;text-align:center}.nav-tabs.nav-justified>.dropdown .dropdown-menu{top:auto;left:auto}@media (min-width:768px){.nav-tabs.nav-justified>li{display:table-cell;width:1%}.nav-tabs.nav-justified>li>a{margin-bottom:0}}.nav-tabs.nav-justified>li>a{margin-right:0;border-radius:4px}.nav-tabs.nav-justified>.active>a,.nav-tabs.nav-justified>.active>a:focus,.nav-tabs.nav-justified>.active>a:hover{border:1px solid #ddd}@media (min-width:768px){.nav-tabs.nav-justified>li>a{border-bottom:1px solid #ddd;border-radius:4px 4px 0 0}.nav-tabs.nav-justified>.active>a,.nav-tabs.nav-justified>.active>a:focus,.nav-tabs.nav-justified>.active>a:hover{border-bottom-color:#fff}}.nav-pills>li{float:left}.nav-pills>li>a{border-radius:4px}.nav-pills>li+li{margin-left:2px}.nav-pills>li.active>a,.nav-pills>li.active>a:focus,.nav-pills>li.active>a:hover{color:#fff;background-color:#337ab7}.nav-stacked>li{float:none}.nav-stacked>li+li{margin-top:2px;margin-left:0}.nav-justified{width:100%}.nav-justified>li{float:none}.nav-justified>li>a{margin-bottom:5px;text-align:center}.nav-justified>.dropdown .dropdown-menu{top:auto;left:auto}@media (min-width:768px){.nav-justified>li{display:table-cell;width:1%}.nav-justified>li>a{margin-bottom:0}}.nav-tabs-justified{border-bottom:0}.nav-tabs-justified>li>a{margin-right:0;border-radius:4px}.nav-tabs-justified>.active>a,.nav-tabs-justified>.active>a:focus,.nav-tabs-justified>.active>a:hover{border:1px solid #ddd}@media (min-width:768px){.nav-tabs-justified>li>a{border-bottom:1px solid #ddd;border-radius:4px 4px 0 0}.nav-tabs-justified>.active>a,.nav-tabs-justified>.active>a:focus,.nav-tabs-justified>.active>a:hover{border-bottom-color:#fff}}.tab-content>.tab-pane{display:none}.tab-content>.active{display:block}.nav-tabs .dropdown-menu{margin-top:-1px;border-top-left-radius:0;border-top-right-radius:0}.navbar{position:relative;min-height:50px;margin-bottom:20px;border:1px solid transparent}@media (min-width:768px){.navbar{border-radius:4px}}@media (min-width:768px){.navbar-header{float:left}}.navbar-collapse{padding-right:15px;padding-left:15px;overflow-x:visible;-webkit-overflow-scrolling:touch;border-top:1px solid transparent;-webkit-box-shadow:inset 0 1px 0 rgba(255,255,255,.1);box-shadow:inset 0 1px 0 rgba(255,255,255,.1)}.navbar-collapse.in{overflow-y:auto}@media (min-width:768px){.navbar-collapse{width:auto;border-top:0;-webkit-box-shadow:none;box-shadow:none}.navbar-collapse.collapse{display:block!important;height:auto!important;padding-bottom:0;overflow:visible!important}.navbar-collapse.in{overflow-y:visible}.navbar-fixed-bottom .navbar-collapse,.navbar-fixed-top .navbar-collapse,.navbar-static-top .navbar-collapse{padding-right:0;padding-left:0}}.navbar-fixed-bottom .navbar-collapse,.navbar-fixed-top .navbar-collapse{max-height:340px}@media (max-device-width:480px) and (orientation:landscape){.navbar-fixed-bottom .navbar-collapse,.navbar-fixed-top .navbar-collapse{max-height:200px}}.container-fluid>.navbar-collapse,.container-fluid>.navbar-header,.container>.navbar-collapse,.container>.navbar-header{margin-right:-15px;margin-left:-15px}@media (min-width:768px){.container-fluid>.navbar-collapse,.container-fluid>.navbar-header,.container>.navbar-collapse,.container>.navbar-header{margin-right:0;margin-left:0}}.navbar-static-top{z-index:1000;border-width:0 0 1px}@media (min-width:768px){.navbar-static-top{border-radius:0}}.navbar-fixed-bottom,.navbar-fixed-top{position:fixed;right:0;left:0;z-index:1030}@media (min-width:768px){.navbar-fixed-bottom,.navbar-fixed-top{border-radius:0}}.navbar-fixed-top{top:0;border-width:0 0 1px}.navbar-fixed-bottom{bottom:0;margin-bottom:0;border-width:1px 0 0}.navbar-brand{float:left;height:50px;padding:15px 15px;font-size:18px;line-height:20px}.navbar-brand:focus,.navbar-brand:hover{text-decoration:none}.navbar-brand>img{display:block}@media (min-width:768px){.navbar>.container .navbar-brand,.navbar>.container-fluid .navbar-brand{margin-left:-15px}}.navbar-toggle{position:relative;float:right;padding:9px 10px;margin-top:8px;margin-right:15px;margin-bottom:8px;background-color:transparent;background-image:none;border:1px solid transparent;border-radius:4px}.navbar-toggle:focus{outline:0}.navbar-toggle .icon-bar{display:block;width:22px;height:2px;border-radius:1px}.navbar-toggle .icon-bar+.icon-bar{margin-top:4px}@media (min-width:768px){.navbar-toggle{display:none}}.navbar-nav{margin:7.5px -15px}.navbar-nav>li>a{padding-top:10px;padding-bottom:10px;line-height:20px}@media (max-width:767px){.navbar-nav .open .dropdown-menu{position:static;float:none;width:auto;margin-top:0;background-color:transparent;border:0;-webkit-box-shadow:none;box-shadow:none}.navbar-nav .open .dropdown-menu .dropdown-header,.navbar-nav .open .dropdown-menu>li>a{padding:5px 15px 5px 25px}.navbar-nav .open .dropdown-menu>li>a{line-height:20px}.navbar-nav .open .dropdown-menu>li>a:focus,.navbar-nav .open .dropdown-menu>li>a:hover{background-image:none}}@media (min-width:768px){.navbar-nav{float:left;margin:0}.navbar-nav>li{float:left}.navbar-nav>li>a{padding-top:15px;padding-bottom:15px}}.navbar-form{padding:10px 15px;margin-top:8px;margin-right:-15px;margin-bottom:8px;margin-left:-15px;border-top:1px solid transparent;border-bottom:1px solid transparent;-webkit-box-shadow:inset 0 1px 0 rgba(255,255,255,.1),0 1px 0 rgba(255,255,255,.1);box-shadow:inset 0 1px 0 rgba(255,255,255,.1),0 1px 0 rgba(255,255,255,.1)}@media (min-width:768px){.navbar-form .form-group{display:inline-block;margin-bottom:0;vertical-align:middle}.navbar-form .form-control{display:inline-block;width:auto;vertical-align:middle}.navbar-form .form-control-static{display:inline-block}.navbar-form .input-group{display:inline-table;vertical-align:middle}.navbar-form .input-group .form-control,.navbar-form .input-group .input-group-addon,.navbar-form .input-group .input-group-btn{width:auto}.navbar-form .input-group>.form-control{width:100%}.navbar-form .control-label{margin-bottom:0;vertical-align:middle}.navbar-form .checkbox,.navbar-form .radio{display:inline-block;margin-top:0;margin-bottom:0;vertical-align:middle}.navbar-form .checkbox label,.navbar-form .radio label{padding-left:0}.navbar-form .checkbox input[type=checkbox],.navbar-form .radio input[type=radio]{position:relative;margin-left:0}.navbar-form .has-feedback .form-control-feedback{top:0}}@media (max-width:767px){.navbar-form .form-group{margin-bottom:5px}.navbar-form .form-group:last-child{margin-bottom:0}}@media (min-width:768px){.navbar-form{width:auto;padding-top:0;padding-bottom:0;margin-right:0;margin-left:0;border:0;-webkit-box-shadow:none;box-shadow:none}}.navbar-nav>li>.dropdown-menu{margin-top:0;border-top-left-radius:0;border-top-right-radius:0}.navbar-fixed-bottom .navbar-nav>li>.dropdown-menu{margin-bottom:0;border-top-left-radius:4px;border-top-right-radius:4px;border-bottom-right-radius:0;border-bottom-left-radius:0}.navbar-btn{margin-top:8px;margin-bottom:8px}.navbar-btn.btn-sm{margin-top:10px;margin-bottom:10px}.navbar-btn.btn-xs{margin-top:14px;margin-bottom:14px}.navbar-text{margin-top:15px;margin-bottom:15px}@media (min-width:768px){.navbar-text{float:left;margin-right:15px;margin-left:15px}}@media (min-width:768px){.navbar-left{float:left!important}.navbar-right{float:right!important;margin-right:-15px}.navbar-right~.navbar-right{margin-right:0}}.navbar-default{background-color:#f8f8f8;border-color:#e7e7e7}.navbar-default .navbar-brand{color:#777}.navbar-default .navbar-brand:focus,.navbar-default .navbar-brand:hover{color:#5e5e5e;background-color:transparent}.navbar-default .navbar-text{color:#777}.navbar-default .navbar-nav>li>a{color:#777}.navbar-default .navbar-nav>li>a:focus,.navbar-default .navbar-nav>li>a:hover{color:#333;background-color:transparent}.navbar-default .navbar-nav>.active>a,.navbar-default .navbar-nav>.active>a:focus,.navbar-default .navbar-nav>.active>a:hover{color:#555;background-color:#e7e7e7}.navbar-default .navbar-nav>.disabled>a,.navbar-default .navbar-nav>.disabled>a:focus,.navbar-default .navbar-nav>.disabled>a:hover{color:#ccc;background-color:transparent}.navbar-default .navbar-toggle{border-color:#ddd}.navbar-default .navbar-toggle:focus,.navbar-default .navbar-toggle:hover{background-color:#ddd}.navbar-default .navbar-toggle .icon-bar{background-color:#888}.navbar-default .navbar-collapse,.navbar-default .navbar-form{border-color:#e7e7e7}.navbar-default .navbar-nav>.open>a,.navbar-default .navbar-nav>.open>a:focus,.navbar-default .navbar-nav>.open>a:hover{color:#555;background-color:#e7e7e7}@media (max-width:767px){.navbar-default .navbar-nav .open .dropdown-menu>li>a{color:#777}.navbar-default .navbar-nav .open .dropdown-menu>li>a:focus,.navbar-default .navbar-nav .open .dropdown-menu>li>a:hover{color:#333;background-color:transparent}.navbar-default .navbar-nav .open .dropdown-menu>.active>a,.navbar-default .navbar-nav .open .dropdown-menu>.active>a:focus,.navbar-default .navbar-nav .open .dropdown-menu>.active>a:hover{color:#555;background-color:#e7e7e7}.navbar-default .navbar-nav .open .dropdown-menu>.disabled>a,.navbar-default .navbar-nav .open .dropdown-menu>.disabled>a:focus,.navbar-default .navbar-nav .open .dropdown-menu>.disabled>a:hover{color:#ccc;background-color:transparent}}.navbar-default .navbar-link{color:#777}.navbar-default .navbar-link:hover{color:#333}.navbar-default .btn-link{color:#777}.navbar-default .btn-link:focus,.navbar-default .btn-link:hover{color:#333}.navbar-default .btn-link[disabled]:focus,.navbar-default .btn-link[disabled]:hover,fieldset[disabled] .navbar-default .btn-link:focus,fieldset[disabled] .navbar-default .btn-link:hover{color:#ccc}.navbar-inverse{background-color:#222;border-color:#080808}.navbar-inverse .navbar-brand{color:#9d9d9d}.navbar-inverse .navbar-brand:focus,.navbar-inverse .navbar-brand:hover{color:#fff;background-color:transparent}.navbar-inverse .navbar-text{color:#9d9d9d}.navbar-inverse .navbar-nav>li>a{color:#9d9d9d}.navbar-inverse .navbar-nav>li>a:focus,.navbar-inverse .navbar-nav>li>a:hover{color:#fff;background-color:transparent}.navbar-inverse .navbar-nav>.active>a,.navbar-inverse .navbar-nav>.active>a:focus,.navbar-inverse .navbar-nav>.active>a:hover{color:#fff;background-color:#080808}.navbar-inverse .navbar-nav>.disabled>a,.navbar-inverse .navbar-nav>.disabled>a:focus,.navbar-inverse .navbar-nav>.disabled>a:hover{color:#444;background-color:transparent}.navbar-inverse .navbar-toggle{border-color:#333}.navbar-inverse .navbar-toggle:focus,.navbar-inverse .navbar-toggle:hover{background-color:#333}.navbar-inverse .navbar-toggle .icon-bar{background-color:#fff}.navbar-inverse .navbar-collapse,.navbar-inverse .navbar-form{border-color:#101010}.navbar-inverse .navbar-nav>.open>a,.navbar-inverse .navbar-nav>.open>a:focus,.navbar-inverse .navbar-nav>.open>a:hover{color:#fff;background-color:#080808}@media (max-width:767px){.navbar-inverse .navbar-nav .open .dropdown-menu>.dropdown-header{border-color:#080808}.navbar-inverse .navbar-nav .open .dropdown-menu .divider{background-color:#080808}.navbar-inverse .navbar-nav .open .dropdown-menu>li>a{color:#9d9d9d}.navbar-inverse .navbar-nav .open .dropdown-menu>li>a:focus,.navbar-inverse .navbar-nav .open .dropdown-menu>li>a:hover{color:#fff;background-color:transparent}.navbar-inverse .navbar-nav .open .dropdown-menu>.active>a,.navbar-inverse .navbar-nav .open .dropdown-menu>.active>a:focus,.navbar-inverse .navbar-nav .open .dropdown-menu>.active>a:hover{color:#fff;background-color:#080808}.navbar-inverse .navbar-nav .open .dropdown-menu>.disabled>a,.navbar-inverse .navbar-nav .open .dropdown-menu>.disabled>a:focus,.navbar-inverse .navbar-nav .open .dropdown-menu>.disabled>a:hover{color:#444;background-color:transparent}}.navbar-inverse .navbar-link{color:#9d9d9d}.navbar-inverse .navbar-link:hover{color:#fff}.navbar-inverse .btn-link{color:#9d9d9d}.navbar-inverse .btn-link:focus,.navbar-inverse .btn-link:hover{color:#fff}.navbar-inverse .btn-link[disabled]:focus,.navbar-inverse .btn-link[disabled]:hover,fieldset[disabled] .navbar-inverse .btn-link:focus,fieldset[disabled] .navbar-inverse .btn-link:hover{color:#444}.breadcrumb{padding:8px 15px;margin-bottom:20px;list-style:none;background-color:#f5f5f5;border-radius:4px}.breadcrumb>li{display:inline-block}.breadcrumb>li+li:before{padding:0 5px;color:#ccc;content:"/\00a0"}.breadcrumb>.active{color:#777}.pagination{display:inline-block;padding-left:0;margin:20px 0;border-radius:4px}.pagination>li{display:inline}.pagination>li>a,.pagination>li>span{position:relative;float:left;padding:6px 12px;margin-left:-1px;line-height:1.42857143;color:#337ab7;text-decoration:none;background-color:#fff;border:1px solid #ddd}.pagination>li:first-child>a,.pagination>li:first-child>span{margin-left:0;border-top-left-radius:4px;border-bottom-left-radius:4px}.pagination>li:last-child>a,.pagination>li:last-child>span{border-top-right-radius:4px;border-bottom-right-radius:4px}.pagination>li>a:focus,.pagination>li>a:hover,.pagination>li>span:focus,.pagination>li>span:hover{z-index:2;color:#23527c;background-color:#eee;border-color:#ddd}.pagination>.active>a,.pagination>.active>a:focus,.pagination>.active>a:hover,.pagination>.active>span,.pagination>.active>span:focus,.pagination>.active>span:hover{z-index:3;color:#fff;cursor:default;background-color:#337ab7;border-color:#337ab7}.pagination>.disabled>a,.pagination>.disabled>a:focus,.pagination>.disabled>a:hover,.pagination>.disabled>span,.pagination>.disabled>span:focus,.pagination>.disabled>span:hover{color:#777;cursor:not-allowed;background-color:#fff;border-color:#ddd}.pagination-lg>li>a,.pagination-lg>li>span{padding:10px 16px;font-size:18px;line-height:1.3333333}.pagination-lg>li:first-child>a,.pagination-lg>li:first-child>span{border-top-left-radius:6px;border-bottom-left-radius:6px}.pagination-lg>li:last-child>a,.pagination-lg>li:last-child>span{border-top-right-radius:6px;border-bottom-right-radius:6px}.pagination-sm>li>a,.pagination-sm>li>span{padding:5px 10px;font-size:12px;line-height:1.5}.pagination-sm>li:first-child>a,.pagination-sm>li:first-child>span{border-top-left-radius:3px;border-bottom-left-radius:3px}.pagination-sm>li:last-child>a,.pagination-sm>li:last-child>span{border-top-right-radius:3px;border-bottom-right-radius:3px}.pager{padding-left:0;margin:20px 0;text-align:center;list-style:none}.pager li{display:inline}.pager li>a,.pager li>span{display:inline-block;padding:5px 14px;background-color:#fff;border:1px solid #ddd;border-radius:15px}.pager li>a:focus,.pager li>a:hover{text-decoration:none;background-color:#eee}.pager .next>a,.pager .next>span{float:right}.pager .previous>a,.pager .previous>span{float:left}.pager .disabled>a,.pager .disabled>a:focus,.pager .disabled>a:hover,.pager .disabled>span{color:#777;cursor:not-allowed;background-color:#fff}.label{display:inline;padding:.2em .6em .3em;font-size:75%;font-weight:700;line-height:1;color:#fff;text-align:center;white-space:nowrap;vertical-align:baseline;border-radius:.25em}a.label:focus,a.label:hover{color:#fff;text-decoration:none;cursor:pointer}.label:empty{display:none}.btn .label{position:relative;top:-1px}.label-default{background-color:#777}.label-default[href]:focus,.label-default[href]:hover{background-color:#5e5e5e}.label-primary{background-color:#337ab7}.label-primary[href]:focus,.label-primary[href]:hover{background-color:#286090}.label-success{background-color:#5cb85c}.label-success[href]:focus,.label-success[href]:hover{background-color:#449d44}.label-info{background-color:#5bc0de}.label-info[href]:focus,.label-info[href]:hover{background-color:#31b0d5}.label-warning{background-color:#f0ad4e}.label-warning[href]:focus,.label-warning[href]:hover{background-color:#ec971f}.label-danger{background-color:#d9534f}.label-danger[href]:focus,.label-danger[href]:hover{background-color:#c9302c}.badge{display:inline-block;min-width:10px;padding:3px 7px;font-size:12px;font-weight:700;line-height:1;color:#fff;text-align:center;white-space:nowrap;vertical-align:middle;background-color:#777;border-radius:10px}.badge:empty{display:none}.btn .badge{position:relative;top:-1px}.btn-group-xs>.btn .badge,.btn-xs .badge{top:0;padding:1px 5px}a.badge:focus,a.badge:hover{color:#fff;text-decoration:none;cursor:pointer}.list-group-item.active>.badge,.nav-pills>.active>a>.badge{color:#337ab7;background-color:#fff}.list-group-item>.badge{float:right}.list-group-item>.badge+.badge{margin-right:5px}.nav-pills>li>a>.badge{margin-left:3px}.jumbotron{padding-top:30px;padding-bottom:30px;margin-bottom:30px;color:inherit;background-color:#eee}.jumbotron .h1,.jumbotron h1{color:inherit}.jumbotron p{margin-bottom:15px;font-size:21px;font-weight:200}.jumbotron>hr{border-top-color:#d5d5d5}.container .jumbotron,.container-fluid .jumbotron{padding-right:15px;padding-left:15px;border-radius:6px}.jumbotron .container{max-width:100%}@media screen and (min-width:768px){.jumbotron{padding-top:48px;padding-bottom:48px}.container .jumbotron,.container-fluid .jumbotron{padding-right:60px;padding-left:60px}.jumbotron .h1,.jumbotron h1{font-size:63px}}.thumbnail{display:block;padding:4px;margin-bottom:20px;line-height:1.42857143;background-color:#fff;border:1px solid #ddd;border-radius:4px;-webkit-transition:border .2s ease-in-out;-o-transition:border .2s ease-in-out;transition:border .2s ease-in-out}.thumbnail a>img,.thumbnail>img{margin-right:auto;margin-left:auto}a.thumbnail.active,a.thumbnail:focus,a.thumbnail:hover{border-color:#337ab7}.thumbnail .caption{padding:9px;color:#333}.alert{padding:15px;margin-bottom:20px;border:1px solid transparent;border-radius:4px}.alert h4{margin-top:0;color:inherit}.alert .alert-link{font-weight:700}.alert>p,.alert>ul{margin-bottom:0}.alert>p+p{margin-top:5px}.alert-dismissable,.alert-dismissible{padding-right:35px}.alert-dismissable .close,.alert-dismissible .close{position:relative;top:-2px;right:-21px;color:inherit}.alert-success{color:#3c763d;background-color:#dff0d8;border-color:#d6e9c6}.alert-success hr{border-top-color:#c9e2b3}.alert-success .alert-link{color:#2b542c}.alert-info{color:#31708f;background-color:#d9edf7;border-color:#bce8f1}.alert-info hr{border-top-color:#a6e1ec}.alert-info .alert-link{color:#245269}.alert-warning{color:#8a6d3b;background-color:#fcf8e3;border-color:#faebcc}.alert-warning hr{border-top-color:#f7e1b5}.alert-warning .alert-link{color:#66512c}.alert-danger{color:#a94442;background-color:#f2dede;border-color:#ebccd1}.alert-danger hr{border-top-color:#e4b9c0}.alert-danger .alert-link{color:#843534}@-webkit-keyframes progress-bar-stripes{from{background-position:40px 0}to{background-position:0 0}}@-o-keyframes progress-bar-stripes{from{background-position:40px 0}to{background-position:0 0}}@keyframes progress-bar-stripes{from{background-position:40px 0}to{background-position:0 0}}.progress{height:20px;margin-bottom:20px;overflow:hidden;background-color:#f5f5f5;border-radius:4px;-webkit-box-shadow:inset 0 1px 2px rgba(0,0,0,.1);box-shadow:inset 0 1px 2px rgba(0,0,0,.1)}.progress-bar{float:left;width:0;height:100%;font-size:12px;line-height:20px;color:#fff;text-align:center;background-color:#337ab7;-webkit-box-shadow:inset 0 -1px 0 rgba(0,0,0,.15);box-shadow:inset 0 -1px 0 rgba(0,0,0,.15);-webkit-transition:width .6s ease;-o-transition:width .6s ease;transition:width .6s ease}.progress-bar-striped,.progress-striped .progress-bar{background-image:-webkit-linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);background-image:-o-linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);background-image:linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);-webkit-background-size:40px 40px;background-size:40px 40px}.progress-bar.active,.progress.active .progress-bar{-webkit-animation:progress-bar-stripes 2s linear infinite;-o-animation:progress-bar-stripes 2s linear infinite;animation:progress-bar-stripes 2s linear infinite}.progress-bar-success{background-color:#5cb85c}.progress-striped .progress-bar-success{background-image:-webkit-linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);background-image:-o-linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);background-image:linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent)}.progress-bar-info{background-color:#5bc0de}.progress-striped .progress-bar-info{background-image:-webkit-linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);background-image:-o-linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);background-image:linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent)}.progress-bar-warning{background-color:#f0ad4e}.progress-striped .progress-bar-warning{background-image:-webkit-linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);background-image:-o-linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);background-image:linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent)}.progress-bar-danger{background-color:#d9534f}.progress-striped .progress-bar-danger{background-image:-webkit-linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);background-image:-o-linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);background-image:linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent)}.media{margin-top:15px}.media:first-child{margin-top:0}.media,.media-body{overflow:hidden;zoom:1}.media-body{width:10000px}.media-object{display:block}.media-object.img-thumbnail{max-width:none}.media-right,.media>.pull-right{padding-left:10px}.media-left,.media>.pull-left{padding-right:10px}.media-body,.media-left,.media-right{display:table-cell;vertical-align:top}.media-middle{vertical-align:middle}.media-bottom{vertical-align:bottom}.media-heading{margin-top:0;margin-bottom:5px}.media-list{padding-left:0;list-style:none}.list-group{padding-left:0;margin-bottom:20px}.list-group-item{position:relative;display:block;padding:10px 15px;margin-bottom:-1px;background-color:#fff;border:1px solid #ddd}.list-group-item:first-child{border-top-left-radius:4px;border-top-right-radius:4px}.list-group-item:last-child{margin-bottom:0;border-bottom-right-radius:4px;border-bottom-left-radius:4px}a.list-group-item,button.list-group-item{color:#555}a.list-group-item .list-group-item-heading,button.list-group-item .list-group-item-heading{color:#333}a.list-group-item:focus,a.list-group-item:hover,button.list-group-item:focus,button.list-group-item:hover{color:#555;text-decoration:none;background-color:#f5f5f5}button.list-group-item{width:100%;text-align:left}.list-group-item.disabled,.list-group-item.disabled:focus,.list-group-item.disabled:hover{color:#777;cursor:not-allowed;background-color:#eee}.list-group-item.disabled .list-group-item-heading,.list-group-item.disabled:focus .list-group-item-heading,.list-group-item.disabled:hover .list-group-item-heading{color:inherit}.list-group-item.disabled .list-group-item-text,.list-group-item.disabled:focus .list-group-item-text,.list-group-item.disabled:hover .list-group-item-text{color:#777}.list-group-item.active,.list-group-item.active:focus,.list-group-item.active:hover{z-index:2;color:#fff;background-color:#337ab7;border-color:#337ab7}.list-group-item.active .list-group-item-heading,.list-group-item.active .list-group-item-heading>.small,.list-group-item.active .list-group-item-heading>small,.list-group-item.active:focus .list-group-item-heading,.list-group-item.active:focus .list-group-item-heading>.small,.list-group-item.active:focus .list-group-item-heading>small,.list-group-item.active:hover .list-group-item-heading,.list-group-item.active:hover .list-group-item-heading>.small,.list-group-item.active:hover .list-group-item-heading>small{color:inherit}.list-group-item.active .list-group-item-text,.list-group-item.active:focus .list-group-item-text,.list-group-item.active:hover .list-group-item-text{color:#c7ddef}.list-group-item-success{color:#3c763d;background-color:#dff0d8}a.list-group-item-success,button.list-group-item-success{color:#3c763d}a.list-group-item-success .list-group-item-heading,button.list-group-item-success .list-group-item-heading{color:inherit}a.list-group-item-success:focus,a.list-group-item-success:hover,button.list-group-item-success:focus,button.list-group-item-success:hover{color:#3c763d;background-color:#d0e9c6}a.list-group-item-success.active,a.list-group-item-success.active:focus,a.list-group-item-success.active:hover,button.list-group-item-success.active,button.list-group-item-success.active:focus,button.list-group-item-success.active:hover{color:#fff;background-color:#3c763d;border-color:#3c763d}.list-group-item-info{color:#31708f;background-color:#d9edf7}a.list-group-item-info,button.list-group-item-info{color:#31708f}a.list-group-item-info .list-group-item-heading,button.list-group-item-info .list-group-item-heading{color:inherit}a.list-group-item-info:focus,a.list-group-item-info:hover,button.list-group-item-info:focus,button.list-group-item-info:hover{color:#31708f;background-color:#c4e3f3}a.list-group-item-info.active,a.list-group-item-info.active:focus,a.list-group-item-info.active:hover,button.list-group-item-info.active,button.list-group-item-info.active:focus,button.list-group-item-info.active:hover{color:#fff;background-color:#31708f;border-color:#31708f}.list-group-item-warning{color:#8a6d3b;background-color:#fcf8e3}a.list-group-item-warning,button.list-group-item-warning{color:#8a6d3b}a.list-group-item-warning .list-group-item-heading,button.list-group-item-warning .list-group-item-heading{color:inherit}a.list-group-item-warning:focus,a.list-group-item-warning:hover,button.list-group-item-warning:focus,button.list-group-item-warning:hover{color:#8a6d3b;background-color:#faf2cc}a.list-group-item-warning.active,a.list-group-item-warning.active:focus,a.list-group-item-warning.active:hover,button.list-group-item-warning.active,button.list-group-item-warning.active:focus,button.list-group-item-warning.active:hover{color:#fff;background-color:#8a6d3b;border-color:#8a6d3b}.list-group-item-danger{color:#a94442;background-color:#f2dede}a.list-group-item-danger,button.list-group-item-danger{color:#a94442}a.list-group-item-danger .list-group-item-heading,button.list-group-item-danger .list-group-item-heading{color:inherit}a.list-group-item-danger:focus,a.list-group-item-danger:hover,button.list-group-item-danger:focus,button.list-group-item-danger:hover{color:#a94442;background-color:#ebcccc}a.list-group-item-danger.active,a.list-group-item-danger.active:focus,a.list-group-item-danger.active:hover,button.list-group-item-danger.active,button.list-group-item-danger.active:focus,button.list-group-item-danger.active:hover{color:#fff;background-color:#a94442;border-color:#a94442}.list-group-item-heading{margin-top:0;margin-bottom:5px}.list-group-item-text{margin-bottom:0;line-height:1.3}.panel{margin-bottom:20px;background-color:#fff;border:1px solid transparent;border-radius:4px;-webkit-box-shadow:0 1px 1px rgba(0,0,0,.05);box-shadow:0 1px 1px rgba(0,0,0,.05)}.panel-body{padding:15px}.panel-heading{padding:10px 15px;border-bottom:1px solid transparent;border-top-left-radius:3px;border-top-right-radius:3px}.panel-heading>.dropdown .dropdown-toggle{color:inherit}.panel-title{margin-top:0;margin-bottom:0;font-size:16px;color:inherit}.panel-title>.small,.panel-title>.small>a,.panel-title>a,.panel-title>small,.panel-title>small>a{color:inherit}.panel-footer{padding:10px 15px;background-color:#f5f5f5;border-top:1px solid #ddd;border-bottom-right-radius:3px;border-bottom-left-radius:3px}.panel>.list-group,.panel>.panel-collapse>.list-group{margin-bottom:0}.panel>.list-group .list-group-item,.panel>.panel-collapse>.list-group .list-group-item{border-width:1px 0;border-radius:0}.panel>.list-group:first-child .list-group-item:first-child,.panel>.panel-collapse>.list-group:first-child .list-group-item:first-child{border-top:0;border-top-left-radius:3px;border-top-right-radius:3px}.panel>.list-group:last-child .list-group-item:last-child,.panel>.panel-collapse>.list-group:last-child .list-group-item:last-child{border-bottom:0;border-bottom-right-radius:3px;border-bottom-left-radius:3px}.panel>.panel-heading+.panel-collapse>.list-group .list-group-item:first-child{border-top-left-radius:0;border-top-right-radius:0}.panel-heading+.list-group .list-group-item:first-child{border-top-width:0}.list-group+.panel-footer{border-top-width:0}.panel>.panel-collapse>.table,.panel>.table,.panel>.table-responsive>.table{margin-bottom:0}.panel>.panel-collapse>.table caption,.panel>.table caption,.panel>.table-responsive>.table caption{padding-right:15px;padding-left:15px}.panel>.table-responsive:first-child>.table:first-child,.panel>.table:first-child{border-top-left-radius:3px;border-top-right-radius:3px}.panel>.table-responsive:first-child>.table:first-child>tbody:first-child>tr:first-child,.panel>.table-responsive:first-child>.table:first-child>thead:first-child>tr:first-child,.panel>.table:first-child>tbody:first-child>tr:first-child,.panel>.table:first-child>thead:first-child>tr:first-child{border-top-left-radius:3px;border-top-right-radius:3px}.panel>.table-responsive:first-child>.table:first-child>tbody:first-child>tr:first-child td:first-child,.panel>.table-responsive:first-child>.table:first-child>tbody:first-child>tr:first-child th:first-child,.panel>.table-responsive:first-child>.table:first-child>thead:first-child>tr:first-child td:first-child,.panel>.table-responsive:first-child>.table:first-child>thead:first-child>tr:first-child th:first-child,.panel>.table:first-child>tbody:first-child>tr:first-child td:first-child,.panel>.table:first-child>tbody:first-child>tr:first-child th:first-child,.panel>.table:first-child>thead:first-child>tr:first-child td:first-child,.panel>.table:first-child>thead:first-child>tr:first-child th:first-child{border-top-left-radius:3px}.panel>.table-responsive:first-child>.table:first-child>tbody:first-child>tr:first-child td:last-child,.panel>.table-responsive:first-child>.table:first-child>tbody:first-child>tr:first-child th:last-child,.panel>.table-responsive:first-child>.table:first-child>thead:first-child>tr:first-child td:last-child,.panel>.table-responsive:first-child>.table:first-child>thead:first-child>tr:first-child th:last-child,.panel>.table:first-child>tbody:first-child>tr:first-child td:last-child,.panel>.table:first-child>tbody:first-child>tr:first-child th:last-child,.panel>.table:first-child>thead:first-child>tr:first-child td:last-child,.panel>.table:first-child>thead:first-child>tr:first-child th:last-child{border-top-right-radius:3px}.panel>.table-responsive:last-child>.table:last-child,.panel>.table:last-child{border-bottom-right-radius:3px;border-bottom-left-radius:3px}.panel>.table-responsive:last-child>.table:last-child>tbody:last-child>tr:last-child,.panel>.table-responsive:last-child>.table:last-child>tfoot:last-child>tr:last-child,.panel>.table:last-child>tbody:last-child>tr:last-child,.panel>.table:last-child>tfoot:last-child>tr:last-child{border-bottom-right-radius:3px;border-bottom-left-radius:3px}.panel>.table-responsive:last-child>.table:last-child>tbody:last-child>tr:last-child td:first-child,.panel>.table-responsive:last-child>.table:last-child>tbody:last-child>tr:last-child th:first-child,.panel>.table-responsive:last-child>.table:last-child>tfoot:last-child>tr:last-child td:first-child,.panel>.table-responsive:last-child>.table:last-child>tfoot:last-child>tr:last-child th:first-child,.panel>.table:last-child>tbody:last-child>tr:last-child td:first-child,.panel>.table:last-child>tbody:last-child>tr:last-child th:first-child,.panel>.table:last-child>tfoot:last-child>tr:last-child td:first-child,.panel>.table:last-child>tfoot:last-child>tr:last-child th:first-child{border-bottom-left-radius:3px}.panel>.table-responsive:last-child>.table:last-child>tbody:last-child>tr:last-child td:last-child,.panel>.table-responsive:last-child>.table:last-child>tbody:last-child>tr:last-child th:last-child,.panel>.table-responsive:last-child>.table:last-child>tfoot:last-child>tr:last-child td:last-child,.panel>.table-responsive:last-child>.table:last-child>tfoot:last-child>tr:last-child th:last-child,.panel>.table:last-child>tbody:last-child>tr:last-child td:last-child,.panel>.table:last-child>tbody:last-child>tr:last-child th:last-child,.panel>.table:last-child>tfoot:last-child>tr:last-child td:last-child,.panel>.table:last-child>tfoot:last-child>tr:last-child th:last-child{border-bottom-right-radius:3px}.panel>.panel-body+.table,.panel>.panel-body+.table-responsive,.panel>.table+.panel-body,.panel>.table-responsive+.panel-body{border-top:1px solid #ddd}.panel>.table>tbody:first-child>tr:first-child td,.panel>.table>tbody:first-child>tr:first-child th{border-top:0}.panel>.table-bordered,.panel>.table-responsive>.table-bordered{border:0}.panel>.table-bordered>tbody>tr>td:first-child,.panel>.table-bordered>tbody>tr>th:first-child,.panel>.table-bordered>tfoot>tr>td:first-child,.panel>.table-bordered>tfoot>tr>th:first-child,.panel>.table-bordered>thead>tr>td:first-child,.panel>.table-bordered>thead>tr>th:first-child,.panel>.table-responsive>.table-bordered>tbody>tr>td:first-child,.panel>.table-responsive>.table-bordered>tbody>tr>th:first-child,.panel>.table-responsive>.table-bordered>tfoot>tr>td:first-child,.panel>.table-responsive>.table-bordered>tfoot>tr>th:first-child,.panel>.table-responsive>.table-bordered>thead>tr>td:first-child,.panel>.table-responsive>.table-bordered>thead>tr>th:first-child{border-left:0}.panel>.table-bordered>tbody>tr>td:last-child,.panel>.table-bordered>tbody>tr>th:last-child,.panel>.table-bordered>tfoot>tr>td:last-child,.panel>.table-bordered>tfoot>tr>th:last-child,.panel>.table-bordered>thead>tr>td:last-child,.panel>.table-bordered>thead>tr>th:last-child,.panel>.table-responsive>.table-bordered>tbody>tr>td:last-child,.panel>.table-responsive>.table-bordered>tbody>tr>th:last-child,.panel>.table-responsive>.table-bordered>tfoot>tr>td:last-child,.panel>.table-responsive>.table-bordered>tfoot>tr>th:last-child,.panel>.table-responsive>.table-bordered>thead>tr>td:last-child,.panel>.table-responsive>.table-bordered>thead>tr>th:last-child{border-right:0}.panel>.table-bordered>tbody>tr:first-child>td,.panel>.table-bordered>tbody>tr:first-child>th,.panel>.table-bordered>thead>tr:first-child>td,.panel>.table-bordered>thead>tr:first-child>th,.panel>.table-responsive>.table-bordered>tbody>tr:first-child>td,.panel>.table-responsive>.table-bordered>tbody>tr:first-child>th,.panel>.table-responsive>.table-bordered>thead>tr:first-child>td,.panel>.table-responsive>.table-bordered>thead>tr:first-child>th{border-bottom:0}.panel>.table-bordered>tbody>tr:last-child>td,.panel>.table-bordered>tbody>tr:last-child>th,.panel>.table-bordered>tfoot>tr:last-child>td,.panel>.table-bordered>tfoot>tr:last-child>th,.panel>.table-responsive>.table-bordered>tbody>tr:last-child>td,.panel>.table-responsive>.table-bordered>tbody>tr:last-child>th,.panel>.table-responsive>.table-bordered>tfoot>tr:last-child>td,.panel>.table-responsive>.table-bordered>tfoot>tr:last-child>th{border-bottom:0}.panel>.table-responsive{margin-bottom:0;border:0}.panel-group{margin-bottom:20px}.panel-group .panel{margin-bottom:0;border-radius:4px}.panel-group .panel+.panel{margin-top:5px}.panel-group .panel-heading{border-bottom:0}.panel-group .panel-heading+.panel-collapse>.list-group,.panel-group .panel-heading+.panel-collapse>.panel-body{border-top:1px solid #ddd}.panel-group .panel-footer{border-top:0}.panel-group .panel-footer+.panel-collapse .panel-body{border-bottom:1px solid #ddd}.panel-default{border-color:#ddd}.panel-default>.panel-heading{color:#333;background-color:#f5f5f5;border-color:#ddd}.panel-default>.panel-heading+.panel-collapse>.panel-body{border-top-color:#ddd}.panel-default>.panel-heading .badge{color:#f5f5f5;background-color:#333}.panel-default>.panel-footer+.panel-collapse>.panel-body{border-bottom-color:#ddd}.panel-primary{border-color:#337ab7}.panel-primary>.panel-heading{color:#fff;background-color:#337ab7;border-color:#337ab7}.panel-primary>.panel-heading+.panel-collapse>.panel-body{border-top-color:#337ab7}.panel-primary>.panel-heading .badge{color:#337ab7;background-color:#fff}.panel-primary>.panel-footer+.panel-collapse>.panel-body{border-bottom-color:#337ab7}.panel-success{border-color:#d6e9c6}.panel-success>.panel-heading{color:#3c763d;background-color:#dff0d8;border-color:#d6e9c6}.panel-success>.panel-heading+.panel-collapse>.panel-body{border-top-color:#d6e9c6}.panel-success>.panel-heading .badge{color:#dff0d8;background-color:#3c763d}.panel-success>.panel-footer+.panel-collapse>.panel-body{border-bottom-color:#d6e9c6}.panel-info{border-color:#bce8f1}.panel-info>.panel-heading{color:#31708f;background-color:#d9edf7;border-color:#bce8f1}.panel-info>.panel-heading+.panel-collapse>.panel-body{border-top-color:#bce8f1}.panel-info>.panel-heading .badge{color:#d9edf7;background-color:#31708f}.panel-info>.panel-footer+.panel-collapse>.panel-body{border-bottom-color:#bce8f1}.panel-warning{border-color:#faebcc}.panel-warning>.panel-heading{color:#8a6d3b;background-color:#fcf8e3;border-color:#faebcc}.panel-warning>.panel-heading+.panel-collapse>.panel-body{border-top-color:#faebcc}.panel-warning>.panel-heading .badge{color:#fcf8e3;background-color:#8a6d3b}.panel-warning>.panel-footer+.panel-collapse>.panel-body{border-bottom-color:#faebcc}.panel-danger{border-color:#ebccd1}.panel-danger>.panel-heading{color:#a94442;background-color:#f2dede;border-color:#ebccd1}.panel-danger>.panel-heading+.panel-collapse>.panel-body{border-top-color:#ebccd1}.panel-danger>.panel-heading .badge{color:#f2dede;background-color:#a94442}.panel-danger>.panel-footer+.panel-collapse>.panel-body{border-bottom-color:#ebccd1}.embed-responsive{position:relative;display:block;height:0;padding:0;overflow:hidden}.embed-responsive .embed-responsive-item,.embed-responsive embed,.embed-responsive iframe,.embed-responsive object,.embed-responsive video{position:absolute;top:0;bottom:0;left:0;width:100%;height:100%;border:0}.embed-responsive-16by9{padding-bottom:56.25%}.embed-responsive-4by3{padding-bottom:75%}.well{min-height:20px;padding:19px;margin-bottom:20px;background-color:#f5f5f5;border:1px solid #e3e3e3;border-radius:4px;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,.05);box-shadow:inset 0 1px 1px rgba(0,0,0,.05)}.well blockquote{border-color:#ddd;border-color:rgba(0,0,0,.15)}.well-lg{padding:24px;border-radius:6px}.well-sm{padding:9px;border-radius:3px}.close{float:right;font-size:21px;font-weight:700;line-height:1;color:#000;text-shadow:0 1px 0 #fff;filter:alpha(opacity=20);opacity:.2}.close:focus,.close:hover{color:#000;text-decoration:none;cursor:pointer;filter:alpha(opacity=50);opacity:.5}button.close{-webkit-appearance:none;padding:0;cursor:pointer;background:0 0;border:0}.modal-open{overflow:hidden}.modal{position:fixed;top:0;right:0;bottom:0;left:0;z-index:1050;display:none;overflow:hidden;-webkit-overflow-scrolling:touch;outline:0}.modal.fade .modal-dialog{-webkit-transition:-webkit-transform .3s ease-out;-o-transition:-o-transform .3s ease-out;transition:transform .3s ease-out;-webkit-transform:translate(0,-25%);-ms-transform:translate(0,-25%);-o-transform:translate(0,-25%);transform:translate(0,-25%)}.modal.in .modal-dialog{-webkit-transform:translate(0,0);-ms-transform:translate(0,0);-o-transform:translate(0,0);transform:translate(0,0)}.modal-open .modal{overflow-x:hidden;overflow-y:auto}.modal-dialog{position:relative;width:auto;margin:10px}.modal-content{position:relative;background-color:#fff;-webkit-background-clip:padding-box;background-clip:padding-box;border:1px solid #999;border:1px solid rgba(0,0,0,.2);border-radius:6px;outline:0;-webkit-box-shadow:0 3px 9px rgba(0,0,0,.5);box-shadow:0 3px 9px rgba(0,0,0,.5)}.modal-backdrop{position:fixed;top:0;right:0;bottom:0;left:0;z-index:1040;background-color:#000}.modal-backdrop.fade{filter:alpha(opacity=0);opacity:0}.modal-backdrop.in{filter:alpha(opacity=50);opacity:.5}.modal-header{padding:15px;border-bottom:1px solid #e5e5e5}.modal-header .close{margin-top:-2px}.modal-title{margin:0;line-height:1.42857143}.modal-body{position:relative;padding:15px}.modal-footer{padding:15px;text-align:right;border-top:1px solid #e5e5e5}.modal-footer .btn+.btn{margin-bottom:0;margin-left:5px}.modal-footer .btn-group .btn+.btn{margin-left:-1px}.modal-footer .btn-block+.btn-block{margin-left:0}.modal-scrollbar-measure{position:absolute;top:-9999px;width:50px;height:50px;overflow:scroll}@media (min-width:768px){.modal-dialog{width:600px;margin:30px auto}.modal-content{-webkit-box-shadow:0 5px 15px rgba(0,0,0,.5);box-shadow:0 5px 15px rgba(0,0,0,.5)}.modal-sm{width:300px}}@media (min-width:992px){.modal-lg{width:900px}}.tooltip{position:absolute;z-index:1070;display:block;font-family:"Helvetica Neue",Helvetica,Arial,sans-serif;font-size:12px;font-style:normal;font-weight:400;line-height:1.42857143;text-align:left;text-align:start;text-decoration:none;text-shadow:none;text-transform:none;letter-spacing:normal;word-break:normal;word-spacing:normal;word-wrap:normal;white-space:normal;filter:alpha(opacity=0);opacity:0;line-break:auto}.tooltip.in{filter:alpha(opacity=90);opacity:.9}.tooltip.top{padding:5px 0;margin-top:-3px}.tooltip.right{padding:0 5px;margin-left:3px}.tooltip.bottom{padding:5px 0;margin-top:3px}.tooltip.left{padding:0 5px;margin-left:-3px}.tooltip-inner{max-width:200px;padding:3px 8px;color:#fff;text-align:center;background-color:#000;border-radius:4px}.tooltip-arrow{position:absolute;width:0;height:0;border-color:transparent;border-style:solid}.tooltip.top .tooltip-arrow{bottom:0;left:50%;margin-left:-5px;border-width:5px 5px 0;border-top-color:#000}.tooltip.top-left .tooltip-arrow{right:5px;bottom:0;margin-bottom:-5px;border-width:5px 5px 0;border-top-color:#000}.tooltip.top-right .tooltip-arrow{bottom:0;left:5px;margin-bottom:-5px;border-width:5px 5px 0;border-top-color:#000}.tooltip.right .tooltip-arrow{top:50%;left:0;margin-top:-5px;border-width:5px 5px 5px 0;border-right-color:#000}.tooltip.left .tooltip-arrow{top:50%;right:0;margin-top:-5px;border-width:5px 0 5px 5px;border-left-color:#000}.tooltip.bottom .tooltip-arrow{top:0;left:50%;margin-left:-5px;border-width:0 5px 5px;border-bottom-color:#000}.tooltip.bottom-left .tooltip-arrow{top:0;right:5px;margin-top:-5px;border-width:0 5px 5px;border-bottom-color:#000}.tooltip.bottom-right .tooltip-arrow{top:0;left:5px;margin-top:-5px;border-width:0 5px 5px;border-bottom-color:#000}.popover{position:absolute;top:0;left:0;z-index:1060;display:none;max-width:276px;padding:1px;font-family:"Helvetica Neue",Helvetica,Arial,sans-serif;font-size:14px;font-style:normal;font-weight:400;line-height:1.42857143;text-align:left;text-align:start;text-decoration:none;text-shadow:none;text-transform:none;letter-spacing:normal;word-break:normal;word-spacing:normal;word-wrap:normal;white-space:normal;background-color:#fff;-webkit-background-clip:padding-box;background-clip:padding-box;border:1px solid #ccc;border:1px solid rgba(0,0,0,.2);border-radius:6px;-webkit-box-shadow:0 5px 10px rgba(0,0,0,.2);box-shadow:0 5px 10px rgba(0,0,0,.2);line-break:auto}.popover.top{margin-top:-10px}.popover.right{margin-left:10px}.popover.bottom{margin-top:10px}.popover.left{margin-left:-10px}.popover-title{padding:8px 14px;margin:0;font-size:14px;background-color:#f7f7f7;border-bottom:1px solid #ebebeb;border-radius:5px 5px 0 0}.popover-content{padding:9px 14px}.popover>.arrow,.popover>.arrow:after{position:absolute;display:block;width:0;height:0;border-color:transparent;border-style:solid}.popover>.arrow{border-width:11px}.popover>.arrow:after{content:"";border-width:10px}.popover.top>.arrow{bottom:-11px;left:50%;margin-left:-11px;border-top-color:#999;border-top-color:rgba(0,0,0,.25);border-bottom-width:0}.popover.top>.arrow:after{bottom:1px;margin-left:-10px;content:" ";border-top-color:#fff;border-bottom-width:0}.popover.right>.arrow{top:50%;left:-11px;margin-top:-11px;border-right-color:#999;border-right-color:rgba(0,0,0,.25);border-left-width:0}.popover.right>.arrow:after{bottom:-10px;left:1px;content:" ";border-right-color:#fff;border-left-width:0}.popover.bottom>.arrow{top:-11px;left:50%;margin-left:-11px;border-top-width:0;border-bottom-color:#999;border-bottom-color:rgba(0,0,0,.25)}.popover.bottom>.arrow:after{top:1px;margin-left:-10px;content:" ";border-top-width:0;border-bottom-color:#fff}.popover.left>.arrow{top:50%;right:-11px;margin-top:-11px;border-right-width:0;border-left-color:#999;border-left-color:rgba(0,0,0,.25)}.popover.left>.arrow:after{right:1px;bottom:-10px;content:" ";border-right-width:0;border-left-color:#fff}.carousel{position:relative}.carousel-inner{position:relative;width:100%;overflow:hidden}.carousel-inner>.item{position:relative;display:none;-webkit-transition:.6s ease-in-out left;-o-transition:.6s ease-in-out left;transition:.6s ease-in-out left}.carousel-inner>.item>a>img,.carousel-inner>.item>img{line-height:1}@media all and (transform-3d),(-webkit-transform-3d){.carousel-inner>.item{-webkit-transition:-webkit-transform .6s ease-in-out;-o-transition:-o-transform .6s ease-in-out;transition:transform .6s ease-in-out;-webkit-backface-visibility:hidden;backface-visibility:hidden;-webkit-perspective:1000px;perspective:1000px}.carousel-inner>.item.active.right,.carousel-inner>.item.next{left:0;-webkit-transform:translate3d(100%,0,0);transform:translate3d(100%,0,0)}.carousel-inner>.item.active.left,.carousel-inner>.item.prev{left:0;-webkit-transform:translate3d(-100%,0,0);transform:translate3d(-100%,0,0)}.carousel-inner>.item.active,.carousel-inner>.item.next.left,.carousel-inner>.item.prev.right{left:0;-webkit-transform:translate3d(0,0,0);transform:translate3d(0,0,0)}}.carousel-inner>.active,.carousel-inner>.next,.carousel-inner>.prev{display:block}.carousel-inner>.active{left:0}.carousel-inner>.next,.carousel-inner>.prev{position:absolute;top:0;width:100%}.carousel-inner>.next{left:100%}.carousel-inner>.prev{left:-100%}.carousel-inner>.next.left,.carousel-inner>.prev.right{left:0}.carousel-inner>.active.left{left:-100%}.carousel-inner>.active.right{left:100%}.carousel-control{position:absolute;top:0;bottom:0;left:0;width:15%;font-size:20px;color:#fff;text-align:center;text-shadow:0 1px 2px rgba(0,0,0,.6);background-color:rgba(0,0,0,0);filter:alpha(opacity=50);opacity:.5}.carousel-control.left{background-image:-webkit-linear-gradient(left,rgba(0,0,0,.5) 0,rgba(0,0,0,.0001) 100%);background-image:-o-linear-gradient(left,rgba(0,0,0,.5) 0,rgba(0,0,0,.0001) 100%);background-image:-webkit-gradient(linear,left top,right top,from(rgba(0,0,0,.5)),to(rgba(0,0,0,.0001)));background-image:linear-gradient(to right,rgba(0,0,0,.5) 0,rgba(0,0,0,.0001) 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#80000000', endColorstr='#00000000', GradientType=1);background-repeat:repeat-x}.carousel-control.right{right:0;left:auto;background-image:-webkit-linear-gradient(left,rgba(0,0,0,.0001) 0,rgba(0,0,0,.5) 100%);background-image:-o-linear-gradient(left,rgba(0,0,0,.0001) 0,rgba(0,0,0,.5) 100%);background-image:-webkit-gradient(linear,left top,right top,from(rgba(0,0,0,.0001)),to(rgba(0,0,0,.5)));background-image:linear-gradient(to right,rgba(0,0,0,.0001) 0,rgba(0,0,0,.5) 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#00000000', endColorstr='#80000000', GradientType=1);background-repeat:repeat-x}.carousel-control:focus,.carousel-control:hover{color:#fff;text-decoration:none;filter:alpha(opacity=90);outline:0;opacity:.9}.carousel-control .glyphicon-chevron-left,.carousel-control .glyphicon-chevron-right,.carousel-control .icon-next,.carousel-control .icon-prev{position:absolute;top:50%;z-index:5;display:inline-block;margin-top:-10px}.carousel-control .glyphicon-chevron-left,.carousel-control .icon-prev{left:50%;margin-left:-10px}.carousel-control .glyphicon-chevron-right,.carousel-control .icon-next{right:50%;margin-right:-10px}.carousel-control .icon-next,.carousel-control .icon-prev{width:20px;height:20px;font-family:serif;line-height:1}.carousel-control .icon-prev:before{content:'\2039'}.carousel-control .icon-next:before{content:'\203a'}.carousel-indicators{position:absolute;bottom:10px;left:50%;z-index:15;width:60%;padding-left:0;margin-left:-30%;text-align:center;list-style:none}.carousel-indicators li{display:inline-block;width:10px;height:10px;margin:1px;text-indent:-999px;cursor:pointer;background-color:#000\9;background-color:rgba(0,0,0,0);border:1px solid #fff;border-radius:10px}.carousel-indicators .active{width:12px;height:12px;margin:0;background-color:#fff}.carousel-caption{position:absolute;right:15%;bottom:20px;left:15%;z-index:10;padding-top:20px;padding-bottom:20px;color:#fff;text-align:center;text-shadow:0 1px 2px rgba(0,0,0,.6)}.carousel-caption .btn{text-shadow:none}@media screen and (min-width:768px){.carousel-control .glyphicon-chevron-left,.carousel-control .glyphicon-chevron-right,.carousel-control .icon-next,.carousel-control .icon-prev{width:30px;height:30px;margin-top:-10px;font-size:30px}.carousel-control .glyphicon-chevron-left,.carousel-control .icon-prev{margin-left:-10px}.carousel-control .glyphicon-chevron-right,.carousel-control .icon-next{margin-right:-10px}.carousel-caption{right:20%;left:20%;padding-bottom:30px}.carousel-indicators{bottom:20px}}.btn-group-vertical>.btn-group:after,.btn-group-vertical>.btn-group:before,.btn-toolbar:after,.btn-toolbar:before,.clearfix:after,.clearfix:before,.container-fluid:after,.container-fluid:before,.container:after,.container:before,.dl-horizontal dd:after,.dl-horizontal dd:before,.form-horizontal .form-group:after,.form-horizontal .form-group:before,.modal-footer:after,.modal-footer:before,.modal-header:after,.modal-header:before,.nav:after,.nav:before,.navbar-collapse:after,.navbar-collapse:before,.navbar-header:after,.navbar-header:before,.navbar:after,.navbar:before,.pager:after,.pager:before,.panel-body:after,.panel-body:before,.row:after,.row:before{display:table;content:" "}.btn-group-vertical>.btn-group:after,.btn-toolbar:after,.clearfix:after,.container-fluid:after,.container:after,.dl-horizontal dd:after,.form-horizontal .form-group:after,.modal-footer:after,.modal-header:after,.nav:after,.navbar-collapse:after,.navbar-header:after,.navbar:after,.pager:after,.panel-body:after,.row:after{clear:both}.center-block{display:block;margin-right:auto;margin-left:auto}.pull-right{float:right!important}.pull-left{float:left!important}.hide{display:none!important}.show{display:block!important}.invisible{visibility:hidden}.text-hide{font:0/0 a;color:transparent;text-shadow:none;background-color:transparent;border:0}.hidden{display:none!important}.affix{position:fixed}@-ms-viewport{width:device-width}.visible-lg,.visible-md,.visible-sm,.visible-xs{display:none!important}.visible-lg-block,.visible-lg-inline,.visible-lg-inline-block,.visible-md-block,.visible-md-inline,.visible-md-inline-block,.visible-sm-block,.visible-sm-inline,.visible-sm-inline-block,.visible-xs-block,.visible-xs-inline,.visible-xs-inline-block{display:none!important}@media (max-width:767px){.visible-xs{display:block!important}table.visible-xs{display:table!important}tr.visible-xs{display:table-row!important}td.visible-xs,th.visible-xs{display:table-cell!important}}@media (max-width:767px){.visible-xs-block{display:block!important}}@media (max-width:767px){.visible-xs-inline{display:inline!important}}@media (max-width:767px){.visible-xs-inline-block{display:inline-block!important}}@media (min-width:768px) and (max-width:991px){.visible-sm{display:block!important}table.visible-sm{display:table!important}tr.visible-sm{display:table-row!important}td.visible-sm,th.visible-sm{display:table-cell!important}}@media (min-width:768px) and (max-width:991px){.visible-sm-block{display:block!important}}@media (min-width:768px) and (max-width:991px){.visible-sm-inline{display:inline!important}}@media (min-width:768px) and (max-width:991px){.visible-sm-inline-block{display:inline-block!important}}@media (min-width:992px) and (max-width:1199px){.visible-md{display:block!important}table.visible-md{display:table!important}tr.visible-md{display:table-row!important}td.visible-md,th.visible-md{display:table-cell!important}}@media (min-width:992px) and (max-width:1199px){.visible-md-block{display:block!important}}@media (min-width:992px) and (max-width:1199px){.visible-md-inline{display:inline!important}}@media (min-width:992px) and (max-width:1199px){.visible-md-inline-block{display:inline-block!important}}@media (min-width:1200px){.visible-lg{display:block!important}table.visible-lg{display:table!important}tr.visible-lg{display:table-row!important}td.visible-lg,th.visible-lg{display:table-cell!important}}@media (min-width:1200px){.visible-lg-block{display:block!important}}@media (min-width:1200px){.visible-lg-inline{display:inline!important}}@media (min-width:1200px){.visible-lg-inline-block{display:inline-block!important}}@media (max-width:767px){.hidden-xs{display:none!important}}@media (min-width:768px) and (max-width:991px){.hidden-sm{display:none!important}}@media (min-width:992px) and (max-width:1199px){.hidden-md{display:none!important}}@media (min-width:1200px){.hidden-lg{display:none!important}}.visible-print{display:none!important}@media print{.visible-print{display:block!important}table.visible-print{display:table!important}tr.visible-print{display:table-row!important}td.visible-print,th.visible-print{display:table-cell!important}}.visible-print-block{display:none!important}@media print{.visible-print-block{display:block!important}}.visible-print-inline{display:none!important}@media print{.visible-print-inline{display:inline!important}}.visible-print-inline-block{display:none!important}@media print{.visible-print-inline-block{display:inline-block!important}}@media print{.hidden-print{display:none!important}}
+ */@media print{*,::after,::before{text-shadow:none!important;box-shadow:none!important}a,a:visited{text-decoration:underline}abbr[title]::after{content:" (" attr(title) ")"}pre{white-space:pre-wrap!important}blockquote,pre{border:1px solid #999;page-break-inside:avoid}thead{display:table-header-group}img,tr{page-break-inside:avoid}h2,h3,p{orphans:3;widows:3}h2,h3{page-break-after:avoid}.navbar{display:none}.badge{border:1px solid #000}.table{border-collapse:collapse!important}.table td,.table th{background-color:#fff!important}.table-bordered td,.table-bordered th{border:1px solid #ddd!important}}html{box-sizing:border-box;font-family:sans-serif;line-height:1.15;-webkit-text-size-adjust:100%;-ms-text-size-adjust:100%;-ms-overflow-style:scrollbar;-webkit-tap-highlight-color:transparent}*,::after,::before{box-sizing:inherit}@-ms-viewport{width:device-width}article,aside,dialog,figcaption,figure,footer,header,hgroup,main,nav,section{display:block}body{margin:0;font-family:-apple-system,BlinkMacSystemFont,"Segoe UI",Roboto,"Helvetica Neue",Arial,sans-serif;font-size:1rem;font-weight:400;line-height:1.5;color:#212529;background-color:#fff}[tabindex="-1"]:focus{outline:0!important}hr{box-sizing:content-box;height:0;overflow:visible}h1,h2,h3,h4,h5,h6{margin-top:0;margin-bottom:.5rem}p{margin-top:0;margin-bottom:1rem}abbr[data-original-title],abbr[title]{text-decoration:underline;-webkit-text-decoration:underline dotted;text-decoration:underline dotted;cursor:help;border-bottom:0}address{margin-bottom:1rem;font-style:normal;line-height:inherit}dl,ol,ul{margin-top:0;margin-bottom:1rem}ol ol,ol ul,ul ol,ul ul{margin-bottom:0}dt{font-weight:700}dd{margin-bottom:.5rem;margin-left:0}blockquote{margin:0 0 1rem}dfn{font-style:italic}b,strong{font-weight:bolder}small{font-size:80%}sub,sup{position:relative;font-size:75%;line-height:0;vertical-align:baseline}sub{bottom:-.25em}sup{top:-.5em}a{color:#007bff;text-decoration:none;background-color:transparent;-webkit-text-decoration-skip:objects}a:hover{color:#0056b3;text-decoration:underline}a:not([href]):not([tabindex]){color:inherit;text-decoration:none}a:not([href]):not([tabindex]):focus,a:not([href]):not([tabindex]):hover{color:inherit;text-decoration:none}a:not([href]):not([tabindex]):focus{outline:0}code,kbd,pre,samp{font-family:monospace,monospace;font-size:1em}pre{margin-top:0;margin-bottom:1rem;overflow:auto}figure{margin:0 0 1rem}img{vertical-align:middle;border-style:none}svg:not(:root){overflow:hidden}[role=button],a,area,button,input,label,select,summary,textarea{-ms-touch-action:manipulation;touch-action:manipulation}table{border-collapse:collapse}caption{padding-top:.75rem;padding-bottom:.75rem;color:#868e96;text-align:left;caption-side:bottom}th{text-align:left}label{display:inline-block;margin-bottom:.5rem}button:focus{outline:1px dotted;outline:5px auto -webkit-focus-ring-color}button,input,optgroup,select,textarea{margin:0;font-family:inherit;font-size:inherit;line-height:inherit}button,input{overflow:visible}button,select{text-transform:none}[type=reset],[type=submit],button,html [type=button]{-webkit-appearance:button}[type=button]::-moz-focus-inner,[type=reset]::-moz-focus-inner,[type=submit]::-moz-focus-inner,button::-moz-focus-inner{padding:0;border-style:none}input[type=checkbox],input[type=radio]{box-sizing:border-box;padding:0}input[type=date],input[type=datetime-local],input[type=month],input[type=time]{-webkit-appearance:listbox}textarea{overflow:auto;resize:vertical}fieldset{min-width:0;padding:0;margin:0;border:0}legend{display:block;width:100%;max-width:100%;padding:0;margin-bottom:.5rem;font-size:1.5rem;line-height:inherit;color:inherit;white-space:normal}progress{vertical-align:baseline}[type=number]::-webkit-inner-spin-button,[type=number]::-webkit-outer-spin-button{height:auto}[type=search]{outline-offset:-2px;-webkit-appearance:none}[type=search]::-webkit-search-cancel-button,[type=search]::-webkit-search-decoration{-webkit-appearance:none}::-webkit-file-upload-button{font:inherit;-webkit-appearance:button}output{display:inline-block}summary{display:list-item}template{display:none}[hidden]{display:none!important}.h1,.h2,.h3,.h4,.h5,.h6,h1,h2,h3,h4,h5,h6{margin-bottom:.5rem;font-family:inherit;font-weight:500;line-height:1.1;color:inherit}.h1,h1{font-size:2.5rem}.h2,h2{font-size:2rem}.h3,h3{font-size:1.75rem}.h4,h4{font-size:1.5rem}.h5,h5{font-size:1.25rem}.h6,h6{font-size:1rem}.lead{font-size:1.25rem;font-weight:300}.display-1{font-size:6rem;font-weight:300;line-height:1.1}.display-2{font-size:5.5rem;font-weight:300;line-height:1.1}.display-3{font-size:4.5rem;font-weight:300;line-height:1.1}.display-4{font-size:3.5rem;font-weight:300;line-height:1.1}hr{margin-top:1rem;margin-bottom:1rem;border:0;border-top:1px solid rgba(0,0,0,.1)}.small,small{font-size:80%;font-weight:400}.mark,mark{padding:.2em;background-color:#fcf8e3}.list-unstyled{padding-left:0;list-style:none}.list-inline{padding-left:0;list-style:none}.list-inline-item{display:inline-block}.list-inline-item:not(:last-child){margin-right:5px}.initialism{font-size:90%;text-transform:uppercase}.blockquote{margin-bottom:1rem;font-size:1.25rem}.blockquote-footer{display:block;font-size:80%;color:#868e96}.blockquote-footer::before{content:"\2014 \00A0"}.img-fluid{max-width:100%;height:auto}.img-thumbnail{padding:.25rem;background-color:#fff;border:1px solid #ddd;border-radius:.25rem;transition:all .2s ease-in-out;max-width:100%;height:auto}.figure{display:inline-block}.figure-img{margin-bottom:.5rem;line-height:1}.figure-caption{font-size:90%;color:#868e96}code,kbd,pre,samp{font-family:Menlo,Monaco,Consolas,"Liberation Mono","Courier New",monospace}code{padding:.2rem .4rem;font-size:90%;color:#bd4147;background-color:#f8f9fa;border-radius:.25rem}a>code{padding:0;color:inherit;background-color:inherit}kbd{padding:.2rem .4rem;font-size:90%;color:#fff;background-color:#212529;border-radius:.2rem}kbd kbd{padding:0;font-size:100%;font-weight:700}pre{display:block;margin-top:0;margin-bottom:1rem;font-size:90%;color:#212529}pre code{padding:0;font-size:inherit;color:inherit;background-color:transparent;border-radius:0}.pre-scrollable{max-height:340px;overflow-y:scroll}.container{margin-right:auto;margin-left:auto;padding-right:15px;padding-left:15px;width:100%}@media (min-width:576px){.container{max-width:540px}}@media (min-width:768px){.container{max-width:720px}}@media (min-width:992px){.container{max-width:960px}}@media (min-width:1200px){.container{max-width:1140px}}.container-fluid{width:100%;margin-right:auto;margin-left:auto;padding-right:15px;padding-left:15px;width:100%}.row{display:-ms-flexbox;display:flex;-ms-flex-wrap:wrap;flex-wrap:wrap;margin-right:-15px;margin-left:-15px}.no-gutters{margin-right:0;margin-left:0}.no-gutters>.col,.no-gutters>[class*=col-]{padding-right:0;padding-left:0}.col,.col-1,.col-10,.col-11,.col-12,.col-2,.col-3,.col-4,.col-5,.col-6,.col-7,.col-8,.col-9,.col-auto,.col-lg,.col-lg-1,.col-lg-10,.col-lg-11,.col-lg-12,.col-lg-2,.col-lg-3,.col-lg-4,.col-lg-5,.col-lg-6,.col-lg-7,.col-lg-8,.col-lg-9,.col-lg-auto,.col-md,.col-md-1,.col-md-10,.col-md-11,.col-md-12,.col-md-2,.col-md-3,.col-md-4,.col-md-5,.col-md-6,.col-md-7,.col-md-8,.col-md-9,.col-md-auto,.col-sm,.col-sm-1,.col-sm-10,.col-sm-11,.col-sm-12,.col-sm-2,.col-sm-3,.col-sm-4,.col-sm-5,.col-sm-6,.col-sm-7,.col-sm-8,.col-sm-9,.col-sm-auto,.col-xl,.col-xl-1,.col-xl-10,.col-xl-11,.col-xl-12,.col-xl-2,.col-xl-3,.col-xl-4,.col-xl-5,.col-xl-6,.col-xl-7,.col-xl-8,.col-xl-9,.col-xl-auto{position:relative;width:100%;min-height:1px;padding-right:15px;padding-left:15px}.col{-ms-flex-preferred-size:0;flex-basis:0;-ms-flex-positive:1;flex-grow:1;max-width:100%}.col-auto{-ms-flex:0 0 auto;flex:0 0 auto;width:auto;max-width:none}.col-1{-ms-flex:0 0 8.333333%;flex:0 0 8.333333%;max-width:8.333333%}.col-2{-ms-flex:0 0 16.666667%;flex:0 0 16.666667%;max-width:16.666667%}.col-3{-ms-flex:0 0 25%;flex:0 0 25%;max-width:25%}.col-4{-ms-flex:0 0 33.333333%;flex:0 0 33.333333%;max-width:33.333333%}.col-5{-ms-flex:0 0 41.666667%;flex:0 0 41.666667%;max-width:41.666667%}.col-6{-ms-flex:0 0 50%;flex:0 0 50%;max-width:50%}.col-7{-ms-flex:0 0 58.333333%;flex:0 0 58.333333%;max-width:58.333333%}.col-8{-ms-flex:0 0 66.666667%;flex:0 0 66.666667%;max-width:66.666667%}.col-9{-ms-flex:0 0 75%;flex:0 0 75%;max-width:75%}.col-10{-ms-flex:0 0 83.333333%;flex:0 0 83.333333%;max-width:83.333333%}.col-11{-ms-flex:0 0 91.666667%;flex:0 0 91.666667%;max-width:91.666667%}.col-12{-ms-flex:0 0 100%;flex:0 0 100%;max-width:100%}.order-1{-ms-flex-order:1;order:1}.order-2{-ms-flex-order:2;order:2}.order-3{-ms-flex-order:3;order:3}.order-4{-ms-flex-order:4;order:4}.order-5{-ms-flex-order:5;order:5}.order-6{-ms-flex-order:6;order:6}.order-7{-ms-flex-order:7;order:7}.order-8{-ms-flex-order:8;order:8}.order-9{-ms-flex-order:9;order:9}.order-10{-ms-flex-order:10;order:10}.order-11{-ms-flex-order:11;order:11}.order-12{-ms-flex-order:12;order:12}@media (min-width:576px){.col-sm{-ms-flex-preferred-size:0;flex-basis:0;-ms-flex-positive:1;flex-grow:1;max-width:100%}.col-sm-auto{-ms-flex:0 0 auto;flex:0 0 auto;width:auto;max-width:none}.col-sm-1{-ms-flex:0 0 8.333333%;flex:0 0 8.333333%;max-width:8.333333%}.col-sm-2{-ms-flex:0 0 16.666667%;flex:0 0 16.666667%;max-width:16.666667%}.col-sm-3{-ms-flex:0 0 25%;flex:0 0 25%;max-width:25%}.col-sm-4{-ms-flex:0 0 33.333333%;flex:0 0 33.333333%;max-width:33.333333%}.col-sm-5{-ms-flex:0 0 41.666667%;flex:0 0 41.666667%;max-width:41.666667%}.col-sm-6{-ms-flex:0 0 50%;flex:0 0 50%;max-width:50%}.col-sm-7{-ms-flex:0 0 58.333333%;flex:0 0 58.333333%;max-width:58.333333%}.col-sm-8{-ms-flex:0 0 66.666667%;flex:0 0 66.666667%;max-width:66.666667%}.col-sm-9{-ms-flex:0 0 75%;flex:0 0 75%;max-width:75%}.col-sm-10{-ms-flex:0 0 83.333333%;flex:0 0 83.333333%;max-width:83.333333%}.col-sm-11{-ms-flex:0 0 91.666667%;flex:0 0 91.666667%;max-width:91.666667%}.col-sm-12{-ms-flex:0 0 100%;flex:0 0 100%;max-width:100%}.order-sm-1{-ms-flex-order:1;order:1}.order-sm-2{-ms-flex-order:2;order:2}.order-sm-3{-ms-flex-order:3;order:3}.order-sm-4{-ms-flex-order:4;order:4}.order-sm-5{-ms-flex-order:5;order:5}.order-sm-6{-ms-flex-order:6;order:6}.order-sm-7{-ms-flex-order:7;order:7}.order-sm-8{-ms-flex-order:8;order:8}.order-sm-9{-ms-flex-order:9;order:9}.order-sm-10{-ms-flex-order:10;order:10}.order-sm-11{-ms-flex-order:11;order:11}.order-sm-12{-ms-flex-order:12;order:12}}@media (min-width:768px){.col-md{-ms-flex-preferred-size:0;flex-basis:0;-ms-flex-positive:1;flex-grow:1;max-width:100%}.col-md-auto{-ms-flex:0 0 auto;flex:0 0 auto;width:auto;max-width:none}.col-md-1{-ms-flex:0 0 8.333333%;flex:0 0 8.333333%;max-width:8.333333%}.col-md-2{-ms-flex:0 0 16.666667%;flex:0 0 16.666667%;max-width:16.666667%}.col-md-3{-ms-flex:0 0 25%;flex:0 0 25%;max-width:25%}.col-md-4{-ms-flex:0 0 33.333333%;flex:0 0 33.333333%;max-width:33.333333%}.col-md-5{-ms-flex:0 0 41.666667%;flex:0 0 41.666667%;max-width:41.666667%}.col-md-6{-ms-flex:0 0 50%;flex:0 0 50%;max-width:50%}.col-md-7{-ms-flex:0 0 58.333333%;flex:0 0 58.333333%;max-width:58.333333%}.col-md-8{-ms-flex:0 0 66.666667%;flex:0 0 66.666667%;max-width:66.666667%}.col-md-9{-ms-flex:0 0 75%;flex:0 0 75%;max-width:75%}.col-md-10{-ms-flex:0 0 83.333333%;flex:0 0 83.333333%;max-width:83.333333%}.col-md-11{-ms-flex:0 0 91.666667%;flex:0 0 91.666667%;max-width:91.666667%}.col-md-12{-ms-flex:0 0 100%;flex:0 0 100%;max-width:100%}.order-md-1{-ms-flex-order:1;order:1}.order-md-2{-ms-flex-order:2;order:2}.order-md-3{-ms-flex-order:3;order:3}.order-md-4{-ms-flex-order:4;order:4}.order-md-5{-ms-flex-order:5;order:5}.order-md-6{-ms-flex-order:6;order:6}.order-md-7{-ms-flex-order:7;order:7}.order-md-8{-ms-flex-order:8;order:8}.order-md-9{-ms-flex-order:9;order:9}.order-md-10{-ms-flex-order:10;order:10}.order-md-11{-ms-flex-order:11;order:11}.order-md-12{-ms-flex-order:12;order:12}}@media (min-width:992px){.col-lg{-ms-flex-preferred-size:0;flex-basis:0;-ms-flex-positive:1;flex-grow:1;max-width:100%}.col-lg-auto{-ms-flex:0 0 auto;flex:0 0 auto;width:auto;max-width:none}.col-lg-1{-ms-flex:0 0 8.333333%;flex:0 0 8.333333%;max-width:8.333333%}.col-lg-2{-ms-flex:0 0 16.666667%;flex:0 0 16.666667%;max-width:16.666667%}.col-lg-3{-ms-flex:0 0 25%;flex:0 0 25%;max-width:25%}.col-lg-4{-ms-flex:0 0 33.333333%;flex:0 0 33.333333%;max-width:33.333333%}.col-lg-5{-ms-flex:0 0 41.666667%;flex:0 0 41.666667%;max-width:41.666667%}.col-lg-6{-ms-flex:0 0 50%;flex:0 0 50%;max-width:50%}.col-lg-7{-ms-flex:0 0 58.333333%;flex:0 0 58.333333%;max-width:58.333333%}.col-lg-8{-ms-flex:0 0 66.666667%;flex:0 0 66.666667%;max-width:66.666667%}.col-lg-9{-ms-flex:0 0 75%;flex:0 0 75%;max-width:75%}.col-lg-10{-ms-flex:0 0 83.333333%;flex:0 0 83.333333%;max-width:83.333333%}.col-lg-11{-ms-flex:0 0 91.666667%;flex:0 0 91.666667%;max-width:91.666667%}.col-lg-12{-ms-flex:0 0 100%;flex:0 0 100%;max-width:100%}.order-lg-1{-ms-flex-order:1;order:1}.order-lg-2{-ms-flex-order:2;order:2}.order-lg-3{-ms-flex-order:3;order:3}.order-lg-4{-ms-flex-order:4;order:4}.order-lg-5{-ms-flex-order:5;order:5}.order-lg-6{-ms-flex-order:6;order:6}.order-lg-7{-ms-flex-order:7;order:7}.order-lg-8{-ms-flex-order:8;order:8}.order-lg-9{-ms-flex-order:9;order:9}.order-lg-10{-ms-flex-order:10;order:10}.order-lg-11{-ms-flex-order:11;order:11}.order-lg-12{-ms-flex-order:12;order:12}}@media (min-width:1200px){.col-xl{-ms-flex-preferred-size:0;flex-basis:0;-ms-flex-positive:1;flex-grow:1;max-width:100%}.col-xl-auto{-ms-flex:0 0 auto;flex:0 0 auto;width:auto;max-width:none}.col-xl-1{-ms-flex:0 0 8.333333%;flex:0 0 8.333333%;max-width:8.333333%}.col-xl-2{-ms-flex:0 0 16.666667%;flex:0 0 16.666667%;max-width:16.666667%}.col-xl-3{-ms-flex:0 0 25%;flex:0 0 25%;max-width:25%}.col-xl-4{-ms-flex:0 0 33.333333%;flex:0 0 33.333333%;max-width:33.333333%}.col-xl-5{-ms-flex:0 0 41.666667%;flex:0 0 41.666667%;max-width:41.666667%}.col-xl-6{-ms-flex:0 0 50%;flex:0 0 50%;max-width:50%}.col-xl-7{-ms-flex:0 0 58.333333%;flex:0 0 58.333333%;max-width:58.333333%}.col-xl-8{-ms-flex:0 0 66.666667%;flex:0 0 66.666667%;max-width:66.666667%}.col-xl-9{-ms-flex:0 0 75%;flex:0 0 75%;max-width:75%}.col-xl-10{-ms-flex:0 0 83.333333%;flex:0 0 83.333333%;max-width:83.333333%}.col-xl-11{-ms-flex:0 0 91.666667%;flex:0 0 91.666667%;max-width:91.666667%}.col-xl-12{-ms-flex:0 0 100%;flex:0 0 100%;max-width:100%}.order-xl-1{-ms-flex-order:1;order:1}.order-xl-2{-ms-flex-order:2;order:2}.order-xl-3{-ms-flex-order:3;order:3}.order-xl-4{-ms-flex-order:4;order:4}.order-xl-5{-ms-flex-order:5;order:5}.order-xl-6{-ms-flex-order:6;order:6}.order-xl-7{-ms-flex-order:7;order:7}.order-xl-8{-ms-flex-order:8;order:8}.order-xl-9{-ms-flex-order:9;order:9}.order-xl-10{-ms-flex-order:10;order:10}.order-xl-11{-ms-flex-order:11;order:11}.order-xl-12{-ms-flex-order:12;order:12}}.table{width:100%;max-width:100%;margin-bottom:1rem;background-color:transparent}.table td,.table th{padding:.75rem;vertical-align:top;border-top:1px solid #e9ecef}.table thead th{vertical-align:bottom;border-bottom:2px solid #e9ecef}.table tbody+tbody{border-top:2px solid #e9ecef}.table .table{background-color:#fff}.table-sm td,.table-sm th{padding:.3rem}.table-bordered{border:1px solid #e9ecef}.table-bordered td,.table-bordered th{border:1px solid #e9ecef}.table-bordered thead td,.table-bordered thead th{border-bottom-width:2px}.table-striped tbody tr:nth-of-type(odd){background-color:rgba(0,0,0,.05)}.table-hover tbody tr:hover{background-color:rgba(0,0,0,.075)}.table-primary,.table-primary>td,.table-primary>th{background-color:#b8daff}.table-hover .table-primary:hover{background-color:#9fcdff}.table-hover .table-primary:hover>td,.table-hover .table-primary:hover>th{background-color:#9fcdff}.table-secondary,.table-secondary>td,.table-secondary>th{background-color:#dddfe2}.table-hover .table-secondary:hover{background-color:#cfd2d6}.table-hover .table-secondary:hover>td,.table-hover .table-secondary:hover>th{background-color:#cfd2d6}.table-success,.table-success>td,.table-success>th{background-color:#c3e6cb}.table-hover .table-success:hover{background-color:#b1dfbb}.table-hover .table-success:hover>td,.table-hover .table-success:hover>th{background-color:#b1dfbb}.table-info,.table-info>td,.table-info>th{background-color:#bee5eb}.table-hover .table-info:hover{background-color:#abdde5}.table-hover .table-info:hover>td,.table-hover .table-info:hover>th{background-color:#abdde5}.table-warning,.table-warning>td,.table-warning>th{background-color:#ffeeba}.table-hover .table-warning:hover{background-color:#ffe8a1}.table-hover .table-warning:hover>td,.table-hover .table-warning:hover>th{background-color:#ffe8a1}.table-danger,.table-danger>td,.table-danger>th{background-color:#f5c6cb}.table-hover .table-danger:hover{background-color:#f1b0b7}.table-hover .table-danger:hover>td,.table-hover .table-danger:hover>th{background-color:#f1b0b7}.table-light,.table-light>td,.table-light>th{background-color:#fdfdfe}.table-hover .table-light:hover{background-color:#ececf6}.table-hover .table-light:hover>td,.table-hover .table-light:hover>th{background-color:#ececf6}.table-dark,.table-dark>td,.table-dark>th{background-color:#c6c8ca}.table-hover .table-dark:hover{background-color:#b9bbbe}.table-hover .table-dark:hover>td,.table-hover .table-dark:hover>th{background-color:#b9bbbe}.table-active,.table-active>td,.table-active>th{background-color:rgba(0,0,0,.075)}.table-hover .table-active:hover{background-color:rgba(0,0,0,.075)}.table-hover .table-active:hover>td,.table-hover .table-active:hover>th{background-color:rgba(0,0,0,.075)}.thead-inverse th{color:#fff;background-color:#212529}.thead-default th{color:#495057;background-color:#e9ecef}.table-inverse{color:#fff;background-color:#212529}.table-inverse td,.table-inverse th,.table-inverse thead th{border-color:#32383e}.table-inverse.table-bordered{border:0}.table-inverse.table-striped tbody tr:nth-of-type(odd){background-color:rgba(255,255,255,.05)}.table-inverse.table-hover tbody tr:hover{background-color:rgba(255,255,255,.075)}@media (max-width:991px){.table-responsive{display:block;width:100%;overflow-x:auto;-ms-overflow-style:-ms-autohiding-scrollbar}.table-responsive.table-bordered{border:0}}.form-control{display:block;width:100%;padding:.5rem .75rem;font-size:1rem;line-height:1.25;color:#495057;background-color:#fff;background-image:none;background-clip:padding-box;border:1px solid rgba(0,0,0,.15);border-radius:.25rem;transition:border-color ease-in-out .15s,box-shadow ease-in-out .15s}.form-control::-ms-expand{background-color:transparent;border:0}.form-control:focus{color:#495057;background-color:#fff;border-color:#80bdff;outline:0}.form-control::-webkit-input-placeholder{color:#868e96;opacity:1}.form-control:-ms-input-placeholder{color:#868e96;opacity:1}.form-control::placeholder{color:#868e96;opacity:1}.form-control:disabled,.form-control[readonly]{background-color:#e9ecef;opacity:1}select.form-control:not([size]):not([multiple]){height:calc(2.25rem + 2px)}select.form-control:focus::-ms-value{color:#495057;background-color:#fff}.form-control-file,.form-control-range{display:block}.col-form-label{padding-top:calc(.5rem - 1px * 2);padding-bottom:calc(.5rem - 1px * 2);margin-bottom:0}.col-form-label-lg{padding-top:calc(.5rem - 1px * 2);padding-bottom:calc(.5rem - 1px * 2);font-size:1.25rem}.col-form-label-sm{padding-top:calc(.25rem - 1px * 2);padding-bottom:calc(.25rem - 1px * 2);font-size:.875rem}.col-form-legend{padding-top:.5rem;padding-bottom:.5rem;margin-bottom:0;font-size:1rem}.form-control-plaintext{padding-top:.5rem;padding-bottom:.5rem;margin-bottom:0;line-height:1.25;border:solid transparent;border-width:1px 0}.form-control-plaintext.form-control-lg,.form-control-plaintext.form-control-sm,.input-group-lg>.form-control-plaintext.form-control,.input-group-lg>.form-control-plaintext.input-group-addon,.input-group-lg>.input-group-btn>.form-control-plaintext.btn,.input-group-sm>.form-control-plaintext.form-control,.input-group-sm>.form-control-plaintext.input-group-addon,.input-group-sm>.input-group-btn>.form-control-plaintext.btn{padding-right:0;padding-left:0}.form-control-sm,.input-group-sm>.form-control,.input-group-sm>.input-group-addon,.input-group-sm>.input-group-btn>.btn{padding:.25rem .5rem;font-size:.875rem;line-height:1.5;border-radius:.2rem}.input-group-sm>.input-group-btn>select.btn:not([size]):not([multiple]),.input-group-sm>select.form-control:not([size]):not([multiple]),.input-group-sm>select.input-group-addon:not([size]):not([multiple]),select.form-control-sm:not([size]):not([multiple]){height:calc(1.8125rem + 2px)}.form-control-lg,.input-group-lg>.form-control,.input-group-lg>.input-group-addon,.input-group-lg>.input-group-btn>.btn{padding:.5rem 1rem;font-size:1.25rem;line-height:1.5;border-radius:.3rem}.input-group-lg>.input-group-btn>select.btn:not([size]):not([multiple]),.input-group-lg>select.form-control:not([size]):not([multiple]),.input-group-lg>select.input-group-addon:not([size]):not([multiple]),select.form-control-lg:not([size]):not([multiple]){height:calc(2.3125rem + 2px)}.form-group{margin-bottom:1rem}.form-text{display:block;margin-top:.25rem}.form-row{display:-ms-flexbox;display:flex;-ms-flex-wrap:wrap;flex-wrap:wrap;margin-right:-5px;margin-left:-5px}.form-row>.col,.form-row>[class*=col-]{padding-right:5px;padding-left:5px}.form-check{position:relative;display:block;margin-bottom:.5rem}.form-check.disabled .form-check-label{color:#868e96}.form-check-label{padding-left:1.25rem;margin-bottom:0}.form-check-input{position:absolute;margin-top:.25rem;margin-left:-1.25rem}.form-check-input:only-child{position:static}.form-check-inline{display:inline-block}.form-check-inline .form-check-label{vertical-align:middle}.form-check-inline+.form-check-inline{margin-left:.75rem}.invalid-feedback{display:none;margin-top:.25rem;font-size:.875rem;color:#dc3545}.invalid-tooltip{position:absolute;top:100%;z-index:5;display:none;width:250px;padding:.5rem;margin-top:.1rem;font-size:.875rem;line-height:1;color:#fff;background-color:rgba(220,53,69,.8);border-radius:.2rem}.custom-select.is-valid,.form-control.is-valid,.was-validated .custom-select:valid,.was-validated .form-control:valid{border-color:#28a745}.custom-select.is-valid:focus,.form-control.is-valid:focus,.was-validated .custom-select:valid:focus,.was-validated .form-control:valid:focus{box-shadow:0 0 0 .2rem rgba(40,167,69,.25)}.custom-select.is-valid~.invalid-feedback,.custom-select.is-valid~.invalid-tooltip,.form-control.is-valid~.invalid-feedback,.form-control.is-valid~.invalid-tooltip,.was-validated .custom-select:valid~.invalid-feedback,.was-validated .custom-select:valid~.invalid-tooltip,.was-validated .form-control:valid~.invalid-feedback,.was-validated .form-control:valid~.invalid-tooltip{display:block}.form-check-input.is-valid+.form-check-label,.was-validated .form-check-input:valid+.form-check-label{color:#28a745}.custom-control-input.is-valid~.custom-control-indicator,.was-validated .custom-control-input:valid~.custom-control-indicator{background-color:rgba(40,167,69,.25)}.custom-control-input.is-valid~.custom-control-description,.was-validated .custom-control-input:valid~.custom-control-description{color:#28a745}.custom-file-input.is-valid~.custom-file-control,.was-validated .custom-file-input:valid~.custom-file-control{border-color:#28a745}.custom-file-input.is-valid~.custom-file-control::before,.was-validated .custom-file-input:valid~.custom-file-control::before{border-color:inherit}.custom-file-input.is-valid:focus,.was-validated .custom-file-input:valid:focus{box-shadow:0 0 0 .2rem rgba(40,167,69,.25)}.custom-select.is-invalid,.form-control.is-invalid,.was-validated .custom-select:invalid,.was-validated .form-control:invalid{border-color:#dc3545}.custom-select.is-invalid:focus,.form-control.is-invalid:focus,.was-validated .custom-select:invalid:focus,.was-validated .form-control:invalid:focus{box-shadow:0 0 0 .2rem rgba(220,53,69,.25)}.custom-select.is-invalid~.invalid-feedback,.custom-select.is-invalid~.invalid-tooltip,.form-control.is-invalid~.invalid-feedback,.form-control.is-invalid~.invalid-tooltip,.was-validated .custom-select:invalid~.invalid-feedback,.was-validated .custom-select:invalid~.invalid-tooltip,.was-validated .form-control:invalid~.invalid-feedback,.was-validated .form-control:invalid~.invalid-tooltip{display:block}.form-check-input.is-invalid+.form-check-label,.was-validated .form-check-input:invalid+.form-check-label{color:#dc3545}.custom-control-input.is-invalid~.custom-control-indicator,.was-validated .custom-control-input:invalid~.custom-control-indicator{background-color:rgba(220,53,69,.25)}.custom-control-input.is-invalid~.custom-control-description,.was-validated .custom-control-input:invalid~.custom-control-description{color:#dc3545}.custom-file-input.is-invalid~.custom-file-control,.was-validated .custom-file-input:invalid~.custom-file-control{border-color:#dc3545}.custom-file-input.is-invalid~.custom-file-control::before,.was-validated .custom-file-input:invalid~.custom-file-control::before{border-color:inherit}.custom-file-input.is-invalid:focus,.was-validated .custom-file-input:invalid:focus{box-shadow:0 0 0 .2rem rgba(220,53,69,.25)}.form-inline{display:-ms-flexbox;display:flex;-ms-flex-flow:row wrap;flex-flow:row wrap;-ms-flex-align:center;align-items:center}.form-inline .form-check{width:100%}@media (min-width:576px){.form-inline label{display:-ms-flexbox;display:flex;-ms-flex-align:center;align-items:center;-ms-flex-pack:center;justify-content:center;margin-bottom:0}.form-inline .form-group{display:-ms-flexbox;display:flex;-ms-flex:0 0 auto;flex:0 0 auto;-ms-flex-flow:row wrap;flex-flow:row wrap;-ms-flex-align:center;align-items:center;margin-bottom:0}.form-inline .form-control{display:inline-block;width:auto;vertical-align:middle}.form-inline .form-control-plaintext{display:inline-block}.form-inline .input-group{width:auto}.form-inline .form-control-label{margin-bottom:0;vertical-align:middle}.form-inline .form-check{display:-ms-flexbox;display:flex;-ms-flex-align:center;align-items:center;-ms-flex-pack:center;justify-content:center;width:auto;margin-top:0;margin-bottom:0}.form-inline .form-check-label{padding-left:0}.form-inline .form-check-input{position:relative;margin-top:0;margin-right:.25rem;margin-left:0}.form-inline .custom-control{display:-ms-flexbox;display:flex;-ms-flex-align:center;align-items:center;-ms-flex-pack:center;justify-content:center;padding-left:0}.form-inline .custom-control-indicator{position:static;display:inline-block;margin-right:.25rem;vertical-align:text-bottom}.form-inline .has-feedback .form-control-feedback{top:0}}.btn{display:inline-block;font-weight:400;text-align:center;white-space:nowrap;vertical-align:middle;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;border:1px solid transparent;padding:.5rem .75rem;font-size:1rem;line-height:1.25;border-radius:.25rem;transition:all .15s ease-in-out}.btn:focus,.btn:hover{text-decoration:none}.btn.focus,.btn:focus{outline:0;box-shadow:0 0 0 3px rgba(0,123,255,.25)}.btn.disabled,.btn:disabled{opacity:.65}.btn.active,.btn:active{background-image:none}a.btn.disabled,fieldset[disabled] a.btn{pointer-events:none}.btn-primary{color:#fff;background-color:#007bff;border-color:#007bff}.btn-primary:hover{color:#fff;background-color:#0069d9;border-color:#0062cc}.btn-primary.focus,.btn-primary:focus{box-shadow:0 0 0 3px rgba(0,123,255,.5)}.btn-primary.disabled,.btn-primary:disabled{background-color:#007bff;border-color:#007bff}.btn-primary.active,.btn-primary:active,.show>.btn-primary.dropdown-toggle{background-color:#0069d9;background-image:none;border-color:#0062cc}.btn-secondary{color:#fff;background-color:#868e96;border-color:#868e96}.btn-secondary:hover{color:#fff;background-color:#727b84;border-color:#6c757d}.btn-secondary.focus,.btn-secondary:focus{box-shadow:0 0 0 3px rgba(134,142,150,.5)}.btn-secondary.disabled,.btn-secondary:disabled{background-color:#868e96;border-color:#868e96}.btn-secondary.active,.btn-secondary:active,.show>.btn-secondary.dropdown-toggle{background-color:#727b84;background-image:none;border-color:#6c757d}.btn-success{color:#fff;background-color:#28a745;border-color:#28a745}.btn-success:hover{color:#fff;background-color:#218838;border-color:#1e7e34}.btn-success.focus,.btn-success:focus{box-shadow:0 0 0 3px rgba(40,167,69,.5)}.btn-success.disabled,.btn-success:disabled{background-color:#28a745;border-color:#28a745}.btn-success.active,.btn-success:active,.show>.btn-success.dropdown-toggle{background-color:#218838;background-image:none;border-color:#1e7e34}.btn-info{color:#fff;background-color:#17a2b8;border-color:#17a2b8}.btn-info:hover{color:#fff;background-color:#138496;border-color:#117a8b}.btn-info.focus,.btn-info:focus{box-shadow:0 0 0 3px rgba(23,162,184,.5)}.btn-info.disabled,.btn-info:disabled{background-color:#17a2b8;border-color:#17a2b8}.btn-info.active,.btn-info:active,.show>.btn-info.dropdown-toggle{background-color:#138496;background-image:none;border-color:#117a8b}.btn-warning{color:#111;background-color:#ffc107;border-color:#ffc107}.btn-warning:hover{color:#111;background-color:#e0a800;border-color:#d39e00}.btn-warning.focus,.btn-warning:focus{box-shadow:0 0 0 3px rgba(255,193,7,.5)}.btn-warning.disabled,.btn-warning:disabled{background-color:#ffc107;border-color:#ffc107}.btn-warning.active,.btn-warning:active,.show>.btn-warning.dropdown-toggle{background-color:#e0a800;background-image:none;border-color:#d39e00}.btn-danger{color:#fff;background-color:#dc3545;border-color:#dc3545}.btn-danger:hover{color:#fff;background-color:#c82333;border-color:#bd2130}.btn-danger.focus,.btn-danger:focus{box-shadow:0 0 0 3px rgba(220,53,69,.5)}.btn-danger.disabled,.btn-danger:disabled{background-color:#dc3545;border-color:#dc3545}.btn-danger.active,.btn-danger:active,.show>.btn-danger.dropdown-toggle{background-color:#c82333;background-image:none;border-color:#bd2130}.btn-light{color:#111;background-color:#f8f9fa;border-color:#f8f9fa}.btn-light:hover{color:#111;background-color:#e2e6ea;border-color:#dae0e5}.btn-light.focus,.btn-light:focus{box-shadow:0 0 0 3px rgba(248,249,250,.5)}.btn-light.disabled,.btn-light:disabled{background-color:#f8f9fa;border-color:#f8f9fa}.btn-light.active,.btn-light:active,.show>.btn-light.dropdown-toggle{background-color:#e2e6ea;background-image:none;border-color:#dae0e5}.btn-dark{color:#fff;background-color:#343a40;border-color:#343a40}.btn-dark:hover{color:#fff;background-color:#23272b;border-color:#1d2124}.btn-dark.focus,.btn-dark:focus{box-shadow:0 0 0 3px rgba(52,58,64,.5)}.btn-dark.disabled,.btn-dark:disabled{background-color:#343a40;border-color:#343a40}.btn-dark.active,.btn-dark:active,.show>.btn-dark.dropdown-toggle{background-color:#23272b;background-image:none;border-color:#1d2124}.btn-outline-primary{color:#007bff;background-color:transparent;background-image:none;border-color:#007bff}.btn-outline-primary:hover{color:#fff;background-color:#007bff;border-color:#007bff}.btn-outline-primary.focus,.btn-outline-primary:focus{box-shadow:0 0 0 3px rgba(0,123,255,.5)}.btn-outline-primary.disabled,.btn-outline-primary:disabled{color:#007bff;background-color:transparent}.btn-outline-primary.active,.btn-outline-primary:active,.show>.btn-outline-primary.dropdown-toggle{color:#fff;background-color:#007bff;border-color:#007bff}.btn-outline-secondary{color:#868e96;background-color:transparent;background-image:none;border-color:#868e96}.btn-outline-secondary:hover{color:#fff;background-color:#868e96;border-color:#868e96}.btn-outline-secondary.focus,.btn-outline-secondary:focus{box-shadow:0 0 0 3px rgba(134,142,150,.5)}.btn-outline-secondary.disabled,.btn-outline-secondary:disabled{color:#868e96;background-color:transparent}.btn-outline-secondary.active,.btn-outline-secondary:active,.show>.btn-outline-secondary.dropdown-toggle{color:#fff;background-color:#868e96;border-color:#868e96}.btn-outline-success{color:#28a745;background-color:transparent;background-image:none;border-color:#28a745}.btn-outline-success:hover{color:#fff;background-color:#28a745;border-color:#28a745}.btn-outline-success.focus,.btn-outline-success:focus{box-shadow:0 0 0 3px rgba(40,167,69,.5)}.btn-outline-success.disabled,.btn-outline-success:disabled{color:#28a745;background-color:transparent}.btn-outline-success.active,.btn-outline-success:active,.show>.btn-outline-success.dropdown-toggle{color:#fff;background-color:#28a745;border-color:#28a745}.btn-outline-info{color:#17a2b8;background-color:transparent;background-image:none;border-color:#17a2b8}.btn-outline-info:hover{color:#fff;background-color:#17a2b8;border-color:#17a2b8}.btn-outline-info.focus,.btn-outline-info:focus{box-shadow:0 0 0 3px rgba(23,162,184,.5)}.btn-outline-info.disabled,.btn-outline-info:disabled{color:#17a2b8;background-color:transparent}.btn-outline-info.active,.btn-outline-info:active,.show>.btn-outline-info.dropdown-toggle{color:#fff;background-color:#17a2b8;border-color:#17a2b8}.btn-outline-warning{color:#ffc107;background-color:transparent;background-image:none;border-color:#ffc107}.btn-outline-warning:hover{color:#fff;background-color:#ffc107;border-color:#ffc107}.btn-outline-warning.focus,.btn-outline-warning:focus{box-shadow:0 0 0 3px rgba(255,193,7,.5)}.btn-outline-warning.disabled,.btn-outline-warning:disabled{color:#ffc107;background-color:transparent}.btn-outline-warning.active,.btn-outline-warning:active,.show>.btn-outline-warning.dropdown-toggle{color:#fff;background-color:#ffc107;border-color:#ffc107}.btn-outline-danger{color:#dc3545;background-color:transparent;background-image:none;border-color:#dc3545}.btn-outline-danger:hover{color:#fff;background-color:#dc3545;border-color:#dc3545}.btn-outline-danger.focus,.btn-outline-danger:focus{box-shadow:0 0 0 3px rgba(220,53,69,.5)}.btn-outline-danger.disabled,.btn-outline-danger:disabled{color:#dc3545;background-color:transparent}.btn-outline-danger.active,.btn-outline-danger:active,.show>.btn-outline-danger.dropdown-toggle{color:#fff;background-color:#dc3545;border-color:#dc3545}.btn-outline-light{color:#f8f9fa;background-color:transparent;background-image:none;border-color:#f8f9fa}.btn-outline-light:hover{color:#fff;background-color:#f8f9fa;border-color:#f8f9fa}.btn-outline-light.focus,.btn-outline-light:focus{box-shadow:0 0 0 3px rgba(248,249,250,.5)}.btn-outline-light.disabled,.btn-outline-light:disabled{color:#f8f9fa;background-color:transparent}.btn-outline-light.active,.btn-outline-light:active,.show>.btn-outline-light.dropdown-toggle{color:#fff;background-color:#f8f9fa;border-color:#f8f9fa}.btn-outline-dark{color:#343a40;background-color:transparent;background-image:none;border-color:#343a40}.btn-outline-dark:hover{color:#fff;background-color:#343a40;border-color:#343a40}.btn-outline-dark.focus,.btn-outline-dark:focus{box-shadow:0 0 0 3px rgba(52,58,64,.5)}.btn-outline-dark.disabled,.btn-outline-dark:disabled{color:#343a40;background-color:transparent}.btn-outline-dark.active,.btn-outline-dark:active,.show>.btn-outline-dark.dropdown-toggle{color:#fff;background-color:#343a40;border-color:#343a40}.btn-link{font-weight:400;color:#007bff;border-radius:0}.btn-link,.btn-link.active,.btn-link:active,.btn-link:disabled{background-color:transparent}.btn-link,.btn-link:active,.btn-link:focus{border-color:transparent;box-shadow:none}.btn-link:hover{border-color:transparent}.btn-link:focus,.btn-link:hover{color:#0056b3;text-decoration:underline;background-color:transparent}.btn-link:disabled{color:#868e96}.btn-link:disabled:focus,.btn-link:disabled:hover{text-decoration:none}.btn-group-lg>.btn,.btn-lg{padding:.5rem 1rem;font-size:1.25rem;line-height:1.5;border-radius:.3rem}.btn-group-sm>.btn,.btn-sm{padding:.25rem .5rem;font-size:.875rem;line-height:1.5;border-radius:.2rem}.btn-block{display:block;width:100%}.btn-block+.btn-block{margin-top:.5rem}input[type=button].btn-block,input[type=reset].btn-block,input[type=submit].btn-block{width:100%}.fade{opacity:0;transition:opacity .15s linear}.fade.show{opacity:1}.collapse{display:none}.collapse.show{display:block}tr.collapse.show{display:table-row}tbody.collapse.show{display:table-row-group}.collapsing{position:relative;height:0;overflow:hidden;transition:height .35s ease}.dropdown,.dropup{position:relative}.dropdown-toggle::after{display:inline-block;width:0;height:0;margin-left:.255em;vertical-align:.255em;content:"";border-top:.3em solid;border-right:.3em solid transparent;border-left:.3em solid transparent}.dropdown-toggle:empty::after{margin-left:0}.dropup .dropdown-menu{margin-top:0;margin-bottom:.125rem}.dropup .dropdown-toggle::after{border-top:0;border-bottom:.3em solid}.dropdown-menu{position:absolute;top:100%;left:0;z-index:1000;display:none;float:left;min-width:10rem;padding:.5rem 0;margin:.125rem 0 0;font-size:1rem;color:#212529;text-align:left;list-style:none;background-color:#fff;background-clip:padding-box;border:1px solid rgba(0,0,0,.15);border-radius:.25rem}.dropdown-divider{height:0;margin:.5rem 0;overflow:hidden;border-top:1px solid #e9ecef}.dropdown-item{display:block;width:100%;padding:.25rem 1.5rem;clear:both;font-weight:400;color:#212529;text-align:inherit;white-space:nowrap;background:0 0;border:0}.dropdown-item:focus,.dropdown-item:hover{color:#16181b;text-decoration:none;background-color:#f8f9fa}.dropdown-item.active,.dropdown-item:active{color:#fff;text-decoration:none;background-color:#007bff}.dropdown-item.disabled,.dropdown-item:disabled{color:#868e96;background-color:transparent}.show>a{outline:0}.dropdown-menu.show{display:block}.dropdown-header{display:block;padding:.5rem 1.5rem;margin-bottom:0;font-size:.875rem;color:#868e96;white-space:nowrap}.btn-group,.btn-group-vertical{position:relative;display:-ms-inline-flexbox;display:inline-flex;vertical-align:middle}.btn-group-vertical>.btn,.btn-group>.btn{position:relative;-ms-flex:0 1 auto;flex:0 1 auto;margin-bottom:0}.btn-group-vertical>.btn:hover,.btn-group>.btn:hover{z-index:2}.btn-group-vertical>.btn.active,.btn-group-vertical>.btn:active,.btn-group-vertical>.btn:focus,.btn-group>.btn.active,.btn-group>.btn:active,.btn-group>.btn:focus{z-index:2}.btn-group .btn+.btn,.btn-group .btn+.btn-group,.btn-group .btn-group+.btn,.btn-group .btn-group+.btn-group,.btn-group-vertical .btn+.btn,.btn-group-vertical .btn+.btn-group,.btn-group-vertical .btn-group+.btn,.btn-group-vertical .btn-group+.btn-group{margin-left:-1px}.btn-toolbar{display:-ms-flexbox;display:flex;-ms-flex-wrap:wrap;flex-wrap:wrap;-ms-flex-pack:start;justify-content:flex-start}.btn-toolbar .input-group{width:auto}.btn-group>.btn:not(:first-child):not(:last-child):not(.dropdown-toggle){border-radius:0}.btn-group>.btn:first-child{margin-left:0}.btn-group>.btn:first-child:not(:last-child):not(.dropdown-toggle){border-top-right-radius:0;border-bottom-right-radius:0}.btn-group>.btn:last-child:not(:first-child),.btn-group>.dropdown-toggle:not(:first-child){border-top-left-radius:0;border-bottom-left-radius:0}.btn-group>.btn-group{float:left}.btn-group>.btn-group:not(:first-child):not(:last-child)>.btn{border-radius:0}.btn-group>.btn-group:first-child:not(:last-child)>.btn:last-child,.btn-group>.btn-group:first-child:not(:last-child)>.dropdown-toggle{border-top-right-radius:0;border-bottom-right-radius:0}.btn-group>.btn-group:last-child:not(:first-child)>.btn:first-child{border-top-left-radius:0;border-bottom-left-radius:0}.btn+.dropdown-toggle-split{padding-right:.5625rem;padding-left:.5625rem}.btn+.dropdown-toggle-split::after{margin-left:0}.btn-group-sm>.btn+.dropdown-toggle-split,.btn-sm+.dropdown-toggle-split{padding-right:.375rem;padding-left:.375rem}.btn-group-lg>.btn+.dropdown-toggle-split,.btn-lg+.dropdown-toggle-split{padding-right:.75rem;padding-left:.75rem}.btn-group-vertical{display:-ms-inline-flexbox;display:inline-flex;-ms-flex-direction:column;flex-direction:column;-ms-flex-align:start;align-items:flex-start;-ms-flex-pack:center;justify-content:center}.btn-group-vertical .btn,.btn-group-vertical .btn-group{width:100%}.btn-group-vertical>.btn+.btn,.btn-group-vertical>.btn+.btn-group,.btn-group-vertical>.btn-group+.btn,.btn-group-vertical>.btn-group+.btn-group{margin-top:-1px;margin-left:0}.btn-group-vertical>.btn:not(:first-child):not(:last-child){border-radius:0}.btn-group-vertical>.btn:first-child:not(:last-child){border-bottom-right-radius:0;border-bottom-left-radius:0}.btn-group-vertical>.btn:last-child:not(:first-child){border-top-left-radius:0;border-top-right-radius:0}.btn-group-vertical>.btn-group:not(:first-child):not(:last-child)>.btn{border-radius:0}.btn-group-vertical>.btn-group:first-child:not(:last-child)>.btn:last-child,.btn-group-vertical>.btn-group:first-child:not(:last-child)>.dropdown-toggle{border-bottom-right-radius:0;border-bottom-left-radius:0}.btn-group-vertical>.btn-group:last-child:not(:first-child)>.btn:first-child{border-top-left-radius:0;border-top-right-radius:0}[data-toggle=buttons]>.btn input[type=checkbox],[data-toggle=buttons]>.btn input[type=radio],[data-toggle=buttons]>.btn-group>.btn input[type=checkbox],[data-toggle=buttons]>.btn-group>.btn input[type=radio]{position:absolute;clip:rect(0,0,0,0);pointer-events:none}.input-group{position:relative;display:-ms-flexbox;display:flex;width:100%}.input-group .form-control{position:relative;z-index:2;-ms-flex:1 1 auto;flex:1 1 auto;width:1%;margin-bottom:0}.input-group .form-control:active,.input-group .form-control:focus,.input-group .form-control:hover{z-index:3}.input-group .form-control,.input-group-addon,.input-group-btn{display:-ms-flexbox;display:flex;-ms-flex-align:center;align-items:center}.input-group .form-control:not(:first-child):not(:last-child),.input-group-addon:not(:first-child):not(:last-child),.input-group-btn:not(:first-child):not(:last-child){border-radius:0}.input-group-addon,.input-group-btn{white-space:nowrap;vertical-align:middle}.input-group-addon{padding:.5rem .75rem;margin-bottom:0;font-size:1rem;font-weight:400;line-height:1.25;color:#495057;text-align:center;background-color:#e9ecef;border:1px solid rgba(0,0,0,.15);border-radius:.25rem}.input-group-addon.form-control-sm,.input-group-sm>.input-group-addon,.input-group-sm>.input-group-btn>.input-group-addon.btn{padding:.25rem .5rem;font-size:.875rem;border-radius:.2rem}.input-group-addon.form-control-lg,.input-group-lg>.input-group-addon,.input-group-lg>.input-group-btn>.input-group-addon.btn{padding:.5rem 1rem;font-size:1.25rem;border-radius:.3rem}.input-group-addon input[type=checkbox],.input-group-addon input[type=radio]{margin-top:0}.input-group .form-control:not(:last-child),.input-group-addon:not(:last-child),.input-group-btn:not(:first-child)>.btn-group:not(:last-child)>.btn,.input-group-btn:not(:first-child)>.btn:not(:last-child):not(.dropdown-toggle),.input-group-btn:not(:last-child)>.btn,.input-group-btn:not(:last-child)>.btn-group>.btn,.input-group-btn:not(:last-child)>.dropdown-toggle{border-top-right-radius:0;border-bottom-right-radius:0}.input-group-addon:not(:last-child){border-right:0}.input-group .form-control:not(:first-child),.input-group-addon:not(:first-child),.input-group-btn:not(:first-child)>.btn,.input-group-btn:not(:first-child)>.btn-group>.btn,.input-group-btn:not(:first-child)>.dropdown-toggle,.input-group-btn:not(:last-child)>.btn-group:not(:first-child)>.btn,.input-group-btn:not(:last-child)>.btn:not(:first-child){border-top-left-radius:0;border-bottom-left-radius:0}.form-control+.input-group-addon:not(:first-child){border-left:0}.input-group-btn{position:relative;font-size:0;white-space:nowrap}.input-group-btn>.btn{position:relative}.input-group-btn>.btn+.btn{margin-left:-1px}.input-group-btn>.btn:active,.input-group-btn>.btn:focus,.input-group-btn>.btn:hover{z-index:3}.input-group-btn:not(:last-child)>.btn,.input-group-btn:not(:last-child)>.btn-group{margin-right:-1px}.input-group-btn:not(:first-child)>.btn,.input-group-btn:not(:first-child)>.btn-group{z-index:2;margin-left:-1px}.input-group-btn:not(:first-child)>.btn-group:active,.input-group-btn:not(:first-child)>.btn-group:focus,.input-group-btn:not(:first-child)>.btn-group:hover,.input-group-btn:not(:first-child)>.btn:active,.input-group-btn:not(:first-child)>.btn:focus,.input-group-btn:not(:first-child)>.btn:hover{z-index:3}.custom-control{position:relative;display:-ms-inline-flexbox;display:inline-flex;min-height:1.5rem;padding-left:1.5rem;margin-right:1rem}.custom-control-input{position:absolute;z-index:-1;opacity:0}.custom-control-input:checked~.custom-control-indicator{color:#fff;background-color:#007bff}.custom-control-input:focus~.custom-control-indicator{box-shadow:0 0 0 1px #fff,0 0 0 3px #007bff}.custom-control-input:active~.custom-control-indicator{color:#fff;background-color:#b3d7ff}.custom-control-input:disabled~.custom-control-indicator{background-color:#e9ecef}.custom-control-input:disabled~.custom-control-description{color:#868e96}.custom-control-indicator{position:absolute;top:.25rem;left:0;display:block;width:1rem;height:1rem;pointer-events:none;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;background-color:#ddd;background-repeat:no-repeat;background-position:center center;background-size:50% 50%}.custom-checkbox .custom-control-indicator{border-radius:.25rem}.custom-checkbox .custom-control-input:checked~.custom-control-indicator{background-image:url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 8 8'%3E%3Cpath fill='%23fff' d='M6.564.75l-3.59 3.612-1.538-1.55L0 4.26 2.974 7.25 8 2.193z'/%3E%3C/svg%3E")}.custom-checkbox .custom-control-input:indeterminate~.custom-control-indicator{background-color:#007bff;background-image:url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 4 4'%3E%3Cpath stroke='%23fff' d='M0 2h4'/%3E%3C/svg%3E")}.custom-radio .custom-control-indicator{border-radius:50%}.custom-radio .custom-control-input:checked~.custom-control-indicator{background-image:url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='-4 -4 8 8'%3E%3Ccircle r='3' fill='%23fff'/%3E%3C/svg%3E")}.custom-controls-stacked{display:-ms-flexbox;display:flex;-ms-flex-direction:column;flex-direction:column}.custom-controls-stacked .custom-control{margin-bottom:.25rem}.custom-controls-stacked .custom-control+.custom-control{margin-left:0}.custom-select{display:inline-block;max-width:100%;height:calc(2.25rem + 2px);padding:.375rem 1.75rem .375rem .75rem;line-height:1.25;color:#495057;vertical-align:middle;background:#fff url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 4 5'%3E%3Cpath fill='%23333' d='M2 0L0 2h4zm0 5L0 3h4z'/%3E%3C/svg%3E") no-repeat right .75rem center;background-size:8px 10px;border:1px solid rgba(0,0,0,.15);border-radius:.25rem;-webkit-appearance:none;-moz-appearance:none;appearance:none}.custom-select:focus{border-color:#80bdff;outline:0}.custom-select:focus::-ms-value{color:#495057;background-color:#fff}.custom-select:disabled{color:#868e96;background-color:#e9ecef}.custom-select::-ms-expand{opacity:0}.custom-select-sm{height:calc(1.8125rem + 2px);padding-top:.375rem;padding-bottom:.375rem;font-size:75%}.custom-file{position:relative;display:inline-block;max-width:100%;height:2.5rem;margin-bottom:0}.custom-file-input{min-width:14rem;max-width:100%;height:2.5rem;margin:0;opacity:0}.custom-file-control{position:absolute;top:0;right:0;left:0;z-index:5;height:2.5rem;padding:.5rem 1rem;line-height:1.5;color:#495057;pointer-events:none;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;background-color:#fff;border:1px solid rgba(0,0,0,.15);border-radius:.25rem}.custom-file-control:lang(en):empty::after{content:"Choose file..."}.custom-file-control::before{position:absolute;top:-1px;right:-1px;bottom:-1px;z-index:6;display:block;height:2.5rem;padding:.5rem 1rem;line-height:1.5;color:#495057;background-color:#e9ecef;border:1px solid rgba(0,0,0,.15);border-radius:0 .25rem .25rem 0}.custom-file-control:lang(en)::before{content:"Browse"}.nav{display:-ms-flexbox;display:flex;-ms-flex-wrap:wrap;flex-wrap:wrap;padding-left:0;margin-bottom:0;list-style:none}.nav-link{display:block;padding:.5rem 1rem}.nav-link:focus,.nav-link:hover{text-decoration:none}.nav-link.disabled{color:#868e96}.nav-tabs{border-bottom:1px solid #ddd}.nav-tabs .nav-item{margin-bottom:-1px}.nav-tabs .nav-link{border:1px solid transparent;border-top-left-radius:.25rem;border-top-right-radius:.25rem}.nav-tabs .nav-link:focus,.nav-tabs .nav-link:hover{border-color:#e9ecef #e9ecef #ddd}.nav-tabs .nav-link.disabled{color:#868e96;background-color:transparent;border-color:transparent}.nav-tabs .nav-item.show .nav-link,.nav-tabs .nav-link.active{color:#495057;background-color:#fff;border-color:#ddd #ddd #fff}.nav-tabs .dropdown-menu{margin-top:-1px;border-top-left-radius:0;border-top-right-radius:0}.nav-pills .nav-link{border-radius:.25rem}.nav-pills .nav-link.active,.show>.nav-pills .nav-link{color:#fff;background-color:#007bff}.nav-fill .nav-item{-ms-flex:1 1 auto;flex:1 1 auto;text-align:center}.nav-justified .nav-item{-ms-flex-preferred-size:0;flex-basis:0;-ms-flex-positive:1;flex-grow:1;text-align:center}.tab-content>.tab-pane{display:none}.tab-content>.active{display:block}.navbar{position:relative;display:-ms-flexbox;display:flex;-ms-flex-wrap:wrap;flex-wrap:wrap;-ms-flex-align:center;align-items:center;-ms-flex-pack:justify;justify-content:space-between;padding:.5rem 1rem}.navbar>.container,.navbar>.container-fluid{display:-ms-flexbox;display:flex;-ms-flex-wrap:wrap;flex-wrap:wrap;-ms-flex-align:center;align-items:center;-ms-flex-pack:justify;justify-content:space-between}.navbar-brand{display:inline-block;padding-top:.3125rem;padding-bottom:.3125rem;margin-right:1rem;font-size:1.25rem;line-height:inherit;white-space:nowrap}.navbar-brand:focus,.navbar-brand:hover{text-decoration:none}.navbar-nav{display:-ms-flexbox;display:flex;-ms-flex-direction:column;flex-direction:column;padding-left:0;margin-bottom:0;list-style:none}.navbar-nav .nav-link{padding-right:0;padding-left:0}.navbar-nav .dropdown-menu{position:static;float:none}.navbar-text{display:inline-block;padding-top:.5rem;padding-bottom:.5rem}.navbar-collapse{-ms-flex-preferred-size:100%;flex-basis:100%;-ms-flex-align:center;align-items:center}.navbar-toggler{padding:.25rem .75rem;font-size:1.25rem;line-height:1;background:0 0;border:1px solid transparent;border-radius:.25rem}.navbar-toggler:focus,.navbar-toggler:hover{text-decoration:none}.navbar-toggler-icon{display:inline-block;width:1.5em;height:1.5em;vertical-align:middle;content:"";background:no-repeat center center;background-size:100% 100%}@media (max-width:575px){.navbar-expand-sm>.container,.navbar-expand-sm>.container-fluid{padding-right:0;padding-left:0}}@media (min-width:576px){.navbar-expand-sm{-ms-flex-direction:row;flex-direction:row;-ms-flex-wrap:nowrap;flex-wrap:nowrap;-ms-flex-pack:start;justify-content:flex-start}.navbar-expand-sm .navbar-nav{-ms-flex-direction:row;flex-direction:row}.navbar-expand-sm .navbar-nav .dropdown-menu{position:absolute}.navbar-expand-sm .navbar-nav .dropdown-menu-right{right:0;left:auto}.navbar-expand-sm .navbar-nav .nav-link{padding-right:.5rem;padding-left:.5rem}.navbar-expand-sm>.container,.navbar-expand-sm>.container-fluid{-ms-flex-wrap:nowrap;flex-wrap:nowrap}.navbar-expand-sm .navbar-collapse{display:-ms-flexbox!important;display:flex!important}.navbar-expand-sm .navbar-toggler{display:none}}@media (max-width:767px){.navbar-expand-md>.container,.navbar-expand-md>.container-fluid{padding-right:0;padding-left:0}}@media (min-width:768px){.navbar-expand-md{-ms-flex-direction:row;flex-direction:row;-ms-flex-wrap:nowrap;flex-wrap:nowrap;-ms-flex-pack:start;justify-content:flex-start}.navbar-expand-md .navbar-nav{-ms-flex-direction:row;flex-direction:row}.navbar-expand-md .navbar-nav .dropdown-menu{position:absolute}.navbar-expand-md .navbar-nav .dropdown-menu-right{right:0;left:auto}.navbar-expand-md .navbar-nav .nav-link{padding-right:.5rem;padding-left:.5rem}.navbar-expand-md>.container,.navbar-expand-md>.container-fluid{-ms-flex-wrap:nowrap;flex-wrap:nowrap}.navbar-expand-md .navbar-collapse{display:-ms-flexbox!important;display:flex!important}.navbar-expand-md .navbar-toggler{display:none}}@media (max-width:991px){.navbar-expand-lg>.container,.navbar-expand-lg>.container-fluid{padding-right:0;padding-left:0}}@media (min-width:992px){.navbar-expand-lg{-ms-flex-direction:row;flex-direction:row;-ms-flex-wrap:nowrap;flex-wrap:nowrap;-ms-flex-pack:start;justify-content:flex-start}.navbar-expand-lg .navbar-nav{-ms-flex-direction:row;flex-direction:row}.navbar-expand-lg .navbar-nav .dropdown-menu{position:absolute}.navbar-expand-lg .navbar-nav .dropdown-menu-right{right:0;left:auto}.navbar-expand-lg .navbar-nav .nav-link{padding-right:.5rem;padding-left:.5rem}.navbar-expand-lg>.container,.navbar-expand-lg>.container-fluid{-ms-flex-wrap:nowrap;flex-wrap:nowrap}.navbar-expand-lg .navbar-collapse{display:-ms-flexbox!important;display:flex!important}.navbar-expand-lg .navbar-toggler{display:none}}@media (max-width:1199px){.navbar-expand-xl>.container,.navbar-expand-xl>.container-fluid{padding-right:0;padding-left:0}}@media (min-width:1200px){.navbar-expand-xl{-ms-flex-direction:row;flex-direction:row;-ms-flex-wrap:nowrap;flex-wrap:nowrap;-ms-flex-pack:start;justify-content:flex-start}.navbar-expand-xl .navbar-nav{-ms-flex-direction:row;flex-direction:row}.navbar-expand-xl .navbar-nav .dropdown-menu{position:absolute}.navbar-expand-xl .navbar-nav .dropdown-menu-right{right:0;left:auto}.navbar-expand-xl .navbar-nav .nav-link{padding-right:.5rem;padding-left:.5rem}.navbar-expand-xl>.container,.navbar-expand-xl>.container-fluid{-ms-flex-wrap:nowrap;flex-wrap:nowrap}.navbar-expand-xl .navbar-collapse{display:-ms-flexbox!important;display:flex!important}.navbar-expand-xl .navbar-toggler{display:none}}.navbar-expand{-ms-flex-direction:row;flex-direction:row;-ms-flex-wrap:nowrap;flex-wrap:nowrap;-ms-flex-pack:start;justify-content:flex-start}.navbar-expand>.container,.navbar-expand>.container-fluid{padding-right:0;padding-left:0}.navbar-expand .navbar-nav{-ms-flex-direction:row;flex-direction:row}.navbar-expand .navbar-nav .dropdown-menu{position:absolute}.navbar-expand .navbar-nav .dropdown-menu-right{right:0;left:auto}.navbar-expand .navbar-nav .nav-link{padding-right:.5rem;padding-left:.5rem}.navbar-expand>.container,.navbar-expand>.container-fluid{-ms-flex-wrap:nowrap;flex-wrap:nowrap}.navbar-expand .navbar-collapse{display:-ms-flexbox!important;display:flex!important}.navbar-expand .navbar-toggler{display:none}.navbar-light .navbar-brand{color:rgba(0,0,0,.9)}.navbar-light .navbar-brand:focus,.navbar-light .navbar-brand:hover{color:rgba(0,0,0,.9)}.navbar-light .navbar-nav .nav-link{color:rgba(0,0,0,.5)}.navbar-light .navbar-nav .nav-link:focus,.navbar-light .navbar-nav .nav-link:hover{color:rgba(0,0,0,.7)}.navbar-light .navbar-nav .nav-link.disabled{color:rgba(0,0,0,.3)}.navbar-light .navbar-nav .active>.nav-link,.navbar-light .navbar-nav .nav-link.active,.navbar-light .navbar-nav .nav-link.show,.navbar-light .navbar-nav .show>.nav-link{color:rgba(0,0,0,.9)}.navbar-light .navbar-toggler{color:rgba(0,0,0,.5);border-color:rgba(0,0,0,.1)}.navbar-light .navbar-toggler-icon{background-image:url("data:image/svg+xml;charset=utf8,%3Csvg viewBox='0 0 30 30' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath stroke='rgba(0, 0, 0, 0.5)' stroke-width='2' stroke-linecap='round' stroke-miterlimit='10' d='M4 7h22M4 15h22M4 23h22'/%3E%3C/svg%3E")}.navbar-light .navbar-text{color:rgba(0,0,0,.5)}.navbar-dark .navbar-brand{color:#fff}.navbar-dark .navbar-brand:focus,.navbar-dark .navbar-brand:hover{color:#fff}.navbar-dark .navbar-nav .nav-link{color:rgba(255,255,255,.5)}.navbar-dark .navbar-nav .nav-link:focus,.navbar-dark .navbar-nav .nav-link:hover{color:rgba(255,255,255,.75)}.navbar-dark .navbar-nav .nav-link.disabled{color:rgba(255,255,255,.25)}.navbar-dark .navbar-nav .active>.nav-link,.navbar-dark .navbar-nav .nav-link.active,.navbar-dark .navbar-nav .nav-link.show,.navbar-dark .navbar-nav .show>.nav-link{color:#fff}.navbar-dark .navbar-toggler{color:rgba(255,255,255,.5);border-color:rgba(255,255,255,.1)}.navbar-dark .navbar-toggler-icon{background-image:url("data:image/svg+xml;charset=utf8,%3Csvg viewBox='0 0 30 30' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath stroke='rgba(255, 255, 255, 0.5)' stroke-width='2' stroke-linecap='round' stroke-miterlimit='10' d='M4 7h22M4 15h22M4 23h22'/%3E%3C/svg%3E")}.navbar-dark .navbar-text{color:rgba(255,255,255,.5)}.card{position:relative;display:-ms-flexbox;display:flex;-ms-flex-direction:column;flex-direction:column;min-width:0;word-wrap:break-word;background-color:#fff;background-clip:border-box;border:1px solid rgba(0,0,0,.125);border-radius:.25rem}.card-body{-ms-flex:1 1 auto;flex:1 1 auto;padding:1.25rem}.card-title{margin-bottom:.75rem}.card-subtitle{margin-top:-.375rem;margin-bottom:0}.card-text:last-child{margin-bottom:0}.card-link:hover{text-decoration:none}.card-link+.card-link{margin-left:1.25rem}.card>.list-group:first-child .list-group-item:first-child{border-top-left-radius:.25rem;border-top-right-radius:.25rem}.card>.list-group:last-child .list-group-item:last-child{border-bottom-right-radius:.25rem;border-bottom-left-radius:.25rem}.card-header{padding:.75rem 1.25rem;margin-bottom:0;background-color:rgba(0,0,0,.03);border-bottom:1px solid rgba(0,0,0,.125)}.card-header:first-child{border-radius:calc(.25rem - 1px) calc(.25rem - 1px) 0 0}.card-footer{padding:.75rem 1.25rem;background-color:rgba(0,0,0,.03);border-top:1px solid rgba(0,0,0,.125)}.card-footer:last-child{border-radius:0 0 calc(.25rem - 1px) calc(.25rem - 1px)}.card-header-tabs{margin-right:-.625rem;margin-bottom:-.75rem;margin-left:-.625rem;border-bottom:0}.card-header-pills{margin-right:-.625rem;margin-left:-.625rem}.card-img-overlay{position:absolute;top:0;right:0;bottom:0;left:0;padding:1.25rem}.card-img{width:100%;border-radius:calc(.25rem - 1px)}.card-img-top{width:100%;border-top-left-radius:calc(.25rem - 1px);border-top-right-radius:calc(.25rem - 1px)}.card-img-bottom{width:100%;border-bottom-right-radius:calc(.25rem - 1px);border-bottom-left-radius:calc(.25rem - 1px)}@media (min-width:576px){.card-deck{display:-ms-flexbox;display:flex;-ms-flex-flow:row wrap;flex-flow:row wrap;margin-right:-15px;margin-left:-15px}.card-deck .card{display:-ms-flexbox;display:flex;-ms-flex:1 0 0%;flex:1 0 0%;-ms-flex-direction:column;flex-direction:column;margin-right:15px;margin-left:15px}}@media (min-width:576px){.card-group{display:-ms-flexbox;display:flex;-ms-flex-flow:row wrap;flex-flow:row wrap}.card-group .card{-ms-flex:1 0 0%;flex:1 0 0%}.card-group .card+.card{margin-left:0;border-left:0}.card-group .card:first-child{border-top-right-radius:0;border-bottom-right-radius:0}.card-group .card:first-child .card-img-top{border-top-right-radius:0}.card-group .card:first-child .card-img-bottom{border-bottom-right-radius:0}.card-group .card:last-child{border-top-left-radius:0;border-bottom-left-radius:0}.card-group .card:last-child .card-img-top{border-top-left-radius:0}.card-group .card:last-child .card-img-bottom{border-bottom-left-radius:0}.card-group .card:not(:first-child):not(:last-child){border-radius:0}.card-group .card:not(:first-child):not(:last-child) .card-img-bottom,.card-group .card:not(:first-child):not(:last-child) .card-img-top{border-radius:0}}.card-columns .card{margin-bottom:.75rem}@media (min-width:576px){.card-columns{-webkit-column-count:3;column-count:3;-webkit-column-gap:1.25rem;column-gap:1.25rem}.card-columns .card{display:inline-block;width:100%}}.breadcrumb{padding:.75rem 1rem;margin-bottom:1rem;list-style:none;background-color:#e9ecef;border-radius:.25rem}.breadcrumb::after{display:block;clear:both;content:""}.breadcrumb-item{float:left}.breadcrumb-item+.breadcrumb-item::before{display:inline-block;padding-right:.5rem;padding-left:.5rem;color:#868e96;content:"/"}.breadcrumb-item+.breadcrumb-item:hover::before{text-decoration:underline}.breadcrumb-item+.breadcrumb-item:hover::before{text-decoration:none}.breadcrumb-item.active{color:#868e96}.pagination{display:-ms-flexbox;display:flex;padding-left:0;list-style:none;border-radius:.25rem}.page-item:first-child .page-link{margin-left:0;border-top-left-radius:.25rem;border-bottom-left-radius:.25rem}.page-item:last-child .page-link{border-top-right-radius:.25rem;border-bottom-right-radius:.25rem}.page-item.active .page-link{z-index:2;color:#fff;background-color:#007bff;border-color:#007bff}.page-item.disabled .page-link{color:#868e96;pointer-events:none;background-color:#fff;border-color:#ddd}.page-link{position:relative;display:block;padding:.5rem .75rem;margin-left:-1px;line-height:1.25;color:#007bff;background-color:#fff;border:1px solid #ddd}.page-link:focus,.page-link:hover{color:#0056b3;text-decoration:none;background-color:#e9ecef;border-color:#ddd}.pagination-lg .page-link{padding:.75rem 1.5rem;font-size:1.25rem;line-height:1.5}.pagination-lg .page-item:first-child .page-link{border-top-left-radius:.3rem;border-bottom-left-radius:.3rem}.pagination-lg .page-item:last-child .page-link{border-top-right-radius:.3rem;border-bottom-right-radius:.3rem}.pagination-sm .page-link{padding:.25rem .5rem;font-size:.875rem;line-height:1.5}.pagination-sm .page-item:first-child .page-link{border-top-left-radius:.2rem;border-bottom-left-radius:.2rem}.pagination-sm .page-item:last-child .page-link{border-top-right-radius:.2rem;border-bottom-right-radius:.2rem}.badge{display:inline-block;padding:.25em .4em;font-size:75%;font-weight:700;line-height:1;color:#fff;text-align:center;white-space:nowrap;vertical-align:baseline;border-radius:.25rem}.badge:empty{display:none}.btn .badge{position:relative;top:-1px}.badge-pill{padding-right:.6em;padding-left:.6em;border-radius:10rem}.badge-primary{color:#fff;background-color:#007bff}.badge-primary[href]:focus,.badge-primary[href]:hover{color:#fff;text-decoration:none;background-color:#0062cc}.badge-secondary{color:#fff;background-color:#868e96}.badge-secondary[href]:focus,.badge-secondary[href]:hover{color:#fff;text-decoration:none;background-color:#6c757d}.badge-success{color:#fff;background-color:#28a745}.badge-success[href]:focus,.badge-success[href]:hover{color:#fff;text-decoration:none;background-color:#1e7e34}.badge-info{color:#fff;background-color:#17a2b8}.badge-info[href]:focus,.badge-info[href]:hover{color:#fff;text-decoration:none;background-color:#117a8b}.badge-warning{color:#111;background-color:#ffc107}.badge-warning[href]:focus,.badge-warning[href]:hover{color:#111;text-decoration:none;background-color:#d39e00}.badge-danger{color:#fff;background-color:#dc3545}.badge-danger[href]:focus,.badge-danger[href]:hover{color:#fff;text-decoration:none;background-color:#bd2130}.badge-light{color:#111;background-color:#f8f9fa}.badge-light[href]:focus,.badge-light[href]:hover{color:#111;text-decoration:none;background-color:#dae0e5}.badge-dark{color:#fff;background-color:#343a40}.badge-dark[href]:focus,.badge-dark[href]:hover{color:#fff;text-decoration:none;background-color:#1d2124}.jumbotron{padding:2rem 1rem;margin-bottom:2rem;background-color:#e9ecef;border-radius:.3rem}@media (min-width:576px){.jumbotron{padding:4rem 2rem}}.jumbotron-fluid{padding-right:0;padding-left:0;border-radius:0}.alert{padding:.75rem 1.25rem;margin-bottom:1rem;border:1px solid transparent;border-radius:.25rem}.alert-heading{color:inherit}.alert-link{font-weight:700}.alert-dismissible .close{position:relative;top:-.75rem;right:-1.25rem;padding:.75rem 1.25rem;color:inherit}.alert-primary{color:#004085;background-color:#cce5ff;border-color:#b8daff}.alert-primary hr{border-top-color:#9fcdff}.alert-primary .alert-link{color:#002752}.alert-secondary{color:#464a4e;background-color:#e7e8ea;border-color:#dddfe2}.alert-secondary hr{border-top-color:#cfd2d6}.alert-secondary .alert-link{color:#2e3133}.alert-success{color:#155724;background-color:#d4edda;border-color:#c3e6cb}.alert-success hr{border-top-color:#b1dfbb}.alert-success .alert-link{color:#0b2e13}.alert-info{color:#0c5460;background-color:#d1ecf1;border-color:#bee5eb}.alert-info hr{border-top-color:#abdde5}.alert-info .alert-link{color:#062c33}.alert-warning{color:#856404;background-color:#fff3cd;border-color:#ffeeba}.alert-warning hr{border-top-color:#ffe8a1}.alert-warning .alert-link{color:#533f03}.alert-danger{color:#721c24;background-color:#f8d7da;border-color:#f5c6cb}.alert-danger hr{border-top-color:#f1b0b7}.alert-danger .alert-link{color:#491217}.alert-light{color:#818182;background-color:#fefefe;border-color:#fdfdfe}.alert-light hr{border-top-color:#ececf6}.alert-light .alert-link{color:#686868}.alert-dark{color:#1b1e21;background-color:#d6d8d9;border-color:#c6c8ca}.alert-dark hr{border-top-color:#b9bbbe}.alert-dark .alert-link{color:#040505}@-webkit-keyframes progress-bar-stripes{from{background-position:1rem 0}to{background-position:0 0}}@keyframes progress-bar-stripes{from{background-position:1rem 0}to{background-position:0 0}}.progress{display:-ms-flexbox;display:flex;overflow:hidden;font-size:.75rem;line-height:1rem;text-align:center;background-color:#e9ecef;border-radius:.25rem}.progress-bar{height:1rem;line-height:1rem;color:#fff;background-color:#007bff;transition:width .6s ease}.progress-bar-striped{background-image:linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);background-size:1rem 1rem}.progress-bar-animated{-webkit-animation:progress-bar-stripes 1s linear infinite;animation:progress-bar-stripes 1s linear infinite}.media{display:-ms-flexbox;display:flex;-ms-flex-align:start;align-items:flex-start}.media-body{-ms-flex:1;flex:1}.list-group{display:-ms-flexbox;display:flex;-ms-flex-direction:column;flex-direction:column;padding-left:0;margin-bottom:0}.list-group-item-action{width:100%;color:#495057;text-align:inherit}.list-group-item-action:focus,.list-group-item-action:hover{color:#495057;text-decoration:none;background-color:#f8f9fa}.list-group-item-action:active{color:#212529;background-color:#e9ecef}.list-group-item{position:relative;display:block;padding:.75rem 1.25rem;margin-bottom:-1px;background-color:#fff;border:1px solid rgba(0,0,0,.125)}.list-group-item:first-child{border-top-left-radius:.25rem;border-top-right-radius:.25rem}.list-group-item:last-child{margin-bottom:0;border-bottom-right-radius:.25rem;border-bottom-left-radius:.25rem}.list-group-item:focus,.list-group-item:hover{text-decoration:none}.list-group-item.disabled,.list-group-item:disabled{color:#868e96;background-color:#fff}.list-group-item.active{z-index:2;color:#fff;background-color:#007bff;border-color:#007bff}.list-group-flush .list-group-item{border-right:0;border-left:0;border-radius:0}.list-group-flush:first-child .list-group-item:first-child{border-top:0}.list-group-flush:last-child .list-group-item:last-child{border-bottom:0}.list-group-item-primary{color:#004085;background-color:#b8daff}a.list-group-item-primary,button.list-group-item-primary{color:#004085}a.list-group-item-primary:focus,a.list-group-item-primary:hover,button.list-group-item-primary:focus,button.list-group-item-primary:hover{color:#004085;background-color:#9fcdff}a.list-group-item-primary.active,button.list-group-item-primary.active{color:#fff;background-color:#004085;border-color:#004085}.list-group-item-secondary{color:#464a4e;background-color:#dddfe2}a.list-group-item-secondary,button.list-group-item-secondary{color:#464a4e}a.list-group-item-secondary:focus,a.list-group-item-secondary:hover,button.list-group-item-secondary:focus,button.list-group-item-secondary:hover{color:#464a4e;background-color:#cfd2d6}a.list-group-item-secondary.active,button.list-group-item-secondary.active{color:#fff;background-color:#464a4e;border-color:#464a4e}.list-group-item-success{color:#155724;background-color:#c3e6cb}a.list-group-item-success,button.list-group-item-success{color:#155724}a.list-group-item-success:focus,a.list-group-item-success:hover,button.list-group-item-success:focus,button.list-group-item-success:hover{color:#155724;background-color:#b1dfbb}a.list-group-item-success.active,button.list-group-item-success.active{color:#fff;background-color:#155724;border-color:#155724}.list-group-item-info{color:#0c5460;background-color:#bee5eb}a.list-group-item-info,button.list-group-item-info{color:#0c5460}a.list-group-item-info:focus,a.list-group-item-info:hover,button.list-group-item-info:focus,button.list-group-item-info:hover{color:#0c5460;background-color:#abdde5}a.list-group-item-info.active,button.list-group-item-info.active{color:#fff;background-color:#0c5460;border-color:#0c5460}.list-group-item-warning{color:#856404;background-color:#ffeeba}a.list-group-item-warning,button.list-group-item-warning{color:#856404}a.list-group-item-warning:focus,a.list-group-item-warning:hover,button.list-group-item-warning:focus,button.list-group-item-warning:hover{color:#856404;background-color:#ffe8a1}a.list-group-item-warning.active,button.list-group-item-warning.active{color:#fff;background-color:#856404;border-color:#856404}.list-group-item-danger{color:#721c24;background-color:#f5c6cb}a.list-group-item-danger,button.list-group-item-danger{color:#721c24}a.list-group-item-danger:focus,a.list-group-item-danger:hover,button.list-group-item-danger:focus,button.list-group-item-danger:hover{color:#721c24;background-color:#f1b0b7}a.list-group-item-danger.active,button.list-group-item-danger.active{color:#fff;background-color:#721c24;border-color:#721c24}.list-group-item-light{color:#818182;background-color:#fdfdfe}a.list-group-item-light,button.list-group-item-light{color:#818182}a.list-group-item-light:focus,a.list-group-item-light:hover,button.list-group-item-light:focus,button.list-group-item-light:hover{color:#818182;background-color:#ececf6}a.list-group-item-light.active,button.list-group-item-light.active{color:#fff;background-color:#818182;border-color:#818182}.list-group-item-dark{color:#1b1e21;background-color:#c6c8ca}a.list-group-item-dark,button.list-group-item-dark{color:#1b1e21}a.list-group-item-dark:focus,a.list-group-item-dark:hover,button.list-group-item-dark:focus,button.list-group-item-dark:hover{color:#1b1e21;background-color:#b9bbbe}a.list-group-item-dark.active,button.list-group-item-dark.active{color:#fff;background-color:#1b1e21;border-color:#1b1e21}.close{float:right;font-size:1.5rem;font-weight:700;line-height:1;color:#000;text-shadow:0 1px 0 #fff;opacity:.5}.close:focus,.close:hover{color:#000;text-decoration:none;opacity:.75}button.close{padding:0;background:0 0;border:0;-webkit-appearance:none}.modal-open{overflow:hidden}.modal{position:fixed;top:0;right:0;bottom:0;left:0;z-index:1050;display:none;overflow:hidden;outline:0}.modal.fade .modal-dialog{transition:-webkit-transform .3s ease-out;transition:transform .3s ease-out;transition:transform .3s ease-out,-webkit-transform .3s ease-out;-webkit-transform:translate(0,-25%);transform:translate(0,-25%)}.modal.show .modal-dialog{-webkit-transform:translate(0,0);transform:translate(0,0)}.modal-open .modal{overflow-x:hidden;overflow-y:auto}.modal-dialog{position:relative;width:auto;margin:10px}.modal-content{position:relative;display:-ms-flexbox;display:flex;-ms-flex-direction:column;flex-direction:column;background-color:#fff;background-clip:padding-box;border:1px solid rgba(0,0,0,.2);border-radius:.3rem;outline:0}.modal-backdrop{position:fixed;top:0;right:0;bottom:0;left:0;z-index:1040;background-color:#000}.modal-backdrop.fade{opacity:0}.modal-backdrop.show{opacity:.5}.modal-header{display:-ms-flexbox;display:flex;-ms-flex-align:center;align-items:center;-ms-flex-pack:justify;justify-content:space-between;padding:15px;border-bottom:1px solid #e9ecef}.modal-title{margin-bottom:0;line-height:1.5}.modal-body{position:relative;-ms-flex:1 1 auto;flex:1 1 auto;padding:15px}.modal-footer{display:-ms-flexbox;display:flex;-ms-flex-align:center;align-items:center;-ms-flex-pack:end;justify-content:flex-end;padding:15px;border-top:1px solid #e9ecef}.modal-footer>:not(:first-child){margin-left:.25rem}.modal-footer>:not(:last-child){margin-right:.25rem}.modal-scrollbar-measure{position:absolute;top:-9999px;width:50px;height:50px;overflow:scroll}@media (min-width:576px){.modal-dialog{max-width:500px;margin:30px auto}.modal-sm{max-width:300px}}@media (min-width:992px){.modal-lg{max-width:800px}}.tooltip{position:absolute;z-index:1070;display:block;margin:0;font-family:-apple-system,BlinkMacSystemFont,"Segoe UI",Roboto,"Helvetica Neue",Arial,sans-serif;font-style:normal;font-weight:400;line-height:1.5;text-align:left;text-align:start;text-decoration:none;text-shadow:none;text-transform:none;letter-spacing:normal;word-break:normal;word-spacing:normal;white-space:normal;line-break:auto;font-size:.875rem;word-wrap:break-word;opacity:0}.tooltip.show{opacity:.9}.tooltip .arrow{position:absolute;display:block;width:5px;height:5px}.tooltip.bs-tooltip-auto[x-placement^=top],.tooltip.bs-tooltip-top{padding:5px 0}.tooltip.bs-tooltip-auto[x-placement^=top] .arrow,.tooltip.bs-tooltip-top .arrow{bottom:0}.tooltip.bs-tooltip-auto[x-placement^=top] .arrow::before,.tooltip.bs-tooltip-top .arrow::before{margin-left:-3px;content:"";border-width:5px 5px 0;border-top-color:#000}.tooltip.bs-tooltip-auto[x-placement^=right],.tooltip.bs-tooltip-right{padding:0 5px}.tooltip.bs-tooltip-auto[x-placement^=right] .arrow,.tooltip.bs-tooltip-right .arrow{left:0}.tooltip.bs-tooltip-auto[x-placement^=right] .arrow::before,.tooltip.bs-tooltip-right .arrow::before{margin-top:-3px;content:"";border-width:5px 5px 5px 0;border-right-color:#000}.tooltip.bs-tooltip-auto[x-placement^=bottom],.tooltip.bs-tooltip-bottom{padding:5px 0}.tooltip.bs-tooltip-auto[x-placement^=bottom] .arrow,.tooltip.bs-tooltip-bottom .arrow{top:0}.tooltip.bs-tooltip-auto[x-placement^=bottom] .arrow::before,.tooltip.bs-tooltip-bottom .arrow::before{margin-left:-3px;content:"";border-width:0 5px 5px;border-bottom-color:#000}.tooltip.bs-tooltip-auto[x-placement^=left],.tooltip.bs-tooltip-left{padding:0 5px}.tooltip.bs-tooltip-auto[x-placement^=left] .arrow,.tooltip.bs-tooltip-left .arrow{right:0}.tooltip.bs-tooltip-auto[x-placement^=left] .arrow::before,.tooltip.bs-tooltip-left .arrow::before{right:0;margin-top:-3px;content:"";border-width:5px 0 5px 5px;border-left-color:#000}.tooltip .arrow::before{position:absolute;border-color:transparent;border-style:solid}.tooltip-inner{max-width:200px;padding:3px 8px;color:#fff;text-align:center;background-color:#000;border-radius:.25rem}.popover{position:absolute;top:0;left:0;z-index:1060;display:block;max-width:276px;padding:1px;font-family:-apple-system,BlinkMacSystemFont,"Segoe UI",Roboto,"Helvetica Neue",Arial,sans-serif;font-style:normal;font-weight:400;line-height:1.5;text-align:left;text-align:start;text-decoration:none;text-shadow:none;text-transform:none;letter-spacing:normal;word-break:normal;word-spacing:normal;white-space:normal;line-break:auto;font-size:.875rem;word-wrap:break-word;background-color:#fff;background-clip:padding-box;border:1px solid rgba(0,0,0,.2);border-radius:.3rem}.popover .arrow{position:absolute;display:block;width:10px;height:5px}.popover .arrow::after,.popover .arrow::before{position:absolute;display:block;border-color:transparent;border-style:solid}.popover .arrow::before{content:"";border-width:11px}.popover .arrow::after{content:"";border-width:11px}.popover.bs-popover-auto[x-placement^=top],.popover.bs-popover-top{margin-bottom:10px}.popover.bs-popover-auto[x-placement^=top] .arrow,.popover.bs-popover-top .arrow{bottom:0}.popover.bs-popover-auto[x-placement^=top] .arrow::after,.popover.bs-popover-auto[x-placement^=top] .arrow::before,.popover.bs-popover-top .arrow::after,.popover.bs-popover-top .arrow::before{border-bottom-width:0}.popover.bs-popover-auto[x-placement^=top] .arrow::before,.popover.bs-popover-top .arrow::before{bottom:-11px;margin-left:-6px;border-top-color:rgba(0,0,0,.25)}.popover.bs-popover-auto[x-placement^=top] .arrow::after,.popover.bs-popover-top .arrow::after{bottom:-10px;margin-left:-6px;border-top-color:#fff}.popover.bs-popover-auto[x-placement^=right],.popover.bs-popover-right{margin-left:10px}.popover.bs-popover-auto[x-placement^=right] .arrow,.popover.bs-popover-right .arrow{left:0}.popover.bs-popover-auto[x-placement^=right] .arrow::after,.popover.bs-popover-auto[x-placement^=right] .arrow::before,.popover.bs-popover-right .arrow::after,.popover.bs-popover-right .arrow::before{margin-top:-8px;border-left-width:0}.popover.bs-popover-auto[x-placement^=right] .arrow::before,.popover.bs-popover-right .arrow::before{left:-11px;border-right-color:rgba(0,0,0,.25)}.popover.bs-popover-auto[x-placement^=right] .arrow::after,.popover.bs-popover-right .arrow::after{left:-10px;border-right-color:#fff}.popover.bs-popover-auto[x-placement^=bottom],.popover.bs-popover-bottom{margin-top:10px}.popover.bs-popover-auto[x-placement^=bottom] .arrow,.popover.bs-popover-bottom .arrow{top:0}.popover.bs-popover-auto[x-placement^=bottom] .arrow::after,.popover.bs-popover-auto[x-placement^=bottom] .arrow::before,.popover.bs-popover-bottom .arrow::after,.popover.bs-popover-bottom .arrow::before{margin-left:-7px;border-top-width:0}.popover.bs-popover-auto[x-placement^=bottom] .arrow::before,.popover.bs-popover-bottom .arrow::before{top:-11px;border-bottom-color:rgba(0,0,0,.25)}.popover.bs-popover-auto[x-placement^=bottom] .arrow::after,.popover.bs-popover-bottom .arrow::after{top:-10px;border-bottom-color:#fff}.popover.bs-popover-auto[x-placement^=bottom] .popover-header::before,.popover.bs-popover-bottom .popover-header::before{position:absolute;top:0;left:50%;display:block;width:20px;margin-left:-10px;content:"";border-bottom:1px solid #f7f7f7}.popover.bs-popover-auto[x-placement^=left],.popover.bs-popover-left{margin-right:10px}.popover.bs-popover-auto[x-placement^=left] .arrow,.popover.bs-popover-left .arrow{right:0}.popover.bs-popover-auto[x-placement^=left] .arrow::after,.popover.bs-popover-auto[x-placement^=left] .arrow::before,.popover.bs-popover-left .arrow::after,.popover.bs-popover-left .arrow::before{margin-top:-8px;border-right-width:0}.popover.bs-popover-auto[x-placement^=left] .arrow::before,.popover.bs-popover-left .arrow::before{right:-11px;border-left-color:rgba(0,0,0,.25)}.popover.bs-popover-auto[x-placement^=left] .arrow::after,.popover.bs-popover-left .arrow::after{right:-10px;border-left-color:#fff}.popover-header{padding:8px 14px;margin-bottom:0;font-size:1rem;color:inherit;background-color:#f7f7f7;border-bottom:1px solid #ebebeb;border-top-left-radius:calc(.3rem - 1px);border-top-right-radius:calc(.3rem - 1px)}.popover-header:empty{display:none}.popover-body{padding:9px 14px;color:#212529}.carousel{position:relative}.carousel-inner{position:relative;width:100%;overflow:hidden}.carousel-item{position:relative;display:none;-ms-flex-align:center;align-items:center;width:100%;transition:-webkit-transform .6s ease;transition:transform .6s ease;transition:transform .6s ease,-webkit-transform .6s ease;-webkit-backface-visibility:hidden;backface-visibility:hidden;-webkit-perspective:1000px;perspective:1000px}.carousel-item-next,.carousel-item-prev,.carousel-item.active{display:block}.carousel-item-next,.carousel-item-prev{position:absolute;top:0}.carousel-item-next.carousel-item-left,.carousel-item-prev.carousel-item-right{-webkit-transform:translateX(0);transform:translateX(0)}@supports ((-webkit-transform-style:preserve-3d) or (transform-style:preserve-3d)){.carousel-item-next.carousel-item-left,.carousel-item-prev.carousel-item-right{-webkit-transform:translate3d(0,0,0);transform:translate3d(0,0,0)}}.active.carousel-item-right,.carousel-item-next{-webkit-transform:translateX(100%);transform:translateX(100%)}@supports ((-webkit-transform-style:preserve-3d) or (transform-style:preserve-3d)){.active.carousel-item-right,.carousel-item-next{-webkit-transform:translate3d(100%,0,0);transform:translate3d(100%,0,0)}}.active.carousel-item-left,.carousel-item-prev{-webkit-transform:translateX(-100%);transform:translateX(-100%)}@supports ((-webkit-transform-style:preserve-3d) or (transform-style:preserve-3d)){.active.carousel-item-left,.carousel-item-prev{-webkit-transform:translate3d(-100%,0,0);transform:translate3d(-100%,0,0)}}.carousel-control-next,.carousel-control-prev{position:absolute;top:0;bottom:0;display:-ms-flexbox;display:flex;-ms-flex-align:center;align-items:center;-ms-flex-pack:center;justify-content:center;width:15%;color:#fff;text-align:center;opacity:.5}.carousel-control-next:focus,.carousel-control-next:hover,.carousel-control-prev:focus,.carousel-control-prev:hover{color:#fff;text-decoration:none;outline:0;opacity:.9}.carousel-control-prev{left:0}.carousel-control-next{right:0}.carousel-control-next-icon,.carousel-control-prev-icon{display:inline-block;width:20px;height:20px;background:transparent no-repeat center center;background-size:100% 100%}.carousel-control-prev-icon{background-image:url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' fill='%23fff' viewBox='0 0 8 8'%3E%3Cpath d='M4 0l-4 4 4 4 1.5-1.5-2.5-2.5 2.5-2.5-1.5-1.5z'/%3E%3C/svg%3E")}.carousel-control-next-icon{background-image:url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' fill='%23fff' viewBox='0 0 8 8'%3E%3Cpath d='M1.5 0l-1.5 1.5 2.5 2.5-2.5 2.5 1.5 1.5 4-4-4-4z'/%3E%3C/svg%3E")}.carousel-indicators{position:absolute;right:0;bottom:10px;left:0;z-index:15;display:-ms-flexbox;display:flex;-ms-flex-pack:center;justify-content:center;padding-left:0;margin-right:15%;margin-left:15%;list-style:none}.carousel-indicators li{position:relative;-ms-flex:0 1 auto;flex:0 1 auto;width:30px;height:3px;margin-right:3px;margin-left:3px;text-indent:-999px;background-color:rgba(255,255,255,.5)}.carousel-indicators li::before{position:absolute;top:-10px;left:0;display:inline-block;width:100%;height:10px;content:""}.carousel-indicators li::after{position:absolute;bottom:-10px;left:0;display:inline-block;width:100%;height:10px;content:""}.carousel-indicators .active{background-color:#fff}.carousel-caption{position:absolute;right:15%;bottom:20px;left:15%;z-index:10;padding-top:20px;padding-bottom:20px;color:#fff;text-align:center}.align-baseline{vertical-align:baseline!important}.align-top{vertical-align:top!important}.align-middle{vertical-align:middle!important}.align-bottom{vertical-align:bottom!important}.align-text-bottom{vertical-align:text-bottom!important}.align-text-top{vertical-align:text-top!important}.bg-primary{background-color:#007bff!important}a.bg-primary:focus,a.bg-primary:hover{background-color:#0062cc!important}.bg-secondary{background-color:#868e96!important}a.bg-secondary:focus,a.bg-secondary:hover{background-color:#6c757d!important}.bg-success{background-color:#28a745!important}a.bg-success:focus,a.bg-success:hover{background-color:#1e7e34!important}.bg-info{background-color:#17a2b8!important}a.bg-info:focus,a.bg-info:hover{background-color:#117a8b!important}.bg-warning{background-color:#ffc107!important}a.bg-warning:focus,a.bg-warning:hover{background-color:#d39e00!important}.bg-danger{background-color:#dc3545!important}a.bg-danger:focus,a.bg-danger:hover{background-color:#bd2130!important}.bg-light{background-color:#f8f9fa!important}a.bg-light:focus,a.bg-light:hover{background-color:#dae0e5!important}.bg-dark{background-color:#343a40!important}a.bg-dark:focus,a.bg-dark:hover{background-color:#1d2124!important}.bg-white{background-color:#fff!important}.bg-transparent{background-color:transparent!important}.border{border:1px solid #e9ecef!important}.border-0{border:0!important}.border-top-0{border-top:0!important}.border-right-0{border-right:0!important}.border-bottom-0{border-bottom:0!important}.border-left-0{border-left:0!important}.border-primary{border-color:#007bff!important}.border-secondary{border-color:#868e96!important}.border-success{border-color:#28a745!important}.border-info{border-color:#17a2b8!important}.border-warning{border-color:#ffc107!important}.border-danger{border-color:#dc3545!important}.border-light{border-color:#f8f9fa!important}.border-dark{border-color:#343a40!important}.border-white{border-color:#fff!important}.rounded{border-radius:.25rem!important}.rounded-top{border-top-left-radius:.25rem!important;border-top-right-radius:.25rem!important}.rounded-right{border-top-right-radius:.25rem!important;border-bottom-right-radius:.25rem!important}.rounded-bottom{border-bottom-right-radius:.25rem!important;border-bottom-left-radius:.25rem!important}.rounded-left{border-top-left-radius:.25rem!important;border-bottom-left-radius:.25rem!important}.rounded-circle{border-radius:50%}.rounded-0{border-radius:0}.clearfix::after{display:block;clear:both;content:""}.d-none{display:none!important}.d-inline{display:inline!important}.d-inline-block{display:inline-block!important}.d-block{display:block!important}.d-table{display:table!important}.d-table-cell{display:table-cell!important}.d-flex{display:-ms-flexbox!important;display:flex!important}.d-inline-flex{display:-ms-inline-flexbox!important;display:inline-flex!important}@media (min-width:576px){.d-sm-none{display:none!important}.d-sm-inline{display:inline!important}.d-sm-inline-block{display:inline-block!important}.d-sm-block{display:block!important}.d-sm-table{display:table!important}.d-sm-table-cell{display:table-cell!important}.d-sm-flex{display:-ms-flexbox!important;display:flex!important}.d-sm-inline-flex{display:-ms-inline-flexbox!important;display:inline-flex!important}}@media (min-width:768px){.d-md-none{display:none!important}.d-md-inline{display:inline!important}.d-md-inline-block{display:inline-block!important}.d-md-block{display:block!important}.d-md-table{display:table!important}.d-md-table-cell{display:table-cell!important}.d-md-flex{display:-ms-flexbox!important;display:flex!important}.d-md-inline-flex{display:-ms-inline-flexbox!important;display:inline-flex!important}}@media (min-width:992px){.d-lg-none{display:none!important}.d-lg-inline{display:inline!important}.d-lg-inline-block{display:inline-block!important}.d-lg-block{display:block!important}.d-lg-table{display:table!important}.d-lg-table-cell{display:table-cell!important}.d-lg-flex{display:-ms-flexbox!important;display:flex!important}.d-lg-inline-flex{display:-ms-inline-flexbox!important;display:inline-flex!important}}@media (min-width:1200px){.d-xl-none{display:none!important}.d-xl-inline{display:inline!important}.d-xl-inline-block{display:inline-block!important}.d-xl-block{display:block!important}.d-xl-table{display:table!important}.d-xl-table-cell{display:table-cell!important}.d-xl-flex{display:-ms-flexbox!important;display:flex!important}.d-xl-inline-flex{display:-ms-inline-flexbox!important;display:inline-flex!important}}.d-print-block{display:none!important}@media print{.d-print-block{display:block!important}}.d-print-inline{display:none!important}@media print{.d-print-inline{display:inline!important}}.d-print-inline-block{display:none!important}@media print{.d-print-inline-block{display:inline-block!important}}@media print{.d-print-none{display:none!important}}.embed-responsive{position:relative;display:block;width:100%;padding:0;overflow:hidden}.embed-responsive::before{display:block;content:""}.embed-responsive .embed-responsive-item,.embed-responsive embed,.embed-responsive iframe,.embed-responsive object,.embed-responsive video{position:absolute;top:0;bottom:0;left:0;width:100%;height:100%;border:0}.embed-responsive-21by9::before{padding-top:42.857143%}.embed-responsive-16by9::before{padding-top:56.25%}.embed-responsive-4by3::before{padding-top:75%}.embed-responsive-1by1::before{padding-top:100%}.flex-row{-ms-flex-direction:row!important;flex-direction:row!important}.flex-column{-ms-flex-direction:column!important;flex-direction:column!important}.flex-row-reverse{-ms-flex-direction:row-reverse!important;flex-direction:row-reverse!important}.flex-column-reverse{-ms-flex-direction:column-reverse!important;flex-direction:column-reverse!important}.flex-wrap{-ms-flex-wrap:wrap!important;flex-wrap:wrap!important}.flex-nowrap{-ms-flex-wrap:nowrap!important;flex-wrap:nowrap!important}.flex-wrap-reverse{-ms-flex-wrap:wrap-reverse!important;flex-wrap:wrap-reverse!important}.justify-content-start{-ms-flex-pack:start!important;justify-content:flex-start!important}.justify-content-end{-ms-flex-pack:end!important;justify-content:flex-end!important}.justify-content-center{-ms-flex-pack:center!important;justify-content:center!important}.justify-content-between{-ms-flex-pack:justify!important;justify-content:space-between!important}.justify-content-around{-ms-flex-pack:distribute!important;justify-content:space-around!important}.align-items-start{-ms-flex-align:start!important;align-items:flex-start!important}.align-items-end{-ms-flex-align:end!important;align-items:flex-end!important}.align-items-center{-ms-flex-align:center!important;align-items:center!important}.align-items-baseline{-ms-flex-align:baseline!important;align-items:baseline!important}.align-items-stretch{-ms-flex-align:stretch!important;align-items:stretch!important}.align-content-start{-ms-flex-line-pack:start!important;align-content:flex-start!important}.align-content-end{-ms-flex-line-pack:end!important;align-content:flex-end!important}.align-content-center{-ms-flex-line-pack:center!important;align-content:center!important}.align-content-between{-ms-flex-line-pack:justify!important;align-content:space-between!important}.align-content-around{-ms-flex-line-pack:distribute!important;align-content:space-around!important}.align-content-stretch{-ms-flex-line-pack:stretch!important;align-content:stretch!important}.align-self-auto{-ms-flex-item-align:auto!important;align-self:auto!important}.align-self-start{-ms-flex-item-align:start!important;align-self:flex-start!important}.align-self-end{-ms-flex-item-align:end!important;align-self:flex-end!important}.align-self-center{-ms-flex-item-align:center!important;align-self:center!important}.align-self-baseline{-ms-flex-item-align:baseline!important;align-self:baseline!important}.align-self-stretch{-ms-flex-item-align:stretch!important;align-self:stretch!important}@media (min-width:576px){.flex-sm-row{-ms-flex-direction:row!important;flex-direction:row!important}.flex-sm-column{-ms-flex-direction:column!important;flex-direction:column!important}.flex-sm-row-reverse{-ms-flex-direction:row-reverse!important;flex-direction:row-reverse!important}.flex-sm-column-reverse{-ms-flex-direction:column-reverse!important;flex-direction:column-reverse!important}.flex-sm-wrap{-ms-flex-wrap:wrap!important;flex-wrap:wrap!important}.flex-sm-nowrap{-ms-flex-wrap:nowrap!important;flex-wrap:nowrap!important}.flex-sm-wrap-reverse{-ms-flex-wrap:wrap-reverse!important;flex-wrap:wrap-reverse!important}.justify-content-sm-start{-ms-flex-pack:start!important;justify-content:flex-start!important}.justify-content-sm-end{-ms-flex-pack:end!important;justify-content:flex-end!important}.justify-content-sm-center{-ms-flex-pack:center!important;justify-content:center!important}.justify-content-sm-between{-ms-flex-pack:justify!important;justify-content:space-between!important}.justify-content-sm-around{-ms-flex-pack:distribute!important;justify-content:space-around!important}.align-items-sm-start{-ms-flex-align:start!important;align-items:flex-start!important}.align-items-sm-end{-ms-flex-align:end!important;align-items:flex-end!important}.align-items-sm-center{-ms-flex-align:center!important;align-items:center!important}.align-items-sm-baseline{-ms-flex-align:baseline!important;align-items:baseline!important}.align-items-sm-stretch{-ms-flex-align:stretch!important;align-items:stretch!important}.align-content-sm-start{-ms-flex-line-pack:start!important;align-content:flex-start!important}.align-content-sm-end{-ms-flex-line-pack:end!important;align-content:flex-end!important}.align-content-sm-center{-ms-flex-line-pack:center!important;align-content:center!important}.align-content-sm-between{-ms-flex-line-pack:justify!important;align-content:space-between!important}.align-content-sm-around{-ms-flex-line-pack:distribute!important;align-content:space-around!important}.align-content-sm-stretch{-ms-flex-line-pack:stretch!important;align-content:stretch!important}.align-self-sm-auto{-ms-flex-item-align:auto!important;align-self:auto!important}.align-self-sm-start{-ms-flex-item-align:start!important;align-self:flex-start!important}.align-self-sm-end{-ms-flex-item-align:end!important;align-self:flex-end!important}.align-self-sm-center{-ms-flex-item-align:center!important;align-self:center!important}.align-self-sm-baseline{-ms-flex-item-align:baseline!important;align-self:baseline!important}.align-self-sm-stretch{-ms-flex-item-align:stretch!important;align-self:stretch!important}}@media (min-width:768px){.flex-md-row{-ms-flex-direction:row!important;flex-direction:row!important}.flex-md-column{-ms-flex-direction:column!important;flex-direction:column!important}.flex-md-row-reverse{-ms-flex-direction:row-reverse!important;flex-direction:row-reverse!important}.flex-md-column-reverse{-ms-flex-direction:column-reverse!important;flex-direction:column-reverse!important}.flex-md-wrap{-ms-flex-wrap:wrap!important;flex-wrap:wrap!important}.flex-md-nowrap{-ms-flex-wrap:nowrap!important;flex-wrap:nowrap!important}.flex-md-wrap-reverse{-ms-flex-wrap:wrap-reverse!important;flex-wrap:wrap-reverse!important}.justify-content-md-start{-ms-flex-pack:start!important;justify-content:flex-start!important}.justify-content-md-end{-ms-flex-pack:end!important;justify-content:flex-end!important}.justify-content-md-center{-ms-flex-pack:center!important;justify-content:center!important}.justify-content-md-between{-ms-flex-pack:justify!important;justify-content:space-between!important}.justify-content-md-around{-ms-flex-pack:distribute!important;justify-content:space-around!important}.align-items-md-start{-ms-flex-align:start!important;align-items:flex-start!important}.align-items-md-end{-ms-flex-align:end!important;align-items:flex-end!important}.align-items-md-center{-ms-flex-align:center!important;align-items:center!important}.align-items-md-baseline{-ms-flex-align:baseline!important;align-items:baseline!important}.align-items-md-stretch{-ms-flex-align:stretch!important;align-items:stretch!important}.align-content-md-start{-ms-flex-line-pack:start!important;align-content:flex-start!important}.align-content-md-end{-ms-flex-line-pack:end!important;align-content:flex-end!important}.align-content-md-center{-ms-flex-line-pack:center!important;align-content:center!important}.align-content-md-between{-ms-flex-line-pack:justify!important;align-content:space-between!important}.align-content-md-around{-ms-flex-line-pack:distribute!important;align-content:space-around!important}.align-content-md-stretch{-ms-flex-line-pack:stretch!important;align-content:stretch!important}.align-self-md-auto{-ms-flex-item-align:auto!important;align-self:auto!important}.align-self-md-start{-ms-flex-item-align:start!important;align-self:flex-start!important}.align-self-md-end{-ms-flex-item-align:end!important;align-self:flex-end!important}.align-self-md-center{-ms-flex-item-align:center!important;align-self:center!important}.align-self-md-baseline{-ms-flex-item-align:baseline!important;align-self:baseline!important}.align-self-md-stretch{-ms-flex-item-align:stretch!important;align-self:stretch!important}}@media (min-width:992px){.flex-lg-row{-ms-flex-direction:row!important;flex-direction:row!important}.flex-lg-column{-ms-flex-direction:column!important;flex-direction:column!important}.flex-lg-row-reverse{-ms-flex-direction:row-reverse!important;flex-direction:row-reverse!important}.flex-lg-column-reverse{-ms-flex-direction:column-reverse!important;flex-direction:column-reverse!important}.flex-lg-wrap{-ms-flex-wrap:wrap!important;flex-wrap:wrap!important}.flex-lg-nowrap{-ms-flex-wrap:nowrap!important;flex-wrap:nowrap!important}.flex-lg-wrap-reverse{-ms-flex-wrap:wrap-reverse!important;flex-wrap:wrap-reverse!important}.justify-content-lg-start{-ms-flex-pack:start!important;justify-content:flex-start!important}.justify-content-lg-end{-ms-flex-pack:end!important;justify-content:flex-end!important}.justify-content-lg-center{-ms-flex-pack:center!important;justify-content:center!important}.justify-content-lg-between{-ms-flex-pack:justify!important;justify-content:space-between!important}.justify-content-lg-around{-ms-flex-pack:distribute!important;justify-content:space-around!important}.align-items-lg-start{-ms-flex-align:start!important;align-items:flex-start!important}.align-items-lg-end{-ms-flex-align:end!important;align-items:flex-end!important}.align-items-lg-center{-ms-flex-align:center!important;align-items:center!important}.align-items-lg-baseline{-ms-flex-align:baseline!important;align-items:baseline!important}.align-items-lg-stretch{-ms-flex-align:stretch!important;align-items:stretch!important}.align-content-lg-start{-ms-flex-line-pack:start!important;align-content:flex-start!important}.align-content-lg-end{-ms-flex-line-pack:end!important;align-content:flex-end!important}.align-content-lg-center{-ms-flex-line-pack:center!important;align-content:center!important}.align-content-lg-between{-ms-flex-line-pack:justify!important;align-content:space-between!important}.align-content-lg-around{-ms-flex-line-pack:distribute!important;align-content:space-around!important}.align-content-lg-stretch{-ms-flex-line-pack:stretch!important;align-content:stretch!important}.align-self-lg-auto{-ms-flex-item-align:auto!important;align-self:auto!important}.align-self-lg-start{-ms-flex-item-align:start!important;align-self:flex-start!important}.align-self-lg-end{-ms-flex-item-align:end!important;align-self:flex-end!important}.align-self-lg-center{-ms-flex-item-align:center!important;align-self:center!important}.align-self-lg-baseline{-ms-flex-item-align:baseline!important;align-self:baseline!important}.align-self-lg-stretch{-ms-flex-item-align:stretch!important;align-self:stretch!important}}@media (min-width:1200px){.flex-xl-row{-ms-flex-direction:row!important;flex-direction:row!important}.flex-xl-column{-ms-flex-direction:column!important;flex-direction:column!important}.flex-xl-row-reverse{-ms-flex-direction:row-reverse!important;flex-direction:row-reverse!important}.flex-xl-column-reverse{-ms-flex-direction:column-reverse!important;flex-direction:column-reverse!important}.flex-xl-wrap{-ms-flex-wrap:wrap!important;flex-wrap:wrap!important}.flex-xl-nowrap{-ms-flex-wrap:nowrap!important;flex-wrap:nowrap!important}.flex-xl-wrap-reverse{-ms-flex-wrap:wrap-reverse!important;flex-wrap:wrap-reverse!important}.justify-content-xl-start{-ms-flex-pack:start!important;justify-content:flex-start!important}.justify-content-xl-end{-ms-flex-pack:end!important;justify-content:flex-end!important}.justify-content-xl-center{-ms-flex-pack:center!important;justify-content:center!important}.justify-content-xl-between{-ms-flex-pack:justify!important;justify-content:space-between!important}.justify-content-xl-around{-ms-flex-pack:distribute!important;justify-content:space-around!important}.align-items-xl-start{-ms-flex-align:start!important;align-items:flex-start!important}.align-items-xl-end{-ms-flex-align:end!important;align-items:flex-end!important}.align-items-xl-center{-ms-flex-align:center!important;align-items:center!important}.align-items-xl-baseline{-ms-flex-align:baseline!important;align-items:baseline!important}.align-items-xl-stretch{-ms-flex-align:stretch!important;align-items:stretch!important}.align-content-xl-start{-ms-flex-line-pack:start!important;align-content:flex-start!important}.align-content-xl-end{-ms-flex-line-pack:end!important;align-content:flex-end!important}.align-content-xl-center{-ms-flex-line-pack:center!important;align-content:center!important}.align-content-xl-between{-ms-flex-line-pack:justify!important;align-content:space-between!important}.align-content-xl-around{-ms-flex-line-pack:distribute!important;align-content:space-around!important}.align-content-xl-stretch{-ms-flex-line-pack:stretch!important;align-content:stretch!important}.align-self-xl-auto{-ms-flex-item-align:auto!important;align-self:auto!important}.align-self-xl-start{-ms-flex-item-align:start!important;align-self:flex-start!important}.align-self-xl-end{-ms-flex-item-align:end!important;align-self:flex-end!important}.align-self-xl-center{-ms-flex-item-align:center!important;align-self:center!important}.align-self-xl-baseline{-ms-flex-item-align:baseline!important;align-self:baseline!important}.align-self-xl-stretch{-ms-flex-item-align:stretch!important;align-self:stretch!important}}.float-left{float:left!important}.float-right{float:right!important}.float-none{float:none!important}@media (min-width:576px){.float-sm-left{float:left!important}.float-sm-right{float:right!important}.float-sm-none{float:none!important}}@media (min-width:768px){.float-md-left{float:left!important}.float-md-right{float:right!important}.float-md-none{float:none!important}}@media (min-width:992px){.float-lg-left{float:left!important}.float-lg-right{float:right!important}.float-lg-none{float:none!important}}@media (min-width:1200px){.float-xl-left{float:left!important}.float-xl-right{float:right!important}.float-xl-none{float:none!important}}.fixed-top{position:fixed;top:0;right:0;left:0;z-index:1030}.fixed-bottom{position:fixed;right:0;bottom:0;left:0;z-index:1030}@supports ((position:-webkit-sticky) or (position:sticky)){.sticky-top{position:-webkit-sticky;position:sticky;top:0;z-index:1020}}.sr-only{position:absolute;width:1px;height:1px;padding:0;overflow:hidden;clip:rect(0,0,0,0);white-space:nowrap;-webkit-clip-path:inset(50%);clip-path:inset(50%);border:0}.sr-only-focusable:active,.sr-only-focusable:focus{position:static;width:auto;height:auto;overflow:visible;clip:auto;white-space:normal;-webkit-clip-path:none;clip-path:none}.w-25{width:25%!important}.w-50{width:50%!important}.w-75{width:75%!important}.w-100{width:100%!important}.h-25{height:25%!important}.h-50{height:50%!important}.h-75{height:75%!important}.h-100{height:100%!important}.mw-100{max-width:100%!important}.mh-100{max-height:100%!important}.m-0{margin:0!important}.mt-0{margin-top:0!important}.mr-0{margin-right:0!important}.mb-0{margin-bottom:0!important}.ml-0{margin-left:0!important}.mx-0{margin-right:0!important;margin-left:0!important}.my-0{margin-top:0!important;margin-bottom:0!important}.m-1{margin:.25rem!important}.mt-1{margin-top:.25rem!important}.mr-1{margin-right:.25rem!important}.mb-1{margin-bottom:.25rem!important}.ml-1{margin-left:.25rem!important}.mx-1{margin-right:.25rem!important;margin-left:.25rem!important}.my-1{margin-top:.25rem!important;margin-bottom:.25rem!important}.m-2{margin:.5rem!important}.mt-2{margin-top:.5rem!important}.mr-2{margin-right:.5rem!important}.mb-2{margin-bottom:.5rem!important}.ml-2{margin-left:.5rem!important}.mx-2{margin-right:.5rem!important;margin-left:.5rem!important}.my-2{margin-top:.5rem!important;margin-bottom:.5rem!important}.m-3{margin:1rem!important}.mt-3{margin-top:1rem!important}.mr-3{margin-right:1rem!important}.mb-3{margin-bottom:1rem!important}.ml-3{margin-left:1rem!important}.mx-3{margin-right:1rem!important;margin-left:1rem!important}.my-3{margin-top:1rem!important;margin-bottom:1rem!important}.m-4{margin:1.5rem!important}.mt-4{margin-top:1.5rem!important}.mr-4{margin-right:1.5rem!important}.mb-4{margin-bottom:1.5rem!important}.ml-4{margin-left:1.5rem!important}.mx-4{margin-right:1.5rem!important;margin-left:1.5rem!important}.my-4{margin-top:1.5rem!important;margin-bottom:1.5rem!important}.m-5{margin:3rem!important}.mt-5{margin-top:3rem!important}.mr-5{margin-right:3rem!important}.mb-5{margin-bottom:3rem!important}.ml-5{margin-left:3rem!important}.mx-5{margin-right:3rem!important;margin-left:3rem!important}.my-5{margin-top:3rem!important;margin-bottom:3rem!important}.p-0{padding:0!important}.pt-0{padding-top:0!important}.pr-0{padding-right:0!important}.pb-0{padding-bottom:0!important}.pl-0{padding-left:0!important}.px-0{padding-right:0!important;padding-left:0!important}.py-0{padding-top:0!important;padding-bottom:0!important}.p-1{padding:.25rem!important}.pt-1{padding-top:.25rem!important}.pr-1{padding-right:.25rem!important}.pb-1{padding-bottom:.25rem!important}.pl-1{padding-left:.25rem!important}.px-1{padding-right:.25rem!important;padding-left:.25rem!important}.py-1{padding-top:.25rem!important;padding-bottom:.25rem!important}.p-2{padding:.5rem!important}.pt-2{padding-top:.5rem!important}.pr-2{padding-right:.5rem!important}.pb-2{padding-bottom:.5rem!important}.pl-2{padding-left:.5rem!important}.px-2{padding-right:.5rem!important;padding-left:.5rem!important}.py-2{padding-top:.5rem!important;padding-bottom:.5rem!important}.p-3{padding:1rem!important}.pt-3{padding-top:1rem!important}.pr-3{padding-right:1rem!important}.pb-3{padding-bottom:1rem!important}.pl-3{padding-left:1rem!important}.px-3{padding-right:1rem!important;padding-left:1rem!important}.py-3{padding-top:1rem!important;padding-bottom:1rem!important}.p-4{padding:1.5rem!important}.pt-4{padding-top:1.5rem!important}.pr-4{padding-right:1.5rem!important}.pb-4{padding-bottom:1.5rem!important}.pl-4{padding-left:1.5rem!important}.px-4{padding-right:1.5rem!important;padding-left:1.5rem!important}.py-4{padding-top:1.5rem!important;padding-bottom:1.5rem!important}.p-5{padding:3rem!important}.pt-5{padding-top:3rem!important}.pr-5{padding-right:3rem!important}.pb-5{padding-bottom:3rem!important}.pl-5{padding-left:3rem!important}.px-5{padding-right:3rem!important;padding-left:3rem!important}.py-5{padding-top:3rem!important;padding-bottom:3rem!important}.m-auto{margin:auto!important}.mt-auto{margin-top:auto!important}.mr-auto{margin-right:auto!important}.mb-auto{margin-bottom:auto!important}.ml-auto{margin-left:auto!important}.mx-auto{margin-right:auto!important;margin-left:auto!important}.my-auto{margin-top:auto!important;margin-bottom:auto!important}@media (min-width:576px){.m-sm-0{margin:0!important}.mt-sm-0{margin-top:0!important}.mr-sm-0{margin-right:0!important}.mb-sm-0{margin-bottom:0!important}.ml-sm-0{margin-left:0!important}.mx-sm-0{margin-right:0!important;margin-left:0!important}.my-sm-0{margin-top:0!important;margin-bottom:0!important}.m-sm-1{margin:.25rem!important}.mt-sm-1{margin-top:.25rem!important}.mr-sm-1{margin-right:.25rem!important}.mb-sm-1{margin-bottom:.25rem!important}.ml-sm-1{margin-left:.25rem!important}.mx-sm-1{margin-right:.25rem!important;margin-left:.25rem!important}.my-sm-1{margin-top:.25rem!important;margin-bottom:.25rem!important}.m-sm-2{margin:.5rem!important}.mt-sm-2{margin-top:.5rem!important}.mr-sm-2{margin-right:.5rem!important}.mb-sm-2{margin-bottom:.5rem!important}.ml-sm-2{margin-left:.5rem!important}.mx-sm-2{margin-right:.5rem!important;margin-left:.5rem!important}.my-sm-2{margin-top:.5rem!important;margin-bottom:.5rem!important}.m-sm-3{margin:1rem!important}.mt-sm-3{margin-top:1rem!important}.mr-sm-3{margin-right:1rem!important}.mb-sm-3{margin-bottom:1rem!important}.ml-sm-3{margin-left:1rem!important}.mx-sm-3{margin-right:1rem!important;margin-left:1rem!important}.my-sm-3{margin-top:1rem!important;margin-bottom:1rem!important}.m-sm-4{margin:1.5rem!important}.mt-sm-4{margin-top:1.5rem!important}.mr-sm-4{margin-right:1.5rem!important}.mb-sm-4{margin-bottom:1.5rem!important}.ml-sm-4{margin-left:1.5rem!important}.mx-sm-4{margin-right:1.5rem!important;margin-left:1.5rem!important}.my-sm-4{margin-top:1.5rem!important;margin-bottom:1.5rem!important}.m-sm-5{margin:3rem!important}.mt-sm-5{margin-top:3rem!important}.mr-sm-5{margin-right:3rem!important}.mb-sm-5{margin-bottom:3rem!important}.ml-sm-5{margin-left:3rem!important}.mx-sm-5{margin-right:3rem!important;margin-left:3rem!important}.my-sm-5{margin-top:3rem!important;margin-bottom:3rem!important}.p-sm-0{padding:0!important}.pt-sm-0{padding-top:0!important}.pr-sm-0{padding-right:0!important}.pb-sm-0{padding-bottom:0!important}.pl-sm-0{padding-left:0!important}.px-sm-0{padding-right:0!important;padding-left:0!important}.py-sm-0{padding-top:0!important;padding-bottom:0!important}.p-sm-1{padding:.25rem!important}.pt-sm-1{padding-top:.25rem!important}.pr-sm-1{padding-right:.25rem!important}.pb-sm-1{padding-bottom:.25rem!important}.pl-sm-1{padding-left:.25rem!important}.px-sm-1{padding-right:.25rem!important;padding-left:.25rem!important}.py-sm-1{padding-top:.25rem!important;padding-bottom:.25rem!important}.p-sm-2{padding:.5rem!important}.pt-sm-2{padding-top:.5rem!important}.pr-sm-2{padding-right:.5rem!important}.pb-sm-2{padding-bottom:.5rem!important}.pl-sm-2{padding-left:.5rem!important}.px-sm-2{padding-right:.5rem!important;padding-left:.5rem!important}.py-sm-2{padding-top:.5rem!important;padding-bottom:.5rem!important}.p-sm-3{padding:1rem!important}.pt-sm-3{padding-top:1rem!important}.pr-sm-3{padding-right:1rem!important}.pb-sm-3{padding-bottom:1rem!important}.pl-sm-3{padding-left:1rem!important}.px-sm-3{padding-right:1rem!important;padding-left:1rem!important}.py-sm-3{padding-top:1rem!important;padding-bottom:1rem!important}.p-sm-4{padding:1.5rem!important}.pt-sm-4{padding-top:1.5rem!important}.pr-sm-4{padding-right:1.5rem!important}.pb-sm-4{padding-bottom:1.5rem!important}.pl-sm-4{padding-left:1.5rem!important}.px-sm-4{padding-right:1.5rem!important;padding-left:1.5rem!important}.py-sm-4{padding-top:1.5rem!important;padding-bottom:1.5rem!important}.p-sm-5{padding:3rem!important}.pt-sm-5{padding-top:3rem!important}.pr-sm-5{padding-right:3rem!important}.pb-sm-5{padding-bottom:3rem!important}.pl-sm-5{padding-left:3rem!important}.px-sm-5{padding-right:3rem!important;padding-left:3rem!important}.py-sm-5{padding-top:3rem!important;padding-bottom:3rem!important}.m-sm-auto{margin:auto!important}.mt-sm-auto{margin-top:auto!important}.mr-sm-auto{margin-right:auto!important}.mb-sm-auto{margin-bottom:auto!important}.ml-sm-auto{margin-left:auto!important}.mx-sm-auto{margin-right:auto!important;margin-left:auto!important}.my-sm-auto{margin-top:auto!important;margin-bottom:auto!important}}@media (min-width:768px){.m-md-0{margin:0!important}.mt-md-0{margin-top:0!important}.mr-md-0{margin-right:0!important}.mb-md-0{margin-bottom:0!important}.ml-md-0{margin-left:0!important}.mx-md-0{margin-right:0!important;margin-left:0!important}.my-md-0{margin-top:0!important;margin-bottom:0!important}.m-md-1{margin:.25rem!important}.mt-md-1{margin-top:.25rem!important}.mr-md-1{margin-right:.25rem!important}.mb-md-1{margin-bottom:.25rem!important}.ml-md-1{margin-left:.25rem!important}.mx-md-1{margin-right:.25rem!important;margin-left:.25rem!important}.my-md-1{margin-top:.25rem!important;margin-bottom:.25rem!important}.m-md-2{margin:.5rem!important}.mt-md-2{margin-top:.5rem!important}.mr-md-2{margin-right:.5rem!important}.mb-md-2{margin-bottom:.5rem!important}.ml-md-2{margin-left:.5rem!important}.mx-md-2{margin-right:.5rem!important;margin-left:.5rem!important}.my-md-2{margin-top:.5rem!important;margin-bottom:.5rem!important}.m-md-3{margin:1rem!important}.mt-md-3{margin-top:1rem!important}.mr-md-3{margin-right:1rem!important}.mb-md-3{margin-bottom:1rem!important}.ml-md-3{margin-left:1rem!important}.mx-md-3{margin-right:1rem!important;margin-left:1rem!important}.my-md-3{margin-top:1rem!important;margin-bottom:1rem!important}.m-md-4{margin:1.5rem!important}.mt-md-4{margin-top:1.5rem!important}.mr-md-4{margin-right:1.5rem!important}.mb-md-4{margin-bottom:1.5rem!important}.ml-md-4{margin-left:1.5rem!important}.mx-md-4{margin-right:1.5rem!important;margin-left:1.5rem!important}.my-md-4{margin-top:1.5rem!important;margin-bottom:1.5rem!important}.m-md-5{margin:3rem!important}.mt-md-5{margin-top:3rem!important}.mr-md-5{margin-right:3rem!important}.mb-md-5{margin-bottom:3rem!important}.ml-md-5{margin-left:3rem!important}.mx-md-5{margin-right:3rem!important;margin-left:3rem!important}.my-md-5{margin-top:3rem!important;margin-bottom:3rem!important}.p-md-0{padding:0!important}.pt-md-0{padding-top:0!important}.pr-md-0{padding-right:0!important}.pb-md-0{padding-bottom:0!important}.pl-md-0{padding-left:0!important}.px-md-0{padding-right:0!important;padding-left:0!important}.py-md-0{padding-top:0!important;padding-bottom:0!important}.p-md-1{padding:.25rem!important}.pt-md-1{padding-top:.25rem!important}.pr-md-1{padding-right:.25rem!important}.pb-md-1{padding-bottom:.25rem!important}.pl-md-1{padding-left:.25rem!important}.px-md-1{padding-right:.25rem!important;padding-left:.25rem!important}.py-md-1{padding-top:.25rem!important;padding-bottom:.25rem!important}.p-md-2{padding:.5rem!important}.pt-md-2{padding-top:.5rem!important}.pr-md-2{padding-right:.5rem!important}.pb-md-2{padding-bottom:.5rem!important}.pl-md-2{padding-left:.5rem!important}.px-md-2{padding-right:.5rem!important;padding-left:.5rem!important}.py-md-2{padding-top:.5rem!important;padding-bottom:.5rem!important}.p-md-3{padding:1rem!important}.pt-md-3{padding-top:1rem!important}.pr-md-3{padding-right:1rem!important}.pb-md-3{padding-bottom:1rem!important}.pl-md-3{padding-left:1rem!important}.px-md-3{padding-right:1rem!important;padding-left:1rem!important}.py-md-3{padding-top:1rem!important;padding-bottom:1rem!important}.p-md-4{padding:1.5rem!important}.pt-md-4{padding-top:1.5rem!important}.pr-md-4{padding-right:1.5rem!important}.pb-md-4{padding-bottom:1.5rem!important}.pl-md-4{padding-left:1.5rem!important}.px-md-4{padding-right:1.5rem!important;padding-left:1.5rem!important}.py-md-4{padding-top:1.5rem!important;padding-bottom:1.5rem!important}.p-md-5{padding:3rem!important}.pt-md-5{padding-top:3rem!important}.pr-md-5{padding-right:3rem!important}.pb-md-5{padding-bottom:3rem!important}.pl-md-5{padding-left:3rem!important}.px-md-5{padding-right:3rem!important;padding-left:3rem!important}.py-md-5{padding-top:3rem!important;padding-bottom:3rem!important}.m-md-auto{margin:auto!important}.mt-md-auto{margin-top:auto!important}.mr-md-auto{margin-right:auto!important}.mb-md-auto{margin-bottom:auto!important}.ml-md-auto{margin-left:auto!important}.mx-md-auto{margin-right:auto!important;margin-left:auto!important}.my-md-auto{margin-top:auto!important;margin-bottom:auto!important}}@media (min-width:992px){.m-lg-0{margin:0!important}.mt-lg-0{margin-top:0!important}.mr-lg-0{margin-right:0!important}.mb-lg-0{margin-bottom:0!important}.ml-lg-0{margin-left:0!important}.mx-lg-0{margin-right:0!important;margin-left:0!important}.my-lg-0{margin-top:0!important;margin-bottom:0!important}.m-lg-1{margin:.25rem!important}.mt-lg-1{margin-top:.25rem!important}.mr-lg-1{margin-right:.25rem!important}.mb-lg-1{margin-bottom:.25rem!important}.ml-lg-1{margin-left:.25rem!important}.mx-lg-1{margin-right:.25rem!important;margin-left:.25rem!important}.my-lg-1{margin-top:.25rem!important;margin-bottom:.25rem!important}.m-lg-2{margin:.5rem!important}.mt-lg-2{margin-top:.5rem!important}.mr-lg-2{margin-right:.5rem!important}.mb-lg-2{margin-bottom:.5rem!important}.ml-lg-2{margin-left:.5rem!important}.mx-lg-2{margin-right:.5rem!important;margin-left:.5rem!important}.my-lg-2{margin-top:.5rem!important;margin-bottom:.5rem!important}.m-lg-3{margin:1rem!important}.mt-lg-3{margin-top:1rem!important}.mr-lg-3{margin-right:1rem!important}.mb-lg-3{margin-bottom:1rem!important}.ml-lg-3{margin-left:1rem!important}.mx-lg-3{margin-right:1rem!important;margin-left:1rem!important}.my-lg-3{margin-top:1rem!important;margin-bottom:1rem!important}.m-lg-4{margin:1.5rem!important}.mt-lg-4{margin-top:1.5rem!important}.mr-lg-4{margin-right:1.5rem!important}.mb-lg-4{margin-bottom:1.5rem!important}.ml-lg-4{margin-left:1.5rem!important}.mx-lg-4{margin-right:1.5rem!important;margin-left:1.5rem!important}.my-lg-4{margin-top:1.5rem!important;margin-bottom:1.5rem!important}.m-lg-5{margin:3rem!important}.mt-lg-5{margin-top:3rem!important}.mr-lg-5{margin-right:3rem!important}.mb-lg-5{margin-bottom:3rem!important}.ml-lg-5{margin-left:3rem!important}.mx-lg-5{margin-right:3rem!important;margin-left:3rem!important}.my-lg-5{margin-top:3rem!important;margin-bottom:3rem!important}.p-lg-0{padding:0!important}.pt-lg-0{padding-top:0!important}.pr-lg-0{padding-right:0!important}.pb-lg-0{padding-bottom:0!important}.pl-lg-0{padding-left:0!important}.px-lg-0{padding-right:0!important;padding-left:0!important}.py-lg-0{padding-top:0!important;padding-bottom:0!important}.p-lg-1{padding:.25rem!important}.pt-lg-1{padding-top:.25rem!important}.pr-lg-1{padding-right:.25rem!important}.pb-lg-1{padding-bottom:.25rem!important}.pl-lg-1{padding-left:.25rem!important}.px-lg-1{padding-right:.25rem!important;padding-left:.25rem!important}.py-lg-1{padding-top:.25rem!important;padding-bottom:.25rem!important}.p-lg-2{padding:.5rem!important}.pt-lg-2{padding-top:.5rem!important}.pr-lg-2{padding-right:.5rem!important}.pb-lg-2{padding-bottom:.5rem!important}.pl-lg-2{padding-left:.5rem!important}.px-lg-2{padding-right:.5rem!important;padding-left:.5rem!important}.py-lg-2{padding-top:.5rem!important;padding-bottom:.5rem!important}.p-lg-3{padding:1rem!important}.pt-lg-3{padding-top:1rem!important}.pr-lg-3{padding-right:1rem!important}.pb-lg-3{padding-bottom:1rem!important}.pl-lg-3{padding-left:1rem!important}.px-lg-3{padding-right:1rem!important;padding-left:1rem!important}.py-lg-3{padding-top:1rem!important;padding-bottom:1rem!important}.p-lg-4{padding:1.5rem!important}.pt-lg-4{padding-top:1.5rem!important}.pr-lg-4{padding-right:1.5rem!important}.pb-lg-4{padding-bottom:1.5rem!important}.pl-lg-4{padding-left:1.5rem!important}.px-lg-4{padding-right:1.5rem!important;padding-left:1.5rem!important}.py-lg-4{padding-top:1.5rem!important;padding-bottom:1.5rem!important}.p-lg-5{padding:3rem!important}.pt-lg-5{padding-top:3rem!important}.pr-lg-5{padding-right:3rem!important}.pb-lg-5{padding-bottom:3rem!important}.pl-lg-5{padding-left:3rem!important}.px-lg-5{padding-right:3rem!important;padding-left:3rem!important}.py-lg-5{padding-top:3rem!important;padding-bottom:3rem!important}.m-lg-auto{margin:auto!important}.mt-lg-auto{margin-top:auto!important}.mr-lg-auto{margin-right:auto!important}.mb-lg-auto{margin-bottom:auto!important}.ml-lg-auto{margin-left:auto!important}.mx-lg-auto{margin-right:auto!important;margin-left:auto!important}.my-lg-auto{margin-top:auto!important;margin-bottom:auto!important}}@media (min-width:1200px){.m-xl-0{margin:0!important}.mt-xl-0{margin-top:0!important}.mr-xl-0{margin-right:0!important}.mb-xl-0{margin-bottom:0!important}.ml-xl-0{margin-left:0!important}.mx-xl-0{margin-right:0!important;margin-left:0!important}.my-xl-0{margin-top:0!important;margin-bottom:0!important}.m-xl-1{margin:.25rem!important}.mt-xl-1{margin-top:.25rem!important}.mr-xl-1{margin-right:.25rem!important}.mb-xl-1{margin-bottom:.25rem!important}.ml-xl-1{margin-left:.25rem!important}.mx-xl-1{margin-right:.25rem!important;margin-left:.25rem!important}.my-xl-1{margin-top:.25rem!important;margin-bottom:.25rem!important}.m-xl-2{margin:.5rem!important}.mt-xl-2{margin-top:.5rem!important}.mr-xl-2{margin-right:.5rem!important}.mb-xl-2{margin-bottom:.5rem!important}.ml-xl-2{margin-left:.5rem!important}.mx-xl-2{margin-right:.5rem!important;margin-left:.5rem!important}.my-xl-2{margin-top:.5rem!important;margin-bottom:.5rem!important}.m-xl-3{margin:1rem!important}.mt-xl-3{margin-top:1rem!important}.mr-xl-3{margin-right:1rem!important}.mb-xl-3{margin-bottom:1rem!important}.ml-xl-3{margin-left:1rem!important}.mx-xl-3{margin-right:1rem!important;margin-left:1rem!important}.my-xl-3{margin-top:1rem!important;margin-bottom:1rem!important}.m-xl-4{margin:1.5rem!important}.mt-xl-4{margin-top:1.5rem!important}.mr-xl-4{margin-right:1.5rem!important}.mb-xl-4{margin-bottom:1.5rem!important}.ml-xl-4{margin-left:1.5rem!important}.mx-xl-4{margin-right:1.5rem!important;margin-left:1.5rem!important}.my-xl-4{margin-top:1.5rem!important;margin-bottom:1.5rem!important}.m-xl-5{margin:3rem!important}.mt-xl-5{margin-top:3rem!important}.mr-xl-5{margin-right:3rem!important}.mb-xl-5{margin-bottom:3rem!important}.ml-xl-5{margin-left:3rem!important}.mx-xl-5{margin-right:3rem!important;margin-left:3rem!important}.my-xl-5{margin-top:3rem!important;margin-bottom:3rem!important}.p-xl-0{padding:0!important}.pt-xl-0{padding-top:0!important}.pr-xl-0{padding-right:0!important}.pb-xl-0{padding-bottom:0!important}.pl-xl-0{padding-left:0!important}.px-xl-0{padding-right:0!important;padding-left:0!important}.py-xl-0{padding-top:0!important;padding-bottom:0!important}.p-xl-1{padding:.25rem!important}.pt-xl-1{padding-top:.25rem!important}.pr-xl-1{padding-right:.25rem!important}.pb-xl-1{padding-bottom:.25rem!important}.pl-xl-1{padding-left:.25rem!important}.px-xl-1{padding-right:.25rem!important;padding-left:.25rem!important}.py-xl-1{padding-top:.25rem!important;padding-bottom:.25rem!important}.p-xl-2{padding:.5rem!important}.pt-xl-2{padding-top:.5rem!important}.pr-xl-2{padding-right:.5rem!important}.pb-xl-2{padding-bottom:.5rem!important}.pl-xl-2{padding-left:.5rem!important}.px-xl-2{padding-right:.5rem!important;padding-left:.5rem!important}.py-xl-2{padding-top:.5rem!important;padding-bottom:.5rem!important}.p-xl-3{padding:1rem!important}.pt-xl-3{padding-top:1rem!important}.pr-xl-3{padding-right:1rem!important}.pb-xl-3{padding-bottom:1rem!important}.pl-xl-3{padding-left:1rem!important}.px-xl-3{padding-right:1rem!important;padding-left:1rem!important}.py-xl-3{padding-top:1rem!important;padding-bottom:1rem!important}.p-xl-4{padding:1.5rem!important}.pt-xl-4{padding-top:1.5rem!important}.pr-xl-4{padding-right:1.5rem!important}.pb-xl-4{padding-bottom:1.5rem!important}.pl-xl-4{padding-left:1.5rem!important}.px-xl-4{padding-right:1.5rem!important;padding-left:1.5rem!important}.py-xl-4{padding-top:1.5rem!important;padding-bottom:1.5rem!important}.p-xl-5{padding:3rem!important}.pt-xl-5{padding-top:3rem!important}.pr-xl-5{padding-right:3rem!important}.pb-xl-5{padding-bottom:3rem!important}.pl-xl-5{padding-left:3rem!important}.px-xl-5{padding-right:3rem!important;padding-left:3rem!important}.py-xl-5{padding-top:3rem!important;padding-bottom:3rem!important}.m-xl-auto{margin:auto!important}.mt-xl-auto{margin-top:auto!important}.mr-xl-auto{margin-right:auto!important}.mb-xl-auto{margin-bottom:auto!important}.ml-xl-auto{margin-left:auto!important}.mx-xl-auto{margin-right:auto!important;margin-left:auto!important}.my-xl-auto{margin-top:auto!important;margin-bottom:auto!important}}.text-justify{text-align:justify!important}.text-nowrap{white-space:nowrap!important}.text-truncate{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.text-left{text-align:left!important}.text-right{text-align:right!important}.text-center{text-align:center!important}@media (min-width:576px){.text-sm-left{text-align:left!important}.text-sm-right{text-align:right!important}.text-sm-center{text-align:center!important}}@media (min-width:768px){.text-md-left{text-align:left!important}.text-md-right{text-align:right!important}.text-md-center{text-align:center!important}}@media (min-width:992px){.text-lg-left{text-align:left!important}.text-lg-right{text-align:right!important}.text-lg-center{text-align:center!important}}@media (min-width:1200px){.text-xl-left{text-align:left!important}.text-xl-right{text-align:right!important}.text-xl-center{text-align:center!important}}.text-lowercase{text-transform:lowercase!important}.text-uppercase{text-transform:uppercase!important}.text-capitalize{text-transform:capitalize!important}.font-weight-normal{font-weight:400}.font-weight-bold{font-weight:700}.font-italic{font-style:italic}.text-white{color:#fff!important}.text-primary{color:#007bff!important}a.text-primary:focus,a.text-primary:hover{color:#0062cc!important}.text-secondary{color:#868e96!important}a.text-secondary:focus,a.text-secondary:hover{color:#6c757d!important}.text-success{color:#28a745!important}a.text-success:focus,a.text-success:hover{color:#1e7e34!important}.text-info{color:#17a2b8!important}a.text-info:focus,a.text-info:hover{color:#117a8b!important}.text-warning{color:#ffc107!important}a.text-warning:focus,a.text-warning:hover{color:#d39e00!important}.text-danger{color:#dc3545!important}a.text-danger:focus,a.text-danger:hover{color:#bd2130!important}.text-light{color:#f8f9fa!important}a.text-light:focus,a.text-light:hover{color:#dae0e5!important}.text-dark{color:#343a40!important}a.text-dark:focus,a.text-dark:hover{color:#1d2124!important}.text-muted{color:#868e96!important}.text-hide{font:0/0 a;color:transparent;text-shadow:none;background-color:transparent;border:0}.visible{visibility:visible!important}.invisible{visibility:hidden!important}
/*# sourceMappingURL=bootstrap.min.css.map */ \ No newline at end of file
diff --git a/library/bootstrap/css/bootstrap.min.css.map b/library/bootstrap/css/bootstrap.min.css.map
index 6c7fa40b9..24aa4f0c2 100644
--- a/library/bootstrap/css/bootstrap.min.css.map
+++ b/library/bootstrap/css/bootstrap.min.css.map
@@ -1 +1 @@
-{"version":3,"sources":["less/normalize.less","less/print.less","bootstrap.css","dist/css/bootstrap.css","less/glyphicons.less","less/scaffolding.less","less/mixins/vendor-prefixes.less","less/mixins/tab-focus.less","less/mixins/image.less","less/type.less","less/mixins/text-emphasis.less","less/mixins/background-variant.less","less/mixins/text-overflow.less","less/code.less","less/grid.less","less/mixins/grid.less","less/mixins/grid-framework.less","less/tables.less","less/mixins/table-row.less","less/forms.less","less/mixins/forms.less","less/buttons.less","less/mixins/buttons.less","less/mixins/opacity.less","less/component-animations.less","less/dropdowns.less","less/mixins/nav-divider.less","less/mixins/reset-filter.less","less/button-groups.less","less/mixins/border-radius.less","less/input-groups.less","less/navs.less","less/navbar.less","less/mixins/nav-vertical-align.less","less/utilities.less","less/breadcrumbs.less","less/pagination.less","less/mixins/pagination.less","less/pager.less","less/labels.less","less/mixins/labels.less","less/badges.less","less/jumbotron.less","less/thumbnails.less","less/alerts.less","less/mixins/alerts.less","less/progress-bars.less","less/mixins/gradients.less","less/mixins/progress-bar.less","less/media.less","less/list-group.less","less/mixins/list-group.less","less/panels.less","less/mixins/panels.less","less/responsive-embed.less","less/wells.less","less/close.less","less/modals.less","less/tooltip.less","less/mixins/reset-text.less","less/popovers.less","less/carousel.less","less/mixins/clearfix.less","less/mixins/center-block.less","less/mixins/hide-text.less","less/responsive-utilities.less","less/mixins/responsive-visibility.less"],"names":[],"mappings":";;;;4EAQA,KACE,YAAA,WACA,yBAAA,KACA,qBAAA,KAOF,KACE,OAAA,EAaF,QAAA,MAAA,QAAA,WAAA,OAAA,OAAA,OAAA,OAAA,KAAA,KAAA,IAAA,QAAA,QAaE,QAAA,MAQF,MAAA,OAAA,SAAA,MAIE,QAAA,aACA,eAAA,SAQF,sBACE,QAAA,KACA,OAAA,EAQF,SAAA,SAEE,QAAA,KAUF,EACE,iBAAA,YAQF,SAAA,QAEE,QAAA,EAUF,YACE,cAAA,IAAA,OAOF,EAAA,OAEE,YAAA,IAOF,IACE,WAAA,OAQF,GACE,OAAA,MAAA,EACA,UAAA,IAOF,KACE,MAAA,KACA,WAAA,KAOF,MACE,UAAA,IAOF,IAAA,IAEE,SAAA,SACA,UAAA,IACA,YAAA,EACA,eAAA,SAGF,IACE,IAAA,MAGF,IACE,OAAA,OAUF,IACE,OAAA,EAOF,eACE,SAAA,OAUF,OACE,OAAA,IAAA,KAOF,GACE,OAAA,EAAA,mBAAA,YAAA,gBAAA,YACA,WAAA,YAOF,IACE,SAAA,KAOF,KAAA,IAAA,IAAA,KAIE,YAAA,UAAA,UACA,UAAA,IAkBF,OAAA,MAAA,SAAA,OAAA,SAKE,OAAA,EACA,KAAA,QACA,MAAA,QAOF,OACE,SAAA,QAUF,OAAA,OAEE,eAAA,KAWF,OAAA,wBAAA,kBAAA,mBAIE,mBAAA,OACA,OAAA,QAOF,iBAAA,qBAEE,OAAA,QAOF,yBAAA,wBAEE,QAAA,EACA,OAAA,EAQF,MACE,YAAA,OAWF,qBAAA,kBAEE,mBAAA,WAAA,gBAAA,WAAA,WAAA,WACA,QAAA,EASF,8CAAA,8CAEE,OAAA,KAQF,mBACE,mBAAA,YACA,gBAAA,YAAA,WAAA,YAAA,mBAAA,UASF,iDAAA,8CAEE,mBAAA,KAOF,SACE,QAAA,MAAA,OAAA,MACA,OAAA,EAAA,IACA,OAAA,IAAA,MAAA,OAQF,OACE,QAAA,EACA,OAAA,EAOF,SACE,SAAA,KAQF,SACE,YAAA,IAUF,MACE,eAAA,EACA,gBAAA,SAGF,GAAA,GAEE,QAAA,uFCjUF,aA7FI,EAAA,OAAA,QAGI,MAAA,eACA,YAAA,eACA,WAAA,cAAA,mBAAA,eACA,WAAA,eAGJ,EAAA,UAEI,gBAAA,UAGJ,cACI,QAAA,KAAA,WAAA,IAGJ,kBACI,QAAA,KAAA,YAAA,IAKJ,6BAAA,mBAEI,QAAA,GAGJ,WAAA,IAEI,OAAA,IAAA,MAAA,KC4KL,kBAAA,MDvKK,MC0KL,QAAA,mBDrKK,IE8KN,GDLC,kBAAA,MDrKK,ICwKL,UAAA,eCUD,GF5KM,GE2KN,EF1KM,QAAA,ECuKL,OAAA,ECSD,GF3KM,GCsKL,iBAAA,MD/JK,QCkKL,QAAA,KCSD,YFtKU,oBCiKT,iBAAA,eD7JK,OCgKL,OAAA,IAAA,MAAA,KD5JK,OC+JL,gBAAA,mBCSD,UFpKU,UC+JT,iBAAA,eDzJS,mBEkKV,mBDLC,OAAA,IAAA,MAAA,gBEjPD,WACA,YAAA,uBFsPD,IAAA,+CE7OC,IAAK,sDAAuD,4BAA6B,iDAAkD,gBAAiB,gDAAiD,eAAgB,+CAAgD,mBAAoB,2EAA4E,cAE7W,WACA,SAAA,SACA,IAAA,IACA,QAAA,aACA,YAAA,uBACA,WAAA,OACA,YAAA,IACA,YAAA,EAIkC,uBAAA,YAAW,wBAAA,UACX,2BAAW,QAAA,QAEX,uBDuPlC,QAAS,QCtPyB,sBFiPnC,uBEjP8C,QAAA,QACX,wBAAW,QAAA,QACX,wBAAW,QAAA,QACX,2BAAW,QAAA,QACX,yBAAW,QAAA,QACX,wBAAW,QAAA,QACX,wBAAW,QAAA,QACX,yBAAW,QAAA,QACX,wBAAW,QAAA,QACX,uBAAW,QAAA,QACX,6BAAW,QAAA,QACX,uBAAW,QAAA,QACX,uBAAW,QAAA,QACX,2BAAW,QAAA,QACX,qBAAW,QAAA,QACX,0BAAW,QAAA,QACX,qBAAW,QAAA,QACX,yBAAW,QAAA,QACX,0BAAW,QAAA,QACX,2BAAW,QAAA,QACX,sBAAW,QAAA,QACX,yBAAW,QAAA,QACX,sBAAW,QAAA,QACX,wBAAW,QAAA,QACX,uBAAW,QAAA,QACX,uBAAW,QAAA,QACX,uBAAW,QAAA,QACX,uBAAW,QAAA,QACX,+BAAW,QAAA,QACX,2BAAW,QAAA,QACX,yBAAW,QAAA,QACX,wBAAW,QAAA,QACX,8BAAW,QAAA,QACX,yBAAW,QAAA,QACX,0BAAW,QAAA,QACX,2BAAW,QAAA,QACX,uBAAW,QAAA,QACX,uBAAW,QAAA,QACX,6BAAW,QAAA,QACX,6BAAW,QAAA,QACX,8BAAW,QAAA,QACX,4BAAW,QAAA,QACX,yBAAW,QAAA,QACX,0BAAW,QAAA,QACX,sBAAW,QAAA,QACX,uBAAW,QAAA,QACX,uBAAW,QAAA,QACX,2BAAW,QAAA,QACX,wBAAW,QAAA,QACX,yBAAW,QAAA,QACX,uBAAW,QAAA,QACX,uBAAW,QAAA,QACX,yBAAW,QAAA,QACX,8BAAW,QAAA,QACX,6BAAW,QAAA,QACX,6BAAW,QAAA,QACX,+BAAW,QAAA,QACX,8BAAW,QAAA,QACX,gCAAW,QAAA,QACX,uBAAW,QAAA,QACX,8BAAW,QAAA,QACX,+BAAW,QAAA,QACX,iCAAW,QAAA,QACX,0BAAW,QAAA,QACX,6BAAW,QAAA,QACX,yBAAW,QAAA,QACX,uBAAW,QAAA,QACX,uBAAW,QAAA,QACX,wBAAW,QAAA,QACX,wBAAW,QAAA,QACX,uBAAW,QAAA,QACX,gCAAW,QAAA,QACX,gCAAW,QAAA,QACX,2BAAW,QAAA,QACX,uBAAW,QAAA,QACX,wBAAW,QAAA,QACX,uBAAW,QAAA,QACX,0BAAW,QAAA,QACX,+BAAW,QAAA,QACX,+BAAW,QAAA,QACX,wBAAW,QAAA,QACX,+BAAW,QAAA,QACX,gCAAW,QAAA,QACX,4BAAW,QAAA,QACX,6BAAW,QAAA,QACX,8BAAW,QAAA,QACX,0BAAW,QAAA,QACX,gCAAW,QAAA,QACX,4BAAW,QAAA,QACX,6BAAW,QAAA,QACX,gCAAW,QAAA,QACX,4BAAW,QAAA,QACX,6BAAW,QAAA,QACX,6BAAW,QAAA,QACX,8BAAW,QAAA,QACX,2BAAW,QAAA,QACX,6BAAW,QAAA,QACX,4BAAW,QAAA,QACX,8BAAW,QAAA,QACX,+BAAW,QAAA,QACX,mCAAW,QAAA,QACX,uBAAW,QAAA,QACX,uBAAW,QAAA,QACX,uBAAW,QAAA,QACX,2BAAW,QAAA,QACX,4BAAW,QAAA,QACX,+BAAW,QAAA,QACX,wBAAW,QAAA,QACX,2BAAW,QAAA,QACX,yBAAW,QAAA,QACX,0BAAW,QAAA,QACX,yBAAW,QAAA,QACX,6BAAW,QAAA,QACX,+BAAW,QAAA,QACX,0BAAW,QAAA,QACX,gCAAW,QAAA,QACX,+BAAW,QAAA,QACX,8BAAW,QAAA,QACX,kCAAW,QAAA,QACX,oCAAW,QAAA,QACX,sBAAW,QAAA,QACX,2BAAW,QAAA,QACX,uBAAW,QAAA,QACX,8BAAW,QAAA,QACX,4BAAW,QAAA,QACX,8BAAW,QAAA,QACX,6BAAW,QAAA,QACX,4BAAW,QAAA,QACX,0BAAW,QAAA,QACX,4BAAW,QAAA,QACX,qCAAW,QAAA,QACX,oCAAW,QAAA,QACX,kCAAW,QAAA,QACX,oCAAW,QAAA,QACX,wBAAW,QAAA,QACX,yBAAW,QAAA,QACX,wBAAW,QAAA,QACX,yBAAW,QAAA,QACX,4BAAW,QAAA,QACX,6BAAW,QAAA,QACX,4BAAW,QAAA,QACX,4BAAW,QAAA,QACX,8BAAW,QAAA,QACX,uBAAW,QAAA,QACX,wBAAW,QAAA,QACX,0BAAW,QAAA,QACX,sBAAW,QAAA,QACX,sBAAW,QAAA,QACX,uBAAW,QAAA,QACX,mCAAW,QAAA,QACX,uCAAW,QAAA,QACX,gCAAW,QAAA,QACX,oCAAW,QAAA,QACX,qCAAW,QAAA,QACX,yCAAW,QAAA,QACX,4BAAW,QAAA,QACX,yBAAW,QAAA,QACX,gCAAW,QAAA,QACX,8BAAW,QAAA,QACX,yBAAW,QAAA,QACX,wBAAW,QAAA,QACX,0BAAW,QAAA,QACX,6BAAW,QAAA,QACX,yBAAW,QAAA,QACX,uBAAW,QAAA,QACX,uBAAW,QAAA,QACX,wBAAW,QAAA,QACX,yBAAW,QAAA,QACX,yBAAW,QAAA,QACX,uBAAW,QAAA,QACX,8BAAW,QAAA,QACX,+BAAW,QAAA,QACX,gCAAW,QAAA,QACX,8BAAW,QAAA,QACX,8BAAW,QAAA,QACX,8BAAW,QAAA,QACX,2BAAW,QAAA,QACX,0BAAW,QAAA,QACX,yBAAW,QAAA,QACX,6BAAW,QAAA,QACX,2BAAW,QAAA,QACX,4BAAW,QAAA,QACX,wBAAW,QAAA,QACX,wBAAW,QAAA,QACX,2BAAW,QAAA,QACX,2BAAW,QAAA,QACX,4BAAW,QAAA,QACX,+BAAW,QAAA,QACX,8BAAW,QAAA,QACX,4BAAW,QAAA,QACX,4BAAW,QAAA,QACX,4BAAW,QAAA,QACX,iCAAW,QAAA,QACX,oCAAW,QAAA,QACX,iCAAW,QAAA,QACX,+BAAW,QAAA,QACX,+BAAW,QAAA,QACX,iCAAW,QAAA,QACX,qBAAW,QAAA,QACX,4BAAW,QAAA,QACX,4BAAW,QAAA,QACX,2BAAW,QAAA,QACX,uBAAW,QAAA,QASX,wBAAW,QAAA,QACX,wBAAW,QAAA,QACX,4BAAW,QAAA,QACX,uBAAW,QAAA,QACX,wBAAW,QAAA,QACX,uBAAW,QAAA,QACX,yBAAW,QAAA,QACX,yBAAW,QAAA,QACX,+BAAW,QAAA,QACX,uBAAW,QAAA,QACX,6BAAW,QAAA,QACX,sBAAW,QAAA,QACX,wBAAW,QAAA,QACX,wBAAW,QAAA,QACX,4BAAW,QAAA,QACX,uBAAW,QAAA,QACX,4BAAW,QAAA,QACX,6BAAW,QAAA,QACX,2BAAW,QAAA,QACX,0BAAW,QAAA,QACX,sBAAW,QAAA,QACX,sBAAW,QAAA,QACX,sBAAW,QAAA,QACX,sBAAW,QAAA,QACX,wBAAW,QAAA,QACX,sBAAW,QAAA,QACX,wBAAW,QAAA,QACX,4BAAW,QAAA,QACX,mCAAW,QAAA,QACX,4BAAW,QAAA,QACX,oCAAW,QAAA,QACX,kCAAW,QAAA,QACX,iCAAW,QAAA,QACX,+BAAW,QAAA,QACX,sBAAW,QAAA,QACX,wBAAW,QAAA,QACX,6BAAW,QAAA,QACX,4BAAW,QAAA,QACX,6BAAW,QAAA,QACX,kCAAW,QAAA,QACX,mCAAW,QAAA,QACX,sCAAW,QAAA,QACX,0CAAW,QAAA,QACX,oCAAW,QAAA,QACX,wCAAW,QAAA,QACX,qCAAW,QAAA,QACX,iCAAW,QAAA,QACX,gCAAW,QAAA,QACX,kCAAW,QAAA,QACX,+BAAW,QAAA,QACX,0BAAW,QAAA,QACX,8BAAW,QAAA,QACX,4BAAW,QAAA,QACX,4BAAW,QAAA,QACX,6BAAW,QAAA,QACX,4BAAW,QAAA,QCtS/C,0BCgEE,QAAA,QHi+BF,EDNC,mBAAA,WGxhCI,gBAAiB,WFiiCZ,WAAY,WGl+BZ,OADL,QJg+BJ,mBAAA,WGthCI,gBAAiB,WACpB,WAAA,WHyhCD,KGrhCC,UAAW,KAEX,4BAAA,cAEA,KACA,YAAA,iBAAA,UAAA,MAAA,WHuhCD,UAAA,KGnhCC,YAAa,WF4hCb,MAAO,KACP,iBAAkB,KExhClB,OADA,MAEA,OHqhCD,SG/gCC,YAAa,QACb,UAAA,QACA,YAAA,QAEA,EFwhCA,MAAO,QEthCL,gBAAA,KAIF,QH8gCD,QKjkCC,MAAA,QACA,gBAAA,UF6DF,QACE,QAAA,IAAA,KAAA,yBHygCD,eAAA,KGlgCC,OHqgCD,OAAA,ECSD,IACE,eAAgB,ODDjB,4BM/kCC,0BLklCF,gBKnlCE,iBADA,eH4EA,QAAS,MACT,UAAA,KHugCD,OAAA,KGhgCC,aACA,cAAA,IAEA,eACA,QAAA,aC6FA,UAAA,KACK,OAAA,KACG,QAAA,IEvLR,YAAA,WACA,iBAAA,KACA,OAAA,IAAA,MAAA,KN+lCD,cAAA,IGjgCC,mBAAoB,IAAI,IAAI,YAC5B,cAAA,IAAA,IAAA,YHmgCD,WAAA,IAAA,IAAA,YG5/BC,YACA,cAAA,IAEA,GH+/BD,WAAA,KGv/BC,cAAe,KACf,OAAA,EACA,WAAA,IAAA,MAAA,KAEA,SACA,SAAA,SACA,MAAA,IACA,OAAA,IACA,QAAA,EHy/BD,OAAA,KGj/BC,SAAA,OF0/BA,KAAM,cEx/BJ,OAAA,EAEA,0BACA,yBACA,SAAA,OACA,MAAA,KHm/BH,OAAA,KGx+BC,OAAQ,EACR,SAAA,QH0+BD,KAAA,KCSD,cACE,OAAQ,QAQV,IACA,IMlpCE,IACA,IACA,IACA,INwoCF,GACA,GACA,GACA,GACA,GACA,GDAC,YAAA,QOlpCC,YAAa,IN2pCb,YAAa,IACb,MAAO,QAoBT,WAZA,UAaA,WAZA,UM5pCI,WN6pCJ,UM5pCI,WN6pCJ,UM5pCI,WN6pCJ,UDMC,WCLD,UACA,UAZA,SAaA,UAZA,SAaA,UAZA,SAaA,UAZA,SAaA,UAZA,SAaA,UAZA,SMppCE,YAAa,INwqCb,YAAa,EACb,MAAO,KAGT,IMxqCE,IAJF,IN2qCA,GAEA,GDLC,GCSC,WAAY,KACZ,cAAe,KASjB,WANA,UDCC,WCCD,UM5qCA,WN8qCA,UACA,UANA,SM5qCI,UN8qCJ,SM3qCA,UN6qCA,SAQE,UAAW,IAGb,IMprCE,IAJF,INurCA,GAEA,GDLC,GCSC,WAAY,KACZ,cAAe,KASjB,WANA,UDCC,WCCD,UMvrCA,WNyrCA,UACA,UANA,SMxrCI,UN0rCJ,SMtrCA,UNwrCA,SMxrCU,UAAA,IACV,IAAA,GAAU,UAAA,KACV,IAAA,GAAU,UAAA,KACV,IAAA,GAAU,UAAA,KACV,IAAA,GAAU,UAAA,KACV,IAAA,GAAU,UAAA,KAOR,IADF,GPssCC,UAAA,KCSD,EMzsCE,OAAA,EAAA,EAAA,KAEA,MPosCD,cAAA,KO/rCC,UAAW,KAwOX,YAAa,IA1OX,YAAA,IPssCH,yBO7rCC,MNssCE,UAAW,MMjsCf,OAAA,MAEE,UAAA,IAKF,MP0rCC,KO1rCsB,QAAA,KP6rCtB,iBAAA,QO5rCsB,WP+rCtB,WAAA,KO9rCsB,YPisCtB,WAAA,MOhsCsB,aPmsCtB,WAAA,OOlsCsB,cPqsCtB,WAAA,QOlsCsB,aPqsCtB,YAAA,OOpsCsB,gBPusCtB,eAAA,UOtsCsB,gBPysCtB,eAAA,UOrsCC,iBPwsCD,eAAA,WQ3yCC,YR8yCD,MAAA,KCSD,cOpzCI,MAAA,QAHF,qBDwGF,qBP6sCC,MAAA,QCSD,cO3zCI,MAAA,QAHF,qBD2GF,qBPitCC,MAAA,QCSD,WOl0CI,MAAA,QAHF,kBD8GF,kBPqtCC,MAAA,QCSD,cOz0CI,MAAA,QAHF,qBDiHF,qBPytCC,MAAA,QCSD,aOh1CI,MAAA,QDwHF,oBAHF,oBExHE,MAAA,QACA,YR01CA,MAAO,KQx1CL,iBAAA,QAHF,mBF8HF,mBP2tCC,iBAAA,QCSD,YQ/1CI,iBAAA,QAHF,mBFiIF,mBP+tCC,iBAAA,QCSD,SQt2CI,iBAAA,QAHF,gBFoIF,gBPmuCC,iBAAA,QCSD,YQ72CI,iBAAA,QAHF,mBFuIF,mBPuuCC,iBAAA,QCSD,WQp3CI,iBAAA,QF6IF,kBADF,kBAEE,iBAAA,QPsuCD,aO7tCC,eAAgB,INsuChB,OAAQ,KAAK,EAAE,KMpuCf,cAAA,IAAA,MAAA,KAFF,GPkuCC,GCSC,WAAY,EACZ,cAAe,KM9tCf,MP0tCD,MO3tCD,MAPI,MASF,cAAA,EAIF,eALE,aAAA,EACA,WAAA,KPkuCD,aO9tCC,aAAc,EAKZ,YAAA,KACA,WAAA,KP6tCH,gBOvtCC,QAAS,aACT,cAAA,IACA,aAAA,IAEF,GNguCE,WAAY,EM9tCZ,cAAA,KAGA,GADF,GP0tCC,YAAA,WOttCC,GPytCD,YAAA,IOnnCD,GAvFM,YAAA,EAEA,yBACA,kBGtNJ,MAAA,KACA,MAAA,MACA,SAAA,OVq6CC,MAAA,KO7nCC,WAAY,MAhFV,cAAA,SPgtCH,YAAA,OOtsCD,kBNgtCE,YAAa,OM1sCjB,0BPssCC,YOrsCC,OAAA,KA9IqB,cAAA,IAAA,OAAA,KAmJvB,YACE,UAAA,IACA,eAAA,UAEA,WPssCD,QAAA,KAAA,KOjsCG,OAAA,EAAA,EAAA,KN0sCF,UAAW,OACX,YAAa,IAAI,MAAM,KMptCzB,yBP+sCC,wBO/sCD,yBNytCE,cAAe,EMnsCb,kBAFA,kBACA,iBPksCH,QAAA,MO/rCG,UAAA,INwsCF,YAAa,WACb,MAAO,KMhsCT,yBP2rCC,yBO3rCD,wBAEE,QAAA,cAEA,oBACA,sBACA,cAAA,KP6rCD,aAAA,EOvrCG,WAAA,MNgsCF,aAAc,IAAI,MAAM,KACxB,YAAa,EMhsCX,kCNksCJ,kCMnsCe,iCACX,oCNmsCJ,oCDLC,mCCUC,QAAS,GMjsCX,iCNmsCA,iCMzsCM,gCAOJ,mCNmsCF,mCDLC,kCO7rCC,QAAA,cPksCD,QWv+CC,cAAe,KVg/Cf,WAAY,OACZ,YAAa,WU7+Cb,KXy+CD,IWr+CD,IACE,KACA,YAAA,MAAA,OAAA,SAAA,cAAA,UAEA,KACA,QAAA,IAAA,IXu+CD,UAAA,IWn+CC,MAAO,QACP,iBAAA,QACA,cAAA,IAEA,IACA,QAAA,IAAA,IACA,UAAA,IV4+CA,MU5+CA,KXq+CD,iBAAA,KW3+CC,cAAe,IASb,mBAAA,MAAA,EAAA,KAAA,EAAA,gBACA,WAAA,MAAA,EAAA,KAAA,EAAA,gBAEA,QV6+CF,QU7+CE,EXq+CH,UAAA,KWh+CC,YAAa,IACb,mBAAA,KACA,WAAA,KAEA,IACA,QAAA,MACA,QAAA,MACA,OAAA,EAAA,EAAA,KACA,UAAA,KACA,YAAA,WACA,MAAA,KACA,WAAA,UXk+CD,UAAA,WW7+CC,iBAAkB,QAehB,OAAA,IAAA,MAAA,KACA,cAAA,IAEA,SACA,QAAA,EACA,UAAA,QXi+CH,MAAA,QW59CC,YAAa,SACb,iBAAA,YACA,cAAA,EC1DF,gBCHE,WAAA,MACA,WAAA,OAEA,Wb8hDD,cAAA,KYxhDC,aAAA,KAqEA,aAAc,KAvEZ,YAAA,KZ+hDH,yBY1hDC,WAkEE,MAAO,OZ69CV,yBY5hDC,WA+DE,MAAO,OZk+CV,0BYzhDC,WCvBA,MAAA,QAGA,iBbmjDD,cAAA,KYthDC,aAAc,KCvBd,aAAA,KACA,YAAA,KCAE,KACE,aAAA,MAEA,YAAA,MAGA,UAAA,WAAA,WAAA,WAAA,UAAA,UAAA,UAAA,UAAA,UAAA,UAAA,UAAA,UAAA,UAAA,WAAA,WAAA,WAAA,UAAA,UAAA,UAAA,UAAA,UAAA,UAAA,UAAA,UAAA,UAAA,WAAA,WAAA,WAAA,UAAA,UAAA,UAAA,UAAA,UAAA,UAAA,UAAA,UAAA,UAAA,WAAA,WAAA,WAAA,UAAA,UAAA,UAAA,UAAA,UAAA,UAAA,UAAA,UdgjDL,SAAA,SchiDG,WAAA,IACE,cAAA,KdkiDL,aAAA,Kc1hDG,UAAA,WAAA,WAAA,WAAA,UAAA,UAAA,UAAA,UAAA,UAAA,UAAA,UAAA,Ud6hDH,MAAA,Kc7hDG,WdgiDH,MAAA,KchiDG,WdmiDH,MAAA,acniDG,WdsiDH,MAAA,actiDG,UdyiDH,MAAA,IcziDG,Ud4iDH,MAAA,ac5iDG,Ud+iDH,MAAA,ac/iDG,UdkjDH,MAAA,IcljDG,UdqjDH,MAAA,acrjDG,UdwjDH,MAAA,acxjDG,Ud2jDH,MAAA,Ic3jDG,Ud8jDH,MAAA,ac/iDG,UdkjDH,MAAA,YcljDG,gBdqjDH,MAAA,KcrjDG,gBdwjDH,MAAA,acxjDG,gBd2jDH,MAAA,ac3jDG,ed8jDH,MAAA,Ic9jDG,edikDH,MAAA,acjkDG,edokDH,MAAA,acpkDG,edukDH,MAAA,IcvkDG,ed0kDH,MAAA,ac1kDG,ed6kDH,MAAA,ac7kDG,edglDH,MAAA,IchlDG,edmlDH,MAAA,ac9kDG,edilDH,MAAA,YchmDG,edmmDH,MAAA,KcnmDG,gBdsmDH,KAAA,KctmDG,gBdymDH,KAAA,aczmDG,gBd4mDH,KAAA,ac5mDG,ed+mDH,KAAA,Ic/mDG,edknDH,KAAA,aclnDG,edqnDH,KAAA,acrnDG,edwnDH,KAAA,IcxnDG,ed2nDH,KAAA,ac3nDG,ed8nDH,KAAA,ac9nDG,edioDH,KAAA,IcjoDG,edooDH,KAAA,ac/nDG,edkoDH,KAAA,YcnnDG,edsnDH,KAAA,KctnDG,kBdynDH,YAAA,KcznDG,kBd4nDH,YAAA,ac5nDG,kBd+nDH,YAAA,ac/nDG,iBdkoDH,YAAA,IcloDG,iBdqoDH,YAAA,acroDG,iBdwoDH,YAAA,acxoDG,iBd2oDH,YAAA,Ic3oDG,iBd8oDH,YAAA,ac9oDG,iBdipDH,YAAA,acjpDG,iBdopDH,YAAA,IcppDG,iBdupDH,YAAA,acvpDG,iBd0pDH,YAAA,Yc5rDG,iBACE,YAAA,EAOJ,yBACE,UAAA,WAAA,WAAA,WAAA,UAAA,UAAA,UAAA,UAAA,UAAA,UAAA,UAAA,Ud0rDD,MAAA,Kc1rDC,Wd6rDD,MAAA,Kc7rDC,WdgsDD,MAAA,achsDC,WdmsDD,MAAA,acnsDC,UdssDD,MAAA,IctsDC,UdysDD,MAAA,aczsDC,Ud4sDD,MAAA,ac5sDC,Ud+sDD,MAAA,Ic/sDC,UdktDD,MAAA,acltDC,UdqtDD,MAAA,acrtDC,UdwtDD,MAAA,IcxtDC,Ud2tDD,MAAA,ac5sDC,Ud+sDD,MAAA,Yc/sDC,gBdktDD,MAAA,KcltDC,gBdqtDD,MAAA,acrtDC,gBdwtDD,MAAA,acxtDC,ed2tDD,MAAA,Ic3tDC,ed8tDD,MAAA,ac9tDC,ediuDD,MAAA,acjuDC,edouDD,MAAA,IcpuDC,eduuDD,MAAA,acvuDC,ed0uDD,MAAA,ac1uDC,ed6uDD,MAAA,Ic7uDC,edgvDD,MAAA,ac3uDC,ed8uDD,MAAA,Yc7vDC,edgwDD,MAAA,KchwDC,gBdmwDD,KAAA,KcnwDC,gBdswDD,KAAA,actwDC,gBdywDD,KAAA,aczwDC,ed4wDD,KAAA,Ic5wDC,ed+wDD,KAAA,ac/wDC,edkxDD,KAAA,aclxDC,edqxDD,KAAA,IcrxDC,edwxDD,KAAA,acxxDC,ed2xDD,KAAA,ac3xDC,ed8xDD,KAAA,Ic9xDC,ediyDD,KAAA,ac5xDC,ed+xDD,KAAA,YchxDC,edmxDD,KAAA,KcnxDC,kBdsxDD,YAAA,KctxDC,kBdyxDD,YAAA,aczxDC,kBd4xDD,YAAA,ac5xDC,iBd+xDD,YAAA,Ic/xDC,iBdkyDD,YAAA,aclyDC,iBdqyDD,YAAA,acryDC,iBdwyDD,YAAA,IcxyDC,iBd2yDD,YAAA,ac3yDC,iBd8yDD,YAAA,ac9yDC,iBdizDD,YAAA,IcjzDC,iBdozDD,YAAA,acpzDC,iBduzDD,YAAA,YY9yDD,iBE3CE,YAAA,GAQF,yBACE,UAAA,WAAA,WAAA,WAAA,UAAA,UAAA,UAAA,UAAA,UAAA,UAAA,UAAA,Udw1DD,MAAA,Kcx1DC,Wd21DD,MAAA,Kc31DC,Wd81DD,MAAA,ac91DC,Wdi2DD,MAAA,acj2DC,Udo2DD,MAAA,Icp2DC,Udu2DD,MAAA,acv2DC,Ud02DD,MAAA,ac12DC,Ud62DD,MAAA,Ic72DC,Udg3DD,MAAA,ach3DC,Udm3DD,MAAA,acn3DC,Uds3DD,MAAA,Ict3DC,Udy3DD,MAAA,ac12DC,Ud62DD,MAAA,Yc72DC,gBdg3DD,MAAA,Kch3DC,gBdm3DD,MAAA,acn3DC,gBds3DD,MAAA,act3DC,edy3DD,MAAA,Icz3DC,ed43DD,MAAA,ac53DC,ed+3DD,MAAA,ac/3DC,edk4DD,MAAA,Icl4DC,edq4DD,MAAA,acr4DC,edw4DD,MAAA,acx4DC,ed24DD,MAAA,Ic34DC,ed84DD,MAAA,acz4DC,ed44DD,MAAA,Yc35DC,ed85DD,MAAA,Kc95DC,gBdi6DD,KAAA,Kcj6DC,gBdo6DD,KAAA,acp6DC,gBdu6DD,KAAA,acv6DC,ed06DD,KAAA,Ic16DC,ed66DD,KAAA,ac76DC,edg7DD,KAAA,ach7DC,edm7DD,KAAA,Icn7DC,eds7DD,KAAA,act7DC,edy7DD,KAAA,acz7DC,ed47DD,KAAA,Ic57DC,ed+7DD,KAAA,ac17DC,ed67DD,KAAA,Yc96DC,edi7DD,KAAA,Kcj7DC,kBdo7DD,YAAA,Kcp7DC,kBdu7DD,YAAA,acv7DC,kBd07DD,YAAA,ac17DC,iBd67DD,YAAA,Ic77DC,iBdg8DD,YAAA,ach8DC,iBdm8DD,YAAA,acn8DC,iBds8DD,YAAA,Ict8DC,iBdy8DD,YAAA,acz8DC,iBd48DD,YAAA,ac58DC,iBd+8DD,YAAA,Ic/8DC,iBdk9DD,YAAA,acl9DC,iBdq9DD,YAAA,YYz8DD,iBE9CE,YAAA,GAQF,0BACE,UAAA,WAAA,WAAA,WAAA,UAAA,UAAA,UAAA,UAAA,UAAA,UAAA,UAAA,Uds/DD,MAAA,Kct/DC,Wdy/DD,MAAA,Kcz/DC,Wd4/DD,MAAA,ac5/DC,Wd+/DD,MAAA,ac//DC,UdkgED,MAAA,IclgEC,UdqgED,MAAA,acrgEC,UdwgED,MAAA,acxgEC,Ud2gED,MAAA,Ic3gEC,Ud8gED,MAAA,ac9gEC,UdihED,MAAA,acjhEC,UdohED,MAAA,IcphEC,UduhED,MAAA,acxgEC,Ud2gED,MAAA,Yc3gEC,gBd8gED,MAAA,Kc9gEC,gBdihED,MAAA,acjhEC,gBdohED,MAAA,acphEC,eduhED,MAAA,IcvhEC,ed0hED,MAAA,ac1hEC,ed6hED,MAAA,ac7hEC,edgiED,MAAA,IchiEC,edmiED,MAAA,acniEC,edsiED,MAAA,actiEC,edyiED,MAAA,IcziEC,ed4iED,MAAA,acviEC,ed0iED,MAAA,YczjEC,ed4jED,MAAA,Kc5jEC,gBd+jED,KAAA,Kc/jEC,gBdkkED,KAAA,aclkEC,gBdqkED,KAAA,acrkEC,edwkED,KAAA,IcxkEC,ed2kED,KAAA,ac3kEC,ed8kED,KAAA,ac9kEC,edilED,KAAA,IcjlEC,edolED,KAAA,acplEC,edulED,KAAA,acvlEC,ed0lED,KAAA,Ic1lEC,ed6lED,KAAA,acxlEC,ed2lED,KAAA,Yc5kEC,ed+kED,KAAA,Kc/kEC,kBdklED,YAAA,KcllEC,kBdqlED,YAAA,acrlEC,kBdwlED,YAAA,acxlEC,iBd2lED,YAAA,Ic3lEC,iBd8lED,YAAA,ac9lEC,iBdimED,YAAA,acjmEC,iBdomED,YAAA,IcpmEC,iBdumED,YAAA,acvmEC,iBd0mED,YAAA,ac1mEC,iBd6mED,YAAA,Ic7mEC,iBdgnED,YAAA,achnEC,iBdmnED,YAAA,YetrED,iBACA,YAAA,GAGA,MACA,iBAAA,YAEA,QfyrED,YAAA,IevrEC,eAAgB,IAChB,MAAA,KfyrED,WAAA,KelrEC,GACA,WAAA,KfsrED,OexrEC,MAAO,KdmsEP,UAAW,KACX,cAAe,KcvrET,mBd0rER,mBczrEQ,mBAHA,mBACA,mBd0rER,mBDHC,QAAA,IensEC,YAAa,WAoBX,eAAA,IACA,WAAA,IAAA,MAAA,KArBJ,mBdktEE,eAAgB,OAChB,cAAe,IAAI,MAAM,KDJ1B,uCCMD,uCcrtEA,wCdstEA,wCclrEI,2CANI,2CforEP,WAAA,EezqEG,mBf4qEH,WAAA,IAAA,MAAA,KCWD,cACE,iBAAkB,Kc/pEpB,6BdkqEA,6BcjqEE,6BAZM,6BfsqEP,6BCMD,6BDHC,QAAA,ICWD,gBACE,OAAQ,IAAI,MAAM,Kc1qEpB,4Bd6qEA,4Bc7qEA,4BAQQ,4Bf8pEP,4BCMD,4Bc7pEM,OAAA,IAAA,MAAA,KAYF,4BAFJ,4BfopEC,oBAAA,IevoEG,yCf0oEH,iBAAA,QehoEC,4BACA,iBAAA,QfooED,uBe9nEG,SAAA,OdyoEF,QAAS,acxoEL,MAAA,KAEA,sBfioEL,sBgB7wEC,SAAA,OfwxEA,QAAS,WACT,MAAO,KAST,0BerxEE,0Bf+wEF,0BAGA,0BexxEM,0BAMJ,0BfgxEF,0BAGA,0BACA,0BDNC,0BCAD,0BAGA,0BASE,iBAAkB,QDLnB,sCgBlyEC,sCAAA,oCfyyEF,sCetxEM,sCf2xEJ,iBAAkB,QASpB,2Be1yEE,2BfoyEF,2BAGA,2Be7yEM,2BAMJ,2BfqyEF,2BAGA,2BACA,2BDNC,2BCAD,2BAGA,2BASE,iBAAkB,QDLnB,uCgBvzEC,uCAAA,qCf8zEF,uCe3yEM,uCfgzEJ,iBAAkB,QASpB,wBe/zEE,wBfyzEF,wBAGA,wBel0EM,wBAMJ,wBf0zEF,wBAGA,wBACA,wBDNC,wBCAD,wBAGA,wBASE,iBAAkB,QDLnB,oCgB50EC,oCAAA,kCfm1EF,oCeh0EM,oCfq0EJ,iBAAkB,QASpB,2Bep1EE,2Bf80EF,2BAGA,2Bev1EM,2BAMJ,2Bf+0EF,2BAGA,2BACA,2BDNC,2BCAD,2BAGA,2BASE,iBAAkB,QDLnB,uCgBj2EC,uCAAA,qCfw2EF,uCer1EM,uCf01EJ,iBAAkB,QASpB,0Bez2EE,0Bfm2EF,0BAGA,0Be52EM,0BAMJ,0Bfo2EF,0BAGA,0BACA,0BDNC,0BCAD,0BAGA,0BASE,iBAAkB,QDLnB,sCehtEC,sCADF,oCdwtEA,sCe12EM,sCDoJJ,iBAAA,QA6DF,kBACE,WAAY,KA3DV,WAAA,KAEA,oCACA,kBACA,MAAA,KfotED,cAAA,Ke7pEC,WAAY,OAnDV,mBAAA,yBfmtEH,OAAA,IAAA,MAAA,KCWD,yBACE,cAAe,Ec5qEjB,qCd+qEA,qCcjtEI,qCARM,qCfktET,qCCMD,qCDHC,YAAA,OCWD,kCACE,OAAQ,EcvrEV,0Dd0rEA,0Dc1rEA,0DAzBU,0Df4sET,0DCMD,0DAME,YAAa,Ec/rEf,yDdksEA,yDclsEA,yDArBU,yDfgtET,yDCMD,yDAME,aAAc,EDLjB,yDe1sEW,yDEzNV,yDjBk6EC,yDiBj6ED,cAAA,GAMA,SjBk6ED,UAAA,EiB/5EC,QAAS,EACT,OAAA,EACA,OAAA,EAEA,OACA,QAAA,MACA,MAAA,KACA,QAAA,EACA,cAAA,KACA,UAAA,KjBi6ED,YAAA,QiB95EC,MAAO,KACP,OAAA,EACA,cAAA,IAAA,MAAA,QAEA,MjBg6ED,QAAA,aiBr5EC,UAAW,Kb4BX,cAAA,IACG,YAAA,IJ63EJ,mBiBr5EC,mBAAoB,WhBg6EjB,gBAAiB,WgB95EpB,WAAA,WjBy5ED,qBiBv5EC,kBAGA,OAAQ,IAAI,EAAE,EACd,WAAA,MjBs5ED,YAAA,OiBj5EC,iBACA,QAAA,MAIF,kBhB25EE,QAAS,MgBz5ET,MAAA,KAIF,iBAAA,ahB05EE,OAAQ,KI99ER,uBY2EF,2BjB64EC,wBiB54EC,QAAA,IAAA,KAAA,yBACA,eAAA,KAEA,OACA,QAAA,MjB+4ED,YAAA,IiBr3EC,UAAW,KACX,YAAA,WACA,MAAA,KAEA,cACA,QAAA,MACA,MAAA,KACA,OAAA,KACA,QAAA,IAAA,KACA,UAAA,KACA,YAAA,WACA,MAAA,KbxDA,iBAAA,KACQ,iBAAA,KAyHR,OAAA,IAAA,MAAA,KACK,cAAA,IACG,mBAAA,MAAA,EAAA,IAAA,IAAA,iBJwzET,WAAA,MAAA,EAAA,IAAA,IAAA,iBkBh8EC,mBAAA,aAAA,YAAA,KAAA,mBAAA,YAAA,KACE,cAAA,aAAA,YAAA,KAAA,WAAA,YAAA,KACA,WAAA,aAAA,YAAA,KAAA,WAAA,YAAA,KdWM,oBJy7ET,aAAA,QIx5EC,QAAA,EACE,mBAAA,MAAA,EAAA,IAAA,IAAA,iBAAA,EAAA,EAAA,IAAA,qBACA,WAAA,MAAA,EAAA,IAAA,IAAA,iBAAA,EAAA,EAAA,IAAA,qBAEF,gCAA0B,MAAA,KJ25E3B,QAAA,EI15EiC,oCJ65EjC,MAAA,KiBh4EG,yCACA,MAAA,KAQF,0BhBs4EA,iBAAkB,YAClB,OAAQ,EgBn4EN,wBjB63EH,wBiB13EC,iChBq4EA,iBAAkB,KgBn4EhB,QAAA,EAIF,wBACE,iCjB03EH,OAAA,YiB72EC,sBjBg3ED,OAAA,KiB91EG,mBhB02EF,mBAAoB,KAEtB,qDgB32EM,8BjBo2EH,8BiBj2EC,wCAAA,+BhB62EA,YAAa,KgB32EX,iCjBy2EH,iCiBt2EC,2CAAA,kChB02EF,0BACA,0BACA,oCACA,2BAKE,YAAa,KgBh3EX,iCjB82EH,iCACF,2CiBp2EC,kChBu2EA,0BACA,0BACA,oCACA,2BgBz2EA,YAAA,MhBi3EF,YgBv2EE,cAAA,KAGA,UADA,OjBi2ED,SAAA,SiBr2EC,QAAS,MhBg3ET,WAAY,KgBx2EV,cAAA,KAGA,gBADA,aAEA,WAAA,KjBi2EH,aAAA,KiB91EC,cAAe,EhBy2Ef,YAAa,IACb,OAAQ,QgBp2ER,+BjBg2ED,sCiBl2EC,yBACA,gCAIA,SAAU,ShBw2EV,WAAY,MgBt2EZ,YAAA,MAIF,oBAAA,cAEE,WAAA,KAGA,iBADA,cAEA,SAAA,SACA,QAAA,aACA,aAAA,KjB61ED,cAAA,EiB31EC,YAAa,IhBs2Eb,eAAgB,OgBp2EhB,OAAA,QAUA,kCjBo1ED,4BCWC,WAAY,EACZ,YAAa,KgBv1Eb,wCAAA,qCjBm1ED,8BCOD,+BgBh2EI,2BhB+1EJ,4BAME,OAAQ,YDNT,0BiBv1EG,uBAMF,oCAAA,iChB61EA,OAAQ,YDNT,yBiBp1EK,sBAaJ,mCAFF,gCAGE,OAAA,YAGA,qBjBy0ED,WAAA,KiBv0EC,YAAA,IhBk1EA,eAAgB,IgBh1Ed,cAAA,EjB00EH,8BiB5zED,8BCnQE,cAAA,EACA,aAAA,EAEA,UACA,OAAA,KlBkkFD,QAAA,IAAA,KkBhkFC,UAAA,KACE,YAAA,IACA,cAAA,IAGF,gBjB0kFA,OAAQ,KiBxkFN,YAAA,KD2PA,0BAFJ,kBAGI,OAAA,KAEA,6BACA,OAAA,KjBy0EH,QAAA,IAAA,KiB/0EC,UAAW,KAST,YAAA,IACA,cAAA,IAVJ,mChB81EE,OAAQ,KgBh1EN,YAAA,KAGA,6CAjBJ,qCAkBI,OAAA,KAEA,oCACA,OAAA,KjBy0EH,WAAA,KiBr0EC,QAAS,IAAI,KC/Rb,UAAA,KACA,YAAA,IAEA,UACA,OAAA,KlBumFD,QAAA,KAAA,KkBrmFC,UAAA,KACE,YAAA,UACA,cAAA,IAGF,gBjB+mFA,OAAQ,KiB7mFN,YAAA,KDuRA,0BAFJ,kBAGI,OAAA,KAEA,6BACA,OAAA,KjBk1EH,QAAA,KAAA,KiBx1EC,UAAW,KAST,YAAA,UACA,cAAA,IAVJ,mChBu2EE,OAAQ,KgBz1EN,YAAA,KAGA,6CAjBJ,qCAkBI,OAAA,KAEA,oCACA,OAAA,KjBk1EH,WAAA,KiBz0EC,QAAS,KAAK,KAEd,UAAA,KjB00ED,YAAA,UiBt0EG,cjBy0EH,SAAA,SiBp0EC,4BACA,cAAA,OAEA,uBACA,SAAA,SACA,IAAA,EACA,MAAA,EACA,QAAA,EACA,QAAA,MACA,MAAA,KjBu0ED,OAAA,KiBr0EC,YAAa,KhBg1Eb,WAAY,OACZ,eAAgB,KDLjB,oDiBv0EC,uCADA,iCAGA,MAAO,KhBg1EP,OAAQ,KACR,YAAa,KDLd,oDiBv0EC,uCADA,iCAKA,MAAO,KhB80EP,OAAQ,KACR,YAAa,KAKf,uBAEA,8BAJA,4BADA,yBAEA,oBAEA,2BDNC,4BkBruFG,mCAJA,yBD0ZJ,gCbvWE,MAAA,QJ2rFD,2BkBxuFG,aAAA,QACE,mBAAA,MAAA,EAAA,IAAA,IAAA,iBd4CJ,WAAA,MAAA,EAAA,IAAA,IAAA,iBJgsFD,iCiBz1EC,aAAc,QC5YZ,mBAAA,MAAA,EAAA,IAAA,IAAA,iBAAA,EAAA,EAAA,IAAA,QACA,WAAA,MAAA,EAAA,IAAA,IAAA,iBAAA,EAAA,EAAA,IAAA,QlByuFH,gCiB91EC,MAAO,QCtYL,iBAAA,QlBuuFH,aAAA,QCWD,oCACE,MAAO,QAKT,uBAEA,8BAJA,4BADA,yBAEA,oBAEA,2BDNC,4BkBnwFG,mCAJA,yBD6ZJ,gCb1WE,MAAA,QJytFD,2BkBtwFG,aAAA,QACE,mBAAA,MAAA,EAAA,IAAA,IAAA,iBd4CJ,WAAA,MAAA,EAAA,IAAA,IAAA,iBJ8tFD,iCiBp3EC,aAAc,QC/YZ,mBAAA,MAAA,EAAA,IAAA,IAAA,iBAAA,EAAA,EAAA,IAAA,QACA,WAAA,MAAA,EAAA,IAAA,IAAA,iBAAA,EAAA,EAAA,IAAA,QlBuwFH,gCiBz3EC,MAAO,QCzYL,iBAAA,QlBqwFH,aAAA,QCWD,oCACE,MAAO,QAKT,qBAEA,4BAJA,0BADA,uBAEA,kBAEA,yBDNC,0BkBjyFG,iCAJA,uBDgaJ,8Bb7WE,MAAA,QJuvFD,yBkBpyFG,aAAA,QACE,mBAAA,MAAA,EAAA,IAAA,IAAA,iBd4CJ,WAAA,MAAA,EAAA,IAAA,IAAA,iBJ4vFD,+BiB/4EC,aAAc,QClZZ,mBAAA,MAAA,EAAA,IAAA,IAAA,iBAAA,EAAA,EAAA,IAAA,QACA,WAAA,MAAA,EAAA,IAAA,IAAA,iBAAA,EAAA,EAAA,IAAA,QlBqyFH,8BiBp5EC,MAAO,QC5YL,iBAAA,QlBmyFH,aAAA,QiB/4EG,kCjBk5EH,MAAA,QiB/4EG,2CjBk5EH,IAAA,KiBv4EC,mDACA,IAAA,EAEA,YjB04ED,QAAA,MiBvzEC,WAAY,IAwEZ,cAAe,KAtIX,MAAA,QAEA,yBjBy3EH,yBiBrvEC,QAAS,aA/HP,cAAA,EACA,eAAA,OjBw3EH,2BiB1vEC,QAAS,aAxHP,MAAA,KjBq3EH,eAAA,OiBj3EG,kCACA,QAAA,aAmHJ,0BhB4wEE,QAAS,aACT,eAAgB,OgBr3Ed,wCjB82EH,6CiBtwED,2CjBywEC,MAAA,KiB72EG,wCACA,MAAA,KAmGJ,4BhBwxEE,cAAe,EgBp3Eb,eAAA,OAGA,uBADA,oBjB82EH,QAAA,aiBpxEC,WAAY,EhB+xEZ,cAAe,EgBr3EX,eAAA,OAsFN,6BAAA,0BAjFI,aAAA,EAiFJ,4CjB6xEC,sCiBx2EG,SAAA,SjB22EH,YAAA,EiBh2ED,kDhB42EE,IAAK,GgBl2EL,2BjB+1EH,kCiBh2EG,wBAEA,+BAXF,YAAa,IhBo3Eb,WAAY,EgBn2EV,cAAA,EJviBF,2BIshBF,wBJrhBE,WAAA,KI4jBA,6BAyBA,aAAc,MAnCV,YAAA,MAEA,yBjBw1EH,gCACF,YAAA,IiBx3EG,cAAe,EAwCf,WAAA,OAwBJ,sDAdQ,MAAA,KjB80EL,yBACF,+CiBn0EC,YAAA,KAEE,UAAW,MjBs0EZ,yBACF,+CmBp6FG,YAAa,IACf,UAAA,MAGA,KACA,QAAA,aACA,QAAA,IAAA,KAAA,cAAA,EACA,UAAA,KACA,YAAA,IACA,YAAA,WACA,WAAA,OC0CA,YAAA,OACA,eAAA,OACA,iBAAA,aACA,aAAA,ahB+JA,OAAA,QACG,oBAAA,KACC,iBAAA,KACI,gBAAA,KJ+tFT,YAAA,KmBv6FG,iBAAA,KlBm7FF,OAAQ,IAAI,MAAM,YAClB,cAAe,IkB96Ff,kBdzBA,kBACA,WLk8FD,kBCOD,kBADA,WAME,QAAS,IAAI,KAAK,yBAClB,eAAgB,KkBh7FhB,WnBy6FD,WmB56FG,WlBw7FF,MAAO,KkBn7FL,gBAAA,Kf6BM,YADR,YJk5FD,iBAAA,KmBz6FC,QAAA,ElBq7FA,mBAAoB,MAAM,EAAE,IAAI,IAAI,iBAC5B,WAAY,MAAM,EAAE,IAAI,IAAI,iBoBh+FpC,cAGA,ejB8DA,wBACQ,OAAA,YJ05FT,OAAA,kBmBz6FG,mBAAA,KlBq7FM,WAAY,KkBn7FhB,QAAA,IASN,eC3DE,yBACA,eAAA,KpBi+FD,aoB99FC,MAAA,KnB0+FA,iBAAkB,KmBx+FhB,aAAA,KpBk+FH,mBoBh+FO,mBAEN,MAAA,KACE,iBAAA,QACA,aAAA,QpBi+FH,mBoB99FC,MAAA,KnB0+FA,iBAAkB,QAClB,aAAc,QmBt+FR,oBADJ,oBpBi+FH,mCoB99FG,MAAA,KnB0+FF,iBAAkB,QAClB,aAAc,QmBt+FN,0BnB4+FV,0BAHA,0BmB1+FM,0BnB4+FN,0BAHA,0BDFC,yCoBx+FK,yCnB4+FN,yCmBv+FE,MAAA,KnB++FA,iBAAkB,QAClB,aAAc,QmBx+FZ,oBpBg+FH,oBoBh+FG,mCnB6+FF,iBAAkB,KmBz+FV,4BnB8+FV,4BAHA,4BDHC,6BCOD,6BAHA,6BkB39FA,sCClBM,sCnB8+FN,sCmBx+FI,iBAAA,KACA,aAAA,KDcJ,oBC9DE,MAAA,KACA,iBAAA,KpB0hGD,aoBvhGC,MAAA,KnBmiGA,iBAAkB,QmBjiGhB,aAAA,QpB2hGH,mBoBzhGO,mBAEN,MAAA,KACE,iBAAA,QACA,aAAA,QpB0hGH,mBoBvhGC,MAAA,KnBmiGA,iBAAkB,QAClB,aAAc,QmB/hGR,oBADJ,oBpB0hGH,mCoBvhGG,MAAA,KnBmiGF,iBAAkB,QAClB,aAAc,QmB/hGN,0BnBqiGV,0BAHA,0BmBniGM,0BnBqiGN,0BAHA,0BDFC,yCoBjiGK,yCnBqiGN,yCmBhiGE,MAAA,KnBwiGA,iBAAkB,QAClB,aAAc,QmBjiGZ,oBpByhGH,oBoBzhGG,mCnBsiGF,iBAAkB,KmBliGV,4BnBuiGV,4BAHA,4BDHC,6BCOD,6BAHA,6BkBjhGA,sCCrBM,sCnBuiGN,sCmBjiGI,iBAAA,QACA,aAAA,QDkBJ,oBClEE,MAAA,QACA,iBAAA,KpBmlGD,aoBhlGC,MAAA,KnB4lGA,iBAAkB,QmB1lGhB,aAAA,QpBolGH,mBoBllGO,mBAEN,MAAA,KACE,iBAAA,QACA,aAAA,QpBmlGH,mBoBhlGC,MAAA,KnB4lGA,iBAAkB,QAClB,aAAc,QmBxlGR,oBADJ,oBpBmlGH,mCoBhlGG,MAAA,KnB4lGF,iBAAkB,QAClB,aAAc,QmBxlGN,0BnB8lGV,0BAHA,0BmB5lGM,0BnB8lGN,0BAHA,0BDFC,yCoB1lGK,yCnB8lGN,yCmBzlGE,MAAA,KnBimGA,iBAAkB,QAClB,aAAc,QmB1lGZ,oBpBklGH,oBoBllGG,mCnB+lGF,iBAAkB,KmB3lGV,4BnBgmGV,4BAHA,4BDHC,6BCOD,6BAHA,6BkBtkGA,sCCzBM,sCnBgmGN,sCmB1lGI,iBAAA,QACA,aAAA,QDsBJ,oBCtEE,MAAA,QACA,iBAAA,KpB4oGD,UoBzoGC,MAAA,KnBqpGA,iBAAkB,QmBnpGhB,aAAA,QpB6oGH,gBoB3oGO,gBAEN,MAAA,KACE,iBAAA,QACA,aAAA,QpB4oGH,gBoBzoGC,MAAA,KnBqpGA,iBAAkB,QAClB,aAAc,QmBjpGR,iBADJ,iBpB4oGH,gCoBzoGG,MAAA,KnBqpGF,iBAAkB,QAClB,aAAc,QmBjpGN,uBnBupGV,uBAHA,uBmBrpGM,uBnBupGN,uBAHA,uBDFC,sCoBnpGK,sCnBupGN,sCmBlpGE,MAAA,KnB0pGA,iBAAkB,QAClB,aAAc,QmBnpGZ,iBpB2oGH,iBoB3oGG,gCnBwpGF,iBAAkB,KmBppGV,yBnBypGV,yBAHA,yBDHC,0BCOD,0BAHA,0BkB3nGA,mCC7BM,mCnBypGN,mCmBnpGI,iBAAA,QACA,aAAA,QD0BJ,iBC1EE,MAAA,QACA,iBAAA,KpBqsGD,aoBlsGC,MAAA,KnB8sGA,iBAAkB,QmB5sGhB,aAAA,QpBssGH,mBoBpsGO,mBAEN,MAAA,KACE,iBAAA,QACA,aAAA,QpBqsGH,mBoBlsGC,MAAA,KnB8sGA,iBAAkB,QAClB,aAAc,QmB1sGR,oBADJ,oBpBqsGH,mCoBlsGG,MAAA,KnB8sGF,iBAAkB,QAClB,aAAc,QmB1sGN,0BnBgtGV,0BAHA,0BmB9sGM,0BnBgtGN,0BAHA,0BDFC,yCoB5sGK,yCnBgtGN,yCmB3sGE,MAAA,KnBmtGA,iBAAkB,QAClB,aAAc,QmB5sGZ,oBpBosGH,oBoBpsGG,mCnBitGF,iBAAkB,KmB7sGV,4BnBktGV,4BAHA,4BDHC,6BCOD,6BAHA,6BkBhrGA,sCCjCM,sCnBktGN,sCmB5sGI,iBAAA,QACA,aAAA,QD8BJ,oBC9EE,MAAA,QACA,iBAAA,KpB8vGD,YoB3vGC,MAAA,KnBuwGA,iBAAkB,QmBrwGhB,aAAA,QpB+vGH,kBoB7vGO,kBAEN,MAAA,KACE,iBAAA,QACA,aAAA,QpB8vGH,kBoB3vGC,MAAA,KnBuwGA,iBAAkB,QAClB,aAAc,QmBnwGR,mBADJ,mBpB8vGH,kCoB3vGG,MAAA,KnBuwGF,iBAAkB,QAClB,aAAc,QmBnwGN,yBnBywGV,yBAHA,yBmBvwGM,yBnBywGN,yBAHA,yBDFC,wCoBrwGK,wCnBywGN,wCmBpwGE,MAAA,KnB4wGA,iBAAkB,QAClB,aAAc,QmBrwGZ,mBpB6vGH,mBoB7vGG,kCnB0wGF,iBAAkB,KmBtwGV,2BnB2wGV,2BAHA,2BDHC,4BCOD,4BAHA,4BkBruGA,qCCrCM,qCnB2wGN,qCmBrwGI,iBAAA,QACA,aAAA,QDuCJ,mBACE,MAAA,QACA,iBAAA,KnB+tGD,UmB5tGC,YAAA,IlBwuGA,MAAO,QACP,cAAe,EAEjB,UGzwGE,iBemCE,iBflCM,oBJkwGT,6BmB7tGC,iBAAA,YlByuGA,mBAAoB,KACZ,WAAY,KkBtuGlB,UAEF,iBAAA,gBnB6tGD,gBmB3tGG,aAAA,YnBiuGH,gBmB/tGG,gBAIA,MAAA,QlBuuGF,gBAAiB,UACjB,iBAAkB,YDNnB,0BmBhuGK,0BAUN,mCATM,mClB2uGJ,MAAO,KmB1yGP,gBAAA,KAGA,mBADA,QpBmyGD,QAAA,KAAA,KmBztGC,UAAW,KlBquGX,YAAa,UmBjzGb,cAAA,IAGA,mBADA,QpB0yGD,QAAA,IAAA,KmB5tGC,UAAW,KlBwuGX,YAAa,ImBxzGb,cAAA,IAGA,mBADA,QpBizGD,QAAA,IAAA,ImB3tGC,UAAW,KACX,YAAA,IACA,cAAA,IAIF,WACE,QAAA,MnB2tGD,MAAA,KCYD,sBACE,WAAY,IqBz3GZ,6BADF,4BtBk3GC,6BI7rGC,MAAA,KAEQ,MJisGT,QAAA,EsBr3GC,mBAAA,QAAA,KAAA,OACE,cAAA,QAAA,KAAA,OtBu3GH,WAAA,QAAA,KAAA,OsBl3GC,StBq3GD,QAAA,EsBn3Ga,UtBs3Gb,QAAA,KsBr3Ga,atBw3Gb,QAAA,MsBv3Ga,etB03Gb,QAAA,UsBt3GC,kBACA,QAAA,gBlBwKA,YACQ,SAAA,SAAA,OAAA,EAOR,SAAA,OACQ,mCAAA,KAAA,8BAAA,KAGR,2BAAA,KACQ,4BAAA,KAAA,uBAAA,KJ2sGT,oBAAA,KuBr5GC,4BAA6B,OAAQ,WACrC,uBAAA,OAAA,WACA,oBAAA,OAAA,WAEA,OACA,QAAA,aACA,MAAA,EACA,OAAA,EACA,YAAA,IACA,eAAA,OvBu5GD,WAAA,IAAA,OuBn5GC,WAAY,IAAI,QtBk6GhB,aAAc,IAAI,MAAM,YsBh6GxB,YAAA,IAAA,MAAA,YAKA,UADF,QvBo5GC,SAAA,SuB94GC,uBACA,QAAA,EAEA,eACA,SAAA,SACA,IAAA,KACA,KAAA,EACA,QAAA,KACA,QAAA,KACA,MAAA,KACA,UAAA,MACA,QAAA,IAAA,EACA,OAAA,IAAA,EAAA,EACA,UAAA,KACA,WAAA,KACA,WAAA,KnBsBA,iBAAA,KACQ,wBAAA,YmBrBR,gBAAA,YtB+5GA,OsB/5GA,IAAA,MAAA,KvBk5GD,OAAA,IAAA,MAAA,gBuB74GC,cAAA,IACE,mBAAA,EAAA,IAAA,KAAA,iBACA,WAAA,EAAA,IAAA,KAAA,iBAzBJ,0BCzBE,MAAA,EACA,KAAA,KAEA,wBxBo8GD,OAAA,IuB96GC,OAAQ,IAAI,EAmCV,SAAA,OACA,iBAAA,QAEA,oBACA,QAAA,MACA,QAAA,IAAA,KACA,MAAA,KvB84GH,YAAA,IuBx4GC,YAAA,WtBw5GA,MAAO,KsBt5GL,YAAA,OvB44GH,0BuB14GG,0BAMF,MAAA,QtBo5GA,gBAAiB,KACjB,iBAAkB,QsBj5GhB,yBAEA,+BADA,+BvBu4GH,MAAA,KuB73GC,gBAAA,KtB64GA,iBAAkB,QAClB,QAAS,EDZV,2BuB33GC,iCAAA,iCAEE,MAAA,KEzGF,iCF2GE,iCAEA,gBAAA,KvB63GH,OAAA,YuBx3GC,iBAAkB,YAGhB,iBAAA,KvBw3GH,OAAA,0DuBn3GG,qBvBs3GH,QAAA,MuB72GC,QACA,QAAA,EAQF,qBACE,MAAA,EACA,KAAA,KAIF,oBACE,MAAA,KACA,KAAA,EAEA,iBACA,QAAA,MACA,QAAA,IAAA,KvBw2GD,UAAA,KuBp2GC,YAAa,WACb,MAAA,KACA,YAAA,OAEA,mBACA,SAAA,MACA,IAAA,EvBs2GD,MAAA,EuBl2GC,OAAQ,EACR,KAAA,EACA,QAAA,IAQF,2BtB42GE,MAAO,EsBx2GL,KAAA,KAEA,eACA,sCvB41GH,QAAA,GuBn2GC,WAAY,EtBm3GZ,cAAe,IAAI,OsBx2GjB,cAAA,IAAA,QAEA,uBvB41GH,8CuBv0GC,IAAK,KAXL,OAAA,KApEA,cAAA,IvB25GC,yBuBv1GD,6BA1DA,MAAA,EACA,KAAA,KvBq5GD,kC0BpiHG,MAAO,KzBojHP,KAAM,GyBhjHR,W1BsiHD,oB0B1iHC,SAAU,SzB0jHV,QAAS,ayBpjHP,eAAA,OAGA,yB1BsiHH,gBCgBC,SAAU,SACV,MAAO,KyB7iHT,gC1BsiHC,gCCYD,+BAFA,+ByBhjHA,uBANM,uBzBujHN,sBAFA,sBAQE,QAAS,EyBljHP,qB1BuiHH,2B0BliHD,2BACE,iC1BoiHD,YAAA,KCgBD,aACE,YAAa,KDZd,kB0B1iHD,wBAAA,0BzB2jHE,MAAO,KDZR,kB0B/hHD,wBACE,0B1BiiHD,YAAA,I0B5hHC,yE1B+hHD,cAAA,E2BhlHC,4BACG,YAAA,EDsDL,mEzB6iHE,wBAAyB,E0B5lHzB,2BAAA,E3BilHD,6C0B5hHD,8CACE,uBAAA,E1B8hHD,0BAAA,E0B3hHC,sB1B8hHD,MAAA,KCgBD,8D0B/mHE,cAAA,E3BomHD,mE0B3hHD,oECjEE,wBAAA,EACG,2BAAA,EDqEL,oEzB0iHE,uBAAwB,EyBxiHxB,0BAAA,EAiBF,mCACE,iCACA,QAAA,EAEF,iCACE,cAAA,IACA,aAAA,IAKF,oCtB/CE,cAAA,KACQ,aAAA,KsBkDR,iCtBnDA,mBAAA,MAAA,EAAA,IAAA,IAAA,iBACQ,WAAA,MAAA,EAAA,IAAA,IAAA,iBsByDV,0CACE,mBAAA,K1BugHD,WAAA,K0BngHC,YACA,YAAA,EAGF,eACE,aAAA,IAAA,IAAA,E1BqgHD,oBAAA,ECgBD,uBACE,aAAc,EAAE,IAAI,IyB1gHlB,yBACA,+BACA,oC1B+/GH,QAAA,M0BtgHC,MAAO,KAcH,MAAA,K1B2/GL,UAAA,KCgBD,oCACE,MAAO,KyBpgHL,8BACA,oC1By/GH,oC0Bp/GC,0CACE,WAAA,K1Bs/GH,YAAA,E2B/pHC,4DACC,cAAA,EAQA,sD3B4pHF,uBAAA,I0Bt/GC,wBAAA,IC/KA,2BAAA,EACC,0BAAA,EAQA,sD3BkqHF,uBAAA,E0Bv/GC,wBAAyB,EACzB,2BAAA,I1By/GD,0BAAA,ICgBD,uE0BtrHE,cAAA,E3B2qHD,4E0Bt/GD,6EC7LE,2BAAA,EACC,0BAAA,EDoMH,6EACE,uBAAA,EACA,wBAAA,EAEA,qB1Bo/GD,QAAA,M0Bx/GC,MAAO,KzBwgHP,aAAc,MyBjgHZ,gBAAA,SAEA,0B1Bq/GH,gC0B9/GC,QAAS,WAYP,MAAA,K1Bq/GH,MAAA,G0Bj/GG,qC1Bo/GH,MAAA,KCgBD,+CACE,KAAM,KyB7+GF,gDAFA,6C1Bs+GL,2D0Br+GK,wDEzOJ,SAAU,SACV,KAAA,cACA,eAAA,K5BitHD,a4B7sHC,SAAA,SACE,QAAA,MACA,gBAAA,S5BgtHH,0B4BxtHC,MAAO,KAeL,cAAA,EACA,aAAA,EAOA,2BACA,SAAA,S5BusHH,QAAA,E4BrsHG,MAAA,KACE,MAAA,K5BusHL,cAAA,ECgBD,iCACE,QAAS,EiBnrHT,8BACA,mCACA,sCACA,OAAA,KlBwqHD,QAAA,KAAA,KkBtqHC,UAAA,KjBsrHA,YAAa,UACb,cAAe,IiBrrHb,oClB0qHH,yCkBvqHC,4CjBurHA,OAAQ,KACR,YAAa,KDTd,8C4B/sHD,mDAAA,sD3B0tHA,sCACA,2CiBzrHI,8CjB8rHF,OAAQ,KiB1sHR,8BACA,mCACA,sCACA,OAAA,KlB+rHD,QAAA,IAAA,KkB7rHC,UAAA,KjB6sHA,YAAa,IACb,cAAe,IiB5sHb,oClBisHH,yCkB9rHC,4CjB8sHA,OAAQ,KACR,YAAa,KDTd,8C4B7tHD,mDAAA,sD3BwuHA,sCACA,2CiBhtHI,8CjBqtHF,OAAQ,K2BzuHR,2B5B6tHD,mB4B7tHC,iB3B8uHA,QAAS,W2BzuHX,8D5B6tHC,sD4B7tHD,oDAEE,cAAA,EAEA,mB5B+tHD,iB4B1tHC,MAAO,GACP,YAAA,OACA,eAAA,OAEA,mBACA,QAAA,IAAA,KACA,UAAA,KACA,YAAA,IACA,YAAA,EACA,MAAA,K5B4tHD,WAAA,O4BztHC,iBAAA,KACE,OAAA,IAAA,MAAA,KACA,cAAA,I5B4tHH,4B4BztHC,QAAA,IAAA,KACE,UAAA,KACA,cAAA,I5B4tHH,4B4B/uHC,QAAS,KAAK,K3B+vHd,UAAW,K2BruHT,cAAA,IAKJ,wCAAA,qC3BquHE,WAAY,EAEd,uCACA,+BACA,kC0B70HE,6CACG,8CC4GL,6D5BqtHC,wE4BptHC,wBAAA,E5ButHD,2BAAA,ECgBD,+BACE,aAAc,EAEhB,sCACA,8B2BhuHA,+D5BstHC,oDCWD,iC0Bl1HE,4CACG,6CCiHH,uBAAA,E5BwtHD,0BAAA,E4BltHC,8BAGA,YAAA,E5BotHD,iB4BxtHC,SAAU,SAUR,UAAA,E5BitHH,YAAA,O4B/sHK,sB5BktHL,SAAA,SCgBD,2BACE,YAAa,K2BxtHb,6BAAA,4B5B4sHD,4B4BzsHK,QAAA,EAGJ,kCAAA,wCAGI,aAAA,K5B4sHL,iC6B12HD,uCACE,QAAA,EACA,YAAA,K7B62HD,K6B/2HC,aAAc,EAOZ,cAAA,EACA,WAAA,KARJ,QAWM,SAAA,SACA,QAAA,M7B42HL,U6B12HK,SAAA,S5B03HJ,QAAS,M4Bx3HH,QAAA,KAAA,KAMJ,gB7Bu2HH,gB6Bt2HK,gBAAA,K7By2HL,iBAAA,KCgBD,mB4Br3HQ,MAAA,KAGA,yBADA,yB7B02HP,MAAA,K6Bl2HG,gBAAA,K5Bk3HF,OAAQ,YACR,iBAAkB,Y4B/2Hd,aAzCN,mB7B64HC,mBwBh5HC,iBAAA,KACA,aAAA,QAEA,kBxBm5HD,OAAA,I6Bn5HC,OAAQ,IAAI,EA0DV,SAAA,O7B41HH,iBAAA,Q6Bl1HC,c7Bq1HD,UAAA,K6Bn1HG,UAEA,cAAA,IAAA,MAAA,KALJ,aASM,MAAA,KACA,cAAA,KAEA,e7Bo1HL,aAAA,I6Bn1HK,YAAA,WACE,OAAA,IAAA,MAAA,Y7Bq1HP,cAAA,IAAA,IAAA,EAAA,ECgBD,qBACE,aAAc,KAAK,KAAK,K4B51HlB,sBAEA,4BADA,4BAEA,MAAA,K7Bi1HP,OAAA,Q6B50HC,iBAAA,KAqDA,OAAA,IAAA,MAAA,KA8BA,oBAAA,YAnFA,wBAwDE,MAAA,K7B2xHH,cAAA,E6BzxHK,2BACA,MAAA,KA3DJ,6BAgEE,cAAA,IACA,WAAA,OAYJ,iDA0DE,IAAK,KAjED,KAAA,K7B0xHH,yB6BztHD,2BA9DM,QAAA,W7B0xHL,MAAA,G6Bn2HD,6BAuFE,cAAA,GAvFF,6B5Bw3HA,aAAc,EACd,cAAe,IDZhB,kC6BtuHD,wCA3BA,wCATM,OAAA,IAAA,MAAA,K7B+wHH,yB6B3uHD,6B5B2vHE,cAAe,IAAI,MAAM,KACzB,cAAe,IAAI,IAAI,EAAE,EDZ1B,kC6B92HD,wC7B+2HD,wC6B72HG,oBAAA,MAIE,c7B+2HL,MAAA,K6B52HK,gB7B+2HL,cAAA,ICgBD,iBACE,YAAa,I4Bv3HP,uBAQR,6B7Bo2HC,6B6Bl2HG,MAAA,K7Bq2HH,iBAAA,Q6Bn2HK,gBACA,MAAA,KAYN,mBACE,WAAA,I7B41HD,YAAA,E6Bz1HG,e7B41HH,MAAA,K6B11HK,kBACA,MAAA,KAPN,oBAYI,cAAA,IACA,WAAA,OAYJ,wCA0DE,IAAK,KAjED,KAAA,K7B21HH,yB6B1xHD,kBA9DM,QAAA,W7B21HL,MAAA,G6Bl1HD,oBACA,cAAA,GAIE,oBACA,cAAA,EANJ,yB5B02HE,aAAc,EACd,cAAe,IDZhB,8B6B1yHD,oCA3BA,oCATM,OAAA,IAAA,MAAA,K7Bm1HH,yB6B/yHD,yB5B+zHE,cAAe,IAAI,MAAM,KACzB,cAAe,IAAI,IAAI,EAAE,EDZ1B,8B6Bx0HD,oC7By0HD,oC6Bv0HG,oBAAA,MAGA,uB7B00HH,QAAA,K6B/zHC,qBF3OA,QAAA,M3B+iID,yB8BxiIC,WAAY,KACZ,uBAAA,EACA,wBAAA,EAEA,Q9B0iID,SAAA,S8BliIC,WAAY,KA8nBZ,cAAe,KAhoBb,OAAA,IAAA,MAAA,Y9ByiIH,yB8BzhIC,QAgnBE,cAAe,K9B86GlB,yB8BjhIC,eACA,MAAA,MAGA,iBACA,cAAA,KAAA,aAAA,KAEA,WAAA,Q9BkhID,2BAAA,M8BhhIC,WAAA,IAAA,MAAA,YACE,mBAAA,MAAA,EAAA,IAAA,EAAA,qB9BkhIH,WAAA,MAAA,EAAA,IAAA,EAAA,qB8Bz7GD,oBArlBI,WAAA,KAEA,yBAAA,iB9BkhID,MAAA,K8BhhIC,WAAA,EACE,mBAAA,KACA,WAAA,KAEA,0B9BkhIH,QAAA,gB8B/gIC,OAAA,eACE,eAAA,E9BihIH,SAAA,kBCkBD,oBACE,WAAY,QDZf,sC8B/gIK,mC9B8gIH,oC8BzgIC,cAAe,E7B4hIf,aAAc,G6Bj+GlB,sCAnjBE,mC7ByhIA,WAAY,MDdX,4D8BngID,sC9BogID,mCCkBG,WAAY,O6B3gId,kCANE,gC9BsgIH,4B8BvgIG,0BAuiBF,aAAc,M7Bm/Gd,YAAa,MAEf,yBDZC,kC8B3gIK,gC9B0gIH,4B8B3gIG,0BAcF,aAAc,EAChB,YAAA,GAMF,mBA8gBE,QAAS,KAhhBP,aAAA,EAAA,EAAA,I9BkgIH,yB8B7/HC,mB7B+gIE,cAAe,G6B1gIjB,qBADA,kB9BggID,SAAA,M8Bz/HC,MAAO,EAggBP,KAAM,E7B4gHN,QAAS,KDdR,yB8B7/HD,qB9B8/HD,kB8B7/HC,cAAA,GAGF,kBACE,IAAA,EACA,aAAA,EAAA,EAAA,I9BigID,qB8B1/HC,OAAQ,EACR,cAAA,EACA,aAAA,IAAA,EAAA,EAEA,cACA,MAAA,K9B4/HD,OAAA,K8B1/HC,QAAA,KAAA,K7B4gIA,UAAW,K6B1gIT,YAAA,KAIA,oBAbJ,oB9BwgIC,gBAAA,K8Bv/HG,kB7B0gIF,QAAS,MDdR,yBACF,iC8Bh/HC,uCACA,YAAA,OAGA,eC9LA,SAAA,SACA,MAAA,MD+LA,QAAA,IAAA,KACA,WAAA,IACA,aAAA,KACA,cAAA,I9Bm/HD,iBAAA,Y8B/+HC,iBAAA,KACE,OAAA,IAAA,MAAA,Y9Bi/HH,cAAA,I8B5+HG,qBACA,QAAA,EAEA,yB9B++HH,QAAA,M8BrgIC,MAAO,KAyBL,OAAA,I9B++HH,cAAA,I8BpjHD,mCAvbI,WAAA,I9Bg/HH,yB8Bt+HC,eACA,QAAA,MAGE,YACA,OAAA,MAAA,M9By+HH,iB8B58HC,YAAA,KA2YA,eAAgB,KAjaZ,YAAA,KAEA,yBACA,iCACA,SAAA,OACA,MAAA,KACA,MAAA,KAAA,WAAA,E9Bs+HH,iBAAA,Y8B3kHC,OAAQ,E7B8lHR,mBAAoB,K6Bt/HhB,WAAA,KAGA,kDAqZN,sC9BklHC,QAAA,IAAA,KAAA,IAAA,KCmBD,sC6Bv/HQ,YAAA,KAmBR,4C9Bs9HD,4C8BvlHG,iBAAkB,M9B4lHnB,yB8B5lHD,YAtYI,MAAA,K9Bq+HH,OAAA,E8Bn+HK,eACA,MAAA,K9Bu+HP,iB8B39HG,YAAa,KACf,eAAA,MAGA,aACA,QAAA,KAAA,K1B9NA,WAAA,IACQ,aAAA,M2B/DR,cAAA,IACA,YAAA,M/B4vID,WAAA,IAAA,MAAA,YiBtuHC,cAAe,IAAI,MAAM,YAwEzB,mBAAoB,MAAM,EAAE,IAAI,EAAE,qBAAyB,EAAE,IAAI,EAAE,qBAtI/D,WAAA,MAAA,EAAA,IAAA,EAAA,qBAAA,EAAA,IAAA,EAAA,qBAEA,yBjBwyHH,yBiBpqHC,QAAS,aA/HP,cAAA,EACA,eAAA,OjBuyHH,2BiBzqHC,QAAS,aAxHP,MAAA,KjBoyHH,eAAA,OiBhyHG,kCACA,QAAA,aAmHJ,0BhBmsHE,QAAS,aACT,eAAgB,OgB5yHd,wCjB6xHH,6CiBrrHD,2CjBwrHC,MAAA,KiB5xHG,wCACA,MAAA,KAmGJ,4BhB+sHE,cAAe,EgB3yHb,eAAA,OAGA,uBADA,oBjB6xHH,QAAA,aiBnsHC,WAAY,EhBstHZ,cAAe,EgB5yHX,eAAA,OAsFN,6BAAA,0BAjFI,aAAA,EAiFJ,4CjB4sHC,sCiBvxHG,SAAA,SjB0xHH,YAAA,E8BngID,kDAmWE,IAAK,GAvWH,yBACE,yB9B8gIL,cAAA,I8B5/HD,oCAoVE,cAAe,GA1Vf,yBACA,aACA,MAAA,KACA,YAAA,E1BzPF,eAAA,EACQ,aAAA,EJmwIP,YAAA,EACF,OAAA,E8BngIG,mBAAoB,KACtB,WAAA,M9BugID,8B8BngIC,WAAY,EACZ,uBAAA,EHzUA,wBAAA,EAQA,mDACC,cAAA,E3By0IF,uBAAA,I8B//HC,wBAAyB,IChVzB,2BAAA,EACA,0BAAA,EDkVA,YCnVA,WAAA,IACA,cAAA,IDqVA,mBCtVA,WAAA,KACA,cAAA,KD+VF,mBChWE,WAAA,KACA,cAAA,KDuWF,aAsSE,WAAY,KA1SV,cAAA,KAEA,yB9B+/HD,aACF,MAAA,K8Bl+HG,aAAc,KAhBhB,YAAA,MACA,yBE5WA,aF8WE,MAAA,eAFF,cAKI,MAAA,gB9Bu/HH,aAAA,M8B7+HD,4BACA,aAAA,GADF,gBAKI,iBAAA,Q9Bg/HH,aAAA,QCmBD,8B6BhgIM,MAAA,KARN,oC9B0/HC,oC8B5+HG,MAAA,Q9B++HH,iBAAA,Y8B1+HK,6B9B6+HL,MAAA,KCmBD,iC6B5/HQ,MAAA,KAKF,uC9By+HL,uCCmBC,MAAO,KACP,iBAAkB,Y6Bz/HZ,sCAIF,4C9Bu+HL,4CCmBC,MAAO,KACP,iBAAkB,Q6Bv/HZ,wCAxCR,8C9BihIC,8C8Bn+HG,MAAA,K9Bs+HH,iBAAA,YCmBD,+B6Bt/HM,aAAA,KAGA,qCApDN,qC9B2hIC,iBAAA,KCmBD,yC6Bp/HI,iBAAA,KAOE,iCAAA,6B7Bk/HJ,aAAc,Q6B9+HR,oCAiCN,0C9B+7HD,0C8B3xHC,MAAO,KA7LC,iBAAA,QACA,yB7B8+HR,sD6B5+HU,MAAA,KAKF,4D9By9HP,4DCmBC,MAAO,KACP,iBAAkB,Y6Bz+HV,2DAIF,iE9Bu9HP,iECmBC,MAAO,KACP,iBAAkB,Q6Bv+HV,6D9B09HX,mEADE,mE8B1jIC,MAAO,KA8GP,iBAAA,aAEE,6B9Bi9HL,MAAA,K8B58HG,mC9B+8HH,MAAA,KCmBD,0B6B/9HM,MAAA,KAIA,gCAAA,gC7Bg+HJ,MAAO,K6Bt9HT,0CARQ,0CASN,mD9Bu8HD,mD8Bt8HC,MAAA,KAFF,gBAKI,iBAAA,K9B08HH,aAAA,QCmBD,8B6B19HM,MAAA,QARN,oC9Bo9HC,oC8Bt8HG,MAAA,K9By8HH,iBAAA,Y8Bp8HK,6B9Bu8HL,MAAA,QCmBD,iC6Bt9HQ,MAAA,QAKF,uC9Bm8HL,uCCmBC,MAAO,KACP,iBAAkB,Y6Bn9HZ,sCAIF,4C9Bi8HL,4CCmBC,MAAO,KACP,iBAAkB,Q6Bj9HZ,wCAxCR,8C9B2+HC,8C8B57HG,MAAA,K9B+7HH,iBAAA,YCmBD,+B6B/8HM,aAAA,KAGA,qCArDN,qC9Bq/HC,iBAAA,KCmBD,yC6B78HI,iBAAA,KAME,iCAAA,6B7B48HJ,aAAc,Q6Bx8HR,oCAuCN,0C9Bm5HD,0C8B33HC,MAAO,KAvDC,iBAAA,QAuDV,yBApDU,kE9Bs7HP,aAAA,Q8Bn7HO,0D9Bs7HP,iBAAA,QCmBD,sD6Bt8HU,MAAA,QAKF,4D9Bm7HP,4DCmBC,MAAO,KACP,iBAAkB,Y6Bn8HV,2DAIF,iE9Bi7HP,iECmBC,MAAO,KACP,iBAAkB,Q6Bj8HV,6D9Bo7HX,mEADE,mE8B1hIC,MAAO,KA+GP,iBAAA,aAEE,6B9Bg7HL,MAAA,Q8B36HG,mC9B86HH,MAAA,KCmBD,0B6B97HM,MAAA,QAIA,gCAAA,gC7B+7HJ,MAAO,KgCvkJT,0CH0oBQ,0CGzoBN,mDjCwjJD,mDiCvjJC,MAAA,KAEA,YACA,QAAA,IAAA,KjC2jJD,cAAA,KiChkJC,WAAY,KAQV,iBAAA,QjC2jJH,cAAA,IiCxjJK,eACA,QAAA,ajC4jJL,yBiCxkJC,QAAS,EAAE,IAkBT,MAAA,KjCyjJH,QAAA,SkC5kJC,oBACA,MAAA,KAEA,YlC+kJD,QAAA,akCnlJC,aAAc,EAOZ,OAAA,KAAA,ElC+kJH,cAAA,ICmBD,eiC/lJM,QAAA,OAEA,iBACA,oBACA,SAAA,SACA,MAAA,KACA,QAAA,IAAA,KACA,YAAA,KACA,YAAA,WlCglJL,MAAA,QkC9kJG,gBAAA,KjCimJF,iBAAkB,KiC9lJZ,OAAA,IAAA,MAAA,KPVH,6B3B2lJJ,gCkC7kJG,YAAA,EjCgmJF,uBAAwB,I0BvnJxB,0BAAA,I3BymJD,4BkCxkJG,+BjC2lJF,wBAAyB,IACzB,2BAA4B,IiCxlJxB,uBAFA,uBAGA,0BAFA,0BlC8kJL,QAAA,EkCtkJG,MAAA,QjCylJF,iBAAkB,KAClB,aAAc,KAEhB,sBiCvlJM,4BAFA,4BjC0lJN,yBiCvlJM,+BAFA,+BAGA,QAAA,ElC2kJL,MAAA,KkCloJC,OAAQ,QjCqpJR,iBAAkB,QAClB,aAAc,QiCnlJV,wBAEA,8BADA,8BjColJN,2BiCtlJM,iCjCulJN,iCDZC,MAAA,KkC/jJC,OAAQ,YjCklJR,iBAAkB,KkC7pJd,aAAA,KAEA,oBnC8oJL,uBmC5oJG,QAAA,KAAA,KlC+pJF,UAAW,K0B1pJX,YAAA,U3B4oJD,gCmC3oJG,mClC8pJF,uBAAwB,I0BvqJxB,0BAAA,I3BypJD,+BkC1kJD,kCjC6lJE,wBAAyB,IkC7qJrB,2BAAA,IAEA,oBnC8pJL,uBmC5pJG,QAAA,IAAA,KlC+qJF,UAAW,K0B1qJX,YAAA,I3B4pJD,gCmC3pJG,mClC8qJF,uBAAwB,I0BvrJxB,0BAAA,I3ByqJD,+BoC3qJD,kCACE,wBAAA,IACA,2BAAA,IAEA,OpC6qJD,aAAA,EoCjrJC,OAAQ,KAAK,EAOX,WAAA,OpC6qJH,WAAA,KCmBD,UmC7rJM,QAAA,OAEA,YACA,eACA,QAAA,apC8qJL,QAAA,IAAA,KoC5rJC,iBAAkB,KnC+sJlB,OAAQ,IAAI,MAAM,KmC5rJd,cAAA,KAnBN,kBpCisJC,kBCmBC,gBAAiB,KmCzrJb,iBAAA,KA3BN,eAAA,kBAkCM,MAAA,MAlCN,mBAAA,sBnC6tJE,MAAO,KmClrJH,mBAEA,yBADA,yBpCqqJL,sBqCltJC,MAAO,KACP,OAAA,YACA,iBAAA,KAEA,OACA,QAAA,OACA,QAAA,KAAA,KAAA,KACA,UAAA,IACA,YAAA,IACA,YAAA,EACA,MAAA,KrCotJD,WAAA,OqChtJG,YAAA,OpCmuJF,eAAgB,SoCjuJZ,cAAA,MrCotJL,cqCltJK,cAKJ,MAAA,KACE,gBAAA,KrC+sJH,OAAA,QqC1sJG,aACA,QAAA,KAOJ,YCtCE,SAAA,StC+uJD,IAAA,KCmBD,eqC7vJM,iBAAA,KALJ,2BD0CF,2BrC4sJC,iBAAA,QCmBD,eqCpwJM,iBAAA,QALJ,2BD8CF,2BrC+sJC,iBAAA,QCmBD,eqC3wJM,iBAAA,QALJ,2BDkDF,2BrCktJC,iBAAA,QCmBD,YqClxJM,iBAAA,QALJ,wBDsDF,wBrCqtJC,iBAAA,QCmBD,eqCzxJM,iBAAA,QALJ,2BD0DF,2BrCwtJC,iBAAA,QCmBD,cqChyJM,iBAAA,QCDJ,0BADF,0BAEE,iBAAA,QAEA,OACA,QAAA,aACA,UAAA,KACA,QAAA,IAAA,IACA,UAAA,KACA,YAAA,IACA,YAAA,EACA,MAAA,KACA,WAAA,OvCqxJD,YAAA,OuClxJC,eAAA,OACE,iBAAA,KvCoxJH,cAAA,KuC/wJG,aACA,QAAA,KAGF,YtCkyJA,SAAU,SsChyJR,IAAA,KAMA,0BvC4wJH,eCmBC,IAAK,EsC7xJD,QAAA,IAAA,IvCgxJL,cuC9wJK,cAKJ,MAAA,KtC4xJA,gBAAiB,KsC1xJf,OAAA,QvC4wJH,+BuCxwJC,4BACE,MAAA,QvC0wJH,iBAAA,KuCtwJG,wBvCywJH,MAAA,MuCrwJG,+BvCwwJH,aAAA,IwCj0JC,uBACA,YAAA,IAEA,WACA,YAAA,KxCo0JD,eAAA,KwCz0JC,cAAe,KvC41Jf,MAAO,QuCn1JL,iBAAA,KAIA,eAbJ,cAcI,MAAA,QxCo0JH,awCl1JC,cAAe,KAmBb,UAAA,KxCk0JH,YAAA,ICmBD,cuCh1JI,iBAAA,QAEA,sBxCi0JH,4BwC31JC,cAAe,KA8Bb,aAAA,KxCg0JH,cAAA,IwC7yJD,sBAfI,UAAA,KxCi0JD,oCwC9zJC,WvCi1JA,YAAa,KuC/0JX,eAAA,KxCi0JH,sBwCvzJD,4BvC00JE,cAAe,KuC90Jb,aAAA,KC5CJ,ezC42JD,cyC32JC,UAAA,MAGA,WACA,QAAA,MACA,QAAA,IACA,cAAA,KrCiLA,YAAA,WACK,iBAAA,KACG,OAAA,IAAA,MAAA,KJ8rJT,cAAA,IyCx3JC,mBAAoB,OAAO,IAAI,YxC24J1B,cAAe,OAAO,IAAI,YwC93J7B,WAAA,OAAA,IAAA,YAKF,iBzC22JD,eCmBC,aAAc,KACd,YAAa,KwCv3JX,mBA1BJ,kBzCk4JC,kByCv2JG,aAAA,QCzBJ,oBACE,QAAA,IACA,MAAA,KAEA,O1Cs4JD,QAAA,K0C14JC,cAAe,KAQb,OAAA,IAAA,MAAA,YAEA,cAAA,IAVJ,UAeI,WAAA,E1Ck4JH,MAAA,QCmBD,mByC/4JI,YAAA,IArBJ,SAyBI,U1C+3JH,cAAA,ECmBD,WyCx4JE,WAAA,IAFF,mBAAA,mBAMI,cAAA,KAEA,0BACA,0B1Cy3JH,SAAA,S0Cj3JC,IAAK,KCvDL,MAAA,MACA,MAAA,Q3C46JD,e0Ct3JC,MAAO,QClDL,iBAAA,Q3C26JH,aAAA,Q2Cx6JG,kB3C26JH,iBAAA,Q2Cn7JC,2BACA,MAAA,Q3Cu7JD,Y0C73JC,MAAO,QCtDL,iBAAA,Q3Cs7JH,aAAA,Q2Cn7JG,e3Cs7JH,iBAAA,Q2C97JC,wBACA,MAAA,Q3Ck8JD,e0Cp4JC,MAAO,QC1DL,iBAAA,Q3Ci8JH,aAAA,Q2C97JG,kB3Ci8JH,iBAAA,Q2Cz8JC,2BACA,MAAA,Q3C68JD,c0C34JC,MAAO,QC9DL,iBAAA,Q3C48JH,aAAA,Q2Cz8JG,iB3C48JH,iBAAA,Q4C78JC,0BAAQ,MAAA,QACR,wCAAQ,K5Cm9JP,oBAAA,KAAA,E4C/8JD,GACA,oBAAA,EAAA,GACA,mCAAQ,K5Cq9JP,oBAAA,KAAA,E4Cv9JD,GACA,oBAAA,EAAA,GACA,gCAAQ,K5Cq9JP,oBAAA,KAAA,E4C78JD,GACA,oBAAA,EAAA,GAGA,UACA,OAAA,KxCsCA,cAAA,KACQ,SAAA,OJ26JT,iBAAA,Q4C78JC,cAAe,IACf,mBAAA,MAAA,EAAA,IAAA,IAAA,eACA,WAAA,MAAA,EAAA,IAAA,IAAA,eAEA,cACA,MAAA,KACA,MAAA,EACA,OAAA,KACA,UAAA,KxCyBA,YAAA,KACQ,MAAA,KAyHR,WAAA,OACK,iBAAA,QACG,mBAAA,MAAA,EAAA,KAAA,EAAA,gBJ+zJT,WAAA,MAAA,EAAA,KAAA,EAAA,gB4C18JC,mBAAoB,MAAM,IAAI,K3Cq+JzB,cAAe,MAAM,IAAI,K4Cp+J5B,WAAA,MAAA,IAAA,KDEF,sBCAE,gCDAF,iBAAA,yK5C88JD,iBAAA,oK4Cv8JC,iBAAiB,iK3Cm+JjB,wBAAyB,KAAK,KG/gK9B,gBAAA,KAAA,KJy/JD,qBIv/JS,+BwCmDR,kBAAmB,qBAAqB,GAAG,OAAO,SErElD,aAAA,qBAAA,GAAA,OAAA,S9C4gKD,UAAA,qBAAA,GAAA,OAAA,S6Cz9JG,sBACA,iBAAA,Q7C69JH,wC4Cx8JC,iBAAkB,yKEzElB,iBAAA,oK9CohKD,iBAAA,iK6Cj+JG,mBACA,iBAAA,Q7Cq+JH,qC4C58JC,iBAAkB,yKE7ElB,iBAAA,oK9C4hKD,iBAAA,iK6Cz+JG,sBACA,iBAAA,Q7C6+JH,wC4Ch9JC,iBAAkB,yKEjFlB,iBAAA,oK9CoiKD,iBAAA,iK6Cj/JG,qBACA,iBAAA,Q7Cq/JH,uC+C5iKC,iBAAkB,yKAElB,iBAAA,oK/C6iKD,iBAAA,iK+C1iKG,O/C6iKH,WAAA,KC4BD,mB8CnkKE,WAAA,E/C4iKD,O+CxiKD,YACE,SAAA,O/C0iKD,KAAA,E+CtiKC,Y/CyiKD,MAAA,Q+CriKG,c/CwiKH,QAAA,MC4BD,4B8C9jKE,UAAA,KAGF,aAAA,mBAEE,aAAA,KAGF,YAAA,kB9C+jKE,cAAe,K8CxjKjB,YAHE,Y/CoiKD,a+ChiKC,QAAA,W/CmiKD,eAAA,I+C/hKC,c/CkiKD,eAAA,O+C7hKC,cACA,eAAA,OAMF,eACE,WAAA,EACA,cAAA,ICvDF,YAEE,aAAA,EACA,WAAA,KAQF,YACE,aAAA,EACA,cAAA,KAGA,iBACA,SAAA,SACA,QAAA,MhD6kKD,QAAA,KAAA,KgD1kKC,cAAA,KrB3BA,iBAAA,KACC,OAAA,IAAA,MAAA,KqB6BD,6BACE,uBAAA,IrBvBF,wBAAA,I3BsmKD,4BgDpkKC,cAAe,E/CgmKf,2BAA4B,I+C9lK5B,0BAAA,IAFF,kBAAA,uBAKI,MAAA,KAIF,2CAAA,gD/CgmKA,MAAO,K+C5lKL,wBAFA,wBhDykKH,6BgDxkKG,6BAKF,MAAO,KACP,gBAAA,KACA,iBAAA,QAKA,uB/C4lKA,MAAO,KACP,WAAY,K+CzlKV,0BhDmkKH,gCgDlkKG,gCALF,MAAA,K/CmmKA,OAAQ,YACR,iBAAkB,KDxBnB,mDgD5kKC,yDAAA,yD/CymKA,MAAO,QDxBR,gDgDhkKC,sDAAA,sD/C6lKA,MAAO,K+CzlKL,wBAEA,8BADA,8BhDmkKH,QAAA,EgDxkKC,MAAA,K/ComKA,iBAAkB,QAClB,aAAc,QAEhB,iDDpBC,wDCuBD,uDADA,uD+CzmKE,8DAYI,6D/C4lKN,uD+CxmKE,8D/C2mKF,6DAKE,MAAO,QDxBR,8CiD1qKG,oDADF,oDAEE,MAAA,QAEA,yBhDusKF,MAAO,QgDrsKH,iBAAA,QAFF,0BAAA,+BAKI,MAAA,QAGF,mDAAA,wDhDwsKJ,MAAO,QDtBR,gCiDhrKO,gCAGF,qCAFE,qChD2sKN,MAAO,QACP,iBAAkB,QAEpB,iCgDvsKQ,uCAFA,uChD0sKR,sCDtBC,4CiDnrKO,4CArBN,MAAA,KACE,iBAAA,QACA,aAAA,QAEA,sBhDouKF,MAAO,QgDluKH,iBAAA,QAFF,uBAAA,4BAKI,MAAA,QAGF,gDAAA,qDhDquKJ,MAAO,QDtBR,6BiD7sKO,6BAGF,kCAFE,kChDwuKN,MAAO,QACP,iBAAkB,QAEpB,8BgDpuKQ,oCAFA,oChDuuKR,mCDtBC,yCiDhtKO,yCArBN,MAAA,KACE,iBAAA,QACA,aAAA,QAEA,yBhDiwKF,MAAO,QgD/vKH,iBAAA,QAFF,0BAAA,+BAKI,MAAA,QAGF,mDAAA,wDhDkwKJ,MAAO,QDtBR,gCiD1uKO,gCAGF,qCAFE,qChDqwKN,MAAO,QACP,iBAAkB,QAEpB,iCgDjwKQ,uCAFA,uChDowKR,sCDtBC,4CiD7uKO,4CArBN,MAAA,KACE,iBAAA,QACA,aAAA,QAEA,wBhD8xKF,MAAO,QgD5xKH,iBAAA,QAFF,yBAAA,8BAKI,MAAA,QAGF,kDAAA,uDhD+xKJ,MAAO,QDtBR,+BiDvwKO,+BAGF,oCAFE,oChDkyKN,MAAO,QACP,iBAAkB,QAEpB,gCgD9xKQ,sCAFA,sChDiyKR,qCDtBC,2CiD1wKO,2CDkGN,MAAO,KACP,iBAAA,QACA,aAAA,QAEF,yBACE,WAAA,EACA,cAAA,IE1HF,sBACE,cAAA,EACA,YAAA,IAEA,O9C0DA,cAAA,KACQ,iBAAA,KJ6uKT,OAAA,IAAA,MAAA,YkDnyKC,cAAe,IACf,mBAAA,EAAA,IAAA,IAAA,gBlDqyKD,WAAA,EAAA,IAAA,IAAA,gBkD/xKC,YACA,QAAA,KvBnBC,e3BuzKF,QAAA,KAAA,KkDtyKC,cAAe,IAAI,MAAM,YAMvB,uBAAA,IlDmyKH,wBAAA,IkD7xKC,0CACA,MAAA,QAEA,alDgyKD,WAAA,EkDpyKC,cAAe,EjDg0Kf,UAAW,KACX,MAAO,QDtBR,oBkD1xKC,sBjDkzKF,eiDxzKI,mBAKJ,qBAEE,MAAA,QvBvCA,cACC,QAAA,KAAA,K3Bs0KF,iBAAA,QkDrxKC,WAAY,IAAI,MAAM,KjDizKtB,2BAA4B,IiD9yK1B,0BAAA,IAHJ,mBAAA,mCAMM,cAAA,ElDwxKL,oCkDnxKG,oDjD+yKF,aAAc,IAAI,EiD7yKZ,cAAA,EvBtEL,4D3B61KF,4EkDjxKG,WAAA,EjD6yKF,uBAAwB,IiD3yKlB,wBAAA,IvBtEL,0D3B21KF,0EkD1yKC,cAAe,EvB1Df,2BAAA,IACC,0BAAA,IuB0FH,+EAEI,uBAAA,ElD8wKH,wBAAA,EkD1wKC,wDlD6wKD,iBAAA,EC4BD,0BACE,iBAAkB,EiDlyKpB,8BlD0wKC,ckD1wKD,gCjDuyKE,cAAe,EiDvyKjB,sCAQM,sBlDwwKL,wCC4BC,cAAe,K0Br5Kf,aAAA,KuByGF,wDlDqxKC,0BC4BC,uBAAwB,IACxB,wBAAyB,IiDlzK3B,yFAoBQ,yFlDwwKP,2DkDzwKO,2DjDqyKN,uBAAwB,IACxB,wBAAyB,IAK3B,wGiD9zKA,wGjD4zKA,wGDtBC,wGCuBD,0EiD7zKA,0EjD2zKA,0EiDnyKU,0EjD2yKR,uBAAwB,IAK1B,uGiDx0KA,uGjDs0KA,uGDtBC,uGCuBD,yEiDv0KA,yEjDq0KA,yEiDzyKU,yEvB7HR,wBAAA,IuBiGF,sDlDqzKC,yBC4BC,2BAA4B,IAC5B,0BAA2B,IiDxyKrB,qFA1CR,qFAyCQ,wDlDmxKP,wDC4BC,2BAA4B,IAC5B,0BAA2B,IAG7B,oGDtBC,oGCwBD,oGiD91KA,oGjD21KA,uEiD7yKU,uEjD+yKV,uEiD71KA,uEjDm2KE,0BAA2B,IAG7B,mGDtBC,mGCwBD,mGiDx2KA,mGjDq2KA,sEiDnzKU,sEjDqzKV,sEiDv2KA,sEjD62KE,2BAA4B,IiDlzK1B,0BlD2xKH,qCkDt1KD,0BAAA,qCA+DI,WAAA,IAAA,MAAA,KA/DJ,kDAAA,kDAmEI,WAAA,EAnEJ,uBAAA,yCjD23KE,OAAQ,EiDjzKA,+CjDqzKV,+CiD/3KA,+CjDi4KA,+CAEA,+CANA,+CDjBC,iECoBD,iEiDh4KA,iEjDk4KA,iEAEA,iEANA,iEAWE,YAAa,EiD3zKL,8CjD+zKV,8CiD74KA,8CjD+4KA,8CAEA,8CANA,8CDjBC,gECoBD,gEiD94KA,gEjDg5KA,gEAEA,gEANA,gEAWE,aAAc,EAIhB,+CiD35KA,+CjDy5KA,+CiDl0KU,+CjDq0KV,iEiD55KA,iEjD05KA,iEDtBC,iEC6BC,cAAe,EAEjB,8CiDn0KU,8CjDq0KV,8CiDr6KA,8CjDo6KA,gEDtBC,gECwBD,gEiDh0KI,gEACA,cAAA,EAUJ,yBACE,cAAA,ElDmyKD,OAAA,EkD/xKG,aACA,cAAA,KANJ,oBASM,cAAA,ElDkyKL,cAAA,IkD7xKG,2BlDgyKH,WAAA,IC4BD,4BiDxzKM,cAAA,EAKF,wDAvBJ,wDlDqzKC,WAAA,IAAA,MAAA,KkD5xKK,2BlD+xKL,WAAA,EmDlhLC,uDnDqhLD,cAAA,IAAA,MAAA,KmDlhLG,eACA,aAAA,KnDshLH,8BmDxhLC,MAAA,KAMI,iBAAA,QnDqhLL,aAAA,KmDlhLK,0DACA,iBAAA,KAGJ,qCAEI,MAAA,QnDmhLL,iBAAA,KmDpiLC,yDnDuiLD,oBAAA,KmDpiLG,eACA,aAAA,QnDwiLH,8BmD1iLC,MAAA,KAMI,iBAAA,QnDuiLL,aAAA,QmDpiLK,0DACA,iBAAA,QAGJ,qCAEI,MAAA,QnDqiLL,iBAAA,KmDtjLC,yDnDyjLD,oBAAA,QmDtjLG,eACA,aAAA,QnD0jLH,8BmD5jLC,MAAA,QAMI,iBAAA,QnDyjLL,aAAA,QmDtjLK,0DACA,iBAAA,QAGJ,qCAEI,MAAA,QnDujLL,iBAAA,QmDxkLC,yDnD2kLD,oBAAA,QmDxkLG,YACA,aAAA,QnD4kLH,2BmD9kLC,MAAA,QAMI,iBAAA,QnD2kLL,aAAA,QmDxkLK,uDACA,iBAAA,QAGJ,kCAEI,MAAA,QnDykLL,iBAAA,QmD1lLC,sDnD6lLD,oBAAA,QmD1lLG,eACA,aAAA,QnD8lLH,8BmDhmLC,MAAA,QAMI,iBAAA,QnD6lLL,aAAA,QmD1lLK,0DACA,iBAAA,QAGJ,qCAEI,MAAA,QnD2lLL,iBAAA,QmD5mLC,yDnD+mLD,oBAAA,QmD5mLG,cACA,aAAA,QnDgnLH,6BmDlnLC,MAAA,QAMI,iBAAA,QnD+mLL,aAAA,QmD5mLK,yDACA,iBAAA,QAGJ,oCAEI,MAAA,QnD6mLL,iBAAA,QoD5nLC,wDACA,oBAAA,QAEA,kBACA,SAAA,SpD+nLD,QAAA,MoDpoLC,OAAQ,EnDgqLR,QAAS,EACT,SAAU,OAEZ,yCmDtpLI,wBADA,yBAEA,yBACA,wBACA,SAAA,SACA,IAAA,EACA,OAAA,EpD+nLH,KAAA,EoD1nLC,MAAO,KACP,OAAA,KpD4nLD,OAAA,EoDvnLC,wBpD0nLD,eAAA,OqDppLC,uBACA,eAAA,IAEA,MACA,WAAA,KACA,QAAA,KjDwDA,cAAA,KACQ,iBAAA,QJgmLT,OAAA,IAAA,MAAA,QqD/pLC,cAAe,IASb,mBAAA,MAAA,EAAA,IAAA,IAAA,gBACA,WAAA,MAAA,EAAA,IAAA,IAAA,gBAKJ,iBACE,aAAA,KACA,aAAA,gBAEF,SACE,QAAA,KACA,cAAA,ICtBF,SACE,QAAA,IACA,cAAA,IAEA,OACA,MAAA,MACA,UAAA,KjCRA,YAAA,IAGA,YAAA,ErBqrLD,MAAA,KsD7qLC,YAAA,EAAA,IAAA,EAAA,KrDysLA,OAAQ,kBqDvsLN,QAAA,GjCbF,aiCeE,ajCZF,MAAA,KrB6rLD,gBAAA,KsDzqLC,OAAA,QACE,OAAA,kBACA,QAAA,GAEA,aACA,mBAAA,KtD2qLH,QAAA,EuDhsLC,OAAQ,QACR,WAAA,IvDksLD,OAAA,EuD7rLC,YACA,SAAA,OAEA,OACA,SAAA,MACA,IAAA,EACA,MAAA,EACA,OAAA,EACA,KAAA,EAIA,QAAA,KvD6rLD,QAAA,KuD1rLC,SAAA,OnD+GA,2BAAA,MACI,QAAA,EAEI,0BAkER,mBAAA,kBAAA,IAAA,SAEK,cAAA,aAAA,IAAA,SACG,WAAA,UAAA,IAAA,SJ6gLT,kBAAA,kBuDhsLC,cAAA,kBnD2GA,aAAA,kBACI,UAAA,kBAEI,wBJwlLT,kBAAA,euDpsLK,cAAe,eACnB,aAAA,eACA,UAAA,eAIF,mBACE,WAAA,OACA,WAAA,KvDqsLD,cuDhsLC,SAAU,SACV,MAAA,KACA,OAAA,KAEA,eACA,SAAA,SnDaA,iBAAA,KACQ,wBAAA,YmDZR,gBAAA,YtD4tLA,OsD5tLA,IAAA,MAAA,KAEA,OAAA,IAAA,MAAA,evDksLD,cAAA,IuD9rLC,QAAS,EACT,mBAAA,EAAA,IAAA,IAAA,eACA,WAAA,EAAA,IAAA,IAAA,eAEA,gBACA,SAAA,MACA,IAAA,EACA,MAAA,EvDgsLD,OAAA,EuD9rLC,KAAA,ElCrEA,QAAA,KAGA,iBAAA,KkCmEA,qBlCtEA,OAAA,iBAGA,QAAA,EkCwEF,mBACE,OAAA,kBACA,QAAA,GAIF,cACE,QAAA,KvDgsLD,cAAA,IAAA,MAAA,QuD3rLC,qBACA,WAAA,KAKF,aACE,OAAA,EACA,YAAA,WAIF,YACE,SAAA,SACA,QAAA,KvD0rLD,cuD5rLC,QAAS,KAQP,WAAA,MACA,WAAA,IAAA,MAAA,QATJ,wBAaI,cAAA,EvDsrLH,YAAA,IuDlrLG,mCvDqrLH,YAAA,KuD/qLC,oCACA,YAAA,EAEA,yBACA,SAAA,SvDkrLD,IAAA,QuDhqLC,MAAO,KAZP,OAAA,KACE,SAAA,OvDgrLD,yBuD7qLD,cnDvEA,MAAA,MACQ,OAAA,KAAA,KmD2ER,eAAY,mBAAA,EAAA,IAAA,KAAA,evD+qLX,WAAA,EAAA,IAAA,KAAA,euDzqLD,UAFA,MAAA,OvDirLD,yBwD/zLC,UACA,MAAA,OCNA,SAEA,SAAA,SACA,QAAA,KACA,QAAA,MACA,YAAA,iBAAA,UAAA,MAAA,WACA,UAAA,KACA,WAAA,OACA,YAAA,IACA,YAAA,WACA,WAAA,KACA,WAAA,MACA,gBAAA,KACA,YAAA,KACA,eAAA,KACA,eAAA,ODHA,WAAA,OnCVA,aAAA,OAGA,UAAA,OrBs1LD,YAAA,OwD30LC,OAAA,iBnCdA,QAAA,ErB61LD,WAAA,KwD90LY,YAAmB,OAAA,kBxDk1L/B,QAAA,GwDj1LY,aAAmB,QAAA,IAAA,ExDq1L/B,WAAA,KwDp1LY,eAAmB,QAAA,EAAA,IxDw1L/B,YAAA,IwDv1LY,gBAAmB,QAAA,IAAA,ExD21L/B,WAAA,IwDt1LC,cACA,QAAA,EAAA,IACA,YAAA,KAEA,eACA,UAAA,MxDy1LD,QAAA,IAAA,IwDr1LC,MAAO,KACP,WAAA,OACA,iBAAA,KACA,cAAA,IAEA,exDu1LD,SAAA,SwDn1LC,MAAA,EACE,OAAA,EACA,aAAA,YACA,aAAA,MAEA,4BxDq1LH,OAAA,EwDn1LC,KAAA,IACE,YAAA,KACA,aAAA,IAAA,IAAA,EACA,iBAAA,KAEA,iCxDq1LH,MAAA,IwDn1LC,OAAA,EACE,cAAA,KACA,aAAA,IAAA,IAAA,EACA,iBAAA,KAEA,kCxDq1LH,OAAA,EwDn1LC,KAAA,IACE,cAAA,KACA,aAAA,IAAA,IAAA,EACA,iBAAA,KAEA,8BxDq1LH,IAAA,IwDn1LC,KAAA,EACE,WAAA,KACA,aAAA,IAAA,IAAA,IAAA,EACA,mBAAA,KAEA,6BxDq1LH,IAAA,IwDn1LC,MAAA,EACE,WAAA,KACA,aAAA,IAAA,EAAA,IAAA,IACA,kBAAA,KAEA,+BxDq1LH,IAAA,EwDn1LC,KAAA,IACE,YAAA,KACA,aAAA,EAAA,IAAA,IACA,oBAAA,KAEA,oCxDq1LH,IAAA,EwDn1LC,MAAA,IACE,WAAA,KACA,aAAA,EAAA,IAAA,IACA,oBAAA,KAEA,qCxDq1LH,IAAA,E0Dl7LC,KAAM,IACN,WAAA,KACA,aAAA,EAAA,IAAA,IACA,oBAAA,KAEA,SACA,SAAA,SACA,IAAA,EDXA,KAAA,EAEA,QAAA,KACA,QAAA,KACA,UAAA,MACA,QAAA,IACA,YAAA,iBAAA,UAAA,MAAA,WACA,UAAA,KACA,WAAA,OACA,YAAA,IACA,YAAA,WACA,WAAA,KACA,WAAA,MACA,gBAAA,KACA,YAAA,KACA,eAAA,KCAA,eAAA,OAEA,WAAA,OACA,aAAA,OAAA,UAAA,OACA,YAAA,OACA,iBAAA,KACA,wBAAA,YtD8CA,gBAAA,YACQ,OAAA,IAAA,MAAA,KJk5LT,OAAA,IAAA,MAAA,e0D77LC,cAAA,IAAY,mBAAA,EAAA,IAAA,KAAA,e1Dg8Lb,WAAA,EAAA,IAAA,KAAA,e0D/7La,WAAA,KACZ,aAAY,WAAA,MACZ,eAAY,YAAA,KAGd,gBACE,WAAA,KAEA,cACA,YAAA,MAEA,e1Dq8LD,QAAA,IAAA,K0Dl8LC,OAAQ,EACR,UAAA,K1Do8LD,iBAAA,Q0D57LC,cAAA,IAAA,MAAA,QzDy9LA,cAAe,IAAI,IAAI,EAAE,EyDt9LvB,iBACA,QAAA,IAAA,KAEA,gBACA,sB1D87LH,SAAA,S0D37LC,QAAS,MACT,MAAA,E1D67LD,OAAA,E0D37LC,aAAc,YACd,aAAA,M1D87LD,gB0Dz7LC,aAAA,KAEE,sBACA,QAAA,GACA,aAAA,KAEA,oB1D27LH,OAAA,M0D17LG,KAAA,IACE,YAAA,MACA,iBAAA,KACA,iBAAA,gBACA,oBAAA,E1D67LL,0B0Dz7LC,OAAA,IACE,YAAA,MACA,QAAA,IACA,iBAAA,KACA,oBAAA,EAEA,sB1D27LH,IAAA,I0D17LG,KAAA,MACE,WAAA,MACA,mBAAA,KACA,mBAAA,gBACA,kBAAA,E1D67LL,4B0Dz7LC,OAAA,MACE,KAAA,IACA,QAAA,IACA,mBAAA,KACA,kBAAA,EAEA,uB1D27LH,IAAA,M0D17LG,KAAA,IACE,YAAA,MACA,iBAAA,EACA,oBAAA,KACA,oBAAA,gB1D67LL,6B0Dx7LC,IAAA,IACE,YAAA,MACA,QAAA,IACA,iBAAA,EACA,oBAAA,KAEA,qB1D07LH,IAAA,I0Dz7LG,MAAA,MACE,WAAA,MACA,mBAAA,EACA,kBAAA,KACA,kBAAA,gB1D47LL,2B2DpjMC,MAAO,IACP,OAAA,M3DsjMD,QAAA,I2DnjMC,mBAAoB,EACpB,kBAAA,KAEA,U3DqjMD,SAAA,S2DljMG,gBACA,SAAA,SvD6KF,MAAA,KACK,SAAA,OJ04LN,sB2D/jMC,SAAU,S1D4lMV,QAAS,K0D9kML,mBAAA,IAAA,YAAA,K3DqjML,cAAA,IAAA,YAAA,K2D3hMC,WAAA,IAAA,YAAA,KvDmKK,4BAFL,0BAGQ,YAAA,EA3JA,qDA+GR,sBAEQ,mBAAA,kBAAA,IAAA,YJ86LP,cAAA,aAAA,IAAA,Y2DzjMG,WAAA,UAAA,IAAA,YvDmHJ,4BAAA,OACQ,oBAAA,OuDjHF,oBAAA,O3D4jML,YAAA,OI58LD,mCHs+LA,2BGr+LQ,KAAA,EuD5GF,kBAAA,sB3D6jML,UAAA,sBC2BD,kCADA,2BG5+LA,KAAA,EACQ,kBAAA,uBuDtGF,UAAA,uBArCN,6B3DomMD,gC2DpmMC,iC1D+nME,KAAM,E0DllMN,kBAAA,mB3D4jMH,UAAA,oBAGA,wB2D5mMD,sBAAA,sBAsDI,QAAA,MAEA,wB3D0jMH,KAAA,E2DtjMG,sB3DyjMH,sB2DrnMC,SAAU,SA+DR,IAAA,E3DyjMH,MAAA,KC0BD,sB0D/kMI,KAAA,KAnEJ,sBAuEI,KAAA,MAvEJ,2BA0EI,4B3DwjMH,KAAA,E2D/iMC,6BACA,KAAA,MAEA,8BACA,KAAA,KtC3FA,kBsC6FA,SAAA,SACA,IAAA,EACA,OAAA,EACA,KAAA,EACA,MAAA,I3DmjMD,UAAA,K2D9iMC,MAAA,KdnGE,WAAA,OACA,YAAA,EAAA,IAAA,IAAA,eACA,iBAAA,cAAA,OAAA,kBACA,QAAA,G7CqpMH,uB2DljMC,iBAAA,sEACE,iBAAA,iEACA,iBAAA,uFdxGA,iBAAA,kEACA,OAAA,+GACA,kBAAA,SACA,wBACA,MAAA,E7C6pMH,KAAA,K2DpjMC,iBAAA,sE1DglMA,iBAAiB,iE0D9kMf,iBAAA,uFACA,iBAAA,kEACA,OAAA,+GtCvHF,kBAAA,SsCyFF,wB3DslMC,wBC4BC,MAAO,KACP,gBAAiB,KACjB,OAAQ,kB0D7kMN,QAAA,EACA,QAAA,G3DwjMH,0C2DhmMD,2CA2CI,6BADA,6B1DklMF,SAAU,S0D7kMR,IAAA,IACA,QAAA,E3DqjMH,QAAA,a2DrmMC,WAAY,MAqDV,0CADA,6B3DsjMH,KAAA,I2D1mMC,YAAa,MA0DX,2CADA,6BAEA,MAAA,IACA,aAAA,MAME,6BADF,6B3DmjMH,MAAA,K2D9iMG,OAAA,KACE,YAAA,M3DgjML,YAAA,E2DriMC,oCACA,QAAA,QAEA,oCACA,QAAA,QAEA,qBACA,SAAA,SACA,OAAA,K3DwiMD,KAAA,I2DjjMC,QAAS,GAYP,MAAA,IACA,aAAA,EACA,YAAA,KACA,WAAA,OACA,WAAA,KAEA,wBACA,QAAA,aAWA,MAAA,KACA,OAAA,K3D8hMH,OAAA,I2D7jMC,YAAa,OAkCX,OAAA,QACA,iBAAA,OACA,iBAAA,cACA,OAAA,IAAA,MAAA,K3D8hMH,cAAA,K2DthMC,6BACA,MAAA,KACA,OAAA,KACA,OAAA,EACA,iBAAA,KAEA,kBACA,SAAA,SACA,MAAA,IACA,OAAA,K3DyhMD,KAAA,I2DxhMC,QAAA,GACE,YAAA,K3D0hMH,eAAA,K2Dj/LC,MAAO,KAhCP,WAAA,O1D8iMA,YAAa,EAAE,IAAI,IAAI,eAEzB,uB0D3iMM,YAAA,KAEA,oCACA,0C3DmhMH,2C2D3hMD,6BAAA,6BAYI,MAAA,K3DmhMH,OAAA,K2D/hMD,WAAA,M1D2jME,UAAW,KDxBZ,0C2D9gMD,6BACE,YAAA,MAEA,2C3DghMD,6B2D5gMD,aAAA,M3D+gMC,kBACF,MAAA,I4D7wMC,KAAA,I3DyyME,eAAgB,KAElB,qBACE,OAAQ,MAkBZ,qCADA,sCADA,mBADA,oBAXA,gBADA,iBAOA,uBADA,wBADA,iBADA,kBADA,wBADA,yBASA,mCADA,oC2DpzME,oBAAA,qBAAA,oBAAA,qB3D2zMF,WADA,YAOA,uBADA,wBADA,qBADA,sBADA,cADA,e2D/zMI,a3Dq0MJ,cDvBC,kB4D7yMG,mB3DqzMJ,WADA,YAwBE,QAAS,MACT,QAAS,IASX,qCADA,mBANA,gBAGA,uBADA,iBADA,wBAIA,mCDhBC,oB6D/0MC,oB5Dk2MF,W+B51MA,uBhCo0MC,qB4D5zMG,cChBF,aACA,kB5D+1MF,W+Br1ME,MAAO,KhCy0MR,cgCt0MC,QAAS,MACT,aAAA,KhCw0MD,YAAA,KgC/zMC,YhCk0MD,MAAA,gBgC/zMC,WhCk0MD,MAAA,egC/zMC,MhCk0MD,QAAA,e8Dz1MC,MACA,QAAA,gBAEA,WACA,WAAA,O9B8BF,WACE,KAAA,EAAA,EAAA,EhCg0MD,MAAA,YgCzzMC,YAAa,KACb,iBAAA,YhC2zMD,OAAA,E+D31MC,Q/D81MD,QAAA,eC4BD,OACE,SAAU,M+Dn4MV,chE42MD,MAAA,aC+BD,YADA,YADA,YADA,YAIE,QAAS,e+Dp5MT,kBhEs4MC,mBgEr4MD,yBhEi4MD,kB+Dl1MD,mBA6IA,yB9D4tMA,kBACA,mB8Dj3ME,yB9D62MF,kBACA,mBACA,yB+Dv5MY,QAAA,eACV,yBAAU,YhE04MT,QAAA,gBC4BD,iB+Dp6MU,QAAA,gBhE64MX,c+D51MG,QAAS,oB/Dg2MV,c+Dl2MC,c/Dm2MH,QAAA,sB+D91MG,yB/Dk2MD,kBACF,QAAA,iB+D91MG,yB/Dk2MD,mBACF,QAAA,kBgEh6MC,yBhEo6MC,yBgEn6MD,QAAA,wBACA,+CAAU,YhEw6MT,QAAA,gBC4BD,iB+Dl8MU,QAAA,gBhE26MX,c+Dr2MG,QAAS,oB/Dy2MV,c+D32MC,c/D42MH,QAAA,sB+Dv2MG,+C/D22MD,kBACF,QAAA,iB+Dv2MG,+C/D22MD,mBACF,QAAA,kBgE97MC,+ChEk8MC,yBgEj8MD,QAAA,wBACA,gDAAU,YhEs8MT,QAAA,gBC4BD,iB+Dh+MU,QAAA,gBhEy8MX,c+D92MG,QAAS,oB/Dk3MV,c+Dp3MC,c/Dq3MH,QAAA,sB+Dh3MG,gD/Do3MD,kBACF,QAAA,iB+Dh3MG,gD/Do3MD,mBACF,QAAA,kBgE59MC,gDhEg+MC,yBgE/9MD,QAAA,wBACA,0BAAU,YhEo+MT,QAAA,gBC4BD,iB+D9/MU,QAAA,gBhEu+MX,c+Dv3MG,QAAS,oB/D23MV,c+D73MC,c/D83MH,QAAA,sB+Dz3MG,0B/D63MD,kBACF,QAAA,iB+Dz3MG,0B/D63MD,mBACF,QAAA,kBgEl/MC,0BhEs/MC,yBACF,QAAA,wBgEv/MC,yBhE2/MC,WACF,QAAA,gBgE5/MC,+ChEggNC,WACF,QAAA,gBgEjgNC,gDhEqgNC,WACF,QAAA,gBAGA,0B+Dh3MC,WA4BE,QAAS,gBC5LX,eAAU,QAAA,eACV,aAAU,ehEyhNT,QAAA,gBC4BD,oB+DnjNU,QAAA,gBhE4hNX,iB+D93MG,QAAS,oBAMX,iB/D23MD,iB+Dt2MG,QAAS,sB/D22MZ,qB+D/3MC,QAAS,e/Dk4MV,a+D53MC,qBAcE,QAAS,iB/Dm3MZ,sB+Dh4MC,QAAS,e/Dm4MV,a+D73MC,sBAOE,QAAS,kB/D23MZ,4B+D53MC,QAAS,eCpLT,ahEojNC,4BACF,QAAA,wBC6BD,aACE,cACE,QAAS","sourcesContent":["/*! normalize.css v3.0.3 | MIT License | github.com/necolas/normalize.css */\n\n//\n// 1. Set default font family to sans-serif.\n// 2. Prevent iOS and IE text size adjust after device orientation change,\n// without disabling user zoom.\n//\n\nhtml {\n font-family: sans-serif; // 1\n -ms-text-size-adjust: 100%; // 2\n -webkit-text-size-adjust: 100%; // 2\n}\n\n//\n// Remove default margin.\n//\n\nbody {\n margin: 0;\n}\n\n// HTML5 display definitions\n// ==========================================================================\n\n//\n// Correct `block` display not defined for any HTML5 element in IE 8/9.\n// Correct `block` display not defined for `details` or `summary` in IE 10/11\n// and Firefox.\n// Correct `block` display not defined for `main` in IE 11.\n//\n\narticle,\naside,\ndetails,\nfigcaption,\nfigure,\nfooter,\nheader,\nhgroup,\nmain,\nmenu,\nnav,\nsection,\nsummary {\n display: block;\n}\n\n//\n// 1. Correct `inline-block` display not defined in IE 8/9.\n// 2. Normalize vertical alignment of `progress` in Chrome, Firefox, and Opera.\n//\n\naudio,\ncanvas,\nprogress,\nvideo {\n display: inline-block; // 1\n vertical-align: baseline; // 2\n}\n\n//\n// Prevent modern browsers from displaying `audio` without controls.\n// Remove excess height in iOS 5 devices.\n//\n\naudio:not([controls]) {\n display: none;\n height: 0;\n}\n\n//\n// Address `[hidden]` styling not present in IE 8/9/10.\n// Hide the `template` element in IE 8/9/10/11, Safari, and Firefox < 22.\n//\n\n[hidden],\ntemplate {\n display: none;\n}\n\n// Links\n// ==========================================================================\n\n//\n// Remove the gray background color from active links in IE 10.\n//\n\na {\n background-color: transparent;\n}\n\n//\n// Improve readability of focused elements when they are also in an\n// active/hover state.\n//\n\na:active,\na:hover {\n outline: 0;\n}\n\n// Text-level semantics\n// ==========================================================================\n\n//\n// Address styling not present in IE 8/9/10/11, Safari, and Chrome.\n//\n\nabbr[title] {\n border-bottom: 1px dotted;\n}\n\n//\n// Address style set to `bolder` in Firefox 4+, Safari, and Chrome.\n//\n\nb,\nstrong {\n font-weight: bold;\n}\n\n//\n// Address styling not present in Safari and Chrome.\n//\n\ndfn {\n font-style: italic;\n}\n\n//\n// Address variable `h1` font-size and margin within `section` and `article`\n// contexts in Firefox 4+, Safari, and Chrome.\n//\n\nh1 {\n font-size: 2em;\n margin: 0.67em 0;\n}\n\n//\n// Address styling not present in IE 8/9.\n//\n\nmark {\n background: #ff0;\n color: #000;\n}\n\n//\n// Address inconsistent and variable font size in all browsers.\n//\n\nsmall {\n font-size: 80%;\n}\n\n//\n// Prevent `sub` and `sup` affecting `line-height` in all browsers.\n//\n\nsub,\nsup {\n font-size: 75%;\n line-height: 0;\n position: relative;\n vertical-align: baseline;\n}\n\nsup {\n top: -0.5em;\n}\n\nsub {\n bottom: -0.25em;\n}\n\n// Embedded content\n// ==========================================================================\n\n//\n// Remove border when inside `a` element in IE 8/9/10.\n//\n\nimg {\n border: 0;\n}\n\n//\n// Correct overflow not hidden in IE 9/10/11.\n//\n\nsvg:not(:root) {\n overflow: hidden;\n}\n\n// Grouping content\n// ==========================================================================\n\n//\n// Address margin not present in IE 8/9 and Safari.\n//\n\nfigure {\n margin: 1em 40px;\n}\n\n//\n// Address differences between Firefox and other browsers.\n//\n\nhr {\n box-sizing: content-box;\n height: 0;\n}\n\n//\n// Contain overflow in all browsers.\n//\n\npre {\n overflow: auto;\n}\n\n//\n// Address odd `em`-unit font size rendering in all browsers.\n//\n\ncode,\nkbd,\npre,\nsamp {\n font-family: monospace, monospace;\n font-size: 1em;\n}\n\n// Forms\n// ==========================================================================\n\n//\n// Known limitation: by default, Chrome and Safari on OS X allow very limited\n// styling of `select`, unless a `border` property is set.\n//\n\n//\n// 1. Correct color not being inherited.\n// Known issue: affects color of disabled elements.\n// 2. Correct font properties not being inherited.\n// 3. Address margins set differently in Firefox 4+, Safari, and Chrome.\n//\n\nbutton,\ninput,\noptgroup,\nselect,\ntextarea {\n color: inherit; // 1\n font: inherit; // 2\n margin: 0; // 3\n}\n\n//\n// Address `overflow` set to `hidden` in IE 8/9/10/11.\n//\n\nbutton {\n overflow: visible;\n}\n\n//\n// Address inconsistent `text-transform` inheritance for `button` and `select`.\n// All other form control elements do not inherit `text-transform` values.\n// Correct `button` style inheritance in Firefox, IE 8/9/10/11, and Opera.\n// Correct `select` style inheritance in Firefox.\n//\n\nbutton,\nselect {\n text-transform: none;\n}\n\n//\n// 1. Avoid the WebKit bug in Android 4.0.* where (2) destroys native `audio`\n// and `video` controls.\n// 2. Correct inability to style clickable `input` types in iOS.\n// 3. Improve usability and consistency of cursor style between image-type\n// `input` and others.\n//\n\nbutton,\nhtml input[type=\"button\"], // 1\ninput[type=\"reset\"],\ninput[type=\"submit\"] {\n -webkit-appearance: button; // 2\n cursor: pointer; // 3\n}\n\n//\n// Re-set default cursor for disabled elements.\n//\n\nbutton[disabled],\nhtml input[disabled] {\n cursor: default;\n}\n\n//\n// Remove inner padding and border in Firefox 4+.\n//\n\nbutton::-moz-focus-inner,\ninput::-moz-focus-inner {\n border: 0;\n padding: 0;\n}\n\n//\n// Address Firefox 4+ setting `line-height` on `input` using `!important` in\n// the UA stylesheet.\n//\n\ninput {\n line-height: normal;\n}\n\n//\n// It's recommended that you don't attempt to style these elements.\n// Firefox's implementation doesn't respect box-sizing, padding, or width.\n//\n// 1. Address box sizing set to `content-box` in IE 8/9/10.\n// 2. Remove excess padding in IE 8/9/10.\n//\n\ninput[type=\"checkbox\"],\ninput[type=\"radio\"] {\n box-sizing: border-box; // 1\n padding: 0; // 2\n}\n\n//\n// Fix the cursor style for Chrome's increment/decrement buttons. For certain\n// `font-size` values of the `input`, it causes the cursor style of the\n// decrement button to change from `default` to `text`.\n//\n\ninput[type=\"number\"]::-webkit-inner-spin-button,\ninput[type=\"number\"]::-webkit-outer-spin-button {\n height: auto;\n}\n\n//\n// 1. Address `appearance` set to `searchfield` in Safari and Chrome.\n// 2. Address `box-sizing` set to `border-box` in Safari and Chrome.\n//\n\ninput[type=\"search\"] {\n -webkit-appearance: textfield; // 1\n box-sizing: content-box; //2\n}\n\n//\n// Remove inner padding and search cancel button in Safari and Chrome on OS X.\n// Safari (but not Chrome) clips the cancel button when the search input has\n// padding (and `textfield` appearance).\n//\n\ninput[type=\"search\"]::-webkit-search-cancel-button,\ninput[type=\"search\"]::-webkit-search-decoration {\n -webkit-appearance: none;\n}\n\n//\n// Define consistent border, margin, and padding.\n//\n\nfieldset {\n border: 1px solid #c0c0c0;\n margin: 0 2px;\n padding: 0.35em 0.625em 0.75em;\n}\n\n//\n// 1. Correct `color` not being inherited in IE 8/9/10/11.\n// 2. Remove padding so people aren't caught out if they zero out fieldsets.\n//\n\nlegend {\n border: 0; // 1\n padding: 0; // 2\n}\n\n//\n// Remove default vertical scrollbar in IE 8/9/10/11.\n//\n\ntextarea {\n overflow: auto;\n}\n\n//\n// Don't inherit the `font-weight` (applied by a rule above).\n// NOTE: the default cannot safely be changed in Chrome and Safari on OS X.\n//\n\noptgroup {\n font-weight: bold;\n}\n\n// Tables\n// ==========================================================================\n\n//\n// Remove most spacing between table cells.\n//\n\ntable {\n border-collapse: collapse;\n border-spacing: 0;\n}\n\ntd,\nth {\n padding: 0;\n}\n","/*! Source: https://github.com/h5bp/html5-boilerplate/blob/master/src/css/main.css */\n\n// ==========================================================================\n// Print styles.\n// Inlined to avoid the additional HTTP request: h5bp.com/r\n// ==========================================================================\n\n@media print {\n *,\n *:before,\n *:after {\n background: transparent !important;\n color: #000 !important; // Black prints faster: h5bp.com/s\n box-shadow: none !important;\n text-shadow: none !important;\n }\n\n a,\n a:visited {\n text-decoration: underline;\n }\n\n a[href]:after {\n content: \" (\" attr(href) \")\";\n }\n\n abbr[title]:after {\n content: \" (\" attr(title) \")\";\n }\n\n // Don't show links that are fragment identifiers,\n // or use the `javascript:` pseudo protocol\n a[href^=\"#\"]:after,\n a[href^=\"javascript:\"]:after {\n content: \"\";\n }\n\n pre,\n blockquote {\n border: 1px solid #999;\n page-break-inside: avoid;\n }\n\n thead {\n display: table-header-group; // h5bp.com/t\n }\n\n tr,\n img {\n page-break-inside: avoid;\n }\n\n img {\n max-width: 100% !important;\n }\n\n p,\n h2,\n h3 {\n orphans: 3;\n widows: 3;\n }\n\n h2,\n h3 {\n page-break-after: avoid;\n }\n\n // Bootstrap specific changes start\n\n // Bootstrap components\n .navbar {\n display: none;\n }\n .btn,\n .dropup > .btn {\n > .caret {\n border-top-color: #000 !important;\n }\n }\n .label {\n border: 1px solid #000;\n }\n\n .table {\n border-collapse: collapse !important;\n\n td,\n th {\n background-color: #fff !important;\n }\n }\n .table-bordered {\n th,\n td {\n border: 1px solid #ddd !important;\n }\n }\n\n // Bootstrap specific changes end\n}\n","/*!\n * Bootstrap v3.3.7 (http://getbootstrap.com)\n * Copyright 2011-2016 Twitter, Inc.\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)\n */\n/*! normalize.css v3.0.3 | MIT License | github.com/necolas/normalize.css */\nhtml {\n font-family: sans-serif;\n -ms-text-size-adjust: 100%;\n -webkit-text-size-adjust: 100%;\n}\nbody {\n margin: 0;\n}\narticle,\naside,\ndetails,\nfigcaption,\nfigure,\nfooter,\nheader,\nhgroup,\nmain,\nmenu,\nnav,\nsection,\nsummary {\n display: block;\n}\naudio,\ncanvas,\nprogress,\nvideo {\n display: inline-block;\n vertical-align: baseline;\n}\naudio:not([controls]) {\n display: none;\n height: 0;\n}\n[hidden],\ntemplate {\n display: none;\n}\na {\n background-color: transparent;\n}\na:active,\na:hover {\n outline: 0;\n}\nabbr[title] {\n border-bottom: 1px dotted;\n}\nb,\nstrong {\n font-weight: bold;\n}\ndfn {\n font-style: italic;\n}\nh1 {\n font-size: 2em;\n margin: 0.67em 0;\n}\nmark {\n background: #ff0;\n color: #000;\n}\nsmall {\n font-size: 80%;\n}\nsub,\nsup {\n font-size: 75%;\n line-height: 0;\n position: relative;\n vertical-align: baseline;\n}\nsup {\n top: -0.5em;\n}\nsub {\n bottom: -0.25em;\n}\nimg {\n border: 0;\n}\nsvg:not(:root) {\n overflow: hidden;\n}\nfigure {\n margin: 1em 40px;\n}\nhr {\n box-sizing: content-box;\n height: 0;\n}\npre {\n overflow: auto;\n}\ncode,\nkbd,\npre,\nsamp {\n font-family: monospace, monospace;\n font-size: 1em;\n}\nbutton,\ninput,\noptgroup,\nselect,\ntextarea {\n color: inherit;\n font: inherit;\n margin: 0;\n}\nbutton {\n overflow: visible;\n}\nbutton,\nselect {\n text-transform: none;\n}\nbutton,\nhtml input[type=\"button\"],\ninput[type=\"reset\"],\ninput[type=\"submit\"] {\n -webkit-appearance: button;\n cursor: pointer;\n}\nbutton[disabled],\nhtml input[disabled] {\n cursor: default;\n}\nbutton::-moz-focus-inner,\ninput::-moz-focus-inner {\n border: 0;\n padding: 0;\n}\ninput {\n line-height: normal;\n}\ninput[type=\"checkbox\"],\ninput[type=\"radio\"] {\n box-sizing: border-box;\n padding: 0;\n}\ninput[type=\"number\"]::-webkit-inner-spin-button,\ninput[type=\"number\"]::-webkit-outer-spin-button {\n height: auto;\n}\ninput[type=\"search\"] {\n -webkit-appearance: textfield;\n box-sizing: content-box;\n}\ninput[type=\"search\"]::-webkit-search-cancel-button,\ninput[type=\"search\"]::-webkit-search-decoration {\n -webkit-appearance: none;\n}\nfieldset {\n border: 1px solid #c0c0c0;\n margin: 0 2px;\n padding: 0.35em 0.625em 0.75em;\n}\nlegend {\n border: 0;\n padding: 0;\n}\ntextarea {\n overflow: auto;\n}\noptgroup {\n font-weight: bold;\n}\ntable {\n border-collapse: collapse;\n border-spacing: 0;\n}\ntd,\nth {\n padding: 0;\n}\n/*! Source: https://github.com/h5bp/html5-boilerplate/blob/master/src/css/main.css */\n@media print {\n *,\n *:before,\n *:after {\n background: transparent !important;\n color: #000 !important;\n box-shadow: none !important;\n text-shadow: none !important;\n }\n a,\n a:visited {\n text-decoration: underline;\n }\n a[href]:after {\n content: \" (\" attr(href) \")\";\n }\n abbr[title]:after {\n content: \" (\" attr(title) \")\";\n }\n a[href^=\"#\"]:after,\n a[href^=\"javascript:\"]:after {\n content: \"\";\n }\n pre,\n blockquote {\n border: 1px solid #999;\n page-break-inside: avoid;\n }\n thead {\n display: table-header-group;\n }\n tr,\n img {\n page-break-inside: avoid;\n }\n img {\n max-width: 100% !important;\n }\n p,\n h2,\n h3 {\n orphans: 3;\n widows: 3;\n }\n h2,\n h3 {\n page-break-after: avoid;\n }\n .navbar {\n display: none;\n }\n .btn > .caret,\n .dropup > .btn > .caret {\n border-top-color: #000 !important;\n }\n .label {\n border: 1px solid #000;\n }\n .table {\n border-collapse: collapse !important;\n }\n .table td,\n .table th {\n background-color: #fff !important;\n }\n .table-bordered th,\n .table-bordered td {\n border: 1px solid #ddd !important;\n }\n}\n@font-face {\n font-family: 'Glyphicons Halflings';\n src: url('../fonts/glyphicons-halflings-regular.eot');\n src: url('../fonts/glyphicons-halflings-regular.eot?#iefix') format('embedded-opentype'), url('../fonts/glyphicons-halflings-regular.woff2') format('woff2'), url('../fonts/glyphicons-halflings-regular.woff') format('woff'), url('../fonts/glyphicons-halflings-regular.ttf') format('truetype'), url('../fonts/glyphicons-halflings-regular.svg#glyphicons_halflingsregular') format('svg');\n}\n.glyphicon {\n position: relative;\n top: 1px;\n display: inline-block;\n font-family: 'Glyphicons Halflings';\n font-style: normal;\n font-weight: normal;\n line-height: 1;\n -webkit-font-smoothing: antialiased;\n -moz-osx-font-smoothing: grayscale;\n}\n.glyphicon-asterisk:before {\n content: \"\\002a\";\n}\n.glyphicon-plus:before {\n content: \"\\002b\";\n}\n.glyphicon-euro:before,\n.glyphicon-eur:before {\n content: \"\\20ac\";\n}\n.glyphicon-minus:before {\n content: \"\\2212\";\n}\n.glyphicon-cloud:before {\n content: \"\\2601\";\n}\n.glyphicon-envelope:before {\n content: \"\\2709\";\n}\n.glyphicon-pencil:before {\n content: \"\\270f\";\n}\n.glyphicon-glass:before {\n content: \"\\e001\";\n}\n.glyphicon-music:before {\n content: \"\\e002\";\n}\n.glyphicon-search:before {\n content: \"\\e003\";\n}\n.glyphicon-heart:before {\n content: \"\\e005\";\n}\n.glyphicon-star:before {\n content: \"\\e006\";\n}\n.glyphicon-star-empty:before {\n content: \"\\e007\";\n}\n.glyphicon-user:before {\n content: \"\\e008\";\n}\n.glyphicon-film:before {\n content: \"\\e009\";\n}\n.glyphicon-th-large:before {\n content: \"\\e010\";\n}\n.glyphicon-th:before {\n content: \"\\e011\";\n}\n.glyphicon-th-list:before {\n content: \"\\e012\";\n}\n.glyphicon-ok:before {\n content: \"\\e013\";\n}\n.glyphicon-remove:before {\n content: \"\\e014\";\n}\n.glyphicon-zoom-in:before {\n content: \"\\e015\";\n}\n.glyphicon-zoom-out:before {\n content: \"\\e016\";\n}\n.glyphicon-off:before {\n content: \"\\e017\";\n}\n.glyphicon-signal:before {\n content: \"\\e018\";\n}\n.glyphicon-cog:before {\n content: \"\\e019\";\n}\n.glyphicon-trash:before {\n content: \"\\e020\";\n}\n.glyphicon-home:before {\n content: \"\\e021\";\n}\n.glyphicon-file:before {\n content: \"\\e022\";\n}\n.glyphicon-time:before {\n content: \"\\e023\";\n}\n.glyphicon-road:before {\n content: \"\\e024\";\n}\n.glyphicon-download-alt:before {\n content: \"\\e025\";\n}\n.glyphicon-download:before {\n content: \"\\e026\";\n}\n.glyphicon-upload:before {\n content: \"\\e027\";\n}\n.glyphicon-inbox:before {\n content: \"\\e028\";\n}\n.glyphicon-play-circle:before {\n content: \"\\e029\";\n}\n.glyphicon-repeat:before {\n content: \"\\e030\";\n}\n.glyphicon-refresh:before {\n content: \"\\e031\";\n}\n.glyphicon-list-alt:before {\n content: \"\\e032\";\n}\n.glyphicon-lock:before {\n content: \"\\e033\";\n}\n.glyphicon-flag:before {\n content: \"\\e034\";\n}\n.glyphicon-headphones:before {\n content: \"\\e035\";\n}\n.glyphicon-volume-off:before {\n content: \"\\e036\";\n}\n.glyphicon-volume-down:before {\n content: \"\\e037\";\n}\n.glyphicon-volume-up:before {\n content: \"\\e038\";\n}\n.glyphicon-qrcode:before {\n content: \"\\e039\";\n}\n.glyphicon-barcode:before {\n content: \"\\e040\";\n}\n.glyphicon-tag:before {\n content: \"\\e041\";\n}\n.glyphicon-tags:before {\n content: \"\\e042\";\n}\n.glyphicon-book:before {\n content: \"\\e043\";\n}\n.glyphicon-bookmark:before {\n content: \"\\e044\";\n}\n.glyphicon-print:before {\n content: \"\\e045\";\n}\n.glyphicon-camera:before {\n content: \"\\e046\";\n}\n.glyphicon-font:before {\n content: \"\\e047\";\n}\n.glyphicon-bold:before {\n content: \"\\e048\";\n}\n.glyphicon-italic:before {\n content: \"\\e049\";\n}\n.glyphicon-text-height:before {\n content: \"\\e050\";\n}\n.glyphicon-text-width:before {\n content: \"\\e051\";\n}\n.glyphicon-align-left:before {\n content: \"\\e052\";\n}\n.glyphicon-align-center:before {\n content: \"\\e053\";\n}\n.glyphicon-align-right:before {\n content: \"\\e054\";\n}\n.glyphicon-align-justify:before {\n content: \"\\e055\";\n}\n.glyphicon-list:before {\n content: \"\\e056\";\n}\n.glyphicon-indent-left:before {\n content: \"\\e057\";\n}\n.glyphicon-indent-right:before {\n content: \"\\e058\";\n}\n.glyphicon-facetime-video:before {\n content: \"\\e059\";\n}\n.glyphicon-picture:before {\n content: \"\\e060\";\n}\n.glyphicon-map-marker:before {\n content: \"\\e062\";\n}\n.glyphicon-adjust:before {\n content: \"\\e063\";\n}\n.glyphicon-tint:before {\n content: \"\\e064\";\n}\n.glyphicon-edit:before {\n content: \"\\e065\";\n}\n.glyphicon-share:before {\n content: \"\\e066\";\n}\n.glyphicon-check:before {\n content: \"\\e067\";\n}\n.glyphicon-move:before {\n content: \"\\e068\";\n}\n.glyphicon-step-backward:before {\n content: \"\\e069\";\n}\n.glyphicon-fast-backward:before {\n content: \"\\e070\";\n}\n.glyphicon-backward:before {\n content: \"\\e071\";\n}\n.glyphicon-play:before {\n content: \"\\e072\";\n}\n.glyphicon-pause:before {\n content: \"\\e073\";\n}\n.glyphicon-stop:before {\n content: \"\\e074\";\n}\n.glyphicon-forward:before {\n content: \"\\e075\";\n}\n.glyphicon-fast-forward:before {\n content: \"\\e076\";\n}\n.glyphicon-step-forward:before {\n content: \"\\e077\";\n}\n.glyphicon-eject:before {\n content: \"\\e078\";\n}\n.glyphicon-chevron-left:before {\n content: \"\\e079\";\n}\n.glyphicon-chevron-right:before {\n content: \"\\e080\";\n}\n.glyphicon-plus-sign:before {\n content: \"\\e081\";\n}\n.glyphicon-minus-sign:before {\n content: \"\\e082\";\n}\n.glyphicon-remove-sign:before {\n content: \"\\e083\";\n}\n.glyphicon-ok-sign:before {\n content: \"\\e084\";\n}\n.glyphicon-question-sign:before {\n content: \"\\e085\";\n}\n.glyphicon-info-sign:before {\n content: \"\\e086\";\n}\n.glyphicon-screenshot:before {\n content: \"\\e087\";\n}\n.glyphicon-remove-circle:before {\n content: \"\\e088\";\n}\n.glyphicon-ok-circle:before {\n content: \"\\e089\";\n}\n.glyphicon-ban-circle:before {\n content: \"\\e090\";\n}\n.glyphicon-arrow-left:before {\n content: \"\\e091\";\n}\n.glyphicon-arrow-right:before {\n content: \"\\e092\";\n}\n.glyphicon-arrow-up:before {\n content: \"\\e093\";\n}\n.glyphicon-arrow-down:before {\n content: \"\\e094\";\n}\n.glyphicon-share-alt:before {\n content: \"\\e095\";\n}\n.glyphicon-resize-full:before {\n content: \"\\e096\";\n}\n.glyphicon-resize-small:before {\n content: \"\\e097\";\n}\n.glyphicon-exclamation-sign:before {\n content: \"\\e101\";\n}\n.glyphicon-gift:before {\n content: \"\\e102\";\n}\n.glyphicon-leaf:before {\n content: \"\\e103\";\n}\n.glyphicon-fire:before {\n content: \"\\e104\";\n}\n.glyphicon-eye-open:before {\n content: \"\\e105\";\n}\n.glyphicon-eye-close:before {\n content: \"\\e106\";\n}\n.glyphicon-warning-sign:before {\n content: \"\\e107\";\n}\n.glyphicon-plane:before {\n content: \"\\e108\";\n}\n.glyphicon-calendar:before {\n content: \"\\e109\";\n}\n.glyphicon-random:before {\n content: \"\\e110\";\n}\n.glyphicon-comment:before {\n content: \"\\e111\";\n}\n.glyphicon-magnet:before {\n content: \"\\e112\";\n}\n.glyphicon-chevron-up:before {\n content: \"\\e113\";\n}\n.glyphicon-chevron-down:before {\n content: \"\\e114\";\n}\n.glyphicon-retweet:before {\n content: \"\\e115\";\n}\n.glyphicon-shopping-cart:before {\n content: \"\\e116\";\n}\n.glyphicon-folder-close:before {\n content: \"\\e117\";\n}\n.glyphicon-folder-open:before {\n content: \"\\e118\";\n}\n.glyphicon-resize-vertical:before {\n content: \"\\e119\";\n}\n.glyphicon-resize-horizontal:before {\n content: \"\\e120\";\n}\n.glyphicon-hdd:before {\n content: \"\\e121\";\n}\n.glyphicon-bullhorn:before {\n content: \"\\e122\";\n}\n.glyphicon-bell:before {\n content: \"\\e123\";\n}\n.glyphicon-certificate:before {\n content: \"\\e124\";\n}\n.glyphicon-thumbs-up:before {\n content: \"\\e125\";\n}\n.glyphicon-thumbs-down:before {\n content: \"\\e126\";\n}\n.glyphicon-hand-right:before {\n content: \"\\e127\";\n}\n.glyphicon-hand-left:before {\n content: \"\\e128\";\n}\n.glyphicon-hand-up:before {\n content: \"\\e129\";\n}\n.glyphicon-hand-down:before {\n content: \"\\e130\";\n}\n.glyphicon-circle-arrow-right:before {\n content: \"\\e131\";\n}\n.glyphicon-circle-arrow-left:before {\n content: \"\\e132\";\n}\n.glyphicon-circle-arrow-up:before {\n content: \"\\e133\";\n}\n.glyphicon-circle-arrow-down:before {\n content: \"\\e134\";\n}\n.glyphicon-globe:before {\n content: \"\\e135\";\n}\n.glyphicon-wrench:before {\n content: \"\\e136\";\n}\n.glyphicon-tasks:before {\n content: \"\\e137\";\n}\n.glyphicon-filter:before {\n content: \"\\e138\";\n}\n.glyphicon-briefcase:before {\n content: \"\\e139\";\n}\n.glyphicon-fullscreen:before {\n content: \"\\e140\";\n}\n.glyphicon-dashboard:before {\n content: \"\\e141\";\n}\n.glyphicon-paperclip:before {\n content: \"\\e142\";\n}\n.glyphicon-heart-empty:before {\n content: \"\\e143\";\n}\n.glyphicon-link:before {\n content: \"\\e144\";\n}\n.glyphicon-phone:before {\n content: \"\\e145\";\n}\n.glyphicon-pushpin:before {\n content: \"\\e146\";\n}\n.glyphicon-usd:before {\n content: \"\\e148\";\n}\n.glyphicon-gbp:before {\n content: \"\\e149\";\n}\n.glyphicon-sort:before {\n content: \"\\e150\";\n}\n.glyphicon-sort-by-alphabet:before {\n content: \"\\e151\";\n}\n.glyphicon-sort-by-alphabet-alt:before {\n content: \"\\e152\";\n}\n.glyphicon-sort-by-order:before {\n content: \"\\e153\";\n}\n.glyphicon-sort-by-order-alt:before {\n content: \"\\e154\";\n}\n.glyphicon-sort-by-attributes:before {\n content: \"\\e155\";\n}\n.glyphicon-sort-by-attributes-alt:before {\n content: \"\\e156\";\n}\n.glyphicon-unchecked:before {\n content: \"\\e157\";\n}\n.glyphicon-expand:before {\n content: \"\\e158\";\n}\n.glyphicon-collapse-down:before {\n content: \"\\e159\";\n}\n.glyphicon-collapse-up:before {\n content: \"\\e160\";\n}\n.glyphicon-log-in:before {\n content: \"\\e161\";\n}\n.glyphicon-flash:before {\n content: \"\\e162\";\n}\n.glyphicon-log-out:before {\n content: \"\\e163\";\n}\n.glyphicon-new-window:before {\n content: \"\\e164\";\n}\n.glyphicon-record:before {\n content: \"\\e165\";\n}\n.glyphicon-save:before {\n content: \"\\e166\";\n}\n.glyphicon-open:before {\n content: \"\\e167\";\n}\n.glyphicon-saved:before {\n content: \"\\e168\";\n}\n.glyphicon-import:before {\n content: \"\\e169\";\n}\n.glyphicon-export:before {\n content: \"\\e170\";\n}\n.glyphicon-send:before {\n content: \"\\e171\";\n}\n.glyphicon-floppy-disk:before {\n content: \"\\e172\";\n}\n.glyphicon-floppy-saved:before {\n content: \"\\e173\";\n}\n.glyphicon-floppy-remove:before {\n content: \"\\e174\";\n}\n.glyphicon-floppy-save:before {\n content: \"\\e175\";\n}\n.glyphicon-floppy-open:before {\n content: \"\\e176\";\n}\n.glyphicon-credit-card:before {\n content: \"\\e177\";\n}\n.glyphicon-transfer:before {\n content: \"\\e178\";\n}\n.glyphicon-cutlery:before {\n content: \"\\e179\";\n}\n.glyphicon-header:before {\n content: \"\\e180\";\n}\n.glyphicon-compressed:before {\n content: \"\\e181\";\n}\n.glyphicon-earphone:before {\n content: \"\\e182\";\n}\n.glyphicon-phone-alt:before {\n content: \"\\e183\";\n}\n.glyphicon-tower:before {\n content: \"\\e184\";\n}\n.glyphicon-stats:before {\n content: \"\\e185\";\n}\n.glyphicon-sd-video:before {\n content: \"\\e186\";\n}\n.glyphicon-hd-video:before {\n content: \"\\e187\";\n}\n.glyphicon-subtitles:before {\n content: \"\\e188\";\n}\n.glyphicon-sound-stereo:before {\n content: \"\\e189\";\n}\n.glyphicon-sound-dolby:before {\n content: \"\\e190\";\n}\n.glyphicon-sound-5-1:before {\n content: \"\\e191\";\n}\n.glyphicon-sound-6-1:before {\n content: \"\\e192\";\n}\n.glyphicon-sound-7-1:before {\n content: \"\\e193\";\n}\n.glyphicon-copyright-mark:before {\n content: \"\\e194\";\n}\n.glyphicon-registration-mark:before {\n content: \"\\e195\";\n}\n.glyphicon-cloud-download:before {\n content: \"\\e197\";\n}\n.glyphicon-cloud-upload:before {\n content: \"\\e198\";\n}\n.glyphicon-tree-conifer:before {\n content: \"\\e199\";\n}\n.glyphicon-tree-deciduous:before {\n content: \"\\e200\";\n}\n.glyphicon-cd:before {\n content: \"\\e201\";\n}\n.glyphicon-save-file:before {\n content: \"\\e202\";\n}\n.glyphicon-open-file:before {\n content: \"\\e203\";\n}\n.glyphicon-level-up:before {\n content: \"\\e204\";\n}\n.glyphicon-copy:before {\n content: \"\\e205\";\n}\n.glyphicon-paste:before {\n content: \"\\e206\";\n}\n.glyphicon-alert:before {\n content: \"\\e209\";\n}\n.glyphicon-equalizer:before {\n content: \"\\e210\";\n}\n.glyphicon-king:before {\n content: \"\\e211\";\n}\n.glyphicon-queen:before {\n content: \"\\e212\";\n}\n.glyphicon-pawn:before {\n content: \"\\e213\";\n}\n.glyphicon-bishop:before {\n content: \"\\e214\";\n}\n.glyphicon-knight:before {\n content: \"\\e215\";\n}\n.glyphicon-baby-formula:before {\n content: \"\\e216\";\n}\n.glyphicon-tent:before {\n content: \"\\26fa\";\n}\n.glyphicon-blackboard:before {\n content: \"\\e218\";\n}\n.glyphicon-bed:before {\n content: \"\\e219\";\n}\n.glyphicon-apple:before {\n content: \"\\f8ff\";\n}\n.glyphicon-erase:before {\n content: \"\\e221\";\n}\n.glyphicon-hourglass:before {\n content: \"\\231b\";\n}\n.glyphicon-lamp:before {\n content: \"\\e223\";\n}\n.glyphicon-duplicate:before {\n content: \"\\e224\";\n}\n.glyphicon-piggy-bank:before {\n content: \"\\e225\";\n}\n.glyphicon-scissors:before {\n content: \"\\e226\";\n}\n.glyphicon-bitcoin:before {\n content: \"\\e227\";\n}\n.glyphicon-btc:before {\n content: \"\\e227\";\n}\n.glyphicon-xbt:before {\n content: \"\\e227\";\n}\n.glyphicon-yen:before {\n content: \"\\00a5\";\n}\n.glyphicon-jpy:before {\n content: \"\\00a5\";\n}\n.glyphicon-ruble:before {\n content: \"\\20bd\";\n}\n.glyphicon-rub:before {\n content: \"\\20bd\";\n}\n.glyphicon-scale:before {\n content: \"\\e230\";\n}\n.glyphicon-ice-lolly:before {\n content: \"\\e231\";\n}\n.glyphicon-ice-lolly-tasted:before {\n content: \"\\e232\";\n}\n.glyphicon-education:before {\n content: \"\\e233\";\n}\n.glyphicon-option-horizontal:before {\n content: \"\\e234\";\n}\n.glyphicon-option-vertical:before {\n content: \"\\e235\";\n}\n.glyphicon-menu-hamburger:before {\n content: \"\\e236\";\n}\n.glyphicon-modal-window:before {\n content: \"\\e237\";\n}\n.glyphicon-oil:before {\n content: \"\\e238\";\n}\n.glyphicon-grain:before {\n content: \"\\e239\";\n}\n.glyphicon-sunglasses:before {\n content: \"\\e240\";\n}\n.glyphicon-text-size:before {\n content: \"\\e241\";\n}\n.glyphicon-text-color:before {\n content: \"\\e242\";\n}\n.glyphicon-text-background:before {\n content: \"\\e243\";\n}\n.glyphicon-object-align-top:before {\n content: \"\\e244\";\n}\n.glyphicon-object-align-bottom:before {\n content: \"\\e245\";\n}\n.glyphicon-object-align-horizontal:before {\n content: \"\\e246\";\n}\n.glyphicon-object-align-left:before {\n content: \"\\e247\";\n}\n.glyphicon-object-align-vertical:before {\n content: \"\\e248\";\n}\n.glyphicon-object-align-right:before {\n content: \"\\e249\";\n}\n.glyphicon-triangle-right:before {\n content: \"\\e250\";\n}\n.glyphicon-triangle-left:before {\n content: \"\\e251\";\n}\n.glyphicon-triangle-bottom:before {\n content: \"\\e252\";\n}\n.glyphicon-triangle-top:before {\n content: \"\\e253\";\n}\n.glyphicon-console:before {\n content: \"\\e254\";\n}\n.glyphicon-superscript:before {\n content: \"\\e255\";\n}\n.glyphicon-subscript:before {\n content: \"\\e256\";\n}\n.glyphicon-menu-left:before {\n content: \"\\e257\";\n}\n.glyphicon-menu-right:before {\n content: \"\\e258\";\n}\n.glyphicon-menu-down:before {\n content: \"\\e259\";\n}\n.glyphicon-menu-up:before {\n content: \"\\e260\";\n}\n* {\n -webkit-box-sizing: border-box;\n -moz-box-sizing: border-box;\n box-sizing: border-box;\n}\n*:before,\n*:after {\n -webkit-box-sizing: border-box;\n -moz-box-sizing: border-box;\n box-sizing: border-box;\n}\nhtml {\n font-size: 10px;\n -webkit-tap-highlight-color: rgba(0, 0, 0, 0);\n}\nbody {\n font-family: \"Helvetica Neue\", Helvetica, Arial, sans-serif;\n font-size: 14px;\n line-height: 1.42857143;\n color: #333333;\n background-color: #fff;\n}\ninput,\nbutton,\nselect,\ntextarea {\n font-family: inherit;\n font-size: inherit;\n line-height: inherit;\n}\na {\n color: #337ab7;\n text-decoration: none;\n}\na:hover,\na:focus {\n color: #23527c;\n text-decoration: underline;\n}\na:focus {\n outline: 5px auto -webkit-focus-ring-color;\n outline-offset: -2px;\n}\nfigure {\n margin: 0;\n}\nimg {\n vertical-align: middle;\n}\n.img-responsive,\n.thumbnail > img,\n.thumbnail a > img,\n.carousel-inner > .item > img,\n.carousel-inner > .item > a > img {\n display: block;\n max-width: 100%;\n height: auto;\n}\n.img-rounded {\n border-radius: 6px;\n}\n.img-thumbnail {\n padding: 4px;\n line-height: 1.42857143;\n background-color: #fff;\n border: 1px solid #ddd;\n border-radius: 4px;\n -webkit-transition: all 0.2s ease-in-out;\n -o-transition: all 0.2s ease-in-out;\n transition: all 0.2s ease-in-out;\n display: inline-block;\n max-width: 100%;\n height: auto;\n}\n.img-circle {\n border-radius: 50%;\n}\nhr {\n margin-top: 20px;\n margin-bottom: 20px;\n border: 0;\n border-top: 1px solid #eeeeee;\n}\n.sr-only {\n position: absolute;\n width: 1px;\n height: 1px;\n margin: -1px;\n padding: 0;\n overflow: hidden;\n clip: rect(0, 0, 0, 0);\n border: 0;\n}\n.sr-only-focusable:active,\n.sr-only-focusable:focus {\n position: static;\n width: auto;\n height: auto;\n margin: 0;\n overflow: visible;\n clip: auto;\n}\n[role=\"button\"] {\n cursor: pointer;\n}\nh1,\nh2,\nh3,\nh4,\nh5,\nh6,\n.h1,\n.h2,\n.h3,\n.h4,\n.h5,\n.h6 {\n font-family: inherit;\n font-weight: 500;\n line-height: 1.1;\n color: inherit;\n}\nh1 small,\nh2 small,\nh3 small,\nh4 small,\nh5 small,\nh6 small,\n.h1 small,\n.h2 small,\n.h3 small,\n.h4 small,\n.h5 small,\n.h6 small,\nh1 .small,\nh2 .small,\nh3 .small,\nh4 .small,\nh5 .small,\nh6 .small,\n.h1 .small,\n.h2 .small,\n.h3 .small,\n.h4 .small,\n.h5 .small,\n.h6 .small {\n font-weight: normal;\n line-height: 1;\n color: #777777;\n}\nh1,\n.h1,\nh2,\n.h2,\nh3,\n.h3 {\n margin-top: 20px;\n margin-bottom: 10px;\n}\nh1 small,\n.h1 small,\nh2 small,\n.h2 small,\nh3 small,\n.h3 small,\nh1 .small,\n.h1 .small,\nh2 .small,\n.h2 .small,\nh3 .small,\n.h3 .small {\n font-size: 65%;\n}\nh4,\n.h4,\nh5,\n.h5,\nh6,\n.h6 {\n margin-top: 10px;\n margin-bottom: 10px;\n}\nh4 small,\n.h4 small,\nh5 small,\n.h5 small,\nh6 small,\n.h6 small,\nh4 .small,\n.h4 .small,\nh5 .small,\n.h5 .small,\nh6 .small,\n.h6 .small {\n font-size: 75%;\n}\nh1,\n.h1 {\n font-size: 36px;\n}\nh2,\n.h2 {\n font-size: 30px;\n}\nh3,\n.h3 {\n font-size: 24px;\n}\nh4,\n.h4 {\n font-size: 18px;\n}\nh5,\n.h5 {\n font-size: 14px;\n}\nh6,\n.h6 {\n font-size: 12px;\n}\np {\n margin: 0 0 10px;\n}\n.lead {\n margin-bottom: 20px;\n font-size: 16px;\n font-weight: 300;\n line-height: 1.4;\n}\n@media (min-width: 768px) {\n .lead {\n font-size: 21px;\n }\n}\nsmall,\n.small {\n font-size: 85%;\n}\nmark,\n.mark {\n background-color: #fcf8e3;\n padding: .2em;\n}\n.text-left {\n text-align: left;\n}\n.text-right {\n text-align: right;\n}\n.text-center {\n text-align: center;\n}\n.text-justify {\n text-align: justify;\n}\n.text-nowrap {\n white-space: nowrap;\n}\n.text-lowercase {\n text-transform: lowercase;\n}\n.text-uppercase {\n text-transform: uppercase;\n}\n.text-capitalize {\n text-transform: capitalize;\n}\n.text-muted {\n color: #777777;\n}\n.text-primary {\n color: #337ab7;\n}\na.text-primary:hover,\na.text-primary:focus {\n color: #286090;\n}\n.text-success {\n color: #3c763d;\n}\na.text-success:hover,\na.text-success:focus {\n color: #2b542c;\n}\n.text-info {\n color: #31708f;\n}\na.text-info:hover,\na.text-info:focus {\n color: #245269;\n}\n.text-warning {\n color: #8a6d3b;\n}\na.text-warning:hover,\na.text-warning:focus {\n color: #66512c;\n}\n.text-danger {\n color: #a94442;\n}\na.text-danger:hover,\na.text-danger:focus {\n color: #843534;\n}\n.bg-primary {\n color: #fff;\n background-color: #337ab7;\n}\na.bg-primary:hover,\na.bg-primary:focus {\n background-color: #286090;\n}\n.bg-success {\n background-color: #dff0d8;\n}\na.bg-success:hover,\na.bg-success:focus {\n background-color: #c1e2b3;\n}\n.bg-info {\n background-color: #d9edf7;\n}\na.bg-info:hover,\na.bg-info:focus {\n background-color: #afd9ee;\n}\n.bg-warning {\n background-color: #fcf8e3;\n}\na.bg-warning:hover,\na.bg-warning:focus {\n background-color: #f7ecb5;\n}\n.bg-danger {\n background-color: #f2dede;\n}\na.bg-danger:hover,\na.bg-danger:focus {\n background-color: #e4b9b9;\n}\n.page-header {\n padding-bottom: 9px;\n margin: 40px 0 20px;\n border-bottom: 1px solid #eeeeee;\n}\nul,\nol {\n margin-top: 0;\n margin-bottom: 10px;\n}\nul ul,\nol ul,\nul ol,\nol ol {\n margin-bottom: 0;\n}\n.list-unstyled {\n padding-left: 0;\n list-style: none;\n}\n.list-inline {\n padding-left: 0;\n list-style: none;\n margin-left: -5px;\n}\n.list-inline > li {\n display: inline-block;\n padding-left: 5px;\n padding-right: 5px;\n}\ndl {\n margin-top: 0;\n margin-bottom: 20px;\n}\ndt,\ndd {\n line-height: 1.42857143;\n}\ndt {\n font-weight: bold;\n}\ndd {\n margin-left: 0;\n}\n@media (min-width: 768px) {\n .dl-horizontal dt {\n float: left;\n width: 160px;\n clear: left;\n text-align: right;\n overflow: hidden;\n text-overflow: ellipsis;\n white-space: nowrap;\n }\n .dl-horizontal dd {\n margin-left: 180px;\n }\n}\nabbr[title],\nabbr[data-original-title] {\n cursor: help;\n border-bottom: 1px dotted #777777;\n}\n.initialism {\n font-size: 90%;\n text-transform: uppercase;\n}\nblockquote {\n padding: 10px 20px;\n margin: 0 0 20px;\n font-size: 17.5px;\n border-left: 5px solid #eeeeee;\n}\nblockquote p:last-child,\nblockquote ul:last-child,\nblockquote ol:last-child {\n margin-bottom: 0;\n}\nblockquote footer,\nblockquote small,\nblockquote .small {\n display: block;\n font-size: 80%;\n line-height: 1.42857143;\n color: #777777;\n}\nblockquote footer:before,\nblockquote small:before,\nblockquote .small:before {\n content: '\\2014 \\00A0';\n}\n.blockquote-reverse,\nblockquote.pull-right {\n padding-right: 15px;\n padding-left: 0;\n border-right: 5px solid #eeeeee;\n border-left: 0;\n text-align: right;\n}\n.blockquote-reverse footer:before,\nblockquote.pull-right footer:before,\n.blockquote-reverse small:before,\nblockquote.pull-right small:before,\n.blockquote-reverse .small:before,\nblockquote.pull-right .small:before {\n content: '';\n}\n.blockquote-reverse footer:after,\nblockquote.pull-right footer:after,\n.blockquote-reverse small:after,\nblockquote.pull-right small:after,\n.blockquote-reverse .small:after,\nblockquote.pull-right .small:after {\n content: '\\00A0 \\2014';\n}\naddress {\n margin-bottom: 20px;\n font-style: normal;\n line-height: 1.42857143;\n}\ncode,\nkbd,\npre,\nsamp {\n font-family: Menlo, Monaco, Consolas, \"Courier New\", monospace;\n}\ncode {\n padding: 2px 4px;\n font-size: 90%;\n color: #c7254e;\n background-color: #f9f2f4;\n border-radius: 4px;\n}\nkbd {\n padding: 2px 4px;\n font-size: 90%;\n color: #fff;\n background-color: #333;\n border-radius: 3px;\n box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.25);\n}\nkbd kbd {\n padding: 0;\n font-size: 100%;\n font-weight: bold;\n box-shadow: none;\n}\npre {\n display: block;\n padding: 9.5px;\n margin: 0 0 10px;\n font-size: 13px;\n line-height: 1.42857143;\n word-break: break-all;\n word-wrap: break-word;\n color: #333333;\n background-color: #f5f5f5;\n border: 1px solid #ccc;\n border-radius: 4px;\n}\npre code {\n padding: 0;\n font-size: inherit;\n color: inherit;\n white-space: pre-wrap;\n background-color: transparent;\n border-radius: 0;\n}\n.pre-scrollable {\n max-height: 340px;\n overflow-y: scroll;\n}\n.container {\n margin-right: auto;\n margin-left: auto;\n padding-left: 15px;\n padding-right: 15px;\n}\n@media (min-width: 768px) {\n .container {\n width: 750px;\n }\n}\n@media (min-width: 992px) {\n .container {\n width: 970px;\n }\n}\n@media (min-width: 1200px) {\n .container {\n width: 1170px;\n }\n}\n.container-fluid {\n margin-right: auto;\n margin-left: auto;\n padding-left: 15px;\n padding-right: 15px;\n}\n.row {\n margin-left: -15px;\n margin-right: -15px;\n}\n.col-xs-1, .col-sm-1, .col-md-1, .col-lg-1, .col-xs-2, .col-sm-2, .col-md-2, .col-lg-2, .col-xs-3, .col-sm-3, .col-md-3, .col-lg-3, .col-xs-4, .col-sm-4, .col-md-4, .col-lg-4, .col-xs-5, .col-sm-5, .col-md-5, .col-lg-5, .col-xs-6, .col-sm-6, .col-md-6, .col-lg-6, .col-xs-7, .col-sm-7, .col-md-7, .col-lg-7, .col-xs-8, .col-sm-8, .col-md-8, .col-lg-8, .col-xs-9, .col-sm-9, .col-md-9, .col-lg-9, .col-xs-10, .col-sm-10, .col-md-10, .col-lg-10, .col-xs-11, .col-sm-11, .col-md-11, .col-lg-11, .col-xs-12, .col-sm-12, .col-md-12, .col-lg-12 {\n position: relative;\n min-height: 1px;\n padding-left: 15px;\n padding-right: 15px;\n}\n.col-xs-1, .col-xs-2, .col-xs-3, .col-xs-4, .col-xs-5, .col-xs-6, .col-xs-7, .col-xs-8, .col-xs-9, .col-xs-10, .col-xs-11, .col-xs-12 {\n float: left;\n}\n.col-xs-12 {\n width: 100%;\n}\n.col-xs-11 {\n width: 91.66666667%;\n}\n.col-xs-10 {\n width: 83.33333333%;\n}\n.col-xs-9 {\n width: 75%;\n}\n.col-xs-8 {\n width: 66.66666667%;\n}\n.col-xs-7 {\n width: 58.33333333%;\n}\n.col-xs-6 {\n width: 50%;\n}\n.col-xs-5 {\n width: 41.66666667%;\n}\n.col-xs-4 {\n width: 33.33333333%;\n}\n.col-xs-3 {\n width: 25%;\n}\n.col-xs-2 {\n width: 16.66666667%;\n}\n.col-xs-1 {\n width: 8.33333333%;\n}\n.col-xs-pull-12 {\n right: 100%;\n}\n.col-xs-pull-11 {\n right: 91.66666667%;\n}\n.col-xs-pull-10 {\n right: 83.33333333%;\n}\n.col-xs-pull-9 {\n right: 75%;\n}\n.col-xs-pull-8 {\n right: 66.66666667%;\n}\n.col-xs-pull-7 {\n right: 58.33333333%;\n}\n.col-xs-pull-6 {\n right: 50%;\n}\n.col-xs-pull-5 {\n right: 41.66666667%;\n}\n.col-xs-pull-4 {\n right: 33.33333333%;\n}\n.col-xs-pull-3 {\n right: 25%;\n}\n.col-xs-pull-2 {\n right: 16.66666667%;\n}\n.col-xs-pull-1 {\n right: 8.33333333%;\n}\n.col-xs-pull-0 {\n right: auto;\n}\n.col-xs-push-12 {\n left: 100%;\n}\n.col-xs-push-11 {\n left: 91.66666667%;\n}\n.col-xs-push-10 {\n left: 83.33333333%;\n}\n.col-xs-push-9 {\n left: 75%;\n}\n.col-xs-push-8 {\n left: 66.66666667%;\n}\n.col-xs-push-7 {\n left: 58.33333333%;\n}\n.col-xs-push-6 {\n left: 50%;\n}\n.col-xs-push-5 {\n left: 41.66666667%;\n}\n.col-xs-push-4 {\n left: 33.33333333%;\n}\n.col-xs-push-3 {\n left: 25%;\n}\n.col-xs-push-2 {\n left: 16.66666667%;\n}\n.col-xs-push-1 {\n left: 8.33333333%;\n}\n.col-xs-push-0 {\n left: auto;\n}\n.col-xs-offset-12 {\n margin-left: 100%;\n}\n.col-xs-offset-11 {\n margin-left: 91.66666667%;\n}\n.col-xs-offset-10 {\n margin-left: 83.33333333%;\n}\n.col-xs-offset-9 {\n margin-left: 75%;\n}\n.col-xs-offset-8 {\n margin-left: 66.66666667%;\n}\n.col-xs-offset-7 {\n margin-left: 58.33333333%;\n}\n.col-xs-offset-6 {\n margin-left: 50%;\n}\n.col-xs-offset-5 {\n margin-left: 41.66666667%;\n}\n.col-xs-offset-4 {\n margin-left: 33.33333333%;\n}\n.col-xs-offset-3 {\n margin-left: 25%;\n}\n.col-xs-offset-2 {\n margin-left: 16.66666667%;\n}\n.col-xs-offset-1 {\n margin-left: 8.33333333%;\n}\n.col-xs-offset-0 {\n margin-left: 0%;\n}\n@media (min-width: 768px) {\n .col-sm-1, .col-sm-2, .col-sm-3, .col-sm-4, .col-sm-5, .col-sm-6, .col-sm-7, .col-sm-8, .col-sm-9, .col-sm-10, .col-sm-11, .col-sm-12 {\n float: left;\n }\n .col-sm-12 {\n width: 100%;\n }\n .col-sm-11 {\n width: 91.66666667%;\n }\n .col-sm-10 {\n width: 83.33333333%;\n }\n .col-sm-9 {\n width: 75%;\n }\n .col-sm-8 {\n width: 66.66666667%;\n }\n .col-sm-7 {\n width: 58.33333333%;\n }\n .col-sm-6 {\n width: 50%;\n }\n .col-sm-5 {\n width: 41.66666667%;\n }\n .col-sm-4 {\n width: 33.33333333%;\n }\n .col-sm-3 {\n width: 25%;\n }\n .col-sm-2 {\n width: 16.66666667%;\n }\n .col-sm-1 {\n width: 8.33333333%;\n }\n .col-sm-pull-12 {\n right: 100%;\n }\n .col-sm-pull-11 {\n right: 91.66666667%;\n }\n .col-sm-pull-10 {\n right: 83.33333333%;\n }\n .col-sm-pull-9 {\n right: 75%;\n }\n .col-sm-pull-8 {\n right: 66.66666667%;\n }\n .col-sm-pull-7 {\n right: 58.33333333%;\n }\n .col-sm-pull-6 {\n right: 50%;\n }\n .col-sm-pull-5 {\n right: 41.66666667%;\n }\n .col-sm-pull-4 {\n right: 33.33333333%;\n }\n .col-sm-pull-3 {\n right: 25%;\n }\n .col-sm-pull-2 {\n right: 16.66666667%;\n }\n .col-sm-pull-1 {\n right: 8.33333333%;\n }\n .col-sm-pull-0 {\n right: auto;\n }\n .col-sm-push-12 {\n left: 100%;\n }\n .col-sm-push-11 {\n left: 91.66666667%;\n }\n .col-sm-push-10 {\n left: 83.33333333%;\n }\n .col-sm-push-9 {\n left: 75%;\n }\n .col-sm-push-8 {\n left: 66.66666667%;\n }\n .col-sm-push-7 {\n left: 58.33333333%;\n }\n .col-sm-push-6 {\n left: 50%;\n }\n .col-sm-push-5 {\n left: 41.66666667%;\n }\n .col-sm-push-4 {\n left: 33.33333333%;\n }\n .col-sm-push-3 {\n left: 25%;\n }\n .col-sm-push-2 {\n left: 16.66666667%;\n }\n .col-sm-push-1 {\n left: 8.33333333%;\n }\n .col-sm-push-0 {\n left: auto;\n }\n .col-sm-offset-12 {\n margin-left: 100%;\n }\n .col-sm-offset-11 {\n margin-left: 91.66666667%;\n }\n .col-sm-offset-10 {\n margin-left: 83.33333333%;\n }\n .col-sm-offset-9 {\n margin-left: 75%;\n }\n .col-sm-offset-8 {\n margin-left: 66.66666667%;\n }\n .col-sm-offset-7 {\n margin-left: 58.33333333%;\n }\n .col-sm-offset-6 {\n margin-left: 50%;\n }\n .col-sm-offset-5 {\n margin-left: 41.66666667%;\n }\n .col-sm-offset-4 {\n margin-left: 33.33333333%;\n }\n .col-sm-offset-3 {\n margin-left: 25%;\n }\n .col-sm-offset-2 {\n margin-left: 16.66666667%;\n }\n .col-sm-offset-1 {\n margin-left: 8.33333333%;\n }\n .col-sm-offset-0 {\n margin-left: 0%;\n }\n}\n@media (min-width: 992px) {\n .col-md-1, .col-md-2, .col-md-3, .col-md-4, .col-md-5, .col-md-6, .col-md-7, .col-md-8, .col-md-9, .col-md-10, .col-md-11, .col-md-12 {\n float: left;\n }\n .col-md-12 {\n width: 100%;\n }\n .col-md-11 {\n width: 91.66666667%;\n }\n .col-md-10 {\n width: 83.33333333%;\n }\n .col-md-9 {\n width: 75%;\n }\n .col-md-8 {\n width: 66.66666667%;\n }\n .col-md-7 {\n width: 58.33333333%;\n }\n .col-md-6 {\n width: 50%;\n }\n .col-md-5 {\n width: 41.66666667%;\n }\n .col-md-4 {\n width: 33.33333333%;\n }\n .col-md-3 {\n width: 25%;\n }\n .col-md-2 {\n width: 16.66666667%;\n }\n .col-md-1 {\n width: 8.33333333%;\n }\n .col-md-pull-12 {\n right: 100%;\n }\n .col-md-pull-11 {\n right: 91.66666667%;\n }\n .col-md-pull-10 {\n right: 83.33333333%;\n }\n .col-md-pull-9 {\n right: 75%;\n }\n .col-md-pull-8 {\n right: 66.66666667%;\n }\n .col-md-pull-7 {\n right: 58.33333333%;\n }\n .col-md-pull-6 {\n right: 50%;\n }\n .col-md-pull-5 {\n right: 41.66666667%;\n }\n .col-md-pull-4 {\n right: 33.33333333%;\n }\n .col-md-pull-3 {\n right: 25%;\n }\n .col-md-pull-2 {\n right: 16.66666667%;\n }\n .col-md-pull-1 {\n right: 8.33333333%;\n }\n .col-md-pull-0 {\n right: auto;\n }\n .col-md-push-12 {\n left: 100%;\n }\n .col-md-push-11 {\n left: 91.66666667%;\n }\n .col-md-push-10 {\n left: 83.33333333%;\n }\n .col-md-push-9 {\n left: 75%;\n }\n .col-md-push-8 {\n left: 66.66666667%;\n }\n .col-md-push-7 {\n left: 58.33333333%;\n }\n .col-md-push-6 {\n left: 50%;\n }\n .col-md-push-5 {\n left: 41.66666667%;\n }\n .col-md-push-4 {\n left: 33.33333333%;\n }\n .col-md-push-3 {\n left: 25%;\n }\n .col-md-push-2 {\n left: 16.66666667%;\n }\n .col-md-push-1 {\n left: 8.33333333%;\n }\n .col-md-push-0 {\n left: auto;\n }\n .col-md-offset-12 {\n margin-left: 100%;\n }\n .col-md-offset-11 {\n margin-left: 91.66666667%;\n }\n .col-md-offset-10 {\n margin-left: 83.33333333%;\n }\n .col-md-offset-9 {\n margin-left: 75%;\n }\n .col-md-offset-8 {\n margin-left: 66.66666667%;\n }\n .col-md-offset-7 {\n margin-left: 58.33333333%;\n }\n .col-md-offset-6 {\n margin-left: 50%;\n }\n .col-md-offset-5 {\n margin-left: 41.66666667%;\n }\n .col-md-offset-4 {\n margin-left: 33.33333333%;\n }\n .col-md-offset-3 {\n margin-left: 25%;\n }\n .col-md-offset-2 {\n margin-left: 16.66666667%;\n }\n .col-md-offset-1 {\n margin-left: 8.33333333%;\n }\n .col-md-offset-0 {\n margin-left: 0%;\n }\n}\n@media (min-width: 1200px) {\n .col-lg-1, .col-lg-2, .col-lg-3, .col-lg-4, .col-lg-5, .col-lg-6, .col-lg-7, .col-lg-8, .col-lg-9, .col-lg-10, .col-lg-11, .col-lg-12 {\n float: left;\n }\n .col-lg-12 {\n width: 100%;\n }\n .col-lg-11 {\n width: 91.66666667%;\n }\n .col-lg-10 {\n width: 83.33333333%;\n }\n .col-lg-9 {\n width: 75%;\n }\n .col-lg-8 {\n width: 66.66666667%;\n }\n .col-lg-7 {\n width: 58.33333333%;\n }\n .col-lg-6 {\n width: 50%;\n }\n .col-lg-5 {\n width: 41.66666667%;\n }\n .col-lg-4 {\n width: 33.33333333%;\n }\n .col-lg-3 {\n width: 25%;\n }\n .col-lg-2 {\n width: 16.66666667%;\n }\n .col-lg-1 {\n width: 8.33333333%;\n }\n .col-lg-pull-12 {\n right: 100%;\n }\n .col-lg-pull-11 {\n right: 91.66666667%;\n }\n .col-lg-pull-10 {\n right: 83.33333333%;\n }\n .col-lg-pull-9 {\n right: 75%;\n }\n .col-lg-pull-8 {\n right: 66.66666667%;\n }\n .col-lg-pull-7 {\n right: 58.33333333%;\n }\n .col-lg-pull-6 {\n right: 50%;\n }\n .col-lg-pull-5 {\n right: 41.66666667%;\n }\n .col-lg-pull-4 {\n right: 33.33333333%;\n }\n .col-lg-pull-3 {\n right: 25%;\n }\n .col-lg-pull-2 {\n right: 16.66666667%;\n }\n .col-lg-pull-1 {\n right: 8.33333333%;\n }\n .col-lg-pull-0 {\n right: auto;\n }\n .col-lg-push-12 {\n left: 100%;\n }\n .col-lg-push-11 {\n left: 91.66666667%;\n }\n .col-lg-push-10 {\n left: 83.33333333%;\n }\n .col-lg-push-9 {\n left: 75%;\n }\n .col-lg-push-8 {\n left: 66.66666667%;\n }\n .col-lg-push-7 {\n left: 58.33333333%;\n }\n .col-lg-push-6 {\n left: 50%;\n }\n .col-lg-push-5 {\n left: 41.66666667%;\n }\n .col-lg-push-4 {\n left: 33.33333333%;\n }\n .col-lg-push-3 {\n left: 25%;\n }\n .col-lg-push-2 {\n left: 16.66666667%;\n }\n .col-lg-push-1 {\n left: 8.33333333%;\n }\n .col-lg-push-0 {\n left: auto;\n }\n .col-lg-offset-12 {\n margin-left: 100%;\n }\n .col-lg-offset-11 {\n margin-left: 91.66666667%;\n }\n .col-lg-offset-10 {\n margin-left: 83.33333333%;\n }\n .col-lg-offset-9 {\n margin-left: 75%;\n }\n .col-lg-offset-8 {\n margin-left: 66.66666667%;\n }\n .col-lg-offset-7 {\n margin-left: 58.33333333%;\n }\n .col-lg-offset-6 {\n margin-left: 50%;\n }\n .col-lg-offset-5 {\n margin-left: 41.66666667%;\n }\n .col-lg-offset-4 {\n margin-left: 33.33333333%;\n }\n .col-lg-offset-3 {\n margin-left: 25%;\n }\n .col-lg-offset-2 {\n margin-left: 16.66666667%;\n }\n .col-lg-offset-1 {\n margin-left: 8.33333333%;\n }\n .col-lg-offset-0 {\n margin-left: 0%;\n }\n}\ntable {\n background-color: transparent;\n}\ncaption {\n padding-top: 8px;\n padding-bottom: 8px;\n color: #777777;\n text-align: left;\n}\nth {\n text-align: left;\n}\n.table {\n width: 100%;\n max-width: 100%;\n margin-bottom: 20px;\n}\n.table > thead > tr > th,\n.table > tbody > tr > th,\n.table > tfoot > tr > th,\n.table > thead > tr > td,\n.table > tbody > tr > td,\n.table > tfoot > tr > td {\n padding: 8px;\n line-height: 1.42857143;\n vertical-align: top;\n border-top: 1px solid #ddd;\n}\n.table > thead > tr > th {\n vertical-align: bottom;\n border-bottom: 2px solid #ddd;\n}\n.table > caption + thead > tr:first-child > th,\n.table > colgroup + thead > tr:first-child > th,\n.table > thead:first-child > tr:first-child > th,\n.table > caption + thead > tr:first-child > td,\n.table > colgroup + thead > tr:first-child > td,\n.table > thead:first-child > tr:first-child > td {\n border-top: 0;\n}\n.table > tbody + tbody {\n border-top: 2px solid #ddd;\n}\n.table .table {\n background-color: #fff;\n}\n.table-condensed > thead > tr > th,\n.table-condensed > tbody > tr > th,\n.table-condensed > tfoot > tr > th,\n.table-condensed > thead > tr > td,\n.table-condensed > tbody > tr > td,\n.table-condensed > tfoot > tr > td {\n padding: 5px;\n}\n.table-bordered {\n border: 1px solid #ddd;\n}\n.table-bordered > thead > tr > th,\n.table-bordered > tbody > tr > th,\n.table-bordered > tfoot > tr > th,\n.table-bordered > thead > tr > td,\n.table-bordered > tbody > tr > td,\n.table-bordered > tfoot > tr > td {\n border: 1px solid #ddd;\n}\n.table-bordered > thead > tr > th,\n.table-bordered > thead > tr > td {\n border-bottom-width: 2px;\n}\n.table-striped > tbody > tr:nth-of-type(odd) {\n background-color: #f9f9f9;\n}\n.table-hover > tbody > tr:hover {\n background-color: #f5f5f5;\n}\ntable col[class*=\"col-\"] {\n position: static;\n float: none;\n display: table-column;\n}\ntable td[class*=\"col-\"],\ntable th[class*=\"col-\"] {\n position: static;\n float: none;\n display: table-cell;\n}\n.table > thead > tr > td.active,\n.table > tbody > tr > td.active,\n.table > tfoot > tr > td.active,\n.table > thead > tr > th.active,\n.table > tbody > tr > th.active,\n.table > tfoot > tr > th.active,\n.table > thead > tr.active > td,\n.table > tbody > tr.active > td,\n.table > tfoot > tr.active > td,\n.table > thead > tr.active > th,\n.table > tbody > tr.active > th,\n.table > tfoot > tr.active > th {\n background-color: #f5f5f5;\n}\n.table-hover > tbody > tr > td.active:hover,\n.table-hover > tbody > tr > th.active:hover,\n.table-hover > tbody > tr.active:hover > td,\n.table-hover > tbody > tr:hover > .active,\n.table-hover > tbody > tr.active:hover > th {\n background-color: #e8e8e8;\n}\n.table > thead > tr > td.success,\n.table > tbody > tr > td.success,\n.table > tfoot > tr > td.success,\n.table > thead > tr > th.success,\n.table > tbody > tr > th.success,\n.table > tfoot > tr > th.success,\n.table > thead > tr.success > td,\n.table > tbody > tr.success > td,\n.table > tfoot > tr.success > td,\n.table > thead > tr.success > th,\n.table > tbody > tr.success > th,\n.table > tfoot > tr.success > th {\n background-color: #dff0d8;\n}\n.table-hover > tbody > tr > td.success:hover,\n.table-hover > tbody > tr > th.success:hover,\n.table-hover > tbody > tr.success:hover > td,\n.table-hover > tbody > tr:hover > .success,\n.table-hover > tbody > tr.success:hover > th {\n background-color: #d0e9c6;\n}\n.table > thead > tr > td.info,\n.table > tbody > tr > td.info,\n.table > tfoot > tr > td.info,\n.table > thead > tr > th.info,\n.table > tbody > tr > th.info,\n.table > tfoot > tr > th.info,\n.table > thead > tr.info > td,\n.table > tbody > tr.info > td,\n.table > tfoot > tr.info > td,\n.table > thead > tr.info > th,\n.table > tbody > tr.info > th,\n.table > tfoot > tr.info > th {\n background-color: #d9edf7;\n}\n.table-hover > tbody > tr > td.info:hover,\n.table-hover > tbody > tr > th.info:hover,\n.table-hover > tbody > tr.info:hover > td,\n.table-hover > tbody > tr:hover > .info,\n.table-hover > tbody > tr.info:hover > th {\n background-color: #c4e3f3;\n}\n.table > thead > tr > td.warning,\n.table > tbody > tr > td.warning,\n.table > tfoot > tr > td.warning,\n.table > thead > tr > th.warning,\n.table > tbody > tr > th.warning,\n.table > tfoot > tr > th.warning,\n.table > thead > tr.warning > td,\n.table > tbody > tr.warning > td,\n.table > tfoot > tr.warning > td,\n.table > thead > tr.warning > th,\n.table > tbody > tr.warning > th,\n.table > tfoot > tr.warning > th {\n background-color: #fcf8e3;\n}\n.table-hover > tbody > tr > td.warning:hover,\n.table-hover > tbody > tr > th.warning:hover,\n.table-hover > tbody > tr.warning:hover > td,\n.table-hover > tbody > tr:hover > .warning,\n.table-hover > tbody > tr.warning:hover > th {\n background-color: #faf2cc;\n}\n.table > thead > tr > td.danger,\n.table > tbody > tr > td.danger,\n.table > tfoot > tr > td.danger,\n.table > thead > tr > th.danger,\n.table > tbody > tr > th.danger,\n.table > tfoot > tr > th.danger,\n.table > thead > tr.danger > td,\n.table > tbody > tr.danger > td,\n.table > tfoot > tr.danger > td,\n.table > thead > tr.danger > th,\n.table > tbody > tr.danger > th,\n.table > tfoot > tr.danger > th {\n background-color: #f2dede;\n}\n.table-hover > tbody > tr > td.danger:hover,\n.table-hover > tbody > tr > th.danger:hover,\n.table-hover > tbody > tr.danger:hover > td,\n.table-hover > tbody > tr:hover > .danger,\n.table-hover > tbody > tr.danger:hover > th {\n background-color: #ebcccc;\n}\n.table-responsive {\n overflow-x: auto;\n min-height: 0.01%;\n}\n@media screen and (max-width: 767px) {\n .table-responsive {\n width: 100%;\n margin-bottom: 15px;\n overflow-y: hidden;\n -ms-overflow-style: -ms-autohiding-scrollbar;\n border: 1px solid #ddd;\n }\n .table-responsive > .table {\n margin-bottom: 0;\n }\n .table-responsive > .table > thead > tr > th,\n .table-responsive > .table > tbody > tr > th,\n .table-responsive > .table > tfoot > tr > th,\n .table-responsive > .table > thead > tr > td,\n .table-responsive > .table > tbody > tr > td,\n .table-responsive > .table > tfoot > tr > td {\n white-space: nowrap;\n }\n .table-responsive > .table-bordered {\n border: 0;\n }\n .table-responsive > .table-bordered > thead > tr > th:first-child,\n .table-responsive > .table-bordered > tbody > tr > th:first-child,\n .table-responsive > .table-bordered > tfoot > tr > th:first-child,\n .table-responsive > .table-bordered > thead > tr > td:first-child,\n .table-responsive > .table-bordered > tbody > tr > td:first-child,\n .table-responsive > .table-bordered > tfoot > tr > td:first-child {\n border-left: 0;\n }\n .table-responsive > .table-bordered > thead > tr > th:last-child,\n .table-responsive > .table-bordered > tbody > tr > th:last-child,\n .table-responsive > .table-bordered > tfoot > tr > th:last-child,\n .table-responsive > .table-bordered > thead > tr > td:last-child,\n .table-responsive > .table-bordered > tbody > tr > td:last-child,\n .table-responsive > .table-bordered > tfoot > tr > td:last-child {\n border-right: 0;\n }\n .table-responsive > .table-bordered > tbody > tr:last-child > th,\n .table-responsive > .table-bordered > tfoot > tr:last-child > th,\n .table-responsive > .table-bordered > tbody > tr:last-child > td,\n .table-responsive > .table-bordered > tfoot > tr:last-child > td {\n border-bottom: 0;\n }\n}\nfieldset {\n padding: 0;\n margin: 0;\n border: 0;\n min-width: 0;\n}\nlegend {\n display: block;\n width: 100%;\n padding: 0;\n margin-bottom: 20px;\n font-size: 21px;\n line-height: inherit;\n color: #333333;\n border: 0;\n border-bottom: 1px solid #e5e5e5;\n}\nlabel {\n display: inline-block;\n max-width: 100%;\n margin-bottom: 5px;\n font-weight: bold;\n}\ninput[type=\"search\"] {\n -webkit-box-sizing: border-box;\n -moz-box-sizing: border-box;\n box-sizing: border-box;\n}\ninput[type=\"radio\"],\ninput[type=\"checkbox\"] {\n margin: 4px 0 0;\n margin-top: 1px \\9;\n line-height: normal;\n}\ninput[type=\"file\"] {\n display: block;\n}\ninput[type=\"range\"] {\n display: block;\n width: 100%;\n}\nselect[multiple],\nselect[size] {\n height: auto;\n}\ninput[type=\"file\"]:focus,\ninput[type=\"radio\"]:focus,\ninput[type=\"checkbox\"]:focus {\n outline: 5px auto -webkit-focus-ring-color;\n outline-offset: -2px;\n}\noutput {\n display: block;\n padding-top: 7px;\n font-size: 14px;\n line-height: 1.42857143;\n color: #555555;\n}\n.form-control {\n display: block;\n width: 100%;\n height: 34px;\n padding: 6px 12px;\n font-size: 14px;\n line-height: 1.42857143;\n color: #555555;\n background-color: #fff;\n background-image: none;\n border: 1px solid #ccc;\n border-radius: 4px;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\n -webkit-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;\n -o-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;\n transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;\n}\n.form-control:focus {\n border-color: #66afe9;\n outline: 0;\n -webkit-box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(102, 175, 233, 0.6);\n box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(102, 175, 233, 0.6);\n}\n.form-control::-moz-placeholder {\n color: #999;\n opacity: 1;\n}\n.form-control:-ms-input-placeholder {\n color: #999;\n}\n.form-control::-webkit-input-placeholder {\n color: #999;\n}\n.form-control::-ms-expand {\n border: 0;\n background-color: transparent;\n}\n.form-control[disabled],\n.form-control[readonly],\nfieldset[disabled] .form-control {\n background-color: #eeeeee;\n opacity: 1;\n}\n.form-control[disabled],\nfieldset[disabled] .form-control {\n cursor: not-allowed;\n}\ntextarea.form-control {\n height: auto;\n}\ninput[type=\"search\"] {\n -webkit-appearance: none;\n}\n@media screen and (-webkit-min-device-pixel-ratio: 0) {\n input[type=\"date\"].form-control,\n input[type=\"time\"].form-control,\n input[type=\"datetime-local\"].form-control,\n input[type=\"month\"].form-control {\n line-height: 34px;\n }\n input[type=\"date\"].input-sm,\n input[type=\"time\"].input-sm,\n input[type=\"datetime-local\"].input-sm,\n input[type=\"month\"].input-sm,\n .input-group-sm input[type=\"date\"],\n .input-group-sm input[type=\"time\"],\n .input-group-sm input[type=\"datetime-local\"],\n .input-group-sm input[type=\"month\"] {\n line-height: 30px;\n }\n input[type=\"date\"].input-lg,\n input[type=\"time\"].input-lg,\n input[type=\"datetime-local\"].input-lg,\n input[type=\"month\"].input-lg,\n .input-group-lg input[type=\"date\"],\n .input-group-lg input[type=\"time\"],\n .input-group-lg input[type=\"datetime-local\"],\n .input-group-lg input[type=\"month\"] {\n line-height: 46px;\n }\n}\n.form-group {\n margin-bottom: 15px;\n}\n.radio,\n.checkbox {\n position: relative;\n display: block;\n margin-top: 10px;\n margin-bottom: 10px;\n}\n.radio label,\n.checkbox label {\n min-height: 20px;\n padding-left: 20px;\n margin-bottom: 0;\n font-weight: normal;\n cursor: pointer;\n}\n.radio input[type=\"radio\"],\n.radio-inline input[type=\"radio\"],\n.checkbox input[type=\"checkbox\"],\n.checkbox-inline input[type=\"checkbox\"] {\n position: absolute;\n margin-left: -20px;\n margin-top: 4px \\9;\n}\n.radio + .radio,\n.checkbox + .checkbox {\n margin-top: -5px;\n}\n.radio-inline,\n.checkbox-inline {\n position: relative;\n display: inline-block;\n padding-left: 20px;\n margin-bottom: 0;\n vertical-align: middle;\n font-weight: normal;\n cursor: pointer;\n}\n.radio-inline + .radio-inline,\n.checkbox-inline + .checkbox-inline {\n margin-top: 0;\n margin-left: 10px;\n}\ninput[type=\"radio\"][disabled],\ninput[type=\"checkbox\"][disabled],\ninput[type=\"radio\"].disabled,\ninput[type=\"checkbox\"].disabled,\nfieldset[disabled] input[type=\"radio\"],\nfieldset[disabled] input[type=\"checkbox\"] {\n cursor: not-allowed;\n}\n.radio-inline.disabled,\n.checkbox-inline.disabled,\nfieldset[disabled] .radio-inline,\nfieldset[disabled] .checkbox-inline {\n cursor: not-allowed;\n}\n.radio.disabled label,\n.checkbox.disabled label,\nfieldset[disabled] .radio label,\nfieldset[disabled] .checkbox label {\n cursor: not-allowed;\n}\n.form-control-static {\n padding-top: 7px;\n padding-bottom: 7px;\n margin-bottom: 0;\n min-height: 34px;\n}\n.form-control-static.input-lg,\n.form-control-static.input-sm {\n padding-left: 0;\n padding-right: 0;\n}\n.input-sm {\n height: 30px;\n padding: 5px 10px;\n font-size: 12px;\n line-height: 1.5;\n border-radius: 3px;\n}\nselect.input-sm {\n height: 30px;\n line-height: 30px;\n}\ntextarea.input-sm,\nselect[multiple].input-sm {\n height: auto;\n}\n.form-group-sm .form-control {\n height: 30px;\n padding: 5px 10px;\n font-size: 12px;\n line-height: 1.5;\n border-radius: 3px;\n}\n.form-group-sm select.form-control {\n height: 30px;\n line-height: 30px;\n}\n.form-group-sm textarea.form-control,\n.form-group-sm select[multiple].form-control {\n height: auto;\n}\n.form-group-sm .form-control-static {\n height: 30px;\n min-height: 32px;\n padding: 6px 10px;\n font-size: 12px;\n line-height: 1.5;\n}\n.input-lg {\n height: 46px;\n padding: 10px 16px;\n font-size: 18px;\n line-height: 1.3333333;\n border-radius: 6px;\n}\nselect.input-lg {\n height: 46px;\n line-height: 46px;\n}\ntextarea.input-lg,\nselect[multiple].input-lg {\n height: auto;\n}\n.form-group-lg .form-control {\n height: 46px;\n padding: 10px 16px;\n font-size: 18px;\n line-height: 1.3333333;\n border-radius: 6px;\n}\n.form-group-lg select.form-control {\n height: 46px;\n line-height: 46px;\n}\n.form-group-lg textarea.form-control,\n.form-group-lg select[multiple].form-control {\n height: auto;\n}\n.form-group-lg .form-control-static {\n height: 46px;\n min-height: 38px;\n padding: 11px 16px;\n font-size: 18px;\n line-height: 1.3333333;\n}\n.has-feedback {\n position: relative;\n}\n.has-feedback .form-control {\n padding-right: 42.5px;\n}\n.form-control-feedback {\n position: absolute;\n top: 0;\n right: 0;\n z-index: 2;\n display: block;\n width: 34px;\n height: 34px;\n line-height: 34px;\n text-align: center;\n pointer-events: none;\n}\n.input-lg + .form-control-feedback,\n.input-group-lg + .form-control-feedback,\n.form-group-lg .form-control + .form-control-feedback {\n width: 46px;\n height: 46px;\n line-height: 46px;\n}\n.input-sm + .form-control-feedback,\n.input-group-sm + .form-control-feedback,\n.form-group-sm .form-control + .form-control-feedback {\n width: 30px;\n height: 30px;\n line-height: 30px;\n}\n.has-success .help-block,\n.has-success .control-label,\n.has-success .radio,\n.has-success .checkbox,\n.has-success .radio-inline,\n.has-success .checkbox-inline,\n.has-success.radio label,\n.has-success.checkbox label,\n.has-success.radio-inline label,\n.has-success.checkbox-inline label {\n color: #3c763d;\n}\n.has-success .form-control {\n border-color: #3c763d;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\n}\n.has-success .form-control:focus {\n border-color: #2b542c;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #67b168;\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #67b168;\n}\n.has-success .input-group-addon {\n color: #3c763d;\n border-color: #3c763d;\n background-color: #dff0d8;\n}\n.has-success .form-control-feedback {\n color: #3c763d;\n}\n.has-warning .help-block,\n.has-warning .control-label,\n.has-warning .radio,\n.has-warning .checkbox,\n.has-warning .radio-inline,\n.has-warning .checkbox-inline,\n.has-warning.radio label,\n.has-warning.checkbox label,\n.has-warning.radio-inline label,\n.has-warning.checkbox-inline label {\n color: #8a6d3b;\n}\n.has-warning .form-control {\n border-color: #8a6d3b;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\n}\n.has-warning .form-control:focus {\n border-color: #66512c;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #c0a16b;\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #c0a16b;\n}\n.has-warning .input-group-addon {\n color: #8a6d3b;\n border-color: #8a6d3b;\n background-color: #fcf8e3;\n}\n.has-warning .form-control-feedback {\n color: #8a6d3b;\n}\n.has-error .help-block,\n.has-error .control-label,\n.has-error .radio,\n.has-error .checkbox,\n.has-error .radio-inline,\n.has-error .checkbox-inline,\n.has-error.radio label,\n.has-error.checkbox label,\n.has-error.radio-inline label,\n.has-error.checkbox-inline label {\n color: #a94442;\n}\n.has-error .form-control {\n border-color: #a94442;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\n}\n.has-error .form-control:focus {\n border-color: #843534;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #ce8483;\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #ce8483;\n}\n.has-error .input-group-addon {\n color: #a94442;\n border-color: #a94442;\n background-color: #f2dede;\n}\n.has-error .form-control-feedback {\n color: #a94442;\n}\n.has-feedback label ~ .form-control-feedback {\n top: 25px;\n}\n.has-feedback label.sr-only ~ .form-control-feedback {\n top: 0;\n}\n.help-block {\n display: block;\n margin-top: 5px;\n margin-bottom: 10px;\n color: #737373;\n}\n@media (min-width: 768px) {\n .form-inline .form-group {\n display: inline-block;\n margin-bottom: 0;\n vertical-align: middle;\n }\n .form-inline .form-control {\n display: inline-block;\n width: auto;\n vertical-align: middle;\n }\n .form-inline .form-control-static {\n display: inline-block;\n }\n .form-inline .input-group {\n display: inline-table;\n vertical-align: middle;\n }\n .form-inline .input-group .input-group-addon,\n .form-inline .input-group .input-group-btn,\n .form-inline .input-group .form-control {\n width: auto;\n }\n .form-inline .input-group > .form-control {\n width: 100%;\n }\n .form-inline .control-label {\n margin-bottom: 0;\n vertical-align: middle;\n }\n .form-inline .radio,\n .form-inline .checkbox {\n display: inline-block;\n margin-top: 0;\n margin-bottom: 0;\n vertical-align: middle;\n }\n .form-inline .radio label,\n .form-inline .checkbox label {\n padding-left: 0;\n }\n .form-inline .radio input[type=\"radio\"],\n .form-inline .checkbox input[type=\"checkbox\"] {\n position: relative;\n margin-left: 0;\n }\n .form-inline .has-feedback .form-control-feedback {\n top: 0;\n }\n}\n.form-horizontal .radio,\n.form-horizontal .checkbox,\n.form-horizontal .radio-inline,\n.form-horizontal .checkbox-inline {\n margin-top: 0;\n margin-bottom: 0;\n padding-top: 7px;\n}\n.form-horizontal .radio,\n.form-horizontal .checkbox {\n min-height: 27px;\n}\n.form-horizontal .form-group {\n margin-left: -15px;\n margin-right: -15px;\n}\n@media (min-width: 768px) {\n .form-horizontal .control-label {\n text-align: right;\n margin-bottom: 0;\n padding-top: 7px;\n }\n}\n.form-horizontal .has-feedback .form-control-feedback {\n right: 15px;\n}\n@media (min-width: 768px) {\n .form-horizontal .form-group-lg .control-label {\n padding-top: 11px;\n font-size: 18px;\n }\n}\n@media (min-width: 768px) {\n .form-horizontal .form-group-sm .control-label {\n padding-top: 6px;\n font-size: 12px;\n }\n}\n.btn {\n display: inline-block;\n margin-bottom: 0;\n font-weight: normal;\n text-align: center;\n vertical-align: middle;\n touch-action: manipulation;\n cursor: pointer;\n background-image: none;\n border: 1px solid transparent;\n white-space: nowrap;\n padding: 6px 12px;\n font-size: 14px;\n line-height: 1.42857143;\n border-radius: 4px;\n -webkit-user-select: none;\n -moz-user-select: none;\n -ms-user-select: none;\n user-select: none;\n}\n.btn:focus,\n.btn:active:focus,\n.btn.active:focus,\n.btn.focus,\n.btn:active.focus,\n.btn.active.focus {\n outline: 5px auto -webkit-focus-ring-color;\n outline-offset: -2px;\n}\n.btn:hover,\n.btn:focus,\n.btn.focus {\n color: #333;\n text-decoration: none;\n}\n.btn:active,\n.btn.active {\n outline: 0;\n background-image: none;\n -webkit-box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);\n box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);\n}\n.btn.disabled,\n.btn[disabled],\nfieldset[disabled] .btn {\n cursor: not-allowed;\n opacity: 0.65;\n filter: alpha(opacity=65);\n -webkit-box-shadow: none;\n box-shadow: none;\n}\na.btn.disabled,\nfieldset[disabled] a.btn {\n pointer-events: none;\n}\n.btn-default {\n color: #333;\n background-color: #fff;\n border-color: #ccc;\n}\n.btn-default:focus,\n.btn-default.focus {\n color: #333;\n background-color: #e6e6e6;\n border-color: #8c8c8c;\n}\n.btn-default:hover {\n color: #333;\n background-color: #e6e6e6;\n border-color: #adadad;\n}\n.btn-default:active,\n.btn-default.active,\n.open > .dropdown-toggle.btn-default {\n color: #333;\n background-color: #e6e6e6;\n border-color: #adadad;\n}\n.btn-default:active:hover,\n.btn-default.active:hover,\n.open > .dropdown-toggle.btn-default:hover,\n.btn-default:active:focus,\n.btn-default.active:focus,\n.open > .dropdown-toggle.btn-default:focus,\n.btn-default:active.focus,\n.btn-default.active.focus,\n.open > .dropdown-toggle.btn-default.focus {\n color: #333;\n background-color: #d4d4d4;\n border-color: #8c8c8c;\n}\n.btn-default:active,\n.btn-default.active,\n.open > .dropdown-toggle.btn-default {\n background-image: none;\n}\n.btn-default.disabled:hover,\n.btn-default[disabled]:hover,\nfieldset[disabled] .btn-default:hover,\n.btn-default.disabled:focus,\n.btn-default[disabled]:focus,\nfieldset[disabled] .btn-default:focus,\n.btn-default.disabled.focus,\n.btn-default[disabled].focus,\nfieldset[disabled] .btn-default.focus {\n background-color: #fff;\n border-color: #ccc;\n}\n.btn-default .badge {\n color: #fff;\n background-color: #333;\n}\n.btn-primary {\n color: #fff;\n background-color: #337ab7;\n border-color: #2e6da4;\n}\n.btn-primary:focus,\n.btn-primary.focus {\n color: #fff;\n background-color: #286090;\n border-color: #122b40;\n}\n.btn-primary:hover {\n color: #fff;\n background-color: #286090;\n border-color: #204d74;\n}\n.btn-primary:active,\n.btn-primary.active,\n.open > .dropdown-toggle.btn-primary {\n color: #fff;\n background-color: #286090;\n border-color: #204d74;\n}\n.btn-primary:active:hover,\n.btn-primary.active:hover,\n.open > .dropdown-toggle.btn-primary:hover,\n.btn-primary:active:focus,\n.btn-primary.active:focus,\n.open > .dropdown-toggle.btn-primary:focus,\n.btn-primary:active.focus,\n.btn-primary.active.focus,\n.open > .dropdown-toggle.btn-primary.focus {\n color: #fff;\n background-color: #204d74;\n border-color: #122b40;\n}\n.btn-primary:active,\n.btn-primary.active,\n.open > .dropdown-toggle.btn-primary {\n background-image: none;\n}\n.btn-primary.disabled:hover,\n.btn-primary[disabled]:hover,\nfieldset[disabled] .btn-primary:hover,\n.btn-primary.disabled:focus,\n.btn-primary[disabled]:focus,\nfieldset[disabled] .btn-primary:focus,\n.btn-primary.disabled.focus,\n.btn-primary[disabled].focus,\nfieldset[disabled] .btn-primary.focus {\n background-color: #337ab7;\n border-color: #2e6da4;\n}\n.btn-primary .badge {\n color: #337ab7;\n background-color: #fff;\n}\n.btn-success {\n color: #fff;\n background-color: #5cb85c;\n border-color: #4cae4c;\n}\n.btn-success:focus,\n.btn-success.focus {\n color: #fff;\n background-color: #449d44;\n border-color: #255625;\n}\n.btn-success:hover {\n color: #fff;\n background-color: #449d44;\n border-color: #398439;\n}\n.btn-success:active,\n.btn-success.active,\n.open > .dropdown-toggle.btn-success {\n color: #fff;\n background-color: #449d44;\n border-color: #398439;\n}\n.btn-success:active:hover,\n.btn-success.active:hover,\n.open > .dropdown-toggle.btn-success:hover,\n.btn-success:active:focus,\n.btn-success.active:focus,\n.open > .dropdown-toggle.btn-success:focus,\n.btn-success:active.focus,\n.btn-success.active.focus,\n.open > .dropdown-toggle.btn-success.focus {\n color: #fff;\n background-color: #398439;\n border-color: #255625;\n}\n.btn-success:active,\n.btn-success.active,\n.open > .dropdown-toggle.btn-success {\n background-image: none;\n}\n.btn-success.disabled:hover,\n.btn-success[disabled]:hover,\nfieldset[disabled] .btn-success:hover,\n.btn-success.disabled:focus,\n.btn-success[disabled]:focus,\nfieldset[disabled] .btn-success:focus,\n.btn-success.disabled.focus,\n.btn-success[disabled].focus,\nfieldset[disabled] .btn-success.focus {\n background-color: #5cb85c;\n border-color: #4cae4c;\n}\n.btn-success .badge {\n color: #5cb85c;\n background-color: #fff;\n}\n.btn-info {\n color: #fff;\n background-color: #5bc0de;\n border-color: #46b8da;\n}\n.btn-info:focus,\n.btn-info.focus {\n color: #fff;\n background-color: #31b0d5;\n border-color: #1b6d85;\n}\n.btn-info:hover {\n color: #fff;\n background-color: #31b0d5;\n border-color: #269abc;\n}\n.btn-info:active,\n.btn-info.active,\n.open > .dropdown-toggle.btn-info {\n color: #fff;\n background-color: #31b0d5;\n border-color: #269abc;\n}\n.btn-info:active:hover,\n.btn-info.active:hover,\n.open > .dropdown-toggle.btn-info:hover,\n.btn-info:active:focus,\n.btn-info.active:focus,\n.open > .dropdown-toggle.btn-info:focus,\n.btn-info:active.focus,\n.btn-info.active.focus,\n.open > .dropdown-toggle.btn-info.focus {\n color: #fff;\n background-color: #269abc;\n border-color: #1b6d85;\n}\n.btn-info:active,\n.btn-info.active,\n.open > .dropdown-toggle.btn-info {\n background-image: none;\n}\n.btn-info.disabled:hover,\n.btn-info[disabled]:hover,\nfieldset[disabled] .btn-info:hover,\n.btn-info.disabled:focus,\n.btn-info[disabled]:focus,\nfieldset[disabled] .btn-info:focus,\n.btn-info.disabled.focus,\n.btn-info[disabled].focus,\nfieldset[disabled] .btn-info.focus {\n background-color: #5bc0de;\n border-color: #46b8da;\n}\n.btn-info .badge {\n color: #5bc0de;\n background-color: #fff;\n}\n.btn-warning {\n color: #fff;\n background-color: #f0ad4e;\n border-color: #eea236;\n}\n.btn-warning:focus,\n.btn-warning.focus {\n color: #fff;\n background-color: #ec971f;\n border-color: #985f0d;\n}\n.btn-warning:hover {\n color: #fff;\n background-color: #ec971f;\n border-color: #d58512;\n}\n.btn-warning:active,\n.btn-warning.active,\n.open > .dropdown-toggle.btn-warning {\n color: #fff;\n background-color: #ec971f;\n border-color: #d58512;\n}\n.btn-warning:active:hover,\n.btn-warning.active:hover,\n.open > .dropdown-toggle.btn-warning:hover,\n.btn-warning:active:focus,\n.btn-warning.active:focus,\n.open > .dropdown-toggle.btn-warning:focus,\n.btn-warning:active.focus,\n.btn-warning.active.focus,\n.open > .dropdown-toggle.btn-warning.focus {\n color: #fff;\n background-color: #d58512;\n border-color: #985f0d;\n}\n.btn-warning:active,\n.btn-warning.active,\n.open > .dropdown-toggle.btn-warning {\n background-image: none;\n}\n.btn-warning.disabled:hover,\n.btn-warning[disabled]:hover,\nfieldset[disabled] .btn-warning:hover,\n.btn-warning.disabled:focus,\n.btn-warning[disabled]:focus,\nfieldset[disabled] .btn-warning:focus,\n.btn-warning.disabled.focus,\n.btn-warning[disabled].focus,\nfieldset[disabled] .btn-warning.focus {\n background-color: #f0ad4e;\n border-color: #eea236;\n}\n.btn-warning .badge {\n color: #f0ad4e;\n background-color: #fff;\n}\n.btn-danger {\n color: #fff;\n background-color: #d9534f;\n border-color: #d43f3a;\n}\n.btn-danger:focus,\n.btn-danger.focus {\n color: #fff;\n background-color: #c9302c;\n border-color: #761c19;\n}\n.btn-danger:hover {\n color: #fff;\n background-color: #c9302c;\n border-color: #ac2925;\n}\n.btn-danger:active,\n.btn-danger.active,\n.open > .dropdown-toggle.btn-danger {\n color: #fff;\n background-color: #c9302c;\n border-color: #ac2925;\n}\n.btn-danger:active:hover,\n.btn-danger.active:hover,\n.open > .dropdown-toggle.btn-danger:hover,\n.btn-danger:active:focus,\n.btn-danger.active:focus,\n.open > .dropdown-toggle.btn-danger:focus,\n.btn-danger:active.focus,\n.btn-danger.active.focus,\n.open > .dropdown-toggle.btn-danger.focus {\n color: #fff;\n background-color: #ac2925;\n border-color: #761c19;\n}\n.btn-danger:active,\n.btn-danger.active,\n.open > .dropdown-toggle.btn-danger {\n background-image: none;\n}\n.btn-danger.disabled:hover,\n.btn-danger[disabled]:hover,\nfieldset[disabled] .btn-danger:hover,\n.btn-danger.disabled:focus,\n.btn-danger[disabled]:focus,\nfieldset[disabled] .btn-danger:focus,\n.btn-danger.disabled.focus,\n.btn-danger[disabled].focus,\nfieldset[disabled] .btn-danger.focus {\n background-color: #d9534f;\n border-color: #d43f3a;\n}\n.btn-danger .badge {\n color: #d9534f;\n background-color: #fff;\n}\n.btn-link {\n color: #337ab7;\n font-weight: normal;\n border-radius: 0;\n}\n.btn-link,\n.btn-link:active,\n.btn-link.active,\n.btn-link[disabled],\nfieldset[disabled] .btn-link {\n background-color: transparent;\n -webkit-box-shadow: none;\n box-shadow: none;\n}\n.btn-link,\n.btn-link:hover,\n.btn-link:focus,\n.btn-link:active {\n border-color: transparent;\n}\n.btn-link:hover,\n.btn-link:focus {\n color: #23527c;\n text-decoration: underline;\n background-color: transparent;\n}\n.btn-link[disabled]:hover,\nfieldset[disabled] .btn-link:hover,\n.btn-link[disabled]:focus,\nfieldset[disabled] .btn-link:focus {\n color: #777777;\n text-decoration: none;\n}\n.btn-lg,\n.btn-group-lg > .btn {\n padding: 10px 16px;\n font-size: 18px;\n line-height: 1.3333333;\n border-radius: 6px;\n}\n.btn-sm,\n.btn-group-sm > .btn {\n padding: 5px 10px;\n font-size: 12px;\n line-height: 1.5;\n border-radius: 3px;\n}\n.btn-xs,\n.btn-group-xs > .btn {\n padding: 1px 5px;\n font-size: 12px;\n line-height: 1.5;\n border-radius: 3px;\n}\n.btn-block {\n display: block;\n width: 100%;\n}\n.btn-block + .btn-block {\n margin-top: 5px;\n}\ninput[type=\"submit\"].btn-block,\ninput[type=\"reset\"].btn-block,\ninput[type=\"button\"].btn-block {\n width: 100%;\n}\n.fade {\n opacity: 0;\n -webkit-transition: opacity 0.15s linear;\n -o-transition: opacity 0.15s linear;\n transition: opacity 0.15s linear;\n}\n.fade.in {\n opacity: 1;\n}\n.collapse {\n display: none;\n}\n.collapse.in {\n display: block;\n}\ntr.collapse.in {\n display: table-row;\n}\ntbody.collapse.in {\n display: table-row-group;\n}\n.collapsing {\n position: relative;\n height: 0;\n overflow: hidden;\n -webkit-transition-property: height, visibility;\n transition-property: height, visibility;\n -webkit-transition-duration: 0.35s;\n transition-duration: 0.35s;\n -webkit-transition-timing-function: ease;\n transition-timing-function: ease;\n}\n.caret {\n display: inline-block;\n width: 0;\n height: 0;\n margin-left: 2px;\n vertical-align: middle;\n border-top: 4px dashed;\n border-top: 4px solid \\9;\n border-right: 4px solid transparent;\n border-left: 4px solid transparent;\n}\n.dropup,\n.dropdown {\n position: relative;\n}\n.dropdown-toggle:focus {\n outline: 0;\n}\n.dropdown-menu {\n position: absolute;\n top: 100%;\n left: 0;\n z-index: 1000;\n display: none;\n float: left;\n min-width: 160px;\n padding: 5px 0;\n margin: 2px 0 0;\n list-style: none;\n font-size: 14px;\n text-align: left;\n background-color: #fff;\n border: 1px solid #ccc;\n border: 1px solid rgba(0, 0, 0, 0.15);\n border-radius: 4px;\n -webkit-box-shadow: 0 6px 12px rgba(0, 0, 0, 0.175);\n box-shadow: 0 6px 12px rgba(0, 0, 0, 0.175);\n background-clip: padding-box;\n}\n.dropdown-menu.pull-right {\n right: 0;\n left: auto;\n}\n.dropdown-menu .divider {\n height: 1px;\n margin: 9px 0;\n overflow: hidden;\n background-color: #e5e5e5;\n}\n.dropdown-menu > li > a {\n display: block;\n padding: 3px 20px;\n clear: both;\n font-weight: normal;\n line-height: 1.42857143;\n color: #333333;\n white-space: nowrap;\n}\n.dropdown-menu > li > a:hover,\n.dropdown-menu > li > a:focus {\n text-decoration: none;\n color: #262626;\n background-color: #f5f5f5;\n}\n.dropdown-menu > .active > a,\n.dropdown-menu > .active > a:hover,\n.dropdown-menu > .active > a:focus {\n color: #fff;\n text-decoration: none;\n outline: 0;\n background-color: #337ab7;\n}\n.dropdown-menu > .disabled > a,\n.dropdown-menu > .disabled > a:hover,\n.dropdown-menu > .disabled > a:focus {\n color: #777777;\n}\n.dropdown-menu > .disabled > a:hover,\n.dropdown-menu > .disabled > a:focus {\n text-decoration: none;\n background-color: transparent;\n background-image: none;\n filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);\n cursor: not-allowed;\n}\n.open > .dropdown-menu {\n display: block;\n}\n.open > a {\n outline: 0;\n}\n.dropdown-menu-right {\n left: auto;\n right: 0;\n}\n.dropdown-menu-left {\n left: 0;\n right: auto;\n}\n.dropdown-header {\n display: block;\n padding: 3px 20px;\n font-size: 12px;\n line-height: 1.42857143;\n color: #777777;\n white-space: nowrap;\n}\n.dropdown-backdrop {\n position: fixed;\n left: 0;\n right: 0;\n bottom: 0;\n top: 0;\n z-index: 990;\n}\n.pull-right > .dropdown-menu {\n right: 0;\n left: auto;\n}\n.dropup .caret,\n.navbar-fixed-bottom .dropdown .caret {\n border-top: 0;\n border-bottom: 4px dashed;\n border-bottom: 4px solid \\9;\n content: \"\";\n}\n.dropup .dropdown-menu,\n.navbar-fixed-bottom .dropdown .dropdown-menu {\n top: auto;\n bottom: 100%;\n margin-bottom: 2px;\n}\n@media (min-width: 768px) {\n .navbar-right .dropdown-menu {\n left: auto;\n right: 0;\n }\n .navbar-right .dropdown-menu-left {\n left: 0;\n right: auto;\n }\n}\n.btn-group,\n.btn-group-vertical {\n position: relative;\n display: inline-block;\n vertical-align: middle;\n}\n.btn-group > .btn,\n.btn-group-vertical > .btn {\n position: relative;\n float: left;\n}\n.btn-group > .btn:hover,\n.btn-group-vertical > .btn:hover,\n.btn-group > .btn:focus,\n.btn-group-vertical > .btn:focus,\n.btn-group > .btn:active,\n.btn-group-vertical > .btn:active,\n.btn-group > .btn.active,\n.btn-group-vertical > .btn.active {\n z-index: 2;\n}\n.btn-group .btn + .btn,\n.btn-group .btn + .btn-group,\n.btn-group .btn-group + .btn,\n.btn-group .btn-group + .btn-group {\n margin-left: -1px;\n}\n.btn-toolbar {\n margin-left: -5px;\n}\n.btn-toolbar .btn,\n.btn-toolbar .btn-group,\n.btn-toolbar .input-group {\n float: left;\n}\n.btn-toolbar > .btn,\n.btn-toolbar > .btn-group,\n.btn-toolbar > .input-group {\n margin-left: 5px;\n}\n.btn-group > .btn:not(:first-child):not(:last-child):not(.dropdown-toggle) {\n border-radius: 0;\n}\n.btn-group > .btn:first-child {\n margin-left: 0;\n}\n.btn-group > .btn:first-child:not(:last-child):not(.dropdown-toggle) {\n border-bottom-right-radius: 0;\n border-top-right-radius: 0;\n}\n.btn-group > .btn:last-child:not(:first-child),\n.btn-group > .dropdown-toggle:not(:first-child) {\n border-bottom-left-radius: 0;\n border-top-left-radius: 0;\n}\n.btn-group > .btn-group {\n float: left;\n}\n.btn-group > .btn-group:not(:first-child):not(:last-child) > .btn {\n border-radius: 0;\n}\n.btn-group > .btn-group:first-child:not(:last-child) > .btn:last-child,\n.btn-group > .btn-group:first-child:not(:last-child) > .dropdown-toggle {\n border-bottom-right-radius: 0;\n border-top-right-radius: 0;\n}\n.btn-group > .btn-group:last-child:not(:first-child) > .btn:first-child {\n border-bottom-left-radius: 0;\n border-top-left-radius: 0;\n}\n.btn-group .dropdown-toggle:active,\n.btn-group.open .dropdown-toggle {\n outline: 0;\n}\n.btn-group > .btn + .dropdown-toggle {\n padding-left: 8px;\n padding-right: 8px;\n}\n.btn-group > .btn-lg + .dropdown-toggle {\n padding-left: 12px;\n padding-right: 12px;\n}\n.btn-group.open .dropdown-toggle {\n -webkit-box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);\n box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);\n}\n.btn-group.open .dropdown-toggle.btn-link {\n -webkit-box-shadow: none;\n box-shadow: none;\n}\n.btn .caret {\n margin-left: 0;\n}\n.btn-lg .caret {\n border-width: 5px 5px 0;\n border-bottom-width: 0;\n}\n.dropup .btn-lg .caret {\n border-width: 0 5px 5px;\n}\n.btn-group-vertical > .btn,\n.btn-group-vertical > .btn-group,\n.btn-group-vertical > .btn-group > .btn {\n display: block;\n float: none;\n width: 100%;\n max-width: 100%;\n}\n.btn-group-vertical > .btn-group > .btn {\n float: none;\n}\n.btn-group-vertical > .btn + .btn,\n.btn-group-vertical > .btn + .btn-group,\n.btn-group-vertical > .btn-group + .btn,\n.btn-group-vertical > .btn-group + .btn-group {\n margin-top: -1px;\n margin-left: 0;\n}\n.btn-group-vertical > .btn:not(:first-child):not(:last-child) {\n border-radius: 0;\n}\n.btn-group-vertical > .btn:first-child:not(:last-child) {\n border-top-right-radius: 4px;\n border-top-left-radius: 4px;\n border-bottom-right-radius: 0;\n border-bottom-left-radius: 0;\n}\n.btn-group-vertical > .btn:last-child:not(:first-child) {\n border-top-right-radius: 0;\n border-top-left-radius: 0;\n border-bottom-right-radius: 4px;\n border-bottom-left-radius: 4px;\n}\n.btn-group-vertical > .btn-group:not(:first-child):not(:last-child) > .btn {\n border-radius: 0;\n}\n.btn-group-vertical > .btn-group:first-child:not(:last-child) > .btn:last-child,\n.btn-group-vertical > .btn-group:first-child:not(:last-child) > .dropdown-toggle {\n border-bottom-right-radius: 0;\n border-bottom-left-radius: 0;\n}\n.btn-group-vertical > .btn-group:last-child:not(:first-child) > .btn:first-child {\n border-top-right-radius: 0;\n border-top-left-radius: 0;\n}\n.btn-group-justified {\n display: table;\n width: 100%;\n table-layout: fixed;\n border-collapse: separate;\n}\n.btn-group-justified > .btn,\n.btn-group-justified > .btn-group {\n float: none;\n display: table-cell;\n width: 1%;\n}\n.btn-group-justified > .btn-group .btn {\n width: 100%;\n}\n.btn-group-justified > .btn-group .dropdown-menu {\n left: auto;\n}\n[data-toggle=\"buttons\"] > .btn input[type=\"radio\"],\n[data-toggle=\"buttons\"] > .btn-group > .btn input[type=\"radio\"],\n[data-toggle=\"buttons\"] > .btn input[type=\"checkbox\"],\n[data-toggle=\"buttons\"] > .btn-group > .btn input[type=\"checkbox\"] {\n position: absolute;\n clip: rect(0, 0, 0, 0);\n pointer-events: none;\n}\n.input-group {\n position: relative;\n display: table;\n border-collapse: separate;\n}\n.input-group[class*=\"col-\"] {\n float: none;\n padding-left: 0;\n padding-right: 0;\n}\n.input-group .form-control {\n position: relative;\n z-index: 2;\n float: left;\n width: 100%;\n margin-bottom: 0;\n}\n.input-group .form-control:focus {\n z-index: 3;\n}\n.input-group-lg > .form-control,\n.input-group-lg > .input-group-addon,\n.input-group-lg > .input-group-btn > .btn {\n height: 46px;\n padding: 10px 16px;\n font-size: 18px;\n line-height: 1.3333333;\n border-radius: 6px;\n}\nselect.input-group-lg > .form-control,\nselect.input-group-lg > .input-group-addon,\nselect.input-group-lg > .input-group-btn > .btn {\n height: 46px;\n line-height: 46px;\n}\ntextarea.input-group-lg > .form-control,\ntextarea.input-group-lg > .input-group-addon,\ntextarea.input-group-lg > .input-group-btn > .btn,\nselect[multiple].input-group-lg > .form-control,\nselect[multiple].input-group-lg > .input-group-addon,\nselect[multiple].input-group-lg > .input-group-btn > .btn {\n height: auto;\n}\n.input-group-sm > .form-control,\n.input-group-sm > .input-group-addon,\n.input-group-sm > .input-group-btn > .btn {\n height: 30px;\n padding: 5px 10px;\n font-size: 12px;\n line-height: 1.5;\n border-radius: 3px;\n}\nselect.input-group-sm > .form-control,\nselect.input-group-sm > .input-group-addon,\nselect.input-group-sm > .input-group-btn > .btn {\n height: 30px;\n line-height: 30px;\n}\ntextarea.input-group-sm > .form-control,\ntextarea.input-group-sm > .input-group-addon,\ntextarea.input-group-sm > .input-group-btn > .btn,\nselect[multiple].input-group-sm > .form-control,\nselect[multiple].input-group-sm > .input-group-addon,\nselect[multiple].input-group-sm > .input-group-btn > .btn {\n height: auto;\n}\n.input-group-addon,\n.input-group-btn,\n.input-group .form-control {\n display: table-cell;\n}\n.input-group-addon:not(:first-child):not(:last-child),\n.input-group-btn:not(:first-child):not(:last-child),\n.input-group .form-control:not(:first-child):not(:last-child) {\n border-radius: 0;\n}\n.input-group-addon,\n.input-group-btn {\n width: 1%;\n white-space: nowrap;\n vertical-align: middle;\n}\n.input-group-addon {\n padding: 6px 12px;\n font-size: 14px;\n font-weight: normal;\n line-height: 1;\n color: #555555;\n text-align: center;\n background-color: #eeeeee;\n border: 1px solid #ccc;\n border-radius: 4px;\n}\n.input-group-addon.input-sm {\n padding: 5px 10px;\n font-size: 12px;\n border-radius: 3px;\n}\n.input-group-addon.input-lg {\n padding: 10px 16px;\n font-size: 18px;\n border-radius: 6px;\n}\n.input-group-addon input[type=\"radio\"],\n.input-group-addon input[type=\"checkbox\"] {\n margin-top: 0;\n}\n.input-group .form-control:first-child,\n.input-group-addon:first-child,\n.input-group-btn:first-child > .btn,\n.input-group-btn:first-child > .btn-group > .btn,\n.input-group-btn:first-child > .dropdown-toggle,\n.input-group-btn:last-child > .btn:not(:last-child):not(.dropdown-toggle),\n.input-group-btn:last-child > .btn-group:not(:last-child) > .btn {\n border-bottom-right-radius: 0;\n border-top-right-radius: 0;\n}\n.input-group-addon:first-child {\n border-right: 0;\n}\n.input-group .form-control:last-child,\n.input-group-addon:last-child,\n.input-group-btn:last-child > .btn,\n.input-group-btn:last-child > .btn-group > .btn,\n.input-group-btn:last-child > .dropdown-toggle,\n.input-group-btn:first-child > .btn:not(:first-child),\n.input-group-btn:first-child > .btn-group:not(:first-child) > .btn {\n border-bottom-left-radius: 0;\n border-top-left-radius: 0;\n}\n.input-group-addon:last-child {\n border-left: 0;\n}\n.input-group-btn {\n position: relative;\n font-size: 0;\n white-space: nowrap;\n}\n.input-group-btn > .btn {\n position: relative;\n}\n.input-group-btn > .btn + .btn {\n margin-left: -1px;\n}\n.input-group-btn > .btn:hover,\n.input-group-btn > .btn:focus,\n.input-group-btn > .btn:active {\n z-index: 2;\n}\n.input-group-btn:first-child > .btn,\n.input-group-btn:first-child > .btn-group {\n margin-right: -1px;\n}\n.input-group-btn:last-child > .btn,\n.input-group-btn:last-child > .btn-group {\n z-index: 2;\n margin-left: -1px;\n}\n.nav {\n margin-bottom: 0;\n padding-left: 0;\n list-style: none;\n}\n.nav > li {\n position: relative;\n display: block;\n}\n.nav > li > a {\n position: relative;\n display: block;\n padding: 10px 15px;\n}\n.nav > li > a:hover,\n.nav > li > a:focus {\n text-decoration: none;\n background-color: #eeeeee;\n}\n.nav > li.disabled > a {\n color: #777777;\n}\n.nav > li.disabled > a:hover,\n.nav > li.disabled > a:focus {\n color: #777777;\n text-decoration: none;\n background-color: transparent;\n cursor: not-allowed;\n}\n.nav .open > a,\n.nav .open > a:hover,\n.nav .open > a:focus {\n background-color: #eeeeee;\n border-color: #337ab7;\n}\n.nav .nav-divider {\n height: 1px;\n margin: 9px 0;\n overflow: hidden;\n background-color: #e5e5e5;\n}\n.nav > li > a > img {\n max-width: none;\n}\n.nav-tabs {\n border-bottom: 1px solid #ddd;\n}\n.nav-tabs > li {\n float: left;\n margin-bottom: -1px;\n}\n.nav-tabs > li > a {\n margin-right: 2px;\n line-height: 1.42857143;\n border: 1px solid transparent;\n border-radius: 4px 4px 0 0;\n}\n.nav-tabs > li > a:hover {\n border-color: #eeeeee #eeeeee #ddd;\n}\n.nav-tabs > li.active > a,\n.nav-tabs > li.active > a:hover,\n.nav-tabs > li.active > a:focus {\n color: #555555;\n background-color: #fff;\n border: 1px solid #ddd;\n border-bottom-color: transparent;\n cursor: default;\n}\n.nav-tabs.nav-justified {\n width: 100%;\n border-bottom: 0;\n}\n.nav-tabs.nav-justified > li {\n float: none;\n}\n.nav-tabs.nav-justified > li > a {\n text-align: center;\n margin-bottom: 5px;\n}\n.nav-tabs.nav-justified > .dropdown .dropdown-menu {\n top: auto;\n left: auto;\n}\n@media (min-width: 768px) {\n .nav-tabs.nav-justified > li {\n display: table-cell;\n width: 1%;\n }\n .nav-tabs.nav-justified > li > a {\n margin-bottom: 0;\n }\n}\n.nav-tabs.nav-justified > li > a {\n margin-right: 0;\n border-radius: 4px;\n}\n.nav-tabs.nav-justified > .active > a,\n.nav-tabs.nav-justified > .active > a:hover,\n.nav-tabs.nav-justified > .active > a:focus {\n border: 1px solid #ddd;\n}\n@media (min-width: 768px) {\n .nav-tabs.nav-justified > li > a {\n border-bottom: 1px solid #ddd;\n border-radius: 4px 4px 0 0;\n }\n .nav-tabs.nav-justified > .active > a,\n .nav-tabs.nav-justified > .active > a:hover,\n .nav-tabs.nav-justified > .active > a:focus {\n border-bottom-color: #fff;\n }\n}\n.nav-pills > li {\n float: left;\n}\n.nav-pills > li > a {\n border-radius: 4px;\n}\n.nav-pills > li + li {\n margin-left: 2px;\n}\n.nav-pills > li.active > a,\n.nav-pills > li.active > a:hover,\n.nav-pills > li.active > a:focus {\n color: #fff;\n background-color: #337ab7;\n}\n.nav-stacked > li {\n float: none;\n}\n.nav-stacked > li + li {\n margin-top: 2px;\n margin-left: 0;\n}\n.nav-justified {\n width: 100%;\n}\n.nav-justified > li {\n float: none;\n}\n.nav-justified > li > a {\n text-align: center;\n margin-bottom: 5px;\n}\n.nav-justified > .dropdown .dropdown-menu {\n top: auto;\n left: auto;\n}\n@media (min-width: 768px) {\n .nav-justified > li {\n display: table-cell;\n width: 1%;\n }\n .nav-justified > li > a {\n margin-bottom: 0;\n }\n}\n.nav-tabs-justified {\n border-bottom: 0;\n}\n.nav-tabs-justified > li > a {\n margin-right: 0;\n border-radius: 4px;\n}\n.nav-tabs-justified > .active > a,\n.nav-tabs-justified > .active > a:hover,\n.nav-tabs-justified > .active > a:focus {\n border: 1px solid #ddd;\n}\n@media (min-width: 768px) {\n .nav-tabs-justified > li > a {\n border-bottom: 1px solid #ddd;\n border-radius: 4px 4px 0 0;\n }\n .nav-tabs-justified > .active > a,\n .nav-tabs-justified > .active > a:hover,\n .nav-tabs-justified > .active > a:focus {\n border-bottom-color: #fff;\n }\n}\n.tab-content > .tab-pane {\n display: none;\n}\n.tab-content > .active {\n display: block;\n}\n.nav-tabs .dropdown-menu {\n margin-top: -1px;\n border-top-right-radius: 0;\n border-top-left-radius: 0;\n}\n.navbar {\n position: relative;\n min-height: 50px;\n margin-bottom: 20px;\n border: 1px solid transparent;\n}\n@media (min-width: 768px) {\n .navbar {\n border-radius: 4px;\n }\n}\n@media (min-width: 768px) {\n .navbar-header {\n float: left;\n }\n}\n.navbar-collapse {\n overflow-x: visible;\n padding-right: 15px;\n padding-left: 15px;\n border-top: 1px solid transparent;\n box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1);\n -webkit-overflow-scrolling: touch;\n}\n.navbar-collapse.in {\n overflow-y: auto;\n}\n@media (min-width: 768px) {\n .navbar-collapse {\n width: auto;\n border-top: 0;\n box-shadow: none;\n }\n .navbar-collapse.collapse {\n display: block !important;\n height: auto !important;\n padding-bottom: 0;\n overflow: visible !important;\n }\n .navbar-collapse.in {\n overflow-y: visible;\n }\n .navbar-fixed-top .navbar-collapse,\n .navbar-static-top .navbar-collapse,\n .navbar-fixed-bottom .navbar-collapse {\n padding-left: 0;\n padding-right: 0;\n }\n}\n.navbar-fixed-top .navbar-collapse,\n.navbar-fixed-bottom .navbar-collapse {\n max-height: 340px;\n}\n@media (max-device-width: 480px) and (orientation: landscape) {\n .navbar-fixed-top .navbar-collapse,\n .navbar-fixed-bottom .navbar-collapse {\n max-height: 200px;\n }\n}\n.container > .navbar-header,\n.container-fluid > .navbar-header,\n.container > .navbar-collapse,\n.container-fluid > .navbar-collapse {\n margin-right: -15px;\n margin-left: -15px;\n}\n@media (min-width: 768px) {\n .container > .navbar-header,\n .container-fluid > .navbar-header,\n .container > .navbar-collapse,\n .container-fluid > .navbar-collapse {\n margin-right: 0;\n margin-left: 0;\n }\n}\n.navbar-static-top {\n z-index: 1000;\n border-width: 0 0 1px;\n}\n@media (min-width: 768px) {\n .navbar-static-top {\n border-radius: 0;\n }\n}\n.navbar-fixed-top,\n.navbar-fixed-bottom {\n position: fixed;\n right: 0;\n left: 0;\n z-index: 1030;\n}\n@media (min-width: 768px) {\n .navbar-fixed-top,\n .navbar-fixed-bottom {\n border-radius: 0;\n }\n}\n.navbar-fixed-top {\n top: 0;\n border-width: 0 0 1px;\n}\n.navbar-fixed-bottom {\n bottom: 0;\n margin-bottom: 0;\n border-width: 1px 0 0;\n}\n.navbar-brand {\n float: left;\n padding: 15px 15px;\n font-size: 18px;\n line-height: 20px;\n height: 50px;\n}\n.navbar-brand:hover,\n.navbar-brand:focus {\n text-decoration: none;\n}\n.navbar-brand > img {\n display: block;\n}\n@media (min-width: 768px) {\n .navbar > .container .navbar-brand,\n .navbar > .container-fluid .navbar-brand {\n margin-left: -15px;\n }\n}\n.navbar-toggle {\n position: relative;\n float: right;\n margin-right: 15px;\n padding: 9px 10px;\n margin-top: 8px;\n margin-bottom: 8px;\n background-color: transparent;\n background-image: none;\n border: 1px solid transparent;\n border-radius: 4px;\n}\n.navbar-toggle:focus {\n outline: 0;\n}\n.navbar-toggle .icon-bar {\n display: block;\n width: 22px;\n height: 2px;\n border-radius: 1px;\n}\n.navbar-toggle .icon-bar + .icon-bar {\n margin-top: 4px;\n}\n@media (min-width: 768px) {\n .navbar-toggle {\n display: none;\n }\n}\n.navbar-nav {\n margin: 7.5px -15px;\n}\n.navbar-nav > li > a {\n padding-top: 10px;\n padding-bottom: 10px;\n line-height: 20px;\n}\n@media (max-width: 767px) {\n .navbar-nav .open .dropdown-menu {\n position: static;\n float: none;\n width: auto;\n margin-top: 0;\n background-color: transparent;\n border: 0;\n box-shadow: none;\n }\n .navbar-nav .open .dropdown-menu > li > a,\n .navbar-nav .open .dropdown-menu .dropdown-header {\n padding: 5px 15px 5px 25px;\n }\n .navbar-nav .open .dropdown-menu > li > a {\n line-height: 20px;\n }\n .navbar-nav .open .dropdown-menu > li > a:hover,\n .navbar-nav .open .dropdown-menu > li > a:focus {\n background-image: none;\n }\n}\n@media (min-width: 768px) {\n .navbar-nav {\n float: left;\n margin: 0;\n }\n .navbar-nav > li {\n float: left;\n }\n .navbar-nav > li > a {\n padding-top: 15px;\n padding-bottom: 15px;\n }\n}\n.navbar-form {\n margin-left: -15px;\n margin-right: -15px;\n padding: 10px 15px;\n border-top: 1px solid transparent;\n border-bottom: 1px solid transparent;\n -webkit-box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1), 0 1px 0 rgba(255, 255, 255, 0.1);\n box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1), 0 1px 0 rgba(255, 255, 255, 0.1);\n margin-top: 8px;\n margin-bottom: 8px;\n}\n@media (min-width: 768px) {\n .navbar-form .form-group {\n display: inline-block;\n margin-bottom: 0;\n vertical-align: middle;\n }\n .navbar-form .form-control {\n display: inline-block;\n width: auto;\n vertical-align: middle;\n }\n .navbar-form .form-control-static {\n display: inline-block;\n }\n .navbar-form .input-group {\n display: inline-table;\n vertical-align: middle;\n }\n .navbar-form .input-group .input-group-addon,\n .navbar-form .input-group .input-group-btn,\n .navbar-form .input-group .form-control {\n width: auto;\n }\n .navbar-form .input-group > .form-control {\n width: 100%;\n }\n .navbar-form .control-label {\n margin-bottom: 0;\n vertical-align: middle;\n }\n .navbar-form .radio,\n .navbar-form .checkbox {\n display: inline-block;\n margin-top: 0;\n margin-bottom: 0;\n vertical-align: middle;\n }\n .navbar-form .radio label,\n .navbar-form .checkbox label {\n padding-left: 0;\n }\n .navbar-form .radio input[type=\"radio\"],\n .navbar-form .checkbox input[type=\"checkbox\"] {\n position: relative;\n margin-left: 0;\n }\n .navbar-form .has-feedback .form-control-feedback {\n top: 0;\n }\n}\n@media (max-width: 767px) {\n .navbar-form .form-group {\n margin-bottom: 5px;\n }\n .navbar-form .form-group:last-child {\n margin-bottom: 0;\n }\n}\n@media (min-width: 768px) {\n .navbar-form {\n width: auto;\n border: 0;\n margin-left: 0;\n margin-right: 0;\n padding-top: 0;\n padding-bottom: 0;\n -webkit-box-shadow: none;\n box-shadow: none;\n }\n}\n.navbar-nav > li > .dropdown-menu {\n margin-top: 0;\n border-top-right-radius: 0;\n border-top-left-radius: 0;\n}\n.navbar-fixed-bottom .navbar-nav > li > .dropdown-menu {\n margin-bottom: 0;\n border-top-right-radius: 4px;\n border-top-left-radius: 4px;\n border-bottom-right-radius: 0;\n border-bottom-left-radius: 0;\n}\n.navbar-btn {\n margin-top: 8px;\n margin-bottom: 8px;\n}\n.navbar-btn.btn-sm {\n margin-top: 10px;\n margin-bottom: 10px;\n}\n.navbar-btn.btn-xs {\n margin-top: 14px;\n margin-bottom: 14px;\n}\n.navbar-text {\n margin-top: 15px;\n margin-bottom: 15px;\n}\n@media (min-width: 768px) {\n .navbar-text {\n float: left;\n margin-left: 15px;\n margin-right: 15px;\n }\n}\n@media (min-width: 768px) {\n .navbar-left {\n float: left !important;\n }\n .navbar-right {\n float: right !important;\n margin-right: -15px;\n }\n .navbar-right ~ .navbar-right {\n margin-right: 0;\n }\n}\n.navbar-default {\n background-color: #f8f8f8;\n border-color: #e7e7e7;\n}\n.navbar-default .navbar-brand {\n color: #777;\n}\n.navbar-default .navbar-brand:hover,\n.navbar-default .navbar-brand:focus {\n color: #5e5e5e;\n background-color: transparent;\n}\n.navbar-default .navbar-text {\n color: #777;\n}\n.navbar-default .navbar-nav > li > a {\n color: #777;\n}\n.navbar-default .navbar-nav > li > a:hover,\n.navbar-default .navbar-nav > li > a:focus {\n color: #333;\n background-color: transparent;\n}\n.navbar-default .navbar-nav > .active > a,\n.navbar-default .navbar-nav > .active > a:hover,\n.navbar-default .navbar-nav > .active > a:focus {\n color: #555;\n background-color: #e7e7e7;\n}\n.navbar-default .navbar-nav > .disabled > a,\n.navbar-default .navbar-nav > .disabled > a:hover,\n.navbar-default .navbar-nav > .disabled > a:focus {\n color: #ccc;\n background-color: transparent;\n}\n.navbar-default .navbar-toggle {\n border-color: #ddd;\n}\n.navbar-default .navbar-toggle:hover,\n.navbar-default .navbar-toggle:focus {\n background-color: #ddd;\n}\n.navbar-default .navbar-toggle .icon-bar {\n background-color: #888;\n}\n.navbar-default .navbar-collapse,\n.navbar-default .navbar-form {\n border-color: #e7e7e7;\n}\n.navbar-default .navbar-nav > .open > a,\n.navbar-default .navbar-nav > .open > a:hover,\n.navbar-default .navbar-nav > .open > a:focus {\n background-color: #e7e7e7;\n color: #555;\n}\n@media (max-width: 767px) {\n .navbar-default .navbar-nav .open .dropdown-menu > li > a {\n color: #777;\n }\n .navbar-default .navbar-nav .open .dropdown-menu > li > a:hover,\n .navbar-default .navbar-nav .open .dropdown-menu > li > a:focus {\n color: #333;\n background-color: transparent;\n }\n .navbar-default .navbar-nav .open .dropdown-menu > .active > a,\n .navbar-default .navbar-nav .open .dropdown-menu > .active > a:hover,\n .navbar-default .navbar-nav .open .dropdown-menu > .active > a:focus {\n color: #555;\n background-color: #e7e7e7;\n }\n .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a,\n .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a:hover,\n .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a:focus {\n color: #ccc;\n background-color: transparent;\n }\n}\n.navbar-default .navbar-link {\n color: #777;\n}\n.navbar-default .navbar-link:hover {\n color: #333;\n}\n.navbar-default .btn-link {\n color: #777;\n}\n.navbar-default .btn-link:hover,\n.navbar-default .btn-link:focus {\n color: #333;\n}\n.navbar-default .btn-link[disabled]:hover,\nfieldset[disabled] .navbar-default .btn-link:hover,\n.navbar-default .btn-link[disabled]:focus,\nfieldset[disabled] .navbar-default .btn-link:focus {\n color: #ccc;\n}\n.navbar-inverse {\n background-color: #222;\n border-color: #080808;\n}\n.navbar-inverse .navbar-brand {\n color: #9d9d9d;\n}\n.navbar-inverse .navbar-brand:hover,\n.navbar-inverse .navbar-brand:focus {\n color: #fff;\n background-color: transparent;\n}\n.navbar-inverse .navbar-text {\n color: #9d9d9d;\n}\n.navbar-inverse .navbar-nav > li > a {\n color: #9d9d9d;\n}\n.navbar-inverse .navbar-nav > li > a:hover,\n.navbar-inverse .navbar-nav > li > a:focus {\n color: #fff;\n background-color: transparent;\n}\n.navbar-inverse .navbar-nav > .active > a,\n.navbar-inverse .navbar-nav > .active > a:hover,\n.navbar-inverse .navbar-nav > .active > a:focus {\n color: #fff;\n background-color: #080808;\n}\n.navbar-inverse .navbar-nav > .disabled > a,\n.navbar-inverse .navbar-nav > .disabled > a:hover,\n.navbar-inverse .navbar-nav > .disabled > a:focus {\n color: #444;\n background-color: transparent;\n}\n.navbar-inverse .navbar-toggle {\n border-color: #333;\n}\n.navbar-inverse .navbar-toggle:hover,\n.navbar-inverse .navbar-toggle:focus {\n background-color: #333;\n}\n.navbar-inverse .navbar-toggle .icon-bar {\n background-color: #fff;\n}\n.navbar-inverse .navbar-collapse,\n.navbar-inverse .navbar-form {\n border-color: #101010;\n}\n.navbar-inverse .navbar-nav > .open > a,\n.navbar-inverse .navbar-nav > .open > a:hover,\n.navbar-inverse .navbar-nav > .open > a:focus {\n background-color: #080808;\n color: #fff;\n}\n@media (max-width: 767px) {\n .navbar-inverse .navbar-nav .open .dropdown-menu > .dropdown-header {\n border-color: #080808;\n }\n .navbar-inverse .navbar-nav .open .dropdown-menu .divider {\n background-color: #080808;\n }\n .navbar-inverse .navbar-nav .open .dropdown-menu > li > a {\n color: #9d9d9d;\n }\n .navbar-inverse .navbar-nav .open .dropdown-menu > li > a:hover,\n .navbar-inverse .navbar-nav .open .dropdown-menu > li > a:focus {\n color: #fff;\n background-color: transparent;\n }\n .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a,\n .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a:hover,\n .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a:focus {\n color: #fff;\n background-color: #080808;\n }\n .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a,\n .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a:hover,\n .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a:focus {\n color: #444;\n background-color: transparent;\n }\n}\n.navbar-inverse .navbar-link {\n color: #9d9d9d;\n}\n.navbar-inverse .navbar-link:hover {\n color: #fff;\n}\n.navbar-inverse .btn-link {\n color: #9d9d9d;\n}\n.navbar-inverse .btn-link:hover,\n.navbar-inverse .btn-link:focus {\n color: #fff;\n}\n.navbar-inverse .btn-link[disabled]:hover,\nfieldset[disabled] .navbar-inverse .btn-link:hover,\n.navbar-inverse .btn-link[disabled]:focus,\nfieldset[disabled] .navbar-inverse .btn-link:focus {\n color: #444;\n}\n.breadcrumb {\n padding: 8px 15px;\n margin-bottom: 20px;\n list-style: none;\n background-color: #f5f5f5;\n border-radius: 4px;\n}\n.breadcrumb > li {\n display: inline-block;\n}\n.breadcrumb > li + li:before {\n content: \"/\\00a0\";\n padding: 0 5px;\n color: #ccc;\n}\n.breadcrumb > .active {\n color: #777777;\n}\n.pagination {\n display: inline-block;\n padding-left: 0;\n margin: 20px 0;\n border-radius: 4px;\n}\n.pagination > li {\n display: inline;\n}\n.pagination > li > a,\n.pagination > li > span {\n position: relative;\n float: left;\n padding: 6px 12px;\n line-height: 1.42857143;\n text-decoration: none;\n color: #337ab7;\n background-color: #fff;\n border: 1px solid #ddd;\n margin-left: -1px;\n}\n.pagination > li:first-child > a,\n.pagination > li:first-child > span {\n margin-left: 0;\n border-bottom-left-radius: 4px;\n border-top-left-radius: 4px;\n}\n.pagination > li:last-child > a,\n.pagination > li:last-child > span {\n border-bottom-right-radius: 4px;\n border-top-right-radius: 4px;\n}\n.pagination > li > a:hover,\n.pagination > li > span:hover,\n.pagination > li > a:focus,\n.pagination > li > span:focus {\n z-index: 2;\n color: #23527c;\n background-color: #eeeeee;\n border-color: #ddd;\n}\n.pagination > .active > a,\n.pagination > .active > span,\n.pagination > .active > a:hover,\n.pagination > .active > span:hover,\n.pagination > .active > a:focus,\n.pagination > .active > span:focus {\n z-index: 3;\n color: #fff;\n background-color: #337ab7;\n border-color: #337ab7;\n cursor: default;\n}\n.pagination > .disabled > span,\n.pagination > .disabled > span:hover,\n.pagination > .disabled > span:focus,\n.pagination > .disabled > a,\n.pagination > .disabled > a:hover,\n.pagination > .disabled > a:focus {\n color: #777777;\n background-color: #fff;\n border-color: #ddd;\n cursor: not-allowed;\n}\n.pagination-lg > li > a,\n.pagination-lg > li > span {\n padding: 10px 16px;\n font-size: 18px;\n line-height: 1.3333333;\n}\n.pagination-lg > li:first-child > a,\n.pagination-lg > li:first-child > span {\n border-bottom-left-radius: 6px;\n border-top-left-radius: 6px;\n}\n.pagination-lg > li:last-child > a,\n.pagination-lg > li:last-child > span {\n border-bottom-right-radius: 6px;\n border-top-right-radius: 6px;\n}\n.pagination-sm > li > a,\n.pagination-sm > li > span {\n padding: 5px 10px;\n font-size: 12px;\n line-height: 1.5;\n}\n.pagination-sm > li:first-child > a,\n.pagination-sm > li:first-child > span {\n border-bottom-left-radius: 3px;\n border-top-left-radius: 3px;\n}\n.pagination-sm > li:last-child > a,\n.pagination-sm > li:last-child > span {\n border-bottom-right-radius: 3px;\n border-top-right-radius: 3px;\n}\n.pager {\n padding-left: 0;\n margin: 20px 0;\n list-style: none;\n text-align: center;\n}\n.pager li {\n display: inline;\n}\n.pager li > a,\n.pager li > span {\n display: inline-block;\n padding: 5px 14px;\n background-color: #fff;\n border: 1px solid #ddd;\n border-radius: 15px;\n}\n.pager li > a:hover,\n.pager li > a:focus {\n text-decoration: none;\n background-color: #eeeeee;\n}\n.pager .next > a,\n.pager .next > span {\n float: right;\n}\n.pager .previous > a,\n.pager .previous > span {\n float: left;\n}\n.pager .disabled > a,\n.pager .disabled > a:hover,\n.pager .disabled > a:focus,\n.pager .disabled > span {\n color: #777777;\n background-color: #fff;\n cursor: not-allowed;\n}\n.label {\n display: inline;\n padding: .2em .6em .3em;\n font-size: 75%;\n font-weight: bold;\n line-height: 1;\n color: #fff;\n text-align: center;\n white-space: nowrap;\n vertical-align: baseline;\n border-radius: .25em;\n}\na.label:hover,\na.label:focus {\n color: #fff;\n text-decoration: none;\n cursor: pointer;\n}\n.label:empty {\n display: none;\n}\n.btn .label {\n position: relative;\n top: -1px;\n}\n.label-default {\n background-color: #777777;\n}\n.label-default[href]:hover,\n.label-default[href]:focus {\n background-color: #5e5e5e;\n}\n.label-primary {\n background-color: #337ab7;\n}\n.label-primary[href]:hover,\n.label-primary[href]:focus {\n background-color: #286090;\n}\n.label-success {\n background-color: #5cb85c;\n}\n.label-success[href]:hover,\n.label-success[href]:focus {\n background-color: #449d44;\n}\n.label-info {\n background-color: #5bc0de;\n}\n.label-info[href]:hover,\n.label-info[href]:focus {\n background-color: #31b0d5;\n}\n.label-warning {\n background-color: #f0ad4e;\n}\n.label-warning[href]:hover,\n.label-warning[href]:focus {\n background-color: #ec971f;\n}\n.label-danger {\n background-color: #d9534f;\n}\n.label-danger[href]:hover,\n.label-danger[href]:focus {\n background-color: #c9302c;\n}\n.badge {\n display: inline-block;\n min-width: 10px;\n padding: 3px 7px;\n font-size: 12px;\n font-weight: bold;\n color: #fff;\n line-height: 1;\n vertical-align: middle;\n white-space: nowrap;\n text-align: center;\n background-color: #777777;\n border-radius: 10px;\n}\n.badge:empty {\n display: none;\n}\n.btn .badge {\n position: relative;\n top: -1px;\n}\n.btn-xs .badge,\n.btn-group-xs > .btn .badge {\n top: 0;\n padding: 1px 5px;\n}\na.badge:hover,\na.badge:focus {\n color: #fff;\n text-decoration: none;\n cursor: pointer;\n}\n.list-group-item.active > .badge,\n.nav-pills > .active > a > .badge {\n color: #337ab7;\n background-color: #fff;\n}\n.list-group-item > .badge {\n float: right;\n}\n.list-group-item > .badge + .badge {\n margin-right: 5px;\n}\n.nav-pills > li > a > .badge {\n margin-left: 3px;\n}\n.jumbotron {\n padding-top: 30px;\n padding-bottom: 30px;\n margin-bottom: 30px;\n color: inherit;\n background-color: #eeeeee;\n}\n.jumbotron h1,\n.jumbotron .h1 {\n color: inherit;\n}\n.jumbotron p {\n margin-bottom: 15px;\n font-size: 21px;\n font-weight: 200;\n}\n.jumbotron > hr {\n border-top-color: #d5d5d5;\n}\n.container .jumbotron,\n.container-fluid .jumbotron {\n border-radius: 6px;\n padding-left: 15px;\n padding-right: 15px;\n}\n.jumbotron .container {\n max-width: 100%;\n}\n@media screen and (min-width: 768px) {\n .jumbotron {\n padding-top: 48px;\n padding-bottom: 48px;\n }\n .container .jumbotron,\n .container-fluid .jumbotron {\n padding-left: 60px;\n padding-right: 60px;\n }\n .jumbotron h1,\n .jumbotron .h1 {\n font-size: 63px;\n }\n}\n.thumbnail {\n display: block;\n padding: 4px;\n margin-bottom: 20px;\n line-height: 1.42857143;\n background-color: #fff;\n border: 1px solid #ddd;\n border-radius: 4px;\n -webkit-transition: border 0.2s ease-in-out;\n -o-transition: border 0.2s ease-in-out;\n transition: border 0.2s ease-in-out;\n}\n.thumbnail > img,\n.thumbnail a > img {\n margin-left: auto;\n margin-right: auto;\n}\na.thumbnail:hover,\na.thumbnail:focus,\na.thumbnail.active {\n border-color: #337ab7;\n}\n.thumbnail .caption {\n padding: 9px;\n color: #333333;\n}\n.alert {\n padding: 15px;\n margin-bottom: 20px;\n border: 1px solid transparent;\n border-radius: 4px;\n}\n.alert h4 {\n margin-top: 0;\n color: inherit;\n}\n.alert .alert-link {\n font-weight: bold;\n}\n.alert > p,\n.alert > ul {\n margin-bottom: 0;\n}\n.alert > p + p {\n margin-top: 5px;\n}\n.alert-dismissable,\n.alert-dismissible {\n padding-right: 35px;\n}\n.alert-dismissable .close,\n.alert-dismissible .close {\n position: relative;\n top: -2px;\n right: -21px;\n color: inherit;\n}\n.alert-success {\n background-color: #dff0d8;\n border-color: #d6e9c6;\n color: #3c763d;\n}\n.alert-success hr {\n border-top-color: #c9e2b3;\n}\n.alert-success .alert-link {\n color: #2b542c;\n}\n.alert-info {\n background-color: #d9edf7;\n border-color: #bce8f1;\n color: #31708f;\n}\n.alert-info hr {\n border-top-color: #a6e1ec;\n}\n.alert-info .alert-link {\n color: #245269;\n}\n.alert-warning {\n background-color: #fcf8e3;\n border-color: #faebcc;\n color: #8a6d3b;\n}\n.alert-warning hr {\n border-top-color: #f7e1b5;\n}\n.alert-warning .alert-link {\n color: #66512c;\n}\n.alert-danger {\n background-color: #f2dede;\n border-color: #ebccd1;\n color: #a94442;\n}\n.alert-danger hr {\n border-top-color: #e4b9c0;\n}\n.alert-danger .alert-link {\n color: #843534;\n}\n@-webkit-keyframes progress-bar-stripes {\n from {\n background-position: 40px 0;\n }\n to {\n background-position: 0 0;\n }\n}\n@keyframes progress-bar-stripes {\n from {\n background-position: 40px 0;\n }\n to {\n background-position: 0 0;\n }\n}\n.progress {\n overflow: hidden;\n height: 20px;\n margin-bottom: 20px;\n background-color: #f5f5f5;\n border-radius: 4px;\n -webkit-box-shadow: inset 0 1px 2px rgba(0, 0, 0, 0.1);\n box-shadow: inset 0 1px 2px rgba(0, 0, 0, 0.1);\n}\n.progress-bar {\n float: left;\n width: 0%;\n height: 100%;\n font-size: 12px;\n line-height: 20px;\n color: #fff;\n text-align: center;\n background-color: #337ab7;\n -webkit-box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.15);\n box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.15);\n -webkit-transition: width 0.6s ease;\n -o-transition: width 0.6s ease;\n transition: width 0.6s ease;\n}\n.progress-striped .progress-bar,\n.progress-bar-striped {\n background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-size: 40px 40px;\n}\n.progress.active .progress-bar,\n.progress-bar.active {\n -webkit-animation: progress-bar-stripes 2s linear infinite;\n -o-animation: progress-bar-stripes 2s linear infinite;\n animation: progress-bar-stripes 2s linear infinite;\n}\n.progress-bar-success {\n background-color: #5cb85c;\n}\n.progress-striped .progress-bar-success {\n background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n}\n.progress-bar-info {\n background-color: #5bc0de;\n}\n.progress-striped .progress-bar-info {\n background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n}\n.progress-bar-warning {\n background-color: #f0ad4e;\n}\n.progress-striped .progress-bar-warning {\n background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n}\n.progress-bar-danger {\n background-color: #d9534f;\n}\n.progress-striped .progress-bar-danger {\n background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n}\n.media {\n margin-top: 15px;\n}\n.media:first-child {\n margin-top: 0;\n}\n.media,\n.media-body {\n zoom: 1;\n overflow: hidden;\n}\n.media-body {\n width: 10000px;\n}\n.media-object {\n display: block;\n}\n.media-object.img-thumbnail {\n max-width: none;\n}\n.media-right,\n.media > .pull-right {\n padding-left: 10px;\n}\n.media-left,\n.media > .pull-left {\n padding-right: 10px;\n}\n.media-left,\n.media-right,\n.media-body {\n display: table-cell;\n vertical-align: top;\n}\n.media-middle {\n vertical-align: middle;\n}\n.media-bottom {\n vertical-align: bottom;\n}\n.media-heading {\n margin-top: 0;\n margin-bottom: 5px;\n}\n.media-list {\n padding-left: 0;\n list-style: none;\n}\n.list-group {\n margin-bottom: 20px;\n padding-left: 0;\n}\n.list-group-item {\n position: relative;\n display: block;\n padding: 10px 15px;\n margin-bottom: -1px;\n background-color: #fff;\n border: 1px solid #ddd;\n}\n.list-group-item:first-child {\n border-top-right-radius: 4px;\n border-top-left-radius: 4px;\n}\n.list-group-item:last-child {\n margin-bottom: 0;\n border-bottom-right-radius: 4px;\n border-bottom-left-radius: 4px;\n}\na.list-group-item,\nbutton.list-group-item {\n color: #555;\n}\na.list-group-item .list-group-item-heading,\nbutton.list-group-item .list-group-item-heading {\n color: #333;\n}\na.list-group-item:hover,\nbutton.list-group-item:hover,\na.list-group-item:focus,\nbutton.list-group-item:focus {\n text-decoration: none;\n color: #555;\n background-color: #f5f5f5;\n}\nbutton.list-group-item {\n width: 100%;\n text-align: left;\n}\n.list-group-item.disabled,\n.list-group-item.disabled:hover,\n.list-group-item.disabled:focus {\n background-color: #eeeeee;\n color: #777777;\n cursor: not-allowed;\n}\n.list-group-item.disabled .list-group-item-heading,\n.list-group-item.disabled:hover .list-group-item-heading,\n.list-group-item.disabled:focus .list-group-item-heading {\n color: inherit;\n}\n.list-group-item.disabled .list-group-item-text,\n.list-group-item.disabled:hover .list-group-item-text,\n.list-group-item.disabled:focus .list-group-item-text {\n color: #777777;\n}\n.list-group-item.active,\n.list-group-item.active:hover,\n.list-group-item.active:focus {\n z-index: 2;\n color: #fff;\n background-color: #337ab7;\n border-color: #337ab7;\n}\n.list-group-item.active .list-group-item-heading,\n.list-group-item.active:hover .list-group-item-heading,\n.list-group-item.active:focus .list-group-item-heading,\n.list-group-item.active .list-group-item-heading > small,\n.list-group-item.active:hover .list-group-item-heading > small,\n.list-group-item.active:focus .list-group-item-heading > small,\n.list-group-item.active .list-group-item-heading > .small,\n.list-group-item.active:hover .list-group-item-heading > .small,\n.list-group-item.active:focus .list-group-item-heading > .small {\n color: inherit;\n}\n.list-group-item.active .list-group-item-text,\n.list-group-item.active:hover .list-group-item-text,\n.list-group-item.active:focus .list-group-item-text {\n color: #c7ddef;\n}\n.list-group-item-success {\n color: #3c763d;\n background-color: #dff0d8;\n}\na.list-group-item-success,\nbutton.list-group-item-success {\n color: #3c763d;\n}\na.list-group-item-success .list-group-item-heading,\nbutton.list-group-item-success .list-group-item-heading {\n color: inherit;\n}\na.list-group-item-success:hover,\nbutton.list-group-item-success:hover,\na.list-group-item-success:focus,\nbutton.list-group-item-success:focus {\n color: #3c763d;\n background-color: #d0e9c6;\n}\na.list-group-item-success.active,\nbutton.list-group-item-success.active,\na.list-group-item-success.active:hover,\nbutton.list-group-item-success.active:hover,\na.list-group-item-success.active:focus,\nbutton.list-group-item-success.active:focus {\n color: #fff;\n background-color: #3c763d;\n border-color: #3c763d;\n}\n.list-group-item-info {\n color: #31708f;\n background-color: #d9edf7;\n}\na.list-group-item-info,\nbutton.list-group-item-info {\n color: #31708f;\n}\na.list-group-item-info .list-group-item-heading,\nbutton.list-group-item-info .list-group-item-heading {\n color: inherit;\n}\na.list-group-item-info:hover,\nbutton.list-group-item-info:hover,\na.list-group-item-info:focus,\nbutton.list-group-item-info:focus {\n color: #31708f;\n background-color: #c4e3f3;\n}\na.list-group-item-info.active,\nbutton.list-group-item-info.active,\na.list-group-item-info.active:hover,\nbutton.list-group-item-info.active:hover,\na.list-group-item-info.active:focus,\nbutton.list-group-item-info.active:focus {\n color: #fff;\n background-color: #31708f;\n border-color: #31708f;\n}\n.list-group-item-warning {\n color: #8a6d3b;\n background-color: #fcf8e3;\n}\na.list-group-item-warning,\nbutton.list-group-item-warning {\n color: #8a6d3b;\n}\na.list-group-item-warning .list-group-item-heading,\nbutton.list-group-item-warning .list-group-item-heading {\n color: inherit;\n}\na.list-group-item-warning:hover,\nbutton.list-group-item-warning:hover,\na.list-group-item-warning:focus,\nbutton.list-group-item-warning:focus {\n color: #8a6d3b;\n background-color: #faf2cc;\n}\na.list-group-item-warning.active,\nbutton.list-group-item-warning.active,\na.list-group-item-warning.active:hover,\nbutton.list-group-item-warning.active:hover,\na.list-group-item-warning.active:focus,\nbutton.list-group-item-warning.active:focus {\n color: #fff;\n background-color: #8a6d3b;\n border-color: #8a6d3b;\n}\n.list-group-item-danger {\n color: #a94442;\n background-color: #f2dede;\n}\na.list-group-item-danger,\nbutton.list-group-item-danger {\n color: #a94442;\n}\na.list-group-item-danger .list-group-item-heading,\nbutton.list-group-item-danger .list-group-item-heading {\n color: inherit;\n}\na.list-group-item-danger:hover,\nbutton.list-group-item-danger:hover,\na.list-group-item-danger:focus,\nbutton.list-group-item-danger:focus {\n color: #a94442;\n background-color: #ebcccc;\n}\na.list-group-item-danger.active,\nbutton.list-group-item-danger.active,\na.list-group-item-danger.active:hover,\nbutton.list-group-item-danger.active:hover,\na.list-group-item-danger.active:focus,\nbutton.list-group-item-danger.active:focus {\n color: #fff;\n background-color: #a94442;\n border-color: #a94442;\n}\n.list-group-item-heading {\n margin-top: 0;\n margin-bottom: 5px;\n}\n.list-group-item-text {\n margin-bottom: 0;\n line-height: 1.3;\n}\n.panel {\n margin-bottom: 20px;\n background-color: #fff;\n border: 1px solid transparent;\n border-radius: 4px;\n -webkit-box-shadow: 0 1px 1px rgba(0, 0, 0, 0.05);\n box-shadow: 0 1px 1px rgba(0, 0, 0, 0.05);\n}\n.panel-body {\n padding: 15px;\n}\n.panel-heading {\n padding: 10px 15px;\n border-bottom: 1px solid transparent;\n border-top-right-radius: 3px;\n border-top-left-radius: 3px;\n}\n.panel-heading > .dropdown .dropdown-toggle {\n color: inherit;\n}\n.panel-title {\n margin-top: 0;\n margin-bottom: 0;\n font-size: 16px;\n color: inherit;\n}\n.panel-title > a,\n.panel-title > small,\n.panel-title > .small,\n.panel-title > small > a,\n.panel-title > .small > a {\n color: inherit;\n}\n.panel-footer {\n padding: 10px 15px;\n background-color: #f5f5f5;\n border-top: 1px solid #ddd;\n border-bottom-right-radius: 3px;\n border-bottom-left-radius: 3px;\n}\n.panel > .list-group,\n.panel > .panel-collapse > .list-group {\n margin-bottom: 0;\n}\n.panel > .list-group .list-group-item,\n.panel > .panel-collapse > .list-group .list-group-item {\n border-width: 1px 0;\n border-radius: 0;\n}\n.panel > .list-group:first-child .list-group-item:first-child,\n.panel > .panel-collapse > .list-group:first-child .list-group-item:first-child {\n border-top: 0;\n border-top-right-radius: 3px;\n border-top-left-radius: 3px;\n}\n.panel > .list-group:last-child .list-group-item:last-child,\n.panel > .panel-collapse > .list-group:last-child .list-group-item:last-child {\n border-bottom: 0;\n border-bottom-right-radius: 3px;\n border-bottom-left-radius: 3px;\n}\n.panel > .panel-heading + .panel-collapse > .list-group .list-group-item:first-child {\n border-top-right-radius: 0;\n border-top-left-radius: 0;\n}\n.panel-heading + .list-group .list-group-item:first-child {\n border-top-width: 0;\n}\n.list-group + .panel-footer {\n border-top-width: 0;\n}\n.panel > .table,\n.panel > .table-responsive > .table,\n.panel > .panel-collapse > .table {\n margin-bottom: 0;\n}\n.panel > .table caption,\n.panel > .table-responsive > .table caption,\n.panel > .panel-collapse > .table caption {\n padding-left: 15px;\n padding-right: 15px;\n}\n.panel > .table:first-child,\n.panel > .table-responsive:first-child > .table:first-child {\n border-top-right-radius: 3px;\n border-top-left-radius: 3px;\n}\n.panel > .table:first-child > thead:first-child > tr:first-child,\n.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child,\n.panel > .table:first-child > tbody:first-child > tr:first-child,\n.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child {\n border-top-left-radius: 3px;\n border-top-right-radius: 3px;\n}\n.panel > .table:first-child > thead:first-child > tr:first-child td:first-child,\n.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child td:first-child,\n.panel > .table:first-child > tbody:first-child > tr:first-child td:first-child,\n.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child td:first-child,\n.panel > .table:first-child > thead:first-child > tr:first-child th:first-child,\n.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child th:first-child,\n.panel > .table:first-child > tbody:first-child > tr:first-child th:first-child,\n.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child th:first-child {\n border-top-left-radius: 3px;\n}\n.panel > .table:first-child > thead:first-child > tr:first-child td:last-child,\n.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child td:last-child,\n.panel > .table:first-child > tbody:first-child > tr:first-child td:last-child,\n.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child td:last-child,\n.panel > .table:first-child > thead:first-child > tr:first-child th:last-child,\n.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child th:last-child,\n.panel > .table:first-child > tbody:first-child > tr:first-child th:last-child,\n.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child th:last-child {\n border-top-right-radius: 3px;\n}\n.panel > .table:last-child,\n.panel > .table-responsive:last-child > .table:last-child {\n border-bottom-right-radius: 3px;\n border-bottom-left-radius: 3px;\n}\n.panel > .table:last-child > tbody:last-child > tr:last-child,\n.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child,\n.panel > .table:last-child > tfoot:last-child > tr:last-child,\n.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child {\n border-bottom-left-radius: 3px;\n border-bottom-right-radius: 3px;\n}\n.panel > .table:last-child > tbody:last-child > tr:last-child td:first-child,\n.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child td:first-child,\n.panel > .table:last-child > tfoot:last-child > tr:last-child td:first-child,\n.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child td:first-child,\n.panel > .table:last-child > tbody:last-child > tr:last-child th:first-child,\n.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child th:first-child,\n.panel > .table:last-child > tfoot:last-child > tr:last-child th:first-child,\n.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child th:first-child {\n border-bottom-left-radius: 3px;\n}\n.panel > .table:last-child > tbody:last-child > tr:last-child td:last-child,\n.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child td:last-child,\n.panel > .table:last-child > tfoot:last-child > tr:last-child td:last-child,\n.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child td:last-child,\n.panel > .table:last-child > tbody:last-child > tr:last-child th:last-child,\n.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child th:last-child,\n.panel > .table:last-child > tfoot:last-child > tr:last-child th:last-child,\n.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child th:last-child {\n border-bottom-right-radius: 3px;\n}\n.panel > .panel-body + .table,\n.panel > .panel-body + .table-responsive,\n.panel > .table + .panel-body,\n.panel > .table-responsive + .panel-body {\n border-top: 1px solid #ddd;\n}\n.panel > .table > tbody:first-child > tr:first-child th,\n.panel > .table > tbody:first-child > tr:first-child td {\n border-top: 0;\n}\n.panel > .table-bordered,\n.panel > .table-responsive > .table-bordered {\n border: 0;\n}\n.panel > .table-bordered > thead > tr > th:first-child,\n.panel > .table-responsive > .table-bordered > thead > tr > th:first-child,\n.panel > .table-bordered > tbody > tr > th:first-child,\n.panel > .table-responsive > .table-bordered > tbody > tr > th:first-child,\n.panel > .table-bordered > tfoot > tr > th:first-child,\n.panel > .table-responsive > .table-bordered > tfoot > tr > th:first-child,\n.panel > .table-bordered > thead > tr > td:first-child,\n.panel > .table-responsive > .table-bordered > thead > tr > td:first-child,\n.panel > .table-bordered > tbody > tr > td:first-child,\n.panel > .table-responsive > .table-bordered > tbody > tr > td:first-child,\n.panel > .table-bordered > tfoot > tr > td:first-child,\n.panel > .table-responsive > .table-bordered > tfoot > tr > td:first-child {\n border-left: 0;\n}\n.panel > .table-bordered > thead > tr > th:last-child,\n.panel > .table-responsive > .table-bordered > thead > tr > th:last-child,\n.panel > .table-bordered > tbody > tr > th:last-child,\n.panel > .table-responsive > .table-bordered > tbody > tr > th:last-child,\n.panel > .table-bordered > tfoot > tr > th:last-child,\n.panel > .table-responsive > .table-bordered > tfoot > tr > th:last-child,\n.panel > .table-bordered > thead > tr > td:last-child,\n.panel > .table-responsive > .table-bordered > thead > tr > td:last-child,\n.panel > .table-bordered > tbody > tr > td:last-child,\n.panel > .table-responsive > .table-bordered > tbody > tr > td:last-child,\n.panel > .table-bordered > tfoot > tr > td:last-child,\n.panel > .table-responsive > .table-bordered > tfoot > tr > td:last-child {\n border-right: 0;\n}\n.panel > .table-bordered > thead > tr:first-child > td,\n.panel > .table-responsive > .table-bordered > thead > tr:first-child > td,\n.panel > .table-bordered > tbody > tr:first-child > td,\n.panel > .table-responsive > .table-bordered > tbody > tr:first-child > td,\n.panel > .table-bordered > thead > tr:first-child > th,\n.panel > .table-responsive > .table-bordered > thead > tr:first-child > th,\n.panel > .table-bordered > tbody > tr:first-child > th,\n.panel > .table-responsive > .table-bordered > tbody > tr:first-child > th {\n border-bottom: 0;\n}\n.panel > .table-bordered > tbody > tr:last-child > td,\n.panel > .table-responsive > .table-bordered > tbody > tr:last-child > td,\n.panel > .table-bordered > tfoot > tr:last-child > td,\n.panel > .table-responsive > .table-bordered > tfoot > tr:last-child > td,\n.panel > .table-bordered > tbody > tr:last-child > th,\n.panel > .table-responsive > .table-bordered > tbody > tr:last-child > th,\n.panel > .table-bordered > tfoot > tr:last-child > th,\n.panel > .table-responsive > .table-bordered > tfoot > tr:last-child > th {\n border-bottom: 0;\n}\n.panel > .table-responsive {\n border: 0;\n margin-bottom: 0;\n}\n.panel-group {\n margin-bottom: 20px;\n}\n.panel-group .panel {\n margin-bottom: 0;\n border-radius: 4px;\n}\n.panel-group .panel + .panel {\n margin-top: 5px;\n}\n.panel-group .panel-heading {\n border-bottom: 0;\n}\n.panel-group .panel-heading + .panel-collapse > .panel-body,\n.panel-group .panel-heading + .panel-collapse > .list-group {\n border-top: 1px solid #ddd;\n}\n.panel-group .panel-footer {\n border-top: 0;\n}\n.panel-group .panel-footer + .panel-collapse .panel-body {\n border-bottom: 1px solid #ddd;\n}\n.panel-default {\n border-color: #ddd;\n}\n.panel-default > .panel-heading {\n color: #333333;\n background-color: #f5f5f5;\n border-color: #ddd;\n}\n.panel-default > .panel-heading + .panel-collapse > .panel-body {\n border-top-color: #ddd;\n}\n.panel-default > .panel-heading .badge {\n color: #f5f5f5;\n background-color: #333333;\n}\n.panel-default > .panel-footer + .panel-collapse > .panel-body {\n border-bottom-color: #ddd;\n}\n.panel-primary {\n border-color: #337ab7;\n}\n.panel-primary > .panel-heading {\n color: #fff;\n background-color: #337ab7;\n border-color: #337ab7;\n}\n.panel-primary > .panel-heading + .panel-collapse > .panel-body {\n border-top-color: #337ab7;\n}\n.panel-primary > .panel-heading .badge {\n color: #337ab7;\n background-color: #fff;\n}\n.panel-primary > .panel-footer + .panel-collapse > .panel-body {\n border-bottom-color: #337ab7;\n}\n.panel-success {\n border-color: #d6e9c6;\n}\n.panel-success > .panel-heading {\n color: #3c763d;\n background-color: #dff0d8;\n border-color: #d6e9c6;\n}\n.panel-success > .panel-heading + .panel-collapse > .panel-body {\n border-top-color: #d6e9c6;\n}\n.panel-success > .panel-heading .badge {\n color: #dff0d8;\n background-color: #3c763d;\n}\n.panel-success > .panel-footer + .panel-collapse > .panel-body {\n border-bottom-color: #d6e9c6;\n}\n.panel-info {\n border-color: #bce8f1;\n}\n.panel-info > .panel-heading {\n color: #31708f;\n background-color: #d9edf7;\n border-color: #bce8f1;\n}\n.panel-info > .panel-heading + .panel-collapse > .panel-body {\n border-top-color: #bce8f1;\n}\n.panel-info > .panel-heading .badge {\n color: #d9edf7;\n background-color: #31708f;\n}\n.panel-info > .panel-footer + .panel-collapse > .panel-body {\n border-bottom-color: #bce8f1;\n}\n.panel-warning {\n border-color: #faebcc;\n}\n.panel-warning > .panel-heading {\n color: #8a6d3b;\n background-color: #fcf8e3;\n border-color: #faebcc;\n}\n.panel-warning > .panel-heading + .panel-collapse > .panel-body {\n border-top-color: #faebcc;\n}\n.panel-warning > .panel-heading .badge {\n color: #fcf8e3;\n background-color: #8a6d3b;\n}\n.panel-warning > .panel-footer + .panel-collapse > .panel-body {\n border-bottom-color: #faebcc;\n}\n.panel-danger {\n border-color: #ebccd1;\n}\n.panel-danger > .panel-heading {\n color: #a94442;\n background-color: #f2dede;\n border-color: #ebccd1;\n}\n.panel-danger > .panel-heading + .panel-collapse > .panel-body {\n border-top-color: #ebccd1;\n}\n.panel-danger > .panel-heading .badge {\n color: #f2dede;\n background-color: #a94442;\n}\n.panel-danger > .panel-footer + .panel-collapse > .panel-body {\n border-bottom-color: #ebccd1;\n}\n.embed-responsive {\n position: relative;\n display: block;\n height: 0;\n padding: 0;\n overflow: hidden;\n}\n.embed-responsive .embed-responsive-item,\n.embed-responsive iframe,\n.embed-responsive embed,\n.embed-responsive object,\n.embed-responsive video {\n position: absolute;\n top: 0;\n left: 0;\n bottom: 0;\n height: 100%;\n width: 100%;\n border: 0;\n}\n.embed-responsive-16by9 {\n padding-bottom: 56.25%;\n}\n.embed-responsive-4by3 {\n padding-bottom: 75%;\n}\n.well {\n min-height: 20px;\n padding: 19px;\n margin-bottom: 20px;\n background-color: #f5f5f5;\n border: 1px solid #e3e3e3;\n border-radius: 4px;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.05);\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.05);\n}\n.well blockquote {\n border-color: #ddd;\n border-color: rgba(0, 0, 0, 0.15);\n}\n.well-lg {\n padding: 24px;\n border-radius: 6px;\n}\n.well-sm {\n padding: 9px;\n border-radius: 3px;\n}\n.close {\n float: right;\n font-size: 21px;\n font-weight: bold;\n line-height: 1;\n color: #000;\n text-shadow: 0 1px 0 #fff;\n opacity: 0.2;\n filter: alpha(opacity=20);\n}\n.close:hover,\n.close:focus {\n color: #000;\n text-decoration: none;\n cursor: pointer;\n opacity: 0.5;\n filter: alpha(opacity=50);\n}\nbutton.close {\n padding: 0;\n cursor: pointer;\n background: transparent;\n border: 0;\n -webkit-appearance: none;\n}\n.modal-open {\n overflow: hidden;\n}\n.modal {\n display: none;\n overflow: hidden;\n position: fixed;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: 1050;\n -webkit-overflow-scrolling: touch;\n outline: 0;\n}\n.modal.fade .modal-dialog {\n -webkit-transform: translate(0, -25%);\n -ms-transform: translate(0, -25%);\n -o-transform: translate(0, -25%);\n transform: translate(0, -25%);\n -webkit-transition: -webkit-transform 0.3s ease-out;\n -moz-transition: -moz-transform 0.3s ease-out;\n -o-transition: -o-transform 0.3s ease-out;\n transition: transform 0.3s ease-out;\n}\n.modal.in .modal-dialog {\n -webkit-transform: translate(0, 0);\n -ms-transform: translate(0, 0);\n -o-transform: translate(0, 0);\n transform: translate(0, 0);\n}\n.modal-open .modal {\n overflow-x: hidden;\n overflow-y: auto;\n}\n.modal-dialog {\n position: relative;\n width: auto;\n margin: 10px;\n}\n.modal-content {\n position: relative;\n background-color: #fff;\n border: 1px solid #999;\n border: 1px solid rgba(0, 0, 0, 0.2);\n border-radius: 6px;\n -webkit-box-shadow: 0 3px 9px rgba(0, 0, 0, 0.5);\n box-shadow: 0 3px 9px rgba(0, 0, 0, 0.5);\n background-clip: padding-box;\n outline: 0;\n}\n.modal-backdrop {\n position: fixed;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: 1040;\n background-color: #000;\n}\n.modal-backdrop.fade {\n opacity: 0;\n filter: alpha(opacity=0);\n}\n.modal-backdrop.in {\n opacity: 0.5;\n filter: alpha(opacity=50);\n}\n.modal-header {\n padding: 15px;\n border-bottom: 1px solid #e5e5e5;\n}\n.modal-header .close {\n margin-top: -2px;\n}\n.modal-title {\n margin: 0;\n line-height: 1.42857143;\n}\n.modal-body {\n position: relative;\n padding: 15px;\n}\n.modal-footer {\n padding: 15px;\n text-align: right;\n border-top: 1px solid #e5e5e5;\n}\n.modal-footer .btn + .btn {\n margin-left: 5px;\n margin-bottom: 0;\n}\n.modal-footer .btn-group .btn + .btn {\n margin-left: -1px;\n}\n.modal-footer .btn-block + .btn-block {\n margin-left: 0;\n}\n.modal-scrollbar-measure {\n position: absolute;\n top: -9999px;\n width: 50px;\n height: 50px;\n overflow: scroll;\n}\n@media (min-width: 768px) {\n .modal-dialog {\n width: 600px;\n margin: 30px auto;\n }\n .modal-content {\n -webkit-box-shadow: 0 5px 15px rgba(0, 0, 0, 0.5);\n box-shadow: 0 5px 15px rgba(0, 0, 0, 0.5);\n }\n .modal-sm {\n width: 300px;\n }\n}\n@media (min-width: 992px) {\n .modal-lg {\n width: 900px;\n }\n}\n.tooltip {\n position: absolute;\n z-index: 1070;\n display: block;\n font-family: \"Helvetica Neue\", Helvetica, Arial, sans-serif;\n font-style: normal;\n font-weight: normal;\n letter-spacing: normal;\n line-break: auto;\n line-height: 1.42857143;\n text-align: left;\n text-align: start;\n text-decoration: none;\n text-shadow: none;\n text-transform: none;\n white-space: normal;\n word-break: normal;\n word-spacing: normal;\n word-wrap: normal;\n font-size: 12px;\n opacity: 0;\n filter: alpha(opacity=0);\n}\n.tooltip.in {\n opacity: 0.9;\n filter: alpha(opacity=90);\n}\n.tooltip.top {\n margin-top: -3px;\n padding: 5px 0;\n}\n.tooltip.right {\n margin-left: 3px;\n padding: 0 5px;\n}\n.tooltip.bottom {\n margin-top: 3px;\n padding: 5px 0;\n}\n.tooltip.left {\n margin-left: -3px;\n padding: 0 5px;\n}\n.tooltip-inner {\n max-width: 200px;\n padding: 3px 8px;\n color: #fff;\n text-align: center;\n background-color: #000;\n border-radius: 4px;\n}\n.tooltip-arrow {\n position: absolute;\n width: 0;\n height: 0;\n border-color: transparent;\n border-style: solid;\n}\n.tooltip.top .tooltip-arrow {\n bottom: 0;\n left: 50%;\n margin-left: -5px;\n border-width: 5px 5px 0;\n border-top-color: #000;\n}\n.tooltip.top-left .tooltip-arrow {\n bottom: 0;\n right: 5px;\n margin-bottom: -5px;\n border-width: 5px 5px 0;\n border-top-color: #000;\n}\n.tooltip.top-right .tooltip-arrow {\n bottom: 0;\n left: 5px;\n margin-bottom: -5px;\n border-width: 5px 5px 0;\n border-top-color: #000;\n}\n.tooltip.right .tooltip-arrow {\n top: 50%;\n left: 0;\n margin-top: -5px;\n border-width: 5px 5px 5px 0;\n border-right-color: #000;\n}\n.tooltip.left .tooltip-arrow {\n top: 50%;\n right: 0;\n margin-top: -5px;\n border-width: 5px 0 5px 5px;\n border-left-color: #000;\n}\n.tooltip.bottom .tooltip-arrow {\n top: 0;\n left: 50%;\n margin-left: -5px;\n border-width: 0 5px 5px;\n border-bottom-color: #000;\n}\n.tooltip.bottom-left .tooltip-arrow {\n top: 0;\n right: 5px;\n margin-top: -5px;\n border-width: 0 5px 5px;\n border-bottom-color: #000;\n}\n.tooltip.bottom-right .tooltip-arrow {\n top: 0;\n left: 5px;\n margin-top: -5px;\n border-width: 0 5px 5px;\n border-bottom-color: #000;\n}\n.popover {\n position: absolute;\n top: 0;\n left: 0;\n z-index: 1060;\n display: none;\n max-width: 276px;\n padding: 1px;\n font-family: \"Helvetica Neue\", Helvetica, Arial, sans-serif;\n font-style: normal;\n font-weight: normal;\n letter-spacing: normal;\n line-break: auto;\n line-height: 1.42857143;\n text-align: left;\n text-align: start;\n text-decoration: none;\n text-shadow: none;\n text-transform: none;\n white-space: normal;\n word-break: normal;\n word-spacing: normal;\n word-wrap: normal;\n font-size: 14px;\n background-color: #fff;\n background-clip: padding-box;\n border: 1px solid #ccc;\n border: 1px solid rgba(0, 0, 0, 0.2);\n border-radius: 6px;\n -webkit-box-shadow: 0 5px 10px rgba(0, 0, 0, 0.2);\n box-shadow: 0 5px 10px rgba(0, 0, 0, 0.2);\n}\n.popover.top {\n margin-top: -10px;\n}\n.popover.right {\n margin-left: 10px;\n}\n.popover.bottom {\n margin-top: 10px;\n}\n.popover.left {\n margin-left: -10px;\n}\n.popover-title {\n margin: 0;\n padding: 8px 14px;\n font-size: 14px;\n background-color: #f7f7f7;\n border-bottom: 1px solid #ebebeb;\n border-radius: 5px 5px 0 0;\n}\n.popover-content {\n padding: 9px 14px;\n}\n.popover > .arrow,\n.popover > .arrow:after {\n position: absolute;\n display: block;\n width: 0;\n height: 0;\n border-color: transparent;\n border-style: solid;\n}\n.popover > .arrow {\n border-width: 11px;\n}\n.popover > .arrow:after {\n border-width: 10px;\n content: \"\";\n}\n.popover.top > .arrow {\n left: 50%;\n margin-left: -11px;\n border-bottom-width: 0;\n border-top-color: #999999;\n border-top-color: rgba(0, 0, 0, 0.25);\n bottom: -11px;\n}\n.popover.top > .arrow:after {\n content: \" \";\n bottom: 1px;\n margin-left: -10px;\n border-bottom-width: 0;\n border-top-color: #fff;\n}\n.popover.right > .arrow {\n top: 50%;\n left: -11px;\n margin-top: -11px;\n border-left-width: 0;\n border-right-color: #999999;\n border-right-color: rgba(0, 0, 0, 0.25);\n}\n.popover.right > .arrow:after {\n content: \" \";\n left: 1px;\n bottom: -10px;\n border-left-width: 0;\n border-right-color: #fff;\n}\n.popover.bottom > .arrow {\n left: 50%;\n margin-left: -11px;\n border-top-width: 0;\n border-bottom-color: #999999;\n border-bottom-color: rgba(0, 0, 0, 0.25);\n top: -11px;\n}\n.popover.bottom > .arrow:after {\n content: \" \";\n top: 1px;\n margin-left: -10px;\n border-top-width: 0;\n border-bottom-color: #fff;\n}\n.popover.left > .arrow {\n top: 50%;\n right: -11px;\n margin-top: -11px;\n border-right-width: 0;\n border-left-color: #999999;\n border-left-color: rgba(0, 0, 0, 0.25);\n}\n.popover.left > .arrow:after {\n content: \" \";\n right: 1px;\n border-right-width: 0;\n border-left-color: #fff;\n bottom: -10px;\n}\n.carousel {\n position: relative;\n}\n.carousel-inner {\n position: relative;\n overflow: hidden;\n width: 100%;\n}\n.carousel-inner > .item {\n display: none;\n position: relative;\n -webkit-transition: 0.6s ease-in-out left;\n -o-transition: 0.6s ease-in-out left;\n transition: 0.6s ease-in-out left;\n}\n.carousel-inner > .item > img,\n.carousel-inner > .item > a > img {\n line-height: 1;\n}\n@media all and (transform-3d), (-webkit-transform-3d) {\n .carousel-inner > .item {\n -webkit-transition: -webkit-transform 0.6s ease-in-out;\n -moz-transition: -moz-transform 0.6s ease-in-out;\n -o-transition: -o-transform 0.6s ease-in-out;\n transition: transform 0.6s ease-in-out;\n -webkit-backface-visibility: hidden;\n -moz-backface-visibility: hidden;\n backface-visibility: hidden;\n -webkit-perspective: 1000px;\n -moz-perspective: 1000px;\n perspective: 1000px;\n }\n .carousel-inner > .item.next,\n .carousel-inner > .item.active.right {\n -webkit-transform: translate3d(100%, 0, 0);\n transform: translate3d(100%, 0, 0);\n left: 0;\n }\n .carousel-inner > .item.prev,\n .carousel-inner > .item.active.left {\n -webkit-transform: translate3d(-100%, 0, 0);\n transform: translate3d(-100%, 0, 0);\n left: 0;\n }\n .carousel-inner > .item.next.left,\n .carousel-inner > .item.prev.right,\n .carousel-inner > .item.active {\n -webkit-transform: translate3d(0, 0, 0);\n transform: translate3d(0, 0, 0);\n left: 0;\n }\n}\n.carousel-inner > .active,\n.carousel-inner > .next,\n.carousel-inner > .prev {\n display: block;\n}\n.carousel-inner > .active {\n left: 0;\n}\n.carousel-inner > .next,\n.carousel-inner > .prev {\n position: absolute;\n top: 0;\n width: 100%;\n}\n.carousel-inner > .next {\n left: 100%;\n}\n.carousel-inner > .prev {\n left: -100%;\n}\n.carousel-inner > .next.left,\n.carousel-inner > .prev.right {\n left: 0;\n}\n.carousel-inner > .active.left {\n left: -100%;\n}\n.carousel-inner > .active.right {\n left: 100%;\n}\n.carousel-control {\n position: absolute;\n top: 0;\n left: 0;\n bottom: 0;\n width: 15%;\n opacity: 0.5;\n filter: alpha(opacity=50);\n font-size: 20px;\n color: #fff;\n text-align: center;\n text-shadow: 0 1px 2px rgba(0, 0, 0, 0.6);\n background-color: rgba(0, 0, 0, 0);\n}\n.carousel-control.left {\n background-image: -webkit-linear-gradient(left, rgba(0, 0, 0, 0.5) 0%, rgba(0, 0, 0, 0.0001) 100%);\n background-image: -o-linear-gradient(left, rgba(0, 0, 0, 0.5) 0%, rgba(0, 0, 0, 0.0001) 100%);\n background-image: linear-gradient(to right, rgba(0, 0, 0, 0.5) 0%, rgba(0, 0, 0, 0.0001) 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#80000000', endColorstr='#00000000', GradientType=1);\n}\n.carousel-control.right {\n left: auto;\n right: 0;\n background-image: -webkit-linear-gradient(left, rgba(0, 0, 0, 0.0001) 0%, rgba(0, 0, 0, 0.5) 100%);\n background-image: -o-linear-gradient(left, rgba(0, 0, 0, 0.0001) 0%, rgba(0, 0, 0, 0.5) 100%);\n background-image: linear-gradient(to right, rgba(0, 0, 0, 0.0001) 0%, rgba(0, 0, 0, 0.5) 100%);\n background-repeat: repeat-x;\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#00000000', endColorstr='#80000000', GradientType=1);\n}\n.carousel-control:hover,\n.carousel-control:focus {\n outline: 0;\n color: #fff;\n text-decoration: none;\n opacity: 0.9;\n filter: alpha(opacity=90);\n}\n.carousel-control .icon-prev,\n.carousel-control .icon-next,\n.carousel-control .glyphicon-chevron-left,\n.carousel-control .glyphicon-chevron-right {\n position: absolute;\n top: 50%;\n margin-top: -10px;\n z-index: 5;\n display: inline-block;\n}\n.carousel-control .icon-prev,\n.carousel-control .glyphicon-chevron-left {\n left: 50%;\n margin-left: -10px;\n}\n.carousel-control .icon-next,\n.carousel-control .glyphicon-chevron-right {\n right: 50%;\n margin-right: -10px;\n}\n.carousel-control .icon-prev,\n.carousel-control .icon-next {\n width: 20px;\n height: 20px;\n line-height: 1;\n font-family: serif;\n}\n.carousel-control .icon-prev:before {\n content: '\\2039';\n}\n.carousel-control .icon-next:before {\n content: '\\203a';\n}\n.carousel-indicators {\n position: absolute;\n bottom: 10px;\n left: 50%;\n z-index: 15;\n width: 60%;\n margin-left: -30%;\n padding-left: 0;\n list-style: none;\n text-align: center;\n}\n.carousel-indicators li {\n display: inline-block;\n width: 10px;\n height: 10px;\n margin: 1px;\n text-indent: -999px;\n border: 1px solid #fff;\n border-radius: 10px;\n cursor: pointer;\n background-color: #000 \\9;\n background-color: rgba(0, 0, 0, 0);\n}\n.carousel-indicators .active {\n margin: 0;\n width: 12px;\n height: 12px;\n background-color: #fff;\n}\n.carousel-caption {\n position: absolute;\n left: 15%;\n right: 15%;\n bottom: 20px;\n z-index: 10;\n padding-top: 20px;\n padding-bottom: 20px;\n color: #fff;\n text-align: center;\n text-shadow: 0 1px 2px rgba(0, 0, 0, 0.6);\n}\n.carousel-caption .btn {\n text-shadow: none;\n}\n@media screen and (min-width: 768px) {\n .carousel-control .glyphicon-chevron-left,\n .carousel-control .glyphicon-chevron-right,\n .carousel-control .icon-prev,\n .carousel-control .icon-next {\n width: 30px;\n height: 30px;\n margin-top: -10px;\n font-size: 30px;\n }\n .carousel-control .glyphicon-chevron-left,\n .carousel-control .icon-prev {\n margin-left: -10px;\n }\n .carousel-control .glyphicon-chevron-right,\n .carousel-control .icon-next {\n margin-right: -10px;\n }\n .carousel-caption {\n left: 20%;\n right: 20%;\n padding-bottom: 30px;\n }\n .carousel-indicators {\n bottom: 20px;\n }\n}\n.clearfix:before,\n.clearfix:after,\n.dl-horizontal dd:before,\n.dl-horizontal dd:after,\n.container:before,\n.container:after,\n.container-fluid:before,\n.container-fluid:after,\n.row:before,\n.row:after,\n.form-horizontal .form-group:before,\n.form-horizontal .form-group:after,\n.btn-toolbar:before,\n.btn-toolbar:after,\n.btn-group-vertical > .btn-group:before,\n.btn-group-vertical > .btn-group:after,\n.nav:before,\n.nav:after,\n.navbar:before,\n.navbar:after,\n.navbar-header:before,\n.navbar-header:after,\n.navbar-collapse:before,\n.navbar-collapse:after,\n.pager:before,\n.pager:after,\n.panel-body:before,\n.panel-body:after,\n.modal-header:before,\n.modal-header:after,\n.modal-footer:before,\n.modal-footer:after {\n content: \" \";\n display: table;\n}\n.clearfix:after,\n.dl-horizontal dd:after,\n.container:after,\n.container-fluid:after,\n.row:after,\n.form-horizontal .form-group:after,\n.btn-toolbar:after,\n.btn-group-vertical > .btn-group:after,\n.nav:after,\n.navbar:after,\n.navbar-header:after,\n.navbar-collapse:after,\n.pager:after,\n.panel-body:after,\n.modal-header:after,\n.modal-footer:after {\n clear: both;\n}\n.center-block {\n display: block;\n margin-left: auto;\n margin-right: auto;\n}\n.pull-right {\n float: right !important;\n}\n.pull-left {\n float: left !important;\n}\n.hide {\n display: none !important;\n}\n.show {\n display: block !important;\n}\n.invisible {\n visibility: hidden;\n}\n.text-hide {\n font: 0/0 a;\n color: transparent;\n text-shadow: none;\n background-color: transparent;\n border: 0;\n}\n.hidden {\n display: none !important;\n}\n.affix {\n position: fixed;\n}\n@-ms-viewport {\n width: device-width;\n}\n.visible-xs,\n.visible-sm,\n.visible-md,\n.visible-lg {\n display: none !important;\n}\n.visible-xs-block,\n.visible-xs-inline,\n.visible-xs-inline-block,\n.visible-sm-block,\n.visible-sm-inline,\n.visible-sm-inline-block,\n.visible-md-block,\n.visible-md-inline,\n.visible-md-inline-block,\n.visible-lg-block,\n.visible-lg-inline,\n.visible-lg-inline-block {\n display: none !important;\n}\n@media (max-width: 767px) {\n .visible-xs {\n display: block !important;\n }\n table.visible-xs {\n display: table !important;\n }\n tr.visible-xs {\n display: table-row !important;\n }\n th.visible-xs,\n td.visible-xs {\n display: table-cell !important;\n }\n}\n@media (max-width: 767px) {\n .visible-xs-block {\n display: block !important;\n }\n}\n@media (max-width: 767px) {\n .visible-xs-inline {\n display: inline !important;\n }\n}\n@media (max-width: 767px) {\n .visible-xs-inline-block {\n display: inline-block !important;\n }\n}\n@media (min-width: 768px) and (max-width: 991px) {\n .visible-sm {\n display: block !important;\n }\n table.visible-sm {\n display: table !important;\n }\n tr.visible-sm {\n display: table-row !important;\n }\n th.visible-sm,\n td.visible-sm {\n display: table-cell !important;\n }\n}\n@media (min-width: 768px) and (max-width: 991px) {\n .visible-sm-block {\n display: block !important;\n }\n}\n@media (min-width: 768px) and (max-width: 991px) {\n .visible-sm-inline {\n display: inline !important;\n }\n}\n@media (min-width: 768px) and (max-width: 991px) {\n .visible-sm-inline-block {\n display: inline-block !important;\n }\n}\n@media (min-width: 992px) and (max-width: 1199px) {\n .visible-md {\n display: block !important;\n }\n table.visible-md {\n display: table !important;\n }\n tr.visible-md {\n display: table-row !important;\n }\n th.visible-md,\n td.visible-md {\n display: table-cell !important;\n }\n}\n@media (min-width: 992px) and (max-width: 1199px) {\n .visible-md-block {\n display: block !important;\n }\n}\n@media (min-width: 992px) and (max-width: 1199px) {\n .visible-md-inline {\n display: inline !important;\n }\n}\n@media (min-width: 992px) and (max-width: 1199px) {\n .visible-md-inline-block {\n display: inline-block !important;\n }\n}\n@media (min-width: 1200px) {\n .visible-lg {\n display: block !important;\n }\n table.visible-lg {\n display: table !important;\n }\n tr.visible-lg {\n display: table-row !important;\n }\n th.visible-lg,\n td.visible-lg {\n display: table-cell !important;\n }\n}\n@media (min-width: 1200px) {\n .visible-lg-block {\n display: block !important;\n }\n}\n@media (min-width: 1200px) {\n .visible-lg-inline {\n display: inline !important;\n }\n}\n@media (min-width: 1200px) {\n .visible-lg-inline-block {\n display: inline-block !important;\n }\n}\n@media (max-width: 767px) {\n .hidden-xs {\n display: none !important;\n }\n}\n@media (min-width: 768px) and (max-width: 991px) {\n .hidden-sm {\n display: none !important;\n }\n}\n@media (min-width: 992px) and (max-width: 1199px) {\n .hidden-md {\n display: none !important;\n }\n}\n@media (min-width: 1200px) {\n .hidden-lg {\n display: none !important;\n }\n}\n.visible-print {\n display: none !important;\n}\n@media print {\n .visible-print {\n display: block !important;\n }\n table.visible-print {\n display: table !important;\n }\n tr.visible-print {\n display: table-row !important;\n }\n th.visible-print,\n td.visible-print {\n display: table-cell !important;\n }\n}\n.visible-print-block {\n display: none !important;\n}\n@media print {\n .visible-print-block {\n display: block !important;\n }\n}\n.visible-print-inline {\n display: none !important;\n}\n@media print {\n .visible-print-inline {\n display: inline !important;\n }\n}\n.visible-print-inline-block {\n display: none !important;\n}\n@media print {\n .visible-print-inline-block {\n display: inline-block !important;\n }\n}\n@media print {\n .hidden-print {\n display: none !important;\n }\n}\n/*# sourceMappingURL=bootstrap.css.map */","/*!\n * Bootstrap v3.3.7 (http://getbootstrap.com)\n * Copyright 2011-2016 Twitter, Inc.\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)\n */\n/*! normalize.css v3.0.3 | MIT License | github.com/necolas/normalize.css */\nhtml {\n font-family: sans-serif;\n -webkit-text-size-adjust: 100%;\n -ms-text-size-adjust: 100%;\n}\nbody {\n margin: 0;\n}\narticle,\naside,\ndetails,\nfigcaption,\nfigure,\nfooter,\nheader,\nhgroup,\nmain,\nmenu,\nnav,\nsection,\nsummary {\n display: block;\n}\naudio,\ncanvas,\nprogress,\nvideo {\n display: inline-block;\n vertical-align: baseline;\n}\naudio:not([controls]) {\n display: none;\n height: 0;\n}\n[hidden],\ntemplate {\n display: none;\n}\na {\n background-color: transparent;\n}\na:active,\na:hover {\n outline: 0;\n}\nabbr[title] {\n border-bottom: 1px dotted;\n}\nb,\nstrong {\n font-weight: bold;\n}\ndfn {\n font-style: italic;\n}\nh1 {\n margin: .67em 0;\n font-size: 2em;\n}\nmark {\n color: #000;\n background: #ff0;\n}\nsmall {\n font-size: 80%;\n}\nsub,\nsup {\n position: relative;\n font-size: 75%;\n line-height: 0;\n vertical-align: baseline;\n}\nsup {\n top: -.5em;\n}\nsub {\n bottom: -.25em;\n}\nimg {\n border: 0;\n}\nsvg:not(:root) {\n overflow: hidden;\n}\nfigure {\n margin: 1em 40px;\n}\nhr {\n height: 0;\n -webkit-box-sizing: content-box;\n -moz-box-sizing: content-box;\n box-sizing: content-box;\n}\npre {\n overflow: auto;\n}\ncode,\nkbd,\npre,\nsamp {\n font-family: monospace, monospace;\n font-size: 1em;\n}\nbutton,\ninput,\noptgroup,\nselect,\ntextarea {\n margin: 0;\n font: inherit;\n color: inherit;\n}\nbutton {\n overflow: visible;\n}\nbutton,\nselect {\n text-transform: none;\n}\nbutton,\nhtml input[type=\"button\"],\ninput[type=\"reset\"],\ninput[type=\"submit\"] {\n -webkit-appearance: button;\n cursor: pointer;\n}\nbutton[disabled],\nhtml input[disabled] {\n cursor: default;\n}\nbutton::-moz-focus-inner,\ninput::-moz-focus-inner {\n padding: 0;\n border: 0;\n}\ninput {\n line-height: normal;\n}\ninput[type=\"checkbox\"],\ninput[type=\"radio\"] {\n -webkit-box-sizing: border-box;\n -moz-box-sizing: border-box;\n box-sizing: border-box;\n padding: 0;\n}\ninput[type=\"number\"]::-webkit-inner-spin-button,\ninput[type=\"number\"]::-webkit-outer-spin-button {\n height: auto;\n}\ninput[type=\"search\"] {\n -webkit-box-sizing: content-box;\n -moz-box-sizing: content-box;\n box-sizing: content-box;\n -webkit-appearance: textfield;\n}\ninput[type=\"search\"]::-webkit-search-cancel-button,\ninput[type=\"search\"]::-webkit-search-decoration {\n -webkit-appearance: none;\n}\nfieldset {\n padding: .35em .625em .75em;\n margin: 0 2px;\n border: 1px solid #c0c0c0;\n}\nlegend {\n padding: 0;\n border: 0;\n}\ntextarea {\n overflow: auto;\n}\noptgroup {\n font-weight: bold;\n}\ntable {\n border-spacing: 0;\n border-collapse: collapse;\n}\ntd,\nth {\n padding: 0;\n}\n/*! Source: https://github.com/h5bp/html5-boilerplate/blob/master/src/css/main.css */\n@media print {\n *,\n *:before,\n *:after {\n color: #000 !important;\n text-shadow: none !important;\n background: transparent !important;\n -webkit-box-shadow: none !important;\n box-shadow: none !important;\n }\n a,\n a:visited {\n text-decoration: underline;\n }\n a[href]:after {\n content: \" (\" attr(href) \")\";\n }\n abbr[title]:after {\n content: \" (\" attr(title) \")\";\n }\n a[href^=\"#\"]:after,\n a[href^=\"javascript:\"]:after {\n content: \"\";\n }\n pre,\n blockquote {\n border: 1px solid #999;\n\n page-break-inside: avoid;\n }\n thead {\n display: table-header-group;\n }\n tr,\n img {\n page-break-inside: avoid;\n }\n img {\n max-width: 100% !important;\n }\n p,\n h2,\n h3 {\n orphans: 3;\n widows: 3;\n }\n h2,\n h3 {\n page-break-after: avoid;\n }\n .navbar {\n display: none;\n }\n .btn > .caret,\n .dropup > .btn > .caret {\n border-top-color: #000 !important;\n }\n .label {\n border: 1px solid #000;\n }\n .table {\n border-collapse: collapse !important;\n }\n .table td,\n .table th {\n background-color: #fff !important;\n }\n .table-bordered th,\n .table-bordered td {\n border: 1px solid #ddd !important;\n }\n}\n@font-face {\n font-family: 'Glyphicons Halflings';\n\n src: url('../fonts/glyphicons-halflings-regular.eot');\n src: url('../fonts/glyphicons-halflings-regular.eot?#iefix') format('embedded-opentype'), url('../fonts/glyphicons-halflings-regular.woff2') format('woff2'), url('../fonts/glyphicons-halflings-regular.woff') format('woff'), url('../fonts/glyphicons-halflings-regular.ttf') format('truetype'), url('../fonts/glyphicons-halflings-regular.svg#glyphicons_halflingsregular') format('svg');\n}\n.glyphicon {\n position: relative;\n top: 1px;\n display: inline-block;\n font-family: 'Glyphicons Halflings';\n font-style: normal;\n font-weight: normal;\n line-height: 1;\n\n -webkit-font-smoothing: antialiased;\n -moz-osx-font-smoothing: grayscale;\n}\n.glyphicon-asterisk:before {\n content: \"\\002a\";\n}\n.glyphicon-plus:before {\n content: \"\\002b\";\n}\n.glyphicon-euro:before,\n.glyphicon-eur:before {\n content: \"\\20ac\";\n}\n.glyphicon-minus:before {\n content: \"\\2212\";\n}\n.glyphicon-cloud:before {\n content: \"\\2601\";\n}\n.glyphicon-envelope:before {\n content: \"\\2709\";\n}\n.glyphicon-pencil:before {\n content: \"\\270f\";\n}\n.glyphicon-glass:before {\n content: \"\\e001\";\n}\n.glyphicon-music:before {\n content: \"\\e002\";\n}\n.glyphicon-search:before {\n content: \"\\e003\";\n}\n.glyphicon-heart:before {\n content: \"\\e005\";\n}\n.glyphicon-star:before {\n content: \"\\e006\";\n}\n.glyphicon-star-empty:before {\n content: \"\\e007\";\n}\n.glyphicon-user:before {\n content: \"\\e008\";\n}\n.glyphicon-film:before {\n content: \"\\e009\";\n}\n.glyphicon-th-large:before {\n content: \"\\e010\";\n}\n.glyphicon-th:before {\n content: \"\\e011\";\n}\n.glyphicon-th-list:before {\n content: \"\\e012\";\n}\n.glyphicon-ok:before {\n content: \"\\e013\";\n}\n.glyphicon-remove:before {\n content: \"\\e014\";\n}\n.glyphicon-zoom-in:before {\n content: \"\\e015\";\n}\n.glyphicon-zoom-out:before {\n content: \"\\e016\";\n}\n.glyphicon-off:before {\n content: \"\\e017\";\n}\n.glyphicon-signal:before {\n content: \"\\e018\";\n}\n.glyphicon-cog:before {\n content: \"\\e019\";\n}\n.glyphicon-trash:before {\n content: \"\\e020\";\n}\n.glyphicon-home:before {\n content: \"\\e021\";\n}\n.glyphicon-file:before {\n content: \"\\e022\";\n}\n.glyphicon-time:before {\n content: \"\\e023\";\n}\n.glyphicon-road:before {\n content: \"\\e024\";\n}\n.glyphicon-download-alt:before {\n content: \"\\e025\";\n}\n.glyphicon-download:before {\n content: \"\\e026\";\n}\n.glyphicon-upload:before {\n content: \"\\e027\";\n}\n.glyphicon-inbox:before {\n content: \"\\e028\";\n}\n.glyphicon-play-circle:before {\n content: \"\\e029\";\n}\n.glyphicon-repeat:before {\n content: \"\\e030\";\n}\n.glyphicon-refresh:before {\n content: \"\\e031\";\n}\n.glyphicon-list-alt:before {\n content: \"\\e032\";\n}\n.glyphicon-lock:before {\n content: \"\\e033\";\n}\n.glyphicon-flag:before {\n content: \"\\e034\";\n}\n.glyphicon-headphones:before {\n content: \"\\e035\";\n}\n.glyphicon-volume-off:before {\n content: \"\\e036\";\n}\n.glyphicon-volume-down:before {\n content: \"\\e037\";\n}\n.glyphicon-volume-up:before {\n content: \"\\e038\";\n}\n.glyphicon-qrcode:before {\n content: \"\\e039\";\n}\n.glyphicon-barcode:before {\n content: \"\\e040\";\n}\n.glyphicon-tag:before {\n content: \"\\e041\";\n}\n.glyphicon-tags:before {\n content: \"\\e042\";\n}\n.glyphicon-book:before {\n content: \"\\e043\";\n}\n.glyphicon-bookmark:before {\n content: \"\\e044\";\n}\n.glyphicon-print:before {\n content: \"\\e045\";\n}\n.glyphicon-camera:before {\n content: \"\\e046\";\n}\n.glyphicon-font:before {\n content: \"\\e047\";\n}\n.glyphicon-bold:before {\n content: \"\\e048\";\n}\n.glyphicon-italic:before {\n content: \"\\e049\";\n}\n.glyphicon-text-height:before {\n content: \"\\e050\";\n}\n.glyphicon-text-width:before {\n content: \"\\e051\";\n}\n.glyphicon-align-left:before {\n content: \"\\e052\";\n}\n.glyphicon-align-center:before {\n content: \"\\e053\";\n}\n.glyphicon-align-right:before {\n content: \"\\e054\";\n}\n.glyphicon-align-justify:before {\n content: \"\\e055\";\n}\n.glyphicon-list:before {\n content: \"\\e056\";\n}\n.glyphicon-indent-left:before {\n content: \"\\e057\";\n}\n.glyphicon-indent-right:before {\n content: \"\\e058\";\n}\n.glyphicon-facetime-video:before {\n content: \"\\e059\";\n}\n.glyphicon-picture:before {\n content: \"\\e060\";\n}\n.glyphicon-map-marker:before {\n content: \"\\e062\";\n}\n.glyphicon-adjust:before {\n content: \"\\e063\";\n}\n.glyphicon-tint:before {\n content: \"\\e064\";\n}\n.glyphicon-edit:before {\n content: \"\\e065\";\n}\n.glyphicon-share:before {\n content: \"\\e066\";\n}\n.glyphicon-check:before {\n content: \"\\e067\";\n}\n.glyphicon-move:before {\n content: \"\\e068\";\n}\n.glyphicon-step-backward:before {\n content: \"\\e069\";\n}\n.glyphicon-fast-backward:before {\n content: \"\\e070\";\n}\n.glyphicon-backward:before {\n content: \"\\e071\";\n}\n.glyphicon-play:before {\n content: \"\\e072\";\n}\n.glyphicon-pause:before {\n content: \"\\e073\";\n}\n.glyphicon-stop:before {\n content: \"\\e074\";\n}\n.glyphicon-forward:before {\n content: \"\\e075\";\n}\n.glyphicon-fast-forward:before {\n content: \"\\e076\";\n}\n.glyphicon-step-forward:before {\n content: \"\\e077\";\n}\n.glyphicon-eject:before {\n content: \"\\e078\";\n}\n.glyphicon-chevron-left:before {\n content: \"\\e079\";\n}\n.glyphicon-chevron-right:before {\n content: \"\\e080\";\n}\n.glyphicon-plus-sign:before {\n content: \"\\e081\";\n}\n.glyphicon-minus-sign:before {\n content: \"\\e082\";\n}\n.glyphicon-remove-sign:before {\n content: \"\\e083\";\n}\n.glyphicon-ok-sign:before {\n content: \"\\e084\";\n}\n.glyphicon-question-sign:before {\n content: \"\\e085\";\n}\n.glyphicon-info-sign:before {\n content: \"\\e086\";\n}\n.glyphicon-screenshot:before {\n content: \"\\e087\";\n}\n.glyphicon-remove-circle:before {\n content: \"\\e088\";\n}\n.glyphicon-ok-circle:before {\n content: \"\\e089\";\n}\n.glyphicon-ban-circle:before {\n content: \"\\e090\";\n}\n.glyphicon-arrow-left:before {\n content: \"\\e091\";\n}\n.glyphicon-arrow-right:before {\n content: \"\\e092\";\n}\n.glyphicon-arrow-up:before {\n content: \"\\e093\";\n}\n.glyphicon-arrow-down:before {\n content: \"\\e094\";\n}\n.glyphicon-share-alt:before {\n content: \"\\e095\";\n}\n.glyphicon-resize-full:before {\n content: \"\\e096\";\n}\n.glyphicon-resize-small:before {\n content: \"\\e097\";\n}\n.glyphicon-exclamation-sign:before {\n content: \"\\e101\";\n}\n.glyphicon-gift:before {\n content: \"\\e102\";\n}\n.glyphicon-leaf:before {\n content: \"\\e103\";\n}\n.glyphicon-fire:before {\n content: \"\\e104\";\n}\n.glyphicon-eye-open:before {\n content: \"\\e105\";\n}\n.glyphicon-eye-close:before {\n content: \"\\e106\";\n}\n.glyphicon-warning-sign:before {\n content: \"\\e107\";\n}\n.glyphicon-plane:before {\n content: \"\\e108\";\n}\n.glyphicon-calendar:before {\n content: \"\\e109\";\n}\n.glyphicon-random:before {\n content: \"\\e110\";\n}\n.glyphicon-comment:before {\n content: \"\\e111\";\n}\n.glyphicon-magnet:before {\n content: \"\\e112\";\n}\n.glyphicon-chevron-up:before {\n content: \"\\e113\";\n}\n.glyphicon-chevron-down:before {\n content: \"\\e114\";\n}\n.glyphicon-retweet:before {\n content: \"\\e115\";\n}\n.glyphicon-shopping-cart:before {\n content: \"\\e116\";\n}\n.glyphicon-folder-close:before {\n content: \"\\e117\";\n}\n.glyphicon-folder-open:before {\n content: \"\\e118\";\n}\n.glyphicon-resize-vertical:before {\n content: \"\\e119\";\n}\n.glyphicon-resize-horizontal:before {\n content: \"\\e120\";\n}\n.glyphicon-hdd:before {\n content: \"\\e121\";\n}\n.glyphicon-bullhorn:before {\n content: \"\\e122\";\n}\n.glyphicon-bell:before {\n content: \"\\e123\";\n}\n.glyphicon-certificate:before {\n content: \"\\e124\";\n}\n.glyphicon-thumbs-up:before {\n content: \"\\e125\";\n}\n.glyphicon-thumbs-down:before {\n content: \"\\e126\";\n}\n.glyphicon-hand-right:before {\n content: \"\\e127\";\n}\n.glyphicon-hand-left:before {\n content: \"\\e128\";\n}\n.glyphicon-hand-up:before {\n content: \"\\e129\";\n}\n.glyphicon-hand-down:before {\n content: \"\\e130\";\n}\n.glyphicon-circle-arrow-right:before {\n content: \"\\e131\";\n}\n.glyphicon-circle-arrow-left:before {\n content: \"\\e132\";\n}\n.glyphicon-circle-arrow-up:before {\n content: \"\\e133\";\n}\n.glyphicon-circle-arrow-down:before {\n content: \"\\e134\";\n}\n.glyphicon-globe:before {\n content: \"\\e135\";\n}\n.glyphicon-wrench:before {\n content: \"\\e136\";\n}\n.glyphicon-tasks:before {\n content: \"\\e137\";\n}\n.glyphicon-filter:before {\n content: \"\\e138\";\n}\n.glyphicon-briefcase:before {\n content: \"\\e139\";\n}\n.glyphicon-fullscreen:before {\n content: \"\\e140\";\n}\n.glyphicon-dashboard:before {\n content: \"\\e141\";\n}\n.glyphicon-paperclip:before {\n content: \"\\e142\";\n}\n.glyphicon-heart-empty:before {\n content: \"\\e143\";\n}\n.glyphicon-link:before {\n content: \"\\e144\";\n}\n.glyphicon-phone:before {\n content: \"\\e145\";\n}\n.glyphicon-pushpin:before {\n content: \"\\e146\";\n}\n.glyphicon-usd:before {\n content: \"\\e148\";\n}\n.glyphicon-gbp:before {\n content: \"\\e149\";\n}\n.glyphicon-sort:before {\n content: \"\\e150\";\n}\n.glyphicon-sort-by-alphabet:before {\n content: \"\\e151\";\n}\n.glyphicon-sort-by-alphabet-alt:before {\n content: \"\\e152\";\n}\n.glyphicon-sort-by-order:before {\n content: \"\\e153\";\n}\n.glyphicon-sort-by-order-alt:before {\n content: \"\\e154\";\n}\n.glyphicon-sort-by-attributes:before {\n content: \"\\e155\";\n}\n.glyphicon-sort-by-attributes-alt:before {\n content: \"\\e156\";\n}\n.glyphicon-unchecked:before {\n content: \"\\e157\";\n}\n.glyphicon-expand:before {\n content: \"\\e158\";\n}\n.glyphicon-collapse-down:before {\n content: \"\\e159\";\n}\n.glyphicon-collapse-up:before {\n content: \"\\e160\";\n}\n.glyphicon-log-in:before {\n content: \"\\e161\";\n}\n.glyphicon-flash:before {\n content: \"\\e162\";\n}\n.glyphicon-log-out:before {\n content: \"\\e163\";\n}\n.glyphicon-new-window:before {\n content: \"\\e164\";\n}\n.glyphicon-record:before {\n content: \"\\e165\";\n}\n.glyphicon-save:before {\n content: \"\\e166\";\n}\n.glyphicon-open:before {\n content: \"\\e167\";\n}\n.glyphicon-saved:before {\n content: \"\\e168\";\n}\n.glyphicon-import:before {\n content: \"\\e169\";\n}\n.glyphicon-export:before {\n content: \"\\e170\";\n}\n.glyphicon-send:before {\n content: \"\\e171\";\n}\n.glyphicon-floppy-disk:before {\n content: \"\\e172\";\n}\n.glyphicon-floppy-saved:before {\n content: \"\\e173\";\n}\n.glyphicon-floppy-remove:before {\n content: \"\\e174\";\n}\n.glyphicon-floppy-save:before {\n content: \"\\e175\";\n}\n.glyphicon-floppy-open:before {\n content: \"\\e176\";\n}\n.glyphicon-credit-card:before {\n content: \"\\e177\";\n}\n.glyphicon-transfer:before {\n content: \"\\e178\";\n}\n.glyphicon-cutlery:before {\n content: \"\\e179\";\n}\n.glyphicon-header:before {\n content: \"\\e180\";\n}\n.glyphicon-compressed:before {\n content: \"\\e181\";\n}\n.glyphicon-earphone:before {\n content: \"\\e182\";\n}\n.glyphicon-phone-alt:before {\n content: \"\\e183\";\n}\n.glyphicon-tower:before {\n content: \"\\e184\";\n}\n.glyphicon-stats:before {\n content: \"\\e185\";\n}\n.glyphicon-sd-video:before {\n content: \"\\e186\";\n}\n.glyphicon-hd-video:before {\n content: \"\\e187\";\n}\n.glyphicon-subtitles:before {\n content: \"\\e188\";\n}\n.glyphicon-sound-stereo:before {\n content: \"\\e189\";\n}\n.glyphicon-sound-dolby:before {\n content: \"\\e190\";\n}\n.glyphicon-sound-5-1:before {\n content: \"\\e191\";\n}\n.glyphicon-sound-6-1:before {\n content: \"\\e192\";\n}\n.glyphicon-sound-7-1:before {\n content: \"\\e193\";\n}\n.glyphicon-copyright-mark:before {\n content: \"\\e194\";\n}\n.glyphicon-registration-mark:before {\n content: \"\\e195\";\n}\n.glyphicon-cloud-download:before {\n content: \"\\e197\";\n}\n.glyphicon-cloud-upload:before {\n content: \"\\e198\";\n}\n.glyphicon-tree-conifer:before {\n content: \"\\e199\";\n}\n.glyphicon-tree-deciduous:before {\n content: \"\\e200\";\n}\n.glyphicon-cd:before {\n content: \"\\e201\";\n}\n.glyphicon-save-file:before {\n content: \"\\e202\";\n}\n.glyphicon-open-file:before {\n content: \"\\e203\";\n}\n.glyphicon-level-up:before {\n content: \"\\e204\";\n}\n.glyphicon-copy:before {\n content: \"\\e205\";\n}\n.glyphicon-paste:before {\n content: \"\\e206\";\n}\n.glyphicon-alert:before {\n content: \"\\e209\";\n}\n.glyphicon-equalizer:before {\n content: \"\\e210\";\n}\n.glyphicon-king:before {\n content: \"\\e211\";\n}\n.glyphicon-queen:before {\n content: \"\\e212\";\n}\n.glyphicon-pawn:before {\n content: \"\\e213\";\n}\n.glyphicon-bishop:before {\n content: \"\\e214\";\n}\n.glyphicon-knight:before {\n content: \"\\e215\";\n}\n.glyphicon-baby-formula:before {\n content: \"\\e216\";\n}\n.glyphicon-tent:before {\n content: \"\\26fa\";\n}\n.glyphicon-blackboard:before {\n content: \"\\e218\";\n}\n.glyphicon-bed:before {\n content: \"\\e219\";\n}\n.glyphicon-apple:before {\n content: \"\\f8ff\";\n}\n.glyphicon-erase:before {\n content: \"\\e221\";\n}\n.glyphicon-hourglass:before {\n content: \"\\231b\";\n}\n.glyphicon-lamp:before {\n content: \"\\e223\";\n}\n.glyphicon-duplicate:before {\n content: \"\\e224\";\n}\n.glyphicon-piggy-bank:before {\n content: \"\\e225\";\n}\n.glyphicon-scissors:before {\n content: \"\\e226\";\n}\n.glyphicon-bitcoin:before {\n content: \"\\e227\";\n}\n.glyphicon-btc:before {\n content: \"\\e227\";\n}\n.glyphicon-xbt:before {\n content: \"\\e227\";\n}\n.glyphicon-yen:before {\n content: \"\\00a5\";\n}\n.glyphicon-jpy:before {\n content: \"\\00a5\";\n}\n.glyphicon-ruble:before {\n content: \"\\20bd\";\n}\n.glyphicon-rub:before {\n content: \"\\20bd\";\n}\n.glyphicon-scale:before {\n content: \"\\e230\";\n}\n.glyphicon-ice-lolly:before {\n content: \"\\e231\";\n}\n.glyphicon-ice-lolly-tasted:before {\n content: \"\\e232\";\n}\n.glyphicon-education:before {\n content: \"\\e233\";\n}\n.glyphicon-option-horizontal:before {\n content: \"\\e234\";\n}\n.glyphicon-option-vertical:before {\n content: \"\\e235\";\n}\n.glyphicon-menu-hamburger:before {\n content: \"\\e236\";\n}\n.glyphicon-modal-window:before {\n content: \"\\e237\";\n}\n.glyphicon-oil:before {\n content: \"\\e238\";\n}\n.glyphicon-grain:before {\n content: \"\\e239\";\n}\n.glyphicon-sunglasses:before {\n content: \"\\e240\";\n}\n.glyphicon-text-size:before {\n content: \"\\e241\";\n}\n.glyphicon-text-color:before {\n content: \"\\e242\";\n}\n.glyphicon-text-background:before {\n content: \"\\e243\";\n}\n.glyphicon-object-align-top:before {\n content: \"\\e244\";\n}\n.glyphicon-object-align-bottom:before {\n content: \"\\e245\";\n}\n.glyphicon-object-align-horizontal:before {\n content: \"\\e246\";\n}\n.glyphicon-object-align-left:before {\n content: \"\\e247\";\n}\n.glyphicon-object-align-vertical:before {\n content: \"\\e248\";\n}\n.glyphicon-object-align-right:before {\n content: \"\\e249\";\n}\n.glyphicon-triangle-right:before {\n content: \"\\e250\";\n}\n.glyphicon-triangle-left:before {\n content: \"\\e251\";\n}\n.glyphicon-triangle-bottom:before {\n content: \"\\e252\";\n}\n.glyphicon-triangle-top:before {\n content: \"\\e253\";\n}\n.glyphicon-console:before {\n content: \"\\e254\";\n}\n.glyphicon-superscript:before {\n content: \"\\e255\";\n}\n.glyphicon-subscript:before {\n content: \"\\e256\";\n}\n.glyphicon-menu-left:before {\n content: \"\\e257\";\n}\n.glyphicon-menu-right:before {\n content: \"\\e258\";\n}\n.glyphicon-menu-down:before {\n content: \"\\e259\";\n}\n.glyphicon-menu-up:before {\n content: \"\\e260\";\n}\n* {\n -webkit-box-sizing: border-box;\n -moz-box-sizing: border-box;\n box-sizing: border-box;\n}\n*:before,\n*:after {\n -webkit-box-sizing: border-box;\n -moz-box-sizing: border-box;\n box-sizing: border-box;\n}\nhtml {\n font-size: 10px;\n\n -webkit-tap-highlight-color: rgba(0, 0, 0, 0);\n}\nbody {\n font-family: \"Helvetica Neue\", Helvetica, Arial, sans-serif;\n font-size: 14px;\n line-height: 1.42857143;\n color: #333;\n background-color: #fff;\n}\ninput,\nbutton,\nselect,\ntextarea {\n font-family: inherit;\n font-size: inherit;\n line-height: inherit;\n}\na {\n color: #337ab7;\n text-decoration: none;\n}\na:hover,\na:focus {\n color: #23527c;\n text-decoration: underline;\n}\na:focus {\n outline: 5px auto -webkit-focus-ring-color;\n outline-offset: -2px;\n}\nfigure {\n margin: 0;\n}\nimg {\n vertical-align: middle;\n}\n.img-responsive,\n.thumbnail > img,\n.thumbnail a > img,\n.carousel-inner > .item > img,\n.carousel-inner > .item > a > img {\n display: block;\n max-width: 100%;\n height: auto;\n}\n.img-rounded {\n border-radius: 6px;\n}\n.img-thumbnail {\n display: inline-block;\n max-width: 100%;\n height: auto;\n padding: 4px;\n line-height: 1.42857143;\n background-color: #fff;\n border: 1px solid #ddd;\n border-radius: 4px;\n -webkit-transition: all .2s ease-in-out;\n -o-transition: all .2s ease-in-out;\n transition: all .2s ease-in-out;\n}\n.img-circle {\n border-radius: 50%;\n}\nhr {\n margin-top: 20px;\n margin-bottom: 20px;\n border: 0;\n border-top: 1px solid #eee;\n}\n.sr-only {\n position: absolute;\n width: 1px;\n height: 1px;\n padding: 0;\n margin: -1px;\n overflow: hidden;\n clip: rect(0, 0, 0, 0);\n border: 0;\n}\n.sr-only-focusable:active,\n.sr-only-focusable:focus {\n position: static;\n width: auto;\n height: auto;\n margin: 0;\n overflow: visible;\n clip: auto;\n}\n[role=\"button\"] {\n cursor: pointer;\n}\nh1,\nh2,\nh3,\nh4,\nh5,\nh6,\n.h1,\n.h2,\n.h3,\n.h4,\n.h5,\n.h6 {\n font-family: inherit;\n font-weight: 500;\n line-height: 1.1;\n color: inherit;\n}\nh1 small,\nh2 small,\nh3 small,\nh4 small,\nh5 small,\nh6 small,\n.h1 small,\n.h2 small,\n.h3 small,\n.h4 small,\n.h5 small,\n.h6 small,\nh1 .small,\nh2 .small,\nh3 .small,\nh4 .small,\nh5 .small,\nh6 .small,\n.h1 .small,\n.h2 .small,\n.h3 .small,\n.h4 .small,\n.h5 .small,\n.h6 .small {\n font-weight: normal;\n line-height: 1;\n color: #777;\n}\nh1,\n.h1,\nh2,\n.h2,\nh3,\n.h3 {\n margin-top: 20px;\n margin-bottom: 10px;\n}\nh1 small,\n.h1 small,\nh2 small,\n.h2 small,\nh3 small,\n.h3 small,\nh1 .small,\n.h1 .small,\nh2 .small,\n.h2 .small,\nh3 .small,\n.h3 .small {\n font-size: 65%;\n}\nh4,\n.h4,\nh5,\n.h5,\nh6,\n.h6 {\n margin-top: 10px;\n margin-bottom: 10px;\n}\nh4 small,\n.h4 small,\nh5 small,\n.h5 small,\nh6 small,\n.h6 small,\nh4 .small,\n.h4 .small,\nh5 .small,\n.h5 .small,\nh6 .small,\n.h6 .small {\n font-size: 75%;\n}\nh1,\n.h1 {\n font-size: 36px;\n}\nh2,\n.h2 {\n font-size: 30px;\n}\nh3,\n.h3 {\n font-size: 24px;\n}\nh4,\n.h4 {\n font-size: 18px;\n}\nh5,\n.h5 {\n font-size: 14px;\n}\nh6,\n.h6 {\n font-size: 12px;\n}\np {\n margin: 0 0 10px;\n}\n.lead {\n margin-bottom: 20px;\n font-size: 16px;\n font-weight: 300;\n line-height: 1.4;\n}\n@media (min-width: 768px) {\n .lead {\n font-size: 21px;\n }\n}\nsmall,\n.small {\n font-size: 85%;\n}\nmark,\n.mark {\n padding: .2em;\n background-color: #fcf8e3;\n}\n.text-left {\n text-align: left;\n}\n.text-right {\n text-align: right;\n}\n.text-center {\n text-align: center;\n}\n.text-justify {\n text-align: justify;\n}\n.text-nowrap {\n white-space: nowrap;\n}\n.text-lowercase {\n text-transform: lowercase;\n}\n.text-uppercase {\n text-transform: uppercase;\n}\n.text-capitalize {\n text-transform: capitalize;\n}\n.text-muted {\n color: #777;\n}\n.text-primary {\n color: #337ab7;\n}\na.text-primary:hover,\na.text-primary:focus {\n color: #286090;\n}\n.text-success {\n color: #3c763d;\n}\na.text-success:hover,\na.text-success:focus {\n color: #2b542c;\n}\n.text-info {\n color: #31708f;\n}\na.text-info:hover,\na.text-info:focus {\n color: #245269;\n}\n.text-warning {\n color: #8a6d3b;\n}\na.text-warning:hover,\na.text-warning:focus {\n color: #66512c;\n}\n.text-danger {\n color: #a94442;\n}\na.text-danger:hover,\na.text-danger:focus {\n color: #843534;\n}\n.bg-primary {\n color: #fff;\n background-color: #337ab7;\n}\na.bg-primary:hover,\na.bg-primary:focus {\n background-color: #286090;\n}\n.bg-success {\n background-color: #dff0d8;\n}\na.bg-success:hover,\na.bg-success:focus {\n background-color: #c1e2b3;\n}\n.bg-info {\n background-color: #d9edf7;\n}\na.bg-info:hover,\na.bg-info:focus {\n background-color: #afd9ee;\n}\n.bg-warning {\n background-color: #fcf8e3;\n}\na.bg-warning:hover,\na.bg-warning:focus {\n background-color: #f7ecb5;\n}\n.bg-danger {\n background-color: #f2dede;\n}\na.bg-danger:hover,\na.bg-danger:focus {\n background-color: #e4b9b9;\n}\n.page-header {\n padding-bottom: 9px;\n margin: 40px 0 20px;\n border-bottom: 1px solid #eee;\n}\nul,\nol {\n margin-top: 0;\n margin-bottom: 10px;\n}\nul ul,\nol ul,\nul ol,\nol ol {\n margin-bottom: 0;\n}\n.list-unstyled {\n padding-left: 0;\n list-style: none;\n}\n.list-inline {\n padding-left: 0;\n margin-left: -5px;\n list-style: none;\n}\n.list-inline > li {\n display: inline-block;\n padding-right: 5px;\n padding-left: 5px;\n}\ndl {\n margin-top: 0;\n margin-bottom: 20px;\n}\ndt,\ndd {\n line-height: 1.42857143;\n}\ndt {\n font-weight: bold;\n}\ndd {\n margin-left: 0;\n}\n@media (min-width: 768px) {\n .dl-horizontal dt {\n float: left;\n width: 160px;\n overflow: hidden;\n clear: left;\n text-align: right;\n text-overflow: ellipsis;\n white-space: nowrap;\n }\n .dl-horizontal dd {\n margin-left: 180px;\n }\n}\nabbr[title],\nabbr[data-original-title] {\n cursor: help;\n border-bottom: 1px dotted #777;\n}\n.initialism {\n font-size: 90%;\n text-transform: uppercase;\n}\nblockquote {\n padding: 10px 20px;\n margin: 0 0 20px;\n font-size: 17.5px;\n border-left: 5px solid #eee;\n}\nblockquote p:last-child,\nblockquote ul:last-child,\nblockquote ol:last-child {\n margin-bottom: 0;\n}\nblockquote footer,\nblockquote small,\nblockquote .small {\n display: block;\n font-size: 80%;\n line-height: 1.42857143;\n color: #777;\n}\nblockquote footer:before,\nblockquote small:before,\nblockquote .small:before {\n content: '\\2014 \\00A0';\n}\n.blockquote-reverse,\nblockquote.pull-right {\n padding-right: 15px;\n padding-left: 0;\n text-align: right;\n border-right: 5px solid #eee;\n border-left: 0;\n}\n.blockquote-reverse footer:before,\nblockquote.pull-right footer:before,\n.blockquote-reverse small:before,\nblockquote.pull-right small:before,\n.blockquote-reverse .small:before,\nblockquote.pull-right .small:before {\n content: '';\n}\n.blockquote-reverse footer:after,\nblockquote.pull-right footer:after,\n.blockquote-reverse small:after,\nblockquote.pull-right small:after,\n.blockquote-reverse .small:after,\nblockquote.pull-right .small:after {\n content: '\\00A0 \\2014';\n}\naddress {\n margin-bottom: 20px;\n font-style: normal;\n line-height: 1.42857143;\n}\ncode,\nkbd,\npre,\nsamp {\n font-family: Menlo, Monaco, Consolas, \"Courier New\", monospace;\n}\ncode {\n padding: 2px 4px;\n font-size: 90%;\n color: #c7254e;\n background-color: #f9f2f4;\n border-radius: 4px;\n}\nkbd {\n padding: 2px 4px;\n font-size: 90%;\n color: #fff;\n background-color: #333;\n border-radius: 3px;\n -webkit-box-shadow: inset 0 -1px 0 rgba(0, 0, 0, .25);\n box-shadow: inset 0 -1px 0 rgba(0, 0, 0, .25);\n}\nkbd kbd {\n padding: 0;\n font-size: 100%;\n font-weight: bold;\n -webkit-box-shadow: none;\n box-shadow: none;\n}\npre {\n display: block;\n padding: 9.5px;\n margin: 0 0 10px;\n font-size: 13px;\n line-height: 1.42857143;\n color: #333;\n word-break: break-all;\n word-wrap: break-word;\n background-color: #f5f5f5;\n border: 1px solid #ccc;\n border-radius: 4px;\n}\npre code {\n padding: 0;\n font-size: inherit;\n color: inherit;\n white-space: pre-wrap;\n background-color: transparent;\n border-radius: 0;\n}\n.pre-scrollable {\n max-height: 340px;\n overflow-y: scroll;\n}\n.container {\n padding-right: 15px;\n padding-left: 15px;\n margin-right: auto;\n margin-left: auto;\n}\n@media (min-width: 768px) {\n .container {\n width: 750px;\n }\n}\n@media (min-width: 992px) {\n .container {\n width: 970px;\n }\n}\n@media (min-width: 1200px) {\n .container {\n width: 1170px;\n }\n}\n.container-fluid {\n padding-right: 15px;\n padding-left: 15px;\n margin-right: auto;\n margin-left: auto;\n}\n.row {\n margin-right: -15px;\n margin-left: -15px;\n}\n.col-xs-1, .col-sm-1, .col-md-1, .col-lg-1, .col-xs-2, .col-sm-2, .col-md-2, .col-lg-2, .col-xs-3, .col-sm-3, .col-md-3, .col-lg-3, .col-xs-4, .col-sm-4, .col-md-4, .col-lg-4, .col-xs-5, .col-sm-5, .col-md-5, .col-lg-5, .col-xs-6, .col-sm-6, .col-md-6, .col-lg-6, .col-xs-7, .col-sm-7, .col-md-7, .col-lg-7, .col-xs-8, .col-sm-8, .col-md-8, .col-lg-8, .col-xs-9, .col-sm-9, .col-md-9, .col-lg-9, .col-xs-10, .col-sm-10, .col-md-10, .col-lg-10, .col-xs-11, .col-sm-11, .col-md-11, .col-lg-11, .col-xs-12, .col-sm-12, .col-md-12, .col-lg-12 {\n position: relative;\n min-height: 1px;\n padding-right: 15px;\n padding-left: 15px;\n}\n.col-xs-1, .col-xs-2, .col-xs-3, .col-xs-4, .col-xs-5, .col-xs-6, .col-xs-7, .col-xs-8, .col-xs-9, .col-xs-10, .col-xs-11, .col-xs-12 {\n float: left;\n}\n.col-xs-12 {\n width: 100%;\n}\n.col-xs-11 {\n width: 91.66666667%;\n}\n.col-xs-10 {\n width: 83.33333333%;\n}\n.col-xs-9 {\n width: 75%;\n}\n.col-xs-8 {\n width: 66.66666667%;\n}\n.col-xs-7 {\n width: 58.33333333%;\n}\n.col-xs-6 {\n width: 50%;\n}\n.col-xs-5 {\n width: 41.66666667%;\n}\n.col-xs-4 {\n width: 33.33333333%;\n}\n.col-xs-3 {\n width: 25%;\n}\n.col-xs-2 {\n width: 16.66666667%;\n}\n.col-xs-1 {\n width: 8.33333333%;\n}\n.col-xs-pull-12 {\n right: 100%;\n}\n.col-xs-pull-11 {\n right: 91.66666667%;\n}\n.col-xs-pull-10 {\n right: 83.33333333%;\n}\n.col-xs-pull-9 {\n right: 75%;\n}\n.col-xs-pull-8 {\n right: 66.66666667%;\n}\n.col-xs-pull-7 {\n right: 58.33333333%;\n}\n.col-xs-pull-6 {\n right: 50%;\n}\n.col-xs-pull-5 {\n right: 41.66666667%;\n}\n.col-xs-pull-4 {\n right: 33.33333333%;\n}\n.col-xs-pull-3 {\n right: 25%;\n}\n.col-xs-pull-2 {\n right: 16.66666667%;\n}\n.col-xs-pull-1 {\n right: 8.33333333%;\n}\n.col-xs-pull-0 {\n right: auto;\n}\n.col-xs-push-12 {\n left: 100%;\n}\n.col-xs-push-11 {\n left: 91.66666667%;\n}\n.col-xs-push-10 {\n left: 83.33333333%;\n}\n.col-xs-push-9 {\n left: 75%;\n}\n.col-xs-push-8 {\n left: 66.66666667%;\n}\n.col-xs-push-7 {\n left: 58.33333333%;\n}\n.col-xs-push-6 {\n left: 50%;\n}\n.col-xs-push-5 {\n left: 41.66666667%;\n}\n.col-xs-push-4 {\n left: 33.33333333%;\n}\n.col-xs-push-3 {\n left: 25%;\n}\n.col-xs-push-2 {\n left: 16.66666667%;\n}\n.col-xs-push-1 {\n left: 8.33333333%;\n}\n.col-xs-push-0 {\n left: auto;\n}\n.col-xs-offset-12 {\n margin-left: 100%;\n}\n.col-xs-offset-11 {\n margin-left: 91.66666667%;\n}\n.col-xs-offset-10 {\n margin-left: 83.33333333%;\n}\n.col-xs-offset-9 {\n margin-left: 75%;\n}\n.col-xs-offset-8 {\n margin-left: 66.66666667%;\n}\n.col-xs-offset-7 {\n margin-left: 58.33333333%;\n}\n.col-xs-offset-6 {\n margin-left: 50%;\n}\n.col-xs-offset-5 {\n margin-left: 41.66666667%;\n}\n.col-xs-offset-4 {\n margin-left: 33.33333333%;\n}\n.col-xs-offset-3 {\n margin-left: 25%;\n}\n.col-xs-offset-2 {\n margin-left: 16.66666667%;\n}\n.col-xs-offset-1 {\n margin-left: 8.33333333%;\n}\n.col-xs-offset-0 {\n margin-left: 0;\n}\n@media (min-width: 768px) {\n .col-sm-1, .col-sm-2, .col-sm-3, .col-sm-4, .col-sm-5, .col-sm-6, .col-sm-7, .col-sm-8, .col-sm-9, .col-sm-10, .col-sm-11, .col-sm-12 {\n float: left;\n }\n .col-sm-12 {\n width: 100%;\n }\n .col-sm-11 {\n width: 91.66666667%;\n }\n .col-sm-10 {\n width: 83.33333333%;\n }\n .col-sm-9 {\n width: 75%;\n }\n .col-sm-8 {\n width: 66.66666667%;\n }\n .col-sm-7 {\n width: 58.33333333%;\n }\n .col-sm-6 {\n width: 50%;\n }\n .col-sm-5 {\n width: 41.66666667%;\n }\n .col-sm-4 {\n width: 33.33333333%;\n }\n .col-sm-3 {\n width: 25%;\n }\n .col-sm-2 {\n width: 16.66666667%;\n }\n .col-sm-1 {\n width: 8.33333333%;\n }\n .col-sm-pull-12 {\n right: 100%;\n }\n .col-sm-pull-11 {\n right: 91.66666667%;\n }\n .col-sm-pull-10 {\n right: 83.33333333%;\n }\n .col-sm-pull-9 {\n right: 75%;\n }\n .col-sm-pull-8 {\n right: 66.66666667%;\n }\n .col-sm-pull-7 {\n right: 58.33333333%;\n }\n .col-sm-pull-6 {\n right: 50%;\n }\n .col-sm-pull-5 {\n right: 41.66666667%;\n }\n .col-sm-pull-4 {\n right: 33.33333333%;\n }\n .col-sm-pull-3 {\n right: 25%;\n }\n .col-sm-pull-2 {\n right: 16.66666667%;\n }\n .col-sm-pull-1 {\n right: 8.33333333%;\n }\n .col-sm-pull-0 {\n right: auto;\n }\n .col-sm-push-12 {\n left: 100%;\n }\n .col-sm-push-11 {\n left: 91.66666667%;\n }\n .col-sm-push-10 {\n left: 83.33333333%;\n }\n .col-sm-push-9 {\n left: 75%;\n }\n .col-sm-push-8 {\n left: 66.66666667%;\n }\n .col-sm-push-7 {\n left: 58.33333333%;\n }\n .col-sm-push-6 {\n left: 50%;\n }\n .col-sm-push-5 {\n left: 41.66666667%;\n }\n .col-sm-push-4 {\n left: 33.33333333%;\n }\n .col-sm-push-3 {\n left: 25%;\n }\n .col-sm-push-2 {\n left: 16.66666667%;\n }\n .col-sm-push-1 {\n left: 8.33333333%;\n }\n .col-sm-push-0 {\n left: auto;\n }\n .col-sm-offset-12 {\n margin-left: 100%;\n }\n .col-sm-offset-11 {\n margin-left: 91.66666667%;\n }\n .col-sm-offset-10 {\n margin-left: 83.33333333%;\n }\n .col-sm-offset-9 {\n margin-left: 75%;\n }\n .col-sm-offset-8 {\n margin-left: 66.66666667%;\n }\n .col-sm-offset-7 {\n margin-left: 58.33333333%;\n }\n .col-sm-offset-6 {\n margin-left: 50%;\n }\n .col-sm-offset-5 {\n margin-left: 41.66666667%;\n }\n .col-sm-offset-4 {\n margin-left: 33.33333333%;\n }\n .col-sm-offset-3 {\n margin-left: 25%;\n }\n .col-sm-offset-2 {\n margin-left: 16.66666667%;\n }\n .col-sm-offset-1 {\n margin-left: 8.33333333%;\n }\n .col-sm-offset-0 {\n margin-left: 0;\n }\n}\n@media (min-width: 992px) {\n .col-md-1, .col-md-2, .col-md-3, .col-md-4, .col-md-5, .col-md-6, .col-md-7, .col-md-8, .col-md-9, .col-md-10, .col-md-11, .col-md-12 {\n float: left;\n }\n .col-md-12 {\n width: 100%;\n }\n .col-md-11 {\n width: 91.66666667%;\n }\n .col-md-10 {\n width: 83.33333333%;\n }\n .col-md-9 {\n width: 75%;\n }\n .col-md-8 {\n width: 66.66666667%;\n }\n .col-md-7 {\n width: 58.33333333%;\n }\n .col-md-6 {\n width: 50%;\n }\n .col-md-5 {\n width: 41.66666667%;\n }\n .col-md-4 {\n width: 33.33333333%;\n }\n .col-md-3 {\n width: 25%;\n }\n .col-md-2 {\n width: 16.66666667%;\n }\n .col-md-1 {\n width: 8.33333333%;\n }\n .col-md-pull-12 {\n right: 100%;\n }\n .col-md-pull-11 {\n right: 91.66666667%;\n }\n .col-md-pull-10 {\n right: 83.33333333%;\n }\n .col-md-pull-9 {\n right: 75%;\n }\n .col-md-pull-8 {\n right: 66.66666667%;\n }\n .col-md-pull-7 {\n right: 58.33333333%;\n }\n .col-md-pull-6 {\n right: 50%;\n }\n .col-md-pull-5 {\n right: 41.66666667%;\n }\n .col-md-pull-4 {\n right: 33.33333333%;\n }\n .col-md-pull-3 {\n right: 25%;\n }\n .col-md-pull-2 {\n right: 16.66666667%;\n }\n .col-md-pull-1 {\n right: 8.33333333%;\n }\n .col-md-pull-0 {\n right: auto;\n }\n .col-md-push-12 {\n left: 100%;\n }\n .col-md-push-11 {\n left: 91.66666667%;\n }\n .col-md-push-10 {\n left: 83.33333333%;\n }\n .col-md-push-9 {\n left: 75%;\n }\n .col-md-push-8 {\n left: 66.66666667%;\n }\n .col-md-push-7 {\n left: 58.33333333%;\n }\n .col-md-push-6 {\n left: 50%;\n }\n .col-md-push-5 {\n left: 41.66666667%;\n }\n .col-md-push-4 {\n left: 33.33333333%;\n }\n .col-md-push-3 {\n left: 25%;\n }\n .col-md-push-2 {\n left: 16.66666667%;\n }\n .col-md-push-1 {\n left: 8.33333333%;\n }\n .col-md-push-0 {\n left: auto;\n }\n .col-md-offset-12 {\n margin-left: 100%;\n }\n .col-md-offset-11 {\n margin-left: 91.66666667%;\n }\n .col-md-offset-10 {\n margin-left: 83.33333333%;\n }\n .col-md-offset-9 {\n margin-left: 75%;\n }\n .col-md-offset-8 {\n margin-left: 66.66666667%;\n }\n .col-md-offset-7 {\n margin-left: 58.33333333%;\n }\n .col-md-offset-6 {\n margin-left: 50%;\n }\n .col-md-offset-5 {\n margin-left: 41.66666667%;\n }\n .col-md-offset-4 {\n margin-left: 33.33333333%;\n }\n .col-md-offset-3 {\n margin-left: 25%;\n }\n .col-md-offset-2 {\n margin-left: 16.66666667%;\n }\n .col-md-offset-1 {\n margin-left: 8.33333333%;\n }\n .col-md-offset-0 {\n margin-left: 0;\n }\n}\n@media (min-width: 1200px) {\n .col-lg-1, .col-lg-2, .col-lg-3, .col-lg-4, .col-lg-5, .col-lg-6, .col-lg-7, .col-lg-8, .col-lg-9, .col-lg-10, .col-lg-11, .col-lg-12 {\n float: left;\n }\n .col-lg-12 {\n width: 100%;\n }\n .col-lg-11 {\n width: 91.66666667%;\n }\n .col-lg-10 {\n width: 83.33333333%;\n }\n .col-lg-9 {\n width: 75%;\n }\n .col-lg-8 {\n width: 66.66666667%;\n }\n .col-lg-7 {\n width: 58.33333333%;\n }\n .col-lg-6 {\n width: 50%;\n }\n .col-lg-5 {\n width: 41.66666667%;\n }\n .col-lg-4 {\n width: 33.33333333%;\n }\n .col-lg-3 {\n width: 25%;\n }\n .col-lg-2 {\n width: 16.66666667%;\n }\n .col-lg-1 {\n width: 8.33333333%;\n }\n .col-lg-pull-12 {\n right: 100%;\n }\n .col-lg-pull-11 {\n right: 91.66666667%;\n }\n .col-lg-pull-10 {\n right: 83.33333333%;\n }\n .col-lg-pull-9 {\n right: 75%;\n }\n .col-lg-pull-8 {\n right: 66.66666667%;\n }\n .col-lg-pull-7 {\n right: 58.33333333%;\n }\n .col-lg-pull-6 {\n right: 50%;\n }\n .col-lg-pull-5 {\n right: 41.66666667%;\n }\n .col-lg-pull-4 {\n right: 33.33333333%;\n }\n .col-lg-pull-3 {\n right: 25%;\n }\n .col-lg-pull-2 {\n right: 16.66666667%;\n }\n .col-lg-pull-1 {\n right: 8.33333333%;\n }\n .col-lg-pull-0 {\n right: auto;\n }\n .col-lg-push-12 {\n left: 100%;\n }\n .col-lg-push-11 {\n left: 91.66666667%;\n }\n .col-lg-push-10 {\n left: 83.33333333%;\n }\n .col-lg-push-9 {\n left: 75%;\n }\n .col-lg-push-8 {\n left: 66.66666667%;\n }\n .col-lg-push-7 {\n left: 58.33333333%;\n }\n .col-lg-push-6 {\n left: 50%;\n }\n .col-lg-push-5 {\n left: 41.66666667%;\n }\n .col-lg-push-4 {\n left: 33.33333333%;\n }\n .col-lg-push-3 {\n left: 25%;\n }\n .col-lg-push-2 {\n left: 16.66666667%;\n }\n .col-lg-push-1 {\n left: 8.33333333%;\n }\n .col-lg-push-0 {\n left: auto;\n }\n .col-lg-offset-12 {\n margin-left: 100%;\n }\n .col-lg-offset-11 {\n margin-left: 91.66666667%;\n }\n .col-lg-offset-10 {\n margin-left: 83.33333333%;\n }\n .col-lg-offset-9 {\n margin-left: 75%;\n }\n .col-lg-offset-8 {\n margin-left: 66.66666667%;\n }\n .col-lg-offset-7 {\n margin-left: 58.33333333%;\n }\n .col-lg-offset-6 {\n margin-left: 50%;\n }\n .col-lg-offset-5 {\n margin-left: 41.66666667%;\n }\n .col-lg-offset-4 {\n margin-left: 33.33333333%;\n }\n .col-lg-offset-3 {\n margin-left: 25%;\n }\n .col-lg-offset-2 {\n margin-left: 16.66666667%;\n }\n .col-lg-offset-1 {\n margin-left: 8.33333333%;\n }\n .col-lg-offset-0 {\n margin-left: 0;\n }\n}\ntable {\n background-color: transparent;\n}\ncaption {\n padding-top: 8px;\n padding-bottom: 8px;\n color: #777;\n text-align: left;\n}\nth {\n text-align: left;\n}\n.table {\n width: 100%;\n max-width: 100%;\n margin-bottom: 20px;\n}\n.table > thead > tr > th,\n.table > tbody > tr > th,\n.table > tfoot > tr > th,\n.table > thead > tr > td,\n.table > tbody > tr > td,\n.table > tfoot > tr > td {\n padding: 8px;\n line-height: 1.42857143;\n vertical-align: top;\n border-top: 1px solid #ddd;\n}\n.table > thead > tr > th {\n vertical-align: bottom;\n border-bottom: 2px solid #ddd;\n}\n.table > caption + thead > tr:first-child > th,\n.table > colgroup + thead > tr:first-child > th,\n.table > thead:first-child > tr:first-child > th,\n.table > caption + thead > tr:first-child > td,\n.table > colgroup + thead > tr:first-child > td,\n.table > thead:first-child > tr:first-child > td {\n border-top: 0;\n}\n.table > tbody + tbody {\n border-top: 2px solid #ddd;\n}\n.table .table {\n background-color: #fff;\n}\n.table-condensed > thead > tr > th,\n.table-condensed > tbody > tr > th,\n.table-condensed > tfoot > tr > th,\n.table-condensed > thead > tr > td,\n.table-condensed > tbody > tr > td,\n.table-condensed > tfoot > tr > td {\n padding: 5px;\n}\n.table-bordered {\n border: 1px solid #ddd;\n}\n.table-bordered > thead > tr > th,\n.table-bordered > tbody > tr > th,\n.table-bordered > tfoot > tr > th,\n.table-bordered > thead > tr > td,\n.table-bordered > tbody > tr > td,\n.table-bordered > tfoot > tr > td {\n border: 1px solid #ddd;\n}\n.table-bordered > thead > tr > th,\n.table-bordered > thead > tr > td {\n border-bottom-width: 2px;\n}\n.table-striped > tbody > tr:nth-of-type(odd) {\n background-color: #f9f9f9;\n}\n.table-hover > tbody > tr:hover {\n background-color: #f5f5f5;\n}\ntable col[class*=\"col-\"] {\n position: static;\n display: table-column;\n float: none;\n}\ntable td[class*=\"col-\"],\ntable th[class*=\"col-\"] {\n position: static;\n display: table-cell;\n float: none;\n}\n.table > thead > tr > td.active,\n.table > tbody > tr > td.active,\n.table > tfoot > tr > td.active,\n.table > thead > tr > th.active,\n.table > tbody > tr > th.active,\n.table > tfoot > tr > th.active,\n.table > thead > tr.active > td,\n.table > tbody > tr.active > td,\n.table > tfoot > tr.active > td,\n.table > thead > tr.active > th,\n.table > tbody > tr.active > th,\n.table > tfoot > tr.active > th {\n background-color: #f5f5f5;\n}\n.table-hover > tbody > tr > td.active:hover,\n.table-hover > tbody > tr > th.active:hover,\n.table-hover > tbody > tr.active:hover > td,\n.table-hover > tbody > tr:hover > .active,\n.table-hover > tbody > tr.active:hover > th {\n background-color: #e8e8e8;\n}\n.table > thead > tr > td.success,\n.table > tbody > tr > td.success,\n.table > tfoot > tr > td.success,\n.table > thead > tr > th.success,\n.table > tbody > tr > th.success,\n.table > tfoot > tr > th.success,\n.table > thead > tr.success > td,\n.table > tbody > tr.success > td,\n.table > tfoot > tr.success > td,\n.table > thead > tr.success > th,\n.table > tbody > tr.success > th,\n.table > tfoot > tr.success > th {\n background-color: #dff0d8;\n}\n.table-hover > tbody > tr > td.success:hover,\n.table-hover > tbody > tr > th.success:hover,\n.table-hover > tbody > tr.success:hover > td,\n.table-hover > tbody > tr:hover > .success,\n.table-hover > tbody > tr.success:hover > th {\n background-color: #d0e9c6;\n}\n.table > thead > tr > td.info,\n.table > tbody > tr > td.info,\n.table > tfoot > tr > td.info,\n.table > thead > tr > th.info,\n.table > tbody > tr > th.info,\n.table > tfoot > tr > th.info,\n.table > thead > tr.info > td,\n.table > tbody > tr.info > td,\n.table > tfoot > tr.info > td,\n.table > thead > tr.info > th,\n.table > tbody > tr.info > th,\n.table > tfoot > tr.info > th {\n background-color: #d9edf7;\n}\n.table-hover > tbody > tr > td.info:hover,\n.table-hover > tbody > tr > th.info:hover,\n.table-hover > tbody > tr.info:hover > td,\n.table-hover > tbody > tr:hover > .info,\n.table-hover > tbody > tr.info:hover > th {\n background-color: #c4e3f3;\n}\n.table > thead > tr > td.warning,\n.table > tbody > tr > td.warning,\n.table > tfoot > tr > td.warning,\n.table > thead > tr > th.warning,\n.table > tbody > tr > th.warning,\n.table > tfoot > tr > th.warning,\n.table > thead > tr.warning > td,\n.table > tbody > tr.warning > td,\n.table > tfoot > tr.warning > td,\n.table > thead > tr.warning > th,\n.table > tbody > tr.warning > th,\n.table > tfoot > tr.warning > th {\n background-color: #fcf8e3;\n}\n.table-hover > tbody > tr > td.warning:hover,\n.table-hover > tbody > tr > th.warning:hover,\n.table-hover > tbody > tr.warning:hover > td,\n.table-hover > tbody > tr:hover > .warning,\n.table-hover > tbody > tr.warning:hover > th {\n background-color: #faf2cc;\n}\n.table > thead > tr > td.danger,\n.table > tbody > tr > td.danger,\n.table > tfoot > tr > td.danger,\n.table > thead > tr > th.danger,\n.table > tbody > tr > th.danger,\n.table > tfoot > tr > th.danger,\n.table > thead > tr.danger > td,\n.table > tbody > tr.danger > td,\n.table > tfoot > tr.danger > td,\n.table > thead > tr.danger > th,\n.table > tbody > tr.danger > th,\n.table > tfoot > tr.danger > th {\n background-color: #f2dede;\n}\n.table-hover > tbody > tr > td.danger:hover,\n.table-hover > tbody > tr > th.danger:hover,\n.table-hover > tbody > tr.danger:hover > td,\n.table-hover > tbody > tr:hover > .danger,\n.table-hover > tbody > tr.danger:hover > th {\n background-color: #ebcccc;\n}\n.table-responsive {\n min-height: .01%;\n overflow-x: auto;\n}\n@media screen and (max-width: 767px) {\n .table-responsive {\n width: 100%;\n margin-bottom: 15px;\n overflow-y: hidden;\n -ms-overflow-style: -ms-autohiding-scrollbar;\n border: 1px solid #ddd;\n }\n .table-responsive > .table {\n margin-bottom: 0;\n }\n .table-responsive > .table > thead > tr > th,\n .table-responsive > .table > tbody > tr > th,\n .table-responsive > .table > tfoot > tr > th,\n .table-responsive > .table > thead > tr > td,\n .table-responsive > .table > tbody > tr > td,\n .table-responsive > .table > tfoot > tr > td {\n white-space: nowrap;\n }\n .table-responsive > .table-bordered {\n border: 0;\n }\n .table-responsive > .table-bordered > thead > tr > th:first-child,\n .table-responsive > .table-bordered > tbody > tr > th:first-child,\n .table-responsive > .table-bordered > tfoot > tr > th:first-child,\n .table-responsive > .table-bordered > thead > tr > td:first-child,\n .table-responsive > .table-bordered > tbody > tr > td:first-child,\n .table-responsive > .table-bordered > tfoot > tr > td:first-child {\n border-left: 0;\n }\n .table-responsive > .table-bordered > thead > tr > th:last-child,\n .table-responsive > .table-bordered > tbody > tr > th:last-child,\n .table-responsive > .table-bordered > tfoot > tr > th:last-child,\n .table-responsive > .table-bordered > thead > tr > td:last-child,\n .table-responsive > .table-bordered > tbody > tr > td:last-child,\n .table-responsive > .table-bordered > tfoot > tr > td:last-child {\n border-right: 0;\n }\n .table-responsive > .table-bordered > tbody > tr:last-child > th,\n .table-responsive > .table-bordered > tfoot > tr:last-child > th,\n .table-responsive > .table-bordered > tbody > tr:last-child > td,\n .table-responsive > .table-bordered > tfoot > tr:last-child > td {\n border-bottom: 0;\n }\n}\nfieldset {\n min-width: 0;\n padding: 0;\n margin: 0;\n border: 0;\n}\nlegend {\n display: block;\n width: 100%;\n padding: 0;\n margin-bottom: 20px;\n font-size: 21px;\n line-height: inherit;\n color: #333;\n border: 0;\n border-bottom: 1px solid #e5e5e5;\n}\nlabel {\n display: inline-block;\n max-width: 100%;\n margin-bottom: 5px;\n font-weight: bold;\n}\ninput[type=\"search\"] {\n -webkit-box-sizing: border-box;\n -moz-box-sizing: border-box;\n box-sizing: border-box;\n}\ninput[type=\"radio\"],\ninput[type=\"checkbox\"] {\n margin: 4px 0 0;\n margin-top: 1px \\9;\n line-height: normal;\n}\ninput[type=\"file\"] {\n display: block;\n}\ninput[type=\"range\"] {\n display: block;\n width: 100%;\n}\nselect[multiple],\nselect[size] {\n height: auto;\n}\ninput[type=\"file\"]:focus,\ninput[type=\"radio\"]:focus,\ninput[type=\"checkbox\"]:focus {\n outline: 5px auto -webkit-focus-ring-color;\n outline-offset: -2px;\n}\noutput {\n display: block;\n padding-top: 7px;\n font-size: 14px;\n line-height: 1.42857143;\n color: #555;\n}\n.form-control {\n display: block;\n width: 100%;\n height: 34px;\n padding: 6px 12px;\n font-size: 14px;\n line-height: 1.42857143;\n color: #555;\n background-color: #fff;\n background-image: none;\n border: 1px solid #ccc;\n border-radius: 4px;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075);\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075);\n -webkit-transition: border-color ease-in-out .15s, -webkit-box-shadow ease-in-out .15s;\n -o-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;\n transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;\n}\n.form-control:focus {\n border-color: #66afe9;\n outline: 0;\n -webkit-box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(102, 175, 233, .6);\n box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(102, 175, 233, .6);\n}\n.form-control::-moz-placeholder {\n color: #999;\n opacity: 1;\n}\n.form-control:-ms-input-placeholder {\n color: #999;\n}\n.form-control::-webkit-input-placeholder {\n color: #999;\n}\n.form-control::-ms-expand {\n background-color: transparent;\n border: 0;\n}\n.form-control[disabled],\n.form-control[readonly],\nfieldset[disabled] .form-control {\n background-color: #eee;\n opacity: 1;\n}\n.form-control[disabled],\nfieldset[disabled] .form-control {\n cursor: not-allowed;\n}\ntextarea.form-control {\n height: auto;\n}\ninput[type=\"search\"] {\n -webkit-appearance: none;\n}\n@media screen and (-webkit-min-device-pixel-ratio: 0) {\n input[type=\"date\"].form-control,\n input[type=\"time\"].form-control,\n input[type=\"datetime-local\"].form-control,\n input[type=\"month\"].form-control {\n line-height: 34px;\n }\n input[type=\"date\"].input-sm,\n input[type=\"time\"].input-sm,\n input[type=\"datetime-local\"].input-sm,\n input[type=\"month\"].input-sm,\n .input-group-sm input[type=\"date\"],\n .input-group-sm input[type=\"time\"],\n .input-group-sm input[type=\"datetime-local\"],\n .input-group-sm input[type=\"month\"] {\n line-height: 30px;\n }\n input[type=\"date\"].input-lg,\n input[type=\"time\"].input-lg,\n input[type=\"datetime-local\"].input-lg,\n input[type=\"month\"].input-lg,\n .input-group-lg input[type=\"date\"],\n .input-group-lg input[type=\"time\"],\n .input-group-lg input[type=\"datetime-local\"],\n .input-group-lg input[type=\"month\"] {\n line-height: 46px;\n }\n}\n.form-group {\n margin-bottom: 15px;\n}\n.radio,\n.checkbox {\n position: relative;\n display: block;\n margin-top: 10px;\n margin-bottom: 10px;\n}\n.radio label,\n.checkbox label {\n min-height: 20px;\n padding-left: 20px;\n margin-bottom: 0;\n font-weight: normal;\n cursor: pointer;\n}\n.radio input[type=\"radio\"],\n.radio-inline input[type=\"radio\"],\n.checkbox input[type=\"checkbox\"],\n.checkbox-inline input[type=\"checkbox\"] {\n position: absolute;\n margin-top: 4px \\9;\n margin-left: -20px;\n}\n.radio + .radio,\n.checkbox + .checkbox {\n margin-top: -5px;\n}\n.radio-inline,\n.checkbox-inline {\n position: relative;\n display: inline-block;\n padding-left: 20px;\n margin-bottom: 0;\n font-weight: normal;\n vertical-align: middle;\n cursor: pointer;\n}\n.radio-inline + .radio-inline,\n.checkbox-inline + .checkbox-inline {\n margin-top: 0;\n margin-left: 10px;\n}\ninput[type=\"radio\"][disabled],\ninput[type=\"checkbox\"][disabled],\ninput[type=\"radio\"].disabled,\ninput[type=\"checkbox\"].disabled,\nfieldset[disabled] input[type=\"radio\"],\nfieldset[disabled] input[type=\"checkbox\"] {\n cursor: not-allowed;\n}\n.radio-inline.disabled,\n.checkbox-inline.disabled,\nfieldset[disabled] .radio-inline,\nfieldset[disabled] .checkbox-inline {\n cursor: not-allowed;\n}\n.radio.disabled label,\n.checkbox.disabled label,\nfieldset[disabled] .radio label,\nfieldset[disabled] .checkbox label {\n cursor: not-allowed;\n}\n.form-control-static {\n min-height: 34px;\n padding-top: 7px;\n padding-bottom: 7px;\n margin-bottom: 0;\n}\n.form-control-static.input-lg,\n.form-control-static.input-sm {\n padding-right: 0;\n padding-left: 0;\n}\n.input-sm {\n height: 30px;\n padding: 5px 10px;\n font-size: 12px;\n line-height: 1.5;\n border-radius: 3px;\n}\nselect.input-sm {\n height: 30px;\n line-height: 30px;\n}\ntextarea.input-sm,\nselect[multiple].input-sm {\n height: auto;\n}\n.form-group-sm .form-control {\n height: 30px;\n padding: 5px 10px;\n font-size: 12px;\n line-height: 1.5;\n border-radius: 3px;\n}\n.form-group-sm select.form-control {\n height: 30px;\n line-height: 30px;\n}\n.form-group-sm textarea.form-control,\n.form-group-sm select[multiple].form-control {\n height: auto;\n}\n.form-group-sm .form-control-static {\n height: 30px;\n min-height: 32px;\n padding: 6px 10px;\n font-size: 12px;\n line-height: 1.5;\n}\n.input-lg {\n height: 46px;\n padding: 10px 16px;\n font-size: 18px;\n line-height: 1.3333333;\n border-radius: 6px;\n}\nselect.input-lg {\n height: 46px;\n line-height: 46px;\n}\ntextarea.input-lg,\nselect[multiple].input-lg {\n height: auto;\n}\n.form-group-lg .form-control {\n height: 46px;\n padding: 10px 16px;\n font-size: 18px;\n line-height: 1.3333333;\n border-radius: 6px;\n}\n.form-group-lg select.form-control {\n height: 46px;\n line-height: 46px;\n}\n.form-group-lg textarea.form-control,\n.form-group-lg select[multiple].form-control {\n height: auto;\n}\n.form-group-lg .form-control-static {\n height: 46px;\n min-height: 38px;\n padding: 11px 16px;\n font-size: 18px;\n line-height: 1.3333333;\n}\n.has-feedback {\n position: relative;\n}\n.has-feedback .form-control {\n padding-right: 42.5px;\n}\n.form-control-feedback {\n position: absolute;\n top: 0;\n right: 0;\n z-index: 2;\n display: block;\n width: 34px;\n height: 34px;\n line-height: 34px;\n text-align: center;\n pointer-events: none;\n}\n.input-lg + .form-control-feedback,\n.input-group-lg + .form-control-feedback,\n.form-group-lg .form-control + .form-control-feedback {\n width: 46px;\n height: 46px;\n line-height: 46px;\n}\n.input-sm + .form-control-feedback,\n.input-group-sm + .form-control-feedback,\n.form-group-sm .form-control + .form-control-feedback {\n width: 30px;\n height: 30px;\n line-height: 30px;\n}\n.has-success .help-block,\n.has-success .control-label,\n.has-success .radio,\n.has-success .checkbox,\n.has-success .radio-inline,\n.has-success .checkbox-inline,\n.has-success.radio label,\n.has-success.checkbox label,\n.has-success.radio-inline label,\n.has-success.checkbox-inline label {\n color: #3c763d;\n}\n.has-success .form-control {\n border-color: #3c763d;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075);\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075);\n}\n.has-success .form-control:focus {\n border-color: #2b542c;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075), 0 0 6px #67b168;\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075), 0 0 6px #67b168;\n}\n.has-success .input-group-addon {\n color: #3c763d;\n background-color: #dff0d8;\n border-color: #3c763d;\n}\n.has-success .form-control-feedback {\n color: #3c763d;\n}\n.has-warning .help-block,\n.has-warning .control-label,\n.has-warning .radio,\n.has-warning .checkbox,\n.has-warning .radio-inline,\n.has-warning .checkbox-inline,\n.has-warning.radio label,\n.has-warning.checkbox label,\n.has-warning.radio-inline label,\n.has-warning.checkbox-inline label {\n color: #8a6d3b;\n}\n.has-warning .form-control {\n border-color: #8a6d3b;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075);\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075);\n}\n.has-warning .form-control:focus {\n border-color: #66512c;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075), 0 0 6px #c0a16b;\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075), 0 0 6px #c0a16b;\n}\n.has-warning .input-group-addon {\n color: #8a6d3b;\n background-color: #fcf8e3;\n border-color: #8a6d3b;\n}\n.has-warning .form-control-feedback {\n color: #8a6d3b;\n}\n.has-error .help-block,\n.has-error .control-label,\n.has-error .radio,\n.has-error .checkbox,\n.has-error .radio-inline,\n.has-error .checkbox-inline,\n.has-error.radio label,\n.has-error.checkbox label,\n.has-error.radio-inline label,\n.has-error.checkbox-inline label {\n color: #a94442;\n}\n.has-error .form-control {\n border-color: #a94442;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075);\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075);\n}\n.has-error .form-control:focus {\n border-color: #843534;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075), 0 0 6px #ce8483;\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075), 0 0 6px #ce8483;\n}\n.has-error .input-group-addon {\n color: #a94442;\n background-color: #f2dede;\n border-color: #a94442;\n}\n.has-error .form-control-feedback {\n color: #a94442;\n}\n.has-feedback label ~ .form-control-feedback {\n top: 25px;\n}\n.has-feedback label.sr-only ~ .form-control-feedback {\n top: 0;\n}\n.help-block {\n display: block;\n margin-top: 5px;\n margin-bottom: 10px;\n color: #737373;\n}\n@media (min-width: 768px) {\n .form-inline .form-group {\n display: inline-block;\n margin-bottom: 0;\n vertical-align: middle;\n }\n .form-inline .form-control {\n display: inline-block;\n width: auto;\n vertical-align: middle;\n }\n .form-inline .form-control-static {\n display: inline-block;\n }\n .form-inline .input-group {\n display: inline-table;\n vertical-align: middle;\n }\n .form-inline .input-group .input-group-addon,\n .form-inline .input-group .input-group-btn,\n .form-inline .input-group .form-control {\n width: auto;\n }\n .form-inline .input-group > .form-control {\n width: 100%;\n }\n .form-inline .control-label {\n margin-bottom: 0;\n vertical-align: middle;\n }\n .form-inline .radio,\n .form-inline .checkbox {\n display: inline-block;\n margin-top: 0;\n margin-bottom: 0;\n vertical-align: middle;\n }\n .form-inline .radio label,\n .form-inline .checkbox label {\n padding-left: 0;\n }\n .form-inline .radio input[type=\"radio\"],\n .form-inline .checkbox input[type=\"checkbox\"] {\n position: relative;\n margin-left: 0;\n }\n .form-inline .has-feedback .form-control-feedback {\n top: 0;\n }\n}\n.form-horizontal .radio,\n.form-horizontal .checkbox,\n.form-horizontal .radio-inline,\n.form-horizontal .checkbox-inline {\n padding-top: 7px;\n margin-top: 0;\n margin-bottom: 0;\n}\n.form-horizontal .radio,\n.form-horizontal .checkbox {\n min-height: 27px;\n}\n.form-horizontal .form-group {\n margin-right: -15px;\n margin-left: -15px;\n}\n@media (min-width: 768px) {\n .form-horizontal .control-label {\n padding-top: 7px;\n margin-bottom: 0;\n text-align: right;\n }\n}\n.form-horizontal .has-feedback .form-control-feedback {\n right: 15px;\n}\n@media (min-width: 768px) {\n .form-horizontal .form-group-lg .control-label {\n padding-top: 11px;\n font-size: 18px;\n }\n}\n@media (min-width: 768px) {\n .form-horizontal .form-group-sm .control-label {\n padding-top: 6px;\n font-size: 12px;\n }\n}\n.btn {\n display: inline-block;\n padding: 6px 12px;\n margin-bottom: 0;\n font-size: 14px;\n font-weight: normal;\n line-height: 1.42857143;\n text-align: center;\n white-space: nowrap;\n vertical-align: middle;\n -ms-touch-action: manipulation;\n touch-action: manipulation;\n cursor: pointer;\n -webkit-user-select: none;\n -moz-user-select: none;\n -ms-user-select: none;\n user-select: none;\n background-image: none;\n border: 1px solid transparent;\n border-radius: 4px;\n}\n.btn:focus,\n.btn:active:focus,\n.btn.active:focus,\n.btn.focus,\n.btn:active.focus,\n.btn.active.focus {\n outline: 5px auto -webkit-focus-ring-color;\n outline-offset: -2px;\n}\n.btn:hover,\n.btn:focus,\n.btn.focus {\n color: #333;\n text-decoration: none;\n}\n.btn:active,\n.btn.active {\n background-image: none;\n outline: 0;\n -webkit-box-shadow: inset 0 3px 5px rgba(0, 0, 0, .125);\n box-shadow: inset 0 3px 5px rgba(0, 0, 0, .125);\n}\n.btn.disabled,\n.btn[disabled],\nfieldset[disabled] .btn {\n cursor: not-allowed;\n filter: alpha(opacity=65);\n -webkit-box-shadow: none;\n box-shadow: none;\n opacity: .65;\n}\na.btn.disabled,\nfieldset[disabled] a.btn {\n pointer-events: none;\n}\n.btn-default {\n color: #333;\n background-color: #fff;\n border-color: #ccc;\n}\n.btn-default:focus,\n.btn-default.focus {\n color: #333;\n background-color: #e6e6e6;\n border-color: #8c8c8c;\n}\n.btn-default:hover {\n color: #333;\n background-color: #e6e6e6;\n border-color: #adadad;\n}\n.btn-default:active,\n.btn-default.active,\n.open > .dropdown-toggle.btn-default {\n color: #333;\n background-color: #e6e6e6;\n border-color: #adadad;\n}\n.btn-default:active:hover,\n.btn-default.active:hover,\n.open > .dropdown-toggle.btn-default:hover,\n.btn-default:active:focus,\n.btn-default.active:focus,\n.open > .dropdown-toggle.btn-default:focus,\n.btn-default:active.focus,\n.btn-default.active.focus,\n.open > .dropdown-toggle.btn-default.focus {\n color: #333;\n background-color: #d4d4d4;\n border-color: #8c8c8c;\n}\n.btn-default:active,\n.btn-default.active,\n.open > .dropdown-toggle.btn-default {\n background-image: none;\n}\n.btn-default.disabled:hover,\n.btn-default[disabled]:hover,\nfieldset[disabled] .btn-default:hover,\n.btn-default.disabled:focus,\n.btn-default[disabled]:focus,\nfieldset[disabled] .btn-default:focus,\n.btn-default.disabled.focus,\n.btn-default[disabled].focus,\nfieldset[disabled] .btn-default.focus {\n background-color: #fff;\n border-color: #ccc;\n}\n.btn-default .badge {\n color: #fff;\n background-color: #333;\n}\n.btn-primary {\n color: #fff;\n background-color: #337ab7;\n border-color: #2e6da4;\n}\n.btn-primary:focus,\n.btn-primary.focus {\n color: #fff;\n background-color: #286090;\n border-color: #122b40;\n}\n.btn-primary:hover {\n color: #fff;\n background-color: #286090;\n border-color: #204d74;\n}\n.btn-primary:active,\n.btn-primary.active,\n.open > .dropdown-toggle.btn-primary {\n color: #fff;\n background-color: #286090;\n border-color: #204d74;\n}\n.btn-primary:active:hover,\n.btn-primary.active:hover,\n.open > .dropdown-toggle.btn-primary:hover,\n.btn-primary:active:focus,\n.btn-primary.active:focus,\n.open > .dropdown-toggle.btn-primary:focus,\n.btn-primary:active.focus,\n.btn-primary.active.focus,\n.open > .dropdown-toggle.btn-primary.focus {\n color: #fff;\n background-color: #204d74;\n border-color: #122b40;\n}\n.btn-primary:active,\n.btn-primary.active,\n.open > .dropdown-toggle.btn-primary {\n background-image: none;\n}\n.btn-primary.disabled:hover,\n.btn-primary[disabled]:hover,\nfieldset[disabled] .btn-primary:hover,\n.btn-primary.disabled:focus,\n.btn-primary[disabled]:focus,\nfieldset[disabled] .btn-primary:focus,\n.btn-primary.disabled.focus,\n.btn-primary[disabled].focus,\nfieldset[disabled] .btn-primary.focus {\n background-color: #337ab7;\n border-color: #2e6da4;\n}\n.btn-primary .badge {\n color: #337ab7;\n background-color: #fff;\n}\n.btn-success {\n color: #fff;\n background-color: #5cb85c;\n border-color: #4cae4c;\n}\n.btn-success:focus,\n.btn-success.focus {\n color: #fff;\n background-color: #449d44;\n border-color: #255625;\n}\n.btn-success:hover {\n color: #fff;\n background-color: #449d44;\n border-color: #398439;\n}\n.btn-success:active,\n.btn-success.active,\n.open > .dropdown-toggle.btn-success {\n color: #fff;\n background-color: #449d44;\n border-color: #398439;\n}\n.btn-success:active:hover,\n.btn-success.active:hover,\n.open > .dropdown-toggle.btn-success:hover,\n.btn-success:active:focus,\n.btn-success.active:focus,\n.open > .dropdown-toggle.btn-success:focus,\n.btn-success:active.focus,\n.btn-success.active.focus,\n.open > .dropdown-toggle.btn-success.focus {\n color: #fff;\n background-color: #398439;\n border-color: #255625;\n}\n.btn-success:active,\n.btn-success.active,\n.open > .dropdown-toggle.btn-success {\n background-image: none;\n}\n.btn-success.disabled:hover,\n.btn-success[disabled]:hover,\nfieldset[disabled] .btn-success:hover,\n.btn-success.disabled:focus,\n.btn-success[disabled]:focus,\nfieldset[disabled] .btn-success:focus,\n.btn-success.disabled.focus,\n.btn-success[disabled].focus,\nfieldset[disabled] .btn-success.focus {\n background-color: #5cb85c;\n border-color: #4cae4c;\n}\n.btn-success .badge {\n color: #5cb85c;\n background-color: #fff;\n}\n.btn-info {\n color: #fff;\n background-color: #5bc0de;\n border-color: #46b8da;\n}\n.btn-info:focus,\n.btn-info.focus {\n color: #fff;\n background-color: #31b0d5;\n border-color: #1b6d85;\n}\n.btn-info:hover {\n color: #fff;\n background-color: #31b0d5;\n border-color: #269abc;\n}\n.btn-info:active,\n.btn-info.active,\n.open > .dropdown-toggle.btn-info {\n color: #fff;\n background-color: #31b0d5;\n border-color: #269abc;\n}\n.btn-info:active:hover,\n.btn-info.active:hover,\n.open > .dropdown-toggle.btn-info:hover,\n.btn-info:active:focus,\n.btn-info.active:focus,\n.open > .dropdown-toggle.btn-info:focus,\n.btn-info:active.focus,\n.btn-info.active.focus,\n.open > .dropdown-toggle.btn-info.focus {\n color: #fff;\n background-color: #269abc;\n border-color: #1b6d85;\n}\n.btn-info:active,\n.btn-info.active,\n.open > .dropdown-toggle.btn-info {\n background-image: none;\n}\n.btn-info.disabled:hover,\n.btn-info[disabled]:hover,\nfieldset[disabled] .btn-info:hover,\n.btn-info.disabled:focus,\n.btn-info[disabled]:focus,\nfieldset[disabled] .btn-info:focus,\n.btn-info.disabled.focus,\n.btn-info[disabled].focus,\nfieldset[disabled] .btn-info.focus {\n background-color: #5bc0de;\n border-color: #46b8da;\n}\n.btn-info .badge {\n color: #5bc0de;\n background-color: #fff;\n}\n.btn-warning {\n color: #fff;\n background-color: #f0ad4e;\n border-color: #eea236;\n}\n.btn-warning:focus,\n.btn-warning.focus {\n color: #fff;\n background-color: #ec971f;\n border-color: #985f0d;\n}\n.btn-warning:hover {\n color: #fff;\n background-color: #ec971f;\n border-color: #d58512;\n}\n.btn-warning:active,\n.btn-warning.active,\n.open > .dropdown-toggle.btn-warning {\n color: #fff;\n background-color: #ec971f;\n border-color: #d58512;\n}\n.btn-warning:active:hover,\n.btn-warning.active:hover,\n.open > .dropdown-toggle.btn-warning:hover,\n.btn-warning:active:focus,\n.btn-warning.active:focus,\n.open > .dropdown-toggle.btn-warning:focus,\n.btn-warning:active.focus,\n.btn-warning.active.focus,\n.open > .dropdown-toggle.btn-warning.focus {\n color: #fff;\n background-color: #d58512;\n border-color: #985f0d;\n}\n.btn-warning:active,\n.btn-warning.active,\n.open > .dropdown-toggle.btn-warning {\n background-image: none;\n}\n.btn-warning.disabled:hover,\n.btn-warning[disabled]:hover,\nfieldset[disabled] .btn-warning:hover,\n.btn-warning.disabled:focus,\n.btn-warning[disabled]:focus,\nfieldset[disabled] .btn-warning:focus,\n.btn-warning.disabled.focus,\n.btn-warning[disabled].focus,\nfieldset[disabled] .btn-warning.focus {\n background-color: #f0ad4e;\n border-color: #eea236;\n}\n.btn-warning .badge {\n color: #f0ad4e;\n background-color: #fff;\n}\n.btn-danger {\n color: #fff;\n background-color: #d9534f;\n border-color: #d43f3a;\n}\n.btn-danger:focus,\n.btn-danger.focus {\n color: #fff;\n background-color: #c9302c;\n border-color: #761c19;\n}\n.btn-danger:hover {\n color: #fff;\n background-color: #c9302c;\n border-color: #ac2925;\n}\n.btn-danger:active,\n.btn-danger.active,\n.open > .dropdown-toggle.btn-danger {\n color: #fff;\n background-color: #c9302c;\n border-color: #ac2925;\n}\n.btn-danger:active:hover,\n.btn-danger.active:hover,\n.open > .dropdown-toggle.btn-danger:hover,\n.btn-danger:active:focus,\n.btn-danger.active:focus,\n.open > .dropdown-toggle.btn-danger:focus,\n.btn-danger:active.focus,\n.btn-danger.active.focus,\n.open > .dropdown-toggle.btn-danger.focus {\n color: #fff;\n background-color: #ac2925;\n border-color: #761c19;\n}\n.btn-danger:active,\n.btn-danger.active,\n.open > .dropdown-toggle.btn-danger {\n background-image: none;\n}\n.btn-danger.disabled:hover,\n.btn-danger[disabled]:hover,\nfieldset[disabled] .btn-danger:hover,\n.btn-danger.disabled:focus,\n.btn-danger[disabled]:focus,\nfieldset[disabled] .btn-danger:focus,\n.btn-danger.disabled.focus,\n.btn-danger[disabled].focus,\nfieldset[disabled] .btn-danger.focus {\n background-color: #d9534f;\n border-color: #d43f3a;\n}\n.btn-danger .badge {\n color: #d9534f;\n background-color: #fff;\n}\n.btn-link {\n font-weight: normal;\n color: #337ab7;\n border-radius: 0;\n}\n.btn-link,\n.btn-link:active,\n.btn-link.active,\n.btn-link[disabled],\nfieldset[disabled] .btn-link {\n background-color: transparent;\n -webkit-box-shadow: none;\n box-shadow: none;\n}\n.btn-link,\n.btn-link:hover,\n.btn-link:focus,\n.btn-link:active {\n border-color: transparent;\n}\n.btn-link:hover,\n.btn-link:focus {\n color: #23527c;\n text-decoration: underline;\n background-color: transparent;\n}\n.btn-link[disabled]:hover,\nfieldset[disabled] .btn-link:hover,\n.btn-link[disabled]:focus,\nfieldset[disabled] .btn-link:focus {\n color: #777;\n text-decoration: none;\n}\n.btn-lg,\n.btn-group-lg > .btn {\n padding: 10px 16px;\n font-size: 18px;\n line-height: 1.3333333;\n border-radius: 6px;\n}\n.btn-sm,\n.btn-group-sm > .btn {\n padding: 5px 10px;\n font-size: 12px;\n line-height: 1.5;\n border-radius: 3px;\n}\n.btn-xs,\n.btn-group-xs > .btn {\n padding: 1px 5px;\n font-size: 12px;\n line-height: 1.5;\n border-radius: 3px;\n}\n.btn-block {\n display: block;\n width: 100%;\n}\n.btn-block + .btn-block {\n margin-top: 5px;\n}\ninput[type=\"submit\"].btn-block,\ninput[type=\"reset\"].btn-block,\ninput[type=\"button\"].btn-block {\n width: 100%;\n}\n.fade {\n opacity: 0;\n -webkit-transition: opacity .15s linear;\n -o-transition: opacity .15s linear;\n transition: opacity .15s linear;\n}\n.fade.in {\n opacity: 1;\n}\n.collapse {\n display: none;\n}\n.collapse.in {\n display: block;\n}\ntr.collapse.in {\n display: table-row;\n}\ntbody.collapse.in {\n display: table-row-group;\n}\n.collapsing {\n position: relative;\n height: 0;\n overflow: hidden;\n -webkit-transition-timing-function: ease;\n -o-transition-timing-function: ease;\n transition-timing-function: ease;\n -webkit-transition-duration: .35s;\n -o-transition-duration: .35s;\n transition-duration: .35s;\n -webkit-transition-property: height, visibility;\n -o-transition-property: height, visibility;\n transition-property: height, visibility;\n}\n.caret {\n display: inline-block;\n width: 0;\n height: 0;\n margin-left: 2px;\n vertical-align: middle;\n border-top: 4px dashed;\n border-top: 4px solid \\9;\n border-right: 4px solid transparent;\n border-left: 4px solid transparent;\n}\n.dropup,\n.dropdown {\n position: relative;\n}\n.dropdown-toggle:focus {\n outline: 0;\n}\n.dropdown-menu {\n position: absolute;\n top: 100%;\n left: 0;\n z-index: 1000;\n display: none;\n float: left;\n min-width: 160px;\n padding: 5px 0;\n margin: 2px 0 0;\n font-size: 14px;\n text-align: left;\n list-style: none;\n background-color: #fff;\n -webkit-background-clip: padding-box;\n background-clip: padding-box;\n border: 1px solid #ccc;\n border: 1px solid rgba(0, 0, 0, .15);\n border-radius: 4px;\n -webkit-box-shadow: 0 6px 12px rgba(0, 0, 0, .175);\n box-shadow: 0 6px 12px rgba(0, 0, 0, .175);\n}\n.dropdown-menu.pull-right {\n right: 0;\n left: auto;\n}\n.dropdown-menu .divider {\n height: 1px;\n margin: 9px 0;\n overflow: hidden;\n background-color: #e5e5e5;\n}\n.dropdown-menu > li > a {\n display: block;\n padding: 3px 20px;\n clear: both;\n font-weight: normal;\n line-height: 1.42857143;\n color: #333;\n white-space: nowrap;\n}\n.dropdown-menu > li > a:hover,\n.dropdown-menu > li > a:focus {\n color: #262626;\n text-decoration: none;\n background-color: #f5f5f5;\n}\n.dropdown-menu > .active > a,\n.dropdown-menu > .active > a:hover,\n.dropdown-menu > .active > a:focus {\n color: #fff;\n text-decoration: none;\n background-color: #337ab7;\n outline: 0;\n}\n.dropdown-menu > .disabled > a,\n.dropdown-menu > .disabled > a:hover,\n.dropdown-menu > .disabled > a:focus {\n color: #777;\n}\n.dropdown-menu > .disabled > a:hover,\n.dropdown-menu > .disabled > a:focus {\n text-decoration: none;\n cursor: not-allowed;\n background-color: transparent;\n background-image: none;\n filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);\n}\n.open > .dropdown-menu {\n display: block;\n}\n.open > a {\n outline: 0;\n}\n.dropdown-menu-right {\n right: 0;\n left: auto;\n}\n.dropdown-menu-left {\n right: auto;\n left: 0;\n}\n.dropdown-header {\n display: block;\n padding: 3px 20px;\n font-size: 12px;\n line-height: 1.42857143;\n color: #777;\n white-space: nowrap;\n}\n.dropdown-backdrop {\n position: fixed;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: 990;\n}\n.pull-right > .dropdown-menu {\n right: 0;\n left: auto;\n}\n.dropup .caret,\n.navbar-fixed-bottom .dropdown .caret {\n content: \"\";\n border-top: 0;\n border-bottom: 4px dashed;\n border-bottom: 4px solid \\9;\n}\n.dropup .dropdown-menu,\n.navbar-fixed-bottom .dropdown .dropdown-menu {\n top: auto;\n bottom: 100%;\n margin-bottom: 2px;\n}\n@media (min-width: 768px) {\n .navbar-right .dropdown-menu {\n right: 0;\n left: auto;\n }\n .navbar-right .dropdown-menu-left {\n right: auto;\n left: 0;\n }\n}\n.btn-group,\n.btn-group-vertical {\n position: relative;\n display: inline-block;\n vertical-align: middle;\n}\n.btn-group > .btn,\n.btn-group-vertical > .btn {\n position: relative;\n float: left;\n}\n.btn-group > .btn:hover,\n.btn-group-vertical > .btn:hover,\n.btn-group > .btn:focus,\n.btn-group-vertical > .btn:focus,\n.btn-group > .btn:active,\n.btn-group-vertical > .btn:active,\n.btn-group > .btn.active,\n.btn-group-vertical > .btn.active {\n z-index: 2;\n}\n.btn-group .btn + .btn,\n.btn-group .btn + .btn-group,\n.btn-group .btn-group + .btn,\n.btn-group .btn-group + .btn-group {\n margin-left: -1px;\n}\n.btn-toolbar {\n margin-left: -5px;\n}\n.btn-toolbar .btn,\n.btn-toolbar .btn-group,\n.btn-toolbar .input-group {\n float: left;\n}\n.btn-toolbar > .btn,\n.btn-toolbar > .btn-group,\n.btn-toolbar > .input-group {\n margin-left: 5px;\n}\n.btn-group > .btn:not(:first-child):not(:last-child):not(.dropdown-toggle) {\n border-radius: 0;\n}\n.btn-group > .btn:first-child {\n margin-left: 0;\n}\n.btn-group > .btn:first-child:not(:last-child):not(.dropdown-toggle) {\n border-top-right-radius: 0;\n border-bottom-right-radius: 0;\n}\n.btn-group > .btn:last-child:not(:first-child),\n.btn-group > .dropdown-toggle:not(:first-child) {\n border-top-left-radius: 0;\n border-bottom-left-radius: 0;\n}\n.btn-group > .btn-group {\n float: left;\n}\n.btn-group > .btn-group:not(:first-child):not(:last-child) > .btn {\n border-radius: 0;\n}\n.btn-group > .btn-group:first-child:not(:last-child) > .btn:last-child,\n.btn-group > .btn-group:first-child:not(:last-child) > .dropdown-toggle {\n border-top-right-radius: 0;\n border-bottom-right-radius: 0;\n}\n.btn-group > .btn-group:last-child:not(:first-child) > .btn:first-child {\n border-top-left-radius: 0;\n border-bottom-left-radius: 0;\n}\n.btn-group .dropdown-toggle:active,\n.btn-group.open .dropdown-toggle {\n outline: 0;\n}\n.btn-group > .btn + .dropdown-toggle {\n padding-right: 8px;\n padding-left: 8px;\n}\n.btn-group > .btn-lg + .dropdown-toggle {\n padding-right: 12px;\n padding-left: 12px;\n}\n.btn-group.open .dropdown-toggle {\n -webkit-box-shadow: inset 0 3px 5px rgba(0, 0, 0, .125);\n box-shadow: inset 0 3px 5px rgba(0, 0, 0, .125);\n}\n.btn-group.open .dropdown-toggle.btn-link {\n -webkit-box-shadow: none;\n box-shadow: none;\n}\n.btn .caret {\n margin-left: 0;\n}\n.btn-lg .caret {\n border-width: 5px 5px 0;\n border-bottom-width: 0;\n}\n.dropup .btn-lg .caret {\n border-width: 0 5px 5px;\n}\n.btn-group-vertical > .btn,\n.btn-group-vertical > .btn-group,\n.btn-group-vertical > .btn-group > .btn {\n display: block;\n float: none;\n width: 100%;\n max-width: 100%;\n}\n.btn-group-vertical > .btn-group > .btn {\n float: none;\n}\n.btn-group-vertical > .btn + .btn,\n.btn-group-vertical > .btn + .btn-group,\n.btn-group-vertical > .btn-group + .btn,\n.btn-group-vertical > .btn-group + .btn-group {\n margin-top: -1px;\n margin-left: 0;\n}\n.btn-group-vertical > .btn:not(:first-child):not(:last-child) {\n border-radius: 0;\n}\n.btn-group-vertical > .btn:first-child:not(:last-child) {\n border-top-left-radius: 4px;\n border-top-right-radius: 4px;\n border-bottom-right-radius: 0;\n border-bottom-left-radius: 0;\n}\n.btn-group-vertical > .btn:last-child:not(:first-child) {\n border-top-left-radius: 0;\n border-top-right-radius: 0;\n border-bottom-right-radius: 4px;\n border-bottom-left-radius: 4px;\n}\n.btn-group-vertical > .btn-group:not(:first-child):not(:last-child) > .btn {\n border-radius: 0;\n}\n.btn-group-vertical > .btn-group:first-child:not(:last-child) > .btn:last-child,\n.btn-group-vertical > .btn-group:first-child:not(:last-child) > .dropdown-toggle {\n border-bottom-right-radius: 0;\n border-bottom-left-radius: 0;\n}\n.btn-group-vertical > .btn-group:last-child:not(:first-child) > .btn:first-child {\n border-top-left-radius: 0;\n border-top-right-radius: 0;\n}\n.btn-group-justified {\n display: table;\n width: 100%;\n table-layout: fixed;\n border-collapse: separate;\n}\n.btn-group-justified > .btn,\n.btn-group-justified > .btn-group {\n display: table-cell;\n float: none;\n width: 1%;\n}\n.btn-group-justified > .btn-group .btn {\n width: 100%;\n}\n.btn-group-justified > .btn-group .dropdown-menu {\n left: auto;\n}\n[data-toggle=\"buttons\"] > .btn input[type=\"radio\"],\n[data-toggle=\"buttons\"] > .btn-group > .btn input[type=\"radio\"],\n[data-toggle=\"buttons\"] > .btn input[type=\"checkbox\"],\n[data-toggle=\"buttons\"] > .btn-group > .btn input[type=\"checkbox\"] {\n position: absolute;\n clip: rect(0, 0, 0, 0);\n pointer-events: none;\n}\n.input-group {\n position: relative;\n display: table;\n border-collapse: separate;\n}\n.input-group[class*=\"col-\"] {\n float: none;\n padding-right: 0;\n padding-left: 0;\n}\n.input-group .form-control {\n position: relative;\n z-index: 2;\n float: left;\n width: 100%;\n margin-bottom: 0;\n}\n.input-group .form-control:focus {\n z-index: 3;\n}\n.input-group-lg > .form-control,\n.input-group-lg > .input-group-addon,\n.input-group-lg > .input-group-btn > .btn {\n height: 46px;\n padding: 10px 16px;\n font-size: 18px;\n line-height: 1.3333333;\n border-radius: 6px;\n}\nselect.input-group-lg > .form-control,\nselect.input-group-lg > .input-group-addon,\nselect.input-group-lg > .input-group-btn > .btn {\n height: 46px;\n line-height: 46px;\n}\ntextarea.input-group-lg > .form-control,\ntextarea.input-group-lg > .input-group-addon,\ntextarea.input-group-lg > .input-group-btn > .btn,\nselect[multiple].input-group-lg > .form-control,\nselect[multiple].input-group-lg > .input-group-addon,\nselect[multiple].input-group-lg > .input-group-btn > .btn {\n height: auto;\n}\n.input-group-sm > .form-control,\n.input-group-sm > .input-group-addon,\n.input-group-sm > .input-group-btn > .btn {\n height: 30px;\n padding: 5px 10px;\n font-size: 12px;\n line-height: 1.5;\n border-radius: 3px;\n}\nselect.input-group-sm > .form-control,\nselect.input-group-sm > .input-group-addon,\nselect.input-group-sm > .input-group-btn > .btn {\n height: 30px;\n line-height: 30px;\n}\ntextarea.input-group-sm > .form-control,\ntextarea.input-group-sm > .input-group-addon,\ntextarea.input-group-sm > .input-group-btn > .btn,\nselect[multiple].input-group-sm > .form-control,\nselect[multiple].input-group-sm > .input-group-addon,\nselect[multiple].input-group-sm > .input-group-btn > .btn {\n height: auto;\n}\n.input-group-addon,\n.input-group-btn,\n.input-group .form-control {\n display: table-cell;\n}\n.input-group-addon:not(:first-child):not(:last-child),\n.input-group-btn:not(:first-child):not(:last-child),\n.input-group .form-control:not(:first-child):not(:last-child) {\n border-radius: 0;\n}\n.input-group-addon,\n.input-group-btn {\n width: 1%;\n white-space: nowrap;\n vertical-align: middle;\n}\n.input-group-addon {\n padding: 6px 12px;\n font-size: 14px;\n font-weight: normal;\n line-height: 1;\n color: #555;\n text-align: center;\n background-color: #eee;\n border: 1px solid #ccc;\n border-radius: 4px;\n}\n.input-group-addon.input-sm {\n padding: 5px 10px;\n font-size: 12px;\n border-radius: 3px;\n}\n.input-group-addon.input-lg {\n padding: 10px 16px;\n font-size: 18px;\n border-radius: 6px;\n}\n.input-group-addon input[type=\"radio\"],\n.input-group-addon input[type=\"checkbox\"] {\n margin-top: 0;\n}\n.input-group .form-control:first-child,\n.input-group-addon:first-child,\n.input-group-btn:first-child > .btn,\n.input-group-btn:first-child > .btn-group > .btn,\n.input-group-btn:first-child > .dropdown-toggle,\n.input-group-btn:last-child > .btn:not(:last-child):not(.dropdown-toggle),\n.input-group-btn:last-child > .btn-group:not(:last-child) > .btn {\n border-top-right-radius: 0;\n border-bottom-right-radius: 0;\n}\n.input-group-addon:first-child {\n border-right: 0;\n}\n.input-group .form-control:last-child,\n.input-group-addon:last-child,\n.input-group-btn:last-child > .btn,\n.input-group-btn:last-child > .btn-group > .btn,\n.input-group-btn:last-child > .dropdown-toggle,\n.input-group-btn:first-child > .btn:not(:first-child),\n.input-group-btn:first-child > .btn-group:not(:first-child) > .btn {\n border-top-left-radius: 0;\n border-bottom-left-radius: 0;\n}\n.input-group-addon:last-child {\n border-left: 0;\n}\n.input-group-btn {\n position: relative;\n font-size: 0;\n white-space: nowrap;\n}\n.input-group-btn > .btn {\n position: relative;\n}\n.input-group-btn > .btn + .btn {\n margin-left: -1px;\n}\n.input-group-btn > .btn:hover,\n.input-group-btn > .btn:focus,\n.input-group-btn > .btn:active {\n z-index: 2;\n}\n.input-group-btn:first-child > .btn,\n.input-group-btn:first-child > .btn-group {\n margin-right: -1px;\n}\n.input-group-btn:last-child > .btn,\n.input-group-btn:last-child > .btn-group {\n z-index: 2;\n margin-left: -1px;\n}\n.nav {\n padding-left: 0;\n margin-bottom: 0;\n list-style: none;\n}\n.nav > li {\n position: relative;\n display: block;\n}\n.nav > li > a {\n position: relative;\n display: block;\n padding: 10px 15px;\n}\n.nav > li > a:hover,\n.nav > li > a:focus {\n text-decoration: none;\n background-color: #eee;\n}\n.nav > li.disabled > a {\n color: #777;\n}\n.nav > li.disabled > a:hover,\n.nav > li.disabled > a:focus {\n color: #777;\n text-decoration: none;\n cursor: not-allowed;\n background-color: transparent;\n}\n.nav .open > a,\n.nav .open > a:hover,\n.nav .open > a:focus {\n background-color: #eee;\n border-color: #337ab7;\n}\n.nav .nav-divider {\n height: 1px;\n margin: 9px 0;\n overflow: hidden;\n background-color: #e5e5e5;\n}\n.nav > li > a > img {\n max-width: none;\n}\n.nav-tabs {\n border-bottom: 1px solid #ddd;\n}\n.nav-tabs > li {\n float: left;\n margin-bottom: -1px;\n}\n.nav-tabs > li > a {\n margin-right: 2px;\n line-height: 1.42857143;\n border: 1px solid transparent;\n border-radius: 4px 4px 0 0;\n}\n.nav-tabs > li > a:hover {\n border-color: #eee #eee #ddd;\n}\n.nav-tabs > li.active > a,\n.nav-tabs > li.active > a:hover,\n.nav-tabs > li.active > a:focus {\n color: #555;\n cursor: default;\n background-color: #fff;\n border: 1px solid #ddd;\n border-bottom-color: transparent;\n}\n.nav-tabs.nav-justified {\n width: 100%;\n border-bottom: 0;\n}\n.nav-tabs.nav-justified > li {\n float: none;\n}\n.nav-tabs.nav-justified > li > a {\n margin-bottom: 5px;\n text-align: center;\n}\n.nav-tabs.nav-justified > .dropdown .dropdown-menu {\n top: auto;\n left: auto;\n}\n@media (min-width: 768px) {\n .nav-tabs.nav-justified > li {\n display: table-cell;\n width: 1%;\n }\n .nav-tabs.nav-justified > li > a {\n margin-bottom: 0;\n }\n}\n.nav-tabs.nav-justified > li > a {\n margin-right: 0;\n border-radius: 4px;\n}\n.nav-tabs.nav-justified > .active > a,\n.nav-tabs.nav-justified > .active > a:hover,\n.nav-tabs.nav-justified > .active > a:focus {\n border: 1px solid #ddd;\n}\n@media (min-width: 768px) {\n .nav-tabs.nav-justified > li > a {\n border-bottom: 1px solid #ddd;\n border-radius: 4px 4px 0 0;\n }\n .nav-tabs.nav-justified > .active > a,\n .nav-tabs.nav-justified > .active > a:hover,\n .nav-tabs.nav-justified > .active > a:focus {\n border-bottom-color: #fff;\n }\n}\n.nav-pills > li {\n float: left;\n}\n.nav-pills > li > a {\n border-radius: 4px;\n}\n.nav-pills > li + li {\n margin-left: 2px;\n}\n.nav-pills > li.active > a,\n.nav-pills > li.active > a:hover,\n.nav-pills > li.active > a:focus {\n color: #fff;\n background-color: #337ab7;\n}\n.nav-stacked > li {\n float: none;\n}\n.nav-stacked > li + li {\n margin-top: 2px;\n margin-left: 0;\n}\n.nav-justified {\n width: 100%;\n}\n.nav-justified > li {\n float: none;\n}\n.nav-justified > li > a {\n margin-bottom: 5px;\n text-align: center;\n}\n.nav-justified > .dropdown .dropdown-menu {\n top: auto;\n left: auto;\n}\n@media (min-width: 768px) {\n .nav-justified > li {\n display: table-cell;\n width: 1%;\n }\n .nav-justified > li > a {\n margin-bottom: 0;\n }\n}\n.nav-tabs-justified {\n border-bottom: 0;\n}\n.nav-tabs-justified > li > a {\n margin-right: 0;\n border-radius: 4px;\n}\n.nav-tabs-justified > .active > a,\n.nav-tabs-justified > .active > a:hover,\n.nav-tabs-justified > .active > a:focus {\n border: 1px solid #ddd;\n}\n@media (min-width: 768px) {\n .nav-tabs-justified > li > a {\n border-bottom: 1px solid #ddd;\n border-radius: 4px 4px 0 0;\n }\n .nav-tabs-justified > .active > a,\n .nav-tabs-justified > .active > a:hover,\n .nav-tabs-justified > .active > a:focus {\n border-bottom-color: #fff;\n }\n}\n.tab-content > .tab-pane {\n display: none;\n}\n.tab-content > .active {\n display: block;\n}\n.nav-tabs .dropdown-menu {\n margin-top: -1px;\n border-top-left-radius: 0;\n border-top-right-radius: 0;\n}\n.navbar {\n position: relative;\n min-height: 50px;\n margin-bottom: 20px;\n border: 1px solid transparent;\n}\n@media (min-width: 768px) {\n .navbar {\n border-radius: 4px;\n }\n}\n@media (min-width: 768px) {\n .navbar-header {\n float: left;\n }\n}\n.navbar-collapse {\n padding-right: 15px;\n padding-left: 15px;\n overflow-x: visible;\n -webkit-overflow-scrolling: touch;\n border-top: 1px solid transparent;\n -webkit-box-shadow: inset 0 1px 0 rgba(255, 255, 255, .1);\n box-shadow: inset 0 1px 0 rgba(255, 255, 255, .1);\n}\n.navbar-collapse.in {\n overflow-y: auto;\n}\n@media (min-width: 768px) {\n .navbar-collapse {\n width: auto;\n border-top: 0;\n -webkit-box-shadow: none;\n box-shadow: none;\n }\n .navbar-collapse.collapse {\n display: block !important;\n height: auto !important;\n padding-bottom: 0;\n overflow: visible !important;\n }\n .navbar-collapse.in {\n overflow-y: visible;\n }\n .navbar-fixed-top .navbar-collapse,\n .navbar-static-top .navbar-collapse,\n .navbar-fixed-bottom .navbar-collapse {\n padding-right: 0;\n padding-left: 0;\n }\n}\n.navbar-fixed-top .navbar-collapse,\n.navbar-fixed-bottom .navbar-collapse {\n max-height: 340px;\n}\n@media (max-device-width: 480px) and (orientation: landscape) {\n .navbar-fixed-top .navbar-collapse,\n .navbar-fixed-bottom .navbar-collapse {\n max-height: 200px;\n }\n}\n.container > .navbar-header,\n.container-fluid > .navbar-header,\n.container > .navbar-collapse,\n.container-fluid > .navbar-collapse {\n margin-right: -15px;\n margin-left: -15px;\n}\n@media (min-width: 768px) {\n .container > .navbar-header,\n .container-fluid > .navbar-header,\n .container > .navbar-collapse,\n .container-fluid > .navbar-collapse {\n margin-right: 0;\n margin-left: 0;\n }\n}\n.navbar-static-top {\n z-index: 1000;\n border-width: 0 0 1px;\n}\n@media (min-width: 768px) {\n .navbar-static-top {\n border-radius: 0;\n }\n}\n.navbar-fixed-top,\n.navbar-fixed-bottom {\n position: fixed;\n right: 0;\n left: 0;\n z-index: 1030;\n}\n@media (min-width: 768px) {\n .navbar-fixed-top,\n .navbar-fixed-bottom {\n border-radius: 0;\n }\n}\n.navbar-fixed-top {\n top: 0;\n border-width: 0 0 1px;\n}\n.navbar-fixed-bottom {\n bottom: 0;\n margin-bottom: 0;\n border-width: 1px 0 0;\n}\n.navbar-brand {\n float: left;\n height: 50px;\n padding: 15px 15px;\n font-size: 18px;\n line-height: 20px;\n}\n.navbar-brand:hover,\n.navbar-brand:focus {\n text-decoration: none;\n}\n.navbar-brand > img {\n display: block;\n}\n@media (min-width: 768px) {\n .navbar > .container .navbar-brand,\n .navbar > .container-fluid .navbar-brand {\n margin-left: -15px;\n }\n}\n.navbar-toggle {\n position: relative;\n float: right;\n padding: 9px 10px;\n margin-top: 8px;\n margin-right: 15px;\n margin-bottom: 8px;\n background-color: transparent;\n background-image: none;\n border: 1px solid transparent;\n border-radius: 4px;\n}\n.navbar-toggle:focus {\n outline: 0;\n}\n.navbar-toggle .icon-bar {\n display: block;\n width: 22px;\n height: 2px;\n border-radius: 1px;\n}\n.navbar-toggle .icon-bar + .icon-bar {\n margin-top: 4px;\n}\n@media (min-width: 768px) {\n .navbar-toggle {\n display: none;\n }\n}\n.navbar-nav {\n margin: 7.5px -15px;\n}\n.navbar-nav > li > a {\n padding-top: 10px;\n padding-bottom: 10px;\n line-height: 20px;\n}\n@media (max-width: 767px) {\n .navbar-nav .open .dropdown-menu {\n position: static;\n float: none;\n width: auto;\n margin-top: 0;\n background-color: transparent;\n border: 0;\n -webkit-box-shadow: none;\n box-shadow: none;\n }\n .navbar-nav .open .dropdown-menu > li > a,\n .navbar-nav .open .dropdown-menu .dropdown-header {\n padding: 5px 15px 5px 25px;\n }\n .navbar-nav .open .dropdown-menu > li > a {\n line-height: 20px;\n }\n .navbar-nav .open .dropdown-menu > li > a:hover,\n .navbar-nav .open .dropdown-menu > li > a:focus {\n background-image: none;\n }\n}\n@media (min-width: 768px) {\n .navbar-nav {\n float: left;\n margin: 0;\n }\n .navbar-nav > li {\n float: left;\n }\n .navbar-nav > li > a {\n padding-top: 15px;\n padding-bottom: 15px;\n }\n}\n.navbar-form {\n padding: 10px 15px;\n margin-top: 8px;\n margin-right: -15px;\n margin-bottom: 8px;\n margin-left: -15px;\n border-top: 1px solid transparent;\n border-bottom: 1px solid transparent;\n -webkit-box-shadow: inset 0 1px 0 rgba(255, 255, 255, .1), 0 1px 0 rgba(255, 255, 255, .1);\n box-shadow: inset 0 1px 0 rgba(255, 255, 255, .1), 0 1px 0 rgba(255, 255, 255, .1);\n}\n@media (min-width: 768px) {\n .navbar-form .form-group {\n display: inline-block;\n margin-bottom: 0;\n vertical-align: middle;\n }\n .navbar-form .form-control {\n display: inline-block;\n width: auto;\n vertical-align: middle;\n }\n .navbar-form .form-control-static {\n display: inline-block;\n }\n .navbar-form .input-group {\n display: inline-table;\n vertical-align: middle;\n }\n .navbar-form .input-group .input-group-addon,\n .navbar-form .input-group .input-group-btn,\n .navbar-form .input-group .form-control {\n width: auto;\n }\n .navbar-form .input-group > .form-control {\n width: 100%;\n }\n .navbar-form .control-label {\n margin-bottom: 0;\n vertical-align: middle;\n }\n .navbar-form .radio,\n .navbar-form .checkbox {\n display: inline-block;\n margin-top: 0;\n margin-bottom: 0;\n vertical-align: middle;\n }\n .navbar-form .radio label,\n .navbar-form .checkbox label {\n padding-left: 0;\n }\n .navbar-form .radio input[type=\"radio\"],\n .navbar-form .checkbox input[type=\"checkbox\"] {\n position: relative;\n margin-left: 0;\n }\n .navbar-form .has-feedback .form-control-feedback {\n top: 0;\n }\n}\n@media (max-width: 767px) {\n .navbar-form .form-group {\n margin-bottom: 5px;\n }\n .navbar-form .form-group:last-child {\n margin-bottom: 0;\n }\n}\n@media (min-width: 768px) {\n .navbar-form {\n width: auto;\n padding-top: 0;\n padding-bottom: 0;\n margin-right: 0;\n margin-left: 0;\n border: 0;\n -webkit-box-shadow: none;\n box-shadow: none;\n }\n}\n.navbar-nav > li > .dropdown-menu {\n margin-top: 0;\n border-top-left-radius: 0;\n border-top-right-radius: 0;\n}\n.navbar-fixed-bottom .navbar-nav > li > .dropdown-menu {\n margin-bottom: 0;\n border-top-left-radius: 4px;\n border-top-right-radius: 4px;\n border-bottom-right-radius: 0;\n border-bottom-left-radius: 0;\n}\n.navbar-btn {\n margin-top: 8px;\n margin-bottom: 8px;\n}\n.navbar-btn.btn-sm {\n margin-top: 10px;\n margin-bottom: 10px;\n}\n.navbar-btn.btn-xs {\n margin-top: 14px;\n margin-bottom: 14px;\n}\n.navbar-text {\n margin-top: 15px;\n margin-bottom: 15px;\n}\n@media (min-width: 768px) {\n .navbar-text {\n float: left;\n margin-right: 15px;\n margin-left: 15px;\n }\n}\n@media (min-width: 768px) {\n .navbar-left {\n float: left !important;\n }\n .navbar-right {\n float: right !important;\n margin-right: -15px;\n }\n .navbar-right ~ .navbar-right {\n margin-right: 0;\n }\n}\n.navbar-default {\n background-color: #f8f8f8;\n border-color: #e7e7e7;\n}\n.navbar-default .navbar-brand {\n color: #777;\n}\n.navbar-default .navbar-brand:hover,\n.navbar-default .navbar-brand:focus {\n color: #5e5e5e;\n background-color: transparent;\n}\n.navbar-default .navbar-text {\n color: #777;\n}\n.navbar-default .navbar-nav > li > a {\n color: #777;\n}\n.navbar-default .navbar-nav > li > a:hover,\n.navbar-default .navbar-nav > li > a:focus {\n color: #333;\n background-color: transparent;\n}\n.navbar-default .navbar-nav > .active > a,\n.navbar-default .navbar-nav > .active > a:hover,\n.navbar-default .navbar-nav > .active > a:focus {\n color: #555;\n background-color: #e7e7e7;\n}\n.navbar-default .navbar-nav > .disabled > a,\n.navbar-default .navbar-nav > .disabled > a:hover,\n.navbar-default .navbar-nav > .disabled > a:focus {\n color: #ccc;\n background-color: transparent;\n}\n.navbar-default .navbar-toggle {\n border-color: #ddd;\n}\n.navbar-default .navbar-toggle:hover,\n.navbar-default .navbar-toggle:focus {\n background-color: #ddd;\n}\n.navbar-default .navbar-toggle .icon-bar {\n background-color: #888;\n}\n.navbar-default .navbar-collapse,\n.navbar-default .navbar-form {\n border-color: #e7e7e7;\n}\n.navbar-default .navbar-nav > .open > a,\n.navbar-default .navbar-nav > .open > a:hover,\n.navbar-default .navbar-nav > .open > a:focus {\n color: #555;\n background-color: #e7e7e7;\n}\n@media (max-width: 767px) {\n .navbar-default .navbar-nav .open .dropdown-menu > li > a {\n color: #777;\n }\n .navbar-default .navbar-nav .open .dropdown-menu > li > a:hover,\n .navbar-default .navbar-nav .open .dropdown-menu > li > a:focus {\n color: #333;\n background-color: transparent;\n }\n .navbar-default .navbar-nav .open .dropdown-menu > .active > a,\n .navbar-default .navbar-nav .open .dropdown-menu > .active > a:hover,\n .navbar-default .navbar-nav .open .dropdown-menu > .active > a:focus {\n color: #555;\n background-color: #e7e7e7;\n }\n .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a,\n .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a:hover,\n .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a:focus {\n color: #ccc;\n background-color: transparent;\n }\n}\n.navbar-default .navbar-link {\n color: #777;\n}\n.navbar-default .navbar-link:hover {\n color: #333;\n}\n.navbar-default .btn-link {\n color: #777;\n}\n.navbar-default .btn-link:hover,\n.navbar-default .btn-link:focus {\n color: #333;\n}\n.navbar-default .btn-link[disabled]:hover,\nfieldset[disabled] .navbar-default .btn-link:hover,\n.navbar-default .btn-link[disabled]:focus,\nfieldset[disabled] .navbar-default .btn-link:focus {\n color: #ccc;\n}\n.navbar-inverse {\n background-color: #222;\n border-color: #080808;\n}\n.navbar-inverse .navbar-brand {\n color: #9d9d9d;\n}\n.navbar-inverse .navbar-brand:hover,\n.navbar-inverse .navbar-brand:focus {\n color: #fff;\n background-color: transparent;\n}\n.navbar-inverse .navbar-text {\n color: #9d9d9d;\n}\n.navbar-inverse .navbar-nav > li > a {\n color: #9d9d9d;\n}\n.navbar-inverse .navbar-nav > li > a:hover,\n.navbar-inverse .navbar-nav > li > a:focus {\n color: #fff;\n background-color: transparent;\n}\n.navbar-inverse .navbar-nav > .active > a,\n.navbar-inverse .navbar-nav > .active > a:hover,\n.navbar-inverse .navbar-nav > .active > a:focus {\n color: #fff;\n background-color: #080808;\n}\n.navbar-inverse .navbar-nav > .disabled > a,\n.navbar-inverse .navbar-nav > .disabled > a:hover,\n.navbar-inverse .navbar-nav > .disabled > a:focus {\n color: #444;\n background-color: transparent;\n}\n.navbar-inverse .navbar-toggle {\n border-color: #333;\n}\n.navbar-inverse .navbar-toggle:hover,\n.navbar-inverse .navbar-toggle:focus {\n background-color: #333;\n}\n.navbar-inverse .navbar-toggle .icon-bar {\n background-color: #fff;\n}\n.navbar-inverse .navbar-collapse,\n.navbar-inverse .navbar-form {\n border-color: #101010;\n}\n.navbar-inverse .navbar-nav > .open > a,\n.navbar-inverse .navbar-nav > .open > a:hover,\n.navbar-inverse .navbar-nav > .open > a:focus {\n color: #fff;\n background-color: #080808;\n}\n@media (max-width: 767px) {\n .navbar-inverse .navbar-nav .open .dropdown-menu > .dropdown-header {\n border-color: #080808;\n }\n .navbar-inverse .navbar-nav .open .dropdown-menu .divider {\n background-color: #080808;\n }\n .navbar-inverse .navbar-nav .open .dropdown-menu > li > a {\n color: #9d9d9d;\n }\n .navbar-inverse .navbar-nav .open .dropdown-menu > li > a:hover,\n .navbar-inverse .navbar-nav .open .dropdown-menu > li > a:focus {\n color: #fff;\n background-color: transparent;\n }\n .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a,\n .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a:hover,\n .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a:focus {\n color: #fff;\n background-color: #080808;\n }\n .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a,\n .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a:hover,\n .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a:focus {\n color: #444;\n background-color: transparent;\n }\n}\n.navbar-inverse .navbar-link {\n color: #9d9d9d;\n}\n.navbar-inverse .navbar-link:hover {\n color: #fff;\n}\n.navbar-inverse .btn-link {\n color: #9d9d9d;\n}\n.navbar-inverse .btn-link:hover,\n.navbar-inverse .btn-link:focus {\n color: #fff;\n}\n.navbar-inverse .btn-link[disabled]:hover,\nfieldset[disabled] .navbar-inverse .btn-link:hover,\n.navbar-inverse .btn-link[disabled]:focus,\nfieldset[disabled] .navbar-inverse .btn-link:focus {\n color: #444;\n}\n.breadcrumb {\n padding: 8px 15px;\n margin-bottom: 20px;\n list-style: none;\n background-color: #f5f5f5;\n border-radius: 4px;\n}\n.breadcrumb > li {\n display: inline-block;\n}\n.breadcrumb > li + li:before {\n padding: 0 5px;\n color: #ccc;\n content: \"/\\00a0\";\n}\n.breadcrumb > .active {\n color: #777;\n}\n.pagination {\n display: inline-block;\n padding-left: 0;\n margin: 20px 0;\n border-radius: 4px;\n}\n.pagination > li {\n display: inline;\n}\n.pagination > li > a,\n.pagination > li > span {\n position: relative;\n float: left;\n padding: 6px 12px;\n margin-left: -1px;\n line-height: 1.42857143;\n color: #337ab7;\n text-decoration: none;\n background-color: #fff;\n border: 1px solid #ddd;\n}\n.pagination > li:first-child > a,\n.pagination > li:first-child > span {\n margin-left: 0;\n border-top-left-radius: 4px;\n border-bottom-left-radius: 4px;\n}\n.pagination > li:last-child > a,\n.pagination > li:last-child > span {\n border-top-right-radius: 4px;\n border-bottom-right-radius: 4px;\n}\n.pagination > li > a:hover,\n.pagination > li > span:hover,\n.pagination > li > a:focus,\n.pagination > li > span:focus {\n z-index: 2;\n color: #23527c;\n background-color: #eee;\n border-color: #ddd;\n}\n.pagination > .active > a,\n.pagination > .active > span,\n.pagination > .active > a:hover,\n.pagination > .active > span:hover,\n.pagination > .active > a:focus,\n.pagination > .active > span:focus {\n z-index: 3;\n color: #fff;\n cursor: default;\n background-color: #337ab7;\n border-color: #337ab7;\n}\n.pagination > .disabled > span,\n.pagination > .disabled > span:hover,\n.pagination > .disabled > span:focus,\n.pagination > .disabled > a,\n.pagination > .disabled > a:hover,\n.pagination > .disabled > a:focus {\n color: #777;\n cursor: not-allowed;\n background-color: #fff;\n border-color: #ddd;\n}\n.pagination-lg > li > a,\n.pagination-lg > li > span {\n padding: 10px 16px;\n font-size: 18px;\n line-height: 1.3333333;\n}\n.pagination-lg > li:first-child > a,\n.pagination-lg > li:first-child > span {\n border-top-left-radius: 6px;\n border-bottom-left-radius: 6px;\n}\n.pagination-lg > li:last-child > a,\n.pagination-lg > li:last-child > span {\n border-top-right-radius: 6px;\n border-bottom-right-radius: 6px;\n}\n.pagination-sm > li > a,\n.pagination-sm > li > span {\n padding: 5px 10px;\n font-size: 12px;\n line-height: 1.5;\n}\n.pagination-sm > li:first-child > a,\n.pagination-sm > li:first-child > span {\n border-top-left-radius: 3px;\n border-bottom-left-radius: 3px;\n}\n.pagination-sm > li:last-child > a,\n.pagination-sm > li:last-child > span {\n border-top-right-radius: 3px;\n border-bottom-right-radius: 3px;\n}\n.pager {\n padding-left: 0;\n margin: 20px 0;\n text-align: center;\n list-style: none;\n}\n.pager li {\n display: inline;\n}\n.pager li > a,\n.pager li > span {\n display: inline-block;\n padding: 5px 14px;\n background-color: #fff;\n border: 1px solid #ddd;\n border-radius: 15px;\n}\n.pager li > a:hover,\n.pager li > a:focus {\n text-decoration: none;\n background-color: #eee;\n}\n.pager .next > a,\n.pager .next > span {\n float: right;\n}\n.pager .previous > a,\n.pager .previous > span {\n float: left;\n}\n.pager .disabled > a,\n.pager .disabled > a:hover,\n.pager .disabled > a:focus,\n.pager .disabled > span {\n color: #777;\n cursor: not-allowed;\n background-color: #fff;\n}\n.label {\n display: inline;\n padding: .2em .6em .3em;\n font-size: 75%;\n font-weight: bold;\n line-height: 1;\n color: #fff;\n text-align: center;\n white-space: nowrap;\n vertical-align: baseline;\n border-radius: .25em;\n}\na.label:hover,\na.label:focus {\n color: #fff;\n text-decoration: none;\n cursor: pointer;\n}\n.label:empty {\n display: none;\n}\n.btn .label {\n position: relative;\n top: -1px;\n}\n.label-default {\n background-color: #777;\n}\n.label-default[href]:hover,\n.label-default[href]:focus {\n background-color: #5e5e5e;\n}\n.label-primary {\n background-color: #337ab7;\n}\n.label-primary[href]:hover,\n.label-primary[href]:focus {\n background-color: #286090;\n}\n.label-success {\n background-color: #5cb85c;\n}\n.label-success[href]:hover,\n.label-success[href]:focus {\n background-color: #449d44;\n}\n.label-info {\n background-color: #5bc0de;\n}\n.label-info[href]:hover,\n.label-info[href]:focus {\n background-color: #31b0d5;\n}\n.label-warning {\n background-color: #f0ad4e;\n}\n.label-warning[href]:hover,\n.label-warning[href]:focus {\n background-color: #ec971f;\n}\n.label-danger {\n background-color: #d9534f;\n}\n.label-danger[href]:hover,\n.label-danger[href]:focus {\n background-color: #c9302c;\n}\n.badge {\n display: inline-block;\n min-width: 10px;\n padding: 3px 7px;\n font-size: 12px;\n font-weight: bold;\n line-height: 1;\n color: #fff;\n text-align: center;\n white-space: nowrap;\n vertical-align: middle;\n background-color: #777;\n border-radius: 10px;\n}\n.badge:empty {\n display: none;\n}\n.btn .badge {\n position: relative;\n top: -1px;\n}\n.btn-xs .badge,\n.btn-group-xs > .btn .badge {\n top: 0;\n padding: 1px 5px;\n}\na.badge:hover,\na.badge:focus {\n color: #fff;\n text-decoration: none;\n cursor: pointer;\n}\n.list-group-item.active > .badge,\n.nav-pills > .active > a > .badge {\n color: #337ab7;\n background-color: #fff;\n}\n.list-group-item > .badge {\n float: right;\n}\n.list-group-item > .badge + .badge {\n margin-right: 5px;\n}\n.nav-pills > li > a > .badge {\n margin-left: 3px;\n}\n.jumbotron {\n padding-top: 30px;\n padding-bottom: 30px;\n margin-bottom: 30px;\n color: inherit;\n background-color: #eee;\n}\n.jumbotron h1,\n.jumbotron .h1 {\n color: inherit;\n}\n.jumbotron p {\n margin-bottom: 15px;\n font-size: 21px;\n font-weight: 200;\n}\n.jumbotron > hr {\n border-top-color: #d5d5d5;\n}\n.container .jumbotron,\n.container-fluid .jumbotron {\n padding-right: 15px;\n padding-left: 15px;\n border-radius: 6px;\n}\n.jumbotron .container {\n max-width: 100%;\n}\n@media screen and (min-width: 768px) {\n .jumbotron {\n padding-top: 48px;\n padding-bottom: 48px;\n }\n .container .jumbotron,\n .container-fluid .jumbotron {\n padding-right: 60px;\n padding-left: 60px;\n }\n .jumbotron h1,\n .jumbotron .h1 {\n font-size: 63px;\n }\n}\n.thumbnail {\n display: block;\n padding: 4px;\n margin-bottom: 20px;\n line-height: 1.42857143;\n background-color: #fff;\n border: 1px solid #ddd;\n border-radius: 4px;\n -webkit-transition: border .2s ease-in-out;\n -o-transition: border .2s ease-in-out;\n transition: border .2s ease-in-out;\n}\n.thumbnail > img,\n.thumbnail a > img {\n margin-right: auto;\n margin-left: auto;\n}\na.thumbnail:hover,\na.thumbnail:focus,\na.thumbnail.active {\n border-color: #337ab7;\n}\n.thumbnail .caption {\n padding: 9px;\n color: #333;\n}\n.alert {\n padding: 15px;\n margin-bottom: 20px;\n border: 1px solid transparent;\n border-radius: 4px;\n}\n.alert h4 {\n margin-top: 0;\n color: inherit;\n}\n.alert .alert-link {\n font-weight: bold;\n}\n.alert > p,\n.alert > ul {\n margin-bottom: 0;\n}\n.alert > p + p {\n margin-top: 5px;\n}\n.alert-dismissable,\n.alert-dismissible {\n padding-right: 35px;\n}\n.alert-dismissable .close,\n.alert-dismissible .close {\n position: relative;\n top: -2px;\n right: -21px;\n color: inherit;\n}\n.alert-success {\n color: #3c763d;\n background-color: #dff0d8;\n border-color: #d6e9c6;\n}\n.alert-success hr {\n border-top-color: #c9e2b3;\n}\n.alert-success .alert-link {\n color: #2b542c;\n}\n.alert-info {\n color: #31708f;\n background-color: #d9edf7;\n border-color: #bce8f1;\n}\n.alert-info hr {\n border-top-color: #a6e1ec;\n}\n.alert-info .alert-link {\n color: #245269;\n}\n.alert-warning {\n color: #8a6d3b;\n background-color: #fcf8e3;\n border-color: #faebcc;\n}\n.alert-warning hr {\n border-top-color: #f7e1b5;\n}\n.alert-warning .alert-link {\n color: #66512c;\n}\n.alert-danger {\n color: #a94442;\n background-color: #f2dede;\n border-color: #ebccd1;\n}\n.alert-danger hr {\n border-top-color: #e4b9c0;\n}\n.alert-danger .alert-link {\n color: #843534;\n}\n@-webkit-keyframes progress-bar-stripes {\n from {\n background-position: 40px 0;\n }\n to {\n background-position: 0 0;\n }\n}\n@-o-keyframes progress-bar-stripes {\n from {\n background-position: 40px 0;\n }\n to {\n background-position: 0 0;\n }\n}\n@keyframes progress-bar-stripes {\n from {\n background-position: 40px 0;\n }\n to {\n background-position: 0 0;\n }\n}\n.progress {\n height: 20px;\n margin-bottom: 20px;\n overflow: hidden;\n background-color: #f5f5f5;\n border-radius: 4px;\n -webkit-box-shadow: inset 0 1px 2px rgba(0, 0, 0, .1);\n box-shadow: inset 0 1px 2px rgba(0, 0, 0, .1);\n}\n.progress-bar {\n float: left;\n width: 0;\n height: 100%;\n font-size: 12px;\n line-height: 20px;\n color: #fff;\n text-align: center;\n background-color: #337ab7;\n -webkit-box-shadow: inset 0 -1px 0 rgba(0, 0, 0, .15);\n box-shadow: inset 0 -1px 0 rgba(0, 0, 0, .15);\n -webkit-transition: width .6s ease;\n -o-transition: width .6s ease;\n transition: width .6s ease;\n}\n.progress-striped .progress-bar,\n.progress-bar-striped {\n background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);\n background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);\n background-image: linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);\n -webkit-background-size: 40px 40px;\n background-size: 40px 40px;\n}\n.progress.active .progress-bar,\n.progress-bar.active {\n -webkit-animation: progress-bar-stripes 2s linear infinite;\n -o-animation: progress-bar-stripes 2s linear infinite;\n animation: progress-bar-stripes 2s linear infinite;\n}\n.progress-bar-success {\n background-color: #5cb85c;\n}\n.progress-striped .progress-bar-success {\n background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);\n background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);\n background-image: linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);\n}\n.progress-bar-info {\n background-color: #5bc0de;\n}\n.progress-striped .progress-bar-info {\n background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);\n background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);\n background-image: linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);\n}\n.progress-bar-warning {\n background-color: #f0ad4e;\n}\n.progress-striped .progress-bar-warning {\n background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);\n background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);\n background-image: linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);\n}\n.progress-bar-danger {\n background-color: #d9534f;\n}\n.progress-striped .progress-bar-danger {\n background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);\n background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);\n background-image: linear-gradient(45deg, rgba(255, 255, 255, .15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, .15) 50%, rgba(255, 255, 255, .15) 75%, transparent 75%, transparent);\n}\n.media {\n margin-top: 15px;\n}\n.media:first-child {\n margin-top: 0;\n}\n.media,\n.media-body {\n overflow: hidden;\n zoom: 1;\n}\n.media-body {\n width: 10000px;\n}\n.media-object {\n display: block;\n}\n.media-object.img-thumbnail {\n max-width: none;\n}\n.media-right,\n.media > .pull-right {\n padding-left: 10px;\n}\n.media-left,\n.media > .pull-left {\n padding-right: 10px;\n}\n.media-left,\n.media-right,\n.media-body {\n display: table-cell;\n vertical-align: top;\n}\n.media-middle {\n vertical-align: middle;\n}\n.media-bottom {\n vertical-align: bottom;\n}\n.media-heading {\n margin-top: 0;\n margin-bottom: 5px;\n}\n.media-list {\n padding-left: 0;\n list-style: none;\n}\n.list-group {\n padding-left: 0;\n margin-bottom: 20px;\n}\n.list-group-item {\n position: relative;\n display: block;\n padding: 10px 15px;\n margin-bottom: -1px;\n background-color: #fff;\n border: 1px solid #ddd;\n}\n.list-group-item:first-child {\n border-top-left-radius: 4px;\n border-top-right-radius: 4px;\n}\n.list-group-item:last-child {\n margin-bottom: 0;\n border-bottom-right-radius: 4px;\n border-bottom-left-radius: 4px;\n}\na.list-group-item,\nbutton.list-group-item {\n color: #555;\n}\na.list-group-item .list-group-item-heading,\nbutton.list-group-item .list-group-item-heading {\n color: #333;\n}\na.list-group-item:hover,\nbutton.list-group-item:hover,\na.list-group-item:focus,\nbutton.list-group-item:focus {\n color: #555;\n text-decoration: none;\n background-color: #f5f5f5;\n}\nbutton.list-group-item {\n width: 100%;\n text-align: left;\n}\n.list-group-item.disabled,\n.list-group-item.disabled:hover,\n.list-group-item.disabled:focus {\n color: #777;\n cursor: not-allowed;\n background-color: #eee;\n}\n.list-group-item.disabled .list-group-item-heading,\n.list-group-item.disabled:hover .list-group-item-heading,\n.list-group-item.disabled:focus .list-group-item-heading {\n color: inherit;\n}\n.list-group-item.disabled .list-group-item-text,\n.list-group-item.disabled:hover .list-group-item-text,\n.list-group-item.disabled:focus .list-group-item-text {\n color: #777;\n}\n.list-group-item.active,\n.list-group-item.active:hover,\n.list-group-item.active:focus {\n z-index: 2;\n color: #fff;\n background-color: #337ab7;\n border-color: #337ab7;\n}\n.list-group-item.active .list-group-item-heading,\n.list-group-item.active:hover .list-group-item-heading,\n.list-group-item.active:focus .list-group-item-heading,\n.list-group-item.active .list-group-item-heading > small,\n.list-group-item.active:hover .list-group-item-heading > small,\n.list-group-item.active:focus .list-group-item-heading > small,\n.list-group-item.active .list-group-item-heading > .small,\n.list-group-item.active:hover .list-group-item-heading > .small,\n.list-group-item.active:focus .list-group-item-heading > .small {\n color: inherit;\n}\n.list-group-item.active .list-group-item-text,\n.list-group-item.active:hover .list-group-item-text,\n.list-group-item.active:focus .list-group-item-text {\n color: #c7ddef;\n}\n.list-group-item-success {\n color: #3c763d;\n background-color: #dff0d8;\n}\na.list-group-item-success,\nbutton.list-group-item-success {\n color: #3c763d;\n}\na.list-group-item-success .list-group-item-heading,\nbutton.list-group-item-success .list-group-item-heading {\n color: inherit;\n}\na.list-group-item-success:hover,\nbutton.list-group-item-success:hover,\na.list-group-item-success:focus,\nbutton.list-group-item-success:focus {\n color: #3c763d;\n background-color: #d0e9c6;\n}\na.list-group-item-success.active,\nbutton.list-group-item-success.active,\na.list-group-item-success.active:hover,\nbutton.list-group-item-success.active:hover,\na.list-group-item-success.active:focus,\nbutton.list-group-item-success.active:focus {\n color: #fff;\n background-color: #3c763d;\n border-color: #3c763d;\n}\n.list-group-item-info {\n color: #31708f;\n background-color: #d9edf7;\n}\na.list-group-item-info,\nbutton.list-group-item-info {\n color: #31708f;\n}\na.list-group-item-info .list-group-item-heading,\nbutton.list-group-item-info .list-group-item-heading {\n color: inherit;\n}\na.list-group-item-info:hover,\nbutton.list-group-item-info:hover,\na.list-group-item-info:focus,\nbutton.list-group-item-info:focus {\n color: #31708f;\n background-color: #c4e3f3;\n}\na.list-group-item-info.active,\nbutton.list-group-item-info.active,\na.list-group-item-info.active:hover,\nbutton.list-group-item-info.active:hover,\na.list-group-item-info.active:focus,\nbutton.list-group-item-info.active:focus {\n color: #fff;\n background-color: #31708f;\n border-color: #31708f;\n}\n.list-group-item-warning {\n color: #8a6d3b;\n background-color: #fcf8e3;\n}\na.list-group-item-warning,\nbutton.list-group-item-warning {\n color: #8a6d3b;\n}\na.list-group-item-warning .list-group-item-heading,\nbutton.list-group-item-warning .list-group-item-heading {\n color: inherit;\n}\na.list-group-item-warning:hover,\nbutton.list-group-item-warning:hover,\na.list-group-item-warning:focus,\nbutton.list-group-item-warning:focus {\n color: #8a6d3b;\n background-color: #faf2cc;\n}\na.list-group-item-warning.active,\nbutton.list-group-item-warning.active,\na.list-group-item-warning.active:hover,\nbutton.list-group-item-warning.active:hover,\na.list-group-item-warning.active:focus,\nbutton.list-group-item-warning.active:focus {\n color: #fff;\n background-color: #8a6d3b;\n border-color: #8a6d3b;\n}\n.list-group-item-danger {\n color: #a94442;\n background-color: #f2dede;\n}\na.list-group-item-danger,\nbutton.list-group-item-danger {\n color: #a94442;\n}\na.list-group-item-danger .list-group-item-heading,\nbutton.list-group-item-danger .list-group-item-heading {\n color: inherit;\n}\na.list-group-item-danger:hover,\nbutton.list-group-item-danger:hover,\na.list-group-item-danger:focus,\nbutton.list-group-item-danger:focus {\n color: #a94442;\n background-color: #ebcccc;\n}\na.list-group-item-danger.active,\nbutton.list-group-item-danger.active,\na.list-group-item-danger.active:hover,\nbutton.list-group-item-danger.active:hover,\na.list-group-item-danger.active:focus,\nbutton.list-group-item-danger.active:focus {\n color: #fff;\n background-color: #a94442;\n border-color: #a94442;\n}\n.list-group-item-heading {\n margin-top: 0;\n margin-bottom: 5px;\n}\n.list-group-item-text {\n margin-bottom: 0;\n line-height: 1.3;\n}\n.panel {\n margin-bottom: 20px;\n background-color: #fff;\n border: 1px solid transparent;\n border-radius: 4px;\n -webkit-box-shadow: 0 1px 1px rgba(0, 0, 0, .05);\n box-shadow: 0 1px 1px rgba(0, 0, 0, .05);\n}\n.panel-body {\n padding: 15px;\n}\n.panel-heading {\n padding: 10px 15px;\n border-bottom: 1px solid transparent;\n border-top-left-radius: 3px;\n border-top-right-radius: 3px;\n}\n.panel-heading > .dropdown .dropdown-toggle {\n color: inherit;\n}\n.panel-title {\n margin-top: 0;\n margin-bottom: 0;\n font-size: 16px;\n color: inherit;\n}\n.panel-title > a,\n.panel-title > small,\n.panel-title > .small,\n.panel-title > small > a,\n.panel-title > .small > a {\n color: inherit;\n}\n.panel-footer {\n padding: 10px 15px;\n background-color: #f5f5f5;\n border-top: 1px solid #ddd;\n border-bottom-right-radius: 3px;\n border-bottom-left-radius: 3px;\n}\n.panel > .list-group,\n.panel > .panel-collapse > .list-group {\n margin-bottom: 0;\n}\n.panel > .list-group .list-group-item,\n.panel > .panel-collapse > .list-group .list-group-item {\n border-width: 1px 0;\n border-radius: 0;\n}\n.panel > .list-group:first-child .list-group-item:first-child,\n.panel > .panel-collapse > .list-group:first-child .list-group-item:first-child {\n border-top: 0;\n border-top-left-radius: 3px;\n border-top-right-radius: 3px;\n}\n.panel > .list-group:last-child .list-group-item:last-child,\n.panel > .panel-collapse > .list-group:last-child .list-group-item:last-child {\n border-bottom: 0;\n border-bottom-right-radius: 3px;\n border-bottom-left-radius: 3px;\n}\n.panel > .panel-heading + .panel-collapse > .list-group .list-group-item:first-child {\n border-top-left-radius: 0;\n border-top-right-radius: 0;\n}\n.panel-heading + .list-group .list-group-item:first-child {\n border-top-width: 0;\n}\n.list-group + .panel-footer {\n border-top-width: 0;\n}\n.panel > .table,\n.panel > .table-responsive > .table,\n.panel > .panel-collapse > .table {\n margin-bottom: 0;\n}\n.panel > .table caption,\n.panel > .table-responsive > .table caption,\n.panel > .panel-collapse > .table caption {\n padding-right: 15px;\n padding-left: 15px;\n}\n.panel > .table:first-child,\n.panel > .table-responsive:first-child > .table:first-child {\n border-top-left-radius: 3px;\n border-top-right-radius: 3px;\n}\n.panel > .table:first-child > thead:first-child > tr:first-child,\n.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child,\n.panel > .table:first-child > tbody:first-child > tr:first-child,\n.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child {\n border-top-left-radius: 3px;\n border-top-right-radius: 3px;\n}\n.panel > .table:first-child > thead:first-child > tr:first-child td:first-child,\n.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child td:first-child,\n.panel > .table:first-child > tbody:first-child > tr:first-child td:first-child,\n.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child td:first-child,\n.panel > .table:first-child > thead:first-child > tr:first-child th:first-child,\n.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child th:first-child,\n.panel > .table:first-child > tbody:first-child > tr:first-child th:first-child,\n.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child th:first-child {\n border-top-left-radius: 3px;\n}\n.panel > .table:first-child > thead:first-child > tr:first-child td:last-child,\n.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child td:last-child,\n.panel > .table:first-child > tbody:first-child > tr:first-child td:last-child,\n.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child td:last-child,\n.panel > .table:first-child > thead:first-child > tr:first-child th:last-child,\n.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child th:last-child,\n.panel > .table:first-child > tbody:first-child > tr:first-child th:last-child,\n.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child th:last-child {\n border-top-right-radius: 3px;\n}\n.panel > .table:last-child,\n.panel > .table-responsive:last-child > .table:last-child {\n border-bottom-right-radius: 3px;\n border-bottom-left-radius: 3px;\n}\n.panel > .table:last-child > tbody:last-child > tr:last-child,\n.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child,\n.panel > .table:last-child > tfoot:last-child > tr:last-child,\n.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child {\n border-bottom-right-radius: 3px;\n border-bottom-left-radius: 3px;\n}\n.panel > .table:last-child > tbody:last-child > tr:last-child td:first-child,\n.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child td:first-child,\n.panel > .table:last-child > tfoot:last-child > tr:last-child td:first-child,\n.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child td:first-child,\n.panel > .table:last-child > tbody:last-child > tr:last-child th:first-child,\n.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child th:first-child,\n.panel > .table:last-child > tfoot:last-child > tr:last-child th:first-child,\n.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child th:first-child {\n border-bottom-left-radius: 3px;\n}\n.panel > .table:last-child > tbody:last-child > tr:last-child td:last-child,\n.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child td:last-child,\n.panel > .table:last-child > tfoot:last-child > tr:last-child td:last-child,\n.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child td:last-child,\n.panel > .table:last-child > tbody:last-child > tr:last-child th:last-child,\n.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child th:last-child,\n.panel > .table:last-child > tfoot:last-child > tr:last-child th:last-child,\n.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child th:last-child {\n border-bottom-right-radius: 3px;\n}\n.panel > .panel-body + .table,\n.panel > .panel-body + .table-responsive,\n.panel > .table + .panel-body,\n.panel > .table-responsive + .panel-body {\n border-top: 1px solid #ddd;\n}\n.panel > .table > tbody:first-child > tr:first-child th,\n.panel > .table > tbody:first-child > tr:first-child td {\n border-top: 0;\n}\n.panel > .table-bordered,\n.panel > .table-responsive > .table-bordered {\n border: 0;\n}\n.panel > .table-bordered > thead > tr > th:first-child,\n.panel > .table-responsive > .table-bordered > thead > tr > th:first-child,\n.panel > .table-bordered > tbody > tr > th:first-child,\n.panel > .table-responsive > .table-bordered > tbody > tr > th:first-child,\n.panel > .table-bordered > tfoot > tr > th:first-child,\n.panel > .table-responsive > .table-bordered > tfoot > tr > th:first-child,\n.panel > .table-bordered > thead > tr > td:first-child,\n.panel > .table-responsive > .table-bordered > thead > tr > td:first-child,\n.panel > .table-bordered > tbody > tr > td:first-child,\n.panel > .table-responsive > .table-bordered > tbody > tr > td:first-child,\n.panel > .table-bordered > tfoot > tr > td:first-child,\n.panel > .table-responsive > .table-bordered > tfoot > tr > td:first-child {\n border-left: 0;\n}\n.panel > .table-bordered > thead > tr > th:last-child,\n.panel > .table-responsive > .table-bordered > thead > tr > th:last-child,\n.panel > .table-bordered > tbody > tr > th:last-child,\n.panel > .table-responsive > .table-bordered > tbody > tr > th:last-child,\n.panel > .table-bordered > tfoot > tr > th:last-child,\n.panel > .table-responsive > .table-bordered > tfoot > tr > th:last-child,\n.panel > .table-bordered > thead > tr > td:last-child,\n.panel > .table-responsive > .table-bordered > thead > tr > td:last-child,\n.panel > .table-bordered > tbody > tr > td:last-child,\n.panel > .table-responsive > .table-bordered > tbody > tr > td:last-child,\n.panel > .table-bordered > tfoot > tr > td:last-child,\n.panel > .table-responsive > .table-bordered > tfoot > tr > td:last-child {\n border-right: 0;\n}\n.panel > .table-bordered > thead > tr:first-child > td,\n.panel > .table-responsive > .table-bordered > thead > tr:first-child > td,\n.panel > .table-bordered > tbody > tr:first-child > td,\n.panel > .table-responsive > .table-bordered > tbody > tr:first-child > td,\n.panel > .table-bordered > thead > tr:first-child > th,\n.panel > .table-responsive > .table-bordered > thead > tr:first-child > th,\n.panel > .table-bordered > tbody > tr:first-child > th,\n.panel > .table-responsive > .table-bordered > tbody > tr:first-child > th {\n border-bottom: 0;\n}\n.panel > .table-bordered > tbody > tr:last-child > td,\n.panel > .table-responsive > .table-bordered > tbody > tr:last-child > td,\n.panel > .table-bordered > tfoot > tr:last-child > td,\n.panel > .table-responsive > .table-bordered > tfoot > tr:last-child > td,\n.panel > .table-bordered > tbody > tr:last-child > th,\n.panel > .table-responsive > .table-bordered > tbody > tr:last-child > th,\n.panel > .table-bordered > tfoot > tr:last-child > th,\n.panel > .table-responsive > .table-bordered > tfoot > tr:last-child > th {\n border-bottom: 0;\n}\n.panel > .table-responsive {\n margin-bottom: 0;\n border: 0;\n}\n.panel-group {\n margin-bottom: 20px;\n}\n.panel-group .panel {\n margin-bottom: 0;\n border-radius: 4px;\n}\n.panel-group .panel + .panel {\n margin-top: 5px;\n}\n.panel-group .panel-heading {\n border-bottom: 0;\n}\n.panel-group .panel-heading + .panel-collapse > .panel-body,\n.panel-group .panel-heading + .panel-collapse > .list-group {\n border-top: 1px solid #ddd;\n}\n.panel-group .panel-footer {\n border-top: 0;\n}\n.panel-group .panel-footer + .panel-collapse .panel-body {\n border-bottom: 1px solid #ddd;\n}\n.panel-default {\n border-color: #ddd;\n}\n.panel-default > .panel-heading {\n color: #333;\n background-color: #f5f5f5;\n border-color: #ddd;\n}\n.panel-default > .panel-heading + .panel-collapse > .panel-body {\n border-top-color: #ddd;\n}\n.panel-default > .panel-heading .badge {\n color: #f5f5f5;\n background-color: #333;\n}\n.panel-default > .panel-footer + .panel-collapse > .panel-body {\n border-bottom-color: #ddd;\n}\n.panel-primary {\n border-color: #337ab7;\n}\n.panel-primary > .panel-heading {\n color: #fff;\n background-color: #337ab7;\n border-color: #337ab7;\n}\n.panel-primary > .panel-heading + .panel-collapse > .panel-body {\n border-top-color: #337ab7;\n}\n.panel-primary > .panel-heading .badge {\n color: #337ab7;\n background-color: #fff;\n}\n.panel-primary > .panel-footer + .panel-collapse > .panel-body {\n border-bottom-color: #337ab7;\n}\n.panel-success {\n border-color: #d6e9c6;\n}\n.panel-success > .panel-heading {\n color: #3c763d;\n background-color: #dff0d8;\n border-color: #d6e9c6;\n}\n.panel-success > .panel-heading + .panel-collapse > .panel-body {\n border-top-color: #d6e9c6;\n}\n.panel-success > .panel-heading .badge {\n color: #dff0d8;\n background-color: #3c763d;\n}\n.panel-success > .panel-footer + .panel-collapse > .panel-body {\n border-bottom-color: #d6e9c6;\n}\n.panel-info {\n border-color: #bce8f1;\n}\n.panel-info > .panel-heading {\n color: #31708f;\n background-color: #d9edf7;\n border-color: #bce8f1;\n}\n.panel-info > .panel-heading + .panel-collapse > .panel-body {\n border-top-color: #bce8f1;\n}\n.panel-info > .panel-heading .badge {\n color: #d9edf7;\n background-color: #31708f;\n}\n.panel-info > .panel-footer + .panel-collapse > .panel-body {\n border-bottom-color: #bce8f1;\n}\n.panel-warning {\n border-color: #faebcc;\n}\n.panel-warning > .panel-heading {\n color: #8a6d3b;\n background-color: #fcf8e3;\n border-color: #faebcc;\n}\n.panel-warning > .panel-heading + .panel-collapse > .panel-body {\n border-top-color: #faebcc;\n}\n.panel-warning > .panel-heading .badge {\n color: #fcf8e3;\n background-color: #8a6d3b;\n}\n.panel-warning > .panel-footer + .panel-collapse > .panel-body {\n border-bottom-color: #faebcc;\n}\n.panel-danger {\n border-color: #ebccd1;\n}\n.panel-danger > .panel-heading {\n color: #a94442;\n background-color: #f2dede;\n border-color: #ebccd1;\n}\n.panel-danger > .panel-heading + .panel-collapse > .panel-body {\n border-top-color: #ebccd1;\n}\n.panel-danger > .panel-heading .badge {\n color: #f2dede;\n background-color: #a94442;\n}\n.panel-danger > .panel-footer + .panel-collapse > .panel-body {\n border-bottom-color: #ebccd1;\n}\n.embed-responsive {\n position: relative;\n display: block;\n height: 0;\n padding: 0;\n overflow: hidden;\n}\n.embed-responsive .embed-responsive-item,\n.embed-responsive iframe,\n.embed-responsive embed,\n.embed-responsive object,\n.embed-responsive video {\n position: absolute;\n top: 0;\n bottom: 0;\n left: 0;\n width: 100%;\n height: 100%;\n border: 0;\n}\n.embed-responsive-16by9 {\n padding-bottom: 56.25%;\n}\n.embed-responsive-4by3 {\n padding-bottom: 75%;\n}\n.well {\n min-height: 20px;\n padding: 19px;\n margin-bottom: 20px;\n background-color: #f5f5f5;\n border: 1px solid #e3e3e3;\n border-radius: 4px;\n -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, .05);\n box-shadow: inset 0 1px 1px rgba(0, 0, 0, .05);\n}\n.well blockquote {\n border-color: #ddd;\n border-color: rgba(0, 0, 0, .15);\n}\n.well-lg {\n padding: 24px;\n border-radius: 6px;\n}\n.well-sm {\n padding: 9px;\n border-radius: 3px;\n}\n.close {\n float: right;\n font-size: 21px;\n font-weight: bold;\n line-height: 1;\n color: #000;\n text-shadow: 0 1px 0 #fff;\n filter: alpha(opacity=20);\n opacity: .2;\n}\n.close:hover,\n.close:focus {\n color: #000;\n text-decoration: none;\n cursor: pointer;\n filter: alpha(opacity=50);\n opacity: .5;\n}\nbutton.close {\n -webkit-appearance: none;\n padding: 0;\n cursor: pointer;\n background: transparent;\n border: 0;\n}\n.modal-open {\n overflow: hidden;\n}\n.modal {\n position: fixed;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: 1050;\n display: none;\n overflow: hidden;\n -webkit-overflow-scrolling: touch;\n outline: 0;\n}\n.modal.fade .modal-dialog {\n -webkit-transition: -webkit-transform .3s ease-out;\n -o-transition: -o-transform .3s ease-out;\n transition: transform .3s ease-out;\n -webkit-transform: translate(0, -25%);\n -ms-transform: translate(0, -25%);\n -o-transform: translate(0, -25%);\n transform: translate(0, -25%);\n}\n.modal.in .modal-dialog {\n -webkit-transform: translate(0, 0);\n -ms-transform: translate(0, 0);\n -o-transform: translate(0, 0);\n transform: translate(0, 0);\n}\n.modal-open .modal {\n overflow-x: hidden;\n overflow-y: auto;\n}\n.modal-dialog {\n position: relative;\n width: auto;\n margin: 10px;\n}\n.modal-content {\n position: relative;\n background-color: #fff;\n -webkit-background-clip: padding-box;\n background-clip: padding-box;\n border: 1px solid #999;\n border: 1px solid rgba(0, 0, 0, .2);\n border-radius: 6px;\n outline: 0;\n -webkit-box-shadow: 0 3px 9px rgba(0, 0, 0, .5);\n box-shadow: 0 3px 9px rgba(0, 0, 0, .5);\n}\n.modal-backdrop {\n position: fixed;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: 1040;\n background-color: #000;\n}\n.modal-backdrop.fade {\n filter: alpha(opacity=0);\n opacity: 0;\n}\n.modal-backdrop.in {\n filter: alpha(opacity=50);\n opacity: .5;\n}\n.modal-header {\n padding: 15px;\n border-bottom: 1px solid #e5e5e5;\n}\n.modal-header .close {\n margin-top: -2px;\n}\n.modal-title {\n margin: 0;\n line-height: 1.42857143;\n}\n.modal-body {\n position: relative;\n padding: 15px;\n}\n.modal-footer {\n padding: 15px;\n text-align: right;\n border-top: 1px solid #e5e5e5;\n}\n.modal-footer .btn + .btn {\n margin-bottom: 0;\n margin-left: 5px;\n}\n.modal-footer .btn-group .btn + .btn {\n margin-left: -1px;\n}\n.modal-footer .btn-block + .btn-block {\n margin-left: 0;\n}\n.modal-scrollbar-measure {\n position: absolute;\n top: -9999px;\n width: 50px;\n height: 50px;\n overflow: scroll;\n}\n@media (min-width: 768px) {\n .modal-dialog {\n width: 600px;\n margin: 30px auto;\n }\n .modal-content {\n -webkit-box-shadow: 0 5px 15px rgba(0, 0, 0, .5);\n box-shadow: 0 5px 15px rgba(0, 0, 0, .5);\n }\n .modal-sm {\n width: 300px;\n }\n}\n@media (min-width: 992px) {\n .modal-lg {\n width: 900px;\n }\n}\n.tooltip {\n position: absolute;\n z-index: 1070;\n display: block;\n font-family: \"Helvetica Neue\", Helvetica, Arial, sans-serif;\n font-size: 12px;\n font-style: normal;\n font-weight: normal;\n line-height: 1.42857143;\n text-align: left;\n text-align: start;\n text-decoration: none;\n text-shadow: none;\n text-transform: none;\n letter-spacing: normal;\n word-break: normal;\n word-spacing: normal;\n word-wrap: normal;\n white-space: normal;\n filter: alpha(opacity=0);\n opacity: 0;\n\n line-break: auto;\n}\n.tooltip.in {\n filter: alpha(opacity=90);\n opacity: .9;\n}\n.tooltip.top {\n padding: 5px 0;\n margin-top: -3px;\n}\n.tooltip.right {\n padding: 0 5px;\n margin-left: 3px;\n}\n.tooltip.bottom {\n padding: 5px 0;\n margin-top: 3px;\n}\n.tooltip.left {\n padding: 0 5px;\n margin-left: -3px;\n}\n.tooltip-inner {\n max-width: 200px;\n padding: 3px 8px;\n color: #fff;\n text-align: center;\n background-color: #000;\n border-radius: 4px;\n}\n.tooltip-arrow {\n position: absolute;\n width: 0;\n height: 0;\n border-color: transparent;\n border-style: solid;\n}\n.tooltip.top .tooltip-arrow {\n bottom: 0;\n left: 50%;\n margin-left: -5px;\n border-width: 5px 5px 0;\n border-top-color: #000;\n}\n.tooltip.top-left .tooltip-arrow {\n right: 5px;\n bottom: 0;\n margin-bottom: -5px;\n border-width: 5px 5px 0;\n border-top-color: #000;\n}\n.tooltip.top-right .tooltip-arrow {\n bottom: 0;\n left: 5px;\n margin-bottom: -5px;\n border-width: 5px 5px 0;\n border-top-color: #000;\n}\n.tooltip.right .tooltip-arrow {\n top: 50%;\n left: 0;\n margin-top: -5px;\n border-width: 5px 5px 5px 0;\n border-right-color: #000;\n}\n.tooltip.left .tooltip-arrow {\n top: 50%;\n right: 0;\n margin-top: -5px;\n border-width: 5px 0 5px 5px;\n border-left-color: #000;\n}\n.tooltip.bottom .tooltip-arrow {\n top: 0;\n left: 50%;\n margin-left: -5px;\n border-width: 0 5px 5px;\n border-bottom-color: #000;\n}\n.tooltip.bottom-left .tooltip-arrow {\n top: 0;\n right: 5px;\n margin-top: -5px;\n border-width: 0 5px 5px;\n border-bottom-color: #000;\n}\n.tooltip.bottom-right .tooltip-arrow {\n top: 0;\n left: 5px;\n margin-top: -5px;\n border-width: 0 5px 5px;\n border-bottom-color: #000;\n}\n.popover {\n position: absolute;\n top: 0;\n left: 0;\n z-index: 1060;\n display: none;\n max-width: 276px;\n padding: 1px;\n font-family: \"Helvetica Neue\", Helvetica, Arial, sans-serif;\n font-size: 14px;\n font-style: normal;\n font-weight: normal;\n line-height: 1.42857143;\n text-align: left;\n text-align: start;\n text-decoration: none;\n text-shadow: none;\n text-transform: none;\n letter-spacing: normal;\n word-break: normal;\n word-spacing: normal;\n word-wrap: normal;\n white-space: normal;\n background-color: #fff;\n -webkit-background-clip: padding-box;\n background-clip: padding-box;\n border: 1px solid #ccc;\n border: 1px solid rgba(0, 0, 0, .2);\n border-radius: 6px;\n -webkit-box-shadow: 0 5px 10px rgba(0, 0, 0, .2);\n box-shadow: 0 5px 10px rgba(0, 0, 0, .2);\n\n line-break: auto;\n}\n.popover.top {\n margin-top: -10px;\n}\n.popover.right {\n margin-left: 10px;\n}\n.popover.bottom {\n margin-top: 10px;\n}\n.popover.left {\n margin-left: -10px;\n}\n.popover-title {\n padding: 8px 14px;\n margin: 0;\n font-size: 14px;\n background-color: #f7f7f7;\n border-bottom: 1px solid #ebebeb;\n border-radius: 5px 5px 0 0;\n}\n.popover-content {\n padding: 9px 14px;\n}\n.popover > .arrow,\n.popover > .arrow:after {\n position: absolute;\n display: block;\n width: 0;\n height: 0;\n border-color: transparent;\n border-style: solid;\n}\n.popover > .arrow {\n border-width: 11px;\n}\n.popover > .arrow:after {\n content: \"\";\n border-width: 10px;\n}\n.popover.top > .arrow {\n bottom: -11px;\n left: 50%;\n margin-left: -11px;\n border-top-color: #999;\n border-top-color: rgba(0, 0, 0, .25);\n border-bottom-width: 0;\n}\n.popover.top > .arrow:after {\n bottom: 1px;\n margin-left: -10px;\n content: \" \";\n border-top-color: #fff;\n border-bottom-width: 0;\n}\n.popover.right > .arrow {\n top: 50%;\n left: -11px;\n margin-top: -11px;\n border-right-color: #999;\n border-right-color: rgba(0, 0, 0, .25);\n border-left-width: 0;\n}\n.popover.right > .arrow:after {\n bottom: -10px;\n left: 1px;\n content: \" \";\n border-right-color: #fff;\n border-left-width: 0;\n}\n.popover.bottom > .arrow {\n top: -11px;\n left: 50%;\n margin-left: -11px;\n border-top-width: 0;\n border-bottom-color: #999;\n border-bottom-color: rgba(0, 0, 0, .25);\n}\n.popover.bottom > .arrow:after {\n top: 1px;\n margin-left: -10px;\n content: \" \";\n border-top-width: 0;\n border-bottom-color: #fff;\n}\n.popover.left > .arrow {\n top: 50%;\n right: -11px;\n margin-top: -11px;\n border-right-width: 0;\n border-left-color: #999;\n border-left-color: rgba(0, 0, 0, .25);\n}\n.popover.left > .arrow:after {\n right: 1px;\n bottom: -10px;\n content: \" \";\n border-right-width: 0;\n border-left-color: #fff;\n}\n.carousel {\n position: relative;\n}\n.carousel-inner {\n position: relative;\n width: 100%;\n overflow: hidden;\n}\n.carousel-inner > .item {\n position: relative;\n display: none;\n -webkit-transition: .6s ease-in-out left;\n -o-transition: .6s ease-in-out left;\n transition: .6s ease-in-out left;\n}\n.carousel-inner > .item > img,\n.carousel-inner > .item > a > img {\n line-height: 1;\n}\n@media all and (transform-3d), (-webkit-transform-3d) {\n .carousel-inner > .item {\n -webkit-transition: -webkit-transform .6s ease-in-out;\n -o-transition: -o-transform .6s ease-in-out;\n transition: transform .6s ease-in-out;\n\n -webkit-backface-visibility: hidden;\n backface-visibility: hidden;\n -webkit-perspective: 1000px;\n perspective: 1000px;\n }\n .carousel-inner > .item.next,\n .carousel-inner > .item.active.right {\n left: 0;\n -webkit-transform: translate3d(100%, 0, 0);\n transform: translate3d(100%, 0, 0);\n }\n .carousel-inner > .item.prev,\n .carousel-inner > .item.active.left {\n left: 0;\n -webkit-transform: translate3d(-100%, 0, 0);\n transform: translate3d(-100%, 0, 0);\n }\n .carousel-inner > .item.next.left,\n .carousel-inner > .item.prev.right,\n .carousel-inner > .item.active {\n left: 0;\n -webkit-transform: translate3d(0, 0, 0);\n transform: translate3d(0, 0, 0);\n }\n}\n.carousel-inner > .active,\n.carousel-inner > .next,\n.carousel-inner > .prev {\n display: block;\n}\n.carousel-inner > .active {\n left: 0;\n}\n.carousel-inner > .next,\n.carousel-inner > .prev {\n position: absolute;\n top: 0;\n width: 100%;\n}\n.carousel-inner > .next {\n left: 100%;\n}\n.carousel-inner > .prev {\n left: -100%;\n}\n.carousel-inner > .next.left,\n.carousel-inner > .prev.right {\n left: 0;\n}\n.carousel-inner > .active.left {\n left: -100%;\n}\n.carousel-inner > .active.right {\n left: 100%;\n}\n.carousel-control {\n position: absolute;\n top: 0;\n bottom: 0;\n left: 0;\n width: 15%;\n font-size: 20px;\n color: #fff;\n text-align: center;\n text-shadow: 0 1px 2px rgba(0, 0, 0, .6);\n background-color: rgba(0, 0, 0, 0);\n filter: alpha(opacity=50);\n opacity: .5;\n}\n.carousel-control.left {\n background-image: -webkit-linear-gradient(left, rgba(0, 0, 0, .5) 0%, rgba(0, 0, 0, .0001) 100%);\n background-image: -o-linear-gradient(left, rgba(0, 0, 0, .5) 0%, rgba(0, 0, 0, .0001) 100%);\n background-image: -webkit-gradient(linear, left top, right top, from(rgba(0, 0, 0, .5)), to(rgba(0, 0, 0, .0001)));\n background-image: linear-gradient(to right, rgba(0, 0, 0, .5) 0%, rgba(0, 0, 0, .0001) 100%);\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#80000000', endColorstr='#00000000', GradientType=1);\n background-repeat: repeat-x;\n}\n.carousel-control.right {\n right: 0;\n left: auto;\n background-image: -webkit-linear-gradient(left, rgba(0, 0, 0, .0001) 0%, rgba(0, 0, 0, .5) 100%);\n background-image: -o-linear-gradient(left, rgba(0, 0, 0, .0001) 0%, rgba(0, 0, 0, .5) 100%);\n background-image: -webkit-gradient(linear, left top, right top, from(rgba(0, 0, 0, .0001)), to(rgba(0, 0, 0, .5)));\n background-image: linear-gradient(to right, rgba(0, 0, 0, .0001) 0%, rgba(0, 0, 0, .5) 100%);\n filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#00000000', endColorstr='#80000000', GradientType=1);\n background-repeat: repeat-x;\n}\n.carousel-control:hover,\n.carousel-control:focus {\n color: #fff;\n text-decoration: none;\n filter: alpha(opacity=90);\n outline: 0;\n opacity: .9;\n}\n.carousel-control .icon-prev,\n.carousel-control .icon-next,\n.carousel-control .glyphicon-chevron-left,\n.carousel-control .glyphicon-chevron-right {\n position: absolute;\n top: 50%;\n z-index: 5;\n display: inline-block;\n margin-top: -10px;\n}\n.carousel-control .icon-prev,\n.carousel-control .glyphicon-chevron-left {\n left: 50%;\n margin-left: -10px;\n}\n.carousel-control .icon-next,\n.carousel-control .glyphicon-chevron-right {\n right: 50%;\n margin-right: -10px;\n}\n.carousel-control .icon-prev,\n.carousel-control .icon-next {\n width: 20px;\n height: 20px;\n font-family: serif;\n line-height: 1;\n}\n.carousel-control .icon-prev:before {\n content: '\\2039';\n}\n.carousel-control .icon-next:before {\n content: '\\203a';\n}\n.carousel-indicators {\n position: absolute;\n bottom: 10px;\n left: 50%;\n z-index: 15;\n width: 60%;\n padding-left: 0;\n margin-left: -30%;\n text-align: center;\n list-style: none;\n}\n.carousel-indicators li {\n display: inline-block;\n width: 10px;\n height: 10px;\n margin: 1px;\n text-indent: -999px;\n cursor: pointer;\n background-color: #000 \\9;\n background-color: rgba(0, 0, 0, 0);\n border: 1px solid #fff;\n border-radius: 10px;\n}\n.carousel-indicators .active {\n width: 12px;\n height: 12px;\n margin: 0;\n background-color: #fff;\n}\n.carousel-caption {\n position: absolute;\n right: 15%;\n bottom: 20px;\n left: 15%;\n z-index: 10;\n padding-top: 20px;\n padding-bottom: 20px;\n color: #fff;\n text-align: center;\n text-shadow: 0 1px 2px rgba(0, 0, 0, .6);\n}\n.carousel-caption .btn {\n text-shadow: none;\n}\n@media screen and (min-width: 768px) {\n .carousel-control .glyphicon-chevron-left,\n .carousel-control .glyphicon-chevron-right,\n .carousel-control .icon-prev,\n .carousel-control .icon-next {\n width: 30px;\n height: 30px;\n margin-top: -10px;\n font-size: 30px;\n }\n .carousel-control .glyphicon-chevron-left,\n .carousel-control .icon-prev {\n margin-left: -10px;\n }\n .carousel-control .glyphicon-chevron-right,\n .carousel-control .icon-next {\n margin-right: -10px;\n }\n .carousel-caption {\n right: 20%;\n left: 20%;\n padding-bottom: 30px;\n }\n .carousel-indicators {\n bottom: 20px;\n }\n}\n.clearfix:before,\n.clearfix:after,\n.dl-horizontal dd:before,\n.dl-horizontal dd:after,\n.container:before,\n.container:after,\n.container-fluid:before,\n.container-fluid:after,\n.row:before,\n.row:after,\n.form-horizontal .form-group:before,\n.form-horizontal .form-group:after,\n.btn-toolbar:before,\n.btn-toolbar:after,\n.btn-group-vertical > .btn-group:before,\n.btn-group-vertical > .btn-group:after,\n.nav:before,\n.nav:after,\n.navbar:before,\n.navbar:after,\n.navbar-header:before,\n.navbar-header:after,\n.navbar-collapse:before,\n.navbar-collapse:after,\n.pager:before,\n.pager:after,\n.panel-body:before,\n.panel-body:after,\n.modal-header:before,\n.modal-header:after,\n.modal-footer:before,\n.modal-footer:after {\n display: table;\n content: \" \";\n}\n.clearfix:after,\n.dl-horizontal dd:after,\n.container:after,\n.container-fluid:after,\n.row:after,\n.form-horizontal .form-group:after,\n.btn-toolbar:after,\n.btn-group-vertical > .btn-group:after,\n.nav:after,\n.navbar:after,\n.navbar-header:after,\n.navbar-collapse:after,\n.pager:after,\n.panel-body:after,\n.modal-header:after,\n.modal-footer:after {\n clear: both;\n}\n.center-block {\n display: block;\n margin-right: auto;\n margin-left: auto;\n}\n.pull-right {\n float: right !important;\n}\n.pull-left {\n float: left !important;\n}\n.hide {\n display: none !important;\n}\n.show {\n display: block !important;\n}\n.invisible {\n visibility: hidden;\n}\n.text-hide {\n font: 0/0 a;\n color: transparent;\n text-shadow: none;\n background-color: transparent;\n border: 0;\n}\n.hidden {\n display: none !important;\n}\n.affix {\n position: fixed;\n}\n@-ms-viewport {\n width: device-width;\n}\n.visible-xs,\n.visible-sm,\n.visible-md,\n.visible-lg {\n display: none !important;\n}\n.visible-xs-block,\n.visible-xs-inline,\n.visible-xs-inline-block,\n.visible-sm-block,\n.visible-sm-inline,\n.visible-sm-inline-block,\n.visible-md-block,\n.visible-md-inline,\n.visible-md-inline-block,\n.visible-lg-block,\n.visible-lg-inline,\n.visible-lg-inline-block {\n display: none !important;\n}\n@media (max-width: 767px) {\n .visible-xs {\n display: block !important;\n }\n table.visible-xs {\n display: table !important;\n }\n tr.visible-xs {\n display: table-row !important;\n }\n th.visible-xs,\n td.visible-xs {\n display: table-cell !important;\n }\n}\n@media (max-width: 767px) {\n .visible-xs-block {\n display: block !important;\n }\n}\n@media (max-width: 767px) {\n .visible-xs-inline {\n display: inline !important;\n }\n}\n@media (max-width: 767px) {\n .visible-xs-inline-block {\n display: inline-block !important;\n }\n}\n@media (min-width: 768px) and (max-width: 991px) {\n .visible-sm {\n display: block !important;\n }\n table.visible-sm {\n display: table !important;\n }\n tr.visible-sm {\n display: table-row !important;\n }\n th.visible-sm,\n td.visible-sm {\n display: table-cell !important;\n }\n}\n@media (min-width: 768px) and (max-width: 991px) {\n .visible-sm-block {\n display: block !important;\n }\n}\n@media (min-width: 768px) and (max-width: 991px) {\n .visible-sm-inline {\n display: inline !important;\n }\n}\n@media (min-width: 768px) and (max-width: 991px) {\n .visible-sm-inline-block {\n display: inline-block !important;\n }\n}\n@media (min-width: 992px) and (max-width: 1199px) {\n .visible-md {\n display: block !important;\n }\n table.visible-md {\n display: table !important;\n }\n tr.visible-md {\n display: table-row !important;\n }\n th.visible-md,\n td.visible-md {\n display: table-cell !important;\n }\n}\n@media (min-width: 992px) and (max-width: 1199px) {\n .visible-md-block {\n display: block !important;\n }\n}\n@media (min-width: 992px) and (max-width: 1199px) {\n .visible-md-inline {\n display: inline !important;\n }\n}\n@media (min-width: 992px) and (max-width: 1199px) {\n .visible-md-inline-block {\n display: inline-block !important;\n }\n}\n@media (min-width: 1200px) {\n .visible-lg {\n display: block !important;\n }\n table.visible-lg {\n display: table !important;\n }\n tr.visible-lg {\n display: table-row !important;\n }\n th.visible-lg,\n td.visible-lg {\n display: table-cell !important;\n }\n}\n@media (min-width: 1200px) {\n .visible-lg-block {\n display: block !important;\n }\n}\n@media (min-width: 1200px) {\n .visible-lg-inline {\n display: inline !important;\n }\n}\n@media (min-width: 1200px) {\n .visible-lg-inline-block {\n display: inline-block !important;\n }\n}\n@media (max-width: 767px) {\n .hidden-xs {\n display: none !important;\n }\n}\n@media (min-width: 768px) and (max-width: 991px) {\n .hidden-sm {\n display: none !important;\n }\n}\n@media (min-width: 992px) and (max-width: 1199px) {\n .hidden-md {\n display: none !important;\n }\n}\n@media (min-width: 1200px) {\n .hidden-lg {\n display: none !important;\n }\n}\n.visible-print {\n display: none !important;\n}\n@media print {\n .visible-print {\n display: block !important;\n }\n table.visible-print {\n display: table !important;\n }\n tr.visible-print {\n display: table-row !important;\n }\n th.visible-print,\n td.visible-print {\n display: table-cell !important;\n }\n}\n.visible-print-block {\n display: none !important;\n}\n@media print {\n .visible-print-block {\n display: block !important;\n }\n}\n.visible-print-inline {\n display: none !important;\n}\n@media print {\n .visible-print-inline {\n display: inline !important;\n }\n}\n.visible-print-inline-block {\n display: none !important;\n}\n@media print {\n .visible-print-inline-block {\n display: inline-block !important;\n }\n}\n@media print {\n .hidden-print {\n display: none !important;\n }\n}\n/*# sourceMappingURL=bootstrap.css.map */\n","//\n// Glyphicons for Bootstrap\n//\n// Since icons are fonts, they can be placed anywhere text is placed and are\n// thus automatically sized to match the surrounding child. To use, create an\n// inline element with the appropriate classes, like so:\n//\n// <a href=\"#\"><span class=\"glyphicon glyphicon-star\"></span> Star</a>\n\n// Import the fonts\n@font-face {\n font-family: 'Glyphicons Halflings';\n src: url('@{icon-font-path}@{icon-font-name}.eot');\n src: url('@{icon-font-path}@{icon-font-name}.eot?#iefix') format('embedded-opentype'),\n url('@{icon-font-path}@{icon-font-name}.woff2') format('woff2'),\n url('@{icon-font-path}@{icon-font-name}.woff') format('woff'),\n url('@{icon-font-path}@{icon-font-name}.ttf') format('truetype'),\n url('@{icon-font-path}@{icon-font-name}.svg#@{icon-font-svg-id}') format('svg');\n}\n\n// Catchall baseclass\n.glyphicon {\n position: relative;\n top: 1px;\n display: inline-block;\n font-family: 'Glyphicons Halflings';\n font-style: normal;\n font-weight: normal;\n line-height: 1;\n -webkit-font-smoothing: antialiased;\n -moz-osx-font-smoothing: grayscale;\n}\n\n// Individual icons\n.glyphicon-asterisk { &:before { content: \"\\002a\"; } }\n.glyphicon-plus { &:before { content: \"\\002b\"; } }\n.glyphicon-euro,\n.glyphicon-eur { &:before { content: \"\\20ac\"; } }\n.glyphicon-minus { &:before { content: \"\\2212\"; } }\n.glyphicon-cloud { &:before { content: \"\\2601\"; } }\n.glyphicon-envelope { &:before { content: \"\\2709\"; } }\n.glyphicon-pencil { &:before { content: \"\\270f\"; } }\n.glyphicon-glass { &:before { content: \"\\e001\"; } }\n.glyphicon-music { &:before { content: \"\\e002\"; } }\n.glyphicon-search { &:before { content: \"\\e003\"; } }\n.glyphicon-heart { &:before { content: \"\\e005\"; } }\n.glyphicon-star { &:before { content: \"\\e006\"; } }\n.glyphicon-star-empty { &:before { content: \"\\e007\"; } }\n.glyphicon-user { &:before { content: \"\\e008\"; } }\n.glyphicon-film { &:before { content: \"\\e009\"; } }\n.glyphicon-th-large { &:before { content: \"\\e010\"; } }\n.glyphicon-th { &:before { content: \"\\e011\"; } }\n.glyphicon-th-list { &:before { content: \"\\e012\"; } }\n.glyphicon-ok { &:before { content: \"\\e013\"; } }\n.glyphicon-remove { &:before { content: \"\\e014\"; } }\n.glyphicon-zoom-in { &:before { content: \"\\e015\"; } }\n.glyphicon-zoom-out { &:before { content: \"\\e016\"; } }\n.glyphicon-off { &:before { content: \"\\e017\"; } }\n.glyphicon-signal { &:before { content: \"\\e018\"; } }\n.glyphicon-cog { &:before { content: \"\\e019\"; } }\n.glyphicon-trash { &:before { content: \"\\e020\"; } }\n.glyphicon-home { &:before { content: \"\\e021\"; } }\n.glyphicon-file { &:before { content: \"\\e022\"; } }\n.glyphicon-time { &:before { content: \"\\e023\"; } }\n.glyphicon-road { &:before { content: \"\\e024\"; } }\n.glyphicon-download-alt { &:before { content: \"\\e025\"; } }\n.glyphicon-download { &:before { content: \"\\e026\"; } }\n.glyphicon-upload { &:before { content: \"\\e027\"; } }\n.glyphicon-inbox { &:before { content: \"\\e028\"; } }\n.glyphicon-play-circle { &:before { content: \"\\e029\"; } }\n.glyphicon-repeat { &:before { content: \"\\e030\"; } }\n.glyphicon-refresh { &:before { content: \"\\e031\"; } }\n.glyphicon-list-alt { &:before { content: \"\\e032\"; } }\n.glyphicon-lock { &:before { content: \"\\e033\"; } }\n.glyphicon-flag { &:before { content: \"\\e034\"; } }\n.glyphicon-headphones { &:before { content: \"\\e035\"; } }\n.glyphicon-volume-off { &:before { content: \"\\e036\"; } }\n.glyphicon-volume-down { &:before { content: \"\\e037\"; } }\n.glyphicon-volume-up { &:before { content: \"\\e038\"; } }\n.glyphicon-qrcode { &:before { content: \"\\e039\"; } }\n.glyphicon-barcode { &:before { content: \"\\e040\"; } }\n.glyphicon-tag { &:before { content: \"\\e041\"; } }\n.glyphicon-tags { &:before { content: \"\\e042\"; } }\n.glyphicon-book { &:before { content: \"\\e043\"; } }\n.glyphicon-bookmark { &:before { content: \"\\e044\"; } }\n.glyphicon-print { &:before { content: \"\\e045\"; } }\n.glyphicon-camera { &:before { content: \"\\e046\"; } }\n.glyphicon-font { &:before { content: \"\\e047\"; } }\n.glyphicon-bold { &:before { content: \"\\e048\"; } }\n.glyphicon-italic { &:before { content: \"\\e049\"; } }\n.glyphicon-text-height { &:before { content: \"\\e050\"; } }\n.glyphicon-text-width { &:before { content: \"\\e051\"; } }\n.glyphicon-align-left { &:before { content: \"\\e052\"; } }\n.glyphicon-align-center { &:before { content: \"\\e053\"; } }\n.glyphicon-align-right { &:before { content: \"\\e054\"; } }\n.glyphicon-align-justify { &:before { content: \"\\e055\"; } }\n.glyphicon-list { &:before { content: \"\\e056\"; } }\n.glyphicon-indent-left { &:before { content: \"\\e057\"; } }\n.glyphicon-indent-right { &:before { content: \"\\e058\"; } }\n.glyphicon-facetime-video { &:before { content: \"\\e059\"; } }\n.glyphicon-picture { &:before { content: \"\\e060\"; } }\n.glyphicon-map-marker { &:before { content: \"\\e062\"; } }\n.glyphicon-adjust { &:before { content: \"\\e063\"; } }\n.glyphicon-tint { &:before { content: \"\\e064\"; } }\n.glyphicon-edit { &:before { content: \"\\e065\"; } }\n.glyphicon-share { &:before { content: \"\\e066\"; } }\n.glyphicon-check { &:before { content: \"\\e067\"; } }\n.glyphicon-move { &:before { content: \"\\e068\"; } }\n.glyphicon-step-backward { &:before { content: \"\\e069\"; } }\n.glyphicon-fast-backward { &:before { content: \"\\e070\"; } }\n.glyphicon-backward { &:before { content: \"\\e071\"; } }\n.glyphicon-play { &:before { content: \"\\e072\"; } }\n.glyphicon-pause { &:before { content: \"\\e073\"; } }\n.glyphicon-stop { &:before { content: \"\\e074\"; } }\n.glyphicon-forward { &:before { content: \"\\e075\"; } }\n.glyphicon-fast-forward { &:before { content: \"\\e076\"; } }\n.glyphicon-step-forward { &:before { content: \"\\e077\"; } }\n.glyphicon-eject { &:before { content: \"\\e078\"; } }\n.glyphicon-chevron-left { &:before { content: \"\\e079\"; } }\n.glyphicon-chevron-right { &:before { content: \"\\e080\"; } }\n.glyphicon-plus-sign { &:before { content: \"\\e081\"; } }\n.glyphicon-minus-sign { &:before { content: \"\\e082\"; } }\n.glyphicon-remove-sign { &:before { content: \"\\e083\"; } }\n.glyphicon-ok-sign { &:before { content: \"\\e084\"; } }\n.glyphicon-question-sign { &:before { content: \"\\e085\"; } }\n.glyphicon-info-sign { &:before { content: \"\\e086\"; } }\n.glyphicon-screenshot { &:before { content: \"\\e087\"; } }\n.glyphicon-remove-circle { &:before { content: \"\\e088\"; } }\n.glyphicon-ok-circle { &:before { content: \"\\e089\"; } }\n.glyphicon-ban-circle { &:before { content: \"\\e090\"; } }\n.glyphicon-arrow-left { &:before { content: \"\\e091\"; } }\n.glyphicon-arrow-right { &:before { content: \"\\e092\"; } }\n.glyphicon-arrow-up { &:before { content: \"\\e093\"; } }\n.glyphicon-arrow-down { &:before { content: \"\\e094\"; } }\n.glyphicon-share-alt { &:before { content: \"\\e095\"; } }\n.glyphicon-resize-full { &:before { content: \"\\e096\"; } }\n.glyphicon-resize-small { &:before { content: \"\\e097\"; } }\n.glyphicon-exclamation-sign { &:before { content: \"\\e101\"; } }\n.glyphicon-gift { &:before { content: \"\\e102\"; } }\n.glyphicon-leaf { &:before { content: \"\\e103\"; } }\n.glyphicon-fire { &:before { content: \"\\e104\"; } }\n.glyphicon-eye-open { &:before { content: \"\\e105\"; } }\n.glyphicon-eye-close { &:before { content: \"\\e106\"; } }\n.glyphicon-warning-sign { &:before { content: \"\\e107\"; } }\n.glyphicon-plane { &:before { content: \"\\e108\"; } }\n.glyphicon-calendar { &:before { content: \"\\e109\"; } }\n.glyphicon-random { &:before { content: \"\\e110\"; } }\n.glyphicon-comment { &:before { content: \"\\e111\"; } }\n.glyphicon-magnet { &:before { content: \"\\e112\"; } }\n.glyphicon-chevron-up { &:before { content: \"\\e113\"; } }\n.glyphicon-chevron-down { &:before { content: \"\\e114\"; } }\n.glyphicon-retweet { &:before { content: \"\\e115\"; } }\n.glyphicon-shopping-cart { &:before { content: \"\\e116\"; } }\n.glyphicon-folder-close { &:before { content: \"\\e117\"; } }\n.glyphicon-folder-open { &:before { content: \"\\e118\"; } }\n.glyphicon-resize-vertical { &:before { content: \"\\e119\"; } }\n.glyphicon-resize-horizontal { &:before { content: \"\\e120\"; } }\n.glyphicon-hdd { &:before { content: \"\\e121\"; } }\n.glyphicon-bullhorn { &:before { content: \"\\e122\"; } }\n.glyphicon-bell { &:before { content: \"\\e123\"; } }\n.glyphicon-certificate { &:before { content: \"\\e124\"; } }\n.glyphicon-thumbs-up { &:before { content: \"\\e125\"; } }\n.glyphicon-thumbs-down { &:before { content: \"\\e126\"; } }\n.glyphicon-hand-right { &:before { content: \"\\e127\"; } }\n.glyphicon-hand-left { &:before { content: \"\\e128\"; } }\n.glyphicon-hand-up { &:before { content: \"\\e129\"; } }\n.glyphicon-hand-down { &:before { content: \"\\e130\"; } }\n.glyphicon-circle-arrow-right { &:before { content: \"\\e131\"; } }\n.glyphicon-circle-arrow-left { &:before { content: \"\\e132\"; } }\n.glyphicon-circle-arrow-up { &:before { content: \"\\e133\"; } }\n.glyphicon-circle-arrow-down { &:before { content: \"\\e134\"; } }\n.glyphicon-globe { &:before { content: \"\\e135\"; } }\n.glyphicon-wrench { &:before { content: \"\\e136\"; } }\n.glyphicon-tasks { &:before { content: \"\\e137\"; } }\n.glyphicon-filter { &:before { content: \"\\e138\"; } }\n.glyphicon-briefcase { &:before { content: \"\\e139\"; } }\n.glyphicon-fullscreen { &:before { content: \"\\e140\"; } }\n.glyphicon-dashboard { &:before { content: \"\\e141\"; } }\n.glyphicon-paperclip { &:before { content: \"\\e142\"; } }\n.glyphicon-heart-empty { &:before { content: \"\\e143\"; } }\n.glyphicon-link { &:before { content: \"\\e144\"; } }\n.glyphicon-phone { &:before { content: \"\\e145\"; } }\n.glyphicon-pushpin { &:before { content: \"\\e146\"; } }\n.glyphicon-usd { &:before { content: \"\\e148\"; } }\n.glyphicon-gbp { &:before { content: \"\\e149\"; } }\n.glyphicon-sort { &:before { content: \"\\e150\"; } }\n.glyphicon-sort-by-alphabet { &:before { content: \"\\e151\"; } }\n.glyphicon-sort-by-alphabet-alt { &:before { content: \"\\e152\"; } }\n.glyphicon-sort-by-order { &:before { content: \"\\e153\"; } }\n.glyphicon-sort-by-order-alt { &:before { content: \"\\e154\"; } }\n.glyphicon-sort-by-attributes { &:before { content: \"\\e155\"; } }\n.glyphicon-sort-by-attributes-alt { &:before { content: \"\\e156\"; } }\n.glyphicon-unchecked { &:before { content: \"\\e157\"; } }\n.glyphicon-expand { &:before { content: \"\\e158\"; } }\n.glyphicon-collapse-down { &:before { content: \"\\e159\"; } }\n.glyphicon-collapse-up { &:before { content: \"\\e160\"; } }\n.glyphicon-log-in { &:before { content: \"\\e161\"; } }\n.glyphicon-flash { &:before { content: \"\\e162\"; } }\n.glyphicon-log-out { &:before { content: \"\\e163\"; } }\n.glyphicon-new-window { &:before { content: \"\\e164\"; } }\n.glyphicon-record { &:before { content: \"\\e165\"; } }\n.glyphicon-save { &:before { content: \"\\e166\"; } }\n.glyphicon-open { &:before { content: \"\\e167\"; } }\n.glyphicon-saved { &:before { content: \"\\e168\"; } }\n.glyphicon-import { &:before { content: \"\\e169\"; } }\n.glyphicon-export { &:before { content: \"\\e170\"; } }\n.glyphicon-send { &:before { content: \"\\e171\"; } }\n.glyphicon-floppy-disk { &:before { content: \"\\e172\"; } }\n.glyphicon-floppy-saved { &:before { content: \"\\e173\"; } }\n.glyphicon-floppy-remove { &:before { content: \"\\e174\"; } }\n.glyphicon-floppy-save { &:before { content: \"\\e175\"; } }\n.glyphicon-floppy-open { &:before { content: \"\\e176\"; } }\n.glyphicon-credit-card { &:before { content: \"\\e177\"; } }\n.glyphicon-transfer { &:before { content: \"\\e178\"; } }\n.glyphicon-cutlery { &:before { content: \"\\e179\"; } }\n.glyphicon-header { &:before { content: \"\\e180\"; } }\n.glyphicon-compressed { &:before { content: \"\\e181\"; } }\n.glyphicon-earphone { &:before { content: \"\\e182\"; } }\n.glyphicon-phone-alt { &:before { content: \"\\e183\"; } }\n.glyphicon-tower { &:before { content: \"\\e184\"; } }\n.glyphicon-stats { &:before { content: \"\\e185\"; } }\n.glyphicon-sd-video { &:before { content: \"\\e186\"; } }\n.glyphicon-hd-video { &:before { content: \"\\e187\"; } }\n.glyphicon-subtitles { &:before { content: \"\\e188\"; } }\n.glyphicon-sound-stereo { &:before { content: \"\\e189\"; } }\n.glyphicon-sound-dolby { &:before { content: \"\\e190\"; } }\n.glyphicon-sound-5-1 { &:before { content: \"\\e191\"; } }\n.glyphicon-sound-6-1 { &:before { content: \"\\e192\"; } }\n.glyphicon-sound-7-1 { &:before { content: \"\\e193\"; } }\n.glyphicon-copyright-mark { &:before { content: \"\\e194\"; } }\n.glyphicon-registration-mark { &:before { content: \"\\e195\"; } }\n.glyphicon-cloud-download { &:before { content: \"\\e197\"; } }\n.glyphicon-cloud-upload { &:before { content: \"\\e198\"; } }\n.glyphicon-tree-conifer { &:before { content: \"\\e199\"; } }\n.glyphicon-tree-deciduous { &:before { content: \"\\e200\"; } }\n.glyphicon-cd { &:before { content: \"\\e201\"; } }\n.glyphicon-save-file { &:before { content: \"\\e202\"; } }\n.glyphicon-open-file { &:before { content: \"\\e203\"; } }\n.glyphicon-level-up { &:before { content: \"\\e204\"; } }\n.glyphicon-copy { &:before { content: \"\\e205\"; } }\n.glyphicon-paste { &:before { content: \"\\e206\"; } }\n// The following 2 Glyphicons are omitted for the time being because\n// they currently use Unicode codepoints that are outside the\n// Basic Multilingual Plane (BMP). Older buggy versions of WebKit can't handle\n// non-BMP codepoints in CSS string escapes, and thus can't display these two icons.\n// Notably, the bug affects some older versions of the Android Browser.\n// More info: https://github.com/twbs/bootstrap/issues/10106\n// .glyphicon-door { &:before { content: \"\\1f6aa\"; } }\n// .glyphicon-key { &:before { content: \"\\1f511\"; } }\n.glyphicon-alert { &:before { content: \"\\e209\"; } }\n.glyphicon-equalizer { &:before { content: \"\\e210\"; } }\n.glyphicon-king { &:before { content: \"\\e211\"; } }\n.glyphicon-queen { &:before { content: \"\\e212\"; } }\n.glyphicon-pawn { &:before { content: \"\\e213\"; } }\n.glyphicon-bishop { &:before { content: \"\\e214\"; } }\n.glyphicon-knight { &:before { content: \"\\e215\"; } }\n.glyphicon-baby-formula { &:before { content: \"\\e216\"; } }\n.glyphicon-tent { &:before { content: \"\\26fa\"; } }\n.glyphicon-blackboard { &:before { content: \"\\e218\"; } }\n.glyphicon-bed { &:before { content: \"\\e219\"; } }\n.glyphicon-apple { &:before { content: \"\\f8ff\"; } }\n.glyphicon-erase { &:before { content: \"\\e221\"; } }\n.glyphicon-hourglass { &:before { content: \"\\231b\"; } }\n.glyphicon-lamp { &:before { content: \"\\e223\"; } }\n.glyphicon-duplicate { &:before { content: \"\\e224\"; } }\n.glyphicon-piggy-bank { &:before { content: \"\\e225\"; } }\n.glyphicon-scissors { &:before { content: \"\\e226\"; } }\n.glyphicon-bitcoin { &:before { content: \"\\e227\"; } }\n.glyphicon-btc { &:before { content: \"\\e227\"; } }\n.glyphicon-xbt { &:before { content: \"\\e227\"; } }\n.glyphicon-yen { &:before { content: \"\\00a5\"; } }\n.glyphicon-jpy { &:before { content: \"\\00a5\"; } }\n.glyphicon-ruble { &:before { content: \"\\20bd\"; } }\n.glyphicon-rub { &:before { content: \"\\20bd\"; } }\n.glyphicon-scale { &:before { content: \"\\e230\"; } }\n.glyphicon-ice-lolly { &:before { content: \"\\e231\"; } }\n.glyphicon-ice-lolly-tasted { &:before { content: \"\\e232\"; } }\n.glyphicon-education { &:before { content: \"\\e233\"; } }\n.glyphicon-option-horizontal { &:before { content: \"\\e234\"; } }\n.glyphicon-option-vertical { &:before { content: \"\\e235\"; } }\n.glyphicon-menu-hamburger { &:before { content: \"\\e236\"; } }\n.glyphicon-modal-window { &:before { content: \"\\e237\"; } }\n.glyphicon-oil { &:before { content: \"\\e238\"; } }\n.glyphicon-grain { &:before { content: \"\\e239\"; } }\n.glyphicon-sunglasses { &:before { content: \"\\e240\"; } }\n.glyphicon-text-size { &:before { content: \"\\e241\"; } }\n.glyphicon-text-color { &:before { content: \"\\e242\"; } }\n.glyphicon-text-background { &:before { content: \"\\e243\"; } }\n.glyphicon-object-align-top { &:before { content: \"\\e244\"; } }\n.glyphicon-object-align-bottom { &:before { content: \"\\e245\"; } }\n.glyphicon-object-align-horizontal{ &:before { content: \"\\e246\"; } }\n.glyphicon-object-align-left { &:before { content: \"\\e247\"; } }\n.glyphicon-object-align-vertical { &:before { content: \"\\e248\"; } }\n.glyphicon-object-align-right { &:before { content: \"\\e249\"; } }\n.glyphicon-triangle-right { &:before { content: \"\\e250\"; } }\n.glyphicon-triangle-left { &:before { content: \"\\e251\"; } }\n.glyphicon-triangle-bottom { &:before { content: \"\\e252\"; } }\n.glyphicon-triangle-top { &:before { content: \"\\e253\"; } }\n.glyphicon-console { &:before { content: \"\\e254\"; } }\n.glyphicon-superscript { &:before { content: \"\\e255\"; } }\n.glyphicon-subscript { &:before { content: \"\\e256\"; } }\n.glyphicon-menu-left { &:before { content: \"\\e257\"; } }\n.glyphicon-menu-right { &:before { content: \"\\e258\"; } }\n.glyphicon-menu-down { &:before { content: \"\\e259\"; } }\n.glyphicon-menu-up { &:before { content: \"\\e260\"; } }\n","//\n// Scaffolding\n// --------------------------------------------------\n\n\n// Reset the box-sizing\n//\n// Heads up! This reset may cause conflicts with some third-party widgets.\n// For recommendations on resolving such conflicts, see\n// http://getbootstrap.com/getting-started/#third-box-sizing\n* {\n .box-sizing(border-box);\n}\n*:before,\n*:after {\n .box-sizing(border-box);\n}\n\n\n// Body reset\n\nhtml {\n font-size: 10px;\n -webkit-tap-highlight-color: rgba(0,0,0,0);\n}\n\nbody {\n font-family: @font-family-base;\n font-size: @font-size-base;\n line-height: @line-height-base;\n color: @text-color;\n background-color: @body-bg;\n}\n\n// Reset fonts for relevant elements\ninput,\nbutton,\nselect,\ntextarea {\n font-family: inherit;\n font-size: inherit;\n line-height: inherit;\n}\n\n\n// Links\n\na {\n color: @link-color;\n text-decoration: none;\n\n &:hover,\n &:focus {\n color: @link-hover-color;\n text-decoration: @link-hover-decoration;\n }\n\n &:focus {\n .tab-focus();\n }\n}\n\n\n// Figures\n//\n// We reset this here because previously Normalize had no `figure` margins. This\n// ensures we don't break anyone's use of the element.\n\nfigure {\n margin: 0;\n}\n\n\n// Images\n\nimg {\n vertical-align: middle;\n}\n\n// Responsive images (ensure images don't scale beyond their parents)\n.img-responsive {\n .img-responsive();\n}\n\n// Rounded corners\n.img-rounded {\n border-radius: @border-radius-large;\n}\n\n// Image thumbnails\n//\n// Heads up! This is mixin-ed into thumbnails.less for `.thumbnail`.\n.img-thumbnail {\n padding: @thumbnail-padding;\n line-height: @line-height-base;\n background-color: @thumbnail-bg;\n border: 1px solid @thumbnail-border;\n border-radius: @thumbnail-border-radius;\n .transition(all .2s ease-in-out);\n\n // Keep them at most 100% wide\n .img-responsive(inline-block);\n}\n\n// Perfect circle\n.img-circle {\n border-radius: 50%; // set radius in percents\n}\n\n\n// Horizontal rules\n\nhr {\n margin-top: @line-height-computed;\n margin-bottom: @line-height-computed;\n border: 0;\n border-top: 1px solid @hr-border;\n}\n\n\n// Only display content to screen readers\n//\n// See: http://a11yproject.com/posts/how-to-hide-content\n\n.sr-only {\n position: absolute;\n width: 1px;\n height: 1px;\n margin: -1px;\n padding: 0;\n overflow: hidden;\n clip: rect(0,0,0,0);\n border: 0;\n}\n\n// Use in conjunction with .sr-only to only display content when it's focused.\n// Useful for \"Skip to main content\" links; see http://www.w3.org/TR/2013/NOTE-WCAG20-TECHS-20130905/G1\n// Credit: HTML5 Boilerplate\n\n.sr-only-focusable {\n &:active,\n &:focus {\n position: static;\n width: auto;\n height: auto;\n margin: 0;\n overflow: visible;\n clip: auto;\n }\n}\n\n\n// iOS \"clickable elements\" fix for role=\"button\"\n//\n// Fixes \"clickability\" issue (and more generally, the firing of events such as focus as well)\n// for traditionally non-focusable elements with role=\"button\"\n// see https://developer.mozilla.org/en-US/docs/Web/Events/click#Safari_Mobile\n\n[role=\"button\"] {\n cursor: pointer;\n}\n","// Vendor Prefixes\n//\n// All vendor mixins are deprecated as of v3.2.0 due to the introduction of\n// Autoprefixer in our Gruntfile. They have been removed in v4.\n\n// - Animations\n// - Backface visibility\n// - Box shadow\n// - Box sizing\n// - Content columns\n// - Hyphens\n// - Placeholder text\n// - Transformations\n// - Transitions\n// - User Select\n\n\n// Animations\n.animation(@animation) {\n -webkit-animation: @animation;\n -o-animation: @animation;\n animation: @animation;\n}\n.animation-name(@name) {\n -webkit-animation-name: @name;\n animation-name: @name;\n}\n.animation-duration(@duration) {\n -webkit-animation-duration: @duration;\n animation-duration: @duration;\n}\n.animation-timing-function(@timing-function) {\n -webkit-animation-timing-function: @timing-function;\n animation-timing-function: @timing-function;\n}\n.animation-delay(@delay) {\n -webkit-animation-delay: @delay;\n animation-delay: @delay;\n}\n.animation-iteration-count(@iteration-count) {\n -webkit-animation-iteration-count: @iteration-count;\n animation-iteration-count: @iteration-count;\n}\n.animation-direction(@direction) {\n -webkit-animation-direction: @direction;\n animation-direction: @direction;\n}\n.animation-fill-mode(@fill-mode) {\n -webkit-animation-fill-mode: @fill-mode;\n animation-fill-mode: @fill-mode;\n}\n\n// Backface visibility\n// Prevent browsers from flickering when using CSS 3D transforms.\n// Default value is `visible`, but can be changed to `hidden`\n\n.backface-visibility(@visibility) {\n -webkit-backface-visibility: @visibility;\n -moz-backface-visibility: @visibility;\n backface-visibility: @visibility;\n}\n\n// Drop shadows\n//\n// Note: Deprecated `.box-shadow()` as of v3.1.0 since all of Bootstrap's\n// supported browsers that have box shadow capabilities now support it.\n\n.box-shadow(@shadow) {\n -webkit-box-shadow: @shadow; // iOS <4.3 & Android <4.1\n box-shadow: @shadow;\n}\n\n// Box sizing\n.box-sizing(@boxmodel) {\n -webkit-box-sizing: @boxmodel;\n -moz-box-sizing: @boxmodel;\n box-sizing: @boxmodel;\n}\n\n// CSS3 Content Columns\n.content-columns(@column-count; @column-gap: @grid-gutter-width) {\n -webkit-column-count: @column-count;\n -moz-column-count: @column-count;\n column-count: @column-count;\n -webkit-column-gap: @column-gap;\n -moz-column-gap: @column-gap;\n column-gap: @column-gap;\n}\n\n// Optional hyphenation\n.hyphens(@mode: auto) {\n word-wrap: break-word;\n -webkit-hyphens: @mode;\n -moz-hyphens: @mode;\n -ms-hyphens: @mode; // IE10+\n -o-hyphens: @mode;\n hyphens: @mode;\n}\n\n// Placeholder text\n.placeholder(@color: @input-color-placeholder) {\n // Firefox\n &::-moz-placeholder {\n color: @color;\n opacity: 1; // Override Firefox's unusual default opacity; see https://github.com/twbs/bootstrap/pull/11526\n }\n &:-ms-input-placeholder { color: @color; } // Internet Explorer 10+\n &::-webkit-input-placeholder { color: @color; } // Safari and Chrome\n}\n\n// Transformations\n.scale(@ratio) {\n -webkit-transform: scale(@ratio);\n -ms-transform: scale(@ratio); // IE9 only\n -o-transform: scale(@ratio);\n transform: scale(@ratio);\n}\n.scale(@ratioX; @ratioY) {\n -webkit-transform: scale(@ratioX, @ratioY);\n -ms-transform: scale(@ratioX, @ratioY); // IE9 only\n -o-transform: scale(@ratioX, @ratioY);\n transform: scale(@ratioX, @ratioY);\n}\n.scaleX(@ratio) {\n -webkit-transform: scaleX(@ratio);\n -ms-transform: scaleX(@ratio); // IE9 only\n -o-transform: scaleX(@ratio);\n transform: scaleX(@ratio);\n}\n.scaleY(@ratio) {\n -webkit-transform: scaleY(@ratio);\n -ms-transform: scaleY(@ratio); // IE9 only\n -o-transform: scaleY(@ratio);\n transform: scaleY(@ratio);\n}\n.skew(@x; @y) {\n -webkit-transform: skewX(@x) skewY(@y);\n -ms-transform: skewX(@x) skewY(@y); // See https://github.com/twbs/bootstrap/issues/4885; IE9+\n -o-transform: skewX(@x) skewY(@y);\n transform: skewX(@x) skewY(@y);\n}\n.translate(@x; @y) {\n -webkit-transform: translate(@x, @y);\n -ms-transform: translate(@x, @y); // IE9 only\n -o-transform: translate(@x, @y);\n transform: translate(@x, @y);\n}\n.translate3d(@x; @y; @z) {\n -webkit-transform: translate3d(@x, @y, @z);\n transform: translate3d(@x, @y, @z);\n}\n.rotate(@degrees) {\n -webkit-transform: rotate(@degrees);\n -ms-transform: rotate(@degrees); // IE9 only\n -o-transform: rotate(@degrees);\n transform: rotate(@degrees);\n}\n.rotateX(@degrees) {\n -webkit-transform: rotateX(@degrees);\n -ms-transform: rotateX(@degrees); // IE9 only\n -o-transform: rotateX(@degrees);\n transform: rotateX(@degrees);\n}\n.rotateY(@degrees) {\n -webkit-transform: rotateY(@degrees);\n -ms-transform: rotateY(@degrees); // IE9 only\n -o-transform: rotateY(@degrees);\n transform: rotateY(@degrees);\n}\n.perspective(@perspective) {\n -webkit-perspective: @perspective;\n -moz-perspective: @perspective;\n perspective: @perspective;\n}\n.perspective-origin(@perspective) {\n -webkit-perspective-origin: @perspective;\n -moz-perspective-origin: @perspective;\n perspective-origin: @perspective;\n}\n.transform-origin(@origin) {\n -webkit-transform-origin: @origin;\n -moz-transform-origin: @origin;\n -ms-transform-origin: @origin; // IE9 only\n transform-origin: @origin;\n}\n\n\n// Transitions\n\n.transition(@transition) {\n -webkit-transition: @transition;\n -o-transition: @transition;\n transition: @transition;\n}\n.transition-property(@transition-property) {\n -webkit-transition-property: @transition-property;\n transition-property: @transition-property;\n}\n.transition-delay(@transition-delay) {\n -webkit-transition-delay: @transition-delay;\n transition-delay: @transition-delay;\n}\n.transition-duration(@transition-duration) {\n -webkit-transition-duration: @transition-duration;\n transition-duration: @transition-duration;\n}\n.transition-timing-function(@timing-function) {\n -webkit-transition-timing-function: @timing-function;\n transition-timing-function: @timing-function;\n}\n.transition-transform(@transition) {\n -webkit-transition: -webkit-transform @transition;\n -moz-transition: -moz-transform @transition;\n -o-transition: -o-transform @transition;\n transition: transform @transition;\n}\n\n\n// User select\n// For selecting text on the page\n\n.user-select(@select) {\n -webkit-user-select: @select;\n -moz-user-select: @select;\n -ms-user-select: @select; // IE10+\n user-select: @select;\n}\n","// WebKit-style focus\n\n.tab-focus() {\n // WebKit-specific. Other browsers will keep their default outline style.\n // (Initially tried to also force default via `outline: initial`,\n // but that seems to erroneously remove the outline in Firefox altogether.)\n outline: 5px auto -webkit-focus-ring-color;\n outline-offset: -2px;\n}\n","// Image Mixins\n// - Responsive image\n// - Retina image\n\n\n// Responsive image\n//\n// Keep images from scaling beyond the width of their parents.\n.img-responsive(@display: block) {\n display: @display;\n max-width: 100%; // Part 1: Set a maximum relative to the parent\n height: auto; // Part 2: Scale the height according to the width, otherwise you get stretching\n}\n\n\n// Retina image\n//\n// Short retina mixin for setting background-image and -size. Note that the\n// spelling of `min--moz-device-pixel-ratio` is intentional.\n.img-retina(@file-1x; @file-2x; @width-1x; @height-1x) {\n background-image: url(\"@{file-1x}\");\n\n @media\n only screen and (-webkit-min-device-pixel-ratio: 2),\n only screen and ( min--moz-device-pixel-ratio: 2),\n only screen and ( -o-min-device-pixel-ratio: 2/1),\n only screen and ( min-device-pixel-ratio: 2),\n only screen and ( min-resolution: 192dpi),\n only screen and ( min-resolution: 2dppx) {\n background-image: url(\"@{file-2x}\");\n background-size: @width-1x @height-1x;\n }\n}\n","//\n// Typography\n// --------------------------------------------------\n\n\n// Headings\n// -------------------------\n\nh1, h2, h3, h4, h5, h6,\n.h1, .h2, .h3, .h4, .h5, .h6 {\n font-family: @headings-font-family;\n font-weight: @headings-font-weight;\n line-height: @headings-line-height;\n color: @headings-color;\n\n small,\n .small {\n font-weight: normal;\n line-height: 1;\n color: @headings-small-color;\n }\n}\n\nh1, .h1,\nh2, .h2,\nh3, .h3 {\n margin-top: @line-height-computed;\n margin-bottom: (@line-height-computed / 2);\n\n small,\n .small {\n font-size: 65%;\n }\n}\nh4, .h4,\nh5, .h5,\nh6, .h6 {\n margin-top: (@line-height-computed / 2);\n margin-bottom: (@line-height-computed / 2);\n\n small,\n .small {\n font-size: 75%;\n }\n}\n\nh1, .h1 { font-size: @font-size-h1; }\nh2, .h2 { font-size: @font-size-h2; }\nh3, .h3 { font-size: @font-size-h3; }\nh4, .h4 { font-size: @font-size-h4; }\nh5, .h5 { font-size: @font-size-h5; }\nh6, .h6 { font-size: @font-size-h6; }\n\n\n// Body text\n// -------------------------\n\np {\n margin: 0 0 (@line-height-computed / 2);\n}\n\n.lead {\n margin-bottom: @line-height-computed;\n font-size: floor((@font-size-base * 1.15));\n font-weight: 300;\n line-height: 1.4;\n\n @media (min-width: @screen-sm-min) {\n font-size: (@font-size-base * 1.5);\n }\n}\n\n\n// Emphasis & misc\n// -------------------------\n\n// Ex: (12px small font / 14px base font) * 100% = about 85%\nsmall,\n.small {\n font-size: floor((100% * @font-size-small / @font-size-base));\n}\n\nmark,\n.mark {\n background-color: @state-warning-bg;\n padding: .2em;\n}\n\n// Alignment\n.text-left { text-align: left; }\n.text-right { text-align: right; }\n.text-center { text-align: center; }\n.text-justify { text-align: justify; }\n.text-nowrap { white-space: nowrap; }\n\n// Transformation\n.text-lowercase { text-transform: lowercase; }\n.text-uppercase { text-transform: uppercase; }\n.text-capitalize { text-transform: capitalize; }\n\n// Contextual colors\n.text-muted {\n color: @text-muted;\n}\n.text-primary {\n .text-emphasis-variant(@brand-primary);\n}\n.text-success {\n .text-emphasis-variant(@state-success-text);\n}\n.text-info {\n .text-emphasis-variant(@state-info-text);\n}\n.text-warning {\n .text-emphasis-variant(@state-warning-text);\n}\n.text-danger {\n .text-emphasis-variant(@state-danger-text);\n}\n\n// Contextual backgrounds\n// For now we'll leave these alongside the text classes until v4 when we can\n// safely shift things around (per SemVer rules).\n.bg-primary {\n // Given the contrast here, this is the only class to have its color inverted\n // automatically.\n color: #fff;\n .bg-variant(@brand-primary);\n}\n.bg-success {\n .bg-variant(@state-success-bg);\n}\n.bg-info {\n .bg-variant(@state-info-bg);\n}\n.bg-warning {\n .bg-variant(@state-warning-bg);\n}\n.bg-danger {\n .bg-variant(@state-danger-bg);\n}\n\n\n// Page header\n// -------------------------\n\n.page-header {\n padding-bottom: ((@line-height-computed / 2) - 1);\n margin: (@line-height-computed * 2) 0 @line-height-computed;\n border-bottom: 1px solid @page-header-border-color;\n}\n\n\n// Lists\n// -------------------------\n\n// Unordered and Ordered lists\nul,\nol {\n margin-top: 0;\n margin-bottom: (@line-height-computed / 2);\n ul,\n ol {\n margin-bottom: 0;\n }\n}\n\n// List options\n\n// Unstyled keeps list items block level, just removes default browser padding and list-style\n.list-unstyled {\n padding-left: 0;\n list-style: none;\n}\n\n// Inline turns list items into inline-block\n.list-inline {\n .list-unstyled();\n margin-left: -5px;\n\n > li {\n display: inline-block;\n padding-left: 5px;\n padding-right: 5px;\n }\n}\n\n// Description Lists\ndl {\n margin-top: 0; // Remove browser default\n margin-bottom: @line-height-computed;\n}\ndt,\ndd {\n line-height: @line-height-base;\n}\ndt {\n font-weight: bold;\n}\ndd {\n margin-left: 0; // Undo browser default\n}\n\n// Horizontal description lists\n//\n// Defaults to being stacked without any of the below styles applied, until the\n// grid breakpoint is reached (default of ~768px).\n\n.dl-horizontal {\n dd {\n &:extend(.clearfix all); // Clear the floated `dt` if an empty `dd` is present\n }\n\n @media (min-width: @dl-horizontal-breakpoint) {\n dt {\n float: left;\n width: (@dl-horizontal-offset - 20);\n clear: left;\n text-align: right;\n .text-overflow();\n }\n dd {\n margin-left: @dl-horizontal-offset;\n }\n }\n}\n\n\n// Misc\n// -------------------------\n\n// Abbreviations and acronyms\nabbr[title],\n// Add data-* attribute to help out our tooltip plugin, per https://github.com/twbs/bootstrap/issues/5257\nabbr[data-original-title] {\n cursor: help;\n border-bottom: 1px dotted @abbr-border-color;\n}\n.initialism {\n font-size: 90%;\n .text-uppercase();\n}\n\n// Blockquotes\nblockquote {\n padding: (@line-height-computed / 2) @line-height-computed;\n margin: 0 0 @line-height-computed;\n font-size: @blockquote-font-size;\n border-left: 5px solid @blockquote-border-color;\n\n p,\n ul,\n ol {\n &:last-child {\n margin-bottom: 0;\n }\n }\n\n // Note: Deprecated small and .small as of v3.1.0\n // Context: https://github.com/twbs/bootstrap/issues/11660\n footer,\n small,\n .small {\n display: block;\n font-size: 80%; // back to default font-size\n line-height: @line-height-base;\n color: @blockquote-small-color;\n\n &:before {\n content: '\\2014 \\00A0'; // em dash, nbsp\n }\n }\n}\n\n// Opposite alignment of blockquote\n//\n// Heads up: `blockquote.pull-right` has been deprecated as of v3.1.0.\n.blockquote-reverse,\nblockquote.pull-right {\n padding-right: 15px;\n padding-left: 0;\n border-right: 5px solid @blockquote-border-color;\n border-left: 0;\n text-align: right;\n\n // Account for citation\n footer,\n small,\n .small {\n &:before { content: ''; }\n &:after {\n content: '\\00A0 \\2014'; // nbsp, em dash\n }\n }\n}\n\n// Addresses\naddress {\n margin-bottom: @line-height-computed;\n font-style: normal;\n line-height: @line-height-base;\n}\n","// Typography\n\n.text-emphasis-variant(@color) {\n color: @color;\n a&:hover,\n a&:focus {\n color: darken(@color, 10%);\n }\n}\n","// Contextual backgrounds\n\n.bg-variant(@color) {\n background-color: @color;\n a&:hover,\n a&:focus {\n background-color: darken(@color, 10%);\n }\n}\n","// Text overflow\n// Requires inline-block or block for proper styling\n\n.text-overflow() {\n overflow: hidden;\n text-overflow: ellipsis;\n white-space: nowrap;\n}\n","//\n// Code (inline and block)\n// --------------------------------------------------\n\n\n// Inline and block code styles\ncode,\nkbd,\npre,\nsamp {\n font-family: @font-family-monospace;\n}\n\n// Inline code\ncode {\n padding: 2px 4px;\n font-size: 90%;\n color: @code-color;\n background-color: @code-bg;\n border-radius: @border-radius-base;\n}\n\n// User input typically entered via keyboard\nkbd {\n padding: 2px 4px;\n font-size: 90%;\n color: @kbd-color;\n background-color: @kbd-bg;\n border-radius: @border-radius-small;\n box-shadow: inset 0 -1px 0 rgba(0,0,0,.25);\n\n kbd {\n padding: 0;\n font-size: 100%;\n font-weight: bold;\n box-shadow: none;\n }\n}\n\n// Blocks of code\npre {\n display: block;\n padding: ((@line-height-computed - 1) / 2);\n margin: 0 0 (@line-height-computed / 2);\n font-size: (@font-size-base - 1); // 14px to 13px\n line-height: @line-height-base;\n word-break: break-all;\n word-wrap: break-word;\n color: @pre-color;\n background-color: @pre-bg;\n border: 1px solid @pre-border-color;\n border-radius: @border-radius-base;\n\n // Account for some code outputs that place code tags in pre tags\n code {\n padding: 0;\n font-size: inherit;\n color: inherit;\n white-space: pre-wrap;\n background-color: transparent;\n border-radius: 0;\n }\n}\n\n// Enable scrollable blocks of code\n.pre-scrollable {\n max-height: @pre-scrollable-max-height;\n overflow-y: scroll;\n}\n","//\n// Grid system\n// --------------------------------------------------\n\n\n// Container widths\n//\n// Set the container width, and override it for fixed navbars in media queries.\n\n.container {\n .container-fixed();\n\n @media (min-width: @screen-sm-min) {\n width: @container-sm;\n }\n @media (min-width: @screen-md-min) {\n width: @container-md;\n }\n @media (min-width: @screen-lg-min) {\n width: @container-lg;\n }\n}\n\n\n// Fluid container\n//\n// Utilizes the mixin meant for fixed width containers, but without any defined\n// width for fluid, full width layouts.\n\n.container-fluid {\n .container-fixed();\n}\n\n\n// Row\n//\n// Rows contain and clear the floats of your columns.\n\n.row {\n .make-row();\n}\n\n\n// Columns\n//\n// Common styles for small and large grid columns\n\n.make-grid-columns();\n\n\n// Extra small grid\n//\n// Columns, offsets, pushes, and pulls for extra small devices like\n// smartphones.\n\n.make-grid(xs);\n\n\n// Small grid\n//\n// Columns, offsets, pushes, and pulls for the small device range, from phones\n// to tablets.\n\n@media (min-width: @screen-sm-min) {\n .make-grid(sm);\n}\n\n\n// Medium grid\n//\n// Columns, offsets, pushes, and pulls for the desktop device range.\n\n@media (min-width: @screen-md-min) {\n .make-grid(md);\n}\n\n\n// Large grid\n//\n// Columns, offsets, pushes, and pulls for the large desktop device range.\n\n@media (min-width: @screen-lg-min) {\n .make-grid(lg);\n}\n","// Grid system\n//\n// Generate semantic grid columns with these mixins.\n\n// Centered container element\n.container-fixed(@gutter: @grid-gutter-width) {\n margin-right: auto;\n margin-left: auto;\n padding-left: floor((@gutter / 2));\n padding-right: ceil((@gutter / 2));\n &:extend(.clearfix all);\n}\n\n// Creates a wrapper for a series of columns\n.make-row(@gutter: @grid-gutter-width) {\n margin-left: ceil((@gutter / -2));\n margin-right: floor((@gutter / -2));\n &:extend(.clearfix all);\n}\n\n// Generate the extra small columns\n.make-xs-column(@columns; @gutter: @grid-gutter-width) {\n position: relative;\n float: left;\n width: percentage((@columns / @grid-columns));\n min-height: 1px;\n padding-left: (@gutter / 2);\n padding-right: (@gutter / 2);\n}\n.make-xs-column-offset(@columns) {\n margin-left: percentage((@columns / @grid-columns));\n}\n.make-xs-column-push(@columns) {\n left: percentage((@columns / @grid-columns));\n}\n.make-xs-column-pull(@columns) {\n right: percentage((@columns / @grid-columns));\n}\n\n// Generate the small columns\n.make-sm-column(@columns; @gutter: @grid-gutter-width) {\n position: relative;\n min-height: 1px;\n padding-left: (@gutter / 2);\n padding-right: (@gutter / 2);\n\n @media (min-width: @screen-sm-min) {\n float: left;\n width: percentage((@columns / @grid-columns));\n }\n}\n.make-sm-column-offset(@columns) {\n @media (min-width: @screen-sm-min) {\n margin-left: percentage((@columns / @grid-columns));\n }\n}\n.make-sm-column-push(@columns) {\n @media (min-width: @screen-sm-min) {\n left: percentage((@columns / @grid-columns));\n }\n}\n.make-sm-column-pull(@columns) {\n @media (min-width: @screen-sm-min) {\n right: percentage((@columns / @grid-columns));\n }\n}\n\n// Generate the medium columns\n.make-md-column(@columns; @gutter: @grid-gutter-width) {\n position: relative;\n min-height: 1px;\n padding-left: (@gutter / 2);\n padding-right: (@gutter / 2);\n\n @media (min-width: @screen-md-min) {\n float: left;\n width: percentage((@columns / @grid-columns));\n }\n}\n.make-md-column-offset(@columns) {\n @media (min-width: @screen-md-min) {\n margin-left: percentage((@columns / @grid-columns));\n }\n}\n.make-md-column-push(@columns) {\n @media (min-width: @screen-md-min) {\n left: percentage((@columns / @grid-columns));\n }\n}\n.make-md-column-pull(@columns) {\n @media (min-width: @screen-md-min) {\n right: percentage((@columns / @grid-columns));\n }\n}\n\n// Generate the large columns\n.make-lg-column(@columns; @gutter: @grid-gutter-width) {\n position: relative;\n min-height: 1px;\n padding-left: (@gutter / 2);\n padding-right: (@gutter / 2);\n\n @media (min-width: @screen-lg-min) {\n float: left;\n width: percentage((@columns / @grid-columns));\n }\n}\n.make-lg-column-offset(@columns) {\n @media (min-width: @screen-lg-min) {\n margin-left: percentage((@columns / @grid-columns));\n }\n}\n.make-lg-column-push(@columns) {\n @media (min-width: @screen-lg-min) {\n left: percentage((@columns / @grid-columns));\n }\n}\n.make-lg-column-pull(@columns) {\n @media (min-width: @screen-lg-min) {\n right: percentage((@columns / @grid-columns));\n }\n}\n","// Framework grid generation\n//\n// Used only by Bootstrap to generate the correct number of grid classes given\n// any value of `@grid-columns`.\n\n.make-grid-columns() {\n // Common styles for all sizes of grid columns, widths 1-12\n .col(@index) { // initial\n @item: ~\".col-xs-@{index}, .col-sm-@{index}, .col-md-@{index}, .col-lg-@{index}\";\n .col((@index + 1), @item);\n }\n .col(@index, @list) when (@index =< @grid-columns) { // general; \"=<\" isn't a typo\n @item: ~\".col-xs-@{index}, .col-sm-@{index}, .col-md-@{index}, .col-lg-@{index}\";\n .col((@index + 1), ~\"@{list}, @{item}\");\n }\n .col(@index, @list) when (@index > @grid-columns) { // terminal\n @{list} {\n position: relative;\n // Prevent columns from collapsing when empty\n min-height: 1px;\n // Inner gutter via padding\n padding-left: ceil((@grid-gutter-width / 2));\n padding-right: floor((@grid-gutter-width / 2));\n }\n }\n .col(1); // kickstart it\n}\n\n.float-grid-columns(@class) {\n .col(@index) { // initial\n @item: ~\".col-@{class}-@{index}\";\n .col((@index + 1), @item);\n }\n .col(@index, @list) when (@index =< @grid-columns) { // general\n @item: ~\".col-@{class}-@{index}\";\n .col((@index + 1), ~\"@{list}, @{item}\");\n }\n .col(@index, @list) when (@index > @grid-columns) { // terminal\n @{list} {\n float: left;\n }\n }\n .col(1); // kickstart it\n}\n\n.calc-grid-column(@index, @class, @type) when (@type = width) and (@index > 0) {\n .col-@{class}-@{index} {\n width: percentage((@index / @grid-columns));\n }\n}\n.calc-grid-column(@index, @class, @type) when (@type = push) and (@index > 0) {\n .col-@{class}-push-@{index} {\n left: percentage((@index / @grid-columns));\n }\n}\n.calc-grid-column(@index, @class, @type) when (@type = push) and (@index = 0) {\n .col-@{class}-push-0 {\n left: auto;\n }\n}\n.calc-grid-column(@index, @class, @type) when (@type = pull) and (@index > 0) {\n .col-@{class}-pull-@{index} {\n right: percentage((@index / @grid-columns));\n }\n}\n.calc-grid-column(@index, @class, @type) when (@type = pull) and (@index = 0) {\n .col-@{class}-pull-0 {\n right: auto;\n }\n}\n.calc-grid-column(@index, @class, @type) when (@type = offset) {\n .col-@{class}-offset-@{index} {\n margin-left: percentage((@index / @grid-columns));\n }\n}\n\n// Basic looping in LESS\n.loop-grid-columns(@index, @class, @type) when (@index >= 0) {\n .calc-grid-column(@index, @class, @type);\n // next iteration\n .loop-grid-columns((@index - 1), @class, @type);\n}\n\n// Create grid for specific class\n.make-grid(@class) {\n .float-grid-columns(@class);\n .loop-grid-columns(@grid-columns, @class, width);\n .loop-grid-columns(@grid-columns, @class, pull);\n .loop-grid-columns(@grid-columns, @class, push);\n .loop-grid-columns(@grid-columns, @class, offset);\n}\n","//\n// Tables\n// --------------------------------------------------\n\n\ntable {\n background-color: @table-bg;\n}\ncaption {\n padding-top: @table-cell-padding;\n padding-bottom: @table-cell-padding;\n color: @text-muted;\n text-align: left;\n}\nth {\n text-align: left;\n}\n\n\n// Baseline styles\n\n.table {\n width: 100%;\n max-width: 100%;\n margin-bottom: @line-height-computed;\n // Cells\n > thead,\n > tbody,\n > tfoot {\n > tr {\n > th,\n > td {\n padding: @table-cell-padding;\n line-height: @line-height-base;\n vertical-align: top;\n border-top: 1px solid @table-border-color;\n }\n }\n }\n // Bottom align for column headings\n > thead > tr > th {\n vertical-align: bottom;\n border-bottom: 2px solid @table-border-color;\n }\n // Remove top border from thead by default\n > caption + thead,\n > colgroup + thead,\n > thead:first-child {\n > tr:first-child {\n > th,\n > td {\n border-top: 0;\n }\n }\n }\n // Account for multiple tbody instances\n > tbody + tbody {\n border-top: 2px solid @table-border-color;\n }\n\n // Nesting\n .table {\n background-color: @body-bg;\n }\n}\n\n\n// Condensed table w/ half padding\n\n.table-condensed {\n > thead,\n > tbody,\n > tfoot {\n > tr {\n > th,\n > td {\n padding: @table-condensed-cell-padding;\n }\n }\n }\n}\n\n\n// Bordered version\n//\n// Add borders all around the table and between all the columns.\n\n.table-bordered {\n border: 1px solid @table-border-color;\n > thead,\n > tbody,\n > tfoot {\n > tr {\n > th,\n > td {\n border: 1px solid @table-border-color;\n }\n }\n }\n > thead > tr {\n > th,\n > td {\n border-bottom-width: 2px;\n }\n }\n}\n\n\n// Zebra-striping\n//\n// Default zebra-stripe styles (alternating gray and transparent backgrounds)\n\n.table-striped {\n > tbody > tr:nth-of-type(odd) {\n background-color: @table-bg-accent;\n }\n}\n\n\n// Hover effect\n//\n// Placed here since it has to come after the potential zebra striping\n\n.table-hover {\n > tbody > tr:hover {\n background-color: @table-bg-hover;\n }\n}\n\n\n// Table cell sizing\n//\n// Reset default table behavior\n\ntable col[class*=\"col-\"] {\n position: static; // Prevent border hiding in Firefox and IE9-11 (see https://github.com/twbs/bootstrap/issues/11623)\n float: none;\n display: table-column;\n}\ntable {\n td,\n th {\n &[class*=\"col-\"] {\n position: static; // Prevent border hiding in Firefox and IE9-11 (see https://github.com/twbs/bootstrap/issues/11623)\n float: none;\n display: table-cell;\n }\n }\n}\n\n\n// Table backgrounds\n//\n// Exact selectors below required to override `.table-striped` and prevent\n// inheritance to nested tables.\n\n// Generate the contextual variants\n.table-row-variant(active; @table-bg-active);\n.table-row-variant(success; @state-success-bg);\n.table-row-variant(info; @state-info-bg);\n.table-row-variant(warning; @state-warning-bg);\n.table-row-variant(danger; @state-danger-bg);\n\n\n// Responsive tables\n//\n// Wrap your tables in `.table-responsive` and we'll make them mobile friendly\n// by enabling horizontal scrolling. Only applies <768px. Everything above that\n// will display normally.\n\n.table-responsive {\n overflow-x: auto;\n min-height: 0.01%; // Workaround for IE9 bug (see https://github.com/twbs/bootstrap/issues/14837)\n\n @media screen and (max-width: @screen-xs-max) {\n width: 100%;\n margin-bottom: (@line-height-computed * 0.75);\n overflow-y: hidden;\n -ms-overflow-style: -ms-autohiding-scrollbar;\n border: 1px solid @table-border-color;\n\n // Tighten up spacing\n > .table {\n margin-bottom: 0;\n\n // Ensure the content doesn't wrap\n > thead,\n > tbody,\n > tfoot {\n > tr {\n > th,\n > td {\n white-space: nowrap;\n }\n }\n }\n }\n\n // Special overrides for the bordered tables\n > .table-bordered {\n border: 0;\n\n // Nuke the appropriate borders so that the parent can handle them\n > thead,\n > tbody,\n > tfoot {\n > tr {\n > th:first-child,\n > td:first-child {\n border-left: 0;\n }\n > th:last-child,\n > td:last-child {\n border-right: 0;\n }\n }\n }\n\n // Only nuke the last row's bottom-border in `tbody` and `tfoot` since\n // chances are there will be only one `tr` in a `thead` and that would\n // remove the border altogether.\n > tbody,\n > tfoot {\n > tr:last-child {\n > th,\n > td {\n border-bottom: 0;\n }\n }\n }\n\n }\n }\n}\n","// Tables\n\n.table-row-variant(@state; @background) {\n // Exact selectors below required to override `.table-striped` and prevent\n // inheritance to nested tables.\n .table > thead > tr,\n .table > tbody > tr,\n .table > tfoot > tr {\n > td.@{state},\n > th.@{state},\n &.@{state} > td,\n &.@{state} > th {\n background-color: @background;\n }\n }\n\n // Hover states for `.table-hover`\n // Note: this is not available for cells or rows within `thead` or `tfoot`.\n .table-hover > tbody > tr {\n > td.@{state}:hover,\n > th.@{state}:hover,\n &.@{state}:hover > td,\n &:hover > .@{state},\n &.@{state}:hover > th {\n background-color: darken(@background, 5%);\n }\n }\n}\n","//\n// Forms\n// --------------------------------------------------\n\n\n// Normalize non-controls\n//\n// Restyle and baseline non-control form elements.\n\nfieldset {\n padding: 0;\n margin: 0;\n border: 0;\n // Chrome and Firefox set a `min-width: min-content;` on fieldsets,\n // so we reset that to ensure it behaves more like a standard block element.\n // See https://github.com/twbs/bootstrap/issues/12359.\n min-width: 0;\n}\n\nlegend {\n display: block;\n width: 100%;\n padding: 0;\n margin-bottom: @line-height-computed;\n font-size: (@font-size-base * 1.5);\n line-height: inherit;\n color: @legend-color;\n border: 0;\n border-bottom: 1px solid @legend-border-color;\n}\n\nlabel {\n display: inline-block;\n max-width: 100%; // Force IE8 to wrap long content (see https://github.com/twbs/bootstrap/issues/13141)\n margin-bottom: 5px;\n font-weight: bold;\n}\n\n\n// Normalize form controls\n//\n// While most of our form styles require extra classes, some basic normalization\n// is required to ensure optimum display with or without those classes to better\n// address browser inconsistencies.\n\n// Override content-box in Normalize (* isn't specific enough)\ninput[type=\"search\"] {\n .box-sizing(border-box);\n}\n\n// Position radios and checkboxes better\ninput[type=\"radio\"],\ninput[type=\"checkbox\"] {\n margin: 4px 0 0;\n margin-top: 1px \\9; // IE8-9\n line-height: normal;\n}\n\ninput[type=\"file\"] {\n display: block;\n}\n\n// Make range inputs behave like textual form controls\ninput[type=\"range\"] {\n display: block;\n width: 100%;\n}\n\n// Make multiple select elements height not fixed\nselect[multiple],\nselect[size] {\n height: auto;\n}\n\n// Focus for file, radio, and checkbox\ninput[type=\"file\"]:focus,\ninput[type=\"radio\"]:focus,\ninput[type=\"checkbox\"]:focus {\n .tab-focus();\n}\n\n// Adjust output element\noutput {\n display: block;\n padding-top: (@padding-base-vertical + 1);\n font-size: @font-size-base;\n line-height: @line-height-base;\n color: @input-color;\n}\n\n\n// Common form controls\n//\n// Shared size and type resets for form controls. Apply `.form-control` to any\n// of the following form controls:\n//\n// select\n// textarea\n// input[type=\"text\"]\n// input[type=\"password\"]\n// input[type=\"datetime\"]\n// input[type=\"datetime-local\"]\n// input[type=\"date\"]\n// input[type=\"month\"]\n// input[type=\"time\"]\n// input[type=\"week\"]\n// input[type=\"number\"]\n// input[type=\"email\"]\n// input[type=\"url\"]\n// input[type=\"search\"]\n// input[type=\"tel\"]\n// input[type=\"color\"]\n\n.form-control {\n display: block;\n width: 100%;\n height: @input-height-base; // Make inputs at least the height of their button counterpart (base line-height + padding + border)\n padding: @padding-base-vertical @padding-base-horizontal;\n font-size: @font-size-base;\n line-height: @line-height-base;\n color: @input-color;\n background-color: @input-bg;\n background-image: none; // Reset unusual Firefox-on-Android default style; see https://github.com/necolas/normalize.css/issues/214\n border: 1px solid @input-border;\n border-radius: @input-border-radius; // Note: This has no effect on <select>s in some browsers, due to the limited stylability of <select>s in CSS.\n .box-shadow(inset 0 1px 1px rgba(0,0,0,.075));\n .transition(~\"border-color ease-in-out .15s, box-shadow ease-in-out .15s\");\n\n // Customize the `:focus` state to imitate native WebKit styles.\n .form-control-focus();\n\n // Placeholder\n .placeholder();\n\n // Unstyle the caret on `<select>`s in IE10+.\n &::-ms-expand {\n border: 0;\n background-color: transparent;\n }\n\n // Disabled and read-only inputs\n //\n // HTML5 says that controls under a fieldset > legend:first-child won't be\n // disabled if the fieldset is disabled. Due to implementation difficulty, we\n // don't honor that edge case; we style them as disabled anyway.\n &[disabled],\n &[readonly],\n fieldset[disabled] & {\n background-color: @input-bg-disabled;\n opacity: 1; // iOS fix for unreadable disabled content; see https://github.com/twbs/bootstrap/issues/11655\n }\n\n &[disabled],\n fieldset[disabled] & {\n cursor: @cursor-disabled;\n }\n\n // Reset height for `textarea`s\n textarea& {\n height: auto;\n }\n}\n\n\n// Search inputs in iOS\n//\n// This overrides the extra rounded corners on search inputs in iOS so that our\n// `.form-control` class can properly style them. Note that this cannot simply\n// be added to `.form-control` as it's not specific enough. For details, see\n// https://github.com/twbs/bootstrap/issues/11586.\n\ninput[type=\"search\"] {\n -webkit-appearance: none;\n}\n\n\n// Special styles for iOS temporal inputs\n//\n// In Mobile Safari, setting `display: block` on temporal inputs causes the\n// text within the input to become vertically misaligned. As a workaround, we\n// set a pixel line-height that matches the given height of the input, but only\n// for Safari. See https://bugs.webkit.org/show_bug.cgi?id=139848\n//\n// Note that as of 9.3, iOS doesn't support `week`.\n\n@media screen and (-webkit-min-device-pixel-ratio: 0) {\n input[type=\"date\"],\n input[type=\"time\"],\n input[type=\"datetime-local\"],\n input[type=\"month\"] {\n &.form-control {\n line-height: @input-height-base;\n }\n\n &.input-sm,\n .input-group-sm & {\n line-height: @input-height-small;\n }\n\n &.input-lg,\n .input-group-lg & {\n line-height: @input-height-large;\n }\n }\n}\n\n\n// Form groups\n//\n// Designed to help with the organization and spacing of vertical forms. For\n// horizontal forms, use the predefined grid classes.\n\n.form-group {\n margin-bottom: @form-group-margin-bottom;\n}\n\n\n// Checkboxes and radios\n//\n// Indent the labels to position radios/checkboxes as hanging controls.\n\n.radio,\n.checkbox {\n position: relative;\n display: block;\n margin-top: 10px;\n margin-bottom: 10px;\n\n label {\n min-height: @line-height-computed; // Ensure the input doesn't jump when there is no text\n padding-left: 20px;\n margin-bottom: 0;\n font-weight: normal;\n cursor: pointer;\n }\n}\n.radio input[type=\"radio\"],\n.radio-inline input[type=\"radio\"],\n.checkbox input[type=\"checkbox\"],\n.checkbox-inline input[type=\"checkbox\"] {\n position: absolute;\n margin-left: -20px;\n margin-top: 4px \\9;\n}\n\n.radio + .radio,\n.checkbox + .checkbox {\n margin-top: -5px; // Move up sibling radios or checkboxes for tighter spacing\n}\n\n// Radios and checkboxes on same line\n.radio-inline,\n.checkbox-inline {\n position: relative;\n display: inline-block;\n padding-left: 20px;\n margin-bottom: 0;\n vertical-align: middle;\n font-weight: normal;\n cursor: pointer;\n}\n.radio-inline + .radio-inline,\n.checkbox-inline + .checkbox-inline {\n margin-top: 0;\n margin-left: 10px; // space out consecutive inline controls\n}\n\n// Apply same disabled cursor tweak as for inputs\n// Some special care is needed because <label>s don't inherit their parent's `cursor`.\n//\n// Note: Neither radios nor checkboxes can be readonly.\ninput[type=\"radio\"],\ninput[type=\"checkbox\"] {\n &[disabled],\n &.disabled,\n fieldset[disabled] & {\n cursor: @cursor-disabled;\n }\n}\n// These classes are used directly on <label>s\n.radio-inline,\n.checkbox-inline {\n &.disabled,\n fieldset[disabled] & {\n cursor: @cursor-disabled;\n }\n}\n// These classes are used on elements with <label> descendants\n.radio,\n.checkbox {\n &.disabled,\n fieldset[disabled] & {\n label {\n cursor: @cursor-disabled;\n }\n }\n}\n\n\n// Static form control text\n//\n// Apply class to a `p` element to make any string of text align with labels in\n// a horizontal form layout.\n\n.form-control-static {\n // Size it appropriately next to real form controls\n padding-top: (@padding-base-vertical + 1);\n padding-bottom: (@padding-base-vertical + 1);\n // Remove default margin from `p`\n margin-bottom: 0;\n min-height: (@line-height-computed + @font-size-base);\n\n &.input-lg,\n &.input-sm {\n padding-left: 0;\n padding-right: 0;\n }\n}\n\n\n// Form control sizing\n//\n// Build on `.form-control` with modifier classes to decrease or increase the\n// height and font-size of form controls.\n//\n// The `.form-group-* form-control` variations are sadly duplicated to avoid the\n// issue documented in https://github.com/twbs/bootstrap/issues/15074.\n\n.input-sm {\n .input-size(@input-height-small; @padding-small-vertical; @padding-small-horizontal; @font-size-small; @line-height-small; @input-border-radius-small);\n}\n.form-group-sm {\n .form-control {\n height: @input-height-small;\n padding: @padding-small-vertical @padding-small-horizontal;\n font-size: @font-size-small;\n line-height: @line-height-small;\n border-radius: @input-border-radius-small;\n }\n select.form-control {\n height: @input-height-small;\n line-height: @input-height-small;\n }\n textarea.form-control,\n select[multiple].form-control {\n height: auto;\n }\n .form-control-static {\n height: @input-height-small;\n min-height: (@line-height-computed + @font-size-small);\n padding: (@padding-small-vertical + 1) @padding-small-horizontal;\n font-size: @font-size-small;\n line-height: @line-height-small;\n }\n}\n\n.input-lg {\n .input-size(@input-height-large; @padding-large-vertical; @padding-large-horizontal; @font-size-large; @line-height-large; @input-border-radius-large);\n}\n.form-group-lg {\n .form-control {\n height: @input-height-large;\n padding: @padding-large-vertical @padding-large-horizontal;\n font-size: @font-size-large;\n line-height: @line-height-large;\n border-radius: @input-border-radius-large;\n }\n select.form-control {\n height: @input-height-large;\n line-height: @input-height-large;\n }\n textarea.form-control,\n select[multiple].form-control {\n height: auto;\n }\n .form-control-static {\n height: @input-height-large;\n min-height: (@line-height-computed + @font-size-large);\n padding: (@padding-large-vertical + 1) @padding-large-horizontal;\n font-size: @font-size-large;\n line-height: @line-height-large;\n }\n}\n\n\n// Form control feedback states\n//\n// Apply contextual and semantic states to individual form controls.\n\n.has-feedback {\n // Enable absolute positioning\n position: relative;\n\n // Ensure icons don't overlap text\n .form-control {\n padding-right: (@input-height-base * 1.25);\n }\n}\n// Feedback icon (requires .glyphicon classes)\n.form-control-feedback {\n position: absolute;\n top: 0;\n right: 0;\n z-index: 2; // Ensure icon is above input groups\n display: block;\n width: @input-height-base;\n height: @input-height-base;\n line-height: @input-height-base;\n text-align: center;\n pointer-events: none;\n}\n.input-lg + .form-control-feedback,\n.input-group-lg + .form-control-feedback,\n.form-group-lg .form-control + .form-control-feedback {\n width: @input-height-large;\n height: @input-height-large;\n line-height: @input-height-large;\n}\n.input-sm + .form-control-feedback,\n.input-group-sm + .form-control-feedback,\n.form-group-sm .form-control + .form-control-feedback {\n width: @input-height-small;\n height: @input-height-small;\n line-height: @input-height-small;\n}\n\n// Feedback states\n.has-success {\n .form-control-validation(@state-success-text; @state-success-text; @state-success-bg);\n}\n.has-warning {\n .form-control-validation(@state-warning-text; @state-warning-text; @state-warning-bg);\n}\n.has-error {\n .form-control-validation(@state-danger-text; @state-danger-text; @state-danger-bg);\n}\n\n// Reposition feedback icon if input has visible label above\n.has-feedback label {\n\n & ~ .form-control-feedback {\n top: (@line-height-computed + 5); // Height of the `label` and its margin\n }\n &.sr-only ~ .form-control-feedback {\n top: 0;\n }\n}\n\n\n// Help text\n//\n// Apply to any element you wish to create light text for placement immediately\n// below a form control. Use for general help, formatting, or instructional text.\n\n.help-block {\n display: block; // account for any element using help-block\n margin-top: 5px;\n margin-bottom: 10px;\n color: lighten(@text-color, 25%); // lighten the text some for contrast\n}\n\n\n// Inline forms\n//\n// Make forms appear inline(-block) by adding the `.form-inline` class. Inline\n// forms begin stacked on extra small (mobile) devices and then go inline when\n// viewports reach <768px.\n//\n// Requires wrapping inputs and labels with `.form-group` for proper display of\n// default HTML form controls and our custom form controls (e.g., input groups).\n//\n// Heads up! This is mixin-ed into `.navbar-form` in navbars.less.\n\n.form-inline {\n\n // Kick in the inline\n @media (min-width: @screen-sm-min) {\n // Inline-block all the things for \"inline\"\n .form-group {\n display: inline-block;\n margin-bottom: 0;\n vertical-align: middle;\n }\n\n // In navbar-form, allow folks to *not* use `.form-group`\n .form-control {\n display: inline-block;\n width: auto; // Prevent labels from stacking above inputs in `.form-group`\n vertical-align: middle;\n }\n\n // Make static controls behave like regular ones\n .form-control-static {\n display: inline-block;\n }\n\n .input-group {\n display: inline-table;\n vertical-align: middle;\n\n .input-group-addon,\n .input-group-btn,\n .form-control {\n width: auto;\n }\n }\n\n // Input groups need that 100% width though\n .input-group > .form-control {\n width: 100%;\n }\n\n .control-label {\n margin-bottom: 0;\n vertical-align: middle;\n }\n\n // Remove default margin on radios/checkboxes that were used for stacking, and\n // then undo the floating of radios and checkboxes to match.\n .radio,\n .checkbox {\n display: inline-block;\n margin-top: 0;\n margin-bottom: 0;\n vertical-align: middle;\n\n label {\n padding-left: 0;\n }\n }\n .radio input[type=\"radio\"],\n .checkbox input[type=\"checkbox\"] {\n position: relative;\n margin-left: 0;\n }\n\n // Re-override the feedback icon.\n .has-feedback .form-control-feedback {\n top: 0;\n }\n }\n}\n\n\n// Horizontal forms\n//\n// Horizontal forms are built on grid classes and allow you to create forms with\n// labels on the left and inputs on the right.\n\n.form-horizontal {\n\n // Consistent vertical alignment of radios and checkboxes\n //\n // Labels also get some reset styles, but that is scoped to a media query below.\n .radio,\n .checkbox,\n .radio-inline,\n .checkbox-inline {\n margin-top: 0;\n margin-bottom: 0;\n padding-top: (@padding-base-vertical + 1); // Default padding plus a border\n }\n // Account for padding we're adding to ensure the alignment and of help text\n // and other content below items\n .radio,\n .checkbox {\n min-height: (@line-height-computed + (@padding-base-vertical + 1));\n }\n\n // Make form groups behave like rows\n .form-group {\n .make-row();\n }\n\n // Reset spacing and right align labels, but scope to media queries so that\n // labels on narrow viewports stack the same as a default form example.\n @media (min-width: @screen-sm-min) {\n .control-label {\n text-align: right;\n margin-bottom: 0;\n padding-top: (@padding-base-vertical + 1); // Default padding plus a border\n }\n }\n\n // Validation states\n //\n // Reposition the icon because it's now within a grid column and columns have\n // `position: relative;` on them. Also accounts for the grid gutter padding.\n .has-feedback .form-control-feedback {\n right: floor((@grid-gutter-width / 2));\n }\n\n // Form group sizes\n //\n // Quick utility class for applying `.input-lg` and `.input-sm` styles to the\n // inputs and labels within a `.form-group`.\n .form-group-lg {\n @media (min-width: @screen-sm-min) {\n .control-label {\n padding-top: (@padding-large-vertical + 1);\n font-size: @font-size-large;\n }\n }\n }\n .form-group-sm {\n @media (min-width: @screen-sm-min) {\n .control-label {\n padding-top: (@padding-small-vertical + 1);\n font-size: @font-size-small;\n }\n }\n }\n}\n","// Form validation states\n//\n// Used in forms.less to generate the form validation CSS for warnings, errors,\n// and successes.\n\n.form-control-validation(@text-color: #555; @border-color: #ccc; @background-color: #f5f5f5) {\n // Color the label and help text\n .help-block,\n .control-label,\n .radio,\n .checkbox,\n .radio-inline,\n .checkbox-inline,\n &.radio label,\n &.checkbox label,\n &.radio-inline label,\n &.checkbox-inline label {\n color: @text-color;\n }\n // Set the border and box shadow on specific inputs to match\n .form-control {\n border-color: @border-color;\n .box-shadow(inset 0 1px 1px rgba(0,0,0,.075)); // Redeclare so transitions work\n &:focus {\n border-color: darken(@border-color, 10%);\n @shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 6px lighten(@border-color, 20%);\n .box-shadow(@shadow);\n }\n }\n // Set validation states also for addons\n .input-group-addon {\n color: @text-color;\n border-color: @border-color;\n background-color: @background-color;\n }\n // Optional feedback icon\n .form-control-feedback {\n color: @text-color;\n }\n}\n\n\n// Form control focus state\n//\n// Generate a customized focus state and for any input with the specified color,\n// which defaults to the `@input-border-focus` variable.\n//\n// We highly encourage you to not customize the default value, but instead use\n// this to tweak colors on an as-needed basis. This aesthetic change is based on\n// WebKit's default styles, but applicable to a wider range of browsers. Its\n// usability and accessibility should be taken into account with any change.\n//\n// Example usage: change the default blue border and shadow to white for better\n// contrast against a dark gray background.\n.form-control-focus(@color: @input-border-focus) {\n @color-rgba: rgba(red(@color), green(@color), blue(@color), .6);\n &:focus {\n border-color: @color;\n outline: 0;\n .box-shadow(~\"inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px @{color-rgba}\");\n }\n}\n\n// Form control sizing\n//\n// Relative text size, padding, and border-radii changes for form controls. For\n// horizontal sizing, wrap controls in the predefined grid classes. `<select>`\n// element gets special love because it's special, and that's a fact!\n.input-size(@input-height; @padding-vertical; @padding-horizontal; @font-size; @line-height; @border-radius) {\n height: @input-height;\n padding: @padding-vertical @padding-horizontal;\n font-size: @font-size;\n line-height: @line-height;\n border-radius: @border-radius;\n\n select& {\n height: @input-height;\n line-height: @input-height;\n }\n\n textarea&,\n select[multiple]& {\n height: auto;\n }\n}\n","//\n// Buttons\n// --------------------------------------------------\n\n\n// Base styles\n// --------------------------------------------------\n\n.btn {\n display: inline-block;\n margin-bottom: 0; // For input.btn\n font-weight: @btn-font-weight;\n text-align: center;\n vertical-align: middle;\n touch-action: manipulation;\n cursor: pointer;\n background-image: none; // Reset unusual Firefox-on-Android default style; see https://github.com/necolas/normalize.css/issues/214\n border: 1px solid transparent;\n white-space: nowrap;\n .button-size(@padding-base-vertical; @padding-base-horizontal; @font-size-base; @line-height-base; @btn-border-radius-base);\n .user-select(none);\n\n &,\n &:active,\n &.active {\n &:focus,\n &.focus {\n .tab-focus();\n }\n }\n\n &:hover,\n &:focus,\n &.focus {\n color: @btn-default-color;\n text-decoration: none;\n }\n\n &:active,\n &.active {\n outline: 0;\n background-image: none;\n .box-shadow(inset 0 3px 5px rgba(0,0,0,.125));\n }\n\n &.disabled,\n &[disabled],\n fieldset[disabled] & {\n cursor: @cursor-disabled;\n .opacity(.65);\n .box-shadow(none);\n }\n\n a& {\n &.disabled,\n fieldset[disabled] & {\n pointer-events: none; // Future-proof disabling of clicks on `<a>` elements\n }\n }\n}\n\n\n// Alternate buttons\n// --------------------------------------------------\n\n.btn-default {\n .button-variant(@btn-default-color; @btn-default-bg; @btn-default-border);\n}\n.btn-primary {\n .button-variant(@btn-primary-color; @btn-primary-bg; @btn-primary-border);\n}\n// Success appears as green\n.btn-success {\n .button-variant(@btn-success-color; @btn-success-bg; @btn-success-border);\n}\n// Info appears as blue-green\n.btn-info {\n .button-variant(@btn-info-color; @btn-info-bg; @btn-info-border);\n}\n// Warning appears as orange\n.btn-warning {\n .button-variant(@btn-warning-color; @btn-warning-bg; @btn-warning-border);\n}\n// Danger and error appear as red\n.btn-danger {\n .button-variant(@btn-danger-color; @btn-danger-bg; @btn-danger-border);\n}\n\n\n// Link buttons\n// -------------------------\n\n// Make a button look and behave like a link\n.btn-link {\n color: @link-color;\n font-weight: normal;\n border-radius: 0;\n\n &,\n &:active,\n &.active,\n &[disabled],\n fieldset[disabled] & {\n background-color: transparent;\n .box-shadow(none);\n }\n &,\n &:hover,\n &:focus,\n &:active {\n border-color: transparent;\n }\n &:hover,\n &:focus {\n color: @link-hover-color;\n text-decoration: @link-hover-decoration;\n background-color: transparent;\n }\n &[disabled],\n fieldset[disabled] & {\n &:hover,\n &:focus {\n color: @btn-link-disabled-color;\n text-decoration: none;\n }\n }\n}\n\n\n// Button Sizes\n// --------------------------------------------------\n\n.btn-lg {\n // line-height: ensure even-numbered height of button next to large input\n .button-size(@padding-large-vertical; @padding-large-horizontal; @font-size-large; @line-height-large; @btn-border-radius-large);\n}\n.btn-sm {\n // line-height: ensure proper height of button next to small input\n .button-size(@padding-small-vertical; @padding-small-horizontal; @font-size-small; @line-height-small; @btn-border-radius-small);\n}\n.btn-xs {\n .button-size(@padding-xs-vertical; @padding-xs-horizontal; @font-size-small; @line-height-small; @btn-border-radius-small);\n}\n\n\n// Block button\n// --------------------------------------------------\n\n.btn-block {\n display: block;\n width: 100%;\n}\n\n// Vertically space out multiple block buttons\n.btn-block + .btn-block {\n margin-top: 5px;\n}\n\n// Specificity overrides\ninput[type=\"submit\"],\ninput[type=\"reset\"],\ninput[type=\"button\"] {\n &.btn-block {\n width: 100%;\n }\n}\n","// Button variants\n//\n// Easily pump out default styles, as well as :hover, :focus, :active,\n// and disabled options for all buttons\n\n.button-variant(@color; @background; @border) {\n color: @color;\n background-color: @background;\n border-color: @border;\n\n &:focus,\n &.focus {\n color: @color;\n background-color: darken(@background, 10%);\n border-color: darken(@border, 25%);\n }\n &:hover {\n color: @color;\n background-color: darken(@background, 10%);\n border-color: darken(@border, 12%);\n }\n &:active,\n &.active,\n .open > .dropdown-toggle& {\n color: @color;\n background-color: darken(@background, 10%);\n border-color: darken(@border, 12%);\n\n &:hover,\n &:focus,\n &.focus {\n color: @color;\n background-color: darken(@background, 17%);\n border-color: darken(@border, 25%);\n }\n }\n &:active,\n &.active,\n .open > .dropdown-toggle& {\n background-image: none;\n }\n &.disabled,\n &[disabled],\n fieldset[disabled] & {\n &:hover,\n &:focus,\n &.focus {\n background-color: @background;\n border-color: @border;\n }\n }\n\n .badge {\n color: @background;\n background-color: @color;\n }\n}\n\n// Button sizes\n.button-size(@padding-vertical; @padding-horizontal; @font-size; @line-height; @border-radius) {\n padding: @padding-vertical @padding-horizontal;\n font-size: @font-size;\n line-height: @line-height;\n border-radius: @border-radius;\n}\n","// Opacity\n\n.opacity(@opacity) {\n opacity: @opacity;\n // IE8 filter\n @opacity-ie: (@opacity * 100);\n filter: ~\"alpha(opacity=@{opacity-ie})\";\n}\n","//\n// Component animations\n// --------------------------------------------------\n\n// Heads up!\n//\n// We don't use the `.opacity()` mixin here since it causes a bug with text\n// fields in IE7-8. Source: https://github.com/twbs/bootstrap/pull/3552.\n\n.fade {\n opacity: 0;\n .transition(opacity .15s linear);\n &.in {\n opacity: 1;\n }\n}\n\n.collapse {\n display: none;\n\n &.in { display: block; }\n tr&.in { display: table-row; }\n tbody&.in { display: table-row-group; }\n}\n\n.collapsing {\n position: relative;\n height: 0;\n overflow: hidden;\n .transition-property(~\"height, visibility\");\n .transition-duration(.35s);\n .transition-timing-function(ease);\n}\n","//\n// Dropdown menus\n// --------------------------------------------------\n\n\n// Dropdown arrow/caret\n.caret {\n display: inline-block;\n width: 0;\n height: 0;\n margin-left: 2px;\n vertical-align: middle;\n border-top: @caret-width-base dashed;\n border-top: @caret-width-base solid ~\"\\9\"; // IE8\n border-right: @caret-width-base solid transparent;\n border-left: @caret-width-base solid transparent;\n}\n\n// The dropdown wrapper (div)\n.dropup,\n.dropdown {\n position: relative;\n}\n\n// Prevent the focus on the dropdown toggle when closing dropdowns\n.dropdown-toggle:focus {\n outline: 0;\n}\n\n// The dropdown menu (ul)\n.dropdown-menu {\n position: absolute;\n top: 100%;\n left: 0;\n z-index: @zindex-dropdown;\n display: none; // none by default, but block on \"open\" of the menu\n float: left;\n min-width: 160px;\n padding: 5px 0;\n margin: 2px 0 0; // override default ul\n list-style: none;\n font-size: @font-size-base;\n text-align: left; // Ensures proper alignment if parent has it changed (e.g., modal footer)\n background-color: @dropdown-bg;\n border: 1px solid @dropdown-fallback-border; // IE8 fallback\n border: 1px solid @dropdown-border;\n border-radius: @border-radius-base;\n .box-shadow(0 6px 12px rgba(0,0,0,.175));\n background-clip: padding-box;\n\n // Aligns the dropdown menu to right\n //\n // Deprecated as of 3.1.0 in favor of `.dropdown-menu-[dir]`\n &.pull-right {\n right: 0;\n left: auto;\n }\n\n // Dividers (basically an hr) within the dropdown\n .divider {\n .nav-divider(@dropdown-divider-bg);\n }\n\n // Links within the dropdown menu\n > li > a {\n display: block;\n padding: 3px 20px;\n clear: both;\n font-weight: normal;\n line-height: @line-height-base;\n color: @dropdown-link-color;\n white-space: nowrap; // prevent links from randomly breaking onto new lines\n }\n}\n\n// Hover/Focus state\n.dropdown-menu > li > a {\n &:hover,\n &:focus {\n text-decoration: none;\n color: @dropdown-link-hover-color;\n background-color: @dropdown-link-hover-bg;\n }\n}\n\n// Active state\n.dropdown-menu > .active > a {\n &,\n &:hover,\n &:focus {\n color: @dropdown-link-active-color;\n text-decoration: none;\n outline: 0;\n background-color: @dropdown-link-active-bg;\n }\n}\n\n// Disabled state\n//\n// Gray out text and ensure the hover/focus state remains gray\n\n.dropdown-menu > .disabled > a {\n &,\n &:hover,\n &:focus {\n color: @dropdown-link-disabled-color;\n }\n\n // Nuke hover/focus effects\n &:hover,\n &:focus {\n text-decoration: none;\n background-color: transparent;\n background-image: none; // Remove CSS gradient\n .reset-filter();\n cursor: @cursor-disabled;\n }\n}\n\n// Open state for the dropdown\n.open {\n // Show the menu\n > .dropdown-menu {\n display: block;\n }\n\n // Remove the outline when :focus is triggered\n > a {\n outline: 0;\n }\n}\n\n// Menu positioning\n//\n// Add extra class to `.dropdown-menu` to flip the alignment of the dropdown\n// menu with the parent.\n.dropdown-menu-right {\n left: auto; // Reset the default from `.dropdown-menu`\n right: 0;\n}\n// With v3, we enabled auto-flipping if you have a dropdown within a right\n// aligned nav component. To enable the undoing of that, we provide an override\n// to restore the default dropdown menu alignment.\n//\n// This is only for left-aligning a dropdown menu within a `.navbar-right` or\n// `.pull-right` nav component.\n.dropdown-menu-left {\n left: 0;\n right: auto;\n}\n\n// Dropdown section headers\n.dropdown-header {\n display: block;\n padding: 3px 20px;\n font-size: @font-size-small;\n line-height: @line-height-base;\n color: @dropdown-header-color;\n white-space: nowrap; // as with > li > a\n}\n\n// Backdrop to catch body clicks on mobile, etc.\n.dropdown-backdrop {\n position: fixed;\n left: 0;\n right: 0;\n bottom: 0;\n top: 0;\n z-index: (@zindex-dropdown - 10);\n}\n\n// Right aligned dropdowns\n.pull-right > .dropdown-menu {\n right: 0;\n left: auto;\n}\n\n// Allow for dropdowns to go bottom up (aka, dropup-menu)\n//\n// Just add .dropup after the standard .dropdown class and you're set, bro.\n// TODO: abstract this so that the navbar fixed styles are not placed here?\n\n.dropup,\n.navbar-fixed-bottom .dropdown {\n // Reverse the caret\n .caret {\n border-top: 0;\n border-bottom: @caret-width-base dashed;\n border-bottom: @caret-width-base solid ~\"\\9\"; // IE8\n content: \"\";\n }\n // Different positioning for bottom up menu\n .dropdown-menu {\n top: auto;\n bottom: 100%;\n margin-bottom: 2px;\n }\n}\n\n\n// Component alignment\n//\n// Reiterate per navbar.less and the modified component alignment there.\n\n@media (min-width: @grid-float-breakpoint) {\n .navbar-right {\n .dropdown-menu {\n .dropdown-menu-right();\n }\n // Necessary for overrides of the default right aligned menu.\n // Will remove come v4 in all likelihood.\n .dropdown-menu-left {\n .dropdown-menu-left();\n }\n }\n}\n","// Horizontal dividers\n//\n// Dividers (basically an hr) within dropdowns and nav lists\n\n.nav-divider(@color: #e5e5e5) {\n height: 1px;\n margin: ((@line-height-computed / 2) - 1) 0;\n overflow: hidden;\n background-color: @color;\n}\n","// Reset filters for IE\n//\n// When you need to remove a gradient background, do not forget to use this to reset\n// the IE filter for IE9 and below.\n\n.reset-filter() {\n filter: e(%(\"progid:DXImageTransform.Microsoft.gradient(enabled = false)\"));\n}\n","//\n// Button groups\n// --------------------------------------------------\n\n// Make the div behave like a button\n.btn-group,\n.btn-group-vertical {\n position: relative;\n display: inline-block;\n vertical-align: middle; // match .btn alignment given font-size hack above\n > .btn {\n position: relative;\n float: left;\n // Bring the \"active\" button to the front\n &:hover,\n &:focus,\n &:active,\n &.active {\n z-index: 2;\n }\n }\n}\n\n// Prevent double borders when buttons are next to each other\n.btn-group {\n .btn + .btn,\n .btn + .btn-group,\n .btn-group + .btn,\n .btn-group + .btn-group {\n margin-left: -1px;\n }\n}\n\n// Optional: Group multiple button groups together for a toolbar\n.btn-toolbar {\n margin-left: -5px; // Offset the first child's margin\n &:extend(.clearfix all);\n\n .btn,\n .btn-group,\n .input-group {\n float: left;\n }\n > .btn,\n > .btn-group,\n > .input-group {\n margin-left: 5px;\n }\n}\n\n.btn-group > .btn:not(:first-child):not(:last-child):not(.dropdown-toggle) {\n border-radius: 0;\n}\n\n// Set corners individual because sometimes a single button can be in a .btn-group and we need :first-child and :last-child to both match\n.btn-group > .btn:first-child {\n margin-left: 0;\n &:not(:last-child):not(.dropdown-toggle) {\n .border-right-radius(0);\n }\n}\n// Need .dropdown-toggle since :last-child doesn't apply, given that a .dropdown-menu is used immediately after it\n.btn-group > .btn:last-child:not(:first-child),\n.btn-group > .dropdown-toggle:not(:first-child) {\n .border-left-radius(0);\n}\n\n// Custom edits for including btn-groups within btn-groups (useful for including dropdown buttons within a btn-group)\n.btn-group > .btn-group {\n float: left;\n}\n.btn-group > .btn-group:not(:first-child):not(:last-child) > .btn {\n border-radius: 0;\n}\n.btn-group > .btn-group:first-child:not(:last-child) {\n > .btn:last-child,\n > .dropdown-toggle {\n .border-right-radius(0);\n }\n}\n.btn-group > .btn-group:last-child:not(:first-child) > .btn:first-child {\n .border-left-radius(0);\n}\n\n// On active and open, don't show outline\n.btn-group .dropdown-toggle:active,\n.btn-group.open .dropdown-toggle {\n outline: 0;\n}\n\n\n// Sizing\n//\n// Remix the default button sizing classes into new ones for easier manipulation.\n\n.btn-group-xs > .btn { &:extend(.btn-xs); }\n.btn-group-sm > .btn { &:extend(.btn-sm); }\n.btn-group-lg > .btn { &:extend(.btn-lg); }\n\n\n// Split button dropdowns\n// ----------------------\n\n// Give the line between buttons some depth\n.btn-group > .btn + .dropdown-toggle {\n padding-left: 8px;\n padding-right: 8px;\n}\n.btn-group > .btn-lg + .dropdown-toggle {\n padding-left: 12px;\n padding-right: 12px;\n}\n\n// The clickable button for toggling the menu\n// Remove the gradient and set the same inset shadow as the :active state\n.btn-group.open .dropdown-toggle {\n .box-shadow(inset 0 3px 5px rgba(0,0,0,.125));\n\n // Show no shadow for `.btn-link` since it has no other button styles.\n &.btn-link {\n .box-shadow(none);\n }\n}\n\n\n// Reposition the caret\n.btn .caret {\n margin-left: 0;\n}\n// Carets in other button sizes\n.btn-lg .caret {\n border-width: @caret-width-large @caret-width-large 0;\n border-bottom-width: 0;\n}\n// Upside down carets for .dropup\n.dropup .btn-lg .caret {\n border-width: 0 @caret-width-large @caret-width-large;\n}\n\n\n// Vertical button groups\n// ----------------------\n\n.btn-group-vertical {\n > .btn,\n > .btn-group,\n > .btn-group > .btn {\n display: block;\n float: none;\n width: 100%;\n max-width: 100%;\n }\n\n // Clear floats so dropdown menus can be properly placed\n > .btn-group {\n &:extend(.clearfix all);\n > .btn {\n float: none;\n }\n }\n\n > .btn + .btn,\n > .btn + .btn-group,\n > .btn-group + .btn,\n > .btn-group + .btn-group {\n margin-top: -1px;\n margin-left: 0;\n }\n}\n\n.btn-group-vertical > .btn {\n &:not(:first-child):not(:last-child) {\n border-radius: 0;\n }\n &:first-child:not(:last-child) {\n .border-top-radius(@btn-border-radius-base);\n .border-bottom-radius(0);\n }\n &:last-child:not(:first-child) {\n .border-top-radius(0);\n .border-bottom-radius(@btn-border-radius-base);\n }\n}\n.btn-group-vertical > .btn-group:not(:first-child):not(:last-child) > .btn {\n border-radius: 0;\n}\n.btn-group-vertical > .btn-group:first-child:not(:last-child) {\n > .btn:last-child,\n > .dropdown-toggle {\n .border-bottom-radius(0);\n }\n}\n.btn-group-vertical > .btn-group:last-child:not(:first-child) > .btn:first-child {\n .border-top-radius(0);\n}\n\n\n// Justified button groups\n// ----------------------\n\n.btn-group-justified {\n display: table;\n width: 100%;\n table-layout: fixed;\n border-collapse: separate;\n > .btn,\n > .btn-group {\n float: none;\n display: table-cell;\n width: 1%;\n }\n > .btn-group .btn {\n width: 100%;\n }\n\n > .btn-group .dropdown-menu {\n left: auto;\n }\n}\n\n\n// Checkbox and radio options\n//\n// In order to support the browser's form validation feedback, powered by the\n// `required` attribute, we have to \"hide\" the inputs via `clip`. We cannot use\n// `display: none;` or `visibility: hidden;` as that also hides the popover.\n// Simply visually hiding the inputs via `opacity` would leave them clickable in\n// certain cases which is prevented by using `clip` and `pointer-events`.\n// This way, we ensure a DOM element is visible to position the popover from.\n//\n// See https://github.com/twbs/bootstrap/pull/12794 and\n// https://github.com/twbs/bootstrap/pull/14559 for more information.\n\n[data-toggle=\"buttons\"] {\n > .btn,\n > .btn-group > .btn {\n input[type=\"radio\"],\n input[type=\"checkbox\"] {\n position: absolute;\n clip: rect(0,0,0,0);\n pointer-events: none;\n }\n }\n}\n","// Single side border-radius\n\n.border-top-radius(@radius) {\n border-top-right-radius: @radius;\n border-top-left-radius: @radius;\n}\n.border-right-radius(@radius) {\n border-bottom-right-radius: @radius;\n border-top-right-radius: @radius;\n}\n.border-bottom-radius(@radius) {\n border-bottom-right-radius: @radius;\n border-bottom-left-radius: @radius;\n}\n.border-left-radius(@radius) {\n border-bottom-left-radius: @radius;\n border-top-left-radius: @radius;\n}\n","//\n// Input groups\n// --------------------------------------------------\n\n// Base styles\n// -------------------------\n.input-group {\n position: relative; // For dropdowns\n display: table;\n border-collapse: separate; // prevent input groups from inheriting border styles from table cells when placed within a table\n\n // Undo padding and float of grid classes\n &[class*=\"col-\"] {\n float: none;\n padding-left: 0;\n padding-right: 0;\n }\n\n .form-control {\n // Ensure that the input is always above the *appended* addon button for\n // proper border colors.\n position: relative;\n z-index: 2;\n\n // IE9 fubars the placeholder attribute in text inputs and the arrows on\n // select elements in input groups. To fix it, we float the input. Details:\n // https://github.com/twbs/bootstrap/issues/11561#issuecomment-28936855\n float: left;\n\n width: 100%;\n margin-bottom: 0;\n\n &:focus {\n z-index: 3;\n }\n }\n}\n\n// Sizing options\n//\n// Remix the default form control sizing classes into new ones for easier\n// manipulation.\n\n.input-group-lg > .form-control,\n.input-group-lg > .input-group-addon,\n.input-group-lg > .input-group-btn > .btn {\n .input-lg();\n}\n.input-group-sm > .form-control,\n.input-group-sm > .input-group-addon,\n.input-group-sm > .input-group-btn > .btn {\n .input-sm();\n}\n\n\n// Display as table-cell\n// -------------------------\n.input-group-addon,\n.input-group-btn,\n.input-group .form-control {\n display: table-cell;\n\n &:not(:first-child):not(:last-child) {\n border-radius: 0;\n }\n}\n// Addon and addon wrapper for buttons\n.input-group-addon,\n.input-group-btn {\n width: 1%;\n white-space: nowrap;\n vertical-align: middle; // Match the inputs\n}\n\n// Text input groups\n// -------------------------\n.input-group-addon {\n padding: @padding-base-vertical @padding-base-horizontal;\n font-size: @font-size-base;\n font-weight: normal;\n line-height: 1;\n color: @input-color;\n text-align: center;\n background-color: @input-group-addon-bg;\n border: 1px solid @input-group-addon-border-color;\n border-radius: @input-border-radius;\n\n // Sizing\n &.input-sm {\n padding: @padding-small-vertical @padding-small-horizontal;\n font-size: @font-size-small;\n border-radius: @input-border-radius-small;\n }\n &.input-lg {\n padding: @padding-large-vertical @padding-large-horizontal;\n font-size: @font-size-large;\n border-radius: @input-border-radius-large;\n }\n\n // Nuke default margins from checkboxes and radios to vertically center within.\n input[type=\"radio\"],\n input[type=\"checkbox\"] {\n margin-top: 0;\n }\n}\n\n// Reset rounded corners\n.input-group .form-control:first-child,\n.input-group-addon:first-child,\n.input-group-btn:first-child > .btn,\n.input-group-btn:first-child > .btn-group > .btn,\n.input-group-btn:first-child > .dropdown-toggle,\n.input-group-btn:last-child > .btn:not(:last-child):not(.dropdown-toggle),\n.input-group-btn:last-child > .btn-group:not(:last-child) > .btn {\n .border-right-radius(0);\n}\n.input-group-addon:first-child {\n border-right: 0;\n}\n.input-group .form-control:last-child,\n.input-group-addon:last-child,\n.input-group-btn:last-child > .btn,\n.input-group-btn:last-child > .btn-group > .btn,\n.input-group-btn:last-child > .dropdown-toggle,\n.input-group-btn:first-child > .btn:not(:first-child),\n.input-group-btn:first-child > .btn-group:not(:first-child) > .btn {\n .border-left-radius(0);\n}\n.input-group-addon:last-child {\n border-left: 0;\n}\n\n// Button input groups\n// -------------------------\n.input-group-btn {\n position: relative;\n // Jankily prevent input button groups from wrapping with `white-space` and\n // `font-size` in combination with `inline-block` on buttons.\n font-size: 0;\n white-space: nowrap;\n\n // Negative margin for spacing, position for bringing hovered/focused/actived\n // element above the siblings.\n > .btn {\n position: relative;\n + .btn {\n margin-left: -1px;\n }\n // Bring the \"active\" button to the front\n &:hover,\n &:focus,\n &:active {\n z-index: 2;\n }\n }\n\n // Negative margin to only have a 1px border between the two\n &:first-child {\n > .btn,\n > .btn-group {\n margin-right: -1px;\n }\n }\n &:last-child {\n > .btn,\n > .btn-group {\n z-index: 2;\n margin-left: -1px;\n }\n }\n}\n","//\n// Navs\n// --------------------------------------------------\n\n\n// Base class\n// --------------------------------------------------\n\n.nav {\n margin-bottom: 0;\n padding-left: 0; // Override default ul/ol\n list-style: none;\n &:extend(.clearfix all);\n\n > li {\n position: relative;\n display: block;\n\n > a {\n position: relative;\n display: block;\n padding: @nav-link-padding;\n &:hover,\n &:focus {\n text-decoration: none;\n background-color: @nav-link-hover-bg;\n }\n }\n\n // Disabled state sets text to gray and nukes hover/tab effects\n &.disabled > a {\n color: @nav-disabled-link-color;\n\n &:hover,\n &:focus {\n color: @nav-disabled-link-hover-color;\n text-decoration: none;\n background-color: transparent;\n cursor: @cursor-disabled;\n }\n }\n }\n\n // Open dropdowns\n .open > a {\n &,\n &:hover,\n &:focus {\n background-color: @nav-link-hover-bg;\n border-color: @link-color;\n }\n }\n\n // Nav dividers (deprecated with v3.0.1)\n //\n // This should have been removed in v3 with the dropping of `.nav-list`, but\n // we missed it. We don't currently support this anywhere, but in the interest\n // of maintaining backward compatibility in case you use it, it's deprecated.\n .nav-divider {\n .nav-divider();\n }\n\n // Prevent IE8 from misplacing imgs\n //\n // See https://github.com/h5bp/html5-boilerplate/issues/984#issuecomment-3985989\n > li > a > img {\n max-width: none;\n }\n}\n\n\n// Tabs\n// -------------------------\n\n// Give the tabs something to sit on\n.nav-tabs {\n border-bottom: 1px solid @nav-tabs-border-color;\n > li {\n float: left;\n // Make the list-items overlay the bottom border\n margin-bottom: -1px;\n\n // Actual tabs (as links)\n > a {\n margin-right: 2px;\n line-height: @line-height-base;\n border: 1px solid transparent;\n border-radius: @border-radius-base @border-radius-base 0 0;\n &:hover {\n border-color: @nav-tabs-link-hover-border-color @nav-tabs-link-hover-border-color @nav-tabs-border-color;\n }\n }\n\n // Active state, and its :hover to override normal :hover\n &.active > a {\n &,\n &:hover,\n &:focus {\n color: @nav-tabs-active-link-hover-color;\n background-color: @nav-tabs-active-link-hover-bg;\n border: 1px solid @nav-tabs-active-link-hover-border-color;\n border-bottom-color: transparent;\n cursor: default;\n }\n }\n }\n // pulling this in mainly for less shorthand\n &.nav-justified {\n .nav-justified();\n .nav-tabs-justified();\n }\n}\n\n\n// Pills\n// -------------------------\n.nav-pills {\n > li {\n float: left;\n\n // Links rendered as pills\n > a {\n border-radius: @nav-pills-border-radius;\n }\n + li {\n margin-left: 2px;\n }\n\n // Active state\n &.active > a {\n &,\n &:hover,\n &:focus {\n color: @nav-pills-active-link-hover-color;\n background-color: @nav-pills-active-link-hover-bg;\n }\n }\n }\n}\n\n\n// Stacked pills\n.nav-stacked {\n > li {\n float: none;\n + li {\n margin-top: 2px;\n margin-left: 0; // no need for this gap between nav items\n }\n }\n}\n\n\n// Nav variations\n// --------------------------------------------------\n\n// Justified nav links\n// -------------------------\n\n.nav-justified {\n width: 100%;\n\n > li {\n float: none;\n > a {\n text-align: center;\n margin-bottom: 5px;\n }\n }\n\n > .dropdown .dropdown-menu {\n top: auto;\n left: auto;\n }\n\n @media (min-width: @screen-sm-min) {\n > li {\n display: table-cell;\n width: 1%;\n > a {\n margin-bottom: 0;\n }\n }\n }\n}\n\n// Move borders to anchors instead of bottom of list\n//\n// Mixin for adding on top the shared `.nav-justified` styles for our tabs\n.nav-tabs-justified {\n border-bottom: 0;\n\n > li > a {\n // Override margin from .nav-tabs\n margin-right: 0;\n border-radius: @border-radius-base;\n }\n\n > .active > a,\n > .active > a:hover,\n > .active > a:focus {\n border: 1px solid @nav-tabs-justified-link-border-color;\n }\n\n @media (min-width: @screen-sm-min) {\n > li > a {\n border-bottom: 1px solid @nav-tabs-justified-link-border-color;\n border-radius: @border-radius-base @border-radius-base 0 0;\n }\n > .active > a,\n > .active > a:hover,\n > .active > a:focus {\n border-bottom-color: @nav-tabs-justified-active-link-border-color;\n }\n }\n}\n\n\n// Tabbable tabs\n// -------------------------\n\n// Hide tabbable panes to start, show them when `.active`\n.tab-content {\n > .tab-pane {\n display: none;\n }\n > .active {\n display: block;\n }\n}\n\n\n// Dropdowns\n// -------------------------\n\n// Specific dropdowns\n.nav-tabs .dropdown-menu {\n // make dropdown border overlap tab border\n margin-top: -1px;\n // Remove the top rounded corners here since there is a hard edge above the menu\n .border-top-radius(0);\n}\n","//\n// Navbars\n// --------------------------------------------------\n\n\n// Wrapper and base class\n//\n// Provide a static navbar from which we expand to create full-width, fixed, and\n// other navbar variations.\n\n.navbar {\n position: relative;\n min-height: @navbar-height; // Ensure a navbar always shows (e.g., without a .navbar-brand in collapsed mode)\n margin-bottom: @navbar-margin-bottom;\n border: 1px solid transparent;\n\n // Prevent floats from breaking the navbar\n &:extend(.clearfix all);\n\n @media (min-width: @grid-float-breakpoint) {\n border-radius: @navbar-border-radius;\n }\n}\n\n\n// Navbar heading\n//\n// Groups `.navbar-brand` and `.navbar-toggle` into a single component for easy\n// styling of responsive aspects.\n\n.navbar-header {\n &:extend(.clearfix all);\n\n @media (min-width: @grid-float-breakpoint) {\n float: left;\n }\n}\n\n\n// Navbar collapse (body)\n//\n// Group your navbar content into this for easy collapsing and expanding across\n// various device sizes. By default, this content is collapsed when <768px, but\n// will expand past that for a horizontal display.\n//\n// To start (on mobile devices) the navbar links, forms, and buttons are stacked\n// vertically and include a `max-height` to overflow in case you have too much\n// content for the user's viewport.\n\n.navbar-collapse {\n overflow-x: visible;\n padding-right: @navbar-padding-horizontal;\n padding-left: @navbar-padding-horizontal;\n border-top: 1px solid transparent;\n box-shadow: inset 0 1px 0 rgba(255,255,255,.1);\n &:extend(.clearfix all);\n -webkit-overflow-scrolling: touch;\n\n &.in {\n overflow-y: auto;\n }\n\n @media (min-width: @grid-float-breakpoint) {\n width: auto;\n border-top: 0;\n box-shadow: none;\n\n &.collapse {\n display: block !important;\n height: auto !important;\n padding-bottom: 0; // Override default setting\n overflow: visible !important;\n }\n\n &.in {\n overflow-y: visible;\n }\n\n // Undo the collapse side padding for navbars with containers to ensure\n // alignment of right-aligned contents.\n .navbar-fixed-top &,\n .navbar-static-top &,\n .navbar-fixed-bottom & {\n padding-left: 0;\n padding-right: 0;\n }\n }\n}\n\n.navbar-fixed-top,\n.navbar-fixed-bottom {\n .navbar-collapse {\n max-height: @navbar-collapse-max-height;\n\n @media (max-device-width: @screen-xs-min) and (orientation: landscape) {\n max-height: 200px;\n }\n }\n}\n\n\n// Both navbar header and collapse\n//\n// When a container is present, change the behavior of the header and collapse.\n\n.container,\n.container-fluid {\n > .navbar-header,\n > .navbar-collapse {\n margin-right: -@navbar-padding-horizontal;\n margin-left: -@navbar-padding-horizontal;\n\n @media (min-width: @grid-float-breakpoint) {\n margin-right: 0;\n margin-left: 0;\n }\n }\n}\n\n\n//\n// Navbar alignment options\n//\n// Display the navbar across the entirety of the page or fixed it to the top or\n// bottom of the page.\n\n// Static top (unfixed, but 100% wide) navbar\n.navbar-static-top {\n z-index: @zindex-navbar;\n border-width: 0 0 1px;\n\n @media (min-width: @grid-float-breakpoint) {\n border-radius: 0;\n }\n}\n\n// Fix the top/bottom navbars when screen real estate supports it\n.navbar-fixed-top,\n.navbar-fixed-bottom {\n position: fixed;\n right: 0;\n left: 0;\n z-index: @zindex-navbar-fixed;\n\n // Undo the rounded corners\n @media (min-width: @grid-float-breakpoint) {\n border-radius: 0;\n }\n}\n.navbar-fixed-top {\n top: 0;\n border-width: 0 0 1px;\n}\n.navbar-fixed-bottom {\n bottom: 0;\n margin-bottom: 0; // override .navbar defaults\n border-width: 1px 0 0;\n}\n\n\n// Brand/project name\n\n.navbar-brand {\n float: left;\n padding: @navbar-padding-vertical @navbar-padding-horizontal;\n font-size: @font-size-large;\n line-height: @line-height-computed;\n height: @navbar-height;\n\n &:hover,\n &:focus {\n text-decoration: none;\n }\n\n > img {\n display: block;\n }\n\n @media (min-width: @grid-float-breakpoint) {\n .navbar > .container &,\n .navbar > .container-fluid & {\n margin-left: -@navbar-padding-horizontal;\n }\n }\n}\n\n\n// Navbar toggle\n//\n// Custom button for toggling the `.navbar-collapse`, powered by the collapse\n// JavaScript plugin.\n\n.navbar-toggle {\n position: relative;\n float: right;\n margin-right: @navbar-padding-horizontal;\n padding: 9px 10px;\n .navbar-vertical-align(34px);\n background-color: transparent;\n background-image: none; // Reset unusual Firefox-on-Android default style; see https://github.com/necolas/normalize.css/issues/214\n border: 1px solid transparent;\n border-radius: @border-radius-base;\n\n // We remove the `outline` here, but later compensate by attaching `:hover`\n // styles to `:focus`.\n &:focus {\n outline: 0;\n }\n\n // Bars\n .icon-bar {\n display: block;\n width: 22px;\n height: 2px;\n border-radius: 1px;\n }\n .icon-bar + .icon-bar {\n margin-top: 4px;\n }\n\n @media (min-width: @grid-float-breakpoint) {\n display: none;\n }\n}\n\n\n// Navbar nav links\n//\n// Builds on top of the `.nav` components with its own modifier class to make\n// the nav the full height of the horizontal nav (above 768px).\n\n.navbar-nav {\n margin: (@navbar-padding-vertical / 2) -@navbar-padding-horizontal;\n\n > li > a {\n padding-top: 10px;\n padding-bottom: 10px;\n line-height: @line-height-computed;\n }\n\n @media (max-width: @grid-float-breakpoint-max) {\n // Dropdowns get custom display when collapsed\n .open .dropdown-menu {\n position: static;\n float: none;\n width: auto;\n margin-top: 0;\n background-color: transparent;\n border: 0;\n box-shadow: none;\n > li > a,\n .dropdown-header {\n padding: 5px 15px 5px 25px;\n }\n > li > a {\n line-height: @line-height-computed;\n &:hover,\n &:focus {\n background-image: none;\n }\n }\n }\n }\n\n // Uncollapse the nav\n @media (min-width: @grid-float-breakpoint) {\n float: left;\n margin: 0;\n\n > li {\n float: left;\n > a {\n padding-top: @navbar-padding-vertical;\n padding-bottom: @navbar-padding-vertical;\n }\n }\n }\n}\n\n\n// Navbar form\n//\n// Extension of the `.form-inline` with some extra flavor for optimum display in\n// our navbars.\n\n.navbar-form {\n margin-left: -@navbar-padding-horizontal;\n margin-right: -@navbar-padding-horizontal;\n padding: 10px @navbar-padding-horizontal;\n border-top: 1px solid transparent;\n border-bottom: 1px solid transparent;\n @shadow: inset 0 1px 0 rgba(255,255,255,.1), 0 1px 0 rgba(255,255,255,.1);\n .box-shadow(@shadow);\n\n // Mixin behavior for optimum display\n .form-inline();\n\n .form-group {\n @media (max-width: @grid-float-breakpoint-max) {\n margin-bottom: 5px;\n\n &:last-child {\n margin-bottom: 0;\n }\n }\n }\n\n // Vertically center in expanded, horizontal navbar\n .navbar-vertical-align(@input-height-base);\n\n // Undo 100% width for pull classes\n @media (min-width: @grid-float-breakpoint) {\n width: auto;\n border: 0;\n margin-left: 0;\n margin-right: 0;\n padding-top: 0;\n padding-bottom: 0;\n .box-shadow(none);\n }\n}\n\n\n// Dropdown menus\n\n// Menu position and menu carets\n.navbar-nav > li > .dropdown-menu {\n margin-top: 0;\n .border-top-radius(0);\n}\n// Menu position and menu caret support for dropups via extra dropup class\n.navbar-fixed-bottom .navbar-nav > li > .dropdown-menu {\n margin-bottom: 0;\n .border-top-radius(@navbar-border-radius);\n .border-bottom-radius(0);\n}\n\n\n// Buttons in navbars\n//\n// Vertically center a button within a navbar (when *not* in a form).\n\n.navbar-btn {\n .navbar-vertical-align(@input-height-base);\n\n &.btn-sm {\n .navbar-vertical-align(@input-height-small);\n }\n &.btn-xs {\n .navbar-vertical-align(22);\n }\n}\n\n\n// Text in navbars\n//\n// Add a class to make any element properly align itself vertically within the navbars.\n\n.navbar-text {\n .navbar-vertical-align(@line-height-computed);\n\n @media (min-width: @grid-float-breakpoint) {\n float: left;\n margin-left: @navbar-padding-horizontal;\n margin-right: @navbar-padding-horizontal;\n }\n}\n\n\n// Component alignment\n//\n// Repurpose the pull utilities as their own navbar utilities to avoid specificity\n// issues with parents and chaining. Only do this when the navbar is uncollapsed\n// though so that navbar contents properly stack and align in mobile.\n//\n// Declared after the navbar components to ensure more specificity on the margins.\n\n@media (min-width: @grid-float-breakpoint) {\n .navbar-left { .pull-left(); }\n .navbar-right {\n .pull-right();\n margin-right: -@navbar-padding-horizontal;\n\n ~ .navbar-right {\n margin-right: 0;\n }\n }\n}\n\n\n// Alternate navbars\n// --------------------------------------------------\n\n// Default navbar\n.navbar-default {\n background-color: @navbar-default-bg;\n border-color: @navbar-default-border;\n\n .navbar-brand {\n color: @navbar-default-brand-color;\n &:hover,\n &:focus {\n color: @navbar-default-brand-hover-color;\n background-color: @navbar-default-brand-hover-bg;\n }\n }\n\n .navbar-text {\n color: @navbar-default-color;\n }\n\n .navbar-nav {\n > li > a {\n color: @navbar-default-link-color;\n\n &:hover,\n &:focus {\n color: @navbar-default-link-hover-color;\n background-color: @navbar-default-link-hover-bg;\n }\n }\n > .active > a {\n &,\n &:hover,\n &:focus {\n color: @navbar-default-link-active-color;\n background-color: @navbar-default-link-active-bg;\n }\n }\n > .disabled > a {\n &,\n &:hover,\n &:focus {\n color: @navbar-default-link-disabled-color;\n background-color: @navbar-default-link-disabled-bg;\n }\n }\n }\n\n .navbar-toggle {\n border-color: @navbar-default-toggle-border-color;\n &:hover,\n &:focus {\n background-color: @navbar-default-toggle-hover-bg;\n }\n .icon-bar {\n background-color: @navbar-default-toggle-icon-bar-bg;\n }\n }\n\n .navbar-collapse,\n .navbar-form {\n border-color: @navbar-default-border;\n }\n\n // Dropdown menu items\n .navbar-nav {\n // Remove background color from open dropdown\n > .open > a {\n &,\n &:hover,\n &:focus {\n background-color: @navbar-default-link-active-bg;\n color: @navbar-default-link-active-color;\n }\n }\n\n @media (max-width: @grid-float-breakpoint-max) {\n // Dropdowns get custom display when collapsed\n .open .dropdown-menu {\n > li > a {\n color: @navbar-default-link-color;\n &:hover,\n &:focus {\n color: @navbar-default-link-hover-color;\n background-color: @navbar-default-link-hover-bg;\n }\n }\n > .active > a {\n &,\n &:hover,\n &:focus {\n color: @navbar-default-link-active-color;\n background-color: @navbar-default-link-active-bg;\n }\n }\n > .disabled > a {\n &,\n &:hover,\n &:focus {\n color: @navbar-default-link-disabled-color;\n background-color: @navbar-default-link-disabled-bg;\n }\n }\n }\n }\n }\n\n\n // Links in navbars\n //\n // Add a class to ensure links outside the navbar nav are colored correctly.\n\n .navbar-link {\n color: @navbar-default-link-color;\n &:hover {\n color: @navbar-default-link-hover-color;\n }\n }\n\n .btn-link {\n color: @navbar-default-link-color;\n &:hover,\n &:focus {\n color: @navbar-default-link-hover-color;\n }\n &[disabled],\n fieldset[disabled] & {\n &:hover,\n &:focus {\n color: @navbar-default-link-disabled-color;\n }\n }\n }\n}\n\n// Inverse navbar\n\n.navbar-inverse {\n background-color: @navbar-inverse-bg;\n border-color: @navbar-inverse-border;\n\n .navbar-brand {\n color: @navbar-inverse-brand-color;\n &:hover,\n &:focus {\n color: @navbar-inverse-brand-hover-color;\n background-color: @navbar-inverse-brand-hover-bg;\n }\n }\n\n .navbar-text {\n color: @navbar-inverse-color;\n }\n\n .navbar-nav {\n > li > a {\n color: @navbar-inverse-link-color;\n\n &:hover,\n &:focus {\n color: @navbar-inverse-link-hover-color;\n background-color: @navbar-inverse-link-hover-bg;\n }\n }\n > .active > a {\n &,\n &:hover,\n &:focus {\n color: @navbar-inverse-link-active-color;\n background-color: @navbar-inverse-link-active-bg;\n }\n }\n > .disabled > a {\n &,\n &:hover,\n &:focus {\n color: @navbar-inverse-link-disabled-color;\n background-color: @navbar-inverse-link-disabled-bg;\n }\n }\n }\n\n // Darken the responsive nav toggle\n .navbar-toggle {\n border-color: @navbar-inverse-toggle-border-color;\n &:hover,\n &:focus {\n background-color: @navbar-inverse-toggle-hover-bg;\n }\n .icon-bar {\n background-color: @navbar-inverse-toggle-icon-bar-bg;\n }\n }\n\n .navbar-collapse,\n .navbar-form {\n border-color: darken(@navbar-inverse-bg, 7%);\n }\n\n // Dropdowns\n .navbar-nav {\n > .open > a {\n &,\n &:hover,\n &:focus {\n background-color: @navbar-inverse-link-active-bg;\n color: @navbar-inverse-link-active-color;\n }\n }\n\n @media (max-width: @grid-float-breakpoint-max) {\n // Dropdowns get custom display\n .open .dropdown-menu {\n > .dropdown-header {\n border-color: @navbar-inverse-border;\n }\n .divider {\n background-color: @navbar-inverse-border;\n }\n > li > a {\n color: @navbar-inverse-link-color;\n &:hover,\n &:focus {\n color: @navbar-inverse-link-hover-color;\n background-color: @navbar-inverse-link-hover-bg;\n }\n }\n > .active > a {\n &,\n &:hover,\n &:focus {\n color: @navbar-inverse-link-active-color;\n background-color: @navbar-inverse-link-active-bg;\n }\n }\n > .disabled > a {\n &,\n &:hover,\n &:focus {\n color: @navbar-inverse-link-disabled-color;\n background-color: @navbar-inverse-link-disabled-bg;\n }\n }\n }\n }\n }\n\n .navbar-link {\n color: @navbar-inverse-link-color;\n &:hover {\n color: @navbar-inverse-link-hover-color;\n }\n }\n\n .btn-link {\n color: @navbar-inverse-link-color;\n &:hover,\n &:focus {\n color: @navbar-inverse-link-hover-color;\n }\n &[disabled],\n fieldset[disabled] & {\n &:hover,\n &:focus {\n color: @navbar-inverse-link-disabled-color;\n }\n }\n }\n}\n","// Navbar vertical align\n//\n// Vertically center elements in the navbar.\n// Example: an element has a height of 30px, so write out `.navbar-vertical-align(30px);` to calculate the appropriate top margin.\n\n.navbar-vertical-align(@element-height) {\n margin-top: ((@navbar-height - @element-height) / 2);\n margin-bottom: ((@navbar-height - @element-height) / 2);\n}\n","//\n// Utility classes\n// --------------------------------------------------\n\n\n// Floats\n// -------------------------\n\n.clearfix {\n .clearfix();\n}\n.center-block {\n .center-block();\n}\n.pull-right {\n float: right !important;\n}\n.pull-left {\n float: left !important;\n}\n\n\n// Toggling content\n// -------------------------\n\n// Note: Deprecated .hide in favor of .hidden or .sr-only (as appropriate) in v3.0.1\n.hide {\n display: none !important;\n}\n.show {\n display: block !important;\n}\n.invisible {\n visibility: hidden;\n}\n.text-hide {\n .text-hide();\n}\n\n\n// Hide from screenreaders and browsers\n//\n// Credit: HTML5 Boilerplate\n\n.hidden {\n display: none !important;\n}\n\n\n// For Affix plugin\n// -------------------------\n\n.affix {\n position: fixed;\n}\n","//\n// Breadcrumbs\n// --------------------------------------------------\n\n\n.breadcrumb {\n padding: @breadcrumb-padding-vertical @breadcrumb-padding-horizontal;\n margin-bottom: @line-height-computed;\n list-style: none;\n background-color: @breadcrumb-bg;\n border-radius: @border-radius-base;\n\n > li {\n display: inline-block;\n\n + li:before {\n content: \"@{breadcrumb-separator}\\00a0\"; // Unicode space added since inline-block means non-collapsing white-space\n padding: 0 5px;\n color: @breadcrumb-color;\n }\n }\n\n > .active {\n color: @breadcrumb-active-color;\n }\n}\n","//\n// Pagination (multiple pages)\n// --------------------------------------------------\n.pagination {\n display: inline-block;\n padding-left: 0;\n margin: @line-height-computed 0;\n border-radius: @border-radius-base;\n\n > li {\n display: inline; // Remove list-style and block-level defaults\n > a,\n > span {\n position: relative;\n float: left; // Collapse white-space\n padding: @padding-base-vertical @padding-base-horizontal;\n line-height: @line-height-base;\n text-decoration: none;\n color: @pagination-color;\n background-color: @pagination-bg;\n border: 1px solid @pagination-border;\n margin-left: -1px;\n }\n &:first-child {\n > a,\n > span {\n margin-left: 0;\n .border-left-radius(@border-radius-base);\n }\n }\n &:last-child {\n > a,\n > span {\n .border-right-radius(@border-radius-base);\n }\n }\n }\n\n > li > a,\n > li > span {\n &:hover,\n &:focus {\n z-index: 2;\n color: @pagination-hover-color;\n background-color: @pagination-hover-bg;\n border-color: @pagination-hover-border;\n }\n }\n\n > .active > a,\n > .active > span {\n &,\n &:hover,\n &:focus {\n z-index: 3;\n color: @pagination-active-color;\n background-color: @pagination-active-bg;\n border-color: @pagination-active-border;\n cursor: default;\n }\n }\n\n > .disabled {\n > span,\n > span:hover,\n > span:focus,\n > a,\n > a:hover,\n > a:focus {\n color: @pagination-disabled-color;\n background-color: @pagination-disabled-bg;\n border-color: @pagination-disabled-border;\n cursor: @cursor-disabled;\n }\n }\n}\n\n// Sizing\n// --------------------------------------------------\n\n// Large\n.pagination-lg {\n .pagination-size(@padding-large-vertical; @padding-large-horizontal; @font-size-large; @line-height-large; @border-radius-large);\n}\n\n// Small\n.pagination-sm {\n .pagination-size(@padding-small-vertical; @padding-small-horizontal; @font-size-small; @line-height-small; @border-radius-small);\n}\n","// Pagination\n\n.pagination-size(@padding-vertical; @padding-horizontal; @font-size; @line-height; @border-radius) {\n > li {\n > a,\n > span {\n padding: @padding-vertical @padding-horizontal;\n font-size: @font-size;\n line-height: @line-height;\n }\n &:first-child {\n > a,\n > span {\n .border-left-radius(@border-radius);\n }\n }\n &:last-child {\n > a,\n > span {\n .border-right-radius(@border-radius);\n }\n }\n }\n}\n","//\n// Pager pagination\n// --------------------------------------------------\n\n\n.pager {\n padding-left: 0;\n margin: @line-height-computed 0;\n list-style: none;\n text-align: center;\n &:extend(.clearfix all);\n li {\n display: inline;\n > a,\n > span {\n display: inline-block;\n padding: 5px 14px;\n background-color: @pager-bg;\n border: 1px solid @pager-border;\n border-radius: @pager-border-radius;\n }\n\n > a:hover,\n > a:focus {\n text-decoration: none;\n background-color: @pager-hover-bg;\n }\n }\n\n .next {\n > a,\n > span {\n float: right;\n }\n }\n\n .previous {\n > a,\n > span {\n float: left;\n }\n }\n\n .disabled {\n > a,\n > a:hover,\n > a:focus,\n > span {\n color: @pager-disabled-color;\n background-color: @pager-bg;\n cursor: @cursor-disabled;\n }\n }\n}\n","//\n// Labels\n// --------------------------------------------------\n\n.label {\n display: inline;\n padding: .2em .6em .3em;\n font-size: 75%;\n font-weight: bold;\n line-height: 1;\n color: @label-color;\n text-align: center;\n white-space: nowrap;\n vertical-align: baseline;\n border-radius: .25em;\n\n // Add hover effects, but only for links\n a& {\n &:hover,\n &:focus {\n color: @label-link-hover-color;\n text-decoration: none;\n cursor: pointer;\n }\n }\n\n // Empty labels collapse automatically (not available in IE8)\n &:empty {\n display: none;\n }\n\n // Quick fix for labels in buttons\n .btn & {\n position: relative;\n top: -1px;\n }\n}\n\n// Colors\n// Contextual variations (linked labels get darker on :hover)\n\n.label-default {\n .label-variant(@label-default-bg);\n}\n\n.label-primary {\n .label-variant(@label-primary-bg);\n}\n\n.label-success {\n .label-variant(@label-success-bg);\n}\n\n.label-info {\n .label-variant(@label-info-bg);\n}\n\n.label-warning {\n .label-variant(@label-warning-bg);\n}\n\n.label-danger {\n .label-variant(@label-danger-bg);\n}\n","// Labels\n\n.label-variant(@color) {\n background-color: @color;\n\n &[href] {\n &:hover,\n &:focus {\n background-color: darken(@color, 10%);\n }\n }\n}\n","//\n// Badges\n// --------------------------------------------------\n\n\n// Base class\n.badge {\n display: inline-block;\n min-width: 10px;\n padding: 3px 7px;\n font-size: @font-size-small;\n font-weight: @badge-font-weight;\n color: @badge-color;\n line-height: @badge-line-height;\n vertical-align: middle;\n white-space: nowrap;\n text-align: center;\n background-color: @badge-bg;\n border-radius: @badge-border-radius;\n\n // Empty badges collapse automatically (not available in IE8)\n &:empty {\n display: none;\n }\n\n // Quick fix for badges in buttons\n .btn & {\n position: relative;\n top: -1px;\n }\n\n .btn-xs &,\n .btn-group-xs > .btn & {\n top: 0;\n padding: 1px 5px;\n }\n\n // Hover state, but only for links\n a& {\n &:hover,\n &:focus {\n color: @badge-link-hover-color;\n text-decoration: none;\n cursor: pointer;\n }\n }\n\n // Account for badges in navs\n .list-group-item.active > &,\n .nav-pills > .active > a > & {\n color: @badge-active-color;\n background-color: @badge-active-bg;\n }\n\n .list-group-item > & {\n float: right;\n }\n\n .list-group-item > & + & {\n margin-right: 5px;\n }\n\n .nav-pills > li > a > & {\n margin-left: 3px;\n }\n}\n","//\n// Jumbotron\n// --------------------------------------------------\n\n\n.jumbotron {\n padding-top: @jumbotron-padding;\n padding-bottom: @jumbotron-padding;\n margin-bottom: @jumbotron-padding;\n color: @jumbotron-color;\n background-color: @jumbotron-bg;\n\n h1,\n .h1 {\n color: @jumbotron-heading-color;\n }\n\n p {\n margin-bottom: (@jumbotron-padding / 2);\n font-size: @jumbotron-font-size;\n font-weight: 200;\n }\n\n > hr {\n border-top-color: darken(@jumbotron-bg, 10%);\n }\n\n .container &,\n .container-fluid & {\n border-radius: @border-radius-large; // Only round corners at higher resolutions if contained in a container\n padding-left: (@grid-gutter-width / 2);\n padding-right: (@grid-gutter-width / 2);\n }\n\n .container {\n max-width: 100%;\n }\n\n @media screen and (min-width: @screen-sm-min) {\n padding-top: (@jumbotron-padding * 1.6);\n padding-bottom: (@jumbotron-padding * 1.6);\n\n .container &,\n .container-fluid & {\n padding-left: (@jumbotron-padding * 2);\n padding-right: (@jumbotron-padding * 2);\n }\n\n h1,\n .h1 {\n font-size: @jumbotron-heading-font-size;\n }\n }\n}\n","//\n// Thumbnails\n// --------------------------------------------------\n\n\n// Mixin and adjust the regular image class\n.thumbnail {\n display: block;\n padding: @thumbnail-padding;\n margin-bottom: @line-height-computed;\n line-height: @line-height-base;\n background-color: @thumbnail-bg;\n border: 1px solid @thumbnail-border;\n border-radius: @thumbnail-border-radius;\n .transition(border .2s ease-in-out);\n\n > img,\n a > img {\n &:extend(.img-responsive);\n margin-left: auto;\n margin-right: auto;\n }\n\n // Add a hover state for linked versions only\n a&:hover,\n a&:focus,\n a&.active {\n border-color: @link-color;\n }\n\n // Image captions\n .caption {\n padding: @thumbnail-caption-padding;\n color: @thumbnail-caption-color;\n }\n}\n","//\n// Alerts\n// --------------------------------------------------\n\n\n// Base styles\n// -------------------------\n\n.alert {\n padding: @alert-padding;\n margin-bottom: @line-height-computed;\n border: 1px solid transparent;\n border-radius: @alert-border-radius;\n\n // Headings for larger alerts\n h4 {\n margin-top: 0;\n // Specified for the h4 to prevent conflicts of changing @headings-color\n color: inherit;\n }\n\n // Provide class for links that match alerts\n .alert-link {\n font-weight: @alert-link-font-weight;\n }\n\n // Improve alignment and spacing of inner content\n > p,\n > ul {\n margin-bottom: 0;\n }\n\n > p + p {\n margin-top: 5px;\n }\n}\n\n// Dismissible alerts\n//\n// Expand the right padding and account for the close button's positioning.\n\n.alert-dismissable, // The misspelled .alert-dismissable was deprecated in 3.2.0.\n.alert-dismissible {\n padding-right: (@alert-padding + 20);\n\n // Adjust close link position\n .close {\n position: relative;\n top: -2px;\n right: -21px;\n color: inherit;\n }\n}\n\n// Alternate styles\n//\n// Generate contextual modifier classes for colorizing the alert.\n\n.alert-success {\n .alert-variant(@alert-success-bg; @alert-success-border; @alert-success-text);\n}\n\n.alert-info {\n .alert-variant(@alert-info-bg; @alert-info-border; @alert-info-text);\n}\n\n.alert-warning {\n .alert-variant(@alert-warning-bg; @alert-warning-border; @alert-warning-text);\n}\n\n.alert-danger {\n .alert-variant(@alert-danger-bg; @alert-danger-border; @alert-danger-text);\n}\n","// Alerts\n\n.alert-variant(@background; @border; @text-color) {\n background-color: @background;\n border-color: @border;\n color: @text-color;\n\n hr {\n border-top-color: darken(@border, 5%);\n }\n .alert-link {\n color: darken(@text-color, 10%);\n }\n}\n","//\n// Progress bars\n// --------------------------------------------------\n\n\n// Bar animations\n// -------------------------\n\n// WebKit\n@-webkit-keyframes progress-bar-stripes {\n from { background-position: 40px 0; }\n to { background-position: 0 0; }\n}\n\n// Spec and IE10+\n@keyframes progress-bar-stripes {\n from { background-position: 40px 0; }\n to { background-position: 0 0; }\n}\n\n\n// Bar itself\n// -------------------------\n\n// Outer container\n.progress {\n overflow: hidden;\n height: @line-height-computed;\n margin-bottom: @line-height-computed;\n background-color: @progress-bg;\n border-radius: @progress-border-radius;\n .box-shadow(inset 0 1px 2px rgba(0,0,0,.1));\n}\n\n// Bar of progress\n.progress-bar {\n float: left;\n width: 0%;\n height: 100%;\n font-size: @font-size-small;\n line-height: @line-height-computed;\n color: @progress-bar-color;\n text-align: center;\n background-color: @progress-bar-bg;\n .box-shadow(inset 0 -1px 0 rgba(0,0,0,.15));\n .transition(width .6s ease);\n}\n\n// Striped bars\n//\n// `.progress-striped .progress-bar` is deprecated as of v3.2.0 in favor of the\n// `.progress-bar-striped` class, which you just add to an existing\n// `.progress-bar`.\n.progress-striped .progress-bar,\n.progress-bar-striped {\n #gradient > .striped();\n background-size: 40px 40px;\n}\n\n// Call animation for the active one\n//\n// `.progress.active .progress-bar` is deprecated as of v3.2.0 in favor of the\n// `.progress-bar.active` approach.\n.progress.active .progress-bar,\n.progress-bar.active {\n .animation(progress-bar-stripes 2s linear infinite);\n}\n\n\n// Variations\n// -------------------------\n\n.progress-bar-success {\n .progress-bar-variant(@progress-bar-success-bg);\n}\n\n.progress-bar-info {\n .progress-bar-variant(@progress-bar-info-bg);\n}\n\n.progress-bar-warning {\n .progress-bar-variant(@progress-bar-warning-bg);\n}\n\n.progress-bar-danger {\n .progress-bar-variant(@progress-bar-danger-bg);\n}\n","// Gradients\n\n#gradient {\n\n // Horizontal gradient, from left to right\n //\n // Creates two color stops, start and end, by specifying a color and position for each color stop.\n // Color stops are not available in IE9 and below.\n .horizontal(@start-color: #555; @end-color: #333; @start-percent: 0%; @end-percent: 100%) {\n background-image: -webkit-linear-gradient(left, @start-color @start-percent, @end-color @end-percent); // Safari 5.1-6, Chrome 10+\n background-image: -o-linear-gradient(left, @start-color @start-percent, @end-color @end-percent); // Opera 12\n background-image: linear-gradient(to right, @start-color @start-percent, @end-color @end-percent); // Standard, IE10, Firefox 16+, Opera 12.10+, Safari 7+, Chrome 26+\n background-repeat: repeat-x;\n filter: e(%(\"progid:DXImageTransform.Microsoft.gradient(startColorstr='%d', endColorstr='%d', GradientType=1)\",argb(@start-color),argb(@end-color))); // IE9 and down\n }\n\n // Vertical gradient, from top to bottom\n //\n // Creates two color stops, start and end, by specifying a color and position for each color stop.\n // Color stops are not available in IE9 and below.\n .vertical(@start-color: #555; @end-color: #333; @start-percent: 0%; @end-percent: 100%) {\n background-image: -webkit-linear-gradient(top, @start-color @start-percent, @end-color @end-percent); // Safari 5.1-6, Chrome 10+\n background-image: -o-linear-gradient(top, @start-color @start-percent, @end-color @end-percent); // Opera 12\n background-image: linear-gradient(to bottom, @start-color @start-percent, @end-color @end-percent); // Standard, IE10, Firefox 16+, Opera 12.10+, Safari 7+, Chrome 26+\n background-repeat: repeat-x;\n filter: e(%(\"progid:DXImageTransform.Microsoft.gradient(startColorstr='%d', endColorstr='%d', GradientType=0)\",argb(@start-color),argb(@end-color))); // IE9 and down\n }\n\n .directional(@start-color: #555; @end-color: #333; @deg: 45deg) {\n background-repeat: repeat-x;\n background-image: -webkit-linear-gradient(@deg, @start-color, @end-color); // Safari 5.1-6, Chrome 10+\n background-image: -o-linear-gradient(@deg, @start-color, @end-color); // Opera 12\n background-image: linear-gradient(@deg, @start-color, @end-color); // Standard, IE10, Firefox 16+, Opera 12.10+, Safari 7+, Chrome 26+\n }\n .horizontal-three-colors(@start-color: #00b3ee; @mid-color: #7a43b6; @color-stop: 50%; @end-color: #c3325f) {\n background-image: -webkit-linear-gradient(left, @start-color, @mid-color @color-stop, @end-color);\n background-image: -o-linear-gradient(left, @start-color, @mid-color @color-stop, @end-color);\n background-image: linear-gradient(to right, @start-color, @mid-color @color-stop, @end-color);\n background-repeat: no-repeat;\n filter: e(%(\"progid:DXImageTransform.Microsoft.gradient(startColorstr='%d', endColorstr='%d', GradientType=1)\",argb(@start-color),argb(@end-color))); // IE9 and down, gets no color-stop at all for proper fallback\n }\n .vertical-three-colors(@start-color: #00b3ee; @mid-color: #7a43b6; @color-stop: 50%; @end-color: #c3325f) {\n background-image: -webkit-linear-gradient(@start-color, @mid-color @color-stop, @end-color);\n background-image: -o-linear-gradient(@start-color, @mid-color @color-stop, @end-color);\n background-image: linear-gradient(@start-color, @mid-color @color-stop, @end-color);\n background-repeat: no-repeat;\n filter: e(%(\"progid:DXImageTransform.Microsoft.gradient(startColorstr='%d', endColorstr='%d', GradientType=0)\",argb(@start-color),argb(@end-color))); // IE9 and down, gets no color-stop at all for proper fallback\n }\n .radial(@inner-color: #555; @outer-color: #333) {\n background-image: -webkit-radial-gradient(circle, @inner-color, @outer-color);\n background-image: radial-gradient(circle, @inner-color, @outer-color);\n background-repeat: no-repeat;\n }\n .striped(@color: rgba(255,255,255,.15); @angle: 45deg) {\n background-image: -webkit-linear-gradient(@angle, @color 25%, transparent 25%, transparent 50%, @color 50%, @color 75%, transparent 75%, transparent);\n background-image: -o-linear-gradient(@angle, @color 25%, transparent 25%, transparent 50%, @color 50%, @color 75%, transparent 75%, transparent);\n background-image: linear-gradient(@angle, @color 25%, transparent 25%, transparent 50%, @color 50%, @color 75%, transparent 75%, transparent);\n }\n}\n","// Progress bars\n\n.progress-bar-variant(@color) {\n background-color: @color;\n\n // Deprecated parent class requirement as of v3.2.0\n .progress-striped & {\n #gradient > .striped();\n }\n}\n",".media {\n // Proper spacing between instances of .media\n margin-top: 15px;\n\n &:first-child {\n margin-top: 0;\n }\n}\n\n.media,\n.media-body {\n zoom: 1;\n overflow: hidden;\n}\n\n.media-body {\n width: 10000px;\n}\n\n.media-object {\n display: block;\n\n // Fix collapse in webkit from max-width: 100% and display: table-cell.\n &.img-thumbnail {\n max-width: none;\n }\n}\n\n.media-right,\n.media > .pull-right {\n padding-left: 10px;\n}\n\n.media-left,\n.media > .pull-left {\n padding-right: 10px;\n}\n\n.media-left,\n.media-right,\n.media-body {\n display: table-cell;\n vertical-align: top;\n}\n\n.media-middle {\n vertical-align: middle;\n}\n\n.media-bottom {\n vertical-align: bottom;\n}\n\n// Reset margins on headings for tighter default spacing\n.media-heading {\n margin-top: 0;\n margin-bottom: 5px;\n}\n\n// Media list variation\n//\n// Undo default ul/ol styles\n.media-list {\n padding-left: 0;\n list-style: none;\n}\n","//\n// List groups\n// --------------------------------------------------\n\n\n// Base class\n//\n// Easily usable on <ul>, <ol>, or <div>.\n\n.list-group {\n // No need to set list-style: none; since .list-group-item is block level\n margin-bottom: 20px;\n padding-left: 0; // reset padding because ul and ol\n}\n\n\n// Individual list items\n//\n// Use on `li`s or `div`s within the `.list-group` parent.\n\n.list-group-item {\n position: relative;\n display: block;\n padding: 10px 15px;\n // Place the border on the list items and negative margin up for better styling\n margin-bottom: -1px;\n background-color: @list-group-bg;\n border: 1px solid @list-group-border;\n\n // Round the first and last items\n &:first-child {\n .border-top-radius(@list-group-border-radius);\n }\n &:last-child {\n margin-bottom: 0;\n .border-bottom-radius(@list-group-border-radius);\n }\n}\n\n\n// Interactive list items\n//\n// Use anchor or button elements instead of `li`s or `div`s to create interactive items.\n// Includes an extra `.active` modifier class for showing selected items.\n\na.list-group-item,\nbutton.list-group-item {\n color: @list-group-link-color;\n\n .list-group-item-heading {\n color: @list-group-link-heading-color;\n }\n\n // Hover state\n &:hover,\n &:focus {\n text-decoration: none;\n color: @list-group-link-hover-color;\n background-color: @list-group-hover-bg;\n }\n}\n\nbutton.list-group-item {\n width: 100%;\n text-align: left;\n}\n\n.list-group-item {\n // Disabled state\n &.disabled,\n &.disabled:hover,\n &.disabled:focus {\n background-color: @list-group-disabled-bg;\n color: @list-group-disabled-color;\n cursor: @cursor-disabled;\n\n // Force color to inherit for custom content\n .list-group-item-heading {\n color: inherit;\n }\n .list-group-item-text {\n color: @list-group-disabled-text-color;\n }\n }\n\n // Active class on item itself, not parent\n &.active,\n &.active:hover,\n &.active:focus {\n z-index: 2; // Place active items above their siblings for proper border styling\n color: @list-group-active-color;\n background-color: @list-group-active-bg;\n border-color: @list-group-active-border;\n\n // Force color to inherit for custom content\n .list-group-item-heading,\n .list-group-item-heading > small,\n .list-group-item-heading > .small {\n color: inherit;\n }\n .list-group-item-text {\n color: @list-group-active-text-color;\n }\n }\n}\n\n\n// Contextual variants\n//\n// Add modifier classes to change text and background color on individual items.\n// Organizationally, this must come after the `:hover` states.\n\n.list-group-item-variant(success; @state-success-bg; @state-success-text);\n.list-group-item-variant(info; @state-info-bg; @state-info-text);\n.list-group-item-variant(warning; @state-warning-bg; @state-warning-text);\n.list-group-item-variant(danger; @state-danger-bg; @state-danger-text);\n\n\n// Custom content options\n//\n// Extra classes for creating well-formatted content within `.list-group-item`s.\n\n.list-group-item-heading {\n margin-top: 0;\n margin-bottom: 5px;\n}\n.list-group-item-text {\n margin-bottom: 0;\n line-height: 1.3;\n}\n","// List Groups\n\n.list-group-item-variant(@state; @background; @color) {\n .list-group-item-@{state} {\n color: @color;\n background-color: @background;\n\n a&,\n button& {\n color: @color;\n\n .list-group-item-heading {\n color: inherit;\n }\n\n &:hover,\n &:focus {\n color: @color;\n background-color: darken(@background, 5%);\n }\n &.active,\n &.active:hover,\n &.active:focus {\n color: #fff;\n background-color: @color;\n border-color: @color;\n }\n }\n }\n}\n","//\n// Panels\n// --------------------------------------------------\n\n\n// Base class\n.panel {\n margin-bottom: @line-height-computed;\n background-color: @panel-bg;\n border: 1px solid transparent;\n border-radius: @panel-border-radius;\n .box-shadow(0 1px 1px rgba(0,0,0,.05));\n}\n\n// Panel contents\n.panel-body {\n padding: @panel-body-padding;\n &:extend(.clearfix all);\n}\n\n// Optional heading\n.panel-heading {\n padding: @panel-heading-padding;\n border-bottom: 1px solid transparent;\n .border-top-radius((@panel-border-radius - 1));\n\n > .dropdown .dropdown-toggle {\n color: inherit;\n }\n}\n\n// Within heading, strip any `h*` tag of its default margins for spacing.\n.panel-title {\n margin-top: 0;\n margin-bottom: 0;\n font-size: ceil((@font-size-base * 1.125));\n color: inherit;\n\n > a,\n > small,\n > .small,\n > small > a,\n > .small > a {\n color: inherit;\n }\n}\n\n// Optional footer (stays gray in every modifier class)\n.panel-footer {\n padding: @panel-footer-padding;\n background-color: @panel-footer-bg;\n border-top: 1px solid @panel-inner-border;\n .border-bottom-radius((@panel-border-radius - 1));\n}\n\n\n// List groups in panels\n//\n// By default, space out list group content from panel headings to account for\n// any kind of custom content between the two.\n\n.panel {\n > .list-group,\n > .panel-collapse > .list-group {\n margin-bottom: 0;\n\n .list-group-item {\n border-width: 1px 0;\n border-radius: 0;\n }\n\n // Add border top radius for first one\n &:first-child {\n .list-group-item:first-child {\n border-top: 0;\n .border-top-radius((@panel-border-radius - 1));\n }\n }\n\n // Add border bottom radius for last one\n &:last-child {\n .list-group-item:last-child {\n border-bottom: 0;\n .border-bottom-radius((@panel-border-radius - 1));\n }\n }\n }\n > .panel-heading + .panel-collapse > .list-group {\n .list-group-item:first-child {\n .border-top-radius(0);\n }\n }\n}\n// Collapse space between when there's no additional content.\n.panel-heading + .list-group {\n .list-group-item:first-child {\n border-top-width: 0;\n }\n}\n.list-group + .panel-footer {\n border-top-width: 0;\n}\n\n// Tables in panels\n//\n// Place a non-bordered `.table` within a panel (not within a `.panel-body`) and\n// watch it go full width.\n\n.panel {\n > .table,\n > .table-responsive > .table,\n > .panel-collapse > .table {\n margin-bottom: 0;\n\n caption {\n padding-left: @panel-body-padding;\n padding-right: @panel-body-padding;\n }\n }\n // Add border top radius for first one\n > .table:first-child,\n > .table-responsive:first-child > .table:first-child {\n .border-top-radius((@panel-border-radius - 1));\n\n > thead:first-child,\n > tbody:first-child {\n > tr:first-child {\n border-top-left-radius: (@panel-border-radius - 1);\n border-top-right-radius: (@panel-border-radius - 1);\n\n td:first-child,\n th:first-child {\n border-top-left-radius: (@panel-border-radius - 1);\n }\n td:last-child,\n th:last-child {\n border-top-right-radius: (@panel-border-radius - 1);\n }\n }\n }\n }\n // Add border bottom radius for last one\n > .table:last-child,\n > .table-responsive:last-child > .table:last-child {\n .border-bottom-radius((@panel-border-radius - 1));\n\n > tbody:last-child,\n > tfoot:last-child {\n > tr:last-child {\n border-bottom-left-radius: (@panel-border-radius - 1);\n border-bottom-right-radius: (@panel-border-radius - 1);\n\n td:first-child,\n th:first-child {\n border-bottom-left-radius: (@panel-border-radius - 1);\n }\n td:last-child,\n th:last-child {\n border-bottom-right-radius: (@panel-border-radius - 1);\n }\n }\n }\n }\n > .panel-body + .table,\n > .panel-body + .table-responsive,\n > .table + .panel-body,\n > .table-responsive + .panel-body {\n border-top: 1px solid @table-border-color;\n }\n > .table > tbody:first-child > tr:first-child th,\n > .table > tbody:first-child > tr:first-child td {\n border-top: 0;\n }\n > .table-bordered,\n > .table-responsive > .table-bordered {\n border: 0;\n > thead,\n > tbody,\n > tfoot {\n > tr {\n > th:first-child,\n > td:first-child {\n border-left: 0;\n }\n > th:last-child,\n > td:last-child {\n border-right: 0;\n }\n }\n }\n > thead,\n > tbody {\n > tr:first-child {\n > td,\n > th {\n border-bottom: 0;\n }\n }\n }\n > tbody,\n > tfoot {\n > tr:last-child {\n > td,\n > th {\n border-bottom: 0;\n }\n }\n }\n }\n > .table-responsive {\n border: 0;\n margin-bottom: 0;\n }\n}\n\n\n// Collapsible panels (aka, accordion)\n//\n// Wrap a series of panels in `.panel-group` to turn them into an accordion with\n// the help of our collapse JavaScript plugin.\n\n.panel-group {\n margin-bottom: @line-height-computed;\n\n // Tighten up margin so it's only between panels\n .panel {\n margin-bottom: 0;\n border-radius: @panel-border-radius;\n\n + .panel {\n margin-top: 5px;\n }\n }\n\n .panel-heading {\n border-bottom: 0;\n\n + .panel-collapse > .panel-body,\n + .panel-collapse > .list-group {\n border-top: 1px solid @panel-inner-border;\n }\n }\n\n .panel-footer {\n border-top: 0;\n + .panel-collapse .panel-body {\n border-bottom: 1px solid @panel-inner-border;\n }\n }\n}\n\n\n// Contextual variations\n.panel-default {\n .panel-variant(@panel-default-border; @panel-default-text; @panel-default-heading-bg; @panel-default-border);\n}\n.panel-primary {\n .panel-variant(@panel-primary-border; @panel-primary-text; @panel-primary-heading-bg; @panel-primary-border);\n}\n.panel-success {\n .panel-variant(@panel-success-border; @panel-success-text; @panel-success-heading-bg; @panel-success-border);\n}\n.panel-info {\n .panel-variant(@panel-info-border; @panel-info-text; @panel-info-heading-bg; @panel-info-border);\n}\n.panel-warning {\n .panel-variant(@panel-warning-border; @panel-warning-text; @panel-warning-heading-bg; @panel-warning-border);\n}\n.panel-danger {\n .panel-variant(@panel-danger-border; @panel-danger-text; @panel-danger-heading-bg; @panel-danger-border);\n}\n","// Panels\n\n.panel-variant(@border; @heading-text-color; @heading-bg-color; @heading-border) {\n border-color: @border;\n\n & > .panel-heading {\n color: @heading-text-color;\n background-color: @heading-bg-color;\n border-color: @heading-border;\n\n + .panel-collapse > .panel-body {\n border-top-color: @border;\n }\n .badge {\n color: @heading-bg-color;\n background-color: @heading-text-color;\n }\n }\n & > .panel-footer {\n + .panel-collapse > .panel-body {\n border-bottom-color: @border;\n }\n }\n}\n","// Embeds responsive\n//\n// Credit: Nicolas Gallagher and SUIT CSS.\n\n.embed-responsive {\n position: relative;\n display: block;\n height: 0;\n padding: 0;\n overflow: hidden;\n\n .embed-responsive-item,\n iframe,\n embed,\n object,\n video {\n position: absolute;\n top: 0;\n left: 0;\n bottom: 0;\n height: 100%;\n width: 100%;\n border: 0;\n }\n}\n\n// Modifier class for 16:9 aspect ratio\n.embed-responsive-16by9 {\n padding-bottom: 56.25%;\n}\n\n// Modifier class for 4:3 aspect ratio\n.embed-responsive-4by3 {\n padding-bottom: 75%;\n}\n","//\n// Wells\n// --------------------------------------------------\n\n\n// Base class\n.well {\n min-height: 20px;\n padding: 19px;\n margin-bottom: 20px;\n background-color: @well-bg;\n border: 1px solid @well-border;\n border-radius: @border-radius-base;\n .box-shadow(inset 0 1px 1px rgba(0,0,0,.05));\n blockquote {\n border-color: #ddd;\n border-color: rgba(0,0,0,.15);\n }\n}\n\n// Sizes\n.well-lg {\n padding: 24px;\n border-radius: @border-radius-large;\n}\n.well-sm {\n padding: 9px;\n border-radius: @border-radius-small;\n}\n","//\n// Close icons\n// --------------------------------------------------\n\n\n.close {\n float: right;\n font-size: (@font-size-base * 1.5);\n font-weight: @close-font-weight;\n line-height: 1;\n color: @close-color;\n text-shadow: @close-text-shadow;\n .opacity(.2);\n\n &:hover,\n &:focus {\n color: @close-color;\n text-decoration: none;\n cursor: pointer;\n .opacity(.5);\n }\n\n // Additional properties for button version\n // iOS requires the button element instead of an anchor tag.\n // If you want the anchor version, it requires `href=\"#\"`.\n // See https://developer.mozilla.org/en-US/docs/Web/Events/click#Safari_Mobile\n button& {\n padding: 0;\n cursor: pointer;\n background: transparent;\n border: 0;\n -webkit-appearance: none;\n }\n}\n","//\n// Modals\n// --------------------------------------------------\n\n// .modal-open - body class for killing the scroll\n// .modal - container to scroll within\n// .modal-dialog - positioning shell for the actual modal\n// .modal-content - actual modal w/ bg and corners and shit\n\n// Kill the scroll on the body\n.modal-open {\n overflow: hidden;\n}\n\n// Container that the modal scrolls within\n.modal {\n display: none;\n overflow: hidden;\n position: fixed;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: @zindex-modal;\n -webkit-overflow-scrolling: touch;\n\n // Prevent Chrome on Windows from adding a focus outline. For details, see\n // https://github.com/twbs/bootstrap/pull/10951.\n outline: 0;\n\n // When fading in the modal, animate it to slide down\n &.fade .modal-dialog {\n .translate(0, -25%);\n .transition-transform(~\"0.3s ease-out\");\n }\n &.in .modal-dialog { .translate(0, 0) }\n}\n.modal-open .modal {\n overflow-x: hidden;\n overflow-y: auto;\n}\n\n// Shell div to position the modal with bottom padding\n.modal-dialog {\n position: relative;\n width: auto;\n margin: 10px;\n}\n\n// Actual modal\n.modal-content {\n position: relative;\n background-color: @modal-content-bg;\n border: 1px solid @modal-content-fallback-border-color; //old browsers fallback (ie8 etc)\n border: 1px solid @modal-content-border-color;\n border-radius: @border-radius-large;\n .box-shadow(0 3px 9px rgba(0,0,0,.5));\n background-clip: padding-box;\n // Remove focus outline from opened modal\n outline: 0;\n}\n\n// Modal background\n.modal-backdrop {\n position: fixed;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: @zindex-modal-background;\n background-color: @modal-backdrop-bg;\n // Fade for backdrop\n &.fade { .opacity(0); }\n &.in { .opacity(@modal-backdrop-opacity); }\n}\n\n// Modal header\n// Top section of the modal w/ title and dismiss\n.modal-header {\n padding: @modal-title-padding;\n border-bottom: 1px solid @modal-header-border-color;\n &:extend(.clearfix all);\n}\n// Close icon\n.modal-header .close {\n margin-top: -2px;\n}\n\n// Title text within header\n.modal-title {\n margin: 0;\n line-height: @modal-title-line-height;\n}\n\n// Modal body\n// Where all modal content resides (sibling of .modal-header and .modal-footer)\n.modal-body {\n position: relative;\n padding: @modal-inner-padding;\n}\n\n// Footer (for actions)\n.modal-footer {\n padding: @modal-inner-padding;\n text-align: right; // right align buttons\n border-top: 1px solid @modal-footer-border-color;\n &:extend(.clearfix all); // clear it in case folks use .pull-* classes on buttons\n\n // Properly space out buttons\n .btn + .btn {\n margin-left: 5px;\n margin-bottom: 0; // account for input[type=\"submit\"] which gets the bottom margin like all other inputs\n }\n // but override that for button groups\n .btn-group .btn + .btn {\n margin-left: -1px;\n }\n // and override it for block buttons as well\n .btn-block + .btn-block {\n margin-left: 0;\n }\n}\n\n// Measure scrollbar width for padding body during modal show/hide\n.modal-scrollbar-measure {\n position: absolute;\n top: -9999px;\n width: 50px;\n height: 50px;\n overflow: scroll;\n}\n\n// Scale up the modal\n@media (min-width: @screen-sm-min) {\n // Automatically set modal's width for larger viewports\n .modal-dialog {\n width: @modal-md;\n margin: 30px auto;\n }\n .modal-content {\n .box-shadow(0 5px 15px rgba(0,0,0,.5));\n }\n\n // Modal sizes\n .modal-sm { width: @modal-sm; }\n}\n\n@media (min-width: @screen-md-min) {\n .modal-lg { width: @modal-lg; }\n}\n","//\n// Tooltips\n// --------------------------------------------------\n\n\n// Base class\n.tooltip {\n position: absolute;\n z-index: @zindex-tooltip;\n display: block;\n // Our parent element can be arbitrary since tooltips are by default inserted as a sibling of their target element.\n // So reset our font and text properties to avoid inheriting weird values.\n .reset-text();\n font-size: @font-size-small;\n\n .opacity(0);\n\n &.in { .opacity(@tooltip-opacity); }\n &.top { margin-top: -3px; padding: @tooltip-arrow-width 0; }\n &.right { margin-left: 3px; padding: 0 @tooltip-arrow-width; }\n &.bottom { margin-top: 3px; padding: @tooltip-arrow-width 0; }\n &.left { margin-left: -3px; padding: 0 @tooltip-arrow-width; }\n}\n\n// Wrapper for the tooltip content\n.tooltip-inner {\n max-width: @tooltip-max-width;\n padding: 3px 8px;\n color: @tooltip-color;\n text-align: center;\n background-color: @tooltip-bg;\n border-radius: @border-radius-base;\n}\n\n// Arrows\n.tooltip-arrow {\n position: absolute;\n width: 0;\n height: 0;\n border-color: transparent;\n border-style: solid;\n}\n// Note: Deprecated .top-left, .top-right, .bottom-left, and .bottom-right as of v3.3.1\n.tooltip {\n &.top .tooltip-arrow {\n bottom: 0;\n left: 50%;\n margin-left: -@tooltip-arrow-width;\n border-width: @tooltip-arrow-width @tooltip-arrow-width 0;\n border-top-color: @tooltip-arrow-color;\n }\n &.top-left .tooltip-arrow {\n bottom: 0;\n right: @tooltip-arrow-width;\n margin-bottom: -@tooltip-arrow-width;\n border-width: @tooltip-arrow-width @tooltip-arrow-width 0;\n border-top-color: @tooltip-arrow-color;\n }\n &.top-right .tooltip-arrow {\n bottom: 0;\n left: @tooltip-arrow-width;\n margin-bottom: -@tooltip-arrow-width;\n border-width: @tooltip-arrow-width @tooltip-arrow-width 0;\n border-top-color: @tooltip-arrow-color;\n }\n &.right .tooltip-arrow {\n top: 50%;\n left: 0;\n margin-top: -@tooltip-arrow-width;\n border-width: @tooltip-arrow-width @tooltip-arrow-width @tooltip-arrow-width 0;\n border-right-color: @tooltip-arrow-color;\n }\n &.left .tooltip-arrow {\n top: 50%;\n right: 0;\n margin-top: -@tooltip-arrow-width;\n border-width: @tooltip-arrow-width 0 @tooltip-arrow-width @tooltip-arrow-width;\n border-left-color: @tooltip-arrow-color;\n }\n &.bottom .tooltip-arrow {\n top: 0;\n left: 50%;\n margin-left: -@tooltip-arrow-width;\n border-width: 0 @tooltip-arrow-width @tooltip-arrow-width;\n border-bottom-color: @tooltip-arrow-color;\n }\n &.bottom-left .tooltip-arrow {\n top: 0;\n right: @tooltip-arrow-width;\n margin-top: -@tooltip-arrow-width;\n border-width: 0 @tooltip-arrow-width @tooltip-arrow-width;\n border-bottom-color: @tooltip-arrow-color;\n }\n &.bottom-right .tooltip-arrow {\n top: 0;\n left: @tooltip-arrow-width;\n margin-top: -@tooltip-arrow-width;\n border-width: 0 @tooltip-arrow-width @tooltip-arrow-width;\n border-bottom-color: @tooltip-arrow-color;\n }\n}\n",".reset-text() {\n font-family: @font-family-base;\n // We deliberately do NOT reset font-size.\n font-style: normal;\n font-weight: normal;\n letter-spacing: normal;\n line-break: auto;\n line-height: @line-height-base;\n text-align: left; // Fallback for where `start` is not supported\n text-align: start;\n text-decoration: none;\n text-shadow: none;\n text-transform: none;\n white-space: normal;\n word-break: normal;\n word-spacing: normal;\n word-wrap: normal;\n}\n","//\n// Popovers\n// --------------------------------------------------\n\n\n.popover {\n position: absolute;\n top: 0;\n left: 0;\n z-index: @zindex-popover;\n display: none;\n max-width: @popover-max-width;\n padding: 1px;\n // Our parent element can be arbitrary since popovers are by default inserted as a sibling of their target element.\n // So reset our font and text properties to avoid inheriting weird values.\n .reset-text();\n font-size: @font-size-base;\n\n background-color: @popover-bg;\n background-clip: padding-box;\n border: 1px solid @popover-fallback-border-color;\n border: 1px solid @popover-border-color;\n border-radius: @border-radius-large;\n .box-shadow(0 5px 10px rgba(0,0,0,.2));\n\n // Offset the popover to account for the popover arrow\n &.top { margin-top: -@popover-arrow-width; }\n &.right { margin-left: @popover-arrow-width; }\n &.bottom { margin-top: @popover-arrow-width; }\n &.left { margin-left: -@popover-arrow-width; }\n}\n\n.popover-title {\n margin: 0; // reset heading margin\n padding: 8px 14px;\n font-size: @font-size-base;\n background-color: @popover-title-bg;\n border-bottom: 1px solid darken(@popover-title-bg, 5%);\n border-radius: (@border-radius-large - 1) (@border-radius-large - 1) 0 0;\n}\n\n.popover-content {\n padding: 9px 14px;\n}\n\n// Arrows\n//\n// .arrow is outer, .arrow:after is inner\n\n.popover > .arrow {\n &,\n &:after {\n position: absolute;\n display: block;\n width: 0;\n height: 0;\n border-color: transparent;\n border-style: solid;\n }\n}\n.popover > .arrow {\n border-width: @popover-arrow-outer-width;\n}\n.popover > .arrow:after {\n border-width: @popover-arrow-width;\n content: \"\";\n}\n\n.popover {\n &.top > .arrow {\n left: 50%;\n margin-left: -@popover-arrow-outer-width;\n border-bottom-width: 0;\n border-top-color: @popover-arrow-outer-fallback-color; // IE8 fallback\n border-top-color: @popover-arrow-outer-color;\n bottom: -@popover-arrow-outer-width;\n &:after {\n content: \" \";\n bottom: 1px;\n margin-left: -@popover-arrow-width;\n border-bottom-width: 0;\n border-top-color: @popover-arrow-color;\n }\n }\n &.right > .arrow {\n top: 50%;\n left: -@popover-arrow-outer-width;\n margin-top: -@popover-arrow-outer-width;\n border-left-width: 0;\n border-right-color: @popover-arrow-outer-fallback-color; // IE8 fallback\n border-right-color: @popover-arrow-outer-color;\n &:after {\n content: \" \";\n left: 1px;\n bottom: -@popover-arrow-width;\n border-left-width: 0;\n border-right-color: @popover-arrow-color;\n }\n }\n &.bottom > .arrow {\n left: 50%;\n margin-left: -@popover-arrow-outer-width;\n border-top-width: 0;\n border-bottom-color: @popover-arrow-outer-fallback-color; // IE8 fallback\n border-bottom-color: @popover-arrow-outer-color;\n top: -@popover-arrow-outer-width;\n &:after {\n content: \" \";\n top: 1px;\n margin-left: -@popover-arrow-width;\n border-top-width: 0;\n border-bottom-color: @popover-arrow-color;\n }\n }\n\n &.left > .arrow {\n top: 50%;\n right: -@popover-arrow-outer-width;\n margin-top: -@popover-arrow-outer-width;\n border-right-width: 0;\n border-left-color: @popover-arrow-outer-fallback-color; // IE8 fallback\n border-left-color: @popover-arrow-outer-color;\n &:after {\n content: \" \";\n right: 1px;\n border-right-width: 0;\n border-left-color: @popover-arrow-color;\n bottom: -@popover-arrow-width;\n }\n }\n}\n","//\n// Carousel\n// --------------------------------------------------\n\n\n// Wrapper for the slide container and indicators\n.carousel {\n position: relative;\n}\n\n.carousel-inner {\n position: relative;\n overflow: hidden;\n width: 100%;\n\n > .item {\n display: none;\n position: relative;\n .transition(.6s ease-in-out left);\n\n // Account for jankitude on images\n > img,\n > a > img {\n &:extend(.img-responsive);\n line-height: 1;\n }\n\n // WebKit CSS3 transforms for supported devices\n @media all and (transform-3d), (-webkit-transform-3d) {\n .transition-transform(~'0.6s ease-in-out');\n .backface-visibility(~'hidden');\n .perspective(1000px);\n\n &.next,\n &.active.right {\n .translate3d(100%, 0, 0);\n left: 0;\n }\n &.prev,\n &.active.left {\n .translate3d(-100%, 0, 0);\n left: 0;\n }\n &.next.left,\n &.prev.right,\n &.active {\n .translate3d(0, 0, 0);\n left: 0;\n }\n }\n }\n\n > .active,\n > .next,\n > .prev {\n display: block;\n }\n\n > .active {\n left: 0;\n }\n\n > .next,\n > .prev {\n position: absolute;\n top: 0;\n width: 100%;\n }\n\n > .next {\n left: 100%;\n }\n > .prev {\n left: -100%;\n }\n > .next.left,\n > .prev.right {\n left: 0;\n }\n\n > .active.left {\n left: -100%;\n }\n > .active.right {\n left: 100%;\n }\n\n}\n\n// Left/right controls for nav\n// ---------------------------\n\n.carousel-control {\n position: absolute;\n top: 0;\n left: 0;\n bottom: 0;\n width: @carousel-control-width;\n .opacity(@carousel-control-opacity);\n font-size: @carousel-control-font-size;\n color: @carousel-control-color;\n text-align: center;\n text-shadow: @carousel-text-shadow;\n background-color: rgba(0, 0, 0, 0); // Fix IE9 click-thru bug\n // We can't have this transition here because WebKit cancels the carousel\n // animation if you trip this while in the middle of another animation.\n\n // Set gradients for backgrounds\n &.left {\n #gradient > .horizontal(@start-color: rgba(0,0,0,.5); @end-color: rgba(0,0,0,.0001));\n }\n &.right {\n left: auto;\n right: 0;\n #gradient > .horizontal(@start-color: rgba(0,0,0,.0001); @end-color: rgba(0,0,0,.5));\n }\n\n // Hover/focus state\n &:hover,\n &:focus {\n outline: 0;\n color: @carousel-control-color;\n text-decoration: none;\n .opacity(.9);\n }\n\n // Toggles\n .icon-prev,\n .icon-next,\n .glyphicon-chevron-left,\n .glyphicon-chevron-right {\n position: absolute;\n top: 50%;\n margin-top: -10px;\n z-index: 5;\n display: inline-block;\n }\n .icon-prev,\n .glyphicon-chevron-left {\n left: 50%;\n margin-left: -10px;\n }\n .icon-next,\n .glyphicon-chevron-right {\n right: 50%;\n margin-right: -10px;\n }\n .icon-prev,\n .icon-next {\n width: 20px;\n height: 20px;\n line-height: 1;\n font-family: serif;\n }\n\n\n .icon-prev {\n &:before {\n content: '\\2039';// SINGLE LEFT-POINTING ANGLE QUOTATION MARK (U+2039)\n }\n }\n .icon-next {\n &:before {\n content: '\\203a';// SINGLE RIGHT-POINTING ANGLE QUOTATION MARK (U+203A)\n }\n }\n}\n\n// Optional indicator pips\n//\n// Add an unordered list with the following class and add a list item for each\n// slide your carousel holds.\n\n.carousel-indicators {\n position: absolute;\n bottom: 10px;\n left: 50%;\n z-index: 15;\n width: 60%;\n margin-left: -30%;\n padding-left: 0;\n list-style: none;\n text-align: center;\n\n li {\n display: inline-block;\n width: 10px;\n height: 10px;\n margin: 1px;\n text-indent: -999px;\n border: 1px solid @carousel-indicator-border-color;\n border-radius: 10px;\n cursor: pointer;\n\n // IE8-9 hack for event handling\n //\n // Internet Explorer 8-9 does not support clicks on elements without a set\n // `background-color`. We cannot use `filter` since that's not viewed as a\n // background color by the browser. Thus, a hack is needed.\n // See https://developer.mozilla.org/en-US/docs/Web/Events/click#Internet_Explorer\n //\n // For IE8, we set solid black as it doesn't support `rgba()`. For IE9, we\n // set alpha transparency for the best results possible.\n background-color: #000 \\9; // IE8\n background-color: rgba(0,0,0,0); // IE9\n }\n .active {\n margin: 0;\n width: 12px;\n height: 12px;\n background-color: @carousel-indicator-active-bg;\n }\n}\n\n// Optional captions\n// -----------------------------\n// Hidden by default for smaller viewports\n.carousel-caption {\n position: absolute;\n left: 15%;\n right: 15%;\n bottom: 20px;\n z-index: 10;\n padding-top: 20px;\n padding-bottom: 20px;\n color: @carousel-caption-color;\n text-align: center;\n text-shadow: @carousel-text-shadow;\n & .btn {\n text-shadow: none; // No shadow for button elements in carousel-caption\n }\n}\n\n\n// Scale up controls for tablets and up\n@media screen and (min-width: @screen-sm-min) {\n\n // Scale up the controls a smidge\n .carousel-control {\n .glyphicon-chevron-left,\n .glyphicon-chevron-right,\n .icon-prev,\n .icon-next {\n width: (@carousel-control-font-size * 1.5);\n height: (@carousel-control-font-size * 1.5);\n margin-top: (@carousel-control-font-size / -2);\n font-size: (@carousel-control-font-size * 1.5);\n }\n .glyphicon-chevron-left,\n .icon-prev {\n margin-left: (@carousel-control-font-size / -2);\n }\n .glyphicon-chevron-right,\n .icon-next {\n margin-right: (@carousel-control-font-size / -2);\n }\n }\n\n // Show and left align the captions\n .carousel-caption {\n left: 20%;\n right: 20%;\n padding-bottom: 30px;\n }\n\n // Move up the indicators\n .carousel-indicators {\n bottom: 20px;\n }\n}\n","// Clearfix\n//\n// For modern browsers\n// 1. The space content is one way to avoid an Opera bug when the\n// contenteditable attribute is included anywhere else in the document.\n// Otherwise it causes space to appear at the top and bottom of elements\n// that are clearfixed.\n// 2. The use of `table` rather than `block` is only necessary if using\n// `:before` to contain the top-margins of child elements.\n//\n// Source: http://nicolasgallagher.com/micro-clearfix-hack/\n\n.clearfix() {\n &:before,\n &:after {\n content: \" \"; // 1\n display: table; // 2\n }\n &:after {\n clear: both;\n }\n}\n","// Center-align a block level element\n\n.center-block() {\n display: block;\n margin-left: auto;\n margin-right: auto;\n}\n","// CSS image replacement\n//\n// Heads up! v3 launched with only `.hide-text()`, but per our pattern for\n// mixins being reused as classes with the same name, this doesn't hold up. As\n// of v3.0.1 we have added `.text-hide()` and deprecated `.hide-text()`.\n//\n// Source: https://github.com/h5bp/html5-boilerplate/commit/aa0396eae757\n\n// Deprecated as of v3.0.1 (has been removed in v4)\n.hide-text() {\n font: ~\"0/0\" a;\n color: transparent;\n text-shadow: none;\n background-color: transparent;\n border: 0;\n}\n\n// New mixin to use as of v3.0.1\n.text-hide() {\n .hide-text();\n}\n","//\n// Responsive: Utility classes\n// --------------------------------------------------\n\n\n// IE10 in Windows (Phone) 8\n//\n// Support for responsive views via media queries is kind of borked in IE10, for\n// Surface/desktop in split view and for Windows Phone 8. This particular fix\n// must be accompanied by a snippet of JavaScript to sniff the user agent and\n// apply some conditional CSS to *only* the Surface/desktop Windows 8. Look at\n// our Getting Started page for more information on this bug.\n//\n// For more information, see the following:\n//\n// Issue: https://github.com/twbs/bootstrap/issues/10497\n// Docs: http://getbootstrap.com/getting-started/#support-ie10-width\n// Source: http://timkadlec.com/2013/01/windows-phone-8-and-device-width/\n// Source: http://timkadlec.com/2012/10/ie10-snap-mode-and-responsive-design/\n\n@-ms-viewport {\n width: device-width;\n}\n\n\n// Visibility utilities\n// Note: Deprecated .visible-xs, .visible-sm, .visible-md, and .visible-lg as of v3.2.0\n.visible-xs,\n.visible-sm,\n.visible-md,\n.visible-lg {\n .responsive-invisibility();\n}\n\n.visible-xs-block,\n.visible-xs-inline,\n.visible-xs-inline-block,\n.visible-sm-block,\n.visible-sm-inline,\n.visible-sm-inline-block,\n.visible-md-block,\n.visible-md-inline,\n.visible-md-inline-block,\n.visible-lg-block,\n.visible-lg-inline,\n.visible-lg-inline-block {\n display: none !important;\n}\n\n.visible-xs {\n @media (max-width: @screen-xs-max) {\n .responsive-visibility();\n }\n}\n.visible-xs-block {\n @media (max-width: @screen-xs-max) {\n display: block !important;\n }\n}\n.visible-xs-inline {\n @media (max-width: @screen-xs-max) {\n display: inline !important;\n }\n}\n.visible-xs-inline-block {\n @media (max-width: @screen-xs-max) {\n display: inline-block !important;\n }\n}\n\n.visible-sm {\n @media (min-width: @screen-sm-min) and (max-width: @screen-sm-max) {\n .responsive-visibility();\n }\n}\n.visible-sm-block {\n @media (min-width: @screen-sm-min) and (max-width: @screen-sm-max) {\n display: block !important;\n }\n}\n.visible-sm-inline {\n @media (min-width: @screen-sm-min) and (max-width: @screen-sm-max) {\n display: inline !important;\n }\n}\n.visible-sm-inline-block {\n @media (min-width: @screen-sm-min) and (max-width: @screen-sm-max) {\n display: inline-block !important;\n }\n}\n\n.visible-md {\n @media (min-width: @screen-md-min) and (max-width: @screen-md-max) {\n .responsive-visibility();\n }\n}\n.visible-md-block {\n @media (min-width: @screen-md-min) and (max-width: @screen-md-max) {\n display: block !important;\n }\n}\n.visible-md-inline {\n @media (min-width: @screen-md-min) and (max-width: @screen-md-max) {\n display: inline !important;\n }\n}\n.visible-md-inline-block {\n @media (min-width: @screen-md-min) and (max-width: @screen-md-max) {\n display: inline-block !important;\n }\n}\n\n.visible-lg {\n @media (min-width: @screen-lg-min) {\n .responsive-visibility();\n }\n}\n.visible-lg-block {\n @media (min-width: @screen-lg-min) {\n display: block !important;\n }\n}\n.visible-lg-inline {\n @media (min-width: @screen-lg-min) {\n display: inline !important;\n }\n}\n.visible-lg-inline-block {\n @media (min-width: @screen-lg-min) {\n display: inline-block !important;\n }\n}\n\n.hidden-xs {\n @media (max-width: @screen-xs-max) {\n .responsive-invisibility();\n }\n}\n.hidden-sm {\n @media (min-width: @screen-sm-min) and (max-width: @screen-sm-max) {\n .responsive-invisibility();\n }\n}\n.hidden-md {\n @media (min-width: @screen-md-min) and (max-width: @screen-md-max) {\n .responsive-invisibility();\n }\n}\n.hidden-lg {\n @media (min-width: @screen-lg-min) {\n .responsive-invisibility();\n }\n}\n\n\n// Print utilities\n//\n// Media queries are placed on the inside to be mixin-friendly.\n\n// Note: Deprecated .visible-print as of v3.2.0\n.visible-print {\n .responsive-invisibility();\n\n @media print {\n .responsive-visibility();\n }\n}\n.visible-print-block {\n display: none !important;\n\n @media print {\n display: block !important;\n }\n}\n.visible-print-inline {\n display: none !important;\n\n @media print {\n display: inline !important;\n }\n}\n.visible-print-inline-block {\n display: none !important;\n\n @media print {\n display: inline-block !important;\n }\n}\n\n.hidden-print {\n @media print {\n .responsive-invisibility();\n }\n}\n","// Responsive utilities\n\n//\n// More easily include all the states for responsive-utilities.less.\n.responsive-visibility() {\n display: block !important;\n table& { display: table !important; }\n tr& { display: table-row !important; }\n th&,\n td& { display: table-cell !important; }\n}\n\n.responsive-invisibility() {\n display: none !important;\n}\n"]} \ No newline at end of file
+{"version":3,"sources":["../../scss/bootstrap.scss","../../scss/_print.scss","dist/css/bootstrap.css","../../scss/_reboot.scss","bootstrap.css","../../scss/mixins/_hover.scss","../../scss/_type.scss","../../scss/mixins/_lists.scss","../../scss/_images.scss","../../scss/mixins/_image.scss","../../scss/mixins/_border-radius.scss","../../scss/mixins/_transition.scss","../../scss/_code.scss","../../scss/_grid.scss","../../scss/mixins/_grid.scss","../../scss/mixins/_breakpoints.scss","../../scss/mixins/_grid-framework.scss","../../scss/_tables.scss","../../scss/mixins/_table-row.scss","../../scss/_forms.scss","../../scss/mixins/_forms.scss","../../scss/_buttons.scss","../../scss/mixins/_buttons.scss","../../scss/_functions.scss","../../scss/_transitions.scss","../../scss/_dropdown.scss","../../scss/mixins/_nav-divider.scss","../../scss/_button-group.scss","../../scss/_input-group.scss","../../scss/_custom-forms.scss","../../scss/_nav.scss","../../scss/_navbar.scss","../../scss/_card.scss","../../scss/_breadcrumb.scss","../../scss/mixins/_clearfix.scss","../../scss/_pagination.scss","../../scss/mixins/_pagination.scss","../../scss/_badge.scss","../../scss/mixins/_badge.scss","../../scss/_jumbotron.scss","../../scss/_alert.scss","../../scss/mixins/_alert.scss","../../scss/_progress.scss","../../scss/mixins/_gradients.scss","../../scss/_media.scss","../../scss/_list-group.scss","../../scss/mixins/_list-group.scss","../../scss/_close.scss","../../scss/_modal.scss","../../scss/_tooltip.scss","../../scss/mixins/_reset-text.scss","../../scss/_popover.scss","../../scss/_carousel.scss","../../scss/utilities/_align.scss","../../scss/mixins/_background-variant.scss","../../scss/utilities/_background.scss","../../scss/utilities/_borders.scss","../../scss/utilities/_display.scss","../../scss/utilities/_embed.scss","../../scss/utilities/_flex.scss","../../scss/utilities/_float.scss","../../scss/mixins/_float.scss","../../scss/utilities/_position.scss","../../scss/utilities/_screenreaders.scss","../../scss/mixins/_screen-reader.scss","../../scss/utilities/_sizing.scss","../../scss/utilities/_spacing.scss","../../scss/utilities/_text.scss","../../scss/mixins/_text-truncate.scss","../../scss/mixins/_text-emphasis.scss","../../scss/mixins/_text-hide.scss","../../scss/utilities/_visibility.scss","../../scss/mixins/_visibility.scss"],"names":[],"mappings":"AAAA;;;;;ACWE,aACE,ECHF,QADA,SDUI,YAAA,eAEA,WAAA,eAGF,ECTF,UDWI,gBAAA,UAQF,mBACE,QAAA,KAAA,YAAA,IAcF,IACE,YAAA,mBCzBJ,WD2BE,IAEE,OAAA,IAAA,MAAA,KACA,kBAAA,MAQF,MACE,QAAA,mBC/BJ,IDkCE,GAEE,kBAAA,MChCJ,GACA,GDkCE,EAGE,QAAA,EACA,OAAA,EAGF,GCpCF,GDsCI,iBAAA,MAMF,QACE,QAAA,KAEF,OACE,OAAA,IAAA,MAAA,KAGF,OACE,gBAAA,mBADF,UCtCF,UD2CM,iBAAA,eCvCN,mBD0CE,mBAGI,OAAA,IAAA,MAAA,gBEpFR,KACE,WAAA,WACA,YAAA,WACA,YAAA,KACA,yBAAA,KACA,qBAAA,KACA,mBAAA,UACA,4BAAA,YAGF,ED8CA,QADA,SC1CE,WAAA,QAKA,cAAgB,MAAA,aAIlB,QAAA,MAAA,OAAA,WAAA,OAAA,OAAA,OAAA,OAAA,KAAA,IAAA,QACE,QAAA,MAQF,KACE,OAAA,EACA,YAAA,aAAA,CAAA,kBAAA,CAAA,UAAA,CAAA,MAAA,CAAA,gBAAA,CAAA,KAAA,CAAA,WACA,UAAA,KACA,YAAA,IACA,YAAA,IACA,MAAA,QACA,iBAAA,KCwCF,sBD/BE,QAAA,YASF,GACE,WAAA,YACA,OAAA,EACA,SAAA,QAYF,GAAA,GAAA,GAAA,GAAA,GAAA,GACE,WAAA,EACA,cAAA,MAOF,EACE,WAAA,EACA,cAAA,KDiBF,0BCPA,YAEE,gBAAA,UACA,wBAAA,UAAA,OAAA,gBAAA,UAAA,OACA,OAAA,KACA,cAAA,EAGF,QACE,cAAA,KACA,WAAA,OACA,YAAA,QDYF,GCTA,GDQA,GCLE,WAAA,EACA,cAAA,KAGF,MDSA,MACA,MAFA,MCJE,cAAA,EAGF,GACE,YAAA,IAGF,GACE,cAAA,MACA,YAAA,EAGF,WACE,OAAA,EAAA,EAAA,KAGF,IACE,WAAA,OAGF,EDQA,OCNE,YAAA,OAGF,MACE,UAAA,IAQF,IDGA,ICDE,SAAA,SACA,UAAA,IACA,YAAA,EACA,eAAA,SAGF,IAAM,OAAA,OACN,IAAM,IAAA,MAON,EACE,MAAA,QACA,gBAAA,KACA,iBAAA,YACA,6BAAA,QEpLE,QFuLA,MAAA,QACA,gBAAA,UAUJ,8BACE,MAAA,QACA,gBAAA,KEzLE,oCAAA,oCF4LA,MAAA,QACA,gBAAA,KANJ,oCAUI,QAAA,EDCJ,KACA,ICOA,IDNA,KCUE,YAAA,SAAA,CAAA,UACA,UAAA,IAGF,IAEE,WAAA,EAEA,cAAA,KAEA,SAAA,KAQF,OAEE,OAAA,EAAA,EAAA,KAQF,IACE,eAAA,OACA,aAAA,KAGF,eACE,SAAA,ODjBF,cC+BA,EDjCA,KACA,OAEA,MACA,MACA,OACA,QACA,SCmCE,iBAAA,aAAA,aAAA,aAQF,MACE,gBAAA,SAGF,QACE,YAAA,OACA,eAAA,OACA,MAAA,QACA,WAAA,KACA,aAAA,OAGF,GAEE,WAAA,KAQF,MAEE,QAAA,aACA,cAAA,MAOF,aACE,QAAA,IAAA,OACA,QAAA,IAAA,KAAA,yBD7CF,OCgDA,MD9CA,SADA,OAEA,SCkDE,OAAA,EACA,YAAA,QACA,UAAA,QACA,YAAA,QAGF,ODhDA,MCkDE,SAAA,QAGF,ODhDA,OCkDE,eAAA,KD5CF,aACA,cCiDA,ODnDA,mBCuDE,mBAAA,ODhDF,gCACA,+BACA,gCCkDA,yBAIE,QAAA,EACA,aAAA,KDjDF,qBCoDA,kBAEE,WAAA,WACA,QAAA,EAIF,iBDpDA,2BACA,kBAFA,iBC8DE,mBAAA,QAGF,SACE,SAAA,KAEA,OAAA,SAGF,SAME,UAAA,EAEA,QAAA,EACA,OAAA,EACA,OAAA,EAKF,OACE,QAAA,MACA,MAAA,KACA,UAAA,KACA,QAAA,EACA,cAAA,MACA,UAAA,OACA,YAAA,QACA,MAAA,QACA,YAAA,OAGF,SACE,eAAA,SCnEF,yCFGA,yCCsEE,OAAA,KCpEF,cD4EE,eAAA,KACA,mBAAA,KCxEF,4CFGA,yCC8EE,mBAAA,KAQF,6BACE,KAAA,QACA,mBAAA,OAOF,OACE,QAAA,aAGF,QACE,QAAA,UAGF,SACE,QAAA,KCrFF,SD2FE,QAAA,eDpFF,IAAK,IAAK,IAAK,IAAK,IAAK,IIvYzB,GAAA,GAAA,GAAA,GAAA,GAAA,GAEE,cAAA,MACA,YAAA,QACA,YAAA,IACA,YAAA,IACA,MAAA,QAGF,IAAA,GAAU,UAAA,OACV,IAAA,GAAU,UAAA,KACV,IAAA,GAAU,UAAA,QACV,IAAA,GAAU,UAAA,OACV,IAAA,GAAU,UAAA,QACV,IAAA,GAAU,UAAA,KAEV,MACE,UAAA,QACA,YAAA,IAIF,WACE,UAAA,KACA,YAAA,IACA,YAAA,IAEF,WACE,UAAA,OACA,YAAA,IACA,YAAA,IAEF,WACE,UAAA,OACA,YAAA,IACA,YAAA,IAEF,WACE,UAAA,OACA,YAAA,IACA,YAAA,IAQF,GACE,WAAA,KACA,cAAA,KACA,OAAA,EACA,WAAA,IAAA,MAAA,eJwZF,OIhZA,MAEE,UAAA,IACA,YAAA,IJmZF,MIhZA,KAEE,QAAA,KACA,iBAAA,QAQF,eC7EE,aAAA,EACA,WAAA,KDiFF,aClFE,aAAA,EACA,WAAA,KDoFF,kBACE,QAAA,aADF,mCAII,aAAA,IAUJ,YACE,UAAA,IACA,eAAA,UAIF,YACE,cAAA,KACA,UAAA,QAGF,mBACE,QAAA,MACA,UAAA,IACA,MAAA,QAHF,2BAMI,QAAA,cEjHJ,WCIE,UAAA,KAGA,OAAA,KDDF,eACE,QAAA,OACA,iBAAA,KACA,OAAA,IAAA,MAAA,KEZE,cAAA,OCCE,WAAA,IAAA,IAAA,YFMJ,UAAA,KAGA,OAAA,KDeF,QAEE,QAAA,aAGF,YACE,cAAA,MACA,YAAA,EAGF,gBACE,UAAA,IACA,MAAA,QIxCF,KV8hBA,IACA,IACA,KU5hBE,YAAA,KAAA,CAAA,MAAA,CAAA,QAAA,CAAA,iBAAA,CAAA,aAAA,CAAA,UAIF,KACE,QAAA,MAAA,MACA,UAAA,IACA,MAAA,QACA,iBAAA,QFTE,cAAA,OEaF,OACE,QAAA,EACA,MAAA,QACA,iBAAA,QAKJ,IACE,QAAA,MAAA,MACA,UAAA,IACA,MAAA,KACA,iBAAA,QFzBE,cAAA,MEqBJ,QASI,QAAA,EACA,UAAA,KACA,YAAA,IAMJ,IACE,QAAA,MACA,WAAA,EACA,cAAA,KACA,UAAA,IACA,MAAA,QALF,SASI,QAAA,EACA,UAAA,QACA,MAAA,QACA,iBAAA,YACA,cAAA,EAKJ,gBACE,WAAA,MACA,WAAA,OCzDA,WCAA,aAAA,KACA,YAAA,KACA,cAAA,KACA,aAAA,KACA,MAAA,KC+CE,yBFnDF,WCYI,UAAA,OCuCF,yBFnDF,WCYI,UAAA,OCuCF,yBFnDF,WCYI,UAAA,OCuCF,0BFnDF,WCYI,UAAA,QDAJ,iBACE,MAAA,KCbF,aAAA,KACA,YAAA,KACA,cAAA,KACA,aAAA,KACA,MAAA,KDmBA,KCLA,QAAA,YAAA,QAAA,KACA,cAAA,KAAA,UAAA,KACA,aAAA,MACA,YAAA,MDQA,YACE,aAAA,EACA,YAAA,EAFF,iBX4mBF,0BWtmBM,cAAA,EACA,aAAA,EGlCJ,KAAA,OAAA,QAAA,QAAA,QAAA,OAAA,OAAA,OAAA,OAAA,OAAA,OAAA,OAAA,Od6oBF,UAEqJ,QAAvI,UAAmG,WAAY,WAAY,WAAhH,UAAW,UAAW,UAAW,UAAW,UAAW,UAAW,UAAW,UACtG,aAFqJ,QAAvI,UAAmG,WAAY,WAAY,WAAhH,UAAW,UAAW,UAAW,UAAW,UAAW,UAAW,UAAW,UACtG,aAFkJ,QAAvI,UAAmG,WAAY,WAAY,WAAhH,UAAW,UAAW,UAAW,UAAW,UAAW,UAAW,UAAW,UACnG,aAEqJ,QAAvI,UAAmG,WAAY,WAAY,WAAhH,UAAW,UAAW,UAAW,UAAW,UAAW,UAAW,UAAW,UACtG,achpBI,SAAA,SACA,MAAA,KACA,WAAA,IACA,cAAA,KACA,aAAA,KAmBE,KACE,wBAAA,EAAA,WAAA,EACA,kBAAA,EAAA,UAAA,EACA,UAAA,KAEF,UACE,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KACA,MAAA,KACA,UAAA,KAIA,OFFN,SAAA,EAAA,EAAA,UAAA,KAAA,EAAA,EAAA,UAIA,UAAA,UEFM,OFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,OFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,OFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,OFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,OFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,OFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,OFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,OFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,QFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,QFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,QFFN,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KAIA,UAAA,KEIM,SACE,eAAA,EAAA,MAAA,EADF,SACE,eAAA,EAAA,MAAA,EADF,SACE,eAAA,EAAA,MAAA,EADF,SACE,eAAA,EAAA,MAAA,EADF,SACE,eAAA,EAAA,MAAA,EADF,SACE,eAAA,EAAA,MAAA,EADF,SACE,eAAA,EAAA,MAAA,EADF,SACE,eAAA,EAAA,MAAA,EADF,SACE,eAAA,EAAA,MAAA,EADF,UACE,eAAA,GAAA,MAAA,GADF,UACE,eAAA,GAAA,MAAA,GADF,UACE,eAAA,GAAA,MAAA,GDMN,yBCzBE,QACE,wBAAA,EAAA,WAAA,EACA,kBAAA,EAAA,UAAA,EACA,UAAA,KAEF,aACE,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KACA,MAAA,KACA,UAAA,KAIA,UFFN,SAAA,EAAA,EAAA,UAAA,KAAA,EAAA,EAAA,UAIA,UAAA,UEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,WFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,WFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,WFFN,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KAIA,UAAA,KEIM,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,aACE,eAAA,GAAA,MAAA,GADF,aACE,eAAA,GAAA,MAAA,GADF,aACE,eAAA,GAAA,MAAA,IDMN,yBCzBE,QACE,wBAAA,EAAA,WAAA,EACA,kBAAA,EAAA,UAAA,EACA,UAAA,KAEF,aACE,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KACA,MAAA,KACA,UAAA,KAIA,UFFN,SAAA,EAAA,EAAA,UAAA,KAAA,EAAA,EAAA,UAIA,UAAA,UEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,WFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,WFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,WFFN,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KAIA,UAAA,KEIM,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,aACE,eAAA,GAAA,MAAA,GADF,aACE,eAAA,GAAA,MAAA,GADF,aACE,eAAA,GAAA,MAAA,IDMN,yBCzBE,QACE,wBAAA,EAAA,WAAA,EACA,kBAAA,EAAA,UAAA,EACA,UAAA,KAEF,aACE,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KACA,MAAA,KACA,UAAA,KAIA,UFFN,SAAA,EAAA,EAAA,UAAA,KAAA,EAAA,EAAA,UAIA,UAAA,UEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,WFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,WFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,WFFN,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KAIA,UAAA,KEIM,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,aACE,eAAA,GAAA,MAAA,GADF,aACE,eAAA,GAAA,MAAA,GADF,aACE,eAAA,GAAA,MAAA,IDMN,0BCzBE,QACE,wBAAA,EAAA,WAAA,EACA,kBAAA,EAAA,UAAA,EACA,UAAA,KAEF,aACE,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KACA,MAAA,KACA,UAAA,KAIA,UFFN,SAAA,EAAA,EAAA,UAAA,KAAA,EAAA,EAAA,UAIA,UAAA,UEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,UFFN,SAAA,EAAA,EAAA,IAAA,KAAA,EAAA,EAAA,IAIA,UAAA,IEFM,WFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,WFFN,SAAA,EAAA,EAAA,WAAA,KAAA,EAAA,EAAA,WAIA,UAAA,WEFM,WFFN,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KAIA,UAAA,KEIM,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,YACE,eAAA,EAAA,MAAA,EADF,aACE,eAAA,GAAA,MAAA,GADF,aACE,eAAA,GAAA,MAAA,GADF,aACE,eAAA,GAAA,MAAA,IC9CV,OACE,MAAA,KACA,UAAA,KACA,cAAA,KACA,iBAAA,YfmyCF,UevyCA,UAQI,QAAA,OACA,eAAA,IACA,WAAA,IAAA,MAAA,QAVJ,gBAcI,eAAA,OACA,cAAA,IAAA,MAAA,QAfJ,mBAmBI,WAAA,IAAA,MAAA,QAnBJ,cAuBI,iBAAA,KfoyCJ,ae3xCA,aAGI,QAAA,MASJ,gBACE,OAAA,IAAA,MAAA,QfuxCF,mBexxCA,mBAKI,OAAA,IAAA,MAAA,QfwxCJ,yBe7xCA,yBAWM,oBAAA,IAUN,yCAEI,iBAAA,gBASJ,4BAGM,iBAAA,iBC9EJ,ehBs1CF,kBADA,kBgBj1CM,iBAAA,QAMJ,kCAKM,iBAAA,QALN,qChBq1CF,qCgB50CU,iBAAA,QAnBR,iBhBq2CF,oBADA,oBgBh2CM,iBAAA,QAMJ,oCAKM,iBAAA,QALN,uChBo2CF,uCgB31CU,iBAAA,QAnBR,ehBo3CF,kBADA,kBgB/2CM,iBAAA,QAMJ,kCAKM,iBAAA,QALN,qChBm3CF,qCgB12CU,iBAAA,QAnBR,YhBm4CF,eADA,egB93CM,iBAAA,QAMJ,+BAKM,iBAAA,QALN,kChBk4CF,kCgBz3CU,iBAAA,QAnBR,ehBk5CF,kBADA,kBgB74CM,iBAAA,QAMJ,kCAKM,iBAAA,QALN,qChBi5CF,qCgBx4CU,iBAAA,QAnBR,chBi6CF,iBADA,iBgB55CM,iBAAA,QAMJ,iCAKM,iBAAA,QALN,oChBg6CF,oCgBv5CU,iBAAA,QAnBR,ahBg7CF,gBADA,gBgB36CM,iBAAA,QAMJ,gCAKM,iBAAA,QALN,mChB+6CF,mCgBt6CU,iBAAA,QAnBR,YhB+7CF,eADA,egB17CM,iBAAA,QAMJ,+BAKM,iBAAA,QALN,kChB87CF,kCgBr7CU,iBAAA,QAnBR,chB88CF,iBADA,iBgBz8CM,iBAAA,iBAMJ,iCAKM,iBAAA,iBALN,oChB68CF,oCgBp8CU,iBAAA,iBDiFV,kBAEI,MAAA,KACA,iBAAA,QAIJ,kBAEI,MAAA,QACA,iBAAA,QAIJ,eACE,MAAA,KACA,iBAAA,Qfu3CF,kBez3CA,kBf03CA,wBen3CI,aAAA,QAPJ,8BAWI,OAAA,EAXJ,uDAgBM,iBAAA,sBAhBN,0CAuBQ,iBAAA,uBFzEJ,yBEsFJ,kBAEI,QAAA,MACA,MAAA,KACA,WAAA,KACA,mBAAA,yBALJ,iCASM,OAAA,GE9JN,cACE,QAAA,MACA,MAAA,KAGA,QAAA,MAAA,OACA,UAAA,KACA,YAAA,KACA,MAAA,QACA,iBAAA,KAEA,iBAAA,KACA,gBAAA,YACA,OAAA,IAAA,MAAA,gBAKE,cAAA,ORnBE,WAAA,aAAA,YAAA,IAAA,CAAA,WAAA,YAAA,KQCN,0BA6BI,iBAAA,YACA,OAAA,ECvBF,oBACE,MAAA,QACA,iBAAA,KACA,aAAA,QACA,QAAA,EDXJ,yCAsCI,MAAA,QAEA,QAAA,EAxCJ,oCAsCI,MAAA,QAEA,QAAA,EAxCJ,2BAsCI,MAAA,QAEA,QAAA,EAxCJ,uBAAA,wBAkDI,iBAAA,QAEA,QAAA,EAIJ,gDAEI,OAAA,oBAFJ,qCAWI,MAAA,QACA,iBAAA,KAKJ,mBjBu/CA,oBiBr/CE,QAAA,MAUF,gBACE,YAAA,sBACA,eAAA,sBACA,cAAA,EAGF,mBACE,YAAA,sBACA,eAAA,sBACA,UAAA,QAGF,mBACE,YAAA,uBACA,eAAA,uBACA,UAAA,QAUF,iBACE,YAAA,MACA,eAAA,MACA,cAAA,EACA,UAAA,KASF,wBACE,YAAA,MACA,eAAA,MACA,cAAA,EACA,YAAA,KACA,OAAA,MAAA,YACA,aAAA,IAAA,EjBu+CgE,wCiB7+ClE,wCjB6+C2G,qDAC3G,0DACA,6DiB/+CA,qDjB4+CA,0DACA,6DiBn+CI,cAAA,EACA,aAAA,EAaJ,iBAAA,8BjB69CA,mCACA,sCiB79CE,QAAA,OAAA,MACA,UAAA,QACA,YAAA,ITxJE,cAAA,MR4nDJ,wEiBh+CA,gEjB+9CA,qEiB/9CA,mDAEI,OAAA,sBAIJ,iBAAA,8BjB+9CA,mCACA,sCiB/9CE,QAAA,MAAA,KACA,UAAA,QACA,YAAA,ITrKE,cAAA,MR2oDJ,wEiBl+CA,gEjBi+CA,qEiBj+CA,mDAEI,OAAA,sBAUJ,YACE,cAAA,KAGF,WACE,QAAA,MACA,WAAA,OAQF,UACE,QAAA,YAAA,QAAA,KACA,cAAA,KAAA,UAAA,KACA,aAAA,KACA,YAAA,KAJF,ejB+9CA,wBiBv9CI,cAAA,IACA,aAAA,IASJ,YACE,SAAA,SACA,QAAA,MACA,cAAA,MAHF,uCAOM,MAAA,QAKN,kBACE,aAAA,QACA,cAAA,EAGF,kBACE,SAAA,SACA,WAAA,OACA,YAAA,SAHF,6BAMI,SAAA,OAKJ,mBACE,QAAA,aADF,qCAII,eAAA,OAJJ,sCAQI,YAAA,OAYJ,kBACE,QAAA,KACA,WAAA,OACA,UAAA,QACA,MAAA,QAGF,iBACE,SAAA,SACA,IAAA,KACA,QAAA,EACA,QAAA,KACA,MAAA,MACA,QAAA,MACA,WAAA,MACA,UAAA,QACA,YAAA,EACA,MAAA,KACA,iBAAA,mBACA,cAAA,MjB48CF,wBkB7sDI,uBAAA,oCAAA,mCAEE,aAAA,QlBitDN,8BkBntDI,6BAAA,0CAAA,yCAKI,WAAA,EAAA,EAAA,EAAA,MAAA,oBlBwtDR,0CACA,yCANuD,yCACvD,wCAA2C,sDAE3C,qDkB3tDI,qDlBwtDJ,oDkB9sDQ,QAAA,MAQJ,6CAAA,yDAGI,MAAA,QAOJ,yDAAA,qEAGI,iBAAA,oBAHJ,2DAAA,uEAMI,MAAA,QAOJ,iDAAA,6DAGI,aAAA,QAHJ,yDAAA,qEAKgB,aAAA,QALhB,kCAAA,8CAQI,WAAA,EAAA,EAAA,EAAA,MAAA,oBlB2sDR,0BkB5vDI,yBAAA,sCAAA,qCAEE,aAAA,QlBgwDN,gCkBlwDI,+BAAA,4CAAA,2CAKI,WAAA,EAAA,EAAA,EAAA,MAAA,oBlBuwDR,4CACA,2CANyD,2CACzD,0CAA6C,wDAE7C,uDkB1wDI,uDlBuwDJ,sDkB7vDQ,QAAA,MAQJ,+CAAA,2DAGI,MAAA,QAOJ,2DAAA,uEAGI,iBAAA,oBAHJ,6DAAA,yEAMI,MAAA,QAOJ,mDAAA,+DAGI,aAAA,QAHJ,2DAAA,uEAKgB,aAAA,QALhB,oCAAA,gDAQI,WAAA,EAAA,EAAA,EAAA,MAAA,oBD+NR,aACE,QAAA,YAAA,QAAA,KACA,cAAA,IAAA,KAAA,UAAA,IAAA,KACA,eAAA,OAAA,YAAA,OAHF,yBASI,MAAA,KJ5PA,yBImPJ,mBAeM,QAAA,YAAA,QAAA,KACA,eAAA,OAAA,YAAA,OACA,cAAA,OAAA,gBAAA,OACA,cAAA,EAlBN,yBAuBM,QAAA,YAAA,QAAA,KACA,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KACA,cAAA,IAAA,KAAA,UAAA,IAAA,KACA,eAAA,OAAA,YAAA,OACA,cAAA,EA3BN,2BAgCM,QAAA,aACA,MAAA,KACA,eAAA,OAlCN,qCAuCM,QAAA,aAvCN,0BA2CM,MAAA,KA3CN,iCA+CM,cAAA,EACA,eAAA,OAhDN,yBAsDM,QAAA,YAAA,QAAA,KACA,eAAA,OAAA,YAAA,OACA,cAAA,OAAA,gBAAA,OACA,MAAA,KACA,WAAA,EACA,cAAA,EA3DN,+BA8DM,aAAA,EA9DN,+BAiEM,SAAA,SACA,WAAA,EACA,aAAA,OACA,YAAA,EApEN,6BAyEM,QAAA,YAAA,QAAA,KACA,eAAA,OAAA,YAAA,OACA,cAAA,OAAA,gBAAA,OACA,aAAA,EA5EN,uCA+EM,SAAA,OACA,QAAA,aACA,aAAA,OACA,eAAA,YAlFN,kDAuFM,IAAA,GE5XN,KACE,QAAA,aACA,YAAA,IACA,WAAA,OACA,YAAA,OACA,eAAA,OACA,oBAAA,KAAA,iBAAA,KAAA,gBAAA,KAAA,YAAA,KACA,OAAA,IAAA,MAAA,YCiEA,QAAA,MAAA,OACA,UAAA,KACA,YAAA,KZ5EE,cAAA,OCCE,WAAA,IAAA,KAAA,YNiBF,WAAA,WgBHA,gBAAA,KAbJ,WAAA,WAiBI,QAAA,EACA,WAAA,EAAA,EAAA,EAAA,IAAA,oBAlBJ,cAAA,cAwBI,QAAA,IAxBJ,YAAA,YA8BI,iBAAA,KAMJ,enBu5DA,yBmBr5DE,eAAA,KASA,aEQE,MAAA,KDtDF,iBAAA,QACA,aAAA,QAGA,mBCkDE,MAAA,KDhDA,iBAAA,QACA,aAAA,QAGF,mBAAA,mBAMI,WAAA,EAAA,EAAA,EAAA,IAAA,mBAKJ,sBAAA,sBAEE,iBAAA,QACA,aAAA,QAGF,oBAAA,oBpBy7DF,mCoBt7DI,iBAAA,QACA,iBAAA,KACA,aAAA,QDcF,eEQE,MAAA,KDtDF,iBAAA,QACA,aAAA,QAGA,qBCkDE,MAAA,KDhDA,iBAAA,QACA,aAAA,QAGF,qBAAA,qBAMI,WAAA,EAAA,EAAA,EAAA,IAAA,qBAKJ,wBAAA,wBAEE,iBAAA,QACA,aAAA,QAGF,sBAAA,sBpBq9DF,qCoBl9DI,iBAAA,QACA,iBAAA,KACA,aAAA,QDcF,aEQE,MAAA,KDtDF,iBAAA,QACA,aAAA,QAGA,mBCkDE,MAAA,KDhDA,iBAAA,QACA,aAAA,QAGF,mBAAA,mBAMI,WAAA,EAAA,EAAA,EAAA,IAAA,mBAKJ,sBAAA,sBAEE,iBAAA,QACA,aAAA,QAGF,oBAAA,oBpBi/DF,mCoB9+DI,iBAAA,QACA,iBAAA,KACA,aAAA,QDcF,UEQE,MAAA,KDtDF,iBAAA,QACA,aAAA,QAGA,gBCkDE,MAAA,KDhDA,iBAAA,QACA,aAAA,QAGF,gBAAA,gBAMI,WAAA,EAAA,EAAA,EAAA,IAAA,oBAKJ,mBAAA,mBAEE,iBAAA,QACA,aAAA,QAGF,iBAAA,iBpB6gEF,gCoB1gEI,iBAAA,QACA,iBAAA,KACA,aAAA,QDcF,aEME,MAAA,KDpDF,iBAAA,QACA,aAAA,QAGA,mBCgDE,MAAA,KD9CA,iBAAA,QACA,aAAA,QAGF,mBAAA,mBAMI,WAAA,EAAA,EAAA,EAAA,IAAA,mBAKJ,sBAAA,sBAEE,iBAAA,QACA,aAAA,QAGF,oBAAA,oBpByiEF,mCoBtiEI,iBAAA,QACA,iBAAA,KACA,aAAA,QDcF,YEQE,MAAA,KDtDF,iBAAA,QACA,aAAA,QAGA,kBCkDE,MAAA,KDhDA,iBAAA,QACA,aAAA,QAGF,kBAAA,kBAMI,WAAA,EAAA,EAAA,EAAA,IAAA,mBAKJ,qBAAA,qBAEE,iBAAA,QACA,aAAA,QAGF,mBAAA,mBpBqkEF,kCoBlkEI,iBAAA,QACA,iBAAA,KACA,aAAA,QDcF,WEME,MAAA,KDpDF,iBAAA,QACA,aAAA,QAGA,iBCgDE,MAAA,KD9CA,iBAAA,QACA,aAAA,QAGF,iBAAA,iBAMI,WAAA,EAAA,EAAA,EAAA,IAAA,qBAKJ,oBAAA,oBAEE,iBAAA,QACA,aAAA,QAGF,kBAAA,kBpBimEF,iCoB9lEI,iBAAA,QACA,iBAAA,KACA,aAAA,QDcF,UEQE,MAAA,KDtDF,iBAAA,QACA,aAAA,QAGA,gBCkDE,MAAA,KDhDA,iBAAA,QACA,aAAA,QAGF,gBAAA,gBAMI,WAAA,EAAA,EAAA,EAAA,IAAA,kBAKJ,mBAAA,mBAEE,iBAAA,QACA,aAAA,QAGF,iBAAA,iBpB6nEF,gCoB1nEI,iBAAA,QACA,iBAAA,KACA,aAAA,QDoBF,qBCdA,MAAA,QACA,iBAAA,YACA,iBAAA,KACA,aAAA,QjBrCE,2BiBwCA,MAAA,KACA,iBAAA,QACA,aAAA,QAGF,2BAAA,2BAEE,WAAA,EAAA,EAAA,EAAA,IAAA,mBAGF,8BAAA,8BAEE,MAAA,QACA,iBAAA,YAGF,4BAAA,4BpBynEF,2CoBtnEI,MAAA,KACA,iBAAA,QACA,aAAA,QDbF,uBCdA,MAAA,QACA,iBAAA,YACA,iBAAA,KACA,aAAA,QjBrCE,6BiBwCA,MAAA,KACA,iBAAA,QACA,aAAA,QAGF,6BAAA,6BAEE,WAAA,EAAA,EAAA,EAAA,IAAA,qBAGF,gCAAA,gCAEE,MAAA,QACA,iBAAA,YAGF,8BAAA,8BpBspEF,6CoBnpEI,MAAA,KACA,iBAAA,QACA,aAAA,QDbF,qBCdA,MAAA,QACA,iBAAA,YACA,iBAAA,KACA,aAAA,QjBrCE,2BiBwCA,MAAA,KACA,iBAAA,QACA,aAAA,QAGF,2BAAA,2BAEE,WAAA,EAAA,EAAA,EAAA,IAAA,mBAGF,8BAAA,8BAEE,MAAA,QACA,iBAAA,YAGF,4BAAA,4BpBmrEF,2CoBhrEI,MAAA,KACA,iBAAA,QACA,aAAA,QDbF,kBCdA,MAAA,QACA,iBAAA,YACA,iBAAA,KACA,aAAA,QjBrCE,wBiBwCA,MAAA,KACA,iBAAA,QACA,aAAA,QAGF,wBAAA,wBAEE,WAAA,EAAA,EAAA,EAAA,IAAA,oBAGF,2BAAA,2BAEE,MAAA,QACA,iBAAA,YAGF,yBAAA,yBpBgtEF,wCoB7sEI,MAAA,KACA,iBAAA,QACA,aAAA,QDbF,qBCdA,MAAA,QACA,iBAAA,YACA,iBAAA,KACA,aAAA,QjBrCE,2BiBwCA,MAAA,KACA,iBAAA,QACA,aAAA,QAGF,2BAAA,2BAEE,WAAA,EAAA,EAAA,EAAA,IAAA,mBAGF,8BAAA,8BAEE,MAAA,QACA,iBAAA,YAGF,4BAAA,4BpB6uEF,2CoB1uEI,MAAA,KACA,iBAAA,QACA,aAAA,QDbF,oBCdA,MAAA,QACA,iBAAA,YACA,iBAAA,KACA,aAAA,QjBrCE,0BiBwCA,MAAA,KACA,iBAAA,QACA,aAAA,QAGF,0BAAA,0BAEE,WAAA,EAAA,EAAA,EAAA,IAAA,mBAGF,6BAAA,6BAEE,MAAA,QACA,iBAAA,YAGF,2BAAA,2BpB0wEF,0CoBvwEI,MAAA,KACA,iBAAA,QACA,aAAA,QDbF,mBCdA,MAAA,QACA,iBAAA,YACA,iBAAA,KACA,aAAA,QjBrCE,yBiBwCA,MAAA,KACA,iBAAA,QACA,aAAA,QAGF,yBAAA,yBAEE,WAAA,EAAA,EAAA,EAAA,IAAA,qBAGF,4BAAA,4BAEE,MAAA,QACA,iBAAA,YAGF,0BAAA,0BpBuyEF,yCoBpyEI,MAAA,KACA,iBAAA,QACA,aAAA,QDbF,kBCdA,MAAA,QACA,iBAAA,YACA,iBAAA,KACA,aAAA,QjBrCE,wBiBwCA,MAAA,KACA,iBAAA,QACA,aAAA,QAGF,wBAAA,wBAEE,WAAA,EAAA,EAAA,EAAA,IAAA,kBAGF,2BAAA,2BAEE,MAAA,QACA,iBAAA,YAGF,yBAAA,yBpBo0EF,wCoBj0EI,MAAA,KACA,iBAAA,QACA,aAAA,QDFJ,UACE,YAAA,IACA,MAAA,QACA,cAAA,EAHF,UAAA,iBAAA,iBAAA,mBASI,iBAAA,YATJ,UAAA,iBAAA,gBAeI,aAAA,YACA,WAAA,KhB3EA,gBgB8EA,aAAA,YhBnEA,gBAAA,gBgBsEA,MAAA,QACA,gBAAA,UACA,iBAAA,YAxBJ,mBA2BI,MAAA,QhB3EA,yBAAA,yBgB8EE,gBAAA,KAUN,mBAAA,QChCE,QAAA,MAAA,KACA,UAAA,QACA,YAAA,IZ5EE,cAAA,MW8GJ,mBAAA,QCpCE,QAAA,OAAA,MACA,UAAA,QACA,YAAA,IZ5EE,cAAA,MWuHJ,WACE,QAAA,MACA,MAAA,KAIF,sBACE,WAAA,MnBq0EF,6BADA,4BmBh0EA,6BAII,MAAA,KG1IJ,MACE,QAAA,EbII,WAAA,QAAA,KAAA,OaLN,WAKI,QAAA,EAIJ,UACE,QAAA,KADF,eAGI,QAAA,MAIJ,iBAEI,QAAA,UAIJ,oBAEI,QAAA,gBAIJ,YACE,SAAA,SACA,OAAA,EACA,SAAA,Ob1BI,WAAA,OAAA,KAAA,KTu+EN,UuB3+EA,QAEE,SAAA,SAGF,wBAGI,QAAA,aACA,MAAA,EACA,OAAA,EACA,YAAA,OACA,eAAA,OACA,QAAA,GACA,WAAA,KAAA,MACA,aAAA,KAAA,MAAA,YACA,YAAA,KAAA,MAAA,YAXJ,8BAeI,YAAA,EAMJ,uBAEI,WAAA,EACA,cAAA,QAHJ,gCAQM,WAAA,EACA,cAAA,KAAA,MAMN,eACE,SAAA,SACA,IAAA,KACA,KAAA,EACA,QAAA,KACA,QAAA,KACA,MAAA,KACA,UAAA,MACA,QAAA,MAAA,EACA,OAAA,QAAA,EAAA,EACA,UAAA,KACA,MAAA,QACA,WAAA,KACA,WAAA,KACA,iBAAA,KACA,gBAAA,YACA,OAAA,IAAA,MAAA,gBftDE,cAAA,Oe4DJ,kBC3DE,OAAA,EACA,OAAA,MAAA,EACA,SAAA,OACA,WAAA,IAAA,MAAA,QD+DF,eACE,QAAA,MACA,MAAA,KACA,QAAA,OAAA,OACA,MAAA,KACA,YAAA,IACA,MAAA,QACA,WAAA,QACA,YAAA,OACA,WAAA,IACA,OAAA,EpB3DE,qBAAA,qBoB8DA,MAAA,QACA,gBAAA,KACA,iBAAA,QAfJ,sBAAA,sBAoBI,MAAA,KACA,gBAAA,KACA,iBAAA,QAtBJ,wBAAA,wBA2BI,MAAA,QACA,iBAAA,YASJ,QAGI,QAAA,EAIJ,oBACE,QAAA,MAIF,iBACE,QAAA,MACA,QAAA,MAAA,OACA,cAAA,EACA,UAAA,QACA,MAAA,QACA,YAAA,OE3HF,WzBklFA,oByBhlFE,SAAA,SACA,QAAA,mBAAA,QAAA,YACA,eAAA,OzBslFF,yByB1lFA,gBAOI,SAAA,SACA,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KACA,cAAA,EzBylFJ,+ByBlmFA,sBAcM,QAAA,EzB2lFN,gCADA,gCADA,+ByBvmFA,uBAAA,uBAAA,sBAmBM,QAAA,EAnBN,qBzB8mFA,2BACA,2BACA,iCACA,8BACA,oCACA,oCACA,0CyBxlFI,YAAA,KAKJ,aACE,QAAA,YAAA,QAAA,KACA,cAAA,KAAA,UAAA,KACA,cAAA,MAAA,gBAAA,WAHF,0BAMI,MAAA,KAIJ,yEACE,cAAA,EAIF,4BACE,YAAA,EADF,mEjBlCI,wBAAA,EACA,2BAAA,EiByCJ,6CzB2lFA,8CQvnFI,uBAAA,EACA,0BAAA,EiBiCJ,sBACE,MAAA,KAEF,8DACE,cAAA,EAEF,mEzB6lFA,oEQnpFI,wBAAA,EACA,2BAAA,EiB2DJ,oEjB9CI,uBAAA,EACA,0BAAA,EiB8DJ,4BACE,cAAA,SACA,aAAA,SAFF,mCAKI,YAAA,EAIJ,0CAAA,+BACE,cAAA,QACA,aAAA,QAGF,0CAAA,+BACE,cAAA,OACA,aAAA,OAoBF,oBACE,QAAA,mBAAA,QAAA,YACA,mBAAA,OAAA,eAAA,OACA,eAAA,MAAA,YAAA,WACA,cAAA,OAAA,gBAAA,OAJF,yBzB2kFA,+ByBnkFI,MAAA,KARJ,8BzBglFA,oCACA,oCACA,0CyBnkFI,WAAA,KACA,YAAA,EAIJ,4DAEI,cAAA,EAFJ,sDjB9HI,2BAAA,EACA,0BAAA,EiB6HJ,sDjB5II,uBAAA,EACA,wBAAA,EiBsJJ,uEACE,cAAA,EAEF,4EzBwkFA,6EQptFI,2BAAA,EACA,0BAAA,EiBiJJ,6EjBhKI,uBAAA,EACA,wBAAA,ER4uFJ,gDEpLA,6CFsLA,2DADA,wDyBxjFM,SAAA,SACA,KAAA,cACA,eAAA,KC9LN,aACE,SAAA,SACA,QAAA,YAAA,QAAA,KACA,MAAA,KAHF,2BAQI,SAAA,SACA,QAAA,EACA,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KAGA,MAAA,GACA,cAAA,EAdJ,kCAAA,iCAAA,iCAkBM,QAAA,E1B+vFN,2B0B1vFA,mB1ByvFA,iB0BrvFE,QAAA,YAAA,QAAA,KACA,eAAA,OAAA,YAAA,O1B8vFF,8D0BnwFA,sD1BkwFA,oDQzxFI,cAAA,EkBmCJ,mB1B4vFA,iB0B1vFE,YAAA,OACA,eAAA,OAyBF,mBACE,QAAA,MAAA,OACA,cAAA,EACA,UAAA,KACA,YAAA,IACA,YAAA,KACA,MAAA,QACA,WAAA,OACA,iBAAA,QACA,OAAA,IAAA,MAAA,gBlBxEE,cAAA,OkB+DJ,mC1BmvFA,mCACA,wD0BtuFI,QAAA,OAAA,MACA,UAAA,QlB9EA,cAAA,MkB+DJ,mC1B2vFA,mCACA,wD0BxuFI,QAAA,MAAA,KACA,UAAA,QlBpFA,cAAA,MRk0FJ,wC0BnwFA,qCA6BI,WAAA,EAUJ,4C1BiuFA,oCAKA,oEADA,+EAHA,uCACA,kDACA,mDQ7zFI,wBAAA,EACA,2BAAA,EkBiGJ,oCACE,aAAA,EAEF,6C1BouFA,qCACA,wCACA,mDACA,oDAEA,oEADA,yDQ/zFI,uBAAA,EACA,0BAAA,EkB+FJ,mDACE,YAAA,EAOF,iBACE,SAAA,SAGA,UAAA,EACA,YAAA,OALF,sBAUI,SAAA,SAVJ,2BAaM,YAAA,KAbN,6BAAA,4BAAA,4BAkBM,QAAA,EAlBN,uC1BovFA,6C0B1tFM,aAAA,KA1BN,wC1ByvFA,8C0BztFM,QAAA,EACA,YAAA,K1B+tFN,qDADA,oDAEA,oD0BjwFA,+CAAA,8CAAA,8CAoCQ,QAAA,EChKR,gBACE,SAAA,SACA,QAAA,mBAAA,QAAA,YACA,WAAA,OACA,aAAA,OACA,aAAA,KAGF,sBACE,SAAA,SACA,QAAA,GACA,QAAA,EAHF,wDAMI,MAAA,KACA,iBAAA,QAPJ,sDAaI,WAAA,EAAA,EAAA,EAAA,IAAA,IAAA,CAAA,EAAA,EAAA,EAAA,IAAA,QAbJ,uDAiBI,MAAA,KACA,iBAAA,QAlBJ,yDAwBM,iBAAA,QAxBN,2DA4BM,MAAA,QASN,0BACE,SAAA,SACA,IAAA,OACA,KAAA,EACA,QAAA,MACA,MAAA,KACA,OAAA,KACA,eAAA,KACA,oBAAA,KAAA,iBAAA,KAAA,gBAAA,KAAA,YAAA,KACA,iBAAA,KACA,kBAAA,UACA,oBAAA,OAAA,OACA,gBAAA,IAAA,IAQF,2CnBxEI,cAAA,OmBwEJ,yEAMI,iBAAA,yMANJ,+EAUI,iBAAA,QACA,iBAAA,sJASJ,wCAEI,cAAA,IAFJ,sEAMI,iBAAA,mJAUJ,yBACE,QAAA,YAAA,QAAA,KACA,mBAAA,OAAA,eAAA,OAFF,yCAKI,cAAA,OALJ,yDAQM,YAAA,EAYN,eACE,QAAA,aACA,UAAA,KACA,OAAA,oBACA,QAAA,QAAA,QAAA,QAAA,OACA,YAAA,KACA,MAAA,QACA,eAAA,OACA,WAAA,KAAA,oKAAA,UAAA,MAAA,OAAA,OACA,gBAAA,IAAA,KACA,OAAA,IAAA,MAAA,gBAEE,cAAA,OAIF,mBAAA,KAAA,gBAAA,KAAA,WAAA,KAhBF,qBAmBI,aAAA,QACA,QAAA,EApBJ,gCA6BM,MAAA,QACA,iBAAA,KA9BN,wBAmCI,MAAA,QACA,iBAAA,QApCJ,2BAyCI,QAAA,EAIJ,kBACE,OAAA,sBACA,YAAA,QACA,eAAA,QACA,UAAA,IAQF,aACE,SAAA,SACA,QAAA,aACA,UAAA,KACA,OAAA,OACA,cAAA,EAGF,mBACE,UAAA,MACA,UAAA,KACA,OAAA,OACA,OAAA,EACA,QAAA,EAOF,qBACE,SAAA,SACA,IAAA,EACA,MAAA,EACA,KAAA,EACA,QAAA,EACA,OAAA,OACA,QAAA,MAAA,KACA,YAAA,IACA,MAAA,QACA,eAAA,KACA,oBAAA,KAAA,iBAAA,KAAA,gBAAA,KAAA,YAAA,KACA,iBAAA,KACA,OAAA,IAAA,MAAA,gBnB1NE,cAAA,OmB6MJ,2CAmBM,QAAA,iBAnBN,6BAwBI,SAAA,SACA,IAAA,KACA,MAAA,KACA,OAAA,KACA,QAAA,EACA,QAAA,MACA,OAAA,OACA,QAAA,MAAA,KACA,YAAA,IACA,MAAA,QACA,iBAAA,QACA,OAAA,IAAA,MAAA,gBnBhPA,cAAA,EAAA,OAAA,OAAA,EmB6MJ,sCAyCM,QAAA,SCrPN,KACE,QAAA,YAAA,QAAA,KACA,cAAA,KAAA,UAAA,KACA,aAAA,EACA,cAAA,EACA,WAAA,KAGF,UACE,QAAA,MACA,QAAA,MAAA,KzBOE,gBAAA,gByBJA,gBAAA,KALJ,mBAUI,MAAA,QAQJ,UACE,cAAA,IAAA,MAAA,KADF,oBAII,cAAA,KAJJ,oBAQI,OAAA,IAAA,MAAA,YpB7BA,uBAAA,OACA,wBAAA,OoBoBJ,0BAAA,0BAYM,aAAA,QAAA,QAAA,KAZN,6BAgBM,MAAA,QACA,iBAAA,YACA,aAAA,Y5B6kGN,mC4B/lGA,2BAwBI,MAAA,QACA,iBAAA,KACA,aAAA,KAAA,KAAA,KA1BJ,yBA+BI,WAAA,KpBpDA,uBAAA,EACA,wBAAA,EoB8DJ,qBpBrEI,cAAA,OoBqEJ,4B5BskGA,2B4BhkGM,MAAA,KACA,iBAAA,QAUN,oBAEI,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KACA,WAAA,OAIJ,yBAEI,wBAAA,EAAA,WAAA,EACA,kBAAA,EAAA,UAAA,EACA,WAAA,OASJ,uBAEI,QAAA,KAFJ,qBAKI,QAAA,MClGJ,QACE,SAAA,SACA,QAAA,YAAA,QAAA,KACA,cAAA,KAAA,UAAA,KACA,eAAA,OAAA,YAAA,OACA,cAAA,QAAA,gBAAA,cACA,QAAA,MAAA,KANF,mB7BuqGA,yB6B3pGI,QAAA,YAAA,QAAA,KACA,cAAA,KAAA,UAAA,KACA,eAAA,OAAA,YAAA,OACA,cAAA,QAAA,gBAAA,cASJ,cACE,QAAA,aACA,YAAA,SACA,eAAA,SACA,aAAA,KACA,UAAA,QACA,YAAA,QACA,YAAA,O1B1BE,oBAAA,oB0B6BA,gBAAA,KASJ,YACE,QAAA,YAAA,QAAA,KACA,mBAAA,OAAA,eAAA,OACA,aAAA,EACA,cAAA,EACA,WAAA,KALF,sBAQI,cAAA,EACA,aAAA,EATJ,2BAaI,SAAA,OACA,MAAA,KASJ,aACE,QAAA,aACA,YAAA,MACA,eAAA,MAYF,iBACE,wBAAA,KAAA,WAAA,KAGA,eAAA,OAAA,YAAA,OAIF,gBACE,QAAA,OAAA,OACA,UAAA,QACA,YAAA,EACA,WAAA,IACA,OAAA,IAAA,MAAA,YrB3GE,cAAA,OLkBA,sBAAA,sB0B6FA,gBAAA,KAMJ,qBACE,QAAA,aACA,MAAA,MACA,OAAA,MACA,eAAA,OACA,QAAA,GACA,WAAA,UAAA,OAAA,OACA,gBAAA,KAAA,KhB3DE,yBgBqEA,6B7BioGF,mC6B7nGQ,cAAA,EACA,aAAA,GhBvFN,yBgBkFA,kBAUI,mBAAA,IAAA,eAAA,IACA,cAAA,OAAA,UAAA,OACA,cAAA,MAAA,gBAAA,WAZJ,8BAeM,mBAAA,IAAA,eAAA,IAfN,6CAkBQ,SAAA,SAlBR,mDAsBQ,MAAA,EACA,KAAA,KAvBR,wCA2BQ,cAAA,MACA,aAAA,MA5BR,6B7BgqGF,mC6B7nGQ,cAAA,OAAA,UAAA,OAnCN,mCAwCM,QAAA,sBAAA,QAAA,eAxCN,kCA6CM,QAAA,MhBlHN,yBgBqEA,6B7B+qGF,mC6B3qGQ,cAAA,EACA,aAAA,GhBvFN,yBgBkFA,kBAUI,mBAAA,IAAA,eAAA,IACA,cAAA,OAAA,UAAA,OACA,cAAA,MAAA,gBAAA,WAZJ,8BAeM,mBAAA,IAAA,eAAA,IAfN,6CAkBQ,SAAA,SAlBR,mDAsBQ,MAAA,EACA,KAAA,KAvBR,wCA2BQ,cAAA,MACA,aAAA,MA5BR,6B7B8sGF,mC6B3qGQ,cAAA,OAAA,UAAA,OAnCN,mCAwCM,QAAA,sBAAA,QAAA,eAxCN,kCA6CM,QAAA,MhBlHN,yBgBqEA,6B7B6tGF,mC6BztGQ,cAAA,EACA,aAAA,GhBvFN,yBgBkFA,kBAUI,mBAAA,IAAA,eAAA,IACA,cAAA,OAAA,UAAA,OACA,cAAA,MAAA,gBAAA,WAZJ,8BAeM,mBAAA,IAAA,eAAA,IAfN,6CAkBQ,SAAA,SAlBR,mDAsBQ,MAAA,EACA,KAAA,KAvBR,wCA2BQ,cAAA,MACA,aAAA,MA5BR,6B7B4vGF,mC6BztGQ,cAAA,OAAA,UAAA,OAnCN,mCAwCM,QAAA,sBAAA,QAAA,eAxCN,kCA6CM,QAAA,MhBlHN,0BgBqEA,6B7B2wGF,mC6BvwGQ,cAAA,EACA,aAAA,GhBvFN,0BgBkFA,kBAUI,mBAAA,IAAA,eAAA,IACA,cAAA,OAAA,UAAA,OACA,cAAA,MAAA,gBAAA,WAZJ,8BAeM,mBAAA,IAAA,eAAA,IAfN,6CAkBQ,SAAA,SAlBR,mDAsBQ,MAAA,EACA,KAAA,KAvBR,wCA2BQ,cAAA,MACA,aAAA,MA5BR,6B7B0yGF,mC6BvwGQ,cAAA,OAAA,UAAA,OAnCN,mCAwCM,QAAA,sBAAA,QAAA,eAxCN,kCA6CM,QAAA,MAlDV,eAeQ,mBAAA,IAAA,eAAA,IACA,cAAA,OAAA,UAAA,OACA,cAAA,MAAA,gBAAA,WAjBR,0B7Bs0GA,gC6B7zGU,cAAA,EACA,aAAA,EAVV,2BAoBU,mBAAA,IAAA,eAAA,IApBV,0CAuBY,SAAA,SAvBZ,gDA2BY,MAAA,EACA,KAAA,KA5BZ,qCAgCY,cAAA,MACA,aAAA,MAjCZ,0B7B+1GA,gC6BvzGU,cAAA,OAAA,UAAA,OAxCV,gCA6CU,QAAA,sBAAA,QAAA,eA7CV,+BAkDU,QAAA,KAaV,4BAEI,MAAA,eAFJ,kCAAA,kCAKM,MAAA,eALN,oCAWM,MAAA,eAXN,0CAAA,0CAcQ,MAAA,eAdR,6CAkBQ,MAAA,e7BizGR,4CAEA,2CADA,yC6Bp0GA,0CA0BM,MAAA,eA1BN,8BA+BI,MAAA,eACA,aAAA,eAhCJ,mCAoCI,iBAAA,oPApCJ,2BAwCI,MAAA,eAKJ,2BAEI,MAAA,KAFJ,iCAAA,iCAKM,MAAA,KALN,mCAWM,MAAA,qBAXN,yCAAA,yCAcQ,MAAA,sBAdR,4CAkBQ,MAAA,sB7B4yGR,2CAEA,0CADA,wC6B/zGA,yCA0BM,MAAA,KA1BN,6BA+BI,MAAA,qBACA,aAAA,qBAhCJ,kCAoCI,iBAAA,0PApCJ,0BAwCI,MAAA,qBCrRJ,MACE,SAAA,SACA,QAAA,YAAA,QAAA,KACA,mBAAA,OAAA,eAAA,OACA,UAAA,EACA,UAAA,WACA,iBAAA,KACA,gBAAA,WACA,OAAA,IAAA,MAAA,iBtBRE,cAAA,OsBYJ,WAGE,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KACA,QAAA,QAGF,YACE,cAAA,OAGF,eACE,WAAA,SACA,cAAA,EAGF,sBACE,cAAA,E3BtBE,iB2B2BA,gBAAA,KAFJ,sBAMI,YAAA,QAIJ,2DtBpCI,uBAAA,OACA,wBAAA,OsBmCJ,yDtBtBI,2BAAA,OACA,0BAAA,OsBwCJ,aACE,QAAA,OAAA,QACA,cAAA,EACA,iBAAA,gBACA,cAAA,IAAA,MAAA,iBAJF,yBtB7DI,cAAA,mBAAA,mBAAA,EAAA,EsBwEJ,aACE,QAAA,OAAA,QACA,iBAAA,gBACA,WAAA,IAAA,MAAA,iBAHF,wBtBxEI,cAAA,EAAA,EAAA,mBAAA,mBsBuFJ,kBACE,aAAA,SACA,cAAA,QACA,YAAA,SACA,cAAA,EAGF,mBACE,aAAA,SACA,YAAA,SAIF,kBACE,SAAA,SACA,IAAA,EACA,MAAA,EACA,OAAA,EACA,KAAA,EACA,QAAA,QAGF,UACE,MAAA,KtB9GE,cAAA,mBsBmHJ,cACE,MAAA,KtB9GE,uBAAA,mBACA,wBAAA,mBsBiHJ,iBACE,MAAA,KtBrGE,2BAAA,mBACA,0BAAA,mBK+BA,yBiB6EF,WACE,QAAA,YAAA,QAAA,KACA,cAAA,IAAA,KAAA,UAAA,IAAA,KACA,aAAA,MACA,YAAA,MAJF,iBAOI,QAAA,YAAA,QAAA,KACA,SAAA,EAAA,EAAA,GAAA,KAAA,EAAA,EAAA,GACA,mBAAA,OAAA,eAAA,OACA,aAAA,KACA,YAAA,MjBxFF,yBiBmGF,YACE,QAAA,YAAA,QAAA,KACA,cAAA,IAAA,KAAA,UAAA,IAAA,KAFF,kBAKI,SAAA,EAAA,EAAA,GAAA,KAAA,EAAA,EAAA,GALJ,wBAQM,YAAA,EACA,YAAA,EATN,8BtB1IE,wBAAA,EACA,2BAAA,EsByIF,4CAkBU,wBAAA,EAlBV,+CAqBU,2BAAA,EArBV,6BtB5HE,uBAAA,EACA,0BAAA,EsB2HF,2CA4BU,uBAAA,EA5BV,8CA+BU,0BAAA,EA/BV,qDAoCQ,cAAA,E9B6iHR,sE8BjlHA,mEAwCU,cAAA,GAaZ,oBAEI,cAAA,OjB1JA,yBiBwJJ,cAMI,qBAAA,EAAA,aAAA,EACA,mBAAA,QAAA,WAAA,QAPJ,oBAUM,QAAA,aACA,MAAA,MC3NN,YACE,QAAA,OAAA,KACA,cAAA,KACA,WAAA,KACA,iBAAA,QvBAE,cAAA,OwBHF,mBACE,QAAA,MACA,MAAA,KACA,QAAA,GDKJ,iBACE,MAAA,KADF,0CAKI,QAAA,aACA,cAAA,MACA,aAAA,MACA,MAAA,QACA,QAAA,IATJ,gDAmBI,gBAAA,UAnBJ,gDAsBI,gBAAA,KAtBJ,wBA0BI,MAAA,QEnCJ,YACE,QAAA,YAAA,QAAA,KAEA,aAAA,EACA,WAAA,KzBAE,cAAA,OyBIJ,kCAGM,YAAA,EzBoBF,uBAAA,OACA,0BAAA,OyBxBJ,iCzBSI,wBAAA,OACA,2BAAA,OyBVJ,6BAcI,QAAA,EACA,MAAA,KACA,iBAAA,QACA,aAAA,QAjBJ,+BAqBI,MAAA,QACA,eAAA,KACA,iBAAA,KACA,aAAA,KAIJ,WACE,SAAA,SACA,QAAA,MACA,QAAA,MAAA,OACA,YAAA,KACA,YAAA,KACA,MAAA,QACA,iBAAA,KACA,OAAA,IAAA,MAAA,K9BtBE,iBAAA,iB8ByBA,MAAA,QACA,gBAAA,KACA,iBAAA,QACA,aAAA,KC/CF,0BACE,QAAA,OAAA,OACA,UAAA,QACA,YAAA,IAKE,iD1BoBF,uBAAA,MACA,0BAAA,M0BhBE,gD1BCF,wBAAA,MACA,2BAAA,M0BfF,0BACE,QAAA,OAAA,MACA,UAAA,QACA,YAAA,IAKE,iD1BoBF,uBAAA,MACA,0BAAA,M0BhBE,gD1BCF,wBAAA,MACA,2BAAA,M2BbJ,OACE,QAAA,aACA,QAAA,MAAA,KACA,UAAA,IACA,YAAA,IACA,YAAA,EACA,MAAA,KACA,WAAA,OACA,YAAA,OACA,eAAA,S3BVE,cAAA,O2BCJ,aAcI,QAAA,KAKJ,YACE,SAAA,SACA,IAAA,KAOF,YACE,cAAA,KACA,aAAA,K3B/BE,cAAA,M2BwCF,ediBE,MAAA,Ke3DF,iBAAA,QjCoBE,2BAAA,2BkBuCA,MAAA,KetDE,gBAAA,KACA,iBAAA,QDoCJ,iBdiBE,MAAA,Ke3DF,iBAAA,QjCoBE,6BAAA,6BkBuCA,MAAA,KetDE,gBAAA,KACA,iBAAA,QDoCJ,ediBE,MAAA,Ke3DF,iBAAA,QjCoBE,2BAAA,2BkBuCA,MAAA,KetDE,gBAAA,KACA,iBAAA,QDoCJ,YdiBE,MAAA,Ke3DF,iBAAA,QjCoBE,wBAAA,wBkBuCA,MAAA,KetDE,gBAAA,KACA,iBAAA,QDoCJ,edeE,MAAA,KezDF,iBAAA,QjCoBE,2BAAA,2BkBqCA,MAAA,KepDE,gBAAA,KACA,iBAAA,QDoCJ,cdiBE,MAAA,Ke3DF,iBAAA,QjCoBE,0BAAA,0BkBuCA,MAAA,KetDE,gBAAA,KACA,iBAAA,QDoCJ,adeE,MAAA,KezDF,iBAAA,QjCoBE,yBAAA,yBkBqCA,MAAA,KepDE,gBAAA,KACA,iBAAA,QDoCJ,YdiBE,MAAA,Ke3DF,iBAAA,QjCoBE,wBAAA,wBkBuCA,MAAA,KetDE,gBAAA,KACA,iBAAA,QCRN,WACE,QAAA,KAAA,KACA,cAAA,KACA,iBAAA,Q7BCE,cAAA,MKoDA,yBwBxDJ,WAOI,QAAA,KAAA,MAIJ,iBACE,cAAA,EACA,aAAA,E7BTE,cAAA,E8BAJ,OACE,QAAA,OAAA,QACA,cAAA,KACA,OAAA,IAAA,MAAA,Y9BHE,cAAA,O8BQJ,eAEE,MAAA,QAIF,YACE,YAAA,IAQF,0BAGI,SAAA,SACA,IAAA,QACA,MAAA,SACA,QAAA,OAAA,QACA,MAAA,QAUF,eC3CA,MAAA,QACA,iBAAA,QACA,aAAA,QAEA,kBACE,iBAAA,QAGF,2BACE,MAAA,QDkCF,iBC3CA,MAAA,QACA,iBAAA,QACA,aAAA,QAEA,oBACE,iBAAA,QAGF,6BACE,MAAA,QDkCF,eC3CA,MAAA,QACA,iBAAA,QACA,aAAA,QAEA,kBACE,iBAAA,QAGF,2BACE,MAAA,QDkCF,YC3CA,MAAA,QACA,iBAAA,QACA,aAAA,QAEA,eACE,iBAAA,QAGF,wBACE,MAAA,QDkCF,eC3CA,MAAA,QACA,iBAAA,QACA,aAAA,QAEA,kBACE,iBAAA,QAGF,2BACE,MAAA,QDkCF,cC3CA,MAAA,QACA,iBAAA,QACA,aAAA,QAEA,iBACE,iBAAA,QAGF,0BACE,MAAA,QDkCF,aC3CA,MAAA,QACA,iBAAA,QACA,aAAA,QAEA,gBACE,iBAAA,QAGF,yBACE,MAAA,QDkCF,YC3CA,MAAA,QACA,iBAAA,QACA,aAAA,QAEA,eACE,iBAAA,QAGF,wBACE,MAAA,QCVJ,wCACE,KAAO,oBAAA,KAAA,EACP,GAAK,oBAAA,EAAA,GAFP,gCACE,KAAO,oBAAA,KAAA,EACP,GAAK,oBAAA,EAAA,GAGP,UACE,QAAA,YAAA,QAAA,KACA,SAAA,OACA,UAAA,OACA,YAAA,KACA,WAAA,OACA,iBAAA,QhCPE,cAAA,OgCYJ,cACE,OAAA,KACA,YAAA,KACA,MAAA,KACA,iBAAA,Q/BfI,WAAA,MAAA,IAAA,K+BmBN,sBCWE,iBAAA,iKDTA,gBAAA,KAAA,KAGF,uBACE,kBAAA,qBAAA,GAAA,OAAA,SAAA,UAAA,qBAAA,GAAA,OAAA,SE9BF,OACE,QAAA,YAAA,QAAA,KACA,eAAA,MAAA,YAAA,WAGF,YACE,SAAA,EAAA,KAAA,ECFF,YACE,QAAA,YAAA,QAAA,KACA,mBAAA,OAAA,eAAA,OAGA,aAAA,EACA,cAAA,EASF,wBACE,MAAA,KACA,MAAA,QACA,WAAA,QxCAE,8BAAA,8BwCIA,MAAA,QACA,gBAAA,KACA,iBAAA,QATJ,+BAaI,MAAA,QACA,iBAAA,QASJ,iBACE,SAAA,SACA,QAAA,MACA,QAAA,OAAA,QAEA,cAAA,KACA,iBAAA,KACA,OAAA,IAAA,MAAA,iBAPF,6BnChCI,uBAAA,OACA,wBAAA,OmC+BJ,4BAcI,cAAA,EnChCA,2BAAA,OACA,0BAAA,OLHA,uBAAA,uBwCuCA,gBAAA,KAnBJ,0BAAA,0BAwBI,MAAA,QACA,iBAAA,KAzBJ,wBA8BI,QAAA,EACA,MAAA,KACA,iBAAA,QACA,aAAA,QAUJ,mCAEI,aAAA,EACA,YAAA,EACA,cAAA,EAJJ,2DASM,WAAA,EATN,yDAeM,cAAA,ECjGJ,yBACE,MAAA,QACA,iBAAA,QAIF,0B5C6wIF,+B4C3wII,MAAA,QzCWA,gCAAA,gCHqwIJ,qCACA,qC4C9wIM,MAAA,QACA,iBAAA,QANJ,iC5CyxIF,sC4C/wIM,MAAA,KACA,iBAAA,QACA,aAAA,QAlBJ,2BACE,MAAA,QACA,iBAAA,QAIF,4B5CqyIF,iC4CnyII,MAAA,QzCWA,kCAAA,kCH6xIJ,uCACA,uC4CtyIM,MAAA,QACA,iBAAA,QANJ,mC5CizIF,wC4CvyIM,MAAA,KACA,iBAAA,QACA,aAAA,QAlBJ,yBACE,MAAA,QACA,iBAAA,QAIF,0B5C6zIF,+B4C3zII,MAAA,QzCWA,gCAAA,gCHqzIJ,qCACA,qC4C9zIM,MAAA,QACA,iBAAA,QANJ,iC5Cy0IF,sC4C/zIM,MAAA,KACA,iBAAA,QACA,aAAA,QAlBJ,sBACE,MAAA,QACA,iBAAA,QAIF,uB5Cq1IF,4B4Cn1II,MAAA,QzCWA,6BAAA,6BH60IJ,kCACA,kC4Ct1IM,MAAA,QACA,iBAAA,QANJ,8B5Ci2IF,mC4Cv1IM,MAAA,KACA,iBAAA,QACA,aAAA,QAlBJ,yBACE,MAAA,QACA,iBAAA,QAIF,0B5C62IF,+B4C32II,MAAA,QzCWA,gCAAA,gCHq2IJ,qCACA,qC4C92IM,MAAA,QACA,iBAAA,QANJ,iC5Cy3IF,sC4C/2IM,MAAA,KACA,iBAAA,QACA,aAAA,QAlBJ,wBACE,MAAA,QACA,iBAAA,QAIF,yB5Cq4IF,8B4Cn4II,MAAA,QzCWA,+BAAA,+BH63IJ,oCACA,oC4Ct4IM,MAAA,QACA,iBAAA,QANJ,gC5Ci5IF,qC4Cv4IM,MAAA,KACA,iBAAA,QACA,aAAA,QAlBJ,uBACE,MAAA,QACA,iBAAA,QAIF,wB5C65IF,6B4C35II,MAAA,QzCWA,8BAAA,8BHq5IJ,mCACA,mC4C95IM,MAAA,QACA,iBAAA,QANJ,+B5Cy6IF,oC4C/5IM,MAAA,KACA,iBAAA,QACA,aAAA,QAlBJ,sBACE,MAAA,QACA,iBAAA,QAIF,uB5Cq7IF,4B4Cn7II,MAAA,QzCWA,6BAAA,6BH66IJ,kCACA,kC4Ct7IM,MAAA,QACA,iBAAA,QANJ,8B5Ci8IF,mC4Cv7IM,MAAA,KACA,iBAAA,QACA,aAAA,QCrBN,OACE,MAAA,MACA,UAAA,OACA,YAAA,IACA,YAAA,EACA,MAAA,KACA,YAAA,EAAA,IAAA,EAAA,KACA,QAAA,G1CeE,aAAA,a0CZA,MAAA,KACA,gBAAA,KACA,QAAA,IAUJ,aACE,QAAA,EACA,WAAA,IACA,OAAA,EACA,mBAAA,KCnBF,YACE,SAAA,OAIF,OACE,SAAA,MACA,IAAA,EACA,MAAA,EACA,OAAA,EACA,KAAA,EACA,QAAA,KACA,QAAA,KACA,SAAA,OAGA,QAAA,EAXF,0BrCPM,WAAA,kBAAA,IAAA,SAAA,WAAA,UAAA,IAAA,SAAA,WAAA,UAAA,IAAA,QAAA,CAAA,kBAAA,IAAA,SqC0BF,kBAAA,kBAAA,UAAA,kBAnBJ,0BAqByB,kBAAA,eAAA,UAAA,eAEzB,mBACE,WAAA,OACA,WAAA,KAIF,cACE,SAAA,SACA,MAAA,KACA,OAAA,KAIF,eACE,SAAA,SACA,QAAA,YAAA,QAAA,KACA,mBAAA,OAAA,eAAA,OACA,iBAAA,KACA,gBAAA,YACA,OAAA,IAAA,MAAA,etClDE,cAAA,MsCsDF,QAAA,EAIF,gBACE,SAAA,MACA,IAAA,EACA,MAAA,EACA,OAAA,EACA,KAAA,EACA,QAAA,KACA,iBAAA,KAPF,qBAUW,QAAA,EAVX,qBAWW,QAAA,GAKX,cACE,QAAA,YAAA,QAAA,KACA,eAAA,OAAA,YAAA,OACA,cAAA,QAAA,gBAAA,cACA,QAAA,KACA,cAAA,IAAA,MAAA,QAIF,aACE,cAAA,EACA,YAAA,IAKF,YACE,SAAA,SAGA,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KACA,QAAA,KAIF,cACE,QAAA,YAAA,QAAA,KACA,eAAA,OAAA,YAAA,OACA,cAAA,IAAA,gBAAA,SACA,QAAA,KACA,WAAA,IAAA,MAAA,QALF,iCAQyB,YAAA,OARzB,gCASwB,aAAA,OAIxB,yBACE,SAAA,SACA,IAAA,QACA,MAAA,KACA,OAAA,KACA,SAAA,OjCjEE,yBiCuEF,cACE,UAAA,MACA,OAAA,KAAA,KAOF,UAAY,UAAA,OjChFV,yBiCoFF,UAAY,UAAA,OC3Id,SACE,SAAA,SACA,QAAA,KACA,QAAA,MACA,OAAA,ECHA,YAAA,aAAA,CAAA,kBAAA,CAAA,UAAA,CAAA,MAAA,CAAA,gBAAA,CAAA,KAAA,CAAA,WAEA,WAAA,OACA,YAAA,IACA,YAAA,IACA,WAAA,KACA,WAAA,MACA,gBAAA,KACA,YAAA,KACA,eAAA,KACA,eAAA,OACA,WAAA,OACA,aAAA,OACA,YAAA,OACA,WAAA,KDPA,UAAA,QAEA,UAAA,WACA,QAAA,EAXF,cAaW,QAAA,GAbX,gBAgBI,SAAA,SACA,QAAA,MACA,MAAA,IACA,OAAA,IAnBJ,2CAAA,wBAuBI,QAAA,IAAA,EAvBJ,kDAAA,+BAyBM,OAAA,EAzBN,0DAAA,uCA6BM,YAAA,KACA,QAAA,GACA,aAAA,IAAA,IAAA,EACA,iBAAA,KAhCN,6CAAA,0BAoCI,QAAA,EAAA,IApCJ,oDAAA,iCAsCM,KAAA,EAtCN,4DAAA,yCA0CM,WAAA,KACA,QAAA,GACA,aAAA,IAAA,IAAA,IAAA,EACA,mBAAA,KA7CN,8CAAA,2BAiDI,QAAA,IAAA,EAjDJ,qDAAA,kCAmDM,IAAA,EAnDN,6DAAA,0CAuDM,YAAA,KACA,QAAA,GACA,aAAA,EAAA,IAAA,IACA,oBAAA,KA1DN,4CAAA,yBA8DI,QAAA,EAAA,IA9DJ,mDAAA,gCAgEM,MAAA,EAhEN,2DAAA,wCAoEM,MAAA,EACA,WAAA,KACA,QAAA,GACA,aAAA,IAAA,EAAA,IAAA,IACA,kBAAA,KAxEN,wBA2FI,SAAA,SACA,aAAA,YACA,aAAA,MAKJ,eACE,UAAA,MACA,QAAA,IAAA,IACA,MAAA,KACA,WAAA,OACA,iBAAA,KvCpGE,cAAA,OyCJJ,SACE,SAAA,SACA,IAAA,EACA,KAAA,EACA,QAAA,KACA,QAAA,MACA,UAAA,MACA,QAAA,IDLA,YAAA,aAAA,CAAA,kBAAA,CAAA,UAAA,CAAA,MAAA,CAAA,gBAAA,CAAA,KAAA,CAAA,WAEA,WAAA,OACA,YAAA,IACA,YAAA,IACA,WAAA,KACA,WAAA,MACA,gBAAA,KACA,YAAA,KACA,eAAA,KACA,eAAA,OACA,WAAA,OACA,aAAA,OACA,YAAA,OACA,WAAA,KCLA,UAAA,QAEA,UAAA,WACA,iBAAA,KACA,gBAAA,YACA,OAAA,IAAA,MAAA,ezCZE,cAAA,MyCJJ,gBAyBI,SAAA,SACA,QAAA,MACA,MAAA,KACA,OAAA,IjDyuJJ,uBiDrwJA,wBAiCI,SAAA,SACA,QAAA,MACA,aAAA,YACA,aAAA,MApCJ,wBAwCI,QAAA,GACA,aAAA,KAzCJ,uBA4CI,QAAA,GACA,aAAA,KA7CJ,2CAAA,wBAmDI,cAAA,KAnDJ,kDAAA,+BAsDM,OAAA,EjDyuJiC,yDiD/xJvC,0DjD+xJA,sCiD/xJA,uCA2DM,oBAAA,EA3DN,0DAAA,uCA+DM,OAAA,MACA,YAAA,KACA,iBAAA,gBAjEN,yDAAA,sCAqEM,OAAA,MACA,YAAA,KACA,iBAAA,KAvEN,6CAAA,0BA4EI,YAAA,KA5EJ,oDAAA,iCA+EM,KAAA,EjDyuJmC,2DiDxzJzC,4DjDwzJA,wCiDxzJA,yCAoFM,WAAA,KACA,kBAAA,EArFN,4DAAA,yCAyFM,KAAA,MACA,mBAAA,gBA1FN,2DAAA,wCA8FM,KAAA,MACA,mBAAA,KA/FN,8CAAA,2BAoGI,WAAA,KApGJ,qDAAA,kCAuGM,IAAA,EjDyuJoC,4DiDh1J1C,6DjDg1JA,yCiDh1JA,0CA4GM,YAAA,KACA,iBAAA,EA7GN,6DAAA,0CAiHM,IAAA,MACA,oBAAA,gBAlHN,4DAAA,yCAsHM,IAAA,MACA,oBAAA,KAvHN,sEAAA,mDA4HM,SAAA,SACA,IAAA,EACA,KAAA,IACA,QAAA,MACA,MAAA,KACA,YAAA,MACA,QAAA,GACA,cAAA,IAAA,MAAA,QAnIN,4CAAA,yBAwII,aAAA,KAxIJ,mDAAA,gCA2IM,MAAA,EjDwuJkC,0DiDn3JxC,2DjDm3JA,uCiDn3JA,wCAgJM,WAAA,KACA,mBAAA,EAjJN,2DAAA,wCAqJM,MAAA,MACA,kBAAA,gBAtJN,0DAAA,uCA0JM,MAAA,MACA,kBAAA,KAqBN,gBACE,QAAA,IAAA,KACA,cAAA,EACA,UAAA,KACA,MAAA,QACA,iBAAA,QACA,cAAA,IAAA,MAAA,QzC5KE,uBAAA,kBACA,wBAAA,kByCqKJ,sBAWI,QAAA,KAIJ,cACE,QAAA,IAAA,KACA,MAAA,QChMF,UACE,SAAA,SAGF,gBACE,SAAA,SACA,MAAA,KACA,SAAA,OAGF,eACE,SAAA,SACA,QAAA,KACA,eAAA,OAAA,YAAA,OACA,MAAA,KzCVI,WAAA,kBAAA,IAAA,KAAA,WAAA,UAAA,IAAA,KAAA,WAAA,UAAA,IAAA,IAAA,CAAA,kBAAA,IAAA,KyCYJ,4BAAA,OAAA,oBAAA,OACA,oBAAA,OAAA,YAAA,OlD85JF,oBACA,oBkD55JA,sBAGE,QAAA,MAGF,oBlD25JA,oBkDz5JE,SAAA,SACA,IAAA,EAIF,uClD05JA,wCkDx5JE,kBAAA,cAAA,UAAA,cAEwC,mFAJ1C,uClDi6JE,wCkD55JE,kBAAA,mBAAA,UAAA,oBlDm6JJ,4BkD/5JA,oBAEE,kBAAA,iBAAA,UAAA,iBAEwC,mFlDk6JxC,4BkDt6JF,oBAKI,kBAAA,sBAAA,UAAA,uBlDw6JJ,2BkDp6JA,oBAEE,kBAAA,kBAAA,UAAA,kBAEwC,mFlDu6JxC,2BkD36JF,oBAKI,kBAAA,uBAAA,UAAA,wBlD66JJ,uBkDp6JA,uBAEE,SAAA,SACA,IAAA,EACA,OAAA,EAEA,QAAA,YAAA,QAAA,KACA,eAAA,OAAA,YAAA,OACA,cAAA,OAAA,gBAAA,OACA,MAAA,IACA,MAAA,KACA,WAAA,OACA,QAAA,GlDy6JF,6BACA,6BGl+JI,6BAAA,6B+C8DA,MAAA,KACA,gBAAA,KACA,QAAA,EACA,QAAA,GAGJ,uBACE,KAAA,EAEF,uBACE,MAAA,ElD06JF,4BkDt6JA,4BAEE,QAAA,aACA,MAAA,KACA,OAAA,KACA,WAAA,YAAA,UAAA,OAAA,OACA,gBAAA,KAAA,KAEF,4BACE,iBAAA,4LAEF,4BACE,iBAAA,8LASF,qBACE,SAAA,SACA,MAAA,EACA,OAAA,KACA,KAAA,EACA,QAAA,GACA,QAAA,YAAA,QAAA,KACA,cAAA,OAAA,gBAAA,OACA,aAAA,EAEA,aAAA,IACA,YAAA,IACA,WAAA,KAZF,wBAeI,SAAA,SACA,SAAA,EAAA,EAAA,KAAA,KAAA,EAAA,EAAA,KACA,MAAA,KACA,OAAA,IACA,aAAA,IACA,YAAA,IACA,YAAA,OACA,iBAAA,qBAtBJ,gCA0BM,SAAA,SACA,IAAA,MACA,KAAA,EACA,QAAA,aACA,MAAA,KACA,OAAA,KACA,QAAA,GAhCN,+BAmCM,SAAA,SACA,OAAA,MACA,KAAA,EACA,QAAA,aACA,MAAA,KACA,OAAA,KACA,QAAA,GAzCN,6BA8CI,iBAAA,KASJ,kBACE,SAAA,SACA,MAAA,IACA,OAAA,KACA,KAAA,IACA,QAAA,GACA,YAAA,KACA,eAAA,KACA,MAAA,KACA,WAAA,OCvLF,gBAAqB,eAAA,mBACrB,WAAqB,eAAA,cACrB,cAAqB,eAAA,iBACrB,cAAqB,eAAA,iBACrB,mBAAqB,eAAA,sBACrB,gBAAqB,eAAA,mBCFnB,YACE,iBAAA,kBjDkBA,mBAAA,mBiDdE,iBAAA,kBALJ,cACE,iBAAA,kBjDkBA,qBAAA,qBiDdE,iBAAA,kBALJ,YACE,iBAAA,kBjDkBA,mBAAA,mBiDdE,iBAAA,kBALJ,SACE,iBAAA,kBjDkBA,gBAAA,gBiDdE,iBAAA,kBALJ,YACE,iBAAA,kBjDkBA,mBAAA,mBiDdE,iBAAA,kBALJ,WACE,iBAAA,kBjDkBA,kBAAA,kBiDdE,iBAAA,kBALJ,UACE,iBAAA,kBjDkBA,iBAAA,iBiDdE,iBAAA,kBALJ,SACE,iBAAA,kBjDkBA,gBAAA,gBiDdE,iBAAA,kBCJN,UAAY,iBAAA,eACZ,gBAAkB,iBAAA,sBCDlB,QAAmB,OAAA,IAAA,MAAA,kBACnB,UAAmB,OAAA,YACnB,cAAmB,WAAA,YACnB,gBAAmB,aAAA,YACnB,iBAAmB,cAAA,YACnB,eAAmB,YAAA,YAGjB,gBACE,aAAA,kBADF,kBACE,aAAA,kBADF,gBACE,aAAA,kBADF,aACE,aAAA,kBADF,gBACE,aAAA,kBADF,eACE,aAAA,kBADF,cACE,aAAA,kBADF,aACE,aAAA,kBAIJ,cACE,aAAA,eAOF,SACE,cAAA,iBAEF,aACE,uBAAA,iBACA,wBAAA,iBAEF,eACE,wBAAA,iBACA,2BAAA,iBAEF,gBACE,2BAAA,iBACA,0BAAA,iBAEF,cACE,uBAAA,iBACA,0BAAA,iBAGF,gBACE,cAAA,IAGF,WACE,cAAA,EtBjDA,iBACE,QAAA,MACA,MAAA,KACA,QAAA,GuBIA,QAA2B,QAAA,eAC3B,UAA2B,QAAA,iBAC3B,gBAA2B,QAAA,uBAC3B,SAA2B,QAAA,gBAC3B,SAA2B,QAAA,gBAC3B,cAA2B,QAAA,qBAC3B,QAA2B,QAAA,sBAAA,QAAA,eAC3B,eAA2B,QAAA,6BAAA,QAAA,sB1CyC3B,yB0ChDA,WAA2B,QAAA,eAC3B,aAA2B,QAAA,iBAC3B,mBAA2B,QAAA,uBAC3B,YAA2B,QAAA,gBAC3B,YAA2B,QAAA,gBAC3B,iBAA2B,QAAA,qBAC3B,WAA2B,QAAA,sBAAA,QAAA,eAC3B,kBAA2B,QAAA,6BAAA,QAAA,uB1CyC3B,yB0ChDA,WAA2B,QAAA,eAC3B,aAA2B,QAAA,iBAC3B,mBAA2B,QAAA,uBAC3B,YAA2B,QAAA,gBAC3B,YAA2B,QAAA,gBAC3B,iBAA2B,QAAA,qBAC3B,WAA2B,QAAA,sBAAA,QAAA,eAC3B,kBAA2B,QAAA,6BAAA,QAAA,uB1CyC3B,yB0ChDA,WAA2B,QAAA,eAC3B,aAA2B,QAAA,iBAC3B,mBAA2B,QAAA,uBAC3B,YAA2B,QAAA,gBAC3B,YAA2B,QAAA,gBAC3B,iBAA2B,QAAA,qBAC3B,WAA2B,QAAA,sBAAA,QAAA,eAC3B,kBAA2B,QAAA,6BAAA,QAAA,uB1CyC3B,0B0ChDA,WAA2B,QAAA,eAC3B,aAA2B,QAAA,iBAC3B,mBAA2B,QAAA,uBAC3B,YAA2B,QAAA,gBAC3B,YAA2B,QAAA,gBAC3B,iBAA2B,QAAA,qBAC3B,WAA2B,QAAA,sBAAA,QAAA,eAC3B,kBAA2B,QAAA,6BAAA,QAAA,uBAS/B,eACE,QAAA,eAEA,aAHF,eAII,QAAA,iBAIJ,gBACE,QAAA,eAEA,aAHF,gBAII,QAAA,kBAIJ,sBACE,QAAA,eAEA,aAHF,sBAII,QAAA,wBAKF,aADF,cAEI,QAAA,gBChDJ,kBACE,SAAA,SACA,QAAA,MACA,MAAA,KACA,QAAA,EACA,SAAA,OALF,0BAQI,QAAA,MACA,QAAA,GATJ,yCxDi+KA,wBADA,yBAEA,yBACA,wBwDl9KI,SAAA,SACA,IAAA,EACA,OAAA,EACA,KAAA,EACA,MAAA,KACA,OAAA,KACA,OAAA,EAIJ,gCAEI,YAAA,WAIJ,gCAEI,YAAA,OAIJ,+BAEI,YAAA,IAIJ,+BAEI,YAAA,KCzCA,UAAgC,mBAAA,cAAA,eAAA,cAChC,aAAgC,mBAAA,iBAAA,eAAA,iBAChC,kBAAgC,mBAAA,sBAAA,eAAA,sBAChC,qBAAgC,mBAAA,yBAAA,eAAA,yBAEhC,WAA8B,cAAA,eAAA,UAAA,eAC9B,aAA8B,cAAA,iBAAA,UAAA,iBAC9B,mBAA8B,cAAA,uBAAA,UAAA,uBAE9B,uBAAoC,cAAA,gBAAA,gBAAA,qBACpC,qBAAoC,cAAA,cAAA,gBAAA,mBACpC,wBAAoC,cAAA,iBAAA,gBAAA,iBACpC,yBAAoC,cAAA,kBAAA,gBAAA,wBACpC,wBAAoC,cAAA,qBAAA,gBAAA,uBAEpC,mBAAiC,eAAA,gBAAA,YAAA,qBACjC,iBAAiC,eAAA,cAAA,YAAA,mBACjC,oBAAiC,eAAA,iBAAA,YAAA,iBACjC,sBAAiC,eAAA,mBAAA,YAAA,mBACjC,qBAAiC,eAAA,kBAAA,YAAA,kBAEjC,qBAAkC,mBAAA,gBAAA,cAAA,qBAClC,mBAAkC,mBAAA,cAAA,cAAA,mBAClC,sBAAkC,mBAAA,iBAAA,cAAA,iBAClC,uBAAkC,mBAAA,kBAAA,cAAA,wBAClC,sBAAkC,mBAAA,qBAAA,cAAA,uBAClC,uBAAkC,mBAAA,kBAAA,cAAA,kBAElC,iBAAgC,oBAAA,eAAA,WAAA,eAChC,kBAAgC,oBAAA,gBAAA,WAAA,qBAChC,gBAAgC,oBAAA,cAAA,WAAA,mBAChC,mBAAgC,oBAAA,iBAAA,WAAA,iBAChC,qBAAgC,oBAAA,mBAAA,WAAA,mBAChC,oBAAgC,oBAAA,kBAAA,WAAA,kB5CehC,yB4ChDA,aAAgC,mBAAA,cAAA,eAAA,cAChC,gBAAgC,mBAAA,iBAAA,eAAA,iBAChC,qBAAgC,mBAAA,sBAAA,eAAA,sBAChC,wBAAgC,mBAAA,yBAAA,eAAA,yBAEhC,cAA8B,cAAA,eAAA,UAAA,eAC9B,gBAA8B,cAAA,iBAAA,UAAA,iBAC9B,sBAA8B,cAAA,uBAAA,UAAA,uBAE9B,0BAAoC,cAAA,gBAAA,gBAAA,qBACpC,wBAAoC,cAAA,cAAA,gBAAA,mBACpC,2BAAoC,cAAA,iBAAA,gBAAA,iBACpC,4BAAoC,cAAA,kBAAA,gBAAA,wBACpC,2BAAoC,cAAA,qBAAA,gBAAA,uBAEpC,sBAAiC,eAAA,gBAAA,YAAA,qBACjC,oBAAiC,eAAA,cAAA,YAAA,mBACjC,uBAAiC,eAAA,iBAAA,YAAA,iBACjC,yBAAiC,eAAA,mBAAA,YAAA,mBACjC,wBAAiC,eAAA,kBAAA,YAAA,kBAEjC,wBAAkC,mBAAA,gBAAA,cAAA,qBAClC,sBAAkC,mBAAA,cAAA,cAAA,mBAClC,yBAAkC,mBAAA,iBAAA,cAAA,iBAClC,0BAAkC,mBAAA,kBAAA,cAAA,wBAClC,yBAAkC,mBAAA,qBAAA,cAAA,uBAClC,0BAAkC,mBAAA,kBAAA,cAAA,kBAElC,oBAAgC,oBAAA,eAAA,WAAA,eAChC,qBAAgC,oBAAA,gBAAA,WAAA,qBAChC,mBAAgC,oBAAA,cAAA,WAAA,mBAChC,sBAAgC,oBAAA,iBAAA,WAAA,iBAChC,wBAAgC,oBAAA,mBAAA,WAAA,mBAChC,uBAAgC,oBAAA,kBAAA,WAAA,mB5CehC,yB4ChDA,aAAgC,mBAAA,cAAA,eAAA,cAChC,gBAAgC,mBAAA,iBAAA,eAAA,iBAChC,qBAAgC,mBAAA,sBAAA,eAAA,sBAChC,wBAAgC,mBAAA,yBAAA,eAAA,yBAEhC,cAA8B,cAAA,eAAA,UAAA,eAC9B,gBAA8B,cAAA,iBAAA,UAAA,iBAC9B,sBAA8B,cAAA,uBAAA,UAAA,uBAE9B,0BAAoC,cAAA,gBAAA,gBAAA,qBACpC,wBAAoC,cAAA,cAAA,gBAAA,mBACpC,2BAAoC,cAAA,iBAAA,gBAAA,iBACpC,4BAAoC,cAAA,kBAAA,gBAAA,wBACpC,2BAAoC,cAAA,qBAAA,gBAAA,uBAEpC,sBAAiC,eAAA,gBAAA,YAAA,qBACjC,oBAAiC,eAAA,cAAA,YAAA,mBACjC,uBAAiC,eAAA,iBAAA,YAAA,iBACjC,yBAAiC,eAAA,mBAAA,YAAA,mBACjC,wBAAiC,eAAA,kBAAA,YAAA,kBAEjC,wBAAkC,mBAAA,gBAAA,cAAA,qBAClC,sBAAkC,mBAAA,cAAA,cAAA,mBAClC,yBAAkC,mBAAA,iBAAA,cAAA,iBAClC,0BAAkC,mBAAA,kBAAA,cAAA,wBAClC,yBAAkC,mBAAA,qBAAA,cAAA,uBAClC,0BAAkC,mBAAA,kBAAA,cAAA,kBAElC,oBAAgC,oBAAA,eAAA,WAAA,eAChC,qBAAgC,oBAAA,gBAAA,WAAA,qBAChC,mBAAgC,oBAAA,cAAA,WAAA,mBAChC,sBAAgC,oBAAA,iBAAA,WAAA,iBAChC,wBAAgC,oBAAA,mBAAA,WAAA,mBAChC,uBAAgC,oBAAA,kBAAA,WAAA,mB5CehC,yB4ChDA,aAAgC,mBAAA,cAAA,eAAA,cAChC,gBAAgC,mBAAA,iBAAA,eAAA,iBAChC,qBAAgC,mBAAA,sBAAA,eAAA,sBAChC,wBAAgC,mBAAA,yBAAA,eAAA,yBAEhC,cAA8B,cAAA,eAAA,UAAA,eAC9B,gBAA8B,cAAA,iBAAA,UAAA,iBAC9B,sBAA8B,cAAA,uBAAA,UAAA,uBAE9B,0BAAoC,cAAA,gBAAA,gBAAA,qBACpC,wBAAoC,cAAA,cAAA,gBAAA,mBACpC,2BAAoC,cAAA,iBAAA,gBAAA,iBACpC,4BAAoC,cAAA,kBAAA,gBAAA,wBACpC,2BAAoC,cAAA,qBAAA,gBAAA,uBAEpC,sBAAiC,eAAA,gBAAA,YAAA,qBACjC,oBAAiC,eAAA,cAAA,YAAA,mBACjC,uBAAiC,eAAA,iBAAA,YAAA,iBACjC,yBAAiC,eAAA,mBAAA,YAAA,mBACjC,wBAAiC,eAAA,kBAAA,YAAA,kBAEjC,wBAAkC,mBAAA,gBAAA,cAAA,qBAClC,sBAAkC,mBAAA,cAAA,cAAA,mBAClC,yBAAkC,mBAAA,iBAAA,cAAA,iBAClC,0BAAkC,mBAAA,kBAAA,cAAA,wBAClC,yBAAkC,mBAAA,qBAAA,cAAA,uBAClC,0BAAkC,mBAAA,kBAAA,cAAA,kBAElC,oBAAgC,oBAAA,eAAA,WAAA,eAChC,qBAAgC,oBAAA,gBAAA,WAAA,qBAChC,mBAAgC,oBAAA,cAAA,WAAA,mBAChC,sBAAgC,oBAAA,iBAAA,WAAA,iBAChC,wBAAgC,oBAAA,mBAAA,WAAA,mBAChC,uBAAgC,oBAAA,kBAAA,WAAA,mB5CehC,0B4ChDA,aAAgC,mBAAA,cAAA,eAAA,cAChC,gBAAgC,mBAAA,iBAAA,eAAA,iBAChC,qBAAgC,mBAAA,sBAAA,eAAA,sBAChC,wBAAgC,mBAAA,yBAAA,eAAA,yBAEhC,cAA8B,cAAA,eAAA,UAAA,eAC9B,gBAA8B,cAAA,iBAAA,UAAA,iBAC9B,sBAA8B,cAAA,uBAAA,UAAA,uBAE9B,0BAAoC,cAAA,gBAAA,gBAAA,qBACpC,wBAAoC,cAAA,cAAA,gBAAA,mBACpC,2BAAoC,cAAA,iBAAA,gBAAA,iBACpC,4BAAoC,cAAA,kBAAA,gBAAA,wBACpC,2BAAoC,cAAA,qBAAA,gBAAA,uBAEpC,sBAAiC,eAAA,gBAAA,YAAA,qBACjC,oBAAiC,eAAA,cAAA,YAAA,mBACjC,uBAAiC,eAAA,iBAAA,YAAA,iBACjC,yBAAiC,eAAA,mBAAA,YAAA,mBACjC,wBAAiC,eAAA,kBAAA,YAAA,kBAEjC,wBAAkC,mBAAA,gBAAA,cAAA,qBAClC,sBAAkC,mBAAA,cAAA,cAAA,mBAClC,yBAAkC,mBAAA,iBAAA,cAAA,iBAClC,0BAAkC,mBAAA,kBAAA,cAAA,wBAClC,yBAAkC,mBAAA,qBAAA,cAAA,uBAClC,0BAAkC,mBAAA,kBAAA,cAAA,kBAElC,oBAAgC,oBAAA,eAAA,WAAA,eAChC,qBAAgC,oBAAA,gBAAA,WAAA,qBAChC,mBAAgC,oBAAA,cAAA,WAAA,mBAChC,sBAAgC,oBAAA,iBAAA,WAAA,iBAChC,wBAAgC,oBAAA,mBAAA,WAAA,mBAChC,uBAAgC,oBAAA,kBAAA,WAAA,mBCrChC,YCHF,MAAA,eDIE,aCDF,MAAA,gBDEE,YCCF,MAAA,e9CiDE,yB6CpDA,eCHF,MAAA,eDIE,gBCDF,MAAA,gBDEE,eCCF,MAAA,gB9CiDE,yB6CpDA,eCHF,MAAA,eDIE,gBCDF,MAAA,gBDEE,eCCF,MAAA,gB9CiDE,yB6CpDA,eCHF,MAAA,eDIE,gBCDF,MAAA,gBDEE,eCCF,MAAA,gB9CiDE,0B6CpDA,eCHF,MAAA,eDIE,gBCDF,MAAA,gBDEE,eCCF,MAAA,gBCLF,WACE,SAAA,MACA,IAAA,EACA,MAAA,EACA,KAAA,EACA,QAAA,KAGF,cACE,SAAA,MACA,MAAA,EACA,OAAA,EACA,KAAA,EACA,QAAA,KAI4B,2DAD9B,YAEI,SAAA,eAAA,SAAA,OACA,IAAA,EACA,QAAA,MClBJ,SCEE,SAAA,SACA,MAAA,IACA,OAAA,IACA,QAAA,EACA,SAAA,OACA,KAAA,cACA,YAAA,OACA,kBAAA,WAAA,UAAA,WACA,OAAA,EAUA,0BAAA,yBAEE,SAAA,OACA,MAAA,KACA,OAAA,KACA,SAAA,QACA,KAAA,KACA,YAAA,OACA,kBAAA,KAAA,UAAA,KC5BA,MAAuB,MAAA,cAAvB,MAAuB,MAAA,cAAvB,MAAuB,MAAA,cAAvB,OAAuB,MAAA,eAAvB,MAAuB,OAAA,cAAvB,MAAuB,OAAA,cAAvB,MAAuB,OAAA,cAAvB,OAAuB,OAAA,eAI3B,QAAU,UAAA,eACV,QAAU,WAAA,eCAF,KAAiC,OAAA,YACjC,MAAiC,WAAA,YACjC,MAAiC,aAAA,YACjC,MAAiC,cAAA,YACjC,MAAiC,YAAA,YACjC,MACE,aAAA,YACA,YAAA,YAEF,MACE,WAAA,YACA,cAAA,YAXF,KAAiC,OAAA,iBACjC,MAAiC,WAAA,iBACjC,MAAiC,aAAA,iBACjC,MAAiC,cAAA,iBACjC,MAAiC,YAAA,iBACjC,MACE,aAAA,iBACA,YAAA,iBAEF,MACE,WAAA,iBACA,cAAA,iBAXF,KAAiC,OAAA,gBACjC,MAAiC,WAAA,gBACjC,MAAiC,aAAA,gBACjC,MAAiC,cAAA,gBACjC,MAAiC,YAAA,gBACjC,MACE,aAAA,gBACA,YAAA,gBAEF,MACE,WAAA,gBACA,cAAA,gBAXF,KAAiC,OAAA,eACjC,MAAiC,WAAA,eACjC,MAAiC,aAAA,eACjC,MAAiC,cAAA,eACjC,MAAiC,YAAA,eACjC,MACE,aAAA,eACA,YAAA,eAEF,MACE,WAAA,eACA,cAAA,eAXF,KAAiC,OAAA,iBACjC,MAAiC,WAAA,iBACjC,MAAiC,aAAA,iBACjC,MAAiC,cAAA,iBACjC,MAAiC,YAAA,iBACjC,MACE,aAAA,iBACA,YAAA,iBAEF,MACE,WAAA,iBACA,cAAA,iBAXF,KAAiC,OAAA,eACjC,MAAiC,WAAA,eACjC,MAAiC,aAAA,eACjC,MAAiC,cAAA,eACjC,MAAiC,YAAA,eACjC,MACE,aAAA,eACA,YAAA,eAEF,MACE,WAAA,eACA,cAAA,eAXF,KAAiC,QAAA,YACjC,MAAiC,YAAA,YACjC,MAAiC,cAAA,YACjC,MAAiC,eAAA,YACjC,MAAiC,aAAA,YACjC,MACE,cAAA,YACA,aAAA,YAEF,MACE,YAAA,YACA,eAAA,YAXF,KAAiC,QAAA,iBACjC,MAAiC,YAAA,iBACjC,MAAiC,cAAA,iBACjC,MAAiC,eAAA,iBACjC,MAAiC,aAAA,iBACjC,MACE,cAAA,iBACA,aAAA,iBAEF,MACE,YAAA,iBACA,eAAA,iBAXF,KAAiC,QAAA,gBACjC,MAAiC,YAAA,gBACjC,MAAiC,cAAA,gBACjC,MAAiC,eAAA,gBACjC,MAAiC,aAAA,gBACjC,MACE,cAAA,gBACA,aAAA,gBAEF,MACE,YAAA,gBACA,eAAA,gBAXF,KAAiC,QAAA,eACjC,MAAiC,YAAA,eACjC,MAAiC,cAAA,eACjC,MAAiC,eAAA,eACjC,MAAiC,aAAA,eACjC,MACE,cAAA,eACA,aAAA,eAEF,MACE,YAAA,eACA,eAAA,eAXF,KAAiC,QAAA,iBACjC,MAAiC,YAAA,iBACjC,MAAiC,cAAA,iBACjC,MAAiC,eAAA,iBACjC,MAAiC,aAAA,iBACjC,MACE,cAAA,iBACA,aAAA,iBAEF,MACE,YAAA,iBACA,eAAA,iBAXF,KAAiC,QAAA,eACjC,MAAiC,YAAA,eACjC,MAAiC,cAAA,eACjC,MAAiC,eAAA,eACjC,MAAiC,aAAA,eACjC,MACE,cAAA,eACA,aAAA,eAEF,MACE,YAAA,eACA,eAAA,eAMN,QAAoB,OAAA,eACpB,SAAoB,WAAA,eACpB,SAAoB,aAAA,eACpB,SAAoB,cAAA,eACpB,SAAoB,YAAA,eACpB,SACE,aAAA,eACA,YAAA,eAEF,SACE,WAAA,eACA,cAAA,enDmBF,yBmD/CI,QAAiC,OAAA,YACjC,SAAiC,WAAA,YACjC,SAAiC,aAAA,YACjC,SAAiC,cAAA,YACjC,SAAiC,YAAA,YACjC,SACE,aAAA,YACA,YAAA,YAEF,SACE,WAAA,YACA,cAAA,YAXF,QAAiC,OAAA,iBACjC,SAAiC,WAAA,iBACjC,SAAiC,aAAA,iBACjC,SAAiC,cAAA,iBACjC,SAAiC,YAAA,iBACjC,SACE,aAAA,iBACA,YAAA,iBAEF,SACE,WAAA,iBACA,cAAA,iBAXF,QAAiC,OAAA,gBACjC,SAAiC,WAAA,gBACjC,SAAiC,aAAA,gBACjC,SAAiC,cAAA,gBACjC,SAAiC,YAAA,gBACjC,SACE,aAAA,gBACA,YAAA,gBAEF,SACE,WAAA,gBACA,cAAA,gBAXF,QAAiC,OAAA,eACjC,SAAiC,WAAA,eACjC,SAAiC,aAAA,eACjC,SAAiC,cAAA,eACjC,SAAiC,YAAA,eACjC,SACE,aAAA,eACA,YAAA,eAEF,SACE,WAAA,eACA,cAAA,eAXF,QAAiC,OAAA,iBACjC,SAAiC,WAAA,iBACjC,SAAiC,aAAA,iBACjC,SAAiC,cAAA,iBACjC,SAAiC,YAAA,iBACjC,SACE,aAAA,iBACA,YAAA,iBAEF,SACE,WAAA,iBACA,cAAA,iBAXF,QAAiC,OAAA,eACjC,SAAiC,WAAA,eACjC,SAAiC,aAAA,eACjC,SAAiC,cAAA,eACjC,SAAiC,YAAA,eACjC,SACE,aAAA,eACA,YAAA,eAEF,SACE,WAAA,eACA,cAAA,eAXF,QAAiC,QAAA,YACjC,SAAiC,YAAA,YACjC,SAAiC,cAAA,YACjC,SAAiC,eAAA,YACjC,SAAiC,aAAA,YACjC,SACE,cAAA,YACA,aAAA,YAEF,SACE,YAAA,YACA,eAAA,YAXF,QAAiC,QAAA,iBACjC,SAAiC,YAAA,iBACjC,SAAiC,cAAA,iBACjC,SAAiC,eAAA,iBACjC,SAAiC,aAAA,iBACjC,SACE,cAAA,iBACA,aAAA,iBAEF,SACE,YAAA,iBACA,eAAA,iBAXF,QAAiC,QAAA,gBACjC,SAAiC,YAAA,gBACjC,SAAiC,cAAA,gBACjC,SAAiC,eAAA,gBACjC,SAAiC,aAAA,gBACjC,SACE,cAAA,gBACA,aAAA,gBAEF,SACE,YAAA,gBACA,eAAA,gBAXF,QAAiC,QAAA,eACjC,SAAiC,YAAA,eACjC,SAAiC,cAAA,eACjC,SAAiC,eAAA,eACjC,SAAiC,aAAA,eACjC,SACE,cAAA,eACA,aAAA,eAEF,SACE,YAAA,eACA,eAAA,eAXF,QAAiC,QAAA,iBACjC,SAAiC,YAAA,iBACjC,SAAiC,cAAA,iBACjC,SAAiC,eAAA,iBACjC,SAAiC,aAAA,iBACjC,SACE,cAAA,iBACA,aAAA,iBAEF,SACE,YAAA,iBACA,eAAA,iBAXF,QAAiC,QAAA,eACjC,SAAiC,YAAA,eACjC,SAAiC,cAAA,eACjC,SAAiC,eAAA,eACjC,SAAiC,aAAA,eACjC,SACE,cAAA,eACA,aAAA,eAEF,SACE,YAAA,eACA,eAAA,eAMN,WAAoB,OAAA,eACpB,YAAoB,WAAA,eACpB,YAAoB,aAAA,eACpB,YAAoB,cAAA,eACpB,YAAoB,YAAA,eACpB,YACE,aAAA,eACA,YAAA,eAEF,YACE,WAAA,eACA,cAAA,gBnDmBF,yBmD/CI,QAAiC,OAAA,YACjC,SAAiC,WAAA,YACjC,SAAiC,aAAA,YACjC,SAAiC,cAAA,YACjC,SAAiC,YAAA,YACjC,SACE,aAAA,YACA,YAAA,YAEF,SACE,WAAA,YACA,cAAA,YAXF,QAAiC,OAAA,iBACjC,SAAiC,WAAA,iBACjC,SAAiC,aAAA,iBACjC,SAAiC,cAAA,iBACjC,SAAiC,YAAA,iBACjC,SACE,aAAA,iBACA,YAAA,iBAEF,SACE,WAAA,iBACA,cAAA,iBAXF,QAAiC,OAAA,gBACjC,SAAiC,WAAA,gBACjC,SAAiC,aAAA,gBACjC,SAAiC,cAAA,gBACjC,SAAiC,YAAA,gBACjC,SACE,aAAA,gBACA,YAAA,gBAEF,SACE,WAAA,gBACA,cAAA,gBAXF,QAAiC,OAAA,eACjC,SAAiC,WAAA,eACjC,SAAiC,aAAA,eACjC,SAAiC,cAAA,eACjC,SAAiC,YAAA,eACjC,SACE,aAAA,eACA,YAAA,eAEF,SACE,WAAA,eACA,cAAA,eAXF,QAAiC,OAAA,iBACjC,SAAiC,WAAA,iBACjC,SAAiC,aAAA,iBACjC,SAAiC,cAAA,iBACjC,SAAiC,YAAA,iBACjC,SACE,aAAA,iBACA,YAAA,iBAEF,SACE,WAAA,iBACA,cAAA,iBAXF,QAAiC,OAAA,eACjC,SAAiC,WAAA,eACjC,SAAiC,aAAA,eACjC,SAAiC,cAAA,eACjC,SAAiC,YAAA,eACjC,SACE,aAAA,eACA,YAAA,eAEF,SACE,WAAA,eACA,cAAA,eAXF,QAAiC,QAAA,YACjC,SAAiC,YAAA,YACjC,SAAiC,cAAA,YACjC,SAAiC,eAAA,YACjC,SAAiC,aAAA,YACjC,SACE,cAAA,YACA,aAAA,YAEF,SACE,YAAA,YACA,eAAA,YAXF,QAAiC,QAAA,iBACjC,SAAiC,YAAA,iBACjC,SAAiC,cAAA,iBACjC,SAAiC,eAAA,iBACjC,SAAiC,aAAA,iBACjC,SACE,cAAA,iBACA,aAAA,iBAEF,SACE,YAAA,iBACA,eAAA,iBAXF,QAAiC,QAAA,gBACjC,SAAiC,YAAA,gBACjC,SAAiC,cAAA,gBACjC,SAAiC,eAAA,gBACjC,SAAiC,aAAA,gBACjC,SACE,cAAA,gBACA,aAAA,gBAEF,SACE,YAAA,gBACA,eAAA,gBAXF,QAAiC,QAAA,eACjC,SAAiC,YAAA,eACjC,SAAiC,cAAA,eACjC,SAAiC,eAAA,eACjC,SAAiC,aAAA,eACjC,SACE,cAAA,eACA,aAAA,eAEF,SACE,YAAA,eACA,eAAA,eAXF,QAAiC,QAAA,iBACjC,SAAiC,YAAA,iBACjC,SAAiC,cAAA,iBACjC,SAAiC,eAAA,iBACjC,SAAiC,aAAA,iBACjC,SACE,cAAA,iBACA,aAAA,iBAEF,SACE,YAAA,iBACA,eAAA,iBAXF,QAAiC,QAAA,eACjC,SAAiC,YAAA,eACjC,SAAiC,cAAA,eACjC,SAAiC,eAAA,eACjC,SAAiC,aAAA,eACjC,SACE,cAAA,eACA,aAAA,eAEF,SACE,YAAA,eACA,eAAA,eAMN,WAAoB,OAAA,eACpB,YAAoB,WAAA,eACpB,YAAoB,aAAA,eACpB,YAAoB,cAAA,eACpB,YAAoB,YAAA,eACpB,YACE,aAAA,eACA,YAAA,eAEF,YACE,WAAA,eACA,cAAA,gBnDmBF,yBmD/CI,QAAiC,OAAA,YACjC,SAAiC,WAAA,YACjC,SAAiC,aAAA,YACjC,SAAiC,cAAA,YACjC,SAAiC,YAAA,YACjC,SACE,aAAA,YACA,YAAA,YAEF,SACE,WAAA,YACA,cAAA,YAXF,QAAiC,OAAA,iBACjC,SAAiC,WAAA,iBACjC,SAAiC,aAAA,iBACjC,SAAiC,cAAA,iBACjC,SAAiC,YAAA,iBACjC,SACE,aAAA,iBACA,YAAA,iBAEF,SACE,WAAA,iBACA,cAAA,iBAXF,QAAiC,OAAA,gBACjC,SAAiC,WAAA,gBACjC,SAAiC,aAAA,gBACjC,SAAiC,cAAA,gBACjC,SAAiC,YAAA,gBACjC,SACE,aAAA,gBACA,YAAA,gBAEF,SACE,WAAA,gBACA,cAAA,gBAXF,QAAiC,OAAA,eACjC,SAAiC,WAAA,eACjC,SAAiC,aAAA,eACjC,SAAiC,cAAA,eACjC,SAAiC,YAAA,eACjC,SACE,aAAA,eACA,YAAA,eAEF,SACE,WAAA,eACA,cAAA,eAXF,QAAiC,OAAA,iBACjC,SAAiC,WAAA,iBACjC,SAAiC,aAAA,iBACjC,SAAiC,cAAA,iBACjC,SAAiC,YAAA,iBACjC,SACE,aAAA,iBACA,YAAA,iBAEF,SACE,WAAA,iBACA,cAAA,iBAXF,QAAiC,OAAA,eACjC,SAAiC,WAAA,eACjC,SAAiC,aAAA,eACjC,SAAiC,cAAA,eACjC,SAAiC,YAAA,eACjC,SACE,aAAA,eACA,YAAA,eAEF,SACE,WAAA,eACA,cAAA,eAXF,QAAiC,QAAA,YACjC,SAAiC,YAAA,YACjC,SAAiC,cAAA,YACjC,SAAiC,eAAA,YACjC,SAAiC,aAAA,YACjC,SACE,cAAA,YACA,aAAA,YAEF,SACE,YAAA,YACA,eAAA,YAXF,QAAiC,QAAA,iBACjC,SAAiC,YAAA,iBACjC,SAAiC,cAAA,iBACjC,SAAiC,eAAA,iBACjC,SAAiC,aAAA,iBACjC,SACE,cAAA,iBACA,aAAA,iBAEF,SACE,YAAA,iBACA,eAAA,iBAXF,QAAiC,QAAA,gBACjC,SAAiC,YAAA,gBACjC,SAAiC,cAAA,gBACjC,SAAiC,eAAA,gBACjC,SAAiC,aAAA,gBACjC,SACE,cAAA,gBACA,aAAA,gBAEF,SACE,YAAA,gBACA,eAAA,gBAXF,QAAiC,QAAA,eACjC,SAAiC,YAAA,eACjC,SAAiC,cAAA,eACjC,SAAiC,eAAA,eACjC,SAAiC,aAAA,eACjC,SACE,cAAA,eACA,aAAA,eAEF,SACE,YAAA,eACA,eAAA,eAXF,QAAiC,QAAA,iBACjC,SAAiC,YAAA,iBACjC,SAAiC,cAAA,iBACjC,SAAiC,eAAA,iBACjC,SAAiC,aAAA,iBACjC,SACE,cAAA,iBACA,aAAA,iBAEF,SACE,YAAA,iBACA,eAAA,iBAXF,QAAiC,QAAA,eACjC,SAAiC,YAAA,eACjC,SAAiC,cAAA,eACjC,SAAiC,eAAA,eACjC,SAAiC,aAAA,eACjC,SACE,cAAA,eACA,aAAA,eAEF,SACE,YAAA,eACA,eAAA,eAMN,WAAoB,OAAA,eACpB,YAAoB,WAAA,eACpB,YAAoB,aAAA,eACpB,YAAoB,cAAA,eACpB,YAAoB,YAAA,eACpB,YACE,aAAA,eACA,YAAA,eAEF,YACE,WAAA,eACA,cAAA,gBnDmBF,0BmD/CI,QAAiC,OAAA,YACjC,SAAiC,WAAA,YACjC,SAAiC,aAAA,YACjC,SAAiC,cAAA,YACjC,SAAiC,YAAA,YACjC,SACE,aAAA,YACA,YAAA,YAEF,SACE,WAAA,YACA,cAAA,YAXF,QAAiC,OAAA,iBACjC,SAAiC,WAAA,iBACjC,SAAiC,aAAA,iBACjC,SAAiC,cAAA,iBACjC,SAAiC,YAAA,iBACjC,SACE,aAAA,iBACA,YAAA,iBAEF,SACE,WAAA,iBACA,cAAA,iBAXF,QAAiC,OAAA,gBACjC,SAAiC,WAAA,gBACjC,SAAiC,aAAA,gBACjC,SAAiC,cAAA,gBACjC,SAAiC,YAAA,gBACjC,SACE,aAAA,gBACA,YAAA,gBAEF,SACE,WAAA,gBACA,cAAA,gBAXF,QAAiC,OAAA,eACjC,SAAiC,WAAA,eACjC,SAAiC,aAAA,eACjC,SAAiC,cAAA,eACjC,SAAiC,YAAA,eACjC,SACE,aAAA,eACA,YAAA,eAEF,SACE,WAAA,eACA,cAAA,eAXF,QAAiC,OAAA,iBACjC,SAAiC,WAAA,iBACjC,SAAiC,aAAA,iBACjC,SAAiC,cAAA,iBACjC,SAAiC,YAAA,iBACjC,SACE,aAAA,iBACA,YAAA,iBAEF,SACE,WAAA,iBACA,cAAA,iBAXF,QAAiC,OAAA,eACjC,SAAiC,WAAA,eACjC,SAAiC,aAAA,eACjC,SAAiC,cAAA,eACjC,SAAiC,YAAA,eACjC,SACE,aAAA,eACA,YAAA,eAEF,SACE,WAAA,eACA,cAAA,eAXF,QAAiC,QAAA,YACjC,SAAiC,YAAA,YACjC,SAAiC,cAAA,YACjC,SAAiC,eAAA,YACjC,SAAiC,aAAA,YACjC,SACE,cAAA,YACA,aAAA,YAEF,SACE,YAAA,YACA,eAAA,YAXF,QAAiC,QAAA,iBACjC,SAAiC,YAAA,iBACjC,SAAiC,cAAA,iBACjC,SAAiC,eAAA,iBACjC,SAAiC,aAAA,iBACjC,SACE,cAAA,iBACA,aAAA,iBAEF,SACE,YAAA,iBACA,eAAA,iBAXF,QAAiC,QAAA,gBACjC,SAAiC,YAAA,gBACjC,SAAiC,cAAA,gBACjC,SAAiC,eAAA,gBACjC,SAAiC,aAAA,gBACjC,SACE,cAAA,gBACA,aAAA,gBAEF,SACE,YAAA,gBACA,eAAA,gBAXF,QAAiC,QAAA,eACjC,SAAiC,YAAA,eACjC,SAAiC,cAAA,eACjC,SAAiC,eAAA,eACjC,SAAiC,aAAA,eACjC,SACE,cAAA,eACA,aAAA,eAEF,SACE,YAAA,eACA,eAAA,eAXF,QAAiC,QAAA,iBACjC,SAAiC,YAAA,iBACjC,SAAiC,cAAA,iBACjC,SAAiC,eAAA,iBACjC,SAAiC,aAAA,iBACjC,SACE,cAAA,iBACA,aAAA,iBAEF,SACE,YAAA,iBACA,eAAA,iBAXF,QAAiC,QAAA,eACjC,SAAiC,YAAA,eACjC,SAAiC,cAAA,eACjC,SAAiC,eAAA,eACjC,SAAiC,aAAA,eACjC,SACE,cAAA,eACA,aAAA,eAEF,SACE,YAAA,eACA,eAAA,eAMN,WAAoB,OAAA,eACpB,YAAoB,WAAA,eACpB,YAAoB,aAAA,eACpB,YAAoB,cAAA,eACpB,YAAoB,YAAA,eACpB,YACE,aAAA,eACA,YAAA,eAEF,YACE,WAAA,eACA,cAAA,gBC/BN,cAAiB,WAAA,kBACjB,aAAiB,YAAA,iBACjB,eCJE,SAAA,OACA,cAAA,SACA,YAAA,ODUE,WAAwB,WAAA,eACxB,YAAwB,WAAA,gBACxB,aAAwB,WAAA,iBpDsCxB,yBoDxCA,cAAwB,WAAA,eACxB,eAAwB,WAAA,gBACxB,gBAAwB,WAAA,kBpDsCxB,yBoDxCA,cAAwB,WAAA,eACxB,eAAwB,WAAA,gBACxB,gBAAwB,WAAA,kBpDsCxB,yBoDxCA,cAAwB,WAAA,eACxB,eAAwB,WAAA,gBACxB,gBAAwB,WAAA,kBpDsCxB,0BoDxCA,cAAwB,WAAA,eACxB,eAAwB,WAAA,gBACxB,gBAAwB,WAAA,kBAM5B,gBAAmB,eAAA,oBACnB,gBAAmB,eAAA,oBACnB,iBAAmB,eAAA,qBAInB,oBAAsB,YAAA,IACtB,kBAAsB,YAAA,IACtB,aAAsB,WAAA,OAItB,YAAc,MAAA,eEjCZ,cACE,MAAA,kBhEkBA,qBAAA,qBgEdE,MAAA,kBALJ,gBACE,MAAA,kBhEkBA,uBAAA,uBgEdE,MAAA,kBALJ,cACE,MAAA,kBhEkBA,qBAAA,qBgEdE,MAAA,kBALJ,WACE,MAAA,kBhEkBA,kBAAA,kBgEdE,MAAA,kBALJ,cACE,MAAA,kBhEkBA,qBAAA,qBgEdE,MAAA,kBALJ,aACE,MAAA,kBhEkBA,oBAAA,oBgEdE,MAAA,kBALJ,YACE,MAAA,kBhEkBA,mBAAA,mBgEdE,MAAA,kBALJ,WACE,MAAA,kBhEkBA,kBAAA,kBgEdE,MAAA,kBFkCN,YAAc,MAAA,kBAId,WG5CE,KAAA,CAAA,CAAA,EAAA,EACA,MAAA,YACA,YAAA,KACA,iBAAA,YACA,OAAA,ECFF,SCDE,WAAA,kBDKF,WCLE,WAAA","sourcesContent":["/*!\n * Bootstrap v4.0.0-beta (https://getbootstrap.com)\n * Copyright 2011-2017 The Bootstrap Authors\n * Copyright 2011-2017 Twitter, Inc.\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)\n */\n\n@import \"functions\";\n@import \"variables\";\n@import \"mixins\";\n@import \"print\";\n@import \"reboot\";\n@import \"type\";\n@import \"images\";\n@import \"code\";\n@import \"grid\";\n@import \"tables\";\n@import \"forms\";\n@import \"buttons\";\n@import \"transitions\";\n@import \"dropdown\";\n@import \"button-group\";\n@import \"input-group\";\n@import \"custom-forms\";\n@import \"nav\";\n@import \"navbar\";\n@import \"card\";\n@import \"breadcrumb\";\n@import \"pagination\";\n@import \"badge\";\n@import \"jumbotron\";\n@import \"alert\";\n@import \"progress\";\n@import \"media\";\n@import \"list-group\";\n@import \"close\";\n@import \"modal\";\n@import \"tooltip\";\n@import \"popover\";\n@import \"carousel\";\n@import \"utilities\";\n","// scss-lint:disable QualifyingElement\n\n// Source: https://github.com/h5bp/html5-boilerplate/blob/master/src/css/main.css\n\n// ==========================================================================\n// Print styles.\n// Inlined to avoid the additional HTTP request:\n// http://www.phpied.com/delay-loading-your-print-css/\n// ==========================================================================\n\n@if $enable-print-styles {\n @media print {\n *,\n *::before,\n *::after {\n // Bootstrap specific; comment out `color` and `background`\n //color: #000 !important; // Black prints faster:\n // http://www.sanbeiji.com/archives/953\n text-shadow: none !important;\n //background: transparent !important;\n box-shadow: none !important;\n }\n\n a,\n a:visited {\n text-decoration: underline;\n }\n\n // Bootstrap specific; comment the following selector out\n //a[href]::after {\n // content: \" (\" attr(href) \")\";\n //}\n\n abbr[title]::after {\n content: \" (\" attr(title) \")\";\n }\n\n // Bootstrap specific; comment the following selector out\n //\n // Don't show links that are fragment identifiers,\n // or use the `javascript:` pseudo protocol\n //\n\n //a[href^=\"#\"]::after,\n //a[href^=\"javascript:\"]::after {\n // content: \"\";\n //}\n\n pre {\n white-space: pre-wrap !important;\n }\n pre,\n blockquote {\n border: $border-width solid #999; // Bootstrap custom code; using `$border-width` instead of 1px\n page-break-inside: avoid;\n }\n\n //\n // Printing Tables:\n // http://css-discuss.incutio.com/wiki/Printing_Tables\n //\n\n thead {\n display: table-header-group;\n }\n\n tr,\n img {\n page-break-inside: avoid;\n }\n\n p,\n h2,\n h3 {\n orphans: 3;\n widows: 3;\n }\n\n h2,\n h3 {\n page-break-after: avoid;\n }\n\n // Bootstrap specific changes start\n\n // Bootstrap components\n .navbar {\n display: none;\n }\n .badge {\n border: $border-width solid #000;\n }\n\n .table {\n border-collapse: collapse !important;\n\n td,\n th {\n background-color: #fff !important;\n }\n }\n .table-bordered {\n th,\n td {\n border: 1px solid #ddd !important;\n }\n }\n\n // Bootstrap specific changes end\n }\n}\n","/*!\n * Bootstrap v4.0.0-beta (https://getbootstrap.com)\n * Copyright 2011-2017 The Bootstrap Authors\n * Copyright 2011-2017 Twitter, Inc.\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)\n */\n@media print {\n *,\n *::before,\n *::after {\n text-shadow: none !important;\n box-shadow: none !important;\n }\n a,\n a:visited {\n text-decoration: underline;\n }\n abbr[title]::after {\n content: \" (\" attr(title) \")\";\n }\n pre {\n white-space: pre-wrap !important;\n }\n pre,\n blockquote {\n border: 1px solid #999;\n page-break-inside: avoid;\n }\n thead {\n display: table-header-group;\n }\n tr,\n img {\n page-break-inside: avoid;\n }\n p,\n h2,\n h3 {\n orphans: 3;\n widows: 3;\n }\n h2,\n h3 {\n page-break-after: avoid;\n }\n .navbar {\n display: none;\n }\n .badge {\n border: 1px solid #000;\n }\n .table {\n border-collapse: collapse !important;\n }\n .table td,\n .table th {\n background-color: #fff !important;\n }\n .table-bordered th,\n .table-bordered td {\n border: 1px solid #ddd !important;\n }\n}\n\nhtml {\n box-sizing: border-box;\n font-family: sans-serif;\n line-height: 1.15;\n -webkit-text-size-adjust: 100%;\n -ms-text-size-adjust: 100%;\n -ms-overflow-style: scrollbar;\n -webkit-tap-highlight-color: transparent;\n}\n\n*,\n*::before,\n*::after {\n box-sizing: inherit;\n}\n\n@-ms-viewport {\n width: device-width;\n}\n\narticle, aside, dialog, figcaption, figure, footer, header, hgroup, main, nav, section {\n display: block;\n}\n\nbody {\n margin: 0;\n font-family: -apple-system, BlinkMacSystemFont, \"Segoe UI\", Roboto, \"Helvetica Neue\", Arial, sans-serif;\n font-size: 1rem;\n font-weight: normal;\n line-height: 1.5;\n color: #212529;\n background-color: #fff;\n}\n\n[tabindex=\"-1\"]:focus {\n outline: none !important;\n}\n\nhr {\n box-sizing: content-box;\n height: 0;\n overflow: visible;\n}\n\nh1, h2, h3, h4, h5, h6 {\n margin-top: 0;\n margin-bottom: .5rem;\n}\n\np {\n margin-top: 0;\n margin-bottom: 1rem;\n}\n\nabbr[title],\nabbr[data-original-title] {\n text-decoration: underline;\n -webkit-text-decoration: underline dotted;\n text-decoration: underline dotted;\n cursor: help;\n border-bottom: 0;\n}\n\naddress {\n margin-bottom: 1rem;\n font-style: normal;\n line-height: inherit;\n}\n\nol,\nul,\ndl {\n margin-top: 0;\n margin-bottom: 1rem;\n}\n\nol ol,\nul ul,\nol ul,\nul ol {\n margin-bottom: 0;\n}\n\ndt {\n font-weight: bold;\n}\n\ndd {\n margin-bottom: .5rem;\n margin-left: 0;\n}\n\nblockquote {\n margin: 0 0 1rem;\n}\n\ndfn {\n font-style: italic;\n}\n\nb,\nstrong {\n font-weight: bolder;\n}\n\nsmall {\n font-size: 80%;\n}\n\nsub,\nsup {\n position: relative;\n font-size: 75%;\n line-height: 0;\n vertical-align: baseline;\n}\n\nsub {\n bottom: -.25em;\n}\n\nsup {\n top: -.5em;\n}\n\na {\n color: #007bff;\n text-decoration: none;\n background-color: transparent;\n -webkit-text-decoration-skip: objects;\n}\n\na:hover {\n color: #0056b3;\n text-decoration: underline;\n}\n\na:not([href]):not([tabindex]) {\n color: inherit;\n text-decoration: none;\n}\n\na:not([href]):not([tabindex]):focus, a:not([href]):not([tabindex]):hover {\n color: inherit;\n text-decoration: none;\n}\n\na:not([href]):not([tabindex]):focus {\n outline: 0;\n}\n\npre,\ncode,\nkbd,\nsamp {\n font-family: monospace, monospace;\n font-size: 1em;\n}\n\npre {\n margin-top: 0;\n margin-bottom: 1rem;\n overflow: auto;\n}\n\nfigure {\n margin: 0 0 1rem;\n}\n\nimg {\n vertical-align: middle;\n border-style: none;\n}\n\nsvg:not(:root) {\n overflow: hidden;\n}\n\na,\narea,\nbutton,\n[role=\"button\"],\ninput,\nlabel,\nselect,\nsummary,\ntextarea {\n -ms-touch-action: manipulation;\n touch-action: manipulation;\n}\n\ntable {\n border-collapse: collapse;\n}\n\ncaption {\n padding-top: 0.75rem;\n padding-bottom: 0.75rem;\n color: #868e96;\n text-align: left;\n caption-side: bottom;\n}\n\nth {\n text-align: left;\n}\n\nlabel {\n display: inline-block;\n margin-bottom: .5rem;\n}\n\nbutton:focus {\n outline: 1px dotted;\n outline: 5px auto -webkit-focus-ring-color;\n}\n\ninput,\nbutton,\nselect,\noptgroup,\ntextarea {\n margin: 0;\n font-family: inherit;\n font-size: inherit;\n line-height: inherit;\n}\n\nbutton,\ninput {\n overflow: visible;\n}\n\nbutton,\nselect {\n text-transform: none;\n}\n\nbutton,\nhtml [type=\"button\"],\n[type=\"reset\"],\n[type=\"submit\"] {\n -webkit-appearance: button;\n}\n\nbutton::-moz-focus-inner,\n[type=\"button\"]::-moz-focus-inner,\n[type=\"reset\"]::-moz-focus-inner,\n[type=\"submit\"]::-moz-focus-inner {\n padding: 0;\n border-style: none;\n}\n\ninput[type=\"radio\"],\ninput[type=\"checkbox\"] {\n box-sizing: border-box;\n padding: 0;\n}\n\ninput[type=\"date\"],\ninput[type=\"time\"],\ninput[type=\"datetime-local\"],\ninput[type=\"month\"] {\n -webkit-appearance: listbox;\n}\n\ntextarea {\n overflow: auto;\n resize: vertical;\n}\n\nfieldset {\n min-width: 0;\n padding: 0;\n margin: 0;\n border: 0;\n}\n\nlegend {\n display: block;\n width: 100%;\n max-width: 100%;\n padding: 0;\n margin-bottom: .5rem;\n font-size: 1.5rem;\n line-height: inherit;\n color: inherit;\n white-space: normal;\n}\n\nprogress {\n vertical-align: baseline;\n}\n\n[type=\"number\"]::-webkit-inner-spin-button,\n[type=\"number\"]::-webkit-outer-spin-button {\n height: auto;\n}\n\n[type=\"search\"] {\n outline-offset: -2px;\n -webkit-appearance: none;\n}\n\n[type=\"search\"]::-webkit-search-cancel-button,\n[type=\"search\"]::-webkit-search-decoration {\n -webkit-appearance: none;\n}\n\n::-webkit-file-upload-button {\n font: inherit;\n -webkit-appearance: button;\n}\n\noutput {\n display: inline-block;\n}\n\nsummary {\n display: list-item;\n}\n\ntemplate {\n display: none;\n}\n\n[hidden] {\n display: none !important;\n}\n\nh1, h2, h3, h4, h5, h6,\n.h1, .h2, .h3, .h4, .h5, .h6 {\n margin-bottom: 0.5rem;\n font-family: inherit;\n font-weight: 500;\n line-height: 1.1;\n color: inherit;\n}\n\nh1, .h1 {\n font-size: 2.5rem;\n}\n\nh2, .h2 {\n font-size: 2rem;\n}\n\nh3, .h3 {\n font-size: 1.75rem;\n}\n\nh4, .h4 {\n font-size: 1.5rem;\n}\n\nh5, .h5 {\n font-size: 1.25rem;\n}\n\nh6, .h6 {\n font-size: 1rem;\n}\n\n.lead {\n font-size: 1.25rem;\n font-weight: 300;\n}\n\n.display-1 {\n font-size: 6rem;\n font-weight: 300;\n line-height: 1.1;\n}\n\n.display-2 {\n font-size: 5.5rem;\n font-weight: 300;\n line-height: 1.1;\n}\n\n.display-3 {\n font-size: 4.5rem;\n font-weight: 300;\n line-height: 1.1;\n}\n\n.display-4 {\n font-size: 3.5rem;\n font-weight: 300;\n line-height: 1.1;\n}\n\nhr {\n margin-top: 1rem;\n margin-bottom: 1rem;\n border: 0;\n border-top: 1px solid rgba(0, 0, 0, 0.1);\n}\n\nsmall,\n.small {\n font-size: 80%;\n font-weight: normal;\n}\n\nmark,\n.mark {\n padding: 0.2em;\n background-color: #fcf8e3;\n}\n\n.list-unstyled {\n padding-left: 0;\n list-style: none;\n}\n\n.list-inline {\n padding-left: 0;\n list-style: none;\n}\n\n.list-inline-item {\n display: inline-block;\n}\n\n.list-inline-item:not(:last-child) {\n margin-right: 5px;\n}\n\n.initialism {\n font-size: 90%;\n text-transform: uppercase;\n}\n\n.blockquote {\n margin-bottom: 1rem;\n font-size: 1.25rem;\n}\n\n.blockquote-footer {\n display: block;\n font-size: 80%;\n color: #868e96;\n}\n\n.blockquote-footer::before {\n content: \"\\2014 \\00A0\";\n}\n\n.img-fluid {\n max-width: 100%;\n height: auto;\n}\n\n.img-thumbnail {\n padding: 0.25rem;\n background-color: #fff;\n border: 1px solid #ddd;\n border-radius: 0.25rem;\n transition: all 0.2s ease-in-out;\n max-width: 100%;\n height: auto;\n}\n\n.figure {\n display: inline-block;\n}\n\n.figure-img {\n margin-bottom: 0.5rem;\n line-height: 1;\n}\n\n.figure-caption {\n font-size: 90%;\n color: #868e96;\n}\n\ncode,\nkbd,\npre,\nsamp {\n font-family: Menlo, Monaco, Consolas, \"Liberation Mono\", \"Courier New\", monospace;\n}\n\ncode {\n padding: 0.2rem 0.4rem;\n font-size: 90%;\n color: #bd4147;\n background-color: #f8f9fa;\n border-radius: 0.25rem;\n}\n\na > code {\n padding: 0;\n color: inherit;\n background-color: inherit;\n}\n\nkbd {\n padding: 0.2rem 0.4rem;\n font-size: 90%;\n color: #fff;\n background-color: #212529;\n border-radius: 0.2rem;\n}\n\nkbd kbd {\n padding: 0;\n font-size: 100%;\n font-weight: bold;\n}\n\npre {\n display: block;\n margin-top: 0;\n margin-bottom: 1rem;\n font-size: 90%;\n color: #212529;\n}\n\npre code {\n padding: 0;\n font-size: inherit;\n color: inherit;\n background-color: transparent;\n border-radius: 0;\n}\n\n.pre-scrollable {\n max-height: 340px;\n overflow-y: scroll;\n}\n\n.container {\n margin-right: auto;\n margin-left: auto;\n padding-right: 15px;\n padding-left: 15px;\n width: 100%;\n}\n\n@media (min-width: 576px) {\n .container {\n max-width: 540px;\n }\n}\n\n@media (min-width: 768px) {\n .container {\n max-width: 720px;\n }\n}\n\n@media (min-width: 992px) {\n .container {\n max-width: 960px;\n }\n}\n\n@media (min-width: 1200px) {\n .container {\n max-width: 1140px;\n }\n}\n\n.container-fluid {\n width: 100%;\n margin-right: auto;\n margin-left: auto;\n padding-right: 15px;\n padding-left: 15px;\n width: 100%;\n}\n\n.row {\n display: -ms-flexbox;\n display: flex;\n -ms-flex-wrap: wrap;\n flex-wrap: wrap;\n margin-right: -15px;\n margin-left: -15px;\n}\n\n.no-gutters {\n margin-right: 0;\n margin-left: 0;\n}\n\n.no-gutters > .col,\n.no-gutters > [class*=\"col-\"] {\n padding-right: 0;\n padding-left: 0;\n}\n\n.col-1, .col-2, .col-3, .col-4, .col-5, .col-6, .col-7, .col-8, .col-9, .col-10, .col-11, .col-12, .col,\n.col-auto, .col-sm-1, .col-sm-2, .col-sm-3, .col-sm-4, .col-sm-5, .col-sm-6, .col-sm-7, .col-sm-8, .col-sm-9, .col-sm-10, .col-sm-11, .col-sm-12, .col-sm,\n.col-sm-auto, .col-md-1, .col-md-2, .col-md-3, .col-md-4, .col-md-5, .col-md-6, .col-md-7, .col-md-8, .col-md-9, .col-md-10, .col-md-11, .col-md-12, .col-md,\n.col-md-auto, .col-lg-1, .col-lg-2, .col-lg-3, .col-lg-4, .col-lg-5, .col-lg-6, .col-lg-7, .col-lg-8, .col-lg-9, .col-lg-10, .col-lg-11, .col-lg-12, .col-lg,\n.col-lg-auto, .col-xl-1, .col-xl-2, .col-xl-3, .col-xl-4, .col-xl-5, .col-xl-6, .col-xl-7, .col-xl-8, .col-xl-9, .col-xl-10, .col-xl-11, .col-xl-12, .col-xl,\n.col-xl-auto {\n position: relative;\n width: 100%;\n min-height: 1px;\n padding-right: 15px;\n padding-left: 15px;\n}\n\n.col {\n -ms-flex-preferred-size: 0;\n flex-basis: 0;\n -ms-flex-positive: 1;\n flex-grow: 1;\n max-width: 100%;\n}\n\n.col-auto {\n -ms-flex: 0 0 auto;\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n}\n\n.col-1 {\n -ms-flex: 0 0 8.333333%;\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n}\n\n.col-2 {\n -ms-flex: 0 0 16.666667%;\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n}\n\n.col-3 {\n -ms-flex: 0 0 25%;\n flex: 0 0 25%;\n max-width: 25%;\n}\n\n.col-4 {\n -ms-flex: 0 0 33.333333%;\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n}\n\n.col-5 {\n -ms-flex: 0 0 41.666667%;\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n}\n\n.col-6 {\n -ms-flex: 0 0 50%;\n flex: 0 0 50%;\n max-width: 50%;\n}\n\n.col-7 {\n -ms-flex: 0 0 58.333333%;\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n}\n\n.col-8 {\n -ms-flex: 0 0 66.666667%;\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n}\n\n.col-9 {\n -ms-flex: 0 0 75%;\n flex: 0 0 75%;\n max-width: 75%;\n}\n\n.col-10 {\n -ms-flex: 0 0 83.333333%;\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n}\n\n.col-11 {\n -ms-flex: 0 0 91.666667%;\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n}\n\n.col-12 {\n -ms-flex: 0 0 100%;\n flex: 0 0 100%;\n max-width: 100%;\n}\n\n.order-1 {\n -ms-flex-order: 1;\n order: 1;\n}\n\n.order-2 {\n -ms-flex-order: 2;\n order: 2;\n}\n\n.order-3 {\n -ms-flex-order: 3;\n order: 3;\n}\n\n.order-4 {\n -ms-flex-order: 4;\n order: 4;\n}\n\n.order-5 {\n -ms-flex-order: 5;\n order: 5;\n}\n\n.order-6 {\n -ms-flex-order: 6;\n order: 6;\n}\n\n.order-7 {\n -ms-flex-order: 7;\n order: 7;\n}\n\n.order-8 {\n -ms-flex-order: 8;\n order: 8;\n}\n\n.order-9 {\n -ms-flex-order: 9;\n order: 9;\n}\n\n.order-10 {\n -ms-flex-order: 10;\n order: 10;\n}\n\n.order-11 {\n -ms-flex-order: 11;\n order: 11;\n}\n\n.order-12 {\n -ms-flex-order: 12;\n order: 12;\n}\n\n@media (min-width: 576px) {\n .col-sm {\n -ms-flex-preferred-size: 0;\n flex-basis: 0;\n -ms-flex-positive: 1;\n flex-grow: 1;\n max-width: 100%;\n }\n .col-sm-auto {\n -ms-flex: 0 0 auto;\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n }\n .col-sm-1 {\n -ms-flex: 0 0 8.333333%;\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n }\n .col-sm-2 {\n -ms-flex: 0 0 16.666667%;\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n }\n .col-sm-3 {\n -ms-flex: 0 0 25%;\n flex: 0 0 25%;\n max-width: 25%;\n }\n .col-sm-4 {\n -ms-flex: 0 0 33.333333%;\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n }\n .col-sm-5 {\n -ms-flex: 0 0 41.666667%;\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n }\n .col-sm-6 {\n -ms-flex: 0 0 50%;\n flex: 0 0 50%;\n max-width: 50%;\n }\n .col-sm-7 {\n -ms-flex: 0 0 58.333333%;\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n }\n .col-sm-8 {\n -ms-flex: 0 0 66.666667%;\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n }\n .col-sm-9 {\n -ms-flex: 0 0 75%;\n flex: 0 0 75%;\n max-width: 75%;\n }\n .col-sm-10 {\n -ms-flex: 0 0 83.333333%;\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n }\n .col-sm-11 {\n -ms-flex: 0 0 91.666667%;\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n }\n .col-sm-12 {\n -ms-flex: 0 0 100%;\n flex: 0 0 100%;\n max-width: 100%;\n }\n .order-sm-1 {\n -ms-flex-order: 1;\n order: 1;\n }\n .order-sm-2 {\n -ms-flex-order: 2;\n order: 2;\n }\n .order-sm-3 {\n -ms-flex-order: 3;\n order: 3;\n }\n .order-sm-4 {\n -ms-flex-order: 4;\n order: 4;\n }\n .order-sm-5 {\n -ms-flex-order: 5;\n order: 5;\n }\n .order-sm-6 {\n -ms-flex-order: 6;\n order: 6;\n }\n .order-sm-7 {\n -ms-flex-order: 7;\n order: 7;\n }\n .order-sm-8 {\n -ms-flex-order: 8;\n order: 8;\n }\n .order-sm-9 {\n -ms-flex-order: 9;\n order: 9;\n }\n .order-sm-10 {\n -ms-flex-order: 10;\n order: 10;\n }\n .order-sm-11 {\n -ms-flex-order: 11;\n order: 11;\n }\n .order-sm-12 {\n -ms-flex-order: 12;\n order: 12;\n }\n}\n\n@media (min-width: 768px) {\n .col-md {\n -ms-flex-preferred-size: 0;\n flex-basis: 0;\n -ms-flex-positive: 1;\n flex-grow: 1;\n max-width: 100%;\n }\n .col-md-auto {\n -ms-flex: 0 0 auto;\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n }\n .col-md-1 {\n -ms-flex: 0 0 8.333333%;\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n }\n .col-md-2 {\n -ms-flex: 0 0 16.666667%;\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n }\n .col-md-3 {\n -ms-flex: 0 0 25%;\n flex: 0 0 25%;\n max-width: 25%;\n }\n .col-md-4 {\n -ms-flex: 0 0 33.333333%;\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n }\n .col-md-5 {\n -ms-flex: 0 0 41.666667%;\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n }\n .col-md-6 {\n -ms-flex: 0 0 50%;\n flex: 0 0 50%;\n max-width: 50%;\n }\n .col-md-7 {\n -ms-flex: 0 0 58.333333%;\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n }\n .col-md-8 {\n -ms-flex: 0 0 66.666667%;\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n }\n .col-md-9 {\n -ms-flex: 0 0 75%;\n flex: 0 0 75%;\n max-width: 75%;\n }\n .col-md-10 {\n -ms-flex: 0 0 83.333333%;\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n }\n .col-md-11 {\n -ms-flex: 0 0 91.666667%;\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n }\n .col-md-12 {\n -ms-flex: 0 0 100%;\n flex: 0 0 100%;\n max-width: 100%;\n }\n .order-md-1 {\n -ms-flex-order: 1;\n order: 1;\n }\n .order-md-2 {\n -ms-flex-order: 2;\n order: 2;\n }\n .order-md-3 {\n -ms-flex-order: 3;\n order: 3;\n }\n .order-md-4 {\n -ms-flex-order: 4;\n order: 4;\n }\n .order-md-5 {\n -ms-flex-order: 5;\n order: 5;\n }\n .order-md-6 {\n -ms-flex-order: 6;\n order: 6;\n }\n .order-md-7 {\n -ms-flex-order: 7;\n order: 7;\n }\n .order-md-8 {\n -ms-flex-order: 8;\n order: 8;\n }\n .order-md-9 {\n -ms-flex-order: 9;\n order: 9;\n }\n .order-md-10 {\n -ms-flex-order: 10;\n order: 10;\n }\n .order-md-11 {\n -ms-flex-order: 11;\n order: 11;\n }\n .order-md-12 {\n -ms-flex-order: 12;\n order: 12;\n }\n}\n\n@media (min-width: 992px) {\n .col-lg {\n -ms-flex-preferred-size: 0;\n flex-basis: 0;\n -ms-flex-positive: 1;\n flex-grow: 1;\n max-width: 100%;\n }\n .col-lg-auto {\n -ms-flex: 0 0 auto;\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n }\n .col-lg-1 {\n -ms-flex: 0 0 8.333333%;\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n }\n .col-lg-2 {\n -ms-flex: 0 0 16.666667%;\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n }\n .col-lg-3 {\n -ms-flex: 0 0 25%;\n flex: 0 0 25%;\n max-width: 25%;\n }\n .col-lg-4 {\n -ms-flex: 0 0 33.333333%;\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n }\n .col-lg-5 {\n -ms-flex: 0 0 41.666667%;\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n }\n .col-lg-6 {\n -ms-flex: 0 0 50%;\n flex: 0 0 50%;\n max-width: 50%;\n }\n .col-lg-7 {\n -ms-flex: 0 0 58.333333%;\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n }\n .col-lg-8 {\n -ms-flex: 0 0 66.666667%;\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n }\n .col-lg-9 {\n -ms-flex: 0 0 75%;\n flex: 0 0 75%;\n max-width: 75%;\n }\n .col-lg-10 {\n -ms-flex: 0 0 83.333333%;\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n }\n .col-lg-11 {\n -ms-flex: 0 0 91.666667%;\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n }\n .col-lg-12 {\n -ms-flex: 0 0 100%;\n flex: 0 0 100%;\n max-width: 100%;\n }\n .order-lg-1 {\n -ms-flex-order: 1;\n order: 1;\n }\n .order-lg-2 {\n -ms-flex-order: 2;\n order: 2;\n }\n .order-lg-3 {\n -ms-flex-order: 3;\n order: 3;\n }\n .order-lg-4 {\n -ms-flex-order: 4;\n order: 4;\n }\n .order-lg-5 {\n -ms-flex-order: 5;\n order: 5;\n }\n .order-lg-6 {\n -ms-flex-order: 6;\n order: 6;\n }\n .order-lg-7 {\n -ms-flex-order: 7;\n order: 7;\n }\n .order-lg-8 {\n -ms-flex-order: 8;\n order: 8;\n }\n .order-lg-9 {\n -ms-flex-order: 9;\n order: 9;\n }\n .order-lg-10 {\n -ms-flex-order: 10;\n order: 10;\n }\n .order-lg-11 {\n -ms-flex-order: 11;\n order: 11;\n }\n .order-lg-12 {\n -ms-flex-order: 12;\n order: 12;\n }\n}\n\n@media (min-width: 1200px) {\n .col-xl {\n -ms-flex-preferred-size: 0;\n flex-basis: 0;\n -ms-flex-positive: 1;\n flex-grow: 1;\n max-width: 100%;\n }\n .col-xl-auto {\n -ms-flex: 0 0 auto;\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n }\n .col-xl-1 {\n -ms-flex: 0 0 8.333333%;\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n }\n .col-xl-2 {\n -ms-flex: 0 0 16.666667%;\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n }\n .col-xl-3 {\n -ms-flex: 0 0 25%;\n flex: 0 0 25%;\n max-width: 25%;\n }\n .col-xl-4 {\n -ms-flex: 0 0 33.333333%;\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n }\n .col-xl-5 {\n -ms-flex: 0 0 41.666667%;\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n }\n .col-xl-6 {\n -ms-flex: 0 0 50%;\n flex: 0 0 50%;\n max-width: 50%;\n }\n .col-xl-7 {\n -ms-flex: 0 0 58.333333%;\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n }\n .col-xl-8 {\n -ms-flex: 0 0 66.666667%;\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n }\n .col-xl-9 {\n -ms-flex: 0 0 75%;\n flex: 0 0 75%;\n max-width: 75%;\n }\n .col-xl-10 {\n -ms-flex: 0 0 83.333333%;\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n }\n .col-xl-11 {\n -ms-flex: 0 0 91.666667%;\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n }\n .col-xl-12 {\n -ms-flex: 0 0 100%;\n flex: 0 0 100%;\n max-width: 100%;\n }\n .order-xl-1 {\n -ms-flex-order: 1;\n order: 1;\n }\n .order-xl-2 {\n -ms-flex-order: 2;\n order: 2;\n }\n .order-xl-3 {\n -ms-flex-order: 3;\n order: 3;\n }\n .order-xl-4 {\n -ms-flex-order: 4;\n order: 4;\n }\n .order-xl-5 {\n -ms-flex-order: 5;\n order: 5;\n }\n .order-xl-6 {\n -ms-flex-order: 6;\n order: 6;\n }\n .order-xl-7 {\n -ms-flex-order: 7;\n order: 7;\n }\n .order-xl-8 {\n -ms-flex-order: 8;\n order: 8;\n }\n .order-xl-9 {\n -ms-flex-order: 9;\n order: 9;\n }\n .order-xl-10 {\n -ms-flex-order: 10;\n order: 10;\n }\n .order-xl-11 {\n -ms-flex-order: 11;\n order: 11;\n }\n .order-xl-12 {\n -ms-flex-order: 12;\n order: 12;\n }\n}\n\n.table {\n width: 100%;\n max-width: 100%;\n margin-bottom: 1rem;\n background-color: transparent;\n}\n\n.table th,\n.table td {\n padding: 0.75rem;\n vertical-align: top;\n border-top: 1px solid #e9ecef;\n}\n\n.table thead th {\n vertical-align: bottom;\n border-bottom: 2px solid #e9ecef;\n}\n\n.table tbody + tbody {\n border-top: 2px solid #e9ecef;\n}\n\n.table .table {\n background-color: #fff;\n}\n\n.table-sm th,\n.table-sm td {\n padding: 0.3rem;\n}\n\n.table-bordered {\n border: 1px solid #e9ecef;\n}\n\n.table-bordered th,\n.table-bordered td {\n border: 1px solid #e9ecef;\n}\n\n.table-bordered thead th,\n.table-bordered thead td {\n border-bottom-width: 2px;\n}\n\n.table-striped tbody tr:nth-of-type(odd) {\n background-color: rgba(0, 0, 0, 0.05);\n}\n\n.table-hover tbody tr:hover {\n background-color: rgba(0, 0, 0, 0.075);\n}\n\n.table-primary,\n.table-primary > th,\n.table-primary > td {\n background-color: #b8daff;\n}\n\n.table-hover .table-primary:hover {\n background-color: #9fcdff;\n}\n\n.table-hover .table-primary:hover > td,\n.table-hover .table-primary:hover > th {\n background-color: #9fcdff;\n}\n\n.table-secondary,\n.table-secondary > th,\n.table-secondary > td {\n background-color: #dddfe2;\n}\n\n.table-hover .table-secondary:hover {\n background-color: #cfd2d6;\n}\n\n.table-hover .table-secondary:hover > td,\n.table-hover .table-secondary:hover > th {\n background-color: #cfd2d6;\n}\n\n.table-success,\n.table-success > th,\n.table-success > td {\n background-color: #c3e6cb;\n}\n\n.table-hover .table-success:hover {\n background-color: #b1dfbb;\n}\n\n.table-hover .table-success:hover > td,\n.table-hover .table-success:hover > th {\n background-color: #b1dfbb;\n}\n\n.table-info,\n.table-info > th,\n.table-info > td {\n background-color: #bee5eb;\n}\n\n.table-hover .table-info:hover {\n background-color: #abdde5;\n}\n\n.table-hover .table-info:hover > td,\n.table-hover .table-info:hover > th {\n background-color: #abdde5;\n}\n\n.table-warning,\n.table-warning > th,\n.table-warning > td {\n background-color: #ffeeba;\n}\n\n.table-hover .table-warning:hover {\n background-color: #ffe8a1;\n}\n\n.table-hover .table-warning:hover > td,\n.table-hover .table-warning:hover > th {\n background-color: #ffe8a1;\n}\n\n.table-danger,\n.table-danger > th,\n.table-danger > td {\n background-color: #f5c6cb;\n}\n\n.table-hover .table-danger:hover {\n background-color: #f1b0b7;\n}\n\n.table-hover .table-danger:hover > td,\n.table-hover .table-danger:hover > th {\n background-color: #f1b0b7;\n}\n\n.table-light,\n.table-light > th,\n.table-light > td {\n background-color: #fdfdfe;\n}\n\n.table-hover .table-light:hover {\n background-color: #ececf6;\n}\n\n.table-hover .table-light:hover > td,\n.table-hover .table-light:hover > th {\n background-color: #ececf6;\n}\n\n.table-dark,\n.table-dark > th,\n.table-dark > td {\n background-color: #c6c8ca;\n}\n\n.table-hover .table-dark:hover {\n background-color: #b9bbbe;\n}\n\n.table-hover .table-dark:hover > td,\n.table-hover .table-dark:hover > th {\n background-color: #b9bbbe;\n}\n\n.table-active,\n.table-active > th,\n.table-active > td {\n background-color: rgba(0, 0, 0, 0.075);\n}\n\n.table-hover .table-active:hover {\n background-color: rgba(0, 0, 0, 0.075);\n}\n\n.table-hover .table-active:hover > td,\n.table-hover .table-active:hover > th {\n background-color: rgba(0, 0, 0, 0.075);\n}\n\n.thead-inverse th {\n color: #fff;\n background-color: #212529;\n}\n\n.thead-default th {\n color: #495057;\n background-color: #e9ecef;\n}\n\n.table-inverse {\n color: #fff;\n background-color: #212529;\n}\n\n.table-inverse th,\n.table-inverse td,\n.table-inverse thead th {\n border-color: #32383e;\n}\n\n.table-inverse.table-bordered {\n border: 0;\n}\n\n.table-inverse.table-striped tbody tr:nth-of-type(odd) {\n background-color: rgba(255, 255, 255, 0.05);\n}\n\n.table-inverse.table-hover tbody tr:hover {\n background-color: rgba(255, 255, 255, 0.075);\n}\n\n@media (max-width: 991px) {\n .table-responsive {\n display: block;\n width: 100%;\n overflow-x: auto;\n -ms-overflow-style: -ms-autohiding-scrollbar;\n }\n .table-responsive.table-bordered {\n border: 0;\n }\n}\n\n.form-control {\n display: block;\n width: 100%;\n padding: 0.5rem 0.75rem;\n font-size: 1rem;\n line-height: 1.25;\n color: #495057;\n background-color: #fff;\n background-image: none;\n background-clip: padding-box;\n border: 1px solid rgba(0, 0, 0, 0.15);\n border-radius: 0.25rem;\n transition: border-color ease-in-out 0.15s, box-shadow ease-in-out 0.15s;\n}\n\n.form-control::-ms-expand {\n background-color: transparent;\n border: 0;\n}\n\n.form-control:focus {\n color: #495057;\n background-color: #fff;\n border-color: #80bdff;\n outline: none;\n}\n\n.form-control::-webkit-input-placeholder {\n color: #868e96;\n opacity: 1;\n}\n\n.form-control:-ms-input-placeholder {\n color: #868e96;\n opacity: 1;\n}\n\n.form-control::placeholder {\n color: #868e96;\n opacity: 1;\n}\n\n.form-control:disabled, .form-control[readonly] {\n background-color: #e9ecef;\n opacity: 1;\n}\n\nselect.form-control:not([size]):not([multiple]) {\n height: calc(2.25rem + 2px);\n}\n\nselect.form-control:focus::-ms-value {\n color: #495057;\n background-color: #fff;\n}\n\n.form-control-file,\n.form-control-range {\n display: block;\n}\n\n.col-form-label {\n padding-top: calc(0.5rem - 1px * 2);\n padding-bottom: calc(0.5rem - 1px * 2);\n margin-bottom: 0;\n}\n\n.col-form-label-lg {\n padding-top: calc(0.5rem - 1px * 2);\n padding-bottom: calc(0.5rem - 1px * 2);\n font-size: 1.25rem;\n}\n\n.col-form-label-sm {\n padding-top: calc(0.25rem - 1px * 2);\n padding-bottom: calc(0.25rem - 1px * 2);\n font-size: 0.875rem;\n}\n\n.col-form-legend {\n padding-top: 0.5rem;\n padding-bottom: 0.5rem;\n margin-bottom: 0;\n font-size: 1rem;\n}\n\n.form-control-plaintext {\n padding-top: 0.5rem;\n padding-bottom: 0.5rem;\n margin-bottom: 0;\n line-height: 1.25;\n border: solid transparent;\n border-width: 1px 0;\n}\n\n.form-control-plaintext.form-control-sm, .input-group-sm > .form-control-plaintext.form-control,\n.input-group-sm > .form-control-plaintext.input-group-addon,\n.input-group-sm > .input-group-btn > .form-control-plaintext.btn, .form-control-plaintext.form-control-lg, .input-group-lg > .form-control-plaintext.form-control,\n.input-group-lg > .form-control-plaintext.input-group-addon,\n.input-group-lg > .input-group-btn > .form-control-plaintext.btn {\n padding-right: 0;\n padding-left: 0;\n}\n\n.form-control-sm, .input-group-sm > .form-control,\n.input-group-sm > .input-group-addon,\n.input-group-sm > .input-group-btn > .btn {\n padding: 0.25rem 0.5rem;\n font-size: 0.875rem;\n line-height: 1.5;\n border-radius: 0.2rem;\n}\n\nselect.form-control-sm:not([size]):not([multiple]), .input-group-sm > select.form-control:not([size]):not([multiple]),\n.input-group-sm > select.input-group-addon:not([size]):not([multiple]),\n.input-group-sm > .input-group-btn > select.btn:not([size]):not([multiple]) {\n height: calc(1.8125rem + 2px);\n}\n\n.form-control-lg, .input-group-lg > .form-control,\n.input-group-lg > .input-group-addon,\n.input-group-lg > .input-group-btn > .btn {\n padding: 0.5rem 1rem;\n font-size: 1.25rem;\n line-height: 1.5;\n border-radius: 0.3rem;\n}\n\nselect.form-control-lg:not([size]):not([multiple]), .input-group-lg > select.form-control:not([size]):not([multiple]),\n.input-group-lg > select.input-group-addon:not([size]):not([multiple]),\n.input-group-lg > .input-group-btn > select.btn:not([size]):not([multiple]) {\n height: calc(2.3125rem + 2px);\n}\n\n.form-group {\n margin-bottom: 1rem;\n}\n\n.form-text {\n display: block;\n margin-top: 0.25rem;\n}\n\n.form-row {\n display: -ms-flexbox;\n display: flex;\n -ms-flex-wrap: wrap;\n flex-wrap: wrap;\n margin-right: -5px;\n margin-left: -5px;\n}\n\n.form-row > .col,\n.form-row > [class*=\"col-\"] {\n padding-right: 5px;\n padding-left: 5px;\n}\n\n.form-check {\n position: relative;\n display: block;\n margin-bottom: 0.5rem;\n}\n\n.form-check.disabled .form-check-label {\n color: #868e96;\n}\n\n.form-check-label {\n padding-left: 1.25rem;\n margin-bottom: 0;\n}\n\n.form-check-input {\n position: absolute;\n margin-top: 0.25rem;\n margin-left: -1.25rem;\n}\n\n.form-check-input:only-child {\n position: static;\n}\n\n.form-check-inline {\n display: inline-block;\n}\n\n.form-check-inline .form-check-label {\n vertical-align: middle;\n}\n\n.form-check-inline + .form-check-inline {\n margin-left: 0.75rem;\n}\n\n.invalid-feedback {\n display: none;\n margin-top: .25rem;\n font-size: .875rem;\n color: #dc3545;\n}\n\n.invalid-tooltip {\n position: absolute;\n top: 100%;\n z-index: 5;\n display: none;\n width: 250px;\n padding: .5rem;\n margin-top: .1rem;\n font-size: .875rem;\n line-height: 1;\n color: #fff;\n background-color: rgba(220, 53, 69, 0.8);\n border-radius: .2rem;\n}\n\n.was-validated .form-control:valid, .form-control.is-valid, .was-validated\n.custom-select:valid,\n.custom-select.is-valid {\n border-color: #28a745;\n}\n\n.was-validated .form-control:valid:focus, .form-control.is-valid:focus, .was-validated\n.custom-select:valid:focus,\n.custom-select.is-valid:focus {\n box-shadow: 0 0 0 0.2rem rgba(40, 167, 69, 0.25);\n}\n\n.was-validated .form-control:valid ~ .invalid-feedback,\n.was-validated .form-control:valid ~ .invalid-tooltip, .form-control.is-valid ~ .invalid-feedback,\n.form-control.is-valid ~ .invalid-tooltip, .was-validated\n.custom-select:valid ~ .invalid-feedback,\n.was-validated\n.custom-select:valid ~ .invalid-tooltip,\n.custom-select.is-valid ~ .invalid-feedback,\n.custom-select.is-valid ~ .invalid-tooltip {\n display: block;\n}\n\n.was-validated .form-check-input:valid + .form-check-label, .form-check-input.is-valid + .form-check-label {\n color: #28a745;\n}\n\n.was-validated .custom-control-input:valid ~ .custom-control-indicator, .custom-control-input.is-valid ~ .custom-control-indicator {\n background-color: rgba(40, 167, 69, 0.25);\n}\n\n.was-validated .custom-control-input:valid ~ .custom-control-description, .custom-control-input.is-valid ~ .custom-control-description {\n color: #28a745;\n}\n\n.was-validated .custom-file-input:valid ~ .custom-file-control, .custom-file-input.is-valid ~ .custom-file-control {\n border-color: #28a745;\n}\n\n.was-validated .custom-file-input:valid ~ .custom-file-control::before, .custom-file-input.is-valid ~ .custom-file-control::before {\n border-color: inherit;\n}\n\n.was-validated .custom-file-input:valid:focus, .custom-file-input.is-valid:focus {\n box-shadow: 0 0 0 0.2rem rgba(40, 167, 69, 0.25);\n}\n\n.was-validated .form-control:invalid, .form-control.is-invalid, .was-validated\n.custom-select:invalid,\n.custom-select.is-invalid {\n border-color: #dc3545;\n}\n\n.was-validated .form-control:invalid:focus, .form-control.is-invalid:focus, .was-validated\n.custom-select:invalid:focus,\n.custom-select.is-invalid:focus {\n box-shadow: 0 0 0 0.2rem rgba(220, 53, 69, 0.25);\n}\n\n.was-validated .form-control:invalid ~ .invalid-feedback,\n.was-validated .form-control:invalid ~ .invalid-tooltip, .form-control.is-invalid ~ .invalid-feedback,\n.form-control.is-invalid ~ .invalid-tooltip, .was-validated\n.custom-select:invalid ~ .invalid-feedback,\n.was-validated\n.custom-select:invalid ~ .invalid-tooltip,\n.custom-select.is-invalid ~ .invalid-feedback,\n.custom-select.is-invalid ~ .invalid-tooltip {\n display: block;\n}\n\n.was-validated .form-check-input:invalid + .form-check-label, .form-check-input.is-invalid + .form-check-label {\n color: #dc3545;\n}\n\n.was-validated .custom-control-input:invalid ~ .custom-control-indicator, .custom-control-input.is-invalid ~ .custom-control-indicator {\n background-color: rgba(220, 53, 69, 0.25);\n}\n\n.was-validated .custom-control-input:invalid ~ .custom-control-description, .custom-control-input.is-invalid ~ .custom-control-description {\n color: #dc3545;\n}\n\n.was-validated .custom-file-input:invalid ~ .custom-file-control, .custom-file-input.is-invalid ~ .custom-file-control {\n border-color: #dc3545;\n}\n\n.was-validated .custom-file-input:invalid ~ .custom-file-control::before, .custom-file-input.is-invalid ~ .custom-file-control::before {\n border-color: inherit;\n}\n\n.was-validated .custom-file-input:invalid:focus, .custom-file-input.is-invalid:focus {\n box-shadow: 0 0 0 0.2rem rgba(220, 53, 69, 0.25);\n}\n\n.form-inline {\n display: -ms-flexbox;\n display: flex;\n -ms-flex-flow: row wrap;\n flex-flow: row wrap;\n -ms-flex-align: center;\n align-items: center;\n}\n\n.form-inline .form-check {\n width: 100%;\n}\n\n@media (min-width: 576px) {\n .form-inline label {\n display: -ms-flexbox;\n display: flex;\n -ms-flex-align: center;\n align-items: center;\n -ms-flex-pack: center;\n justify-content: center;\n margin-bottom: 0;\n }\n .form-inline .form-group {\n display: -ms-flexbox;\n display: flex;\n -ms-flex: 0 0 auto;\n flex: 0 0 auto;\n -ms-flex-flow: row wrap;\n flex-flow: row wrap;\n -ms-flex-align: center;\n align-items: center;\n margin-bottom: 0;\n }\n .form-inline .form-control {\n display: inline-block;\n width: auto;\n vertical-align: middle;\n }\n .form-inline .form-control-plaintext {\n display: inline-block;\n }\n .form-inline .input-group {\n width: auto;\n }\n .form-inline .form-control-label {\n margin-bottom: 0;\n vertical-align: middle;\n }\n .form-inline .form-check {\n display: -ms-flexbox;\n display: flex;\n -ms-flex-align: center;\n align-items: center;\n -ms-flex-pack: center;\n justify-content: center;\n width: auto;\n margin-top: 0;\n margin-bottom: 0;\n }\n .form-inline .form-check-label {\n padding-left: 0;\n }\n .form-inline .form-check-input {\n position: relative;\n margin-top: 0;\n margin-right: 0.25rem;\n margin-left: 0;\n }\n .form-inline .custom-control {\n display: -ms-flexbox;\n display: flex;\n -ms-flex-align: center;\n align-items: center;\n -ms-flex-pack: center;\n justify-content: center;\n padding-left: 0;\n }\n .form-inline .custom-control-indicator {\n position: static;\n display: inline-block;\n margin-right: 0.25rem;\n vertical-align: text-bottom;\n }\n .form-inline .has-feedback .form-control-feedback {\n top: 0;\n }\n}\n\n.btn {\n display: inline-block;\n font-weight: normal;\n text-align: center;\n white-space: nowrap;\n vertical-align: middle;\n -webkit-user-select: none;\n -moz-user-select: none;\n -ms-user-select: none;\n user-select: none;\n border: 1px solid transparent;\n padding: 0.5rem 0.75rem;\n font-size: 1rem;\n line-height: 1.25;\n border-radius: 0.25rem;\n transition: all 0.15s ease-in-out;\n}\n\n.btn:focus, .btn:hover {\n text-decoration: none;\n}\n\n.btn:focus, .btn.focus {\n outline: 0;\n box-shadow: 0 0 0 3px rgba(0, 123, 255, 0.25);\n}\n\n.btn.disabled, .btn:disabled {\n opacity: .65;\n}\n\n.btn:active, .btn.active {\n background-image: none;\n}\n\na.btn.disabled,\nfieldset[disabled] a.btn {\n pointer-events: none;\n}\n\n.btn-primary {\n color: #fff;\n background-color: #007bff;\n border-color: #007bff;\n}\n\n.btn-primary:hover {\n color: #fff;\n background-color: #0069d9;\n border-color: #0062cc;\n}\n\n.btn-primary:focus, .btn-primary.focus {\n box-shadow: 0 0 0 3px rgba(0, 123, 255, 0.5);\n}\n\n.btn-primary.disabled, .btn-primary:disabled {\n background-color: #007bff;\n border-color: #007bff;\n}\n\n.btn-primary:active, .btn-primary.active,\n.show > .btn-primary.dropdown-toggle {\n background-color: #0069d9;\n background-image: none;\n border-color: #0062cc;\n}\n\n.btn-secondary {\n color: #fff;\n background-color: #868e96;\n border-color: #868e96;\n}\n\n.btn-secondary:hover {\n color: #fff;\n background-color: #727b84;\n border-color: #6c757d;\n}\n\n.btn-secondary:focus, .btn-secondary.focus {\n box-shadow: 0 0 0 3px rgba(134, 142, 150, 0.5);\n}\n\n.btn-secondary.disabled, .btn-secondary:disabled {\n background-color: #868e96;\n border-color: #868e96;\n}\n\n.btn-secondary:active, .btn-secondary.active,\n.show > .btn-secondary.dropdown-toggle {\n background-color: #727b84;\n background-image: none;\n border-color: #6c757d;\n}\n\n.btn-success {\n color: #fff;\n background-color: #28a745;\n border-color: #28a745;\n}\n\n.btn-success:hover {\n color: #fff;\n background-color: #218838;\n border-color: #1e7e34;\n}\n\n.btn-success:focus, .btn-success.focus {\n box-shadow: 0 0 0 3px rgba(40, 167, 69, 0.5);\n}\n\n.btn-success.disabled, .btn-success:disabled {\n background-color: #28a745;\n border-color: #28a745;\n}\n\n.btn-success:active, .btn-success.active,\n.show > .btn-success.dropdown-toggle {\n background-color: #218838;\n background-image: none;\n border-color: #1e7e34;\n}\n\n.btn-info {\n color: #fff;\n background-color: #17a2b8;\n border-color: #17a2b8;\n}\n\n.btn-info:hover {\n color: #fff;\n background-color: #138496;\n border-color: #117a8b;\n}\n\n.btn-info:focus, .btn-info.focus {\n box-shadow: 0 0 0 3px rgba(23, 162, 184, 0.5);\n}\n\n.btn-info.disabled, .btn-info:disabled {\n background-color: #17a2b8;\n border-color: #17a2b8;\n}\n\n.btn-info:active, .btn-info.active,\n.show > .btn-info.dropdown-toggle {\n background-color: #138496;\n background-image: none;\n border-color: #117a8b;\n}\n\n.btn-warning {\n color: #111;\n background-color: #ffc107;\n border-color: #ffc107;\n}\n\n.btn-warning:hover {\n color: #111;\n background-color: #e0a800;\n border-color: #d39e00;\n}\n\n.btn-warning:focus, .btn-warning.focus {\n box-shadow: 0 0 0 3px rgba(255, 193, 7, 0.5);\n}\n\n.btn-warning.disabled, .btn-warning:disabled {\n background-color: #ffc107;\n border-color: #ffc107;\n}\n\n.btn-warning:active, .btn-warning.active,\n.show > .btn-warning.dropdown-toggle {\n background-color: #e0a800;\n background-image: none;\n border-color: #d39e00;\n}\n\n.btn-danger {\n color: #fff;\n background-color: #dc3545;\n border-color: #dc3545;\n}\n\n.btn-danger:hover {\n color: #fff;\n background-color: #c82333;\n border-color: #bd2130;\n}\n\n.btn-danger:focus, .btn-danger.focus {\n box-shadow: 0 0 0 3px rgba(220, 53, 69, 0.5);\n}\n\n.btn-danger.disabled, .btn-danger:disabled {\n background-color: #dc3545;\n border-color: #dc3545;\n}\n\n.btn-danger:active, .btn-danger.active,\n.show > .btn-danger.dropdown-toggle {\n background-color: #c82333;\n background-image: none;\n border-color: #bd2130;\n}\n\n.btn-light {\n color: #111;\n background-color: #f8f9fa;\n border-color: #f8f9fa;\n}\n\n.btn-light:hover {\n color: #111;\n background-color: #e2e6ea;\n border-color: #dae0e5;\n}\n\n.btn-light:focus, .btn-light.focus {\n box-shadow: 0 0 0 3px rgba(248, 249, 250, 0.5);\n}\n\n.btn-light.disabled, .btn-light:disabled {\n background-color: #f8f9fa;\n border-color: #f8f9fa;\n}\n\n.btn-light:active, .btn-light.active,\n.show > .btn-light.dropdown-toggle {\n background-color: #e2e6ea;\n background-image: none;\n border-color: #dae0e5;\n}\n\n.btn-dark {\n color: #fff;\n background-color: #343a40;\n border-color: #343a40;\n}\n\n.btn-dark:hover {\n color: #fff;\n background-color: #23272b;\n border-color: #1d2124;\n}\n\n.btn-dark:focus, .btn-dark.focus {\n box-shadow: 0 0 0 3px rgba(52, 58, 64, 0.5);\n}\n\n.btn-dark.disabled, .btn-dark:disabled {\n background-color: #343a40;\n border-color: #343a40;\n}\n\n.btn-dark:active, .btn-dark.active,\n.show > .btn-dark.dropdown-toggle {\n background-color: #23272b;\n background-image: none;\n border-color: #1d2124;\n}\n\n.btn-outline-primary {\n color: #007bff;\n background-color: transparent;\n background-image: none;\n border-color: #007bff;\n}\n\n.btn-outline-primary:hover {\n color: #fff;\n background-color: #007bff;\n border-color: #007bff;\n}\n\n.btn-outline-primary:focus, .btn-outline-primary.focus {\n box-shadow: 0 0 0 3px rgba(0, 123, 255, 0.5);\n}\n\n.btn-outline-primary.disabled, .btn-outline-primary:disabled {\n color: #007bff;\n background-color: transparent;\n}\n\n.btn-outline-primary:active, .btn-outline-primary.active,\n.show > .btn-outline-primary.dropdown-toggle {\n color: #fff;\n background-color: #007bff;\n border-color: #007bff;\n}\n\n.btn-outline-secondary {\n color: #868e96;\n background-color: transparent;\n background-image: none;\n border-color: #868e96;\n}\n\n.btn-outline-secondary:hover {\n color: #fff;\n background-color: #868e96;\n border-color: #868e96;\n}\n\n.btn-outline-secondary:focus, .btn-outline-secondary.focus {\n box-shadow: 0 0 0 3px rgba(134, 142, 150, 0.5);\n}\n\n.btn-outline-secondary.disabled, .btn-outline-secondary:disabled {\n color: #868e96;\n background-color: transparent;\n}\n\n.btn-outline-secondary:active, .btn-outline-secondary.active,\n.show > .btn-outline-secondary.dropdown-toggle {\n color: #fff;\n background-color: #868e96;\n border-color: #868e96;\n}\n\n.btn-outline-success {\n color: #28a745;\n background-color: transparent;\n background-image: none;\n border-color: #28a745;\n}\n\n.btn-outline-success:hover {\n color: #fff;\n background-color: #28a745;\n border-color: #28a745;\n}\n\n.btn-outline-success:focus, .btn-outline-success.focus {\n box-shadow: 0 0 0 3px rgba(40, 167, 69, 0.5);\n}\n\n.btn-outline-success.disabled, .btn-outline-success:disabled {\n color: #28a745;\n background-color: transparent;\n}\n\n.btn-outline-success:active, .btn-outline-success.active,\n.show > .btn-outline-success.dropdown-toggle {\n color: #fff;\n background-color: #28a745;\n border-color: #28a745;\n}\n\n.btn-outline-info {\n color: #17a2b8;\n background-color: transparent;\n background-image: none;\n border-color: #17a2b8;\n}\n\n.btn-outline-info:hover {\n color: #fff;\n background-color: #17a2b8;\n border-color: #17a2b8;\n}\n\n.btn-outline-info:focus, .btn-outline-info.focus {\n box-shadow: 0 0 0 3px rgba(23, 162, 184, 0.5);\n}\n\n.btn-outline-info.disabled, .btn-outline-info:disabled {\n color: #17a2b8;\n background-color: transparent;\n}\n\n.btn-outline-info:active, .btn-outline-info.active,\n.show > .btn-outline-info.dropdown-toggle {\n color: #fff;\n background-color: #17a2b8;\n border-color: #17a2b8;\n}\n\n.btn-outline-warning {\n color: #ffc107;\n background-color: transparent;\n background-image: none;\n border-color: #ffc107;\n}\n\n.btn-outline-warning:hover {\n color: #fff;\n background-color: #ffc107;\n border-color: #ffc107;\n}\n\n.btn-outline-warning:focus, .btn-outline-warning.focus {\n box-shadow: 0 0 0 3px rgba(255, 193, 7, 0.5);\n}\n\n.btn-outline-warning.disabled, .btn-outline-warning:disabled {\n color: #ffc107;\n background-color: transparent;\n}\n\n.btn-outline-warning:active, .btn-outline-warning.active,\n.show > .btn-outline-warning.dropdown-toggle {\n color: #fff;\n background-color: #ffc107;\n border-color: #ffc107;\n}\n\n.btn-outline-danger {\n color: #dc3545;\n background-color: transparent;\n background-image: none;\n border-color: #dc3545;\n}\n\n.btn-outline-danger:hover {\n color: #fff;\n background-color: #dc3545;\n border-color: #dc3545;\n}\n\n.btn-outline-danger:focus, .btn-outline-danger.focus {\n box-shadow: 0 0 0 3px rgba(220, 53, 69, 0.5);\n}\n\n.btn-outline-danger.disabled, .btn-outline-danger:disabled {\n color: #dc3545;\n background-color: transparent;\n}\n\n.btn-outline-danger:active, .btn-outline-danger.active,\n.show > .btn-outline-danger.dropdown-toggle {\n color: #fff;\n background-color: #dc3545;\n border-color: #dc3545;\n}\n\n.btn-outline-light {\n color: #f8f9fa;\n background-color: transparent;\n background-image: none;\n border-color: #f8f9fa;\n}\n\n.btn-outline-light:hover {\n color: #fff;\n background-color: #f8f9fa;\n border-color: #f8f9fa;\n}\n\n.btn-outline-light:focus, .btn-outline-light.focus {\n box-shadow: 0 0 0 3px rgba(248, 249, 250, 0.5);\n}\n\n.btn-outline-light.disabled, .btn-outline-light:disabled {\n color: #f8f9fa;\n background-color: transparent;\n}\n\n.btn-outline-light:active, .btn-outline-light.active,\n.show > .btn-outline-light.dropdown-toggle {\n color: #fff;\n background-color: #f8f9fa;\n border-color: #f8f9fa;\n}\n\n.btn-outline-dark {\n color: #343a40;\n background-color: transparent;\n background-image: none;\n border-color: #343a40;\n}\n\n.btn-outline-dark:hover {\n color: #fff;\n background-color: #343a40;\n border-color: #343a40;\n}\n\n.btn-outline-dark:focus, .btn-outline-dark.focus {\n box-shadow: 0 0 0 3px rgba(52, 58, 64, 0.5);\n}\n\n.btn-outline-dark.disabled, .btn-outline-dark:disabled {\n color: #343a40;\n background-color: transparent;\n}\n\n.btn-outline-dark:active, .btn-outline-dark.active,\n.show > .btn-outline-dark.dropdown-toggle {\n color: #fff;\n background-color: #343a40;\n border-color: #343a40;\n}\n\n.btn-link {\n font-weight: normal;\n color: #007bff;\n border-radius: 0;\n}\n\n.btn-link, .btn-link:active, .btn-link.active, .btn-link:disabled {\n background-color: transparent;\n}\n\n.btn-link, .btn-link:focus, .btn-link:active {\n border-color: transparent;\n box-shadow: none;\n}\n\n.btn-link:hover {\n border-color: transparent;\n}\n\n.btn-link:focus, .btn-link:hover {\n color: #0056b3;\n text-decoration: underline;\n background-color: transparent;\n}\n\n.btn-link:disabled {\n color: #868e96;\n}\n\n.btn-link:disabled:focus, .btn-link:disabled:hover {\n text-decoration: none;\n}\n\n.btn-lg, .btn-group-lg > .btn {\n padding: 0.5rem 1rem;\n font-size: 1.25rem;\n line-height: 1.5;\n border-radius: 0.3rem;\n}\n\n.btn-sm, .btn-group-sm > .btn {\n padding: 0.25rem 0.5rem;\n font-size: 0.875rem;\n line-height: 1.5;\n border-radius: 0.2rem;\n}\n\n.btn-block {\n display: block;\n width: 100%;\n}\n\n.btn-block + .btn-block {\n margin-top: 0.5rem;\n}\n\ninput[type=\"submit\"].btn-block,\ninput[type=\"reset\"].btn-block,\ninput[type=\"button\"].btn-block {\n width: 100%;\n}\n\n.fade {\n opacity: 0;\n transition: opacity 0.15s linear;\n}\n\n.fade.show {\n opacity: 1;\n}\n\n.collapse {\n display: none;\n}\n\n.collapse.show {\n display: block;\n}\n\ntr.collapse.show {\n display: table-row;\n}\n\ntbody.collapse.show {\n display: table-row-group;\n}\n\n.collapsing {\n position: relative;\n height: 0;\n overflow: hidden;\n transition: height 0.35s ease;\n}\n\n.dropup,\n.dropdown {\n position: relative;\n}\n\n.dropdown-toggle::after {\n display: inline-block;\n width: 0;\n height: 0;\n margin-left: 0.255em;\n vertical-align: 0.255em;\n content: \"\";\n border-top: 0.3em solid;\n border-right: 0.3em solid transparent;\n border-left: 0.3em solid transparent;\n}\n\n.dropdown-toggle:empty::after {\n margin-left: 0;\n}\n\n.dropup .dropdown-menu {\n margin-top: 0;\n margin-bottom: 0.125rem;\n}\n\n.dropup .dropdown-toggle::after {\n border-top: 0;\n border-bottom: 0.3em solid;\n}\n\n.dropdown-menu {\n position: absolute;\n top: 100%;\n left: 0;\n z-index: 1000;\n display: none;\n float: left;\n min-width: 10rem;\n padding: 0.5rem 0;\n margin: 0.125rem 0 0;\n font-size: 1rem;\n color: #212529;\n text-align: left;\n list-style: none;\n background-color: #fff;\n background-clip: padding-box;\n border: 1px solid rgba(0, 0, 0, 0.15);\n border-radius: 0.25rem;\n}\n\n.dropdown-divider {\n height: 0;\n margin: 0.5rem 0;\n overflow: hidden;\n border-top: 1px solid #e9ecef;\n}\n\n.dropdown-item {\n display: block;\n width: 100%;\n padding: 0.25rem 1.5rem;\n clear: both;\n font-weight: normal;\n color: #212529;\n text-align: inherit;\n white-space: nowrap;\n background: none;\n border: 0;\n}\n\n.dropdown-item:focus, .dropdown-item:hover {\n color: #16181b;\n text-decoration: none;\n background-color: #f8f9fa;\n}\n\n.dropdown-item.active, .dropdown-item:active {\n color: #fff;\n text-decoration: none;\n background-color: #007bff;\n}\n\n.dropdown-item.disabled, .dropdown-item:disabled {\n color: #868e96;\n background-color: transparent;\n}\n\n.show > a {\n outline: 0;\n}\n\n.dropdown-menu.show {\n display: block;\n}\n\n.dropdown-header {\n display: block;\n padding: 0.5rem 1.5rem;\n margin-bottom: 0;\n font-size: 0.875rem;\n color: #868e96;\n white-space: nowrap;\n}\n\n.btn-group,\n.btn-group-vertical {\n position: relative;\n display: -ms-inline-flexbox;\n display: inline-flex;\n vertical-align: middle;\n}\n\n.btn-group > .btn,\n.btn-group-vertical > .btn {\n position: relative;\n -ms-flex: 0 1 auto;\n flex: 0 1 auto;\n margin-bottom: 0;\n}\n\n.btn-group > .btn:hover,\n.btn-group-vertical > .btn:hover {\n z-index: 2;\n}\n\n.btn-group > .btn:focus, .btn-group > .btn:active, .btn-group > .btn.active,\n.btn-group-vertical > .btn:focus,\n.btn-group-vertical > .btn:active,\n.btn-group-vertical > .btn.active {\n z-index: 2;\n}\n\n.btn-group .btn + .btn,\n.btn-group .btn + .btn-group,\n.btn-group .btn-group + .btn,\n.btn-group .btn-group + .btn-group,\n.btn-group-vertical .btn + .btn,\n.btn-group-vertical .btn + .btn-group,\n.btn-group-vertical .btn-group + .btn,\n.btn-group-vertical .btn-group + .btn-group {\n margin-left: -1px;\n}\n\n.btn-toolbar {\n display: -ms-flexbox;\n display: flex;\n -ms-flex-wrap: wrap;\n flex-wrap: wrap;\n -ms-flex-pack: start;\n justify-content: flex-start;\n}\n\n.btn-toolbar .input-group {\n width: auto;\n}\n\n.btn-group > .btn:not(:first-child):not(:last-child):not(.dropdown-toggle) {\n border-radius: 0;\n}\n\n.btn-group > .btn:first-child {\n margin-left: 0;\n}\n\n.btn-group > .btn:first-child:not(:last-child):not(.dropdown-toggle) {\n border-top-right-radius: 0;\n border-bottom-right-radius: 0;\n}\n\n.btn-group > .btn:last-child:not(:first-child),\n.btn-group > .dropdown-toggle:not(:first-child) {\n border-top-left-radius: 0;\n border-bottom-left-radius: 0;\n}\n\n.btn-group > .btn-group {\n float: left;\n}\n\n.btn-group > .btn-group:not(:first-child):not(:last-child) > .btn {\n border-radius: 0;\n}\n\n.btn-group > .btn-group:first-child:not(:last-child) > .btn:last-child,\n.btn-group > .btn-group:first-child:not(:last-child) > .dropdown-toggle {\n border-top-right-radius: 0;\n border-bottom-right-radius: 0;\n}\n\n.btn-group > .btn-group:last-child:not(:first-child) > .btn:first-child {\n border-top-left-radius: 0;\n border-bottom-left-radius: 0;\n}\n\n.btn + .dropdown-toggle-split {\n padding-right: 0.5625rem;\n padding-left: 0.5625rem;\n}\n\n.btn + .dropdown-toggle-split::after {\n margin-left: 0;\n}\n\n.btn-sm + .dropdown-toggle-split, .btn-group-sm > .btn + .dropdown-toggle-split {\n padding-right: 0.375rem;\n padding-left: 0.375rem;\n}\n\n.btn-lg + .dropdown-toggle-split, .btn-group-lg > .btn + .dropdown-toggle-split {\n padding-right: 0.75rem;\n padding-left: 0.75rem;\n}\n\n.btn-group-vertical {\n display: -ms-inline-flexbox;\n display: inline-flex;\n -ms-flex-direction: column;\n flex-direction: column;\n -ms-flex-align: start;\n align-items: flex-start;\n -ms-flex-pack: center;\n justify-content: center;\n}\n\n.btn-group-vertical .btn,\n.btn-group-vertical .btn-group {\n width: 100%;\n}\n\n.btn-group-vertical > .btn + .btn,\n.btn-group-vertical > .btn + .btn-group,\n.btn-group-vertical > .btn-group + .btn,\n.btn-group-vertical > .btn-group + .btn-group {\n margin-top: -1px;\n margin-left: 0;\n}\n\n.btn-group-vertical > .btn:not(:first-child):not(:last-child) {\n border-radius: 0;\n}\n\n.btn-group-vertical > .btn:first-child:not(:last-child) {\n border-bottom-right-radius: 0;\n border-bottom-left-radius: 0;\n}\n\n.btn-group-vertical > .btn:last-child:not(:first-child) {\n border-top-left-radius: 0;\n border-top-right-radius: 0;\n}\n\n.btn-group-vertical > .btn-group:not(:first-child):not(:last-child) > .btn {\n border-radius: 0;\n}\n\n.btn-group-vertical > .btn-group:first-child:not(:last-child) > .btn:last-child,\n.btn-group-vertical > .btn-group:first-child:not(:last-child) > .dropdown-toggle {\n border-bottom-right-radius: 0;\n border-bottom-left-radius: 0;\n}\n\n.btn-group-vertical > .btn-group:last-child:not(:first-child) > .btn:first-child {\n border-top-left-radius: 0;\n border-top-right-radius: 0;\n}\n\n[data-toggle=\"buttons\"] > .btn input[type=\"radio\"],\n[data-toggle=\"buttons\"] > .btn input[type=\"checkbox\"],\n[data-toggle=\"buttons\"] > .btn-group > .btn input[type=\"radio\"],\n[data-toggle=\"buttons\"] > .btn-group > .btn input[type=\"checkbox\"] {\n position: absolute;\n clip: rect(0, 0, 0, 0);\n pointer-events: none;\n}\n\n.input-group {\n position: relative;\n display: -ms-flexbox;\n display: flex;\n width: 100%;\n}\n\n.input-group .form-control {\n position: relative;\n z-index: 2;\n -ms-flex: 1 1 auto;\n flex: 1 1 auto;\n width: 1%;\n margin-bottom: 0;\n}\n\n.input-group .form-control:focus, .input-group .form-control:active, .input-group .form-control:hover {\n z-index: 3;\n}\n\n.input-group-addon,\n.input-group-btn,\n.input-group .form-control {\n display: -ms-flexbox;\n display: flex;\n -ms-flex-align: center;\n align-items: center;\n}\n\n.input-group-addon:not(:first-child):not(:last-child),\n.input-group-btn:not(:first-child):not(:last-child),\n.input-group .form-control:not(:first-child):not(:last-child) {\n border-radius: 0;\n}\n\n.input-group-addon,\n.input-group-btn {\n white-space: nowrap;\n vertical-align: middle;\n}\n\n.input-group-addon {\n padding: 0.5rem 0.75rem;\n margin-bottom: 0;\n font-size: 1rem;\n font-weight: normal;\n line-height: 1.25;\n color: #495057;\n text-align: center;\n background-color: #e9ecef;\n border: 1px solid rgba(0, 0, 0, 0.15);\n border-radius: 0.25rem;\n}\n\n.input-group-addon.form-control-sm,\n.input-group-sm > .input-group-addon,\n.input-group-sm > .input-group-btn > .input-group-addon.btn {\n padding: 0.25rem 0.5rem;\n font-size: 0.875rem;\n border-radius: 0.2rem;\n}\n\n.input-group-addon.form-control-lg,\n.input-group-lg > .input-group-addon,\n.input-group-lg > .input-group-btn > .input-group-addon.btn {\n padding: 0.5rem 1rem;\n font-size: 1.25rem;\n border-radius: 0.3rem;\n}\n\n.input-group-addon input[type=\"radio\"],\n.input-group-addon input[type=\"checkbox\"] {\n margin-top: 0;\n}\n\n.input-group .form-control:not(:last-child),\n.input-group-addon:not(:last-child),\n.input-group-btn:not(:last-child) > .btn,\n.input-group-btn:not(:last-child) > .btn-group > .btn,\n.input-group-btn:not(:last-child) > .dropdown-toggle,\n.input-group-btn:not(:first-child) > .btn:not(:last-child):not(.dropdown-toggle),\n.input-group-btn:not(:first-child) > .btn-group:not(:last-child) > .btn {\n border-top-right-radius: 0;\n border-bottom-right-radius: 0;\n}\n\n.input-group-addon:not(:last-child) {\n border-right: 0;\n}\n\n.input-group .form-control:not(:first-child),\n.input-group-addon:not(:first-child),\n.input-group-btn:not(:first-child) > .btn,\n.input-group-btn:not(:first-child) > .btn-group > .btn,\n.input-group-btn:not(:first-child) > .dropdown-toggle,\n.input-group-btn:not(:last-child) > .btn:not(:first-child),\n.input-group-btn:not(:last-child) > .btn-group:not(:first-child) > .btn {\n border-top-left-radius: 0;\n border-bottom-left-radius: 0;\n}\n\n.form-control + .input-group-addon:not(:first-child) {\n border-left: 0;\n}\n\n.input-group-btn {\n position: relative;\n font-size: 0;\n white-space: nowrap;\n}\n\n.input-group-btn > .btn {\n position: relative;\n}\n\n.input-group-btn > .btn + .btn {\n margin-left: -1px;\n}\n\n.input-group-btn > .btn:focus, .input-group-btn > .btn:active, .input-group-btn > .btn:hover {\n z-index: 3;\n}\n\n.input-group-btn:not(:last-child) > .btn,\n.input-group-btn:not(:last-child) > .btn-group {\n margin-right: -1px;\n}\n\n.input-group-btn:not(:first-child) > .btn,\n.input-group-btn:not(:first-child) > .btn-group {\n z-index: 2;\n margin-left: -1px;\n}\n\n.input-group-btn:not(:first-child) > .btn:focus, .input-group-btn:not(:first-child) > .btn:active, .input-group-btn:not(:first-child) > .btn:hover,\n.input-group-btn:not(:first-child) > .btn-group:focus,\n.input-group-btn:not(:first-child) > .btn-group:active,\n.input-group-btn:not(:first-child) > .btn-group:hover {\n z-index: 3;\n}\n\n.custom-control {\n position: relative;\n display: -ms-inline-flexbox;\n display: inline-flex;\n min-height: 1.5rem;\n padding-left: 1.5rem;\n margin-right: 1rem;\n}\n\n.custom-control-input {\n position: absolute;\n z-index: -1;\n opacity: 0;\n}\n\n.custom-control-input:checked ~ .custom-control-indicator {\n color: #fff;\n background-color: #007bff;\n}\n\n.custom-control-input:focus ~ .custom-control-indicator {\n box-shadow: 0 0 0 1px #fff, 0 0 0 3px #007bff;\n}\n\n.custom-control-input:active ~ .custom-control-indicator {\n color: #fff;\n background-color: #b3d7ff;\n}\n\n.custom-control-input:disabled ~ .custom-control-indicator {\n background-color: #e9ecef;\n}\n\n.custom-control-input:disabled ~ .custom-control-description {\n color: #868e96;\n}\n\n.custom-control-indicator {\n position: absolute;\n top: 0.25rem;\n left: 0;\n display: block;\n width: 1rem;\n height: 1rem;\n pointer-events: none;\n -webkit-user-select: none;\n -moz-user-select: none;\n -ms-user-select: none;\n user-select: none;\n background-color: #ddd;\n background-repeat: no-repeat;\n background-position: center center;\n background-size: 50% 50%;\n}\n\n.custom-checkbox .custom-control-indicator {\n border-radius: 0.25rem;\n}\n\n.custom-checkbox .custom-control-input:checked ~ .custom-control-indicator {\n background-image: url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 8 8'%3E%3Cpath fill='%23fff' d='M6.564.75l-3.59 3.612-1.538-1.55L0 4.26 2.974 7.25 8 2.193z'/%3E%3C/svg%3E\");\n}\n\n.custom-checkbox .custom-control-input:indeterminate ~ .custom-control-indicator {\n background-color: #007bff;\n background-image: url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 4 4'%3E%3Cpath stroke='%23fff' d='M0 2h4'/%3E%3C/svg%3E\");\n}\n\n.custom-radio .custom-control-indicator {\n border-radius: 50%;\n}\n\n.custom-radio .custom-control-input:checked ~ .custom-control-indicator {\n background-image: url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='-4 -4 8 8'%3E%3Ccircle r='3' fill='%23fff'/%3E%3C/svg%3E\");\n}\n\n.custom-controls-stacked {\n display: -ms-flexbox;\n display: flex;\n -ms-flex-direction: column;\n flex-direction: column;\n}\n\n.custom-controls-stacked .custom-control {\n margin-bottom: 0.25rem;\n}\n\n.custom-controls-stacked .custom-control + .custom-control {\n margin-left: 0;\n}\n\n.custom-select {\n display: inline-block;\n max-width: 100%;\n height: calc(2.25rem + 2px);\n padding: 0.375rem 1.75rem 0.375rem 0.75rem;\n line-height: 1.25;\n color: #495057;\n vertical-align: middle;\n background: #fff url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 4 5'%3E%3Cpath fill='%23333' d='M2 0L0 2h4zm0 5L0 3h4z'/%3E%3C/svg%3E\") no-repeat right 0.75rem center;\n background-size: 8px 10px;\n border: 1px solid rgba(0, 0, 0, 0.15);\n border-radius: 0.25rem;\n -webkit-appearance: none;\n -moz-appearance: none;\n appearance: none;\n}\n\n.custom-select:focus {\n border-color: #80bdff;\n outline: none;\n}\n\n.custom-select:focus::-ms-value {\n color: #495057;\n background-color: #fff;\n}\n\n.custom-select:disabled {\n color: #868e96;\n background-color: #e9ecef;\n}\n\n.custom-select::-ms-expand {\n opacity: 0;\n}\n\n.custom-select-sm {\n height: calc(1.8125rem + 2px);\n padding-top: 0.375rem;\n padding-bottom: 0.375rem;\n font-size: 75%;\n}\n\n.custom-file {\n position: relative;\n display: inline-block;\n max-width: 100%;\n height: 2.5rem;\n margin-bottom: 0;\n}\n\n.custom-file-input {\n min-width: 14rem;\n max-width: 100%;\n height: 2.5rem;\n margin: 0;\n opacity: 0;\n}\n\n.custom-file-control {\n position: absolute;\n top: 0;\n right: 0;\n left: 0;\n z-index: 5;\n height: 2.5rem;\n padding: 0.5rem 1rem;\n line-height: 1.5;\n color: #495057;\n pointer-events: none;\n -webkit-user-select: none;\n -moz-user-select: none;\n -ms-user-select: none;\n user-select: none;\n background-color: #fff;\n border: 1px solid rgba(0, 0, 0, 0.15);\n border-radius: 0.25rem;\n}\n\n.custom-file-control:lang(en):empty::after {\n content: \"Choose file...\";\n}\n\n.custom-file-control::before {\n position: absolute;\n top: -1px;\n right: -1px;\n bottom: -1px;\n z-index: 6;\n display: block;\n height: 2.5rem;\n padding: 0.5rem 1rem;\n line-height: 1.5;\n color: #495057;\n background-color: #e9ecef;\n border: 1px solid rgba(0, 0, 0, 0.15);\n border-radius: 0 0.25rem 0.25rem 0;\n}\n\n.custom-file-control:lang(en)::before {\n content: \"Browse\";\n}\n\n.nav {\n display: -ms-flexbox;\n display: flex;\n -ms-flex-wrap: wrap;\n flex-wrap: wrap;\n padding-left: 0;\n margin-bottom: 0;\n list-style: none;\n}\n\n.nav-link {\n display: block;\n padding: 0.5rem 1rem;\n}\n\n.nav-link:focus, .nav-link:hover {\n text-decoration: none;\n}\n\n.nav-link.disabled {\n color: #868e96;\n}\n\n.nav-tabs {\n border-bottom: 1px solid #ddd;\n}\n\n.nav-tabs .nav-item {\n margin-bottom: -1px;\n}\n\n.nav-tabs .nav-link {\n border: 1px solid transparent;\n border-top-left-radius: 0.25rem;\n border-top-right-radius: 0.25rem;\n}\n\n.nav-tabs .nav-link:focus, .nav-tabs .nav-link:hover {\n border-color: #e9ecef #e9ecef #ddd;\n}\n\n.nav-tabs .nav-link.disabled {\n color: #868e96;\n background-color: transparent;\n border-color: transparent;\n}\n\n.nav-tabs .nav-link.active,\n.nav-tabs .nav-item.show .nav-link {\n color: #495057;\n background-color: #fff;\n border-color: #ddd #ddd #fff;\n}\n\n.nav-tabs .dropdown-menu {\n margin-top: -1px;\n border-top-left-radius: 0;\n border-top-right-radius: 0;\n}\n\n.nav-pills .nav-link {\n border-radius: 0.25rem;\n}\n\n.nav-pills .nav-link.active,\n.show > .nav-pills .nav-link {\n color: #fff;\n background-color: #007bff;\n}\n\n.nav-fill .nav-item {\n -ms-flex: 1 1 auto;\n flex: 1 1 auto;\n text-align: center;\n}\n\n.nav-justified .nav-item {\n -ms-flex-preferred-size: 0;\n flex-basis: 0;\n -ms-flex-positive: 1;\n flex-grow: 1;\n text-align: center;\n}\n\n.tab-content > .tab-pane {\n display: none;\n}\n\n.tab-content > .active {\n display: block;\n}\n\n.navbar {\n position: relative;\n display: -ms-flexbox;\n display: flex;\n -ms-flex-wrap: wrap;\n flex-wrap: wrap;\n -ms-flex-align: center;\n align-items: center;\n -ms-flex-pack: justify;\n justify-content: space-between;\n padding: 0.5rem 1rem;\n}\n\n.navbar > .container,\n.navbar > .container-fluid {\n display: -ms-flexbox;\n display: flex;\n -ms-flex-wrap: wrap;\n flex-wrap: wrap;\n -ms-flex-align: center;\n align-items: center;\n -ms-flex-pack: justify;\n justify-content: space-between;\n}\n\n.navbar-brand {\n display: inline-block;\n padding-top: 0.3125rem;\n padding-bottom: 0.3125rem;\n margin-right: 1rem;\n font-size: 1.25rem;\n line-height: inherit;\n white-space: nowrap;\n}\n\n.navbar-brand:focus, .navbar-brand:hover {\n text-decoration: none;\n}\n\n.navbar-nav {\n display: -ms-flexbox;\n display: flex;\n -ms-flex-direction: column;\n flex-direction: column;\n padding-left: 0;\n margin-bottom: 0;\n list-style: none;\n}\n\n.navbar-nav .nav-link {\n padding-right: 0;\n padding-left: 0;\n}\n\n.navbar-nav .dropdown-menu {\n position: static;\n float: none;\n}\n\n.navbar-text {\n display: inline-block;\n padding-top: 0.5rem;\n padding-bottom: 0.5rem;\n}\n\n.navbar-collapse {\n -ms-flex-preferred-size: 100%;\n flex-basis: 100%;\n -ms-flex-align: center;\n align-items: center;\n}\n\n.navbar-toggler {\n padding: 0.25rem 0.75rem;\n font-size: 1.25rem;\n line-height: 1;\n background: transparent;\n border: 1px solid transparent;\n border-radius: 0.25rem;\n}\n\n.navbar-toggler:focus, .navbar-toggler:hover {\n text-decoration: none;\n}\n\n.navbar-toggler-icon {\n display: inline-block;\n width: 1.5em;\n height: 1.5em;\n vertical-align: middle;\n content: \"\";\n background: no-repeat center center;\n background-size: 100% 100%;\n}\n\n@media (max-width: 575px) {\n .navbar-expand-sm > .container,\n .navbar-expand-sm > .container-fluid {\n padding-right: 0;\n padding-left: 0;\n }\n}\n\n@media (min-width: 576px) {\n .navbar-expand-sm {\n -ms-flex-direction: row;\n flex-direction: row;\n -ms-flex-wrap: nowrap;\n flex-wrap: nowrap;\n -ms-flex-pack: start;\n justify-content: flex-start;\n }\n .navbar-expand-sm .navbar-nav {\n -ms-flex-direction: row;\n flex-direction: row;\n }\n .navbar-expand-sm .navbar-nav .dropdown-menu {\n position: absolute;\n }\n .navbar-expand-sm .navbar-nav .dropdown-menu-right {\n right: 0;\n left: auto;\n }\n .navbar-expand-sm .navbar-nav .nav-link {\n padding-right: .5rem;\n padding-left: .5rem;\n }\n .navbar-expand-sm > .container,\n .navbar-expand-sm > .container-fluid {\n -ms-flex-wrap: nowrap;\n flex-wrap: nowrap;\n }\n .navbar-expand-sm .navbar-collapse {\n display: -ms-flexbox !important;\n display: flex !important;\n }\n .navbar-expand-sm .navbar-toggler {\n display: none;\n }\n}\n\n@media (max-width: 767px) {\n .navbar-expand-md > .container,\n .navbar-expand-md > .container-fluid {\n padding-right: 0;\n padding-left: 0;\n }\n}\n\n@media (min-width: 768px) {\n .navbar-expand-md {\n -ms-flex-direction: row;\n flex-direction: row;\n -ms-flex-wrap: nowrap;\n flex-wrap: nowrap;\n -ms-flex-pack: start;\n justify-content: flex-start;\n }\n .navbar-expand-md .navbar-nav {\n -ms-flex-direction: row;\n flex-direction: row;\n }\n .navbar-expand-md .navbar-nav .dropdown-menu {\n position: absolute;\n }\n .navbar-expand-md .navbar-nav .dropdown-menu-right {\n right: 0;\n left: auto;\n }\n .navbar-expand-md .navbar-nav .nav-link {\n padding-right: .5rem;\n padding-left: .5rem;\n }\n .navbar-expand-md > .container,\n .navbar-expand-md > .container-fluid {\n -ms-flex-wrap: nowrap;\n flex-wrap: nowrap;\n }\n .navbar-expand-md .navbar-collapse {\n display: -ms-flexbox !important;\n display: flex !important;\n }\n .navbar-expand-md .navbar-toggler {\n display: none;\n }\n}\n\n@media (max-width: 991px) {\n .navbar-expand-lg > .container,\n .navbar-expand-lg > .container-fluid {\n padding-right: 0;\n padding-left: 0;\n }\n}\n\n@media (min-width: 992px) {\n .navbar-expand-lg {\n -ms-flex-direction: row;\n flex-direction: row;\n -ms-flex-wrap: nowrap;\n flex-wrap: nowrap;\n -ms-flex-pack: start;\n justify-content: flex-start;\n }\n .navbar-expand-lg .navbar-nav {\n -ms-flex-direction: row;\n flex-direction: row;\n }\n .navbar-expand-lg .navbar-nav .dropdown-menu {\n position: absolute;\n }\n .navbar-expand-lg .navbar-nav .dropdown-menu-right {\n right: 0;\n left: auto;\n }\n .navbar-expand-lg .navbar-nav .nav-link {\n padding-right: .5rem;\n padding-left: .5rem;\n }\n .navbar-expand-lg > .container,\n .navbar-expand-lg > .container-fluid {\n -ms-flex-wrap: nowrap;\n flex-wrap: nowrap;\n }\n .navbar-expand-lg .navbar-collapse {\n display: -ms-flexbox !important;\n display: flex !important;\n }\n .navbar-expand-lg .navbar-toggler {\n display: none;\n }\n}\n\n@media (max-width: 1199px) {\n .navbar-expand-xl > .container,\n .navbar-expand-xl > .container-fluid {\n padding-right: 0;\n padding-left: 0;\n }\n}\n\n@media (min-width: 1200px) {\n .navbar-expand-xl {\n -ms-flex-direction: row;\n flex-direction: row;\n -ms-flex-wrap: nowrap;\n flex-wrap: nowrap;\n -ms-flex-pack: start;\n justify-content: flex-start;\n }\n .navbar-expand-xl .navbar-nav {\n -ms-flex-direction: row;\n flex-direction: row;\n }\n .navbar-expand-xl .navbar-nav .dropdown-menu {\n position: absolute;\n }\n .navbar-expand-xl .navbar-nav .dropdown-menu-right {\n right: 0;\n left: auto;\n }\n .navbar-expand-xl .navbar-nav .nav-link {\n padding-right: .5rem;\n padding-left: .5rem;\n }\n .navbar-expand-xl > .container,\n .navbar-expand-xl > .container-fluid {\n -ms-flex-wrap: nowrap;\n flex-wrap: nowrap;\n }\n .navbar-expand-xl .navbar-collapse {\n display: -ms-flexbox !important;\n display: flex !important;\n }\n .navbar-expand-xl .navbar-toggler {\n display: none;\n }\n}\n\n.navbar-expand {\n -ms-flex-direction: row;\n flex-direction: row;\n -ms-flex-wrap: nowrap;\n flex-wrap: nowrap;\n -ms-flex-pack: start;\n justify-content: flex-start;\n}\n\n.navbar-expand > .container,\n.navbar-expand > .container-fluid {\n padding-right: 0;\n padding-left: 0;\n}\n\n.navbar-expand .navbar-nav {\n -ms-flex-direction: row;\n flex-direction: row;\n}\n\n.navbar-expand .navbar-nav .dropdown-menu {\n position: absolute;\n}\n\n.navbar-expand .navbar-nav .dropdown-menu-right {\n right: 0;\n left: auto;\n}\n\n.navbar-expand .navbar-nav .nav-link {\n padding-right: .5rem;\n padding-left: .5rem;\n}\n\n.navbar-expand > .container,\n.navbar-expand > .container-fluid {\n -ms-flex-wrap: nowrap;\n flex-wrap: nowrap;\n}\n\n.navbar-expand .navbar-collapse {\n display: -ms-flexbox !important;\n display: flex !important;\n}\n\n.navbar-expand .navbar-toggler {\n display: none;\n}\n\n.navbar-light .navbar-brand {\n color: rgba(0, 0, 0, 0.9);\n}\n\n.navbar-light .navbar-brand:focus, .navbar-light .navbar-brand:hover {\n color: rgba(0, 0, 0, 0.9);\n}\n\n.navbar-light .navbar-nav .nav-link {\n color: rgba(0, 0, 0, 0.5);\n}\n\n.navbar-light .navbar-nav .nav-link:focus, .navbar-light .navbar-nav .nav-link:hover {\n color: rgba(0, 0, 0, 0.7);\n}\n\n.navbar-light .navbar-nav .nav-link.disabled {\n color: rgba(0, 0, 0, 0.3);\n}\n\n.navbar-light .navbar-nav .show > .nav-link,\n.navbar-light .navbar-nav .active > .nav-link,\n.navbar-light .navbar-nav .nav-link.show,\n.navbar-light .navbar-nav .nav-link.active {\n color: rgba(0, 0, 0, 0.9);\n}\n\n.navbar-light .navbar-toggler {\n color: rgba(0, 0, 0, 0.5);\n border-color: rgba(0, 0, 0, 0.1);\n}\n\n.navbar-light .navbar-toggler-icon {\n background-image: url(\"data:image/svg+xml;charset=utf8,%3Csvg viewBox='0 0 30 30' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath stroke='rgba(0, 0, 0, 0.5)' stroke-width='2' stroke-linecap='round' stroke-miterlimit='10' d='M4 7h22M4 15h22M4 23h22'/%3E%3C/svg%3E\");\n}\n\n.navbar-light .navbar-text {\n color: rgba(0, 0, 0, 0.5);\n}\n\n.navbar-dark .navbar-brand {\n color: white;\n}\n\n.navbar-dark .navbar-brand:focus, .navbar-dark .navbar-brand:hover {\n color: white;\n}\n\n.navbar-dark .navbar-nav .nav-link {\n color: rgba(255, 255, 255, 0.5);\n}\n\n.navbar-dark .navbar-nav .nav-link:focus, .navbar-dark .navbar-nav .nav-link:hover {\n color: rgba(255, 255, 255, 0.75);\n}\n\n.navbar-dark .navbar-nav .nav-link.disabled {\n color: rgba(255, 255, 255, 0.25);\n}\n\n.navbar-dark .navbar-nav .show > .nav-link,\n.navbar-dark .navbar-nav .active > .nav-link,\n.navbar-dark .navbar-nav .nav-link.show,\n.navbar-dark .navbar-nav .nav-link.active {\n color: white;\n}\n\n.navbar-dark .navbar-toggler {\n color: rgba(255, 255, 255, 0.5);\n border-color: rgba(255, 255, 255, 0.1);\n}\n\n.navbar-dark .navbar-toggler-icon {\n background-image: url(\"data:image/svg+xml;charset=utf8,%3Csvg viewBox='0 0 30 30' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath stroke='rgba(255, 255, 255, 0.5)' stroke-width='2' stroke-linecap='round' stroke-miterlimit='10' d='M4 7h22M4 15h22M4 23h22'/%3E%3C/svg%3E\");\n}\n\n.navbar-dark .navbar-text {\n color: rgba(255, 255, 255, 0.5);\n}\n\n.card {\n position: relative;\n display: -ms-flexbox;\n display: flex;\n -ms-flex-direction: column;\n flex-direction: column;\n min-width: 0;\n word-wrap: break-word;\n background-color: #fff;\n background-clip: border-box;\n border: 1px solid rgba(0, 0, 0, 0.125);\n border-radius: 0.25rem;\n}\n\n.card-body {\n -ms-flex: 1 1 auto;\n flex: 1 1 auto;\n padding: 1.25rem;\n}\n\n.card-title {\n margin-bottom: 0.75rem;\n}\n\n.card-subtitle {\n margin-top: -0.375rem;\n margin-bottom: 0;\n}\n\n.card-text:last-child {\n margin-bottom: 0;\n}\n\n.card-link:hover {\n text-decoration: none;\n}\n\n.card-link + .card-link {\n margin-left: 1.25rem;\n}\n\n.card > .list-group:first-child .list-group-item:first-child {\n border-top-left-radius: 0.25rem;\n border-top-right-radius: 0.25rem;\n}\n\n.card > .list-group:last-child .list-group-item:last-child {\n border-bottom-right-radius: 0.25rem;\n border-bottom-left-radius: 0.25rem;\n}\n\n.card-header {\n padding: 0.75rem 1.25rem;\n margin-bottom: 0;\n background-color: rgba(0, 0, 0, 0.03);\n border-bottom: 1px solid rgba(0, 0, 0, 0.125);\n}\n\n.card-header:first-child {\n border-radius: calc(0.25rem - 1px) calc(0.25rem - 1px) 0 0;\n}\n\n.card-footer {\n padding: 0.75rem 1.25rem;\n background-color: rgba(0, 0, 0, 0.03);\n border-top: 1px solid rgba(0, 0, 0, 0.125);\n}\n\n.card-footer:last-child {\n border-radius: 0 0 calc(0.25rem - 1px) calc(0.25rem - 1px);\n}\n\n.card-header-tabs {\n margin-right: -0.625rem;\n margin-bottom: -0.75rem;\n margin-left: -0.625rem;\n border-bottom: 0;\n}\n\n.card-header-pills {\n margin-right: -0.625rem;\n margin-left: -0.625rem;\n}\n\n.card-img-overlay {\n position: absolute;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n padding: 1.25rem;\n}\n\n.card-img {\n width: 100%;\n border-radius: calc(0.25rem - 1px);\n}\n\n.card-img-top {\n width: 100%;\n border-top-left-radius: calc(0.25rem - 1px);\n border-top-right-radius: calc(0.25rem - 1px);\n}\n\n.card-img-bottom {\n width: 100%;\n border-bottom-right-radius: calc(0.25rem - 1px);\n border-bottom-left-radius: calc(0.25rem - 1px);\n}\n\n@media (min-width: 576px) {\n .card-deck {\n display: -ms-flexbox;\n display: flex;\n -ms-flex-flow: row wrap;\n flex-flow: row wrap;\n margin-right: -15px;\n margin-left: -15px;\n }\n .card-deck .card {\n display: -ms-flexbox;\n display: flex;\n -ms-flex: 1 0 0%;\n flex: 1 0 0%;\n -ms-flex-direction: column;\n flex-direction: column;\n margin-right: 15px;\n margin-left: 15px;\n }\n}\n\n@media (min-width: 576px) {\n .card-group {\n display: -ms-flexbox;\n display: flex;\n -ms-flex-flow: row wrap;\n flex-flow: row wrap;\n }\n .card-group .card {\n -ms-flex: 1 0 0%;\n flex: 1 0 0%;\n }\n .card-group .card + .card {\n margin-left: 0;\n border-left: 0;\n }\n .card-group .card:first-child {\n border-top-right-radius: 0;\n border-bottom-right-radius: 0;\n }\n .card-group .card:first-child .card-img-top {\n border-top-right-radius: 0;\n }\n .card-group .card:first-child .card-img-bottom {\n border-bottom-right-radius: 0;\n }\n .card-group .card:last-child {\n border-top-left-radius: 0;\n border-bottom-left-radius: 0;\n }\n .card-group .card:last-child .card-img-top {\n border-top-left-radius: 0;\n }\n .card-group .card:last-child .card-img-bottom {\n border-bottom-left-radius: 0;\n }\n .card-group .card:not(:first-child):not(:last-child) {\n border-radius: 0;\n }\n .card-group .card:not(:first-child):not(:last-child) .card-img-top,\n .card-group .card:not(:first-child):not(:last-child) .card-img-bottom {\n border-radius: 0;\n }\n}\n\n.card-columns .card {\n margin-bottom: 0.75rem;\n}\n\n@media (min-width: 576px) {\n .card-columns {\n -webkit-column-count: 3;\n column-count: 3;\n -webkit-column-gap: 1.25rem;\n column-gap: 1.25rem;\n }\n .card-columns .card {\n display: inline-block;\n width: 100%;\n }\n}\n\n.breadcrumb {\n padding: 0.75rem 1rem;\n margin-bottom: 1rem;\n list-style: none;\n background-color: #e9ecef;\n border-radius: 0.25rem;\n}\n\n.breadcrumb::after {\n display: block;\n clear: both;\n content: \"\";\n}\n\n.breadcrumb-item {\n float: left;\n}\n\n.breadcrumb-item + .breadcrumb-item::before {\n display: inline-block;\n padding-right: 0.5rem;\n padding-left: 0.5rem;\n color: #868e96;\n content: \"/\";\n}\n\n.breadcrumb-item + .breadcrumb-item:hover::before {\n text-decoration: underline;\n}\n\n.breadcrumb-item + .breadcrumb-item:hover::before {\n text-decoration: none;\n}\n\n.breadcrumb-item.active {\n color: #868e96;\n}\n\n.pagination {\n display: -ms-flexbox;\n display: flex;\n padding-left: 0;\n list-style: none;\n border-radius: 0.25rem;\n}\n\n.page-item:first-child .page-link {\n margin-left: 0;\n border-top-left-radius: 0.25rem;\n border-bottom-left-radius: 0.25rem;\n}\n\n.page-item:last-child .page-link {\n border-top-right-radius: 0.25rem;\n border-bottom-right-radius: 0.25rem;\n}\n\n.page-item.active .page-link {\n z-index: 2;\n color: #fff;\n background-color: #007bff;\n border-color: #007bff;\n}\n\n.page-item.disabled .page-link {\n color: #868e96;\n pointer-events: none;\n background-color: #fff;\n border-color: #ddd;\n}\n\n.page-link {\n position: relative;\n display: block;\n padding: 0.5rem 0.75rem;\n margin-left: -1px;\n line-height: 1.25;\n color: #007bff;\n background-color: #fff;\n border: 1px solid #ddd;\n}\n\n.page-link:focus, .page-link:hover {\n color: #0056b3;\n text-decoration: none;\n background-color: #e9ecef;\n border-color: #ddd;\n}\n\n.pagination-lg .page-link {\n padding: 0.75rem 1.5rem;\n font-size: 1.25rem;\n line-height: 1.5;\n}\n\n.pagination-lg .page-item:first-child .page-link {\n border-top-left-radius: 0.3rem;\n border-bottom-left-radius: 0.3rem;\n}\n\n.pagination-lg .page-item:last-child .page-link {\n border-top-right-radius: 0.3rem;\n border-bottom-right-radius: 0.3rem;\n}\n\n.pagination-sm .page-link {\n padding: 0.25rem 0.5rem;\n font-size: 0.875rem;\n line-height: 1.5;\n}\n\n.pagination-sm .page-item:first-child .page-link {\n border-top-left-radius: 0.2rem;\n border-bottom-left-radius: 0.2rem;\n}\n\n.pagination-sm .page-item:last-child .page-link {\n border-top-right-radius: 0.2rem;\n border-bottom-right-radius: 0.2rem;\n}\n\n.badge {\n display: inline-block;\n padding: 0.25em 0.4em;\n font-size: 75%;\n font-weight: bold;\n line-height: 1;\n color: #fff;\n text-align: center;\n white-space: nowrap;\n vertical-align: baseline;\n border-radius: 0.25rem;\n}\n\n.badge:empty {\n display: none;\n}\n\n.btn .badge {\n position: relative;\n top: -1px;\n}\n\n.badge-pill {\n padding-right: 0.6em;\n padding-left: 0.6em;\n border-radius: 10rem;\n}\n\n.badge-primary {\n color: #fff;\n background-color: #007bff;\n}\n\n.badge-primary[href]:focus, .badge-primary[href]:hover {\n color: #fff;\n text-decoration: none;\n background-color: #0062cc;\n}\n\n.badge-secondary {\n color: #fff;\n background-color: #868e96;\n}\n\n.badge-secondary[href]:focus, .badge-secondary[href]:hover {\n color: #fff;\n text-decoration: none;\n background-color: #6c757d;\n}\n\n.badge-success {\n color: #fff;\n background-color: #28a745;\n}\n\n.badge-success[href]:focus, .badge-success[href]:hover {\n color: #fff;\n text-decoration: none;\n background-color: #1e7e34;\n}\n\n.badge-info {\n color: #fff;\n background-color: #17a2b8;\n}\n\n.badge-info[href]:focus, .badge-info[href]:hover {\n color: #fff;\n text-decoration: none;\n background-color: #117a8b;\n}\n\n.badge-warning {\n color: #111;\n background-color: #ffc107;\n}\n\n.badge-warning[href]:focus, .badge-warning[href]:hover {\n color: #111;\n text-decoration: none;\n background-color: #d39e00;\n}\n\n.badge-danger {\n color: #fff;\n background-color: #dc3545;\n}\n\n.badge-danger[href]:focus, .badge-danger[href]:hover {\n color: #fff;\n text-decoration: none;\n background-color: #bd2130;\n}\n\n.badge-light {\n color: #111;\n background-color: #f8f9fa;\n}\n\n.badge-light[href]:focus, .badge-light[href]:hover {\n color: #111;\n text-decoration: none;\n background-color: #dae0e5;\n}\n\n.badge-dark {\n color: #fff;\n background-color: #343a40;\n}\n\n.badge-dark[href]:focus, .badge-dark[href]:hover {\n color: #fff;\n text-decoration: none;\n background-color: #1d2124;\n}\n\n.jumbotron {\n padding: 2rem 1rem;\n margin-bottom: 2rem;\n background-color: #e9ecef;\n border-radius: 0.3rem;\n}\n\n@media (min-width: 576px) {\n .jumbotron {\n padding: 4rem 2rem;\n }\n}\n\n.jumbotron-fluid {\n padding-right: 0;\n padding-left: 0;\n border-radius: 0;\n}\n\n.alert {\n padding: 0.75rem 1.25rem;\n margin-bottom: 1rem;\n border: 1px solid transparent;\n border-radius: 0.25rem;\n}\n\n.alert-heading {\n color: inherit;\n}\n\n.alert-link {\n font-weight: bold;\n}\n\n.alert-dismissible .close {\n position: relative;\n top: -0.75rem;\n right: -1.25rem;\n padding: 0.75rem 1.25rem;\n color: inherit;\n}\n\n.alert-primary {\n color: #004085;\n background-color: #cce5ff;\n border-color: #b8daff;\n}\n\n.alert-primary hr {\n border-top-color: #9fcdff;\n}\n\n.alert-primary .alert-link {\n color: #002752;\n}\n\n.alert-secondary {\n color: #464a4e;\n background-color: #e7e8ea;\n border-color: #dddfe2;\n}\n\n.alert-secondary hr {\n border-top-color: #cfd2d6;\n}\n\n.alert-secondary .alert-link {\n color: #2e3133;\n}\n\n.alert-success {\n color: #155724;\n background-color: #d4edda;\n border-color: #c3e6cb;\n}\n\n.alert-success hr {\n border-top-color: #b1dfbb;\n}\n\n.alert-success .alert-link {\n color: #0b2e13;\n}\n\n.alert-info {\n color: #0c5460;\n background-color: #d1ecf1;\n border-color: #bee5eb;\n}\n\n.alert-info hr {\n border-top-color: #abdde5;\n}\n\n.alert-info .alert-link {\n color: #062c33;\n}\n\n.alert-warning {\n color: #856404;\n background-color: #fff3cd;\n border-color: #ffeeba;\n}\n\n.alert-warning hr {\n border-top-color: #ffe8a1;\n}\n\n.alert-warning .alert-link {\n color: #533f03;\n}\n\n.alert-danger {\n color: #721c24;\n background-color: #f8d7da;\n border-color: #f5c6cb;\n}\n\n.alert-danger hr {\n border-top-color: #f1b0b7;\n}\n\n.alert-danger .alert-link {\n color: #491217;\n}\n\n.alert-light {\n color: #818182;\n background-color: #fefefe;\n border-color: #fdfdfe;\n}\n\n.alert-light hr {\n border-top-color: #ececf6;\n}\n\n.alert-light .alert-link {\n color: #686868;\n}\n\n.alert-dark {\n color: #1b1e21;\n background-color: #d6d8d9;\n border-color: #c6c8ca;\n}\n\n.alert-dark hr {\n border-top-color: #b9bbbe;\n}\n\n.alert-dark .alert-link {\n color: #040505;\n}\n\n@-webkit-keyframes progress-bar-stripes {\n from {\n background-position: 1rem 0;\n }\n to {\n background-position: 0 0;\n }\n}\n\n@keyframes progress-bar-stripes {\n from {\n background-position: 1rem 0;\n }\n to {\n background-position: 0 0;\n }\n}\n\n.progress {\n display: -ms-flexbox;\n display: flex;\n overflow: hidden;\n font-size: 0.75rem;\n line-height: 1rem;\n text-align: center;\n background-color: #e9ecef;\n border-radius: 0.25rem;\n}\n\n.progress-bar {\n height: 1rem;\n line-height: 1rem;\n color: #fff;\n background-color: #007bff;\n transition: width 0.6s ease;\n}\n\n.progress-bar-striped {\n background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-size: 1rem 1rem;\n}\n\n.progress-bar-animated {\n -webkit-animation: progress-bar-stripes 1s linear infinite;\n animation: progress-bar-stripes 1s linear infinite;\n}\n\n.media {\n display: -ms-flexbox;\n display: flex;\n -ms-flex-align: start;\n align-items: flex-start;\n}\n\n.media-body {\n -ms-flex: 1;\n flex: 1;\n}\n\n.list-group {\n display: -ms-flexbox;\n display: flex;\n -ms-flex-direction: column;\n flex-direction: column;\n padding-left: 0;\n margin-bottom: 0;\n}\n\n.list-group-item-action {\n width: 100%;\n color: #495057;\n text-align: inherit;\n}\n\n.list-group-item-action:focus, .list-group-item-action:hover {\n color: #495057;\n text-decoration: none;\n background-color: #f8f9fa;\n}\n\n.list-group-item-action:active {\n color: #212529;\n background-color: #e9ecef;\n}\n\n.list-group-item {\n position: relative;\n display: block;\n padding: 0.75rem 1.25rem;\n margin-bottom: -1px;\n background-color: #fff;\n border: 1px solid rgba(0, 0, 0, 0.125);\n}\n\n.list-group-item:first-child {\n border-top-left-radius: 0.25rem;\n border-top-right-radius: 0.25rem;\n}\n\n.list-group-item:last-child {\n margin-bottom: 0;\n border-bottom-right-radius: 0.25rem;\n border-bottom-left-radius: 0.25rem;\n}\n\n.list-group-item:focus, .list-group-item:hover {\n text-decoration: none;\n}\n\n.list-group-item.disabled, .list-group-item:disabled {\n color: #868e96;\n background-color: #fff;\n}\n\n.list-group-item.active {\n z-index: 2;\n color: #fff;\n background-color: #007bff;\n border-color: #007bff;\n}\n\n.list-group-flush .list-group-item {\n border-right: 0;\n border-left: 0;\n border-radius: 0;\n}\n\n.list-group-flush:first-child .list-group-item:first-child {\n border-top: 0;\n}\n\n.list-group-flush:last-child .list-group-item:last-child {\n border-bottom: 0;\n}\n\n.list-group-item-primary {\n color: #004085;\n background-color: #b8daff;\n}\n\na.list-group-item-primary,\nbutton.list-group-item-primary {\n color: #004085;\n}\n\na.list-group-item-primary:focus, a.list-group-item-primary:hover,\nbutton.list-group-item-primary:focus,\nbutton.list-group-item-primary:hover {\n color: #004085;\n background-color: #9fcdff;\n}\n\na.list-group-item-primary.active,\nbutton.list-group-item-primary.active {\n color: #fff;\n background-color: #004085;\n border-color: #004085;\n}\n\n.list-group-item-secondary {\n color: #464a4e;\n background-color: #dddfe2;\n}\n\na.list-group-item-secondary,\nbutton.list-group-item-secondary {\n color: #464a4e;\n}\n\na.list-group-item-secondary:focus, a.list-group-item-secondary:hover,\nbutton.list-group-item-secondary:focus,\nbutton.list-group-item-secondary:hover {\n color: #464a4e;\n background-color: #cfd2d6;\n}\n\na.list-group-item-secondary.active,\nbutton.list-group-item-secondary.active {\n color: #fff;\n background-color: #464a4e;\n border-color: #464a4e;\n}\n\n.list-group-item-success {\n color: #155724;\n background-color: #c3e6cb;\n}\n\na.list-group-item-success,\nbutton.list-group-item-success {\n color: #155724;\n}\n\na.list-group-item-success:focus, a.list-group-item-success:hover,\nbutton.list-group-item-success:focus,\nbutton.list-group-item-success:hover {\n color: #155724;\n background-color: #b1dfbb;\n}\n\na.list-group-item-success.active,\nbutton.list-group-item-success.active {\n color: #fff;\n background-color: #155724;\n border-color: #155724;\n}\n\n.list-group-item-info {\n color: #0c5460;\n background-color: #bee5eb;\n}\n\na.list-group-item-info,\nbutton.list-group-item-info {\n color: #0c5460;\n}\n\na.list-group-item-info:focus, a.list-group-item-info:hover,\nbutton.list-group-item-info:focus,\nbutton.list-group-item-info:hover {\n color: #0c5460;\n background-color: #abdde5;\n}\n\na.list-group-item-info.active,\nbutton.list-group-item-info.active {\n color: #fff;\n background-color: #0c5460;\n border-color: #0c5460;\n}\n\n.list-group-item-warning {\n color: #856404;\n background-color: #ffeeba;\n}\n\na.list-group-item-warning,\nbutton.list-group-item-warning {\n color: #856404;\n}\n\na.list-group-item-warning:focus, a.list-group-item-warning:hover,\nbutton.list-group-item-warning:focus,\nbutton.list-group-item-warning:hover {\n color: #856404;\n background-color: #ffe8a1;\n}\n\na.list-group-item-warning.active,\nbutton.list-group-item-warning.active {\n color: #fff;\n background-color: #856404;\n border-color: #856404;\n}\n\n.list-group-item-danger {\n color: #721c24;\n background-color: #f5c6cb;\n}\n\na.list-group-item-danger,\nbutton.list-group-item-danger {\n color: #721c24;\n}\n\na.list-group-item-danger:focus, a.list-group-item-danger:hover,\nbutton.list-group-item-danger:focus,\nbutton.list-group-item-danger:hover {\n color: #721c24;\n background-color: #f1b0b7;\n}\n\na.list-group-item-danger.active,\nbutton.list-group-item-danger.active {\n color: #fff;\n background-color: #721c24;\n border-color: #721c24;\n}\n\n.list-group-item-light {\n color: #818182;\n background-color: #fdfdfe;\n}\n\na.list-group-item-light,\nbutton.list-group-item-light {\n color: #818182;\n}\n\na.list-group-item-light:focus, a.list-group-item-light:hover,\nbutton.list-group-item-light:focus,\nbutton.list-group-item-light:hover {\n color: #818182;\n background-color: #ececf6;\n}\n\na.list-group-item-light.active,\nbutton.list-group-item-light.active {\n color: #fff;\n background-color: #818182;\n border-color: #818182;\n}\n\n.list-group-item-dark {\n color: #1b1e21;\n background-color: #c6c8ca;\n}\n\na.list-group-item-dark,\nbutton.list-group-item-dark {\n color: #1b1e21;\n}\n\na.list-group-item-dark:focus, a.list-group-item-dark:hover,\nbutton.list-group-item-dark:focus,\nbutton.list-group-item-dark:hover {\n color: #1b1e21;\n background-color: #b9bbbe;\n}\n\na.list-group-item-dark.active,\nbutton.list-group-item-dark.active {\n color: #fff;\n background-color: #1b1e21;\n border-color: #1b1e21;\n}\n\n.close {\n float: right;\n font-size: 1.5rem;\n font-weight: bold;\n line-height: 1;\n color: #000;\n text-shadow: 0 1px 0 #fff;\n opacity: .5;\n}\n\n.close:focus, .close:hover {\n color: #000;\n text-decoration: none;\n opacity: .75;\n}\n\nbutton.close {\n padding: 0;\n background: transparent;\n border: 0;\n -webkit-appearance: none;\n}\n\n.modal-open {\n overflow: hidden;\n}\n\n.modal {\n position: fixed;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: 1050;\n display: none;\n overflow: hidden;\n outline: 0;\n}\n\n.modal.fade .modal-dialog {\n transition: -webkit-transform 0.3s ease-out;\n transition: transform 0.3s ease-out;\n transition: transform 0.3s ease-out, -webkit-transform 0.3s ease-out;\n -webkit-transform: translate(0, -25%);\n transform: translate(0, -25%);\n}\n\n.modal.show .modal-dialog {\n -webkit-transform: translate(0, 0);\n transform: translate(0, 0);\n}\n\n.modal-open .modal {\n overflow-x: hidden;\n overflow-y: auto;\n}\n\n.modal-dialog {\n position: relative;\n width: auto;\n margin: 10px;\n}\n\n.modal-content {\n position: relative;\n display: -ms-flexbox;\n display: flex;\n -ms-flex-direction: column;\n flex-direction: column;\n background-color: #fff;\n background-clip: padding-box;\n border: 1px solid rgba(0, 0, 0, 0.2);\n border-radius: 0.3rem;\n outline: 0;\n}\n\n.modal-backdrop {\n position: fixed;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: 1040;\n background-color: #000;\n}\n\n.modal-backdrop.fade {\n opacity: 0;\n}\n\n.modal-backdrop.show {\n opacity: 0.5;\n}\n\n.modal-header {\n display: -ms-flexbox;\n display: flex;\n -ms-flex-align: center;\n align-items: center;\n -ms-flex-pack: justify;\n justify-content: space-between;\n padding: 15px;\n border-bottom: 1px solid #e9ecef;\n}\n\n.modal-title {\n margin-bottom: 0;\n line-height: 1.5;\n}\n\n.modal-body {\n position: relative;\n -ms-flex: 1 1 auto;\n flex: 1 1 auto;\n padding: 15px;\n}\n\n.modal-footer {\n display: -ms-flexbox;\n display: flex;\n -ms-flex-align: center;\n align-items: center;\n -ms-flex-pack: end;\n justify-content: flex-end;\n padding: 15px;\n border-top: 1px solid #e9ecef;\n}\n\n.modal-footer > :not(:first-child) {\n margin-left: .25rem;\n}\n\n.modal-footer > :not(:last-child) {\n margin-right: .25rem;\n}\n\n.modal-scrollbar-measure {\n position: absolute;\n top: -9999px;\n width: 50px;\n height: 50px;\n overflow: scroll;\n}\n\n@media (min-width: 576px) {\n .modal-dialog {\n max-width: 500px;\n margin: 30px auto;\n }\n .modal-sm {\n max-width: 300px;\n }\n}\n\n@media (min-width: 992px) {\n .modal-lg {\n max-width: 800px;\n }\n}\n\n.tooltip {\n position: absolute;\n z-index: 1070;\n display: block;\n margin: 0;\n font-family: -apple-system, BlinkMacSystemFont, \"Segoe UI\", Roboto, \"Helvetica Neue\", Arial, sans-serif;\n font-style: normal;\n font-weight: normal;\n line-height: 1.5;\n text-align: left;\n text-align: start;\n text-decoration: none;\n text-shadow: none;\n text-transform: none;\n letter-spacing: normal;\n word-break: normal;\n word-spacing: normal;\n white-space: normal;\n line-break: auto;\n font-size: 0.875rem;\n word-wrap: break-word;\n opacity: 0;\n}\n\n.tooltip.show {\n opacity: 0.9;\n}\n\n.tooltip .arrow {\n position: absolute;\n display: block;\n width: 5px;\n height: 5px;\n}\n\n.tooltip.bs-tooltip-top, .tooltip.bs-tooltip-auto[x-placement^=\"top\"] {\n padding: 5px 0;\n}\n\n.tooltip.bs-tooltip-top .arrow, .tooltip.bs-tooltip-auto[x-placement^=\"top\"] .arrow {\n bottom: 0;\n}\n\n.tooltip.bs-tooltip-top .arrow::before, .tooltip.bs-tooltip-auto[x-placement^=\"top\"] .arrow::before {\n margin-left: -3px;\n content: \"\";\n border-width: 5px 5px 0;\n border-top-color: #000;\n}\n\n.tooltip.bs-tooltip-right, .tooltip.bs-tooltip-auto[x-placement^=\"right\"] {\n padding: 0 5px;\n}\n\n.tooltip.bs-tooltip-right .arrow, .tooltip.bs-tooltip-auto[x-placement^=\"right\"] .arrow {\n left: 0;\n}\n\n.tooltip.bs-tooltip-right .arrow::before, .tooltip.bs-tooltip-auto[x-placement^=\"right\"] .arrow::before {\n margin-top: -3px;\n content: \"\";\n border-width: 5px 5px 5px 0;\n border-right-color: #000;\n}\n\n.tooltip.bs-tooltip-bottom, .tooltip.bs-tooltip-auto[x-placement^=\"bottom\"] {\n padding: 5px 0;\n}\n\n.tooltip.bs-tooltip-bottom .arrow, .tooltip.bs-tooltip-auto[x-placement^=\"bottom\"] .arrow {\n top: 0;\n}\n\n.tooltip.bs-tooltip-bottom .arrow::before, .tooltip.bs-tooltip-auto[x-placement^=\"bottom\"] .arrow::before {\n margin-left: -3px;\n content: \"\";\n border-width: 0 5px 5px;\n border-bottom-color: #000;\n}\n\n.tooltip.bs-tooltip-left, .tooltip.bs-tooltip-auto[x-placement^=\"left\"] {\n padding: 0 5px;\n}\n\n.tooltip.bs-tooltip-left .arrow, .tooltip.bs-tooltip-auto[x-placement^=\"left\"] .arrow {\n right: 0;\n}\n\n.tooltip.bs-tooltip-left .arrow::before, .tooltip.bs-tooltip-auto[x-placement^=\"left\"] .arrow::before {\n right: 0;\n margin-top: -3px;\n content: \"\";\n border-width: 5px 0 5px 5px;\n border-left-color: #000;\n}\n\n.tooltip .arrow::before {\n position: absolute;\n border-color: transparent;\n border-style: solid;\n}\n\n.tooltip-inner {\n max-width: 200px;\n padding: 3px 8px;\n color: #fff;\n text-align: center;\n background-color: #000;\n border-radius: 0.25rem;\n}\n\n.popover {\n position: absolute;\n top: 0;\n left: 0;\n z-index: 1060;\n display: block;\n max-width: 276px;\n padding: 1px;\n font-family: -apple-system, BlinkMacSystemFont, \"Segoe UI\", Roboto, \"Helvetica Neue\", Arial, sans-serif;\n font-style: normal;\n font-weight: normal;\n line-height: 1.5;\n text-align: left;\n text-align: start;\n text-decoration: none;\n text-shadow: none;\n text-transform: none;\n letter-spacing: normal;\n word-break: normal;\n word-spacing: normal;\n white-space: normal;\n line-break: auto;\n font-size: 0.875rem;\n word-wrap: break-word;\n background-color: #fff;\n background-clip: padding-box;\n border: 1px solid rgba(0, 0, 0, 0.2);\n border-radius: 0.3rem;\n}\n\n.popover .arrow {\n position: absolute;\n display: block;\n width: 10px;\n height: 5px;\n}\n\n.popover .arrow::before,\n.popover .arrow::after {\n position: absolute;\n display: block;\n border-color: transparent;\n border-style: solid;\n}\n\n.popover .arrow::before {\n content: \"\";\n border-width: 11px;\n}\n\n.popover .arrow::after {\n content: \"\";\n border-width: 11px;\n}\n\n.popover.bs-popover-top, .popover.bs-popover-auto[x-placement^=\"top\"] {\n margin-bottom: 10px;\n}\n\n.popover.bs-popover-top .arrow, .popover.bs-popover-auto[x-placement^=\"top\"] .arrow {\n bottom: 0;\n}\n\n.popover.bs-popover-top .arrow::before, .popover.bs-popover-auto[x-placement^=\"top\"] .arrow::before,\n.popover.bs-popover-top .arrow::after, .popover.bs-popover-auto[x-placement^=\"top\"] .arrow::after {\n border-bottom-width: 0;\n}\n\n.popover.bs-popover-top .arrow::before, .popover.bs-popover-auto[x-placement^=\"top\"] .arrow::before {\n bottom: -11px;\n margin-left: -6px;\n border-top-color: rgba(0, 0, 0, 0.25);\n}\n\n.popover.bs-popover-top .arrow::after, .popover.bs-popover-auto[x-placement^=\"top\"] .arrow::after {\n bottom: -10px;\n margin-left: -6px;\n border-top-color: #fff;\n}\n\n.popover.bs-popover-right, .popover.bs-popover-auto[x-placement^=\"right\"] {\n margin-left: 10px;\n}\n\n.popover.bs-popover-right .arrow, .popover.bs-popover-auto[x-placement^=\"right\"] .arrow {\n left: 0;\n}\n\n.popover.bs-popover-right .arrow::before, .popover.bs-popover-auto[x-placement^=\"right\"] .arrow::before,\n.popover.bs-popover-right .arrow::after, .popover.bs-popover-auto[x-placement^=\"right\"] .arrow::after {\n margin-top: -8px;\n border-left-width: 0;\n}\n\n.popover.bs-popover-right .arrow::before, .popover.bs-popover-auto[x-placement^=\"right\"] .arrow::before {\n left: -11px;\n border-right-color: rgba(0, 0, 0, 0.25);\n}\n\n.popover.bs-popover-right .arrow::after, .popover.bs-popover-auto[x-placement^=\"right\"] .arrow::after {\n left: -10px;\n border-right-color: #fff;\n}\n\n.popover.bs-popover-bottom, .popover.bs-popover-auto[x-placement^=\"bottom\"] {\n margin-top: 10px;\n}\n\n.popover.bs-popover-bottom .arrow, .popover.bs-popover-auto[x-placement^=\"bottom\"] .arrow {\n top: 0;\n}\n\n.popover.bs-popover-bottom .arrow::before, .popover.bs-popover-auto[x-placement^=\"bottom\"] .arrow::before,\n.popover.bs-popover-bottom .arrow::after, .popover.bs-popover-auto[x-placement^=\"bottom\"] .arrow::after {\n margin-left: -7px;\n border-top-width: 0;\n}\n\n.popover.bs-popover-bottom .arrow::before, .popover.bs-popover-auto[x-placement^=\"bottom\"] .arrow::before {\n top: -11px;\n border-bottom-color: rgba(0, 0, 0, 0.25);\n}\n\n.popover.bs-popover-bottom .arrow::after, .popover.bs-popover-auto[x-placement^=\"bottom\"] .arrow::after {\n top: -10px;\n border-bottom-color: #fff;\n}\n\n.popover.bs-popover-bottom .popover-header::before, .popover.bs-popover-auto[x-placement^=\"bottom\"] .popover-header::before {\n position: absolute;\n top: 0;\n left: 50%;\n display: block;\n width: 20px;\n margin-left: -10px;\n content: \"\";\n border-bottom: 1px solid #f7f7f7;\n}\n\n.popover.bs-popover-left, .popover.bs-popover-auto[x-placement^=\"left\"] {\n margin-right: 10px;\n}\n\n.popover.bs-popover-left .arrow, .popover.bs-popover-auto[x-placement^=\"left\"] .arrow {\n right: 0;\n}\n\n.popover.bs-popover-left .arrow::before, .popover.bs-popover-auto[x-placement^=\"left\"] .arrow::before,\n.popover.bs-popover-left .arrow::after, .popover.bs-popover-auto[x-placement^=\"left\"] .arrow::after {\n margin-top: -8px;\n border-right-width: 0;\n}\n\n.popover.bs-popover-left .arrow::before, .popover.bs-popover-auto[x-placement^=\"left\"] .arrow::before {\n right: -11px;\n border-left-color: rgba(0, 0, 0, 0.25);\n}\n\n.popover.bs-popover-left .arrow::after, .popover.bs-popover-auto[x-placement^=\"left\"] .arrow::after {\n right: -10px;\n border-left-color: #fff;\n}\n\n.popover-header {\n padding: 8px 14px;\n margin-bottom: 0;\n font-size: 1rem;\n color: inherit;\n background-color: #f7f7f7;\n border-bottom: 1px solid #ebebeb;\n border-top-left-radius: calc(0.3rem - 1px);\n border-top-right-radius: calc(0.3rem - 1px);\n}\n\n.popover-header:empty {\n display: none;\n}\n\n.popover-body {\n padding: 9px 14px;\n color: #212529;\n}\n\n.carousel {\n position: relative;\n}\n\n.carousel-inner {\n position: relative;\n width: 100%;\n overflow: hidden;\n}\n\n.carousel-item {\n position: relative;\n display: none;\n -ms-flex-align: center;\n align-items: center;\n width: 100%;\n transition: -webkit-transform 0.6s ease;\n transition: transform 0.6s ease;\n transition: transform 0.6s ease, -webkit-transform 0.6s ease;\n -webkit-backface-visibility: hidden;\n backface-visibility: hidden;\n -webkit-perspective: 1000px;\n perspective: 1000px;\n}\n\n.carousel-item.active,\n.carousel-item-next,\n.carousel-item-prev {\n display: block;\n}\n\n.carousel-item-next,\n.carousel-item-prev {\n position: absolute;\n top: 0;\n}\n\n.carousel-item-next.carousel-item-left,\n.carousel-item-prev.carousel-item-right {\n -webkit-transform: translateX(0);\n transform: translateX(0);\n}\n\n@supports ((-webkit-transform-style: preserve-3d) or (transform-style: preserve-3d)) {\n .carousel-item-next.carousel-item-left,\n .carousel-item-prev.carousel-item-right {\n -webkit-transform: translate3d(0, 0, 0);\n transform: translate3d(0, 0, 0);\n }\n}\n\n.carousel-item-next,\n.active.carousel-item-right {\n -webkit-transform: translateX(100%);\n transform: translateX(100%);\n}\n\n@supports ((-webkit-transform-style: preserve-3d) or (transform-style: preserve-3d)) {\n .carousel-item-next,\n .active.carousel-item-right {\n -webkit-transform: translate3d(100%, 0, 0);\n transform: translate3d(100%, 0, 0);\n }\n}\n\n.carousel-item-prev,\n.active.carousel-item-left {\n -webkit-transform: translateX(-100%);\n transform: translateX(-100%);\n}\n\n@supports ((-webkit-transform-style: preserve-3d) or (transform-style: preserve-3d)) {\n .carousel-item-prev,\n .active.carousel-item-left {\n -webkit-transform: translate3d(-100%, 0, 0);\n transform: translate3d(-100%, 0, 0);\n }\n}\n\n.carousel-control-prev,\n.carousel-control-next {\n position: absolute;\n top: 0;\n bottom: 0;\n display: -ms-flexbox;\n display: flex;\n -ms-flex-align: center;\n align-items: center;\n -ms-flex-pack: center;\n justify-content: center;\n width: 15%;\n color: #fff;\n text-align: center;\n opacity: 0.5;\n}\n\n.carousel-control-prev:focus, .carousel-control-prev:hover,\n.carousel-control-next:focus,\n.carousel-control-next:hover {\n color: #fff;\n text-decoration: none;\n outline: 0;\n opacity: .9;\n}\n\n.carousel-control-prev {\n left: 0;\n}\n\n.carousel-control-next {\n right: 0;\n}\n\n.carousel-control-prev-icon,\n.carousel-control-next-icon {\n display: inline-block;\n width: 20px;\n height: 20px;\n background: transparent no-repeat center center;\n background-size: 100% 100%;\n}\n\n.carousel-control-prev-icon {\n background-image: url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' fill='%23fff' viewBox='0 0 8 8'%3E%3Cpath d='M4 0l-4 4 4 4 1.5-1.5-2.5-2.5 2.5-2.5-1.5-1.5z'/%3E%3C/svg%3E\");\n}\n\n.carousel-control-next-icon {\n background-image: url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' fill='%23fff' viewBox='0 0 8 8'%3E%3Cpath d='M1.5 0l-1.5 1.5 2.5 2.5-2.5 2.5 1.5 1.5 4-4-4-4z'/%3E%3C/svg%3E\");\n}\n\n.carousel-indicators {\n position: absolute;\n right: 0;\n bottom: 10px;\n left: 0;\n z-index: 15;\n display: -ms-flexbox;\n display: flex;\n -ms-flex-pack: center;\n justify-content: center;\n padding-left: 0;\n margin-right: 15%;\n margin-left: 15%;\n list-style: none;\n}\n\n.carousel-indicators li {\n position: relative;\n -ms-flex: 0 1 auto;\n flex: 0 1 auto;\n width: 30px;\n height: 3px;\n margin-right: 3px;\n margin-left: 3px;\n text-indent: -999px;\n background-color: rgba(255, 255, 255, 0.5);\n}\n\n.carousel-indicators li::before {\n position: absolute;\n top: -10px;\n left: 0;\n display: inline-block;\n width: 100%;\n height: 10px;\n content: \"\";\n}\n\n.carousel-indicators li::after {\n position: absolute;\n bottom: -10px;\n left: 0;\n display: inline-block;\n width: 100%;\n height: 10px;\n content: \"\";\n}\n\n.carousel-indicators .active {\n background-color: #fff;\n}\n\n.carousel-caption {\n position: absolute;\n right: 15%;\n bottom: 20px;\n left: 15%;\n z-index: 10;\n padding-top: 20px;\n padding-bottom: 20px;\n color: #fff;\n text-align: center;\n}\n\n.align-baseline {\n vertical-align: baseline !important;\n}\n\n.align-top {\n vertical-align: top !important;\n}\n\n.align-middle {\n vertical-align: middle !important;\n}\n\n.align-bottom {\n vertical-align: bottom !important;\n}\n\n.align-text-bottom {\n vertical-align: text-bottom !important;\n}\n\n.align-text-top {\n vertical-align: text-top !important;\n}\n\n.bg-primary {\n background-color: #007bff !important;\n}\n\na.bg-primary:focus, a.bg-primary:hover {\n background-color: #0062cc !important;\n}\n\n.bg-secondary {\n background-color: #868e96 !important;\n}\n\na.bg-secondary:focus, a.bg-secondary:hover {\n background-color: #6c757d !important;\n}\n\n.bg-success {\n background-color: #28a745 !important;\n}\n\na.bg-success:focus, a.bg-success:hover {\n background-color: #1e7e34 !important;\n}\n\n.bg-info {\n background-color: #17a2b8 !important;\n}\n\na.bg-info:focus, a.bg-info:hover {\n background-color: #117a8b !important;\n}\n\n.bg-warning {\n background-color: #ffc107 !important;\n}\n\na.bg-warning:focus, a.bg-warning:hover {\n background-color: #d39e00 !important;\n}\n\n.bg-danger {\n background-color: #dc3545 !important;\n}\n\na.bg-danger:focus, a.bg-danger:hover {\n background-color: #bd2130 !important;\n}\n\n.bg-light {\n background-color: #f8f9fa !important;\n}\n\na.bg-light:focus, a.bg-light:hover {\n background-color: #dae0e5 !important;\n}\n\n.bg-dark {\n background-color: #343a40 !important;\n}\n\na.bg-dark:focus, a.bg-dark:hover {\n background-color: #1d2124 !important;\n}\n\n.bg-white {\n background-color: #fff !important;\n}\n\n.bg-transparent {\n background-color: transparent !important;\n}\n\n.border {\n border: 1px solid #e9ecef !important;\n}\n\n.border-0 {\n border: 0 !important;\n}\n\n.border-top-0 {\n border-top: 0 !important;\n}\n\n.border-right-0 {\n border-right: 0 !important;\n}\n\n.border-bottom-0 {\n border-bottom: 0 !important;\n}\n\n.border-left-0 {\n border-left: 0 !important;\n}\n\n.border-primary {\n border-color: #007bff !important;\n}\n\n.border-secondary {\n border-color: #868e96 !important;\n}\n\n.border-success {\n border-color: #28a745 !important;\n}\n\n.border-info {\n border-color: #17a2b8 !important;\n}\n\n.border-warning {\n border-color: #ffc107 !important;\n}\n\n.border-danger {\n border-color: #dc3545 !important;\n}\n\n.border-light {\n border-color: #f8f9fa !important;\n}\n\n.border-dark {\n border-color: #343a40 !important;\n}\n\n.border-white {\n border-color: #fff !important;\n}\n\n.rounded {\n border-radius: 0.25rem !important;\n}\n\n.rounded-top {\n border-top-left-radius: 0.25rem !important;\n border-top-right-radius: 0.25rem !important;\n}\n\n.rounded-right {\n border-top-right-radius: 0.25rem !important;\n border-bottom-right-radius: 0.25rem !important;\n}\n\n.rounded-bottom {\n border-bottom-right-radius: 0.25rem !important;\n border-bottom-left-radius: 0.25rem !important;\n}\n\n.rounded-left {\n border-top-left-radius: 0.25rem !important;\n border-bottom-left-radius: 0.25rem !important;\n}\n\n.rounded-circle {\n border-radius: 50%;\n}\n\n.rounded-0 {\n border-radius: 0;\n}\n\n.clearfix::after {\n display: block;\n clear: both;\n content: \"\";\n}\n\n.d-none {\n display: none !important;\n}\n\n.d-inline {\n display: inline !important;\n}\n\n.d-inline-block {\n display: inline-block !important;\n}\n\n.d-block {\n display: block !important;\n}\n\n.d-table {\n display: table !important;\n}\n\n.d-table-cell {\n display: table-cell !important;\n}\n\n.d-flex {\n display: -ms-flexbox !important;\n display: flex !important;\n}\n\n.d-inline-flex {\n display: -ms-inline-flexbox !important;\n display: inline-flex !important;\n}\n\n@media (min-width: 576px) {\n .d-sm-none {\n display: none !important;\n }\n .d-sm-inline {\n display: inline !important;\n }\n .d-sm-inline-block {\n display: inline-block !important;\n }\n .d-sm-block {\n display: block !important;\n }\n .d-sm-table {\n display: table !important;\n }\n .d-sm-table-cell {\n display: table-cell !important;\n }\n .d-sm-flex {\n display: -ms-flexbox !important;\n display: flex !important;\n }\n .d-sm-inline-flex {\n display: -ms-inline-flexbox !important;\n display: inline-flex !important;\n }\n}\n\n@media (min-width: 768px) {\n .d-md-none {\n display: none !important;\n }\n .d-md-inline {\n display: inline !important;\n }\n .d-md-inline-block {\n display: inline-block !important;\n }\n .d-md-block {\n display: block !important;\n }\n .d-md-table {\n display: table !important;\n }\n .d-md-table-cell {\n display: table-cell !important;\n }\n .d-md-flex {\n display: -ms-flexbox !important;\n display: flex !important;\n }\n .d-md-inline-flex {\n display: -ms-inline-flexbox !important;\n display: inline-flex !important;\n }\n}\n\n@media (min-width: 992px) {\n .d-lg-none {\n display: none !important;\n }\n .d-lg-inline {\n display: inline !important;\n }\n .d-lg-inline-block {\n display: inline-block !important;\n }\n .d-lg-block {\n display: block !important;\n }\n .d-lg-table {\n display: table !important;\n }\n .d-lg-table-cell {\n display: table-cell !important;\n }\n .d-lg-flex {\n display: -ms-flexbox !important;\n display: flex !important;\n }\n .d-lg-inline-flex {\n display: -ms-inline-flexbox !important;\n display: inline-flex !important;\n }\n}\n\n@media (min-width: 1200px) {\n .d-xl-none {\n display: none !important;\n }\n .d-xl-inline {\n display: inline !important;\n }\n .d-xl-inline-block {\n display: inline-block !important;\n }\n .d-xl-block {\n display: block !important;\n }\n .d-xl-table {\n display: table !important;\n }\n .d-xl-table-cell {\n display: table-cell !important;\n }\n .d-xl-flex {\n display: -ms-flexbox !important;\n display: flex !important;\n }\n .d-xl-inline-flex {\n display: -ms-inline-flexbox !important;\n display: inline-flex !important;\n }\n}\n\n.d-print-block {\n display: none !important;\n}\n\n@media print {\n .d-print-block {\n display: block !important;\n }\n}\n\n.d-print-inline {\n display: none !important;\n}\n\n@media print {\n .d-print-inline {\n display: inline !important;\n }\n}\n\n.d-print-inline-block {\n display: none !important;\n}\n\n@media print {\n .d-print-inline-block {\n display: inline-block !important;\n }\n}\n\n@media print {\n .d-print-none {\n display: none !important;\n }\n}\n\n.embed-responsive {\n position: relative;\n display: block;\n width: 100%;\n padding: 0;\n overflow: hidden;\n}\n\n.embed-responsive::before {\n display: block;\n content: \"\";\n}\n\n.embed-responsive .embed-responsive-item,\n.embed-responsive iframe,\n.embed-responsive embed,\n.embed-responsive object,\n.embed-responsive video {\n position: absolute;\n top: 0;\n bottom: 0;\n left: 0;\n width: 100%;\n height: 100%;\n border: 0;\n}\n\n.embed-responsive-21by9::before {\n padding-top: 42.857143%;\n}\n\n.embed-responsive-16by9::before {\n padding-top: 56.25%;\n}\n\n.embed-responsive-4by3::before {\n padding-top: 75%;\n}\n\n.embed-responsive-1by1::before {\n padding-top: 100%;\n}\n\n.flex-row {\n -ms-flex-direction: row !important;\n flex-direction: row !important;\n}\n\n.flex-column {\n -ms-flex-direction: column !important;\n flex-direction: column !important;\n}\n\n.flex-row-reverse {\n -ms-flex-direction: row-reverse !important;\n flex-direction: row-reverse !important;\n}\n\n.flex-column-reverse {\n -ms-flex-direction: column-reverse !important;\n flex-direction: column-reverse !important;\n}\n\n.flex-wrap {\n -ms-flex-wrap: wrap !important;\n flex-wrap: wrap !important;\n}\n\n.flex-nowrap {\n -ms-flex-wrap: nowrap !important;\n flex-wrap: nowrap !important;\n}\n\n.flex-wrap-reverse {\n -ms-flex-wrap: wrap-reverse !important;\n flex-wrap: wrap-reverse !important;\n}\n\n.justify-content-start {\n -ms-flex-pack: start !important;\n justify-content: flex-start !important;\n}\n\n.justify-content-end {\n -ms-flex-pack: end !important;\n justify-content: flex-end !important;\n}\n\n.justify-content-center {\n -ms-flex-pack: center !important;\n justify-content: center !important;\n}\n\n.justify-content-between {\n -ms-flex-pack: justify !important;\n justify-content: space-between !important;\n}\n\n.justify-content-around {\n -ms-flex-pack: distribute !important;\n justify-content: space-around !important;\n}\n\n.align-items-start {\n -ms-flex-align: start !important;\n align-items: flex-start !important;\n}\n\n.align-items-end {\n -ms-flex-align: end !important;\n align-items: flex-end !important;\n}\n\n.align-items-center {\n -ms-flex-align: center !important;\n align-items: center !important;\n}\n\n.align-items-baseline {\n -ms-flex-align: baseline !important;\n align-items: baseline !important;\n}\n\n.align-items-stretch {\n -ms-flex-align: stretch !important;\n align-items: stretch !important;\n}\n\n.align-content-start {\n -ms-flex-line-pack: start !important;\n align-content: flex-start !important;\n}\n\n.align-content-end {\n -ms-flex-line-pack: end !important;\n align-content: flex-end !important;\n}\n\n.align-content-center {\n -ms-flex-line-pack: center !important;\n align-content: center !important;\n}\n\n.align-content-between {\n -ms-flex-line-pack: justify !important;\n align-content: space-between !important;\n}\n\n.align-content-around {\n -ms-flex-line-pack: distribute !important;\n align-content: space-around !important;\n}\n\n.align-content-stretch {\n -ms-flex-line-pack: stretch !important;\n align-content: stretch !important;\n}\n\n.align-self-auto {\n -ms-flex-item-align: auto !important;\n align-self: auto !important;\n}\n\n.align-self-start {\n -ms-flex-item-align: start !important;\n align-self: flex-start !important;\n}\n\n.align-self-end {\n -ms-flex-item-align: end !important;\n align-self: flex-end !important;\n}\n\n.align-self-center {\n -ms-flex-item-align: center !important;\n align-self: center !important;\n}\n\n.align-self-baseline {\n -ms-flex-item-align: baseline !important;\n align-self: baseline !important;\n}\n\n.align-self-stretch {\n -ms-flex-item-align: stretch !important;\n align-self: stretch !important;\n}\n\n@media (min-width: 576px) {\n .flex-sm-row {\n -ms-flex-direction: row !important;\n flex-direction: row !important;\n }\n .flex-sm-column {\n -ms-flex-direction: column !important;\n flex-direction: column !important;\n }\n .flex-sm-row-reverse {\n -ms-flex-direction: row-reverse !important;\n flex-direction: row-reverse !important;\n }\n .flex-sm-column-reverse {\n -ms-flex-direction: column-reverse !important;\n flex-direction: column-reverse !important;\n }\n .flex-sm-wrap {\n -ms-flex-wrap: wrap !important;\n flex-wrap: wrap !important;\n }\n .flex-sm-nowrap {\n -ms-flex-wrap: nowrap !important;\n flex-wrap: nowrap !important;\n }\n .flex-sm-wrap-reverse {\n -ms-flex-wrap: wrap-reverse !important;\n flex-wrap: wrap-reverse !important;\n }\n .justify-content-sm-start {\n -ms-flex-pack: start !important;\n justify-content: flex-start !important;\n }\n .justify-content-sm-end {\n -ms-flex-pack: end !important;\n justify-content: flex-end !important;\n }\n .justify-content-sm-center {\n -ms-flex-pack: center !important;\n justify-content: center !important;\n }\n .justify-content-sm-between {\n -ms-flex-pack: justify !important;\n justify-content: space-between !important;\n }\n .justify-content-sm-around {\n -ms-flex-pack: distribute !important;\n justify-content: space-around !important;\n }\n .align-items-sm-start {\n -ms-flex-align: start !important;\n align-items: flex-start !important;\n }\n .align-items-sm-end {\n -ms-flex-align: end !important;\n align-items: flex-end !important;\n }\n .align-items-sm-center {\n -ms-flex-align: center !important;\n align-items: center !important;\n }\n .align-items-sm-baseline {\n -ms-flex-align: baseline !important;\n align-items: baseline !important;\n }\n .align-items-sm-stretch {\n -ms-flex-align: stretch !important;\n align-items: stretch !important;\n }\n .align-content-sm-start {\n -ms-flex-line-pack: start !important;\n align-content: flex-start !important;\n }\n .align-content-sm-end {\n -ms-flex-line-pack: end !important;\n align-content: flex-end !important;\n }\n .align-content-sm-center {\n -ms-flex-line-pack: center !important;\n align-content: center !important;\n }\n .align-content-sm-between {\n -ms-flex-line-pack: justify !important;\n align-content: space-between !important;\n }\n .align-content-sm-around {\n -ms-flex-line-pack: distribute !important;\n align-content: space-around !important;\n }\n .align-content-sm-stretch {\n -ms-flex-line-pack: stretch !important;\n align-content: stretch !important;\n }\n .align-self-sm-auto {\n -ms-flex-item-align: auto !important;\n align-self: auto !important;\n }\n .align-self-sm-start {\n -ms-flex-item-align: start !important;\n align-self: flex-start !important;\n }\n .align-self-sm-end {\n -ms-flex-item-align: end !important;\n align-self: flex-end !important;\n }\n .align-self-sm-center {\n -ms-flex-item-align: center !important;\n align-self: center !important;\n }\n .align-self-sm-baseline {\n -ms-flex-item-align: baseline !important;\n align-self: baseline !important;\n }\n .align-self-sm-stretch {\n -ms-flex-item-align: stretch !important;\n align-self: stretch !important;\n }\n}\n\n@media (min-width: 768px) {\n .flex-md-row {\n -ms-flex-direction: row !important;\n flex-direction: row !important;\n }\n .flex-md-column {\n -ms-flex-direction: column !important;\n flex-direction: column !important;\n }\n .flex-md-row-reverse {\n -ms-flex-direction: row-reverse !important;\n flex-direction: row-reverse !important;\n }\n .flex-md-column-reverse {\n -ms-flex-direction: column-reverse !important;\n flex-direction: column-reverse !important;\n }\n .flex-md-wrap {\n -ms-flex-wrap: wrap !important;\n flex-wrap: wrap !important;\n }\n .flex-md-nowrap {\n -ms-flex-wrap: nowrap !important;\n flex-wrap: nowrap !important;\n }\n .flex-md-wrap-reverse {\n -ms-flex-wrap: wrap-reverse !important;\n flex-wrap: wrap-reverse !important;\n }\n .justify-content-md-start {\n -ms-flex-pack: start !important;\n justify-content: flex-start !important;\n }\n .justify-content-md-end {\n -ms-flex-pack: end !important;\n justify-content: flex-end !important;\n }\n .justify-content-md-center {\n -ms-flex-pack: center !important;\n justify-content: center !important;\n }\n .justify-content-md-between {\n -ms-flex-pack: justify !important;\n justify-content: space-between !important;\n }\n .justify-content-md-around {\n -ms-flex-pack: distribute !important;\n justify-content: space-around !important;\n }\n .align-items-md-start {\n -ms-flex-align: start !important;\n align-items: flex-start !important;\n }\n .align-items-md-end {\n -ms-flex-align: end !important;\n align-items: flex-end !important;\n }\n .align-items-md-center {\n -ms-flex-align: center !important;\n align-items: center !important;\n }\n .align-items-md-baseline {\n -ms-flex-align: baseline !important;\n align-items: baseline !important;\n }\n .align-items-md-stretch {\n -ms-flex-align: stretch !important;\n align-items: stretch !important;\n }\n .align-content-md-start {\n -ms-flex-line-pack: start !important;\n align-content: flex-start !important;\n }\n .align-content-md-end {\n -ms-flex-line-pack: end !important;\n align-content: flex-end !important;\n }\n .align-content-md-center {\n -ms-flex-line-pack: center !important;\n align-content: center !important;\n }\n .align-content-md-between {\n -ms-flex-line-pack: justify !important;\n align-content: space-between !important;\n }\n .align-content-md-around {\n -ms-flex-line-pack: distribute !important;\n align-content: space-around !important;\n }\n .align-content-md-stretch {\n -ms-flex-line-pack: stretch !important;\n align-content: stretch !important;\n }\n .align-self-md-auto {\n -ms-flex-item-align: auto !important;\n align-self: auto !important;\n }\n .align-self-md-start {\n -ms-flex-item-align: start !important;\n align-self: flex-start !important;\n }\n .align-self-md-end {\n -ms-flex-item-align: end !important;\n align-self: flex-end !important;\n }\n .align-self-md-center {\n -ms-flex-item-align: center !important;\n align-self: center !important;\n }\n .align-self-md-baseline {\n -ms-flex-item-align: baseline !important;\n align-self: baseline !important;\n }\n .align-self-md-stretch {\n -ms-flex-item-align: stretch !important;\n align-self: stretch !important;\n }\n}\n\n@media (min-width: 992px) {\n .flex-lg-row {\n -ms-flex-direction: row !important;\n flex-direction: row !important;\n }\n .flex-lg-column {\n -ms-flex-direction: column !important;\n flex-direction: column !important;\n }\n .flex-lg-row-reverse {\n -ms-flex-direction: row-reverse !important;\n flex-direction: row-reverse !important;\n }\n .flex-lg-column-reverse {\n -ms-flex-direction: column-reverse !important;\n flex-direction: column-reverse !important;\n }\n .flex-lg-wrap {\n -ms-flex-wrap: wrap !important;\n flex-wrap: wrap !important;\n }\n .flex-lg-nowrap {\n -ms-flex-wrap: nowrap !important;\n flex-wrap: nowrap !important;\n }\n .flex-lg-wrap-reverse {\n -ms-flex-wrap: wrap-reverse !important;\n flex-wrap: wrap-reverse !important;\n }\n .justify-content-lg-start {\n -ms-flex-pack: start !important;\n justify-content: flex-start !important;\n }\n .justify-content-lg-end {\n -ms-flex-pack: end !important;\n justify-content: flex-end !important;\n }\n .justify-content-lg-center {\n -ms-flex-pack: center !important;\n justify-content: center !important;\n }\n .justify-content-lg-between {\n -ms-flex-pack: justify !important;\n justify-content: space-between !important;\n }\n .justify-content-lg-around {\n -ms-flex-pack: distribute !important;\n justify-content: space-around !important;\n }\n .align-items-lg-start {\n -ms-flex-align: start !important;\n align-items: flex-start !important;\n }\n .align-items-lg-end {\n -ms-flex-align: end !important;\n align-items: flex-end !important;\n }\n .align-items-lg-center {\n -ms-flex-align: center !important;\n align-items: center !important;\n }\n .align-items-lg-baseline {\n -ms-flex-align: baseline !important;\n align-items: baseline !important;\n }\n .align-items-lg-stretch {\n -ms-flex-align: stretch !important;\n align-items: stretch !important;\n }\n .align-content-lg-start {\n -ms-flex-line-pack: start !important;\n align-content: flex-start !important;\n }\n .align-content-lg-end {\n -ms-flex-line-pack: end !important;\n align-content: flex-end !important;\n }\n .align-content-lg-center {\n -ms-flex-line-pack: center !important;\n align-content: center !important;\n }\n .align-content-lg-between {\n -ms-flex-line-pack: justify !important;\n align-content: space-between !important;\n }\n .align-content-lg-around {\n -ms-flex-line-pack: distribute !important;\n align-content: space-around !important;\n }\n .align-content-lg-stretch {\n -ms-flex-line-pack: stretch !important;\n align-content: stretch !important;\n }\n .align-self-lg-auto {\n -ms-flex-item-align: auto !important;\n align-self: auto !important;\n }\n .align-self-lg-start {\n -ms-flex-item-align: start !important;\n align-self: flex-start !important;\n }\n .align-self-lg-end {\n -ms-flex-item-align: end !important;\n align-self: flex-end !important;\n }\n .align-self-lg-center {\n -ms-flex-item-align: center !important;\n align-self: center !important;\n }\n .align-self-lg-baseline {\n -ms-flex-item-align: baseline !important;\n align-self: baseline !important;\n }\n .align-self-lg-stretch {\n -ms-flex-item-align: stretch !important;\n align-self: stretch !important;\n }\n}\n\n@media (min-width: 1200px) {\n .flex-xl-row {\n -ms-flex-direction: row !important;\n flex-direction: row !important;\n }\n .flex-xl-column {\n -ms-flex-direction: column !important;\n flex-direction: column !important;\n }\n .flex-xl-row-reverse {\n -ms-flex-direction: row-reverse !important;\n flex-direction: row-reverse !important;\n }\n .flex-xl-column-reverse {\n -ms-flex-direction: column-reverse !important;\n flex-direction: column-reverse !important;\n }\n .flex-xl-wrap {\n -ms-flex-wrap: wrap !important;\n flex-wrap: wrap !important;\n }\n .flex-xl-nowrap {\n -ms-flex-wrap: nowrap !important;\n flex-wrap: nowrap !important;\n }\n .flex-xl-wrap-reverse {\n -ms-flex-wrap: wrap-reverse !important;\n flex-wrap: wrap-reverse !important;\n }\n .justify-content-xl-start {\n -ms-flex-pack: start !important;\n justify-content: flex-start !important;\n }\n .justify-content-xl-end {\n -ms-flex-pack: end !important;\n justify-content: flex-end !important;\n }\n .justify-content-xl-center {\n -ms-flex-pack: center !important;\n justify-content: center !important;\n }\n .justify-content-xl-between {\n -ms-flex-pack: justify !important;\n justify-content: space-between !important;\n }\n .justify-content-xl-around {\n -ms-flex-pack: distribute !important;\n justify-content: space-around !important;\n }\n .align-items-xl-start {\n -ms-flex-align: start !important;\n align-items: flex-start !important;\n }\n .align-items-xl-end {\n -ms-flex-align: end !important;\n align-items: flex-end !important;\n }\n .align-items-xl-center {\n -ms-flex-align: center !important;\n align-items: center !important;\n }\n .align-items-xl-baseline {\n -ms-flex-align: baseline !important;\n align-items: baseline !important;\n }\n .align-items-xl-stretch {\n -ms-flex-align: stretch !important;\n align-items: stretch !important;\n }\n .align-content-xl-start {\n -ms-flex-line-pack: start !important;\n align-content: flex-start !important;\n }\n .align-content-xl-end {\n -ms-flex-line-pack: end !important;\n align-content: flex-end !important;\n }\n .align-content-xl-center {\n -ms-flex-line-pack: center !important;\n align-content: center !important;\n }\n .align-content-xl-between {\n -ms-flex-line-pack: justify !important;\n align-content: space-between !important;\n }\n .align-content-xl-around {\n -ms-flex-line-pack: distribute !important;\n align-content: space-around !important;\n }\n .align-content-xl-stretch {\n -ms-flex-line-pack: stretch !important;\n align-content: stretch !important;\n }\n .align-self-xl-auto {\n -ms-flex-item-align: auto !important;\n align-self: auto !important;\n }\n .align-self-xl-start {\n -ms-flex-item-align: start !important;\n align-self: flex-start !important;\n }\n .align-self-xl-end {\n -ms-flex-item-align: end !important;\n align-self: flex-end !important;\n }\n .align-self-xl-center {\n -ms-flex-item-align: center !important;\n align-self: center !important;\n }\n .align-self-xl-baseline {\n -ms-flex-item-align: baseline !important;\n align-self: baseline !important;\n }\n .align-self-xl-stretch {\n -ms-flex-item-align: stretch !important;\n align-self: stretch !important;\n }\n}\n\n.float-left {\n float: left !important;\n}\n\n.float-right {\n float: right !important;\n}\n\n.float-none {\n float: none !important;\n}\n\n@media (min-width: 576px) {\n .float-sm-left {\n float: left !important;\n }\n .float-sm-right {\n float: right !important;\n }\n .float-sm-none {\n float: none !important;\n }\n}\n\n@media (min-width: 768px) {\n .float-md-left {\n float: left !important;\n }\n .float-md-right {\n float: right !important;\n }\n .float-md-none {\n float: none !important;\n }\n}\n\n@media (min-width: 992px) {\n .float-lg-left {\n float: left !important;\n }\n .float-lg-right {\n float: right !important;\n }\n .float-lg-none {\n float: none !important;\n }\n}\n\n@media (min-width: 1200px) {\n .float-xl-left {\n float: left !important;\n }\n .float-xl-right {\n float: right !important;\n }\n .float-xl-none {\n float: none !important;\n }\n}\n\n.fixed-top {\n position: fixed;\n top: 0;\n right: 0;\n left: 0;\n z-index: 1030;\n}\n\n.fixed-bottom {\n position: fixed;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: 1030;\n}\n\n@supports ((position: -webkit-sticky) or (position: sticky)) {\n .sticky-top {\n position: -webkit-sticky;\n position: sticky;\n top: 0;\n z-index: 1020;\n }\n}\n\n.sr-only {\n position: absolute;\n width: 1px;\n height: 1px;\n padding: 0;\n overflow: hidden;\n clip: rect(0, 0, 0, 0);\n white-space: nowrap;\n -webkit-clip-path: inset(50%);\n clip-path: inset(50%);\n border: 0;\n}\n\n.sr-only-focusable:active, .sr-only-focusable:focus {\n position: static;\n width: auto;\n height: auto;\n overflow: visible;\n clip: auto;\n white-space: normal;\n -webkit-clip-path: none;\n clip-path: none;\n}\n\n.w-25 {\n width: 25% !important;\n}\n\n.w-50 {\n width: 50% !important;\n}\n\n.w-75 {\n width: 75% !important;\n}\n\n.w-100 {\n width: 100% !important;\n}\n\n.h-25 {\n height: 25% !important;\n}\n\n.h-50 {\n height: 50% !important;\n}\n\n.h-75 {\n height: 75% !important;\n}\n\n.h-100 {\n height: 100% !important;\n}\n\n.mw-100 {\n max-width: 100% !important;\n}\n\n.mh-100 {\n max-height: 100% !important;\n}\n\n.m-0 {\n margin: 0 !important;\n}\n\n.mt-0 {\n margin-top: 0 !important;\n}\n\n.mr-0 {\n margin-right: 0 !important;\n}\n\n.mb-0 {\n margin-bottom: 0 !important;\n}\n\n.ml-0 {\n margin-left: 0 !important;\n}\n\n.mx-0 {\n margin-right: 0 !important;\n margin-left: 0 !important;\n}\n\n.my-0 {\n margin-top: 0 !important;\n margin-bottom: 0 !important;\n}\n\n.m-1 {\n margin: 0.25rem !important;\n}\n\n.mt-1 {\n margin-top: 0.25rem !important;\n}\n\n.mr-1 {\n margin-right: 0.25rem !important;\n}\n\n.mb-1 {\n margin-bottom: 0.25rem !important;\n}\n\n.ml-1 {\n margin-left: 0.25rem !important;\n}\n\n.mx-1 {\n margin-right: 0.25rem !important;\n margin-left: 0.25rem !important;\n}\n\n.my-1 {\n margin-top: 0.25rem !important;\n margin-bottom: 0.25rem !important;\n}\n\n.m-2 {\n margin: 0.5rem !important;\n}\n\n.mt-2 {\n margin-top: 0.5rem !important;\n}\n\n.mr-2 {\n margin-right: 0.5rem !important;\n}\n\n.mb-2 {\n margin-bottom: 0.5rem !important;\n}\n\n.ml-2 {\n margin-left: 0.5rem !important;\n}\n\n.mx-2 {\n margin-right: 0.5rem !important;\n margin-left: 0.5rem !important;\n}\n\n.my-2 {\n margin-top: 0.5rem !important;\n margin-bottom: 0.5rem !important;\n}\n\n.m-3 {\n margin: 1rem !important;\n}\n\n.mt-3 {\n margin-top: 1rem !important;\n}\n\n.mr-3 {\n margin-right: 1rem !important;\n}\n\n.mb-3 {\n margin-bottom: 1rem !important;\n}\n\n.ml-3 {\n margin-left: 1rem !important;\n}\n\n.mx-3 {\n margin-right: 1rem !important;\n margin-left: 1rem !important;\n}\n\n.my-3 {\n margin-top: 1rem !important;\n margin-bottom: 1rem !important;\n}\n\n.m-4 {\n margin: 1.5rem !important;\n}\n\n.mt-4 {\n margin-top: 1.5rem !important;\n}\n\n.mr-4 {\n margin-right: 1.5rem !important;\n}\n\n.mb-4 {\n margin-bottom: 1.5rem !important;\n}\n\n.ml-4 {\n margin-left: 1.5rem !important;\n}\n\n.mx-4 {\n margin-right: 1.5rem !important;\n margin-left: 1.5rem !important;\n}\n\n.my-4 {\n margin-top: 1.5rem !important;\n margin-bottom: 1.5rem !important;\n}\n\n.m-5 {\n margin: 3rem !important;\n}\n\n.mt-5 {\n margin-top: 3rem !important;\n}\n\n.mr-5 {\n margin-right: 3rem !important;\n}\n\n.mb-5 {\n margin-bottom: 3rem !important;\n}\n\n.ml-5 {\n margin-left: 3rem !important;\n}\n\n.mx-5 {\n margin-right: 3rem !important;\n margin-left: 3rem !important;\n}\n\n.my-5 {\n margin-top: 3rem !important;\n margin-bottom: 3rem !important;\n}\n\n.p-0 {\n padding: 0 !important;\n}\n\n.pt-0 {\n padding-top: 0 !important;\n}\n\n.pr-0 {\n padding-right: 0 !important;\n}\n\n.pb-0 {\n padding-bottom: 0 !important;\n}\n\n.pl-0 {\n padding-left: 0 !important;\n}\n\n.px-0 {\n padding-right: 0 !important;\n padding-left: 0 !important;\n}\n\n.py-0 {\n padding-top: 0 !important;\n padding-bottom: 0 !important;\n}\n\n.p-1 {\n padding: 0.25rem !important;\n}\n\n.pt-1 {\n padding-top: 0.25rem !important;\n}\n\n.pr-1 {\n padding-right: 0.25rem !important;\n}\n\n.pb-1 {\n padding-bottom: 0.25rem !important;\n}\n\n.pl-1 {\n padding-left: 0.25rem !important;\n}\n\n.px-1 {\n padding-right: 0.25rem !important;\n padding-left: 0.25rem !important;\n}\n\n.py-1 {\n padding-top: 0.25rem !important;\n padding-bottom: 0.25rem !important;\n}\n\n.p-2 {\n padding: 0.5rem !important;\n}\n\n.pt-2 {\n padding-top: 0.5rem !important;\n}\n\n.pr-2 {\n padding-right: 0.5rem !important;\n}\n\n.pb-2 {\n padding-bottom: 0.5rem !important;\n}\n\n.pl-2 {\n padding-left: 0.5rem !important;\n}\n\n.px-2 {\n padding-right: 0.5rem !important;\n padding-left: 0.5rem !important;\n}\n\n.py-2 {\n padding-top: 0.5rem !important;\n padding-bottom: 0.5rem !important;\n}\n\n.p-3 {\n padding: 1rem !important;\n}\n\n.pt-3 {\n padding-top: 1rem !important;\n}\n\n.pr-3 {\n padding-right: 1rem !important;\n}\n\n.pb-3 {\n padding-bottom: 1rem !important;\n}\n\n.pl-3 {\n padding-left: 1rem !important;\n}\n\n.px-3 {\n padding-right: 1rem !important;\n padding-left: 1rem !important;\n}\n\n.py-3 {\n padding-top: 1rem !important;\n padding-bottom: 1rem !important;\n}\n\n.p-4 {\n padding: 1.5rem !important;\n}\n\n.pt-4 {\n padding-top: 1.5rem !important;\n}\n\n.pr-4 {\n padding-right: 1.5rem !important;\n}\n\n.pb-4 {\n padding-bottom: 1.5rem !important;\n}\n\n.pl-4 {\n padding-left: 1.5rem !important;\n}\n\n.px-4 {\n padding-right: 1.5rem !important;\n padding-left: 1.5rem !important;\n}\n\n.py-4 {\n padding-top: 1.5rem !important;\n padding-bottom: 1.5rem !important;\n}\n\n.p-5 {\n padding: 3rem !important;\n}\n\n.pt-5 {\n padding-top: 3rem !important;\n}\n\n.pr-5 {\n padding-right: 3rem !important;\n}\n\n.pb-5 {\n padding-bottom: 3rem !important;\n}\n\n.pl-5 {\n padding-left: 3rem !important;\n}\n\n.px-5 {\n padding-right: 3rem !important;\n padding-left: 3rem !important;\n}\n\n.py-5 {\n padding-top: 3rem !important;\n padding-bottom: 3rem !important;\n}\n\n.m-auto {\n margin: auto !important;\n}\n\n.mt-auto {\n margin-top: auto !important;\n}\n\n.mr-auto {\n margin-right: auto !important;\n}\n\n.mb-auto {\n margin-bottom: auto !important;\n}\n\n.ml-auto {\n margin-left: auto !important;\n}\n\n.mx-auto {\n margin-right: auto !important;\n margin-left: auto !important;\n}\n\n.my-auto {\n margin-top: auto !important;\n margin-bottom: auto !important;\n}\n\n@media (min-width: 576px) {\n .m-sm-0 {\n margin: 0 !important;\n }\n .mt-sm-0 {\n margin-top: 0 !important;\n }\n .mr-sm-0 {\n margin-right: 0 !important;\n }\n .mb-sm-0 {\n margin-bottom: 0 !important;\n }\n .ml-sm-0 {\n margin-left: 0 !important;\n }\n .mx-sm-0 {\n margin-right: 0 !important;\n margin-left: 0 !important;\n }\n .my-sm-0 {\n margin-top: 0 !important;\n margin-bottom: 0 !important;\n }\n .m-sm-1 {\n margin: 0.25rem !important;\n }\n .mt-sm-1 {\n margin-top: 0.25rem !important;\n }\n .mr-sm-1 {\n margin-right: 0.25rem !important;\n }\n .mb-sm-1 {\n margin-bottom: 0.25rem !important;\n }\n .ml-sm-1 {\n margin-left: 0.25rem !important;\n }\n .mx-sm-1 {\n margin-right: 0.25rem !important;\n margin-left: 0.25rem !important;\n }\n .my-sm-1 {\n margin-top: 0.25rem !important;\n margin-bottom: 0.25rem !important;\n }\n .m-sm-2 {\n margin: 0.5rem !important;\n }\n .mt-sm-2 {\n margin-top: 0.5rem !important;\n }\n .mr-sm-2 {\n margin-right: 0.5rem !important;\n }\n .mb-sm-2 {\n margin-bottom: 0.5rem !important;\n }\n .ml-sm-2 {\n margin-left: 0.5rem !important;\n }\n .mx-sm-2 {\n margin-right: 0.5rem !important;\n margin-left: 0.5rem !important;\n }\n .my-sm-2 {\n margin-top: 0.5rem !important;\n margin-bottom: 0.5rem !important;\n }\n .m-sm-3 {\n margin: 1rem !important;\n }\n .mt-sm-3 {\n margin-top: 1rem !important;\n }\n .mr-sm-3 {\n margin-right: 1rem !important;\n }\n .mb-sm-3 {\n margin-bottom: 1rem !important;\n }\n .ml-sm-3 {\n margin-left: 1rem !important;\n }\n .mx-sm-3 {\n margin-right: 1rem !important;\n margin-left: 1rem !important;\n }\n .my-sm-3 {\n margin-top: 1rem !important;\n margin-bottom: 1rem !important;\n }\n .m-sm-4 {\n margin: 1.5rem !important;\n }\n .mt-sm-4 {\n margin-top: 1.5rem !important;\n }\n .mr-sm-4 {\n margin-right: 1.5rem !important;\n }\n .mb-sm-4 {\n margin-bottom: 1.5rem !important;\n }\n .ml-sm-4 {\n margin-left: 1.5rem !important;\n }\n .mx-sm-4 {\n margin-right: 1.5rem !important;\n margin-left: 1.5rem !important;\n }\n .my-sm-4 {\n margin-top: 1.5rem !important;\n margin-bottom: 1.5rem !important;\n }\n .m-sm-5 {\n margin: 3rem !important;\n }\n .mt-sm-5 {\n margin-top: 3rem !important;\n }\n .mr-sm-5 {\n margin-right: 3rem !important;\n }\n .mb-sm-5 {\n margin-bottom: 3rem !important;\n }\n .ml-sm-5 {\n margin-left: 3rem !important;\n }\n .mx-sm-5 {\n margin-right: 3rem !important;\n margin-left: 3rem !important;\n }\n .my-sm-5 {\n margin-top: 3rem !important;\n margin-bottom: 3rem !important;\n }\n .p-sm-0 {\n padding: 0 !important;\n }\n .pt-sm-0 {\n padding-top: 0 !important;\n }\n .pr-sm-0 {\n padding-right: 0 !important;\n }\n .pb-sm-0 {\n padding-bottom: 0 !important;\n }\n .pl-sm-0 {\n padding-left: 0 !important;\n }\n .px-sm-0 {\n padding-right: 0 !important;\n padding-left: 0 !important;\n }\n .py-sm-0 {\n padding-top: 0 !important;\n padding-bottom: 0 !important;\n }\n .p-sm-1 {\n padding: 0.25rem !important;\n }\n .pt-sm-1 {\n padding-top: 0.25rem !important;\n }\n .pr-sm-1 {\n padding-right: 0.25rem !important;\n }\n .pb-sm-1 {\n padding-bottom: 0.25rem !important;\n }\n .pl-sm-1 {\n padding-left: 0.25rem !important;\n }\n .px-sm-1 {\n padding-right: 0.25rem !important;\n padding-left: 0.25rem !important;\n }\n .py-sm-1 {\n padding-top: 0.25rem !important;\n padding-bottom: 0.25rem !important;\n }\n .p-sm-2 {\n padding: 0.5rem !important;\n }\n .pt-sm-2 {\n padding-top: 0.5rem !important;\n }\n .pr-sm-2 {\n padding-right: 0.5rem !important;\n }\n .pb-sm-2 {\n padding-bottom: 0.5rem !important;\n }\n .pl-sm-2 {\n padding-left: 0.5rem !important;\n }\n .px-sm-2 {\n padding-right: 0.5rem !important;\n padding-left: 0.5rem !important;\n }\n .py-sm-2 {\n padding-top: 0.5rem !important;\n padding-bottom: 0.5rem !important;\n }\n .p-sm-3 {\n padding: 1rem !important;\n }\n .pt-sm-3 {\n padding-top: 1rem !important;\n }\n .pr-sm-3 {\n padding-right: 1rem !important;\n }\n .pb-sm-3 {\n padding-bottom: 1rem !important;\n }\n .pl-sm-3 {\n padding-left: 1rem !important;\n }\n .px-sm-3 {\n padding-right: 1rem !important;\n padding-left: 1rem !important;\n }\n .py-sm-3 {\n padding-top: 1rem !important;\n padding-bottom: 1rem !important;\n }\n .p-sm-4 {\n padding: 1.5rem !important;\n }\n .pt-sm-4 {\n padding-top: 1.5rem !important;\n }\n .pr-sm-4 {\n padding-right: 1.5rem !important;\n }\n .pb-sm-4 {\n padding-bottom: 1.5rem !important;\n }\n .pl-sm-4 {\n padding-left: 1.5rem !important;\n }\n .px-sm-4 {\n padding-right: 1.5rem !important;\n padding-left: 1.5rem !important;\n }\n .py-sm-4 {\n padding-top: 1.5rem !important;\n padding-bottom: 1.5rem !important;\n }\n .p-sm-5 {\n padding: 3rem !important;\n }\n .pt-sm-5 {\n padding-top: 3rem !important;\n }\n .pr-sm-5 {\n padding-right: 3rem !important;\n }\n .pb-sm-5 {\n padding-bottom: 3rem !important;\n }\n .pl-sm-5 {\n padding-left: 3rem !important;\n }\n .px-sm-5 {\n padding-right: 3rem !important;\n padding-left: 3rem !important;\n }\n .py-sm-5 {\n padding-top: 3rem !important;\n padding-bottom: 3rem !important;\n }\n .m-sm-auto {\n margin: auto !important;\n }\n .mt-sm-auto {\n margin-top: auto !important;\n }\n .mr-sm-auto {\n margin-right: auto !important;\n }\n .mb-sm-auto {\n margin-bottom: auto !important;\n }\n .ml-sm-auto {\n margin-left: auto !important;\n }\n .mx-sm-auto {\n margin-right: auto !important;\n margin-left: auto !important;\n }\n .my-sm-auto {\n margin-top: auto !important;\n margin-bottom: auto !important;\n }\n}\n\n@media (min-width: 768px) {\n .m-md-0 {\n margin: 0 !important;\n }\n .mt-md-0 {\n margin-top: 0 !important;\n }\n .mr-md-0 {\n margin-right: 0 !important;\n }\n .mb-md-0 {\n margin-bottom: 0 !important;\n }\n .ml-md-0 {\n margin-left: 0 !important;\n }\n .mx-md-0 {\n margin-right: 0 !important;\n margin-left: 0 !important;\n }\n .my-md-0 {\n margin-top: 0 !important;\n margin-bottom: 0 !important;\n }\n .m-md-1 {\n margin: 0.25rem !important;\n }\n .mt-md-1 {\n margin-top: 0.25rem !important;\n }\n .mr-md-1 {\n margin-right: 0.25rem !important;\n }\n .mb-md-1 {\n margin-bottom: 0.25rem !important;\n }\n .ml-md-1 {\n margin-left: 0.25rem !important;\n }\n .mx-md-1 {\n margin-right: 0.25rem !important;\n margin-left: 0.25rem !important;\n }\n .my-md-1 {\n margin-top: 0.25rem !important;\n margin-bottom: 0.25rem !important;\n }\n .m-md-2 {\n margin: 0.5rem !important;\n }\n .mt-md-2 {\n margin-top: 0.5rem !important;\n }\n .mr-md-2 {\n margin-right: 0.5rem !important;\n }\n .mb-md-2 {\n margin-bottom: 0.5rem !important;\n }\n .ml-md-2 {\n margin-left: 0.5rem !important;\n }\n .mx-md-2 {\n margin-right: 0.5rem !important;\n margin-left: 0.5rem !important;\n }\n .my-md-2 {\n margin-top: 0.5rem !important;\n margin-bottom: 0.5rem !important;\n }\n .m-md-3 {\n margin: 1rem !important;\n }\n .mt-md-3 {\n margin-top: 1rem !important;\n }\n .mr-md-3 {\n margin-right: 1rem !important;\n }\n .mb-md-3 {\n margin-bottom: 1rem !important;\n }\n .ml-md-3 {\n margin-left: 1rem !important;\n }\n .mx-md-3 {\n margin-right: 1rem !important;\n margin-left: 1rem !important;\n }\n .my-md-3 {\n margin-top: 1rem !important;\n margin-bottom: 1rem !important;\n }\n .m-md-4 {\n margin: 1.5rem !important;\n }\n .mt-md-4 {\n margin-top: 1.5rem !important;\n }\n .mr-md-4 {\n margin-right: 1.5rem !important;\n }\n .mb-md-4 {\n margin-bottom: 1.5rem !important;\n }\n .ml-md-4 {\n margin-left: 1.5rem !important;\n }\n .mx-md-4 {\n margin-right: 1.5rem !important;\n margin-left: 1.5rem !important;\n }\n .my-md-4 {\n margin-top: 1.5rem !important;\n margin-bottom: 1.5rem !important;\n }\n .m-md-5 {\n margin: 3rem !important;\n }\n .mt-md-5 {\n margin-top: 3rem !important;\n }\n .mr-md-5 {\n margin-right: 3rem !important;\n }\n .mb-md-5 {\n margin-bottom: 3rem !important;\n }\n .ml-md-5 {\n margin-left: 3rem !important;\n }\n .mx-md-5 {\n margin-right: 3rem !important;\n margin-left: 3rem !important;\n }\n .my-md-5 {\n margin-top: 3rem !important;\n margin-bottom: 3rem !important;\n }\n .p-md-0 {\n padding: 0 !important;\n }\n .pt-md-0 {\n padding-top: 0 !important;\n }\n .pr-md-0 {\n padding-right: 0 !important;\n }\n .pb-md-0 {\n padding-bottom: 0 !important;\n }\n .pl-md-0 {\n padding-left: 0 !important;\n }\n .px-md-0 {\n padding-right: 0 !important;\n padding-left: 0 !important;\n }\n .py-md-0 {\n padding-top: 0 !important;\n padding-bottom: 0 !important;\n }\n .p-md-1 {\n padding: 0.25rem !important;\n }\n .pt-md-1 {\n padding-top: 0.25rem !important;\n }\n .pr-md-1 {\n padding-right: 0.25rem !important;\n }\n .pb-md-1 {\n padding-bottom: 0.25rem !important;\n }\n .pl-md-1 {\n padding-left: 0.25rem !important;\n }\n .px-md-1 {\n padding-right: 0.25rem !important;\n padding-left: 0.25rem !important;\n }\n .py-md-1 {\n padding-top: 0.25rem !important;\n padding-bottom: 0.25rem !important;\n }\n .p-md-2 {\n padding: 0.5rem !important;\n }\n .pt-md-2 {\n padding-top: 0.5rem !important;\n }\n .pr-md-2 {\n padding-right: 0.5rem !important;\n }\n .pb-md-2 {\n padding-bottom: 0.5rem !important;\n }\n .pl-md-2 {\n padding-left: 0.5rem !important;\n }\n .px-md-2 {\n padding-right: 0.5rem !important;\n padding-left: 0.5rem !important;\n }\n .py-md-2 {\n padding-top: 0.5rem !important;\n padding-bottom: 0.5rem !important;\n }\n .p-md-3 {\n padding: 1rem !important;\n }\n .pt-md-3 {\n padding-top: 1rem !important;\n }\n .pr-md-3 {\n padding-right: 1rem !important;\n }\n .pb-md-3 {\n padding-bottom: 1rem !important;\n }\n .pl-md-3 {\n padding-left: 1rem !important;\n }\n .px-md-3 {\n padding-right: 1rem !important;\n padding-left: 1rem !important;\n }\n .py-md-3 {\n padding-top: 1rem !important;\n padding-bottom: 1rem !important;\n }\n .p-md-4 {\n padding: 1.5rem !important;\n }\n .pt-md-4 {\n padding-top: 1.5rem !important;\n }\n .pr-md-4 {\n padding-right: 1.5rem !important;\n }\n .pb-md-4 {\n padding-bottom: 1.5rem !important;\n }\n .pl-md-4 {\n padding-left: 1.5rem !important;\n }\n .px-md-4 {\n padding-right: 1.5rem !important;\n padding-left: 1.5rem !important;\n }\n .py-md-4 {\n padding-top: 1.5rem !important;\n padding-bottom: 1.5rem !important;\n }\n .p-md-5 {\n padding: 3rem !important;\n }\n .pt-md-5 {\n padding-top: 3rem !important;\n }\n .pr-md-5 {\n padding-right: 3rem !important;\n }\n .pb-md-5 {\n padding-bottom: 3rem !important;\n }\n .pl-md-5 {\n padding-left: 3rem !important;\n }\n .px-md-5 {\n padding-right: 3rem !important;\n padding-left: 3rem !important;\n }\n .py-md-5 {\n padding-top: 3rem !important;\n padding-bottom: 3rem !important;\n }\n .m-md-auto {\n margin: auto !important;\n }\n .mt-md-auto {\n margin-top: auto !important;\n }\n .mr-md-auto {\n margin-right: auto !important;\n }\n .mb-md-auto {\n margin-bottom: auto !important;\n }\n .ml-md-auto {\n margin-left: auto !important;\n }\n .mx-md-auto {\n margin-right: auto !important;\n margin-left: auto !important;\n }\n .my-md-auto {\n margin-top: auto !important;\n margin-bottom: auto !important;\n }\n}\n\n@media (min-width: 992px) {\n .m-lg-0 {\n margin: 0 !important;\n }\n .mt-lg-0 {\n margin-top: 0 !important;\n }\n .mr-lg-0 {\n margin-right: 0 !important;\n }\n .mb-lg-0 {\n margin-bottom: 0 !important;\n }\n .ml-lg-0 {\n margin-left: 0 !important;\n }\n .mx-lg-0 {\n margin-right: 0 !important;\n margin-left: 0 !important;\n }\n .my-lg-0 {\n margin-top: 0 !important;\n margin-bottom: 0 !important;\n }\n .m-lg-1 {\n margin: 0.25rem !important;\n }\n .mt-lg-1 {\n margin-top: 0.25rem !important;\n }\n .mr-lg-1 {\n margin-right: 0.25rem !important;\n }\n .mb-lg-1 {\n margin-bottom: 0.25rem !important;\n }\n .ml-lg-1 {\n margin-left: 0.25rem !important;\n }\n .mx-lg-1 {\n margin-right: 0.25rem !important;\n margin-left: 0.25rem !important;\n }\n .my-lg-1 {\n margin-top: 0.25rem !important;\n margin-bottom: 0.25rem !important;\n }\n .m-lg-2 {\n margin: 0.5rem !important;\n }\n .mt-lg-2 {\n margin-top: 0.5rem !important;\n }\n .mr-lg-2 {\n margin-right: 0.5rem !important;\n }\n .mb-lg-2 {\n margin-bottom: 0.5rem !important;\n }\n .ml-lg-2 {\n margin-left: 0.5rem !important;\n }\n .mx-lg-2 {\n margin-right: 0.5rem !important;\n margin-left: 0.5rem !important;\n }\n .my-lg-2 {\n margin-top: 0.5rem !important;\n margin-bottom: 0.5rem !important;\n }\n .m-lg-3 {\n margin: 1rem !important;\n }\n .mt-lg-3 {\n margin-top: 1rem !important;\n }\n .mr-lg-3 {\n margin-right: 1rem !important;\n }\n .mb-lg-3 {\n margin-bottom: 1rem !important;\n }\n .ml-lg-3 {\n margin-left: 1rem !important;\n }\n .mx-lg-3 {\n margin-right: 1rem !important;\n margin-left: 1rem !important;\n }\n .my-lg-3 {\n margin-top: 1rem !important;\n margin-bottom: 1rem !important;\n }\n .m-lg-4 {\n margin: 1.5rem !important;\n }\n .mt-lg-4 {\n margin-top: 1.5rem !important;\n }\n .mr-lg-4 {\n margin-right: 1.5rem !important;\n }\n .mb-lg-4 {\n margin-bottom: 1.5rem !important;\n }\n .ml-lg-4 {\n margin-left: 1.5rem !important;\n }\n .mx-lg-4 {\n margin-right: 1.5rem !important;\n margin-left: 1.5rem !important;\n }\n .my-lg-4 {\n margin-top: 1.5rem !important;\n margin-bottom: 1.5rem !important;\n }\n .m-lg-5 {\n margin: 3rem !important;\n }\n .mt-lg-5 {\n margin-top: 3rem !important;\n }\n .mr-lg-5 {\n margin-right: 3rem !important;\n }\n .mb-lg-5 {\n margin-bottom: 3rem !important;\n }\n .ml-lg-5 {\n margin-left: 3rem !important;\n }\n .mx-lg-5 {\n margin-right: 3rem !important;\n margin-left: 3rem !important;\n }\n .my-lg-5 {\n margin-top: 3rem !important;\n margin-bottom: 3rem !important;\n }\n .p-lg-0 {\n padding: 0 !important;\n }\n .pt-lg-0 {\n padding-top: 0 !important;\n }\n .pr-lg-0 {\n padding-right: 0 !important;\n }\n .pb-lg-0 {\n padding-bottom: 0 !important;\n }\n .pl-lg-0 {\n padding-left: 0 !important;\n }\n .px-lg-0 {\n padding-right: 0 !important;\n padding-left: 0 !important;\n }\n .py-lg-0 {\n padding-top: 0 !important;\n padding-bottom: 0 !important;\n }\n .p-lg-1 {\n padding: 0.25rem !important;\n }\n .pt-lg-1 {\n padding-top: 0.25rem !important;\n }\n .pr-lg-1 {\n padding-right: 0.25rem !important;\n }\n .pb-lg-1 {\n padding-bottom: 0.25rem !important;\n }\n .pl-lg-1 {\n padding-left: 0.25rem !important;\n }\n .px-lg-1 {\n padding-right: 0.25rem !important;\n padding-left: 0.25rem !important;\n }\n .py-lg-1 {\n padding-top: 0.25rem !important;\n padding-bottom: 0.25rem !important;\n }\n .p-lg-2 {\n padding: 0.5rem !important;\n }\n .pt-lg-2 {\n padding-top: 0.5rem !important;\n }\n .pr-lg-2 {\n padding-right: 0.5rem !important;\n }\n .pb-lg-2 {\n padding-bottom: 0.5rem !important;\n }\n .pl-lg-2 {\n padding-left: 0.5rem !important;\n }\n .px-lg-2 {\n padding-right: 0.5rem !important;\n padding-left: 0.5rem !important;\n }\n .py-lg-2 {\n padding-top: 0.5rem !important;\n padding-bottom: 0.5rem !important;\n }\n .p-lg-3 {\n padding: 1rem !important;\n }\n .pt-lg-3 {\n padding-top: 1rem !important;\n }\n .pr-lg-3 {\n padding-right: 1rem !important;\n }\n .pb-lg-3 {\n padding-bottom: 1rem !important;\n }\n .pl-lg-3 {\n padding-left: 1rem !important;\n }\n .px-lg-3 {\n padding-right: 1rem !important;\n padding-left: 1rem !important;\n }\n .py-lg-3 {\n padding-top: 1rem !important;\n padding-bottom: 1rem !important;\n }\n .p-lg-4 {\n padding: 1.5rem !important;\n }\n .pt-lg-4 {\n padding-top: 1.5rem !important;\n }\n .pr-lg-4 {\n padding-right: 1.5rem !important;\n }\n .pb-lg-4 {\n padding-bottom: 1.5rem !important;\n }\n .pl-lg-4 {\n padding-left: 1.5rem !important;\n }\n .px-lg-4 {\n padding-right: 1.5rem !important;\n padding-left: 1.5rem !important;\n }\n .py-lg-4 {\n padding-top: 1.5rem !important;\n padding-bottom: 1.5rem !important;\n }\n .p-lg-5 {\n padding: 3rem !important;\n }\n .pt-lg-5 {\n padding-top: 3rem !important;\n }\n .pr-lg-5 {\n padding-right: 3rem !important;\n }\n .pb-lg-5 {\n padding-bottom: 3rem !important;\n }\n .pl-lg-5 {\n padding-left: 3rem !important;\n }\n .px-lg-5 {\n padding-right: 3rem !important;\n padding-left: 3rem !important;\n }\n .py-lg-5 {\n padding-top: 3rem !important;\n padding-bottom: 3rem !important;\n }\n .m-lg-auto {\n margin: auto !important;\n }\n .mt-lg-auto {\n margin-top: auto !important;\n }\n .mr-lg-auto {\n margin-right: auto !important;\n }\n .mb-lg-auto {\n margin-bottom: auto !important;\n }\n .ml-lg-auto {\n margin-left: auto !important;\n }\n .mx-lg-auto {\n margin-right: auto !important;\n margin-left: auto !important;\n }\n .my-lg-auto {\n margin-top: auto !important;\n margin-bottom: auto !important;\n }\n}\n\n@media (min-width: 1200px) {\n .m-xl-0 {\n margin: 0 !important;\n }\n .mt-xl-0 {\n margin-top: 0 !important;\n }\n .mr-xl-0 {\n margin-right: 0 !important;\n }\n .mb-xl-0 {\n margin-bottom: 0 !important;\n }\n .ml-xl-0 {\n margin-left: 0 !important;\n }\n .mx-xl-0 {\n margin-right: 0 !important;\n margin-left: 0 !important;\n }\n .my-xl-0 {\n margin-top: 0 !important;\n margin-bottom: 0 !important;\n }\n .m-xl-1 {\n margin: 0.25rem !important;\n }\n .mt-xl-1 {\n margin-top: 0.25rem !important;\n }\n .mr-xl-1 {\n margin-right: 0.25rem !important;\n }\n .mb-xl-1 {\n margin-bottom: 0.25rem !important;\n }\n .ml-xl-1 {\n margin-left: 0.25rem !important;\n }\n .mx-xl-1 {\n margin-right: 0.25rem !important;\n margin-left: 0.25rem !important;\n }\n .my-xl-1 {\n margin-top: 0.25rem !important;\n margin-bottom: 0.25rem !important;\n }\n .m-xl-2 {\n margin: 0.5rem !important;\n }\n .mt-xl-2 {\n margin-top: 0.5rem !important;\n }\n .mr-xl-2 {\n margin-right: 0.5rem !important;\n }\n .mb-xl-2 {\n margin-bottom: 0.5rem !important;\n }\n .ml-xl-2 {\n margin-left: 0.5rem !important;\n }\n .mx-xl-2 {\n margin-right: 0.5rem !important;\n margin-left: 0.5rem !important;\n }\n .my-xl-2 {\n margin-top: 0.5rem !important;\n margin-bottom: 0.5rem !important;\n }\n .m-xl-3 {\n margin: 1rem !important;\n }\n .mt-xl-3 {\n margin-top: 1rem !important;\n }\n .mr-xl-3 {\n margin-right: 1rem !important;\n }\n .mb-xl-3 {\n margin-bottom: 1rem !important;\n }\n .ml-xl-3 {\n margin-left: 1rem !important;\n }\n .mx-xl-3 {\n margin-right: 1rem !important;\n margin-left: 1rem !important;\n }\n .my-xl-3 {\n margin-top: 1rem !important;\n margin-bottom: 1rem !important;\n }\n .m-xl-4 {\n margin: 1.5rem !important;\n }\n .mt-xl-4 {\n margin-top: 1.5rem !important;\n }\n .mr-xl-4 {\n margin-right: 1.5rem !important;\n }\n .mb-xl-4 {\n margin-bottom: 1.5rem !important;\n }\n .ml-xl-4 {\n margin-left: 1.5rem !important;\n }\n .mx-xl-4 {\n margin-right: 1.5rem !important;\n margin-left: 1.5rem !important;\n }\n .my-xl-4 {\n margin-top: 1.5rem !important;\n margin-bottom: 1.5rem !important;\n }\n .m-xl-5 {\n margin: 3rem !important;\n }\n .mt-xl-5 {\n margin-top: 3rem !important;\n }\n .mr-xl-5 {\n margin-right: 3rem !important;\n }\n .mb-xl-5 {\n margin-bottom: 3rem !important;\n }\n .ml-xl-5 {\n margin-left: 3rem !important;\n }\n .mx-xl-5 {\n margin-right: 3rem !important;\n margin-left: 3rem !important;\n }\n .my-xl-5 {\n margin-top: 3rem !important;\n margin-bottom: 3rem !important;\n }\n .p-xl-0 {\n padding: 0 !important;\n }\n .pt-xl-0 {\n padding-top: 0 !important;\n }\n .pr-xl-0 {\n padding-right: 0 !important;\n }\n .pb-xl-0 {\n padding-bottom: 0 !important;\n }\n .pl-xl-0 {\n padding-left: 0 !important;\n }\n .px-xl-0 {\n padding-right: 0 !important;\n padding-left: 0 !important;\n }\n .py-xl-0 {\n padding-top: 0 !important;\n padding-bottom: 0 !important;\n }\n .p-xl-1 {\n padding: 0.25rem !important;\n }\n .pt-xl-1 {\n padding-top: 0.25rem !important;\n }\n .pr-xl-1 {\n padding-right: 0.25rem !important;\n }\n .pb-xl-1 {\n padding-bottom: 0.25rem !important;\n }\n .pl-xl-1 {\n padding-left: 0.25rem !important;\n }\n .px-xl-1 {\n padding-right: 0.25rem !important;\n padding-left: 0.25rem !important;\n }\n .py-xl-1 {\n padding-top: 0.25rem !important;\n padding-bottom: 0.25rem !important;\n }\n .p-xl-2 {\n padding: 0.5rem !important;\n }\n .pt-xl-2 {\n padding-top: 0.5rem !important;\n }\n .pr-xl-2 {\n padding-right: 0.5rem !important;\n }\n .pb-xl-2 {\n padding-bottom: 0.5rem !important;\n }\n .pl-xl-2 {\n padding-left: 0.5rem !important;\n }\n .px-xl-2 {\n padding-right: 0.5rem !important;\n padding-left: 0.5rem !important;\n }\n .py-xl-2 {\n padding-top: 0.5rem !important;\n padding-bottom: 0.5rem !important;\n }\n .p-xl-3 {\n padding: 1rem !important;\n }\n .pt-xl-3 {\n padding-top: 1rem !important;\n }\n .pr-xl-3 {\n padding-right: 1rem !important;\n }\n .pb-xl-3 {\n padding-bottom: 1rem !important;\n }\n .pl-xl-3 {\n padding-left: 1rem !important;\n }\n .px-xl-3 {\n padding-right: 1rem !important;\n padding-left: 1rem !important;\n }\n .py-xl-3 {\n padding-top: 1rem !important;\n padding-bottom: 1rem !important;\n }\n .p-xl-4 {\n padding: 1.5rem !important;\n }\n .pt-xl-4 {\n padding-top: 1.5rem !important;\n }\n .pr-xl-4 {\n padding-right: 1.5rem !important;\n }\n .pb-xl-4 {\n padding-bottom: 1.5rem !important;\n }\n .pl-xl-4 {\n padding-left: 1.5rem !important;\n }\n .px-xl-4 {\n padding-right: 1.5rem !important;\n padding-left: 1.5rem !important;\n }\n .py-xl-4 {\n padding-top: 1.5rem !important;\n padding-bottom: 1.5rem !important;\n }\n .p-xl-5 {\n padding: 3rem !important;\n }\n .pt-xl-5 {\n padding-top: 3rem !important;\n }\n .pr-xl-5 {\n padding-right: 3rem !important;\n }\n .pb-xl-5 {\n padding-bottom: 3rem !important;\n }\n .pl-xl-5 {\n padding-left: 3rem !important;\n }\n .px-xl-5 {\n padding-right: 3rem !important;\n padding-left: 3rem !important;\n }\n .py-xl-5 {\n padding-top: 3rem !important;\n padding-bottom: 3rem !important;\n }\n .m-xl-auto {\n margin: auto !important;\n }\n .mt-xl-auto {\n margin-top: auto !important;\n }\n .mr-xl-auto {\n margin-right: auto !important;\n }\n .mb-xl-auto {\n margin-bottom: auto !important;\n }\n .ml-xl-auto {\n margin-left: auto !important;\n }\n .mx-xl-auto {\n margin-right: auto !important;\n margin-left: auto !important;\n }\n .my-xl-auto {\n margin-top: auto !important;\n margin-bottom: auto !important;\n }\n}\n\n.text-justify {\n text-align: justify !important;\n}\n\n.text-nowrap {\n white-space: nowrap !important;\n}\n\n.text-truncate {\n overflow: hidden;\n text-overflow: ellipsis;\n white-space: nowrap;\n}\n\n.text-left {\n text-align: left !important;\n}\n\n.text-right {\n text-align: right !important;\n}\n\n.text-center {\n text-align: center !important;\n}\n\n@media (min-width: 576px) {\n .text-sm-left {\n text-align: left !important;\n }\n .text-sm-right {\n text-align: right !important;\n }\n .text-sm-center {\n text-align: center !important;\n }\n}\n\n@media (min-width: 768px) {\n .text-md-left {\n text-align: left !important;\n }\n .text-md-right {\n text-align: right !important;\n }\n .text-md-center {\n text-align: center !important;\n }\n}\n\n@media (min-width: 992px) {\n .text-lg-left {\n text-align: left !important;\n }\n .text-lg-right {\n text-align: right !important;\n }\n .text-lg-center {\n text-align: center !important;\n }\n}\n\n@media (min-width: 1200px) {\n .text-xl-left {\n text-align: left !important;\n }\n .text-xl-right {\n text-align: right !important;\n }\n .text-xl-center {\n text-align: center !important;\n }\n}\n\n.text-lowercase {\n text-transform: lowercase !important;\n}\n\n.text-uppercase {\n text-transform: uppercase !important;\n}\n\n.text-capitalize {\n text-transform: capitalize !important;\n}\n\n.font-weight-normal {\n font-weight: normal;\n}\n\n.font-weight-bold {\n font-weight: bold;\n}\n\n.font-italic {\n font-style: italic;\n}\n\n.text-white {\n color: #fff !important;\n}\n\n.text-primary {\n color: #007bff !important;\n}\n\na.text-primary:focus, a.text-primary:hover {\n color: #0062cc !important;\n}\n\n.text-secondary {\n color: #868e96 !important;\n}\n\na.text-secondary:focus, a.text-secondary:hover {\n color: #6c757d !important;\n}\n\n.text-success {\n color: #28a745 !important;\n}\n\na.text-success:focus, a.text-success:hover {\n color: #1e7e34 !important;\n}\n\n.text-info {\n color: #17a2b8 !important;\n}\n\na.text-info:focus, a.text-info:hover {\n color: #117a8b !important;\n}\n\n.text-warning {\n color: #ffc107 !important;\n}\n\na.text-warning:focus, a.text-warning:hover {\n color: #d39e00 !important;\n}\n\n.text-danger {\n color: #dc3545 !important;\n}\n\na.text-danger:focus, a.text-danger:hover {\n color: #bd2130 !important;\n}\n\n.text-light {\n color: #f8f9fa !important;\n}\n\na.text-light:focus, a.text-light:hover {\n color: #dae0e5 !important;\n}\n\n.text-dark {\n color: #343a40 !important;\n}\n\na.text-dark:focus, a.text-dark:hover {\n color: #1d2124 !important;\n}\n\n.text-muted {\n color: #868e96 !important;\n}\n\n.text-hide {\n font: 0/0 a;\n color: transparent;\n text-shadow: none;\n background-color: transparent;\n border: 0;\n}\n\n.visible {\n visibility: visible !important;\n}\n\n.invisible {\n visibility: hidden !important;\n}\n/*# sourceMappingURL=bootstrap.css.map */","// scss-lint:disable QualifyingElement, DuplicateProperty, VendorPrefix\n\n// Reboot\n//\n// Normalization of HTML elements, manually forked from Normalize.css to remove\n// styles targeting irrelevant browsers while applying new styles.\n//\n// Normalize is licensed MIT. https://github.com/necolas/normalize.css\n\n\n// Document\n//\n// 1. Change from `box-sizing: content-box` so that `width` is not affected by `padding` or `border`.\n// 2. Change the default font family in all browsers.\n// 3. Correct the line height in all browsers.\n// 4. Prevent adjustments of font size after orientation changes in IE on Windows Phone and in iOS.\n// 5. Setting @viewport causes scrollbars to overlap content in IE11 and Edge, so\n// we force a non-overlapping, non-auto-hiding scrollbar to counteract.\n// 6. Change the default tap highlight to be completely transparent in iOS.\n\nhtml {\n box-sizing: border-box; // 1\n font-family: sans-serif; // 2\n line-height: 1.15; // 3\n -webkit-text-size-adjust: 100%; // 4\n -ms-text-size-adjust: 100%; // 4\n -ms-overflow-style: scrollbar; // 5\n -webkit-tap-highlight-color: rgba(0,0,0,0); // 6\n}\n\n*,\n*::before,\n*::after {\n box-sizing: inherit; // 1\n}\n\n// IE10+ doesn't honor `<meta name=\"viewport\">` in some cases.\n@at-root {\n @-ms-viewport { width: device-width; }\n}\n\n// Shim for \"new\" HTML5 structural elements to display correctly (IE10, older browsers)\narticle, aside, dialog, figcaption, figure, footer, header, hgroup, main, nav, section {\n display: block;\n}\n\n// Body\n//\n// 1. Remove the margin in all browsers.\n// 2. As a best practice, apply a default `background-color`.\n\nbody {\n margin: 0; // 1\n font-family: $font-family-base;\n font-size: $font-size-base;\n font-weight: $font-weight-base;\n line-height: $line-height-base;\n color: $body-color;\n background-color: $body-bg; // 2\n}\n\n// Suppress the focus outline on elements that cannot be accessed via keyboard.\n// This prevents an unwanted focus outline from appearing around elements that\n// might still respond to pointer events.\n//\n// Credit: https://github.com/suitcss/base\n[tabindex=\"-1\"]:focus {\n outline: none !important;\n}\n\n\n// Content grouping\n//\n// 1. Add the correct box sizing in Firefox.\n// 2. Show the overflow in Edge and IE.\n\nhr {\n box-sizing: content-box; // 1\n height: 0; // 1\n overflow: visible; // 2\n}\n\n\n//\n// Typography\n//\n\n// Remove top margins from headings\n//\n// By default, `<h1>`-`<h6>` all receive top and bottom margins. We nuke the top\n// margin for easier control within type scales as it avoids margin collapsing.\nh1, h2, h3, h4, h5, h6 {\n margin-top: 0;\n margin-bottom: .5rem;\n}\n\n// Reset margins on paragraphs\n//\n// Similarly, the top margin on `<p>`s get reset. However, we also reset the\n// bottom margin to use `rem` units instead of `em`.\np {\n margin-top: 0;\n margin-bottom: 1rem;\n}\n\n// Abbreviations\n//\n// 1. Remove the bottom border in Firefox 39-.\n// 2. Add the correct text decoration in Chrome, Edge, IE, Opera, and Safari.\n// 3. Add explicit cursor to indicate changed behavior.\n// 4. Duplicate behavior to the data-* attribute for our tooltip plugin\n\nabbr[title],\nabbr[data-original-title] { // 4\n text-decoration: underline; // 2\n text-decoration: underline dotted; // 2\n cursor: help; // 3\n border-bottom: 0; // 1\n}\n\naddress {\n margin-bottom: 1rem;\n font-style: normal;\n line-height: inherit;\n}\n\nol,\nul,\ndl {\n margin-top: 0;\n margin-bottom: 1rem;\n}\n\nol ol,\nul ul,\nol ul,\nul ol {\n margin-bottom: 0;\n}\n\ndt {\n font-weight: $dt-font-weight;\n}\n\ndd {\n margin-bottom: .5rem;\n margin-left: 0; // Undo browser default\n}\n\nblockquote {\n margin: 0 0 1rem;\n}\n\ndfn {\n font-style: italic; // Add the correct font style in Android 4.3-\n}\n\nb,\nstrong {\n font-weight: bolder; // Add the correct font weight in Chrome, Edge, and Safari\n}\n\nsmall {\n font-size: 80%; // Add the correct font size in all browsers\n}\n\n//\n// Prevent `sub` and `sup` elements from affecting the line height in\n// all browsers.\n//\n\nsub,\nsup {\n position: relative;\n font-size: 75%;\n line-height: 0;\n vertical-align: baseline;\n}\n\nsub { bottom: -.25em; }\nsup { top: -.5em; }\n\n\n//\n// Links\n//\n\na {\n color: $link-color;\n text-decoration: $link-decoration;\n background-color: transparent; // Remove the gray background on active links in IE 10.\n -webkit-text-decoration-skip: objects; // Remove gaps in links underline in iOS 8+ and Safari 8+.\n\n @include hover {\n color: $link-hover-color;\n text-decoration: $link-hover-decoration;\n }\n}\n\n// And undo these styles for placeholder links/named anchors (without href)\n// which have not been made explicitly keyboard-focusable (without tabindex).\n// It would be more straightforward to just use a[href] in previous block, but that\n// causes specificity issues in many other styles that are too complex to fix.\n// See https://github.com/twbs/bootstrap/issues/19402\n\na:not([href]):not([tabindex]) {\n color: inherit;\n text-decoration: none;\n\n @include hover-focus {\n color: inherit;\n text-decoration: none;\n }\n\n &:focus {\n outline: 0;\n }\n}\n\n\n//\n// Code\n//\n\npre,\ncode,\nkbd,\nsamp {\n font-family: monospace, monospace; // Correct the inheritance and scaling of font size in all browsers.\n font-size: 1em; // Correct the odd `em` font sizing in all browsers.\n}\n\npre {\n // Remove browser default top margin\n margin-top: 0;\n // Reset browser default of `1em` to use `rem`s\n margin-bottom: 1rem;\n // Don't allow content to break outside\n overflow: auto;\n}\n\n\n//\n// Figures\n//\n\nfigure {\n // Apply a consistent margin strategy (matches our type styles).\n margin: 0 0 1rem;\n}\n\n\n//\n// Images and content\n//\n\nimg {\n vertical-align: middle;\n border-style: none; // Remove the border on images inside links in IE 10-.\n}\n\nsvg:not(:root) {\n overflow: hidden; // Hide the overflow in IE\n}\n\n\n// Avoid 300ms click delay on touch devices that support the `touch-action` CSS property.\n//\n// In particular, unlike most other browsers, IE11+Edge on Windows 10 on touch devices and IE Mobile 10-11\n// DON'T remove the click delay when `<meta name=\"viewport\" content=\"width=device-width\">` is present.\n// However, they DO support removing the click delay via `touch-action: manipulation`.\n// See:\n// * https://v4-alpha.getbootstrap.com/content/reboot/#click-delay-optimization-for-touch\n// * http://caniuse.com/#feat=css-touch-action\n// * https://patrickhlauke.github.io/touch/tests/results/#suppressing-300ms-delay\n\na,\narea,\nbutton,\n[role=\"button\"],\ninput,\nlabel,\nselect,\nsummary,\ntextarea {\n touch-action: manipulation;\n}\n\n\n//\n// Tables\n//\n\ntable {\n border-collapse: collapse; // Prevent double borders\n}\n\ncaption {\n padding-top: $table-cell-padding;\n padding-bottom: $table-cell-padding;\n color: $text-muted;\n text-align: left;\n caption-side: bottom;\n}\n\nth {\n // Matches default `<td>` alignment\n text-align: left;\n}\n\n\n//\n// Forms\n//\n\nlabel {\n // Allow labels to use `margin` for spacing.\n display: inline-block;\n margin-bottom: .5rem;\n}\n\n// Work around a Firefox/IE bug where the transparent `button` background\n// results in a loss of the default `button` focus styles.\n//\n// Credit: https://github.com/suitcss/base/\nbutton:focus {\n outline: 1px dotted;\n outline: 5px auto -webkit-focus-ring-color;\n}\n\ninput,\nbutton,\nselect,\noptgroup,\ntextarea {\n margin: 0; // Remove the margin in Firefox and Safari\n font-family: inherit;\n font-size: inherit;\n line-height: inherit;\n}\n\nbutton,\ninput {\n overflow: visible; // Show the overflow in Edge\n}\n\nbutton,\nselect {\n text-transform: none; // Remove the inheritance of text transform in Firefox\n}\n\n// 1. Prevent a WebKit bug where (2) destroys native `audio` and `video`\n// controls in Android 4.\n// 2. Correct the inability to style clickable types in iOS and Safari.\nbutton,\nhtml [type=\"button\"], // 1\n[type=\"reset\"],\n[type=\"submit\"] {\n -webkit-appearance: button; // 2\n}\n\n// Remove inner border and padding from Firefox, but don't restore the outline like Normalize.\nbutton::-moz-focus-inner,\n[type=\"button\"]::-moz-focus-inner,\n[type=\"reset\"]::-moz-focus-inner,\n[type=\"submit\"]::-moz-focus-inner {\n padding: 0;\n border-style: none;\n}\n\ninput[type=\"radio\"],\ninput[type=\"checkbox\"] {\n box-sizing: border-box; // 1. Add the correct box sizing in IE 10-\n padding: 0; // 2. Remove the padding in IE 10-\n}\n\n\ninput[type=\"date\"],\ninput[type=\"time\"],\ninput[type=\"datetime-local\"],\ninput[type=\"month\"] {\n // Remove the default appearance of temporal inputs to avoid a Mobile Safari\n // bug where setting a custom line-height prevents text from being vertically\n // centered within the input.\n // See https://bugs.webkit.org/show_bug.cgi?id=139848\n // and https://github.com/twbs/bootstrap/issues/11266\n -webkit-appearance: listbox;\n}\n\ntextarea {\n overflow: auto; // Remove the default vertical scrollbar in IE.\n // Textareas should really only resize vertically so they don't break their (horizontal) containers.\n resize: vertical;\n}\n\nfieldset {\n // Browsers set a default `min-width: min-content;` on fieldsets,\n // unlike e.g. `<div>`s, which have `min-width: 0;` by default.\n // So we reset that to ensure fieldsets behave more like a standard block element.\n // See https://github.com/twbs/bootstrap/issues/12359\n // and https://html.spec.whatwg.org/multipage/#the-fieldset-and-legend-elements\n min-width: 0;\n // Reset the default outline behavior of fieldsets so they don't affect page layout.\n padding: 0;\n margin: 0;\n border: 0;\n}\n\n// 1. Correct the text wrapping in Edge and IE.\n// 2. Correct the color inheritance from `fieldset` elements in IE.\nlegend {\n display: block;\n width: 100%;\n max-width: 100%; // 1\n padding: 0;\n margin-bottom: .5rem;\n font-size: 1.5rem;\n line-height: inherit;\n color: inherit; // 2\n white-space: normal; // 1\n}\n\nprogress {\n vertical-align: baseline; // Add the correct vertical alignment in Chrome, Firefox, and Opera.\n}\n\n// Correct the cursor style of increment and decrement buttons in Chrome.\n[type=\"number\"]::-webkit-inner-spin-button,\n[type=\"number\"]::-webkit-outer-spin-button {\n height: auto;\n}\n\n[type=\"search\"] {\n // This overrides the extra rounded corners on search inputs in iOS so that our\n // `.form-control` class can properly style them. Note that this cannot simply\n // be added to `.form-control` as it's not specific enough. For details, see\n // https://github.com/twbs/bootstrap/issues/11586.\n outline-offset: -2px; // 2. Correct the outline style in Safari.\n -webkit-appearance: none;\n}\n\n//\n// Remove the inner padding and cancel buttons in Chrome and Safari on macOS.\n//\n\n[type=\"search\"]::-webkit-search-cancel-button,\n[type=\"search\"]::-webkit-search-decoration {\n -webkit-appearance: none;\n}\n\n//\n// 1. Correct the inability to style clickable types in iOS and Safari.\n// 2. Change font properties to `inherit` in Safari.\n//\n\n::-webkit-file-upload-button {\n font: inherit; // 2\n -webkit-appearance: button; // 1\n}\n\n//\n// Correct element displays\n//\n\noutput {\n display: inline-block;\n}\n\nsummary {\n display: list-item; // Add the correct display in all browsers\n}\n\ntemplate {\n display: none; // Add the correct display in IE\n}\n\n// Always hide an element with the `hidden` HTML attribute (from PureCSS).\n// Needed for proper display in IE 10-.\n[hidden] {\n display: none !important;\n}\n","/*!\n * Bootstrap v4.0.0-beta (https://getbootstrap.com)\n * Copyright 2011-2017 The Bootstrap Authors\n * Copyright 2011-2017 Twitter, Inc.\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)\n */\n@media print {\n *,\n *::before,\n *::after {\n text-shadow: none !important;\n box-shadow: none !important;\n }\n a,\n a:visited {\n text-decoration: underline;\n }\n abbr[title]::after {\n content: \" (\" attr(title) \")\";\n }\n pre {\n white-space: pre-wrap !important;\n }\n pre,\n blockquote {\n border: 1px solid #999;\n page-break-inside: avoid;\n }\n thead {\n display: table-header-group;\n }\n tr,\n img {\n page-break-inside: avoid;\n }\n p,\n h2,\n h3 {\n orphans: 3;\n widows: 3;\n }\n h2,\n h3 {\n page-break-after: avoid;\n }\n .navbar {\n display: none;\n }\n .badge {\n border: 1px solid #000;\n }\n .table {\n border-collapse: collapse !important;\n }\n .table td,\n .table th {\n background-color: #fff !important;\n }\n .table-bordered th,\n .table-bordered td {\n border: 1px solid #ddd !important;\n }\n}\n\nhtml {\n box-sizing: border-box;\n font-family: sans-serif;\n line-height: 1.15;\n -webkit-text-size-adjust: 100%;\n -ms-text-size-adjust: 100%;\n -ms-overflow-style: scrollbar;\n -webkit-tap-highlight-color: transparent;\n}\n\n*,\n*::before,\n*::after {\n box-sizing: inherit;\n}\n\n@-ms-viewport {\n width: device-width;\n}\n\narticle, aside, dialog, figcaption, figure, footer, header, hgroup, main, nav, section {\n display: block;\n}\n\nbody {\n margin: 0;\n font-family: -apple-system, BlinkMacSystemFont, \"Segoe UI\", Roboto, \"Helvetica Neue\", Arial, sans-serif;\n font-size: 1rem;\n font-weight: normal;\n line-height: 1.5;\n color: #212529;\n background-color: #fff;\n}\n\n[tabindex=\"-1\"]:focus {\n outline: none !important;\n}\n\nhr {\n box-sizing: content-box;\n height: 0;\n overflow: visible;\n}\n\nh1, h2, h3, h4, h5, h6 {\n margin-top: 0;\n margin-bottom: .5rem;\n}\n\np {\n margin-top: 0;\n margin-bottom: 1rem;\n}\n\nabbr[title],\nabbr[data-original-title] {\n text-decoration: underline;\n text-decoration: underline dotted;\n cursor: help;\n border-bottom: 0;\n}\n\naddress {\n margin-bottom: 1rem;\n font-style: normal;\n line-height: inherit;\n}\n\nol,\nul,\ndl {\n margin-top: 0;\n margin-bottom: 1rem;\n}\n\nol ol,\nul ul,\nol ul,\nul ol {\n margin-bottom: 0;\n}\n\ndt {\n font-weight: bold;\n}\n\ndd {\n margin-bottom: .5rem;\n margin-left: 0;\n}\n\nblockquote {\n margin: 0 0 1rem;\n}\n\ndfn {\n font-style: italic;\n}\n\nb,\nstrong {\n font-weight: bolder;\n}\n\nsmall {\n font-size: 80%;\n}\n\nsub,\nsup {\n position: relative;\n font-size: 75%;\n line-height: 0;\n vertical-align: baseline;\n}\n\nsub {\n bottom: -.25em;\n}\n\nsup {\n top: -.5em;\n}\n\na {\n color: #007bff;\n text-decoration: none;\n background-color: transparent;\n -webkit-text-decoration-skip: objects;\n}\n\na:hover {\n color: #0056b3;\n text-decoration: underline;\n}\n\na:not([href]):not([tabindex]) {\n color: inherit;\n text-decoration: none;\n}\n\na:not([href]):not([tabindex]):focus, a:not([href]):not([tabindex]):hover {\n color: inherit;\n text-decoration: none;\n}\n\na:not([href]):not([tabindex]):focus {\n outline: 0;\n}\n\npre,\ncode,\nkbd,\nsamp {\n font-family: monospace, monospace;\n font-size: 1em;\n}\n\npre {\n margin-top: 0;\n margin-bottom: 1rem;\n overflow: auto;\n}\n\nfigure {\n margin: 0 0 1rem;\n}\n\nimg {\n vertical-align: middle;\n border-style: none;\n}\n\nsvg:not(:root) {\n overflow: hidden;\n}\n\na,\narea,\nbutton,\n[role=\"button\"],\ninput,\nlabel,\nselect,\nsummary,\ntextarea {\n touch-action: manipulation;\n}\n\ntable {\n border-collapse: collapse;\n}\n\ncaption {\n padding-top: 0.75rem;\n padding-bottom: 0.75rem;\n color: #868e96;\n text-align: left;\n caption-side: bottom;\n}\n\nth {\n text-align: left;\n}\n\nlabel {\n display: inline-block;\n margin-bottom: .5rem;\n}\n\nbutton:focus {\n outline: 1px dotted;\n outline: 5px auto -webkit-focus-ring-color;\n}\n\ninput,\nbutton,\nselect,\noptgroup,\ntextarea {\n margin: 0;\n font-family: inherit;\n font-size: inherit;\n line-height: inherit;\n}\n\nbutton,\ninput {\n overflow: visible;\n}\n\nbutton,\nselect {\n text-transform: none;\n}\n\nbutton,\nhtml [type=\"button\"],\n[type=\"reset\"],\n[type=\"submit\"] {\n -webkit-appearance: button;\n}\n\nbutton::-moz-focus-inner,\n[type=\"button\"]::-moz-focus-inner,\n[type=\"reset\"]::-moz-focus-inner,\n[type=\"submit\"]::-moz-focus-inner {\n padding: 0;\n border-style: none;\n}\n\ninput[type=\"radio\"],\ninput[type=\"checkbox\"] {\n box-sizing: border-box;\n padding: 0;\n}\n\ninput[type=\"date\"],\ninput[type=\"time\"],\ninput[type=\"datetime-local\"],\ninput[type=\"month\"] {\n -webkit-appearance: listbox;\n}\n\ntextarea {\n overflow: auto;\n resize: vertical;\n}\n\nfieldset {\n min-width: 0;\n padding: 0;\n margin: 0;\n border: 0;\n}\n\nlegend {\n display: block;\n width: 100%;\n max-width: 100%;\n padding: 0;\n margin-bottom: .5rem;\n font-size: 1.5rem;\n line-height: inherit;\n color: inherit;\n white-space: normal;\n}\n\nprogress {\n vertical-align: baseline;\n}\n\n[type=\"number\"]::-webkit-inner-spin-button,\n[type=\"number\"]::-webkit-outer-spin-button {\n height: auto;\n}\n\n[type=\"search\"] {\n outline-offset: -2px;\n -webkit-appearance: none;\n}\n\n[type=\"search\"]::-webkit-search-cancel-button,\n[type=\"search\"]::-webkit-search-decoration {\n -webkit-appearance: none;\n}\n\n::-webkit-file-upload-button {\n font: inherit;\n -webkit-appearance: button;\n}\n\noutput {\n display: inline-block;\n}\n\nsummary {\n display: list-item;\n}\n\ntemplate {\n display: none;\n}\n\n[hidden] {\n display: none !important;\n}\n\nh1, h2, h3, h4, h5, h6,\n.h1, .h2, .h3, .h4, .h5, .h6 {\n margin-bottom: 0.5rem;\n font-family: inherit;\n font-weight: 500;\n line-height: 1.1;\n color: inherit;\n}\n\nh1, .h1 {\n font-size: 2.5rem;\n}\n\nh2, .h2 {\n font-size: 2rem;\n}\n\nh3, .h3 {\n font-size: 1.75rem;\n}\n\nh4, .h4 {\n font-size: 1.5rem;\n}\n\nh5, .h5 {\n font-size: 1.25rem;\n}\n\nh6, .h6 {\n font-size: 1rem;\n}\n\n.lead {\n font-size: 1.25rem;\n font-weight: 300;\n}\n\n.display-1 {\n font-size: 6rem;\n font-weight: 300;\n line-height: 1.1;\n}\n\n.display-2 {\n font-size: 5.5rem;\n font-weight: 300;\n line-height: 1.1;\n}\n\n.display-3 {\n font-size: 4.5rem;\n font-weight: 300;\n line-height: 1.1;\n}\n\n.display-4 {\n font-size: 3.5rem;\n font-weight: 300;\n line-height: 1.1;\n}\n\nhr {\n margin-top: 1rem;\n margin-bottom: 1rem;\n border: 0;\n border-top: 1px solid rgba(0, 0, 0, 0.1);\n}\n\nsmall,\n.small {\n font-size: 80%;\n font-weight: normal;\n}\n\nmark,\n.mark {\n padding: 0.2em;\n background-color: #fcf8e3;\n}\n\n.list-unstyled {\n padding-left: 0;\n list-style: none;\n}\n\n.list-inline {\n padding-left: 0;\n list-style: none;\n}\n\n.list-inline-item {\n display: inline-block;\n}\n\n.list-inline-item:not(:last-child) {\n margin-right: 5px;\n}\n\n.initialism {\n font-size: 90%;\n text-transform: uppercase;\n}\n\n.blockquote {\n margin-bottom: 1rem;\n font-size: 1.25rem;\n}\n\n.blockquote-footer {\n display: block;\n font-size: 80%;\n color: #868e96;\n}\n\n.blockquote-footer::before {\n content: \"\\2014 \\00A0\";\n}\n\n.img-fluid {\n max-width: 100%;\n height: auto;\n}\n\n.img-thumbnail {\n padding: 0.25rem;\n background-color: #fff;\n border: 1px solid #ddd;\n border-radius: 0.25rem;\n transition: all 0.2s ease-in-out;\n max-width: 100%;\n height: auto;\n}\n\n.figure {\n display: inline-block;\n}\n\n.figure-img {\n margin-bottom: 0.5rem;\n line-height: 1;\n}\n\n.figure-caption {\n font-size: 90%;\n color: #868e96;\n}\n\ncode,\nkbd,\npre,\nsamp {\n font-family: Menlo, Monaco, Consolas, \"Liberation Mono\", \"Courier New\", monospace;\n}\n\ncode {\n padding: 0.2rem 0.4rem;\n font-size: 90%;\n color: #bd4147;\n background-color: #f8f9fa;\n border-radius: 0.25rem;\n}\n\na > code {\n padding: 0;\n color: inherit;\n background-color: inherit;\n}\n\nkbd {\n padding: 0.2rem 0.4rem;\n font-size: 90%;\n color: #fff;\n background-color: #212529;\n border-radius: 0.2rem;\n}\n\nkbd kbd {\n padding: 0;\n font-size: 100%;\n font-weight: bold;\n}\n\npre {\n display: block;\n margin-top: 0;\n margin-bottom: 1rem;\n font-size: 90%;\n color: #212529;\n}\n\npre code {\n padding: 0;\n font-size: inherit;\n color: inherit;\n background-color: transparent;\n border-radius: 0;\n}\n\n.pre-scrollable {\n max-height: 340px;\n overflow-y: scroll;\n}\n\n.container {\n margin-right: auto;\n margin-left: auto;\n padding-right: 15px;\n padding-left: 15px;\n width: 100%;\n}\n\n@media (min-width: 576px) {\n .container {\n max-width: 540px;\n }\n}\n\n@media (min-width: 768px) {\n .container {\n max-width: 720px;\n }\n}\n\n@media (min-width: 992px) {\n .container {\n max-width: 960px;\n }\n}\n\n@media (min-width: 1200px) {\n .container {\n max-width: 1140px;\n }\n}\n\n.container-fluid {\n width: 100%;\n margin-right: auto;\n margin-left: auto;\n padding-right: 15px;\n padding-left: 15px;\n width: 100%;\n}\n\n.row {\n display: flex;\n flex-wrap: wrap;\n margin-right: -15px;\n margin-left: -15px;\n}\n\n.no-gutters {\n margin-right: 0;\n margin-left: 0;\n}\n\n.no-gutters > .col,\n.no-gutters > [class*=\"col-\"] {\n padding-right: 0;\n padding-left: 0;\n}\n\n.col-1, .col-2, .col-3, .col-4, .col-5, .col-6, .col-7, .col-8, .col-9, .col-10, .col-11, .col-12, .col,\n.col-auto, .col-sm-1, .col-sm-2, .col-sm-3, .col-sm-4, .col-sm-5, .col-sm-6, .col-sm-7, .col-sm-8, .col-sm-9, .col-sm-10, .col-sm-11, .col-sm-12, .col-sm,\n.col-sm-auto, .col-md-1, .col-md-2, .col-md-3, .col-md-4, .col-md-5, .col-md-6, .col-md-7, .col-md-8, .col-md-9, .col-md-10, .col-md-11, .col-md-12, .col-md,\n.col-md-auto, .col-lg-1, .col-lg-2, .col-lg-3, .col-lg-4, .col-lg-5, .col-lg-6, .col-lg-7, .col-lg-8, .col-lg-9, .col-lg-10, .col-lg-11, .col-lg-12, .col-lg,\n.col-lg-auto, .col-xl-1, .col-xl-2, .col-xl-3, .col-xl-4, .col-xl-5, .col-xl-6, .col-xl-7, .col-xl-8, .col-xl-9, .col-xl-10, .col-xl-11, .col-xl-12, .col-xl,\n.col-xl-auto {\n position: relative;\n width: 100%;\n min-height: 1px;\n padding-right: 15px;\n padding-left: 15px;\n}\n\n.col {\n flex-basis: 0;\n flex-grow: 1;\n max-width: 100%;\n}\n\n.col-auto {\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n}\n\n.col-1 {\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n}\n\n.col-2 {\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n}\n\n.col-3 {\n flex: 0 0 25%;\n max-width: 25%;\n}\n\n.col-4 {\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n}\n\n.col-5 {\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n}\n\n.col-6 {\n flex: 0 0 50%;\n max-width: 50%;\n}\n\n.col-7 {\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n}\n\n.col-8 {\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n}\n\n.col-9 {\n flex: 0 0 75%;\n max-width: 75%;\n}\n\n.col-10 {\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n}\n\n.col-11 {\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n}\n\n.col-12 {\n flex: 0 0 100%;\n max-width: 100%;\n}\n\n.order-1 {\n order: 1;\n}\n\n.order-2 {\n order: 2;\n}\n\n.order-3 {\n order: 3;\n}\n\n.order-4 {\n order: 4;\n}\n\n.order-5 {\n order: 5;\n}\n\n.order-6 {\n order: 6;\n}\n\n.order-7 {\n order: 7;\n}\n\n.order-8 {\n order: 8;\n}\n\n.order-9 {\n order: 9;\n}\n\n.order-10 {\n order: 10;\n}\n\n.order-11 {\n order: 11;\n}\n\n.order-12 {\n order: 12;\n}\n\n@media (min-width: 576px) {\n .col-sm {\n flex-basis: 0;\n flex-grow: 1;\n max-width: 100%;\n }\n .col-sm-auto {\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n }\n .col-sm-1 {\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n }\n .col-sm-2 {\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n }\n .col-sm-3 {\n flex: 0 0 25%;\n max-width: 25%;\n }\n .col-sm-4 {\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n }\n .col-sm-5 {\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n }\n .col-sm-6 {\n flex: 0 0 50%;\n max-width: 50%;\n }\n .col-sm-7 {\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n }\n .col-sm-8 {\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n }\n .col-sm-9 {\n flex: 0 0 75%;\n max-width: 75%;\n }\n .col-sm-10 {\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n }\n .col-sm-11 {\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n }\n .col-sm-12 {\n flex: 0 0 100%;\n max-width: 100%;\n }\n .order-sm-1 {\n order: 1;\n }\n .order-sm-2 {\n order: 2;\n }\n .order-sm-3 {\n order: 3;\n }\n .order-sm-4 {\n order: 4;\n }\n .order-sm-5 {\n order: 5;\n }\n .order-sm-6 {\n order: 6;\n }\n .order-sm-7 {\n order: 7;\n }\n .order-sm-8 {\n order: 8;\n }\n .order-sm-9 {\n order: 9;\n }\n .order-sm-10 {\n order: 10;\n }\n .order-sm-11 {\n order: 11;\n }\n .order-sm-12 {\n order: 12;\n }\n}\n\n@media (min-width: 768px) {\n .col-md {\n flex-basis: 0;\n flex-grow: 1;\n max-width: 100%;\n }\n .col-md-auto {\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n }\n .col-md-1 {\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n }\n .col-md-2 {\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n }\n .col-md-3 {\n flex: 0 0 25%;\n max-width: 25%;\n }\n .col-md-4 {\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n }\n .col-md-5 {\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n }\n .col-md-6 {\n flex: 0 0 50%;\n max-width: 50%;\n }\n .col-md-7 {\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n }\n .col-md-8 {\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n }\n .col-md-9 {\n flex: 0 0 75%;\n max-width: 75%;\n }\n .col-md-10 {\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n }\n .col-md-11 {\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n }\n .col-md-12 {\n flex: 0 0 100%;\n max-width: 100%;\n }\n .order-md-1 {\n order: 1;\n }\n .order-md-2 {\n order: 2;\n }\n .order-md-3 {\n order: 3;\n }\n .order-md-4 {\n order: 4;\n }\n .order-md-5 {\n order: 5;\n }\n .order-md-6 {\n order: 6;\n }\n .order-md-7 {\n order: 7;\n }\n .order-md-8 {\n order: 8;\n }\n .order-md-9 {\n order: 9;\n }\n .order-md-10 {\n order: 10;\n }\n .order-md-11 {\n order: 11;\n }\n .order-md-12 {\n order: 12;\n }\n}\n\n@media (min-width: 992px) {\n .col-lg {\n flex-basis: 0;\n flex-grow: 1;\n max-width: 100%;\n }\n .col-lg-auto {\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n }\n .col-lg-1 {\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n }\n .col-lg-2 {\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n }\n .col-lg-3 {\n flex: 0 0 25%;\n max-width: 25%;\n }\n .col-lg-4 {\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n }\n .col-lg-5 {\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n }\n .col-lg-6 {\n flex: 0 0 50%;\n max-width: 50%;\n }\n .col-lg-7 {\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n }\n .col-lg-8 {\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n }\n .col-lg-9 {\n flex: 0 0 75%;\n max-width: 75%;\n }\n .col-lg-10 {\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n }\n .col-lg-11 {\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n }\n .col-lg-12 {\n flex: 0 0 100%;\n max-width: 100%;\n }\n .order-lg-1 {\n order: 1;\n }\n .order-lg-2 {\n order: 2;\n }\n .order-lg-3 {\n order: 3;\n }\n .order-lg-4 {\n order: 4;\n }\n .order-lg-5 {\n order: 5;\n }\n .order-lg-6 {\n order: 6;\n }\n .order-lg-7 {\n order: 7;\n }\n .order-lg-8 {\n order: 8;\n }\n .order-lg-9 {\n order: 9;\n }\n .order-lg-10 {\n order: 10;\n }\n .order-lg-11 {\n order: 11;\n }\n .order-lg-12 {\n order: 12;\n }\n}\n\n@media (min-width: 1200px) {\n .col-xl {\n flex-basis: 0;\n flex-grow: 1;\n max-width: 100%;\n }\n .col-xl-auto {\n flex: 0 0 auto;\n width: auto;\n max-width: none;\n }\n .col-xl-1 {\n flex: 0 0 8.333333%;\n max-width: 8.333333%;\n }\n .col-xl-2 {\n flex: 0 0 16.666667%;\n max-width: 16.666667%;\n }\n .col-xl-3 {\n flex: 0 0 25%;\n max-width: 25%;\n }\n .col-xl-4 {\n flex: 0 0 33.333333%;\n max-width: 33.333333%;\n }\n .col-xl-5 {\n flex: 0 0 41.666667%;\n max-width: 41.666667%;\n }\n .col-xl-6 {\n flex: 0 0 50%;\n max-width: 50%;\n }\n .col-xl-7 {\n flex: 0 0 58.333333%;\n max-width: 58.333333%;\n }\n .col-xl-8 {\n flex: 0 0 66.666667%;\n max-width: 66.666667%;\n }\n .col-xl-9 {\n flex: 0 0 75%;\n max-width: 75%;\n }\n .col-xl-10 {\n flex: 0 0 83.333333%;\n max-width: 83.333333%;\n }\n .col-xl-11 {\n flex: 0 0 91.666667%;\n max-width: 91.666667%;\n }\n .col-xl-12 {\n flex: 0 0 100%;\n max-width: 100%;\n }\n .order-xl-1 {\n order: 1;\n }\n .order-xl-2 {\n order: 2;\n }\n .order-xl-3 {\n order: 3;\n }\n .order-xl-4 {\n order: 4;\n }\n .order-xl-5 {\n order: 5;\n }\n .order-xl-6 {\n order: 6;\n }\n .order-xl-7 {\n order: 7;\n }\n .order-xl-8 {\n order: 8;\n }\n .order-xl-9 {\n order: 9;\n }\n .order-xl-10 {\n order: 10;\n }\n .order-xl-11 {\n order: 11;\n }\n .order-xl-12 {\n order: 12;\n }\n}\n\n.table {\n width: 100%;\n max-width: 100%;\n margin-bottom: 1rem;\n background-color: transparent;\n}\n\n.table th,\n.table td {\n padding: 0.75rem;\n vertical-align: top;\n border-top: 1px solid #e9ecef;\n}\n\n.table thead th {\n vertical-align: bottom;\n border-bottom: 2px solid #e9ecef;\n}\n\n.table tbody + tbody {\n border-top: 2px solid #e9ecef;\n}\n\n.table .table {\n background-color: #fff;\n}\n\n.table-sm th,\n.table-sm td {\n padding: 0.3rem;\n}\n\n.table-bordered {\n border: 1px solid #e9ecef;\n}\n\n.table-bordered th,\n.table-bordered td {\n border: 1px solid #e9ecef;\n}\n\n.table-bordered thead th,\n.table-bordered thead td {\n border-bottom-width: 2px;\n}\n\n.table-striped tbody tr:nth-of-type(odd) {\n background-color: rgba(0, 0, 0, 0.05);\n}\n\n.table-hover tbody tr:hover {\n background-color: rgba(0, 0, 0, 0.075);\n}\n\n.table-primary,\n.table-primary > th,\n.table-primary > td {\n background-color: #b8daff;\n}\n\n.table-hover .table-primary:hover {\n background-color: #9fcdff;\n}\n\n.table-hover .table-primary:hover > td,\n.table-hover .table-primary:hover > th {\n background-color: #9fcdff;\n}\n\n.table-secondary,\n.table-secondary > th,\n.table-secondary > td {\n background-color: #dddfe2;\n}\n\n.table-hover .table-secondary:hover {\n background-color: #cfd2d6;\n}\n\n.table-hover .table-secondary:hover > td,\n.table-hover .table-secondary:hover > th {\n background-color: #cfd2d6;\n}\n\n.table-success,\n.table-success > th,\n.table-success > td {\n background-color: #c3e6cb;\n}\n\n.table-hover .table-success:hover {\n background-color: #b1dfbb;\n}\n\n.table-hover .table-success:hover > td,\n.table-hover .table-success:hover > th {\n background-color: #b1dfbb;\n}\n\n.table-info,\n.table-info > th,\n.table-info > td {\n background-color: #bee5eb;\n}\n\n.table-hover .table-info:hover {\n background-color: #abdde5;\n}\n\n.table-hover .table-info:hover > td,\n.table-hover .table-info:hover > th {\n background-color: #abdde5;\n}\n\n.table-warning,\n.table-warning > th,\n.table-warning > td {\n background-color: #ffeeba;\n}\n\n.table-hover .table-warning:hover {\n background-color: #ffe8a1;\n}\n\n.table-hover .table-warning:hover > td,\n.table-hover .table-warning:hover > th {\n background-color: #ffe8a1;\n}\n\n.table-danger,\n.table-danger > th,\n.table-danger > td {\n background-color: #f5c6cb;\n}\n\n.table-hover .table-danger:hover {\n background-color: #f1b0b7;\n}\n\n.table-hover .table-danger:hover > td,\n.table-hover .table-danger:hover > th {\n background-color: #f1b0b7;\n}\n\n.table-light,\n.table-light > th,\n.table-light > td {\n background-color: #fdfdfe;\n}\n\n.table-hover .table-light:hover {\n background-color: #ececf6;\n}\n\n.table-hover .table-light:hover > td,\n.table-hover .table-light:hover > th {\n background-color: #ececf6;\n}\n\n.table-dark,\n.table-dark > th,\n.table-dark > td {\n background-color: #c6c8ca;\n}\n\n.table-hover .table-dark:hover {\n background-color: #b9bbbe;\n}\n\n.table-hover .table-dark:hover > td,\n.table-hover .table-dark:hover > th {\n background-color: #b9bbbe;\n}\n\n.table-active,\n.table-active > th,\n.table-active > td {\n background-color: rgba(0, 0, 0, 0.075);\n}\n\n.table-hover .table-active:hover {\n background-color: rgba(0, 0, 0, 0.075);\n}\n\n.table-hover .table-active:hover > td,\n.table-hover .table-active:hover > th {\n background-color: rgba(0, 0, 0, 0.075);\n}\n\n.thead-inverse th {\n color: #fff;\n background-color: #212529;\n}\n\n.thead-default th {\n color: #495057;\n background-color: #e9ecef;\n}\n\n.table-inverse {\n color: #fff;\n background-color: #212529;\n}\n\n.table-inverse th,\n.table-inverse td,\n.table-inverse thead th {\n border-color: #32383e;\n}\n\n.table-inverse.table-bordered {\n border: 0;\n}\n\n.table-inverse.table-striped tbody tr:nth-of-type(odd) {\n background-color: rgba(255, 255, 255, 0.05);\n}\n\n.table-inverse.table-hover tbody tr:hover {\n background-color: rgba(255, 255, 255, 0.075);\n}\n\n@media (max-width: 991px) {\n .table-responsive {\n display: block;\n width: 100%;\n overflow-x: auto;\n -ms-overflow-style: -ms-autohiding-scrollbar;\n }\n .table-responsive.table-bordered {\n border: 0;\n }\n}\n\n.form-control {\n display: block;\n width: 100%;\n padding: 0.5rem 0.75rem;\n font-size: 1rem;\n line-height: 1.25;\n color: #495057;\n background-color: #fff;\n background-image: none;\n background-clip: padding-box;\n border: 1px solid rgba(0, 0, 0, 0.15);\n border-radius: 0.25rem;\n transition: border-color ease-in-out 0.15s, box-shadow ease-in-out 0.15s;\n}\n\n.form-control::-ms-expand {\n background-color: transparent;\n border: 0;\n}\n\n.form-control:focus {\n color: #495057;\n background-color: #fff;\n border-color: #80bdff;\n outline: none;\n}\n\n.form-control::placeholder {\n color: #868e96;\n opacity: 1;\n}\n\n.form-control:disabled, .form-control[readonly] {\n background-color: #e9ecef;\n opacity: 1;\n}\n\nselect.form-control:not([size]):not([multiple]) {\n height: calc(2.25rem + 2px);\n}\n\nselect.form-control:focus::-ms-value {\n color: #495057;\n background-color: #fff;\n}\n\n.form-control-file,\n.form-control-range {\n display: block;\n}\n\n.col-form-label {\n padding-top: calc(0.5rem - 1px * 2);\n padding-bottom: calc(0.5rem - 1px * 2);\n margin-bottom: 0;\n}\n\n.col-form-label-lg {\n padding-top: calc(0.5rem - 1px * 2);\n padding-bottom: calc(0.5rem - 1px * 2);\n font-size: 1.25rem;\n}\n\n.col-form-label-sm {\n padding-top: calc(0.25rem - 1px * 2);\n padding-bottom: calc(0.25rem - 1px * 2);\n font-size: 0.875rem;\n}\n\n.col-form-legend {\n padding-top: 0.5rem;\n padding-bottom: 0.5rem;\n margin-bottom: 0;\n font-size: 1rem;\n}\n\n.form-control-plaintext {\n padding-top: 0.5rem;\n padding-bottom: 0.5rem;\n margin-bottom: 0;\n line-height: 1.25;\n border: solid transparent;\n border-width: 1px 0;\n}\n\n.form-control-plaintext.form-control-sm, .input-group-sm > .form-control-plaintext.form-control,\n.input-group-sm > .form-control-plaintext.input-group-addon,\n.input-group-sm > .input-group-btn > .form-control-plaintext.btn, .form-control-plaintext.form-control-lg, .input-group-lg > .form-control-plaintext.form-control,\n.input-group-lg > .form-control-plaintext.input-group-addon,\n.input-group-lg > .input-group-btn > .form-control-plaintext.btn {\n padding-right: 0;\n padding-left: 0;\n}\n\n.form-control-sm, .input-group-sm > .form-control,\n.input-group-sm > .input-group-addon,\n.input-group-sm > .input-group-btn > .btn {\n padding: 0.25rem 0.5rem;\n font-size: 0.875rem;\n line-height: 1.5;\n border-radius: 0.2rem;\n}\n\nselect.form-control-sm:not([size]):not([multiple]), .input-group-sm > select.form-control:not([size]):not([multiple]),\n.input-group-sm > select.input-group-addon:not([size]):not([multiple]),\n.input-group-sm > .input-group-btn > select.btn:not([size]):not([multiple]) {\n height: calc(1.8125rem + 2px);\n}\n\n.form-control-lg, .input-group-lg > .form-control,\n.input-group-lg > .input-group-addon,\n.input-group-lg > .input-group-btn > .btn {\n padding: 0.5rem 1rem;\n font-size: 1.25rem;\n line-height: 1.5;\n border-radius: 0.3rem;\n}\n\nselect.form-control-lg:not([size]):not([multiple]), .input-group-lg > select.form-control:not([size]):not([multiple]),\n.input-group-lg > select.input-group-addon:not([size]):not([multiple]),\n.input-group-lg > .input-group-btn > select.btn:not([size]):not([multiple]) {\n height: calc(2.3125rem + 2px);\n}\n\n.form-group {\n margin-bottom: 1rem;\n}\n\n.form-text {\n display: block;\n margin-top: 0.25rem;\n}\n\n.form-row {\n display: flex;\n flex-wrap: wrap;\n margin-right: -5px;\n margin-left: -5px;\n}\n\n.form-row > .col,\n.form-row > [class*=\"col-\"] {\n padding-right: 5px;\n padding-left: 5px;\n}\n\n.form-check {\n position: relative;\n display: block;\n margin-bottom: 0.5rem;\n}\n\n.form-check.disabled .form-check-label {\n color: #868e96;\n}\n\n.form-check-label {\n padding-left: 1.25rem;\n margin-bottom: 0;\n}\n\n.form-check-input {\n position: absolute;\n margin-top: 0.25rem;\n margin-left: -1.25rem;\n}\n\n.form-check-input:only-child {\n position: static;\n}\n\n.form-check-inline {\n display: inline-block;\n}\n\n.form-check-inline .form-check-label {\n vertical-align: middle;\n}\n\n.form-check-inline + .form-check-inline {\n margin-left: 0.75rem;\n}\n\n.invalid-feedback {\n display: none;\n margin-top: .25rem;\n font-size: .875rem;\n color: #dc3545;\n}\n\n.invalid-tooltip {\n position: absolute;\n top: 100%;\n z-index: 5;\n display: none;\n width: 250px;\n padding: .5rem;\n margin-top: .1rem;\n font-size: .875rem;\n line-height: 1;\n color: #fff;\n background-color: rgba(220, 53, 69, 0.8);\n border-radius: .2rem;\n}\n\n.was-validated .form-control:valid, .form-control.is-valid, .was-validated\n.custom-select:valid,\n.custom-select.is-valid {\n border-color: #28a745;\n}\n\n.was-validated .form-control:valid:focus, .form-control.is-valid:focus, .was-validated\n.custom-select:valid:focus,\n.custom-select.is-valid:focus {\n box-shadow: 0 0 0 0.2rem rgba(40, 167, 69, 0.25);\n}\n\n.was-validated .form-control:valid ~ .invalid-feedback,\n.was-validated .form-control:valid ~ .invalid-tooltip, .form-control.is-valid ~ .invalid-feedback,\n.form-control.is-valid ~ .invalid-tooltip, .was-validated\n.custom-select:valid ~ .invalid-feedback,\n.was-validated\n.custom-select:valid ~ .invalid-tooltip,\n.custom-select.is-valid ~ .invalid-feedback,\n.custom-select.is-valid ~ .invalid-tooltip {\n display: block;\n}\n\n.was-validated .form-check-input:valid + .form-check-label, .form-check-input.is-valid + .form-check-label {\n color: #28a745;\n}\n\n.was-validated .custom-control-input:valid ~ .custom-control-indicator, .custom-control-input.is-valid ~ .custom-control-indicator {\n background-color: rgba(40, 167, 69, 0.25);\n}\n\n.was-validated .custom-control-input:valid ~ .custom-control-description, .custom-control-input.is-valid ~ .custom-control-description {\n color: #28a745;\n}\n\n.was-validated .custom-file-input:valid ~ .custom-file-control, .custom-file-input.is-valid ~ .custom-file-control {\n border-color: #28a745;\n}\n\n.was-validated .custom-file-input:valid ~ .custom-file-control::before, .custom-file-input.is-valid ~ .custom-file-control::before {\n border-color: inherit;\n}\n\n.was-validated .custom-file-input:valid:focus, .custom-file-input.is-valid:focus {\n box-shadow: 0 0 0 0.2rem rgba(40, 167, 69, 0.25);\n}\n\n.was-validated .form-control:invalid, .form-control.is-invalid, .was-validated\n.custom-select:invalid,\n.custom-select.is-invalid {\n border-color: #dc3545;\n}\n\n.was-validated .form-control:invalid:focus, .form-control.is-invalid:focus, .was-validated\n.custom-select:invalid:focus,\n.custom-select.is-invalid:focus {\n box-shadow: 0 0 0 0.2rem rgba(220, 53, 69, 0.25);\n}\n\n.was-validated .form-control:invalid ~ .invalid-feedback,\n.was-validated .form-control:invalid ~ .invalid-tooltip, .form-control.is-invalid ~ .invalid-feedback,\n.form-control.is-invalid ~ .invalid-tooltip, .was-validated\n.custom-select:invalid ~ .invalid-feedback,\n.was-validated\n.custom-select:invalid ~ .invalid-tooltip,\n.custom-select.is-invalid ~ .invalid-feedback,\n.custom-select.is-invalid ~ .invalid-tooltip {\n display: block;\n}\n\n.was-validated .form-check-input:invalid + .form-check-label, .form-check-input.is-invalid + .form-check-label {\n color: #dc3545;\n}\n\n.was-validated .custom-control-input:invalid ~ .custom-control-indicator, .custom-control-input.is-invalid ~ .custom-control-indicator {\n background-color: rgba(220, 53, 69, 0.25);\n}\n\n.was-validated .custom-control-input:invalid ~ .custom-control-description, .custom-control-input.is-invalid ~ .custom-control-description {\n color: #dc3545;\n}\n\n.was-validated .custom-file-input:invalid ~ .custom-file-control, .custom-file-input.is-invalid ~ .custom-file-control {\n border-color: #dc3545;\n}\n\n.was-validated .custom-file-input:invalid ~ .custom-file-control::before, .custom-file-input.is-invalid ~ .custom-file-control::before {\n border-color: inherit;\n}\n\n.was-validated .custom-file-input:invalid:focus, .custom-file-input.is-invalid:focus {\n box-shadow: 0 0 0 0.2rem rgba(220, 53, 69, 0.25);\n}\n\n.form-inline {\n display: flex;\n flex-flow: row wrap;\n align-items: center;\n}\n\n.form-inline .form-check {\n width: 100%;\n}\n\n@media (min-width: 576px) {\n .form-inline label {\n display: flex;\n align-items: center;\n justify-content: center;\n margin-bottom: 0;\n }\n .form-inline .form-group {\n display: flex;\n flex: 0 0 auto;\n flex-flow: row wrap;\n align-items: center;\n margin-bottom: 0;\n }\n .form-inline .form-control {\n display: inline-block;\n width: auto;\n vertical-align: middle;\n }\n .form-inline .form-control-plaintext {\n display: inline-block;\n }\n .form-inline .input-group {\n width: auto;\n }\n .form-inline .form-control-label {\n margin-bottom: 0;\n vertical-align: middle;\n }\n .form-inline .form-check {\n display: flex;\n align-items: center;\n justify-content: center;\n width: auto;\n margin-top: 0;\n margin-bottom: 0;\n }\n .form-inline .form-check-label {\n padding-left: 0;\n }\n .form-inline .form-check-input {\n position: relative;\n margin-top: 0;\n margin-right: 0.25rem;\n margin-left: 0;\n }\n .form-inline .custom-control {\n display: flex;\n align-items: center;\n justify-content: center;\n padding-left: 0;\n }\n .form-inline .custom-control-indicator {\n position: static;\n display: inline-block;\n margin-right: 0.25rem;\n vertical-align: text-bottom;\n }\n .form-inline .has-feedback .form-control-feedback {\n top: 0;\n }\n}\n\n.btn {\n display: inline-block;\n font-weight: normal;\n text-align: center;\n white-space: nowrap;\n vertical-align: middle;\n user-select: none;\n border: 1px solid transparent;\n padding: 0.5rem 0.75rem;\n font-size: 1rem;\n line-height: 1.25;\n border-radius: 0.25rem;\n transition: all 0.15s ease-in-out;\n}\n\n.btn:focus, .btn:hover {\n text-decoration: none;\n}\n\n.btn:focus, .btn.focus {\n outline: 0;\n box-shadow: 0 0 0 3px rgba(0, 123, 255, 0.25);\n}\n\n.btn.disabled, .btn:disabled {\n opacity: .65;\n}\n\n.btn:active, .btn.active {\n background-image: none;\n}\n\na.btn.disabled,\nfieldset[disabled] a.btn {\n pointer-events: none;\n}\n\n.btn-primary {\n color: #fff;\n background-color: #007bff;\n border-color: #007bff;\n}\n\n.btn-primary:hover {\n color: #fff;\n background-color: #0069d9;\n border-color: #0062cc;\n}\n\n.btn-primary:focus, .btn-primary.focus {\n box-shadow: 0 0 0 3px rgba(0, 123, 255, 0.5);\n}\n\n.btn-primary.disabled, .btn-primary:disabled {\n background-color: #007bff;\n border-color: #007bff;\n}\n\n.btn-primary:active, .btn-primary.active,\n.show > .btn-primary.dropdown-toggle {\n background-color: #0069d9;\n background-image: none;\n border-color: #0062cc;\n}\n\n.btn-secondary {\n color: #fff;\n background-color: #868e96;\n border-color: #868e96;\n}\n\n.btn-secondary:hover {\n color: #fff;\n background-color: #727b84;\n border-color: #6c757d;\n}\n\n.btn-secondary:focus, .btn-secondary.focus {\n box-shadow: 0 0 0 3px rgba(134, 142, 150, 0.5);\n}\n\n.btn-secondary.disabled, .btn-secondary:disabled {\n background-color: #868e96;\n border-color: #868e96;\n}\n\n.btn-secondary:active, .btn-secondary.active,\n.show > .btn-secondary.dropdown-toggle {\n background-color: #727b84;\n background-image: none;\n border-color: #6c757d;\n}\n\n.btn-success {\n color: #fff;\n background-color: #28a745;\n border-color: #28a745;\n}\n\n.btn-success:hover {\n color: #fff;\n background-color: #218838;\n border-color: #1e7e34;\n}\n\n.btn-success:focus, .btn-success.focus {\n box-shadow: 0 0 0 3px rgba(40, 167, 69, 0.5);\n}\n\n.btn-success.disabled, .btn-success:disabled {\n background-color: #28a745;\n border-color: #28a745;\n}\n\n.btn-success:active, .btn-success.active,\n.show > .btn-success.dropdown-toggle {\n background-color: #218838;\n background-image: none;\n border-color: #1e7e34;\n}\n\n.btn-info {\n color: #fff;\n background-color: #17a2b8;\n border-color: #17a2b8;\n}\n\n.btn-info:hover {\n color: #fff;\n background-color: #138496;\n border-color: #117a8b;\n}\n\n.btn-info:focus, .btn-info.focus {\n box-shadow: 0 0 0 3px rgba(23, 162, 184, 0.5);\n}\n\n.btn-info.disabled, .btn-info:disabled {\n background-color: #17a2b8;\n border-color: #17a2b8;\n}\n\n.btn-info:active, .btn-info.active,\n.show > .btn-info.dropdown-toggle {\n background-color: #138496;\n background-image: none;\n border-color: #117a8b;\n}\n\n.btn-warning {\n color: #111;\n background-color: #ffc107;\n border-color: #ffc107;\n}\n\n.btn-warning:hover {\n color: #111;\n background-color: #e0a800;\n border-color: #d39e00;\n}\n\n.btn-warning:focus, .btn-warning.focus {\n box-shadow: 0 0 0 3px rgba(255, 193, 7, 0.5);\n}\n\n.btn-warning.disabled, .btn-warning:disabled {\n background-color: #ffc107;\n border-color: #ffc107;\n}\n\n.btn-warning:active, .btn-warning.active,\n.show > .btn-warning.dropdown-toggle {\n background-color: #e0a800;\n background-image: none;\n border-color: #d39e00;\n}\n\n.btn-danger {\n color: #fff;\n background-color: #dc3545;\n border-color: #dc3545;\n}\n\n.btn-danger:hover {\n color: #fff;\n background-color: #c82333;\n border-color: #bd2130;\n}\n\n.btn-danger:focus, .btn-danger.focus {\n box-shadow: 0 0 0 3px rgba(220, 53, 69, 0.5);\n}\n\n.btn-danger.disabled, .btn-danger:disabled {\n background-color: #dc3545;\n border-color: #dc3545;\n}\n\n.btn-danger:active, .btn-danger.active,\n.show > .btn-danger.dropdown-toggle {\n background-color: #c82333;\n background-image: none;\n border-color: #bd2130;\n}\n\n.btn-light {\n color: #111;\n background-color: #f8f9fa;\n border-color: #f8f9fa;\n}\n\n.btn-light:hover {\n color: #111;\n background-color: #e2e6ea;\n border-color: #dae0e5;\n}\n\n.btn-light:focus, .btn-light.focus {\n box-shadow: 0 0 0 3px rgba(248, 249, 250, 0.5);\n}\n\n.btn-light.disabled, .btn-light:disabled {\n background-color: #f8f9fa;\n border-color: #f8f9fa;\n}\n\n.btn-light:active, .btn-light.active,\n.show > .btn-light.dropdown-toggle {\n background-color: #e2e6ea;\n background-image: none;\n border-color: #dae0e5;\n}\n\n.btn-dark {\n color: #fff;\n background-color: #343a40;\n border-color: #343a40;\n}\n\n.btn-dark:hover {\n color: #fff;\n background-color: #23272b;\n border-color: #1d2124;\n}\n\n.btn-dark:focus, .btn-dark.focus {\n box-shadow: 0 0 0 3px rgba(52, 58, 64, 0.5);\n}\n\n.btn-dark.disabled, .btn-dark:disabled {\n background-color: #343a40;\n border-color: #343a40;\n}\n\n.btn-dark:active, .btn-dark.active,\n.show > .btn-dark.dropdown-toggle {\n background-color: #23272b;\n background-image: none;\n border-color: #1d2124;\n}\n\n.btn-outline-primary {\n color: #007bff;\n background-color: transparent;\n background-image: none;\n border-color: #007bff;\n}\n\n.btn-outline-primary:hover {\n color: #fff;\n background-color: #007bff;\n border-color: #007bff;\n}\n\n.btn-outline-primary:focus, .btn-outline-primary.focus {\n box-shadow: 0 0 0 3px rgba(0, 123, 255, 0.5);\n}\n\n.btn-outline-primary.disabled, .btn-outline-primary:disabled {\n color: #007bff;\n background-color: transparent;\n}\n\n.btn-outline-primary:active, .btn-outline-primary.active,\n.show > .btn-outline-primary.dropdown-toggle {\n color: #fff;\n background-color: #007bff;\n border-color: #007bff;\n}\n\n.btn-outline-secondary {\n color: #868e96;\n background-color: transparent;\n background-image: none;\n border-color: #868e96;\n}\n\n.btn-outline-secondary:hover {\n color: #fff;\n background-color: #868e96;\n border-color: #868e96;\n}\n\n.btn-outline-secondary:focus, .btn-outline-secondary.focus {\n box-shadow: 0 0 0 3px rgba(134, 142, 150, 0.5);\n}\n\n.btn-outline-secondary.disabled, .btn-outline-secondary:disabled {\n color: #868e96;\n background-color: transparent;\n}\n\n.btn-outline-secondary:active, .btn-outline-secondary.active,\n.show > .btn-outline-secondary.dropdown-toggle {\n color: #fff;\n background-color: #868e96;\n border-color: #868e96;\n}\n\n.btn-outline-success {\n color: #28a745;\n background-color: transparent;\n background-image: none;\n border-color: #28a745;\n}\n\n.btn-outline-success:hover {\n color: #fff;\n background-color: #28a745;\n border-color: #28a745;\n}\n\n.btn-outline-success:focus, .btn-outline-success.focus {\n box-shadow: 0 0 0 3px rgba(40, 167, 69, 0.5);\n}\n\n.btn-outline-success.disabled, .btn-outline-success:disabled {\n color: #28a745;\n background-color: transparent;\n}\n\n.btn-outline-success:active, .btn-outline-success.active,\n.show > .btn-outline-success.dropdown-toggle {\n color: #fff;\n background-color: #28a745;\n border-color: #28a745;\n}\n\n.btn-outline-info {\n color: #17a2b8;\n background-color: transparent;\n background-image: none;\n border-color: #17a2b8;\n}\n\n.btn-outline-info:hover {\n color: #fff;\n background-color: #17a2b8;\n border-color: #17a2b8;\n}\n\n.btn-outline-info:focus, .btn-outline-info.focus {\n box-shadow: 0 0 0 3px rgba(23, 162, 184, 0.5);\n}\n\n.btn-outline-info.disabled, .btn-outline-info:disabled {\n color: #17a2b8;\n background-color: transparent;\n}\n\n.btn-outline-info:active, .btn-outline-info.active,\n.show > .btn-outline-info.dropdown-toggle {\n color: #fff;\n background-color: #17a2b8;\n border-color: #17a2b8;\n}\n\n.btn-outline-warning {\n color: #ffc107;\n background-color: transparent;\n background-image: none;\n border-color: #ffc107;\n}\n\n.btn-outline-warning:hover {\n color: #fff;\n background-color: #ffc107;\n border-color: #ffc107;\n}\n\n.btn-outline-warning:focus, .btn-outline-warning.focus {\n box-shadow: 0 0 0 3px rgba(255, 193, 7, 0.5);\n}\n\n.btn-outline-warning.disabled, .btn-outline-warning:disabled {\n color: #ffc107;\n background-color: transparent;\n}\n\n.btn-outline-warning:active, .btn-outline-warning.active,\n.show > .btn-outline-warning.dropdown-toggle {\n color: #fff;\n background-color: #ffc107;\n border-color: #ffc107;\n}\n\n.btn-outline-danger {\n color: #dc3545;\n background-color: transparent;\n background-image: none;\n border-color: #dc3545;\n}\n\n.btn-outline-danger:hover {\n color: #fff;\n background-color: #dc3545;\n border-color: #dc3545;\n}\n\n.btn-outline-danger:focus, .btn-outline-danger.focus {\n box-shadow: 0 0 0 3px rgba(220, 53, 69, 0.5);\n}\n\n.btn-outline-danger.disabled, .btn-outline-danger:disabled {\n color: #dc3545;\n background-color: transparent;\n}\n\n.btn-outline-danger:active, .btn-outline-danger.active,\n.show > .btn-outline-danger.dropdown-toggle {\n color: #fff;\n background-color: #dc3545;\n border-color: #dc3545;\n}\n\n.btn-outline-light {\n color: #f8f9fa;\n background-color: transparent;\n background-image: none;\n border-color: #f8f9fa;\n}\n\n.btn-outline-light:hover {\n color: #fff;\n background-color: #f8f9fa;\n border-color: #f8f9fa;\n}\n\n.btn-outline-light:focus, .btn-outline-light.focus {\n box-shadow: 0 0 0 3px rgba(248, 249, 250, 0.5);\n}\n\n.btn-outline-light.disabled, .btn-outline-light:disabled {\n color: #f8f9fa;\n background-color: transparent;\n}\n\n.btn-outline-light:active, .btn-outline-light.active,\n.show > .btn-outline-light.dropdown-toggle {\n color: #fff;\n background-color: #f8f9fa;\n border-color: #f8f9fa;\n}\n\n.btn-outline-dark {\n color: #343a40;\n background-color: transparent;\n background-image: none;\n border-color: #343a40;\n}\n\n.btn-outline-dark:hover {\n color: #fff;\n background-color: #343a40;\n border-color: #343a40;\n}\n\n.btn-outline-dark:focus, .btn-outline-dark.focus {\n box-shadow: 0 0 0 3px rgba(52, 58, 64, 0.5);\n}\n\n.btn-outline-dark.disabled, .btn-outline-dark:disabled {\n color: #343a40;\n background-color: transparent;\n}\n\n.btn-outline-dark:active, .btn-outline-dark.active,\n.show > .btn-outline-dark.dropdown-toggle {\n color: #fff;\n background-color: #343a40;\n border-color: #343a40;\n}\n\n.btn-link {\n font-weight: normal;\n color: #007bff;\n border-radius: 0;\n}\n\n.btn-link, .btn-link:active, .btn-link.active, .btn-link:disabled {\n background-color: transparent;\n}\n\n.btn-link, .btn-link:focus, .btn-link:active {\n border-color: transparent;\n box-shadow: none;\n}\n\n.btn-link:hover {\n border-color: transparent;\n}\n\n.btn-link:focus, .btn-link:hover {\n color: #0056b3;\n text-decoration: underline;\n background-color: transparent;\n}\n\n.btn-link:disabled {\n color: #868e96;\n}\n\n.btn-link:disabled:focus, .btn-link:disabled:hover {\n text-decoration: none;\n}\n\n.btn-lg, .btn-group-lg > .btn {\n padding: 0.5rem 1rem;\n font-size: 1.25rem;\n line-height: 1.5;\n border-radius: 0.3rem;\n}\n\n.btn-sm, .btn-group-sm > .btn {\n padding: 0.25rem 0.5rem;\n font-size: 0.875rem;\n line-height: 1.5;\n border-radius: 0.2rem;\n}\n\n.btn-block {\n display: block;\n width: 100%;\n}\n\n.btn-block + .btn-block {\n margin-top: 0.5rem;\n}\n\ninput[type=\"submit\"].btn-block,\ninput[type=\"reset\"].btn-block,\ninput[type=\"button\"].btn-block {\n width: 100%;\n}\n\n.fade {\n opacity: 0;\n transition: opacity 0.15s linear;\n}\n\n.fade.show {\n opacity: 1;\n}\n\n.collapse {\n display: none;\n}\n\n.collapse.show {\n display: block;\n}\n\ntr.collapse.show {\n display: table-row;\n}\n\ntbody.collapse.show {\n display: table-row-group;\n}\n\n.collapsing {\n position: relative;\n height: 0;\n overflow: hidden;\n transition: height 0.35s ease;\n}\n\n.dropup,\n.dropdown {\n position: relative;\n}\n\n.dropdown-toggle::after {\n display: inline-block;\n width: 0;\n height: 0;\n margin-left: 0.255em;\n vertical-align: 0.255em;\n content: \"\";\n border-top: 0.3em solid;\n border-right: 0.3em solid transparent;\n border-left: 0.3em solid transparent;\n}\n\n.dropdown-toggle:empty::after {\n margin-left: 0;\n}\n\n.dropup .dropdown-menu {\n margin-top: 0;\n margin-bottom: 0.125rem;\n}\n\n.dropup .dropdown-toggle::after {\n border-top: 0;\n border-bottom: 0.3em solid;\n}\n\n.dropdown-menu {\n position: absolute;\n top: 100%;\n left: 0;\n z-index: 1000;\n display: none;\n float: left;\n min-width: 10rem;\n padding: 0.5rem 0;\n margin: 0.125rem 0 0;\n font-size: 1rem;\n color: #212529;\n text-align: left;\n list-style: none;\n background-color: #fff;\n background-clip: padding-box;\n border: 1px solid rgba(0, 0, 0, 0.15);\n border-radius: 0.25rem;\n}\n\n.dropdown-divider {\n height: 0;\n margin: 0.5rem 0;\n overflow: hidden;\n border-top: 1px solid #e9ecef;\n}\n\n.dropdown-item {\n display: block;\n width: 100%;\n padding: 0.25rem 1.5rem;\n clear: both;\n font-weight: normal;\n color: #212529;\n text-align: inherit;\n white-space: nowrap;\n background: none;\n border: 0;\n}\n\n.dropdown-item:focus, .dropdown-item:hover {\n color: #16181b;\n text-decoration: none;\n background-color: #f8f9fa;\n}\n\n.dropdown-item.active, .dropdown-item:active {\n color: #fff;\n text-decoration: none;\n background-color: #007bff;\n}\n\n.dropdown-item.disabled, .dropdown-item:disabled {\n color: #868e96;\n background-color: transparent;\n}\n\n.show > a {\n outline: 0;\n}\n\n.dropdown-menu.show {\n display: block;\n}\n\n.dropdown-header {\n display: block;\n padding: 0.5rem 1.5rem;\n margin-bottom: 0;\n font-size: 0.875rem;\n color: #868e96;\n white-space: nowrap;\n}\n\n.btn-group,\n.btn-group-vertical {\n position: relative;\n display: inline-flex;\n vertical-align: middle;\n}\n\n.btn-group > .btn,\n.btn-group-vertical > .btn {\n position: relative;\n flex: 0 1 auto;\n margin-bottom: 0;\n}\n\n.btn-group > .btn:hover,\n.btn-group-vertical > .btn:hover {\n z-index: 2;\n}\n\n.btn-group > .btn:focus, .btn-group > .btn:active, .btn-group > .btn.active,\n.btn-group-vertical > .btn:focus,\n.btn-group-vertical > .btn:active,\n.btn-group-vertical > .btn.active {\n z-index: 2;\n}\n\n.btn-group .btn + .btn,\n.btn-group .btn + .btn-group,\n.btn-group .btn-group + .btn,\n.btn-group .btn-group + .btn-group,\n.btn-group-vertical .btn + .btn,\n.btn-group-vertical .btn + .btn-group,\n.btn-group-vertical .btn-group + .btn,\n.btn-group-vertical .btn-group + .btn-group {\n margin-left: -1px;\n}\n\n.btn-toolbar {\n display: flex;\n flex-wrap: wrap;\n justify-content: flex-start;\n}\n\n.btn-toolbar .input-group {\n width: auto;\n}\n\n.btn-group > .btn:not(:first-child):not(:last-child):not(.dropdown-toggle) {\n border-radius: 0;\n}\n\n.btn-group > .btn:first-child {\n margin-left: 0;\n}\n\n.btn-group > .btn:first-child:not(:last-child):not(.dropdown-toggle) {\n border-top-right-radius: 0;\n border-bottom-right-radius: 0;\n}\n\n.btn-group > .btn:last-child:not(:first-child),\n.btn-group > .dropdown-toggle:not(:first-child) {\n border-top-left-radius: 0;\n border-bottom-left-radius: 0;\n}\n\n.btn-group > .btn-group {\n float: left;\n}\n\n.btn-group > .btn-group:not(:first-child):not(:last-child) > .btn {\n border-radius: 0;\n}\n\n.btn-group > .btn-group:first-child:not(:last-child) > .btn:last-child,\n.btn-group > .btn-group:first-child:not(:last-child) > .dropdown-toggle {\n border-top-right-radius: 0;\n border-bottom-right-radius: 0;\n}\n\n.btn-group > .btn-group:last-child:not(:first-child) > .btn:first-child {\n border-top-left-radius: 0;\n border-bottom-left-radius: 0;\n}\n\n.btn + .dropdown-toggle-split {\n padding-right: 0.5625rem;\n padding-left: 0.5625rem;\n}\n\n.btn + .dropdown-toggle-split::after {\n margin-left: 0;\n}\n\n.btn-sm + .dropdown-toggle-split, .btn-group-sm > .btn + .dropdown-toggle-split {\n padding-right: 0.375rem;\n padding-left: 0.375rem;\n}\n\n.btn-lg + .dropdown-toggle-split, .btn-group-lg > .btn + .dropdown-toggle-split {\n padding-right: 0.75rem;\n padding-left: 0.75rem;\n}\n\n.btn-group-vertical {\n display: inline-flex;\n flex-direction: column;\n align-items: flex-start;\n justify-content: center;\n}\n\n.btn-group-vertical .btn,\n.btn-group-vertical .btn-group {\n width: 100%;\n}\n\n.btn-group-vertical > .btn + .btn,\n.btn-group-vertical > .btn + .btn-group,\n.btn-group-vertical > .btn-group + .btn,\n.btn-group-vertical > .btn-group + .btn-group {\n margin-top: -1px;\n margin-left: 0;\n}\n\n.btn-group-vertical > .btn:not(:first-child):not(:last-child) {\n border-radius: 0;\n}\n\n.btn-group-vertical > .btn:first-child:not(:last-child) {\n border-bottom-right-radius: 0;\n border-bottom-left-radius: 0;\n}\n\n.btn-group-vertical > .btn:last-child:not(:first-child) {\n border-top-left-radius: 0;\n border-top-right-radius: 0;\n}\n\n.btn-group-vertical > .btn-group:not(:first-child):not(:last-child) > .btn {\n border-radius: 0;\n}\n\n.btn-group-vertical > .btn-group:first-child:not(:last-child) > .btn:last-child,\n.btn-group-vertical > .btn-group:first-child:not(:last-child) > .dropdown-toggle {\n border-bottom-right-radius: 0;\n border-bottom-left-radius: 0;\n}\n\n.btn-group-vertical > .btn-group:last-child:not(:first-child) > .btn:first-child {\n border-top-left-radius: 0;\n border-top-right-radius: 0;\n}\n\n[data-toggle=\"buttons\"] > .btn input[type=\"radio\"],\n[data-toggle=\"buttons\"] > .btn input[type=\"checkbox\"],\n[data-toggle=\"buttons\"] > .btn-group > .btn input[type=\"radio\"],\n[data-toggle=\"buttons\"] > .btn-group > .btn input[type=\"checkbox\"] {\n position: absolute;\n clip: rect(0, 0, 0, 0);\n pointer-events: none;\n}\n\n.input-group {\n position: relative;\n display: flex;\n width: 100%;\n}\n\n.input-group .form-control {\n position: relative;\n z-index: 2;\n flex: 1 1 auto;\n width: 1%;\n margin-bottom: 0;\n}\n\n.input-group .form-control:focus, .input-group .form-control:active, .input-group .form-control:hover {\n z-index: 3;\n}\n\n.input-group-addon,\n.input-group-btn,\n.input-group .form-control {\n display: flex;\n align-items: center;\n}\n\n.input-group-addon:not(:first-child):not(:last-child),\n.input-group-btn:not(:first-child):not(:last-child),\n.input-group .form-control:not(:first-child):not(:last-child) {\n border-radius: 0;\n}\n\n.input-group-addon,\n.input-group-btn {\n white-space: nowrap;\n vertical-align: middle;\n}\n\n.input-group-addon {\n padding: 0.5rem 0.75rem;\n margin-bottom: 0;\n font-size: 1rem;\n font-weight: normal;\n line-height: 1.25;\n color: #495057;\n text-align: center;\n background-color: #e9ecef;\n border: 1px solid rgba(0, 0, 0, 0.15);\n border-radius: 0.25rem;\n}\n\n.input-group-addon.form-control-sm,\n.input-group-sm > .input-group-addon,\n.input-group-sm > .input-group-btn > .input-group-addon.btn {\n padding: 0.25rem 0.5rem;\n font-size: 0.875rem;\n border-radius: 0.2rem;\n}\n\n.input-group-addon.form-control-lg,\n.input-group-lg > .input-group-addon,\n.input-group-lg > .input-group-btn > .input-group-addon.btn {\n padding: 0.5rem 1rem;\n font-size: 1.25rem;\n border-radius: 0.3rem;\n}\n\n.input-group-addon input[type=\"radio\"],\n.input-group-addon input[type=\"checkbox\"] {\n margin-top: 0;\n}\n\n.input-group .form-control:not(:last-child),\n.input-group-addon:not(:last-child),\n.input-group-btn:not(:last-child) > .btn,\n.input-group-btn:not(:last-child) > .btn-group > .btn,\n.input-group-btn:not(:last-child) > .dropdown-toggle,\n.input-group-btn:not(:first-child) > .btn:not(:last-child):not(.dropdown-toggle),\n.input-group-btn:not(:first-child) > .btn-group:not(:last-child) > .btn {\n border-top-right-radius: 0;\n border-bottom-right-radius: 0;\n}\n\n.input-group-addon:not(:last-child) {\n border-right: 0;\n}\n\n.input-group .form-control:not(:first-child),\n.input-group-addon:not(:first-child),\n.input-group-btn:not(:first-child) > .btn,\n.input-group-btn:not(:first-child) > .btn-group > .btn,\n.input-group-btn:not(:first-child) > .dropdown-toggle,\n.input-group-btn:not(:last-child) > .btn:not(:first-child),\n.input-group-btn:not(:last-child) > .btn-group:not(:first-child) > .btn {\n border-top-left-radius: 0;\n border-bottom-left-radius: 0;\n}\n\n.form-control + .input-group-addon:not(:first-child) {\n border-left: 0;\n}\n\n.input-group-btn {\n position: relative;\n font-size: 0;\n white-space: nowrap;\n}\n\n.input-group-btn > .btn {\n position: relative;\n}\n\n.input-group-btn > .btn + .btn {\n margin-left: -1px;\n}\n\n.input-group-btn > .btn:focus, .input-group-btn > .btn:active, .input-group-btn > .btn:hover {\n z-index: 3;\n}\n\n.input-group-btn:not(:last-child) > .btn,\n.input-group-btn:not(:last-child) > .btn-group {\n margin-right: -1px;\n}\n\n.input-group-btn:not(:first-child) > .btn,\n.input-group-btn:not(:first-child) > .btn-group {\n z-index: 2;\n margin-left: -1px;\n}\n\n.input-group-btn:not(:first-child) > .btn:focus, .input-group-btn:not(:first-child) > .btn:active, .input-group-btn:not(:first-child) > .btn:hover,\n.input-group-btn:not(:first-child) > .btn-group:focus,\n.input-group-btn:not(:first-child) > .btn-group:active,\n.input-group-btn:not(:first-child) > .btn-group:hover {\n z-index: 3;\n}\n\n.custom-control {\n position: relative;\n display: inline-flex;\n min-height: 1.5rem;\n padding-left: 1.5rem;\n margin-right: 1rem;\n}\n\n.custom-control-input {\n position: absolute;\n z-index: -1;\n opacity: 0;\n}\n\n.custom-control-input:checked ~ .custom-control-indicator {\n color: #fff;\n background-color: #007bff;\n}\n\n.custom-control-input:focus ~ .custom-control-indicator {\n box-shadow: 0 0 0 1px #fff, 0 0 0 3px #007bff;\n}\n\n.custom-control-input:active ~ .custom-control-indicator {\n color: #fff;\n background-color: #b3d7ff;\n}\n\n.custom-control-input:disabled ~ .custom-control-indicator {\n background-color: #e9ecef;\n}\n\n.custom-control-input:disabled ~ .custom-control-description {\n color: #868e96;\n}\n\n.custom-control-indicator {\n position: absolute;\n top: 0.25rem;\n left: 0;\n display: block;\n width: 1rem;\n height: 1rem;\n pointer-events: none;\n user-select: none;\n background-color: #ddd;\n background-repeat: no-repeat;\n background-position: center center;\n background-size: 50% 50%;\n}\n\n.custom-checkbox .custom-control-indicator {\n border-radius: 0.25rem;\n}\n\n.custom-checkbox .custom-control-input:checked ~ .custom-control-indicator {\n background-image: url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 8 8'%3E%3Cpath fill='%23fff' d='M6.564.75l-3.59 3.612-1.538-1.55L0 4.26 2.974 7.25 8 2.193z'/%3E%3C/svg%3E\");\n}\n\n.custom-checkbox .custom-control-input:indeterminate ~ .custom-control-indicator {\n background-color: #007bff;\n background-image: url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 4 4'%3E%3Cpath stroke='%23fff' d='M0 2h4'/%3E%3C/svg%3E\");\n}\n\n.custom-radio .custom-control-indicator {\n border-radius: 50%;\n}\n\n.custom-radio .custom-control-input:checked ~ .custom-control-indicator {\n background-image: url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='-4 -4 8 8'%3E%3Ccircle r='3' fill='%23fff'/%3E%3C/svg%3E\");\n}\n\n.custom-controls-stacked {\n display: flex;\n flex-direction: column;\n}\n\n.custom-controls-stacked .custom-control {\n margin-bottom: 0.25rem;\n}\n\n.custom-controls-stacked .custom-control + .custom-control {\n margin-left: 0;\n}\n\n.custom-select {\n display: inline-block;\n max-width: 100%;\n height: calc(2.25rem + 2px);\n padding: 0.375rem 1.75rem 0.375rem 0.75rem;\n line-height: 1.25;\n color: #495057;\n vertical-align: middle;\n background: #fff url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 4 5'%3E%3Cpath fill='%23333' d='M2 0L0 2h4zm0 5L0 3h4z'/%3E%3C/svg%3E\") no-repeat right 0.75rem center;\n background-size: 8px 10px;\n border: 1px solid rgba(0, 0, 0, 0.15);\n border-radius: 0.25rem;\n appearance: none;\n}\n\n.custom-select:focus {\n border-color: #80bdff;\n outline: none;\n}\n\n.custom-select:focus::-ms-value {\n color: #495057;\n background-color: #fff;\n}\n\n.custom-select:disabled {\n color: #868e96;\n background-color: #e9ecef;\n}\n\n.custom-select::-ms-expand {\n opacity: 0;\n}\n\n.custom-select-sm {\n height: calc(1.8125rem + 2px);\n padding-top: 0.375rem;\n padding-bottom: 0.375rem;\n font-size: 75%;\n}\n\n.custom-file {\n position: relative;\n display: inline-block;\n max-width: 100%;\n height: 2.5rem;\n margin-bottom: 0;\n}\n\n.custom-file-input {\n min-width: 14rem;\n max-width: 100%;\n height: 2.5rem;\n margin: 0;\n opacity: 0;\n}\n\n.custom-file-control {\n position: absolute;\n top: 0;\n right: 0;\n left: 0;\n z-index: 5;\n height: 2.5rem;\n padding: 0.5rem 1rem;\n line-height: 1.5;\n color: #495057;\n pointer-events: none;\n user-select: none;\n background-color: #fff;\n border: 1px solid rgba(0, 0, 0, 0.15);\n border-radius: 0.25rem;\n}\n\n.custom-file-control:lang(en):empty::after {\n content: \"Choose file...\";\n}\n\n.custom-file-control::before {\n position: absolute;\n top: -1px;\n right: -1px;\n bottom: -1px;\n z-index: 6;\n display: block;\n height: 2.5rem;\n padding: 0.5rem 1rem;\n line-height: 1.5;\n color: #495057;\n background-color: #e9ecef;\n border: 1px solid rgba(0, 0, 0, 0.15);\n border-radius: 0 0.25rem 0.25rem 0;\n}\n\n.custom-file-control:lang(en)::before {\n content: \"Browse\";\n}\n\n.nav {\n display: flex;\n flex-wrap: wrap;\n padding-left: 0;\n margin-bottom: 0;\n list-style: none;\n}\n\n.nav-link {\n display: block;\n padding: 0.5rem 1rem;\n}\n\n.nav-link:focus, .nav-link:hover {\n text-decoration: none;\n}\n\n.nav-link.disabled {\n color: #868e96;\n}\n\n.nav-tabs {\n border-bottom: 1px solid #ddd;\n}\n\n.nav-tabs .nav-item {\n margin-bottom: -1px;\n}\n\n.nav-tabs .nav-link {\n border: 1px solid transparent;\n border-top-left-radius: 0.25rem;\n border-top-right-radius: 0.25rem;\n}\n\n.nav-tabs .nav-link:focus, .nav-tabs .nav-link:hover {\n border-color: #e9ecef #e9ecef #ddd;\n}\n\n.nav-tabs .nav-link.disabled {\n color: #868e96;\n background-color: transparent;\n border-color: transparent;\n}\n\n.nav-tabs .nav-link.active,\n.nav-tabs .nav-item.show .nav-link {\n color: #495057;\n background-color: #fff;\n border-color: #ddd #ddd #fff;\n}\n\n.nav-tabs .dropdown-menu {\n margin-top: -1px;\n border-top-left-radius: 0;\n border-top-right-radius: 0;\n}\n\n.nav-pills .nav-link {\n border-radius: 0.25rem;\n}\n\n.nav-pills .nav-link.active,\n.show > .nav-pills .nav-link {\n color: #fff;\n background-color: #007bff;\n}\n\n.nav-fill .nav-item {\n flex: 1 1 auto;\n text-align: center;\n}\n\n.nav-justified .nav-item {\n flex-basis: 0;\n flex-grow: 1;\n text-align: center;\n}\n\n.tab-content > .tab-pane {\n display: none;\n}\n\n.tab-content > .active {\n display: block;\n}\n\n.navbar {\n position: relative;\n display: flex;\n flex-wrap: wrap;\n align-items: center;\n justify-content: space-between;\n padding: 0.5rem 1rem;\n}\n\n.navbar > .container,\n.navbar > .container-fluid {\n display: flex;\n flex-wrap: wrap;\n align-items: center;\n justify-content: space-between;\n}\n\n.navbar-brand {\n display: inline-block;\n padding-top: 0.3125rem;\n padding-bottom: 0.3125rem;\n margin-right: 1rem;\n font-size: 1.25rem;\n line-height: inherit;\n white-space: nowrap;\n}\n\n.navbar-brand:focus, .navbar-brand:hover {\n text-decoration: none;\n}\n\n.navbar-nav {\n display: flex;\n flex-direction: column;\n padding-left: 0;\n margin-bottom: 0;\n list-style: none;\n}\n\n.navbar-nav .nav-link {\n padding-right: 0;\n padding-left: 0;\n}\n\n.navbar-nav .dropdown-menu {\n position: static;\n float: none;\n}\n\n.navbar-text {\n display: inline-block;\n padding-top: 0.5rem;\n padding-bottom: 0.5rem;\n}\n\n.navbar-collapse {\n flex-basis: 100%;\n align-items: center;\n}\n\n.navbar-toggler {\n padding: 0.25rem 0.75rem;\n font-size: 1.25rem;\n line-height: 1;\n background: transparent;\n border: 1px solid transparent;\n border-radius: 0.25rem;\n}\n\n.navbar-toggler:focus, .navbar-toggler:hover {\n text-decoration: none;\n}\n\n.navbar-toggler-icon {\n display: inline-block;\n width: 1.5em;\n height: 1.5em;\n vertical-align: middle;\n content: \"\";\n background: no-repeat center center;\n background-size: 100% 100%;\n}\n\n@media (max-width: 575px) {\n .navbar-expand-sm > .container,\n .navbar-expand-sm > .container-fluid {\n padding-right: 0;\n padding-left: 0;\n }\n}\n\n@media (min-width: 576px) {\n .navbar-expand-sm {\n flex-direction: row;\n flex-wrap: nowrap;\n justify-content: flex-start;\n }\n .navbar-expand-sm .navbar-nav {\n flex-direction: row;\n }\n .navbar-expand-sm .navbar-nav .dropdown-menu {\n position: absolute;\n }\n .navbar-expand-sm .navbar-nav .dropdown-menu-right {\n right: 0;\n left: auto;\n }\n .navbar-expand-sm .navbar-nav .nav-link {\n padding-right: .5rem;\n padding-left: .5rem;\n }\n .navbar-expand-sm > .container,\n .navbar-expand-sm > .container-fluid {\n flex-wrap: nowrap;\n }\n .navbar-expand-sm .navbar-collapse {\n display: flex !important;\n }\n .navbar-expand-sm .navbar-toggler {\n display: none;\n }\n}\n\n@media (max-width: 767px) {\n .navbar-expand-md > .container,\n .navbar-expand-md > .container-fluid {\n padding-right: 0;\n padding-left: 0;\n }\n}\n\n@media (min-width: 768px) {\n .navbar-expand-md {\n flex-direction: row;\n flex-wrap: nowrap;\n justify-content: flex-start;\n }\n .navbar-expand-md .navbar-nav {\n flex-direction: row;\n }\n .navbar-expand-md .navbar-nav .dropdown-menu {\n position: absolute;\n }\n .navbar-expand-md .navbar-nav .dropdown-menu-right {\n right: 0;\n left: auto;\n }\n .navbar-expand-md .navbar-nav .nav-link {\n padding-right: .5rem;\n padding-left: .5rem;\n }\n .navbar-expand-md > .container,\n .navbar-expand-md > .container-fluid {\n flex-wrap: nowrap;\n }\n .navbar-expand-md .navbar-collapse {\n display: flex !important;\n }\n .navbar-expand-md .navbar-toggler {\n display: none;\n }\n}\n\n@media (max-width: 991px) {\n .navbar-expand-lg > .container,\n .navbar-expand-lg > .container-fluid {\n padding-right: 0;\n padding-left: 0;\n }\n}\n\n@media (min-width: 992px) {\n .navbar-expand-lg {\n flex-direction: row;\n flex-wrap: nowrap;\n justify-content: flex-start;\n }\n .navbar-expand-lg .navbar-nav {\n flex-direction: row;\n }\n .navbar-expand-lg .navbar-nav .dropdown-menu {\n position: absolute;\n }\n .navbar-expand-lg .navbar-nav .dropdown-menu-right {\n right: 0;\n left: auto;\n }\n .navbar-expand-lg .navbar-nav .nav-link {\n padding-right: .5rem;\n padding-left: .5rem;\n }\n .navbar-expand-lg > .container,\n .navbar-expand-lg > .container-fluid {\n flex-wrap: nowrap;\n }\n .navbar-expand-lg .navbar-collapse {\n display: flex !important;\n }\n .navbar-expand-lg .navbar-toggler {\n display: none;\n }\n}\n\n@media (max-width: 1199px) {\n .navbar-expand-xl > .container,\n .navbar-expand-xl > .container-fluid {\n padding-right: 0;\n padding-left: 0;\n }\n}\n\n@media (min-width: 1200px) {\n .navbar-expand-xl {\n flex-direction: row;\n flex-wrap: nowrap;\n justify-content: flex-start;\n }\n .navbar-expand-xl .navbar-nav {\n flex-direction: row;\n }\n .navbar-expand-xl .navbar-nav .dropdown-menu {\n position: absolute;\n }\n .navbar-expand-xl .navbar-nav .dropdown-menu-right {\n right: 0;\n left: auto;\n }\n .navbar-expand-xl .navbar-nav .nav-link {\n padding-right: .5rem;\n padding-left: .5rem;\n }\n .navbar-expand-xl > .container,\n .navbar-expand-xl > .container-fluid {\n flex-wrap: nowrap;\n }\n .navbar-expand-xl .navbar-collapse {\n display: flex !important;\n }\n .navbar-expand-xl .navbar-toggler {\n display: none;\n }\n}\n\n.navbar-expand {\n flex-direction: row;\n flex-wrap: nowrap;\n justify-content: flex-start;\n}\n\n.navbar-expand > .container,\n.navbar-expand > .container-fluid {\n padding-right: 0;\n padding-left: 0;\n}\n\n.navbar-expand .navbar-nav {\n flex-direction: row;\n}\n\n.navbar-expand .navbar-nav .dropdown-menu {\n position: absolute;\n}\n\n.navbar-expand .navbar-nav .dropdown-menu-right {\n right: 0;\n left: auto;\n}\n\n.navbar-expand .navbar-nav .nav-link {\n padding-right: .5rem;\n padding-left: .5rem;\n}\n\n.navbar-expand > .container,\n.navbar-expand > .container-fluid {\n flex-wrap: nowrap;\n}\n\n.navbar-expand .navbar-collapse {\n display: flex !important;\n}\n\n.navbar-expand .navbar-toggler {\n display: none;\n}\n\n.navbar-light .navbar-brand {\n color: rgba(0, 0, 0, 0.9);\n}\n\n.navbar-light .navbar-brand:focus, .navbar-light .navbar-brand:hover {\n color: rgba(0, 0, 0, 0.9);\n}\n\n.navbar-light .navbar-nav .nav-link {\n color: rgba(0, 0, 0, 0.5);\n}\n\n.navbar-light .navbar-nav .nav-link:focus, .navbar-light .navbar-nav .nav-link:hover {\n color: rgba(0, 0, 0, 0.7);\n}\n\n.navbar-light .navbar-nav .nav-link.disabled {\n color: rgba(0, 0, 0, 0.3);\n}\n\n.navbar-light .navbar-nav .show > .nav-link,\n.navbar-light .navbar-nav .active > .nav-link,\n.navbar-light .navbar-nav .nav-link.show,\n.navbar-light .navbar-nav .nav-link.active {\n color: rgba(0, 0, 0, 0.9);\n}\n\n.navbar-light .navbar-toggler {\n color: rgba(0, 0, 0, 0.5);\n border-color: rgba(0, 0, 0, 0.1);\n}\n\n.navbar-light .navbar-toggler-icon {\n background-image: url(\"data:image/svg+xml;charset=utf8,%3Csvg viewBox='0 0 30 30' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath stroke='rgba(0, 0, 0, 0.5)' stroke-width='2' stroke-linecap='round' stroke-miterlimit='10' d='M4 7h22M4 15h22M4 23h22'/%3E%3C/svg%3E\");\n}\n\n.navbar-light .navbar-text {\n color: rgba(0, 0, 0, 0.5);\n}\n\n.navbar-dark .navbar-brand {\n color: white;\n}\n\n.navbar-dark .navbar-brand:focus, .navbar-dark .navbar-brand:hover {\n color: white;\n}\n\n.navbar-dark .navbar-nav .nav-link {\n color: rgba(255, 255, 255, 0.5);\n}\n\n.navbar-dark .navbar-nav .nav-link:focus, .navbar-dark .navbar-nav .nav-link:hover {\n color: rgba(255, 255, 255, 0.75);\n}\n\n.navbar-dark .navbar-nav .nav-link.disabled {\n color: rgba(255, 255, 255, 0.25);\n}\n\n.navbar-dark .navbar-nav .show > .nav-link,\n.navbar-dark .navbar-nav .active > .nav-link,\n.navbar-dark .navbar-nav .nav-link.show,\n.navbar-dark .navbar-nav .nav-link.active {\n color: white;\n}\n\n.navbar-dark .navbar-toggler {\n color: rgba(255, 255, 255, 0.5);\n border-color: rgba(255, 255, 255, 0.1);\n}\n\n.navbar-dark .navbar-toggler-icon {\n background-image: url(\"data:image/svg+xml;charset=utf8,%3Csvg viewBox='0 0 30 30' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath stroke='rgba(255, 255, 255, 0.5)' stroke-width='2' stroke-linecap='round' stroke-miterlimit='10' d='M4 7h22M4 15h22M4 23h22'/%3E%3C/svg%3E\");\n}\n\n.navbar-dark .navbar-text {\n color: rgba(255, 255, 255, 0.5);\n}\n\n.card {\n position: relative;\n display: flex;\n flex-direction: column;\n min-width: 0;\n word-wrap: break-word;\n background-color: #fff;\n background-clip: border-box;\n border: 1px solid rgba(0, 0, 0, 0.125);\n border-radius: 0.25rem;\n}\n\n.card-body {\n flex: 1 1 auto;\n padding: 1.25rem;\n}\n\n.card-title {\n margin-bottom: 0.75rem;\n}\n\n.card-subtitle {\n margin-top: -0.375rem;\n margin-bottom: 0;\n}\n\n.card-text:last-child {\n margin-bottom: 0;\n}\n\n.card-link:hover {\n text-decoration: none;\n}\n\n.card-link + .card-link {\n margin-left: 1.25rem;\n}\n\n.card > .list-group:first-child .list-group-item:first-child {\n border-top-left-radius: 0.25rem;\n border-top-right-radius: 0.25rem;\n}\n\n.card > .list-group:last-child .list-group-item:last-child {\n border-bottom-right-radius: 0.25rem;\n border-bottom-left-radius: 0.25rem;\n}\n\n.card-header {\n padding: 0.75rem 1.25rem;\n margin-bottom: 0;\n background-color: rgba(0, 0, 0, 0.03);\n border-bottom: 1px solid rgba(0, 0, 0, 0.125);\n}\n\n.card-header:first-child {\n border-radius: calc(0.25rem - 1px) calc(0.25rem - 1px) 0 0;\n}\n\n.card-footer {\n padding: 0.75rem 1.25rem;\n background-color: rgba(0, 0, 0, 0.03);\n border-top: 1px solid rgba(0, 0, 0, 0.125);\n}\n\n.card-footer:last-child {\n border-radius: 0 0 calc(0.25rem - 1px) calc(0.25rem - 1px);\n}\n\n.card-header-tabs {\n margin-right: -0.625rem;\n margin-bottom: -0.75rem;\n margin-left: -0.625rem;\n border-bottom: 0;\n}\n\n.card-header-pills {\n margin-right: -0.625rem;\n margin-left: -0.625rem;\n}\n\n.card-img-overlay {\n position: absolute;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n padding: 1.25rem;\n}\n\n.card-img {\n width: 100%;\n border-radius: calc(0.25rem - 1px);\n}\n\n.card-img-top {\n width: 100%;\n border-top-left-radius: calc(0.25rem - 1px);\n border-top-right-radius: calc(0.25rem - 1px);\n}\n\n.card-img-bottom {\n width: 100%;\n border-bottom-right-radius: calc(0.25rem - 1px);\n border-bottom-left-radius: calc(0.25rem - 1px);\n}\n\n@media (min-width: 576px) {\n .card-deck {\n display: flex;\n flex-flow: row wrap;\n margin-right: -15px;\n margin-left: -15px;\n }\n .card-deck .card {\n display: flex;\n flex: 1 0 0%;\n flex-direction: column;\n margin-right: 15px;\n margin-left: 15px;\n }\n}\n\n@media (min-width: 576px) {\n .card-group {\n display: flex;\n flex-flow: row wrap;\n }\n .card-group .card {\n flex: 1 0 0%;\n }\n .card-group .card + .card {\n margin-left: 0;\n border-left: 0;\n }\n .card-group .card:first-child {\n border-top-right-radius: 0;\n border-bottom-right-radius: 0;\n }\n .card-group .card:first-child .card-img-top {\n border-top-right-radius: 0;\n }\n .card-group .card:first-child .card-img-bottom {\n border-bottom-right-radius: 0;\n }\n .card-group .card:last-child {\n border-top-left-radius: 0;\n border-bottom-left-radius: 0;\n }\n .card-group .card:last-child .card-img-top {\n border-top-left-radius: 0;\n }\n .card-group .card:last-child .card-img-bottom {\n border-bottom-left-radius: 0;\n }\n .card-group .card:not(:first-child):not(:last-child) {\n border-radius: 0;\n }\n .card-group .card:not(:first-child):not(:last-child) .card-img-top,\n .card-group .card:not(:first-child):not(:last-child) .card-img-bottom {\n border-radius: 0;\n }\n}\n\n.card-columns .card {\n margin-bottom: 0.75rem;\n}\n\n@media (min-width: 576px) {\n .card-columns {\n column-count: 3;\n column-gap: 1.25rem;\n }\n .card-columns .card {\n display: inline-block;\n width: 100%;\n }\n}\n\n.breadcrumb {\n padding: 0.75rem 1rem;\n margin-bottom: 1rem;\n list-style: none;\n background-color: #e9ecef;\n border-radius: 0.25rem;\n}\n\n.breadcrumb::after {\n display: block;\n clear: both;\n content: \"\";\n}\n\n.breadcrumb-item {\n float: left;\n}\n\n.breadcrumb-item + .breadcrumb-item::before {\n display: inline-block;\n padding-right: 0.5rem;\n padding-left: 0.5rem;\n color: #868e96;\n content: \"/\";\n}\n\n.breadcrumb-item + .breadcrumb-item:hover::before {\n text-decoration: underline;\n}\n\n.breadcrumb-item + .breadcrumb-item:hover::before {\n text-decoration: none;\n}\n\n.breadcrumb-item.active {\n color: #868e96;\n}\n\n.pagination {\n display: flex;\n padding-left: 0;\n list-style: none;\n border-radius: 0.25rem;\n}\n\n.page-item:first-child .page-link {\n margin-left: 0;\n border-top-left-radius: 0.25rem;\n border-bottom-left-radius: 0.25rem;\n}\n\n.page-item:last-child .page-link {\n border-top-right-radius: 0.25rem;\n border-bottom-right-radius: 0.25rem;\n}\n\n.page-item.active .page-link {\n z-index: 2;\n color: #fff;\n background-color: #007bff;\n border-color: #007bff;\n}\n\n.page-item.disabled .page-link {\n color: #868e96;\n pointer-events: none;\n background-color: #fff;\n border-color: #ddd;\n}\n\n.page-link {\n position: relative;\n display: block;\n padding: 0.5rem 0.75rem;\n margin-left: -1px;\n line-height: 1.25;\n color: #007bff;\n background-color: #fff;\n border: 1px solid #ddd;\n}\n\n.page-link:focus, .page-link:hover {\n color: #0056b3;\n text-decoration: none;\n background-color: #e9ecef;\n border-color: #ddd;\n}\n\n.pagination-lg .page-link {\n padding: 0.75rem 1.5rem;\n font-size: 1.25rem;\n line-height: 1.5;\n}\n\n.pagination-lg .page-item:first-child .page-link {\n border-top-left-radius: 0.3rem;\n border-bottom-left-radius: 0.3rem;\n}\n\n.pagination-lg .page-item:last-child .page-link {\n border-top-right-radius: 0.3rem;\n border-bottom-right-radius: 0.3rem;\n}\n\n.pagination-sm .page-link {\n padding: 0.25rem 0.5rem;\n font-size: 0.875rem;\n line-height: 1.5;\n}\n\n.pagination-sm .page-item:first-child .page-link {\n border-top-left-radius: 0.2rem;\n border-bottom-left-radius: 0.2rem;\n}\n\n.pagination-sm .page-item:last-child .page-link {\n border-top-right-radius: 0.2rem;\n border-bottom-right-radius: 0.2rem;\n}\n\n.badge {\n display: inline-block;\n padding: 0.25em 0.4em;\n font-size: 75%;\n font-weight: bold;\n line-height: 1;\n color: #fff;\n text-align: center;\n white-space: nowrap;\n vertical-align: baseline;\n border-radius: 0.25rem;\n}\n\n.badge:empty {\n display: none;\n}\n\n.btn .badge {\n position: relative;\n top: -1px;\n}\n\n.badge-pill {\n padding-right: 0.6em;\n padding-left: 0.6em;\n border-radius: 10rem;\n}\n\n.badge-primary {\n color: #fff;\n background-color: #007bff;\n}\n\n.badge-primary[href]:focus, .badge-primary[href]:hover {\n color: #fff;\n text-decoration: none;\n background-color: #0062cc;\n}\n\n.badge-secondary {\n color: #fff;\n background-color: #868e96;\n}\n\n.badge-secondary[href]:focus, .badge-secondary[href]:hover {\n color: #fff;\n text-decoration: none;\n background-color: #6c757d;\n}\n\n.badge-success {\n color: #fff;\n background-color: #28a745;\n}\n\n.badge-success[href]:focus, .badge-success[href]:hover {\n color: #fff;\n text-decoration: none;\n background-color: #1e7e34;\n}\n\n.badge-info {\n color: #fff;\n background-color: #17a2b8;\n}\n\n.badge-info[href]:focus, .badge-info[href]:hover {\n color: #fff;\n text-decoration: none;\n background-color: #117a8b;\n}\n\n.badge-warning {\n color: #111;\n background-color: #ffc107;\n}\n\n.badge-warning[href]:focus, .badge-warning[href]:hover {\n color: #111;\n text-decoration: none;\n background-color: #d39e00;\n}\n\n.badge-danger {\n color: #fff;\n background-color: #dc3545;\n}\n\n.badge-danger[href]:focus, .badge-danger[href]:hover {\n color: #fff;\n text-decoration: none;\n background-color: #bd2130;\n}\n\n.badge-light {\n color: #111;\n background-color: #f8f9fa;\n}\n\n.badge-light[href]:focus, .badge-light[href]:hover {\n color: #111;\n text-decoration: none;\n background-color: #dae0e5;\n}\n\n.badge-dark {\n color: #fff;\n background-color: #343a40;\n}\n\n.badge-dark[href]:focus, .badge-dark[href]:hover {\n color: #fff;\n text-decoration: none;\n background-color: #1d2124;\n}\n\n.jumbotron {\n padding: 2rem 1rem;\n margin-bottom: 2rem;\n background-color: #e9ecef;\n border-radius: 0.3rem;\n}\n\n@media (min-width: 576px) {\n .jumbotron {\n padding: 4rem 2rem;\n }\n}\n\n.jumbotron-fluid {\n padding-right: 0;\n padding-left: 0;\n border-radius: 0;\n}\n\n.alert {\n padding: 0.75rem 1.25rem;\n margin-bottom: 1rem;\n border: 1px solid transparent;\n border-radius: 0.25rem;\n}\n\n.alert-heading {\n color: inherit;\n}\n\n.alert-link {\n font-weight: bold;\n}\n\n.alert-dismissible .close {\n position: relative;\n top: -0.75rem;\n right: -1.25rem;\n padding: 0.75rem 1.25rem;\n color: inherit;\n}\n\n.alert-primary {\n color: #004085;\n background-color: #cce5ff;\n border-color: #b8daff;\n}\n\n.alert-primary hr {\n border-top-color: #9fcdff;\n}\n\n.alert-primary .alert-link {\n color: #002752;\n}\n\n.alert-secondary {\n color: #464a4e;\n background-color: #e7e8ea;\n border-color: #dddfe2;\n}\n\n.alert-secondary hr {\n border-top-color: #cfd2d6;\n}\n\n.alert-secondary .alert-link {\n color: #2e3133;\n}\n\n.alert-success {\n color: #155724;\n background-color: #d4edda;\n border-color: #c3e6cb;\n}\n\n.alert-success hr {\n border-top-color: #b1dfbb;\n}\n\n.alert-success .alert-link {\n color: #0b2e13;\n}\n\n.alert-info {\n color: #0c5460;\n background-color: #d1ecf1;\n border-color: #bee5eb;\n}\n\n.alert-info hr {\n border-top-color: #abdde5;\n}\n\n.alert-info .alert-link {\n color: #062c33;\n}\n\n.alert-warning {\n color: #856404;\n background-color: #fff3cd;\n border-color: #ffeeba;\n}\n\n.alert-warning hr {\n border-top-color: #ffe8a1;\n}\n\n.alert-warning .alert-link {\n color: #533f03;\n}\n\n.alert-danger {\n color: #721c24;\n background-color: #f8d7da;\n border-color: #f5c6cb;\n}\n\n.alert-danger hr {\n border-top-color: #f1b0b7;\n}\n\n.alert-danger .alert-link {\n color: #491217;\n}\n\n.alert-light {\n color: #818182;\n background-color: #fefefe;\n border-color: #fdfdfe;\n}\n\n.alert-light hr {\n border-top-color: #ececf6;\n}\n\n.alert-light .alert-link {\n color: #686868;\n}\n\n.alert-dark {\n color: #1b1e21;\n background-color: #d6d8d9;\n border-color: #c6c8ca;\n}\n\n.alert-dark hr {\n border-top-color: #b9bbbe;\n}\n\n.alert-dark .alert-link {\n color: #040505;\n}\n\n@keyframes progress-bar-stripes {\n from {\n background-position: 1rem 0;\n }\n to {\n background-position: 0 0;\n }\n}\n\n.progress {\n display: flex;\n overflow: hidden;\n font-size: 0.75rem;\n line-height: 1rem;\n text-align: center;\n background-color: #e9ecef;\n border-radius: 0.25rem;\n}\n\n.progress-bar {\n height: 1rem;\n line-height: 1rem;\n color: #fff;\n background-color: #007bff;\n transition: width 0.6s ease;\n}\n\n.progress-bar-striped {\n background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\n background-size: 1rem 1rem;\n}\n\n.progress-bar-animated {\n animation: progress-bar-stripes 1s linear infinite;\n}\n\n.media {\n display: flex;\n align-items: flex-start;\n}\n\n.media-body {\n flex: 1;\n}\n\n.list-group {\n display: flex;\n flex-direction: column;\n padding-left: 0;\n margin-bottom: 0;\n}\n\n.list-group-item-action {\n width: 100%;\n color: #495057;\n text-align: inherit;\n}\n\n.list-group-item-action:focus, .list-group-item-action:hover {\n color: #495057;\n text-decoration: none;\n background-color: #f8f9fa;\n}\n\n.list-group-item-action:active {\n color: #212529;\n background-color: #e9ecef;\n}\n\n.list-group-item {\n position: relative;\n display: block;\n padding: 0.75rem 1.25rem;\n margin-bottom: -1px;\n background-color: #fff;\n border: 1px solid rgba(0, 0, 0, 0.125);\n}\n\n.list-group-item:first-child {\n border-top-left-radius: 0.25rem;\n border-top-right-radius: 0.25rem;\n}\n\n.list-group-item:last-child {\n margin-bottom: 0;\n border-bottom-right-radius: 0.25rem;\n border-bottom-left-radius: 0.25rem;\n}\n\n.list-group-item:focus, .list-group-item:hover {\n text-decoration: none;\n}\n\n.list-group-item.disabled, .list-group-item:disabled {\n color: #868e96;\n background-color: #fff;\n}\n\n.list-group-item.active {\n z-index: 2;\n color: #fff;\n background-color: #007bff;\n border-color: #007bff;\n}\n\n.list-group-flush .list-group-item {\n border-right: 0;\n border-left: 0;\n border-radius: 0;\n}\n\n.list-group-flush:first-child .list-group-item:first-child {\n border-top: 0;\n}\n\n.list-group-flush:last-child .list-group-item:last-child {\n border-bottom: 0;\n}\n\n.list-group-item-primary {\n color: #004085;\n background-color: #b8daff;\n}\n\na.list-group-item-primary,\nbutton.list-group-item-primary {\n color: #004085;\n}\n\na.list-group-item-primary:focus, a.list-group-item-primary:hover,\nbutton.list-group-item-primary:focus,\nbutton.list-group-item-primary:hover {\n color: #004085;\n background-color: #9fcdff;\n}\n\na.list-group-item-primary.active,\nbutton.list-group-item-primary.active {\n color: #fff;\n background-color: #004085;\n border-color: #004085;\n}\n\n.list-group-item-secondary {\n color: #464a4e;\n background-color: #dddfe2;\n}\n\na.list-group-item-secondary,\nbutton.list-group-item-secondary {\n color: #464a4e;\n}\n\na.list-group-item-secondary:focus, a.list-group-item-secondary:hover,\nbutton.list-group-item-secondary:focus,\nbutton.list-group-item-secondary:hover {\n color: #464a4e;\n background-color: #cfd2d6;\n}\n\na.list-group-item-secondary.active,\nbutton.list-group-item-secondary.active {\n color: #fff;\n background-color: #464a4e;\n border-color: #464a4e;\n}\n\n.list-group-item-success {\n color: #155724;\n background-color: #c3e6cb;\n}\n\na.list-group-item-success,\nbutton.list-group-item-success {\n color: #155724;\n}\n\na.list-group-item-success:focus, a.list-group-item-success:hover,\nbutton.list-group-item-success:focus,\nbutton.list-group-item-success:hover {\n color: #155724;\n background-color: #b1dfbb;\n}\n\na.list-group-item-success.active,\nbutton.list-group-item-success.active {\n color: #fff;\n background-color: #155724;\n border-color: #155724;\n}\n\n.list-group-item-info {\n color: #0c5460;\n background-color: #bee5eb;\n}\n\na.list-group-item-info,\nbutton.list-group-item-info {\n color: #0c5460;\n}\n\na.list-group-item-info:focus, a.list-group-item-info:hover,\nbutton.list-group-item-info:focus,\nbutton.list-group-item-info:hover {\n color: #0c5460;\n background-color: #abdde5;\n}\n\na.list-group-item-info.active,\nbutton.list-group-item-info.active {\n color: #fff;\n background-color: #0c5460;\n border-color: #0c5460;\n}\n\n.list-group-item-warning {\n color: #856404;\n background-color: #ffeeba;\n}\n\na.list-group-item-warning,\nbutton.list-group-item-warning {\n color: #856404;\n}\n\na.list-group-item-warning:focus, a.list-group-item-warning:hover,\nbutton.list-group-item-warning:focus,\nbutton.list-group-item-warning:hover {\n color: #856404;\n background-color: #ffe8a1;\n}\n\na.list-group-item-warning.active,\nbutton.list-group-item-warning.active {\n color: #fff;\n background-color: #856404;\n border-color: #856404;\n}\n\n.list-group-item-danger {\n color: #721c24;\n background-color: #f5c6cb;\n}\n\na.list-group-item-danger,\nbutton.list-group-item-danger {\n color: #721c24;\n}\n\na.list-group-item-danger:focus, a.list-group-item-danger:hover,\nbutton.list-group-item-danger:focus,\nbutton.list-group-item-danger:hover {\n color: #721c24;\n background-color: #f1b0b7;\n}\n\na.list-group-item-danger.active,\nbutton.list-group-item-danger.active {\n color: #fff;\n background-color: #721c24;\n border-color: #721c24;\n}\n\n.list-group-item-light {\n color: #818182;\n background-color: #fdfdfe;\n}\n\na.list-group-item-light,\nbutton.list-group-item-light {\n color: #818182;\n}\n\na.list-group-item-light:focus, a.list-group-item-light:hover,\nbutton.list-group-item-light:focus,\nbutton.list-group-item-light:hover {\n color: #818182;\n background-color: #ececf6;\n}\n\na.list-group-item-light.active,\nbutton.list-group-item-light.active {\n color: #fff;\n background-color: #818182;\n border-color: #818182;\n}\n\n.list-group-item-dark {\n color: #1b1e21;\n background-color: #c6c8ca;\n}\n\na.list-group-item-dark,\nbutton.list-group-item-dark {\n color: #1b1e21;\n}\n\na.list-group-item-dark:focus, a.list-group-item-dark:hover,\nbutton.list-group-item-dark:focus,\nbutton.list-group-item-dark:hover {\n color: #1b1e21;\n background-color: #b9bbbe;\n}\n\na.list-group-item-dark.active,\nbutton.list-group-item-dark.active {\n color: #fff;\n background-color: #1b1e21;\n border-color: #1b1e21;\n}\n\n.close {\n float: right;\n font-size: 1.5rem;\n font-weight: bold;\n line-height: 1;\n color: #000;\n text-shadow: 0 1px 0 #fff;\n opacity: .5;\n}\n\n.close:focus, .close:hover {\n color: #000;\n text-decoration: none;\n opacity: .75;\n}\n\nbutton.close {\n padding: 0;\n background: transparent;\n border: 0;\n -webkit-appearance: none;\n}\n\n.modal-open {\n overflow: hidden;\n}\n\n.modal {\n position: fixed;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: 1050;\n display: none;\n overflow: hidden;\n outline: 0;\n}\n\n.modal.fade .modal-dialog {\n transition: transform 0.3s ease-out;\n transform: translate(0, -25%);\n}\n\n.modal.show .modal-dialog {\n transform: translate(0, 0);\n}\n\n.modal-open .modal {\n overflow-x: hidden;\n overflow-y: auto;\n}\n\n.modal-dialog {\n position: relative;\n width: auto;\n margin: 10px;\n}\n\n.modal-content {\n position: relative;\n display: flex;\n flex-direction: column;\n background-color: #fff;\n background-clip: padding-box;\n border: 1px solid rgba(0, 0, 0, 0.2);\n border-radius: 0.3rem;\n outline: 0;\n}\n\n.modal-backdrop {\n position: fixed;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: 1040;\n background-color: #000;\n}\n\n.modal-backdrop.fade {\n opacity: 0;\n}\n\n.modal-backdrop.show {\n opacity: 0.5;\n}\n\n.modal-header {\n display: flex;\n align-items: center;\n justify-content: space-between;\n padding: 15px;\n border-bottom: 1px solid #e9ecef;\n}\n\n.modal-title {\n margin-bottom: 0;\n line-height: 1.5;\n}\n\n.modal-body {\n position: relative;\n flex: 1 1 auto;\n padding: 15px;\n}\n\n.modal-footer {\n display: flex;\n align-items: center;\n justify-content: flex-end;\n padding: 15px;\n border-top: 1px solid #e9ecef;\n}\n\n.modal-footer > :not(:first-child) {\n margin-left: .25rem;\n}\n\n.modal-footer > :not(:last-child) {\n margin-right: .25rem;\n}\n\n.modal-scrollbar-measure {\n position: absolute;\n top: -9999px;\n width: 50px;\n height: 50px;\n overflow: scroll;\n}\n\n@media (min-width: 576px) {\n .modal-dialog {\n max-width: 500px;\n margin: 30px auto;\n }\n .modal-sm {\n max-width: 300px;\n }\n}\n\n@media (min-width: 992px) {\n .modal-lg {\n max-width: 800px;\n }\n}\n\n.tooltip {\n position: absolute;\n z-index: 1070;\n display: block;\n margin: 0;\n font-family: -apple-system, BlinkMacSystemFont, \"Segoe UI\", Roboto, \"Helvetica Neue\", Arial, sans-serif;\n font-style: normal;\n font-weight: normal;\n line-height: 1.5;\n text-align: left;\n text-align: start;\n text-decoration: none;\n text-shadow: none;\n text-transform: none;\n letter-spacing: normal;\n word-break: normal;\n word-spacing: normal;\n white-space: normal;\n line-break: auto;\n font-size: 0.875rem;\n word-wrap: break-word;\n opacity: 0;\n}\n\n.tooltip.show {\n opacity: 0.9;\n}\n\n.tooltip .arrow {\n position: absolute;\n display: block;\n width: 5px;\n height: 5px;\n}\n\n.tooltip.bs-tooltip-top, .tooltip.bs-tooltip-auto[x-placement^=\"top\"] {\n padding: 5px 0;\n}\n\n.tooltip.bs-tooltip-top .arrow, .tooltip.bs-tooltip-auto[x-placement^=\"top\"] .arrow {\n bottom: 0;\n}\n\n.tooltip.bs-tooltip-top .arrow::before, .tooltip.bs-tooltip-auto[x-placement^=\"top\"] .arrow::before {\n margin-left: -3px;\n content: \"\";\n border-width: 5px 5px 0;\n border-top-color: #000;\n}\n\n.tooltip.bs-tooltip-right, .tooltip.bs-tooltip-auto[x-placement^=\"right\"] {\n padding: 0 5px;\n}\n\n.tooltip.bs-tooltip-right .arrow, .tooltip.bs-tooltip-auto[x-placement^=\"right\"] .arrow {\n left: 0;\n}\n\n.tooltip.bs-tooltip-right .arrow::before, .tooltip.bs-tooltip-auto[x-placement^=\"right\"] .arrow::before {\n margin-top: -3px;\n content: \"\";\n border-width: 5px 5px 5px 0;\n border-right-color: #000;\n}\n\n.tooltip.bs-tooltip-bottom, .tooltip.bs-tooltip-auto[x-placement^=\"bottom\"] {\n padding: 5px 0;\n}\n\n.tooltip.bs-tooltip-bottom .arrow, .tooltip.bs-tooltip-auto[x-placement^=\"bottom\"] .arrow {\n top: 0;\n}\n\n.tooltip.bs-tooltip-bottom .arrow::before, .tooltip.bs-tooltip-auto[x-placement^=\"bottom\"] .arrow::before {\n margin-left: -3px;\n content: \"\";\n border-width: 0 5px 5px;\n border-bottom-color: #000;\n}\n\n.tooltip.bs-tooltip-left, .tooltip.bs-tooltip-auto[x-placement^=\"left\"] {\n padding: 0 5px;\n}\n\n.tooltip.bs-tooltip-left .arrow, .tooltip.bs-tooltip-auto[x-placement^=\"left\"] .arrow {\n right: 0;\n}\n\n.tooltip.bs-tooltip-left .arrow::before, .tooltip.bs-tooltip-auto[x-placement^=\"left\"] .arrow::before {\n right: 0;\n margin-top: -3px;\n content: \"\";\n border-width: 5px 0 5px 5px;\n border-left-color: #000;\n}\n\n.tooltip .arrow::before {\n position: absolute;\n border-color: transparent;\n border-style: solid;\n}\n\n.tooltip-inner {\n max-width: 200px;\n padding: 3px 8px;\n color: #fff;\n text-align: center;\n background-color: #000;\n border-radius: 0.25rem;\n}\n\n.popover {\n position: absolute;\n top: 0;\n left: 0;\n z-index: 1060;\n display: block;\n max-width: 276px;\n padding: 1px;\n font-family: -apple-system, BlinkMacSystemFont, \"Segoe UI\", Roboto, \"Helvetica Neue\", Arial, sans-serif;\n font-style: normal;\n font-weight: normal;\n line-height: 1.5;\n text-align: left;\n text-align: start;\n text-decoration: none;\n text-shadow: none;\n text-transform: none;\n letter-spacing: normal;\n word-break: normal;\n word-spacing: normal;\n white-space: normal;\n line-break: auto;\n font-size: 0.875rem;\n word-wrap: break-word;\n background-color: #fff;\n background-clip: padding-box;\n border: 1px solid rgba(0, 0, 0, 0.2);\n border-radius: 0.3rem;\n}\n\n.popover .arrow {\n position: absolute;\n display: block;\n width: 10px;\n height: 5px;\n}\n\n.popover .arrow::before,\n.popover .arrow::after {\n position: absolute;\n display: block;\n border-color: transparent;\n border-style: solid;\n}\n\n.popover .arrow::before {\n content: \"\";\n border-width: 11px;\n}\n\n.popover .arrow::after {\n content: \"\";\n border-width: 11px;\n}\n\n.popover.bs-popover-top, .popover.bs-popover-auto[x-placement^=\"top\"] {\n margin-bottom: 10px;\n}\n\n.popover.bs-popover-top .arrow, .popover.bs-popover-auto[x-placement^=\"top\"] .arrow {\n bottom: 0;\n}\n\n.popover.bs-popover-top .arrow::before, .popover.bs-popover-auto[x-placement^=\"top\"] .arrow::before,\n.popover.bs-popover-top .arrow::after, .popover.bs-popover-auto[x-placement^=\"top\"] .arrow::after {\n border-bottom-width: 0;\n}\n\n.popover.bs-popover-top .arrow::before, .popover.bs-popover-auto[x-placement^=\"top\"] .arrow::before {\n bottom: -11px;\n margin-left: -6px;\n border-top-color: rgba(0, 0, 0, 0.25);\n}\n\n.popover.bs-popover-top .arrow::after, .popover.bs-popover-auto[x-placement^=\"top\"] .arrow::after {\n bottom: -10px;\n margin-left: -6px;\n border-top-color: #fff;\n}\n\n.popover.bs-popover-right, .popover.bs-popover-auto[x-placement^=\"right\"] {\n margin-left: 10px;\n}\n\n.popover.bs-popover-right .arrow, .popover.bs-popover-auto[x-placement^=\"right\"] .arrow {\n left: 0;\n}\n\n.popover.bs-popover-right .arrow::before, .popover.bs-popover-auto[x-placement^=\"right\"] .arrow::before,\n.popover.bs-popover-right .arrow::after, .popover.bs-popover-auto[x-placement^=\"right\"] .arrow::after {\n margin-top: -8px;\n border-left-width: 0;\n}\n\n.popover.bs-popover-right .arrow::before, .popover.bs-popover-auto[x-placement^=\"right\"] .arrow::before {\n left: -11px;\n border-right-color: rgba(0, 0, 0, 0.25);\n}\n\n.popover.bs-popover-right .arrow::after, .popover.bs-popover-auto[x-placement^=\"right\"] .arrow::after {\n left: -10px;\n border-right-color: #fff;\n}\n\n.popover.bs-popover-bottom, .popover.bs-popover-auto[x-placement^=\"bottom\"] {\n margin-top: 10px;\n}\n\n.popover.bs-popover-bottom .arrow, .popover.bs-popover-auto[x-placement^=\"bottom\"] .arrow {\n top: 0;\n}\n\n.popover.bs-popover-bottom .arrow::before, .popover.bs-popover-auto[x-placement^=\"bottom\"] .arrow::before,\n.popover.bs-popover-bottom .arrow::after, .popover.bs-popover-auto[x-placement^=\"bottom\"] .arrow::after {\n margin-left: -7px;\n border-top-width: 0;\n}\n\n.popover.bs-popover-bottom .arrow::before, .popover.bs-popover-auto[x-placement^=\"bottom\"] .arrow::before {\n top: -11px;\n border-bottom-color: rgba(0, 0, 0, 0.25);\n}\n\n.popover.bs-popover-bottom .arrow::after, .popover.bs-popover-auto[x-placement^=\"bottom\"] .arrow::after {\n top: -10px;\n border-bottom-color: #fff;\n}\n\n.popover.bs-popover-bottom .popover-header::before, .popover.bs-popover-auto[x-placement^=\"bottom\"] .popover-header::before {\n position: absolute;\n top: 0;\n left: 50%;\n display: block;\n width: 20px;\n margin-left: -10px;\n content: \"\";\n border-bottom: 1px solid #f7f7f7;\n}\n\n.popover.bs-popover-left, .popover.bs-popover-auto[x-placement^=\"left\"] {\n margin-right: 10px;\n}\n\n.popover.bs-popover-left .arrow, .popover.bs-popover-auto[x-placement^=\"left\"] .arrow {\n right: 0;\n}\n\n.popover.bs-popover-left .arrow::before, .popover.bs-popover-auto[x-placement^=\"left\"] .arrow::before,\n.popover.bs-popover-left .arrow::after, .popover.bs-popover-auto[x-placement^=\"left\"] .arrow::after {\n margin-top: -8px;\n border-right-width: 0;\n}\n\n.popover.bs-popover-left .arrow::before, .popover.bs-popover-auto[x-placement^=\"left\"] .arrow::before {\n right: -11px;\n border-left-color: rgba(0, 0, 0, 0.25);\n}\n\n.popover.bs-popover-left .arrow::after, .popover.bs-popover-auto[x-placement^=\"left\"] .arrow::after {\n right: -10px;\n border-left-color: #fff;\n}\n\n.popover-header {\n padding: 8px 14px;\n margin-bottom: 0;\n font-size: 1rem;\n color: inherit;\n background-color: #f7f7f7;\n border-bottom: 1px solid #ebebeb;\n border-top-left-radius: calc(0.3rem - 1px);\n border-top-right-radius: calc(0.3rem - 1px);\n}\n\n.popover-header:empty {\n display: none;\n}\n\n.popover-body {\n padding: 9px 14px;\n color: #212529;\n}\n\n.carousel {\n position: relative;\n}\n\n.carousel-inner {\n position: relative;\n width: 100%;\n overflow: hidden;\n}\n\n.carousel-item {\n position: relative;\n display: none;\n align-items: center;\n width: 100%;\n transition: transform 0.6s ease;\n backface-visibility: hidden;\n perspective: 1000px;\n}\n\n.carousel-item.active,\n.carousel-item-next,\n.carousel-item-prev {\n display: block;\n}\n\n.carousel-item-next,\n.carousel-item-prev {\n position: absolute;\n top: 0;\n}\n\n.carousel-item-next.carousel-item-left,\n.carousel-item-prev.carousel-item-right {\n transform: translateX(0);\n}\n\n@supports (transform-style: preserve-3d) {\n .carousel-item-next.carousel-item-left,\n .carousel-item-prev.carousel-item-right {\n transform: translate3d(0, 0, 0);\n }\n}\n\n.carousel-item-next,\n.active.carousel-item-right {\n transform: translateX(100%);\n}\n\n@supports (transform-style: preserve-3d) {\n .carousel-item-next,\n .active.carousel-item-right {\n transform: translate3d(100%, 0, 0);\n }\n}\n\n.carousel-item-prev,\n.active.carousel-item-left {\n transform: translateX(-100%);\n}\n\n@supports (transform-style: preserve-3d) {\n .carousel-item-prev,\n .active.carousel-item-left {\n transform: translate3d(-100%, 0, 0);\n }\n}\n\n.carousel-control-prev,\n.carousel-control-next {\n position: absolute;\n top: 0;\n bottom: 0;\n display: flex;\n align-items: center;\n justify-content: center;\n width: 15%;\n color: #fff;\n text-align: center;\n opacity: 0.5;\n}\n\n.carousel-control-prev:focus, .carousel-control-prev:hover,\n.carousel-control-next:focus,\n.carousel-control-next:hover {\n color: #fff;\n text-decoration: none;\n outline: 0;\n opacity: .9;\n}\n\n.carousel-control-prev {\n left: 0;\n}\n\n.carousel-control-next {\n right: 0;\n}\n\n.carousel-control-prev-icon,\n.carousel-control-next-icon {\n display: inline-block;\n width: 20px;\n height: 20px;\n background: transparent no-repeat center center;\n background-size: 100% 100%;\n}\n\n.carousel-control-prev-icon {\n background-image: url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' fill='%23fff' viewBox='0 0 8 8'%3E%3Cpath d='M4 0l-4 4 4 4 1.5-1.5-2.5-2.5 2.5-2.5-1.5-1.5z'/%3E%3C/svg%3E\");\n}\n\n.carousel-control-next-icon {\n background-image: url(\"data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' fill='%23fff' viewBox='0 0 8 8'%3E%3Cpath d='M1.5 0l-1.5 1.5 2.5 2.5-2.5 2.5 1.5 1.5 4-4-4-4z'/%3E%3C/svg%3E\");\n}\n\n.carousel-indicators {\n position: absolute;\n right: 0;\n bottom: 10px;\n left: 0;\n z-index: 15;\n display: flex;\n justify-content: center;\n padding-left: 0;\n margin-right: 15%;\n margin-left: 15%;\n list-style: none;\n}\n\n.carousel-indicators li {\n position: relative;\n flex: 0 1 auto;\n width: 30px;\n height: 3px;\n margin-right: 3px;\n margin-left: 3px;\n text-indent: -999px;\n background-color: rgba(255, 255, 255, 0.5);\n}\n\n.carousel-indicators li::before {\n position: absolute;\n top: -10px;\n left: 0;\n display: inline-block;\n width: 100%;\n height: 10px;\n content: \"\";\n}\n\n.carousel-indicators li::after {\n position: absolute;\n bottom: -10px;\n left: 0;\n display: inline-block;\n width: 100%;\n height: 10px;\n content: \"\";\n}\n\n.carousel-indicators .active {\n background-color: #fff;\n}\n\n.carousel-caption {\n position: absolute;\n right: 15%;\n bottom: 20px;\n left: 15%;\n z-index: 10;\n padding-top: 20px;\n padding-bottom: 20px;\n color: #fff;\n text-align: center;\n}\n\n.align-baseline {\n vertical-align: baseline !important;\n}\n\n.align-top {\n vertical-align: top !important;\n}\n\n.align-middle {\n vertical-align: middle !important;\n}\n\n.align-bottom {\n vertical-align: bottom !important;\n}\n\n.align-text-bottom {\n vertical-align: text-bottom !important;\n}\n\n.align-text-top {\n vertical-align: text-top !important;\n}\n\n.bg-primary {\n background-color: #007bff !important;\n}\n\na.bg-primary:focus, a.bg-primary:hover {\n background-color: #0062cc !important;\n}\n\n.bg-secondary {\n background-color: #868e96 !important;\n}\n\na.bg-secondary:focus, a.bg-secondary:hover {\n background-color: #6c757d !important;\n}\n\n.bg-success {\n background-color: #28a745 !important;\n}\n\na.bg-success:focus, a.bg-success:hover {\n background-color: #1e7e34 !important;\n}\n\n.bg-info {\n background-color: #17a2b8 !important;\n}\n\na.bg-info:focus, a.bg-info:hover {\n background-color: #117a8b !important;\n}\n\n.bg-warning {\n background-color: #ffc107 !important;\n}\n\na.bg-warning:focus, a.bg-warning:hover {\n background-color: #d39e00 !important;\n}\n\n.bg-danger {\n background-color: #dc3545 !important;\n}\n\na.bg-danger:focus, a.bg-danger:hover {\n background-color: #bd2130 !important;\n}\n\n.bg-light {\n background-color: #f8f9fa !important;\n}\n\na.bg-light:focus, a.bg-light:hover {\n background-color: #dae0e5 !important;\n}\n\n.bg-dark {\n background-color: #343a40 !important;\n}\n\na.bg-dark:focus, a.bg-dark:hover {\n background-color: #1d2124 !important;\n}\n\n.bg-white {\n background-color: #fff !important;\n}\n\n.bg-transparent {\n background-color: transparent !important;\n}\n\n.border {\n border: 1px solid #e9ecef !important;\n}\n\n.border-0 {\n border: 0 !important;\n}\n\n.border-top-0 {\n border-top: 0 !important;\n}\n\n.border-right-0 {\n border-right: 0 !important;\n}\n\n.border-bottom-0 {\n border-bottom: 0 !important;\n}\n\n.border-left-0 {\n border-left: 0 !important;\n}\n\n.border-primary {\n border-color: #007bff !important;\n}\n\n.border-secondary {\n border-color: #868e96 !important;\n}\n\n.border-success {\n border-color: #28a745 !important;\n}\n\n.border-info {\n border-color: #17a2b8 !important;\n}\n\n.border-warning {\n border-color: #ffc107 !important;\n}\n\n.border-danger {\n border-color: #dc3545 !important;\n}\n\n.border-light {\n border-color: #f8f9fa !important;\n}\n\n.border-dark {\n border-color: #343a40 !important;\n}\n\n.border-white {\n border-color: #fff !important;\n}\n\n.rounded {\n border-radius: 0.25rem !important;\n}\n\n.rounded-top {\n border-top-left-radius: 0.25rem !important;\n border-top-right-radius: 0.25rem !important;\n}\n\n.rounded-right {\n border-top-right-radius: 0.25rem !important;\n border-bottom-right-radius: 0.25rem !important;\n}\n\n.rounded-bottom {\n border-bottom-right-radius: 0.25rem !important;\n border-bottom-left-radius: 0.25rem !important;\n}\n\n.rounded-left {\n border-top-left-radius: 0.25rem !important;\n border-bottom-left-radius: 0.25rem !important;\n}\n\n.rounded-circle {\n border-radius: 50%;\n}\n\n.rounded-0 {\n border-radius: 0;\n}\n\n.clearfix::after {\n display: block;\n clear: both;\n content: \"\";\n}\n\n.d-none {\n display: none !important;\n}\n\n.d-inline {\n display: inline !important;\n}\n\n.d-inline-block {\n display: inline-block !important;\n}\n\n.d-block {\n display: block !important;\n}\n\n.d-table {\n display: table !important;\n}\n\n.d-table-cell {\n display: table-cell !important;\n}\n\n.d-flex {\n display: flex !important;\n}\n\n.d-inline-flex {\n display: inline-flex !important;\n}\n\n@media (min-width: 576px) {\n .d-sm-none {\n display: none !important;\n }\n .d-sm-inline {\n display: inline !important;\n }\n .d-sm-inline-block {\n display: inline-block !important;\n }\n .d-sm-block {\n display: block !important;\n }\n .d-sm-table {\n display: table !important;\n }\n .d-sm-table-cell {\n display: table-cell !important;\n }\n .d-sm-flex {\n display: flex !important;\n }\n .d-sm-inline-flex {\n display: inline-flex !important;\n }\n}\n\n@media (min-width: 768px) {\n .d-md-none {\n display: none !important;\n }\n .d-md-inline {\n display: inline !important;\n }\n .d-md-inline-block {\n display: inline-block !important;\n }\n .d-md-block {\n display: block !important;\n }\n .d-md-table {\n display: table !important;\n }\n .d-md-table-cell {\n display: table-cell !important;\n }\n .d-md-flex {\n display: flex !important;\n }\n .d-md-inline-flex {\n display: inline-flex !important;\n }\n}\n\n@media (min-width: 992px) {\n .d-lg-none {\n display: none !important;\n }\n .d-lg-inline {\n display: inline !important;\n }\n .d-lg-inline-block {\n display: inline-block !important;\n }\n .d-lg-block {\n display: block !important;\n }\n .d-lg-table {\n display: table !important;\n }\n .d-lg-table-cell {\n display: table-cell !important;\n }\n .d-lg-flex {\n display: flex !important;\n }\n .d-lg-inline-flex {\n display: inline-flex !important;\n }\n}\n\n@media (min-width: 1200px) {\n .d-xl-none {\n display: none !important;\n }\n .d-xl-inline {\n display: inline !important;\n }\n .d-xl-inline-block {\n display: inline-block !important;\n }\n .d-xl-block {\n display: block !important;\n }\n .d-xl-table {\n display: table !important;\n }\n .d-xl-table-cell {\n display: table-cell !important;\n }\n .d-xl-flex {\n display: flex !important;\n }\n .d-xl-inline-flex {\n display: inline-flex !important;\n }\n}\n\n.d-print-block {\n display: none !important;\n}\n\n@media print {\n .d-print-block {\n display: block !important;\n }\n}\n\n.d-print-inline {\n display: none !important;\n}\n\n@media print {\n .d-print-inline {\n display: inline !important;\n }\n}\n\n.d-print-inline-block {\n display: none !important;\n}\n\n@media print {\n .d-print-inline-block {\n display: inline-block !important;\n }\n}\n\n@media print {\n .d-print-none {\n display: none !important;\n }\n}\n\n.embed-responsive {\n position: relative;\n display: block;\n width: 100%;\n padding: 0;\n overflow: hidden;\n}\n\n.embed-responsive::before {\n display: block;\n content: \"\";\n}\n\n.embed-responsive .embed-responsive-item,\n.embed-responsive iframe,\n.embed-responsive embed,\n.embed-responsive object,\n.embed-responsive video {\n position: absolute;\n top: 0;\n bottom: 0;\n left: 0;\n width: 100%;\n height: 100%;\n border: 0;\n}\n\n.embed-responsive-21by9::before {\n padding-top: 42.857143%;\n}\n\n.embed-responsive-16by9::before {\n padding-top: 56.25%;\n}\n\n.embed-responsive-4by3::before {\n padding-top: 75%;\n}\n\n.embed-responsive-1by1::before {\n padding-top: 100%;\n}\n\n.flex-row {\n flex-direction: row !important;\n}\n\n.flex-column {\n flex-direction: column !important;\n}\n\n.flex-row-reverse {\n flex-direction: row-reverse !important;\n}\n\n.flex-column-reverse {\n flex-direction: column-reverse !important;\n}\n\n.flex-wrap {\n flex-wrap: wrap !important;\n}\n\n.flex-nowrap {\n flex-wrap: nowrap !important;\n}\n\n.flex-wrap-reverse {\n flex-wrap: wrap-reverse !important;\n}\n\n.justify-content-start {\n justify-content: flex-start !important;\n}\n\n.justify-content-end {\n justify-content: flex-end !important;\n}\n\n.justify-content-center {\n justify-content: center !important;\n}\n\n.justify-content-between {\n justify-content: space-between !important;\n}\n\n.justify-content-around {\n justify-content: space-around !important;\n}\n\n.align-items-start {\n align-items: flex-start !important;\n}\n\n.align-items-end {\n align-items: flex-end !important;\n}\n\n.align-items-center {\n align-items: center !important;\n}\n\n.align-items-baseline {\n align-items: baseline !important;\n}\n\n.align-items-stretch {\n align-items: stretch !important;\n}\n\n.align-content-start {\n align-content: flex-start !important;\n}\n\n.align-content-end {\n align-content: flex-end !important;\n}\n\n.align-content-center {\n align-content: center !important;\n}\n\n.align-content-between {\n align-content: space-between !important;\n}\n\n.align-content-around {\n align-content: space-around !important;\n}\n\n.align-content-stretch {\n align-content: stretch !important;\n}\n\n.align-self-auto {\n align-self: auto !important;\n}\n\n.align-self-start {\n align-self: flex-start !important;\n}\n\n.align-self-end {\n align-self: flex-end !important;\n}\n\n.align-self-center {\n align-self: center !important;\n}\n\n.align-self-baseline {\n align-self: baseline !important;\n}\n\n.align-self-stretch {\n align-self: stretch !important;\n}\n\n@media (min-width: 576px) {\n .flex-sm-row {\n flex-direction: row !important;\n }\n .flex-sm-column {\n flex-direction: column !important;\n }\n .flex-sm-row-reverse {\n flex-direction: row-reverse !important;\n }\n .flex-sm-column-reverse {\n flex-direction: column-reverse !important;\n }\n .flex-sm-wrap {\n flex-wrap: wrap !important;\n }\n .flex-sm-nowrap {\n flex-wrap: nowrap !important;\n }\n .flex-sm-wrap-reverse {\n flex-wrap: wrap-reverse !important;\n }\n .justify-content-sm-start {\n justify-content: flex-start !important;\n }\n .justify-content-sm-end {\n justify-content: flex-end !important;\n }\n .justify-content-sm-center {\n justify-content: center !important;\n }\n .justify-content-sm-between {\n justify-content: space-between !important;\n }\n .justify-content-sm-around {\n justify-content: space-around !important;\n }\n .align-items-sm-start {\n align-items: flex-start !important;\n }\n .align-items-sm-end {\n align-items: flex-end !important;\n }\n .align-items-sm-center {\n align-items: center !important;\n }\n .align-items-sm-baseline {\n align-items: baseline !important;\n }\n .align-items-sm-stretch {\n align-items: stretch !important;\n }\n .align-content-sm-start {\n align-content: flex-start !important;\n }\n .align-content-sm-end {\n align-content: flex-end !important;\n }\n .align-content-sm-center {\n align-content: center !important;\n }\n .align-content-sm-between {\n align-content: space-between !important;\n }\n .align-content-sm-around {\n align-content: space-around !important;\n }\n .align-content-sm-stretch {\n align-content: stretch !important;\n }\n .align-self-sm-auto {\n align-self: auto !important;\n }\n .align-self-sm-start {\n align-self: flex-start !important;\n }\n .align-self-sm-end {\n align-self: flex-end !important;\n }\n .align-self-sm-center {\n align-self: center !important;\n }\n .align-self-sm-baseline {\n align-self: baseline !important;\n }\n .align-self-sm-stretch {\n align-self: stretch !important;\n }\n}\n\n@media (min-width: 768px) {\n .flex-md-row {\n flex-direction: row !important;\n }\n .flex-md-column {\n flex-direction: column !important;\n }\n .flex-md-row-reverse {\n flex-direction: row-reverse !important;\n }\n .flex-md-column-reverse {\n flex-direction: column-reverse !important;\n }\n .flex-md-wrap {\n flex-wrap: wrap !important;\n }\n .flex-md-nowrap {\n flex-wrap: nowrap !important;\n }\n .flex-md-wrap-reverse {\n flex-wrap: wrap-reverse !important;\n }\n .justify-content-md-start {\n justify-content: flex-start !important;\n }\n .justify-content-md-end {\n justify-content: flex-end !important;\n }\n .justify-content-md-center {\n justify-content: center !important;\n }\n .justify-content-md-between {\n justify-content: space-between !important;\n }\n .justify-content-md-around {\n justify-content: space-around !important;\n }\n .align-items-md-start {\n align-items: flex-start !important;\n }\n .align-items-md-end {\n align-items: flex-end !important;\n }\n .align-items-md-center {\n align-items: center !important;\n }\n .align-items-md-baseline {\n align-items: baseline !important;\n }\n .align-items-md-stretch {\n align-items: stretch !important;\n }\n .align-content-md-start {\n align-content: flex-start !important;\n }\n .align-content-md-end {\n align-content: flex-end !important;\n }\n .align-content-md-center {\n align-content: center !important;\n }\n .align-content-md-between {\n align-content: space-between !important;\n }\n .align-content-md-around {\n align-content: space-around !important;\n }\n .align-content-md-stretch {\n align-content: stretch !important;\n }\n .align-self-md-auto {\n align-self: auto !important;\n }\n .align-self-md-start {\n align-self: flex-start !important;\n }\n .align-self-md-end {\n align-self: flex-end !important;\n }\n .align-self-md-center {\n align-self: center !important;\n }\n .align-self-md-baseline {\n align-self: baseline !important;\n }\n .align-self-md-stretch {\n align-self: stretch !important;\n }\n}\n\n@media (min-width: 992px) {\n .flex-lg-row {\n flex-direction: row !important;\n }\n .flex-lg-column {\n flex-direction: column !important;\n }\n .flex-lg-row-reverse {\n flex-direction: row-reverse !important;\n }\n .flex-lg-column-reverse {\n flex-direction: column-reverse !important;\n }\n .flex-lg-wrap {\n flex-wrap: wrap !important;\n }\n .flex-lg-nowrap {\n flex-wrap: nowrap !important;\n }\n .flex-lg-wrap-reverse {\n flex-wrap: wrap-reverse !important;\n }\n .justify-content-lg-start {\n justify-content: flex-start !important;\n }\n .justify-content-lg-end {\n justify-content: flex-end !important;\n }\n .justify-content-lg-center {\n justify-content: center !important;\n }\n .justify-content-lg-between {\n justify-content: space-between !important;\n }\n .justify-content-lg-around {\n justify-content: space-around !important;\n }\n .align-items-lg-start {\n align-items: flex-start !important;\n }\n .align-items-lg-end {\n align-items: flex-end !important;\n }\n .align-items-lg-center {\n align-items: center !important;\n }\n .align-items-lg-baseline {\n align-items: baseline !important;\n }\n .align-items-lg-stretch {\n align-items: stretch !important;\n }\n .align-content-lg-start {\n align-content: flex-start !important;\n }\n .align-content-lg-end {\n align-content: flex-end !important;\n }\n .align-content-lg-center {\n align-content: center !important;\n }\n .align-content-lg-between {\n align-content: space-between !important;\n }\n .align-content-lg-around {\n align-content: space-around !important;\n }\n .align-content-lg-stretch {\n align-content: stretch !important;\n }\n .align-self-lg-auto {\n align-self: auto !important;\n }\n .align-self-lg-start {\n align-self: flex-start !important;\n }\n .align-self-lg-end {\n align-self: flex-end !important;\n }\n .align-self-lg-center {\n align-self: center !important;\n }\n .align-self-lg-baseline {\n align-self: baseline !important;\n }\n .align-self-lg-stretch {\n align-self: stretch !important;\n }\n}\n\n@media (min-width: 1200px) {\n .flex-xl-row {\n flex-direction: row !important;\n }\n .flex-xl-column {\n flex-direction: column !important;\n }\n .flex-xl-row-reverse {\n flex-direction: row-reverse !important;\n }\n .flex-xl-column-reverse {\n flex-direction: column-reverse !important;\n }\n .flex-xl-wrap {\n flex-wrap: wrap !important;\n }\n .flex-xl-nowrap {\n flex-wrap: nowrap !important;\n }\n .flex-xl-wrap-reverse {\n flex-wrap: wrap-reverse !important;\n }\n .justify-content-xl-start {\n justify-content: flex-start !important;\n }\n .justify-content-xl-end {\n justify-content: flex-end !important;\n }\n .justify-content-xl-center {\n justify-content: center !important;\n }\n .justify-content-xl-between {\n justify-content: space-between !important;\n }\n .justify-content-xl-around {\n justify-content: space-around !important;\n }\n .align-items-xl-start {\n align-items: flex-start !important;\n }\n .align-items-xl-end {\n align-items: flex-end !important;\n }\n .align-items-xl-center {\n align-items: center !important;\n }\n .align-items-xl-baseline {\n align-items: baseline !important;\n }\n .align-items-xl-stretch {\n align-items: stretch !important;\n }\n .align-content-xl-start {\n align-content: flex-start !important;\n }\n .align-content-xl-end {\n align-content: flex-end !important;\n }\n .align-content-xl-center {\n align-content: center !important;\n }\n .align-content-xl-between {\n align-content: space-between !important;\n }\n .align-content-xl-around {\n align-content: space-around !important;\n }\n .align-content-xl-stretch {\n align-content: stretch !important;\n }\n .align-self-xl-auto {\n align-self: auto !important;\n }\n .align-self-xl-start {\n align-self: flex-start !important;\n }\n .align-self-xl-end {\n align-self: flex-end !important;\n }\n .align-self-xl-center {\n align-self: center !important;\n }\n .align-self-xl-baseline {\n align-self: baseline !important;\n }\n .align-self-xl-stretch {\n align-self: stretch !important;\n }\n}\n\n.float-left {\n float: left !important;\n}\n\n.float-right {\n float: right !important;\n}\n\n.float-none {\n float: none !important;\n}\n\n@media (min-width: 576px) {\n .float-sm-left {\n float: left !important;\n }\n .float-sm-right {\n float: right !important;\n }\n .float-sm-none {\n float: none !important;\n }\n}\n\n@media (min-width: 768px) {\n .float-md-left {\n float: left !important;\n }\n .float-md-right {\n float: right !important;\n }\n .float-md-none {\n float: none !important;\n }\n}\n\n@media (min-width: 992px) {\n .float-lg-left {\n float: left !important;\n }\n .float-lg-right {\n float: right !important;\n }\n .float-lg-none {\n float: none !important;\n }\n}\n\n@media (min-width: 1200px) {\n .float-xl-left {\n float: left !important;\n }\n .float-xl-right {\n float: right !important;\n }\n .float-xl-none {\n float: none !important;\n }\n}\n\n.fixed-top {\n position: fixed;\n top: 0;\n right: 0;\n left: 0;\n z-index: 1030;\n}\n\n.fixed-bottom {\n position: fixed;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: 1030;\n}\n\n@supports (position: sticky) {\n .sticky-top {\n position: sticky;\n top: 0;\n z-index: 1020;\n }\n}\n\n.sr-only {\n position: absolute;\n width: 1px;\n height: 1px;\n padding: 0;\n overflow: hidden;\n clip: rect(0, 0, 0, 0);\n white-space: nowrap;\n clip-path: inset(50%);\n border: 0;\n}\n\n.sr-only-focusable:active, .sr-only-focusable:focus {\n position: static;\n width: auto;\n height: auto;\n overflow: visible;\n clip: auto;\n white-space: normal;\n clip-path: none;\n}\n\n.w-25 {\n width: 25% !important;\n}\n\n.w-50 {\n width: 50% !important;\n}\n\n.w-75 {\n width: 75% !important;\n}\n\n.w-100 {\n width: 100% !important;\n}\n\n.h-25 {\n height: 25% !important;\n}\n\n.h-50 {\n height: 50% !important;\n}\n\n.h-75 {\n height: 75% !important;\n}\n\n.h-100 {\n height: 100% !important;\n}\n\n.mw-100 {\n max-width: 100% !important;\n}\n\n.mh-100 {\n max-height: 100% !important;\n}\n\n.m-0 {\n margin: 0 !important;\n}\n\n.mt-0 {\n margin-top: 0 !important;\n}\n\n.mr-0 {\n margin-right: 0 !important;\n}\n\n.mb-0 {\n margin-bottom: 0 !important;\n}\n\n.ml-0 {\n margin-left: 0 !important;\n}\n\n.mx-0 {\n margin-right: 0 !important;\n margin-left: 0 !important;\n}\n\n.my-0 {\n margin-top: 0 !important;\n margin-bottom: 0 !important;\n}\n\n.m-1 {\n margin: 0.25rem !important;\n}\n\n.mt-1 {\n margin-top: 0.25rem !important;\n}\n\n.mr-1 {\n margin-right: 0.25rem !important;\n}\n\n.mb-1 {\n margin-bottom: 0.25rem !important;\n}\n\n.ml-1 {\n margin-left: 0.25rem !important;\n}\n\n.mx-1 {\n margin-right: 0.25rem !important;\n margin-left: 0.25rem !important;\n}\n\n.my-1 {\n margin-top: 0.25rem !important;\n margin-bottom: 0.25rem !important;\n}\n\n.m-2 {\n margin: 0.5rem !important;\n}\n\n.mt-2 {\n margin-top: 0.5rem !important;\n}\n\n.mr-2 {\n margin-right: 0.5rem !important;\n}\n\n.mb-2 {\n margin-bottom: 0.5rem !important;\n}\n\n.ml-2 {\n margin-left: 0.5rem !important;\n}\n\n.mx-2 {\n margin-right: 0.5rem !important;\n margin-left: 0.5rem !important;\n}\n\n.my-2 {\n margin-top: 0.5rem !important;\n margin-bottom: 0.5rem !important;\n}\n\n.m-3 {\n margin: 1rem !important;\n}\n\n.mt-3 {\n margin-top: 1rem !important;\n}\n\n.mr-3 {\n margin-right: 1rem !important;\n}\n\n.mb-3 {\n margin-bottom: 1rem !important;\n}\n\n.ml-3 {\n margin-left: 1rem !important;\n}\n\n.mx-3 {\n margin-right: 1rem !important;\n margin-left: 1rem !important;\n}\n\n.my-3 {\n margin-top: 1rem !important;\n margin-bottom: 1rem !important;\n}\n\n.m-4 {\n margin: 1.5rem !important;\n}\n\n.mt-4 {\n margin-top: 1.5rem !important;\n}\n\n.mr-4 {\n margin-right: 1.5rem !important;\n}\n\n.mb-4 {\n margin-bottom: 1.5rem !important;\n}\n\n.ml-4 {\n margin-left: 1.5rem !important;\n}\n\n.mx-4 {\n margin-right: 1.5rem !important;\n margin-left: 1.5rem !important;\n}\n\n.my-4 {\n margin-top: 1.5rem !important;\n margin-bottom: 1.5rem !important;\n}\n\n.m-5 {\n margin: 3rem !important;\n}\n\n.mt-5 {\n margin-top: 3rem !important;\n}\n\n.mr-5 {\n margin-right: 3rem !important;\n}\n\n.mb-5 {\n margin-bottom: 3rem !important;\n}\n\n.ml-5 {\n margin-left: 3rem !important;\n}\n\n.mx-5 {\n margin-right: 3rem !important;\n margin-left: 3rem !important;\n}\n\n.my-5 {\n margin-top: 3rem !important;\n margin-bottom: 3rem !important;\n}\n\n.p-0 {\n padding: 0 !important;\n}\n\n.pt-0 {\n padding-top: 0 !important;\n}\n\n.pr-0 {\n padding-right: 0 !important;\n}\n\n.pb-0 {\n padding-bottom: 0 !important;\n}\n\n.pl-0 {\n padding-left: 0 !important;\n}\n\n.px-0 {\n padding-right: 0 !important;\n padding-left: 0 !important;\n}\n\n.py-0 {\n padding-top: 0 !important;\n padding-bottom: 0 !important;\n}\n\n.p-1 {\n padding: 0.25rem !important;\n}\n\n.pt-1 {\n padding-top: 0.25rem !important;\n}\n\n.pr-1 {\n padding-right: 0.25rem !important;\n}\n\n.pb-1 {\n padding-bottom: 0.25rem !important;\n}\n\n.pl-1 {\n padding-left: 0.25rem !important;\n}\n\n.px-1 {\n padding-right: 0.25rem !important;\n padding-left: 0.25rem !important;\n}\n\n.py-1 {\n padding-top: 0.25rem !important;\n padding-bottom: 0.25rem !important;\n}\n\n.p-2 {\n padding: 0.5rem !important;\n}\n\n.pt-2 {\n padding-top: 0.5rem !important;\n}\n\n.pr-2 {\n padding-right: 0.5rem !important;\n}\n\n.pb-2 {\n padding-bottom: 0.5rem !important;\n}\n\n.pl-2 {\n padding-left: 0.5rem !important;\n}\n\n.px-2 {\n padding-right: 0.5rem !important;\n padding-left: 0.5rem !important;\n}\n\n.py-2 {\n padding-top: 0.5rem !important;\n padding-bottom: 0.5rem !important;\n}\n\n.p-3 {\n padding: 1rem !important;\n}\n\n.pt-3 {\n padding-top: 1rem !important;\n}\n\n.pr-3 {\n padding-right: 1rem !important;\n}\n\n.pb-3 {\n padding-bottom: 1rem !important;\n}\n\n.pl-3 {\n padding-left: 1rem !important;\n}\n\n.px-3 {\n padding-right: 1rem !important;\n padding-left: 1rem !important;\n}\n\n.py-3 {\n padding-top: 1rem !important;\n padding-bottom: 1rem !important;\n}\n\n.p-4 {\n padding: 1.5rem !important;\n}\n\n.pt-4 {\n padding-top: 1.5rem !important;\n}\n\n.pr-4 {\n padding-right: 1.5rem !important;\n}\n\n.pb-4 {\n padding-bottom: 1.5rem !important;\n}\n\n.pl-4 {\n padding-left: 1.5rem !important;\n}\n\n.px-4 {\n padding-right: 1.5rem !important;\n padding-left: 1.5rem !important;\n}\n\n.py-4 {\n padding-top: 1.5rem !important;\n padding-bottom: 1.5rem !important;\n}\n\n.p-5 {\n padding: 3rem !important;\n}\n\n.pt-5 {\n padding-top: 3rem !important;\n}\n\n.pr-5 {\n padding-right: 3rem !important;\n}\n\n.pb-5 {\n padding-bottom: 3rem !important;\n}\n\n.pl-5 {\n padding-left: 3rem !important;\n}\n\n.px-5 {\n padding-right: 3rem !important;\n padding-left: 3rem !important;\n}\n\n.py-5 {\n padding-top: 3rem !important;\n padding-bottom: 3rem !important;\n}\n\n.m-auto {\n margin: auto !important;\n}\n\n.mt-auto {\n margin-top: auto !important;\n}\n\n.mr-auto {\n margin-right: auto !important;\n}\n\n.mb-auto {\n margin-bottom: auto !important;\n}\n\n.ml-auto {\n margin-left: auto !important;\n}\n\n.mx-auto {\n margin-right: auto !important;\n margin-left: auto !important;\n}\n\n.my-auto {\n margin-top: auto !important;\n margin-bottom: auto !important;\n}\n\n@media (min-width: 576px) {\n .m-sm-0 {\n margin: 0 !important;\n }\n .mt-sm-0 {\n margin-top: 0 !important;\n }\n .mr-sm-0 {\n margin-right: 0 !important;\n }\n .mb-sm-0 {\n margin-bottom: 0 !important;\n }\n .ml-sm-0 {\n margin-left: 0 !important;\n }\n .mx-sm-0 {\n margin-right: 0 !important;\n margin-left: 0 !important;\n }\n .my-sm-0 {\n margin-top: 0 !important;\n margin-bottom: 0 !important;\n }\n .m-sm-1 {\n margin: 0.25rem !important;\n }\n .mt-sm-1 {\n margin-top: 0.25rem !important;\n }\n .mr-sm-1 {\n margin-right: 0.25rem !important;\n }\n .mb-sm-1 {\n margin-bottom: 0.25rem !important;\n }\n .ml-sm-1 {\n margin-left: 0.25rem !important;\n }\n .mx-sm-1 {\n margin-right: 0.25rem !important;\n margin-left: 0.25rem !important;\n }\n .my-sm-1 {\n margin-top: 0.25rem !important;\n margin-bottom: 0.25rem !important;\n }\n .m-sm-2 {\n margin: 0.5rem !important;\n }\n .mt-sm-2 {\n margin-top: 0.5rem !important;\n }\n .mr-sm-2 {\n margin-right: 0.5rem !important;\n }\n .mb-sm-2 {\n margin-bottom: 0.5rem !important;\n }\n .ml-sm-2 {\n margin-left: 0.5rem !important;\n }\n .mx-sm-2 {\n margin-right: 0.5rem !important;\n margin-left: 0.5rem !important;\n }\n .my-sm-2 {\n margin-top: 0.5rem !important;\n margin-bottom: 0.5rem !important;\n }\n .m-sm-3 {\n margin: 1rem !important;\n }\n .mt-sm-3 {\n margin-top: 1rem !important;\n }\n .mr-sm-3 {\n margin-right: 1rem !important;\n }\n .mb-sm-3 {\n margin-bottom: 1rem !important;\n }\n .ml-sm-3 {\n margin-left: 1rem !important;\n }\n .mx-sm-3 {\n margin-right: 1rem !important;\n margin-left: 1rem !important;\n }\n .my-sm-3 {\n margin-top: 1rem !important;\n margin-bottom: 1rem !important;\n }\n .m-sm-4 {\n margin: 1.5rem !important;\n }\n .mt-sm-4 {\n margin-top: 1.5rem !important;\n }\n .mr-sm-4 {\n margin-right: 1.5rem !important;\n }\n .mb-sm-4 {\n margin-bottom: 1.5rem !important;\n }\n .ml-sm-4 {\n margin-left: 1.5rem !important;\n }\n .mx-sm-4 {\n margin-right: 1.5rem !important;\n margin-left: 1.5rem !important;\n }\n .my-sm-4 {\n margin-top: 1.5rem !important;\n margin-bottom: 1.5rem !important;\n }\n .m-sm-5 {\n margin: 3rem !important;\n }\n .mt-sm-5 {\n margin-top: 3rem !important;\n }\n .mr-sm-5 {\n margin-right: 3rem !important;\n }\n .mb-sm-5 {\n margin-bottom: 3rem !important;\n }\n .ml-sm-5 {\n margin-left: 3rem !important;\n }\n .mx-sm-5 {\n margin-right: 3rem !important;\n margin-left: 3rem !important;\n }\n .my-sm-5 {\n margin-top: 3rem !important;\n margin-bottom: 3rem !important;\n }\n .p-sm-0 {\n padding: 0 !important;\n }\n .pt-sm-0 {\n padding-top: 0 !important;\n }\n .pr-sm-0 {\n padding-right: 0 !important;\n }\n .pb-sm-0 {\n padding-bottom: 0 !important;\n }\n .pl-sm-0 {\n padding-left: 0 !important;\n }\n .px-sm-0 {\n padding-right: 0 !important;\n padding-left: 0 !important;\n }\n .py-sm-0 {\n padding-top: 0 !important;\n padding-bottom: 0 !important;\n }\n .p-sm-1 {\n padding: 0.25rem !important;\n }\n .pt-sm-1 {\n padding-top: 0.25rem !important;\n }\n .pr-sm-1 {\n padding-right: 0.25rem !important;\n }\n .pb-sm-1 {\n padding-bottom: 0.25rem !important;\n }\n .pl-sm-1 {\n padding-left: 0.25rem !important;\n }\n .px-sm-1 {\n padding-right: 0.25rem !important;\n padding-left: 0.25rem !important;\n }\n .py-sm-1 {\n padding-top: 0.25rem !important;\n padding-bottom: 0.25rem !important;\n }\n .p-sm-2 {\n padding: 0.5rem !important;\n }\n .pt-sm-2 {\n padding-top: 0.5rem !important;\n }\n .pr-sm-2 {\n padding-right: 0.5rem !important;\n }\n .pb-sm-2 {\n padding-bottom: 0.5rem !important;\n }\n .pl-sm-2 {\n padding-left: 0.5rem !important;\n }\n .px-sm-2 {\n padding-right: 0.5rem !important;\n padding-left: 0.5rem !important;\n }\n .py-sm-2 {\n padding-top: 0.5rem !important;\n padding-bottom: 0.5rem !important;\n }\n .p-sm-3 {\n padding: 1rem !important;\n }\n .pt-sm-3 {\n padding-top: 1rem !important;\n }\n .pr-sm-3 {\n padding-right: 1rem !important;\n }\n .pb-sm-3 {\n padding-bottom: 1rem !important;\n }\n .pl-sm-3 {\n padding-left: 1rem !important;\n }\n .px-sm-3 {\n padding-right: 1rem !important;\n padding-left: 1rem !important;\n }\n .py-sm-3 {\n padding-top: 1rem !important;\n padding-bottom: 1rem !important;\n }\n .p-sm-4 {\n padding: 1.5rem !important;\n }\n .pt-sm-4 {\n padding-top: 1.5rem !important;\n }\n .pr-sm-4 {\n padding-right: 1.5rem !important;\n }\n .pb-sm-4 {\n padding-bottom: 1.5rem !important;\n }\n .pl-sm-4 {\n padding-left: 1.5rem !important;\n }\n .px-sm-4 {\n padding-right: 1.5rem !important;\n padding-left: 1.5rem !important;\n }\n .py-sm-4 {\n padding-top: 1.5rem !important;\n padding-bottom: 1.5rem !important;\n }\n .p-sm-5 {\n padding: 3rem !important;\n }\n .pt-sm-5 {\n padding-top: 3rem !important;\n }\n .pr-sm-5 {\n padding-right: 3rem !important;\n }\n .pb-sm-5 {\n padding-bottom: 3rem !important;\n }\n .pl-sm-5 {\n padding-left: 3rem !important;\n }\n .px-sm-5 {\n padding-right: 3rem !important;\n padding-left: 3rem !important;\n }\n .py-sm-5 {\n padding-top: 3rem !important;\n padding-bottom: 3rem !important;\n }\n .m-sm-auto {\n margin: auto !important;\n }\n .mt-sm-auto {\n margin-top: auto !important;\n }\n .mr-sm-auto {\n margin-right: auto !important;\n }\n .mb-sm-auto {\n margin-bottom: auto !important;\n }\n .ml-sm-auto {\n margin-left: auto !important;\n }\n .mx-sm-auto {\n margin-right: auto !important;\n margin-left: auto !important;\n }\n .my-sm-auto {\n margin-top: auto !important;\n margin-bottom: auto !important;\n }\n}\n\n@media (min-width: 768px) {\n .m-md-0 {\n margin: 0 !important;\n }\n .mt-md-0 {\n margin-top: 0 !important;\n }\n .mr-md-0 {\n margin-right: 0 !important;\n }\n .mb-md-0 {\n margin-bottom: 0 !important;\n }\n .ml-md-0 {\n margin-left: 0 !important;\n }\n .mx-md-0 {\n margin-right: 0 !important;\n margin-left: 0 !important;\n }\n .my-md-0 {\n margin-top: 0 !important;\n margin-bottom: 0 !important;\n }\n .m-md-1 {\n margin: 0.25rem !important;\n }\n .mt-md-1 {\n margin-top: 0.25rem !important;\n }\n .mr-md-1 {\n margin-right: 0.25rem !important;\n }\n .mb-md-1 {\n margin-bottom: 0.25rem !important;\n }\n .ml-md-1 {\n margin-left: 0.25rem !important;\n }\n .mx-md-1 {\n margin-right: 0.25rem !important;\n margin-left: 0.25rem !important;\n }\n .my-md-1 {\n margin-top: 0.25rem !important;\n margin-bottom: 0.25rem !important;\n }\n .m-md-2 {\n margin: 0.5rem !important;\n }\n .mt-md-2 {\n margin-top: 0.5rem !important;\n }\n .mr-md-2 {\n margin-right: 0.5rem !important;\n }\n .mb-md-2 {\n margin-bottom: 0.5rem !important;\n }\n .ml-md-2 {\n margin-left: 0.5rem !important;\n }\n .mx-md-2 {\n margin-right: 0.5rem !important;\n margin-left: 0.5rem !important;\n }\n .my-md-2 {\n margin-top: 0.5rem !important;\n margin-bottom: 0.5rem !important;\n }\n .m-md-3 {\n margin: 1rem !important;\n }\n .mt-md-3 {\n margin-top: 1rem !important;\n }\n .mr-md-3 {\n margin-right: 1rem !important;\n }\n .mb-md-3 {\n margin-bottom: 1rem !important;\n }\n .ml-md-3 {\n margin-left: 1rem !important;\n }\n .mx-md-3 {\n margin-right: 1rem !important;\n margin-left: 1rem !important;\n }\n .my-md-3 {\n margin-top: 1rem !important;\n margin-bottom: 1rem !important;\n }\n .m-md-4 {\n margin: 1.5rem !important;\n }\n .mt-md-4 {\n margin-top: 1.5rem !important;\n }\n .mr-md-4 {\n margin-right: 1.5rem !important;\n }\n .mb-md-4 {\n margin-bottom: 1.5rem !important;\n }\n .ml-md-4 {\n margin-left: 1.5rem !important;\n }\n .mx-md-4 {\n margin-right: 1.5rem !important;\n margin-left: 1.5rem !important;\n }\n .my-md-4 {\n margin-top: 1.5rem !important;\n margin-bottom: 1.5rem !important;\n }\n .m-md-5 {\n margin: 3rem !important;\n }\n .mt-md-5 {\n margin-top: 3rem !important;\n }\n .mr-md-5 {\n margin-right: 3rem !important;\n }\n .mb-md-5 {\n margin-bottom: 3rem !important;\n }\n .ml-md-5 {\n margin-left: 3rem !important;\n }\n .mx-md-5 {\n margin-right: 3rem !important;\n margin-left: 3rem !important;\n }\n .my-md-5 {\n margin-top: 3rem !important;\n margin-bottom: 3rem !important;\n }\n .p-md-0 {\n padding: 0 !important;\n }\n .pt-md-0 {\n padding-top: 0 !important;\n }\n .pr-md-0 {\n padding-right: 0 !important;\n }\n .pb-md-0 {\n padding-bottom: 0 !important;\n }\n .pl-md-0 {\n padding-left: 0 !important;\n }\n .px-md-0 {\n padding-right: 0 !important;\n padding-left: 0 !important;\n }\n .py-md-0 {\n padding-top: 0 !important;\n padding-bottom: 0 !important;\n }\n .p-md-1 {\n padding: 0.25rem !important;\n }\n .pt-md-1 {\n padding-top: 0.25rem !important;\n }\n .pr-md-1 {\n padding-right: 0.25rem !important;\n }\n .pb-md-1 {\n padding-bottom: 0.25rem !important;\n }\n .pl-md-1 {\n padding-left: 0.25rem !important;\n }\n .px-md-1 {\n padding-right: 0.25rem !important;\n padding-left: 0.25rem !important;\n }\n .py-md-1 {\n padding-top: 0.25rem !important;\n padding-bottom: 0.25rem !important;\n }\n .p-md-2 {\n padding: 0.5rem !important;\n }\n .pt-md-2 {\n padding-top: 0.5rem !important;\n }\n .pr-md-2 {\n padding-right: 0.5rem !important;\n }\n .pb-md-2 {\n padding-bottom: 0.5rem !important;\n }\n .pl-md-2 {\n padding-left: 0.5rem !important;\n }\n .px-md-2 {\n padding-right: 0.5rem !important;\n padding-left: 0.5rem !important;\n }\n .py-md-2 {\n padding-top: 0.5rem !important;\n padding-bottom: 0.5rem !important;\n }\n .p-md-3 {\n padding: 1rem !important;\n }\n .pt-md-3 {\n padding-top: 1rem !important;\n }\n .pr-md-3 {\n padding-right: 1rem !important;\n }\n .pb-md-3 {\n padding-bottom: 1rem !important;\n }\n .pl-md-3 {\n padding-left: 1rem !important;\n }\n .px-md-3 {\n padding-right: 1rem !important;\n padding-left: 1rem !important;\n }\n .py-md-3 {\n padding-top: 1rem !important;\n padding-bottom: 1rem !important;\n }\n .p-md-4 {\n padding: 1.5rem !important;\n }\n .pt-md-4 {\n padding-top: 1.5rem !important;\n }\n .pr-md-4 {\n padding-right: 1.5rem !important;\n }\n .pb-md-4 {\n padding-bottom: 1.5rem !important;\n }\n .pl-md-4 {\n padding-left: 1.5rem !important;\n }\n .px-md-4 {\n padding-right: 1.5rem !important;\n padding-left: 1.5rem !important;\n }\n .py-md-4 {\n padding-top: 1.5rem !important;\n padding-bottom: 1.5rem !important;\n }\n .p-md-5 {\n padding: 3rem !important;\n }\n .pt-md-5 {\n padding-top: 3rem !important;\n }\n .pr-md-5 {\n padding-right: 3rem !important;\n }\n .pb-md-5 {\n padding-bottom: 3rem !important;\n }\n .pl-md-5 {\n padding-left: 3rem !important;\n }\n .px-md-5 {\n padding-right: 3rem !important;\n padding-left: 3rem !important;\n }\n .py-md-5 {\n padding-top: 3rem !important;\n padding-bottom: 3rem !important;\n }\n .m-md-auto {\n margin: auto !important;\n }\n .mt-md-auto {\n margin-top: auto !important;\n }\n .mr-md-auto {\n margin-right: auto !important;\n }\n .mb-md-auto {\n margin-bottom: auto !important;\n }\n .ml-md-auto {\n margin-left: auto !important;\n }\n .mx-md-auto {\n margin-right: auto !important;\n margin-left: auto !important;\n }\n .my-md-auto {\n margin-top: auto !important;\n margin-bottom: auto !important;\n }\n}\n\n@media (min-width: 992px) {\n .m-lg-0 {\n margin: 0 !important;\n }\n .mt-lg-0 {\n margin-top: 0 !important;\n }\n .mr-lg-0 {\n margin-right: 0 !important;\n }\n .mb-lg-0 {\n margin-bottom: 0 !important;\n }\n .ml-lg-0 {\n margin-left: 0 !important;\n }\n .mx-lg-0 {\n margin-right: 0 !important;\n margin-left: 0 !important;\n }\n .my-lg-0 {\n margin-top: 0 !important;\n margin-bottom: 0 !important;\n }\n .m-lg-1 {\n margin: 0.25rem !important;\n }\n .mt-lg-1 {\n margin-top: 0.25rem !important;\n }\n .mr-lg-1 {\n margin-right: 0.25rem !important;\n }\n .mb-lg-1 {\n margin-bottom: 0.25rem !important;\n }\n .ml-lg-1 {\n margin-left: 0.25rem !important;\n }\n .mx-lg-1 {\n margin-right: 0.25rem !important;\n margin-left: 0.25rem !important;\n }\n .my-lg-1 {\n margin-top: 0.25rem !important;\n margin-bottom: 0.25rem !important;\n }\n .m-lg-2 {\n margin: 0.5rem !important;\n }\n .mt-lg-2 {\n margin-top: 0.5rem !important;\n }\n .mr-lg-2 {\n margin-right: 0.5rem !important;\n }\n .mb-lg-2 {\n margin-bottom: 0.5rem !important;\n }\n .ml-lg-2 {\n margin-left: 0.5rem !important;\n }\n .mx-lg-2 {\n margin-right: 0.5rem !important;\n margin-left: 0.5rem !important;\n }\n .my-lg-2 {\n margin-top: 0.5rem !important;\n margin-bottom: 0.5rem !important;\n }\n .m-lg-3 {\n margin: 1rem !important;\n }\n .mt-lg-3 {\n margin-top: 1rem !important;\n }\n .mr-lg-3 {\n margin-right: 1rem !important;\n }\n .mb-lg-3 {\n margin-bottom: 1rem !important;\n }\n .ml-lg-3 {\n margin-left: 1rem !important;\n }\n .mx-lg-3 {\n margin-right: 1rem !important;\n margin-left: 1rem !important;\n }\n .my-lg-3 {\n margin-top: 1rem !important;\n margin-bottom: 1rem !important;\n }\n .m-lg-4 {\n margin: 1.5rem !important;\n }\n .mt-lg-4 {\n margin-top: 1.5rem !important;\n }\n .mr-lg-4 {\n margin-right: 1.5rem !important;\n }\n .mb-lg-4 {\n margin-bottom: 1.5rem !important;\n }\n .ml-lg-4 {\n margin-left: 1.5rem !important;\n }\n .mx-lg-4 {\n margin-right: 1.5rem !important;\n margin-left: 1.5rem !important;\n }\n .my-lg-4 {\n margin-top: 1.5rem !important;\n margin-bottom: 1.5rem !important;\n }\n .m-lg-5 {\n margin: 3rem !important;\n }\n .mt-lg-5 {\n margin-top: 3rem !important;\n }\n .mr-lg-5 {\n margin-right: 3rem !important;\n }\n .mb-lg-5 {\n margin-bottom: 3rem !important;\n }\n .ml-lg-5 {\n margin-left: 3rem !important;\n }\n .mx-lg-5 {\n margin-right: 3rem !important;\n margin-left: 3rem !important;\n }\n .my-lg-5 {\n margin-top: 3rem !important;\n margin-bottom: 3rem !important;\n }\n .p-lg-0 {\n padding: 0 !important;\n }\n .pt-lg-0 {\n padding-top: 0 !important;\n }\n .pr-lg-0 {\n padding-right: 0 !important;\n }\n .pb-lg-0 {\n padding-bottom: 0 !important;\n }\n .pl-lg-0 {\n padding-left: 0 !important;\n }\n .px-lg-0 {\n padding-right: 0 !important;\n padding-left: 0 !important;\n }\n .py-lg-0 {\n padding-top: 0 !important;\n padding-bottom: 0 !important;\n }\n .p-lg-1 {\n padding: 0.25rem !important;\n }\n .pt-lg-1 {\n padding-top: 0.25rem !important;\n }\n .pr-lg-1 {\n padding-right: 0.25rem !important;\n }\n .pb-lg-1 {\n padding-bottom: 0.25rem !important;\n }\n .pl-lg-1 {\n padding-left: 0.25rem !important;\n }\n .px-lg-1 {\n padding-right: 0.25rem !important;\n padding-left: 0.25rem !important;\n }\n .py-lg-1 {\n padding-top: 0.25rem !important;\n padding-bottom: 0.25rem !important;\n }\n .p-lg-2 {\n padding: 0.5rem !important;\n }\n .pt-lg-2 {\n padding-top: 0.5rem !important;\n }\n .pr-lg-2 {\n padding-right: 0.5rem !important;\n }\n .pb-lg-2 {\n padding-bottom: 0.5rem !important;\n }\n .pl-lg-2 {\n padding-left: 0.5rem !important;\n }\n .px-lg-2 {\n padding-right: 0.5rem !important;\n padding-left: 0.5rem !important;\n }\n .py-lg-2 {\n padding-top: 0.5rem !important;\n padding-bottom: 0.5rem !important;\n }\n .p-lg-3 {\n padding: 1rem !important;\n }\n .pt-lg-3 {\n padding-top: 1rem !important;\n }\n .pr-lg-3 {\n padding-right: 1rem !important;\n }\n .pb-lg-3 {\n padding-bottom: 1rem !important;\n }\n .pl-lg-3 {\n padding-left: 1rem !important;\n }\n .px-lg-3 {\n padding-right: 1rem !important;\n padding-left: 1rem !important;\n }\n .py-lg-3 {\n padding-top: 1rem !important;\n padding-bottom: 1rem !important;\n }\n .p-lg-4 {\n padding: 1.5rem !important;\n }\n .pt-lg-4 {\n padding-top: 1.5rem !important;\n }\n .pr-lg-4 {\n padding-right: 1.5rem !important;\n }\n .pb-lg-4 {\n padding-bottom: 1.5rem !important;\n }\n .pl-lg-4 {\n padding-left: 1.5rem !important;\n }\n .px-lg-4 {\n padding-right: 1.5rem !important;\n padding-left: 1.5rem !important;\n }\n .py-lg-4 {\n padding-top: 1.5rem !important;\n padding-bottom: 1.5rem !important;\n }\n .p-lg-5 {\n padding: 3rem !important;\n }\n .pt-lg-5 {\n padding-top: 3rem !important;\n }\n .pr-lg-5 {\n padding-right: 3rem !important;\n }\n .pb-lg-5 {\n padding-bottom: 3rem !important;\n }\n .pl-lg-5 {\n padding-left: 3rem !important;\n }\n .px-lg-5 {\n padding-right: 3rem !important;\n padding-left: 3rem !important;\n }\n .py-lg-5 {\n padding-top: 3rem !important;\n padding-bottom: 3rem !important;\n }\n .m-lg-auto {\n margin: auto !important;\n }\n .mt-lg-auto {\n margin-top: auto !important;\n }\n .mr-lg-auto {\n margin-right: auto !important;\n }\n .mb-lg-auto {\n margin-bottom: auto !important;\n }\n .ml-lg-auto {\n margin-left: auto !important;\n }\n .mx-lg-auto {\n margin-right: auto !important;\n margin-left: auto !important;\n }\n .my-lg-auto {\n margin-top: auto !important;\n margin-bottom: auto !important;\n }\n}\n\n@media (min-width: 1200px) {\n .m-xl-0 {\n margin: 0 !important;\n }\n .mt-xl-0 {\n margin-top: 0 !important;\n }\n .mr-xl-0 {\n margin-right: 0 !important;\n }\n .mb-xl-0 {\n margin-bottom: 0 !important;\n }\n .ml-xl-0 {\n margin-left: 0 !important;\n }\n .mx-xl-0 {\n margin-right: 0 !important;\n margin-left: 0 !important;\n }\n .my-xl-0 {\n margin-top: 0 !important;\n margin-bottom: 0 !important;\n }\n .m-xl-1 {\n margin: 0.25rem !important;\n }\n .mt-xl-1 {\n margin-top: 0.25rem !important;\n }\n .mr-xl-1 {\n margin-right: 0.25rem !important;\n }\n .mb-xl-1 {\n margin-bottom: 0.25rem !important;\n }\n .ml-xl-1 {\n margin-left: 0.25rem !important;\n }\n .mx-xl-1 {\n margin-right: 0.25rem !important;\n margin-left: 0.25rem !important;\n }\n .my-xl-1 {\n margin-top: 0.25rem !important;\n margin-bottom: 0.25rem !important;\n }\n .m-xl-2 {\n margin: 0.5rem !important;\n }\n .mt-xl-2 {\n margin-top: 0.5rem !important;\n }\n .mr-xl-2 {\n margin-right: 0.5rem !important;\n }\n .mb-xl-2 {\n margin-bottom: 0.5rem !important;\n }\n .ml-xl-2 {\n margin-left: 0.5rem !important;\n }\n .mx-xl-2 {\n margin-right: 0.5rem !important;\n margin-left: 0.5rem !important;\n }\n .my-xl-2 {\n margin-top: 0.5rem !important;\n margin-bottom: 0.5rem !important;\n }\n .m-xl-3 {\n margin: 1rem !important;\n }\n .mt-xl-3 {\n margin-top: 1rem !important;\n }\n .mr-xl-3 {\n margin-right: 1rem !important;\n }\n .mb-xl-3 {\n margin-bottom: 1rem !important;\n }\n .ml-xl-3 {\n margin-left: 1rem !important;\n }\n .mx-xl-3 {\n margin-right: 1rem !important;\n margin-left: 1rem !important;\n }\n .my-xl-3 {\n margin-top: 1rem !important;\n margin-bottom: 1rem !important;\n }\n .m-xl-4 {\n margin: 1.5rem !important;\n }\n .mt-xl-4 {\n margin-top: 1.5rem !important;\n }\n .mr-xl-4 {\n margin-right: 1.5rem !important;\n }\n .mb-xl-4 {\n margin-bottom: 1.5rem !important;\n }\n .ml-xl-4 {\n margin-left: 1.5rem !important;\n }\n .mx-xl-4 {\n margin-right: 1.5rem !important;\n margin-left: 1.5rem !important;\n }\n .my-xl-4 {\n margin-top: 1.5rem !important;\n margin-bottom: 1.5rem !important;\n }\n .m-xl-5 {\n margin: 3rem !important;\n }\n .mt-xl-5 {\n margin-top: 3rem !important;\n }\n .mr-xl-5 {\n margin-right: 3rem !important;\n }\n .mb-xl-5 {\n margin-bottom: 3rem !important;\n }\n .ml-xl-5 {\n margin-left: 3rem !important;\n }\n .mx-xl-5 {\n margin-right: 3rem !important;\n margin-left: 3rem !important;\n }\n .my-xl-5 {\n margin-top: 3rem !important;\n margin-bottom: 3rem !important;\n }\n .p-xl-0 {\n padding: 0 !important;\n }\n .pt-xl-0 {\n padding-top: 0 !important;\n }\n .pr-xl-0 {\n padding-right: 0 !important;\n }\n .pb-xl-0 {\n padding-bottom: 0 !important;\n }\n .pl-xl-0 {\n padding-left: 0 !important;\n }\n .px-xl-0 {\n padding-right: 0 !important;\n padding-left: 0 !important;\n }\n .py-xl-0 {\n padding-top: 0 !important;\n padding-bottom: 0 !important;\n }\n .p-xl-1 {\n padding: 0.25rem !important;\n }\n .pt-xl-1 {\n padding-top: 0.25rem !important;\n }\n .pr-xl-1 {\n padding-right: 0.25rem !important;\n }\n .pb-xl-1 {\n padding-bottom: 0.25rem !important;\n }\n .pl-xl-1 {\n padding-left: 0.25rem !important;\n }\n .px-xl-1 {\n padding-right: 0.25rem !important;\n padding-left: 0.25rem !important;\n }\n .py-xl-1 {\n padding-top: 0.25rem !important;\n padding-bottom: 0.25rem !important;\n }\n .p-xl-2 {\n padding: 0.5rem !important;\n }\n .pt-xl-2 {\n padding-top: 0.5rem !important;\n }\n .pr-xl-2 {\n padding-right: 0.5rem !important;\n }\n .pb-xl-2 {\n padding-bottom: 0.5rem !important;\n }\n .pl-xl-2 {\n padding-left: 0.5rem !important;\n }\n .px-xl-2 {\n padding-right: 0.5rem !important;\n padding-left: 0.5rem !important;\n }\n .py-xl-2 {\n padding-top: 0.5rem !important;\n padding-bottom: 0.5rem !important;\n }\n .p-xl-3 {\n padding: 1rem !important;\n }\n .pt-xl-3 {\n padding-top: 1rem !important;\n }\n .pr-xl-3 {\n padding-right: 1rem !important;\n }\n .pb-xl-3 {\n padding-bottom: 1rem !important;\n }\n .pl-xl-3 {\n padding-left: 1rem !important;\n }\n .px-xl-3 {\n padding-right: 1rem !important;\n padding-left: 1rem !important;\n }\n .py-xl-3 {\n padding-top: 1rem !important;\n padding-bottom: 1rem !important;\n }\n .p-xl-4 {\n padding: 1.5rem !important;\n }\n .pt-xl-4 {\n padding-top: 1.5rem !important;\n }\n .pr-xl-4 {\n padding-right: 1.5rem !important;\n }\n .pb-xl-4 {\n padding-bottom: 1.5rem !important;\n }\n .pl-xl-4 {\n padding-left: 1.5rem !important;\n }\n .px-xl-4 {\n padding-right: 1.5rem !important;\n padding-left: 1.5rem !important;\n }\n .py-xl-4 {\n padding-top: 1.5rem !important;\n padding-bottom: 1.5rem !important;\n }\n .p-xl-5 {\n padding: 3rem !important;\n }\n .pt-xl-5 {\n padding-top: 3rem !important;\n }\n .pr-xl-5 {\n padding-right: 3rem !important;\n }\n .pb-xl-5 {\n padding-bottom: 3rem !important;\n }\n .pl-xl-5 {\n padding-left: 3rem !important;\n }\n .px-xl-5 {\n padding-right: 3rem !important;\n padding-left: 3rem !important;\n }\n .py-xl-5 {\n padding-top: 3rem !important;\n padding-bottom: 3rem !important;\n }\n .m-xl-auto {\n margin: auto !important;\n }\n .mt-xl-auto {\n margin-top: auto !important;\n }\n .mr-xl-auto {\n margin-right: auto !important;\n }\n .mb-xl-auto {\n margin-bottom: auto !important;\n }\n .ml-xl-auto {\n margin-left: auto !important;\n }\n .mx-xl-auto {\n margin-right: auto !important;\n margin-left: auto !important;\n }\n .my-xl-auto {\n margin-top: auto !important;\n margin-bottom: auto !important;\n }\n}\n\n.text-justify {\n text-align: justify !important;\n}\n\n.text-nowrap {\n white-space: nowrap !important;\n}\n\n.text-truncate {\n overflow: hidden;\n text-overflow: ellipsis;\n white-space: nowrap;\n}\n\n.text-left {\n text-align: left !important;\n}\n\n.text-right {\n text-align: right !important;\n}\n\n.text-center {\n text-align: center !important;\n}\n\n@media (min-width: 576px) {\n .text-sm-left {\n text-align: left !important;\n }\n .text-sm-right {\n text-align: right !important;\n }\n .text-sm-center {\n text-align: center !important;\n }\n}\n\n@media (min-width: 768px) {\n .text-md-left {\n text-align: left !important;\n }\n .text-md-right {\n text-align: right !important;\n }\n .text-md-center {\n text-align: center !important;\n }\n}\n\n@media (min-width: 992px) {\n .text-lg-left {\n text-align: left !important;\n }\n .text-lg-right {\n text-align: right !important;\n }\n .text-lg-center {\n text-align: center !important;\n }\n}\n\n@media (min-width: 1200px) {\n .text-xl-left {\n text-align: left !important;\n }\n .text-xl-right {\n text-align: right !important;\n }\n .text-xl-center {\n text-align: center !important;\n }\n}\n\n.text-lowercase {\n text-transform: lowercase !important;\n}\n\n.text-uppercase {\n text-transform: uppercase !important;\n}\n\n.text-capitalize {\n text-transform: capitalize !important;\n}\n\n.font-weight-normal {\n font-weight: normal;\n}\n\n.font-weight-bold {\n font-weight: bold;\n}\n\n.font-italic {\n font-style: italic;\n}\n\n.text-white {\n color: #fff !important;\n}\n\n.text-primary {\n color: #007bff !important;\n}\n\na.text-primary:focus, a.text-primary:hover {\n color: #0062cc !important;\n}\n\n.text-secondary {\n color: #868e96 !important;\n}\n\na.text-secondary:focus, a.text-secondary:hover {\n color: #6c757d !important;\n}\n\n.text-success {\n color: #28a745 !important;\n}\n\na.text-success:focus, a.text-success:hover {\n color: #1e7e34 !important;\n}\n\n.text-info {\n color: #17a2b8 !important;\n}\n\na.text-info:focus, a.text-info:hover {\n color: #117a8b !important;\n}\n\n.text-warning {\n color: #ffc107 !important;\n}\n\na.text-warning:focus, a.text-warning:hover {\n color: #d39e00 !important;\n}\n\n.text-danger {\n color: #dc3545 !important;\n}\n\na.text-danger:focus, a.text-danger:hover {\n color: #bd2130 !important;\n}\n\n.text-light {\n color: #f8f9fa !important;\n}\n\na.text-light:focus, a.text-light:hover {\n color: #dae0e5 !important;\n}\n\n.text-dark {\n color: #343a40 !important;\n}\n\na.text-dark:focus, a.text-dark:hover {\n color: #1d2124 !important;\n}\n\n.text-muted {\n color: #868e96 !important;\n}\n\n.text-hide {\n font: 0/0 a;\n color: transparent;\n text-shadow: none;\n background-color: transparent;\n border: 0;\n}\n\n.visible {\n visibility: visible !important;\n}\n\n.invisible {\n visibility: hidden !important;\n}\n\n/*# sourceMappingURL=bootstrap.css.map */","@mixin hover {\n // TODO: re-enable along with mq4-hover-shim\n// @if $enable-hover-media-query {\n// // See Media Queries Level 4: https://drafts.csswg.org/mediaqueries/#hover\n// // Currently shimmed by https://github.com/twbs/mq4-hover-shim\n// @media (hover: hover) {\n// &:hover { @content }\n// }\n// }\n// @else {\n// scss-lint:disable Indentation\n &:hover { @content }\n// scss-lint:enable Indentation\n// }\n}\n\n\n@mixin hover-focus {\n @if $enable-hover-media-query {\n &:focus { @content }\n @include hover { @content }\n } @else {\n &:focus,\n &:hover {\n @content\n }\n }\n}\n\n@mixin plain-hover-focus {\n @if $enable-hover-media-query {\n &,\n &:focus {\n @content\n }\n @include hover { @content }\n } @else {\n &,\n &:focus,\n &:hover {\n @content\n }\n }\n}\n\n@mixin hover-focus-active {\n @if $enable-hover-media-query {\n &:focus,\n &:active {\n @content\n }\n @include hover { @content }\n } @else {\n &:focus,\n &:active,\n &:hover {\n @content\n }\n }\n}\n","//\n// Headings\n//\n\nh1, h2, h3, h4, h5, h6,\n.h1, .h2, .h3, .h4, .h5, .h6 {\n margin-bottom: $headings-margin-bottom;\n font-family: $headings-font-family;\n font-weight: $headings-font-weight;\n line-height: $headings-line-height;\n color: $headings-color;\n}\n\nh1, .h1 { font-size: $h1-font-size; }\nh2, .h2 { font-size: $h2-font-size; }\nh3, .h3 { font-size: $h3-font-size; }\nh4, .h4 { font-size: $h4-font-size; }\nh5, .h5 { font-size: $h5-font-size; }\nh6, .h6 { font-size: $h6-font-size; }\n\n.lead {\n font-size: $lead-font-size;\n font-weight: $lead-font-weight;\n}\n\n// Type display classes\n.display-1 {\n font-size: $display1-size;\n font-weight: $display1-weight;\n line-height: $display-line-height;\n}\n.display-2 {\n font-size: $display2-size;\n font-weight: $display2-weight;\n line-height: $display-line-height;\n}\n.display-3 {\n font-size: $display3-size;\n font-weight: $display3-weight;\n line-height: $display-line-height;\n}\n.display-4 {\n font-size: $display4-size;\n font-weight: $display4-weight;\n line-height: $display-line-height;\n}\n\n\n//\n// Horizontal rules\n//\n\nhr {\n margin-top: 1rem;\n margin-bottom: 1rem;\n border: 0;\n border-top: $hr-border-width solid $hr-border-color;\n}\n\n\n//\n// Emphasis\n//\n\nsmall,\n.small {\n font-size: $small-font-size;\n font-weight: $font-weight-normal;\n}\n\nmark,\n.mark {\n padding: $mark-padding;\n background-color: $mark-bg;\n}\n\n\n//\n// Lists\n//\n\n.list-unstyled {\n @include list-unstyled;\n}\n\n// Inline turns list items into inline-block\n.list-inline {\n @include list-unstyled;\n}\n.list-inline-item {\n display: inline-block;\n\n &:not(:last-child) {\n margin-right: $list-inline-padding;\n }\n}\n\n\n//\n// Misc\n//\n\n// Builds on `abbr`\n.initialism {\n font-size: 90%;\n text-transform: uppercase;\n}\n\n// Blockquotes\n.blockquote {\n margin-bottom: $spacer;\n font-size: $blockquote-font-size;\n}\n\n.blockquote-footer {\n display: block;\n font-size: 80%; // back to default font-size\n color: $blockquote-small-color;\n\n &::before {\n content: \"\\2014 \\00A0\"; // em dash, nbsp\n }\n}\n","// Lists\n\n// Unstyled keeps list items block level, just removes default browser padding and list-style\n@mixin list-unstyled {\n padding-left: 0;\n list-style: none;\n}\n","// Responsive images (ensure images don't scale beyond their parents)\n//\n// This is purposefully opt-in via an explicit class rather than being the default for all `<img>`s.\n// We previously tried the \"images are responsive by default\" approach in Bootstrap v2,\n// and abandoned it in Bootstrap v3 because it breaks lots of third-party widgets (including Google Maps)\n// which weren't expecting the images within themselves to be involuntarily resized.\n// See also https://github.com/twbs/bootstrap/issues/18178\n.img-fluid {\n @include img-fluid;\n}\n\n\n// Image thumbnails\n.img-thumbnail {\n padding: $thumbnail-padding;\n background-color: $thumbnail-bg;\n border: $thumbnail-border-width solid $thumbnail-border-color;\n @include border-radius($thumbnail-border-radius);\n @include transition($thumbnail-transition);\n @include box-shadow($thumbnail-box-shadow);\n\n // Keep them at most 100% wide\n @include img-fluid;\n}\n\n//\n// Figures\n//\n\n.figure {\n // Ensures the caption's text aligns with the image.\n display: inline-block;\n}\n\n.figure-img {\n margin-bottom: ($spacer / 2);\n line-height: 1;\n}\n\n.figure-caption {\n font-size: $figure-caption-font-size;\n color: $figure-caption-color;\n}\n","// Image Mixins\n// - Responsive image\n// - Retina image\n\n\n// Responsive image\n//\n// Keep images from scaling beyond the width of their parents.\n\n@mixin img-fluid {\n // Part 1: Set a maximum relative to the parent\n max-width: 100%;\n // Part 2: Override the height to auto, otherwise images will be stretched\n // when setting a width and height attribute on the img element.\n height: auto;\n}\n\n\n// Retina image\n//\n// Short retina mixin for setting background-image and -size.\n\n@mixin img-retina($file-1x, $file-2x, $width-1x, $height-1x) {\n background-image: url($file-1x);\n\n // Autoprefixer takes care of adding -webkit-min-device-pixel-ratio and -o-min-device-pixel-ratio,\n // but doesn't convert dppx=>dpi.\n // There's no such thing as unprefixed min-device-pixel-ratio since it's nonstandard.\n // Compatibility info: http://caniuse.com/#feat=css-media-resolution\n @media\n only screen and (min-resolution: 192dpi), // IE9-11 don't support dppx\n only screen and (min-resolution: 2dppx) { // Standardized\n background-image: url($file-2x);\n background-size: $width-1x $height-1x;\n }\n}\n","// Single side border-radius\n\n@mixin border-radius($radius: $border-radius) {\n @if $enable-rounded {\n border-radius: $radius;\n }\n}\n\n@mixin border-top-radius($radius) {\n @if $enable-rounded {\n border-top-left-radius: $radius;\n border-top-right-radius: $radius;\n }\n}\n\n@mixin border-right-radius($radius) {\n @if $enable-rounded {\n border-top-right-radius: $radius;\n border-bottom-right-radius: $radius;\n }\n}\n\n@mixin border-bottom-radius($radius) {\n @if $enable-rounded {\n border-bottom-right-radius: $radius;\n border-bottom-left-radius: $radius;\n }\n}\n\n@mixin border-left-radius($radius) {\n @if $enable-rounded {\n border-top-left-radius: $radius;\n border-bottom-left-radius: $radius;\n }\n}\n","@mixin transition($transition...) {\n @if $enable-transitions {\n @if length($transition) == 0 {\n transition: $transition-base;\n } @else {\n transition: $transition;\n }\n }\n}\n","// Inline and block code styles\ncode,\nkbd,\npre,\nsamp {\n font-family: $font-family-monospace;\n}\n\n// Inline code\ncode {\n padding: $code-padding-y $code-padding-x;\n font-size: $code-font-size;\n color: $code-color;\n background-color: $code-bg;\n @include border-radius($border-radius);\n\n // Streamline the style when inside anchors to avoid broken underline and more\n a > & {\n padding: 0;\n color: inherit;\n background-color: inherit;\n }\n}\n\n// User input typically entered via keyboard\nkbd {\n padding: $code-padding-y $code-padding-x;\n font-size: $code-font-size;\n color: $kbd-color;\n background-color: $kbd-bg;\n @include border-radius($border-radius-sm);\n @include box-shadow($kbd-box-shadow);\n\n kbd {\n padding: 0;\n font-size: 100%;\n font-weight: $nested-kbd-font-weight;\n @include box-shadow(none);\n }\n}\n\n// Blocks of code\npre {\n display: block;\n margin-top: 0;\n margin-bottom: 1rem;\n font-size: $code-font-size;\n color: $pre-color;\n\n // Account for some code outputs that place code tags in pre tags\n code {\n padding: 0;\n font-size: inherit;\n color: inherit;\n background-color: transparent;\n border-radius: 0;\n }\n}\n\n// Enable scrollable blocks of code\n.pre-scrollable {\n max-height: $pre-scrollable-max-height;\n overflow-y: scroll;\n}\n","// Container widths\n//\n// Set the container width, and override it for fixed navbars in media queries.\n\n@if $enable-grid-classes {\n .container {\n @include make-container();\n @include make-container-max-widths();\n }\n}\n\n// Fluid container\n//\n// Utilizes the mixin meant for fixed width containers, but with 100% width for\n// fluid, full width layouts.\n\n@if $enable-grid-classes {\n .container-fluid {\n width: 100%;\n @include make-container();\n }\n}\n\n// Row\n//\n// Rows contain and clear the floats of your columns.\n\n@if $enable-grid-classes {\n .row {\n @include make-row();\n }\n\n // Remove the negative margin from default .row, then the horizontal padding\n // from all immediate children columns (to prevent runaway style inheritance).\n .no-gutters {\n margin-right: 0;\n margin-left: 0;\n\n > .col,\n > [class*=\"col-\"] {\n padding-right: 0;\n padding-left: 0;\n }\n }\n}\n\n// Columns\n//\n// Common styles for small and large grid columns\n\n@if $enable-grid-classes {\n @include make-grid-columns();\n}\n","/// Grid system\n//\n// Generate semantic grid columns with these mixins.\n\n@mixin make-container() {\n margin-right: auto;\n margin-left: auto;\n padding-right: ($grid-gutter-width / 2);\n padding-left: ($grid-gutter-width / 2);\n width: 100%;\n}\n\n\n// For each breakpoint, define the maximum width of the container in a media query\n@mixin make-container-max-widths($max-widths: $container-max-widths, $breakpoints: $grid-breakpoints) {\n @each $breakpoint, $container-max-width in $max-widths {\n @include media-breakpoint-up($breakpoint, $breakpoints) {\n max-width: $container-max-width;\n }\n }\n}\n\n@mixin make-row() {\n display: flex;\n flex-wrap: wrap;\n margin-right: ($grid-gutter-width / -2);\n margin-left: ($grid-gutter-width / -2);\n}\n\n@mixin make-col-ready() {\n position: relative;\n // Prevent columns from becoming too narrow when at smaller grid tiers by\n // always setting `width: 100%;`. This works because we use `flex` values\n // later on to override this initial width.\n width: 100%;\n min-height: 1px; // Prevent collapsing\n padding-right: ($grid-gutter-width / 2);\n padding-left: ($grid-gutter-width / 2);\n}\n\n@mixin make-col($size, $columns: $grid-columns) {\n flex: 0 0 percentage($size / $columns);\n // Add a `max-width` to ensure content within each column does not blow out\n // the width of the column. Applies to IE10+ and Firefox. Chrome and Safari\n // do not appear to require this.\n max-width: percentage($size / $columns);\n}\n","// Breakpoint viewport sizes and media queries.\n//\n// Breakpoints are defined as a map of (name: minimum width), order from small to large:\n//\n// (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px)\n//\n// The map defined in the `$grid-breakpoints` global variable is used as the `$breakpoints` argument by default.\n\n// Name of the next breakpoint, or null for the last breakpoint.\n//\n// >> breakpoint-next(sm)\n// md\n// >> breakpoint-next(sm, (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px))\n// md\n// >> breakpoint-next(sm, $breakpoint-names: (xs sm md lg xl))\n// md\n@function breakpoint-next($name, $breakpoints: $grid-breakpoints, $breakpoint-names: map-keys($breakpoints)) {\n $n: index($breakpoint-names, $name);\n @return if($n < length($breakpoint-names), nth($breakpoint-names, $n + 1), null);\n}\n\n// Minimum breakpoint width. Null for the smallest (first) breakpoint.\n//\n// >> breakpoint-min(sm, (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px))\n// 576px\n@function breakpoint-min($name, $breakpoints: $grid-breakpoints) {\n $min: map-get($breakpoints, $name);\n @return if($min != 0, $min, null);\n}\n\n// Maximum breakpoint width. Null for the largest (last) breakpoint.\n// The maximum value is calculated as the minimum of the next one less 0.1.\n//\n// >> breakpoint-max(sm, (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px))\n// 767px\n@function breakpoint-max($name, $breakpoints: $grid-breakpoints) {\n $next: breakpoint-next($name, $breakpoints);\n @return if($next, breakpoint-min($next, $breakpoints) - 1px, null);\n}\n\n// Returns a blank string if smallest breakpoint, otherwise returns the name with a dash infront.\n// Useful for making responsive utilities.\n//\n// >> breakpoint-infix(xs, (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px))\n// \"\" (Returns a blank string)\n// >> breakpoint-infix(sm, (xs: 0, sm: 576px, md: 768px, lg: 992px, xl: 1200px))\n// \"-sm\"\n@function breakpoint-infix($name, $breakpoints: $grid-breakpoints) {\n @return if(breakpoint-min($name, $breakpoints) == null, \"\", \"-#{$name}\");\n}\n\n// Media of at least the minimum breakpoint width. No query for the smallest breakpoint.\n// Makes the @content apply to the given breakpoint and wider.\n@mixin media-breakpoint-up($name, $breakpoints: $grid-breakpoints) {\n $min: breakpoint-min($name, $breakpoints);\n @if $min {\n @media (min-width: $min) {\n @content;\n }\n } @else {\n @content;\n }\n}\n\n// Media of at most the maximum breakpoint width. No query for the largest breakpoint.\n// Makes the @content apply to the given breakpoint and narrower.\n@mixin media-breakpoint-down($name, $breakpoints: $grid-breakpoints) {\n $max: breakpoint-max($name, $breakpoints);\n @if $max {\n @media (max-width: $max) {\n @content;\n }\n } @else {\n @content;\n }\n}\n\n// Media that spans multiple breakpoint widths.\n// Makes the @content apply between the min and max breakpoints\n@mixin media-breakpoint-between($lower, $upper, $breakpoints: $grid-breakpoints) {\n $min: breakpoint-min($lower, $breakpoints);\n $max: breakpoint-max($upper, $breakpoints);\n\n @media (min-width: $min) and (max-width: $max) {\n @content;\n }\n}\n\n// Media between the breakpoint's minimum and maximum widths.\n// No minimum for the smallest breakpoint, and no maximum for the largest one.\n// Makes the @content apply only to the given breakpoint, not viewports any wider or narrower.\n@mixin media-breakpoint-only($name, $breakpoints: $grid-breakpoints) {\n $min: breakpoint-min($name, $breakpoints);\n $max: breakpoint-max($name, $breakpoints);\n\n @if $min != null and $max != null {\n @media (min-width: $min) and (max-width: $max) {\n @content;\n }\n } @else if $max == null {\n @include media-breakpoint-up($name)\n } @else if $min == null {\n @include media-breakpoint-down($name)\n }\n}\n","// Framework grid generation\n//\n// Used only by Bootstrap to generate the correct number of grid classes given\n// any value of `$grid-columns`.\n\n@mixin make-grid-columns($columns: $grid-columns, $gutter: $grid-gutter-width, $breakpoints: $grid-breakpoints) {\n // Common properties for all breakpoints\n %grid-column {\n position: relative;\n width: 100%;\n min-height: 1px; // Prevent columns from collapsing when empty\n padding-right: ($gutter / 2);\n padding-left: ($gutter / 2);\n }\n\n @each $breakpoint in map-keys($breakpoints) {\n $infix: breakpoint-infix($breakpoint, $breakpoints);\n\n // Allow columns to stretch full width below their breakpoints\n @for $i from 1 through $columns {\n .col#{$infix}-#{$i} {\n @extend %grid-column;\n }\n }\n .col#{$infix},\n .col#{$infix}-auto {\n @extend %grid-column;\n }\n\n @include media-breakpoint-up($breakpoint, $breakpoints) {\n // Provide basic `.col-{bp}` classes for equal-width flexbox columns\n .col#{$infix} {\n flex-basis: 0;\n flex-grow: 1;\n max-width: 100%;\n }\n .col#{$infix}-auto {\n flex: 0 0 auto;\n width: auto;\n max-width: none; // Reset earlier grid tiers\n }\n\n @for $i from 1 through $columns {\n .col#{$infix}-#{$i} {\n @include make-col($i, $columns);\n }\n }\n\n @for $i from 1 through $columns {\n .order#{$infix}-#{$i} {\n order: $i;\n }\n }\n }\n }\n}\n","//\n// Basic Bootstrap table\n//\n\n.table {\n width: 100%;\n max-width: 100%;\n margin-bottom: $spacer;\n background-color: $table-bg; // Reset for nesting within parents with `background-color`.\n\n th,\n td {\n padding: $table-cell-padding;\n vertical-align: top;\n border-top: $table-border-width solid $table-border-color;\n }\n\n thead th {\n vertical-align: bottom;\n border-bottom: (2 * $table-border-width) solid $table-border-color;\n }\n\n tbody + tbody {\n border-top: (2 * $table-border-width) solid $table-border-color;\n }\n\n .table {\n background-color: $body-bg;\n }\n}\n\n\n//\n// Condensed table w/ half padding\n//\n\n.table-sm {\n th,\n td {\n padding: $table-cell-padding-sm;\n }\n}\n\n\n// Bordered version\n//\n// Add borders all around the table and between all the columns.\n\n.table-bordered {\n border: $table-border-width solid $table-border-color;\n\n th,\n td {\n border: $table-border-width solid $table-border-color;\n }\n\n thead {\n th,\n td {\n border-bottom-width: (2 * $table-border-width);\n }\n }\n}\n\n\n// Zebra-striping\n//\n// Default zebra-stripe styles (alternating gray and transparent backgrounds)\n\n.table-striped {\n tbody tr:nth-of-type(odd) {\n background-color: $table-accent-bg;\n }\n}\n\n\n// Hover effect\n//\n// Placed here since it has to come after the potential zebra striping\n\n.table-hover {\n tbody tr {\n @include hover {\n background-color: $table-hover-bg;\n }\n }\n}\n\n\n// Table backgrounds\n//\n// Exact selectors below required to override `.table-striped` and prevent\n// inheritance to nested tables.\n\n@each $color, $value in $theme-colors {\n @include table-row-variant($color, theme-color-level($color, -9));\n}\n\n@include table-row-variant(active, $table-active-bg);\n\n\n// Inverse styles\n//\n// Same table markup, but inverted color scheme: dark background and light text.\n\n.thead-inverse {\n th {\n color: $table-inverse-color;\n background-color: $table-inverse-bg;\n }\n}\n\n.thead-default {\n th {\n color: $table-head-color;\n background-color: $table-head-bg;\n }\n}\n\n.table-inverse {\n color: $table-inverse-color;\n background-color: $table-inverse-bg;\n\n th,\n td,\n thead th {\n border-color: $table-inverse-border-color;\n }\n\n &.table-bordered {\n border: 0;\n }\n\n &.table-striped {\n tbody tr:nth-of-type(odd) {\n background-color: $table-inverse-accent-bg;\n }\n }\n\n &.table-hover {\n tbody tr {\n @include hover {\n background-color: $table-inverse-hover-bg;\n }\n }\n }\n}\n\n\n// Responsive tables\n//\n// Add `.table-responsive` to `.table`s and we'll make them mobile friendly by\n// enabling horizontal scrolling. Only applies <768px. Everything above that\n// will display normally.\n\n.table-responsive {\n @include media-breakpoint-down(md) {\n display: block;\n width: 100%;\n overflow-x: auto;\n -ms-overflow-style: -ms-autohiding-scrollbar; // See https://github.com/twbs/bootstrap/pull/10057\n\n // Prevent double border on horizontal scroll due to use of `display: block;`\n &.table-bordered {\n border: 0;\n }\n }\n}\n","// Tables\n\n@mixin table-row-variant($state, $background) {\n // Exact selectors below required to override `.table-striped` and prevent\n // inheritance to nested tables.\n .table-#{$state} {\n &,\n > th,\n > td {\n background-color: $background;\n }\n }\n\n // Hover states for `.table-hover`\n // Note: this is not available for cells or rows within `thead` or `tfoot`.\n .table-hover {\n $hover-background: darken($background, 5%);\n\n .table-#{$state} {\n @include hover {\n background-color: $hover-background;\n\n > td,\n > th {\n background-color: $hover-background;\n }\n }\n }\n }\n}\n","// scss-lint:disable QualifyingElement, VendorPrefix\n\n//\n// Textual form controls\n//\n\n.form-control {\n display: block;\n width: 100%;\n // // Make inputs at least the height of their button counterpart (base line-height + padding + border)\n // height: $input-height;\n padding: $input-btn-padding-y $input-btn-padding-x;\n font-size: $font-size-base;\n line-height: $input-btn-line-height;\n color: $input-color;\n background-color: $input-bg;\n // Reset unusual Firefox-on-Android default style; see https://github.com/necolas/normalize.css/issues/214.\n background-image: none;\n background-clip: padding-box;\n border: $input-btn-border-width solid $input-border-color;\n\n // Note: This has no effect on <select>s in some browsers, due to the limited stylability of `<select>`s in CSS.\n @if $enable-rounded {\n // Manually use the if/else instead of the mixin to account for iOS override\n border-radius: $input-border-radius;\n } @else {\n // Otherwise undo the iOS default\n border-radius: 0;\n }\n\n @include box-shadow($input-box-shadow);\n @include transition($input-transition);\n\n // Unstyle the caret on `<select>`s in IE10+.\n &::-ms-expand {\n background-color: transparent;\n border: 0;\n }\n\n // Customize the `:focus` state to imitate native WebKit styles.\n @include form-control-focus();\n\n // Placeholder\n &::placeholder {\n color: $input-placeholder-color;\n // Override Firefox's unusual default opacity; see https://github.com/twbs/bootstrap/pull/11526.\n opacity: 1;\n }\n\n // Disabled and read-only inputs\n //\n // HTML5 says that controls under a fieldset > legend:first-child won't be\n // disabled if the fieldset is disabled. Due to implementation difficulty, we\n // don't honor that edge case; we style them as disabled anyway.\n &:disabled,\n &[readonly] {\n background-color: $input-disabled-bg;\n // iOS fix for unreadable disabled content; see https://github.com/twbs/bootstrap/issues/11655.\n opacity: 1;\n }\n}\n\nselect.form-control {\n &:not([size]):not([multiple]) {\n height: $input-height;\n }\n\n &:focus::-ms-value {\n // Suppress the nested default white text on blue background highlight given to\n // the selected option text when the (still closed) <select> receives focus\n // in IE and (under certain conditions) Edge, as it looks bad and cannot be made to\n // match the appearance of the native widget.\n // See https://github.com/twbs/bootstrap/issues/19398.\n color: $input-color;\n background-color: $input-bg;\n }\n}\n\n// Make file inputs better match text inputs by forcing them to new lines.\n.form-control-file,\n.form-control-range {\n display: block;\n}\n\n\n//\n// Labels\n//\n\n// For use with horizontal and inline forms, when you need the label text to\n// align with the form controls.\n.col-form-label {\n padding-top: calc(#{$input-btn-padding-y} - #{$input-btn-border-width} * 2);\n padding-bottom: calc(#{$input-btn-padding-y} - #{$input-btn-border-width} * 2);\n margin-bottom: 0; // Override the `<label>` default\n}\n\n.col-form-label-lg {\n padding-top: calc(#{$input-btn-padding-y-lg} - #{$input-btn-border-width} * 2);\n padding-bottom: calc(#{$input-btn-padding-y-lg} - #{$input-btn-border-width} * 2);\n font-size: $font-size-lg;\n}\n\n.col-form-label-sm {\n padding-top: calc(#{$input-btn-padding-y-sm} - #{$input-btn-border-width} * 2);\n padding-bottom: calc(#{$input-btn-padding-y-sm} - #{$input-btn-border-width} * 2);\n font-size: $font-size-sm;\n}\n\n\n//\n// Legends\n//\n\n// For use with horizontal and inline forms, when you need the legend text to\n// be the same size as regular labels, and to align with the form controls.\n.col-form-legend {\n padding-top: $input-btn-padding-y;\n padding-bottom: $input-btn-padding-y;\n margin-bottom: 0;\n font-size: $font-size-base;\n}\n\n\n// Readonly controls as plain text\n//\n// Apply class to a readonly input to make it appear like regular plain\n// text (without any border, background color, focus indicator)\n\n.form-control-plaintext {\n padding-top: $input-btn-padding-y;\n padding-bottom: $input-btn-padding-y;\n margin-bottom: 0; // match inputs if this class comes on inputs with default margins\n line-height: $input-btn-line-height;\n border: solid transparent;\n border-width: $input-btn-border-width 0;\n\n &.form-control-sm,\n &.form-control-lg {\n padding-right: 0;\n padding-left: 0;\n }\n}\n\n\n// Form control sizing\n//\n// Build on `.form-control` with modifier classes to decrease or increase the\n// height and font-size of form controls.\n//\n// The `.form-group-* form-control` variations are sadly duplicated to avoid the\n// issue documented in https://github.com/twbs/bootstrap/issues/15074.\n\n.form-control-sm {\n padding: $input-btn-padding-y-sm $input-btn-padding-x-sm;\n font-size: $font-size-sm;\n line-height: $input-btn-line-height-sm;\n @include border-radius($input-border-radius-sm);\n}\n\nselect.form-control-sm {\n &:not([size]):not([multiple]) {\n height: $input-height-sm;\n }\n}\n\n.form-control-lg {\n padding: $input-btn-padding-y-lg $input-btn-padding-x-lg;\n font-size: $font-size-lg;\n line-height: $input-btn-line-height-lg;\n @include border-radius($input-border-radius-lg);\n}\n\nselect.form-control-lg {\n &:not([size]):not([multiple]) {\n height: $input-height-lg;\n }\n}\n\n\n// Form groups\n//\n// Designed to help with the organization and spacing of vertical forms. For\n// horizontal forms, use the predefined grid classes.\n\n.form-group {\n margin-bottom: $form-group-margin-bottom;\n}\n\n.form-text {\n display: block;\n margin-top: $form-text-margin-top;\n}\n\n\n// Form grid\n//\n// Special replacement for our grid system's `.row` for tighter form layouts.\n\n.form-row {\n display: flex;\n flex-wrap: wrap;\n margin-right: -5px;\n margin-left: -5px;\n\n > .col,\n > [class*=\"col-\"] {\n padding-right: 5px;\n padding-left: 5px;\n }\n}\n\n\n// Checkboxes and radios\n//\n// Indent the labels to position radios/checkboxes as hanging controls.\n\n.form-check {\n position: relative;\n display: block;\n margin-bottom: $form-check-margin-bottom;\n\n &.disabled {\n .form-check-label {\n color: $text-muted;\n }\n }\n}\n\n.form-check-label {\n padding-left: $form-check-input-gutter;\n margin-bottom: 0; // Override default `<label>` bottom margin\n}\n\n.form-check-input {\n position: absolute;\n margin-top: $form-check-input-margin-y;\n margin-left: -$form-check-input-gutter;\n\n &:only-child {\n position: static;\n }\n}\n\n// Radios and checkboxes on same line\n.form-check-inline {\n display: inline-block;\n\n .form-check-label {\n vertical-align: middle;\n }\n\n + .form-check-inline {\n margin-left: $form-check-inline-margin-x;\n }\n}\n\n\n// Form validation\n//\n// Provide feedback to users when form field values are valid or invalid. Works\n// primarily for client-side validation via scoped `:invalid` and `:valid`\n// pseudo-classes but also includes `.is-invalid` and `.is-valid` classes for\n// server side validation.\n\n.invalid-feedback {\n display: none;\n margin-top: .25rem;\n font-size: .875rem;\n color: $form-feedback-invalid-color;\n}\n\n.invalid-tooltip {\n position: absolute;\n top: 100%;\n z-index: 5;\n display: none;\n width: 250px;\n padding: .5rem;\n margin-top: .1rem;\n font-size: .875rem;\n line-height: 1;\n color: #fff;\n background-color: rgba($form-feedback-invalid-color,.8);\n border-radius: .2rem;\n}\n\n@include form-validation-state(\"valid\", $form-feedback-valid-color);\n@include form-validation-state(\"invalid\", $form-feedback-invalid-color);\n\n// Inline forms\n//\n// Make forms appear inline(-block) by adding the `.form-inline` class. Inline\n// forms begin stacked on extra small (mobile) devices and then go inline when\n// viewports reach <768px.\n//\n// Requires wrapping inputs and labels with `.form-group` for proper display of\n// default HTML form controls and our custom form controls (e.g., input groups).\n\n.form-inline {\n display: flex;\n flex-flow: row wrap;\n align-items: center; // Prevent shorter elements from growing to same height as others (e.g., small buttons growing to normal sized button height)\n\n // Because we use flex, the initial sizing of checkboxes is collapsed and\n // doesn't occupy the full-width (which is what we want for xs grid tier),\n // so we force that here.\n .form-check {\n width: 100%;\n }\n\n // Kick in the inline\n @include media-breakpoint-up(sm) {\n label {\n display: flex;\n align-items: center;\n justify-content: center;\n margin-bottom: 0;\n }\n\n // Inline-block all the things for \"inline\"\n .form-group {\n display: flex;\n flex: 0 0 auto;\n flex-flow: row wrap;\n align-items: center;\n margin-bottom: 0;\n }\n\n // Allow folks to *not* use `.form-group`\n .form-control {\n display: inline-block;\n width: auto; // Prevent labels from stacking above inputs in `.form-group`\n vertical-align: middle;\n }\n\n // Make static controls behave like regular ones\n .form-control-plaintext {\n display: inline-block;\n }\n\n .input-group {\n width: auto;\n }\n\n .form-control-label {\n margin-bottom: 0;\n vertical-align: middle;\n }\n\n // Remove default margin on radios/checkboxes that were used for stacking, and\n // then undo the floating of radios and checkboxes to match.\n .form-check {\n display: flex;\n align-items: center;\n justify-content: center;\n width: auto;\n margin-top: 0;\n margin-bottom: 0;\n }\n .form-check-label {\n padding-left: 0;\n }\n .form-check-input {\n position: relative;\n margin-top: 0;\n margin-right: $form-check-input-margin-x;\n margin-left: 0;\n }\n\n // Custom form controls\n .custom-control {\n display: flex;\n align-items: center;\n justify-content: center;\n padding-left: 0;\n }\n .custom-control-indicator {\n position: static;\n display: inline-block;\n margin-right: $form-check-input-margin-x; // Flexbox alignment means we lose our HTML space here, so we compensate.\n vertical-align: text-bottom;\n }\n\n // Re-override the feedback icon.\n .has-feedback .form-control-feedback {\n top: 0;\n }\n }\n}\n","// Form control focus state\n//\n// Generate a customized focus state and for any input with the specified color,\n// which defaults to the `@input-border-color-focus` variable.\n//\n// We highly encourage you to not customize the default value, but instead use\n// this to tweak colors on an as-needed basis. This aesthetic change is based on\n// WebKit's default styles, but applicable to a wider range of browsers. Its\n// usability and accessibility should be taken into account with any change.\n//\n// Example usage: change the default blue border and shadow to white for better\n// contrast against a dark gray background.\n@mixin form-control-focus() {\n &:focus {\n color: $input-focus-color;\n background-color: $input-focus-bg;\n border-color: $input-focus-border-color;\n outline: none;\n @include box-shadow($input-focus-box-shadow);\n }\n}\n\n\n@mixin form-validation-state($state, $color) {\n\n .form-control,\n .custom-select {\n .was-validated &:#{$state},\n &.is-#{$state} {\n border-color: $color;\n\n &:focus {\n box-shadow: 0 0 0 .2rem rgba($color,.25);\n }\n\n ~ .invalid-feedback,\n ~ .invalid-tooltip {\n display: block;\n }\n }\n }\n\n\n // TODO: redo check markup lol crap\n .form-check-input {\n .was-validated &:#{$state},\n &.is-#{$state} {\n + .form-check-label {\n color: $color;\n }\n }\n }\n\n // custom radios and checks\n .custom-control-input {\n .was-validated &:#{$state},\n &.is-#{$state} {\n ~ .custom-control-indicator {\n background-color: rgba($color, .25);\n }\n ~ .custom-control-description {\n color: $color;\n }\n }\n }\n\n // custom file\n .custom-file-input {\n .was-validated &:#{$state},\n &.is-#{$state} {\n ~ .custom-file-control {\n border-color: $color;\n\n &::before { border-color: inherit; }\n }\n &:focus {\n box-shadow: 0 0 0 .2rem rgba($color,.25);\n }\n }\n }\n}\n","// scss-lint:disable QualifyingElement\n\n//\n// Base styles\n//\n\n.btn {\n display: inline-block;\n font-weight: $btn-font-weight;\n text-align: center;\n white-space: nowrap;\n vertical-align: middle;\n user-select: none;\n border: $input-btn-border-width solid transparent;\n @include button-size($input-btn-padding-y, $input-btn-padding-x, $font-size-base, $input-btn-line-height, $btn-border-radius);\n @include transition($btn-transition);\n\n // Share hover and focus styles\n @include hover-focus {\n text-decoration: none;\n }\n &:focus,\n &.focus {\n outline: 0;\n box-shadow: $btn-focus-box-shadow;\n }\n\n // Disabled comes first so active can properly restyle\n &.disabled,\n &:disabled {\n opacity: .65;\n @include box-shadow(none);\n }\n\n &:active,\n &.active {\n background-image: none;\n @include box-shadow($btn-focus-box-shadow, $btn-active-box-shadow);\n }\n}\n\n// Future-proof disabling of clicks on `<a>` elements\na.btn.disabled,\nfieldset[disabled] a.btn {\n pointer-events: none;\n}\n\n\n//\n// Alternate buttons\n//\n\n@each $color, $value in $theme-colors {\n .btn-#{$color} {\n @include button-variant($value, $value);\n }\n}\n\n@each $color, $value in $theme-colors {\n .btn-outline-#{$color} {\n @include button-outline-variant($value, #fff);\n }\n}\n\n\n//\n// Link buttons\n//\n\n// Make a button look and behave like a link\n.btn-link {\n font-weight: $font-weight-normal;\n color: $link-color;\n border-radius: 0;\n\n &,\n &:active,\n &.active,\n &:disabled {\n background-color: transparent;\n @include box-shadow(none);\n }\n &,\n &:focus,\n &:active {\n border-color: transparent;\n box-shadow: none;\n }\n @include hover {\n border-color: transparent;\n }\n @include hover-focus {\n color: $link-hover-color;\n text-decoration: $link-hover-decoration;\n background-color: transparent;\n }\n &:disabled {\n color: $btn-link-disabled-color;\n\n @include hover-focus {\n text-decoration: none;\n }\n }\n}\n\n\n//\n// Button Sizes\n//\n\n.btn-lg {\n @include button-size($input-btn-padding-y-lg, $input-btn-padding-x-lg, $font-size-lg, $line-height-lg, $btn-border-radius-lg);\n}\n\n.btn-sm {\n @include button-size($input-btn-padding-y-sm, $input-btn-padding-x-sm, $font-size-sm, $line-height-sm, $btn-border-radius-sm);\n}\n\n\n//\n// Block button\n//\n\n.btn-block {\n display: block;\n width: 100%;\n}\n\n// Vertically space out multiple block buttons\n.btn-block + .btn-block {\n margin-top: $btn-block-spacing-y;\n}\n\n// Specificity overrides\ninput[type=\"submit\"],\ninput[type=\"reset\"],\ninput[type=\"button\"] {\n &.btn-block {\n width: 100%;\n }\n}\n","// Button variants\n//\n// Easily pump out default styles, as well as :hover, :focus, :active,\n// and disabled options for all buttons\n\n@mixin button-variant($background, $border, $active-background: darken($background, 7.5%), $active-border: darken($border, 10%)) {\n @include color-yiq($background);\n background-color: $background;\n border-color: $border;\n @include box-shadow($btn-box-shadow);\n\n &:hover {\n @include color-yiq($background);\n background-color: $active-background;\n border-color: $active-border;\n }\n\n &:focus,\n &.focus {\n // Avoid using mixin so we can pass custom focus shadow properly\n @if $enable-shadows {\n box-shadow: $btn-box-shadow, 0 0 0 3px rgba($border, .5);\n } @else {\n box-shadow: 0 0 0 3px rgba($border, .5);\n }\n }\n\n // Disabled comes first so active can properly restyle\n &.disabled,\n &:disabled {\n background-color: $background;\n border-color: $border;\n }\n\n &:active,\n &.active,\n .show > &.dropdown-toggle {\n background-color: $active-background;\n background-image: none; // Remove the gradient for the pressed/active state\n border-color: $active-border;\n @include box-shadow($btn-active-box-shadow);\n }\n}\n\n@mixin button-outline-variant($color, $color-hover: #fff) {\n color: $color;\n background-color: transparent;\n background-image: none;\n border-color: $color;\n\n @include hover {\n color: $color-hover;\n background-color: $color;\n border-color: $color;\n }\n\n &:focus,\n &.focus {\n box-shadow: 0 0 0 3px rgba($color, .5);\n }\n\n &.disabled,\n &:disabled {\n color: $color;\n background-color: transparent;\n }\n\n &:active,\n &.active,\n .show > &.dropdown-toggle {\n color: $color-hover;\n background-color: $color;\n border-color: $color;\n }\n}\n\n// Button sizes\n@mixin button-size($padding-y, $padding-x, $font-size, $line-height, $border-radius) {\n padding: $padding-y $padding-x;\n font-size: $font-size;\n line-height: $line-height;\n @include border-radius($border-radius);\n}\n","// Bootstrap functions\n//\n// Utility mixins and functions for evalutating source code across our variables, maps, and mixins.\n\n// Ascending\n// Used to evaluate Sass maps like our grid breakpoints.\n@mixin _assert-ascending($map, $map-name) {\n $prev-key: null;\n $prev-num: null;\n @each $key, $num in $map {\n @if $prev-num == null {\n // Do nothing\n } @else if not comparable($prev-num, $num) {\n @warn \"Potentially invalid value for #{$map-name}: This map must be in ascending order, but key '#{$key}' has value #{$num} whose unit makes it incomparable to #{$prev-num}, the value of the previous key '#{$prev-key}' !\";\n } @else if $prev-num >= $num {\n @warn \"Invalid value for #{$map-name}: This map must be in ascending order, but key '#{$key}' has value #{$num} which isn't greater than #{$prev-num}, the value of the previous key '#{$prev-key}' !\";\n }\n $prev-key: $key;\n $prev-num: $num;\n }\n}\n\n// Starts at zero\n// Another grid mixin that ensures the min-width of the lowest breakpoint starts at 0.\n@mixin _assert-starts-at-zero($map) {\n $values: map-values($map);\n $first-value: nth($values, 1);\n @if $first-value != 0 {\n @warn \"First breakpoint in `$grid-breakpoints` must start at 0, but starts at #{$first-value}.\";\n }\n}\n\n// Replace `$search` with `$replace` in `$string`\n// Used on our SVG icon backgrounds for custom forms.\n//\n// @author Hugo Giraudel\n// @param {String} $string - Initial string\n// @param {String} $search - Substring to replace\n// @param {String} $replace ('') - New value\n// @return {String} - Updated string\n@function str-replace($string, $search, $replace: \"\") {\n $index: str-index($string, $search);\n\n @if $index {\n @return str-slice($string, 1, $index - 1) + $replace + str-replace(str-slice($string, $index + str-length($search)), $search, $replace);\n }\n\n @return $string;\n}\n\n// Color contrast\n@mixin color-yiq($color) {\n $r: red($color);\n $g: green($color);\n $b: blue($color);\n\n $yiq: (($r * 299) + ($g * 587) + ($b * 114)) / 1000;\n\n @if ($yiq >= 150) {\n color: #111;\n } @else {\n color: #fff;\n }\n}\n\n// Retreive color Sass maps\n@function color($key: \"blue\") {\n @return map-get($colors, $key);\n}\n\n@function theme-color($key: \"primary\") {\n @return map-get($theme-colors, $key);\n}\n\n@function grayscale($key: \"100\") {\n @return map-get($grays, $key);\n}\n\n// Request a theme color level\n@function theme-color-level($color-name: \"primary\", $level: 0) {\n $color: theme-color($color-name);\n $color-base: if($level > 0, #000, #fff);\n\n @if $level < 0 {\n // Lighter values need a quick double negative for the Sass math to work\n @return mix($color-base, $color, $level * -1 * $theme-color-interval);\n } @else {\n @return mix($color-base, $color, $level * $theme-color-interval);\n }\n}\n",".fade {\n opacity: 0;\n @include transition($transition-fade);\n\n &.show {\n opacity: 1;\n }\n}\n\n.collapse {\n display: none;\n &.show {\n display: block;\n }\n}\n\ntr {\n &.collapse.show {\n display: table-row;\n }\n}\n\ntbody {\n &.collapse.show {\n display: table-row-group;\n }\n}\n\n.collapsing {\n position: relative;\n height: 0;\n overflow: hidden;\n @include transition($transition-collapse);\n}\n","// The dropdown wrapper (`<div>`)\n.dropup,\n.dropdown {\n position: relative;\n}\n\n.dropdown-toggle {\n // Generate the caret automatically\n &::after {\n display: inline-block;\n width: 0;\n height: 0;\n margin-left: $caret-width * .85;\n vertical-align: $caret-width * .85;\n content: \"\";\n border-top: $caret-width solid;\n border-right: $caret-width solid transparent;\n border-left: $caret-width solid transparent;\n }\n\n &:empty::after {\n margin-left: 0;\n }\n}\n\n// Allow for dropdowns to go bottom up (aka, dropup-menu)\n// Just add .dropup after the standard .dropdown class and you're set.\n.dropup {\n .dropdown-menu {\n margin-top: 0;\n margin-bottom: $dropdown-spacer;\n }\n\n .dropdown-toggle {\n &::after {\n border-top: 0;\n border-bottom: $caret-width solid;\n }\n }\n}\n\n// The dropdown menu\n.dropdown-menu {\n position: absolute;\n top: 100%;\n left: 0;\n z-index: $zindex-dropdown;\n display: none; // none by default, but block on \"open\" of the menu\n float: left;\n min-width: $dropdown-min-width;\n padding: $dropdown-padding-y 0;\n margin: $dropdown-spacer 0 0; // override default ul\n font-size: $font-size-base; // Redeclare because nesting can cause inheritance issues\n color: $body-color;\n text-align: left; // Ensures proper alignment if parent has it changed (e.g., modal footer)\n list-style: none;\n background-color: $dropdown-bg;\n background-clip: padding-box;\n border: $dropdown-border-width solid $dropdown-border-color;\n @include border-radius($border-radius);\n @include box-shadow($dropdown-box-shadow);\n}\n\n// Dividers (basically an `<hr>`) within the dropdown\n.dropdown-divider {\n @include nav-divider($dropdown-divider-bg);\n}\n\n// Links, buttons, and more within the dropdown menu\n//\n// `<button>`-specific styles are denoted with `// For <button>s`\n.dropdown-item {\n display: block;\n width: 100%; // For `<button>`s\n padding: $dropdown-item-padding-y $dropdown-item-padding-x;\n clear: both;\n font-weight: $font-weight-normal;\n color: $dropdown-link-color;\n text-align: inherit; // For `<button>`s\n white-space: nowrap; // prevent links from randomly breaking onto new lines\n background: none; // For `<button>`s\n border: 0; // For `<button>`s\n\n @include hover-focus {\n color: $dropdown-link-hover-color;\n text-decoration: none;\n background-color: $dropdown-link-hover-bg;\n }\n\n &.active,\n &:active {\n color: $dropdown-link-active-color;\n text-decoration: none;\n background-color: $dropdown-link-active-bg;\n }\n\n &.disabled,\n &:disabled {\n color: $dropdown-link-disabled-color;\n background-color: transparent;\n // Remove CSS gradients if they're enabled\n @if $enable-gradients {\n background-image: none;\n }\n }\n}\n\n// Open state for the dropdown\n.show {\n // Remove the outline when :focus is triggered\n > a {\n outline: 0;\n }\n}\n\n.dropdown-menu.show {\n display: block;\n}\n\n// Dropdown section headers\n.dropdown-header {\n display: block;\n padding: $dropdown-padding-y $dropdown-item-padding-x;\n margin-bottom: 0; // for use with heading elements\n font-size: $font-size-sm;\n color: $dropdown-header-color;\n white-space: nowrap; // as with > li > a\n}\n","// Horizontal dividers\n//\n// Dividers (basically an hr) within dropdowns and nav lists\n\n@mixin nav-divider($color: #e5e5e5) {\n height: 0;\n margin: ($spacer / 2) 0;\n overflow: hidden;\n border-top: 1px solid $color;\n}\n","// scss-lint:disable QualifyingElement\n\n// Make the div behave like a button\n.btn-group,\n.btn-group-vertical {\n position: relative;\n display: inline-flex;\n vertical-align: middle; // match .btn alignment given font-size hack above\n\n > .btn {\n position: relative;\n flex: 0 1 auto;\n margin-bottom: 0;\n\n // Bring the hover, focused, and \"active\" buttons to the front to overlay\n // the borders properly\n @include hover {\n z-index: 2;\n }\n &:focus,\n &:active,\n &.active {\n z-index: 2;\n }\n }\n\n // Prevent double borders when buttons are next to each other\n .btn + .btn,\n .btn + .btn-group,\n .btn-group + .btn,\n .btn-group + .btn-group {\n margin-left: -$input-btn-border-width;\n }\n}\n\n// Optional: Group multiple button groups together for a toolbar\n.btn-toolbar {\n display: flex;\n flex-wrap: wrap;\n justify-content: flex-start;\n\n .input-group {\n width: auto;\n }\n}\n\n.btn-group > .btn:not(:first-child):not(:last-child):not(.dropdown-toggle) {\n border-radius: 0;\n}\n\n// Set corners individual because sometimes a single button can be in a .btn-group and we need :first-child and :last-child to both match\n.btn-group > .btn:first-child {\n margin-left: 0;\n\n &:not(:last-child):not(.dropdown-toggle) {\n @include border-right-radius(0);\n }\n}\n// Need .dropdown-toggle since :last-child doesn't apply given a .dropdown-menu immediately after it\n.btn-group > .btn:last-child:not(:first-child),\n.btn-group > .dropdown-toggle:not(:first-child) {\n @include border-left-radius(0);\n}\n\n// Custom edits for including btn-groups within btn-groups (useful for including dropdown buttons within a btn-group)\n.btn-group > .btn-group {\n float: left;\n}\n.btn-group > .btn-group:not(:first-child):not(:last-child) > .btn {\n border-radius: 0;\n}\n.btn-group > .btn-group:first-child:not(:last-child) {\n > .btn:last-child,\n > .dropdown-toggle {\n @include border-right-radius(0);\n }\n}\n.btn-group > .btn-group:last-child:not(:first-child) > .btn:first-child {\n @include border-left-radius(0);\n}\n\n\n// Sizing\n//\n// Remix the default button sizing classes into new ones for easier manipulation.\n\n.btn-group-sm > .btn { @extend .btn-sm; }\n.btn-group-lg > .btn { @extend .btn-lg; }\n\n\n//\n// Split button dropdowns\n//\n\n.btn + .dropdown-toggle-split {\n padding-right: $input-btn-padding-x * .75;\n padding-left: $input-btn-padding-x * .75;\n\n &::after {\n margin-left: 0;\n }\n}\n\n.btn-sm + .dropdown-toggle-split {\n padding-right: $input-btn-padding-x-sm * .75;\n padding-left: $input-btn-padding-x-sm * .75;\n}\n\n.btn-lg + .dropdown-toggle-split {\n padding-right: $input-btn-padding-x-lg * .75;\n padding-left: $input-btn-padding-x-lg * .75;\n}\n\n\n// The clickable button for toggling the menu\n// Set the same inset shadow as the :active state\n.btn-group.show .dropdown-toggle {\n @include box-shadow($btn-active-box-shadow);\n\n // Show no shadow for `.btn-link` since it has no other button styles.\n &.btn-link {\n @include box-shadow(none);\n }\n}\n\n\n//\n// Vertical button groups\n//\n\n.btn-group-vertical {\n display: inline-flex;\n flex-direction: column;\n align-items: flex-start;\n justify-content: center;\n\n .btn,\n .btn-group {\n width: 100%;\n }\n\n > .btn + .btn,\n > .btn + .btn-group,\n > .btn-group + .btn,\n > .btn-group + .btn-group {\n margin-top: -$input-btn-border-width;\n margin-left: 0;\n }\n}\n\n.btn-group-vertical > .btn {\n &:not(:first-child):not(:last-child) {\n border-radius: 0;\n }\n &:first-child:not(:last-child) {\n @include border-bottom-radius(0);\n }\n &:last-child:not(:first-child) {\n @include border-top-radius(0);\n }\n}\n.btn-group-vertical > .btn-group:not(:first-child):not(:last-child) > .btn {\n border-radius: 0;\n}\n.btn-group-vertical > .btn-group:first-child:not(:last-child) {\n > .btn:last-child,\n > .dropdown-toggle {\n @include border-bottom-radius(0);\n }\n}\n.btn-group-vertical > .btn-group:last-child:not(:first-child) > .btn:first-child {\n @include border-top-radius(0);\n}\n\n\n// Checkbox and radio options\n//\n// In order to support the browser's form validation feedback, powered by the\n// `required` attribute, we have to \"hide\" the inputs via `clip`. We cannot use\n// `display: none;` or `visibility: hidden;` as that also hides the popover.\n// Simply visually hiding the inputs via `opacity` would leave them clickable in\n// certain cases which is prevented by using `clip` and `pointer-events`.\n// This way, we ensure a DOM element is visible to position the popover from.\n//\n// See https://github.com/twbs/bootstrap/pull/12794 and\n// https://github.com/twbs/bootstrap/pull/14559 for more information.\n\n[data-toggle=\"buttons\"] {\n > .btn,\n > .btn-group > .btn {\n input[type=\"radio\"],\n input[type=\"checkbox\"] {\n position: absolute;\n clip: rect(0,0,0,0);\n pointer-events: none;\n }\n }\n}\n","//\n// Base styles\n//\n\n.input-group {\n position: relative;\n display: flex;\n width: 100%;\n\n .form-control {\n // Ensure that the input is always above the *appended* addon button for\n // proper border colors.\n position: relative;\n z-index: 2;\n flex: 1 1 auto;\n // Add width 1% and flex-basis auto to ensure that button will not wrap out\n // the column. Applies to IE Edge+ and Firefox. Chrome does not require this.\n width: 1%;\n margin-bottom: 0;\n\n // Bring the \"active\" form control to the front\n @include hover-focus-active {\n z-index: 3;\n }\n }\n}\n\n.input-group-addon,\n.input-group-btn,\n.input-group .form-control {\n // Vertically centers the content of the addons within the input group\n display: flex;\n align-items: center;\n\n &:not(:first-child):not(:last-child) {\n @include border-radius(0);\n }\n}\n\n.input-group-addon,\n.input-group-btn {\n white-space: nowrap;\n vertical-align: middle; // Match the inputs\n}\n\n\n// Sizing options\n//\n// Remix the default form control sizing classes into new ones for easier\n// manipulation.\n\n.input-group-lg > .form-control,\n.input-group-lg > .input-group-addon,\n.input-group-lg > .input-group-btn > .btn {\n @extend .form-control-lg;\n}\n.input-group-sm > .form-control,\n.input-group-sm > .input-group-addon,\n.input-group-sm > .input-group-btn > .btn {\n @extend .form-control-sm;\n}\n\n\n//\n// Text input groups\n//\n\n.input-group-addon {\n padding: $input-btn-padding-y $input-btn-padding-x;\n margin-bottom: 0; // Allow use of <label> elements by overriding our default margin-bottom\n font-size: $font-size-base; // Match inputs\n font-weight: $font-weight-normal;\n line-height: $input-btn-line-height;\n color: $input-color;\n text-align: center;\n background-color: $input-group-addon-bg;\n border: $input-btn-border-width solid $input-group-addon-border-color;\n @include border-radius($input-border-radius);\n\n // Sizing\n &.form-control-sm {\n padding: $input-btn-padding-y-sm $input-btn-padding-x-sm;\n font-size: $font-size-sm;\n @include border-radius($input-border-radius-sm);\n }\n\n &.form-control-lg {\n padding: $input-btn-padding-y-lg $input-btn-padding-x-lg;\n font-size: $font-size-lg;\n @include border-radius($input-border-radius-lg);\n }\n\n // scss-lint:disable QualifyingElement\n // Nuke default margins from checkboxes and radios to vertically center within.\n input[type=\"radio\"],\n input[type=\"checkbox\"] {\n margin-top: 0;\n }\n // scss-lint:enable QualifyingElement\n}\n\n\n//\n// Reset rounded corners\n//\n\n.input-group .form-control:not(:last-child),\n.input-group-addon:not(:last-child),\n.input-group-btn:not(:last-child) > .btn,\n.input-group-btn:not(:last-child) > .btn-group > .btn,\n.input-group-btn:not(:last-child) > .dropdown-toggle,\n.input-group-btn:not(:first-child) > .btn:not(:last-child):not(.dropdown-toggle),\n.input-group-btn:not(:first-child) > .btn-group:not(:last-child) > .btn {\n @include border-right-radius(0);\n}\n.input-group-addon:not(:last-child) {\n border-right: 0;\n}\n.input-group .form-control:not(:first-child),\n.input-group-addon:not(:first-child),\n.input-group-btn:not(:first-child) > .btn,\n.input-group-btn:not(:first-child) > .btn-group > .btn,\n.input-group-btn:not(:first-child) > .dropdown-toggle,\n.input-group-btn:not(:last-child) > .btn:not(:first-child),\n.input-group-btn:not(:last-child) > .btn-group:not(:first-child) > .btn {\n @include border-left-radius(0);\n}\n.form-control + .input-group-addon:not(:first-child) {\n border-left: 0;\n}\n\n//\n// Button input groups\n//\n\n.input-group-btn {\n position: relative;\n // Jankily prevent input button groups from wrapping with `white-space` and\n // `font-size` in combination with `inline-block` on buttons.\n font-size: 0;\n white-space: nowrap;\n\n // Negative margin for spacing, position for bringing hovered/focused/actived\n // element above the siblings.\n > .btn {\n position: relative;\n\n + .btn {\n margin-left: (-$input-btn-border-width);\n }\n\n // Bring the \"active\" button to the front\n @include hover-focus-active {\n z-index: 3;\n }\n }\n\n // Negative margin to only have a single, shared border between the two\n &:not(:last-child) {\n > .btn,\n > .btn-group {\n margin-right: (-$input-btn-border-width);\n }\n }\n &:not(:first-child) {\n > .btn,\n > .btn-group {\n z-index: 2;\n margin-left: (-$input-btn-border-width);\n // Because specificity\n @include hover-focus-active {\n z-index: 3;\n }\n }\n }\n}\n","// scss-lint:disable PropertyCount, VendorPrefix\n\n// Embedded icons from Open Iconic.\n// Released under MIT and copyright 2014 Waybury.\n// https://useiconic.com/open\n\n\n// Checkboxes and radios\n//\n// Base class takes care of all the key behavioral aspects.\n\n.custom-control {\n position: relative;\n display: inline-flex;\n min-height: (1rem * $line-height-base);\n padding-left: $custom-control-gutter;\n margin-right: $custom-control-spacer-x;\n}\n\n.custom-control-input {\n position: absolute;\n z-index: -1; // Put the input behind the label so it doesn't overlay text\n opacity: 0;\n\n &:checked ~ .custom-control-indicator {\n color: $custom-control-indicator-checked-color;\n background-color: $custom-control-indicator-checked-bg;\n @include box-shadow($custom-control-indicator-checked-box-shadow);\n }\n\n &:focus ~ .custom-control-indicator {\n // the mixin is not used here to make sure there is feedback\n box-shadow: $custom-control-indicator-focus-box-shadow;\n }\n\n &:active ~ .custom-control-indicator {\n color: $custom-control-indicator-active-color;\n background-color: $custom-control-indicator-active-bg;\n @include box-shadow($custom-control-indicator-active-box-shadow);\n }\n\n &:disabled {\n ~ .custom-control-indicator {\n background-color: $custom-control-indicator-disabled-bg;\n }\n\n ~ .custom-control-description {\n color: $custom-control-description-disabled-color;\n }\n }\n}\n\n// Custom indicator\n//\n// Generates a shadow element to create our makeshift checkbox/radio background.\n\n.custom-control-indicator {\n position: absolute;\n top: (($line-height-base - $custom-control-indicator-size) / 2);\n left: 0;\n display: block;\n width: $custom-control-indicator-size;\n height: $custom-control-indicator-size;\n pointer-events: none;\n user-select: none;\n background-color: $custom-control-indicator-bg;\n background-repeat: no-repeat;\n background-position: center center;\n background-size: $custom-control-indicator-bg-size;\n @include box-shadow($custom-control-indicator-box-shadow);\n}\n\n// Checkboxes\n//\n// Tweak just a few things for checkboxes.\n\n.custom-checkbox {\n .custom-control-indicator {\n @include border-radius($custom-checkbox-indicator-border-radius);\n }\n\n .custom-control-input:checked ~ .custom-control-indicator {\n background-image: $custom-checkbox-indicator-icon-checked;\n }\n\n .custom-control-input:indeterminate ~ .custom-control-indicator {\n background-color: $custom-checkbox-indicator-indeterminate-bg;\n background-image: $custom-checkbox-indicator-icon-indeterminate;\n @include box-shadow($custom-checkbox-indicator-indeterminate-box-shadow);\n }\n}\n\n// Radios\n//\n// Tweak just a few things for radios.\n\n.custom-radio {\n .custom-control-indicator {\n border-radius: $custom-radio-indicator-border-radius;\n }\n\n .custom-control-input:checked ~ .custom-control-indicator {\n background-image: $custom-radio-indicator-icon-checked;\n }\n}\n\n\n// Layout options\n//\n// By default radios and checkboxes are `inline-block` with no additional spacing\n// set. Use these optional classes to tweak the layout.\n\n.custom-controls-stacked {\n display: flex;\n flex-direction: column;\n\n .custom-control {\n margin-bottom: $custom-control-spacer-y;\n\n + .custom-control {\n margin-left: 0;\n }\n }\n}\n\n\n// Select\n//\n// Replaces the browser default select with a custom one, mostly pulled from\n// http://primercss.io.\n//\n\n.custom-select {\n display: inline-block;\n max-width: 100%;\n height: $input-height;\n padding: $custom-select-padding-y ($custom-select-padding-x + $custom-select-indicator-padding) $custom-select-padding-y $custom-select-padding-x;\n line-height: $custom-select-line-height;\n color: $custom-select-color;\n vertical-align: middle;\n background: $custom-select-bg $custom-select-indicator no-repeat right $custom-select-padding-x center;\n background-size: $custom-select-bg-size;\n border: $custom-select-border-width solid $custom-select-border-color;\n @if $enable-rounded {\n border-radius: $custom-select-border-radius;\n } @else {\n border-radius: 0;\n }\n appearance: none;\n\n &:focus {\n border-color: $custom-select-focus-border-color;\n outline: none;\n @include box-shadow($custom-select-focus-box-shadow);\n\n &::-ms-value {\n // For visual consistency with other platforms/browsers,\n // supress the default white text on blue background highlight given to\n // the selected option text when the (still closed) <select> receives focus\n // in IE and (under certain conditions) Edge.\n // See https://github.com/twbs/bootstrap/issues/19398.\n color: $input-color;\n background-color: $input-bg;\n }\n }\n\n &:disabled {\n color: $custom-select-disabled-color;\n background-color: $custom-select-disabled-bg;\n }\n\n // Hides the default caret in IE11\n &::-ms-expand {\n opacity: 0;\n }\n}\n\n.custom-select-sm {\n height: $custom-select-height-sm;\n padding-top: $custom-select-padding-y;\n padding-bottom: $custom-select-padding-y;\n font-size: $custom-select-font-size-sm;\n}\n\n\n// File\n//\n// Custom file input.\n\n.custom-file {\n position: relative;\n display: inline-block;\n max-width: 100%;\n height: $custom-file-height;\n margin-bottom: 0;\n}\n\n.custom-file-input {\n min-width: $custom-file-width;\n max-width: 100%;\n height: $custom-file-height;\n margin: 0;\n opacity: 0;\n\n &:focus ~ .custom-file-control {\n @include box-shadow($custom-file-focus-box-shadow);\n }\n}\n\n.custom-file-control {\n position: absolute;\n top: 0;\n right: 0;\n left: 0;\n z-index: 5;\n height: $custom-file-height;\n padding: $custom-file-padding-x $custom-file-padding-y;\n line-height: $custom-file-line-height;\n color: $custom-file-color;\n pointer-events: none;\n user-select: none;\n background-color: $custom-file-bg;\n border: $custom-file-border-width solid $custom-file-border-color;\n @include border-radius($custom-file-border-radius);\n @include box-shadow($custom-file-box-shadow);\n\n @each $lang, $text in map-get($custom-file-text, placeholder) {\n &:lang(#{$lang}):empty::after {\n content: $text;\n }\n }\n\n &::before {\n position: absolute;\n top: -$custom-file-border-width;\n right: -$custom-file-border-width;\n bottom: -$custom-file-border-width;\n z-index: 6;\n display: block;\n height: $custom-file-height;\n padding: $custom-file-padding-x $custom-file-padding-y;\n line-height: $custom-file-line-height;\n color: $custom-file-button-color;\n background-color: $custom-file-button-bg;\n border: $custom-file-border-width solid $custom-file-border-color;\n @include border-radius(0 $custom-file-border-radius $custom-file-border-radius 0);\n }\n\n @each $lang, $text in map-get($custom-file-text, button-label) {\n &:lang(#{$lang})::before {\n content: $text;\n }\n }\n}\n","// Base class\n//\n// Kickstart any navigation component with a set of style resets. Works with\n// `<nav>`s or `<ul>`s.\n\n.nav {\n display: flex;\n flex-wrap: wrap;\n padding-left: 0;\n margin-bottom: 0;\n list-style: none;\n}\n\n.nav-link {\n display: block;\n padding: $nav-link-padding-y $nav-link-padding-x;\n\n @include hover-focus {\n text-decoration: none;\n }\n\n // Disabled state lightens text\n &.disabled {\n color: $nav-link-disabled-color;\n }\n}\n\n//\n// Tabs\n//\n\n.nav-tabs {\n border-bottom: $nav-tabs-border-width solid $nav-tabs-border-color;\n\n .nav-item {\n margin-bottom: -$nav-tabs-border-width;\n }\n\n .nav-link {\n border: $nav-tabs-border-width solid transparent;\n @include border-top-radius($nav-tabs-border-radius);\n\n @include hover-focus {\n border-color: $nav-tabs-link-hover-border-color $nav-tabs-link-hover-border-color $nav-tabs-border-color;\n }\n\n &.disabled {\n color: $nav-link-disabled-color;\n background-color: transparent;\n border-color: transparent;\n }\n }\n\n .nav-link.active,\n .nav-item.show .nav-link {\n color: $nav-tabs-link-active-color;\n background-color: $nav-tabs-link-active-bg;\n border-color: $nav-tabs-link-active-border-color $nav-tabs-link-active-border-color $nav-tabs-link-active-bg;\n }\n\n .dropdown-menu {\n // Make dropdown border overlap tab border\n margin-top: -$nav-tabs-border-width;\n // Remove the top rounded corners here since there is a hard edge above the menu\n @include border-top-radius(0);\n }\n}\n\n\n//\n// Pills\n//\n\n.nav-pills {\n .nav-link {\n @include border-radius($nav-pills-border-radius);\n\n &.active,\n .show > & {\n color: $nav-pills-link-active-color;\n background-color: $nav-pills-link-active-bg;\n }\n }\n}\n\n\n//\n// Justified variants\n//\n\n.nav-fill {\n .nav-item {\n flex: 1 1 auto;\n text-align: center;\n }\n}\n\n.nav-justified {\n .nav-item {\n flex-basis: 0;\n flex-grow: 1;\n text-align: center;\n }\n}\n\n\n// Tabbable tabs\n//\n// Hide tabbable panes to start, show them when `.active`\n\n.tab-content {\n > .tab-pane {\n display: none;\n }\n > .active {\n display: block;\n }\n}\n","// Contents\n//\n// Navbar\n// Navbar brand\n// Navbar nav\n// Navbar text\n// Navbar divider\n// Responsive navbar\n// Navbar position\n// Navbar themes\n\n\n// Navbar\n//\n// Provide a static navbar from which we expand to create full-width, fixed, and\n// other navbar variations.\n\n.navbar {\n position: relative;\n display: flex;\n flex-wrap: wrap; // allow us to do the line break for collapsing content\n align-items: center;\n justify-content: space-between; // space out brand from logo\n padding: $navbar-padding-y $navbar-padding-x;\n\n // Because flex properties aren't inherited, we need to redeclare these first\n // few properities so that content nested within behave properly.\n > .container,\n > .container-fluid {\n display: flex;\n flex-wrap: wrap;\n align-items: center;\n justify-content: space-between;\n }\n}\n\n\n// Navbar brand\n//\n// Used for brand, project, or site names.\n\n.navbar-brand {\n display: inline-block;\n padding-top: $navbar-brand-padding-y;\n padding-bottom: $navbar-brand-padding-y;\n margin-right: $navbar-padding-x;\n font-size: $navbar-brand-font-size;\n line-height: inherit;\n white-space: nowrap;\n\n @include hover-focus {\n text-decoration: none;\n }\n}\n\n\n// Navbar nav\n//\n// Custom navbar navigation (doesn't require `.nav`, but does make use of `.nav-link`).\n\n.navbar-nav {\n display: flex;\n flex-direction: column; // cannot use `inherit` to get the `.navbar`s value\n padding-left: 0;\n margin-bottom: 0;\n list-style: none;\n\n .nav-link {\n padding-right: 0;\n padding-left: 0;\n }\n\n .dropdown-menu {\n position: static;\n float: none;\n }\n}\n\n\n// Navbar text\n//\n//\n\n.navbar-text {\n display: inline-block;\n padding-top: $nav-link-padding-y;\n padding-bottom: $nav-link-padding-y;\n}\n\n\n// Responsive navbar\n//\n// Custom styles for responsive collapsing and toggling of navbar contents.\n// Powered by the collapse Bootstrap JavaScript plugin.\n\n// When collapsed, prevent the toggleable navbar contents from appearing in\n// the default flexbox row orienation. Requires the use of `flex-wrap: wrap`\n// on the `.navbar` parent.\n.navbar-collapse {\n flex-basis: 100%;\n // For always expanded or extra full navbars, ensure content aligns itself\n // properly vertically. Can be easily overridden with flex utilities.\n align-items: center;\n}\n\n// Button for toggling the navbar when in its collapsed state\n.navbar-toggler {\n padding: $navbar-toggler-padding-y $navbar-toggler-padding-x;\n font-size: $navbar-toggler-font-size;\n line-height: 1;\n background: transparent; // remove default button style\n border: $border-width solid transparent; // remove default button style\n @include border-radius($navbar-toggler-border-radius);\n\n @include hover-focus {\n text-decoration: none;\n }\n}\n\n// Keep as a separate element so folks can easily override it with another icon\n// or image file as needed.\n.navbar-toggler-icon {\n display: inline-block;\n width: 1.5em;\n height: 1.5em;\n vertical-align: middle;\n content: \"\";\n background: no-repeat center center;\n background-size: 100% 100%;\n}\n\n// Generate series of `.navbar-expand-*` responsive classes for configuring\n// where your navbar collapses.\n.navbar-expand {\n @each $breakpoint in map-keys($grid-breakpoints) {\n $next: breakpoint-next($breakpoint, $grid-breakpoints);\n $infix: breakpoint-infix($next, $grid-breakpoints);\n\n &#{$infix} {\n @include media-breakpoint-down($breakpoint) {\n > .container,\n > .container-fluid {\n padding-right: 0;\n padding-left: 0;\n }\n }\n\n @include media-breakpoint-up($next) {\n flex-direction: row;\n flex-wrap: nowrap;\n justify-content: flex-start;\n\n .navbar-nav {\n flex-direction: row;\n\n .dropdown-menu {\n position: absolute;\n }\n\n .dropdown-menu-right {\n right: 0;\n left: auto; // Reset the default from `.dropdown-menu`\n }\n\n .nav-link {\n padding-right: .5rem;\n padding-left: .5rem;\n }\n }\n\n // For nesting containers, have to redeclare for alignment purposes\n > .container,\n > .container-fluid {\n flex-wrap: nowrap;\n }\n\n // scss-lint:disable ImportantRule\n .navbar-collapse {\n display: flex !important;\n }\n // scss-lint:enable ImportantRule\n\n .navbar-toggler {\n display: none;\n }\n }\n }\n }\n}\n\n\n// Navbar themes\n//\n// Styles for switching between navbars with light or dark background.\n\n// Dark links against a light background\n.navbar-light {\n .navbar-brand {\n color: $navbar-light-active-color;\n\n @include hover-focus {\n color: $navbar-light-active-color;\n }\n }\n\n .navbar-nav {\n .nav-link {\n color: $navbar-light-color;\n\n @include hover-focus {\n color: $navbar-light-hover-color;\n }\n\n &.disabled {\n color: $navbar-light-disabled-color;\n }\n }\n\n .show > .nav-link,\n .active > .nav-link,\n .nav-link.show,\n .nav-link.active {\n color: $navbar-light-active-color;\n }\n }\n\n .navbar-toggler {\n color: $navbar-light-color;\n border-color: $navbar-light-toggler-border-color;\n }\n\n .navbar-toggler-icon {\n background-image: $navbar-light-toggler-icon-bg;\n }\n\n .navbar-text {\n color: $navbar-light-color;\n }\n}\n\n// White links against a dark background\n.navbar-dark {\n .navbar-brand {\n color: $navbar-dark-active-color;\n\n @include hover-focus {\n color: $navbar-dark-active-color;\n }\n }\n\n .navbar-nav {\n .nav-link {\n color: $navbar-dark-color;\n\n @include hover-focus {\n color: $navbar-dark-hover-color;\n }\n\n &.disabled {\n color: $navbar-dark-disabled-color;\n }\n }\n\n .show > .nav-link,\n .active > .nav-link,\n .nav-link.show,\n .nav-link.active {\n color: $navbar-dark-active-color;\n }\n }\n\n .navbar-toggler {\n color: $navbar-dark-color;\n border-color: $navbar-dark-toggler-border-color;\n }\n\n .navbar-toggler-icon {\n background-image: $navbar-dark-toggler-icon-bg;\n }\n\n .navbar-text {\n color: $navbar-dark-color;\n }\n}\n","//\n// Base styles\n//\n\n.card {\n position: relative;\n display: flex;\n flex-direction: column;\n min-width: 0;\n word-wrap: break-word;\n background-color: $card-bg;\n background-clip: border-box;\n border: $card-border-width solid $card-border-color;\n @include border-radius($card-border-radius);\n}\n\n.card-body {\n // Enable `flex-grow: 1` for decks and groups so that card blocks take up\n // as much space as possible, ensuring footers are aligned to the bottom.\n flex: 1 1 auto;\n padding: $card-spacer-x;\n}\n\n.card-title {\n margin-bottom: $card-spacer-y;\n}\n\n.card-subtitle {\n margin-top: -($card-spacer-y / 2);\n margin-bottom: 0;\n}\n\n.card-text:last-child {\n margin-bottom: 0;\n}\n\n.card-link {\n @include hover {\n text-decoration: none;\n }\n\n + .card-link {\n margin-left: $card-spacer-x;\n }\n}\n\n.card {\n > .list-group:first-child {\n .list-group-item:first-child {\n @include border-top-radius($card-border-radius);\n }\n }\n\n > .list-group:last-child {\n .list-group-item:last-child {\n @include border-bottom-radius($card-border-radius);\n }\n }\n}\n\n\n//\n// Optional textual caps\n//\n\n.card-header {\n padding: $card-spacer-y $card-spacer-x;\n margin-bottom: 0; // Removes the default margin-bottom of <hN>\n background-color: $card-cap-bg;\n border-bottom: $card-border-width solid $card-border-color;\n\n &:first-child {\n @include border-radius($card-inner-border-radius $card-inner-border-radius 0 0);\n }\n}\n\n.card-footer {\n padding: $card-spacer-y $card-spacer-x;\n background-color: $card-cap-bg;\n border-top: $card-border-width solid $card-border-color;\n\n &:last-child {\n @include border-radius(0 0 $card-inner-border-radius $card-inner-border-radius);\n }\n}\n\n\n//\n// Header navs\n//\n\n.card-header-tabs {\n margin-right: -($card-spacer-x / 2);\n margin-bottom: -$card-spacer-y;\n margin-left: -($card-spacer-x / 2);\n border-bottom: 0;\n}\n\n.card-header-pills {\n margin-right: -($card-spacer-x / 2);\n margin-left: -($card-spacer-x / 2);\n}\n\n// Card image\n.card-img-overlay {\n position: absolute;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n padding: $card-img-overlay-padding;\n}\n\n.card-img {\n width: 100%; // Required because we use flexbox and this inherently applies align-self: stretch\n @include border-radius($card-inner-border-radius);\n}\n\n// Card image caps\n.card-img-top {\n width: 100%; // Required because we use flexbox and this inherently applies align-self: stretch\n @include border-top-radius($card-inner-border-radius);\n}\n\n.card-img-bottom {\n width: 100%; // Required because we use flexbox and this inherently applies align-self: stretch\n @include border-bottom-radius($card-inner-border-radius);\n}\n\n\n// Card deck\n\n@include media-breakpoint-up(sm) {\n .card-deck {\n display: flex;\n flex-flow: row wrap;\n margin-right: -$card-deck-margin;\n margin-left: -$card-deck-margin;\n\n .card {\n display: flex;\n flex: 1 0 0%;\n flex-direction: column;\n margin-right: $card-deck-margin;\n margin-left: $card-deck-margin;\n }\n }\n}\n\n\n//\n// Card groups\n//\n\n@include media-breakpoint-up(sm) {\n .card-group {\n display: flex;\n flex-flow: row wrap;\n\n .card {\n flex: 1 0 0%;\n\n + .card {\n margin-left: 0;\n border-left: 0;\n }\n\n // Handle rounded corners\n @if $enable-rounded {\n &:first-child {\n @include border-right-radius(0);\n\n .card-img-top {\n border-top-right-radius: 0;\n }\n .card-img-bottom {\n border-bottom-right-radius: 0;\n }\n }\n &:last-child {\n @include border-left-radius(0);\n\n .card-img-top {\n border-top-left-radius: 0;\n }\n .card-img-bottom {\n border-bottom-left-radius: 0;\n }\n }\n\n &:not(:first-child):not(:last-child) {\n border-radius: 0;\n\n .card-img-top,\n .card-img-bottom {\n border-radius: 0;\n }\n }\n }\n }\n }\n}\n\n\n//\n// Columns\n//\n\n.card-columns {\n .card {\n margin-bottom: $card-columns-margin;\n }\n\n @include media-breakpoint-up(sm) {\n column-count: $card-columns-count;\n column-gap: $card-columns-gap;\n\n .card {\n display: inline-block; // Don't let them vertically span multiple columns\n width: 100%; // Don't let their width change\n }\n }\n}\n",".breadcrumb {\n padding: $breadcrumb-padding-y $breadcrumb-padding-x;\n margin-bottom: 1rem;\n list-style: none;\n background-color: $breadcrumb-bg;\n @include border-radius($border-radius);\n @include clearfix;\n}\n\n.breadcrumb-item {\n float: left;\n\n // The separator between breadcrumbs (by default, a forward-slash: \"/\")\n + .breadcrumb-item::before {\n display: inline-block; // Suppress underlining of the separator in modern browsers\n padding-right: $breadcrumb-item-padding;\n padding-left: $breadcrumb-item-padding;\n color: $breadcrumb-divider-color;\n content: \"#{$breadcrumb-divider}\";\n }\n\n // IE9-11 hack to properly handle hyperlink underlines for breadcrumbs built\n // without `<ul>`s. The `::before` pseudo-element generates an element\n // *within* the .breadcrumb-item and thereby inherits the `text-decoration`.\n //\n // To trick IE into suppressing the underline, we give the pseudo-element an\n // underline and then immediately remove it.\n + .breadcrumb-item:hover::before {\n text-decoration: underline;\n }\n + .breadcrumb-item:hover::before {\n text-decoration: none;\n }\n\n &.active {\n color: $breadcrumb-active-color;\n }\n}\n","@mixin clearfix() {\n &::after {\n display: block;\n clear: both;\n content: \"\";\n }\n}\n",".pagination {\n display: flex;\n // 1-2: Disable browser default list styles\n padding-left: 0; // 1\n list-style: none; // 2\n @include border-radius();\n}\n\n.page-item {\n &:first-child {\n .page-link {\n margin-left: 0;\n @include border-left-radius($border-radius);\n }\n }\n &:last-child {\n .page-link {\n @include border-right-radius($border-radius);\n }\n }\n\n &.active .page-link {\n z-index: 2;\n color: $pagination-active-color;\n background-color: $pagination-active-bg;\n border-color: $pagination-active-border-color;\n }\n\n &.disabled .page-link {\n color: $pagination-disabled-color;\n pointer-events: none;\n background-color: $pagination-disabled-bg;\n border-color: $pagination-disabled-border-color;\n }\n}\n\n.page-link {\n position: relative;\n display: block;\n padding: $pagination-padding-y $pagination-padding-x;\n margin-left: -1px;\n line-height: $pagination-line-height;\n color: $pagination-color;\n background-color: $pagination-bg;\n border: $pagination-border-width solid $pagination-border-color;\n\n @include hover-focus {\n color: $pagination-hover-color;\n text-decoration: none;\n background-color: $pagination-hover-bg;\n border-color: $pagination-hover-border-color;\n }\n}\n\n\n//\n// Sizing\n//\n\n.pagination-lg {\n @include pagination-size($pagination-padding-y-lg, $pagination-padding-x-lg, $font-size-lg, $line-height-lg, $border-radius-lg);\n}\n\n.pagination-sm {\n @include pagination-size($pagination-padding-y-sm, $pagination-padding-x-sm, $font-size-sm, $line-height-sm, $border-radius-sm);\n}\n","// Pagination\n\n@mixin pagination-size($padding-y, $padding-x, $font-size, $line-height, $border-radius) {\n .page-link {\n padding: $padding-y $padding-x;\n font-size: $font-size;\n line-height: $line-height;\n }\n\n .page-item {\n &:first-child {\n .page-link {\n @include border-left-radius($border-radius);\n }\n }\n &:last-child {\n .page-link {\n @include border-right-radius($border-radius);\n }\n }\n }\n}\n","// Base class\n//\n// Requires one of the contextual, color modifier classes for `color` and\n// `background-color`.\n\n.badge {\n display: inline-block;\n padding: $badge-padding-y $badge-padding-x;\n font-size: $badge-font-size;\n font-weight: $badge-font-weight;\n line-height: 1;\n color: $badge-color;\n text-align: center;\n white-space: nowrap;\n vertical-align: baseline;\n @include border-radius();\n\n // Empty badges collapse automatically\n &:empty {\n display: none;\n }\n}\n\n// Quick fix for badges in buttons\n.btn .badge {\n position: relative;\n top: -1px;\n}\n\n// Pill badges\n//\n// Make them extra rounded with a modifier to replace v3's badges.\n\n.badge-pill {\n padding-right: $badge-pill-padding-x;\n padding-left: $badge-pill-padding-x;\n @include border-radius($badge-pill-border-radius);\n}\n\n// Colors\n//\n// Contextual variations (linked badges get darker on :hover).\n\n@each $color, $value in $theme-colors {\n .badge-#{$color} {\n @include badge-variant($value);\n }\n}\n","@mixin badge-variant($bg) {\n @include color-yiq($bg);\n background-color: $bg;\n\n &[href] {\n @include hover-focus {\n @include color-yiq($bg);\n text-decoration: none;\n background-color: darken($bg, 10%);\n }\n }\n}\n",".jumbotron {\n padding: $jumbotron-padding ($jumbotron-padding / 2);\n margin-bottom: $jumbotron-padding;\n background-color: $jumbotron-bg;\n @include border-radius($border-radius-lg);\n\n @include media-breakpoint-up(sm) {\n padding: ($jumbotron-padding * 2) $jumbotron-padding;\n }\n}\n\n.jumbotron-fluid {\n padding-right: 0;\n padding-left: 0;\n @include border-radius(0);\n}\n","//\n// Base styles\n//\n\n.alert {\n padding: $alert-padding-y $alert-padding-x;\n margin-bottom: $alert-margin-bottom;\n border: $alert-border-width solid transparent;\n @include border-radius($alert-border-radius);\n}\n\n// Headings for larger alerts\n.alert-heading {\n // Specified to prevent conflicts of changing $headings-color\n color: inherit;\n}\n\n// Provide class for links that match alerts\n.alert-link {\n font-weight: $alert-link-font-weight;\n}\n\n\n// Dismissible alerts\n//\n// Expand the right padding and account for the close button's positioning.\n\n.alert-dismissible {\n // Adjust close link position\n .close {\n position: relative;\n top: -$alert-padding-y;\n right: -$alert-padding-x;\n padding: $alert-padding-y $alert-padding-x;\n color: inherit;\n }\n}\n\n\n// Alternate styles\n//\n// Generate contextual modifier classes for colorizing the alert.\n\n@each $color, $value in $theme-colors {\n .alert-#{$color} {\n @include alert-variant(theme-color-level($color, -10), theme-color-level($color, -9), theme-color-level($color, 6));\n }\n}\n","@mixin alert-variant($background, $border, $color) {\n color: $color;\n background-color: $background;\n border-color: $border;\n\n hr {\n border-top-color: darken($border, 5%);\n }\n\n .alert-link {\n color: darken($color, 10%);\n }\n}\n","@keyframes progress-bar-stripes {\n from { background-position: $progress-height 0; }\n to { background-position: 0 0; }\n}\n\n.progress {\n display: flex;\n overflow: hidden; // force rounded corners by cropping it\n font-size: $progress-font-size;\n line-height: $progress-height;\n text-align: center;\n background-color: $progress-bg;\n @include border-radius($progress-border-radius);\n @include box-shadow($progress-box-shadow);\n}\n\n.progress-bar {\n height: $progress-height;\n line-height: $progress-height;\n color: $progress-bar-color;\n background-color: $progress-bar-bg;\n @include transition($progress-bar-transition);\n}\n\n.progress-bar-striped {\n @include gradient-striped();\n background-size: $progress-height $progress-height;\n}\n\n.progress-bar-animated {\n animation: progress-bar-stripes $progress-bar-animation-timing;\n}\n","// Gradients\n\n// Horizontal gradient, from left to right\n//\n// Creates two color stops, start and end, by specifying a color and position for each color stop.\n@mixin gradient-x($start-color: #555, $end-color: #333, $start-percent: 0%, $end-percent: 100%) {\n background-image: linear-gradient(to right, $start-color $start-percent, $end-color $end-percent);\n background-repeat: repeat-x;\n}\n\n// Vertical gradient, from top to bottom\n//\n// Creates two color stops, start and end, by specifying a color and position for each color stop.\n@mixin gradient-y($start-color: #555, $end-color: #333, $start-percent: 0%, $end-percent: 100%) {\n background-image: linear-gradient(to bottom, $start-color $start-percent, $end-color $end-percent);\n background-repeat: repeat-x;\n}\n\n@mixin gradient-directional($start-color: #555, $end-color: #333, $deg: 45deg) {\n background-image: linear-gradient($deg, $start-color, $end-color);\n background-repeat: repeat-x;\n}\n@mixin gradient-x-three-colors($start-color: #00b3ee, $mid-color: #7a43b6, $color-stop: 50%, $end-color: #c3325f) {\n background-image: linear-gradient(to right, $start-color, $mid-color $color-stop, $end-color);\n background-repeat: no-repeat;\n}\n@mixin gradient-y-three-colors($start-color: #00b3ee, $mid-color: #7a43b6, $color-stop: 50%, $end-color: #c3325f) {\n background-image: linear-gradient($start-color, $mid-color $color-stop, $end-color);\n background-repeat: no-repeat;\n}\n@mixin gradient-radial($inner-color: #555, $outer-color: #333) {\n background-image: radial-gradient(circle, $inner-color, $outer-color);\n background-repeat: no-repeat;\n}\n@mixin gradient-striped($color: rgba(255,255,255,.15), $angle: 45deg) {\n background-image: linear-gradient($angle, $color 25%, transparent 25%, transparent 50%, $color 50%, $color 75%, transparent 75%, transparent);\n}\n",".media {\n display: flex;\n align-items: flex-start;\n}\n\n.media-body {\n flex: 1;\n}\n","// Base class\n//\n// Easily usable on <ul>, <ol>, or <div>.\n\n.list-group {\n display: flex;\n flex-direction: column;\n\n // No need to set list-style: none; since .list-group-item is block level\n padding-left: 0; // reset padding because ul and ol\n margin-bottom: 0;\n}\n\n\n// Interactive list items\n//\n// Use anchor or button elements instead of `li`s or `div`s to create interactive\n// list items. Includes an extra `.active` modifier class for selected items.\n\n.list-group-item-action {\n width: 100%; // For `<button>`s (anchors become 100% by default though)\n color: $list-group-action-color;\n text-align: inherit; // For `<button>`s (anchors inherit)\n\n // Hover state\n @include hover-focus {\n color: $list-group-action-hover-color;\n text-decoration: none;\n background-color: $list-group-hover-bg;\n }\n\n &:active {\n color: $list-group-action-active-color;\n background-color: $list-group-action-active-bg;\n }\n}\n\n\n// Individual list items\n//\n// Use on `li`s or `div`s within the `.list-group` parent.\n\n.list-group-item {\n position: relative;\n display: block;\n padding: $list-group-item-padding-y $list-group-item-padding-x;\n // Place the border on the list items and negative margin up for better styling\n margin-bottom: -$list-group-border-width;\n background-color: $list-group-bg;\n border: $list-group-border-width solid $list-group-border-color;\n\n &:first-child {\n @include border-top-radius($list-group-border-radius);\n }\n\n &:last-child {\n margin-bottom: 0;\n @include border-bottom-radius($list-group-border-radius);\n }\n\n @include hover-focus {\n text-decoration: none;\n }\n\n &.disabled,\n &:disabled {\n color: $list-group-disabled-color;\n background-color: $list-group-disabled-bg;\n }\n\n // Include both here for `<a>`s and `<button>`s\n &.active {\n z-index: 2; // Place active items above their siblings for proper border styling\n color: $list-group-active-color;\n background-color: $list-group-active-bg;\n border-color: $list-group-active-border-color;\n }\n}\n\n\n// Flush list items\n//\n// Remove borders and border-radius to keep list group items edge-to-edge. Most\n// useful within other components (e.g., cards).\n\n.list-group-flush {\n .list-group-item {\n border-right: 0;\n border-left: 0;\n border-radius: 0;\n }\n\n &:first-child {\n .list-group-item:first-child {\n border-top: 0;\n }\n }\n\n &:last-child {\n .list-group-item:last-child {\n border-bottom: 0;\n }\n }\n}\n\n\n// Contextual variants\n//\n// Add modifier classes to change text and background color on individual items.\n// Organizationally, this must come after the `:hover` states.\n\n@each $color, $value in $theme-colors {\n @include list-group-item-variant($color, theme-color-level($color, -9), theme-color-level($color, 6));\n}\n","// List Groups\n\n@mixin list-group-item-variant($state, $background, $color) {\n .list-group-item-#{$state} {\n color: $color;\n background-color: $background;\n }\n\n //scss-lint:disable QualifyingElement\n a.list-group-item-#{$state},\n button.list-group-item-#{$state} {\n color: $color;\n\n @include hover-focus {\n color: $color;\n background-color: darken($background, 5%);\n }\n\n &.active {\n color: #fff;\n background-color: $color;\n border-color: $color;\n }\n }\n // scss-lint:enable QualifyingElement\n}\n",".close {\n float: right;\n font-size: $close-font-size;\n font-weight: $close-font-weight;\n line-height: 1;\n color: $close-color;\n text-shadow: $close-text-shadow;\n opacity: .5;\n\n @include hover-focus {\n color: $close-color;\n text-decoration: none;\n opacity: .75;\n }\n}\n\n// Additional properties for button version\n// iOS requires the button element instead of an anchor tag.\n// If you want the anchor version, it requires `href=\"#\"`.\n// See https://developer.mozilla.org/en-US/docs/Web/Events/click#Safari_Mobile\n\n// scss-lint:disable QualifyingElement\nbutton.close {\n padding: 0;\n background: transparent;\n border: 0;\n -webkit-appearance: none;\n}\n// scss-lint:enable QualifyingElement\n","// .modal-open - body class for killing the scroll\n// .modal - container to scroll within\n// .modal-dialog - positioning shell for the actual modal\n// .modal-content - actual modal w/ bg and corners and stuff\n\n\n// Kill the scroll on the body\n.modal-open {\n overflow: hidden;\n}\n\n// Container that the modal scrolls within\n.modal {\n position: fixed;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: $zindex-modal;\n display: none;\n overflow: hidden;\n // Prevent Chrome on Windows from adding a focus outline. For details, see\n // https://github.com/twbs/bootstrap/pull/10951.\n outline: 0;\n // We deliberately don't use `-webkit-overflow-scrolling: touch;` due to a\n // gnarly iOS Safari bug: https://bugs.webkit.org/show_bug.cgi?id=158342\n // See also https://github.com/twbs/bootstrap/issues/17695\n\n // When fading in the modal, animate it to slide down\n &.fade .modal-dialog {\n @include transition($modal-transition);\n transform: translate(0, -25%);\n }\n &.show .modal-dialog { transform: translate(0, 0); }\n}\n.modal-open .modal {\n overflow-x: hidden;\n overflow-y: auto;\n}\n\n// Shell div to position the modal with bottom padding\n.modal-dialog {\n position: relative;\n width: auto;\n margin: $modal-dialog-margin;\n}\n\n// Actual modal\n.modal-content {\n position: relative;\n display: flex;\n flex-direction: column;\n background-color: $modal-content-bg;\n background-clip: padding-box;\n border: $modal-content-border-width solid $modal-content-border-color;\n @include border-radius($border-radius-lg);\n @include box-shadow($modal-content-box-shadow-xs);\n // Remove focus outline from opened modal\n outline: 0;\n}\n\n// Modal background\n.modal-backdrop {\n position: fixed;\n top: 0;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: $zindex-modal-backdrop;\n background-color: $modal-backdrop-bg;\n\n // Fade for backdrop\n &.fade { opacity: 0; }\n &.show { opacity: $modal-backdrop-opacity; }\n}\n\n// Modal header\n// Top section of the modal w/ title and dismiss\n.modal-header {\n display: flex;\n align-items: center; // vertically center it\n justify-content: space-between; // Put modal header elements (title and dismiss) on opposite ends\n padding: $modal-header-padding;\n border-bottom: $modal-header-border-width solid $modal-header-border-color;\n}\n\n// Title text within header\n.modal-title {\n margin-bottom: 0;\n line-height: $modal-title-line-height;\n}\n\n// Modal body\n// Where all modal content resides (sibling of .modal-header and .modal-footer)\n.modal-body {\n position: relative;\n // Enable `flex-grow: 1` so that the body take up as much space as possible\n // when should there be a fixed height on `.modal-dialog`.\n flex: 1 1 auto;\n padding: $modal-inner-padding;\n}\n\n// Footer (for actions)\n.modal-footer {\n display: flex;\n align-items: center; // vertically center\n justify-content: flex-end; // Right align buttons with flex property because text-align doesn't work on flex items\n padding: $modal-inner-padding;\n border-top: $modal-footer-border-width solid $modal-footer-border-color;\n\n // Easily place margin between footer elements\n > :not(:first-child) { margin-left: .25rem; }\n > :not(:last-child) { margin-right: .25rem; }\n}\n\n// Measure scrollbar width for padding body during modal show/hide\n.modal-scrollbar-measure {\n position: absolute;\n top: -9999px;\n width: 50px;\n height: 50px;\n overflow: scroll;\n}\n\n// Scale up the modal\n@include media-breakpoint-up(sm) {\n // Automatically set modal's width for larger viewports\n .modal-dialog {\n max-width: $modal-md;\n margin: $modal-dialog-margin-y-sm-up auto;\n }\n\n .modal-content {\n @include box-shadow($modal-content-box-shadow-sm-up);\n }\n\n .modal-sm { max-width: $modal-sm; }\n}\n\n@include media-breakpoint-up(lg) {\n .modal-lg { max-width: $modal-lg; }\n}\n","// Base class\n.tooltip {\n position: absolute;\n z-index: $zindex-tooltip;\n display: block;\n margin: $tooltip-margin;\n // Our parent element can be arbitrary since tooltips are by default inserted as a sibling of their target element.\n // So reset our font and text properties to avoid inheriting weird values.\n @include reset-text();\n font-size: $font-size-sm;\n // Allow breaking very long words so they don't overflow the tooltip's bounds\n word-wrap: break-word;\n opacity: 0;\n\n &.show { opacity: $tooltip-opacity; }\n\n .arrow {\n position: absolute;\n display: block;\n width: $tooltip-arrow-width;\n height: $tooltip-arrow-height;\n }\n\n &.bs-tooltip-top {\n padding: $tooltip-arrow-width 0;\n .arrow {\n bottom: 0;\n }\n\n .arrow::before {\n margin-left: -($tooltip-arrow-width - 2);\n content: \"\";\n border-width: $tooltip-arrow-width $tooltip-arrow-width 0;\n border-top-color: $tooltip-arrow-color;\n }\n }\n &.bs-tooltip-right {\n padding: 0 $tooltip-arrow-width;\n .arrow {\n left: 0;\n }\n\n .arrow::before {\n margin-top: -($tooltip-arrow-width - 2);\n content: \"\";\n border-width: $tooltip-arrow-width $tooltip-arrow-width $tooltip-arrow-width 0;\n border-right-color: $tooltip-arrow-color;\n }\n }\n &.bs-tooltip-bottom {\n padding: $tooltip-arrow-width 0;\n .arrow {\n top: 0;\n }\n\n .arrow::before {\n margin-left: -($tooltip-arrow-width - 2);\n content: \"\";\n border-width: 0 $tooltip-arrow-width $tooltip-arrow-width;\n border-bottom-color: $tooltip-arrow-color;\n }\n }\n &.bs-tooltip-left {\n padding: 0 $tooltip-arrow-width;\n .arrow {\n right: 0;\n }\n\n .arrow::before {\n right: 0;\n margin-top: -($tooltip-arrow-width - 2);\n content: \"\";\n border-width: $tooltip-arrow-width 0 $tooltip-arrow-width $tooltip-arrow-width;\n border-left-color: $tooltip-arrow-color;\n }\n }\n &.bs-tooltip-auto {\n &[x-placement^=\"top\"] {\n @extend .bs-tooltip-top;\n }\n &[x-placement^=\"right\"] {\n @extend .bs-tooltip-right;\n }\n &[x-placement^=\"bottom\"] {\n @extend .bs-tooltip-bottom;\n }\n &[x-placement^=\"left\"] {\n @extend .bs-tooltip-left;\n }\n }\n\n .arrow::before {\n position: absolute;\n border-color: transparent;\n border-style: solid;\n }\n}\n\n// Wrapper for the tooltip content\n.tooltip-inner {\n max-width: $tooltip-max-width;\n padding: $tooltip-padding-y $tooltip-padding-x;\n color: $tooltip-color;\n text-align: center;\n background-color: $tooltip-bg;\n @include border-radius($border-radius);\n}\n","// scss-lint:disable DuplicateProperty\n@mixin reset-text {\n font-family: $font-family-base;\n // We deliberately do NOT reset font-size or word-wrap.\n font-style: normal;\n font-weight: $font-weight-normal;\n line-height: $line-height-base;\n text-align: left; // Fallback for where `start` is not supported\n text-align: start;\n text-decoration: none;\n text-shadow: none;\n text-transform: none;\n letter-spacing: normal;\n word-break: normal;\n word-spacing: normal;\n white-space: normal;\n line-break: auto;\n}\n",".popover {\n position: absolute;\n top: 0;\n left: 0;\n z-index: $zindex-popover;\n display: block;\n max-width: $popover-max-width;\n padding: $popover-inner-padding;\n // Our parent element can be arbitrary since tooltips are by default inserted as a sibling of their target element.\n // So reset our font and text properties to avoid inheriting weird values.\n @include reset-text();\n font-size: $font-size-sm;\n // Allow breaking very long words so they don't overflow the popover's bounds\n word-wrap: break-word;\n background-color: $popover-bg;\n background-clip: padding-box;\n border: $popover-border-width solid $popover-border-color;\n @include border-radius($border-radius-lg);\n @include box-shadow($popover-box-shadow);\n\n // Arrows\n //\n // .arrow is outer, .arrow::after is inner\n\n .arrow {\n position: absolute;\n display: block;\n width: $popover-arrow-width;\n height: $popover-arrow-height;\n }\n\n .arrow::before,\n .arrow::after {\n position: absolute;\n display: block;\n border-color: transparent;\n border-style: solid;\n }\n\n .arrow::before {\n content: \"\";\n border-width: $popover-arrow-outer-width;\n }\n .arrow::after {\n content: \"\";\n border-width: $popover-arrow-outer-width;\n }\n\n // Popover directions\n\n &.bs-popover-top {\n margin-bottom: $popover-arrow-width;\n\n .arrow {\n bottom: 0;\n }\n\n .arrow::before,\n .arrow::after {\n border-bottom-width: 0;\n }\n\n .arrow::before {\n bottom: -$popover-arrow-outer-width;\n margin-left: -($popover-arrow-outer-width - 5);\n border-top-color: $popover-arrow-outer-color;\n }\n\n .arrow::after {\n bottom: -($popover-arrow-outer-width - 1);\n margin-left: -($popover-arrow-outer-width - 5);\n border-top-color: $popover-arrow-color;\n }\n }\n\n &.bs-popover-right {\n margin-left: $popover-arrow-width;\n\n .arrow {\n left: 0;\n }\n\n .arrow::before,\n .arrow::after {\n margin-top: -($popover-arrow-outer-width - 3);\n border-left-width: 0;\n }\n\n .arrow::before {\n left: -$popover-arrow-outer-width;\n border-right-color: $popover-arrow-outer-color;\n }\n\n .arrow::after {\n left: -($popover-arrow-outer-width - 1);\n border-right-color: $popover-arrow-color;\n }\n }\n\n &.bs-popover-bottom {\n margin-top: $popover-arrow-width;\n\n .arrow {\n top: 0;\n }\n\n .arrow::before,\n .arrow::after {\n margin-left: -($popover-arrow-width - 3);\n border-top-width: 0;\n }\n\n .arrow::before {\n top: -$popover-arrow-outer-width;\n border-bottom-color: $popover-arrow-outer-color;\n }\n\n .arrow::after {\n top: -($popover-arrow-outer-width - 1);\n border-bottom-color: $popover-arrow-color;\n }\n\n // This will remove the popover-header's border just below the arrow\n .popover-header::before {\n position: absolute;\n top: 0;\n left: 50%;\n display: block;\n width: 20px;\n margin-left: -10px;\n content: \"\";\n border-bottom: 1px solid $popover-header-bg;\n }\n }\n\n &.bs-popover-left {\n margin-right: $popover-arrow-width;\n\n .arrow {\n right: 0;\n }\n\n .arrow::before,\n .arrow::after {\n margin-top: -($popover-arrow-outer-width - 3);\n border-right-width: 0;\n }\n\n .arrow::before {\n right: -$popover-arrow-outer-width;\n border-left-color: $popover-arrow-outer-color;\n }\n\n .arrow::after {\n right: -($popover-arrow-outer-width - 1);\n border-left-color: $popover-arrow-color;\n }\n }\n &.bs-popover-auto {\n &[x-placement^=\"top\"] {\n @extend .bs-popover-top;\n }\n &[x-placement^=\"right\"] {\n @extend .bs-popover-right;\n }\n &[x-placement^=\"bottom\"] {\n @extend .bs-popover-bottom;\n }\n &[x-placement^=\"left\"] {\n @extend .bs-popover-left;\n }\n }\n}\n\n\n// Offset the popover to account for the popover arrow\n.popover-header {\n padding: $popover-header-padding-y $popover-header-padding-x;\n margin-bottom: 0; // Reset the default from Reboot\n font-size: $font-size-base;\n color: $popover-header-color;\n background-color: $popover-header-bg;\n border-bottom: $popover-border-width solid darken($popover-header-bg, 5%);\n $offset-border-width: calc(#{$border-radius-lg} - #{$popover-border-width});\n @include border-top-radius($offset-border-width);\n\n &:empty {\n display: none;\n }\n}\n\n.popover-body {\n padding: $popover-body-padding-y $popover-body-padding-x;\n color: $popover-body-color;\n}\n","// Wrapper for the slide container and indicators\n.carousel {\n position: relative;\n}\n\n.carousel-inner {\n position: relative;\n width: 100%;\n overflow: hidden;\n}\n\n.carousel-item {\n position: relative;\n display: none;\n align-items: center;\n width: 100%;\n @include transition($carousel-transition);\n backface-visibility: hidden;\n perspective: 1000px;\n}\n\n.carousel-item.active,\n.carousel-item-next,\n.carousel-item-prev {\n display: block;\n}\n\n.carousel-item-next,\n.carousel-item-prev {\n position: absolute;\n top: 0;\n}\n\n// CSS3 transforms when supported by the browser\n.carousel-item-next.carousel-item-left,\n.carousel-item-prev.carousel-item-right {\n transform: translateX(0);\n\n @supports (transform-style: preserve-3d) {\n transform: translate3d(0, 0, 0);\n }\n}\n\n.carousel-item-next,\n.active.carousel-item-right {\n transform: translateX(100%);\n\n @supports (transform-style: preserve-3d) {\n transform: translate3d(100%, 0, 0);\n }\n}\n\n.carousel-item-prev,\n.active.carousel-item-left {\n transform: translateX(-100%);\n\n @supports (transform-style: preserve-3d) {\n transform: translate3d(-100%, 0, 0);\n }\n}\n\n\n//\n// Left/right controls for nav\n//\n\n.carousel-control-prev,\n.carousel-control-next {\n position: absolute;\n top: 0;\n bottom: 0;\n // Use flex for alignment (1-3)\n display: flex; // 1. allow flex styles\n align-items: center; // 2. vertically center contents\n justify-content: center; // 3. horizontally center contents\n width: $carousel-control-width;\n color: $carousel-control-color;\n text-align: center;\n opacity: $carousel-control-opacity;\n // We can't have a transition here because WebKit cancels the carousel\n // animation if you trip this while in the middle of another animation.\n\n // Hover/focus state\n @include hover-focus {\n color: $carousel-control-color;\n text-decoration: none;\n outline: 0;\n opacity: .9;\n }\n}\n.carousel-control-prev {\n left: 0;\n}\n.carousel-control-next {\n right: 0;\n}\n\n// Icons for within\n.carousel-control-prev-icon,\n.carousel-control-next-icon {\n display: inline-block;\n width: $carousel-control-icon-width;\n height: $carousel-control-icon-width;\n background: transparent no-repeat center center;\n background-size: 100% 100%;\n}\n.carousel-control-prev-icon {\n background-image: $carousel-control-prev-icon-bg;\n}\n.carousel-control-next-icon {\n background-image: $carousel-control-next-icon-bg;\n}\n\n\n// Optional indicator pips\n//\n// Add an ordered list with the following class and add a list item for each\n// slide your carousel holds.\n\n.carousel-indicators {\n position: absolute;\n right: 0;\n bottom: 10px;\n left: 0;\n z-index: 15;\n display: flex;\n justify-content: center;\n padding-left: 0; // override <ol> default\n // Use the .carousel-control's width as margin so we don't overlay those\n margin-right: $carousel-control-width;\n margin-left: $carousel-control-width;\n list-style: none;\n\n li {\n position: relative;\n flex: 0 1 auto;\n width: $carousel-indicator-width;\n height: $carousel-indicator-height;\n margin-right: $carousel-indicator-spacer;\n margin-left: $carousel-indicator-spacer;\n text-indent: -999px;\n background-color: rgba($carousel-indicator-active-bg, .5);\n\n // Use pseudo classes to increase the hit area by 10px on top and bottom.\n &::before {\n position: absolute;\n top: -10px;\n left: 0;\n display: inline-block;\n width: 100%;\n height: 10px;\n content: \"\";\n }\n &::after {\n position: absolute;\n bottom: -10px;\n left: 0;\n display: inline-block;\n width: 100%;\n height: 10px;\n content: \"\";\n }\n }\n\n .active {\n background-color: $carousel-indicator-active-bg;\n }\n}\n\n\n// Optional captions\n//\n//\n\n.carousel-caption {\n position: absolute;\n right: ((100% - $carousel-caption-width) / 2);\n bottom: 20px;\n left: ((100% - $carousel-caption-width) / 2);\n z-index: 10;\n padding-top: 20px;\n padding-bottom: 20px;\n color: $carousel-caption-color;\n text-align: center;\n}\n",".align-baseline { vertical-align: baseline !important; } // Browser default\n.align-top { vertical-align: top !important; }\n.align-middle { vertical-align: middle !important; }\n.align-bottom { vertical-align: bottom !important; }\n.align-text-bottom { vertical-align: text-bottom !important; }\n.align-text-top { vertical-align: text-top !important; }\n","// Contextual backgrounds\n\n@mixin bg-variant($parent, $color) {\n #{$parent} {\n background-color: $color !important;\n }\n a#{$parent} {\n @include hover-focus {\n background-color: darken($color, 10%) !important;\n }\n }\n}\n","@each $color, $value in $theme-colors {\n @include bg-variant('.bg-#{$color}', $value);\n}\n\n.bg-white { background-color: $white !important; }\n.bg-transparent { background-color: transparent !important; }\n","//\n// Border\n//\n\n.border { border: 1px solid $gray-200 !important; }\n.border-0 { border: 0 !important; }\n.border-top-0 { border-top: 0 !important; }\n.border-right-0 { border-right: 0 !important; }\n.border-bottom-0 { border-bottom: 0 !important; }\n.border-left-0 { border-left: 0 !important; }\n\n@each $color, $value in $theme-colors {\n .border-#{$color} {\n border-color: $value !important;\n }\n}\n\n.border-white {\n border-color: $white !important;\n}\n\n//\n// Border-radius\n//\n\n.rounded {\n border-radius: $border-radius !important;\n}\n.rounded-top {\n border-top-left-radius: $border-radius !important;\n border-top-right-radius: $border-radius !important;\n}\n.rounded-right {\n border-top-right-radius: $border-radius !important;\n border-bottom-right-radius: $border-radius !important;\n}\n.rounded-bottom {\n border-bottom-right-radius: $border-radius !important;\n border-bottom-left-radius: $border-radius !important;\n}\n.rounded-left {\n border-top-left-radius: $border-radius !important;\n border-bottom-left-radius: $border-radius !important;\n}\n\n.rounded-circle {\n border-radius: 50%;\n}\n\n.rounded-0 {\n border-radius: 0;\n}\n","//\n// Utilities for common `display` values\n//\n\n@each $breakpoint in map-keys($grid-breakpoints) {\n @include media-breakpoint-up($breakpoint) {\n $infix: breakpoint-infix($breakpoint, $grid-breakpoints);\n\n .d#{$infix}-none { display: none !important; }\n .d#{$infix}-inline { display: inline !important; }\n .d#{$infix}-inline-block { display: inline-block !important; }\n .d#{$infix}-block { display: block !important; }\n .d#{$infix}-table { display: table !important; }\n .d#{$infix}-table-cell { display: table-cell !important; }\n .d#{$infix}-flex { display: flex !important; }\n .d#{$infix}-inline-flex { display: inline-flex !important; }\n }\n}\n\n\n//\n// Utilities for toggling `display` in print\n//\n\n.d-print-block {\n display: none !important;\n\n @media print {\n display: block !important;\n }\n}\n\n.d-print-inline {\n display: none !important;\n\n @media print {\n display: inline !important;\n }\n}\n\n.d-print-inline-block {\n display: none !important;\n\n @media print {\n display: inline-block !important;\n }\n}\n\n.d-print-none {\n @media print {\n display: none !important;\n }\n}\n","// Credit: Nicolas Gallagher and SUIT CSS.\n\n.embed-responsive {\n position: relative;\n display: block;\n width: 100%;\n padding: 0;\n overflow: hidden;\n\n &::before {\n display: block;\n content: \"\";\n }\n\n .embed-responsive-item,\n iframe,\n embed,\n object,\n video {\n position: absolute;\n top: 0;\n bottom: 0;\n left: 0;\n width: 100%;\n height: 100%;\n border: 0;\n }\n}\n\n.embed-responsive-21by9 {\n &::before {\n padding-top: percentage(9 / 21);\n }\n}\n\n.embed-responsive-16by9 {\n &::before {\n padding-top: percentage(9 / 16);\n }\n}\n\n.embed-responsive-4by3 {\n &::before {\n padding-top: percentage(3 / 4);\n }\n}\n\n.embed-responsive-1by1 {\n &::before {\n padding-top: percentage(1 / 1);\n }\n}\n","// Flex variation\n//\n// Custom styles for additional flex alignment options.\n\n@each $breakpoint in map-keys($grid-breakpoints) {\n @include media-breakpoint-up($breakpoint) {\n $infix: breakpoint-infix($breakpoint, $grid-breakpoints);\n\n .flex#{$infix}-row { flex-direction: row !important; }\n .flex#{$infix}-column { flex-direction: column !important; }\n .flex#{$infix}-row-reverse { flex-direction: row-reverse !important; }\n .flex#{$infix}-column-reverse { flex-direction: column-reverse !important; }\n\n .flex#{$infix}-wrap { flex-wrap: wrap !important; }\n .flex#{$infix}-nowrap { flex-wrap: nowrap !important; }\n .flex#{$infix}-wrap-reverse { flex-wrap: wrap-reverse !important; }\n\n .justify-content#{$infix}-start { justify-content: flex-start !important; }\n .justify-content#{$infix}-end { justify-content: flex-end !important; }\n .justify-content#{$infix}-center { justify-content: center !important; }\n .justify-content#{$infix}-between { justify-content: space-between !important; }\n .justify-content#{$infix}-around { justify-content: space-around !important; }\n\n .align-items#{$infix}-start { align-items: flex-start !important; }\n .align-items#{$infix}-end { align-items: flex-end !important; }\n .align-items#{$infix}-center { align-items: center !important; }\n .align-items#{$infix}-baseline { align-items: baseline !important; }\n .align-items#{$infix}-stretch { align-items: stretch !important; }\n\n .align-content#{$infix}-start { align-content: flex-start !important; }\n .align-content#{$infix}-end { align-content: flex-end !important; }\n .align-content#{$infix}-center { align-content: center !important; }\n .align-content#{$infix}-between { align-content: space-between !important; }\n .align-content#{$infix}-around { align-content: space-around !important; }\n .align-content#{$infix}-stretch { align-content: stretch !important; }\n\n .align-self#{$infix}-auto { align-self: auto !important; }\n .align-self#{$infix}-start { align-self: flex-start !important; }\n .align-self#{$infix}-end { align-self: flex-end !important; }\n .align-self#{$infix}-center { align-self: center !important; }\n .align-self#{$infix}-baseline { align-self: baseline !important; }\n .align-self#{$infix}-stretch { align-self: stretch !important; }\n }\n}\n","@each $breakpoint in map-keys($grid-breakpoints) {\n @include media-breakpoint-up($breakpoint) {\n $infix: breakpoint-infix($breakpoint, $grid-breakpoints);\n\n .float#{$infix}-left { @include float-left; }\n .float#{$infix}-right { @include float-right; }\n .float#{$infix}-none { @include float-none; }\n }\n}\n","@mixin float-left {\n float: left !important;\n}\n@mixin float-right {\n float: right !important;\n}\n@mixin float-none {\n float: none !important;\n}\n","// Positioning\n\n.fixed-top {\n position: fixed;\n top: 0;\n right: 0;\n left: 0;\n z-index: $zindex-fixed;\n}\n\n.fixed-bottom {\n position: fixed;\n right: 0;\n bottom: 0;\n left: 0;\n z-index: $zindex-fixed;\n}\n\n.sticky-top {\n @supports (position: sticky) {\n position: sticky;\n top: 0;\n z-index: $zindex-sticky;\n }\n}\n","//\n// Screenreaders\n//\n\n.sr-only {\n @include sr-only();\n}\n\n.sr-only-focusable {\n @include sr-only-focusable();\n}\n","// Only display content to screen readers\n//\n// See: http://a11yproject.com/posts/how-to-hide-content\n// See: http://hugogiraudel.com/2016/10/13/css-hide-and-seek/\n\n@mixin sr-only {\n position: absolute;\n width: 1px;\n height: 1px;\n padding: 0;\n overflow: hidden;\n clip: rect(0,0,0,0);\n white-space: nowrap;\n clip-path: inset(50%);\n border: 0;\n}\n\n// Use in conjunction with .sr-only to only display content when it's focused.\n//\n// Useful for \"Skip to main content\" links; see https://www.w3.org/TR/2013/NOTE-WCAG20-TECHS-20130905/G1\n//\n// Credit: HTML5 Boilerplate\n\n@mixin sr-only-focusable {\n &:active,\n &:focus {\n position: static;\n width: auto;\n height: auto;\n overflow: visible;\n clip: auto;\n white-space: normal;\n clip-path: none;\n }\n}\n","// Width and height\n\n@each $prop, $abbrev in (width: w, height: h) {\n @each $size, $length in $sizes {\n .#{$abbrev}-#{$size} { #{$prop}: $length !important; }\n }\n}\n\n.mw-100 { max-width: 100% !important; }\n.mh-100 { max-height: 100% !important; }\n","// Margin and Padding\n\n@each $breakpoint in map-keys($grid-breakpoints) {\n @include media-breakpoint-up($breakpoint) {\n $infix: breakpoint-infix($breakpoint, $grid-breakpoints);\n\n @each $prop, $abbrev in (margin: m, padding: p) {\n @each $size, $length in $spacers {\n\n .#{$abbrev}#{$infix}-#{$size} { #{$prop}: $length !important; }\n .#{$abbrev}t#{$infix}-#{$size} { #{$prop}-top: $length !important; }\n .#{$abbrev}r#{$infix}-#{$size} { #{$prop}-right: $length !important; }\n .#{$abbrev}b#{$infix}-#{$size} { #{$prop}-bottom: $length !important; }\n .#{$abbrev}l#{$infix}-#{$size} { #{$prop}-left: $length !important; }\n .#{$abbrev}x#{$infix}-#{$size} {\n #{$prop}-right: $length !important;\n #{$prop}-left: $length !important;\n }\n .#{$abbrev}y#{$infix}-#{$size} {\n #{$prop}-top: $length !important;\n #{$prop}-bottom: $length !important;\n }\n }\n }\n\n // Some special margin utils\n .m#{$infix}-auto { margin: auto !important; }\n .mt#{$infix}-auto { margin-top: auto !important; }\n .mr#{$infix}-auto { margin-right: auto !important; }\n .mb#{$infix}-auto { margin-bottom: auto !important; }\n .ml#{$infix}-auto { margin-left: auto !important; }\n .mx#{$infix}-auto {\n margin-right: auto !important;\n margin-left: auto !important;\n }\n .my#{$infix}-auto {\n margin-top: auto !important;\n margin-bottom: auto !important;\n }\n }\n}\n","//\n// Text\n//\n\n// Alignment\n\n.text-justify { text-align: justify !important; }\n.text-nowrap { white-space: nowrap !important; }\n.text-truncate { @include text-truncate; }\n\n// Responsive alignment\n\n@each $breakpoint in map-keys($grid-breakpoints) {\n @include media-breakpoint-up($breakpoint) {\n $infix: breakpoint-infix($breakpoint, $grid-breakpoints);\n\n .text#{$infix}-left { text-align: left !important; }\n .text#{$infix}-right { text-align: right !important; }\n .text#{$infix}-center { text-align: center !important; }\n }\n}\n\n// Transformation\n\n.text-lowercase { text-transform: lowercase !important; }\n.text-uppercase { text-transform: uppercase !important; }\n.text-capitalize { text-transform: capitalize !important; }\n\n// Weight and italics\n\n.font-weight-normal { font-weight: $font-weight-normal; }\n.font-weight-bold { font-weight: $font-weight-bold; }\n.font-italic { font-style: italic; }\n\n// Contextual colors\n\n.text-white { color: #fff !important; }\n\n@each $color, $value in $theme-colors {\n @include text-emphasis-variant('.text-#{$color}', $value);\n}\n\n.text-muted { color: $text-muted !important; }\n\n// Misc\n\n.text-hide {\n @include text-hide();\n}\n","// Text truncate\n// Requires inline-block or block for proper styling\n\n@mixin text-truncate() {\n overflow: hidden;\n text-overflow: ellipsis;\n white-space: nowrap;\n}\n","// Typography\n\n@mixin text-emphasis-variant($parent, $color) {\n #{$parent} {\n color: $color !important;\n }\n a#{$parent} {\n @include hover-focus {\n color: darken($color, 10%) !important;\n }\n }\n}\n","// CSS image replacement\n@mixin text-hide() {\n font: 0/0 a;\n color: transparent;\n text-shadow: none;\n background-color: transparent;\n border: 0;\n}\n","//\n// Visibility utilities\n//\n\n.visible {\n @include invisible(visible);\n}\n\n.invisible {\n @include invisible(hidden);\n}\n","// Visibility\n\n@mixin invisible($visibility) {\n visibility: $visibility !important;\n}\n"]} \ No newline at end of file
diff --git a/library/bootstrap/fonts/glyphicons-halflings-regular.eot b/library/bootstrap/fonts/glyphicons-halflings-regular.eot
deleted file mode 100644
index b93a4953f..000000000
--- a/library/bootstrap/fonts/glyphicons-halflings-regular.eot
+++ /dev/null
Binary files differ
diff --git a/library/bootstrap/fonts/glyphicons-halflings-regular.svg b/library/bootstrap/fonts/glyphicons-halflings-regular.svg
deleted file mode 100644
index 94fb5490a..000000000
--- a/library/bootstrap/fonts/glyphicons-halflings-regular.svg
+++ /dev/null
@@ -1,288 +0,0 @@
-<?xml version="1.0" standalone="no"?>
-<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd" >
-<svg xmlns="http://www.w3.org/2000/svg">
-<metadata></metadata>
-<defs>
-<font id="glyphicons_halflingsregular" horiz-adv-x="1200" >
-<font-face units-per-em="1200" ascent="960" descent="-240" />
-<missing-glyph horiz-adv-x="500" />
-<glyph horiz-adv-x="0" />
-<glyph horiz-adv-x="400" />
-<glyph unicode=" " />
-<glyph unicode="*" d="M600 1100q15 0 34 -1.5t30 -3.5l11 -1q10 -2 17.5 -10.5t7.5 -18.5v-224l158 158q7 7 18 8t19 -6l106 -106q7 -8 6 -19t-8 -18l-158 -158h224q10 0 18.5 -7.5t10.5 -17.5q6 -41 6 -75q0 -15 -1.5 -34t-3.5 -30l-1 -11q-2 -10 -10.5 -17.5t-18.5 -7.5h-224l158 -158 q7 -7 8 -18t-6 -19l-106 -106q-8 -7 -19 -6t-18 8l-158 158v-224q0 -10 -7.5 -18.5t-17.5 -10.5q-41 -6 -75 -6q-15 0 -34 1.5t-30 3.5l-11 1q-10 2 -17.5 10.5t-7.5 18.5v224l-158 -158q-7 -7 -18 -8t-19 6l-106 106q-7 8 -6 19t8 18l158 158h-224q-10 0 -18.5 7.5 t-10.5 17.5q-6 41 -6 75q0 15 1.5 34t3.5 30l1 11q2 10 10.5 17.5t18.5 7.5h224l-158 158q-7 7 -8 18t6 19l106 106q8 7 19 6t18 -8l158 -158v224q0 10 7.5 18.5t17.5 10.5q41 6 75 6z" />
-<glyph unicode="+" d="M450 1100h200q21 0 35.5 -14.5t14.5 -35.5v-350h350q21 0 35.5 -14.5t14.5 -35.5v-200q0 -21 -14.5 -35.5t-35.5 -14.5h-350v-350q0 -21 -14.5 -35.5t-35.5 -14.5h-200q-21 0 -35.5 14.5t-14.5 35.5v350h-350q-21 0 -35.5 14.5t-14.5 35.5v200q0 21 14.5 35.5t35.5 14.5 h350v350q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xa0;" />
-<glyph unicode="&#xa5;" d="M825 1100h250q10 0 12.5 -5t-5.5 -13l-364 -364q-6 -6 -11 -18h268q10 0 13 -6t-3 -14l-120 -160q-6 -8 -18 -14t-22 -6h-125v-100h275q10 0 13 -6t-3 -14l-120 -160q-6 -8 -18 -14t-22 -6h-125v-174q0 -11 -7.5 -18.5t-18.5 -7.5h-148q-11 0 -18.5 7.5t-7.5 18.5v174 h-275q-10 0 -13 6t3 14l120 160q6 8 18 14t22 6h125v100h-275q-10 0 -13 6t3 14l120 160q6 8 18 14t22 6h118q-5 12 -11 18l-364 364q-8 8 -5.5 13t12.5 5h250q25 0 43 -18l164 -164q8 -8 18 -8t18 8l164 164q18 18 43 18z" />
-<glyph unicode="&#x2000;" horiz-adv-x="650" />
-<glyph unicode="&#x2001;" horiz-adv-x="1300" />
-<glyph unicode="&#x2002;" horiz-adv-x="650" />
-<glyph unicode="&#x2003;" horiz-adv-x="1300" />
-<glyph unicode="&#x2004;" horiz-adv-x="433" />
-<glyph unicode="&#x2005;" horiz-adv-x="325" />
-<glyph unicode="&#x2006;" horiz-adv-x="216" />
-<glyph unicode="&#x2007;" horiz-adv-x="216" />
-<glyph unicode="&#x2008;" horiz-adv-x="162" />
-<glyph unicode="&#x2009;" horiz-adv-x="260" />
-<glyph unicode="&#x200a;" horiz-adv-x="72" />
-<glyph unicode="&#x202f;" horiz-adv-x="260" />
-<glyph unicode="&#x205f;" horiz-adv-x="325" />
-<glyph unicode="&#x20ac;" d="M744 1198q242 0 354 -189q60 -104 66 -209h-181q0 45 -17.5 82.5t-43.5 61.5t-58 40.5t-60.5 24t-51.5 7.5q-19 0 -40.5 -5.5t-49.5 -20.5t-53 -38t-49 -62.5t-39 -89.5h379l-100 -100h-300q-6 -50 -6 -100h406l-100 -100h-300q9 -74 33 -132t52.5 -91t61.5 -54.5t59 -29 t47 -7.5q22 0 50.5 7.5t60.5 24.5t58 41t43.5 61t17.5 80h174q-30 -171 -128 -278q-107 -117 -274 -117q-206 0 -324 158q-36 48 -69 133t-45 204h-217l100 100h112q1 47 6 100h-218l100 100h134q20 87 51 153.5t62 103.5q117 141 297 141z" />
-<glyph unicode="&#x20bd;" d="M428 1200h350q67 0 120 -13t86 -31t57 -49.5t35 -56.5t17 -64.5t6.5 -60.5t0.5 -57v-16.5v-16.5q0 -36 -0.5 -57t-6.5 -61t-17 -65t-35 -57t-57 -50.5t-86 -31.5t-120 -13h-178l-2 -100h288q10 0 13 -6t-3 -14l-120 -160q-6 -8 -18 -14t-22 -6h-138v-175q0 -11 -5.5 -18 t-15.5 -7h-149q-10 0 -17.5 7.5t-7.5 17.5v175h-267q-10 0 -13 6t3 14l120 160q6 8 18 14t22 6h117v100h-267q-10 0 -13 6t3 14l120 160q6 8 18 14t22 6h117v475q0 10 7.5 17.5t17.5 7.5zM600 1000v-300h203q64 0 86.5 33t22.5 119q0 84 -22.5 116t-86.5 32h-203z" />
-<glyph unicode="&#x2212;" d="M250 700h800q21 0 35.5 -14.5t14.5 -35.5v-200q0 -21 -14.5 -35.5t-35.5 -14.5h-800q-21 0 -35.5 14.5t-14.5 35.5v200q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#x231b;" d="M1000 1200v-150q0 -21 -14.5 -35.5t-35.5 -14.5h-50v-100q0 -91 -49.5 -165.5t-130.5 -109.5q81 -35 130.5 -109.5t49.5 -165.5v-150h50q21 0 35.5 -14.5t14.5 -35.5v-150h-800v150q0 21 14.5 35.5t35.5 14.5h50v150q0 91 49.5 165.5t130.5 109.5q-81 35 -130.5 109.5 t-49.5 165.5v100h-50q-21 0 -35.5 14.5t-14.5 35.5v150h800zM400 1000v-100q0 -60 32.5 -109.5t87.5 -73.5q28 -12 44 -37t16 -55t-16 -55t-44 -37q-55 -24 -87.5 -73.5t-32.5 -109.5v-150h400v150q0 60 -32.5 109.5t-87.5 73.5q-28 12 -44 37t-16 55t16 55t44 37 q55 24 87.5 73.5t32.5 109.5v100h-400z" />
-<glyph unicode="&#x25fc;" horiz-adv-x="500" d="M0 0z" />
-<glyph unicode="&#x2601;" d="M503 1089q110 0 200.5 -59.5t134.5 -156.5q44 14 90 14q120 0 205 -86.5t85 -206.5q0 -121 -85 -207.5t-205 -86.5h-750q-79 0 -135.5 57t-56.5 137q0 69 42.5 122.5t108.5 67.5q-2 12 -2 37q0 153 108 260.5t260 107.5z" />
-<glyph unicode="&#x26fa;" d="M774 1193.5q16 -9.5 20.5 -27t-5.5 -33.5l-136 -187l467 -746h30q20 0 35 -18.5t15 -39.5v-42h-1200v42q0 21 15 39.5t35 18.5h30l468 746l-135 183q-10 16 -5.5 34t20.5 28t34 5.5t28 -20.5l111 -148l112 150q9 16 27 20.5t34 -5zM600 200h377l-182 112l-195 534v-646z " />
-<glyph unicode="&#x2709;" d="M25 1100h1150q10 0 12.5 -5t-5.5 -13l-564 -567q-8 -8 -18 -8t-18 8l-564 567q-8 8 -5.5 13t12.5 5zM18 882l264 -264q8 -8 8 -18t-8 -18l-264 -264q-8 -8 -13 -5.5t-5 12.5v550q0 10 5 12.5t13 -5.5zM918 618l264 264q8 8 13 5.5t5 -12.5v-550q0 -10 -5 -12.5t-13 5.5 l-264 264q-8 8 -8 18t8 18zM818 482l364 -364q8 -8 5.5 -13t-12.5 -5h-1150q-10 0 -12.5 5t5.5 13l364 364q8 8 18 8t18 -8l164 -164q8 -8 18 -8t18 8l164 164q8 8 18 8t18 -8z" />
-<glyph unicode="&#x270f;" d="M1011 1210q19 0 33 -13l153 -153q13 -14 13 -33t-13 -33l-99 -92l-214 214l95 96q13 14 32 14zM1013 800l-615 -614l-214 214l614 614zM317 96l-333 -112l110 335z" />
-<glyph unicode="&#xe001;" d="M700 650v-550h250q21 0 35.5 -14.5t14.5 -35.5v-50h-800v50q0 21 14.5 35.5t35.5 14.5h250v550l-500 550h1200z" />
-<glyph unicode="&#xe002;" d="M368 1017l645 163q39 15 63 0t24 -49v-831q0 -55 -41.5 -95.5t-111.5 -63.5q-79 -25 -147 -4.5t-86 75t25.5 111.5t122.5 82q72 24 138 8v521l-600 -155v-606q0 -42 -44 -90t-109 -69q-79 -26 -147 -5.5t-86 75.5t25.5 111.5t122.5 82.5q72 24 138 7v639q0 38 14.5 59 t53.5 34z" />
-<glyph unicode="&#xe003;" d="M500 1191q100 0 191 -39t156.5 -104.5t104.5 -156.5t39 -191l-1 -2l1 -5q0 -141 -78 -262l275 -274q23 -26 22.5 -44.5t-22.5 -42.5l-59 -58q-26 -20 -46.5 -20t-39.5 20l-275 274q-119 -77 -261 -77l-5 1l-2 -1q-100 0 -191 39t-156.5 104.5t-104.5 156.5t-39 191 t39 191t104.5 156.5t156.5 104.5t191 39zM500 1022q-88 0 -162 -43t-117 -117t-43 -162t43 -162t117 -117t162 -43t162 43t117 117t43 162t-43 162t-117 117t-162 43z" />
-<glyph unicode="&#xe005;" d="M649 949q48 68 109.5 104t121.5 38.5t118.5 -20t102.5 -64t71 -100.5t27 -123q0 -57 -33.5 -117.5t-94 -124.5t-126.5 -127.5t-150 -152.5t-146 -174q-62 85 -145.5 174t-150 152.5t-126.5 127.5t-93.5 124.5t-33.5 117.5q0 64 28 123t73 100.5t104 64t119 20 t120.5 -38.5t104.5 -104z" />
-<glyph unicode="&#xe006;" d="M407 800l131 353q7 19 17.5 19t17.5 -19l129 -353h421q21 0 24 -8.5t-14 -20.5l-342 -249l130 -401q7 -20 -0.5 -25.5t-24.5 6.5l-343 246l-342 -247q-17 -12 -24.5 -6.5t-0.5 25.5l130 400l-347 251q-17 12 -14 20.5t23 8.5h429z" />
-<glyph unicode="&#xe007;" d="M407 800l131 353q7 19 17.5 19t17.5 -19l129 -353h421q21 0 24 -8.5t-14 -20.5l-342 -249l130 -401q7 -20 -0.5 -25.5t-24.5 6.5l-343 246l-342 -247q-17 -12 -24.5 -6.5t-0.5 25.5l130 400l-347 251q-17 12 -14 20.5t23 8.5h429zM477 700h-240l197 -142l-74 -226 l193 139l195 -140l-74 229l192 140h-234l-78 211z" />
-<glyph unicode="&#xe008;" d="M600 1200q124 0 212 -88t88 -212v-250q0 -46 -31 -98t-69 -52v-75q0 -10 6 -21.5t15 -17.5l358 -230q9 -5 15 -16.5t6 -21.5v-93q0 -10 -7.5 -17.5t-17.5 -7.5h-1150q-10 0 -17.5 7.5t-7.5 17.5v93q0 10 6 21.5t15 16.5l358 230q9 6 15 17.5t6 21.5v75q-38 0 -69 52 t-31 98v250q0 124 88 212t212 88z" />
-<glyph unicode="&#xe009;" d="M25 1100h1150q10 0 17.5 -7.5t7.5 -17.5v-1050q0 -10 -7.5 -17.5t-17.5 -7.5h-1150q-10 0 -17.5 7.5t-7.5 17.5v1050q0 10 7.5 17.5t17.5 7.5zM100 1000v-100h100v100h-100zM875 1000h-550q-10 0 -17.5 -7.5t-7.5 -17.5v-350q0 -10 7.5 -17.5t17.5 -7.5h550 q10 0 17.5 7.5t7.5 17.5v350q0 10 -7.5 17.5t-17.5 7.5zM1000 1000v-100h100v100h-100zM100 800v-100h100v100h-100zM1000 800v-100h100v100h-100zM100 600v-100h100v100h-100zM1000 600v-100h100v100h-100zM875 500h-550q-10 0 -17.5 -7.5t-7.5 -17.5v-350q0 -10 7.5 -17.5 t17.5 -7.5h550q10 0 17.5 7.5t7.5 17.5v350q0 10 -7.5 17.5t-17.5 7.5zM100 400v-100h100v100h-100zM1000 400v-100h100v100h-100zM100 200v-100h100v100h-100zM1000 200v-100h100v100h-100z" />
-<glyph unicode="&#xe010;" d="M50 1100h400q21 0 35.5 -14.5t14.5 -35.5v-400q0 -21 -14.5 -35.5t-35.5 -14.5h-400q-21 0 -35.5 14.5t-14.5 35.5v400q0 21 14.5 35.5t35.5 14.5zM650 1100h400q21 0 35.5 -14.5t14.5 -35.5v-400q0 -21 -14.5 -35.5t-35.5 -14.5h-400q-21 0 -35.5 14.5t-14.5 35.5v400 q0 21 14.5 35.5t35.5 14.5zM50 500h400q21 0 35.5 -14.5t14.5 -35.5v-400q0 -21 -14.5 -35.5t-35.5 -14.5h-400q-21 0 -35.5 14.5t-14.5 35.5v400q0 21 14.5 35.5t35.5 14.5zM650 500h400q21 0 35.5 -14.5t14.5 -35.5v-400q0 -21 -14.5 -35.5t-35.5 -14.5h-400 q-21 0 -35.5 14.5t-14.5 35.5v400q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe011;" d="M50 1100h200q21 0 35.5 -14.5t14.5 -35.5v-200q0 -21 -14.5 -35.5t-35.5 -14.5h-200q-21 0 -35.5 14.5t-14.5 35.5v200q0 21 14.5 35.5t35.5 14.5zM450 1100h200q21 0 35.5 -14.5t14.5 -35.5v-200q0 -21 -14.5 -35.5t-35.5 -14.5h-200q-21 0 -35.5 14.5t-14.5 35.5v200 q0 21 14.5 35.5t35.5 14.5zM850 1100h200q21 0 35.5 -14.5t14.5 -35.5v-200q0 -21 -14.5 -35.5t-35.5 -14.5h-200q-21 0 -35.5 14.5t-14.5 35.5v200q0 21 14.5 35.5t35.5 14.5zM50 700h200q21 0 35.5 -14.5t14.5 -35.5v-200q0 -21 -14.5 -35.5t-35.5 -14.5h-200 q-21 0 -35.5 14.5t-14.5 35.5v200q0 21 14.5 35.5t35.5 14.5zM450 700h200q21 0 35.5 -14.5t14.5 -35.5v-200q0 -21 -14.5 -35.5t-35.5 -14.5h-200q-21 0 -35.5 14.5t-14.5 35.5v200q0 21 14.5 35.5t35.5 14.5zM850 700h200q21 0 35.5 -14.5t14.5 -35.5v-200 q0 -21 -14.5 -35.5t-35.5 -14.5h-200q-21 0 -35.5 14.5t-14.5 35.5v200q0 21 14.5 35.5t35.5 14.5zM50 300h200q21 0 35.5 -14.5t14.5 -35.5v-200q0 -21 -14.5 -35.5t-35.5 -14.5h-200q-21 0 -35.5 14.5t-14.5 35.5v200q0 21 14.5 35.5t35.5 14.5zM450 300h200 q21 0 35.5 -14.5t14.5 -35.5v-200q0 -21 -14.5 -35.5t-35.5 -14.5h-200q-21 0 -35.5 14.5t-14.5 35.5v200q0 21 14.5 35.5t35.5 14.5zM850 300h200q21 0 35.5 -14.5t14.5 -35.5v-200q0 -21 -14.5 -35.5t-35.5 -14.5h-200q-21 0 -35.5 14.5t-14.5 35.5v200q0 21 14.5 35.5 t35.5 14.5z" />
-<glyph unicode="&#xe012;" d="M50 1100h200q21 0 35.5 -14.5t14.5 -35.5v-200q0 -21 -14.5 -35.5t-35.5 -14.5h-200q-21 0 -35.5 14.5t-14.5 35.5v200q0 21 14.5 35.5t35.5 14.5zM450 1100h700q21 0 35.5 -14.5t14.5 -35.5v-200q0 -21 -14.5 -35.5t-35.5 -14.5h-700q-21 0 -35.5 14.5t-14.5 35.5v200 q0 21 14.5 35.5t35.5 14.5zM50 700h200q21 0 35.5 -14.5t14.5 -35.5v-200q0 -21 -14.5 -35.5t-35.5 -14.5h-200q-21 0 -35.5 14.5t-14.5 35.5v200q0 21 14.5 35.5t35.5 14.5zM450 700h700q21 0 35.5 -14.5t14.5 -35.5v-200q0 -21 -14.5 -35.5t-35.5 -14.5h-700 q-21 0 -35.5 14.5t-14.5 35.5v200q0 21 14.5 35.5t35.5 14.5zM50 300h200q21 0 35.5 -14.5t14.5 -35.5v-200q0 -21 -14.5 -35.5t-35.5 -14.5h-200q-21 0 -35.5 14.5t-14.5 35.5v200q0 21 14.5 35.5t35.5 14.5zM450 300h700q21 0 35.5 -14.5t14.5 -35.5v-200 q0 -21 -14.5 -35.5t-35.5 -14.5h-700q-21 0 -35.5 14.5t-14.5 35.5v200q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe013;" d="M465 477l571 571q8 8 18 8t17 -8l177 -177q8 -7 8 -17t-8 -18l-783 -784q-7 -8 -17.5 -8t-17.5 8l-384 384q-8 8 -8 18t8 17l177 177q7 8 17 8t18 -8l171 -171q7 -7 18 -7t18 7z" />
-<glyph unicode="&#xe014;" d="M904 1083l178 -179q8 -8 8 -18.5t-8 -17.5l-267 -268l267 -268q8 -7 8 -17.5t-8 -18.5l-178 -178q-8 -8 -18.5 -8t-17.5 8l-268 267l-268 -267q-7 -8 -17.5 -8t-18.5 8l-178 178q-8 8 -8 18.5t8 17.5l267 268l-267 268q-8 7 -8 17.5t8 18.5l178 178q8 8 18.5 8t17.5 -8 l268 -267l268 268q7 7 17.5 7t18.5 -7z" />
-<glyph unicode="&#xe015;" d="M507 1177q98 0 187.5 -38.5t154.5 -103.5t103.5 -154.5t38.5 -187.5q0 -141 -78 -262l300 -299q8 -8 8 -18.5t-8 -18.5l-109 -108q-7 -8 -17.5 -8t-18.5 8l-300 299q-119 -77 -261 -77q-98 0 -188 38.5t-154.5 103t-103 154.5t-38.5 188t38.5 187.5t103 154.5 t154.5 103.5t188 38.5zM506.5 1023q-89.5 0 -165.5 -44t-120 -120.5t-44 -166t44 -165.5t120 -120t165.5 -44t166 44t120.5 120t44 165.5t-44 166t-120.5 120.5t-166 44zM425 900h150q10 0 17.5 -7.5t7.5 -17.5v-75h75q10 0 17.5 -7.5t7.5 -17.5v-150q0 -10 -7.5 -17.5 t-17.5 -7.5h-75v-75q0 -10 -7.5 -17.5t-17.5 -7.5h-150q-10 0 -17.5 7.5t-7.5 17.5v75h-75q-10 0 -17.5 7.5t-7.5 17.5v150q0 10 7.5 17.5t17.5 7.5h75v75q0 10 7.5 17.5t17.5 7.5z" />
-<glyph unicode="&#xe016;" d="M507 1177q98 0 187.5 -38.5t154.5 -103.5t103.5 -154.5t38.5 -187.5q0 -141 -78 -262l300 -299q8 -8 8 -18.5t-8 -18.5l-109 -108q-7 -8 -17.5 -8t-18.5 8l-300 299q-119 -77 -261 -77q-98 0 -188 38.5t-154.5 103t-103 154.5t-38.5 188t38.5 187.5t103 154.5 t154.5 103.5t188 38.5zM506.5 1023q-89.5 0 -165.5 -44t-120 -120.5t-44 -166t44 -165.5t120 -120t165.5 -44t166 44t120.5 120t44 165.5t-44 166t-120.5 120.5t-166 44zM325 800h350q10 0 17.5 -7.5t7.5 -17.5v-150q0 -10 -7.5 -17.5t-17.5 -7.5h-350q-10 0 -17.5 7.5 t-7.5 17.5v150q0 10 7.5 17.5t17.5 7.5z" />
-<glyph unicode="&#xe017;" d="M550 1200h100q21 0 35.5 -14.5t14.5 -35.5v-400q0 -21 -14.5 -35.5t-35.5 -14.5h-100q-21 0 -35.5 14.5t-14.5 35.5v400q0 21 14.5 35.5t35.5 14.5zM800 975v166q167 -62 272 -209.5t105 -331.5q0 -117 -45.5 -224t-123 -184.5t-184.5 -123t-224 -45.5t-224 45.5 t-184.5 123t-123 184.5t-45.5 224q0 184 105 331.5t272 209.5v-166q-103 -55 -165 -155t-62 -220q0 -116 57 -214.5t155.5 -155.5t214.5 -57t214.5 57t155.5 155.5t57 214.5q0 120 -62 220t-165 155z" />
-<glyph unicode="&#xe018;" d="M1025 1200h150q10 0 17.5 -7.5t7.5 -17.5v-1150q0 -10 -7.5 -17.5t-17.5 -7.5h-150q-10 0 -17.5 7.5t-7.5 17.5v1150q0 10 7.5 17.5t17.5 7.5zM725 800h150q10 0 17.5 -7.5t7.5 -17.5v-750q0 -10 -7.5 -17.5t-17.5 -7.5h-150q-10 0 -17.5 7.5t-7.5 17.5v750 q0 10 7.5 17.5t17.5 7.5zM425 500h150q10 0 17.5 -7.5t7.5 -17.5v-450q0 -10 -7.5 -17.5t-17.5 -7.5h-150q-10 0 -17.5 7.5t-7.5 17.5v450q0 10 7.5 17.5t17.5 7.5zM125 300h150q10 0 17.5 -7.5t7.5 -17.5v-250q0 -10 -7.5 -17.5t-17.5 -7.5h-150q-10 0 -17.5 7.5t-7.5 17.5 v250q0 10 7.5 17.5t17.5 7.5z" />
-<glyph unicode="&#xe019;" d="M600 1174q33 0 74 -5l38 -152l5 -1q49 -14 94 -39l5 -2l134 80q61 -48 104 -105l-80 -134l3 -5q25 -44 39 -93l1 -6l152 -38q5 -43 5 -73q0 -34 -5 -74l-152 -38l-1 -6q-15 -49 -39 -93l-3 -5l80 -134q-48 -61 -104 -105l-134 81l-5 -3q-44 -25 -94 -39l-5 -2l-38 -151 q-43 -5 -74 -5q-33 0 -74 5l-38 151l-5 2q-49 14 -94 39l-5 3l-134 -81q-60 48 -104 105l80 134l-3 5q-25 45 -38 93l-2 6l-151 38q-6 42 -6 74q0 33 6 73l151 38l2 6q13 48 38 93l3 5l-80 134q47 61 105 105l133 -80l5 2q45 25 94 39l5 1l38 152q43 5 74 5zM600 815 q-89 0 -152 -63t-63 -151.5t63 -151.5t152 -63t152 63t63 151.5t-63 151.5t-152 63z" />
-<glyph unicode="&#xe020;" d="M500 1300h300q41 0 70.5 -29.5t29.5 -70.5v-100h275q10 0 17.5 -7.5t7.5 -17.5v-75h-1100v75q0 10 7.5 17.5t17.5 7.5h275v100q0 41 29.5 70.5t70.5 29.5zM500 1200v-100h300v100h-300zM1100 900v-800q0 -41 -29.5 -70.5t-70.5 -29.5h-700q-41 0 -70.5 29.5t-29.5 70.5 v800h900zM300 800v-700h100v700h-100zM500 800v-700h100v700h-100zM700 800v-700h100v700h-100zM900 800v-700h100v700h-100z" />
-<glyph unicode="&#xe021;" d="M18 618l620 608q8 7 18.5 7t17.5 -7l608 -608q8 -8 5.5 -13t-12.5 -5h-175v-575q0 -10 -7.5 -17.5t-17.5 -7.5h-250q-10 0 -17.5 7.5t-7.5 17.5v375h-300v-375q0 -10 -7.5 -17.5t-17.5 -7.5h-250q-10 0 -17.5 7.5t-7.5 17.5v575h-175q-10 0 -12.5 5t5.5 13z" />
-<glyph unicode="&#xe022;" d="M600 1200v-400q0 -41 29.5 -70.5t70.5 -29.5h300v-650q0 -21 -14.5 -35.5t-35.5 -14.5h-800q-21 0 -35.5 14.5t-14.5 35.5v1100q0 21 14.5 35.5t35.5 14.5h450zM1000 800h-250q-21 0 -35.5 14.5t-14.5 35.5v250z" />
-<glyph unicode="&#xe023;" d="M600 1177q117 0 224 -45.5t184.5 -123t123 -184.5t45.5 -224t-45.5 -224t-123 -184.5t-184.5 -123t-224 -45.5t-224 45.5t-184.5 123t-123 184.5t-45.5 224t45.5 224t123 184.5t184.5 123t224 45.5zM600 1027q-116 0 -214.5 -57t-155.5 -155.5t-57 -214.5t57 -214.5 t155.5 -155.5t214.5 -57t214.5 57t155.5 155.5t57 214.5t-57 214.5t-155.5 155.5t-214.5 57zM525 900h50q10 0 17.5 -7.5t7.5 -17.5v-275h175q10 0 17.5 -7.5t7.5 -17.5v-50q0 -10 -7.5 -17.5t-17.5 -7.5h-250q-10 0 -17.5 7.5t-7.5 17.5v350q0 10 7.5 17.5t17.5 7.5z" />
-<glyph unicode="&#xe024;" d="M1300 0h-538l-41 400h-242l-41 -400h-538l431 1200h209l-21 -300h162l-20 300h208zM515 800l-27 -300h224l-27 300h-170z" />
-<glyph unicode="&#xe025;" d="M550 1200h200q21 0 35.5 -14.5t14.5 -35.5v-450h191q20 0 25.5 -11.5t-7.5 -27.5l-327 -400q-13 -16 -32 -16t-32 16l-327 400q-13 16 -7.5 27.5t25.5 11.5h191v450q0 21 14.5 35.5t35.5 14.5zM1125 400h50q10 0 17.5 -7.5t7.5 -17.5v-350q0 -10 -7.5 -17.5t-17.5 -7.5 h-1050q-10 0 -17.5 7.5t-7.5 17.5v350q0 10 7.5 17.5t17.5 7.5h50q10 0 17.5 -7.5t7.5 -17.5v-175h900v175q0 10 7.5 17.5t17.5 7.5z" />
-<glyph unicode="&#xe026;" d="M600 1177q117 0 224 -45.5t184.5 -123t123 -184.5t45.5 -224t-45.5 -224t-123 -184.5t-184.5 -123t-224 -45.5t-224 45.5t-184.5 123t-123 184.5t-45.5 224t45.5 224t123 184.5t184.5 123t224 45.5zM600 1027q-116 0 -214.5 -57t-155.5 -155.5t-57 -214.5t57 -214.5 t155.5 -155.5t214.5 -57t214.5 57t155.5 155.5t57 214.5t-57 214.5t-155.5 155.5t-214.5 57zM525 900h150q10 0 17.5 -7.5t7.5 -17.5v-275h137q21 0 26 -11.5t-8 -27.5l-223 -275q-13 -16 -32 -16t-32 16l-223 275q-13 16 -8 27.5t26 11.5h137v275q0 10 7.5 17.5t17.5 7.5z " />
-<glyph unicode="&#xe027;" d="M600 1177q117 0 224 -45.5t184.5 -123t123 -184.5t45.5 -224t-45.5 -224t-123 -184.5t-184.5 -123t-224 -45.5t-224 45.5t-184.5 123t-123 184.5t-45.5 224t45.5 224t123 184.5t184.5 123t224 45.5zM600 1027q-116 0 -214.5 -57t-155.5 -155.5t-57 -214.5t57 -214.5 t155.5 -155.5t214.5 -57t214.5 57t155.5 155.5t57 214.5t-57 214.5t-155.5 155.5t-214.5 57zM632 914l223 -275q13 -16 8 -27.5t-26 -11.5h-137v-275q0 -10 -7.5 -17.5t-17.5 -7.5h-150q-10 0 -17.5 7.5t-7.5 17.5v275h-137q-21 0 -26 11.5t8 27.5l223 275q13 16 32 16 t32 -16z" />
-<glyph unicode="&#xe028;" d="M225 1200h750q10 0 19.5 -7t12.5 -17l186 -652q7 -24 7 -49v-425q0 -12 -4 -27t-9 -17q-12 -6 -37 -6h-1100q-12 0 -27 4t-17 8q-6 13 -6 38l1 425q0 25 7 49l185 652q3 10 12.5 17t19.5 7zM878 1000h-556q-10 0 -19 -7t-11 -18l-87 -450q-2 -11 4 -18t16 -7h150 q10 0 19.5 -7t11.5 -17l38 -152q2 -10 11.5 -17t19.5 -7h250q10 0 19.5 7t11.5 17l38 152q2 10 11.5 17t19.5 7h150q10 0 16 7t4 18l-87 450q-2 11 -11 18t-19 7z" />
-<glyph unicode="&#xe029;" d="M600 1177q117 0 224 -45.5t184.5 -123t123 -184.5t45.5 -224t-45.5 -224t-123 -184.5t-184.5 -123t-224 -45.5t-224 45.5t-184.5 123t-123 184.5t-45.5 224t45.5 224t123 184.5t184.5 123t224 45.5zM600 1027q-116 0 -214.5 -57t-155.5 -155.5t-57 -214.5t57 -214.5 t155.5 -155.5t214.5 -57t214.5 57t155.5 155.5t57 214.5t-57 214.5t-155.5 155.5t-214.5 57zM540 820l253 -190q17 -12 17 -30t-17 -30l-253 -190q-16 -12 -28 -6.5t-12 26.5v400q0 21 12 26.5t28 -6.5z" />
-<glyph unicode="&#xe030;" d="M947 1060l135 135q7 7 12.5 5t5.5 -13v-362q0 -10 -7.5 -17.5t-17.5 -7.5h-362q-11 0 -13 5.5t5 12.5l133 133q-109 76 -238 76q-116 0 -214.5 -57t-155.5 -155.5t-57 -214.5t57 -214.5t155.5 -155.5t214.5 -57t214.5 57t155.5 155.5t57 214.5h150q0 -117 -45.5 -224 t-123 -184.5t-184.5 -123t-224 -45.5t-224 45.5t-184.5 123t-123 184.5t-45.5 224t45.5 224t123 184.5t184.5 123t224 45.5q192 0 347 -117z" />
-<glyph unicode="&#xe031;" d="M947 1060l135 135q7 7 12.5 5t5.5 -13v-361q0 -11 -7.5 -18.5t-18.5 -7.5h-361q-11 0 -13 5.5t5 12.5l134 134q-110 75 -239 75q-116 0 -214.5 -57t-155.5 -155.5t-57 -214.5h-150q0 117 45.5 224t123 184.5t184.5 123t224 45.5q192 0 347 -117zM1027 600h150 q0 -117 -45.5 -224t-123 -184.5t-184.5 -123t-224 -45.5q-192 0 -348 118l-134 -134q-7 -8 -12.5 -5.5t-5.5 12.5v360q0 11 7.5 18.5t18.5 7.5h360q10 0 12.5 -5.5t-5.5 -12.5l-133 -133q110 -76 240 -76q116 0 214.5 57t155.5 155.5t57 214.5z" />
-<glyph unicode="&#xe032;" d="M125 1200h1050q10 0 17.5 -7.5t7.5 -17.5v-1150q0 -10 -7.5 -17.5t-17.5 -7.5h-1050q-10 0 -17.5 7.5t-7.5 17.5v1150q0 10 7.5 17.5t17.5 7.5zM1075 1000h-850q-10 0 -17.5 -7.5t-7.5 -17.5v-850q0 -10 7.5 -17.5t17.5 -7.5h850q10 0 17.5 7.5t7.5 17.5v850 q0 10 -7.5 17.5t-17.5 7.5zM325 900h50q10 0 17.5 -7.5t7.5 -17.5v-50q0 -10 -7.5 -17.5t-17.5 -7.5h-50q-10 0 -17.5 7.5t-7.5 17.5v50q0 10 7.5 17.5t17.5 7.5zM525 900h450q10 0 17.5 -7.5t7.5 -17.5v-50q0 -10 -7.5 -17.5t-17.5 -7.5h-450q-10 0 -17.5 7.5t-7.5 17.5v50 q0 10 7.5 17.5t17.5 7.5zM325 700h50q10 0 17.5 -7.5t7.5 -17.5v-50q0 -10 -7.5 -17.5t-17.5 -7.5h-50q-10 0 -17.5 7.5t-7.5 17.5v50q0 10 7.5 17.5t17.5 7.5zM525 700h450q10 0 17.5 -7.5t7.5 -17.5v-50q0 -10 -7.5 -17.5t-17.5 -7.5h-450q-10 0 -17.5 7.5t-7.5 17.5v50 q0 10 7.5 17.5t17.5 7.5zM325 500h50q10 0 17.5 -7.5t7.5 -17.5v-50q0 -10 -7.5 -17.5t-17.5 -7.5h-50q-10 0 -17.5 7.5t-7.5 17.5v50q0 10 7.5 17.5t17.5 7.5zM525 500h450q10 0 17.5 -7.5t7.5 -17.5v-50q0 -10 -7.5 -17.5t-17.5 -7.5h-450q-10 0 -17.5 7.5t-7.5 17.5v50 q0 10 7.5 17.5t17.5 7.5zM325 300h50q10 0 17.5 -7.5t7.5 -17.5v-50q0 -10 -7.5 -17.5t-17.5 -7.5h-50q-10 0 -17.5 7.5t-7.5 17.5v50q0 10 7.5 17.5t17.5 7.5zM525 300h450q10 0 17.5 -7.5t7.5 -17.5v-50q0 -10 -7.5 -17.5t-17.5 -7.5h-450q-10 0 -17.5 7.5t-7.5 17.5v50 q0 10 7.5 17.5t17.5 7.5z" />
-<glyph unicode="&#xe033;" d="M900 800v200q0 83 -58.5 141.5t-141.5 58.5h-300q-82 0 -141 -59t-59 -141v-200h-100q-41 0 -70.5 -29.5t-29.5 -70.5v-600q0 -41 29.5 -70.5t70.5 -29.5h900q41 0 70.5 29.5t29.5 70.5v600q0 41 -29.5 70.5t-70.5 29.5h-100zM400 800v150q0 21 15 35.5t35 14.5h200 q20 0 35 -14.5t15 -35.5v-150h-300z" />
-<glyph unicode="&#xe034;" d="M125 1100h50q10 0 17.5 -7.5t7.5 -17.5v-1075h-100v1075q0 10 7.5 17.5t17.5 7.5zM1075 1052q4 0 9 -2q16 -6 16 -23v-421q0 -6 -3 -12q-33 -59 -66.5 -99t-65.5 -58t-56.5 -24.5t-52.5 -6.5q-26 0 -57.5 6.5t-52.5 13.5t-60 21q-41 15 -63 22.5t-57.5 15t-65.5 7.5 q-85 0 -160 -57q-7 -5 -15 -5q-6 0 -11 3q-14 7 -14 22v438q22 55 82 98.5t119 46.5q23 2 43 0.5t43 -7t32.5 -8.5t38 -13t32.5 -11q41 -14 63.5 -21t57 -14t63.5 -7q103 0 183 87q7 8 18 8z" />
-<glyph unicode="&#xe035;" d="M600 1175q116 0 227 -49.5t192.5 -131t131 -192.5t49.5 -227v-300q0 -10 -7.5 -17.5t-17.5 -7.5h-50q-10 0 -17.5 7.5t-7.5 17.5v300q0 127 -70.5 231.5t-184.5 161.5t-245 57t-245 -57t-184.5 -161.5t-70.5 -231.5v-300q0 -10 -7.5 -17.5t-17.5 -7.5h-50 q-10 0 -17.5 7.5t-7.5 17.5v300q0 116 49.5 227t131 192.5t192.5 131t227 49.5zM220 500h160q8 0 14 -6t6 -14v-460q0 -8 -6 -14t-14 -6h-160q-8 0 -14 6t-6 14v460q0 8 6 14t14 6zM820 500h160q8 0 14 -6t6 -14v-460q0 -8 -6 -14t-14 -6h-160q-8 0 -14 6t-6 14v460 q0 8 6 14t14 6z" />
-<glyph unicode="&#xe036;" d="M321 814l258 172q9 6 15 2.5t6 -13.5v-750q0 -10 -6 -13.5t-15 2.5l-258 172q-21 14 -46 14h-250q-10 0 -17.5 7.5t-7.5 17.5v350q0 10 7.5 17.5t17.5 7.5h250q25 0 46 14zM900 668l120 120q7 7 17 7t17 -7l34 -34q7 -7 7 -17t-7 -17l-120 -120l120 -120q7 -7 7 -17 t-7 -17l-34 -34q-7 -7 -17 -7t-17 7l-120 119l-120 -119q-7 -7 -17 -7t-17 7l-34 34q-7 7 -7 17t7 17l119 120l-119 120q-7 7 -7 17t7 17l34 34q7 8 17 8t17 -8z" />
-<glyph unicode="&#xe037;" d="M321 814l258 172q9 6 15 2.5t6 -13.5v-750q0 -10 -6 -13.5t-15 2.5l-258 172q-21 14 -46 14h-250q-10 0 -17.5 7.5t-7.5 17.5v350q0 10 7.5 17.5t17.5 7.5h250q25 0 46 14zM766 900h4q10 -1 16 -10q96 -129 96 -290q0 -154 -90 -281q-6 -9 -17 -10l-3 -1q-9 0 -16 6 l-29 23q-7 7 -8.5 16.5t4.5 17.5q72 103 72 229q0 132 -78 238q-6 8 -4.5 18t9.5 17l29 22q7 5 15 5z" />
-<glyph unicode="&#xe038;" d="M967 1004h3q11 -1 17 -10q135 -179 135 -396q0 -105 -34 -206.5t-98 -185.5q-7 -9 -17 -10h-3q-9 0 -16 6l-42 34q-8 6 -9 16t5 18q111 150 111 328q0 90 -29.5 176t-84.5 157q-6 9 -5 19t10 16l42 33q7 5 15 5zM321 814l258 172q9 6 15 2.5t6 -13.5v-750q0 -10 -6 -13.5 t-15 2.5l-258 172q-21 14 -46 14h-250q-10 0 -17.5 7.5t-7.5 17.5v350q0 10 7.5 17.5t17.5 7.5h250q25 0 46 14zM766 900h4q10 -1 16 -10q96 -129 96 -290q0 -154 -90 -281q-6 -9 -17 -10l-3 -1q-9 0 -16 6l-29 23q-7 7 -8.5 16.5t4.5 17.5q72 103 72 229q0 132 -78 238 q-6 8 -4.5 18.5t9.5 16.5l29 22q7 5 15 5z" />
-<glyph unicode="&#xe039;" d="M500 900h100v-100h-100v-100h-400v-100h-100v600h500v-300zM1200 700h-200v-100h200v-200h-300v300h-200v300h-100v200h600v-500zM100 1100v-300h300v300h-300zM800 1100v-300h300v300h-300zM300 900h-100v100h100v-100zM1000 900h-100v100h100v-100zM300 500h200v-500 h-500v500h200v100h100v-100zM800 300h200v-100h-100v-100h-200v100h-100v100h100v200h-200v100h300v-300zM100 400v-300h300v300h-300zM300 200h-100v100h100v-100zM1200 200h-100v100h100v-100zM700 0h-100v100h100v-100zM1200 0h-300v100h300v-100z" />
-<glyph unicode="&#xe040;" d="M100 200h-100v1000h100v-1000zM300 200h-100v1000h100v-1000zM700 200h-200v1000h200v-1000zM900 200h-100v1000h100v-1000zM1200 200h-200v1000h200v-1000zM400 0h-300v100h300v-100zM600 0h-100v91h100v-91zM800 0h-100v91h100v-91zM1100 0h-200v91h200v-91z" />
-<glyph unicode="&#xe041;" d="M500 1200l682 -682q8 -8 8 -18t-8 -18l-464 -464q-8 -8 -18 -8t-18 8l-682 682l1 475q0 10 7.5 17.5t17.5 7.5h474zM319.5 1024.5q-29.5 29.5 -71 29.5t-71 -29.5t-29.5 -71.5t29.5 -71.5t71 -29.5t71 29.5t29.5 71.5t-29.5 71.5z" />
-<glyph unicode="&#xe042;" d="M500 1200l682 -682q8 -8 8 -18t-8 -18l-464 -464q-8 -8 -18 -8t-18 8l-682 682l1 475q0 10 7.5 17.5t17.5 7.5h474zM800 1200l682 -682q8 -8 8 -18t-8 -18l-464 -464q-8 -8 -18 -8t-18 8l-56 56l424 426l-700 700h150zM319.5 1024.5q-29.5 29.5 -71 29.5t-71 -29.5 t-29.5 -71.5t29.5 -71.5t71 -29.5t71 29.5t29.5 71.5t-29.5 71.5z" />
-<glyph unicode="&#xe043;" d="M300 1200h825q75 0 75 -75v-900q0 -25 -18 -43l-64 -64q-8 -8 -13 -5.5t-5 12.5v950q0 10 -7.5 17.5t-17.5 7.5h-700q-25 0 -43 -18l-64 -64q-8 -8 -5.5 -13t12.5 -5h700q10 0 17.5 -7.5t7.5 -17.5v-950q0 -10 -7.5 -17.5t-17.5 -7.5h-850q-10 0 -17.5 7.5t-7.5 17.5v975 q0 25 18 43l139 139q18 18 43 18z" />
-<glyph unicode="&#xe044;" d="M250 1200h800q21 0 35.5 -14.5t14.5 -35.5v-1150l-450 444l-450 -445v1151q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe045;" d="M822 1200h-444q-11 0 -19 -7.5t-9 -17.5l-78 -301q-7 -24 7 -45l57 -108q6 -9 17.5 -15t21.5 -6h450q10 0 21.5 6t17.5 15l62 108q14 21 7 45l-83 301q-1 10 -9 17.5t-19 7.5zM1175 800h-150q-10 0 -21 -6.5t-15 -15.5l-78 -156q-4 -9 -15 -15.5t-21 -6.5h-550 q-10 0 -21 6.5t-15 15.5l-78 156q-4 9 -15 15.5t-21 6.5h-150q-10 0 -17.5 -7.5t-7.5 -17.5v-650q0 -10 7.5 -17.5t17.5 -7.5h150q10 0 17.5 7.5t7.5 17.5v150q0 10 7.5 17.5t17.5 7.5h750q10 0 17.5 -7.5t7.5 -17.5v-150q0 -10 7.5 -17.5t17.5 -7.5h150q10 0 17.5 7.5 t7.5 17.5v650q0 10 -7.5 17.5t-17.5 7.5zM850 200h-500q-10 0 -19.5 -7t-11.5 -17l-38 -152q-2 -10 3.5 -17t15.5 -7h600q10 0 15.5 7t3.5 17l-38 152q-2 10 -11.5 17t-19.5 7z" />
-<glyph unicode="&#xe046;" d="M500 1100h200q56 0 102.5 -20.5t72.5 -50t44 -59t25 -50.5l6 -20h150q41 0 70.5 -29.5t29.5 -70.5v-600q0 -41 -29.5 -70.5t-70.5 -29.5h-1000q-41 0 -70.5 29.5t-29.5 70.5v600q0 41 29.5 70.5t70.5 29.5h150q2 8 6.5 21.5t24 48t45 61t72 48t102.5 21.5zM900 800v-100 h100v100h-100zM600 730q-95 0 -162.5 -67.5t-67.5 -162.5t67.5 -162.5t162.5 -67.5t162.5 67.5t67.5 162.5t-67.5 162.5t-162.5 67.5zM600 603q43 0 73 -30t30 -73t-30 -73t-73 -30t-73 30t-30 73t30 73t73 30z" />
-<glyph unicode="&#xe047;" d="M681 1199l385 -998q20 -50 60 -92q18 -19 36.5 -29.5t27.5 -11.5l10 -2v-66h-417v66q53 0 75 43.5t5 88.5l-82 222h-391q-58 -145 -92 -234q-11 -34 -6.5 -57t25.5 -37t46 -20t55 -6v-66h-365v66q56 24 84 52q12 12 25 30.5t20 31.5l7 13l399 1006h93zM416 521h340 l-162 457z" />
-<glyph unicode="&#xe048;" d="M753 641q5 -1 14.5 -4.5t36 -15.5t50.5 -26.5t53.5 -40t50.5 -54.5t35.5 -70t14.5 -87q0 -67 -27.5 -125.5t-71.5 -97.5t-98.5 -66.5t-108.5 -40.5t-102 -13h-500v89q41 7 70.5 32.5t29.5 65.5v827q0 24 -0.5 34t-3.5 24t-8.5 19.5t-17 13.5t-28 12.5t-42.5 11.5v71 l471 -1q57 0 115.5 -20.5t108 -57t80.5 -94t31 -124.5q0 -51 -15.5 -96.5t-38 -74.5t-45 -50.5t-38.5 -30.5zM400 700h139q78 0 130.5 48.5t52.5 122.5q0 41 -8.5 70.5t-29.5 55.5t-62.5 39.5t-103.5 13.5h-118v-350zM400 200h216q80 0 121 50.5t41 130.5q0 90 -62.5 154.5 t-156.5 64.5h-159v-400z" />
-<glyph unicode="&#xe049;" d="M877 1200l2 -57q-83 -19 -116 -45.5t-40 -66.5l-132 -839q-9 -49 13 -69t96 -26v-97h-500v97q186 16 200 98l173 832q3 17 3 30t-1.5 22.5t-9 17.5t-13.5 12.5t-21.5 10t-26 8.5t-33.5 10q-13 3 -19 5v57h425z" />
-<glyph unicode="&#xe050;" d="M1300 900h-50q0 21 -4 37t-9.5 26.5t-18 17.5t-22 11t-28.5 5.5t-31 2t-37 0.5h-200v-850q0 -22 25 -34.5t50 -13.5l25 -2v-100h-400v100q4 0 11 0.5t24 3t30 7t24 15t11 24.5v850h-200q-25 0 -37 -0.5t-31 -2t-28.5 -5.5t-22 -11t-18 -17.5t-9.5 -26.5t-4 -37h-50v300 h1000v-300zM175 1000h-75v-800h75l-125 -167l-125 167h75v800h-75l125 167z" />
-<glyph unicode="&#xe051;" d="M1100 900h-50q0 21 -4 37t-9.5 26.5t-18 17.5t-22 11t-28.5 5.5t-31 2t-37 0.5h-200v-650q0 -22 25 -34.5t50 -13.5l25 -2v-100h-400v100q4 0 11 0.5t24 3t30 7t24 15t11 24.5v650h-200q-25 0 -37 -0.5t-31 -2t-28.5 -5.5t-22 -11t-18 -17.5t-9.5 -26.5t-4 -37h-50v300 h1000v-300zM1167 50l-167 -125v75h-800v-75l-167 125l167 125v-75h800v75z" />
-<glyph unicode="&#xe052;" d="M50 1100h600q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-600q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5zM50 800h1000q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-1000q-21 0 -35.5 14.5t-14.5 35.5v100 q0 21 14.5 35.5t35.5 14.5zM50 500h800q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-800q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5zM50 200h1100q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-1100 q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe053;" d="M250 1100h700q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-700q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5zM50 800h1100q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-1100q-21 0 -35.5 14.5t-14.5 35.5v100 q0 21 14.5 35.5t35.5 14.5zM250 500h700q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-700q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5zM50 200h1100q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-1100 q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe054;" d="M500 950v100q0 21 14.5 35.5t35.5 14.5h600q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-600q-21 0 -35.5 14.5t-14.5 35.5zM100 650v100q0 21 14.5 35.5t35.5 14.5h1000q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-1000 q-21 0 -35.5 14.5t-14.5 35.5zM300 350v100q0 21 14.5 35.5t35.5 14.5h800q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-800q-21 0 -35.5 14.5t-14.5 35.5zM0 50v100q0 21 14.5 35.5t35.5 14.5h1100q21 0 35.5 -14.5t14.5 -35.5v-100 q0 -21 -14.5 -35.5t-35.5 -14.5h-1100q-21 0 -35.5 14.5t-14.5 35.5z" />
-<glyph unicode="&#xe055;" d="M50 1100h1100q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-1100q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5zM50 800h1100q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-1100q-21 0 -35.5 14.5t-14.5 35.5v100 q0 21 14.5 35.5t35.5 14.5zM50 500h1100q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-1100q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5zM50 200h1100q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-1100 q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe056;" d="M50 1100h100q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-100q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5zM350 1100h800q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-800q-21 0 -35.5 14.5t-14.5 35.5v100 q0 21 14.5 35.5t35.5 14.5zM50 800h100q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-100q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5zM350 800h800q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-800 q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5zM50 500h100q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-100q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5zM350 500h800q21 0 35.5 -14.5t14.5 -35.5v-100 q0 -21 -14.5 -35.5t-35.5 -14.5h-800q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5zM50 200h100q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-100q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5zM350 200h800 q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-800q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe057;" d="M400 0h-100v1100h100v-1100zM550 1100h100q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-100q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5zM550 800h500q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-500 q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5zM267 550l-167 -125v75h-200v100h200v75zM550 500h300q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-300q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5zM550 200h600 q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-600q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe058;" d="M50 1100h100q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-100q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5zM900 0h-100v1100h100v-1100zM50 800h500q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-500 q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5zM1100 600h200v-100h-200v-75l-167 125l167 125v-75zM50 500h300q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-300q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5zM50 200h600 q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-600q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe059;" d="M75 1000h750q31 0 53 -22t22 -53v-650q0 -31 -22 -53t-53 -22h-750q-31 0 -53 22t-22 53v650q0 31 22 53t53 22zM1200 300l-300 300l300 300v-600z" />
-<glyph unicode="&#xe060;" d="M44 1100h1112q18 0 31 -13t13 -31v-1012q0 -18 -13 -31t-31 -13h-1112q-18 0 -31 13t-13 31v1012q0 18 13 31t31 13zM100 1000v-737l247 182l298 -131l-74 156l293 318l236 -288v500h-1000zM342 884q56 0 95 -39t39 -94.5t-39 -95t-95 -39.5t-95 39.5t-39 95t39 94.5 t95 39z" />
-<glyph unicode="&#xe062;" d="M648 1169q117 0 216 -60t156.5 -161t57.5 -218q0 -115 -70 -258q-69 -109 -158 -225.5t-143 -179.5l-54 -62q-9 8 -25.5 24.5t-63.5 67.5t-91 103t-98.5 128t-95.5 148q-60 132 -60 249q0 88 34 169.5t91.5 142t137 96.5t166.5 36zM652.5 974q-91.5 0 -156.5 -65 t-65 -157t65 -156.5t156.5 -64.5t156.5 64.5t65 156.5t-65 157t-156.5 65z" />
-<glyph unicode="&#xe063;" d="M600 1177q117 0 224 -45.5t184.5 -123t123 -184.5t45.5 -224t-45.5 -224t-123 -184.5t-184.5 -123t-224 -45.5t-224 45.5t-184.5 123t-123 184.5t-45.5 224t45.5 224t123 184.5t184.5 123t224 45.5zM600 173v854q-116 0 -214.5 -57t-155.5 -155.5t-57 -214.5t57 -214.5 t155.5 -155.5t214.5 -57z" />
-<glyph unicode="&#xe064;" d="M554 1295q21 -72 57.5 -143.5t76 -130t83 -118t82.5 -117t70 -116t49.5 -126t18.5 -136.5q0 -71 -25.5 -135t-68.5 -111t-99 -82t-118.5 -54t-125.5 -23q-84 5 -161.5 34t-139.5 78.5t-99 125t-37 164.5q0 69 18 136.5t49.5 126.5t69.5 116.5t81.5 117.5t83.5 119 t76.5 131t58.5 143zM344 710q-23 -33 -43.5 -70.5t-40.5 -102.5t-17 -123q1 -37 14.5 -69.5t30 -52t41 -37t38.5 -24.5t33 -15q21 -7 32 -1t13 22l6 34q2 10 -2.5 22t-13.5 19q-5 4 -14 12t-29.5 40.5t-32.5 73.5q-26 89 6 271q2 11 -6 11q-8 1 -15 -10z" />
-<glyph unicode="&#xe065;" d="M1000 1013l108 115q2 1 5 2t13 2t20.5 -1t25 -9.5t28.5 -21.5q22 -22 27 -43t0 -32l-6 -10l-108 -115zM350 1100h400q50 0 105 -13l-187 -187h-368q-41 0 -70.5 -29.5t-29.5 -70.5v-500q0 -41 29.5 -70.5t70.5 -29.5h500q41 0 70.5 29.5t29.5 70.5v182l200 200v-332 q0 -165 -93.5 -257.5t-256.5 -92.5h-400q-165 0 -257.5 92.5t-92.5 257.5v400q0 165 92.5 257.5t257.5 92.5zM1009 803l-362 -362l-161 -50l55 170l355 355z" />
-<glyph unicode="&#xe066;" d="M350 1100h361q-164 -146 -216 -200h-195q-41 0 -70.5 -29.5t-29.5 -70.5v-500q0 -41 29.5 -70.5t70.5 -29.5h500q41 0 70.5 29.5t29.5 70.5l200 153v-103q0 -165 -92.5 -257.5t-257.5 -92.5h-400q-165 0 -257.5 92.5t-92.5 257.5v400q0 165 92.5 257.5t257.5 92.5z M824 1073l339 -301q8 -7 8 -17.5t-8 -17.5l-340 -306q-7 -6 -12.5 -4t-6.5 11v203q-26 1 -54.5 0t-78.5 -7.5t-92 -17.5t-86 -35t-70 -57q10 59 33 108t51.5 81.5t65 58.5t68.5 40.5t67 24.5t56 13.5t40 4.5v210q1 10 6.5 12.5t13.5 -4.5z" />
-<glyph unicode="&#xe067;" d="M350 1100h350q60 0 127 -23l-178 -177h-349q-41 0 -70.5 -29.5t-29.5 -70.5v-500q0 -41 29.5 -70.5t70.5 -29.5h500q41 0 70.5 29.5t29.5 70.5v69l200 200v-219q0 -165 -92.5 -257.5t-257.5 -92.5h-400q-165 0 -257.5 92.5t-92.5 257.5v400q0 165 92.5 257.5t257.5 92.5z M643 639l395 395q7 7 17.5 7t17.5 -7l101 -101q7 -7 7 -17.5t-7 -17.5l-531 -532q-7 -7 -17.5 -7t-17.5 7l-248 248q-7 7 -7 17.5t7 17.5l101 101q7 7 17.5 7t17.5 -7l111 -111q8 -7 18 -7t18 7z" />
-<glyph unicode="&#xe068;" d="M318 918l264 264q8 8 18 8t18 -8l260 -264q7 -8 4.5 -13t-12.5 -5h-170v-200h200v173q0 10 5 12t13 -5l264 -260q8 -7 8 -17.5t-8 -17.5l-264 -265q-8 -7 -13 -5t-5 12v173h-200v-200h170q10 0 12.5 -5t-4.5 -13l-260 -264q-8 -8 -18 -8t-18 8l-264 264q-8 8 -5.5 13 t12.5 5h175v200h-200v-173q0 -10 -5 -12t-13 5l-264 265q-8 7 -8 17.5t8 17.5l264 260q8 7 13 5t5 -12v-173h200v200h-175q-10 0 -12.5 5t5.5 13z" />
-<glyph unicode="&#xe069;" d="M250 1100h100q21 0 35.5 -14.5t14.5 -35.5v-438l464 453q15 14 25.5 10t10.5 -25v-1000q0 -21 -10.5 -25t-25.5 10l-464 453v-438q0 -21 -14.5 -35.5t-35.5 -14.5h-100q-21 0 -35.5 14.5t-14.5 35.5v1000q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe070;" d="M50 1100h100q21 0 35.5 -14.5t14.5 -35.5v-438l464 453q15 14 25.5 10t10.5 -25v-438l464 453q15 14 25.5 10t10.5 -25v-1000q0 -21 -10.5 -25t-25.5 10l-464 453v-438q0 -21 -10.5 -25t-25.5 10l-464 453v-438q0 -21 -14.5 -35.5t-35.5 -14.5h-100q-21 0 -35.5 14.5 t-14.5 35.5v1000q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe071;" d="M1200 1050v-1000q0 -21 -10.5 -25t-25.5 10l-464 453v-438q0 -21 -10.5 -25t-25.5 10l-492 480q-15 14 -15 35t15 35l492 480q15 14 25.5 10t10.5 -25v-438l464 453q15 14 25.5 10t10.5 -25z" />
-<glyph unicode="&#xe072;" d="M243 1074l814 -498q18 -11 18 -26t-18 -26l-814 -498q-18 -11 -30.5 -4t-12.5 28v1000q0 21 12.5 28t30.5 -4z" />
-<glyph unicode="&#xe073;" d="M250 1000h200q21 0 35.5 -14.5t14.5 -35.5v-800q0 -21 -14.5 -35.5t-35.5 -14.5h-200q-21 0 -35.5 14.5t-14.5 35.5v800q0 21 14.5 35.5t35.5 14.5zM650 1000h200q21 0 35.5 -14.5t14.5 -35.5v-800q0 -21 -14.5 -35.5t-35.5 -14.5h-200q-21 0 -35.5 14.5t-14.5 35.5v800 q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe074;" d="M1100 950v-800q0 -21 -14.5 -35.5t-35.5 -14.5h-800q-21 0 -35.5 14.5t-14.5 35.5v800q0 21 14.5 35.5t35.5 14.5h800q21 0 35.5 -14.5t14.5 -35.5z" />
-<glyph unicode="&#xe075;" d="M500 612v438q0 21 10.5 25t25.5 -10l492 -480q15 -14 15 -35t-15 -35l-492 -480q-15 -14 -25.5 -10t-10.5 25v438l-464 -453q-15 -14 -25.5 -10t-10.5 25v1000q0 21 10.5 25t25.5 -10z" />
-<glyph unicode="&#xe076;" d="M1048 1102l100 1q20 0 35 -14.5t15 -35.5l5 -1000q0 -21 -14.5 -35.5t-35.5 -14.5l-100 -1q-21 0 -35.5 14.5t-14.5 35.5l-2 437l-463 -454q-14 -15 -24.5 -10.5t-10.5 25.5l-2 437l-462 -455q-15 -14 -25.5 -9.5t-10.5 24.5l-5 1000q0 21 10.5 25.5t25.5 -10.5l466 -450 l-2 438q0 20 10.5 24.5t25.5 -9.5l466 -451l-2 438q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe077;" d="M850 1100h100q21 0 35.5 -14.5t14.5 -35.5v-1000q0 -21 -14.5 -35.5t-35.5 -14.5h-100q-21 0 -35.5 14.5t-14.5 35.5v438l-464 -453q-15 -14 -25.5 -10t-10.5 25v1000q0 21 10.5 25t25.5 -10l464 -453v438q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe078;" d="M686 1081l501 -540q15 -15 10.5 -26t-26.5 -11h-1042q-22 0 -26.5 11t10.5 26l501 540q15 15 36 15t36 -15zM150 400h1000q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-1000q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe079;" d="M885 900l-352 -353l352 -353l-197 -198l-552 552l552 550z" />
-<glyph unicode="&#xe080;" d="M1064 547l-551 -551l-198 198l353 353l-353 353l198 198z" />
-<glyph unicode="&#xe081;" d="M600 1177q117 0 224 -45.5t184.5 -123t123 -184.5t45.5 -224t-45.5 -224t-123 -184.5t-184.5 -123t-224 -45.5t-224 45.5t-184.5 123t-123 184.5t-45.5 224t45.5 224t123 184.5t184.5 123t224 45.5zM650 900h-100q-21 0 -35.5 -14.5t-14.5 -35.5v-150h-150 q-21 0 -35.5 -14.5t-14.5 -35.5v-100q0 -21 14.5 -35.5t35.5 -14.5h150v-150q0 -21 14.5 -35.5t35.5 -14.5h100q21 0 35.5 14.5t14.5 35.5v150h150q21 0 35.5 14.5t14.5 35.5v100q0 21 -14.5 35.5t-35.5 14.5h-150v150q0 21 -14.5 35.5t-35.5 14.5z" />
-<glyph unicode="&#xe082;" d="M600 1177q117 0 224 -45.5t184.5 -123t123 -184.5t45.5 -224t-45.5 -224t-123 -184.5t-184.5 -123t-224 -45.5t-224 45.5t-184.5 123t-123 184.5t-45.5 224t45.5 224t123 184.5t184.5 123t224 45.5zM850 700h-500q-21 0 -35.5 -14.5t-14.5 -35.5v-100q0 -21 14.5 -35.5 t35.5 -14.5h500q21 0 35.5 14.5t14.5 35.5v100q0 21 -14.5 35.5t-35.5 14.5z" />
-<glyph unicode="&#xe083;" d="M600 1177q117 0 224 -45.5t184.5 -123t123 -184.5t45.5 -224t-45.5 -224t-123 -184.5t-184.5 -123t-224 -45.5t-224 45.5t-184.5 123t-123 184.5t-45.5 224t45.5 224t123 184.5t184.5 123t224 45.5zM741.5 913q-12.5 0 -21.5 -9l-120 -120l-120 120q-9 9 -21.5 9 t-21.5 -9l-141 -141q-9 -9 -9 -21.5t9 -21.5l120 -120l-120 -120q-9 -9 -9 -21.5t9 -21.5l141 -141q9 -9 21.5 -9t21.5 9l120 120l120 -120q9 -9 21.5 -9t21.5 9l141 141q9 9 9 21.5t-9 21.5l-120 120l120 120q9 9 9 21.5t-9 21.5l-141 141q-9 9 -21.5 9z" />
-<glyph unicode="&#xe084;" d="M600 1177q117 0 224 -45.5t184.5 -123t123 -184.5t45.5 -224t-45.5 -224t-123 -184.5t-184.5 -123t-224 -45.5t-224 45.5t-184.5 123t-123 184.5t-45.5 224t45.5 224t123 184.5t184.5 123t224 45.5zM546 623l-84 85q-7 7 -17.5 7t-18.5 -7l-139 -139q-7 -8 -7 -18t7 -18 l242 -241q7 -8 17.5 -8t17.5 8l375 375q7 7 7 17.5t-7 18.5l-139 139q-7 7 -17.5 7t-17.5 -7z" />
-<glyph unicode="&#xe085;" d="M600 1177q117 0 224 -45.5t184.5 -123t123 -184.5t45.5 -224t-45.5 -224t-123 -184.5t-184.5 -123t-224 -45.5t-224 45.5t-184.5 123t-123 184.5t-45.5 224t45.5 224t123 184.5t184.5 123t224 45.5zM588 941q-29 0 -59 -5.5t-63 -20.5t-58 -38.5t-41.5 -63t-16.5 -89.5 q0 -25 20 -25h131q30 -5 35 11q6 20 20.5 28t45.5 8q20 0 31.5 -10.5t11.5 -28.5q0 -23 -7 -34t-26 -18q-1 0 -13.5 -4t-19.5 -7.5t-20 -10.5t-22 -17t-18.5 -24t-15.5 -35t-8 -46q-1 -8 5.5 -16.5t20.5 -8.5h173q7 0 22 8t35 28t37.5 48t29.5 74t12 100q0 47 -17 83 t-42.5 57t-59.5 34.5t-64 18t-59 4.5zM675 400h-150q-10 0 -17.5 -7.5t-7.5 -17.5v-150q0 -10 7.5 -17.5t17.5 -7.5h150q10 0 17.5 7.5t7.5 17.5v150q0 10 -7.5 17.5t-17.5 7.5z" />
-<glyph unicode="&#xe086;" d="M600 1177q117 0 224 -45.5t184.5 -123t123 -184.5t45.5 -224t-45.5 -224t-123 -184.5t-184.5 -123t-224 -45.5t-224 45.5t-184.5 123t-123 184.5t-45.5 224t45.5 224t123 184.5t184.5 123t224 45.5zM675 1000h-150q-10 0 -17.5 -7.5t-7.5 -17.5v-150q0 -10 7.5 -17.5 t17.5 -7.5h150q10 0 17.5 7.5t7.5 17.5v150q0 10 -7.5 17.5t-17.5 7.5zM675 700h-250q-10 0 -17.5 -7.5t-7.5 -17.5v-50q0 -10 7.5 -17.5t17.5 -7.5h75v-200h-75q-10 0 -17.5 -7.5t-7.5 -17.5v-50q0 -10 7.5 -17.5t17.5 -7.5h350q10 0 17.5 7.5t7.5 17.5v50q0 10 -7.5 17.5 t-17.5 7.5h-75v275q0 10 -7.5 17.5t-17.5 7.5z" />
-<glyph unicode="&#xe087;" d="M525 1200h150q10 0 17.5 -7.5t7.5 -17.5v-194q103 -27 178.5 -102.5t102.5 -178.5h194q10 0 17.5 -7.5t7.5 -17.5v-150q0 -10 -7.5 -17.5t-17.5 -7.5h-194q-27 -103 -102.5 -178.5t-178.5 -102.5v-194q0 -10 -7.5 -17.5t-17.5 -7.5h-150q-10 0 -17.5 7.5t-7.5 17.5v194 q-103 27 -178.5 102.5t-102.5 178.5h-194q-10 0 -17.5 7.5t-7.5 17.5v150q0 10 7.5 17.5t17.5 7.5h194q27 103 102.5 178.5t178.5 102.5v194q0 10 7.5 17.5t17.5 7.5zM700 893v-168q0 -10 -7.5 -17.5t-17.5 -7.5h-150q-10 0 -17.5 7.5t-7.5 17.5v168q-68 -23 -119 -74 t-74 -119h168q10 0 17.5 -7.5t7.5 -17.5v-150q0 -10 -7.5 -17.5t-17.5 -7.5h-168q23 -68 74 -119t119 -74v168q0 10 7.5 17.5t17.5 7.5h150q10 0 17.5 -7.5t7.5 -17.5v-168q68 23 119 74t74 119h-168q-10 0 -17.5 7.5t-7.5 17.5v150q0 10 7.5 17.5t17.5 7.5h168 q-23 68 -74 119t-119 74z" />
-<glyph unicode="&#xe088;" d="M600 1177q117 0 224 -45.5t184.5 -123t123 -184.5t45.5 -224t-45.5 -224t-123 -184.5t-184.5 -123t-224 -45.5t-224 45.5t-184.5 123t-123 184.5t-45.5 224t45.5 224t123 184.5t184.5 123t224 45.5zM600 1027q-116 0 -214.5 -57t-155.5 -155.5t-57 -214.5t57 -214.5 t155.5 -155.5t214.5 -57t214.5 57t155.5 155.5t57 214.5t-57 214.5t-155.5 155.5t-214.5 57zM759 823l64 -64q7 -7 7 -17.5t-7 -17.5l-124 -124l124 -124q7 -7 7 -17.5t-7 -17.5l-64 -64q-7 -7 -17.5 -7t-17.5 7l-124 124l-124 -124q-7 -7 -17.5 -7t-17.5 7l-64 64 q-7 7 -7 17.5t7 17.5l124 124l-124 124q-7 7 -7 17.5t7 17.5l64 64q7 7 17.5 7t17.5 -7l124 -124l124 124q7 7 17.5 7t17.5 -7z" />
-<glyph unicode="&#xe089;" d="M600 1177q117 0 224 -45.5t184.5 -123t123 -184.5t45.5 -224t-45.5 -224t-123 -184.5t-184.5 -123t-224 -45.5t-224 45.5t-184.5 123t-123 184.5t-45.5 224t45.5 224t123 184.5t184.5 123t224 45.5zM600 1027q-116 0 -214.5 -57t-155.5 -155.5t-57 -214.5t57 -214.5 t155.5 -155.5t214.5 -57t214.5 57t155.5 155.5t57 214.5t-57 214.5t-155.5 155.5t-214.5 57zM782 788l106 -106q7 -7 7 -17.5t-7 -17.5l-320 -321q-8 -7 -18 -7t-18 7l-202 203q-8 7 -8 17.5t8 17.5l106 106q7 8 17.5 8t17.5 -8l79 -79l197 197q7 7 17.5 7t17.5 -7z" />
-<glyph unicode="&#xe090;" d="M600 1177q117 0 224 -45.5t184.5 -123t123 -184.5t45.5 -224t-45.5 -224t-123 -184.5t-184.5 -123t-224 -45.5t-224 45.5t-184.5 123t-123 184.5t-45.5 224t45.5 224t123 184.5t184.5 123t224 45.5zM600 1027q-116 0 -214.5 -57t-155.5 -155.5t-57 -214.5q0 -120 65 -225 l587 587q-105 65 -225 65zM965 819l-584 -584q104 -62 219 -62q116 0 214.5 57t155.5 155.5t57 214.5q0 115 -62 219z" />
-<glyph unicode="&#xe091;" d="M39 582l522 427q16 13 27.5 8t11.5 -26v-291h550q21 0 35.5 -14.5t14.5 -35.5v-200q0 -21 -14.5 -35.5t-35.5 -14.5h-550v-291q0 -21 -11.5 -26t-27.5 8l-522 427q-16 13 -16 32t16 32z" />
-<glyph unicode="&#xe092;" d="M639 1009l522 -427q16 -13 16 -32t-16 -32l-522 -427q-16 -13 -27.5 -8t-11.5 26v291h-550q-21 0 -35.5 14.5t-14.5 35.5v200q0 21 14.5 35.5t35.5 14.5h550v291q0 21 11.5 26t27.5 -8z" />
-<glyph unicode="&#xe093;" d="M682 1161l427 -522q13 -16 8 -27.5t-26 -11.5h-291v-550q0 -21 -14.5 -35.5t-35.5 -14.5h-200q-21 0 -35.5 14.5t-14.5 35.5v550h-291q-21 0 -26 11.5t8 27.5l427 522q13 16 32 16t32 -16z" />
-<glyph unicode="&#xe094;" d="M550 1200h200q21 0 35.5 -14.5t14.5 -35.5v-550h291q21 0 26 -11.5t-8 -27.5l-427 -522q-13 -16 -32 -16t-32 16l-427 522q-13 16 -8 27.5t26 11.5h291v550q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe095;" d="M639 1109l522 -427q16 -13 16 -32t-16 -32l-522 -427q-16 -13 -27.5 -8t-11.5 26v291q-94 -2 -182 -20t-170.5 -52t-147 -92.5t-100.5 -135.5q5 105 27 193.5t67.5 167t113 135t167 91.5t225.5 42v262q0 21 11.5 26t27.5 -8z" />
-<glyph unicode="&#xe096;" d="M850 1200h300q21 0 35.5 -14.5t14.5 -35.5v-300q0 -21 -10.5 -25t-24.5 10l-94 94l-249 -249q-8 -7 -18 -7t-18 7l-106 106q-7 8 -7 18t7 18l249 249l-94 94q-14 14 -10 24.5t25 10.5zM350 0h-300q-21 0 -35.5 14.5t-14.5 35.5v300q0 21 10.5 25t24.5 -10l94 -94l249 249 q8 7 18 7t18 -7l106 -106q7 -8 7 -18t-7 -18l-249 -249l94 -94q14 -14 10 -24.5t-25 -10.5z" />
-<glyph unicode="&#xe097;" d="M1014 1120l106 -106q7 -8 7 -18t-7 -18l-249 -249l94 -94q14 -14 10 -24.5t-25 -10.5h-300q-21 0 -35.5 14.5t-14.5 35.5v300q0 21 10.5 25t24.5 -10l94 -94l249 249q8 7 18 7t18 -7zM250 600h300q21 0 35.5 -14.5t14.5 -35.5v-300q0 -21 -10.5 -25t-24.5 10l-94 94 l-249 -249q-8 -7 -18 -7t-18 7l-106 106q-7 8 -7 18t7 18l249 249l-94 94q-14 14 -10 24.5t25 10.5z" />
-<glyph unicode="&#xe101;" d="M600 1177q117 0 224 -45.5t184.5 -123t123 -184.5t45.5 -224t-45.5 -224t-123 -184.5t-184.5 -123t-224 -45.5t-224 45.5t-184.5 123t-123 184.5t-45.5 224t45.5 224t123 184.5t184.5 123t224 45.5zM704 900h-208q-20 0 -32 -14.5t-8 -34.5l58 -302q4 -20 21.5 -34.5 t37.5 -14.5h54q20 0 37.5 14.5t21.5 34.5l58 302q4 20 -8 34.5t-32 14.5zM675 400h-150q-10 0 -17.5 -7.5t-7.5 -17.5v-150q0 -10 7.5 -17.5t17.5 -7.5h150q10 0 17.5 7.5t7.5 17.5v150q0 10 -7.5 17.5t-17.5 7.5z" />
-<glyph unicode="&#xe102;" d="M260 1200q9 0 19 -2t15 -4l5 -2q22 -10 44 -23l196 -118q21 -13 36 -24q29 -21 37 -12q11 13 49 35l196 118q22 13 45 23q17 7 38 7q23 0 47 -16.5t37 -33.5l13 -16q14 -21 18 -45l25 -123l8 -44q1 -9 8.5 -14.5t17.5 -5.5h61q10 0 17.5 -7.5t7.5 -17.5v-50 q0 -10 -7.5 -17.5t-17.5 -7.5h-50q-10 0 -17.5 -7.5t-7.5 -17.5v-175h-400v300h-200v-300h-400v175q0 10 -7.5 17.5t-17.5 7.5h-50q-10 0 -17.5 7.5t-7.5 17.5v50q0 10 7.5 17.5t17.5 7.5h61q11 0 18 3t7 8q0 4 9 52l25 128q5 25 19 45q2 3 5 7t13.5 15t21.5 19.5t26.5 15.5 t29.5 7zM915 1079l-166 -162q-7 -7 -5 -12t12 -5h219q10 0 15 7t2 17l-51 149q-3 10 -11 12t-15 -6zM463 917l-177 157q-8 7 -16 5t-11 -12l-51 -143q-3 -10 2 -17t15 -7h231q11 0 12.5 5t-5.5 12zM500 0h-375q-10 0 -17.5 7.5t-7.5 17.5v375h400v-400zM1100 400v-375 q0 -10 -7.5 -17.5t-17.5 -7.5h-375v400h400z" />
-<glyph unicode="&#xe103;" d="M1165 1190q8 3 21 -6.5t13 -17.5q-2 -178 -24.5 -323.5t-55.5 -245.5t-87 -174.5t-102.5 -118.5t-118 -68.5t-118.5 -33t-120 -4.5t-105 9.5t-90 16.5q-61 12 -78 11q-4 1 -12.5 0t-34 -14.5t-52.5 -40.5l-153 -153q-26 -24 -37 -14.5t-11 43.5q0 64 42 102q8 8 50.5 45 t66.5 58q19 17 35 47t13 61q-9 55 -10 102.5t7 111t37 130t78 129.5q39 51 80 88t89.5 63.5t94.5 45t113.5 36t129 31t157.5 37t182 47.5zM1116 1098q-8 9 -22.5 -3t-45.5 -50q-38 -47 -119 -103.5t-142 -89.5l-62 -33q-56 -30 -102 -57t-104 -68t-102.5 -80.5t-85.5 -91 t-64 -104.5q-24 -56 -31 -86t2 -32t31.5 17.5t55.5 59.5q25 30 94 75.5t125.5 77.5t147.5 81q70 37 118.5 69t102 79.5t99 111t86.5 148.5q22 50 24 60t-6 19z" />
-<glyph unicode="&#xe104;" d="M653 1231q-39 -67 -54.5 -131t-10.5 -114.5t24.5 -96.5t47.5 -80t63.5 -62.5t68.5 -46.5t65 -30q-4 7 -17.5 35t-18.5 39.5t-17 39.5t-17 43t-13 42t-9.5 44.5t-2 42t4 43t13.5 39t23 38.5q96 -42 165 -107.5t105 -138t52 -156t13 -159t-19 -149.5q-13 -55 -44 -106.5 t-68 -87t-78.5 -64.5t-72.5 -45t-53 -22q-72 -22 -127 -11q-31 6 -13 19q6 3 17 7q13 5 32.5 21t41 44t38.5 63.5t21.5 81.5t-6.5 94.5t-50 107t-104 115.5q10 -104 -0.5 -189t-37 -140.5t-65 -93t-84 -52t-93.5 -11t-95 24.5q-80 36 -131.5 114t-53.5 171q-2 23 0 49.5 t4.5 52.5t13.5 56t27.5 60t46 64.5t69.5 68.5q-8 -53 -5 -102.5t17.5 -90t34 -68.5t44.5 -39t49 -2q31 13 38.5 36t-4.5 55t-29 64.5t-36 75t-26 75.5q-15 85 2 161.5t53.5 128.5t85.5 92.5t93.5 61t81.5 25.5z" />
-<glyph unicode="&#xe105;" d="M600 1094q82 0 160.5 -22.5t140 -59t116.5 -82.5t94.5 -95t68 -95t42.5 -82.5t14 -57.5t-14 -57.5t-43 -82.5t-68.5 -95t-94.5 -95t-116.5 -82.5t-140 -59t-159.5 -22.5t-159.5 22.5t-140 59t-116.5 82.5t-94.5 95t-68.5 95t-43 82.5t-14 57.5t14 57.5t42.5 82.5t68 95 t94.5 95t116.5 82.5t140 59t160.5 22.5zM888 829q-15 15 -18 12t5 -22q25 -57 25 -119q0 -124 -88 -212t-212 -88t-212 88t-88 212q0 59 23 114q8 19 4.5 22t-17.5 -12q-70 -69 -160 -184q-13 -16 -15 -40.5t9 -42.5q22 -36 47 -71t70 -82t92.5 -81t113 -58.5t133.5 -24.5 t133.5 24t113 58.5t92.5 81.5t70 81.5t47 70.5q11 18 9 42.5t-14 41.5q-90 117 -163 189zM448 727l-35 -36q-15 -15 -19.5 -38.5t4.5 -41.5q37 -68 93 -116q16 -13 38.5 -11t36.5 17l35 34q14 15 12.5 33.5t-16.5 33.5q-44 44 -89 117q-11 18 -28 20t-32 -12z" />
-<glyph unicode="&#xe106;" d="M592 0h-148l31 120q-91 20 -175.5 68.5t-143.5 106.5t-103.5 119t-66.5 110t-22 76q0 21 14 57.5t42.5 82.5t68 95t94.5 95t116.5 82.5t140 59t160.5 22.5q61 0 126 -15l32 121h148zM944 770l47 181q108 -85 176.5 -192t68.5 -159q0 -26 -19.5 -71t-59.5 -102t-93 -112 t-129 -104.5t-158 -75.5l46 173q77 49 136 117t97 131q11 18 9 42.5t-14 41.5q-54 70 -107 130zM310 824q-70 -69 -160 -184q-13 -16 -15 -40.5t9 -42.5q18 -30 39 -60t57 -70.5t74 -73t90 -61t105 -41.5l41 154q-107 18 -178.5 101.5t-71.5 193.5q0 59 23 114q8 19 4.5 22 t-17.5 -12zM448 727l-35 -36q-15 -15 -19.5 -38.5t4.5 -41.5q37 -68 93 -116q16 -13 38.5 -11t36.5 17l12 11l22 86l-3 4q-44 44 -89 117q-11 18 -28 20t-32 -12z" />
-<glyph unicode="&#xe107;" d="M-90 100l642 1066q20 31 48 28.5t48 -35.5l642 -1056q21 -32 7.5 -67.5t-50.5 -35.5h-1294q-37 0 -50.5 34t7.5 66zM155 200h345v75q0 10 7.5 17.5t17.5 7.5h150q10 0 17.5 -7.5t7.5 -17.5v-75h345l-445 723zM496 700h208q20 0 32 -14.5t8 -34.5l-58 -252 q-4 -20 -21.5 -34.5t-37.5 -14.5h-54q-20 0 -37.5 14.5t-21.5 34.5l-58 252q-4 20 8 34.5t32 14.5z" />
-<glyph unicode="&#xe108;" d="M650 1200q62 0 106 -44t44 -106v-339l363 -325q15 -14 26 -38.5t11 -44.5v-41q0 -20 -12 -26.5t-29 5.5l-359 249v-263q100 -93 100 -113v-64q0 -21 -13 -29t-32 1l-205 128l-205 -128q-19 -9 -32 -1t-13 29v64q0 20 100 113v263l-359 -249q-17 -12 -29 -5.5t-12 26.5v41 q0 20 11 44.5t26 38.5l363 325v339q0 62 44 106t106 44z" />
-<glyph unicode="&#xe109;" d="M850 1200h100q21 0 35.5 -14.5t14.5 -35.5v-50h50q21 0 35.5 -14.5t14.5 -35.5v-150h-1100v150q0 21 14.5 35.5t35.5 14.5h50v50q0 21 14.5 35.5t35.5 14.5h100q21 0 35.5 -14.5t14.5 -35.5v-50h500v50q0 21 14.5 35.5t35.5 14.5zM1100 800v-750q0 -21 -14.5 -35.5 t-35.5 -14.5h-1000q-21 0 -35.5 14.5t-14.5 35.5v750h1100zM100 600v-100h100v100h-100zM300 600v-100h100v100h-100zM500 600v-100h100v100h-100zM700 600v-100h100v100h-100zM900 600v-100h100v100h-100zM100 400v-100h100v100h-100zM300 400v-100h100v100h-100zM500 400 v-100h100v100h-100zM700 400v-100h100v100h-100zM900 400v-100h100v100h-100zM100 200v-100h100v100h-100zM300 200v-100h100v100h-100zM500 200v-100h100v100h-100zM700 200v-100h100v100h-100zM900 200v-100h100v100h-100z" />
-<glyph unicode="&#xe110;" d="M1135 1165l249 -230q15 -14 15 -35t-15 -35l-249 -230q-14 -14 -24.5 -10t-10.5 25v150h-159l-600 -600h-291q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5h209l600 600h241v150q0 21 10.5 25t24.5 -10zM522 819l-141 -141l-122 122h-209q-21 0 -35.5 14.5 t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5h291zM1135 565l249 -230q15 -14 15 -35t-15 -35l-249 -230q-14 -14 -24.5 -10t-10.5 25v150h-241l-181 181l141 141l122 -122h159v150q0 21 10.5 25t24.5 -10z" />
-<glyph unicode="&#xe111;" d="M100 1100h1000q41 0 70.5 -29.5t29.5 -70.5v-600q0 -41 -29.5 -70.5t-70.5 -29.5h-596l-304 -300v300h-100q-41 0 -70.5 29.5t-29.5 70.5v600q0 41 29.5 70.5t70.5 29.5z" />
-<glyph unicode="&#xe112;" d="M150 1200h200q21 0 35.5 -14.5t14.5 -35.5v-250h-300v250q0 21 14.5 35.5t35.5 14.5zM850 1200h200q21 0 35.5 -14.5t14.5 -35.5v-250h-300v250q0 21 14.5 35.5t35.5 14.5zM1100 800v-300q0 -41 -3 -77.5t-15 -89.5t-32 -96t-58 -89t-89 -77t-129 -51t-174 -20t-174 20 t-129 51t-89 77t-58 89t-32 96t-15 89.5t-3 77.5v300h300v-250v-27v-42.5t1.5 -41t5 -38t10 -35t16.5 -30t25.5 -24.5t35 -19t46.5 -12t60 -4t60 4.5t46.5 12.5t35 19.5t25 25.5t17 30.5t10 35t5 38t2 40.5t-0.5 42v25v250h300z" />
-<glyph unicode="&#xe113;" d="M1100 411l-198 -199l-353 353l-353 -353l-197 199l551 551z" />
-<glyph unicode="&#xe114;" d="M1101 789l-550 -551l-551 551l198 199l353 -353l353 353z" />
-<glyph unicode="&#xe115;" d="M404 1000h746q21 0 35.5 -14.5t14.5 -35.5v-551h150q21 0 25 -10.5t-10 -24.5l-230 -249q-14 -15 -35 -15t-35 15l-230 249q-14 14 -10 24.5t25 10.5h150v401h-381zM135 984l230 -249q14 -14 10 -24.5t-25 -10.5h-150v-400h385l215 -200h-750q-21 0 -35.5 14.5 t-14.5 35.5v550h-150q-21 0 -25 10.5t10 24.5l230 249q14 15 35 15t35 -15z" />
-<glyph unicode="&#xe116;" d="M56 1200h94q17 0 31 -11t18 -27l38 -162h896q24 0 39 -18.5t10 -42.5l-100 -475q-5 -21 -27 -42.5t-55 -21.5h-633l48 -200h535q21 0 35.5 -14.5t14.5 -35.5t-14.5 -35.5t-35.5 -14.5h-50v-50q0 -21 -14.5 -35.5t-35.5 -14.5t-35.5 14.5t-14.5 35.5v50h-300v-50 q0 -21 -14.5 -35.5t-35.5 -14.5t-35.5 14.5t-14.5 35.5v50h-31q-18 0 -32.5 10t-20.5 19l-5 10l-201 961h-54q-20 0 -35 14.5t-15 35.5t15 35.5t35 14.5z" />
-<glyph unicode="&#xe117;" d="M1200 1000v-100h-1200v100h200q0 41 29.5 70.5t70.5 29.5h300q41 0 70.5 -29.5t29.5 -70.5h500zM0 800h1200v-800h-1200v800z" />
-<glyph unicode="&#xe118;" d="M200 800l-200 -400v600h200q0 41 29.5 70.5t70.5 29.5h300q42 0 71 -29.5t29 -70.5h500v-200h-1000zM1500 700l-300 -700h-1200l300 700h1200z" />
-<glyph unicode="&#xe119;" d="M635 1184l230 -249q14 -14 10 -24.5t-25 -10.5h-150v-601h150q21 0 25 -10.5t-10 -24.5l-230 -249q-14 -15 -35 -15t-35 15l-230 249q-14 14 -10 24.5t25 10.5h150v601h-150q-21 0 -25 10.5t10 24.5l230 249q14 15 35 15t35 -15z" />
-<glyph unicode="&#xe120;" d="M936 864l249 -229q14 -15 14 -35.5t-14 -35.5l-249 -229q-15 -15 -25.5 -10.5t-10.5 24.5v151h-600v-151q0 -20 -10.5 -24.5t-25.5 10.5l-249 229q-14 15 -14 35.5t14 35.5l249 229q15 15 25.5 10.5t10.5 -25.5v-149h600v149q0 21 10.5 25.5t25.5 -10.5z" />
-<glyph unicode="&#xe121;" d="M1169 400l-172 732q-5 23 -23 45.5t-38 22.5h-672q-20 0 -38 -20t-23 -41l-172 -739h1138zM1100 300h-1000q-41 0 -70.5 -29.5t-29.5 -70.5v-100q0 -41 29.5 -70.5t70.5 -29.5h1000q41 0 70.5 29.5t29.5 70.5v100q0 41 -29.5 70.5t-70.5 29.5zM800 100v100h100v-100h-100 zM1000 100v100h100v-100h-100z" />
-<glyph unicode="&#xe122;" d="M1150 1100q21 0 35.5 -14.5t14.5 -35.5v-850q0 -21 -14.5 -35.5t-35.5 -14.5t-35.5 14.5t-14.5 35.5v850q0 21 14.5 35.5t35.5 14.5zM1000 200l-675 200h-38l47 -276q3 -16 -5.5 -20t-29.5 -4h-7h-84q-20 0 -34.5 14t-18.5 35q-55 337 -55 351v250v6q0 16 1 23.5t6.5 14 t17.5 6.5h200l675 250v-850zM0 750v-250q-4 0 -11 0.5t-24 6t-30 15t-24 30t-11 48.5v50q0 26 10.5 46t25 30t29 16t25.5 7z" />
-<glyph unicode="&#xe123;" d="M553 1200h94q20 0 29 -10.5t3 -29.5l-18 -37q83 -19 144 -82.5t76 -140.5l63 -327l118 -173h17q19 0 33 -14.5t14 -35t-13 -40.5t-31 -27q-8 -4 -23 -9.5t-65 -19.5t-103 -25t-132.5 -20t-158.5 -9q-57 0 -115 5t-104 12t-88.5 15.5t-73.5 17.5t-54.5 16t-35.5 12l-11 4 q-18 8 -31 28t-13 40.5t14 35t33 14.5h17l118 173l63 327q15 77 76 140t144 83l-18 32q-6 19 3.5 32t28.5 13zM498 110q50 -6 102 -6q53 0 102 6q-12 -49 -39.5 -79.5t-62.5 -30.5t-63 30.5t-39 79.5z" />
-<glyph unicode="&#xe124;" d="M800 946l224 78l-78 -224l234 -45l-180 -155l180 -155l-234 -45l78 -224l-224 78l-45 -234l-155 180l-155 -180l-45 234l-224 -78l78 224l-234 45l180 155l-180 155l234 45l-78 224l224 -78l45 234l155 -180l155 180z" />
-<glyph unicode="&#xe125;" d="M650 1200h50q40 0 70 -40.5t30 -84.5v-150l-28 -125h328q40 0 70 -40.5t30 -84.5v-100q0 -45 -29 -74l-238 -344q-16 -24 -38 -40.5t-45 -16.5h-250q-7 0 -42 25t-66 50l-31 25h-61q-45 0 -72.5 18t-27.5 57v400q0 36 20 63l145 196l96 198q13 28 37.5 48t51.5 20z M650 1100l-100 -212l-150 -213v-375h100l136 -100h214l250 375v125h-450l50 225v175h-50zM50 800h100q21 0 35.5 -14.5t14.5 -35.5v-500q0 -21 -14.5 -35.5t-35.5 -14.5h-100q-21 0 -35.5 14.5t-14.5 35.5v500q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe126;" d="M600 1100h250q23 0 45 -16.5t38 -40.5l238 -344q29 -29 29 -74v-100q0 -44 -30 -84.5t-70 -40.5h-328q28 -118 28 -125v-150q0 -44 -30 -84.5t-70 -40.5h-50q-27 0 -51.5 20t-37.5 48l-96 198l-145 196q-20 27 -20 63v400q0 39 27.5 57t72.5 18h61q124 100 139 100z M50 1000h100q21 0 35.5 -14.5t14.5 -35.5v-500q0 -21 -14.5 -35.5t-35.5 -14.5h-100q-21 0 -35.5 14.5t-14.5 35.5v500q0 21 14.5 35.5t35.5 14.5zM636 1000l-136 -100h-100v-375l150 -213l100 -212h50v175l-50 225h450v125l-250 375h-214z" />
-<glyph unicode="&#xe127;" d="M356 873l363 230q31 16 53 -6l110 -112q13 -13 13.5 -32t-11.5 -34l-84 -121h302q84 0 138 -38t54 -110t-55 -111t-139 -39h-106l-131 -339q-6 -21 -19.5 -41t-28.5 -20h-342q-7 0 -90 81t-83 94v525q0 17 14 35.5t28 28.5zM400 792v-503l100 -89h293l131 339 q6 21 19.5 41t28.5 20h203q21 0 30.5 25t0.5 50t-31 25h-456h-7h-6h-5.5t-6 0.5t-5 1.5t-5 2t-4 2.5t-4 4t-2.5 4.5q-12 25 5 47l146 183l-86 83zM50 800h100q21 0 35.5 -14.5t14.5 -35.5v-500q0 -21 -14.5 -35.5t-35.5 -14.5h-100q-21 0 -35.5 14.5t-14.5 35.5v500 q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe128;" d="M475 1103l366 -230q2 -1 6 -3.5t14 -10.5t18 -16.5t14.5 -20t6.5 -22.5v-525q0 -13 -86 -94t-93 -81h-342q-15 0 -28.5 20t-19.5 41l-131 339h-106q-85 0 -139.5 39t-54.5 111t54 110t138 38h302l-85 121q-11 15 -10.5 34t13.5 32l110 112q22 22 53 6zM370 945l146 -183 q17 -22 5 -47q-2 -2 -3.5 -4.5t-4 -4t-4 -2.5t-5 -2t-5 -1.5t-6 -0.5h-6h-6.5h-6h-475v-100h221q15 0 29 -20t20 -41l130 -339h294l106 89v503l-342 236zM1050 800h100q21 0 35.5 -14.5t14.5 -35.5v-500q0 -21 -14.5 -35.5t-35.5 -14.5h-100q-21 0 -35.5 14.5t-14.5 35.5 v500q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe129;" d="M550 1294q72 0 111 -55t39 -139v-106l339 -131q21 -6 41 -19.5t20 -28.5v-342q0 -7 -81 -90t-94 -83h-525q-17 0 -35.5 14t-28.5 28l-9 14l-230 363q-16 31 6 53l112 110q13 13 32 13.5t34 -11.5l121 -84v302q0 84 38 138t110 54zM600 972v203q0 21 -25 30.5t-50 0.5 t-25 -31v-456v-7v-6v-5.5t-0.5 -6t-1.5 -5t-2 -5t-2.5 -4t-4 -4t-4.5 -2.5q-25 -12 -47 5l-183 146l-83 -86l236 -339h503l89 100v293l-339 131q-21 6 -41 19.5t-20 28.5zM450 200h500q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-500 q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe130;" d="M350 1100h500q21 0 35.5 14.5t14.5 35.5v100q0 21 -14.5 35.5t-35.5 14.5h-500q-21 0 -35.5 -14.5t-14.5 -35.5v-100q0 -21 14.5 -35.5t35.5 -14.5zM600 306v-106q0 -84 -39 -139t-111 -55t-110 54t-38 138v302l-121 -84q-15 -12 -34 -11.5t-32 13.5l-112 110 q-22 22 -6 53l230 363q1 2 3.5 6t10.5 13.5t16.5 17t20 13.5t22.5 6h525q13 0 94 -83t81 -90v-342q0 -15 -20 -28.5t-41 -19.5zM308 900l-236 -339l83 -86l183 146q22 17 47 5q2 -1 4.5 -2.5t4 -4t2.5 -4t2 -5t1.5 -5t0.5 -6v-5.5v-6v-7v-456q0 -22 25 -31t50 0.5t25 30.5 v203q0 15 20 28.5t41 19.5l339 131v293l-89 100h-503z" />
-<glyph unicode="&#xe131;" d="M600 1178q118 0 225 -45.5t184.5 -123t123 -184.5t45.5 -225t-45.5 -225t-123 -184.5t-184.5 -123t-225 -45.5t-225 45.5t-184.5 123t-123 184.5t-45.5 225t45.5 225t123 184.5t184.5 123t225 45.5zM914 632l-275 223q-16 13 -27.5 8t-11.5 -26v-137h-275 q-10 0 -17.5 -7.5t-7.5 -17.5v-150q0 -10 7.5 -17.5t17.5 -7.5h275v-137q0 -21 11.5 -26t27.5 8l275 223q16 13 16 32t-16 32z" />
-<glyph unicode="&#xe132;" d="M600 1178q118 0 225 -45.5t184.5 -123t123 -184.5t45.5 -225t-45.5 -225t-123 -184.5t-184.5 -123t-225 -45.5t-225 45.5t-184.5 123t-123 184.5t-45.5 225t45.5 225t123 184.5t184.5 123t225 45.5zM561 855l-275 -223q-16 -13 -16 -32t16 -32l275 -223q16 -13 27.5 -8 t11.5 26v137h275q10 0 17.5 7.5t7.5 17.5v150q0 10 -7.5 17.5t-17.5 7.5h-275v137q0 21 -11.5 26t-27.5 -8z" />
-<glyph unicode="&#xe133;" d="M600 1178q118 0 225 -45.5t184.5 -123t123 -184.5t45.5 -225t-45.5 -225t-123 -184.5t-184.5 -123t-225 -45.5t-225 45.5t-184.5 123t-123 184.5t-45.5 225t45.5 225t123 184.5t184.5 123t225 45.5zM855 639l-223 275q-13 16 -32 16t-32 -16l-223 -275q-13 -16 -8 -27.5 t26 -11.5h137v-275q0 -10 7.5 -17.5t17.5 -7.5h150q10 0 17.5 7.5t7.5 17.5v275h137q21 0 26 11.5t-8 27.5z" />
-<glyph unicode="&#xe134;" d="M600 1178q118 0 225 -45.5t184.5 -123t123 -184.5t45.5 -225t-45.5 -225t-123 -184.5t-184.5 -123t-225 -45.5t-225 45.5t-184.5 123t-123 184.5t-45.5 225t45.5 225t123 184.5t184.5 123t225 45.5zM675 900h-150q-10 0 -17.5 -7.5t-7.5 -17.5v-275h-137q-21 0 -26 -11.5 t8 -27.5l223 -275q13 -16 32 -16t32 16l223 275q13 16 8 27.5t-26 11.5h-137v275q0 10 -7.5 17.5t-17.5 7.5z" />
-<glyph unicode="&#xe135;" d="M600 1176q116 0 222.5 -46t184 -123.5t123.5 -184t46 -222.5t-46 -222.5t-123.5 -184t-184 -123.5t-222.5 -46t-222.5 46t-184 123.5t-123.5 184t-46 222.5t46 222.5t123.5 184t184 123.5t222.5 46zM627 1101q-15 -12 -36.5 -20.5t-35.5 -12t-43 -8t-39 -6.5 q-15 -3 -45.5 0t-45.5 -2q-20 -7 -51.5 -26.5t-34.5 -34.5q-3 -11 6.5 -22.5t8.5 -18.5q-3 -34 -27.5 -91t-29.5 -79q-9 -34 5 -93t8 -87q0 -9 17 -44.5t16 -59.5q12 0 23 -5t23.5 -15t19.5 -14q16 -8 33 -15t40.5 -15t34.5 -12q21 -9 52.5 -32t60 -38t57.5 -11 q7 -15 -3 -34t-22.5 -40t-9.5 -38q13 -21 23 -34.5t27.5 -27.5t36.5 -18q0 -7 -3.5 -16t-3.5 -14t5 -17q104 -2 221 112q30 29 46.5 47t34.5 49t21 63q-13 8 -37 8.5t-36 7.5q-15 7 -49.5 15t-51.5 19q-18 0 -41 -0.5t-43 -1.5t-42 -6.5t-38 -16.5q-51 -35 -66 -12 q-4 1 -3.5 25.5t0.5 25.5q-6 13 -26.5 17.5t-24.5 6.5q1 15 -0.5 30.5t-7 28t-18.5 11.5t-31 -21q-23 -25 -42 4q-19 28 -8 58q6 16 22 22q6 -1 26 -1.5t33.5 -4t19.5 -13.5q7 -12 18 -24t21.5 -20.5t20 -15t15.5 -10.5l5 -3q2 12 7.5 30.5t8 34.5t-0.5 32q-3 18 3.5 29 t18 22.5t15.5 24.5q6 14 10.5 35t8 31t15.5 22.5t34 22.5q-6 18 10 36q8 0 24 -1.5t24.5 -1.5t20 4.5t20.5 15.5q-10 23 -31 42.5t-37.5 29.5t-49 27t-43.5 23q0 1 2 8t3 11.5t1.5 10.5t-1 9.5t-4.5 4.5q31 -13 58.5 -14.5t38.5 2.5l12 5q5 28 -9.5 46t-36.5 24t-50 15 t-41 20q-18 -4 -37 0zM613 994q0 -17 8 -42t17 -45t9 -23q-8 1 -39.5 5.5t-52.5 10t-37 16.5q3 11 16 29.5t16 25.5q10 -10 19 -10t14 6t13.5 14.5t16.5 12.5z" />
-<glyph unicode="&#xe136;" d="M756 1157q164 92 306 -9l-259 -138l145 -232l251 126q6 -89 -34 -156.5t-117 -110.5q-60 -34 -127 -39.5t-126 16.5l-596 -596q-15 -16 -36.5 -16t-36.5 16l-111 110q-15 15 -15 36.5t15 37.5l600 599q-34 101 5.5 201.5t135.5 154.5z" />
-<glyph unicode="&#xe137;" horiz-adv-x="1220" d="M100 1196h1000q41 0 70.5 -29.5t29.5 -70.5v-100q0 -41 -29.5 -70.5t-70.5 -29.5h-1000q-41 0 -70.5 29.5t-29.5 70.5v100q0 41 29.5 70.5t70.5 29.5zM1100 1096h-200v-100h200v100zM100 796h1000q41 0 70.5 -29.5t29.5 -70.5v-100q0 -41 -29.5 -70.5t-70.5 -29.5h-1000 q-41 0 -70.5 29.5t-29.5 70.5v100q0 41 29.5 70.5t70.5 29.5zM1100 696h-500v-100h500v100zM100 396h1000q41 0 70.5 -29.5t29.5 -70.5v-100q0 -41 -29.5 -70.5t-70.5 -29.5h-1000q-41 0 -70.5 29.5t-29.5 70.5v100q0 41 29.5 70.5t70.5 29.5zM1100 296h-300v-100h300v100z " />
-<glyph unicode="&#xe138;" d="M150 1200h900q21 0 35.5 -14.5t14.5 -35.5t-14.5 -35.5t-35.5 -14.5h-900q-21 0 -35.5 14.5t-14.5 35.5t14.5 35.5t35.5 14.5zM700 500v-300l-200 -200v500l-350 500h900z" />
-<glyph unicode="&#xe139;" d="M500 1200h200q41 0 70.5 -29.5t29.5 -70.5v-100h300q41 0 70.5 -29.5t29.5 -70.5v-400h-500v100h-200v-100h-500v400q0 41 29.5 70.5t70.5 29.5h300v100q0 41 29.5 70.5t70.5 29.5zM500 1100v-100h200v100h-200zM1200 400v-200q0 -41 -29.5 -70.5t-70.5 -29.5h-1000 q-41 0 -70.5 29.5t-29.5 70.5v200h1200z" />
-<glyph unicode="&#xe140;" d="M50 1200h300q21 0 25 -10.5t-10 -24.5l-94 -94l199 -199q7 -8 7 -18t-7 -18l-106 -106q-8 -7 -18 -7t-18 7l-199 199l-94 -94q-14 -14 -24.5 -10t-10.5 25v300q0 21 14.5 35.5t35.5 14.5zM850 1200h300q21 0 35.5 -14.5t14.5 -35.5v-300q0 -21 -10.5 -25t-24.5 10l-94 94 l-199 -199q-8 -7 -18 -7t-18 7l-106 106q-7 8 -7 18t7 18l199 199l-94 94q-14 14 -10 24.5t25 10.5zM364 470l106 -106q7 -8 7 -18t-7 -18l-199 -199l94 -94q14 -14 10 -24.5t-25 -10.5h-300q-21 0 -35.5 14.5t-14.5 35.5v300q0 21 10.5 25t24.5 -10l94 -94l199 199 q8 7 18 7t18 -7zM1071 271l94 94q14 14 24.5 10t10.5 -25v-300q0 -21 -14.5 -35.5t-35.5 -14.5h-300q-21 0 -25 10.5t10 24.5l94 94l-199 199q-7 8 -7 18t7 18l106 106q8 7 18 7t18 -7z" />
-<glyph unicode="&#xe141;" d="M596 1192q121 0 231.5 -47.5t190 -127t127 -190t47.5 -231.5t-47.5 -231.5t-127 -190.5t-190 -127t-231.5 -47t-231.5 47t-190.5 127t-127 190.5t-47 231.5t47 231.5t127 190t190.5 127t231.5 47.5zM596 1010q-112 0 -207.5 -55.5t-151 -151t-55.5 -207.5t55.5 -207.5 t151 -151t207.5 -55.5t207.5 55.5t151 151t55.5 207.5t-55.5 207.5t-151 151t-207.5 55.5zM454.5 905q22.5 0 38.5 -16t16 -38.5t-16 -39t-38.5 -16.5t-38.5 16.5t-16 39t16 38.5t38.5 16zM754.5 905q22.5 0 38.5 -16t16 -38.5t-16 -39t-38 -16.5q-14 0 -29 10l-55 -145 q17 -23 17 -51q0 -36 -25.5 -61.5t-61.5 -25.5t-61.5 25.5t-25.5 61.5q0 32 20.5 56.5t51.5 29.5l122 126l1 1q-9 14 -9 28q0 23 16 39t38.5 16zM345.5 709q22.5 0 38.5 -16t16 -38.5t-16 -38.5t-38.5 -16t-38.5 16t-16 38.5t16 38.5t38.5 16zM854.5 709q22.5 0 38.5 -16 t16 -38.5t-16 -38.5t-38.5 -16t-38.5 16t-16 38.5t16 38.5t38.5 16z" />
-<glyph unicode="&#xe142;" d="M546 173l469 470q91 91 99 192q7 98 -52 175.5t-154 94.5q-22 4 -47 4q-34 0 -66.5 -10t-56.5 -23t-55.5 -38t-48 -41.5t-48.5 -47.5q-376 -375 -391 -390q-30 -27 -45 -41.5t-37.5 -41t-32 -46.5t-16 -47.5t-1.5 -56.5q9 -62 53.5 -95t99.5 -33q74 0 125 51l548 548 q36 36 20 75q-7 16 -21.5 26t-32.5 10q-26 0 -50 -23q-13 -12 -39 -38l-341 -338q-15 -15 -35.5 -15.5t-34.5 13.5t-14 34.5t14 34.5q327 333 361 367q35 35 67.5 51.5t78.5 16.5q14 0 29 -1q44 -8 74.5 -35.5t43.5 -68.5q14 -47 2 -96.5t-47 -84.5q-12 -11 -32 -32 t-79.5 -81t-114.5 -115t-124.5 -123.5t-123 -119.5t-96.5 -89t-57 -45q-56 -27 -120 -27q-70 0 -129 32t-93 89q-48 78 -35 173t81 163l511 511q71 72 111 96q91 55 198 55q80 0 152 -33q78 -36 129.5 -103t66.5 -154q17 -93 -11 -183.5t-94 -156.5l-482 -476 q-15 -15 -36 -16t-37 14t-17.5 34t14.5 35z" />
-<glyph unicode="&#xe143;" d="M649 949q48 68 109.5 104t121.5 38.5t118.5 -20t102.5 -64t71 -100.5t27 -123q0 -57 -33.5 -117.5t-94 -124.5t-126.5 -127.5t-150 -152.5t-146 -174q-62 85 -145.5 174t-150 152.5t-126.5 127.5t-93.5 124.5t-33.5 117.5q0 64 28 123t73 100.5t104 64t119 20 t120.5 -38.5t104.5 -104zM896 972q-33 0 -64.5 -19t-56.5 -46t-47.5 -53.5t-43.5 -45.5t-37.5 -19t-36 19t-40 45.5t-43 53.5t-54 46t-65.5 19q-67 0 -122.5 -55.5t-55.5 -132.5q0 -23 13.5 -51t46 -65t57.5 -63t76 -75l22 -22q15 -14 44 -44t50.5 -51t46 -44t41 -35t23 -12 t23.5 12t42.5 36t46 44t52.5 52t44 43q4 4 12 13q43 41 63.5 62t52 55t46 55t26 46t11.5 44q0 79 -53 133.5t-120 54.5z" />
-<glyph unicode="&#xe144;" d="M776.5 1214q93.5 0 159.5 -66l141 -141q66 -66 66 -160q0 -42 -28 -95.5t-62 -87.5l-29 -29q-31 53 -77 99l-18 18l95 95l-247 248l-389 -389l212 -212l-105 -106l-19 18l-141 141q-66 66 -66 159t66 159l283 283q65 66 158.5 66zM600 706l105 105q10 -8 19 -17l141 -141 q66 -66 66 -159t-66 -159l-283 -283q-66 -66 -159 -66t-159 66l-141 141q-66 66 -66 159.5t66 159.5l55 55q29 -55 75 -102l18 -17l-95 -95l247 -248l389 389z" />
-<glyph unicode="&#xe145;" d="M603 1200q85 0 162 -15t127 -38t79 -48t29 -46v-953q0 -41 -29.5 -70.5t-70.5 -29.5h-600q-41 0 -70.5 29.5t-29.5 70.5v953q0 21 30 46.5t81 48t129 37.5t163 15zM300 1000v-700h600v700h-600zM600 254q-43 0 -73.5 -30.5t-30.5 -73.5t30.5 -73.5t73.5 -30.5t73.5 30.5 t30.5 73.5t-30.5 73.5t-73.5 30.5z" />
-<glyph unicode="&#xe146;" d="M902 1185l283 -282q15 -15 15 -36t-14.5 -35.5t-35.5 -14.5t-35 15l-36 35l-279 -267v-300l-212 210l-308 -307l-280 -203l203 280l307 308l-210 212h300l267 279l-35 36q-15 14 -15 35t14.5 35.5t35.5 14.5t35 -15z" />
-<glyph unicode="&#xe148;" d="M700 1248v-78q38 -5 72.5 -14.5t75.5 -31.5t71 -53.5t52 -84t24 -118.5h-159q-4 36 -10.5 59t-21 45t-40 35.5t-64.5 20.5v-307l64 -13q34 -7 64 -16.5t70 -32t67.5 -52.5t47.5 -80t20 -112q0 -139 -89 -224t-244 -97v-77h-100v79q-150 16 -237 103q-40 40 -52.5 93.5 t-15.5 139.5h139q5 -77 48.5 -126t117.5 -65v335l-27 8q-46 14 -79 26.5t-72 36t-63 52t-40 72.5t-16 98q0 70 25 126t67.5 92t94.5 57t110 27v77h100zM600 754v274q-29 -4 -50 -11t-42 -21.5t-31.5 -41.5t-10.5 -65q0 -29 7 -50.5t16.5 -34t28.5 -22.5t31.5 -14t37.5 -10 q9 -3 13 -4zM700 547v-310q22 2 42.5 6.5t45 15.5t41.5 27t29 42t12 59.5t-12.5 59.5t-38 44.5t-53 31t-66.5 24.5z" />
-<glyph unicode="&#xe149;" d="M561 1197q84 0 160.5 -40t123.5 -109.5t47 -147.5h-153q0 40 -19.5 71.5t-49.5 48.5t-59.5 26t-55.5 9q-37 0 -79 -14.5t-62 -35.5q-41 -44 -41 -101q0 -26 13.5 -63t26.5 -61t37 -66q6 -9 9 -14h241v-100h-197q8 -50 -2.5 -115t-31.5 -95q-45 -62 -99 -112 q34 10 83 17.5t71 7.5q32 1 102 -16t104 -17q83 0 136 30l50 -147q-31 -19 -58 -30.5t-55 -15.5t-42 -4.5t-46 -0.5q-23 0 -76 17t-111 32.5t-96 11.5q-39 -3 -82 -16t-67 -25l-23 -11l-55 145q4 3 16 11t15.5 10.5t13 9t15.5 12t14.5 14t17.5 18.5q48 55 54 126.5 t-30 142.5h-221v100h166q-23 47 -44 104q-7 20 -12 41.5t-6 55.5t6 66.5t29.5 70.5t58.5 71q97 88 263 88z" />
-<glyph unicode="&#xe150;" d="M400 300h150q21 0 25 -11t-10 -25l-230 -250q-14 -15 -35 -15t-35 15l-230 250q-14 14 -10 25t25 11h150v900h200v-900zM935 1184l230 -249q14 -14 10 -24.5t-25 -10.5h-150v-900h-200v900h-150q-21 0 -25 10.5t10 24.5l230 249q14 15 35 15t35 -15z" />
-<glyph unicode="&#xe151;" d="M1000 700h-100v100h-100v-100h-100v500h300v-500zM400 300h150q21 0 25 -11t-10 -25l-230 -250q-14 -15 -35 -15t-35 15l-230 250q-14 14 -10 25t25 11h150v900h200v-900zM801 1100v-200h100v200h-100zM1000 350l-200 -250h200v-100h-300v150l200 250h-200v100h300v-150z " />
-<glyph unicode="&#xe152;" d="M400 300h150q21 0 25 -11t-10 -25l-230 -250q-14 -15 -35 -15t-35 15l-230 250q-14 14 -10 25t25 11h150v900h200v-900zM1000 1050l-200 -250h200v-100h-300v150l200 250h-200v100h300v-150zM1000 0h-100v100h-100v-100h-100v500h300v-500zM801 400v-200h100v200h-100z " />
-<glyph unicode="&#xe153;" d="M400 300h150q21 0 25 -11t-10 -25l-230 -250q-14 -15 -35 -15t-35 15l-230 250q-14 14 -10 25t25 11h150v900h200v-900zM1000 700h-100v400h-100v100h200v-500zM1100 0h-100v100h-200v400h300v-500zM901 400v-200h100v200h-100z" />
-<glyph unicode="&#xe154;" d="M400 300h150q21 0 25 -11t-10 -25l-230 -250q-14 -15 -35 -15t-35 15l-230 250q-14 14 -10 25t25 11h150v900h200v-900zM1100 700h-100v100h-200v400h300v-500zM901 1100v-200h100v200h-100zM1000 0h-100v400h-100v100h200v-500z" />
-<glyph unicode="&#xe155;" d="M400 300h150q21 0 25 -11t-10 -25l-230 -250q-14 -15 -35 -15t-35 15l-230 250q-14 14 -10 25t25 11h150v900h200v-900zM900 1000h-200v200h200v-200zM1000 700h-300v200h300v-200zM1100 400h-400v200h400v-200zM1200 100h-500v200h500v-200z" />
-<glyph unicode="&#xe156;" d="M400 300h150q21 0 25 -11t-10 -25l-230 -250q-14 -15 -35 -15t-35 15l-230 250q-14 14 -10 25t25 11h150v900h200v-900zM1200 1000h-500v200h500v-200zM1100 700h-400v200h400v-200zM1000 400h-300v200h300v-200zM900 100h-200v200h200v-200z" />
-<glyph unicode="&#xe157;" d="M350 1100h400q162 0 256 -93.5t94 -256.5v-400q0 -165 -93.5 -257.5t-256.5 -92.5h-400q-165 0 -257.5 92.5t-92.5 257.5v400q0 165 92.5 257.5t257.5 92.5zM800 900h-500q-41 0 -70.5 -29.5t-29.5 -70.5v-500q0 -41 29.5 -70.5t70.5 -29.5h500q41 0 70.5 29.5t29.5 70.5 v500q0 41 -29.5 70.5t-70.5 29.5z" />
-<glyph unicode="&#xe158;" d="M350 1100h400q165 0 257.5 -92.5t92.5 -257.5v-400q0 -165 -92.5 -257.5t-257.5 -92.5h-400q-163 0 -256.5 92.5t-93.5 257.5v400q0 163 94 256.5t256 93.5zM800 900h-500q-41 0 -70.5 -29.5t-29.5 -70.5v-500q0 -41 29.5 -70.5t70.5 -29.5h500q41 0 70.5 29.5t29.5 70.5 v500q0 41 -29.5 70.5t-70.5 29.5zM440 770l253 -190q17 -12 17 -30t-17 -30l-253 -190q-16 -12 -28 -6.5t-12 26.5v400q0 21 12 26.5t28 -6.5z" />
-<glyph unicode="&#xe159;" d="M350 1100h400q163 0 256.5 -94t93.5 -256v-400q0 -165 -92.5 -257.5t-257.5 -92.5h-400q-165 0 -257.5 92.5t-92.5 257.5v400q0 163 92.5 256.5t257.5 93.5zM800 900h-500q-41 0 -70.5 -29.5t-29.5 -70.5v-500q0 -41 29.5 -70.5t70.5 -29.5h500q41 0 70.5 29.5t29.5 70.5 v500q0 41 -29.5 70.5t-70.5 29.5zM350 700h400q21 0 26.5 -12t-6.5 -28l-190 -253q-12 -17 -30 -17t-30 17l-190 253q-12 16 -6.5 28t26.5 12z" />
-<glyph unicode="&#xe160;" d="M350 1100h400q165 0 257.5 -92.5t92.5 -257.5v-400q0 -163 -92.5 -256.5t-257.5 -93.5h-400q-163 0 -256.5 94t-93.5 256v400q0 165 92.5 257.5t257.5 92.5zM800 900h-500q-41 0 -70.5 -29.5t-29.5 -70.5v-500q0 -41 29.5 -70.5t70.5 -29.5h500q41 0 70.5 29.5t29.5 70.5 v500q0 41 -29.5 70.5t-70.5 29.5zM580 693l190 -253q12 -16 6.5 -28t-26.5 -12h-400q-21 0 -26.5 12t6.5 28l190 253q12 17 30 17t30 -17z" />
-<glyph unicode="&#xe161;" d="M550 1100h400q165 0 257.5 -92.5t92.5 -257.5v-400q0 -165 -92.5 -257.5t-257.5 -92.5h-400q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5h450q41 0 70.5 29.5t29.5 70.5v500q0 41 -29.5 70.5t-70.5 29.5h-450q-21 0 -35.5 14.5t-14.5 35.5v100 q0 21 14.5 35.5t35.5 14.5zM338 867l324 -284q16 -14 16 -33t-16 -33l-324 -284q-16 -14 -27 -9t-11 26v150h-250q-21 0 -35.5 14.5t-14.5 35.5v200q0 21 14.5 35.5t35.5 14.5h250v150q0 21 11 26t27 -9z" />
-<glyph unicode="&#xe162;" d="M793 1182l9 -9q8 -10 5 -27q-3 -11 -79 -225.5t-78 -221.5l300 1q24 0 32.5 -17.5t-5.5 -35.5q-1 0 -133.5 -155t-267 -312.5t-138.5 -162.5q-12 -15 -26 -15h-9l-9 8q-9 11 -4 32q2 9 42 123.5t79 224.5l39 110h-302q-23 0 -31 19q-10 21 6 41q75 86 209.5 237.5 t228 257t98.5 111.5q9 16 25 16h9z" />
-<glyph unicode="&#xe163;" d="M350 1100h400q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-450q-41 0 -70.5 -29.5t-29.5 -70.5v-500q0 -41 29.5 -70.5t70.5 -29.5h450q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-400q-165 0 -257.5 92.5t-92.5 257.5v400 q0 165 92.5 257.5t257.5 92.5zM938 867l324 -284q16 -14 16 -33t-16 -33l-324 -284q-16 -14 -27 -9t-11 26v150h-250q-21 0 -35.5 14.5t-14.5 35.5v200q0 21 14.5 35.5t35.5 14.5h250v150q0 21 11 26t27 -9z" />
-<glyph unicode="&#xe164;" d="M750 1200h400q21 0 35.5 -14.5t14.5 -35.5v-400q0 -21 -10.5 -25t-24.5 10l-109 109l-312 -312q-15 -15 -35.5 -15t-35.5 15l-141 141q-15 15 -15 35.5t15 35.5l312 312l-109 109q-14 14 -10 24.5t25 10.5zM456 900h-156q-41 0 -70.5 -29.5t-29.5 -70.5v-500 q0 -41 29.5 -70.5t70.5 -29.5h500q41 0 70.5 29.5t29.5 70.5v148l200 200v-298q0 -165 -93.5 -257.5t-256.5 -92.5h-400q-165 0 -257.5 92.5t-92.5 257.5v400q0 165 92.5 257.5t257.5 92.5h300z" />
-<glyph unicode="&#xe165;" d="M600 1186q119 0 227.5 -46.5t187 -125t125 -187t46.5 -227.5t-46.5 -227.5t-125 -187t-187 -125t-227.5 -46.5t-227.5 46.5t-187 125t-125 187t-46.5 227.5t46.5 227.5t125 187t187 125t227.5 46.5zM600 1022q-115 0 -212 -56.5t-153.5 -153.5t-56.5 -212t56.5 -212 t153.5 -153.5t212 -56.5t212 56.5t153.5 153.5t56.5 212t-56.5 212t-153.5 153.5t-212 56.5zM600 794q80 0 137 -57t57 -137t-57 -137t-137 -57t-137 57t-57 137t57 137t137 57z" />
-<glyph unicode="&#xe166;" d="M450 1200h200q21 0 35.5 -14.5t14.5 -35.5v-350h245q20 0 25 -11t-9 -26l-383 -426q-14 -15 -33.5 -15t-32.5 15l-379 426q-13 15 -8.5 26t25.5 11h250v350q0 21 14.5 35.5t35.5 14.5zM50 300h1000q21 0 35.5 -14.5t14.5 -35.5v-250h-1100v250q0 21 14.5 35.5t35.5 14.5z M900 200v-50h100v50h-100z" />
-<glyph unicode="&#xe167;" d="M583 1182l378 -435q14 -15 9 -31t-26 -16h-244v-250q0 -20 -17 -35t-39 -15h-200q-20 0 -32 14.5t-12 35.5v250h-250q-20 0 -25.5 16.5t8.5 31.5l383 431q14 16 33.5 17t33.5 -14zM50 300h1000q21 0 35.5 -14.5t14.5 -35.5v-250h-1100v250q0 21 14.5 35.5t35.5 14.5z M900 200v-50h100v50h-100z" />
-<glyph unicode="&#xe168;" d="M396 723l369 369q7 7 17.5 7t17.5 -7l139 -139q7 -8 7 -18.5t-7 -17.5l-525 -525q-7 -8 -17.5 -8t-17.5 8l-292 291q-7 8 -7 18t7 18l139 139q8 7 18.5 7t17.5 -7zM50 300h1000q21 0 35.5 -14.5t14.5 -35.5v-250h-1100v250q0 21 14.5 35.5t35.5 14.5zM900 200v-50h100v50 h-100z" />
-<glyph unicode="&#xe169;" d="M135 1023l142 142q14 14 35 14t35 -14l77 -77l-212 -212l-77 76q-14 15 -14 36t14 35zM655 855l210 210q14 14 24.5 10t10.5 -25l-2 -599q-1 -20 -15.5 -35t-35.5 -15l-597 -1q-21 0 -25 10.5t10 24.5l208 208l-154 155l212 212zM50 300h1000q21 0 35.5 -14.5t14.5 -35.5 v-250h-1100v250q0 21 14.5 35.5t35.5 14.5zM900 200v-50h100v50h-100z" />
-<glyph unicode="&#xe170;" d="M350 1200l599 -2q20 -1 35 -15.5t15 -35.5l1 -597q0 -21 -10.5 -25t-24.5 10l-208 208l-155 -154l-212 212l155 154l-210 210q-14 14 -10 24.5t25 10.5zM524 512l-76 -77q-15 -14 -36 -14t-35 14l-142 142q-14 14 -14 35t14 35l77 77zM50 300h1000q21 0 35.5 -14.5 t14.5 -35.5v-250h-1100v250q0 21 14.5 35.5t35.5 14.5zM900 200v-50h100v50h-100z" />
-<glyph unicode="&#xe171;" d="M1200 103l-483 276l-314 -399v423h-399l1196 796v-1096zM483 424v-230l683 953z" />
-<glyph unicode="&#xe172;" d="M1100 1000v-850q0 -21 -14.5 -35.5t-35.5 -14.5h-150v400h-700v-400h-150q-21 0 -35.5 14.5t-14.5 35.5v1000q0 20 14.5 35t35.5 15h250v-300h500v300h100zM700 1000h-100v200h100v-200z" />
-<glyph unicode="&#xe173;" d="M1100 1000l-2 -149l-299 -299l-95 95q-9 9 -21.5 9t-21.5 -9l-149 -147h-312v-400h-150q-21 0 -35.5 14.5t-14.5 35.5v1000q0 20 14.5 35t35.5 15h250v-300h500v300h100zM700 1000h-100v200h100v-200zM1132 638l106 -106q7 -7 7 -17.5t-7 -17.5l-420 -421q-8 -7 -18 -7 t-18 7l-202 203q-8 7 -8 17.5t8 17.5l106 106q7 8 17.5 8t17.5 -8l79 -79l297 297q7 7 17.5 7t17.5 -7z" />
-<glyph unicode="&#xe174;" d="M1100 1000v-269l-103 -103l-134 134q-15 15 -33.5 16.5t-34.5 -12.5l-266 -266h-329v-400h-150q-21 0 -35.5 14.5t-14.5 35.5v1000q0 20 14.5 35t35.5 15h250v-300h500v300h100zM700 1000h-100v200h100v-200zM1202 572l70 -70q15 -15 15 -35.5t-15 -35.5l-131 -131 l131 -131q15 -15 15 -35.5t-15 -35.5l-70 -70q-15 -15 -35.5 -15t-35.5 15l-131 131l-131 -131q-15 -15 -35.5 -15t-35.5 15l-70 70q-15 15 -15 35.5t15 35.5l131 131l-131 131q-15 15 -15 35.5t15 35.5l70 70q15 15 35.5 15t35.5 -15l131 -131l131 131q15 15 35.5 15 t35.5 -15z" />
-<glyph unicode="&#xe175;" d="M1100 1000v-300h-350q-21 0 -35.5 -14.5t-14.5 -35.5v-150h-500v-400h-150q-21 0 -35.5 14.5t-14.5 35.5v1000q0 20 14.5 35t35.5 15h250v-300h500v300h100zM700 1000h-100v200h100v-200zM850 600h100q21 0 35.5 -14.5t14.5 -35.5v-250h150q21 0 25 -10.5t-10 -24.5 l-230 -230q-14 -14 -35 -14t-35 14l-230 230q-14 14 -10 24.5t25 10.5h150v250q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe176;" d="M1100 1000v-400l-165 165q-14 15 -35 15t-35 -15l-263 -265h-402v-400h-150q-21 0 -35.5 14.5t-14.5 35.5v1000q0 20 14.5 35t35.5 15h250v-300h500v300h100zM700 1000h-100v200h100v-200zM935 565l230 -229q14 -15 10 -25.5t-25 -10.5h-150v-250q0 -20 -14.5 -35 t-35.5 -15h-100q-21 0 -35.5 15t-14.5 35v250h-150q-21 0 -25 10.5t10 25.5l230 229q14 15 35 15t35 -15z" />
-<glyph unicode="&#xe177;" d="M50 1100h1100q21 0 35.5 -14.5t14.5 -35.5v-150h-1200v150q0 21 14.5 35.5t35.5 14.5zM1200 800v-550q0 -21 -14.5 -35.5t-35.5 -14.5h-1100q-21 0 -35.5 14.5t-14.5 35.5v550h1200zM100 500v-200h400v200h-400z" />
-<glyph unicode="&#xe178;" d="M935 1165l248 -230q14 -14 14 -35t-14 -35l-248 -230q-14 -14 -24.5 -10t-10.5 25v150h-400v200h400v150q0 21 10.5 25t24.5 -10zM200 800h-50q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5h50v-200zM400 800h-100v200h100v-200zM18 435l247 230 q14 14 24.5 10t10.5 -25v-150h400v-200h-400v-150q0 -21 -10.5 -25t-24.5 10l-247 230q-15 14 -15 35t15 35zM900 300h-100v200h100v-200zM1000 500h51q20 0 34.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-34.5 -14.5h-51v200z" />
-<glyph unicode="&#xe179;" d="M862 1073l276 116q25 18 43.5 8t18.5 -41v-1106q0 -21 -14.5 -35.5t-35.5 -14.5h-200q-21 0 -35.5 14.5t-14.5 35.5v397q-4 1 -11 5t-24 17.5t-30 29t-24 42t-11 56.5v359q0 31 18.5 65t43.5 52zM550 1200q22 0 34.5 -12.5t14.5 -24.5l1 -13v-450q0 -28 -10.5 -59.5 t-25 -56t-29 -45t-25.5 -31.5l-10 -11v-447q0 -21 -14.5 -35.5t-35.5 -14.5h-200q-21 0 -35.5 14.5t-14.5 35.5v447q-4 4 -11 11.5t-24 30.5t-30 46t-24 55t-11 60v450q0 2 0.5 5.5t4 12t8.5 15t14.5 12t22.5 5.5q20 0 32.5 -12.5t14.5 -24.5l3 -13v-350h100v350v5.5t2.5 12 t7 15t15 12t25.5 5.5q23 0 35.5 -12.5t13.5 -24.5l1 -13v-350h100v350q0 2 0.5 5.5t3 12t7 15t15 12t24.5 5.5z" />
-<glyph unicode="&#xe180;" d="M1200 1100v-56q-4 0 -11 -0.5t-24 -3t-30 -7.5t-24 -15t-11 -24v-888q0 -22 25 -34.5t50 -13.5l25 -2v-56h-400v56q75 0 87.5 6.5t12.5 43.5v394h-500v-394q0 -37 12.5 -43.5t87.5 -6.5v-56h-400v56q4 0 11 0.5t24 3t30 7.5t24 15t11 24v888q0 22 -25 34.5t-50 13.5 l-25 2v56h400v-56q-75 0 -87.5 -6.5t-12.5 -43.5v-394h500v394q0 37 -12.5 43.5t-87.5 6.5v56h400z" />
-<glyph unicode="&#xe181;" d="M675 1000h375q21 0 35.5 -14.5t14.5 -35.5v-150h-105l-295 -98v98l-200 200h-400l100 100h375zM100 900h300q41 0 70.5 -29.5t29.5 -70.5v-500q0 -41 -29.5 -70.5t-70.5 -29.5h-300q-41 0 -70.5 29.5t-29.5 70.5v500q0 41 29.5 70.5t70.5 29.5zM100 800v-200h300v200 h-300zM1100 535l-400 -133v163l400 133v-163zM100 500v-200h300v200h-300zM1100 398v-248q0 -21 -14.5 -35.5t-35.5 -14.5h-375l-100 -100h-375l-100 100h400l200 200h105z" />
-<glyph unicode="&#xe182;" d="M17 1007l162 162q17 17 40 14t37 -22l139 -194q14 -20 11 -44.5t-20 -41.5l-119 -118q102 -142 228 -268t267 -227l119 118q17 17 42.5 19t44.5 -12l192 -136q19 -14 22.5 -37.5t-13.5 -40.5l-163 -162q-3 -1 -9.5 -1t-29.5 2t-47.5 6t-62.5 14.5t-77.5 26.5t-90 42.5 t-101.5 60t-111 83t-119 108.5q-74 74 -133.5 150.5t-94.5 138.5t-60 119.5t-34.5 100t-15 74.5t-4.5 48z" />
-<glyph unicode="&#xe183;" d="M600 1100q92 0 175 -10.5t141.5 -27t108.5 -36.5t81.5 -40t53.5 -37t31 -27l9 -10v-200q0 -21 -14.5 -33t-34.5 -9l-202 34q-20 3 -34.5 20t-14.5 38v146q-141 24 -300 24t-300 -24v-146q0 -21 -14.5 -38t-34.5 -20l-202 -34q-20 -3 -34.5 9t-14.5 33v200q3 4 9.5 10.5 t31 26t54 37.5t80.5 39.5t109 37.5t141 26.5t175 10.5zM600 795q56 0 97 -9.5t60 -23.5t30 -28t12 -24l1 -10v-50l365 -303q14 -15 24.5 -40t10.5 -45v-212q0 -21 -14.5 -35.5t-35.5 -14.5h-1100q-21 0 -35.5 14.5t-14.5 35.5v212q0 20 10.5 45t24.5 40l365 303v50 q0 4 1 10.5t12 23t30 29t60 22.5t97 10z" />
-<glyph unicode="&#xe184;" d="M1100 700l-200 -200h-600l-200 200v500h200v-200h200v200h200v-200h200v200h200v-500zM250 400h700q21 0 35.5 -14.5t14.5 -35.5t-14.5 -35.5t-35.5 -14.5h-12l137 -100h-950l137 100h-12q-21 0 -35.5 14.5t-14.5 35.5t14.5 35.5t35.5 14.5zM50 100h1100q21 0 35.5 -14.5 t14.5 -35.5v-50h-1200v50q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe185;" d="M700 1100h-100q-41 0 -70.5 -29.5t-29.5 -70.5v-1000h300v1000q0 41 -29.5 70.5t-70.5 29.5zM1100 800h-100q-41 0 -70.5 -29.5t-29.5 -70.5v-700h300v700q0 41 -29.5 70.5t-70.5 29.5zM400 0h-300v400q0 41 29.5 70.5t70.5 29.5h100q41 0 70.5 -29.5t29.5 -70.5v-400z " />
-<glyph unicode="&#xe186;" d="M200 1100h700q124 0 212 -88t88 -212v-500q0 -124 -88 -212t-212 -88h-700q-124 0 -212 88t-88 212v500q0 124 88 212t212 88zM100 900v-700h900v700h-900zM500 700h-200v-100h200v-300h-300v100h200v100h-200v300h300v-100zM900 700v-300l-100 -100h-200v500h200z M700 700v-300h100v300h-100z" />
-<glyph unicode="&#xe187;" d="M200 1100h700q124 0 212 -88t88 -212v-500q0 -124 -88 -212t-212 -88h-700q-124 0 -212 88t-88 212v500q0 124 88 212t212 88zM100 900v-700h900v700h-900zM500 300h-100v200h-100v-200h-100v500h100v-200h100v200h100v-500zM900 700v-300l-100 -100h-200v500h200z M700 700v-300h100v300h-100z" />
-<glyph unicode="&#xe188;" d="M200 1100h700q124 0 212 -88t88 -212v-500q0 -124 -88 -212t-212 -88h-700q-124 0 -212 88t-88 212v500q0 124 88 212t212 88zM100 900v-700h900v700h-900zM500 700h-200v-300h200v-100h-300v500h300v-100zM900 700h-200v-300h200v-100h-300v500h300v-100z" />
-<glyph unicode="&#xe189;" d="M200 1100h700q124 0 212 -88t88 -212v-500q0 -124 -88 -212t-212 -88h-700q-124 0 -212 88t-88 212v500q0 124 88 212t212 88zM100 900v-700h900v700h-900zM500 400l-300 150l300 150v-300zM900 550l-300 -150v300z" />
-<glyph unicode="&#xe190;" d="M200 1100h700q124 0 212 -88t88 -212v-500q0 -124 -88 -212t-212 -88h-700q-124 0 -212 88t-88 212v500q0 124 88 212t212 88zM100 900v-700h900v700h-900zM900 300h-700v500h700v-500zM800 700h-130q-38 0 -66.5 -43t-28.5 -108t27 -107t68 -42h130v300zM300 700v-300 h130q41 0 68 42t27 107t-28.5 108t-66.5 43h-130z" />
-<glyph unicode="&#xe191;" d="M200 1100h700q124 0 212 -88t88 -212v-500q0 -124 -88 -212t-212 -88h-700q-124 0 -212 88t-88 212v500q0 124 88 212t212 88zM100 900v-700h900v700h-900zM500 700h-200v-100h200v-300h-300v100h200v100h-200v300h300v-100zM900 300h-100v400h-100v100h200v-500z M700 300h-100v100h100v-100z" />
-<glyph unicode="&#xe192;" d="M200 1100h700q124 0 212 -88t88 -212v-500q0 -124 -88 -212t-212 -88h-700q-124 0 -212 88t-88 212v500q0 124 88 212t212 88zM100 900v-700h900v700h-900zM300 700h200v-400h-300v500h100v-100zM900 300h-100v400h-100v100h200v-500zM300 600v-200h100v200h-100z M700 300h-100v100h100v-100z" />
-<glyph unicode="&#xe193;" d="M200 1100h700q124 0 212 -88t88 -212v-500q0 -124 -88 -212t-212 -88h-700q-124 0 -212 88t-88 212v500q0 124 88 212t212 88zM100 900v-700h900v700h-900zM500 500l-199 -200h-100v50l199 200v150h-200v100h300v-300zM900 300h-100v400h-100v100h200v-500zM701 300h-100 v100h100v-100z" />
-<glyph unicode="&#xe194;" d="M600 1191q120 0 229.5 -47t188.5 -126t126 -188.5t47 -229.5t-47 -229.5t-126 -188.5t-188.5 -126t-229.5 -47t-229.5 47t-188.5 126t-126 188.5t-47 229.5t47 229.5t126 188.5t188.5 126t229.5 47zM600 1021q-114 0 -211 -56.5t-153.5 -153.5t-56.5 -211t56.5 -211 t153.5 -153.5t211 -56.5t211 56.5t153.5 153.5t56.5 211t-56.5 211t-153.5 153.5t-211 56.5zM800 700h-300v-200h300v-100h-300l-100 100v200l100 100h300v-100z" />
-<glyph unicode="&#xe195;" d="M600 1191q120 0 229.5 -47t188.5 -126t126 -188.5t47 -229.5t-47 -229.5t-126 -188.5t-188.5 -126t-229.5 -47t-229.5 47t-188.5 126t-126 188.5t-47 229.5t47 229.5t126 188.5t188.5 126t229.5 47zM600 1021q-114 0 -211 -56.5t-153.5 -153.5t-56.5 -211t56.5 -211 t153.5 -153.5t211 -56.5t211 56.5t153.5 153.5t56.5 211t-56.5 211t-153.5 153.5t-211 56.5zM800 700v-100l-50 -50l100 -100v-50h-100l-100 100h-150v-100h-100v400h300zM500 700v-100h200v100h-200z" />
-<glyph unicode="&#xe197;" d="M503 1089q110 0 200.5 -59.5t134.5 -156.5q44 14 90 14q120 0 205 -86.5t85 -207t-85 -207t-205 -86.5h-128v250q0 21 -14.5 35.5t-35.5 14.5h-300q-21 0 -35.5 -14.5t-14.5 -35.5v-250h-222q-80 0 -136 57.5t-56 136.5q0 69 43 122.5t108 67.5q-2 19 -2 37q0 100 49 185 t134 134t185 49zM525 500h150q10 0 17.5 -7.5t7.5 -17.5v-275h137q21 0 26 -11.5t-8 -27.5l-223 -244q-13 -16 -32 -16t-32 16l-223 244q-13 16 -8 27.5t26 11.5h137v275q0 10 7.5 17.5t17.5 7.5z" />
-<glyph unicode="&#xe198;" d="M502 1089q110 0 201 -59.5t135 -156.5q43 15 89 15q121 0 206 -86.5t86 -206.5q0 -99 -60 -181t-150 -110l-378 360q-13 16 -31.5 16t-31.5 -16l-381 -365h-9q-79 0 -135.5 57.5t-56.5 136.5q0 69 43 122.5t108 67.5q-2 19 -2 38q0 100 49 184.5t133.5 134t184.5 49.5z M632 467l223 -228q13 -16 8 -27.5t-26 -11.5h-137v-275q0 -10 -7.5 -17.5t-17.5 -7.5h-150q-10 0 -17.5 7.5t-7.5 17.5v275h-137q-21 0 -26 11.5t8 27.5q199 204 223 228q19 19 31.5 19t32.5 -19z" />
-<glyph unicode="&#xe199;" d="M700 100v100h400l-270 300h170l-270 300h170l-300 333l-300 -333h170l-270 -300h170l-270 -300h400v-100h-50q-21 0 -35.5 -14.5t-14.5 -35.5v-50h400v50q0 21 -14.5 35.5t-35.5 14.5h-50z" />
-<glyph unicode="&#xe200;" d="M600 1179q94 0 167.5 -56.5t99.5 -145.5q89 -6 150.5 -71.5t61.5 -155.5q0 -61 -29.5 -112.5t-79.5 -82.5q9 -29 9 -55q0 -74 -52.5 -126.5t-126.5 -52.5q-55 0 -100 30v-251q21 0 35.5 -14.5t14.5 -35.5v-50h-300v50q0 21 14.5 35.5t35.5 14.5v251q-45 -30 -100 -30 q-74 0 -126.5 52.5t-52.5 126.5q0 18 4 38q-47 21 -75.5 65t-28.5 97q0 74 52.5 126.5t126.5 52.5q5 0 23 -2q0 2 -1 10t-1 13q0 116 81.5 197.5t197.5 81.5z" />
-<glyph unicode="&#xe201;" d="M1010 1010q111 -111 150.5 -260.5t0 -299t-150.5 -260.5q-83 -83 -191.5 -126.5t-218.5 -43.5t-218.5 43.5t-191.5 126.5q-111 111 -150.5 260.5t0 299t150.5 260.5q83 83 191.5 126.5t218.5 43.5t218.5 -43.5t191.5 -126.5zM476 1065q-4 0 -8 -1q-121 -34 -209.5 -122.5 t-122.5 -209.5q-4 -12 2.5 -23t18.5 -14l36 -9q3 -1 7 -1q23 0 29 22q27 96 98 166q70 71 166 98q11 3 17.5 13.5t3.5 22.5l-9 35q-3 13 -14 19q-7 4 -15 4zM512 920q-4 0 -9 -2q-80 -24 -138.5 -82.5t-82.5 -138.5q-4 -13 2 -24t19 -14l34 -9q4 -1 8 -1q22 0 28 21 q18 58 58.5 98.5t97.5 58.5q12 3 18 13.5t3 21.5l-9 35q-3 12 -14 19q-7 4 -15 4zM719.5 719.5q-49.5 49.5 -119.5 49.5t-119.5 -49.5t-49.5 -119.5t49.5 -119.5t119.5 -49.5t119.5 49.5t49.5 119.5t-49.5 119.5zM855 551q-22 0 -28 -21q-18 -58 -58.5 -98.5t-98.5 -57.5 q-11 -4 -17 -14.5t-3 -21.5l9 -35q3 -12 14 -19q7 -4 15 -4q4 0 9 2q80 24 138.5 82.5t82.5 138.5q4 13 -2.5 24t-18.5 14l-34 9q-4 1 -8 1zM1000 515q-23 0 -29 -22q-27 -96 -98 -166q-70 -71 -166 -98q-11 -3 -17.5 -13.5t-3.5 -22.5l9 -35q3 -13 14 -19q7 -4 15 -4 q4 0 8 1q121 34 209.5 122.5t122.5 209.5q4 12 -2.5 23t-18.5 14l-36 9q-3 1 -7 1z" />
-<glyph unicode="&#xe202;" d="M700 800h300v-380h-180v200h-340v-200h-380v755q0 10 7.5 17.5t17.5 7.5h575v-400zM1000 900h-200v200zM700 300h162l-212 -212l-212 212h162v200h100v-200zM520 0h-395q-10 0 -17.5 7.5t-7.5 17.5v395zM1000 220v-195q0 -10 -7.5 -17.5t-17.5 -7.5h-195z" />
-<glyph unicode="&#xe203;" d="M700 800h300v-520l-350 350l-550 -550v1095q0 10 7.5 17.5t17.5 7.5h575v-400zM1000 900h-200v200zM862 200h-162v-200h-100v200h-162l212 212zM480 0h-355q-10 0 -17.5 7.5t-7.5 17.5v55h380v-80zM1000 80v-55q0 -10 -7.5 -17.5t-17.5 -7.5h-155v80h180z" />
-<glyph unicode="&#xe204;" d="M1162 800h-162v-200h100l100 -100h-300v300h-162l212 212zM200 800h200q27 0 40 -2t29.5 -10.5t23.5 -30t7 -57.5h300v-100h-600l-200 -350v450h100q0 36 7 57.5t23.5 30t29.5 10.5t40 2zM800 400h240l-240 -400h-800l300 500h500v-100z" />
-<glyph unicode="&#xe205;" d="M650 1100h100q21 0 35.5 -14.5t14.5 -35.5v-50h50q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-300q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5h50v50q0 21 14.5 35.5t35.5 14.5zM1000 850v150q41 0 70.5 -29.5t29.5 -70.5v-800 q0 -41 -29.5 -70.5t-70.5 -29.5h-600q-1 0 -20 4l246 246l-326 326v324q0 41 29.5 70.5t70.5 29.5v-150q0 -62 44 -106t106 -44h300q62 0 106 44t44 106zM412 250l-212 -212v162h-200v100h200v162z" />
-<glyph unicode="&#xe206;" d="M450 1100h100q21 0 35.5 -14.5t14.5 -35.5v-50h50q21 0 35.5 -14.5t14.5 -35.5v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-300q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5h50v50q0 21 14.5 35.5t35.5 14.5zM800 850v150q41 0 70.5 -29.5t29.5 -70.5v-500 h-200v-300h200q0 -36 -7 -57.5t-23.5 -30t-29.5 -10.5t-40 -2h-600q-41 0 -70.5 29.5t-29.5 70.5v800q0 41 29.5 70.5t70.5 29.5v-150q0 -62 44 -106t106 -44h300q62 0 106 44t44 106zM1212 250l-212 -212v162h-200v100h200v162z" />
-<glyph unicode="&#xe209;" d="M658 1197l637 -1104q23 -38 7 -65.5t-60 -27.5h-1276q-44 0 -60 27.5t7 65.5l637 1104q22 39 54 39t54 -39zM704 800h-208q-20 0 -32 -14.5t-8 -34.5l58 -302q4 -20 21.5 -34.5t37.5 -14.5h54q20 0 37.5 14.5t21.5 34.5l58 302q4 20 -8 34.5t-32 14.5zM500 300v-100h200 v100h-200z" />
-<glyph unicode="&#xe210;" d="M425 1100h250q10 0 17.5 -7.5t7.5 -17.5v-150q0 -10 -7.5 -17.5t-17.5 -7.5h-250q-10 0 -17.5 7.5t-7.5 17.5v150q0 10 7.5 17.5t17.5 7.5zM425 800h250q10 0 17.5 -7.5t7.5 -17.5v-150q0 -10 -7.5 -17.5t-17.5 -7.5h-250q-10 0 -17.5 7.5t-7.5 17.5v150q0 10 7.5 17.5 t17.5 7.5zM825 800h250q10 0 17.5 -7.5t7.5 -17.5v-150q0 -10 -7.5 -17.5t-17.5 -7.5h-250q-10 0 -17.5 7.5t-7.5 17.5v150q0 10 7.5 17.5t17.5 7.5zM25 500h250q10 0 17.5 -7.5t7.5 -17.5v-150q0 -10 -7.5 -17.5t-17.5 -7.5h-250q-10 0 -17.5 7.5t-7.5 17.5v150 q0 10 7.5 17.5t17.5 7.5zM425 500h250q10 0 17.5 -7.5t7.5 -17.5v-150q0 -10 -7.5 -17.5t-17.5 -7.5h-250q-10 0 -17.5 7.5t-7.5 17.5v150q0 10 7.5 17.5t17.5 7.5zM825 500h250q10 0 17.5 -7.5t7.5 -17.5v-150q0 -10 -7.5 -17.5t-17.5 -7.5h-250q-10 0 -17.5 7.5t-7.5 17.5 v150q0 10 7.5 17.5t17.5 7.5zM25 200h250q10 0 17.5 -7.5t7.5 -17.5v-150q0 -10 -7.5 -17.5t-17.5 -7.5h-250q-10 0 -17.5 7.5t-7.5 17.5v150q0 10 7.5 17.5t17.5 7.5zM425 200h250q10 0 17.5 -7.5t7.5 -17.5v-150q0 -10 -7.5 -17.5t-17.5 -7.5h-250q-10 0 -17.5 7.5 t-7.5 17.5v150q0 10 7.5 17.5t17.5 7.5zM825 200h250q10 0 17.5 -7.5t7.5 -17.5v-150q0 -10 -7.5 -17.5t-17.5 -7.5h-250q-10 0 -17.5 7.5t-7.5 17.5v150q0 10 7.5 17.5t17.5 7.5z" />
-<glyph unicode="&#xe211;" d="M700 1200h100v-200h-100v-100h350q62 0 86.5 -39.5t-3.5 -94.5l-66 -132q-41 -83 -81 -134h-772q-40 51 -81 134l-66 132q-28 55 -3.5 94.5t86.5 39.5h350v100h-100v200h100v100h200v-100zM250 400h700q21 0 35.5 -14.5t14.5 -35.5t-14.5 -35.5t-35.5 -14.5h-12l137 -100 h-950l138 100h-13q-21 0 -35.5 14.5t-14.5 35.5t14.5 35.5t35.5 14.5zM50 100h1100q21 0 35.5 -14.5t14.5 -35.5v-50h-1200v50q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe212;" d="M600 1300q40 0 68.5 -29.5t28.5 -70.5h-194q0 41 28.5 70.5t68.5 29.5zM443 1100h314q18 -37 18 -75q0 -8 -3 -25h328q41 0 44.5 -16.5t-30.5 -38.5l-175 -145h-678l-178 145q-34 22 -29 38.5t46 16.5h328q-3 17 -3 25q0 38 18 75zM250 700h700q21 0 35.5 -14.5 t14.5 -35.5t-14.5 -35.5t-35.5 -14.5h-150v-200l275 -200h-950l275 200v200h-150q-21 0 -35.5 14.5t-14.5 35.5t14.5 35.5t35.5 14.5zM50 100h1100q21 0 35.5 -14.5t14.5 -35.5v-50h-1200v50q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe213;" d="M600 1181q75 0 128 -53t53 -128t-53 -128t-128 -53t-128 53t-53 128t53 128t128 53zM602 798h46q34 0 55.5 -28.5t21.5 -86.5q0 -76 39 -183h-324q39 107 39 183q0 58 21.5 86.5t56.5 28.5h45zM250 400h700q21 0 35.5 -14.5t14.5 -35.5t-14.5 -35.5t-35.5 -14.5h-13 l138 -100h-950l137 100h-12q-21 0 -35.5 14.5t-14.5 35.5t14.5 35.5t35.5 14.5zM50 100h1100q21 0 35.5 -14.5t14.5 -35.5v-50h-1200v50q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe214;" d="M600 1300q47 0 92.5 -53.5t71 -123t25.5 -123.5q0 -78 -55.5 -133.5t-133.5 -55.5t-133.5 55.5t-55.5 133.5q0 62 34 143l144 -143l111 111l-163 163q34 26 63 26zM602 798h46q34 0 55.5 -28.5t21.5 -86.5q0 -76 39 -183h-324q39 107 39 183q0 58 21.5 86.5t56.5 28.5h45 zM250 400h700q21 0 35.5 -14.5t14.5 -35.5t-14.5 -35.5t-35.5 -14.5h-13l138 -100h-950l137 100h-12q-21 0 -35.5 14.5t-14.5 35.5t14.5 35.5t35.5 14.5zM50 100h1100q21 0 35.5 -14.5t14.5 -35.5v-50h-1200v50q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe215;" d="M600 1200l300 -161v-139h-300q0 -57 18.5 -108t50 -91.5t63 -72t70 -67.5t57.5 -61h-530q-60 83 -90.5 177.5t-30.5 178.5t33 164.5t87.5 139.5t126 96.5t145.5 41.5v-98zM250 400h700q21 0 35.5 -14.5t14.5 -35.5t-14.5 -35.5t-35.5 -14.5h-13l138 -100h-950l137 100 h-12q-21 0 -35.5 14.5t-14.5 35.5t14.5 35.5t35.5 14.5zM50 100h1100q21 0 35.5 -14.5t14.5 -35.5v-50h-1200v50q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe216;" d="M600 1300q41 0 70.5 -29.5t29.5 -70.5v-78q46 -26 73 -72t27 -100v-50h-400v50q0 54 27 100t73 72v78q0 41 29.5 70.5t70.5 29.5zM400 800h400q54 0 100 -27t72 -73h-172v-100h200v-100h-200v-100h200v-100h-200v-100h200q0 -83 -58.5 -141.5t-141.5 -58.5h-400 q-83 0 -141.5 58.5t-58.5 141.5v400q0 83 58.5 141.5t141.5 58.5z" />
-<glyph unicode="&#xe218;" d="M150 1100h900q21 0 35.5 -14.5t14.5 -35.5v-500q0 -21 -14.5 -35.5t-35.5 -14.5h-900q-21 0 -35.5 14.5t-14.5 35.5v500q0 21 14.5 35.5t35.5 14.5zM125 400h950q10 0 17.5 -7.5t7.5 -17.5v-50q0 -10 -7.5 -17.5t-17.5 -7.5h-283l224 -224q13 -13 13 -31.5t-13 -32 t-31.5 -13.5t-31.5 13l-88 88h-524l-87 -88q-13 -13 -32 -13t-32 13.5t-13 32t13 31.5l224 224h-289q-10 0 -17.5 7.5t-7.5 17.5v50q0 10 7.5 17.5t17.5 7.5zM541 300l-100 -100h324l-100 100h-124z" />
-<glyph unicode="&#xe219;" d="M200 1100h800q83 0 141.5 -58.5t58.5 -141.5v-200h-100q0 41 -29.5 70.5t-70.5 29.5h-250q-41 0 -70.5 -29.5t-29.5 -70.5h-100q0 41 -29.5 70.5t-70.5 29.5h-250q-41 0 -70.5 -29.5t-29.5 -70.5h-100v200q0 83 58.5 141.5t141.5 58.5zM100 600h1000q41 0 70.5 -29.5 t29.5 -70.5v-300h-1200v300q0 41 29.5 70.5t70.5 29.5zM300 100v-50q0 -21 -14.5 -35.5t-35.5 -14.5h-100q-21 0 -35.5 14.5t-14.5 35.5v50h200zM1100 100v-50q0 -21 -14.5 -35.5t-35.5 -14.5h-100q-21 0 -35.5 14.5t-14.5 35.5v50h200z" />
-<glyph unicode="&#xe221;" d="M480 1165l682 -683q31 -31 31 -75.5t-31 -75.5l-131 -131h-481l-517 518q-32 31 -32 75.5t32 75.5l295 296q31 31 75.5 31t76.5 -31zM108 794l342 -342l303 304l-341 341zM250 100h800q21 0 35.5 -14.5t14.5 -35.5v-50h-900v50q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe223;" d="M1057 647l-189 506q-8 19 -27.5 33t-40.5 14h-400q-21 0 -40.5 -14t-27.5 -33l-189 -506q-8 -19 1.5 -33t30.5 -14h625v-150q0 -21 14.5 -35.5t35.5 -14.5t35.5 14.5t14.5 35.5v150h125q21 0 30.5 14t1.5 33zM897 0h-595v50q0 21 14.5 35.5t35.5 14.5h50v50 q0 21 14.5 35.5t35.5 14.5h48v300h200v-300h47q21 0 35.5 -14.5t14.5 -35.5v-50h50q21 0 35.5 -14.5t14.5 -35.5v-50z" />
-<glyph unicode="&#xe224;" d="M900 800h300v-575q0 -10 -7.5 -17.5t-17.5 -7.5h-375v591l-300 300v84q0 10 7.5 17.5t17.5 7.5h375v-400zM1200 900h-200v200zM400 600h300v-575q0 -10 -7.5 -17.5t-17.5 -7.5h-650q-10 0 -17.5 7.5t-7.5 17.5v950q0 10 7.5 17.5t17.5 7.5h375v-400zM700 700h-200v200z " />
-<glyph unicode="&#xe225;" d="M484 1095h195q75 0 146 -32.5t124 -86t89.5 -122.5t48.5 -142q18 -14 35 -20q31 -10 64.5 6.5t43.5 48.5q10 34 -15 71q-19 27 -9 43q5 8 12.5 11t19 -1t23.5 -16q41 -44 39 -105q-3 -63 -46 -106.5t-104 -43.5h-62q-7 -55 -35 -117t-56 -100l-39 -234q-3 -20 -20 -34.5 t-38 -14.5h-100q-21 0 -33 14.5t-9 34.5l12 70q-49 -14 -91 -14h-195q-24 0 -65 8l-11 -64q-3 -20 -20 -34.5t-38 -14.5h-100q-21 0 -33 14.5t-9 34.5l26 157q-84 74 -128 175l-159 53q-19 7 -33 26t-14 40v50q0 21 14.5 35.5t35.5 14.5h124q11 87 56 166l-111 95 q-16 14 -12.5 23.5t24.5 9.5h203q116 101 250 101zM675 1000h-250q-10 0 -17.5 -7.5t-7.5 -17.5v-50q0 -10 7.5 -17.5t17.5 -7.5h250q10 0 17.5 7.5t7.5 17.5v50q0 10 -7.5 17.5t-17.5 7.5z" />
-<glyph unicode="&#xe226;" d="M641 900l423 247q19 8 42 2.5t37 -21.5l32 -38q14 -15 12.5 -36t-17.5 -34l-139 -120h-390zM50 1100h106q67 0 103 -17t66 -71l102 -212h823q21 0 35.5 -14.5t14.5 -35.5v-50q0 -21 -14 -40t-33 -26l-737 -132q-23 -4 -40 6t-26 25q-42 67 -100 67h-300q-62 0 -106 44 t-44 106v200q0 62 44 106t106 44zM173 928h-80q-19 0 -28 -14t-9 -35v-56q0 -51 42 -51h134q16 0 21.5 8t5.5 24q0 11 -16 45t-27 51q-18 28 -43 28zM550 727q-32 0 -54.5 -22.5t-22.5 -54.5t22.5 -54.5t54.5 -22.5t54.5 22.5t22.5 54.5t-22.5 54.5t-54.5 22.5zM130 389 l152 130q18 19 34 24t31 -3.5t24.5 -17.5t25.5 -28q28 -35 50.5 -51t48.5 -13l63 5l48 -179q13 -61 -3.5 -97.5t-67.5 -79.5l-80 -69q-47 -40 -109 -35.5t-103 51.5l-130 151q-40 47 -35.5 109.5t51.5 102.5zM380 377l-102 -88q-31 -27 2 -65l37 -43q13 -15 27.5 -19.5 t31.5 6.5l61 53q19 16 14 49q-2 20 -12 56t-17 45q-11 12 -19 14t-23 -8z" />
-<glyph unicode="&#xe227;" d="M625 1200h150q10 0 17.5 -7.5t7.5 -17.5v-109q79 -33 131 -87.5t53 -128.5q1 -46 -15 -84.5t-39 -61t-46 -38t-39 -21.5l-17 -6q6 0 15 -1.5t35 -9t50 -17.5t53 -30t50 -45t35.5 -64t14.5 -84q0 -59 -11.5 -105.5t-28.5 -76.5t-44 -51t-49.5 -31.5t-54.5 -16t-49.5 -6.5 t-43.5 -1v-75q0 -10 -7.5 -17.5t-17.5 -7.5h-150q-10 0 -17.5 7.5t-7.5 17.5v75h-100v-75q0 -10 -7.5 -17.5t-17.5 -7.5h-150q-10 0 -17.5 7.5t-7.5 17.5v75h-175q-10 0 -17.5 7.5t-7.5 17.5v150q0 10 7.5 17.5t17.5 7.5h75v600h-75q-10 0 -17.5 7.5t-7.5 17.5v150 q0 10 7.5 17.5t17.5 7.5h175v75q0 10 7.5 17.5t17.5 7.5h150q10 0 17.5 -7.5t7.5 -17.5v-75h100v75q0 10 7.5 17.5t17.5 7.5zM400 900v-200h263q28 0 48.5 10.5t30 25t15 29t5.5 25.5l1 10q0 4 -0.5 11t-6 24t-15 30t-30 24t-48.5 11h-263zM400 500v-200h363q28 0 48.5 10.5 t30 25t15 29t5.5 25.5l1 10q0 4 -0.5 11t-6 24t-15 30t-30 24t-48.5 11h-363z" />
-<glyph unicode="&#xe230;" d="M212 1198h780q86 0 147 -61t61 -147v-416q0 -51 -18 -142.5t-36 -157.5l-18 -66q-29 -87 -93.5 -146.5t-146.5 -59.5h-572q-82 0 -147 59t-93 147q-8 28 -20 73t-32 143.5t-20 149.5v416q0 86 61 147t147 61zM600 1045q-70 0 -132.5 -11.5t-105.5 -30.5t-78.5 -41.5 t-57 -45t-36 -41t-20.5 -30.5l-6 -12l156 -243h560l156 243q-2 5 -6 12.5t-20 29.5t-36.5 42t-57 44.5t-79 42t-105 29.5t-132.5 12zM762 703h-157l195 261z" />
-<glyph unicode="&#xe231;" d="M475 1300h150q103 0 189 -86t86 -189v-500q0 -41 -42 -83t-83 -42h-450q-41 0 -83 42t-42 83v500q0 103 86 189t189 86zM700 300v-225q0 -21 -27 -48t-48 -27h-150q-21 0 -48 27t-27 48v225h300z" />
-<glyph unicode="&#xe232;" d="M475 1300h96q0 -150 89.5 -239.5t239.5 -89.5v-446q0 -41 -42 -83t-83 -42h-450q-41 0 -83 42t-42 83v500q0 103 86 189t189 86zM700 300v-225q0 -21 -27 -48t-48 -27h-150q-21 0 -48 27t-27 48v225h300z" />
-<glyph unicode="&#xe233;" d="M1294 767l-638 -283l-378 170l-78 -60v-224l100 -150v-199l-150 148l-150 -149v200l100 150v250q0 4 -0.5 10.5t0 9.5t1 8t3 8t6.5 6l47 40l-147 65l642 283zM1000 380l-350 -166l-350 166v147l350 -165l350 165v-147z" />
-<glyph unicode="&#xe234;" d="M250 800q62 0 106 -44t44 -106t-44 -106t-106 -44t-106 44t-44 106t44 106t106 44zM650 800q62 0 106 -44t44 -106t-44 -106t-106 -44t-106 44t-44 106t44 106t106 44zM1050 800q62 0 106 -44t44 -106t-44 -106t-106 -44t-106 44t-44 106t44 106t106 44z" />
-<glyph unicode="&#xe235;" d="M550 1100q62 0 106 -44t44 -106t-44 -106t-106 -44t-106 44t-44 106t44 106t106 44zM550 700q62 0 106 -44t44 -106t-44 -106t-106 -44t-106 44t-44 106t44 106t106 44zM550 300q62 0 106 -44t44 -106t-44 -106t-106 -44t-106 44t-44 106t44 106t106 44z" />
-<glyph unicode="&#xe236;" d="M125 1100h950q10 0 17.5 -7.5t7.5 -17.5v-150q0 -10 -7.5 -17.5t-17.5 -7.5h-950q-10 0 -17.5 7.5t-7.5 17.5v150q0 10 7.5 17.5t17.5 7.5zM125 700h950q10 0 17.5 -7.5t7.5 -17.5v-150q0 -10 -7.5 -17.5t-17.5 -7.5h-950q-10 0 -17.5 7.5t-7.5 17.5v150q0 10 7.5 17.5 t17.5 7.5zM125 300h950q10 0 17.5 -7.5t7.5 -17.5v-150q0 -10 -7.5 -17.5t-17.5 -7.5h-950q-10 0 -17.5 7.5t-7.5 17.5v150q0 10 7.5 17.5t17.5 7.5z" />
-<glyph unicode="&#xe237;" d="M350 1200h500q162 0 256 -93.5t94 -256.5v-500q0 -165 -93.5 -257.5t-256.5 -92.5h-500q-165 0 -257.5 92.5t-92.5 257.5v500q0 165 92.5 257.5t257.5 92.5zM900 1000h-600q-41 0 -70.5 -29.5t-29.5 -70.5v-600q0 -41 29.5 -70.5t70.5 -29.5h600q41 0 70.5 29.5 t29.5 70.5v600q0 41 -29.5 70.5t-70.5 29.5zM350 900h500q21 0 35.5 -14.5t14.5 -35.5v-300q0 -21 -14.5 -35.5t-35.5 -14.5h-500q-21 0 -35.5 14.5t-14.5 35.5v300q0 21 14.5 35.5t35.5 14.5zM400 800v-200h400v200h-400z" />
-<glyph unicode="&#xe238;" d="M150 1100h1000q21 0 35.5 -14.5t14.5 -35.5t-14.5 -35.5t-35.5 -14.5h-50v-200h50q21 0 35.5 -14.5t14.5 -35.5t-14.5 -35.5t-35.5 -14.5h-50v-200h50q21 0 35.5 -14.5t14.5 -35.5t-14.5 -35.5t-35.5 -14.5h-50v-200h50q21 0 35.5 -14.5t14.5 -35.5t-14.5 -35.5 t-35.5 -14.5h-1000q-21 0 -35.5 14.5t-14.5 35.5t14.5 35.5t35.5 14.5h50v200h-50q-21 0 -35.5 14.5t-14.5 35.5t14.5 35.5t35.5 14.5h50v200h-50q-21 0 -35.5 14.5t-14.5 35.5t14.5 35.5t35.5 14.5h50v200h-50q-21 0 -35.5 14.5t-14.5 35.5t14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe239;" d="M650 1187q87 -67 118.5 -156t0 -178t-118.5 -155q-87 66 -118.5 155t0 178t118.5 156zM300 800q124 0 212 -88t88 -212q-124 0 -212 88t-88 212zM1000 800q0 -124 -88 -212t-212 -88q0 124 88 212t212 88zM300 500q124 0 212 -88t88 -212q-124 0 -212 88t-88 212z M1000 500q0 -124 -88 -212t-212 -88q0 124 88 212t212 88zM700 199v-144q0 -21 -14.5 -35.5t-35.5 -14.5t-35.5 14.5t-14.5 35.5v142q40 -4 43 -4q17 0 57 6z" />
-<glyph unicode="&#xe240;" d="M745 878l69 19q25 6 45 -12l298 -295q11 -11 15 -26.5t-2 -30.5q-5 -14 -18 -23.5t-28 -9.5h-8q1 0 1 -13q0 -29 -2 -56t-8.5 -62t-20 -63t-33 -53t-51 -39t-72.5 -14h-146q-184 0 -184 288q0 24 10 47q-20 4 -62 4t-63 -4q11 -24 11 -47q0 -288 -184 -288h-142 q-48 0 -84.5 21t-56 51t-32 71.5t-16 75t-3.5 68.5q0 13 2 13h-7q-15 0 -27.5 9.5t-18.5 23.5q-6 15 -2 30.5t15 25.5l298 296q20 18 46 11l76 -19q20 -5 30.5 -22.5t5.5 -37.5t-22.5 -31t-37.5 -5l-51 12l-182 -193h891l-182 193l-44 -12q-20 -5 -37.5 6t-22.5 31t6 37.5 t31 22.5z" />
-<glyph unicode="&#xe241;" d="M1200 900h-50q0 21 -4 37t-9.5 26.5t-18 17.5t-22 11t-28.5 5.5t-31 2t-37 0.5h-200v-850q0 -22 25 -34.5t50 -13.5l25 -2v-100h-400v100q4 0 11 0.5t24 3t30 7t24 15t11 24.5v850h-200q-25 0 -37 -0.5t-31 -2t-28.5 -5.5t-22 -11t-18 -17.5t-9.5 -26.5t-4 -37h-50v300 h1000v-300zM500 450h-25q0 15 -4 24.5t-9 14.5t-17 7.5t-20 3t-25 0.5h-100v-425q0 -11 12.5 -17.5t25.5 -7.5h12v-50h-200v50q50 0 50 25v425h-100q-17 0 -25 -0.5t-20 -3t-17 -7.5t-9 -14.5t-4 -24.5h-25v150h500v-150z" />
-<glyph unicode="&#xe242;" d="M1000 300v50q-25 0 -55 32q-14 14 -25 31t-16 27l-4 11l-289 747h-69l-300 -754q-18 -35 -39 -56q-9 -9 -24.5 -18.5t-26.5 -14.5l-11 -5v-50h273v50q-49 0 -78.5 21.5t-11.5 67.5l69 176h293l61 -166q13 -34 -3.5 -66.5t-55.5 -32.5v-50h312zM412 691l134 342l121 -342 h-255zM1100 150v-100q0 -21 -14.5 -35.5t-35.5 -14.5h-1000q-21 0 -35.5 14.5t-14.5 35.5v100q0 21 14.5 35.5t35.5 14.5h1000q21 0 35.5 -14.5t14.5 -35.5z" />
-<glyph unicode="&#xe243;" d="M50 1200h1100q21 0 35.5 -14.5t14.5 -35.5v-1100q0 -21 -14.5 -35.5t-35.5 -14.5h-1100q-21 0 -35.5 14.5t-14.5 35.5v1100q0 21 14.5 35.5t35.5 14.5zM611 1118h-70q-13 0 -18 -12l-299 -753q-17 -32 -35 -51q-18 -18 -56 -34q-12 -5 -12 -18v-50q0 -8 5.5 -14t14.5 -6 h273q8 0 14 6t6 14v50q0 8 -6 14t-14 6q-55 0 -71 23q-10 14 0 39l63 163h266l57 -153q11 -31 -6 -55q-12 -17 -36 -17q-8 0 -14 -6t-6 -14v-50q0 -8 6 -14t14 -6h313q8 0 14 6t6 14v50q0 7 -5.5 13t-13.5 7q-17 0 -42 25q-25 27 -40 63h-1l-288 748q-5 12 -19 12zM639 611 h-197l103 264z" />
-<glyph unicode="&#xe244;" d="M1200 1100h-1200v100h1200v-100zM50 1000h400q21 0 35.5 -14.5t14.5 -35.5v-900q0 -21 -14.5 -35.5t-35.5 -14.5h-400q-21 0 -35.5 14.5t-14.5 35.5v900q0 21 14.5 35.5t35.5 14.5zM650 1000h400q21 0 35.5 -14.5t14.5 -35.5v-400q0 -21 -14.5 -35.5t-35.5 -14.5h-400 q-21 0 -35.5 14.5t-14.5 35.5v400q0 21 14.5 35.5t35.5 14.5zM700 900v-300h300v300h-300z" />
-<glyph unicode="&#xe245;" d="M50 1200h400q21 0 35.5 -14.5t14.5 -35.5v-900q0 -21 -14.5 -35.5t-35.5 -14.5h-400q-21 0 -35.5 14.5t-14.5 35.5v900q0 21 14.5 35.5t35.5 14.5zM650 700h400q21 0 35.5 -14.5t14.5 -35.5v-400q0 -21 -14.5 -35.5t-35.5 -14.5h-400q-21 0 -35.5 14.5t-14.5 35.5v400 q0 21 14.5 35.5t35.5 14.5zM700 600v-300h300v300h-300zM1200 0h-1200v100h1200v-100z" />
-<glyph unicode="&#xe246;" d="M50 1000h400q21 0 35.5 -14.5t14.5 -35.5v-350h100v150q0 21 14.5 35.5t35.5 14.5h400q21 0 35.5 -14.5t14.5 -35.5v-150h100v-100h-100v-150q0 -21 -14.5 -35.5t-35.5 -14.5h-400q-21 0 -35.5 14.5t-14.5 35.5v150h-100v-350q0 -21 -14.5 -35.5t-35.5 -14.5h-400 q-21 0 -35.5 14.5t-14.5 35.5v800q0 21 14.5 35.5t35.5 14.5zM700 700v-300h300v300h-300z" />
-<glyph unicode="&#xe247;" d="M100 0h-100v1200h100v-1200zM250 1100h400q21 0 35.5 -14.5t14.5 -35.5v-400q0 -21 -14.5 -35.5t-35.5 -14.5h-400q-21 0 -35.5 14.5t-14.5 35.5v400q0 21 14.5 35.5t35.5 14.5zM300 1000v-300h300v300h-300zM250 500h900q21 0 35.5 -14.5t14.5 -35.5v-400 q0 -21 -14.5 -35.5t-35.5 -14.5h-900q-21 0 -35.5 14.5t-14.5 35.5v400q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe248;" d="M600 1100h150q21 0 35.5 -14.5t14.5 -35.5v-400q0 -21 -14.5 -35.5t-35.5 -14.5h-150v-100h450q21 0 35.5 -14.5t14.5 -35.5v-400q0 -21 -14.5 -35.5t-35.5 -14.5h-900q-21 0 -35.5 14.5t-14.5 35.5v400q0 21 14.5 35.5t35.5 14.5h350v100h-150q-21 0 -35.5 14.5 t-14.5 35.5v400q0 21 14.5 35.5t35.5 14.5h150v100h100v-100zM400 1000v-300h300v300h-300z" />
-<glyph unicode="&#xe249;" d="M1200 0h-100v1200h100v-1200zM550 1100h400q21 0 35.5 -14.5t14.5 -35.5v-400q0 -21 -14.5 -35.5t-35.5 -14.5h-400q-21 0 -35.5 14.5t-14.5 35.5v400q0 21 14.5 35.5t35.5 14.5zM600 1000v-300h300v300h-300zM50 500h900q21 0 35.5 -14.5t14.5 -35.5v-400 q0 -21 -14.5 -35.5t-35.5 -14.5h-900q-21 0 -35.5 14.5t-14.5 35.5v400q0 21 14.5 35.5t35.5 14.5z" />
-<glyph unicode="&#xe250;" d="M865 565l-494 -494q-23 -23 -41 -23q-14 0 -22 13.5t-8 38.5v1000q0 25 8 38.5t22 13.5q18 0 41 -23l494 -494q14 -14 14 -35t-14 -35z" />
-<glyph unicode="&#xe251;" d="M335 635l494 494q29 29 50 20.5t21 -49.5v-1000q0 -41 -21 -49.5t-50 20.5l-494 494q-14 14 -14 35t14 35z" />
-<glyph unicode="&#xe252;" d="M100 900h1000q41 0 49.5 -21t-20.5 -50l-494 -494q-14 -14 -35 -14t-35 14l-494 494q-29 29 -20.5 50t49.5 21z" />
-<glyph unicode="&#xe253;" d="M635 865l494 -494q29 -29 20.5 -50t-49.5 -21h-1000q-41 0 -49.5 21t20.5 50l494 494q14 14 35 14t35 -14z" />
-<glyph unicode="&#xe254;" d="M700 741v-182l-692 -323v221l413 193l-413 193v221zM1200 0h-800v200h800v-200z" />
-<glyph unicode="&#xe255;" d="M1200 900h-200v-100h200v-100h-300v300h200v100h-200v100h300v-300zM0 700h50q0 21 4 37t9.5 26.5t18 17.5t22 11t28.5 5.5t31 2t37 0.5h100v-550q0 -22 -25 -34.5t-50 -13.5l-25 -2v-100h400v100q-4 0 -11 0.5t-24 3t-30 7t-24 15t-11 24.5v550h100q25 0 37 -0.5t31 -2 t28.5 -5.5t22 -11t18 -17.5t9.5 -26.5t4 -37h50v300h-800v-300z" />
-<glyph unicode="&#xe256;" d="M800 700h-50q0 21 -4 37t-9.5 26.5t-18 17.5t-22 11t-28.5 5.5t-31 2t-37 0.5h-100v-550q0 -22 25 -34.5t50 -14.5l25 -1v-100h-400v100q4 0 11 0.5t24 3t30 7t24 15t11 24.5v550h-100q-25 0 -37 -0.5t-31 -2t-28.5 -5.5t-22 -11t-18 -17.5t-9.5 -26.5t-4 -37h-50v300 h800v-300zM1100 200h-200v-100h200v-100h-300v300h200v100h-200v100h300v-300z" />
-<glyph unicode="&#xe257;" d="M701 1098h160q16 0 21 -11t-7 -23l-464 -464l464 -464q12 -12 7 -23t-21 -11h-160q-13 0 -23 9l-471 471q-7 8 -7 18t7 18l471 471q10 9 23 9z" />
-<glyph unicode="&#xe258;" d="M339 1098h160q13 0 23 -9l471 -471q7 -8 7 -18t-7 -18l-471 -471q-10 -9 -23 -9h-160q-16 0 -21 11t7 23l464 464l-464 464q-12 12 -7 23t21 11z" />
-<glyph unicode="&#xe259;" d="M1087 882q11 -5 11 -21v-160q0 -13 -9 -23l-471 -471q-8 -7 -18 -7t-18 7l-471 471q-9 10 -9 23v160q0 16 11 21t23 -7l464 -464l464 464q12 12 23 7z" />
-<glyph unicode="&#xe260;" d="M618 993l471 -471q9 -10 9 -23v-160q0 -16 -11 -21t-23 7l-464 464l-464 -464q-12 -12 -23 -7t-11 21v160q0 13 9 23l471 471q8 7 18 7t18 -7z" />
-<glyph unicode="&#xf8ff;" d="M1000 1200q0 -124 -88 -212t-212 -88q0 124 88 212t212 88zM450 1000h100q21 0 40 -14t26 -33l79 -194q5 1 16 3q34 6 54 9.5t60 7t65.5 1t61 -10t56.5 -23t42.5 -42t29 -64t5 -92t-19.5 -121.5q-1 -7 -3 -19.5t-11 -50t-20.5 -73t-32.5 -81.5t-46.5 -83t-64 -70 t-82.5 -50q-13 -5 -42 -5t-65.5 2.5t-47.5 2.5q-14 0 -49.5 -3.5t-63 -3.5t-43.5 7q-57 25 -104.5 78.5t-75 111.5t-46.5 112t-26 90l-7 35q-15 63 -18 115t4.5 88.5t26 64t39.5 43.5t52 25.5t58.5 13t62.5 2t59.5 -4.5t55.5 -8l-147 192q-12 18 -5.5 30t27.5 12z" />
-<glyph unicode="&#x1f511;" d="M250 1200h600q21 0 35.5 -14.5t14.5 -35.5v-400q0 -21 -14.5 -35.5t-35.5 -14.5h-150v-500l-255 -178q-19 -9 -32 -1t-13 29v650h-150q-21 0 -35.5 14.5t-14.5 35.5v400q0 21 14.5 35.5t35.5 14.5zM400 1100v-100h300v100h-300z" />
-<glyph unicode="&#x1f6aa;" d="M250 1200h750q39 0 69.5 -40.5t30.5 -84.5v-933l-700 -117v950l600 125h-700v-1000h-100v1025q0 23 15.5 49t34.5 26zM500 525v-100l100 20v100z" />
-</font>
-</defs></svg> \ No newline at end of file
diff --git a/library/bootstrap/fonts/glyphicons-halflings-regular.ttf b/library/bootstrap/fonts/glyphicons-halflings-regular.ttf
deleted file mode 100644
index 1413fc609..000000000
--- a/library/bootstrap/fonts/glyphicons-halflings-regular.ttf
+++ /dev/null
Binary files differ
diff --git a/library/bootstrap/fonts/glyphicons-halflings-regular.woff b/library/bootstrap/fonts/glyphicons-halflings-regular.woff
deleted file mode 100644
index 9e612858f..000000000
--- a/library/bootstrap/fonts/glyphicons-halflings-regular.woff
+++ /dev/null
Binary files differ
diff --git a/library/bootstrap/fonts/glyphicons-halflings-regular.woff2 b/library/bootstrap/fonts/glyphicons-halflings-regular.woff2
deleted file mode 100644
index 64539b54c..000000000
--- a/library/bootstrap/fonts/glyphicons-halflings-regular.woff2
+++ /dev/null
Binary files differ
diff --git a/library/bootstrap/js/bootstrap.js b/library/bootstrap/js/bootstrap.js
index 8a2e99a53..7597fb328 100644
--- a/library/bootstrap/js/bootstrap.js
+++ b/library/bootstrap/js/bootstrap.js
@@ -1,2377 +1,3831 @@
/*!
- * Bootstrap v3.3.7 (http://getbootstrap.com)
- * Copyright 2011-2016 Twitter, Inc.
- * Licensed under the MIT license
+ * Bootstrap v4.0.0-beta (https://getbootstrap.com)
+ * Copyright 2011-2017 The Bootstrap Authors (https://github.com/twbs/bootstrap/graphs/contributors)
+ * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
*/
if (typeof jQuery === 'undefined') {
- throw new Error('Bootstrap\'s JavaScript requires jQuery')
+ throw new Error('Bootstrap\'s JavaScript requires jQuery. jQuery must be included before Bootstrap\'s JavaScript.')
}
-+function ($) {
- 'use strict';
+(function ($) {
var version = $.fn.jquery.split(' ')[0].split('.')
- if ((version[0] < 2 && version[1] < 9) || (version[0] == 1 && version[1] == 9 && version[2] < 1) || (version[0] > 3)) {
- throw new Error('Bootstrap\'s JavaScript requires jQuery version 1.9.1 or higher, but lower than version 4')
+ if ((version[0] < 2 && version[1] < 9) || (version[0] == 1 && version[1] == 9 && version[2] < 1) || (version[0] >= 4)) {
+ throw new Error('Bootstrap\'s JavaScript requires at least jQuery v1.9.1 but less than v4.0.0')
}
-}(jQuery);
+})(jQuery);
+
+(function () {
+var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };
+
+var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
+
+function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-/* ========================================================================
- * Bootstrap: transition.js v3.3.7
- * http://getbootstrap.com/javascript/#transitions
- * ========================================================================
- * Copyright 2011-2016 Twitter, Inc.
+function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
+
+function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
+
+/**
+ * --------------------------------------------------------------------------
+ * Bootstrap (v4.0.0-beta): util.js
* Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
- * ======================================================================== */
+ * --------------------------------------------------------------------------
+ */
+var Util = function ($) {
-+function ($) {
- 'use strict';
+ /**
+ * ------------------------------------------------------------------------
+ * Private TransitionEnd Helpers
+ * ------------------------------------------------------------------------
+ */
- // CSS TRANSITION SUPPORT (Shoutout: http://www.modernizr.com/)
- // ============================================================
+ var transition = false;
- function transitionEnd() {
- var el = document.createElement('bootstrap')
+ var MAX_UID = 1000000;
- var transEndEventNames = {
- WebkitTransition : 'webkitTransitionEnd',
- MozTransition : 'transitionend',
- OTransition : 'oTransitionEnd otransitionend',
- transition : 'transitionend'
- }
+ var TransitionEndEvent = {
+ WebkitTransition: 'webkitTransitionEnd',
+ MozTransition: 'transitionend',
+ OTransition: 'oTransitionEnd otransitionend',
+ transition: 'transitionend'
- for (var name in transEndEventNames) {
- if (el.style[name] !== undefined) {
- return { end: transEndEventNames[name] }
- }
- }
+ // shoutout AngusCroll (https://goo.gl/pxwQGp)
+ };function toType(obj) {
+ return {}.toString.call(obj).match(/\s([a-zA-Z]+)/)[1].toLowerCase();
+ }
- return false // explicit for ie8 ( ._.)
+ function isElement(obj) {
+ return (obj[0] || obj).nodeType;
}
- // http://blog.alexmaccaw.com/css-transitions
- $.fn.emulateTransitionEnd = function (duration) {
- var called = false
- var $el = this
- $(this).one('bsTransitionEnd', function () { called = true })
- var callback = function () { if (!called) $($el).trigger($.support.transition.end) }
- setTimeout(callback, duration)
- return this
+ function getSpecialTransitionEndEvent() {
+ return {
+ bindType: transition.end,
+ delegateType: transition.end,
+ handle: function handle(event) {
+ if ($(event.target).is(this)) {
+ return event.handleObj.handler.apply(this, arguments); // eslint-disable-line prefer-rest-params
+ }
+ return undefined;
+ }
+ };
}
- $(function () {
- $.support.transition = transitionEnd()
+ function transitionEndTest() {
+ if (window.QUnit) {
+ return false;
+ }
- if (!$.support.transition) return
+ var el = document.createElement('bootstrap');
- $.event.special.bsTransitionEnd = {
- bindType: $.support.transition.end,
- delegateType: $.support.transition.end,
- handle: function (e) {
- if ($(e.target).is(this)) return e.handleObj.handler.apply(this, arguments)
+ for (var name in TransitionEndEvent) {
+ if (el.style[name] !== undefined) {
+ return {
+ end: TransitionEndEvent[name]
+ };
}
}
- })
-}(jQuery);
+ return false;
+ }
-/* ========================================================================
- * Bootstrap: alert.js v3.3.7
- * http://getbootstrap.com/javascript/#alerts
- * ========================================================================
- * Copyright 2011-2016 Twitter, Inc.
- * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
- * ======================================================================== */
+ function transitionEndEmulator(duration) {
+ var _this = this;
+ var called = false;
-+function ($) {
- 'use strict';
+ $(this).one(Util.TRANSITION_END, function () {
+ called = true;
+ });
- // ALERT CLASS DEFINITION
- // ======================
+ setTimeout(function () {
+ if (!called) {
+ Util.triggerTransitionEnd(_this);
+ }
+ }, duration);
- var dismiss = '[data-dismiss="alert"]'
- var Alert = function (el) {
- $(el).on('click', dismiss, this.close)
+ return this;
}
- Alert.VERSION = '3.3.7'
+ function setTransitionEndSupport() {
+ transition = transitionEndTest();
- Alert.TRANSITION_DURATION = 150
+ $.fn.emulateTransitionEnd = transitionEndEmulator;
- Alert.prototype.close = function (e) {
- var $this = $(this)
- var selector = $this.attr('data-target')
-
- if (!selector) {
- selector = $this.attr('href')
- selector = selector && selector.replace(/.*(?=#[^\s]*$)/, '') // strip for ie7
+ if (Util.supportsTransitionEnd()) {
+ $.event.special[Util.TRANSITION_END] = getSpecialTransitionEndEvent();
}
+ }
- var $parent = $(selector === '#' ? [] : selector)
+ /**
+ * --------------------------------------------------------------------------
+ * Public Util Api
+ * --------------------------------------------------------------------------
+ */
- if (e) e.preventDefault()
+ var Util = {
- if (!$parent.length) {
- $parent = $this.closest('.alert')
+ TRANSITION_END: 'bsTransitionEnd',
+
+ getUID: function getUID(prefix) {
+ do {
+ // eslint-disable-next-line no-bitwise
+ prefix += ~~(Math.random() * MAX_UID); // "~~" acts like a faster Math.floor() here
+ } while (document.getElementById(prefix));
+ return prefix;
+ },
+ getSelectorFromElement: function getSelectorFromElement(element) {
+ var selector = element.getAttribute('data-target');
+ if (!selector || selector === '#') {
+ selector = element.getAttribute('href') || '';
+ }
+
+ try {
+ var $selector = $(selector);
+ return $selector.length > 0 ? selector : null;
+ } catch (error) {
+ return null;
+ }
+ },
+ reflow: function reflow(element) {
+ return element.offsetHeight;
+ },
+ triggerTransitionEnd: function triggerTransitionEnd(element) {
+ $(element).trigger(transition.end);
+ },
+ supportsTransitionEnd: function supportsTransitionEnd() {
+ return Boolean(transition);
+ },
+ typeCheckConfig: function typeCheckConfig(componentName, config, configTypes) {
+ for (var property in configTypes) {
+ if (configTypes.hasOwnProperty(property)) {
+ var expectedTypes = configTypes[property];
+ var value = config[property];
+ var valueType = value && isElement(value) ? 'element' : toType(value);
+
+ if (!new RegExp(expectedTypes).test(valueType)) {
+ throw new Error(componentName.toUpperCase() + ': ' + ('Option "' + property + '" provided type "' + valueType + '" ') + ('but expected type "' + expectedTypes + '".'));
+ }
+ }
+ }
}
+ };
- $parent.trigger(e = $.Event('close.bs.alert'))
+ setTransitionEndSupport();
- if (e.isDefaultPrevented()) return
+ return Util;
+}(jQuery);
- $parent.removeClass('in')
+/**
+ * --------------------------------------------------------------------------
+ * Bootstrap (v4.0.0-beta): alert.js
+ * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
+ * --------------------------------------------------------------------------
+ */
- function removeElement() {
- // detach from parent, fire event then clean up data
- $parent.detach().trigger('closed.bs.alert').remove()
+var Alert = function ($) {
+
+ /**
+ * ------------------------------------------------------------------------
+ * Constants
+ * ------------------------------------------------------------------------
+ */
+
+ var NAME = 'alert';
+ var VERSION = '4.0.0-beta';
+ var DATA_KEY = 'bs.alert';
+ var EVENT_KEY = '.' + DATA_KEY;
+ var DATA_API_KEY = '.data-api';
+ var JQUERY_NO_CONFLICT = $.fn[NAME];
+ var TRANSITION_DURATION = 150;
+
+ var Selector = {
+ DISMISS: '[data-dismiss="alert"]'
+ };
+
+ var Event = {
+ CLOSE: 'close' + EVENT_KEY,
+ CLOSED: 'closed' + EVENT_KEY,
+ CLICK_DATA_API: 'click' + EVENT_KEY + DATA_API_KEY
+ };
+
+ var ClassName = {
+ ALERT: 'alert',
+ FADE: 'fade',
+ SHOW: 'show'
+
+ /**
+ * ------------------------------------------------------------------------
+ * Class Definition
+ * ------------------------------------------------------------------------
+ */
+
+ };
+ var Alert = function () {
+ function Alert(element) {
+ _classCallCheck(this, Alert);
+
+ this._element = element;
}
- $.support.transition && $parent.hasClass('fade') ?
- $parent
- .one('bsTransitionEnd', removeElement)
- .emulateTransitionEnd(Alert.TRANSITION_DURATION) :
- removeElement()
- }
+ // getters
+ // public
- // ALERT PLUGIN DEFINITION
- // =======================
+ Alert.prototype.close = function close(element) {
+ element = element || this._element;
- function Plugin(option) {
- return this.each(function () {
- var $this = $(this)
- var data = $this.data('bs.alert')
+ var rootElement = this._getRootElement(element);
+ var customEvent = this._triggerCloseEvent(rootElement);
- if (!data) $this.data('bs.alert', (data = new Alert(this)))
- if (typeof option == 'string') data[option].call($this)
- })
- }
+ if (customEvent.isDefaultPrevented()) {
+ return;
+ }
- var old = $.fn.alert
+ this._removeElement(rootElement);
+ };
- $.fn.alert = Plugin
- $.fn.alert.Constructor = Alert
+ Alert.prototype.dispose = function dispose() {
+ $.removeData(this._element, DATA_KEY);
+ this._element = null;
+ };
+ // private
- // ALERT NO CONFLICT
- // =================
+ Alert.prototype._getRootElement = function _getRootElement(element) {
+ var selector = Util.getSelectorFromElement(element);
+ var parent = false;
- $.fn.alert.noConflict = function () {
- $.fn.alert = old
- return this
- }
+ if (selector) {
+ parent = $(selector)[0];
+ }
+ if (!parent) {
+ parent = $(element).closest('.' + ClassName.ALERT)[0];
+ }
- // ALERT DATA-API
- // ==============
+ return parent;
+ };
- $(document).on('click.bs.alert.data-api', dismiss, Alert.prototype.close)
+ Alert.prototype._triggerCloseEvent = function _triggerCloseEvent(element) {
+ var closeEvent = $.Event(Event.CLOSE);
-}(jQuery);
+ $(element).trigger(closeEvent);
+ return closeEvent;
+ };
-/* ========================================================================
- * Bootstrap: button.js v3.3.7
- * http://getbootstrap.com/javascript/#buttons
- * ========================================================================
- * Copyright 2011-2016 Twitter, Inc.
- * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
- * ======================================================================== */
+ Alert.prototype._removeElement = function _removeElement(element) {
+ var _this2 = this;
+ $(element).removeClass(ClassName.SHOW);
-+function ($) {
- 'use strict';
+ if (!Util.supportsTransitionEnd() || !$(element).hasClass(ClassName.FADE)) {
+ this._destroyElement(element);
+ return;
+ }
- // BUTTON PUBLIC CLASS DEFINITION
- // ==============================
+ $(element).one(Util.TRANSITION_END, function (event) {
+ return _this2._destroyElement(element, event);
+ }).emulateTransitionEnd(TRANSITION_DURATION);
+ };
- var Button = function (element, options) {
- this.$element = $(element)
- this.options = $.extend({}, Button.DEFAULTS, options)
- this.isLoading = false
- }
+ Alert.prototype._destroyElement = function _destroyElement(element) {
+ $(element).detach().trigger(Event.CLOSED).remove();
+ };
- Button.VERSION = '3.3.7'
+ // static
- Button.DEFAULTS = {
- loadingText: 'loading...'
- }
+ Alert._jQueryInterface = function _jQueryInterface(config) {
+ return this.each(function () {
+ var $element = $(this);
+ var data = $element.data(DATA_KEY);
- Button.prototype.setState = function (state) {
- var d = 'disabled'
- var $el = this.$element
- var val = $el.is('input') ? 'val' : 'html'
- var data = $el.data()
+ if (!data) {
+ data = new Alert(this);
+ $element.data(DATA_KEY, data);
+ }
- state += 'Text'
+ if (config === 'close') {
+ data[config](this);
+ }
+ });
+ };
- if (data.resetText == null) $el.data('resetText', $el[val]())
+ Alert._handleDismiss = function _handleDismiss(alertInstance) {
+ return function (event) {
+ if (event) {
+ event.preventDefault();
+ }
- // push to event loop to allow forms to submit
- setTimeout($.proxy(function () {
- $el[val](data[state] == null ? this.options[state] : data[state])
+ alertInstance.close(this);
+ };
+ };
- if (state == 'loadingText') {
- this.isLoading = true
- $el.addClass(d).attr(d, d).prop(d, true)
- } else if (this.isLoading) {
- this.isLoading = false
- $el.removeClass(d).removeAttr(d).prop(d, false)
+ _createClass(Alert, null, [{
+ key: 'VERSION',
+ get: function get() {
+ return VERSION;
}
- }, this), 0)
- }
+ }]);
- Button.prototype.toggle = function () {
- var changed = true
- var $parent = this.$element.closest('[data-toggle="buttons"]')
-
- if ($parent.length) {
- var $input = this.$element.find('input')
- if ($input.prop('type') == 'radio') {
- if ($input.prop('checked')) changed = false
- $parent.find('.active').removeClass('active')
- this.$element.addClass('active')
- } else if ($input.prop('type') == 'checkbox') {
- if (($input.prop('checked')) !== this.$element.hasClass('active')) changed = false
- this.$element.toggleClass('active')
- }
- $input.prop('checked', this.$element.hasClass('active'))
- if (changed) $input.trigger('change')
- } else {
- this.$element.attr('aria-pressed', !this.$element.hasClass('active'))
- this.$element.toggleClass('active')
- }
- }
+ return Alert;
+ }();
+ /**
+ * ------------------------------------------------------------------------
+ * Data Api implementation
+ * ------------------------------------------------------------------------
+ */
- // BUTTON PLUGIN DEFINITION
- // ========================
+ $(document).on(Event.CLICK_DATA_API, Selector.DISMISS, Alert._handleDismiss(new Alert()));
- function Plugin(option) {
- return this.each(function () {
- var $this = $(this)
- var data = $this.data('bs.button')
- var options = typeof option == 'object' && option
+ /**
+ * ------------------------------------------------------------------------
+ * jQuery
+ * ------------------------------------------------------------------------
+ */
- if (!data) $this.data('bs.button', (data = new Button(this, options)))
+ $.fn[NAME] = Alert._jQueryInterface;
+ $.fn[NAME].Constructor = Alert;
+ $.fn[NAME].noConflict = function () {
+ $.fn[NAME] = JQUERY_NO_CONFLICT;
+ return Alert._jQueryInterface;
+ };
- if (option == 'toggle') data.toggle()
- else if (option) data.setState(option)
- })
- }
+ return Alert;
+}(jQuery);
- var old = $.fn.button
+/**
+ * --------------------------------------------------------------------------
+ * Bootstrap (v4.0.0-beta): button.js
+ * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
+ * --------------------------------------------------------------------------
+ */
- $.fn.button = Plugin
- $.fn.button.Constructor = Button
+var Button = function ($) {
+
+ /**
+ * ------------------------------------------------------------------------
+ * Constants
+ * ------------------------------------------------------------------------
+ */
+
+ var NAME = 'button';
+ var VERSION = '4.0.0-beta';
+ var DATA_KEY = 'bs.button';
+ var EVENT_KEY = '.' + DATA_KEY;
+ var DATA_API_KEY = '.data-api';
+ var JQUERY_NO_CONFLICT = $.fn[NAME];
+
+ var ClassName = {
+ ACTIVE: 'active',
+ BUTTON: 'btn',
+ FOCUS: 'focus'
+ };
+
+ var Selector = {
+ DATA_TOGGLE_CARROT: '[data-toggle^="button"]',
+ DATA_TOGGLE: '[data-toggle="buttons"]',
+ INPUT: 'input',
+ ACTIVE: '.active',
+ BUTTON: '.btn'
+ };
+
+ var Event = {
+ CLICK_DATA_API: 'click' + EVENT_KEY + DATA_API_KEY,
+ FOCUS_BLUR_DATA_API: 'focus' + EVENT_KEY + DATA_API_KEY + ' ' + ('blur' + EVENT_KEY + DATA_API_KEY)
+
+ /**
+ * ------------------------------------------------------------------------
+ * Class Definition
+ * ------------------------------------------------------------------------
+ */
+
+ };
+ var Button = function () {
+ function Button(element) {
+ _classCallCheck(this, Button);
+
+ this._element = element;
+ }
+ // getters
+
+ // public
+
+ Button.prototype.toggle = function toggle() {
+ var triggerChangeEvent = true;
+ var addAriaPressed = true;
+ var rootElement = $(this._element).closest(Selector.DATA_TOGGLE)[0];
+
+ if (rootElement) {
+ var input = $(this._element).find(Selector.INPUT)[0];
+
+ if (input) {
+ if (input.type === 'radio') {
+ if (input.checked && $(this._element).hasClass(ClassName.ACTIVE)) {
+ triggerChangeEvent = false;
+ } else {
+ var activeElement = $(rootElement).find(Selector.ACTIVE)[0];
+
+ if (activeElement) {
+ $(activeElement).removeClass(ClassName.ACTIVE);
+ }
+ }
+ }
+
+ if (triggerChangeEvent) {
+ if (input.hasAttribute('disabled') || rootElement.hasAttribute('disabled') || input.classList.contains('disabled') || rootElement.classList.contains('disabled')) {
+ return;
+ }
+ input.checked = !$(this._element).hasClass(ClassName.ACTIVE);
+ $(input).trigger('change');
+ }
+
+ input.focus();
+ addAriaPressed = false;
+ }
+ }
- // BUTTON NO CONFLICT
- // ==================
+ if (addAriaPressed) {
+ this._element.setAttribute('aria-pressed', !$(this._element).hasClass(ClassName.ACTIVE));
+ }
- $.fn.button.noConflict = function () {
- $.fn.button = old
- return this
- }
+ if (triggerChangeEvent) {
+ $(this._element).toggleClass(ClassName.ACTIVE);
+ }
+ };
+ Button.prototype.dispose = function dispose() {
+ $.removeData(this._element, DATA_KEY);
+ this._element = null;
+ };
- // BUTTON DATA-API
- // ===============
+ // static
- $(document)
- .on('click.bs.button.data-api', '[data-toggle^="button"]', function (e) {
- var $btn = $(e.target).closest('.btn')
- Plugin.call($btn, 'toggle')
- if (!($(e.target).is('input[type="radio"], input[type="checkbox"]'))) {
- // Prevent double click on radios, and the double selections (so cancellation) on checkboxes
- e.preventDefault()
- // The target component still receive the focus
- if ($btn.is('input,button')) $btn.trigger('focus')
- else $btn.find('input:visible,button:visible').first().trigger('focus')
- }
- })
- .on('focus.bs.button.data-api blur.bs.button.data-api', '[data-toggle^="button"]', function (e) {
- $(e.target).closest('.btn').toggleClass('focus', /^focus(in)?$/.test(e.type))
- })
+ Button._jQueryInterface = function _jQueryInterface(config) {
+ return this.each(function () {
+ var data = $(this).data(DATA_KEY);
-}(jQuery);
+ if (!data) {
+ data = new Button(this);
+ $(this).data(DATA_KEY, data);
+ }
-/* ========================================================================
- * Bootstrap: carousel.js v3.3.7
- * http://getbootstrap.com/javascript/#carousel
- * ========================================================================
- * Copyright 2011-2016 Twitter, Inc.
- * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
- * ======================================================================== */
+ if (config === 'toggle') {
+ data[config]();
+ }
+ });
+ };
+ _createClass(Button, null, [{
+ key: 'VERSION',
+ get: function get() {
+ return VERSION;
+ }
+ }]);
-+function ($) {
- 'use strict';
+ return Button;
+ }();
- // CAROUSEL CLASS DEFINITION
- // =========================
+ /**
+ * ------------------------------------------------------------------------
+ * Data Api implementation
+ * ------------------------------------------------------------------------
+ */
- var Carousel = function (element, options) {
- this.$element = $(element)
- this.$indicators = this.$element.find('.carousel-indicators')
- this.options = options
- this.paused = null
- this.sliding = null
- this.interval = null
- this.$active = null
- this.$items = null
+ $(document).on(Event.CLICK_DATA_API, Selector.DATA_TOGGLE_CARROT, function (event) {
+ event.preventDefault();
- this.options.keyboard && this.$element.on('keydown.bs.carousel', $.proxy(this.keydown, this))
+ var button = event.target;
- this.options.pause == 'hover' && !('ontouchstart' in document.documentElement) && this.$element
- .on('mouseenter.bs.carousel', $.proxy(this.pause, this))
- .on('mouseleave.bs.carousel', $.proxy(this.cycle, this))
- }
+ if (!$(button).hasClass(ClassName.BUTTON)) {
+ button = $(button).closest(Selector.BUTTON);
+ }
- Carousel.VERSION = '3.3.7'
+ Button._jQueryInterface.call($(button), 'toggle');
+ }).on(Event.FOCUS_BLUR_DATA_API, Selector.DATA_TOGGLE_CARROT, function (event) {
+ var button = $(event.target).closest(Selector.BUTTON)[0];
+ $(button).toggleClass(ClassName.FOCUS, /^focus(in)?$/.test(event.type));
+ });
+
+ /**
+ * ------------------------------------------------------------------------
+ * jQuery
+ * ------------------------------------------------------------------------
+ */
+
+ $.fn[NAME] = Button._jQueryInterface;
+ $.fn[NAME].Constructor = Button;
+ $.fn[NAME].noConflict = function () {
+ $.fn[NAME] = JQUERY_NO_CONFLICT;
+ return Button._jQueryInterface;
+ };
+
+ return Button;
+}(jQuery);
- Carousel.TRANSITION_DURATION = 600
+/**
+ * --------------------------------------------------------------------------
+ * Bootstrap (v4.0.0-beta): carousel.js
+ * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
+ * --------------------------------------------------------------------------
+ */
- Carousel.DEFAULTS = {
+var Carousel = function ($) {
+
+ /**
+ * ------------------------------------------------------------------------
+ * Constants
+ * ------------------------------------------------------------------------
+ */
+
+ var NAME = 'carousel';
+ var VERSION = '4.0.0-beta';
+ var DATA_KEY = 'bs.carousel';
+ var EVENT_KEY = '.' + DATA_KEY;
+ var DATA_API_KEY = '.data-api';
+ var JQUERY_NO_CONFLICT = $.fn[NAME];
+ var TRANSITION_DURATION = 600;
+ var ARROW_LEFT_KEYCODE = 37; // KeyboardEvent.which value for left arrow key
+ var ARROW_RIGHT_KEYCODE = 39; // KeyboardEvent.which value for right arrow key
+ var TOUCHEVENT_COMPAT_WAIT = 500; // Time for mouse compat events to fire after touch
+
+ var Default = {
interval: 5000,
+ keyboard: true,
+ slide: false,
pause: 'hover',
- wrap: true,
- keyboard: true
- }
-
- Carousel.prototype.keydown = function (e) {
- if (/input|textarea/i.test(e.target.tagName)) return
- switch (e.which) {
- case 37: this.prev(); break
- case 39: this.next(); break
- default: return
+ wrap: true
+ };
+
+ var DefaultType = {
+ interval: '(number|boolean)',
+ keyboard: 'boolean',
+ slide: '(boolean|string)',
+ pause: '(string|boolean)',
+ wrap: 'boolean'
+ };
+
+ var Direction = {
+ NEXT: 'next',
+ PREV: 'prev',
+ LEFT: 'left',
+ RIGHT: 'right'
+ };
+
+ var Event = {
+ SLIDE: 'slide' + EVENT_KEY,
+ SLID: 'slid' + EVENT_KEY,
+ KEYDOWN: 'keydown' + EVENT_KEY,
+ MOUSEENTER: 'mouseenter' + EVENT_KEY,
+ MOUSELEAVE: 'mouseleave' + EVENT_KEY,
+ TOUCHEND: 'touchend' + EVENT_KEY,
+ LOAD_DATA_API: 'load' + EVENT_KEY + DATA_API_KEY,
+ CLICK_DATA_API: 'click' + EVENT_KEY + DATA_API_KEY
+ };
+
+ var ClassName = {
+ CAROUSEL: 'carousel',
+ ACTIVE: 'active',
+ SLIDE: 'slide',
+ RIGHT: 'carousel-item-right',
+ LEFT: 'carousel-item-left',
+ NEXT: 'carousel-item-next',
+ PREV: 'carousel-item-prev',
+ ITEM: 'carousel-item'
+ };
+
+ var Selector = {
+ ACTIVE: '.active',
+ ACTIVE_ITEM: '.active.carousel-item',
+ ITEM: '.carousel-item',
+ NEXT_PREV: '.carousel-item-next, .carousel-item-prev',
+ INDICATORS: '.carousel-indicators',
+ DATA_SLIDE: '[data-slide], [data-slide-to]',
+ DATA_RIDE: '[data-ride="carousel"]'
+
+ /**
+ * ------------------------------------------------------------------------
+ * Class Definition
+ * ------------------------------------------------------------------------
+ */
+
+ };
+ var Carousel = function () {
+ function Carousel(element, config) {
+ _classCallCheck(this, Carousel);
+
+ this._items = null;
+ this._interval = null;
+ this._activeElement = null;
+
+ this._isPaused = false;
+ this._isSliding = false;
+
+ this.touchTimeout = null;
+
+ this._config = this._getConfig(config);
+ this._element = $(element)[0];
+ this._indicatorsElement = $(this._element).find(Selector.INDICATORS)[0];
+
+ this._addEventListeners();
}
- e.preventDefault()
- }
+ // getters
- Carousel.prototype.cycle = function (e) {
- e || (this.paused = false)
+ // public
- this.interval && clearInterval(this.interval)
+ Carousel.prototype.next = function next() {
+ if (!this._isSliding) {
+ this._slide(Direction.NEXT);
+ }
+ };
- this.options.interval
- && !this.paused
- && (this.interval = setInterval($.proxy(this.next, this), this.options.interval))
+ Carousel.prototype.nextWhenVisible = function nextWhenVisible() {
+ // Don't call next when the page isn't visible
+ if (!document.hidden) {
+ this.next();
+ }
+ };
- return this
- }
+ Carousel.prototype.prev = function prev() {
+ if (!this._isSliding) {
+ this._slide(Direction.PREV);
+ }
+ };
- Carousel.prototype.getItemIndex = function (item) {
- this.$items = item.parent().children('.item')
- return this.$items.index(item || this.$active)
- }
+ Carousel.prototype.pause = function pause(event) {
+ if (!event) {
+ this._isPaused = true;
+ }
- Carousel.prototype.getItemForDirection = function (direction, active) {
- var activeIndex = this.getItemIndex(active)
- var willWrap = (direction == 'prev' && activeIndex === 0)
- || (direction == 'next' && activeIndex == (this.$items.length - 1))
- if (willWrap && !this.options.wrap) return active
- var delta = direction == 'prev' ? -1 : 1
- var itemIndex = (activeIndex + delta) % this.$items.length
- return this.$items.eq(itemIndex)
- }
+ if ($(this._element).find(Selector.NEXT_PREV)[0] && Util.supportsTransitionEnd()) {
+ Util.triggerTransitionEnd(this._element);
+ this.cycle(true);
+ }
- Carousel.prototype.to = function (pos) {
- var that = this
- var activeIndex = this.getItemIndex(this.$active = this.$element.find('.item.active'))
+ clearInterval(this._interval);
+ this._interval = null;
+ };
- if (pos > (this.$items.length - 1) || pos < 0) return
+ Carousel.prototype.cycle = function cycle(event) {
+ if (!event) {
+ this._isPaused = false;
+ }
- if (this.sliding) return this.$element.one('slid.bs.carousel', function () { that.to(pos) }) // yes, "slid"
- if (activeIndex == pos) return this.pause().cycle()
+ if (this._interval) {
+ clearInterval(this._interval);
+ this._interval = null;
+ }
- return this.slide(pos > activeIndex ? 'next' : 'prev', this.$items.eq(pos))
- }
+ if (this._config.interval && !this._isPaused) {
+ this._interval = setInterval((document.visibilityState ? this.nextWhenVisible : this.next).bind(this), this._config.interval);
+ }
+ };
- Carousel.prototype.pause = function (e) {
- e || (this.paused = true)
+ Carousel.prototype.to = function to(index) {
+ var _this3 = this;
- if (this.$element.find('.next, .prev').length && $.support.transition) {
- this.$element.trigger($.support.transition.end)
- this.cycle(true)
- }
+ this._activeElement = $(this._element).find(Selector.ACTIVE_ITEM)[0];
- this.interval = clearInterval(this.interval)
+ var activeIndex = this._getItemIndex(this._activeElement);
- return this
- }
+ if (index > this._items.length - 1 || index < 0) {
+ return;
+ }
- Carousel.prototype.next = function () {
- if (this.sliding) return
- return this.slide('next')
- }
+ if (this._isSliding) {
+ $(this._element).one(Event.SLID, function () {
+ return _this3.to(index);
+ });
+ return;
+ }
- Carousel.prototype.prev = function () {
- if (this.sliding) return
- return this.slide('prev')
- }
+ if (activeIndex === index) {
+ this.pause();
+ this.cycle();
+ return;
+ }
- Carousel.prototype.slide = function (type, next) {
- var $active = this.$element.find('.item.active')
- var $next = next || this.getItemForDirection(type, $active)
- var isCycling = this.interval
- var direction = type == 'next' ? 'left' : 'right'
- var that = this
+ var direction = index > activeIndex ? Direction.NEXT : Direction.PREV;
- if ($next.hasClass('active')) return (this.sliding = false)
+ this._slide(direction, this._items[index]);
+ };
- var relatedTarget = $next[0]
- var slideEvent = $.Event('slide.bs.carousel', {
- relatedTarget: relatedTarget,
- direction: direction
- })
- this.$element.trigger(slideEvent)
- if (slideEvent.isDefaultPrevented()) return
+ Carousel.prototype.dispose = function dispose() {
+ $(this._element).off(EVENT_KEY);
+ $.removeData(this._element, DATA_KEY);
- this.sliding = true
+ this._items = null;
+ this._config = null;
+ this._element = null;
+ this._interval = null;
+ this._isPaused = null;
+ this._isSliding = null;
+ this._activeElement = null;
+ this._indicatorsElement = null;
+ };
- isCycling && this.pause()
+ // private
- if (this.$indicators.length) {
- this.$indicators.find('.active').removeClass('active')
- var $nextIndicator = $(this.$indicators.children()[this.getItemIndex($next)])
- $nextIndicator && $nextIndicator.addClass('active')
- }
+ Carousel.prototype._getConfig = function _getConfig(config) {
+ config = $.extend({}, Default, config);
+ Util.typeCheckConfig(NAME, config, DefaultType);
+ return config;
+ };
- var slidEvent = $.Event('slid.bs.carousel', { relatedTarget: relatedTarget, direction: direction }) // yes, "slid"
- if ($.support.transition && this.$element.hasClass('slide')) {
- $next.addClass(type)
- $next[0].offsetWidth // force reflow
- $active.addClass(direction)
- $next.addClass(direction)
- $active
- .one('bsTransitionEnd', function () {
- $next.removeClass([type, direction].join(' ')).addClass('active')
- $active.removeClass(['active', direction].join(' '))
- that.sliding = false
- setTimeout(function () {
- that.$element.trigger(slidEvent)
- }, 0)
- })
- .emulateTransitionEnd(Carousel.TRANSITION_DURATION)
- } else {
- $active.removeClass('active')
- $next.addClass('active')
- this.sliding = false
- this.$element.trigger(slidEvent)
- }
+ Carousel.prototype._addEventListeners = function _addEventListeners() {
+ var _this4 = this;
- isCycling && this.cycle()
+ if (this._config.keyboard) {
+ $(this._element).on(Event.KEYDOWN, function (event) {
+ return _this4._keydown(event);
+ });
+ }
- return this
- }
+ if (this._config.pause === 'hover') {
+ $(this._element).on(Event.MOUSEENTER, function (event) {
+ return _this4.pause(event);
+ }).on(Event.MOUSELEAVE, function (event) {
+ return _this4.cycle(event);
+ });
+ if ('ontouchstart' in document.documentElement) {
+ // if it's a touch-enabled device, mouseenter/leave are fired as
+ // part of the mouse compatibility events on first tap - the carousel
+ // would stop cycling until user tapped out of it;
+ // here, we listen for touchend, explicitly pause the carousel
+ // (as if it's the second time we tap on it, mouseenter compat event
+ // is NOT fired) and after a timeout (to allow for mouse compatibility
+ // events to fire) we explicitly restart cycling
+ $(this._element).on(Event.TOUCHEND, function () {
+ _this4.pause();
+ if (_this4.touchTimeout) {
+ clearTimeout(_this4.touchTimeout);
+ }
+ _this4.touchTimeout = setTimeout(function (event) {
+ return _this4.cycle(event);
+ }, TOUCHEVENT_COMPAT_WAIT + _this4._config.interval);
+ });
+ }
+ }
+ };
+ Carousel.prototype._keydown = function _keydown(event) {
+ if (/input|textarea/i.test(event.target.tagName)) {
+ return;
+ }
- // CAROUSEL PLUGIN DEFINITION
- // ==========================
+ switch (event.which) {
+ case ARROW_LEFT_KEYCODE:
+ event.preventDefault();
+ this.prev();
+ break;
+ case ARROW_RIGHT_KEYCODE:
+ event.preventDefault();
+ this.next();
+ break;
+ default:
+ return;
+ }
+ };
+
+ Carousel.prototype._getItemIndex = function _getItemIndex(element) {
+ this._items = $.makeArray($(element).parent().find(Selector.ITEM));
+ return this._items.indexOf(element);
+ };
+
+ Carousel.prototype._getItemByDirection = function _getItemByDirection(direction, activeElement) {
+ var isNextDirection = direction === Direction.NEXT;
+ var isPrevDirection = direction === Direction.PREV;
+ var activeIndex = this._getItemIndex(activeElement);
+ var lastItemIndex = this._items.length - 1;
+ var isGoingToWrap = isPrevDirection && activeIndex === 0 || isNextDirection && activeIndex === lastItemIndex;
+
+ if (isGoingToWrap && !this._config.wrap) {
+ return activeElement;
+ }
- function Plugin(option) {
- return this.each(function () {
- var $this = $(this)
- var data = $this.data('bs.carousel')
- var options = $.extend({}, Carousel.DEFAULTS, $this.data(), typeof option == 'object' && option)
- var action = typeof option == 'string' ? option : options.slide
+ var delta = direction === Direction.PREV ? -1 : 1;
+ var itemIndex = (activeIndex + delta) % this._items.length;
- if (!data) $this.data('bs.carousel', (data = new Carousel(this, options)))
- if (typeof option == 'number') data.to(option)
- else if (action) data[action]()
- else if (options.interval) data.pause().cycle()
- })
- }
+ return itemIndex === -1 ? this._items[this._items.length - 1] : this._items[itemIndex];
+ };
- var old = $.fn.carousel
+ Carousel.prototype._triggerSlideEvent = function _triggerSlideEvent(relatedTarget, eventDirectionName) {
+ var targetIndex = this._getItemIndex(relatedTarget);
+ var fromIndex = this._getItemIndex($(this._element).find(Selector.ACTIVE_ITEM)[0]);
+ var slideEvent = $.Event(Event.SLIDE, {
+ relatedTarget: relatedTarget,
+ direction: eventDirectionName,
+ from: fromIndex,
+ to: targetIndex
+ });
- $.fn.carousel = Plugin
- $.fn.carousel.Constructor = Carousel
+ $(this._element).trigger(slideEvent);
+ return slideEvent;
+ };
- // CAROUSEL NO CONFLICT
- // ====================
+ Carousel.prototype._setActiveIndicatorElement = function _setActiveIndicatorElement(element) {
+ if (this._indicatorsElement) {
+ $(this._indicatorsElement).find(Selector.ACTIVE).removeClass(ClassName.ACTIVE);
- $.fn.carousel.noConflict = function () {
- $.fn.carousel = old
- return this
- }
+ var nextIndicator = this._indicatorsElement.children[this._getItemIndex(element)];
+ if (nextIndicator) {
+ $(nextIndicator).addClass(ClassName.ACTIVE);
+ }
+ }
+ };
- // CAROUSEL DATA-API
- // =================
+ Carousel.prototype._slide = function _slide(direction, element) {
+ var _this5 = this;
- var clickHandler = function (e) {
- var href
- var $this = $(this)
- var $target = $($this.attr('data-target') || (href = $this.attr('href')) && href.replace(/.*(?=#[^\s]+$)/, '')) // strip for ie7
- if (!$target.hasClass('carousel')) return
- var options = $.extend({}, $target.data(), $this.data())
- var slideIndex = $this.attr('data-slide-to')
- if (slideIndex) options.interval = false
+ var activeElement = $(this._element).find(Selector.ACTIVE_ITEM)[0];
+ var activeElementIndex = this._getItemIndex(activeElement);
+ var nextElement = element || activeElement && this._getItemByDirection(direction, activeElement);
+ var nextElementIndex = this._getItemIndex(nextElement);
+ var isCycling = Boolean(this._interval);
- Plugin.call($target, options)
+ var directionalClassName = void 0;
+ var orderClassName = void 0;
+ var eventDirectionName = void 0;
- if (slideIndex) {
- $target.data('bs.carousel').to(slideIndex)
- }
+ if (direction === Direction.NEXT) {
+ directionalClassName = ClassName.LEFT;
+ orderClassName = ClassName.NEXT;
+ eventDirectionName = Direction.LEFT;
+ } else {
+ directionalClassName = ClassName.RIGHT;
+ orderClassName = ClassName.PREV;
+ eventDirectionName = Direction.RIGHT;
+ }
- e.preventDefault()
- }
+ if (nextElement && $(nextElement).hasClass(ClassName.ACTIVE)) {
+ this._isSliding = false;
+ return;
+ }
- $(document)
- .on('click.bs.carousel.data-api', '[data-slide]', clickHandler)
- .on('click.bs.carousel.data-api', '[data-slide-to]', clickHandler)
+ var slideEvent = this._triggerSlideEvent(nextElement, eventDirectionName);
+ if (slideEvent.isDefaultPrevented()) {
+ return;
+ }
- $(window).on('load', function () {
- $('[data-ride="carousel"]').each(function () {
- var $carousel = $(this)
- Plugin.call($carousel, $carousel.data())
- })
- })
+ if (!activeElement || !nextElement) {
+ // some weirdness is happening, so we bail
+ return;
+ }
-}(jQuery);
+ this._isSliding = true;
-/* ========================================================================
- * Bootstrap: collapse.js v3.3.7
- * http://getbootstrap.com/javascript/#collapse
- * ========================================================================
- * Copyright 2011-2016 Twitter, Inc.
- * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
- * ======================================================================== */
+ if (isCycling) {
+ this.pause();
+ }
-/* jshint latedef: false */
+ this._setActiveIndicatorElement(nextElement);
-+function ($) {
- 'use strict';
+ var slidEvent = $.Event(Event.SLID, {
+ relatedTarget: nextElement,
+ direction: eventDirectionName,
+ from: activeElementIndex,
+ to: nextElementIndex
+ });
- // COLLAPSE PUBLIC CLASS DEFINITION
- // ================================
+ if (Util.supportsTransitionEnd() && $(this._element).hasClass(ClassName.SLIDE)) {
- var Collapse = function (element, options) {
- this.$element = $(element)
- this.options = $.extend({}, Collapse.DEFAULTS, options)
- this.$trigger = $('[data-toggle="collapse"][href="#' + element.id + '"],' +
- '[data-toggle="collapse"][data-target="#' + element.id + '"]')
- this.transitioning = null
+ $(nextElement).addClass(orderClassName);
- if (this.options.parent) {
- this.$parent = this.getParent()
- } else {
- this.addAriaAndCollapsedClass(this.$element, this.$trigger)
- }
+ Util.reflow(nextElement);
- if (this.options.toggle) this.toggle()
- }
+ $(activeElement).addClass(directionalClassName);
+ $(nextElement).addClass(directionalClassName);
- Collapse.VERSION = '3.3.7'
+ $(activeElement).one(Util.TRANSITION_END, function () {
+ $(nextElement).removeClass(directionalClassName + ' ' + orderClassName).addClass(ClassName.ACTIVE);
- Collapse.TRANSITION_DURATION = 350
+ $(activeElement).removeClass(ClassName.ACTIVE + ' ' + orderClassName + ' ' + directionalClassName);
- Collapse.DEFAULTS = {
- toggle: true
- }
+ _this5._isSliding = false;
- Collapse.prototype.dimension = function () {
- var hasWidth = this.$element.hasClass('width')
- return hasWidth ? 'width' : 'height'
- }
+ setTimeout(function () {
+ return $(_this5._element).trigger(slidEvent);
+ }, 0);
+ }).emulateTransitionEnd(TRANSITION_DURATION);
+ } else {
+ $(activeElement).removeClass(ClassName.ACTIVE);
+ $(nextElement).addClass(ClassName.ACTIVE);
- Collapse.prototype.show = function () {
- if (this.transitioning || this.$element.hasClass('in')) return
+ this._isSliding = false;
+ $(this._element).trigger(slidEvent);
+ }
- var activesData
- var actives = this.$parent && this.$parent.children('.panel').children('.in, .collapsing')
+ if (isCycling) {
+ this.cycle();
+ }
+ };
- if (actives && actives.length) {
- activesData = actives.data('bs.collapse')
- if (activesData && activesData.transitioning) return
- }
+ // static
- var startEvent = $.Event('show.bs.collapse')
- this.$element.trigger(startEvent)
- if (startEvent.isDefaultPrevented()) return
+ Carousel._jQueryInterface = function _jQueryInterface(config) {
+ return this.each(function () {
+ var data = $(this).data(DATA_KEY);
+ var _config = $.extend({}, Default, $(this).data());
- if (actives && actives.length) {
- Plugin.call(actives, 'hide')
- activesData || actives.data('bs.collapse', null)
- }
+ if ((typeof config === 'undefined' ? 'undefined' : _typeof(config)) === 'object') {
+ $.extend(_config, config);
+ }
- var dimension = this.dimension()
+ var action = typeof config === 'string' ? config : _config.slide;
- this.$element
- .removeClass('collapse')
- .addClass('collapsing')[dimension](0)
- .attr('aria-expanded', true)
+ if (!data) {
+ data = new Carousel(this, _config);
+ $(this).data(DATA_KEY, data);
+ }
- this.$trigger
- .removeClass('collapsed')
- .attr('aria-expanded', true)
+ if (typeof config === 'number') {
+ data.to(config);
+ } else if (typeof action === 'string') {
+ if (data[action] === undefined) {
+ throw new Error('No method named "' + action + '"');
+ }
+ data[action]();
+ } else if (_config.interval) {
+ data.pause();
+ data.cycle();
+ }
+ });
+ };
- this.transitioning = 1
+ Carousel._dataApiClickHandler = function _dataApiClickHandler(event) {
+ var selector = Util.getSelectorFromElement(this);
- var complete = function () {
- this.$element
- .removeClass('collapsing')
- .addClass('collapse in')[dimension]('')
- this.transitioning = 0
- this.$element
- .trigger('shown.bs.collapse')
- }
+ if (!selector) {
+ return;
+ }
- if (!$.support.transition) return complete.call(this)
+ var target = $(selector)[0];
- var scrollSize = $.camelCase(['scroll', dimension].join('-'))
+ if (!target || !$(target).hasClass(ClassName.CAROUSEL)) {
+ return;
+ }
- this.$element
- .one('bsTransitionEnd', $.proxy(complete, this))
- .emulateTransitionEnd(Collapse.TRANSITION_DURATION)[dimension](this.$element[0][scrollSize])
- }
+ var config = $.extend({}, $(target).data(), $(this).data());
+ var slideIndex = this.getAttribute('data-slide-to');
- Collapse.prototype.hide = function () {
- if (this.transitioning || !this.$element.hasClass('in')) return
+ if (slideIndex) {
+ config.interval = false;
+ }
- var startEvent = $.Event('hide.bs.collapse')
- this.$element.trigger(startEvent)
- if (startEvent.isDefaultPrevented()) return
+ Carousel._jQueryInterface.call($(target), config);
- var dimension = this.dimension()
+ if (slideIndex) {
+ $(target).data(DATA_KEY).to(slideIndex);
+ }
- this.$element[dimension](this.$element[dimension]())[0].offsetHeight
+ event.preventDefault();
+ };
- this.$element
- .addClass('collapsing')
- .removeClass('collapse in')
- .attr('aria-expanded', false)
+ _createClass(Carousel, null, [{
+ key: 'VERSION',
+ get: function get() {
+ return VERSION;
+ }
+ }, {
+ key: 'Default',
+ get: function get() {
+ return Default;
+ }
+ }]);
+
+ return Carousel;
+ }();
+
+ /**
+ * ------------------------------------------------------------------------
+ * Data Api implementation
+ * ------------------------------------------------------------------------
+ */
+
+ $(document).on(Event.CLICK_DATA_API, Selector.DATA_SLIDE, Carousel._dataApiClickHandler);
+
+ $(window).on(Event.LOAD_DATA_API, function () {
+ $(Selector.DATA_RIDE).each(function () {
+ var $carousel = $(this);
+ Carousel._jQueryInterface.call($carousel, $carousel.data());
+ });
+ });
+
+ /**
+ * ------------------------------------------------------------------------
+ * jQuery
+ * ------------------------------------------------------------------------
+ */
+
+ $.fn[NAME] = Carousel._jQueryInterface;
+ $.fn[NAME].Constructor = Carousel;
+ $.fn[NAME].noConflict = function () {
+ $.fn[NAME] = JQUERY_NO_CONFLICT;
+ return Carousel._jQueryInterface;
+ };
+
+ return Carousel;
+}(jQuery);
- this.$trigger
- .addClass('collapsed')
- .attr('aria-expanded', false)
+/**
+ * --------------------------------------------------------------------------
+ * Bootstrap (v4.0.0-beta): collapse.js
+ * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
+ * --------------------------------------------------------------------------
+ */
- this.transitioning = 1
+var Collapse = function ($) {
+
+ /**
+ * ------------------------------------------------------------------------
+ * Constants
+ * ------------------------------------------------------------------------
+ */
+
+ var NAME = 'collapse';
+ var VERSION = '4.0.0-beta';
+ var DATA_KEY = 'bs.collapse';
+ var EVENT_KEY = '.' + DATA_KEY;
+ var DATA_API_KEY = '.data-api';
+ var JQUERY_NO_CONFLICT = $.fn[NAME];
+ var TRANSITION_DURATION = 600;
+
+ var Default = {
+ toggle: true,
+ parent: ''
+ };
+
+ var DefaultType = {
+ toggle: 'boolean',
+ parent: 'string'
+ };
+
+ var Event = {
+ SHOW: 'show' + EVENT_KEY,
+ SHOWN: 'shown' + EVENT_KEY,
+ HIDE: 'hide' + EVENT_KEY,
+ HIDDEN: 'hidden' + EVENT_KEY,
+ CLICK_DATA_API: 'click' + EVENT_KEY + DATA_API_KEY
+ };
+
+ var ClassName = {
+ SHOW: 'show',
+ COLLAPSE: 'collapse',
+ COLLAPSING: 'collapsing',
+ COLLAPSED: 'collapsed'
+ };
+
+ var Dimension = {
+ WIDTH: 'width',
+ HEIGHT: 'height'
+ };
+
+ var Selector = {
+ ACTIVES: '.show, .collapsing',
+ DATA_TOGGLE: '[data-toggle="collapse"]'
+
+ /**
+ * ------------------------------------------------------------------------
+ * Class Definition
+ * ------------------------------------------------------------------------
+ */
+
+ };
+ var Collapse = function () {
+ function Collapse(element, config) {
+ _classCallCheck(this, Collapse);
+
+ this._isTransitioning = false;
+ this._element = element;
+ this._config = this._getConfig(config);
+ this._triggerArray = $.makeArray($('[data-toggle="collapse"][href="#' + element.id + '"],' + ('[data-toggle="collapse"][data-target="#' + element.id + '"]')));
+ var tabToggles = $(Selector.DATA_TOGGLE);
+ for (var i = 0; i < tabToggles.length; i++) {
+ var elem = tabToggles[i];
+ var selector = Util.getSelectorFromElement(elem);
+ if (selector !== null && $(selector).filter(element).length > 0) {
+ this._triggerArray.push(elem);
+ }
+ }
- var complete = function () {
- this.transitioning = 0
- this.$element
- .removeClass('collapsing')
- .addClass('collapse')
- .trigger('hidden.bs.collapse')
- }
+ this._parent = this._config.parent ? this._getParent() : null;
- if (!$.support.transition) return complete.call(this)
+ if (!this._config.parent) {
+ this._addAriaAndCollapsedClass(this._element, this._triggerArray);
+ }
- this.$element
- [dimension](0)
- .one('bsTransitionEnd', $.proxy(complete, this))
- .emulateTransitionEnd(Collapse.TRANSITION_DURATION)
- }
+ if (this._config.toggle) {
+ this.toggle();
+ }
+ }
- Collapse.prototype.toggle = function () {
- this[this.$element.hasClass('in') ? 'hide' : 'show']()
- }
+ // getters
- Collapse.prototype.getParent = function () {
- return $(this.options.parent)
- .find('[data-toggle="collapse"][data-parent="' + this.options.parent + '"]')
- .each($.proxy(function (i, element) {
- var $element = $(element)
- this.addAriaAndCollapsedClass(getTargetFromTrigger($element), $element)
- }, this))
- .end()
- }
+ // public
- Collapse.prototype.addAriaAndCollapsedClass = function ($element, $trigger) {
- var isOpen = $element.hasClass('in')
+ Collapse.prototype.toggle = function toggle() {
+ if ($(this._element).hasClass(ClassName.SHOW)) {
+ this.hide();
+ } else {
+ this.show();
+ }
+ };
- $element.attr('aria-expanded', isOpen)
- $trigger
- .toggleClass('collapsed', !isOpen)
- .attr('aria-expanded', isOpen)
- }
+ Collapse.prototype.show = function show() {
+ var _this6 = this;
- function getTargetFromTrigger($trigger) {
- var href
- var target = $trigger.attr('data-target')
- || (href = $trigger.attr('href')) && href.replace(/.*(?=#[^\s]+$)/, '') // strip for ie7
+ if (this._isTransitioning || $(this._element).hasClass(ClassName.SHOW)) {
+ return;
+ }
- return $(target)
- }
+ var actives = void 0;
+ var activesData = void 0;
+ if (this._parent) {
+ actives = $.makeArray($(this._parent).children().children(Selector.ACTIVES));
+ if (!actives.length) {
+ actives = null;
+ }
+ }
- // COLLAPSE PLUGIN DEFINITION
- // ==========================
+ if (actives) {
+ activesData = $(actives).data(DATA_KEY);
+ if (activesData && activesData._isTransitioning) {
+ return;
+ }
+ }
- function Plugin(option) {
- return this.each(function () {
- var $this = $(this)
- var data = $this.data('bs.collapse')
- var options = $.extend({}, Collapse.DEFAULTS, $this.data(), typeof option == 'object' && option)
+ var startEvent = $.Event(Event.SHOW);
+ $(this._element).trigger(startEvent);
+ if (startEvent.isDefaultPrevented()) {
+ return;
+ }
- if (!data && options.toggle && /show|hide/.test(option)) options.toggle = false
- if (!data) $this.data('bs.collapse', (data = new Collapse(this, options)))
- if (typeof option == 'string') data[option]()
- })
- }
+ if (actives) {
+ Collapse._jQueryInterface.call($(actives), 'hide');
+ if (!activesData) {
+ $(actives).data(DATA_KEY, null);
+ }
+ }
- var old = $.fn.collapse
+ var dimension = this._getDimension();
- $.fn.collapse = Plugin
- $.fn.collapse.Constructor = Collapse
+ $(this._element).removeClass(ClassName.COLLAPSE).addClass(ClassName.COLLAPSING);
+ this._element.style[dimension] = 0;
- // COLLAPSE NO CONFLICT
- // ====================
+ if (this._triggerArray.length) {
+ $(this._triggerArray).removeClass(ClassName.COLLAPSED).attr('aria-expanded', true);
+ }
- $.fn.collapse.noConflict = function () {
- $.fn.collapse = old
- return this
- }
+ this.setTransitioning(true);
+ var complete = function complete() {
+ $(_this6._element).removeClass(ClassName.COLLAPSING).addClass(ClassName.COLLAPSE).addClass(ClassName.SHOW);
- // COLLAPSE DATA-API
- // =================
+ _this6._element.style[dimension] = '';
- $(document).on('click.bs.collapse.data-api', '[data-toggle="collapse"]', function (e) {
- var $this = $(this)
+ _this6.setTransitioning(false);
- if (!$this.attr('data-target')) e.preventDefault()
+ $(_this6._element).trigger(Event.SHOWN);
+ };
- var $target = getTargetFromTrigger($this)
- var data = $target.data('bs.collapse')
- var option = data ? 'toggle' : $this.data()
+ if (!Util.supportsTransitionEnd()) {
+ complete();
+ return;
+ }
- Plugin.call($target, option)
- })
+ var capitalizedDimension = dimension[0].toUpperCase() + dimension.slice(1);
+ var scrollSize = 'scroll' + capitalizedDimension;
-}(jQuery);
+ $(this._element).one(Util.TRANSITION_END, complete).emulateTransitionEnd(TRANSITION_DURATION);
-/* ========================================================================
- * Bootstrap: dropdown.js v3.3.7
- * http://getbootstrap.com/javascript/#dropdowns
- * ========================================================================
- * Copyright 2011-2016 Twitter, Inc.
- * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
- * ======================================================================== */
+ this._element.style[dimension] = this._element[scrollSize] + 'px';
+ };
+ Collapse.prototype.hide = function hide() {
+ var _this7 = this;
-+function ($) {
- 'use strict';
+ if (this._isTransitioning || !$(this._element).hasClass(ClassName.SHOW)) {
+ return;
+ }
- // DROPDOWN CLASS DEFINITION
- // =========================
+ var startEvent = $.Event(Event.HIDE);
+ $(this._element).trigger(startEvent);
+ if (startEvent.isDefaultPrevented()) {
+ return;
+ }
- var backdrop = '.dropdown-backdrop'
- var toggle = '[data-toggle="dropdown"]'
- var Dropdown = function (element) {
- $(element).on('click.bs.dropdown', this.toggle)
- }
+ var dimension = this._getDimension();
- Dropdown.VERSION = '3.3.7'
+ this._element.style[dimension] = this._element.getBoundingClientRect()[dimension] + 'px';
- function getParent($this) {
- var selector = $this.attr('data-target')
+ Util.reflow(this._element);
- if (!selector) {
- selector = $this.attr('href')
- selector = selector && /#[A-Za-z]/.test(selector) && selector.replace(/.*(?=#[^\s]*$)/, '') // strip for ie7
- }
+ $(this._element).addClass(ClassName.COLLAPSING).removeClass(ClassName.COLLAPSE).removeClass(ClassName.SHOW);
- var $parent = selector && $(selector)
+ if (this._triggerArray.length) {
+ for (var i = 0; i < this._triggerArray.length; i++) {
+ var trigger = this._triggerArray[i];
+ var selector = Util.getSelectorFromElement(trigger);
+ if (selector !== null) {
+ var $elem = $(selector);
+ if (!$elem.hasClass(ClassName.SHOW)) {
+ $(trigger).addClass(ClassName.COLLAPSED).attr('aria-expanded', false);
+ }
+ }
+ }
+ }
- return $parent && $parent.length ? $parent : $this.parent()
- }
+ this.setTransitioning(true);
- function clearMenus(e) {
- if (e && e.which === 3) return
- $(backdrop).remove()
- $(toggle).each(function () {
- var $this = $(this)
- var $parent = getParent($this)
- var relatedTarget = { relatedTarget: this }
+ var complete = function complete() {
+ _this7.setTransitioning(false);
+ $(_this7._element).removeClass(ClassName.COLLAPSING).addClass(ClassName.COLLAPSE).trigger(Event.HIDDEN);
+ };
- if (!$parent.hasClass('open')) return
+ this._element.style[dimension] = '';
- if (e && e.type == 'click' && /input|textarea/i.test(e.target.tagName) && $.contains($parent[0], e.target)) return
+ if (!Util.supportsTransitionEnd()) {
+ complete();
+ return;
+ }
- $parent.trigger(e = $.Event('hide.bs.dropdown', relatedTarget))
+ $(this._element).one(Util.TRANSITION_END, complete).emulateTransitionEnd(TRANSITION_DURATION);
+ };
- if (e.isDefaultPrevented()) return
+ Collapse.prototype.setTransitioning = function setTransitioning(isTransitioning) {
+ this._isTransitioning = isTransitioning;
+ };
- $this.attr('aria-expanded', 'false')
- $parent.removeClass('open').trigger($.Event('hidden.bs.dropdown', relatedTarget))
- })
- }
+ Collapse.prototype.dispose = function dispose() {
+ $.removeData(this._element, DATA_KEY);
- Dropdown.prototype.toggle = function (e) {
- var $this = $(this)
+ this._config = null;
+ this._parent = null;
+ this._element = null;
+ this._triggerArray = null;
+ this._isTransitioning = null;
+ };
- if ($this.is('.disabled, :disabled')) return
+ // private
- var $parent = getParent($this)
- var isActive = $parent.hasClass('open')
+ Collapse.prototype._getConfig = function _getConfig(config) {
+ config = $.extend({}, Default, config);
+ config.toggle = Boolean(config.toggle); // coerce string values
+ Util.typeCheckConfig(NAME, config, DefaultType);
+ return config;
+ };
- clearMenus()
+ Collapse.prototype._getDimension = function _getDimension() {
+ var hasWidth = $(this._element).hasClass(Dimension.WIDTH);
+ return hasWidth ? Dimension.WIDTH : Dimension.HEIGHT;
+ };
- if (!isActive) {
- if ('ontouchstart' in document.documentElement && !$parent.closest('.navbar-nav').length) {
- // if mobile we use a backdrop because click events don't delegate
- $(document.createElement('div'))
- .addClass('dropdown-backdrop')
- .insertAfter($(this))
- .on('click', clearMenus)
- }
+ Collapse.prototype._getParent = function _getParent() {
+ var _this8 = this;
- var relatedTarget = { relatedTarget: this }
- $parent.trigger(e = $.Event('show.bs.dropdown', relatedTarget))
+ var parent = $(this._config.parent)[0];
+ var selector = '[data-toggle="collapse"][data-parent="' + this._config.parent + '"]';
- if (e.isDefaultPrevented()) return
+ $(parent).find(selector).each(function (i, element) {
+ _this8._addAriaAndCollapsedClass(Collapse._getTargetFromElement(element), [element]);
+ });
- $this
- .trigger('focus')
- .attr('aria-expanded', 'true')
+ return parent;
+ };
- $parent
- .toggleClass('open')
- .trigger($.Event('shown.bs.dropdown', relatedTarget))
- }
+ Collapse.prototype._addAriaAndCollapsedClass = function _addAriaAndCollapsedClass(element, triggerArray) {
+ if (element) {
+ var isOpen = $(element).hasClass(ClassName.SHOW);
- return false
- }
+ if (triggerArray.length) {
+ $(triggerArray).toggleClass(ClassName.COLLAPSED, !isOpen).attr('aria-expanded', isOpen);
+ }
+ }
+ };
- Dropdown.prototype.keydown = function (e) {
- if (!/(38|40|27|32)/.test(e.which) || /input|textarea/i.test(e.target.tagName)) return
+ // static
- var $this = $(this)
+ Collapse._getTargetFromElement = function _getTargetFromElement(element) {
+ var selector = Util.getSelectorFromElement(element);
+ return selector ? $(selector)[0] : null;
+ };
- e.preventDefault()
- e.stopPropagation()
+ Collapse._jQueryInterface = function _jQueryInterface(config) {
+ return this.each(function () {
+ var $this = $(this);
+ var data = $this.data(DATA_KEY);
+ var _config = $.extend({}, Default, $this.data(), (typeof config === 'undefined' ? 'undefined' : _typeof(config)) === 'object' && config);
- if ($this.is('.disabled, :disabled')) return
+ if (!data && _config.toggle && /show|hide/.test(config)) {
+ _config.toggle = false;
+ }
- var $parent = getParent($this)
- var isActive = $parent.hasClass('open')
+ if (!data) {
+ data = new Collapse(this, _config);
+ $this.data(DATA_KEY, data);
+ }
- if (!isActive && e.which != 27 || isActive && e.which == 27) {
- if (e.which == 27) $parent.find(toggle).trigger('focus')
- return $this.trigger('click')
- }
+ if (typeof config === 'string') {
+ if (data[config] === undefined) {
+ throw new Error('No method named "' + config + '"');
+ }
+ data[config]();
+ }
+ });
+ };
- var desc = ' li:not(.disabled):visible a'
- var $items = $parent.find('.dropdown-menu' + desc)
+ _createClass(Collapse, null, [{
+ key: 'VERSION',
+ get: function get() {
+ return VERSION;
+ }
+ }, {
+ key: 'Default',
+ get: function get() {
+ return Default;
+ }
+ }]);
- if (!$items.length) return
+ return Collapse;
+ }();
- var index = $items.index(e.target)
+ /**
+ * ------------------------------------------------------------------------
+ * Data Api implementation
+ * ------------------------------------------------------------------------
+ */
- if (e.which == 38 && index > 0) index-- // up
- if (e.which == 40 && index < $items.length - 1) index++ // down
- if (!~index) index = 0
+ $(document).on(Event.CLICK_DATA_API, Selector.DATA_TOGGLE, function (event) {
+ if (!/input|textarea/i.test(event.target.tagName)) {
+ event.preventDefault();
+ }
- $items.eq(index).trigger('focus')
- }
+ var $trigger = $(this);
+ var selector = Util.getSelectorFromElement(this);
+ $(selector).each(function () {
+ var $target = $(this);
+ var data = $target.data(DATA_KEY);
+ var config = data ? 'toggle' : $trigger.data();
+ Collapse._jQueryInterface.call($target, config);
+ });
+ });
+
+ /**
+ * ------------------------------------------------------------------------
+ * jQuery
+ * ------------------------------------------------------------------------
+ */
+
+ $.fn[NAME] = Collapse._jQueryInterface;
+ $.fn[NAME].Constructor = Collapse;
+ $.fn[NAME].noConflict = function () {
+ $.fn[NAME] = JQUERY_NO_CONFLICT;
+ return Collapse._jQueryInterface;
+ };
+
+ return Collapse;
+}(jQuery);
+/* global Popper */
- // DROPDOWN PLUGIN DEFINITION
- // ==========================
+/**
+ * --------------------------------------------------------------------------
+ * Bootstrap (v4.0.0-beta): dropdown.js
+ * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
+ * --------------------------------------------------------------------------
+ */
- function Plugin(option) {
- return this.each(function () {
- var $this = $(this)
- var data = $this.data('bs.dropdown')
+var Dropdown = function ($) {
+
+ /**
+ * Check for Popper dependency
+ * Popper - https://popper.js.org
+ */
+ if (typeof Popper === 'undefined') {
+ throw new Error('Bootstrap dropdown require Popper.js (https://popper.js.org)');
+ }
+
+ /**
+ * ------------------------------------------------------------------------
+ * Constants
+ * ------------------------------------------------------------------------
+ */
+
+ var NAME = 'dropdown';
+ var VERSION = '4.0.0-beta';
+ var DATA_KEY = 'bs.dropdown';
+ var EVENT_KEY = '.' + DATA_KEY;
+ var DATA_API_KEY = '.data-api';
+ var JQUERY_NO_CONFLICT = $.fn[NAME];
+ var ESCAPE_KEYCODE = 27; // KeyboardEvent.which value for Escape (Esc) key
+ var SPACE_KEYCODE = 32; // KeyboardEvent.which value for space key
+ var TAB_KEYCODE = 9; // KeyboardEvent.which value for tab key
+ var ARROW_UP_KEYCODE = 38; // KeyboardEvent.which value for up arrow key
+ var ARROW_DOWN_KEYCODE = 40; // KeyboardEvent.which value for down arrow key
+ var RIGHT_MOUSE_BUTTON_WHICH = 3; // MouseEvent.which value for the right button (assuming a right-handed mouse)
+ var REGEXP_KEYDOWN = new RegExp(ARROW_UP_KEYCODE + '|' + ARROW_DOWN_KEYCODE + '|' + ESCAPE_KEYCODE);
+
+ var Event = {
+ HIDE: 'hide' + EVENT_KEY,
+ HIDDEN: 'hidden' + EVENT_KEY,
+ SHOW: 'show' + EVENT_KEY,
+ SHOWN: 'shown' + EVENT_KEY,
+ CLICK: 'click' + EVENT_KEY,
+ CLICK_DATA_API: 'click' + EVENT_KEY + DATA_API_KEY,
+ KEYDOWN_DATA_API: 'keydown' + EVENT_KEY + DATA_API_KEY,
+ KEYUP_DATA_API: 'keyup' + EVENT_KEY + DATA_API_KEY
+ };
+
+ var ClassName = {
+ DISABLED: 'disabled',
+ SHOW: 'show',
+ DROPUP: 'dropup',
+ MENURIGHT: 'dropdown-menu-right',
+ MENULEFT: 'dropdown-menu-left'
+ };
+
+ var Selector = {
+ DATA_TOGGLE: '[data-toggle="dropdown"]',
+ FORM_CHILD: '.dropdown form',
+ MENU: '.dropdown-menu',
+ NAVBAR_NAV: '.navbar-nav',
+ VISIBLE_ITEMS: '.dropdown-menu .dropdown-item:not(.disabled)'
+ };
+
+ var AttachmentMap = {
+ TOP: 'top-start',
+ TOPEND: 'top-end',
+ BOTTOM: 'bottom-start',
+ BOTTOMEND: 'bottom-end'
+ };
+
+ var Default = {
+ placement: AttachmentMap.BOTTOM,
+ offset: 0,
+ flip: true
+ };
+
+ var DefaultType = {
+ placement: 'string',
+ offset: '(number|string)',
+ flip: 'boolean'
+
+ /**
+ * ------------------------------------------------------------------------
+ * Class Definition
+ * ------------------------------------------------------------------------
+ */
+
+ };
+ var Dropdown = function () {
+ function Dropdown(element, config) {
+ _classCallCheck(this, Dropdown);
+
+ this._element = element;
+ this._popper = null;
+ this._config = this._getConfig(config);
+ this._menu = this._getMenuElement();
+ this._inNavbar = this._detectNavbar();
+
+ this._addEventListeners();
+ }
- if (!data) $this.data('bs.dropdown', (data = new Dropdown(this)))
- if (typeof option == 'string') data[option].call($this)
- })
- }
+ // getters
- var old = $.fn.dropdown
+ // public
- $.fn.dropdown = Plugin
- $.fn.dropdown.Constructor = Dropdown
+ Dropdown.prototype.toggle = function toggle() {
+ if (this._element.disabled || $(this._element).hasClass(ClassName.DISABLED)) {
+ return;
+ }
+ var parent = Dropdown._getParentFromElement(this._element);
+ var isActive = $(this._menu).hasClass(ClassName.SHOW);
- // DROPDOWN NO CONFLICT
- // ====================
+ Dropdown._clearMenus();
- $.fn.dropdown.noConflict = function () {
- $.fn.dropdown = old
- return this
- }
+ if (isActive) {
+ return;
+ }
+ var relatedTarget = {
+ relatedTarget: this._element
+ };
+ var showEvent = $.Event(Event.SHOW, relatedTarget);
- // APPLY TO STANDARD DROPDOWN ELEMENTS
- // ===================================
+ $(parent).trigger(showEvent);
- $(document)
- .on('click.bs.dropdown.data-api', clearMenus)
- .on('click.bs.dropdown.data-api', '.dropdown form', function (e) { e.stopPropagation() })
- .on('click.bs.dropdown.data-api', toggle, Dropdown.prototype.toggle)
- .on('keydown.bs.dropdown.data-api', toggle, Dropdown.prototype.keydown)
- .on('keydown.bs.dropdown.data-api', '.dropdown-menu', Dropdown.prototype.keydown)
+ if (showEvent.isDefaultPrevented()) {
+ return;
+ }
-}(jQuery);
+ var element = this._element;
+ // for dropup with alignment we use the parent as popper container
+ if ($(parent).hasClass(ClassName.DROPUP)) {
+ if ($(this._menu).hasClass(ClassName.MENULEFT) || $(this._menu).hasClass(ClassName.MENURIGHT)) {
+ element = parent;
+ }
+ }
+ this._popper = new Popper(element, this._menu, this._getPopperConfig());
+
+ // if this is a touch-enabled device we add extra
+ // empty mouseover listeners to the body's immediate children;
+ // only needed because of broken event delegation on iOS
+ // https://www.quirksmode.org/blog/archives/2014/02/mouse_event_bub.html
+ if ('ontouchstart' in document.documentElement && !$(parent).closest(Selector.NAVBAR_NAV).length) {
+ $('body').children().on('mouseover', null, $.noop);
+ }
-/* ========================================================================
- * Bootstrap: modal.js v3.3.7
- * http://getbootstrap.com/javascript/#modals
- * ========================================================================
- * Copyright 2011-2016 Twitter, Inc.
- * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
- * ======================================================================== */
-
-
-+function ($) {
- 'use strict';
-
- // MODAL CLASS DEFINITION
- // ======================
-
- var Modal = function (element, options) {
- this.options = options
- this.$body = $(document.body)
- this.$element = $(element)
- this.$dialog = this.$element.find('.modal-dialog')
- this.$backdrop = null
- this.isShown = null
- this.originalBodyPad = null
- this.scrollbarWidth = 0
- this.ignoreBackdropClick = false
-
- if (this.options.remote) {
- this.$element
- .find('.modal-content')
- .load(this.options.remote, $.proxy(function () {
- this.$element.trigger('loaded.bs.modal')
- }, this))
- }
- }
+ this._element.focus();
+ this._element.setAttribute('aria-expanded', true);
- Modal.VERSION = '3.3.7'
+ $(this._menu).toggleClass(ClassName.SHOW);
+ $(parent).toggleClass(ClassName.SHOW).trigger($.Event(Event.SHOWN, relatedTarget));
+ };
- Modal.TRANSITION_DURATION = 300
- Modal.BACKDROP_TRANSITION_DURATION = 150
+ Dropdown.prototype.dispose = function dispose() {
+ $.removeData(this._element, DATA_KEY);
+ $(this._element).off(EVENT_KEY);
+ this._element = null;
+ this._menu = null;
+ if (this._popper !== null) {
+ this._popper.destroy();
+ }
+ this._popper = null;
+ };
- Modal.DEFAULTS = {
- backdrop: true,
- keyboard: true,
- show: true
- }
+ Dropdown.prototype.update = function update() {
+ this._inNavbar = this._detectNavbar();
+ if (this._popper !== null) {
+ this._popper.scheduleUpdate();
+ }
+ };
- Modal.prototype.toggle = function (_relatedTarget) {
- return this.isShown ? this.hide() : this.show(_relatedTarget)
- }
+ // private
- Modal.prototype.show = function (_relatedTarget) {
- var that = this
- var e = $.Event('show.bs.modal', { relatedTarget: _relatedTarget })
+ Dropdown.prototype._addEventListeners = function _addEventListeners() {
+ var _this9 = this;
- this.$element.trigger(e)
+ $(this._element).on(Event.CLICK, function (event) {
+ event.preventDefault();
+ event.stopPropagation();
+ _this9.toggle();
+ });
+ };
- if (this.isShown || e.isDefaultPrevented()) return
+ Dropdown.prototype._getConfig = function _getConfig(config) {
+ var elementData = $(this._element).data();
+ if (elementData.placement !== undefined) {
+ elementData.placement = AttachmentMap[elementData.placement.toUpperCase()];
+ }
- this.isShown = true
+ config = $.extend({}, this.constructor.Default, $(this._element).data(), config);
- this.checkScrollbar()
- this.setScrollbar()
- this.$body.addClass('modal-open')
+ Util.typeCheckConfig(NAME, config, this.constructor.DefaultType);
- this.escape()
- this.resize()
+ return config;
+ };
- this.$element.on('click.dismiss.bs.modal', '[data-dismiss="modal"]', $.proxy(this.hide, this))
+ Dropdown.prototype._getMenuElement = function _getMenuElement() {
+ if (!this._menu) {
+ var parent = Dropdown._getParentFromElement(this._element);
+ this._menu = $(parent).find(Selector.MENU)[0];
+ }
+ return this._menu;
+ };
+
+ Dropdown.prototype._getPlacement = function _getPlacement() {
+ var $parentDropdown = $(this._element).parent();
+ var placement = this._config.placement;
+
+ // Handle dropup
+ if ($parentDropdown.hasClass(ClassName.DROPUP) || this._config.placement === AttachmentMap.TOP) {
+ placement = AttachmentMap.TOP;
+ if ($(this._menu).hasClass(ClassName.MENURIGHT)) {
+ placement = AttachmentMap.TOPEND;
+ }
+ } else if ($(this._menu).hasClass(ClassName.MENURIGHT)) {
+ placement = AttachmentMap.BOTTOMEND;
+ }
+ return placement;
+ };
+
+ Dropdown.prototype._detectNavbar = function _detectNavbar() {
+ return $(this._element).closest('.navbar').length > 0;
+ };
+
+ Dropdown.prototype._getPopperConfig = function _getPopperConfig() {
+ var popperConfig = {
+ placement: this._getPlacement(),
+ modifiers: {
+ offset: {
+ offset: this._config.offset
+ },
+ flip: {
+ enabled: this._config.flip
+ }
+ }
- this.$dialog.on('mousedown.dismiss.bs.modal', function () {
- that.$element.one('mouseup.dismiss.bs.modal', function (e) {
- if ($(e.target).is(that.$element)) that.ignoreBackdropClick = true
- })
- })
+ // Disable Popper.js for Dropdown in Navbar
+ };if (this._inNavbar) {
+ popperConfig.modifiers.applyStyle = {
+ enabled: !this._inNavbar
+ };
+ }
+ return popperConfig;
+ };
- this.backdrop(function () {
- var transition = $.support.transition && that.$element.hasClass('fade')
+ // static
- if (!that.$element.parent().length) {
- that.$element.appendTo(that.$body) // don't move modals dom position
- }
+ Dropdown._jQueryInterface = function _jQueryInterface(config) {
+ return this.each(function () {
+ var data = $(this).data(DATA_KEY);
+ var _config = (typeof config === 'undefined' ? 'undefined' : _typeof(config)) === 'object' ? config : null;
- that.$element
- .show()
- .scrollTop(0)
+ if (!data) {
+ data = new Dropdown(this, _config);
+ $(this).data(DATA_KEY, data);
+ }
- that.adjustDialog()
+ if (typeof config === 'string') {
+ if (data[config] === undefined) {
+ throw new Error('No method named "' + config + '"');
+ }
+ data[config]();
+ }
+ });
+ };
- if (transition) {
- that.$element[0].offsetWidth // force reflow
+ Dropdown._clearMenus = function _clearMenus(event) {
+ if (event && (event.which === RIGHT_MOUSE_BUTTON_WHICH || event.type === 'keyup' && event.which !== TAB_KEYCODE)) {
+ return;
}
- that.$element.addClass('in')
+ var toggles = $.makeArray($(Selector.DATA_TOGGLE));
+ for (var i = 0; i < toggles.length; i++) {
+ var parent = Dropdown._getParentFromElement(toggles[i]);
+ var context = $(toggles[i]).data(DATA_KEY);
+ var relatedTarget = {
+ relatedTarget: toggles[i]
+ };
- that.enforceFocus()
+ if (!context) {
+ continue;
+ }
- var e = $.Event('shown.bs.modal', { relatedTarget: _relatedTarget })
+ var dropdownMenu = context._menu;
+ if (!$(parent).hasClass(ClassName.SHOW)) {
+ continue;
+ }
- transition ?
- that.$dialog // wait for modal to slide in
- .one('bsTransitionEnd', function () {
- that.$element.trigger('focus').trigger(e)
- })
- .emulateTransitionEnd(Modal.TRANSITION_DURATION) :
- that.$element.trigger('focus').trigger(e)
- })
- }
+ if (event && (event.type === 'click' && /input|textarea/i.test(event.target.tagName) || event.type === 'keyup' && event.which === TAB_KEYCODE) && $.contains(parent, event.target)) {
+ continue;
+ }
- Modal.prototype.hide = function (e) {
- if (e) e.preventDefault()
+ var hideEvent = $.Event(Event.HIDE, relatedTarget);
+ $(parent).trigger(hideEvent);
+ if (hideEvent.isDefaultPrevented()) {
+ continue;
+ }
- e = $.Event('hide.bs.modal')
+ // if this is a touch-enabled device we remove the extra
+ // empty mouseover listeners we added for iOS support
+ if ('ontouchstart' in document.documentElement) {
+ $('body').children().off('mouseover', null, $.noop);
+ }
- this.$element.trigger(e)
+ toggles[i].setAttribute('aria-expanded', 'false');
- if (!this.isShown || e.isDefaultPrevented()) return
+ $(dropdownMenu).removeClass(ClassName.SHOW);
+ $(parent).removeClass(ClassName.SHOW).trigger($.Event(Event.HIDDEN, relatedTarget));
+ }
+ };
- this.isShown = false
+ Dropdown._getParentFromElement = function _getParentFromElement(element) {
+ var parent = void 0;
+ var selector = Util.getSelectorFromElement(element);
- this.escape()
- this.resize()
+ if (selector) {
+ parent = $(selector)[0];
+ }
- $(document).off('focusin.bs.modal')
+ return parent || element.parentNode;
+ };
- this.$element
- .removeClass('in')
- .off('click.dismiss.bs.modal')
- .off('mouseup.dismiss.bs.modal')
+ Dropdown._dataApiKeydownHandler = function _dataApiKeydownHandler(event) {
+ if (!REGEXP_KEYDOWN.test(event.which) || /button/i.test(event.target.tagName) && event.which === SPACE_KEYCODE || /input|textarea/i.test(event.target.tagName)) {
+ return;
+ }
- this.$dialog.off('mousedown.dismiss.bs.modal')
+ event.preventDefault();
+ event.stopPropagation();
- $.support.transition && this.$element.hasClass('fade') ?
- this.$element
- .one('bsTransitionEnd', $.proxy(this.hideModal, this))
- .emulateTransitionEnd(Modal.TRANSITION_DURATION) :
- this.hideModal()
- }
+ if (this.disabled || $(this).hasClass(ClassName.DISABLED)) {
+ return;
+ }
+
+ var parent = Dropdown._getParentFromElement(this);
+ var isActive = $(parent).hasClass(ClassName.SHOW);
- Modal.prototype.enforceFocus = function () {
- $(document)
- .off('focusin.bs.modal') // guard against infinite focus loop
- .on('focusin.bs.modal', $.proxy(function (e) {
- if (document !== e.target &&
- this.$element[0] !== e.target &&
- !this.$element.has(e.target).length) {
- this.$element.trigger('focus')
+ if (!isActive && (event.which !== ESCAPE_KEYCODE || event.which !== SPACE_KEYCODE) || isActive && (event.which === ESCAPE_KEYCODE || event.which === SPACE_KEYCODE)) {
+
+ if (event.which === ESCAPE_KEYCODE) {
+ var toggle = $(parent).find(Selector.DATA_TOGGLE)[0];
+ $(toggle).trigger('focus');
}
- }, this))
- }
- Modal.prototype.escape = function () {
- if (this.isShown && this.options.keyboard) {
- this.$element.on('keydown.dismiss.bs.modal', $.proxy(function (e) {
- e.which == 27 && this.hide()
- }, this))
- } else if (!this.isShown) {
- this.$element.off('keydown.dismiss.bs.modal')
- }
- }
+ $(this).trigger('click');
+ return;
+ }
- Modal.prototype.resize = function () {
- if (this.isShown) {
- $(window).on('resize.bs.modal', $.proxy(this.handleUpdate, this))
- } else {
- $(window).off('resize.bs.modal')
- }
- }
+ var items = $(parent).find(Selector.VISIBLE_ITEMS).get();
- Modal.prototype.hideModal = function () {
- var that = this
- this.$element.hide()
- this.backdrop(function () {
- that.$body.removeClass('modal-open')
- that.resetAdjustments()
- that.resetScrollbar()
- that.$element.trigger('hidden.bs.modal')
- })
- }
+ if (!items.length) {
+ return;
+ }
- Modal.prototype.removeBackdrop = function () {
- this.$backdrop && this.$backdrop.remove()
- this.$backdrop = null
- }
+ var index = items.indexOf(event.target);
+
+ if (event.which === ARROW_UP_KEYCODE && index > 0) {
+ // up
+ index--;
+ }
- Modal.prototype.backdrop = function (callback) {
- var that = this
- var animate = this.$element.hasClass('fade') ? 'fade' : ''
+ if (event.which === ARROW_DOWN_KEYCODE && index < items.length - 1) {
+ // down
+ index++;
+ }
- if (this.isShown && this.options.backdrop) {
- var doAnimate = $.support.transition && animate
+ if (index < 0) {
+ index = 0;
+ }
- this.$backdrop = $(document.createElement('div'))
- .addClass('modal-backdrop ' + animate)
- .appendTo(this.$body)
+ items[index].focus();
+ };
- this.$element.on('click.dismiss.bs.modal', $.proxy(function (e) {
- if (this.ignoreBackdropClick) {
- this.ignoreBackdropClick = false
- return
- }
- if (e.target !== e.currentTarget) return
- this.options.backdrop == 'static'
- ? this.$element[0].focus()
- : this.hide()
- }, this))
+ _createClass(Dropdown, null, [{
+ key: 'VERSION',
+ get: function get() {
+ return VERSION;
+ }
+ }, {
+ key: 'Default',
+ get: function get() {
+ return Default;
+ }
+ }, {
+ key: 'DefaultType',
+ get: function get() {
+ return DefaultType;
+ }
+ }]);
+
+ return Dropdown;
+ }();
+
+ /**
+ * ------------------------------------------------------------------------
+ * Data Api implementation
+ * ------------------------------------------------------------------------
+ */
+
+ $(document).on(Event.KEYDOWN_DATA_API, Selector.DATA_TOGGLE, Dropdown._dataApiKeydownHandler).on(Event.KEYDOWN_DATA_API, Selector.MENU, Dropdown._dataApiKeydownHandler).on(Event.CLICK_DATA_API + ' ' + Event.KEYUP_DATA_API, Dropdown._clearMenus).on(Event.CLICK_DATA_API, Selector.DATA_TOGGLE, function (event) {
+ event.preventDefault();
+ event.stopPropagation();
+ Dropdown._jQueryInterface.call($(this), 'toggle');
+ }).on(Event.CLICK_DATA_API, Selector.FORM_CHILD, function (e) {
+ e.stopPropagation();
+ });
+
+ /**
+ * ------------------------------------------------------------------------
+ * jQuery
+ * ------------------------------------------------------------------------
+ */
+
+ $.fn[NAME] = Dropdown._jQueryInterface;
+ $.fn[NAME].Constructor = Dropdown;
+ $.fn[NAME].noConflict = function () {
+ $.fn[NAME] = JQUERY_NO_CONFLICT;
+ return Dropdown._jQueryInterface;
+ };
+
+ return Dropdown;
+}(jQuery);
+
+/**
+ * --------------------------------------------------------------------------
+ * Bootstrap (v4.0.0-beta): modal.js
+ * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
+ * --------------------------------------------------------------------------
+ */
- if (doAnimate) this.$backdrop[0].offsetWidth // force reflow
+var Modal = function ($) {
+
+ /**
+ * ------------------------------------------------------------------------
+ * Constants
+ * ------------------------------------------------------------------------
+ */
+
+ var NAME = 'modal';
+ var VERSION = '4.0.0-beta';
+ var DATA_KEY = 'bs.modal';
+ var EVENT_KEY = '.' + DATA_KEY;
+ var DATA_API_KEY = '.data-api';
+ var JQUERY_NO_CONFLICT = $.fn[NAME];
+ var TRANSITION_DURATION = 300;
+ var BACKDROP_TRANSITION_DURATION = 150;
+ var ESCAPE_KEYCODE = 27; // KeyboardEvent.which value for Escape (Esc) key
+
+ var Default = {
+ backdrop: true,
+ keyboard: true,
+ focus: true,
+ show: true
+ };
+
+ var DefaultType = {
+ backdrop: '(boolean|string)',
+ keyboard: 'boolean',
+ focus: 'boolean',
+ show: 'boolean'
+ };
+
+ var Event = {
+ HIDE: 'hide' + EVENT_KEY,
+ HIDDEN: 'hidden' + EVENT_KEY,
+ SHOW: 'show' + EVENT_KEY,
+ SHOWN: 'shown' + EVENT_KEY,
+ FOCUSIN: 'focusin' + EVENT_KEY,
+ RESIZE: 'resize' + EVENT_KEY,
+ CLICK_DISMISS: 'click.dismiss' + EVENT_KEY,
+ KEYDOWN_DISMISS: 'keydown.dismiss' + EVENT_KEY,
+ MOUSEUP_DISMISS: 'mouseup.dismiss' + EVENT_KEY,
+ MOUSEDOWN_DISMISS: 'mousedown.dismiss' + EVENT_KEY,
+ CLICK_DATA_API: 'click' + EVENT_KEY + DATA_API_KEY
+ };
+
+ var ClassName = {
+ SCROLLBAR_MEASURER: 'modal-scrollbar-measure',
+ BACKDROP: 'modal-backdrop',
+ OPEN: 'modal-open',
+ FADE: 'fade',
+ SHOW: 'show'
+ };
+
+ var Selector = {
+ DIALOG: '.modal-dialog',
+ DATA_TOGGLE: '[data-toggle="modal"]',
+ DATA_DISMISS: '[data-dismiss="modal"]',
+ FIXED_CONTENT: '.fixed-top, .fixed-bottom, .is-fixed, .sticky-top',
+ NAVBAR_TOGGLER: '.navbar-toggler'
+
+ /**
+ * ------------------------------------------------------------------------
+ * Class Definition
+ * ------------------------------------------------------------------------
+ */
+
+ };
+ var Modal = function () {
+ function Modal(element, config) {
+ _classCallCheck(this, Modal);
+
+ this._config = this._getConfig(config);
+ this._element = element;
+ this._dialog = $(element).find(Selector.DIALOG)[0];
+ this._backdrop = null;
+ this._isShown = false;
+ this._isBodyOverflowing = false;
+ this._ignoreBackdropClick = false;
+ this._originalBodyPadding = 0;
+ this._scrollbarWidth = 0;
+ }
- this.$backdrop.addClass('in')
+ // getters
- if (!callback) return
+ // public
- doAnimate ?
- this.$backdrop
- .one('bsTransitionEnd', callback)
- .emulateTransitionEnd(Modal.BACKDROP_TRANSITION_DURATION) :
- callback()
+ Modal.prototype.toggle = function toggle(relatedTarget) {
+ return this._isShown ? this.hide() : this.show(relatedTarget);
+ };
- } else if (!this.isShown && this.$backdrop) {
- this.$backdrop.removeClass('in')
+ Modal.prototype.show = function show(relatedTarget) {
+ var _this10 = this;
- var callbackRemove = function () {
- that.removeBackdrop()
- callback && callback()
+ if (this._isTransitioning) {
+ return;
}
- $.support.transition && this.$element.hasClass('fade') ?
- this.$backdrop
- .one('bsTransitionEnd', callbackRemove)
- .emulateTransitionEnd(Modal.BACKDROP_TRANSITION_DURATION) :
- callbackRemove()
- } else if (callback) {
- callback()
- }
- }
+ if (Util.supportsTransitionEnd() && $(this._element).hasClass(ClassName.FADE)) {
+ this._isTransitioning = true;
+ }
- // these following methods are used to handle overflowing modals
+ var showEvent = $.Event(Event.SHOW, {
+ relatedTarget: relatedTarget
+ });
- Modal.prototype.handleUpdate = function () {
- this.adjustDialog()
- }
+ $(this._element).trigger(showEvent);
- Modal.prototype.adjustDialog = function () {
- var modalIsOverflowing = this.$element[0].scrollHeight > document.documentElement.clientHeight
+ if (this._isShown || showEvent.isDefaultPrevented()) {
+ return;
+ }
- this.$element.css({
- paddingLeft: !this.bodyIsOverflowing && modalIsOverflowing ? this.scrollbarWidth : '',
- paddingRight: this.bodyIsOverflowing && !modalIsOverflowing ? this.scrollbarWidth : ''
- })
- }
+ this._isShown = true;
- Modal.prototype.resetAdjustments = function () {
- this.$element.css({
- paddingLeft: '',
- paddingRight: ''
- })
- }
+ this._checkScrollbar();
+ this._setScrollbar();
- Modal.prototype.checkScrollbar = function () {
- var fullWindowWidth = window.innerWidth
- if (!fullWindowWidth) { // workaround for missing window.innerWidth in IE8
- var documentElementRect = document.documentElement.getBoundingClientRect()
- fullWindowWidth = documentElementRect.right - Math.abs(documentElementRect.left)
- }
- this.bodyIsOverflowing = document.body.clientWidth < fullWindowWidth
- this.scrollbarWidth = this.measureScrollbar()
- }
+ $(document.body).addClass(ClassName.OPEN);
- Modal.prototype.setScrollbar = function () {
- var bodyPad = parseInt((this.$body.css('padding-right') || 0), 10)
- this.originalBodyPad = document.body.style.paddingRight || ''
- if (this.bodyIsOverflowing) this.$body.css('padding-right', bodyPad + this.scrollbarWidth)
- }
+ this._setEscapeEvent();
+ this._setResizeEvent();
- Modal.prototype.resetScrollbar = function () {
- this.$body.css('padding-right', this.originalBodyPad)
- }
+ $(this._element).on(Event.CLICK_DISMISS, Selector.DATA_DISMISS, function (event) {
+ return _this10.hide(event);
+ });
- Modal.prototype.measureScrollbar = function () { // thx walsh
- var scrollDiv = document.createElement('div')
- scrollDiv.className = 'modal-scrollbar-measure'
- this.$body.append(scrollDiv)
- var scrollbarWidth = scrollDiv.offsetWidth - scrollDiv.clientWidth
- this.$body[0].removeChild(scrollDiv)
- return scrollbarWidth
- }
+ $(this._dialog).on(Event.MOUSEDOWN_DISMISS, function () {
+ $(_this10._element).one(Event.MOUSEUP_DISMISS, function (event) {
+ if ($(event.target).is(_this10._element)) {
+ _this10._ignoreBackdropClick = true;
+ }
+ });
+ });
+ this._showBackdrop(function () {
+ return _this10._showElement(relatedTarget);
+ });
+ };
- // MODAL PLUGIN DEFINITION
- // =======================
+ Modal.prototype.hide = function hide(event) {
+ var _this11 = this;
- function Plugin(option, _relatedTarget) {
- return this.each(function () {
- var $this = $(this)
- var data = $this.data('bs.modal')
- var options = $.extend({}, Modal.DEFAULTS, $this.data(), typeof option == 'object' && option)
+ if (event) {
+ event.preventDefault();
+ }
- if (!data) $this.data('bs.modal', (data = new Modal(this, options)))
- if (typeof option == 'string') data[option](_relatedTarget)
- else if (options.show) data.show(_relatedTarget)
- })
- }
+ if (this._isTransitioning || !this._isShown) {
+ return;
+ }
- var old = $.fn.modal
+ var transition = Util.supportsTransitionEnd() && $(this._element).hasClass(ClassName.FADE);
- $.fn.modal = Plugin
- $.fn.modal.Constructor = Modal
+ if (transition) {
+ this._isTransitioning = true;
+ }
+ var hideEvent = $.Event(Event.HIDE);
- // MODAL NO CONFLICT
- // =================
+ $(this._element).trigger(hideEvent);
- $.fn.modal.noConflict = function () {
- $.fn.modal = old
- return this
- }
+ if (!this._isShown || hideEvent.isDefaultPrevented()) {
+ return;
+ }
+ this._isShown = false;
- // MODAL DATA-API
- // ==============
+ this._setEscapeEvent();
+ this._setResizeEvent();
- $(document).on('click.bs.modal.data-api', '[data-toggle="modal"]', function (e) {
- var $this = $(this)
- var href = $this.attr('href')
- var $target = $($this.attr('data-target') || (href && href.replace(/.*(?=#[^\s]+$)/, ''))) // strip for ie7
- var option = $target.data('bs.modal') ? 'toggle' : $.extend({ remote: !/#/.test(href) && href }, $target.data(), $this.data())
+ $(document).off(Event.FOCUSIN);
- if ($this.is('a')) e.preventDefault()
+ $(this._element).removeClass(ClassName.SHOW);
- $target.one('show.bs.modal', function (showEvent) {
- if (showEvent.isDefaultPrevented()) return // only register focus restorer if modal will actually get shown
- $target.one('hidden.bs.modal', function () {
- $this.is(':visible') && $this.trigger('focus')
- })
- })
- Plugin.call($target, option, this)
- })
+ $(this._element).off(Event.CLICK_DISMISS);
+ $(this._dialog).off(Event.MOUSEDOWN_DISMISS);
-}(jQuery);
+ if (transition) {
-/* ========================================================================
- * Bootstrap: tooltip.js v3.3.7
- * http://getbootstrap.com/javascript/#tooltip
- * Inspired by the original jQuery.tipsy by Jason Frame
- * ========================================================================
- * Copyright 2011-2016 Twitter, Inc.
- * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
- * ======================================================================== */
+ $(this._element).one(Util.TRANSITION_END, function (event) {
+ return _this11._hideModal(event);
+ }).emulateTransitionEnd(TRANSITION_DURATION);
+ } else {
+ this._hideModal();
+ }
+ };
+ Modal.prototype.dispose = function dispose() {
+ $.removeData(this._element, DATA_KEY);
-+function ($) {
- 'use strict';
+ $(window, document, this._element, this._backdrop).off(EVENT_KEY);
- // TOOLTIP PUBLIC CLASS DEFINITION
- // ===============================
+ this._config = null;
+ this._element = null;
+ this._dialog = null;
+ this._backdrop = null;
+ this._isShown = null;
+ this._isBodyOverflowing = null;
+ this._ignoreBackdropClick = null;
+ this._scrollbarWidth = null;
+ };
- var Tooltip = function (element, options) {
- this.type = null
- this.options = null
- this.enabled = null
- this.timeout = null
- this.hoverState = null
- this.$element = null
- this.inState = null
+ Modal.prototype.handleUpdate = function handleUpdate() {
+ this._adjustDialog();
+ };
- this.init('tooltip', element, options)
- }
+ // private
- Tooltip.VERSION = '3.3.7'
+ Modal.prototype._getConfig = function _getConfig(config) {
+ config = $.extend({}, Default, config);
+ Util.typeCheckConfig(NAME, config, DefaultType);
+ return config;
+ };
- Tooltip.TRANSITION_DURATION = 150
+ Modal.prototype._showElement = function _showElement(relatedTarget) {
+ var _this12 = this;
- Tooltip.DEFAULTS = {
- animation: true,
- placement: 'top',
- selector: false,
- template: '<div class="tooltip" role="tooltip"><div class="tooltip-arrow"></div><div class="tooltip-inner"></div></div>',
- trigger: 'hover focus',
- title: '',
- delay: 0,
- html: false,
- container: false,
- viewport: {
- selector: 'body',
- padding: 0
- }
- }
+ var transition = Util.supportsTransitionEnd() && $(this._element).hasClass(ClassName.FADE);
- Tooltip.prototype.init = function (type, element, options) {
- this.enabled = true
- this.type = type
- this.$element = $(element)
- this.options = this.getOptions(options)
- this.$viewport = this.options.viewport && $($.isFunction(this.options.viewport) ? this.options.viewport.call(this, this.$element) : (this.options.viewport.selector || this.options.viewport))
- this.inState = { click: false, hover: false, focus: false }
+ if (!this._element.parentNode || this._element.parentNode.nodeType !== Node.ELEMENT_NODE) {
+ // don't move modals dom position
+ document.body.appendChild(this._element);
+ }
- if (this.$element[0] instanceof document.constructor && !this.options.selector) {
- throw new Error('`selector` option must be specified when initializing ' + this.type + ' on the window.document object!')
- }
+ this._element.style.display = 'block';
+ this._element.removeAttribute('aria-hidden');
+ this._element.scrollTop = 0;
+
+ if (transition) {
+ Util.reflow(this._element);
+ }
- var triggers = this.options.trigger.split(' ')
+ $(this._element).addClass(ClassName.SHOW);
- for (var i = triggers.length; i--;) {
- var trigger = triggers[i]
+ if (this._config.focus) {
+ this._enforceFocus();
+ }
- if (trigger == 'click') {
- this.$element.on('click.' + this.type, this.options.selector, $.proxy(this.toggle, this))
- } else if (trigger != 'manual') {
- var eventIn = trigger == 'hover' ? 'mouseenter' : 'focusin'
- var eventOut = trigger == 'hover' ? 'mouseleave' : 'focusout'
+ var shownEvent = $.Event(Event.SHOWN, {
+ relatedTarget: relatedTarget
+ });
- this.$element.on(eventIn + '.' + this.type, this.options.selector, $.proxy(this.enter, this))
- this.$element.on(eventOut + '.' + this.type, this.options.selector, $.proxy(this.leave, this))
+ var transitionComplete = function transitionComplete() {
+ if (_this12._config.focus) {
+ _this12._element.focus();
+ }
+ _this12._isTransitioning = false;
+ $(_this12._element).trigger(shownEvent);
+ };
+
+ if (transition) {
+ $(this._dialog).one(Util.TRANSITION_END, transitionComplete).emulateTransitionEnd(TRANSITION_DURATION);
+ } else {
+ transitionComplete();
}
- }
+ };
- this.options.selector ?
- (this._options = $.extend({}, this.options, { trigger: 'manual', selector: '' })) :
- this.fixTitle()
- }
+ Modal.prototype._enforceFocus = function _enforceFocus() {
+ var _this13 = this;
- Tooltip.prototype.getDefaults = function () {
- return Tooltip.DEFAULTS
- }
+ $(document).off(Event.FOCUSIN) // guard against infinite focus loop
+ .on(Event.FOCUSIN, function (event) {
+ if (document !== event.target && _this13._element !== event.target && !$(_this13._element).has(event.target).length) {
+ _this13._element.focus();
+ }
+ });
+ };
+
+ Modal.prototype._setEscapeEvent = function _setEscapeEvent() {
+ var _this14 = this;
+
+ if (this._isShown && this._config.keyboard) {
+ $(this._element).on(Event.KEYDOWN_DISMISS, function (event) {
+ if (event.which === ESCAPE_KEYCODE) {
+ event.preventDefault();
+ _this14.hide();
+ }
+ });
+ } else if (!this._isShown) {
+ $(this._element).off(Event.KEYDOWN_DISMISS);
+ }
+ };
- Tooltip.prototype.getOptions = function (options) {
- options = $.extend({}, this.getDefaults(), this.$element.data(), options)
+ Modal.prototype._setResizeEvent = function _setResizeEvent() {
+ var _this15 = this;
- if (options.delay && typeof options.delay == 'number') {
- options.delay = {
- show: options.delay,
- hide: options.delay
+ if (this._isShown) {
+ $(window).on(Event.RESIZE, function (event) {
+ return _this15.handleUpdate(event);
+ });
+ } else {
+ $(window).off(Event.RESIZE);
}
- }
+ };
+
+ Modal.prototype._hideModal = function _hideModal() {
+ var _this16 = this;
+
+ this._element.style.display = 'none';
+ this._element.setAttribute('aria-hidden', true);
+ this._isTransitioning = false;
+ this._showBackdrop(function () {
+ $(document.body).removeClass(ClassName.OPEN);
+ _this16._resetAdjustments();
+ _this16._resetScrollbar();
+ $(_this16._element).trigger(Event.HIDDEN);
+ });
+ };
+
+ Modal.prototype._removeBackdrop = function _removeBackdrop() {
+ if (this._backdrop) {
+ $(this._backdrop).remove();
+ this._backdrop = null;
+ }
+ };
- return options
- }
+ Modal.prototype._showBackdrop = function _showBackdrop(callback) {
+ var _this17 = this;
- Tooltip.prototype.getDelegateOptions = function () {
- var options = {}
- var defaults = this.getDefaults()
+ var animate = $(this._element).hasClass(ClassName.FADE) ? ClassName.FADE : '';
- this._options && $.each(this._options, function (key, value) {
- if (defaults[key] != value) options[key] = value
- })
+ if (this._isShown && this._config.backdrop) {
+ var doAnimate = Util.supportsTransitionEnd() && animate;
- return options
- }
+ this._backdrop = document.createElement('div');
+ this._backdrop.className = ClassName.BACKDROP;
- Tooltip.prototype.enter = function (obj) {
- var self = obj instanceof this.constructor ?
- obj : $(obj.currentTarget).data('bs.' + this.type)
+ if (animate) {
+ $(this._backdrop).addClass(animate);
+ }
- if (!self) {
- self = new this.constructor(obj.currentTarget, this.getDelegateOptions())
- $(obj.currentTarget).data('bs.' + this.type, self)
- }
+ $(this._backdrop).appendTo(document.body);
+
+ $(this._element).on(Event.CLICK_DISMISS, function (event) {
+ if (_this17._ignoreBackdropClick) {
+ _this17._ignoreBackdropClick = false;
+ return;
+ }
+ if (event.target !== event.currentTarget) {
+ return;
+ }
+ if (_this17._config.backdrop === 'static') {
+ _this17._element.focus();
+ } else {
+ _this17.hide();
+ }
+ });
+
+ if (doAnimate) {
+ Util.reflow(this._backdrop);
+ }
- if (obj instanceof $.Event) {
- self.inState[obj.type == 'focusin' ? 'focus' : 'hover'] = true
- }
+ $(this._backdrop).addClass(ClassName.SHOW);
- if (self.tip().hasClass('in') || self.hoverState == 'in') {
- self.hoverState = 'in'
- return
- }
+ if (!callback) {
+ return;
+ }
- clearTimeout(self.timeout)
+ if (!doAnimate) {
+ callback();
+ return;
+ }
- self.hoverState = 'in'
+ $(this._backdrop).one(Util.TRANSITION_END, callback).emulateTransitionEnd(BACKDROP_TRANSITION_DURATION);
+ } else if (!this._isShown && this._backdrop) {
+ $(this._backdrop).removeClass(ClassName.SHOW);
+
+ var callbackRemove = function callbackRemove() {
+ _this17._removeBackdrop();
+ if (callback) {
+ callback();
+ }
+ };
+
+ if (Util.supportsTransitionEnd() && $(this._element).hasClass(ClassName.FADE)) {
+ $(this._backdrop).one(Util.TRANSITION_END, callbackRemove).emulateTransitionEnd(BACKDROP_TRANSITION_DURATION);
+ } else {
+ callbackRemove();
+ }
+ } else if (callback) {
+ callback();
+ }
+ };
- if (!self.options.delay || !self.options.delay.show) return self.show()
+ // ----------------------------------------------------------------------
+ // the following methods are used to handle overflowing modals
+ // todo (fat): these should probably be refactored out of modal.js
+ // ----------------------------------------------------------------------
- self.timeout = setTimeout(function () {
- if (self.hoverState == 'in') self.show()
- }, self.options.delay.show)
- }
+ Modal.prototype._adjustDialog = function _adjustDialog() {
+ var isModalOverflowing = this._element.scrollHeight > document.documentElement.clientHeight;
- Tooltip.prototype.isInStateTrue = function () {
- for (var key in this.inState) {
- if (this.inState[key]) return true
- }
+ if (!this._isBodyOverflowing && isModalOverflowing) {
+ this._element.style.paddingLeft = this._scrollbarWidth + 'px';
+ }
- return false
- }
+ if (this._isBodyOverflowing && !isModalOverflowing) {
+ this._element.style.paddingRight = this._scrollbarWidth + 'px';
+ }
+ };
+
+ Modal.prototype._resetAdjustments = function _resetAdjustments() {
+ this._element.style.paddingLeft = '';
+ this._element.style.paddingRight = '';
+ };
+
+ Modal.prototype._checkScrollbar = function _checkScrollbar() {
+ this._isBodyOverflowing = document.body.clientWidth < window.innerWidth;
+ this._scrollbarWidth = this._getScrollbarWidth();
+ };
+
+ Modal.prototype._setScrollbar = function _setScrollbar() {
+ var _this18 = this;
+
+ if (this._isBodyOverflowing) {
+ // Note: DOMNode.style.paddingRight returns the actual value or '' if not set
+ // while $(DOMNode).css('padding-right') returns the calculated value or 0 if not set
+
+ // Adjust fixed content padding
+ $(Selector.FIXED_CONTENT).each(function (index, element) {
+ var actualPadding = $(element)[0].style.paddingRight;
+ var calculatedPadding = $(element).css('padding-right');
+ $(element).data('padding-right', actualPadding).css('padding-right', parseFloat(calculatedPadding) + _this18._scrollbarWidth + 'px');
+ });
+
+ // Adjust navbar-toggler margin
+ $(Selector.NAVBAR_TOGGLER).each(function (index, element) {
+ var actualMargin = $(element)[0].style.marginRight;
+ var calculatedMargin = $(element).css('margin-right');
+ $(element).data('margin-right', actualMargin).css('margin-right', parseFloat(calculatedMargin) + _this18._scrollbarWidth + 'px');
+ });
+
+ // Adjust body padding
+ var actualPadding = document.body.style.paddingRight;
+ var calculatedPadding = $('body').css('padding-right');
+ $('body').data('padding-right', actualPadding).css('padding-right', parseFloat(calculatedPadding) + this._scrollbarWidth + 'px');
+ }
+ };
+
+ Modal.prototype._resetScrollbar = function _resetScrollbar() {
+ // Restore fixed content padding
+ $(Selector.FIXED_CONTENT).each(function (index, element) {
+ var padding = $(element).data('padding-right');
+ if (typeof padding !== 'undefined') {
+ $(element).css('padding-right', padding).removeData('padding-right');
+ }
+ });
- Tooltip.prototype.leave = function (obj) {
- var self = obj instanceof this.constructor ?
- obj : $(obj.currentTarget).data('bs.' + this.type)
+ // Restore navbar-toggler margin
+ $(Selector.NAVBAR_TOGGLER).each(function (index, element) {
+ var margin = $(element).data('margin-right');
+ if (typeof margin !== 'undefined') {
+ $(element).css('margin-right', margin).removeData('margin-right');
+ }
+ });
- if (!self) {
- self = new this.constructor(obj.currentTarget, this.getDelegateOptions())
- $(obj.currentTarget).data('bs.' + this.type, self)
- }
+ // Restore body padding
+ var padding = $('body').data('padding-right');
+ if (typeof padding !== 'undefined') {
+ $('body').css('padding-right', padding).removeData('padding-right');
+ }
+ };
+
+ Modal.prototype._getScrollbarWidth = function _getScrollbarWidth() {
+ // thx d.walsh
+ var scrollDiv = document.createElement('div');
+ scrollDiv.className = ClassName.SCROLLBAR_MEASURER;
+ document.body.appendChild(scrollDiv);
+ var scrollbarWidth = scrollDiv.getBoundingClientRect().width - scrollDiv.clientWidth;
+ document.body.removeChild(scrollDiv);
+ return scrollbarWidth;
+ };
+
+ // static
+
+ Modal._jQueryInterface = function _jQueryInterface(config, relatedTarget) {
+ return this.each(function () {
+ var data = $(this).data(DATA_KEY);
+ var _config = $.extend({}, Modal.Default, $(this).data(), (typeof config === 'undefined' ? 'undefined' : _typeof(config)) === 'object' && config);
+
+ if (!data) {
+ data = new Modal(this, _config);
+ $(this).data(DATA_KEY, data);
+ }
- if (obj instanceof $.Event) {
- self.inState[obj.type == 'focusout' ? 'focus' : 'hover'] = false
- }
+ if (typeof config === 'string') {
+ if (data[config] === undefined) {
+ throw new Error('No method named "' + config + '"');
+ }
+ data[config](relatedTarget);
+ } else if (_config.show) {
+ data.show(relatedTarget);
+ }
+ });
+ };
- if (self.isInStateTrue()) return
+ _createClass(Modal, null, [{
+ key: 'VERSION',
+ get: function get() {
+ return VERSION;
+ }
+ }, {
+ key: 'Default',
+ get: function get() {
+ return Default;
+ }
+ }]);
- clearTimeout(self.timeout)
+ return Modal;
+ }();
- self.hoverState = 'out'
+ /**
+ * ------------------------------------------------------------------------
+ * Data Api implementation
+ * ------------------------------------------------------------------------
+ */
- if (!self.options.delay || !self.options.delay.hide) return self.hide()
+ $(document).on(Event.CLICK_DATA_API, Selector.DATA_TOGGLE, function (event) {
+ var _this19 = this;
- self.timeout = setTimeout(function () {
- if (self.hoverState == 'out') self.hide()
- }, self.options.delay.hide)
- }
+ var target = void 0;
+ var selector = Util.getSelectorFromElement(this);
- Tooltip.prototype.show = function () {
- var e = $.Event('show.bs.' + this.type)
+ if (selector) {
+ target = $(selector)[0];
+ }
- if (this.hasContent() && this.enabled) {
- this.$element.trigger(e)
+ var config = $(target).data(DATA_KEY) ? 'toggle' : $.extend({}, $(target).data(), $(this).data());
- var inDom = $.contains(this.$element[0].ownerDocument.documentElement, this.$element[0])
- if (e.isDefaultPrevented() || !inDom) return
- var that = this
+ if (this.tagName === 'A' || this.tagName === 'AREA') {
+ event.preventDefault();
+ }
- var $tip = this.tip()
+ var $target = $(target).one(Event.SHOW, function (showEvent) {
+ if (showEvent.isDefaultPrevented()) {
+ // only register focus restorer if modal will actually get shown
+ return;
+ }
- var tipId = this.getUID(this.type)
+ $target.one(Event.HIDDEN, function () {
+ if ($(_this19).is(':visible')) {
+ _this19.focus();
+ }
+ });
+ });
+
+ Modal._jQueryInterface.call($(target), config, this);
+ });
+
+ /**
+ * ------------------------------------------------------------------------
+ * jQuery
+ * ------------------------------------------------------------------------
+ */
+
+ $.fn[NAME] = Modal._jQueryInterface;
+ $.fn[NAME].Constructor = Modal;
+ $.fn[NAME].noConflict = function () {
+ $.fn[NAME] = JQUERY_NO_CONFLICT;
+ return Modal._jQueryInterface;
+ };
+
+ return Modal;
+}(jQuery);
- this.setContent()
- $tip.attr('id', tipId)
- this.$element.attr('aria-describedby', tipId)
+/**
+ * --------------------------------------------------------------------------
+ * Bootstrap (v4.0.0-beta): scrollspy.js
+ * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
+ * --------------------------------------------------------------------------
+ */
- if (this.options.animation) $tip.addClass('fade')
+var ScrollSpy = function ($) {
+
+ /**
+ * ------------------------------------------------------------------------
+ * Constants
+ * ------------------------------------------------------------------------
+ */
+
+ var NAME = 'scrollspy';
+ var VERSION = '4.0.0-beta';
+ var DATA_KEY = 'bs.scrollspy';
+ var EVENT_KEY = '.' + DATA_KEY;
+ var DATA_API_KEY = '.data-api';
+ var JQUERY_NO_CONFLICT = $.fn[NAME];
+
+ var Default = {
+ offset: 10,
+ method: 'auto',
+ target: ''
+ };
+
+ var DefaultType = {
+ offset: 'number',
+ method: 'string',
+ target: '(string|element)'
+ };
+
+ var Event = {
+ ACTIVATE: 'activate' + EVENT_KEY,
+ SCROLL: 'scroll' + EVENT_KEY,
+ LOAD_DATA_API: 'load' + EVENT_KEY + DATA_API_KEY
+ };
+
+ var ClassName = {
+ DROPDOWN_ITEM: 'dropdown-item',
+ DROPDOWN_MENU: 'dropdown-menu',
+ ACTIVE: 'active'
+ };
+
+ var Selector = {
+ DATA_SPY: '[data-spy="scroll"]',
+ ACTIVE: '.active',
+ NAV_LIST_GROUP: '.nav, .list-group',
+ NAV_LINKS: '.nav-link',
+ LIST_ITEMS: '.list-group-item',
+ DROPDOWN: '.dropdown',
+ DROPDOWN_ITEMS: '.dropdown-item',
+ DROPDOWN_TOGGLE: '.dropdown-toggle'
+ };
+
+ var OffsetMethod = {
+ OFFSET: 'offset',
+ POSITION: 'position'
+
+ /**
+ * ------------------------------------------------------------------------
+ * Class Definition
+ * ------------------------------------------------------------------------
+ */
+
+ };
+ var ScrollSpy = function () {
+ function ScrollSpy(element, config) {
+ var _this20 = this;
+
+ _classCallCheck(this, ScrollSpy);
+
+ this._element = element;
+ this._scrollElement = element.tagName === 'BODY' ? window : element;
+ this._config = this._getConfig(config);
+ this._selector = this._config.target + ' ' + Selector.NAV_LINKS + ',' + (this._config.target + ' ' + Selector.LIST_ITEMS + ',') + (this._config.target + ' ' + Selector.DROPDOWN_ITEMS);
+ this._offsets = [];
+ this._targets = [];
+ this._activeTarget = null;
+ this._scrollHeight = 0;
+
+ $(this._scrollElement).on(Event.SCROLL, function (event) {
+ return _this20._process(event);
+ });
+
+ this.refresh();
+ this._process();
+ }
- var placement = typeof this.options.placement == 'function' ?
- this.options.placement.call(this, $tip[0], this.$element[0]) :
- this.options.placement
+ // getters
- var autoToken = /\s?auto?\s?/i
- var autoPlace = autoToken.test(placement)
- if (autoPlace) placement = placement.replace(autoToken, '') || 'top'
+ // public
- $tip
- .detach()
- .css({ top: 0, left: 0, display: 'block' })
- .addClass(placement)
- .data('bs.' + this.type, this)
+ ScrollSpy.prototype.refresh = function refresh() {
+ var _this21 = this;
- this.options.container ? $tip.appendTo(this.options.container) : $tip.insertAfter(this.$element)
- this.$element.trigger('inserted.bs.' + this.type)
+ var autoMethod = this._scrollElement !== this._scrollElement.window ? OffsetMethod.POSITION : OffsetMethod.OFFSET;
- var pos = this.getPosition()
- var actualWidth = $tip[0].offsetWidth
- var actualHeight = $tip[0].offsetHeight
+ var offsetMethod = this._config.method === 'auto' ? autoMethod : this._config.method;
- if (autoPlace) {
- var orgPlacement = placement
- var viewportDim = this.getPosition(this.$viewport)
+ var offsetBase = offsetMethod === OffsetMethod.POSITION ? this._getScrollTop() : 0;
- placement = placement == 'bottom' && pos.bottom + actualHeight > viewportDim.bottom ? 'top' :
- placement == 'top' && pos.top - actualHeight < viewportDim.top ? 'bottom' :
- placement == 'right' && pos.right + actualWidth > viewportDim.width ? 'left' :
- placement == 'left' && pos.left - actualWidth < viewportDim.left ? 'right' :
- placement
+ this._offsets = [];
+ this._targets = [];
- $tip
- .removeClass(orgPlacement)
- .addClass(placement)
- }
+ this._scrollHeight = this._getScrollHeight();
- var calculatedOffset = this.getCalculatedOffset(placement, pos, actualWidth, actualHeight)
+ var targets = $.makeArray($(this._selector));
- this.applyPlacement(calculatedOffset, placement)
+ targets.map(function (element) {
+ var target = void 0;
+ var targetSelector = Util.getSelectorFromElement(element);
- var complete = function () {
- var prevHoverState = that.hoverState
- that.$element.trigger('shown.bs.' + that.type)
- that.hoverState = null
+ if (targetSelector) {
+ target = $(targetSelector)[0];
+ }
- if (prevHoverState == 'out') that.leave(that)
+ if (target) {
+ var targetBCR = target.getBoundingClientRect();
+ if (targetBCR.width || targetBCR.height) {
+ // todo (fat): remove sketch reliance on jQuery position/offset
+ return [$(target)[offsetMethod]().top + offsetBase, targetSelector];
+ }
+ }
+ return null;
+ }).filter(function (item) {
+ return item;
+ }).sort(function (a, b) {
+ return a[0] - b[0];
+ }).forEach(function (item) {
+ _this21._offsets.push(item[0]);
+ _this21._targets.push(item[1]);
+ });
+ };
+
+ ScrollSpy.prototype.dispose = function dispose() {
+ $.removeData(this._element, DATA_KEY);
+ $(this._scrollElement).off(EVENT_KEY);
+
+ this._element = null;
+ this._scrollElement = null;
+ this._config = null;
+ this._selector = null;
+ this._offsets = null;
+ this._targets = null;
+ this._activeTarget = null;
+ this._scrollHeight = null;
+ };
+
+ // private
+
+ ScrollSpy.prototype._getConfig = function _getConfig(config) {
+ config = $.extend({}, Default, config);
+
+ if (typeof config.target !== 'string') {
+ var id = $(config.target).attr('id');
+ if (!id) {
+ id = Util.getUID(NAME);
+ $(config.target).attr('id', id);
+ }
+ config.target = '#' + id;
}
- $.support.transition && this.$tip.hasClass('fade') ?
- $tip
- .one('bsTransitionEnd', complete)
- .emulateTransitionEnd(Tooltip.TRANSITION_DURATION) :
- complete()
- }
- }
+ Util.typeCheckConfig(NAME, config, DefaultType);
- Tooltip.prototype.applyPlacement = function (offset, placement) {
- var $tip = this.tip()
- var width = $tip[0].offsetWidth
- var height = $tip[0].offsetHeight
+ return config;
+ };
- // manually read margins because getBoundingClientRect includes difference
- var marginTop = parseInt($tip.css('margin-top'), 10)
- var marginLeft = parseInt($tip.css('margin-left'), 10)
+ ScrollSpy.prototype._getScrollTop = function _getScrollTop() {
+ return this._scrollElement === window ? this._scrollElement.pageYOffset : this._scrollElement.scrollTop;
+ };
- // we must check for NaN for ie 8/9
- if (isNaN(marginTop)) marginTop = 0
- if (isNaN(marginLeft)) marginLeft = 0
+ ScrollSpy.prototype._getScrollHeight = function _getScrollHeight() {
+ return this._scrollElement.scrollHeight || Math.max(document.body.scrollHeight, document.documentElement.scrollHeight);
+ };
- offset.top += marginTop
- offset.left += marginLeft
+ ScrollSpy.prototype._getOffsetHeight = function _getOffsetHeight() {
+ return this._scrollElement === window ? window.innerHeight : this._scrollElement.getBoundingClientRect().height;
+ };
- // $.fn.offset doesn't round pixel values
- // so we use setOffset directly with our own function B-0
- $.offset.setOffset($tip[0], $.extend({
- using: function (props) {
- $tip.css({
- top: Math.round(props.top),
- left: Math.round(props.left)
- })
- }
- }, offset), 0)
+ ScrollSpy.prototype._process = function _process() {
+ var scrollTop = this._getScrollTop() + this._config.offset;
+ var scrollHeight = this._getScrollHeight();
+ var maxScroll = this._config.offset + scrollHeight - this._getOffsetHeight();
- $tip.addClass('in')
+ if (this._scrollHeight !== scrollHeight) {
+ this.refresh();
+ }
- // check to see if placing tip in new offset caused the tip to resize itself
- var actualWidth = $tip[0].offsetWidth
- var actualHeight = $tip[0].offsetHeight
+ if (scrollTop >= maxScroll) {
+ var target = this._targets[this._targets.length - 1];
- if (placement == 'top' && actualHeight != height) {
- offset.top = offset.top + height - actualHeight
- }
-
- var delta = this.getViewportAdjustedDelta(placement, offset, actualWidth, actualHeight)
+ if (this._activeTarget !== target) {
+ this._activate(target);
+ }
+ return;
+ }
- if (delta.left) offset.left += delta.left
- else offset.top += delta.top
+ if (this._activeTarget && scrollTop < this._offsets[0] && this._offsets[0] > 0) {
+ this._activeTarget = null;
+ this._clear();
+ return;
+ }
- var isVertical = /top|bottom/.test(placement)
- var arrowDelta = isVertical ? delta.left * 2 - width + actualWidth : delta.top * 2 - height + actualHeight
- var arrowOffsetPosition = isVertical ? 'offsetWidth' : 'offsetHeight'
+ for (var i = this._offsets.length; i--;) {
+ var isActiveTarget = this._activeTarget !== this._targets[i] && scrollTop >= this._offsets[i] && (this._offsets[i + 1] === undefined || scrollTop < this._offsets[i + 1]);
- $tip.offset(offset)
- this.replaceArrow(arrowDelta, $tip[0][arrowOffsetPosition], isVertical)
- }
+ if (isActiveTarget) {
+ this._activate(this._targets[i]);
+ }
+ }
+ };
- Tooltip.prototype.replaceArrow = function (delta, dimension, isVertical) {
- this.arrow()
- .css(isVertical ? 'left' : 'top', 50 * (1 - delta / dimension) + '%')
- .css(isVertical ? 'top' : 'left', '')
- }
+ ScrollSpy.prototype._activate = function _activate(target) {
+ this._activeTarget = target;
- Tooltip.prototype.setContent = function () {
- var $tip = this.tip()
- var title = this.getTitle()
+ this._clear();
- $tip.find('.tooltip-inner')[this.options.html ? 'html' : 'text'](title)
- $tip.removeClass('fade in top bottom left right')
- }
+ var queries = this._selector.split(',');
+ queries = queries.map(function (selector) {
+ return selector + '[data-target="' + target + '"],' + (selector + '[href="' + target + '"]');
+ });
- Tooltip.prototype.hide = function (callback) {
- var that = this
- var $tip = $(this.$tip)
- var e = $.Event('hide.bs.' + this.type)
+ var $link = $(queries.join(','));
- function complete() {
- if (that.hoverState != 'in') $tip.detach()
- if (that.$element) { // TODO: Check whether guarding this code with this `if` is really necessary.
- that.$element
- .removeAttr('aria-describedby')
- .trigger('hidden.bs.' + that.type)
+ if ($link.hasClass(ClassName.DROPDOWN_ITEM)) {
+ $link.closest(Selector.DROPDOWN).find(Selector.DROPDOWN_TOGGLE).addClass(ClassName.ACTIVE);
+ $link.addClass(ClassName.ACTIVE);
+ } else {
+ // Set triggered link as active
+ $link.addClass(ClassName.ACTIVE);
+ // Set triggered links parents as active
+ // With both <ul> and <nav> markup a parent is the previous sibling of any nav ancestor
+ $link.parents(Selector.NAV_LIST_GROUP).prev(Selector.NAV_LINKS + ', ' + Selector.LIST_ITEMS).addClass(ClassName.ACTIVE);
}
- callback && callback()
- }
- this.$element.trigger(e)
+ $(this._scrollElement).trigger(Event.ACTIVATE, {
+ relatedTarget: target
+ });
+ };
- if (e.isDefaultPrevented()) return
+ ScrollSpy.prototype._clear = function _clear() {
+ $(this._selector).filter(Selector.ACTIVE).removeClass(ClassName.ACTIVE);
+ };
- $tip.removeClass('in')
+ // static
- $.support.transition && $tip.hasClass('fade') ?
- $tip
- .one('bsTransitionEnd', complete)
- .emulateTransitionEnd(Tooltip.TRANSITION_DURATION) :
- complete()
+ ScrollSpy._jQueryInterface = function _jQueryInterface(config) {
+ return this.each(function () {
+ var data = $(this).data(DATA_KEY);
+ var _config = (typeof config === 'undefined' ? 'undefined' : _typeof(config)) === 'object' && config;
- this.hoverState = null
+ if (!data) {
+ data = new ScrollSpy(this, _config);
+ $(this).data(DATA_KEY, data);
+ }
- return this
- }
+ if (typeof config === 'string') {
+ if (data[config] === undefined) {
+ throw new Error('No method named "' + config + '"');
+ }
+ data[config]();
+ }
+ });
+ };
- Tooltip.prototype.fixTitle = function () {
- var $e = this.$element
- if ($e.attr('title') || typeof $e.attr('data-original-title') != 'string') {
- $e.attr('data-original-title', $e.attr('title') || '').attr('title', '')
- }
- }
+ _createClass(ScrollSpy, null, [{
+ key: 'VERSION',
+ get: function get() {
+ return VERSION;
+ }
+ }, {
+ key: 'Default',
+ get: function get() {
+ return Default;
+ }
+ }]);
- Tooltip.prototype.hasContent = function () {
- return this.getTitle()
- }
+ return ScrollSpy;
+ }();
- Tooltip.prototype.getPosition = function ($element) {
- $element = $element || this.$element
+ /**
+ * ------------------------------------------------------------------------
+ * Data Api implementation
+ * ------------------------------------------------------------------------
+ */
- var el = $element[0]
- var isBody = el.tagName == 'BODY'
+ $(window).on(Event.LOAD_DATA_API, function () {
+ var scrollSpys = $.makeArray($(Selector.DATA_SPY));
- var elRect = el.getBoundingClientRect()
- if (elRect.width == null) {
- // width and height are missing in IE8, so compute them manually; see https://github.com/twbs/bootstrap/issues/14093
- elRect = $.extend({}, elRect, { width: elRect.right - elRect.left, height: elRect.bottom - elRect.top })
+ for (var i = scrollSpys.length; i--;) {
+ var $spy = $(scrollSpys[i]);
+ ScrollSpy._jQueryInterface.call($spy, $spy.data());
}
- var isSvg = window.SVGElement && el instanceof window.SVGElement
- // Avoid using $.offset() on SVGs since it gives incorrect results in jQuery 3.
- // See https://github.com/twbs/bootstrap/issues/20280
- var elOffset = isBody ? { top: 0, left: 0 } : (isSvg ? null : $element.offset())
- var scroll = { scroll: isBody ? document.documentElement.scrollTop || document.body.scrollTop : $element.scrollTop() }
- var outerDims = isBody ? { width: $(window).width(), height: $(window).height() } : null
-
- return $.extend({}, elRect, scroll, outerDims, elOffset)
- }
-
- Tooltip.prototype.getCalculatedOffset = function (placement, pos, actualWidth, actualHeight) {
- return placement == 'bottom' ? { top: pos.top + pos.height, left: pos.left + pos.width / 2 - actualWidth / 2 } :
- placement == 'top' ? { top: pos.top - actualHeight, left: pos.left + pos.width / 2 - actualWidth / 2 } :
- placement == 'left' ? { top: pos.top + pos.height / 2 - actualHeight / 2, left: pos.left - actualWidth } :
- /* placement == 'right' */ { top: pos.top + pos.height / 2 - actualHeight / 2, left: pos.left + pos.width }
+ });
+
+ /**
+ * ------------------------------------------------------------------------
+ * jQuery
+ * ------------------------------------------------------------------------
+ */
+
+ $.fn[NAME] = ScrollSpy._jQueryInterface;
+ $.fn[NAME].Constructor = ScrollSpy;
+ $.fn[NAME].noConflict = function () {
+ $.fn[NAME] = JQUERY_NO_CONFLICT;
+ return ScrollSpy._jQueryInterface;
+ };
+
+ return ScrollSpy;
+}(jQuery);
- }
+/**
+ * --------------------------------------------------------------------------
+ * Bootstrap (v4.0.0-beta): tab.js
+ * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
+ * --------------------------------------------------------------------------
+ */
- Tooltip.prototype.getViewportAdjustedDelta = function (placement, pos, actualWidth, actualHeight) {
- var delta = { top: 0, left: 0 }
- if (!this.$viewport) return delta
-
- var viewportPadding = this.options.viewport && this.options.viewport.padding || 0
- var viewportDimensions = this.getPosition(this.$viewport)
-
- if (/right|left/.test(placement)) {
- var topEdgeOffset = pos.top - viewportPadding - viewportDimensions.scroll
- var bottomEdgeOffset = pos.top + viewportPadding - viewportDimensions.scroll + actualHeight
- if (topEdgeOffset < viewportDimensions.top) { // top overflow
- delta.top = viewportDimensions.top - topEdgeOffset
- } else if (bottomEdgeOffset > viewportDimensions.top + viewportDimensions.height) { // bottom overflow
- delta.top = viewportDimensions.top + viewportDimensions.height - bottomEdgeOffset
- }
- } else {
- var leftEdgeOffset = pos.left - viewportPadding
- var rightEdgeOffset = pos.left + viewportPadding + actualWidth
- if (leftEdgeOffset < viewportDimensions.left) { // left overflow
- delta.left = viewportDimensions.left - leftEdgeOffset
- } else if (rightEdgeOffset > viewportDimensions.right) { // right overflow
- delta.left = viewportDimensions.left + viewportDimensions.width - rightEdgeOffset
- }
+var Tab = function ($) {
+
+ /**
+ * ------------------------------------------------------------------------
+ * Constants
+ * ------------------------------------------------------------------------
+ */
+
+ var NAME = 'tab';
+ var VERSION = '4.0.0-beta';
+ var DATA_KEY = 'bs.tab';
+ var EVENT_KEY = '.' + DATA_KEY;
+ var DATA_API_KEY = '.data-api';
+ var JQUERY_NO_CONFLICT = $.fn[NAME];
+ var TRANSITION_DURATION = 150;
+
+ var Event = {
+ HIDE: 'hide' + EVENT_KEY,
+ HIDDEN: 'hidden' + EVENT_KEY,
+ SHOW: 'show' + EVENT_KEY,
+ SHOWN: 'shown' + EVENT_KEY,
+ CLICK_DATA_API: 'click' + EVENT_KEY + DATA_API_KEY
+ };
+
+ var ClassName = {
+ DROPDOWN_MENU: 'dropdown-menu',
+ ACTIVE: 'active',
+ DISABLED: 'disabled',
+ FADE: 'fade',
+ SHOW: 'show'
+ };
+
+ var Selector = {
+ DROPDOWN: '.dropdown',
+ NAV_LIST_GROUP: '.nav, .list-group',
+ ACTIVE: '.active',
+ DATA_TOGGLE: '[data-toggle="tab"], [data-toggle="pill"], [data-toggle="list"]',
+ DROPDOWN_TOGGLE: '.dropdown-toggle',
+ DROPDOWN_ACTIVE_CHILD: '> .dropdown-menu .active'
+
+ /**
+ * ------------------------------------------------------------------------
+ * Class Definition
+ * ------------------------------------------------------------------------
+ */
+
+ };
+ var Tab = function () {
+ function Tab(element) {
+ _classCallCheck(this, Tab);
+
+ this._element = element;
}
- return delta
- }
+ // getters
- Tooltip.prototype.getTitle = function () {
- var title
- var $e = this.$element
- var o = this.options
+ // public
- title = $e.attr('data-original-title')
- || (typeof o.title == 'function' ? o.title.call($e[0]) : o.title)
+ Tab.prototype.show = function show() {
+ var _this22 = this;
- return title
- }
+ if (this._element.parentNode && this._element.parentNode.nodeType === Node.ELEMENT_NODE && $(this._element).hasClass(ClassName.ACTIVE) || $(this._element).hasClass(ClassName.DISABLED)) {
+ return;
+ }
- Tooltip.prototype.getUID = function (prefix) {
- do prefix += ~~(Math.random() * 1000000)
- while (document.getElementById(prefix))
- return prefix
- }
+ var target = void 0;
+ var previous = void 0;
+ var listElement = $(this._element).closest(Selector.NAV_LIST_GROUP)[0];
+ var selector = Util.getSelectorFromElement(this._element);
- Tooltip.prototype.tip = function () {
- if (!this.$tip) {
- this.$tip = $(this.options.template)
- if (this.$tip.length != 1) {
- throw new Error(this.type + ' `template` option must consist of exactly 1 top-level element!')
+ if (listElement) {
+ previous = $.makeArray($(listElement).find(Selector.ACTIVE));
+ previous = previous[previous.length - 1];
}
- }
- return this.$tip
- }
- Tooltip.prototype.arrow = function () {
- return (this.$arrow = this.$arrow || this.tip().find('.tooltip-arrow'))
- }
+ var hideEvent = $.Event(Event.HIDE, {
+ relatedTarget: this._element
+ });
- Tooltip.prototype.enable = function () {
- this.enabled = true
- }
+ var showEvent = $.Event(Event.SHOW, {
+ relatedTarget: previous
+ });
- Tooltip.prototype.disable = function () {
- this.enabled = false
- }
+ if (previous) {
+ $(previous).trigger(hideEvent);
+ }
- Tooltip.prototype.toggleEnabled = function () {
- this.enabled = !this.enabled
- }
+ $(this._element).trigger(showEvent);
- Tooltip.prototype.toggle = function (e) {
- var self = this
- if (e) {
- self = $(e.currentTarget).data('bs.' + this.type)
- if (!self) {
- self = new this.constructor(e.currentTarget, this.getDelegateOptions())
- $(e.currentTarget).data('bs.' + this.type, self)
+ if (showEvent.isDefaultPrevented() || hideEvent.isDefaultPrevented()) {
+ return;
}
- }
-
- if (e) {
- self.inState.click = !self.inState.click
- if (self.isInStateTrue()) self.enter(self)
- else self.leave(self)
- } else {
- self.tip().hasClass('in') ? self.leave(self) : self.enter(self)
- }
- }
- Tooltip.prototype.destroy = function () {
- var that = this
- clearTimeout(this.timeout)
- this.hide(function () {
- that.$element.off('.' + that.type).removeData('bs.' + that.type)
- if (that.$tip) {
- that.$tip.detach()
- }
- that.$tip = null
- that.$arrow = null
- that.$viewport = null
- that.$element = null
- })
- }
+ if (selector) {
+ target = $(selector)[0];
+ }
+ this._activate(this._element, listElement);
- // TOOLTIP PLUGIN DEFINITION
- // =========================
+ var complete = function complete() {
+ var hiddenEvent = $.Event(Event.HIDDEN, {
+ relatedTarget: _this22._element
+ });
- function Plugin(option) {
- return this.each(function () {
- var $this = $(this)
- var data = $this.data('bs.tooltip')
- var options = typeof option == 'object' && option
+ var shownEvent = $.Event(Event.SHOWN, {
+ relatedTarget: previous
+ });
- if (!data && /destroy|hide/.test(option)) return
- if (!data) $this.data('bs.tooltip', (data = new Tooltip(this, options)))
- if (typeof option == 'string') data[option]()
- })
- }
+ $(previous).trigger(hiddenEvent);
+ $(_this22._element).trigger(shownEvent);
+ };
- var old = $.fn.tooltip
+ if (target) {
+ this._activate(target, target.parentNode, complete);
+ } else {
+ complete();
+ }
+ };
- $.fn.tooltip = Plugin
- $.fn.tooltip.Constructor = Tooltip
+ Tab.prototype.dispose = function dispose() {
+ $.removeData(this._element, DATA_KEY);
+ this._element = null;
+ };
+ // private
- // TOOLTIP NO CONFLICT
- // ===================
+ Tab.prototype._activate = function _activate(element, container, callback) {
+ var _this23 = this;
- $.fn.tooltip.noConflict = function () {
- $.fn.tooltip = old
- return this
- }
+ var active = $(container).find(Selector.ACTIVE)[0];
+ var isTransitioning = callback && Util.supportsTransitionEnd() && active && $(active).hasClass(ClassName.FADE);
-}(jQuery);
+ var complete = function complete() {
+ return _this23._transitionComplete(element, active, isTransitioning, callback);
+ };
-/* ========================================================================
- * Bootstrap: popover.js v3.3.7
- * http://getbootstrap.com/javascript/#popovers
- * ========================================================================
- * Copyright 2011-2016 Twitter, Inc.
- * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
- * ======================================================================== */
+ if (active && isTransitioning) {
+ $(active).one(Util.TRANSITION_END, complete).emulateTransitionEnd(TRANSITION_DURATION);
+ } else {
+ complete();
+ }
+ if (active) {
+ $(active).removeClass(ClassName.SHOW);
+ }
+ };
-+function ($) {
- 'use strict';
+ Tab.prototype._transitionComplete = function _transitionComplete(element, active, isTransitioning, callback) {
+ if (active) {
+ $(active).removeClass(ClassName.ACTIVE);
- // POPOVER PUBLIC CLASS DEFINITION
- // ===============================
+ var dropdownChild = $(active.parentNode).find(Selector.DROPDOWN_ACTIVE_CHILD)[0];
- var Popover = function (element, options) {
- this.init('popover', element, options)
- }
+ if (dropdownChild) {
+ $(dropdownChild).removeClass(ClassName.ACTIVE);
+ }
- if (!$.fn.tooltip) throw new Error('Popover requires tooltip.js')
+ active.setAttribute('aria-expanded', false);
+ }
- Popover.VERSION = '3.3.7'
+ $(element).addClass(ClassName.ACTIVE);
+ element.setAttribute('aria-expanded', true);
- Popover.DEFAULTS = $.extend({}, $.fn.tooltip.Constructor.DEFAULTS, {
- placement: 'right',
- trigger: 'click',
- content: '',
- template: '<div class="popover" role="tooltip"><div class="arrow"></div><h3 class="popover-title"></h3><div class="popover-content"></div></div>'
- })
+ if (isTransitioning) {
+ Util.reflow(element);
+ $(element).addClass(ClassName.SHOW);
+ } else {
+ $(element).removeClass(ClassName.FADE);
+ }
+ if (element.parentNode && $(element.parentNode).hasClass(ClassName.DROPDOWN_MENU)) {
- // NOTE: POPOVER EXTENDS tooltip.js
- // ================================
+ var dropdownElement = $(element).closest(Selector.DROPDOWN)[0];
+ if (dropdownElement) {
+ $(dropdownElement).find(Selector.DROPDOWN_TOGGLE).addClass(ClassName.ACTIVE);
+ }
- Popover.prototype = $.extend({}, $.fn.tooltip.Constructor.prototype)
+ element.setAttribute('aria-expanded', true);
+ }
- Popover.prototype.constructor = Popover
+ if (callback) {
+ callback();
+ }
+ };
- Popover.prototype.getDefaults = function () {
- return Popover.DEFAULTS
- }
+ // static
- Popover.prototype.setContent = function () {
- var $tip = this.tip()
- var title = this.getTitle()
- var content = this.getContent()
+ Tab._jQueryInterface = function _jQueryInterface(config) {
+ return this.each(function () {
+ var $this = $(this);
+ var data = $this.data(DATA_KEY);
- $tip.find('.popover-title')[this.options.html ? 'html' : 'text'](title)
- $tip.find('.popover-content').children().detach().end()[ // we use append for html objects to maintain js events
- this.options.html ? (typeof content == 'string' ? 'html' : 'append') : 'text'
- ](content)
+ if (!data) {
+ data = new Tab(this);
+ $this.data(DATA_KEY, data);
+ }
- $tip.removeClass('fade top bottom left right in')
+ if (typeof config === 'string') {
+ if (data[config] === undefined) {
+ throw new Error('No method named "' + config + '"');
+ }
+ data[config]();
+ }
+ });
+ };
- // IE8 doesn't accept hiding via the `:empty` pseudo selector, we have to do
- // this manually by checking the contents.
- if (!$tip.find('.popover-title').html()) $tip.find('.popover-title').hide()
- }
+ _createClass(Tab, null, [{
+ key: 'VERSION',
+ get: function get() {
+ return VERSION;
+ }
+ }]);
+
+ return Tab;
+ }();
+
+ /**
+ * ------------------------------------------------------------------------
+ * Data Api implementation
+ * ------------------------------------------------------------------------
+ */
+
+ $(document).on(Event.CLICK_DATA_API, Selector.DATA_TOGGLE, function (event) {
+ event.preventDefault();
+ Tab._jQueryInterface.call($(this), 'show');
+ });
+
+ /**
+ * ------------------------------------------------------------------------
+ * jQuery
+ * ------------------------------------------------------------------------
+ */
+
+ $.fn[NAME] = Tab._jQueryInterface;
+ $.fn[NAME].Constructor = Tab;
+ $.fn[NAME].noConflict = function () {
+ $.fn[NAME] = JQUERY_NO_CONFLICT;
+ return Tab._jQueryInterface;
+ };
+
+ return Tab;
+}(jQuery);
- Popover.prototype.hasContent = function () {
- return this.getTitle() || this.getContent()
- }
+/* global Popper */
- Popover.prototype.getContent = function () {
- var $e = this.$element
- var o = this.options
+/**
+ * --------------------------------------------------------------------------
+ * Bootstrap (v4.0.0-beta): tooltip.js
+ * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
+ * --------------------------------------------------------------------------
+ */
- return $e.attr('data-content')
- || (typeof o.content == 'function' ?
- o.content.call($e[0]) :
- o.content)
- }
+var Tooltip = function ($) {
+
+ /**
+ * Check for Popper dependency
+ * Popper - https://popper.js.org
+ */
+ if (typeof Popper === 'undefined') {
+ throw new Error('Bootstrap tooltips require Popper.js (https://popper.js.org)');
+ }
+
+ /**
+ * ------------------------------------------------------------------------
+ * Constants
+ * ------------------------------------------------------------------------
+ */
+
+ var NAME = 'tooltip';
+ var VERSION = '4.0.0-beta';
+ var DATA_KEY = 'bs.tooltip';
+ var EVENT_KEY = '.' + DATA_KEY;
+ var JQUERY_NO_CONFLICT = $.fn[NAME];
+ var TRANSITION_DURATION = 150;
+ var CLASS_PREFIX = 'bs-tooltip';
+ var BSCLS_PREFIX_REGEX = new RegExp('(^|\\s)' + CLASS_PREFIX + '\\S+', 'g');
+
+ var DefaultType = {
+ animation: 'boolean',
+ template: 'string',
+ title: '(string|element|function)',
+ trigger: 'string',
+ delay: '(number|object)',
+ html: 'boolean',
+ selector: '(string|boolean)',
+ placement: '(string|function)',
+ offset: '(number|string)',
+ container: '(string|element|boolean)',
+ fallbackPlacement: '(string|array)'
+ };
+
+ var AttachmentMap = {
+ AUTO: 'auto',
+ TOP: 'top',
+ RIGHT: 'right',
+ BOTTOM: 'bottom',
+ LEFT: 'left'
+ };
+
+ var Default = {
+ animation: true,
+ template: '<div class="tooltip" role="tooltip">' + '<div class="arrow"></div>' + '<div class="tooltip-inner"></div></div>',
+ trigger: 'hover focus',
+ title: '',
+ delay: 0,
+ html: false,
+ selector: false,
+ placement: 'top',
+ offset: 0,
+ container: false,
+ fallbackPlacement: 'flip'
+ };
+
+ var HoverState = {
+ SHOW: 'show',
+ OUT: 'out'
+ };
+
+ var Event = {
+ HIDE: 'hide' + EVENT_KEY,
+ HIDDEN: 'hidden' + EVENT_KEY,
+ SHOW: 'show' + EVENT_KEY,
+ SHOWN: 'shown' + EVENT_KEY,
+ INSERTED: 'inserted' + EVENT_KEY,
+ CLICK: 'click' + EVENT_KEY,
+ FOCUSIN: 'focusin' + EVENT_KEY,
+ FOCUSOUT: 'focusout' + EVENT_KEY,
+ MOUSEENTER: 'mouseenter' + EVENT_KEY,
+ MOUSELEAVE: 'mouseleave' + EVENT_KEY
+ };
+
+ var ClassName = {
+ FADE: 'fade',
+ SHOW: 'show'
+ };
+
+ var Selector = {
+ TOOLTIP: '.tooltip',
+ TOOLTIP_INNER: '.tooltip-inner',
+ ARROW: '.arrow'
+ };
+
+ var Trigger = {
+ HOVER: 'hover',
+ FOCUS: 'focus',
+ CLICK: 'click',
+ MANUAL: 'manual'
+
+ /**
+ * ------------------------------------------------------------------------
+ * Class Definition
+ * ------------------------------------------------------------------------
+ */
+
+ };
+ var Tooltip = function () {
+ function Tooltip(element, config) {
+ _classCallCheck(this, Tooltip);
+
+ // private
+ this._isEnabled = true;
+ this._timeout = 0;
+ this._hoverState = '';
+ this._activeTrigger = {};
+ this._popper = null;
+
+ // protected
+ this.element = element;
+ this.config = this._getConfig(config);
+ this.tip = null;
+
+ this._setListeners();
+ }
- Popover.prototype.arrow = function () {
- return (this.$arrow = this.$arrow || this.tip().find('.arrow'))
- }
+ // getters
+ // public
- // POPOVER PLUGIN DEFINITION
- // =========================
+ Tooltip.prototype.enable = function enable() {
+ this._isEnabled = true;
+ };
- function Plugin(option) {
- return this.each(function () {
- var $this = $(this)
- var data = $this.data('bs.popover')
- var options = typeof option == 'object' && option
+ Tooltip.prototype.disable = function disable() {
+ this._isEnabled = false;
+ };
- if (!data && /destroy|hide/.test(option)) return
- if (!data) $this.data('bs.popover', (data = new Popover(this, options)))
- if (typeof option == 'string') data[option]()
- })
- }
+ Tooltip.prototype.toggleEnabled = function toggleEnabled() {
+ this._isEnabled = !this._isEnabled;
+ };
- var old = $.fn.popover
+ Tooltip.prototype.toggle = function toggle(event) {
+ if (event) {
+ var dataKey = this.constructor.DATA_KEY;
+ var context = $(event.currentTarget).data(dataKey);
- $.fn.popover = Plugin
- $.fn.popover.Constructor = Popover
+ if (!context) {
+ context = new this.constructor(event.currentTarget, this._getDelegateConfig());
+ $(event.currentTarget).data(dataKey, context);
+ }
+ context._activeTrigger.click = !context._activeTrigger.click;
- // POPOVER NO CONFLICT
- // ===================
+ if (context._isWithActiveTrigger()) {
+ context._enter(null, context);
+ } else {
+ context._leave(null, context);
+ }
+ } else {
- $.fn.popover.noConflict = function () {
- $.fn.popover = old
- return this
- }
+ if ($(this.getTipElement()).hasClass(ClassName.SHOW)) {
+ this._leave(null, this);
+ return;
+ }
-}(jQuery);
+ this._enter(null, this);
+ }
+ };
-/* ========================================================================
- * Bootstrap: scrollspy.js v3.3.7
- * http://getbootstrap.com/javascript/#scrollspy
- * ========================================================================
- * Copyright 2011-2016 Twitter, Inc.
- * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
- * ======================================================================== */
+ Tooltip.prototype.dispose = function dispose() {
+ clearTimeout(this._timeout);
+ $.removeData(this.element, this.constructor.DATA_KEY);
-+function ($) {
- 'use strict';
+ $(this.element).off(this.constructor.EVENT_KEY);
+ $(this.element).closest('.modal').off('hide.bs.modal');
- // SCROLLSPY CLASS DEFINITION
- // ==========================
+ if (this.tip) {
+ $(this.tip).remove();
+ }
- function ScrollSpy(element, options) {
- this.$body = $(document.body)
- this.$scrollElement = $(element).is(document.body) ? $(window) : $(element)
- this.options = $.extend({}, ScrollSpy.DEFAULTS, options)
- this.selector = (this.options.target || '') + ' .nav li > a'
- this.offsets = []
- this.targets = []
- this.activeTarget = null
- this.scrollHeight = 0
+ this._isEnabled = null;
+ this._timeout = null;
+ this._hoverState = null;
+ this._activeTrigger = null;
+ if (this._popper !== null) {
+ this._popper.destroy();
+ }
+ this._popper = null;
- this.$scrollElement.on('scroll.bs.scrollspy', $.proxy(this.process, this))
- this.refresh()
- this.process()
- }
+ this.element = null;
+ this.config = null;
+ this.tip = null;
+ };
- ScrollSpy.VERSION = '3.3.7'
+ Tooltip.prototype.show = function show() {
+ var _this24 = this;
- ScrollSpy.DEFAULTS = {
- offset: 10
- }
+ if ($(this.element).css('display') === 'none') {
+ throw new Error('Please use show on visible elements');
+ }
- ScrollSpy.prototype.getScrollHeight = function () {
- return this.$scrollElement[0].scrollHeight || Math.max(this.$body[0].scrollHeight, document.documentElement.scrollHeight)
- }
+ var showEvent = $.Event(this.constructor.Event.SHOW);
+ if (this.isWithContent() && this._isEnabled) {
+ $(this.element).trigger(showEvent);
- ScrollSpy.prototype.refresh = function () {
- var that = this
- var offsetMethod = 'offset'
- var offsetBase = 0
+ var isInTheDom = $.contains(this.element.ownerDocument.documentElement, this.element);
- this.offsets = []
- this.targets = []
- this.scrollHeight = this.getScrollHeight()
+ if (showEvent.isDefaultPrevented() || !isInTheDom) {
+ return;
+ }
- if (!$.isWindow(this.$scrollElement[0])) {
- offsetMethod = 'position'
- offsetBase = this.$scrollElement.scrollTop()
- }
+ var tip = this.getTipElement();
+ var tipId = Util.getUID(this.constructor.NAME);
- this.$body
- .find(this.selector)
- .map(function () {
- var $el = $(this)
- var href = $el.data('target') || $el.attr('href')
- var $href = /^#./.test(href) && $(href)
-
- return ($href
- && $href.length
- && $href.is(':visible')
- && [[$href[offsetMethod]().top + offsetBase, href]]) || null
- })
- .sort(function (a, b) { return a[0] - b[0] })
- .each(function () {
- that.offsets.push(this[0])
- that.targets.push(this[1])
- })
- }
+ tip.setAttribute('id', tipId);
+ this.element.setAttribute('aria-describedby', tipId);
- ScrollSpy.prototype.process = function () {
- var scrollTop = this.$scrollElement.scrollTop() + this.options.offset
- var scrollHeight = this.getScrollHeight()
- var maxScroll = this.options.offset + scrollHeight - this.$scrollElement.height()
- var offsets = this.offsets
- var targets = this.targets
- var activeTarget = this.activeTarget
- var i
-
- if (this.scrollHeight != scrollHeight) {
- this.refresh()
- }
+ this.setContent();
- if (scrollTop >= maxScroll) {
- return activeTarget != (i = targets[targets.length - 1]) && this.activate(i)
- }
+ if (this.config.animation) {
+ $(tip).addClass(ClassName.FADE);
+ }
- if (activeTarget && scrollTop < offsets[0]) {
- this.activeTarget = null
- return this.clear()
- }
+ var placement = typeof this.config.placement === 'function' ? this.config.placement.call(this, tip, this.element) : this.config.placement;
- for (i = offsets.length; i--;) {
- activeTarget != targets[i]
- && scrollTop >= offsets[i]
- && (offsets[i + 1] === undefined || scrollTop < offsets[i + 1])
- && this.activate(targets[i])
- }
- }
+ var attachment = this._getAttachment(placement);
+ this.addAttachmentClass(attachment);
- ScrollSpy.prototype.activate = function (target) {
- this.activeTarget = target
+ var container = this.config.container === false ? document.body : $(this.config.container);
- this.clear()
+ $(tip).data(this.constructor.DATA_KEY, this);
- var selector = this.selector +
- '[data-target="' + target + '"],' +
- this.selector + '[href="' + target + '"]'
+ if (!$.contains(this.element.ownerDocument.documentElement, this.tip)) {
+ $(tip).appendTo(container);
+ }
- var active = $(selector)
- .parents('li')
- .addClass('active')
+ $(this.element).trigger(this.constructor.Event.INSERTED);
+
+ this._popper = new Popper(this.element, tip, {
+ placement: attachment,
+ modifiers: {
+ offset: {
+ offset: this.config.offset
+ },
+ flip: {
+ behavior: this.config.fallbackPlacement
+ },
+ arrow: {
+ element: Selector.ARROW
+ }
+ },
+ onCreate: function onCreate(data) {
+ if (data.originalPlacement !== data.placement) {
+ _this24._handlePopperPlacementChange(data);
+ }
+ },
+ onUpdate: function onUpdate(data) {
+ _this24._handlePopperPlacementChange(data);
+ }
+ });
+
+ $(tip).addClass(ClassName.SHOW);
+
+ // if this is a touch-enabled device we add extra
+ // empty mouseover listeners to the body's immediate children;
+ // only needed because of broken event delegation on iOS
+ // https://www.quirksmode.org/blog/archives/2014/02/mouse_event_bub.html
+ if ('ontouchstart' in document.documentElement) {
+ $('body').children().on('mouseover', null, $.noop);
+ }
- if (active.parent('.dropdown-menu').length) {
- active = active
- .closest('li.dropdown')
- .addClass('active')
- }
+ var complete = function complete() {
+ if (_this24.config.animation) {
+ _this24._fixTransition();
+ }
+ var prevHoverState = _this24._hoverState;
+ _this24._hoverState = null;
- active.trigger('activate.bs.scrollspy')
- }
+ $(_this24.element).trigger(_this24.constructor.Event.SHOWN);
- ScrollSpy.prototype.clear = function () {
- $(this.selector)
- .parentsUntil(this.options.target, '.active')
- .removeClass('active')
- }
+ if (prevHoverState === HoverState.OUT) {
+ _this24._leave(null, _this24);
+ }
+ };
+ if (Util.supportsTransitionEnd() && $(this.tip).hasClass(ClassName.FADE)) {
+ $(this.tip).one(Util.TRANSITION_END, complete).emulateTransitionEnd(Tooltip._TRANSITION_DURATION);
+ } else {
+ complete();
+ }
+ }
+ };
- // SCROLLSPY PLUGIN DEFINITION
- // ===========================
+ Tooltip.prototype.hide = function hide(callback) {
+ var _this25 = this;
- function Plugin(option) {
- return this.each(function () {
- var $this = $(this)
- var data = $this.data('bs.scrollspy')
- var options = typeof option == 'object' && option
+ var tip = this.getTipElement();
+ var hideEvent = $.Event(this.constructor.Event.HIDE);
+ var complete = function complete() {
+ if (_this25._hoverState !== HoverState.SHOW && tip.parentNode) {
+ tip.parentNode.removeChild(tip);
+ }
- if (!data) $this.data('bs.scrollspy', (data = new ScrollSpy(this, options)))
- if (typeof option == 'string') data[option]()
- })
- }
+ _this25._cleanTipClass();
+ _this25.element.removeAttribute('aria-describedby');
+ $(_this25.element).trigger(_this25.constructor.Event.HIDDEN);
+ if (_this25._popper !== null) {
+ _this25._popper.destroy();
+ }
- var old = $.fn.scrollspy
+ if (callback) {
+ callback();
+ }
+ };
- $.fn.scrollspy = Plugin
- $.fn.scrollspy.Constructor = ScrollSpy
+ $(this.element).trigger(hideEvent);
+ if (hideEvent.isDefaultPrevented()) {
+ return;
+ }
- // SCROLLSPY NO CONFLICT
- // =====================
+ $(tip).removeClass(ClassName.SHOW);
- $.fn.scrollspy.noConflict = function () {
- $.fn.scrollspy = old
- return this
- }
+ // if this is a touch-enabled device we remove the extra
+ // empty mouseover listeners we added for iOS support
+ if ('ontouchstart' in document.documentElement) {
+ $('body').children().off('mouseover', null, $.noop);
+ }
+ this._activeTrigger[Trigger.CLICK] = false;
+ this._activeTrigger[Trigger.FOCUS] = false;
+ this._activeTrigger[Trigger.HOVER] = false;
- // SCROLLSPY DATA-API
- // ==================
+ if (Util.supportsTransitionEnd() && $(this.tip).hasClass(ClassName.FADE)) {
- $(window).on('load.bs.scrollspy.data-api', function () {
- $('[data-spy="scroll"]').each(function () {
- var $spy = $(this)
- Plugin.call($spy, $spy.data())
- })
- })
+ $(tip).one(Util.TRANSITION_END, complete).emulateTransitionEnd(TRANSITION_DURATION);
+ } else {
+ complete();
+ }
-}(jQuery);
+ this._hoverState = '';
+ };
-/* ========================================================================
- * Bootstrap: tab.js v3.3.7
- * http://getbootstrap.com/javascript/#tabs
- * ========================================================================
- * Copyright 2011-2016 Twitter, Inc.
- * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
- * ======================================================================== */
+ Tooltip.prototype.update = function update() {
+ if (this._popper !== null) {
+ this._popper.scheduleUpdate();
+ }
+ };
+
+ // protected
+
+ Tooltip.prototype.isWithContent = function isWithContent() {
+ return Boolean(this.getTitle());
+ };
+
+ Tooltip.prototype.addAttachmentClass = function addAttachmentClass(attachment) {
+ $(this.getTipElement()).addClass(CLASS_PREFIX + '-' + attachment);
+ };
+
+ Tooltip.prototype.getTipElement = function getTipElement() {
+ return this.tip = this.tip || $(this.config.template)[0];
+ };
+
+ Tooltip.prototype.setContent = function setContent() {
+ var $tip = $(this.getTipElement());
+ this.setElementContent($tip.find(Selector.TOOLTIP_INNER), this.getTitle());
+ $tip.removeClass(ClassName.FADE + ' ' + ClassName.SHOW);
+ };
+
+ Tooltip.prototype.setElementContent = function setElementContent($element, content) {
+ var html = this.config.html;
+ if ((typeof content === 'undefined' ? 'undefined' : _typeof(content)) === 'object' && (content.nodeType || content.jquery)) {
+ // content is a DOM node or a jQuery
+ if (html) {
+ if (!$(content).parent().is($element)) {
+ $element.empty().append(content);
+ }
+ } else {
+ $element.text($(content).text());
+ }
+ } else {
+ $element[html ? 'html' : 'text'](content);
+ }
+ };
+ Tooltip.prototype.getTitle = function getTitle() {
+ var title = this.element.getAttribute('data-original-title');
-+function ($) {
- 'use strict';
+ if (!title) {
+ title = typeof this.config.title === 'function' ? this.config.title.call(this.element) : this.config.title;
+ }
- // TAB CLASS DEFINITION
- // ====================
+ return title;
+ };
- var Tab = function (element) {
- // jscs:disable requireDollarBeforejQueryAssignment
- this.element = $(element)
- // jscs:enable requireDollarBeforejQueryAssignment
- }
+ // private
- Tab.VERSION = '3.3.7'
+ Tooltip.prototype._getAttachment = function _getAttachment(placement) {
+ return AttachmentMap[placement.toUpperCase()];
+ };
- Tab.TRANSITION_DURATION = 150
+ Tooltip.prototype._setListeners = function _setListeners() {
+ var _this26 = this;
- Tab.prototype.show = function () {
- var $this = this.element
- var $ul = $this.closest('ul:not(.dropdown-menu)')
- var selector = $this.data('target')
+ var triggers = this.config.trigger.split(' ');
- if (!selector) {
- selector = $this.attr('href')
- selector = selector && selector.replace(/.*(?=#[^\s]*$)/, '') // strip for ie7
- }
+ triggers.forEach(function (trigger) {
+ if (trigger === 'click') {
+ $(_this26.element).on(_this26.constructor.Event.CLICK, _this26.config.selector, function (event) {
+ return _this26.toggle(event);
+ });
+ } else if (trigger !== Trigger.MANUAL) {
+ var eventIn = trigger === Trigger.HOVER ? _this26.constructor.Event.MOUSEENTER : _this26.constructor.Event.FOCUSIN;
+ var eventOut = trigger === Trigger.HOVER ? _this26.constructor.Event.MOUSELEAVE : _this26.constructor.Event.FOCUSOUT;
- if ($this.parent('li').hasClass('active')) return
-
- var $previous = $ul.find('.active:last a')
- var hideEvent = $.Event('hide.bs.tab', {
- relatedTarget: $this[0]
- })
- var showEvent = $.Event('show.bs.tab', {
- relatedTarget: $previous[0]
- })
-
- $previous.trigger(hideEvent)
- $this.trigger(showEvent)
-
- if (showEvent.isDefaultPrevented() || hideEvent.isDefaultPrevented()) return
-
- var $target = $(selector)
-
- this.activate($this.closest('li'), $ul)
- this.activate($target, $target.parent(), function () {
- $previous.trigger({
- type: 'hidden.bs.tab',
- relatedTarget: $this[0]
- })
- $this.trigger({
- type: 'shown.bs.tab',
- relatedTarget: $previous[0]
- })
- })
- }
+ $(_this26.element).on(eventIn, _this26.config.selector, function (event) {
+ return _this26._enter(event);
+ }).on(eventOut, _this26.config.selector, function (event) {
+ return _this26._leave(event);
+ });
+ }
- Tab.prototype.activate = function (element, container, callback) {
- var $active = container.find('> .active')
- var transition = callback
- && $.support.transition
- && ($active.length && $active.hasClass('fade') || !!container.find('> .fade').length)
-
- function next() {
- $active
- .removeClass('active')
- .find('> .dropdown-menu > .active')
- .removeClass('active')
- .end()
- .find('[data-toggle="tab"]')
- .attr('aria-expanded', false)
-
- element
- .addClass('active')
- .find('[data-toggle="tab"]')
- .attr('aria-expanded', true)
+ $(_this26.element).closest('.modal').on('hide.bs.modal', function () {
+ return _this26.hide();
+ });
+ });
- if (transition) {
- element[0].offsetWidth // reflow for transition
- element.addClass('in')
+ if (this.config.selector) {
+ this.config = $.extend({}, this.config, {
+ trigger: 'manual',
+ selector: ''
+ });
} else {
- element.removeClass('fade')
+ this._fixTitle();
}
+ };
- if (element.parent('.dropdown-menu').length) {
- element
- .closest('li.dropdown')
- .addClass('active')
- .end()
- .find('[data-toggle="tab"]')
- .attr('aria-expanded', true)
+ Tooltip.prototype._fixTitle = function _fixTitle() {
+ var titleType = _typeof(this.element.getAttribute('data-original-title'));
+ if (this.element.getAttribute('title') || titleType !== 'string') {
+ this.element.setAttribute('data-original-title', this.element.getAttribute('title') || '');
+ this.element.setAttribute('title', '');
}
+ };
- callback && callback()
- }
+ Tooltip.prototype._enter = function _enter(event, context) {
+ var dataKey = this.constructor.DATA_KEY;
- $active.length && transition ?
- $active
- .one('bsTransitionEnd', next)
- .emulateTransitionEnd(Tab.TRANSITION_DURATION) :
- next()
+ context = context || $(event.currentTarget).data(dataKey);
- $active.removeClass('in')
- }
+ if (!context) {
+ context = new this.constructor(event.currentTarget, this._getDelegateConfig());
+ $(event.currentTarget).data(dataKey, context);
+ }
+ if (event) {
+ context._activeTrigger[event.type === 'focusin' ? Trigger.FOCUS : Trigger.HOVER] = true;
+ }
- // TAB PLUGIN DEFINITION
- // =====================
+ if ($(context.getTipElement()).hasClass(ClassName.SHOW) || context._hoverState === HoverState.SHOW) {
+ context._hoverState = HoverState.SHOW;
+ return;
+ }
- function Plugin(option) {
- return this.each(function () {
- var $this = $(this)
- var data = $this.data('bs.tab')
+ clearTimeout(context._timeout);
- if (!data) $this.data('bs.tab', (data = new Tab(this)))
- if (typeof option == 'string') data[option]()
- })
- }
+ context._hoverState = HoverState.SHOW;
- var old = $.fn.tab
+ if (!context.config.delay || !context.config.delay.show) {
+ context.show();
+ return;
+ }
- $.fn.tab = Plugin
- $.fn.tab.Constructor = Tab
+ context._timeout = setTimeout(function () {
+ if (context._hoverState === HoverState.SHOW) {
+ context.show();
+ }
+ }, context.config.delay.show);
+ };
+ Tooltip.prototype._leave = function _leave(event, context) {
+ var dataKey = this.constructor.DATA_KEY;
- // TAB NO CONFLICT
- // ===============
+ context = context || $(event.currentTarget).data(dataKey);
- $.fn.tab.noConflict = function () {
- $.fn.tab = old
- return this
- }
+ if (!context) {
+ context = new this.constructor(event.currentTarget, this._getDelegateConfig());
+ $(event.currentTarget).data(dataKey, context);
+ }
+ if (event) {
+ context._activeTrigger[event.type === 'focusout' ? Trigger.FOCUS : Trigger.HOVER] = false;
+ }
- // TAB DATA-API
- // ============
+ if (context._isWithActiveTrigger()) {
+ return;
+ }
- var clickHandler = function (e) {
- e.preventDefault()
- Plugin.call($(this), 'show')
- }
+ clearTimeout(context._timeout);
- $(document)
- .on('click.bs.tab.data-api', '[data-toggle="tab"]', clickHandler)
- .on('click.bs.tab.data-api', '[data-toggle="pill"]', clickHandler)
+ context._hoverState = HoverState.OUT;
-}(jQuery);
+ if (!context.config.delay || !context.config.delay.hide) {
+ context.hide();
+ return;
+ }
-/* ========================================================================
- * Bootstrap: affix.js v3.3.7
- * http://getbootstrap.com/javascript/#affix
- * ========================================================================
- * Copyright 2011-2016 Twitter, Inc.
- * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
- * ======================================================================== */
+ context._timeout = setTimeout(function () {
+ if (context._hoverState === HoverState.OUT) {
+ context.hide();
+ }
+ }, context.config.delay.hide);
+ };
+ Tooltip.prototype._isWithActiveTrigger = function _isWithActiveTrigger() {
+ for (var trigger in this._activeTrigger) {
+ if (this._activeTrigger[trigger]) {
+ return true;
+ }
+ }
-+function ($) {
- 'use strict';
+ return false;
+ };
- // AFFIX CLASS DEFINITION
- // ======================
+ Tooltip.prototype._getConfig = function _getConfig(config) {
+ config = $.extend({}, this.constructor.Default, $(this.element).data(), config);
- var Affix = function (element, options) {
- this.options = $.extend({}, Affix.DEFAULTS, options)
+ if (config.delay && typeof config.delay === 'number') {
+ config.delay = {
+ show: config.delay,
+ hide: config.delay
+ };
+ }
- this.$target = $(this.options.target)
- .on('scroll.bs.affix.data-api', $.proxy(this.checkPosition, this))
- .on('click.bs.affix.data-api', $.proxy(this.checkPositionWithEventLoop, this))
+ if (config.title && typeof config.title === 'number') {
+ config.title = config.title.toString();
+ }
- this.$element = $(element)
- this.affixed = null
- this.unpin = null
- this.pinnedOffset = null
+ if (config.content && typeof config.content === 'number') {
+ config.content = config.content.toString();
+ }
- this.checkPosition()
- }
+ Util.typeCheckConfig(NAME, config, this.constructor.DefaultType);
- Affix.VERSION = '3.3.7'
+ return config;
+ };
- Affix.RESET = 'affix affix-top affix-bottom'
+ Tooltip.prototype._getDelegateConfig = function _getDelegateConfig() {
+ var config = {};
- Affix.DEFAULTS = {
- offset: 0,
- target: window
- }
+ if (this.config) {
+ for (var key in this.config) {
+ if (this.constructor.Default[key] !== this.config[key]) {
+ config[key] = this.config[key];
+ }
+ }
+ }
- Affix.prototype.getState = function (scrollHeight, height, offsetTop, offsetBottom) {
- var scrollTop = this.$target.scrollTop()
- var position = this.$element.offset()
- var targetHeight = this.$target.height()
+ return config;
+ };
- if (offsetTop != null && this.affixed == 'top') return scrollTop < offsetTop ? 'top' : false
+ Tooltip.prototype._cleanTipClass = function _cleanTipClass() {
+ var $tip = $(this.getTipElement());
+ var tabClass = $tip.attr('class').match(BSCLS_PREFIX_REGEX);
+ if (tabClass !== null && tabClass.length > 0) {
+ $tip.removeClass(tabClass.join(''));
+ }
+ };
+
+ Tooltip.prototype._handlePopperPlacementChange = function _handlePopperPlacementChange(data) {
+ this._cleanTipClass();
+ this.addAttachmentClass(this._getAttachment(data.placement));
+ };
+
+ Tooltip.prototype._fixTransition = function _fixTransition() {
+ var tip = this.getTipElement();
+ var initConfigAnimation = this.config.animation;
+ if (tip.getAttribute('x-placement') !== null) {
+ return;
+ }
+ $(tip).removeClass(ClassName.FADE);
+ this.config.animation = false;
+ this.hide();
+ this.show();
+ this.config.animation = initConfigAnimation;
+ };
+
+ // static
+
+ Tooltip._jQueryInterface = function _jQueryInterface(config) {
+ return this.each(function () {
+ var data = $(this).data(DATA_KEY);
+ var _config = (typeof config === 'undefined' ? 'undefined' : _typeof(config)) === 'object' && config;
+
+ if (!data && /dispose|hide/.test(config)) {
+ return;
+ }
- if (this.affixed == 'bottom') {
- if (offsetTop != null) return (scrollTop + this.unpin <= position.top) ? false : 'bottom'
- return (scrollTop + targetHeight <= scrollHeight - offsetBottom) ? false : 'bottom'
- }
+ if (!data) {
+ data = new Tooltip(this, _config);
+ $(this).data(DATA_KEY, data);
+ }
+
+ if (typeof config === 'string') {
+ if (data[config] === undefined) {
+ throw new Error('No method named "' + config + '"');
+ }
+ data[config]();
+ }
+ });
+ };
+
+ _createClass(Tooltip, null, [{
+ key: 'VERSION',
+ get: function get() {
+ return VERSION;
+ }
+ }, {
+ key: 'Default',
+ get: function get() {
+ return Default;
+ }
+ }, {
+ key: 'NAME',
+ get: function get() {
+ return NAME;
+ }
+ }, {
+ key: 'DATA_KEY',
+ get: function get() {
+ return DATA_KEY;
+ }
+ }, {
+ key: 'Event',
+ get: function get() {
+ return Event;
+ }
+ }, {
+ key: 'EVENT_KEY',
+ get: function get() {
+ return EVENT_KEY;
+ }
+ }, {
+ key: 'DefaultType',
+ get: function get() {
+ return DefaultType;
+ }
+ }]);
- var initializing = this.affixed == null
- var colliderTop = initializing ? scrollTop : position.top
- var colliderHeight = initializing ? targetHeight : height
+ return Tooltip;
+ }();
- if (offsetTop != null && scrollTop <= offsetTop) return 'top'
- if (offsetBottom != null && (colliderTop + colliderHeight >= scrollHeight - offsetBottom)) return 'bottom'
+ /**
+ * ------------------------------------------------------------------------
+ * jQuery
+ * ------------------------------------------------------------------------
+ */
- return false
- }
+ $.fn[NAME] = Tooltip._jQueryInterface;
+ $.fn[NAME].Constructor = Tooltip;
+ $.fn[NAME].noConflict = function () {
+ $.fn[NAME] = JQUERY_NO_CONFLICT;
+ return Tooltip._jQueryInterface;
+ };
- Affix.prototype.getPinnedOffset = function () {
- if (this.pinnedOffset) return this.pinnedOffset
- this.$element.removeClass(Affix.RESET).addClass('affix')
- var scrollTop = this.$target.scrollTop()
- var position = this.$element.offset()
- return (this.pinnedOffset = position.top - scrollTop)
- }
+ return Tooltip;
+}(jQuery);
- Affix.prototype.checkPositionWithEventLoop = function () {
- setTimeout($.proxy(this.checkPosition, this), 1)
- }
+/**
+ * --------------------------------------------------------------------------
+ * Bootstrap (v4.0.0-beta): popover.js
+ * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
+ * --------------------------------------------------------------------------
+ */
- Affix.prototype.checkPosition = function () {
- if (!this.$element.is(':visible')) return
+var Popover = function ($) {
- var height = this.$element.height()
- var offset = this.options.offset
- var offsetTop = offset.top
- var offsetBottom = offset.bottom
- var scrollHeight = Math.max($(document).height(), $(document.body).height())
+ /**
+ * ------------------------------------------------------------------------
+ * Constants
+ * ------------------------------------------------------------------------
+ */
- if (typeof offset != 'object') offsetBottom = offsetTop = offset
- if (typeof offsetTop == 'function') offsetTop = offset.top(this.$element)
- if (typeof offsetBottom == 'function') offsetBottom = offset.bottom(this.$element)
+ var NAME = 'popover';
+ var VERSION = '4.0.0-beta';
+ var DATA_KEY = 'bs.popover';
+ var EVENT_KEY = '.' + DATA_KEY;
+ var JQUERY_NO_CONFLICT = $.fn[NAME];
+ var CLASS_PREFIX = 'bs-popover';
+ var BSCLS_PREFIX_REGEX = new RegExp('(^|\\s)' + CLASS_PREFIX + '\\S+', 'g');
- var affix = this.getState(scrollHeight, height, offsetTop, offsetBottom)
+ var Default = $.extend({}, Tooltip.Default, {
+ placement: 'right',
+ trigger: 'click',
+ content: '',
+ template: '<div class="popover" role="tooltip">' + '<div class="arrow"></div>' + '<h3 class="popover-header"></h3>' + '<div class="popover-body"></div></div>'
+ });
+
+ var DefaultType = $.extend({}, Tooltip.DefaultType, {
+ content: '(string|element|function)'
+ });
+
+ var ClassName = {
+ FADE: 'fade',
+ SHOW: 'show'
+ };
+
+ var Selector = {
+ TITLE: '.popover-header',
+ CONTENT: '.popover-body'
+ };
+
+ var Event = {
+ HIDE: 'hide' + EVENT_KEY,
+ HIDDEN: 'hidden' + EVENT_KEY,
+ SHOW: 'show' + EVENT_KEY,
+ SHOWN: 'shown' + EVENT_KEY,
+ INSERTED: 'inserted' + EVENT_KEY,
+ CLICK: 'click' + EVENT_KEY,
+ FOCUSIN: 'focusin' + EVENT_KEY,
+ FOCUSOUT: 'focusout' + EVENT_KEY,
+ MOUSEENTER: 'mouseenter' + EVENT_KEY,
+ MOUSELEAVE: 'mouseleave' + EVENT_KEY
+
+ /**
+ * ------------------------------------------------------------------------
+ * Class Definition
+ * ------------------------------------------------------------------------
+ */
+
+ };
+ var Popover = function (_Tooltip) {
+ _inherits(Popover, _Tooltip);
+
+ function Popover() {
+ _classCallCheck(this, Popover);
+
+ return _possibleConstructorReturn(this, _Tooltip.apply(this, arguments));
+ }
- if (this.affixed != affix) {
- if (this.unpin != null) this.$element.css('top', '')
+ // overrides
- var affixType = 'affix' + (affix ? '-' + affix : '')
- var e = $.Event(affixType + '.bs.affix')
+ Popover.prototype.isWithContent = function isWithContent() {
+ return this.getTitle() || this._getContent();
+ };
- this.$element.trigger(e)
+ Popover.prototype.addAttachmentClass = function addAttachmentClass(attachment) {
+ $(this.getTipElement()).addClass(CLASS_PREFIX + '-' + attachment);
+ };
- if (e.isDefaultPrevented()) return
+ Popover.prototype.getTipElement = function getTipElement() {
+ return this.tip = this.tip || $(this.config.template)[0];
+ };
- this.affixed = affix
- this.unpin = affix == 'bottom' ? this.getPinnedOffset() : null
+ Popover.prototype.setContent = function setContent() {
+ var $tip = $(this.getTipElement());
- this.$element
- .removeClass(Affix.RESET)
- .addClass(affixType)
- .trigger(affixType.replace('affix', 'affixed') + '.bs.affix')
- }
+ // we use append for html objects to maintain js events
+ this.setElementContent($tip.find(Selector.TITLE), this.getTitle());
+ this.setElementContent($tip.find(Selector.CONTENT), this._getContent());
- if (affix == 'bottom') {
- this.$element.offset({
- top: scrollHeight - height - offsetBottom
- })
- }
- }
+ $tip.removeClass(ClassName.FADE + ' ' + ClassName.SHOW);
+ };
+ // private
- // AFFIX PLUGIN DEFINITION
- // =======================
+ Popover.prototype._getContent = function _getContent() {
+ return this.element.getAttribute('data-content') || (typeof this.config.content === 'function' ? this.config.content.call(this.element) : this.config.content);
+ };
- function Plugin(option) {
- return this.each(function () {
- var $this = $(this)
- var data = $this.data('bs.affix')
- var options = typeof option == 'object' && option
+ Popover.prototype._cleanTipClass = function _cleanTipClass() {
+ var $tip = $(this.getTipElement());
+ var tabClass = $tip.attr('class').match(BSCLS_PREFIX_REGEX);
+ if (tabClass !== null && tabClass.length > 0) {
+ $tip.removeClass(tabClass.join(''));
+ }
+ };
- if (!data) $this.data('bs.affix', (data = new Affix(this, options)))
- if (typeof option == 'string') data[option]()
- })
- }
+ // static
- var old = $.fn.affix
+ Popover._jQueryInterface = function _jQueryInterface(config) {
+ return this.each(function () {
+ var data = $(this).data(DATA_KEY);
+ var _config = (typeof config === 'undefined' ? 'undefined' : _typeof(config)) === 'object' ? config : null;
- $.fn.affix = Plugin
- $.fn.affix.Constructor = Affix
+ if (!data && /destroy|hide/.test(config)) {
+ return;
+ }
+ if (!data) {
+ data = new Popover(this, _config);
+ $(this).data(DATA_KEY, data);
+ }
- // AFFIX NO CONFLICT
- // =================
+ if (typeof config === 'string') {
+ if (data[config] === undefined) {
+ throw new Error('No method named "' + config + '"');
+ }
+ data[config]();
+ }
+ });
+ };
- $.fn.affix.noConflict = function () {
- $.fn.affix = old
- return this
- }
+ _createClass(Popover, null, [{
+ key: 'VERSION',
- // AFFIX DATA-API
- // ==============
+ // getters
- $(window).on('load', function () {
- $('[data-spy="affix"]').each(function () {
- var $spy = $(this)
- var data = $spy.data()
+ get: function get() {
+ return VERSION;
+ }
+ }, {
+ key: 'Default',
+ get: function get() {
+ return Default;
+ }
+ }, {
+ key: 'NAME',
+ get: function get() {
+ return NAME;
+ }
+ }, {
+ key: 'DATA_KEY',
+ get: function get() {
+ return DATA_KEY;
+ }
+ }, {
+ key: 'Event',
+ get: function get() {
+ return Event;
+ }
+ }, {
+ key: 'EVENT_KEY',
+ get: function get() {
+ return EVENT_KEY;
+ }
+ }, {
+ key: 'DefaultType',
+ get: function get() {
+ return DefaultType;
+ }
+ }]);
- data.offset = data.offset || {}
+ return Popover;
+ }(Tooltip);
- if (data.offsetBottom != null) data.offset.bottom = data.offsetBottom
- if (data.offsetTop != null) data.offset.top = data.offsetTop
+ /**
+ * ------------------------------------------------------------------------
+ * jQuery
+ * ------------------------------------------------------------------------
+ */
- Plugin.call($spy, data)
- })
- })
+ $.fn[NAME] = Popover._jQueryInterface;
+ $.fn[NAME].Constructor = Popover;
+ $.fn[NAME].noConflict = function () {
+ $.fn[NAME] = JQUERY_NO_CONFLICT;
+ return Popover._jQueryInterface;
+ };
+ return Popover;
}(jQuery);
+
+
+})(); \ No newline at end of file
diff --git a/library/bootstrap/js/bootstrap.min.js b/library/bootstrap/js/bootstrap.min.js
index 9bcd2fcca..e1874769b 100644
--- a/library/bootstrap/js/bootstrap.min.js
+++ b/library/bootstrap/js/bootstrap.min.js
@@ -1,7 +1,6 @@
/*!
- * Bootstrap v3.3.7 (http://getbootstrap.com)
- * Copyright 2011-2016 Twitter, Inc.
- * Licensed under the MIT license
+ * Bootstrap v4.0.0-beta (https://getbootstrap.com)
+ * Copyright 2011-2017 The Bootstrap Authors (https://github.com/twbs/bootstrap/graphs/contributors)
+ * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
*/
-if("undefined"==typeof jQuery)throw new Error("Bootstrap's JavaScript requires jQuery");+function(a){"use strict";var b=a.fn.jquery.split(" ")[0].split(".");if(b[0]<2&&b[1]<9||1==b[0]&&9==b[1]&&b[2]<1||b[0]>3)throw new Error("Bootstrap's JavaScript requires jQuery version 1.9.1 or higher, but lower than version 4")}(jQuery),+function(a){"use strict";function b(){var a=document.createElement("bootstrap"),b={WebkitTransition:"webkitTransitionEnd",MozTransition:"transitionend",OTransition:"oTransitionEnd otransitionend",transition:"transitionend"};for(var c in b)if(void 0!==a.style[c])return{end:b[c]};return!1}a.fn.emulateTransitionEnd=function(b){var c=!1,d=this;a(this).one("bsTransitionEnd",function(){c=!0});var e=function(){c||a(d).trigger(a.support.transition.end)};return setTimeout(e,b),this},a(function(){a.support.transition=b(),a.support.transition&&(a.event.special.bsTransitionEnd={bindType:a.support.transition.end,delegateType:a.support.transition.end,handle:function(b){if(a(b.target).is(this))return b.handleObj.handler.apply(this,arguments)}})})}(jQuery),+function(a){"use strict";function b(b){return this.each(function(){var c=a(this),e=c.data("bs.alert");e||c.data("bs.alert",e=new d(this)),"string"==typeof b&&e[b].call(c)})}var c='[data-dismiss="alert"]',d=function(b){a(b).on("click",c,this.close)};d.VERSION="3.3.7",d.TRANSITION_DURATION=150,d.prototype.close=function(b){function c(){g.detach().trigger("closed.bs.alert").remove()}var e=a(this),f=e.attr("data-target");f||(f=e.attr("href"),f=f&&f.replace(/.*(?=#[^\s]*$)/,""));var g=a("#"===f?[]:f);b&&b.preventDefault(),g.length||(g=e.closest(".alert")),g.trigger(b=a.Event("close.bs.alert")),b.isDefaultPrevented()||(g.removeClass("in"),a.support.transition&&g.hasClass("fade")?g.one("bsTransitionEnd",c).emulateTransitionEnd(d.TRANSITION_DURATION):c())};var e=a.fn.alert;a.fn.alert=b,a.fn.alert.Constructor=d,a.fn.alert.noConflict=function(){return a.fn.alert=e,this},a(document).on("click.bs.alert.data-api",c,d.prototype.close)}(jQuery),+function(a){"use strict";function b(b){return this.each(function(){var d=a(this),e=d.data("bs.button"),f="object"==typeof b&&b;e||d.data("bs.button",e=new c(this,f)),"toggle"==b?e.toggle():b&&e.setState(b)})}var c=function(b,d){this.$element=a(b),this.options=a.extend({},c.DEFAULTS,d),this.isLoading=!1};c.VERSION="3.3.7",c.DEFAULTS={loadingText:"loading..."},c.prototype.setState=function(b){var c="disabled",d=this.$element,e=d.is("input")?"val":"html",f=d.data();b+="Text",null==f.resetText&&d.data("resetText",d[e]()),setTimeout(a.proxy(function(){d[e](null==f[b]?this.options[b]:f[b]),"loadingText"==b?(this.isLoading=!0,d.addClass(c).attr(c,c).prop(c,!0)):this.isLoading&&(this.isLoading=!1,d.removeClass(c).removeAttr(c).prop(c,!1))},this),0)},c.prototype.toggle=function(){var a=!0,b=this.$element.closest('[data-toggle="buttons"]');if(b.length){var c=this.$element.find("input");"radio"==c.prop("type")?(c.prop("checked")&&(a=!1),b.find(".active").removeClass("active"),this.$element.addClass("active")):"checkbox"==c.prop("type")&&(c.prop("checked")!==this.$element.hasClass("active")&&(a=!1),this.$element.toggleClass("active")),c.prop("checked",this.$element.hasClass("active")),a&&c.trigger("change")}else this.$element.attr("aria-pressed",!this.$element.hasClass("active")),this.$element.toggleClass("active")};var d=a.fn.button;a.fn.button=b,a.fn.button.Constructor=c,a.fn.button.noConflict=function(){return a.fn.button=d,this},a(document).on("click.bs.button.data-api",'[data-toggle^="button"]',function(c){var d=a(c.target).closest(".btn");b.call(d,"toggle"),a(c.target).is('input[type="radio"], input[type="checkbox"]')||(c.preventDefault(),d.is("input,button")?d.trigger("focus"):d.find("input:visible,button:visible").first().trigger("focus"))}).on("focus.bs.button.data-api blur.bs.button.data-api",'[data-toggle^="button"]',function(b){a(b.target).closest(".btn").toggleClass("focus",/^focus(in)?$/.test(b.type))})}(jQuery),+function(a){"use strict";function b(b){return this.each(function(){var d=a(this),e=d.data("bs.carousel"),f=a.extend({},c.DEFAULTS,d.data(),"object"==typeof b&&b),g="string"==typeof b?b:f.slide;e||d.data("bs.carousel",e=new c(this,f)),"number"==typeof b?e.to(b):g?e[g]():f.interval&&e.pause().cycle()})}var c=function(b,c){this.$element=a(b),this.$indicators=this.$element.find(".carousel-indicators"),this.options=c,this.paused=null,this.sliding=null,this.interval=null,this.$active=null,this.$items=null,this.options.keyboard&&this.$element.on("keydown.bs.carousel",a.proxy(this.keydown,this)),"hover"==this.options.pause&&!("ontouchstart"in document.documentElement)&&this.$element.on("mouseenter.bs.carousel",a.proxy(this.pause,this)).on("mouseleave.bs.carousel",a.proxy(this.cycle,this))};c.VERSION="3.3.7",c.TRANSITION_DURATION=600,c.DEFAULTS={interval:5e3,pause:"hover",wrap:!0,keyboard:!0},c.prototype.keydown=function(a){if(!/input|textarea/i.test(a.target.tagName)){switch(a.which){case 37:this.prev();break;case 39:this.next();break;default:return}a.preventDefault()}},c.prototype.cycle=function(b){return b||(this.paused=!1),this.interval&&clearInterval(this.interval),this.options.interval&&!this.paused&&(this.interval=setInterval(a.proxy(this.next,this),this.options.interval)),this},c.prototype.getItemIndex=function(a){return this.$items=a.parent().children(".item"),this.$items.index(a||this.$active)},c.prototype.getItemForDirection=function(a,b){var c=this.getItemIndex(b),d="prev"==a&&0===c||"next"==a&&c==this.$items.length-1;if(d&&!this.options.wrap)return b;var e="prev"==a?-1:1,f=(c+e)%this.$items.length;return this.$items.eq(f)},c.prototype.to=function(a){var b=this,c=this.getItemIndex(this.$active=this.$element.find(".item.active"));if(!(a>this.$items.length-1||a<0))return this.sliding?this.$element.one("slid.bs.carousel",function(){b.to(a)}):c==a?this.pause().cycle():this.slide(a>c?"next":"prev",this.$items.eq(a))},c.prototype.pause=function(b){return b||(this.paused=!0),this.$element.find(".next, .prev").length&&a.support.transition&&(this.$element.trigger(a.support.transition.end),this.cycle(!0)),this.interval=clearInterval(this.interval),this},c.prototype.next=function(){if(!this.sliding)return this.slide("next")},c.prototype.prev=function(){if(!this.sliding)return this.slide("prev")},c.prototype.slide=function(b,d){var e=this.$element.find(".item.active"),f=d||this.getItemForDirection(b,e),g=this.interval,h="next"==b?"left":"right",i=this;if(f.hasClass("active"))return this.sliding=!1;var j=f[0],k=a.Event("slide.bs.carousel",{relatedTarget:j,direction:h});if(this.$element.trigger(k),!k.isDefaultPrevented()){if(this.sliding=!0,g&&this.pause(),this.$indicators.length){this.$indicators.find(".active").removeClass("active");var l=a(this.$indicators.children()[this.getItemIndex(f)]);l&&l.addClass("active")}var m=a.Event("slid.bs.carousel",{relatedTarget:j,direction:h});return a.support.transition&&this.$element.hasClass("slide")?(f.addClass(b),f[0].offsetWidth,e.addClass(h),f.addClass(h),e.one("bsTransitionEnd",function(){f.removeClass([b,h].join(" ")).addClass("active"),e.removeClass(["active",h].join(" ")),i.sliding=!1,setTimeout(function(){i.$element.trigger(m)},0)}).emulateTransitionEnd(c.TRANSITION_DURATION)):(e.removeClass("active"),f.addClass("active"),this.sliding=!1,this.$element.trigger(m)),g&&this.cycle(),this}};var d=a.fn.carousel;a.fn.carousel=b,a.fn.carousel.Constructor=c,a.fn.carousel.noConflict=function(){return a.fn.carousel=d,this};var e=function(c){var d,e=a(this),f=a(e.attr("data-target")||(d=e.attr("href"))&&d.replace(/.*(?=#[^\s]+$)/,""));if(f.hasClass("carousel")){var g=a.extend({},f.data(),e.data()),h=e.attr("data-slide-to");h&&(g.interval=!1),b.call(f,g),h&&f.data("bs.carousel").to(h),c.preventDefault()}};a(document).on("click.bs.carousel.data-api","[data-slide]",e).on("click.bs.carousel.data-api","[data-slide-to]",e),a(window).on("load",function(){a('[data-ride="carousel"]').each(function(){var c=a(this);b.call(c,c.data())})})}(jQuery),+function(a){"use strict";function b(b){var c,d=b.attr("data-target")||(c=b.attr("href"))&&c.replace(/.*(?=#[^\s]+$)/,"");return a(d)}function c(b){return this.each(function(){var c=a(this),e=c.data("bs.collapse"),f=a.extend({},d.DEFAULTS,c.data(),"object"==typeof b&&b);!e&&f.toggle&&/show|hide/.test(b)&&(f.toggle=!1),e||c.data("bs.collapse",e=new d(this,f)),"string"==typeof b&&e[b]()})}var d=function(b,c){this.$element=a(b),this.options=a.extend({},d.DEFAULTS,c),this.$trigger=a('[data-toggle="collapse"][href="#'+b.id+'"],[data-toggle="collapse"][data-target="#'+b.id+'"]'),this.transitioning=null,this.options.parent?this.$parent=this.getParent():this.addAriaAndCollapsedClass(this.$element,this.$trigger),this.options.toggle&&this.toggle()};d.VERSION="3.3.7",d.TRANSITION_DURATION=350,d.DEFAULTS={toggle:!0},d.prototype.dimension=function(){var a=this.$element.hasClass("width");return a?"width":"height"},d.prototype.show=function(){if(!this.transitioning&&!this.$element.hasClass("in")){var b,e=this.$parent&&this.$parent.children(".panel").children(".in, .collapsing");if(!(e&&e.length&&(b=e.data("bs.collapse"),b&&b.transitioning))){var f=a.Event("show.bs.collapse");if(this.$element.trigger(f),!f.isDefaultPrevented()){e&&e.length&&(c.call(e,"hide"),b||e.data("bs.collapse",null));var g=this.dimension();this.$element.removeClass("collapse").addClass("collapsing")[g](0).attr("aria-expanded",!0),this.$trigger.removeClass("collapsed").attr("aria-expanded",!0),this.transitioning=1;var h=function(){this.$element.removeClass("collapsing").addClass("collapse in")[g](""),this.transitioning=0,this.$element.trigger("shown.bs.collapse")};if(!a.support.transition)return h.call(this);var i=a.camelCase(["scroll",g].join("-"));this.$element.one("bsTransitionEnd",a.proxy(h,this)).emulateTransitionEnd(d.TRANSITION_DURATION)[g](this.$element[0][i])}}}},d.prototype.hide=function(){if(!this.transitioning&&this.$element.hasClass("in")){var b=a.Event("hide.bs.collapse");if(this.$element.trigger(b),!b.isDefaultPrevented()){var c=this.dimension();this.$element[c](this.$element[c]())[0].offsetHeight,this.$element.addClass("collapsing").removeClass("collapse in").attr("aria-expanded",!1),this.$trigger.addClass("collapsed").attr("aria-expanded",!1),this.transitioning=1;var e=function(){this.transitioning=0,this.$element.removeClass("collapsing").addClass("collapse").trigger("hidden.bs.collapse")};return a.support.transition?void this.$element[c](0).one("bsTransitionEnd",a.proxy(e,this)).emulateTransitionEnd(d.TRANSITION_DURATION):e.call(this)}}},d.prototype.toggle=function(){this[this.$element.hasClass("in")?"hide":"show"]()},d.prototype.getParent=function(){return a(this.options.parent).find('[data-toggle="collapse"][data-parent="'+this.options.parent+'"]').each(a.proxy(function(c,d){var e=a(d);this.addAriaAndCollapsedClass(b(e),e)},this)).end()},d.prototype.addAriaAndCollapsedClass=function(a,b){var c=a.hasClass("in");a.attr("aria-expanded",c),b.toggleClass("collapsed",!c).attr("aria-expanded",c)};var e=a.fn.collapse;a.fn.collapse=c,a.fn.collapse.Constructor=d,a.fn.collapse.noConflict=function(){return a.fn.collapse=e,this},a(document).on("click.bs.collapse.data-api",'[data-toggle="collapse"]',function(d){var e=a(this);e.attr("data-target")||d.preventDefault();var f=b(e),g=f.data("bs.collapse"),h=g?"toggle":e.data();c.call(f,h)})}(jQuery),+function(a){"use strict";function b(b){var c=b.attr("data-target");c||(c=b.attr("href"),c=c&&/#[A-Za-z]/.test(c)&&c.replace(/.*(?=#[^\s]*$)/,""));var d=c&&a(c);return d&&d.length?d:b.parent()}function c(c){c&&3===c.which||(a(e).remove(),a(f).each(function(){var d=a(this),e=b(d),f={relatedTarget:this};e.hasClass("open")&&(c&&"click"==c.type&&/input|textarea/i.test(c.target.tagName)&&a.contains(e[0],c.target)||(e.trigger(c=a.Event("hide.bs.dropdown",f)),c.isDefaultPrevented()||(d.attr("aria-expanded","false"),e.removeClass("open").trigger(a.Event("hidden.bs.dropdown",f)))))}))}function d(b){return this.each(function(){var c=a(this),d=c.data("bs.dropdown");d||c.data("bs.dropdown",d=new g(this)),"string"==typeof b&&d[b].call(c)})}var e=".dropdown-backdrop",f='[data-toggle="dropdown"]',g=function(b){a(b).on("click.bs.dropdown",this.toggle)};g.VERSION="3.3.7",g.prototype.toggle=function(d){var e=a(this);if(!e.is(".disabled, :disabled")){var f=b(e),g=f.hasClass("open");if(c(),!g){"ontouchstart"in document.documentElement&&!f.closest(".navbar-nav").length&&a(document.createElement("div")).addClass("dropdown-backdrop").insertAfter(a(this)).on("click",c);var h={relatedTarget:this};if(f.trigger(d=a.Event("show.bs.dropdown",h)),d.isDefaultPrevented())return;e.trigger("focus").attr("aria-expanded","true"),f.toggleClass("open").trigger(a.Event("shown.bs.dropdown",h))}return!1}},g.prototype.keydown=function(c){if(/(38|40|27|32)/.test(c.which)&&!/input|textarea/i.test(c.target.tagName)){var d=a(this);if(c.preventDefault(),c.stopPropagation(),!d.is(".disabled, :disabled")){var e=b(d),g=e.hasClass("open");if(!g&&27!=c.which||g&&27==c.which)return 27==c.which&&e.find(f).trigger("focus"),d.trigger("click");var h=" li:not(.disabled):visible a",i=e.find(".dropdown-menu"+h);if(i.length){var j=i.index(c.target);38==c.which&&j>0&&j--,40==c.which&&j<i.length-1&&j++,~j||(j=0),i.eq(j).trigger("focus")}}}};var h=a.fn.dropdown;a.fn.dropdown=d,a.fn.dropdown.Constructor=g,a.fn.dropdown.noConflict=function(){return a.fn.dropdown=h,this},a(document).on("click.bs.dropdown.data-api",c).on("click.bs.dropdown.data-api",".dropdown form",function(a){a.stopPropagation()}).on("click.bs.dropdown.data-api",f,g.prototype.toggle).on("keydown.bs.dropdown.data-api",f,g.prototype.keydown).on("keydown.bs.dropdown.data-api",".dropdown-menu",g.prototype.keydown)}(jQuery),+function(a){"use strict";function b(b,d){return this.each(function(){var e=a(this),f=e.data("bs.modal"),g=a.extend({},c.DEFAULTS,e.data(),"object"==typeof b&&b);f||e.data("bs.modal",f=new c(this,g)),"string"==typeof b?f[b](d):g.show&&f.show(d)})}var c=function(b,c){this.options=c,this.$body=a(document.body),this.$element=a(b),this.$dialog=this.$element.find(".modal-dialog"),this.$backdrop=null,this.isShown=null,this.originalBodyPad=null,this.scrollbarWidth=0,this.ignoreBackdropClick=!1,this.options.remote&&this.$element.find(".modal-content").load(this.options.remote,a.proxy(function(){this.$element.trigger("loaded.bs.modal")},this))};c.VERSION="3.3.7",c.TRANSITION_DURATION=300,c.BACKDROP_TRANSITION_DURATION=150,c.DEFAULTS={backdrop:!0,keyboard:!0,show:!0},c.prototype.toggle=function(a){return this.isShown?this.hide():this.show(a)},c.prototype.show=function(b){var d=this,e=a.Event("show.bs.modal",{relatedTarget:b});this.$element.trigger(e),this.isShown||e.isDefaultPrevented()||(this.isShown=!0,this.checkScrollbar(),this.setScrollbar(),this.$body.addClass("modal-open"),this.escape(),this.resize(),this.$element.on("click.dismiss.bs.modal",'[data-dismiss="modal"]',a.proxy(this.hide,this)),this.$dialog.on("mousedown.dismiss.bs.modal",function(){d.$element.one("mouseup.dismiss.bs.modal",function(b){a(b.target).is(d.$element)&&(d.ignoreBackdropClick=!0)})}),this.backdrop(function(){var e=a.support.transition&&d.$element.hasClass("fade");d.$element.parent().length||d.$element.appendTo(d.$body),d.$element.show().scrollTop(0),d.adjustDialog(),e&&d.$element[0].offsetWidth,d.$element.addClass("in"),d.enforceFocus();var f=a.Event("shown.bs.modal",{relatedTarget:b});e?d.$dialog.one("bsTransitionEnd",function(){d.$element.trigger("focus").trigger(f)}).emulateTransitionEnd(c.TRANSITION_DURATION):d.$element.trigger("focus").trigger(f)}))},c.prototype.hide=function(b){b&&b.preventDefault(),b=a.Event("hide.bs.modal"),this.$element.trigger(b),this.isShown&&!b.isDefaultPrevented()&&(this.isShown=!1,this.escape(),this.resize(),a(document).off("focusin.bs.modal"),this.$element.removeClass("in").off("click.dismiss.bs.modal").off("mouseup.dismiss.bs.modal"),this.$dialog.off("mousedown.dismiss.bs.modal"),a.support.transition&&this.$element.hasClass("fade")?this.$element.one("bsTransitionEnd",a.proxy(this.hideModal,this)).emulateTransitionEnd(c.TRANSITION_DURATION):this.hideModal())},c.prototype.enforceFocus=function(){a(document).off("focusin.bs.modal").on("focusin.bs.modal",a.proxy(function(a){document===a.target||this.$element[0]===a.target||this.$element.has(a.target).length||this.$element.trigger("focus")},this))},c.prototype.escape=function(){this.isShown&&this.options.keyboard?this.$element.on("keydown.dismiss.bs.modal",a.proxy(function(a){27==a.which&&this.hide()},this)):this.isShown||this.$element.off("keydown.dismiss.bs.modal")},c.prototype.resize=function(){this.isShown?a(window).on("resize.bs.modal",a.proxy(this.handleUpdate,this)):a(window).off("resize.bs.modal")},c.prototype.hideModal=function(){var a=this;this.$element.hide(),this.backdrop(function(){a.$body.removeClass("modal-open"),a.resetAdjustments(),a.resetScrollbar(),a.$element.trigger("hidden.bs.modal")})},c.prototype.removeBackdrop=function(){this.$backdrop&&this.$backdrop.remove(),this.$backdrop=null},c.prototype.backdrop=function(b){var d=this,e=this.$element.hasClass("fade")?"fade":"";if(this.isShown&&this.options.backdrop){var f=a.support.transition&&e;if(this.$backdrop=a(document.createElement("div")).addClass("modal-backdrop "+e).appendTo(this.$body),this.$element.on("click.dismiss.bs.modal",a.proxy(function(a){return this.ignoreBackdropClick?void(this.ignoreBackdropClick=!1):void(a.target===a.currentTarget&&("static"==this.options.backdrop?this.$element[0].focus():this.hide()))},this)),f&&this.$backdrop[0].offsetWidth,this.$backdrop.addClass("in"),!b)return;f?this.$backdrop.one("bsTransitionEnd",b).emulateTransitionEnd(c.BACKDROP_TRANSITION_DURATION):b()}else if(!this.isShown&&this.$backdrop){this.$backdrop.removeClass("in");var g=function(){d.removeBackdrop(),b&&b()};a.support.transition&&this.$element.hasClass("fade")?this.$backdrop.one("bsTransitionEnd",g).emulateTransitionEnd(c.BACKDROP_TRANSITION_DURATION):g()}else b&&b()},c.prototype.handleUpdate=function(){this.adjustDialog()},c.prototype.adjustDialog=function(){var a=this.$element[0].scrollHeight>document.documentElement.clientHeight;this.$element.css({paddingLeft:!this.bodyIsOverflowing&&a?this.scrollbarWidth:"",paddingRight:this.bodyIsOverflowing&&!a?this.scrollbarWidth:""})},c.prototype.resetAdjustments=function(){this.$element.css({paddingLeft:"",paddingRight:""})},c.prototype.checkScrollbar=function(){var a=window.innerWidth;if(!a){var b=document.documentElement.getBoundingClientRect();a=b.right-Math.abs(b.left)}this.bodyIsOverflowing=document.body.clientWidth<a,this.scrollbarWidth=this.measureScrollbar()},c.prototype.setScrollbar=function(){var a=parseInt(this.$body.css("padding-right")||0,10);this.originalBodyPad=document.body.style.paddingRight||"",this.bodyIsOverflowing&&this.$body.css("padding-right",a+this.scrollbarWidth)},c.prototype.resetScrollbar=function(){this.$body.css("padding-right",this.originalBodyPad)},c.prototype.measureScrollbar=function(){var a=document.createElement("div");a.className="modal-scrollbar-measure",this.$body.append(a);var b=a.offsetWidth-a.clientWidth;return this.$body[0].removeChild(a),b};var d=a.fn.modal;a.fn.modal=b,a.fn.modal.Constructor=c,a.fn.modal.noConflict=function(){return a.fn.modal=d,this},a(document).on("click.bs.modal.data-api",'[data-toggle="modal"]',function(c){var d=a(this),e=d.attr("href"),f=a(d.attr("data-target")||e&&e.replace(/.*(?=#[^\s]+$)/,"")),g=f.data("bs.modal")?"toggle":a.extend({remote:!/#/.test(e)&&e},f.data(),d.data());d.is("a")&&c.preventDefault(),f.one("show.bs.modal",function(a){a.isDefaultPrevented()||f.one("hidden.bs.modal",function(){d.is(":visible")&&d.trigger("focus")})}),b.call(f,g,this)})}(jQuery),+function(a){"use strict";function b(b){return this.each(function(){var d=a(this),e=d.data("bs.tooltip"),f="object"==typeof b&&b;!e&&/destroy|hide/.test(b)||(e||d.data("bs.tooltip",e=new c(this,f)),"string"==typeof b&&e[b]())})}var c=function(a,b){this.type=null,this.options=null,this.enabled=null,this.timeout=null,this.hoverState=null,this.$element=null,this.inState=null,this.init("tooltip",a,b)};c.VERSION="3.3.7",c.TRANSITION_DURATION=150,c.DEFAULTS={animation:!0,placement:"top",selector:!1,template:'<div class="tooltip" role="tooltip"><div class="tooltip-arrow"></div><div class="tooltip-inner"></div></div>',trigger:"hover focus",title:"",delay:0,html:!1,container:!1,viewport:{selector:"body",padding:0}},c.prototype.init=function(b,c,d){if(this.enabled=!0,this.type=b,this.$element=a(c),this.options=this.getOptions(d),this.$viewport=this.options.viewport&&a(a.isFunction(this.options.viewport)?this.options.viewport.call(this,this.$element):this.options.viewport.selector||this.options.viewport),this.inState={click:!1,hover:!1,focus:!1},this.$element[0]instanceof document.constructor&&!this.options.selector)throw new Error("`selector` option must be specified when initializing "+this.type+" on the window.document object!");for(var e=this.options.trigger.split(" "),f=e.length;f--;){var g=e[f];if("click"==g)this.$element.on("click."+this.type,this.options.selector,a.proxy(this.toggle,this));else if("manual"!=g){var h="hover"==g?"mouseenter":"focusin",i="hover"==g?"mouseleave":"focusout";this.$element.on(h+"."+this.type,this.options.selector,a.proxy(this.enter,this)),this.$element.on(i+"."+this.type,this.options.selector,a.proxy(this.leave,this))}}this.options.selector?this._options=a.extend({},this.options,{trigger:"manual",selector:""}):this.fixTitle()},c.prototype.getDefaults=function(){return c.DEFAULTS},c.prototype.getOptions=function(b){return b=a.extend({},this.getDefaults(),this.$element.data(),b),b.delay&&"number"==typeof b.delay&&(b.delay={show:b.delay,hide:b.delay}),b},c.prototype.getDelegateOptions=function(){var b={},c=this.getDefaults();return this._options&&a.each(this._options,function(a,d){c[a]!=d&&(b[a]=d)}),b},c.prototype.enter=function(b){var c=b instanceof this.constructor?b:a(b.currentTarget).data("bs."+this.type);return c||(c=new this.constructor(b.currentTarget,this.getDelegateOptions()),a(b.currentTarget).data("bs."+this.type,c)),b instanceof a.Event&&(c.inState["focusin"==b.type?"focus":"hover"]=!0),c.tip().hasClass("in")||"in"==c.hoverState?void(c.hoverState="in"):(clearTimeout(c.timeout),c.hoverState="in",c.options.delay&&c.options.delay.show?void(c.timeout=setTimeout(function(){"in"==c.hoverState&&c.show()},c.options.delay.show)):c.show())},c.prototype.isInStateTrue=function(){for(var a in this.inState)if(this.inState[a])return!0;return!1},c.prototype.leave=function(b){var c=b instanceof this.constructor?b:a(b.currentTarget).data("bs."+this.type);if(c||(c=new this.constructor(b.currentTarget,this.getDelegateOptions()),a(b.currentTarget).data("bs."+this.type,c)),b instanceof a.Event&&(c.inState["focusout"==b.type?"focus":"hover"]=!1),!c.isInStateTrue())return clearTimeout(c.timeout),c.hoverState="out",c.options.delay&&c.options.delay.hide?void(c.timeout=setTimeout(function(){"out"==c.hoverState&&c.hide()},c.options.delay.hide)):c.hide()},c.prototype.show=function(){var b=a.Event("show.bs."+this.type);if(this.hasContent()&&this.enabled){this.$element.trigger(b);var d=a.contains(this.$element[0].ownerDocument.documentElement,this.$element[0]);if(b.isDefaultPrevented()||!d)return;var e=this,f=this.tip(),g=this.getUID(this.type);this.setContent(),f.attr("id",g),this.$element.attr("aria-describedby",g),this.options.animation&&f.addClass("fade");var h="function"==typeof this.options.placement?this.options.placement.call(this,f[0],this.$element[0]):this.options.placement,i=/\s?auto?\s?/i,j=i.test(h);j&&(h=h.replace(i,"")||"top"),f.detach().css({top:0,left:0,display:"block"}).addClass(h).data("bs."+this.type,this),this.options.container?f.appendTo(this.options.container):f.insertAfter(this.$element),this.$element.trigger("inserted.bs."+this.type);var k=this.getPosition(),l=f[0].offsetWidth,m=f[0].offsetHeight;if(j){var n=h,o=this.getPosition(this.$viewport);h="bottom"==h&&k.bottom+m>o.bottom?"top":"top"==h&&k.top-m<o.top?"bottom":"right"==h&&k.right+l>o.width?"left":"left"==h&&k.left-l<o.left?"right":h,f.removeClass(n).addClass(h)}var p=this.getCalculatedOffset(h,k,l,m);this.applyPlacement(p,h);var q=function(){var a=e.hoverState;e.$element.trigger("shown.bs."+e.type),e.hoverState=null,"out"==a&&e.leave(e)};a.support.transition&&this.$tip.hasClass("fade")?f.one("bsTransitionEnd",q).emulateTransitionEnd(c.TRANSITION_DURATION):q()}},c.prototype.applyPlacement=function(b,c){var d=this.tip(),e=d[0].offsetWidth,f=d[0].offsetHeight,g=parseInt(d.css("margin-top"),10),h=parseInt(d.css("margin-left"),10);isNaN(g)&&(g=0),isNaN(h)&&(h=0),b.top+=g,b.left+=h,a.offset.setOffset(d[0],a.extend({using:function(a){d.css({top:Math.round(a.top),left:Math.round(a.left)})}},b),0),d.addClass("in");var i=d[0].offsetWidth,j=d[0].offsetHeight;"top"==c&&j!=f&&(b.top=b.top+f-j);var k=this.getViewportAdjustedDelta(c,b,i,j);k.left?b.left+=k.left:b.top+=k.top;var l=/top|bottom/.test(c),m=l?2*k.left-e+i:2*k.top-f+j,n=l?"offsetWidth":"offsetHeight";d.offset(b),this.replaceArrow(m,d[0][n],l)},c.prototype.replaceArrow=function(a,b,c){this.arrow().css(c?"left":"top",50*(1-a/b)+"%").css(c?"top":"left","")},c.prototype.setContent=function(){var a=this.tip(),b=this.getTitle();a.find(".tooltip-inner")[this.options.html?"html":"text"](b),a.removeClass("fade in top bottom left right")},c.prototype.hide=function(b){function d(){"in"!=e.hoverState&&f.detach(),e.$element&&e.$element.removeAttr("aria-describedby").trigger("hidden.bs."+e.type),b&&b()}var e=this,f=a(this.$tip),g=a.Event("hide.bs."+this.type);if(this.$element.trigger(g),!g.isDefaultPrevented())return f.removeClass("in"),a.support.transition&&f.hasClass("fade")?f.one("bsTransitionEnd",d).emulateTransitionEnd(c.TRANSITION_DURATION):d(),this.hoverState=null,this},c.prototype.fixTitle=function(){var a=this.$element;(a.attr("title")||"string"!=typeof a.attr("data-original-title"))&&a.attr("data-original-title",a.attr("title")||"").attr("title","")},c.prototype.hasContent=function(){return this.getTitle()},c.prototype.getPosition=function(b){b=b||this.$element;var c=b[0],d="BODY"==c.tagName,e=c.getBoundingClientRect();null==e.width&&(e=a.extend({},e,{width:e.right-e.left,height:e.bottom-e.top}));var f=window.SVGElement&&c instanceof window.SVGElement,g=d?{top:0,left:0}:f?null:b.offset(),h={scroll:d?document.documentElement.scrollTop||document.body.scrollTop:b.scrollTop()},i=d?{width:a(window).width(),height:a(window).height()}:null;return a.extend({},e,h,i,g)},c.prototype.getCalculatedOffset=function(a,b,c,d){return"bottom"==a?{top:b.top+b.height,left:b.left+b.width/2-c/2}:"top"==a?{top:b.top-d,left:b.left+b.width/2-c/2}:"left"==a?{top:b.top+b.height/2-d/2,left:b.left-c}:{top:b.top+b.height/2-d/2,left:b.left+b.width}},c.prototype.getViewportAdjustedDelta=function(a,b,c,d){var e={top:0,left:0};if(!this.$viewport)return e;var f=this.options.viewport&&this.options.viewport.padding||0,g=this.getPosition(this.$viewport);if(/right|left/.test(a)){var h=b.top-f-g.scroll,i=b.top+f-g.scroll+d;h<g.top?e.top=g.top-h:i>g.top+g.height&&(e.top=g.top+g.height-i)}else{var j=b.left-f,k=b.left+f+c;j<g.left?e.left=g.left-j:k>g.right&&(e.left=g.left+g.width-k)}return e},c.prototype.getTitle=function(){var a,b=this.$element,c=this.options;return a=b.attr("data-original-title")||("function"==typeof c.title?c.title.call(b[0]):c.title)},c.prototype.getUID=function(a){do a+=~~(1e6*Math.random());while(document.getElementById(a));return a},c.prototype.tip=function(){if(!this.$tip&&(this.$tip=a(this.options.template),1!=this.$tip.length))throw new Error(this.type+" `template` option must consist of exactly 1 top-level element!");return this.$tip},c.prototype.arrow=function(){return this.$arrow=this.$arrow||this.tip().find(".tooltip-arrow")},c.prototype.enable=function(){this.enabled=!0},c.prototype.disable=function(){this.enabled=!1},c.prototype.toggleEnabled=function(){this.enabled=!this.enabled},c.prototype.toggle=function(b){var c=this;b&&(c=a(b.currentTarget).data("bs."+this.type),c||(c=new this.constructor(b.currentTarget,this.getDelegateOptions()),a(b.currentTarget).data("bs."+this.type,c))),b?(c.inState.click=!c.inState.click,c.isInStateTrue()?c.enter(c):c.leave(c)):c.tip().hasClass("in")?c.leave(c):c.enter(c)},c.prototype.destroy=function(){var a=this;clearTimeout(this.timeout),this.hide(function(){a.$element.off("."+a.type).removeData("bs."+a.type),a.$tip&&a.$tip.detach(),a.$tip=null,a.$arrow=null,a.$viewport=null,a.$element=null})};var d=a.fn.tooltip;a.fn.tooltip=b,a.fn.tooltip.Constructor=c,a.fn.tooltip.noConflict=function(){return a.fn.tooltip=d,this}}(jQuery),+function(a){"use strict";function b(b){return this.each(function(){var d=a(this),e=d.data("bs.popover"),f="object"==typeof b&&b;!e&&/destroy|hide/.test(b)||(e||d.data("bs.popover",e=new c(this,f)),"string"==typeof b&&e[b]())})}var c=function(a,b){this.init("popover",a,b)};if(!a.fn.tooltip)throw new Error("Popover requires tooltip.js");c.VERSION="3.3.7",c.DEFAULTS=a.extend({},a.fn.tooltip.Constructor.DEFAULTS,{placement:"right",trigger:"click",content:"",template:'<div class="popover" role="tooltip"><div class="arrow"></div><h3 class="popover-title"></h3><div class="popover-content"></div></div>'}),c.prototype=a.extend({},a.fn.tooltip.Constructor.prototype),c.prototype.constructor=c,c.prototype.getDefaults=function(){return c.DEFAULTS},c.prototype.setContent=function(){var a=this.tip(),b=this.getTitle(),c=this.getContent();a.find(".popover-title")[this.options.html?"html":"text"](b),a.find(".popover-content").children().detach().end()[this.options.html?"string"==typeof c?"html":"append":"text"](c),a.removeClass("fade top bottom left right in"),a.find(".popover-title").html()||a.find(".popover-title").hide()},c.prototype.hasContent=function(){return this.getTitle()||this.getContent()},c.prototype.getContent=function(){var a=this.$element,b=this.options;return a.attr("data-content")||("function"==typeof b.content?b.content.call(a[0]):b.content)},c.prototype.arrow=function(){return this.$arrow=this.$arrow||this.tip().find(".arrow")};var d=a.fn.popover;a.fn.popover=b,a.fn.popover.Constructor=c,a.fn.popover.noConflict=function(){return a.fn.popover=d,this}}(jQuery),+function(a){"use strict";function b(c,d){this.$body=a(document.body),this.$scrollElement=a(a(c).is(document.body)?window:c),this.options=a.extend({},b.DEFAULTS,d),this.selector=(this.options.target||"")+" .nav li > a",this.offsets=[],this.targets=[],this.activeTarget=null,this.scrollHeight=0,this.$scrollElement.on("scroll.bs.scrollspy",a.proxy(this.process,this)),this.refresh(),this.process()}function c(c){return this.each(function(){var d=a(this),e=d.data("bs.scrollspy"),f="object"==typeof c&&c;e||d.data("bs.scrollspy",e=new b(this,f)),"string"==typeof c&&e[c]()})}b.VERSION="3.3.7",b.DEFAULTS={offset:10},b.prototype.getScrollHeight=function(){return this.$scrollElement[0].scrollHeight||Math.max(this.$body[0].scrollHeight,document.documentElement.scrollHeight)},b.prototype.refresh=function(){var b=this,c="offset",d=0;this.offsets=[],this.targets=[],this.scrollHeight=this.getScrollHeight(),a.isWindow(this.$scrollElement[0])||(c="position",d=this.$scrollElement.scrollTop()),this.$body.find(this.selector).map(function(){var b=a(this),e=b.data("target")||b.attr("href"),f=/^#./.test(e)&&a(e);return f&&f.length&&f.is(":visible")&&[[f[c]().top+d,e]]||null}).sort(function(a,b){return a[0]-b[0]}).each(function(){b.offsets.push(this[0]),b.targets.push(this[1])})},b.prototype.process=function(){var a,b=this.$scrollElement.scrollTop()+this.options.offset,c=this.getScrollHeight(),d=this.options.offset+c-this.$scrollElement.height(),e=this.offsets,f=this.targets,g=this.activeTarget;if(this.scrollHeight!=c&&this.refresh(),b>=d)return g!=(a=f[f.length-1])&&this.activate(a);if(g&&b<e[0])return this.activeTarget=null,this.clear();for(a=e.length;a--;)g!=f[a]&&b>=e[a]&&(void 0===e[a+1]||b<e[a+1])&&this.activate(f[a])},b.prototype.activate=function(b){
-this.activeTarget=b,this.clear();var c=this.selector+'[data-target="'+b+'"],'+this.selector+'[href="'+b+'"]',d=a(c).parents("li").addClass("active");d.parent(".dropdown-menu").length&&(d=d.closest("li.dropdown").addClass("active")),d.trigger("activate.bs.scrollspy")},b.prototype.clear=function(){a(this.selector).parentsUntil(this.options.target,".active").removeClass("active")};var d=a.fn.scrollspy;a.fn.scrollspy=c,a.fn.scrollspy.Constructor=b,a.fn.scrollspy.noConflict=function(){return a.fn.scrollspy=d,this},a(window).on("load.bs.scrollspy.data-api",function(){a('[data-spy="scroll"]').each(function(){var b=a(this);c.call(b,b.data())})})}(jQuery),+function(a){"use strict";function b(b){return this.each(function(){var d=a(this),e=d.data("bs.tab");e||d.data("bs.tab",e=new c(this)),"string"==typeof b&&e[b]()})}var c=function(b){this.element=a(b)};c.VERSION="3.3.7",c.TRANSITION_DURATION=150,c.prototype.show=function(){var b=this.element,c=b.closest("ul:not(.dropdown-menu)"),d=b.data("target");if(d||(d=b.attr("href"),d=d&&d.replace(/.*(?=#[^\s]*$)/,"")),!b.parent("li").hasClass("active")){var e=c.find(".active:last a"),f=a.Event("hide.bs.tab",{relatedTarget:b[0]}),g=a.Event("show.bs.tab",{relatedTarget:e[0]});if(e.trigger(f),b.trigger(g),!g.isDefaultPrevented()&&!f.isDefaultPrevented()){var h=a(d);this.activate(b.closest("li"),c),this.activate(h,h.parent(),function(){e.trigger({type:"hidden.bs.tab",relatedTarget:b[0]}),b.trigger({type:"shown.bs.tab",relatedTarget:e[0]})})}}},c.prototype.activate=function(b,d,e){function f(){g.removeClass("active").find("> .dropdown-menu > .active").removeClass("active").end().find('[data-toggle="tab"]').attr("aria-expanded",!1),b.addClass("active").find('[data-toggle="tab"]').attr("aria-expanded",!0),h?(b[0].offsetWidth,b.addClass("in")):b.removeClass("fade"),b.parent(".dropdown-menu").length&&b.closest("li.dropdown").addClass("active").end().find('[data-toggle="tab"]').attr("aria-expanded",!0),e&&e()}var g=d.find("> .active"),h=e&&a.support.transition&&(g.length&&g.hasClass("fade")||!!d.find("> .fade").length);g.length&&h?g.one("bsTransitionEnd",f).emulateTransitionEnd(c.TRANSITION_DURATION):f(),g.removeClass("in")};var d=a.fn.tab;a.fn.tab=b,a.fn.tab.Constructor=c,a.fn.tab.noConflict=function(){return a.fn.tab=d,this};var e=function(c){c.preventDefault(),b.call(a(this),"show")};a(document).on("click.bs.tab.data-api",'[data-toggle="tab"]',e).on("click.bs.tab.data-api",'[data-toggle="pill"]',e)}(jQuery),+function(a){"use strict";function b(b){return this.each(function(){var d=a(this),e=d.data("bs.affix"),f="object"==typeof b&&b;e||d.data("bs.affix",e=new c(this,f)),"string"==typeof b&&e[b]()})}var c=function(b,d){this.options=a.extend({},c.DEFAULTS,d),this.$target=a(this.options.target).on("scroll.bs.affix.data-api",a.proxy(this.checkPosition,this)).on("click.bs.affix.data-api",a.proxy(this.checkPositionWithEventLoop,this)),this.$element=a(b),this.affixed=null,this.unpin=null,this.pinnedOffset=null,this.checkPosition()};c.VERSION="3.3.7",c.RESET="affix affix-top affix-bottom",c.DEFAULTS={offset:0,target:window},c.prototype.getState=function(a,b,c,d){var e=this.$target.scrollTop(),f=this.$element.offset(),g=this.$target.height();if(null!=c&&"top"==this.affixed)return e<c&&"top";if("bottom"==this.affixed)return null!=c?!(e+this.unpin<=f.top)&&"bottom":!(e+g<=a-d)&&"bottom";var h=null==this.affixed,i=h?e:f.top,j=h?g:b;return null!=c&&e<=c?"top":null!=d&&i+j>=a-d&&"bottom"},c.prototype.getPinnedOffset=function(){if(this.pinnedOffset)return this.pinnedOffset;this.$element.removeClass(c.RESET).addClass("affix");var a=this.$target.scrollTop(),b=this.$element.offset();return this.pinnedOffset=b.top-a},c.prototype.checkPositionWithEventLoop=function(){setTimeout(a.proxy(this.checkPosition,this),1)},c.prototype.checkPosition=function(){if(this.$element.is(":visible")){var b=this.$element.height(),d=this.options.offset,e=d.top,f=d.bottom,g=Math.max(a(document).height(),a(document.body).height());"object"!=typeof d&&(f=e=d),"function"==typeof e&&(e=d.top(this.$element)),"function"==typeof f&&(f=d.bottom(this.$element));var h=this.getState(g,b,e,f);if(this.affixed!=h){null!=this.unpin&&this.$element.css("top","");var i="affix"+(h?"-"+h:""),j=a.Event(i+".bs.affix");if(this.$element.trigger(j),j.isDefaultPrevented())return;this.affixed=h,this.unpin="bottom"==h?this.getPinnedOffset():null,this.$element.removeClass(c.RESET).addClass(i).trigger(i.replace("affix","affixed")+".bs.affix")}"bottom"==h&&this.$element.offset({top:g-b-f})}};var d=a.fn.affix;a.fn.affix=b,a.fn.affix.Constructor=c,a.fn.affix.noConflict=function(){return a.fn.affix=d,this},a(window).on("load",function(){a('[data-spy="affix"]').each(function(){var c=a(this),d=c.data();d.offset=d.offset||{},null!=d.offsetBottom&&(d.offset.bottom=d.offsetBottom),null!=d.offsetTop&&(d.offset.top=d.offsetTop),b.call(c,d)})})}(jQuery); \ No newline at end of file
+if("undefined"==typeof jQuery)throw new Error("Bootstrap's JavaScript requires jQuery. jQuery must be included before Bootstrap's JavaScript.");!function(t){var e=jQuery.fn.jquery.split(" ")[0].split(".");if(e[0]<2&&e[1]<9||1==e[0]&&9==e[1]&&e[2]<1||e[0]>=4)throw new Error("Bootstrap's JavaScript requires at least jQuery v1.9.1 but less than v4.0.0")}(),function(){function t(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function e(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}function n(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}var i="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},o=function(){function t(t,e){for(var n=0;n<e.length;n++){var i=e[n];i.enumerable=i.enumerable||!1,i.configurable=!0,"value"in i&&(i.writable=!0),Object.defineProperty(t,i.key,i)}}return function(e,n,i){return n&&t(e.prototype,n),i&&t(e,i),e}}(),r=function(t){function e(t){return{}.toString.call(t).match(/\s([a-zA-Z]+)/)[1].toLowerCase()}function n(t){return(t[0]||t).nodeType}function i(){return{bindType:s.end,delegateType:s.end,handle:function(e){if(t(e.target).is(this))return e.handleObj.handler.apply(this,arguments)}}}function o(){if(window.QUnit)return!1;var t=document.createElement("bootstrap");for(var e in a)if(void 0!==t.style[e])return{end:a[e]};return!1}function r(e){var n=this,i=!1;return t(this).one(l.TRANSITION_END,function(){i=!0}),setTimeout(function(){i||l.triggerTransitionEnd(n)},e),this}var s=!1,a={WebkitTransition:"webkitTransitionEnd",MozTransition:"transitionend",OTransition:"oTransitionEnd otransitionend",transition:"transitionend"},l={TRANSITION_END:"bsTransitionEnd",getUID:function(t){do{t+=~~(1e6*Math.random())}while(document.getElementById(t));return t},getSelectorFromElement:function(e){var n=e.getAttribute("data-target");n&&"#"!==n||(n=e.getAttribute("href")||"");try{return t(n).length>0?n:null}catch(t){return null}},reflow:function(t){return t.offsetHeight},triggerTransitionEnd:function(e){t(e).trigger(s.end)},supportsTransitionEnd:function(){return Boolean(s)},typeCheckConfig:function(t,i,o){for(var r in o)if(o.hasOwnProperty(r)){var s=o[r],a=i[r],l=a&&n(a)?"element":e(a);if(!new RegExp(s).test(l))throw new Error(t.toUpperCase()+': Option "'+r+'" provided type "'+l+'" but expected type "'+s+'".')}}};return s=o(),t.fn.emulateTransitionEnd=r,l.supportsTransitionEnd()&&(t.event.special[l.TRANSITION_END]=i()),l}(jQuery),s=(function(t){var e="alert",i=t.fn[e],s={DISMISS:'[data-dismiss="alert"]'},a={CLOSE:"close.bs.alert",CLOSED:"closed.bs.alert",CLICK_DATA_API:"click.bs.alert.data-api"},l={ALERT:"alert",FADE:"fade",SHOW:"show"},h=function(){function e(t){n(this,e),this._element=t}return e.prototype.close=function(t){t=t||this._element;var e=this._getRootElement(t);this._triggerCloseEvent(e).isDefaultPrevented()||this._removeElement(e)},e.prototype.dispose=function(){t.removeData(this._element,"bs.alert"),this._element=null},e.prototype._getRootElement=function(e){var n=r.getSelectorFromElement(e),i=!1;return n&&(i=t(n)[0]),i||(i=t(e).closest("."+l.ALERT)[0]),i},e.prototype._triggerCloseEvent=function(e){var n=t.Event(a.CLOSE);return t(e).trigger(n),n},e.prototype._removeElement=function(e){var n=this;t(e).removeClass(l.SHOW),r.supportsTransitionEnd()&&t(e).hasClass(l.FADE)?t(e).one(r.TRANSITION_END,function(t){return n._destroyElement(e,t)}).emulateTransitionEnd(150):this._destroyElement(e)},e.prototype._destroyElement=function(e){t(e).detach().trigger(a.CLOSED).remove()},e._jQueryInterface=function(n){return this.each(function(){var i=t(this),o=i.data("bs.alert");o||(o=new e(this),i.data("bs.alert",o)),"close"===n&&o[n](this)})},e._handleDismiss=function(t){return function(e){e&&e.preventDefault(),t.close(this)}},o(e,null,[{key:"VERSION",get:function(){return"4.0.0-beta"}}]),e}();t(document).on(a.CLICK_DATA_API,s.DISMISS,h._handleDismiss(new h)),t.fn[e]=h._jQueryInterface,t.fn[e].Constructor=h,t.fn[e].noConflict=function(){return t.fn[e]=i,h._jQueryInterface}}(jQuery),function(t){var e="button",i=t.fn[e],r={ACTIVE:"active",BUTTON:"btn",FOCUS:"focus"},s={DATA_TOGGLE_CARROT:'[data-toggle^="button"]',DATA_TOGGLE:'[data-toggle="buttons"]',INPUT:"input",ACTIVE:".active",BUTTON:".btn"},a={CLICK_DATA_API:"click.bs.button.data-api",FOCUS_BLUR_DATA_API:"focus.bs.button.data-api blur.bs.button.data-api"},l=function(){function e(t){n(this,e),this._element=t}return e.prototype.toggle=function(){var e=!0,n=!0,i=t(this._element).closest(s.DATA_TOGGLE)[0];if(i){var o=t(this._element).find(s.INPUT)[0];if(o){if("radio"===o.type)if(o.checked&&t(this._element).hasClass(r.ACTIVE))e=!1;else{var a=t(i).find(s.ACTIVE)[0];a&&t(a).removeClass(r.ACTIVE)}if(e){if(o.hasAttribute("disabled")||i.hasAttribute("disabled")||o.classList.contains("disabled")||i.classList.contains("disabled"))return;o.checked=!t(this._element).hasClass(r.ACTIVE),t(o).trigger("change")}o.focus(),n=!1}}n&&this._element.setAttribute("aria-pressed",!t(this._element).hasClass(r.ACTIVE)),e&&t(this._element).toggleClass(r.ACTIVE)},e.prototype.dispose=function(){t.removeData(this._element,"bs.button"),this._element=null},e._jQueryInterface=function(n){return this.each(function(){var i=t(this).data("bs.button");i||(i=new e(this),t(this).data("bs.button",i)),"toggle"===n&&i[n]()})},o(e,null,[{key:"VERSION",get:function(){return"4.0.0-beta"}}]),e}();t(document).on(a.CLICK_DATA_API,s.DATA_TOGGLE_CARROT,function(e){e.preventDefault();var n=e.target;t(n).hasClass(r.BUTTON)||(n=t(n).closest(s.BUTTON)),l._jQueryInterface.call(t(n),"toggle")}).on(a.FOCUS_BLUR_DATA_API,s.DATA_TOGGLE_CARROT,function(e){var n=t(e.target).closest(s.BUTTON)[0];t(n).toggleClass(r.FOCUS,/^focus(in)?$/.test(e.type))}),t.fn[e]=l._jQueryInterface,t.fn[e].Constructor=l,t.fn[e].noConflict=function(){return t.fn[e]=i,l._jQueryInterface}}(jQuery),function(t){var e="carousel",s="bs.carousel",a="."+s,l=t.fn[e],h={interval:5e3,keyboard:!0,slide:!1,pause:"hover",wrap:!0},c={interval:"(number|boolean)",keyboard:"boolean",slide:"(boolean|string)",pause:"(string|boolean)",wrap:"boolean"},u={NEXT:"next",PREV:"prev",LEFT:"left",RIGHT:"right"},d={SLIDE:"slide"+a,SLID:"slid"+a,KEYDOWN:"keydown"+a,MOUSEENTER:"mouseenter"+a,MOUSELEAVE:"mouseleave"+a,TOUCHEND:"touchend"+a,LOAD_DATA_API:"load.bs.carousel.data-api",CLICK_DATA_API:"click.bs.carousel.data-api"},f={CAROUSEL:"carousel",ACTIVE:"active",SLIDE:"slide",RIGHT:"carousel-item-right",LEFT:"carousel-item-left",NEXT:"carousel-item-next",PREV:"carousel-item-prev",ITEM:"carousel-item"},p={ACTIVE:".active",ACTIVE_ITEM:".active.carousel-item",ITEM:".carousel-item",NEXT_PREV:".carousel-item-next, .carousel-item-prev",INDICATORS:".carousel-indicators",DATA_SLIDE:"[data-slide], [data-slide-to]",DATA_RIDE:'[data-ride="carousel"]'},_=function(){function l(e,i){n(this,l),this._items=null,this._interval=null,this._activeElement=null,this._isPaused=!1,this._isSliding=!1,this.touchTimeout=null,this._config=this._getConfig(i),this._element=t(e)[0],this._indicatorsElement=t(this._element).find(p.INDICATORS)[0],this._addEventListeners()}return l.prototype.next=function(){this._isSliding||this._slide(u.NEXT)},l.prototype.nextWhenVisible=function(){document.hidden||this.next()},l.prototype.prev=function(){this._isSliding||this._slide(u.PREV)},l.prototype.pause=function(e){e||(this._isPaused=!0),t(this._element).find(p.NEXT_PREV)[0]&&r.supportsTransitionEnd()&&(r.triggerTransitionEnd(this._element),this.cycle(!0)),clearInterval(this._interval),this._interval=null},l.prototype.cycle=function(t){t||(this._isPaused=!1),this._interval&&(clearInterval(this._interval),this._interval=null),this._config.interval&&!this._isPaused&&(this._interval=setInterval((document.visibilityState?this.nextWhenVisible:this.next).bind(this),this._config.interval))},l.prototype.to=function(e){var n=this;this._activeElement=t(this._element).find(p.ACTIVE_ITEM)[0];var i=this._getItemIndex(this._activeElement);if(!(e>this._items.length-1||e<0))if(this._isSliding)t(this._element).one(d.SLID,function(){return n.to(e)});else{if(i===e)return this.pause(),void this.cycle();var o=e>i?u.NEXT:u.PREV;this._slide(o,this._items[e])}},l.prototype.dispose=function(){t(this._element).off(a),t.removeData(this._element,s),this._items=null,this._config=null,this._element=null,this._interval=null,this._isPaused=null,this._isSliding=null,this._activeElement=null,this._indicatorsElement=null},l.prototype._getConfig=function(n){return n=t.extend({},h,n),r.typeCheckConfig(e,n,c),n},l.prototype._addEventListeners=function(){var e=this;this._config.keyboard&&t(this._element).on(d.KEYDOWN,function(t){return e._keydown(t)}),"hover"===this._config.pause&&(t(this._element).on(d.MOUSEENTER,function(t){return e.pause(t)}).on(d.MOUSELEAVE,function(t){return e.cycle(t)}),"ontouchstart"in document.documentElement&&t(this._element).on(d.TOUCHEND,function(){e.pause(),e.touchTimeout&&clearTimeout(e.touchTimeout),e.touchTimeout=setTimeout(function(t){return e.cycle(t)},500+e._config.interval)}))},l.prototype._keydown=function(t){if(!/input|textarea/i.test(t.target.tagName))switch(t.which){case 37:t.preventDefault(),this.prev();break;case 39:t.preventDefault(),this.next();break;default:return}},l.prototype._getItemIndex=function(e){return this._items=t.makeArray(t(e).parent().find(p.ITEM)),this._items.indexOf(e)},l.prototype._getItemByDirection=function(t,e){var n=t===u.NEXT,i=t===u.PREV,o=this._getItemIndex(e),r=this._items.length-1;if((i&&0===o||n&&o===r)&&!this._config.wrap)return e;var s=(o+(t===u.PREV?-1:1))%this._items.length;return-1===s?this._items[this._items.length-1]:this._items[s]},l.prototype._triggerSlideEvent=function(e,n){var i=this._getItemIndex(e),o=this._getItemIndex(t(this._element).find(p.ACTIVE_ITEM)[0]),r=t.Event(d.SLIDE,{relatedTarget:e,direction:n,from:o,to:i});return t(this._element).trigger(r),r},l.prototype._setActiveIndicatorElement=function(e){if(this._indicatorsElement){t(this._indicatorsElement).find(p.ACTIVE).removeClass(f.ACTIVE);var n=this._indicatorsElement.children[this._getItemIndex(e)];n&&t(n).addClass(f.ACTIVE)}},l.prototype._slide=function(e,n){var i=this,o=t(this._element).find(p.ACTIVE_ITEM)[0],s=this._getItemIndex(o),a=n||o&&this._getItemByDirection(e,o),l=this._getItemIndex(a),h=Boolean(this._interval),c=void 0,_=void 0,g=void 0;if(e===u.NEXT?(c=f.LEFT,_=f.NEXT,g=u.LEFT):(c=f.RIGHT,_=f.PREV,g=u.RIGHT),a&&t(a).hasClass(f.ACTIVE))this._isSliding=!1;else if(!this._triggerSlideEvent(a,g).isDefaultPrevented()&&o&&a){this._isSliding=!0,h&&this.pause(),this._setActiveIndicatorElement(a);var m=t.Event(d.SLID,{relatedTarget:a,direction:g,from:s,to:l});r.supportsTransitionEnd()&&t(this._element).hasClass(f.SLIDE)?(t(a).addClass(_),r.reflow(a),t(o).addClass(c),t(a).addClass(c),t(o).one(r.TRANSITION_END,function(){t(a).removeClass(c+" "+_).addClass(f.ACTIVE),t(o).removeClass(f.ACTIVE+" "+_+" "+c),i._isSliding=!1,setTimeout(function(){return t(i._element).trigger(m)},0)}).emulateTransitionEnd(600)):(t(o).removeClass(f.ACTIVE),t(a).addClass(f.ACTIVE),this._isSliding=!1,t(this._element).trigger(m)),h&&this.cycle()}},l._jQueryInterface=function(e){return this.each(function(){var n=t(this).data(s),o=t.extend({},h,t(this).data());"object"===(void 0===e?"undefined":i(e))&&t.extend(o,e);var r="string"==typeof e?e:o.slide;if(n||(n=new l(this,o),t(this).data(s,n)),"number"==typeof e)n.to(e);else if("string"==typeof r){if(void 0===n[r])throw new Error('No method named "'+r+'"');n[r]()}else o.interval&&(n.pause(),n.cycle())})},l._dataApiClickHandler=function(e){var n=r.getSelectorFromElement(this);if(n){var i=t(n)[0];if(i&&t(i).hasClass(f.CAROUSEL)){var o=t.extend({},t(i).data(),t(this).data()),a=this.getAttribute("data-slide-to");a&&(o.interval=!1),l._jQueryInterface.call(t(i),o),a&&t(i).data(s).to(a),e.preventDefault()}}},o(l,null,[{key:"VERSION",get:function(){return"4.0.0-beta"}},{key:"Default",get:function(){return h}}]),l}();t(document).on(d.CLICK_DATA_API,p.DATA_SLIDE,_._dataApiClickHandler),t(window).on(d.LOAD_DATA_API,function(){t(p.DATA_RIDE).each(function(){var e=t(this);_._jQueryInterface.call(e,e.data())})}),t.fn[e]=_._jQueryInterface,t.fn[e].Constructor=_,t.fn[e].noConflict=function(){return t.fn[e]=l,_._jQueryInterface}}(jQuery),function(t){var e="collapse",s="bs.collapse",a=t.fn[e],l={toggle:!0,parent:""},h={toggle:"boolean",parent:"string"},c={SHOW:"show.bs.collapse",SHOWN:"shown.bs.collapse",HIDE:"hide.bs.collapse",HIDDEN:"hidden.bs.collapse",CLICK_DATA_API:"click.bs.collapse.data-api"},u={SHOW:"show",COLLAPSE:"collapse",COLLAPSING:"collapsing",COLLAPSED:"collapsed"},d={WIDTH:"width",HEIGHT:"height"},f={ACTIVES:".show, .collapsing",DATA_TOGGLE:'[data-toggle="collapse"]'},p=function(){function a(e,i){n(this,a),this._isTransitioning=!1,this._element=e,this._config=this._getConfig(i),this._triggerArray=t.makeArray(t('[data-toggle="collapse"][href="#'+e.id+'"],[data-toggle="collapse"][data-target="#'+e.id+'"]'));for(var o=t(f.DATA_TOGGLE),s=0;s<o.length;s++){var l=o[s],h=r.getSelectorFromElement(l);null!==h&&t(h).filter(e).length>0&&this._triggerArray.push(l)}this._parent=this._config.parent?this._getParent():null,this._config.parent||this._addAriaAndCollapsedClass(this._element,this._triggerArray),this._config.toggle&&this.toggle()}return a.prototype.toggle=function(){t(this._element).hasClass(u.SHOW)?this.hide():this.show()},a.prototype.show=function(){var e=this;if(!this._isTransitioning&&!t(this._element).hasClass(u.SHOW)){var n=void 0,i=void 0;if(this._parent&&((n=t.makeArray(t(this._parent).children().children(f.ACTIVES))).length||(n=null)),!(n&&(i=t(n).data(s))&&i._isTransitioning)){var o=t.Event(c.SHOW);if(t(this._element).trigger(o),!o.isDefaultPrevented()){n&&(a._jQueryInterface.call(t(n),"hide"),i||t(n).data(s,null));var l=this._getDimension();t(this._element).removeClass(u.COLLAPSE).addClass(u.COLLAPSING),this._element.style[l]=0,this._triggerArray.length&&t(this._triggerArray).removeClass(u.COLLAPSED).attr("aria-expanded",!0),this.setTransitioning(!0);var h=function(){t(e._element).removeClass(u.COLLAPSING).addClass(u.COLLAPSE).addClass(u.SHOW),e._element.style[l]="",e.setTransitioning(!1),t(e._element).trigger(c.SHOWN)};if(r.supportsTransitionEnd()){var d="scroll"+(l[0].toUpperCase()+l.slice(1));t(this._element).one(r.TRANSITION_END,h).emulateTransitionEnd(600),this._element.style[l]=this._element[d]+"px"}else h()}}}},a.prototype.hide=function(){var e=this;if(!this._isTransitioning&&t(this._element).hasClass(u.SHOW)){var n=t.Event(c.HIDE);if(t(this._element).trigger(n),!n.isDefaultPrevented()){var i=this._getDimension();if(this._element.style[i]=this._element.getBoundingClientRect()[i]+"px",r.reflow(this._element),t(this._element).addClass(u.COLLAPSING).removeClass(u.COLLAPSE).removeClass(u.SHOW),this._triggerArray.length)for(var o=0;o<this._triggerArray.length;o++){var s=this._triggerArray[o],a=r.getSelectorFromElement(s);null!==a&&(t(a).hasClass(u.SHOW)||t(s).addClass(u.COLLAPSED).attr("aria-expanded",!1))}this.setTransitioning(!0);var l=function(){e.setTransitioning(!1),t(e._element).removeClass(u.COLLAPSING).addClass(u.COLLAPSE).trigger(c.HIDDEN)};this._element.style[i]="",r.supportsTransitionEnd()?t(this._element).one(r.TRANSITION_END,l).emulateTransitionEnd(600):l()}}},a.prototype.setTransitioning=function(t){this._isTransitioning=t},a.prototype.dispose=function(){t.removeData(this._element,s),this._config=null,this._parent=null,this._element=null,this._triggerArray=null,this._isTransitioning=null},a.prototype._getConfig=function(n){return n=t.extend({},l,n),n.toggle=Boolean(n.toggle),r.typeCheckConfig(e,n,h),n},a.prototype._getDimension=function(){return t(this._element).hasClass(d.WIDTH)?d.WIDTH:d.HEIGHT},a.prototype._getParent=function(){var e=this,n=t(this._config.parent)[0],i='[data-toggle="collapse"][data-parent="'+this._config.parent+'"]';return t(n).find(i).each(function(t,n){e._addAriaAndCollapsedClass(a._getTargetFromElement(n),[n])}),n},a.prototype._addAriaAndCollapsedClass=function(e,n){if(e){var i=t(e).hasClass(u.SHOW);n.length&&t(n).toggleClass(u.COLLAPSED,!i).attr("aria-expanded",i)}},a._getTargetFromElement=function(e){var n=r.getSelectorFromElement(e);return n?t(n)[0]:null},a._jQueryInterface=function(e){return this.each(function(){var n=t(this),o=n.data(s),r=t.extend({},l,n.data(),"object"===(void 0===e?"undefined":i(e))&&e);if(!o&&r.toggle&&/show|hide/.test(e)&&(r.toggle=!1),o||(o=new a(this,r),n.data(s,o)),"string"==typeof e){if(void 0===o[e])throw new Error('No method named "'+e+'"');o[e]()}})},o(a,null,[{key:"VERSION",get:function(){return"4.0.0-beta"}},{key:"Default",get:function(){return l}}]),a}();t(document).on(c.CLICK_DATA_API,f.DATA_TOGGLE,function(e){/input|textarea/i.test(e.target.tagName)||e.preventDefault();var n=t(this),i=r.getSelectorFromElement(this);t(i).each(function(){var e=t(this),i=e.data(s)?"toggle":n.data();p._jQueryInterface.call(e,i)})}),t.fn[e]=p._jQueryInterface,t.fn[e].Constructor=p,t.fn[e].noConflict=function(){return t.fn[e]=a,p._jQueryInterface}}(jQuery),function(t){if("undefined"==typeof Popper)throw new Error("Bootstrap dropdown require Popper.js (https://popper.js.org)");var e="dropdown",s="bs.dropdown",a="."+s,l=t.fn[e],h=new RegExp("38|40|27"),c={HIDE:"hide"+a,HIDDEN:"hidden"+a,SHOW:"show"+a,SHOWN:"shown"+a,CLICK:"click"+a,CLICK_DATA_API:"click.bs.dropdown.data-api",KEYDOWN_DATA_API:"keydown.bs.dropdown.data-api",KEYUP_DATA_API:"keyup.bs.dropdown.data-api"},u={DISABLED:"disabled",SHOW:"show",DROPUP:"dropup",MENURIGHT:"dropdown-menu-right",MENULEFT:"dropdown-menu-left"},d={DATA_TOGGLE:'[data-toggle="dropdown"]',FORM_CHILD:".dropdown form",MENU:".dropdown-menu",NAVBAR_NAV:".navbar-nav",VISIBLE_ITEMS:".dropdown-menu .dropdown-item:not(.disabled)"},f={TOP:"top-start",TOPEND:"top-end",BOTTOM:"bottom-start",BOTTOMEND:"bottom-end"},p={placement:f.BOTTOM,offset:0,flip:!0},_={placement:"string",offset:"(number|string)",flip:"boolean"},g=function(){function l(t,e){n(this,l),this._element=t,this._popper=null,this._config=this._getConfig(e),this._menu=this._getMenuElement(),this._inNavbar=this._detectNavbar(),this._addEventListeners()}return l.prototype.toggle=function(){if(!this._element.disabled&&!t(this._element).hasClass(u.DISABLED)){var e=l._getParentFromElement(this._element),n=t(this._menu).hasClass(u.SHOW);if(l._clearMenus(),!n){var i={relatedTarget:this._element},o=t.Event(c.SHOW,i);if(t(e).trigger(o),!o.isDefaultPrevented()){var r=this._element;t(e).hasClass(u.DROPUP)&&(t(this._menu).hasClass(u.MENULEFT)||t(this._menu).hasClass(u.MENURIGHT))&&(r=e),this._popper=new Popper(r,this._menu,this._getPopperConfig()),"ontouchstart"in document.documentElement&&!t(e).closest(d.NAVBAR_NAV).length&&t("body").children().on("mouseover",null,t.noop),this._element.focus(),this._element.setAttribute("aria-expanded",!0),t(this._menu).toggleClass(u.SHOW),t(e).toggleClass(u.SHOW).trigger(t.Event(c.SHOWN,i))}}}},l.prototype.dispose=function(){t.removeData(this._element,s),t(this._element).off(a),this._element=null,this._menu=null,null!==this._popper&&this._popper.destroy(),this._popper=null},l.prototype.update=function(){this._inNavbar=this._detectNavbar(),null!==this._popper&&this._popper.scheduleUpdate()},l.prototype._addEventListeners=function(){var e=this;t(this._element).on(c.CLICK,function(t){t.preventDefault(),t.stopPropagation(),e.toggle()})},l.prototype._getConfig=function(n){var i=t(this._element).data();return void 0!==i.placement&&(i.placement=f[i.placement.toUpperCase()]),n=t.extend({},this.constructor.Default,t(this._element).data(),n),r.typeCheckConfig(e,n,this.constructor.DefaultType),n},l.prototype._getMenuElement=function(){if(!this._menu){var e=l._getParentFromElement(this._element);this._menu=t(e).find(d.MENU)[0]}return this._menu},l.prototype._getPlacement=function(){var e=t(this._element).parent(),n=this._config.placement;return e.hasClass(u.DROPUP)||this._config.placement===f.TOP?(n=f.TOP,t(this._menu).hasClass(u.MENURIGHT)&&(n=f.TOPEND)):t(this._menu).hasClass(u.MENURIGHT)&&(n=f.BOTTOMEND),n},l.prototype._detectNavbar=function(){return t(this._element).closest(".navbar").length>0},l.prototype._getPopperConfig=function(){var t={placement:this._getPlacement(),modifiers:{offset:{offset:this._config.offset},flip:{enabled:this._config.flip}}};return this._inNavbar&&(t.modifiers.applyStyle={enabled:!this._inNavbar}),t},l._jQueryInterface=function(e){return this.each(function(){var n=t(this).data(s),o="object"===(void 0===e?"undefined":i(e))?e:null;if(n||(n=new l(this,o),t(this).data(s,n)),"string"==typeof e){if(void 0===n[e])throw new Error('No method named "'+e+'"');n[e]()}})},l._clearMenus=function(e){if(!e||3!==e.which&&("keyup"!==e.type||9===e.which))for(var n=t.makeArray(t(d.DATA_TOGGLE)),i=0;i<n.length;i++){var o=l._getParentFromElement(n[i]),r=t(n[i]).data(s),a={relatedTarget:n[i]};if(r){var h=r._menu;if(t(o).hasClass(u.SHOW)&&!(e&&("click"===e.type&&/input|textarea/i.test(e.target.tagName)||"keyup"===e.type&&9===e.which)&&t.contains(o,e.target))){var f=t.Event(c.HIDE,a);t(o).trigger(f),f.isDefaultPrevented()||("ontouchstart"in document.documentElement&&t("body").children().off("mouseover",null,t.noop),n[i].setAttribute("aria-expanded","false"),t(h).removeClass(u.SHOW),t(o).removeClass(u.SHOW).trigger(t.Event(c.HIDDEN,a)))}}}},l._getParentFromElement=function(e){var n=void 0,i=r.getSelectorFromElement(e);return i&&(n=t(i)[0]),n||e.parentNode},l._dataApiKeydownHandler=function(e){if(!(!h.test(e.which)||/button/i.test(e.target.tagName)&&32===e.which||/input|textarea/i.test(e.target.tagName)||(e.preventDefault(),e.stopPropagation(),this.disabled||t(this).hasClass(u.DISABLED)))){var n=l._getParentFromElement(this),i=t(n).hasClass(u.SHOW);if((i||27===e.which&&32===e.which)&&(!i||27!==e.which&&32!==e.which)){var o=t(n).find(d.VISIBLE_ITEMS).get();if(o.length){var r=o.indexOf(e.target);38===e.which&&r>0&&r--,40===e.which&&r<o.length-1&&r++,r<0&&(r=0),o[r].focus()}}else{if(27===e.which){var s=t(n).find(d.DATA_TOGGLE)[0];t(s).trigger("focus")}t(this).trigger("click")}}},o(l,null,[{key:"VERSION",get:function(){return"4.0.0-beta"}},{key:"Default",get:function(){return p}},{key:"DefaultType",get:function(){return _}}]),l}();t(document).on(c.KEYDOWN_DATA_API,d.DATA_TOGGLE,g._dataApiKeydownHandler).on(c.KEYDOWN_DATA_API,d.MENU,g._dataApiKeydownHandler).on(c.CLICK_DATA_API+" "+c.KEYUP_DATA_API,g._clearMenus).on(c.CLICK_DATA_API,d.DATA_TOGGLE,function(e){e.preventDefault(),e.stopPropagation(),g._jQueryInterface.call(t(this),"toggle")}).on(c.CLICK_DATA_API,d.FORM_CHILD,function(t){t.stopPropagation()}),t.fn[e]=g._jQueryInterface,t.fn[e].Constructor=g,t.fn[e].noConflict=function(){return t.fn[e]=l,g._jQueryInterface}}(jQuery),function(t){var e="modal",s=".bs.modal",a=t.fn[e],l={backdrop:!0,keyboard:!0,focus:!0,show:!0},h={backdrop:"(boolean|string)",keyboard:"boolean",focus:"boolean",show:"boolean"},c={HIDE:"hide.bs.modal",HIDDEN:"hidden.bs.modal",SHOW:"show.bs.modal",SHOWN:"shown.bs.modal",FOCUSIN:"focusin.bs.modal",RESIZE:"resize.bs.modal",CLICK_DISMISS:"click.dismiss.bs.modal",KEYDOWN_DISMISS:"keydown.dismiss.bs.modal",MOUSEUP_DISMISS:"mouseup.dismiss.bs.modal",MOUSEDOWN_DISMISS:"mousedown.dismiss.bs.modal",CLICK_DATA_API:"click.bs.modal.data-api"},u={SCROLLBAR_MEASURER:"modal-scrollbar-measure",BACKDROP:"modal-backdrop",OPEN:"modal-open",FADE:"fade",SHOW:"show"},d={DIALOG:".modal-dialog",DATA_TOGGLE:'[data-toggle="modal"]',DATA_DISMISS:'[data-dismiss="modal"]',FIXED_CONTENT:".fixed-top, .fixed-bottom, .is-fixed, .sticky-top",NAVBAR_TOGGLER:".navbar-toggler"},f=function(){function a(e,i){n(this,a),this._config=this._getConfig(i),this._element=e,this._dialog=t(e).find(d.DIALOG)[0],this._backdrop=null,this._isShown=!1,this._isBodyOverflowing=!1,this._ignoreBackdropClick=!1,this._originalBodyPadding=0,this._scrollbarWidth=0}return a.prototype.toggle=function(t){return this._isShown?this.hide():this.show(t)},a.prototype.show=function(e){var n=this;if(!this._isTransitioning){r.supportsTransitionEnd()&&t(this._element).hasClass(u.FADE)&&(this._isTransitioning=!0);var i=t.Event(c.SHOW,{relatedTarget:e});t(this._element).trigger(i),this._isShown||i.isDefaultPrevented()||(this._isShown=!0,this._checkScrollbar(),this._setScrollbar(),t(document.body).addClass(u.OPEN),this._setEscapeEvent(),this._setResizeEvent(),t(this._element).on(c.CLICK_DISMISS,d.DATA_DISMISS,function(t){return n.hide(t)}),t(this._dialog).on(c.MOUSEDOWN_DISMISS,function(){t(n._element).one(c.MOUSEUP_DISMISS,function(e){t(e.target).is(n._element)&&(n._ignoreBackdropClick=!0)})}),this._showBackdrop(function(){return n._showElement(e)}))}},a.prototype.hide=function(e){var n=this;if(e&&e.preventDefault(),!this._isTransitioning&&this._isShown){var i=r.supportsTransitionEnd()&&t(this._element).hasClass(u.FADE);i&&(this._isTransitioning=!0);var o=t.Event(c.HIDE);t(this._element).trigger(o),this._isShown&&!o.isDefaultPrevented()&&(this._isShown=!1,this._setEscapeEvent(),this._setResizeEvent(),t(document).off(c.FOCUSIN),t(this._element).removeClass(u.SHOW),t(this._element).off(c.CLICK_DISMISS),t(this._dialog).off(c.MOUSEDOWN_DISMISS),i?t(this._element).one(r.TRANSITION_END,function(t){return n._hideModal(t)}).emulateTransitionEnd(300):this._hideModal())}},a.prototype.dispose=function(){t.removeData(this._element,"bs.modal"),t(window,document,this._element,this._backdrop).off(s),this._config=null,this._element=null,this._dialog=null,this._backdrop=null,this._isShown=null,this._isBodyOverflowing=null,this._ignoreBackdropClick=null,this._scrollbarWidth=null},a.prototype.handleUpdate=function(){this._adjustDialog()},a.prototype._getConfig=function(n){return n=t.extend({},l,n),r.typeCheckConfig(e,n,h),n},a.prototype._showElement=function(e){var n=this,i=r.supportsTransitionEnd()&&t(this._element).hasClass(u.FADE);this._element.parentNode&&this._element.parentNode.nodeType===Node.ELEMENT_NODE||document.body.appendChild(this._element),this._element.style.display="block",this._element.removeAttribute("aria-hidden"),this._element.scrollTop=0,i&&r.reflow(this._element),t(this._element).addClass(u.SHOW),this._config.focus&&this._enforceFocus();var o=t.Event(c.SHOWN,{relatedTarget:e}),s=function(){n._config.focus&&n._element.focus(),n._isTransitioning=!1,t(n._element).trigger(o)};i?t(this._dialog).one(r.TRANSITION_END,s).emulateTransitionEnd(300):s()},a.prototype._enforceFocus=function(){var e=this;t(document).off(c.FOCUSIN).on(c.FOCUSIN,function(n){document===n.target||e._element===n.target||t(e._element).has(n.target).length||e._element.focus()})},a.prototype._setEscapeEvent=function(){var e=this;this._isShown&&this._config.keyboard?t(this._element).on(c.KEYDOWN_DISMISS,function(t){27===t.which&&(t.preventDefault(),e.hide())}):this._isShown||t(this._element).off(c.KEYDOWN_DISMISS)},a.prototype._setResizeEvent=function(){var e=this;this._isShown?t(window).on(c.RESIZE,function(t){return e.handleUpdate(t)}):t(window).off(c.RESIZE)},a.prototype._hideModal=function(){var e=this;this._element.style.display="none",this._element.setAttribute("aria-hidden",!0),this._isTransitioning=!1,this._showBackdrop(function(){t(document.body).removeClass(u.OPEN),e._resetAdjustments(),e._resetScrollbar(),t(e._element).trigger(c.HIDDEN)})},a.prototype._removeBackdrop=function(){this._backdrop&&(t(this._backdrop).remove(),this._backdrop=null)},a.prototype._showBackdrop=function(e){var n=this,i=t(this._element).hasClass(u.FADE)?u.FADE:"";if(this._isShown&&this._config.backdrop){var o=r.supportsTransitionEnd()&&i;if(this._backdrop=document.createElement("div"),this._backdrop.className=u.BACKDROP,i&&t(this._backdrop).addClass(i),t(this._backdrop).appendTo(document.body),t(this._element).on(c.CLICK_DISMISS,function(t){n._ignoreBackdropClick?n._ignoreBackdropClick=!1:t.target===t.currentTarget&&("static"===n._config.backdrop?n._element.focus():n.hide())}),o&&r.reflow(this._backdrop),t(this._backdrop).addClass(u.SHOW),!e)return;if(!o)return void e();t(this._backdrop).one(r.TRANSITION_END,e).emulateTransitionEnd(150)}else if(!this._isShown&&this._backdrop){t(this._backdrop).removeClass(u.SHOW);var s=function(){n._removeBackdrop(),e&&e()};r.supportsTransitionEnd()&&t(this._element).hasClass(u.FADE)?t(this._backdrop).one(r.TRANSITION_END,s).emulateTransitionEnd(150):s()}else e&&e()},a.prototype._adjustDialog=function(){var t=this._element.scrollHeight>document.documentElement.clientHeight;!this._isBodyOverflowing&&t&&(this._element.style.paddingLeft=this._scrollbarWidth+"px"),this._isBodyOverflowing&&!t&&(this._element.style.paddingRight=this._scrollbarWidth+"px")},a.prototype._resetAdjustments=function(){this._element.style.paddingLeft="",this._element.style.paddingRight=""},a.prototype._checkScrollbar=function(){this._isBodyOverflowing=document.body.clientWidth<window.innerWidth,this._scrollbarWidth=this._getScrollbarWidth()},a.prototype._setScrollbar=function(){var e=this;if(this._isBodyOverflowing){t(d.FIXED_CONTENT).each(function(n,i){var o=t(i)[0].style.paddingRight,r=t(i).css("padding-right");t(i).data("padding-right",o).css("padding-right",parseFloat(r)+e._scrollbarWidth+"px")}),t(d.NAVBAR_TOGGLER).each(function(n,i){var o=t(i)[0].style.marginRight,r=t(i).css("margin-right");t(i).data("margin-right",o).css("margin-right",parseFloat(r)+e._scrollbarWidth+"px")});var n=document.body.style.paddingRight,i=t("body").css("padding-right");t("body").data("padding-right",n).css("padding-right",parseFloat(i)+this._scrollbarWidth+"px")}},a.prototype._resetScrollbar=function(){t(d.FIXED_CONTENT).each(function(e,n){var i=t(n).data("padding-right");void 0!==i&&t(n).css("padding-right",i).removeData("padding-right")}),t(d.NAVBAR_TOGGLER).each(function(e,n){var i=t(n).data("margin-right");void 0!==i&&t(n).css("margin-right",i).removeData("margin-right")});var e=t("body").data("padding-right");void 0!==e&&t("body").css("padding-right",e).removeData("padding-right")},a.prototype._getScrollbarWidth=function(){var t=document.createElement("div");t.className=u.SCROLLBAR_MEASURER,document.body.appendChild(t);var e=t.getBoundingClientRect().width-t.clientWidth;return document.body.removeChild(t),e},a._jQueryInterface=function(e,n){return this.each(function(){var o=t(this).data("bs.modal"),r=t.extend({},a.Default,t(this).data(),"object"===(void 0===e?"undefined":i(e))&&e);if(o||(o=new a(this,r),t(this).data("bs.modal",o)),"string"==typeof e){if(void 0===o[e])throw new Error('No method named "'+e+'"');o[e](n)}else r.show&&o.show(n)})},o(a,null,[{key:"VERSION",get:function(){return"4.0.0-beta"}},{key:"Default",get:function(){return l}}]),a}();t(document).on(c.CLICK_DATA_API,d.DATA_TOGGLE,function(e){var n=this,i=void 0,o=r.getSelectorFromElement(this);o&&(i=t(o)[0]);var s=t(i).data("bs.modal")?"toggle":t.extend({},t(i).data(),t(this).data());"A"!==this.tagName&&"AREA"!==this.tagName||e.preventDefault();var a=t(i).one(c.SHOW,function(e){e.isDefaultPrevented()||a.one(c.HIDDEN,function(){t(n).is(":visible")&&n.focus()})});f._jQueryInterface.call(t(i),s,this)}),t.fn[e]=f._jQueryInterface,t.fn[e].Constructor=f,t.fn[e].noConflict=function(){return t.fn[e]=a,f._jQueryInterface}}(jQuery),function(t){var e="scrollspy",s=t.fn[e],a={offset:10,method:"auto",target:""},l={offset:"number",method:"string",target:"(string|element)"},h={ACTIVATE:"activate.bs.scrollspy",SCROLL:"scroll.bs.scrollspy",LOAD_DATA_API:"load.bs.scrollspy.data-api"},c={DROPDOWN_ITEM:"dropdown-item",DROPDOWN_MENU:"dropdown-menu",ACTIVE:"active"},u={DATA_SPY:'[data-spy="scroll"]',ACTIVE:".active",NAV_LIST_GROUP:".nav, .list-group",NAV_LINKS:".nav-link",LIST_ITEMS:".list-group-item",DROPDOWN:".dropdown",DROPDOWN_ITEMS:".dropdown-item",DROPDOWN_TOGGLE:".dropdown-toggle"},d={OFFSET:"offset",POSITION:"position"},f=function(){function s(e,i){var o=this;n(this,s),this._element=e,this._scrollElement="BODY"===e.tagName?window:e,this._config=this._getConfig(i),this._selector=this._config.target+" "+u.NAV_LINKS+","+this._config.target+" "+u.LIST_ITEMS+","+this._config.target+" "+u.DROPDOWN_ITEMS,this._offsets=[],this._targets=[],this._activeTarget=null,this._scrollHeight=0,t(this._scrollElement).on(h.SCROLL,function(t){return o._process(t)}),this.refresh(),this._process()}return s.prototype.refresh=function(){var e=this,n=this._scrollElement!==this._scrollElement.window?d.POSITION:d.OFFSET,i="auto"===this._config.method?n:this._config.method,o=i===d.POSITION?this._getScrollTop():0;this._offsets=[],this._targets=[],this._scrollHeight=this._getScrollHeight(),t.makeArray(t(this._selector)).map(function(e){var n=void 0,s=r.getSelectorFromElement(e);if(s&&(n=t(s)[0]),n){var a=n.getBoundingClientRect();if(a.width||a.height)return[t(n)[i]().top+o,s]}return null}).filter(function(t){return t}).sort(function(t,e){return t[0]-e[0]}).forEach(function(t){e._offsets.push(t[0]),e._targets.push(t[1])})},s.prototype.dispose=function(){t.removeData(this._element,"bs.scrollspy"),t(this._scrollElement).off(".bs.scrollspy"),this._element=null,this._scrollElement=null,this._config=null,this._selector=null,this._offsets=null,this._targets=null,this._activeTarget=null,this._scrollHeight=null},s.prototype._getConfig=function(n){if("string"!=typeof(n=t.extend({},a,n)).target){var i=t(n.target).attr("id");i||(i=r.getUID(e),t(n.target).attr("id",i)),n.target="#"+i}return r.typeCheckConfig(e,n,l),n},s.prototype._getScrollTop=function(){return this._scrollElement===window?this._scrollElement.pageYOffset:this._scrollElement.scrollTop},s.prototype._getScrollHeight=function(){return this._scrollElement.scrollHeight||Math.max(document.body.scrollHeight,document.documentElement.scrollHeight)},s.prototype._getOffsetHeight=function(){return this._scrollElement===window?window.innerHeight:this._scrollElement.getBoundingClientRect().height},s.prototype._process=function(){var t=this._getScrollTop()+this._config.offset,e=this._getScrollHeight(),n=this._config.offset+e-this._getOffsetHeight();if(this._scrollHeight!==e&&this.refresh(),t>=n){var i=this._targets[this._targets.length-1];this._activeTarget!==i&&this._activate(i)}else{if(this._activeTarget&&t<this._offsets[0]&&this._offsets[0]>0)return this._activeTarget=null,void this._clear();for(var o=this._offsets.length;o--;)this._activeTarget!==this._targets[o]&&t>=this._offsets[o]&&(void 0===this._offsets[o+1]||t<this._offsets[o+1])&&this._activate(this._targets[o])}},s.prototype._activate=function(e){this._activeTarget=e,this._clear();var n=this._selector.split(",");n=n.map(function(t){return t+'[data-target="'+e+'"],'+t+'[href="'+e+'"]'});var i=t(n.join(","));i.hasClass(c.DROPDOWN_ITEM)?(i.closest(u.DROPDOWN).find(u.DROPDOWN_TOGGLE).addClass(c.ACTIVE),i.addClass(c.ACTIVE)):(i.addClass(c.ACTIVE),i.parents(u.NAV_LIST_GROUP).prev(u.NAV_LINKS+", "+u.LIST_ITEMS).addClass(c.ACTIVE)),t(this._scrollElement).trigger(h.ACTIVATE,{relatedTarget:e})},s.prototype._clear=function(){t(this._selector).filter(u.ACTIVE).removeClass(c.ACTIVE)},s._jQueryInterface=function(e){return this.each(function(){var n=t(this).data("bs.scrollspy"),o="object"===(void 0===e?"undefined":i(e))&&e;if(n||(n=new s(this,o),t(this).data("bs.scrollspy",n)),"string"==typeof e){if(void 0===n[e])throw new Error('No method named "'+e+'"');n[e]()}})},o(s,null,[{key:"VERSION",get:function(){return"4.0.0-beta"}},{key:"Default",get:function(){return a}}]),s}();t(window).on(h.LOAD_DATA_API,function(){for(var e=t.makeArray(t(u.DATA_SPY)),n=e.length;n--;){var i=t(e[n]);f._jQueryInterface.call(i,i.data())}}),t.fn[e]=f._jQueryInterface,t.fn[e].Constructor=f,t.fn[e].noConflict=function(){return t.fn[e]=s,f._jQueryInterface}}(jQuery),function(t){var e=t.fn.tab,i={HIDE:"hide.bs.tab",HIDDEN:"hidden.bs.tab",SHOW:"show.bs.tab",SHOWN:"shown.bs.tab",CLICK_DATA_API:"click.bs.tab.data-api"},s={DROPDOWN_MENU:"dropdown-menu",ACTIVE:"active",DISABLED:"disabled",FADE:"fade",SHOW:"show"},a={DROPDOWN:".dropdown",NAV_LIST_GROUP:".nav, .list-group",ACTIVE:".active",DATA_TOGGLE:'[data-toggle="tab"], [data-toggle="pill"], [data-toggle="list"]',DROPDOWN_TOGGLE:".dropdown-toggle",DROPDOWN_ACTIVE_CHILD:"> .dropdown-menu .active"},l=function(){function e(t){n(this,e),this._element=t}return e.prototype.show=function(){var e=this;if(!(this._element.parentNode&&this._element.parentNode.nodeType===Node.ELEMENT_NODE&&t(this._element).hasClass(s.ACTIVE)||t(this._element).hasClass(s.DISABLED))){var n=void 0,o=void 0,l=t(this._element).closest(a.NAV_LIST_GROUP)[0],h=r.getSelectorFromElement(this._element);l&&(o=t.makeArray(t(l).find(a.ACTIVE)),o=o[o.length-1]);var c=t.Event(i.HIDE,{relatedTarget:this._element}),u=t.Event(i.SHOW,{relatedTarget:o});if(o&&t(o).trigger(c),t(this._element).trigger(u),!u.isDefaultPrevented()&&!c.isDefaultPrevented()){h&&(n=t(h)[0]),this._activate(this._element,l);var d=function(){var n=t.Event(i.HIDDEN,{relatedTarget:e._element}),r=t.Event(i.SHOWN,{relatedTarget:o});t(o).trigger(n),t(e._element).trigger(r)};n?this._activate(n,n.parentNode,d):d()}}},e.prototype.dispose=function(){t.removeData(this._element,"bs.tab"),this._element=null},e.prototype._activate=function(e,n,i){var o=this,l=t(n).find(a.ACTIVE)[0],h=i&&r.supportsTransitionEnd()&&l&&t(l).hasClass(s.FADE),c=function(){return o._transitionComplete(e,l,h,i)};l&&h?t(l).one(r.TRANSITION_END,c).emulateTransitionEnd(150):c(),l&&t(l).removeClass(s.SHOW)},e.prototype._transitionComplete=function(e,n,i,o){if(n){t(n).removeClass(s.ACTIVE);var l=t(n.parentNode).find(a.DROPDOWN_ACTIVE_CHILD)[0];l&&t(l).removeClass(s.ACTIVE),n.setAttribute("aria-expanded",!1)}if(t(e).addClass(s.ACTIVE),e.setAttribute("aria-expanded",!0),i?(r.reflow(e),t(e).addClass(s.SHOW)):t(e).removeClass(s.FADE),e.parentNode&&t(e.parentNode).hasClass(s.DROPDOWN_MENU)){var h=t(e).closest(a.DROPDOWN)[0];h&&t(h).find(a.DROPDOWN_TOGGLE).addClass(s.ACTIVE),e.setAttribute("aria-expanded",!0)}o&&o()},e._jQueryInterface=function(n){return this.each(function(){var i=t(this),o=i.data("bs.tab");if(o||(o=new e(this),i.data("bs.tab",o)),"string"==typeof n){if(void 0===o[n])throw new Error('No method named "'+n+'"');o[n]()}})},o(e,null,[{key:"VERSION",get:function(){return"4.0.0-beta"}}]),e}();t(document).on(i.CLICK_DATA_API,a.DATA_TOGGLE,function(e){e.preventDefault(),l._jQueryInterface.call(t(this),"show")}),t.fn.tab=l._jQueryInterface,t.fn.tab.Constructor=l,t.fn.tab.noConflict=function(){return t.fn.tab=e,l._jQueryInterface}}(jQuery),function(t){if("undefined"==typeof Popper)throw new Error("Bootstrap tooltips require Popper.js (https://popper.js.org)");var e="tooltip",s=".bs.tooltip",a=t.fn[e],l=new RegExp("(^|\\s)bs-tooltip\\S+","g"),h={animation:"boolean",template:"string",title:"(string|element|function)",trigger:"string",delay:"(number|object)",html:"boolean",selector:"(string|boolean)",placement:"(string|function)",offset:"(number|string)",container:"(string|element|boolean)",fallbackPlacement:"(string|array)"},c={AUTO:"auto",TOP:"top",RIGHT:"right",BOTTOM:"bottom",LEFT:"left"},u={animation:!0,template:'<div class="tooltip" role="tooltip"><div class="arrow"></div><div class="tooltip-inner"></div></div>',trigger:"hover focus",title:"",delay:0,html:!1,selector:!1,placement:"top",offset:0,container:!1,fallbackPlacement:"flip"},d={SHOW:"show",OUT:"out"},f={HIDE:"hide"+s,HIDDEN:"hidden"+s,SHOW:"show"+s,SHOWN:"shown"+s,INSERTED:"inserted"+s,CLICK:"click"+s,FOCUSIN:"focusin"+s,FOCUSOUT:"focusout"+s,MOUSEENTER:"mouseenter"+s,MOUSELEAVE:"mouseleave"+s},p={FADE:"fade",SHOW:"show"},_={TOOLTIP:".tooltip",TOOLTIP_INNER:".tooltip-inner",ARROW:".arrow"},g={HOVER:"hover",FOCUS:"focus",CLICK:"click",MANUAL:"manual"},m=function(){function a(t,e){n(this,a),this._isEnabled=!0,this._timeout=0,this._hoverState="",this._activeTrigger={},this._popper=null,this.element=t,this.config=this._getConfig(e),this.tip=null,this._setListeners()}return a.prototype.enable=function(){this._isEnabled=!0},a.prototype.disable=function(){this._isEnabled=!1},a.prototype.toggleEnabled=function(){this._isEnabled=!this._isEnabled},a.prototype.toggle=function(e){if(e){var n=this.constructor.DATA_KEY,i=t(e.currentTarget).data(n);i||(i=new this.constructor(e.currentTarget,this._getDelegateConfig()),t(e.currentTarget).data(n,i)),i._activeTrigger.click=!i._activeTrigger.click,i._isWithActiveTrigger()?i._enter(null,i):i._leave(null,i)}else{if(t(this.getTipElement()).hasClass(p.SHOW))return void this._leave(null,this);this._enter(null,this)}},a.prototype.dispose=function(){clearTimeout(this._timeout),t.removeData(this.element,this.constructor.DATA_KEY),t(this.element).off(this.constructor.EVENT_KEY),t(this.element).closest(".modal").off("hide.bs.modal"),this.tip&&t(this.tip).remove(),this._isEnabled=null,this._timeout=null,this._hoverState=null,this._activeTrigger=null,null!==this._popper&&this._popper.destroy(),this._popper=null,this.element=null,this.config=null,this.tip=null},a.prototype.show=function(){var e=this;if("none"===t(this.element).css("display"))throw new Error("Please use show on visible elements");var n=t.Event(this.constructor.Event.SHOW);if(this.isWithContent()&&this._isEnabled){t(this.element).trigger(n);var i=t.contains(this.element.ownerDocument.documentElement,this.element);if(n.isDefaultPrevented()||!i)return;var o=this.getTipElement(),s=r.getUID(this.constructor.NAME);o.setAttribute("id",s),this.element.setAttribute("aria-describedby",s),this.setContent(),this.config.animation&&t(o).addClass(p.FADE);var l="function"==typeof this.config.placement?this.config.placement.call(this,o,this.element):this.config.placement,h=this._getAttachment(l);this.addAttachmentClass(h);var c=!1===this.config.container?document.body:t(this.config.container);t(o).data(this.constructor.DATA_KEY,this),t.contains(this.element.ownerDocument.documentElement,this.tip)||t(o).appendTo(c),t(this.element).trigger(this.constructor.Event.INSERTED),this._popper=new Popper(this.element,o,{placement:h,modifiers:{offset:{offset:this.config.offset},flip:{behavior:this.config.fallbackPlacement},arrow:{element:_.ARROW}},onCreate:function(t){t.originalPlacement!==t.placement&&e._handlePopperPlacementChange(t)},onUpdate:function(t){e._handlePopperPlacementChange(t)}}),t(o).addClass(p.SHOW),"ontouchstart"in document.documentElement&&t("body").children().on("mouseover",null,t.noop);var u=function(){e.config.animation&&e._fixTransition();var n=e._hoverState;e._hoverState=null,t(e.element).trigger(e.constructor.Event.SHOWN),n===d.OUT&&e._leave(null,e)};r.supportsTransitionEnd()&&t(this.tip).hasClass(p.FADE)?t(this.tip).one(r.TRANSITION_END,u).emulateTransitionEnd(a._TRANSITION_DURATION):u()}},a.prototype.hide=function(e){var n=this,i=this.getTipElement(),o=t.Event(this.constructor.Event.HIDE),s=function(){n._hoverState!==d.SHOW&&i.parentNode&&i.parentNode.removeChild(i),n._cleanTipClass(),n.element.removeAttribute("aria-describedby"),t(n.element).trigger(n.constructor.Event.HIDDEN),null!==n._popper&&n._popper.destroy(),e&&e()};t(this.element).trigger(o),o.isDefaultPrevented()||(t(i).removeClass(p.SHOW),"ontouchstart"in document.documentElement&&t("body").children().off("mouseover",null,t.noop),this._activeTrigger[g.CLICK]=!1,this._activeTrigger[g.FOCUS]=!1,this._activeTrigger[g.HOVER]=!1,r.supportsTransitionEnd()&&t(this.tip).hasClass(p.FADE)?t(i).one(r.TRANSITION_END,s).emulateTransitionEnd(150):s(),this._hoverState="")},a.prototype.update=function(){null!==this._popper&&this._popper.scheduleUpdate()},a.prototype.isWithContent=function(){return Boolean(this.getTitle())},a.prototype.addAttachmentClass=function(e){t(this.getTipElement()).addClass("bs-tooltip-"+e)},a.prototype.getTipElement=function(){return this.tip=this.tip||t(this.config.template)[0]},a.prototype.setContent=function(){var e=t(this.getTipElement());this.setElementContent(e.find(_.TOOLTIP_INNER),this.getTitle()),e.removeClass(p.FADE+" "+p.SHOW)},a.prototype.setElementContent=function(e,n){var o=this.config.html;"object"===(void 0===n?"undefined":i(n))&&(n.nodeType||n.jquery)?o?t(n).parent().is(e)||e.empty().append(n):e.text(t(n).text()):e[o?"html":"text"](n)},a.prototype.getTitle=function(){var t=this.element.getAttribute("data-original-title");return t||(t="function"==typeof this.config.title?this.config.title.call(this.element):this.config.title),t},a.prototype._getAttachment=function(t){return c[t.toUpperCase()]},a.prototype._setListeners=function(){var e=this;this.config.trigger.split(" ").forEach(function(n){if("click"===n)t(e.element).on(e.constructor.Event.CLICK,e.config.selector,function(t){return e.toggle(t)});else if(n!==g.MANUAL){var i=n===g.HOVER?e.constructor.Event.MOUSEENTER:e.constructor.Event.FOCUSIN,o=n===g.HOVER?e.constructor.Event.MOUSELEAVE:e.constructor.Event.FOCUSOUT;t(e.element).on(i,e.config.selector,function(t){return e._enter(t)}).on(o,e.config.selector,function(t){return e._leave(t)})}t(e.element).closest(".modal").on("hide.bs.modal",function(){return e.hide()})}),this.config.selector?this.config=t.extend({},this.config,{trigger:"manual",selector:""}):this._fixTitle()},a.prototype._fixTitle=function(){var t=i(this.element.getAttribute("data-original-title"));(this.element.getAttribute("title")||"string"!==t)&&(this.element.setAttribute("data-original-title",this.element.getAttribute("title")||""),this.element.setAttribute("title",""))},a.prototype._enter=function(e,n){var i=this.constructor.DATA_KEY;(n=n||t(e.currentTarget).data(i))||(n=new this.constructor(e.currentTarget,this._getDelegateConfig()),t(e.currentTarget).data(i,n)),e&&(n._activeTrigger["focusin"===e.type?g.FOCUS:g.HOVER]=!0),t(n.getTipElement()).hasClass(p.SHOW)||n._hoverState===d.SHOW?n._hoverState=d.SHOW:(clearTimeout(n._timeout),n._hoverState=d.SHOW,n.config.delay&&n.config.delay.show?n._timeout=setTimeout(function(){n._hoverState===d.SHOW&&n.show()},n.config.delay.show):n.show())},a.prototype._leave=function(e,n){var i=this.constructor.DATA_KEY;(n=n||t(e.currentTarget).data(i))||(n=new this.constructor(e.currentTarget,this._getDelegateConfig()),t(e.currentTarget).data(i,n)),e&&(n._activeTrigger["focusout"===e.type?g.FOCUS:g.HOVER]=!1),n._isWithActiveTrigger()||(clearTimeout(n._timeout),n._hoverState=d.OUT,n.config.delay&&n.config.delay.hide?n._timeout=setTimeout(function(){n._hoverState===d.OUT&&n.hide()},n.config.delay.hide):n.hide())},a.prototype._isWithActiveTrigger=function(){for(var t in this._activeTrigger)if(this._activeTrigger[t])return!0;return!1},a.prototype._getConfig=function(n){return(n=t.extend({},this.constructor.Default,t(this.element).data(),n)).delay&&"number"==typeof n.delay&&(n.delay={show:n.delay,hide:n.delay}),n.title&&"number"==typeof n.title&&(n.title=n.title.toString()),n.content&&"number"==typeof n.content&&(n.content=n.content.toString()),r.typeCheckConfig(e,n,this.constructor.DefaultType),n},a.prototype._getDelegateConfig=function(){var t={};if(this.config)for(var e in this.config)this.constructor.Default[e]!==this.config[e]&&(t[e]=this.config[e]);return t},a.prototype._cleanTipClass=function(){var e=t(this.getTipElement()),n=e.attr("class").match(l);null!==n&&n.length>0&&e.removeClass(n.join(""))},a.prototype._handlePopperPlacementChange=function(t){this._cleanTipClass(),this.addAttachmentClass(this._getAttachment(t.placement))},a.prototype._fixTransition=function(){var e=this.getTipElement(),n=this.config.animation;null===e.getAttribute("x-placement")&&(t(e).removeClass(p.FADE),this.config.animation=!1,this.hide(),this.show(),this.config.animation=n)},a._jQueryInterface=function(e){return this.each(function(){var n=t(this).data("bs.tooltip"),o="object"===(void 0===e?"undefined":i(e))&&e;if((n||!/dispose|hide/.test(e))&&(n||(n=new a(this,o),t(this).data("bs.tooltip",n)),"string"==typeof e)){if(void 0===n[e])throw new Error('No method named "'+e+'"');n[e]()}})},o(a,null,[{key:"VERSION",get:function(){return"4.0.0-beta"}},{key:"Default",get:function(){return u}},{key:"NAME",get:function(){return e}},{key:"DATA_KEY",get:function(){return"bs.tooltip"}},{key:"Event",get:function(){return f}},{key:"EVENT_KEY",get:function(){return s}},{key:"DefaultType",get:function(){return h}}]),a}();return t.fn[e]=m._jQueryInterface,t.fn[e].Constructor=m,t.fn[e].noConflict=function(){return t.fn[e]=a,m._jQueryInterface},m}(jQuery));!function(r){var a="popover",l=".bs.popover",h=r.fn[a],c=new RegExp("(^|\\s)bs-popover\\S+","g"),u=r.extend({},s.Default,{placement:"right",trigger:"click",content:"",template:'<div class="popover" role="tooltip"><div class="arrow"></div><h3 class="popover-header"></h3><div class="popover-body"></div></div>'}),d=r.extend({},s.DefaultType,{content:"(string|element|function)"}),f={FADE:"fade",SHOW:"show"},p={TITLE:".popover-header",CONTENT:".popover-body"},_={HIDE:"hide"+l,HIDDEN:"hidden"+l,SHOW:"show"+l,SHOWN:"shown"+l,INSERTED:"inserted"+l,CLICK:"click"+l,FOCUSIN:"focusin"+l,FOCUSOUT:"focusout"+l,MOUSEENTER:"mouseenter"+l,MOUSELEAVE:"mouseleave"+l},g=function(s){function h(){return n(this,h),t(this,s.apply(this,arguments))}return e(h,s),h.prototype.isWithContent=function(){return this.getTitle()||this._getContent()},h.prototype.addAttachmentClass=function(t){r(this.getTipElement()).addClass("bs-popover-"+t)},h.prototype.getTipElement=function(){return this.tip=this.tip||r(this.config.template)[0]},h.prototype.setContent=function(){var t=r(this.getTipElement());this.setElementContent(t.find(p.TITLE),this.getTitle()),this.setElementContent(t.find(p.CONTENT),this._getContent()),t.removeClass(f.FADE+" "+f.SHOW)},h.prototype._getContent=function(){return this.element.getAttribute("data-content")||("function"==typeof this.config.content?this.config.content.call(this.element):this.config.content)},h.prototype._cleanTipClass=function(){var t=r(this.getTipElement()),e=t.attr("class").match(c);null!==e&&e.length>0&&t.removeClass(e.join(""))},h._jQueryInterface=function(t){return this.each(function(){var e=r(this).data("bs.popover"),n="object"===(void 0===t?"undefined":i(t))?t:null;if((e||!/destroy|hide/.test(t))&&(e||(e=new h(this,n),r(this).data("bs.popover",e)),"string"==typeof t)){if(void 0===e[t])throw new Error('No method named "'+t+'"');e[t]()}})},o(h,null,[{key:"VERSION",get:function(){return"4.0.0-beta"}},{key:"Default",get:function(){return u}},{key:"NAME",get:function(){return a}},{key:"DATA_KEY",get:function(){return"bs.popover"}},{key:"Event",get:function(){return _}},{key:"EVENT_KEY",get:function(){return l}},{key:"DefaultType",get:function(){return d}}]),h}(s);r.fn[a]=g._jQueryInterface,r.fn[a].Constructor=g,r.fn[a].noConflict=function(){return r.fn[a]=h,g._jQueryInterface}}(jQuery)}(); \ No newline at end of file
diff --git a/library/cacert.pem b/library/cacert.pem
index 29dbfa286..55958581d 100644
--- a/library/cacert.pem
+++ b/library/cacert.pem
@@ -1,20 +1,20 @@
##
## Bundle of CA Root Certificates
##
-## Certificate data from Mozilla as of: Wed Apr 20 03:12:05 2016
+## Certificate data from Mozilla as of: Wed Jun 7 03:12:05 2017 GMT
##
## This is a bundle of X.509 certificates of public Certificate Authorities
## (CA). These were automatically extracted from Mozilla's root certificates
## file (certdata.txt). This file can be found in the mozilla source tree:
-## http://hg.mozilla.org/releases/mozilla-release/raw-file/default/security/nss/lib/ckfw/builtins/certdata.txt
+## https://hg.mozilla.org/releases/mozilla-release/raw-file/default/security/nss/lib/ckfw/builtins/certdata.txt
##
## It contains the certificates in PEM format and therefore
## can be directly used with curl / libcurl / php_curl, or with
## an Apache+mod_ssl webserver for SSL client authentication.
## Just configure this file as the SSLCACertificateFile.
##
-## Conversion done with mk-ca-bundle.pl version 1.25.
-## SHA1: 5df367cda83086392e1acdf22bfef00c48d5eba6
+## Conversion done with mk-ca-bundle.pl version 1.27.
+## SHA256: 93753268e1c596aee21893fb1c6975338389132f15c942ed65fc394a904371d7
##
@@ -252,27 +252,6 @@ W3iDVuycNsMm4hH2Z0kdkquM++v/eu6FSqdQgPCnXEqULl8FmTxSQeDNtGPPAUO6nIPcj2A781q0
tHuu2guQOHXvgR1m0vdXcDazv/wor3ElhVsT/h5/WrQ8
-----END CERTIFICATE-----
-RSA Security 2048 v3
-====================
------BEGIN CERTIFICATE-----
-MIIDYTCCAkmgAwIBAgIQCgEBAQAAAnwAAAAKAAAAAjANBgkqhkiG9w0BAQUFADA6MRkwFwYDVQQK
-ExBSU0EgU2VjdXJpdHkgSW5jMR0wGwYDVQQLExRSU0EgU2VjdXJpdHkgMjA0OCBWMzAeFw0wMTAy
-MjIyMDM5MjNaFw0yNjAyMjIyMDM5MjNaMDoxGTAXBgNVBAoTEFJTQSBTZWN1cml0eSBJbmMxHTAb
-BgNVBAsTFFJTQSBTZWN1cml0eSAyMDQ4IFYzMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKC
-AQEAt49VcdKA3XtpeafwGFAyPGJn9gqVB93mG/Oe2dJBVGutn3y+Gc37RqtBaB4Y6lXIL5F4iSj7
-Jylg/9+PjDvJSZu1pJTOAeo+tWN7fyb9Gd3AIb2E0S1PRsNO3Ng3OTsor8udGuorryGlwSMiuLgb
-WhOHV4PR8CDn6E8jQrAApX2J6elhc5SYcSa8LWrg903w8bYqODGBDSnhAMFRD0xS+ARaqn1y07iH
-KrtjEAMqs6FPDVpeRrc9DvV07Jmf+T0kgYim3WBU6JU2PcYJk5qjEoAAVZkZR73QpXzDuvsf9/UP
-+Ky5tfQ3mBMY3oVbtwyCO4dvlTlYMNpuAWgXIszACwIDAQABo2MwYTAPBgNVHRMBAf8EBTADAQH/
-MA4GA1UdDwEB/wQEAwIBBjAfBgNVHSMEGDAWgBQHw1EwpKrpRa41JPr/JCwz0LGdjDAdBgNVHQ4E
-FgQUB8NRMKSq6UWuNST6/yQsM9CxnYwwDQYJKoZIhvcNAQEFBQADggEBAF8+hnZuuDU8TjYcHnmY
-v/3VEhF5Ug7uMYm83X/50cYVIeiKAVQNOvtUudZj1LGqlk2iQk3UUx+LEN5/Zb5gEydxiKRz44Rj
-0aRV4VCT5hsOedBnvEbIvz8XDZXmxpBp3ue0L96VfdASPz0+f00/FGj1EVDVwfSQpQgdMWD/YIwj
-VAqv/qFuxdF6Kmh4zx6CCiC0H63lhbJqaHVOrSU3lIW+vaHU6rcMSzyd6BIA8F+sDeGscGNz9395
-nzIlQnQFgCi/vcEkllgVsRch6YlL2weIZ/QVrXA+L02FO8K32/6YaCOJ4XQP3vTFhGMpG8zLB8kA
-pKnXwiJPZ9d37CAFYd4=
------END CERTIFICATE-----
-
GeoTrust Global CA
==================
-----BEGIN CERTIFICATE-----
@@ -1241,33 +1220,6 @@ wKeI8lN3s2Berq4o2jUsbzRF0ybh3uxbTydrFny9RAQYgrOJeRcQcT16ohZO9QHNpGxlaKFJdlxD
ydi8NmdspZS11My5vWo1ViHe2MPr+8ukYEywVaCge1ey
-----END CERTIFICATE-----
-WellsSecure Public Root Certificate Authority
-=============================================
------BEGIN CERTIFICATE-----
-MIIEvTCCA6WgAwIBAgIBATANBgkqhkiG9w0BAQUFADCBhTELMAkGA1UEBhMCVVMxIDAeBgNVBAoM
-F1dlbGxzIEZhcmdvIFdlbGxzU2VjdXJlMRwwGgYDVQQLDBNXZWxscyBGYXJnbyBCYW5rIE5BMTYw
-NAYDVQQDDC1XZWxsc1NlY3VyZSBQdWJsaWMgUm9vdCBDZXJ0aWZpY2F0ZSBBdXRob3JpdHkwHhcN
-MDcxMjEzMTcwNzU0WhcNMjIxMjE0MDAwNzU0WjCBhTELMAkGA1UEBhMCVVMxIDAeBgNVBAoMF1dl
-bGxzIEZhcmdvIFdlbGxzU2VjdXJlMRwwGgYDVQQLDBNXZWxscyBGYXJnbyBCYW5rIE5BMTYwNAYD
-VQQDDC1XZWxsc1NlY3VyZSBQdWJsaWMgUm9vdCBDZXJ0aWZpY2F0ZSBBdXRob3JpdHkwggEiMA0G
-CSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDub7S9eeKPCCGeOARBJe+rWxxTkqxtnt3CxC5FlAM1
-iGd0V+PfjLindo8796jE2yljDpFoNoqXjopxaAkH5OjUDk/41itMpBb570OYj7OeUt9tkTmPOL13
-i0Nj67eT/DBMHAGTthP796EfvyXhdDcsHqRePGj4S78NuR4uNuip5Kf4D8uCdXw1LSLWwr8L87T8
-bJVhHlfXBIEyg1J55oNjz7fLY4sR4r1e6/aN7ZVyKLSsEmLpSjPmgzKuBXWVvYSV2ypcm44uDLiB
-K0HmOFafSZtsdvqKXfcBeYF8wYNABf5x/Qw/zE5gCQ5lRxAvAcAFP4/4s0HvWkJ+We/SlwxlAgMB
-AAGjggE0MIIBMDAPBgNVHRMBAf8EBTADAQH/MDkGA1UdHwQyMDAwLqAsoCqGKGh0dHA6Ly9jcmwu
-cGtpLndlbGxzZmFyZ28uY29tL3dzcHJjYS5jcmwwDgYDVR0PAQH/BAQDAgHGMB0GA1UdDgQWBBQm
-lRkQ2eihl5H/3BnZtQQ+0nMKajCBsgYDVR0jBIGqMIGngBQmlRkQ2eihl5H/3BnZtQQ+0nMKaqGB
-i6SBiDCBhTELMAkGA1UEBhMCVVMxIDAeBgNVBAoMF1dlbGxzIEZhcmdvIFdlbGxzU2VjdXJlMRww
-GgYDVQQLDBNXZWxscyBGYXJnbyBCYW5rIE5BMTYwNAYDVQQDDC1XZWxsc1NlY3VyZSBQdWJsaWMg
-Um9vdCBDZXJ0aWZpY2F0ZSBBdXRob3JpdHmCAQEwDQYJKoZIhvcNAQEFBQADggEBALkVsUSRzCPI
-K0134/iaeycNzXK7mQDKfGYZUMbVmO2rvwNa5U3lHshPcZeG1eMd/ZDJPHV3V3p9+N701NX3leZ0
-bh08rnyd2wIDBSxxSyU+B+NemvVmFymIGjifz6pBA4SXa5M4esowRBskRDPQ5NHcKDj0E0M1NSlj
-qHyita04pO2t/caaH/+Xc/77szWnk4bGdpEA5qxRFsQnMlzbc9qlk1eOPm01JghZ1edE13YgY+es
-E2fDbbFwRnzVlhE9iW9dqKHrjQrawx0zbKPqZxmamX9LPYNRKh3KL4YMon4QLSvUFpULB6ouFJJJ
-tylv2G0xffX8oRAHh84vWdw+WNs=
------END CERTIFICATE-----
-
COMODO ECC Certification Authority
==================================
-----BEGIN CERTIFICATE-----
@@ -1285,30 +1237,6 @@ FAkK+qDmfQjGGoe9GKhzvSbKYAydzpmfz1wPMOG+FDHqAjAU9JM8SaczepBGR7NjfRObTrdvGDeA
U/7dIOA1mjbRxwG55tzd8/8dLDoWV9mSOdY=
-----END CERTIFICATE-----
-IGC/A
-=====
------BEGIN CERTIFICATE-----
-MIIEAjCCAuqgAwIBAgIFORFFEJQwDQYJKoZIhvcNAQEFBQAwgYUxCzAJBgNVBAYTAkZSMQ8wDQYD
-VQQIEwZGcmFuY2UxDjAMBgNVBAcTBVBhcmlzMRAwDgYDVQQKEwdQTS9TR0ROMQ4wDAYDVQQLEwVE
-Q1NTSTEOMAwGA1UEAxMFSUdDL0ExIzAhBgkqhkiG9w0BCQEWFGlnY2FAc2dkbi5wbS5nb3V2LmZy
-MB4XDTAyMTIxMzE0MjkyM1oXDTIwMTAxNzE0MjkyMlowgYUxCzAJBgNVBAYTAkZSMQ8wDQYDVQQI
-EwZGcmFuY2UxDjAMBgNVBAcTBVBhcmlzMRAwDgYDVQQKEwdQTS9TR0ROMQ4wDAYDVQQLEwVEQ1NT
-STEOMAwGA1UEAxMFSUdDL0ExIzAhBgkqhkiG9w0BCQEWFGlnY2FAc2dkbi5wbS5nb3V2LmZyMIIB
-IjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAsh/R0GLFMzvABIaIs9z4iPf930Pfeo2aSVz2
-TqrMHLmh6yeJ8kbpO0px1R2OLc/mratjUMdUC24SyZA2xtgv2pGqaMVy/hcKshd+ebUyiHDKcMCW
-So7kVc0dJ5S/znIq7Fz5cyD+vfcuiWe4u0dzEvfRNWk68gq5rv9GQkaiv6GFGvm/5P9JhfejcIYy
-HF2fYPepraX/z9E0+X1bF8bc1g4oa8Ld8fUzaJ1O/Id8NhLWo4DoQw1VYZTqZDdH6nfK0LJYBcNd
-frGoRpAxVs5wKpayMLh35nnAvSk7/ZR3TL0gzUEl4C7HG7vupARB0l2tEmqKm0f7yd1GQOGdPDPQ
-tQIDAQABo3cwdTAPBgNVHRMBAf8EBTADAQH/MAsGA1UdDwQEAwIBRjAVBgNVHSAEDjAMMAoGCCqB
-egF5AQEBMB0GA1UdDgQWBBSjBS8YYFDCiQrdKyFP/45OqDAxNjAfBgNVHSMEGDAWgBSjBS8YYFDC
-iQrdKyFP/45OqDAxNjANBgkqhkiG9w0BAQUFAAOCAQEABdwm2Pp3FURo/C9mOnTgXeQp/wYHE4RK
-q89toB9RlPhJy3Q2FLwV3duJL92PoF189RLrn544pEfMs5bZvpwlqwN+Mw+VgQ39FuCIvjfwbF3Q
-MZsyK10XZZOYYLxuj7GoPB7ZHPOpJkL5ZB3C55L29B5aqhlSXa/oovdgoPaN8In1buAKBQGVyYsg
-Crpa/JosPL3Dt8ldeCUFP1YUmwza+zpI/pdpXsoQhvdOlgQITeywvl3cO45Pwf2aNjSaTFR+FwNI
-lQgRHAdvhQh+XU3Endv7rs6y0bO4g2wdsrN58dhwmX7wEwLOXt1R0982gaEbeC9xs/FZTEYYKKuF
-0mBWWg==
------END CERTIFICATE-----
-
Security Communication EV RootCA1
=================================
-----BEGIN CERTIFICATE-----
@@ -1353,46 +1281,6 @@ hNVQA7bihKOmNqoROgHhGEvWRGizPflTdISzRpFGlgC3gCy24eMQ4tui5yiPAZZiFj4A4xylNoEY
okxSdsARo27mHbrjWr42U8U+dY+GaSlYU7Wcu2+fXMUY7N0v4ZjJ/L7fCg0=
-----END CERTIFICATE-----
-Microsec e-Szigno Root CA
-=========================
------BEGIN CERTIFICATE-----
-MIIHqDCCBpCgAwIBAgIRAMy4579OKRr9otxmpRwsDxEwDQYJKoZIhvcNAQEFBQAwcjELMAkGA1UE
-BhMCSFUxETAPBgNVBAcTCEJ1ZGFwZXN0MRYwFAYDVQQKEw1NaWNyb3NlYyBMdGQuMRQwEgYDVQQL
-EwtlLVN6aWdubyBDQTEiMCAGA1UEAxMZTWljcm9zZWMgZS1Temlnbm8gUm9vdCBDQTAeFw0wNTA0
-MDYxMjI4NDRaFw0xNzA0MDYxMjI4NDRaMHIxCzAJBgNVBAYTAkhVMREwDwYDVQQHEwhCdWRhcGVz
-dDEWMBQGA1UEChMNTWljcm9zZWMgTHRkLjEUMBIGA1UECxMLZS1Temlnbm8gQ0ExIjAgBgNVBAMT
-GU1pY3Jvc2VjIGUtU3ppZ25vIFJvb3QgQ0EwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIB
-AQDtyADVgXvNOABHzNuEwSFpLHSQDCHZU4ftPkNEU6+r+ICbPHiN1I2uuO/TEdyB5s87lozWbxXG
-d36hL+BfkrYn13aaHUM86tnsL+4582pnS4uCzyL4ZVX+LMsvfUh6PXX5qqAnu3jCBspRwn5mS6/N
-oqdNAoI/gqyFxuEPkEeZlApxcpMqyabAvjxWTHOSJ/FrtfX9/DAFYJLG65Z+AZHCabEeHXtTRbjc
-QR/Ji3HWVBTji1R4P770Yjtb9aPs1ZJ04nQw7wHb4dSrmZsqa/i9phyGI0Jf7Enemotb9HI6QMVJ
-PqW+jqpx62z69Rrkav17fVVA71hu5tnVvCSrwe+3AgMBAAGjggQ3MIIEMzBnBggrBgEFBQcBAQRb
-MFkwKAYIKwYBBQUHMAGGHGh0dHBzOi8vcmNhLmUtc3ppZ25vLmh1L29jc3AwLQYIKwYBBQUHMAKG
-IWh0dHA6Ly93d3cuZS1zemlnbm8uaHUvUm9vdENBLmNydDAPBgNVHRMBAf8EBTADAQH/MIIBcwYD
-VR0gBIIBajCCAWYwggFiBgwrBgEEAYGoGAIBAQEwggFQMCgGCCsGAQUFBwIBFhxodHRwOi8vd3d3
-LmUtc3ppZ25vLmh1L1NaU1ovMIIBIgYIKwYBBQUHAgIwggEUHoIBEABBACAAdABhAG4A+gBzAO0A
-dAB2AOEAbgB5ACAA6QByAHQAZQBsAG0AZQB6AOkAcwDpAGgAZQB6ACAA6QBzACAAZQBsAGYAbwBn
-AGEAZADhAHMA4QBoAG8AegAgAGEAIABTAHoAbwBsAGcA4QBsAHQAYQB0APMAIABTAHoAbwBsAGcA
-4QBsAHQAYQB0AOEAcwBpACAAUwB6AGEAYgDhAGwAeQB6AGEAdABhACAAcwB6AGUAcgBpAG4AdAAg
-AGsAZQBsAGwAIABlAGwAagDhAHIAbgBpADoAIABoAHQAdABwADoALwAvAHcAdwB3AC4AZQAtAHMA
-egBpAGcAbgBvAC4AaAB1AC8AUwBaAFMAWgAvMIHIBgNVHR8EgcAwgb0wgbqggbeggbSGIWh0dHA6
-Ly93d3cuZS1zemlnbm8uaHUvUm9vdENBLmNybIaBjmxkYXA6Ly9sZGFwLmUtc3ppZ25vLmh1L0NO
-PU1pY3Jvc2VjJTIwZS1Temlnbm8lMjBSb290JTIwQ0EsT1U9ZS1Temlnbm8lMjBDQSxPPU1pY3Jv
-c2VjJTIwTHRkLixMPUJ1ZGFwZXN0LEM9SFU/Y2VydGlmaWNhdGVSZXZvY2F0aW9uTGlzdDtiaW5h
-cnkwDgYDVR0PAQH/BAQDAgEGMIGWBgNVHREEgY4wgYuBEGluZm9AZS1zemlnbm8uaHWkdzB1MSMw
-IQYDVQQDDBpNaWNyb3NlYyBlLVN6aWduw7MgUm9vdCBDQTEWMBQGA1UECwwNZS1TemlnbsOzIEhT
-WjEWMBQGA1UEChMNTWljcm9zZWMgS2Z0LjERMA8GA1UEBxMIQnVkYXBlc3QxCzAJBgNVBAYTAkhV
-MIGsBgNVHSMEgaQwgaGAFMegSXUWYYTbMUuE0vE3QJDvTtz3oXakdDByMQswCQYDVQQGEwJIVTER
-MA8GA1UEBxMIQnVkYXBlc3QxFjAUBgNVBAoTDU1pY3Jvc2VjIEx0ZC4xFDASBgNVBAsTC2UtU3pp
-Z25vIENBMSIwIAYDVQQDExlNaWNyb3NlYyBlLVN6aWdubyBSb290IENBghEAzLjnv04pGv2i3Gal
-HCwPETAdBgNVHQ4EFgQUx6BJdRZhhNsxS4TS8TdAkO9O3PcwDQYJKoZIhvcNAQEFBQADggEBANMT
-nGZjWS7KXHAM/IO8VbH0jgdsZifOwTsgqRy7RlRw7lrMoHfqaEQn6/Ip3Xep1fvj1KcExJW4C+FE
-aGAHQzAxQmHl7tnlJNUb3+FKG6qfx1/4ehHqE5MAyopYse7tDk2016g2JnzgOsHVV4Lxdbb9iV/a
-86g4nzUGCM4ilb7N1fy+W955a9x6qWVmvrElWl/tftOsRm1M9DKHtCAE4Gx4sHfRhUZLphK3dehK
-yVZs15KrnfVJONJPU+NVkBHbmJbGSfI+9J8b4PeI3CVimUTYc78/MPMMNz7UwiiAc7EBt51alhQB
-S6kRnSlqLtBdgcDPsiBDxwPgN05dCtxZICU=
------END CERTIFICATE-----
-
Certigna
========
-----BEGIN CERTIFICATE-----
@@ -1518,58 +1406,6 @@ LBOhgLJeDEoTniDYYkCrkOpkSi+sDQESeUWoL4cZaMjihccwsnX5OD+ywJO0a+IDRM5noN+J1q2M
dqMTw5RhK2vZbMEHCiIHhWyFJEapvj+LeISCfiQMnf2BN+MlqO02TpUsyZyQ2uypQjyttgI=
-----END CERTIFICATE-----
-Buypass Class 2 CA 1
-====================
------BEGIN CERTIFICATE-----
-MIIDUzCCAjugAwIBAgIBATANBgkqhkiG9w0BAQUFADBLMQswCQYDVQQGEwJOTzEdMBsGA1UECgwU
-QnV5cGFzcyBBUy05ODMxNjMzMjcxHTAbBgNVBAMMFEJ1eXBhc3MgQ2xhc3MgMiBDQSAxMB4XDTA2
-MTAxMzEwMjUwOVoXDTE2MTAxMzEwMjUwOVowSzELMAkGA1UEBhMCTk8xHTAbBgNVBAoMFEJ1eXBh
-c3MgQVMtOTgzMTYzMzI3MR0wGwYDVQQDDBRCdXlwYXNzIENsYXNzIDIgQ0EgMTCCASIwDQYJKoZI
-hvcNAQEBBQADggEPADCCAQoCggEBAIs8B0XY9t/mx8q6jUPFR42wWsE425KEHK8T1A9vNkYgxC7M
-cXA0ojTTNy7Y3Tp3L8DrKehc0rWpkTSHIln+zNvnma+WwajHQN2lFYxuyHyXA8vmIPLXl18xoS83
-0r7uvqmtqEyeIWZDO6i88wmjONVZJMHCR3axiFyCO7srpgTXjAePzdVBHfCuuCkslFJgNJQ72uA4
-0Z0zPhX0kzLFANq1KWYOOngPIVJfAuWSeyXTkh4vFZ2B5J2O6O+JzhRMVB0cgRJNcKi+EAUXfh/R
-uFdV7c27UsKwHnjCTTZoy1YmwVLBvXb3WNVyfh9EdrsAiR0WnVE1703CVu9r4Iw7DekCAwEAAaNC
-MEAwDwYDVR0TAQH/BAUwAwEB/zAdBgNVHQ4EFgQUP42aWYv8e3uco684sDntkHGA1sgwDgYDVR0P
-AQH/BAQDAgEGMA0GCSqGSIb3DQEBBQUAA4IBAQAVGn4TirnoB6NLJzKyQJHyIdFkhb5jatLPgcIV
-1Xp+DCmsNx4cfHZSldq1fyOhKXdlyTKdqC5Wq2B2zha0jX94wNWZUYN/Xtm+DKhQ7SLHrQVMdvvt
-7h5HZPb3J31cKA9FxVxiXqaakZG3Uxcu3K1gnZZkOb1naLKuBctN518fV4bVIJwo+28TOPX2EZL2
-fZleHwzoq0QkKXJAPTZSr4xYkHPB7GEseaHsh7U/2k3ZIQAw3pDaDtMaSKk+hQsUi4y8QZ5q9w5w
-wDX3OaJdZtB7WZ+oRxKaJyOkLY4ng5IgodcVf/EuGO70SH8vf/GhGLWhC5SgYiAynB321O+/TIho
------END CERTIFICATE-----
-
-EBG Elektronik Sertifika Hizmet Sa\xC4\x9Flay\xc4\xb1\x63\xc4\xb1s\xc4\xb1
-==========================================================================
------BEGIN CERTIFICATE-----
-MIIF5zCCA8+gAwIBAgIITK9zQhyOdAIwDQYJKoZIhvcNAQEFBQAwgYAxODA2BgNVBAMML0VCRyBF
-bGVrdHJvbmlrIFNlcnRpZmlrYSBIaXptZXQgU2HEn2xhecSxY8Sxc8SxMTcwNQYDVQQKDC5FQkcg
-QmlsacWfaW0gVGVrbm9sb2ppbGVyaSB2ZSBIaXptZXRsZXJpIEEuxZ4uMQswCQYDVQQGEwJUUjAe
-Fw0wNjA4MTcwMDIxMDlaFw0xNjA4MTQwMDMxMDlaMIGAMTgwNgYDVQQDDC9FQkcgRWxla3Ryb25p
-ayBTZXJ0aWZpa2EgSGl6bWV0IFNhxJ9sYXnEsWPEsXPEsTE3MDUGA1UECgwuRUJHIEJpbGnFn2lt
-IFRla25vbG9qaWxlcmkgdmUgSGl6bWV0bGVyaSBBLsWeLjELMAkGA1UEBhMCVFIwggIiMA0GCSqG
-SIb3DQEBAQUAA4ICDwAwggIKAoICAQDuoIRh0DpqZhAy2DE4f6en5f2h4fuXd7hxlugTlkaDT7by
-X3JWbhNgpQGR4lvFzVcfd2NR/y8927k/qqk153nQ9dAktiHq6yOU/im/+4mRDGSaBUorzAzu8T2b
-gmmkTPiab+ci2hC6X5L8GCcKqKpE+i4stPtGmggDg3KriORqcsnlZR9uKg+ds+g75AxuetpX/dfr
-eYteIAbTdgtsApWjluTLdlHRKJ2hGvxEok3MenaoDT2/F08iiFD9rrbskFBKW5+VQarKD7JK/oCZ
-TqNGFav4c0JqwmZ2sQomFd2TkuzbqV9UIlKRcF0T6kjsbgNs2d1s/OsNA/+mgxKb8amTD8UmTDGy
-Y5lhcucqZJnSuOl14nypqZoaqsNW2xCaPINStnuWt6yHd6i58mcLlEOzrz5z+kI2sSXFCjEmN1Zn
-uqMLfdb3ic1nobc6HmZP9qBVFCVMLDMNpkGMvQQxahByCp0OLna9XvNRiYuoP1Vzv9s6xiQFlpJI
-qkuNKgPlV5EQ9GooFW5Hd4RcUXSfGenmHmMWOeMRFeNYGkS9y8RsZteEBt8w9DeiQyJ50hBs37vm
-ExH8nYQKE3vwO9D8owrXieqWfo1IhR5kX9tUoqzVegJ5a9KK8GfaZXINFHDk6Y54jzJ0fFfy1tb0
-Nokb+Clsi7n2l9GkLqq+CxnCRelwXQIDAJ3Zo2MwYTAPBgNVHRMBAf8EBTADAQH/MA4GA1UdDwEB
-/wQEAwIBBjAdBgNVHQ4EFgQU587GT/wWZ5b6SqMHwQSny2re2kcwHwYDVR0jBBgwFoAU587GT/wW
-Z5b6SqMHwQSny2re2kcwDQYJKoZIhvcNAQEFBQADggIBAJuYml2+8ygjdsZs93/mQJ7ANtyVDR2t
-FcU22NU57/IeIl6zgrRdu0waypIN30ckHrMk2pGI6YNw3ZPX6bqz3xZaPt7gyPvT/Wwp+BVGoGgm
-zJNSroIBk5DKd8pNSe/iWtkqvTDOTLKBtjDOWU/aWR1qeqRFsIImgYZ29fUQALjuswnoT4cCB64k
-XPBfrAowzIpAoHMEwfuJJPaaHFy3PApnNgUIMbOv2AFoKuB4j3TeuFGkjGwgPaL7s9QJ/XvCgKqT
-bCmYIai7FvOpEl90tYeY8pUm3zTvilORiF0alKM/fCL414i6poyWqD1SNGKfAB5UVUJnxk1Gj7sU
-RT0KlhaOEKGXmdXTMIXM3rRyt7yKPBgpaP3ccQfuJDlq+u2lrDgv+R4QDgZxGhBM/nV+/x5XOULK
-1+EVoVZVWRvRo68R2E7DpSvvkL/A7IITW43WciyTTo9qKd+FPNMN4KIYEsxVL0e3p5sC/kH2iExt
-2qkBR4NkJ2IQgtYSe14DHzSpyZH+r11thie3I6p1GMog57AP14kOpmciY/SDQSsGS7tY1dHXt7kQ
-Y9iJSrSq3RZj9W6+YKH47ejWkE8axsWgKdOnIaj1Wjz3x0miIZpKlVIglnKaZsv30oZDfCK+lvm9
-AahH3eU7QPl1K5srRmSGjR70j/sHd9DqSaIcjVIUpgqT
------END CERTIFICATE-----
-
certSIGN ROOT CA
================
-----BEGIN CERTIFICATE-----
@@ -1611,28 +1447,6 @@ G8kS1sHNzYDzAgE8yGnLRUhj2JTQ7IUOO04RZfSCjKY9ri4ilAnIXOo8gV0WKgOXFlUJ24pBgp5m
mxE=
-----END CERTIFICATE-----
-ApplicationCA - Japanese Government
-===================================
------BEGIN CERTIFICATE-----
-MIIDoDCCAoigAwIBAgIBMTANBgkqhkiG9w0BAQUFADBDMQswCQYDVQQGEwJKUDEcMBoGA1UEChMT
-SmFwYW5lc2UgR292ZXJubWVudDEWMBQGA1UECxMNQXBwbGljYXRpb25DQTAeFw0wNzEyMTIxNTAw
-MDBaFw0xNzEyMTIxNTAwMDBaMEMxCzAJBgNVBAYTAkpQMRwwGgYDVQQKExNKYXBhbmVzZSBHb3Zl
-cm5tZW50MRYwFAYDVQQLEw1BcHBsaWNhdGlvbkNBMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIB
-CgKCAQEAp23gdE6Hj6UG3mii24aZS2QNcfAKBZuOquHMLtJqO8F6tJdhjYq+xpqcBrSGUeQ3DnR4
-fl+Kf5Sk10cI/VBaVuRorChzoHvpfxiSQE8tnfWuREhzNgaeZCw7NCPbXCbkcXmP1G55IrmTwcrN
-wVbtiGrXoDkhBFcsovW8R0FPXjQilbUfKW1eSvNNcr5BViCH/OlQR9cwFO5cjFW6WY2H/CPek9AE
-jP3vbb3QesmlOmpyM8ZKDQUXKi17safY1vC+9D/qDihtQWEjdnjDuGWk81quzMKq2edY3rZ+nYVu
-nyoKb58DKTCXKB28t89UKU5RMfkntigm/qJj5kEW8DOYRwIDAQABo4GeMIGbMB0GA1UdDgQWBBRU
-WssmP3HMlEYNllPqa0jQk/5CdTAOBgNVHQ8BAf8EBAMCAQYwWQYDVR0RBFIwUKROMEwxCzAJBgNV
-BAYTAkpQMRgwFgYDVQQKDA/ml6XmnKzlm73mlL/lupwxIzAhBgNVBAsMGuOCouODl+ODquOCseOD
-vOOCt+ODp+ODs0NBMA8GA1UdEwEB/wQFMAMBAf8wDQYJKoZIhvcNAQEFBQADggEBADlqRHZ3ODrs
-o2dGD/mLBqj7apAxzn7s2tGJfHrrLgy9mTLnsCTWw//1sogJhyzjVOGjprIIC8CFqMjSnHH2HZ9g
-/DgzE+Ge3Atf2hZQKXsvcJEPmbo0NI2VdMV+eKlmXb3KIXdCEKxmJj3ekav9FfBv7WxfEPjzFvYD
-io+nEhEMy/0/ecGc/WLuo89UDNErXxc+4z6/wCs+CZv+iKZ+tJIX/COUgb1up8WMwusRRdv4QcmW
-dupwX3kSa+SjB1oF7ydJzyGfikwJcGapJsErEU4z0g781mzSDjJkaP+tBXhfAx2o45CsJOAPQKdL
-rosot4LKGAfmt1t06SAZf7IbiVQ=
------END CERTIFICATE-----
-
GeoTrust Primary Certification Authority - G3
=============================================
-----BEGIN CERTIFICATE-----
@@ -1764,7 +1578,7 @@ AJw9SDkjOVgaFRJZap7v1VmyHVIsmXHNxynfGyphe3HR3vPA5Q06Sqotp9iGKt0uEA==
-----END CERTIFICATE-----
NetLock Arany (Class Gold) Főtanúsítvány
-============================================
+========================================
-----BEGIN CERTIFICATE-----
MIIEFTCCAv2gAwIBAgIGSUEs5AAQMA0GCSqGSIb3DQEBCwUAMIGnMQswCQYDVQQGEwJIVTERMA8G
A1UEBwwIQnVkYXBlc3QxFTATBgNVBAoMDE5ldExvY2sgS2Z0LjE3MDUGA1UECwwuVGFuw7pzw610
@@ -1819,34 +1633,6 @@ IPVVYpbtbZNQvOSqeK3Zywplh6ZmwcSBo3c6WB4L7oOLnR7SUqTMHW+wmG2UMbX4cQrcufx9MmDm
66+KAQ==
-----END CERTIFICATE-----
-Juur-SK
-=======
------BEGIN CERTIFICATE-----
-MIIE5jCCA86gAwIBAgIEO45L/DANBgkqhkiG9w0BAQUFADBdMRgwFgYJKoZIhvcNAQkBFglwa2lA
-c2suZWUxCzAJBgNVBAYTAkVFMSIwIAYDVQQKExlBUyBTZXJ0aWZpdHNlZXJpbWlza2Vza3VzMRAw
-DgYDVQQDEwdKdXVyLVNLMB4XDTAxMDgzMDE0MjMwMVoXDTE2MDgyNjE0MjMwMVowXTEYMBYGCSqG
-SIb3DQEJARYJcGtpQHNrLmVlMQswCQYDVQQGEwJFRTEiMCAGA1UEChMZQVMgU2VydGlmaXRzZWVy
-aW1pc2tlc2t1czEQMA4GA1UEAxMHSnV1ci1TSzCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoC
-ggEBAIFxNj4zB9bjMI0TfncyRsvPGbJgMUaXhvSYRqTCZUXP00B841oiqBB4M8yIsdOBSvZiF3tf
-TQou0M+LI+5PAk676w7KvRhj6IAcjeEcjT3g/1tf6mTll+g/mX8MCgkzABpTpyHhOEvWgxutr2TC
-+Rx6jGZITWYfGAriPrsfB2WThbkasLnE+w0R9vXW+RvHLCu3GFH+4Hv2qEivbDtPL+/40UceJlfw
-UR0zlv/vWT3aTdEVNMfqPxZIe5EcgEMPPbgFPtGzlc3Yyg/CQ2fbt5PgIoIuvvVoKIO5wTtpeyDa
-Tpxt4brNj3pssAki14sL2xzVWiZbDcDq5WDQn/413z8CAwEAAaOCAawwggGoMA8GA1UdEwEB/wQF
-MAMBAf8wggEWBgNVHSAEggENMIIBCTCCAQUGCisGAQQBzh8BAQEwgfYwgdAGCCsGAQUFBwICMIHD
-HoHAAFMAZQBlACAAcwBlAHIAdABpAGYAaQBrAGEAYQB0ACAAbwBuACAAdgDkAGwAagBhAHMAdABh
-AHQAdQBkACAAQQBTAC0AaQBzACAAUwBlAHIAdABpAGYAaQB0AHMAZQBlAHIAaQBtAGkAcwBrAGUA
-cwBrAHUAcwAgAGEAbABhAG0ALQBTAEsAIABzAGUAcgB0AGkAZgBpAGsAYQBhAHQAaQBkAGUAIABr
-AGkAbgBuAGkAdABhAG0AaQBzAGUAawBzMCEGCCsGAQUFBwIBFhVodHRwOi8vd3d3LnNrLmVlL2Nw
-cy8wKwYDVR0fBCQwIjAgoB6gHIYaaHR0cDovL3d3dy5zay5lZS9qdXVyL2NybC8wHQYDVR0OBBYE
-FASqekej5ImvGs8KQKcYP2/v6X2+MB8GA1UdIwQYMBaAFASqekej5ImvGs8KQKcYP2/v6X2+MA4G
-A1UdDwEB/wQEAwIB5jANBgkqhkiG9w0BAQUFAAOCAQEAe8EYlFOiCfP+JmeaUOTDBS8rNXiRTHyo
-ERF5TElZrMj3hWVcRrs7EKACr81Ptcw2Kuxd/u+gkcm2k298gFTsxwhwDY77guwqYHhpNjbRxZyL
-abVAyJRld/JXIWY7zoVAtjNjGr95HvxcHdMdkxuLDF2FvZkwMhgJkVLpfKG6/2SSmuz+Ne6ML678
-IIbsSt4beDI3poHSna9aEhbKmVv8b20OxaAehsmR0FyYgl9jDIpaq9iVpszLita/ZEuOyoqysOkh
-Mp6qqIWYNIE5ITuoOlIyPfZrN4YGWhWY3PARZv40ILcD9EEQfTmEeZZyY7aWAuVrua0ZTbvGRNs2
-yyqcjg==
------END CERTIFICATE-----
-
Hongkong Post Root CA 1
=======================
-----BEGIN CERTIFICATE-----
@@ -2280,7 +2066,7 @@ Zt3hrvJBW8qYVoNzcOSGGtIxQbovvi0TWnZvTuhOgQ4/WwMioBK+ZlgRSssDxLQqKi2WF+A5VLxI
-----END CERTIFICATE-----
Certinomis - Autorité Racine
-=============================
+============================
-----BEGIN CERTIFICATE-----
MIIFnDCCA4SgAwIBAgIBATANBgkqhkiG9w0BAQUFADBjMQswCQYDVQQGEwJGUjETMBEGA1UEChMK
Q2VydGlub21pczEXMBUGA1UECxMOMDAwMiA0MzM5OTg5MDMxJjAkBgNVBAMMHUNlcnRpbm9taXMg
@@ -2310,41 +2096,6 @@ wk01+dIL8hf2rGbVJLJP0RyZwG71fet0BLj5TXcJ17TPBzAJ8bgAVtkXFhYKK4bfjwEZGuW7gmP/
vgt2Fl43N+bYdJeimUV5
-----END CERTIFICATE-----
-Root CA Generalitat Valenciana
-==============================
------BEGIN CERTIFICATE-----
-MIIGizCCBXOgAwIBAgIEO0XlaDANBgkqhkiG9w0BAQUFADBoMQswCQYDVQQGEwJFUzEfMB0GA1UE
-ChMWR2VuZXJhbGl0YXQgVmFsZW5jaWFuYTEPMA0GA1UECxMGUEtJR1ZBMScwJQYDVQQDEx5Sb290
-IENBIEdlbmVyYWxpdGF0IFZhbGVuY2lhbmEwHhcNMDEwNzA2MTYyMjQ3WhcNMjEwNzAxMTUyMjQ3
-WjBoMQswCQYDVQQGEwJFUzEfMB0GA1UEChMWR2VuZXJhbGl0YXQgVmFsZW5jaWFuYTEPMA0GA1UE
-CxMGUEtJR1ZBMScwJQYDVQQDEx5Sb290IENBIEdlbmVyYWxpdGF0IFZhbGVuY2lhbmEwggEiMA0G
-CSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDGKqtXETcvIorKA3Qdyu0togu8M1JAJke+WmmmO3I2
-F0zo37i7L3bhQEZ0ZQKQUgi0/6iMweDHiVYQOTPvaLRfX9ptI6GJXiKjSgbwJ/BXufjpTjJ3Cj9B
-ZPPrZe52/lSqfR0grvPXdMIKX/UIKFIIzFVd0g/bmoGlu6GzwZTNVOAydTGRGmKy3nXiz0+J2ZGQ
-D0EbtFpKd71ng+CT516nDOeB0/RSrFOyA8dEJvt55cs0YFAQexvba9dHq198aMpunUEDEO5rmXte
-JajCq+TA81yc477OMUxkHl6AovWDfgzWyoxVjr7gvkkHD6MkQXpYHYTqWBLI4bft75PelAgxAgMB
-AAGjggM7MIIDNzAyBggrBgEFBQcBAQQmMCQwIgYIKwYBBQUHMAGGFmh0dHA6Ly9vY3NwLnBraS5n
-dmEuZXMwEgYDVR0TAQH/BAgwBgEB/wIBAjCCAjQGA1UdIASCAiswggInMIICIwYKKwYBBAG/VQIB
-ADCCAhMwggHoBggrBgEFBQcCAjCCAdoeggHWAEEAdQB0AG8AcgBpAGQAYQBkACAAZABlACAAQwBl
-AHIAdABpAGYAaQBjAGEAYwBpAPMAbgAgAFIAYQDtAHoAIABkAGUAIABsAGEAIABHAGUAbgBlAHIA
-YQBsAGkAdABhAHQAIABWAGEAbABlAG4AYwBpAGEAbgBhAC4ADQAKAEwAYQAgAEQAZQBjAGwAYQBy
-AGEAYwBpAPMAbgAgAGQAZQAgAFAAcgDhAGMAdABpAGMAYQBzACAAZABlACAAQwBlAHIAdABpAGYA
-aQBjAGEAYwBpAPMAbgAgAHEAdQBlACAAcgBpAGcAZQAgAGUAbAAgAGYAdQBuAGMAaQBvAG4AYQBt
-AGkAZQBuAHQAbwAgAGQAZQAgAGwAYQAgAHAAcgBlAHMAZQBuAHQAZQAgAEEAdQB0AG8AcgBpAGQA
-YQBkACAAZABlACAAQwBlAHIAdABpAGYAaQBjAGEAYwBpAPMAbgAgAHMAZQAgAGUAbgBjAHUAZQBu
-AHQAcgBhACAAZQBuACAAbABhACAAZABpAHIAZQBjAGMAaQDzAG4AIAB3AGUAYgAgAGgAdAB0AHAA
-OgAvAC8AdwB3AHcALgBwAGsAaQAuAGcAdgBhAC4AZQBzAC8AYwBwAHMwJQYIKwYBBQUHAgEWGWh0
-dHA6Ly93d3cucGtpLmd2YS5lcy9jcHMwHQYDVR0OBBYEFHs100DSHHgZZu90ECjcPk+yeAT8MIGV
-BgNVHSMEgY0wgYqAFHs100DSHHgZZu90ECjcPk+yeAT8oWykajBoMQswCQYDVQQGEwJFUzEfMB0G
-A1UEChMWR2VuZXJhbGl0YXQgVmFsZW5jaWFuYTEPMA0GA1UECxMGUEtJR1ZBMScwJQYDVQQDEx5S
-b290IENBIEdlbmVyYWxpdGF0IFZhbGVuY2lhbmGCBDtF5WgwDQYJKoZIhvcNAQEFBQADggEBACRh
-TvW1yEICKrNcda3FbcrnlD+laJWIwVTAEGmiEi8YPyVQqHxK6sYJ2fR1xkDar1CdPaUWu20xxsdz
-Ckj+IHLtb8zog2EWRpABlUt9jppSCS/2bxzkoXHPjCpaF3ODR00PNvsETUlR4hTJZGH71BTg9J63
-NI8KJr2XXPR5OkowGcytT6CYirQxlyric21+eLj4iIlPsSKRZEv1UN4D2+XFducTZnV+ZfsBn5OH
-iJ35Rld8TWCvmHMTI6QgkYH60GFmuH3Rr9ZvHmw96RH9qfmCIoaZM3Fa6hlXPZHNqcCjbgcTpsnt
-+GijnsNacgmHKNHEc8RzGF9QdRYxn7fofMM=
------END CERTIFICATE-----
-
TWCA Root Certification Authority
=================================
-----BEGIN CERTIFICATE-----
@@ -3675,7 +3426,7 @@ ekD6819kR5LLU7m7Wc5P/dAVUwHY3+vZ5nbv0CO7O6l5s9UCKc2Jo5YPSjXnTkLAdc0Hz+Ys63su
-----END CERTIFICATE-----
TÜRKTRUST Elektronik Sertifika Hizmet Sağlayıcısı H5
-=========================================================
+====================================================
-----BEGIN CERTIFICATE-----
MIIEJzCCAw+gAwIBAgIHAI4X/iQggTANBgkqhkiG9w0BAQsFADCBsTELMAkGA1UEBhMCVFIxDzAN
BgNVBAcMBkFua2FyYTFNMEsGA1UECgxEVMOcUktUUlVTVCBCaWxnaSDEsGxldGnFn2ltIHZlIEJp
@@ -3698,30 +3449,6 @@ lpKQd/Ct9JDpEXjXk4nAPQu6KfTomZ1yju2dL+6SfaHx/126M2CFYv4HAqGEVka+lgqaE9chTLd8
B59OTj+RdPsnnRHM3eaxynFNExc5JsUpISuTKWqW+qtB4Uu2NQvAmxU=
-----END CERTIFICATE-----
-TÜRKTRUST Elektronik Sertifika Hizmet Sağlayıcısı H6
-=========================================================
------BEGIN CERTIFICATE-----
-MIIEJjCCAw6gAwIBAgIGfaHyZeyKMA0GCSqGSIb3DQEBCwUAMIGxMQswCQYDVQQGEwJUUjEPMA0G
-A1UEBwwGQW5rYXJhMU0wSwYDVQQKDERUw5xSS1RSVVNUIEJpbGdpIMSwbGV0acWfaW0gdmUgQmls
-acWfaW0gR8O8dmVubGnEn2kgSGl6bWV0bGVyaSBBLsWeLjFCMEAGA1UEAww5VMOcUktUUlVTVCBF
-bGVrdHJvbmlrIFNlcnRpZmlrYSBIaXptZXQgU2HEn2xhecSxY8Sxc8SxIEg2MB4XDTEzMTIxODA5
-MDQxMFoXDTIzMTIxNjA5MDQxMFowgbExCzAJBgNVBAYTAlRSMQ8wDQYDVQQHDAZBbmthcmExTTBL
-BgNVBAoMRFTDnFJLVFJVU1QgQmlsZ2kgxLBsZXRpxZ9pbSB2ZSBCaWxpxZ9pbSBHw7x2ZW5sacSf
-aSBIaXptZXRsZXJpIEEuxZ4uMUIwQAYDVQQDDDlUw5xSS1RSVVNUIEVsZWt0cm9uaWsgU2VydGlm
-aWthIEhpem1ldCBTYcSfbGF5xLFjxLFzxLEgSDYwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEK
-AoIBAQCdsGjW6L0UlqMACprx9MfMkU1xeHe59yEmFXNRFpQJRwXiM/VomjX/3EsvMsew7eKC5W/a
-2uqsxgbPJQ1BgfbBOCK9+bGlprMBvD9QFyv26WZV1DOzXPhDIHiTVRZwGTLmiddk671IUP320EED
-wnS3/faAz1vFq6TWlRKb55cTMgPp1KtDWxbtMyJkKbbSk60vbNg9tvYdDjTu0n2pVQ8g9P0pu5Fb
-HH3GQjhtQiht1AH7zYiXSX6484P4tZgvsycLSF5W506jM7NE1qXyGJTtHB6plVxiSvgNZ1GpryHV
-+DKdeboaX+UEVU0TRv/yz3THGmNtwx8XEsMeED5gCLMxAgMBAAGjQjBAMB0GA1UdDgQWBBTdVRcT
-9qzoSCHK77Wv0QAy7Z6MtTAOBgNVHQ8BAf8EBAMCAQYwDwYDVR0TAQH/BAUwAwEB/zANBgkqhkiG
-9w0BAQsFAAOCAQEAb1gNl0OqFlQ+v6nfkkU/hQu7VtMMUszIv3ZnXuaqs6fvuay0EBQNdH49ba3R
-fdCaqaXKGDsCQC4qnFAUi/5XfldcEQlLNkVS9z2sFP1E34uXI9TDwe7UU5X+LEr+DXCqu4svLcsy
-o4LyVN/Y8t3XSHLuSqMplsNEzm61kod2pLv0kmzOLBQJZo6NrRa1xxsJYTvjIKIDgI6tflEATseW
-hvtDmHd9KMeP2Cpu54Rvl0EpABZeTeIT6lnAY2c6RPuY/ATTMHKm9ocJV612ph1jmv3XZch4gyt1
-O6VbuA1df74jrlZVlFjvH4GMKrLN5ptjnhi85WsGtAuYSyher4hYyw==
------END CERTIFICATE-----
-
Certinomis - Root CA
====================
-----BEGIN CERTIFICATE-----
@@ -3863,6 +3590,369 @@ ypnTycUm/Q1oBEauttmbjL4ZvrHG8hnjXALKLNhvSgfZyTXaQHXyxKcZb55CEJh15pWLYLztxRLX
is7VmFxWlgPF7ncGNf/P5O4/E2Hu29othfDNrp2yGAlFw5Khchf8R7agCyzxxN5DaAhqXzvwdmP7
zAYspsbiDrW5viSP
-----END CERTIFICATE-----
+
+Hellenic Academic and Research Institutions RootCA 2015
+=======================================================
+-----BEGIN CERTIFICATE-----
+MIIGCzCCA/OgAwIBAgIBADANBgkqhkiG9w0BAQsFADCBpjELMAkGA1UEBhMCR1IxDzANBgNVBAcT
+BkF0aGVuczFEMEIGA1UEChM7SGVsbGVuaWMgQWNhZGVtaWMgYW5kIFJlc2VhcmNoIEluc3RpdHV0
+aW9ucyBDZXJ0LiBBdXRob3JpdHkxQDA+BgNVBAMTN0hlbGxlbmljIEFjYWRlbWljIGFuZCBSZXNl
+YXJjaCBJbnN0aXR1dGlvbnMgUm9vdENBIDIwMTUwHhcNMTUwNzA3MTAxMTIxWhcNNDAwNjMwMTAx
+MTIxWjCBpjELMAkGA1UEBhMCR1IxDzANBgNVBAcTBkF0aGVuczFEMEIGA1UEChM7SGVsbGVuaWMg
+QWNhZGVtaWMgYW5kIFJlc2VhcmNoIEluc3RpdHV0aW9ucyBDZXJ0LiBBdXRob3JpdHkxQDA+BgNV
+BAMTN0hlbGxlbmljIEFjYWRlbWljIGFuZCBSZXNlYXJjaCBJbnN0aXR1dGlvbnMgUm9vdENBIDIw
+MTUwggIiMA0GCSqGSIb3DQEBAQUAA4ICDwAwggIKAoICAQDC+Kk/G4n8PDwEXT2QNrCROnk8Zlrv
+bTkBSRq0t89/TSNTt5AA4xMqKKYx8ZEA4yjsriFBzh/a/X0SWwGDD7mwX5nh8hKDgE0GPt+sr+eh
+iGsxr/CL0BgzuNtFajT0AoAkKAoCFZVedioNmToUW/bLy1O8E00BiDeUJRtCvCLYjqOWXjrZMts+
+6PAQZe104S+nfK8nNLspfZu2zwnI5dMK/IhlZXQK3HMcXM1AsRzUtoSMTFDPaI6oWa7CJ06CojXd
+FPQf/7J31Ycvqm59JCfnxssm5uX+Zwdj2EUN3TpZZTlYepKZcj2chF6IIbjV9Cz82XBST3i4vTwr
+i5WY9bPRaM8gFH5MXF/ni+X1NYEZN9cRCLdmvtNKzoNXADrDgfgXy5I2XdGj2HUb4Ysn6npIQf1F
+GQatJ5lOwXBH3bWfgVMS5bGMSF0xQxfjjMZ6Y5ZLKTBOhE5iGV48zpeQpX8B653g+IuJ3SWYPZK2
+fu/Z8VFRfS0myGlZYeCsargqNhEEelC9MoS+L9xy1dcdFkfkR2YgP/SWxa+OAXqlD3pk9Q0Yh9mu
+iNX6hME6wGkoLfINaFGq46V3xqSQDqE3izEjR8EJCOtu93ib14L8hCCZSRm2Ekax+0VVFqmjZayc
+Bw/qa9wfLgZy7IaIEuQt218FL+TwA9MmM+eAws1CoRc0CwIDAQABo0IwQDAPBgNVHRMBAf8EBTAD
+AQH/MA4GA1UdDwEB/wQEAwIBBjAdBgNVHQ4EFgQUcRVnyMjJvXVdctA4GGqd83EkVAswDQYJKoZI
+hvcNAQELBQADggIBAHW7bVRLqhBYRjTyYtcWNl0IXtVsyIe9tC5G8jH4fOpCtZMWVdyhDBKg2mF+
+D1hYc2Ryx+hFjtyp8iY/xnmMsVMIM4GwVhO+5lFc2JsKT0ucVlMC6U/2DWDqTUJV6HwbISHTGzrM
+d/K4kPFox/la/vot9L/J9UUbzjgQKjeKeaO04wlshYaT/4mWJ3iBj2fjRnRUjtkNaeJK9E10A/+y
+d+2VZ5fkscWrv2oj6NSU4kQoYsRL4vDY4ilrGnB+JGGTe08DMiUNRSQrlrRGar9KC/eaj8GsGsVn
+82800vpzY4zvFrCopEYq+OsS7HK07/grfoxSwIuEVPkvPuNVqNxmsdnhX9izjFk0WaSrT2y7Hxjb
+davYy5LNlDhhDgcGH0tGEPEVvo2FXDtKK4F5D7Rpn0lQl033DlZdwJVqwjbDG2jJ9SrcR5q+ss7F
+Jej6A7na+RZukYT1HCjI/CbM1xyQVqdfbzoEvM14iQuODy+jqk+iGxI9FghAD/FGTNeqewjBCvVt
+J94Cj8rDtSvK6evIIVM4pcw72Hc3MKJP2W/R8kCtQXoXxdZKNYm3QdV8hn9VTYNKpXMgwDqvkPGa
+JI7ZjnHKe7iG2rKPmT4dEw0SEe7Uq/DpFXYC5ODfqiAeW2GFZECpkJcNrVPSWh2HagCXZWK0vm9q
+p/UsQu0yrbYhnr68
+-----END CERTIFICATE-----
+
+Hellenic Academic and Research Institutions ECC RootCA 2015
+===========================================================
+-----BEGIN CERTIFICATE-----
+MIICwzCCAkqgAwIBAgIBADAKBggqhkjOPQQDAjCBqjELMAkGA1UEBhMCR1IxDzANBgNVBAcTBkF0
+aGVuczFEMEIGA1UEChM7SGVsbGVuaWMgQWNhZGVtaWMgYW5kIFJlc2VhcmNoIEluc3RpdHV0aW9u
+cyBDZXJ0LiBBdXRob3JpdHkxRDBCBgNVBAMTO0hlbGxlbmljIEFjYWRlbWljIGFuZCBSZXNlYXJj
+aCBJbnN0aXR1dGlvbnMgRUNDIFJvb3RDQSAyMDE1MB4XDTE1MDcwNzEwMzcxMloXDTQwMDYzMDEw
+MzcxMlowgaoxCzAJBgNVBAYTAkdSMQ8wDQYDVQQHEwZBdGhlbnMxRDBCBgNVBAoTO0hlbGxlbmlj
+IEFjYWRlbWljIGFuZCBSZXNlYXJjaCBJbnN0aXR1dGlvbnMgQ2VydC4gQXV0aG9yaXR5MUQwQgYD
+VQQDEztIZWxsZW5pYyBBY2FkZW1pYyBhbmQgUmVzZWFyY2ggSW5zdGl0dXRpb25zIEVDQyBSb290
+Q0EgMjAxNTB2MBAGByqGSM49AgEGBSuBBAAiA2IABJKgQehLgoRc4vgxEZmGZE4JJS+dQS8KrjVP
+dJWyUWRrjWvmP3CV8AVER6ZyOFB2lQJajq4onvktTpnvLEhvTCUp6NFxW98dwXU3tNf6e3pCnGoK
+Vlp8aQuqgAkkbH7BRqNCMEAwDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAQYwHQYDVR0O
+BBYEFLQiC4KZJAEOnLvkDv2/+5cgk5kqMAoGCCqGSM49BAMCA2cAMGQCMGfOFmI4oqxiRaeplSTA
+GiecMjvAwNW6qef4BENThe5SId6d9SWDPp5YSy/XZxMOIQIwBeF1Ad5o7SofTUwJCA3sS61kFyjn
+dc5FZXIhF8siQQ6ME5g4mlRtm8rifOoCWCKR
+-----END CERTIFICATE-----
+
+Certplus Root CA G1
+===================
+-----BEGIN CERTIFICATE-----
+MIIFazCCA1OgAwIBAgISESBVg+QtPlRWhS2DN7cs3EYRMA0GCSqGSIb3DQEBDQUAMD4xCzAJBgNV
+BAYTAkZSMREwDwYDVQQKDAhDZXJ0cGx1czEcMBoGA1UEAwwTQ2VydHBsdXMgUm9vdCBDQSBHMTAe
+Fw0xNDA1MjYwMDAwMDBaFw0zODAxMTUwMDAwMDBaMD4xCzAJBgNVBAYTAkZSMREwDwYDVQQKDAhD
+ZXJ0cGx1czEcMBoGA1UEAwwTQ2VydHBsdXMgUm9vdCBDQSBHMTCCAiIwDQYJKoZIhvcNAQEBBQAD
+ggIPADCCAgoCggIBANpQh7bauKk+nWT6VjOaVj0W5QOVsjQcmm1iBdTYj+eJZJ+622SLZOZ5KmHN
+r49aiZFluVj8tANfkT8tEBXgfs+8/H9DZ6itXjYj2JizTfNDnjl8KvzsiNWI7nC9hRYt6kuJPKNx
+Qv4c/dMcLRC4hlTqQ7jbxofaqK6AJc96Jh2qkbBIb6613p7Y1/oA/caP0FG7Yn2ksYyy/yARujVj
+BYZHYEMzkPZHogNPlk2dT8Hq6pyi/jQu3rfKG3akt62f6ajUeD94/vI4CTYd0hYCyOwqaK/1jpTv
+LRN6HkJKHRUxrgwEV/xhc/MxVoYxgKDEEW4wduOU8F8ExKyHcomYxZ3MVwia9Az8fXoFOvpHgDm2
+z4QTd28n6v+WZxcIbekN1iNQMLAVdBM+5S//Ds3EC0pd8NgAM0lm66EYfFkuPSi5YXHLtaW6uOrc
+4nBvCGrch2c0798wct3zyT8j/zXhviEpIDCB5BmlIOklynMxdCm+4kLV87ImZsdo/Rmz5yCTmehd
+4F6H50boJZwKKSTUzViGUkAksnsPmBIgJPaQbEfIDbsYIC7Z/fyL8inqh3SV4EJQeIQEQWGw9CEj
+jy3LKCHyamz0GqbFFLQ3ZU+V/YDI+HLlJWvEYLF7bY5KinPOWftwenMGE9nTdDckQQoRb5fc5+R+
+ob0V8rqHDz1oihYHAgMBAAGjYzBhMA4GA1UdDwEB/wQEAwIBBjAPBgNVHRMBAf8EBTADAQH/MB0G
+A1UdDgQWBBSowcCbkahDFXxdBie0KlHYlwuBsTAfBgNVHSMEGDAWgBSowcCbkahDFXxdBie0KlHY
+lwuBsTANBgkqhkiG9w0BAQ0FAAOCAgEAnFZvAX7RvUz1isbwJh/k4DgYzDLDKTudQSk0YcbX8ACh
+66Ryj5QXvBMsdbRX7gp8CXrc1cqh0DQT+Hern+X+2B50ioUHj3/MeXrKls3N/U/7/SMNkPX0XtPG
+YX2eEeAC7gkE2Qfdpoq3DIMku4NQkv5gdRE+2J2winq14J2by5BSS7CTKtQ+FjPlnsZlFT5kOwQ/
+2wyPX1wdaR+v8+khjPPvl/aatxm2hHSco1S1cE5j2FddUyGbQJJD+tZ3VTNPZNX70Cxqjm0lpu+F
+6ALEUz65noe8zDUa3qHpimOHZR4RKttjd5cUvpoUmRGywO6wT/gUITJDT5+rosuoD6o7BlXGEilX
+CNQ314cnrUlZp5GrRHpejXDbl85IULFzk/bwg2D5zfHhMf1bfHEhYxQUqq/F3pN+aLHsIqKqkHWe
+tUNy6mSjhEv9DKgma3GX7lZjZuhCVPnHHd/Qj1vfyDBviP4NxDMcU6ij/UgQ8uQKTuEVV/xuZDDC
+VRHc6qnNSlSsKWNEz0pAoNZoWRsz+e86i9sgktxChL8Bq4fA1SCC28a5g4VCXA9DO2pJNdWY9BW/
++mGBDAkgGNLQFwzLSABQ6XaCjGTXOqAHVcweMcDvOrRl++O/QmueD6i9a5jc2NvLi6Td11n0bt3+
+qsOR0C5CB8AMTVPNJLFMWx5R9N/pkvo=
+-----END CERTIFICATE-----
+
+Certplus Root CA G2
+===================
+-----BEGIN CERTIFICATE-----
+MIICHDCCAaKgAwIBAgISESDZkc6uo+jF5//pAq/Pc7xVMAoGCCqGSM49BAMDMD4xCzAJBgNVBAYT
+AkZSMREwDwYDVQQKDAhDZXJ0cGx1czEcMBoGA1UEAwwTQ2VydHBsdXMgUm9vdCBDQSBHMjAeFw0x
+NDA1MjYwMDAwMDBaFw0zODAxMTUwMDAwMDBaMD4xCzAJBgNVBAYTAkZSMREwDwYDVQQKDAhDZXJ0
+cGx1czEcMBoGA1UEAwwTQ2VydHBsdXMgUm9vdCBDQSBHMjB2MBAGByqGSM49AgEGBSuBBAAiA2IA
+BM0PW1aC3/BFGtat93nwHcmsltaeTpwftEIRyoa/bfuFo8XlGVzX7qY/aWfYeOKmycTbLXku54uN
+Am8xIk0G42ByRZ0OQneezs/lf4WbGOT8zC5y0xaTTsqZY1yhBSpsBqNjMGEwDgYDVR0PAQH/BAQD
+AgEGMA8GA1UdEwEB/wQFMAMBAf8wHQYDVR0OBBYEFNqDYwJ5jtpMxjwjFNiPwyCrKGBZMB8GA1Ud
+IwQYMBaAFNqDYwJ5jtpMxjwjFNiPwyCrKGBZMAoGCCqGSM49BAMDA2gAMGUCMHD+sAvZ94OX7PNV
+HdTcswYO/jOYnYs5kGuUIe22113WTNchp+e/IQ8rzfcq3IUHnQIxAIYUFuXcsGXCwI4Un78kFmjl
+vPl5adytRSv3tjFzzAalU5ORGpOucGpnutee5WEaXw==
+-----END CERTIFICATE-----
+
+OpenTrust Root CA G1
+====================
+-----BEGIN CERTIFICATE-----
+MIIFbzCCA1egAwIBAgISESCzkFU5fX82bWTCp59rY45nMA0GCSqGSIb3DQEBCwUAMEAxCzAJBgNV
+BAYTAkZSMRIwEAYDVQQKDAlPcGVuVHJ1c3QxHTAbBgNVBAMMFE9wZW5UcnVzdCBSb290IENBIEcx
+MB4XDTE0MDUyNjA4NDU1MFoXDTM4MDExNTAwMDAwMFowQDELMAkGA1UEBhMCRlIxEjAQBgNVBAoM
+CU9wZW5UcnVzdDEdMBsGA1UEAwwUT3BlblRydXN0IFJvb3QgQ0EgRzEwggIiMA0GCSqGSIb3DQEB
+AQUAA4ICDwAwggIKAoICAQD4eUbalsUwXopxAy1wpLuwxQjczeY1wICkES3d5oeuXT2R0odsN7fa
+Yp6bwiTXj/HbpqbfRm9RpnHLPhsxZ2L3EVs0J9V5ToybWL0iEA1cJwzdMOWo010hOHQX/uMftk87
+ay3bfWAfjH1MBcLrARYVmBSO0ZB3Ij/swjm4eTrwSSTilZHcYTSSjFR077F9jAHiOH3BX2pfJLKO
+YheteSCtqx234LSWSE9mQxAGFiQD4eCcjsZGT44ameGPuY4zbGneWK2gDqdkVBFpRGZPTBKnjix9
+xNRbxQA0MMHZmf4yzgeEtE7NCv82TWLxp2NX5Ntqp66/K7nJ5rInieV+mhxNaMbBGN4zK1FGSxyO
+9z0M+Yo0FMT7MzUj8czxKselu7Cizv5Ta01BG2Yospb6p64KTrk5M0ScdMGTHPjgniQlQ/GbI4Kq
+3ywgsNw2TgOzfALU5nsaqocTvz6hdLubDuHAk5/XpGbKuxs74zD0M1mKB3IDVedzagMxbm+WG+Oi
+n6+Sx+31QrclTDsTBM8clq8cIqPQqwWyTBIjUtz9GVsnnB47ev1CI9sjgBPwvFEVVJSmdz7QdFG9
+URQIOTfLHzSpMJ1ShC5VkLG631UAC9hWLbFJSXKAqWLXwPYYEQRVzXR7z2FwefR7LFxckvzluFqr
+TJOVoSfupb7PcSNCupt2LQIDAQABo2MwYTAOBgNVHQ8BAf8EBAMCAQYwDwYDVR0TAQH/BAUwAwEB
+/zAdBgNVHQ4EFgQUl0YhVyE12jZVx/PxN3DlCPaTKbYwHwYDVR0jBBgwFoAUl0YhVyE12jZVx/Px
+N3DlCPaTKbYwDQYJKoZIhvcNAQELBQADggIBAB3dAmB84DWn5ph76kTOZ0BP8pNuZtQ5iSas000E
+PLuHIT839HEl2ku6q5aCgZG27dmxpGWX4m9kWaSW7mDKHyP7Rbr/jyTwyqkxf3kfgLMtMrpkZ2Cv
+uVnN35pJ06iCsfmYlIrM4LvgBBuZYLFGZdwIorJGnkSI6pN+VxbSFXJfLkur1J1juONI5f6ELlgK
+n0Md/rcYkoZDSw6cMoYsYPXpSOqV7XAp8dUv/TW0V8/bhUiZucJvbI/NeJWsZCj9VrDDb8O+WVLh
+X4SPgPL0DTatdrOjteFkdjpY3H1PXlZs5VVZV6Xf8YpmMIzUUmI4d7S+KNfKNsSbBfD4Fdvb8e80
+nR14SohWZ25g/4/Ii+GOvUKpMwpZQhISKvqxnUOOBZuZ2mKtVzazHbYNeS2WuOvyDEsMpZTGMKcm
+GS3tTAZQMPH9WD25SxdfGbRqhFS0OE85og2WaMMolP3tLR9Ka0OWLpABEPs4poEL0L9109S5zvE/
+bw4cHjdx5RiHdRk/ULlepEU0rbDK5uUTdg8xFKmOLZTW1YVNcxVPS/KyPu1svf0OnWZzsD2097+o
+4BGkxK51CUpjAEggpsadCwmKtODmzj7HPiY46SvepghJAwSQiumPv+i2tCqjI40cHLI5kqiPAlxA
+OXXUc0ECd97N4EOH1uS6SsNsEn/+KuYj1oxx
+-----END CERTIFICATE-----
+
+OpenTrust Root CA G2
+====================
+-----BEGIN CERTIFICATE-----
+MIIFbzCCA1egAwIBAgISESChaRu/vbm9UpaPI+hIvyYRMA0GCSqGSIb3DQEBDQUAMEAxCzAJBgNV
+BAYTAkZSMRIwEAYDVQQKDAlPcGVuVHJ1c3QxHTAbBgNVBAMMFE9wZW5UcnVzdCBSb290IENBIEcy
+MB4XDTE0MDUyNjAwMDAwMFoXDTM4MDExNTAwMDAwMFowQDELMAkGA1UEBhMCRlIxEjAQBgNVBAoM
+CU9wZW5UcnVzdDEdMBsGA1UEAwwUT3BlblRydXN0IFJvb3QgQ0EgRzIwggIiMA0GCSqGSIb3DQEB
+AQUAA4ICDwAwggIKAoICAQDMtlelM5QQgTJT32F+D3Y5z1zCU3UdSXqWON2ic2rxb95eolq5cSG+
+Ntmh/LzubKh8NBpxGuga2F8ORAbtp+Dz0mEL4DKiltE48MLaARf85KxP6O6JHnSrT78eCbY2albz
+4e6WiWYkBuTNQjpK3eCasMSCRbP+yatcfD7J6xcvDH1urqWPyKwlCm/61UWY0jUJ9gNDlP7ZvyCV
+eYCYitmJNbtRG6Q3ffyZO6v/v6wNj0OxmXsWEH4db0fEFY8ElggGQgT4hNYdvJGmQr5J1WqIP7wt
+UdGejeBSzFfdNTVY27SPJIjki9/ca1TSgSuyzpJLHB9G+h3Ykst2Z7UJmQnlrBcUVXDGPKBWCgOz
+3GIZ38i1MH/1PCZ1Eb3XG7OHngevZXHloM8apwkQHZOJZlvoPGIytbU6bumFAYueQ4xncyhZW+vj
+3CzMpSZyYhK05pyDRPZRpOLAeiRXyg6lPzq1O4vldu5w5pLeFlwoW5cZJ5L+epJUzpM5ChaHvGOz
+9bGTXOBut9Dq+WIyiET7vycotjCVXRIouZW+j1MY5aIYFuJWpLIsEPUdN6b4t/bQWVyJ98LVtZR0
+0dX+G7bw5tYee9I8y6jj9RjzIR9u701oBnstXW5DiabA+aC/gh7PU3+06yzbXfZqfUAkBXKJOAGT
+y3HCOV0GEfZvePg3DTmEJwIDAQABo2MwYTAOBgNVHQ8BAf8EBAMCAQYwDwYDVR0TAQH/BAUwAwEB
+/zAdBgNVHQ4EFgQUajn6QiL35okATV59M4PLuG53hq8wHwYDVR0jBBgwFoAUajn6QiL35okATV59
+M4PLuG53hq8wDQYJKoZIhvcNAQENBQADggIBAJjLq0A85TMCl38th6aP1F5Kr7ge57tx+4BkJamz
+Gj5oXScmp7oq4fBXgwpkTx4idBvpkF/wrM//T2h6OKQQbA2xx6R3gBi2oihEdqc0nXGEL8pZ0keI
+mUEiyTCYYW49qKgFbdEfwFFEVn8nNQLdXpgKQuswv42hm1GqO+qTRmTFAHneIWv2V6CG1wZy7HBG
+S4tz3aAhdT7cHcCP009zHIXZ/n9iyJVvttN7jLpTwm+bREx50B1ws9efAvSyB7DH5fitIw6mVskp
+EndI2S9G/Tvw/HRwkqWOOAgfZDC2t0v7NqwQjqBSM2OdAzVWxWm9xiNaJ5T2pBL4LTM8oValX9YZ
+6e18CL13zSdkzJTaTkZQh+D5wVOAHrut+0dSixv9ovneDiK3PTNZbNTe9ZUGMg1RGUFcPk8G97kr
+gCf2o6p6fAbhQ8MTOWIaNr3gKC6UAuQpLmBVrkA9sHSSXvAgZJY/X0VdiLWK2gKgW0VU3jg9CcCo
+SmVGFvyqv1ROTVu+OEO3KMqLM6oaJbolXCkvW0pujOotnCr2BXbgd5eAiN1nE28daCSLT7d0geX0
+YJ96Vdc+N9oWaz53rK4YcJUIeSkDiv7BO7M/Gg+kO14fWKGVyasvc0rQLW6aWQ9VGHgtPFGml4vm
+u7JwqkwR3v98KzfUetF3NI/n+UL3PIEMS1IK
+-----END CERTIFICATE-----
+
+OpenTrust Root CA G3
+====================
+-----BEGIN CERTIFICATE-----
+MIICITCCAaagAwIBAgISESDm+Ez8JLC+BUCs2oMbNGA/MAoGCCqGSM49BAMDMEAxCzAJBgNVBAYT
+AkZSMRIwEAYDVQQKDAlPcGVuVHJ1c3QxHTAbBgNVBAMMFE9wZW5UcnVzdCBSb290IENBIEczMB4X
+DTE0MDUyNjAwMDAwMFoXDTM4MDExNTAwMDAwMFowQDELMAkGA1UEBhMCRlIxEjAQBgNVBAoMCU9w
+ZW5UcnVzdDEdMBsGA1UEAwwUT3BlblRydXN0IFJvb3QgQ0EgRzMwdjAQBgcqhkjOPQIBBgUrgQQA
+IgNiAARK7liuTcpm3gY6oxH84Bjwbhy6LTAMidnW7ptzg6kjFYwvWYpa3RTqnVkrQ7cG7DK2uu5B
+ta1doYXM6h0UZqNnfkbilPPntlahFVmhTzeXuSIevRHr9LIfXsMUmuXZl5mjYzBhMA4GA1UdDwEB
+/wQEAwIBBjAPBgNVHRMBAf8EBTADAQH/MB0GA1UdDgQWBBRHd8MUi2I5DMlv4VBN0BBY3JWIbTAf
+BgNVHSMEGDAWgBRHd8MUi2I5DMlv4VBN0BBY3JWIbTAKBggqhkjOPQQDAwNpADBmAjEAj6jcnboM
+BBf6Fek9LykBl7+BFjNAk2z8+e2AcG+qj9uEwov1NcoG3GRvaBbhj5G5AjEA2Euly8LQCGzpGPta
+3U1fJAuwACEl74+nBCZx4nxp5V2a+EEfOzmTk51V6s2N8fvB
+-----END CERTIFICATE-----
+
+ISRG Root X1
+============
+-----BEGIN CERTIFICATE-----
+MIIFazCCA1OgAwIBAgIRAIIQz7DSQONZRGPgu2OCiwAwDQYJKoZIhvcNAQELBQAwTzELMAkGA1UE
+BhMCVVMxKTAnBgNVBAoTIEludGVybmV0IFNlY3VyaXR5IFJlc2VhcmNoIEdyb3VwMRUwEwYDVQQD
+EwxJU1JHIFJvb3QgWDEwHhcNMTUwNjA0MTEwNDM4WhcNMzUwNjA0MTEwNDM4WjBPMQswCQYDVQQG
+EwJVUzEpMCcGA1UEChMgSW50ZXJuZXQgU2VjdXJpdHkgUmVzZWFyY2ggR3JvdXAxFTATBgNVBAMT
+DElTUkcgUm9vdCBYMTCCAiIwDQYJKoZIhvcNAQEBBQADggIPADCCAgoCggIBAK3oJHP0FDfzm54r
+Vygch77ct984kIxuPOZXoHj3dcKi/vVqbvYATyjb3miGbESTtrFj/RQSa78f0uoxmyF+0TM8ukj1
+3Xnfs7j/EvEhmkvBioZxaUpmZmyPfjxwv60pIgbz5MDmgK7iS4+3mX6UA5/TR5d8mUgjU+g4rk8K
+b4Mu0UlXjIB0ttov0DiNewNwIRt18jA8+o+u3dpjq+sWT8KOEUt+zwvo/7V3LvSye0rgTBIlDHCN
+Aymg4VMk7BPZ7hm/ELNKjD+Jo2FR3qyHB5T0Y3HsLuJvW5iB4YlcNHlsdu87kGJ55tukmi8mxdAQ
+4Q7e2RCOFvu396j3x+UCB5iPNgiV5+I3lg02dZ77DnKxHZu8A/lJBdiB3QW0KtZB6awBdpUKD9jf
+1b0SHzUvKBds0pjBqAlkd25HN7rOrFleaJ1/ctaJxQZBKT5ZPt0m9STJEadao0xAH0ahmbWnOlFu
+hjuefXKnEgV4We0+UXgVCwOPjdAvBbI+e0ocS3MFEvzG6uBQE3xDk3SzynTnjh8BCNAw1FtxNrQH
+usEwMFxIt4I7mKZ9YIqioymCzLq9gwQbooMDQaHWBfEbwrbwqHyGO0aoSCqI3Haadr8faqU9GY/r
+OPNk3sgrDQoo//fb4hVC1CLQJ13hef4Y53CIrU7m2Ys6xt0nUW7/vGT1M0NPAgMBAAGjQjBAMA4G
+A1UdDwEB/wQEAwIBBjAPBgNVHRMBAf8EBTADAQH/MB0GA1UdDgQWBBR5tFnme7bl5AFzgAiIyBpY
+9umbbjANBgkqhkiG9w0BAQsFAAOCAgEAVR9YqbyyqFDQDLHYGmkgJykIrGF1XIpu+ILlaS/V9lZL
+ubhzEFnTIZd+50xx+7LSYK05qAvqFyFWhfFQDlnrzuBZ6brJFe+GnY+EgPbk6ZGQ3BebYhtF8GaV
+0nxvwuo77x/Py9auJ/GpsMiu/X1+mvoiBOv/2X/qkSsisRcOj/KKNFtY2PwByVS5uCbMiogziUwt
+hDyC3+6WVwW6LLv3xLfHTjuCvjHIInNzktHCgKQ5ORAzI4JMPJ+GslWYHb4phowim57iaztXOoJw
+TdwJx4nLCgdNbOhdjsnvzqvHu7UrTkXWStAmzOVyyghqpZXjFaH3pO3JLF+l+/+sKAIuvtd7u+Nx
+e5AW0wdeRlN8NwdCjNPElpzVmbUq4JUagEiuTDkHzsxHpFKVK7q4+63SM1N95R1NbdWhscdCb+ZA
+JzVcoyi3B43njTOQ5yOf+1CceWxG1bQVs5ZufpsMljq4Ui0/1lvh+wjChP4kqKOJ2qxq4RgqsahD
+YVvTH9w7jXbyLeiNdd8XM2w9U/t7y0Ff/9yi0GE44Za4rF2LN9d11TPAmRGunUHBcnWEvgJBQl9n
+JEiU0Zsnvgc/ubhPgXRR4Xq37Z0j4r7g1SgEEzwxA57demyPxgcYxn/eR44/KJ4EBs+lVDR3veyJ
+m+kXQ99b21/+jh5Xos1AnX5iItreGCc=
+-----END CERTIFICATE-----
+
+AC RAIZ FNMT-RCM
+================
+-----BEGIN CERTIFICATE-----
+MIIFgzCCA2ugAwIBAgIPXZONMGc2yAYdGsdUhGkHMA0GCSqGSIb3DQEBCwUAMDsxCzAJBgNVBAYT
+AkVTMREwDwYDVQQKDAhGTk1ULVJDTTEZMBcGA1UECwwQQUMgUkFJWiBGTk1ULVJDTTAeFw0wODEw
+MjkxNTU5NTZaFw0zMDAxMDEwMDAwMDBaMDsxCzAJBgNVBAYTAkVTMREwDwYDVQQKDAhGTk1ULVJD
+TTEZMBcGA1UECwwQQUMgUkFJWiBGTk1ULVJDTTCCAiIwDQYJKoZIhvcNAQEBBQADggIPADCCAgoC
+ggIBALpxgHpMhm5/yBNtwMZ9HACXjywMI7sQmkCpGreHiPibVmr75nuOi5KOpyVdWRHbNi63URcf
+qQgfBBckWKo3Shjf5TnUV/3XwSyRAZHiItQDwFj8d0fsjz50Q7qsNI1NOHZnjrDIbzAzWHFctPVr
+btQBULgTfmxKo0nRIBnuvMApGGWn3v7v3QqQIecaZ5JCEJhfTzC8PhxFtBDXaEAUwED653cXeuYL
+j2VbPNmaUtu1vZ5Gzz3rkQUCwJaydkxNEJY7kvqcfw+Z374jNUUeAlz+taibmSXaXvMiwzn15Cou
+08YfxGyqxRxqAQVKL9LFwag0Jl1mpdICIfkYtwb1TplvqKtMUejPUBjFd8g5CSxJkjKZqLsXF3mw
+WsXmo8RZZUc1g16p6DULmbvkzSDGm0oGObVo/CK67lWMK07q87Hj/LaZmtVC+nFNCM+HHmpxffnT
+tOmlcYF7wk5HlqX2doWjKI/pgG6BU6VtX7hI+cL5NqYuSf+4lsKMB7ObiFj86xsc3i1w4peSMKGJ
+47xVqCfWS+2QrYv6YyVZLag13cqXM7zlzced0ezvXg5KkAYmY6252TUtB7p2ZSysV4999AeU14EC
+ll2jB0nVetBX+RvnU0Z1qrB5QstocQjpYL05ac70r8NWQMetUqIJ5G+GR4of6ygnXYMgrwTJbFaa
+i0b1AgMBAAGjgYMwgYAwDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAQYwHQYDVR0OBBYE
+FPd9xf3E6Jobd2Sn9R2gzL+HYJptMD4GA1UdIAQ3MDUwMwYEVR0gADArMCkGCCsGAQUFBwIBFh1o
+dHRwOi8vd3d3LmNlcnQuZm5tdC5lcy9kcGNzLzANBgkqhkiG9w0BAQsFAAOCAgEAB5BK3/MjTvDD
+nFFlm5wioooMhfNzKWtN/gHiqQxjAb8EZ6WdmF/9ARP67Jpi6Yb+tmLSbkyU+8B1RXxlDPiyN8+s
+D8+Nb/kZ94/sHvJwnvDKuO+3/3Y3dlv2bojzr2IyIpMNOmqOFGYMLVN0V2Ue1bLdI4E7pWYjJ2cJ
+j+F3qkPNZVEI7VFY/uY5+ctHhKQV8Xa7pO6kO8Rf77IzlhEYt8llvhjho6Tc+hj507wTmzl6NLrT
+Qfv6MooqtyuGC2mDOL7Nii4LcK2NJpLuHvUBKwrZ1pebbuCoGRw6IYsMHkCtA+fdZn71uSANA+iW
++YJF1DngoABd15jmfZ5nc8OaKveri6E6FO80vFIOiZiaBECEHX5FaZNXzuvO+FB8TxxuBEOb+dY7
+Ixjp6o7RTUaN8Tvkasq6+yO3m/qZASlaWFot4/nUbQ4mrcFuNLwy+AwF+mWj2zs3gyLp1txyM/1d
+8iC9djwj2ij3+RvrWWTV3F9yfiD8zYm1kGdNYno/Tq0dwzn+evQoFt9B9kiABdcPUXmsEKvU7ANm
+5mqwujGSQkBqvjrTcuFqN1W8rB2Vt2lh8kORdOag0wokRqEIr9baRRmW1FMdW4R58MD3R++Lj8UG
+rp1MYp3/RgT408m2ECVAdf4WqslKYIYvuu8wd+RU4riEmViAqhOLUTpPSPaLtrM=
+-----END CERTIFICATE-----
+
+Amazon Root CA 1
+================
+-----BEGIN CERTIFICATE-----
+MIIDQTCCAimgAwIBAgITBmyfz5m/jAo54vB4ikPmljZbyjANBgkqhkiG9w0BAQsFADA5MQswCQYD
+VQQGEwJVUzEPMA0GA1UEChMGQW1hem9uMRkwFwYDVQQDExBBbWF6b24gUm9vdCBDQSAxMB4XDTE1
+MDUyNjAwMDAwMFoXDTM4MDExNzAwMDAwMFowOTELMAkGA1UEBhMCVVMxDzANBgNVBAoTBkFtYXpv
+bjEZMBcGA1UEAxMQQW1hem9uIFJvb3QgQ0EgMTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoC
+ggEBALJ4gHHKeNXjca9HgFB0fW7Y14h29Jlo91ghYPl0hAEvrAIthtOgQ3pOsqTQNroBvo3bSMgH
+FzZM9O6II8c+6zf1tRn4SWiw3te5djgdYZ6k/oI2peVKVuRF4fn9tBb6dNqcmzU5L/qwIFAGbHrQ
+gLKm+a/sRxmPUDgH3KKHOVj4utWp+UhnMJbulHheb4mjUcAwhmahRWa6VOujw5H5SNz/0egwLX0t
+dHA114gk957EWW67c4cX8jJGKLhD+rcdqsq08p8kDi1L93FcXmn/6pUCyziKrlA4b9v7LWIbxcce
+VOF34GfID5yHI9Y/QCB/IIDEgEw+OyQmjgSubJrIqg0CAwEAAaNCMEAwDwYDVR0TAQH/BAUwAwEB
+/zAOBgNVHQ8BAf8EBAMCAYYwHQYDVR0OBBYEFIQYzIU07LwMlJQuCFmcx7IQTgoIMA0GCSqGSIb3
+DQEBCwUAA4IBAQCY8jdaQZChGsV2USggNiMOruYou6r4lK5IpDB/G/wkjUu0yKGX9rbxenDIU5PM
+CCjjmCXPI6T53iHTfIUJrU6adTrCC2qJeHZERxhlbI1Bjjt/msv0tadQ1wUsN+gDS63pYaACbvXy
+8MWy7Vu33PqUXHeeE6V/Uq2V8viTO96LXFvKWlJbYK8U90vvo/ufQJVtMVT8QtPHRh8jrdkPSHCa
+2XV4cdFyQzR1bldZwgJcJmApzyMZFo6IQ6XU5MsI+yMRQ+hDKXJioaldXgjUkK642M4UwtBV8ob2
+xJNDd2ZhwLnoQdeXeGADbkpyrqXRfboQnoZsG4q5WTP468SQvvG5
+-----END CERTIFICATE-----
+
+Amazon Root CA 2
+================
+-----BEGIN CERTIFICATE-----
+MIIFQTCCAymgAwIBAgITBmyf0pY1hp8KD+WGePhbJruKNzANBgkqhkiG9w0BAQwFADA5MQswCQYD
+VQQGEwJVUzEPMA0GA1UEChMGQW1hem9uMRkwFwYDVQQDExBBbWF6b24gUm9vdCBDQSAyMB4XDTE1
+MDUyNjAwMDAwMFoXDTQwMDUyNjAwMDAwMFowOTELMAkGA1UEBhMCVVMxDzANBgNVBAoTBkFtYXpv
+bjEZMBcGA1UEAxMQQW1hem9uIFJvb3QgQ0EgMjCCAiIwDQYJKoZIhvcNAQEBBQADggIPADCCAgoC
+ggIBAK2Wny2cSkxKgXlRmeyKy2tgURO8TW0G/LAIjd0ZEGrHJgw12MBvIITplLGbhQPDW9tK6Mj4
+kHbZW0/jTOgGNk3Mmqw9DJArktQGGWCsN0R5hYGCrVo34A3MnaZMUnbqQ523BNFQ9lXg1dKmSYXp
+N+nKfq5clU1Imj+uIFptiJXZNLhSGkOQsL9sBbm2eLfq0OQ6PBJTYv9K8nu+NQWpEjTj82R0Yiw9
+AElaKP4yRLuH3WUnAnE72kr3H9rN9yFVkE8P7K6C4Z9r2UXTu/Bfh+08LDmG2j/e7HJV63mjrdvd
+fLC6HM783k81ds8P+HgfajZRRidhW+mez/CiVX18JYpvL7TFz4QuK/0NURBs+18bvBt+xa47mAEx
+kv8LV/SasrlX6avvDXbR8O70zoan4G7ptGmh32n2M8ZpLpcTnqWHsFcQgTfJU7O7f/aS0ZzQGPSS
+btqDT6ZjmUyl+17vIWR6IF9sZIUVyzfpYgwLKhbcAS4y2j5L9Z469hdAlO+ekQiG+r5jqFoz7Mt0
+Q5X5bGlSNscpb/xVA1wf+5+9R+vnSUeVC06JIglJ4PVhHvG/LopyboBZ/1c6+XUyo05f7O0oYtlN
+c/LMgRdg7c3r3NunysV+Ar3yVAhU/bQtCSwXVEqY0VThUWcI0u1ufm8/0i2BWSlmy5A5lREedCf+
+3euvAgMBAAGjQjBAMA8GA1UdEwEB/wQFMAMBAf8wDgYDVR0PAQH/BAQDAgGGMB0GA1UdDgQWBBSw
+DPBMMPQFWAJI/TPlUq9LhONmUjANBgkqhkiG9w0BAQwFAAOCAgEAqqiAjw54o+Ci1M3m9Zh6O+oA
+A7CXDpO8Wqj2LIxyh6mx/H9z/WNxeKWHWc8w4Q0QshNabYL1auaAn6AFC2jkR2vHat+2/XcycuUY
++gn0oJMsXdKMdYV2ZZAMA3m3MSNjrXiDCYZohMr/+c8mmpJ5581LxedhpxfL86kSk5Nrp+gvU5LE
+YFiwzAJRGFuFjWJZY7attN6a+yb3ACfAXVU3dJnJUH/jWS5E4ywl7uxMMne0nxrpS10gxdr9HIcW
+xkPo1LsmmkVwXqkLN1PiRnsn/eBG8om3zEK2yygmbtmlyTrIQRNg91CMFa6ybRoVGld45pIq2WWQ
+gj9sAq+uEjonljYE1x2igGOpm/HlurR8FLBOybEfdF849lHqm/osohHUqS0nGkWxr7JOcQ3AWEbW
+aQbLU8uz/mtBzUF+fUwPfHJ5elnNXkoOrJupmHN5fLT0zLm4BwyydFy4x2+IoZCn9Kr5v2c69BoV
+Yh63n749sSmvZ6ES8lgQGVMDMBu4Gon2nL2XA46jCfMdiyHxtN/kHNGfZQIG6lzWE7OE76KlXIx3
+KadowGuuQNKotOrN8I1LOJwZmhsoVLiJkO/KdYE+HvJkJMcYr07/R54H9jVlpNMKVv/1F2Rs76gi
+JUmTtt8AF9pYfl3uxRuw0dFfIRDH+fO6AgonB8Xx1sfT4PsJYGw=
+-----END CERTIFICATE-----
+
+Amazon Root CA 3
+================
+-----BEGIN CERTIFICATE-----
+MIIBtjCCAVugAwIBAgITBmyf1XSXNmY/Owua2eiedgPySjAKBggqhkjOPQQDAjA5MQswCQYDVQQG
+EwJVUzEPMA0GA1UEChMGQW1hem9uMRkwFwYDVQQDExBBbWF6b24gUm9vdCBDQSAzMB4XDTE1MDUy
+NjAwMDAwMFoXDTQwMDUyNjAwMDAwMFowOTELMAkGA1UEBhMCVVMxDzANBgNVBAoTBkFtYXpvbjEZ
+MBcGA1UEAxMQQW1hem9uIFJvb3QgQ0EgMzBZMBMGByqGSM49AgEGCCqGSM49AwEHA0IABCmXp8ZB
+f8ANm+gBG1bG8lKlui2yEujSLtf6ycXYqm0fc4E7O5hrOXwzpcVOho6AF2hiRVd9RFgdszflZwjr
+Zt6jQjBAMA8GA1UdEwEB/wQFMAMBAf8wDgYDVR0PAQH/BAQDAgGGMB0GA1UdDgQWBBSrttvXBp43
+rDCGB5Fwx5zEGbF4wDAKBggqhkjOPQQDAgNJADBGAiEA4IWSoxe3jfkrBqWTrBqYaGFy+uGh0Psc
+eGCmQ5nFuMQCIQCcAu/xlJyzlvnrxir4tiz+OpAUFteMYyRIHN8wfdVoOw==
+-----END CERTIFICATE-----
+
+Amazon Root CA 4
+================
+-----BEGIN CERTIFICATE-----
+MIIB8jCCAXigAwIBAgITBmyf18G7EEwpQ+Vxe3ssyBrBDjAKBggqhkjOPQQDAzA5MQswCQYDVQQG
+EwJVUzEPMA0GA1UEChMGQW1hem9uMRkwFwYDVQQDExBBbWF6b24gUm9vdCBDQSA0MB4XDTE1MDUy
+NjAwMDAwMFoXDTQwMDUyNjAwMDAwMFowOTELMAkGA1UEBhMCVVMxDzANBgNVBAoTBkFtYXpvbjEZ
+MBcGA1UEAxMQQW1hem9uIFJvb3QgQ0EgNDB2MBAGByqGSM49AgEGBSuBBAAiA2IABNKrijdPo1MN
+/sGKe0uoe0ZLY7Bi9i0b2whxIdIA6GO9mif78DluXeo9pcmBqqNbIJhFXRbb/egQbeOc4OO9X4Ri
+83BkM6DLJC9wuoihKqB1+IGuYgbEgds5bimwHvouXKNCMEAwDwYDVR0TAQH/BAUwAwEB/zAOBgNV
+HQ8BAf8EBAMCAYYwHQYDVR0OBBYEFNPsxzplbszh2naaVvuc84ZtV+WBMAoGCCqGSM49BAMDA2gA
+MGUCMDqLIfG9fhGt0O9Yli/W651+kI0rz2ZVwyzjKKlwCkcO8DdZEv8tmZQoTipPNU0zWgIxAOp1
+AE47xDqUEpHJWEadIRNyp4iciuRMStuW1KyLa2tJElMzrdfkviT8tQp21KW8EA==
+-----END CERTIFICATE-----
+
+LuxTrust Global Root 2
+======================
+-----BEGIN CERTIFICATE-----
+MIIFwzCCA6ugAwIBAgIUCn6m30tEntpqJIWe5rgV0xZ/u7EwDQYJKoZIhvcNAQELBQAwRjELMAkG
+A1UEBhMCTFUxFjAUBgNVBAoMDUx1eFRydXN0IFMuQS4xHzAdBgNVBAMMFkx1eFRydXN0IEdsb2Jh
+bCBSb290IDIwHhcNMTUwMzA1MTMyMTU3WhcNMzUwMzA1MTMyMTU3WjBGMQswCQYDVQQGEwJMVTEW
+MBQGA1UECgwNTHV4VHJ1c3QgUy5BLjEfMB0GA1UEAwwWTHV4VHJ1c3QgR2xvYmFsIFJvb3QgMjCC
+AiIwDQYJKoZIhvcNAQEBBQADggIPADCCAgoCggIBANeFl78RmOnwYoNMPIf5U2o3C/IPPIfOb9wm
+Kb3FibrJgz337spbxm1Jc7TJRqMbNBM/wYlFV/TZsfs2ZUv7COJIcRHIbjuend+JZTemhfY7RBi2
+xjcwYkSSl2l9QjAk5A0MiWtj3sXh306pFGxT4GHO9hcvHTy95iJMHZP1EMShduxq3sVs35a0VkBC
+wGKSMKEtFZSg0iAGCW5qbeXrt77U8PEVfIvmTroTzEsnXpk8F12PgX8zPU/TPxvsXD/wPEx1bvKm
+1Z3aLQdjAsZy6ZS8TEmVT4hSyNvoaYL4zDRbIvCGp4m9SAptZoFtyMhk+wHh9OHe2Z7d21vUKpkm
+FRseTJIpgp7VkoGSQXAZ96Tlk0u8d2cx3Rz9MXANF5kM+Qw5GSoXtTBxVdUPrljhPS80m8+f9niF
+wpN6cj5mj5wWEWCPnolvZ77gR1o7DJpni89Gxq44o/KnvObWhWszJHAiS8sIm7vI+AIpHb4gDEa/
+a4ebsypmQjVGbKq6rfmYe+lQVRQxv7HaLe2ArWgk+2mr2HETMOZns4dA/Yl+8kPREd8vZS9kzl8U
+ubG/Mb2HeFpZZYiq/FkySIbWTLkpS5XTdvN3JW1CHDiDTf2jX5t/Lax5Gw5CMZdjpPuKadUiDTSQ
+MC6otOBttpSsvItO13D8xTiOZCXhTTmQzsmHhFhxAgMBAAGjgagwgaUwDwYDVR0TAQH/BAUwAwEB
+/zBCBgNVHSAEOzA5MDcGByuBKwEBAQowLDAqBggrBgEFBQcCARYeaHR0cHM6Ly9yZXBvc2l0b3J5
+Lmx1eHRydXN0Lmx1MA4GA1UdDwEB/wQEAwIBBjAfBgNVHSMEGDAWgBT/GCh2+UgFLKGu8SsbK7JT
++Et8szAdBgNVHQ4EFgQU/xgodvlIBSyhrvErGyuyU/hLfLMwDQYJKoZIhvcNAQELBQADggIBAGoZ
+FO1uecEsh9QNcH7X9njJCwROxLHOk3D+sFTAMs2ZMGQXvw/l4jP9BzZAcg4atmpZ1gDlaCDdLnIN
+H2pkMSCEfUmmWjfrRcmF9dTHF5kH5ptV5AzoqbTOjFu1EVzPig4N1qx3gf4ynCSecs5U89BvolbW
+7MM3LGVYvlcAGvI1+ut7MV3CwRI9loGIlonBWVx65n9wNOeD4rHh4bhY79SV5GCc8JaXcozrhAIu
+ZY+kt9J/Z93I055cqqmkoCUUBpvsT34tC38ddfEz2O3OuHVtPlu5mB0xDVbYQw8wkbIEa91WvpWA
+VWe+2M2D2RjuLg+GLZKecBPs3lHJQ3gCpU3I+V/EkVhGFndadKpAvAefMLmx9xIX3eP/JEAdemrR
+TxgKqpAd60Ae36EeRJIQmvKN4dFLRp7oRUKX6kWZ8+xm1QL68qZKJKrezrnK+T+Tb/mjuuqlPpmt
+/f97mfVl7vBZKGfXkJWkE4SphMHozs51k2MavDzq1WQfLSoSOcbDWjLtR5EWDrw4wVDej8oqkDQc
+7kGUnF4ZLvhFSZl0kbAEb+MEWrGrKqv+x9CWttrhSmQGbmBNvUJO/3jaJMobtNeWOWyu8Q6qp31I
+iyBMz2TWuJdGsE7RKlY6oJO9r4Ak4Ap+58rVyuiFVdw2KuGUaJPHZnJED4AhMmwlxyOAgwrr
+-----END CERTIFICATE-----
+
+TUBITAK Kamu SM SSL Kok Sertifikasi - Surum 1
+=============================================
+-----BEGIN CERTIFICATE-----
+MIIEYzCCA0ugAwIBAgIBATANBgkqhkiG9w0BAQsFADCB0jELMAkGA1UEBhMCVFIxGDAWBgNVBAcT
+D0dlYnplIC0gS29jYWVsaTFCMEAGA1UEChM5VHVya2l5ZSBCaWxpbXNlbCB2ZSBUZWtub2xvamlr
+IEFyYXN0aXJtYSBLdXJ1bXUgLSBUVUJJVEFLMS0wKwYDVQQLEyRLYW11IFNlcnRpZmlrYXN5b24g
+TWVya2V6aSAtIEthbXUgU00xNjA0BgNVBAMTLVRVQklUQUsgS2FtdSBTTSBTU0wgS29rIFNlcnRp
+ZmlrYXNpIC0gU3VydW0gMTAeFw0xMzExMjUwODI1NTVaFw00MzEwMjUwODI1NTVaMIHSMQswCQYD
+VQQGEwJUUjEYMBYGA1UEBxMPR2ViemUgLSBLb2NhZWxpMUIwQAYDVQQKEzlUdXJraXllIEJpbGlt
+c2VsIHZlIFRla25vbG9qaWsgQXJhc3Rpcm1hIEt1cnVtdSAtIFRVQklUQUsxLTArBgNVBAsTJEth
+bXUgU2VydGlmaWthc3lvbiBNZXJrZXppIC0gS2FtdSBTTTE2MDQGA1UEAxMtVFVCSVRBSyBLYW11
+IFNNIFNTTCBLb2sgU2VydGlmaWthc2kgLSBTdXJ1bSAxMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8A
+MIIBCgKCAQEAr3UwM6q7a9OZLBI3hNmNe5eA027n/5tQlT6QlVZC1xl8JoSNkvoBHToP4mQ4t4y8
+6Ij5iySrLqP1N+RAjhgleYN1Hzv/bKjFxlb4tO2KRKOrbEz8HdDc72i9z+SqzvBV96I01INrN3wc
+wv61A+xXzry0tcXtAA9TNypN9E8Mg/uGz8v+jE69h/mniyFXnHrfA2eJLJ2XYacQuFWQfw4tJzh0
+3+f92k4S400VIgLI4OD8D62K18lUUMw7D8oWgITQUVbDjlZ/iSIzL+aFCr2lqBs23tPcLG07xxO9
+WSMs5uWk99gL7eqQQESolbuT1dCANLZGeA4fAJNG4e7p+exPFwIDAQABo0IwQDAdBgNVHQ4EFgQU
+ZT/HiobGPN08VFw1+DrtUgxHV8gwDgYDVR0PAQH/BAQDAgEGMA8GA1UdEwEB/wQFMAMBAf8wDQYJ
+KoZIhvcNAQELBQADggEBACo/4fEyjq7hmFxLXs9rHmoJ0iKpEsdeV31zVmSAhHqT5Am5EM2fKifh
+AHe+SMg1qIGf5LgsyX8OsNJLN13qudULXjS99HMpw+0mFZx+CFOKWI3QSyjfwbPfIPP54+M638yc
+lNhOT8NrF7f3cuitZjO1JVOr4PhMqZ398g26rrnZqsZr+ZO7rqu4lzwDGrpDxpa5RXI4s6ehlj2R
+e37AIVNMh+3yC1SVUZPVIqUNivGTDj5UDrDYyU7c8jEyVupk+eq1nRZmQnLzf9OxMUP8pI4X8W0j
+q5Rm+K37DwhuJi1/FwcJsoz7UMCflo3Ptv0AnVoUmr8CRPXBwp8iXqIPoeM=
+-----END CERTIFICATE-----
-----BEGIN CERTIFICATE-----
MIIGCDCCA/CgAwIBAgIQKy5u6tl1NmwUim7bo3yMBzANBgkqhkiG9w0BAQwFADCB
hTELMAkGA1UEBhMCR0IxGzAZBgNVBAgTEkdyZWF0ZXIgTWFuY2hlc3RlcjEQMA4G
diff --git a/library/certs/cacert.pem b/library/certs/cacert.pem
index c15368bdc..8f1357b66 100644
--- a/library/certs/cacert.pem
+++ b/library/certs/cacert.pem
@@ -1,20 +1,20 @@
##
## Bundle of CA Root Certificates
##
-## Certificate data from Mozilla as of: Wed Apr 20 03:12:05 2016
+## Certificate data from Mozilla as of: Wed Jun 7 03:12:05 2017 GMT
##
## This is a bundle of X.509 certificates of public Certificate Authorities
## (CA). These were automatically extracted from Mozilla's root certificates
## file (certdata.txt). This file can be found in the mozilla source tree:
-## http://hg.mozilla.org/releases/mozilla-release/raw-file/default/security/nss/lib/ckfw/builtins/certdata.txt
+## https://hg.mozilla.org/releases/mozilla-release/raw-file/default/security/nss/lib/ckfw/builtins/certdata.txt
##
## It contains the certificates in PEM format and therefore
## can be directly used with curl / libcurl / php_curl, or with
## an Apache+mod_ssl webserver for SSL client authentication.
## Just configure this file as the SSLCACertificateFile.
##
-## Conversion done with mk-ca-bundle.pl version 1.25.
-## SHA1: 5df367cda83086392e1acdf22bfef00c48d5eba6
+## Conversion done with mk-ca-bundle.pl version 1.27.
+## SHA256: 93753268e1c596aee21893fb1c6975338389132f15c942ed65fc394a904371d7
##
@@ -252,27 +252,6 @@ W3iDVuycNsMm4hH2Z0kdkquM++v/eu6FSqdQgPCnXEqULl8FmTxSQeDNtGPPAUO6nIPcj2A781q0
tHuu2guQOHXvgR1m0vdXcDazv/wor3ElhVsT/h5/WrQ8
-----END CERTIFICATE-----
-RSA Security 2048 v3
-====================
------BEGIN CERTIFICATE-----
-MIIDYTCCAkmgAwIBAgIQCgEBAQAAAnwAAAAKAAAAAjANBgkqhkiG9w0BAQUFADA6MRkwFwYDVQQK
-ExBSU0EgU2VjdXJpdHkgSW5jMR0wGwYDVQQLExRSU0EgU2VjdXJpdHkgMjA0OCBWMzAeFw0wMTAy
-MjIyMDM5MjNaFw0yNjAyMjIyMDM5MjNaMDoxGTAXBgNVBAoTEFJTQSBTZWN1cml0eSBJbmMxHTAb
-BgNVBAsTFFJTQSBTZWN1cml0eSAyMDQ4IFYzMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKC
-AQEAt49VcdKA3XtpeafwGFAyPGJn9gqVB93mG/Oe2dJBVGutn3y+Gc37RqtBaB4Y6lXIL5F4iSj7
-Jylg/9+PjDvJSZu1pJTOAeo+tWN7fyb9Gd3AIb2E0S1PRsNO3Ng3OTsor8udGuorryGlwSMiuLgb
-WhOHV4PR8CDn6E8jQrAApX2J6elhc5SYcSa8LWrg903w8bYqODGBDSnhAMFRD0xS+ARaqn1y07iH
-KrtjEAMqs6FPDVpeRrc9DvV07Jmf+T0kgYim3WBU6JU2PcYJk5qjEoAAVZkZR73QpXzDuvsf9/UP
-+Ky5tfQ3mBMY3oVbtwyCO4dvlTlYMNpuAWgXIszACwIDAQABo2MwYTAPBgNVHRMBAf8EBTADAQH/
-MA4GA1UdDwEB/wQEAwIBBjAfBgNVHSMEGDAWgBQHw1EwpKrpRa41JPr/JCwz0LGdjDAdBgNVHQ4E
-FgQUB8NRMKSq6UWuNST6/yQsM9CxnYwwDQYJKoZIhvcNAQEFBQADggEBAF8+hnZuuDU8TjYcHnmY
-v/3VEhF5Ug7uMYm83X/50cYVIeiKAVQNOvtUudZj1LGqlk2iQk3UUx+LEN5/Zb5gEydxiKRz44Rj
-0aRV4VCT5hsOedBnvEbIvz8XDZXmxpBp3ue0L96VfdASPz0+f00/FGj1EVDVwfSQpQgdMWD/YIwj
-VAqv/qFuxdF6Kmh4zx6CCiC0H63lhbJqaHVOrSU3lIW+vaHU6rcMSzyd6BIA8F+sDeGscGNz9395
-nzIlQnQFgCi/vcEkllgVsRch6YlL2weIZ/QVrXA+L02FO8K32/6YaCOJ4XQP3vTFhGMpG8zLB8kA
-pKnXwiJPZ9d37CAFYd4=
------END CERTIFICATE-----
-
GeoTrust Global CA
==================
-----BEGIN CERTIFICATE-----
@@ -1241,33 +1220,6 @@ wKeI8lN3s2Berq4o2jUsbzRF0ybh3uxbTydrFny9RAQYgrOJeRcQcT16ohZO9QHNpGxlaKFJdlxD
ydi8NmdspZS11My5vWo1ViHe2MPr+8ukYEywVaCge1ey
-----END CERTIFICATE-----
-WellsSecure Public Root Certificate Authority
-=============================================
------BEGIN CERTIFICATE-----
-MIIEvTCCA6WgAwIBAgIBATANBgkqhkiG9w0BAQUFADCBhTELMAkGA1UEBhMCVVMxIDAeBgNVBAoM
-F1dlbGxzIEZhcmdvIFdlbGxzU2VjdXJlMRwwGgYDVQQLDBNXZWxscyBGYXJnbyBCYW5rIE5BMTYw
-NAYDVQQDDC1XZWxsc1NlY3VyZSBQdWJsaWMgUm9vdCBDZXJ0aWZpY2F0ZSBBdXRob3JpdHkwHhcN
-MDcxMjEzMTcwNzU0WhcNMjIxMjE0MDAwNzU0WjCBhTELMAkGA1UEBhMCVVMxIDAeBgNVBAoMF1dl
-bGxzIEZhcmdvIFdlbGxzU2VjdXJlMRwwGgYDVQQLDBNXZWxscyBGYXJnbyBCYW5rIE5BMTYwNAYD
-VQQDDC1XZWxsc1NlY3VyZSBQdWJsaWMgUm9vdCBDZXJ0aWZpY2F0ZSBBdXRob3JpdHkwggEiMA0G
-CSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDub7S9eeKPCCGeOARBJe+rWxxTkqxtnt3CxC5FlAM1
-iGd0V+PfjLindo8796jE2yljDpFoNoqXjopxaAkH5OjUDk/41itMpBb570OYj7OeUt9tkTmPOL13
-i0Nj67eT/DBMHAGTthP796EfvyXhdDcsHqRePGj4S78NuR4uNuip5Kf4D8uCdXw1LSLWwr8L87T8
-bJVhHlfXBIEyg1J55oNjz7fLY4sR4r1e6/aN7ZVyKLSsEmLpSjPmgzKuBXWVvYSV2ypcm44uDLiB
-K0HmOFafSZtsdvqKXfcBeYF8wYNABf5x/Qw/zE5gCQ5lRxAvAcAFP4/4s0HvWkJ+We/SlwxlAgMB
-AAGjggE0MIIBMDAPBgNVHRMBAf8EBTADAQH/MDkGA1UdHwQyMDAwLqAsoCqGKGh0dHA6Ly9jcmwu
-cGtpLndlbGxzZmFyZ28uY29tL3dzcHJjYS5jcmwwDgYDVR0PAQH/BAQDAgHGMB0GA1UdDgQWBBQm
-lRkQ2eihl5H/3BnZtQQ+0nMKajCBsgYDVR0jBIGqMIGngBQmlRkQ2eihl5H/3BnZtQQ+0nMKaqGB
-i6SBiDCBhTELMAkGA1UEBhMCVVMxIDAeBgNVBAoMF1dlbGxzIEZhcmdvIFdlbGxzU2VjdXJlMRww
-GgYDVQQLDBNXZWxscyBGYXJnbyBCYW5rIE5BMTYwNAYDVQQDDC1XZWxsc1NlY3VyZSBQdWJsaWMg
-Um9vdCBDZXJ0aWZpY2F0ZSBBdXRob3JpdHmCAQEwDQYJKoZIhvcNAQEFBQADggEBALkVsUSRzCPI
-K0134/iaeycNzXK7mQDKfGYZUMbVmO2rvwNa5U3lHshPcZeG1eMd/ZDJPHV3V3p9+N701NX3leZ0
-bh08rnyd2wIDBSxxSyU+B+NemvVmFymIGjifz6pBA4SXa5M4esowRBskRDPQ5NHcKDj0E0M1NSlj
-qHyita04pO2t/caaH/+Xc/77szWnk4bGdpEA5qxRFsQnMlzbc9qlk1eOPm01JghZ1edE13YgY+es
-E2fDbbFwRnzVlhE9iW9dqKHrjQrawx0zbKPqZxmamX9LPYNRKh3KL4YMon4QLSvUFpULB6ouFJJJ
-tylv2G0xffX8oRAHh84vWdw+WNs=
------END CERTIFICATE-----
-
COMODO ECC Certification Authority
==================================
-----BEGIN CERTIFICATE-----
@@ -1285,30 +1237,6 @@ FAkK+qDmfQjGGoe9GKhzvSbKYAydzpmfz1wPMOG+FDHqAjAU9JM8SaczepBGR7NjfRObTrdvGDeA
U/7dIOA1mjbRxwG55tzd8/8dLDoWV9mSOdY=
-----END CERTIFICATE-----
-IGC/A
-=====
------BEGIN CERTIFICATE-----
-MIIEAjCCAuqgAwIBAgIFORFFEJQwDQYJKoZIhvcNAQEFBQAwgYUxCzAJBgNVBAYTAkZSMQ8wDQYD
-VQQIEwZGcmFuY2UxDjAMBgNVBAcTBVBhcmlzMRAwDgYDVQQKEwdQTS9TR0ROMQ4wDAYDVQQLEwVE
-Q1NTSTEOMAwGA1UEAxMFSUdDL0ExIzAhBgkqhkiG9w0BCQEWFGlnY2FAc2dkbi5wbS5nb3V2LmZy
-MB4XDTAyMTIxMzE0MjkyM1oXDTIwMTAxNzE0MjkyMlowgYUxCzAJBgNVBAYTAkZSMQ8wDQYDVQQI
-EwZGcmFuY2UxDjAMBgNVBAcTBVBhcmlzMRAwDgYDVQQKEwdQTS9TR0ROMQ4wDAYDVQQLEwVEQ1NT
-STEOMAwGA1UEAxMFSUdDL0ExIzAhBgkqhkiG9w0BCQEWFGlnY2FAc2dkbi5wbS5nb3V2LmZyMIIB
-IjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAsh/R0GLFMzvABIaIs9z4iPf930Pfeo2aSVz2
-TqrMHLmh6yeJ8kbpO0px1R2OLc/mratjUMdUC24SyZA2xtgv2pGqaMVy/hcKshd+ebUyiHDKcMCW
-So7kVc0dJ5S/znIq7Fz5cyD+vfcuiWe4u0dzEvfRNWk68gq5rv9GQkaiv6GFGvm/5P9JhfejcIYy
-HF2fYPepraX/z9E0+X1bF8bc1g4oa8Ld8fUzaJ1O/Id8NhLWo4DoQw1VYZTqZDdH6nfK0LJYBcNd
-frGoRpAxVs5wKpayMLh35nnAvSk7/ZR3TL0gzUEl4C7HG7vupARB0l2tEmqKm0f7yd1GQOGdPDPQ
-tQIDAQABo3cwdTAPBgNVHRMBAf8EBTADAQH/MAsGA1UdDwQEAwIBRjAVBgNVHSAEDjAMMAoGCCqB
-egF5AQEBMB0GA1UdDgQWBBSjBS8YYFDCiQrdKyFP/45OqDAxNjAfBgNVHSMEGDAWgBSjBS8YYFDC
-iQrdKyFP/45OqDAxNjANBgkqhkiG9w0BAQUFAAOCAQEABdwm2Pp3FURo/C9mOnTgXeQp/wYHE4RK
-q89toB9RlPhJy3Q2FLwV3duJL92PoF189RLrn544pEfMs5bZvpwlqwN+Mw+VgQ39FuCIvjfwbF3Q
-MZsyK10XZZOYYLxuj7GoPB7ZHPOpJkL5ZB3C55L29B5aqhlSXa/oovdgoPaN8In1buAKBQGVyYsg
-Crpa/JosPL3Dt8ldeCUFP1YUmwza+zpI/pdpXsoQhvdOlgQITeywvl3cO45Pwf2aNjSaTFR+FwNI
-lQgRHAdvhQh+XU3Endv7rs6y0bO4g2wdsrN58dhwmX7wEwLOXt1R0982gaEbeC9xs/FZTEYYKKuF
-0mBWWg==
------END CERTIFICATE-----
-
Security Communication EV RootCA1
=================================
-----BEGIN CERTIFICATE-----
@@ -1353,46 +1281,6 @@ hNVQA7bihKOmNqoROgHhGEvWRGizPflTdISzRpFGlgC3gCy24eMQ4tui5yiPAZZiFj4A4xylNoEY
okxSdsARo27mHbrjWr42U8U+dY+GaSlYU7Wcu2+fXMUY7N0v4ZjJ/L7fCg0=
-----END CERTIFICATE-----
-Microsec e-Szigno Root CA
-=========================
------BEGIN CERTIFICATE-----
-MIIHqDCCBpCgAwIBAgIRAMy4579OKRr9otxmpRwsDxEwDQYJKoZIhvcNAQEFBQAwcjELMAkGA1UE
-BhMCSFUxETAPBgNVBAcTCEJ1ZGFwZXN0MRYwFAYDVQQKEw1NaWNyb3NlYyBMdGQuMRQwEgYDVQQL
-EwtlLVN6aWdubyBDQTEiMCAGA1UEAxMZTWljcm9zZWMgZS1Temlnbm8gUm9vdCBDQTAeFw0wNTA0
-MDYxMjI4NDRaFw0xNzA0MDYxMjI4NDRaMHIxCzAJBgNVBAYTAkhVMREwDwYDVQQHEwhCdWRhcGVz
-dDEWMBQGA1UEChMNTWljcm9zZWMgTHRkLjEUMBIGA1UECxMLZS1Temlnbm8gQ0ExIjAgBgNVBAMT
-GU1pY3Jvc2VjIGUtU3ppZ25vIFJvb3QgQ0EwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIB
-AQDtyADVgXvNOABHzNuEwSFpLHSQDCHZU4ftPkNEU6+r+ICbPHiN1I2uuO/TEdyB5s87lozWbxXG
-d36hL+BfkrYn13aaHUM86tnsL+4582pnS4uCzyL4ZVX+LMsvfUh6PXX5qqAnu3jCBspRwn5mS6/N
-oqdNAoI/gqyFxuEPkEeZlApxcpMqyabAvjxWTHOSJ/FrtfX9/DAFYJLG65Z+AZHCabEeHXtTRbjc
-QR/Ji3HWVBTji1R4P770Yjtb9aPs1ZJ04nQw7wHb4dSrmZsqa/i9phyGI0Jf7Enemotb9HI6QMVJ
-PqW+jqpx62z69Rrkav17fVVA71hu5tnVvCSrwe+3AgMBAAGjggQ3MIIEMzBnBggrBgEFBQcBAQRb
-MFkwKAYIKwYBBQUHMAGGHGh0dHBzOi8vcmNhLmUtc3ppZ25vLmh1L29jc3AwLQYIKwYBBQUHMAKG
-IWh0dHA6Ly93d3cuZS1zemlnbm8uaHUvUm9vdENBLmNydDAPBgNVHRMBAf8EBTADAQH/MIIBcwYD
-VR0gBIIBajCCAWYwggFiBgwrBgEEAYGoGAIBAQEwggFQMCgGCCsGAQUFBwIBFhxodHRwOi8vd3d3
-LmUtc3ppZ25vLmh1L1NaU1ovMIIBIgYIKwYBBQUHAgIwggEUHoIBEABBACAAdABhAG4A+gBzAO0A
-dAB2AOEAbgB5ACAA6QByAHQAZQBsAG0AZQB6AOkAcwDpAGgAZQB6ACAA6QBzACAAZQBsAGYAbwBn
-AGEAZADhAHMA4QBoAG8AegAgAGEAIABTAHoAbwBsAGcA4QBsAHQAYQB0APMAIABTAHoAbwBsAGcA
-4QBsAHQAYQB0AOEAcwBpACAAUwB6AGEAYgDhAGwAeQB6AGEAdABhACAAcwB6AGUAcgBpAG4AdAAg
-AGsAZQBsAGwAIABlAGwAagDhAHIAbgBpADoAIABoAHQAdABwADoALwAvAHcAdwB3AC4AZQAtAHMA
-egBpAGcAbgBvAC4AaAB1AC8AUwBaAFMAWgAvMIHIBgNVHR8EgcAwgb0wgbqggbeggbSGIWh0dHA6
-Ly93d3cuZS1zemlnbm8uaHUvUm9vdENBLmNybIaBjmxkYXA6Ly9sZGFwLmUtc3ppZ25vLmh1L0NO
-PU1pY3Jvc2VjJTIwZS1Temlnbm8lMjBSb290JTIwQ0EsT1U9ZS1Temlnbm8lMjBDQSxPPU1pY3Jv
-c2VjJTIwTHRkLixMPUJ1ZGFwZXN0LEM9SFU/Y2VydGlmaWNhdGVSZXZvY2F0aW9uTGlzdDtiaW5h
-cnkwDgYDVR0PAQH/BAQDAgEGMIGWBgNVHREEgY4wgYuBEGluZm9AZS1zemlnbm8uaHWkdzB1MSMw
-IQYDVQQDDBpNaWNyb3NlYyBlLVN6aWduw7MgUm9vdCBDQTEWMBQGA1UECwwNZS1TemlnbsOzIEhT
-WjEWMBQGA1UEChMNTWljcm9zZWMgS2Z0LjERMA8GA1UEBxMIQnVkYXBlc3QxCzAJBgNVBAYTAkhV
-MIGsBgNVHSMEgaQwgaGAFMegSXUWYYTbMUuE0vE3QJDvTtz3oXakdDByMQswCQYDVQQGEwJIVTER
-MA8GA1UEBxMIQnVkYXBlc3QxFjAUBgNVBAoTDU1pY3Jvc2VjIEx0ZC4xFDASBgNVBAsTC2UtU3pp
-Z25vIENBMSIwIAYDVQQDExlNaWNyb3NlYyBlLVN6aWdubyBSb290IENBghEAzLjnv04pGv2i3Gal
-HCwPETAdBgNVHQ4EFgQUx6BJdRZhhNsxS4TS8TdAkO9O3PcwDQYJKoZIhvcNAQEFBQADggEBANMT
-nGZjWS7KXHAM/IO8VbH0jgdsZifOwTsgqRy7RlRw7lrMoHfqaEQn6/Ip3Xep1fvj1KcExJW4C+FE
-aGAHQzAxQmHl7tnlJNUb3+FKG6qfx1/4ehHqE5MAyopYse7tDk2016g2JnzgOsHVV4Lxdbb9iV/a
-86g4nzUGCM4ilb7N1fy+W955a9x6qWVmvrElWl/tftOsRm1M9DKHtCAE4Gx4sHfRhUZLphK3dehK
-yVZs15KrnfVJONJPU+NVkBHbmJbGSfI+9J8b4PeI3CVimUTYc78/MPMMNz7UwiiAc7EBt51alhQB
-S6kRnSlqLtBdgcDPsiBDxwPgN05dCtxZICU=
------END CERTIFICATE-----
-
Certigna
========
-----BEGIN CERTIFICATE-----
@@ -1518,58 +1406,6 @@ LBOhgLJeDEoTniDYYkCrkOpkSi+sDQESeUWoL4cZaMjihccwsnX5OD+ywJO0a+IDRM5noN+J1q2M
dqMTw5RhK2vZbMEHCiIHhWyFJEapvj+LeISCfiQMnf2BN+MlqO02TpUsyZyQ2uypQjyttgI=
-----END CERTIFICATE-----
-Buypass Class 2 CA 1
-====================
------BEGIN CERTIFICATE-----
-MIIDUzCCAjugAwIBAgIBATANBgkqhkiG9w0BAQUFADBLMQswCQYDVQQGEwJOTzEdMBsGA1UECgwU
-QnV5cGFzcyBBUy05ODMxNjMzMjcxHTAbBgNVBAMMFEJ1eXBhc3MgQ2xhc3MgMiBDQSAxMB4XDTA2
-MTAxMzEwMjUwOVoXDTE2MTAxMzEwMjUwOVowSzELMAkGA1UEBhMCTk8xHTAbBgNVBAoMFEJ1eXBh
-c3MgQVMtOTgzMTYzMzI3MR0wGwYDVQQDDBRCdXlwYXNzIENsYXNzIDIgQ0EgMTCCASIwDQYJKoZI
-hvcNAQEBBQADggEPADCCAQoCggEBAIs8B0XY9t/mx8q6jUPFR42wWsE425KEHK8T1A9vNkYgxC7M
-cXA0ojTTNy7Y3Tp3L8DrKehc0rWpkTSHIln+zNvnma+WwajHQN2lFYxuyHyXA8vmIPLXl18xoS83
-0r7uvqmtqEyeIWZDO6i88wmjONVZJMHCR3axiFyCO7srpgTXjAePzdVBHfCuuCkslFJgNJQ72uA4
-0Z0zPhX0kzLFANq1KWYOOngPIVJfAuWSeyXTkh4vFZ2B5J2O6O+JzhRMVB0cgRJNcKi+EAUXfh/R
-uFdV7c27UsKwHnjCTTZoy1YmwVLBvXb3WNVyfh9EdrsAiR0WnVE1703CVu9r4Iw7DekCAwEAAaNC
-MEAwDwYDVR0TAQH/BAUwAwEB/zAdBgNVHQ4EFgQUP42aWYv8e3uco684sDntkHGA1sgwDgYDVR0P
-AQH/BAQDAgEGMA0GCSqGSIb3DQEBBQUAA4IBAQAVGn4TirnoB6NLJzKyQJHyIdFkhb5jatLPgcIV
-1Xp+DCmsNx4cfHZSldq1fyOhKXdlyTKdqC5Wq2B2zha0jX94wNWZUYN/Xtm+DKhQ7SLHrQVMdvvt
-7h5HZPb3J31cKA9FxVxiXqaakZG3Uxcu3K1gnZZkOb1naLKuBctN518fV4bVIJwo+28TOPX2EZL2
-fZleHwzoq0QkKXJAPTZSr4xYkHPB7GEseaHsh7U/2k3ZIQAw3pDaDtMaSKk+hQsUi4y8QZ5q9w5w
-wDX3OaJdZtB7WZ+oRxKaJyOkLY4ng5IgodcVf/EuGO70SH8vf/GhGLWhC5SgYiAynB321O+/TIho
------END CERTIFICATE-----
-
-EBG Elektronik Sertifika Hizmet Sa\xC4\x9Flay\xc4\xb1\x63\xc4\xb1s\xc4\xb1
-==========================================================================
------BEGIN CERTIFICATE-----
-MIIF5zCCA8+gAwIBAgIITK9zQhyOdAIwDQYJKoZIhvcNAQEFBQAwgYAxODA2BgNVBAMML0VCRyBF
-bGVrdHJvbmlrIFNlcnRpZmlrYSBIaXptZXQgU2HEn2xhecSxY8Sxc8SxMTcwNQYDVQQKDC5FQkcg
-QmlsacWfaW0gVGVrbm9sb2ppbGVyaSB2ZSBIaXptZXRsZXJpIEEuxZ4uMQswCQYDVQQGEwJUUjAe
-Fw0wNjA4MTcwMDIxMDlaFw0xNjA4MTQwMDMxMDlaMIGAMTgwNgYDVQQDDC9FQkcgRWxla3Ryb25p
-ayBTZXJ0aWZpa2EgSGl6bWV0IFNhxJ9sYXnEsWPEsXPEsTE3MDUGA1UECgwuRUJHIEJpbGnFn2lt
-IFRla25vbG9qaWxlcmkgdmUgSGl6bWV0bGVyaSBBLsWeLjELMAkGA1UEBhMCVFIwggIiMA0GCSqG
-SIb3DQEBAQUAA4ICDwAwggIKAoICAQDuoIRh0DpqZhAy2DE4f6en5f2h4fuXd7hxlugTlkaDT7by
-X3JWbhNgpQGR4lvFzVcfd2NR/y8927k/qqk153nQ9dAktiHq6yOU/im/+4mRDGSaBUorzAzu8T2b
-gmmkTPiab+ci2hC6X5L8GCcKqKpE+i4stPtGmggDg3KriORqcsnlZR9uKg+ds+g75AxuetpX/dfr
-eYteIAbTdgtsApWjluTLdlHRKJ2hGvxEok3MenaoDT2/F08iiFD9rrbskFBKW5+VQarKD7JK/oCZ
-TqNGFav4c0JqwmZ2sQomFd2TkuzbqV9UIlKRcF0T6kjsbgNs2d1s/OsNA/+mgxKb8amTD8UmTDGy
-Y5lhcucqZJnSuOl14nypqZoaqsNW2xCaPINStnuWt6yHd6i58mcLlEOzrz5z+kI2sSXFCjEmN1Zn
-uqMLfdb3ic1nobc6HmZP9qBVFCVMLDMNpkGMvQQxahByCp0OLna9XvNRiYuoP1Vzv9s6xiQFlpJI
-qkuNKgPlV5EQ9GooFW5Hd4RcUXSfGenmHmMWOeMRFeNYGkS9y8RsZteEBt8w9DeiQyJ50hBs37vm
-ExH8nYQKE3vwO9D8owrXieqWfo1IhR5kX9tUoqzVegJ5a9KK8GfaZXINFHDk6Y54jzJ0fFfy1tb0
-Nokb+Clsi7n2l9GkLqq+CxnCRelwXQIDAJ3Zo2MwYTAPBgNVHRMBAf8EBTADAQH/MA4GA1UdDwEB
-/wQEAwIBBjAdBgNVHQ4EFgQU587GT/wWZ5b6SqMHwQSny2re2kcwHwYDVR0jBBgwFoAU587GT/wW
-Z5b6SqMHwQSny2re2kcwDQYJKoZIhvcNAQEFBQADggIBAJuYml2+8ygjdsZs93/mQJ7ANtyVDR2t
-FcU22NU57/IeIl6zgrRdu0waypIN30ckHrMk2pGI6YNw3ZPX6bqz3xZaPt7gyPvT/Wwp+BVGoGgm
-zJNSroIBk5DKd8pNSe/iWtkqvTDOTLKBtjDOWU/aWR1qeqRFsIImgYZ29fUQALjuswnoT4cCB64k
-XPBfrAowzIpAoHMEwfuJJPaaHFy3PApnNgUIMbOv2AFoKuB4j3TeuFGkjGwgPaL7s9QJ/XvCgKqT
-bCmYIai7FvOpEl90tYeY8pUm3zTvilORiF0alKM/fCL414i6poyWqD1SNGKfAB5UVUJnxk1Gj7sU
-RT0KlhaOEKGXmdXTMIXM3rRyt7yKPBgpaP3ccQfuJDlq+u2lrDgv+R4QDgZxGhBM/nV+/x5XOULK
-1+EVoVZVWRvRo68R2E7DpSvvkL/A7IITW43WciyTTo9qKd+FPNMN4KIYEsxVL0e3p5sC/kH2iExt
-2qkBR4NkJ2IQgtYSe14DHzSpyZH+r11thie3I6p1GMog57AP14kOpmciY/SDQSsGS7tY1dHXt7kQ
-Y9iJSrSq3RZj9W6+YKH47ejWkE8axsWgKdOnIaj1Wjz3x0miIZpKlVIglnKaZsv30oZDfCK+lvm9
-AahH3eU7QPl1K5srRmSGjR70j/sHd9DqSaIcjVIUpgqT
------END CERTIFICATE-----
-
certSIGN ROOT CA
================
-----BEGIN CERTIFICATE-----
@@ -1611,28 +1447,6 @@ G8kS1sHNzYDzAgE8yGnLRUhj2JTQ7IUOO04RZfSCjKY9ri4ilAnIXOo8gV0WKgOXFlUJ24pBgp5m
mxE=
-----END CERTIFICATE-----
-ApplicationCA - Japanese Government
-===================================
------BEGIN CERTIFICATE-----
-MIIDoDCCAoigAwIBAgIBMTANBgkqhkiG9w0BAQUFADBDMQswCQYDVQQGEwJKUDEcMBoGA1UEChMT
-SmFwYW5lc2UgR292ZXJubWVudDEWMBQGA1UECxMNQXBwbGljYXRpb25DQTAeFw0wNzEyMTIxNTAw
-MDBaFw0xNzEyMTIxNTAwMDBaMEMxCzAJBgNVBAYTAkpQMRwwGgYDVQQKExNKYXBhbmVzZSBHb3Zl
-cm5tZW50MRYwFAYDVQQLEw1BcHBsaWNhdGlvbkNBMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIB
-CgKCAQEAp23gdE6Hj6UG3mii24aZS2QNcfAKBZuOquHMLtJqO8F6tJdhjYq+xpqcBrSGUeQ3DnR4
-fl+Kf5Sk10cI/VBaVuRorChzoHvpfxiSQE8tnfWuREhzNgaeZCw7NCPbXCbkcXmP1G55IrmTwcrN
-wVbtiGrXoDkhBFcsovW8R0FPXjQilbUfKW1eSvNNcr5BViCH/OlQR9cwFO5cjFW6WY2H/CPek9AE
-jP3vbb3QesmlOmpyM8ZKDQUXKi17safY1vC+9D/qDihtQWEjdnjDuGWk81quzMKq2edY3rZ+nYVu
-nyoKb58DKTCXKB28t89UKU5RMfkntigm/qJj5kEW8DOYRwIDAQABo4GeMIGbMB0GA1UdDgQWBBRU
-WssmP3HMlEYNllPqa0jQk/5CdTAOBgNVHQ8BAf8EBAMCAQYwWQYDVR0RBFIwUKROMEwxCzAJBgNV
-BAYTAkpQMRgwFgYDVQQKDA/ml6XmnKzlm73mlL/lupwxIzAhBgNVBAsMGuOCouODl+ODquOCseOD
-vOOCt+ODp+ODs0NBMA8GA1UdEwEB/wQFMAMBAf8wDQYJKoZIhvcNAQEFBQADggEBADlqRHZ3ODrs
-o2dGD/mLBqj7apAxzn7s2tGJfHrrLgy9mTLnsCTWw//1sogJhyzjVOGjprIIC8CFqMjSnHH2HZ9g
-/DgzE+Ge3Atf2hZQKXsvcJEPmbo0NI2VdMV+eKlmXb3KIXdCEKxmJj3ekav9FfBv7WxfEPjzFvYD
-io+nEhEMy/0/ecGc/WLuo89UDNErXxc+4z6/wCs+CZv+iKZ+tJIX/COUgb1up8WMwusRRdv4QcmW
-dupwX3kSa+SjB1oF7ydJzyGfikwJcGapJsErEU4z0g781mzSDjJkaP+tBXhfAx2o45CsJOAPQKdL
-rosot4LKGAfmt1t06SAZf7IbiVQ=
------END CERTIFICATE-----
-
GeoTrust Primary Certification Authority - G3
=============================================
-----BEGIN CERTIFICATE-----
@@ -1764,7 +1578,7 @@ AJw9SDkjOVgaFRJZap7v1VmyHVIsmXHNxynfGyphe3HR3vPA5Q06Sqotp9iGKt0uEA==
-----END CERTIFICATE-----
NetLock Arany (Class Gold) Főtanúsítvány
-============================================
+========================================
-----BEGIN CERTIFICATE-----
MIIEFTCCAv2gAwIBAgIGSUEs5AAQMA0GCSqGSIb3DQEBCwUAMIGnMQswCQYDVQQGEwJIVTERMA8G
A1UEBwwIQnVkYXBlc3QxFTATBgNVBAoMDE5ldExvY2sgS2Z0LjE3MDUGA1UECwwuVGFuw7pzw610
@@ -1819,34 +1633,6 @@ IPVVYpbtbZNQvOSqeK3Zywplh6ZmwcSBo3c6WB4L7oOLnR7SUqTMHW+wmG2UMbX4cQrcufx9MmDm
66+KAQ==
-----END CERTIFICATE-----
-Juur-SK
-=======
------BEGIN CERTIFICATE-----
-MIIE5jCCA86gAwIBAgIEO45L/DANBgkqhkiG9w0BAQUFADBdMRgwFgYJKoZIhvcNAQkBFglwa2lA
-c2suZWUxCzAJBgNVBAYTAkVFMSIwIAYDVQQKExlBUyBTZXJ0aWZpdHNlZXJpbWlza2Vza3VzMRAw
-DgYDVQQDEwdKdXVyLVNLMB4XDTAxMDgzMDE0MjMwMVoXDTE2MDgyNjE0MjMwMVowXTEYMBYGCSqG
-SIb3DQEJARYJcGtpQHNrLmVlMQswCQYDVQQGEwJFRTEiMCAGA1UEChMZQVMgU2VydGlmaXRzZWVy
-aW1pc2tlc2t1czEQMA4GA1UEAxMHSnV1ci1TSzCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoC
-ggEBAIFxNj4zB9bjMI0TfncyRsvPGbJgMUaXhvSYRqTCZUXP00B841oiqBB4M8yIsdOBSvZiF3tf
-TQou0M+LI+5PAk676w7KvRhj6IAcjeEcjT3g/1tf6mTll+g/mX8MCgkzABpTpyHhOEvWgxutr2TC
-+Rx6jGZITWYfGAriPrsfB2WThbkasLnE+w0R9vXW+RvHLCu3GFH+4Hv2qEivbDtPL+/40UceJlfw
-UR0zlv/vWT3aTdEVNMfqPxZIe5EcgEMPPbgFPtGzlc3Yyg/CQ2fbt5PgIoIuvvVoKIO5wTtpeyDa
-Tpxt4brNj3pssAki14sL2xzVWiZbDcDq5WDQn/413z8CAwEAAaOCAawwggGoMA8GA1UdEwEB/wQF
-MAMBAf8wggEWBgNVHSAEggENMIIBCTCCAQUGCisGAQQBzh8BAQEwgfYwgdAGCCsGAQUFBwICMIHD
-HoHAAFMAZQBlACAAcwBlAHIAdABpAGYAaQBrAGEAYQB0ACAAbwBuACAAdgDkAGwAagBhAHMAdABh
-AHQAdQBkACAAQQBTAC0AaQBzACAAUwBlAHIAdABpAGYAaQB0AHMAZQBlAHIAaQBtAGkAcwBrAGUA
-cwBrAHUAcwAgAGEAbABhAG0ALQBTAEsAIABzAGUAcgB0AGkAZgBpAGsAYQBhAHQAaQBkAGUAIABr
-AGkAbgBuAGkAdABhAG0AaQBzAGUAawBzMCEGCCsGAQUFBwIBFhVodHRwOi8vd3d3LnNrLmVlL2Nw
-cy8wKwYDVR0fBCQwIjAgoB6gHIYaaHR0cDovL3d3dy5zay5lZS9qdXVyL2NybC8wHQYDVR0OBBYE
-FASqekej5ImvGs8KQKcYP2/v6X2+MB8GA1UdIwQYMBaAFASqekej5ImvGs8KQKcYP2/v6X2+MA4G
-A1UdDwEB/wQEAwIB5jANBgkqhkiG9w0BAQUFAAOCAQEAe8EYlFOiCfP+JmeaUOTDBS8rNXiRTHyo
-ERF5TElZrMj3hWVcRrs7EKACr81Ptcw2Kuxd/u+gkcm2k298gFTsxwhwDY77guwqYHhpNjbRxZyL
-abVAyJRld/JXIWY7zoVAtjNjGr95HvxcHdMdkxuLDF2FvZkwMhgJkVLpfKG6/2SSmuz+Ne6ML678
-IIbsSt4beDI3poHSna9aEhbKmVv8b20OxaAehsmR0FyYgl9jDIpaq9iVpszLita/ZEuOyoqysOkh
-Mp6qqIWYNIE5ITuoOlIyPfZrN4YGWhWY3PARZv40ILcD9EEQfTmEeZZyY7aWAuVrua0ZTbvGRNs2
-yyqcjg==
------END CERTIFICATE-----
-
Hongkong Post Root CA 1
=======================
-----BEGIN CERTIFICATE-----
@@ -2280,7 +2066,7 @@ Zt3hrvJBW8qYVoNzcOSGGtIxQbovvi0TWnZvTuhOgQ4/WwMioBK+ZlgRSssDxLQqKi2WF+A5VLxI
-----END CERTIFICATE-----
Certinomis - Autorité Racine
-=============================
+============================
-----BEGIN CERTIFICATE-----
MIIFnDCCA4SgAwIBAgIBATANBgkqhkiG9w0BAQUFADBjMQswCQYDVQQGEwJGUjETMBEGA1UEChMK
Q2VydGlub21pczEXMBUGA1UECxMOMDAwMiA0MzM5OTg5MDMxJjAkBgNVBAMMHUNlcnRpbm9taXMg
@@ -2310,41 +2096,6 @@ wk01+dIL8hf2rGbVJLJP0RyZwG71fet0BLj5TXcJ17TPBzAJ8bgAVtkXFhYKK4bfjwEZGuW7gmP/
vgt2Fl43N+bYdJeimUV5
-----END CERTIFICATE-----
-Root CA Generalitat Valenciana
-==============================
------BEGIN CERTIFICATE-----
-MIIGizCCBXOgAwIBAgIEO0XlaDANBgkqhkiG9w0BAQUFADBoMQswCQYDVQQGEwJFUzEfMB0GA1UE
-ChMWR2VuZXJhbGl0YXQgVmFsZW5jaWFuYTEPMA0GA1UECxMGUEtJR1ZBMScwJQYDVQQDEx5Sb290
-IENBIEdlbmVyYWxpdGF0IFZhbGVuY2lhbmEwHhcNMDEwNzA2MTYyMjQ3WhcNMjEwNzAxMTUyMjQ3
-WjBoMQswCQYDVQQGEwJFUzEfMB0GA1UEChMWR2VuZXJhbGl0YXQgVmFsZW5jaWFuYTEPMA0GA1UE
-CxMGUEtJR1ZBMScwJQYDVQQDEx5Sb290IENBIEdlbmVyYWxpdGF0IFZhbGVuY2lhbmEwggEiMA0G
-CSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDGKqtXETcvIorKA3Qdyu0togu8M1JAJke+WmmmO3I2
-F0zo37i7L3bhQEZ0ZQKQUgi0/6iMweDHiVYQOTPvaLRfX9ptI6GJXiKjSgbwJ/BXufjpTjJ3Cj9B
-ZPPrZe52/lSqfR0grvPXdMIKX/UIKFIIzFVd0g/bmoGlu6GzwZTNVOAydTGRGmKy3nXiz0+J2ZGQ
-D0EbtFpKd71ng+CT516nDOeB0/RSrFOyA8dEJvt55cs0YFAQexvba9dHq198aMpunUEDEO5rmXte
-JajCq+TA81yc477OMUxkHl6AovWDfgzWyoxVjr7gvkkHD6MkQXpYHYTqWBLI4bft75PelAgxAgMB
-AAGjggM7MIIDNzAyBggrBgEFBQcBAQQmMCQwIgYIKwYBBQUHMAGGFmh0dHA6Ly9vY3NwLnBraS5n
-dmEuZXMwEgYDVR0TAQH/BAgwBgEB/wIBAjCCAjQGA1UdIASCAiswggInMIICIwYKKwYBBAG/VQIB
-ADCCAhMwggHoBggrBgEFBQcCAjCCAdoeggHWAEEAdQB0AG8AcgBpAGQAYQBkACAAZABlACAAQwBl
-AHIAdABpAGYAaQBjAGEAYwBpAPMAbgAgAFIAYQDtAHoAIABkAGUAIABsAGEAIABHAGUAbgBlAHIA
-YQBsAGkAdABhAHQAIABWAGEAbABlAG4AYwBpAGEAbgBhAC4ADQAKAEwAYQAgAEQAZQBjAGwAYQBy
-AGEAYwBpAPMAbgAgAGQAZQAgAFAAcgDhAGMAdABpAGMAYQBzACAAZABlACAAQwBlAHIAdABpAGYA
-aQBjAGEAYwBpAPMAbgAgAHEAdQBlACAAcgBpAGcAZQAgAGUAbAAgAGYAdQBuAGMAaQBvAG4AYQBt
-AGkAZQBuAHQAbwAgAGQAZQAgAGwAYQAgAHAAcgBlAHMAZQBuAHQAZQAgAEEAdQB0AG8AcgBpAGQA
-YQBkACAAZABlACAAQwBlAHIAdABpAGYAaQBjAGEAYwBpAPMAbgAgAHMAZQAgAGUAbgBjAHUAZQBu
-AHQAcgBhACAAZQBuACAAbABhACAAZABpAHIAZQBjAGMAaQDzAG4AIAB3AGUAYgAgAGgAdAB0AHAA
-OgAvAC8AdwB3AHcALgBwAGsAaQAuAGcAdgBhAC4AZQBzAC8AYwBwAHMwJQYIKwYBBQUHAgEWGWh0
-dHA6Ly93d3cucGtpLmd2YS5lcy9jcHMwHQYDVR0OBBYEFHs100DSHHgZZu90ECjcPk+yeAT8MIGV
-BgNVHSMEgY0wgYqAFHs100DSHHgZZu90ECjcPk+yeAT8oWykajBoMQswCQYDVQQGEwJFUzEfMB0G
-A1UEChMWR2VuZXJhbGl0YXQgVmFsZW5jaWFuYTEPMA0GA1UECxMGUEtJR1ZBMScwJQYDVQQDEx5S
-b290IENBIEdlbmVyYWxpdGF0IFZhbGVuY2lhbmGCBDtF5WgwDQYJKoZIhvcNAQEFBQADggEBACRh
-TvW1yEICKrNcda3FbcrnlD+laJWIwVTAEGmiEi8YPyVQqHxK6sYJ2fR1xkDar1CdPaUWu20xxsdz
-Ckj+IHLtb8zog2EWRpABlUt9jppSCS/2bxzkoXHPjCpaF3ODR00PNvsETUlR4hTJZGH71BTg9J63
-NI8KJr2XXPR5OkowGcytT6CYirQxlyric21+eLj4iIlPsSKRZEv1UN4D2+XFducTZnV+ZfsBn5OH
-iJ35Rld8TWCvmHMTI6QgkYH60GFmuH3Rr9ZvHmw96RH9qfmCIoaZM3Fa6hlXPZHNqcCjbgcTpsnt
-+GijnsNacgmHKNHEc8RzGF9QdRYxn7fofMM=
------END CERTIFICATE-----
-
TWCA Root Certification Authority
=================================
-----BEGIN CERTIFICATE-----
@@ -3675,7 +3426,7 @@ ekD6819kR5LLU7m7Wc5P/dAVUwHY3+vZ5nbv0CO7O6l5s9UCKc2Jo5YPSjXnTkLAdc0Hz+Ys63su
-----END CERTIFICATE-----
TÜRKTRUST Elektronik Sertifika Hizmet Sağlayıcısı H5
-=========================================================
+====================================================
-----BEGIN CERTIFICATE-----
MIIEJzCCAw+gAwIBAgIHAI4X/iQggTANBgkqhkiG9w0BAQsFADCBsTELMAkGA1UEBhMCVFIxDzAN
BgNVBAcMBkFua2FyYTFNMEsGA1UECgxEVMOcUktUUlVTVCBCaWxnaSDEsGxldGnFn2ltIHZlIEJp
@@ -3698,30 +3449,6 @@ lpKQd/Ct9JDpEXjXk4nAPQu6KfTomZ1yju2dL+6SfaHx/126M2CFYv4HAqGEVka+lgqaE9chTLd8
B59OTj+RdPsnnRHM3eaxynFNExc5JsUpISuTKWqW+qtB4Uu2NQvAmxU=
-----END CERTIFICATE-----
-TÜRKTRUST Elektronik Sertifika Hizmet Sağlayıcısı H6
-=========================================================
------BEGIN CERTIFICATE-----
-MIIEJjCCAw6gAwIBAgIGfaHyZeyKMA0GCSqGSIb3DQEBCwUAMIGxMQswCQYDVQQGEwJUUjEPMA0G
-A1UEBwwGQW5rYXJhMU0wSwYDVQQKDERUw5xSS1RSVVNUIEJpbGdpIMSwbGV0acWfaW0gdmUgQmls
-acWfaW0gR8O8dmVubGnEn2kgSGl6bWV0bGVyaSBBLsWeLjFCMEAGA1UEAww5VMOcUktUUlVTVCBF
-bGVrdHJvbmlrIFNlcnRpZmlrYSBIaXptZXQgU2HEn2xhecSxY8Sxc8SxIEg2MB4XDTEzMTIxODA5
-MDQxMFoXDTIzMTIxNjA5MDQxMFowgbExCzAJBgNVBAYTAlRSMQ8wDQYDVQQHDAZBbmthcmExTTBL
-BgNVBAoMRFTDnFJLVFJVU1QgQmlsZ2kgxLBsZXRpxZ9pbSB2ZSBCaWxpxZ9pbSBHw7x2ZW5sacSf
-aSBIaXptZXRsZXJpIEEuxZ4uMUIwQAYDVQQDDDlUw5xSS1RSVVNUIEVsZWt0cm9uaWsgU2VydGlm
-aWthIEhpem1ldCBTYcSfbGF5xLFjxLFzxLEgSDYwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEK
-AoIBAQCdsGjW6L0UlqMACprx9MfMkU1xeHe59yEmFXNRFpQJRwXiM/VomjX/3EsvMsew7eKC5W/a
-2uqsxgbPJQ1BgfbBOCK9+bGlprMBvD9QFyv26WZV1DOzXPhDIHiTVRZwGTLmiddk671IUP320EED
-wnS3/faAz1vFq6TWlRKb55cTMgPp1KtDWxbtMyJkKbbSk60vbNg9tvYdDjTu0n2pVQ8g9P0pu5Fb
-HH3GQjhtQiht1AH7zYiXSX6484P4tZgvsycLSF5W506jM7NE1qXyGJTtHB6plVxiSvgNZ1GpryHV
-+DKdeboaX+UEVU0TRv/yz3THGmNtwx8XEsMeED5gCLMxAgMBAAGjQjBAMB0GA1UdDgQWBBTdVRcT
-9qzoSCHK77Wv0QAy7Z6MtTAOBgNVHQ8BAf8EBAMCAQYwDwYDVR0TAQH/BAUwAwEB/zANBgkqhkiG
-9w0BAQsFAAOCAQEAb1gNl0OqFlQ+v6nfkkU/hQu7VtMMUszIv3ZnXuaqs6fvuay0EBQNdH49ba3R
-fdCaqaXKGDsCQC4qnFAUi/5XfldcEQlLNkVS9z2sFP1E34uXI9TDwe7UU5X+LEr+DXCqu4svLcsy
-o4LyVN/Y8t3XSHLuSqMplsNEzm61kod2pLv0kmzOLBQJZo6NrRa1xxsJYTvjIKIDgI6tflEATseW
-hvtDmHd9KMeP2Cpu54Rvl0EpABZeTeIT6lnAY2c6RPuY/ATTMHKm9ocJV612ph1jmv3XZch4gyt1
-O6VbuA1df74jrlZVlFjvH4GMKrLN5ptjnhi85WsGtAuYSyher4hYyw==
------END CERTIFICATE-----
-
Certinomis - Root CA
====================
-----BEGIN CERTIFICATE-----
@@ -3863,3 +3590,366 @@ ypnTycUm/Q1oBEauttmbjL4ZvrHG8hnjXALKLNhvSgfZyTXaQHXyxKcZb55CEJh15pWLYLztxRLX
is7VmFxWlgPF7ncGNf/P5O4/E2Hu29othfDNrp2yGAlFw5Khchf8R7agCyzxxN5DaAhqXzvwdmP7
zAYspsbiDrW5viSP
-----END CERTIFICATE-----
+
+Hellenic Academic and Research Institutions RootCA 2015
+=======================================================
+-----BEGIN CERTIFICATE-----
+MIIGCzCCA/OgAwIBAgIBADANBgkqhkiG9w0BAQsFADCBpjELMAkGA1UEBhMCR1IxDzANBgNVBAcT
+BkF0aGVuczFEMEIGA1UEChM7SGVsbGVuaWMgQWNhZGVtaWMgYW5kIFJlc2VhcmNoIEluc3RpdHV0
+aW9ucyBDZXJ0LiBBdXRob3JpdHkxQDA+BgNVBAMTN0hlbGxlbmljIEFjYWRlbWljIGFuZCBSZXNl
+YXJjaCBJbnN0aXR1dGlvbnMgUm9vdENBIDIwMTUwHhcNMTUwNzA3MTAxMTIxWhcNNDAwNjMwMTAx
+MTIxWjCBpjELMAkGA1UEBhMCR1IxDzANBgNVBAcTBkF0aGVuczFEMEIGA1UEChM7SGVsbGVuaWMg
+QWNhZGVtaWMgYW5kIFJlc2VhcmNoIEluc3RpdHV0aW9ucyBDZXJ0LiBBdXRob3JpdHkxQDA+BgNV
+BAMTN0hlbGxlbmljIEFjYWRlbWljIGFuZCBSZXNlYXJjaCBJbnN0aXR1dGlvbnMgUm9vdENBIDIw
+MTUwggIiMA0GCSqGSIb3DQEBAQUAA4ICDwAwggIKAoICAQDC+Kk/G4n8PDwEXT2QNrCROnk8Zlrv
+bTkBSRq0t89/TSNTt5AA4xMqKKYx8ZEA4yjsriFBzh/a/X0SWwGDD7mwX5nh8hKDgE0GPt+sr+eh
+iGsxr/CL0BgzuNtFajT0AoAkKAoCFZVedioNmToUW/bLy1O8E00BiDeUJRtCvCLYjqOWXjrZMts+
+6PAQZe104S+nfK8nNLspfZu2zwnI5dMK/IhlZXQK3HMcXM1AsRzUtoSMTFDPaI6oWa7CJ06CojXd
+FPQf/7J31Ycvqm59JCfnxssm5uX+Zwdj2EUN3TpZZTlYepKZcj2chF6IIbjV9Cz82XBST3i4vTwr
+i5WY9bPRaM8gFH5MXF/ni+X1NYEZN9cRCLdmvtNKzoNXADrDgfgXy5I2XdGj2HUb4Ysn6npIQf1F
+GQatJ5lOwXBH3bWfgVMS5bGMSF0xQxfjjMZ6Y5ZLKTBOhE5iGV48zpeQpX8B653g+IuJ3SWYPZK2
+fu/Z8VFRfS0myGlZYeCsargqNhEEelC9MoS+L9xy1dcdFkfkR2YgP/SWxa+OAXqlD3pk9Q0Yh9mu
+iNX6hME6wGkoLfINaFGq46V3xqSQDqE3izEjR8EJCOtu93ib14L8hCCZSRm2Ekax+0VVFqmjZayc
+Bw/qa9wfLgZy7IaIEuQt218FL+TwA9MmM+eAws1CoRc0CwIDAQABo0IwQDAPBgNVHRMBAf8EBTAD
+AQH/MA4GA1UdDwEB/wQEAwIBBjAdBgNVHQ4EFgQUcRVnyMjJvXVdctA4GGqd83EkVAswDQYJKoZI
+hvcNAQELBQADggIBAHW7bVRLqhBYRjTyYtcWNl0IXtVsyIe9tC5G8jH4fOpCtZMWVdyhDBKg2mF+
+D1hYc2Ryx+hFjtyp8iY/xnmMsVMIM4GwVhO+5lFc2JsKT0ucVlMC6U/2DWDqTUJV6HwbISHTGzrM
+d/K4kPFox/la/vot9L/J9UUbzjgQKjeKeaO04wlshYaT/4mWJ3iBj2fjRnRUjtkNaeJK9E10A/+y
+d+2VZ5fkscWrv2oj6NSU4kQoYsRL4vDY4ilrGnB+JGGTe08DMiUNRSQrlrRGar9KC/eaj8GsGsVn
+82800vpzY4zvFrCopEYq+OsS7HK07/grfoxSwIuEVPkvPuNVqNxmsdnhX9izjFk0WaSrT2y7Hxjb
+davYy5LNlDhhDgcGH0tGEPEVvo2FXDtKK4F5D7Rpn0lQl033DlZdwJVqwjbDG2jJ9SrcR5q+ss7F
+Jej6A7na+RZukYT1HCjI/CbM1xyQVqdfbzoEvM14iQuODy+jqk+iGxI9FghAD/FGTNeqewjBCvVt
+J94Cj8rDtSvK6evIIVM4pcw72Hc3MKJP2W/R8kCtQXoXxdZKNYm3QdV8hn9VTYNKpXMgwDqvkPGa
+JI7ZjnHKe7iG2rKPmT4dEw0SEe7Uq/DpFXYC5ODfqiAeW2GFZECpkJcNrVPSWh2HagCXZWK0vm9q
+p/UsQu0yrbYhnr68
+-----END CERTIFICATE-----
+
+Hellenic Academic and Research Institutions ECC RootCA 2015
+===========================================================
+-----BEGIN CERTIFICATE-----
+MIICwzCCAkqgAwIBAgIBADAKBggqhkjOPQQDAjCBqjELMAkGA1UEBhMCR1IxDzANBgNVBAcTBkF0
+aGVuczFEMEIGA1UEChM7SGVsbGVuaWMgQWNhZGVtaWMgYW5kIFJlc2VhcmNoIEluc3RpdHV0aW9u
+cyBDZXJ0LiBBdXRob3JpdHkxRDBCBgNVBAMTO0hlbGxlbmljIEFjYWRlbWljIGFuZCBSZXNlYXJj
+aCBJbnN0aXR1dGlvbnMgRUNDIFJvb3RDQSAyMDE1MB4XDTE1MDcwNzEwMzcxMloXDTQwMDYzMDEw
+MzcxMlowgaoxCzAJBgNVBAYTAkdSMQ8wDQYDVQQHEwZBdGhlbnMxRDBCBgNVBAoTO0hlbGxlbmlj
+IEFjYWRlbWljIGFuZCBSZXNlYXJjaCBJbnN0aXR1dGlvbnMgQ2VydC4gQXV0aG9yaXR5MUQwQgYD
+VQQDEztIZWxsZW5pYyBBY2FkZW1pYyBhbmQgUmVzZWFyY2ggSW5zdGl0dXRpb25zIEVDQyBSb290
+Q0EgMjAxNTB2MBAGByqGSM49AgEGBSuBBAAiA2IABJKgQehLgoRc4vgxEZmGZE4JJS+dQS8KrjVP
+dJWyUWRrjWvmP3CV8AVER6ZyOFB2lQJajq4onvktTpnvLEhvTCUp6NFxW98dwXU3tNf6e3pCnGoK
+Vlp8aQuqgAkkbH7BRqNCMEAwDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAQYwHQYDVR0O
+BBYEFLQiC4KZJAEOnLvkDv2/+5cgk5kqMAoGCCqGSM49BAMCA2cAMGQCMGfOFmI4oqxiRaeplSTA
+GiecMjvAwNW6qef4BENThe5SId6d9SWDPp5YSy/XZxMOIQIwBeF1Ad5o7SofTUwJCA3sS61kFyjn
+dc5FZXIhF8siQQ6ME5g4mlRtm8rifOoCWCKR
+-----END CERTIFICATE-----
+
+Certplus Root CA G1
+===================
+-----BEGIN CERTIFICATE-----
+MIIFazCCA1OgAwIBAgISESBVg+QtPlRWhS2DN7cs3EYRMA0GCSqGSIb3DQEBDQUAMD4xCzAJBgNV
+BAYTAkZSMREwDwYDVQQKDAhDZXJ0cGx1czEcMBoGA1UEAwwTQ2VydHBsdXMgUm9vdCBDQSBHMTAe
+Fw0xNDA1MjYwMDAwMDBaFw0zODAxMTUwMDAwMDBaMD4xCzAJBgNVBAYTAkZSMREwDwYDVQQKDAhD
+ZXJ0cGx1czEcMBoGA1UEAwwTQ2VydHBsdXMgUm9vdCBDQSBHMTCCAiIwDQYJKoZIhvcNAQEBBQAD
+ggIPADCCAgoCggIBANpQh7bauKk+nWT6VjOaVj0W5QOVsjQcmm1iBdTYj+eJZJ+622SLZOZ5KmHN
+r49aiZFluVj8tANfkT8tEBXgfs+8/H9DZ6itXjYj2JizTfNDnjl8KvzsiNWI7nC9hRYt6kuJPKNx
+Qv4c/dMcLRC4hlTqQ7jbxofaqK6AJc96Jh2qkbBIb6613p7Y1/oA/caP0FG7Yn2ksYyy/yARujVj
+BYZHYEMzkPZHogNPlk2dT8Hq6pyi/jQu3rfKG3akt62f6ajUeD94/vI4CTYd0hYCyOwqaK/1jpTv
+LRN6HkJKHRUxrgwEV/xhc/MxVoYxgKDEEW4wduOU8F8ExKyHcomYxZ3MVwia9Az8fXoFOvpHgDm2
+z4QTd28n6v+WZxcIbekN1iNQMLAVdBM+5S//Ds3EC0pd8NgAM0lm66EYfFkuPSi5YXHLtaW6uOrc
+4nBvCGrch2c0798wct3zyT8j/zXhviEpIDCB5BmlIOklynMxdCm+4kLV87ImZsdo/Rmz5yCTmehd
+4F6H50boJZwKKSTUzViGUkAksnsPmBIgJPaQbEfIDbsYIC7Z/fyL8inqh3SV4EJQeIQEQWGw9CEj
+jy3LKCHyamz0GqbFFLQ3ZU+V/YDI+HLlJWvEYLF7bY5KinPOWftwenMGE9nTdDckQQoRb5fc5+R+
+ob0V8rqHDz1oihYHAgMBAAGjYzBhMA4GA1UdDwEB/wQEAwIBBjAPBgNVHRMBAf8EBTADAQH/MB0G
+A1UdDgQWBBSowcCbkahDFXxdBie0KlHYlwuBsTAfBgNVHSMEGDAWgBSowcCbkahDFXxdBie0KlHY
+lwuBsTANBgkqhkiG9w0BAQ0FAAOCAgEAnFZvAX7RvUz1isbwJh/k4DgYzDLDKTudQSk0YcbX8ACh
+66Ryj5QXvBMsdbRX7gp8CXrc1cqh0DQT+Hern+X+2B50ioUHj3/MeXrKls3N/U/7/SMNkPX0XtPG
+YX2eEeAC7gkE2Qfdpoq3DIMku4NQkv5gdRE+2J2winq14J2by5BSS7CTKtQ+FjPlnsZlFT5kOwQ/
+2wyPX1wdaR+v8+khjPPvl/aatxm2hHSco1S1cE5j2FddUyGbQJJD+tZ3VTNPZNX70Cxqjm0lpu+F
+6ALEUz65noe8zDUa3qHpimOHZR4RKttjd5cUvpoUmRGywO6wT/gUITJDT5+rosuoD6o7BlXGEilX
+CNQ314cnrUlZp5GrRHpejXDbl85IULFzk/bwg2D5zfHhMf1bfHEhYxQUqq/F3pN+aLHsIqKqkHWe
+tUNy6mSjhEv9DKgma3GX7lZjZuhCVPnHHd/Qj1vfyDBviP4NxDMcU6ij/UgQ8uQKTuEVV/xuZDDC
+VRHc6qnNSlSsKWNEz0pAoNZoWRsz+e86i9sgktxChL8Bq4fA1SCC28a5g4VCXA9DO2pJNdWY9BW/
++mGBDAkgGNLQFwzLSABQ6XaCjGTXOqAHVcweMcDvOrRl++O/QmueD6i9a5jc2NvLi6Td11n0bt3+
+qsOR0C5CB8AMTVPNJLFMWx5R9N/pkvo=
+-----END CERTIFICATE-----
+
+Certplus Root CA G2
+===================
+-----BEGIN CERTIFICATE-----
+MIICHDCCAaKgAwIBAgISESDZkc6uo+jF5//pAq/Pc7xVMAoGCCqGSM49BAMDMD4xCzAJBgNVBAYT
+AkZSMREwDwYDVQQKDAhDZXJ0cGx1czEcMBoGA1UEAwwTQ2VydHBsdXMgUm9vdCBDQSBHMjAeFw0x
+NDA1MjYwMDAwMDBaFw0zODAxMTUwMDAwMDBaMD4xCzAJBgNVBAYTAkZSMREwDwYDVQQKDAhDZXJ0
+cGx1czEcMBoGA1UEAwwTQ2VydHBsdXMgUm9vdCBDQSBHMjB2MBAGByqGSM49AgEGBSuBBAAiA2IA
+BM0PW1aC3/BFGtat93nwHcmsltaeTpwftEIRyoa/bfuFo8XlGVzX7qY/aWfYeOKmycTbLXku54uN
+Am8xIk0G42ByRZ0OQneezs/lf4WbGOT8zC5y0xaTTsqZY1yhBSpsBqNjMGEwDgYDVR0PAQH/BAQD
+AgEGMA8GA1UdEwEB/wQFMAMBAf8wHQYDVR0OBBYEFNqDYwJ5jtpMxjwjFNiPwyCrKGBZMB8GA1Ud
+IwQYMBaAFNqDYwJ5jtpMxjwjFNiPwyCrKGBZMAoGCCqGSM49BAMDA2gAMGUCMHD+sAvZ94OX7PNV
+HdTcswYO/jOYnYs5kGuUIe22113WTNchp+e/IQ8rzfcq3IUHnQIxAIYUFuXcsGXCwI4Un78kFmjl
+vPl5adytRSv3tjFzzAalU5ORGpOucGpnutee5WEaXw==
+-----END CERTIFICATE-----
+
+OpenTrust Root CA G1
+====================
+-----BEGIN CERTIFICATE-----
+MIIFbzCCA1egAwIBAgISESCzkFU5fX82bWTCp59rY45nMA0GCSqGSIb3DQEBCwUAMEAxCzAJBgNV
+BAYTAkZSMRIwEAYDVQQKDAlPcGVuVHJ1c3QxHTAbBgNVBAMMFE9wZW5UcnVzdCBSb290IENBIEcx
+MB4XDTE0MDUyNjA4NDU1MFoXDTM4MDExNTAwMDAwMFowQDELMAkGA1UEBhMCRlIxEjAQBgNVBAoM
+CU9wZW5UcnVzdDEdMBsGA1UEAwwUT3BlblRydXN0IFJvb3QgQ0EgRzEwggIiMA0GCSqGSIb3DQEB
+AQUAA4ICDwAwggIKAoICAQD4eUbalsUwXopxAy1wpLuwxQjczeY1wICkES3d5oeuXT2R0odsN7fa
+Yp6bwiTXj/HbpqbfRm9RpnHLPhsxZ2L3EVs0J9V5ToybWL0iEA1cJwzdMOWo010hOHQX/uMftk87
+ay3bfWAfjH1MBcLrARYVmBSO0ZB3Ij/swjm4eTrwSSTilZHcYTSSjFR077F9jAHiOH3BX2pfJLKO
+YheteSCtqx234LSWSE9mQxAGFiQD4eCcjsZGT44ameGPuY4zbGneWK2gDqdkVBFpRGZPTBKnjix9
+xNRbxQA0MMHZmf4yzgeEtE7NCv82TWLxp2NX5Ntqp66/K7nJ5rInieV+mhxNaMbBGN4zK1FGSxyO
+9z0M+Yo0FMT7MzUj8czxKselu7Cizv5Ta01BG2Yospb6p64KTrk5M0ScdMGTHPjgniQlQ/GbI4Kq
+3ywgsNw2TgOzfALU5nsaqocTvz6hdLubDuHAk5/XpGbKuxs74zD0M1mKB3IDVedzagMxbm+WG+Oi
+n6+Sx+31QrclTDsTBM8clq8cIqPQqwWyTBIjUtz9GVsnnB47ev1CI9sjgBPwvFEVVJSmdz7QdFG9
+URQIOTfLHzSpMJ1ShC5VkLG631UAC9hWLbFJSXKAqWLXwPYYEQRVzXR7z2FwefR7LFxckvzluFqr
+TJOVoSfupb7PcSNCupt2LQIDAQABo2MwYTAOBgNVHQ8BAf8EBAMCAQYwDwYDVR0TAQH/BAUwAwEB
+/zAdBgNVHQ4EFgQUl0YhVyE12jZVx/PxN3DlCPaTKbYwHwYDVR0jBBgwFoAUl0YhVyE12jZVx/Px
+N3DlCPaTKbYwDQYJKoZIhvcNAQELBQADggIBAB3dAmB84DWn5ph76kTOZ0BP8pNuZtQ5iSas000E
+PLuHIT839HEl2ku6q5aCgZG27dmxpGWX4m9kWaSW7mDKHyP7Rbr/jyTwyqkxf3kfgLMtMrpkZ2Cv
+uVnN35pJ06iCsfmYlIrM4LvgBBuZYLFGZdwIorJGnkSI6pN+VxbSFXJfLkur1J1juONI5f6ELlgK
+n0Md/rcYkoZDSw6cMoYsYPXpSOqV7XAp8dUv/TW0V8/bhUiZucJvbI/NeJWsZCj9VrDDb8O+WVLh
+X4SPgPL0DTatdrOjteFkdjpY3H1PXlZs5VVZV6Xf8YpmMIzUUmI4d7S+KNfKNsSbBfD4Fdvb8e80
+nR14SohWZ25g/4/Ii+GOvUKpMwpZQhISKvqxnUOOBZuZ2mKtVzazHbYNeS2WuOvyDEsMpZTGMKcm
+GS3tTAZQMPH9WD25SxdfGbRqhFS0OE85og2WaMMolP3tLR9Ka0OWLpABEPs4poEL0L9109S5zvE/
+bw4cHjdx5RiHdRk/ULlepEU0rbDK5uUTdg8xFKmOLZTW1YVNcxVPS/KyPu1svf0OnWZzsD2097+o
+4BGkxK51CUpjAEggpsadCwmKtODmzj7HPiY46SvepghJAwSQiumPv+i2tCqjI40cHLI5kqiPAlxA
+OXXUc0ECd97N4EOH1uS6SsNsEn/+KuYj1oxx
+-----END CERTIFICATE-----
+
+OpenTrust Root CA G2
+====================
+-----BEGIN CERTIFICATE-----
+MIIFbzCCA1egAwIBAgISESChaRu/vbm9UpaPI+hIvyYRMA0GCSqGSIb3DQEBDQUAMEAxCzAJBgNV
+BAYTAkZSMRIwEAYDVQQKDAlPcGVuVHJ1c3QxHTAbBgNVBAMMFE9wZW5UcnVzdCBSb290IENBIEcy
+MB4XDTE0MDUyNjAwMDAwMFoXDTM4MDExNTAwMDAwMFowQDELMAkGA1UEBhMCRlIxEjAQBgNVBAoM
+CU9wZW5UcnVzdDEdMBsGA1UEAwwUT3BlblRydXN0IFJvb3QgQ0EgRzIwggIiMA0GCSqGSIb3DQEB
+AQUAA4ICDwAwggIKAoICAQDMtlelM5QQgTJT32F+D3Y5z1zCU3UdSXqWON2ic2rxb95eolq5cSG+
+Ntmh/LzubKh8NBpxGuga2F8ORAbtp+Dz0mEL4DKiltE48MLaARf85KxP6O6JHnSrT78eCbY2albz
+4e6WiWYkBuTNQjpK3eCasMSCRbP+yatcfD7J6xcvDH1urqWPyKwlCm/61UWY0jUJ9gNDlP7ZvyCV
+eYCYitmJNbtRG6Q3ffyZO6v/v6wNj0OxmXsWEH4db0fEFY8ElggGQgT4hNYdvJGmQr5J1WqIP7wt
+UdGejeBSzFfdNTVY27SPJIjki9/ca1TSgSuyzpJLHB9G+h3Ykst2Z7UJmQnlrBcUVXDGPKBWCgOz
+3GIZ38i1MH/1PCZ1Eb3XG7OHngevZXHloM8apwkQHZOJZlvoPGIytbU6bumFAYueQ4xncyhZW+vj
+3CzMpSZyYhK05pyDRPZRpOLAeiRXyg6lPzq1O4vldu5w5pLeFlwoW5cZJ5L+epJUzpM5ChaHvGOz
+9bGTXOBut9Dq+WIyiET7vycotjCVXRIouZW+j1MY5aIYFuJWpLIsEPUdN6b4t/bQWVyJ98LVtZR0
+0dX+G7bw5tYee9I8y6jj9RjzIR9u701oBnstXW5DiabA+aC/gh7PU3+06yzbXfZqfUAkBXKJOAGT
+y3HCOV0GEfZvePg3DTmEJwIDAQABo2MwYTAOBgNVHQ8BAf8EBAMCAQYwDwYDVR0TAQH/BAUwAwEB
+/zAdBgNVHQ4EFgQUajn6QiL35okATV59M4PLuG53hq8wHwYDVR0jBBgwFoAUajn6QiL35okATV59
+M4PLuG53hq8wDQYJKoZIhvcNAQENBQADggIBAJjLq0A85TMCl38th6aP1F5Kr7ge57tx+4BkJamz
+Gj5oXScmp7oq4fBXgwpkTx4idBvpkF/wrM//T2h6OKQQbA2xx6R3gBi2oihEdqc0nXGEL8pZ0keI
+mUEiyTCYYW49qKgFbdEfwFFEVn8nNQLdXpgKQuswv42hm1GqO+qTRmTFAHneIWv2V6CG1wZy7HBG
+S4tz3aAhdT7cHcCP009zHIXZ/n9iyJVvttN7jLpTwm+bREx50B1ws9efAvSyB7DH5fitIw6mVskp
+EndI2S9G/Tvw/HRwkqWOOAgfZDC2t0v7NqwQjqBSM2OdAzVWxWm9xiNaJ5T2pBL4LTM8oValX9YZ
+6e18CL13zSdkzJTaTkZQh+D5wVOAHrut+0dSixv9ovneDiK3PTNZbNTe9ZUGMg1RGUFcPk8G97kr
+gCf2o6p6fAbhQ8MTOWIaNr3gKC6UAuQpLmBVrkA9sHSSXvAgZJY/X0VdiLWK2gKgW0VU3jg9CcCo
+SmVGFvyqv1ROTVu+OEO3KMqLM6oaJbolXCkvW0pujOotnCr2BXbgd5eAiN1nE28daCSLT7d0geX0
+YJ96Vdc+N9oWaz53rK4YcJUIeSkDiv7BO7M/Gg+kO14fWKGVyasvc0rQLW6aWQ9VGHgtPFGml4vm
+u7JwqkwR3v98KzfUetF3NI/n+UL3PIEMS1IK
+-----END CERTIFICATE-----
+
+OpenTrust Root CA G3
+====================
+-----BEGIN CERTIFICATE-----
+MIICITCCAaagAwIBAgISESDm+Ez8JLC+BUCs2oMbNGA/MAoGCCqGSM49BAMDMEAxCzAJBgNVBAYT
+AkZSMRIwEAYDVQQKDAlPcGVuVHJ1c3QxHTAbBgNVBAMMFE9wZW5UcnVzdCBSb290IENBIEczMB4X
+DTE0MDUyNjAwMDAwMFoXDTM4MDExNTAwMDAwMFowQDELMAkGA1UEBhMCRlIxEjAQBgNVBAoMCU9w
+ZW5UcnVzdDEdMBsGA1UEAwwUT3BlblRydXN0IFJvb3QgQ0EgRzMwdjAQBgcqhkjOPQIBBgUrgQQA
+IgNiAARK7liuTcpm3gY6oxH84Bjwbhy6LTAMidnW7ptzg6kjFYwvWYpa3RTqnVkrQ7cG7DK2uu5B
+ta1doYXM6h0UZqNnfkbilPPntlahFVmhTzeXuSIevRHr9LIfXsMUmuXZl5mjYzBhMA4GA1UdDwEB
+/wQEAwIBBjAPBgNVHRMBAf8EBTADAQH/MB0GA1UdDgQWBBRHd8MUi2I5DMlv4VBN0BBY3JWIbTAf
+BgNVHSMEGDAWgBRHd8MUi2I5DMlv4VBN0BBY3JWIbTAKBggqhkjOPQQDAwNpADBmAjEAj6jcnboM
+BBf6Fek9LykBl7+BFjNAk2z8+e2AcG+qj9uEwov1NcoG3GRvaBbhj5G5AjEA2Euly8LQCGzpGPta
+3U1fJAuwACEl74+nBCZx4nxp5V2a+EEfOzmTk51V6s2N8fvB
+-----END CERTIFICATE-----
+
+ISRG Root X1
+============
+-----BEGIN CERTIFICATE-----
+MIIFazCCA1OgAwIBAgIRAIIQz7DSQONZRGPgu2OCiwAwDQYJKoZIhvcNAQELBQAwTzELMAkGA1UE
+BhMCVVMxKTAnBgNVBAoTIEludGVybmV0IFNlY3VyaXR5IFJlc2VhcmNoIEdyb3VwMRUwEwYDVQQD
+EwxJU1JHIFJvb3QgWDEwHhcNMTUwNjA0MTEwNDM4WhcNMzUwNjA0MTEwNDM4WjBPMQswCQYDVQQG
+EwJVUzEpMCcGA1UEChMgSW50ZXJuZXQgU2VjdXJpdHkgUmVzZWFyY2ggR3JvdXAxFTATBgNVBAMT
+DElTUkcgUm9vdCBYMTCCAiIwDQYJKoZIhvcNAQEBBQADggIPADCCAgoCggIBAK3oJHP0FDfzm54r
+Vygch77ct984kIxuPOZXoHj3dcKi/vVqbvYATyjb3miGbESTtrFj/RQSa78f0uoxmyF+0TM8ukj1
+3Xnfs7j/EvEhmkvBioZxaUpmZmyPfjxwv60pIgbz5MDmgK7iS4+3mX6UA5/TR5d8mUgjU+g4rk8K
+b4Mu0UlXjIB0ttov0DiNewNwIRt18jA8+o+u3dpjq+sWT8KOEUt+zwvo/7V3LvSye0rgTBIlDHCN
+Aymg4VMk7BPZ7hm/ELNKjD+Jo2FR3qyHB5T0Y3HsLuJvW5iB4YlcNHlsdu87kGJ55tukmi8mxdAQ
+4Q7e2RCOFvu396j3x+UCB5iPNgiV5+I3lg02dZ77DnKxHZu8A/lJBdiB3QW0KtZB6awBdpUKD9jf
+1b0SHzUvKBds0pjBqAlkd25HN7rOrFleaJ1/ctaJxQZBKT5ZPt0m9STJEadao0xAH0ahmbWnOlFu
+hjuefXKnEgV4We0+UXgVCwOPjdAvBbI+e0ocS3MFEvzG6uBQE3xDk3SzynTnjh8BCNAw1FtxNrQH
+usEwMFxIt4I7mKZ9YIqioymCzLq9gwQbooMDQaHWBfEbwrbwqHyGO0aoSCqI3Haadr8faqU9GY/r
+OPNk3sgrDQoo//fb4hVC1CLQJ13hef4Y53CIrU7m2Ys6xt0nUW7/vGT1M0NPAgMBAAGjQjBAMA4G
+A1UdDwEB/wQEAwIBBjAPBgNVHRMBAf8EBTADAQH/MB0GA1UdDgQWBBR5tFnme7bl5AFzgAiIyBpY
+9umbbjANBgkqhkiG9w0BAQsFAAOCAgEAVR9YqbyyqFDQDLHYGmkgJykIrGF1XIpu+ILlaS/V9lZL
+ubhzEFnTIZd+50xx+7LSYK05qAvqFyFWhfFQDlnrzuBZ6brJFe+GnY+EgPbk6ZGQ3BebYhtF8GaV
+0nxvwuo77x/Py9auJ/GpsMiu/X1+mvoiBOv/2X/qkSsisRcOj/KKNFtY2PwByVS5uCbMiogziUwt
+hDyC3+6WVwW6LLv3xLfHTjuCvjHIInNzktHCgKQ5ORAzI4JMPJ+GslWYHb4phowim57iaztXOoJw
+TdwJx4nLCgdNbOhdjsnvzqvHu7UrTkXWStAmzOVyyghqpZXjFaH3pO3JLF+l+/+sKAIuvtd7u+Nx
+e5AW0wdeRlN8NwdCjNPElpzVmbUq4JUagEiuTDkHzsxHpFKVK7q4+63SM1N95R1NbdWhscdCb+ZA
+JzVcoyi3B43njTOQ5yOf+1CceWxG1bQVs5ZufpsMljq4Ui0/1lvh+wjChP4kqKOJ2qxq4RgqsahD
+YVvTH9w7jXbyLeiNdd8XM2w9U/t7y0Ff/9yi0GE44Za4rF2LN9d11TPAmRGunUHBcnWEvgJBQl9n
+JEiU0Zsnvgc/ubhPgXRR4Xq37Z0j4r7g1SgEEzwxA57demyPxgcYxn/eR44/KJ4EBs+lVDR3veyJ
+m+kXQ99b21/+jh5Xos1AnX5iItreGCc=
+-----END CERTIFICATE-----
+
+AC RAIZ FNMT-RCM
+================
+-----BEGIN CERTIFICATE-----
+MIIFgzCCA2ugAwIBAgIPXZONMGc2yAYdGsdUhGkHMA0GCSqGSIb3DQEBCwUAMDsxCzAJBgNVBAYT
+AkVTMREwDwYDVQQKDAhGTk1ULVJDTTEZMBcGA1UECwwQQUMgUkFJWiBGTk1ULVJDTTAeFw0wODEw
+MjkxNTU5NTZaFw0zMDAxMDEwMDAwMDBaMDsxCzAJBgNVBAYTAkVTMREwDwYDVQQKDAhGTk1ULVJD
+TTEZMBcGA1UECwwQQUMgUkFJWiBGTk1ULVJDTTCCAiIwDQYJKoZIhvcNAQEBBQADggIPADCCAgoC
+ggIBALpxgHpMhm5/yBNtwMZ9HACXjywMI7sQmkCpGreHiPibVmr75nuOi5KOpyVdWRHbNi63URcf
+qQgfBBckWKo3Shjf5TnUV/3XwSyRAZHiItQDwFj8d0fsjz50Q7qsNI1NOHZnjrDIbzAzWHFctPVr
+btQBULgTfmxKo0nRIBnuvMApGGWn3v7v3QqQIecaZ5JCEJhfTzC8PhxFtBDXaEAUwED653cXeuYL
+j2VbPNmaUtu1vZ5Gzz3rkQUCwJaydkxNEJY7kvqcfw+Z374jNUUeAlz+taibmSXaXvMiwzn15Cou
+08YfxGyqxRxqAQVKL9LFwag0Jl1mpdICIfkYtwb1TplvqKtMUejPUBjFd8g5CSxJkjKZqLsXF3mw
+WsXmo8RZZUc1g16p6DULmbvkzSDGm0oGObVo/CK67lWMK07q87Hj/LaZmtVC+nFNCM+HHmpxffnT
+tOmlcYF7wk5HlqX2doWjKI/pgG6BU6VtX7hI+cL5NqYuSf+4lsKMB7ObiFj86xsc3i1w4peSMKGJ
+47xVqCfWS+2QrYv6YyVZLag13cqXM7zlzced0ezvXg5KkAYmY6252TUtB7p2ZSysV4999AeU14EC
+ll2jB0nVetBX+RvnU0Z1qrB5QstocQjpYL05ac70r8NWQMetUqIJ5G+GR4of6ygnXYMgrwTJbFaa
+i0b1AgMBAAGjgYMwgYAwDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAQYwHQYDVR0OBBYE
+FPd9xf3E6Jobd2Sn9R2gzL+HYJptMD4GA1UdIAQ3MDUwMwYEVR0gADArMCkGCCsGAQUFBwIBFh1o
+dHRwOi8vd3d3LmNlcnQuZm5tdC5lcy9kcGNzLzANBgkqhkiG9w0BAQsFAAOCAgEAB5BK3/MjTvDD
+nFFlm5wioooMhfNzKWtN/gHiqQxjAb8EZ6WdmF/9ARP67Jpi6Yb+tmLSbkyU+8B1RXxlDPiyN8+s
+D8+Nb/kZ94/sHvJwnvDKuO+3/3Y3dlv2bojzr2IyIpMNOmqOFGYMLVN0V2Ue1bLdI4E7pWYjJ2cJ
+j+F3qkPNZVEI7VFY/uY5+ctHhKQV8Xa7pO6kO8Rf77IzlhEYt8llvhjho6Tc+hj507wTmzl6NLrT
+Qfv6MooqtyuGC2mDOL7Nii4LcK2NJpLuHvUBKwrZ1pebbuCoGRw6IYsMHkCtA+fdZn71uSANA+iW
++YJF1DngoABd15jmfZ5nc8OaKveri6E6FO80vFIOiZiaBECEHX5FaZNXzuvO+FB8TxxuBEOb+dY7
+Ixjp6o7RTUaN8Tvkasq6+yO3m/qZASlaWFot4/nUbQ4mrcFuNLwy+AwF+mWj2zs3gyLp1txyM/1d
+8iC9djwj2ij3+RvrWWTV3F9yfiD8zYm1kGdNYno/Tq0dwzn+evQoFt9B9kiABdcPUXmsEKvU7ANm
+5mqwujGSQkBqvjrTcuFqN1W8rB2Vt2lh8kORdOag0wokRqEIr9baRRmW1FMdW4R58MD3R++Lj8UG
+rp1MYp3/RgT408m2ECVAdf4WqslKYIYvuu8wd+RU4riEmViAqhOLUTpPSPaLtrM=
+-----END CERTIFICATE-----
+
+Amazon Root CA 1
+================
+-----BEGIN CERTIFICATE-----
+MIIDQTCCAimgAwIBAgITBmyfz5m/jAo54vB4ikPmljZbyjANBgkqhkiG9w0BAQsFADA5MQswCQYD
+VQQGEwJVUzEPMA0GA1UEChMGQW1hem9uMRkwFwYDVQQDExBBbWF6b24gUm9vdCBDQSAxMB4XDTE1
+MDUyNjAwMDAwMFoXDTM4MDExNzAwMDAwMFowOTELMAkGA1UEBhMCVVMxDzANBgNVBAoTBkFtYXpv
+bjEZMBcGA1UEAxMQQW1hem9uIFJvb3QgQ0EgMTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoC
+ggEBALJ4gHHKeNXjca9HgFB0fW7Y14h29Jlo91ghYPl0hAEvrAIthtOgQ3pOsqTQNroBvo3bSMgH
+FzZM9O6II8c+6zf1tRn4SWiw3te5djgdYZ6k/oI2peVKVuRF4fn9tBb6dNqcmzU5L/qwIFAGbHrQ
+gLKm+a/sRxmPUDgH3KKHOVj4utWp+UhnMJbulHheb4mjUcAwhmahRWa6VOujw5H5SNz/0egwLX0t
+dHA114gk957EWW67c4cX8jJGKLhD+rcdqsq08p8kDi1L93FcXmn/6pUCyziKrlA4b9v7LWIbxcce
+VOF34GfID5yHI9Y/QCB/IIDEgEw+OyQmjgSubJrIqg0CAwEAAaNCMEAwDwYDVR0TAQH/BAUwAwEB
+/zAOBgNVHQ8BAf8EBAMCAYYwHQYDVR0OBBYEFIQYzIU07LwMlJQuCFmcx7IQTgoIMA0GCSqGSIb3
+DQEBCwUAA4IBAQCY8jdaQZChGsV2USggNiMOruYou6r4lK5IpDB/G/wkjUu0yKGX9rbxenDIU5PM
+CCjjmCXPI6T53iHTfIUJrU6adTrCC2qJeHZERxhlbI1Bjjt/msv0tadQ1wUsN+gDS63pYaACbvXy
+8MWy7Vu33PqUXHeeE6V/Uq2V8viTO96LXFvKWlJbYK8U90vvo/ufQJVtMVT8QtPHRh8jrdkPSHCa
+2XV4cdFyQzR1bldZwgJcJmApzyMZFo6IQ6XU5MsI+yMRQ+hDKXJioaldXgjUkK642M4UwtBV8ob2
+xJNDd2ZhwLnoQdeXeGADbkpyrqXRfboQnoZsG4q5WTP468SQvvG5
+-----END CERTIFICATE-----
+
+Amazon Root CA 2
+================
+-----BEGIN CERTIFICATE-----
+MIIFQTCCAymgAwIBAgITBmyf0pY1hp8KD+WGePhbJruKNzANBgkqhkiG9w0BAQwFADA5MQswCQYD
+VQQGEwJVUzEPMA0GA1UEChMGQW1hem9uMRkwFwYDVQQDExBBbWF6b24gUm9vdCBDQSAyMB4XDTE1
+MDUyNjAwMDAwMFoXDTQwMDUyNjAwMDAwMFowOTELMAkGA1UEBhMCVVMxDzANBgNVBAoTBkFtYXpv
+bjEZMBcGA1UEAxMQQW1hem9uIFJvb3QgQ0EgMjCCAiIwDQYJKoZIhvcNAQEBBQADggIPADCCAgoC
+ggIBAK2Wny2cSkxKgXlRmeyKy2tgURO8TW0G/LAIjd0ZEGrHJgw12MBvIITplLGbhQPDW9tK6Mj4
+kHbZW0/jTOgGNk3Mmqw9DJArktQGGWCsN0R5hYGCrVo34A3MnaZMUnbqQ523BNFQ9lXg1dKmSYXp
+N+nKfq5clU1Imj+uIFptiJXZNLhSGkOQsL9sBbm2eLfq0OQ6PBJTYv9K8nu+NQWpEjTj82R0Yiw9
+AElaKP4yRLuH3WUnAnE72kr3H9rN9yFVkE8P7K6C4Z9r2UXTu/Bfh+08LDmG2j/e7HJV63mjrdvd
+fLC6HM783k81ds8P+HgfajZRRidhW+mez/CiVX18JYpvL7TFz4QuK/0NURBs+18bvBt+xa47mAEx
+kv8LV/SasrlX6avvDXbR8O70zoan4G7ptGmh32n2M8ZpLpcTnqWHsFcQgTfJU7O7f/aS0ZzQGPSS
+btqDT6ZjmUyl+17vIWR6IF9sZIUVyzfpYgwLKhbcAS4y2j5L9Z469hdAlO+ekQiG+r5jqFoz7Mt0
+Q5X5bGlSNscpb/xVA1wf+5+9R+vnSUeVC06JIglJ4PVhHvG/LopyboBZ/1c6+XUyo05f7O0oYtlN
+c/LMgRdg7c3r3NunysV+Ar3yVAhU/bQtCSwXVEqY0VThUWcI0u1ufm8/0i2BWSlmy5A5lREedCf+
+3euvAgMBAAGjQjBAMA8GA1UdEwEB/wQFMAMBAf8wDgYDVR0PAQH/BAQDAgGGMB0GA1UdDgQWBBSw
+DPBMMPQFWAJI/TPlUq9LhONmUjANBgkqhkiG9w0BAQwFAAOCAgEAqqiAjw54o+Ci1M3m9Zh6O+oA
+A7CXDpO8Wqj2LIxyh6mx/H9z/WNxeKWHWc8w4Q0QshNabYL1auaAn6AFC2jkR2vHat+2/XcycuUY
++gn0oJMsXdKMdYV2ZZAMA3m3MSNjrXiDCYZohMr/+c8mmpJ5581LxedhpxfL86kSk5Nrp+gvU5LE
+YFiwzAJRGFuFjWJZY7attN6a+yb3ACfAXVU3dJnJUH/jWS5E4ywl7uxMMne0nxrpS10gxdr9HIcW
+xkPo1LsmmkVwXqkLN1PiRnsn/eBG8om3zEK2yygmbtmlyTrIQRNg91CMFa6ybRoVGld45pIq2WWQ
+gj9sAq+uEjonljYE1x2igGOpm/HlurR8FLBOybEfdF849lHqm/osohHUqS0nGkWxr7JOcQ3AWEbW
+aQbLU8uz/mtBzUF+fUwPfHJ5elnNXkoOrJupmHN5fLT0zLm4BwyydFy4x2+IoZCn9Kr5v2c69BoV
+Yh63n749sSmvZ6ES8lgQGVMDMBu4Gon2nL2XA46jCfMdiyHxtN/kHNGfZQIG6lzWE7OE76KlXIx3
+KadowGuuQNKotOrN8I1LOJwZmhsoVLiJkO/KdYE+HvJkJMcYr07/R54H9jVlpNMKVv/1F2Rs76gi
+JUmTtt8AF9pYfl3uxRuw0dFfIRDH+fO6AgonB8Xx1sfT4PsJYGw=
+-----END CERTIFICATE-----
+
+Amazon Root CA 3
+================
+-----BEGIN CERTIFICATE-----
+MIIBtjCCAVugAwIBAgITBmyf1XSXNmY/Owua2eiedgPySjAKBggqhkjOPQQDAjA5MQswCQYDVQQG
+EwJVUzEPMA0GA1UEChMGQW1hem9uMRkwFwYDVQQDExBBbWF6b24gUm9vdCBDQSAzMB4XDTE1MDUy
+NjAwMDAwMFoXDTQwMDUyNjAwMDAwMFowOTELMAkGA1UEBhMCVVMxDzANBgNVBAoTBkFtYXpvbjEZ
+MBcGA1UEAxMQQW1hem9uIFJvb3QgQ0EgMzBZMBMGByqGSM49AgEGCCqGSM49AwEHA0IABCmXp8ZB
+f8ANm+gBG1bG8lKlui2yEujSLtf6ycXYqm0fc4E7O5hrOXwzpcVOho6AF2hiRVd9RFgdszflZwjr
+Zt6jQjBAMA8GA1UdEwEB/wQFMAMBAf8wDgYDVR0PAQH/BAQDAgGGMB0GA1UdDgQWBBSrttvXBp43
+rDCGB5Fwx5zEGbF4wDAKBggqhkjOPQQDAgNJADBGAiEA4IWSoxe3jfkrBqWTrBqYaGFy+uGh0Psc
+eGCmQ5nFuMQCIQCcAu/xlJyzlvnrxir4tiz+OpAUFteMYyRIHN8wfdVoOw==
+-----END CERTIFICATE-----
+
+Amazon Root CA 4
+================
+-----BEGIN CERTIFICATE-----
+MIIB8jCCAXigAwIBAgITBmyf18G7EEwpQ+Vxe3ssyBrBDjAKBggqhkjOPQQDAzA5MQswCQYDVQQG
+EwJVUzEPMA0GA1UEChMGQW1hem9uMRkwFwYDVQQDExBBbWF6b24gUm9vdCBDQSA0MB4XDTE1MDUy
+NjAwMDAwMFoXDTQwMDUyNjAwMDAwMFowOTELMAkGA1UEBhMCVVMxDzANBgNVBAoTBkFtYXpvbjEZ
+MBcGA1UEAxMQQW1hem9uIFJvb3QgQ0EgNDB2MBAGByqGSM49AgEGBSuBBAAiA2IABNKrijdPo1MN
+/sGKe0uoe0ZLY7Bi9i0b2whxIdIA6GO9mif78DluXeo9pcmBqqNbIJhFXRbb/egQbeOc4OO9X4Ri
+83BkM6DLJC9wuoihKqB1+IGuYgbEgds5bimwHvouXKNCMEAwDwYDVR0TAQH/BAUwAwEB/zAOBgNV
+HQ8BAf8EBAMCAYYwHQYDVR0OBBYEFNPsxzplbszh2naaVvuc84ZtV+WBMAoGCCqGSM49BAMDA2gA
+MGUCMDqLIfG9fhGt0O9Yli/W651+kI0rz2ZVwyzjKKlwCkcO8DdZEv8tmZQoTipPNU0zWgIxAOp1
+AE47xDqUEpHJWEadIRNyp4iciuRMStuW1KyLa2tJElMzrdfkviT8tQp21KW8EA==
+-----END CERTIFICATE-----
+
+LuxTrust Global Root 2
+======================
+-----BEGIN CERTIFICATE-----
+MIIFwzCCA6ugAwIBAgIUCn6m30tEntpqJIWe5rgV0xZ/u7EwDQYJKoZIhvcNAQELBQAwRjELMAkG
+A1UEBhMCTFUxFjAUBgNVBAoMDUx1eFRydXN0IFMuQS4xHzAdBgNVBAMMFkx1eFRydXN0IEdsb2Jh
+bCBSb290IDIwHhcNMTUwMzA1MTMyMTU3WhcNMzUwMzA1MTMyMTU3WjBGMQswCQYDVQQGEwJMVTEW
+MBQGA1UECgwNTHV4VHJ1c3QgUy5BLjEfMB0GA1UEAwwWTHV4VHJ1c3QgR2xvYmFsIFJvb3QgMjCC
+AiIwDQYJKoZIhvcNAQEBBQADggIPADCCAgoCggIBANeFl78RmOnwYoNMPIf5U2o3C/IPPIfOb9wm
+Kb3FibrJgz337spbxm1Jc7TJRqMbNBM/wYlFV/TZsfs2ZUv7COJIcRHIbjuend+JZTemhfY7RBi2
+xjcwYkSSl2l9QjAk5A0MiWtj3sXh306pFGxT4GHO9hcvHTy95iJMHZP1EMShduxq3sVs35a0VkBC
+wGKSMKEtFZSg0iAGCW5qbeXrt77U8PEVfIvmTroTzEsnXpk8F12PgX8zPU/TPxvsXD/wPEx1bvKm
+1Z3aLQdjAsZy6ZS8TEmVT4hSyNvoaYL4zDRbIvCGp4m9SAptZoFtyMhk+wHh9OHe2Z7d21vUKpkm
+FRseTJIpgp7VkoGSQXAZ96Tlk0u8d2cx3Rz9MXANF5kM+Qw5GSoXtTBxVdUPrljhPS80m8+f9niF
+wpN6cj5mj5wWEWCPnolvZ77gR1o7DJpni89Gxq44o/KnvObWhWszJHAiS8sIm7vI+AIpHb4gDEa/
+a4ebsypmQjVGbKq6rfmYe+lQVRQxv7HaLe2ArWgk+2mr2HETMOZns4dA/Yl+8kPREd8vZS9kzl8U
+ubG/Mb2HeFpZZYiq/FkySIbWTLkpS5XTdvN3JW1CHDiDTf2jX5t/Lax5Gw5CMZdjpPuKadUiDTSQ
+MC6otOBttpSsvItO13D8xTiOZCXhTTmQzsmHhFhxAgMBAAGjgagwgaUwDwYDVR0TAQH/BAUwAwEB
+/zBCBgNVHSAEOzA5MDcGByuBKwEBAQowLDAqBggrBgEFBQcCARYeaHR0cHM6Ly9yZXBvc2l0b3J5
+Lmx1eHRydXN0Lmx1MA4GA1UdDwEB/wQEAwIBBjAfBgNVHSMEGDAWgBT/GCh2+UgFLKGu8SsbK7JT
++Et8szAdBgNVHQ4EFgQU/xgodvlIBSyhrvErGyuyU/hLfLMwDQYJKoZIhvcNAQELBQADggIBAGoZ
+FO1uecEsh9QNcH7X9njJCwROxLHOk3D+sFTAMs2ZMGQXvw/l4jP9BzZAcg4atmpZ1gDlaCDdLnIN
+H2pkMSCEfUmmWjfrRcmF9dTHF5kH5ptV5AzoqbTOjFu1EVzPig4N1qx3gf4ynCSecs5U89BvolbW
+7MM3LGVYvlcAGvI1+ut7MV3CwRI9loGIlonBWVx65n9wNOeD4rHh4bhY79SV5GCc8JaXcozrhAIu
+ZY+kt9J/Z93I055cqqmkoCUUBpvsT34tC38ddfEz2O3OuHVtPlu5mB0xDVbYQw8wkbIEa91WvpWA
+VWe+2M2D2RjuLg+GLZKecBPs3lHJQ3gCpU3I+V/EkVhGFndadKpAvAefMLmx9xIX3eP/JEAdemrR
+TxgKqpAd60Ae36EeRJIQmvKN4dFLRp7oRUKX6kWZ8+xm1QL68qZKJKrezrnK+T+Tb/mjuuqlPpmt
+/f97mfVl7vBZKGfXkJWkE4SphMHozs51k2MavDzq1WQfLSoSOcbDWjLtR5EWDrw4wVDej8oqkDQc
+7kGUnF4ZLvhFSZl0kbAEb+MEWrGrKqv+x9CWttrhSmQGbmBNvUJO/3jaJMobtNeWOWyu8Q6qp31I
+iyBMz2TWuJdGsE7RKlY6oJO9r4Ak4Ap+58rVyuiFVdw2KuGUaJPHZnJED4AhMmwlxyOAgwrr
+-----END CERTIFICATE-----
+
+TUBITAK Kamu SM SSL Kok Sertifikasi - Surum 1
+=============================================
+-----BEGIN CERTIFICATE-----
+MIIEYzCCA0ugAwIBAgIBATANBgkqhkiG9w0BAQsFADCB0jELMAkGA1UEBhMCVFIxGDAWBgNVBAcT
+D0dlYnplIC0gS29jYWVsaTFCMEAGA1UEChM5VHVya2l5ZSBCaWxpbXNlbCB2ZSBUZWtub2xvamlr
+IEFyYXN0aXJtYSBLdXJ1bXUgLSBUVUJJVEFLMS0wKwYDVQQLEyRLYW11IFNlcnRpZmlrYXN5b24g
+TWVya2V6aSAtIEthbXUgU00xNjA0BgNVBAMTLVRVQklUQUsgS2FtdSBTTSBTU0wgS29rIFNlcnRp
+ZmlrYXNpIC0gU3VydW0gMTAeFw0xMzExMjUwODI1NTVaFw00MzEwMjUwODI1NTVaMIHSMQswCQYD
+VQQGEwJUUjEYMBYGA1UEBxMPR2ViemUgLSBLb2NhZWxpMUIwQAYDVQQKEzlUdXJraXllIEJpbGlt
+c2VsIHZlIFRla25vbG9qaWsgQXJhc3Rpcm1hIEt1cnVtdSAtIFRVQklUQUsxLTArBgNVBAsTJEth
+bXUgU2VydGlmaWthc3lvbiBNZXJrZXppIC0gS2FtdSBTTTE2MDQGA1UEAxMtVFVCSVRBSyBLYW11
+IFNNIFNTTCBLb2sgU2VydGlmaWthc2kgLSBTdXJ1bSAxMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8A
+MIIBCgKCAQEAr3UwM6q7a9OZLBI3hNmNe5eA027n/5tQlT6QlVZC1xl8JoSNkvoBHToP4mQ4t4y8
+6Ij5iySrLqP1N+RAjhgleYN1Hzv/bKjFxlb4tO2KRKOrbEz8HdDc72i9z+SqzvBV96I01INrN3wc
+wv61A+xXzry0tcXtAA9TNypN9E8Mg/uGz8v+jE69h/mniyFXnHrfA2eJLJ2XYacQuFWQfw4tJzh0
+3+f92k4S400VIgLI4OD8D62K18lUUMw7D8oWgITQUVbDjlZ/iSIzL+aFCr2lqBs23tPcLG07xxO9
+WSMs5uWk99gL7eqQQESolbuT1dCANLZGeA4fAJNG4e7p+exPFwIDAQABo0IwQDAdBgNVHQ4EFgQU
+ZT/HiobGPN08VFw1+DrtUgxHV8gwDgYDVR0PAQH/BAQDAgEGMA8GA1UdEwEB/wQFMAMBAf8wDQYJ
+KoZIhvcNAQELBQADggEBACo/4fEyjq7hmFxLXs9rHmoJ0iKpEsdeV31zVmSAhHqT5Am5EM2fKifh
+AHe+SMg1qIGf5LgsyX8OsNJLN13qudULXjS99HMpw+0mFZx+CFOKWI3QSyjfwbPfIPP54+M638yc
+lNhOT8NrF7f3cuitZjO1JVOr4PhMqZ398g26rrnZqsZr+ZO7rqu4lzwDGrpDxpa5RXI4s6ehlj2R
+e37AIVNMh+3yC1SVUZPVIqUNivGTDj5UDrDYyU7c8jEyVupk+eq1nRZmQnLzf9OxMUP8pI4X8W0j
+q5Rm+K37DwhuJi1/FwcJsoz7UMCflo3Ptv0AnVoUmr8CRPXBwp8iXqIPoeM=
+-----END CERTIFICATE-----
diff --git a/library/emoji.json b/library/emoji.json
deleted file mode 100644
index dc28c13a1..000000000
--- a/library/emoji.json
+++ /dev/null
@@ -1 +0,0 @@
-{"grinning":{"unicode":"1f600","unicode_alternates":"","name":"grinning face","shortname":":grinning:","category":"people","emoji_order":"1","aliases":[],"aliases_ascii":[],"keywords":["happy","smiley","emotion","emotion"]},"grimacing":{"unicode":"1f62c","unicode_alternates":"","name":"grimacing face","shortname":":grimacing:","category":"people","emoji_order":"2","aliases":[],"aliases_ascii":[],"keywords":["silly","smiley","emotion","emotion","selfie","selfie"]},"grin":{"unicode":"1f601","unicode_alternates":"","name":"grinning face with smiling eyes","shortname":":grin:","category":"people","emoji_order":"3","aliases":[],"aliases_ascii":[],"keywords":["happy","silly","smiley","emotion","emotion","good","good","selfie","selfie"]},"joy":{"unicode":"1f602","unicode_alternates":"","name":"face with tears of joy","shortname":":joy:","category":"people","emoji_order":"4","aliases":[],"aliases_ascii":[":')",":'-)"],"keywords":["happy","silly","smiley","cry","laugh","laugh","emotion","emotion","sarcastic","sarcastic"]},"smiley":{"unicode":"1f603","unicode_alternates":"","name":"smiling face with open mouth","shortname":":smiley:","category":"people","emoji_order":"5","aliases":[],"aliases_ascii":[":D",":-D","=D"],"keywords":["happy","smiley","emotion","emotion","good","good"]},"smile":{"unicode":"1f604","unicode_alternates":"","name":"smiling face with open mouth and smiling eyes","shortname":":smile:","category":"people","emoji_order":"6","aliases":[],"aliases_ascii":[],"keywords":["happy","smiley","emotion","emotion"]},"sweat_smile":{"unicode":"1f605","unicode_alternates":"","name":"smiling face with open mouth and cold sweat","shortname":":sweat_smile:","category":"people","emoji_order":"7","aliases":[],"aliases_ascii":["':)","':-)","'=)","':D","':-D","'=D"],"keywords":["smiley","workout","sweat","emotion","emotion"]},"laughing":{"unicode":"1f606","unicode_alternates":"","name":"smiling face with open mouth and tightly-closed eyes","shortname":":laughing:","category":"people","emoji_order":"8","aliases":[":satisfied:"],"aliases_ascii":[">:)",">;)",">:-)",">=)"],"keywords":["happy","smiley","laugh","laugh","emotion","emotion"]},"innocent":{"unicode":"1f607","unicode_alternates":"","name":"smiling face with halo","shortname":":innocent:","category":"people","emoji_order":"9","aliases":[],"aliases_ascii":["O:-)","0:-3","0:3","0:-)","0:)","0;^)","O:)","O;-)","O=)","0;-)","O:-3","O:3"],"keywords":["smiley","emotion","emotion"]},"wink":{"unicode":"1f609","unicode_alternates":"","name":"winking face","shortname":":wink:","category":"people","emoji_order":"10","aliases":[],"aliases_ascii":[";)",";-)","*-)","*)",";-]",";]",";D",";^)"],"keywords":["silly","smiley","emotion","emotion"]},"blush":{"unicode":"1f60a","unicode_alternates":"","name":"smiling face with smiling eyes","shortname":":blush:","category":"people","emoji_order":"11","aliases":[],"aliases_ascii":[],"keywords":["happy","smiley","emotion","emotion","good","good","beautiful","beautiful"]},"slight_smile":{"unicode":"1f642","unicode_alternates":"","name":"slightly smiling face","shortname":":slight_smile:","category":"people","emoji_order":"12","aliases":[":slightly_smiling_face:"],"aliases_ascii":[":)",":-)","=]","=)",":]"],"keywords":["happy","smiley"]},"upside_down":{"unicode":"1f643","unicode_alternates":"","name":"upside-down face","shortname":":upside_down:","category":"people","emoji_order":"13","aliases":[":upside_down_face:"],"aliases_ascii":[],"keywords":["silly","smiley","sarcastic","sarcastic"]},"relaxed":{"unicode":"263a","unicode_alternates":"263a-fe0f","name":"white smiling face","shortname":":relaxed:","category":"people","emoji_order":"14","aliases":[],"aliases_ascii":[],"keywords":["happy","smiley"]},"yum":{"unicode":"1f60b","unicode_alternates":"","name":"face savouring delicious food","shortname":":yum:","category":"people","emoji_order":"15","aliases":[],"aliases_ascii":[],"keywords":["happy","silly","smiley","emotion","emotion","sarcastic","sarcastic","good","good"]},"relieved":{"unicode":"1f60c","unicode_alternates":"","name":"relieved face","shortname":":relieved:","category":"people","emoji_order":"16","aliases":[],"aliases_ascii":[],"keywords":["smiley","emotion","emotion"]},"heart_eyes":{"unicode":"1f60d","unicode_alternates":"","name":"smiling face with heart-shaped eyes","shortname":":heart_eyes:","category":"people","emoji_order":"17","aliases":[],"aliases_ascii":[],"keywords":["happy","smiley","love","sex","heart eyes","emotion","emotion","beautiful","beautiful"]},"kissing_heart":{"unicode":"1f618","unicode_alternates":"","name":"face throwing a kiss","shortname":":kissing_heart:","category":"people","emoji_order":"18","aliases":[],"aliases_ascii":[":*",":-*","=*",":^*"],"keywords":["smiley","love","sexy"]},"kissing":{"unicode":"1f617","unicode_alternates":"","name":"kissing face","shortname":":kissing:","category":"people","emoji_order":"19","aliases":[],"aliases_ascii":[],"keywords":["smiley","sexy"]},"kissing_smiling_eyes":{"unicode":"1f619","unicode_alternates":"","name":"kissing face with smiling eyes","shortname":":kissing_smiling_eyes:","category":"people","emoji_order":"20","aliases":[],"aliases_ascii":[],"keywords":["smiley","sexy"]},"kissing_closed_eyes":{"unicode":"1f61a","unicode_alternates":"","name":"kissing face with closed eyes","shortname":":kissing_closed_eyes:","category":"people","emoji_order":"21","aliases":[],"aliases_ascii":[],"keywords":["smiley","sexy"]},"stuck_out_tongue_winking_eye":{"unicode":"1f61c","unicode_alternates":"","name":"face with stuck-out tongue and winking eye","shortname":":stuck_out_tongue_winking_eye:","category":"people","emoji_order":"22","aliases":[],"aliases_ascii":[">:P","X-P","x-p"],"keywords":["happy","smiley","emotion","emotion","parties","parties"]},"stuck_out_tongue_closed_eyes":{"unicode":"1f61d","unicode_alternates":"","name":"face with stuck-out tongue and tightly-closed eyes","shortname":":stuck_out_tongue_closed_eyes:","category":"people","emoji_order":"23","aliases":[],"aliases_ascii":[],"keywords":["happy","smiley","emotion","emotion"]},"stuck_out_tongue":{"unicode":"1f61b","unicode_alternates":"","name":"face with stuck-out tongue","shortname":":stuck_out_tongue:","category":"people","emoji_order":"24","aliases":[],"aliases_ascii":[":P",":-P","=P",":-p",":p","=p",":-\u00de",":\u00de",":\u00fe",":-\u00fe",":-b",":b","d:"],"keywords":["smiley","sex","emotion","emotion"]},"money_mouth":{"unicode":"1f911","unicode_alternates":"","name":"money-mouth face","shortname":":money_mouth:","category":"people","emoji_order":"25","aliases":[":money_mouth_face:"],"aliases_ascii":[],"keywords":["smiley","win","win","money","money","emotion","emotion","boys night","boys night"]},"nerd":{"unicode":"1f913","unicode_alternates":"","name":"nerd face","shortname":":nerd:","category":"people","emoji_order":"26","aliases":[":nerd_face:"],"aliases_ascii":[],"keywords":["smiley","glasses"]},"sunglasses":{"unicode":"1f60e","unicode_alternates":"","name":"smiling face with sunglasses","shortname":":sunglasses:","category":"people","emoji_order":"27","aliases":[],"aliases_ascii":["B-)","B)","8)","8-)","B-D","8-D"],"keywords":["silly","smiley","emojione","glasses","boys night","boys night"]},"hugging":{"unicode":"1f917","unicode_alternates":"","name":"hugging face","shortname":":hugging:","category":"people","emoji_order":"28","aliases":[":hugging_face:"],"aliases_ascii":[],"keywords":["smiley","hug","thank you"]},"smirk":{"unicode":"1f60f","unicode_alternates":"","name":"smirking face","shortname":":smirk:","category":"people","emoji_order":"29","aliases":[],"aliases_ascii":[],"keywords":["silly","smiley","sexy","sarcastic","sarcastic"]},"no_mouth":{"unicode":"1f636","unicode_alternates":"","name":"face without mouth","shortname":":no_mouth:","category":"people","emoji_order":"30","aliases":[],"aliases_ascii":[":-X",":X",":-#",":#","=X","=x",":x",":-x","=#"],"keywords":["mad","smiley","neutral","emotion","emotion"]},"neutral_face":{"unicode":"1f610","unicode_alternates":"","name":"neutral face","shortname":":neutral_face:","category":"people","emoji_order":"31","aliases":[],"aliases_ascii":[],"keywords":["mad","smiley","shrug","neutral","emotion","emotion"]},"expressionless":{"unicode":"1f611","unicode_alternates":"","name":"expressionless face","shortname":":expressionless:","category":"people","emoji_order":"32","aliases":[],"aliases_ascii":["-_-","-__-","-___-"],"keywords":["mad","smiley","neutral","emotion","emotion"]},"unamused":{"unicode":"1f612","unicode_alternates":"","name":"unamused face","shortname":":unamused:","category":"people","emoji_order":"33","aliases":[],"aliases_ascii":[],"keywords":["sad","mad","smiley","tired","emotion","emotion"]},"rolling_eyes":{"unicode":"1f644","unicode_alternates":"","name":"face with rolling eyes","shortname":":rolling_eyes:","category":"people","emoji_order":"34","aliases":[":face_with_rolling_eyes:"],"aliases_ascii":[],"keywords":["mad","smiley","rolling eyes","emotion","emotion","sarcastic","sarcastic"]},"thinking":{"unicode":"1f914","unicode_alternates":"","name":"thinking face","shortname":":thinking:","category":"people","emoji_order":"35","aliases":[":thinking_face:"],"aliases_ascii":[],"keywords":["smiley","thinking","boys night","boys night"]},"flushed":{"unicode":"1f633","unicode_alternates":"","name":"flushed face","shortname":":flushed:","category":"people","emoji_order":"36","aliases":[],"aliases_ascii":[":$","=$"],"keywords":["smiley","emotion","emotion","omg","omg"]},"disappointed":{"unicode":"1f61e","unicode_alternates":"","name":"disappointed face","shortname":":disappointed:","category":"people","emoji_order":"37","aliases":[],"aliases_ascii":[">:[",":-(",":(",":-[",":[","=("],"keywords":["sad","smiley","tired","emotion","emotion"]},"worried":{"unicode":"1f61f","unicode_alternates":"","name":"worried face","shortname":":worried:","category":"people","emoji_order":"38","aliases":[],"aliases_ascii":[],"keywords":["sad","smiley","emotion","emotion"]},"angry":{"unicode":"1f620","unicode_alternates":"","name":"angry face","shortname":":angry:","category":"people","emoji_order":"39","aliases":[],"aliases_ascii":[">:(",">:-(",":@"],"keywords":["mad","smiley","emotion","emotion"]},"rage":{"unicode":"1f621","unicode_alternates":"","name":"pouting face","shortname":":rage:","category":"people","emoji_order":"40","aliases":[],"aliases_ascii":[],"keywords":["mad","smiley","angry","emotion","emotion"]},"pensive":{"unicode":"1f614","unicode_alternates":"","name":"pensive face","shortname":":pensive:","category":"people","emoji_order":"41","aliases":[],"aliases_ascii":[],"keywords":["sad","smiley","emotion","emotion","rip","rip"]},"confused":{"unicode":"1f615","unicode_alternates":"","name":"confused face","shortname":":confused:","category":"people","emoji_order":"42","aliases":[],"aliases_ascii":[">:\\",">:\/",":-\/",":-.",":\/",":\\","=\/","=\\",":L","=L"],"keywords":["smiley","surprised","emotion","emotion"]},"slight_frown":{"unicode":"1f641","unicode_alternates":"","name":"slightly frowning face","shortname":":slight_frown:","category":"people","emoji_order":"43","aliases":[":slightly_frowning_face:"],"aliases_ascii":[],"keywords":["sad","smiley","emotion","emotion"]},"frowning2":{"unicode":"2639","unicode_alternates":"2639-fe0f","name":"white frowning face","shortname":":frowning2:","category":"people","emoji_order":"44","aliases":[":white_frowning_face:"],"aliases_ascii":[],"keywords":["sad","smiley","emotion","emotion"]},"persevere":{"unicode":"1f623","unicode_alternates":"","name":"persevering face","shortname":":persevere:","category":"people","emoji_order":"45","aliases":[],"aliases_ascii":[">.<"],"keywords":["sad","smiley","angry","emotion","emotion"]},"confounded":{"unicode":"1f616","unicode_alternates":"","name":"confounded face","shortname":":confounded:","category":"people","emoji_order":"46","aliases":[],"aliases_ascii":[],"keywords":["sad","smiley","angry","emotion","emotion"]},"tired_face":{"unicode":"1f62b","unicode_alternates":"","name":"tired face","shortname":":tired_face:","category":"people","emoji_order":"47","aliases":[],"aliases_ascii":[],"keywords":["sad","smiley","tired","emotion","emotion"]},"weary":{"unicode":"1f629","unicode_alternates":"","name":"weary face","shortname":":weary:","category":"people","emoji_order":"48","aliases":[],"aliases_ascii":[],"keywords":["sad","smiley","tired","stressed","emotion","emotion"]},"triumph":{"unicode":"1f624","unicode_alternates":"","name":"face with look of triumph","shortname":":triumph:","category":"people","emoji_order":"49","aliases":[],"aliases_ascii":[],"keywords":["mad","smiley","angry","emotion","emotion","steam","steam"]},"open_mouth":{"unicode":"1f62e","unicode_alternates":"","name":"face with open mouth","shortname":":open_mouth:","category":"people","emoji_order":"50","aliases":[],"aliases_ascii":[":-O",":O",":-o",":o","O_O",">:O"],"keywords":["smiley","surprised","wow","wow","emotion","emotion"]},"scream":{"unicode":"1f631","unicode_alternates":"","name":"face screaming in fear","shortname":":scream:","category":"people","emoji_order":"51","aliases":[],"aliases_ascii":[],"keywords":["smiley","surprised","wow","wow","emotion","emotion","omg","omg"]},"fearful":{"unicode":"1f628","unicode_alternates":"","name":"fearful face","shortname":":fearful:","category":"people","emoji_order":"52","aliases":[],"aliases_ascii":["D:"],"keywords":["smiley","surprised","emotion","emotion"]},"cold_sweat":{"unicode":"1f630","unicode_alternates":"","name":"face with open mouth and cold sweat","shortname":":cold_sweat:","category":"people","emoji_order":"53","aliases":[],"aliases_ascii":[],"keywords":["smiley","sweat","emotion","emotion"]},"hushed":{"unicode":"1f62f","unicode_alternates":"","name":"hushed face","shortname":":hushed:","category":"people","emoji_order":"54","aliases":[],"aliases_ascii":[],"keywords":["smiley","surprised","wow","wow"]},"frowning":{"unicode":"1f626","unicode_alternates":"","name":"frowning face with open mouth","shortname":":frowning:","category":"people","emoji_order":"55","aliases":[],"aliases_ascii":[],"keywords":["sad","smiley","surprised","emotion","emotion"]},"anguished":{"unicode":"1f627","unicode_alternates":"","name":"anguished face","shortname":":anguished:","category":"people","emoji_order":"56","aliases":[],"aliases_ascii":[],"keywords":["sad","smiley","surprised","emotion","emotion"]},"cry":{"unicode":"1f622","unicode_alternates":"","name":"crying face","shortname":":cry:","category":"people","emoji_order":"57","aliases":[],"aliases_ascii":[":'(",":'-(",";(",";-("],"keywords":["sad","smiley","cry","emotion","emotion","rip","rip","heartbreak","heartbreak"]},"disappointed_relieved":{"unicode":"1f625","unicode_alternates":"","name":"disappointed but relieved face","shortname":":disappointed_relieved:","category":"people","emoji_order":"58","aliases":[],"aliases_ascii":[],"keywords":["sad","smiley","stressed","sweat","cry","emotion","emotion"]},"sleepy":{"unicode":"1f62a","unicode_alternates":"","name":"sleepy face","shortname":":sleepy:","category":"people","emoji_order":"59","aliases":[],"aliases_ascii":[],"keywords":["smiley","sick","emotion","emotion"]},"sweat":{"unicode":"1f613","unicode_alternates":"","name":"face with cold sweat","shortname":":sweat:","category":"people","emoji_order":"60","aliases":[],"aliases_ascii":["':(","':-(","'=("],"keywords":["sad","smiley","stressed","sweat","emotion","emotion"]},"sob":{"unicode":"1f62d","unicode_alternates":"","name":"loudly crying face","shortname":":sob:","category":"people","emoji_order":"61","aliases":[],"aliases_ascii":[],"keywords":["sad","smiley","cry","emotion","emotion","heartbreak","heartbreak"]},"dizzy_face":{"unicode":"1f635","unicode_alternates":"","name":"dizzy face","shortname":":dizzy_face:","category":"people","emoji_order":"62","aliases":[],"aliases_ascii":["#-)","#)","%-)","%)","X)","X-)"],"keywords":["smiley","surprised","dead","wow","wow","emotion","emotion","omg","omg"]},"astonished":{"unicode":"1f632","unicode_alternates":"","name":"astonished face","shortname":":astonished:","category":"people","emoji_order":"63","aliases":[],"aliases_ascii":[],"keywords":["smiley","surprised","wow","wow","emotion","emotion","omg","omg"]},"zipper_mouth":{"unicode":"1f910","unicode_alternates":"","name":"zipper-mouth face","shortname":":zipper_mouth:","category":"people","emoji_order":"64","aliases":[":zipper_mouth_face:"],"aliases_ascii":[],"keywords":["mad","smiley"]},"mask":{"unicode":"1f637","unicode_alternates":"","name":"face with medical mask","shortname":":mask:","category":"people","emoji_order":"65","aliases":[],"aliases_ascii":[],"keywords":["smiley","dead","health","sick"]},"thermometer_face":{"unicode":"1f912","unicode_alternates":"","name":"face with thermometer","shortname":":thermometer_face:","category":"people","emoji_order":"66","aliases":[":face_with_thermometer:"],"aliases_ascii":[],"keywords":["smiley","health","sick","emotion","emotion"]},"head_bandage":{"unicode":"1f915","unicode_alternates":"","name":"face with head-bandage","shortname":":head_bandage:","category":"people","emoji_order":"67","aliases":[":face_with_head_bandage:"],"aliases_ascii":[],"keywords":["smiley","health","sick","emotion","emotion"]},"sleeping":{"unicode":"1f634","unicode_alternates":"","name":"sleeping face","shortname":":sleeping:","category":"people","emoji_order":"68","aliases":[],"aliases_ascii":[],"keywords":["smiley","tired","emotion","emotion","goodnight","goodnight"]},"zzz":{"unicode":"1f4a4","unicode_alternates":"","name":"sleeping symbol","shortname":":zzz:","category":"people","emoji_order":"69","aliases":[],"aliases_ascii":[],"keywords":["tired","goodnight","goodnight"]},"poop":{"unicode":"1f4a9","unicode_alternates":"","name":"pile of poo","shortname":":poop:","category":"people","emoji_order":"70","aliases":[":shit:",":hankey:",":poo:"],"aliases_ascii":[],"keywords":["bathroom","shit","sol","sol","diarrhea","diarrhea"]},"smiling_imp":{"unicode":"1f608","unicode_alternates":"","name":"smiling face with horns","shortname":":smiling_imp:","category":"people","emoji_order":"71","aliases":[],"aliases_ascii":[],"keywords":["silly","smiley","angry","monster","devil","devil","boys night","boys night"]},"imp":{"unicode":"1f47f","unicode_alternates":"","name":"imp","shortname":":imp:","category":"people","emoji_order":"72","aliases":[],"aliases_ascii":[],"keywords":["smiley","monster","devil","devil","wth","wth"]},"japanese_ogre":{"unicode":"1f479","unicode_alternates":"","name":"japanese ogre","shortname":":japanese_ogre:","category":"people","emoji_order":"73","aliases":[],"aliases_ascii":[],"keywords":["monster"]},"japanese_goblin":{"unicode":"1f47a","unicode_alternates":"","name":"japanese goblin","shortname":":japanese_goblin:","category":"people","emoji_order":"74","aliases":[],"aliases_ascii":[],"keywords":["angry","monster"]},"skull":{"unicode":"1f480","unicode_alternates":"","name":"skull","shortname":":skull:","category":"people","emoji_order":"75","aliases":[":skeleton:"],"aliases_ascii":[],"keywords":["dead","halloween","skull"]},"ghost":{"unicode":"1f47b","unicode_alternates":"","name":"ghost","shortname":":ghost:","category":"people","emoji_order":"76","aliases":[],"aliases_ascii":[],"keywords":["holidays","halloween","monster"]},"alien":{"unicode":"1f47d","unicode_alternates":"","name":"extraterrestrial alien","shortname":":alien:","category":"people","emoji_order":"77","aliases":[],"aliases_ascii":[],"keywords":["space","monster","alien","scientology","scientology"]},"robot":{"unicode":"1f916","unicode_alternates":"","name":"robot face","shortname":":robot:","category":"people","emoji_order":"78","aliases":[":robot_face:"],"aliases_ascii":[],"keywords":["monster","robot"]},"smiley_cat":{"unicode":"1f63a","unicode_alternates":"","name":"smiling cat face with open mouth","shortname":":smiley_cat:","category":"people","emoji_order":"79","aliases":[],"aliases_ascii":[],"keywords":["happy","cat","cat","animal","animal"]},"smile_cat":{"unicode":"1f638","unicode_alternates":"","name":"grinning cat face with smiling eyes","shortname":":smile_cat:","category":"people","emoji_order":"80","aliases":[],"aliases_ascii":[],"keywords":["happy","cat","cat","animal","animal"]},"joy_cat":{"unicode":"1f639","unicode_alternates":"","name":"cat face with tears of joy","shortname":":joy_cat:","category":"people","emoji_order":"81","aliases":[],"aliases_ascii":[],"keywords":["happy","silly","cry","laugh","laugh","cat","cat","animal","animal","sarcastic","sarcastic"]},"heart_eyes_cat":{"unicode":"1f63b","unicode_alternates":"","name":"smiling cat face with heart-shaped eyes","shortname":":heart_eyes_cat:","category":"people","emoji_order":"82","aliases":[],"aliases_ascii":[],"keywords":["heart eyes","cat","cat","animal","animal","beautiful","beautiful"]},"smirk_cat":{"unicode":"1f63c","unicode_alternates":"","name":"cat face with wry smile","shortname":":smirk_cat:","category":"people","emoji_order":"83","aliases":[],"aliases_ascii":[],"keywords":["cat","cat","animal","animal"]},"kissing_cat":{"unicode":"1f63d","unicode_alternates":"","name":"kissing cat face with closed eyes","shortname":":kissing_cat:","category":"people","emoji_order":"84","aliases":[],"aliases_ascii":[],"keywords":["cat","cat","animal","animal"]},"scream_cat":{"unicode":"1f640","unicode_alternates":"","name":"weary cat face","shortname":":scream_cat:","category":"people","emoji_order":"85","aliases":[],"aliases_ascii":[],"keywords":["cat","cat","animal","animal"]},"crying_cat_face":{"unicode":"1f63f","unicode_alternates":"","name":"crying cat face","shortname":":crying_cat_face:","category":"people","emoji_order":"86","aliases":[],"aliases_ascii":[],"keywords":["cry","cat","cat","animal","animal"]},"pouting_cat":{"unicode":"1f63e","unicode_alternates":"","name":"pouting cat face","shortname":":pouting_cat:","category":"people","emoji_order":"87","aliases":[],"aliases_ascii":[],"keywords":["cat","cat","animal","animal"]},"raised_hands":{"unicode":"1f64c","unicode_alternates":"","name":"person raising both hands in celebration","shortname":":raised_hands:","category":"people","emoji_order":"88","aliases":[],"aliases_ascii":[],"keywords":["body","hands","diversity","diversity","perfect","perfect","good","good","parties","parties"]},"clap":{"unicode":"1f44f","unicode_alternates":"","name":"clapping hands sign","shortname":":clap:","category":"people","emoji_order":"89","aliases":[],"aliases_ascii":[],"keywords":["body","hands","win","win","diversity","diversity","good","good","beautiful","beautiful"]},"wave":{"unicode":"1f44b","unicode_alternates":"","name":"waving hand sign","shortname":":wave:","category":"people","emoji_order":"90","aliases":[],"aliases_ascii":[],"keywords":["body","hands","hi","diversity","diversity"]},"thumbsup":{"unicode":"1f44d","unicode_alternates":"","name":"thumbs up sign","shortname":":thumbsup:","category":"people","emoji_order":"91","aliases":[":+1:",":thumbup:"],"aliases_ascii":[],"keywords":["body","hands","hi","luck","thank you","diversity","diversity","perfect","perfect","good","good","beautiful","beautiful"]},"thumbsdown":{"unicode":"1f44e","unicode_alternates":"","name":"thumbs down sign","shortname":":thumbsdown:","category":"people","emoji_order":"92","aliases":[":-1:",":thumbdown:"],"aliases_ascii":[],"keywords":["body","hands","diversity","diversity"]},"punch":{"unicode":"1f44a","unicode_alternates":"","name":"fisted hand sign","shortname":":punch:","category":"people","emoji_order":"93","aliases":[],"aliases_ascii":[],"keywords":["body","hands","hi","fist bump","diversity","diversity","boys night","boys night"]},"fist":{"unicode":"270a","unicode_alternates":"","name":"raised fist","shortname":":fist:","category":"people","emoji_order":"94","aliases":[],"aliases_ascii":[],"keywords":["body","hands","hi","fist bump","diversity","diversity","condolence","condolence"]},"v":{"unicode":"270c","unicode_alternates":"270c-fe0f","name":"victory hand","shortname":":v:","category":"people","emoji_order":"95","aliases":[],"aliases_ascii":[],"keywords":["body","hands","hi","thank you","peace","peace","diversity","diversity","girls night","girls night"]},"ok_hand":{"unicode":"1f44c","unicode_alternates":"","name":"ok hand sign","shortname":":ok_hand:","category":"people","emoji_order":"96","aliases":[],"aliases_ascii":[],"keywords":["body","hands","hi","diversity","diversity","perfect","perfect","good","good","beautiful","beautiful"]},"raised_hand":{"unicode":"270b","unicode_alternates":"","name":"raised hand","shortname":":raised_hand:","category":"people","emoji_order":"97","aliases":[],"aliases_ascii":[],"keywords":["body","hands","hi","diversity","diversity","girls night","girls night"]},"open_hands":{"unicode":"1f450","unicode_alternates":"","name":"open hands sign","shortname":":open_hands:","category":"people","emoji_order":"98","aliases":[],"aliases_ascii":[],"keywords":["body","hands","diversity","diversity","condolence","condolence"]},"muscle":{"unicode":"1f4aa","unicode_alternates":"","name":"flexed biceps","shortname":":muscle:","category":"people","emoji_order":"99","aliases":[],"aliases_ascii":[],"keywords":["body","hands","workout","flex","win","win","diversity","diversity","feminist","feminist","boys night","boys night"]},"pray":{"unicode":"1f64f","unicode_alternates":"","name":"person with folded hands","shortname":":pray:","category":"people","emoji_order":"100","aliases":[],"aliases_ascii":[],"keywords":["body","hands","hi","luck","thank you","pray","pray","diversity","diversity","scientology","scientology"]},"point_up":{"unicode":"261d","unicode_alternates":"261d-fe0f","name":"white up pointing index","shortname":":point_up:","category":"people","emoji_order":"101","aliases":[],"aliases_ascii":[],"keywords":["body","hands","emojione","diversity","diversity"]},"point_up_2":{"unicode":"1f446","unicode_alternates":"","name":"white up pointing backhand index","shortname":":point_up_2:","category":"people","emoji_order":"102","aliases":[],"aliases_ascii":[],"keywords":["body","hands","diversity","diversity"]},"point_down":{"unicode":"1f447","unicode_alternates":"","name":"white down pointing backhand index","shortname":":point_down:","category":"people","emoji_order":"103","aliases":[],"aliases_ascii":[],"keywords":["body","hands","diversity","diversity"]},"point_left":{"unicode":"1f448","unicode_alternates":"","name":"white left pointing backhand index","shortname":":point_left:","category":"people","emoji_order":"104","aliases":[],"aliases_ascii":[],"keywords":["body","hands","hi","diversity","diversity"]},"point_right":{"unicode":"1f449","unicode_alternates":"","name":"white right pointing backhand index","shortname":":point_right:","category":"people","emoji_order":"105","aliases":[],"aliases_ascii":[],"keywords":["body","hands","hi","diversity","diversity"]},"middle_finger":{"unicode":"1f595","unicode_alternates":"","name":"reversed hand with middle finger extended","shortname":":middle_finger:","category":"people","emoji_order":"106","aliases":[":reversed_hand_with_middle_finger_extended:"],"aliases_ascii":[],"keywords":["body","hands","middle finger","diversity","diversity"]},"hand_splayed":{"unicode":"1f590","unicode_alternates":"1f590-fe0f","name":"raised hand with fingers splayed","shortname":":hand_splayed:","category":"people","emoji_order":"107","aliases":[":raised_hand_with_fingers_splayed:"],"aliases_ascii":[],"keywords":["body","hands","hi","diversity","diversity"]},"metal":{"unicode":"1f918","unicode_alternates":"","name":"sign of the horns","shortname":":metal:","category":"people","emoji_order":"108","aliases":[":sign_of_the_horns:"],"aliases_ascii":[],"keywords":["body","hands","hi","diversity","diversity","boys night","boys night","parties","parties"]},"vulcan":{"unicode":"1f596","unicode_alternates":"","name":"raised hand with part between middle and ring fingers","shortname":":vulcan:","category":"people","emoji_order":"109","aliases":[":raised_hand_with_part_between_middle_and_ring_fingers:"],"aliases_ascii":[],"keywords":["body","hands","hi","diversity","diversity"]},"writing_hand":{"unicode":"270d","unicode_alternates":"270d-fe0f","name":"writing hand","shortname":":writing_hand:","category":"people","emoji_order":"110","aliases":[],"aliases_ascii":[],"keywords":["body","hands","write","diversity","diversity"]},"nail_care":{"unicode":"1f485","unicode_alternates":"","name":"nail polish","shortname":":nail_care:","category":"people","emoji_order":"111","aliases":[],"aliases_ascii":[],"keywords":["women","body","hands","nailpolish","diversity","diversity","girls night","girls night"]},"lips":{"unicode":"1f444","unicode_alternates":"","name":"mouth","shortname":":lips:","category":"people","emoji_order":"112","aliases":[],"aliases_ascii":[],"keywords":["women","body","sexy","lip"]},"tongue":{"unicode":"1f445","unicode_alternates":"","name":"tongue","shortname":":tongue:","category":"people","emoji_order":"113","aliases":[],"aliases_ascii":[],"keywords":["body","sexy","lip"]},"ear":{"unicode":"1f442","unicode_alternates":"","name":"ear","shortname":":ear:","category":"people","emoji_order":"114","aliases":[],"aliases_ascii":[],"keywords":["body","diversity","diversity"]},"nose":{"unicode":"1f443","unicode_alternates":"","name":"nose","shortname":":nose:","category":"people","emoji_order":"115","aliases":[],"aliases_ascii":[],"keywords":["body","diversity","diversity"]},"eye":{"unicode":"1f441","unicode_alternates":"1f441-fe0f","name":"eye","shortname":":eye:","category":"people","emoji_order":"116","aliases":[],"aliases_ascii":[],"keywords":["body","eyes"]},"eyes":{"unicode":"1f440","unicode_alternates":"","name":"eyes","shortname":":eyes:","category":"people","emoji_order":"117","aliases":[],"aliases_ascii":[],"keywords":["body","eyes"]},"bust_in_silhouette":{"unicode":"1f464","unicode_alternates":"","name":"bust in silhouette","shortname":":bust_in_silhouette:","category":"people","emoji_order":"118","aliases":[],"aliases_ascii":[],"keywords":["people"]},"busts_in_silhouette":{"unicode":"1f465","unicode_alternates":"","name":"busts in silhouette","shortname":":busts_in_silhouette:","category":"people","emoji_order":"119","aliases":[],"aliases_ascii":[],"keywords":["people"]},"speaking_head":{"unicode":"1f5e3","unicode_alternates":"1f5e3-fe0f","name":"speaking head in silhouette","shortname":":speaking_head:","category":"people","emoji_order":"120","aliases":[":speaking_head_in_silhouette:"],"aliases_ascii":[],"keywords":["people","talk"]},"baby":{"unicode":"1f476","unicode_alternates":"","name":"baby","shortname":":baby:","category":"people","emoji_order":"121","aliases":[],"aliases_ascii":[],"keywords":["people","baby","diversity","diversity"]},"boy":{"unicode":"1f466","unicode_alternates":"","name":"boy","shortname":":boy:","category":"people","emoji_order":"122","aliases":[],"aliases_ascii":[],"keywords":["people","baby","diversity","diversity"]},"girl":{"unicode":"1f467","unicode_alternates":"","name":"girl","shortname":":girl:","category":"people","emoji_order":"123","aliases":[],"aliases_ascii":[],"keywords":["people","women","baby","diversity","diversity"]},"man":{"unicode":"1f468","unicode_alternates":"","name":"man","shortname":":man:","category":"people","emoji_order":"124","aliases":[],"aliases_ascii":[],"keywords":["people","men","sex","diversity","diversity","selfie","selfie","boys night","boys night"]},"woman":{"unicode":"1f469","unicode_alternates":"","name":"woman","shortname":":woman:","category":"people","emoji_order":"125","aliases":[],"aliases_ascii":[],"keywords":["people","women","sex","diversity","diversity","feminist","feminist","selfie","selfie","girls night","girls night"]},"person_with_blond_hair":{"unicode":"1f471","unicode_alternates":"","name":"person with blond hair","shortname":":person_with_blond_hair:","category":"people","emoji_order":"126","aliases":[],"aliases_ascii":[],"keywords":["people","men","diversity","diversity"]},"older_man":{"unicode":"1f474","unicode_alternates":"","name":"older man","shortname":":older_man:","category":"people","emoji_order":"127","aliases":[],"aliases_ascii":[],"keywords":["people","men","old people","diversity","diversity"]},"older_woman":{"unicode":"1f475","unicode_alternates":"","name":"older woman","shortname":":older_woman:","category":"people","emoji_order":"128","aliases":[":grandma:"],"aliases_ascii":[],"keywords":["people","old people","diversity","diversity"]},"man_with_gua_pi_mao":{"unicode":"1f472","unicode_alternates":"","name":"man with gua pi mao","shortname":":man_with_gua_pi_mao:","category":"people","emoji_order":"129","aliases":[],"aliases_ascii":[],"keywords":["people","hat","men","diversity","diversity"]},"man_with_turban":{"unicode":"1f473","unicode_alternates":"","name":"man with turban","shortname":":man_with_turban:","category":"people","emoji_order":"130","aliases":[],"aliases_ascii":[],"keywords":["people","hat","diversity","diversity"]},"cop":{"unicode":"1f46e","unicode_alternates":"","name":"police officer","shortname":":cop:","category":"people","emoji_order":"131","aliases":[],"aliases_ascii":[],"keywords":["people","hat","men","diversity","diversity","job","job","police","police","911","911"]},"construction_worker":{"unicode":"1f477","unicode_alternates":"","name":"construction worker","shortname":":construction_worker:","category":"people","emoji_order":"132","aliases":[],"aliases_ascii":[],"keywords":["people","hat","men","diversity","diversity","job","job"]},"guardsman":{"unicode":"1f482","unicode_alternates":"","name":"guardsman","shortname":":guardsman:","category":"people","emoji_order":"133","aliases":[],"aliases_ascii":[],"keywords":["people","hat","men","diversity","diversity","job","job"]},"spy":{"unicode":"1f575","unicode_alternates":"1f575-fe0f","name":"sleuth or spy","shortname":":spy:","category":"people","emoji_order":"134","aliases":[":sleuth_or_spy:"],"aliases_ascii":[],"keywords":["people","hat","men","glasses","diversity","diversity","job","job"]},"santa":{"unicode":"1f385","unicode_alternates":"","name":"father christmas","shortname":":santa:","category":"people","emoji_order":"135","aliases":[],"aliases_ascii":[],"keywords":["people","hat","winter","holidays","christmas","diversity","diversity","santa","santa"]},"angel":{"unicode":"1f47c","unicode_alternates":"","name":"baby angel","shortname":":angel:","category":"people","emoji_order":"136","aliases":[],"aliases_ascii":[],"keywords":["people","diversity","diversity","omg","omg"]},"princess":{"unicode":"1f478","unicode_alternates":"","name":"princess","shortname":":princess:","category":"people","emoji_order":"137","aliases":[],"aliases_ascii":[],"keywords":["people","women","diversity","diversity","beautiful","beautiful","girls night","girls night"]},"bride_with_veil":{"unicode":"1f470","unicode_alternates":"","name":"bride with veil","shortname":":bride_with_veil:","category":"people","emoji_order":"138","aliases":[],"aliases_ascii":[],"keywords":["people","wedding","women","diversity","diversity"]},"walking":{"unicode":"1f6b6","unicode_alternates":"","name":"pedestrian","shortname":":walking:","category":"people","emoji_order":"139","aliases":[],"aliases_ascii":[],"keywords":["people","men","diversity","diversity"]},"runner":{"unicode":"1f3c3","unicode_alternates":"","name":"runner","shortname":":runner:","category":"people","emoji_order":"140","aliases":[],"aliases_ascii":[],"keywords":["people","men","diversity","diversity","boys night","boys night","run","run"]},"dancer":{"unicode":"1f483","unicode_alternates":"","name":"dancer","shortname":":dancer:","category":"people","emoji_order":"141","aliases":[],"aliases_ascii":[],"keywords":["people","women","sexy","diversity","diversity","girls night","girls night","dance","dance"]},"dancers":{"unicode":"1f46f","unicode_alternates":"","name":"woman with bunny ears","shortname":":dancers:","category":"people","emoji_order":"142","aliases":[],"aliases_ascii":[],"keywords":["people","women","sexy","girls night","girls night","boys night","boys night","parties","parties","dance","dance"]},"couple":{"unicode":"1f46b","unicode_alternates":"","name":"man and woman holding hands","shortname":":couple:","category":"people","emoji_order":"143","aliases":[],"aliases_ascii":[],"keywords":["people","sex","creationism","creationism"]},"two_men_holding_hands":{"unicode":"1f46c","unicode_alternates":"","name":"two men holding hands","shortname":":two_men_holding_hands:","category":"people","emoji_order":"144","aliases":[],"aliases_ascii":[],"keywords":["people","gay","men","sex","lgbt","lgbt"]},"two_women_holding_hands":{"unicode":"1f46d","unicode_alternates":"","name":"two women holding hands","shortname":":two_women_holding_hands:","category":"people","emoji_order":"145","aliases":[],"aliases_ascii":[],"keywords":["people","women","sex","lgbt","lgbt","lesbian","lesbian","girls night","girls night"]},"bow":{"unicode":"1f647","unicode_alternates":"","name":"person bowing deeply","shortname":":bow:","category":"people","emoji_order":"146","aliases":[],"aliases_ascii":[],"keywords":["people","pray","pray","diversity","diversity"]},"information_desk_person":{"unicode":"1f481","unicode_alternates":"","name":"information desk person","shortname":":information_desk_person:","category":"people","emoji_order":"147","aliases":[],"aliases_ascii":[],"keywords":["people","women","diversity","diversity"]},"no_good":{"unicode":"1f645","unicode_alternates":"","name":"face with no good gesture","shortname":":no_good:","category":"people","emoji_order":"148","aliases":[],"aliases_ascii":[],"keywords":["people","women","diversity","diversity","girls night","girls night"]},"ok_woman":{"unicode":"1f646","unicode_alternates":"","name":"face with ok gesture","shortname":":ok_woman:","category":"people","emoji_order":"149","aliases":[],"aliases_ascii":["*\\0\/*","\\0\/","*\\O\/*","\\O\/"],"keywords":["people","women","diversity","diversity"]},"raising_hand":{"unicode":"1f64b","unicode_alternates":"","name":"happy person raising one hand","shortname":":raising_hand:","category":"people","emoji_order":"150","aliases":[],"aliases_ascii":[],"keywords":["people","women","diversity","diversity"]},"person_with_pouting_face":{"unicode":"1f64e","unicode_alternates":"","name":"person with pouting face","shortname":":person_with_pouting_face:","category":"people","emoji_order":"151","aliases":[],"aliases_ascii":[],"keywords":["people","women","diversity","diversity"]},"person_frowning":{"unicode":"1f64d","unicode_alternates":"","name":"person frowning","shortname":":person_frowning:","category":"people","emoji_order":"152","aliases":[],"aliases_ascii":[],"keywords":["people","women","diversity","diversity"]},"haircut":{"unicode":"1f487","unicode_alternates":"","name":"haircut","shortname":":haircut:","category":"people","emoji_order":"153","aliases":[],"aliases_ascii":[],"keywords":["people","women","diversity","diversity"]},"massage":{"unicode":"1f486","unicode_alternates":"","name":"face massage","shortname":":massage:","category":"people","emoji_order":"154","aliases":[],"aliases_ascii":[],"keywords":["people","women","diversity","diversity"]},"couple_with_heart":{"unicode":"1f491","unicode_alternates":"","name":"couple with heart","shortname":":couple_with_heart:","category":"people","emoji_order":"155","aliases":[],"aliases_ascii":[],"keywords":["people","love","sex"]},"couple_ww":{"unicode":"1f469-2764-1f469","unicode_alternates":"1f469-200d-2764-fe0f-200d-1f469","name":"couple (woman,woman)","shortname":":couple_ww:","category":"people","emoji_order":"156","aliases":[":couple_with_heart_ww:"],"aliases_ascii":[],"keywords":["people","women","love","sex","lgbt","lgbt"]},"couple_mm":{"unicode":"1f468-2764-1f468","unicode_alternates":"1f468-200d-2764-fe0f-200d-1f468","name":"couple (man,man)","shortname":":couple_mm:","category":"people","emoji_order":"157","aliases":[":couple_with_heart_mm:"],"aliases_ascii":[],"keywords":["people","gay","men","love","sex","lgbt","lgbt"]},"couplekiss":{"unicode":"1f48f","unicode_alternates":"","name":"kiss","shortname":":couplekiss:","category":"people","emoji_order":"158","aliases":[],"aliases_ascii":[],"keywords":["people","love","sex"]},"kiss_ww":{"unicode":"1f469-2764-1f48b-1f469","unicode_alternates":"1f469-200d-2764-fe0f-200d-1f48b-200d-1f469","name":"kiss (woman,woman)","shortname":":kiss_ww:","category":"people","emoji_order":"159","aliases":[":couplekiss_ww:"],"aliases_ascii":[],"keywords":["people","women","love","sex","lgbt","lgbt","lesbian","lesbian"]},"kiss_mm":{"unicode":"1f468-2764-1f48b-1f468","unicode_alternates":"1f468-200d-2764-fe0f-200d-1f48b-200d-1f468","name":"kiss (man,man)","shortname":":kiss_mm:","category":"people","emoji_order":"160","aliases":[":couplekiss_mm:"],"aliases_ascii":[],"keywords":["people","gay","men","love","sex","lgbt","lgbt"]},"family":{"unicode":"1f46a","unicode_alternates":"","name":"family","shortname":":family:","category":"people","emoji_order":"161","aliases":[],"aliases_ascii":[],"keywords":["people","family","baby"]},"family_mwg":{"unicode":"1f468-1f469-1f467","unicode_alternates":"1f468-200d-1f469-200d-1f467","name":"family (man,woman,girl)","shortname":":family_mwg:","category":"people","emoji_order":"162","aliases":[],"aliases_ascii":[],"keywords":["people","family","baby"]},"family_mwgb":{"unicode":"1f468-1f469-1f467-1f466","unicode_alternates":"1f468-200d-1f469-200d-1f467-200d-1f466","name":"family (man,woman,girl,boy)","shortname":":family_mwgb:","category":"people","emoji_order":"163","aliases":[],"aliases_ascii":[],"keywords":["people","family","baby"]},"family_mwbb":{"unicode":"1f468-1f469-1f466-1f466","unicode_alternates":"1f468-200d-1f469-200d-1f466-200d-1f466","name":"family (man,woman,boy,boy)","shortname":":family_mwbb:","category":"people","emoji_order":"164","aliases":[],"aliases_ascii":[],"keywords":["people","family","baby"]},"family_mwgg":{"unicode":"1f468-1f469-1f467-1f467","unicode_alternates":"1f468-200d-1f469-200d-1f467-200d-1f467","name":"family (man,woman,girl,girl)","shortname":":family_mwgg:","category":"people","emoji_order":"165","aliases":[],"aliases_ascii":[],"keywords":["people","family","baby"]},"family_wwb":{"unicode":"1f469-1f469-1f466","unicode_alternates":"1f469-200d-1f469-200d-1f466","name":"family (woman,woman,boy)","shortname":":family_wwb:","category":"people","emoji_order":"166","aliases":[],"aliases_ascii":[],"keywords":["people","family","women","baby","lgbt","lgbt","lesbian","lesbian"]},"family_wwg":{"unicode":"1f469-1f469-1f467","unicode_alternates":"1f469-200d-1f469-200d-1f467","name":"family (woman,woman,girl)","shortname":":family_wwg:","category":"people","emoji_order":"167","aliases":[],"aliases_ascii":[],"keywords":["people","family","women","baby","lgbt","lgbt","lesbian","lesbian"]},"family_wwgb":{"unicode":"1f469-1f469-1f467-1f466","unicode_alternates":"1f469-200d-1f469-200d-1f467-200d-1f466","name":"family (woman,woman,girl,boy)","shortname":":family_wwgb:","category":"people","emoji_order":"168","aliases":[],"aliases_ascii":[],"keywords":["people","family","women","baby","lgbt","lgbt","lesbian","lesbian"]},"family_wwbb":{"unicode":"1f469-1f469-1f466-1f466","unicode_alternates":"1f469-200d-1f469-200d-1f466-200d-1f466","name":"family (woman,woman,boy,boy)","shortname":":family_wwbb:","category":"people","emoji_order":"169","aliases":[],"aliases_ascii":[],"keywords":["people","family","women","baby","lgbt","lgbt","lesbian","lesbian"]},"family_wwgg":{"unicode":"1f469-1f469-1f467-1f467","unicode_alternates":"1f469-200d-1f469-200d-1f467-200d-1f467","name":"family (woman,woman,girl,girl)","shortname":":family_wwgg:","category":"people","emoji_order":"170","aliases":[],"aliases_ascii":[],"keywords":["people","family","women","baby","lgbt","lgbt","lesbian","lesbian"]},"family_mmb":{"unicode":"1f468-1f468-1f466","unicode_alternates":"1f468-200d-1f468-200d-1f466","name":"family (man,man,boy)","shortname":":family_mmb:","category":"people","emoji_order":"171","aliases":[],"aliases_ascii":[],"keywords":["people","gay","family","men","baby","lgbt","lgbt"]},"family_mmg":{"unicode":"1f468-1f468-1f467","unicode_alternates":"1f468-200d-1f468-200d-1f467","name":"family (man,man,girl)","shortname":":family_mmg:","category":"people","emoji_order":"172","aliases":[],"aliases_ascii":[],"keywords":["people","gay","family","men","baby","lgbt","lgbt"]},"family_mmgb":{"unicode":"1f468-1f468-1f467-1f466","unicode_alternates":"1f468-200d-1f468-200d-1f467-200d-1f466","name":"family (man,man,girl,boy)","shortname":":family_mmgb:","category":"people","emoji_order":"173","aliases":[],"aliases_ascii":[],"keywords":["people","gay","family","men","baby","lgbt","lgbt"]},"family_mmbb":{"unicode":"1f468-1f468-1f466-1f466","unicode_alternates":"1f468-200d-1f468-200d-1f466-200d-1f466","name":"family (man,man,boy,boy)","shortname":":family_mmbb:","category":"people","emoji_order":"174","aliases":[],"aliases_ascii":[],"keywords":["people","gay","family","men","baby","lgbt","lgbt"]},"family_mmgg":{"unicode":"1f468-1f468-1f467-1f467","unicode_alternates":"1f468-200d-1f468-200d-1f467-200d-1f467","name":"family (man,man,girl,girl)","shortname":":family_mmgg:","category":"people","emoji_order":"175","aliases":[],"aliases_ascii":[],"keywords":["people","gay","family","men","baby","lgbt","lgbt"]},"womans_clothes":{"unicode":"1f45a","unicode_alternates":"","name":"womans clothes","shortname":":womans_clothes:","category":"people","emoji_order":"176","aliases":[],"aliases_ascii":[],"keywords":["women","fashion"]},"shirt":{"unicode":"1f455","unicode_alternates":"","name":"t-shirt","shortname":":shirt:","category":"people","emoji_order":"177","aliases":[],"aliases_ascii":[],"keywords":["fashion"]},"jeans":{"unicode":"1f456","unicode_alternates":"","name":"jeans","shortname":":jeans:","category":"people","emoji_order":"178","aliases":[],"aliases_ascii":[],"keywords":["fashion"]},"necktie":{"unicode":"1f454","unicode_alternates":"","name":"necktie","shortname":":necktie:","category":"people","emoji_order":"179","aliases":[],"aliases_ascii":[],"keywords":["fashion"]},"dress":{"unicode":"1f457","unicode_alternates":"","name":"dress","shortname":":dress:","category":"people","emoji_order":"180","aliases":[],"aliases_ascii":[],"keywords":["women","fashion","sexy","girls night","girls night"]},"bikini":{"unicode":"1f459","unicode_alternates":"","name":"bikini","shortname":":bikini:","category":"people","emoji_order":"181","aliases":[],"aliases_ascii":[],"keywords":["women","fashion","sexy","vacation","tropical","swim"]},"kimono":{"unicode":"1f458","unicode_alternates":"","name":"kimono","shortname":":kimono:","category":"people","emoji_order":"182","aliases":[],"aliases_ascii":[],"keywords":["fashion"]},"lipstick":{"unicode":"1f484","unicode_alternates":"","name":"lipstick","shortname":":lipstick:","category":"people","emoji_order":"183","aliases":[],"aliases_ascii":[],"keywords":["object","women","fashion","sexy","lip"]},"kiss":{"unicode":"1f48b","unicode_alternates":"","name":"kiss mark","shortname":":kiss:","category":"people","emoji_order":"184","aliases":[],"aliases_ascii":[],"keywords":["women","love","sexy","lip","beautiful","beautiful","girls night","girls night"]},"footprints":{"unicode":"1f463","unicode_alternates":"","name":"footprints","shortname":":footprints:","category":"people","emoji_order":"185","aliases":[],"aliases_ascii":[],"keywords":[]},"high_heel":{"unicode":"1f460","unicode_alternates":"","name":"high-heeled shoe","shortname":":high_heel:","category":"people","emoji_order":"186","aliases":[],"aliases_ascii":[],"keywords":["women","fashion","shoe","sexy","accessories","girls night","girls night"]},"sandal":{"unicode":"1f461","unicode_alternates":"","name":"womans sandal","shortname":":sandal:","category":"people","emoji_order":"187","aliases":[],"aliases_ascii":[],"keywords":["fashion","shoe","accessories"]},"boot":{"unicode":"1f462","unicode_alternates":"","name":"womans boots","shortname":":boot:","category":"people","emoji_order":"188","aliases":[],"aliases_ascii":[],"keywords":["women","fashion","shoe","sexy","accessories"]},"mans_shoe":{"unicode":"1f45e","unicode_alternates":"","name":"mans shoe","shortname":":mans_shoe:","category":"people","emoji_order":"189","aliases":[],"aliases_ascii":[],"keywords":["fashion","shoe","accessories"]},"athletic_shoe":{"unicode":"1f45f","unicode_alternates":"","name":"athletic shoe","shortname":":athletic_shoe:","category":"people","emoji_order":"190","aliases":[],"aliases_ascii":[],"keywords":["fashion","shoe","accessories","boys night","boys night"]},"womans_hat":{"unicode":"1f452","unicode_alternates":"","name":"womans hat","shortname":":womans_hat:","category":"people","emoji_order":"191","aliases":[],"aliases_ascii":[],"keywords":["women","fashion","accessories"]},"tophat":{"unicode":"1f3a9","unicode_alternates":"","name":"top hat","shortname":":tophat:","category":"people","emoji_order":"192","aliases":[],"aliases_ascii":[],"keywords":["hat","fashion","accessories"]},"helmet_with_cross":{"unicode":"26d1","unicode_alternates":"26d1-fe0f","name":"helmet with white cross","shortname":":helmet_with_cross:","category":"people","emoji_order":"193","aliases":[":helmet_with_white_cross:"],"aliases_ascii":[],"keywords":["object","hat","accessories","job","job"]},"mortar_board":{"unicode":"1f393","unicode_alternates":"","name":"graduation cap","shortname":":mortar_board:","category":"people","emoji_order":"194","aliases":[],"aliases_ascii":[],"keywords":["hat","office","accessories"]},"crown":{"unicode":"1f451","unicode_alternates":"","name":"crown","shortname":":crown:","category":"people","emoji_order":"195","aliases":[],"aliases_ascii":[],"keywords":["object","gem","accessories"]},"school_satchel":{"unicode":"1f392","unicode_alternates":"","name":"school satchel","shortname":":school_satchel:","category":"people","emoji_order":"196","aliases":[],"aliases_ascii":[],"keywords":["bag","fashion","office","vacation","accessories"]},"pouch":{"unicode":"1f45d","unicode_alternates":"","name":"pouch","shortname":":pouch:","category":"people","emoji_order":"197","aliases":[],"aliases_ascii":[],"keywords":["bag","women","fashion","accessories"]},"purse":{"unicode":"1f45b","unicode_alternates":"","name":"purse","shortname":":purse:","category":"people","emoji_order":"198","aliases":[],"aliases_ascii":[],"keywords":["bag","women","fashion","accessories","money","money"]},"handbag":{"unicode":"1f45c","unicode_alternates":"","name":"handbag","shortname":":handbag:","category":"people","emoji_order":"199","aliases":[],"aliases_ascii":[],"keywords":["bag","women","fashion","vacation","accessories"]},"briefcase":{"unicode":"1f4bc","unicode_alternates":"","name":"briefcase","shortname":":briefcase:","category":"people","emoji_order":"200","aliases":[],"aliases_ascii":[],"keywords":["bag","work","accessories","nutcase","nutcase","job","job"]},"eyeglasses":{"unicode":"1f453","unicode_alternates":"","name":"eyeglasses","shortname":":eyeglasses:","category":"people","emoji_order":"201","aliases":[],"aliases_ascii":[],"keywords":["fashion","glasses","accessories"]},"dark_sunglasses":{"unicode":"1f576","unicode_alternates":"1f576-fe0f","name":"dark sunglasses","shortname":":dark_sunglasses:","category":"people","emoji_order":"202","aliases":[],"aliases_ascii":[],"keywords":["fashion","glasses","accessories"]},"ring":{"unicode":"1f48d","unicode_alternates":"","name":"ring","shortname":":ring:","category":"people","emoji_order":"203","aliases":[],"aliases_ascii":[],"keywords":["wedding","object","fashion","gem","accessories"]},"closed_umbrella":{"unicode":"1f302","unicode_alternates":"","name":"closed umbrella","shortname":":closed_umbrella:","category":"people","emoji_order":"204","aliases":[],"aliases_ascii":[],"keywords":["object","sky","rain","accessories"]},"dog":{"unicode":"1f436","unicode_alternates":"","name":"dog face","shortname":":dog:","category":"nature","emoji_order":"205","aliases":[],"aliases_ascii":[],"keywords":["dog","dog","pug","pug","animal","animal"]},"cat":{"unicode":"1f431","unicode_alternates":"","name":"cat face","shortname":":cat:","category":"nature","emoji_order":"206","aliases":[],"aliases_ascii":[],"keywords":["halloween","vagina","cat","cat","animal","animal"]},"mouse":{"unicode":"1f42d","unicode_alternates":"","name":"mouse face","shortname":":mouse:","category":"nature","emoji_order":"207","aliases":[],"aliases_ascii":[],"keywords":["animal","animal"]},"hamster":{"unicode":"1f439","unicode_alternates":"","name":"hamster face","shortname":":hamster:","category":"nature","emoji_order":"208","aliases":[],"aliases_ascii":[],"keywords":["animal","animal"]},"rabbit":{"unicode":"1f430","unicode_alternates":"","name":"rabbit face","shortname":":rabbit:","category":"nature","emoji_order":"209","aliases":[],"aliases_ascii":[],"keywords":["wildlife","animal","animal"]},"bear":{"unicode":"1f43b","unicode_alternates":"","name":"bear face","shortname":":bear:","category":"nature","emoji_order":"210","aliases":[],"aliases_ascii":[],"keywords":["wildlife","roar","animal","animal"]},"panda_face":{"unicode":"1f43c","unicode_alternates":"","name":"panda face","shortname":":panda_face:","category":"nature","emoji_order":"211","aliases":[],"aliases_ascii":[],"keywords":["wildlife","roar","animal","animal"]},"koala":{"unicode":"1f428","unicode_alternates":"","name":"koala","shortname":":koala:","category":"nature","emoji_order":"212","aliases":[],"aliases_ascii":[],"keywords":["wildlife","animal","animal"]},"tiger":{"unicode":"1f42f","unicode_alternates":"","name":"tiger face","shortname":":tiger:","category":"nature","emoji_order":"213","aliases":[],"aliases_ascii":[],"keywords":["wildlife","roar","cat","cat","animal","animal"]},"lion_face":{"unicode":"1f981","unicode_alternates":"","name":"lion face","shortname":":lion_face:","category":"nature","emoji_order":"214","aliases":[":lion:"],"aliases_ascii":[],"keywords":["wildlife","roar","cat","cat","animal","animal"]},"cow":{"unicode":"1f42e","unicode_alternates":"","name":"cow face","shortname":":cow:","category":"nature","emoji_order":"215","aliases":[],"aliases_ascii":[],"keywords":["animal","animal"]},"pig":{"unicode":"1f437","unicode_alternates":"","name":"pig face","shortname":":pig:","category":"nature","emoji_order":"216","aliases":[],"aliases_ascii":[],"keywords":["animal","animal"]},"pig_nose":{"unicode":"1f43d","unicode_alternates":"","name":"pig nose","shortname":":pig_nose:","category":"nature","emoji_order":"217","aliases":[],"aliases_ascii":[],"keywords":["animal","animal"]},"frog":{"unicode":"1f438","unicode_alternates":"","name":"frog face","shortname":":frog:","category":"nature","emoji_order":"218","aliases":[],"aliases_ascii":[],"keywords":["wildlife","animal","animal"]},"octopus":{"unicode":"1f419","unicode_alternates":"","name":"octopus","shortname":":octopus:","category":"nature","emoji_order":"219","aliases":[],"aliases_ascii":[],"keywords":["wildlife","animal","animal"]},"monkey_face":{"unicode":"1f435","unicode_alternates":"","name":"monkey face","shortname":":monkey_face:","category":"nature","emoji_order":"220","aliases":[],"aliases_ascii":[],"keywords":["animal","animal"]},"see_no_evil":{"unicode":"1f648","unicode_alternates":"","name":"see-no-evil monkey","shortname":":see_no_evil:","category":"nature","emoji_order":"221","aliases":[],"aliases_ascii":[],"keywords":["animal","animal"]},"hear_no_evil":{"unicode":"1f649","unicode_alternates":"","name":"hear-no-evil monkey","shortname":":hear_no_evil:","category":"nature","emoji_order":"222","aliases":[],"aliases_ascii":[],"keywords":["animal","animal"]},"speak_no_evil":{"unicode":"1f64a","unicode_alternates":"","name":"speak-no-evil monkey","shortname":":speak_no_evil:","category":"nature","emoji_order":"223","aliases":[],"aliases_ascii":[],"keywords":["animal","animal"]},"monkey":{"unicode":"1f412","unicode_alternates":"","name":"monkey","shortname":":monkey:","category":"nature","emoji_order":"224","aliases":[],"aliases_ascii":[],"keywords":["wildlife","animal","animal"]},"chicken":{"unicode":"1f414","unicode_alternates":"","name":"chicken","shortname":":chicken:","category":"nature","emoji_order":"225","aliases":[],"aliases_ascii":[],"keywords":["animal","animal","chicken","chicken"]},"penguin":{"unicode":"1f427","unicode_alternates":"","name":"penguin","shortname":":penguin:","category":"nature","emoji_order":"226","aliases":[],"aliases_ascii":[],"keywords":["wildlife","animal","animal"]},"bird":{"unicode":"1f426","unicode_alternates":"","name":"bird","shortname":":bird:","category":"nature","emoji_order":"227","aliases":[],"aliases_ascii":[],"keywords":["wildlife","animal","animal"]},"baby_chick":{"unicode":"1f424","unicode_alternates":"","name":"baby chick","shortname":":baby_chick:","category":"nature","emoji_order":"228","aliases":[],"aliases_ascii":[],"keywords":["animal","animal","chicken","chicken"]},"hatching_chick":{"unicode":"1f423","unicode_alternates":"","name":"hatching chick","shortname":":hatching_chick:","category":"nature","emoji_order":"229","aliases":[],"aliases_ascii":[],"keywords":["animal","animal","chicken","chicken"]},"hatched_chick":{"unicode":"1f425","unicode_alternates":"","name":"front-facing baby chick","shortname":":hatched_chick:","category":"nature","emoji_order":"230","aliases":[],"aliases_ascii":[],"keywords":["animal","animal","chicken","chicken"]},"wolf":{"unicode":"1f43a","unicode_alternates":"","name":"wolf face","shortname":":wolf:","category":"nature","emoji_order":"231","aliases":[],"aliases_ascii":[],"keywords":["wildlife","roar","animal","animal"]},"boar":{"unicode":"1f417","unicode_alternates":"","name":"boar","shortname":":boar:","category":"nature","emoji_order":"232","aliases":[],"aliases_ascii":[],"keywords":["wildlife","animal","animal"]},"horse":{"unicode":"1f434","unicode_alternates":"","name":"horse face","shortname":":horse:","category":"nature","emoji_order":"233","aliases":[],"aliases_ascii":[],"keywords":["wildlife","animal","animal"]},"unicorn":{"unicode":"1f984","unicode_alternates":"","name":"unicorn face","shortname":":unicorn:","category":"nature","emoji_order":"234","aliases":[":unicorn_face:"],"aliases_ascii":[],"keywords":["animal","animal"]},"bee":{"unicode":"1f41d","unicode_alternates":"","name":"honeybee","shortname":":bee:","category":"nature","emoji_order":"235","aliases":[],"aliases_ascii":[],"keywords":["insects","animal","animal"]},"bug":{"unicode":"1f41b","unicode_alternates":"","name":"bug","shortname":":bug:","category":"nature","emoji_order":"236","aliases":[],"aliases_ascii":[],"keywords":["insects","animal","animal"]},"snail":{"unicode":"1f40c","unicode_alternates":"","name":"snail","shortname":":snail:","category":"nature","emoji_order":"237","aliases":[],"aliases_ascii":[],"keywords":["insects","animal","animal"]},"beetle":{"unicode":"1f41e","unicode_alternates":"","name":"lady beetle","shortname":":beetle:","category":"nature","emoji_order":"238","aliases":[],"aliases_ascii":[],"keywords":["insects","animal","animal"]},"ant":{"unicode":"1f41c","unicode_alternates":"","name":"ant","shortname":":ant:","category":"nature","emoji_order":"239","aliases":[],"aliases_ascii":[],"keywords":["insects","animal","animal"]},"spider":{"unicode":"1f577","unicode_alternates":"1f577-fe0f","name":"spider","shortname":":spider:","category":"nature","emoji_order":"240","aliases":[],"aliases_ascii":[],"keywords":["insects","halloween","animal","animal"]},"scorpion":{"unicode":"1f982","unicode_alternates":"","name":"scorpion","shortname":":scorpion:","category":"nature","emoji_order":"241","aliases":[],"aliases_ascii":[],"keywords":["insects","reptile","reptile","animal","animal"]},"crab":{"unicode":"1f980","unicode_alternates":"","name":"crab","shortname":":crab:","category":"nature","emoji_order":"242","aliases":[],"aliases_ascii":[],"keywords":["tropical","animal","animal"]},"snake":{"unicode":"1f40d","unicode_alternates":"","name":"snake","shortname":":snake:","category":"nature","emoji_order":"243","aliases":[],"aliases_ascii":[],"keywords":["wildlife","reptile","reptile","animal","animal","creationism","creationism"]},"turtle":{"unicode":"1f422","unicode_alternates":"","name":"turtle","shortname":":turtle:","category":"nature","emoji_order":"244","aliases":[],"aliases_ascii":[],"keywords":["wildlife","reptile","reptile","animal","animal"]},"tropical_fish":{"unicode":"1f420","unicode_alternates":"","name":"tropical fish","shortname":":tropical_fish:","category":"nature","emoji_order":"245","aliases":[],"aliases_ascii":[],"keywords":["wildlife","animal","animal"]},"fish":{"unicode":"1f41f","unicode_alternates":"","name":"fish","shortname":":fish:","category":"nature","emoji_order":"246","aliases":[],"aliases_ascii":[],"keywords":["wildlife","animal","animal"]},"blowfish":{"unicode":"1f421","unicode_alternates":"","name":"blowfish","shortname":":blowfish:","category":"nature","emoji_order":"247","aliases":[],"aliases_ascii":[],"keywords":["wildlife","animal","animal"]},"dolphin":{"unicode":"1f42c","unicode_alternates":"","name":"dolphin","shortname":":dolphin:","category":"nature","emoji_order":"248","aliases":[],"aliases_ascii":[],"keywords":["wildlife","tropical","animal","animal"]},"whale":{"unicode":"1f433","unicode_alternates":"","name":"spouting whale","shortname":":whale:","category":"nature","emoji_order":"249","aliases":[],"aliases_ascii":[],"keywords":["wildlife","tropical","whales","whales","animal","animal"]},"whale2":{"unicode":"1f40b","unicode_alternates":"","name":"whale","shortname":":whale2:","category":"nature","emoji_order":"250","aliases":[],"aliases_ascii":[],"keywords":["wildlife","tropical","whales","whales","animal","animal"]},"crocodile":{"unicode":"1f40a","unicode_alternates":"","name":"crocodile","shortname":":crocodile:","category":"nature","emoji_order":"251","aliases":[],"aliases_ascii":[],"keywords":["wildlife","reptile","reptile","animal","animal"]},"leopard":{"unicode":"1f406","unicode_alternates":"","name":"leopard","shortname":":leopard:","category":"nature","emoji_order":"252","aliases":[],"aliases_ascii":[],"keywords":["wildlife","roar","animal","animal"]},"tiger2":{"unicode":"1f405","unicode_alternates":"","name":"tiger","shortname":":tiger2:","category":"nature","emoji_order":"253","aliases":[],"aliases_ascii":[],"keywords":["wildlife","roar","animal","animal"]},"water_buffalo":{"unicode":"1f403","unicode_alternates":"","name":"water buffalo","shortname":":water_buffalo:","category":"nature","emoji_order":"254","aliases":[],"aliases_ascii":[],"keywords":["wildlife","animal","animal"]},"ox":{"unicode":"1f402","unicode_alternates":"","name":"ox","shortname":":ox:","category":"nature","emoji_order":"255","aliases":[],"aliases_ascii":[],"keywords":["animal","animal"]},"cow2":{"unicode":"1f404","unicode_alternates":"","name":"cow","shortname":":cow2:","category":"nature","emoji_order":"256","aliases":[],"aliases_ascii":[],"keywords":["animal","animal"]},"dromedary_camel":{"unicode":"1f42a","unicode_alternates":"","name":"dromedary camel","shortname":":dromedary_camel:","category":"nature","emoji_order":"257","aliases":[],"aliases_ascii":[],"keywords":["wildlife","animal","animal"]},"camel":{"unicode":"1f42b","unicode_alternates":"","name":"bactrian camel","shortname":":camel:","category":"nature","emoji_order":"258","aliases":[],"aliases_ascii":[],"keywords":["wildlife","animal","animal","hump day","hump day"]},"elephant":{"unicode":"1f418","unicode_alternates":"","name":"elephant","shortname":":elephant:","category":"nature","emoji_order":"259","aliases":[],"aliases_ascii":[],"keywords":["wildlife","animal","animal"]},"goat":{"unicode":"1f410","unicode_alternates":"","name":"goat","shortname":":goat:","category":"nature","emoji_order":"260","aliases":[],"aliases_ascii":[],"keywords":["animal","animal"]},"ram":{"unicode":"1f40f","unicode_alternates":"","name":"ram","shortname":":ram:","category":"nature","emoji_order":"261","aliases":[],"aliases_ascii":[],"keywords":["wildlife","animal","animal"]},"sheep":{"unicode":"1f411","unicode_alternates":"","name":"sheep","shortname":":sheep:","category":"nature","emoji_order":"262","aliases":[],"aliases_ascii":[],"keywords":["animal","animal"]},"racehorse":{"unicode":"1f40e","unicode_alternates":"","name":"horse","shortname":":racehorse:","category":"nature","emoji_order":"263","aliases":[],"aliases_ascii":[],"keywords":["wildlife","animal","animal"]},"pig2":{"unicode":"1f416","unicode_alternates":"","name":"pig","shortname":":pig2:","category":"nature","emoji_order":"264","aliases":[],"aliases_ascii":[],"keywords":["animal","animal"]},"rat":{"unicode":"1f400","unicode_alternates":"","name":"rat","shortname":":rat:","category":"nature","emoji_order":"265","aliases":[],"aliases_ascii":[],"keywords":["animal","animal"]},"mouse2":{"unicode":"1f401","unicode_alternates":"","name":"mouse","shortname":":mouse2:","category":"nature","emoji_order":"266","aliases":[],"aliases_ascii":[],"keywords":["animal","animal"]},"rooster":{"unicode":"1f413","unicode_alternates":"","name":"rooster","shortname":":rooster:","category":"nature","emoji_order":"267","aliases":[],"aliases_ascii":[],"keywords":["animal","animal"]},"turkey":{"unicode":"1f983","unicode_alternates":"","name":"turkey","shortname":":turkey:","category":"nature","emoji_order":"268","aliases":[],"aliases_ascii":[],"keywords":["wildlife","animal","animal"]},"dove":{"unicode":"1f54a","unicode_alternates":"1f54a-fe0f","name":"dove of peace","shortname":":dove:","category":"nature","emoji_order":"269","aliases":[":dove_of_peace:"],"aliases_ascii":[],"keywords":["animal","animal"]},"dog2":{"unicode":"1f415","unicode_alternates":"","name":"dog","shortname":":dog2:","category":"nature","emoji_order":"270","aliases":[],"aliases_ascii":[],"keywords":["dog","dog","pug","pug","animal","animal"]},"poodle":{"unicode":"1f429","unicode_alternates":"","name":"poodle","shortname":":poodle:","category":"nature","emoji_order":"271","aliases":[],"aliases_ascii":[],"keywords":["dog","dog","animal","animal"]},"cat2":{"unicode":"1f408","unicode_alternates":"","name":"cat","shortname":":cat2:","category":"nature","emoji_order":"272","aliases":[],"aliases_ascii":[],"keywords":["halloween","cat","cat","animal","animal"]},"rabbit2":{"unicode":"1f407","unicode_alternates":"","name":"rabbit","shortname":":rabbit2:","category":"nature","emoji_order":"273","aliases":[],"aliases_ascii":[],"keywords":["wildlife","animal","animal"]},"chipmunk":{"unicode":"1f43f","unicode_alternates":"1f43f-fe0f","name":"chipmunk","shortname":":chipmunk:","category":"nature","emoji_order":"274","aliases":[],"aliases_ascii":[],"keywords":["wildlife","animal","animal"]},"feet":{"unicode":"1f43e","unicode_alternates":"","name":"paw prints","shortname":":feet:","category":"nature","emoji_order":"275","aliases":[":paw_prints:"],"aliases_ascii":[],"keywords":["animal","animal"]},"dragon":{"unicode":"1f409","unicode_alternates":"","name":"dragon","shortname":":dragon:","category":"nature","emoji_order":"276","aliases":[],"aliases_ascii":[],"keywords":["roar","reptile","reptile","animal","animal"]},"dragon_face":{"unicode":"1f432","unicode_alternates":"","name":"dragon face","shortname":":dragon_face:","category":"nature","emoji_order":"277","aliases":[],"aliases_ascii":[],"keywords":["roar","monster","reptile","reptile","animal","animal"]},"cactus":{"unicode":"1f335","unicode_alternates":"","name":"cactus","shortname":":cactus:","category":"nature","emoji_order":"278","aliases":[],"aliases_ascii":[],"keywords":["nature","plant","trees","trees"]},"christmas_tree":{"unicode":"1f384","unicode_alternates":"","name":"christmas tree","shortname":":christmas_tree:","category":"nature","emoji_order":"279","aliases":[],"aliases_ascii":[],"keywords":["plant","holidays","christmas","trees","trees"]},"evergreen_tree":{"unicode":"1f332","unicode_alternates":"","name":"evergreen tree","shortname":":evergreen_tree:","category":"nature","emoji_order":"280","aliases":[],"aliases_ascii":[],"keywords":["nature","plant","holidays","christmas","camp","trees","trees"]},"deciduous_tree":{"unicode":"1f333","unicode_alternates":"","name":"deciduous tree","shortname":":deciduous_tree:","category":"nature","emoji_order":"281","aliases":[],"aliases_ascii":[],"keywords":["nature","plant","camp","trees","trees"]},"palm_tree":{"unicode":"1f334","unicode_alternates":"","name":"palm tree","shortname":":palm_tree:","category":"nature","emoji_order":"282","aliases":[],"aliases_ascii":[],"keywords":["nature","plant","tropical","trees","trees"]},"seedling":{"unicode":"1f331","unicode_alternates":"","name":"seedling","shortname":":seedling:","category":"nature","emoji_order":"283","aliases":[],"aliases_ascii":[],"keywords":["nature","plant","leaf","leaf"]},"herb":{"unicode":"1f33f","unicode_alternates":"","name":"herb","shortname":":herb:","category":"nature","emoji_order":"284","aliases":[],"aliases_ascii":[],"keywords":["nature","plant","leaf","leaf"]},"shamrock":{"unicode":"2618","unicode_alternates":"2618-fe0f","name":"shamrock","shortname":":shamrock:","category":"nature","emoji_order":"285","aliases":[],"aliases_ascii":[],"keywords":["nature","plant","luck","leaf","leaf"]},"four_leaf_clover":{"unicode":"1f340","unicode_alternates":"","name":"four leaf clover","shortname":":four_leaf_clover:","category":"nature","emoji_order":"286","aliases":[],"aliases_ascii":[],"keywords":["nature","plant","luck","leaf","leaf","sol","sol"]},"bamboo":{"unicode":"1f38d","unicode_alternates":"","name":"pine decoration","shortname":":bamboo:","category":"nature","emoji_order":"287","aliases":[],"aliases_ascii":[],"keywords":["nature","plant"]},"tanabata_tree":{"unicode":"1f38b","unicode_alternates":"","name":"tanabata tree","shortname":":tanabata_tree:","category":"nature","emoji_order":"288","aliases":[],"aliases_ascii":[],"keywords":["nature","plant","trees","trees"]},"leaves":{"unicode":"1f343","unicode_alternates":"","name":"leaf fluttering in wind","shortname":":leaves:","category":"nature","emoji_order":"289","aliases":[],"aliases_ascii":[],"keywords":["nature","plant","leaf","leaf"]},"fallen_leaf":{"unicode":"1f342","unicode_alternates":"","name":"fallen leaf","shortname":":fallen_leaf:","category":"nature","emoji_order":"290","aliases":[],"aliases_ascii":[],"keywords":["nature","plant","leaf","leaf"]},"maple_leaf":{"unicode":"1f341","unicode_alternates":"","name":"maple leaf","shortname":":maple_leaf:","category":"nature","emoji_order":"291","aliases":[],"aliases_ascii":[],"keywords":["nature","plant","leaf","leaf"]},"ear_of_rice":{"unicode":"1f33e","unicode_alternates":"","name":"ear of rice","shortname":":ear_of_rice:","category":"nature","emoji_order":"292","aliases":[],"aliases_ascii":[],"keywords":["nature","plant","leaf","leaf"]},"hibiscus":{"unicode":"1f33a","unicode_alternates":"","name":"hibiscus","shortname":":hibiscus:","category":"nature","emoji_order":"293","aliases":[],"aliases_ascii":[],"keywords":["nature","flower","plant","tropical"]},"sunflower":{"unicode":"1f33b","unicode_alternates":"","name":"sunflower","shortname":":sunflower:","category":"nature","emoji_order":"294","aliases":[],"aliases_ascii":[],"keywords":["nature","flower","plant"]},"rose":{"unicode":"1f339","unicode_alternates":"","name":"rose","shortname":":rose:","category":"nature","emoji_order":"295","aliases":[],"aliases_ascii":[],"keywords":["nature","flower","plant","rip","rip","condolence","condolence","beautiful","beautiful"]},"tulip":{"unicode":"1f337","unicode_alternates":"","name":"tulip","shortname":":tulip:","category":"nature","emoji_order":"296","aliases":[],"aliases_ascii":[],"keywords":["nature","flower","plant","vagina","girls night","girls night"]},"blossom":{"unicode":"1f33c","unicode_alternates":"","name":"blossom","shortname":":blossom:","category":"nature","emoji_order":"297","aliases":[],"aliases_ascii":[],"keywords":["nature","flower","plant"]},"cherry_blossom":{"unicode":"1f338","unicode_alternates":"","name":"cherry blossom","shortname":":cherry_blossom:","category":"nature","emoji_order":"298","aliases":[],"aliases_ascii":[],"keywords":["nature","flower","plant","tropical"]},"bouquet":{"unicode":"1f490","unicode_alternates":"","name":"bouquet","shortname":":bouquet:","category":"nature","emoji_order":"299","aliases":[],"aliases_ascii":[],"keywords":["nature","flower","plant","rip","rip","condolence","condolence"]},"mushroom":{"unicode":"1f344","unicode_alternates":"","name":"mushroom","shortname":":mushroom:","category":"nature","emoji_order":"300","aliases":[],"aliases_ascii":[],"keywords":["nature","plant","drugs","drugs"]},"chestnut":{"unicode":"1f330","unicode_alternates":"","name":"chestnut","shortname":":chestnut:","category":"nature","emoji_order":"301","aliases":[],"aliases_ascii":[],"keywords":["nature","plant"]},"jack_o_lantern":{"unicode":"1f383","unicode_alternates":"","name":"jack-o-lantern","shortname":":jack_o_lantern:","category":"nature","emoji_order":"302","aliases":[],"aliases_ascii":[],"keywords":["holidays","halloween"]},"shell":{"unicode":"1f41a","unicode_alternates":"","name":"spiral shell","shortname":":shell:","category":"nature","emoji_order":"303","aliases":[],"aliases_ascii":[],"keywords":[]},"spider_web":{"unicode":"1f578","unicode_alternates":"1f578-fe0f","name":"spider web","shortname":":spider_web:","category":"nature","emoji_order":"304","aliases":[],"aliases_ascii":[],"keywords":["halloween"]},"earth_americas":{"unicode":"1f30e","unicode_alternates":"","name":"earth globe americas","shortname":":earth_americas:","category":"nature","emoji_order":"305","aliases":[],"aliases_ascii":[],"keywords":["map","vacation","globe","globe"]},"earth_africa":{"unicode":"1f30d","unicode_alternates":"","name":"earth globe europe-africa","shortname":":earth_africa:","category":"nature","emoji_order":"306","aliases":[],"aliases_ascii":[],"keywords":["map","vacation","globe","globe"]},"earth_asia":{"unicode":"1f30f","unicode_alternates":"","name":"earth globe asia-australia","shortname":":earth_asia:","category":"nature","emoji_order":"307","aliases":[],"aliases_ascii":[],"keywords":["map","vacation","globe","globe"]},"full_moon":{"unicode":"1f315","unicode_alternates":"","name":"full moon symbol","shortname":":full_moon:","category":"nature","emoji_order":"308","aliases":[],"aliases_ascii":[],"keywords":["space","sky","moon","moon"]},"waning_gibbous_moon":{"unicode":"1f316","unicode_alternates":"","name":"waning gibbous moon symbol","shortname":":waning_gibbous_moon:","category":"nature","emoji_order":"309","aliases":[],"aliases_ascii":[],"keywords":["space","sky","moon","moon"]},"last_quarter_moon":{"unicode":"1f317","unicode_alternates":"","name":"last quarter moon symbol","shortname":":last_quarter_moon:","category":"nature","emoji_order":"310","aliases":[],"aliases_ascii":[],"keywords":["space","sky","moon","moon"]},"waning_crescent_moon":{"unicode":"1f318","unicode_alternates":"","name":"waning crescent moon symbol","shortname":":waning_crescent_moon:","category":"nature","emoji_order":"311","aliases":[],"aliases_ascii":[],"keywords":["space","sky","moon","moon"]},"new_moon":{"unicode":"1f311","unicode_alternates":"","name":"new moon symbol","shortname":":new_moon:","category":"nature","emoji_order":"312","aliases":[],"aliases_ascii":[],"keywords":["space","sky","moon","moon"]},"waxing_crescent_moon":{"unicode":"1f312","unicode_alternates":"","name":"waxing crescent moon symbol","shortname":":waxing_crescent_moon:","category":"nature","emoji_order":"313","aliases":[],"aliases_ascii":[],"keywords":["space","sky","moon","moon"]},"first_quarter_moon":{"unicode":"1f313","unicode_alternates":"","name":"first quarter moon symbol","shortname":":first_quarter_moon:","category":"nature","emoji_order":"314","aliases":[],"aliases_ascii":[],"keywords":["space","sky","moon","moon"]},"waxing_gibbous_moon":{"unicode":"1f314","unicode_alternates":"","name":"waxing gibbous moon symbol","shortname":":waxing_gibbous_moon:","category":"nature","emoji_order":"315","aliases":[],"aliases_ascii":[],"keywords":["space","sky","moon","moon"]},"new_moon_with_face":{"unicode":"1f31a","unicode_alternates":"","name":"new moon with face","shortname":":new_moon_with_face:","category":"nature","emoji_order":"316","aliases":[],"aliases_ascii":[],"keywords":["space","sky","goodnight","goodnight","moon","moon"]},"full_moon_with_face":{"unicode":"1f31d","unicode_alternates":"","name":"full moon with face","shortname":":full_moon_with_face:","category":"nature","emoji_order":"317","aliases":[],"aliases_ascii":[],"keywords":["space","sky","goodnight","goodnight","moon","moon"]},"first_quarter_moon_with_face":{"unicode":"1f31b","unicode_alternates":"","name":"first quarter moon with face","shortname":":first_quarter_moon_with_face:","category":"nature","emoji_order":"318","aliases":[],"aliases_ascii":[],"keywords":["space","sky","moon","moon"]},"last_quarter_moon_with_face":{"unicode":"1f31c","unicode_alternates":"","name":"last quarter moon with face","shortname":":last_quarter_moon_with_face:","category":"nature","emoji_order":"319","aliases":[],"aliases_ascii":[],"keywords":["space","sky","moon","moon"]},"sun_with_face":{"unicode":"1f31e","unicode_alternates":"","name":"sun with face","shortname":":sun_with_face:","category":"nature","emoji_order":"320","aliases":[],"aliases_ascii":[],"keywords":["sky","day","sun","hump day","hump day","morning","morning"]},"crescent_moon":{"unicode":"1f319","unicode_alternates":"","name":"crescent moon","shortname":":crescent_moon:","category":"nature","emoji_order":"321","aliases":[],"aliases_ascii":[],"keywords":["space","sky","goodnight","goodnight","moon","moon"]},"star":{"unicode":"2b50","unicode_alternates":"2b50-fe0f","name":"white medium star","shortname":":star:","category":"nature","emoji_order":"322","aliases":[],"aliases_ascii":[],"keywords":["space","sky","star"]},"star2":{"unicode":"1f31f","unicode_alternates":"","name":"glowing star","shortname":":star2:","category":"nature","emoji_order":"323","aliases":[],"aliases_ascii":[],"keywords":["space","sky","star"]},"dizzy":{"unicode":"1f4ab","unicode_alternates":"","name":"dizzy symbol","shortname":":dizzy:","category":"nature","emoji_order":"324","aliases":[],"aliases_ascii":[],"keywords":["star","symbol"]},"sparkles":{"unicode":"2728","unicode_alternates":"","name":"sparkles","shortname":":sparkles:","category":"nature","emoji_order":"325","aliases":[],"aliases_ascii":[],"keywords":["star","girls night","girls night"]},"comet":{"unicode":"2604","unicode_alternates":"2604-fe0f","name":"comet","shortname":":comet:","category":"nature","emoji_order":"326","aliases":[],"aliases_ascii":[],"keywords":["space","sky"]},"sunny":{"unicode":"2600","unicode_alternates":"2600-fe0f","name":"black sun with rays","shortname":":sunny:","category":"nature","emoji_order":"327","aliases":[],"aliases_ascii":[],"keywords":["weather","sky","day","sun","hot","hot","morning","morning"]},"white_sun_small_cloud":{"unicode":"1f324","unicode_alternates":"1f324-fe0f","name":"white sun with small cloud","shortname":":white_sun_small_cloud:","category":"nature","emoji_order":"328","aliases":[":white_sun_with_small_cloud:"],"aliases_ascii":[],"keywords":["weather","sky","cloud","sun"]},"partly_sunny":{"unicode":"26c5","unicode_alternates":"26c5-fe0f","name":"sun behind cloud","shortname":":partly_sunny:","category":"nature","emoji_order":"329","aliases":[],"aliases_ascii":[],"keywords":["weather","sky","cloud","sun"]},"white_sun_cloud":{"unicode":"1f325","unicode_alternates":"1f325-fe0f","name":"white sun behind cloud","shortname":":white_sun_cloud:","category":"nature","emoji_order":"330","aliases":[":white_sun_behind_cloud:"],"aliases_ascii":[],"keywords":["weather","sky","cloud","cold","sun"]},"white_sun_rain_cloud":{"unicode":"1f326","unicode_alternates":"1f326-fe0f","name":"white sun behind cloud with rain","shortname":":white_sun_rain_cloud:","category":"nature","emoji_order":"331","aliases":[":white_sun_behind_cloud_with_rain:"],"aliases_ascii":[],"keywords":["weather","sky","cloud","cold","rain","sun"]},"cloud":{"unicode":"2601","unicode_alternates":"2601-fe0f","name":"cloud","shortname":":cloud:","category":"nature","emoji_order":"332","aliases":[],"aliases_ascii":[],"keywords":["weather","sky","cloud","cold","rain"]},"cloud_rain":{"unicode":"1f327","unicode_alternates":"1f327-fe0f","name":"cloud with rain","shortname":":cloud_rain:","category":"nature","emoji_order":"333","aliases":[":cloud_with_rain:"],"aliases_ascii":[],"keywords":["weather","winter","sky","cloud","cold","rain"]},"thunder_cloud_rain":{"unicode":"26c8","unicode_alternates":"26c8-fe0f","name":"thunder cloud and rain","shortname":":thunder_cloud_rain:","category":"nature","emoji_order":"334","aliases":[":thunder_cloud_and_rain:"],"aliases_ascii":[],"keywords":["weather","sky","cloud","cold","rain"]},"cloud_lightning":{"unicode":"1f329","unicode_alternates":"1f329-fe0f","name":"cloud with lightning","shortname":":cloud_lightning:","category":"nature","emoji_order":"335","aliases":[":cloud_with_lightning:"],"aliases_ascii":[],"keywords":["weather","sky","cloud","cold","rain"]},"zap":{"unicode":"26a1","unicode_alternates":"26a1-fe0f","name":"high voltage sign","shortname":":zap:","category":"nature","emoji_order":"336","aliases":[],"aliases_ascii":[],"keywords":["weather","sky","diarrhea","diarrhea"]},"fire":{"unicode":"1f525","unicode_alternates":"","name":"fire","shortname":":fire:","category":"nature","emoji_order":"337","aliases":[":flame:"],"aliases_ascii":[],"keywords":["wth","wth","hot","hot"]},"boom":{"unicode":"1f4a5","unicode_alternates":"","name":"collision symbol","shortname":":boom:","category":"nature","emoji_order":"338","aliases":[],"aliases_ascii":[],"keywords":["symbol","blast","blast"]},"snowflake":{"unicode":"2744","unicode_alternates":"2744-fe0f","name":"snowflake","shortname":":snowflake:","category":"nature","emoji_order":"339","aliases":[],"aliases_ascii":[],"keywords":["weather","winter","sky","holidays","cold","snow","snow"]},"cloud_snow":{"unicode":"1f328","unicode_alternates":"1f328-fe0f","name":"cloud with snow","shortname":":cloud_snow:","category":"nature","emoji_order":"340","aliases":[":cloud_with_snow:"],"aliases_ascii":[],"keywords":["weather","winter","sky","cloud","cold","snow","snow"]},"snowman2":{"unicode":"2603","unicode_alternates":"2603-fe0f","name":"snowman","shortname":":snowman2:","category":"nature","emoji_order":"341","aliases":[],"aliases_ascii":[],"keywords":["weather","winter","holidays","christmas","cold","snow","snow"]},"snowman":{"unicode":"26c4","unicode_alternates":"26c4-fe0f","name":"snowman without snow","shortname":":snowman:","category":"nature","emoji_order":"342","aliases":[],"aliases_ascii":[],"keywords":["weather","winter","holidays","cold","snow","snow"]},"wind_blowing_face":{"unicode":"1f32c","unicode_alternates":"1f32c-fe0f","name":"wind blowing face","shortname":":wind_blowing_face:","category":"nature","emoji_order":"343","aliases":[],"aliases_ascii":[],"keywords":["weather","cold"]},"dash":{"unicode":"1f4a8","unicode_alternates":"","name":"dash symbol","shortname":":dash:","category":"nature","emoji_order":"344","aliases":[],"aliases_ascii":[],"keywords":["cloud","cold","smoking","smoking"]},"cloud_tornado":{"unicode":"1f32a","unicode_alternates":"1f32a-fe0f","name":"cloud with tornado","shortname":":cloud_tornado:","category":"nature","emoji_order":"345","aliases":[":cloud_with_tornado:"],"aliases_ascii":[],"keywords":["weather","sky","cold"]},"fog":{"unicode":"1f32b","unicode_alternates":"1f32b-fe0f","name":"fog","shortname":":fog:","category":"nature","emoji_order":"346","aliases":[],"aliases_ascii":[],"keywords":["weather","sky","cold"]},"umbrella2":{"unicode":"2602","unicode_alternates":"2602-fe0f","name":"umbrella","shortname":":umbrella2:","category":"nature","emoji_order":"347","aliases":[],"aliases_ascii":[],"keywords":["weather","object","sky","cold"]},"umbrella":{"unicode":"2614","unicode_alternates":"2614-fe0f","name":"umbrella with rain drops","shortname":":umbrella:","category":"nature","emoji_order":"348","aliases":[],"aliases_ascii":[],"keywords":["weather","sky","cold","rain"]},"droplet":{"unicode":"1f4a7","unicode_alternates":"","name":"droplet","shortname":":droplet:","category":"nature","emoji_order":"349","aliases":[],"aliases_ascii":[],"keywords":["weather","sky","rain"]},"sweat_drops":{"unicode":"1f4a6","unicode_alternates":"","name":"splashing sweat symbol","shortname":":sweat_drops:","category":"nature","emoji_order":"350","aliases":[],"aliases_ascii":[],"keywords":["rain","stressed","sweat"]},"ocean":{"unicode":"1f30a","unicode_alternates":"","name":"water wave","shortname":":ocean:","category":"nature","emoji_order":"351","aliases":[],"aliases_ascii":[],"keywords":["weather","boat","tropical","swim"]},"green_apple":{"unicode":"1f34f","unicode_alternates":"","name":"green apple","shortname":":green_apple:","category":"food","emoji_order":"352","aliases":[],"aliases_ascii":[],"keywords":["fruit","food"]},"apple":{"unicode":"1f34e","unicode_alternates":"","name":"red apple","shortname":":apple:","category":"food","emoji_order":"353","aliases":[],"aliases_ascii":[],"keywords":["fruit","food","creationism","creationism"]},"pear":{"unicode":"1f350","unicode_alternates":"","name":"pear","shortname":":pear:","category":"food","emoji_order":"354","aliases":[],"aliases_ascii":[],"keywords":["fruit","food"]},"tangerine":{"unicode":"1f34a","unicode_alternates":"","name":"tangerine","shortname":":tangerine:","category":"food","emoji_order":"355","aliases":[],"aliases_ascii":[],"keywords":["fruit","food"]},"lemon":{"unicode":"1f34b","unicode_alternates":"","name":"lemon","shortname":":lemon:","category":"food","emoji_order":"356","aliases":[],"aliases_ascii":[],"keywords":["fruit","food"]},"banana":{"unicode":"1f34c","unicode_alternates":"","name":"banana","shortname":":banana:","category":"food","emoji_order":"357","aliases":[],"aliases_ascii":[],"keywords":["fruit","penis","food"]},"watermelon":{"unicode":"1f349","unicode_alternates":"","name":"watermelon","shortname":":watermelon:","category":"food","emoji_order":"358","aliases":[],"aliases_ascii":[],"keywords":["fruit","food"]},"grapes":{"unicode":"1f347","unicode_alternates":"","name":"grapes","shortname":":grapes:","category":"food","emoji_order":"359","aliases":[],"aliases_ascii":[],"keywords":["fruit","food"]},"strawberry":{"unicode":"1f353","unicode_alternates":"","name":"strawberry","shortname":":strawberry:","category":"food","emoji_order":"360","aliases":[],"aliases_ascii":[],"keywords":["fruit","food"]},"melon":{"unicode":"1f348","unicode_alternates":"","name":"melon","shortname":":melon:","category":"food","emoji_order":"361","aliases":[],"aliases_ascii":[],"keywords":["fruit","boobs","food"]},"cherries":{"unicode":"1f352","unicode_alternates":"","name":"cherries","shortname":":cherries:","category":"food","emoji_order":"362","aliases":[],"aliases_ascii":[],"keywords":["fruit","food"]},"peach":{"unicode":"1f351","unicode_alternates":"","name":"peach","shortname":":peach:","category":"food","emoji_order":"363","aliases":[],"aliases_ascii":[],"keywords":["fruit","butt","food"]},"pineapple":{"unicode":"1f34d","unicode_alternates":"","name":"pineapple","shortname":":pineapple:","category":"food","emoji_order":"364","aliases":[],"aliases_ascii":[],"keywords":["fruit","food","tropical"]},"tomato":{"unicode":"1f345","unicode_alternates":"","name":"tomato","shortname":":tomato:","category":"food","emoji_order":"365","aliases":[],"aliases_ascii":[],"keywords":["fruit","vegetables","food"]},"eggplant":{"unicode":"1f346","unicode_alternates":"","name":"aubergine","shortname":":eggplant:","category":"food","emoji_order":"366","aliases":[],"aliases_ascii":[],"keywords":["vegetables","penis","food"]},"hot_pepper":{"unicode":"1f336","unicode_alternates":"1f336-fe0f","name":"hot pepper","shortname":":hot_pepper:","category":"food","emoji_order":"367","aliases":[],"aliases_ascii":[],"keywords":["vegetables","food"]},"corn":{"unicode":"1f33d","unicode_alternates":"","name":"ear of maize","shortname":":corn:","category":"food","emoji_order":"368","aliases":[],"aliases_ascii":[],"keywords":["vegetables","food"]},"sweet_potato":{"unicode":"1f360","unicode_alternates":"","name":"roasted sweet potato","shortname":":sweet_potato:","category":"food","emoji_order":"369","aliases":[],"aliases_ascii":[],"keywords":["vegetables","food"]},"honey_pot":{"unicode":"1f36f","unicode_alternates":"","name":"honey pot","shortname":":honey_pot:","category":"food","emoji_order":"370","aliases":[],"aliases_ascii":[],"keywords":["food","vagina"]},"bread":{"unicode":"1f35e","unicode_alternates":"","name":"bread","shortname":":bread:","category":"food","emoji_order":"371","aliases":[],"aliases_ascii":[],"keywords":["food"]},"cheese":{"unicode":"1f9c0","unicode_alternates":"","name":"cheese wedge","shortname":":cheese:","category":"food","emoji_order":"372","aliases":[":cheese_wedge:"],"aliases_ascii":[],"keywords":["food"]},"poultry_leg":{"unicode":"1f357","unicode_alternates":"","name":"poultry leg","shortname":":poultry_leg:","category":"food","emoji_order":"373","aliases":[],"aliases_ascii":[],"keywords":["food","holidays"]},"meat_on_bone":{"unicode":"1f356","unicode_alternates":"","name":"meat on bone","shortname":":meat_on_bone:","category":"food","emoji_order":"374","aliases":[],"aliases_ascii":[],"keywords":["food"]},"fried_shrimp":{"unicode":"1f364","unicode_alternates":"","name":"fried shrimp","shortname":":fried_shrimp:","category":"food","emoji_order":"375","aliases":[],"aliases_ascii":[],"keywords":["food"]},"egg":{"unicode":"1f373","unicode_alternates":"","name":"cooking","shortname":":egg:","category":"food","emoji_order":"376","aliases":[],"aliases_ascii":[],"keywords":["food"]},"hamburger":{"unicode":"1f354","unicode_alternates":"","name":"hamburger","shortname":":hamburger:","category":"food","emoji_order":"377","aliases":[],"aliases_ascii":[],"keywords":["america","food"]},"fries":{"unicode":"1f35f","unicode_alternates":"","name":"french fries","shortname":":fries:","category":"food","emoji_order":"378","aliases":[],"aliases_ascii":[],"keywords":["america","food"]},"hotdog":{"unicode":"1f32d","unicode_alternates":"","name":"hot dog","shortname":":hotdog:","category":"food","emoji_order":"379","aliases":[":hot_dog:"],"aliases_ascii":[],"keywords":["america","food"]},"pizza":{"unicode":"1f355","unicode_alternates":"","name":"slice of pizza","shortname":":pizza:","category":"food","emoji_order":"380","aliases":[],"aliases_ascii":[],"keywords":["italian","food","boys night","boys night"]},"spaghetti":{"unicode":"1f35d","unicode_alternates":"","name":"spaghetti","shortname":":spaghetti:","category":"food","emoji_order":"381","aliases":[],"aliases_ascii":[],"keywords":["noodles","pasta","italian","food"]},"taco":{"unicode":"1f32e","unicode_alternates":"","name":"taco","shortname":":taco:","category":"food","emoji_order":"382","aliases":[],"aliases_ascii":[],"keywords":["food","mexican","vagina"]},"burrito":{"unicode":"1f32f","unicode_alternates":"","name":"burrito","shortname":":burrito:","category":"food","emoji_order":"383","aliases":[],"aliases_ascii":[],"keywords":["food","mexican"]},"ramen":{"unicode":"1f35c","unicode_alternates":"","name":"steaming bowl","shortname":":ramen:","category":"food","emoji_order":"384","aliases":[],"aliases_ascii":[],"keywords":["noodles","ramen","japan","food"]},"stew":{"unicode":"1f372","unicode_alternates":"","name":"pot of food","shortname":":stew:","category":"food","emoji_order":"385","aliases":[],"aliases_ascii":[],"keywords":["food","steam","steam"]},"fish_cake":{"unicode":"1f365","unicode_alternates":"","name":"fish cake with swirl design","shortname":":fish_cake:","category":"food","emoji_order":"386","aliases":[],"aliases_ascii":[],"keywords":["sushi","food"]},"sushi":{"unicode":"1f363","unicode_alternates":"","name":"sushi","shortname":":sushi:","category":"food","emoji_order":"387","aliases":[],"aliases_ascii":[],"keywords":["sushi","japan","food"]},"bento":{"unicode":"1f371","unicode_alternates":"","name":"bento box","shortname":":bento:","category":"food","emoji_order":"388","aliases":[],"aliases_ascii":[],"keywords":["object","sushi","japan","food"]},"curry":{"unicode":"1f35b","unicode_alternates":"","name":"curry and rice","shortname":":curry:","category":"food","emoji_order":"389","aliases":[],"aliases_ascii":[],"keywords":["food"]},"rice_ball":{"unicode":"1f359","unicode_alternates":"","name":"rice ball","shortname":":rice_ball:","category":"food","emoji_order":"390","aliases":[],"aliases_ascii":[],"keywords":["sushi","japan","food"]},"rice":{"unicode":"1f35a","unicode_alternates":"","name":"cooked rice","shortname":":rice:","category":"food","emoji_order":"391","aliases":[],"aliases_ascii":[],"keywords":["sushi","japan","food"]},"rice_cracker":{"unicode":"1f358","unicode_alternates":"","name":"rice cracker","shortname":":rice_cracker:","category":"food","emoji_order":"392","aliases":[],"aliases_ascii":[],"keywords":["sushi","food"]},"oden":{"unicode":"1f362","unicode_alternates":"","name":"oden","shortname":":oden:","category":"food","emoji_order":"393","aliases":[],"aliases_ascii":[],"keywords":["food"]},"dango":{"unicode":"1f361","unicode_alternates":"","name":"dango","shortname":":dango:","category":"food","emoji_order":"394","aliases":[],"aliases_ascii":[],"keywords":["food"]},"shaved_ice":{"unicode":"1f367","unicode_alternates":"","name":"shaved ice","shortname":":shaved_ice:","category":"food","emoji_order":"395","aliases":[],"aliases_ascii":[],"keywords":["food"]},"ice_cream":{"unicode":"1f368","unicode_alternates":"","name":"ice cream","shortname":":ice_cream:","category":"food","emoji_order":"396","aliases":[],"aliases_ascii":[],"keywords":["food"]},"icecream":{"unicode":"1f366","unicode_alternates":"","name":"soft ice cream","shortname":":icecream:","category":"food","emoji_order":"397","aliases":[],"aliases_ascii":[],"keywords":["food"]},"cake":{"unicode":"1f370","unicode_alternates":"","name":"shortcake","shortname":":cake:","category":"food","emoji_order":"398","aliases":[],"aliases_ascii":[],"keywords":["food"]},"birthday":{"unicode":"1f382","unicode_alternates":"","name":"birthday cake","shortname":":birthday:","category":"food","emoji_order":"399","aliases":[],"aliases_ascii":[],"keywords":["birthday","food","parties","parties"]},"custard":{"unicode":"1f36e","unicode_alternates":"","name":"custard","shortname":":custard:","category":"food","emoji_order":"400","aliases":[":pudding:",":flan:"],"aliases_ascii":[],"keywords":["food"]},"candy":{"unicode":"1f36c","unicode_alternates":"","name":"candy","shortname":":candy:","category":"food","emoji_order":"401","aliases":[],"aliases_ascii":[],"keywords":["food","halloween"]},"lollipop":{"unicode":"1f36d","unicode_alternates":"","name":"lollipop","shortname":":lollipop:","category":"food","emoji_order":"402","aliases":[],"aliases_ascii":[],"keywords":["food","halloween"]},"chocolate_bar":{"unicode":"1f36b","unicode_alternates":"","name":"chocolate bar","shortname":":chocolate_bar:","category":"food","emoji_order":"403","aliases":[],"aliases_ascii":[],"keywords":["food","halloween"]},"popcorn":{"unicode":"1f37f","unicode_alternates":"","name":"popcorn","shortname":":popcorn:","category":"food","emoji_order":"404","aliases":[],"aliases_ascii":[],"keywords":["food","parties","parties"]},"doughnut":{"unicode":"1f369","unicode_alternates":"","name":"doughnut","shortname":":doughnut:","category":"food","emoji_order":"405","aliases":[],"aliases_ascii":[],"keywords":["food"]},"cookie":{"unicode":"1f36a","unicode_alternates":"","name":"cookie","shortname":":cookie:","category":"food","emoji_order":"406","aliases":[],"aliases_ascii":[],"keywords":["food","vagina"]},"beer":{"unicode":"1f37a","unicode_alternates":"","name":"beer mug","shortname":":beer:","category":"food","emoji_order":"407","aliases":[],"aliases_ascii":[],"keywords":["drink","beer","alcohol","parties","parties"]},"beers":{"unicode":"1f37b","unicode_alternates":"","name":"clinking beer mugs","shortname":":beers:","category":"food","emoji_order":"408","aliases":[],"aliases_ascii":[],"keywords":["drink","cheers","beer","alcohol","thank you","boys night","boys night","parties","parties"]},"wine_glass":{"unicode":"1f377","unicode_alternates":"","name":"wine glass","shortname":":wine_glass:","category":"food","emoji_order":"409","aliases":[],"aliases_ascii":[],"keywords":["drink","italian","alcohol","girls night","girls night","parties","parties"]},"cocktail":{"unicode":"1f378","unicode_alternates":"","name":"cocktail glass","shortname":":cocktail:","category":"food","emoji_order":"410","aliases":[],"aliases_ascii":[],"keywords":["drink","cocktail","alcohol","girls night","girls night","parties","parties"]},"tropical_drink":{"unicode":"1f379","unicode_alternates":"","name":"tropical drink","shortname":":tropical_drink:","category":"food","emoji_order":"411","aliases":[],"aliases_ascii":[],"keywords":["drink","cocktail","tropical","alcohol"]},"champagne":{"unicode":"1f37e","unicode_alternates":"","name":"bottle with popping cork","shortname":":champagne:","category":"food","emoji_order":"412","aliases":[":bottle_with_popping_cork:"],"aliases_ascii":[],"keywords":["drink","cheers","alcohol","parties","parties"]},"sake":{"unicode":"1f376","unicode_alternates":"","name":"sake bottle and cup","shortname":":sake:","category":"food","emoji_order":"413","aliases":[],"aliases_ascii":[],"keywords":["drink","japan","sake","alcohol","girls night","girls night"]},"tea":{"unicode":"1f375","unicode_alternates":"","name":"teacup without handle","shortname":":tea:","category":"food","emoji_order":"414","aliases":[],"aliases_ascii":[],"keywords":["drink","japan","caffeine","steam","steam","morning","morning"]},"coffee":{"unicode":"2615","unicode_alternates":"2615-fe0f","name":"hot beverage","shortname":":coffee:","category":"food","emoji_order":"415","aliases":[],"aliases_ascii":[],"keywords":["drink","caffeine","steam","steam","morning","morning"]},"baby_bottle":{"unicode":"1f37c","unicode_alternates":"","name":"baby bottle","shortname":":baby_bottle:","category":"food","emoji_order":"416","aliases":[],"aliases_ascii":[],"keywords":["drink","object","food","baby"]},"fork_and_knife":{"unicode":"1f374","unicode_alternates":"","name":"fork and knife","shortname":":fork_and_knife:","category":"food","emoji_order":"417","aliases":[],"aliases_ascii":[],"keywords":["object","weapon","food"]},"fork_knife_plate":{"unicode":"1f37d","unicode_alternates":"1f37d-fe0f","name":"fork and knife with plate","shortname":":fork_knife_plate:","category":"food","emoji_order":"418","aliases":[":fork_and_knife_with_plate:"],"aliases_ascii":[],"keywords":["object","food"]},"soccer":{"unicode":"26bd","unicode_alternates":"26bd-fe0f","name":"soccer ball","shortname":":soccer:","category":"activity","emoji_order":"419","aliases":[],"aliases_ascii":[],"keywords":["game","ball","sport","soccer","football"]},"basketball":{"unicode":"1f3c0","unicode_alternates":"","name":"basketball and hoop","shortname":":basketball:","category":"activity","emoji_order":"420","aliases":[],"aliases_ascii":[],"keywords":["game","ball","sport","basketball"]},"football":{"unicode":"1f3c8","unicode_alternates":"","name":"american football","shortname":":football:","category":"activity","emoji_order":"421","aliases":[],"aliases_ascii":[],"keywords":["america","game","ball","sport","football"]},"baseball":{"unicode":"26be","unicode_alternates":"26be-fe0f","name":"baseball","shortname":":baseball:","category":"activity","emoji_order":"422","aliases":[],"aliases_ascii":[],"keywords":["game","ball","sport","baseball"]},"tennis":{"unicode":"1f3be","unicode_alternates":"","name":"tennis racquet and ball","shortname":":tennis:","category":"activity","emoji_order":"423","aliases":[],"aliases_ascii":[],"keywords":["game","ball","sport","tennis"]},"volleyball":{"unicode":"1f3d0","unicode_alternates":"","name":"volleyball","shortname":":volleyball:","category":"activity","emoji_order":"424","aliases":[],"aliases_ascii":[],"keywords":["game","ball","sport","volleyball"]},"rugby_football":{"unicode":"1f3c9","unicode_alternates":"","name":"rugby football","shortname":":rugby_football:","category":"activity","emoji_order":"425","aliases":[],"aliases_ascii":[],"keywords":["game","sport","football"]},"8ball":{"unicode":"1f3b1","unicode_alternates":"","name":"billiards","shortname":":8ball:","category":"activity","emoji_order":"426","aliases":[],"aliases_ascii":[],"keywords":["game","ball","sport","billiards","luck","boys night","boys night"]},"golf":{"unicode":"26f3","unicode_alternates":"26f3-fe0f","name":"flag in hole","shortname":":golf:","category":"activity","emoji_order":"427","aliases":[],"aliases_ascii":[],"keywords":["game","ball","vacation","sport","golf","golf"]},"golfer":{"unicode":"1f3cc","unicode_alternates":"1f3cc-fe0f","name":"golfer","shortname":":golfer:","category":"activity","emoji_order":"428","aliases":[],"aliases_ascii":[],"keywords":["men","game","ball","vacation","sport","golf","golf"]},"ping_pong":{"unicode":"1f3d3","unicode_alternates":"","name":"table tennis paddle and ball","shortname":":ping_pong:","category":"activity","emoji_order":"429","aliases":[":table_tennis:"],"aliases_ascii":[],"keywords":["game","ball","sport","ping pong"]},"badminton":{"unicode":"1f3f8","unicode_alternates":"","name":"badminton racquet","shortname":":badminton:","category":"activity","emoji_order":"430","aliases":[],"aliases_ascii":[],"keywords":["game","sport","badminton"]},"hockey":{"unicode":"1f3d2","unicode_alternates":"","name":"ice hockey stick and puck","shortname":":hockey:","category":"activity","emoji_order":"431","aliases":[],"aliases_ascii":[],"keywords":["game","sport","hockey"]},"field_hockey":{"unicode":"1f3d1","unicode_alternates":"","name":"field hockey stick and ball","shortname":":field_hockey:","category":"activity","emoji_order":"432","aliases":[],"aliases_ascii":[],"keywords":["ball","sport","hockey"]},"cricket":{"unicode":"1f3cf","unicode_alternates":"","name":"cricket bat and ball","shortname":":cricket:","category":"activity","emoji_order":"433","aliases":[":cricket_bat_ball:"],"aliases_ascii":[],"keywords":["ball","sport","cricket"]},"ski":{"unicode":"1f3bf","unicode_alternates":"","name":"ski and ski boot","shortname":":ski:","category":"activity","emoji_order":"434","aliases":[],"aliases_ascii":[],"keywords":["cold","sport","skiing"]},"skier":{"unicode":"26f7","unicode_alternates":"26f7-fe0f","name":"skier","shortname":":skier:","category":"activity","emoji_order":"435","aliases":[],"aliases_ascii":[],"keywords":["hat","vacation","cold","sport","skiing"]},"snowboarder":{"unicode":"1f3c2","unicode_alternates":"","name":"snowboarder","shortname":":snowboarder:","category":"activity","emoji_order":"436","aliases":[],"aliases_ascii":[],"keywords":["hat","vacation","cold","sport","snowboarding"]},"ice_skate":{"unicode":"26f8","unicode_alternates":"26f8-fe0f","name":"ice skate","shortname":":ice_skate:","category":"activity","emoji_order":"437","aliases":[],"aliases_ascii":[],"keywords":["cold","sport","ice skating"]},"bow_and_arrow":{"unicode":"1f3f9","unicode_alternates":"","name":"bow and arrow","shortname":":bow_and_arrow:","category":"activity","emoji_order":"438","aliases":[":archery:"],"aliases_ascii":[],"keywords":["weapon","sport"]},"fishing_pole_and_fish":{"unicode":"1f3a3","unicode_alternates":"","name":"fishing pole and fish","shortname":":fishing_pole_and_fish:","category":"activity","emoji_order":"439","aliases":[],"aliases_ascii":[],"keywords":["vacation","sport","fishing"]},"rowboat":{"unicode":"1f6a3","unicode_alternates":"","name":"rowboat","shortname":":rowboat:","category":"activity","emoji_order":"440","aliases":[],"aliases_ascii":[],"keywords":["men","workout","sport","rowing","diversity","diversity"]},"swimmer":{"unicode":"1f3ca","unicode_alternates":"","name":"swimmer","shortname":":swimmer:","category":"activity","emoji_order":"441","aliases":[],"aliases_ascii":[],"keywords":["workout","sport","swim","diversity","diversity"]},"surfer":{"unicode":"1f3c4","unicode_alternates":"","name":"surfer","shortname":":surfer:","category":"activity","emoji_order":"442","aliases":[],"aliases_ascii":[],"keywords":["men","vacation","tropical","sport","diversity","diversity"]},"bath":{"unicode":"1f6c0","unicode_alternates":"","name":"bath","shortname":":bath:","category":"activity","emoji_order":"443","aliases":[],"aliases_ascii":[],"keywords":["bathroom","tired","diversity","diversity","steam","steam"]},"basketball_player":{"unicode":"26f9","unicode_alternates":"26f9-fe0f","name":"person with ball","shortname":":basketball_player:","category":"activity","emoji_order":"444","aliases":[":person_with_ball:"],"aliases_ascii":[],"keywords":["men","game","ball","sport","basketball","diversity","diversity"]},"lifter":{"unicode":"1f3cb","unicode_alternates":"1f3cb-fe0f","name":"weight lifter","shortname":":lifter:","category":"activity","emoji_order":"445","aliases":[":weight_lifter:"],"aliases_ascii":[],"keywords":["men","workout","flex","sport","weight lifting","win","win","diversity","diversity"]},"bicyclist":{"unicode":"1f6b4","unicode_alternates":"","name":"bicyclist","shortname":":bicyclist:","category":"activity","emoji_order":"446","aliases":[],"aliases_ascii":[],"keywords":["men","workout","sport","bike","diversity","diversity"]},"mountain_bicyclist":{"unicode":"1f6b5","unicode_alternates":"","name":"mountain bicyclist","shortname":":mountain_bicyclist:","category":"activity","emoji_order":"447","aliases":[],"aliases_ascii":[],"keywords":["men","sport","bike","diversity","diversity"]},"horse_racing":{"unicode":"1f3c7","unicode_alternates":"","name":"horse racing","shortname":":horse_racing:","category":"activity","emoji_order":"448","aliases":[],"aliases_ascii":[],"keywords":["men","sport","horse racing"]},"levitate":{"unicode":"1f574","unicode_alternates":"1f574-fe0f","name":"man in business suit levitating","shortname":":levitate:","category":"activity","emoji_order":"449","aliases":[":man_in_business_suit_levitating:"],"aliases_ascii":[],"keywords":["men","job","job"]},"trophy":{"unicode":"1f3c6","unicode_alternates":"","name":"trophy","shortname":":trophy:","category":"activity","emoji_order":"450","aliases":[],"aliases_ascii":[],"keywords":["object","game","award","win","win","perfect","perfect","parties","parties"]},"running_shirt_with_sash":{"unicode":"1f3bd","unicode_alternates":"","name":"running shirt with sash","shortname":":running_shirt_with_sash:","category":"activity","emoji_order":"451","aliases":[],"aliases_ascii":[],"keywords":["award"]},"medal":{"unicode":"1f3c5","unicode_alternates":"","name":"sports medal","shortname":":medal:","category":"activity","emoji_order":"452","aliases":[":sports_medal:"],"aliases_ascii":[],"keywords":["object","award","sport","win","win","perfect","perfect"]},"military_medal":{"unicode":"1f396","unicode_alternates":"1f396-fe0f","name":"military medal","shortname":":military_medal:","category":"activity","emoji_order":"453","aliases":[],"aliases_ascii":[],"keywords":["object","award","win","win"]},"reminder_ribbon":{"unicode":"1f397","unicode_alternates":"1f397-fe0f","name":"reminder ribbon","shortname":":reminder_ribbon:","category":"activity","emoji_order":"454","aliases":[],"aliases_ascii":[],"keywords":["award"]},"rosette":{"unicode":"1f3f5","unicode_alternates":"1f3f5-fe0f","name":"rosette","shortname":":rosette:","category":"activity","emoji_order":"455","aliases":[],"aliases_ascii":[],"keywords":["tropical"]},"ticket":{"unicode":"1f3ab","unicode_alternates":"","name":"ticket","shortname":":ticket:","category":"activity","emoji_order":"456","aliases":[],"aliases_ascii":[],"keywords":["theatre","movie","parties","parties"]},"tickets":{"unicode":"1f39f","unicode_alternates":"1f39f-fe0f","name":"admission tickets","shortname":":tickets:","category":"activity","emoji_order":"457","aliases":[":admission_tickets:"],"aliases_ascii":[],"keywords":["theatre","movie","parties","parties"]},"performing_arts":{"unicode":"1f3ad","unicode_alternates":"","name":"performing arts","shortname":":performing_arts:","category":"activity","emoji_order":"458","aliases":[],"aliases_ascii":[],"keywords":["theatre","movie"]},"art":{"unicode":"1f3a8","unicode_alternates":"","name":"artist palette","shortname":":art:","category":"activity","emoji_order":"459","aliases":[],"aliases_ascii":[],"keywords":[]},"circus_tent":{"unicode":"1f3aa","unicode_alternates":"","name":"circus tent","shortname":":circus_tent:","category":"activity","emoji_order":"460","aliases":[],"aliases_ascii":[],"keywords":["circus tent"]},"microphone":{"unicode":"1f3a4","unicode_alternates":"","name":"microphone","shortname":":microphone:","category":"activity","emoji_order":"461","aliases":[],"aliases_ascii":[],"keywords":["instruments"]},"headphones":{"unicode":"1f3a7","unicode_alternates":"","name":"headphone","shortname":":headphones:","category":"activity","emoji_order":"462","aliases":[],"aliases_ascii":[],"keywords":["instruments"]},"musical_score":{"unicode":"1f3bc","unicode_alternates":"","name":"musical score","shortname":":musical_score:","category":"activity","emoji_order":"463","aliases":[],"aliases_ascii":[],"keywords":["instruments"]},"musical_keyboard":{"unicode":"1f3b9","unicode_alternates":"","name":"musical keyboard","shortname":":musical_keyboard:","category":"activity","emoji_order":"464","aliases":[],"aliases_ascii":[],"keywords":["instruments"]},"saxophone":{"unicode":"1f3b7","unicode_alternates":"","name":"saxophone","shortname":":saxophone:","category":"activity","emoji_order":"465","aliases":[],"aliases_ascii":[],"keywords":["instruments"]},"trumpet":{"unicode":"1f3ba","unicode_alternates":"","name":"trumpet","shortname":":trumpet:","category":"activity","emoji_order":"466","aliases":[],"aliases_ascii":[],"keywords":["instruments"]},"guitar":{"unicode":"1f3b8","unicode_alternates":"","name":"guitar","shortname":":guitar:","category":"activity","emoji_order":"467","aliases":[],"aliases_ascii":[],"keywords":["instruments"]},"violin":{"unicode":"1f3bb","unicode_alternates":"","name":"violin","shortname":":violin:","category":"activity","emoji_order":"468","aliases":[],"aliases_ascii":[],"keywords":["instruments","sarcastic","sarcastic"]},"clapper":{"unicode":"1f3ac","unicode_alternates":"","name":"clapper board","shortname":":clapper:","category":"activity","emoji_order":"469","aliases":[],"aliases_ascii":[],"keywords":["movie"]},"video_game":{"unicode":"1f3ae","unicode_alternates":"","name":"video game","shortname":":video_game:","category":"activity","emoji_order":"470","aliases":[],"aliases_ascii":[],"keywords":["electronics","game","boys night","boys night"]},"space_invader":{"unicode":"1f47e","unicode_alternates":"","name":"alien monster","shortname":":space_invader:","category":"activity","emoji_order":"471","aliases":[],"aliases_ascii":[],"keywords":["monster","alien"]},"dart":{"unicode":"1f3af","unicode_alternates":"","name":"direct hit","shortname":":dart:","category":"activity","emoji_order":"472","aliases":[],"aliases_ascii":[],"keywords":["game","sport","boys night","boys night"]},"game_die":{"unicode":"1f3b2","unicode_alternates":"","name":"game die","shortname":":game_die:","category":"activity","emoji_order":"473","aliases":[],"aliases_ascii":[],"keywords":["object","game","boys night","boys night"]},"slot_machine":{"unicode":"1f3b0","unicode_alternates":"","name":"slot machine","shortname":":slot_machine:","category":"activity","emoji_order":"474","aliases":[],"aliases_ascii":[],"keywords":["game","boys night","boys night"]},"bowling":{"unicode":"1f3b3","unicode_alternates":"","name":"bowling","shortname":":bowling:","category":"activity","emoji_order":"475","aliases":[],"aliases_ascii":[],"keywords":["game","ball","sport","boys night","boys night"]},"red_car":{"unicode":"1f697","unicode_alternates":"","name":"automobile","shortname":":red_car:","category":"travel","emoji_order":"476","aliases":[],"aliases_ascii":[],"keywords":["transportation","car","travel"]},"taxi":{"unicode":"1f695","unicode_alternates":"","name":"taxi","shortname":":taxi:","category":"travel","emoji_order":"477","aliases":[],"aliases_ascii":[],"keywords":["transportation","car","travel"]},"blue_car":{"unicode":"1f699","unicode_alternates":"","name":"recreational vehicle","shortname":":blue_car:","category":"travel","emoji_order":"478","aliases":[],"aliases_ascii":[],"keywords":["transportation","car","travel"]},"bus":{"unicode":"1f68c","unicode_alternates":"","name":"bus","shortname":":bus:","category":"travel","emoji_order":"479","aliases":[],"aliases_ascii":[],"keywords":["transportation","bus","office"]},"trolleybus":{"unicode":"1f68e","unicode_alternates":"","name":"trolleybus","shortname":":trolleybus:","category":"travel","emoji_order":"480","aliases":[],"aliases_ascii":[],"keywords":["transportation","bus","travel"]},"race_car":{"unicode":"1f3ce","unicode_alternates":"1f3ce-fe0f","name":"racing car","shortname":":race_car:","category":"travel","emoji_order":"481","aliases":[":racing_car:"],"aliases_ascii":[],"keywords":["transportation","car"]},"police_car":{"unicode":"1f693","unicode_alternates":"","name":"police car","shortname":":police_car:","category":"travel","emoji_order":"482","aliases":[],"aliases_ascii":[],"keywords":["transportation","car","police","police","911","911"]},"ambulance":{"unicode":"1f691","unicode_alternates":"","name":"ambulance","shortname":":ambulance:","category":"travel","emoji_order":"483","aliases":[],"aliases_ascii":[],"keywords":["transportation","911","911"]},"fire_engine":{"unicode":"1f692","unicode_alternates":"","name":"fire engine","shortname":":fire_engine:","category":"travel","emoji_order":"484","aliases":[],"aliases_ascii":[],"keywords":["transportation","truck","911","911"]},"minibus":{"unicode":"1f690","unicode_alternates":"","name":"minibus","shortname":":minibus:","category":"travel","emoji_order":"485","aliases":[],"aliases_ascii":[],"keywords":["transportation","bus"]},"truck":{"unicode":"1f69a","unicode_alternates":"","name":"delivery truck","shortname":":truck:","category":"travel","emoji_order":"486","aliases":[],"aliases_ascii":[],"keywords":["transportation","truck"]},"articulated_lorry":{"unicode":"1f69b","unicode_alternates":"","name":"articulated lorry","shortname":":articulated_lorry:","category":"travel","emoji_order":"487","aliases":[],"aliases_ascii":[],"keywords":["transportation","truck"]},"tractor":{"unicode":"1f69c","unicode_alternates":"","name":"tractor","shortname":":tractor:","category":"travel","emoji_order":"488","aliases":[],"aliases_ascii":[],"keywords":["transportation"]},"motorcycle":{"unicode":"1f3cd","unicode_alternates":"1f3cd-fe0f","name":"racing motorcycle","shortname":":motorcycle:","category":"travel","emoji_order":"489","aliases":[":racing_motorcycle:"],"aliases_ascii":[],"keywords":["transportation","travel","bike"]},"bike":{"unicode":"1f6b2","unicode_alternates":"","name":"bicycle","shortname":":bike:","category":"travel","emoji_order":"490","aliases":[],"aliases_ascii":[],"keywords":["transportation","travel","bike"]},"rotating_light":{"unicode":"1f6a8","unicode_alternates":"","name":"police cars revolving light","shortname":":rotating_light:","category":"travel","emoji_order":"491","aliases":[],"aliases_ascii":[],"keywords":["transportation","object","police","police","911","911"]},"oncoming_police_car":{"unicode":"1f694","unicode_alternates":"","name":"oncoming police car","shortname":":oncoming_police_car:","category":"travel","emoji_order":"492","aliases":[],"aliases_ascii":[],"keywords":["transportation","car","police","police","911","911"]},"oncoming_bus":{"unicode":"1f68d","unicode_alternates":"","name":"oncoming bus","shortname":":oncoming_bus:","category":"travel","emoji_order":"493","aliases":[],"aliases_ascii":[],"keywords":["transportation","bus","travel"]},"oncoming_automobile":{"unicode":"1f698","unicode_alternates":"","name":"oncoming automobile","shortname":":oncoming_automobile:","category":"travel","emoji_order":"494","aliases":[],"aliases_ascii":[],"keywords":["transportation","car","travel"]},"oncoming_taxi":{"unicode":"1f696","unicode_alternates":"","name":"oncoming taxi","shortname":":oncoming_taxi:","category":"travel","emoji_order":"495","aliases":[],"aliases_ascii":[],"keywords":["transportation","car","travel"]},"aerial_tramway":{"unicode":"1f6a1","unicode_alternates":"","name":"aerial tramway","shortname":":aerial_tramway:","category":"travel","emoji_order":"496","aliases":[],"aliases_ascii":[],"keywords":["transportation","travel","train"]},"mountain_cableway":{"unicode":"1f6a0","unicode_alternates":"","name":"mountain cableway","shortname":":mountain_cableway:","category":"travel","emoji_order":"497","aliases":[],"aliases_ascii":[],"keywords":["transportation","travel","train"]},"suspension_railway":{"unicode":"1f69f","unicode_alternates":"","name":"suspension railway","shortname":":suspension_railway:","category":"travel","emoji_order":"498","aliases":[],"aliases_ascii":[],"keywords":["transportation","travel","train"]},"railway_car":{"unicode":"1f683","unicode_alternates":"","name":"railway car","shortname":":railway_car:","category":"travel","emoji_order":"499","aliases":[],"aliases_ascii":[],"keywords":["transportation","travel","train"]},"train":{"unicode":"1f68b","unicode_alternates":"","name":"tram car","shortname":":train:","category":"travel","emoji_order":"500","aliases":[],"aliases_ascii":[],"keywords":["transportation","travel","train"]},"monorail":{"unicode":"1f69d","unicode_alternates":"","name":"monorail","shortname":":monorail:","category":"travel","emoji_order":"501","aliases":[],"aliases_ascii":[],"keywords":["transportation","travel","train","vacation"]},"bullettrain_side":{"unicode":"1f684","unicode_alternates":"","name":"high-speed train","shortname":":bullettrain_side:","category":"travel","emoji_order":"502","aliases":[],"aliases_ascii":[],"keywords":["transportation","travel","train"]},"bullettrain_front":{"unicode":"1f685","unicode_alternates":"","name":"high-speed train with bullet nose","shortname":":bullettrain_front:","category":"travel","emoji_order":"503","aliases":[],"aliases_ascii":[],"keywords":["transportation","travel","train"]},"light_rail":{"unicode":"1f688","unicode_alternates":"","name":"light rail","shortname":":light_rail:","category":"travel","emoji_order":"504","aliases":[],"aliases_ascii":[],"keywords":["transportation","travel","train"]},"mountain_railway":{"unicode":"1f69e","unicode_alternates":"","name":"mountain railway","shortname":":mountain_railway:","category":"travel","emoji_order":"505","aliases":[],"aliases_ascii":[],"keywords":["transportation","travel","train"]},"steam_locomotive":{"unicode":"1f682","unicode_alternates":"","name":"steam locomotive","shortname":":steam_locomotive:","category":"travel","emoji_order":"506","aliases":[],"aliases_ascii":[],"keywords":["transportation","travel","train","steam","steam"]},"train2":{"unicode":"1f686","unicode_alternates":"","name":"train","shortname":":train2:","category":"travel","emoji_order":"507","aliases":[],"aliases_ascii":[],"keywords":["transportation","travel","train"]},"metro":{"unicode":"1f687","unicode_alternates":"","name":"metro","shortname":":metro:","category":"travel","emoji_order":"508","aliases":[],"aliases_ascii":[],"keywords":["transportation","travel","train"]},"tram":{"unicode":"1f68a","unicode_alternates":"","name":"tram","shortname":":tram:","category":"travel","emoji_order":"509","aliases":[],"aliases_ascii":[],"keywords":["transportation","travel","train"]},"station":{"unicode":"1f689","unicode_alternates":"","name":"station","shortname":":station:","category":"travel","emoji_order":"510","aliases":[],"aliases_ascii":[],"keywords":["transportation","travel","train"]},"helicopter":{"unicode":"1f681","unicode_alternates":"","name":"helicopter","shortname":":helicopter:","category":"travel","emoji_order":"511","aliases":[],"aliases_ascii":[],"keywords":["transportation","plane","travel","fly","fly"]},"airplane_small":{"unicode":"1f6e9","unicode_alternates":"1f6e9-fe0f","name":"small airplane","shortname":":airplane_small:","category":"travel","emoji_order":"512","aliases":[":small_airplane:"],"aliases_ascii":[],"keywords":["transportation","plane","travel","vacation","fly","fly"]},"airplane":{"unicode":"2708","unicode_alternates":"2708-fe0f","name":"airplane","shortname":":airplane:","category":"travel","emoji_order":"513","aliases":[],"aliases_ascii":[],"keywords":["transportation","plane","travel","vacation","fly","fly"]},"airplane_departure":{"unicode":"1f6eb","unicode_alternates":"","name":"airplane departure","shortname":":airplane_departure:","category":"travel","emoji_order":"514","aliases":[],"aliases_ascii":[],"keywords":["transportation","plane","travel","vacation","fly","fly"]},"airplane_arriving":{"unicode":"1f6ec","unicode_alternates":"","name":"airplane arriving","shortname":":airplane_arriving:","category":"travel","emoji_order":"515","aliases":[],"aliases_ascii":[],"keywords":["transportation","plane","travel","vacation","fly","fly"]},"sailboat":{"unicode":"26f5","unicode_alternates":"26f5-fe0f","name":"sailboat","shortname":":sailboat:","category":"travel","emoji_order":"516","aliases":[],"aliases_ascii":[],"keywords":["transportation","travel","boat","vacation"]},"motorboat":{"unicode":"1f6e5","unicode_alternates":"1f6e5-fe0f","name":"motorboat","shortname":":motorboat:","category":"travel","emoji_order":"517","aliases":[],"aliases_ascii":[],"keywords":["transportation","travel","boat"]},"speedboat":{"unicode":"1f6a4","unicode_alternates":"","name":"speedboat","shortname":":speedboat:","category":"travel","emoji_order":"518","aliases":[],"aliases_ascii":[],"keywords":["transportation","travel","boat","vacation","tropical"]},"ferry":{"unicode":"26f4","unicode_alternates":"26f4-fe0f","name":"ferry","shortname":":ferry:","category":"travel","emoji_order":"519","aliases":[],"aliases_ascii":[],"keywords":["transportation","travel","boat","vacation"]},"cruise_ship":{"unicode":"1f6f3","unicode_alternates":"1f6f3-fe0f","name":"passenger ship","shortname":":cruise_ship:","category":"travel","emoji_order":"520","aliases":[":passenger_ship:"],"aliases_ascii":[],"keywords":["transportation","travel","boat","vacation"]},"rocket":{"unicode":"1f680","unicode_alternates":"","name":"rocket","shortname":":rocket:","category":"travel","emoji_order":"521","aliases":[],"aliases_ascii":[],"keywords":["transportation","object","space","fly","fly","blast","blast"]},"satellite_orbital":{"unicode":"1f6f0","unicode_alternates":"1f6f0-fe0f","name":"satellite","shortname":":satellite_orbital:","category":"travel","emoji_order":"522","aliases":[],"aliases_ascii":[],"keywords":["object"]},"seat":{"unicode":"1f4ba","unicode_alternates":"","name":"seat","shortname":":seat:","category":"travel","emoji_order":"523","aliases":[],"aliases_ascii":[],"keywords":["transportation","object","travel","vacation"]},"anchor":{"unicode":"2693","unicode_alternates":"2693-fe0f","name":"anchor","shortname":":anchor:","category":"travel","emoji_order":"524","aliases":[],"aliases_ascii":[],"keywords":["object","travel","boat","vacation"]},"construction":{"unicode":"1f6a7","unicode_alternates":"","name":"construction sign","shortname":":construction:","category":"travel","emoji_order":"525","aliases":[],"aliases_ascii":[],"keywords":["object"]},"fuelpump":{"unicode":"26fd","unicode_alternates":"26fd-fe0f","name":"fuel pump","shortname":":fuelpump:","category":"travel","emoji_order":"526","aliases":[],"aliases_ascii":[],"keywords":["object","gas pump"]},"busstop":{"unicode":"1f68f","unicode_alternates":"","name":"bus stop","shortname":":busstop:","category":"travel","emoji_order":"527","aliases":[],"aliases_ascii":[],"keywords":["object"]},"vertical_traffic_light":{"unicode":"1f6a6","unicode_alternates":"","name":"vertical traffic light","shortname":":vertical_traffic_light:","category":"travel","emoji_order":"528","aliases":[],"aliases_ascii":[],"keywords":["object","stop light"]},"traffic_light":{"unicode":"1f6a5","unicode_alternates":"","name":"horizontal traffic light","shortname":":traffic_light:","category":"travel","emoji_order":"529","aliases":[],"aliases_ascii":[],"keywords":["object","stop light"]},"checkered_flag":{"unicode":"1f3c1","unicode_alternates":"","name":"chequered flag","shortname":":checkered_flag:","category":"travel","emoji_order":"530","aliases":[],"aliases_ascii":[],"keywords":["object"]},"ship":{"unicode":"1f6a2","unicode_alternates":"","name":"ship","shortname":":ship:","category":"travel","emoji_order":"531","aliases":[],"aliases_ascii":[],"keywords":["transportation","travel","boat","vacation"]},"ferris_wheel":{"unicode":"1f3a1","unicode_alternates":"","name":"ferris wheel","shortname":":ferris_wheel:","category":"travel","emoji_order":"532","aliases":[],"aliases_ascii":[],"keywords":["places","vacation","ferris wheel"]},"roller_coaster":{"unicode":"1f3a2","unicode_alternates":"","name":"roller coaster","shortname":":roller_coaster:","category":"travel","emoji_order":"533","aliases":[],"aliases_ascii":[],"keywords":["places","vacation","roller coaster"]},"carousel_horse":{"unicode":"1f3a0","unicode_alternates":"","name":"carousel horse","shortname":":carousel_horse:","category":"travel","emoji_order":"534","aliases":[],"aliases_ascii":[],"keywords":["places","object","vacation","roller coaster","carousel"]},"construction_site":{"unicode":"1f3d7","unicode_alternates":"1f3d7-fe0f","name":"building construction","shortname":":construction_site:","category":"travel","emoji_order":"535","aliases":[":building_construction:"],"aliases_ascii":[],"keywords":["building","crane"]},"foggy":{"unicode":"1f301","unicode_alternates":"","name":"foggy","shortname":":foggy:","category":"travel","emoji_order":"536","aliases":[],"aliases_ascii":[],"keywords":["places","building","sky","travel","vacation"]},"tokyo_tower":{"unicode":"1f5fc","unicode_alternates":"","name":"tokyo tower","shortname":":tokyo_tower:","category":"travel","emoji_order":"537","aliases":[],"aliases_ascii":[],"keywords":["places","travel","vacation","eiffel tower"]},"factory":{"unicode":"1f3ed","unicode_alternates":"","name":"factory","shortname":":factory:","category":"travel","emoji_order":"538","aliases":[],"aliases_ascii":[],"keywords":["places","building","travel","steam","steam"]},"fountain":{"unicode":"26f2","unicode_alternates":"26f2-fe0f","name":"fountain","shortname":":fountain:","category":"travel","emoji_order":"539","aliases":[],"aliases_ascii":[],"keywords":["travel","vacation"]},"rice_scene":{"unicode":"1f391","unicode_alternates":"","name":"moon viewing ceremony","shortname":":rice_scene:","category":"travel","emoji_order":"540","aliases":[],"aliases_ascii":[],"keywords":["places","space","sky","travel"]},"mountain":{"unicode":"26f0","unicode_alternates":"26f0-fe0f","name":"mountain","shortname":":mountain:","category":"travel","emoji_order":"541","aliases":[],"aliases_ascii":[],"keywords":["places","travel","vacation","camp"]},"mountain_snow":{"unicode":"1f3d4","unicode_alternates":"1f3d4-fe0f","name":"snow capped mountain","shortname":":mountain_snow:","category":"travel","emoji_order":"542","aliases":[":snow_capped_mountain:"],"aliases_ascii":[],"keywords":["places","travel","vacation","cold","camp"]},"mount_fuji":{"unicode":"1f5fb","unicode_alternates":"","name":"mount fuji","shortname":":mount_fuji:","category":"travel","emoji_order":"543","aliases":[],"aliases_ascii":[],"keywords":["places","travel","vacation","cold","camp"]},"volcano":{"unicode":"1f30b","unicode_alternates":"","name":"volcano","shortname":":volcano:","category":"travel","emoji_order":"544","aliases":[],"aliases_ascii":[],"keywords":["places","tropical"]},"japan":{"unicode":"1f5fe","unicode_alternates":"","name":"silhouette of japan","shortname":":japan:","category":"travel","emoji_order":"545","aliases":[],"aliases_ascii":[],"keywords":["places","travel","map","vacation","tropical"]},"camping":{"unicode":"1f3d5","unicode_alternates":"1f3d5-fe0f","name":"camping","shortname":":camping:","category":"travel","emoji_order":"546","aliases":[],"aliases_ascii":[],"keywords":["places","travel","vacation","camp"]},"tent":{"unicode":"26fa","unicode_alternates":"26fa-fe0f","name":"tent","shortname":":tent:","category":"travel","emoji_order":"547","aliases":[],"aliases_ascii":[],"keywords":["places","travel","vacation","camp"]},"park":{"unicode":"1f3de","unicode_alternates":"1f3de-fe0f","name":"national park","shortname":":park:","category":"travel","emoji_order":"548","aliases":[":national_park:"],"aliases_ascii":[],"keywords":["travel","vacation","park","camp"]},"motorway":{"unicode":"1f6e3","unicode_alternates":"1f6e3-fe0f","name":"motorway","shortname":":motorway:","category":"travel","emoji_order":"549","aliases":[],"aliases_ascii":[],"keywords":["travel","vacation","camp"]},"railway_track":{"unicode":"1f6e4","unicode_alternates":"1f6e4-fe0f","name":"railway track","shortname":":railway_track:","category":"travel","emoji_order":"550","aliases":[":railroad_track:"],"aliases_ascii":[],"keywords":["travel","train","vacation"]},"sunrise":{"unicode":"1f305","unicode_alternates":"","name":"sunrise","shortname":":sunrise:","category":"travel","emoji_order":"551","aliases":[],"aliases_ascii":[],"keywords":["places","sky","travel","vacation","tropical","day","sun","hump day","hump day","morning","morning"]},"sunrise_over_mountains":{"unicode":"1f304","unicode_alternates":"","name":"sunrise over mountains","shortname":":sunrise_over_mountains:","category":"travel","emoji_order":"552","aliases":[],"aliases_ascii":[],"keywords":["places","sky","travel","vacation","day","sun","camp","morning","morning"]},"desert":{"unicode":"1f3dc","unicode_alternates":"1f3dc-fe0f","name":"desert","shortname":":desert:","category":"travel","emoji_order":"553","aliases":[],"aliases_ascii":[],"keywords":["places","travel","vacation","hot","hot"]},"beach":{"unicode":"1f3d6","unicode_alternates":"1f3d6-fe0f","name":"beach with umbrella","shortname":":beach:","category":"travel","emoji_order":"554","aliases":[":beach_with_umbrella:"],"aliases_ascii":[],"keywords":["places","travel","vacation","tropical","beach","swim"]},"island":{"unicode":"1f3dd","unicode_alternates":"1f3dd-fe0f","name":"desert island","shortname":":island:","category":"travel","emoji_order":"555","aliases":[":desert_island:"],"aliases_ascii":[],"keywords":["places","travel","vacation","tropical","beach","swim"]},"city_sunset":{"unicode":"1f307","unicode_alternates":"","name":"sunset over buildings","shortname":":city_sunset:","category":"travel","emoji_order":"556","aliases":[":city_sunrise:"],"aliases_ascii":[],"keywords":["places","building","sky","vacation"]},"city_dusk":{"unicode":"1f306","unicode_alternates":"","name":"cityscape at dusk","shortname":":city_dusk:","category":"travel","emoji_order":"557","aliases":[],"aliases_ascii":[],"keywords":["places","building"]},"cityscape":{"unicode":"1f3d9","unicode_alternates":"1f3d9-fe0f","name":"cityscape","shortname":":cityscape:","category":"travel","emoji_order":"558","aliases":[],"aliases_ascii":[],"keywords":["places","building","vacation"]},"night_with_stars":{"unicode":"1f303","unicode_alternates":"","name":"night with stars","shortname":":night_with_stars:","category":"travel","emoji_order":"559","aliases":[],"aliases_ascii":[],"keywords":["places","building","sky","vacation","goodnight","goodnight"]},"bridge_at_night":{"unicode":"1f309","unicode_alternates":"","name":"bridge at night","shortname":":bridge_at_night:","category":"travel","emoji_order":"560","aliases":[],"aliases_ascii":[],"keywords":["places","travel","vacation","goodnight","goodnight"]},"milky_way":{"unicode":"1f30c","unicode_alternates":"","name":"milky way","shortname":":milky_way:","category":"travel","emoji_order":"561","aliases":[],"aliases_ascii":[],"keywords":["places","space","sky","travel","vacation"]},"stars":{"unicode":"1f320","unicode_alternates":"","name":"shooting star","shortname":":stars:","category":"travel","emoji_order":"562","aliases":[],"aliases_ascii":[],"keywords":["space"]},"sparkler":{"unicode":"1f387","unicode_alternates":"","name":"firework sparkler","shortname":":sparkler:","category":"travel","emoji_order":"563","aliases":[],"aliases_ascii":[],"keywords":["parties","parties"]},"fireworks":{"unicode":"1f386","unicode_alternates":"","name":"fireworks","shortname":":fireworks:","category":"travel","emoji_order":"564","aliases":[],"aliases_ascii":[],"keywords":["parties","parties"]},"rainbow":{"unicode":"1f308","unicode_alternates":"","name":"rainbow","shortname":":rainbow:","category":"travel","emoji_order":"565","aliases":[],"aliases_ascii":[],"keywords":["weather","gay","sky","rain"]},"homes":{"unicode":"1f3d8","unicode_alternates":"1f3d8-fe0f","name":"house buildings","shortname":":homes:","category":"travel","emoji_order":"566","aliases":[":house_buildings:"],"aliases_ascii":[],"keywords":["places","building","house"]},"european_castle":{"unicode":"1f3f0","unicode_alternates":"","name":"european castle","shortname":":european_castle:","category":"travel","emoji_order":"567","aliases":[],"aliases_ascii":[],"keywords":["places","building","travel","vacation"]},"japanese_castle":{"unicode":"1f3ef","unicode_alternates":"","name":"japanese castle","shortname":":japanese_castle:","category":"travel","emoji_order":"568","aliases":[],"aliases_ascii":[],"keywords":["places","building","travel","vacation"]},"stadium":{"unicode":"1f3df","unicode_alternates":"1f3df-fe0f","name":"stadium","shortname":":stadium:","category":"travel","emoji_order":"569","aliases":[],"aliases_ascii":[],"keywords":["places","building","travel","vacation","boys night","boys night"]},"statue_of_liberty":{"unicode":"1f5fd","unicode_alternates":"","name":"statue of liberty","shortname":":statue_of_liberty:","category":"travel","emoji_order":"570","aliases":[],"aliases_ascii":[],"keywords":["places","america","travel","vacation","statue of liberty","free speech","free speech"]},"house":{"unicode":"1f3e0","unicode_alternates":"","name":"house building","shortname":":house:","category":"travel","emoji_order":"571","aliases":[],"aliases_ascii":[],"keywords":["places","building","house"]},"house_with_garden":{"unicode":"1f3e1","unicode_alternates":"","name":"house with garden","shortname":":house_with_garden:","category":"travel","emoji_order":"572","aliases":[],"aliases_ascii":[],"keywords":["places","building","house"]},"house_abandoned":{"unicode":"1f3da","unicode_alternates":"1f3da-fe0f","name":"derelict house building","shortname":":house_abandoned:","category":"travel","emoji_order":"573","aliases":[":derelict_house_building:"],"aliases_ascii":[],"keywords":["places","building","house"]},"office":{"unicode":"1f3e2","unicode_alternates":"","name":"office building","shortname":":office:","category":"travel","emoji_order":"574","aliases":[],"aliases_ascii":[],"keywords":["places","building","work"]},"department_store":{"unicode":"1f3ec","unicode_alternates":"","name":"department store","shortname":":department_store:","category":"travel","emoji_order":"575","aliases":[],"aliases_ascii":[],"keywords":["places","building"]},"post_office":{"unicode":"1f3e3","unicode_alternates":"","name":"japanese post office","shortname":":post_office:","category":"travel","emoji_order":"576","aliases":[],"aliases_ascii":[],"keywords":["places","building","post office"]},"european_post_office":{"unicode":"1f3e4","unicode_alternates":"","name":"european post office","shortname":":european_post_office:","category":"travel","emoji_order":"577","aliases":[],"aliases_ascii":[],"keywords":["places","building","post office"]},"hospital":{"unicode":"1f3e5","unicode_alternates":"","name":"hospital","shortname":":hospital:","category":"travel","emoji_order":"578","aliases":[],"aliases_ascii":[],"keywords":["places","building","health","911","911"]},"bank":{"unicode":"1f3e6","unicode_alternates":"","name":"bank","shortname":":bank:","category":"travel","emoji_order":"579","aliases":[],"aliases_ascii":[],"keywords":["places","building"]},"hotel":{"unicode":"1f3e8","unicode_alternates":"","name":"hotel","shortname":":hotel:","category":"travel","emoji_order":"580","aliases":[],"aliases_ascii":[],"keywords":["places","building","vacation"]},"convenience_store":{"unicode":"1f3ea","unicode_alternates":"","name":"convenience store","shortname":":convenience_store:","category":"travel","emoji_order":"581","aliases":[],"aliases_ascii":[],"keywords":["places","building"]},"school":{"unicode":"1f3eb","unicode_alternates":"","name":"school","shortname":":school:","category":"travel","emoji_order":"582","aliases":[],"aliases_ascii":[],"keywords":["places","building"]},"love_hotel":{"unicode":"1f3e9","unicode_alternates":"","name":"love hotel","shortname":":love_hotel:","category":"travel","emoji_order":"583","aliases":[],"aliases_ascii":[],"keywords":["places","building","love"]},"wedding":{"unicode":"1f492","unicode_alternates":"","name":"wedding","shortname":":wedding:","category":"travel","emoji_order":"584","aliases":[],"aliases_ascii":[],"keywords":["places","wedding","building","love","parties","parties"]},"classical_building":{"unicode":"1f3db","unicode_alternates":"1f3db-fe0f","name":"classical building","shortname":":classical_building:","category":"travel","emoji_order":"585","aliases":[],"aliases_ascii":[],"keywords":["places","building","travel","vacation"]},"church":{"unicode":"26ea","unicode_alternates":"26ea-fe0f","name":"church","shortname":":church:","category":"travel","emoji_order":"586","aliases":[],"aliases_ascii":[],"keywords":["places","wedding","religion","building","condolence","condolence"]},"mosque":{"unicode":"1f54c","unicode_alternates":"","name":"mosque","shortname":":mosque:","category":"travel","emoji_order":"587","aliases":[],"aliases_ascii":[],"keywords":["places","religion","building","vacation","condolence","condolence"]},"synagogue":{"unicode":"1f54d","unicode_alternates":"","name":"synagogue","shortname":":synagogue:","category":"travel","emoji_order":"588","aliases":[],"aliases_ascii":[],"keywords":["places","religion","building","travel","vacation","condolence","condolence"]},"kaaba":{"unicode":"1f54b","unicode_alternates":"","name":"kaaba","shortname":":kaaba:","category":"travel","emoji_order":"589","aliases":[],"aliases_ascii":[],"keywords":["places","religion","building","condolence","condolence"]},"shinto_shrine":{"unicode":"26e9","unicode_alternates":"26e9-fe0f","name":"shinto shrine","shortname":":shinto_shrine:","category":"travel","emoji_order":"590","aliases":[],"aliases_ascii":[],"keywords":["places","building","travel","vacation"]},"watch":{"unicode":"231a","unicode_alternates":"231a-fe0f","name":"watch","shortname":":watch:","category":"objects","emoji_order":"591","aliases":[],"aliases_ascii":[],"keywords":["electronics","time"]},"iphone":{"unicode":"1f4f1","unicode_alternates":"","name":"mobile phone","shortname":":iphone:","category":"objects","emoji_order":"592","aliases":[],"aliases_ascii":[],"keywords":["electronics","phone","selfie","selfie"]},"calling":{"unicode":"1f4f2","unicode_alternates":"","name":"mobile phone with rightwards arrow at left","shortname":":calling:","category":"objects","emoji_order":"593","aliases":[],"aliases_ascii":[],"keywords":["electronics","phone","selfie","selfie"]},"computer":{"unicode":"1f4bb","unicode_alternates":"","name":"personal computer","shortname":":computer:","category":"objects","emoji_order":"594","aliases":[],"aliases_ascii":[],"keywords":["electronics","work","office"]},"keyboard":{"unicode":"2328","unicode_alternates":"2328-fe0f","name":"keyboard","shortname":":keyboard:","category":"objects","emoji_order":"595","aliases":[],"aliases_ascii":[],"keywords":["electronics","work","office"]},"desktop":{"unicode":"1f5a5","unicode_alternates":"1f5a5-fe0f","name":"desktop computer","shortname":":desktop:","category":"objects","emoji_order":"596","aliases":[":desktop_computer:"],"aliases_ascii":[],"keywords":["electronics","work"]},"printer":{"unicode":"1f5a8","unicode_alternates":"1f5a8-fe0f","name":"printer","shortname":":printer:","category":"objects","emoji_order":"597","aliases":[],"aliases_ascii":[],"keywords":["electronics","work","office"]},"mouse_three_button":{"unicode":"1f5b1","unicode_alternates":"1f5b1-fe0f","name":"three button mouse","shortname":":mouse_three_button:","category":"objects","emoji_order":"598","aliases":[":three_button_mouse:"],"aliases_ascii":[],"keywords":["electronics","work","game","office"]},"trackball":{"unicode":"1f5b2","unicode_alternates":"1f5b2-fe0f","name":"trackball","shortname":":trackball:","category":"objects","emoji_order":"599","aliases":[],"aliases_ascii":[],"keywords":["electronics","work","game","office"]},"joystick":{"unicode":"1f579","unicode_alternates":"1f579-fe0f","name":"joystick","shortname":":joystick:","category":"objects","emoji_order":"600","aliases":[],"aliases_ascii":[],"keywords":["electronics","game","boys night","boys night"]},"compression":{"unicode":"1f5dc","unicode_alternates":"1f5dc-fe0f","name":"compression","shortname":":compression:","category":"objects","emoji_order":"601","aliases":[],"aliases_ascii":[],"keywords":[]},"minidisc":{"unicode":"1f4bd","unicode_alternates":"","name":"minidisc","shortname":":minidisc:","category":"objects","emoji_order":"602","aliases":[],"aliases_ascii":[],"keywords":["electronics"]},"floppy_disk":{"unicode":"1f4be","unicode_alternates":"","name":"floppy disk","shortname":":floppy_disk:","category":"objects","emoji_order":"603","aliases":[],"aliases_ascii":[],"keywords":["electronics","office"]},"cd":{"unicode":"1f4bf","unicode_alternates":"","name":"optical disc","shortname":":cd:","category":"objects","emoji_order":"604","aliases":[],"aliases_ascii":[],"keywords":["electronics"]},"dvd":{"unicode":"1f4c0","unicode_alternates":"","name":"dvd","shortname":":dvd:","category":"objects","emoji_order":"605","aliases":[],"aliases_ascii":[],"keywords":["electronics"]},"vhs":{"unicode":"1f4fc","unicode_alternates":"","name":"videocassette","shortname":":vhs:","category":"objects","emoji_order":"606","aliases":[],"aliases_ascii":[],"keywords":["electronics"]},"camera":{"unicode":"1f4f7","unicode_alternates":"","name":"camera","shortname":":camera:","category":"objects","emoji_order":"607","aliases":[],"aliases_ascii":[],"keywords":["electronics","camera","selfie","selfie"]},"camera_with_flash":{"unicode":"1f4f8","unicode_alternates":"","name":"camera with flash","shortname":":camera_with_flash:","category":"objects","emoji_order":"608","aliases":[],"aliases_ascii":[],"keywords":["electronics","camera"]},"video_camera":{"unicode":"1f4f9","unicode_alternates":"","name":"video camera","shortname":":video_camera:","category":"objects","emoji_order":"609","aliases":[],"aliases_ascii":[],"keywords":["electronics","camera","movie"]},"movie_camera":{"unicode":"1f3a5","unicode_alternates":"","name":"movie camera","shortname":":movie_camera:","category":"objects","emoji_order":"610","aliases":[],"aliases_ascii":[],"keywords":["object","camera","movie"]},"projector":{"unicode":"1f4fd","unicode_alternates":"1f4fd-fe0f","name":"film projector","shortname":":projector:","category":"objects","emoji_order":"611","aliases":[":film_projector:"],"aliases_ascii":[],"keywords":["object","camera","movie"]},"film_frames":{"unicode":"1f39e","unicode_alternates":"1f39e-fe0f","name":"film frames","shortname":":film_frames:","category":"objects","emoji_order":"612","aliases":[],"aliases_ascii":[],"keywords":["object","camera","movie"]},"telephone_receiver":{"unicode":"1f4de","unicode_alternates":"","name":"telephone receiver","shortname":":telephone_receiver:","category":"objects","emoji_order":"613","aliases":[],"aliases_ascii":[],"keywords":["electronics","phone"]},"telephone":{"unicode":"260e","unicode_alternates":"260e-fe0f","name":"black telephone","shortname":":telephone:","category":"objects","emoji_order":"614","aliases":[],"aliases_ascii":[],"keywords":["electronics","phone"]},"pager":{"unicode":"1f4df","unicode_alternates":"","name":"pager","shortname":":pager:","category":"objects","emoji_order":"615","aliases":[],"aliases_ascii":[],"keywords":["electronics","work"]},"fax":{"unicode":"1f4e0","unicode_alternates":"","name":"fax machine","shortname":":fax:","category":"objects","emoji_order":"616","aliases":[],"aliases_ascii":[],"keywords":["electronics","work","office"]},"tv":{"unicode":"1f4fa","unicode_alternates":"","name":"television","shortname":":tv:","category":"objects","emoji_order":"617","aliases":[],"aliases_ascii":[],"keywords":["electronics"]},"radio":{"unicode":"1f4fb","unicode_alternates":"","name":"radio","shortname":":radio:","category":"objects","emoji_order":"618","aliases":[],"aliases_ascii":[],"keywords":["electronics"]},"microphone2":{"unicode":"1f399","unicode_alternates":"1f399-fe0f","name":"studio microphone","shortname":":microphone2:","category":"objects","emoji_order":"619","aliases":[":studio_microphone:"],"aliases_ascii":[],"keywords":["electronics","object"]},"level_slider":{"unicode":"1f39a","unicode_alternates":"1f39a-fe0f","name":"level slider","shortname":":level_slider:","category":"objects","emoji_order":"620","aliases":[],"aliases_ascii":[],"keywords":[]},"control_knobs":{"unicode":"1f39b","unicode_alternates":"1f39b-fe0f","name":"control knobs","shortname":":control_knobs:","category":"objects","emoji_order":"621","aliases":[],"aliases_ascii":[],"keywords":["time"]},"stopwatch":{"unicode":"23f1","unicode_alternates":"23f1-fe0f","name":"stopwatch","shortname":":stopwatch:","category":"objects","emoji_order":"622","aliases":[],"aliases_ascii":[],"keywords":["electronics","time"]},"timer":{"unicode":"23f2","unicode_alternates":"23f2-fe0f","name":"timer clock","shortname":":timer:","category":"objects","emoji_order":"623","aliases":[":timer_clock:"],"aliases_ascii":[],"keywords":["object","time"]},"alarm_clock":{"unicode":"23f0","unicode_alternates":"","name":"alarm clock","shortname":":alarm_clock:","category":"objects","emoji_order":"624","aliases":[],"aliases_ascii":[],"keywords":["object","time"]},"clock":{"unicode":"1f570","unicode_alternates":"1f570-fe0f","name":"mantlepiece clock","shortname":":clock:","category":"objects","emoji_order":"625","aliases":[":mantlepiece_clock:"],"aliases_ascii":[],"keywords":["object","time"]},"hourglass_flowing_sand":{"unicode":"23f3","unicode_alternates":"","name":"hourglass with flowing sand","shortname":":hourglass_flowing_sand:","category":"objects","emoji_order":"626","aliases":[],"aliases_ascii":[],"keywords":["object","time"]},"hourglass":{"unicode":"231b","unicode_alternates":"231b-fe0f","name":"hourglass","shortname":":hourglass:","category":"objects","emoji_order":"627","aliases":[],"aliases_ascii":[],"keywords":["object","time"]},"satellite":{"unicode":"1f4e1","unicode_alternates":"","name":"satellite antenna","shortname":":satellite:","category":"objects","emoji_order":"628","aliases":[],"aliases_ascii":[],"keywords":["object"]},"battery":{"unicode":"1f50b","unicode_alternates":"","name":"battery","shortname":":battery:","category":"objects","emoji_order":"629","aliases":[],"aliases_ascii":[],"keywords":["object"]},"electric_plug":{"unicode":"1f50c","unicode_alternates":"","name":"electric plug","shortname":":electric_plug:","category":"objects","emoji_order":"630","aliases":[],"aliases_ascii":[],"keywords":["electronics"]},"bulb":{"unicode":"1f4a1","unicode_alternates":"","name":"electric light bulb","shortname":":bulb:","category":"objects","emoji_order":"631","aliases":[],"aliases_ascii":[],"keywords":["object","science"]},"flashlight":{"unicode":"1f526","unicode_alternates":"","name":"electric torch","shortname":":flashlight:","category":"objects","emoji_order":"632","aliases":[],"aliases_ascii":[],"keywords":["electronics","object"]},"candle":{"unicode":"1f56f","unicode_alternates":"1f56f-fe0f","name":"candle","shortname":":candle:","category":"objects","emoji_order":"633","aliases":[],"aliases_ascii":[],"keywords":["object"]},"wastebasket":{"unicode":"1f5d1","unicode_alternates":"1f5d1-fe0f","name":"wastebasket","shortname":":wastebasket:","category":"objects","emoji_order":"634","aliases":[],"aliases_ascii":[],"keywords":["object","work"]},"oil":{"unicode":"1f6e2","unicode_alternates":"1f6e2-fe0f","name":"oil drum","shortname":":oil:","category":"objects","emoji_order":"635","aliases":[":oil_drum:"],"aliases_ascii":[],"keywords":["object"]},"money_with_wings":{"unicode":"1f4b8","unicode_alternates":"","name":"money with wings","shortname":":money_with_wings:","category":"objects","emoji_order":"636","aliases":[],"aliases_ascii":[],"keywords":["money","money","boys night","boys night"]},"dollar":{"unicode":"1f4b5","unicode_alternates":"","name":"banknote with dollar sign","shortname":":dollar:","category":"objects","emoji_order":"637","aliases":[],"aliases_ascii":[],"keywords":["money","money"]},"yen":{"unicode":"1f4b4","unicode_alternates":"","name":"banknote with yen sign","shortname":":yen:","category":"objects","emoji_order":"638","aliases":[],"aliases_ascii":[],"keywords":["money","money"]},"euro":{"unicode":"1f4b6","unicode_alternates":"","name":"banknote with euro sign","shortname":":euro:","category":"objects","emoji_order":"639","aliases":[],"aliases_ascii":[],"keywords":["money","money"]},"pound":{"unicode":"1f4b7","unicode_alternates":"","name":"banknote with pound sign","shortname":":pound:","category":"objects","emoji_order":"640","aliases":[],"aliases_ascii":[],"keywords":["money","money"]},"moneybag":{"unicode":"1f4b0","unicode_alternates":"","name":"money bag","shortname":":moneybag:","category":"objects","emoji_order":"641","aliases":[],"aliases_ascii":[],"keywords":["bag","award","money","money"]},"credit_card":{"unicode":"1f4b3","unicode_alternates":"","name":"credit card","shortname":":credit_card:","category":"objects","emoji_order":"642","aliases":[],"aliases_ascii":[],"keywords":["object","money","money","boys night","boys night"]},"gem":{"unicode":"1f48e","unicode_alternates":"","name":"gem stone","shortname":":gem:","category":"objects","emoji_order":"643","aliases":[],"aliases_ascii":[],"keywords":["object","gem"]},"scales":{"unicode":"2696","unicode_alternates":"2696-fe0f","name":"scales","shortname":":scales:","category":"objects","emoji_order":"644","aliases":[],"aliases_ascii":[],"keywords":["object"]},"wrench":{"unicode":"1f527","unicode_alternates":"","name":"wrench","shortname":":wrench:","category":"objects","emoji_order":"645","aliases":[],"aliases_ascii":[],"keywords":["object","tool"]},"hammer":{"unicode":"1f528","unicode_alternates":"","name":"hammer","shortname":":hammer:","category":"objects","emoji_order":"646","aliases":[],"aliases_ascii":[],"keywords":["object","tool","weapon"]},"hammer_pick":{"unicode":"2692","unicode_alternates":"2692-fe0f","name":"hammer and pick","shortname":":hammer_pick:","category":"objects","emoji_order":"647","aliases":[":hammer_and_pick:"],"aliases_ascii":[],"keywords":["object","tool","weapon"]},"tools":{"unicode":"1f6e0","unicode_alternates":"1f6e0-fe0f","name":"hammer and wrench","shortname":":tools:","category":"objects","emoji_order":"648","aliases":[":hammer_and_wrench:"],"aliases_ascii":[],"keywords":["object","tool"]},"pick":{"unicode":"26cf","unicode_alternates":"26cf-fe0f","name":"pick","shortname":":pick:","category":"objects","emoji_order":"649","aliases":[],"aliases_ascii":[],"keywords":["object","tool","weapon"]},"nut_and_bolt":{"unicode":"1f529","unicode_alternates":"","name":"nut and bolt","shortname":":nut_and_bolt:","category":"objects","emoji_order":"650","aliases":[],"aliases_ascii":[],"keywords":["object","tool","nutcase","nutcase"]},"gear":{"unicode":"2699","unicode_alternates":"2699-fe0f","name":"gear","shortname":":gear:","category":"objects","emoji_order":"651","aliases":[],"aliases_ascii":[],"keywords":["object","tool"]},"chains":{"unicode":"26d3","unicode_alternates":"26d3-fe0f","name":"chains","shortname":":chains:","category":"objects","emoji_order":"652","aliases":[],"aliases_ascii":[],"keywords":["object","tool"]},"gun":{"unicode":"1f52b","unicode_alternates":"","name":"pistol","shortname":":gun:","category":"objects","emoji_order":"653","aliases":[],"aliases_ascii":[],"keywords":["object","weapon","dead","gun","sarcastic","sarcastic"]},"bomb":{"unicode":"1f4a3","unicode_alternates":"","name":"bomb","shortname":":bomb:","category":"objects","emoji_order":"654","aliases":[],"aliases_ascii":[],"keywords":["object","weapon","dead","blast","blast"]},"knife":{"unicode":"1f52a","unicode_alternates":"","name":"hocho","shortname":":knife:","category":"objects","emoji_order":"655","aliases":[],"aliases_ascii":[],"keywords":["object","weapon"]},"dagger":{"unicode":"1f5e1","unicode_alternates":"1f5e1-fe0f","name":"dagger knife","shortname":":dagger:","category":"objects","emoji_order":"656","aliases":[":dagger_knife:"],"aliases_ascii":[],"keywords":["object","weapon"]},"crossed_swords":{"unicode":"2694","unicode_alternates":"2694-fe0f","name":"crossed swords","shortname":":crossed_swords:","category":"objects","emoji_order":"657","aliases":[],"aliases_ascii":[],"keywords":["object","weapon"]},"shield":{"unicode":"1f6e1","unicode_alternates":"1f6e1-fe0f","name":"shield","shortname":":shield:","category":"objects","emoji_order":"658","aliases":[],"aliases_ascii":[],"keywords":["object"]},"smoking":{"unicode":"1f6ac","unicode_alternates":"","name":"smoking symbol","shortname":":smoking:","category":"objects","emoji_order":"659","aliases":[],"aliases_ascii":[],"keywords":["symbol","drugs","drugs","smoking","smoking"]},"skull_crossbones":{"unicode":"2620","unicode_alternates":"2620-fe0f","name":"skull and crossbones","shortname":":skull_crossbones:","category":"objects","emoji_order":"660","aliases":[":skull_and_crossbones:"],"aliases_ascii":[],"keywords":["symbol","dead","skull"]},"coffin":{"unicode":"26b0","unicode_alternates":"26b0-fe0f","name":"coffin","shortname":":coffin:","category":"objects","emoji_order":"661","aliases":[],"aliases_ascii":[],"keywords":["object","dead","rip","rip"]},"urn":{"unicode":"26b1","unicode_alternates":"26b1-fe0f","name":"funeral urn","shortname":":urn:","category":"objects","emoji_order":"662","aliases":[":funeral_urn:"],"aliases_ascii":[],"keywords":["object","dead","rip","rip"]},"amphora":{"unicode":"1f3fa","unicode_alternates":"","name":"amphora","shortname":":amphora:","category":"objects","emoji_order":"663","aliases":[],"aliases_ascii":[],"keywords":["object"]},"crystal_ball":{"unicode":"1f52e","unicode_alternates":"","name":"crystal ball","shortname":":crystal_ball:","category":"objects","emoji_order":"664","aliases":[],"aliases_ascii":[],"keywords":["object","ball"]},"prayer_beads":{"unicode":"1f4ff","unicode_alternates":"","name":"prayer beads","shortname":":prayer_beads:","category":"objects","emoji_order":"665","aliases":[],"aliases_ascii":[],"keywords":["object","rosary"]},"barber":{"unicode":"1f488","unicode_alternates":"","name":"barber pole","shortname":":barber:","category":"objects","emoji_order":"666","aliases":[],"aliases_ascii":[],"keywords":["object"]},"alembic":{"unicode":"2697","unicode_alternates":"2697-fe0f","name":"alembic","shortname":":alembic:","category":"objects","emoji_order":"667","aliases":[],"aliases_ascii":[],"keywords":["object","science"]},"telescope":{"unicode":"1f52d","unicode_alternates":"","name":"telescope","shortname":":telescope:","category":"objects","emoji_order":"668","aliases":[],"aliases_ascii":[],"keywords":["object","space","science"]},"microscope":{"unicode":"1f52c","unicode_alternates":"","name":"microscope","shortname":":microscope:","category":"objects","emoji_order":"669","aliases":[],"aliases_ascii":[],"keywords":["object","science"]},"hole":{"unicode":"1f573","unicode_alternates":"1f573-fe0f","name":"hole","shortname":":hole:","category":"objects","emoji_order":"670","aliases":[],"aliases_ascii":[],"keywords":["object"]},"pill":{"unicode":"1f48a","unicode_alternates":"","name":"pill","shortname":":pill:","category":"objects","emoji_order":"671","aliases":[],"aliases_ascii":[],"keywords":["object","health","drugs","drugs"]},"syringe":{"unicode":"1f489","unicode_alternates":"","name":"syringe","shortname":":syringe:","category":"objects","emoji_order":"672","aliases":[],"aliases_ascii":[],"keywords":["object","weapon","health","drugs","drugs"]},"thermometer":{"unicode":"1f321","unicode_alternates":"1f321-fe0f","name":"thermometer","shortname":":thermometer:","category":"objects","emoji_order":"673","aliases":[],"aliases_ascii":[],"keywords":["object","science","health","hot","hot"]},"label":{"unicode":"1f3f7","unicode_alternates":"1f3f7-fe0f","name":"label","shortname":":label:","category":"objects","emoji_order":"674","aliases":[],"aliases_ascii":[],"keywords":["object"]},"bookmark":{"unicode":"1f516","unicode_alternates":"","name":"bookmark","shortname":":bookmark:","category":"objects","emoji_order":"675","aliases":[],"aliases_ascii":[],"keywords":["object","book"]},"toilet":{"unicode":"1f6bd","unicode_alternates":"","name":"toilet","shortname":":toilet:","category":"objects","emoji_order":"676","aliases":[],"aliases_ascii":[],"keywords":["object","bathroom"]},"shower":{"unicode":"1f6bf","unicode_alternates":"","name":"shower","shortname":":shower:","category":"objects","emoji_order":"677","aliases":[],"aliases_ascii":[],"keywords":["object","bathroom"]},"bathtub":{"unicode":"1f6c1","unicode_alternates":"","name":"bathtub","shortname":":bathtub:","category":"objects","emoji_order":"678","aliases":[],"aliases_ascii":[],"keywords":["object","bathroom","tired","steam","steam"]},"key":{"unicode":"1f511","unicode_alternates":"","name":"key","shortname":":key:","category":"objects","emoji_order":"679","aliases":[],"aliases_ascii":[],"keywords":["object","lock"]},"key2":{"unicode":"1f5dd","unicode_alternates":"1f5dd-fe0f","name":"old key","shortname":":key2:","category":"objects","emoji_order":"680","aliases":[":old_key:"],"aliases_ascii":[],"keywords":["object","lock"]},"couch":{"unicode":"1f6cb","unicode_alternates":"1f6cb-fe0f","name":"couch and lamp","shortname":":couch:","category":"objects","emoji_order":"681","aliases":[":couch_and_lamp:"],"aliases_ascii":[],"keywords":["object"]},"sleeping_accommodation":{"unicode":"1f6cc","unicode_alternates":"","name":"sleeping accommodation","shortname":":sleeping_accommodation:","category":"objects","emoji_order":"682","aliases":[],"aliases_ascii":[],"keywords":["tired"]},"bed":{"unicode":"1f6cf","unicode_alternates":"1f6cf-fe0f","name":"bed","shortname":":bed:","category":"objects","emoji_order":"683","aliases":[],"aliases_ascii":[],"keywords":["object","tired"]},"door":{"unicode":"1f6aa","unicode_alternates":"","name":"door","shortname":":door:","category":"objects","emoji_order":"684","aliases":[],"aliases_ascii":[],"keywords":["object"]},"bellhop":{"unicode":"1f6ce","unicode_alternates":"1f6ce-fe0f","name":"bellhop bell","shortname":":bellhop:","category":"objects","emoji_order":"685","aliases":[":bellhop_bell:"],"aliases_ascii":[],"keywords":["object"]},"frame_photo":{"unicode":"1f5bc","unicode_alternates":"1f5bc-fe0f","name":"frame with picture","shortname":":frame_photo:","category":"objects","emoji_order":"686","aliases":[":frame_with_picture:"],"aliases_ascii":[],"keywords":["travel","vacation"]},"map":{"unicode":"1f5fa","unicode_alternates":"1f5fa-fe0f","name":"world map","shortname":":map:","category":"objects","emoji_order":"687","aliases":[":world_map:"],"aliases_ascii":[],"keywords":["travel","map","vacation"]},"beach_umbrella":{"unicode":"26f1","unicode_alternates":"26f1-fe0f","name":"umbrella on ground","shortname":":beach_umbrella:","category":"objects","emoji_order":"688","aliases":[":umbrella_on_ground:"],"aliases_ascii":[],"keywords":["travel","vacation","tropical"]},"moyai":{"unicode":"1f5ff","unicode_alternates":"","name":"moyai","shortname":":moyai:","category":"objects","emoji_order":"689","aliases":[],"aliases_ascii":[],"keywords":["travel","vacation"]},"shopping_bags":{"unicode":"1f6cd","unicode_alternates":"1f6cd-fe0f","name":"shopping bags","shortname":":shopping_bags:","category":"objects","emoji_order":"690","aliases":[],"aliases_ascii":[],"keywords":["object","birthday","parties","parties"]},"balloon":{"unicode":"1f388","unicode_alternates":"","name":"balloon","shortname":":balloon:","category":"objects","emoji_order":"691","aliases":[],"aliases_ascii":[],"keywords":["object","birthday","good","good","parties","parties"]},"flags":{"unicode":"1f38f","unicode_alternates":"","name":"carp streamer","shortname":":flags:","category":"objects","emoji_order":"692","aliases":[],"aliases_ascii":[],"keywords":["object","japan"]},"ribbon":{"unicode":"1f380","unicode_alternates":"","name":"ribbon","shortname":":ribbon:","category":"objects","emoji_order":"693","aliases":[],"aliases_ascii":[],"keywords":["object","gift","birthday"]},"gift":{"unicode":"1f381","unicode_alternates":"","name":"wrapped present","shortname":":gift:","category":"objects","emoji_order":"694","aliases":[],"aliases_ascii":[],"keywords":["object","gift","birthday","holidays","christmas","parties","parties"]},"confetti_ball":{"unicode":"1f38a","unicode_alternates":"","name":"confetti ball","shortname":":confetti_ball:","category":"objects","emoji_order":"695","aliases":[],"aliases_ascii":[],"keywords":["object","birthday","holidays","cheers","girls night","girls night","boys night","boys night","parties","parties"]},"tada":{"unicode":"1f389","unicode_alternates":"","name":"party popper","shortname":":tada:","category":"objects","emoji_order":"696","aliases":[],"aliases_ascii":[],"keywords":["object","birthday","holidays","cheers","good","good","girls night","girls night","boys night","boys night","parties","parties"]},"dolls":{"unicode":"1f38e","unicode_alternates":"","name":"japanese dolls","shortname":":dolls:","category":"objects","emoji_order":"697","aliases":[],"aliases_ascii":[],"keywords":["people","japan"]},"wind_chime":{"unicode":"1f390","unicode_alternates":"","name":"wind chime","shortname":":wind_chime:","category":"objects","emoji_order":"698","aliases":[],"aliases_ascii":[],"keywords":["object","japan"]},"crossed_flags":{"unicode":"1f38c","unicode_alternates":"","name":"crossed flags","shortname":":crossed_flags:","category":"objects","emoji_order":"699","aliases":[],"aliases_ascii":[],"keywords":["object","japan"]},"izakaya_lantern":{"unicode":"1f3ee","unicode_alternates":"","name":"izakaya lantern","shortname":":izakaya_lantern:","category":"objects","emoji_order":"700","aliases":[],"aliases_ascii":[],"keywords":["object","japan"]},"envelope":{"unicode":"2709","unicode_alternates":"2709-fe0f","name":"envelope","shortname":":envelope:","category":"objects","emoji_order":"701","aliases":[],"aliases_ascii":[],"keywords":["object","office","write"]},"envelope_with_arrow":{"unicode":"1f4e9","unicode_alternates":"","name":"envelope with downwards arrow above","shortname":":envelope_with_arrow:","category":"objects","emoji_order":"702","aliases":[],"aliases_ascii":[],"keywords":["object","office"]},"incoming_envelope":{"unicode":"1f4e8","unicode_alternates":"","name":"incoming envelope","shortname":":incoming_envelope:","category":"objects","emoji_order":"703","aliases":[],"aliases_ascii":[],"keywords":["object"]},"e-mail":{"unicode":"1f4e7","unicode_alternates":"","name":"e-mail symbol","shortname":":e-mail:","category":"objects","emoji_order":"704","aliases":[":email:"],"aliases_ascii":[],"keywords":["office"]},"love_letter":{"unicode":"1f48c","unicode_alternates":"","name":"love letter","shortname":":love_letter:","category":"objects","emoji_order":"705","aliases":[],"aliases_ascii":[],"keywords":["object"]},"postbox":{"unicode":"1f4ee","unicode_alternates":"","name":"postbox","shortname":":postbox:","category":"objects","emoji_order":"706","aliases":[],"aliases_ascii":[],"keywords":["object"]},"mailbox_closed":{"unicode":"1f4ea","unicode_alternates":"","name":"closed mailbox with lowered flag","shortname":":mailbox_closed:","category":"objects","emoji_order":"707","aliases":[],"aliases_ascii":[],"keywords":["object","office"]},"mailbox":{"unicode":"1f4eb","unicode_alternates":"","name":"closed mailbox with raised flag","shortname":":mailbox:","category":"objects","emoji_order":"708","aliases":[],"aliases_ascii":[],"keywords":["object"]},"mailbox_with_mail":{"unicode":"1f4ec","unicode_alternates":"","name":"open mailbox with raised flag","shortname":":mailbox_with_mail:","category":"objects","emoji_order":"709","aliases":[],"aliases_ascii":[],"keywords":["object"]},"mailbox_with_no_mail":{"unicode":"1f4ed","unicode_alternates":"","name":"open mailbox with lowered flag","shortname":":mailbox_with_no_mail:","category":"objects","emoji_order":"710","aliases":[],"aliases_ascii":[],"keywords":["object"]},"package":{"unicode":"1f4e6","unicode_alternates":"","name":"package","shortname":":package:","category":"objects","emoji_order":"711","aliases":[],"aliases_ascii":[],"keywords":["object","gift","office"]},"postal_horn":{"unicode":"1f4ef","unicode_alternates":"","name":"postal horn","shortname":":postal_horn:","category":"objects","emoji_order":"712","aliases":[],"aliases_ascii":[],"keywords":["object"]},"inbox_tray":{"unicode":"1f4e5","unicode_alternates":"","name":"inbox tray","shortname":":inbox_tray:","category":"objects","emoji_order":"713","aliases":[],"aliases_ascii":[],"keywords":["work","office"]},"outbox_tray":{"unicode":"1f4e4","unicode_alternates":"","name":"outbox tray","shortname":":outbox_tray:","category":"objects","emoji_order":"714","aliases":[],"aliases_ascii":[],"keywords":["work","office"]},"scroll":{"unicode":"1f4dc","unicode_alternates":"","name":"scroll","shortname":":scroll:","category":"objects","emoji_order":"715","aliases":[],"aliases_ascii":[],"keywords":["object","office"]},"page_with_curl":{"unicode":"1f4c3","unicode_alternates":"","name":"page with curl","shortname":":page_with_curl:","category":"objects","emoji_order":"716","aliases":[],"aliases_ascii":[],"keywords":["office","write"]},"bookmark_tabs":{"unicode":"1f4d1","unicode_alternates":"","name":"bookmark tabs","shortname":":bookmark_tabs:","category":"objects","emoji_order":"717","aliases":[],"aliases_ascii":[],"keywords":["office","write"]},"bar_chart":{"unicode":"1f4ca","unicode_alternates":"","name":"bar chart","shortname":":bar_chart:","category":"objects","emoji_order":"718","aliases":[],"aliases_ascii":[],"keywords":["work","office"]},"chart_with_upwards_trend":{"unicode":"1f4c8","unicode_alternates":"","name":"chart with upwards trend","shortname":":chart_with_upwards_trend:","category":"objects","emoji_order":"719","aliases":[],"aliases_ascii":[],"keywords":["work","office"]},"chart_with_downwards_trend":{"unicode":"1f4c9","unicode_alternates":"","name":"chart with downwards trend","shortname":":chart_with_downwards_trend:","category":"objects","emoji_order":"720","aliases":[],"aliases_ascii":[],"keywords":["work","office"]},"page_facing_up":{"unicode":"1f4c4","unicode_alternates":"","name":"page facing up","shortname":":page_facing_up:","category":"objects","emoji_order":"721","aliases":[],"aliases_ascii":[],"keywords":["work","office","write"]},"date":{"unicode":"1f4c5","unicode_alternates":"","name":"calendar","shortname":":date:","category":"objects","emoji_order":"722","aliases":[],"aliases_ascii":[],"keywords":["object","office"]},"calendar":{"unicode":"1f4c6","unicode_alternates":"","name":"tear-off calendar","shortname":":calendar:","category":"objects","emoji_order":"723","aliases":[],"aliases_ascii":[],"keywords":["object","office"]},"calendar_spiral":{"unicode":"1f5d3","unicode_alternates":"1f5d3-fe0f","name":"spiral calendar pad","shortname":":calendar_spiral:","category":"objects","emoji_order":"724","aliases":[":spiral_calendar_pad:"],"aliases_ascii":[],"keywords":["object","office"]},"card_index":{"unicode":"1f4c7","unicode_alternates":"","name":"card index","shortname":":card_index:","category":"objects","emoji_order":"725","aliases":[],"aliases_ascii":[],"keywords":["object","work","office"]},"card_box":{"unicode":"1f5c3","unicode_alternates":"1f5c3-fe0f","name":"card file box","shortname":":card_box:","category":"objects","emoji_order":"726","aliases":[":card_file_box:"],"aliases_ascii":[],"keywords":["object","work","office"]},"ballot_box":{"unicode":"1f5f3","unicode_alternates":"1f5f3-fe0f","name":"ballot box with ballot","shortname":":ballot_box:","category":"objects","emoji_order":"727","aliases":[":ballot_box_with_ballot:"],"aliases_ascii":[],"keywords":["object","office"]},"file_cabinet":{"unicode":"1f5c4","unicode_alternates":"1f5c4-fe0f","name":"file cabinet","shortname":":file_cabinet:","category":"objects","emoji_order":"728","aliases":[],"aliases_ascii":[],"keywords":["object","work","office"]},"clipboard":{"unicode":"1f4cb","unicode_alternates":"","name":"clipboard","shortname":":clipboard:","category":"objects","emoji_order":"729","aliases":[],"aliases_ascii":[],"keywords":["object","work","office","write"]},"notepad_spiral":{"unicode":"1f5d2","unicode_alternates":"1f5d2-fe0f","name":"spiral note pad","shortname":":notepad_spiral:","category":"objects","emoji_order":"730","aliases":[":spiral_note_pad:"],"aliases_ascii":[],"keywords":["work","office","write"]},"file_folder":{"unicode":"1f4c1","unicode_alternates":"","name":"file folder","shortname":":file_folder:","category":"objects","emoji_order":"731","aliases":[],"aliases_ascii":[],"keywords":["work","office"]},"open_file_folder":{"unicode":"1f4c2","unicode_alternates":"","name":"open file folder","shortname":":open_file_folder:","category":"objects","emoji_order":"732","aliases":[],"aliases_ascii":[],"keywords":["work","office"]},"dividers":{"unicode":"1f5c2","unicode_alternates":"1f5c2-fe0f","name":"card index dividers","shortname":":dividers:","category":"objects","emoji_order":"733","aliases":[":card_index_dividers:"],"aliases_ascii":[],"keywords":["work","office"]},"newspaper2":{"unicode":"1f5de","unicode_alternates":"1f5de-fe0f","name":"rolled-up newspaper","shortname":":newspaper2:","category":"objects","emoji_order":"734","aliases":[":rolled_up_newspaper:"],"aliases_ascii":[],"keywords":["office","write"]},"newspaper":{"unicode":"1f4f0","unicode_alternates":"","name":"newspaper","shortname":":newspaper:","category":"objects","emoji_order":"735","aliases":[],"aliases_ascii":[],"keywords":["office","write"]},"notebook":{"unicode":"1f4d3","unicode_alternates":"","name":"notebook","shortname":":notebook:","category":"objects","emoji_order":"736","aliases":[],"aliases_ascii":[],"keywords":["object","office","write"]},"closed_book":{"unicode":"1f4d5","unicode_alternates":"","name":"closed book","shortname":":closed_book:","category":"objects","emoji_order":"737","aliases":[],"aliases_ascii":[],"keywords":["object","office","write","book"]},"green_book":{"unicode":"1f4d7","unicode_alternates":"","name":"green book","shortname":":green_book:","category":"objects","emoji_order":"738","aliases":[],"aliases_ascii":[],"keywords":["object","office","book"]},"blue_book":{"unicode":"1f4d8","unicode_alternates":"","name":"blue book","shortname":":blue_book:","category":"objects","emoji_order":"739","aliases":[],"aliases_ascii":[],"keywords":["object","office","write","book"]},"orange_book":{"unicode":"1f4d9","unicode_alternates":"","name":"orange book","shortname":":orange_book:","category":"objects","emoji_order":"740","aliases":[],"aliases_ascii":[],"keywords":["object","office","write","book"]},"notebook_with_decorative_cover":{"unicode":"1f4d4","unicode_alternates":"","name":"notebook with decorative cover","shortname":":notebook_with_decorative_cover:","category":"objects","emoji_order":"741","aliases":[],"aliases_ascii":[],"keywords":["object","office","write"]},"ledger":{"unicode":"1f4d2","unicode_alternates":"","name":"ledger","shortname":":ledger:","category":"objects","emoji_order":"742","aliases":[],"aliases_ascii":[],"keywords":["object","office","write"]},"books":{"unicode":"1f4da","unicode_alternates":"","name":"books","shortname":":books:","category":"objects","emoji_order":"743","aliases":[],"aliases_ascii":[],"keywords":["object","office","write","book"]},"book":{"unicode":"1f4d6","unicode_alternates":"","name":"open book","shortname":":book:","category":"objects","emoji_order":"744","aliases":[],"aliases_ascii":[],"keywords":["object","office","write","book"]},"link":{"unicode":"1f517","unicode_alternates":"","name":"link symbol","shortname":":link:","category":"objects","emoji_order":"745","aliases":[],"aliases_ascii":[],"keywords":["symbol","office"]},"paperclip":{"unicode":"1f4ce","unicode_alternates":"","name":"paperclip","shortname":":paperclip:","category":"objects","emoji_order":"746","aliases":[],"aliases_ascii":[],"keywords":["object","work","office"]},"paperclips":{"unicode":"1f587","unicode_alternates":"1f587-fe0f","name":"linked paperclips","shortname":":paperclips:","category":"objects","emoji_order":"747","aliases":[":linked_paperclips:"],"aliases_ascii":[],"keywords":["object","work","office"]},"scissors":{"unicode":"2702","unicode_alternates":"2702-fe0f","name":"black scissors","shortname":":scissors:","category":"objects","emoji_order":"748","aliases":[],"aliases_ascii":[],"keywords":["object","tool","weapon","office"]},"triangular_ruler":{"unicode":"1f4d0","unicode_alternates":"","name":"triangular ruler","shortname":":triangular_ruler:","category":"objects","emoji_order":"749","aliases":[],"aliases_ascii":[],"keywords":["object","tool","office"]},"straight_ruler":{"unicode":"1f4cf","unicode_alternates":"","name":"straight ruler","shortname":":straight_ruler:","category":"objects","emoji_order":"750","aliases":[],"aliases_ascii":[],"keywords":["object","tool","office"]},"pushpin":{"unicode":"1f4cc","unicode_alternates":"","name":"pushpin","shortname":":pushpin:","category":"objects","emoji_order":"751","aliases":[],"aliases_ascii":[],"keywords":["object","office"]},"round_pushpin":{"unicode":"1f4cd","unicode_alternates":"","name":"round pushpin","shortname":":round_pushpin:","category":"objects","emoji_order":"752","aliases":[],"aliases_ascii":[],"keywords":["object","office"]},"triangular_flag_on_post":{"unicode":"1f6a9","unicode_alternates":"","name":"triangular flag on post","shortname":":triangular_flag_on_post:","category":"objects","emoji_order":"753","aliases":[],"aliases_ascii":[],"keywords":["object"]},"flag_white":{"unicode":"1f3f3","unicode_alternates":"1f3f3-fe0f","name":"waving white flag","shortname":":flag_white:","category":"objects","emoji_order":"754","aliases":[":waving_white_flag:"],"aliases_ascii":[],"keywords":["object"]},"flag_black":{"unicode":"1f3f4","unicode_alternates":"","name":"waving black flag","shortname":":flag_black:","category":"objects","emoji_order":"755","aliases":[":waving_black_flag:"],"aliases_ascii":[],"keywords":["object"]},"closed_lock_with_key":{"unicode":"1f510","unicode_alternates":"","name":"closed lock with key","shortname":":closed_lock_with_key:","category":"objects","emoji_order":"756","aliases":[],"aliases_ascii":[],"keywords":["object","lock"]},"lock":{"unicode":"1f512","unicode_alternates":"","name":"lock","shortname":":lock:","category":"objects","emoji_order":"757","aliases":[],"aliases_ascii":[],"keywords":["object","lock"]},"unlock":{"unicode":"1f513","unicode_alternates":"","name":"open lock","shortname":":unlock:","category":"objects","emoji_order":"758","aliases":[],"aliases_ascii":[],"keywords":["object","lock"]},"lock_with_ink_pen":{"unicode":"1f50f","unicode_alternates":"","name":"lock with ink pen","shortname":":lock_with_ink_pen:","category":"objects","emoji_order":"759","aliases":[],"aliases_ascii":[],"keywords":["object","lock"]},"pen_ballpoint":{"unicode":"1f58a","unicode_alternates":"1f58a-fe0f","name":"lower left ballpoint pen","shortname":":pen_ballpoint:","category":"objects","emoji_order":"760","aliases":[":lower_left_ballpoint_pen:"],"aliases_ascii":[],"keywords":["object","office","write"]},"pen_fountain":{"unicode":"1f58b","unicode_alternates":"1f58b-fe0f","name":"lower left fountain pen","shortname":":pen_fountain:","category":"objects","emoji_order":"761","aliases":[":lower_left_fountain_pen:"],"aliases_ascii":[],"keywords":["object","office","write"]},"black_nib":{"unicode":"2712","unicode_alternates":"2712-fe0f","name":"black nib","shortname":":black_nib:","category":"objects","emoji_order":"762","aliases":[],"aliases_ascii":[],"keywords":["object","office","write"]},"pencil":{"unicode":"1f4dd","unicode_alternates":"","name":"memo","shortname":":pencil:","category":"objects","emoji_order":"763","aliases":[],"aliases_ascii":[],"keywords":["work","office","write"]},"pencil2":{"unicode":"270f","unicode_alternates":"270f-fe0f","name":"pencil","shortname":":pencil2:","category":"objects","emoji_order":"764","aliases":[],"aliases_ascii":[],"keywords":["object","office","write"]},"crayon":{"unicode":"1f58d","unicode_alternates":"1f58d-fe0f","name":"lower left crayon","shortname":":crayon:","category":"objects","emoji_order":"765","aliases":[":lower_left_crayon:"],"aliases_ascii":[],"keywords":["object","office","write"]},"paintbrush":{"unicode":"1f58c","unicode_alternates":"1f58c-fe0f","name":"lower left paintbrush","shortname":":paintbrush:","category":"objects","emoji_order":"766","aliases":[":lower_left_paintbrush:"],"aliases_ascii":[],"keywords":["object","office","write"]},"mag":{"unicode":"1f50d","unicode_alternates":"","name":"left-pointing magnifying glass","shortname":":mag:","category":"objects","emoji_order":"767","aliases":[],"aliases_ascii":[],"keywords":["object"]},"mag_right":{"unicode":"1f50e","unicode_alternates":"","name":"right-pointing magnifying glass","shortname":":mag_right:","category":"objects","emoji_order":"768","aliases":[],"aliases_ascii":[],"keywords":["object"]},"heart":{"unicode":"2764","unicode_alternates":"2764-fe0f","name":"heavy black heart","shortname":":heart:","category":"symbols","emoji_order":"769","aliases":[],"aliases_ascii":["<3"],"keywords":["love","symbol","parties","parties"]},"yellow_heart":{"unicode":"1f49b","unicode_alternates":"","name":"yellow heart","shortname":":yellow_heart:","category":"symbols","emoji_order":"770","aliases":[],"aliases_ascii":[],"keywords":["love","symbol"]},"green_heart":{"unicode":"1f49a","unicode_alternates":"","name":"green heart","shortname":":green_heart:","category":"symbols","emoji_order":"771","aliases":[],"aliases_ascii":[],"keywords":["love","symbol"]},"blue_heart":{"unicode":"1f499","unicode_alternates":"","name":"blue heart","shortname":":blue_heart:","category":"symbols","emoji_order":"772","aliases":[],"aliases_ascii":[],"keywords":["love","symbol"]},"purple_heart":{"unicode":"1f49c","unicode_alternates":"","name":"purple heart","shortname":":purple_heart:","category":"symbols","emoji_order":"773","aliases":[],"aliases_ascii":[],"keywords":["love","symbol"]},"broken_heart":{"unicode":"1f494","unicode_alternates":"","name":"broken heart","shortname":":broken_heart:","category":"symbols","emoji_order":"774","aliases":[],"aliases_ascii":["<\/3"],"keywords":["love","symbol","heartbreak","heartbreak"]},"heart_exclamation":{"unicode":"2763","unicode_alternates":"2763-fe0f","name":"heavy heart exclamation mark ornament","shortname":":heart_exclamation:","category":"symbols","emoji_order":"775","aliases":[":heavy_heart_exclamation_mark_ornament:"],"aliases_ascii":[],"keywords":["love","symbol"]},"two_hearts":{"unicode":"1f495","unicode_alternates":"","name":"two hearts","shortname":":two_hearts:","category":"symbols","emoji_order":"776","aliases":[],"aliases_ascii":[],"keywords":["love","symbol"]},"revolving_hearts":{"unicode":"1f49e","unicode_alternates":"","name":"revolving hearts","shortname":":revolving_hearts:","category":"symbols","emoji_order":"777","aliases":[],"aliases_ascii":[],"keywords":["love","symbol"]},"heartbeat":{"unicode":"1f493","unicode_alternates":"","name":"beating heart","shortname":":heartbeat:","category":"symbols","emoji_order":"778","aliases":[],"aliases_ascii":[],"keywords":["love","symbol"]},"heartpulse":{"unicode":"1f497","unicode_alternates":"","name":"growing heart","shortname":":heartpulse:","category":"symbols","emoji_order":"779","aliases":[],"aliases_ascii":[],"keywords":["love","symbol"]},"sparkling_heart":{"unicode":"1f496","unicode_alternates":"","name":"sparkling heart","shortname":":sparkling_heart:","category":"symbols","emoji_order":"780","aliases":[],"aliases_ascii":[],"keywords":["love","symbol","girls night","girls night"]},"cupid":{"unicode":"1f498","unicode_alternates":"","name":"heart with arrow","shortname":":cupid:","category":"symbols","emoji_order":"781","aliases":[],"aliases_ascii":[],"keywords":["love","symbol"]},"gift_heart":{"unicode":"1f49d","unicode_alternates":"","name":"heart with ribbon","shortname":":gift_heart:","category":"symbols","emoji_order":"782","aliases":[],"aliases_ascii":[],"keywords":["love","symbol","condolence","condolence"]},"heart_decoration":{"unicode":"1f49f","unicode_alternates":"","name":"heart decoration","shortname":":heart_decoration:","category":"symbols","emoji_order":"783","aliases":[],"aliases_ascii":[],"keywords":["love","symbol"]},"peace":{"unicode":"262e","unicode_alternates":"262e-fe0f","name":"peace symbol","shortname":":peace:","category":"symbols","emoji_order":"784","aliases":[":peace_symbol:"],"aliases_ascii":[],"keywords":["symbol","peace","peace","drugs","drugs"]},"cross":{"unicode":"271d","unicode_alternates":"271d-fe0f","name":"latin cross","shortname":":cross:","category":"symbols","emoji_order":"785","aliases":[":latin_cross:"],"aliases_ascii":[],"keywords":["religion","symbol"]},"star_and_crescent":{"unicode":"262a","unicode_alternates":"262a-fe0f","name":"star and crescent","shortname":":star_and_crescent:","category":"symbols","emoji_order":"786","aliases":[],"aliases_ascii":[],"keywords":["religion","symbol"]},"om_symbol":{"unicode":"1f549","unicode_alternates":"1f549-fe0f","name":"om symbol","shortname":":om_symbol:","category":"symbols","emoji_order":"787","aliases":[],"aliases_ascii":[],"keywords":["religion","symbol"]},"wheel_of_dharma":{"unicode":"2638","unicode_alternates":"2638-fe0f","name":"wheel of dharma","shortname":":wheel_of_dharma:","category":"symbols","emoji_order":"788","aliases":[],"aliases_ascii":[],"keywords":["religion","symbol"]},"star_of_david":{"unicode":"2721","unicode_alternates":"2721-fe0f","name":"star of david","shortname":":star_of_david:","category":"symbols","emoji_order":"789","aliases":[],"aliases_ascii":[],"keywords":["religion","jew","star","symbol"]},"six_pointed_star":{"unicode":"1f52f","unicode_alternates":"","name":"six pointed star with middle dot","shortname":":six_pointed_star:","category":"symbols","emoji_order":"790","aliases":[],"aliases_ascii":[],"keywords":["religion","jew","star","symbol"]},"menorah":{"unicode":"1f54e","unicode_alternates":"","name":"menorah with nine branches","shortname":":menorah:","category":"symbols","emoji_order":"791","aliases":[],"aliases_ascii":[],"keywords":["religion","object","jew","symbol","holidays"]},"yin_yang":{"unicode":"262f","unicode_alternates":"262f-fe0f","name":"yin yang","shortname":":yin_yang:","category":"symbols","emoji_order":"792","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"orthodox_cross":{"unicode":"2626","unicode_alternates":"2626-fe0f","name":"orthodox cross","shortname":":orthodox_cross:","category":"symbols","emoji_order":"793","aliases":[],"aliases_ascii":[],"keywords":["religion","symbol"]},"place_of_worship":{"unicode":"1f6d0","unicode_alternates":"","name":"place of worship","shortname":":place_of_worship:","category":"symbols","emoji_order":"794","aliases":[":worship_symbol:"],"aliases_ascii":[],"keywords":["religion","symbol","pray","pray"]},"ophiuchus":{"unicode":"26ce","unicode_alternates":"","name":"ophiuchus","shortname":":ophiuchus:","category":"symbols","emoji_order":"795","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"aries":{"unicode":"2648","unicode_alternates":"2648-fe0f","name":"aries","shortname":":aries:","category":"symbols","emoji_order":"796","aliases":[],"aliases_ascii":[],"keywords":["zodiac","symbol"]},"taurus":{"unicode":"2649","unicode_alternates":"2649-fe0f","name":"taurus","shortname":":taurus:","category":"symbols","emoji_order":"797","aliases":[],"aliases_ascii":[],"keywords":["zodiac","symbol"]},"gemini":{"unicode":"264a","unicode_alternates":"264a-fe0f","name":"gemini","shortname":":gemini:","category":"symbols","emoji_order":"798","aliases":[],"aliases_ascii":[],"keywords":["zodiac","symbol"]},"cancer":{"unicode":"264b","unicode_alternates":"264b-fe0f","name":"cancer","shortname":":cancer:","category":"symbols","emoji_order":"799","aliases":[],"aliases_ascii":[],"keywords":["zodiac","symbol"]},"leo":{"unicode":"264c","unicode_alternates":"264c-fe0f","name":"leo","shortname":":leo:","category":"symbols","emoji_order":"800","aliases":[],"aliases_ascii":[],"keywords":["zodiac","symbol"]},"virgo":{"unicode":"264d","unicode_alternates":"264d-fe0f","name":"virgo","shortname":":virgo:","category":"symbols","emoji_order":"801","aliases":[],"aliases_ascii":[],"keywords":["zodiac","symbol"]},"libra":{"unicode":"264e","unicode_alternates":"264e-fe0f","name":"libra","shortname":":libra:","category":"symbols","emoji_order":"802","aliases":[],"aliases_ascii":[],"keywords":["zodiac","symbol"]},"scorpius":{"unicode":"264f","unicode_alternates":"264f-fe0f","name":"scorpius","shortname":":scorpius:","category":"symbols","emoji_order":"803","aliases":[],"aliases_ascii":[],"keywords":["zodiac","symbol"]},"sagittarius":{"unicode":"2650","unicode_alternates":"2650-fe0f","name":"sagittarius","shortname":":sagittarius:","category":"symbols","emoji_order":"804","aliases":[],"aliases_ascii":[],"keywords":["zodiac","symbol"]},"capricorn":{"unicode":"2651","unicode_alternates":"2651-fe0f","name":"capricorn","shortname":":capricorn:","category":"symbols","emoji_order":"805","aliases":[],"aliases_ascii":[],"keywords":["zodiac","symbol"]},"aquarius":{"unicode":"2652","unicode_alternates":"2652-fe0f","name":"aquarius","shortname":":aquarius:","category":"symbols","emoji_order":"806","aliases":[],"aliases_ascii":[],"keywords":["zodiac","symbol"]},"pisces":{"unicode":"2653","unicode_alternates":"2653-fe0f","name":"pisces","shortname":":pisces:","category":"symbols","emoji_order":"807","aliases":[],"aliases_ascii":[],"keywords":["zodiac","symbol"]},"id":{"unicode":"1f194","unicode_alternates":"","name":"squared id","shortname":":id:","category":"symbols","emoji_order":"808","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"atom":{"unicode":"269b","unicode_alternates":"269b-fe0f","name":"atom symbol","shortname":":atom:","category":"symbols","emoji_order":"809","aliases":[":atom_symbol:"],"aliases_ascii":[],"keywords":["symbol","science"]},"u7a7a":{"unicode":"1f233","unicode_alternates":"","name":"squared cjk unified ideograph-7a7a","shortname":":u7a7a:","category":"symbols","emoji_order":"810","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"u5272":{"unicode":"1f239","unicode_alternates":"","name":"squared cjk unified ideograph-5272","shortname":":u5272:","category":"symbols","emoji_order":"811","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"radioactive":{"unicode":"2622","unicode_alternates":"2622-fe0f","name":"radioactive sign","shortname":":radioactive:","category":"symbols","emoji_order":"812","aliases":[":radioactive_sign:"],"aliases_ascii":[],"keywords":["symbol","science"]},"biohazard":{"unicode":"2623","unicode_alternates":"2623-fe0f","name":"biohazard sign","shortname":":biohazard:","category":"symbols","emoji_order":"813","aliases":[":biohazard_sign:"],"aliases_ascii":[],"keywords":["symbol","science"]},"mobile_phone_off":{"unicode":"1f4f4","unicode_alternates":"","name":"mobile phone off","shortname":":mobile_phone_off:","category":"symbols","emoji_order":"814","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"vibration_mode":{"unicode":"1f4f3","unicode_alternates":"","name":"vibration mode","shortname":":vibration_mode:","category":"symbols","emoji_order":"815","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"u6709":{"unicode":"1f236","unicode_alternates":"","name":"squared cjk unified ideograph-6709","shortname":":u6709:","category":"symbols","emoji_order":"816","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"u7121":{"unicode":"1f21a","unicode_alternates":"1f21a-fe0f","name":"squared cjk unified ideograph-7121","shortname":":u7121:","category":"symbols","emoji_order":"817","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"u7533":{"unicode":"1f238","unicode_alternates":"","name":"squared cjk unified ideograph-7533","shortname":":u7533:","category":"symbols","emoji_order":"818","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"u55b6":{"unicode":"1f23a","unicode_alternates":"","name":"squared cjk unified ideograph-55b6","shortname":":u55b6:","category":"symbols","emoji_order":"819","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"u6708":{"unicode":"1f237","unicode_alternates":"1f237-fe0f","name":"squared cjk unified ideograph-6708","shortname":":u6708:","category":"symbols","emoji_order":"820","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"eight_pointed_black_star":{"unicode":"2734","unicode_alternates":"2734-fe0f","name":"eight pointed black star","shortname":":eight_pointed_black_star:","category":"symbols","emoji_order":"821","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"vs":{"unicode":"1f19a","unicode_alternates":"","name":"squared vs","shortname":":vs:","category":"symbols","emoji_order":"822","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"accept":{"unicode":"1f251","unicode_alternates":"","name":"circled ideograph accept","shortname":":accept:","category":"symbols","emoji_order":"823","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"white_flower":{"unicode":"1f4ae","unicode_alternates":"","name":"white flower","shortname":":white_flower:","category":"symbols","emoji_order":"824","aliases":[],"aliases_ascii":[],"keywords":["flower","symbol"]},"ideograph_advantage":{"unicode":"1f250","unicode_alternates":"","name":"circled ideograph advantage","shortname":":ideograph_advantage:","category":"symbols","emoji_order":"825","aliases":[],"aliases_ascii":[],"keywords":["japan","symbol"]},"secret":{"unicode":"3299","unicode_alternates":"3299-fe0f","name":"circled ideograph secret","shortname":":secret:","category":"symbols","emoji_order":"826","aliases":[],"aliases_ascii":[],"keywords":["japan","symbol"]},"congratulations":{"unicode":"3297","unicode_alternates":"3297-fe0f","name":"circled ideograph congratulation","shortname":":congratulations:","category":"symbols","emoji_order":"827","aliases":[],"aliases_ascii":[],"keywords":["japan","symbol"]},"u5408":{"unicode":"1f234","unicode_alternates":"","name":"squared cjk unified ideograph-5408","shortname":":u5408:","category":"symbols","emoji_order":"828","aliases":[],"aliases_ascii":[],"keywords":["japan","symbol"]},"u6e80":{"unicode":"1f235","unicode_alternates":"","name":"squared cjk unified ideograph-6e80","shortname":":u6e80:","category":"symbols","emoji_order":"829","aliases":[],"aliases_ascii":[],"keywords":["japan","symbol"]},"u7981":{"unicode":"1f232","unicode_alternates":"","name":"squared cjk unified ideograph-7981","shortname":":u7981:","category":"symbols","emoji_order":"830","aliases":[],"aliases_ascii":[],"keywords":["japan","symbol"]},"a":{"unicode":"1f170","unicode_alternates":"","name":"negative squared latin capital letter a","shortname":":a:","category":"symbols","emoji_order":"831","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"b":{"unicode":"1f171","unicode_alternates":"","name":"negative squared latin capital letter b","shortname":":b:","category":"symbols","emoji_order":"832","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"ab":{"unicode":"1f18e","unicode_alternates":"","name":"negative squared ab","shortname":":ab:","category":"symbols","emoji_order":"833","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"cl":{"unicode":"1f191","unicode_alternates":"","name":"squared cl","shortname":":cl:","category":"symbols","emoji_order":"834","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"o2":{"unicode":"1f17e","unicode_alternates":"","name":"negative squared latin capital letter o","shortname":":o2:","category":"symbols","emoji_order":"835","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"sos":{"unicode":"1f198","unicode_alternates":"","name":"squared sos","shortname":":sos:","category":"symbols","emoji_order":"836","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"no_entry":{"unicode":"26d4","unicode_alternates":"26d4-fe0f","name":"no entry","shortname":":no_entry:","category":"symbols","emoji_order":"837","aliases":[],"aliases_ascii":[],"keywords":["symbol","circle","circle"]},"name_badge":{"unicode":"1f4db","unicode_alternates":"","name":"name badge","shortname":":name_badge:","category":"symbols","emoji_order":"838","aliases":[],"aliases_ascii":[],"keywords":["work"]},"no_entry_sign":{"unicode":"1f6ab","unicode_alternates":"","name":"no entry sign","shortname":":no_entry_sign:","category":"symbols","emoji_order":"839","aliases":[],"aliases_ascii":[],"keywords":["symbol","circle","circle"]},"x":{"unicode":"274c","unicode_alternates":"","name":"cross mark","shortname":":x:","category":"symbols","emoji_order":"840","aliases":[],"aliases_ascii":[],"keywords":["symbol","sol","sol"]},"o":{"unicode":"2b55","unicode_alternates":"2b55-fe0f","name":"heavy large circle","shortname":":o:","category":"symbols","emoji_order":"841","aliases":[],"aliases_ascii":[],"keywords":["symbol","circle","circle"]},"anger":{"unicode":"1f4a2","unicode_alternates":"","name":"anger symbol","shortname":":anger:","category":"symbols","emoji_order":"842","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"hotsprings":{"unicode":"2668","unicode_alternates":"2668-fe0f","name":"hot springs","shortname":":hotsprings:","category":"symbols","emoji_order":"843","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"no_pedestrians":{"unicode":"1f6b7","unicode_alternates":"","name":"no pedestrians","shortname":":no_pedestrians:","category":"symbols","emoji_order":"844","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"do_not_litter":{"unicode":"1f6af","unicode_alternates":"","name":"do not litter symbol","shortname":":do_not_litter:","category":"symbols","emoji_order":"845","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"no_bicycles":{"unicode":"1f6b3","unicode_alternates":"","name":"no bicycles","shortname":":no_bicycles:","category":"symbols","emoji_order":"846","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"non-potable_water":{"unicode":"1f6b1","unicode_alternates":"","name":"non-potable water symbol","shortname":":non-potable_water:","category":"symbols","emoji_order":"847","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"underage":{"unicode":"1f51e","unicode_alternates":"","name":"no one under eighteen symbol","shortname":":underage:","category":"symbols","emoji_order":"848","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"no_mobile_phones":{"unicode":"1f4f5","unicode_alternates":"","name":"no mobile phones","shortname":":no_mobile_phones:","category":"symbols","emoji_order":"849","aliases":[],"aliases_ascii":[],"keywords":["symbol","phone"]},"exclamation":{"unicode":"2757","unicode_alternates":"2757-fe0f","name":"heavy exclamation mark symbol","shortname":":exclamation:","category":"symbols","emoji_order":"850","aliases":[],"aliases_ascii":[],"keywords":["symbol","punctuation"]},"grey_exclamation":{"unicode":"2755","unicode_alternates":"","name":"white exclamation mark ornament","shortname":":grey_exclamation:","category":"symbols","emoji_order":"851","aliases":[],"aliases_ascii":[],"keywords":["symbol","punctuation"]},"question":{"unicode":"2753","unicode_alternates":"","name":"black question mark ornament","shortname":":question:","category":"symbols","emoji_order":"852","aliases":[],"aliases_ascii":[],"keywords":["symbol","punctuation","wth","wth"]},"grey_question":{"unicode":"2754","unicode_alternates":"","name":"white question mark ornament","shortname":":grey_question:","category":"symbols","emoji_order":"853","aliases":[],"aliases_ascii":[],"keywords":["symbol","punctuation"]},"bangbang":{"unicode":"203c","unicode_alternates":"203c-fe0f","name":"double exclamation mark","shortname":":bangbang:","category":"symbols","emoji_order":"854","aliases":[],"aliases_ascii":[],"keywords":["symbol","punctuation"]},"interrobang":{"unicode":"2049","unicode_alternates":"2049-fe0f","name":"exclamation question mark","shortname":":interrobang:","category":"symbols","emoji_order":"855","aliases":[],"aliases_ascii":[],"keywords":["symbol","punctuation"]},"100":{"unicode":"1f4af","unicode_alternates":"","name":"hundred points symbol","shortname":":100:","category":"symbols","emoji_order":"856","aliases":[],"aliases_ascii":[],"keywords":["symbol","wow","wow","win","win","perfect","perfect","parties","parties"]},"low_brightness":{"unicode":"1f505","unicode_alternates":"","name":"low brightness symbol","shortname":":low_brightness:","category":"symbols","emoji_order":"857","aliases":[],"aliases_ascii":[],"keywords":["symbol","sun"]},"high_brightness":{"unicode":"1f506","unicode_alternates":"","name":"high brightness symbol","shortname":":high_brightness:","category":"symbols","emoji_order":"858","aliases":[],"aliases_ascii":[],"keywords":["symbol","sun"]},"trident":{"unicode":"1f531","unicode_alternates":"","name":"trident emblem","shortname":":trident:","category":"symbols","emoji_order":"859","aliases":[],"aliases_ascii":[],"keywords":["object","symbol"]},"fleur-de-lis":{"unicode":"269c","unicode_alternates":"269c-fe0f","name":"fleur-de-lis","shortname":":fleur-de-lis:","category":"symbols","emoji_order":"860","aliases":[],"aliases_ascii":[],"keywords":["object","symbol"]},"part_alternation_mark":{"unicode":"303d","unicode_alternates":"303d-fe0f","name":"part alternation mark","shortname":":part_alternation_mark:","category":"symbols","emoji_order":"861","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"warning":{"unicode":"26a0","unicode_alternates":"26a0-fe0f","name":"warning sign","shortname":":warning:","category":"symbols","emoji_order":"862","aliases":[],"aliases_ascii":[],"keywords":["symbol","punctuation"]},"children_crossing":{"unicode":"1f6b8","unicode_alternates":"","name":"children crossing","shortname":":children_crossing:","category":"symbols","emoji_order":"863","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"beginner":{"unicode":"1f530","unicode_alternates":"","name":"japanese symbol for beginner","shortname":":beginner:","category":"symbols","emoji_order":"864","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"recycle":{"unicode":"267b","unicode_alternates":"267b-fe0f","name":"black universal recycling symbol","shortname":":recycle:","category":"symbols","emoji_order":"865","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"u6307":{"unicode":"1f22f","unicode_alternates":"1f22f-fe0f","name":"squared cjk unified ideograph-6307","shortname":":u6307:","category":"symbols","emoji_order":"866","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"chart":{"unicode":"1f4b9","unicode_alternates":"","name":"chart with upwards trend and yen sign","shortname":":chart:","category":"symbols","emoji_order":"867","aliases":[],"aliases_ascii":[],"keywords":["symbol","money","money"]},"sparkle":{"unicode":"2747","unicode_alternates":"2747-fe0f","name":"sparkle","shortname":":sparkle:","category":"symbols","emoji_order":"868","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"eight_spoked_asterisk":{"unicode":"2733","unicode_alternates":"2733-fe0f","name":"eight spoked asterisk","shortname":":eight_spoked_asterisk:","category":"symbols","emoji_order":"869","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"negative_squared_cross_mark":{"unicode":"274e","unicode_alternates":"","name":"negative squared cross mark","shortname":":negative_squared_cross_mark:","category":"symbols","emoji_order":"870","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"white_check_mark":{"unicode":"2705","unicode_alternates":"","name":"white heavy check mark","shortname":":white_check_mark:","category":"symbols","emoji_order":"871","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"diamond_shape_with_a_dot_inside":{"unicode":"1f4a0","unicode_alternates":"","name":"diamond shape with a dot inside","shortname":":diamond_shape_with_a_dot_inside:","category":"symbols","emoji_order":"872","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"cyclone":{"unicode":"1f300","unicode_alternates":"","name":"cyclone","shortname":":cyclone:","category":"symbols","emoji_order":"873","aliases":[],"aliases_ascii":[],"keywords":["symbol","drugs","drugs"]},"loop":{"unicode":"27bf","unicode_alternates":"","name":"double curly loop","shortname":":loop:","category":"symbols","emoji_order":"874","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"globe_with_meridians":{"unicode":"1f310","unicode_alternates":"","name":"globe with meridians","shortname":":globe_with_meridians:","category":"symbols","emoji_order":"875","aliases":[],"aliases_ascii":[],"keywords":["symbol","globe","globe"]},"m":{"unicode":"24c2","unicode_alternates":"24c2-fe0f","name":"circled latin capital letter m","shortname":":m:","category":"symbols","emoji_order":"876","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"atm":{"unicode":"1f3e7","unicode_alternates":"","name":"automated teller machine","shortname":":atm:","category":"symbols","emoji_order":"877","aliases":[],"aliases_ascii":[],"keywords":["electronics","symbol","money","money"]},"sa":{"unicode":"1f202","unicode_alternates":"1f202-fe0f","name":"squared katakana sa","shortname":":sa:","category":"symbols","emoji_order":"878","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"passport_control":{"unicode":"1f6c2","unicode_alternates":"","name":"passport control","shortname":":passport_control:","category":"symbols","emoji_order":"879","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"customs":{"unicode":"1f6c3","unicode_alternates":"","name":"customs","shortname":":customs:","category":"symbols","emoji_order":"880","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"baggage_claim":{"unicode":"1f6c4","unicode_alternates":"","name":"baggage claim","shortname":":baggage_claim:","category":"symbols","emoji_order":"881","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"left_luggage":{"unicode":"1f6c5","unicode_alternates":"","name":"left luggage","shortname":":left_luggage:","category":"symbols","emoji_order":"882","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"wheelchair":{"unicode":"267f","unicode_alternates":"267f-fe0f","name":"wheelchair symbol","shortname":":wheelchair:","category":"symbols","emoji_order":"883","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"no_smoking":{"unicode":"1f6ad","unicode_alternates":"","name":"no smoking symbol","shortname":":no_smoking:","category":"symbols","emoji_order":"884","aliases":[],"aliases_ascii":[],"keywords":["symbol","smoking","smoking"]},"wc":{"unicode":"1f6be","unicode_alternates":"","name":"water closet","shortname":":wc:","category":"symbols","emoji_order":"885","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"parking":{"unicode":"1f17f","unicode_alternates":"1f17f-fe0f","name":"negative squared latin capital letter p","shortname":":parking:","category":"symbols","emoji_order":"886","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"potable_water":{"unicode":"1f6b0","unicode_alternates":"","name":"potable water symbol","shortname":":potable_water:","category":"symbols","emoji_order":"887","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"mens":{"unicode":"1f6b9","unicode_alternates":"","name":"mens symbol","shortname":":mens:","category":"symbols","emoji_order":"888","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"womens":{"unicode":"1f6ba","unicode_alternates":"","name":"womens symbol","shortname":":womens:","category":"symbols","emoji_order":"889","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"baby_symbol":{"unicode":"1f6bc","unicode_alternates":"","name":"baby symbol","shortname":":baby_symbol:","category":"symbols","emoji_order":"890","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"restroom":{"unicode":"1f6bb","unicode_alternates":"","name":"restroom","shortname":":restroom:","category":"symbols","emoji_order":"891","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"put_litter_in_its_place":{"unicode":"1f6ae","unicode_alternates":"","name":"put litter in its place symbol","shortname":":put_litter_in_its_place:","category":"symbols","emoji_order":"892","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"cinema":{"unicode":"1f3a6","unicode_alternates":"","name":"cinema","shortname":":cinema:","category":"symbols","emoji_order":"893","aliases":[],"aliases_ascii":[],"keywords":["symbol","camera","movie"]},"signal_strength":{"unicode":"1f4f6","unicode_alternates":"","name":"antenna with bars","shortname":":signal_strength:","category":"symbols","emoji_order":"894","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"koko":{"unicode":"1f201","unicode_alternates":"","name":"squared katakana koko","shortname":":koko:","category":"symbols","emoji_order":"895","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"ng":{"unicode":"1f196","unicode_alternates":"","name":"squared ng","shortname":":ng:","category":"symbols","emoji_order":"896","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"ok":{"unicode":"1f197","unicode_alternates":"","name":"squared ok","shortname":":ok:","category":"symbols","emoji_order":"897","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"up":{"unicode":"1f199","unicode_alternates":"","name":"squared up with exclamation mark","shortname":":up:","category":"symbols","emoji_order":"898","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"cool":{"unicode":"1f192","unicode_alternates":"","name":"squared cool","shortname":":cool:","category":"symbols","emoji_order":"899","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"new":{"unicode":"1f195","unicode_alternates":"","name":"squared new","shortname":":new:","category":"symbols","emoji_order":"900","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"free":{"unicode":"1f193","unicode_alternates":"","name":"squared free","shortname":":free:","category":"symbols","emoji_order":"901","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"zero":{"unicode":"0030-20e3","unicode_alternates":"0030-fe0f-20e3","name":"keycap digit zero","shortname":":zero:","category":"symbols","emoji_order":"902","aliases":[],"aliases_ascii":[],"keywords":["number","math","symbol"]},"one":{"unicode":"0031-20e3","unicode_alternates":"0031-fe0f-20e3","name":"keycap digit one","shortname":":one:","category":"symbols","emoji_order":"903","aliases":[],"aliases_ascii":[],"keywords":["number","math","symbol"]},"two":{"unicode":"0032-20e3","unicode_alternates":"0032-fe0f-20e3","name":"keycap digit two","shortname":":two:","category":"symbols","emoji_order":"904","aliases":[],"aliases_ascii":[],"keywords":["number","math","symbol"]},"three":{"unicode":"0033-20e3","unicode_alternates":"0033-fe0f-20e3","name":"keycap digit three","shortname":":three:","category":"symbols","emoji_order":"905","aliases":[],"aliases_ascii":[],"keywords":["number","math","symbol"]},"four":{"unicode":"0034-20e3","unicode_alternates":"0034-fe0f-20e3","name":"keycap digit four","shortname":":four:","category":"symbols","emoji_order":"906","aliases":[],"aliases_ascii":[],"keywords":["number","math","symbol"]},"five":{"unicode":"0035-20e3","unicode_alternates":"0035-fe0f-20e3","name":"keycap digit five","shortname":":five:","category":"symbols","emoji_order":"907","aliases":[],"aliases_ascii":[],"keywords":["number","math","symbol"]},"six":{"unicode":"0036-20e3","unicode_alternates":"0036-fe0f-20e3","name":"keycap digit six","shortname":":six:","category":"symbols","emoji_order":"908","aliases":[],"aliases_ascii":[],"keywords":["number","math","symbol"]},"seven":{"unicode":"0037-20e3","unicode_alternates":"0037-fe0f-20e3","name":"keycap digit seven","shortname":":seven:","category":"symbols","emoji_order":"909","aliases":[],"aliases_ascii":[],"keywords":["number","math","symbol"]},"eight":{"unicode":"0038-20e3","unicode_alternates":"0038-fe0f-20e3","name":"keycap digit eight","shortname":":eight:","category":"symbols","emoji_order":"910","aliases":[],"aliases_ascii":[],"keywords":["number","math","symbol"]},"nine":{"unicode":"0039-20e3","unicode_alternates":"0039-fe0f-20e3","name":"keycap digit nine","shortname":":nine:","category":"symbols","emoji_order":"911","aliases":[],"aliases_ascii":[],"keywords":["number","math","symbol"]},"ten":{"unicode":"1f51f","unicode_alternates":"","name":"keycap ten","shortname":":ten:","category":"symbols","emoji_order":"912","aliases":[],"aliases_ascii":[],"keywords":["number","math","symbol"]},"1234":{"unicode":"1f522","unicode_alternates":"","name":"input symbol for numbers","shortname":":1234:","category":"symbols","emoji_order":"913","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"arrow_forward":{"unicode":"25b6","unicode_alternates":"25b6-fe0f","name":"black right-pointing triangle","shortname":":arrow_forward:","category":"symbols","emoji_order":"914","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol","triangle","triangle"]},"pause_button":{"unicode":"23f8","unicode_alternates":"23f8-fe0f","name":"double vertical bar","shortname":":pause_button:","category":"symbols","emoji_order":"915","aliases":[":double_vertical_bar:"],"aliases_ascii":[],"keywords":["symbol"]},"play_pause":{"unicode":"23ef","unicode_alternates":"23ef-fe0f","name":"black right-pointing double triangle with double vertical bar","shortname":":play_pause:","category":"symbols","emoji_order":"916","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"stop_button":{"unicode":"23f9","unicode_alternates":"23f9-fe0f","name":"black square for stop","shortname":":stop_button:","category":"symbols","emoji_order":"917","aliases":[],"aliases_ascii":[],"keywords":["symbol","square","square"]},"record_button":{"unicode":"23fa","unicode_alternates":"23fa-fe0f","name":"black circle for record","shortname":":record_button:","category":"symbols","emoji_order":"918","aliases":[],"aliases_ascii":[],"keywords":["symbol","circle","circle"]},"track_next":{"unicode":"23ed","unicode_alternates":"23ed-fe0f","name":"black right-pointing double triangle with vertical bar","shortname":":track_next:","category":"symbols","emoji_order":"919","aliases":[":next_track:"],"aliases_ascii":[],"keywords":["arrow","symbol"]},"track_previous":{"unicode":"23ee","unicode_alternates":"23ee-fe0f","name":"black left-pointing double triangle with vertical bar","shortname":":track_previous:","category":"symbols","emoji_order":"920","aliases":[":previous_track:"],"aliases_ascii":[],"keywords":["arrow","symbol"]},"fast_forward":{"unicode":"23e9","unicode_alternates":"","name":"black right-pointing double triangle","shortname":":fast_forward:","category":"symbols","emoji_order":"921","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"rewind":{"unicode":"23ea","unicode_alternates":"","name":"black left-pointing double triangle","shortname":":rewind:","category":"symbols","emoji_order":"922","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"twisted_rightwards_arrows":{"unicode":"1f500","unicode_alternates":"","name":"twisted rightwards arrows","shortname":":twisted_rightwards_arrows:","category":"symbols","emoji_order":"923","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"repeat":{"unicode":"1f501","unicode_alternates":"","name":"clockwise rightwards and leftwards open circle arrows","shortname":":repeat:","category":"symbols","emoji_order":"924","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"repeat_one":{"unicode":"1f502","unicode_alternates":"","name":"clockwise rightwards and leftwards open circle arrows with circled one overlay","shortname":":repeat_one:","category":"symbols","emoji_order":"925","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"arrow_backward":{"unicode":"25c0","unicode_alternates":"25c0-fe0f","name":"black left-pointing triangle","shortname":":arrow_backward:","category":"symbols","emoji_order":"926","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol","triangle","triangle"]},"arrow_up_small":{"unicode":"1f53c","unicode_alternates":"","name":"up-pointing small red triangle","shortname":":arrow_up_small:","category":"symbols","emoji_order":"927","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol","triangle","triangle"]},"arrow_down_small":{"unicode":"1f53d","unicode_alternates":"","name":"down-pointing small red triangle","shortname":":arrow_down_small:","category":"symbols","emoji_order":"928","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol","triangle","triangle"]},"arrow_double_up":{"unicode":"23eb","unicode_alternates":"","name":"black up-pointing double triangle","shortname":":arrow_double_up:","category":"symbols","emoji_order":"929","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"arrow_double_down":{"unicode":"23ec","unicode_alternates":"","name":"black down-pointing double triangle","shortname":":arrow_double_down:","category":"symbols","emoji_order":"930","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"arrow_right":{"unicode":"27a1","unicode_alternates":"27a1-fe0f","name":"black rightwards arrow","shortname":":arrow_right:","category":"symbols","emoji_order":"931","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"arrow_left":{"unicode":"2b05","unicode_alternates":"2b05-fe0f","name":"leftwards black arrow","shortname":":arrow_left:","category":"symbols","emoji_order":"932","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"arrow_up":{"unicode":"2b06","unicode_alternates":"2b06-fe0f","name":"upwards black arrow","shortname":":arrow_up:","category":"symbols","emoji_order":"933","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"arrow_down":{"unicode":"2b07","unicode_alternates":"2b07-fe0f","name":"downwards black arrow","shortname":":arrow_down:","category":"symbols","emoji_order":"934","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"arrow_upper_right":{"unicode":"2197","unicode_alternates":"2197-fe0f","name":"north east arrow","shortname":":arrow_upper_right:","category":"symbols","emoji_order":"935","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"arrow_lower_right":{"unicode":"2198","unicode_alternates":"2198-fe0f","name":"south east arrow","shortname":":arrow_lower_right:","category":"symbols","emoji_order":"936","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"arrow_lower_left":{"unicode":"2199","unicode_alternates":"2199-fe0f","name":"south west arrow","shortname":":arrow_lower_left:","category":"symbols","emoji_order":"937","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"arrow_upper_left":{"unicode":"2196","unicode_alternates":"2196-fe0f","name":"north west arrow","shortname":":arrow_upper_left:","category":"symbols","emoji_order":"938","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"arrow_up_down":{"unicode":"2195","unicode_alternates":"2195-fe0f","name":"up down arrow","shortname":":arrow_up_down:","category":"symbols","emoji_order":"939","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"left_right_arrow":{"unicode":"2194","unicode_alternates":"2194-fe0f","name":"left right arrow","shortname":":left_right_arrow:","category":"symbols","emoji_order":"940","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"arrows_counterclockwise":{"unicode":"1f504","unicode_alternates":"","name":"anticlockwise downwards and upwards open circle arrows","shortname":":arrows_counterclockwise:","category":"symbols","emoji_order":"941","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"arrow_right_hook":{"unicode":"21aa","unicode_alternates":"21aa-fe0f","name":"rightwards arrow with hook","shortname":":arrow_right_hook:","category":"symbols","emoji_order":"942","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"leftwards_arrow_with_hook":{"unicode":"21a9","unicode_alternates":"21a9-fe0f","name":"leftwards arrow with hook","shortname":":leftwards_arrow_with_hook:","category":"symbols","emoji_order":"943","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"arrow_heading_up":{"unicode":"2934","unicode_alternates":"2934-fe0f","name":"arrow pointing rightwards then curving upwards","shortname":":arrow_heading_up:","category":"symbols","emoji_order":"944","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"arrow_heading_down":{"unicode":"2935","unicode_alternates":"2935-fe0f","name":"arrow pointing rightwards then curving downwards","shortname":":arrow_heading_down:","category":"symbols","emoji_order":"945","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"hash":{"unicode":"0023-20e3","unicode_alternates":"0023-fe0f-20e3","name":"keycap number sign","shortname":":hash:","category":"symbols","emoji_order":"946","aliases":[],"aliases_ascii":[],"keywords":["number","symbol"]},"asterisk":{"unicode":"002a-20e3","unicode_alternates":"002a-fe0f-20e3","name":"keycap asterisk","shortname":":asterisk:","category":"symbols","emoji_order":"947","aliases":[":keycap_asterisk:"],"aliases_ascii":[],"keywords":["symbol"]},"information_source":{"unicode":"2139","unicode_alternates":"2139-fe0f","name":"information source","shortname":":information_source:","category":"symbols","emoji_order":"948","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"abc":{"unicode":"1f524","unicode_alternates":"","name":"input symbol for latin letters","shortname":":abc:","category":"symbols","emoji_order":"949","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"abcd":{"unicode":"1f521","unicode_alternates":"","name":"input symbol for latin small letters","shortname":":abcd:","category":"symbols","emoji_order":"950","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"capital_abcd":{"unicode":"1f520","unicode_alternates":"","name":"input symbol for latin capital letters","shortname":":capital_abcd:","category":"symbols","emoji_order":"951","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"symbols":{"unicode":"1f523","unicode_alternates":"","name":"input symbol for symbols","shortname":":symbols:","category":"symbols","emoji_order":"952","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"musical_note":{"unicode":"1f3b5","unicode_alternates":"","name":"musical note","shortname":":musical_note:","category":"symbols","emoji_order":"953","aliases":[],"aliases_ascii":[],"keywords":["instruments","symbol"]},"notes":{"unicode":"1f3b6","unicode_alternates":"","name":"multiple musical notes","shortname":":notes:","category":"symbols","emoji_order":"954","aliases":[],"aliases_ascii":[],"keywords":["instruments","symbol"]},"wavy_dash":{"unicode":"3030","unicode_alternates":"3030-fe0f","name":"wavy dash","shortname":":wavy_dash:","category":"symbols","emoji_order":"955","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"curly_loop":{"unicode":"27b0","unicode_alternates":"","name":"curly loop","shortname":":curly_loop:","category":"symbols","emoji_order":"956","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"heavy_check_mark":{"unicode":"2714","unicode_alternates":"2714-fe0f","name":"heavy check mark","shortname":":heavy_check_mark:","category":"symbols","emoji_order":"957","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"arrows_clockwise":{"unicode":"1f503","unicode_alternates":"","name":"clockwise downwards and upwards open circle arrows","shortname":":arrows_clockwise:","category":"symbols","emoji_order":"958","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"heavy_plus_sign":{"unicode":"2795","unicode_alternates":"","name":"heavy plus sign","shortname":":heavy_plus_sign:","category":"symbols","emoji_order":"959","aliases":[],"aliases_ascii":[],"keywords":["math","symbol"]},"heavy_minus_sign":{"unicode":"2796","unicode_alternates":"","name":"heavy minus sign","shortname":":heavy_minus_sign:","category":"symbols","emoji_order":"960","aliases":[],"aliases_ascii":[],"keywords":["math","symbol"]},"heavy_division_sign":{"unicode":"2797","unicode_alternates":"","name":"heavy division sign","shortname":":heavy_division_sign:","category":"symbols","emoji_order":"961","aliases":[],"aliases_ascii":[],"keywords":["math","symbol"]},"heavy_multiplication_x":{"unicode":"2716","unicode_alternates":"2716-fe0f","name":"heavy multiplication x","shortname":":heavy_multiplication_x:","category":"symbols","emoji_order":"962","aliases":[],"aliases_ascii":[],"keywords":["math","symbol"]},"heavy_dollar_sign":{"unicode":"1f4b2","unicode_alternates":"","name":"heavy dollar sign","shortname":":heavy_dollar_sign:","category":"symbols","emoji_order":"963","aliases":[],"aliases_ascii":[],"keywords":["math","symbol","money","money"]},"currency_exchange":{"unicode":"1f4b1","unicode_alternates":"","name":"currency exchange","shortname":":currency_exchange:","category":"symbols","emoji_order":"964","aliases":[],"aliases_ascii":[],"keywords":["symbol","money","money"]},"copyright":{"unicode":"00a9","unicode_alternates":"00a9-fe0f","name":"copyright sign","shortname":":copyright:","category":"symbols","emoji_order":"965","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"registered":{"unicode":"00ae","unicode_alternates":"00ae-fe0f","name":"registered sign","shortname":":registered:","category":"symbols","emoji_order":"966","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"tm":{"unicode":"2122","unicode_alternates":"2122-fe0f","name":"trade mark sign","shortname":":tm:","category":"symbols","emoji_order":"967","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"end":{"unicode":"1f51a","unicode_alternates":"","name":"end with leftwards arrow above","shortname":":end:","category":"symbols","emoji_order":"968","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"back":{"unicode":"1f519","unicode_alternates":"","name":"back with leftwards arrow above","shortname":":back:","category":"symbols","emoji_order":"969","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"on":{"unicode":"1f51b","unicode_alternates":"","name":"on with exclamation mark with left right arrow abo","shortname":":on:","category":"symbols","emoji_order":"970","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"top":{"unicode":"1f51d","unicode_alternates":"","name":"top with upwards arrow above","shortname":":top:","category":"symbols","emoji_order":"971","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"soon":{"unicode":"1f51c","unicode_alternates":"","name":"soon with rightwards arrow above","shortname":":soon:","category":"symbols","emoji_order":"972","aliases":[],"aliases_ascii":[],"keywords":["arrow","symbol"]},"ballot_box_with_check":{"unicode":"2611","unicode_alternates":"2611-fe0f","name":"ballot box with check","shortname":":ballot_box_with_check:","category":"symbols","emoji_order":"973","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"radio_button":{"unicode":"1f518","unicode_alternates":"","name":"radio button","shortname":":radio_button:","category":"symbols","emoji_order":"974","aliases":[],"aliases_ascii":[],"keywords":["symbol","circle","circle"]},"white_circle":{"unicode":"26aa","unicode_alternates":"26aa-fe0f","name":"medium white circle","shortname":":white_circle:","category":"symbols","emoji_order":"975","aliases":[],"aliases_ascii":[],"keywords":["shapes","symbol","circle","circle"]},"black_circle":{"unicode":"26ab","unicode_alternates":"26ab-fe0f","name":"medium black circle","shortname":":black_circle:","category":"symbols","emoji_order":"976","aliases":[],"aliases_ascii":[],"keywords":["shapes","symbol","circle","circle"]},"red_circle":{"unicode":"1f534","unicode_alternates":"","name":"large red circle","shortname":":red_circle:","category":"symbols","emoji_order":"977","aliases":[],"aliases_ascii":[],"keywords":["shapes","symbol","circle","circle"]},"large_blue_circle":{"unicode":"1f535","unicode_alternates":"","name":"large blue circle","shortname":":large_blue_circle:","category":"symbols","emoji_order":"978","aliases":[],"aliases_ascii":[],"keywords":["shapes","symbol","circle","circle"]},"small_orange_diamond":{"unicode":"1f538","unicode_alternates":"","name":"small orange diamond","shortname":":small_orange_diamond:","category":"symbols","emoji_order":"979","aliases":[],"aliases_ascii":[],"keywords":["shapes","symbol"]},"small_blue_diamond":{"unicode":"1f539","unicode_alternates":"","name":"small blue diamond","shortname":":small_blue_diamond:","category":"symbols","emoji_order":"980","aliases":[],"aliases_ascii":[],"keywords":["shapes","symbol"]},"large_orange_diamond":{"unicode":"1f536","unicode_alternates":"","name":"large orange diamond","shortname":":large_orange_diamond:","category":"symbols","emoji_order":"981","aliases":[],"aliases_ascii":[],"keywords":["shapes","symbol"]},"large_blue_diamond":{"unicode":"1f537","unicode_alternates":"","name":"large blue diamond","shortname":":large_blue_diamond:","category":"symbols","emoji_order":"982","aliases":[],"aliases_ascii":[],"keywords":["shapes","symbol"]},"small_red_triangle":{"unicode":"1f53a","unicode_alternates":"","name":"up-pointing red triangle","shortname":":small_red_triangle:","category":"symbols","emoji_order":"983","aliases":[],"aliases_ascii":[],"keywords":["shapes","symbol","triangle","triangle"]},"black_small_square":{"unicode":"25aa","unicode_alternates":"25aa-fe0f","name":"black small square","shortname":":black_small_square:","category":"symbols","emoji_order":"984","aliases":[],"aliases_ascii":[],"keywords":["shapes","symbol","square","square"]},"white_small_square":{"unicode":"25ab","unicode_alternates":"25ab-fe0f","name":"white small square","shortname":":white_small_square:","category":"symbols","emoji_order":"985","aliases":[],"aliases_ascii":[],"keywords":["shapes","symbol","square","square"]},"black_large_square":{"unicode":"2b1b","unicode_alternates":"2b1b-fe0f","name":"black large square","shortname":":black_large_square:","category":"symbols","emoji_order":"986","aliases":[],"aliases_ascii":[],"keywords":["shapes","symbol","square","square"]},"white_large_square":{"unicode":"2b1c","unicode_alternates":"2b1c-fe0f","name":"white large square","shortname":":white_large_square:","category":"symbols","emoji_order":"987","aliases":[],"aliases_ascii":[],"keywords":["shapes","symbol","square","square"]},"small_red_triangle_down":{"unicode":"1f53b","unicode_alternates":"","name":"down-pointing red triangle","shortname":":small_red_triangle_down:","category":"symbols","emoji_order":"988","aliases":[],"aliases_ascii":[],"keywords":["shapes","symbol","triangle","triangle"]},"black_medium_square":{"unicode":"25fc","unicode_alternates":"25fc-fe0f","name":"black medium square","shortname":":black_medium_square:","category":"symbols","emoji_order":"989","aliases":[],"aliases_ascii":[],"keywords":["shapes","symbol","square","square"]},"white_medium_square":{"unicode":"25fb","unicode_alternates":"25fb-fe0f","name":"white medium square","shortname":":white_medium_square:","category":"symbols","emoji_order":"990","aliases":[],"aliases_ascii":[],"keywords":["shapes","symbol","square","square"]},"black_medium_small_square":{"unicode":"25fe","unicode_alternates":"25fe-fe0f","name":"black medium small square","shortname":":black_medium_small_square:","category":"symbols","emoji_order":"991","aliases":[],"aliases_ascii":[],"keywords":["shapes","symbol","square","square"]},"white_medium_small_square":{"unicode":"25fd","unicode_alternates":"25fd-fe0f","name":"white medium small square","shortname":":white_medium_small_square:","category":"symbols","emoji_order":"992","aliases":[],"aliases_ascii":[],"keywords":["shapes","symbol","square","square"]},"black_square_button":{"unicode":"1f532","unicode_alternates":"","name":"black square button","shortname":":black_square_button:","category":"symbols","emoji_order":"993","aliases":[],"aliases_ascii":[],"keywords":["shapes","symbol","square","square"]},"white_square_button":{"unicode":"1f533","unicode_alternates":"","name":"white square button","shortname":":white_square_button:","category":"symbols","emoji_order":"994","aliases":[],"aliases_ascii":[],"keywords":["shapes","symbol","square","square"]},"speaker":{"unicode":"1f508","unicode_alternates":"","name":"speaker","shortname":":speaker:","category":"symbols","emoji_order":"995","aliases":[],"aliases_ascii":[],"keywords":["alarm","symbol"]},"sound":{"unicode":"1f509","unicode_alternates":"","name":"speaker with one sound wave","shortname":":sound:","category":"symbols","emoji_order":"996","aliases":[],"aliases_ascii":[],"keywords":["alarm","symbol"]},"loud_sound":{"unicode":"1f50a","unicode_alternates":"","name":"speaker with three sound waves","shortname":":loud_sound:","category":"symbols","emoji_order":"997","aliases":[],"aliases_ascii":[],"keywords":["alarm","symbol"]},"mute":{"unicode":"1f507","unicode_alternates":"","name":"speaker with cancellation stroke","shortname":":mute:","category":"symbols","emoji_order":"998","aliases":[],"aliases_ascii":[],"keywords":["alarm","symbol"]},"mega":{"unicode":"1f4e3","unicode_alternates":"","name":"cheering megaphone","shortname":":mega:","category":"symbols","emoji_order":"999","aliases":[],"aliases_ascii":[],"keywords":["object","sport"]},"loudspeaker":{"unicode":"1f4e2","unicode_alternates":"","name":"public address loudspeaker","shortname":":loudspeaker:","category":"symbols","emoji_order":"1000","aliases":[],"aliases_ascii":[],"keywords":["object","alarm","symbol"]},"bell":{"unicode":"1f514","unicode_alternates":"","name":"bell","shortname":":bell:","category":"symbols","emoji_order":"1001","aliases":[],"aliases_ascii":[],"keywords":["object","alarm","symbol"]},"no_bell":{"unicode":"1f515","unicode_alternates":"","name":"bell with cancellation stroke","shortname":":no_bell:","category":"symbols","emoji_order":"1002","aliases":[],"aliases_ascii":[],"keywords":["alarm","symbol"]},"black_joker":{"unicode":"1f0cf","unicode_alternates":"","name":"playing card black joker","shortname":":black_joker:","category":"symbols","emoji_order":"1003","aliases":[],"aliases_ascii":[],"keywords":["object","symbol","game"]},"mahjong":{"unicode":"1f004","unicode_alternates":"1f004-fe0f","name":"mahjong tile red dragon","shortname":":mahjong:","category":"symbols","emoji_order":"1004","aliases":[],"aliases_ascii":[],"keywords":["object","symbol","game"]},"spades":{"unicode":"2660","unicode_alternates":"2660-fe0f","name":"black spade suit","shortname":":spades:","category":"symbols","emoji_order":"1005","aliases":[],"aliases_ascii":[],"keywords":["symbol","game"]},"clubs":{"unicode":"2663","unicode_alternates":"2663-fe0f","name":"black club suit","shortname":":clubs:","category":"symbols","emoji_order":"1006","aliases":[],"aliases_ascii":[],"keywords":["symbol","game"]},"hearts":{"unicode":"2665","unicode_alternates":"2665-fe0f","name":"black heart suit","shortname":":hearts:","category":"symbols","emoji_order":"1007","aliases":[],"aliases_ascii":[],"keywords":["love","symbol","game"]},"diamonds":{"unicode":"2666","unicode_alternates":"2666-fe0f","name":"black diamond suit","shortname":":diamonds:","category":"symbols","emoji_order":"1008","aliases":[],"aliases_ascii":[],"keywords":["shapes","symbol","game"]},"flower_playing_cards":{"unicode":"1f3b4","unicode_alternates":"","name":"flower playing cards","shortname":":flower_playing_cards:","category":"symbols","emoji_order":"1009","aliases":[],"aliases_ascii":[],"keywords":["object","symbol"]},"thought_balloon":{"unicode":"1f4ad","unicode_alternates":"","name":"thought balloon","shortname":":thought_balloon:","category":"symbols","emoji_order":"1010","aliases":[],"aliases_ascii":[],"keywords":["symbol"]},"anger_right":{"unicode":"1f5ef","unicode_alternates":"1f5ef-fe0f","name":"right anger bubble","shortname":":anger_right:","category":"symbols","emoji_order":"1011","aliases":[":right_anger_bubble:"],"aliases_ascii":[],"keywords":["symbol"]},"speech_balloon":{"unicode":"1f4ac","unicode_alternates":"","name":"speech balloon","shortname":":speech_balloon:","category":"symbols","emoji_order":"1012","aliases":[],"aliases_ascii":[],"keywords":["symbol","free speech","free speech"]},"clock1":{"unicode":"1f550","unicode_alternates":"","name":"clock face one oclock","shortname":":clock1:","category":"symbols","emoji_order":"1013","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"clock2":{"unicode":"1f551","unicode_alternates":"","name":"clock face two oclock","shortname":":clock2:","category":"symbols","emoji_order":"1014","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"clock3":{"unicode":"1f552","unicode_alternates":"","name":"clock face three oclock","shortname":":clock3:","category":"symbols","emoji_order":"1015","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"clock4":{"unicode":"1f553","unicode_alternates":"","name":"clock face four oclock","shortname":":clock4:","category":"symbols","emoji_order":"1016","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"clock5":{"unicode":"1f554","unicode_alternates":"","name":"clock face five oclock","shortname":":clock5:","category":"symbols","emoji_order":"1017","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"clock6":{"unicode":"1f555","unicode_alternates":"","name":"clock face six oclock","shortname":":clock6:","category":"symbols","emoji_order":"1018","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"clock7":{"unicode":"1f556","unicode_alternates":"","name":"clock face seven oclock","shortname":":clock7:","category":"symbols","emoji_order":"1019","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"clock8":{"unicode":"1f557","unicode_alternates":"","name":"clock face eight oclock","shortname":":clock8:","category":"symbols","emoji_order":"1020","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"clock9":{"unicode":"1f558","unicode_alternates":"","name":"clock face nine oclock","shortname":":clock9:","category":"symbols","emoji_order":"1021","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"clock10":{"unicode":"1f559","unicode_alternates":"","name":"clock face ten oclock","shortname":":clock10:","category":"symbols","emoji_order":"1022","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"clock11":{"unicode":"1f55a","unicode_alternates":"","name":"clock face eleven oclock","shortname":":clock11:","category":"symbols","emoji_order":"1023","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"clock12":{"unicode":"1f55b","unicode_alternates":"","name":"clock face twelve oclock","shortname":":clock12:","category":"symbols","emoji_order":"1024","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"clock130":{"unicode":"1f55c","unicode_alternates":"","name":"clock face one-thirty","shortname":":clock130:","category":"symbols","emoji_order":"1025","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"clock230":{"unicode":"1f55d","unicode_alternates":"","name":"clock face two-thirty","shortname":":clock230:","category":"symbols","emoji_order":"1026","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"clock330":{"unicode":"1f55e","unicode_alternates":"","name":"clock face three-thirty","shortname":":clock330:","category":"symbols","emoji_order":"1027","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"clock430":{"unicode":"1f55f","unicode_alternates":"","name":"clock face four-thirty","shortname":":clock430:","category":"symbols","emoji_order":"1028","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"clock530":{"unicode":"1f560","unicode_alternates":"","name":"clock face five-thirty","shortname":":clock530:","category":"symbols","emoji_order":"1029","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"clock630":{"unicode":"1f561","unicode_alternates":"","name":"clock face six-thirty","shortname":":clock630:","category":"symbols","emoji_order":"1030","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"clock730":{"unicode":"1f562","unicode_alternates":"","name":"clock face seven-thirty","shortname":":clock730:","category":"symbols","emoji_order":"1031","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"clock830":{"unicode":"1f563","unicode_alternates":"","name":"clock face eight-thirty","shortname":":clock830:","category":"symbols","emoji_order":"1032","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"clock930":{"unicode":"1f564","unicode_alternates":"","name":"clock face nine-thirty","shortname":":clock930:","category":"symbols","emoji_order":"1033","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"clock1030":{"unicode":"1f565","unicode_alternates":"","name":"clock face ten-thirty","shortname":":clock1030:","category":"symbols","emoji_order":"1034","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"clock1130":{"unicode":"1f566","unicode_alternates":"","name":"clock face eleven-thirty","shortname":":clock1130:","category":"symbols","emoji_order":"1035","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"clock1230":{"unicode":"1f567","unicode_alternates":"","name":"clock face twelve-thirty","shortname":":clock1230:","category":"symbols","emoji_order":"1036","aliases":[],"aliases_ascii":[],"keywords":["symbol","time"]},"eye_in_speech_bubble":{"unicode":"1f441-1f5e8","unicode_alternates":"1f441-200d-1f5e8","name":"eye in speech bubble","shortname":":eye_in_speech_bubble:","category":"symbols","emoji_order":"1037","aliases":[],"aliases_ascii":[],"keywords":["object","symbol","eyes","talk"]},"flag_ac":{"unicode":"1f1e6-1f1e8","unicode_alternates":"","name":"ascension","shortname":":flag_ac:","category":"flags","emoji_order":"1038","aliases":[":ac:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_af":{"unicode":"1f1e6-1f1eb","unicode_alternates":"","name":"afghanistan","shortname":":flag_af:","category":"flags","emoji_order":"1039","aliases":[":af:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_al":{"unicode":"1f1e6-1f1f1","unicode_alternates":"","name":"albania","shortname":":flag_al:","category":"flags","emoji_order":"1040","aliases":[":al:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_dz":{"unicode":"1f1e9-1f1ff","unicode_alternates":"","name":"algeria","shortname":":flag_dz:","category":"flags","emoji_order":"1041","aliases":[":dz:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ad":{"unicode":"1f1e6-1f1e9","unicode_alternates":"","name":"andorra","shortname":":flag_ad:","category":"flags","emoji_order":"1042","aliases":[":ad:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ao":{"unicode":"1f1e6-1f1f4","unicode_alternates":"","name":"angola","shortname":":flag_ao:","category":"flags","emoji_order":"1043","aliases":[":ao:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ai":{"unicode":"1f1e6-1f1ee","unicode_alternates":"","name":"anguilla","shortname":":flag_ai:","category":"flags","emoji_order":"1044","aliases":[":ai:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ag":{"unicode":"1f1e6-1f1ec","unicode_alternates":"","name":"antigua and barbuda","shortname":":flag_ag:","category":"flags","emoji_order":"1045","aliases":[":ag:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ar":{"unicode":"1f1e6-1f1f7","unicode_alternates":"","name":"argentina","shortname":":flag_ar:","category":"flags","emoji_order":"1046","aliases":[":ar:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_am":{"unicode":"1f1e6-1f1f2","unicode_alternates":"","name":"armenia","shortname":":flag_am:","category":"flags","emoji_order":"1047","aliases":[":am:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_aw":{"unicode":"1f1e6-1f1fc","unicode_alternates":"","name":"aruba","shortname":":flag_aw:","category":"flags","emoji_order":"1048","aliases":[":aw:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_au":{"unicode":"1f1e6-1f1fa","unicode_alternates":"","name":"australia","shortname":":flag_au:","category":"flags","emoji_order":"1049","aliases":[":au:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_at":{"unicode":"1f1e6-1f1f9","unicode_alternates":"","name":"austria","shortname":":flag_at:","category":"flags","emoji_order":"1050","aliases":[":at:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_az":{"unicode":"1f1e6-1f1ff","unicode_alternates":"","name":"azerbaijan","shortname":":flag_az:","category":"flags","emoji_order":"1051","aliases":[":az:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_bs":{"unicode":"1f1e7-1f1f8","unicode_alternates":"","name":"the bahamas","shortname":":flag_bs:","category":"flags","emoji_order":"1052","aliases":[":bs:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_bh":{"unicode":"1f1e7-1f1ed","unicode_alternates":"","name":"bahrain","shortname":":flag_bh:","category":"flags","emoji_order":"1053","aliases":[":bh:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_bd":{"unicode":"1f1e7-1f1e9","unicode_alternates":"","name":"bangladesh","shortname":":flag_bd:","category":"flags","emoji_order":"1054","aliases":[":bd:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_bb":{"unicode":"1f1e7-1f1e7","unicode_alternates":"","name":"barbados","shortname":":flag_bb:","category":"flags","emoji_order":"1055","aliases":[":bb:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_by":{"unicode":"1f1e7-1f1fe","unicode_alternates":"","name":"belarus","shortname":":flag_by:","category":"flags","emoji_order":"1056","aliases":[":by:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_be":{"unicode":"1f1e7-1f1ea","unicode_alternates":"","name":"belgium","shortname":":flag_be:","category":"flags","emoji_order":"1057","aliases":[":be:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_bz":{"unicode":"1f1e7-1f1ff","unicode_alternates":"","name":"belize","shortname":":flag_bz:","category":"flags","emoji_order":"1058","aliases":[":bz:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_bj":{"unicode":"1f1e7-1f1ef","unicode_alternates":"","name":"benin","shortname":":flag_bj:","category":"flags","emoji_order":"1059","aliases":[":bj:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_bm":{"unicode":"1f1e7-1f1f2","unicode_alternates":"","name":"bermuda","shortname":":flag_bm:","category":"flags","emoji_order":"1060","aliases":[":bm:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_bt":{"unicode":"1f1e7-1f1f9","unicode_alternates":"","name":"bhutan","shortname":":flag_bt:","category":"flags","emoji_order":"1061","aliases":[":bt:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_bo":{"unicode":"1f1e7-1f1f4","unicode_alternates":"","name":"bolivia","shortname":":flag_bo:","category":"flags","emoji_order":"1062","aliases":[":bo:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ba":{"unicode":"1f1e7-1f1e6","unicode_alternates":"","name":"bosnia and herzegovina","shortname":":flag_ba:","category":"flags","emoji_order":"1063","aliases":[":ba:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_bw":{"unicode":"1f1e7-1f1fc","unicode_alternates":"","name":"botswana","shortname":":flag_bw:","category":"flags","emoji_order":"1064","aliases":[":bw:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_br":{"unicode":"1f1e7-1f1f7","unicode_alternates":"","name":"brazil","shortname":":flag_br:","category":"flags","emoji_order":"1065","aliases":[":br:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_bn":{"unicode":"1f1e7-1f1f3","unicode_alternates":"","name":"brunei","shortname":":flag_bn:","category":"flags","emoji_order":"1066","aliases":[":bn:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_bg":{"unicode":"1f1e7-1f1ec","unicode_alternates":"","name":"bulgaria","shortname":":flag_bg:","category":"flags","emoji_order":"1067","aliases":[":bg:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_bf":{"unicode":"1f1e7-1f1eb","unicode_alternates":"","name":"burkina faso","shortname":":flag_bf:","category":"flags","emoji_order":"1068","aliases":[":bf:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_bi":{"unicode":"1f1e7-1f1ee","unicode_alternates":"","name":"burundi","shortname":":flag_bi:","category":"flags","emoji_order":"1069","aliases":[":bi:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_cv":{"unicode":"1f1e8-1f1fb","unicode_alternates":"","name":"cape verde","shortname":":flag_cv:","category":"flags","emoji_order":"1070","aliases":[":cv:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_kh":{"unicode":"1f1f0-1f1ed","unicode_alternates":"","name":"cambodia","shortname":":flag_kh:","category":"flags","emoji_order":"1071","aliases":[":kh:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_cm":{"unicode":"1f1e8-1f1f2","unicode_alternates":"","name":"cameroon","shortname":":flag_cm:","category":"flags","emoji_order":"1072","aliases":[":cm:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ca":{"unicode":"1f1e8-1f1e6","unicode_alternates":"","name":"canada","shortname":":flag_ca:","category":"flags","emoji_order":"1073","aliases":[":ca:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ky":{"unicode":"1f1f0-1f1fe","unicode_alternates":"","name":"cayman islands","shortname":":flag_ky:","category":"flags","emoji_order":"1074","aliases":[":ky:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_cf":{"unicode":"1f1e8-1f1eb","unicode_alternates":"","name":"central african republic","shortname":":flag_cf:","category":"flags","emoji_order":"1075","aliases":[":cf:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_td":{"unicode":"1f1f9-1f1e9","unicode_alternates":"","name":"chad","shortname":":flag_td:","category":"flags","emoji_order":"1076","aliases":[":td:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_cl":{"unicode":"1f1e8-1f1f1","unicode_alternates":"","name":"chile","shortname":":flag_cl:","category":"flags","emoji_order":"1077","aliases":[":chile:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_cn":{"unicode":"1f1e8-1f1f3","unicode_alternates":"","name":"china","shortname":":flag_cn:","category":"flags","emoji_order":"1078","aliases":[":cn:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_co":{"unicode":"1f1e8-1f1f4","unicode_alternates":"","name":"colombia","shortname":":flag_co:","category":"flags","emoji_order":"1079","aliases":[":co:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_km":{"unicode":"1f1f0-1f1f2","unicode_alternates":"","name":"the comoros","shortname":":flag_km:","category":"flags","emoji_order":"1080","aliases":[":km:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_cg":{"unicode":"1f1e8-1f1ec","unicode_alternates":"","name":"the republic of the congo","shortname":":flag_cg:","category":"flags","emoji_order":"1081","aliases":[":cg:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_cd":{"unicode":"1f1e8-1f1e9","unicode_alternates":"","name":"the democratic republic of the congo","shortname":":flag_cd:","category":"flags","emoji_order":"1082","aliases":[":congo:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_cr":{"unicode":"1f1e8-1f1f7","unicode_alternates":"","name":"costa rica","shortname":":flag_cr:","category":"flags","emoji_order":"1083","aliases":[":cr:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_hr":{"unicode":"1f1ed-1f1f7","unicode_alternates":"","name":"croatia","shortname":":flag_hr:","category":"flags","emoji_order":"1084","aliases":[":hr:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_cu":{"unicode":"1f1e8-1f1fa","unicode_alternates":"","name":"cuba","shortname":":flag_cu:","category":"flags","emoji_order":"1085","aliases":[":cu:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_cy":{"unicode":"1f1e8-1f1fe","unicode_alternates":"","name":"cyprus","shortname":":flag_cy:","category":"flags","emoji_order":"1086","aliases":[":cy:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_cz":{"unicode":"1f1e8-1f1ff","unicode_alternates":"","name":"the czech republic","shortname":":flag_cz:","category":"flags","emoji_order":"1087","aliases":[":cz:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_dk":{"unicode":"1f1e9-1f1f0","unicode_alternates":"","name":"denmark","shortname":":flag_dk:","category":"flags","emoji_order":"1088","aliases":[":dk:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_dj":{"unicode":"1f1e9-1f1ef","unicode_alternates":"","name":"djibouti","shortname":":flag_dj:","category":"flags","emoji_order":"1089","aliases":[":dj:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_dm":{"unicode":"1f1e9-1f1f2","unicode_alternates":"","name":"dominica","shortname":":flag_dm:","category":"flags","emoji_order":"1090","aliases":[":dm:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_do":{"unicode":"1f1e9-1f1f4","unicode_alternates":"","name":"the dominican republic","shortname":":flag_do:","category":"flags","emoji_order":"1091","aliases":[":do:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ec":{"unicode":"1f1ea-1f1e8","unicode_alternates":"","name":"ecuador","shortname":":flag_ec:","category":"flags","emoji_order":"1092","aliases":[":ec:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_eg":{"unicode":"1f1ea-1f1ec","unicode_alternates":"","name":"egypt","shortname":":flag_eg:","category":"flags","emoji_order":"1093","aliases":[":eg:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_sv":{"unicode":"1f1f8-1f1fb","unicode_alternates":"","name":"el salvador","shortname":":flag_sv:","category":"flags","emoji_order":"1094","aliases":[":sv:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_gq":{"unicode":"1f1ec-1f1f6","unicode_alternates":"","name":"equatorial guinea","shortname":":flag_gq:","category":"flags","emoji_order":"1095","aliases":[":gq:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_er":{"unicode":"1f1ea-1f1f7","unicode_alternates":"","name":"eritrea","shortname":":flag_er:","category":"flags","emoji_order":"1096","aliases":[":er:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ee":{"unicode":"1f1ea-1f1ea","unicode_alternates":"","name":"estonia","shortname":":flag_ee:","category":"flags","emoji_order":"1097","aliases":[":ee:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_et":{"unicode":"1f1ea-1f1f9","unicode_alternates":"","name":"ethiopia","shortname":":flag_et:","category":"flags","emoji_order":"1098","aliases":[":et:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_fk":{"unicode":"1f1eb-1f1f0","unicode_alternates":"","name":"falkland islands","shortname":":flag_fk:","category":"flags","emoji_order":"1099","aliases":[":fk:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_fo":{"unicode":"1f1eb-1f1f4","unicode_alternates":"","name":"faroe islands","shortname":":flag_fo:","category":"flags","emoji_order":"1100","aliases":[":fo:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_fj":{"unicode":"1f1eb-1f1ef","unicode_alternates":"","name":"fiji","shortname":":flag_fj:","category":"flags","emoji_order":"1101","aliases":[":fj:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_fi":{"unicode":"1f1eb-1f1ee","unicode_alternates":"","name":"finland","shortname":":flag_fi:","category":"flags","emoji_order":"1102","aliases":[":fi:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_fr":{"unicode":"1f1eb-1f1f7","unicode_alternates":"","name":"france","shortname":":flag_fr:","category":"flags","emoji_order":"1103","aliases":[":fr:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_pf":{"unicode":"1f1f5-1f1eb","unicode_alternates":"","name":"french polynesia","shortname":":flag_pf:","category":"flags","emoji_order":"1104","aliases":[":pf:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ga":{"unicode":"1f1ec-1f1e6","unicode_alternates":"","name":"gabon","shortname":":flag_ga:","category":"flags","emoji_order":"1105","aliases":[":ga:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_gm":{"unicode":"1f1ec-1f1f2","unicode_alternates":"","name":"the gambia","shortname":":flag_gm:","category":"flags","emoji_order":"1106","aliases":[":gm:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ge":{"unicode":"1f1ec-1f1ea","unicode_alternates":"","name":"georgia","shortname":":flag_ge:","category":"flags","emoji_order":"1107","aliases":[":ge:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_de":{"unicode":"1f1e9-1f1ea","unicode_alternates":"","name":"germany","shortname":":flag_de:","category":"flags","emoji_order":"1108","aliases":[":de:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_gh":{"unicode":"1f1ec-1f1ed","unicode_alternates":"","name":"ghana","shortname":":flag_gh:","category":"flags","emoji_order":"1109","aliases":[":gh:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_gi":{"unicode":"1f1ec-1f1ee","unicode_alternates":"","name":"gibraltar","shortname":":flag_gi:","category":"flags","emoji_order":"1110","aliases":[":gi:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_gr":{"unicode":"1f1ec-1f1f7","unicode_alternates":"","name":"greece","shortname":":flag_gr:","category":"flags","emoji_order":"1111","aliases":[":gr:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_gl":{"unicode":"1f1ec-1f1f1","unicode_alternates":"","name":"greenland","shortname":":flag_gl:","category":"flags","emoji_order":"1112","aliases":[":gl:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_gd":{"unicode":"1f1ec-1f1e9","unicode_alternates":"","name":"grenada","shortname":":flag_gd:","category":"flags","emoji_order":"1113","aliases":[":gd:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_gu":{"unicode":"1f1ec-1f1fa","unicode_alternates":"","name":"guam","shortname":":flag_gu:","category":"flags","emoji_order":"1114","aliases":[":gu:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_gt":{"unicode":"1f1ec-1f1f9","unicode_alternates":"","name":"guatemala","shortname":":flag_gt:","category":"flags","emoji_order":"1115","aliases":[":gt:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_gn":{"unicode":"1f1ec-1f1f3","unicode_alternates":"","name":"guinea","shortname":":flag_gn:","category":"flags","emoji_order":"1116","aliases":[":gn:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_gw":{"unicode":"1f1ec-1f1fc","unicode_alternates":"","name":"guinea-bissau","shortname":":flag_gw:","category":"flags","emoji_order":"1117","aliases":[":gw:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_gy":{"unicode":"1f1ec-1f1fe","unicode_alternates":"","name":"guyana","shortname":":flag_gy:","category":"flags","emoji_order":"1118","aliases":[":gy:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ht":{"unicode":"1f1ed-1f1f9","unicode_alternates":"","name":"haiti","shortname":":flag_ht:","category":"flags","emoji_order":"1119","aliases":[":ht:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_hn":{"unicode":"1f1ed-1f1f3","unicode_alternates":"","name":"honduras","shortname":":flag_hn:","category":"flags","emoji_order":"1120","aliases":[":hn:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_hk":{"unicode":"1f1ed-1f1f0","unicode_alternates":"","name":"hong kong","shortname":":flag_hk:","category":"flags","emoji_order":"1121","aliases":[":hk:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_hu":{"unicode":"1f1ed-1f1fa","unicode_alternates":"","name":"hungary","shortname":":flag_hu:","category":"flags","emoji_order":"1122","aliases":[":hu:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_is":{"unicode":"1f1ee-1f1f8","unicode_alternates":"","name":"iceland","shortname":":flag_is:","category":"flags","emoji_order":"1123","aliases":[":is:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_in":{"unicode":"1f1ee-1f1f3","unicode_alternates":"","name":"india","shortname":":flag_in:","category":"flags","emoji_order":"1124","aliases":[":in:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_id":{"unicode":"1f1ee-1f1e9","unicode_alternates":"","name":"indonesia","shortname":":flag_id:","category":"flags","emoji_order":"1125","aliases":[":indonesia:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ir":{"unicode":"1f1ee-1f1f7","unicode_alternates":"","name":"iran","shortname":":flag_ir:","category":"flags","emoji_order":"1126","aliases":[":ir:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_iq":{"unicode":"1f1ee-1f1f6","unicode_alternates":"","name":"iraq","shortname":":flag_iq:","category":"flags","emoji_order":"1127","aliases":[":iq:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ie":{"unicode":"1f1ee-1f1ea","unicode_alternates":"","name":"ireland","shortname":":flag_ie:","category":"flags","emoji_order":"1128","aliases":[":ie:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_il":{"unicode":"1f1ee-1f1f1","unicode_alternates":"","name":"israel","shortname":":flag_il:","category":"flags","emoji_order":"1129","aliases":[":il:"],"aliases_ascii":[],"keywords":["jew","country","flag","flag"]},"flag_it":{"unicode":"1f1ee-1f1f9","unicode_alternates":"","name":"italy","shortname":":flag_it:","category":"flags","emoji_order":"1130","aliases":[":it:"],"aliases_ascii":[],"keywords":["italian","country","flag","flag"]},"flag_ci":{"unicode":"1f1e8-1f1ee","unicode_alternates":"","name":"c\u00f4te d\u2019ivoire","shortname":":flag_ci:","category":"flags","emoji_order":"1131","aliases":[":ci:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_jm":{"unicode":"1f1ef-1f1f2","unicode_alternates":"","name":"jamaica","shortname":":flag_jm:","category":"flags","emoji_order":"1132","aliases":[":jm:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_jp":{"unicode":"1f1ef-1f1f5","unicode_alternates":"","name":"japan","shortname":":flag_jp:","category":"flags","emoji_order":"1133","aliases":[":jp:"],"aliases_ascii":[],"keywords":["japan","country","flag","flag"]},"flag_je":{"unicode":"1f1ef-1f1ea","unicode_alternates":"","name":"jersey","shortname":":flag_je:","category":"flags","emoji_order":"1134","aliases":[":je:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_jo":{"unicode":"1f1ef-1f1f4","unicode_alternates":"","name":"jordan","shortname":":flag_jo:","category":"flags","emoji_order":"1135","aliases":[":jo:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_kz":{"unicode":"1f1f0-1f1ff","unicode_alternates":"","name":"kazakhstan","shortname":":flag_kz:","category":"flags","emoji_order":"1136","aliases":[":kz:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ke":{"unicode":"1f1f0-1f1ea","unicode_alternates":"","name":"kenya","shortname":":flag_ke:","category":"flags","emoji_order":"1137","aliases":[":ke:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ki":{"unicode":"1f1f0-1f1ee","unicode_alternates":"","name":"kiribati","shortname":":flag_ki:","category":"flags","emoji_order":"1138","aliases":[":ki:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_xk":{"unicode":"1f1fd-1f1f0","unicode_alternates":"","name":"kosovo","shortname":":flag_xk:","category":"flags","emoji_order":"1139","aliases":[":xk:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_kw":{"unicode":"1f1f0-1f1fc","unicode_alternates":"","name":"kuwait","shortname":":flag_kw:","category":"flags","emoji_order":"1140","aliases":[":kw:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_kg":{"unicode":"1f1f0-1f1ec","unicode_alternates":"","name":"kyrgyzstan","shortname":":flag_kg:","category":"flags","emoji_order":"1141","aliases":[":kg:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_la":{"unicode":"1f1f1-1f1e6","unicode_alternates":"","name":"laos","shortname":":flag_la:","category":"flags","emoji_order":"1142","aliases":[":la:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_lv":{"unicode":"1f1f1-1f1fb","unicode_alternates":"","name":"latvia","shortname":":flag_lv:","category":"flags","emoji_order":"1143","aliases":[":lv:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_lb":{"unicode":"1f1f1-1f1e7","unicode_alternates":"","name":"lebanon","shortname":":flag_lb:","category":"flags","emoji_order":"1144","aliases":[":lb:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ls":{"unicode":"1f1f1-1f1f8","unicode_alternates":"","name":"lesotho","shortname":":flag_ls:","category":"flags","emoji_order":"1145","aliases":[":ls:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_lr":{"unicode":"1f1f1-1f1f7","unicode_alternates":"","name":"liberia","shortname":":flag_lr:","category":"flags","emoji_order":"1146","aliases":[":lr:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ly":{"unicode":"1f1f1-1f1fe","unicode_alternates":"","name":"libya","shortname":":flag_ly:","category":"flags","emoji_order":"1147","aliases":[":ly:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_li":{"unicode":"1f1f1-1f1ee","unicode_alternates":"","name":"liechtenstein","shortname":":flag_li:","category":"flags","emoji_order":"1148","aliases":[":li:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_lt":{"unicode":"1f1f1-1f1f9","unicode_alternates":"","name":"lithuania","shortname":":flag_lt:","category":"flags","emoji_order":"1149","aliases":[":lt:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_lu":{"unicode":"1f1f1-1f1fa","unicode_alternates":"","name":"luxembourg","shortname":":flag_lu:","category":"flags","emoji_order":"1150","aliases":[":lu:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_mo":{"unicode":"1f1f2-1f1f4","unicode_alternates":"","name":"macau","shortname":":flag_mo:","category":"flags","emoji_order":"1151","aliases":[":mo:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_mk":{"unicode":"1f1f2-1f1f0","unicode_alternates":"","name":"macedonia","shortname":":flag_mk:","category":"flags","emoji_order":"1152","aliases":[":mk:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_mg":{"unicode":"1f1f2-1f1ec","unicode_alternates":"","name":"madagascar","shortname":":flag_mg:","category":"flags","emoji_order":"1153","aliases":[":mg:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_mw":{"unicode":"1f1f2-1f1fc","unicode_alternates":"","name":"malawi","shortname":":flag_mw:","category":"flags","emoji_order":"1154","aliases":[":mw:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_my":{"unicode":"1f1f2-1f1fe","unicode_alternates":"","name":"malaysia","shortname":":flag_my:","category":"flags","emoji_order":"1155","aliases":[":my:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_mv":{"unicode":"1f1f2-1f1fb","unicode_alternates":"","name":"maldives","shortname":":flag_mv:","category":"flags","emoji_order":"1156","aliases":[":mv:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ml":{"unicode":"1f1f2-1f1f1","unicode_alternates":"","name":"mali","shortname":":flag_ml:","category":"flags","emoji_order":"1157","aliases":[":ml:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_mt":{"unicode":"1f1f2-1f1f9","unicode_alternates":"","name":"malta","shortname":":flag_mt:","category":"flags","emoji_order":"1158","aliases":[":mt:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_mh":{"unicode":"1f1f2-1f1ed","unicode_alternates":"","name":"the marshall islands","shortname":":flag_mh:","category":"flags","emoji_order":"1159","aliases":[":mh:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_mr":{"unicode":"1f1f2-1f1f7","unicode_alternates":"","name":"mauritania","shortname":":flag_mr:","category":"flags","emoji_order":"1160","aliases":[":mr:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_mu":{"unicode":"1f1f2-1f1fa","unicode_alternates":"","name":"mauritius","shortname":":flag_mu:","category":"flags","emoji_order":"1161","aliases":[":mu:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_mx":{"unicode":"1f1f2-1f1fd","unicode_alternates":"","name":"mexico","shortname":":flag_mx:","category":"flags","emoji_order":"1162","aliases":[":mx:"],"aliases_ascii":[],"keywords":["country","mexican","flag","flag"]},"flag_fm":{"unicode":"1f1eb-1f1f2","unicode_alternates":"","name":"micronesia","shortname":":flag_fm:","category":"flags","emoji_order":"1163","aliases":[":fm:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_md":{"unicode":"1f1f2-1f1e9","unicode_alternates":"","name":"moldova","shortname":":flag_md:","category":"flags","emoji_order":"1164","aliases":[":md:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_mc":{"unicode":"1f1f2-1f1e8","unicode_alternates":"","name":"monaco","shortname":":flag_mc:","category":"flags","emoji_order":"1165","aliases":[":mc:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_mn":{"unicode":"1f1f2-1f1f3","unicode_alternates":"","name":"mongolia","shortname":":flag_mn:","category":"flags","emoji_order":"1166","aliases":[":mn:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_me":{"unicode":"1f1f2-1f1ea","unicode_alternates":"","name":"montenegro","shortname":":flag_me:","category":"flags","emoji_order":"1167","aliases":[":me:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ms":{"unicode":"1f1f2-1f1f8","unicode_alternates":"","name":"montserrat","shortname":":flag_ms:","category":"flags","emoji_order":"1168","aliases":[":ms:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ma":{"unicode":"1f1f2-1f1e6","unicode_alternates":"","name":"morocco","shortname":":flag_ma:","category":"flags","emoji_order":"1169","aliases":[":ma:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_mz":{"unicode":"1f1f2-1f1ff","unicode_alternates":"","name":"mozambique","shortname":":flag_mz:","category":"flags","emoji_order":"1170","aliases":[":mz:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_mm":{"unicode":"1f1f2-1f1f2","unicode_alternates":"","name":"myanmar","shortname":":flag_mm:","category":"flags","emoji_order":"1171","aliases":[":mm:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_na":{"unicode":"1f1f3-1f1e6","unicode_alternates":"","name":"namibia","shortname":":flag_na:","category":"flags","emoji_order":"1172","aliases":[":na:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_nr":{"unicode":"1f1f3-1f1f7","unicode_alternates":"","name":"nauru","shortname":":flag_nr:","category":"flags","emoji_order":"1173","aliases":[":nr:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_np":{"unicode":"1f1f3-1f1f5","unicode_alternates":"","name":"nepal","shortname":":flag_np:","category":"flags","emoji_order":"1174","aliases":[":np:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_nl":{"unicode":"1f1f3-1f1f1","unicode_alternates":"","name":"the netherlands","shortname":":flag_nl:","category":"flags","emoji_order":"1175","aliases":[":nl:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_nc":{"unicode":"1f1f3-1f1e8","unicode_alternates":"","name":"new caledonia","shortname":":flag_nc:","category":"flags","emoji_order":"1176","aliases":[":nc:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_nz":{"unicode":"1f1f3-1f1ff","unicode_alternates":"","name":"new zealand","shortname":":flag_nz:","category":"flags","emoji_order":"1177","aliases":[":nz:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ni":{"unicode":"1f1f3-1f1ee","unicode_alternates":"","name":"nicaragua","shortname":":flag_ni:","category":"flags","emoji_order":"1178","aliases":[":ni:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ne":{"unicode":"1f1f3-1f1ea","unicode_alternates":"","name":"niger","shortname":":flag_ne:","category":"flags","emoji_order":"1179","aliases":[":ne:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ng":{"unicode":"1f1f3-1f1ec","unicode_alternates":"","name":"nigeria","shortname":":flag_ng:","category":"flags","emoji_order":"1180","aliases":[":nigeria:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_nu":{"unicode":"1f1f3-1f1fa","unicode_alternates":"","name":"niue","shortname":":flag_nu:","category":"flags","emoji_order":"1181","aliases":[":nu:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_kp":{"unicode":"1f1f0-1f1f5","unicode_alternates":"","name":"north korea","shortname":":flag_kp:","category":"flags","emoji_order":"1182","aliases":[":kp:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_no":{"unicode":"1f1f3-1f1f4","unicode_alternates":"","name":"norway","shortname":":flag_no:","category":"flags","emoji_order":"1183","aliases":[":no:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_om":{"unicode":"1f1f4-1f1f2","unicode_alternates":"","name":"oman","shortname":":flag_om:","category":"flags","emoji_order":"1184","aliases":[":om:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_pk":{"unicode":"1f1f5-1f1f0","unicode_alternates":"","name":"pakistan","shortname":":flag_pk:","category":"flags","emoji_order":"1185","aliases":[":pk:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_pw":{"unicode":"1f1f5-1f1fc","unicode_alternates":"","name":"palau","shortname":":flag_pw:","category":"flags","emoji_order":"1186","aliases":[":pw:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ps":{"unicode":"1f1f5-1f1f8","unicode_alternates":"","name":"palestinian authority","shortname":":flag_ps:","category":"flags","emoji_order":"1187","aliases":[":ps:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_pa":{"unicode":"1f1f5-1f1e6","unicode_alternates":"","name":"panama","shortname":":flag_pa:","category":"flags","emoji_order":"1188","aliases":[":pa:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_pg":{"unicode":"1f1f5-1f1ec","unicode_alternates":"","name":"papua new guinea","shortname":":flag_pg:","category":"flags","emoji_order":"1189","aliases":[":pg:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_py":{"unicode":"1f1f5-1f1fe","unicode_alternates":"","name":"paraguay","shortname":":flag_py:","category":"flags","emoji_order":"1190","aliases":[":py:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_pe":{"unicode":"1f1f5-1f1ea","unicode_alternates":"","name":"peru","shortname":":flag_pe:","category":"flags","emoji_order":"1191","aliases":[":pe:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ph":{"unicode":"1f1f5-1f1ed","unicode_alternates":"","name":"the philippines","shortname":":flag_ph:","category":"flags","emoji_order":"1192","aliases":[":ph:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_pl":{"unicode":"1f1f5-1f1f1","unicode_alternates":"","name":"poland","shortname":":flag_pl:","category":"flags","emoji_order":"1193","aliases":[":pl:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_pt":{"unicode":"1f1f5-1f1f9","unicode_alternates":"","name":"portugal","shortname":":flag_pt:","category":"flags","emoji_order":"1194","aliases":[":pt:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_pr":{"unicode":"1f1f5-1f1f7","unicode_alternates":"","name":"puerto rico","shortname":":flag_pr:","category":"flags","emoji_order":"1195","aliases":[":pr:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_qa":{"unicode":"1f1f6-1f1e6","unicode_alternates":"","name":"qatar","shortname":":flag_qa:","category":"flags","emoji_order":"1196","aliases":[":qa:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ro":{"unicode":"1f1f7-1f1f4","unicode_alternates":"","name":"romania","shortname":":flag_ro:","category":"flags","emoji_order":"1197","aliases":[":ro:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ru":{"unicode":"1f1f7-1f1fa","unicode_alternates":"","name":"russia","shortname":":flag_ru:","category":"flags","emoji_order":"1198","aliases":[":ru:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_rw":{"unicode":"1f1f7-1f1fc","unicode_alternates":"","name":"rwanda","shortname":":flag_rw:","category":"flags","emoji_order":"1199","aliases":[":rw:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_sh":{"unicode":"1f1f8-1f1ed","unicode_alternates":"","name":"saint helena","shortname":":flag_sh:","category":"flags","emoji_order":"1200","aliases":[":sh:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_kn":{"unicode":"1f1f0-1f1f3","unicode_alternates":"","name":"saint kitts and nevis","shortname":":flag_kn:","category":"flags","emoji_order":"1201","aliases":[":kn:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_lc":{"unicode":"1f1f1-1f1e8","unicode_alternates":"","name":"saint lucia","shortname":":flag_lc:","category":"flags","emoji_order":"1202","aliases":[":lc:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_vc":{"unicode":"1f1fb-1f1e8","unicode_alternates":"","name":"saint vincent and the grenadines","shortname":":flag_vc:","category":"flags","emoji_order":"1203","aliases":[":vc:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ws":{"unicode":"1f1fc-1f1f8","unicode_alternates":"","name":"samoa","shortname":":flag_ws:","category":"flags","emoji_order":"1204","aliases":[":ws:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_sm":{"unicode":"1f1f8-1f1f2","unicode_alternates":"","name":"san marino","shortname":":flag_sm:","category":"flags","emoji_order":"1205","aliases":[":sm:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_st":{"unicode":"1f1f8-1f1f9","unicode_alternates":"","name":"s\u00e3o tom\u00e9 and pr\u00edncipe","shortname":":flag_st:","category":"flags","emoji_order":"1206","aliases":[":st:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_sa":{"unicode":"1f1f8-1f1e6","unicode_alternates":"","name":"saudi arabia","shortname":":flag_sa:","category":"flags","emoji_order":"1207","aliases":[":saudiarabia:",":saudi:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_sn":{"unicode":"1f1f8-1f1f3","unicode_alternates":"","name":"senegal","shortname":":flag_sn:","category":"flags","emoji_order":"1208","aliases":[":sn:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_rs":{"unicode":"1f1f7-1f1f8","unicode_alternates":"","name":"serbia","shortname":":flag_rs:","category":"flags","emoji_order":"1209","aliases":[":rs:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_sc":{"unicode":"1f1f8-1f1e8","unicode_alternates":"","name":"the seychelles","shortname":":flag_sc:","category":"flags","emoji_order":"1210","aliases":[":sc:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_sl":{"unicode":"1f1f8-1f1f1","unicode_alternates":"","name":"sierra leone","shortname":":flag_sl:","category":"flags","emoji_order":"1211","aliases":[":sl:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_sg":{"unicode":"1f1f8-1f1ec","unicode_alternates":"","name":"singapore","shortname":":flag_sg:","category":"flags","emoji_order":"1212","aliases":[":sg:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_sk":{"unicode":"1f1f8-1f1f0","unicode_alternates":"","name":"slovakia","shortname":":flag_sk:","category":"flags","emoji_order":"1213","aliases":[":sk:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_si":{"unicode":"1f1f8-1f1ee","unicode_alternates":"","name":"slovenia","shortname":":flag_si:","category":"flags","emoji_order":"1214","aliases":[":si:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_sb":{"unicode":"1f1f8-1f1e7","unicode_alternates":"","name":"the solomon islands","shortname":":flag_sb:","category":"flags","emoji_order":"1215","aliases":[":sb:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_so":{"unicode":"1f1f8-1f1f4","unicode_alternates":"","name":"somalia","shortname":":flag_so:","category":"flags","emoji_order":"1216","aliases":[":so:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_za":{"unicode":"1f1ff-1f1e6","unicode_alternates":"","name":"south africa","shortname":":flag_za:","category":"flags","emoji_order":"1217","aliases":[":za:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_kr":{"unicode":"1f1f0-1f1f7","unicode_alternates":"","name":"korea","shortname":":flag_kr:","category":"flags","emoji_order":"1218","aliases":[":kr:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_es":{"unicode":"1f1ea-1f1f8","unicode_alternates":"","name":"spain","shortname":":flag_es:","category":"flags","emoji_order":"1219","aliases":[":es:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_lk":{"unicode":"1f1f1-1f1f0","unicode_alternates":"","name":"sri lanka","shortname":":flag_lk:","category":"flags","emoji_order":"1220","aliases":[":lk:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_sd":{"unicode":"1f1f8-1f1e9","unicode_alternates":"","name":"sudan","shortname":":flag_sd:","category":"flags","emoji_order":"1221","aliases":[":sd:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_sr":{"unicode":"1f1f8-1f1f7","unicode_alternates":"","name":"suriname","shortname":":flag_sr:","category":"flags","emoji_order":"1222","aliases":[":sr:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_sz":{"unicode":"1f1f8-1f1ff","unicode_alternates":"","name":"swaziland","shortname":":flag_sz:","category":"flags","emoji_order":"1223","aliases":[":sz:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_se":{"unicode":"1f1f8-1f1ea","unicode_alternates":"","name":"sweden","shortname":":flag_se:","category":"flags","emoji_order":"1224","aliases":[":se:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ch":{"unicode":"1f1e8-1f1ed","unicode_alternates":"","name":"switzerland","shortname":":flag_ch:","category":"flags","emoji_order":"1225","aliases":[":ch:"],"aliases_ascii":[],"keywords":["country","neutral","flag","flag"]},"flag_sy":{"unicode":"1f1f8-1f1fe","unicode_alternates":"","name":"syria","shortname":":flag_sy:","category":"flags","emoji_order":"1226","aliases":[":sy:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_tw":{"unicode":"1f1f9-1f1fc","unicode_alternates":"","name":"the republic of china","shortname":":flag_tw:","category":"flags","emoji_order":"1227","aliases":[":tw:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_tj":{"unicode":"1f1f9-1f1ef","unicode_alternates":"","name":"tajikistan","shortname":":flag_tj:","category":"flags","emoji_order":"1228","aliases":[":tj:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_tz":{"unicode":"1f1f9-1f1ff","unicode_alternates":"","name":"tanzania","shortname":":flag_tz:","category":"flags","emoji_order":"1229","aliases":[":tz:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_th":{"unicode":"1f1f9-1f1ed","unicode_alternates":"","name":"thailand","shortname":":flag_th:","category":"flags","emoji_order":"1230","aliases":[":th:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_tl":{"unicode":"1f1f9-1f1f1","unicode_alternates":"","name":"timor-leste","shortname":":flag_tl:","category":"flags","emoji_order":"1231","aliases":[":tl:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_tg":{"unicode":"1f1f9-1f1ec","unicode_alternates":"","name":"togo","shortname":":flag_tg:","category":"flags","emoji_order":"1232","aliases":[":tg:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_to":{"unicode":"1f1f9-1f1f4","unicode_alternates":"","name":"tonga","shortname":":flag_to:","category":"flags","emoji_order":"1233","aliases":[":to:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_tt":{"unicode":"1f1f9-1f1f9","unicode_alternates":"","name":"trinidad and tobago","shortname":":flag_tt:","category":"flags","emoji_order":"1234","aliases":[":tt:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_tn":{"unicode":"1f1f9-1f1f3","unicode_alternates":"","name":"tunisia","shortname":":flag_tn:","category":"flags","emoji_order":"1235","aliases":[":tn:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_tr":{"unicode":"1f1f9-1f1f7","unicode_alternates":"","name":"turkey","shortname":":flag_tr:","category":"flags","emoji_order":"1236","aliases":[":tr:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_tm":{"unicode":"1f1f9-1f1f2","unicode_alternates":"","name":"turkmenistan","shortname":":flag_tm:","category":"flags","emoji_order":"1237","aliases":[":turkmenistan:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_tv":{"unicode":"1f1f9-1f1fb","unicode_alternates":"","name":"tuvalu","shortname":":flag_tv:","category":"flags","emoji_order":"1238","aliases":[":tuvalu:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ug":{"unicode":"1f1fa-1f1ec","unicode_alternates":"","name":"uganda","shortname":":flag_ug:","category":"flags","emoji_order":"1239","aliases":[":ug:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ua":{"unicode":"1f1fa-1f1e6","unicode_alternates":"","name":"ukraine","shortname":":flag_ua:","category":"flags","emoji_order":"1240","aliases":[":ua:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ae":{"unicode":"1f1e6-1f1ea","unicode_alternates":"","name":"the united arab emirates","shortname":":flag_ae:","category":"flags","emoji_order":"1241","aliases":[":ae:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_gb":{"unicode":"1f1ec-1f1e7","unicode_alternates":"","name":"great britain","shortname":":flag_gb:","category":"flags","emoji_order":"1242","aliases":[":gb:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_us":{"unicode":"1f1fa-1f1f8","unicode_alternates":"","name":"united states","shortname":":flag_us:","category":"flags","emoji_order":"1243","aliases":[":us:"],"aliases_ascii":[],"keywords":["america","country","flag","flag"]},"flag_vi":{"unicode":"1f1fb-1f1ee","unicode_alternates":"","name":"u.s. virgin islands","shortname":":flag_vi:","category":"flags","emoji_order":"1244","aliases":[":vi:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_uy":{"unicode":"1f1fa-1f1fe","unicode_alternates":"","name":"uruguay","shortname":":flag_uy:","category":"flags","emoji_order":"1245","aliases":[":uy:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_uz":{"unicode":"1f1fa-1f1ff","unicode_alternates":"","name":"uzbekistan","shortname":":flag_uz:","category":"flags","emoji_order":"1246","aliases":[":uz:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_vu":{"unicode":"1f1fb-1f1fa","unicode_alternates":"","name":"vanuatu","shortname":":flag_vu:","category":"flags","emoji_order":"1247","aliases":[":vu:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_va":{"unicode":"1f1fb-1f1e6","unicode_alternates":"","name":"the vatican city","shortname":":flag_va:","category":"flags","emoji_order":"1248","aliases":[":va:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ve":{"unicode":"1f1fb-1f1ea","unicode_alternates":"","name":"venezuela","shortname":":flag_ve:","category":"flags","emoji_order":"1249","aliases":[":ve:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_vn":{"unicode":"1f1fb-1f1f3","unicode_alternates":"","name":"vietnam","shortname":":flag_vn:","category":"flags","emoji_order":"1250","aliases":[":vn:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_wf":{"unicode":"1f1fc-1f1eb","unicode_alternates":"","name":"wallis and futuna","shortname":":flag_wf:","category":"flags","emoji_order":"1251","aliases":[":wf:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_eh":{"unicode":"1f1ea-1f1ed","unicode_alternates":"","name":"western sahara","shortname":":flag_eh:","category":"flags","emoji_order":"1252","aliases":[":eh:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ye":{"unicode":"1f1fe-1f1ea","unicode_alternates":"","name":"yemen","shortname":":flag_ye:","category":"flags","emoji_order":"1253","aliases":[":ye:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_zm":{"unicode":"1f1ff-1f1f2","unicode_alternates":"","name":"zambia","shortname":":flag_zm:","category":"flags","emoji_order":"1254","aliases":[":zm:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_zw":{"unicode":"1f1ff-1f1fc","unicode_alternates":"","name":"zimbabwe","shortname":":flag_zw:","category":"flags","emoji_order":"1255","aliases":[":zw:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_re":{"unicode":"1f1f7-1f1ea","unicode_alternates":"","name":"r\u00e9union","shortname":":flag_re:","category":"flags","emoji_order":"1256","aliases":[":re:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ax":{"unicode":"1f1e6-1f1fd","unicode_alternates":"","name":"\u00e5land islands","shortname":":flag_ax:","category":"flags","emoji_order":"1257","aliases":[":ax:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ta":{"unicode":"1f1f9-1f1e6","unicode_alternates":"","name":"tristan da cunha","shortname":":flag_ta:","category":"flags","emoji_order":"1258","aliases":[":ta:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_io":{"unicode":"1f1ee-1f1f4","unicode_alternates":"","name":"british indian ocean territory","shortname":":flag_io:","category":"flags","emoji_order":"1259","aliases":[":io:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_bq":{"unicode":"1f1e7-1f1f6","unicode_alternates":"","name":"caribbean netherlands","shortname":":flag_bq:","category":"flags","emoji_order":"1260","aliases":[":bq:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_cx":{"unicode":"1f1e8-1f1fd","unicode_alternates":"","name":"christmas island","shortname":":flag_cx:","category":"flags","emoji_order":"1261","aliases":[":cx:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_cc":{"unicode":"1f1e8-1f1e8","unicode_alternates":"","name":"cocos (keeling) islands","shortname":":flag_cc:","category":"flags","emoji_order":"1262","aliases":[":cc:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_gg":{"unicode":"1f1ec-1f1ec","unicode_alternates":"","name":"guernsey","shortname":":flag_gg:","category":"flags","emoji_order":"1263","aliases":[":gg:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_im":{"unicode":"1f1ee-1f1f2","unicode_alternates":"","name":"isle of man","shortname":":flag_im:","category":"flags","emoji_order":"1264","aliases":[":im:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_yt":{"unicode":"1f1fe-1f1f9","unicode_alternates":"","name":"mayotte","shortname":":flag_yt:","category":"flags","emoji_order":"1265","aliases":[":yt:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_nf":{"unicode":"1f1f3-1f1eb","unicode_alternates":"","name":"norfolk island","shortname":":flag_nf:","category":"flags","emoji_order":"1266","aliases":[":nf:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_pn":{"unicode":"1f1f5-1f1f3","unicode_alternates":"","name":"pitcairn","shortname":":flag_pn:","category":"flags","emoji_order":"1267","aliases":[":pn:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_bl":{"unicode":"1f1e7-1f1f1","unicode_alternates":"","name":"saint barth\u00e9lemy","shortname":":flag_bl:","category":"flags","emoji_order":"1268","aliases":[":bl:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_pm":{"unicode":"1f1f5-1f1f2","unicode_alternates":"","name":"saint pierre and miquelon","shortname":":flag_pm:","category":"flags","emoji_order":"1269","aliases":[":pm:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_gs":{"unicode":"1f1ec-1f1f8","unicode_alternates":"","name":"south georgia","shortname":":flag_gs:","category":"flags","emoji_order":"1270","aliases":[":gs:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_tk":{"unicode":"1f1f9-1f1f0","unicode_alternates":"","name":"tokelau","shortname":":flag_tk:","category":"flags","emoji_order":"1271","aliases":[":tk:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_bv":{"unicode":"1f1e7-1f1fb","unicode_alternates":"","name":"bouvet island","shortname":":flag_bv:","category":"flags","emoji_order":"1272","aliases":[":bv:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_hm":{"unicode":"1f1ed-1f1f2","unicode_alternates":"","name":"heard island and mcdonald islands","shortname":":flag_hm:","category":"flags","emoji_order":"1273","aliases":[":hm:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_sj":{"unicode":"1f1f8-1f1ef","unicode_alternates":"","name":"svalbard and jan mayen","shortname":":flag_sj:","category":"flags","emoji_order":"1274","aliases":[":sj:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_um":{"unicode":"1f1fa-1f1f2","unicode_alternates":"","name":"united states minor outlying islands","shortname":":flag_um:","category":"flags","emoji_order":"1275","aliases":[":um:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ic":{"unicode":"1f1ee-1f1e8","unicode_alternates":"","name":"canary islands","shortname":":flag_ic:","category":"flags","emoji_order":"1276","aliases":[":ic:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ea":{"unicode":"1f1ea-1f1e6","unicode_alternates":"","name":"ceuta, melilla","shortname":":flag_ea:","category":"flags","emoji_order":"1277","aliases":[":ea:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_cp":{"unicode":"1f1e8-1f1f5","unicode_alternates":"","name":"clipperton island","shortname":":flag_cp:","category":"flags","emoji_order":"1278","aliases":[":cp:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_dg":{"unicode":"1f1e9-1f1ec","unicode_alternates":"","name":"diego garcia","shortname":":flag_dg:","category":"flags","emoji_order":"1279","aliases":[":dg:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_as":{"unicode":"1f1e6-1f1f8","unicode_alternates":"","name":"american samoa","shortname":":flag_as:","category":"flags","emoji_order":"1280","aliases":[":as:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_aq":{"unicode":"1f1e6-1f1f6","unicode_alternates":"","name":"antarctica","shortname":":flag_aq:","category":"flags","emoji_order":"1281","aliases":[":aq:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_vg":{"unicode":"1f1fb-1f1ec","unicode_alternates":"","name":"british virgin islands","shortname":":flag_vg:","category":"flags","emoji_order":"1282","aliases":[":vg:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ck":{"unicode":"1f1e8-1f1f0","unicode_alternates":"","name":"cook islands","shortname":":flag_ck:","category":"flags","emoji_order":"1283","aliases":[":ck:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_cw":{"unicode":"1f1e8-1f1fc","unicode_alternates":"","name":"cura\u00e7ao","shortname":":flag_cw:","category":"flags","emoji_order":"1284","aliases":[":cw:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_eu":{"unicode":"1f1ea-1f1fa","unicode_alternates":"","name":"european union","shortname":":flag_eu:","category":"flags","emoji_order":"1285","aliases":[":eu:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_gf":{"unicode":"1f1ec-1f1eb","unicode_alternates":"","name":"french guiana","shortname":":flag_gf:","category":"flags","emoji_order":"1286","aliases":[":gf:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_tf":{"unicode":"1f1f9-1f1eb","unicode_alternates":"","name":"french southern territories","shortname":":flag_tf:","category":"flags","emoji_order":"1287","aliases":[":tf:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_gp":{"unicode":"1f1ec-1f1f5","unicode_alternates":"","name":"guadeloupe","shortname":":flag_gp:","category":"flags","emoji_order":"1288","aliases":[":gp:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_mq":{"unicode":"1f1f2-1f1f6","unicode_alternates":"","name":"martinique","shortname":":flag_mq:","category":"flags","emoji_order":"1289","aliases":[":mq:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_mp":{"unicode":"1f1f2-1f1f5","unicode_alternates":"","name":"northern mariana islands","shortname":":flag_mp:","category":"flags","emoji_order":"1290","aliases":[":mp:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_sx":{"unicode":"1f1f8-1f1fd","unicode_alternates":"","name":"sint maarten","shortname":":flag_sx:","category":"flags","emoji_order":"1291","aliases":[":sx:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_ss":{"unicode":"1f1f8-1f1f8","unicode_alternates":"","name":"south sudan","shortname":":flag_ss:","category":"flags","emoji_order":"1292","aliases":[":ss:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_tc":{"unicode":"1f1f9-1f1e8","unicode_alternates":"","name":"turks and caicos islands","shortname":":flag_tc:","category":"flags","emoji_order":"1293","aliases":[":tc:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"flag_mf":{"unicode":"1f1f2-1f1eb","unicode_alternates":"","name":"saint martin","shortname":":flag_mf:","category":"flags","emoji_order":"1294","aliases":[":mf:"],"aliases_ascii":[],"keywords":["country","flag","flag"]},"raised_hands_tone1":{"unicode":"1f64c-1f3fb","unicode_alternates":"","name":"person raising both hands in celebration tone 1","shortname":":raised_hands_tone1:","category":"people","emoji_order":"1295","aliases":[],"aliases_ascii":[],"keywords":[]},"raised_hands_tone2":{"unicode":"1f64c-1f3fc","unicode_alternates":"","name":"person raising both hands in celebration tone 2","shortname":":raised_hands_tone2:","category":"people","emoji_order":"1296","aliases":[],"aliases_ascii":[],"keywords":[]},"raised_hands_tone3":{"unicode":"1f64c-1f3fd","unicode_alternates":"","name":"person raising both hands in celebration tone 3","shortname":":raised_hands_tone3:","category":"people","emoji_order":"1297","aliases":[],"aliases_ascii":[],"keywords":[]},"raised_hands_tone4":{"unicode":"1f64c-1f3fe","unicode_alternates":"","name":"person raising both hands in celebration tone 4","shortname":":raised_hands_tone4:","category":"people","emoji_order":"1298","aliases":[],"aliases_ascii":[],"keywords":[]},"raised_hands_tone5":{"unicode":"1f64c-1f3ff","unicode_alternates":"","name":"person raising both hands in celebration tone 5","shortname":":raised_hands_tone5:","category":"people","emoji_order":"1299","aliases":[],"aliases_ascii":[],"keywords":[]},"clap_tone1":{"unicode":"1f44f-1f3fb","unicode_alternates":"","name":"clapping hands sign tone 1","shortname":":clap_tone1:","category":"people","emoji_order":"1300","aliases":[],"aliases_ascii":[],"keywords":[]},"clap_tone2":{"unicode":"1f44f-1f3fc","unicode_alternates":"","name":"clapping hands sign tone 2","shortname":":clap_tone2:","category":"people","emoji_order":"1301","aliases":[],"aliases_ascii":[],"keywords":[]},"clap_tone3":{"unicode":"1f44f-1f3fd","unicode_alternates":"","name":"clapping hands sign tone 3","shortname":":clap_tone3:","category":"people","emoji_order":"1302","aliases":[],"aliases_ascii":[],"keywords":[]},"clap_tone4":{"unicode":"1f44f-1f3fe","unicode_alternates":"","name":"clapping hands sign tone 4","shortname":":clap_tone4:","category":"people","emoji_order":"1303","aliases":[],"aliases_ascii":[],"keywords":[]},"clap_tone5":{"unicode":"1f44f-1f3ff","unicode_alternates":"","name":"clapping hands sign tone 5","shortname":":clap_tone5:","category":"people","emoji_order":"1304","aliases":[],"aliases_ascii":[],"keywords":[]},"wave_tone1":{"unicode":"1f44b-1f3fb","unicode_alternates":"","name":"waving hand sign tone 1","shortname":":wave_tone1:","category":"people","emoji_order":"1305","aliases":[],"aliases_ascii":[],"keywords":[]},"wave_tone2":{"unicode":"1f44b-1f3fc","unicode_alternates":"","name":"waving hand sign tone 2","shortname":":wave_tone2:","category":"people","emoji_order":"1306","aliases":[],"aliases_ascii":[],"keywords":[]},"wave_tone3":{"unicode":"1f44b-1f3fd","unicode_alternates":"","name":"waving hand sign tone 3","shortname":":wave_tone3:","category":"people","emoji_order":"1307","aliases":[],"aliases_ascii":[],"keywords":[]},"wave_tone4":{"unicode":"1f44b-1f3fe","unicode_alternates":"","name":"waving hand sign tone 4","shortname":":wave_tone4:","category":"people","emoji_order":"1308","aliases":[],"aliases_ascii":[],"keywords":[]},"wave_tone5":{"unicode":"1f44b-1f3ff","unicode_alternates":"","name":"waving hand sign tone 5","shortname":":wave_tone5:","category":"people","emoji_order":"1309","aliases":[],"aliases_ascii":[],"keywords":[]},"thumbsup_tone1":{"unicode":"1f44d-1f3fb","unicode_alternates":"","name":"thumbs up sign tone 1","shortname":":thumbsup_tone1:","category":"people","emoji_order":"1310","aliases":[":+1_tone1:",":thumbup_tone1:"],"aliases_ascii":[],"keywords":[]},"thumbsup_tone2":{"unicode":"1f44d-1f3fc","unicode_alternates":"","name":"thumbs up sign tone 2","shortname":":thumbsup_tone2:","category":"people","emoji_order":"1311","aliases":[":+1_tone2:",":thumbup_tone2:"],"aliases_ascii":[],"keywords":[]},"thumbsup_tone3":{"unicode":"1f44d-1f3fd","unicode_alternates":"","name":"thumbs up sign tone 3","shortname":":thumbsup_tone3:","category":"people","emoji_order":"1312","aliases":[":+1_tone3:",":thumbup_tone3:"],"aliases_ascii":[],"keywords":[]},"thumbsup_tone4":{"unicode":"1f44d-1f3fe","unicode_alternates":"","name":"thumbs up sign tone 4","shortname":":thumbsup_tone4:","category":"people","emoji_order":"1313","aliases":[":+1_tone4:",":thumbup_tone4:"],"aliases_ascii":[],"keywords":[]},"thumbsup_tone5":{"unicode":"1f44d-1f3ff","unicode_alternates":"","name":"thumbs up sign tone 5","shortname":":thumbsup_tone5:","category":"people","emoji_order":"1314","aliases":[":+1_tone5:",":thumbup_tone5:"],"aliases_ascii":[],"keywords":[]},"thumbsdown_tone1":{"unicode":"1f44e-1f3fb","unicode_alternates":"","name":"thumbs down sign tone 1","shortname":":thumbsdown_tone1:","category":"people","emoji_order":"1315","aliases":[":-1_tone1:",":thumbdown_tone1:"],"aliases_ascii":[],"keywords":[]},"thumbsdown_tone2":{"unicode":"1f44e-1f3fc","unicode_alternates":"","name":"thumbs down sign tone 2","shortname":":thumbsdown_tone2:","category":"people","emoji_order":"1316","aliases":[":-1_tone2:",":thumbdown_tone2:"],"aliases_ascii":[],"keywords":[]},"thumbsdown_tone3":{"unicode":"1f44e-1f3fd","unicode_alternates":"","name":"thumbs down sign tone 3","shortname":":thumbsdown_tone3:","category":"people","emoji_order":"1317","aliases":[":-1_tone3:",":thumbdown_tone3:"],"aliases_ascii":[],"keywords":[]},"thumbsdown_tone4":{"unicode":"1f44e-1f3fe","unicode_alternates":"","name":"thumbs down sign tone 4","shortname":":thumbsdown_tone4:","category":"people","emoji_order":"1318","aliases":[":-1_tone4:",":thumbdown_tone4:"],"aliases_ascii":[],"keywords":[]},"thumbsdown_tone5":{"unicode":"1f44e-1f3ff","unicode_alternates":"","name":"thumbs down sign tone 5","shortname":":thumbsdown_tone5:","category":"people","emoji_order":"1319","aliases":[":-1_tone5:",":thumbdown_tone5:"],"aliases_ascii":[],"keywords":[]},"punch_tone1":{"unicode":"1f44a-1f3fb","unicode_alternates":"","name":"fisted hand sign tone 1","shortname":":punch_tone1:","category":"people","emoji_order":"1320","aliases":[],"aliases_ascii":[],"keywords":[]},"punch_tone2":{"unicode":"1f44a-1f3fc","unicode_alternates":"","name":"fisted hand sign tone 2","shortname":":punch_tone2:","category":"people","emoji_order":"1321","aliases":[],"aliases_ascii":[],"keywords":[]},"punch_tone3":{"unicode":"1f44a-1f3fd","unicode_alternates":"","name":"fisted hand sign tone 3","shortname":":punch_tone3:","category":"people","emoji_order":"1322","aliases":[],"aliases_ascii":[],"keywords":[]},"punch_tone4":{"unicode":"1f44a-1f3fe","unicode_alternates":"","name":"fisted hand sign tone 4","shortname":":punch_tone4:","category":"people","emoji_order":"1323","aliases":[],"aliases_ascii":[],"keywords":[]},"punch_tone5":{"unicode":"1f44a-1f3ff","unicode_alternates":"","name":"fisted hand sign tone 5","shortname":":punch_tone5:","category":"people","emoji_order":"1324","aliases":[],"aliases_ascii":[],"keywords":[]},"fist_tone1":{"unicode":"270a-1f3fb","unicode_alternates":"","name":"raised fist tone 1","shortname":":fist_tone1:","category":"people","emoji_order":"1325","aliases":[],"aliases_ascii":[],"keywords":[]},"fist_tone2":{"unicode":"270a-1f3fc","unicode_alternates":"","name":"raised fist tone 2","shortname":":fist_tone2:","category":"people","emoji_order":"1326","aliases":[],"aliases_ascii":[],"keywords":[]},"fist_tone3":{"unicode":"270a-1f3fd","unicode_alternates":"","name":"raised fist tone 3","shortname":":fist_tone3:","category":"people","emoji_order":"1327","aliases":[],"aliases_ascii":[],"keywords":[]},"fist_tone4":{"unicode":"270a-1f3fe","unicode_alternates":"","name":"raised fist tone 4","shortname":":fist_tone4:","category":"people","emoji_order":"1328","aliases":[],"aliases_ascii":[],"keywords":[]},"fist_tone5":{"unicode":"270a-1f3ff","unicode_alternates":"","name":"raised fist tone 5","shortname":":fist_tone5:","category":"people","emoji_order":"1329","aliases":[],"aliases_ascii":[],"keywords":[]},"v_tone1":{"unicode":"270c-1f3fb","unicode_alternates":"","name":"victory hand tone 1","shortname":":v_tone1:","category":"people","emoji_order":"1330","aliases":[],"aliases_ascii":[],"keywords":[]},"v_tone2":{"unicode":"270c-1f3fc","unicode_alternates":"","name":"victory hand tone 2","shortname":":v_tone2:","category":"people","emoji_order":"1331","aliases":[],"aliases_ascii":[],"keywords":[]},"v_tone3":{"unicode":"270c-1f3fd","unicode_alternates":"","name":"victory hand tone 3","shortname":":v_tone3:","category":"people","emoji_order":"1332","aliases":[],"aliases_ascii":[],"keywords":[]},"v_tone4":{"unicode":"270c-1f3fe","unicode_alternates":"","name":"victory hand tone 4","shortname":":v_tone4:","category":"people","emoji_order":"1333","aliases":[],"aliases_ascii":[],"keywords":[]},"v_tone5":{"unicode":"270c-1f3ff","unicode_alternates":"","name":"victory hand tone 5","shortname":":v_tone5:","category":"people","emoji_order":"1334","aliases":[],"aliases_ascii":[],"keywords":[]},"ok_hand_tone1":{"unicode":"1f44c-1f3fb","unicode_alternates":"","name":"ok hand sign tone 1","shortname":":ok_hand_tone1:","category":"people","emoji_order":"1335","aliases":[],"aliases_ascii":[],"keywords":[]},"ok_hand_tone2":{"unicode":"1f44c-1f3fc","unicode_alternates":"","name":"ok hand sign tone 2","shortname":":ok_hand_tone2:","category":"people","emoji_order":"1336","aliases":[],"aliases_ascii":[],"keywords":[]},"ok_hand_tone3":{"unicode":"1f44c-1f3fd","unicode_alternates":"","name":"ok hand sign tone 3","shortname":":ok_hand_tone3:","category":"people","emoji_order":"1337","aliases":[],"aliases_ascii":[],"keywords":[]},"ok_hand_tone4":{"unicode":"1f44c-1f3fe","unicode_alternates":"","name":"ok hand sign tone 4","shortname":":ok_hand_tone4:","category":"people","emoji_order":"1338","aliases":[],"aliases_ascii":[],"keywords":[]},"ok_hand_tone5":{"unicode":"1f44c-1f3ff","unicode_alternates":"","name":"ok hand sign tone 5","shortname":":ok_hand_tone5:","category":"people","emoji_order":"1339","aliases":[],"aliases_ascii":[],"keywords":[]},"raised_hand_tone1":{"unicode":"270b-1f3fb","unicode_alternates":"","name":"raised hand tone 1","shortname":":raised_hand_tone1:","category":"people","emoji_order":"1340","aliases":[],"aliases_ascii":[],"keywords":[]},"raised_hand_tone2":{"unicode":"270b-1f3fc","unicode_alternates":"","name":"raised hand tone 2","shortname":":raised_hand_tone2:","category":"people","emoji_order":"1341","aliases":[],"aliases_ascii":[],"keywords":[]},"raised_hand_tone3":{"unicode":"270b-1f3fd","unicode_alternates":"","name":"raised hand tone 3","shortname":":raised_hand_tone3:","category":"people","emoji_order":"1342","aliases":[],"aliases_ascii":[],"keywords":[]},"raised_hand_tone4":{"unicode":"270b-1f3fe","unicode_alternates":"","name":"raised hand tone 4","shortname":":raised_hand_tone4:","category":"people","emoji_order":"1343","aliases":[],"aliases_ascii":[],"keywords":[]},"raised_hand_tone5":{"unicode":"270b-1f3ff","unicode_alternates":"","name":"raised hand tone 5","shortname":":raised_hand_tone5:","category":"people","emoji_order":"1344","aliases":[],"aliases_ascii":[],"keywords":[]},"open_hands_tone1":{"unicode":"1f450-1f3fb","unicode_alternates":"","name":"open hands sign tone 1","shortname":":open_hands_tone1:","category":"people","emoji_order":"1345","aliases":[],"aliases_ascii":[],"keywords":[]},"open_hands_tone2":{"unicode":"1f450-1f3fc","unicode_alternates":"","name":"open hands sign tone 2","shortname":":open_hands_tone2:","category":"people","emoji_order":"1346","aliases":[],"aliases_ascii":[],"keywords":[]},"open_hands_tone3":{"unicode":"1f450-1f3fd","unicode_alternates":"","name":"open hands sign tone 3","shortname":":open_hands_tone3:","category":"people","emoji_order":"1347","aliases":[],"aliases_ascii":[],"keywords":[]},"open_hands_tone4":{"unicode":"1f450-1f3fe","unicode_alternates":"","name":"open hands sign tone 4","shortname":":open_hands_tone4:","category":"people","emoji_order":"1348","aliases":[],"aliases_ascii":[],"keywords":[]},"open_hands_tone5":{"unicode":"1f450-1f3ff","unicode_alternates":"","name":"open hands sign tone 5","shortname":":open_hands_tone5:","category":"people","emoji_order":"1349","aliases":[],"aliases_ascii":[],"keywords":[]},"muscle_tone1":{"unicode":"1f4aa-1f3fb","unicode_alternates":"","name":"flexed biceps tone 1","shortname":":muscle_tone1:","category":"people","emoji_order":"1350","aliases":[],"aliases_ascii":[],"keywords":[]},"muscle_tone2":{"unicode":"1f4aa-1f3fc","unicode_alternates":"","name":"flexed biceps tone 2","shortname":":muscle_tone2:","category":"people","emoji_order":"1351","aliases":[],"aliases_ascii":[],"keywords":[]},"muscle_tone3":{"unicode":"1f4aa-1f3fd","unicode_alternates":"","name":"flexed biceps tone 3","shortname":":muscle_tone3:","category":"people","emoji_order":"1352","aliases":[],"aliases_ascii":[],"keywords":[]},"muscle_tone4":{"unicode":"1f4aa-1f3fe","unicode_alternates":"","name":"flexed biceps tone 4","shortname":":muscle_tone4:","category":"people","emoji_order":"1353","aliases":[],"aliases_ascii":[],"keywords":[]},"muscle_tone5":{"unicode":"1f4aa-1f3ff","unicode_alternates":"","name":"flexed biceps tone 5","shortname":":muscle_tone5:","category":"people","emoji_order":"1354","aliases":[],"aliases_ascii":[],"keywords":[]},"pray_tone1":{"unicode":"1f64f-1f3fb","unicode_alternates":"","name":"person with folded hands tone 1","shortname":":pray_tone1:","category":"people","emoji_order":"1355","aliases":[],"aliases_ascii":[],"keywords":[]},"pray_tone2":{"unicode":"1f64f-1f3fc","unicode_alternates":"","name":"person with folded hands tone 2","shortname":":pray_tone2:","category":"people","emoji_order":"1356","aliases":[],"aliases_ascii":[],"keywords":[]},"pray_tone3":{"unicode":"1f64f-1f3fd","unicode_alternates":"","name":"person with folded hands tone 3","shortname":":pray_tone3:","category":"people","emoji_order":"1357","aliases":[],"aliases_ascii":[],"keywords":[]},"pray_tone4":{"unicode":"1f64f-1f3fe","unicode_alternates":"","name":"person with folded hands tone 4","shortname":":pray_tone4:","category":"people","emoji_order":"1358","aliases":[],"aliases_ascii":[],"keywords":[]},"pray_tone5":{"unicode":"1f64f-1f3ff","unicode_alternates":"","name":"person with folded hands tone 5","shortname":":pray_tone5:","category":"people","emoji_order":"1359","aliases":[],"aliases_ascii":[],"keywords":[]},"point_up_tone1":{"unicode":"261d-1f3fb","unicode_alternates":"","name":"white up pointing index tone 1","shortname":":point_up_tone1:","category":"people","emoji_order":"1360","aliases":[],"aliases_ascii":[],"keywords":[]},"point_up_tone2":{"unicode":"261d-1f3fc","unicode_alternates":"","name":"white up pointing index tone 2","shortname":":point_up_tone2:","category":"people","emoji_order":"1361","aliases":[],"aliases_ascii":[],"keywords":[]},"point_up_tone3":{"unicode":"261d-1f3fd","unicode_alternates":"","name":"white up pointing index tone 3","shortname":":point_up_tone3:","category":"people","emoji_order":"1362","aliases":[],"aliases_ascii":[],"keywords":[]},"point_up_tone4":{"unicode":"261d-1f3fe","unicode_alternates":"","name":"white up pointing index tone 4","shortname":":point_up_tone4:","category":"people","emoji_order":"1363","aliases":[],"aliases_ascii":[],"keywords":[]},"point_up_tone5":{"unicode":"261d-1f3ff","unicode_alternates":"","name":"white up pointing index tone 5","shortname":":point_up_tone5:","category":"people","emoji_order":"1364","aliases":[],"aliases_ascii":[],"keywords":[]},"point_up_2_tone1":{"unicode":"1f446-1f3fb","unicode_alternates":"","name":"white up pointing backhand index tone 1","shortname":":point_up_2_tone1:","category":"people","emoji_order":"1365","aliases":[],"aliases_ascii":[],"keywords":[]},"point_up_2_tone2":{"unicode":"1f446-1f3fc","unicode_alternates":"","name":"white up pointing backhand index tone 2","shortname":":point_up_2_tone2:","category":"people","emoji_order":"1366","aliases":[],"aliases_ascii":[],"keywords":[]},"point_up_2_tone3":{"unicode":"1f446-1f3fd","unicode_alternates":"","name":"white up pointing backhand index tone 3","shortname":":point_up_2_tone3:","category":"people","emoji_order":"1367","aliases":[],"aliases_ascii":[],"keywords":[]},"point_up_2_tone4":{"unicode":"1f446-1f3fe","unicode_alternates":"","name":"white up pointing backhand index tone 4","shortname":":point_up_2_tone4:","category":"people","emoji_order":"1368","aliases":[],"aliases_ascii":[],"keywords":[]},"point_up_2_tone5":{"unicode":"1f446-1f3ff","unicode_alternates":"","name":"white up pointing backhand index tone 5","shortname":":point_up_2_tone5:","category":"people","emoji_order":"1369","aliases":[],"aliases_ascii":[],"keywords":[]},"point_down_tone1":{"unicode":"1f447-1f3fb","unicode_alternates":"","name":"white down pointing backhand index tone 1","shortname":":point_down_tone1:","category":"people","emoji_order":"1370","aliases":[],"aliases_ascii":[],"keywords":[]},"point_down_tone2":{"unicode":"1f447-1f3fc","unicode_alternates":"","name":"white down pointing backhand index tone 2","shortname":":point_down_tone2:","category":"people","emoji_order":"1371","aliases":[],"aliases_ascii":[],"keywords":[]},"point_down_tone3":{"unicode":"1f447-1f3fd","unicode_alternates":"","name":"white down pointing backhand index tone 3","shortname":":point_down_tone3:","category":"people","emoji_order":"1372","aliases":[],"aliases_ascii":[],"keywords":[]},"point_down_tone4":{"unicode":"1f447-1f3fe","unicode_alternates":"","name":"white down pointing backhand index tone 4","shortname":":point_down_tone4:","category":"people","emoji_order":"1373","aliases":[],"aliases_ascii":[],"keywords":[]},"point_down_tone5":{"unicode":"1f447-1f3ff","unicode_alternates":"","name":"white down pointing backhand index tone 5","shortname":":point_down_tone5:","category":"people","emoji_order":"1374","aliases":[],"aliases_ascii":[],"keywords":[]},"point_left_tone1":{"unicode":"1f448-1f3fb","unicode_alternates":"","name":"white left pointing backhand index tone 1","shortname":":point_left_tone1:","category":"people","emoji_order":"1375","aliases":[],"aliases_ascii":[],"keywords":[]},"point_left_tone2":{"unicode":"1f448-1f3fc","unicode_alternates":"","name":"white left pointing backhand index tone 2","shortname":":point_left_tone2:","category":"people","emoji_order":"1376","aliases":[],"aliases_ascii":[],"keywords":[]},"point_left_tone3":{"unicode":"1f448-1f3fd","unicode_alternates":"","name":"white left pointing backhand index tone 3","shortname":":point_left_tone3:","category":"people","emoji_order":"1377","aliases":[],"aliases_ascii":[],"keywords":[]},"point_left_tone4":{"unicode":"1f448-1f3fe","unicode_alternates":"","name":"white left pointing backhand index tone 4","shortname":":point_left_tone4:","category":"people","emoji_order":"1378","aliases":[],"aliases_ascii":[],"keywords":[]},"point_left_tone5":{"unicode":"1f448-1f3ff","unicode_alternates":"","name":"white left pointing backhand index tone 5","shortname":":point_left_tone5:","category":"people","emoji_order":"1379","aliases":[],"aliases_ascii":[],"keywords":[]},"point_right_tone1":{"unicode":"1f449-1f3fb","unicode_alternates":"","name":"white right pointing backhand index tone 1","shortname":":point_right_tone1:","category":"people","emoji_order":"1380","aliases":[],"aliases_ascii":[],"keywords":[]},"point_right_tone2":{"unicode":"1f449-1f3fc","unicode_alternates":"","name":"white right pointing backhand index tone 2","shortname":":point_right_tone2:","category":"people","emoji_order":"1381","aliases":[],"aliases_ascii":[],"keywords":[]},"point_right_tone3":{"unicode":"1f449-1f3fd","unicode_alternates":"","name":"white right pointing backhand index tone 3","shortname":":point_right_tone3:","category":"people","emoji_order":"1382","aliases":[],"aliases_ascii":[],"keywords":[]},"point_right_tone4":{"unicode":"1f449-1f3fe","unicode_alternates":"","name":"white right pointing backhand index tone 4","shortname":":point_right_tone4:","category":"people","emoji_order":"1383","aliases":[],"aliases_ascii":[],"keywords":[]},"point_right_tone5":{"unicode":"1f449-1f3ff","unicode_alternates":"","name":"white right pointing backhand index tone 5","shortname":":point_right_tone5:","category":"people","emoji_order":"1384","aliases":[],"aliases_ascii":[],"keywords":[]},"middle_finger_tone1":{"unicode":"1f595-1f3fb","unicode_alternates":"","name":"reversed hand with middle finger extended tone 1","shortname":":middle_finger_tone1:","category":"people","emoji_order":"1385","aliases":[":reversed_hand_with_middle_finger_extended_tone1:"],"aliases_ascii":[],"keywords":[]},"middle_finger_tone2":{"unicode":"1f595-1f3fc","unicode_alternates":"","name":"reversed hand with middle finger extended tone 2","shortname":":middle_finger_tone2:","category":"people","emoji_order":"1386","aliases":[":reversed_hand_with_middle_finger_extended_tone2:"],"aliases_ascii":[],"keywords":[]},"middle_finger_tone3":{"unicode":"1f595-1f3fd","unicode_alternates":"","name":"reversed hand with middle finger extended tone 3","shortname":":middle_finger_tone3:","category":"people","emoji_order":"1387","aliases":[":reversed_hand_with_middle_finger_extended_tone3:"],"aliases_ascii":[],"keywords":[]},"middle_finger_tone4":{"unicode":"1f595-1f3fe","unicode_alternates":"","name":"reversed hand with middle finger extended tone 4","shortname":":middle_finger_tone4:","category":"people","emoji_order":"1388","aliases":[":reversed_hand_with_middle_finger_extended_tone4:"],"aliases_ascii":[],"keywords":[]},"middle_finger_tone5":{"unicode":"1f595-1f3ff","unicode_alternates":"","name":"reversed hand with middle finger extended tone 5","shortname":":middle_finger_tone5:","category":"people","emoji_order":"1389","aliases":[":reversed_hand_with_middle_finger_extended_tone5:"],"aliases_ascii":[],"keywords":[]},"hand_splayed_tone1":{"unicode":"1f590-1f3fb","unicode_alternates":"","name":"raised hand with fingers splayed tone 1","shortname":":hand_splayed_tone1:","category":"people","emoji_order":"1390","aliases":[":raised_hand_with_fingers_splayed_tone1:"],"aliases_ascii":[],"keywords":[]},"hand_splayed_tone2":{"unicode":"1f590-1f3fc","unicode_alternates":"","name":"raised hand with fingers splayed tone 2","shortname":":hand_splayed_tone2:","category":"people","emoji_order":"1391","aliases":[":raised_hand_with_fingers_splayed_tone2:"],"aliases_ascii":[],"keywords":[]},"hand_splayed_tone3":{"unicode":"1f590-1f3fd","unicode_alternates":"","name":"raised hand with fingers splayed tone 3","shortname":":hand_splayed_tone3:","category":"people","emoji_order":"1392","aliases":[":raised_hand_with_fingers_splayed_tone3:"],"aliases_ascii":[],"keywords":[]},"hand_splayed_tone4":{"unicode":"1f590-1f3fe","unicode_alternates":"","name":"raised hand with fingers splayed tone 4","shortname":":hand_splayed_tone4:","category":"people","emoji_order":"1393","aliases":[":raised_hand_with_fingers_splayed_tone4:"],"aliases_ascii":[],"keywords":[]},"hand_splayed_tone5":{"unicode":"1f590-1f3ff","unicode_alternates":"","name":"raised hand with fingers splayed tone 5","shortname":":hand_splayed_tone5:","category":"people","emoji_order":"1394","aliases":[":raised_hand_with_fingers_splayed_tone5:"],"aliases_ascii":[],"keywords":[]},"metal_tone1":{"unicode":"1f918-1f3fb","unicode_alternates":"","name":"sign of the horns tone 1","shortname":":metal_tone1:","category":"people","emoji_order":"1395","aliases":[":sign_of_the_horns_tone1:"],"aliases_ascii":[],"keywords":[]},"metal_tone2":{"unicode":"1f918-1f3fc","unicode_alternates":"","name":"sign of the horns tone 2","shortname":":metal_tone2:","category":"people","emoji_order":"1396","aliases":[":sign_of_the_horns_tone2:"],"aliases_ascii":[],"keywords":[]},"metal_tone3":{"unicode":"1f918-1f3fd","unicode_alternates":"","name":"sign of the horns tone 3","shortname":":metal_tone3:","category":"people","emoji_order":"1397","aliases":[":sign_of_the_horns_tone3:"],"aliases_ascii":[],"keywords":[]},"metal_tone4":{"unicode":"1f918-1f3fe","unicode_alternates":"","name":"sign of the horns tone 4","shortname":":metal_tone4:","category":"people","emoji_order":"1398","aliases":[":sign_of_the_horns_tone4:"],"aliases_ascii":[],"keywords":[]},"metal_tone5":{"unicode":"1f918-1f3ff","unicode_alternates":"","name":"sign of the horns tone 5","shortname":":metal_tone5:","category":"people","emoji_order":"1399","aliases":[":sign_of_the_horns_tone5:"],"aliases_ascii":[],"keywords":[]},"vulcan_tone1":{"unicode":"1f596-1f3fb","unicode_alternates":"","name":"raised hand with part between middle and ring fingers tone 1","shortname":":vulcan_tone1:","category":"people","emoji_order":"1400","aliases":[":raised_hand_with_part_between_middle_and_ring_fingers_tone1:"],"aliases_ascii":[],"keywords":[]},"vulcan_tone2":{"unicode":"1f596-1f3fc","unicode_alternates":"","name":"raised hand with part between middle and ring fingers tone 2","shortname":":vulcan_tone2:","category":"people","emoji_order":"1401","aliases":[":raised_hand_with_part_between_middle_and_ring_fingers_tone2:"],"aliases_ascii":[],"keywords":[]},"vulcan_tone3":{"unicode":"1f596-1f3fd","unicode_alternates":"","name":"raised hand with part between middle and ring fingers tone 3","shortname":":vulcan_tone3:","category":"people","emoji_order":"1402","aliases":[":raised_hand_with_part_between_middle_and_ring_fingers_tone3:"],"aliases_ascii":[],"keywords":[]},"vulcan_tone4":{"unicode":"1f596-1f3fe","unicode_alternates":"","name":"raised hand with part between middle and ring fingers tone 4","shortname":":vulcan_tone4:","category":"people","emoji_order":"1403","aliases":[":raised_hand_with_part_between_middle_and_ring_fingers_tone4:"],"aliases_ascii":[],"keywords":[]},"vulcan_tone5":{"unicode":"1f596-1f3ff","unicode_alternates":"","name":"raised hand with part between middle and ring fingers tone 5","shortname":":vulcan_tone5:","category":"people","emoji_order":"1404","aliases":[":raised_hand_with_part_between_middle_and_ring_fingers_tone5:"],"aliases_ascii":[],"keywords":[]},"writing_hand_tone1":{"unicode":"270d-1f3fb","unicode_alternates":"","name":"writing hand tone 1","shortname":":writing_hand_tone1:","category":"people","emoji_order":"1405","aliases":[],"aliases_ascii":[],"keywords":[]},"writing_hand_tone2":{"unicode":"270d-1f3fc","unicode_alternates":"","name":"writing hand tone 2","shortname":":writing_hand_tone2:","category":"people","emoji_order":"1406","aliases":[],"aliases_ascii":[],"keywords":[]},"writing_hand_tone3":{"unicode":"270d-1f3fd","unicode_alternates":"","name":"writing hand tone 3","shortname":":writing_hand_tone3:","category":"people","emoji_order":"1407","aliases":[],"aliases_ascii":[],"keywords":[]},"writing_hand_tone4":{"unicode":"270d-1f3fe","unicode_alternates":"","name":"writing hand tone 4","shortname":":writing_hand_tone4:","category":"people","emoji_order":"1408","aliases":[],"aliases_ascii":[],"keywords":[]},"writing_hand_tone5":{"unicode":"270d-1f3ff","unicode_alternates":"","name":"writing hand tone 5","shortname":":writing_hand_tone5:","category":"people","emoji_order":"1409","aliases":[],"aliases_ascii":[],"keywords":[]},"nail_care_tone1":{"unicode":"1f485-1f3fb","unicode_alternates":"","name":"nail polish tone 1","shortname":":nail_care_tone1:","category":"people","emoji_order":"1410","aliases":[],"aliases_ascii":[],"keywords":[]},"nail_care_tone2":{"unicode":"1f485-1f3fc","unicode_alternates":"","name":"nail polish tone 2","shortname":":nail_care_tone2:","category":"people","emoji_order":"1411","aliases":[],"aliases_ascii":[],"keywords":[]},"nail_care_tone3":{"unicode":"1f485-1f3fd","unicode_alternates":"","name":"nail polish tone 3","shortname":":nail_care_tone3:","category":"people","emoji_order":"1412","aliases":[],"aliases_ascii":[],"keywords":[]},"nail_care_tone4":{"unicode":"1f485-1f3fe","unicode_alternates":"","name":"nail polish tone 4","shortname":":nail_care_tone4:","category":"people","emoji_order":"1413","aliases":[],"aliases_ascii":[],"keywords":[]},"nail_care_tone5":{"unicode":"1f485-1f3ff","unicode_alternates":"","name":"nail polish tone 5","shortname":":nail_care_tone5:","category":"people","emoji_order":"1414","aliases":[],"aliases_ascii":[],"keywords":[]},"ear_tone1":{"unicode":"1f442-1f3fb","unicode_alternates":"","name":"ear tone 1","shortname":":ear_tone1:","category":"people","emoji_order":"1415","aliases":[],"aliases_ascii":[],"keywords":[]},"ear_tone2":{"unicode":"1f442-1f3fc","unicode_alternates":"","name":"ear tone 2","shortname":":ear_tone2:","category":"people","emoji_order":"1416","aliases":[],"aliases_ascii":[],"keywords":[]},"ear_tone3":{"unicode":"1f442-1f3fd","unicode_alternates":"","name":"ear tone 3","shortname":":ear_tone3:","category":"people","emoji_order":"1417","aliases":[],"aliases_ascii":[],"keywords":[]},"ear_tone4":{"unicode":"1f442-1f3fe","unicode_alternates":"","name":"ear tone 4","shortname":":ear_tone4:","category":"people","emoji_order":"1418","aliases":[],"aliases_ascii":[],"keywords":[]},"ear_tone5":{"unicode":"1f442-1f3ff","unicode_alternates":"","name":"ear tone 5","shortname":":ear_tone5:","category":"people","emoji_order":"1419","aliases":[],"aliases_ascii":[],"keywords":[]},"nose_tone1":{"unicode":"1f443-1f3fb","unicode_alternates":"","name":"nose tone 1","shortname":":nose_tone1:","category":"people","emoji_order":"1420","aliases":[],"aliases_ascii":[],"keywords":[]},"nose_tone2":{"unicode":"1f443-1f3fc","unicode_alternates":"","name":"nose tone 2","shortname":":nose_tone2:","category":"people","emoji_order":"1421","aliases":[],"aliases_ascii":[],"keywords":[]},"nose_tone3":{"unicode":"1f443-1f3fd","unicode_alternates":"","name":"nose tone 3","shortname":":nose_tone3:","category":"people","emoji_order":"1422","aliases":[],"aliases_ascii":[],"keywords":[]},"nose_tone4":{"unicode":"1f443-1f3fe","unicode_alternates":"","name":"nose tone 4","shortname":":nose_tone4:","category":"people","emoji_order":"1423","aliases":[],"aliases_ascii":[],"keywords":[]},"nose_tone5":{"unicode":"1f443-1f3ff","unicode_alternates":"","name":"nose tone 5","shortname":":nose_tone5:","category":"people","emoji_order":"1424","aliases":[],"aliases_ascii":[],"keywords":[]},"baby_tone1":{"unicode":"1f476-1f3fb","unicode_alternates":"","name":"baby tone 1","shortname":":baby_tone1:","category":"people","emoji_order":"1425","aliases":[],"aliases_ascii":[],"keywords":[]},"baby_tone2":{"unicode":"1f476-1f3fc","unicode_alternates":"","name":"baby tone 2","shortname":":baby_tone2:","category":"people","emoji_order":"1426","aliases":[],"aliases_ascii":[],"keywords":[]},"baby_tone3":{"unicode":"1f476-1f3fd","unicode_alternates":"","name":"baby tone 3","shortname":":baby_tone3:","category":"people","emoji_order":"1427","aliases":[],"aliases_ascii":[],"keywords":[]},"baby_tone4":{"unicode":"1f476-1f3fe","unicode_alternates":"","name":"baby tone 4","shortname":":baby_tone4:","category":"people","emoji_order":"1428","aliases":[],"aliases_ascii":[],"keywords":[]},"baby_tone5":{"unicode":"1f476-1f3ff","unicode_alternates":"","name":"baby tone 5","shortname":":baby_tone5:","category":"people","emoji_order":"1429","aliases":[],"aliases_ascii":[],"keywords":[]},"boy_tone1":{"unicode":"1f466-1f3fb","unicode_alternates":"","name":"boy tone 1","shortname":":boy_tone1:","category":"people","emoji_order":"1430","aliases":[],"aliases_ascii":[],"keywords":[]},"boy_tone2":{"unicode":"1f466-1f3fc","unicode_alternates":"","name":"boy tone 2","shortname":":boy_tone2:","category":"people","emoji_order":"1431","aliases":[],"aliases_ascii":[],"keywords":[]},"boy_tone3":{"unicode":"1f466-1f3fd","unicode_alternates":"","name":"boy tone 3","shortname":":boy_tone3:","category":"people","emoji_order":"1432","aliases":[],"aliases_ascii":[],"keywords":[]},"boy_tone4":{"unicode":"1f466-1f3fe","unicode_alternates":"","name":"boy tone 4","shortname":":boy_tone4:","category":"people","emoji_order":"1433","aliases":[],"aliases_ascii":[],"keywords":[]},"boy_tone5":{"unicode":"1f466-1f3ff","unicode_alternates":"","name":"boy tone 5","shortname":":boy_tone5:","category":"people","emoji_order":"1434","aliases":[],"aliases_ascii":[],"keywords":[]},"girl_tone1":{"unicode":"1f467-1f3fb","unicode_alternates":"","name":"girl tone 1","shortname":":girl_tone1:","category":"people","emoji_order":"1435","aliases":[],"aliases_ascii":[],"keywords":[]},"girl_tone2":{"unicode":"1f467-1f3fc","unicode_alternates":"","name":"girl tone 2","shortname":":girl_tone2:","category":"people","emoji_order":"1436","aliases":[],"aliases_ascii":[],"keywords":[]},"girl_tone3":{"unicode":"1f467-1f3fd","unicode_alternates":"","name":"girl tone 3","shortname":":girl_tone3:","category":"people","emoji_order":"1437","aliases":[],"aliases_ascii":[],"keywords":[]},"girl_tone4":{"unicode":"1f467-1f3fe","unicode_alternates":"","name":"girl tone 4","shortname":":girl_tone4:","category":"people","emoji_order":"1438","aliases":[],"aliases_ascii":[],"keywords":[]},"girl_tone5":{"unicode":"1f467-1f3ff","unicode_alternates":"","name":"girl tone 5","shortname":":girl_tone5:","category":"people","emoji_order":"1439","aliases":[],"aliases_ascii":[],"keywords":[]},"man_tone1":{"unicode":"1f468-1f3fb","unicode_alternates":"","name":"man tone 1","shortname":":man_tone1:","category":"people","emoji_order":"1440","aliases":[],"aliases_ascii":[],"keywords":[]},"man_tone2":{"unicode":"1f468-1f3fc","unicode_alternates":"","name":"man tone 2","shortname":":man_tone2:","category":"people","emoji_order":"1441","aliases":[],"aliases_ascii":[],"keywords":[]},"man_tone3":{"unicode":"1f468-1f3fd","unicode_alternates":"","name":"man tone 3","shortname":":man_tone3:","category":"people","emoji_order":"1442","aliases":[],"aliases_ascii":[],"keywords":[]},"man_tone4":{"unicode":"1f468-1f3fe","unicode_alternates":"","name":"man tone 4","shortname":":man_tone4:","category":"people","emoji_order":"1443","aliases":[],"aliases_ascii":[],"keywords":[]},"man_tone5":{"unicode":"1f468-1f3ff","unicode_alternates":"","name":"man tone 5","shortname":":man_tone5:","category":"people","emoji_order":"1444","aliases":[],"aliases_ascii":[],"keywords":[]},"woman_tone1":{"unicode":"1f469-1f3fb","unicode_alternates":"","name":"woman tone 1","shortname":":woman_tone1:","category":"people","emoji_order":"1445","aliases":[],"aliases_ascii":[],"keywords":[]},"woman_tone2":{"unicode":"1f469-1f3fc","unicode_alternates":"","name":"woman tone 2","shortname":":woman_tone2:","category":"people","emoji_order":"1446","aliases":[],"aliases_ascii":[],"keywords":[]},"woman_tone3":{"unicode":"1f469-1f3fd","unicode_alternates":"","name":"woman tone 3","shortname":":woman_tone3:","category":"people","emoji_order":"1447","aliases":[],"aliases_ascii":[],"keywords":[]},"woman_tone4":{"unicode":"1f469-1f3fe","unicode_alternates":"","name":"woman tone 4","shortname":":woman_tone4:","category":"people","emoji_order":"1448","aliases":[],"aliases_ascii":[],"keywords":[]},"woman_tone5":{"unicode":"1f469-1f3ff","unicode_alternates":"","name":"woman tone 5","shortname":":woman_tone5:","category":"people","emoji_order":"1449","aliases":[],"aliases_ascii":[],"keywords":[]},"person_with_blond_hair_tone1":{"unicode":"1f471-1f3fb","unicode_alternates":"","name":"person with blond hair tone 1","shortname":":person_with_blond_hair_tone1:","category":"people","emoji_order":"1450","aliases":[],"aliases_ascii":[],"keywords":[]},"person_with_blond_hair_tone2":{"unicode":"1f471-1f3fc","unicode_alternates":"","name":"person with blond hair tone 2","shortname":":person_with_blond_hair_tone2:","category":"people","emoji_order":"1451","aliases":[],"aliases_ascii":[],"keywords":[]},"person_with_blond_hair_tone3":{"unicode":"1f471-1f3fd","unicode_alternates":"","name":"person with blond hair tone 3","shortname":":person_with_blond_hair_tone3:","category":"people","emoji_order":"1452","aliases":[],"aliases_ascii":[],"keywords":[]},"person_with_blond_hair_tone4":{"unicode":"1f471-1f3fe","unicode_alternates":"","name":"person with blond hair tone 4","shortname":":person_with_blond_hair_tone4:","category":"people","emoji_order":"1453","aliases":[],"aliases_ascii":[],"keywords":[]},"person_with_blond_hair_tone5":{"unicode":"1f471-1f3ff","unicode_alternates":"","name":"person with blond hair tone 5","shortname":":person_with_blond_hair_tone5:","category":"people","emoji_order":"1454","aliases":[],"aliases_ascii":[],"keywords":[]},"older_man_tone1":{"unicode":"1f474-1f3fb","unicode_alternates":"","name":"older man tone 1","shortname":":older_man_tone1:","category":"people","emoji_order":"1455","aliases":[],"aliases_ascii":[],"keywords":[]},"older_man_tone2":{"unicode":"1f474-1f3fc","unicode_alternates":"","name":"older man tone 2","shortname":":older_man_tone2:","category":"people","emoji_order":"1456","aliases":[],"aliases_ascii":[],"keywords":[]},"older_man_tone3":{"unicode":"1f474-1f3fd","unicode_alternates":"","name":"older man tone 3","shortname":":older_man_tone3:","category":"people","emoji_order":"1457","aliases":[],"aliases_ascii":[],"keywords":[]},"older_man_tone4":{"unicode":"1f474-1f3fe","unicode_alternates":"","name":"older man tone 4","shortname":":older_man_tone4:","category":"people","emoji_order":"1458","aliases":[],"aliases_ascii":[],"keywords":[]},"older_man_tone5":{"unicode":"1f474-1f3ff","unicode_alternates":"","name":"older man tone 5","shortname":":older_man_tone5:","category":"people","emoji_order":"1459","aliases":[],"aliases_ascii":[],"keywords":[]},"older_woman_tone1":{"unicode":"1f475-1f3fb","unicode_alternates":"","name":"older woman tone 1","shortname":":older_woman_tone1:","category":"people","emoji_order":"1460","aliases":[":grandma_tone1:"],"aliases_ascii":[],"keywords":[]},"older_woman_tone2":{"unicode":"1f475-1f3fc","unicode_alternates":"","name":"older woman tone 2","shortname":":older_woman_tone2:","category":"people","emoji_order":"1461","aliases":[":grandma_tone2:"],"aliases_ascii":[],"keywords":[]},"older_woman_tone3":{"unicode":"1f475-1f3fd","unicode_alternates":"","name":"older woman tone 3","shortname":":older_woman_tone3:","category":"people","emoji_order":"1462","aliases":[":grandma_tone3:"],"aliases_ascii":[],"keywords":[]},"older_woman_tone4":{"unicode":"1f475-1f3fe","unicode_alternates":"","name":"older woman tone 4","shortname":":older_woman_tone4:","category":"people","emoji_order":"1463","aliases":[":grandma_tone4:"],"aliases_ascii":[],"keywords":[]},"older_woman_tone5":{"unicode":"1f475-1f3ff","unicode_alternates":"","name":"older woman tone 5","shortname":":older_woman_tone5:","category":"people","emoji_order":"1464","aliases":[":grandma_tone5:"],"aliases_ascii":[],"keywords":[]},"man_with_gua_pi_mao_tone1":{"unicode":"1f472-1f3fb","unicode_alternates":"","name":"man with gua pi mao tone 1","shortname":":man_with_gua_pi_mao_tone1:","category":"people","emoji_order":"1465","aliases":[],"aliases_ascii":[],"keywords":[]},"man_with_gua_pi_mao_tone2":{"unicode":"1f472-1f3fc","unicode_alternates":"","name":"man with gua pi mao tone 2","shortname":":man_with_gua_pi_mao_tone2:","category":"people","emoji_order":"1466","aliases":[],"aliases_ascii":[],"keywords":[]},"man_with_gua_pi_mao_tone3":{"unicode":"1f472-1f3fd","unicode_alternates":"","name":"man with gua pi mao tone 3","shortname":":man_with_gua_pi_mao_tone3:","category":"people","emoji_order":"1467","aliases":[],"aliases_ascii":[],"keywords":[]},"man_with_gua_pi_mao_tone4":{"unicode":"1f472-1f3fe","unicode_alternates":"","name":"man with gua pi mao tone 4","shortname":":man_with_gua_pi_mao_tone4:","category":"people","emoji_order":"1468","aliases":[],"aliases_ascii":[],"keywords":[]},"man_with_gua_pi_mao_tone5":{"unicode":"1f472-1f3ff","unicode_alternates":"","name":"man with gua pi mao tone 5","shortname":":man_with_gua_pi_mao_tone5:","category":"people","emoji_order":"1469","aliases":[],"aliases_ascii":[],"keywords":[]},"man_with_turban_tone1":{"unicode":"1f473-1f3fb","unicode_alternates":"","name":"man with turban tone 1","shortname":":man_with_turban_tone1:","category":"people","emoji_order":"1470","aliases":[],"aliases_ascii":[],"keywords":[]},"man_with_turban_tone2":{"unicode":"1f473-1f3fc","unicode_alternates":"","name":"man with turban tone 2","shortname":":man_with_turban_tone2:","category":"people","emoji_order":"1471","aliases":[],"aliases_ascii":[],"keywords":[]},"man_with_turban_tone3":{"unicode":"1f473-1f3fd","unicode_alternates":"","name":"man with turban tone 3","shortname":":man_with_turban_tone3:","category":"people","emoji_order":"1472","aliases":[],"aliases_ascii":[],"keywords":[]},"man_with_turban_tone4":{"unicode":"1f473-1f3fe","unicode_alternates":"","name":"man with turban tone 4","shortname":":man_with_turban_tone4:","category":"people","emoji_order":"1473","aliases":[],"aliases_ascii":[],"keywords":[]},"man_with_turban_tone5":{"unicode":"1f473-1f3ff","unicode_alternates":"","name":"man with turban tone 5","shortname":":man_with_turban_tone5:","category":"people","emoji_order":"1474","aliases":[],"aliases_ascii":[],"keywords":[]},"cop_tone1":{"unicode":"1f46e-1f3fb","unicode_alternates":"","name":"police officer tone 1","shortname":":cop_tone1:","category":"people","emoji_order":"1475","aliases":[],"aliases_ascii":[],"keywords":[]},"cop_tone2":{"unicode":"1f46e-1f3fc","unicode_alternates":"","name":"police officer tone 2","shortname":":cop_tone2:","category":"people","emoji_order":"1476","aliases":[],"aliases_ascii":[],"keywords":[]},"cop_tone3":{"unicode":"1f46e-1f3fd","unicode_alternates":"","name":"police officer tone 3","shortname":":cop_tone3:","category":"people","emoji_order":"1477","aliases":[],"aliases_ascii":[],"keywords":[]},"cop_tone4":{"unicode":"1f46e-1f3fe","unicode_alternates":"","name":"police officer tone 4","shortname":":cop_tone4:","category":"people","emoji_order":"1478","aliases":[],"aliases_ascii":[],"keywords":[]},"cop_tone5":{"unicode":"1f46e-1f3ff","unicode_alternates":"","name":"police officer tone 5","shortname":":cop_tone5:","category":"people","emoji_order":"1479","aliases":[],"aliases_ascii":[],"keywords":[]},"construction_worker_tone1":{"unicode":"1f477-1f3fb","unicode_alternates":"","name":"construction worker tone 1","shortname":":construction_worker_tone1:","category":"people","emoji_order":"1480","aliases":[],"aliases_ascii":[],"keywords":[]},"construction_worker_tone2":{"unicode":"1f477-1f3fc","unicode_alternates":"","name":"construction worker tone 2","shortname":":construction_worker_tone2:","category":"people","emoji_order":"1481","aliases":[],"aliases_ascii":[],"keywords":[]},"construction_worker_tone3":{"unicode":"1f477-1f3fd","unicode_alternates":"","name":"construction worker tone 3","shortname":":construction_worker_tone3:","category":"people","emoji_order":"1482","aliases":[],"aliases_ascii":[],"keywords":[]},"construction_worker_tone4":{"unicode":"1f477-1f3fe","unicode_alternates":"","name":"construction worker tone 4","shortname":":construction_worker_tone4:","category":"people","emoji_order":"1483","aliases":[],"aliases_ascii":[],"keywords":[]},"construction_worker_tone5":{"unicode":"1f477-1f3ff","unicode_alternates":"","name":"construction worker tone 5","shortname":":construction_worker_tone5:","category":"people","emoji_order":"1484","aliases":[],"aliases_ascii":[],"keywords":[]},"guardsman_tone1":{"unicode":"1f482-1f3fb","unicode_alternates":"","name":"guardsman tone 1","shortname":":guardsman_tone1:","category":"people","emoji_order":"1485","aliases":[],"aliases_ascii":[],"keywords":[]},"guardsman_tone2":{"unicode":"1f482-1f3fc","unicode_alternates":"","name":"guardsman tone 2","shortname":":guardsman_tone2:","category":"people","emoji_order":"1486","aliases":[],"aliases_ascii":[],"keywords":[]},"guardsman_tone3":{"unicode":"1f482-1f3fd","unicode_alternates":"","name":"guardsman tone 3","shortname":":guardsman_tone3:","category":"people","emoji_order":"1487","aliases":[],"aliases_ascii":[],"keywords":[]},"guardsman_tone4":{"unicode":"1f482-1f3fe","unicode_alternates":"","name":"guardsman tone 4","shortname":":guardsman_tone4:","category":"people","emoji_order":"1488","aliases":[],"aliases_ascii":[],"keywords":[]},"guardsman_tone5":{"unicode":"1f482-1f3ff","unicode_alternates":"","name":"guardsman tone 5","shortname":":guardsman_tone5:","category":"people","emoji_order":"1489","aliases":[],"aliases_ascii":[],"keywords":[]},"santa_tone1":{"unicode":"1f385-1f3fb","unicode_alternates":"","name":"father christmas tone 1","shortname":":santa_tone1:","category":"people","emoji_order":"1490","aliases":[],"aliases_ascii":[],"keywords":[]},"santa_tone2":{"unicode":"1f385-1f3fc","unicode_alternates":"","name":"father christmas tone 2","shortname":":santa_tone2:","category":"people","emoji_order":"1491","aliases":[],"aliases_ascii":[],"keywords":[]},"santa_tone3":{"unicode":"1f385-1f3fd","unicode_alternates":"","name":"father christmas tone 3","shortname":":santa_tone3:","category":"people","emoji_order":"1492","aliases":[],"aliases_ascii":[],"keywords":[]},"santa_tone4":{"unicode":"1f385-1f3fe","unicode_alternates":"","name":"father christmas tone 4","shortname":":santa_tone4:","category":"people","emoji_order":"1493","aliases":[],"aliases_ascii":[],"keywords":[]},"santa_tone5":{"unicode":"1f385-1f3ff","unicode_alternates":"","name":"father christmas tone 5","shortname":":santa_tone5:","category":"people","emoji_order":"1494","aliases":[],"aliases_ascii":[],"keywords":[]},"angel_tone1":{"unicode":"1f47c-1f3fb","unicode_alternates":"","name":"baby angel tone 1","shortname":":angel_tone1:","category":"people","emoji_order":"1495","aliases":[],"aliases_ascii":[],"keywords":[]},"angel_tone2":{"unicode":"1f47c-1f3fc","unicode_alternates":"","name":"baby angel tone 2","shortname":":angel_tone2:","category":"people","emoji_order":"1496","aliases":[],"aliases_ascii":[],"keywords":[]},"angel_tone3":{"unicode":"1f47c-1f3fd","unicode_alternates":"","name":"baby angel tone 3","shortname":":angel_tone3:","category":"people","emoji_order":"1497","aliases":[],"aliases_ascii":[],"keywords":[]},"angel_tone4":{"unicode":"1f47c-1f3fe","unicode_alternates":"","name":"baby angel tone 4","shortname":":angel_tone4:","category":"people","emoji_order":"1498","aliases":[],"aliases_ascii":[],"keywords":[]},"angel_tone5":{"unicode":"1f47c-1f3ff","unicode_alternates":"","name":"baby angel tone 5","shortname":":angel_tone5:","category":"people","emoji_order":"1499","aliases":[],"aliases_ascii":[],"keywords":[]},"princess_tone1":{"unicode":"1f478-1f3fb","unicode_alternates":"","name":"princess tone 1","shortname":":princess_tone1:","category":"people","emoji_order":"1500","aliases":[],"aliases_ascii":[],"keywords":[]},"princess_tone2":{"unicode":"1f478-1f3fc","unicode_alternates":"","name":"princess tone 2","shortname":":princess_tone2:","category":"people","emoji_order":"1501","aliases":[],"aliases_ascii":[],"keywords":[]},"princess_tone3":{"unicode":"1f478-1f3fd","unicode_alternates":"","name":"princess tone 3","shortname":":princess_tone3:","category":"people","emoji_order":"1502","aliases":[],"aliases_ascii":[],"keywords":[]},"princess_tone4":{"unicode":"1f478-1f3fe","unicode_alternates":"","name":"princess tone 4","shortname":":princess_tone4:","category":"people","emoji_order":"1503","aliases":[],"aliases_ascii":[],"keywords":[]},"princess_tone5":{"unicode":"1f478-1f3ff","unicode_alternates":"","name":"princess tone 5","shortname":":princess_tone5:","category":"people","emoji_order":"1504","aliases":[],"aliases_ascii":[],"keywords":[]},"bride_with_veil_tone1":{"unicode":"1f470-1f3fb","unicode_alternates":"","name":"bride with veil tone 1","shortname":":bride_with_veil_tone1:","category":"people","emoji_order":"1505","aliases":[],"aliases_ascii":[],"keywords":[]},"bride_with_veil_tone2":{"unicode":"1f470-1f3fc","unicode_alternates":"","name":"bride with veil tone 2","shortname":":bride_with_veil_tone2:","category":"people","emoji_order":"1506","aliases":[],"aliases_ascii":[],"keywords":[]},"bride_with_veil_tone3":{"unicode":"1f470-1f3fd","unicode_alternates":"","name":"bride with veil tone 3","shortname":":bride_with_veil_tone3:","category":"people","emoji_order":"1507","aliases":[],"aliases_ascii":[],"keywords":[]},"bride_with_veil_tone4":{"unicode":"1f470-1f3fe","unicode_alternates":"","name":"bride with veil tone 4","shortname":":bride_with_veil_tone4:","category":"people","emoji_order":"1508","aliases":[],"aliases_ascii":[],"keywords":[]},"bride_with_veil_tone5":{"unicode":"1f470-1f3ff","unicode_alternates":"","name":"bride with veil tone 5","shortname":":bride_with_veil_tone5:","category":"people","emoji_order":"1509","aliases":[],"aliases_ascii":[],"keywords":[]},"walking_tone1":{"unicode":"1f6b6-1f3fb","unicode_alternates":"","name":"pedestrian tone 1","shortname":":walking_tone1:","category":"people","emoji_order":"1510","aliases":[],"aliases_ascii":[],"keywords":[]},"walking_tone2":{"unicode":"1f6b6-1f3fc","unicode_alternates":"","name":"pedestrian tone 2","shortname":":walking_tone2:","category":"people","emoji_order":"1511","aliases":[],"aliases_ascii":[],"keywords":[]},"walking_tone3":{"unicode":"1f6b6-1f3fd","unicode_alternates":"","name":"pedestrian tone 3","shortname":":walking_tone3:","category":"people","emoji_order":"1512","aliases":[],"aliases_ascii":[],"keywords":[]},"walking_tone4":{"unicode":"1f6b6-1f3fe","unicode_alternates":"","name":"pedestrian tone 4","shortname":":walking_tone4:","category":"people","emoji_order":"1513","aliases":[],"aliases_ascii":[],"keywords":[]},"walking_tone5":{"unicode":"1f6b6-1f3ff","unicode_alternates":"","name":"pedestrian tone 5","shortname":":walking_tone5:","category":"people","emoji_order":"1514","aliases":[],"aliases_ascii":[],"keywords":[]},"runner_tone1":{"unicode":"1f3c3-1f3fb","unicode_alternates":"","name":"runner tone 1","shortname":":runner_tone1:","category":"people","emoji_order":"1515","aliases":[],"aliases_ascii":[],"keywords":[]},"runner_tone2":{"unicode":"1f3c3-1f3fc","unicode_alternates":"","name":"runner tone 2","shortname":":runner_tone2:","category":"people","emoji_order":"1516","aliases":[],"aliases_ascii":[],"keywords":[]},"runner_tone3":{"unicode":"1f3c3-1f3fd","unicode_alternates":"","name":"runner tone 3","shortname":":runner_tone3:","category":"people","emoji_order":"1517","aliases":[],"aliases_ascii":[],"keywords":[]},"runner_tone4":{"unicode":"1f3c3-1f3fe","unicode_alternates":"","name":"runner tone 4","shortname":":runner_tone4:","category":"people","emoji_order":"1518","aliases":[],"aliases_ascii":[],"keywords":[]},"runner_tone5":{"unicode":"1f3c3-1f3ff","unicode_alternates":"","name":"runner tone 5","shortname":":runner_tone5:","category":"people","emoji_order":"1519","aliases":[],"aliases_ascii":[],"keywords":[]},"dancer_tone1":{"unicode":"1f483-1f3fb","unicode_alternates":"","name":"dancer tone 1","shortname":":dancer_tone1:","category":"people","emoji_order":"1520","aliases":[],"aliases_ascii":[],"keywords":[]},"dancer_tone2":{"unicode":"1f483-1f3fc","unicode_alternates":"","name":"dancer tone 2","shortname":":dancer_tone2:","category":"people","emoji_order":"1521","aliases":[],"aliases_ascii":[],"keywords":[]},"dancer_tone3":{"unicode":"1f483-1f3fd","unicode_alternates":"","name":"dancer tone 3","shortname":":dancer_tone3:","category":"people","emoji_order":"1522","aliases":[],"aliases_ascii":[],"keywords":[]},"dancer_tone4":{"unicode":"1f483-1f3fe","unicode_alternates":"","name":"dancer tone 4","shortname":":dancer_tone4:","category":"people","emoji_order":"1523","aliases":[],"aliases_ascii":[],"keywords":[]},"dancer_tone5":{"unicode":"1f483-1f3ff","unicode_alternates":"","name":"dancer tone 5","shortname":":dancer_tone5:","category":"people","emoji_order":"1524","aliases":[],"aliases_ascii":[],"keywords":[]},"bow_tone1":{"unicode":"1f647-1f3fb","unicode_alternates":"","name":"person bowing deeply tone 1","shortname":":bow_tone1:","category":"people","emoji_order":"1525","aliases":[],"aliases_ascii":[],"keywords":[]},"bow_tone2":{"unicode":"1f647-1f3fc","unicode_alternates":"","name":"person bowing deeply tone 2","shortname":":bow_tone2:","category":"people","emoji_order":"1526","aliases":[],"aliases_ascii":[],"keywords":[]},"bow_tone3":{"unicode":"1f647-1f3fd","unicode_alternates":"","name":"person bowing deeply tone 3","shortname":":bow_tone3:","category":"people","emoji_order":"1527","aliases":[],"aliases_ascii":[],"keywords":[]},"bow_tone4":{"unicode":"1f647-1f3fe","unicode_alternates":"","name":"person bowing deeply tone 4","shortname":":bow_tone4:","category":"people","emoji_order":"1528","aliases":[],"aliases_ascii":[],"keywords":[]},"bow_tone5":{"unicode":"1f647-1f3ff","unicode_alternates":"","name":"person bowing deeply tone 5","shortname":":bow_tone5:","category":"people","emoji_order":"1529","aliases":[],"aliases_ascii":[],"keywords":[]},"information_desk_person_tone1":{"unicode":"1f481-1f3fb","unicode_alternates":"","name":"information desk person tone 1","shortname":":information_desk_person_tone1:","category":"people","emoji_order":"1530","aliases":[],"aliases_ascii":[],"keywords":[]},"information_desk_person_tone2":{"unicode":"1f481-1f3fc","unicode_alternates":"","name":"information desk person tone 2","shortname":":information_desk_person_tone2:","category":"people","emoji_order":"1531","aliases":[],"aliases_ascii":[],"keywords":[]},"information_desk_person_tone3":{"unicode":"1f481-1f3fd","unicode_alternates":"","name":"information desk person tone 3","shortname":":information_desk_person_tone3:","category":"people","emoji_order":"1532","aliases":[],"aliases_ascii":[],"keywords":[]},"information_desk_person_tone4":{"unicode":"1f481-1f3fe","unicode_alternates":"","name":"information desk person tone 4","shortname":":information_desk_person_tone4:","category":"people","emoji_order":"1533","aliases":[],"aliases_ascii":[],"keywords":[]},"information_desk_person_tone5":{"unicode":"1f481-1f3ff","unicode_alternates":"","name":"information desk person tone 5","shortname":":information_desk_person_tone5:","category":"people","emoji_order":"1534","aliases":[],"aliases_ascii":[],"keywords":[]},"no_good_tone1":{"unicode":"1f645-1f3fb","unicode_alternates":"","name":"face with no good gesture tone 1","shortname":":no_good_tone1:","category":"people","emoji_order":"1535","aliases":[],"aliases_ascii":[],"keywords":[]},"no_good_tone2":{"unicode":"1f645-1f3fc","unicode_alternates":"","name":"face with no good gesture tone 2","shortname":":no_good_tone2:","category":"people","emoji_order":"1536","aliases":[],"aliases_ascii":[],"keywords":[]},"no_good_tone3":{"unicode":"1f645-1f3fd","unicode_alternates":"","name":"face with no good gesture tone 3","shortname":":no_good_tone3:","category":"people","emoji_order":"1537","aliases":[],"aliases_ascii":[],"keywords":[]},"no_good_tone4":{"unicode":"1f645-1f3fe","unicode_alternates":"","name":"face with no good gesture tone 4","shortname":":no_good_tone4:","category":"people","emoji_order":"1538","aliases":[],"aliases_ascii":[],"keywords":[]},"no_good_tone5":{"unicode":"1f645-1f3ff","unicode_alternates":"","name":"face with no good gesture tone 5","shortname":":no_good_tone5:","category":"people","emoji_order":"1539","aliases":[],"aliases_ascii":[],"keywords":[]},"ok_woman_tone1":{"unicode":"1f646-1f3fb","unicode_alternates":"","name":"face with ok gesture tone1","shortname":":ok_woman_tone1:","category":"people","emoji_order":"1540","aliases":[],"aliases_ascii":[],"keywords":[]},"ok_woman_tone2":{"unicode":"1f646-1f3fc","unicode_alternates":"","name":"face with ok gesture tone2","shortname":":ok_woman_tone2:","category":"people","emoji_order":"1541","aliases":[],"aliases_ascii":[],"keywords":[]},"ok_woman_tone3":{"unicode":"1f646-1f3fd","unicode_alternates":"","name":"face with ok gesture tone3","shortname":":ok_woman_tone3:","category":"people","emoji_order":"1542","aliases":[],"aliases_ascii":[],"keywords":[]},"ok_woman_tone4":{"unicode":"1f646-1f3fe","unicode_alternates":"","name":"face with ok gesture tone4","shortname":":ok_woman_tone4:","category":"people","emoji_order":"1543","aliases":[],"aliases_ascii":[],"keywords":[]},"ok_woman_tone5":{"unicode":"1f646-1f3ff","unicode_alternates":"","name":"face with ok gesture tone5","shortname":":ok_woman_tone5:","category":"people","emoji_order":"1544","aliases":[],"aliases_ascii":[],"keywords":[]},"raising_hand_tone1":{"unicode":"1f64b-1f3fb","unicode_alternates":"","name":"happy person raising one hand tone1","shortname":":raising_hand_tone1:","category":"people","emoji_order":"1545","aliases":[],"aliases_ascii":[],"keywords":[]},"raising_hand_tone2":{"unicode":"1f64b-1f3fc","unicode_alternates":"","name":"happy person raising one hand tone2","shortname":":raising_hand_tone2:","category":"people","emoji_order":"1546","aliases":[],"aliases_ascii":[],"keywords":[]},"raising_hand_tone3":{"unicode":"1f64b-1f3fd","unicode_alternates":"","name":"happy person raising one hand tone3","shortname":":raising_hand_tone3:","category":"people","emoji_order":"1547","aliases":[],"aliases_ascii":[],"keywords":[]},"raising_hand_tone4":{"unicode":"1f64b-1f3fe","unicode_alternates":"","name":"happy person raising one hand tone4","shortname":":raising_hand_tone4:","category":"people","emoji_order":"1548","aliases":[],"aliases_ascii":[],"keywords":[]},"raising_hand_tone5":{"unicode":"1f64b-1f3ff","unicode_alternates":"","name":"happy person raising one hand tone5","shortname":":raising_hand_tone5:","category":"people","emoji_order":"1549","aliases":[],"aliases_ascii":[],"keywords":[]},"person_with_pouting_face_tone1":{"unicode":"1f64e-1f3fb","unicode_alternates":"","name":"person with pouting face tone1","shortname":":person_with_pouting_face_tone1:","category":"people","emoji_order":"1550","aliases":[],"aliases_ascii":[],"keywords":[]},"person_with_pouting_face_tone2":{"unicode":"1f64e-1f3fc","unicode_alternates":"","name":"person with pouting face tone2","shortname":":person_with_pouting_face_tone2:","category":"people","emoji_order":"1551","aliases":[],"aliases_ascii":[],"keywords":[]},"person_with_pouting_face_tone3":{"unicode":"1f64e-1f3fd","unicode_alternates":"","name":"person with pouting face tone3","shortname":":person_with_pouting_face_tone3:","category":"people","emoji_order":"1552","aliases":[],"aliases_ascii":[],"keywords":[]},"person_with_pouting_face_tone4":{"unicode":"1f64e-1f3fe","unicode_alternates":"","name":"person with pouting face tone4","shortname":":person_with_pouting_face_tone4:","category":"people","emoji_order":"1553","aliases":[],"aliases_ascii":[],"keywords":[]},"person_with_pouting_face_tone5":{"unicode":"1f64e-1f3ff","unicode_alternates":"","name":"person with pouting face tone5","shortname":":person_with_pouting_face_tone5:","category":"people","emoji_order":"1554","aliases":[],"aliases_ascii":[],"keywords":[]},"person_frowning_tone1":{"unicode":"1f64d-1f3fb","unicode_alternates":"","name":"person frowning tone 1","shortname":":person_frowning_tone1:","category":"people","emoji_order":"1555","aliases":[],"aliases_ascii":[],"keywords":[]},"person_frowning_tone2":{"unicode":"1f64d-1f3fc","unicode_alternates":"","name":"person frowning tone 2","shortname":":person_frowning_tone2:","category":"people","emoji_order":"1556","aliases":[],"aliases_ascii":[],"keywords":[]},"person_frowning_tone3":{"unicode":"1f64d-1f3fd","unicode_alternates":"","name":"person frowning tone 3","shortname":":person_frowning_tone3:","category":"people","emoji_order":"1557","aliases":[],"aliases_ascii":[],"keywords":[]},"person_frowning_tone4":{"unicode":"1f64d-1f3fe","unicode_alternates":"","name":"person frowning tone 4","shortname":":person_frowning_tone4:","category":"people","emoji_order":"1558","aliases":[],"aliases_ascii":[],"keywords":[]},"person_frowning_tone5":{"unicode":"1f64d-1f3ff","unicode_alternates":"","name":"person frowning tone 5","shortname":":person_frowning_tone5:","category":"people","emoji_order":"1559","aliases":[],"aliases_ascii":[],"keywords":[]},"haircut_tone1":{"unicode":"1f487-1f3fb","unicode_alternates":"","name":"haircut tone 1","shortname":":haircut_tone1:","category":"people","emoji_order":"1560","aliases":[],"aliases_ascii":[],"keywords":[]},"haircut_tone2":{"unicode":"1f487-1f3fc","unicode_alternates":"","name":"haircut tone 2","shortname":":haircut_tone2:","category":"people","emoji_order":"1561","aliases":[],"aliases_ascii":[],"keywords":[]},"haircut_tone3":{"unicode":"1f487-1f3fd","unicode_alternates":"","name":"haircut tone 3","shortname":":haircut_tone3:","category":"people","emoji_order":"1562","aliases":[],"aliases_ascii":[],"keywords":[]},"haircut_tone4":{"unicode":"1f487-1f3fe","unicode_alternates":"","name":"haircut tone 4","shortname":":haircut_tone4:","category":"people","emoji_order":"1563","aliases":[],"aliases_ascii":[],"keywords":[]},"haircut_tone5":{"unicode":"1f487-1f3ff","unicode_alternates":"","name":"haircut tone 5","shortname":":haircut_tone5:","category":"people","emoji_order":"1564","aliases":[],"aliases_ascii":[],"keywords":[]},"massage_tone1":{"unicode":"1f486-1f3fb","unicode_alternates":"","name":"face massage tone 1","shortname":":massage_tone1:","category":"people","emoji_order":"1565","aliases":[],"aliases_ascii":[],"keywords":[]},"massage_tone2":{"unicode":"1f486-1f3fc","unicode_alternates":"","name":"face massage tone 2","shortname":":massage_tone2:","category":"people","emoji_order":"1566","aliases":[],"aliases_ascii":[],"keywords":[]},"massage_tone3":{"unicode":"1f486-1f3fd","unicode_alternates":"","name":"face massage tone 3","shortname":":massage_tone3:","category":"people","emoji_order":"1567","aliases":[],"aliases_ascii":[],"keywords":[]},"massage_tone4":{"unicode":"1f486-1f3fe","unicode_alternates":"","name":"face massage tone 4","shortname":":massage_tone4:","category":"people","emoji_order":"1568","aliases":[],"aliases_ascii":[],"keywords":[]},"massage_tone5":{"unicode":"1f486-1f3ff","unicode_alternates":"","name":"face massage tone 5","shortname":":massage_tone5:","category":"people","emoji_order":"1569","aliases":[],"aliases_ascii":[],"keywords":[]},"rowboat_tone1":{"unicode":"1f6a3-1f3fb","unicode_alternates":"","name":"rowboat tone 1","shortname":":rowboat_tone1:","category":"activity","emoji_order":"1570","aliases":[],"aliases_ascii":[],"keywords":[]},"rowboat_tone2":{"unicode":"1f6a3-1f3fc","unicode_alternates":"","name":"rowboat tone 2","shortname":":rowboat_tone2:","category":"activity","emoji_order":"1571","aliases":[],"aliases_ascii":[],"keywords":[]},"rowboat_tone3":{"unicode":"1f6a3-1f3fd","unicode_alternates":"","name":"rowboat tone 3","shortname":":rowboat_tone3:","category":"activity","emoji_order":"1572","aliases":[],"aliases_ascii":[],"keywords":[]},"rowboat_tone4":{"unicode":"1f6a3-1f3fe","unicode_alternates":"","name":"rowboat tone 4","shortname":":rowboat_tone4:","category":"activity","emoji_order":"1573","aliases":[],"aliases_ascii":[],"keywords":[]},"rowboat_tone5":{"unicode":"1f6a3-1f3ff","unicode_alternates":"","name":"rowboat tone 5","shortname":":rowboat_tone5:","category":"activity","emoji_order":"1574","aliases":[],"aliases_ascii":[],"keywords":[]},"swimmer_tone1":{"unicode":"1f3ca-1f3fb","unicode_alternates":"","name":"swimmer tone 1","shortname":":swimmer_tone1:","category":"activity","emoji_order":"1575","aliases":[],"aliases_ascii":[],"keywords":[]},"swimmer_tone2":{"unicode":"1f3ca-1f3fc","unicode_alternates":"","name":"swimmer tone 2","shortname":":swimmer_tone2:","category":"activity","emoji_order":"1576","aliases":[],"aliases_ascii":[],"keywords":[]},"swimmer_tone3":{"unicode":"1f3ca-1f3fd","unicode_alternates":"","name":"swimmer tone 3","shortname":":swimmer_tone3:","category":"activity","emoji_order":"1577","aliases":[],"aliases_ascii":[],"keywords":[]},"swimmer_tone4":{"unicode":"1f3ca-1f3fe","unicode_alternates":"","name":"swimmer tone 4","shortname":":swimmer_tone4:","category":"activity","emoji_order":"1578","aliases":[],"aliases_ascii":[],"keywords":[]},"swimmer_tone5":{"unicode":"1f3ca-1f3ff","unicode_alternates":"","name":"swimmer tone 5","shortname":":swimmer_tone5:","category":"activity","emoji_order":"1579","aliases":[],"aliases_ascii":[],"keywords":[]},"surfer_tone1":{"unicode":"1f3c4-1f3fb","unicode_alternates":"","name":"surfer tone 1","shortname":":surfer_tone1:","category":"activity","emoji_order":"1580","aliases":[],"aliases_ascii":[],"keywords":[]},"surfer_tone2":{"unicode":"1f3c4-1f3fc","unicode_alternates":"","name":"surfer tone 2","shortname":":surfer_tone2:","category":"activity","emoji_order":"1581","aliases":[],"aliases_ascii":[],"keywords":[]},"surfer_tone3":{"unicode":"1f3c4-1f3fd","unicode_alternates":"","name":"surfer tone 3","shortname":":surfer_tone3:","category":"activity","emoji_order":"1582","aliases":[],"aliases_ascii":[],"keywords":[]},"surfer_tone4":{"unicode":"1f3c4-1f3fe","unicode_alternates":"","name":"surfer tone 4","shortname":":surfer_tone4:","category":"activity","emoji_order":"1583","aliases":[],"aliases_ascii":[],"keywords":[]},"surfer_tone5":{"unicode":"1f3c4-1f3ff","unicode_alternates":"","name":"surfer tone 5","shortname":":surfer_tone5:","category":"activity","emoji_order":"1584","aliases":[],"aliases_ascii":[],"keywords":[]},"bath_tone1":{"unicode":"1f6c0-1f3fb","unicode_alternates":"","name":"bath tone 1","shortname":":bath_tone1:","category":"activity","emoji_order":"1585","aliases":[],"aliases_ascii":[],"keywords":[]},"bath_tone2":{"unicode":"1f6c0-1f3fc","unicode_alternates":"","name":"bath tone 2","shortname":":bath_tone2:","category":"activity","emoji_order":"1586","aliases":[],"aliases_ascii":[],"keywords":[]},"bath_tone3":{"unicode":"1f6c0-1f3fd","unicode_alternates":"","name":"bath tone 3","shortname":":bath_tone3:","category":"activity","emoji_order":"1587","aliases":[],"aliases_ascii":[],"keywords":[]},"bath_tone4":{"unicode":"1f6c0-1f3fe","unicode_alternates":"","name":"bath tone 4","shortname":":bath_tone4:","category":"activity","emoji_order":"1588","aliases":[],"aliases_ascii":[],"keywords":[]},"bath_tone5":{"unicode":"1f6c0-1f3ff","unicode_alternates":"","name":"bath tone 5","shortname":":bath_tone5:","category":"activity","emoji_order":"1589","aliases":[],"aliases_ascii":[],"keywords":[]},"basketball_player_tone1":{"unicode":"26f9-1f3fb","unicode_alternates":"","name":"person with ball tone 1","shortname":":basketball_player_tone1:","category":"activity","emoji_order":"1590","aliases":[":person_with_ball_tone1:"],"aliases_ascii":[],"keywords":[]},"basketball_player_tone2":{"unicode":"26f9-1f3fc","unicode_alternates":"","name":"person with ball tone 2","shortname":":basketball_player_tone2:","category":"activity","emoji_order":"1591","aliases":[":person_with_ball_tone2:"],"aliases_ascii":[],"keywords":[]},"basketball_player_tone3":{"unicode":"26f9-1f3fd","unicode_alternates":"","name":"person with ball tone 3","shortname":":basketball_player_tone3:","category":"activity","emoji_order":"1592","aliases":[":person_with_ball_tone3:"],"aliases_ascii":[],"keywords":[]},"basketball_player_tone4":{"unicode":"26f9-1f3fe","unicode_alternates":"","name":"person with ball tone 4","shortname":":basketball_player_tone4:","category":"activity","emoji_order":"1593","aliases":[":person_with_ball_tone4:"],"aliases_ascii":[],"keywords":[]},"basketball_player_tone5":{"unicode":"26f9-1f3ff","unicode_alternates":"","name":"person with ball tone 5","shortname":":basketball_player_tone5:","category":"activity","emoji_order":"1594","aliases":[":person_with_ball_tone5:"],"aliases_ascii":[],"keywords":[]},"lifter_tone1":{"unicode":"1f3cb-1f3fb","unicode_alternates":"","name":"weight lifter tone 1","shortname":":lifter_tone1:","category":"activity","emoji_order":"1595","aliases":[":weight_lifter_tone1:"],"aliases_ascii":[],"keywords":[]},"lifter_tone2":{"unicode":"1f3cb-1f3fc","unicode_alternates":"","name":"weight lifter tone 2","shortname":":lifter_tone2:","category":"activity","emoji_order":"1596","aliases":[":weight_lifter_tone2:"],"aliases_ascii":[],"keywords":[]},"lifter_tone3":{"unicode":"1f3cb-1f3fd","unicode_alternates":"","name":"weight lifter tone 3","shortname":":lifter_tone3:","category":"activity","emoji_order":"1597","aliases":[":weight_lifter_tone3:"],"aliases_ascii":[],"keywords":[]},"lifter_tone4":{"unicode":"1f3cb-1f3fe","unicode_alternates":"","name":"weight lifter tone 4","shortname":":lifter_tone4:","category":"activity","emoji_order":"1598","aliases":[":weight_lifter_tone4:"],"aliases_ascii":[],"keywords":[]},"lifter_tone5":{"unicode":"1f3cb-1f3ff","unicode_alternates":"","name":"weight lifter tone 5","shortname":":lifter_tone5:","category":"activity","emoji_order":"1599","aliases":[":weight_lifter_tone5:"],"aliases_ascii":[],"keywords":[]},"bicyclist_tone1":{"unicode":"1f6b4-1f3fb","unicode_alternates":"","name":"bicyclist tone 1","shortname":":bicyclist_tone1:","category":"activity","emoji_order":"1600","aliases":[],"aliases_ascii":[],"keywords":[]},"bicyclist_tone2":{"unicode":"1f6b4-1f3fc","unicode_alternates":"","name":"bicyclist tone 2","shortname":":bicyclist_tone2:","category":"activity","emoji_order":"1601","aliases":[],"aliases_ascii":[],"keywords":[]},"bicyclist_tone3":{"unicode":"1f6b4-1f3fd","unicode_alternates":"","name":"bicyclist tone 3","shortname":":bicyclist_tone3:","category":"activity","emoji_order":"1602","aliases":[],"aliases_ascii":[],"keywords":[]},"bicyclist_tone4":{"unicode":"1f6b4-1f3fe","unicode_alternates":"","name":"bicyclist tone 4","shortname":":bicyclist_tone4:","category":"activity","emoji_order":"1603","aliases":[],"aliases_ascii":[],"keywords":[]},"bicyclist_tone5":{"unicode":"1f6b4-1f3ff","unicode_alternates":"","name":"bicyclist tone 5","shortname":":bicyclist_tone5:","category":"activity","emoji_order":"1604","aliases":[],"aliases_ascii":[],"keywords":[]},"mountain_bicyclist_tone1":{"unicode":"1f6b5-1f3fb","unicode_alternates":"","name":"mountain bicyclist tone 1","shortname":":mountain_bicyclist_tone1:","category":"activity","emoji_order":"1605","aliases":[],"aliases_ascii":[],"keywords":[]},"mountain_bicyclist_tone2":{"unicode":"1f6b5-1f3fc","unicode_alternates":"","name":"mountain bicyclist tone 2","shortname":":mountain_bicyclist_tone2:","category":"activity","emoji_order":"1606","aliases":[],"aliases_ascii":[],"keywords":[]},"mountain_bicyclist_tone3":{"unicode":"1f6b5-1f3fd","unicode_alternates":"","name":"mountain bicyclist tone 3","shortname":":mountain_bicyclist_tone3:","category":"activity","emoji_order":"1607","aliases":[],"aliases_ascii":[],"keywords":[]},"mountain_bicyclist_tone4":{"unicode":"1f6b5-1f3fe","unicode_alternates":"","name":"mountain bicyclist tone 4","shortname":":mountain_bicyclist_tone4:","category":"activity","emoji_order":"1608","aliases":[],"aliases_ascii":[],"keywords":[]},"mountain_bicyclist_tone5":{"unicode":"1f6b5-1f3ff","unicode_alternates":"","name":"mountain bicyclist tone 5","shortname":":mountain_bicyclist_tone5:","category":"activity","emoji_order":"1609","aliases":[],"aliases_ascii":[],"keywords":[]},"horse_racing_tone1":{"unicode":"1f3c7-1f3fb","unicode_alternates":"","name":"horse racing tone 1","shortname":":horse_racing_tone1:","category":"activity","emoji_order":"1610","aliases":[],"aliases_ascii":[],"keywords":[]},"horse_racing_tone2":{"unicode":"1f3c7-1f3fc","unicode_alternates":"","name":"horse racing tone 2","shortname":":horse_racing_tone2:","category":"activity","emoji_order":"1611","aliases":[],"aliases_ascii":[],"keywords":[]},"horse_racing_tone3":{"unicode":"1f3c7-1f3fd","unicode_alternates":"","name":"horse racing tone 3","shortname":":horse_racing_tone3:","category":"activity","emoji_order":"1612","aliases":[],"aliases_ascii":[],"keywords":[]},"horse_racing_tone4":{"unicode":"1f3c7-1f3fe","unicode_alternates":"","name":"horse racing tone 4","shortname":":horse_racing_tone4:","category":"activity","emoji_order":"1613","aliases":[],"aliases_ascii":[],"keywords":[]},"horse_racing_tone5":{"unicode":"1f3c7-1f3ff","unicode_alternates":"","name":"horse racing tone 5","shortname":":horse_racing_tone5:","category":"activity","emoji_order":"1614","aliases":[],"aliases_ascii":[],"keywords":[]},"spy_tone1":{"unicode":"1f575-1f3fb","unicode_alternates":"","name":"sleuth or spy tone 1","shortname":":spy_tone1:","category":"people","emoji_order":"1615","aliases":[":sleuth_or_spy_tone1:"],"aliases_ascii":[],"keywords":[]},"spy_tone2":{"unicode":"1f575-1f3fc","unicode_alternates":"","name":"sleuth or spy tone 2","shortname":":spy_tone2:","category":"people","emoji_order":"1616","aliases":[":sleuth_or_spy_tone2:"],"aliases_ascii":[],"keywords":[]},"spy_tone3":{"unicode":"1f575-1f3fd","unicode_alternates":"","name":"sleuth or spy tone 3","shortname":":spy_tone3:","category":"people","emoji_order":"1617","aliases":[":sleuth_or_spy_tone3:"],"aliases_ascii":[],"keywords":[]},"spy_tone4":{"unicode":"1f575-1f3fe","unicode_alternates":"","name":"sleuth or spy tone 4","shortname":":spy_tone4:","category":"people","emoji_order":"1618","aliases":[":sleuth_or_spy_tone4:"],"aliases_ascii":[],"keywords":[]},"spy_tone5":{"unicode":"1f575-1f3ff","unicode_alternates":"","name":"sleuth or spy tone 5","shortname":":spy_tone5:","category":"people","emoji_order":"1619","aliases":[":sleuth_or_spy_tone5:"],"aliases_ascii":[],"keywords":[]},"tone1":{"unicode":"1f3fb","unicode_alternates":"","name":"emoji modifier Fitzpatrick type-1-2","shortname":":tone1:","category":"modifier","emoji_order":"1620","aliases":[],"aliases_ascii":[],"keywords":[]},"tone2":{"unicode":"1f3fc","unicode_alternates":"","name":"emoji modifier Fitzpatrick type-3","shortname":":tone2:","category":"modifier","emoji_order":"1621","aliases":[],"aliases_ascii":[],"keywords":[]},"tone3":{"unicode":"1f3fd","unicode_alternates":"","name":"emoji modifier Fitzpatrick type-4","shortname":":tone3:","category":"modifier","emoji_order":"1622","aliases":[],"aliases_ascii":[],"keywords":[]},"tone4":{"unicode":"1f3fe","unicode_alternates":"","name":"emoji modifier Fitzpatrick type-5","shortname":":tone4:","category":"modifier","emoji_order":"1623","aliases":[],"aliases_ascii":[],"keywords":[]},"tone5":{"unicode":"1f3ff","unicode_alternates":"","name":"emoji modifier Fitzpatrick type-6","shortname":":tone5:","category":"modifier","emoji_order":"1624","aliases":[],"aliases_ascii":[],"keywords":[]}} \ No newline at end of file
diff --git a/library/fullcalendar/CHANGELOG.txt b/library/fullcalendar/CHANGELOG.txt
index ed2eddb8a..379f23691 100644
--- a/library/fullcalendar/CHANGELOG.txt
+++ b/library/fullcalendar/CHANGELOG.txt
@@ -1,4 +1,25 @@
+v3.2.0 (2017-02-14)
+-------------------
+
+Features:
+- `selectMinDistance`, threshold before a mouse selection begins (#2428)
+
+Bugfixes:
+- iOS 10, unwanted scrolling while dragging events/selection (#3403)
+- dayClick triggered when swiping on touch devices (#3332)
+- dayClick not functioning on Firefix mobile (#3450)
+- title computed incorrectly for views with no weekends (#2884)
+- unwanted scrollbars in month-view when non-integer width (#3453, #3444)
+- incorrect date formatting for locales with non-standlone month/day names (#3478)
+- date formatting, incorrect omission of trailing period for certain locales (#2504, #3486)
+- formatRange should collapse same week numbers (#3467)
+- Taiwanese locale updated (#3426)
+- Finnish noEventsMessage updated (#3476)
+- Croatian (hr) buttonText is blank (#3270)
+- JSON feed PHP example, date range math bug (#3485)
+
+
v3.1.0 (2016-12-05)
-------------------
diff --git a/library/fullcalendar/fullcalendar.css b/library/fullcalendar/fullcalendar.css
index 5620e0bd6..a2f76c960 100644
--- a/library/fullcalendar/fullcalendar.css
+++ b/library/fullcalendar/fullcalendar.css
@@ -1,7 +1,7 @@
/*!
- * FullCalendar v3.1.0 Stylesheet
- * Docs & License: http://fullcalendar.io/
- * (c) 2016 Adam Shaw
+ * FullCalendar v3.2.0 Stylesheet
+ * Docs & License: https://fullcalendar.io/
+ * (c) 2017 Adam Shaw
*/
diff --git a/library/fullcalendar/fullcalendar.js b/library/fullcalendar/fullcalendar.js
index b7371e25f..04399302b 100644
--- a/library/fullcalendar/fullcalendar.js
+++ b/library/fullcalendar/fullcalendar.js
@@ -1,7 +1,7 @@
/*!
- * FullCalendar v3.1.0
- * Docs & License: http://fullcalendar.io/
- * (c) 2016 Adam Shaw
+ * FullCalendar v3.2.0
+ * Docs & License: https://fullcalendar.io/
+ * (c) 2017 Adam Shaw
*/
(function(factory) {
@@ -19,8 +19,11 @@
;;
var FC = $.fullCalendar = {
- version: "3.1.0",
- internalApiVersion: 7
+ version: "3.2.0",
+ // When introducing internal API incompatibilities (where fullcalendar plugins would break),
+ // the minor version of the calendar should be upped (ex: 2.7.2 -> 2.8.0)
+ // and the below integer should be incremented.
+ internalApiVersion: 8
};
var fcViews = FC.views = {};
@@ -313,12 +316,13 @@ function getContentRect(el, origin) {
// NOTE: should use clientLeft/clientTop, but very unreliable cross-browser.
function getScrollbarWidths(el) {
var leftRightWidth = el.innerWidth() - el[0].clientWidth; // the paddings cancel out, leaving the scrollbars
- var widths = {
- left: 0,
- right: 0,
- top: 0,
- bottom: el.innerHeight() - el[0].clientHeight // the paddings cancel out, leaving the bottom scrollbar
- };
+ var bottomWidth = el.innerHeight() - el[0].clientHeight; // "
+ var widths;
+
+ leftRightWidth = sanitizeScrollbarWidth(leftRightWidth);
+ bottomWidth = sanitizeScrollbarWidth(bottomWidth);
+
+ widths = { left: 0, right: 0, top: 0, bottom: bottomWidth };
if (getIsLeftRtlScrollbars() && el.css('direction') == 'rtl') { // is the scrollbar on the left side?
widths.left = leftRightWidth;
@@ -331,6 +335,15 @@ function getScrollbarWidths(el) {
}
+// The scrollbar width computations in getScrollbarWidths are sometimes flawed when it comes to
+// retina displays, rounding, and IE11. Massage them into a usable value.
+function sanitizeScrollbarWidth(width) {
+ width = Math.max(0, width); // no negatives
+ width = Math.round(width);
+ return width;
+}
+
+
// Logic for determining if, when the element is right-to-left, the scrollbar appears on the left side
var _isLeftRtlScrollbars = null;
@@ -381,24 +394,28 @@ function isPrimaryMouseButton(ev) {
function getEvX(ev) {
- if (ev.pageX !== undefined) {
- return ev.pageX;
- }
var touches = ev.originalEvent.touches;
- if (touches) {
+
+ // on mobile FF, pageX for touch events is present, but incorrect,
+ // so, look at touch coordinates first.
+ if (touches && touches.length) {
return touches[0].pageX;
}
+
+ return ev.pageX;
}
function getEvY(ev) {
- if (ev.pageY !== undefined) {
- return ev.pageY;
- }
var touches = ev.originalEvent.touches;
- if (touches) {
+
+ // on mobile FF, pageX for touch events is present, but incorrect,
+ // so, look at touch coordinates first.
+ if (touches && touches.length) {
return touches[0].pageY;
}
+
+ return ev.pageY;
}
@@ -413,33 +430,15 @@ function preventSelection(el) {
}
-// Stops a mouse/touch event from doing it's native browser action
-function preventDefault(ev) {
- ev.preventDefault();
-}
-
-
-// attach a handler to get called when ANY scroll action happens on the page.
-// this was impossible to do with normal on/off because 'scroll' doesn't bubble.
-// http://stackoverflow.com/a/32954565/96342
-// returns `true` on success.
-function bindAnyScroll(handler) {
- if (window.addEventListener) {
- window.addEventListener('scroll', handler, true); // useCapture=true
- return true;
- }
- return false;
+function allowSelection(el) {
+ el.removeClass('fc-unselectable')
+ .off('selectstart', preventDefault);
}
-// undoes bindAnyScroll. must pass in the original function.
-// returns `true` on success.
-function unbindAnyScroll(handler) {
- if (window.removeEventListener) {
- window.removeEventListener('scroll', handler, true); // useCapture=true
- return true;
- }
- return false;
+// Stops a mouse/touch event from doing it's native browser action
+function preventDefault(ev) {
+ ev.preventDefault();
}
@@ -1329,38 +1328,42 @@ newMomentProto.toISOString = function() {
};
;;
+(function() {
-// Single Date Formatting
-// -------------------------------------------------------------------------------------------------
-
-
-// call this if you want Moment's original format method to be used
-function oldMomentFormat(mom, formatStr) {
- return oldMomentProto.format.call(mom, formatStr); // oldMomentProto defined in moment-ext.js
-}
-
+// exports
+FC.formatDate = formatDate;
+FC.formatRange = formatRange;
+FC.oldMomentFormat = oldMomentFormat;
+FC.queryMostGranularFormatUnit = queryMostGranularFormatUnit;
-// Formats `date` with a Moment formatting string, but allow our non-zero areas and
-// additional token.
-function formatDate(date, formatStr) {
- return formatDateWithChunks(date, getFormatStringChunks(formatStr));
-}
+// Config
+// ---------------------------------------------------------------------------------------------------------------------
-function formatDateWithChunks(date, chunks) {
- var s = '';
- var i;
-
- for (i=0; i<chunks.length; i++) {
- s += formatDateWithChunk(date, chunks[i]);
- }
+/*
+Inserted between chunks in the fake ("intermediate") formatting string.
+Important that it passes as whitespace (\s) because moment often identifies non-standalone months
+via a regexp with an \s.
+*/
+var PART_SEPARATOR = '\u000b'; // vertical tab
- return s;
-}
+/*
+Inserted as the first character of a literal-text chunk to indicate that the literal text is not actually literal text,
+but rather, a "special" token that has custom rendering (see specialTokens map).
+*/
+var SPECIAL_TOKEN_MARKER = '\u001f'; // information separator 1
+/*
+Inserted at the beginning and end of a span of text that must have non-zero numeric characters.
+Handling of these markers is done in a post-processing step at the very end of text rendering.
+*/
+var MAYBE_MARKER = '\u001e'; // information separator 2
+var MAYBE_REGEXP = new RegExp(MAYBE_MARKER + '([^' + MAYBE_MARKER + ']*)' + MAYBE_MARKER, 'g'); // must be global
-// addition formatting tokens we want recognized
-var tokenOverrides = {
+/*
+Addition formatting tokens we want recognized
+*/
+var specialTokens = {
t: function(date) { // "a" or "p"
return oldMomentFormat(date, 'a').charAt(0);
},
@@ -1369,28 +1372,39 @@ var tokenOverrides = {
}
};
+/*
+The first characters of formatting tokens for units that are 1 day or larger.
+`value` is for ranking relative size (lower means bigger).
+`unit` is a normalized unit, used for comparing moments.
+*/
+var largeTokenMap = {
+ Y: { value: 1, unit: 'year' },
+ M: { value: 2, unit: 'month' },
+ W: { value: 3, unit: 'week' }, // ISO week
+ w: { value: 3, unit: 'week' }, // local week
+ D: { value: 4, unit: 'day' }, // day of month
+ d: { value: 4, unit: 'day' } // day of week
+};
+
-function formatDateWithChunk(date, chunk) {
- var token;
- var maybeStr;
+// Single Date Formatting
+// ---------------------------------------------------------------------------------------------------------------------
- if (typeof chunk === 'string') { // a literal string
- return chunk;
- }
- else if ((token = chunk.token)) { // a token, like "YYYY"
- if (tokenOverrides[token]) {
- return tokenOverrides[token](date); // use our custom token
- }
- return oldMomentFormat(date, token);
- }
- else if (chunk.maybe) { // a grouping of other chunks that must be non-zero
- maybeStr = formatDateWithChunks(date, chunk.maybe);
- if (maybeStr.match(/[1-9]/)) {
- return maybeStr;
- }
- }
+/*
+Formats `date` with a Moment formatting string, but allow our non-zero areas and special token
+*/
+function formatDate(date, formatStr) {
+ return renderFakeFormatString(
+ getParsedFormatString(formatStr).fakeFormatString,
+ date
+ );
+}
- return '';
+/*
+Call this if you want Moment's original format method to be used
+*/
+function oldMomentFormat(mom, formatStr) {
+ return oldMomentProto.format.call(mom, formatStr); // oldMomentProto defined in moment-ext.js
}
@@ -1398,10 +1412,12 @@ function formatDateWithChunk(date, chunk) {
// -------------------------------------------------------------------------------------------------
// TODO: make it work with timezone offset
-// Using a formatting string meant for a single date, generate a range string, like
-// "Sep 2 - 9 2013", that intelligently inserts a separator where the dates differ.
-// If the dates are the same as far as the format string is concerned, just return a single
-// rendering of one date, without any separator.
+/*
+Using a formatting string meant for a single date, generate a range string, like
+"Sep 2 - 9 2013", that intelligently inserts a separator where the dates differ.
+If the dates are the same as far as the format string is concerned, just return a single
+rendering of one date, without any separator.
+*/
function formatRange(date1, date2, formatStr, separator, isRTL) {
var localeData;
@@ -1410,28 +1426,31 @@ function formatRange(date1, date2, formatStr, separator, isRTL) {
localeData = date1.localeData();
- // Expand localized format strings, like "LL" -> "MMMM D YYYY"
- formatStr = localeData.longDateFormat(formatStr) || formatStr;
+ // Expand localized format strings, like "LL" -> "MMMM D YYYY".
// BTW, this is not important for `formatDate` because it is impossible to put custom tokens
// or non-zero areas in Moment's localized format strings.
+ formatStr = localeData.longDateFormat(formatStr) || formatStr;
- separator = separator || ' - ';
-
- return formatRangeWithChunks(
+ return renderParsedFormat(
+ getParsedFormatString(formatStr),
date1,
date2,
- getFormatStringChunks(formatStr),
- separator,
+ separator || ' - ',
isRTL
);
}
-FC.formatRange = formatRange; // expose
-
-function formatRangeWithChunks(date1, date2, chunks, separator, isRTL) {
- var unzonedDate1 = date1.clone().stripZone(); // for formatSimilarChunk
+/*
+Renders a range with an already-parsed format string.
+*/
+function renderParsedFormat(parsedFormat, date1, date2, separator, isRTL) {
+ var sameUnits = parsedFormat.sameUnits;
+ var unzonedDate1 = date1.clone().stripZone(); // for same-unit comparisons
var unzonedDate2 = date2.clone().stripZone(); // "
- var chunkStr; // the rendering of the chunk
+
+ var renderedParts1 = renderFakeFormatStringParts(parsedFormat.fakeFormatString, date1);
+ var renderedParts2 = renderFakeFormatStringParts(parsedFormat.fakeFormatString, date2);
+
var leftI;
var leftStr = '';
var rightI;
@@ -1443,28 +1462,35 @@ function formatRangeWithChunks(date1, date2, chunks, separator, isRTL) {
// Start at the leftmost side of the formatting string and continue until you hit a token
// that is not the same between dates.
- for (leftI=0; leftI<chunks.length; leftI++) {
- chunkStr = formatSimilarChunk(date1, date2, unzonedDate1, unzonedDate2, chunks[leftI]);
- if (chunkStr === false) {
- break;
- }
- leftStr += chunkStr;
+ for (
+ leftI = 0;
+ leftI < sameUnits.length && (!sameUnits[leftI] || unzonedDate1.isSame(unzonedDate2, sameUnits[leftI]));
+ leftI++
+ ) {
+ leftStr += renderedParts1[leftI];
}
// Similarly, start at the rightmost side of the formatting string and move left
- for (rightI=chunks.length-1; rightI>leftI; rightI--) {
- chunkStr = formatSimilarChunk(date1, date2, unzonedDate1, unzonedDate2, chunks[rightI]);
- if (chunkStr === false) {
+ for (
+ rightI = sameUnits.length - 1;
+ rightI > leftI && (!sameUnits[rightI] || unzonedDate1.isSame(unzonedDate2, sameUnits[rightI]));
+ rightI--
+ ) {
+ // If current chunk is on the boundary of unique date-content, and is a special-case
+ // date-formatting postfix character, then don't consume it. Consider it unique date-content.
+ // TODO: make configurable
+ if (rightI - 1 === leftI && renderedParts1[rightI] === '.') {
break;
}
- rightStr = chunkStr + rightStr;
+
+ rightStr = renderedParts1[rightI] + rightStr;
}
// The area in the middle is different for both of the dates.
// Collect them distinctly so we can jam them together later.
- for (middleI=leftI; middleI<=rightI; middleI++) {
- middleStr1 += formatDateWithChunk(date1, chunks[middleI]);
- middleStr2 += formatDateWithChunk(date2, chunks[middleI]);
+ for (middleI = leftI; middleI <= rightI; middleI++) {
+ middleStr1 += renderedParts1[middleI];
+ middleStr2 += renderedParts2[middleI];
}
if (middleStr1 || middleStr2) {
@@ -1476,77 +1502,59 @@ function formatRangeWithChunks(date1, date2, chunks, separator, isRTL) {
}
}
- return leftStr + middleStr + rightStr;
+ return processMaybeMarkers(
+ leftStr + middleStr + rightStr
+ );
}
-var similarUnitMap = {
- Y: 'year',
- M: 'month',
- D: 'day', // day of month
- d: 'day', // day of week
- // prevents a separator between anything time-related...
- A: 'second', // AM/PM
- a: 'second', // am/pm
- T: 'second', // A/P
- t: 'second', // a/p
- H: 'second', // hour (24)
- h: 'second', // hour (12)
- m: 'second', // minute
- s: 'second' // second
-};
-// TODO: week maybe?
-
-
-// Given a formatting chunk, and given that both dates are similar in the regard the
-// formatting chunk is concerned, format date1 against `chunk`. Otherwise, return `false`.
-function formatSimilarChunk(date1, date2, unzonedDate1, unzonedDate2, chunk) {
- var token;
- var unit;
+// Format String Parsing
+// ---------------------------------------------------------------------------------------------------------------------
- if (typeof chunk === 'string') { // a literal string
- return chunk;
- }
- else if ((token = chunk.token)) {
- unit = similarUnitMap[token.charAt(0)];
+var parsedFormatStrCache = {};
- // are the dates the same for this unit of measurement?
- // use the unzoned dates for this calculation because unreliable when near DST (bug #2396)
- if (unit && unzonedDate1.isSame(unzonedDate2, unit)) {
- return oldMomentFormat(date1, token); // would be the same if we used `date2`
- // BTW, don't support custom tokens
- }
- }
-
- return false; // the chunk is NOT the same for the two dates
- // BTW, don't support splitting on non-zero areas
+/*
+Returns a parsed format string, leveraging a cache.
+*/
+function getParsedFormatString(formatStr) {
+ return parsedFormatStrCache[formatStr] ||
+ (parsedFormatStrCache[formatStr] = parseFormatString(formatStr));
}
-
-// Chunking Utils
-// -------------------------------------------------------------------------------------------------
-
-
-var formatStringChunkCache = {};
-
-
-function getFormatStringChunks(formatStr) {
- if (formatStr in formatStringChunkCache) {
- return formatStringChunkCache[formatStr];
- }
- return (formatStringChunkCache[formatStr] = chunkFormatString(formatStr));
+/*
+Parses a format string into the following:
+- fakeFormatString: a momentJS formatting string, littered with special control characters that get post-processed.
+- sameUnits: for every part in fakeFormatString, if the part is a token, the value will be a unit string (like "day"),
+ that indicates how similar a range's start & end must be in order to share the same formatted text.
+ If not a token, then the value is null.
+ Always a flat array (not nested liked "chunks").
+*/
+function parseFormatString(formatStr) {
+ var chunks = chunkFormatString(formatStr);
+
+ return {
+ fakeFormatString: buildFakeFormatString(chunks),
+ sameUnits: buildSameUnits(chunks)
+ };
}
-
-// Break the formatting string into an array of chunks
+/*
+Break the formatting string into an array of chunks.
+A 'maybe' chunk will have nested chunks.
+*/
function chunkFormatString(formatStr) {
var chunks = [];
- var chunker = /\[([^\]]*)\]|\(([^\)]*)\)|(LTS|LT|(\w)\4*o?)|([^\w\[\(]+)/g; // TODO: more descrimination
var match;
+ // TODO: more descrimination
+ // \4 is a backreference to the first character of a multi-character set.
+ var chunker = /\[([^\]]*)\]|\(([^\)]*)\)|(LTS|LT|(\w)\4*o?)|([^\w\[\(]+)/g;
+
while ((match = chunker.exec(formatStr))) {
if (match[1]) { // a literal string inside [ ... ]
- chunks.push(match[1]);
+ chunks.push.apply(chunks, // append
+ splitStringLiteral(match[1])
+ );
}
else if (match[2]) { // non-zero formatting inside ( ... )
chunks.push({ maybe: chunkFormatString(match[2]) });
@@ -1555,41 +1563,166 @@ function chunkFormatString(formatStr) {
chunks.push({ token: match[3] });
}
else if (match[5]) { // an unenclosed literal string
- chunks.push(match[5]);
+ chunks.push.apply(chunks, // append
+ splitStringLiteral(match[5])
+ );
}
}
return chunks;
}
+/*
+Potentially splits a literal-text string into multiple parts. For special cases.
+*/
+function splitStringLiteral(s) {
+ if (s === '. ') {
+ return [ '.', ' ' ]; // for locales with periods bound to the end of each year/month/date
+ }
+ else {
+ return [ s ];
+ }
+}
-// Misc Utils
-// -------------------------------------------------------------------------------------------------
+/*
+Given chunks parsed from a real format string, generate a fake (aka "intermediate") format string with special control
+characters that will eventually be given to moment for formatting, and then post-processed.
+*/
+function buildFakeFormatString(chunks) {
+ var parts = [];
+ var i, chunk;
+ for (i = 0; i < chunks.length; i++) {
+ chunk = chunks[i];
-// granularity only goes up until day
-// TODO: unify with similarUnitMap
-var tokenGranularities = {
- Y: { value: 1, unit: 'year' },
- M: { value: 2, unit: 'month' },
- W: { value: 3, unit: 'week' },
- w: { value: 3, unit: 'week' },
- D: { value: 4, unit: 'day' }, // day of month
- d: { value: 4, unit: 'day' } // day of week
-};
+ if (typeof chunk === 'string') {
+ parts.push('[' + chunk + ']');
+ }
+ else if (chunk.token) {
+ if (chunk.token in specialTokens) {
+ parts.push(
+ SPECIAL_TOKEN_MARKER + // useful during post-processing
+ '[' + chunk.token + ']' // preserve as literal text
+ );
+ }
+ else {
+ parts.push(chunk.token); // unprotected text implies a format string
+ }
+ }
+ else if (chunk.maybe) {
+ parts.push(
+ MAYBE_MARKER + // useful during post-processing
+ buildFakeFormatString(chunk.maybe) +
+ MAYBE_MARKER
+ );
+ }
+ }
+
+ return parts.join(PART_SEPARATOR);
+}
-// returns a unit string, either 'year', 'month', 'day', or null
-// for the most granular formatting token in the string.
-FC.queryMostGranularFormatUnit = function(formatStr) {
- var chunks = getFormatStringChunks(formatStr);
+/*
+Given parsed chunks from a real formatting string, generates an array of unit strings (like "day") that indicate
+in which regard two dates must be similar in order to share range formatting text.
+The `chunks` can be nested (because of "maybe" chunks), however, the returned array will be flat.
+*/
+function buildSameUnits(chunks) {
+ var units = [];
+ var i, chunk;
+ var tokenInfo;
+
+ for (i = 0; i < chunks.length; i++) {
+ chunk = chunks[i];
+
+ if (chunk.token) {
+ tokenInfo = largeTokenMap[chunk.token.charAt(0)];
+ units.push(tokenInfo ? tokenInfo.unit : 'second'); // default to a very strict same-second
+ }
+ else if (chunk.maybe) {
+ units.push.apply(units, // append
+ buildSameUnits(chunk.maybe)
+ );
+ }
+ else {
+ units.push(null);
+ }
+ }
+
+ return units;
+}
+
+
+// Rendering to text
+// ---------------------------------------------------------------------------------------------------------------------
+
+/*
+Formats a date with a fake format string, post-processes the control characters, then returns.
+*/
+function renderFakeFormatString(fakeFormatString, date) {
+ return processMaybeMarkers(
+ renderFakeFormatStringParts(fakeFormatString, date).join('')
+ );
+}
+
+/*
+Formats a date into parts that will have been post-processed, EXCEPT for the "maybe" markers.
+*/
+function renderFakeFormatStringParts(fakeFormatString, date) {
+ var parts = [];
+ var fakeRender = oldMomentFormat(date, fakeFormatString);
+ var fakeParts = fakeRender.split(PART_SEPARATOR);
+ var i, fakePart;
+
+ for (i = 0; i < fakeParts.length; i++) {
+ fakePart = fakeParts[i];
+
+ if (fakePart.charAt(0) === SPECIAL_TOKEN_MARKER) {
+ parts.push(
+ // the literal string IS the token's name.
+ // call special token's registered function.
+ specialTokens[fakePart.substring(1)](date)
+ );
+ }
+ else {
+ parts.push(fakePart);
+ }
+ }
+
+ return parts;
+}
+
+/*
+Accepts an almost-finally-formatted string and processes the "maybe" control characters, returning a new string.
+*/
+function processMaybeMarkers(s) {
+ return s.replace(MAYBE_REGEXP, function(m0, m1) { // regex assumed to have 'g' flag
+ if (m1.match(/[1-9]/)) { // any non-zero numeric characters?
+ return m1;
+ }
+ else {
+ return '';
+ }
+ });
+}
+
+
+// Misc Utils
+// -------------------------------------------------------------------------------------------------
+
+/*
+Returns a unit string, either 'year', 'month', 'day', or null for the most granular formatting token in the string.
+*/
+function queryMostGranularFormatUnit(formatStr) {
+ var chunks = chunkFormatString(formatStr);
var i, chunk;
var candidate;
var best;
for (i = 0; i < chunks.length; i++) {
chunk = chunks[i];
+
if (chunk.token) {
- candidate = tokenGranularities[chunk.token.charAt(0)];
+ candidate = largeTokenMap[chunk.token.charAt(0)];
if (candidate) {
if (!best || candidate.value > best.value) {
best = candidate;
@@ -1605,6 +1738,13 @@ FC.queryMostGranularFormatUnit = function(formatStr) {
return null;
};
+})();
+
+// quick local references
+var formatDate = FC.formatDate;
+var formatRange = FC.formatRange;
+var oldMomentFormat = FC.oldMomentFormat;
+
;;
FC.Class = Class; // export
@@ -1998,35 +2138,6 @@ var ListenerMixin = FC.ListenerMixin = (function() {
})();
;;
-// simple class for toggle a `isIgnoringMouse` flag on delay
-// initMouseIgnoring must first be called, with a millisecond delay setting.
-var MouseIgnorerMixin = {
-
- isIgnoringMouse: false, // bool
- delayUnignoreMouse: null, // method
-
-
- initMouseIgnoring: function(delay) {
- this.delayUnignoreMouse = debounce(proxy(this, 'unignoreMouse'), delay || 1000);
- },
-
-
- // temporarily ignore mouse actions on segments
- tempIgnoreMouse: function() {
- this.isIgnoringMouse = true;
- this.delayUnignoreMouse();
- },
-
-
- // delayUnignoreMouse eventually calls this
- unignoreMouse: function() {
- this.isIgnoringMouse = false;
- }
-
-};
-
-;;
-
/* A rectangular panel that is absolutely positioned over other content
------------------------------------------------------------------------------------------------------------------------
Options:
@@ -2457,7 +2568,7 @@ var CoordCache = FC.CoordCache = Class.extend({
----------------------------------------------------------------------------------------------------------------------*/
// TODO: use Emitter
-var DragListener = FC.DragListener = Class.extend(ListenerMixin, MouseIgnorerMixin, {
+var DragListener = FC.DragListener = Class.extend(ListenerMixin, {
options: null,
subjectEl: null,
@@ -2480,13 +2591,12 @@ var DragListener = FC.DragListener = Class.extend(ListenerMixin, MouseIgnorerMix
delayTimeoutId: null,
minDistance: null,
- handleTouchScrollProxy: null, // calls handleTouchScroll, always bound to `this`
+ shouldCancelTouchScroll: true,
+ scrollAlwaysKills: false,
constructor: function(options) {
this.options = options || {};
- this.handleTouchScrollProxy = proxy(this, 'handleTouchScroll');
- this.initMouseIgnoring(500);
},
@@ -2498,7 +2608,7 @@ var DragListener = FC.DragListener = Class.extend(ListenerMixin, MouseIgnorerMix
var isTouch = getEvIsTouch(ev);
if (ev.type === 'mousedown') {
- if (this.isIgnoringMouse) {
+ if (GlobalEmitter.get().shouldIgnoreMouse()) {
return;
}
else if (!isPrimaryMouseButton(ev)) {
@@ -2517,6 +2627,8 @@ var DragListener = FC.DragListener = Class.extend(ListenerMixin, MouseIgnorerMix
this.minDistance = firstDefined(extraOptions.distance, this.options.distance, 0);
this.subjectEl = this.options.subjectEl;
+ preventSelection($('body'));
+
this.isInteracting = true;
this.isTouch = isTouch;
this.isDelayEnded = false;
@@ -2558,12 +2670,7 @@ var DragListener = FC.DragListener = Class.extend(ListenerMixin, MouseIgnorerMix
this.isInteracting = false;
this.handleInteractionEnd(ev, isCancelled);
- // a touchstart+touchend on the same element will result in the following addition simulated events:
- // mouseover + mouseout + click
- // let's ignore these bogus events
- if (this.isTouch) {
- this.tempIgnoreMouse();
- }
+ allowSelection($('body'));
}
},
@@ -2578,45 +2685,25 @@ var DragListener = FC.DragListener = Class.extend(ListenerMixin, MouseIgnorerMix
bindHandlers: function() {
- var _this = this;
- var touchStartIgnores = 1;
+ // some browsers (Safari in iOS 10) don't allow preventDefault on touch events that are bound after touchstart,
+ // so listen to the GlobalEmitter singleton, which is always bound, instead of the document directly.
+ var globalEmitter = GlobalEmitter.get();
if (this.isTouch) {
- this.listenTo($(document), {
+ this.listenTo(globalEmitter, {
touchmove: this.handleTouchMove,
touchend: this.endInteraction,
- touchcancel: this.endInteraction,
-
- // Sometimes touchend doesn't fire
- // (can't figure out why. touchcancel doesn't fire either. has to do with scrolling?)
- // If another touchstart happens, we know it's bogus, so cancel the drag.
- // touchend will continue to be broken until user does a shorttap/scroll, but this is best we can do.
- touchstart: function(ev) {
- if (touchStartIgnores) { // bindHandlers is called from within a touchstart,
- touchStartIgnores--; // and we don't want this to fire immediately, so ignore.
- }
- else {
- _this.endInteraction(ev, true); // isCancelled=true
- }
- }
+ scroll: this.handleTouchScroll
});
-
- // listen to ALL scroll actions on the page
- if (
- !bindAnyScroll(this.handleTouchScrollProxy) && // hopefully this works and short-circuits the rest
- this.scrollEl // otherwise, attach a single handler to this
- ) {
- this.listenTo(this.scrollEl, 'scroll', this.handleTouchScroll);
- }
}
else {
- this.listenTo($(document), {
+ this.listenTo(globalEmitter, {
mousemove: this.handleMouseMove,
mouseup: this.endInteraction
});
}
- this.listenTo($(document), {
+ this.listenTo(globalEmitter, {
selectstart: preventDefault, // don't allow selection while dragging
contextmenu: preventDefault // long taps would open menu on Chrome dev tools
});
@@ -2624,13 +2711,7 @@ var DragListener = FC.DragListener = Class.extend(ListenerMixin, MouseIgnorerMix
unbindHandlers: function() {
- this.stopListeningTo($(document));
-
- // unbind scroll listening
- unbindAnyScroll(this.handleTouchScrollProxy);
- if (this.scrollEl) {
- this.stopListeningTo(this.scrollEl, 'scroll');
- }
+ this.stopListeningTo(GlobalEmitter.get());
},
@@ -2738,8 +2819,9 @@ var DragListener = FC.DragListener = Class.extend(ListenerMixin, MouseIgnorerMix
handleTouchMove: function(ev) {
+
// prevent inertia and touchmove-scrolling while dragging
- if (this.isDragging) {
+ if (this.isDragging && this.shouldCancelTouchScroll) {
ev.preventDefault();
}
@@ -2759,7 +2841,7 @@ var DragListener = FC.DragListener = Class.extend(ListenerMixin, MouseIgnorerMix
handleTouchScroll: function(ev) {
// if the drag is being initiated by touch, but a scroll happens before
// the drag-initiating delay is over, cancel the drag
- if (!this.isDragging) {
+ if (!this.isDragging || this.scrollAlwaysKills) {
this.endInteraction(ev, true); // isCancelled=true
}
},
@@ -2982,7 +3064,7 @@ options:
var HitDragListener = DragListener.extend({
component: null, // converts coordinates to hits
- // methods: prepareHits, releaseHits, queryHit
+ // methods: hitsNeeded, hitsNotNeeded, queryHit
origHit: null, // the hit the mouse was over when listening started
hit: null, // the hit the mouse is over
@@ -3004,7 +3086,8 @@ var HitDragListener = DragListener.extend({
var origPoint;
var point;
- this.computeCoords();
+ this.component.hitsNeeded();
+ this.computeScrollBounds(); // for autoscroll
if (ev) {
origPoint = { left: getEvX(ev), top: getEvY(ev) };
@@ -3043,13 +3126,6 @@ var HitDragListener = DragListener.extend({
},
- // Recomputes the drag-critical positions of elements
- computeCoords: function() {
- this.component.prepareHits();
- this.computeScrollBounds(); // why is this here??????
- },
-
-
// Called when the actual drag has started
handleDragStart: function(ev) {
var hit;
@@ -3128,7 +3204,7 @@ var HitDragListener = DragListener.extend({
this.origHit = null;
this.hit = null;
- this.component.releaseHits();
+ this.component.hitsNotNeeded();
},
@@ -3136,7 +3212,12 @@ var HitDragListener = DragListener.extend({
handleScrollEnd: function() {
DragListener.prototype.handleScrollEnd.apply(this, arguments); // call the super-method
- this.computeCoords(); // hits' absolute positions will be in new places. recompute
+ // hits' absolute positions will be in new places after a user's scroll.
+ // HACK for recomputing.
+ if (this.isDragging) {
+ this.component.releaseHits();
+ this.component.prepareHits();
+ }
},
@@ -3186,6 +3267,231 @@ function isHitPropsWithin(subHit, superHit) {
;;
+/*
+Listens to document and window-level user-interaction events, like touch events and mouse events,
+and fires these events as-is to whoever is observing a GlobalEmitter.
+Best when used as a singleton via GlobalEmitter.get()
+
+Normalizes mouse/touch events. For examples:
+- ignores the the simulated mouse events that happen after a quick tap: mousemove+mousedown+mouseup+click
+- compensates for various buggy scenarios where a touchend does not fire
+*/
+
+FC.touchMouseIgnoreWait = 500;
+
+var GlobalEmitter = Class.extend(ListenerMixin, EmitterMixin, {
+
+ isTouching: false,
+ mouseIgnoreDepth: 0,
+ handleScrollProxy: null,
+
+
+ bind: function() {
+ var _this = this;
+
+ this.listenTo($(document), {
+ touchstart: this.handleTouchStart,
+ touchcancel: this.handleTouchCancel,
+ touchend: this.handleTouchEnd,
+ mousedown: this.handleMouseDown,
+ mousemove: this.handleMouseMove,
+ mouseup: this.handleMouseUp,
+ click: this.handleClick,
+ selectstart: this.handleSelectStart,
+ contextmenu: this.handleContextMenu
+ });
+
+ // because we need to call preventDefault
+ // because https://www.chromestatus.com/features/5093566007214080
+ // TODO: investigate performance because this is a global handler
+ window.addEventListener(
+ 'touchmove',
+ this.handleTouchMoveProxy = function(ev) {
+ _this.handleTouchMove($.Event(ev));
+ },
+ { passive: false } // allows preventDefault()
+ );
+
+ // attach a handler to get called when ANY scroll action happens on the page.
+ // this was impossible to do with normal on/off because 'scroll' doesn't bubble.
+ // http://stackoverflow.com/a/32954565/96342
+ window.addEventListener(
+ 'scroll',
+ this.handleScrollProxy = function(ev) {
+ _this.handleScroll($.Event(ev));
+ },
+ true // useCapture
+ );
+ },
+
+ unbind: function() {
+ this.stopListeningTo($(document));
+
+ window.removeEventListener(
+ 'touchmove',
+ this.handleTouchMoveProxy
+ );
+
+ window.removeEventListener(
+ 'scroll',
+ this.handleScrollProxy,
+ true // useCapture
+ );
+ },
+
+
+ // Touch Handlers
+ // -----------------------------------------------------------------------------------------------------------------
+
+ handleTouchStart: function(ev) {
+
+ // if a previous touch interaction never ended with a touchend, then implicitly end it,
+ // but since a new touch interaction is about to begin, don't start the mouse ignore period.
+ this.stopTouch(ev, true); // skipMouseIgnore=true
+
+ this.isTouching = true;
+ this.trigger('touchstart', ev);
+ },
+
+ handleTouchMove: function(ev) {
+ if (this.isTouching) {
+ this.trigger('touchmove', ev);
+ }
+ },
+
+ handleTouchCancel: function(ev) {
+ if (this.isTouching) {
+ this.trigger('touchcancel', ev);
+
+ // Have touchcancel fire an artificial touchend. That way, handlers won't need to listen to both.
+ // If touchend fires later, it won't have any effect b/c isTouching will be false.
+ this.stopTouch(ev);
+ }
+ },
+
+ handleTouchEnd: function(ev) {
+ this.stopTouch(ev);
+ },
+
+
+ // Mouse Handlers
+ // -----------------------------------------------------------------------------------------------------------------
+
+ handleMouseDown: function(ev) {
+ if (!this.shouldIgnoreMouse()) {
+ this.trigger('mousedown', ev);
+ }
+ },
+
+ handleMouseMove: function(ev) {
+ if (!this.shouldIgnoreMouse()) {
+ this.trigger('mousemove', ev);
+ }
+ },
+
+ handleMouseUp: function(ev) {
+ if (!this.shouldIgnoreMouse()) {
+ this.trigger('mouseup', ev);
+ }
+ },
+
+ handleClick: function(ev) {
+ if (!this.shouldIgnoreMouse()) {
+ this.trigger('click', ev);
+ }
+ },
+
+
+ // Misc Handlers
+ // -----------------------------------------------------------------------------------------------------------------
+
+ handleSelectStart: function(ev) {
+ this.trigger('selectstart', ev);
+ },
+
+ handleContextMenu: function(ev) {
+ this.trigger('contextmenu', ev);
+ },
+
+ handleScroll: function(ev) {
+ this.trigger('scroll', ev);
+ },
+
+
+ // Utils
+ // -----------------------------------------------------------------------------------------------------------------
+
+ stopTouch: function(ev, skipMouseIgnore) {
+ if (this.isTouching) {
+ this.isTouching = false;
+ this.trigger('touchend', ev);
+
+ if (!skipMouseIgnore) {
+ this.startTouchMouseIgnore();
+ }
+ }
+ },
+
+ startTouchMouseIgnore: function() {
+ var _this = this;
+ var wait = FC.touchMouseIgnoreWait;
+
+ if (wait) {
+ this.mouseIgnoreDepth++;
+ setTimeout(function() {
+ _this.mouseIgnoreDepth--;
+ }, wait);
+ }
+ },
+
+ shouldIgnoreMouse: function() {
+ return this.isTouching || Boolean(this.mouseIgnoreDepth);
+ }
+
+});
+
+
+// Singleton
+// ---------------------------------------------------------------------------------------------------------------------
+
+(function() {
+ var globalEmitter = null;
+ var neededCount = 0;
+
+
+ // gets the singleton
+ GlobalEmitter.get = function() {
+
+ if (!globalEmitter) {
+ globalEmitter = new GlobalEmitter();
+ globalEmitter.bind();
+ }
+
+ return globalEmitter;
+ };
+
+
+ // called when an object knows it will need a GlobalEmitter in the near future.
+ GlobalEmitter.needed = function() {
+ GlobalEmitter.get(); // ensures globalEmitter
+ neededCount++;
+ };
+
+
+ // called when the object that originally called needed() doesn't need a GlobalEmitter anymore.
+ GlobalEmitter.unneeded = function() {
+ neededCount--;
+
+ if (!neededCount) { // nobody else needs it
+ globalEmitter.unbind();
+ globalEmitter = null;
+ }
+ };
+
+})();
+
+;;
+
/* Creates a clone of an element and lets it track the mouse as it moves
----------------------------------------------------------------------------------------------------------------------*/
@@ -3383,7 +3689,7 @@ var MouseFollower = Class.extend(ListenerMixin, {
/* An abstract class comprised of a "grid" of areas that each represent a specific datetime
----------------------------------------------------------------------------------------------------------------------*/
-var Grid = FC.Grid = Class.extend(ListenerMixin, MouseIgnorerMixin, {
+var Grid = FC.Grid = Class.extend(ListenerMixin, {
// self-config, overridable by subclasses
hasDayInteractions: true, // can user click/select ranges of time?
@@ -3409,7 +3715,8 @@ var Grid = FC.Grid = Class.extend(ListenerMixin, MouseIgnorerMixin, {
// TODO: port isTimeScale into same system?
largeUnit: null,
- dayDragListener: null,
+ dayClickListener: null,
+ daySelectListener: null,
segDragListener: null,
segResizeListener: null,
externalDragListener: null,
@@ -3420,8 +3727,8 @@ var Grid = FC.Grid = Class.extend(ListenerMixin, MouseIgnorerMixin, {
this.isRTL = view.opt('isRTL');
this.elsByFill = {};
- this.dayDragListener = this.buildDayDragListener();
- this.initMouseIgnoring();
+ this.dayClickListener = this.buildDayClickListener();
+ this.daySelectListener = this.buildDaySelectListener();
},
@@ -3516,6 +3823,20 @@ var Grid = FC.Grid = Class.extend(ListenerMixin, MouseIgnorerMixin, {
/* Hit Area
------------------------------------------------------------------------------------------------------------------*/
+ hitsNeededDepth: 0, // necessary because multiple callers might need the same hits
+
+ hitsNeeded: function() {
+ if (!(this.hitsNeededDepth++)) {
+ this.prepareHits();
+ }
+ },
+
+ hitsNotNeeded: function() {
+ if (this.hitsNeededDepth && !(--this.hitsNeededDepth)) {
+ this.releaseHits();
+ }
+ },
+
// Called before one or more queryHit calls might happen. Should prepare any cached coordinates for queryHit
prepareHits: function() {
@@ -3643,9 +3964,19 @@ var Grid = FC.Grid = Class.extend(ListenerMixin, MouseIgnorerMixin, {
// Process a mousedown on an element that represents a day. For day clicking and selecting.
dayMousedown: function(ev) {
- if (!this.isIgnoringMouse) {
- this.dayDragListener.startInteraction(ev, {
- //distance: 5, // needs more work if we want dayClick to fire correctly
+ var view = this.view;
+
+ // prevent a user's clickaway for unselecting a range or an event from
+ // causing a dayClick or starting an immediate new selection.
+ if (view.isSelected || view.selectedEvent) {
+ return;
+ }
+
+ this.dayClickListener.startInteraction(ev);
+
+ if (view.opt('selectable')) {
+ this.daySelectListener.startInteraction(ev, {
+ distance: view.opt('selectMinDistance')
});
}
},
@@ -3653,40 +3984,79 @@ var Grid = FC.Grid = Class.extend(ListenerMixin, MouseIgnorerMixin, {
dayTouchStart: function(ev) {
var view = this.view;
- var selectLongPressDelay = view.opt('selectLongPressDelay');
+ var selectLongPressDelay;
- // HACK to prevent a user's clickaway for unselecting a range or an event
- // from causing a dayClick.
+ // prevent a user's clickaway for unselecting a range or an event from
+ // causing a dayClick or starting an immediate new selection.
if (view.isSelected || view.selectedEvent) {
- this.tempIgnoreMouse();
+ return;
}
+ selectLongPressDelay = view.opt('selectLongPressDelay');
if (selectLongPressDelay == null) {
selectLongPressDelay = view.opt('longPressDelay'); // fallback
}
- this.dayDragListener.startInteraction(ev, {
- delay: selectLongPressDelay
- });
+ this.dayClickListener.startInteraction(ev);
+
+ if (view.opt('selectable')) {
+ this.daySelectListener.startInteraction(ev, {
+ delay: selectLongPressDelay
+ });
+ }
},
- // Creates a listener that tracks the user's drag across day elements.
- // For day clicking and selecting.
- buildDayDragListener: function() {
+ // Creates a listener that tracks the user's drag across day elements, for day clicking.
+ buildDayClickListener: function() {
var _this = this;
var view = this.view;
- var isSelectable = view.opt('selectable');
var dayClickHit; // null if invalid dayClick
+
+ var dragListener = new HitDragListener(this, {
+ scroll: view.opt('dragScroll'),
+ interactionStart: function() {
+ dayClickHit = dragListener.origHit;
+ },
+ hitOver: function(hit, isOrig, origHit) {
+ // if user dragged to another cell at any point, it can no longer be a dayClick
+ if (!isOrig) {
+ dayClickHit = null;
+ }
+ },
+ hitOut: function() { // called before mouse moves to a different hit OR moved out of all hits
+ dayClickHit = null;
+ },
+ interactionEnd: function(ev, isCancelled) {
+ if (!isCancelled && dayClickHit) {
+ view.triggerDayClick(
+ _this.getHitSpan(dayClickHit),
+ _this.getHitEl(dayClickHit),
+ ev
+ );
+ }
+ }
+ });
+
+ // because dayClickListener won't be called with any time delay, "dragging" will begin immediately,
+ // which will kill any touchmoving/scrolling. Prevent this.
+ dragListener.shouldCancelTouchScroll = false;
+
+ dragListener.scrollAlwaysKills = true;
+
+ return dragListener;
+ },
+
+
+ // Creates a listener that tracks the user's drag across day elements, for day selecting.
+ buildDaySelectListener: function() {
+ var _this = this;
+ var view = this.view;
var selectionSpan; // null if invalid selection
- // this listener tracks a mousedown on a day element, and a subsequent drag.
- // if the drag ends on the same day, it is a 'dayClick'.
- // if 'selectable' is enabled, this listener also detects selections.
var dragListener = new HitDragListener(this, {
scroll: view.opt('dragScroll'),
interactionStart: function() {
- dayClickHit = dragListener.origHit; // for dayClick, where no dragging happens
selectionSpan = null;
},
dragStart: function() {
@@ -3695,27 +4065,20 @@ var Grid = FC.Grid = Class.extend(ListenerMixin, MouseIgnorerMixin, {
hitOver: function(hit, isOrig, origHit) {
if (origHit) { // click needs to have started on a hit
- // if user dragged to another cell at any point, it can no longer be a dayClick
- if (!isOrig) {
- dayClickHit = null;
- }
+ selectionSpan = _this.computeSelection(
+ _this.getHitSpan(origHit),
+ _this.getHitSpan(hit)
+ );
- if (isSelectable) {
- selectionSpan = _this.computeSelection(
- _this.getHitSpan(origHit),
- _this.getHitSpan(hit)
- );
- if (selectionSpan) {
- _this.renderSelection(selectionSpan);
- }
- else if (selectionSpan === false) {
- disableCursor();
- }
+ if (selectionSpan) {
+ _this.renderSelection(selectionSpan);
+ }
+ else if (selectionSpan === false) {
+ disableCursor();
}
}
},
hitOut: function() { // called before mouse moves to a different hit OR moved out of all hits
- dayClickHit = null;
selectionSpan = null;
_this.unrenderSelection();
},
@@ -3723,21 +4086,9 @@ var Grid = FC.Grid = Class.extend(ListenerMixin, MouseIgnorerMixin, {
enableCursor();
},
interactionEnd: function(ev, isCancelled) {
- if (!isCancelled) {
- if (
- dayClickHit &&
- !_this.isIgnoringMouse // see hack in dayTouchStart
- ) {
- view.triggerDayClick(
- _this.getHitSpan(dayClickHit),
- _this.getHitEl(dayClickHit),
- ev
- );
- }
- if (selectionSpan) {
- // the selection will already have been rendered. just report it
- view.reportSelection(selectionSpan, ev);
- }
+ if (!isCancelled && selectionSpan) {
+ // the selection will already have been rendered. just report it
+ view.reportSelection(selectionSpan, ev);
}
}
});
@@ -3750,7 +4101,8 @@ var Grid = FC.Grid = Class.extend(ListenerMixin, MouseIgnorerMixin, {
// Useful for when public API methods that result in re-rendering are invoked during a drag.
// Also useful for when touch devices misbehave and don't fire their touchend.
clearDragListeners: function() {
- this.dayDragListener.endInteraction();
+ this.dayClickListener.endInteraction();
+ this.daySelectListener.endInteraction();
if (this.segDragListener) {
this.segDragListener.endInteraction(); // will clear this.segDragListener
@@ -4269,7 +4621,6 @@ Grid.mixin({
// Attaches event-element-related handlers to an arbitrary container element. leverages bubbling.
bindSegHandlersToEl: function(el) {
this.bindSegHandlerToEl(el, 'touchstart', this.handleSegTouchStart);
- this.bindSegHandlerToEl(el, 'touchend', this.handleSegTouchEnd);
this.bindSegHandlerToEl(el, 'mouseenter', this.handleSegMouseover);
this.bindSegHandlerToEl(el, 'mouseleave', this.handleSegMouseout);
this.bindSegHandlerToEl(el, 'mousedown', this.handleSegMousedown);
@@ -4304,7 +4655,7 @@ Grid.mixin({
// Updates internal state and triggers handlers for when an event element is moused over
handleSegMouseover: function(seg, ev) {
if (
- !this.isIgnoringMouse &&
+ !GlobalEmitter.get().shouldIgnoreMouse() &&
!this.mousedOverSeg
) {
this.mousedOverSeg = seg;
@@ -4374,16 +4725,6 @@ Grid.mixin({
delay: isSelected ? 0 : eventLongPressDelay // do delay if not already selected
});
}
-
- // a long tap simulates a mouseover. ignore this bogus mouseover.
- this.tempIgnoreMouse();
- },
-
-
- handleSegTouchEnd: function(seg, ev) {
- // touchstart+touchend = click, which simulates a mouseover.
- // ignore this bogus mouseover.
- this.tempIgnoreMouse();
},
@@ -4509,7 +4850,7 @@ Grid.mixin({
if (dropLocation) {
// no need to re-show original, will rerender all anyways. esp important if eventRenderWait
- view.reportEventDrop(event, dropLocation, _this.largeUnit, el, ev);
+ view.reportSegDrop(seg, dropLocation, _this.largeUnit, el, ev);
}
else {
view.showEvent(event);
@@ -4812,7 +5153,7 @@ Grid.mixin({
if (resizeLocation) { // valid date to resize to?
// no need to re-show original, will rerender all anyways. esp important if eventRenderWait
- view.reportEventResize(event, resizeLocation, _this.largeUnit, el, ev);
+ view.reportSegResize(seg, resizeLocation, _this.largeUnit, el, ev);
}
else {
view.showEvent(event);
@@ -6833,9 +7174,9 @@ DayGrid.mixin({
// because segments in the popover are not part of a grid coordinate system, provide a hint to any
// grids that want to do drag-n-drop about which cell it came from
- this.prepareHits();
+ this.hitsNeeded();
segs[i].hit = this.getCellHit(row, col);
- this.releaseHits();
+ this.hitsNotNeeded();
segContainer.append(segs[i].el);
}
@@ -8261,11 +8602,23 @@ var View = FC.View = Class.extend(EmitterMixin, ListenerMixin, {
// Computes what the title at the top of the calendar should be for this view
computeTitle: function() {
+ var start, end;
+
+ // for views that span a large unit of time, show the proper interval, ignoring stray days before and after
+ if (this.intervalUnit === 'year' || this.intervalUnit === 'month') {
+ start = this.intervalStart;
+ end = this.intervalEnd;
+ }
+ else { // for day units or smaller, use the actual day range
+ start = this.start;
+ end = this.end;
+ }
+
return this.formatRange(
{
// in case intervalStart/End has a time, make sure timezone is correct
- start: this.calendar.applyTimezone(this.intervalStart),
- end: this.calendar.applyTimezone(this.intervalEnd)
+ start: this.calendar.applyTimezone(start),
+ end: this.calendar.applyTimezone(end)
},
this.opt('titleFormat') || this.computeTitleFormat(),
this.opt('titleRangeSeparator')
@@ -8579,14 +8932,16 @@ var View = FC.View = Class.extend(EmitterMixin, ListenerMixin, {
// Binds DOM handlers to elements that reside outside the view container, such as the document
bindGlobalHandlers: function() {
- this.listenTo($(document), 'mousedown', this.handleDocumentMousedown);
- this.listenTo($(document), 'touchstart', this.processUnselect);
+ this.listenTo(GlobalEmitter.get(), {
+ touchstart: this.processUnselect,
+ mousedown: this.handleDocumentMousedown
+ });
},
// Unbinds DOM handlers from elements that reside outside the view container
unbindGlobalHandlers: function() {
- this.stopListeningTo($(document));
+ this.stopListeningTo(GlobalEmitter.get());
},
@@ -9158,15 +9513,15 @@ var View = FC.View = Class.extend(EmitterMixin, ListenerMixin, {
// Must be called when an event in the view is dropped onto new location.
// `dropLocation` is an object that contains the new zoned start/end/allDay values for the event.
- reportEventDrop: function(event, dropLocation, largeUnit, el, ev) {
+ reportSegDrop: function(seg, dropLocation, largeUnit, el, ev) {
var calendar = this.calendar;
- var mutateResult = calendar.mutateEvent(event, dropLocation, largeUnit);
+ var mutateResult = calendar.mutateSeg(seg, dropLocation, largeUnit);
var undoFunc = function() {
mutateResult.undo();
calendar.reportEventChange();
};
- this.triggerEventDrop(event, mutateResult.dateDelta, undoFunc, el, ev);
+ this.triggerEventDrop(seg.event, mutateResult.dateDelta, undoFunc, el, ev);
calendar.reportEventChange(); // will rerender events
},
@@ -9261,15 +9616,15 @@ var View = FC.View = Class.extend(EmitterMixin, ListenerMixin, {
// Must be called when an event in the view has been resized to a new length
- reportEventResize: function(event, resizeLocation, largeUnit, el, ev) {
+ reportSegResize: function(seg, resizeLocation, largeUnit, el, ev) {
var calendar = this.calendar;
- var mutateResult = calendar.mutateEvent(event, resizeLocation, largeUnit);
+ var mutateResult = calendar.mutateSeg(seg, resizeLocation, largeUnit);
var undoFunc = function() {
mutateResult.undo();
calendar.reportEventChange();
};
- this.triggerEventResize(event, mutateResult.durationDelta, undoFunc, el, ev);
+ this.triggerEventResize(seg.event, mutateResult.durationDelta, undoFunc, el, ev);
calendar.reportEventChange(); // will rerender events
},
@@ -10202,6 +10557,9 @@ Calendar.mixin(EmitterMixin);
function Calendar_constructor(element, overrides) {
var t = this;
+ // declare the current calendar instance relies on GlobalEmitter. needed for garbage collection.
+ GlobalEmitter.needed();
+
// Exports
// -----------------------------------------------------------------------------------
@@ -10545,6 +10903,8 @@ function Calendar_constructor(element, overrides) {
if (windowResizeProxy) {
$(window).unbind('resize', windowResizeProxy);
}
+
+ GlobalEmitter.unneeded();
}
@@ -11176,6 +11536,7 @@ Calendar.defaults = {
//selectable: false,
unselectAuto: true,
+ //selectMinDistance: 0,
dropAccept: '*',
@@ -12551,6 +12912,12 @@ function EventManager() { // assumed to be a calendar
}
+// returns an undo function
+Calendar.prototype.mutateSeg = function(seg, newProps) {
+ return this.mutateEvent(seg.event, newProps);
+};
+
+
// hook for external libs to manipulate event properties upon creation.
// should manipulate the event in-place.
Calendar.prototype.normalizeEvent = function(event) {
@@ -13096,6 +13463,16 @@ var BasicView = FC.BasicView = View.extend({
// forward all hit-related method calls to dayGrid
+ hitsNeeded: function() {
+ this.dayGrid.hitsNeeded();
+ },
+
+
+ hitsNotNeeded: function() {
+ this.dayGrid.hitsNotNeeded();
+ },
+
+
prepareHits: function() {
this.dayGrid.prepareHits();
},
@@ -13623,6 +14000,22 @@ var AgendaView = FC.AgendaView = View.extend({
// forward all hit-related method calls to the grids (dayGrid might not be defined)
+ hitsNeeded: function() {
+ this.timeGrid.hitsNeeded();
+ if (this.dayGrid) {
+ this.dayGrid.hitsNeeded();
+ }
+ },
+
+
+ hitsNotNeeded: function() {
+ this.timeGrid.hitsNotNeeded();
+ if (this.dayGrid) {
+ this.dayGrid.hitsNotNeeded();
+ }
+ },
+
+
prepareHits: function() {
this.timeGrid.prepareHits();
if (this.dayGrid) {
diff --git a/library/fullcalendar/fullcalendar.min.css b/library/fullcalendar/fullcalendar.min.css
index 1339120b4..255dbfffa 100644
--- a/library/fullcalendar/fullcalendar.min.css
+++ b/library/fullcalendar/fullcalendar.min.css
@@ -1,5 +1,5 @@
/*!
- * FullCalendar v3.1.0 Stylesheet
- * Docs & License: http://fullcalendar.io/
- * (c) 2016 Adam Shaw
+ * FullCalendar v3.2.0 Stylesheet
+ * Docs & License: https://fullcalendar.io/
+ * (c) 2017 Adam Shaw
*/.fc-icon,body .fc{font-size:1em}.fc-button-group,.fc-icon{display:inline-block}.fc-bg,.fc-row .fc-bgevent-skeleton,.fc-row .fc-highlight-skeleton{bottom:0}.fc-icon,.fc-unselectable{-khtml-user-select:none;-webkit-touch-callout:none}.fc{direction:ltr;text-align:left}.fc-rtl{text-align:right}.fc th,.fc-basic-view td.fc-week-number,.fc-icon,.fc-toolbar{text-align:center}.fc-unthemed .fc-content,.fc-unthemed .fc-divider,.fc-unthemed .fc-list-heading td,.fc-unthemed .fc-list-view,.fc-unthemed .fc-popover,.fc-unthemed .fc-row,.fc-unthemed tbody,.fc-unthemed td,.fc-unthemed th,.fc-unthemed thead{border-color:#ddd}.fc-unthemed .fc-popover{background-color:#fff}.fc-unthemed .fc-divider,.fc-unthemed .fc-list-heading td,.fc-unthemed .fc-popover .fc-header{background:#eee}.fc-unthemed .fc-popover .fc-header .fc-close{color:#666}.fc-unthemed td.fc-today{background:#fcf8e3}.fc-highlight{background:#bce8f1;opacity:.3}.fc-bgevent{background:#8fdf82;opacity:.3}.fc-nonbusiness{background:#d7d7d7}.fc-icon{height:1em;line-height:1em;overflow:hidden;font-family:"Courier New",Courier,monospace;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none}.fc-icon:after{position:relative}.fc-icon-left-single-arrow:after{content:"\02039";font-weight:700;font-size:200%;top:-7%}.fc-icon-right-single-arrow:after{content:"\0203A";font-weight:700;font-size:200%;top:-7%}.fc-icon-left-double-arrow:after{content:"\000AB";font-size:160%;top:-7%}.fc-icon-right-double-arrow:after{content:"\000BB";font-size:160%;top:-7%}.fc-icon-left-triangle:after{content:"\25C4";font-size:125%;top:3%}.fc-icon-right-triangle:after{content:"\25BA";font-size:125%;top:3%}.fc-icon-down-triangle:after{content:"\25BC";font-size:125%;top:2%}.fc-icon-x:after{content:"\000D7";font-size:200%;top:6%}.fc button{-moz-box-sizing:border-box;-webkit-box-sizing:border-box;box-sizing:border-box;margin:0;height:2.1em;padding:0 .6em;font-size:1em;white-space:nowrap;cursor:pointer}.fc button::-moz-focus-inner{margin:0;padding:0}.fc-state-default{border:1px solid;background-color:#f5f5f5;background-image:-moz-linear-gradient(top,#fff,#e6e6e6);background-image:-webkit-gradient(linear,0 0,0 100%,from(#fff),to(#e6e6e6));background-image:-webkit-linear-gradient(top,#fff,#e6e6e6);background-image:-o-linear-gradient(top,#fff,#e6e6e6);background-image:linear-gradient(to bottom,#fff,#e6e6e6);background-repeat:repeat-x;border-color:#e6e6e6 #e6e6e6 #bfbfbf;border-color:rgba(0,0,0,.1) rgba(0,0,0,.1) rgba(0,0,0,.25);color:#333;text-shadow:0 1px 1px rgba(255,255,255,.75);box-shadow:inset 0 1px 0 rgba(255,255,255,.2),0 1px 2px rgba(0,0,0,.05)}.fc-state-default.fc-corner-left{border-top-left-radius:4px;border-bottom-left-radius:4px}.fc-state-default.fc-corner-right{border-top-right-radius:4px;border-bottom-right-radius:4px}.fc button .fc-icon{position:relative;top:-.05em;margin:0 .2em;vertical-align:middle}.fc-state-active,.fc-state-disabled,.fc-state-down,.fc-state-hover{color:#333;background-color:#e6e6e6}.fc-state-hover{color:#333;text-decoration:none;background-position:0 -15px;-webkit-transition:background-position .1s linear;-moz-transition:background-position .1s linear;-o-transition:background-position .1s linear;transition:background-position .1s linear}.fc-state-active,.fc-state-down{background-color:#ccc;background-image:none;box-shadow:inset 0 2px 4px rgba(0,0,0,.15),0 1px 2px rgba(0,0,0,.05)}.fc-state-disabled{cursor:default;background-image:none;opacity:.65;box-shadow:none}.fc-event.fc-draggable,.fc-event[href],.fc-popover .fc-header .fc-close,a[data-goto]{cursor:pointer}.fc .fc-button-group>*{float:left;margin:0 0 0 -1px}.fc .fc-button-group>:first-child{margin-left:0}.fc-popover{position:absolute;box-shadow:0 2px 6px rgba(0,0,0,.15)}.fc-popover .fc-header{padding:2px 4px}.fc-popover .fc-header .fc-title{margin:0 2px}.fc-ltr .fc-popover .fc-header .fc-title,.fc-rtl .fc-popover .fc-header .fc-close{float:left}.fc-ltr .fc-popover .fc-header .fc-close,.fc-rtl .fc-popover .fc-header .fc-title{float:right}.fc-unthemed .fc-popover{border-width:1px;border-style:solid}.fc-unthemed .fc-popover .fc-header .fc-close{font-size:.9em;margin-top:2px}.fc-popover>.ui-widget-header+.ui-widget-content{border-top:0}.fc-divider{border-style:solid;border-width:1px}hr.fc-divider{height:0;margin:0;padding:0 0 2px;border-width:1px 0}.fc-bg table,.fc-row .fc-bgevent-skeleton table,.fc-row .fc-highlight-skeleton table{height:100%}.fc-clear{clear:both}.fc-bg,.fc-bgevent-skeleton,.fc-helper-skeleton,.fc-highlight-skeleton{position:absolute;top:0;left:0;right:0}.fc table{width:100%;box-sizing:border-box;table-layout:fixed;border-collapse:collapse;border-spacing:0;font-size:1em}.fc td,.fc th{border-style:solid;border-width:1px;padding:0;vertical-align:top}.fc td.fc-today{border-style:double}a[data-goto]:hover{text-decoration:underline}.fc .fc-row{border-style:solid;border-width:0}.fc-row table{border-left:0 hidden transparent;border-right:0 hidden transparent;border-bottom:0 hidden transparent}.fc-row:first-child table{border-top:0 hidden transparent}.fc-row{position:relative}.fc-row .fc-bg{z-index:1}.fc-row .fc-bgevent-skeleton td,.fc-row .fc-highlight-skeleton td{border-color:transparent}.fc-row .fc-bgevent-skeleton{z-index:2}.fc-row .fc-highlight-skeleton{z-index:3}.fc-row .fc-content-skeleton{position:relative;z-index:4;padding-bottom:2px}.fc-row .fc-helper-skeleton{z-index:5}.fc-row .fc-content-skeleton td,.fc-row .fc-helper-skeleton td{background:0 0;border-color:transparent;border-bottom:0}.fc-row .fc-content-skeleton tbody td,.fc-row .fc-helper-skeleton tbody td{border-top:0}.fc-scroller{-webkit-overflow-scrolling:touch}.fc-row.fc-rigid,.fc-time-grid-event{overflow:hidden}.fc-scroller>.fc-day-grid,.fc-scroller>.fc-time-grid{position:relative;width:100%}.fc-event{position:relative;display:block;font-size:.85em;line-height:1.3;border-radius:3px;border:1px solid #3a87ad;font-weight:400}.fc-event,.fc-event-dot{background-color:#3a87ad}.fc-event,.fc-event:hover,.ui-widget .fc-event{color:#fff;text-decoration:none}.fc-not-allowed,.fc-not-allowed .fc-event{cursor:not-allowed}.fc-event .fc-bg{z-index:1;background:#fff;opacity:.25}.fc-event .fc-content{position:relative;z-index:2}.fc-event .fc-resizer{position:absolute;z-index:4;display:none}.fc-event.fc-allow-mouse-resize .fc-resizer,.fc-event.fc-selected .fc-resizer{display:block}.fc-event.fc-selected .fc-resizer:before{content:"";position:absolute;z-index:9999;top:50%;left:50%;width:40px;height:40px;margin-left:-20px;margin-top:-20px}.fc-event.fc-selected{z-index:9999!important;box-shadow:0 2px 5px rgba(0,0,0,.2)}.fc-event.fc-selected.fc-dragging{box-shadow:0 2px 7px rgba(0,0,0,.3)}.fc-h-event.fc-selected:before{content:"";position:absolute;z-index:3;top:-10px;bottom:-10px;left:0;right:0}.fc-ltr .fc-h-event.fc-not-start,.fc-rtl .fc-h-event.fc-not-end{margin-left:0;border-left-width:0;padding-left:1px;border-top-left-radius:0;border-bottom-left-radius:0}.fc-ltr .fc-h-event.fc-not-end,.fc-rtl .fc-h-event.fc-not-start{margin-right:0;border-right-width:0;padding-right:1px;border-top-right-radius:0;border-bottom-right-radius:0}.fc-ltr .fc-h-event .fc-start-resizer,.fc-rtl .fc-h-event .fc-end-resizer{cursor:w-resize;left:-1px}.fc-ltr .fc-h-event .fc-end-resizer,.fc-rtl .fc-h-event .fc-start-resizer{cursor:e-resize;right:-1px}.fc-h-event.fc-allow-mouse-resize .fc-resizer{width:7px;top:-1px;bottom:-1px}.fc-h-event.fc-selected .fc-resizer{border-radius:4px;border-width:1px;width:6px;height:6px;border-style:solid;border-color:inherit;background:#fff;top:50%;margin-top:-4px}.fc-ltr .fc-h-event.fc-selected .fc-start-resizer,.fc-rtl .fc-h-event.fc-selected .fc-end-resizer{margin-left:-4px}.fc-ltr .fc-h-event.fc-selected .fc-end-resizer,.fc-rtl .fc-h-event.fc-selected .fc-start-resizer{margin-right:-4px}.fc-day-grid-event{margin:1px 2px 0;padding:0 1px}tr:first-child>td>.fc-day-grid-event{margin-top:2px}.fc-day-grid-event.fc-selected:after{content:"";position:absolute;z-index:1;top:-1px;right:-1px;bottom:-1px;left:-1px;background:#000;opacity:.25}.fc-day-grid-event .fc-content{white-space:nowrap;overflow:hidden}.fc-day-grid-event .fc-time{font-weight:700}.fc-ltr .fc-day-grid-event.fc-allow-mouse-resize .fc-start-resizer,.fc-rtl .fc-day-grid-event.fc-allow-mouse-resize .fc-end-resizer{margin-left:-2px}.fc-ltr .fc-day-grid-event.fc-allow-mouse-resize .fc-end-resizer,.fc-rtl .fc-day-grid-event.fc-allow-mouse-resize .fc-start-resizer{margin-right:-2px}a.fc-more{margin:1px 3px;font-size:.85em;cursor:pointer;text-decoration:none}a.fc-more:hover{text-decoration:underline}.fc-limited{display:none}.fc-day-grid .fc-row{z-index:1}.fc-more-popover{z-index:2;width:220px}.fc-more-popover .fc-event-container{padding:10px}.fc-now-indicator{position:absolute;border:0 solid red}.fc-unselectable{-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;-webkit-tap-highlight-color:transparent}.fc-toolbar.fc-header-toolbar{margin-bottom:1em}.fc-toolbar.fc-footer-toolbar{margin-top:1em}.fc-toolbar .fc-left{float:left}.fc-toolbar .fc-right{float:right}.fc-toolbar .fc-center{display:inline-block}.fc .fc-toolbar>*>*{float:left;margin-left:.75em}.fc .fc-toolbar>*>:first-child{margin-left:0}.fc-toolbar h2{margin:0}.fc-toolbar button{position:relative}.fc-toolbar .fc-state-hover,.fc-toolbar .ui-state-hover{z-index:2}.fc-toolbar .fc-state-down{z-index:3}.fc-toolbar .fc-state-active,.fc-toolbar .ui-state-active{z-index:4}.fc-toolbar button:focus{z-index:5}.fc-view-container *,.fc-view-container :after,.fc-view-container :before{-webkit-box-sizing:content-box;-moz-box-sizing:content-box;box-sizing:content-box}.fc-view,.fc-view>table{position:relative;z-index:1}.fc-basicDay-view .fc-content-skeleton,.fc-basicWeek-view .fc-content-skeleton{padding-bottom:1em}.fc-basic-view .fc-body .fc-row{min-height:4em}.fc-row.fc-rigid .fc-content-skeleton{position:absolute;top:0;left:0;right:0}.fc-day-top.fc-other-month{opacity:.3}.fc-basic-view .fc-day-number,.fc-basic-view .fc-week-number{padding:2px}.fc-basic-view th.fc-day-number,.fc-basic-view th.fc-week-number{padding:0 2px}.fc-ltr .fc-basic-view .fc-day-top .fc-day-number{float:right}.fc-rtl .fc-basic-view .fc-day-top .fc-day-number{float:left}.fc-ltr .fc-basic-view .fc-day-top .fc-week-number{float:left;border-radius:0 0 3px}.fc-rtl .fc-basic-view .fc-day-top .fc-week-number{float:right;border-radius:0 0 0 3px}.fc-basic-view .fc-day-top .fc-week-number{min-width:1.5em;text-align:center;background-color:#f2f2f2;color:grey}.fc-basic-view td.fc-week-number>*{display:inline-block;min-width:1.25em}.fc-agenda-view .fc-day-grid{position:relative;z-index:2}.fc-agenda-view .fc-day-grid .fc-row{min-height:3em}.fc-agenda-view .fc-day-grid .fc-row .fc-content-skeleton{padding-bottom:1em}.fc .fc-axis{vertical-align:middle;padding:0 4px;white-space:nowrap}.fc-ltr .fc-axis{text-align:right}.fc-rtl .fc-axis{text-align:left}.ui-widget td.fc-axis{font-weight:400}.fc-time-grid,.fc-time-grid-container{position:relative;z-index:1}.fc-time-grid{min-height:100%}.fc-time-grid table{border:0 hidden transparent}.fc-time-grid>.fc-bg{z-index:1}.fc-time-grid .fc-slats,.fc-time-grid>hr{position:relative;z-index:2}.fc-time-grid .fc-content-col{position:relative}.fc-time-grid .fc-content-skeleton{position:absolute;z-index:3;top:0;left:0;right:0}.fc-time-grid .fc-business-container{position:relative;z-index:1}.fc-time-grid .fc-bgevent-container{position:relative;z-index:2}.fc-time-grid .fc-highlight-container{z-index:3;position:relative}.fc-time-grid .fc-event-container{position:relative;z-index:4}.fc-time-grid .fc-now-indicator-line{z-index:5}.fc-time-grid .fc-helper-container{position:relative;z-index:6}.fc-time-grid .fc-slats td{height:1.5em;border-bottom:0}.fc-time-grid .fc-slats .fc-minor td{border-top-style:dotted}.fc-time-grid .fc-slats .ui-widget-content{background:0 0}.fc-time-grid .fc-highlight{position:absolute;left:0;right:0}.fc-ltr .fc-time-grid .fc-event-container{margin:0 2.5% 0 2px}.fc-rtl .fc-time-grid .fc-event-container{margin:0 2px 0 2.5%}.fc-time-grid .fc-bgevent,.fc-time-grid .fc-event{position:absolute;z-index:1}.fc-time-grid .fc-bgevent{left:0;right:0}.fc-v-event.fc-not-start{border-top-width:0;padding-top:1px;border-top-left-radius:0;border-top-right-radius:0}.fc-v-event.fc-not-end{border-bottom-width:0;padding-bottom:1px;border-bottom-left-radius:0;border-bottom-right-radius:0}.fc-time-grid-event.fc-selected{overflow:visible}.fc-time-grid-event.fc-selected .fc-bg{display:none}.fc-time-grid-event .fc-content{overflow:hidden}.fc-time-grid-event .fc-time,.fc-time-grid-event .fc-title{padding:0 1px}.fc-time-grid-event .fc-time{font-size:.85em;white-space:nowrap}.fc-time-grid-event.fc-short .fc-content{white-space:nowrap}.fc-time-grid-event.fc-short .fc-time,.fc-time-grid-event.fc-short .fc-title{display:inline-block;vertical-align:top}.fc-time-grid-event.fc-short .fc-time span{display:none}.fc-time-grid-event.fc-short .fc-time:before{content:attr(data-start)}.fc-time-grid-event.fc-short .fc-time:after{content:"\000A0-\000A0"}.fc-time-grid-event.fc-short .fc-title{font-size:.85em;padding:0}.fc-time-grid-event.fc-allow-mouse-resize .fc-resizer{left:0;right:0;bottom:0;height:8px;overflow:hidden;line-height:8px;font-size:11px;font-family:monospace;text-align:center;cursor:s-resize}.fc-time-grid-event.fc-allow-mouse-resize .fc-resizer:after{content:"="}.fc-time-grid-event.fc-selected .fc-resizer{border-radius:5px;border-width:1px;width:8px;height:8px;border-style:solid;border-color:inherit;background:#fff;left:50%;margin-left:-5px;bottom:-5px}.fc-time-grid .fc-now-indicator-line{border-top-width:1px;left:0;right:0}.fc-time-grid .fc-now-indicator-arrow{margin-top:-5px}.fc-ltr .fc-time-grid .fc-now-indicator-arrow{left:0;border-width:5px 0 5px 6px;border-top-color:transparent;border-bottom-color:transparent}.fc-rtl .fc-time-grid .fc-now-indicator-arrow{right:0;border-width:5px 6px 5px 0;border-top-color:transparent;border-bottom-color:transparent}.fc-event-dot{display:inline-block;width:10px;height:10px;border-radius:5px}.fc-rtl .fc-list-view{direction:rtl}.fc-list-view{border-width:1px;border-style:solid}.fc .fc-list-table{table-layout:auto}.fc-list-table td{border-width:1px 0 0;padding:8px 14px}.fc-list-table tr:first-child td{border-top-width:0}.fc-list-heading{border-bottom-width:1px}.fc-list-heading td{font-weight:700}.fc-ltr .fc-list-heading-main{float:left}.fc-ltr .fc-list-heading-alt,.fc-rtl .fc-list-heading-main{float:right}.fc-rtl .fc-list-heading-alt{float:left}.fc-list-item.fc-has-url{cursor:pointer}.fc-list-item:hover td{background-color:#f5f5f5}.fc-list-item-marker,.fc-list-item-time{white-space:nowrap;width:1px}.fc-ltr .fc-list-item-marker{padding-right:0}.fc-rtl .fc-list-item-marker{padding-left:0}.fc-list-item-title a{text-decoration:none;color:inherit}.fc-list-item-title a[href]:hover{text-decoration:underline}.fc-list-empty-wrap2{position:absolute;top:0;left:0;right:0;bottom:0}.fc-list-empty-wrap1{width:100%;height:100%;display:table}.fc-list-empty{display:table-cell;vertical-align:middle;text-align:center}.fc-unthemed .fc-list-empty{background-color:#eee} \ No newline at end of file
diff --git a/library/fullcalendar/fullcalendar.min.js b/library/fullcalendar/fullcalendar.min.js
index 8484b7c45..c5eb8c751 100644
--- a/library/fullcalendar/fullcalendar.min.js
+++ b/library/fullcalendar/fullcalendar.min.js
@@ -1,10 +1,10 @@
/*!
- * FullCalendar v3.1.0
- * Docs & License: http://fullcalendar.io/
- * (c) 2016 Adam Shaw
+ * FullCalendar v3.2.0
+ * Docs & License: https://fullcalendar.io/
+ * (c) 2017 Adam Shaw
*/
-!function(t){"function"==typeof define&&define.amd?define(["jquery","moment"],t):"object"==typeof exports?module.exports=t(require("jquery"),require("moment")):t(jQuery,moment)}(function(t,e){function n(t){return q(t,$t)}function i(t,e){e.left&&t.css({"border-left-width":1,"margin-left":e.left-1}),e.right&&t.css({"border-right-width":1,"margin-right":e.right-1})}function r(t){t.css({"margin-left":"","margin-right":"","border-left-width":"","border-right-width":""})}function s(){t("body").addClass("fc-not-allowed")}function o(){t("body").removeClass("fc-not-allowed")}function l(e,n,i){var r=Math.floor(n/e.length),s=Math.floor(n-r*(e.length-1)),o=[],l=[],u=[],c=0;a(e),e.each(function(n,i){var a=n===e.length-1?s:r,d=t(i).outerHeight(!0);d<a?(o.push(i),l.push(d),u.push(t(i).height())):c+=d}),i&&(n-=c,r=Math.floor(n/o.length),s=Math.floor(n-r*(o.length-1))),t(o).each(function(e,n){var i=e===o.length-1?s:r,a=l[e],c=u[e],d=i-(a-c);a<i&&t(n).height(d)})}function a(t){t.height("")}function u(e){var n=0;return e.find("> *").each(function(e,i){var r=t(i).outerWidth();r>n&&(n=r)}),n++,e.width(n),n}function c(t,e){var n,i=t.add(e);return i.css({position:"relative",left:-1}),n=t.outerHeight()-e.outerHeight(),i.css({position:"",left:""}),n}function d(e){var n=e.css("position"),i=e.parents().filter(function(){var e=t(this);return/(auto|scroll)/.test(e.css("overflow")+e.css("overflow-y")+e.css("overflow-x"))}).eq(0);return"fixed"!==n&&i.length?i:t(e[0].ownerDocument||document)}function h(t,e){var n=t.offset(),i=n.left-(e?e.left:0),r=n.top-(e?e.top:0);return{left:i,right:i+t.outerWidth(),top:r,bottom:r+t.outerHeight()}}function f(t,e){var n=t.offset(),i=p(t),r=n.left+y(t,"border-left-width")+i.left-(e?e.left:0),s=n.top+y(t,"border-top-width")+i.top-(e?e.top:0);return{left:r,right:r+t[0].clientWidth,top:s,bottom:s+t[0].clientHeight}}function g(t,e){var n=t.offset(),i=n.left+y(t,"border-left-width")+y(t,"padding-left")-(e?e.left:0),r=n.top+y(t,"border-top-width")+y(t,"padding-top")-(e?e.top:0);return{left:i,right:i+t.width(),top:r,bottom:r+t.height()}}function p(t){var e=t.innerWidth()-t[0].clientWidth,n={left:0,right:0,top:0,bottom:t.innerHeight()-t[0].clientHeight};return v()&&"rtl"==t.css("direction")?n.left=e:n.right=e,n}function v(){return null===Qt&&(Qt=m()),Qt}function m(){var e=t("<div><div/></div>").css({position:"absolute",top:-1e3,left:0,border:0,padding:0,overflow:"scroll",direction:"rtl"}).appendTo("body"),n=e.children(),i=n.offset().left>e.offset().left;return e.remove(),i}function y(t,e){return parseFloat(t.css(e))||0}function S(t){return 1==t.which&&!t.ctrlKey}function w(t){if(void 0!==t.pageX)return t.pageX;var e=t.originalEvent.touches;return e?e[0].pageX:void 0}function E(t){if(void 0!==t.pageY)return t.pageY;var e=t.originalEvent.touches;return e?e[0].pageY:void 0}function b(t){return/^touch/.test(t.type)}function D(t){t.addClass("fc-unselectable").on("selectstart",T)}function T(t){t.preventDefault()}function C(t){return!!window.addEventListener&&(window.addEventListener("scroll",t,!0),!0)}function H(t){return!!window.removeEventListener&&(window.removeEventListener("scroll",t,!0),!0)}function R(t,e){var n={left:Math.max(t.left,e.left),right:Math.min(t.right,e.right),top:Math.max(t.top,e.top),bottom:Math.min(t.bottom,e.bottom)};return n.left<n.right&&n.top<n.bottom&&n}function x(t,e){return{left:Math.min(Math.max(t.left,e.left),e.right),top:Math.min(Math.max(t.top,e.top),e.bottom)}}function I(t){return{left:(t.left+t.right)/2,top:(t.top+t.bottom)/2}}function k(t,e){return{left:t.left-e.left,top:t.top-e.top}}function L(e){var n,i,r=[],s=[];for("string"==typeof e?s=e.split(/\s*,\s*/):"function"==typeof e?s=[e]:t.isArray(e)&&(s=e),n=0;n<s.length;n++)i=s[n],"string"==typeof i?r.push("-"==i.charAt(0)?{field:i.substring(1),order:-1}:{field:i,order:1}):"function"==typeof i&&r.push({func:i});return r}function M(t,e,n){var i,r;for(i=0;i<n.length;i++)if(r=B(t,e,n[i]))return r;return 0}function B(t,e,n){return n.func?n.func(t,e):z(t[n.field],e[n.field])*(n.order||1)}function z(e,n){return e||n?null==n?-1:null==e?1:"string"===t.type(e)||"string"===t.type(n)?String(e).localeCompare(String(n)):e-n:0}function F(t,e){var n,i,r,s,o=t.start,l=t.end,a=e.start,u=e.end;if(l>a&&o<u)return o>=a?(n=o.clone(),r=!0):(n=a.clone(),r=!1),l<=u?(i=l.clone(),s=!0):(i=u.clone(),s=!1),{start:n,end:i,isStart:r,isEnd:s}}function N(t,n){return e.duration({days:t.clone().stripTime().diff(n.clone().stripTime(),"days"),ms:t.time()-n.time()})}function G(t,n){return e.duration({days:t.clone().stripTime().diff(n.clone().stripTime(),"days")})}function O(t,n,i){return e.duration(Math.round(t.diff(n,i,!0)),i)}function A(t,e){var n,i,r;for(n=0;n<Kt.length&&(i=Kt[n],r=V(i,t,e),!(r>=1&&ot(r)));n++);return i}function V(t,n,i){return null!=i?i.diff(n,t,!0):e.isDuration(n)?n.as(t):n.end.diff(n.start,t,!0)}function P(t,e,n){var i;return W(n)?(e-t)/n:(i=n.asMonths(),Math.abs(i)>=1&&ot(i)?e.diff(t,"months",!0)/i:e.diff(t,"days",!0)/n.asDays())}function _(t,e){var n,i;return W(t)||W(e)?t/e:(n=t.asMonths(),i=e.asMonths(),Math.abs(n)>=1&&ot(n)&&Math.abs(i)>=1&&ot(i)?n/i:t.asDays()/e.asDays())}function Y(t,n){var i;return W(t)?e.duration(t*n):(i=t.asMonths(),Math.abs(i)>=1&&ot(i)?e.duration({months:i*n}):e.duration({days:t.asDays()*n}))}function W(t){return Boolean(t.hours()||t.minutes()||t.seconds()||t.milliseconds())}function U(t){return"[object Date]"===Object.prototype.toString.call(t)||t instanceof Date}function j(t){return/^\d+\:\d+(?:\:\d+\.?(?:\d{3})?)?$/.test(t)}function q(t,e){var n,i,r,s,o,l,a={};if(e)for(n=0;n<e.length;n++){for(i=e[n],r=[],s=t.length-1;s>=0;s--)if(o=t[s][i],"object"==typeof o)r.unshift(o);else if(void 0!==o){a[i]=o;break}r.length&&(a[i]=q(r))}for(n=t.length-1;n>=0;n--){l=t[n];for(i in l)i in a||(a[i]=l[i])}return a}function Z(t){var e=function(){};return e.prototype=t,new e}function $(t,e){for(var n in t)Q(t,n)&&(e[n]=t[n])}function Q(t,e){return Jt.call(t,e)}function X(e){return/undefined|null|boolean|number|string/.test(t.type(e))}function K(e,n,i){if(t.isFunction(e)&&(e=[e]),e){var r,s;for(r=0;r<e.length;r++)s=e[r].apply(n,i)||s;return s}}function J(){for(var t=0;t<arguments.length;t++)if(void 0!==arguments[t])return arguments[t]}function tt(t){return(t+"").replace(/&/g,"&amp;").replace(/</g,"&lt;").replace(/>/g,"&gt;").replace(/'/g,"&#039;").replace(/"/g,"&quot;").replace(/\n/g,"<br />")}function et(t){return t.replace(/&.*?;/g,"")}function nt(e){var n=[];return t.each(e,function(t,e){null!=e&&n.push(t+":"+e)}),n.join(";")}function it(e){var n=[];return t.each(e,function(t,e){null!=e&&n.push(t+'="'+tt(e)+'"')}),n.join(" ")}function rt(t){return t.charAt(0).toUpperCase()+t.slice(1)}function st(t,e){return t-e}function ot(t){return t%1===0}function lt(t,e){var n=t[e];return function(){return n.apply(t,arguments)}}function at(t,e,n){var i,r,s,o,l,a=function(){var u=+new Date-o;u<e?i=setTimeout(a,e-u):(i=null,n||(l=t.apply(s,r),s=r=null))};return function(){s=this,r=arguments,o=+new Date;var u=n&&!i;return i||(i=setTimeout(a,e)),u&&(l=t.apply(s,r),s=r=null),l}}function ut(n,i,r){var s,o,l,a,u=n[0],c=1==n.length&&"string"==typeof u;return e.isMoment(u)||U(u)||void 0===u?a=e.apply(null,n):(s=!1,o=!1,c?te.test(u)?(u+="-01",n=[u],s=!0,o=!0):(l=ee.exec(u))&&(s=!l[5],o=!0):t.isArray(u)&&(o=!0),a=i||s?e.utc.apply(e,n):e.apply(null,n),s?(a._ambigTime=!0,a._ambigZone=!0):r&&(o?a._ambigZone=!0:c&&a.utcOffset(u))),a._fullCalendar=!0,a}function ct(t,e){return ie.format.call(t,e)}function dt(t,e){return ht(t,mt(e))}function ht(t,e){var n,i="";for(n=0;n<e.length;n++)i+=ft(t,e[n]);return i}function ft(t,e){var n,i;return"string"==typeof e?e:(n=e.token)?se[n]?se[n](t):ct(t,n):e.maybe&&(i=ht(t,e.maybe),i.match(/[1-9]/))?i:""}function gt(t,e,n,i,r){var s;return t=qt.moment.parseZone(t),e=qt.moment.parseZone(e),s=t.localeData(),n=s.longDateFormat(n)||n,i=i||" - ",pt(t,e,mt(n),i,r)}function pt(t,e,n,i,r){var s,o,l,a,u=t.clone().stripZone(),c=e.clone().stripZone(),d="",h="",f="",g="",p="";for(o=0;o<n.length&&(s=vt(t,e,u,c,n[o]),s!==!1);o++)d+=s;for(l=n.length-1;l>o&&(s=vt(t,e,u,c,n[l]),s!==!1);l--)h=s+h;for(a=o;a<=l;a++)f+=ft(t,n[a]),g+=ft(e,n[a]);return(f||g)&&(p=r?g+i+f:f+i+g),d+p+h}function vt(t,e,n,i,r){var s,o;return"string"==typeof r?r:!!((s=r.token)&&(o=oe[s.charAt(0)],o&&n.isSame(i,o)))&&ct(t,s)}function mt(t){return t in le?le[t]:le[t]=yt(t)}function yt(t){for(var e,n=[],i=/\[([^\]]*)\]|\(([^\)]*)\)|(LTS|LT|(\w)\4*o?)|([^\w\[\(]+)/g;e=i.exec(t);)e[1]?n.push(e[1]):e[2]?n.push({maybe:yt(e[2])}):e[3]?n.push({token:e[3]}):e[5]&&n.push(e[5]);return n}function St(){}function wt(t,e){var n;return Q(e,"constructor")&&(n=e.constructor),"function"!=typeof n&&(n=e.constructor=function(){t.apply(this,arguments)}),n.prototype=Z(t.prototype),$(e,n.prototype),$(t,n),n}function Et(t,e){$(e,t.prototype)}function bt(e){var n=t.Deferred(),i=n.promise();if("function"==typeof e&&e(function(t){bt.immediate&&(i._value=t),n.resolve(t)},function(){n.reject()}),bt.immediate){var r=i.then;i.then=function(t,e){var n=i.state();if("resolved"===n){if("function"==typeof t)return bt.resolve(t(i._value))}else if("rejected"===n&&"function"==typeof e)return e(),i;return r.call(i,t,e)}}return i}function Dt(t){function e(t){return new bt(function(e){var i=function(){bt.resolve(t()).then(e).then(function(){n.shift(),n.length&&n[0]()})};n.push(i),1===n.length&&i()})}var n=[];this.add="number"==typeof t?at(e,t):e,this.addQuickly=e}function Tt(t,e){return!t&&!e||!(!t||!e)&&(t.component===e.component&&Ct(t,e)&&Ct(e,t))}function Ct(t,e){for(var n in t)if(!/^(component|left|right|top|bottom)$/.test(n)&&t[n]!==e[n])return!1;return!0}function Ht(t){return{start:t.start.clone(),end:t.end?t.end.clone():null,allDay:t.allDay}}function Rt(t){var e=It(t);return"background"===e||"inverse-background"===e}function xt(t){return"inverse-background"===It(t)}function It(t){return J((t.source||{}).rendering,t.rendering)}function kt(t){var e,n,i={};for(e=0;e<t.length;e++)n=t[e],(i[n._id]||(i[n._id]=[])).push(n);return i}function Lt(t,e){return t.start-e.start}function Mt(n){var i,r,s,o,l=qt.dataAttrPrefix;return l&&(l+="-"),i=n.data(l+"event")||null,i&&(i="object"==typeof i?t.extend({},i):{},r=i.start,null==r&&(r=i.time),s=i.duration,o=i.stick,delete i.start,delete i.time,delete i.duration,delete i.stick),null==r&&(r=n.data(l+"start")),null==r&&(r=n.data(l+"time")),null==s&&(s=n.data(l+"duration")),null==o&&(o=n.data(l+"stick")),r=null!=r?e.duration(r):null,s=null!=s?e.duration(s):null,o=Boolean(o),{eventProps:i,startTime:r,duration:s,stick:o}}function Bt(t,e){var n,i;for(n=0;n<e.length;n++)if(i=e[n],i.leftCol<=t.rightCol&&i.rightCol>=t.leftCol)return!0;return!1}function zt(t,e){return t.leftCol-e.leftCol}function Ft(t){var e,n,i,r=[];for(e=0;e<t.length;e++){for(n=t[e],i=0;i<r.length&&Ot(n,r[i]).length;i++);n.level=i,(r[i]||(r[i]=[])).push(n)}return r}function Nt(t){var e,n,i,r,s;for(e=0;e<t.length;e++)for(n=t[e],i=0;i<n.length;i++)for(r=n[i],r.forwardSegs=[],s=e+1;s<t.length;s++)Ot(r,t[s],r.forwardSegs)}function Gt(t){var e,n,i=t.forwardSegs,r=0;if(void 0===t.forwardPressure){for(e=0;e<i.length;e++)n=i[e],Gt(n),r=Math.max(r,1+n.forwardPressure);t.forwardPressure=r}}function Ot(t,e,n){n=n||[];for(var i=0;i<e.length;i++)At(t,e[i])&&n.push(e[i]);return n}function At(t,e){return t.bottom>e.top&&t.top<e.bottom}function Vt(t){this.items=t||[]}function Pt(e,n){function i(t){n=t}function r(){var i=n.layout;p=e.options.theme?"ui":"fc",i?(g?g.empty():g=this.el=t("<div class='fc-toolbar "+n.extraClasses+"'/>"),g.append(o("left")).append(o("right")).append(o("center")).append('<div class="fc-clear"/>')):s()}function s(){g&&(g.remove(),g=f.el=null)}function o(i){var r=t('<div class="fc-'+i+'"/>'),s=n.layout[i];return s&&t.each(s.split(" "),function(n){var i,s=t(),o=!0;t.each(this.split(","),function(n,i){var r,l,a,u,c,d,h,f,g,m;"title"==i?(s=s.add(t("<h2>&nbsp;</h2>")),o=!1):((r=(e.options.customButtons||{})[i])?(a=function(t){r.click&&r.click.call(m[0],t)},u="",c=r.text):(l=e.getViewSpec(i))?(a=function(){e.changeView(i)},v.push(i),u=l.buttonTextOverride,c=l.buttonTextDefault):e[i]&&(a=function(){e[i]()},u=(e.overrides.buttonText||{})[i],c=e.options.buttonText[i]),a&&(d=r?r.themeIcon:e.options.themeButtonIcons[i],h=r?r.icon:e.options.buttonIcons[i],f=u?tt(u):d&&e.options.theme?"<span class='ui-icon ui-icon-"+d+"'></span>":h&&!e.options.theme?"<span class='fc-icon fc-icon-"+h+"'></span>":tt(c),g=["fc-"+i+"-button",p+"-button",p+"-state-default"],m=t('<button type="button" class="'+g.join(" ")+'">'+f+"</button>").click(function(t){m.hasClass(p+"-state-disabled")||(a(t),(m.hasClass(p+"-state-active")||m.hasClass(p+"-state-disabled"))&&m.removeClass(p+"-state-hover"))}).mousedown(function(){m.not("."+p+"-state-active").not("."+p+"-state-disabled").addClass(p+"-state-down")}).mouseup(function(){m.removeClass(p+"-state-down")}).hover(function(){m.not("."+p+"-state-active").not("."+p+"-state-disabled").addClass(p+"-state-hover")},function(){m.removeClass(p+"-state-hover").removeClass(p+"-state-down")}),s=s.add(m)))}),o&&s.first().addClass(p+"-corner-left").end().last().addClass(p+"-corner-right").end(),s.length>1?(i=t("<div/>"),o&&i.addClass("fc-button-group"),i.append(s),r.append(i)):r.append(s)}),r}function l(t){g&&g.find("h2").text(t)}function a(t){g&&g.find(".fc-"+t+"-button").addClass(p+"-state-active")}function u(t){g&&g.find(".fc-"+t+"-button").removeClass(p+"-state-active")}function c(t){g&&g.find(".fc-"+t+"-button").prop("disabled",!0).addClass(p+"-state-disabled")}function d(t){g&&g.find(".fc-"+t+"-button").prop("disabled",!1).removeClass(p+"-state-disabled")}function h(){return v}var f=this;f.setToolbarOptions=i,f.render=r,f.removeElement=s,f.updateTitle=l,f.activateButton=a,f.deactivateButton=u,f.disableButton=c,f.enableButton=d,f.getViewsWithButtons=h,f.el=null;var g,p,v=[]}function _t(n,i){function r(t){t._locale=Y}function s(){q?a()&&(f(),u()):o()}function o(){n.addClass("fc"),n.on("click.fc","a[data-goto]",function(e){var n=t(this),i=n.data("goto"),r=_.moment(i.date),s=i.type,o=Q.opt("navLink"+rt(s)+"Click");"function"==typeof o?o(r,e):("string"==typeof o&&(s=o),B(r,s))}),_.bindOption("theme",function(t){$=t?"ui":"fc",n.toggleClass("ui-widget",t),n.toggleClass("fc-unthemed",!t)}),_.bindOptions(["isRTL","locale"],function(t){n.toggleClass("fc-ltr",!t),n.toggleClass("fc-rtl",t)}),q=t("<div class='fc-view-container'/>").prependTo(n);var e=y();W=new Vt(e),U=_.header=e[0],j=_.footer=e[1],E(),b(),u(_.options.defaultView),_.options.handleWindowResize&&(K=at(v,_.options.windowResizeDelay),t(window).resize(K))}function l(){Q&&Q.removeElement(),W.proxyCall("removeElement"),q.remove(),n.removeClass("fc fc-ltr fc-rtl fc-unthemed ui-widget"),n.off(".fc"),K&&t(window).unbind("resize",K)}function a(){return n.is(":visible")}function u(e,n){nt++;var i=Q&&e&&Q.type!==e;i&&(F(),c()),!Q&&e&&(Q=_.view=et[e]||(et[e]=_.instantiateView(e)),Q.setElement(t("<div class='fc-view fc-"+e+"-view' />").appendTo(q)),W.proxyCall("activateButton",e)),Q&&(J=Q.massageCurrentDate(J),Q.isDateSet&&J>=Q.intervalStart&&J<Q.intervalEnd||a()&&(n&&Q.captureInitialScroll(n),Q.setDate(J,n),n&&Q.releaseScroll(),D())),i&&N(),nt--}function c(){W.proxyCall("deactivateButton",Q.type),Q.removeElement(),Q=_.view=null}function d(){nt++,F();var t=Q.type,e=Q.queryScroll();c(),f(),u(t,e),N(),nt--}function h(t){if(a())return t&&g(),nt++,Q.updateSize(!0),nt--,!0}function f(){a()&&g()}function g(){var t=_.options.contentHeight,e=_.options.height;X="number"==typeof t?t:"function"==typeof t?t():"number"==typeof e?e-p():"function"==typeof e?e()-p():"parent"===e?n.parent().height()-p():Math.round(q.width()/Math.max(_.options.aspectRatio,.5))}function p(){return W.items.reduce(function(t,e){var n=e.el?e.el.outerHeight(!0):0;return t+n},0)}function v(t){!nt&&t.target===window&&Q.start&&h(!0)&&Q.publiclyTrigger("windowResize",tt)}function m(){a()&&_.reportEventChange()}function y(){return[new Pt(_,S()),new Pt(_,w())]}function S(){return{extraClasses:"fc-header-toolbar",layout:_.options.header}}function w(){return{extraClasses:"fc-footer-toolbar",layout:_.options.footer}}function E(){U.setToolbarOptions(S()),U.render(),U.el&&n.prepend(U.el)}function b(){j.setToolbarOptions(w()),j.render(),j.el&&n.append(j.el)}function D(){var t=_.getNow();t>=Q.intervalStart&&t<Q.intervalEnd?W.proxyCall("disableButton","today"):W.proxyCall("enableButton","today")}function T(t,e){Q.select(_.buildSelectSpan.apply(_,arguments))}function C(){Q&&Q.unselect()}function H(){J=Q.computePrevDate(J),u()}function R(){J=Q.computeNextDate(J),u()}function x(){J.add(-1,"years"),u()}function I(){J.add(1,"years"),u()}function k(){J=_.getNow(),u()}function L(t){J=_.moment(t).stripZone(),u()}function M(t){J.add(e.duration(t)),u()}function B(t,e){var n;e=e||"day",n=_.getViewSpec(e)||_.getUnitViewSpec(e),J=t.clone(),u(n?n.type:null)}function z(){return _.applyTimezone(J)}function F(){it++||q.css({width:"100%",height:q.height(),overflow:"hidden"})}function N(){--it||q.css({width:"",height:"",overflow:""})}function G(){return _}function O(){return Q}function A(t,e){var n;if("string"==typeof t){if(void 0===e)return _.options[t];n={},n[t]=e,V(n)}else"object"==typeof t&&V(t)}function V(t){var e,n=0;for(e in t)_.dynamicOverrides[e]=t[e];_.viewSpecCache={},_.populateOptionsHash();for(e in t)_.triggerOptionHandlers(e),n++;if(1===n){if("height"===e||"contentHeight"===e||"aspectRatio"===e)return void h(!0);if("defaultDate"===e)return;if("businessHours"===e)return void(Q&&(Q.unrenderBusinessHours(),Q.renderBusinessHours()));if("timezone"===e)return _.rezoneArrayEventSources(),void _.refetchEvents()}E(),b(),et={},d()}function P(t,e){var n=Array.prototype.slice.call(arguments,2);if(e=e||tt,this.triggerWith(t,e,n),_.options[t])return _.options[t].apply(e,n)}var _=this;_.render=s,_.destroy=l,_.rerenderEvents=m,_.changeView=u,_.select=T,_.unselect=C,_.prev=H,_.next=R,_.prevYear=x,_.nextYear=I,_.today=k,_.gotoDate=L,_.incrementDate=M,_.zoomTo=B,_.getDate=z,_.getCalendar=G,_.getView=O,_.option=A,_.publiclyTrigger=P,_.dynamicOverrides={},_.viewSpecCache={},_.optionHandlers={},_.overrides=t.extend({},i),_.populateOptionsHash();var Y;_.bindOptions(["locale","monthNames","monthNamesShort","dayNames","dayNamesShort","firstDay","weekNumberCalculation"],function(t,e,n,i,s,o,l){if("iso"===l&&(l="ISO"),Y=Z(Wt(t)),e&&(Y._months=e),n&&(Y._monthsShort=n),i&&(Y._weekdays=i),s&&(Y._weekdaysShort=s),null==o&&"ISO"===l&&(o=1),null!=o){var a=Z(Y._week);a.dow=o,Y._week=a}"ISO"!==l&&"local"!==l&&"function"!=typeof l||(Y._fullCalendar_weekCalc=l),J&&r(J)}),_.defaultAllDayEventDuration=e.duration(_.options.defaultAllDayEventDuration),_.defaultTimedEventDuration=e.duration(_.options.defaultTimedEventDuration),_.moment=function(){var t;return"local"===_.options.timezone?(t=qt.moment.apply(null,arguments),t.hasTime()&&t.local()):t="UTC"===_.options.timezone?qt.moment.utc.apply(null,arguments):qt.moment.parseZone.apply(null,arguments),r(t),t},_.localizeMoment=r,_.getIsAmbigTimezone=function(){return"local"!==_.options.timezone&&"UTC"!==_.options.timezone},_.applyTimezone=function(t){if(!t.hasTime())return t.clone();var e,n=_.moment(t.toArray()),i=t.time()-n.time();return i&&(e=n.clone().add(i),t.time()-e.time()===0&&(n=e)),n},_.getNow=function(){var t=_.options.now;return"function"==typeof t&&(t=t()),_.moment(t).stripZone()},_.getEventEnd=function(t){return t.end?t.end.clone():_.getDefaultEventEnd(t.allDay,t.start)},_.getDefaultEventEnd=function(t,e){var n=e.clone();return t?n.stripTime().add(_.defaultAllDayEventDuration):n.add(_.defaultTimedEventDuration),_.getIsAmbigTimezone()&&n.stripZone(),n},_.humanizeDuration=function(t){return t.locale(_.options.locale).humanize()},Ut.call(_);var W,U,j,q,$,Q,X,K,J,tt=n[0],et={},nt=0;J=null!=_.options.defaultDate?_.moment(_.options.defaultDate).stripZone():_.getNow(),_.getSuggestedViewHeight=function(){return void 0===X&&f(),X},_.isHeightAuto=function(){return"auto"===_.options.contentHeight||"auto"===_.options.height},_.setToolbarsTitle=function(t){W.proxyCall("updateTitle",t)},_.freezeContentHeight=F,_.thawContentHeight=N;var it=0;_.initialize()}function Yt(e){t.each(Re,function(t,n){null==e[t]&&(e[t]=n(e))})}function Wt(t){return e.localeData(t)||e.localeData("en")}function Ut(){function n(t,e){return!U.options.lazyFetching||s(t,e)?o(t,e):bt.resolve($)}function i(){$=r(nt),U.trigger("eventsReset",$)}function r(t){var e,n,i=[];for(e=0;e<t.length;e++)n=t[e],n.start.clone().stripZone()<Z&&U.getEventEnd(n).stripZone()>q&&i.push(n);return i}function s(t,e){return!q||t<q||e>Z}function o(t,e){return q=t,Z=e,l()}function l(){return u(tt,"reset")}function a(t){return u(E(t))}function u(t,e){var n,i;for("reset"===e?nt=[]:"add"!==e&&(nt=C(nt,t)),n=0;n<t.length;n++)i=t[n],"pending"!==i._status&&et++,i._fetchId=(i._fetchId||0)+1,i._status="pending";for(n=0;n<t.length;n++)i=t[n],c(i,i._fetchId);return et?new bt(function(t){U.one("eventsReceived",t)}):bt.resolve($)}function c(e,n){f(e,function(i){var r,s,o,l=t.isArray(e.events);if(n===e._fetchId&&"rejected"!==e._status){if(e._status="resolved",i)for(r=0;r<i.length;r++)s=i[r],o=l?s:F(s,e),o&&nt.push.apply(nt,_(o));h()}})}function d(t){var e="pending"===t._status;t._status="rejected",e&&h()}function h(){et--,et||(i(nt),U.trigger("eventsReceived",$))}function f(e,n){var i,r,s=qt.sourceFetchers;for(i=0;i<s.length;i++){if(r=s[i].call(U,e,q.clone(),Z.clone(),U.options.timezone,n),r===!0)return;if("object"==typeof r)return void f(r,n)}var o=e.events;if(o)t.isFunction(o)?(U.pushLoading(),o.call(U,q.clone(),Z.clone(),U.options.timezone,function(t){n(t),U.popLoading()})):t.isArray(o)?n(o):n();else{var l=e.url;if(l){var a,u=e.success,c=e.error,d=e.complete;a=t.isFunction(e.data)?e.data():e.data;var h=t.extend({},a||{}),g=J(e.startParam,U.options.startParam),p=J(e.endParam,U.options.endParam),v=J(e.timezoneParam,U.options.timezoneParam);g&&(h[g]=q.format()),p&&(h[p]=Z.format()),U.options.timezone&&"local"!=U.options.timezone&&(h[v]=U.options.timezone),U.pushLoading(),t.ajax(t.extend({},xe,e,{data:h,success:function(e){e=e||[];var i=K(u,this,arguments);t.isArray(i)&&(e=i),n(e)},error:function(){K(c,this,arguments),n()},complete:function(){K(d,this,arguments),U.popLoading()}}))}else n()}}function g(t){var e=p(t);e&&(tt.push(e),u([e],"add"))}function p(e){var n,i,r=qt.sourceNormalizers;if(t.isFunction(e)||t.isArray(e)?n={events:e}:"string"==typeof e?n={url:e}:"object"==typeof e&&(n=t.extend({},e)),n){for(n.className?"string"==typeof n.className&&(n.className=n.className.split(/\s+/)):n.className=[],t.isArray(n.events)&&(n.origArray=n.events,n.events=t.map(n.events,function(t){return F(t,n)})),i=0;i<r.length;i++)r[i].call(U,n);return n}}function v(t){y(b(t))}function m(t){null==t?y(tt,!0):y(E(t))}function y(e,n){var r;for(r=0;r<e.length;r++)d(e[r]);n?(tt=[],nt=[]):(tt=t.grep(tt,function(t){for(r=0;r<e.length;r++)if(t===e[r])return!1;return!0}),nt=C(nt,e)),i()}function S(){return tt.slice(1)}function w(e){return t.grep(tt,function(t){return t.id&&t.id===e})[0]}function E(e){e?t.isArray(e)||(e=[e]):e=[];var n,i=[];for(n=0;n<e.length;n++)i.push.apply(i,b(e[n]));return i}function b(e){var n,i;for(n=0;n<tt.length;n++)if(i=tt[n],i===e)return[i];return i=w(e),i?[i]:t.grep(tt,function(t){return D(e,t)})}function D(t,e){return t&&e&&T(t)==T(e)}function T(t){return("object"==typeof t?t.origArray||t.googleCalendarId||t.url||t.events:null)||t}function C(e,n){return t.grep(e,function(t){for(var e=0;e<n.length;e++)if(t.source===n[e])return!1;return!0})}function H(t){R([t])}function R(t){var e,n;for(e=0;e<t.length;e++)n=t[e],n.start=U.moment(n.start),n.end?n.end=U.moment(n.end):n.end=null,Y(n,x(n));i()}function x(e){var n={};return t.each(e,function(t,e){I(t)&&void 0!==e&&X(e)&&(n[t]=e)}),n}function I(t){return!/^_|^(id|allDay|start|end)$/.test(t)}function k(t,e){return L([t],e)}function L(t,e){var n,r,s,o,l,a=[];for(s=0;s<t.length;s++)if(r=F(t[s])){for(n=_(r),o=0;o<n.length;o++)l=n[o],l.source||(e&&(Q.events.push(l),l.source=Q),nt.push(l));a=a.concat(n)}return a.length&&i(),a}function M(e){var n,r;for(null==e?e=function(){return!0}:t.isFunction(e)||(n=e+"",e=function(t){return t._id==n}),nt=t.grep(nt,e,!0),r=0;r<tt.length;r++)t.isArray(tt[r].events)&&(tt[r].events=t.grep(tt[r].events,e,!0));i()}function B(e){return t.isFunction(e)?t.grep(nt,e):null!=e?(e+="",t.grep(nt,function(t){return t._id==e})):nt}function z(t){t.start=U.moment(t.start),t.end&&(t.end=U.moment(t.end)),jt(t)}function F(n,i){var r,s,o,l={};if(U.options.eventDataTransform&&(n=U.options.eventDataTransform(n)),i&&i.eventDataTransform&&(n=i.eventDataTransform(n)),t.extend(l,n),i&&(l.source=i),l._id=n._id||(void 0===n.id?"_fc"+Ie++:n.id+""),n.className?"string"==typeof n.className?l.className=n.className.split(/\s+/):l.className=n.className:l.className=[],r=n.start||n.date,s=n.end,j(r)&&(r=e.duration(r)),j(s)&&(s=e.duration(s)),n.dow||e.isDuration(r)||e.isDuration(s))l.start=r?e.duration(r):null,l.end=s?e.duration(s):null,l._recurring=!0;else{if(r&&(r=U.moment(r),!r.isValid()))return!1;s&&(s=U.moment(s),s.isValid()||(s=null)),o=n.allDay,void 0===o&&(o=J(i?i.allDayDefault:void 0,U.options.allDayDefault)),A(r,s,o,l)}return U.normalizeEvent(l),l}function A(t,e,n,i){i.start=t,i.end=e,i.allDay=n,V(i),jt(i)}function V(t){P(t),t.end&&!t.end.isAfter(t.start)&&(t.end=null),t.end||(U.options.forceEventDuration?t.end=U.getDefaultEventEnd(t.allDay,t.start):t.end=null)}function P(t){null==t.allDay&&(t.allDay=!(t.start.hasTime()||t.end&&t.end.hasTime())),t.allDay?(t.start.stripTime(),t.end&&t.end.stripTime()):(t.start.hasTime()||(t.start=U.applyTimezone(t.start.time(0))),t.end&&!t.end.hasTime()&&(t.end=U.applyTimezone(t.end.time(0))))}function _(e,n,i){var r,s,o,l,a,u,c,d,h,f=[];if(n=n||q,i=i||Z,e)if(e._recurring){if(s=e.dow)for(r={},o=0;o<s.length;o++)r[s[o]]=!0;for(l=n.clone().stripTime();l.isBefore(i);)r&&!r[l.day()]||(a=e.start,u=e.end,c=l.clone(),d=null,a&&(c=c.time(a)),u&&(d=l.clone().time(u)),h=t.extend({},e),A(c,d,!a&&!u,h),f.push(h)),l.add(1,"days")}else f.push(e);return f}function Y(e,n,i){function r(t,e){return i?O(t,e,i):n.allDay?G(t,e):N(t,e)}var s,o,l,a,u,c,d={};return n=n||{},n.start||(n.start=e.start.clone()),void 0===n.end&&(n.end=e.end?e.end.clone():null),null==n.allDay&&(n.allDay=e.allDay),V(n),s={start:e._start.clone(),end:e._end?e._end.clone():U.getDefaultEventEnd(e._allDay,e._start),allDay:n.allDay},V(s),o=null!==e._end&&null===n.end,l=r(n.start,s.start),n.end?(a=r(n.end,s.end),u=a.subtract(l)):u=null,t.each(n,function(t,e){I(t)&&void 0!==e&&(d[t]=e)}),c=W(B(e._id),o,n.allDay,l,u,d),{dateDelta:l,durationDelta:u,undo:c}}function W(e,n,i,r,s,o){var l=U.getIsAmbigTimezone(),a=[];return r&&!r.valueOf()&&(r=null),s&&!s.valueOf()&&(s=null),t.each(e,function(e,u){var c,d;c={start:u.start.clone(),end:u.end?u.end.clone():null,allDay:u.allDay},t.each(o,function(t){c[t]=u[t]}),d={start:u._start,end:u._end,allDay:i},V(d),n?d.end=null:s&&!d.end&&(d.end=U.getDefaultEventEnd(d.allDay,d.start)),r&&(d.start.add(r),d.end&&d.end.add(r)),s&&d.end.add(s),l&&!d.allDay&&(r||s)&&(d.start.stripZone(),d.end&&d.end.stripZone()),t.extend(u,o,d),jt(u),a.push(function(){t.extend(u,c),jt(u)})}),function(){for(var t=0;t<a.length;t++)a[t]()}}var U=this;U.requestEvents=n,U.reportEventChange=i,U.isFetchNeeded=s,U.fetchEvents=o,U.fetchEventSources=u,U.refetchEvents=l,U.refetchEventSources=a,U.getEventSources=S,U.getEventSourceById=w,U.addEventSource=g,U.removeEventSource=v,U.removeEventSources=m,U.updateEvent=H,U.updateEvents=R,U.renderEvent=k,U.renderEvents=L,U.removeEvents=M,U.clientEvents=B,U.mutateEvent=Y,U.normalizeEventDates=V,U.normalizeEventTimes=P;var q,Z,$,Q={events:[]},tt=[Q],et=0,nt=[];t.each((U.options.events?[U.options.events]:[]).concat(U.options.eventSources||[]),function(t,e){var n=p(e);n&&tt.push(n)}),U.getEventCache=function(){return nt},U.getPrunedEventCache=function(){return $},U.rezoneArrayEventSources=function(){var e,n,i;for(e=0;e<tt.length;e++)if(n=tt[e].events,t.isArray(n))for(i=0;i<n.length;i++)z(n[i])},U.buildEventFromInput=F,U.expandEvent=_}function jt(t){t._allDay=t.allDay,t._start=t.start.clone(),t._end=t.end?t.end.clone():null}var qt=t.fullCalendar={version:"3.1.0",internalApiVersion:7},Zt=qt.views={};t.fn.fullCalendar=function(e){var n=Array.prototype.slice.call(arguments,1),i=this;return this.each(function(r,s){var o,l=t(s),a=l.data("fullCalendar");"string"==typeof e?a&&t.isFunction(a[e])&&(o=a[e].apply(a,n),r||(i=o),"destroy"===e&&l.removeData("fullCalendar")):a||(a=new De(l,e),l.data("fullCalendar",a),a.render())}),i};var $t=["header","footer","buttonText","buttonIcons","themeButtonIcons"];qt.intersectRanges=F,qt.applyAll=K,qt.debounce=at,qt.isInt=ot,qt.htmlEscape=tt,qt.cssToStr=nt,qt.proxy=lt,qt.capitaliseFirstLetter=rt,qt.getOuterRect=h,qt.getClientRect=f,qt.getContentRect=g,qt.getScrollbarWidths=p;var Qt=null;qt.preventDefault=T,qt.intersectRects=R,qt.parseFieldSpecs=L,qt.compareByFieldSpecs=M,qt.compareByFieldSpec=B,qt.flexibleCompare=z,qt.computeIntervalUnit=A,qt.divideRangeByDuration=P,qt.divideDurationByDuration=_,qt.multiplyDuration=Y,qt.durationHasTime=W;var Xt=["sun","mon","tue","wed","thu","fri","sat"],Kt=["year","month","week","day","hour","minute","second","millisecond"];qt.log=function(){var t=window.console;if(t&&t.log)return t.log.apply(t,arguments)},qt.warn=function(){var t=window.console;return t&&t.warn?t.warn.apply(t,arguments):qt.log.apply(qt,arguments)};var Jt={}.hasOwnProperty;qt.createObject=Z;var te=/^\s*\d{4}-\d\d$/,ee=/^\s*\d{4}-(?:(\d\d-\d\d)|(W\d\d$)|(W\d\d-\d)|(\d\d\d))((T| )(\d\d(:\d\d(:\d\d(\.\d+)?)?)?)?)?$/,ne=e.fn,ie=t.extend({},ne),re=e.momentProperties;re.push("_fullCalendar"),re.push("_ambigTime"),re.push("_ambigZone"),qt.moment=function(){return ut(arguments)},qt.moment.utc=function(){var t=ut(arguments,!0);return t.hasTime()&&t.utc(),t},qt.moment.parseZone=function(){return ut(arguments,!0,!0)},ne.week=ne.weeks=function(t){var e=this._locale._fullCalendar_weekCalc;return null==t&&"function"==typeof e?e(this):"ISO"===e?ie.isoWeek.apply(this,arguments):ie.week.apply(this,arguments)},ne.time=function(t){if(!this._fullCalendar)return ie.time.apply(this,arguments);if(null==t)return e.duration({hours:this.hours(),minutes:this.minutes(),seconds:this.seconds(),milliseconds:this.milliseconds()});this._ambigTime=!1,e.isDuration(t)||e.isMoment(t)||(t=e.duration(t));var n=0;return e.isDuration(t)&&(n=24*Math.floor(t.asDays())),this.hours(n+t.hours()).minutes(t.minutes()).seconds(t.seconds()).milliseconds(t.milliseconds())},ne.stripTime=function(){return this._ambigTime||(this.utc(!0),this.set({hours:0,minutes:0,seconds:0,ms:0}),this._ambigTime=!0,this._ambigZone=!0),this},ne.hasTime=function(){return!this._ambigTime},ne.stripZone=function(){var t;return this._ambigZone||(t=this._ambigTime,this.utc(!0),this._ambigTime=t||!1,this._ambigZone=!0),this},ne.hasZone=function(){return!this._ambigZone},ne.local=function(t){return ie.local.call(this,this._ambigZone||t),this._ambigTime=!1,this._ambigZone=!1,this},ne.utc=function(t){return ie.utc.call(this,t),this._ambigTime=!1,this._ambigZone=!1,this},ne.utcOffset=function(t){return null!=t&&(this._ambigTime=!1,this._ambigZone=!1),ie.utcOffset.apply(this,arguments)},ne.format=function(){return this._fullCalendar&&arguments[0]?dt(this,arguments[0]):this._ambigTime?ct(this,"YYYY-MM-DD"):this._ambigZone?ct(this,"YYYY-MM-DD[T]HH:mm:ss"):ie.format.apply(this,arguments)},ne.toISOString=function(){return this._ambigTime?ct(this,"YYYY-MM-DD"):this._ambigZone?ct(this,"YYYY-MM-DD[T]HH:mm:ss"):ie.toISOString.apply(this,arguments)};var se={t:function(t){return ct(t,"a").charAt(0)},T:function(t){return ct(t,"A").charAt(0)}};qt.formatRange=gt;var oe={Y:"year",M:"month",D:"day",d:"day",A:"second",a:"second",T:"second",t:"second",H:"second",h:"second",m:"second",s:"second"},le={},ae={Y:{value:1,unit:"year"},M:{value:2,unit:"month"},W:{value:3,unit:"week"},w:{value:3,unit:"week"},D:{value:4,unit:"day"},d:{value:4,unit:"day"}};qt.queryMostGranularFormatUnit=function(t){
-var e,n,i,r,s=mt(t);for(e=0;e<s.length;e++)n=s[e],n.token&&(i=ae[n.token.charAt(0)],i&&(!r||i.value>r.value)&&(r=i));return r?r.unit:null},qt.Class=St,St.extend=function(){var t,e,n=arguments.length;for(t=0;t<n;t++)e=arguments[t],t<n-1&&Et(this,e);return wt(this,e||{})},St.mixin=function(t){Et(this,t)},qt.Promise=bt,bt.immediate=!0,bt.resolve=function(e){if(e&&"function"==typeof e.resolve)return e.promise();if(e&&"function"==typeof e.then)return e;var n=t.Deferred().resolve(e),i=n.promise();if(bt.immediate){var r=i.then;i._value=e,i.then=function(t,n){return"function"==typeof t?bt.resolve(t(e)):r.call(i,t,n)}}return i},bt.reject=function(){return t.Deferred().reject().promise()},bt.all=function(e){var n,i,r,s=!1;if(bt.immediate)for(s=!0,n=[],i=0;i<e.length;i++)if(r=e[i],r&&"function"==typeof r.state&&"resolved"===r.state()&&"_value"in r)n.push(r._value);else{if(r&&"function"==typeof r.then){s=!1;break}n.push(r)}return s?bt.resolve(n):t.when.apply(t.when,e).then(function(){return t.when(t.makeArray(arguments))})},qt.TaskQueue=Dt;var ue=qt.EmitterMixin={on:function(e,n){return t(this).on(e,this._prepareIntercept(n)),this},one:function(e,n){return t(this).one(e,this._prepareIntercept(n)),this},_prepareIntercept:function(e){var n=function(t,n){return e.apply(n.context||this,n.args||[])};return e.guid||(e.guid=t.guid++),n.guid=e.guid,n},off:function(e,n){return t(this).off(e,n),this},trigger:function(e){var n=Array.prototype.slice.call(arguments,1);return t(this).triggerHandler(e,{args:n}),this},triggerWith:function(e,n,i){return t(this).triggerHandler(e,{context:n,args:i}),this}},ce=qt.ListenerMixin=function(){var e=0,n={listenerId:null,listenTo:function(e,n,i){if("object"==typeof n)for(var r in n)n.hasOwnProperty(r)&&this.listenTo(e,r,n[r]);else"string"==typeof n&&e.on(n+"."+this.getListenerNamespace(),t.proxy(i,this))},stopListeningTo:function(t,e){t.off((e||"")+"."+this.getListenerNamespace())},getListenerNamespace:function(){return null==this.listenerId&&(this.listenerId=e++),"_listener"+this.listenerId}};return n}(),de={isIgnoringMouse:!1,delayUnignoreMouse:null,initMouseIgnoring:function(t){this.delayUnignoreMouse=at(lt(this,"unignoreMouse"),t||1e3)},tempIgnoreMouse:function(){this.isIgnoringMouse=!0,this.delayUnignoreMouse()},unignoreMouse:function(){this.isIgnoringMouse=!1}},he=St.extend(ce,{isHidden:!0,options:null,el:null,margin:10,constructor:function(t){this.options=t||{}},show:function(){this.isHidden&&(this.el||this.render(),this.el.show(),this.position(),this.isHidden=!1,this.trigger("show"))},hide:function(){this.isHidden||(this.el.hide(),this.isHidden=!0,this.trigger("hide"))},render:function(){var e=this,n=this.options;this.el=t('<div class="fc-popover"/>').addClass(n.className||"").css({top:0,left:0}).append(n.content).appendTo(n.parentEl),this.el.on("click",".fc-close",function(){e.hide()}),n.autoHide&&this.listenTo(t(document),"mousedown",this.documentMousedown)},documentMousedown:function(e){this.el&&!t(e.target).closest(this.el).length&&this.hide()},removeElement:function(){this.hide(),this.el&&(this.el.remove(),this.el=null),this.stopListeningTo(t(document),"mousedown")},position:function(){var e,n,i,r,s,o=this.options,l=this.el.offsetParent().offset(),a=this.el.outerWidth(),u=this.el.outerHeight(),c=t(window),h=d(this.el);r=o.top||0,s=void 0!==o.left?o.left:void 0!==o.right?o.right-a:0,h.is(window)||h.is(document)?(h=c,e=0,n=0):(i=h.offset(),e=i.top,n=i.left),e+=c.scrollTop(),n+=c.scrollLeft(),o.viewportConstrain!==!1&&(r=Math.min(r,e+h.outerHeight()-u-this.margin),r=Math.max(r,e+this.margin),s=Math.min(s,n+h.outerWidth()-a-this.margin),s=Math.max(s,n+this.margin)),this.el.css({top:r-l.top,left:s-l.left})},trigger:function(t){this.options[t]&&this.options[t].apply(this,Array.prototype.slice.call(arguments,1))}}),fe=qt.CoordCache=St.extend({els:null,forcedOffsetParentEl:null,origin:null,boundingRect:null,isHorizontal:!1,isVertical:!1,lefts:null,rights:null,tops:null,bottoms:null,constructor:function(e){this.els=t(e.els),this.isHorizontal=e.isHorizontal,this.isVertical=e.isVertical,this.forcedOffsetParentEl=e.offsetParent?t(e.offsetParent):null},build:function(){var t=this.forcedOffsetParentEl;!t&&this.els.length>0&&(t=this.els.eq(0).offsetParent()),this.origin=t?t.offset():null,this.boundingRect=this.queryBoundingRect(),this.isHorizontal&&this.buildElHorizontals(),this.isVertical&&this.buildElVerticals()},clear:function(){this.origin=null,this.boundingRect=null,this.lefts=null,this.rights=null,this.tops=null,this.bottoms=null},ensureBuilt:function(){this.origin||this.build()},buildElHorizontals:function(){var e=[],n=[];this.els.each(function(i,r){var s=t(r),o=s.offset().left,l=s.outerWidth();e.push(o),n.push(o+l)}),this.lefts=e,this.rights=n},buildElVerticals:function(){var e=[],n=[];this.els.each(function(i,r){var s=t(r),o=s.offset().top,l=s.outerHeight();e.push(o),n.push(o+l)}),this.tops=e,this.bottoms=n},getHorizontalIndex:function(t){this.ensureBuilt();var e,n=this.lefts,i=this.rights,r=n.length;for(e=0;e<r;e++)if(t>=n[e]&&t<i[e])return e},getVerticalIndex:function(t){this.ensureBuilt();var e,n=this.tops,i=this.bottoms,r=n.length;for(e=0;e<r;e++)if(t>=n[e]&&t<i[e])return e},getLeftOffset:function(t){return this.ensureBuilt(),this.lefts[t]},getLeftPosition:function(t){return this.ensureBuilt(),this.lefts[t]-this.origin.left},getRightOffset:function(t){return this.ensureBuilt(),this.rights[t]},getRightPosition:function(t){return this.ensureBuilt(),this.rights[t]-this.origin.left},getWidth:function(t){return this.ensureBuilt(),this.rights[t]-this.lefts[t]},getTopOffset:function(t){return this.ensureBuilt(),this.tops[t]},getTopPosition:function(t){return this.ensureBuilt(),this.tops[t]-this.origin.top},getBottomOffset:function(t){return this.ensureBuilt(),this.bottoms[t]},getBottomPosition:function(t){return this.ensureBuilt(),this.bottoms[t]-this.origin.top},getHeight:function(t){return this.ensureBuilt(),this.bottoms[t]-this.tops[t]},queryBoundingRect:function(){var t;return this.els.length>0&&(t=d(this.els.eq(0)),!t.is(document))?f(t):null},isPointInBounds:function(t,e){return this.isLeftInBounds(t)&&this.isTopInBounds(e)},isLeftInBounds:function(t){return!this.boundingRect||t>=this.boundingRect.left&&t<this.boundingRect.right},isTopInBounds:function(t){return!this.boundingRect||t>=this.boundingRect.top&&t<this.boundingRect.bottom}}),ge=qt.DragListener=St.extend(ce,de,{options:null,subjectEl:null,originX:null,originY:null,scrollEl:null,isInteracting:!1,isDistanceSurpassed:!1,isDelayEnded:!1,isDragging:!1,isTouch:!1,delay:null,delayTimeoutId:null,minDistance:null,handleTouchScrollProxy:null,constructor:function(t){this.options=t||{},this.handleTouchScrollProxy=lt(this,"handleTouchScroll"),this.initMouseIgnoring(500)},startInteraction:function(e,n){var i=b(e);if("mousedown"===e.type){if(this.isIgnoringMouse)return;if(!S(e))return;e.preventDefault()}this.isInteracting||(n=n||{},this.delay=J(n.delay,this.options.delay,0),this.minDistance=J(n.distance,this.options.distance,0),this.subjectEl=this.options.subjectEl,this.isInteracting=!0,this.isTouch=i,this.isDelayEnded=!1,this.isDistanceSurpassed=!1,this.originX=w(e),this.originY=E(e),this.scrollEl=d(t(e.target)),this.bindHandlers(),this.initAutoScroll(),this.handleInteractionStart(e),this.startDelay(e),this.minDistance||this.handleDistanceSurpassed(e))},handleInteractionStart:function(t){this.trigger("interactionStart",t)},endInteraction:function(t,e){this.isInteracting&&(this.endDrag(t),this.delayTimeoutId&&(clearTimeout(this.delayTimeoutId),this.delayTimeoutId=null),this.destroyAutoScroll(),this.unbindHandlers(),this.isInteracting=!1,this.handleInteractionEnd(t,e),this.isTouch&&this.tempIgnoreMouse())},handleInteractionEnd:function(t,e){this.trigger("interactionEnd",t,e||!1)},bindHandlers:function(){var e=this,n=1;this.isTouch?(this.listenTo(t(document),{touchmove:this.handleTouchMove,touchend:this.endInteraction,touchcancel:this.endInteraction,touchstart:function(t){n?n--:e.endInteraction(t,!0)}}),!C(this.handleTouchScrollProxy)&&this.scrollEl&&this.listenTo(this.scrollEl,"scroll",this.handleTouchScroll)):this.listenTo(t(document),{mousemove:this.handleMouseMove,mouseup:this.endInteraction}),this.listenTo(t(document),{selectstart:T,contextmenu:T})},unbindHandlers:function(){this.stopListeningTo(t(document)),H(this.handleTouchScrollProxy),this.scrollEl&&this.stopListeningTo(this.scrollEl,"scroll")},startDrag:function(t,e){this.startInteraction(t,e),this.isDragging||(this.isDragging=!0,this.handleDragStart(t))},handleDragStart:function(t){this.trigger("dragStart",t)},handleMove:function(t){var e,n=w(t)-this.originX,i=E(t)-this.originY,r=this.minDistance;this.isDistanceSurpassed||(e=n*n+i*i,e>=r*r&&this.handleDistanceSurpassed(t)),this.isDragging&&this.handleDrag(n,i,t)},handleDrag:function(t,e,n){this.trigger("drag",t,e,n),this.updateAutoScroll(n)},endDrag:function(t){this.isDragging&&(this.isDragging=!1,this.handleDragEnd(t))},handleDragEnd:function(t){this.trigger("dragEnd",t)},startDelay:function(t){var e=this;this.delay?this.delayTimeoutId=setTimeout(function(){e.handleDelayEnd(t)},this.delay):this.handleDelayEnd(t)},handleDelayEnd:function(t){this.isDelayEnded=!0,this.isDistanceSurpassed&&this.startDrag(t)},handleDistanceSurpassed:function(t){this.isDistanceSurpassed=!0,this.isDelayEnded&&this.startDrag(t)},handleTouchMove:function(t){this.isDragging&&t.preventDefault(),this.handleMove(t)},handleMouseMove:function(t){this.handleMove(t)},handleTouchScroll:function(t){this.isDragging||this.endInteraction(t,!0)},trigger:function(t){this.options[t]&&this.options[t].apply(this,Array.prototype.slice.call(arguments,1)),this["_"+t]&&this["_"+t].apply(this,Array.prototype.slice.call(arguments,1))}});ge.mixin({isAutoScroll:!1,scrollBounds:null,scrollTopVel:null,scrollLeftVel:null,scrollIntervalId:null,scrollSensitivity:30,scrollSpeed:200,scrollIntervalMs:50,initAutoScroll:function(){var t=this.scrollEl;this.isAutoScroll=this.options.scroll&&t&&!t.is(window)&&!t.is(document),this.isAutoScroll&&this.listenTo(t,"scroll",at(this.handleDebouncedScroll,100))},destroyAutoScroll:function(){this.endAutoScroll(),this.isAutoScroll&&this.stopListeningTo(this.scrollEl,"scroll")},computeScrollBounds:function(){this.isAutoScroll&&(this.scrollBounds=h(this.scrollEl))},updateAutoScroll:function(t){var e,n,i,r,s=this.scrollSensitivity,o=this.scrollBounds,l=0,a=0;o&&(e=(s-(E(t)-o.top))/s,n=(s-(o.bottom-E(t)))/s,i=(s-(w(t)-o.left))/s,r=(s-(o.right-w(t)))/s,e>=0&&e<=1?l=e*this.scrollSpeed*-1:n>=0&&n<=1&&(l=n*this.scrollSpeed),i>=0&&i<=1?a=i*this.scrollSpeed*-1:r>=0&&r<=1&&(a=r*this.scrollSpeed)),this.setScrollVel(l,a)},setScrollVel:function(t,e){this.scrollTopVel=t,this.scrollLeftVel=e,this.constrainScrollVel(),!this.scrollTopVel&&!this.scrollLeftVel||this.scrollIntervalId||(this.scrollIntervalId=setInterval(lt(this,"scrollIntervalFunc"),this.scrollIntervalMs))},constrainScrollVel:function(){var t=this.scrollEl;this.scrollTopVel<0?t.scrollTop()<=0&&(this.scrollTopVel=0):this.scrollTopVel>0&&t.scrollTop()+t[0].clientHeight>=t[0].scrollHeight&&(this.scrollTopVel=0),this.scrollLeftVel<0?t.scrollLeft()<=0&&(this.scrollLeftVel=0):this.scrollLeftVel>0&&t.scrollLeft()+t[0].clientWidth>=t[0].scrollWidth&&(this.scrollLeftVel=0)},scrollIntervalFunc:function(){var t=this.scrollEl,e=this.scrollIntervalMs/1e3;this.scrollTopVel&&t.scrollTop(t.scrollTop()+this.scrollTopVel*e),this.scrollLeftVel&&t.scrollLeft(t.scrollLeft()+this.scrollLeftVel*e),this.constrainScrollVel(),this.scrollTopVel||this.scrollLeftVel||this.endAutoScroll()},endAutoScroll:function(){this.scrollIntervalId&&(clearInterval(this.scrollIntervalId),this.scrollIntervalId=null,this.handleScrollEnd())},handleDebouncedScroll:function(){this.scrollIntervalId||this.handleScrollEnd()},handleScrollEnd:function(){}});var pe=ge.extend({component:null,origHit:null,hit:null,coordAdjust:null,constructor:function(t,e){ge.call(this,e),this.component=t},handleInteractionStart:function(t){var e,n,i,r=this.subjectEl;this.computeCoords(),t?(n={left:w(t),top:E(t)},i=n,r&&(e=h(r),i=x(i,e)),this.origHit=this.queryHit(i.left,i.top),r&&this.options.subjectCenter&&(this.origHit&&(e=R(this.origHit,e)||e),i=I(e)),this.coordAdjust=k(i,n)):(this.origHit=null,this.coordAdjust=null),ge.prototype.handleInteractionStart.apply(this,arguments)},computeCoords:function(){this.component.prepareHits(),this.computeScrollBounds()},handleDragStart:function(t){var e;ge.prototype.handleDragStart.apply(this,arguments),e=this.queryHit(w(t),E(t)),e&&this.handleHitOver(e)},handleDrag:function(t,e,n){var i;ge.prototype.handleDrag.apply(this,arguments),i=this.queryHit(w(n),E(n)),Tt(i,this.hit)||(this.hit&&this.handleHitOut(),i&&this.handleHitOver(i))},handleDragEnd:function(){this.handleHitDone(),ge.prototype.handleDragEnd.apply(this,arguments)},handleHitOver:function(t){var e=Tt(t,this.origHit);this.hit=t,this.trigger("hitOver",this.hit,e,this.origHit)},handleHitOut:function(){this.hit&&(this.trigger("hitOut",this.hit),this.handleHitDone(),this.hit=null)},handleHitDone:function(){this.hit&&this.trigger("hitDone",this.hit)},handleInteractionEnd:function(){ge.prototype.handleInteractionEnd.apply(this,arguments),this.origHit=null,this.hit=null,this.component.releaseHits()},handleScrollEnd:function(){ge.prototype.handleScrollEnd.apply(this,arguments),this.computeCoords()},queryHit:function(t,e){return this.coordAdjust&&(t+=this.coordAdjust.left,e+=this.coordAdjust.top),this.component.queryHit(t,e)}}),ve=St.extend(ce,{options:null,sourceEl:null,el:null,parentEl:null,top0:null,left0:null,y0:null,x0:null,topDelta:null,leftDelta:null,isFollowing:!1,isHidden:!1,isAnimating:!1,constructor:function(e,n){this.options=n=n||{},this.sourceEl=e,this.parentEl=n.parentEl?t(n.parentEl):e.parent()},start:function(e){this.isFollowing||(this.isFollowing=!0,this.y0=E(e),this.x0=w(e),this.topDelta=0,this.leftDelta=0,this.isHidden||this.updatePosition(),b(e)?this.listenTo(t(document),"touchmove",this.handleMove):this.listenTo(t(document),"mousemove",this.handleMove))},stop:function(e,n){function i(){r.isAnimating=!1,r.removeElement(),r.top0=r.left0=null,n&&n()}var r=this,s=this.options.revertDuration;this.isFollowing&&!this.isAnimating&&(this.isFollowing=!1,this.stopListeningTo(t(document)),e&&s&&!this.isHidden?(this.isAnimating=!0,this.el.animate({top:this.top0,left:this.left0},{duration:s,complete:i})):i())},getEl:function(){var t=this.el;return t||(t=this.el=this.sourceEl.clone().addClass(this.options.additionalClass||"").css({position:"absolute",visibility:"",display:this.isHidden?"none":"",margin:0,right:"auto",bottom:"auto",width:this.sourceEl.width(),height:this.sourceEl.height(),opacity:this.options.opacity||"",zIndex:this.options.zIndex}),t.addClass("fc-unselectable"),t.appendTo(this.parentEl)),t},removeElement:function(){this.el&&(this.el.remove(),this.el=null)},updatePosition:function(){var t,e;this.getEl(),null===this.top0&&(t=this.sourceEl.offset(),e=this.el.offsetParent().offset(),this.top0=t.top-e.top,this.left0=t.left-e.left),this.el.css({top:this.top0+this.topDelta,left:this.left0+this.leftDelta})},handleMove:function(t){this.topDelta=E(t)-this.y0,this.leftDelta=w(t)-this.x0,this.isHidden||this.updatePosition()},hide:function(){this.isHidden||(this.isHidden=!0,this.el&&this.el.hide())},show:function(){this.isHidden&&(this.isHidden=!1,this.updatePosition(),this.getEl().show())}}),me=qt.Grid=St.extend(ce,de,{hasDayInteractions:!0,view:null,isRTL:null,start:null,end:null,el:null,elsByFill:null,eventTimeFormat:null,displayEventTime:null,displayEventEnd:null,minResizeDuration:null,largeUnit:null,dayDragListener:null,segDragListener:null,segResizeListener:null,externalDragListener:null,constructor:function(t){this.view=t,this.isRTL=t.opt("isRTL"),this.elsByFill={},this.dayDragListener=this.buildDayDragListener(),this.initMouseIgnoring()},computeEventTimeFormat:function(){return this.view.opt("smallTimeFormat")},computeDisplayEventTime:function(){return!0},computeDisplayEventEnd:function(){return!0},setRange:function(t){this.start=t.start.clone(),this.end=t.end.clone(),this.rangeUpdated(),this.processRangeOptions()},rangeUpdated:function(){},processRangeOptions:function(){var t,e,n=this.view;this.eventTimeFormat=n.opt("eventTimeFormat")||n.opt("timeFormat")||this.computeEventTimeFormat(),t=n.opt("displayEventTime"),null==t&&(t=this.computeDisplayEventTime()),e=n.opt("displayEventEnd"),null==e&&(e=this.computeDisplayEventEnd()),this.displayEventTime=t,this.displayEventEnd=e},spanToSegs:function(t){},diffDates:function(t,e){return this.largeUnit?O(t,e,this.largeUnit):N(t,e)},prepareHits:function(){},releaseHits:function(){},queryHit:function(t,e){},getHitSpan:function(t){},getHitEl:function(t){},setElement:function(t){this.el=t,this.hasDayInteractions&&(D(t),this.bindDayHandler("touchstart",this.dayTouchStart),this.bindDayHandler("mousedown",this.dayMousedown)),this.bindSegHandlers(),this.bindGlobalHandlers()},bindDayHandler:function(e,n){var i=this;this.el.on(e,function(e){if(!t(e.target).is(i.segSelector+","+i.segSelector+" *,.fc-more,a[data-goto]"))return n.call(i,e)})},removeElement:function(){this.unbindGlobalHandlers(),this.clearDragListeners(),this.el.remove()},renderSkeleton:function(){},renderDates:function(){},unrenderDates:function(){},bindGlobalHandlers:function(){this.listenTo(t(document),{dragstart:this.externalDragStart,sortstart:this.externalDragStart})},unbindGlobalHandlers:function(){this.stopListeningTo(t(document))},dayMousedown:function(t){this.isIgnoringMouse||this.dayDragListener.startInteraction(t,{})},dayTouchStart:function(t){var e=this.view,n=e.opt("selectLongPressDelay");(e.isSelected||e.selectedEvent)&&this.tempIgnoreMouse(),null==n&&(n=e.opt("longPressDelay")),this.dayDragListener.startInteraction(t,{delay:n})},buildDayDragListener:function(){var t,e,n=this,i=this.view,r=i.opt("selectable"),l=new pe(this,{scroll:i.opt("dragScroll"),interactionStart:function(){t=l.origHit,e=null},dragStart:function(){i.unselect()},hitOver:function(i,o,l){l&&(o||(t=null),r&&(e=n.computeSelection(n.getHitSpan(l),n.getHitSpan(i)),e?n.renderSelection(e):e===!1&&s()))},hitOut:function(){t=null,e=null,n.unrenderSelection()},hitDone:function(){o()},interactionEnd:function(r,s){s||(t&&!n.isIgnoringMouse&&i.triggerDayClick(n.getHitSpan(t),n.getHitEl(t),r),e&&i.reportSelection(e,r))}});return l},clearDragListeners:function(){this.dayDragListener.endInteraction(),this.segDragListener&&this.segDragListener.endInteraction(),this.segResizeListener&&this.segResizeListener.endInteraction(),this.externalDragListener&&this.externalDragListener.endInteraction()},renderEventLocationHelper:function(t,e){var n=this.fabricateHelperEvent(t,e);return this.renderHelper(n,e)},fabricateHelperEvent:function(t,e){var n=e?Z(e.event):{};return n.start=t.start.clone(),n.end=t.end?t.end.clone():null,n.allDay=null,this.view.calendar.normalizeEventDates(n),n.className=(n.className||[]).concat("fc-helper"),e||(n.editable=!1),n},renderHelper:function(t,e){},unrenderHelper:function(){},renderSelection:function(t){this.renderHighlight(t)},unrenderSelection:function(){this.unrenderHighlight()},computeSelection:function(t,e){var n=this.computeSelectionSpan(t,e);return!(n&&!this.view.calendar.isSelectionSpanAllowed(n))&&n},computeSelectionSpan:function(t,e){var n=[t.start,t.end,e.start,e.end];return n.sort(st),{start:n[0].clone(),end:n[3].clone()}},renderHighlight:function(t){this.renderFill("highlight",this.spanToSegs(t))},unrenderHighlight:function(){this.unrenderFill("highlight")},highlightSegClasses:function(){return["fc-highlight"]},renderBusinessHours:function(){},unrenderBusinessHours:function(){},getNowIndicatorUnit:function(){},renderNowIndicator:function(t){},unrenderNowIndicator:function(){},renderFill:function(t,e){},unrenderFill:function(t){var e=this.elsByFill[t];e&&(e.remove(),delete this.elsByFill[t])},renderFillSegEls:function(e,n){var i,r=this,s=this[e+"SegEl"],o="",l=[];if(n.length){for(i=0;i<n.length;i++)o+=this.fillSegHtml(e,n[i]);t(o).each(function(e,i){var o=n[e],a=t(i);s&&(a=s.call(r,o,a)),a&&(a=t(a),a.is(r.fillSegTag)&&(o.el=a,l.push(o)))})}return l},fillSegTag:"div",fillSegHtml:function(t,e){var n=this[t+"SegClasses"],i=this[t+"SegCss"],r=n?n.call(this,e):[],s=nt(i?i.call(this,e):{});return"<"+this.fillSegTag+(r.length?' class="'+r.join(" ")+'"':"")+(s?' style="'+s+'"':"")+" />"},getDayClasses:function(t,e){var n=this.view,i=n.calendar.getNow(),r=["fc-"+Xt[t.day()]];return 1==n.intervalDuration.as("months")&&t.month()!=n.intervalStart.month()&&r.push("fc-other-month"),t.isSame(i,"day")?(r.push("fc-today"),e!==!0&&r.push(n.highlightStateClass)):t<i?r.push("fc-past"):r.push("fc-future"),r}});me.mixin({segSelector:".fc-event-container > *",mousedOverSeg:null,isDraggingSeg:!1,isResizingSeg:!1,isDraggingExternal:!1,segs:null,renderEvents:function(t){var e,n=[],i=[];for(e=0;e<t.length;e++)(Rt(t[e])?n:i).push(t[e]);this.segs=[].concat(this.renderBgEvents(n),this.renderFgEvents(i))},renderBgEvents:function(t){var e=this.eventsToSegs(t);return this.renderBgSegs(e)||e},renderFgEvents:function(t){var e=this.eventsToSegs(t);return this.renderFgSegs(e)||e},unrenderEvents:function(){this.handleSegMouseout(),this.clearDragListeners(),this.unrenderFgSegs(),this.unrenderBgSegs(),this.segs=null},getEventSegs:function(){return this.segs||[]},renderFgSegs:function(t){},unrenderFgSegs:function(){},renderFgSegEls:function(e,n){var i,r=this.view,s="",o=[];if(e.length){for(i=0;i<e.length;i++)s+=this.fgSegHtml(e[i],n);t(s).each(function(n,i){var s=e[n],l=r.resolveEventEl(s.event,t(i));l&&(l.data("fc-seg",s),s.el=l,o.push(s))})}return o},fgSegHtml:function(t,e){},renderBgSegs:function(t){return this.renderFill("bgEvent",t)},unrenderBgSegs:function(){this.unrenderFill("bgEvent")},bgEventSegEl:function(t,e){return this.view.resolveEventEl(t.event,e)},bgEventSegClasses:function(t){var e=t.event,n=e.source||{};return["fc-bgevent"].concat(e.className,n.className||[])},bgEventSegCss:function(t){return{"background-color":this.getSegSkinCss(t)["background-color"]}},businessHoursSegClasses:function(t){return["fc-nonbusiness","fc-bgevent"]},buildBusinessHourSegs:function(t,e){return this.eventsToSegs(this.buildBusinessHourEvents(t,e))},buildBusinessHourEvents:function(e,n){var i,r=this.view.calendar;return null==n&&(n=r.options.businessHours),i=r.computeBusinessHourEvents(e,n),!i.length&&n&&(i=[t.extend({},ke,{start:this.view.end,end:this.view.end,dow:null})]),i},bindSegHandlers:function(){this.bindSegHandlersToEl(this.el)},bindSegHandlersToEl:function(t){this.bindSegHandlerToEl(t,"touchstart",this.handleSegTouchStart),this.bindSegHandlerToEl(t,"touchend",this.handleSegTouchEnd),this.bindSegHandlerToEl(t,"mouseenter",this.handleSegMouseover),this.bindSegHandlerToEl(t,"mouseleave",this.handleSegMouseout),this.bindSegHandlerToEl(t,"mousedown",this.handleSegMousedown),this.bindSegHandlerToEl(t,"click",this.handleSegClick)},bindSegHandlerToEl:function(e,n,i){var r=this;e.on(n,this.segSelector,function(e){var n=t(this).data("fc-seg");if(n&&!r.isDraggingSeg&&!r.isResizingSeg)return i.call(r,n,e)})},handleSegClick:function(t,e){var n=this.view.publiclyTrigger("eventClick",t.el[0],t.event,e);n===!1&&e.preventDefault()},handleSegMouseover:function(t,e){this.isIgnoringMouse||this.mousedOverSeg||(this.mousedOverSeg=t,this.view.isEventResizable(t.event)&&t.el.addClass("fc-allow-mouse-resize"),this.view.publiclyTrigger("eventMouseover",t.el[0],t.event,e))},handleSegMouseout:function(t,e){e=e||{},this.mousedOverSeg&&(t=t||this.mousedOverSeg,this.mousedOverSeg=null,this.view.isEventResizable(t.event)&&t.el.removeClass("fc-allow-mouse-resize"),this.view.publiclyTrigger("eventMouseout",t.el[0],t.event,e))},handleSegMousedown:function(t,e){var n=this.startSegResize(t,e,{distance:5});!n&&this.view.isEventDraggable(t.event)&&this.buildSegDragListener(t).startInteraction(e,{distance:5})},handleSegTouchStart:function(t,e){var n,i,r=this.view,s=t.event,o=r.isEventSelected(s),l=r.isEventDraggable(s),a=r.isEventResizable(s),u=!1;o&&a&&(u=this.startSegResize(t,e)),u||!l&&!a||(i=r.opt("eventLongPressDelay"),null==i&&(i=r.opt("longPressDelay")),n=l?this.buildSegDragListener(t):this.buildSegSelectListener(t),n.startInteraction(e,{delay:o?0:i})),this.tempIgnoreMouse()},handleSegTouchEnd:function(t,e){this.tempIgnoreMouse()},startSegResize:function(e,n,i){return!!t(n.target).is(".fc-resizer")&&(this.buildSegResizeListener(e,t(n.target).is(".fc-start-resizer")).startInteraction(n,i),!0)},buildSegDragListener:function(t){var e,n,i,r=this,l=this.view,a=l.calendar,u=t.el,c=t.event;if(this.segDragListener)return this.segDragListener;var d=this.segDragListener=new pe(l,{scroll:l.opt("dragScroll"),subjectEl:u,subjectCenter:!0,interactionStart:function(i){t.component=r,e=!1,n=new ve(t.el,{additionalClass:"fc-dragging",parentEl:l.el,opacity:d.isTouch?null:l.opt("dragOpacity"),revertDuration:l.opt("dragRevertDuration"),zIndex:2}),n.hide(),n.start(i)},dragStart:function(n){d.isTouch&&!l.isEventSelected(c)&&l.selectEvent(c),e=!0,r.handleSegMouseout(t,n),r.segDragStart(t,n),l.hideEvent(c)},hitOver:function(e,o,u){var h;t.hit&&(u=t.hit),i=r.computeEventDrop(u.component.getHitSpan(u),e.component.getHitSpan(e),c),i&&!a.isEventSpanAllowed(r.eventToSpan(i),c)&&(s(),i=null),i&&(h=l.renderDrag(i,t))?(h.addClass("fc-dragging"),d.isTouch||r.applyDragOpacity(h),n.hide()):n.show(),o&&(i=null)},hitOut:function(){l.unrenderDrag(),n.show(),i=null},hitDone:function(){o()},interactionEnd:function(s){delete t.component,n.stop(!i,function(){e&&(l.unrenderDrag(),r.segDragStop(t,s)),i?l.reportEventDrop(c,i,r.largeUnit,u,s):l.showEvent(c)}),r.segDragListener=null}});return d},buildSegSelectListener:function(t){var e=this,n=this.view,i=t.event;if(this.segDragListener)return this.segDragListener;var r=this.segDragListener=new ge({dragStart:function(t){r.isTouch&&!n.isEventSelected(i)&&n.selectEvent(i)},interactionEnd:function(t){e.segDragListener=null}});return r},segDragStart:function(t,e){this.isDraggingSeg=!0,this.view.publiclyTrigger("eventDragStart",t.el[0],t.event,e,{})},segDragStop:function(t,e){this.isDraggingSeg=!1,this.view.publiclyTrigger("eventDragStop",t.el[0],t.event,e,{})},computeEventDrop:function(t,e,n){var i,r,s=this.view.calendar,o=t.start,l=e.start;return o.hasTime()===l.hasTime()?(i=this.diffDates(l,o),n.allDay&&W(i)?(r={start:n.start.clone(),end:s.getEventEnd(n),allDay:!1},s.normalizeEventTimes(r)):r=Ht(n),r.start.add(i),r.end&&r.end.add(i)):r={start:l.clone(),end:null,allDay:!l.hasTime()},r},applyDragOpacity:function(t){var e=this.view.opt("dragOpacity");null!=e&&t.css("opacity",e)},externalDragStart:function(e,n){var i,r,s=this.view;s.opt("droppable")&&(i=t((n?n.item:null)||e.target),r=s.opt("dropAccept"),(t.isFunction(r)?r.call(i[0],i):i.is(r))&&(this.isDraggingExternal||this.listenToExternalDrag(i,e,n)))},listenToExternalDrag:function(t,e,n){var i,r=this,l=this.view.calendar,a=Mt(t),u=r.externalDragListener=new pe(this,{interactionStart:function(){r.isDraggingExternal=!0},hitOver:function(t){i=r.computeExternalDrop(t.component.getHitSpan(t),a),i&&!l.isExternalSpanAllowed(r.eventToSpan(i),i,a.eventProps)&&(s(),i=null),i&&r.renderDrag(i)},hitOut:function(){i=null},hitDone:function(){o(),r.unrenderDrag()},interactionEnd:function(e){i&&r.view.reportExternalDrop(a,i,t,e,n),r.isDraggingExternal=!1,r.externalDragListener=null}});u.startDrag(e)},computeExternalDrop:function(t,e){var n=this.view.calendar,i={start:n.applyTimezone(t.start),end:null};return e.startTime&&!i.start.hasTime()&&i.start.time(e.startTime),e.duration&&(i.end=i.start.clone().add(e.duration)),i},renderDrag:function(t,e){},unrenderDrag:function(){},buildSegResizeListener:function(t,e){var n,i,r=this,l=this.view,a=l.calendar,u=t.el,c=t.event,d=a.getEventEnd(c),h=this.segResizeListener=new pe(this,{scroll:l.opt("dragScroll"),subjectEl:u,interactionStart:function(){n=!1},dragStart:function(e){n=!0,r.handleSegMouseout(t,e),r.segResizeStart(t,e)},hitOver:function(n,o,u){var h=r.getHitSpan(u),f=r.getHitSpan(n);i=e?r.computeEventStartResize(h,f,c):r.computeEventEndResize(h,f,c),i&&(a.isEventSpanAllowed(r.eventToSpan(i),c)?i.start.isSame(c.start.clone().stripZone())&&i.end.isSame(d.clone().stripZone())&&(i=null):(s(),i=null)),i&&(l.hideEvent(c),r.renderEventResize(i,t))},hitOut:function(){i=null,l.showEvent(c)},hitDone:function(){r.unrenderEventResize(),o()},interactionEnd:function(e){n&&r.segResizeStop(t,e),i?l.reportEventResize(c,i,r.largeUnit,u,e):l.showEvent(c),r.segResizeListener=null}});return h},segResizeStart:function(t,e){this.isResizingSeg=!0,this.view.publiclyTrigger("eventResizeStart",t.el[0],t.event,e,{})},segResizeStop:function(t,e){this.isResizingSeg=!1,this.view.publiclyTrigger("eventResizeStop",t.el[0],t.event,e,{})},computeEventStartResize:function(t,e,n){return this.computeEventResize("start",t,e,n)},computeEventEndResize:function(t,e,n){return this.computeEventResize("end",t,e,n)},computeEventResize:function(t,e,n,i){var r,s,o=this.view.calendar,l=this.diffDates(n[t],e[t]);return r={start:i.start.clone(),end:o.getEventEnd(i),allDay:i.allDay},r.allDay&&W(l)&&(r.allDay=!1,o.normalizeEventTimes(r)),r[t].add(l),r.start.isBefore(r.end)||(s=this.minResizeDuration||(i.allDay?o.defaultAllDayEventDuration:o.defaultTimedEventDuration),"start"==t?r.start=r.end.clone().subtract(s):r.end=r.start.clone().add(s)),r},renderEventResize:function(t,e){},unrenderEventResize:function(){},getEventTimeText:function(t,e,n){return null==e&&(e=this.eventTimeFormat),null==n&&(n=this.displayEventEnd),this.displayEventTime&&t.start.hasTime()?n&&t.end?this.view.formatRange(t,e):t.start.format(e):""},getSegClasses:function(t,e,n){var i=this.view,r=["fc-event",t.isStart?"fc-start":"fc-not-start",t.isEnd?"fc-end":"fc-not-end"].concat(this.getSegCustomClasses(t));return e&&r.push("fc-draggable"),n&&r.push("fc-resizable"),i.isEventSelected(t.event)&&r.push("fc-selected"),r},getSegCustomClasses:function(t){var e=t.event;return[].concat(e.className,e.source?e.source.className:[])},getSegSkinCss:function(t){return{"background-color":this.getSegBackgroundColor(t),"border-color":this.getSegBorderColor(t),color:this.getSegTextColor(t)}},getSegBackgroundColor:function(t){return t.event.backgroundColor||t.event.color||this.getSegDefaultBackgroundColor(t)},getSegDefaultBackgroundColor:function(t){var e=t.event.source||{};return e.backgroundColor||e.color||this.view.opt("eventBackgroundColor")||this.view.opt("eventColor")},getSegBorderColor:function(t){return t.event.borderColor||t.event.color||this.getSegDefaultBorderColor(t)},getSegDefaultBorderColor:function(t){var e=t.event.source||{};return e.borderColor||e.color||this.view.opt("eventBorderColor")||this.view.opt("eventColor")},getSegTextColor:function(t){return t.event.textColor||this.getSegDefaultTextColor(t)},getSegDefaultTextColor:function(t){var e=t.event.source||{};return e.textColor||this.view.opt("eventTextColor")},eventToSegs:function(t){return this.eventsToSegs([t])},eventToSpan:function(t){return this.eventToSpans(t)[0]},eventToSpans:function(t){var e=this.eventToRange(t);return this.eventRangeToSpans(e,t)},eventsToSegs:function(e,n){var i=this,r=kt(e),s=[];return t.each(r,function(t,e){var r,o=[];for(r=0;r<e.length;r++)o.push(i.eventToRange(e[r]));if(xt(e[0]))for(o=i.invertRanges(o),r=0;r<o.length;r++)s.push.apply(s,i.eventRangeToSegs(o[r],e[0],n));else for(r=0;r<o.length;r++)s.push.apply(s,i.eventRangeToSegs(o[r],e[r],n))}),s},eventToRange:function(t){var e=this.view.calendar,n=t.start.clone().stripZone(),i=(t.end?t.end.clone():e.getDefaultEventEnd(null!=t.allDay?t.allDay:!t.start.hasTime(),t.start)).stripZone();return e.localizeMoment(n),e.localizeMoment(i),{start:n,end:i}},eventRangeToSegs:function(t,e,n){var i,r=this.eventRangeToSpans(t,e),s=[];for(i=0;i<r.length;i++)s.push.apply(s,this.eventSpanToSegs(r[i],e,n));return s},eventRangeToSpans:function(e,n){return[t.extend({},e)]},eventSpanToSegs:function(t,e,n){var i,r,s=n?n(t):this.spanToSegs(t);
-for(i=0;i<s.length;i++)r=s[i],r.event=e,r.eventStartMS=+t.start,r.eventDurationMS=t.end-t.start;return s},invertRanges:function(t){var e,n,i=this.view,r=i.start.clone(),s=i.end.clone(),o=[],l=r;for(t.sort(Lt),e=0;e<t.length;e++)n=t[e],n.start>l&&o.push({start:l,end:n.start}),l=n.end;return l<s&&o.push({start:l,end:s}),o},sortEventSegs:function(t){t.sort(lt(this,"compareEventSegs"))},compareEventSegs:function(t,e){return t.eventStartMS-e.eventStartMS||e.eventDurationMS-t.eventDurationMS||e.event.allDay-t.event.allDay||M(t.event,e.event,this.view.eventOrderSpecs)}}),qt.pluckEventDateProps=Ht,qt.isBgEvent=Rt,qt.dataAttrPrefix="";var ye=qt.DayTableMixin={breakOnWeeks:!1,dayDates:null,dayIndices:null,daysPerRow:null,rowCnt:null,colCnt:null,colHeadFormat:null,updateDayTable:function(){for(var t,e,n,i=this.view,r=this.start.clone(),s=-1,o=[],l=[];r.isBefore(this.end);)i.isHiddenDay(r)?o.push(s+.5):(s++,o.push(s),l.push(r.clone())),r.add(1,"days");if(this.breakOnWeeks){for(e=l[0].day(),t=1;t<l.length&&l[t].day()!=e;t++);n=Math.ceil(l.length/t)}else n=1,t=l.length;this.dayDates=l,this.dayIndices=o,this.daysPerRow=t,this.rowCnt=n,this.updateDayTableCols()},updateDayTableCols:function(){this.colCnt=this.computeColCnt(),this.colHeadFormat=this.view.opt("columnFormat")||this.computeColHeadFormat()},computeColCnt:function(){return this.daysPerRow},getCellDate:function(t,e){return this.dayDates[this.getCellDayIndex(t,e)].clone()},getCellRange:function(t,e){var n=this.getCellDate(t,e),i=n.clone().add(1,"days");return{start:n,end:i}},getCellDayIndex:function(t,e){return t*this.daysPerRow+this.getColDayIndex(e)},getColDayIndex:function(t){return this.isRTL?this.colCnt-1-t:t},getDateDayIndex:function(t){var e=this.dayIndices,n=t.diff(this.start,"days");return n<0?e[0]-1:n>=e.length?e[e.length-1]+1:e[n]},computeColHeadFormat:function(){return this.rowCnt>1||this.colCnt>10?"ddd":this.colCnt>1?this.view.opt("dayOfMonthFormat"):"dddd"},sliceRangeByRow:function(t){var e,n,i,r,s,o=this.daysPerRow,l=this.view.computeDayRange(t),a=this.getDateDayIndex(l.start),u=this.getDateDayIndex(l.end.clone().subtract(1,"days")),c=[];for(e=0;e<this.rowCnt;e++)n=e*o,i=n+o-1,r=Math.max(a,n),s=Math.min(u,i),r=Math.ceil(r),s=Math.floor(s),r<=s&&c.push({row:e,firstRowDayIndex:r-n,lastRowDayIndex:s-n,isStart:r===a,isEnd:s===u});return c},sliceRangeByDay:function(t){var e,n,i,r,s,o,l=this.daysPerRow,a=this.view.computeDayRange(t),u=this.getDateDayIndex(a.start),c=this.getDateDayIndex(a.end.clone().subtract(1,"days")),d=[];for(e=0;e<this.rowCnt;e++)for(n=e*l,i=n+l-1,r=n;r<=i;r++)s=Math.max(u,r),o=Math.min(c,r),s=Math.ceil(s),o=Math.floor(o),s<=o&&d.push({row:e,firstRowDayIndex:s-n,lastRowDayIndex:o-n,isStart:s===u,isEnd:o===c});return d},renderHeadHtml:function(){var t=this.view;return'<div class="fc-row '+t.widgetHeaderClass+'"><table><thead>'+this.renderHeadTrHtml()+"</thead></table></div>"},renderHeadIntroHtml:function(){return this.renderIntroHtml()},renderHeadTrHtml:function(){return"<tr>"+(this.isRTL?"":this.renderHeadIntroHtml())+this.renderHeadDateCellsHtml()+(this.isRTL?this.renderHeadIntroHtml():"")+"</tr>"},renderHeadDateCellsHtml:function(){var t,e,n=[];for(t=0;t<this.colCnt;t++)e=this.getCellDate(0,t),n.push(this.renderHeadDateCellHtml(e));return n.join("")},renderHeadDateCellHtml:function(t,e,n){var i=this.view,r=["fc-day-header",i.widgetHeaderClass];return 1===this.rowCnt?r=r.concat(this.getDayClasses(t,!0)):r.push("fc-"+Xt[t.day()]),'<th class="'+r.join(" ")+'"'+(1===this.rowCnt?' data-date="'+t.format("YYYY-MM-DD")+'"':"")+(e>1?' colspan="'+e+'"':"")+(n?" "+n:"")+">"+i.buildGotoAnchorHtml({date:t,forceOff:this.rowCnt>1||1===this.colCnt},tt(t.format(this.colHeadFormat)))+"</th>"},renderBgTrHtml:function(t){return"<tr>"+(this.isRTL?"":this.renderBgIntroHtml(t))+this.renderBgCellsHtml(t)+(this.isRTL?this.renderBgIntroHtml(t):"")+"</tr>"},renderBgIntroHtml:function(t){return this.renderIntroHtml()},renderBgCellsHtml:function(t){var e,n,i=[];for(e=0;e<this.colCnt;e++)n=this.getCellDate(t,e),i.push(this.renderBgCellHtml(n));return i.join("")},renderBgCellHtml:function(t,e){var n=this.view,i=this.getDayClasses(t);return i.unshift("fc-day",n.widgetContentClass),'<td class="'+i.join(" ")+'" data-date="'+t.format("YYYY-MM-DD")+'"'+(e?" "+e:"")+"></td>"},renderIntroHtml:function(){},bookendCells:function(t){var e=this.renderIntroHtml();e&&(this.isRTL?t.append(e):t.prepend(e))}},Se=qt.DayGrid=me.extend(ye,{numbersVisible:!1,bottomCoordPadding:0,rowEls:null,cellEls:null,helperEls:null,rowCoordCache:null,colCoordCache:null,renderDates:function(t){var e,n,i=this.view,r=this.rowCnt,s=this.colCnt,o="";for(e=0;e<r;e++)o+=this.renderDayRowHtml(e,t);for(this.el.html(o),this.rowEls=this.el.find(".fc-row"),this.cellEls=this.el.find(".fc-day"),this.rowCoordCache=new fe({els:this.rowEls,isVertical:!0}),this.colCoordCache=new fe({els:this.cellEls.slice(0,this.colCnt),isHorizontal:!0}),e=0;e<r;e++)for(n=0;n<s;n++)i.publiclyTrigger("dayRender",null,this.getCellDate(e,n),this.getCellEl(e,n))},unrenderDates:function(){this.removeSegPopover()},renderBusinessHours:function(){var t=this.buildBusinessHourSegs(!0);this.renderFill("businessHours",t,"bgevent")},unrenderBusinessHours:function(){this.unrenderFill("businessHours")},renderDayRowHtml:function(t,e){var n=this.view,i=["fc-row","fc-week",n.widgetContentClass];return e&&i.push("fc-rigid"),'<div class="'+i.join(" ")+'"><div class="fc-bg"><table>'+this.renderBgTrHtml(t)+'</table></div><div class="fc-content-skeleton"><table>'+(this.numbersVisible?"<thead>"+this.renderNumberTrHtml(t)+"</thead>":"")+"</table></div></div>"},renderNumberTrHtml:function(t){return"<tr>"+(this.isRTL?"":this.renderNumberIntroHtml(t))+this.renderNumberCellsHtml(t)+(this.isRTL?this.renderNumberIntroHtml(t):"")+"</tr>"},renderNumberIntroHtml:function(t){return this.renderIntroHtml()},renderNumberCellsHtml:function(t){var e,n,i=[];for(e=0;e<this.colCnt;e++)n=this.getCellDate(t,e),i.push(this.renderNumberCellHtml(n));return i.join("")},renderNumberCellHtml:function(t){var e,n,i="";return this.view.dayNumbersVisible||this.view.cellWeekNumbersVisible?(e=this.getDayClasses(t),e.unshift("fc-day-top"),this.view.cellWeekNumbersVisible&&(n="ISO"===t._locale._fullCalendar_weekCalc?1:t._locale.firstDayOfWeek()),i+='<td class="'+e.join(" ")+'" data-date="'+t.format()+'">',this.view.cellWeekNumbersVisible&&t.day()==n&&(i+=this.view.buildGotoAnchorHtml({date:t,type:"week"},{class:"fc-week-number"},t.format("w"))),this.view.dayNumbersVisible&&(i+=this.view.buildGotoAnchorHtml(t,{class:"fc-day-number"},t.date())),i+="</td>"):"<td/>"},computeEventTimeFormat:function(){return this.view.opt("extraSmallTimeFormat")},computeDisplayEventEnd:function(){return 1==this.colCnt},rangeUpdated:function(){this.updateDayTable()},spanToSegs:function(t){var e,n,i=this.sliceRangeByRow(t);for(e=0;e<i.length;e++)n=i[e],this.isRTL?(n.leftCol=this.daysPerRow-1-n.lastRowDayIndex,n.rightCol=this.daysPerRow-1-n.firstRowDayIndex):(n.leftCol=n.firstRowDayIndex,n.rightCol=n.lastRowDayIndex);return i},prepareHits:function(){this.colCoordCache.build(),this.rowCoordCache.build(),this.rowCoordCache.bottoms[this.rowCnt-1]+=this.bottomCoordPadding},releaseHits:function(){this.colCoordCache.clear(),this.rowCoordCache.clear()},queryHit:function(t,e){if(this.colCoordCache.isLeftInBounds(t)&&this.rowCoordCache.isTopInBounds(e)){var n=this.colCoordCache.getHorizontalIndex(t),i=this.rowCoordCache.getVerticalIndex(e);if(null!=i&&null!=n)return this.getCellHit(i,n)}},getHitSpan:function(t){return this.getCellRange(t.row,t.col)},getHitEl:function(t){return this.getCellEl(t.row,t.col)},getCellHit:function(t,e){return{row:t,col:e,component:this,left:this.colCoordCache.getLeftOffset(e),right:this.colCoordCache.getRightOffset(e),top:this.rowCoordCache.getTopOffset(t),bottom:this.rowCoordCache.getBottomOffset(t)}},getCellEl:function(t,e){return this.cellEls.eq(t*this.colCnt+e)},renderDrag:function(t,e){if(this.renderHighlight(this.eventToSpan(t)),e&&e.component!==this)return this.renderEventLocationHelper(t,e)},unrenderDrag:function(){this.unrenderHighlight(),this.unrenderHelper()},renderEventResize:function(t,e){return this.renderHighlight(this.eventToSpan(t)),this.renderEventLocationHelper(t,e)},unrenderEventResize:function(){this.unrenderHighlight(),this.unrenderHelper()},renderHelper:function(e,n){var i,r=[],s=this.eventToSegs(e);return s=this.renderFgSegEls(s),i=this.renderSegRows(s),this.rowEls.each(function(e,s){var o,l=t(s),a=t('<div class="fc-helper-skeleton"><table/></div>');o=n&&n.row===e?n.el.position().top:l.find(".fc-content-skeleton tbody").position().top,a.css("top",o).find("table").append(i[e].tbodyEl),l.append(a),r.push(a[0])}),this.helperEls=t(r)},unrenderHelper:function(){this.helperEls&&(this.helperEls.remove(),this.helperEls=null)},fillSegTag:"td",renderFill:function(e,n,i){var r,s,o,l=[];for(n=this.renderFillSegEls(e,n),r=0;r<n.length;r++)s=n[r],o=this.renderFillRow(e,s,i),this.rowEls.eq(s.row).append(o),l.push(o[0]);return this.elsByFill[e]=t(l),n},renderFillRow:function(e,n,i){var r,s,o=this.colCnt,l=n.leftCol,a=n.rightCol+1;return i=i||e.toLowerCase(),r=t('<div class="fc-'+i+'-skeleton"><table><tr/></table></div>'),s=r.find("tr"),l>0&&s.append('<td colspan="'+l+'"/>'),s.append(n.el.attr("colspan",a-l)),a<o&&s.append('<td colspan="'+(o-a)+'"/>'),this.bookendCells(s),r}});Se.mixin({rowStructs:null,unrenderEvents:function(){this.removeSegPopover(),me.prototype.unrenderEvents.apply(this,arguments)},getEventSegs:function(){return me.prototype.getEventSegs.call(this).concat(this.popoverSegs||[])},renderBgSegs:function(e){var n=t.grep(e,function(t){return t.event.allDay});return me.prototype.renderBgSegs.call(this,n)},renderFgSegs:function(e){var n;return e=this.renderFgSegEls(e),n=this.rowStructs=this.renderSegRows(e),this.rowEls.each(function(e,i){t(i).find(".fc-content-skeleton > table").append(n[e].tbodyEl)}),e},unrenderFgSegs:function(){for(var t,e=this.rowStructs||[];t=e.pop();)t.tbodyEl.remove();this.rowStructs=null},renderSegRows:function(t){var e,n,i=[];for(e=this.groupSegRows(t),n=0;n<e.length;n++)i.push(this.renderSegRow(n,e[n]));return i},fgSegHtml:function(t,e){var n,i,r=this.view,s=t.event,o=r.isEventDraggable(s),l=!e&&s.allDay&&t.isStart&&r.isEventResizableFromStart(s),a=!e&&s.allDay&&t.isEnd&&r.isEventResizableFromEnd(s),u=this.getSegClasses(t,o,l||a),c=nt(this.getSegSkinCss(t)),d="";return u.unshift("fc-day-grid-event","fc-h-event"),t.isStart&&(n=this.getEventTimeText(s),n&&(d='<span class="fc-time">'+tt(n)+"</span>")),i='<span class="fc-title">'+(tt(s.title||"")||"&nbsp;")+"</span>",'<a class="'+u.join(" ")+'"'+(s.url?' href="'+tt(s.url)+'"':"")+(c?' style="'+c+'"':"")+'><div class="fc-content">'+(this.isRTL?i+" "+d:d+" "+i)+"</div>"+(l?'<div class="fc-resizer fc-start-resizer" />':"")+(a?'<div class="fc-resizer fc-end-resizer" />':"")+"</a>"},renderSegRow:function(e,n){function i(e){for(;o<e;)c=(m[r-1]||[])[o],c?c.attr("rowspan",parseInt(c.attr("rowspan")||1,10)+1):(c=t("<td/>"),l.append(c)),v[r][o]=c,m[r][o]=c,o++}var r,s,o,l,a,u,c,d=this.colCnt,h=this.buildSegLevels(n),f=Math.max(1,h.length),g=t("<tbody/>"),p=[],v=[],m=[];for(r=0;r<f;r++){if(s=h[r],o=0,l=t("<tr/>"),p.push([]),v.push([]),m.push([]),s)for(a=0;a<s.length;a++){for(u=s[a],i(u.leftCol),c=t('<td class="fc-event-container"/>').append(u.el),u.leftCol!=u.rightCol?c.attr("colspan",u.rightCol-u.leftCol+1):m[r][o]=c;o<=u.rightCol;)v[r][o]=c,p[r][o]=u,o++;l.append(c)}i(d),this.bookendCells(l),g.append(l)}return{row:e,tbodyEl:g,cellMatrix:v,segMatrix:p,segLevels:h,segs:n}},buildSegLevels:function(t){var e,n,i,r=[];for(this.sortEventSegs(t),e=0;e<t.length;e++){for(n=t[e],i=0;i<r.length&&Bt(n,r[i]);i++);n.level=i,(r[i]||(r[i]=[])).push(n)}for(i=0;i<r.length;i++)r[i].sort(zt);return r},groupSegRows:function(t){var e,n=[];for(e=0;e<this.rowCnt;e++)n.push([]);for(e=0;e<t.length;e++)n[t[e].row].push(t[e]);return n}}),Se.mixin({segPopover:null,popoverSegs:null,removeSegPopover:function(){this.segPopover&&this.segPopover.hide()},limitRows:function(t){var e,n,i=this.rowStructs||[];for(e=0;e<i.length;e++)this.unlimitRow(e),n=!!t&&("number"==typeof t?t:this.computeRowLevelLimit(e)),n!==!1&&this.limitRow(e,n)},computeRowLevelLimit:function(e){function n(e,n){s=Math.max(s,t(n).outerHeight())}var i,r,s,o=this.rowEls.eq(e),l=o.height(),a=this.rowStructs[e].tbodyEl.children();for(i=0;i<a.length;i++)if(r=a.eq(i).removeClass("fc-limited"),s=0,r.find("> td > :first-child").each(n),r.position().top+s>l)return i;return!1},limitRow:function(e,n){function i(i){for(;b<i;)u=S.getCellSegs(e,b,n),u.length&&(h=s[n-1][b],y=S.renderMoreLink(e,b,u),m=t("<div/>").append(y),h.append(m),E.push(m[0])),b++}var r,s,o,l,a,u,c,d,h,f,g,p,v,m,y,S=this,w=this.rowStructs[e],E=[],b=0;if(n&&n<w.segLevels.length){for(r=w.segLevels[n-1],s=w.cellMatrix,o=w.tbodyEl.children().slice(n).addClass("fc-limited").get(),l=0;l<r.length;l++){for(a=r[l],i(a.leftCol),d=[],c=0;b<=a.rightCol;)u=this.getCellSegs(e,b,n),d.push(u),c+=u.length,b++;if(c){for(h=s[n-1][a.leftCol],f=h.attr("rowspan")||1,g=[],p=0;p<d.length;p++)v=t('<td class="fc-more-cell"/>').attr("rowspan",f),u=d[p],y=this.renderMoreLink(e,a.leftCol+p,[a].concat(u)),m=t("<div/>").append(y),v.append(m),g.push(v[0]),E.push(v[0]);h.addClass("fc-limited").after(t(g)),o.push(h[0])}}i(this.colCnt),w.moreEls=t(E),w.limitedEls=t(o)}},unlimitRow:function(t){var e=this.rowStructs[t];e.moreEls&&(e.moreEls.remove(),e.moreEls=null),e.limitedEls&&(e.limitedEls.removeClass("fc-limited"),e.limitedEls=null)},renderMoreLink:function(e,n,i){var r=this,s=this.view;return t('<a class="fc-more"/>').text(this.getMoreLinkText(i.length)).on("click",function(o){var l=s.opt("eventLimitClick"),a=r.getCellDate(e,n),u=t(this),c=r.getCellEl(e,n),d=r.getCellSegs(e,n),h=r.resliceDaySegs(d,a),f=r.resliceDaySegs(i,a);"function"==typeof l&&(l=s.publiclyTrigger("eventLimitClick",null,{date:a,dayEl:c,moreEl:u,segs:h,hiddenSegs:f},o)),"popover"===l?r.showSegPopover(e,n,u,h):"string"==typeof l&&s.calendar.zoomTo(a,l)})},showSegPopover:function(t,e,n,i){var r,s,o=this,l=this.view,a=n.parent();r=1==this.rowCnt?l.el:this.rowEls.eq(t),s={className:"fc-more-popover",content:this.renderSegPopoverContent(t,e,i),parentEl:this.view.el,top:r.offset().top,autoHide:!0,viewportConstrain:l.opt("popoverViewportConstrain"),hide:function(){if(o.popoverSegs)for(var t,e=0;e<o.popoverSegs.length;++e)t=o.popoverSegs[e],l.publiclyTrigger("eventDestroy",t.event,t.event,t.el);o.segPopover.removeElement(),o.segPopover=null,o.popoverSegs=null}},this.isRTL?s.right=a.offset().left+a.outerWidth()+1:s.left=a.offset().left-1,this.segPopover=new he(s),this.segPopover.show(),this.bindSegHandlersToEl(this.segPopover.el)},renderSegPopoverContent:function(e,n,i){var r,s=this.view,o=s.opt("theme"),l=this.getCellDate(e,n).format(s.opt("dayPopoverFormat")),a=t('<div class="fc-header '+s.widgetHeaderClass+'"><span class="fc-close '+(o?"ui-icon ui-icon-closethick":"fc-icon fc-icon-x")+'"></span><span class="fc-title">'+tt(l)+'</span><div class="fc-clear"/></div><div class="fc-body '+s.widgetContentClass+'"><div class="fc-event-container"></div></div>'),u=a.find(".fc-event-container");for(i=this.renderFgSegEls(i,!0),this.popoverSegs=i,r=0;r<i.length;r++)this.prepareHits(),i[r].hit=this.getCellHit(e,n),this.releaseHits(),u.append(i[r].el);return a},resliceDaySegs:function(e,n){var i=t.map(e,function(t){return t.event}),r=n.clone(),s=r.clone().add(1,"days"),o={start:r,end:s};return e=this.eventsToSegs(i,function(t){var e=F(t,o);return e?[e]:[]}),this.sortEventSegs(e),e},getMoreLinkText:function(t){var e=this.view.opt("eventLimitText");return"function"==typeof e?e(t):"+"+t+" "+e},getCellSegs:function(t,e,n){for(var i,r=this.rowStructs[t].segMatrix,s=n||0,o=[];s<r.length;)i=r[s][e],i&&o.push(i),s++;return o}});var we=qt.TimeGrid=me.extend(ye,{slotDuration:null,snapDuration:null,snapsPerSlot:null,minTime:null,maxTime:null,labelFormat:null,labelInterval:null,colEls:null,slatContainerEl:null,slatEls:null,nowIndicatorEls:null,colCoordCache:null,slatCoordCache:null,constructor:function(){me.apply(this,arguments),this.processOptions()},renderDates:function(){this.el.html(this.renderHtml()),this.colEls=this.el.find(".fc-day"),this.slatContainerEl=this.el.find(".fc-slats"),this.slatEls=this.slatContainerEl.find("tr"),this.colCoordCache=new fe({els:this.colEls,isHorizontal:!0}),this.slatCoordCache=new fe({els:this.slatEls,isVertical:!0}),this.renderContentSkeleton()},renderHtml:function(){return'<div class="fc-bg"><table>'+this.renderBgTrHtml(0)+'</table></div><div class="fc-slats"><table>'+this.renderSlatRowHtml()+"</table></div>"},renderSlatRowHtml:function(){for(var t,n,i,r=this.view,s=this.isRTL,o="",l=e.duration(+this.minTime);l<this.maxTime;)t=this.start.clone().time(l),n=ot(_(l,this.labelInterval)),i='<td class="fc-axis fc-time '+r.widgetContentClass+'" '+r.axisStyleAttr()+">"+(n?"<span>"+tt(t.format(this.labelFormat))+"</span>":"")+"</td>",o+='<tr data-time="'+t.format("HH:mm:ss")+'"'+(n?"":' class="fc-minor"')+">"+(s?"":i)+'<td class="'+r.widgetContentClass+'"/>'+(s?i:"")+"</tr>",l.add(this.slotDuration);return o},processOptions:function(){var n,i=this.view,r=i.opt("slotDuration"),s=i.opt("snapDuration");r=e.duration(r),s=s?e.duration(s):r,this.slotDuration=r,this.snapDuration=s,this.snapsPerSlot=r/s,this.minResizeDuration=s,this.minTime=e.duration(i.opt("minTime")),this.maxTime=e.duration(i.opt("maxTime")),n=i.opt("slotLabelFormat"),t.isArray(n)&&(n=n[n.length-1]),this.labelFormat=n||i.opt("smallTimeFormat"),n=i.opt("slotLabelInterval"),this.labelInterval=n?e.duration(n):this.computeLabelInterval(r)},computeLabelInterval:function(t){var n,i,r;for(n=Oe.length-1;n>=0;n--)if(i=e.duration(Oe[n]),r=_(i,t),ot(r)&&r>1)return i;return e.duration(t)},computeEventTimeFormat:function(){return this.view.opt("noMeridiemTimeFormat")},computeDisplayEventEnd:function(){return!0},prepareHits:function(){this.colCoordCache.build(),this.slatCoordCache.build()},releaseHits:function(){this.colCoordCache.clear()},queryHit:function(t,e){var n=this.snapsPerSlot,i=this.colCoordCache,r=this.slatCoordCache;if(i.isLeftInBounds(t)&&r.isTopInBounds(e)){var s=i.getHorizontalIndex(t),o=r.getVerticalIndex(e);if(null!=s&&null!=o){var l=r.getTopOffset(o),a=r.getHeight(o),u=(e-l)/a,c=Math.floor(u*n),d=o*n+c,h=l+c/n*a,f=l+(c+1)/n*a;return{col:s,snap:d,component:this,left:i.getLeftOffset(s),right:i.getRightOffset(s),top:h,bottom:f}}}},getHitSpan:function(t){var e,n=this.getCellDate(0,t.col),i=this.computeSnapTime(t.snap);return n.time(i),e=n.clone().add(this.snapDuration),{start:n,end:e}},getHitEl:function(t){return this.colEls.eq(t.col)},rangeUpdated:function(){this.updateDayTable()},computeSnapTime:function(t){return e.duration(this.minTime+this.snapDuration*t)},spanToSegs:function(t){var e,n=this.sliceRangeByTimes(t);for(e=0;e<n.length;e++)this.isRTL?n[e].col=this.daysPerRow-1-n[e].dayIndex:n[e].col=n[e].dayIndex;return n},sliceRangeByTimes:function(t){var e,n,i,r,s=[];for(n=0;n<this.daysPerRow;n++)i=this.dayDates[n].clone(),r={start:i.clone().time(this.minTime),end:i.clone().time(this.maxTime)},e=F(t,r),e&&(e.dayIndex=n,s.push(e));return s},updateSize:function(t){this.slatCoordCache.build(),t&&this.updateSegVerticals([].concat(this.fgSegs||[],this.bgSegs||[],this.businessSegs||[]))},getTotalSlatHeight:function(){return this.slatContainerEl.outerHeight()},computeDateTop:function(t,n){return this.computeTimeTop(e.duration(t-n.clone().stripTime()))},computeTimeTop:function(t){var e,n,i=this.slatEls.length,r=(t-this.minTime)/this.slotDuration;return r=Math.max(0,r),r=Math.min(i,r),e=Math.floor(r),e=Math.min(e,i-1),n=r-e,this.slatCoordCache.getTopPosition(e)+this.slatCoordCache.getHeight(e)*n},renderDrag:function(t,e){return e?this.renderEventLocationHelper(t,e):void this.renderHighlight(this.eventToSpan(t))},unrenderDrag:function(){this.unrenderHelper(),this.unrenderHighlight()},renderEventResize:function(t,e){return this.renderEventLocationHelper(t,e)},unrenderEventResize:function(){this.unrenderHelper()},renderHelper:function(t,e){return this.renderHelperSegs(this.eventToSegs(t),e)},unrenderHelper:function(){this.unrenderHelperSegs()},renderBusinessHours:function(){this.renderBusinessSegs(this.buildBusinessHourSegs())},unrenderBusinessHours:function(){this.unrenderBusinessSegs()},getNowIndicatorUnit:function(){return"minute"},renderNowIndicator:function(e){var n,i=this.spanToSegs({start:e,end:e}),r=this.computeDateTop(e,e),s=[];for(n=0;n<i.length;n++)s.push(t('<div class="fc-now-indicator fc-now-indicator-line"></div>').css("top",r).appendTo(this.colContainerEls.eq(i[n].col))[0]);i.length>0&&s.push(t('<div class="fc-now-indicator fc-now-indicator-arrow"></div>').css("top",r).appendTo(this.el.find(".fc-content-skeleton"))[0]),this.nowIndicatorEls=t(s)},unrenderNowIndicator:function(){this.nowIndicatorEls&&(this.nowIndicatorEls.remove(),this.nowIndicatorEls=null)},renderSelection:function(t){this.view.opt("selectHelper")?this.renderEventLocationHelper(t):this.renderHighlight(t)},unrenderSelection:function(){this.unrenderHelper(),this.unrenderHighlight()},renderHighlight:function(t){this.renderHighlightSegs(this.spanToSegs(t))},unrenderHighlight:function(){this.unrenderHighlightSegs()}});we.mixin({colContainerEls:null,fgContainerEls:null,bgContainerEls:null,helperContainerEls:null,highlightContainerEls:null,businessContainerEls:null,fgSegs:null,bgSegs:null,helperSegs:null,highlightSegs:null,businessSegs:null,renderContentSkeleton:function(){var e,n,i="";for(e=0;e<this.colCnt;e++)i+='<td><div class="fc-content-col"><div class="fc-event-container fc-helper-container"></div><div class="fc-event-container"></div><div class="fc-highlight-container"></div><div class="fc-bgevent-container"></div><div class="fc-business-container"></div></div></td>';n=t('<div class="fc-content-skeleton"><table><tr>'+i+"</tr></table></div>"),this.colContainerEls=n.find(".fc-content-col"),this.helperContainerEls=n.find(".fc-helper-container"),this.fgContainerEls=n.find(".fc-event-container:not(.fc-helper-container)"),this.bgContainerEls=n.find(".fc-bgevent-container"),this.highlightContainerEls=n.find(".fc-highlight-container"),this.businessContainerEls=n.find(".fc-business-container"),this.bookendCells(n.find("tr")),this.el.append(n)},renderFgSegs:function(t){return t=this.renderFgSegsIntoContainers(t,this.fgContainerEls),this.fgSegs=t,t},unrenderFgSegs:function(){this.unrenderNamedSegs("fgSegs")},renderHelperSegs:function(e,n){var i,r,s,o=[];for(e=this.renderFgSegsIntoContainers(e,this.helperContainerEls),i=0;i<e.length;i++)r=e[i],n&&n.col===r.col&&(s=n.el,r.el.css({left:s.css("left"),right:s.css("right"),"margin-left":s.css("margin-left"),"margin-right":s.css("margin-right")})),o.push(r.el[0]);return this.helperSegs=e,t(o)},unrenderHelperSegs:function(){this.unrenderNamedSegs("helperSegs")},renderBgSegs:function(t){return t=this.renderFillSegEls("bgEvent",t),this.updateSegVerticals(t),this.attachSegsByCol(this.groupSegsByCol(t),this.bgContainerEls),this.bgSegs=t,t},unrenderBgSegs:function(){this.unrenderNamedSegs("bgSegs")},renderHighlightSegs:function(t){t=this.renderFillSegEls("highlight",t),this.updateSegVerticals(t),this.attachSegsByCol(this.groupSegsByCol(t),this.highlightContainerEls),this.highlightSegs=t},unrenderHighlightSegs:function(){this.unrenderNamedSegs("highlightSegs")},renderBusinessSegs:function(t){t=this.renderFillSegEls("businessHours",t),this.updateSegVerticals(t),this.attachSegsByCol(this.groupSegsByCol(t),this.businessContainerEls),this.businessSegs=t},unrenderBusinessSegs:function(){this.unrenderNamedSegs("businessSegs")},groupSegsByCol:function(t){var e,n=[];for(e=0;e<this.colCnt;e++)n.push([]);for(e=0;e<t.length;e++)n[t[e].col].push(t[e]);return n},attachSegsByCol:function(t,e){var n,i,r;for(n=0;n<this.colCnt;n++)for(i=t[n],r=0;r<i.length;r++)e.eq(n).append(i[r].el)},unrenderNamedSegs:function(t){var e,n=this[t];if(n){for(e=0;e<n.length;e++)n[e].el.remove();this[t]=null}},renderFgSegsIntoContainers:function(t,e){var n,i;for(t=this.renderFgSegEls(t),n=this.groupSegsByCol(t),i=0;i<this.colCnt;i++)this.updateFgSegCoords(n[i]);return this.attachSegsByCol(n,e),t},fgSegHtml:function(t,e){var n,i,r,s=this.view,o=t.event,l=s.isEventDraggable(o),a=!e&&t.isStart&&s.isEventResizableFromStart(o),u=!e&&t.isEnd&&s.isEventResizableFromEnd(o),c=this.getSegClasses(t,l,a||u),d=nt(this.getSegSkinCss(t));return c.unshift("fc-time-grid-event","fc-v-event"),s.isMultiDayEvent(o)?(t.isStart||t.isEnd)&&(n=this.getEventTimeText(t),i=this.getEventTimeText(t,"LT"),r=this.getEventTimeText(t,null,!1)):(n=this.getEventTimeText(o),i=this.getEventTimeText(o,"LT"),r=this.getEventTimeText(o,null,!1)),'<a class="'+c.join(" ")+'"'+(o.url?' href="'+tt(o.url)+'"':"")+(d?' style="'+d+'"':"")+'><div class="fc-content">'+(n?'<div class="fc-time" data-start="'+tt(r)+'" data-full="'+tt(i)+'"><span>'+tt(n)+"</span></div>":"")+(o.title?'<div class="fc-title">'+tt(o.title)+"</div>":"")+'</div><div class="fc-bg"/>'+(u?'<div class="fc-resizer fc-end-resizer" />':"")+"</a>"},updateSegVerticals:function(t){this.computeSegVerticals(t),this.assignSegVerticals(t)},computeSegVerticals:function(t){var e,n;for(e=0;e<t.length;e++)n=t[e],n.top=this.computeDateTop(n.start,n.start),n.bottom=this.computeDateTop(n.end,n.start)},assignSegVerticals:function(t){var e,n;for(e=0;e<t.length;e++)n=t[e],n.el.css(this.generateSegVerticalCss(n))},generateSegVerticalCss:function(t){return{top:t.top,bottom:-t.bottom}},updateFgSegCoords:function(t){this.computeSegVerticals(t),this.computeFgSegHorizontals(t),this.assignSegVerticals(t),this.assignFgSegHorizontals(t)},computeFgSegHorizontals:function(t){var e,n,i;if(this.sortEventSegs(t),e=Ft(t),Nt(e),n=e[0]){for(i=0;i<n.length;i++)Gt(n[i]);for(i=0;i<n.length;i++)this.computeFgSegForwardBack(n[i],0,0)}},computeFgSegForwardBack:function(t,e,n){var i,r=t.forwardSegs;if(void 0===t.forwardCoord)for(r.length?(this.sortForwardSegs(r),this.computeFgSegForwardBack(r[0],e+1,n),t.forwardCoord=r[0].backwardCoord):t.forwardCoord=1,t.backwardCoord=t.forwardCoord-(t.forwardCoord-n)/(e+1),i=0;i<r.length;i++)this.computeFgSegForwardBack(r[i],0,t.forwardCoord)},sortForwardSegs:function(t){t.sort(lt(this,"compareForwardSegs"))},compareForwardSegs:function(t,e){return e.forwardPressure-t.forwardPressure||(t.backwardCoord||0)-(e.backwardCoord||0)||this.compareEventSegs(t,e)},assignFgSegHorizontals:function(t){var e,n;for(e=0;e<t.length;e++)n=t[e],n.el.css(this.generateFgSegHorizontalCss(n)),n.bottom-n.top<30&&n.el.addClass("fc-short")},generateFgSegHorizontalCss:function(t){var e,n,i=this.view.opt("slotEventOverlap"),r=t.backwardCoord,s=t.forwardCoord,o=this.generateSegVerticalCss(t);return i&&(s=Math.min(1,r+2*(s-r))),this.isRTL?(e=1-s,n=r):(e=r,n=1-s),o.zIndex=t.level+1,o.left=100*e+"%",o.right=100*n+"%",i&&t.forwardPressure&&(o[this.isRTL?"marginLeft":"marginRight"]=20),o}});var Ee=qt.View=St.extend(ue,ce,{type:null,name:null,title:null,calendar:null,options:null,el:null,isDateSet:!1,isDateRendered:!1,dateRenderQueue:null,isEventsBound:!1,isEventsSet:!1,isEventsRendered:!1,eventRenderQueue:null,start:null,end:null,intervalStart:null,intervalEnd:null,intervalDuration:null,intervalUnit:null,isRTL:!1,isSelected:!1,selectedEvent:null,eventOrderSpecs:null,widgetHeaderClass:null,widgetContentClass:null,highlightStateClass:null,nextDayThreshold:null,isHiddenDayHash:null,isNowIndicatorRendered:null,initialNowDate:null,initialNowQueriedMs:null,nowIndicatorTimeoutID:null,nowIndicatorIntervalID:null,constructor:function(t,n,i,r){this.calendar=t,this.type=this.name=n,this.options=i,this.intervalDuration=r||e.duration(1,"day"),this.nextDayThreshold=e.duration(this.opt("nextDayThreshold")),this.initThemingProps(),this.initHiddenDays(),this.isRTL=this.opt("isRTL"),this.eventOrderSpecs=L(this.opt("eventOrder")),this.dateRenderQueue=new Dt,this.eventRenderQueue=new Dt(this.opt("eventRenderWait")),this.initialize()},initialize:function(){},opt:function(t){return this.options[t]},publiclyTrigger:function(t,e){var n=this.calendar;return n.publiclyTrigger.apply(n,[t,e||this].concat(Array.prototype.slice.call(arguments,2),[this]))},rejectOn:function(t,e){var n=this;return new bt(function(i,r){function s(){n.off(t,r)}n.one(t,r),e.then(function(t){s(),i(t)},function(){s(),r()})})},setRange:function(e){t.extend(this,e),this.updateTitle()},computeRange:function(t){var e,n,i=A(this.intervalDuration),r=t.clone().startOf(i),s=r.clone().add(this.intervalDuration);return/year|month|week|day/.test(i)?(r.stripTime(),s.stripTime()):(r.hasTime()||(r=this.calendar.time(0)),s.hasTime()||(s=this.calendar.time(0))),e=r.clone(),e=this.skipHiddenDays(e),n=s.clone(),n=this.skipHiddenDays(n,-1,!0),{intervalUnit:i,intervalStart:r,intervalEnd:s,start:e,end:n}},computePrevDate:function(t){return this.massageCurrentDate(t.clone().startOf(this.intervalUnit).subtract(this.intervalDuration),-1)},computeNextDate:function(t){return this.massageCurrentDate(t.clone().startOf(this.intervalUnit).add(this.intervalDuration))},massageCurrentDate:function(t,e){return this.intervalDuration.as("days")<=1&&this.isHiddenDay(t)&&(t=this.skipHiddenDays(t,e),t.startOf("day")),t},updateTitle:function(){this.title=this.computeTitle(),this.calendar.setToolbarsTitle(this.title)},computeTitle:function(){return this.formatRange({start:this.calendar.applyTimezone(this.intervalStart),end:this.calendar.applyTimezone(this.intervalEnd)},this.opt("titleFormat")||this.computeTitleFormat(),this.opt("titleRangeSeparator"))},computeTitleFormat:function(){return"year"==this.intervalUnit?"YYYY":"month"==this.intervalUnit?this.opt("monthYearFormat"):this.intervalDuration.as("days")>1?"ll":"LL"},formatRange:function(t,e,n){var i=t.end;return i.hasTime()||(i=i.clone().subtract(1)),gt(t.start,i,e,n,this.opt("isRTL"))},getAllDayHtml:function(){return this.opt("allDayHtml")||tt(this.opt("allDayText"))},buildGotoAnchorHtml:function(e,n,i){var r,s,o,l;return t.isPlainObject(e)?(r=e.date,s=e.type,o=e.forceOff):r=e,r=qt.moment(r),l={date:r.format("YYYY-MM-DD"),type:s||"day"},"string"==typeof n&&(i=n,n=null),n=n?" "+it(n):"",i=i||"",!o&&this.opt("navLinks")?"<a"+n+' data-goto="'+tt(JSON.stringify(l))+'">'+i+"</a>":"<span"+n+">"+i+"</span>"},setElement:function(t){this.el=t,this.bindGlobalHandlers(),this.renderSkeleton()},removeElement:function(){this.unsetDate(),this.unrenderSkeleton(),this.unbindGlobalHandlers(),this.el.remove()},renderSkeleton:function(){},unrenderSkeleton:function(){},setDate:function(t){var e=this.isDateSet;this.isDateSet=!0,this.handleDate(t,e),this.trigger(e?"dateReset":"dateSet",t)},unsetDate:function(){this.isDateSet&&(this.isDateSet=!1,this.handleDateUnset(),this.trigger("dateUnset"))},handleDate:function(t,e){var n=this;this.unbindEvents(),this.requestDateRender(t).then(function(){n.bindEvents()})},handleDateUnset:function(){this.unbindEvents(),this.requestDateUnrender()},requestDateRender:function(t){var e=this;return this.dateRenderQueue.add(function(){return e.executeDateRender(t)})},requestDateUnrender:function(){var t=this;return this.dateRenderQueue.add(function(){return t.executeDateUnrender()})},executeDateRender:function(t){var e=this;return t?this.captureInitialScroll():this.captureScroll(),this.freezeHeight(),this.executeDateUnrender().then(function(){t&&e.setRange(e.computeRange(t)),e.render&&e.render(),e.renderDates(),e.updateSize(),e.renderBusinessHours(),e.startNowIndicator(),e.thawHeight(),e.releaseScroll(),e.isDateRendered=!0,e.onDateRender(),e.trigger("dateRender")})},executeDateUnrender:function(){var t=this;return t.isDateRendered?this.requestEventsUnrender().then(function(){t.unselect(),t.stopNowIndicator(),t.triggerUnrender(),t.unrenderBusinessHours(),t.unrenderDates(),t.destroy&&t.destroy(),t.isDateRendered=!1,t.trigger("dateUnrender")}):bt.resolve()},onDateRender:function(){this.triggerRender()},renderDates:function(){},unrenderDates:function(){},triggerRender:function(){this.publiclyTrigger("viewRender",this,this,this.el);
-},triggerUnrender:function(){this.publiclyTrigger("viewDestroy",this,this,this.el)},bindGlobalHandlers:function(){this.listenTo(t(document),"mousedown",this.handleDocumentMousedown),this.listenTo(t(document),"touchstart",this.processUnselect)},unbindGlobalHandlers:function(){this.stopListeningTo(t(document))},initThemingProps:function(){var t=this.opt("theme")?"ui":"fc";this.widgetHeaderClass=t+"-widget-header",this.widgetContentClass=t+"-widget-content",this.highlightStateClass=t+"-state-highlight"},renderBusinessHours:function(){},unrenderBusinessHours:function(){},startNowIndicator:function(){var t,n,i,r=this;this.opt("nowIndicator")&&(t=this.getNowIndicatorUnit(),t&&(n=lt(this,"updateNowIndicator"),this.initialNowDate=this.calendar.getNow(),this.initialNowQueriedMs=+new Date,this.renderNowIndicator(this.initialNowDate),this.isNowIndicatorRendered=!0,i=this.initialNowDate.clone().startOf(t).add(1,t)-this.initialNowDate,this.nowIndicatorTimeoutID=setTimeout(function(){r.nowIndicatorTimeoutID=null,n(),i=+e.duration(1,t),i=Math.max(100,i),r.nowIndicatorIntervalID=setInterval(n,i)},i)))},updateNowIndicator:function(){this.isNowIndicatorRendered&&(this.unrenderNowIndicator(),this.renderNowIndicator(this.initialNowDate.clone().add(new Date-this.initialNowQueriedMs)))},stopNowIndicator:function(){this.isNowIndicatorRendered&&(this.nowIndicatorTimeoutID&&(clearTimeout(this.nowIndicatorTimeoutID),this.nowIndicatorTimeoutID=null),this.nowIndicatorIntervalID&&(clearTimeout(this.nowIndicatorIntervalID),this.nowIndicatorIntervalID=null),this.unrenderNowIndicator(),this.isNowIndicatorRendered=!1)},getNowIndicatorUnit:function(){},renderNowIndicator:function(t){},unrenderNowIndicator:function(){},updateSize:function(t){t&&this.captureScroll(),this.updateHeight(t),this.updateWidth(t),this.updateNowIndicator(),t&&this.releaseScroll()},updateWidth:function(t){},updateHeight:function(t){var e=this.calendar;this.setHeight(e.getSuggestedViewHeight(),e.isHeightAuto())},setHeight:function(t,e){},capturedScroll:null,capturedScrollDepth:0,captureScroll:function(){return!this.capturedScrollDepth++&&(this.capturedScroll=this.isDateRendered?this.queryScroll():{},!0)},captureInitialScroll:function(e){this.captureScroll()&&(this.capturedScroll.isInitial=!0,e?t.extend(this.capturedScroll,e):this.capturedScroll.isComputed=!0)},releaseScroll:function(){var e=this.capturedScroll,n=this.discardScroll();e.isComputed&&(n?t.extend(e,this.computeInitialScroll()):e=null),e&&(e.isInitial?this.hardSetScroll(e):this.setScroll(e))},discardScroll:function(){return!--this.capturedScrollDepth&&(this.capturedScroll=null,!0)},computeInitialScroll:function(){return{}},queryScroll:function(){return{}},hardSetScroll:function(t){var e=this,n=function(){e.setScroll(t)};n(),setTimeout(n,0)},setScroll:function(t){},freezeHeight:function(){this.calendar.freezeContentHeight()},thawHeight:function(){this.calendar.thawContentHeight()},bindEvents:function(){var t=this;this.isEventsBound||(this.isEventsBound=!0,this.rejectOn("eventsUnbind",this.requestEvents()).then(function(e){t.listenTo(t.calendar,"eventsReset",t.setEvents),t.setEvents(e)}))},unbindEvents:function(){this.isEventsBound&&(this.isEventsBound=!1,this.stopListeningTo(this.calendar,"eventsReset"),this.unsetEvents(),this.trigger("eventsUnbind"))},setEvents:function(t){var e=this.isEventSet;this.isEventsSet=!0,this.handleEvents(t,e),this.trigger(e?"eventsReset":"eventsSet",t)},unsetEvents:function(){this.isEventsSet&&(this.isEventsSet=!1,this.handleEventsUnset(),this.trigger("eventsUnset"))},whenEventsSet:function(){var t=this;return this.isEventsSet?bt.resolve(this.getCurrentEvents()):new bt(function(e){t.one("eventsSet",e)})},handleEvents:function(t,e){this.requestEventsRender(t)},handleEventsUnset:function(){this.requestEventsUnrender()},requestEventsRender:function(t){var e=this;return this.eventRenderQueue.add(function(){return e.executeEventsRender(t)})},requestEventsUnrender:function(){var t=this;return this.isEventsRendered?this.eventRenderQueue.addQuickly(function(){return t.executeEventsUnrender()}):bt.resolve()},requestCurrentEventsRender:function(){return this.isEventsSet?void this.requestEventsRender(this.getCurrentEvents()):bt.reject()},executeEventsRender:function(t){var e=this;return this.captureScroll(),this.freezeHeight(),this.executeEventsUnrender().then(function(){e.renderEvents(t),e.thawHeight(),e.releaseScroll(),e.isEventsRendered=!0,e.onEventsRender(),e.trigger("eventsRender")})},executeEventsUnrender:function(){return this.isEventsRendered&&(this.onBeforeEventsUnrender(),this.captureScroll(),this.freezeHeight(),this.destroyEvents&&this.destroyEvents(),this.unrenderEvents(),this.thawHeight(),this.releaseScroll(),this.isEventsRendered=!1,this.trigger("eventsUnrender")),bt.resolve()},onEventsRender:function(){this.renderedEventSegEach(function(t){this.publiclyTrigger("eventAfterRender",t.event,t.event,t.el)}),this.publiclyTrigger("eventAfterAllRender")},onBeforeEventsUnrender:function(){this.renderedEventSegEach(function(t){this.publiclyTrigger("eventDestroy",t.event,t.event,t.el)})},renderEvents:function(t){},unrenderEvents:function(){},requestEvents:function(){return this.calendar.requestEvents(this.start,this.end)},getCurrentEvents:function(){return this.calendar.getPrunedEventCache()},resolveEventEl:function(e,n){var i=this.publiclyTrigger("eventRender",e,e,n);return i===!1?n=null:i&&i!==!0&&(n=t(i)),n},showEvent:function(t){this.renderedEventSegEach(function(t){t.el.css("visibility","")},t)},hideEvent:function(t){this.renderedEventSegEach(function(t){t.el.css("visibility","hidden")},t)},renderedEventSegEach:function(t,e){var n,i=this.getEventSegs();for(n=0;n<i.length;n++)e&&i[n].event._id!==e._id||i[n].el&&t.call(this,i[n])},getEventSegs:function(){return[]},isEventDraggable:function(t){return this.isEventStartEditable(t)},isEventStartEditable:function(t){return J(t.startEditable,(t.source||{}).startEditable,this.opt("eventStartEditable"),this.isEventGenerallyEditable(t))},isEventGenerallyEditable:function(t){return J(t.editable,(t.source||{}).editable,this.opt("editable"))},reportEventDrop:function(t,e,n,i,r){var s=this.calendar,o=s.mutateEvent(t,e,n),l=function(){o.undo(),s.reportEventChange()};this.triggerEventDrop(t,o.dateDelta,l,i,r),s.reportEventChange()},triggerEventDrop:function(t,e,n,i,r){this.publiclyTrigger("eventDrop",i[0],t,e,n,r,{})},reportExternalDrop:function(e,n,i,r,s){var o,l,a=e.eventProps;a&&(o=t.extend({},a,n),l=this.calendar.renderEvent(o,e.stick)[0]),this.triggerExternalDrop(l,n,i,r,s)},triggerExternalDrop:function(t,e,n,i,r){this.publiclyTrigger("drop",n[0],e.start,i,r),t&&this.publiclyTrigger("eventReceive",null,t)},renderDrag:function(t,e){},unrenderDrag:function(){},isEventResizableFromStart:function(t){return this.opt("eventResizableFromStart")&&this.isEventResizable(t)},isEventResizableFromEnd:function(t){return this.isEventResizable(t)},isEventResizable:function(t){var e=t.source||{};return J(t.durationEditable,e.durationEditable,this.opt("eventDurationEditable"),t.editable,e.editable,this.opt("editable"))},reportEventResize:function(t,e,n,i,r){var s=this.calendar,o=s.mutateEvent(t,e,n),l=function(){o.undo(),s.reportEventChange()};this.triggerEventResize(t,o.durationDelta,l,i,r),s.reportEventChange()},triggerEventResize:function(t,e,n,i,r){this.publiclyTrigger("eventResize",i[0],t,e,n,r,{})},select:function(t,e){this.unselect(e),this.renderSelection(t),this.reportSelection(t,e)},renderSelection:function(t){},reportSelection:function(t,e){this.isSelected=!0,this.triggerSelect(t,e)},triggerSelect:function(t,e){this.publiclyTrigger("select",null,this.calendar.applyTimezone(t.start),this.calendar.applyTimezone(t.end),e)},unselect:function(t){this.isSelected&&(this.isSelected=!1,this.destroySelection&&this.destroySelection(),this.unrenderSelection(),this.publiclyTrigger("unselect",null,t))},unrenderSelection:function(){},selectEvent:function(t){this.selectedEvent&&this.selectedEvent===t||(this.unselectEvent(),this.renderedEventSegEach(function(t){t.el.addClass("fc-selected")},t),this.selectedEvent=t)},unselectEvent:function(){this.selectedEvent&&(this.renderedEventSegEach(function(t){t.el.removeClass("fc-selected")},this.selectedEvent),this.selectedEvent=null)},isEventSelected:function(t){return this.selectedEvent&&this.selectedEvent._id===t._id},handleDocumentMousedown:function(t){S(t)&&this.processUnselect(t)},processUnselect:function(t){this.processRangeUnselect(t),this.processEventUnselect(t)},processRangeUnselect:function(e){var n;this.isSelected&&this.opt("unselectAuto")&&(n=this.opt("unselectCancel"),n&&t(e.target).closest(n).length||this.unselect(e))},processEventUnselect:function(e){this.selectedEvent&&(t(e.target).closest(".fc-selected").length||this.unselectEvent())},triggerDayClick:function(t,e,n){this.publiclyTrigger("dayClick",e,this.calendar.applyTimezone(t.start),n)},initHiddenDays:function(){var e,n=this.opt("hiddenDays")||[],i=[],r=0;for(this.opt("weekends")===!1&&n.push(0,6),e=0;e<7;e++)(i[e]=t.inArray(e,n)!==-1)||r++;if(!r)throw"invalid hiddenDays";this.isHiddenDayHash=i},isHiddenDay:function(t){return e.isMoment(t)&&(t=t.day()),this.isHiddenDayHash[t]},skipHiddenDays:function(t,e,n){var i=t.clone();for(e=e||1;this.isHiddenDayHash[(i.day()+(n?e:0)+7)%7];)i.add(e,"days");return i},computeDayRange:function(t){var e,n=t.start.clone().stripTime(),i=t.end,r=null;return i&&(r=i.clone().stripTime(),e=+i.time(),e&&e>=this.nextDayThreshold&&r.add(1,"days")),(!i||r<=n)&&(r=n.clone().add(1,"days")),{start:n,end:r}},isMultiDayEvent:function(t){var e=this.computeDayRange(t);return e.end.diff(e.start,"days")>1}}),be=qt.Scroller=St.extend({el:null,scrollEl:null,overflowX:null,overflowY:null,constructor:function(t){t=t||{},this.overflowX=t.overflowX||t.overflow||"auto",this.overflowY=t.overflowY||t.overflow||"auto"},render:function(){this.el=this.renderEl(),this.applyOverflow()},renderEl:function(){return this.scrollEl=t('<div class="fc-scroller"></div>')},clear:function(){this.setHeight("auto"),this.applyOverflow()},destroy:function(){this.el.remove()},applyOverflow:function(){this.scrollEl.css({"overflow-x":this.overflowX,"overflow-y":this.overflowY})},lockOverflow:function(t){var e=this.overflowX,n=this.overflowY;t=t||this.getScrollbarWidths(),"auto"===e&&(e=t.top||t.bottom||this.scrollEl[0].scrollWidth-1>this.scrollEl[0].clientWidth?"scroll":"hidden"),"auto"===n&&(n=t.left||t.right||this.scrollEl[0].scrollHeight-1>this.scrollEl[0].clientHeight?"scroll":"hidden"),this.scrollEl.css({"overflow-x":e,"overflow-y":n})},setHeight:function(t){this.scrollEl.height(t)},getScrollTop:function(){return this.scrollEl.scrollTop()},setScrollTop:function(t){this.scrollEl.scrollTop(t)},getClientWidth:function(){return this.scrollEl[0].clientWidth},getClientHeight:function(){return this.scrollEl[0].clientHeight},getScrollbarWidths:function(){return p(this.scrollEl)}});Vt.prototype.proxyCall=function(t){var e=Array.prototype.slice.call(arguments,1),n=[];return this.items.forEach(function(i){n.push(i[t].apply(i,e))}),n};var De=qt.Calendar=St.extend({dirDefaults:null,localeDefaults:null,overrides:null,dynamicOverrides:null,options:null,viewSpecCache:null,view:null,header:null,footer:null,loadingLevel:0,constructor:_t,initialize:function(){},populateOptionsHash:function(){var t,e,i,r;t=J(this.dynamicOverrides.locale,this.overrides.locale),e=Te[t],e||(t=De.defaults.locale,e=Te[t]||{}),i=J(this.dynamicOverrides.isRTL,this.overrides.isRTL,e.isRTL,De.defaults.isRTL),r=i?De.rtlDefaults:{},this.dirDefaults=r,this.localeDefaults=e,this.options=n([De.defaults,r,e,this.overrides,this.dynamicOverrides]),Yt(this.options)},getViewSpec:function(t){var e=this.viewSpecCache;return e[t]||(e[t]=this.buildViewSpec(t))},getUnitViewSpec:function(e){var n,i,r;if(t.inArray(e,Kt)!=-1)for(n=this.header.getViewsWithButtons(),t.each(qt.views,function(t){n.push(t)}),i=0;i<n.length;i++)if(r=this.getViewSpec(n[i]),r&&r.singleUnit==e)return r},buildViewSpec:function(t){for(var i,r,s,o,l=this.overrides.views||{},a=[],u=[],c=[],d=t;d;)i=Zt[d],r=l[d],d=null,"function"==typeof i&&(i={class:i}),i&&(a.unshift(i),u.unshift(i.defaults||{}),s=s||i.duration,d=d||i.type),r&&(c.unshift(r),s=s||r.duration,d=d||r.type);return i=q(a),i.type=t,!!i.class&&(s&&(s=e.duration(s),s.valueOf()&&(i.duration=s,o=A(s),1===s.as(o)&&(i.singleUnit=o,c.unshift(l[o]||{})))),i.defaults=n(u),i.overrides=n(c),this.buildViewSpecOptions(i),this.buildViewSpecButtonText(i,t),i)},buildViewSpecOptions:function(t){t.options=n([De.defaults,t.defaults,this.dirDefaults,this.localeDefaults,this.overrides,t.overrides,this.dynamicOverrides]),Yt(t.options)},buildViewSpecButtonText:function(t,e){function n(n){var i=n.buttonText||{};return i[e]||(t.buttonTextKey?i[t.buttonTextKey]:null)||(t.singleUnit?i[t.singleUnit]:null)}t.buttonTextOverride=n(this.dynamicOverrides)||n(this.overrides)||t.overrides.buttonText,t.buttonTextDefault=n(this.localeDefaults)||n(this.dirDefaults)||t.defaults.buttonText||n(De.defaults)||(t.duration?this.humanizeDuration(t.duration):null)||e},instantiateView:function(t){var e=this.getViewSpec(t);return new e.class(this,t,e.options,e.duration)},isValidViewType:function(t){return Boolean(this.getViewSpec(t))},pushLoading:function(){this.loadingLevel++||this.publiclyTrigger("loading",null,!0,this.view)},popLoading:function(){--this.loadingLevel||this.publiclyTrigger("loading",null,!1,this.view)},buildSelectSpan:function(t,e){var n,i=this.moment(t).stripZone();return n=e?this.moment(e).stripZone():i.hasTime()?i.clone().add(this.defaultTimedEventDuration):i.clone().add(this.defaultAllDayEventDuration),{start:i,end:n}}});De.mixin(ue),De.mixin({optionHandlers:null,bindOption:function(t,e){this.bindOptions([t],e)},bindOptions:function(t,e){var n,i={func:e,names:t};for(n=0;n<t.length;n++)this.registerOptionHandlerObj(t[n],i);this.triggerOptionHandlerObj(i)},registerOptionHandlerObj:function(t,e){(this.optionHandlers[t]||(this.optionHandlers[t]=[])).push(e)},triggerOptionHandlers:function(t){var e,n=this.optionHandlers[t]||[];for(e=0;e<n.length;e++)this.triggerOptionHandlerObj(n[e])},triggerOptionHandlerObj:function(t){var e,n=t.names,i=[];for(e=0;e<n.length;e++)i.push(this.options[n[e]]);t.func.apply(this,i)}}),De.defaults={titleRangeSeparator:" – ",monthYearFormat:"MMMM YYYY",defaultTimedEventDuration:"02:00:00",defaultAllDayEventDuration:{days:1},forceEventDuration:!1,nextDayThreshold:"09:00:00",defaultView:"month",aspectRatio:1.35,header:{left:"title",center:"",right:"today prev,next"},weekends:!0,weekNumbers:!1,weekNumberTitle:"W",weekNumberCalculation:"local",scrollTime:"06:00:00",lazyFetching:!0,startParam:"start",endParam:"end",timezoneParam:"timezone",timezone:!1,isRTL:!1,buttonText:{prev:"prev",next:"next",prevYear:"prev year",nextYear:"next year",year:"year",today:"today",month:"month",week:"week",day:"day"},buttonIcons:{prev:"left-single-arrow",next:"right-single-arrow",prevYear:"left-double-arrow",nextYear:"right-double-arrow"},allDayText:"all-day",theme:!1,themeButtonIcons:{prev:"circle-triangle-w",next:"circle-triangle-e",prevYear:"seek-prev",nextYear:"seek-next"},dragOpacity:.75,dragRevertDuration:500,dragScroll:!0,unselectAuto:!0,dropAccept:"*",eventOrder:"title",eventLimit:!1,eventLimitText:"more",eventLimitClick:"popover",dayPopoverFormat:"LL",handleWindowResize:!0,windowResizeDelay:100,longPressDelay:1e3},De.englishDefaults={dayPopoverFormat:"dddd, MMMM D"},De.rtlDefaults={header:{left:"next,prev today",center:"",right:"title"},buttonIcons:{prev:"right-single-arrow",next:"left-single-arrow",prevYear:"right-double-arrow",nextYear:"left-double-arrow"},themeButtonIcons:{prev:"circle-triangle-e",next:"circle-triangle-w",nextYear:"seek-prev",prevYear:"seek-next"}};var Te=qt.locales={};qt.datepickerLocale=function(e,n,i){var r=Te[e]||(Te[e]={});r.isRTL=i.isRTL,r.weekNumberTitle=i.weekHeader,t.each(Ce,function(t,e){r[t]=e(i)}),t.datepicker&&(t.datepicker.regional[n]=t.datepicker.regional[e]=i,t.datepicker.regional.en=t.datepicker.regional[""],t.datepicker.setDefaults(i))},qt.locale=function(e,i){var r,s;r=Te[e]||(Te[e]={}),i&&(r=Te[e]=n([r,i])),s=Wt(e),t.each(He,function(t,e){null==r[t]&&(r[t]=e(s,r))}),De.defaults.locale=e};var Ce={buttonText:function(t){return{prev:et(t.prevText),next:et(t.nextText),today:et(t.currentText)}},monthYearFormat:function(t){return t.showMonthAfterYear?"YYYY["+t.yearSuffix+"] MMMM":"MMMM YYYY["+t.yearSuffix+"]"}},He={dayOfMonthFormat:function(t,e){var n=t.longDateFormat("l");return n=n.replace(/^Y+[^\w\s]*|[^\w\s]*Y+$/g,""),e.isRTL?n+=" ddd":n="ddd "+n,n},mediumTimeFormat:function(t){return t.longDateFormat("LT").replace(/\s*a$/i,"a")},smallTimeFormat:function(t){return t.longDateFormat("LT").replace(":mm","(:mm)").replace(/(\Wmm)$/,"($1)").replace(/\s*a$/i,"a")},extraSmallTimeFormat:function(t){return t.longDateFormat("LT").replace(":mm","(:mm)").replace(/(\Wmm)$/,"($1)").replace(/\s*a$/i,"t")},hourFormat:function(t){return t.longDateFormat("LT").replace(":mm","").replace(/(\Wmm)$/,"").replace(/\s*a$/i,"a")},noMeridiemTimeFormat:function(t){return t.longDateFormat("LT").replace(/\s*a$/i,"")}},Re={smallDayDateFormat:function(t){return t.isRTL?"D dd":"dd D"},weekFormat:function(t){return t.isRTL?"w[ "+t.weekNumberTitle+"]":"["+t.weekNumberTitle+" ]w"},smallWeekFormat:function(t){return t.isRTL?"w["+t.weekNumberTitle+"]":"["+t.weekNumberTitle+"]w"}};qt.locale("en",De.englishDefaults),qt.sourceNormalizers=[],qt.sourceFetchers=[];var xe={dataType:"json",cache:!1},Ie=1;De.prototype.normalizeEvent=function(t){},De.prototype.spanContainsSpan=function(t,e){var n=t.start.clone().stripZone(),i=this.getEventEnd(t).stripZone();return e.start>=n&&e.end<=i},De.prototype.getPeerEvents=function(t,e){var n,i,r=this.getEventCache(),s=[];for(n=0;n<r.length;n++)i=r[n],e&&e._id===i._id||s.push(i);return s},De.prototype.isEventSpanAllowed=function(t,e){var n=e.source||{},i=J(e.constraint,n.constraint,this.options.eventConstraint),r=J(e.overlap,n.overlap,this.options.eventOverlap);return this.isSpanAllowed(t,i,r,e)&&(!this.options.eventAllow||this.options.eventAllow(t,e)!==!1)},De.prototype.isExternalSpanAllowed=function(e,n,i){var r,s;return i&&(r=t.extend({},i,n),s=this.expandEvent(this.buildEventFromInput(r))[0]),s?this.isEventSpanAllowed(e,s):this.isSelectionSpanAllowed(e)},De.prototype.isSelectionSpanAllowed=function(t){return this.isSpanAllowed(t,this.options.selectConstraint,this.options.selectOverlap)&&(!this.options.selectAllow||this.options.selectAllow(t)!==!1)},De.prototype.isSpanAllowed=function(t,e,n,i){var r,s,o,l,a,u;if(null!=e&&(r=this.constraintToEvents(e))){for(s=!1,l=0;l<r.length;l++)if(this.spanContainsSpan(r[l],t)){s=!0;break}if(!s)return!1}for(o=this.getPeerEvents(t,i),l=0;l<o.length;l++)if(a=o[l],this.eventIntersectsRange(a,t)){if(n===!1)return!1;if("function"==typeof n&&!n(a,i))return!1;if(i){if(u=J(a.overlap,(a.source||{}).overlap),u===!1)return!1;if("function"==typeof u&&!u(i,a))return!1}}return!0},De.prototype.constraintToEvents=function(t){return"businessHours"===t?this.getCurrentBusinessHourEvents():"object"==typeof t?null!=t.start?this.expandEvent(this.buildEventFromInput(t)):null:this.clientEvents(t)},De.prototype.eventIntersectsRange=function(t,e){var n=t.start.clone().stripZone(),i=this.getEventEnd(t).stripZone();return e.start<i&&e.end>n};var ke={id:"_fcBusinessHours",start:"09:00",end:"17:00",dow:[1,2,3,4,5],rendering:"inverse-background"};De.prototype.getCurrentBusinessHourEvents=function(t){return this.computeBusinessHourEvents(t,this.options.businessHours)},De.prototype.computeBusinessHourEvents=function(e,n){return n===!0?this.expandBusinessHourEvents(e,[{}]):t.isPlainObject(n)?this.expandBusinessHourEvents(e,[n]):t.isArray(n)?this.expandBusinessHourEvents(e,n,!0):[]},De.prototype.expandBusinessHourEvents=function(e,n,i){var r,s,o=this.getView(),l=[];for(r=0;r<n.length;r++)s=n[r],i&&!s.dow||(s=t.extend({},ke,s),e&&(s.start=null,s.end=null),l.push.apply(l,this.expandEvent(this.buildEventFromInput(s),o.start,o.end)));return l};var Le=qt.BasicView=Ee.extend({scroller:null,dayGridClass:Se,dayGrid:null,dayNumbersVisible:!1,colWeekNumbersVisible:!1,cellWeekNumbersVisible:!1,weekNumberWidth:null,headContainerEl:null,headRowEl:null,initialize:function(){this.dayGrid=this.instantiateDayGrid(),this.scroller=new be({overflowX:"hidden",overflowY:"auto"})},instantiateDayGrid:function(){var t=this.dayGridClass.extend(Me);return new t(this)},setRange:function(t){Ee.prototype.setRange.call(this,t),this.dayGrid.breakOnWeeks=/year|month|week/.test(this.intervalUnit),this.dayGrid.setRange(t)},computeRange:function(t){var e=Ee.prototype.computeRange.call(this,t);return/year|month/.test(e.intervalUnit)&&(e.start.startOf("week"),e.start=this.skipHiddenDays(e.start),e.end.weekday()&&(e.end.add(1,"week").startOf("week"),e.end=this.skipHiddenDays(e.end,-1,!0))),e},renderDates:function(){this.dayNumbersVisible=this.dayGrid.rowCnt>1,this.opt("weekNumbers")&&(this.opt("weekNumbersWithinDays")?(this.cellWeekNumbersVisible=!0,this.colWeekNumbersVisible=!1):(this.cellWeekNumbersVisible=!1,this.colWeekNumbersVisible=!0)),this.dayGrid.numbersVisible=this.dayNumbersVisible||this.cellWeekNumbersVisible||this.colWeekNumbersVisible,this.el.addClass("fc-basic-view").html(this.renderSkeletonHtml()),this.renderHead(),this.scroller.render();var e=this.scroller.el.addClass("fc-day-grid-container"),n=t('<div class="fc-day-grid" />').appendTo(e);this.el.find(".fc-body > tr > td").append(e),this.dayGrid.setElement(n),this.dayGrid.renderDates(this.hasRigidRows())},renderHead:function(){this.headContainerEl=this.el.find(".fc-head-container").html(this.dayGrid.renderHeadHtml()),this.headRowEl=this.headContainerEl.find(".fc-row")},unrenderDates:function(){this.dayGrid.unrenderDates(),this.dayGrid.removeElement(),this.scroller.destroy()},renderBusinessHours:function(){this.dayGrid.renderBusinessHours()},unrenderBusinessHours:function(){this.dayGrid.unrenderBusinessHours()},renderSkeletonHtml:function(){return'<table><thead class="fc-head"><tr><td class="fc-head-container '+this.widgetHeaderClass+'"></td></tr></thead><tbody class="fc-body"><tr><td class="'+this.widgetContentClass+'"></td></tr></tbody></table>'},weekNumberStyleAttr:function(){return null!==this.weekNumberWidth?'style="width:'+this.weekNumberWidth+'px"':""},hasRigidRows:function(){var t=this.opt("eventLimit");return t&&"number"!=typeof t},updateWidth:function(){this.colWeekNumbersVisible&&(this.weekNumberWidth=u(this.el.find(".fc-week-number")))},setHeight:function(t,e){var n,s,o=this.opt("eventLimit");this.scroller.clear(),r(this.headRowEl),this.dayGrid.removeSegPopover(),o&&"number"==typeof o&&this.dayGrid.limitRows(o),n=this.computeScrollerHeight(t),this.setGridHeight(n,e),o&&"number"!=typeof o&&this.dayGrid.limitRows(o),e||(this.scroller.setHeight(n),s=this.scroller.getScrollbarWidths(),(s.left||s.right)&&(i(this.headRowEl,s),n=this.computeScrollerHeight(t),this.scroller.setHeight(n)),this.scroller.lockOverflow(s))},computeScrollerHeight:function(t){return t-c(this.el,this.scroller.el)},setGridHeight:function(t,e){e?a(this.dayGrid.rowEls):l(this.dayGrid.rowEls,t,!0)},computeInitialScroll:function(){return{top:0}},queryScroll:function(){return{top:this.scroller.getScrollTop()}},setScroll:function(t){this.scroller.setScrollTop(t.top)},prepareHits:function(){this.dayGrid.prepareHits()},releaseHits:function(){this.dayGrid.releaseHits()},queryHit:function(t,e){return this.dayGrid.queryHit(t,e)},getHitSpan:function(t){return this.dayGrid.getHitSpan(t)},getHitEl:function(t){return this.dayGrid.getHitEl(t)},renderEvents:function(t){this.dayGrid.renderEvents(t),this.updateHeight()},getEventSegs:function(){return this.dayGrid.getEventSegs()},unrenderEvents:function(){this.dayGrid.unrenderEvents()},renderDrag:function(t,e){return this.dayGrid.renderDrag(t,e)},unrenderDrag:function(){this.dayGrid.unrenderDrag()},renderSelection:function(t){this.dayGrid.renderSelection(t)},unrenderSelection:function(){this.dayGrid.unrenderSelection()}}),Me={renderHeadIntroHtml:function(){var t=this.view;return t.colWeekNumbersVisible?'<th class="fc-week-number '+t.widgetHeaderClass+'" '+t.weekNumberStyleAttr()+"><span>"+tt(t.opt("weekNumberTitle"))+"</span></th>":""},renderNumberIntroHtml:function(t){var e=this.view,n=this.getCellDate(t,0);return e.colWeekNumbersVisible?'<td class="fc-week-number" '+e.weekNumberStyleAttr()+">"+e.buildGotoAnchorHtml({date:n,type:"week",forceOff:1===this.colCnt},n.format("w"))+"</td>":""},renderBgIntroHtml:function(){var t=this.view;return t.colWeekNumbersVisible?'<td class="fc-week-number '+t.widgetContentClass+'" '+t.weekNumberStyleAttr()+"></td>":""},renderIntroHtml:function(){var t=this.view;return t.colWeekNumbersVisible?'<td class="fc-week-number" '+t.weekNumberStyleAttr()+"></td>":""}},Be=qt.MonthView=Le.extend({computeRange:function(t){var e,n=Le.prototype.computeRange.call(this,t);return this.isFixedWeeks()&&(e=Math.ceil(n.end.diff(n.start,"weeks",!0)),n.end.add(6-e,"weeks")),n},setGridHeight:function(t,e){e&&(t*=this.rowCnt/6),l(this.dayGrid.rowEls,t,!e)},isFixedWeeks:function(){return this.opt("fixedWeekCount")}});Zt.basic={class:Le},Zt.basicDay={type:"basic",duration:{days:1}},Zt.basicWeek={type:"basic",duration:{weeks:1}},Zt.month={class:Be,duration:{months:1},defaults:{fixedWeekCount:!0}};var ze=qt.AgendaView=Ee.extend({scroller:null,timeGridClass:we,timeGrid:null,dayGridClass:Se,dayGrid:null,axisWidth:null,headContainerEl:null,noScrollRowEls:null,bottomRuleEl:null,initialize:function(){this.timeGrid=this.instantiateTimeGrid(),this.opt("allDaySlot")&&(this.dayGrid=this.instantiateDayGrid()),this.scroller=new be({overflowX:"hidden",overflowY:"auto"})},instantiateTimeGrid:function(){var t=this.timeGridClass.extend(Fe);return new t(this)},instantiateDayGrid:function(){var t=this.dayGridClass.extend(Ne);return new t(this)},setRange:function(t){Ee.prototype.setRange.call(this,t),this.timeGrid.setRange(t),this.dayGrid&&this.dayGrid.setRange(t)},renderDates:function(){this.el.addClass("fc-agenda-view").html(this.renderSkeletonHtml()),this.renderHead(),this.scroller.render();var e=this.scroller.el.addClass("fc-time-grid-container"),n=t('<div class="fc-time-grid" />').appendTo(e);this.el.find(".fc-body > tr > td").append(e),this.timeGrid.setElement(n),this.timeGrid.renderDates(),this.bottomRuleEl=t('<hr class="fc-divider '+this.widgetHeaderClass+'"/>').appendTo(this.timeGrid.el),this.dayGrid&&(this.dayGrid.setElement(this.el.find(".fc-day-grid")),this.dayGrid.renderDates(),this.dayGrid.bottomCoordPadding=this.dayGrid.el.next("hr").outerHeight()),this.noScrollRowEls=this.el.find(".fc-row:not(.fc-scroller *)")},renderHead:function(){this.headContainerEl=this.el.find(".fc-head-container").html(this.timeGrid.renderHeadHtml())},unrenderDates:function(){this.timeGrid.unrenderDates(),this.timeGrid.removeElement(),this.dayGrid&&(this.dayGrid.unrenderDates(),this.dayGrid.removeElement()),this.scroller.destroy()},renderSkeletonHtml:function(){return'<table><thead class="fc-head"><tr><td class="fc-head-container '+this.widgetHeaderClass+'"></td></tr></thead><tbody class="fc-body"><tr><td class="'+this.widgetContentClass+'">'+(this.dayGrid?'<div class="fc-day-grid"/><hr class="fc-divider '+this.widgetHeaderClass+'"/>':"")+"</td></tr></tbody></table>"},axisStyleAttr:function(){return null!==this.axisWidth?'style="width:'+this.axisWidth+'px"':""},renderBusinessHours:function(){this.timeGrid.renderBusinessHours(),this.dayGrid&&this.dayGrid.renderBusinessHours()},unrenderBusinessHours:function(){this.timeGrid.unrenderBusinessHours(),this.dayGrid&&this.dayGrid.unrenderBusinessHours()},getNowIndicatorUnit:function(){return this.timeGrid.getNowIndicatorUnit()},renderNowIndicator:function(t){this.timeGrid.renderNowIndicator(t)},unrenderNowIndicator:function(){this.timeGrid.unrenderNowIndicator()},updateSize:function(t){this.timeGrid.updateSize(t),Ee.prototype.updateSize.call(this,t)},updateWidth:function(){this.axisWidth=u(this.el.find(".fc-axis"))},setHeight:function(t,e){var n,s,o;this.bottomRuleEl.hide(),this.scroller.clear(),r(this.noScrollRowEls),this.dayGrid&&(this.dayGrid.removeSegPopover(),n=this.opt("eventLimit"),n&&"number"!=typeof n&&(n=Ge),n&&this.dayGrid.limitRows(n)),e||(s=this.computeScrollerHeight(t),this.scroller.setHeight(s),o=this.scroller.getScrollbarWidths(),(o.left||o.right)&&(i(this.noScrollRowEls,o),s=this.computeScrollerHeight(t),this.scroller.setHeight(s)),this.scroller.lockOverflow(o),this.timeGrid.getTotalSlatHeight()<s&&this.bottomRuleEl.show())},computeScrollerHeight:function(t){return t-c(this.el,this.scroller.el)},computeInitialScroll:function(){var t=e.duration(this.opt("scrollTime")),n=this.timeGrid.computeTimeTop(t);return n=Math.ceil(n),n&&n++,{top:n}},queryScroll:function(){return{top:this.scroller.getScrollTop()}},setScroll:function(t){this.scroller.setScrollTop(t.top)},prepareHits:function(){this.timeGrid.prepareHits(),this.dayGrid&&this.dayGrid.prepareHits()},releaseHits:function(){this.timeGrid.releaseHits(),this.dayGrid&&this.dayGrid.releaseHits()},queryHit:function(t,e){var n=this.timeGrid.queryHit(t,e);return!n&&this.dayGrid&&(n=this.dayGrid.queryHit(t,e)),n},getHitSpan:function(t){return t.component.getHitSpan(t)},getHitEl:function(t){return t.component.getHitEl(t)},renderEvents:function(t){var e,n,i=[],r=[],s=[];for(n=0;n<t.length;n++)t[n].allDay?i.push(t[n]):r.push(t[n]);e=this.timeGrid.renderEvents(r),this.dayGrid&&(s=this.dayGrid.renderEvents(i)),this.updateHeight()},getEventSegs:function(){return this.timeGrid.getEventSegs().concat(this.dayGrid?this.dayGrid.getEventSegs():[])},unrenderEvents:function(){this.timeGrid.unrenderEvents(),this.dayGrid&&this.dayGrid.unrenderEvents()},renderDrag:function(t,e){return t.start.hasTime()?this.timeGrid.renderDrag(t,e):this.dayGrid?this.dayGrid.renderDrag(t,e):void 0},unrenderDrag:function(){this.timeGrid.unrenderDrag(),this.dayGrid&&this.dayGrid.unrenderDrag()},renderSelection:function(t){t.start.hasTime()||t.end.hasTime()?this.timeGrid.renderSelection(t):this.dayGrid&&this.dayGrid.renderSelection(t)},unrenderSelection:function(){this.timeGrid.unrenderSelection(),this.dayGrid&&this.dayGrid.unrenderSelection()}}),Fe={renderHeadIntroHtml:function(){var t,e=this.view;return e.opt("weekNumbers")?(t=this.start.format(e.opt("smallWeekFormat")),'<th class="fc-axis fc-week-number '+e.widgetHeaderClass+'" '+e.axisStyleAttr()+">"+e.buildGotoAnchorHtml({date:this.start,type:"week",forceOff:this.colCnt>1},tt(t))+"</th>"):'<th class="fc-axis '+e.widgetHeaderClass+'" '+e.axisStyleAttr()+"></th>"},renderBgIntroHtml:function(){var t=this.view;return'<td class="fc-axis '+t.widgetContentClass+'" '+t.axisStyleAttr()+"></td>"},renderIntroHtml:function(){var t=this.view;return'<td class="fc-axis" '+t.axisStyleAttr()+"></td>"}},Ne={renderBgIntroHtml:function(){var t=this.view;return'<td class="fc-axis '+t.widgetContentClass+'" '+t.axisStyleAttr()+"><span>"+t.getAllDayHtml()+"</span></td>"},renderIntroHtml:function(){var t=this.view;return'<td class="fc-axis" '+t.axisStyleAttr()+"></td>"}},Ge=5,Oe=[{hours:1},{minutes:30},{minutes:15},{seconds:30},{seconds:15}];Zt.agenda={class:ze,defaults:{allDaySlot:!0,slotDuration:"00:30:00",minTime:"00:00:00",maxTime:"24:00:00",slotEventOverlap:!0}},Zt.agendaDay={type:"agenda",duration:{days:1}},Zt.agendaWeek={type:"agenda",duration:{weeks:1}};var Ae=Ee.extend({grid:null,scroller:null,initialize:function(){this.grid=new Ve(this),this.scroller=new be({overflowX:"hidden",overflowY:"auto"})},setRange:function(t){Ee.prototype.setRange.call(this,t),this.grid.setRange(t)},renderSkeleton:function(){this.el.addClass("fc-list-view "+this.widgetContentClass),this.scroller.render(),this.scroller.el.appendTo(this.el),this.grid.setElement(this.scroller.scrollEl)},unrenderSkeleton:function(){this.scroller.destroy()},setHeight:function(t,e){this.scroller.setHeight(this.computeScrollerHeight(t))},computeScrollerHeight:function(t){return t-c(this.el,this.scroller.el);
-},renderEvents:function(t){this.grid.renderEvents(t)},unrenderEvents:function(){this.grid.unrenderEvents()},isEventResizable:function(t){return!1},isEventDraggable:function(t){return!1}}),Ve=me.extend({segSelector:".fc-list-item",hasDayInteractions:!1,spanToSegs:function(t){for(var e,n=this.view,i=n.start.clone().time(0),r=0,s=[];i<n.end;)if(e=F(t,{start:i,end:i.clone().add(1,"day")}),e&&(e.dayIndex=r,s.push(e)),i.add(1,"day"),r++,e&&!e.isEnd&&t.end.hasTime()&&t.end<i.clone().add(this.view.nextDayThreshold)){e.end=t.end.clone(),e.isEnd=!0;break}return s},computeEventTimeFormat:function(){return this.view.opt("mediumTimeFormat")},handleSegClick:function(e,n){var i;me.prototype.handleSegClick.apply(this,arguments),t(n.target).closest("a[href]").length||(i=e.event.url,i&&!n.isDefaultPrevented()&&(window.location.href=i))},renderFgSegs:function(t){return t=this.renderFgSegEls(t),t.length?this.renderSegList(t):this.renderEmptyMessage(),t},renderEmptyMessage:function(){this.el.html('<div class="fc-list-empty-wrap2"><div class="fc-list-empty-wrap1"><div class="fc-list-empty">'+tt(this.view.opt("noEventsMessage"))+"</div></div></div>")},renderSegList:function(e){var n,i,r,s=this.groupSegsByDay(e),o=t('<table class="fc-list-table"><tbody/></table>'),l=o.find("tbody");for(n=0;n<s.length;n++)if(i=s[n])for(l.append(this.dayHeaderHtml(this.view.start.clone().add(n,"days"))),this.sortEventSegs(i),r=0;r<i.length;r++)l.append(i[r].el);this.el.empty().append(o)},groupSegsByDay:function(t){var e,n,i=[];for(e=0;e<t.length;e++)n=t[e],(i[n.dayIndex]||(i[n.dayIndex]=[])).push(n);return i},dayHeaderHtml:function(t){var e=this.view,n=e.opt("listDayFormat"),i=e.opt("listDayAltFormat");return'<tr class="fc-list-heading" data-date="'+t.format("YYYY-MM-DD")+'"><td class="'+e.widgetHeaderClass+'" colspan="3">'+(n?e.buildGotoAnchorHtml(t,{class:"fc-list-heading-main"},tt(t.format(n))):"")+(i?e.buildGotoAnchorHtml(t,{class:"fc-list-heading-alt"},tt(t.format(i))):"")+"</td></tr>"},fgSegHtml:function(t){var e,n=this.view,i=["fc-list-item"].concat(this.getSegCustomClasses(t)),r=this.getSegBackgroundColor(t),s=t.event,o=s.url;return e=s.allDay?n.getAllDayHtml():n.isMultiDayEvent(s)?t.isStart||t.isEnd?tt(this.getEventTimeText(t)):n.getAllDayHtml():tt(this.getEventTimeText(s)),o&&i.push("fc-has-url"),'<tr class="'+i.join(" ")+'">'+(this.displayEventTime?'<td class="fc-list-item-time '+n.widgetContentClass+'">'+(e||"")+"</td>":"")+'<td class="fc-list-item-marker '+n.widgetContentClass+'"><span class="fc-event-dot"'+(r?' style="background-color:'+r+'"':"")+'></span></td><td class="fc-list-item-title '+n.widgetContentClass+'"><a'+(o?' href="'+tt(o)+'"':"")+">"+tt(t.event.title||"")+"</a></td></tr>"}});return Zt.list={class:Ae,buttonTextKey:"list",defaults:{buttonText:"list",listDayFormat:"LL",noEventsMessage:"No events to display"}},Zt.listDay={type:"list",duration:{days:1},defaults:{listDayFormat:"dddd"}},Zt.listWeek={type:"list",duration:{weeks:1},defaults:{listDayFormat:"dddd",listDayAltFormat:"LL"}},Zt.listMonth={type:"list",duration:{month:1},defaults:{listDayAltFormat:"dddd"}},Zt.listYear={type:"list",duration:{year:1},defaults:{listDayAltFormat:"dddd"}},qt}); \ No newline at end of file
+!function(t){"function"==typeof define&&define.amd?define(["jquery","moment"],t):"object"==typeof exports?module.exports=t(require("jquery"),require("moment")):t(jQuery,moment)}(function(t,e){function n(t){return q(t,Vt)}function i(t,e){e.left&&t.css({"border-left-width":1,"margin-left":e.left-1}),e.right&&t.css({"border-right-width":1,"margin-right":e.right-1})}function r(t){t.css({"margin-left":"","margin-right":"","border-left-width":"","border-right-width":""})}function s(){t("body").addClass("fc-not-allowed")}function o(){t("body").removeClass("fc-not-allowed")}function l(e,n,i){var r=Math.floor(n/e.length),s=Math.floor(n-r*(e.length-1)),o=[],l=[],u=[],c=0;a(e),e.each(function(n,i){var a=n===e.length-1?s:r,d=t(i).outerHeight(!0);d<a?(o.push(i),l.push(d),u.push(t(i).height())):c+=d}),i&&(n-=c,r=Math.floor(n/o.length),s=Math.floor(n-r*(o.length-1))),t(o).each(function(e,n){var i=e===o.length-1?s:r,a=l[e],c=u[e],d=i-(a-c);a<i&&t(n).height(d)})}function a(t){t.height("")}function u(e){var n=0;return e.find("> *").each(function(e,i){var r=t(i).outerWidth();r>n&&(n=r)}),n++,e.width(n),n}function c(t,e){var n,i=t.add(e);return i.css({position:"relative",left:-1}),n=t.outerHeight()-e.outerHeight(),i.css({position:"",left:""}),n}function d(e){var n=e.css("position"),i=e.parents().filter(function(){var e=t(this);return/(auto|scroll)/.test(e.css("overflow")+e.css("overflow-y")+e.css("overflow-x"))}).eq(0);return"fixed"!==n&&i.length?i:t(e[0].ownerDocument||document)}function h(t,e){var n=t.offset(),i=n.left-(e?e.left:0),r=n.top-(e?e.top:0);return{left:i,right:i+t.outerWidth(),top:r,bottom:r+t.outerHeight()}}function f(t,e){var n=t.offset(),i=p(t),r=n.left+S(t,"border-left-width")+i.left-(e?e.left:0),s=n.top+S(t,"border-top-width")+i.top-(e?e.top:0);return{left:r,right:r+t[0].clientWidth,top:s,bottom:s+t[0].clientHeight}}function g(t,e){var n=t.offset(),i=n.left+S(t,"border-left-width")+S(t,"padding-left")-(e?e.left:0),r=n.top+S(t,"border-top-width")+S(t,"padding-top")-(e?e.top:0);return{left:i,right:i+t.width(),top:r,bottom:r+t.height()}}function p(t){var e,n=t.innerWidth()-t[0].clientWidth,i=t.innerHeight()-t[0].clientHeight;return n=v(n),i=v(i),e={left:0,right:0,top:0,bottom:i},m()&&"rtl"==t.css("direction")?e.left=n:e.right=n,e}function v(t){return t=Math.max(0,t),t=Math.round(t)}function m(){return null===Pt&&(Pt=y()),Pt}function y(){var e=t("<div><div/></div>").css({position:"absolute",top:-1e3,left:0,border:0,padding:0,overflow:"scroll",direction:"rtl"}).appendTo("body"),n=e.children(),i=n.offset().left>e.offset().left;return e.remove(),i}function S(t,e){return parseFloat(t.css(e))||0}function w(t){return 1==t.which&&!t.ctrlKey}function E(t){var e=t.originalEvent.touches;return e&&e.length?e[0].pageX:t.pageX}function b(t){var e=t.originalEvent.touches;return e&&e.length?e[0].pageY:t.pageY}function D(t){return/^touch/.test(t.type)}function T(t){t.addClass("fc-unselectable").on("selectstart",H)}function C(t){t.removeClass("fc-unselectable").off("selectstart",H)}function H(t){t.preventDefault()}function x(t,e){var n={left:Math.max(t.left,e.left),right:Math.min(t.right,e.right),top:Math.max(t.top,e.top),bottom:Math.min(t.bottom,e.bottom)};return n.left<n.right&&n.top<n.bottom&&n}function R(t,e){return{left:Math.min(Math.max(t.left,e.left),e.right),top:Math.min(Math.max(t.top,e.top),e.bottom)}}function I(t){return{left:(t.left+t.right)/2,top:(t.top+t.bottom)/2}}function k(t,e){return{left:t.left-e.left,top:t.top-e.top}}function L(e){var n,i,r=[],s=[];for("string"==typeof e?s=e.split(/\s*,\s*/):"function"==typeof e?s=[e]:t.isArray(e)&&(s=e),n=0;n<s.length;n++)i=s[n],"string"==typeof i?r.push("-"==i.charAt(0)?{field:i.substring(1),order:-1}:{field:i,order:1}):"function"==typeof i&&r.push({func:i});return r}function M(t,e,n){var i,r;for(i=0;i<n.length;i++)if(r=B(t,e,n[i]))return r;return 0}function B(t,e,n){return n.func?n.func(t,e):N(t[n.field],e[n.field])*(n.order||1)}function N(e,n){return e||n?null==n?-1:null==e?1:"string"===t.type(e)||"string"===t.type(n)?String(e).localeCompare(String(n)):e-n:0}function F(t,e){var n,i,r,s,o=t.start,l=t.end,a=e.start,u=e.end;if(l>a&&o<u)return o>=a?(n=o.clone(),r=!0):(n=a.clone(),r=!1),l<=u?(i=l.clone(),s=!0):(i=u.clone(),s=!1),{start:n,end:i,isStart:r,isEnd:s}}function z(t,n){return e.duration({days:t.clone().stripTime().diff(n.clone().stripTime(),"days"),ms:t.time()-n.time()})}function G(t,n){return e.duration({days:t.clone().stripTime().diff(n.clone().stripTime(),"days")})}function O(t,n,i){return e.duration(Math.round(t.diff(n,i,!0)),i)}function A(t,e){var n,i,r;for(n=0;n<Yt.length&&(i=Yt[n],r=V(i,t,e),!(r>=1&&ot(r)));n++);return i}function V(t,n,i){return null!=i?i.diff(n,t,!0):e.isDuration(n)?n.as(t):n.end.diff(n.start,t,!0)}function P(t,e,n){var i;return W(n)?(e-t)/n:(i=n.asMonths(),Math.abs(i)>=1&&ot(i)?e.diff(t,"months",!0)/i:e.diff(t,"days",!0)/n.asDays())}function _(t,e){var n,i;return W(t)||W(e)?t/e:(n=t.asMonths(),i=e.asMonths(),Math.abs(n)>=1&&ot(n)&&Math.abs(i)>=1&&ot(i)?n/i:t.asDays()/e.asDays())}function Y(t,n){var i;return W(t)?e.duration(t*n):(i=t.asMonths(),Math.abs(i)>=1&&ot(i)?e.duration({months:i*n}):e.duration({days:t.asDays()*n}))}function W(t){return Boolean(t.hours()||t.minutes()||t.seconds()||t.milliseconds())}function U(t){return"[object Date]"===Object.prototype.toString.call(t)||t instanceof Date}function j(t){return/^\d+\:\d+(?:\:\d+\.?(?:\d{3})?)?$/.test(t)}function q(t,e){var n,i,r,s,o,l,a={};if(e)for(n=0;n<e.length;n++){for(i=e[n],r=[],s=t.length-1;s>=0;s--)if(o=t[s][i],"object"==typeof o)r.unshift(o);else if(void 0!==o){a[i]=o;break}r.length&&(a[i]=q(r))}for(n=t.length-1;n>=0;n--){l=t[n];for(i in l)i in a||(a[i]=l[i])}return a}function Z(t){var e=function(){};return e.prototype=t,new e}function $(t,e){for(var n in t)Q(t,n)&&(e[n]=t[n])}function Q(t,e){return Wt.call(t,e)}function X(e){return/undefined|null|boolean|number|string/.test(t.type(e))}function K(e,n,i){if(t.isFunction(e)&&(e=[e]),e){var r,s;for(r=0;r<e.length;r++)s=e[r].apply(n,i)||s;return s}}function J(){for(var t=0;t<arguments.length;t++)if(void 0!==arguments[t])return arguments[t]}function tt(t){return(t+"").replace(/&/g,"&amp;").replace(/</g,"&lt;").replace(/>/g,"&gt;").replace(/'/g,"&#039;").replace(/"/g,"&quot;").replace(/\n/g,"<br />")}function et(t){return t.replace(/&.*?;/g,"")}function nt(e){var n=[];return t.each(e,function(t,e){null!=e&&n.push(t+":"+e)}),n.join(";")}function it(e){var n=[];return t.each(e,function(t,e){null!=e&&n.push(t+'="'+tt(e)+'"')}),n.join(" ")}function rt(t){return t.charAt(0).toUpperCase()+t.slice(1)}function st(t,e){return t-e}function ot(t){return t%1===0}function lt(t,e){var n=t[e];return function(){return n.apply(t,arguments)}}function at(t,e,n){var i,r,s,o,l,a=function(){var u=+new Date-o;u<e?i=setTimeout(a,e-u):(i=null,n||(l=t.apply(s,r),s=r=null))};return function(){s=this,r=arguments,o=+new Date;var u=n&&!i;return i||(i=setTimeout(a,e)),u&&(l=t.apply(s,r),s=r=null),l}}function ut(n,i,r){var s,o,l,a,u=n[0],c=1==n.length&&"string"==typeof u;return e.isMoment(u)||U(u)||void 0===u?a=e.apply(null,n):(s=!1,o=!1,c?Ut.test(u)?(u+="-01",n=[u],s=!0,o=!0):(l=jt.exec(u))&&(s=!l[5],o=!0):t.isArray(u)&&(o=!0),a=i||s?e.utc.apply(e,n):e.apply(null,n),s?(a._ambigTime=!0,a._ambigZone=!0):r&&(o?a._ambigZone=!0:c&&a.utcOffset(u))),a._fullCalendar=!0,a}function ct(){}function dt(t,e){var n;return Q(e,"constructor")&&(n=e.constructor),"function"!=typeof n&&(n=e.constructor=function(){t.apply(this,arguments)}),n.prototype=Z(t.prototype),$(e,n.prototype),$(t,n),n}function ht(t,e){$(e,t.prototype)}function ft(e){var n=t.Deferred(),i=n.promise();if("function"==typeof e&&e(function(t){ft.immediate&&(i._value=t),n.resolve(t)},function(){n.reject()}),ft.immediate){var r=i.then;i.then=function(t,e){var n=i.state();if("resolved"===n){if("function"==typeof t)return ft.resolve(t(i._value))}else if("rejected"===n&&"function"==typeof e)return e(),i;return r.call(i,t,e)}}return i}function gt(t){function e(t){return new ft(function(e){var i=function(){ft.resolve(t()).then(e).then(function(){n.shift(),n.length&&n[0]()})};n.push(i),1===n.length&&i()})}var n=[];this.add="number"==typeof t?at(e,t):e,this.addQuickly=e}function pt(t,e){return!t&&!e||!(!t||!e)&&(t.component===e.component&&vt(t,e)&&vt(e,t))}function vt(t,e){for(var n in t)if(!/^(component|left|right|top|bottom)$/.test(n)&&t[n]!==e[n])return!1;return!0}function mt(t){return{start:t.start.clone(),end:t.end?t.end.clone():null,allDay:t.allDay}}function yt(t){var e=wt(t);return"background"===e||"inverse-background"===e}function St(t){return"inverse-background"===wt(t)}function wt(t){return J((t.source||{}).rendering,t.rendering)}function Et(t){var e,n,i={};for(e=0;e<t.length;e++)n=t[e],(i[n._id]||(i[n._id]=[])).push(n);return i}function bt(t,e){return t.start-e.start}function Dt(n){var i,r,s,o,l=Ot.dataAttrPrefix;return l&&(l+="-"),i=n.data(l+"event")||null,i&&(i="object"==typeof i?t.extend({},i):{},r=i.start,null==r&&(r=i.time),s=i.duration,o=i.stick,delete i.start,delete i.time,delete i.duration,delete i.stick),null==r&&(r=n.data(l+"start")),null==r&&(r=n.data(l+"time")),null==s&&(s=n.data(l+"duration")),null==o&&(o=n.data(l+"stick")),r=null!=r?e.duration(r):null,s=null!=s?e.duration(s):null,o=Boolean(o),{eventProps:i,startTime:r,duration:s,stick:o}}function Tt(t,e){var n,i;for(n=0;n<e.length;n++)if(i=e[n],i.leftCol<=t.rightCol&&i.rightCol>=t.leftCol)return!0;return!1}function Ct(t,e){return t.leftCol-e.leftCol}function Ht(t){var e,n,i,r=[];for(e=0;e<t.length;e++){for(n=t[e],i=0;i<r.length&&It(n,r[i]).length;i++);n.level=i,(r[i]||(r[i]=[])).push(n)}return r}function xt(t){var e,n,i,r,s;for(e=0;e<t.length;e++)for(n=t[e],i=0;i<n.length;i++)for(r=n[i],r.forwardSegs=[],s=e+1;s<t.length;s++)It(r,t[s],r.forwardSegs)}function Rt(t){var e,n,i=t.forwardSegs,r=0;if(void 0===t.forwardPressure){for(e=0;e<i.length;e++)n=i[e],Rt(n),r=Math.max(r,1+n.forwardPressure);t.forwardPressure=r}}function It(t,e,n){n=n||[];for(var i=0;i<e.length;i++)kt(t,e[i])&&n.push(e[i]);return n}function kt(t,e){return t.bottom>e.top&&t.top<e.bottom}function Lt(t){this.items=t||[]}function Mt(e,n){function i(t){n=t}function r(){var i=n.layout;p=e.options.theme?"ui":"fc",i?(g?g.empty():g=this.el=t("<div class='fc-toolbar "+n.extraClasses+"'/>"),g.append(o("left")).append(o("right")).append(o("center")).append('<div class="fc-clear"/>')):s()}function s(){g&&(g.remove(),g=f.el=null)}function o(i){var r=t('<div class="fc-'+i+'"/>'),s=n.layout[i];return s&&t.each(s.split(" "),function(n){var i,s=t(),o=!0;t.each(this.split(","),function(n,i){var r,l,a,u,c,d,h,f,g,m;"title"==i?(s=s.add(t("<h2>&nbsp;</h2>")),o=!1):((r=(e.options.customButtons||{})[i])?(a=function(t){r.click&&r.click.call(m[0],t)},u="",c=r.text):(l=e.getViewSpec(i))?(a=function(){e.changeView(i)},v.push(i),u=l.buttonTextOverride,c=l.buttonTextDefault):e[i]&&(a=function(){e[i]()},u=(e.overrides.buttonText||{})[i],c=e.options.buttonText[i]),a&&(d=r?r.themeIcon:e.options.themeButtonIcons[i],h=r?r.icon:e.options.buttonIcons[i],f=u?tt(u):d&&e.options.theme?"<span class='ui-icon ui-icon-"+d+"'></span>":h&&!e.options.theme?"<span class='fc-icon fc-icon-"+h+"'></span>":tt(c),g=["fc-"+i+"-button",p+"-button",p+"-state-default"],m=t('<button type="button" class="'+g.join(" ")+'">'+f+"</button>").click(function(t){m.hasClass(p+"-state-disabled")||(a(t),(m.hasClass(p+"-state-active")||m.hasClass(p+"-state-disabled"))&&m.removeClass(p+"-state-hover"))}).mousedown(function(){m.not("."+p+"-state-active").not("."+p+"-state-disabled").addClass(p+"-state-down")}).mouseup(function(){m.removeClass(p+"-state-down")}).hover(function(){m.not("."+p+"-state-active").not("."+p+"-state-disabled").addClass(p+"-state-hover")},function(){m.removeClass(p+"-state-hover").removeClass(p+"-state-down")}),s=s.add(m)))}),o&&s.first().addClass(p+"-corner-left").end().last().addClass(p+"-corner-right").end(),s.length>1?(i=t("<div/>"),o&&i.addClass("fc-button-group"),i.append(s),r.append(i)):r.append(s)}),r}function l(t){g&&g.find("h2").text(t)}function a(t){g&&g.find(".fc-"+t+"-button").addClass(p+"-state-active")}function u(t){g&&g.find(".fc-"+t+"-button").removeClass(p+"-state-active")}function c(t){g&&g.find(".fc-"+t+"-button").prop("disabled",!0).addClass(p+"-state-disabled")}function d(t){g&&g.find(".fc-"+t+"-button").prop("disabled",!1).removeClass(p+"-state-disabled")}function h(){return v}var f=this;f.setToolbarOptions=i,f.render=r,f.removeElement=s,f.updateTitle=l,f.activateButton=a,f.deactivateButton=u,f.disableButton=c,f.enableButton=d,f.getViewsWithButtons=h,f.el=null;var g,p,v=[]}function Bt(n,i){function r(t){t._locale=Y}function s(){q?a()&&(f(),u()):o()}function o(){n.addClass("fc"),n.on("click.fc","a[data-goto]",function(e){var n=t(this),i=n.data("goto"),r=_.moment(i.date),s=i.type,o=Q.opt("navLink"+rt(s)+"Click");"function"==typeof o?o(r,e):("string"==typeof o&&(s=o),B(r,s))}),_.bindOption("theme",function(t){$=t?"ui":"fc",n.toggleClass("ui-widget",t),n.toggleClass("fc-unthemed",!t)}),_.bindOptions(["isRTL","locale"],function(t){n.toggleClass("fc-ltr",!t),n.toggleClass("fc-rtl",t)}),q=t("<div class='fc-view-container'/>").prependTo(n);var e=y();W=new Lt(e),U=_.header=e[0],j=_.footer=e[1],E(),b(),u(_.options.defaultView),_.options.handleWindowResize&&(K=at(v,_.options.windowResizeDelay),t(window).resize(K))}function l(){Q&&Q.removeElement(),W.proxyCall("removeElement"),q.remove(),n.removeClass("fc fc-ltr fc-rtl fc-unthemed ui-widget"),n.off(".fc"),K&&t(window).unbind("resize",K),se.unneeded()}function a(){return n.is(":visible")}function u(e,n){nt++;var i=Q&&e&&Q.type!==e;i&&(F(),c()),!Q&&e&&(Q=_.view=et[e]||(et[e]=_.instantiateView(e)),Q.setElement(t("<div class='fc-view fc-"+e+"-view' />").appendTo(q)),W.proxyCall("activateButton",e)),Q&&(J=Q.massageCurrentDate(J),Q.isDateSet&&J>=Q.intervalStart&&J<Q.intervalEnd||a()&&(n&&Q.captureInitialScroll(n),Q.setDate(J,n),n&&Q.releaseScroll(),D())),i&&z(),nt--}function c(){W.proxyCall("deactivateButton",Q.type),Q.removeElement(),Q=_.view=null}function d(){nt++,F();var t=Q.type,e=Q.queryScroll();c(),f(),u(t,e),z(),nt--}function h(t){if(a())return t&&g(),nt++,Q.updateSize(!0),nt--,!0}function f(){a()&&g()}function g(){var t=_.options.contentHeight,e=_.options.height;X="number"==typeof t?t:"function"==typeof t?t():"number"==typeof e?e-p():"function"==typeof e?e()-p():"parent"===e?n.parent().height()-p():Math.round(q.width()/Math.max(_.options.aspectRatio,.5))}function p(){return W.items.reduce(function(t,e){var n=e.el?e.el.outerHeight(!0):0;return t+n},0)}function v(t){!nt&&t.target===window&&Q.start&&h(!0)&&Q.publiclyTrigger("windowResize",tt)}function m(){a()&&_.reportEventChange()}function y(){return[new Mt(_,S()),new Mt(_,w())]}function S(){return{extraClasses:"fc-header-toolbar",layout:_.options.header}}function w(){return{extraClasses:"fc-footer-toolbar",layout:_.options.footer}}function E(){U.setToolbarOptions(S()),U.render(),U.el&&n.prepend(U.el)}function b(){j.setToolbarOptions(w()),j.render(),j.el&&n.append(j.el)}function D(){var t=_.getNow();t>=Q.intervalStart&&t<Q.intervalEnd?W.proxyCall("disableButton","today"):W.proxyCall("enableButton","today")}function T(t,e){Q.select(_.buildSelectSpan.apply(_,arguments))}function C(){Q&&Q.unselect()}function H(){J=Q.computePrevDate(J),u()}function x(){J=Q.computeNextDate(J),u()}function R(){J.add(-1,"years"),u()}function I(){J.add(1,"years"),u()}function k(){J=_.getNow(),u()}function L(t){J=_.moment(t).stripZone(),u()}function M(t){J.add(e.duration(t)),u()}function B(t,e){var n;e=e||"day",n=_.getViewSpec(e)||_.getUnitViewSpec(e),J=t.clone(),u(n?n.type:null)}function N(){return _.applyTimezone(J)}function F(){it++||q.css({width:"100%",height:q.height(),overflow:"hidden"})}function z(){--it||q.css({width:"",height:"",overflow:""})}function G(){return _}function O(){return Q}function A(t,e){var n;if("string"==typeof t){if(void 0===e)return _.options[t];n={},n[t]=e,V(n)}else"object"==typeof t&&V(t)}function V(t){var e,n=0;for(e in t)_.dynamicOverrides[e]=t[e];_.viewSpecCache={},_.populateOptionsHash();for(e in t)_.triggerOptionHandlers(e),n++;if(1===n){if("height"===e||"contentHeight"===e||"aspectRatio"===e)return void h(!0);if("defaultDate"===e)return;if("businessHours"===e)return void(Q&&(Q.unrenderBusinessHours(),Q.renderBusinessHours()));if("timezone"===e)return _.rezoneArrayEventSources(),void _.refetchEvents()}E(),b(),et={},d()}function P(t,e){var n=Array.prototype.slice.call(arguments,2);if(e=e||tt,this.triggerWith(t,e,n),_.options[t])return _.options[t].apply(e,n)}var _=this;se.needed(),_.render=s,_.destroy=l,_.rerenderEvents=m,_.changeView=u,_.select=T,_.unselect=C,_.prev=H,_.next=x,_.prevYear=R,_.nextYear=I,_.today=k,_.gotoDate=L,_.incrementDate=M,_.zoomTo=B,_.getDate=N,_.getCalendar=G,_.getView=O,_.option=A,_.publiclyTrigger=P,_.dynamicOverrides={},_.viewSpecCache={},_.optionHandlers={},_.overrides=t.extend({},i),_.populateOptionsHash();var Y;_.bindOptions(["locale","monthNames","monthNamesShort","dayNames","dayNamesShort","firstDay","weekNumberCalculation"],function(t,e,n,i,s,o,l){if("iso"===l&&(l="ISO"),Y=Z(Ft(t)),e&&(Y._months=e),n&&(Y._monthsShort=n),i&&(Y._weekdays=i),s&&(Y._weekdaysShort=s),null==o&&"ISO"===l&&(o=1),null!=o){var a=Z(Y._week);a.dow=o,Y._week=a}"ISO"!==l&&"local"!==l&&"function"!=typeof l||(Y._fullCalendar_weekCalc=l),J&&r(J)}),_.defaultAllDayEventDuration=e.duration(_.options.defaultAllDayEventDuration),_.defaultTimedEventDuration=e.duration(_.options.defaultTimedEventDuration),_.moment=function(){var t;return"local"===_.options.timezone?(t=Ot.moment.apply(null,arguments),t.hasTime()&&t.local()):t="UTC"===_.options.timezone?Ot.moment.utc.apply(null,arguments):Ot.moment.parseZone.apply(null,arguments),r(t),t},_.localizeMoment=r,_.getIsAmbigTimezone=function(){return"local"!==_.options.timezone&&"UTC"!==_.options.timezone},_.applyTimezone=function(t){if(!t.hasTime())return t.clone();var e,n=_.moment(t.toArray()),i=t.time()-n.time();return i&&(e=n.clone().add(i),t.time()-e.time()===0&&(n=e)),n},_.getNow=function(){var t=_.options.now;return"function"==typeof t&&(t=t()),_.moment(t).stripZone()},_.getEventEnd=function(t){return t.end?t.end.clone():_.getDefaultEventEnd(t.allDay,t.start)},_.getDefaultEventEnd=function(t,e){var n=e.clone();return t?n.stripTime().add(_.defaultAllDayEventDuration):n.add(_.defaultTimedEventDuration),_.getIsAmbigTimezone()&&n.stripZone(),n},_.humanizeDuration=function(t){return t.locale(_.options.locale).humanize()},zt.call(_);var W,U,j,q,$,Q,X,K,J,tt=n[0],et={},nt=0;J=null!=_.options.defaultDate?_.moment(_.options.defaultDate).stripZone():_.getNow(),_.getSuggestedViewHeight=function(){return void 0===X&&f(),X},_.isHeightAuto=function(){return"auto"===_.options.contentHeight||"auto"===_.options.height},_.setToolbarsTitle=function(t){W.proxyCall("updateTitle",t)},_.freezeContentHeight=F,_.thawContentHeight=z;var it=0;_.initialize()}function Nt(e){t.each(me,function(t,n){null==e[t]&&(e[t]=n(e))})}function Ft(t){return e.localeData(t)||e.localeData("en")}function zt(){function n(t,e){return!U.options.lazyFetching||s(t,e)?o(t,e):ft.resolve($)}function i(){$=r(nt),U.trigger("eventsReset",$)}function r(t){var e,n,i=[];for(e=0;e<t.length;e++)n=t[e],n.start.clone().stripZone()<Z&&U.getEventEnd(n).stripZone()>q&&i.push(n);return i}function s(t,e){return!q||t<q||e>Z}function o(t,e){return q=t,Z=e,l()}function l(){return u(tt,"reset")}function a(t){return u(E(t))}function u(t,e){var n,i;for("reset"===e?nt=[]:"add"!==e&&(nt=C(nt,t)),n=0;n<t.length;n++)i=t[n],"pending"!==i._status&&et++,i._fetchId=(i._fetchId||0)+1,i._status="pending";for(n=0;n<t.length;n++)i=t[n],c(i,i._fetchId);return et?new ft(function(t){U.one("eventsReceived",t)}):ft.resolve($)}function c(e,n){f(e,function(i){var r,s,o,l=t.isArray(e.events);if(n===e._fetchId&&"rejected"!==e._status){if(e._status="resolved",i)for(r=0;r<i.length;r++)s=i[r],o=l?s:F(s,e),o&&nt.push.apply(nt,_(o));h()}})}function d(t){var e="pending"===t._status;t._status="rejected",e&&h()}function h(){et--,et||(i(nt),U.trigger("eventsReceived",$))}function f(e,n){var i,r,s=Ot.sourceFetchers;for(i=0;i<s.length;i++){if(r=s[i].call(U,e,q.clone(),Z.clone(),U.options.timezone,n),r===!0)return;if("object"==typeof r)return void f(r,n)}var o=e.events;if(o)t.isFunction(o)?(U.pushLoading(),o.call(U,q.clone(),Z.clone(),U.options.timezone,function(t){n(t),U.popLoading()})):t.isArray(o)?n(o):n();else{var l=e.url;if(l){var a,u=e.success,c=e.error,d=e.complete;a=t.isFunction(e.data)?e.data():e.data;var h=t.extend({},a||{}),g=J(e.startParam,U.options.startParam),p=J(e.endParam,U.options.endParam),v=J(e.timezoneParam,U.options.timezoneParam);g&&(h[g]=q.format()),p&&(h[p]=Z.format()),U.options.timezone&&"local"!=U.options.timezone&&(h[v]=U.options.timezone),U.pushLoading(),t.ajax(t.extend({},ye,e,{data:h,success:function(e){e=e||[];var i=K(u,this,arguments);t.isArray(i)&&(e=i),n(e)},error:function(){K(c,this,arguments),n()},complete:function(){K(d,this,arguments),U.popLoading()}}))}else n()}}function g(t){var e=p(t);e&&(tt.push(e),u([e],"add"))}function p(e){var n,i,r=Ot.sourceNormalizers;if(t.isFunction(e)||t.isArray(e)?n={events:e}:"string"==typeof e?n={url:e}:"object"==typeof e&&(n=t.extend({},e)),n){for(n.className?"string"==typeof n.className&&(n.className=n.className.split(/\s+/)):n.className=[],t.isArray(n.events)&&(n.origArray=n.events,n.events=t.map(n.events,function(t){return F(t,n)})),i=0;i<r.length;i++)r[i].call(U,n);return n}}function v(t){y(b(t))}function m(t){null==t?y(tt,!0):y(E(t))}function y(e,n){var r;for(r=0;r<e.length;r++)d(e[r]);n?(tt=[],nt=[]):(tt=t.grep(tt,function(t){for(r=0;r<e.length;r++)if(t===e[r])return!1;return!0}),nt=C(nt,e)),i()}function S(){return tt.slice(1)}function w(e){return t.grep(tt,function(t){return t.id&&t.id===e})[0]}function E(e){e?t.isArray(e)||(e=[e]):e=[];var n,i=[];for(n=0;n<e.length;n++)i.push.apply(i,b(e[n]));return i}function b(e){var n,i;for(n=0;n<tt.length;n++)if(i=tt[n],i===e)return[i];return i=w(e),i?[i]:t.grep(tt,function(t){return D(e,t)})}function D(t,e){return t&&e&&T(t)==T(e)}function T(t){return("object"==typeof t?t.origArray||t.googleCalendarId||t.url||t.events:null)||t}function C(e,n){return t.grep(e,function(t){for(var e=0;e<n.length;e++)if(t.source===n[e])return!1;return!0})}function H(t){x([t])}function x(t){var e,n;for(e=0;e<t.length;e++)n=t[e],n.start=U.moment(n.start),n.end?n.end=U.moment(n.end):n.end=null,Y(n,R(n));i()}function R(e){var n={};return t.each(e,function(t,e){I(t)&&void 0!==e&&X(e)&&(n[t]=e)}),n}function I(t){return!/^_|^(id|allDay|start|end)$/.test(t)}function k(t,e){return L([t],e)}function L(t,e){var n,r,s,o,l,a=[];for(s=0;s<t.length;s++)if(r=F(t[s])){for(n=_(r),o=0;o<n.length;o++)l=n[o],l.source||(e&&(Q.events.push(l),l.source=Q),nt.push(l));a=a.concat(n)}return a.length&&i(),a}function M(e){var n,r;for(null==e?e=function(){return!0}:t.isFunction(e)||(n=e+"",e=function(t){return t._id==n}),nt=t.grep(nt,e,!0),r=0;r<tt.length;r++)t.isArray(tt[r].events)&&(tt[r].events=t.grep(tt[r].events,e,!0));i()}function B(e){return t.isFunction(e)?t.grep(nt,e):null!=e?(e+="",t.grep(nt,function(t){return t._id==e})):nt}function N(t){t.start=U.moment(t.start),t.end&&(t.end=U.moment(t.end)),Gt(t)}function F(n,i){var r,s,o,l={};if(U.options.eventDataTransform&&(n=U.options.eventDataTransform(n)),i&&i.eventDataTransform&&(n=i.eventDataTransform(n)),t.extend(l,n),i&&(l.source=i),l._id=n._id||(void 0===n.id?"_fc"+Se++:n.id+""),n.className?"string"==typeof n.className?l.className=n.className.split(/\s+/):l.className=n.className:l.className=[],r=n.start||n.date,s=n.end,j(r)&&(r=e.duration(r)),j(s)&&(s=e.duration(s)),n.dow||e.isDuration(r)||e.isDuration(s))l.start=r?e.duration(r):null,l.end=s?e.duration(s):null,l._recurring=!0;else{if(r&&(r=U.moment(r),!r.isValid()))return!1;s&&(s=U.moment(s),s.isValid()||(s=null)),o=n.allDay,void 0===o&&(o=J(i?i.allDayDefault:void 0,U.options.allDayDefault)),A(r,s,o,l)}return U.normalizeEvent(l),l}function A(t,e,n,i){i.start=t,i.end=e,i.allDay=n,V(i),Gt(i)}function V(t){P(t),t.end&&!t.end.isAfter(t.start)&&(t.end=null),t.end||(U.options.forceEventDuration?t.end=U.getDefaultEventEnd(t.allDay,t.start):t.end=null)}function P(t){null==t.allDay&&(t.allDay=!(t.start.hasTime()||t.end&&t.end.hasTime())),t.allDay?(t.start.stripTime(),t.end&&t.end.stripTime()):(t.start.hasTime()||(t.start=U.applyTimezone(t.start.time(0))),t.end&&!t.end.hasTime()&&(t.end=U.applyTimezone(t.end.time(0))))}function _(e,n,i){var r,s,o,l,a,u,c,d,h,f=[];if(n=n||q,i=i||Z,e)if(e._recurring){if(s=e.dow)for(r={},o=0;o<s.length;o++)r[s[o]]=!0;for(l=n.clone().stripTime();l.isBefore(i);)r&&!r[l.day()]||(a=e.start,u=e.end,c=l.clone(),d=null,a&&(c=c.time(a)),u&&(d=l.clone().time(u)),h=t.extend({},e),A(c,d,!a&&!u,h),f.push(h)),l.add(1,"days")}else f.push(e);return f}function Y(e,n,i){function r(t,e){return i?O(t,e,i):n.allDay?G(t,e):z(t,e)}var s,o,l,a,u,c,d={};return n=n||{},n.start||(n.start=e.start.clone()),void 0===n.end&&(n.end=e.end?e.end.clone():null),null==n.allDay&&(n.allDay=e.allDay),V(n),s={start:e._start.clone(),end:e._end?e._end.clone():U.getDefaultEventEnd(e._allDay,e._start),allDay:n.allDay},V(s),o=null!==e._end&&null===n.end,l=r(n.start,s.start),n.end?(a=r(n.end,s.end),u=a.subtract(l)):u=null,t.each(n,function(t,e){I(t)&&void 0!==e&&(d[t]=e)}),c=W(B(e._id),o,n.allDay,l,u,d),{dateDelta:l,durationDelta:u,undo:c}}function W(e,n,i,r,s,o){var l=U.getIsAmbigTimezone(),a=[];return r&&!r.valueOf()&&(r=null),s&&!s.valueOf()&&(s=null),t.each(e,function(e,u){var c,d;c={start:u.start.clone(),end:u.end?u.end.clone():null,allDay:u.allDay},t.each(o,function(t){c[t]=u[t]}),d={start:u._start,end:u._end,allDay:i},V(d),n?d.end=null:s&&!d.end&&(d.end=U.getDefaultEventEnd(d.allDay,d.start)),r&&(d.start.add(r),d.end&&d.end.add(r)),s&&d.end.add(s),l&&!d.allDay&&(r||s)&&(d.start.stripZone(),d.end&&d.end.stripZone()),t.extend(u,o,d),Gt(u),a.push(function(){t.extend(u,c),Gt(u)})}),function(){for(var t=0;t<a.length;t++)a[t]()}}var U=this;U.requestEvents=n,U.reportEventChange=i,U.isFetchNeeded=s,U.fetchEvents=o,U.fetchEventSources=u,U.refetchEvents=l,U.refetchEventSources=a,U.getEventSources=S,U.getEventSourceById=w,U.addEventSource=g,U.removeEventSource=v,U.removeEventSources=m,U.updateEvent=H,U.updateEvents=x,U.renderEvent=k,U.renderEvents=L,U.removeEvents=M,U.clientEvents=B,U.mutateEvent=Y,U.normalizeEventDates=V,U.normalizeEventTimes=P;var q,Z,$,Q={events:[]},tt=[Q],et=0,nt=[];t.each((U.options.events?[U.options.events]:[]).concat(U.options.eventSources||[]),function(t,e){var n=p(e);n&&tt.push(n)}),U.getEventCache=function(){return nt},U.getPrunedEventCache=function(){return $},U.rezoneArrayEventSources=function(){var e,n,i;for(e=0;e<tt.length;e++)if(n=tt[e].events,t.isArray(n))for(i=0;i<n.length;i++)N(n[i])},U.buildEventFromInput=F,U.expandEvent=_}function Gt(t){t._allDay=t.allDay,t._start=t.start.clone(),t._end=t.end?t.end.clone():null}var Ot=t.fullCalendar={version:"3.2.0",internalApiVersion:8},At=Ot.views={};t.fn.fullCalendar=function(e){var n=Array.prototype.slice.call(arguments,1),i=this;return this.each(function(r,s){var o,l=t(s),a=l.data("fullCalendar");"string"==typeof e?a&&t.isFunction(a[e])&&(o=a[e].apply(a,n),r||(i=o),"destroy"===e&&l.removeData("fullCalendar")):a||(a=new fe(l,e),l.data("fullCalendar",a),a.render())}),i};var Vt=["header","footer","buttonText","buttonIcons","themeButtonIcons"];Ot.intersectRanges=F,Ot.applyAll=K,Ot.debounce=at,Ot.isInt=ot,Ot.htmlEscape=tt,Ot.cssToStr=nt,Ot.proxy=lt,Ot.capitaliseFirstLetter=rt,Ot.getOuterRect=h,Ot.getClientRect=f,Ot.getContentRect=g,Ot.getScrollbarWidths=p;var Pt=null;Ot.preventDefault=H,Ot.intersectRects=x,Ot.parseFieldSpecs=L,Ot.compareByFieldSpecs=M,Ot.compareByFieldSpec=B,Ot.flexibleCompare=N,Ot.computeIntervalUnit=A,Ot.divideRangeByDuration=P,Ot.divideDurationByDuration=_,Ot.multiplyDuration=Y,Ot.durationHasTime=W;var _t=["sun","mon","tue","wed","thu","fri","sat"],Yt=["year","month","week","day","hour","minute","second","millisecond"];Ot.log=function(){var t=window.console;if(t&&t.log)return t.log.apply(t,arguments)},Ot.warn=function(){var t=window.console;return t&&t.warn?t.warn.apply(t,arguments):Ot.log.apply(Ot,arguments)};var Wt={}.hasOwnProperty;Ot.createObject=Z;var Ut=/^\s*\d{4}-\d\d$/,jt=/^\s*\d{4}-(?:(\d\d-\d\d)|(W\d\d$)|(W\d\d-\d)|(\d\d\d))((T| )(\d\d(:\d\d(:\d\d(\.\d+)?)?)?)?)?$/,qt=e.fn,Zt=t.extend({},qt),$t=e.momentProperties;$t.push("_fullCalendar"),$t.push("_ambigTime"),$t.push("_ambigZone"),Ot.moment=function(){return ut(arguments)},Ot.moment.utc=function(){var t=ut(arguments,!0);return t.hasTime()&&t.utc(),t},Ot.moment.parseZone=function(){return ut(arguments,!0,!0)},qt.week=qt.weeks=function(t){var e=this._locale._fullCalendar_weekCalc;return null==t&&"function"==typeof e?e(this):"ISO"===e?Zt.isoWeek.apply(this,arguments):Zt.week.apply(this,arguments)},qt.time=function(t){if(!this._fullCalendar)return Zt.time.apply(this,arguments);if(null==t)return e.duration({hours:this.hours(),minutes:this.minutes(),seconds:this.seconds(),milliseconds:this.milliseconds()});this._ambigTime=!1,e.isDuration(t)||e.isMoment(t)||(t=e.duration(t));var n=0;return e.isDuration(t)&&(n=24*Math.floor(t.asDays())),this.hours(n+t.hours()).minutes(t.minutes()).seconds(t.seconds()).milliseconds(t.milliseconds())},qt.stripTime=function(){return this._ambigTime||(this.utc(!0),this.set({hours:0,minutes:0,seconds:0,ms:0}),this._ambigTime=!0,this._ambigZone=!0),this},qt.hasTime=function(){return!this._ambigTime},qt.stripZone=function(){var t;return this._ambigZone||(t=this._ambigTime,this.utc(!0),this._ambigTime=t||!1,this._ambigZone=!0),this},qt.hasZone=function(){return!this._ambigZone},qt.local=function(t){return Zt.local.call(this,this._ambigZone||t),this._ambigTime=!1,this._ambigZone=!1,this},qt.utc=function(t){return Zt.utc.call(this,t),this._ambigTime=!1,this._ambigZone=!1,this},qt.utcOffset=function(t){return null!=t&&(this._ambigTime=!1,this._ambigZone=!1),Zt.utcOffset.apply(this,arguments)},qt.format=function(){return this._fullCalendar&&arguments[0]?Qt(this,arguments[0]):this._ambigTime?Kt(this,"YYYY-MM-DD"):this._ambigZone?Kt(this,"YYYY-MM-DD[T]HH:mm:ss"):Zt.format.apply(this,arguments)},qt.toISOString=function(){return this._ambigTime?Kt(this,"YYYY-MM-DD"):this._ambigZone?Kt(this,"YYYY-MM-DD[T]HH:mm:ss"):Zt.toISOString.apply(this,arguments)},function(){function t(t,e){return c(r(e).fakeFormatString,t)}function e(t,e){return Zt.format.call(t,e)}function n(t,e,n,s,o){var l;return t=Ot.moment.parseZone(t),e=Ot.moment.parseZone(e),l=t.localeData(),n=l.longDateFormat(n)||n,i(r(n),t,e,s||" - ",o)}function i(t,e,n,i,r){var s,o,l,a=t.sameUnits,u=e.clone().stripZone(),c=n.clone().stripZone(),f=d(t.fakeFormatString,e),g=d(t.fakeFormatString,n),p="",v="",m="",y="",S="";for(s=0;s<a.length&&(!a[s]||u.isSame(c,a[s]));s++)p+=f[s];for(o=a.length-1;o>s&&(!a[o]||u.isSame(c,a[o]))&&(o-1!==s||"."!==f[o]);o--)v=f[o]+v;for(l=s;l<=o;l++)m+=f[l],y+=g[l];return(m||y)&&(S=r?y+i+m:m+i+y),h(p+S+v)}function r(t){return w[t]||(w[t]=s(t))}function s(t){var e=o(t);return{fakeFormatString:a(e),sameUnits:u(e)}}function o(t){for(var e,n=[],i=/\[([^\]]*)\]|\(([^\)]*)\)|(LTS|LT|(\w)\4*o?)|([^\w\[\(]+)/g;e=i.exec(t);)e[1]?n.push.apply(n,l(e[1])):e[2]?n.push({maybe:o(e[2])}):e[3]?n.push({token:e[3]}):e[5]&&n.push.apply(n,l(e[5]));return n}function l(t){return". "===t?["."," "]:[t]}function a(t){var e,n,i=[];for(e=0;e<t.length;e++)n=t[e],"string"==typeof n?i.push("["+n+"]"):n.token?n.token in y?i.push(p+"["+n.token+"]"):i.push(n.token):n.maybe&&i.push(v+a(n.maybe)+v);return i.join(g)}function u(t){var e,n,i,r=[];for(e=0;e<t.length;e++)n=t[e],n.token?(i=S[n.token.charAt(0)],r.push(i?i.unit:"second")):n.maybe?r.push.apply(r,u(n.maybe)):r.push(null);return r}function c(t,e){return h(d(t,e).join(""))}function d(t,n){var i,r,s=[],o=e(n,t),l=o.split(g);for(i=0;i<l.length;i++)r=l[i],r.charAt(0)===p?s.push(y[r.substring(1)](n)):s.push(r);return s}function h(t){return t.replace(m,function(t,e){
+return e.match(/[1-9]/)?e:""})}function f(t){var e,n,i,r,s=o(t);for(e=0;e<s.length;e++)n=s[e],n.token&&(i=S[n.token.charAt(0)],i&&(!r||i.value>r.value)&&(r=i));return r?r.unit:null}Ot.formatDate=t,Ot.formatRange=n,Ot.oldMomentFormat=e,Ot.queryMostGranularFormatUnit=f;var g="\v",p="",v="",m=new RegExp(v+"([^"+v+"]*)"+v,"g"),y={t:function(t){return e(t,"a").charAt(0)},T:function(t){return e(t,"A").charAt(0)}},S={Y:{value:1,unit:"year"},M:{value:2,unit:"month"},W:{value:3,unit:"week"},w:{value:3,unit:"week"},D:{value:4,unit:"day"},d:{value:4,unit:"day"}},w={}}();var Qt=Ot.formatDate,Xt=Ot.formatRange,Kt=Ot.oldMomentFormat;Ot.Class=ct,ct.extend=function(){var t,e,n=arguments.length;for(t=0;t<n;t++)e=arguments[t],t<n-1&&ht(this,e);return dt(this,e||{})},ct.mixin=function(t){ht(this,t)},Ot.Promise=ft,ft.immediate=!0,ft.resolve=function(e){if(e&&"function"==typeof e.resolve)return e.promise();if(e&&"function"==typeof e.then)return e;var n=t.Deferred().resolve(e),i=n.promise();if(ft.immediate){var r=i.then;i._value=e,i.then=function(t,n){return"function"==typeof t?ft.resolve(t(e)):r.call(i,t,n)}}return i},ft.reject=function(){return t.Deferred().reject().promise()},ft.all=function(e){var n,i,r,s=!1;if(ft.immediate)for(s=!0,n=[],i=0;i<e.length;i++)if(r=e[i],r&&"function"==typeof r.state&&"resolved"===r.state()&&"_value"in r)n.push(r._value);else{if(r&&"function"==typeof r.then){s=!1;break}n.push(r)}return s?ft.resolve(n):t.when.apply(t.when,e).then(function(){return t.when(t.makeArray(arguments))})},Ot.TaskQueue=gt;var Jt=Ot.EmitterMixin={on:function(e,n){return t(this).on(e,this._prepareIntercept(n)),this},one:function(e,n){return t(this).one(e,this._prepareIntercept(n)),this},_prepareIntercept:function(e){var n=function(t,n){return e.apply(n.context||this,n.args||[])};return e.guid||(e.guid=t.guid++),n.guid=e.guid,n},off:function(e,n){return t(this).off(e,n),this},trigger:function(e){var n=Array.prototype.slice.call(arguments,1);return t(this).triggerHandler(e,{args:n}),this},triggerWith:function(e,n,i){return t(this).triggerHandler(e,{context:n,args:i}),this}},te=Ot.ListenerMixin=function(){var e=0,n={listenerId:null,listenTo:function(e,n,i){if("object"==typeof n)for(var r in n)n.hasOwnProperty(r)&&this.listenTo(e,r,n[r]);else"string"==typeof n&&e.on(n+"."+this.getListenerNamespace(),t.proxy(i,this))},stopListeningTo:function(t,e){t.off((e||"")+"."+this.getListenerNamespace())},getListenerNamespace:function(){return null==this.listenerId&&(this.listenerId=e++),"_listener"+this.listenerId}};return n}(),ee=ct.extend(te,{isHidden:!0,options:null,el:null,margin:10,constructor:function(t){this.options=t||{}},show:function(){this.isHidden&&(this.el||this.render(),this.el.show(),this.position(),this.isHidden=!1,this.trigger("show"))},hide:function(){this.isHidden||(this.el.hide(),this.isHidden=!0,this.trigger("hide"))},render:function(){var e=this,n=this.options;this.el=t('<div class="fc-popover"/>').addClass(n.className||"").css({top:0,left:0}).append(n.content).appendTo(n.parentEl),this.el.on("click",".fc-close",function(){e.hide()}),n.autoHide&&this.listenTo(t(document),"mousedown",this.documentMousedown)},documentMousedown:function(e){this.el&&!t(e.target).closest(this.el).length&&this.hide()},removeElement:function(){this.hide(),this.el&&(this.el.remove(),this.el=null),this.stopListeningTo(t(document),"mousedown")},position:function(){var e,n,i,r,s,o=this.options,l=this.el.offsetParent().offset(),a=this.el.outerWidth(),u=this.el.outerHeight(),c=t(window),h=d(this.el);r=o.top||0,s=void 0!==o.left?o.left:void 0!==o.right?o.right-a:0,h.is(window)||h.is(document)?(h=c,e=0,n=0):(i=h.offset(),e=i.top,n=i.left),e+=c.scrollTop(),n+=c.scrollLeft(),o.viewportConstrain!==!1&&(r=Math.min(r,e+h.outerHeight()-u-this.margin),r=Math.max(r,e+this.margin),s=Math.min(s,n+h.outerWidth()-a-this.margin),s=Math.max(s,n+this.margin)),this.el.css({top:r-l.top,left:s-l.left})},trigger:function(t){this.options[t]&&this.options[t].apply(this,Array.prototype.slice.call(arguments,1))}}),ne=Ot.CoordCache=ct.extend({els:null,forcedOffsetParentEl:null,origin:null,boundingRect:null,isHorizontal:!1,isVertical:!1,lefts:null,rights:null,tops:null,bottoms:null,constructor:function(e){this.els=t(e.els),this.isHorizontal=e.isHorizontal,this.isVertical=e.isVertical,this.forcedOffsetParentEl=e.offsetParent?t(e.offsetParent):null},build:function(){var t=this.forcedOffsetParentEl;!t&&this.els.length>0&&(t=this.els.eq(0).offsetParent()),this.origin=t?t.offset():null,this.boundingRect=this.queryBoundingRect(),this.isHorizontal&&this.buildElHorizontals(),this.isVertical&&this.buildElVerticals()},clear:function(){this.origin=null,this.boundingRect=null,this.lefts=null,this.rights=null,this.tops=null,this.bottoms=null},ensureBuilt:function(){this.origin||this.build()},buildElHorizontals:function(){var e=[],n=[];this.els.each(function(i,r){var s=t(r),o=s.offset().left,l=s.outerWidth();e.push(o),n.push(o+l)}),this.lefts=e,this.rights=n},buildElVerticals:function(){var e=[],n=[];this.els.each(function(i,r){var s=t(r),o=s.offset().top,l=s.outerHeight();e.push(o),n.push(o+l)}),this.tops=e,this.bottoms=n},getHorizontalIndex:function(t){this.ensureBuilt();var e,n=this.lefts,i=this.rights,r=n.length;for(e=0;e<r;e++)if(t>=n[e]&&t<i[e])return e},getVerticalIndex:function(t){this.ensureBuilt();var e,n=this.tops,i=this.bottoms,r=n.length;for(e=0;e<r;e++)if(t>=n[e]&&t<i[e])return e},getLeftOffset:function(t){return this.ensureBuilt(),this.lefts[t]},getLeftPosition:function(t){return this.ensureBuilt(),this.lefts[t]-this.origin.left},getRightOffset:function(t){return this.ensureBuilt(),this.rights[t]},getRightPosition:function(t){return this.ensureBuilt(),this.rights[t]-this.origin.left},getWidth:function(t){return this.ensureBuilt(),this.rights[t]-this.lefts[t]},getTopOffset:function(t){return this.ensureBuilt(),this.tops[t]},getTopPosition:function(t){return this.ensureBuilt(),this.tops[t]-this.origin.top},getBottomOffset:function(t){return this.ensureBuilt(),this.bottoms[t]},getBottomPosition:function(t){return this.ensureBuilt(),this.bottoms[t]-this.origin.top},getHeight:function(t){return this.ensureBuilt(),this.bottoms[t]-this.tops[t]},queryBoundingRect:function(){var t;return this.els.length>0&&(t=d(this.els.eq(0)),!t.is(document))?f(t):null},isPointInBounds:function(t,e){return this.isLeftInBounds(t)&&this.isTopInBounds(e)},isLeftInBounds:function(t){return!this.boundingRect||t>=this.boundingRect.left&&t<this.boundingRect.right},isTopInBounds:function(t){return!this.boundingRect||t>=this.boundingRect.top&&t<this.boundingRect.bottom}}),ie=Ot.DragListener=ct.extend(te,{options:null,subjectEl:null,originX:null,originY:null,scrollEl:null,isInteracting:!1,isDistanceSurpassed:!1,isDelayEnded:!1,isDragging:!1,isTouch:!1,delay:null,delayTimeoutId:null,minDistance:null,shouldCancelTouchScroll:!0,scrollAlwaysKills:!1,constructor:function(t){this.options=t||{}},startInteraction:function(e,n){var i=D(e);if("mousedown"===e.type){if(se.get().shouldIgnoreMouse())return;if(!w(e))return;e.preventDefault()}this.isInteracting||(n=n||{},this.delay=J(n.delay,this.options.delay,0),this.minDistance=J(n.distance,this.options.distance,0),this.subjectEl=this.options.subjectEl,T(t("body")),this.isInteracting=!0,this.isTouch=i,this.isDelayEnded=!1,this.isDistanceSurpassed=!1,this.originX=E(e),this.originY=b(e),this.scrollEl=d(t(e.target)),this.bindHandlers(),this.initAutoScroll(),this.handleInteractionStart(e),this.startDelay(e),this.minDistance||this.handleDistanceSurpassed(e))},handleInteractionStart:function(t){this.trigger("interactionStart",t)},endInteraction:function(e,n){this.isInteracting&&(this.endDrag(e),this.delayTimeoutId&&(clearTimeout(this.delayTimeoutId),this.delayTimeoutId=null),this.destroyAutoScroll(),this.unbindHandlers(),this.isInteracting=!1,this.handleInteractionEnd(e,n),C(t("body")))},handleInteractionEnd:function(t,e){this.trigger("interactionEnd",t,e||!1)},bindHandlers:function(){var t=se.get();this.isTouch?this.listenTo(t,{touchmove:this.handleTouchMove,touchend:this.endInteraction,scroll:this.handleTouchScroll}):this.listenTo(t,{mousemove:this.handleMouseMove,mouseup:this.endInteraction}),this.listenTo(t,{selectstart:H,contextmenu:H})},unbindHandlers:function(){this.stopListeningTo(se.get())},startDrag:function(t,e){this.startInteraction(t,e),this.isDragging||(this.isDragging=!0,this.handleDragStart(t))},handleDragStart:function(t){this.trigger("dragStart",t)},handleMove:function(t){var e,n=E(t)-this.originX,i=b(t)-this.originY,r=this.minDistance;this.isDistanceSurpassed||(e=n*n+i*i,e>=r*r&&this.handleDistanceSurpassed(t)),this.isDragging&&this.handleDrag(n,i,t)},handleDrag:function(t,e,n){this.trigger("drag",t,e,n),this.updateAutoScroll(n)},endDrag:function(t){this.isDragging&&(this.isDragging=!1,this.handleDragEnd(t))},handleDragEnd:function(t){this.trigger("dragEnd",t)},startDelay:function(t){var e=this;this.delay?this.delayTimeoutId=setTimeout(function(){e.handleDelayEnd(t)},this.delay):this.handleDelayEnd(t)},handleDelayEnd:function(t){this.isDelayEnded=!0,this.isDistanceSurpassed&&this.startDrag(t)},handleDistanceSurpassed:function(t){this.isDistanceSurpassed=!0,this.isDelayEnded&&this.startDrag(t)},handleTouchMove:function(t){this.isDragging&&this.shouldCancelTouchScroll&&t.preventDefault(),this.handleMove(t)},handleMouseMove:function(t){this.handleMove(t)},handleTouchScroll:function(t){this.isDragging&&!this.scrollAlwaysKills||this.endInteraction(t,!0)},trigger:function(t){this.options[t]&&this.options[t].apply(this,Array.prototype.slice.call(arguments,1)),this["_"+t]&&this["_"+t].apply(this,Array.prototype.slice.call(arguments,1))}});ie.mixin({isAutoScroll:!1,scrollBounds:null,scrollTopVel:null,scrollLeftVel:null,scrollIntervalId:null,scrollSensitivity:30,scrollSpeed:200,scrollIntervalMs:50,initAutoScroll:function(){var t=this.scrollEl;this.isAutoScroll=this.options.scroll&&t&&!t.is(window)&&!t.is(document),this.isAutoScroll&&this.listenTo(t,"scroll",at(this.handleDebouncedScroll,100))},destroyAutoScroll:function(){this.endAutoScroll(),this.isAutoScroll&&this.stopListeningTo(this.scrollEl,"scroll")},computeScrollBounds:function(){this.isAutoScroll&&(this.scrollBounds=h(this.scrollEl))},updateAutoScroll:function(t){var e,n,i,r,s=this.scrollSensitivity,o=this.scrollBounds,l=0,a=0;o&&(e=(s-(b(t)-o.top))/s,n=(s-(o.bottom-b(t)))/s,i=(s-(E(t)-o.left))/s,r=(s-(o.right-E(t)))/s,e>=0&&e<=1?l=e*this.scrollSpeed*-1:n>=0&&n<=1&&(l=n*this.scrollSpeed),i>=0&&i<=1?a=i*this.scrollSpeed*-1:r>=0&&r<=1&&(a=r*this.scrollSpeed)),this.setScrollVel(l,a)},setScrollVel:function(t,e){this.scrollTopVel=t,this.scrollLeftVel=e,this.constrainScrollVel(),!this.scrollTopVel&&!this.scrollLeftVel||this.scrollIntervalId||(this.scrollIntervalId=setInterval(lt(this,"scrollIntervalFunc"),this.scrollIntervalMs))},constrainScrollVel:function(){var t=this.scrollEl;this.scrollTopVel<0?t.scrollTop()<=0&&(this.scrollTopVel=0):this.scrollTopVel>0&&t.scrollTop()+t[0].clientHeight>=t[0].scrollHeight&&(this.scrollTopVel=0),this.scrollLeftVel<0?t.scrollLeft()<=0&&(this.scrollLeftVel=0):this.scrollLeftVel>0&&t.scrollLeft()+t[0].clientWidth>=t[0].scrollWidth&&(this.scrollLeftVel=0)},scrollIntervalFunc:function(){var t=this.scrollEl,e=this.scrollIntervalMs/1e3;this.scrollTopVel&&t.scrollTop(t.scrollTop()+this.scrollTopVel*e),this.scrollLeftVel&&t.scrollLeft(t.scrollLeft()+this.scrollLeftVel*e),this.constrainScrollVel(),this.scrollTopVel||this.scrollLeftVel||this.endAutoScroll()},endAutoScroll:function(){this.scrollIntervalId&&(clearInterval(this.scrollIntervalId),this.scrollIntervalId=null,this.handleScrollEnd())},handleDebouncedScroll:function(){this.scrollIntervalId||this.handleScrollEnd()},handleScrollEnd:function(){}});var re=ie.extend({component:null,origHit:null,hit:null,coordAdjust:null,constructor:function(t,e){ie.call(this,e),this.component=t},handleInteractionStart:function(t){var e,n,i,r=this.subjectEl;this.component.hitsNeeded(),this.computeScrollBounds(),t?(n={left:E(t),top:b(t)},i=n,r&&(e=h(r),i=R(i,e)),this.origHit=this.queryHit(i.left,i.top),r&&this.options.subjectCenter&&(this.origHit&&(e=x(this.origHit,e)||e),i=I(e)),this.coordAdjust=k(i,n)):(this.origHit=null,this.coordAdjust=null),ie.prototype.handleInteractionStart.apply(this,arguments)},handleDragStart:function(t){var e;ie.prototype.handleDragStart.apply(this,arguments),e=this.queryHit(E(t),b(t)),e&&this.handleHitOver(e)},handleDrag:function(t,e,n){var i;ie.prototype.handleDrag.apply(this,arguments),i=this.queryHit(E(n),b(n)),pt(i,this.hit)||(this.hit&&this.handleHitOut(),i&&this.handleHitOver(i))},handleDragEnd:function(){this.handleHitDone(),ie.prototype.handleDragEnd.apply(this,arguments)},handleHitOver:function(t){var e=pt(t,this.origHit);this.hit=t,this.trigger("hitOver",this.hit,e,this.origHit)},handleHitOut:function(){this.hit&&(this.trigger("hitOut",this.hit),this.handleHitDone(),this.hit=null)},handleHitDone:function(){this.hit&&this.trigger("hitDone",this.hit)},handleInteractionEnd:function(){ie.prototype.handleInteractionEnd.apply(this,arguments),this.origHit=null,this.hit=null,this.component.hitsNotNeeded()},handleScrollEnd:function(){ie.prototype.handleScrollEnd.apply(this,arguments),this.isDragging&&(this.component.releaseHits(),this.component.prepareHits())},queryHit:function(t,e){return this.coordAdjust&&(t+=this.coordAdjust.left,e+=this.coordAdjust.top),this.component.queryHit(t,e)}});Ot.touchMouseIgnoreWait=500;var se=ct.extend(te,Jt,{isTouching:!1,mouseIgnoreDepth:0,handleScrollProxy:null,bind:function(){var e=this;this.listenTo(t(document),{touchstart:this.handleTouchStart,touchcancel:this.handleTouchCancel,touchend:this.handleTouchEnd,mousedown:this.handleMouseDown,mousemove:this.handleMouseMove,mouseup:this.handleMouseUp,click:this.handleClick,selectstart:this.handleSelectStart,contextmenu:this.handleContextMenu}),window.addEventListener("touchmove",this.handleTouchMoveProxy=function(n){e.handleTouchMove(t.Event(n))},{passive:!1}),window.addEventListener("scroll",this.handleScrollProxy=function(n){e.handleScroll(t.Event(n))},!0)},unbind:function(){this.stopListeningTo(t(document)),window.removeEventListener("touchmove",this.handleTouchMoveProxy),window.removeEventListener("scroll",this.handleScrollProxy,!0)},handleTouchStart:function(t){this.stopTouch(t,!0),this.isTouching=!0,this.trigger("touchstart",t)},handleTouchMove:function(t){this.isTouching&&this.trigger("touchmove",t)},handleTouchCancel:function(t){this.isTouching&&(this.trigger("touchcancel",t),this.stopTouch(t))},handleTouchEnd:function(t){this.stopTouch(t)},handleMouseDown:function(t){this.shouldIgnoreMouse()||this.trigger("mousedown",t)},handleMouseMove:function(t){this.shouldIgnoreMouse()||this.trigger("mousemove",t)},handleMouseUp:function(t){this.shouldIgnoreMouse()||this.trigger("mouseup",t)},handleClick:function(t){this.shouldIgnoreMouse()||this.trigger("click",t)},handleSelectStart:function(t){this.trigger("selectstart",t)},handleContextMenu:function(t){this.trigger("contextmenu",t)},handleScroll:function(t){this.trigger("scroll",t)},stopTouch:function(t,e){this.isTouching&&(this.isTouching=!1,this.trigger("touchend",t),e||this.startTouchMouseIgnore())},startTouchMouseIgnore:function(){var t=this,e=Ot.touchMouseIgnoreWait;e&&(this.mouseIgnoreDepth++,setTimeout(function(){t.mouseIgnoreDepth--},e))},shouldIgnoreMouse:function(){return this.isTouching||Boolean(this.mouseIgnoreDepth)}});!function(){var t=null,e=0;se.get=function(){return t||(t=new se,t.bind()),t},se.needed=function(){se.get(),e++},se.unneeded=function(){e--,e||(t.unbind(),t=null)}}();var oe=ct.extend(te,{options:null,sourceEl:null,el:null,parentEl:null,top0:null,left0:null,y0:null,x0:null,topDelta:null,leftDelta:null,isFollowing:!1,isHidden:!1,isAnimating:!1,constructor:function(e,n){this.options=n=n||{},this.sourceEl=e,this.parentEl=n.parentEl?t(n.parentEl):e.parent()},start:function(e){this.isFollowing||(this.isFollowing=!0,this.y0=b(e),this.x0=E(e),this.topDelta=0,this.leftDelta=0,this.isHidden||this.updatePosition(),D(e)?this.listenTo(t(document),"touchmove",this.handleMove):this.listenTo(t(document),"mousemove",this.handleMove))},stop:function(e,n){function i(){r.isAnimating=!1,r.removeElement(),r.top0=r.left0=null,n&&n()}var r=this,s=this.options.revertDuration;this.isFollowing&&!this.isAnimating&&(this.isFollowing=!1,this.stopListeningTo(t(document)),e&&s&&!this.isHidden?(this.isAnimating=!0,this.el.animate({top:this.top0,left:this.left0},{duration:s,complete:i})):i())},getEl:function(){var t=this.el;return t||(t=this.el=this.sourceEl.clone().addClass(this.options.additionalClass||"").css({position:"absolute",visibility:"",display:this.isHidden?"none":"",margin:0,right:"auto",bottom:"auto",width:this.sourceEl.width(),height:this.sourceEl.height(),opacity:this.options.opacity||"",zIndex:this.options.zIndex}),t.addClass("fc-unselectable"),t.appendTo(this.parentEl)),t},removeElement:function(){this.el&&(this.el.remove(),this.el=null)},updatePosition:function(){var t,e;this.getEl(),null===this.top0&&(t=this.sourceEl.offset(),e=this.el.offsetParent().offset(),this.top0=t.top-e.top,this.left0=t.left-e.left),this.el.css({top:this.top0+this.topDelta,left:this.left0+this.leftDelta})},handleMove:function(t){this.topDelta=b(t)-this.y0,this.leftDelta=E(t)-this.x0,this.isHidden||this.updatePosition()},hide:function(){this.isHidden||(this.isHidden=!0,this.el&&this.el.hide())},show:function(){this.isHidden&&(this.isHidden=!1,this.updatePosition(),this.getEl().show())}}),le=Ot.Grid=ct.extend(te,{hasDayInteractions:!0,view:null,isRTL:null,start:null,end:null,el:null,elsByFill:null,eventTimeFormat:null,displayEventTime:null,displayEventEnd:null,minResizeDuration:null,largeUnit:null,dayClickListener:null,daySelectListener:null,segDragListener:null,segResizeListener:null,externalDragListener:null,constructor:function(t){this.view=t,this.isRTL=t.opt("isRTL"),this.elsByFill={},this.dayClickListener=this.buildDayClickListener(),this.daySelectListener=this.buildDaySelectListener()},computeEventTimeFormat:function(){return this.view.opt("smallTimeFormat")},computeDisplayEventTime:function(){return!0},computeDisplayEventEnd:function(){return!0},setRange:function(t){this.start=t.start.clone(),this.end=t.end.clone(),this.rangeUpdated(),this.processRangeOptions()},rangeUpdated:function(){},processRangeOptions:function(){var t,e,n=this.view;this.eventTimeFormat=n.opt("eventTimeFormat")||n.opt("timeFormat")||this.computeEventTimeFormat(),t=n.opt("displayEventTime"),null==t&&(t=this.computeDisplayEventTime()),e=n.opt("displayEventEnd"),null==e&&(e=this.computeDisplayEventEnd()),this.displayEventTime=t,this.displayEventEnd=e},spanToSegs:function(t){},diffDates:function(t,e){return this.largeUnit?O(t,e,this.largeUnit):z(t,e)},hitsNeededDepth:0,hitsNeeded:function(){this.hitsNeededDepth++||this.prepareHits()},hitsNotNeeded:function(){this.hitsNeededDepth&&!--this.hitsNeededDepth&&this.releaseHits()},prepareHits:function(){},releaseHits:function(){},queryHit:function(t,e){},getHitSpan:function(t){},getHitEl:function(t){},setElement:function(t){this.el=t,this.hasDayInteractions&&(T(t),this.bindDayHandler("touchstart",this.dayTouchStart),this.bindDayHandler("mousedown",this.dayMousedown)),this.bindSegHandlers(),this.bindGlobalHandlers()},bindDayHandler:function(e,n){var i=this;this.el.on(e,function(e){if(!t(e.target).is(i.segSelector+","+i.segSelector+" *,.fc-more,a[data-goto]"))return n.call(i,e)})},removeElement:function(){this.unbindGlobalHandlers(),this.clearDragListeners(),this.el.remove()},renderSkeleton:function(){},renderDates:function(){},unrenderDates:function(){},bindGlobalHandlers:function(){this.listenTo(t(document),{dragstart:this.externalDragStart,sortstart:this.externalDragStart})},unbindGlobalHandlers:function(){this.stopListeningTo(t(document))},dayMousedown:function(t){var e=this.view;e.isSelected||e.selectedEvent||(this.dayClickListener.startInteraction(t),e.opt("selectable")&&this.daySelectListener.startInteraction(t,{distance:e.opt("selectMinDistance")}))},dayTouchStart:function(t){var e,n=this.view;n.isSelected||n.selectedEvent||(e=n.opt("selectLongPressDelay"),null==e&&(e=n.opt("longPressDelay")),this.dayClickListener.startInteraction(t),n.opt("selectable")&&this.daySelectListener.startInteraction(t,{delay:e}))},buildDayClickListener:function(){var t,e=this,n=this.view,i=new re(this,{scroll:n.opt("dragScroll"),interactionStart:function(){t=i.origHit},hitOver:function(e,n,i){n||(t=null)},hitOut:function(){t=null},interactionEnd:function(i,r){!r&&t&&n.triggerDayClick(e.getHitSpan(t),e.getHitEl(t),i)}});return i.shouldCancelTouchScroll=!1,i.scrollAlwaysKills=!0,i},buildDaySelectListener:function(){var t,e=this,n=this.view,i=new re(this,{scroll:n.opt("dragScroll"),interactionStart:function(){t=null},dragStart:function(){n.unselect()},hitOver:function(n,i,r){r&&(t=e.computeSelection(e.getHitSpan(r),e.getHitSpan(n)),t?e.renderSelection(t):t===!1&&s())},hitOut:function(){t=null,e.unrenderSelection()},hitDone:function(){o()},interactionEnd:function(e,i){!i&&t&&n.reportSelection(t,e)}});return i},clearDragListeners:function(){this.dayClickListener.endInteraction(),this.daySelectListener.endInteraction(),this.segDragListener&&this.segDragListener.endInteraction(),this.segResizeListener&&this.segResizeListener.endInteraction(),this.externalDragListener&&this.externalDragListener.endInteraction()},renderEventLocationHelper:function(t,e){var n=this.fabricateHelperEvent(t,e);return this.renderHelper(n,e)},fabricateHelperEvent:function(t,e){var n=e?Z(e.event):{};return n.start=t.start.clone(),n.end=t.end?t.end.clone():null,n.allDay=null,this.view.calendar.normalizeEventDates(n),n.className=(n.className||[]).concat("fc-helper"),e||(n.editable=!1),n},renderHelper:function(t,e){},unrenderHelper:function(){},renderSelection:function(t){this.renderHighlight(t)},unrenderSelection:function(){this.unrenderHighlight()},computeSelection:function(t,e){var n=this.computeSelectionSpan(t,e);return!(n&&!this.view.calendar.isSelectionSpanAllowed(n))&&n},computeSelectionSpan:function(t,e){var n=[t.start,t.end,e.start,e.end];return n.sort(st),{start:n[0].clone(),end:n[3].clone()}},renderHighlight:function(t){this.renderFill("highlight",this.spanToSegs(t))},unrenderHighlight:function(){this.unrenderFill("highlight")},highlightSegClasses:function(){return["fc-highlight"]},renderBusinessHours:function(){},unrenderBusinessHours:function(){},getNowIndicatorUnit:function(){},renderNowIndicator:function(t){},unrenderNowIndicator:function(){},renderFill:function(t,e){},unrenderFill:function(t){var e=this.elsByFill[t];e&&(e.remove(),delete this.elsByFill[t])},renderFillSegEls:function(e,n){var i,r=this,s=this[e+"SegEl"],o="",l=[];if(n.length){for(i=0;i<n.length;i++)o+=this.fillSegHtml(e,n[i]);t(o).each(function(e,i){var o=n[e],a=t(i);s&&(a=s.call(r,o,a)),a&&(a=t(a),a.is(r.fillSegTag)&&(o.el=a,l.push(o)))})}return l},fillSegTag:"div",fillSegHtml:function(t,e){var n=this[t+"SegClasses"],i=this[t+"SegCss"],r=n?n.call(this,e):[],s=nt(i?i.call(this,e):{});return"<"+this.fillSegTag+(r.length?' class="'+r.join(" ")+'"':"")+(s?' style="'+s+'"':"")+" />"},getDayClasses:function(t,e){var n=this.view,i=n.calendar.getNow(),r=["fc-"+_t[t.day()]];return 1==n.intervalDuration.as("months")&&t.month()!=n.intervalStart.month()&&r.push("fc-other-month"),t.isSame(i,"day")?(r.push("fc-today"),e!==!0&&r.push(n.highlightStateClass)):t<i?r.push("fc-past"):r.push("fc-future"),r}});le.mixin({segSelector:".fc-event-container > *",mousedOverSeg:null,isDraggingSeg:!1,isResizingSeg:!1,isDraggingExternal:!1,segs:null,renderEvents:function(t){var e,n=[],i=[];for(e=0;e<t.length;e++)(yt(t[e])?n:i).push(t[e]);this.segs=[].concat(this.renderBgEvents(n),this.renderFgEvents(i))},renderBgEvents:function(t){var e=this.eventsToSegs(t);return this.renderBgSegs(e)||e},renderFgEvents:function(t){var e=this.eventsToSegs(t);return this.renderFgSegs(e)||e},unrenderEvents:function(){this.handleSegMouseout(),this.clearDragListeners(),this.unrenderFgSegs(),this.unrenderBgSegs(),this.segs=null},getEventSegs:function(){return this.segs||[]},renderFgSegs:function(t){},unrenderFgSegs:function(){},renderFgSegEls:function(e,n){var i,r=this.view,s="",o=[];if(e.length){for(i=0;i<e.length;i++)s+=this.fgSegHtml(e[i],n);t(s).each(function(n,i){var s=e[n],l=r.resolveEventEl(s.event,t(i));l&&(l.data("fc-seg",s),s.el=l,o.push(s))})}return o},fgSegHtml:function(t,e){},renderBgSegs:function(t){return this.renderFill("bgEvent",t)},unrenderBgSegs:function(){this.unrenderFill("bgEvent")},bgEventSegEl:function(t,e){return this.view.resolveEventEl(t.event,e)},bgEventSegClasses:function(t){var e=t.event,n=e.source||{};return["fc-bgevent"].concat(e.className,n.className||[])},bgEventSegCss:function(t){return{"background-color":this.getSegSkinCss(t)["background-color"]}},businessHoursSegClasses:function(t){return["fc-nonbusiness","fc-bgevent"]},buildBusinessHourSegs:function(t,e){return this.eventsToSegs(this.buildBusinessHourEvents(t,e))},buildBusinessHourEvents:function(e,n){var i,r=this.view.calendar;return null==n&&(n=r.options.businessHours),i=r.computeBusinessHourEvents(e,n),!i.length&&n&&(i=[t.extend({},we,{start:this.view.end,end:this.view.end,dow:null})]),i},bindSegHandlers:function(){this.bindSegHandlersToEl(this.el)},bindSegHandlersToEl:function(t){this.bindSegHandlerToEl(t,"touchstart",this.handleSegTouchStart),this.bindSegHandlerToEl(t,"mouseenter",this.handleSegMouseover),this.bindSegHandlerToEl(t,"mouseleave",this.handleSegMouseout),this.bindSegHandlerToEl(t,"mousedown",this.handleSegMousedown),this.bindSegHandlerToEl(t,"click",this.handleSegClick)},bindSegHandlerToEl:function(e,n,i){var r=this;e.on(n,this.segSelector,function(e){var n=t(this).data("fc-seg");if(n&&!r.isDraggingSeg&&!r.isResizingSeg)return i.call(r,n,e)})},handleSegClick:function(t,e){var n=this.view.publiclyTrigger("eventClick",t.el[0],t.event,e);n===!1&&e.preventDefault()},handleSegMouseover:function(t,e){se.get().shouldIgnoreMouse()||this.mousedOverSeg||(this.mousedOverSeg=t,this.view.isEventResizable(t.event)&&t.el.addClass("fc-allow-mouse-resize"),this.view.publiclyTrigger("eventMouseover",t.el[0],t.event,e))},handleSegMouseout:function(t,e){e=e||{},this.mousedOverSeg&&(t=t||this.mousedOverSeg,this.mousedOverSeg=null,this.view.isEventResizable(t.event)&&t.el.removeClass("fc-allow-mouse-resize"),this.view.publiclyTrigger("eventMouseout",t.el[0],t.event,e))},handleSegMousedown:function(t,e){var n=this.startSegResize(t,e,{distance:5});!n&&this.view.isEventDraggable(t.event)&&this.buildSegDragListener(t).startInteraction(e,{distance:5})},handleSegTouchStart:function(t,e){var n,i,r=this.view,s=t.event,o=r.isEventSelected(s),l=r.isEventDraggable(s),a=r.isEventResizable(s),u=!1;o&&a&&(u=this.startSegResize(t,e)),u||!l&&!a||(i=r.opt("eventLongPressDelay"),null==i&&(i=r.opt("longPressDelay")),n=l?this.buildSegDragListener(t):this.buildSegSelectListener(t),n.startInteraction(e,{delay:o?0:i}))},startSegResize:function(e,n,i){return!!t(n.target).is(".fc-resizer")&&(this.buildSegResizeListener(e,t(n.target).is(".fc-start-resizer")).startInteraction(n,i),!0)},buildSegDragListener:function(t){var e,n,i,r=this,l=this.view,a=l.calendar,u=t.el,c=t.event;if(this.segDragListener)return this.segDragListener;var d=this.segDragListener=new re(l,{scroll:l.opt("dragScroll"),subjectEl:u,subjectCenter:!0,interactionStart:function(i){t.component=r,e=!1,n=new oe(t.el,{additionalClass:"fc-dragging",parentEl:l.el,opacity:d.isTouch?null:l.opt("dragOpacity"),revertDuration:l.opt("dragRevertDuration"),zIndex:2}),n.hide(),n.start(i)},dragStart:function(n){d.isTouch&&!l.isEventSelected(c)&&l.selectEvent(c),e=!0,r.handleSegMouseout(t,n),r.segDragStart(t,n),l.hideEvent(c)},hitOver:function(e,o,u){var h;t.hit&&(u=t.hit),i=r.computeEventDrop(u.component.getHitSpan(u),e.component.getHitSpan(e),c),i&&!a.isEventSpanAllowed(r.eventToSpan(i),c)&&(s(),i=null),i&&(h=l.renderDrag(i,t))?(h.addClass("fc-dragging"),d.isTouch||r.applyDragOpacity(h),n.hide()):n.show(),o&&(i=null)},hitOut:function(){l.unrenderDrag(),n.show(),i=null},hitDone:function(){o()},interactionEnd:function(s){delete t.component,n.stop(!i,function(){e&&(l.unrenderDrag(),r.segDragStop(t,s)),i?l.reportSegDrop(t,i,r.largeUnit,u,s):l.showEvent(c)}),r.segDragListener=null}});return d},buildSegSelectListener:function(t){var e=this,n=this.view,i=t.event;if(this.segDragListener)return this.segDragListener;var r=this.segDragListener=new ie({dragStart:function(t){r.isTouch&&!n.isEventSelected(i)&&n.selectEvent(i)},interactionEnd:function(t){e.segDragListener=null}});return r},segDragStart:function(t,e){this.isDraggingSeg=!0,this.view.publiclyTrigger("eventDragStart",t.el[0],t.event,e,{})},segDragStop:function(t,e){this.isDraggingSeg=!1,this.view.publiclyTrigger("eventDragStop",t.el[0],t.event,e,{})},computeEventDrop:function(t,e,n){var i,r,s=this.view.calendar,o=t.start,l=e.start;return o.hasTime()===l.hasTime()?(i=this.diffDates(l,o),n.allDay&&W(i)?(r={start:n.start.clone(),end:s.getEventEnd(n),allDay:!1},s.normalizeEventTimes(r)):r=mt(n),r.start.add(i),r.end&&r.end.add(i)):r={start:l.clone(),end:null,allDay:!l.hasTime()},r},applyDragOpacity:function(t){var e=this.view.opt("dragOpacity");null!=e&&t.css("opacity",e)},externalDragStart:function(e,n){var i,r,s=this.view;s.opt("droppable")&&(i=t((n?n.item:null)||e.target),r=s.opt("dropAccept"),(t.isFunction(r)?r.call(i[0],i):i.is(r))&&(this.isDraggingExternal||this.listenToExternalDrag(i,e,n)))},listenToExternalDrag:function(t,e,n){var i,r=this,l=this.view.calendar,a=Dt(t),u=r.externalDragListener=new re(this,{interactionStart:function(){r.isDraggingExternal=!0},hitOver:function(t){i=r.computeExternalDrop(t.component.getHitSpan(t),a),i&&!l.isExternalSpanAllowed(r.eventToSpan(i),i,a.eventProps)&&(s(),i=null),i&&r.renderDrag(i)},hitOut:function(){i=null},hitDone:function(){o(),r.unrenderDrag()},interactionEnd:function(e){i&&r.view.reportExternalDrop(a,i,t,e,n),r.isDraggingExternal=!1,r.externalDragListener=null}});u.startDrag(e)},computeExternalDrop:function(t,e){var n=this.view.calendar,i={start:n.applyTimezone(t.start),end:null};return e.startTime&&!i.start.hasTime()&&i.start.time(e.startTime),e.duration&&(i.end=i.start.clone().add(e.duration)),i},renderDrag:function(t,e){},unrenderDrag:function(){},buildSegResizeListener:function(t,e){var n,i,r=this,l=this.view,a=l.calendar,u=t.el,c=t.event,d=a.getEventEnd(c),h=this.segResizeListener=new re(this,{scroll:l.opt("dragScroll"),subjectEl:u,interactionStart:function(){n=!1},dragStart:function(e){n=!0,r.handleSegMouseout(t,e),r.segResizeStart(t,e)},hitOver:function(n,o,u){var h=r.getHitSpan(u),f=r.getHitSpan(n);i=e?r.computeEventStartResize(h,f,c):r.computeEventEndResize(h,f,c),i&&(a.isEventSpanAllowed(r.eventToSpan(i),c)?i.start.isSame(c.start.clone().stripZone())&&i.end.isSame(d.clone().stripZone())&&(i=null):(s(),i=null)),i&&(l.hideEvent(c),r.renderEventResize(i,t))},hitOut:function(){i=null,l.showEvent(c)},hitDone:function(){r.unrenderEventResize(),o()},interactionEnd:function(e){n&&r.segResizeStop(t,e),i?l.reportSegResize(t,i,r.largeUnit,u,e):l.showEvent(c),r.segResizeListener=null}});return h},segResizeStart:function(t,e){this.isResizingSeg=!0,this.view.publiclyTrigger("eventResizeStart",t.el[0],t.event,e,{})},segResizeStop:function(t,e){this.isResizingSeg=!1,this.view.publiclyTrigger("eventResizeStop",t.el[0],t.event,e,{})},computeEventStartResize:function(t,e,n){return this.computeEventResize("start",t,e,n)},computeEventEndResize:function(t,e,n){return this.computeEventResize("end",t,e,n)},computeEventResize:function(t,e,n,i){var r,s,o=this.view.calendar,l=this.diffDates(n[t],e[t]);return r={start:i.start.clone(),end:o.getEventEnd(i),allDay:i.allDay},r.allDay&&W(l)&&(r.allDay=!1,o.normalizeEventTimes(r)),r[t].add(l),r.start.isBefore(r.end)||(s=this.minResizeDuration||(i.allDay?o.defaultAllDayEventDuration:o.defaultTimedEventDuration),"start"==t?r.start=r.end.clone().subtract(s):r.end=r.start.clone().add(s)),
+r},renderEventResize:function(t,e){},unrenderEventResize:function(){},getEventTimeText:function(t,e,n){return null==e&&(e=this.eventTimeFormat),null==n&&(n=this.displayEventEnd),this.displayEventTime&&t.start.hasTime()?n&&t.end?this.view.formatRange(t,e):t.start.format(e):""},getSegClasses:function(t,e,n){var i=this.view,r=["fc-event",t.isStart?"fc-start":"fc-not-start",t.isEnd?"fc-end":"fc-not-end"].concat(this.getSegCustomClasses(t));return e&&r.push("fc-draggable"),n&&r.push("fc-resizable"),i.isEventSelected(t.event)&&r.push("fc-selected"),r},getSegCustomClasses:function(t){var e=t.event;return[].concat(e.className,e.source?e.source.className:[])},getSegSkinCss:function(t){return{"background-color":this.getSegBackgroundColor(t),"border-color":this.getSegBorderColor(t),color:this.getSegTextColor(t)}},getSegBackgroundColor:function(t){return t.event.backgroundColor||t.event.color||this.getSegDefaultBackgroundColor(t)},getSegDefaultBackgroundColor:function(t){var e=t.event.source||{};return e.backgroundColor||e.color||this.view.opt("eventBackgroundColor")||this.view.opt("eventColor")},getSegBorderColor:function(t){return t.event.borderColor||t.event.color||this.getSegDefaultBorderColor(t)},getSegDefaultBorderColor:function(t){var e=t.event.source||{};return e.borderColor||e.color||this.view.opt("eventBorderColor")||this.view.opt("eventColor")},getSegTextColor:function(t){return t.event.textColor||this.getSegDefaultTextColor(t)},getSegDefaultTextColor:function(t){var e=t.event.source||{};return e.textColor||this.view.opt("eventTextColor")},eventToSegs:function(t){return this.eventsToSegs([t])},eventToSpan:function(t){return this.eventToSpans(t)[0]},eventToSpans:function(t){var e=this.eventToRange(t);return this.eventRangeToSpans(e,t)},eventsToSegs:function(e,n){var i=this,r=Et(e),s=[];return t.each(r,function(t,e){var r,o=[];for(r=0;r<e.length;r++)o.push(i.eventToRange(e[r]));if(St(e[0]))for(o=i.invertRanges(o),r=0;r<o.length;r++)s.push.apply(s,i.eventRangeToSegs(o[r],e[0],n));else for(r=0;r<o.length;r++)s.push.apply(s,i.eventRangeToSegs(o[r],e[r],n))}),s},eventToRange:function(t){var e=this.view.calendar,n=t.start.clone().stripZone(),i=(t.end?t.end.clone():e.getDefaultEventEnd(null!=t.allDay?t.allDay:!t.start.hasTime(),t.start)).stripZone();return e.localizeMoment(n),e.localizeMoment(i),{start:n,end:i}},eventRangeToSegs:function(t,e,n){var i,r=this.eventRangeToSpans(t,e),s=[];for(i=0;i<r.length;i++)s.push.apply(s,this.eventSpanToSegs(r[i],e,n));return s},eventRangeToSpans:function(e,n){return[t.extend({},e)]},eventSpanToSegs:function(t,e,n){var i,r,s=n?n(t):this.spanToSegs(t);for(i=0;i<s.length;i++)r=s[i],r.event=e,r.eventStartMS=+t.start,r.eventDurationMS=t.end-t.start;return s},invertRanges:function(t){var e,n,i=this.view,r=i.start.clone(),s=i.end.clone(),o=[],l=r;for(t.sort(bt),e=0;e<t.length;e++)n=t[e],n.start>l&&o.push({start:l,end:n.start}),l=n.end;return l<s&&o.push({start:l,end:s}),o},sortEventSegs:function(t){t.sort(lt(this,"compareEventSegs"))},compareEventSegs:function(t,e){return t.eventStartMS-e.eventStartMS||e.eventDurationMS-t.eventDurationMS||e.event.allDay-t.event.allDay||M(t.event,e.event,this.view.eventOrderSpecs)}}),Ot.pluckEventDateProps=mt,Ot.isBgEvent=yt,Ot.dataAttrPrefix="";var ae=Ot.DayTableMixin={breakOnWeeks:!1,dayDates:null,dayIndices:null,daysPerRow:null,rowCnt:null,colCnt:null,colHeadFormat:null,updateDayTable:function(){for(var t,e,n,i=this.view,r=this.start.clone(),s=-1,o=[],l=[];r.isBefore(this.end);)i.isHiddenDay(r)?o.push(s+.5):(s++,o.push(s),l.push(r.clone())),r.add(1,"days");if(this.breakOnWeeks){for(e=l[0].day(),t=1;t<l.length&&l[t].day()!=e;t++);n=Math.ceil(l.length/t)}else n=1,t=l.length;this.dayDates=l,this.dayIndices=o,this.daysPerRow=t,this.rowCnt=n,this.updateDayTableCols()},updateDayTableCols:function(){this.colCnt=this.computeColCnt(),this.colHeadFormat=this.view.opt("columnFormat")||this.computeColHeadFormat()},computeColCnt:function(){return this.daysPerRow},getCellDate:function(t,e){return this.dayDates[this.getCellDayIndex(t,e)].clone()},getCellRange:function(t,e){var n=this.getCellDate(t,e),i=n.clone().add(1,"days");return{start:n,end:i}},getCellDayIndex:function(t,e){return t*this.daysPerRow+this.getColDayIndex(e)},getColDayIndex:function(t){return this.isRTL?this.colCnt-1-t:t},getDateDayIndex:function(t){var e=this.dayIndices,n=t.diff(this.start,"days");return n<0?e[0]-1:n>=e.length?e[e.length-1]+1:e[n]},computeColHeadFormat:function(){return this.rowCnt>1||this.colCnt>10?"ddd":this.colCnt>1?this.view.opt("dayOfMonthFormat"):"dddd"},sliceRangeByRow:function(t){var e,n,i,r,s,o=this.daysPerRow,l=this.view.computeDayRange(t),a=this.getDateDayIndex(l.start),u=this.getDateDayIndex(l.end.clone().subtract(1,"days")),c=[];for(e=0;e<this.rowCnt;e++)n=e*o,i=n+o-1,r=Math.max(a,n),s=Math.min(u,i),r=Math.ceil(r),s=Math.floor(s),r<=s&&c.push({row:e,firstRowDayIndex:r-n,lastRowDayIndex:s-n,isStart:r===a,isEnd:s===u});return c},sliceRangeByDay:function(t){var e,n,i,r,s,o,l=this.daysPerRow,a=this.view.computeDayRange(t),u=this.getDateDayIndex(a.start),c=this.getDateDayIndex(a.end.clone().subtract(1,"days")),d=[];for(e=0;e<this.rowCnt;e++)for(n=e*l,i=n+l-1,r=n;r<=i;r++)s=Math.max(u,r),o=Math.min(c,r),s=Math.ceil(s),o=Math.floor(o),s<=o&&d.push({row:e,firstRowDayIndex:s-n,lastRowDayIndex:o-n,isStart:s===u,isEnd:o===c});return d},renderHeadHtml:function(){var t=this.view;return'<div class="fc-row '+t.widgetHeaderClass+'"><table><thead>'+this.renderHeadTrHtml()+"</thead></table></div>"},renderHeadIntroHtml:function(){return this.renderIntroHtml()},renderHeadTrHtml:function(){return"<tr>"+(this.isRTL?"":this.renderHeadIntroHtml())+this.renderHeadDateCellsHtml()+(this.isRTL?this.renderHeadIntroHtml():"")+"</tr>"},renderHeadDateCellsHtml:function(){var t,e,n=[];for(t=0;t<this.colCnt;t++)e=this.getCellDate(0,t),n.push(this.renderHeadDateCellHtml(e));return n.join("")},renderHeadDateCellHtml:function(t,e,n){var i=this.view,r=["fc-day-header",i.widgetHeaderClass];return 1===this.rowCnt?r=r.concat(this.getDayClasses(t,!0)):r.push("fc-"+_t[t.day()]),'<th class="'+r.join(" ")+'"'+(1===this.rowCnt?' data-date="'+t.format("YYYY-MM-DD")+'"':"")+(e>1?' colspan="'+e+'"':"")+(n?" "+n:"")+">"+i.buildGotoAnchorHtml({date:t,forceOff:this.rowCnt>1||1===this.colCnt},tt(t.format(this.colHeadFormat)))+"</th>"},renderBgTrHtml:function(t){return"<tr>"+(this.isRTL?"":this.renderBgIntroHtml(t))+this.renderBgCellsHtml(t)+(this.isRTL?this.renderBgIntroHtml(t):"")+"</tr>"},renderBgIntroHtml:function(t){return this.renderIntroHtml()},renderBgCellsHtml:function(t){var e,n,i=[];for(e=0;e<this.colCnt;e++)n=this.getCellDate(t,e),i.push(this.renderBgCellHtml(n));return i.join("")},renderBgCellHtml:function(t,e){var n=this.view,i=this.getDayClasses(t);return i.unshift("fc-day",n.widgetContentClass),'<td class="'+i.join(" ")+'" data-date="'+t.format("YYYY-MM-DD")+'"'+(e?" "+e:"")+"></td>"},renderIntroHtml:function(){},bookendCells:function(t){var e=this.renderIntroHtml();e&&(this.isRTL?t.append(e):t.prepend(e))}},ue=Ot.DayGrid=le.extend(ae,{numbersVisible:!1,bottomCoordPadding:0,rowEls:null,cellEls:null,helperEls:null,rowCoordCache:null,colCoordCache:null,renderDates:function(t){var e,n,i=this.view,r=this.rowCnt,s=this.colCnt,o="";for(e=0;e<r;e++)o+=this.renderDayRowHtml(e,t);for(this.el.html(o),this.rowEls=this.el.find(".fc-row"),this.cellEls=this.el.find(".fc-day"),this.rowCoordCache=new ne({els:this.rowEls,isVertical:!0}),this.colCoordCache=new ne({els:this.cellEls.slice(0,this.colCnt),isHorizontal:!0}),e=0;e<r;e++)for(n=0;n<s;n++)i.publiclyTrigger("dayRender",null,this.getCellDate(e,n),this.getCellEl(e,n))},unrenderDates:function(){this.removeSegPopover()},renderBusinessHours:function(){var t=this.buildBusinessHourSegs(!0);this.renderFill("businessHours",t,"bgevent")},unrenderBusinessHours:function(){this.unrenderFill("businessHours")},renderDayRowHtml:function(t,e){var n=this.view,i=["fc-row","fc-week",n.widgetContentClass];return e&&i.push("fc-rigid"),'<div class="'+i.join(" ")+'"><div class="fc-bg"><table>'+this.renderBgTrHtml(t)+'</table></div><div class="fc-content-skeleton"><table>'+(this.numbersVisible?"<thead>"+this.renderNumberTrHtml(t)+"</thead>":"")+"</table></div></div>"},renderNumberTrHtml:function(t){return"<tr>"+(this.isRTL?"":this.renderNumberIntroHtml(t))+this.renderNumberCellsHtml(t)+(this.isRTL?this.renderNumberIntroHtml(t):"")+"</tr>"},renderNumberIntroHtml:function(t){return this.renderIntroHtml()},renderNumberCellsHtml:function(t){var e,n,i=[];for(e=0;e<this.colCnt;e++)n=this.getCellDate(t,e),i.push(this.renderNumberCellHtml(n));return i.join("")},renderNumberCellHtml:function(t){var e,n,i="";return this.view.dayNumbersVisible||this.view.cellWeekNumbersVisible?(e=this.getDayClasses(t),e.unshift("fc-day-top"),this.view.cellWeekNumbersVisible&&(n="ISO"===t._locale._fullCalendar_weekCalc?1:t._locale.firstDayOfWeek()),i+='<td class="'+e.join(" ")+'" data-date="'+t.format()+'">',this.view.cellWeekNumbersVisible&&t.day()==n&&(i+=this.view.buildGotoAnchorHtml({date:t,type:"week"},{class:"fc-week-number"},t.format("w"))),this.view.dayNumbersVisible&&(i+=this.view.buildGotoAnchorHtml(t,{class:"fc-day-number"},t.date())),i+="</td>"):"<td/>"},computeEventTimeFormat:function(){return this.view.opt("extraSmallTimeFormat")},computeDisplayEventEnd:function(){return 1==this.colCnt},rangeUpdated:function(){this.updateDayTable()},spanToSegs:function(t){var e,n,i=this.sliceRangeByRow(t);for(e=0;e<i.length;e++)n=i[e],this.isRTL?(n.leftCol=this.daysPerRow-1-n.lastRowDayIndex,n.rightCol=this.daysPerRow-1-n.firstRowDayIndex):(n.leftCol=n.firstRowDayIndex,n.rightCol=n.lastRowDayIndex);return i},prepareHits:function(){this.colCoordCache.build(),this.rowCoordCache.build(),this.rowCoordCache.bottoms[this.rowCnt-1]+=this.bottomCoordPadding},releaseHits:function(){this.colCoordCache.clear(),this.rowCoordCache.clear()},queryHit:function(t,e){if(this.colCoordCache.isLeftInBounds(t)&&this.rowCoordCache.isTopInBounds(e)){var n=this.colCoordCache.getHorizontalIndex(t),i=this.rowCoordCache.getVerticalIndex(e);if(null!=i&&null!=n)return this.getCellHit(i,n)}},getHitSpan:function(t){return this.getCellRange(t.row,t.col)},getHitEl:function(t){return this.getCellEl(t.row,t.col)},getCellHit:function(t,e){return{row:t,col:e,component:this,left:this.colCoordCache.getLeftOffset(e),right:this.colCoordCache.getRightOffset(e),top:this.rowCoordCache.getTopOffset(t),bottom:this.rowCoordCache.getBottomOffset(t)}},getCellEl:function(t,e){return this.cellEls.eq(t*this.colCnt+e)},renderDrag:function(t,e){if(this.renderHighlight(this.eventToSpan(t)),e&&e.component!==this)return this.renderEventLocationHelper(t,e)},unrenderDrag:function(){this.unrenderHighlight(),this.unrenderHelper()},renderEventResize:function(t,e){return this.renderHighlight(this.eventToSpan(t)),this.renderEventLocationHelper(t,e)},unrenderEventResize:function(){this.unrenderHighlight(),this.unrenderHelper()},renderHelper:function(e,n){var i,r=[],s=this.eventToSegs(e);return s=this.renderFgSegEls(s),i=this.renderSegRows(s),this.rowEls.each(function(e,s){var o,l=t(s),a=t('<div class="fc-helper-skeleton"><table/></div>');o=n&&n.row===e?n.el.position().top:l.find(".fc-content-skeleton tbody").position().top,a.css("top",o).find("table").append(i[e].tbodyEl),l.append(a),r.push(a[0])}),this.helperEls=t(r)},unrenderHelper:function(){this.helperEls&&(this.helperEls.remove(),this.helperEls=null)},fillSegTag:"td",renderFill:function(e,n,i){var r,s,o,l=[];for(n=this.renderFillSegEls(e,n),r=0;r<n.length;r++)s=n[r],o=this.renderFillRow(e,s,i),this.rowEls.eq(s.row).append(o),l.push(o[0]);return this.elsByFill[e]=t(l),n},renderFillRow:function(e,n,i){var r,s,o=this.colCnt,l=n.leftCol,a=n.rightCol+1;return i=i||e.toLowerCase(),r=t('<div class="fc-'+i+'-skeleton"><table><tr/></table></div>'),s=r.find("tr"),l>0&&s.append('<td colspan="'+l+'"/>'),s.append(n.el.attr("colspan",a-l)),a<o&&s.append('<td colspan="'+(o-a)+'"/>'),this.bookendCells(s),r}});ue.mixin({rowStructs:null,unrenderEvents:function(){this.removeSegPopover(),le.prototype.unrenderEvents.apply(this,arguments)},getEventSegs:function(){return le.prototype.getEventSegs.call(this).concat(this.popoverSegs||[])},renderBgSegs:function(e){var n=t.grep(e,function(t){return t.event.allDay});return le.prototype.renderBgSegs.call(this,n)},renderFgSegs:function(e){var n;return e=this.renderFgSegEls(e),n=this.rowStructs=this.renderSegRows(e),this.rowEls.each(function(e,i){t(i).find(".fc-content-skeleton > table").append(n[e].tbodyEl)}),e},unrenderFgSegs:function(){for(var t,e=this.rowStructs||[];t=e.pop();)t.tbodyEl.remove();this.rowStructs=null},renderSegRows:function(t){var e,n,i=[];for(e=this.groupSegRows(t),n=0;n<e.length;n++)i.push(this.renderSegRow(n,e[n]));return i},fgSegHtml:function(t,e){var n,i,r=this.view,s=t.event,o=r.isEventDraggable(s),l=!e&&s.allDay&&t.isStart&&r.isEventResizableFromStart(s),a=!e&&s.allDay&&t.isEnd&&r.isEventResizableFromEnd(s),u=this.getSegClasses(t,o,l||a),c=nt(this.getSegSkinCss(t)),d="";return u.unshift("fc-day-grid-event","fc-h-event"),t.isStart&&(n=this.getEventTimeText(s),n&&(d='<span class="fc-time">'+tt(n)+"</span>")),i='<span class="fc-title">'+(tt(s.title||"")||"&nbsp;")+"</span>",'<a class="'+u.join(" ")+'"'+(s.url?' href="'+tt(s.url)+'"':"")+(c?' style="'+c+'"':"")+'><div class="fc-content">'+(this.isRTL?i+" "+d:d+" "+i)+"</div>"+(l?'<div class="fc-resizer fc-start-resizer" />':"")+(a?'<div class="fc-resizer fc-end-resizer" />':"")+"</a>"},renderSegRow:function(e,n){function i(e){for(;o<e;)c=(m[r-1]||[])[o],c?c.attr("rowspan",parseInt(c.attr("rowspan")||1,10)+1):(c=t("<td/>"),l.append(c)),v[r][o]=c,m[r][o]=c,o++}var r,s,o,l,a,u,c,d=this.colCnt,h=this.buildSegLevels(n),f=Math.max(1,h.length),g=t("<tbody/>"),p=[],v=[],m=[];for(r=0;r<f;r++){if(s=h[r],o=0,l=t("<tr/>"),p.push([]),v.push([]),m.push([]),s)for(a=0;a<s.length;a++){for(u=s[a],i(u.leftCol),c=t('<td class="fc-event-container"/>').append(u.el),u.leftCol!=u.rightCol?c.attr("colspan",u.rightCol-u.leftCol+1):m[r][o]=c;o<=u.rightCol;)v[r][o]=c,p[r][o]=u,o++;l.append(c)}i(d),this.bookendCells(l),g.append(l)}return{row:e,tbodyEl:g,cellMatrix:v,segMatrix:p,segLevels:h,segs:n}},buildSegLevels:function(t){var e,n,i,r=[];for(this.sortEventSegs(t),e=0;e<t.length;e++){for(n=t[e],i=0;i<r.length&&Tt(n,r[i]);i++);n.level=i,(r[i]||(r[i]=[])).push(n)}for(i=0;i<r.length;i++)r[i].sort(Ct);return r},groupSegRows:function(t){var e,n=[];for(e=0;e<this.rowCnt;e++)n.push([]);for(e=0;e<t.length;e++)n[t[e].row].push(t[e]);return n}}),ue.mixin({segPopover:null,popoverSegs:null,removeSegPopover:function(){this.segPopover&&this.segPopover.hide()},limitRows:function(t){var e,n,i=this.rowStructs||[];for(e=0;e<i.length;e++)this.unlimitRow(e),n=!!t&&("number"==typeof t?t:this.computeRowLevelLimit(e)),n!==!1&&this.limitRow(e,n)},computeRowLevelLimit:function(e){function n(e,n){s=Math.max(s,t(n).outerHeight())}var i,r,s,o=this.rowEls.eq(e),l=o.height(),a=this.rowStructs[e].tbodyEl.children();for(i=0;i<a.length;i++)if(r=a.eq(i).removeClass("fc-limited"),s=0,r.find("> td > :first-child").each(n),r.position().top+s>l)return i;return!1},limitRow:function(e,n){function i(i){for(;b<i;)u=S.getCellSegs(e,b,n),u.length&&(h=s[n-1][b],y=S.renderMoreLink(e,b,u),m=t("<div/>").append(y),h.append(m),E.push(m[0])),b++}var r,s,o,l,a,u,c,d,h,f,g,p,v,m,y,S=this,w=this.rowStructs[e],E=[],b=0;if(n&&n<w.segLevels.length){for(r=w.segLevels[n-1],s=w.cellMatrix,o=w.tbodyEl.children().slice(n).addClass("fc-limited").get(),l=0;l<r.length;l++){for(a=r[l],i(a.leftCol),d=[],c=0;b<=a.rightCol;)u=this.getCellSegs(e,b,n),d.push(u),c+=u.length,b++;if(c){for(h=s[n-1][a.leftCol],f=h.attr("rowspan")||1,g=[],p=0;p<d.length;p++)v=t('<td class="fc-more-cell"/>').attr("rowspan",f),u=d[p],y=this.renderMoreLink(e,a.leftCol+p,[a].concat(u)),m=t("<div/>").append(y),v.append(m),g.push(v[0]),E.push(v[0]);h.addClass("fc-limited").after(t(g)),o.push(h[0])}}i(this.colCnt),w.moreEls=t(E),w.limitedEls=t(o)}},unlimitRow:function(t){var e=this.rowStructs[t];e.moreEls&&(e.moreEls.remove(),e.moreEls=null),e.limitedEls&&(e.limitedEls.removeClass("fc-limited"),e.limitedEls=null)},renderMoreLink:function(e,n,i){var r=this,s=this.view;return t('<a class="fc-more"/>').text(this.getMoreLinkText(i.length)).on("click",function(o){var l=s.opt("eventLimitClick"),a=r.getCellDate(e,n),u=t(this),c=r.getCellEl(e,n),d=r.getCellSegs(e,n),h=r.resliceDaySegs(d,a),f=r.resliceDaySegs(i,a);"function"==typeof l&&(l=s.publiclyTrigger("eventLimitClick",null,{date:a,dayEl:c,moreEl:u,segs:h,hiddenSegs:f},o)),"popover"===l?r.showSegPopover(e,n,u,h):"string"==typeof l&&s.calendar.zoomTo(a,l)})},showSegPopover:function(t,e,n,i){var r,s,o=this,l=this.view,a=n.parent();r=1==this.rowCnt?l.el:this.rowEls.eq(t),s={className:"fc-more-popover",content:this.renderSegPopoverContent(t,e,i),parentEl:this.view.el,top:r.offset().top,autoHide:!0,viewportConstrain:l.opt("popoverViewportConstrain"),hide:function(){if(o.popoverSegs)for(var t,e=0;e<o.popoverSegs.length;++e)t=o.popoverSegs[e],l.publiclyTrigger("eventDestroy",t.event,t.event,t.el);o.segPopover.removeElement(),o.segPopover=null,o.popoverSegs=null}},this.isRTL?s.right=a.offset().left+a.outerWidth()+1:s.left=a.offset().left-1,this.segPopover=new ee(s),this.segPopover.show(),this.bindSegHandlersToEl(this.segPopover.el)},renderSegPopoverContent:function(e,n,i){var r,s=this.view,o=s.opt("theme"),l=this.getCellDate(e,n).format(s.opt("dayPopoverFormat")),a=t('<div class="fc-header '+s.widgetHeaderClass+'"><span class="fc-close '+(o?"ui-icon ui-icon-closethick":"fc-icon fc-icon-x")+'"></span><span class="fc-title">'+tt(l)+'</span><div class="fc-clear"/></div><div class="fc-body '+s.widgetContentClass+'"><div class="fc-event-container"></div></div>'),u=a.find(".fc-event-container");for(i=this.renderFgSegEls(i,!0),this.popoverSegs=i,r=0;r<i.length;r++)this.hitsNeeded(),i[r].hit=this.getCellHit(e,n),this.hitsNotNeeded(),u.append(i[r].el);return a},resliceDaySegs:function(e,n){var i=t.map(e,function(t){return t.event}),r=n.clone(),s=r.clone().add(1,"days"),o={start:r,end:s};return e=this.eventsToSegs(i,function(t){var e=F(t,o);return e?[e]:[]}),this.sortEventSegs(e),e},getMoreLinkText:function(t){var e=this.view.opt("eventLimitText");return"function"==typeof e?e(t):"+"+t+" "+e},getCellSegs:function(t,e,n){for(var i,r=this.rowStructs[t].segMatrix,s=n||0,o=[];s<r.length;)i=r[s][e],i&&o.push(i),s++;return o}});var ce=Ot.TimeGrid=le.extend(ae,{slotDuration:null,snapDuration:null,snapsPerSlot:null,minTime:null,maxTime:null,labelFormat:null,labelInterval:null,colEls:null,slatContainerEl:null,slatEls:null,nowIndicatorEls:null,colCoordCache:null,slatCoordCache:null,constructor:function(){le.apply(this,arguments),this.processOptions()},renderDates:function(){this.el.html(this.renderHtml()),this.colEls=this.el.find(".fc-day"),this.slatContainerEl=this.el.find(".fc-slats"),this.slatEls=this.slatContainerEl.find("tr"),this.colCoordCache=new ne({els:this.colEls,isHorizontal:!0}),this.slatCoordCache=new ne({els:this.slatEls,isVertical:!0}),this.renderContentSkeleton()},renderHtml:function(){return'<div class="fc-bg"><table>'+this.renderBgTrHtml(0)+'</table></div><div class="fc-slats"><table>'+this.renderSlatRowHtml()+"</table></div>"},renderSlatRowHtml:function(){for(var t,n,i,r=this.view,s=this.isRTL,o="",l=e.duration(+this.minTime);l<this.maxTime;)t=this.start.clone().time(l),n=ot(_(l,this.labelInterval)),i='<td class="fc-axis fc-time '+r.widgetContentClass+'" '+r.axisStyleAttr()+">"+(n?"<span>"+tt(t.format(this.labelFormat))+"</span>":"")+"</td>",o+='<tr data-time="'+t.format("HH:mm:ss")+'"'+(n?"":' class="fc-minor"')+">"+(s?"":i)+'<td class="'+r.widgetContentClass+'"/>'+(s?i:"")+"</tr>",l.add(this.slotDuration);return o},processOptions:function(){var n,i=this.view,r=i.opt("slotDuration"),s=i.opt("snapDuration");r=e.duration(r),s=s?e.duration(s):r,this.slotDuration=r,this.snapDuration=s,this.snapsPerSlot=r/s,this.minResizeDuration=s,this.minTime=e.duration(i.opt("minTime")),this.maxTime=e.duration(i.opt("maxTime")),n=i.opt("slotLabelFormat"),t.isArray(n)&&(n=n[n.length-1]),this.labelFormat=n||i.opt("smallTimeFormat"),n=i.opt("slotLabelInterval"),this.labelInterval=n?e.duration(n):this.computeLabelInterval(r)},computeLabelInterval:function(t){var n,i,r;for(n=Re.length-1;n>=0;n--)if(i=e.duration(Re[n]),r=_(i,t),ot(r)&&r>1)return i;return e.duration(t)},computeEventTimeFormat:function(){return this.view.opt("noMeridiemTimeFormat")},computeDisplayEventEnd:function(){return!0},prepareHits:function(){this.colCoordCache.build(),this.slatCoordCache.build()},releaseHits:function(){this.colCoordCache.clear()},queryHit:function(t,e){var n=this.snapsPerSlot,i=this.colCoordCache,r=this.slatCoordCache;if(i.isLeftInBounds(t)&&r.isTopInBounds(e)){var s=i.getHorizontalIndex(t),o=r.getVerticalIndex(e);if(null!=s&&null!=o){var l=r.getTopOffset(o),a=r.getHeight(o),u=(e-l)/a,c=Math.floor(u*n),d=o*n+c,h=l+c/n*a,f=l+(c+1)/n*a;return{col:s,snap:d,component:this,left:i.getLeftOffset(s),right:i.getRightOffset(s),top:h,bottom:f}}}},getHitSpan:function(t){var e,n=this.getCellDate(0,t.col),i=this.computeSnapTime(t.snap);return n.time(i),e=n.clone().add(this.snapDuration),{start:n,end:e}},getHitEl:function(t){return this.colEls.eq(t.col)},rangeUpdated:function(){this.updateDayTable()},computeSnapTime:function(t){return e.duration(this.minTime+this.snapDuration*t)},spanToSegs:function(t){var e,n=this.sliceRangeByTimes(t);for(e=0;e<n.length;e++)this.isRTL?n[e].col=this.daysPerRow-1-n[e].dayIndex:n[e].col=n[e].dayIndex;return n},sliceRangeByTimes:function(t){var e,n,i,r,s=[];for(n=0;n<this.daysPerRow;n++)i=this.dayDates[n].clone(),r={start:i.clone().time(this.minTime),end:i.clone().time(this.maxTime)},e=F(t,r),e&&(e.dayIndex=n,s.push(e));return s},updateSize:function(t){this.slatCoordCache.build(),t&&this.updateSegVerticals([].concat(this.fgSegs||[],this.bgSegs||[],this.businessSegs||[]))},getTotalSlatHeight:function(){return this.slatContainerEl.outerHeight()},computeDateTop:function(t,n){return this.computeTimeTop(e.duration(t-n.clone().stripTime()))},computeTimeTop:function(t){var e,n,i=this.slatEls.length,r=(t-this.minTime)/this.slotDuration;return r=Math.max(0,r),r=Math.min(i,r),e=Math.floor(r),e=Math.min(e,i-1),n=r-e,this.slatCoordCache.getTopPosition(e)+this.slatCoordCache.getHeight(e)*n},renderDrag:function(t,e){return e?this.renderEventLocationHelper(t,e):void this.renderHighlight(this.eventToSpan(t))},unrenderDrag:function(){this.unrenderHelper(),this.unrenderHighlight()},renderEventResize:function(t,e){return this.renderEventLocationHelper(t,e)},unrenderEventResize:function(){this.unrenderHelper()},renderHelper:function(t,e){return this.renderHelperSegs(this.eventToSegs(t),e)},unrenderHelper:function(){this.unrenderHelperSegs()},renderBusinessHours:function(){this.renderBusinessSegs(this.buildBusinessHourSegs())},unrenderBusinessHours:function(){this.unrenderBusinessSegs()},getNowIndicatorUnit:function(){return"minute"},renderNowIndicator:function(e){var n,i=this.spanToSegs({start:e,end:e}),r=this.computeDateTop(e,e),s=[];for(n=0;n<i.length;n++)s.push(t('<div class="fc-now-indicator fc-now-indicator-line"></div>').css("top",r).appendTo(this.colContainerEls.eq(i[n].col))[0]);i.length>0&&s.push(t('<div class="fc-now-indicator fc-now-indicator-arrow"></div>').css("top",r).appendTo(this.el.find(".fc-content-skeleton"))[0]),this.nowIndicatorEls=t(s)},unrenderNowIndicator:function(){this.nowIndicatorEls&&(this.nowIndicatorEls.remove(),this.nowIndicatorEls=null)},renderSelection:function(t){this.view.opt("selectHelper")?this.renderEventLocationHelper(t):this.renderHighlight(t)},unrenderSelection:function(){this.unrenderHelper(),this.unrenderHighlight()},renderHighlight:function(t){this.renderHighlightSegs(this.spanToSegs(t))},unrenderHighlight:function(){this.unrenderHighlightSegs()}});ce.mixin({colContainerEls:null,fgContainerEls:null,bgContainerEls:null,helperContainerEls:null,highlightContainerEls:null,businessContainerEls:null,fgSegs:null,bgSegs:null,helperSegs:null,highlightSegs:null,businessSegs:null,renderContentSkeleton:function(){var e,n,i="";for(e=0;e<this.colCnt;e++)i+='<td><div class="fc-content-col"><div class="fc-event-container fc-helper-container"></div><div class="fc-event-container"></div><div class="fc-highlight-container"></div><div class="fc-bgevent-container"></div><div class="fc-business-container"></div></div></td>';n=t('<div class="fc-content-skeleton"><table><tr>'+i+"</tr></table></div>"),this.colContainerEls=n.find(".fc-content-col"),this.helperContainerEls=n.find(".fc-helper-container"),this.fgContainerEls=n.find(".fc-event-container:not(.fc-helper-container)"),this.bgContainerEls=n.find(".fc-bgevent-container"),this.highlightContainerEls=n.find(".fc-highlight-container"),this.businessContainerEls=n.find(".fc-business-container"),this.bookendCells(n.find("tr")),this.el.append(n)},renderFgSegs:function(t){return t=this.renderFgSegsIntoContainers(t,this.fgContainerEls),this.fgSegs=t,t},unrenderFgSegs:function(){this.unrenderNamedSegs("fgSegs")},renderHelperSegs:function(e,n){var i,r,s,o=[];for(e=this.renderFgSegsIntoContainers(e,this.helperContainerEls),i=0;i<e.length;i++)r=e[i],n&&n.col===r.col&&(s=n.el,r.el.css({left:s.css("left"),right:s.css("right"),"margin-left":s.css("margin-left"),"margin-right":s.css("margin-right")})),o.push(r.el[0]);return this.helperSegs=e,t(o)},unrenderHelperSegs:function(){this.unrenderNamedSegs("helperSegs")},renderBgSegs:function(t){return t=this.renderFillSegEls("bgEvent",t),this.updateSegVerticals(t),this.attachSegsByCol(this.groupSegsByCol(t),this.bgContainerEls),this.bgSegs=t,t},unrenderBgSegs:function(){this.unrenderNamedSegs("bgSegs")},renderHighlightSegs:function(t){t=this.renderFillSegEls("highlight",t),this.updateSegVerticals(t),this.attachSegsByCol(this.groupSegsByCol(t),this.highlightContainerEls),this.highlightSegs=t},unrenderHighlightSegs:function(){this.unrenderNamedSegs("highlightSegs")},renderBusinessSegs:function(t){t=this.renderFillSegEls("businessHours",t),this.updateSegVerticals(t),this.attachSegsByCol(this.groupSegsByCol(t),this.businessContainerEls),this.businessSegs=t},unrenderBusinessSegs:function(){this.unrenderNamedSegs("businessSegs")},groupSegsByCol:function(t){var e,n=[];for(e=0;e<this.colCnt;e++)n.push([]);for(e=0;e<t.length;e++)n[t[e].col].push(t[e]);return n},attachSegsByCol:function(t,e){var n,i,r;for(n=0;n<this.colCnt;n++)for(i=t[n],r=0;r<i.length;r++)e.eq(n).append(i[r].el)},unrenderNamedSegs:function(t){var e,n=this[t];if(n){for(e=0;e<n.length;e++)n[e].el.remove();this[t]=null}},renderFgSegsIntoContainers:function(t,e){var n,i;for(t=this.renderFgSegEls(t),n=this.groupSegsByCol(t),i=0;i<this.colCnt;i++)this.updateFgSegCoords(n[i]);return this.attachSegsByCol(n,e),t},fgSegHtml:function(t,e){var n,i,r,s=this.view,o=t.event,l=s.isEventDraggable(o),a=!e&&t.isStart&&s.isEventResizableFromStart(o),u=!e&&t.isEnd&&s.isEventResizableFromEnd(o),c=this.getSegClasses(t,l,a||u),d=nt(this.getSegSkinCss(t));return c.unshift("fc-time-grid-event","fc-v-event"),s.isMultiDayEvent(o)?(t.isStart||t.isEnd)&&(n=this.getEventTimeText(t),i=this.getEventTimeText(t,"LT"),r=this.getEventTimeText(t,null,!1)):(n=this.getEventTimeText(o),i=this.getEventTimeText(o,"LT"),r=this.getEventTimeText(o,null,!1)),'<a class="'+c.join(" ")+'"'+(o.url?' href="'+tt(o.url)+'"':"")+(d?' style="'+d+'"':"")+'><div class="fc-content">'+(n?'<div class="fc-time" data-start="'+tt(r)+'" data-full="'+tt(i)+'"><span>'+tt(n)+"</span></div>":"")+(o.title?'<div class="fc-title">'+tt(o.title)+"</div>":"")+'</div><div class="fc-bg"/>'+(u?'<div class="fc-resizer fc-end-resizer" />':"")+"</a>"},updateSegVerticals:function(t){this.computeSegVerticals(t),this.assignSegVerticals(t)},computeSegVerticals:function(t){var e,n;for(e=0;e<t.length;e++)n=t[e],n.top=this.computeDateTop(n.start,n.start),n.bottom=this.computeDateTop(n.end,n.start)},assignSegVerticals:function(t){var e,n;for(e=0;e<t.length;e++)n=t[e],n.el.css(this.generateSegVerticalCss(n))},generateSegVerticalCss:function(t){return{top:t.top,bottom:-t.bottom}},updateFgSegCoords:function(t){this.computeSegVerticals(t),this.computeFgSegHorizontals(t),this.assignSegVerticals(t),this.assignFgSegHorizontals(t)},computeFgSegHorizontals:function(t){var e,n,i;if(this.sortEventSegs(t),e=Ht(t),xt(e),n=e[0]){for(i=0;i<n.length;i++)Rt(n[i]);for(i=0;i<n.length;i++)this.computeFgSegForwardBack(n[i],0,0)}},computeFgSegForwardBack:function(t,e,n){var i,r=t.forwardSegs;if(void 0===t.forwardCoord)for(r.length?(this.sortForwardSegs(r),this.computeFgSegForwardBack(r[0],e+1,n),t.forwardCoord=r[0].backwardCoord):t.forwardCoord=1,t.backwardCoord=t.forwardCoord-(t.forwardCoord-n)/(e+1),i=0;i<r.length;i++)this.computeFgSegForwardBack(r[i],0,t.forwardCoord)},sortForwardSegs:function(t){t.sort(lt(this,"compareForwardSegs"))},compareForwardSegs:function(t,e){return e.forwardPressure-t.forwardPressure||(t.backwardCoord||0)-(e.backwardCoord||0)||this.compareEventSegs(t,e)},assignFgSegHorizontals:function(t){var e,n;for(e=0;e<t.length;e++)n=t[e],n.el.css(this.generateFgSegHorizontalCss(n)),n.bottom-n.top<30&&n.el.addClass("fc-short")},generateFgSegHorizontalCss:function(t){var e,n,i=this.view.opt("slotEventOverlap"),r=t.backwardCoord,s=t.forwardCoord,o=this.generateSegVerticalCss(t);return i&&(s=Math.min(1,r+2*(s-r))),this.isRTL?(e=1-s,n=r):(e=r,n=1-s),o.zIndex=t.level+1,o.left=100*e+"%",o.right=100*n+"%",i&&t.forwardPressure&&(o[this.isRTL?"marginLeft":"marginRight"]=20),o}});var de=Ot.View=ct.extend(Jt,te,{type:null,name:null,title:null,calendar:null,options:null,el:null,isDateSet:!1,isDateRendered:!1,dateRenderQueue:null,isEventsBound:!1,isEventsSet:!1,isEventsRendered:!1,eventRenderQueue:null,start:null,end:null,intervalStart:null,intervalEnd:null,intervalDuration:null,intervalUnit:null,isRTL:!1,isSelected:!1,selectedEvent:null,eventOrderSpecs:null,widgetHeaderClass:null,widgetContentClass:null,highlightStateClass:null,nextDayThreshold:null,isHiddenDayHash:null,isNowIndicatorRendered:null,initialNowDate:null,initialNowQueriedMs:null,nowIndicatorTimeoutID:null,nowIndicatorIntervalID:null,constructor:function(t,n,i,r){this.calendar=t,this.type=this.name=n,this.options=i,this.intervalDuration=r||e.duration(1,"day"),this.nextDayThreshold=e.duration(this.opt("nextDayThreshold")),this.initThemingProps(),this.initHiddenDays(),this.isRTL=this.opt("isRTL"),this.eventOrderSpecs=L(this.opt("eventOrder")),this.dateRenderQueue=new gt,this.eventRenderQueue=new gt(this.opt("eventRenderWait")),this.initialize()},initialize:function(){},opt:function(t){return this.options[t]},publiclyTrigger:function(t,e){var n=this.calendar;return n.publiclyTrigger.apply(n,[t,e||this].concat(Array.prototype.slice.call(arguments,2),[this]))},rejectOn:function(t,e){var n=this;return new ft(function(i,r){function s(){n.off(t,r)}n.one(t,r),e.then(function(t){s(),i(t)},function(){s(),r()})})},setRange:function(e){t.extend(this,e),this.updateTitle()},computeRange:function(t){var e,n,i=A(this.intervalDuration),r=t.clone().startOf(i),s=r.clone().add(this.intervalDuration);return/year|month|week|day/.test(i)?(r.stripTime(),s.stripTime()):(r.hasTime()||(r=this.calendar.time(0)),s.hasTime()||(s=this.calendar.time(0))),e=r.clone(),e=this.skipHiddenDays(e),n=s.clone(),n=this.skipHiddenDays(n,-1,!0),{intervalUnit:i,intervalStart:r,intervalEnd:s,start:e,end:n}},computePrevDate:function(t){return this.massageCurrentDate(t.clone().startOf(this.intervalUnit).subtract(this.intervalDuration),-1)},computeNextDate:function(t){return this.massageCurrentDate(t.clone().startOf(this.intervalUnit).add(this.intervalDuration))},massageCurrentDate:function(t,e){return this.intervalDuration.as("days")<=1&&this.isHiddenDay(t)&&(t=this.skipHiddenDays(t,e),t.startOf("day")),t},updateTitle:function(){this.title=this.computeTitle(),this.calendar.setToolbarsTitle(this.title)},computeTitle:function(){var t,e;return"year"===this.intervalUnit||"month"===this.intervalUnit?(t=this.intervalStart,
+e=this.intervalEnd):(t=this.start,e=this.end),this.formatRange({start:this.calendar.applyTimezone(t),end:this.calendar.applyTimezone(e)},this.opt("titleFormat")||this.computeTitleFormat(),this.opt("titleRangeSeparator"))},computeTitleFormat:function(){return"year"==this.intervalUnit?"YYYY":"month"==this.intervalUnit?this.opt("monthYearFormat"):this.intervalDuration.as("days")>1?"ll":"LL"},formatRange:function(t,e,n){var i=t.end;return i.hasTime()||(i=i.clone().subtract(1)),Xt(t.start,i,e,n,this.opt("isRTL"))},getAllDayHtml:function(){return this.opt("allDayHtml")||tt(this.opt("allDayText"))},buildGotoAnchorHtml:function(e,n,i){var r,s,o,l;return t.isPlainObject(e)?(r=e.date,s=e.type,o=e.forceOff):r=e,r=Ot.moment(r),l={date:r.format("YYYY-MM-DD"),type:s||"day"},"string"==typeof n&&(i=n,n=null),n=n?" "+it(n):"",i=i||"",!o&&this.opt("navLinks")?"<a"+n+' data-goto="'+tt(JSON.stringify(l))+'">'+i+"</a>":"<span"+n+">"+i+"</span>"},setElement:function(t){this.el=t,this.bindGlobalHandlers(),this.renderSkeleton()},removeElement:function(){this.unsetDate(),this.unrenderSkeleton(),this.unbindGlobalHandlers(),this.el.remove()},renderSkeleton:function(){},unrenderSkeleton:function(){},setDate:function(t){var e=this.isDateSet;this.isDateSet=!0,this.handleDate(t,e),this.trigger(e?"dateReset":"dateSet",t)},unsetDate:function(){this.isDateSet&&(this.isDateSet=!1,this.handleDateUnset(),this.trigger("dateUnset"))},handleDate:function(t,e){var n=this;this.unbindEvents(),this.requestDateRender(t).then(function(){n.bindEvents()})},handleDateUnset:function(){this.unbindEvents(),this.requestDateUnrender()},requestDateRender:function(t){var e=this;return this.dateRenderQueue.add(function(){return e.executeDateRender(t)})},requestDateUnrender:function(){var t=this;return this.dateRenderQueue.add(function(){return t.executeDateUnrender()})},executeDateRender:function(t){var e=this;return t?this.captureInitialScroll():this.captureScroll(),this.freezeHeight(),this.executeDateUnrender().then(function(){t&&e.setRange(e.computeRange(t)),e.render&&e.render(),e.renderDates(),e.updateSize(),e.renderBusinessHours(),e.startNowIndicator(),e.thawHeight(),e.releaseScroll(),e.isDateRendered=!0,e.onDateRender(),e.trigger("dateRender")})},executeDateUnrender:function(){var t=this;return t.isDateRendered?this.requestEventsUnrender().then(function(){t.unselect(),t.stopNowIndicator(),t.triggerUnrender(),t.unrenderBusinessHours(),t.unrenderDates(),t.destroy&&t.destroy(),t.isDateRendered=!1,t.trigger("dateUnrender")}):ft.resolve()},onDateRender:function(){this.triggerRender()},renderDates:function(){},unrenderDates:function(){},triggerRender:function(){this.publiclyTrigger("viewRender",this,this,this.el)},triggerUnrender:function(){this.publiclyTrigger("viewDestroy",this,this,this.el)},bindGlobalHandlers:function(){this.listenTo(se.get(),{touchstart:this.processUnselect,mousedown:this.handleDocumentMousedown})},unbindGlobalHandlers:function(){this.stopListeningTo(se.get())},initThemingProps:function(){var t=this.opt("theme")?"ui":"fc";this.widgetHeaderClass=t+"-widget-header",this.widgetContentClass=t+"-widget-content",this.highlightStateClass=t+"-state-highlight"},renderBusinessHours:function(){},unrenderBusinessHours:function(){},startNowIndicator:function(){var t,n,i,r=this;this.opt("nowIndicator")&&(t=this.getNowIndicatorUnit(),t&&(n=lt(this,"updateNowIndicator"),this.initialNowDate=this.calendar.getNow(),this.initialNowQueriedMs=+new Date,this.renderNowIndicator(this.initialNowDate),this.isNowIndicatorRendered=!0,i=this.initialNowDate.clone().startOf(t).add(1,t)-this.initialNowDate,this.nowIndicatorTimeoutID=setTimeout(function(){r.nowIndicatorTimeoutID=null,n(),i=+e.duration(1,t),i=Math.max(100,i),r.nowIndicatorIntervalID=setInterval(n,i)},i)))},updateNowIndicator:function(){this.isNowIndicatorRendered&&(this.unrenderNowIndicator(),this.renderNowIndicator(this.initialNowDate.clone().add(new Date-this.initialNowQueriedMs)))},stopNowIndicator:function(){this.isNowIndicatorRendered&&(this.nowIndicatorTimeoutID&&(clearTimeout(this.nowIndicatorTimeoutID),this.nowIndicatorTimeoutID=null),this.nowIndicatorIntervalID&&(clearTimeout(this.nowIndicatorIntervalID),this.nowIndicatorIntervalID=null),this.unrenderNowIndicator(),this.isNowIndicatorRendered=!1)},getNowIndicatorUnit:function(){},renderNowIndicator:function(t){},unrenderNowIndicator:function(){},updateSize:function(t){t&&this.captureScroll(),this.updateHeight(t),this.updateWidth(t),this.updateNowIndicator(),t&&this.releaseScroll()},updateWidth:function(t){},updateHeight:function(t){var e=this.calendar;this.setHeight(e.getSuggestedViewHeight(),e.isHeightAuto())},setHeight:function(t,e){},capturedScroll:null,capturedScrollDepth:0,captureScroll:function(){return!this.capturedScrollDepth++&&(this.capturedScroll=this.isDateRendered?this.queryScroll():{},!0)},captureInitialScroll:function(e){this.captureScroll()&&(this.capturedScroll.isInitial=!0,e?t.extend(this.capturedScroll,e):this.capturedScroll.isComputed=!0)},releaseScroll:function(){var e=this.capturedScroll,n=this.discardScroll();e.isComputed&&(n?t.extend(e,this.computeInitialScroll()):e=null),e&&(e.isInitial?this.hardSetScroll(e):this.setScroll(e))},discardScroll:function(){return!--this.capturedScrollDepth&&(this.capturedScroll=null,!0)},computeInitialScroll:function(){return{}},queryScroll:function(){return{}},hardSetScroll:function(t){var e=this,n=function(){e.setScroll(t)};n(),setTimeout(n,0)},setScroll:function(t){},freezeHeight:function(){this.calendar.freezeContentHeight()},thawHeight:function(){this.calendar.thawContentHeight()},bindEvents:function(){var t=this;this.isEventsBound||(this.isEventsBound=!0,this.rejectOn("eventsUnbind",this.requestEvents()).then(function(e){t.listenTo(t.calendar,"eventsReset",t.setEvents),t.setEvents(e)}))},unbindEvents:function(){this.isEventsBound&&(this.isEventsBound=!1,this.stopListeningTo(this.calendar,"eventsReset"),this.unsetEvents(),this.trigger("eventsUnbind"))},setEvents:function(t){var e=this.isEventSet;this.isEventsSet=!0,this.handleEvents(t,e),this.trigger(e?"eventsReset":"eventsSet",t)},unsetEvents:function(){this.isEventsSet&&(this.isEventsSet=!1,this.handleEventsUnset(),this.trigger("eventsUnset"))},whenEventsSet:function(){var t=this;return this.isEventsSet?ft.resolve(this.getCurrentEvents()):new ft(function(e){t.one("eventsSet",e)})},handleEvents:function(t,e){this.requestEventsRender(t)},handleEventsUnset:function(){this.requestEventsUnrender()},requestEventsRender:function(t){var e=this;return this.eventRenderQueue.add(function(){return e.executeEventsRender(t)})},requestEventsUnrender:function(){var t=this;return this.isEventsRendered?this.eventRenderQueue.addQuickly(function(){return t.executeEventsUnrender()}):ft.resolve()},requestCurrentEventsRender:function(){return this.isEventsSet?void this.requestEventsRender(this.getCurrentEvents()):ft.reject()},executeEventsRender:function(t){var e=this;return this.captureScroll(),this.freezeHeight(),this.executeEventsUnrender().then(function(){e.renderEvents(t),e.thawHeight(),e.releaseScroll(),e.isEventsRendered=!0,e.onEventsRender(),e.trigger("eventsRender")})},executeEventsUnrender:function(){return this.isEventsRendered&&(this.onBeforeEventsUnrender(),this.captureScroll(),this.freezeHeight(),this.destroyEvents&&this.destroyEvents(),this.unrenderEvents(),this.thawHeight(),this.releaseScroll(),this.isEventsRendered=!1,this.trigger("eventsUnrender")),ft.resolve()},onEventsRender:function(){this.renderedEventSegEach(function(t){this.publiclyTrigger("eventAfterRender",t.event,t.event,t.el)}),this.publiclyTrigger("eventAfterAllRender")},onBeforeEventsUnrender:function(){this.renderedEventSegEach(function(t){this.publiclyTrigger("eventDestroy",t.event,t.event,t.el)})},renderEvents:function(t){},unrenderEvents:function(){},requestEvents:function(){return this.calendar.requestEvents(this.start,this.end)},getCurrentEvents:function(){return this.calendar.getPrunedEventCache()},resolveEventEl:function(e,n){var i=this.publiclyTrigger("eventRender",e,e,n);return i===!1?n=null:i&&i!==!0&&(n=t(i)),n},showEvent:function(t){this.renderedEventSegEach(function(t){t.el.css("visibility","")},t)},hideEvent:function(t){this.renderedEventSegEach(function(t){t.el.css("visibility","hidden")},t)},renderedEventSegEach:function(t,e){var n,i=this.getEventSegs();for(n=0;n<i.length;n++)e&&i[n].event._id!==e._id||i[n].el&&t.call(this,i[n])},getEventSegs:function(){return[]},isEventDraggable:function(t){return this.isEventStartEditable(t)},isEventStartEditable:function(t){return J(t.startEditable,(t.source||{}).startEditable,this.opt("eventStartEditable"),this.isEventGenerallyEditable(t))},isEventGenerallyEditable:function(t){return J(t.editable,(t.source||{}).editable,this.opt("editable"))},reportSegDrop:function(t,e,n,i,r){var s=this.calendar,o=s.mutateSeg(t,e,n),l=function(){o.undo(),s.reportEventChange()};this.triggerEventDrop(t.event,o.dateDelta,l,i,r),s.reportEventChange()},triggerEventDrop:function(t,e,n,i,r){this.publiclyTrigger("eventDrop",i[0],t,e,n,r,{})},reportExternalDrop:function(e,n,i,r,s){var o,l,a=e.eventProps;a&&(o=t.extend({},a,n),l=this.calendar.renderEvent(o,e.stick)[0]),this.triggerExternalDrop(l,n,i,r,s)},triggerExternalDrop:function(t,e,n,i,r){this.publiclyTrigger("drop",n[0],e.start,i,r),t&&this.publiclyTrigger("eventReceive",null,t)},renderDrag:function(t,e){},unrenderDrag:function(){},isEventResizableFromStart:function(t){return this.opt("eventResizableFromStart")&&this.isEventResizable(t)},isEventResizableFromEnd:function(t){return this.isEventResizable(t)},isEventResizable:function(t){var e=t.source||{};return J(t.durationEditable,e.durationEditable,this.opt("eventDurationEditable"),t.editable,e.editable,this.opt("editable"))},reportSegResize:function(t,e,n,i,r){var s=this.calendar,o=s.mutateSeg(t,e,n),l=function(){o.undo(),s.reportEventChange()};this.triggerEventResize(t.event,o.durationDelta,l,i,r),s.reportEventChange()},triggerEventResize:function(t,e,n,i,r){this.publiclyTrigger("eventResize",i[0],t,e,n,r,{})},select:function(t,e){this.unselect(e),this.renderSelection(t),this.reportSelection(t,e)},renderSelection:function(t){},reportSelection:function(t,e){this.isSelected=!0,this.triggerSelect(t,e)},triggerSelect:function(t,e){this.publiclyTrigger("select",null,this.calendar.applyTimezone(t.start),this.calendar.applyTimezone(t.end),e)},unselect:function(t){this.isSelected&&(this.isSelected=!1,this.destroySelection&&this.destroySelection(),this.unrenderSelection(),this.publiclyTrigger("unselect",null,t))},unrenderSelection:function(){},selectEvent:function(t){this.selectedEvent&&this.selectedEvent===t||(this.unselectEvent(),this.renderedEventSegEach(function(t){t.el.addClass("fc-selected")},t),this.selectedEvent=t)},unselectEvent:function(){this.selectedEvent&&(this.renderedEventSegEach(function(t){t.el.removeClass("fc-selected")},this.selectedEvent),this.selectedEvent=null)},isEventSelected:function(t){return this.selectedEvent&&this.selectedEvent._id===t._id},handleDocumentMousedown:function(t){w(t)&&this.processUnselect(t)},processUnselect:function(t){this.processRangeUnselect(t),this.processEventUnselect(t)},processRangeUnselect:function(e){var n;this.isSelected&&this.opt("unselectAuto")&&(n=this.opt("unselectCancel"),n&&t(e.target).closest(n).length||this.unselect(e))},processEventUnselect:function(e){this.selectedEvent&&(t(e.target).closest(".fc-selected").length||this.unselectEvent())},triggerDayClick:function(t,e,n){this.publiclyTrigger("dayClick",e,this.calendar.applyTimezone(t.start),n)},initHiddenDays:function(){var e,n=this.opt("hiddenDays")||[],i=[],r=0;for(this.opt("weekends")===!1&&n.push(0,6),e=0;e<7;e++)(i[e]=t.inArray(e,n)!==-1)||r++;if(!r)throw"invalid hiddenDays";this.isHiddenDayHash=i},isHiddenDay:function(t){return e.isMoment(t)&&(t=t.day()),this.isHiddenDayHash[t]},skipHiddenDays:function(t,e,n){var i=t.clone();for(e=e||1;this.isHiddenDayHash[(i.day()+(n?e:0)+7)%7];)i.add(e,"days");return i},computeDayRange:function(t){var e,n=t.start.clone().stripTime(),i=t.end,r=null;return i&&(r=i.clone().stripTime(),e=+i.time(),e&&e>=this.nextDayThreshold&&r.add(1,"days")),(!i||r<=n)&&(r=n.clone().add(1,"days")),{start:n,end:r}},isMultiDayEvent:function(t){var e=this.computeDayRange(t);return e.end.diff(e.start,"days")>1}}),he=Ot.Scroller=ct.extend({el:null,scrollEl:null,overflowX:null,overflowY:null,constructor:function(t){t=t||{},this.overflowX=t.overflowX||t.overflow||"auto",this.overflowY=t.overflowY||t.overflow||"auto"},render:function(){this.el=this.renderEl(),this.applyOverflow()},renderEl:function(){return this.scrollEl=t('<div class="fc-scroller"></div>')},clear:function(){this.setHeight("auto"),this.applyOverflow()},destroy:function(){this.el.remove()},applyOverflow:function(){this.scrollEl.css({"overflow-x":this.overflowX,"overflow-y":this.overflowY})},lockOverflow:function(t){var e=this.overflowX,n=this.overflowY;t=t||this.getScrollbarWidths(),"auto"===e&&(e=t.top||t.bottom||this.scrollEl[0].scrollWidth-1>this.scrollEl[0].clientWidth?"scroll":"hidden"),"auto"===n&&(n=t.left||t.right||this.scrollEl[0].scrollHeight-1>this.scrollEl[0].clientHeight?"scroll":"hidden"),this.scrollEl.css({"overflow-x":e,"overflow-y":n})},setHeight:function(t){this.scrollEl.height(t)},getScrollTop:function(){return this.scrollEl.scrollTop()},setScrollTop:function(t){this.scrollEl.scrollTop(t)},getClientWidth:function(){return this.scrollEl[0].clientWidth},getClientHeight:function(){return this.scrollEl[0].clientHeight},getScrollbarWidths:function(){return p(this.scrollEl)}});Lt.prototype.proxyCall=function(t){var e=Array.prototype.slice.call(arguments,1),n=[];return this.items.forEach(function(i){n.push(i[t].apply(i,e))}),n};var fe=Ot.Calendar=ct.extend({dirDefaults:null,localeDefaults:null,overrides:null,dynamicOverrides:null,options:null,viewSpecCache:null,view:null,header:null,footer:null,loadingLevel:0,constructor:Bt,initialize:function(){},populateOptionsHash:function(){var t,e,i,r;t=J(this.dynamicOverrides.locale,this.overrides.locale),e=ge[t],e||(t=fe.defaults.locale,e=ge[t]||{}),i=J(this.dynamicOverrides.isRTL,this.overrides.isRTL,e.isRTL,fe.defaults.isRTL),r=i?fe.rtlDefaults:{},this.dirDefaults=r,this.localeDefaults=e,this.options=n([fe.defaults,r,e,this.overrides,this.dynamicOverrides]),Nt(this.options)},getViewSpec:function(t){var e=this.viewSpecCache;return e[t]||(e[t]=this.buildViewSpec(t))},getUnitViewSpec:function(e){var n,i,r;if(t.inArray(e,Yt)!=-1)for(n=this.header.getViewsWithButtons(),t.each(Ot.views,function(t){n.push(t)}),i=0;i<n.length;i++)if(r=this.getViewSpec(n[i]),r&&r.singleUnit==e)return r},buildViewSpec:function(t){for(var i,r,s,o,l=this.overrides.views||{},a=[],u=[],c=[],d=t;d;)i=At[d],r=l[d],d=null,"function"==typeof i&&(i={class:i}),i&&(a.unshift(i),u.unshift(i.defaults||{}),s=s||i.duration,d=d||i.type),r&&(c.unshift(r),s=s||r.duration,d=d||r.type);return i=q(a),i.type=t,!!i.class&&(s&&(s=e.duration(s),s.valueOf()&&(i.duration=s,o=A(s),1===s.as(o)&&(i.singleUnit=o,c.unshift(l[o]||{})))),i.defaults=n(u),i.overrides=n(c),this.buildViewSpecOptions(i),this.buildViewSpecButtonText(i,t),i)},buildViewSpecOptions:function(t){t.options=n([fe.defaults,t.defaults,this.dirDefaults,this.localeDefaults,this.overrides,t.overrides,this.dynamicOverrides]),Nt(t.options)},buildViewSpecButtonText:function(t,e){function n(n){var i=n.buttonText||{};return i[e]||(t.buttonTextKey?i[t.buttonTextKey]:null)||(t.singleUnit?i[t.singleUnit]:null)}t.buttonTextOverride=n(this.dynamicOverrides)||n(this.overrides)||t.overrides.buttonText,t.buttonTextDefault=n(this.localeDefaults)||n(this.dirDefaults)||t.defaults.buttonText||n(fe.defaults)||(t.duration?this.humanizeDuration(t.duration):null)||e},instantiateView:function(t){var e=this.getViewSpec(t);return new e.class(this,t,e.options,e.duration)},isValidViewType:function(t){return Boolean(this.getViewSpec(t))},pushLoading:function(){this.loadingLevel++||this.publiclyTrigger("loading",null,!0,this.view)},popLoading:function(){--this.loadingLevel||this.publiclyTrigger("loading",null,!1,this.view)},buildSelectSpan:function(t,e){var n,i=this.moment(t).stripZone();return n=e?this.moment(e).stripZone():i.hasTime()?i.clone().add(this.defaultTimedEventDuration):i.clone().add(this.defaultAllDayEventDuration),{start:i,end:n}}});fe.mixin(Jt),fe.mixin({optionHandlers:null,bindOption:function(t,e){this.bindOptions([t],e)},bindOptions:function(t,e){var n,i={func:e,names:t};for(n=0;n<t.length;n++)this.registerOptionHandlerObj(t[n],i);this.triggerOptionHandlerObj(i)},registerOptionHandlerObj:function(t,e){(this.optionHandlers[t]||(this.optionHandlers[t]=[])).push(e)},triggerOptionHandlers:function(t){var e,n=this.optionHandlers[t]||[];for(e=0;e<n.length;e++)this.triggerOptionHandlerObj(n[e])},triggerOptionHandlerObj:function(t){var e,n=t.names,i=[];for(e=0;e<n.length;e++)i.push(this.options[n[e]]);t.func.apply(this,i)}}),fe.defaults={titleRangeSeparator:" – ",monthYearFormat:"MMMM YYYY",defaultTimedEventDuration:"02:00:00",defaultAllDayEventDuration:{days:1},forceEventDuration:!1,nextDayThreshold:"09:00:00",defaultView:"month",aspectRatio:1.35,header:{left:"title",center:"",right:"today prev,next"},weekends:!0,weekNumbers:!1,weekNumberTitle:"W",weekNumberCalculation:"local",scrollTime:"06:00:00",lazyFetching:!0,startParam:"start",endParam:"end",timezoneParam:"timezone",timezone:!1,isRTL:!1,buttonText:{prev:"prev",next:"next",prevYear:"prev year",nextYear:"next year",year:"year",today:"today",month:"month",week:"week",day:"day"},buttonIcons:{prev:"left-single-arrow",next:"right-single-arrow",prevYear:"left-double-arrow",nextYear:"right-double-arrow"},allDayText:"all-day",theme:!1,themeButtonIcons:{prev:"circle-triangle-w",next:"circle-triangle-e",prevYear:"seek-prev",nextYear:"seek-next"},dragOpacity:.75,dragRevertDuration:500,dragScroll:!0,unselectAuto:!0,dropAccept:"*",eventOrder:"title",eventLimit:!1,eventLimitText:"more",eventLimitClick:"popover",dayPopoverFormat:"LL",handleWindowResize:!0,windowResizeDelay:100,longPressDelay:1e3},fe.englishDefaults={dayPopoverFormat:"dddd, MMMM D"},fe.rtlDefaults={header:{left:"next,prev today",center:"",right:"title"},buttonIcons:{prev:"right-single-arrow",next:"left-single-arrow",prevYear:"right-double-arrow",nextYear:"left-double-arrow"},themeButtonIcons:{prev:"circle-triangle-e",next:"circle-triangle-w",nextYear:"seek-prev",prevYear:"seek-next"}};var ge=Ot.locales={};Ot.datepickerLocale=function(e,n,i){var r=ge[e]||(ge[e]={});r.isRTL=i.isRTL,r.weekNumberTitle=i.weekHeader,t.each(pe,function(t,e){r[t]=e(i)}),t.datepicker&&(t.datepicker.regional[n]=t.datepicker.regional[e]=i,t.datepicker.regional.en=t.datepicker.regional[""],t.datepicker.setDefaults(i))},Ot.locale=function(e,i){var r,s;r=ge[e]||(ge[e]={}),i&&(r=ge[e]=n([r,i])),s=Ft(e),t.each(ve,function(t,e){null==r[t]&&(r[t]=e(s,r))}),fe.defaults.locale=e};var pe={buttonText:function(t){return{prev:et(t.prevText),next:et(t.nextText),today:et(t.currentText)}},monthYearFormat:function(t){return t.showMonthAfterYear?"YYYY["+t.yearSuffix+"] MMMM":"MMMM YYYY["+t.yearSuffix+"]"}},ve={dayOfMonthFormat:function(t,e){var n=t.longDateFormat("l");return n=n.replace(/^Y+[^\w\s]*|[^\w\s]*Y+$/g,""),e.isRTL?n+=" ddd":n="ddd "+n,n},mediumTimeFormat:function(t){return t.longDateFormat("LT").replace(/\s*a$/i,"a")},smallTimeFormat:function(t){return t.longDateFormat("LT").replace(":mm","(:mm)").replace(/(\Wmm)$/,"($1)").replace(/\s*a$/i,"a")},extraSmallTimeFormat:function(t){return t.longDateFormat("LT").replace(":mm","(:mm)").replace(/(\Wmm)$/,"($1)").replace(/\s*a$/i,"t")},hourFormat:function(t){return t.longDateFormat("LT").replace(":mm","").replace(/(\Wmm)$/,"").replace(/\s*a$/i,"a")},noMeridiemTimeFormat:function(t){return t.longDateFormat("LT").replace(/\s*a$/i,"")}},me={smallDayDateFormat:function(t){return t.isRTL?"D dd":"dd D"},weekFormat:function(t){return t.isRTL?"w[ "+t.weekNumberTitle+"]":"["+t.weekNumberTitle+" ]w"},smallWeekFormat:function(t){return t.isRTL?"w["+t.weekNumberTitle+"]":"["+t.weekNumberTitle+"]w"}};Ot.locale("en",fe.englishDefaults),Ot.sourceNormalizers=[],Ot.sourceFetchers=[];var ye={dataType:"json",cache:!1},Se=1;fe.prototype.mutateSeg=function(t,e){return this.mutateEvent(t.event,e)},fe.prototype.normalizeEvent=function(t){},fe.prototype.spanContainsSpan=function(t,e){var n=t.start.clone().stripZone(),i=this.getEventEnd(t).stripZone();return e.start>=n&&e.end<=i},fe.prototype.getPeerEvents=function(t,e){var n,i,r=this.getEventCache(),s=[];for(n=0;n<r.length;n++)i=r[n],e&&e._id===i._id||s.push(i);return s},fe.prototype.isEventSpanAllowed=function(t,e){var n=e.source||{},i=J(e.constraint,n.constraint,this.options.eventConstraint),r=J(e.overlap,n.overlap,this.options.eventOverlap);return this.isSpanAllowed(t,i,r,e)&&(!this.options.eventAllow||this.options.eventAllow(t,e)!==!1)},fe.prototype.isExternalSpanAllowed=function(e,n,i){var r,s;return i&&(r=t.extend({},i,n),s=this.expandEvent(this.buildEventFromInput(r))[0]),s?this.isEventSpanAllowed(e,s):this.isSelectionSpanAllowed(e)},fe.prototype.isSelectionSpanAllowed=function(t){return this.isSpanAllowed(t,this.options.selectConstraint,this.options.selectOverlap)&&(!this.options.selectAllow||this.options.selectAllow(t)!==!1)},fe.prototype.isSpanAllowed=function(t,e,n,i){var r,s,o,l,a,u;if(null!=e&&(r=this.constraintToEvents(e))){for(s=!1,l=0;l<r.length;l++)if(this.spanContainsSpan(r[l],t)){s=!0;break}if(!s)return!1}for(o=this.getPeerEvents(t,i),l=0;l<o.length;l++)if(a=o[l],this.eventIntersectsRange(a,t)){if(n===!1)return!1;if("function"==typeof n&&!n(a,i))return!1;if(i){if(u=J(a.overlap,(a.source||{}).overlap),u===!1)return!1;if("function"==typeof u&&!u(i,a))return!1}}return!0},fe.prototype.constraintToEvents=function(t){return"businessHours"===t?this.getCurrentBusinessHourEvents():"object"==typeof t?null!=t.start?this.expandEvent(this.buildEventFromInput(t)):null:this.clientEvents(t)},fe.prototype.eventIntersectsRange=function(t,e){var n=t.start.clone().stripZone(),i=this.getEventEnd(t).stripZone();return e.start<i&&e.end>n};var we={id:"_fcBusinessHours",start:"09:00",end:"17:00",dow:[1,2,3,4,5],rendering:"inverse-background"};fe.prototype.getCurrentBusinessHourEvents=function(t){return this.computeBusinessHourEvents(t,this.options.businessHours)},fe.prototype.computeBusinessHourEvents=function(e,n){return n===!0?this.expandBusinessHourEvents(e,[{}]):t.isPlainObject(n)?this.expandBusinessHourEvents(e,[n]):t.isArray(n)?this.expandBusinessHourEvents(e,n,!0):[]},fe.prototype.expandBusinessHourEvents=function(e,n,i){var r,s,o=this.getView(),l=[];for(r=0;r<n.length;r++)s=n[r],i&&!s.dow||(s=t.extend({},we,s),e&&(s.start=null,s.end=null),l.push.apply(l,this.expandEvent(this.buildEventFromInput(s),o.start,o.end)));return l};var Ee=Ot.BasicView=de.extend({scroller:null,dayGridClass:ue,dayGrid:null,dayNumbersVisible:!1,colWeekNumbersVisible:!1,cellWeekNumbersVisible:!1,weekNumberWidth:null,headContainerEl:null,headRowEl:null,initialize:function(){this.dayGrid=this.instantiateDayGrid(),this.scroller=new he({overflowX:"hidden",overflowY:"auto"})},instantiateDayGrid:function(){var t=this.dayGridClass.extend(be);return new t(this)},setRange:function(t){de.prototype.setRange.call(this,t),this.dayGrid.breakOnWeeks=/year|month|week/.test(this.intervalUnit),this.dayGrid.setRange(t)},computeRange:function(t){var e=de.prototype.computeRange.call(this,t);return/year|month/.test(e.intervalUnit)&&(e.start.startOf("week"),e.start=this.skipHiddenDays(e.start),e.end.weekday()&&(e.end.add(1,"week").startOf("week"),e.end=this.skipHiddenDays(e.end,-1,!0))),e},renderDates:function(){this.dayNumbersVisible=this.dayGrid.rowCnt>1,this.opt("weekNumbers")&&(this.opt("weekNumbersWithinDays")?(this.cellWeekNumbersVisible=!0,this.colWeekNumbersVisible=!1):(this.cellWeekNumbersVisible=!1,this.colWeekNumbersVisible=!0)),this.dayGrid.numbersVisible=this.dayNumbersVisible||this.cellWeekNumbersVisible||this.colWeekNumbersVisible,this.el.addClass("fc-basic-view").html(this.renderSkeletonHtml()),this.renderHead(),this.scroller.render();var e=this.scroller.el.addClass("fc-day-grid-container"),n=t('<div class="fc-day-grid" />').appendTo(e);this.el.find(".fc-body > tr > td").append(e),this.dayGrid.setElement(n),this.dayGrid.renderDates(this.hasRigidRows())},renderHead:function(){this.headContainerEl=this.el.find(".fc-head-container").html(this.dayGrid.renderHeadHtml()),this.headRowEl=this.headContainerEl.find(".fc-row")},unrenderDates:function(){this.dayGrid.unrenderDates(),this.dayGrid.removeElement(),this.scroller.destroy()},renderBusinessHours:function(){this.dayGrid.renderBusinessHours()},unrenderBusinessHours:function(){this.dayGrid.unrenderBusinessHours()},renderSkeletonHtml:function(){return'<table><thead class="fc-head"><tr><td class="fc-head-container '+this.widgetHeaderClass+'"></td></tr></thead><tbody class="fc-body"><tr><td class="'+this.widgetContentClass+'"></td></tr></tbody></table>'},weekNumberStyleAttr:function(){return null!==this.weekNumberWidth?'style="width:'+this.weekNumberWidth+'px"':""},hasRigidRows:function(){var t=this.opt("eventLimit");return t&&"number"!=typeof t},updateWidth:function(){this.colWeekNumbersVisible&&(this.weekNumberWidth=u(this.el.find(".fc-week-number")))},setHeight:function(t,e){var n,s,o=this.opt("eventLimit");this.scroller.clear(),r(this.headRowEl),this.dayGrid.removeSegPopover(),o&&"number"==typeof o&&this.dayGrid.limitRows(o),n=this.computeScrollerHeight(t),this.setGridHeight(n,e),o&&"number"!=typeof o&&this.dayGrid.limitRows(o),e||(this.scroller.setHeight(n),s=this.scroller.getScrollbarWidths(),(s.left||s.right)&&(i(this.headRowEl,s),n=this.computeScrollerHeight(t),this.scroller.setHeight(n)),this.scroller.lockOverflow(s))},computeScrollerHeight:function(t){return t-c(this.el,this.scroller.el)},setGridHeight:function(t,e){e?a(this.dayGrid.rowEls):l(this.dayGrid.rowEls,t,!0)},computeInitialScroll:function(){return{top:0}},queryScroll:function(){return{top:this.scroller.getScrollTop()}},setScroll:function(t){this.scroller.setScrollTop(t.top)},hitsNeeded:function(){this.dayGrid.hitsNeeded()},hitsNotNeeded:function(){this.dayGrid.hitsNotNeeded()},prepareHits:function(){this.dayGrid.prepareHits()},releaseHits:function(){this.dayGrid.releaseHits()},queryHit:function(t,e){return this.dayGrid.queryHit(t,e)},getHitSpan:function(t){return this.dayGrid.getHitSpan(t)},getHitEl:function(t){return this.dayGrid.getHitEl(t)},renderEvents:function(t){this.dayGrid.renderEvents(t),this.updateHeight()},getEventSegs:function(){return this.dayGrid.getEventSegs()},unrenderEvents:function(){this.dayGrid.unrenderEvents()},renderDrag:function(t,e){return this.dayGrid.renderDrag(t,e)},unrenderDrag:function(){this.dayGrid.unrenderDrag()},renderSelection:function(t){this.dayGrid.renderSelection(t)},unrenderSelection:function(){this.dayGrid.unrenderSelection()}}),be={renderHeadIntroHtml:function(){var t=this.view;return t.colWeekNumbersVisible?'<th class="fc-week-number '+t.widgetHeaderClass+'" '+t.weekNumberStyleAttr()+"><span>"+tt(t.opt("weekNumberTitle"))+"</span></th>":""},renderNumberIntroHtml:function(t){var e=this.view,n=this.getCellDate(t,0);return e.colWeekNumbersVisible?'<td class="fc-week-number" '+e.weekNumberStyleAttr()+">"+e.buildGotoAnchorHtml({date:n,type:"week",forceOff:1===this.colCnt},n.format("w"))+"</td>":""},renderBgIntroHtml:function(){var t=this.view;return t.colWeekNumbersVisible?'<td class="fc-week-number '+t.widgetContentClass+'" '+t.weekNumberStyleAttr()+"></td>":""},renderIntroHtml:function(){var t=this.view;return t.colWeekNumbersVisible?'<td class="fc-week-number" '+t.weekNumberStyleAttr()+"></td>":""}},De=Ot.MonthView=Ee.extend({computeRange:function(t){var e,n=Ee.prototype.computeRange.call(this,t);return this.isFixedWeeks()&&(e=Math.ceil(n.end.diff(n.start,"weeks",!0)),n.end.add(6-e,"weeks")),n},setGridHeight:function(t,e){e&&(t*=this.rowCnt/6),l(this.dayGrid.rowEls,t,!e)},isFixedWeeks:function(){return this.opt("fixedWeekCount")}});At.basic={class:Ee},At.basicDay={type:"basic",duration:{days:1}},At.basicWeek={type:"basic",duration:{weeks:1}},At.month={class:De,duration:{months:1},defaults:{fixedWeekCount:!0}};var Te=Ot.AgendaView=de.extend({scroller:null,timeGridClass:ce,timeGrid:null,dayGridClass:ue,dayGrid:null,axisWidth:null,headContainerEl:null,noScrollRowEls:null,bottomRuleEl:null,initialize:function(){this.timeGrid=this.instantiateTimeGrid(),this.opt("allDaySlot")&&(this.dayGrid=this.instantiateDayGrid()),this.scroller=new he({overflowX:"hidden",overflowY:"auto"})},instantiateTimeGrid:function(){var t=this.timeGridClass.extend(Ce);return new t(this)},instantiateDayGrid:function(){var t=this.dayGridClass.extend(He);return new t(this)},setRange:function(t){de.prototype.setRange.call(this,t),this.timeGrid.setRange(t),this.dayGrid&&this.dayGrid.setRange(t)},renderDates:function(){this.el.addClass("fc-agenda-view").html(this.renderSkeletonHtml()),this.renderHead(),this.scroller.render();var e=this.scroller.el.addClass("fc-time-grid-container"),n=t('<div class="fc-time-grid" />').appendTo(e);this.el.find(".fc-body > tr > td").append(e),this.timeGrid.setElement(n),this.timeGrid.renderDates(),this.bottomRuleEl=t('<hr class="fc-divider '+this.widgetHeaderClass+'"/>').appendTo(this.timeGrid.el),this.dayGrid&&(this.dayGrid.setElement(this.el.find(".fc-day-grid")),this.dayGrid.renderDates(),this.dayGrid.bottomCoordPadding=this.dayGrid.el.next("hr").outerHeight()),this.noScrollRowEls=this.el.find(".fc-row:not(.fc-scroller *)")},renderHead:function(){this.headContainerEl=this.el.find(".fc-head-container").html(this.timeGrid.renderHeadHtml())},unrenderDates:function(){this.timeGrid.unrenderDates(),this.timeGrid.removeElement(),this.dayGrid&&(this.dayGrid.unrenderDates(),this.dayGrid.removeElement()),this.scroller.destroy()},renderSkeletonHtml:function(){return'<table><thead class="fc-head"><tr><td class="fc-head-container '+this.widgetHeaderClass+'"></td></tr></thead><tbody class="fc-body"><tr><td class="'+this.widgetContentClass+'">'+(this.dayGrid?'<div class="fc-day-grid"/><hr class="fc-divider '+this.widgetHeaderClass+'"/>':"")+"</td></tr></tbody></table>"},axisStyleAttr:function(){return null!==this.axisWidth?'style="width:'+this.axisWidth+'px"':""},renderBusinessHours:function(){this.timeGrid.renderBusinessHours(),this.dayGrid&&this.dayGrid.renderBusinessHours()},unrenderBusinessHours:function(){this.timeGrid.unrenderBusinessHours(),this.dayGrid&&this.dayGrid.unrenderBusinessHours()},getNowIndicatorUnit:function(){return this.timeGrid.getNowIndicatorUnit()},renderNowIndicator:function(t){this.timeGrid.renderNowIndicator(t)},unrenderNowIndicator:function(){this.timeGrid.unrenderNowIndicator()},updateSize:function(t){this.timeGrid.updateSize(t),de.prototype.updateSize.call(this,t)},updateWidth:function(){this.axisWidth=u(this.el.find(".fc-axis"))},setHeight:function(t,e){var n,s,o;this.bottomRuleEl.hide(),this.scroller.clear(),r(this.noScrollRowEls),this.dayGrid&&(this.dayGrid.removeSegPopover(),n=this.opt("eventLimit"),n&&"number"!=typeof n&&(n=xe),n&&this.dayGrid.limitRows(n)),e||(s=this.computeScrollerHeight(t),this.scroller.setHeight(s),o=this.scroller.getScrollbarWidths(),(o.left||o.right)&&(i(this.noScrollRowEls,o),s=this.computeScrollerHeight(t),this.scroller.setHeight(s)),this.scroller.lockOverflow(o),this.timeGrid.getTotalSlatHeight()<s&&this.bottomRuleEl.show())},computeScrollerHeight:function(t){return t-c(this.el,this.scroller.el)},computeInitialScroll:function(){var t=e.duration(this.opt("scrollTime")),n=this.timeGrid.computeTimeTop(t);return n=Math.ceil(n),n&&n++,{top:n}},queryScroll:function(){return{top:this.scroller.getScrollTop()}},setScroll:function(t){this.scroller.setScrollTop(t.top)},hitsNeeded:function(){this.timeGrid.hitsNeeded(),this.dayGrid&&this.dayGrid.hitsNeeded()},hitsNotNeeded:function(){this.timeGrid.hitsNotNeeded(),this.dayGrid&&this.dayGrid.hitsNotNeeded()},prepareHits:function(){this.timeGrid.prepareHits(),this.dayGrid&&this.dayGrid.prepareHits();
+},releaseHits:function(){this.timeGrid.releaseHits(),this.dayGrid&&this.dayGrid.releaseHits()},queryHit:function(t,e){var n=this.timeGrid.queryHit(t,e);return!n&&this.dayGrid&&(n=this.dayGrid.queryHit(t,e)),n},getHitSpan:function(t){return t.component.getHitSpan(t)},getHitEl:function(t){return t.component.getHitEl(t)},renderEvents:function(t){var e,n,i=[],r=[],s=[];for(n=0;n<t.length;n++)t[n].allDay?i.push(t[n]):r.push(t[n]);e=this.timeGrid.renderEvents(r),this.dayGrid&&(s=this.dayGrid.renderEvents(i)),this.updateHeight()},getEventSegs:function(){return this.timeGrid.getEventSegs().concat(this.dayGrid?this.dayGrid.getEventSegs():[])},unrenderEvents:function(){this.timeGrid.unrenderEvents(),this.dayGrid&&this.dayGrid.unrenderEvents()},renderDrag:function(t,e){return t.start.hasTime()?this.timeGrid.renderDrag(t,e):this.dayGrid?this.dayGrid.renderDrag(t,e):void 0},unrenderDrag:function(){this.timeGrid.unrenderDrag(),this.dayGrid&&this.dayGrid.unrenderDrag()},renderSelection:function(t){t.start.hasTime()||t.end.hasTime()?this.timeGrid.renderSelection(t):this.dayGrid&&this.dayGrid.renderSelection(t)},unrenderSelection:function(){this.timeGrid.unrenderSelection(),this.dayGrid&&this.dayGrid.unrenderSelection()}}),Ce={renderHeadIntroHtml:function(){var t,e=this.view;return e.opt("weekNumbers")?(t=this.start.format(e.opt("smallWeekFormat")),'<th class="fc-axis fc-week-number '+e.widgetHeaderClass+'" '+e.axisStyleAttr()+">"+e.buildGotoAnchorHtml({date:this.start,type:"week",forceOff:this.colCnt>1},tt(t))+"</th>"):'<th class="fc-axis '+e.widgetHeaderClass+'" '+e.axisStyleAttr()+"></th>"},renderBgIntroHtml:function(){var t=this.view;return'<td class="fc-axis '+t.widgetContentClass+'" '+t.axisStyleAttr()+"></td>"},renderIntroHtml:function(){var t=this.view;return'<td class="fc-axis" '+t.axisStyleAttr()+"></td>"}},He={renderBgIntroHtml:function(){var t=this.view;return'<td class="fc-axis '+t.widgetContentClass+'" '+t.axisStyleAttr()+"><span>"+t.getAllDayHtml()+"</span></td>"},renderIntroHtml:function(){var t=this.view;return'<td class="fc-axis" '+t.axisStyleAttr()+"></td>"}},xe=5,Re=[{hours:1},{minutes:30},{minutes:15},{seconds:30},{seconds:15}];At.agenda={class:Te,defaults:{allDaySlot:!0,slotDuration:"00:30:00",minTime:"00:00:00",maxTime:"24:00:00",slotEventOverlap:!0}},At.agendaDay={type:"agenda",duration:{days:1}},At.agendaWeek={type:"agenda",duration:{weeks:1}};var Ie=de.extend({grid:null,scroller:null,initialize:function(){this.grid=new ke(this),this.scroller=new he({overflowX:"hidden",overflowY:"auto"})},setRange:function(t){de.prototype.setRange.call(this,t),this.grid.setRange(t)},renderSkeleton:function(){this.el.addClass("fc-list-view "+this.widgetContentClass),this.scroller.render(),this.scroller.el.appendTo(this.el),this.grid.setElement(this.scroller.scrollEl)},unrenderSkeleton:function(){this.scroller.destroy()},setHeight:function(t,e){this.scroller.setHeight(this.computeScrollerHeight(t))},computeScrollerHeight:function(t){return t-c(this.el,this.scroller.el)},renderEvents:function(t){this.grid.renderEvents(t)},unrenderEvents:function(){this.grid.unrenderEvents()},isEventResizable:function(t){return!1},isEventDraggable:function(t){return!1}}),ke=le.extend({segSelector:".fc-list-item",hasDayInteractions:!1,spanToSegs:function(t){for(var e,n=this.view,i=n.start.clone().time(0),r=0,s=[];i<n.end;)if(e=F(t,{start:i,end:i.clone().add(1,"day")}),e&&(e.dayIndex=r,s.push(e)),i.add(1,"day"),r++,e&&!e.isEnd&&t.end.hasTime()&&t.end<i.clone().add(this.view.nextDayThreshold)){e.end=t.end.clone(),e.isEnd=!0;break}return s},computeEventTimeFormat:function(){return this.view.opt("mediumTimeFormat")},handleSegClick:function(e,n){var i;le.prototype.handleSegClick.apply(this,arguments),t(n.target).closest("a[href]").length||(i=e.event.url,i&&!n.isDefaultPrevented()&&(window.location.href=i))},renderFgSegs:function(t){return t=this.renderFgSegEls(t),t.length?this.renderSegList(t):this.renderEmptyMessage(),t},renderEmptyMessage:function(){this.el.html('<div class="fc-list-empty-wrap2"><div class="fc-list-empty-wrap1"><div class="fc-list-empty">'+tt(this.view.opt("noEventsMessage"))+"</div></div></div>")},renderSegList:function(e){var n,i,r,s=this.groupSegsByDay(e),o=t('<table class="fc-list-table"><tbody/></table>'),l=o.find("tbody");for(n=0;n<s.length;n++)if(i=s[n])for(l.append(this.dayHeaderHtml(this.view.start.clone().add(n,"days"))),this.sortEventSegs(i),r=0;r<i.length;r++)l.append(i[r].el);this.el.empty().append(o)},groupSegsByDay:function(t){var e,n,i=[];for(e=0;e<t.length;e++)n=t[e],(i[n.dayIndex]||(i[n.dayIndex]=[])).push(n);return i},dayHeaderHtml:function(t){var e=this.view,n=e.opt("listDayFormat"),i=e.opt("listDayAltFormat");return'<tr class="fc-list-heading" data-date="'+t.format("YYYY-MM-DD")+'"><td class="'+e.widgetHeaderClass+'" colspan="3">'+(n?e.buildGotoAnchorHtml(t,{class:"fc-list-heading-main"},tt(t.format(n))):"")+(i?e.buildGotoAnchorHtml(t,{class:"fc-list-heading-alt"},tt(t.format(i))):"")+"</td></tr>"},fgSegHtml:function(t){var e,n=this.view,i=["fc-list-item"].concat(this.getSegCustomClasses(t)),r=this.getSegBackgroundColor(t),s=t.event,o=s.url;return e=s.allDay?n.getAllDayHtml():n.isMultiDayEvent(s)?t.isStart||t.isEnd?tt(this.getEventTimeText(t)):n.getAllDayHtml():tt(this.getEventTimeText(s)),o&&i.push("fc-has-url"),'<tr class="'+i.join(" ")+'">'+(this.displayEventTime?'<td class="fc-list-item-time '+n.widgetContentClass+'">'+(e||"")+"</td>":"")+'<td class="fc-list-item-marker '+n.widgetContentClass+'"><span class="fc-event-dot"'+(r?' style="background-color:'+r+'"':"")+'></span></td><td class="fc-list-item-title '+n.widgetContentClass+'"><a'+(o?' href="'+tt(o)+'"':"")+">"+tt(t.event.title||"")+"</a></td></tr>"}});return At.list={class:Ie,buttonTextKey:"list",defaults:{buttonText:"list",listDayFormat:"LL",noEventsMessage:"No events to display"}},At.listDay={type:"list",duration:{days:1},defaults:{listDayFormat:"dddd"}},At.listWeek={type:"list",duration:{weeks:1},defaults:{listDayFormat:"dddd",listDayAltFormat:"LL"}},At.listMonth={type:"list",duration:{month:1},defaults:{listDayAltFormat:"dddd"}},At.listYear={type:"list",duration:{year:1},defaults:{listDayAltFormat:"dddd"}},Ot}); \ No newline at end of file
diff --git a/library/fullcalendar/fullcalendar.print.css b/library/fullcalendar/fullcalendar.print.css
index 5e1183071..c92bdd9df 100644
--- a/library/fullcalendar/fullcalendar.print.css
+++ b/library/fullcalendar/fullcalendar.print.css
@@ -1,7 +1,7 @@
/*!
- * FullCalendar v3.1.0 Print Stylesheet
- * Docs & License: http://fullcalendar.io/
- * (c) 2016 Adam Shaw
+ * FullCalendar v3.2.0 Print Stylesheet
+ * Docs & License: https://fullcalendar.io/
+ * (c) 2017 Adam Shaw
*/
/*
diff --git a/library/fullcalendar/fullcalendar.print.min.css b/library/fullcalendar/fullcalendar.print.min.css
index 05281cf21..c193968d7 100644
--- a/library/fullcalendar/fullcalendar.print.min.css
+++ b/library/fullcalendar/fullcalendar.print.min.css
@@ -1,5 +1,5 @@
/*!
- * FullCalendar v3.1.0 Print Stylesheet
- * Docs & License: http://fullcalendar.io/
- * (c) 2016 Adam Shaw
+ * FullCalendar v3.2.0 Print Stylesheet
+ * Docs & License: https://fullcalendar.io/
+ * (c) 2017 Adam Shaw
*/.fc-bg,.fc-bgevent-container,.fc-bgevent-skeleton,.fc-business-container,.fc-event .fc-resizer,.fc-helper-container,.fc-helper-skeleton,.fc-highlight-container,.fc-highlight-skeleton{display:none}.fc tbody .fc-row,.fc-time-grid{min-height:0!important}.fc-time-grid .fc-event.fc-not-end:after,.fc-time-grid .fc-event.fc-not-start:before{content:"..."}.fc{max-width:100%!important}.fc-event{background:#fff!important;color:#000!important;page-break-inside:avoid}.fc hr,.fc tbody,.fc td,.fc th,.fc thead,.fc-row{border-color:#ccc!important;background:#fff!important}.fc tbody .fc-row{height:auto!important}.fc tbody .fc-row .fc-content-skeleton{position:static;padding-bottom:0!important}.fc tbody .fc-row .fc-content-skeleton tbody tr:last-child td{padding-bottom:1em}.fc tbody .fc-row .fc-content-skeleton table{height:1em}.fc-more,.fc-more-cell{display:none!important}.fc tr.fc-limited{display:table-row!important}.fc td.fc-limited{display:table-cell!important}.fc-agenda-view .fc-axis,.fc-popover{display:none}.fc-slats,.fc-time-grid hr{display:none!important}.fc button,.fc-button-group,.fc-time-grid .fc-event .fc-time span{display:none}.fc-time-grid .fc-content-skeleton{position:static}.fc-time-grid .fc-content-skeleton table{height:4em}.fc-time-grid .fc-event-container{margin:0!important}.fc-time-grid .fc-event{position:static!important;margin:3px 2px!important}.fc-time-grid .fc-event.fc-not-end{border-bottom-width:1px!important}.fc-time-grid .fc-event.fc-not-start{border-top-width:1px!important}.fc-time-grid .fc-event .fc-time{white-space:normal!important}.fc-time-grid .fc-event .fc-time:after{content:attr(data-full)}.fc-day-grid-container,.fc-scroller,.fc-time-grid-container{overflow:visible!important;height:auto!important}.fc-row{border:0!important;margin:0!important} \ No newline at end of file
diff --git a/library/fullcalendar/gcal.js b/library/fullcalendar/gcal.js
index 1975cca72..7e895337e 100644
--- a/library/fullcalendar/gcal.js
+++ b/library/fullcalendar/gcal.js
@@ -1,7 +1,7 @@
/*!
- * FullCalendar v3.1.0 Google Calendar Plugin
- * Docs & License: http://fullcalendar.io/
- * (c) 2016 Adam Shaw
+ * FullCalendar v3.2.0 Google Calendar Plugin
+ * Docs & License: https://fullcalendar.io/
+ * (c) 2017 Adam Shaw
*/
(function(factory) {
diff --git a/library/fullcalendar/gcal.min.js b/library/fullcalendar/gcal.min.js
index 08876848f..02e7ea4d5 100644
--- a/library/fullcalendar/gcal.min.js
+++ b/library/fullcalendar/gcal.min.js
@@ -1,6 +1,6 @@
/*!
- * FullCalendar v3.1.0 Google Calendar Plugin
- * Docs & License: http://fullcalendar.io/
- * (c) 2016 Adam Shaw
+ * FullCalendar v3.2.0 Google Calendar Plugin
+ * Docs & License: https://fullcalendar.io/
+ * (c) 2017 Adam Shaw
*/
!function(e){"function"==typeof define&&define.amd?define(["jquery"],e):"object"==typeof exports?module.exports=e(require("jquery")):e(jQuery)}(function(e){function a(a,t,d,c,i){function s(o,r){var l=r||[{message:o}];(a.googleCalendarError||e.noop).apply(i,l),(i.options.googleCalendarError||e.noop).apply(i,l),n.warn.apply(null,[o].concat(r||[]))}var u,g,p=r+"/"+encodeURIComponent(a.googleCalendarId)+"/events?callback=?",m=a.googleCalendarApiKey||i.options.googleCalendarApiKey,f=a.success;return m?(t.hasZone()||(t=t.clone().utc().add(-1,"day")),d.hasZone()||(d=d.clone().utc().add(1,"day")),c&&"local"!=c&&(g=c.replace(" ","_")),u=e.extend({},a.data||{},{key:m,timeMin:t.format(),timeMax:d.format(),timeZone:g,singleEvents:!0,maxResults:9999}),e.extend({},a,{googleCalendarId:null,url:p,data:u,startParam:!1,endParam:!1,timezoneParam:!1,success:function(a){var r,n,t=[];if(a.error)s("Google Calendar API: "+a.error.message,a.error.errors);else if(a.items&&(e.each(a.items,function(e,a){var r=a.htmlLink||null;g&&null!==r&&(r=o(r,"ctz="+g)),t.push({id:a.id,title:a.summary,start:a.start.dateTime||a.start.date,end:a.end.dateTime||a.end.date,url:r,location:a.location,description:a.description})}),r=[t].concat(Array.prototype.slice.call(arguments,1)),n=l(f,this,r),e.isArray(n)))return n;return t}})):(s("Specify a googleCalendarApiKey. See http://fullcalendar.io/docs/google_calendar/"),{})}function o(e,a){return e.replace(/(\?.*?)?(#|$)/,function(e,o,r){return(o?o+"&":"?")+a+r})}var r="https://www.googleapis.com/calendar/v3/calendars",n=e.fullCalendar,l=n.applyAll;n.sourceNormalizers.push(function(e){var a,o=e.googleCalendarId,r=e.url;!o&&r&&(/^[^\/]+@([^\/\.]+\.)*(google|googlemail|gmail)\.com$/.test(r)?o=r:((a=/^https:\/\/www.googleapis.com\/calendar\/v3\/calendars\/([^\/]*)/.exec(r))||(a=/^https?:\/\/www.google.com\/calendar\/feeds\/([^\/]*)/.exec(r)))&&(o=decodeURIComponent(a[1])),o&&(e.googleCalendarId=o)),o&&(null==e.editable&&(e.editable=!1),e.url=o)}),n.sourceFetchers.push(function(e,o,r,n){if(e.googleCalendarId)return a(e,o,r,n,this)})}); \ No newline at end of file
diff --git a/library/fullcalendar/locale-all.js b/library/fullcalendar/locale-all.js
index a648a74bc..689a86e07 100644
--- a/library/fullcalendar/locale-all.js
+++ b/library/fullcalendar/locale-all.js
@@ -1,5 +1,5 @@
!function(e){"function"==typeof define&&define.amd?define(["jquery","moment"],e):"object"==typeof exports?module.exports=e(require("jquery"),require("moment")):e(jQuery,moment)}(function(e,a){!function(){!function(){var e=a.defineLocale("af",{months:"Januarie_Februarie_Maart_April_Mei_Junie_Julie_Augustus_September_Oktober_November_Desember".split("_"),monthsShort:"Jan_Feb_Mrt_Apr_Mei_Jun_Jul_Aug_Sep_Okt_Nov_Des".split("_"),weekdays:"Sondag_Maandag_Dinsdag_Woensdag_Donderdag_Vrydag_Saterdag".split("_"),weekdaysShort:"Son_Maa_Din_Woe_Don_Vry_Sat".split("_"),weekdaysMin:"So_Ma_Di_Wo_Do_Vr_Sa".split("_"),meridiemParse:/vm|nm/i,isPM:function(e){return/^nm$/i.test(e)},meridiem:function(e,a,t){return e<12?t?"vm":"VM":t?"nm":"NM"},longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd, D MMMM YYYY HH:mm"},calendar:{sameDay:"[Vandag om] LT",nextDay:"[Môre om] LT",nextWeek:"dddd [om] LT",lastDay:"[Gister om] LT",lastWeek:"[Laas] dddd [om] LT",sameElse:"L"},relativeTime:{future:"oor %s",past:"%s gelede",s:"'n paar sekondes",m:"'n minuut",mm:"%d minute",h:"'n uur",hh:"%d ure",d:"'n dag",dd:"%d dae",M:"'n maand",MM:"%d maande",y:"'n jaar",yy:"%d jaar"},ordinalParse:/\d{1,2}(ste|de)/,ordinal:function(e){return e+(1===e||8===e||e>=20?"ste":"de")},week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("af","af",{closeText:"Selekteer",prevText:"Vorige",nextText:"Volgende",currentText:"Vandag",monthNames:["Januarie","Februarie","Maart","April","Mei","Junie","Julie","Augustus","September","Oktober","November","Desember"],monthNamesShort:["Jan","Feb","Mrt","Apr","Mei","Jun","Jul","Aug","Sep","Okt","Nov","Des"],dayNames:["Sondag","Maandag","Dinsdag","Woensdag","Donderdag","Vrydag","Saterdag"],dayNamesShort:["Son","Maa","Din","Woe","Don","Vry","Sat"],dayNamesMin:["So","Ma","Di","Wo","Do","Vr","Sa"],weekHeader:"Wk",dateFormat:"dd/mm/yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("af",{buttonText:{year:"Jaar",month:"Maand",week:"Week",day:"Dag",list:"Agenda"},allDayHtml:"Heeldag",eventLimitText:"Addisionele",noEventsMessage:"Daar is geen gebeurtenis"})}(),function(){!function(){var e={1:"١",2:"٢",3:"٣",4:"٤",5:"٥",6:"٦",7:"٧",8:"٨",9:"٩",0:"٠"},t={"١":"1","٢":"2","٣":"3","٤":"4","٥":"5","٦":"6","٧":"7","٨":"8","٩":"9","٠":"0"},n=function(e){return 0===e?0:1===e?1:2===e?2:e%100>=3&&e%100<=10?3:e%100>=11?4:5},r={s:["أقل من ثانية","ثانية واحدة",["ثانيتان","ثانيتين"],"%d ثوان","%d ثانية","%d ثانية"],m:["أقل من دقيقة","دقيقة واحدة",["دقيقتان","دقيقتين"],"%d دقائق","%d دقيقة","%d دقيقة"],h:["أقل من ساعة","ساعة واحدة",["ساعتان","ساعتين"],"%d ساعات","%d ساعة","%d ساعة"],d:["أقل من يوم","يوم واحد",["يومان","يومين"],"%d أيام","%d يومًا","%d يوم"],M:["أقل من شهر","شهر واحد",["شهران","شهرين"],"%d أشهر","%d شهرا","%d شهر"],y:["أقل من عام","عام واحد",["عامان","عامين"],"%d أعوام","%d عامًا","%d عام"]},s=function(e){return function(a,t,s,d){var i=n(a),o=r[e][n(a)];return 2===i&&(o=o[t?0:1]),o.replace(/%d/i,a)}},d=["كانون الثاني يناير","شباط فبراير","آذار مارس","نيسان أبريل","أيار مايو","حزيران يونيو","تموز يوليو","آب أغسطس","أيلول سبتمبر","تشرين الأول أكتوبر","تشرين الثاني نوفمبر","كانون الأول ديسمبر"],i=a.defineLocale("ar",{months:d,monthsShort:d,weekdays:"الأحد_الإثنين_الثلاثاء_الأربعاء_الخميس_الجمعة_السبت".split("_"),weekdaysShort:"أحد_إثنين_ثلاثاء_أربعاء_خميس_جمعة_سبت".split("_"),weekdaysMin:"ح_ن_ث_ر_خ_ج_س".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"D/‏M/‏YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd D MMMM YYYY HH:mm"},meridiemParse:/ص|م/,isPM:function(e){return"م"===e},meridiem:function(e,a,t){return e<12?"ص":"م"},calendar:{sameDay:"[اليوم عند الساعة] LT",nextDay:"[غدًا عند الساعة] LT",nextWeek:"dddd [عند الساعة] LT",lastDay:"[أمس عند الساعة] LT",lastWeek:"dddd [عند الساعة] LT",sameElse:"L"},relativeTime:{future:"بعد %s",past:"منذ %s",s:s("s"),m:s("m"),mm:s("m"),h:s("h"),hh:s("h"),d:s("d"),dd:s("d"),M:s("M"),MM:s("M"),y:s("y"),yy:s("y")},preparse:function(e){return e.replace(/\u200f/g,"").replace(/[١٢٣٤٥٦٧٨٩٠]/g,function(e){return t[e]}).replace(/،/g,",")},postformat:function(a){return a.replace(/\d/g,function(a){return e[a]}).replace(/,/g,"،")},week:{dow:6,doy:12}});return i}(),e.fullCalendar.datepickerLocale("ar","ar",{closeText:"إغلاق",prevText:"&#x3C;السابق",nextText:"التالي&#x3E;",currentText:"اليوم",monthNames:["يناير","فبراير","مارس","أبريل","مايو","يونيو","يوليو","أغسطس","سبتمبر","أكتوبر","نوفمبر","ديسمبر"],monthNamesShort:["1","2","3","4","5","6","7","8","9","10","11","12"],dayNames:["الأحد","الاثنين","الثلاثاء","الأربعاء","الخميس","الجمعة","السبت"],dayNamesShort:["أحد","اثنين","ثلاثاء","أربعاء","خميس","جمعة","سبت"],dayNamesMin:["ح","ن","ث","ر","خ","ج","س"],weekHeader:"أسبوع",dateFormat:"dd/mm/yy",firstDay:0,isRTL:!0,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("ar",{buttonText:{month:"شهر",week:"أسبوع",day:"يوم",list:"أجندة"},allDayText:"اليوم كله",eventLimitText:"أخرى",noEventsMessage:"أي أحداث لعرض"})}(),function(){!function(){var e=a.defineLocale("ar-dz",{months:"جانفي_فيفري_مارس_أفريل_ماي_جوان_جويلية_أوت_سبتمبر_أكتوبر_نوفمبر_ديسمبر".split("_"),monthsShort:"جانفي_فيفري_مارس_أفريل_ماي_جوان_جويلية_أوت_سبتمبر_أكتوبر_نوفمبر_ديسمبر".split("_"),weekdays:"الأحد_الإثنين_الثلاثاء_الأربعاء_الخميس_الجمعة_السبت".split("_"),weekdaysShort:"احد_اثنين_ثلاثاء_اربعاء_خميس_جمعة_سبت".split("_"),weekdaysMin:"أح_إث_ثلا_أر_خم_جم_سب".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd D MMMM YYYY HH:mm"},calendar:{sameDay:"[اليوم على الساعة] LT",nextDay:"[غدا على الساعة] LT",nextWeek:"dddd [على الساعة] LT",lastDay:"[أمس على الساعة] LT",lastWeek:"dddd [على الساعة] LT",sameElse:"L"},relativeTime:{future:"في %s",past:"منذ %s",s:"ثوان",m:"دقيقة",mm:"%d دقائق",h:"ساعة",hh:"%d ساعات",d:"يوم",dd:"%d أيام",M:"شهر",MM:"%d أشهر",y:"سنة",yy:"%d سنوات"},week:{dow:0,doy:4}});return e}(),e.fullCalendar.datepickerLocale("ar-dz","ar-DZ",{closeText:"إغلاق",prevText:"&#x3C;السابق",nextText:"التالي&#x3E;",currentText:"اليوم",monthNames:["جانفي","فيفري","مارس","أفريل","ماي","جوان","جويلية","أوت","سبتمبر","أكتوبر","نوفمبر","ديسمبر"],monthNamesShort:["1","2","3","4","5","6","7","8","9","10","11","12"],dayNames:["الأحد","الاثنين","الثلاثاء","الأربعاء","الخميس","الجمعة","السبت"],dayNamesShort:["الأحد","الاثنين","الثلاثاء","الأربعاء","الخميس","الجمعة","السبت"],dayNamesMin:["ح","ن","ث","ر","خ","ج","س"],weekHeader:"أسبوع",dateFormat:"dd/mm/yy",firstDay:6,isRTL:!0,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("ar-dz",{buttonText:{month:"شهر",week:"أسبوع",day:"يوم",list:"أجندة"},allDayText:"اليوم كله",eventLimitText:"أخرى",noEventsMessage:"أي أحداث لعرض"})}(),function(){!function(){var e={1:"1",2:"2",3:"3",4:"4",5:"5",6:"6",7:"7",8:"8",9:"9",0:"0"},t=function(e){return 0===e?0:1===e?1:2===e?2:e%100>=3&&e%100<=10?3:e%100>=11?4:5},n={s:["أقل من ثانية","ثانية واحدة",["ثانيتان","ثانيتين"],"%d ثوان","%d ثانية","%d ثانية"],m:["أقل من دقيقة","دقيقة واحدة",["دقيقتان","دقيقتين"],"%d دقائق","%d دقيقة","%d دقيقة"],h:["أقل من ساعة","ساعة واحدة",["ساعتان","ساعتين"],"%d ساعات","%d ساعة","%d ساعة"],d:["أقل من يوم","يوم واحد",["يومان","يومين"],"%d أيام","%d يومًا","%d يوم"],M:["أقل من شهر","شهر واحد",["شهران","شهرين"],"%d أشهر","%d شهرا","%d شهر"],y:["أقل من عام","عام واحد",["عامان","عامين"],"%d أعوام","%d عامًا","%d عام"]},r=function(e){return function(a,r,s,d){var i=t(a),o=n[e][t(a)];return 2===i&&(o=o[r?0:1]),o.replace(/%d/i,a)}},s=["يناير","فبراير","مارس","أبريل","مايو","يونيو","يوليو","أغسطس","سبتمبر","أكتوبر","نوفمبر","ديسمبر"],d=a.defineLocale("ar-ly",{months:s,monthsShort:s,weekdays:"الأحد_الإثنين_الثلاثاء_الأربعاء_الخميس_الجمعة_السبت".split("_"),weekdaysShort:"أحد_إثنين_ثلاثاء_أربعاء_خميس_جمعة_سبت".split("_"),weekdaysMin:"ح_ن_ث_ر_خ_ج_س".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"D/‏M/‏YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd D MMMM YYYY HH:mm"},meridiemParse:/ص|م/,isPM:function(e){return"م"===e},meridiem:function(e,a,t){return e<12?"ص":"م"},calendar:{sameDay:"[اليوم عند الساعة] LT",nextDay:"[غدًا عند الساعة] LT",nextWeek:"dddd [عند الساعة] LT",lastDay:"[أمس عند الساعة] LT",lastWeek:"dddd [عند الساعة] LT",sameElse:"L"},relativeTime:{future:"بعد %s",past:"منذ %s",s:r("s"),m:r("m"),mm:r("m"),h:r("h"),hh:r("h"),d:r("d"),dd:r("d"),M:r("M"),MM:r("M"),y:r("y"),yy:r("y")},preparse:function(e){return e.replace(/\u200f/g,"").replace(/،/g,",")},postformat:function(a){return a.replace(/\d/g,function(a){return e[a]}).replace(/,/g,"،")},week:{dow:6,doy:12}});return d}(),e.fullCalendar.datepickerLocale("ar-ly","ar",{closeText:"إغلاق",prevText:"&#x3C;السابق",nextText:"التالي&#x3E;",currentText:"اليوم",monthNames:["يناير","فبراير","مارس","أبريل","مايو","يونيو","يوليو","أغسطس","سبتمبر","أكتوبر","نوفمبر","ديسمبر"],monthNamesShort:["1","2","3","4","5","6","7","8","9","10","11","12"],dayNames:["الأحد","الاثنين","الثلاثاء","الأربعاء","الخميس","الجمعة","السبت"],dayNamesShort:["أحد","اثنين","ثلاثاء","أربعاء","خميس","جمعة","سبت"],dayNamesMin:["ح","ن","ث","ر","خ","ج","س"],weekHeader:"أسبوع",dateFormat:"dd/mm/yy",firstDay:0,isRTL:!0,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("ar-ly",{buttonText:{month:"شهر",week:"أسبوع",day:"يوم",list:"أجندة"},allDayText:"اليوم كله",eventLimitText:"أخرى",noEventsMessage:"أي أحداث لعرض"})}(),function(){!function(){var e=a.defineLocale("ar-ma",{months:"يناير_فبراير_مارس_أبريل_ماي_يونيو_يوليوز_غشت_شتنبر_أكتوبر_نونبر_دجنبر".split("_"),monthsShort:"يناير_فبراير_مارس_أبريل_ماي_يونيو_يوليوز_غشت_شتنبر_أكتوبر_نونبر_دجنبر".split("_"),weekdays:"الأحد_الإتنين_الثلاثاء_الأربعاء_الخميس_الجمعة_السبت".split("_"),weekdaysShort:"احد_اتنين_ثلاثاء_اربعاء_خميس_جمعة_سبت".split("_"),weekdaysMin:"ح_ن_ث_ر_خ_ج_س".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd D MMMM YYYY HH:mm"},calendar:{sameDay:"[اليوم على الساعة] LT",nextDay:"[غدا على الساعة] LT",nextWeek:"dddd [على الساعة] LT",lastDay:"[أمس على الساعة] LT",lastWeek:"dddd [على الساعة] LT",sameElse:"L"},relativeTime:{future:"في %s",past:"منذ %s",s:"ثوان",m:"دقيقة",mm:"%d دقائق",h:"ساعة",hh:"%d ساعات",d:"يوم",dd:"%d أيام",M:"شهر",MM:"%d أشهر",y:"سنة",yy:"%d سنوات"},week:{dow:6,doy:12}});return e}(),e.fullCalendar.datepickerLocale("ar-ma","ar",{closeText:"إغلاق",prevText:"&#x3C;السابق",nextText:"التالي&#x3E;",currentText:"اليوم",monthNames:["يناير","فبراير","مارس","أبريل","مايو","يونيو","يوليو","أغسطس","سبتمبر","أكتوبر","نوفمبر","ديسمبر"],monthNamesShort:["1","2","3","4","5","6","7","8","9","10","11","12"],dayNames:["الأحد","الاثنين","الثلاثاء","الأربعاء","الخميس","الجمعة","السبت"],dayNamesShort:["أحد","اثنين","ثلاثاء","أربعاء","خميس","جمعة","سبت"],dayNamesMin:["ح","ن","ث","ر","خ","ج","س"],weekHeader:"أسبوع",dateFormat:"dd/mm/yy",firstDay:0,isRTL:!0,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("ar-ma",{buttonText:{month:"شهر",week:"أسبوع",day:"يوم",list:"أجندة"},allDayText:"اليوم كله",eventLimitText:"أخرى",noEventsMessage:"أي أحداث لعرض"})}(),function(){!function(){var e={1:"١",2:"٢",3:"٣",4:"٤",5:"٥",6:"٦",7:"٧",8:"٨",9:"٩",0:"٠"},t={"١":"1","٢":"2","٣":"3","٤":"4","٥":"5","٦":"6","٧":"7","٨":"8","٩":"9","٠":"0"},n=a.defineLocale("ar-sa",{months:"يناير_فبراير_مارس_أبريل_مايو_يونيو_يوليو_أغسطس_سبتمبر_أكتوبر_نوفمبر_ديسمبر".split("_"),monthsShort:"يناير_فبراير_مارس_أبريل_مايو_يونيو_يوليو_أغسطس_سبتمبر_أكتوبر_نوفمبر_ديسمبر".split("_"),weekdays:"الأحد_الإثنين_الثلاثاء_الأربعاء_الخميس_الجمعة_السبت".split("_"),weekdaysShort:"أحد_إثنين_ثلاثاء_أربعاء_خميس_جمعة_سبت".split("_"),weekdaysMin:"ح_ن_ث_ر_خ_ج_س".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd D MMMM YYYY HH:mm"},meridiemParse:/ص|م/,isPM:function(e){return"م"===e},meridiem:function(e,a,t){return e<12?"ص":"م"},calendar:{sameDay:"[اليوم على الساعة] LT",nextDay:"[غدا على الساعة] LT",nextWeek:"dddd [على الساعة] LT",lastDay:"[أمس على الساعة] LT",lastWeek:"dddd [على الساعة] LT",sameElse:"L"},relativeTime:{future:"في %s",past:"منذ %s",s:"ثوان",m:"دقيقة",mm:"%d دقائق",h:"ساعة",hh:"%d ساعات",d:"يوم",dd:"%d أيام",M:"شهر",MM:"%d أشهر",y:"سنة",yy:"%d سنوات"},preparse:function(e){return e.replace(/[١٢٣٤٥٦٧٨٩٠]/g,function(e){return t[e]}).replace(/،/g,",")},postformat:function(a){return a.replace(/\d/g,function(a){return e[a]}).replace(/,/g,"،")},week:{dow:0,doy:6}});return n}(),e.fullCalendar.datepickerLocale("ar-sa","ar",{closeText:"إغلاق",prevText:"&#x3C;السابق",nextText:"التالي&#x3E;",currentText:"اليوم",monthNames:["يناير","فبراير","مارس","أبريل","مايو","يونيو","يوليو","أغسطس","سبتمبر","أكتوبر","نوفمبر","ديسمبر"],monthNamesShort:["1","2","3","4","5","6","7","8","9","10","11","12"],dayNames:["الأحد","الاثنين","الثلاثاء","الأربعاء","الخميس","الجمعة","السبت"],dayNamesShort:["أحد","اثنين","ثلاثاء","أربعاء","خميس","جمعة","سبت"],dayNamesMin:["ح","ن","ث","ر","خ","ج","س"],weekHeader:"أسبوع",dateFormat:"dd/mm/yy",firstDay:0,isRTL:!0,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("ar-sa",{buttonText:{month:"شهر",week:"أسبوع",day:"يوم",list:"أجندة"},allDayText:"اليوم كله",eventLimitText:"أخرى",noEventsMessage:"أي أحداث لعرض"})}(),function(){!function(){var e=a.defineLocale("ar-tn",{months:"جانفي_فيفري_مارس_أفريل_ماي_جوان_جويلية_أوت_سبتمبر_أكتوبر_نوفمبر_ديسمبر".split("_"),monthsShort:"جانفي_فيفري_مارس_أفريل_ماي_جوان_جويلية_أوت_سبتمبر_أكتوبر_نوفمبر_ديسمبر".split("_"),weekdays:"الأحد_الإثنين_الثلاثاء_الأربعاء_الخميس_الجمعة_السبت".split("_"),weekdaysShort:"أحد_إثنين_ثلاثاء_أربعاء_خميس_جمعة_سبت".split("_"),weekdaysMin:"ح_ن_ث_ر_خ_ج_س".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd D MMMM YYYY HH:mm"},calendar:{sameDay:"[اليوم على الساعة] LT",nextDay:"[غدا على الساعة] LT",nextWeek:"dddd [على الساعة] LT",lastDay:"[أمس على الساعة] LT",lastWeek:"dddd [على الساعة] LT",sameElse:"L"},relativeTime:{future:"في %s",past:"منذ %s",s:"ثوان",m:"دقيقة",mm:"%d دقائق",h:"ساعة",hh:"%d ساعات",d:"يوم",dd:"%d أيام",M:"شهر",MM:"%d أشهر",y:"سنة",yy:"%d سنوات"},week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("ar-tn","ar",{closeText:"إغلاق",prevText:"&#x3C;السابق",nextText:"التالي&#x3E;",currentText:"اليوم",monthNames:["يناير","فبراير","مارس","أبريل","مايو","يونيو","يوليو","أغسطس","سبتمبر","أكتوبر","نوفمبر","ديسمبر"],monthNamesShort:["1","2","3","4","5","6","7","8","9","10","11","12"],dayNames:["الأحد","الاثنين","الثلاثاء","الأربعاء","الخميس","الجمعة","السبت"],dayNamesShort:["أحد","اثنين","ثلاثاء","أربعاء","خميس","جمعة","سبت"],dayNamesMin:["ح","ن","ث","ر","خ","ج","س"],weekHeader:"أسبوع",dateFormat:"dd/mm/yy",firstDay:0,isRTL:!0,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("ar-tn",{buttonText:{month:"شهر",week:"أسبوع",day:"يوم",list:"أجندة"},allDayText:"اليوم كله",eventLimitText:"أخرى",noEventsMessage:"أي أحداث لعرض"})}(),function(){!function(){var e=a.defineLocale("bg",{months:"януари_февруари_март_април_май_юни_юли_август_септември_октомври_ноември_декември".split("_"),monthsShort:"янр_фев_мар_апр_май_юни_юли_авг_сеп_окт_ное_дек".split("_"),weekdays:"неделя_понеделник_вторник_сряда_четвъртък_петък_събота".split("_"),weekdaysShort:"нед_пон_вто_сря_чет_пет_съб".split("_"),weekdaysMin:"нд_пн_вт_ср_чт_пт_сб".split("_"),longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"D.MM.YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY H:mm",LLLL:"dddd, D MMMM YYYY H:mm"},calendar:{sameDay:"[Днес в] LT",nextDay:"[Утре в] LT",nextWeek:"dddd [в] LT",lastDay:"[Вчера в] LT",lastWeek:function(){switch(this.day()){case 0:case 3:case 6:return"[В изминалата] dddd [в] LT";case 1:case 2:case 4:case 5:return"[В изминалия] dddd [в] LT"}},sameElse:"L"},relativeTime:{future:"след %s",past:"преди %s",s:"няколко секунди",m:"минута",mm:"%d минути",h:"час",hh:"%d часа",d:"ден",dd:"%d дни",M:"месец",MM:"%d месеца",y:"година",yy:"%d години"},ordinalParse:/\d{1,2}-(ев|ен|ти|ви|ри|ми)/,ordinal:function(e){var a=e%10,t=e%100;return 0===e?e+"-ев":0===t?e+"-ен":t>10&&t<20?e+"-ти":1===a?e+"-ви":2===a?e+"-ри":7===a||8===a?e+"-ми":e+"-ти"},week:{dow:1,doy:7}});return e}(),e.fullCalendar.datepickerLocale("bg","bg",{closeText:"затвори",prevText:"&#x3C;назад",nextText:"напред&#x3E;",nextBigText:"&#x3E;&#x3E;",currentText:"днес",monthNames:["Януари","Февруари","Март","Април","Май","Юни","Юли","Август","Септември","Октомври","Ноември","Декември"],monthNamesShort:["Яну","Фев","Мар","Апр","Май","Юни","Юли","Авг","Сеп","Окт","Нов","Дек"],dayNames:["Неделя","Понеделник","Вторник","Сряда","Четвъртък","Петък","Събота"],dayNamesShort:["Нед","Пон","Вто","Сря","Чет","Пет","Съб"],dayNamesMin:["Не","По","Вт","Ср","Че","Пе","Съ"],weekHeader:"Wk",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("bg",{buttonText:{month:"Месец",week:"Седмица",day:"Ден",list:"График"},allDayText:"Цял ден",eventLimitText:function(e){return"+още "+e},noEventsMessage:"Няма събития за показване"})}(),function(){!function(){var e=a.defineLocale("ca",{months:"gener_febrer_març_abril_maig_juny_juliol_agost_setembre_octubre_novembre_desembre".split("_"),monthsShort:"gen._febr._mar._abr._mai._jun._jul._ag._set._oct._nov._des.".split("_"),monthsParseExact:!0,weekdays:"diumenge_dilluns_dimarts_dimecres_dijous_divendres_dissabte".split("_"),weekdaysShort:"dg._dl._dt._dc._dj._dv._ds.".split("_"),weekdaysMin:"Dg_Dl_Dt_Dc_Dj_Dv_Ds".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY H:mm",LLLL:"dddd D MMMM YYYY H:mm"},calendar:{sameDay:function(){return"[avui a "+(1!==this.hours()?"les":"la")+"] LT"},nextDay:function(){return"[demà a "+(1!==this.hours()?"les":"la")+"] LT"},nextWeek:function(){return"dddd [a "+(1!==this.hours()?"les":"la")+"] LT"},lastDay:function(){return"[ahir a "+(1!==this.hours()?"les":"la")+"] LT"},lastWeek:function(){return"[el] dddd [passat a "+(1!==this.hours()?"les":"la")+"] LT"},sameElse:"L"},relativeTime:{future:"d'aquí %s",past:"fa %s",s:"uns segons",m:"un minut",mm:"%d minuts",h:"una hora",hh:"%d hores",d:"un dia",dd:"%d dies",M:"un mes",MM:"%d mesos",y:"un any",yy:"%d anys"},ordinalParse:/\d{1,2}(r|n|t|è|a)/,ordinal:function(e,a){var t=1===e?"r":2===e?"n":3===e?"r":4===e?"t":"è";return"w"!==a&&"W"!==a||(t="a"),e+t},week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("ca","ca",{closeText:"Tanca",prevText:"Anterior",nextText:"Següent",currentText:"Avui",monthNames:["gener","febrer","març","abril","maig","juny","juliol","agost","setembre","octubre","novembre","desembre"],monthNamesShort:["gen","feb","març","abr","maig","juny","jul","ag","set","oct","nov","des"],dayNames:["diumenge","dilluns","dimarts","dimecres","dijous","divendres","dissabte"],dayNamesShort:["dg","dl","dt","dc","dj","dv","ds"],dayNamesMin:["dg","dl","dt","dc","dj","dv","ds"],weekHeader:"Set",dateFormat:"dd/mm/yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("ca",{buttonText:{month:"Mes",week:"Setmana",day:"Dia",list:"Agenda"},allDayText:"Tot el dia",eventLimitText:"més",noEventsMessage:"No hi ha esdeveniments per mostrar"})}(),function(){!function(){function e(e){return e>1&&e<5&&1!==~~(e/10)}function t(a,t,n,r){var s=a+" ";switch(n){case"s":return t||r?"pár sekund":"pár sekundami";case"m":return t?"minuta":r?"minutu":"minutou";case"mm":return t||r?s+(e(a)?"minuty":"minut"):s+"minutami";case"h":return t?"hodina":r?"hodinu":"hodinou";case"hh":return t||r?s+(e(a)?"hodiny":"hodin"):s+"hodinami";case"d":return t||r?"den":"dnem";case"dd":return t||r?s+(e(a)?"dny":"dní"):s+"dny";case"M":return t||r?"měsíc":"měsícem";case"MM":return t||r?s+(e(a)?"měsíce":"měsíců"):s+"měsíci";case"y":return t||r?"rok":"rokem";case"yy":return t||r?s+(e(a)?"roky":"let"):s+"lety"}}var n="leden_únor_březen_duben_květen_červen_červenec_srpen_září_říjen_listopad_prosinec".split("_"),r="led_úno_bře_dub_kvě_čvn_čvc_srp_zář_říj_lis_pro".split("_"),s=a.defineLocale("cs",{months:n,monthsShort:r,monthsParse:function(e,a){var t,n=[];for(t=0;t<12;t++)n[t]=new RegExp("^"+e[t]+"$|^"+a[t]+"$","i");return n}(n,r),shortMonthsParse:function(e){var a,t=[];for(a=0;a<12;a++)t[a]=new RegExp("^"+e[a]+"$","i");return t}(r),longMonthsParse:function(e){var a,t=[];for(a=0;a<12;a++)t[a]=new RegExp("^"+e[a]+"$","i");return t}(n),weekdays:"neděle_pondělí_úterý_středa_čtvrtek_pátek_sobota".split("_"),weekdaysShort:"ne_po_út_st_čt_pá_so".split("_"),weekdaysMin:"ne_po_út_st_čt_pá_so".split("_"),longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"DD.MM.YYYY",LL:"D. MMMM YYYY",LLL:"D. MMMM YYYY H:mm",LLLL:"dddd D. MMMM YYYY H:mm",l:"D. M. YYYY"},calendar:{sameDay:"[dnes v] LT",nextDay:"[zítra v] LT",nextWeek:function(){switch(this.day()){case 0:return"[v neděli v] LT";case 1:case 2:return"[v] dddd [v] LT";case 3:return"[ve středu v] LT";case 4:return"[ve čtvrtek v] LT";case 5:return"[v pátek v] LT";case 6:return"[v sobotu v] LT"}},lastDay:"[včera v] LT",lastWeek:function(){switch(this.day()){case 0:return"[minulou neděli v] LT";case 1:case 2:return"[minulé] dddd [v] LT";case 3:return"[minulou středu v] LT";case 4:case 5:return"[minulý] dddd [v] LT";case 6:return"[minulou sobotu v] LT"}},sameElse:"L"},relativeTime:{future:"za %s",past:"před %s",s:t,m:t,mm:t,h:t,hh:t,d:t,dd:t,M:t,MM:t,y:t,yy:t},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:4}});return s}(),e.fullCalendar.datepickerLocale("cs","cs",{closeText:"Zavřít",prevText:"&#x3C;Dříve",nextText:"Později&#x3E;",currentText:"Nyní",monthNames:["leden","únor","březen","duben","květen","červen","červenec","srpen","září","říjen","listopad","prosinec"],monthNamesShort:["led","úno","bře","dub","kvě","čer","čvc","srp","zář","říj","lis","pro"],dayNames:["neděle","pondělí","úterý","středa","čtvrtek","pátek","sobota"],dayNamesShort:["ne","po","út","st","čt","pá","so"],dayNamesMin:["ne","po","út","st","čt","pá","so"],weekHeader:"Týd",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("cs",{buttonText:{month:"Měsíc",week:"Týden",day:"Den",list:"Agenda"},allDayText:"Celý den",eventLimitText:function(e){return"+další: "+e},noEventsMessage:"Žádné akce k zobrazení"})}(),function(){!function(){var e=a.defineLocale("da",{months:"januar_februar_marts_april_maj_juni_juli_august_september_oktober_november_december".split("_"),monthsShort:"jan_feb_mar_apr_maj_jun_jul_aug_sep_okt_nov_dec".split("_"),weekdays:"søndag_mandag_tirsdag_onsdag_torsdag_fredag_lørdag".split("_"),weekdaysShort:"søn_man_tir_ons_tor_fre_lør".split("_"),weekdaysMin:"sø_ma_ti_on_to_fr_lø".split("_"),longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D. MMMM YYYY",LLL:"D. MMMM YYYY HH:mm",LLLL:"dddd [d.] D. MMMM YYYY HH:mm"},calendar:{sameDay:"[I dag kl.] LT",nextDay:"[I morgen kl.] LT",nextWeek:"dddd [kl.] LT",lastDay:"[I går kl.] LT",lastWeek:"[sidste] dddd [kl] LT",sameElse:"L"},relativeTime:{future:"om %s",past:"%s siden",s:"få sekunder",m:"et minut",mm:"%d minutter",h:"en time",hh:"%d timer",d:"en dag",dd:"%d dage",M:"en måned",MM:"%d måneder",y:"et år",yy:"%d år"},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("da","da",{closeText:"Luk",prevText:"&#x3C;Forrige",nextText:"Næste&#x3E;",currentText:"Idag",monthNames:["Januar","Februar","Marts","April","Maj","Juni","Juli","August","September","Oktober","November","December"],monthNamesShort:["Jan","Feb","Mar","Apr","Maj","Jun","Jul","Aug","Sep","Okt","Nov","Dec"],dayNames:["Søndag","Mandag","Tirsdag","Onsdag","Torsdag","Fredag","Lørdag"],dayNamesShort:["Søn","Man","Tir","Ons","Tor","Fre","Lør"],dayNamesMin:["Sø","Ma","Ti","On","To","Fr","Lø"],weekHeader:"Uge",dateFormat:"dd-mm-yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("da",{buttonText:{month:"Måned",week:"Uge",day:"Dag",list:"Agenda"},allDayText:"Hele dagen",eventLimitText:"flere",noEventsMessage:"Ingen arrangementer at vise"})}(),function(){!function(){function e(e,a,t,n){var r={m:["eine Minute","einer Minute"],h:["eine Stunde","einer Stunde"],d:["ein Tag","einem Tag"],dd:[e+" Tage",e+" Tagen"],M:["ein Monat","einem Monat"],MM:[e+" Monate",e+" Monaten"],y:["ein Jahr","einem Jahr"],yy:[e+" Jahre",e+" Jahren"]};return a?r[t][0]:r[t][1]}var t=a.defineLocale("de",{months:"Januar_Februar_März_April_Mai_Juni_Juli_August_September_Oktober_November_Dezember".split("_"),monthsShort:"Jan._Febr._Mrz._Apr._Mai_Jun._Jul._Aug._Sept._Okt._Nov._Dez.".split("_"),monthsParseExact:!0,weekdays:"Sonntag_Montag_Dienstag_Mittwoch_Donnerstag_Freitag_Samstag".split("_"),weekdaysShort:"So._Mo._Di._Mi._Do._Fr._Sa.".split("_"),weekdaysMin:"So_Mo_Di_Mi_Do_Fr_Sa".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD.MM.YYYY",LL:"D. MMMM YYYY",LLL:"D. MMMM YYYY HH:mm",LLLL:"dddd, D. MMMM YYYY HH:mm"},calendar:{sameDay:"[heute um] LT [Uhr]",sameElse:"L",nextDay:"[morgen um] LT [Uhr]",nextWeek:"dddd [um] LT [Uhr]",lastDay:"[gestern um] LT [Uhr]",lastWeek:"[letzten] dddd [um] LT [Uhr]"},relativeTime:{future:"in %s",past:"vor %s",s:"ein paar Sekunden",m:e,mm:"%d Minuten",h:e,hh:"%d Stunden",d:e,dd:e,M:e,MM:e,y:e,yy:e},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:4}});return t}(),e.fullCalendar.datepickerLocale("de","de",{closeText:"Schließen",prevText:"&#x3C;Zurück",nextText:"Vor&#x3E;",currentText:"Heute",monthNames:["Januar","Februar","März","April","Mai","Juni","Juli","August","September","Oktober","November","Dezember"],monthNamesShort:["Jan","Feb","Mär","Apr","Mai","Jun","Jul","Aug","Sep","Okt","Nov","Dez"],dayNames:["Sonntag","Montag","Dienstag","Mittwoch","Donnerstag","Freitag","Samstag"],dayNamesShort:["So","Mo","Di","Mi","Do","Fr","Sa"],dayNamesMin:["So","Mo","Di","Mi","Do","Fr","Sa"],weekHeader:"KW",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("de",{buttonText:{month:"Monat",week:"Woche",day:"Tag",list:"Terminübersicht"},allDayText:"Ganztägig",eventLimitText:function(e){return"+ weitere "+e},noEventsMessage:"Keine Ereignisse anzuzeigen"})}(),function(){!function(){function e(e,a,t,n){var r={m:["eine Minute","einer Minute"],h:["eine Stunde","einer Stunde"],d:["ein Tag","einem Tag"],dd:[e+" Tage",e+" Tagen"],M:["ein Monat","einem Monat"],MM:[e+" Monate",e+" Monaten"],y:["ein Jahr","einem Jahr"],yy:[e+" Jahre",e+" Jahren"]};return a?r[t][0]:r[t][1]}var t=a.defineLocale("de-at",{months:"Jänner_Februar_März_April_Mai_Juni_Juli_August_September_Oktober_November_Dezember".split("_"),monthsShort:"Jän._Febr._Mrz._Apr._Mai_Jun._Jul._Aug._Sept._Okt._Nov._Dez.".split("_"),monthsParseExact:!0,weekdays:"Sonntag_Montag_Dienstag_Mittwoch_Donnerstag_Freitag_Samstag".split("_"),weekdaysShort:"So._Mo._Di._Mi._Do._Fr._Sa.".split("_"),weekdaysMin:"So_Mo_Di_Mi_Do_Fr_Sa".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD.MM.YYYY",LL:"D. MMMM YYYY",LLL:"D. MMMM YYYY HH:mm",LLLL:"dddd, D. MMMM YYYY HH:mm"},calendar:{sameDay:"[heute um] LT [Uhr]",sameElse:"L",nextDay:"[morgen um] LT [Uhr]",nextWeek:"dddd [um] LT [Uhr]",lastDay:"[gestern um] LT [Uhr]",lastWeek:"[letzten] dddd [um] LT [Uhr]"},relativeTime:{future:"in %s",past:"vor %s",s:"ein paar Sekunden",m:e,mm:"%d Minuten",h:e,hh:"%d Stunden",d:e,dd:e,M:e,MM:e,y:e,yy:e},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:4}});return t}(),e.fullCalendar.datepickerLocale("de-at","de",{closeText:"Schließen",prevText:"&#x3C;Zurück",nextText:"Vor&#x3E;",currentText:"Heute",monthNames:["Januar","Februar","März","April","Mai","Juni","Juli","August","September","Oktober","November","Dezember"],monthNamesShort:["Jan","Feb","Mär","Apr","Mai","Jun","Jul","Aug","Sep","Okt","Nov","Dez"],dayNames:["Sonntag","Montag","Dienstag","Mittwoch","Donnerstag","Freitag","Samstag"],dayNamesShort:["So","Mo","Di","Mi","Do","Fr","Sa"],dayNamesMin:["So","Mo","Di","Mi","Do","Fr","Sa"],weekHeader:"KW",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("de-at",{buttonText:{month:"Monat",week:"Woche",day:"Tag",list:"Terminübersicht"},allDayText:"Ganztägig",eventLimitText:function(e){return"+ weitere "+e},noEventsMessage:"Keine Ereignisse anzuzeigen"})}(),function(){!function(){function e(e){return e instanceof Function||"[object Function]"===Object.prototype.toString.call(e)}var t=a.defineLocale("el",{monthsNominativeEl:"Ιανουάριος_Φεβρουάριος_Μάρτιος_Απρίλιος_Μάιος_Ιούνιος_Ιούλιος_Αύγουστος_Σεπτέμβριος_Οκτώβριος_Νοέμβριος_Δεκέμβριος".split("_"),monthsGenitiveEl:"Ιανουαρίου_Φεβρουαρίου_Μαρτίου_Απριλίου_Μαΐου_Ιουνίου_Ιουλίου_Αυγούστου_Σεπτεμβρίου_Οκτωβρίου_Νοεμβρίου_Δεκεμβρίου".split("_"),months:function(e,a){return/D/.test(a.substring(0,a.indexOf("MMMM")))?this._monthsGenitiveEl[e.month()]:this._monthsNominativeEl[e.month()]},monthsShort:"Ιαν_Φεβ_Μαρ_Απρ_Μαϊ_Ιουν_Ιουλ_Αυγ_Σεπ_Οκτ_Νοε_Δεκ".split("_"),weekdays:"Κυριακή_Δευτέρα_Τρίτη_Τετάρτη_Πέμπτη_Παρασκευή_Σάββατο".split("_"),weekdaysShort:"Κυρ_Δευ_Τρι_Τετ_Πεμ_Παρ_Σαβ".split("_"),weekdaysMin:"Κυ_Δε_Τρ_Τε_Πε_Πα_Σα".split("_"),meridiem:function(e,a,t){return e>11?t?"μμ":"ΜΜ":t?"πμ":"ΠΜ"},isPM:function(e){return"μ"===(e+"").toLowerCase()[0]},meridiemParse:/[ΠΜ]\.?Μ?\.?/i,longDateFormat:{LT:"h:mm A",LTS:"h:mm:ss A",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY h:mm A",LLLL:"dddd, D MMMM YYYY h:mm A"},calendarEl:{sameDay:"[Σήμερα {}] LT",nextDay:"[Αύριο {}] LT",nextWeek:"dddd [{}] LT",lastDay:"[Χθες {}] LT",lastWeek:function(){switch(this.day()){case 6:return"[το προηγούμενο] dddd [{}] LT";default:return"[την προηγούμενη] dddd [{}] LT"}},sameElse:"L"},calendar:function(a,t){var n=this._calendarEl[a],r=t&&t.hours();return e(n)&&(n=n.apply(t)),n.replace("{}",r%12===1?"στη":"στις")},relativeTime:{future:"σε %s",past:"%s πριν",s:"λίγα δευτερόλεπτα",m:"ένα λεπτό",mm:"%d λεπτά",h:"μία ώρα",hh:"%d ώρες",d:"μία μέρα",dd:"%d μέρες",M:"ένας μήνας",MM:"%d μήνες",y:"ένας χρόνος",yy:"%d χρόνια"},ordinalParse:/\d{1,2}η/,ordinal:"%dη",week:{dow:1,doy:4}});return t}(),e.fullCalendar.datepickerLocale("el","el",{closeText:"Κλείσιμο",prevText:"Προηγούμενος",nextText:"Επόμενος",currentText:"Σήμερα",monthNames:["Ιανουάριος","Φεβρουάριος","Μάρτιος","Απρίλιος","Μάιος","Ιούνιος","Ιούλιος","Αύγουστος","Σεπτέμβριος","Οκτώβριος","Νοέμβριος","Δεκέμβριος"],monthNamesShort:["Ιαν","Φεβ","Μαρ","Απρ","Μαι","Ιουν","Ιουλ","Αυγ","Σεπ","Οκτ","Νοε","Δεκ"],dayNames:["Κυριακή","Δευτέρα","Τρίτη","Τετάρτη","Πέμπτη","Παρασκευή","Σάββατο"],dayNamesShort:["Κυρ","Δευ","Τρι","Τετ","Πεμ","Παρ","Σαβ"],dayNamesMin:["Κυ","Δε","Τρ","Τε","Πε","Πα","Σα"],weekHeader:"Εβδ",dateFormat:"dd/mm/yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("el",{buttonText:{month:"Μήνας",week:"Εβδομάδα",day:"Ημέρα",list:"Ατζέντα"},allDayText:"Ολοήμερο",eventLimitText:"περισσότερα",noEventsMessage:"Δεν υπάρχουν γεγονότα για να εμφανιστεί"})}(),function(){!function(){var e=a.defineLocale("en-au",{months:"January_February_March_April_May_June_July_August_September_October_November_December".split("_"),monthsShort:"Jan_Feb_Mar_Apr_May_Jun_Jul_Aug_Sep_Oct_Nov_Dec".split("_"),weekdays:"Sunday_Monday_Tuesday_Wednesday_Thursday_Friday_Saturday".split("_"),weekdaysShort:"Sun_Mon_Tue_Wed_Thu_Fri_Sat".split("_"),weekdaysMin:"Su_Mo_Tu_We_Th_Fr_Sa".split("_"),longDateFormat:{LT:"h:mm A",LTS:"h:mm:ss A",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY h:mm A",LLLL:"dddd, D MMMM YYYY h:mm A"},calendar:{sameDay:"[Today at] LT",nextDay:"[Tomorrow at] LT",nextWeek:"dddd [at] LT",lastDay:"[Yesterday at] LT",lastWeek:"[Last] dddd [at] LT",sameElse:"L"},relativeTime:{future:"in %s",past:"%s ago",s:"a few seconds",m:"a minute",mm:"%d minutes",h:"an hour",hh:"%d hours",d:"a day",dd:"%d days",M:"a month",MM:"%d months",y:"a year",yy:"%d years"},ordinalParse:/\d{1,2}(st|nd|rd|th)/,ordinal:function(e){var a=e%10,t=1===~~(e%100/10)?"th":1===a?"st":2===a?"nd":3===a?"rd":"th";return e+t},week:{
-dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("en-au","en-AU",{closeText:"Done",prevText:"Prev",nextText:"Next",currentText:"Today",monthNames:["January","February","March","April","May","June","July","August","September","October","November","December"],monthNamesShort:["Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"],dayNames:["Sunday","Monday","Tuesday","Wednesday","Thursday","Friday","Saturday"],dayNamesShort:["Sun","Mon","Tue","Wed","Thu","Fri","Sat"],dayNamesMin:["Su","Mo","Tu","We","Th","Fr","Sa"],weekHeader:"Wk",dateFormat:"dd/mm/yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("en-au")}(),function(){!function(){var e=a.defineLocale("en-ca",{months:"January_February_March_April_May_June_July_August_September_October_November_December".split("_"),monthsShort:"Jan_Feb_Mar_Apr_May_Jun_Jul_Aug_Sep_Oct_Nov_Dec".split("_"),weekdays:"Sunday_Monday_Tuesday_Wednesday_Thursday_Friday_Saturday".split("_"),weekdaysShort:"Sun_Mon_Tue_Wed_Thu_Fri_Sat".split("_"),weekdaysMin:"Su_Mo_Tu_We_Th_Fr_Sa".split("_"),longDateFormat:{LT:"h:mm A",LTS:"h:mm:ss A",L:"YYYY-MM-DD",LL:"MMMM D, YYYY",LLL:"MMMM D, YYYY h:mm A",LLLL:"dddd, MMMM D, YYYY h:mm A"},calendar:{sameDay:"[Today at] LT",nextDay:"[Tomorrow at] LT",nextWeek:"dddd [at] LT",lastDay:"[Yesterday at] LT",lastWeek:"[Last] dddd [at] LT",sameElse:"L"},relativeTime:{future:"in %s",past:"%s ago",s:"a few seconds",m:"a minute",mm:"%d minutes",h:"an hour",hh:"%d hours",d:"a day",dd:"%d days",M:"a month",MM:"%d months",y:"a year",yy:"%d years"},ordinalParse:/\d{1,2}(st|nd|rd|th)/,ordinal:function(e){var a=e%10,t=1===~~(e%100/10)?"th":1===a?"st":2===a?"nd":3===a?"rd":"th";return e+t}});return e}(),e.fullCalendar.locale("en-ca")}(),function(){!function(){var e=a.defineLocale("en-gb",{months:"January_February_March_April_May_June_July_August_September_October_November_December".split("_"),monthsShort:"Jan_Feb_Mar_Apr_May_Jun_Jul_Aug_Sep_Oct_Nov_Dec".split("_"),weekdays:"Sunday_Monday_Tuesday_Wednesday_Thursday_Friday_Saturday".split("_"),weekdaysShort:"Sun_Mon_Tue_Wed_Thu_Fri_Sat".split("_"),weekdaysMin:"Su_Mo_Tu_We_Th_Fr_Sa".split("_"),longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd, D MMMM YYYY HH:mm"},calendar:{sameDay:"[Today at] LT",nextDay:"[Tomorrow at] LT",nextWeek:"dddd [at] LT",lastDay:"[Yesterday at] LT",lastWeek:"[Last] dddd [at] LT",sameElse:"L"},relativeTime:{future:"in %s",past:"%s ago",s:"a few seconds",m:"a minute",mm:"%d minutes",h:"an hour",hh:"%d hours",d:"a day",dd:"%d days",M:"a month",MM:"%d months",y:"a year",yy:"%d years"},ordinalParse:/\d{1,2}(st|nd|rd|th)/,ordinal:function(e){var a=e%10,t=1===~~(e%100/10)?"th":1===a?"st":2===a?"nd":3===a?"rd":"th";return e+t},week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("en-gb","en-GB",{closeText:"Done",prevText:"Prev",nextText:"Next",currentText:"Today",monthNames:["January","February","March","April","May","June","July","August","September","October","November","December"],monthNamesShort:["Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"],dayNames:["Sunday","Monday","Tuesday","Wednesday","Thursday","Friday","Saturday"],dayNamesShort:["Sun","Mon","Tue","Wed","Thu","Fri","Sat"],dayNamesMin:["Su","Mo","Tu","We","Th","Fr","Sa"],weekHeader:"Wk",dateFormat:"dd/mm/yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("en-gb")}(),function(){!function(){var e=a.defineLocale("en-ie",{months:"January_February_March_April_May_June_July_August_September_October_November_December".split("_"),monthsShort:"Jan_Feb_Mar_Apr_May_Jun_Jul_Aug_Sep_Oct_Nov_Dec".split("_"),weekdays:"Sunday_Monday_Tuesday_Wednesday_Thursday_Friday_Saturday".split("_"),weekdaysShort:"Sun_Mon_Tue_Wed_Thu_Fri_Sat".split("_"),weekdaysMin:"Su_Mo_Tu_We_Th_Fr_Sa".split("_"),longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD-MM-YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd D MMMM YYYY HH:mm"},calendar:{sameDay:"[Today at] LT",nextDay:"[Tomorrow at] LT",nextWeek:"dddd [at] LT",lastDay:"[Yesterday at] LT",lastWeek:"[Last] dddd [at] LT",sameElse:"L"},relativeTime:{future:"in %s",past:"%s ago",s:"a few seconds",m:"a minute",mm:"%d minutes",h:"an hour",hh:"%d hours",d:"a day",dd:"%d days",M:"a month",MM:"%d months",y:"a year",yy:"%d years"},ordinalParse:/\d{1,2}(st|nd|rd|th)/,ordinal:function(e){var a=e%10,t=1===~~(e%100/10)?"th":1===a?"st":2===a?"nd":3===a?"rd":"th";return e+t},week:{dow:1,doy:4}});return e}(),e.fullCalendar.locale("en-ie")}(),function(){!function(){var e=a.defineLocale("en-nz",{months:"January_February_March_April_May_June_July_August_September_October_November_December".split("_"),monthsShort:"Jan_Feb_Mar_Apr_May_Jun_Jul_Aug_Sep_Oct_Nov_Dec".split("_"),weekdays:"Sunday_Monday_Tuesday_Wednesday_Thursday_Friday_Saturday".split("_"),weekdaysShort:"Sun_Mon_Tue_Wed_Thu_Fri_Sat".split("_"),weekdaysMin:"Su_Mo_Tu_We_Th_Fr_Sa".split("_"),longDateFormat:{LT:"h:mm A",LTS:"h:mm:ss A",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY h:mm A",LLLL:"dddd, D MMMM YYYY h:mm A"},calendar:{sameDay:"[Today at] LT",nextDay:"[Tomorrow at] LT",nextWeek:"dddd [at] LT",lastDay:"[Yesterday at] LT",lastWeek:"[Last] dddd [at] LT",sameElse:"L"},relativeTime:{future:"in %s",past:"%s ago",s:"a few seconds",m:"a minute",mm:"%d minutes",h:"an hour",hh:"%d hours",d:"a day",dd:"%d days",M:"a month",MM:"%d months",y:"a year",yy:"%d years"},ordinalParse:/\d{1,2}(st|nd|rd|th)/,ordinal:function(e){var a=e%10,t=1===~~(e%100/10)?"th":1===a?"st":2===a?"nd":3===a?"rd":"th";return e+t},week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("en-nz","en-NZ",{closeText:"Done",prevText:"Prev",nextText:"Next",currentText:"Today",monthNames:["January","February","March","April","May","June","July","August","September","October","November","December"],monthNamesShort:["Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"],dayNames:["Sunday","Monday","Tuesday","Wednesday","Thursday","Friday","Saturday"],dayNamesShort:["Sun","Mon","Tue","Wed","Thu","Fri","Sat"],dayNamesMin:["Su","Mo","Tu","We","Th","Fr","Sa"],weekHeader:"Wk",dateFormat:"dd/mm/yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("en-nz")}(),function(){!function(){var e="ene._feb._mar._abr._may._jun._jul._ago._sep._oct._nov._dic.".split("_"),t="ene_feb_mar_abr_may_jun_jul_ago_sep_oct_nov_dic".split("_"),n=a.defineLocale("es",{months:"enero_febrero_marzo_abril_mayo_junio_julio_agosto_septiembre_octubre_noviembre_diciembre".split("_"),monthsShort:function(a,n){return/-MMM-/.test(n)?t[a.month()]:e[a.month()]},monthsParseExact:!0,weekdays:"domingo_lunes_martes_miércoles_jueves_viernes_sábado".split("_"),weekdaysShort:"dom._lun._mar._mié._jue._vie._sáb.".split("_"),weekdaysMin:"do_lu_ma_mi_ju_vi_sá".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"DD/MM/YYYY",LL:"D [de] MMMM [de] YYYY",LLL:"D [de] MMMM [de] YYYY H:mm",LLLL:"dddd, D [de] MMMM [de] YYYY H:mm"},calendar:{sameDay:function(){return"[hoy a la"+(1!==this.hours()?"s":"")+"] LT"},nextDay:function(){return"[mañana a la"+(1!==this.hours()?"s":"")+"] LT"},nextWeek:function(){return"dddd [a la"+(1!==this.hours()?"s":"")+"] LT"},lastDay:function(){return"[ayer a la"+(1!==this.hours()?"s":"")+"] LT"},lastWeek:function(){return"[el] dddd [pasado a la"+(1!==this.hours()?"s":"")+"] LT"},sameElse:"L"},relativeTime:{future:"en %s",past:"hace %s",s:"unos segundos",m:"un minuto",mm:"%d minutos",h:"una hora",hh:"%d horas",d:"un día",dd:"%d días",M:"un mes",MM:"%d meses",y:"un año",yy:"%d años"},ordinalParse:/\d{1,2}º/,ordinal:"%dº",week:{dow:1,doy:4}});return n}(),e.fullCalendar.datepickerLocale("es","es",{closeText:"Cerrar",prevText:"&#x3C;Ant",nextText:"Sig&#x3E;",currentText:"Hoy",monthNames:["enero","febrero","marzo","abril","mayo","junio","julio","agosto","septiembre","octubre","noviembre","diciembre"],monthNamesShort:["ene","feb","mar","abr","may","jun","jul","ago","sep","oct","nov","dic"],dayNames:["domingo","lunes","martes","miércoles","jueves","viernes","sábado"],dayNamesShort:["dom","lun","mar","mié","jue","vie","sáb"],dayNamesMin:["D","L","M","X","J","V","S"],weekHeader:"Sm",dateFormat:"dd/mm/yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("es",{buttonText:{month:"Mes",week:"Semana",day:"Día",list:"Agenda"},allDayHtml:"Todo<br/>el día",eventLimitText:"más",noEventsMessage:"No hay eventos para mostrar"})}(),function(){!function(){var e="ene._feb._mar._abr._may._jun._jul._ago._sep._oct._nov._dic.".split("_"),t="ene_feb_mar_abr_may_jun_jul_ago_sep_oct_nov_dic".split("_"),n=a.defineLocale("es-do",{months:"enero_febrero_marzo_abril_mayo_junio_julio_agosto_septiembre_octubre_noviembre_diciembre".split("_"),monthsShort:function(a,n){return/-MMM-/.test(n)?t[a.month()]:e[a.month()]},monthsParseExact:!0,weekdays:"domingo_lunes_martes_miércoles_jueves_viernes_sábado".split("_"),weekdaysShort:"dom._lun._mar._mié._jue._vie._sáb.".split("_"),weekdaysMin:"do_lu_ma_mi_ju_vi_sá".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"h:mm A",LTS:"h:mm:ss A",L:"DD/MM/YYYY",LL:"D [de] MMMM [de] YYYY",LLL:"D [de] MMMM [de] YYYY h:mm A",LLLL:"dddd, D [de] MMMM [de] YYYY h:mm A"},calendar:{sameDay:function(){return"[hoy a la"+(1!==this.hours()?"s":"")+"] LT"},nextDay:function(){return"[mañana a la"+(1!==this.hours()?"s":"")+"] LT"},nextWeek:function(){return"dddd [a la"+(1!==this.hours()?"s":"")+"] LT"},lastDay:function(){return"[ayer a la"+(1!==this.hours()?"s":"")+"] LT"},lastWeek:function(){return"[el] dddd [pasado a la"+(1!==this.hours()?"s":"")+"] LT"},sameElse:"L"},relativeTime:{future:"en %s",past:"hace %s",s:"unos segundos",m:"un minuto",mm:"%d minutos",h:"una hora",hh:"%d horas",d:"un día",dd:"%d días",M:"un mes",MM:"%d meses",y:"un año",yy:"%d años"},ordinalParse:/\d{1,2}º/,ordinal:"%dº",week:{dow:1,doy:4}});return n}(),e.fullCalendar.datepickerLocale("es-do","es",{closeText:"Cerrar",prevText:"&#x3C;Ant",nextText:"Sig&#x3E;",currentText:"Hoy",monthNames:["enero","febrero","marzo","abril","mayo","junio","julio","agosto","septiembre","octubre","noviembre","diciembre"],monthNamesShort:["ene","feb","mar","abr","may","jun","jul","ago","sep","oct","nov","dic"],dayNames:["domingo","lunes","martes","miércoles","jueves","viernes","sábado"],dayNamesShort:["dom","lun","mar","mié","jue","vie","sáb"],dayNamesMin:["D","L","M","X","J","V","S"],weekHeader:"Sm",dateFormat:"dd/mm/yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("es-do",{buttonText:{month:"Mes",week:"Semana",day:"Día",list:"Agenda"},allDayHtml:"Todo<br/>el día",eventLimitText:"más",noEventsMessage:"No hay eventos para mostrar"})}(),function(){!function(){var e=a.defineLocale("eu",{months:"urtarrila_otsaila_martxoa_apirila_maiatza_ekaina_uztaila_abuztua_iraila_urria_azaroa_abendua".split("_"),monthsShort:"urt._ots._mar._api._mai._eka._uzt._abu._ira._urr._aza._abe.".split("_"),monthsParseExact:!0,weekdays:"igandea_astelehena_asteartea_asteazkena_osteguna_ostirala_larunbata".split("_"),weekdaysShort:"ig._al._ar._az._og._ol._lr.".split("_"),weekdaysMin:"ig_al_ar_az_og_ol_lr".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"YYYY-MM-DD",LL:"YYYY[ko] MMMM[ren] D[a]",LLL:"YYYY[ko] MMMM[ren] D[a] HH:mm",LLLL:"dddd, YYYY[ko] MMMM[ren] D[a] HH:mm",l:"YYYY-M-D",ll:"YYYY[ko] MMM D[a]",lll:"YYYY[ko] MMM D[a] HH:mm",llll:"ddd, YYYY[ko] MMM D[a] HH:mm"},calendar:{sameDay:"[gaur] LT[etan]",nextDay:"[bihar] LT[etan]",nextWeek:"dddd LT[etan]",lastDay:"[atzo] LT[etan]",lastWeek:"[aurreko] dddd LT[etan]",sameElse:"L"},relativeTime:{future:"%s barru",past:"duela %s",s:"segundo batzuk",m:"minutu bat",mm:"%d minutu",h:"ordu bat",hh:"%d ordu",d:"egun bat",dd:"%d egun",M:"hilabete bat",MM:"%d hilabete",y:"urte bat",yy:"%d urte"},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:7}});return e}(),e.fullCalendar.datepickerLocale("eu","eu",{closeText:"Egina",prevText:"&#x3C;Aur",nextText:"Hur&#x3E;",currentText:"Gaur",monthNames:["urtarrila","otsaila","martxoa","apirila","maiatza","ekaina","uztaila","abuztua","iraila","urria","azaroa","abendua"],monthNamesShort:["urt.","ots.","mar.","api.","mai.","eka.","uzt.","abu.","ira.","urr.","aza.","abe."],dayNames:["igandea","astelehena","asteartea","asteazkena","osteguna","ostirala","larunbata"],dayNamesShort:["ig.","al.","ar.","az.","og.","ol.","lr."],dayNamesMin:["ig","al","ar","az","og","ol","lr"],weekHeader:"As",dateFormat:"yy-mm-dd",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("eu",{buttonText:{month:"Hilabetea",week:"Astea",day:"Eguna",list:"Agenda"},allDayHtml:"Egun<br/>osoa",eventLimitText:"gehiago",noEventsMessage:"Ez dago ekitaldirik erakusteko"})}(),function(){!function(){var e={1:"۱",2:"۲",3:"۳",4:"۴",5:"۵",6:"۶",7:"۷",8:"۸",9:"۹",0:"۰"},t={"۱":"1","۲":"2","۳":"3","۴":"4","۵":"5","۶":"6","۷":"7","۸":"8","۹":"9","۰":"0"},n=a.defineLocale("fa",{months:"ژانویه_فوریه_مارس_آوریل_مه_ژوئن_ژوئیه_اوت_سپتامبر_اکتبر_نوامبر_دسامبر".split("_"),monthsShort:"ژانویه_فوریه_مارس_آوریل_مه_ژوئن_ژوئیه_اوت_سپتامبر_اکتبر_نوامبر_دسامبر".split("_"),weekdays:"یک‌شنبه_دوشنبه_سه‌شنبه_چهارشنبه_پنج‌شنبه_جمعه_شنبه".split("_"),weekdaysShort:"یک‌شنبه_دوشنبه_سه‌شنبه_چهارشنبه_پنج‌شنبه_جمعه_شنبه".split("_"),weekdaysMin:"ی_د_س_چ_پ_ج_ش".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd, D MMMM YYYY HH:mm"},meridiemParse:/قبل از ظهر|بعد از ظهر/,isPM:function(e){return/بعد از ظهر/.test(e)},meridiem:function(e,a,t){return e<12?"قبل از ظهر":"بعد از ظهر"},calendar:{sameDay:"[امروز ساعت] LT",nextDay:"[فردا ساعت] LT",nextWeek:"dddd [ساعت] LT",lastDay:"[دیروز ساعت] LT",lastWeek:"dddd [پیش] [ساعت] LT",sameElse:"L"},relativeTime:{future:"در %s",past:"%s پیش",s:"چندین ثانیه",m:"یک دقیقه",mm:"%d دقیقه",h:"یک ساعت",hh:"%d ساعت",d:"یک روز",dd:"%d روز",M:"یک ماه",MM:"%d ماه",y:"یک سال",yy:"%d سال"},preparse:function(e){return e.replace(/[۰-۹]/g,function(e){return t[e]}).replace(/،/g,",")},postformat:function(a){return a.replace(/\d/g,function(a){return e[a]}).replace(/,/g,"،")},ordinalParse:/\d{1,2}م/,ordinal:"%dم",week:{dow:6,doy:12}});return n}(),e.fullCalendar.datepickerLocale("fa","fa",{closeText:"بستن",prevText:"&#x3C;قبلی",nextText:"بعدی&#x3E;",currentText:"امروز",monthNames:["ژانویه","فوریه","مارس","آوریل","مه","ژوئن","ژوئیه","اوت","سپتامبر","اکتبر","نوامبر","دسامبر"],monthNamesShort:["1","2","3","4","5","6","7","8","9","10","11","12"],dayNames:["يکشنبه","دوشنبه","سه‌شنبه","چهارشنبه","پنجشنبه","جمعه","شنبه"],dayNamesShort:["ی","د","س","چ","پ","ج","ش"],dayNamesMin:["ی","د","س","چ","پ","ج","ش"],weekHeader:"هف",dateFormat:"yy/mm/dd",firstDay:6,isRTL:!0,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("fa",{buttonText:{month:"ماه",week:"هفته",day:"روز",list:"برنامه"},allDayText:"تمام روز",eventLimitText:function(e){return"بیش از "+e},noEventsMessage:"هیچ رویدادی به نمایش"})}(),function(){!function(){function e(e,a,n,r){var s="";switch(n){case"s":return r?"muutaman sekunnin":"muutama sekunti";case"m":return r?"minuutin":"minuutti";case"mm":s=r?"minuutin":"minuuttia";break;case"h":return r?"tunnin":"tunti";case"hh":s=r?"tunnin":"tuntia";break;case"d":return r?"päivän":"päivä";case"dd":s=r?"päivän":"päivää";break;case"M":return r?"kuukauden":"kuukausi";case"MM":s=r?"kuukauden":"kuukautta";break;case"y":return r?"vuoden":"vuosi";case"yy":s=r?"vuoden":"vuotta"}return s=t(e,r)+" "+s}function t(e,a){return e<10?a?r[e]:n[e]:e}var n="nolla yksi kaksi kolme neljä viisi kuusi seitsemän kahdeksan yhdeksän".split(" "),r=["nolla","yhden","kahden","kolmen","neljän","viiden","kuuden",n[7],n[8],n[9]],s=a.defineLocale("fi",{months:"tammikuu_helmikuu_maaliskuu_huhtikuu_toukokuu_kesäkuu_heinäkuu_elokuu_syyskuu_lokakuu_marraskuu_joulukuu".split("_"),monthsShort:"tammi_helmi_maalis_huhti_touko_kesä_heinä_elo_syys_loka_marras_joulu".split("_"),weekdays:"sunnuntai_maanantai_tiistai_keskiviikko_torstai_perjantai_lauantai".split("_"),weekdaysShort:"su_ma_ti_ke_to_pe_la".split("_"),weekdaysMin:"su_ma_ti_ke_to_pe_la".split("_"),longDateFormat:{LT:"HH.mm",LTS:"HH.mm.ss",L:"DD.MM.YYYY",LL:"Do MMMM[ta] YYYY",LLL:"Do MMMM[ta] YYYY, [klo] HH.mm",LLLL:"dddd, Do MMMM[ta] YYYY, [klo] HH.mm",l:"D.M.YYYY",ll:"Do MMM YYYY",lll:"Do MMM YYYY, [klo] HH.mm",llll:"ddd, Do MMM YYYY, [klo] HH.mm"},calendar:{sameDay:"[tänään] [klo] LT",nextDay:"[huomenna] [klo] LT",nextWeek:"dddd [klo] LT",lastDay:"[eilen] [klo] LT",lastWeek:"[viime] dddd[na] [klo] LT",sameElse:"L"},relativeTime:{future:"%s päästä",past:"%s sitten",s:e,m:e,mm:e,h:e,hh:e,d:e,dd:e,M:e,MM:e,y:e,yy:e},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:4}});return s}(),e.fullCalendar.datepickerLocale("fi","fi",{closeText:"Sulje",prevText:"&#xAB;Edellinen",nextText:"Seuraava&#xBB;",currentText:"Tänään",monthNames:["Tammikuu","Helmikuu","Maaliskuu","Huhtikuu","Toukokuu","Kesäkuu","Heinäkuu","Elokuu","Syyskuu","Lokakuu","Marraskuu","Joulukuu"],monthNamesShort:["Tammi","Helmi","Maalis","Huhti","Touko","Kesä","Heinä","Elo","Syys","Loka","Marras","Joulu"],dayNamesShort:["Su","Ma","Ti","Ke","To","Pe","La"],dayNames:["Sunnuntai","Maanantai","Tiistai","Keskiviikko","Torstai","Perjantai","Lauantai"],dayNamesMin:["Su","Ma","Ti","Ke","To","Pe","La"],weekHeader:"Vk",dateFormat:"d.m.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("fi",{buttonText:{month:"Kuukausi",week:"Viikko",day:"Päivä",list:"Tapahtumat"},allDayText:"Koko päivä",eventLimitText:"lisää",noEventsMessage:"Ei tapahtumia näytettäviä"})}(),function(){!function(){var e=a.defineLocale("fr",{months:"janvier_février_mars_avril_mai_juin_juillet_août_septembre_octobre_novembre_décembre".split("_"),monthsShort:"janv._févr._mars_avr._mai_juin_juil._août_sept._oct._nov._déc.".split("_"),monthsParseExact:!0,weekdays:"dimanche_lundi_mardi_mercredi_jeudi_vendredi_samedi".split("_"),weekdaysShort:"dim._lun._mar._mer._jeu._ven._sam.".split("_"),weekdaysMin:"Di_Lu_Ma_Me_Je_Ve_Sa".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd D MMMM YYYY HH:mm"},calendar:{sameDay:"[Aujourd'hui à] LT",nextDay:"[Demain à] LT",nextWeek:"dddd [à] LT",lastDay:"[Hier à] LT",lastWeek:"dddd [dernier à] LT",sameElse:"L"},relativeTime:{future:"dans %s",past:"il y a %s",s:"quelques secondes",m:"une minute",mm:"%d minutes",h:"une heure",hh:"%d heures",d:"un jour",dd:"%d jours",M:"un mois",MM:"%d mois",y:"un an",yy:"%d ans"},ordinalParse:/\d{1,2}(er|)/,ordinal:function(e){return e+(1===e?"er":"")},week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("fr","fr",{closeText:"Fermer",prevText:"Précédent",nextText:"Suivant",currentText:"Aujourd'hui",monthNames:["janvier","février","mars","avril","mai","juin","juillet","août","septembre","octobre","novembre","décembre"],monthNamesShort:["janv.","févr.","mars","avr.","mai","juin","juil.","août","sept.","oct.","nov.","déc."],dayNames:["dimanche","lundi","mardi","mercredi","jeudi","vendredi","samedi"],dayNamesShort:["dim.","lun.","mar.","mer.","jeu.","ven.","sam."],dayNamesMin:["D","L","M","M","J","V","S"],weekHeader:"Sem.",dateFormat:"dd/mm/yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("fr",{buttonText:{year:"Année",month:"Mois",week:"Semaine",day:"Jour",list:"Mon planning"},allDayHtml:"Toute la<br/>journée",eventLimitText:"en plus",noEventsMessage:"Aucun événement à afficher"})}(),function(){!function(){var e=a.defineLocale("fr-ca",{months:"janvier_février_mars_avril_mai_juin_juillet_août_septembre_octobre_novembre_décembre".split("_"),monthsShort:"janv._févr._mars_avr._mai_juin_juil._août_sept._oct._nov._déc.".split("_"),monthsParseExact:!0,weekdays:"dimanche_lundi_mardi_mercredi_jeudi_vendredi_samedi".split("_"),weekdaysShort:"dim._lun._mar._mer._jeu._ven._sam.".split("_"),weekdaysMin:"Di_Lu_Ma_Me_Je_Ve_Sa".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"YYYY-MM-DD",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd D MMMM YYYY HH:mm"},calendar:{sameDay:"[Aujourd'hui à] LT",nextDay:"[Demain à] LT",nextWeek:"dddd [à] LT",lastDay:"[Hier à] LT",lastWeek:"dddd [dernier à] LT",sameElse:"L"},relativeTime:{future:"dans %s",past:"il y a %s",s:"quelques secondes",m:"une minute",mm:"%d minutes",h:"une heure",hh:"%d heures",d:"un jour",dd:"%d jours",M:"un mois",MM:"%d mois",y:"un an",yy:"%d ans"},ordinalParse:/\d{1,2}(er|e)/,ordinal:function(e){return e+(1===e?"er":"e")}});return e}(),e.fullCalendar.datepickerLocale("fr-ca","fr-CA",{closeText:"Fermer",prevText:"Précédent",nextText:"Suivant",currentText:"Aujourd'hui",monthNames:["janvier","février","mars","avril","mai","juin","juillet","août","septembre","octobre","novembre","décembre"],monthNamesShort:["janv.","févr.","mars","avril","mai","juin","juil.","août","sept.","oct.","nov.","déc."],dayNames:["dimanche","lundi","mardi","mercredi","jeudi","vendredi","samedi"],dayNamesShort:["dim.","lun.","mar.","mer.","jeu.","ven.","sam."],dayNamesMin:["D","L","M","M","J","V","S"],weekHeader:"Sem.",dateFormat:"yy-mm-dd",firstDay:0,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("fr-ca",{buttonText:{year:"Année",month:"Mois",week:"Semaine",day:"Jour",list:"Mon planning"},allDayHtml:"Toute la<br/>journée",eventLimitText:"en plus",noEventsMessage:"Aucun événement à afficher"})}(),function(){!function(){var e=a.defineLocale("fr-ch",{months:"janvier_février_mars_avril_mai_juin_juillet_août_septembre_octobre_novembre_décembre".split("_"),monthsShort:"janv._févr._mars_avr._mai_juin_juil._août_sept._oct._nov._déc.".split("_"),monthsParseExact:!0,weekdays:"dimanche_lundi_mardi_mercredi_jeudi_vendredi_samedi".split("_"),weekdaysShort:"dim._lun._mar._mer._jeu._ven._sam.".split("_"),weekdaysMin:"Di_Lu_Ma_Me_Je_Ve_Sa".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD.MM.YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd D MMMM YYYY HH:mm"},calendar:{sameDay:"[Aujourd'hui à] LT",nextDay:"[Demain à] LT",nextWeek:"dddd [à] LT",lastDay:"[Hier à] LT",lastWeek:"dddd [dernier à] LT",sameElse:"L"},relativeTime:{future:"dans %s",past:"il y a %s",s:"quelques secondes",m:"une minute",mm:"%d minutes",h:"une heure",hh:"%d heures",d:"un jour",dd:"%d jours",M:"un mois",MM:"%d mois",y:"un an",yy:"%d ans"},ordinalParse:/\d{1,2}(er|e)/,ordinal:function(e){return e+(1===e?"er":"e")},week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("fr-ch","fr-CH",{closeText:"Fermer",prevText:"&#x3C;Préc",nextText:"Suiv&#x3E;",currentText:"Courant",monthNames:["janvier","février","mars","avril","mai","juin","juillet","août","septembre","octobre","novembre","décembre"],monthNamesShort:["janv.","févr.","mars","avril","mai","juin","juil.","août","sept.","oct.","nov.","déc."],dayNames:["dimanche","lundi","mardi","mercredi","jeudi","vendredi","samedi"],dayNamesShort:["dim.","lun.","mar.","mer.","jeu.","ven.","sam."],dayNamesMin:["D","L","M","M","J","V","S"],weekHeader:"Sm",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("fr-ch",{buttonText:{year:"Année",month:"Mois",week:"Semaine",day:"Jour",list:"Mon planning"},allDayHtml:"Toute la<br/>journée",eventLimitText:"en plus",noEventsMessage:"Aucun événement à afficher"})}(),function(){!function(){var e=a.defineLocale("gl",{months:"xaneiro_febreiro_marzo_abril_maio_xuño_xullo_agosto_setembro_outubro_novembro_decembro".split("_"),monthsShort:"xan._feb._mar._abr._mai._xuñ._xul._ago._set._out._nov._dec.".split("_"),monthsParseExact:!0,weekdays:"domingo_luns_martes_mércores_xoves_venres_sábado".split("_"),weekdaysShort:"dom._lun._mar._mér._xov._ven._sáb.".split("_"),weekdaysMin:"do_lu_ma_mé_xo_ve_sá".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"DD/MM/YYYY",LL:"D [de] MMMM [de] YYYY",LLL:"D [de] MMMM [de] YYYY H:mm",LLLL:"dddd, D [de] MMMM [de] YYYY H:mm"},calendar:{sameDay:function(){return"[hoxe "+(1!==this.hours()?"ás":"á")+"] LT"},nextDay:function(){return"[mañá "+(1!==this.hours()?"ás":"á")+"] LT"},nextWeek:function(){return"dddd ["+(1!==this.hours()?"ás":"a")+"] LT"},lastDay:function(){return"[onte "+(1!==this.hours()?"á":"a")+"] LT"},lastWeek:function(){return"[o] dddd [pasado "+(1!==this.hours()?"ás":"a")+"] LT"},sameElse:"L"},relativeTime:{future:function(e){return 0===e.indexOf("un")?"n"+e:"en "+e},past:"hai %s",s:"uns segundos",m:"un minuto",mm:"%d minutos",h:"unha hora",hh:"%d horas",d:"un día",dd:"%d días",M:"un mes",MM:"%d meses",y:"un ano",yy:"%d anos"},ordinalParse:/\d{1,2}º/,ordinal:"%dº",week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("gl","gl",{closeText:"Pechar",prevText:"&#x3C;Ant",nextText:"Seg&#x3E;",currentText:"Hoxe",monthNames:["Xaneiro","Febreiro","Marzo","Abril","Maio","Xuño","Xullo","Agosto","Setembro","Outubro","Novembro","Decembro"],monthNamesShort:["Xan","Feb","Mar","Abr","Mai","Xuñ","Xul","Ago","Set","Out","Nov","Dec"],dayNames:["Domingo","Luns","Martes","Mércores","Xoves","Venres","Sábado"],dayNamesShort:["Dom","Lun","Mar","Mér","Xov","Ven","Sáb"],dayNamesMin:["Do","Lu","Ma","Mé","Xo","Ve","Sá"],weekHeader:"Sm",dateFormat:"dd/mm/yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("gl",{buttonText:{month:"Mes",week:"Semana",day:"Día",list:"Axenda"},allDayHtml:"Todo<br/>o día",eventLimitText:"máis",noEventsMessage:"Non hai eventos para amosar"})}(),function(){!function(){var e=a.defineLocale("he",{months:"ינואר_פברואר_מרץ_אפריל_מאי_יוני_יולי_אוגוסט_ספטמבר_אוקטובר_נובמבר_דצמבר".split("_"),monthsShort:"ינו׳_פבר׳_מרץ_אפר׳_מאי_יוני_יולי_אוג׳_ספט׳_אוק׳_נוב׳_דצמ׳".split("_"),weekdays:"ראשון_שני_שלישי_רביעי_חמישי_שישי_שבת".split("_"),weekdaysShort:"א׳_ב׳_ג׳_ד׳_ה׳_ו׳_ש׳".split("_"),weekdaysMin:"א_ב_ג_ד_ה_ו_ש".split("_"),longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D [ב]MMMM YYYY",LLL:"D [ב]MMMM YYYY HH:mm",LLLL:"dddd, D [ב]MMMM YYYY HH:mm",l:"D/M/YYYY",ll:"D MMM YYYY",lll:"D MMM YYYY HH:mm",llll:"ddd, D MMM YYYY HH:mm"},calendar:{sameDay:"[היום ב־]LT",nextDay:"[מחר ב־]LT",nextWeek:"dddd [בשעה] LT",lastDay:"[אתמול ב־]LT",lastWeek:"[ביום] dddd [האחרון בשעה] LT",sameElse:"L"},relativeTime:{future:"בעוד %s",past:"לפני %s",s:"מספר שניות",m:"דקה",mm:"%d דקות",h:"שעה",hh:function(e){return 2===e?"שעתיים":e+" שעות"},d:"יום",dd:function(e){return 2===e?"יומיים":e+" ימים"},M:"חודש",MM:function(e){return 2===e?"חודשיים":e+" חודשים"},y:"שנה",yy:function(e){return 2===e?"שנתיים":e%10===0&&10!==e?e+" שנה":e+" שנים"}},meridiemParse:/אחה"צ|לפנה"צ|אחרי הצהריים|לפני הצהריים|לפנות בוקר|בבוקר|בערב/i,isPM:function(e){return/^(אחה"צ|אחרי הצהריים|בערב)$/.test(e)},meridiem:function(e,a,t){return e<5?"לפנות בוקר":e<10?"בבוקר":e<12?t?'לפנה"צ':"לפני הצהריים":e<18?t?'אחה"צ':"אחרי הצהריים":"בערב"}});return e}(),e.fullCalendar.datepickerLocale("he","he",{closeText:"סגור",prevText:"&#x3C;הקודם",nextText:"הבא&#x3E;",currentText:"היום",monthNames:["ינואר","פברואר","מרץ","אפריל","מאי","יוני","יולי","אוגוסט","ספטמבר","אוקטובר","נובמבר","דצמבר"],monthNamesShort:["ינו","פבר","מרץ","אפר","מאי","יוני","יולי","אוג","ספט","אוק","נוב","דצמ"],dayNames:["ראשון","שני","שלישי","רביעי","חמישי","שישי","שבת"],dayNamesShort:["א'","ב'","ג'","ד'","ה'","ו'","שבת"],dayNamesMin:["א'","ב'","ג'","ד'","ה'","ו'","שבת"],weekHeader:"Wk",dateFormat:"dd/mm/yy",firstDay:0,isRTL:!0,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("he",{buttonText:{month:"חודש",week:"שבוע",day:"יום",list:"סדר יום"},allDayText:"כל היום",eventLimitText:"אחר",noEventsMessage:"אין אירועים להצגה",weekNumberTitle:"שבוע"})}(),function(){!function(){var e={1:"१",2:"२",3:"३",4:"४",5:"५",6:"६",7:"७",8:"८",9:"९",0:"०"},t={"१":"1","२":"2","३":"3","४":"4","५":"5","६":"6","७":"7","८":"8","९":"9","०":"0"},n=a.defineLocale("hi",{months:"जनवरी_फ़रवरी_मार्च_अप्रैल_मई_जून_जुलाई_अगस्त_सितम्बर_अक्टूबर_नवम्बर_दिसम्बर".split("_"),monthsShort:"जन._फ़र._मार्च_अप्रै._मई_जून_जुल._अग._सित._अक्टू._नव._दिस.".split("_"),monthsParseExact:!0,weekdays:"रविवार_सोमवार_मंगलवार_बुधवार_गुरूवार_शुक्रवार_शनिवार".split("_"),weekdaysShort:"रवि_सोम_मंगल_बुध_गुरू_शुक्र_शनि".split("_"),weekdaysMin:"र_सो_मं_बु_गु_शु_श".split("_"),longDateFormat:{LT:"A h:mm बजे",LTS:"A h:mm:ss बजे",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY, A h:mm बजे",LLLL:"dddd, D MMMM YYYY, A h:mm बजे"},calendar:{sameDay:"[आज] LT",nextDay:"[कल] LT",nextWeek:"dddd, LT",lastDay:"[कल] LT",lastWeek:"[पिछले] dddd, LT",sameElse:"L"},relativeTime:{future:"%s में",past:"%s पहले",s:"कुछ ही क्षण",m:"एक मिनट",mm:"%d मिनट",h:"एक घंटा",hh:"%d घंटे",d:"एक दिन",dd:"%d दिन",M:"एक महीने",MM:"%d महीने",y:"एक वर्ष",yy:"%d वर्ष"},preparse:function(e){return e.replace(/[१२३४५६७८९०]/g,function(e){return t[e]})},postformat:function(a){return a.replace(/\d/g,function(a){return e[a]})},meridiemParse:/रात|सुबह|दोपहर|शाम/,meridiemHour:function(e,a){return 12===e&&(e=0),"रात"===a?e<4?e:e+12:"सुबह"===a?e:"दोपहर"===a?e>=10?e:e+12:"शाम"===a?e+12:void 0},meridiem:function(e,a,t){return e<4?"रात":e<10?"सुबह":e<17?"दोपहर":e<20?"शाम":"रात"},week:{dow:0,doy:6}});return n}(),e.fullCalendar.datepickerLocale("hi","hi",{closeText:"बंद",prevText:"पिछला",nextText:"अगला",currentText:"आज",monthNames:["जनवरी ","फरवरी","मार्च","अप्रेल","मई","जून","जूलाई","अगस्त ","सितम्बर","अक्टूबर","नवम्बर","दिसम्बर"],monthNamesShort:["जन","फर","मार्च","अप्रेल","मई","जून","जूलाई","अग","सित","अक्ट","नव","दि"],dayNames:["रविवार","सोमवार","मंगलवार","बुधवार","गुरुवार","शुक्रवार","शनिवार"],dayNamesShort:["रवि","सोम","मंगल","बुध","गुरु","शुक्र","शनि"],dayNamesMin:["रवि","सोम","मंगल","बुध","गुरु","शुक्र","शनि"],weekHeader:"हफ्ता",dateFormat:"dd/mm/yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("hi",{buttonText:{month:"महीना",week:"सप्ताह",day:"दिन",list:"कार्यसूची"},allDayText:"सभी दिन",eventLimitText:function(e){return"+अधिक "+e},noEventsMessage:"कोई घटनाओं को प्रदर्शित करने के लिए"})}(),function(){!function(){function e(e,a,t){var n=e+" ";switch(t){case"m":return a?"jedna minuta":"jedne minute";case"mm":return n+=1===e?"minuta":2===e||3===e||4===e?"minute":"minuta";case"h":return a?"jedan sat":"jednog sata";case"hh":return n+=1===e?"sat":2===e||3===e||4===e?"sata":"sati";case"dd":return n+=1===e?"dan":"dana";case"MM":return n+=1===e?"mjesec":2===e||3===e||4===e?"mjeseca":"mjeseci";case"yy":return n+=1===e?"godina":2===e||3===e||4===e?"godine":"godina"}}var t=a.defineLocale("hr",{months:{format:"siječnja_veljače_ožujka_travnja_svibnja_lipnja_srpnja_kolovoza_rujna_listopada_studenoga_prosinca".split("_"),standalone:"siječanj_veljača_ožujak_travanj_svibanj_lipanj_srpanj_kolovoz_rujan_listopad_studeni_prosinac".split("_")},monthsShort:"sij._velj._ožu._tra._svi._lip._srp._kol._ruj._lis._stu._pro.".split("_"),monthsParseExact:!0,weekdays:"nedjelja_ponedjeljak_utorak_srijeda_četvrtak_petak_subota".split("_"),weekdaysShort:"ned._pon._uto._sri._čet._pet._sub.".split("_"),weekdaysMin:"ne_po_ut_sr_če_pe_su".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"DD.MM.YYYY",LL:"D. MMMM YYYY",LLL:"D. MMMM YYYY H:mm",LLLL:"dddd, D. MMMM YYYY H:mm"},calendar:{sameDay:"[danas u] LT",nextDay:"[sutra u] LT",nextWeek:function(){switch(this.day()){case 0:return"[u] [nedjelju] [u] LT";case 3:return"[u] [srijedu] [u] LT";case 6:return"[u] [subotu] [u] LT";case 1:case 2:case 4:case 5:return"[u] dddd [u] LT"}},lastDay:"[jučer u] LT",lastWeek:function(){switch(this.day()){case 0:case 3:return"[prošlu] dddd [u] LT";case 6:return"[prošle] [subote] [u] LT";case 1:case 2:case 4:case 5:return"[prošli] dddd [u] LT"}},sameElse:"L"},relativeTime:{future:"za %s",past:"prije %s",s:"par sekundi",m:e,mm:e,h:e,hh:e,d:"dan",dd:e,M:"mjesec",MM:e,y:"godinu",yy:e},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:7}});return t}(),e.fullCalendar.datepickerLocale("hr","hr",{closeText:"Zatvori",prevText:"&#x3C;",nextText:"&#x3E;",currentText:"Danas",monthNames:["Siječanj","Veljača","Ožujak","Travanj","Svibanj","Lipanj","Srpanj","Kolovoz","Rujan","Listopad","Studeni","Prosinac"],
-monthNamesShort:["Sij","Velj","Ožu","Tra","Svi","Lip","Srp","Kol","Ruj","Lis","Stu","Pro"],dayNames:["Nedjelja","Ponedjeljak","Utorak","Srijeda","Četvrtak","Petak","Subota"],dayNamesShort:["Ned","Pon","Uto","Sri","Čet","Pet","Sub"],dayNamesMin:["Ne","Po","Ut","Sr","Če","Pe","Su"],weekHeader:"Tje",dateFormat:"dd.mm.yy.",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("hr",{buttonText:{month:"Mjesec",week:"Tjedan",day:"Dan",list:"Raspored"},allDayText:"Cijeli dan",eventLimitText:function(e){return"+ još "+e},noEventsMessage:"Nema događaja za prikaz"})}(),function(){!function(){function e(e,a,t,n){var r=e;switch(t){case"s":return n||a?"néhány másodperc":"néhány másodperce";case"m":return"egy"+(n||a?" perc":" perce");case"mm":return r+(n||a?" perc":" perce");case"h":return"egy"+(n||a?" óra":" órája");case"hh":return r+(n||a?" óra":" órája");case"d":return"egy"+(n||a?" nap":" napja");case"dd":return r+(n||a?" nap":" napja");case"M":return"egy"+(n||a?" hónap":" hónapja");case"MM":return r+(n||a?" hónap":" hónapja");case"y":return"egy"+(n||a?" év":" éve");case"yy":return r+(n||a?" év":" éve")}return""}function t(e){return(e?"":"[múlt] ")+"["+n[this.day()]+"] LT[-kor]"}var n="vasárnap hétfőn kedden szerdán csütörtökön pénteken szombaton".split(" "),r=a.defineLocale("hu",{months:"január_február_március_április_május_június_július_augusztus_szeptember_október_november_december".split("_"),monthsShort:"jan_feb_márc_ápr_máj_jún_júl_aug_szept_okt_nov_dec".split("_"),weekdays:"vasárnap_hétfő_kedd_szerda_csütörtök_péntek_szombat".split("_"),weekdaysShort:"vas_hét_kedd_sze_csüt_pén_szo".split("_"),weekdaysMin:"v_h_k_sze_cs_p_szo".split("_"),longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"YYYY.MM.DD.",LL:"YYYY. MMMM D.",LLL:"YYYY. MMMM D. H:mm",LLLL:"YYYY. MMMM D., dddd H:mm"},meridiemParse:/de|du/i,isPM:function(e){return"u"===e.charAt(1).toLowerCase()},meridiem:function(e,a,t){return e<12?t===!0?"de":"DE":t===!0?"du":"DU"},calendar:{sameDay:"[ma] LT[-kor]",nextDay:"[holnap] LT[-kor]",nextWeek:function(){return t.call(this,!0)},lastDay:"[tegnap] LT[-kor]",lastWeek:function(){return t.call(this,!1)},sameElse:"L"},relativeTime:{future:"%s múlva",past:"%s",s:e,m:e,mm:e,h:e,hh:e,d:e,dd:e,M:e,MM:e,y:e,yy:e},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:4}});return r}(),e.fullCalendar.datepickerLocale("hu","hu",{closeText:"bezár",prevText:"vissza",nextText:"előre",currentText:"ma",monthNames:["Január","Február","Március","Április","Május","Június","Július","Augusztus","Szeptember","Október","November","December"],monthNamesShort:["Jan","Feb","Már","Ápr","Máj","Jún","Júl","Aug","Szep","Okt","Nov","Dec"],dayNames:["Vasárnap","Hétfő","Kedd","Szerda","Csütörtök","Péntek","Szombat"],dayNamesShort:["Vas","Hét","Ked","Sze","Csü","Pén","Szo"],dayNamesMin:["V","H","K","Sze","Cs","P","Szo"],weekHeader:"Hét",dateFormat:"yy.mm.dd.",firstDay:1,isRTL:!1,showMonthAfterYear:!0,yearSuffix:""}),e.fullCalendar.locale("hu",{buttonText:{month:"Hónap",week:"Hét",day:"Nap",list:"Napló"},allDayText:"Egész nap",eventLimitText:"további",noEventsMessage:"Nincs megjeleníthető események"})}(),function(){!function(){var e=a.defineLocale("id",{months:"Januari_Februari_Maret_April_Mei_Juni_Juli_Agustus_September_Oktober_November_Desember".split("_"),monthsShort:"Jan_Feb_Mar_Apr_Mei_Jun_Jul_Ags_Sep_Okt_Nov_Des".split("_"),weekdays:"Minggu_Senin_Selasa_Rabu_Kamis_Jumat_Sabtu".split("_"),weekdaysShort:"Min_Sen_Sel_Rab_Kam_Jum_Sab".split("_"),weekdaysMin:"Mg_Sn_Sl_Rb_Km_Jm_Sb".split("_"),longDateFormat:{LT:"HH.mm",LTS:"HH.mm.ss",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY [pukul] HH.mm",LLLL:"dddd, D MMMM YYYY [pukul] HH.mm"},meridiemParse:/pagi|siang|sore|malam/,meridiemHour:function(e,a){return 12===e&&(e=0),"pagi"===a?e:"siang"===a?e>=11?e:e+12:"sore"===a||"malam"===a?e+12:void 0},meridiem:function(e,a,t){return e<11?"pagi":e<15?"siang":e<19?"sore":"malam"},calendar:{sameDay:"[Hari ini pukul] LT",nextDay:"[Besok pukul] LT",nextWeek:"dddd [pukul] LT",lastDay:"[Kemarin pukul] LT",lastWeek:"dddd [lalu pukul] LT",sameElse:"L"},relativeTime:{future:"dalam %s",past:"%s yang lalu",s:"beberapa detik",m:"semenit",mm:"%d menit",h:"sejam",hh:"%d jam",d:"sehari",dd:"%d hari",M:"sebulan",MM:"%d bulan",y:"setahun",yy:"%d tahun"},week:{dow:1,doy:7}});return e}(),e.fullCalendar.datepickerLocale("id","id",{closeText:"Tutup",prevText:"&#x3C;mundur",nextText:"maju&#x3E;",currentText:"hari ini",monthNames:["Januari","Februari","Maret","April","Mei","Juni","Juli","Agustus","September","Oktober","Nopember","Desember"],monthNamesShort:["Jan","Feb","Mar","Apr","Mei","Jun","Jul","Agus","Sep","Okt","Nop","Des"],dayNames:["Minggu","Senin","Selasa","Rabu","Kamis","Jumat","Sabtu"],dayNamesShort:["Min","Sen","Sel","Rab","kam","Jum","Sab"],dayNamesMin:["Mg","Sn","Sl","Rb","Km","jm","Sb"],weekHeader:"Mg",dateFormat:"dd/mm/yy",firstDay:0,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("id",{buttonText:{month:"Bulan",week:"Minggu",day:"Hari",list:"Agenda"},allDayHtml:"Sehari<br/>penuh",eventLimitText:"lebih",noEventsMessage:"Tidak ada acara untuk ditampilkan"})}(),function(){!function(){function e(e){return e%100===11||e%10!==1}function t(a,t,n,r){var s=a+" ";switch(n){case"s":return t||r?"nokkrar sekúndur":"nokkrum sekúndum";case"m":return t?"mínúta":"mínútu";case"mm":return e(a)?s+(t||r?"mínútur":"mínútum"):t?s+"mínúta":s+"mínútu";case"hh":return e(a)?s+(t||r?"klukkustundir":"klukkustundum"):s+"klukkustund";case"d":return t?"dagur":r?"dag":"degi";case"dd":return e(a)?t?s+"dagar":s+(r?"daga":"dögum"):t?s+"dagur":s+(r?"dag":"degi");case"M":return t?"mánuður":r?"mánuð":"mánuði";case"MM":return e(a)?t?s+"mánuðir":s+(r?"mánuði":"mánuðum"):t?s+"mánuður":s+(r?"mánuð":"mánuði");case"y":return t||r?"ár":"ári";case"yy":return e(a)?s+(t||r?"ár":"árum"):s+(t||r?"ár":"ári")}}var n=a.defineLocale("is",{months:"janúar_febrúar_mars_apríl_maí_júní_júlí_ágúst_september_október_nóvember_desember".split("_"),monthsShort:"jan_feb_mar_apr_maí_jún_júl_ágú_sep_okt_nóv_des".split("_"),weekdays:"sunnudagur_mánudagur_þriðjudagur_miðvikudagur_fimmtudagur_föstudagur_laugardagur".split("_"),weekdaysShort:"sun_mán_þri_mið_fim_fös_lau".split("_"),weekdaysMin:"Su_Má_Þr_Mi_Fi_Fö_La".split("_"),longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"DD.MM.YYYY",LL:"D. MMMM YYYY",LLL:"D. MMMM YYYY [kl.] H:mm",LLLL:"dddd, D. MMMM YYYY [kl.] H:mm"},calendar:{sameDay:"[í dag kl.] LT",nextDay:"[á morgun kl.] LT",nextWeek:"dddd [kl.] LT",lastDay:"[í gær kl.] LT",lastWeek:"[síðasta] dddd [kl.] LT",sameElse:"L"},relativeTime:{future:"eftir %s",past:"fyrir %s síðan",s:t,m:t,mm:t,h:"klukkustund",hh:t,d:t,dd:t,M:t,MM:t,y:t,yy:t},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:4}});return n}(),e.fullCalendar.datepickerLocale("is","is",{closeText:"Loka",prevText:"&#x3C; Fyrri",nextText:"Næsti &#x3E;",currentText:"Í dag",monthNames:["Janúar","Febrúar","Mars","Apríl","Maí","Júní","Júlí","Ágúst","September","Október","Nóvember","Desember"],monthNamesShort:["Jan","Feb","Mar","Apr","Maí","Jún","Júl","Ágú","Sep","Okt","Nóv","Des"],dayNames:["Sunnudagur","Mánudagur","Þriðjudagur","Miðvikudagur","Fimmtudagur","Föstudagur","Laugardagur"],dayNamesShort:["Sun","Mán","Þri","Mið","Fim","Fös","Lau"],dayNamesMin:["Su","Má","Þr","Mi","Fi","Fö","La"],weekHeader:"Vika",dateFormat:"dd.mm.yy",firstDay:0,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("is",{buttonText:{month:"Mánuður",week:"Vika",day:"Dagur",list:"Dagskrá"},allDayHtml:"Allan<br/>daginn",eventLimitText:"meira",noEventsMessage:"Engir viðburðir til að sýna"})}(),function(){!function(){var e=a.defineLocale("it",{months:"gennaio_febbraio_marzo_aprile_maggio_giugno_luglio_agosto_settembre_ottobre_novembre_dicembre".split("_"),monthsShort:"gen_feb_mar_apr_mag_giu_lug_ago_set_ott_nov_dic".split("_"),weekdays:"Domenica_Lunedì_Martedì_Mercoledì_Giovedì_Venerdì_Sabato".split("_"),weekdaysShort:"Dom_Lun_Mar_Mer_Gio_Ven_Sab".split("_"),weekdaysMin:"Do_Lu_Ma_Me_Gi_Ve_Sa".split("_"),longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd, D MMMM YYYY HH:mm"},calendar:{sameDay:"[Oggi alle] LT",nextDay:"[Domani alle] LT",nextWeek:"dddd [alle] LT",lastDay:"[Ieri alle] LT",lastWeek:function(){switch(this.day()){case 0:return"[la scorsa] dddd [alle] LT";default:return"[lo scorso] dddd [alle] LT"}},sameElse:"L"},relativeTime:{future:function(e){return(/^[0-9].+$/.test(e)?"tra":"in")+" "+e},past:"%s fa",s:"alcuni secondi",m:"un minuto",mm:"%d minuti",h:"un'ora",hh:"%d ore",d:"un giorno",dd:"%d giorni",M:"un mese",MM:"%d mesi",y:"un anno",yy:"%d anni"},ordinalParse:/\d{1,2}º/,ordinal:"%dº",week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("it","it",{closeText:"Chiudi",prevText:"&#x3C;Prec",nextText:"Succ&#x3E;",currentText:"Oggi",monthNames:["Gennaio","Febbraio","Marzo","Aprile","Maggio","Giugno","Luglio","Agosto","Settembre","Ottobre","Novembre","Dicembre"],monthNamesShort:["Gen","Feb","Mar","Apr","Mag","Giu","Lug","Ago","Set","Ott","Nov","Dic"],dayNames:["Domenica","Lunedì","Martedì","Mercoledì","Giovedì","Venerdì","Sabato"],dayNamesShort:["Dom","Lun","Mar","Mer","Gio","Ven","Sab"],dayNamesMin:["Do","Lu","Ma","Me","Gi","Ve","Sa"],weekHeader:"Sm",dateFormat:"dd/mm/yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("it",{buttonText:{month:"Mese",week:"Settimana",day:"Giorno",list:"Agenda"},allDayHtml:"Tutto il<br/>giorno",eventLimitText:function(e){return"+altri "+e},noEventsMessage:"Non ci sono eventi da visualizzare"})}(),function(){!function(){var e=a.defineLocale("ja",{months:"1月_2月_3月_4月_5月_6月_7月_8月_9月_10月_11月_12月".split("_"),monthsShort:"1月_2月_3月_4月_5月_6月_7月_8月_9月_10月_11月_12月".split("_"),weekdays:"日曜日_月曜日_火曜日_水曜日_木曜日_金曜日_土曜日".split("_"),weekdaysShort:"日_月_火_水_木_金_土".split("_"),weekdaysMin:"日_月_火_水_木_金_土".split("_"),longDateFormat:{LT:"Ah時m分",LTS:"Ah時m分s秒",L:"YYYY/MM/DD",LL:"YYYY年M月D日",LLL:"YYYY年M月D日Ah時m分",LLLL:"YYYY年M月D日Ah時m分 dddd"},meridiemParse:/午前|午後/i,isPM:function(e){return"午後"===e},meridiem:function(e,a,t){return e<12?"午前":"午後"},calendar:{sameDay:"[今日] LT",nextDay:"[明日] LT",nextWeek:"[来週]dddd LT",lastDay:"[昨日] LT",lastWeek:"[前週]dddd LT",sameElse:"L"},ordinalParse:/\d{1,2}日/,ordinal:function(e,a){switch(a){case"d":case"D":case"DDD":return e+"日";default:return e}},relativeTime:{future:"%s後",past:"%s前",s:"数秒",m:"1分",mm:"%d分",h:"1時間",hh:"%d時間",d:"1日",dd:"%d日",M:"1ヶ月",MM:"%dヶ月",y:"1年",yy:"%d年"}});return e}(),e.fullCalendar.datepickerLocale("ja","ja",{closeText:"閉じる",prevText:"&#x3C;前",nextText:"次&#x3E;",currentText:"今日",monthNames:["1月","2月","3月","4月","5月","6月","7月","8月","9月","10月","11月","12月"],monthNamesShort:["1月","2月","3月","4月","5月","6月","7月","8月","9月","10月","11月","12月"],dayNames:["日曜日","月曜日","火曜日","水曜日","木曜日","金曜日","土曜日"],dayNamesShort:["日","月","火","水","木","金","土"],dayNamesMin:["日","月","火","水","木","金","土"],weekHeader:"週",dateFormat:"yy/mm/dd",firstDay:0,isRTL:!1,showMonthAfterYear:!0,yearSuffix:"年"}),e.fullCalendar.locale("ja",{buttonText:{month:"月",week:"週",day:"日",list:"予定リスト"},allDayText:"終日",eventLimitText:function(e){return"他 "+e+" 件"},noEventsMessage:"イベントが表示されないように"})}(),function(){!function(){var e={0:"-ші",1:"-ші",2:"-ші",3:"-ші",4:"-ші",5:"-ші",6:"-шы",7:"-ші",8:"-ші",9:"-шы",10:"-шы",20:"-шы",30:"-шы",40:"-шы",50:"-ші",60:"-шы",70:"-ші",80:"-ші",90:"-шы",100:"-ші"},t=a.defineLocale("kk",{months:"қаңтар_ақпан_наурыз_сәуір_мамыр_маусым_шілде_тамыз_қыркүйек_қазан_қараша_желтоқсан".split("_"),monthsShort:"қаң_ақп_нау_сәу_мам_мау_шіл_там_қыр_қаз_қар_жел".split("_"),weekdays:"жексенбі_дүйсенбі_сейсенбі_сәрсенбі_бейсенбі_жұма_сенбі".split("_"),weekdaysShort:"жек_дүй_сей_сәр_бей_жұм_сен".split("_"),weekdaysMin:"жк_дй_сй_ср_бй_жм_сн".split("_"),longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD.MM.YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd, D MMMM YYYY HH:mm"},calendar:{sameDay:"[Бүгін сағат] LT",nextDay:"[Ертең сағат] LT",nextWeek:"dddd [сағат] LT",lastDay:"[Кеше сағат] LT",lastWeek:"[Өткен аптаның] dddd [сағат] LT",sameElse:"L"},relativeTime:{future:"%s ішінде",past:"%s бұрын",s:"бірнеше секунд",m:"бір минут",mm:"%d минут",h:"бір сағат",hh:"%d сағат",d:"бір күн",dd:"%d күн",M:"бір ай",MM:"%d ай",y:"бір жыл",yy:"%d жыл"},ordinalParse:/\d{1,2}-(ші|шы)/,ordinal:function(a){var t=a%10,n=a>=100?100:null;return a+(e[a]||e[t]||e[n])},week:{dow:1,doy:7}});return t}(),e.fullCalendar.datepickerLocale("kk","kk",{closeText:"Жабу",prevText:"&#x3C;Алдыңғы",nextText:"Келесі&#x3E;",currentText:"Бүгін",monthNames:["Қаңтар","Ақпан","Наурыз","Сәуір","Мамыр","Маусым","Шілде","Тамыз","Қыркүйек","Қазан","Қараша","Желтоқсан"],monthNamesShort:["Қаң","Ақп","Нау","Сәу","Мам","Мау","Шіл","Там","Қыр","Қаз","Қар","Жел"],dayNames:["Жексенбі","Дүйсенбі","Сейсенбі","Сәрсенбі","Бейсенбі","Жұма","Сенбі"],dayNamesShort:["жкс","дсн","ссн","срс","бсн","жма","снб"],dayNamesMin:["Жк","Дс","Сс","Ср","Бс","Жм","Сн"],weekHeader:"Не",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("kk",{buttonText:{month:"Ай",week:"Апта",day:"Күн",list:"Күн тәртібі"},allDayText:"Күні бойы",eventLimitText:function(e){return"+ тағы "+e},noEventsMessage:"Көрсету үшін оқиғалар жоқ"})}(),function(){!function(){var e=a.defineLocale("ko",{months:"1월_2월_3월_4월_5월_6월_7월_8월_9월_10월_11월_12월".split("_"),monthsShort:"1월_2월_3월_4월_5월_6월_7월_8월_9월_10월_11월_12월".split("_"),weekdays:"일요일_월요일_화요일_수요일_목요일_금요일_토요일".split("_"),weekdaysShort:"일_월_화_수_목_금_토".split("_"),weekdaysMin:"일_월_화_수_목_금_토".split("_"),longDateFormat:{LT:"A h시 m분",LTS:"A h시 m분 s초",L:"YYYY.MM.DD",LL:"YYYY년 MMMM D일",LLL:"YYYY년 MMMM D일 A h시 m분",LLLL:"YYYY년 MMMM D일 dddd A h시 m분"},calendar:{sameDay:"오늘 LT",nextDay:"내일 LT",nextWeek:"dddd LT",lastDay:"어제 LT",lastWeek:"지난주 dddd LT",sameElse:"L"},relativeTime:{future:"%s 후",past:"%s 전",s:"몇 초",ss:"%d초",m:"일분",mm:"%d분",h:"한 시간",hh:"%d시간",d:"하루",dd:"%d일",M:"한 달",MM:"%d달",y:"일 년",yy:"%d년"},ordinalParse:/\d{1,2}일/,ordinal:"%d일",meridiemParse:/오전|오후/,isPM:function(e){return"오후"===e},meridiem:function(e,a,t){return e<12?"오전":"오후"}});return e}(),e.fullCalendar.datepickerLocale("ko","ko",{closeText:"닫기",prevText:"이전달",nextText:"다음달",currentText:"오늘",monthNames:["1월","2월","3월","4월","5월","6월","7월","8월","9월","10월","11월","12월"],monthNamesShort:["1월","2월","3월","4월","5월","6월","7월","8월","9월","10월","11월","12월"],dayNames:["일요일","월요일","화요일","수요일","목요일","금요일","토요일"],dayNamesShort:["일","월","화","수","목","금","토"],dayNamesMin:["일","월","화","수","목","금","토"],weekHeader:"주",dateFormat:"yy. m. d.",firstDay:0,isRTL:!1,showMonthAfterYear:!0,yearSuffix:"년"}),e.fullCalendar.locale("ko",{buttonText:{month:"월",week:"주",day:"일",list:"일정목록"},allDayText:"종일",eventLimitText:"개",noEventsMessage:"일정이 표시 없습니다"})}(),function(){!function(){function e(e,a,t,n){var r={m:["eng Minutt","enger Minutt"],h:["eng Stonn","enger Stonn"],d:["een Dag","engem Dag"],M:["ee Mount","engem Mount"],y:["ee Joer","engem Joer"]};return a?r[t][0]:r[t][1]}function t(e){var a=e.substr(0,e.indexOf(" "));return r(a)?"a "+e:"an "+e}function n(e){var a=e.substr(0,e.indexOf(" "));return r(a)?"viru "+e:"virun "+e}function r(e){if(e=parseInt(e,10),isNaN(e))return!1;if(e<0)return!0;if(e<10)return 4<=e&&e<=7;if(e<100){var a=e%10,t=e/10;return r(0===a?t:a)}if(e<1e4){for(;e>=10;)e/=10;return r(e)}return e/=1e3,r(e)}var s=a.defineLocale("lb",{months:"Januar_Februar_Mäerz_Abrëll_Mee_Juni_Juli_August_September_Oktober_November_Dezember".split("_"),monthsShort:"Jan._Febr._Mrz._Abr._Mee_Jun._Jul._Aug._Sept._Okt._Nov._Dez.".split("_"),monthsParseExact:!0,weekdays:"Sonndeg_Méindeg_Dënschdeg_Mëttwoch_Donneschdeg_Freideg_Samschdeg".split("_"),weekdaysShort:"So._Mé._Dë._Më._Do._Fr._Sa.".split("_"),weekdaysMin:"So_Mé_Dë_Më_Do_Fr_Sa".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"H:mm [Auer]",LTS:"H:mm:ss [Auer]",L:"DD.MM.YYYY",LL:"D. MMMM YYYY",LLL:"D. MMMM YYYY H:mm [Auer]",LLLL:"dddd, D. MMMM YYYY H:mm [Auer]"},calendar:{sameDay:"[Haut um] LT",sameElse:"L",nextDay:"[Muer um] LT",nextWeek:"dddd [um] LT",lastDay:"[Gëschter um] LT",lastWeek:function(){switch(this.day()){case 2:case 4:return"[Leschten] dddd [um] LT";default:return"[Leschte] dddd [um] LT"}}},relativeTime:{future:t,past:n,s:"e puer Sekonnen",m:e,mm:"%d Minutten",h:e,hh:"%d Stonnen",d:e,dd:"%d Deeg",M:e,MM:"%d Méint",y:e,yy:"%d Joer"},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:4}});return s}(),e.fullCalendar.datepickerLocale("lb","lb",{closeText:"Fäerdeg",prevText:"Zréck",nextText:"Weider",currentText:"Haut",monthNames:["Januar","Februar","Mäerz","Abrëll","Mee","Juni","Juli","August","September","Oktober","November","Dezember"],monthNamesShort:["Jan","Feb","Mäe","Abr","Mee","Jun","Jul","Aug","Sep","Okt","Nov","Dez"],dayNames:["Sonndeg","Méindeg","Dënschdeg","Mëttwoch","Donneschdeg","Freideg","Samschdeg"],dayNamesShort:["Son","Méi","Dën","Mët","Don","Fre","Sam"],dayNamesMin:["So","Mé","Dë","Më","Do","Fr","Sa"],weekHeader:"W",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("lb",{buttonText:{month:"Mount",week:"Woch",day:"Dag",list:"Terminiwwersiicht"},allDayText:"Ganzen Dag",eventLimitText:"méi",noEventsMessage:"Nee Evenementer ze affichéieren"})}(),function(){!function(){function e(e,a,t,n){return a?"kelios sekundės":n?"kelių sekundžių":"kelias sekundes"}function t(e,a,t,n){return a?r(t)[0]:n?r(t)[1]:r(t)[2]}function n(e){return e%10===0||e>10&&e<20}function r(e){return d[e].split("_")}function s(e,a,s,d){var i=e+" ";return 1===e?i+t(e,a,s[0],d):a?i+(n(e)?r(s)[1]:r(s)[0]):d?i+r(s)[1]:i+(n(e)?r(s)[1]:r(s)[2])}var d={m:"minutė_minutės_minutę",mm:"minutės_minučių_minutes",h:"valanda_valandos_valandą",hh:"valandos_valandų_valandas",d:"diena_dienos_dieną",dd:"dienos_dienų_dienas",M:"mėnuo_mėnesio_mėnesį",MM:"mėnesiai_mėnesių_mėnesius",y:"metai_metų_metus",yy:"metai_metų_metus"},i=a.defineLocale("lt",{months:{format:"sausio_vasario_kovo_balandžio_gegužės_birželio_liepos_rugpjūčio_rugsėjo_spalio_lapkričio_gruodžio".split("_"),standalone:"sausis_vasaris_kovas_balandis_gegužė_birželis_liepa_rugpjūtis_rugsėjis_spalis_lapkritis_gruodis".split("_"),isFormat:/D[oD]?(\[[^\[\]]*\]|\s)+MMMM?|MMMM?(\[[^\[\]]*\]|\s)+D[oD]?/},monthsShort:"sau_vas_kov_bal_geg_bir_lie_rgp_rgs_spa_lap_grd".split("_"),weekdays:{format:"sekmadienį_pirmadienį_antradienį_trečiadienį_ketvirtadienį_penktadienį_šeštadienį".split("_"),standalone:"sekmadienis_pirmadienis_antradienis_trečiadienis_ketvirtadienis_penktadienis_šeštadienis".split("_"),isFormat:/dddd HH:mm/},weekdaysShort:"Sek_Pir_Ant_Tre_Ket_Pen_Šeš".split("_"),weekdaysMin:"S_P_A_T_K_Pn_Š".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"YYYY-MM-DD",LL:"YYYY [m.] MMMM D [d.]",LLL:"YYYY [m.] MMMM D [d.], HH:mm [val.]",LLLL:"YYYY [m.] MMMM D [d.], dddd, HH:mm [val.]",l:"YYYY-MM-DD",ll:"YYYY [m.] MMMM D [d.]",lll:"YYYY [m.] MMMM D [d.], HH:mm [val.]",llll:"YYYY [m.] MMMM D [d.], ddd, HH:mm [val.]"},calendar:{sameDay:"[Šiandien] LT",nextDay:"[Rytoj] LT",nextWeek:"dddd LT",lastDay:"[Vakar] LT",lastWeek:"[Praėjusį] dddd LT",sameElse:"L"},relativeTime:{future:"po %s",past:"prieš %s",s:e,m:t,mm:s,h:t,hh:s,d:t,dd:s,M:t,MM:s,y:t,yy:s},ordinalParse:/\d{1,2}-oji/,ordinal:function(e){return e+"-oji"},week:{dow:1,doy:4}});return i}(),e.fullCalendar.datepickerLocale("lt","lt",{closeText:"Uždaryti",prevText:"&#x3C;Atgal",nextText:"Pirmyn&#x3E;",currentText:"Šiandien",monthNames:["Sausis","Vasaris","Kovas","Balandis","Gegužė","Birželis","Liepa","Rugpjūtis","Rugsėjis","Spalis","Lapkritis","Gruodis"],monthNamesShort:["Sau","Vas","Kov","Bal","Geg","Bir","Lie","Rugp","Rugs","Spa","Lap","Gru"],dayNames:["sekmadienis","pirmadienis","antradienis","trečiadienis","ketvirtadienis","penktadienis","šeštadienis"],dayNamesShort:["sek","pir","ant","tre","ket","pen","šeš"],dayNamesMin:["Se","Pr","An","Tr","Ke","Pe","Še"],weekHeader:"SAV",dateFormat:"yy-mm-dd",firstDay:1,isRTL:!1,showMonthAfterYear:!0,yearSuffix:""}),e.fullCalendar.locale("lt",{buttonText:{month:"Mėnuo",week:"Savaitė",day:"Diena",list:"Darbotvarkė"},allDayText:"Visą dieną",eventLimitText:"daugiau",noEventsMessage:"Nėra įvykių rodyti"})}(),function(){!function(){function e(e,a,t){return t?a%10===1&&a%100!==11?e[2]:e[3]:a%10===1&&a%100!==11?e[0]:e[1]}function t(a,t,n){return a+" "+e(s[n],a,t)}function n(a,t,n){return e(s[n],a,t)}function r(e,a){return a?"dažas sekundes":"dažām sekundēm"}var s={m:"minūtes_minūtēm_minūte_minūtes".split("_"),mm:"minūtes_minūtēm_minūte_minūtes".split("_"),h:"stundas_stundām_stunda_stundas".split("_"),hh:"stundas_stundām_stunda_stundas".split("_"),d:"dienas_dienām_diena_dienas".split("_"),dd:"dienas_dienām_diena_dienas".split("_"),M:"mēneša_mēnešiem_mēnesis_mēneši".split("_"),MM:"mēneša_mēnešiem_mēnesis_mēneši".split("_"),y:"gada_gadiem_gads_gadi".split("_"),yy:"gada_gadiem_gads_gadi".split("_")},d=a.defineLocale("lv",{months:"janvāris_februāris_marts_aprīlis_maijs_jūnijs_jūlijs_augusts_septembris_oktobris_novembris_decembris".split("_"),monthsShort:"jan_feb_mar_apr_mai_jūn_jūl_aug_sep_okt_nov_dec".split("_"),weekdays:"svētdiena_pirmdiena_otrdiena_trešdiena_ceturtdiena_piektdiena_sestdiena".split("_"),weekdaysShort:"Sv_P_O_T_C_Pk_S".split("_"),weekdaysMin:"Sv_P_O_T_C_Pk_S".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD.MM.YYYY.",LL:"YYYY. [gada] D. MMMM",LLL:"YYYY. [gada] D. MMMM, HH:mm",LLLL:"YYYY. [gada] D. MMMM, dddd, HH:mm"},calendar:{sameDay:"[Šodien pulksten] LT",nextDay:"[Rīt pulksten] LT",nextWeek:"dddd [pulksten] LT",lastDay:"[Vakar pulksten] LT",lastWeek:"[Pagājušā] dddd [pulksten] LT",sameElse:"L"},relativeTime:{future:"pēc %s",past:"pirms %s",s:r,m:n,mm:t,h:n,hh:t,d:n,dd:t,M:n,MM:t,y:n,yy:t},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:4}});return d}(),e.fullCalendar.datepickerLocale("lv","lv",{closeText:"Aizvērt",prevText:"Iepr.",nextText:"Nāk.",currentText:"Šodien",monthNames:["Janvāris","Februāris","Marts","Aprīlis","Maijs","Jūnijs","Jūlijs","Augusts","Septembris","Oktobris","Novembris","Decembris"],monthNamesShort:["Jan","Feb","Mar","Apr","Mai","Jūn","Jūl","Aug","Sep","Okt","Nov","Dec"],dayNames:["svētdiena","pirmdiena","otrdiena","trešdiena","ceturtdiena","piektdiena","sestdiena"],dayNamesShort:["svt","prm","otr","tre","ctr","pkt","sst"],dayNamesMin:["Sv","Pr","Ot","Tr","Ct","Pk","Ss"],weekHeader:"Ned.",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("lv",{buttonText:{month:"Mēnesis",week:"Nedēļa",day:"Diena",list:"Dienas kārtība"},allDayText:"Visu dienu",eventLimitText:function(e){return"+vēl "+e},noEventsMessage:"Nav notikumu, lai parādītu"})}(),function(){!function(){var e=a.defineLocale("mk",{months:"јануари_февруари_март_април_мај_јуни_јули_август_септември_октомври_ноември_декември".split("_"),monthsShort:"јан_фев_мар_апр_мај_јун_јул_авг_сеп_окт_ное_дек".split("_"),weekdays:"недела_понеделник_вторник_среда_четврток_петок_сабота".split("_"),weekdaysShort:"нед_пон_вто_сре_чет_пет_саб".split("_"),weekdaysMin:"нe_пo_вт_ср_че_пе_сa".split("_"),longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"D.MM.YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY H:mm",LLLL:"dddd, D MMMM YYYY H:mm"},calendar:{sameDay:"[Денес во] LT",nextDay:"[Утре во] LT",nextWeek:"[Во] dddd [во] LT",lastDay:"[Вчера во] LT",lastWeek:function(){switch(this.day()){case 0:case 3:case 6:return"[Изминатата] dddd [во] LT";case 1:case 2:case 4:case 5:return"[Изминатиот] dddd [во] LT"}},sameElse:"L"},relativeTime:{future:"после %s",past:"пред %s",s:"неколку секунди",m:"минута",mm:"%d минути",h:"час",hh:"%d часа",d:"ден",dd:"%d дена",M:"месец",MM:"%d месеци",y:"година",yy:"%d години"},ordinalParse:/\d{1,2}-(ев|ен|ти|ви|ри|ми)/,ordinal:function(e){var a=e%10,t=e%100;return 0===e?e+"-ев":0===t?e+"-ен":t>10&&t<20?e+"-ти":1===a?e+"-ви":2===a?e+"-ри":7===a||8===a?e+"-ми":e+"-ти"},week:{dow:1,doy:7}});return e}(),e.fullCalendar.datepickerLocale("mk","mk",{closeText:"Затвори",prevText:"&#x3C;",nextText:"&#x3E;",currentText:"Денес",monthNames:["Јануари","Февруари","Март","Април","Мај","Јуни","Јули","Август","Септември","Октомври","Ноември","Декември"],monthNamesShort:["Јан","Фев","Мар","Апр","Мај","Јун","Јул","Авг","Сеп","Окт","Ное","Дек"],dayNames:["Недела","Понеделник","Вторник","Среда","Четврток","Петок","Сабота"],dayNamesShort:["Нед","Пон","Вто","Сре","Чет","Пет","Саб"],dayNamesMin:["Не","По","Вт","Ср","Че","Пе","Са"],weekHeader:"Сед",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("mk",{buttonText:{month:"Месец",week:"Недела",day:"Ден",list:"График"},allDayText:"Цел ден",eventLimitText:function(e){return"+повеќе "+e},noEventsMessage:"Нема настани за прикажување"})}(),function(){!function(){var e=a.defineLocale("ms",{months:"Januari_Februari_Mac_April_Mei_Jun_Julai_Ogos_September_Oktober_November_Disember".split("_"),monthsShort:"Jan_Feb_Mac_Apr_Mei_Jun_Jul_Ogs_Sep_Okt_Nov_Dis".split("_"),weekdays:"Ahad_Isnin_Selasa_Rabu_Khamis_Jumaat_Sabtu".split("_"),weekdaysShort:"Ahd_Isn_Sel_Rab_Kha_Jum_Sab".split("_"),weekdaysMin:"Ah_Is_Sl_Rb_Km_Jm_Sb".split("_"),longDateFormat:{LT:"HH.mm",LTS:"HH.mm.ss",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY [pukul] HH.mm",LLLL:"dddd, D MMMM YYYY [pukul] HH.mm"},meridiemParse:/pagi|tengahari|petang|malam/,meridiemHour:function(e,a){return 12===e&&(e=0),"pagi"===a?e:"tengahari"===a?e>=11?e:e+12:"petang"===a||"malam"===a?e+12:void 0},meridiem:function(e,a,t){return e<11?"pagi":e<15?"tengahari":e<19?"petang":"malam"},calendar:{sameDay:"[Hari ini pukul] LT",nextDay:"[Esok pukul] LT",nextWeek:"dddd [pukul] LT",lastDay:"[Kelmarin pukul] LT",lastWeek:"dddd [lepas pukul] LT",sameElse:"L"},relativeTime:{future:"dalam %s",past:"%s yang lepas",s:"beberapa saat",m:"seminit",mm:"%d minit",h:"sejam",hh:"%d jam",d:"sehari",dd:"%d hari",M:"sebulan",MM:"%d bulan",y:"setahun",yy:"%d tahun"},week:{dow:1,doy:7}});return e}(),e.fullCalendar.datepickerLocale("ms","ms",{closeText:"Tutup",prevText:"&#x3C;Sebelum",nextText:"Selepas&#x3E;",currentText:"hari ini",monthNames:["Januari","Februari","Mac","April","Mei","Jun","Julai","Ogos","September","Oktober","November","Disember"],monthNamesShort:["Jan","Feb","Mac","Apr","Mei","Jun","Jul","Ogo","Sep","Okt","Nov","Dis"],dayNames:["Ahad","Isnin","Selasa","Rabu","Khamis","Jumaat","Sabtu"],dayNamesShort:["Aha","Isn","Sel","Rab","kha","Jum","Sab"],dayNamesMin:["Ah","Is","Se","Ra","Kh","Ju","Sa"],weekHeader:"Mg",dateFormat:"dd/mm/yy",firstDay:0,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("ms",{buttonText:{month:"Bulan",week:"Minggu",day:"Hari",list:"Agenda"},allDayText:"Sepanjang hari",eventLimitText:function(e){return"masih ada "+e+" acara"},noEventsMessage:"Tiada peristiwa untuk dipaparkan"})}(),function(){!function(){var e=a.defineLocale("ms-my",{months:"Januari_Februari_Mac_April_Mei_Jun_Julai_Ogos_September_Oktober_November_Disember".split("_"),monthsShort:"Jan_Feb_Mac_Apr_Mei_Jun_Jul_Ogs_Sep_Okt_Nov_Dis".split("_"),weekdays:"Ahad_Isnin_Selasa_Rabu_Khamis_Jumaat_Sabtu".split("_"),weekdaysShort:"Ahd_Isn_Sel_Rab_Kha_Jum_Sab".split("_"),weekdaysMin:"Ah_Is_Sl_Rb_Km_Jm_Sb".split("_"),longDateFormat:{LT:"HH.mm",LTS:"HH.mm.ss",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY [pukul] HH.mm",LLLL:"dddd, D MMMM YYYY [pukul] HH.mm"},meridiemParse:/pagi|tengahari|petang|malam/,meridiemHour:function(e,a){return 12===e&&(e=0),"pagi"===a?e:"tengahari"===a?e>=11?e:e+12:"petang"===a||"malam"===a?e+12:void 0},meridiem:function(e,a,t){return e<11?"pagi":e<15?"tengahari":e<19?"petang":"malam"},calendar:{sameDay:"[Hari ini pukul] LT",nextDay:"[Esok pukul] LT",nextWeek:"dddd [pukul] LT",lastDay:"[Kelmarin pukul] LT",lastWeek:"dddd [lepas pukul] LT",sameElse:"L"},relativeTime:{future:"dalam %s",past:"%s yang lepas",s:"beberapa saat",m:"seminit",mm:"%d minit",h:"sejam",hh:"%d jam",d:"sehari",dd:"%d hari",M:"sebulan",MM:"%d bulan",y:"setahun",yy:"%d tahun"},week:{dow:1,doy:7}});return e}(),e.fullCalendar.datepickerLocale("ms-my","ms",{closeText:"Tutup",prevText:"&#x3C;Sebelum",nextText:"Selepas&#x3E;",currentText:"hari ini",monthNames:["Januari","Februari","Mac","April","Mei","Jun","Julai","Ogos","September","Oktober","November","Disember"],monthNamesShort:["Jan","Feb","Mac","Apr","Mei","Jun","Jul","Ogo","Sep","Okt","Nov","Dis"],dayNames:["Ahad","Isnin","Selasa","Rabu","Khamis","Jumaat","Sabtu"],dayNamesShort:["Aha","Isn","Sel","Rab","kha","Jum","Sab"],dayNamesMin:["Ah","Is","Se","Ra","Kh","Ju","Sa"],weekHeader:"Mg",dateFormat:"dd/mm/yy",firstDay:0,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("ms-my",{buttonText:{month:"Bulan",week:"Minggu",day:"Hari",list:"Agenda"},allDayText:"Sepanjang hari",eventLimitText:function(e){return"masih ada "+e+" acara"},noEventsMessage:"Tiada peristiwa untuk dipaparkan"})}(),function(){!function(){var e=a.defineLocale("nb",{months:"januar_februar_mars_april_mai_juni_juli_august_september_oktober_november_desember".split("_"),monthsShort:"jan._feb._mars_april_mai_juni_juli_aug._sep._okt._nov._des.".split("_"),monthsParseExact:!0,weekdays:"søndag_mandag_tirsdag_onsdag_torsdag_fredag_lørdag".split("_"),weekdaysShort:"sø._ma._ti._on._to._fr._lø.".split("_"),weekdaysMin:"sø_ma_ti_on_to_fr_lø".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD.MM.YYYY",LL:"D. MMMM YYYY",LLL:"D. MMMM YYYY [kl.] HH:mm",LLLL:"dddd D. MMMM YYYY [kl.] HH:mm"},calendar:{sameDay:"[i dag kl.] LT",nextDay:"[i morgen kl.] LT",nextWeek:"dddd [kl.] LT",lastDay:"[i går kl.] LT",lastWeek:"[forrige] dddd [kl.] LT",sameElse:"L"},relativeTime:{future:"om %s",past:"%s siden",s:"noen sekunder",m:"ett minutt",mm:"%d minutter",h:"en time",hh:"%d timer",d:"en dag",dd:"%d dager",M:"en måned",MM:"%d måneder",y:"ett år",yy:"%d år"},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("nb","nb",{closeText:"Lukk",prevText:"&#xAB;Forrige",nextText:"Neste&#xBB;",currentText:"I dag",monthNames:["januar","februar","mars","april","mai","juni","juli","august","september","oktober","november","desember"],monthNamesShort:["jan","feb","mar","apr","mai","jun","jul","aug","sep","okt","nov","des"],dayNamesShort:["søn","man","tir","ons","tor","fre","lør"],dayNames:["søndag","mandag","tirsdag","onsdag","torsdag","fredag","lørdag"],dayNamesMin:["sø","ma","ti","on","to","fr","lø"],weekHeader:"Uke",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("nb",{buttonText:{month:"Måned",week:"Uke",day:"Dag",list:"Agenda"},allDayText:"Hele dagen",eventLimitText:"til",noEventsMessage:"Ingen hendelser å vise"})}(),function(){!function(){var e="jan._feb._mrt._apr._mei_jun._jul._aug._sep._okt._nov._dec.".split("_"),t="jan_feb_mrt_apr_mei_jun_jul_aug_sep_okt_nov_dec".split("_"),n=[/^jan/i,/^feb/i,/^maart|mrt.?$/i,/^apr/i,/^mei$/i,/^jun[i.]?$/i,/^jul[i.]?$/i,/^aug/i,/^sep/i,/^okt/i,/^nov/i,/^dec/i],r=/^(januari|februari|maart|april|mei|april|ju[nl]i|augustus|september|oktober|november|december|jan\.?|feb\.?|mrt\.?|apr\.?|ju[nl]\.?|aug\.?|sep\.?|okt\.?|nov\.?|dec\.?)/i,s=a.defineLocale("nl",{months:"januari_februari_maart_april_mei_juni_juli_augustus_september_oktober_november_december".split("_"),monthsShort:function(a,n){return/-MMM-/.test(n)?t[a.month()]:e[a.month()]},monthsRegex:r,monthsShortRegex:r,monthsStrictRegex:/^(januari|februari|maart|mei|ju[nl]i|april|augustus|september|oktober|november|december)/i,monthsShortStrictRegex:/^(jan\.?|feb\.?|mrt\.?|apr\.?|mei|ju[nl]\.?|aug\.?|sep\.?|okt\.?|nov\.?|dec\.?)/i,monthsParse:n,longMonthsParse:n,shortMonthsParse:n,weekdays:"zondag_maandag_dinsdag_woensdag_donderdag_vrijdag_zaterdag".split("_"),weekdaysShort:"zo._ma._di._wo._do._vr._za.".split("_"),weekdaysMin:"Zo_Ma_Di_Wo_Do_Vr_Za".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD-MM-YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd D MMMM YYYY HH:mm"},calendar:{sameDay:"[vandaag om] LT",nextDay:"[morgen om] LT",nextWeek:"dddd [om] LT",lastDay:"[gisteren om] LT",
-lastWeek:"[afgelopen] dddd [om] LT",sameElse:"L"},relativeTime:{future:"over %s",past:"%s geleden",s:"een paar seconden",m:"één minuut",mm:"%d minuten",h:"één uur",hh:"%d uur",d:"één dag",dd:"%d dagen",M:"één maand",MM:"%d maanden",y:"één jaar",yy:"%d jaar"},ordinalParse:/\d{1,2}(ste|de)/,ordinal:function(e){return e+(1===e||8===e||e>=20?"ste":"de")},week:{dow:1,doy:4}});return s}(),e.fullCalendar.datepickerLocale("nl","nl",{closeText:"Sluiten",prevText:"←",nextText:"→",currentText:"Vandaag",monthNames:["januari","februari","maart","april","mei","juni","juli","augustus","september","oktober","november","december"],monthNamesShort:["jan","feb","mrt","apr","mei","jun","jul","aug","sep","okt","nov","dec"],dayNames:["zondag","maandag","dinsdag","woensdag","donderdag","vrijdag","zaterdag"],dayNamesShort:["zon","maa","din","woe","don","vri","zat"],dayNamesMin:["zo","ma","di","wo","do","vr","za"],weekHeader:"Wk",dateFormat:"dd-mm-yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("nl",{buttonText:{month:"Maand",week:"Week",day:"Dag",list:"Agenda"},allDayText:"Hele dag",eventLimitText:"extra",noEventsMessage:"Geen evenementen om te laten zien"})}(),function(){!function(){var e="jan._feb._mrt._apr._mei_jun._jul._aug._sep._okt._nov._dec.".split("_"),t="jan_feb_mrt_apr_mei_jun_jul_aug_sep_okt_nov_dec".split("_"),n=[/^jan/i,/^feb/i,/^maart|mrt.?$/i,/^apr/i,/^mei$/i,/^jun[i.]?$/i,/^jul[i.]?$/i,/^aug/i,/^sep/i,/^okt/i,/^nov/i,/^dec/i],r=/^(januari|februari|maart|april|mei|april|ju[nl]i|augustus|september|oktober|november|december|jan\.?|feb\.?|mrt\.?|apr\.?|ju[nl]\.?|aug\.?|sep\.?|okt\.?|nov\.?|dec\.?)/i,s=a.defineLocale("nl-be",{months:"januari_februari_maart_april_mei_juni_juli_augustus_september_oktober_november_december".split("_"),monthsShort:function(a,n){return/-MMM-/.test(n)?t[a.month()]:e[a.month()]},monthsRegex:r,monthsShortRegex:r,monthsStrictRegex:/^(januari|februari|maart|mei|ju[nl]i|april|augustus|september|oktober|november|december)/i,monthsShortStrictRegex:/^(jan\.?|feb\.?|mrt\.?|apr\.?|mei|ju[nl]\.?|aug\.?|sep\.?|okt\.?|nov\.?|dec\.?)/i,monthsParse:n,longMonthsParse:n,shortMonthsParse:n,weekdays:"zondag_maandag_dinsdag_woensdag_donderdag_vrijdag_zaterdag".split("_"),weekdaysShort:"zo._ma._di._wo._do._vr._za.".split("_"),weekdaysMin:"Zo_Ma_Di_Wo_Do_Vr_Za".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd D MMMM YYYY HH:mm"},calendar:{sameDay:"[vandaag om] LT",nextDay:"[morgen om] LT",nextWeek:"dddd [om] LT",lastDay:"[gisteren om] LT",lastWeek:"[afgelopen] dddd [om] LT",sameElse:"L"},relativeTime:{future:"over %s",past:"%s geleden",s:"een paar seconden",m:"één minuut",mm:"%d minuten",h:"één uur",hh:"%d uur",d:"één dag",dd:"%d dagen",M:"één maand",MM:"%d maanden",y:"één jaar",yy:"%d jaar"},ordinalParse:/\d{1,2}(ste|de)/,ordinal:function(e){return e+(1===e||8===e||e>=20?"ste":"de")},week:{dow:1,doy:4}});return s}(),e.fullCalendar.datepickerLocale("nl-be","nl-BE",{closeText:"Sluiten",prevText:"←",nextText:"→",currentText:"Vandaag",monthNames:["januari","februari","maart","april","mei","juni","juli","augustus","september","oktober","november","december"],monthNamesShort:["jan","feb","mrt","apr","mei","jun","jul","aug","sep","okt","nov","dec"],dayNames:["zondag","maandag","dinsdag","woensdag","donderdag","vrijdag","zaterdag"],dayNamesShort:["zon","maa","din","woe","don","vri","zat"],dayNamesMin:["zo","ma","di","wo","do","vr","za"],weekHeader:"Wk",dateFormat:"dd/mm/yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("nl-be",{buttonText:{month:"Maand",week:"Week",day:"Dag",list:"Agenda"},allDayText:"Hele dag",eventLimitText:"extra",noEventsMessage:"Geen evenementen om te laten zien"})}(),function(){!function(){var e=a.defineLocale("nn",{months:"januar_februar_mars_april_mai_juni_juli_august_september_oktober_november_desember".split("_"),monthsShort:"jan_feb_mar_apr_mai_jun_jul_aug_sep_okt_nov_des".split("_"),weekdays:"sundag_måndag_tysdag_onsdag_torsdag_fredag_laurdag".split("_"),weekdaysShort:"sun_mån_tys_ons_tor_fre_lau".split("_"),weekdaysMin:"su_må_ty_on_to_fr_lø".split("_"),longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD.MM.YYYY",LL:"D. MMMM YYYY",LLL:"D. MMMM YYYY [kl.] H:mm",LLLL:"dddd D. MMMM YYYY [kl.] HH:mm"},calendar:{sameDay:"[I dag klokka] LT",nextDay:"[I morgon klokka] LT",nextWeek:"dddd [klokka] LT",lastDay:"[I går klokka] LT",lastWeek:"[Føregåande] dddd [klokka] LT",sameElse:"L"},relativeTime:{future:"om %s",past:"%s sidan",s:"nokre sekund",m:"eit minutt",mm:"%d minutt",h:"ein time",hh:"%d timar",d:"ein dag",dd:"%d dagar",M:"ein månad",MM:"%d månader",y:"eit år",yy:"%d år"},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("nn","nn",{closeText:"Lukk",prevText:"&#xAB;Førre",nextText:"Neste&#xBB;",currentText:"I dag",monthNames:["januar","februar","mars","april","mai","juni","juli","august","september","oktober","november","desember"],monthNamesShort:["jan","feb","mar","apr","mai","jun","jul","aug","sep","okt","nov","des"],dayNamesShort:["sun","mån","tys","ons","tor","fre","lau"],dayNames:["sundag","måndag","tysdag","onsdag","torsdag","fredag","laurdag"],dayNamesMin:["su","må","ty","on","to","fr","la"],weekHeader:"Veke",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("nn",{buttonText:{month:"Månad",week:"Veke",day:"Dag",list:"Agenda"},allDayText:"Heile dagen",eventLimitText:"til",noEventsMessage:"Ingen hendelser å vise"})}(),function(){!function(){function e(e){return e%10<5&&e%10>1&&~~(e/10)%10!==1}function t(a,t,n){var r=a+" ";switch(n){case"m":return t?"minuta":"minutę";case"mm":return r+(e(a)?"minuty":"minut");case"h":return t?"godzina":"godzinę";case"hh":return r+(e(a)?"godziny":"godzin");case"MM":return r+(e(a)?"miesiące":"miesięcy");case"yy":return r+(e(a)?"lata":"lat")}}var n="styczeń_luty_marzec_kwiecień_maj_czerwiec_lipiec_sierpień_wrzesień_październik_listopad_grudzień".split("_"),r="stycznia_lutego_marca_kwietnia_maja_czerwca_lipca_sierpnia_września_października_listopada_grudnia".split("_"),s=a.defineLocale("pl",{months:function(e,a){return""===a?"("+r[e.month()]+"|"+n[e.month()]+")":/D MMMM/.test(a)?r[e.month()]:n[e.month()]},monthsShort:"sty_lut_mar_kwi_maj_cze_lip_sie_wrz_paź_lis_gru".split("_"),weekdays:"niedziela_poniedziałek_wtorek_środa_czwartek_piątek_sobota".split("_"),weekdaysShort:"ndz_pon_wt_śr_czw_pt_sob".split("_"),weekdaysMin:"Nd_Pn_Wt_Śr_Cz_Pt_So".split("_"),longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD.MM.YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd, D MMMM YYYY HH:mm"},calendar:{sameDay:"[Dziś o] LT",nextDay:"[Jutro o] LT",nextWeek:"[W] dddd [o] LT",lastDay:"[Wczoraj o] LT",lastWeek:function(){switch(this.day()){case 0:return"[W zeszłą niedzielę o] LT";case 3:return"[W zeszłą środę o] LT";case 6:return"[W zeszłą sobotę o] LT";default:return"[W zeszły] dddd [o] LT"}},sameElse:"L"},relativeTime:{future:"za %s",past:"%s temu",s:"kilka sekund",m:t,mm:t,h:t,hh:t,d:"1 dzień",dd:"%d dni",M:"miesiąc",MM:t,y:"rok",yy:t},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:4}});return s}(),e.fullCalendar.datepickerLocale("pl","pl",{closeText:"Zamknij",prevText:"&#x3C;Poprzedni",nextText:"Następny&#x3E;",currentText:"Dziś",monthNames:["Styczeń","Luty","Marzec","Kwiecień","Maj","Czerwiec","Lipiec","Sierpień","Wrzesień","Październik","Listopad","Grudzień"],monthNamesShort:["Sty","Lu","Mar","Kw","Maj","Cze","Lip","Sie","Wrz","Pa","Lis","Gru"],dayNames:["Niedziela","Poniedziałek","Wtorek","Środa","Czwartek","Piątek","Sobota"],dayNamesShort:["Nie","Pn","Wt","Śr","Czw","Pt","So"],dayNamesMin:["N","Pn","Wt","Śr","Cz","Pt","So"],weekHeader:"Tydz",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("pl",{buttonText:{month:"Miesiąc",week:"Tydzień",day:"Dzień",list:"Plan dnia"},allDayText:"Cały dzień",eventLimitText:"więcej",noEventsMessage:"Brak wydarzeń do wyświetlenia"})}(),function(){!function(){var e=a.defineLocale("pt",{months:"Janeiro_Fevereiro_Março_Abril_Maio_Junho_Julho_Agosto_Setembro_Outubro_Novembro_Dezembro".split("_"),monthsShort:"Jan_Fev_Mar_Abr_Mai_Jun_Jul_Ago_Set_Out_Nov_Dez".split("_"),weekdays:"Domingo_Segunda-Feira_Terça-Feira_Quarta-Feira_Quinta-Feira_Sexta-Feira_Sábado".split("_"),weekdaysShort:"Dom_Seg_Ter_Qua_Qui_Sex_Sáb".split("_"),weekdaysMin:"Dom_2ª_3ª_4ª_5ª_6ª_Sáb".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D [de] MMMM [de] YYYY",LLL:"D [de] MMMM [de] YYYY HH:mm",LLLL:"dddd, D [de] MMMM [de] YYYY HH:mm"},calendar:{sameDay:"[Hoje às] LT",nextDay:"[Amanhã às] LT",nextWeek:"dddd [às] LT",lastDay:"[Ontem às] LT",lastWeek:function(){return 0===this.day()||6===this.day()?"[Último] dddd [às] LT":"[Última] dddd [às] LT"},sameElse:"L"},relativeTime:{future:"em %s",past:"há %s",s:"segundos",m:"um minuto",mm:"%d minutos",h:"uma hora",hh:"%d horas",d:"um dia",dd:"%d dias",M:"um mês",MM:"%d meses",y:"um ano",yy:"%d anos"},ordinalParse:/\d{1,2}º/,ordinal:"%dº",week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("pt","pt",{closeText:"Fechar",prevText:"Anterior",nextText:"Seguinte",currentText:"Hoje",monthNames:["Janeiro","Fevereiro","Março","Abril","Maio","Junho","Julho","Agosto","Setembro","Outubro","Novembro","Dezembro"],monthNamesShort:["Jan","Fev","Mar","Abr","Mai","Jun","Jul","Ago","Set","Out","Nov","Dez"],dayNames:["Domingo","Segunda-feira","Terça-feira","Quarta-feira","Quinta-feira","Sexta-feira","Sábado"],dayNamesShort:["Dom","Seg","Ter","Qua","Qui","Sex","Sáb"],dayNamesMin:["Dom","Seg","Ter","Qua","Qui","Sex","Sáb"],weekHeader:"Sem",dateFormat:"dd/mm/yy",firstDay:0,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("pt",{buttonText:{month:"Mês",week:"Semana",day:"Dia",list:"Agenda"},allDayText:"Todo o dia",eventLimitText:"mais",noEventsMessage:"Não há eventos para mostrar"})}(),function(){!function(){var e=a.defineLocale("pt-br",{months:"Janeiro_Fevereiro_Março_Abril_Maio_Junho_Julho_Agosto_Setembro_Outubro_Novembro_Dezembro".split("_"),monthsShort:"Jan_Fev_Mar_Abr_Mai_Jun_Jul_Ago_Set_Out_Nov_Dez".split("_"),weekdays:"Domingo_Segunda-feira_Terça-feira_Quarta-feira_Quinta-feira_Sexta-feira_Sábado".split("_"),weekdaysShort:"Dom_Seg_Ter_Qua_Qui_Sex_Sáb".split("_"),weekdaysMin:"Dom_2ª_3ª_4ª_5ª_6ª_Sáb".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D [de] MMMM [de] YYYY",LLL:"D [de] MMMM [de] YYYY [às] HH:mm",LLLL:"dddd, D [de] MMMM [de] YYYY [às] HH:mm"},calendar:{sameDay:"[Hoje às] LT",nextDay:"[Amanhã às] LT",nextWeek:"dddd [às] LT",lastDay:"[Ontem às] LT",lastWeek:function(){return 0===this.day()||6===this.day()?"[Último] dddd [às] LT":"[Última] dddd [às] LT"},sameElse:"L"},relativeTime:{future:"em %s",past:"%s atrás",s:"poucos segundos",m:"um minuto",mm:"%d minutos",h:"uma hora",hh:"%d horas",d:"um dia",dd:"%d dias",M:"um mês",MM:"%d meses",y:"um ano",yy:"%d anos"},ordinalParse:/\d{1,2}º/,ordinal:"%dº"});return e}(),e.fullCalendar.datepickerLocale("pt-br","pt-BR",{closeText:"Fechar",prevText:"&#x3C;Anterior",nextText:"Próximo&#x3E;",currentText:"Hoje",monthNames:["Janeiro","Fevereiro","Março","Abril","Maio","Junho","Julho","Agosto","Setembro","Outubro","Novembro","Dezembro"],monthNamesShort:["Jan","Fev","Mar","Abr","Mai","Jun","Jul","Ago","Set","Out","Nov","Dez"],dayNames:["Domingo","Segunda-feira","Terça-feira","Quarta-feira","Quinta-feira","Sexta-feira","Sábado"],dayNamesShort:["Dom","Seg","Ter","Qua","Qui","Sex","Sáb"],dayNamesMin:["Dom","Seg","Ter","Qua","Qui","Sex","Sáb"],weekHeader:"Sm",dateFormat:"dd/mm/yy",firstDay:0,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("pt-br",{buttonText:{month:"Mês",week:"Semana",day:"Dia",list:"Compromissos"},allDayText:"dia inteiro",eventLimitText:function(e){return"mais +"+e},noEventsMessage:"Não há eventos para mostrar"})}(),function(){!function(){function e(e,a,t){var n={mm:"minute",hh:"ore",dd:"zile",MM:"luni",yy:"ani"},r=" ";return(e%100>=20||e>=100&&e%100===0)&&(r=" de "),e+r+n[t]}var t=a.defineLocale("ro",{months:"ianuarie_februarie_martie_aprilie_mai_iunie_iulie_august_septembrie_octombrie_noiembrie_decembrie".split("_"),monthsShort:"ian._febr._mart._apr._mai_iun._iul._aug._sept._oct._nov._dec.".split("_"),monthsParseExact:!0,weekdays:"duminică_luni_marți_miercuri_joi_vineri_sâmbătă".split("_"),weekdaysShort:"Dum_Lun_Mar_Mie_Joi_Vin_Sâm".split("_"),weekdaysMin:"Du_Lu_Ma_Mi_Jo_Vi_Sâ".split("_"),longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"DD.MM.YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY H:mm",LLLL:"dddd, D MMMM YYYY H:mm"},calendar:{sameDay:"[azi la] LT",nextDay:"[mâine la] LT",nextWeek:"dddd [la] LT",lastDay:"[ieri la] LT",lastWeek:"[fosta] dddd [la] LT",sameElse:"L"},relativeTime:{future:"peste %s",past:"%s în urmă",s:"câteva secunde",m:"un minut",mm:e,h:"o oră",hh:e,d:"o zi",dd:e,M:"o lună",MM:e,y:"un an",yy:e},week:{dow:1,doy:7}});return t}(),e.fullCalendar.datepickerLocale("ro","ro",{closeText:"Închide",prevText:"&#xAB; Luna precedentă",nextText:"Luna următoare &#xBB;",currentText:"Azi",monthNames:["Ianuarie","Februarie","Martie","Aprilie","Mai","Iunie","Iulie","August","Septembrie","Octombrie","Noiembrie","Decembrie"],monthNamesShort:["Ian","Feb","Mar","Apr","Mai","Iun","Iul","Aug","Sep","Oct","Nov","Dec"],dayNames:["Duminică","Luni","Marţi","Miercuri","Joi","Vineri","Sâmbătă"],dayNamesShort:["Dum","Lun","Mar","Mie","Joi","Vin","Sâm"],dayNamesMin:["Du","Lu","Ma","Mi","Jo","Vi","Sâ"],weekHeader:"Săpt",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("ro",{buttonText:{prev:"precedentă",next:"următoare",month:"Lună",week:"Săptămână",day:"Zi",list:"Agendă"},allDayText:"Toată ziua",eventLimitText:function(e){return"+alte "+e},noEventsMessage:"Nu există evenimente de afișat"})}(),function(){!function(){function e(e,a){var t=e.split("_");return a%10===1&&a%100!==11?t[0]:a%10>=2&&a%10<=4&&(a%100<10||a%100>=20)?t[1]:t[2]}function t(a,t,n){var r={mm:t?"минута_минуты_минут":"минуту_минуты_минут",hh:"час_часа_часов",dd:"день_дня_дней",MM:"месяц_месяца_месяцев",yy:"год_года_лет"};return"m"===n?t?"минута":"минуту":a+" "+e(r[n],+a)}var n=[/^янв/i,/^фев/i,/^мар/i,/^апр/i,/^ма[йя]/i,/^июн/i,/^июл/i,/^авг/i,/^сен/i,/^окт/i,/^ноя/i,/^дек/i],r=a.defineLocale("ru",{months:{format:"января_февраля_марта_апреля_мая_июня_июля_августа_сентября_октября_ноября_декабря".split("_"),standalone:"январь_февраль_март_апрель_май_июнь_июль_август_сентябрь_октябрь_ноябрь_декабрь".split("_")},monthsShort:{format:"янв._февр._мар._апр._мая_июня_июля_авг._сент._окт._нояб._дек.".split("_"),standalone:"янв._февр._март_апр._май_июнь_июль_авг._сент._окт._нояб._дек.".split("_")},weekdays:{standalone:"воскресенье_понедельник_вторник_среда_четверг_пятница_суббота".split("_"),format:"воскресенье_понедельник_вторник_среду_четверг_пятницу_субботу".split("_"),isFormat:/\[ ?[Вв] ?(?:прошлую|следующую|эту)? ?\] ?dddd/},weekdaysShort:"вс_пн_вт_ср_чт_пт_сб".split("_"),weekdaysMin:"вс_пн_вт_ср_чт_пт_сб".split("_"),monthsParse:n,longMonthsParse:n,shortMonthsParse:n,monthsRegex:/^(январ[ья]|янв\.?|феврал[ья]|февр?\.?|марта?|мар\.?|апрел[ья]|апр\.?|ма[йя]|июн[ья]|июн\.?|июл[ья]|июл\.?|августа?|авг\.?|сентябр[ья]|сент?\.?|октябр[ья]|окт\.?|ноябр[ья]|нояб?\.?|декабр[ья]|дек\.?)/i,monthsShortRegex:/^(январ[ья]|янв\.?|феврал[ья]|февр?\.?|марта?|мар\.?|апрел[ья]|апр\.?|ма[йя]|июн[ья]|июн\.?|июл[ья]|июл\.?|августа?|авг\.?|сентябр[ья]|сент?\.?|октябр[ья]|окт\.?|ноябр[ья]|нояб?\.?|декабр[ья]|дек\.?)/i,monthsStrictRegex:/^(январ[яь]|феврал[яь]|марта?|апрел[яь]|ма[яй]|июн[яь]|июл[яь]|августа?|сентябр[яь]|октябр[яь]|ноябр[яь]|декабр[яь])/i,monthsShortStrictRegex:/^(янв\.|февр?\.|мар[т.]|апр\.|ма[яй]|июн[ья.]|июл[ья.]|авг\.|сент?\.|окт\.|нояб?\.|дек\.)/i,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD.MM.YYYY",LL:"D MMMM YYYY г.",LLL:"D MMMM YYYY г., HH:mm",LLLL:"dddd, D MMMM YYYY г., HH:mm"},calendar:{sameDay:"[Сегодня в] LT",nextDay:"[Завтра в] LT",lastDay:"[Вчера в] LT",nextWeek:function(e){if(e.week()===this.week())return 2===this.day()?"[Во] dddd [в] LT":"[В] dddd [в] LT";switch(this.day()){case 0:return"[В следующее] dddd [в] LT";case 1:case 2:case 4:return"[В следующий] dddd [в] LT";case 3:case 5:case 6:return"[В следующую] dddd [в] LT"}},lastWeek:function(e){if(e.week()===this.week())return 2===this.day()?"[Во] dddd [в] LT":"[В] dddd [в] LT";switch(this.day()){case 0:return"[В прошлое] dddd [в] LT";case 1:case 2:case 4:return"[В прошлый] dddd [в] LT";case 3:case 5:case 6:return"[В прошлую] dddd [в] LT"}},sameElse:"L"},relativeTime:{future:"через %s",past:"%s назад",s:"несколько секунд",m:t,mm:t,h:"час",hh:t,d:"день",dd:t,M:"месяц",MM:t,y:"год",yy:t},meridiemParse:/ночи|утра|дня|вечера/i,isPM:function(e){return/^(дня|вечера)$/.test(e)},meridiem:function(e,a,t){return e<4?"ночи":e<12?"утра":e<17?"дня":"вечера"},ordinalParse:/\d{1,2}-(й|го|я)/,ordinal:function(e,a){switch(a){case"M":case"d":case"DDD":return e+"-й";case"D":return e+"-го";case"w":case"W":return e+"-я";default:return e}},week:{dow:1,doy:7}});return r}(),e.fullCalendar.datepickerLocale("ru","ru",{closeText:"Закрыть",prevText:"&#x3C;Пред",nextText:"След&#x3E;",currentText:"Сегодня",monthNames:["Январь","Февраль","Март","Апрель","Май","Июнь","Июль","Август","Сентябрь","Октябрь","Ноябрь","Декабрь"],monthNamesShort:["Янв","Фев","Мар","Апр","Май","Июн","Июл","Авг","Сен","Окт","Ноя","Дек"],dayNames:["воскресенье","понедельник","вторник","среда","четверг","пятница","суббота"],dayNamesShort:["вск","пнд","втр","срд","чтв","птн","сбт"],dayNamesMin:["Вс","Пн","Вт","Ср","Чт","Пт","Сб"],weekHeader:"Нед",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("ru",{buttonText:{month:"Месяц",week:"Неделя",day:"День",list:"Повестка дня"},allDayText:"Весь день",eventLimitText:function(e){return"+ ещё "+e},noEventsMessage:"Нет событий для отображения"})}(),function(){!function(){function e(e){return e>1&&e<5}function t(a,t,n,r){var s=a+" ";switch(n){case"s":return t||r?"pár sekúnd":"pár sekundami";case"m":return t?"minúta":r?"minútu":"minútou";case"mm":return t||r?s+(e(a)?"minúty":"minút"):s+"minútami";case"h":return t?"hodina":r?"hodinu":"hodinou";case"hh":return t||r?s+(e(a)?"hodiny":"hodín"):s+"hodinami";case"d":return t||r?"deň":"dňom";case"dd":return t||r?s+(e(a)?"dni":"dní"):s+"dňami";case"M":return t||r?"mesiac":"mesiacom";case"MM":return t||r?s+(e(a)?"mesiace":"mesiacov"):s+"mesiacmi";case"y":return t||r?"rok":"rokom";case"yy":return t||r?s+(e(a)?"roky":"rokov"):s+"rokmi"}}var n="január_február_marec_apríl_máj_jún_júl_august_september_október_november_december".split("_"),r="jan_feb_mar_apr_máj_jún_júl_aug_sep_okt_nov_dec".split("_"),s=a.defineLocale("sk",{months:n,monthsShort:r,weekdays:"nedeľa_pondelok_utorok_streda_štvrtok_piatok_sobota".split("_"),weekdaysShort:"ne_po_ut_st_št_pi_so".split("_"),weekdaysMin:"ne_po_ut_st_št_pi_so".split("_"),longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"DD.MM.YYYY",LL:"D. MMMM YYYY",LLL:"D. MMMM YYYY H:mm",LLLL:"dddd D. MMMM YYYY H:mm"},calendar:{sameDay:"[dnes o] LT",nextDay:"[zajtra o] LT",nextWeek:function(){switch(this.day()){case 0:return"[v nedeľu o] LT";case 1:case 2:return"[v] dddd [o] LT";case 3:return"[v stredu o] LT";case 4:return"[vo štvrtok o] LT";case 5:return"[v piatok o] LT";case 6:return"[v sobotu o] LT"}},lastDay:"[včera o] LT",lastWeek:function(){switch(this.day()){case 0:return"[minulú nedeľu o] LT";case 1:case 2:return"[minulý] dddd [o] LT";case 3:return"[minulú stredu o] LT";case 4:case 5:return"[minulý] dddd [o] LT";case 6:return"[minulú sobotu o] LT"}},sameElse:"L"},relativeTime:{future:"za %s",past:"pred %s",s:t,m:t,mm:t,h:t,hh:t,d:t,dd:t,M:t,MM:t,y:t,yy:t},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:4}});return s}(),e.fullCalendar.datepickerLocale("sk","sk",{closeText:"Zavrieť",prevText:"&#x3C;Predchádzajúci",nextText:"Nasledujúci&#x3E;",currentText:"Dnes",monthNames:["január","február","marec","apríl","máj","jún","júl","august","september","október","november","december"],monthNamesShort:["Jan","Feb","Mar","Apr","Máj","Jún","Júl","Aug","Sep","Okt","Nov","Dec"],dayNames:["nedeľa","pondelok","utorok","streda","štvrtok","piatok","sobota"],dayNamesShort:["Ned","Pon","Uto","Str","Štv","Pia","Sob"],dayNamesMin:["Ne","Po","Ut","St","Št","Pia","So"],weekHeader:"Ty",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("sk",{buttonText:{month:"Mesiac",week:"Týždeň",day:"Deň",list:"Rozvrh"},allDayText:"Celý deň",eventLimitText:function(e){return"+ďalšie: "+e},noEventsMessage:"Žiadne akcie na zobrazenie"})}(),function(){!function(){function e(e,a,t,n){var r=e+" ";switch(t){case"s":return a||n?"nekaj sekund":"nekaj sekundami";case"m":return a?"ena minuta":"eno minuto";case"mm":return r+=1===e?a?"minuta":"minuto":2===e?a||n?"minuti":"minutama":e<5?a||n?"minute":"minutami":a||n?"minut":"minutami";case"h":return a?"ena ura":"eno uro";case"hh":return r+=1===e?a?"ura":"uro":2===e?a||n?"uri":"urama":e<5?a||n?"ure":"urami":a||n?"ur":"urami";case"d":return a||n?"en dan":"enim dnem";case"dd":return r+=1===e?a||n?"dan":"dnem":2===e?a||n?"dni":"dnevoma":a||n?"dni":"dnevi";case"M":return a||n?"en mesec":"enim mesecem";case"MM":return r+=1===e?a||n?"mesec":"mesecem":2===e?a||n?"meseca":"mesecema":e<5?a||n?"mesece":"meseci":a||n?"mesecev":"meseci";case"y":return a||n?"eno leto":"enim letom";case"yy":return r+=1===e?a||n?"leto":"letom":2===e?a||n?"leti":"letoma":e<5?a||n?"leta":"leti":a||n?"let":"leti"}}var t=a.defineLocale("sl",{months:"januar_februar_marec_april_maj_junij_julij_avgust_september_oktober_november_december".split("_"),monthsShort:"jan._feb._mar._apr._maj._jun._jul._avg._sep._okt._nov._dec.".split("_"),monthsParseExact:!0,weekdays:"nedelja_ponedeljek_torek_sreda_četrtek_petek_sobota".split("_"),weekdaysShort:"ned._pon._tor._sre._čet._pet._sob.".split("_"),weekdaysMin:"ne_po_to_sr_če_pe_so".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"DD.MM.YYYY",LL:"D. MMMM YYYY",LLL:"D. MMMM YYYY H:mm",LLLL:"dddd, D. MMMM YYYY H:mm"},calendar:{sameDay:"[danes ob] LT",nextDay:"[jutri ob] LT",nextWeek:function(){switch(this.day()){case 0:return"[v] [nedeljo] [ob] LT";case 3:return"[v] [sredo] [ob] LT";case 6:return"[v] [soboto] [ob] LT";case 1:case 2:case 4:case 5:return"[v] dddd [ob] LT"}},lastDay:"[včeraj ob] LT",lastWeek:function(){switch(this.day()){case 0:return"[prejšnjo] [nedeljo] [ob] LT";case 3:return"[prejšnjo] [sredo] [ob] LT";case 6:return"[prejšnjo] [soboto] [ob] LT";case 1:case 2:case 4:case 5:return"[prejšnji] dddd [ob] LT"}},sameElse:"L"},relativeTime:{future:"čez %s",past:"pred %s",s:e,m:e,mm:e,h:e,hh:e,d:e,dd:e,M:e,MM:e,y:e,yy:e},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:7}});return t}(),e.fullCalendar.datepickerLocale("sl","sl",{closeText:"Zapri",prevText:"&#x3C;Prejšnji",nextText:"Naslednji&#x3E;",currentText:"Trenutni",monthNames:["Januar","Februar","Marec","April","Maj","Junij","Julij","Avgust","September","Oktober","November","December"],monthNamesShort:["Jan","Feb","Mar","Apr","Maj","Jun","Jul","Avg","Sep","Okt","Nov","Dec"],dayNames:["Nedelja","Ponedeljek","Torek","Sreda","Četrtek","Petek","Sobota"],dayNamesShort:["Ned","Pon","Tor","Sre","Čet","Pet","Sob"],dayNamesMin:["Ne","Po","To","Sr","Če","Pe","So"],weekHeader:"Teden",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("sl",{buttonText:{month:"Mesec",week:"Teden",day:"Dan",list:"Dnevni red"},allDayText:"Ves dan",eventLimitText:"več",noEventsMessage:"Ni dogodkov za prikaz"})}(),function(){!function(){var e={words:{m:["jedan minut","jedne minute"],mm:["minut","minute","minuta"],h:["jedan sat","jednog sata"],hh:["sat","sata","sati"],dd:["dan","dana","dana"],MM:["mesec","meseca","meseci"],yy:["godina","godine","godina"]},correctGrammaticalCase:function(e,a){return 1===e?a[0]:e>=2&&e<=4?a[1]:a[2]},translate:function(a,t,n){var r=e.words[n];return 1===n.length?t?r[0]:r[1]:a+" "+e.correctGrammaticalCase(a,r)}},t=a.defineLocale("sr",{months:"januar_februar_mart_april_maj_jun_jul_avgust_septembar_oktobar_novembar_decembar".split("_"),monthsShort:"jan._feb._mar._apr._maj_jun_jul_avg._sep._okt._nov._dec.".split("_"),monthsParseExact:!0,weekdays:"nedelja_ponedeljak_utorak_sreda_četvrtak_petak_subota".split("_"),weekdaysShort:"ned._pon._uto._sre._čet._pet._sub.".split("_"),weekdaysMin:"ne_po_ut_sr_če_pe_su".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"DD.MM.YYYY",LL:"D. MMMM YYYY",LLL:"D. MMMM YYYY H:mm",LLLL:"dddd, D. MMMM YYYY H:mm"},calendar:{sameDay:"[danas u] LT",nextDay:"[sutra u] LT",nextWeek:function(){switch(this.day()){case 0:return"[u] [nedelju] [u] LT";case 3:return"[u] [sredu] [u] LT";case 6:return"[u] [subotu] [u] LT";case 1:case 2:case 4:case 5:return"[u] dddd [u] LT"}},lastDay:"[juče u] LT",lastWeek:function(){var e=["[prošle] [nedelje] [u] LT","[prošlog] [ponedeljka] [u] LT","[prošlog] [utorka] [u] LT","[prošle] [srede] [u] LT","[prošlog] [četvrtka] [u] LT","[prošlog] [petka] [u] LT","[prošle] [subote] [u] LT"];return e[this.day()]},sameElse:"L"},relativeTime:{future:"za %s",past:"pre %s",s:"nekoliko sekundi",m:e.translate,mm:e.translate,h:e.translate,hh:e.translate,d:"dan",dd:e.translate,M:"mesec",MM:e.translate,y:"godinu",yy:e.translate},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:7}});return t}(),e.fullCalendar.datepickerLocale("sr","sr",{closeText:"Затвори",prevText:"&#x3C;",nextText:"&#x3E;",currentText:"Данас",monthNames:["Јануар","Фебруар","Март","Април","Мај","Јун","Јул","Август","Септембар","Октобар","Новембар","Децембар"],monthNamesShort:["Јан","Феб","Мар","Апр","Мај","Јун","Јул","Авг","Сеп","Окт","Нов","Дец"],dayNames:["Недеља","Понедељак","Уторак","Среда","Четвртак","Петак","Субота"],dayNamesShort:["Нед","Пон","Уто","Сре","Чет","Пет","Суб"],dayNamesMin:["Не","По","Ут","Ср","Че","Пе","Су"],weekHeader:"Сед",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("sr",{buttonText:{month:"Месец",week:"Недеља",day:"Дан",list:"Планер"},allDayText:"Цео дан",eventLimitText:function(e){return"+ још "+e},noEventsMessage:"Нема догађаја за приказ"})}(),function(){!function(){var e={words:{m:["један минут","једне минуте"],mm:["минут","минуте","минута"],h:["један сат","једног сата"],hh:["сат","сата","сати"],dd:["дан","дана","дана"],MM:["месец","месеца","месеци"],yy:["година","године","година"]},correctGrammaticalCase:function(e,a){return 1===e?a[0]:e>=2&&e<=4?a[1]:a[2]},translate:function(a,t,n){var r=e.words[n];return 1===n.length?t?r[0]:r[1]:a+" "+e.correctGrammaticalCase(a,r)}},t=a.defineLocale("sr-cyrl",{months:"јануар_фебруар_март_април_мај_јун_јул_август_септембар_октобар_новембар_децембар".split("_"),monthsShort:"јан._феб._мар._апр._мај_јун_јул_авг._сеп._окт._нов._дец.".split("_"),monthsParseExact:!0,weekdays:"недеља_понедељак_уторак_среда_четвртак_петак_субота".split("_"),weekdaysShort:"нед._пон._уто._сре._чет._пет._суб.".split("_"),weekdaysMin:"не_по_ут_ср_че_пе_су".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"DD.MM.YYYY",LL:"D. MMMM YYYY",LLL:"D. MMMM YYYY H:mm",LLLL:"dddd, D. MMMM YYYY H:mm"},calendar:{sameDay:"[данас у] LT",nextDay:"[сутра у] LT",nextWeek:function(){switch(this.day()){case 0:return"[у] [недељу] [у] LT";case 3:return"[у] [среду] [у] LT";case 6:return"[у] [суботу] [у] LT";case 1:case 2:case 4:case 5:return"[у] dddd [у] LT"}},lastDay:"[јуче у] LT",lastWeek:function(){var e=["[прошле] [недеље] [у] LT","[прошлог] [понедељка] [у] LT","[прошлог] [уторка] [у] LT","[прошле] [среде] [у] LT","[прошлог] [четвртка] [у] LT","[прошлог] [петка] [у] LT","[прошле] [суботе] [у] LT"];return e[this.day()]},sameElse:"L"},relativeTime:{future:"за %s",past:"пре %s",s:"неколико секунди",m:e.translate,mm:e.translate,h:e.translate,hh:e.translate,d:"дан",dd:e.translate,M:"месец",MM:e.translate,y:"годину",yy:e.translate},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:7}});return t}(),e.fullCalendar.datepickerLocale("sr-cyrl","sr",{closeText:"Затвори",prevText:"&#x3C;",nextText:"&#x3E;",currentText:"Данас",monthNames:["Јануар","Фебруар","Март","Април","Мај","Јун","Јул","Август","Септембар","Октобар","Новембар","Децембар"],monthNamesShort:["Јан","Феб","Мар","Апр","Мај","Јун","Јул","Авг","Сеп","Окт","Нов","Дец"],dayNames:["Недеља","Понедељак","Уторак","Среда","Четвртак","Петак","Субота"],dayNamesShort:["Нед","Пон","Уто","Сре","Чет","Пет","Суб"],dayNamesMin:["Не","По","Ут","Ср","Че","Пе","Су"],weekHeader:"Сед",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("sr-cyrl",{buttonText:{month:"Месец",week:"Недеља",day:"Дан",list:"Планер"},allDayText:"Цео дан",eventLimitText:function(e){return"+ још "+e},noEventsMessage:"Нема догађаја за приказ"})}(),function(){!function(){var e=a.defineLocale("sv",{months:"januari_februari_mars_april_maj_juni_juli_augusti_september_oktober_november_december".split("_"),monthsShort:"jan_feb_mar_apr_maj_jun_jul_aug_sep_okt_nov_dec".split("_"),weekdays:"söndag_måndag_tisdag_onsdag_torsdag_fredag_lördag".split("_"),weekdaysShort:"sön_mån_tis_ons_tor_fre_lör".split("_"),weekdaysMin:"sö_må_ti_on_to_fr_lö".split("_"),longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"YYYY-MM-DD",LL:"D MMMM YYYY",LLL:"D MMMM YYYY [kl.] HH:mm",LLLL:"dddd D MMMM YYYY [kl.] HH:mm",lll:"D MMM YYYY HH:mm",llll:"ddd D MMM YYYY HH:mm"},calendar:{sameDay:"[Idag] LT",nextDay:"[Imorgon] LT",lastDay:"[Igår] LT",nextWeek:"[På] dddd LT",lastWeek:"[I] dddd[s] LT",sameElse:"L"},relativeTime:{future:"om %s",past:"för %s sedan",s:"några sekunder",m:"en minut",mm:"%d minuter",h:"en timme",hh:"%d timmar",d:"en dag",dd:"%d dagar",M:"en månad",MM:"%d månader",y:"ett år",yy:"%d år"},ordinalParse:/\d{1,2}(e|a)/,ordinal:function(e){var a=e%10,t=1===~~(e%100/10)?"e":1===a?"a":2===a?"a":"e";return e+t},week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("sv","sv",{closeText:"Stäng",prevText:"&#xAB;Förra",nextText:"Nästa&#xBB;",currentText:"Idag",monthNames:["Januari","Februari","Mars","April","Maj","Juni","Juli","Augusti","September","Oktober","November","December"],monthNamesShort:["Jan","Feb","Mar","Apr","Maj","Jun","Jul","Aug","Sep","Okt","Nov","Dec"],dayNamesShort:["Sön","Mån","Tis","Ons","Tor","Fre","Lör"],dayNames:["Söndag","Måndag","Tisdag","Onsdag","Torsdag","Fredag","Lördag"],dayNamesMin:["Sö","Må","Ti","On","To","Fr","Lö"],weekHeader:"Ve",dateFormat:"yy-mm-dd",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("sv",{buttonText:{month:"Månad",week:"Vecka",day:"Dag",list:"Program"},allDayText:"Heldag",eventLimitText:"till",noEventsMessage:"Inga händelser att visa"})}(),function(){!function(){var e=a.defineLocale("th",{months:"มกราคม_กุมภาพันธ์_มีนาคม_เมษายน_พฤษภาคม_มิถุนายน_กรกฎาคม_สิงหาคม_กันยายน_ตุลาคม_พฤศจิกายน_ธันวาคม".split("_"),monthsShort:"ม.ค._ก.พ._มี.ค._เม.ย._พ.ค._มิ.ย._ก.ค._ส.ค._ก.ย._ต.ค._พ.ย._ธ.ค.".split("_"),monthsParseExact:!0,weekdays:"อาทิตย์_จันทร์_อังคาร_พุธ_พฤหัสบดี_ศุกร์_เสาร์".split("_"),weekdaysShort:"อาทิตย์_จันทร์_อังคาร_พุธ_พฤหัส_ศุกร์_เสาร์".split("_"),weekdaysMin:"อา._จ._อ._พ._พฤ._ศ._ส.".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"YYYY/MM/DD",LL:"D MMMM YYYY",LLL:"D MMMM YYYY เวลา H:mm",LLLL:"วันddddที่ D MMMM YYYY เวลา H:mm"},meridiemParse:/ก่อนเที่ยง|หลังเที่ยง/,isPM:function(e){return"หลังเที่ยง"===e},meridiem:function(e,a,t){return e<12?"ก่อนเที่ยง":"หลังเที่ยง"},calendar:{sameDay:"[วันนี้ เวลา] LT",nextDay:"[พรุ่งนี้ เวลา] LT",nextWeek:"dddd[หน้า เวลา] LT",lastDay:"[เมื่อวานนี้ เวลา] LT",lastWeek:"[วัน]dddd[ที่แล้ว เวลา] LT",sameElse:"L"},relativeTime:{future:"อีก %s",past:"%sที่แล้ว",s:"ไม่กี่วินาที",m:"1 นาที",mm:"%d นาที",h:"1 ชั่วโมง",hh:"%d ชั่วโมง",d:"1 วัน",dd:"%d วัน",M:"1 เดือน",MM:"%d เดือน",y:"1 ปี",yy:"%d ปี"
-}});return e}(),e.fullCalendar.datepickerLocale("th","th",{closeText:"ปิด",prevText:"&#xAB;&#xA0;ย้อน",nextText:"ถัดไป&#xA0;&#xBB;",currentText:"วันนี้",monthNames:["มกราคม","กุมภาพันธ์","มีนาคม","เมษายน","พฤษภาคม","มิถุนายน","กรกฎาคม","สิงหาคม","กันยายน","ตุลาคม","พฤศจิกายน","ธันวาคม"],monthNamesShort:["ม.ค.","ก.พ.","มี.ค.","เม.ย.","พ.ค.","มิ.ย.","ก.ค.","ส.ค.","ก.ย.","ต.ค.","พ.ย.","ธ.ค."],dayNames:["อาทิตย์","จันทร์","อังคาร","พุธ","พฤหัสบดี","ศุกร์","เสาร์"],dayNamesShort:["อา.","จ.","อ.","พ.","พฤ.","ศ.","ส."],dayNamesMin:["อา.","จ.","อ.","พ.","พฤ.","ศ.","ส."],weekHeader:"Wk",dateFormat:"dd/mm/yy",firstDay:0,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("th",{buttonText:{month:"เดือน",week:"สัปดาห์",day:"วัน",list:"แผนงาน"},allDayText:"ตลอดวัน",eventLimitText:"เพิ่มเติม",noEventsMessage:"ไม่มีกิจกรรมที่จะแสดง"})}(),function(){!function(){var e={1:"'inci",5:"'inci",8:"'inci",70:"'inci",80:"'inci",2:"'nci",7:"'nci",20:"'nci",50:"'nci",3:"'üncü",4:"'üncü",100:"'üncü",6:"'ncı",9:"'uncu",10:"'uncu",30:"'uncu",60:"'ıncı",90:"'ıncı"},t=a.defineLocale("tr",{months:"Ocak_Şubat_Mart_Nisan_Mayıs_Haziran_Temmuz_Ağustos_Eylül_Ekim_Kasım_Aralık".split("_"),monthsShort:"Oca_Şub_Mar_Nis_May_Haz_Tem_Ağu_Eyl_Eki_Kas_Ara".split("_"),weekdays:"Pazar_Pazartesi_Salı_Çarşamba_Perşembe_Cuma_Cumartesi".split("_"),weekdaysShort:"Paz_Pts_Sal_Çar_Per_Cum_Cts".split("_"),weekdaysMin:"Pz_Pt_Sa_Ça_Pe_Cu_Ct".split("_"),longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD.MM.YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd, D MMMM YYYY HH:mm"},calendar:{sameDay:"[bugün saat] LT",nextDay:"[yarın saat] LT",nextWeek:"[haftaya] dddd [saat] LT",lastDay:"[dün] LT",lastWeek:"[geçen hafta] dddd [saat] LT",sameElse:"L"},relativeTime:{future:"%s sonra",past:"%s önce",s:"birkaç saniye",m:"bir dakika",mm:"%d dakika",h:"bir saat",hh:"%d saat",d:"bir gün",dd:"%d gün",M:"bir ay",MM:"%d ay",y:"bir yıl",yy:"%d yıl"},ordinalParse:/\d{1,2}'(inci|nci|üncü|ncı|uncu|ıncı)/,ordinal:function(a){if(0===a)return a+"'ıncı";var t=a%10,n=a%100-t,r=a>=100?100:null;return a+(e[t]||e[n]||e[r])},week:{dow:1,doy:7}});return t}(),e.fullCalendar.datepickerLocale("tr","tr",{closeText:"kapat",prevText:"&#x3C;geri",nextText:"ileri&#x3e",currentText:"bugün",monthNames:["Ocak","Şubat","Mart","Nisan","Mayıs","Haziran","Temmuz","Ağustos","Eylül","Ekim","Kasım","Aralık"],monthNamesShort:["Oca","Şub","Mar","Nis","May","Haz","Tem","Ağu","Eyl","Eki","Kas","Ara"],dayNames:["Pazar","Pazartesi","Salı","Çarşamba","Perşembe","Cuma","Cumartesi"],dayNamesShort:["Pz","Pt","Sa","Ça","Pe","Cu","Ct"],dayNamesMin:["Pz","Pt","Sa","Ça","Pe","Cu","Ct"],weekHeader:"Hf",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("tr",{buttonText:{next:"ileri",month:"Ay",week:"Hafta",day:"Gün",list:"Ajanda"},allDayText:"Tüm gün",eventLimitText:"daha fazla",noEventsMessage:"Herhangi bir etkinlik görüntülemek için"})}(),function(){!function(){function e(e,a){var t=e.split("_");return a%10===1&&a%100!==11?t[0]:a%10>=2&&a%10<=4&&(a%100<10||a%100>=20)?t[1]:t[2]}function t(a,t,n){var r={mm:t?"хвилина_хвилини_хвилин":"хвилину_хвилини_хвилин",hh:t?"година_години_годин":"годину_години_годин",dd:"день_дні_днів",MM:"місяць_місяці_місяців",yy:"рік_роки_років"};return"m"===n?t?"хвилина":"хвилину":"h"===n?t?"година":"годину":a+" "+e(r[n],+a)}function n(e,a){var t={nominative:"неділя_понеділок_вівторок_середа_четвер_п’ятниця_субота".split("_"),accusative:"неділю_понеділок_вівторок_середу_четвер_п’ятницю_суботу".split("_"),genitive:"неділі_понеділка_вівторка_середи_четверга_п’ятниці_суботи".split("_")},n=/(\[[ВвУу]\]) ?dddd/.test(a)?"accusative":/\[?(?:минулої|наступної)? ?\] ?dddd/.test(a)?"genitive":"nominative";return t[n][e.day()]}function r(e){return function(){return e+"о"+(11===this.hours()?"б":"")+"] LT"}}var s=a.defineLocale("uk",{months:{format:"січня_лютого_березня_квітня_травня_червня_липня_серпня_вересня_жовтня_листопада_грудня".split("_"),standalone:"січень_лютий_березень_квітень_травень_червень_липень_серпень_вересень_жовтень_листопад_грудень".split("_")},monthsShort:"січ_лют_бер_квіт_трав_черв_лип_серп_вер_жовт_лист_груд".split("_"),weekdays:n,weekdaysShort:"нд_пн_вт_ср_чт_пт_сб".split("_"),weekdaysMin:"нд_пн_вт_ср_чт_пт_сб".split("_"),longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD.MM.YYYY",LL:"D MMMM YYYY р.",LLL:"D MMMM YYYY р., HH:mm",LLLL:"dddd, D MMMM YYYY р., HH:mm"},calendar:{sameDay:r("[Сьогодні "),nextDay:r("[Завтра "),lastDay:r("[Вчора "),nextWeek:r("[У] dddd ["),lastWeek:function(){switch(this.day()){case 0:case 3:case 5:case 6:return r("[Минулої] dddd [").call(this);case 1:case 2:case 4:return r("[Минулого] dddd [").call(this)}},sameElse:"L"},relativeTime:{future:"за %s",past:"%s тому",s:"декілька секунд",m:t,mm:t,h:"годину",hh:t,d:"день",dd:t,M:"місяць",MM:t,y:"рік",yy:t},meridiemParse:/ночі|ранку|дня|вечора/,isPM:function(e){return/^(дня|вечора)$/.test(e)},meridiem:function(e,a,t){return e<4?"ночі":e<12?"ранку":e<17?"дня":"вечора"},ordinalParse:/\d{1,2}-(й|го)/,ordinal:function(e,a){switch(a){case"M":case"d":case"DDD":case"w":case"W":return e+"-й";case"D":return e+"-го";default:return e}},week:{dow:1,doy:7}});return s}(),e.fullCalendar.datepickerLocale("uk","uk",{closeText:"Закрити",prevText:"&#x3C;",nextText:"&#x3E;",currentText:"Сьогодні",monthNames:["Січень","Лютий","Березень","Квітень","Травень","Червень","Липень","Серпень","Вересень","Жовтень","Листопад","Грудень"],monthNamesShort:["Січ","Лют","Бер","Кві","Тра","Чер","Лип","Сер","Вер","Жов","Лис","Гру"],dayNames:["неділя","понеділок","вівторок","середа","четвер","п’ятниця","субота"],dayNamesShort:["нед","пнд","вів","срд","чтв","птн","сбт"],dayNamesMin:["Нд","Пн","Вт","Ср","Чт","Пт","Сб"],weekHeader:"Тиж",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("uk",{buttonText:{month:"Місяць",week:"Тиждень",day:"День",list:"Порядок денний"},allDayText:"Увесь день",eventLimitText:function(e){return"+ще "+e+"..."},noEventsMessage:"Немає подій для відображення"})}(),function(){!function(){var e=a.defineLocale("vi",{months:"tháng 1_tháng 2_tháng 3_tháng 4_tháng 5_tháng 6_tháng 7_tháng 8_tháng 9_tháng 10_tháng 11_tháng 12".split("_"),monthsShort:"Th01_Th02_Th03_Th04_Th05_Th06_Th07_Th08_Th09_Th10_Th11_Th12".split("_"),monthsParseExact:!0,weekdays:"chủ nhật_thứ hai_thứ ba_thứ tư_thứ năm_thứ sáu_thứ bảy".split("_"),weekdaysShort:"CN_T2_T3_T4_T5_T6_T7".split("_"),weekdaysMin:"CN_T2_T3_T4_T5_T6_T7".split("_"),weekdaysParseExact:!0,meridiemParse:/sa|ch/i,isPM:function(e){return/^ch$/i.test(e)},meridiem:function(e,a,t){return e<12?t?"sa":"SA":t?"ch":"CH"},longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D MMMM [năm] YYYY",LLL:"D MMMM [năm] YYYY HH:mm",LLLL:"dddd, D MMMM [năm] YYYY HH:mm",l:"DD/M/YYYY",ll:"D MMM YYYY",lll:"D MMM YYYY HH:mm",llll:"ddd, D MMM YYYY HH:mm"},calendar:{sameDay:"[Hôm nay lúc] LT",nextDay:"[Ngày mai lúc] LT",nextWeek:"dddd [tuần tới lúc] LT",lastDay:"[Hôm qua lúc] LT",lastWeek:"dddd [tuần rồi lúc] LT",sameElse:"L"},relativeTime:{future:"%s tới",past:"%s trước",s:"vài giây",m:"một phút",mm:"%d phút",h:"một giờ",hh:"%d giờ",d:"một ngày",dd:"%d ngày",M:"một tháng",MM:"%d tháng",y:"một năm",yy:"%d năm"},ordinalParse:/\d{1,2}/,ordinal:function(e){return e},week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("vi","vi",{closeText:"Đóng",prevText:"&#x3C;Trước",nextText:"Tiếp&#x3E;",currentText:"Hôm nay",monthNames:["Tháng Một","Tháng Hai","Tháng Ba","Tháng Tư","Tháng Năm","Tháng Sáu","Tháng Bảy","Tháng Tám","Tháng Chín","Tháng Mười","Tháng Mười Một","Tháng Mười Hai"],monthNamesShort:["Tháng 1","Tháng 2","Tháng 3","Tháng 4","Tháng 5","Tháng 6","Tháng 7","Tháng 8","Tháng 9","Tháng 10","Tháng 11","Tháng 12"],dayNames:["Chủ Nhật","Thứ Hai","Thứ Ba","Thứ Tư","Thứ Năm","Thứ Sáu","Thứ Bảy"],dayNamesShort:["CN","T2","T3","T4","T5","T6","T7"],dayNamesMin:["CN","T2","T3","T4","T5","T6","T7"],weekHeader:"Tu",dateFormat:"dd/mm/yy",firstDay:0,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("vi",{buttonText:{month:"Tháng",week:"Tuần",day:"Ngày",list:"Lịch biểu"},allDayText:"Cả ngày",eventLimitText:function(e){return"+ thêm "+e},noEventsMessage:"Không có sự kiện để hiển thị"})}(),function(){!function(){var e=a.defineLocale("zh-cn",{months:"一月_二月_三月_四月_五月_六月_七月_八月_九月_十月_十一月_十二月".split("_"),monthsShort:"1月_2月_3月_4月_5月_6月_7月_8月_9月_10月_11月_12月".split("_"),weekdays:"星期日_星期一_星期二_星期三_星期四_星期五_星期六".split("_"),weekdaysShort:"周日_周一_周二_周三_周四_周五_周六".split("_"),weekdaysMin:"日_一_二_三_四_五_六".split("_"),longDateFormat:{LT:"Ah点mm分",LTS:"Ah点m分s秒",L:"YYYY-MM-DD",LL:"YYYY年MMMD日",LLL:"YYYY年MMMD日Ah点mm分",LLLL:"YYYY年MMMD日ddddAh点mm分",l:"YYYY-MM-DD",ll:"YYYY年MMMD日",lll:"YYYY年MMMD日Ah点mm分",llll:"YYYY年MMMD日ddddAh点mm分"},meridiemParse:/凌晨|早上|上午|中午|下午|晚上/,meridiemHour:function(e,a){return 12===e&&(e=0),"凌晨"===a||"早上"===a||"上午"===a?e:"下午"===a||"晚上"===a?e+12:e>=11?e:e+12},meridiem:function(e,a,t){var n=100*e+a;return n<600?"凌晨":n<900?"早上":n<1130?"上午":n<1230?"中午":n<1800?"下午":"晚上"},calendar:{sameDay:function(){return 0===this.minutes()?"[今天]Ah[点整]":"[今天]LT"},nextDay:function(){return 0===this.minutes()?"[明天]Ah[点整]":"[明天]LT"},lastDay:function(){return 0===this.minutes()?"[昨天]Ah[点整]":"[昨天]LT"},nextWeek:function(){var e,t;return e=a().startOf("week"),t=this.diff(e,"days")>=7?"[下]":"[本]",0===this.minutes()?t+"dddAh点整":t+"dddAh点mm"},lastWeek:function(){var e,t;return e=a().startOf("week"),t=this.unix()<e.unix()?"[上]":"[本]",0===this.minutes()?t+"dddAh点整":t+"dddAh点mm"},sameElse:"LL"},ordinalParse:/\d{1,2}(日|月|周)/,ordinal:function(e,a){switch(a){case"d":case"D":case"DDD":return e+"日";case"M":return e+"月";case"w":case"W":return e+"周";default:return e}},relativeTime:{future:"%s内",past:"%s前",s:"几秒",m:"1 分钟",mm:"%d 分钟",h:"1 小时",hh:"%d 小时",d:"1 天",dd:"%d 天",M:"1 个月",MM:"%d 个月",y:"1 年",yy:"%d 年"},week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("zh-cn","zh-CN",{closeText:"关闭",prevText:"&#x3C;上月",nextText:"下月&#x3E;",currentText:"今天",monthNames:["一月","二月","三月","四月","五月","六月","七月","八月","九月","十月","十一月","十二月"],monthNamesShort:["一月","二月","三月","四月","五月","六月","七月","八月","九月","十月","十一月","十二月"],dayNames:["星期日","星期一","星期二","星期三","星期四","星期五","星期六"],dayNamesShort:["周日","周一","周二","周三","周四","周五","周六"],dayNamesMin:["日","一","二","三","四","五","六"],weekHeader:"周",dateFormat:"yy-mm-dd",firstDay:1,isRTL:!1,showMonthAfterYear:!0,yearSuffix:"年"}),e.fullCalendar.locale("zh-cn",{buttonText:{month:"月",week:"周",day:"日",list:"日程"},allDayText:"全天",eventLimitText:function(e){return"另外 "+e+" 个"},noEventsMessage:"没有事件显示"})}(),function(){!function(){var e=a.defineLocale("zh-tw",{months:"一月_二月_三月_四月_五月_六月_七月_八月_九月_十月_十一月_十二月".split("_"),monthsShort:"1月_2月_3月_4月_5月_6月_7月_8月_9月_10月_11月_12月".split("_"),weekdays:"星期日_星期一_星期二_星期三_星期四_星期五_星期六".split("_"),weekdaysShort:"週日_週一_週二_週三_週四_週五_週六".split("_"),weekdaysMin:"日_一_二_三_四_五_六".split("_"),longDateFormat:{LT:"Ah點mm分",LTS:"Ah點m分s秒",L:"YYYY年MMMD日",LL:"YYYY年MMMD日",LLL:"YYYY年MMMD日Ah點mm分",LLLL:"YYYY年MMMD日ddddAh點mm分",l:"YYYY年MMMD日",ll:"YYYY年MMMD日",lll:"YYYY年MMMD日Ah點mm分",llll:"YYYY年MMMD日ddddAh點mm分"},meridiemParse:/凌晨|早上|上午|中午|下午|晚上/,meridiemHour:function(e,a){return 12===e&&(e=0),"凌晨"===a||"早上"===a||"上午"===a?e:"中午"===a?e>=11?e:e+12:"下午"===a||"晚上"===a?e+12:void 0},meridiem:function(e,a,t){var n=100*e+a;return n<600?"凌晨":n<900?"早上":n<1130?"上午":n<1230?"中午":n<1800?"下午":"晚上"},calendar:{sameDay:"[今天]LT",nextDay:"[明天]LT",nextWeek:"[下]ddddLT",lastDay:"[昨天]LT",lastWeek:"[上]ddddLT",sameElse:"L"},ordinalParse:/\d{1,2}(日|月|週)/,ordinal:function(e,a){switch(a){case"d":case"D":case"DDD":return e+"日";case"M":return e+"月";case"w":case"W":return e+"週";default:return e}},relativeTime:{future:"%s內",past:"%s前",s:"幾秒",m:"1 分鐘",mm:"%d 分鐘",h:"1 小時",hh:"%d 小時",d:"1 天",dd:"%d 天",M:"1 個月",MM:"%d 個月",y:"1 年",yy:"%d 年"}});return e}(),e.fullCalendar.datepickerLocale("zh-tw","zh-TW",{closeText:"關閉",prevText:"&#x3C;上月",nextText:"下月&#x3E;",currentText:"今天",monthNames:["一月","二月","三月","四月","五月","六月","七月","八月","九月","十月","十一月","十二月"],monthNamesShort:["一月","二月","三月","四月","五月","六月","七月","八月","九月","十月","十一月","十二月"],dayNames:["星期日","星期一","星期二","星期三","星期四","星期五","星期六"],dayNamesShort:["周日","周一","周二","周三","周四","周五","周六"],dayNamesMin:["日","一","二","三","四","五","六"],weekHeader:"周",dateFormat:"yy/mm/dd",firstDay:1,isRTL:!1,showMonthAfterYear:!0,yearSuffix:"年"}),e.fullCalendar.locale("zh-tw",{buttonText:{month:"月",week:"週",day:"天",list:"待辦事項"},allDayText:"全天",eventLimitText:"更多",noEventsMessage:"没有事件显示"})}(),a.locale("en"),e.fullCalendar.locale("en"),e.datepicker&&e.datepicker.setDefaults(e.datepicker.regional[""])}); \ No newline at end of file
+dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("en-au","en-AU",{closeText:"Done",prevText:"Prev",nextText:"Next",currentText:"Today",monthNames:["January","February","March","April","May","June","July","August","September","October","November","December"],monthNamesShort:["Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"],dayNames:["Sunday","Monday","Tuesday","Wednesday","Thursday","Friday","Saturday"],dayNamesShort:["Sun","Mon","Tue","Wed","Thu","Fri","Sat"],dayNamesMin:["Su","Mo","Tu","We","Th","Fr","Sa"],weekHeader:"Wk",dateFormat:"dd/mm/yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("en-au")}(),function(){!function(){var e=a.defineLocale("en-ca",{months:"January_February_March_April_May_June_July_August_September_October_November_December".split("_"),monthsShort:"Jan_Feb_Mar_Apr_May_Jun_Jul_Aug_Sep_Oct_Nov_Dec".split("_"),weekdays:"Sunday_Monday_Tuesday_Wednesday_Thursday_Friday_Saturday".split("_"),weekdaysShort:"Sun_Mon_Tue_Wed_Thu_Fri_Sat".split("_"),weekdaysMin:"Su_Mo_Tu_We_Th_Fr_Sa".split("_"),longDateFormat:{LT:"h:mm A",LTS:"h:mm:ss A",L:"YYYY-MM-DD",LL:"MMMM D, YYYY",LLL:"MMMM D, YYYY h:mm A",LLLL:"dddd, MMMM D, YYYY h:mm A"},calendar:{sameDay:"[Today at] LT",nextDay:"[Tomorrow at] LT",nextWeek:"dddd [at] LT",lastDay:"[Yesterday at] LT",lastWeek:"[Last] dddd [at] LT",sameElse:"L"},relativeTime:{future:"in %s",past:"%s ago",s:"a few seconds",m:"a minute",mm:"%d minutes",h:"an hour",hh:"%d hours",d:"a day",dd:"%d days",M:"a month",MM:"%d months",y:"a year",yy:"%d years"},ordinalParse:/\d{1,2}(st|nd|rd|th)/,ordinal:function(e){var a=e%10,t=1===~~(e%100/10)?"th":1===a?"st":2===a?"nd":3===a?"rd":"th";return e+t}});return e}(),e.fullCalendar.locale("en-ca")}(),function(){!function(){var e=a.defineLocale("en-gb",{months:"January_February_March_April_May_June_July_August_September_October_November_December".split("_"),monthsShort:"Jan_Feb_Mar_Apr_May_Jun_Jul_Aug_Sep_Oct_Nov_Dec".split("_"),weekdays:"Sunday_Monday_Tuesday_Wednesday_Thursday_Friday_Saturday".split("_"),weekdaysShort:"Sun_Mon_Tue_Wed_Thu_Fri_Sat".split("_"),weekdaysMin:"Su_Mo_Tu_We_Th_Fr_Sa".split("_"),longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd, D MMMM YYYY HH:mm"},calendar:{sameDay:"[Today at] LT",nextDay:"[Tomorrow at] LT",nextWeek:"dddd [at] LT",lastDay:"[Yesterday at] LT",lastWeek:"[Last] dddd [at] LT",sameElse:"L"},relativeTime:{future:"in %s",past:"%s ago",s:"a few seconds",m:"a minute",mm:"%d minutes",h:"an hour",hh:"%d hours",d:"a day",dd:"%d days",M:"a month",MM:"%d months",y:"a year",yy:"%d years"},ordinalParse:/\d{1,2}(st|nd|rd|th)/,ordinal:function(e){var a=e%10,t=1===~~(e%100/10)?"th":1===a?"st":2===a?"nd":3===a?"rd":"th";return e+t},week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("en-gb","en-GB",{closeText:"Done",prevText:"Prev",nextText:"Next",currentText:"Today",monthNames:["January","February","March","April","May","June","July","August","September","October","November","December"],monthNamesShort:["Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"],dayNames:["Sunday","Monday","Tuesday","Wednesday","Thursday","Friday","Saturday"],dayNamesShort:["Sun","Mon","Tue","Wed","Thu","Fri","Sat"],dayNamesMin:["Su","Mo","Tu","We","Th","Fr","Sa"],weekHeader:"Wk",dateFormat:"dd/mm/yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("en-gb")}(),function(){!function(){var e=a.defineLocale("en-ie",{months:"January_February_March_April_May_June_July_August_September_October_November_December".split("_"),monthsShort:"Jan_Feb_Mar_Apr_May_Jun_Jul_Aug_Sep_Oct_Nov_Dec".split("_"),weekdays:"Sunday_Monday_Tuesday_Wednesday_Thursday_Friday_Saturday".split("_"),weekdaysShort:"Sun_Mon_Tue_Wed_Thu_Fri_Sat".split("_"),weekdaysMin:"Su_Mo_Tu_We_Th_Fr_Sa".split("_"),longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD-MM-YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd D MMMM YYYY HH:mm"},calendar:{sameDay:"[Today at] LT",nextDay:"[Tomorrow at] LT",nextWeek:"dddd [at] LT",lastDay:"[Yesterday at] LT",lastWeek:"[Last] dddd [at] LT",sameElse:"L"},relativeTime:{future:"in %s",past:"%s ago",s:"a few seconds",m:"a minute",mm:"%d minutes",h:"an hour",hh:"%d hours",d:"a day",dd:"%d days",M:"a month",MM:"%d months",y:"a year",yy:"%d years"},ordinalParse:/\d{1,2}(st|nd|rd|th)/,ordinal:function(e){var a=e%10,t=1===~~(e%100/10)?"th":1===a?"st":2===a?"nd":3===a?"rd":"th";return e+t},week:{dow:1,doy:4}});return e}(),e.fullCalendar.locale("en-ie")}(),function(){!function(){var e=a.defineLocale("en-nz",{months:"January_February_March_April_May_June_July_August_September_October_November_December".split("_"),monthsShort:"Jan_Feb_Mar_Apr_May_Jun_Jul_Aug_Sep_Oct_Nov_Dec".split("_"),weekdays:"Sunday_Monday_Tuesday_Wednesday_Thursday_Friday_Saturday".split("_"),weekdaysShort:"Sun_Mon_Tue_Wed_Thu_Fri_Sat".split("_"),weekdaysMin:"Su_Mo_Tu_We_Th_Fr_Sa".split("_"),longDateFormat:{LT:"h:mm A",LTS:"h:mm:ss A",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY h:mm A",LLLL:"dddd, D MMMM YYYY h:mm A"},calendar:{sameDay:"[Today at] LT",nextDay:"[Tomorrow at] LT",nextWeek:"dddd [at] LT",lastDay:"[Yesterday at] LT",lastWeek:"[Last] dddd [at] LT",sameElse:"L"},relativeTime:{future:"in %s",past:"%s ago",s:"a few seconds",m:"a minute",mm:"%d minutes",h:"an hour",hh:"%d hours",d:"a day",dd:"%d days",M:"a month",MM:"%d months",y:"a year",yy:"%d years"},ordinalParse:/\d{1,2}(st|nd|rd|th)/,ordinal:function(e){var a=e%10,t=1===~~(e%100/10)?"th":1===a?"st":2===a?"nd":3===a?"rd":"th";return e+t},week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("en-nz","en-NZ",{closeText:"Done",prevText:"Prev",nextText:"Next",currentText:"Today",monthNames:["January","February","March","April","May","June","July","August","September","October","November","December"],monthNamesShort:["Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"],dayNames:["Sunday","Monday","Tuesday","Wednesday","Thursday","Friday","Saturday"],dayNamesShort:["Sun","Mon","Tue","Wed","Thu","Fri","Sat"],dayNamesMin:["Su","Mo","Tu","We","Th","Fr","Sa"],weekHeader:"Wk",dateFormat:"dd/mm/yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("en-nz")}(),function(){!function(){var e="ene._feb._mar._abr._may._jun._jul._ago._sep._oct._nov._dic.".split("_"),t="ene_feb_mar_abr_may_jun_jul_ago_sep_oct_nov_dic".split("_"),n=a.defineLocale("es",{months:"enero_febrero_marzo_abril_mayo_junio_julio_agosto_septiembre_octubre_noviembre_diciembre".split("_"),monthsShort:function(a,n){return/-MMM-/.test(n)?t[a.month()]:e[a.month()]},monthsParseExact:!0,weekdays:"domingo_lunes_martes_miércoles_jueves_viernes_sábado".split("_"),weekdaysShort:"dom._lun._mar._mié._jue._vie._sáb.".split("_"),weekdaysMin:"do_lu_ma_mi_ju_vi_sá".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"DD/MM/YYYY",LL:"D [de] MMMM [de] YYYY",LLL:"D [de] MMMM [de] YYYY H:mm",LLLL:"dddd, D [de] MMMM [de] YYYY H:mm"},calendar:{sameDay:function(){return"[hoy a la"+(1!==this.hours()?"s":"")+"] LT"},nextDay:function(){return"[mañana a la"+(1!==this.hours()?"s":"")+"] LT"},nextWeek:function(){return"dddd [a la"+(1!==this.hours()?"s":"")+"] LT"},lastDay:function(){return"[ayer a la"+(1!==this.hours()?"s":"")+"] LT"},lastWeek:function(){return"[el] dddd [pasado a la"+(1!==this.hours()?"s":"")+"] LT"},sameElse:"L"},relativeTime:{future:"en %s",past:"hace %s",s:"unos segundos",m:"un minuto",mm:"%d minutos",h:"una hora",hh:"%d horas",d:"un día",dd:"%d días",M:"un mes",MM:"%d meses",y:"un año",yy:"%d años"},ordinalParse:/\d{1,2}º/,ordinal:"%dº",week:{dow:1,doy:4}});return n}(),e.fullCalendar.datepickerLocale("es","es",{closeText:"Cerrar",prevText:"&#x3C;Ant",nextText:"Sig&#x3E;",currentText:"Hoy",monthNames:["enero","febrero","marzo","abril","mayo","junio","julio","agosto","septiembre","octubre","noviembre","diciembre"],monthNamesShort:["ene","feb","mar","abr","may","jun","jul","ago","sep","oct","nov","dic"],dayNames:["domingo","lunes","martes","miércoles","jueves","viernes","sábado"],dayNamesShort:["dom","lun","mar","mié","jue","vie","sáb"],dayNamesMin:["D","L","M","X","J","V","S"],weekHeader:"Sm",dateFormat:"dd/mm/yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("es",{buttonText:{month:"Mes",week:"Semana",day:"Día",list:"Agenda"},allDayHtml:"Todo<br/>el día",eventLimitText:"más",noEventsMessage:"No hay eventos para mostrar"})}(),function(){!function(){var e="ene._feb._mar._abr._may._jun._jul._ago._sep._oct._nov._dic.".split("_"),t="ene_feb_mar_abr_may_jun_jul_ago_sep_oct_nov_dic".split("_"),n=a.defineLocale("es-do",{months:"enero_febrero_marzo_abril_mayo_junio_julio_agosto_septiembre_octubre_noviembre_diciembre".split("_"),monthsShort:function(a,n){return/-MMM-/.test(n)?t[a.month()]:e[a.month()]},monthsParseExact:!0,weekdays:"domingo_lunes_martes_miércoles_jueves_viernes_sábado".split("_"),weekdaysShort:"dom._lun._mar._mié._jue._vie._sáb.".split("_"),weekdaysMin:"do_lu_ma_mi_ju_vi_sá".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"h:mm A",LTS:"h:mm:ss A",L:"DD/MM/YYYY",LL:"D [de] MMMM [de] YYYY",LLL:"D [de] MMMM [de] YYYY h:mm A",LLLL:"dddd, D [de] MMMM [de] YYYY h:mm A"},calendar:{sameDay:function(){return"[hoy a la"+(1!==this.hours()?"s":"")+"] LT"},nextDay:function(){return"[mañana a la"+(1!==this.hours()?"s":"")+"] LT"},nextWeek:function(){return"dddd [a la"+(1!==this.hours()?"s":"")+"] LT"},lastDay:function(){return"[ayer a la"+(1!==this.hours()?"s":"")+"] LT"},lastWeek:function(){return"[el] dddd [pasado a la"+(1!==this.hours()?"s":"")+"] LT"},sameElse:"L"},relativeTime:{future:"en %s",past:"hace %s",s:"unos segundos",m:"un minuto",mm:"%d minutos",h:"una hora",hh:"%d horas",d:"un día",dd:"%d días",M:"un mes",MM:"%d meses",y:"un año",yy:"%d años"},ordinalParse:/\d{1,2}º/,ordinal:"%dº",week:{dow:1,doy:4}});return n}(),e.fullCalendar.datepickerLocale("es-do","es",{closeText:"Cerrar",prevText:"&#x3C;Ant",nextText:"Sig&#x3E;",currentText:"Hoy",monthNames:["enero","febrero","marzo","abril","mayo","junio","julio","agosto","septiembre","octubre","noviembre","diciembre"],monthNamesShort:["ene","feb","mar","abr","may","jun","jul","ago","sep","oct","nov","dic"],dayNames:["domingo","lunes","martes","miércoles","jueves","viernes","sábado"],dayNamesShort:["dom","lun","mar","mié","jue","vie","sáb"],dayNamesMin:["D","L","M","X","J","V","S"],weekHeader:"Sm",dateFormat:"dd/mm/yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("es-do",{buttonText:{month:"Mes",week:"Semana",day:"Día",list:"Agenda"},allDayHtml:"Todo<br/>el día",eventLimitText:"más",noEventsMessage:"No hay eventos para mostrar"})}(),function(){!function(){var e=a.defineLocale("eu",{months:"urtarrila_otsaila_martxoa_apirila_maiatza_ekaina_uztaila_abuztua_iraila_urria_azaroa_abendua".split("_"),monthsShort:"urt._ots._mar._api._mai._eka._uzt._abu._ira._urr._aza._abe.".split("_"),monthsParseExact:!0,weekdays:"igandea_astelehena_asteartea_asteazkena_osteguna_ostirala_larunbata".split("_"),weekdaysShort:"ig._al._ar._az._og._ol._lr.".split("_"),weekdaysMin:"ig_al_ar_az_og_ol_lr".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"YYYY-MM-DD",LL:"YYYY[ko] MMMM[ren] D[a]",LLL:"YYYY[ko] MMMM[ren] D[a] HH:mm",LLLL:"dddd, YYYY[ko] MMMM[ren] D[a] HH:mm",l:"YYYY-M-D",ll:"YYYY[ko] MMM D[a]",lll:"YYYY[ko] MMM D[a] HH:mm",llll:"ddd, YYYY[ko] MMM D[a] HH:mm"},calendar:{sameDay:"[gaur] LT[etan]",nextDay:"[bihar] LT[etan]",nextWeek:"dddd LT[etan]",lastDay:"[atzo] LT[etan]",lastWeek:"[aurreko] dddd LT[etan]",sameElse:"L"},relativeTime:{future:"%s barru",past:"duela %s",s:"segundo batzuk",m:"minutu bat",mm:"%d minutu",h:"ordu bat",hh:"%d ordu",d:"egun bat",dd:"%d egun",M:"hilabete bat",MM:"%d hilabete",y:"urte bat",yy:"%d urte"},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:7}});return e}(),e.fullCalendar.datepickerLocale("eu","eu",{closeText:"Egina",prevText:"&#x3C;Aur",nextText:"Hur&#x3E;",currentText:"Gaur",monthNames:["urtarrila","otsaila","martxoa","apirila","maiatza","ekaina","uztaila","abuztua","iraila","urria","azaroa","abendua"],monthNamesShort:["urt.","ots.","mar.","api.","mai.","eka.","uzt.","abu.","ira.","urr.","aza.","abe."],dayNames:["igandea","astelehena","asteartea","asteazkena","osteguna","ostirala","larunbata"],dayNamesShort:["ig.","al.","ar.","az.","og.","ol.","lr."],dayNamesMin:["ig","al","ar","az","og","ol","lr"],weekHeader:"As",dateFormat:"yy-mm-dd",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("eu",{buttonText:{month:"Hilabetea",week:"Astea",day:"Eguna",list:"Agenda"},allDayHtml:"Egun<br/>osoa",eventLimitText:"gehiago",noEventsMessage:"Ez dago ekitaldirik erakusteko"})}(),function(){!function(){var e={1:"۱",2:"۲",3:"۳",4:"۴",5:"۵",6:"۶",7:"۷",8:"۸",9:"۹",0:"۰"},t={"۱":"1","۲":"2","۳":"3","۴":"4","۵":"5","۶":"6","۷":"7","۸":"8","۹":"9","۰":"0"},n=a.defineLocale("fa",{months:"ژانویه_فوریه_مارس_آوریل_مه_ژوئن_ژوئیه_اوت_سپتامبر_اکتبر_نوامبر_دسامبر".split("_"),monthsShort:"ژانویه_فوریه_مارس_آوریل_مه_ژوئن_ژوئیه_اوت_سپتامبر_اکتبر_نوامبر_دسامبر".split("_"),weekdays:"یک‌شنبه_دوشنبه_سه‌شنبه_چهارشنبه_پنج‌شنبه_جمعه_شنبه".split("_"),weekdaysShort:"یک‌شنبه_دوشنبه_سه‌شنبه_چهارشنبه_پنج‌شنبه_جمعه_شنبه".split("_"),weekdaysMin:"ی_د_س_چ_پ_ج_ش".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd, D MMMM YYYY HH:mm"},meridiemParse:/قبل از ظهر|بعد از ظهر/,isPM:function(e){return/بعد از ظهر/.test(e)},meridiem:function(e,a,t){return e<12?"قبل از ظهر":"بعد از ظهر"},calendar:{sameDay:"[امروز ساعت] LT",nextDay:"[فردا ساعت] LT",nextWeek:"dddd [ساعت] LT",lastDay:"[دیروز ساعت] LT",lastWeek:"dddd [پیش] [ساعت] LT",sameElse:"L"},relativeTime:{future:"در %s",past:"%s پیش",s:"چندین ثانیه",m:"یک دقیقه",mm:"%d دقیقه",h:"یک ساعت",hh:"%d ساعت",d:"یک روز",dd:"%d روز",M:"یک ماه",MM:"%d ماه",y:"یک سال",yy:"%d سال"},preparse:function(e){return e.replace(/[۰-۹]/g,function(e){return t[e]}).replace(/،/g,",")},postformat:function(a){return a.replace(/\d/g,function(a){return e[a]}).replace(/,/g,"،")},ordinalParse:/\d{1,2}م/,ordinal:"%dم",week:{dow:6,doy:12}});return n}(),e.fullCalendar.datepickerLocale("fa","fa",{closeText:"بستن",prevText:"&#x3C;قبلی",nextText:"بعدی&#x3E;",currentText:"امروز",monthNames:["ژانویه","فوریه","مارس","آوریل","مه","ژوئن","ژوئیه","اوت","سپتامبر","اکتبر","نوامبر","دسامبر"],monthNamesShort:["1","2","3","4","5","6","7","8","9","10","11","12"],dayNames:["يکشنبه","دوشنبه","سه‌شنبه","چهارشنبه","پنجشنبه","جمعه","شنبه"],dayNamesShort:["ی","د","س","چ","پ","ج","ش"],dayNamesMin:["ی","د","س","چ","پ","ج","ش"],weekHeader:"هف",dateFormat:"yy/mm/dd",firstDay:6,isRTL:!0,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("fa",{buttonText:{month:"ماه",week:"هفته",day:"روز",list:"برنامه"},allDayText:"تمام روز",eventLimitText:function(e){return"بیش از "+e},noEventsMessage:"هیچ رویدادی به نمایش"})}(),function(){!function(){function e(e,a,n,r){var s="";switch(n){case"s":return r?"muutaman sekunnin":"muutama sekunti";case"m":return r?"minuutin":"minuutti";case"mm":s=r?"minuutin":"minuuttia";break;case"h":return r?"tunnin":"tunti";case"hh":s=r?"tunnin":"tuntia";break;case"d":return r?"päivän":"päivä";case"dd":s=r?"päivän":"päivää";break;case"M":return r?"kuukauden":"kuukausi";case"MM":s=r?"kuukauden":"kuukautta";break;case"y":return r?"vuoden":"vuosi";case"yy":s=r?"vuoden":"vuotta"}return s=t(e,r)+" "+s}function t(e,a){return e<10?a?r[e]:n[e]:e}var n="nolla yksi kaksi kolme neljä viisi kuusi seitsemän kahdeksan yhdeksän".split(" "),r=["nolla","yhden","kahden","kolmen","neljän","viiden","kuuden",n[7],n[8],n[9]],s=a.defineLocale("fi",{months:"tammikuu_helmikuu_maaliskuu_huhtikuu_toukokuu_kesäkuu_heinäkuu_elokuu_syyskuu_lokakuu_marraskuu_joulukuu".split("_"),monthsShort:"tammi_helmi_maalis_huhti_touko_kesä_heinä_elo_syys_loka_marras_joulu".split("_"),weekdays:"sunnuntai_maanantai_tiistai_keskiviikko_torstai_perjantai_lauantai".split("_"),weekdaysShort:"su_ma_ti_ke_to_pe_la".split("_"),weekdaysMin:"su_ma_ti_ke_to_pe_la".split("_"),longDateFormat:{LT:"HH.mm",LTS:"HH.mm.ss",L:"DD.MM.YYYY",LL:"Do MMMM[ta] YYYY",LLL:"Do MMMM[ta] YYYY, [klo] HH.mm",LLLL:"dddd, Do MMMM[ta] YYYY, [klo] HH.mm",l:"D.M.YYYY",ll:"Do MMM YYYY",lll:"Do MMM YYYY, [klo] HH.mm",llll:"ddd, Do MMM YYYY, [klo] HH.mm"},calendar:{sameDay:"[tänään] [klo] LT",nextDay:"[huomenna] [klo] LT",nextWeek:"dddd [klo] LT",lastDay:"[eilen] [klo] LT",lastWeek:"[viime] dddd[na] [klo] LT",sameElse:"L"},relativeTime:{future:"%s päästä",past:"%s sitten",s:e,m:e,mm:e,h:e,hh:e,d:e,dd:e,M:e,MM:e,y:e,yy:e},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:4}});return s}(),e.fullCalendar.datepickerLocale("fi","fi",{closeText:"Sulje",prevText:"&#xAB;Edellinen",nextText:"Seuraava&#xBB;",currentText:"Tänään",monthNames:["Tammikuu","Helmikuu","Maaliskuu","Huhtikuu","Toukokuu","Kesäkuu","Heinäkuu","Elokuu","Syyskuu","Lokakuu","Marraskuu","Joulukuu"],monthNamesShort:["Tammi","Helmi","Maalis","Huhti","Touko","Kesä","Heinä","Elo","Syys","Loka","Marras","Joulu"],dayNamesShort:["Su","Ma","Ti","Ke","To","Pe","La"],dayNames:["Sunnuntai","Maanantai","Tiistai","Keskiviikko","Torstai","Perjantai","Lauantai"],dayNamesMin:["Su","Ma","Ti","Ke","To","Pe","La"],weekHeader:"Vk",dateFormat:"d.m.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("fi",{buttonText:{month:"Kuukausi",week:"Viikko",day:"Päivä",list:"Tapahtumat"},allDayText:"Koko päivä",eventLimitText:"lisää",noEventsMessage:"Ei näytettäviä tapahtumia"})}(),function(){!function(){var e=a.defineLocale("fr",{months:"janvier_février_mars_avril_mai_juin_juillet_août_septembre_octobre_novembre_décembre".split("_"),monthsShort:"janv._févr._mars_avr._mai_juin_juil._août_sept._oct._nov._déc.".split("_"),monthsParseExact:!0,weekdays:"dimanche_lundi_mardi_mercredi_jeudi_vendredi_samedi".split("_"),weekdaysShort:"dim._lun._mar._mer._jeu._ven._sam.".split("_"),weekdaysMin:"Di_Lu_Ma_Me_Je_Ve_Sa".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd D MMMM YYYY HH:mm"},calendar:{sameDay:"[Aujourd'hui à] LT",nextDay:"[Demain à] LT",nextWeek:"dddd [à] LT",lastDay:"[Hier à] LT",lastWeek:"dddd [dernier à] LT",sameElse:"L"},relativeTime:{future:"dans %s",past:"il y a %s",s:"quelques secondes",m:"une minute",mm:"%d minutes",h:"une heure",hh:"%d heures",d:"un jour",dd:"%d jours",M:"un mois",MM:"%d mois",y:"un an",yy:"%d ans"},ordinalParse:/\d{1,2}(er|)/,ordinal:function(e){return e+(1===e?"er":"")},week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("fr","fr",{closeText:"Fermer",prevText:"Précédent",nextText:"Suivant",currentText:"Aujourd'hui",monthNames:["janvier","février","mars","avril","mai","juin","juillet","août","septembre","octobre","novembre","décembre"],monthNamesShort:["janv.","févr.","mars","avr.","mai","juin","juil.","août","sept.","oct.","nov.","déc."],dayNames:["dimanche","lundi","mardi","mercredi","jeudi","vendredi","samedi"],dayNamesShort:["dim.","lun.","mar.","mer.","jeu.","ven.","sam."],dayNamesMin:["D","L","M","M","J","V","S"],weekHeader:"Sem.",dateFormat:"dd/mm/yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("fr",{buttonText:{year:"Année",month:"Mois",week:"Semaine",day:"Jour",list:"Mon planning"},allDayHtml:"Toute la<br/>journée",eventLimitText:"en plus",noEventsMessage:"Aucun événement à afficher"})}(),function(){!function(){var e=a.defineLocale("fr-ca",{months:"janvier_février_mars_avril_mai_juin_juillet_août_septembre_octobre_novembre_décembre".split("_"),monthsShort:"janv._févr._mars_avr._mai_juin_juil._août_sept._oct._nov._déc.".split("_"),monthsParseExact:!0,weekdays:"dimanche_lundi_mardi_mercredi_jeudi_vendredi_samedi".split("_"),weekdaysShort:"dim._lun._mar._mer._jeu._ven._sam.".split("_"),weekdaysMin:"Di_Lu_Ma_Me_Je_Ve_Sa".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"YYYY-MM-DD",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd D MMMM YYYY HH:mm"},calendar:{sameDay:"[Aujourd'hui à] LT",nextDay:"[Demain à] LT",nextWeek:"dddd [à] LT",lastDay:"[Hier à] LT",lastWeek:"dddd [dernier à] LT",sameElse:"L"},relativeTime:{future:"dans %s",past:"il y a %s",s:"quelques secondes",m:"une minute",mm:"%d minutes",h:"une heure",hh:"%d heures",d:"un jour",dd:"%d jours",M:"un mois",MM:"%d mois",y:"un an",yy:"%d ans"},ordinalParse:/\d{1,2}(er|e)/,ordinal:function(e){return e+(1===e?"er":"e")}});return e}(),e.fullCalendar.datepickerLocale("fr-ca","fr-CA",{closeText:"Fermer",prevText:"Précédent",nextText:"Suivant",currentText:"Aujourd'hui",monthNames:["janvier","février","mars","avril","mai","juin","juillet","août","septembre","octobre","novembre","décembre"],monthNamesShort:["janv.","févr.","mars","avril","mai","juin","juil.","août","sept.","oct.","nov.","déc."],dayNames:["dimanche","lundi","mardi","mercredi","jeudi","vendredi","samedi"],dayNamesShort:["dim.","lun.","mar.","mer.","jeu.","ven.","sam."],dayNamesMin:["D","L","M","M","J","V","S"],weekHeader:"Sem.",dateFormat:"yy-mm-dd",firstDay:0,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("fr-ca",{buttonText:{year:"Année",month:"Mois",week:"Semaine",day:"Jour",list:"Mon planning"},allDayHtml:"Toute la<br/>journée",eventLimitText:"en plus",noEventsMessage:"Aucun événement à afficher"})}(),function(){!function(){var e=a.defineLocale("fr-ch",{months:"janvier_février_mars_avril_mai_juin_juillet_août_septembre_octobre_novembre_décembre".split("_"),monthsShort:"janv._févr._mars_avr._mai_juin_juil._août_sept._oct._nov._déc.".split("_"),monthsParseExact:!0,weekdays:"dimanche_lundi_mardi_mercredi_jeudi_vendredi_samedi".split("_"),weekdaysShort:"dim._lun._mar._mer._jeu._ven._sam.".split("_"),weekdaysMin:"Di_Lu_Ma_Me_Je_Ve_Sa".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD.MM.YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd D MMMM YYYY HH:mm"},calendar:{sameDay:"[Aujourd'hui à] LT",nextDay:"[Demain à] LT",nextWeek:"dddd [à] LT",lastDay:"[Hier à] LT",lastWeek:"dddd [dernier à] LT",sameElse:"L"},relativeTime:{future:"dans %s",past:"il y a %s",s:"quelques secondes",m:"une minute",mm:"%d minutes",h:"une heure",hh:"%d heures",d:"un jour",dd:"%d jours",M:"un mois",MM:"%d mois",y:"un an",yy:"%d ans"},ordinalParse:/\d{1,2}(er|e)/,ordinal:function(e){return e+(1===e?"er":"e")},week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("fr-ch","fr-CH",{closeText:"Fermer",prevText:"&#x3C;Préc",nextText:"Suiv&#x3E;",currentText:"Courant",monthNames:["janvier","février","mars","avril","mai","juin","juillet","août","septembre","octobre","novembre","décembre"],monthNamesShort:["janv.","févr.","mars","avril","mai","juin","juil.","août","sept.","oct.","nov.","déc."],dayNames:["dimanche","lundi","mardi","mercredi","jeudi","vendredi","samedi"],dayNamesShort:["dim.","lun.","mar.","mer.","jeu.","ven.","sam."],dayNamesMin:["D","L","M","M","J","V","S"],weekHeader:"Sm",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("fr-ch",{buttonText:{year:"Année",month:"Mois",week:"Semaine",day:"Jour",list:"Mon planning"},allDayHtml:"Toute la<br/>journée",eventLimitText:"en plus",noEventsMessage:"Aucun événement à afficher"})}(),function(){!function(){var e=a.defineLocale("gl",{months:"xaneiro_febreiro_marzo_abril_maio_xuño_xullo_agosto_setembro_outubro_novembro_decembro".split("_"),monthsShort:"xan._feb._mar._abr._mai._xuñ._xul._ago._set._out._nov._dec.".split("_"),monthsParseExact:!0,weekdays:"domingo_luns_martes_mércores_xoves_venres_sábado".split("_"),weekdaysShort:"dom._lun._mar._mér._xov._ven._sáb.".split("_"),weekdaysMin:"do_lu_ma_mé_xo_ve_sá".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"DD/MM/YYYY",LL:"D [de] MMMM [de] YYYY",LLL:"D [de] MMMM [de] YYYY H:mm",LLLL:"dddd, D [de] MMMM [de] YYYY H:mm"},calendar:{sameDay:function(){return"[hoxe "+(1!==this.hours()?"ás":"á")+"] LT"},nextDay:function(){return"[mañá "+(1!==this.hours()?"ás":"á")+"] LT"},nextWeek:function(){return"dddd ["+(1!==this.hours()?"ás":"a")+"] LT"},lastDay:function(){return"[onte "+(1!==this.hours()?"á":"a")+"] LT"},lastWeek:function(){return"[o] dddd [pasado "+(1!==this.hours()?"ás":"a")+"] LT"},sameElse:"L"},relativeTime:{future:function(e){return 0===e.indexOf("un")?"n"+e:"en "+e},past:"hai %s",s:"uns segundos",m:"un minuto",mm:"%d minutos",h:"unha hora",hh:"%d horas",d:"un día",dd:"%d días",M:"un mes",MM:"%d meses",y:"un ano",yy:"%d anos"},ordinalParse:/\d{1,2}º/,ordinal:"%dº",week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("gl","gl",{closeText:"Pechar",prevText:"&#x3C;Ant",nextText:"Seg&#x3E;",currentText:"Hoxe",monthNames:["Xaneiro","Febreiro","Marzo","Abril","Maio","Xuño","Xullo","Agosto","Setembro","Outubro","Novembro","Decembro"],monthNamesShort:["Xan","Feb","Mar","Abr","Mai","Xuñ","Xul","Ago","Set","Out","Nov","Dec"],dayNames:["Domingo","Luns","Martes","Mércores","Xoves","Venres","Sábado"],dayNamesShort:["Dom","Lun","Mar","Mér","Xov","Ven","Sáb"],dayNamesMin:["Do","Lu","Ma","Mé","Xo","Ve","Sá"],weekHeader:"Sm",dateFormat:"dd/mm/yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("gl",{buttonText:{month:"Mes",week:"Semana",day:"Día",list:"Axenda"},allDayHtml:"Todo<br/>o día",eventLimitText:"máis",noEventsMessage:"Non hai eventos para amosar"})}(),function(){!function(){var e=a.defineLocale("he",{months:"ינואר_פברואר_מרץ_אפריל_מאי_יוני_יולי_אוגוסט_ספטמבר_אוקטובר_נובמבר_דצמבר".split("_"),monthsShort:"ינו׳_פבר׳_מרץ_אפר׳_מאי_יוני_יולי_אוג׳_ספט׳_אוק׳_נוב׳_דצמ׳".split("_"),weekdays:"ראשון_שני_שלישי_רביעי_חמישי_שישי_שבת".split("_"),weekdaysShort:"א׳_ב׳_ג׳_ד׳_ה׳_ו׳_ש׳".split("_"),weekdaysMin:"א_ב_ג_ד_ה_ו_ש".split("_"),longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D [ב]MMMM YYYY",LLL:"D [ב]MMMM YYYY HH:mm",LLLL:"dddd, D [ב]MMMM YYYY HH:mm",l:"D/M/YYYY",ll:"D MMM YYYY",lll:"D MMM YYYY HH:mm",llll:"ddd, D MMM YYYY HH:mm"},calendar:{sameDay:"[היום ב־]LT",nextDay:"[מחר ב־]LT",nextWeek:"dddd [בשעה] LT",lastDay:"[אתמול ב־]LT",lastWeek:"[ביום] dddd [האחרון בשעה] LT",sameElse:"L"},relativeTime:{future:"בעוד %s",past:"לפני %s",s:"מספר שניות",m:"דקה",mm:"%d דקות",h:"שעה",hh:function(e){return 2===e?"שעתיים":e+" שעות"},d:"יום",dd:function(e){return 2===e?"יומיים":e+" ימים"},M:"חודש",MM:function(e){return 2===e?"חודשיים":e+" חודשים"},y:"שנה",yy:function(e){return 2===e?"שנתיים":e%10===0&&10!==e?e+" שנה":e+" שנים"}},meridiemParse:/אחה"צ|לפנה"צ|אחרי הצהריים|לפני הצהריים|לפנות בוקר|בבוקר|בערב/i,isPM:function(e){return/^(אחה"צ|אחרי הצהריים|בערב)$/.test(e)},meridiem:function(e,a,t){return e<5?"לפנות בוקר":e<10?"בבוקר":e<12?t?'לפנה"צ':"לפני הצהריים":e<18?t?'אחה"צ':"אחרי הצהריים":"בערב"}});return e}(),e.fullCalendar.datepickerLocale("he","he",{closeText:"סגור",prevText:"&#x3C;הקודם",nextText:"הבא&#x3E;",currentText:"היום",monthNames:["ינואר","פברואר","מרץ","אפריל","מאי","יוני","יולי","אוגוסט","ספטמבר","אוקטובר","נובמבר","דצמבר"],monthNamesShort:["ינו","פבר","מרץ","אפר","מאי","יוני","יולי","אוג","ספט","אוק","נוב","דצמ"],dayNames:["ראשון","שני","שלישי","רביעי","חמישי","שישי","שבת"],dayNamesShort:["א'","ב'","ג'","ד'","ה'","ו'","שבת"],dayNamesMin:["א'","ב'","ג'","ד'","ה'","ו'","שבת"],weekHeader:"Wk",dateFormat:"dd/mm/yy",firstDay:0,isRTL:!0,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("he",{buttonText:{month:"חודש",week:"שבוע",day:"יום",list:"סדר יום"},allDayText:"כל היום",eventLimitText:"אחר",noEventsMessage:"אין אירועים להצגה",weekNumberTitle:"שבוע"})}(),function(){!function(){var e={1:"१",2:"२",3:"३",4:"४",5:"५",6:"६",7:"७",8:"८",9:"९",0:"०"},t={"१":"1","२":"2","३":"3","४":"4","५":"5","६":"6","७":"7","८":"8","९":"9","०":"0"},n=a.defineLocale("hi",{months:"जनवरी_फ़रवरी_मार्च_अप्रैल_मई_जून_जुलाई_अगस्त_सितम्बर_अक्टूबर_नवम्बर_दिसम्बर".split("_"),monthsShort:"जन._फ़र._मार्च_अप्रै._मई_जून_जुल._अग._सित._अक्टू._नव._दिस.".split("_"),monthsParseExact:!0,weekdays:"रविवार_सोमवार_मंगलवार_बुधवार_गुरूवार_शुक्रवार_शनिवार".split("_"),weekdaysShort:"रवि_सोम_मंगल_बुध_गुरू_शुक्र_शनि".split("_"),weekdaysMin:"र_सो_मं_बु_गु_शु_श".split("_"),longDateFormat:{LT:"A h:mm बजे",LTS:"A h:mm:ss बजे",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY, A h:mm बजे",LLLL:"dddd, D MMMM YYYY, A h:mm बजे"},calendar:{sameDay:"[आज] LT",nextDay:"[कल] LT",nextWeek:"dddd, LT",lastDay:"[कल] LT",lastWeek:"[पिछले] dddd, LT",sameElse:"L"},relativeTime:{future:"%s में",past:"%s पहले",s:"कुछ ही क्षण",m:"एक मिनट",mm:"%d मिनट",h:"एक घंटा",hh:"%d घंटे",d:"एक दिन",dd:"%d दिन",M:"एक महीने",MM:"%d महीने",y:"एक वर्ष",yy:"%d वर्ष"},preparse:function(e){return e.replace(/[१२३४५६७८९०]/g,function(e){return t[e]})},postformat:function(a){return a.replace(/\d/g,function(a){return e[a]})},meridiemParse:/रात|सुबह|दोपहर|शाम/,meridiemHour:function(e,a){return 12===e&&(e=0),"रात"===a?e<4?e:e+12:"सुबह"===a?e:"दोपहर"===a?e>=10?e:e+12:"शाम"===a?e+12:void 0},meridiem:function(e,a,t){return e<4?"रात":e<10?"सुबह":e<17?"दोपहर":e<20?"शाम":"रात"},week:{dow:0,doy:6}});return n}(),e.fullCalendar.datepickerLocale("hi","hi",{closeText:"बंद",prevText:"पिछला",nextText:"अगला",currentText:"आज",monthNames:["जनवरी ","फरवरी","मार्च","अप्रेल","मई","जून","जूलाई","अगस्त ","सितम्बर","अक्टूबर","नवम्बर","दिसम्बर"],monthNamesShort:["जन","फर","मार्च","अप्रेल","मई","जून","जूलाई","अग","सित","अक्ट","नव","दि"],dayNames:["रविवार","सोमवार","मंगलवार","बुधवार","गुरुवार","शुक्रवार","शनिवार"],dayNamesShort:["रवि","सोम","मंगल","बुध","गुरु","शुक्र","शनि"],dayNamesMin:["रवि","सोम","मंगल","बुध","गुरु","शुक्र","शनि"],weekHeader:"हफ्ता",dateFormat:"dd/mm/yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("hi",{buttonText:{month:"महीना",week:"सप्ताह",day:"दिन",list:"कार्यसूची"},allDayText:"सभी दिन",eventLimitText:function(e){return"+अधिक "+e},noEventsMessage:"कोई घटनाओं को प्रदर्शित करने के लिए"})}(),function(){!function(){function e(e,a,t){var n=e+" ";switch(t){case"m":return a?"jedna minuta":"jedne minute";case"mm":return n+=1===e?"minuta":2===e||3===e||4===e?"minute":"minuta";case"h":return a?"jedan sat":"jednog sata";case"hh":return n+=1===e?"sat":2===e||3===e||4===e?"sata":"sati";case"dd":return n+=1===e?"dan":"dana";case"MM":return n+=1===e?"mjesec":2===e||3===e||4===e?"mjeseca":"mjeseci";case"yy":return n+=1===e?"godina":2===e||3===e||4===e?"godine":"godina"}}var t=a.defineLocale("hr",{months:{format:"siječnja_veljače_ožujka_travnja_svibnja_lipnja_srpnja_kolovoza_rujna_listopada_studenoga_prosinca".split("_"),standalone:"siječanj_veljača_ožujak_travanj_svibanj_lipanj_srpanj_kolovoz_rujan_listopad_studeni_prosinac".split("_")},monthsShort:"sij._velj._ožu._tra._svi._lip._srp._kol._ruj._lis._stu._pro.".split("_"),monthsParseExact:!0,weekdays:"nedjelja_ponedjeljak_utorak_srijeda_četvrtak_petak_subota".split("_"),weekdaysShort:"ned._pon._uto._sri._čet._pet._sub.".split("_"),weekdaysMin:"ne_po_ut_sr_če_pe_su".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"DD.MM.YYYY",LL:"D. MMMM YYYY",LLL:"D. MMMM YYYY H:mm",LLLL:"dddd, D. MMMM YYYY H:mm"},calendar:{sameDay:"[danas u] LT",nextDay:"[sutra u] LT",nextWeek:function(){switch(this.day()){case 0:return"[u] [nedjelju] [u] LT";case 3:return"[u] [srijedu] [u] LT";case 6:return"[u] [subotu] [u] LT";case 1:case 2:case 4:case 5:return"[u] dddd [u] LT"}},lastDay:"[jučer u] LT",lastWeek:function(){switch(this.day()){case 0:case 3:return"[prošlu] dddd [u] LT";case 6:return"[prošle] [subote] [u] LT";case 1:case 2:case 4:case 5:return"[prošli] dddd [u] LT"}},sameElse:"L"},relativeTime:{future:"za %s",past:"prije %s",s:"par sekundi",m:e,mm:e,h:e,hh:e,d:"dan",dd:e,M:"mjesec",MM:e,y:"godinu",yy:e},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:7}});return t}(),e.fullCalendar.datepickerLocale("hr","hr",{closeText:"Zatvori",prevText:"&#x3C;",nextText:"&#x3E;",currentText:"Danas",monthNames:["Siječanj","Veljača","Ožujak","Travanj","Svibanj","Lipanj","Srpanj","Kolovoz","Rujan","Listopad","Studeni","Prosinac"],
+monthNamesShort:["Sij","Velj","Ožu","Tra","Svi","Lip","Srp","Kol","Ruj","Lis","Stu","Pro"],dayNames:["Nedjelja","Ponedjeljak","Utorak","Srijeda","Četvrtak","Petak","Subota"],dayNamesShort:["Ned","Pon","Uto","Sri","Čet","Pet","Sub"],dayNamesMin:["Ne","Po","Ut","Sr","Če","Pe","Su"],weekHeader:"Tje",dateFormat:"dd.mm.yy.",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("hr",{buttonText:{prev:"Prijašnji",next:"Sljedeći",month:"Mjesec",week:"Tjedan",day:"Dan",list:"Raspored"},allDayText:"Cijeli dan",eventLimitText:function(e){return"+ još "+e},noEventsMessage:"Nema događaja za prikaz"})}(),function(){!function(){function e(e,a,t,n){var r=e;switch(t){case"s":return n||a?"néhány másodperc":"néhány másodperce";case"m":return"egy"+(n||a?" perc":" perce");case"mm":return r+(n||a?" perc":" perce");case"h":return"egy"+(n||a?" óra":" órája");case"hh":return r+(n||a?" óra":" órája");case"d":return"egy"+(n||a?" nap":" napja");case"dd":return r+(n||a?" nap":" napja");case"M":return"egy"+(n||a?" hónap":" hónapja");case"MM":return r+(n||a?" hónap":" hónapja");case"y":return"egy"+(n||a?" év":" éve");case"yy":return r+(n||a?" év":" éve")}return""}function t(e){return(e?"":"[múlt] ")+"["+n[this.day()]+"] LT[-kor]"}var n="vasárnap hétfőn kedden szerdán csütörtökön pénteken szombaton".split(" "),r=a.defineLocale("hu",{months:"január_február_március_április_május_június_július_augusztus_szeptember_október_november_december".split("_"),monthsShort:"jan_feb_márc_ápr_máj_jún_júl_aug_szept_okt_nov_dec".split("_"),weekdays:"vasárnap_hétfő_kedd_szerda_csütörtök_péntek_szombat".split("_"),weekdaysShort:"vas_hét_kedd_sze_csüt_pén_szo".split("_"),weekdaysMin:"v_h_k_sze_cs_p_szo".split("_"),longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"YYYY.MM.DD.",LL:"YYYY. MMMM D.",LLL:"YYYY. MMMM D. H:mm",LLLL:"YYYY. MMMM D., dddd H:mm"},meridiemParse:/de|du/i,isPM:function(e){return"u"===e.charAt(1).toLowerCase()},meridiem:function(e,a,t){return e<12?t===!0?"de":"DE":t===!0?"du":"DU"},calendar:{sameDay:"[ma] LT[-kor]",nextDay:"[holnap] LT[-kor]",nextWeek:function(){return t.call(this,!0)},lastDay:"[tegnap] LT[-kor]",lastWeek:function(){return t.call(this,!1)},sameElse:"L"},relativeTime:{future:"%s múlva",past:"%s",s:e,m:e,mm:e,h:e,hh:e,d:e,dd:e,M:e,MM:e,y:e,yy:e},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:4}});return r}(),e.fullCalendar.datepickerLocale("hu","hu",{closeText:"bezár",prevText:"vissza",nextText:"előre",currentText:"ma",monthNames:["Január","Február","Március","Április","Május","Június","Július","Augusztus","Szeptember","Október","November","December"],monthNamesShort:["Jan","Feb","Már","Ápr","Máj","Jún","Júl","Aug","Szep","Okt","Nov","Dec"],dayNames:["Vasárnap","Hétfő","Kedd","Szerda","Csütörtök","Péntek","Szombat"],dayNamesShort:["Vas","Hét","Ked","Sze","Csü","Pén","Szo"],dayNamesMin:["V","H","K","Sze","Cs","P","Szo"],weekHeader:"Hét",dateFormat:"yy.mm.dd.",firstDay:1,isRTL:!1,showMonthAfterYear:!0,yearSuffix:""}),e.fullCalendar.locale("hu",{buttonText:{month:"Hónap",week:"Hét",day:"Nap",list:"Napló"},allDayText:"Egész nap",eventLimitText:"további",noEventsMessage:"Nincs megjeleníthető események"})}(),function(){!function(){var e=a.defineLocale("id",{months:"Januari_Februari_Maret_April_Mei_Juni_Juli_Agustus_September_Oktober_November_Desember".split("_"),monthsShort:"Jan_Feb_Mar_Apr_Mei_Jun_Jul_Ags_Sep_Okt_Nov_Des".split("_"),weekdays:"Minggu_Senin_Selasa_Rabu_Kamis_Jumat_Sabtu".split("_"),weekdaysShort:"Min_Sen_Sel_Rab_Kam_Jum_Sab".split("_"),weekdaysMin:"Mg_Sn_Sl_Rb_Km_Jm_Sb".split("_"),longDateFormat:{LT:"HH.mm",LTS:"HH.mm.ss",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY [pukul] HH.mm",LLLL:"dddd, D MMMM YYYY [pukul] HH.mm"},meridiemParse:/pagi|siang|sore|malam/,meridiemHour:function(e,a){return 12===e&&(e=0),"pagi"===a?e:"siang"===a?e>=11?e:e+12:"sore"===a||"malam"===a?e+12:void 0},meridiem:function(e,a,t){return e<11?"pagi":e<15?"siang":e<19?"sore":"malam"},calendar:{sameDay:"[Hari ini pukul] LT",nextDay:"[Besok pukul] LT",nextWeek:"dddd [pukul] LT",lastDay:"[Kemarin pukul] LT",lastWeek:"dddd [lalu pukul] LT",sameElse:"L"},relativeTime:{future:"dalam %s",past:"%s yang lalu",s:"beberapa detik",m:"semenit",mm:"%d menit",h:"sejam",hh:"%d jam",d:"sehari",dd:"%d hari",M:"sebulan",MM:"%d bulan",y:"setahun",yy:"%d tahun"},week:{dow:1,doy:7}});return e}(),e.fullCalendar.datepickerLocale("id","id",{closeText:"Tutup",prevText:"&#x3C;mundur",nextText:"maju&#x3E;",currentText:"hari ini",monthNames:["Januari","Februari","Maret","April","Mei","Juni","Juli","Agustus","September","Oktober","Nopember","Desember"],monthNamesShort:["Jan","Feb","Mar","Apr","Mei","Jun","Jul","Agus","Sep","Okt","Nop","Des"],dayNames:["Minggu","Senin","Selasa","Rabu","Kamis","Jumat","Sabtu"],dayNamesShort:["Min","Sen","Sel","Rab","kam","Jum","Sab"],dayNamesMin:["Mg","Sn","Sl","Rb","Km","jm","Sb"],weekHeader:"Mg",dateFormat:"dd/mm/yy",firstDay:0,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("id",{buttonText:{month:"Bulan",week:"Minggu",day:"Hari",list:"Agenda"},allDayHtml:"Sehari<br/>penuh",eventLimitText:"lebih",noEventsMessage:"Tidak ada acara untuk ditampilkan"})}(),function(){!function(){function e(e){return e%100===11||e%10!==1}function t(a,t,n,r){var s=a+" ";switch(n){case"s":return t||r?"nokkrar sekúndur":"nokkrum sekúndum";case"m":return t?"mínúta":"mínútu";case"mm":return e(a)?s+(t||r?"mínútur":"mínútum"):t?s+"mínúta":s+"mínútu";case"hh":return e(a)?s+(t||r?"klukkustundir":"klukkustundum"):s+"klukkustund";case"d":return t?"dagur":r?"dag":"degi";case"dd":return e(a)?t?s+"dagar":s+(r?"daga":"dögum"):t?s+"dagur":s+(r?"dag":"degi");case"M":return t?"mánuður":r?"mánuð":"mánuði";case"MM":return e(a)?t?s+"mánuðir":s+(r?"mánuði":"mánuðum"):t?s+"mánuður":s+(r?"mánuð":"mánuði");case"y":return t||r?"ár":"ári";case"yy":return e(a)?s+(t||r?"ár":"árum"):s+(t||r?"ár":"ári")}}var n=a.defineLocale("is",{months:"janúar_febrúar_mars_apríl_maí_júní_júlí_ágúst_september_október_nóvember_desember".split("_"),monthsShort:"jan_feb_mar_apr_maí_jún_júl_ágú_sep_okt_nóv_des".split("_"),weekdays:"sunnudagur_mánudagur_þriðjudagur_miðvikudagur_fimmtudagur_föstudagur_laugardagur".split("_"),weekdaysShort:"sun_mán_þri_mið_fim_fös_lau".split("_"),weekdaysMin:"Su_Má_Þr_Mi_Fi_Fö_La".split("_"),longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"DD.MM.YYYY",LL:"D. MMMM YYYY",LLL:"D. MMMM YYYY [kl.] H:mm",LLLL:"dddd, D. MMMM YYYY [kl.] H:mm"},calendar:{sameDay:"[í dag kl.] LT",nextDay:"[á morgun kl.] LT",nextWeek:"dddd [kl.] LT",lastDay:"[í gær kl.] LT",lastWeek:"[síðasta] dddd [kl.] LT",sameElse:"L"},relativeTime:{future:"eftir %s",past:"fyrir %s síðan",s:t,m:t,mm:t,h:"klukkustund",hh:t,d:t,dd:t,M:t,MM:t,y:t,yy:t},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:4}});return n}(),e.fullCalendar.datepickerLocale("is","is",{closeText:"Loka",prevText:"&#x3C; Fyrri",nextText:"Næsti &#x3E;",currentText:"Í dag",monthNames:["Janúar","Febrúar","Mars","Apríl","Maí","Júní","Júlí","Ágúst","September","Október","Nóvember","Desember"],monthNamesShort:["Jan","Feb","Mar","Apr","Maí","Jún","Júl","Ágú","Sep","Okt","Nóv","Des"],dayNames:["Sunnudagur","Mánudagur","Þriðjudagur","Miðvikudagur","Fimmtudagur","Föstudagur","Laugardagur"],dayNamesShort:["Sun","Mán","Þri","Mið","Fim","Fös","Lau"],dayNamesMin:["Su","Má","Þr","Mi","Fi","Fö","La"],weekHeader:"Vika",dateFormat:"dd.mm.yy",firstDay:0,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("is",{buttonText:{month:"Mánuður",week:"Vika",day:"Dagur",list:"Dagskrá"},allDayHtml:"Allan<br/>daginn",eventLimitText:"meira",noEventsMessage:"Engir viðburðir til að sýna"})}(),function(){!function(){var e=a.defineLocale("it",{months:"gennaio_febbraio_marzo_aprile_maggio_giugno_luglio_agosto_settembre_ottobre_novembre_dicembre".split("_"),monthsShort:"gen_feb_mar_apr_mag_giu_lug_ago_set_ott_nov_dic".split("_"),weekdays:"Domenica_Lunedì_Martedì_Mercoledì_Giovedì_Venerdì_Sabato".split("_"),weekdaysShort:"Dom_Lun_Mar_Mer_Gio_Ven_Sab".split("_"),weekdaysMin:"Do_Lu_Ma_Me_Gi_Ve_Sa".split("_"),longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd, D MMMM YYYY HH:mm"},calendar:{sameDay:"[Oggi alle] LT",nextDay:"[Domani alle] LT",nextWeek:"dddd [alle] LT",lastDay:"[Ieri alle] LT",lastWeek:function(){switch(this.day()){case 0:return"[la scorsa] dddd [alle] LT";default:return"[lo scorso] dddd [alle] LT"}},sameElse:"L"},relativeTime:{future:function(e){return(/^[0-9].+$/.test(e)?"tra":"in")+" "+e},past:"%s fa",s:"alcuni secondi",m:"un minuto",mm:"%d minuti",h:"un'ora",hh:"%d ore",d:"un giorno",dd:"%d giorni",M:"un mese",MM:"%d mesi",y:"un anno",yy:"%d anni"},ordinalParse:/\d{1,2}º/,ordinal:"%dº",week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("it","it",{closeText:"Chiudi",prevText:"&#x3C;Prec",nextText:"Succ&#x3E;",currentText:"Oggi",monthNames:["Gennaio","Febbraio","Marzo","Aprile","Maggio","Giugno","Luglio","Agosto","Settembre","Ottobre","Novembre","Dicembre"],monthNamesShort:["Gen","Feb","Mar","Apr","Mag","Giu","Lug","Ago","Set","Ott","Nov","Dic"],dayNames:["Domenica","Lunedì","Martedì","Mercoledì","Giovedì","Venerdì","Sabato"],dayNamesShort:["Dom","Lun","Mar","Mer","Gio","Ven","Sab"],dayNamesMin:["Do","Lu","Ma","Me","Gi","Ve","Sa"],weekHeader:"Sm",dateFormat:"dd/mm/yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("it",{buttonText:{month:"Mese",week:"Settimana",day:"Giorno",list:"Agenda"},allDayHtml:"Tutto il<br/>giorno",eventLimitText:function(e){return"+altri "+e},noEventsMessage:"Non ci sono eventi da visualizzare"})}(),function(){!function(){var e=a.defineLocale("ja",{months:"1月_2月_3月_4月_5月_6月_7月_8月_9月_10月_11月_12月".split("_"),monthsShort:"1月_2月_3月_4月_5月_6月_7月_8月_9月_10月_11月_12月".split("_"),weekdays:"日曜日_月曜日_火曜日_水曜日_木曜日_金曜日_土曜日".split("_"),weekdaysShort:"日_月_火_水_木_金_土".split("_"),weekdaysMin:"日_月_火_水_木_金_土".split("_"),longDateFormat:{LT:"Ah時m分",LTS:"Ah時m分s秒",L:"YYYY/MM/DD",LL:"YYYY年M月D日",LLL:"YYYY年M月D日Ah時m分",LLLL:"YYYY年M月D日Ah時m分 dddd"},meridiemParse:/午前|午後/i,isPM:function(e){return"午後"===e},meridiem:function(e,a,t){return e<12?"午前":"午後"},calendar:{sameDay:"[今日] LT",nextDay:"[明日] LT",nextWeek:"[来週]dddd LT",lastDay:"[昨日] LT",lastWeek:"[前週]dddd LT",sameElse:"L"},ordinalParse:/\d{1,2}日/,ordinal:function(e,a){switch(a){case"d":case"D":case"DDD":return e+"日";default:return e}},relativeTime:{future:"%s後",past:"%s前",s:"数秒",m:"1分",mm:"%d分",h:"1時間",hh:"%d時間",d:"1日",dd:"%d日",M:"1ヶ月",MM:"%dヶ月",y:"1年",yy:"%d年"}});return e}(),e.fullCalendar.datepickerLocale("ja","ja",{closeText:"閉じる",prevText:"&#x3C;前",nextText:"次&#x3E;",currentText:"今日",monthNames:["1月","2月","3月","4月","5月","6月","7月","8月","9月","10月","11月","12月"],monthNamesShort:["1月","2月","3月","4月","5月","6月","7月","8月","9月","10月","11月","12月"],dayNames:["日曜日","月曜日","火曜日","水曜日","木曜日","金曜日","土曜日"],dayNamesShort:["日","月","火","水","木","金","土"],dayNamesMin:["日","月","火","水","木","金","土"],weekHeader:"週",dateFormat:"yy/mm/dd",firstDay:0,isRTL:!1,showMonthAfterYear:!0,yearSuffix:"年"}),e.fullCalendar.locale("ja",{buttonText:{month:"月",week:"週",day:"日",list:"予定リスト"},allDayText:"終日",eventLimitText:function(e){return"他 "+e+" 件"},noEventsMessage:"イベントが表示されないように"})}(),function(){!function(){var e={0:"-ші",1:"-ші",2:"-ші",3:"-ші",4:"-ші",5:"-ші",6:"-шы",7:"-ші",8:"-ші",9:"-шы",10:"-шы",20:"-шы",30:"-шы",40:"-шы",50:"-ші",60:"-шы",70:"-ші",80:"-ші",90:"-шы",100:"-ші"},t=a.defineLocale("kk",{months:"қаңтар_ақпан_наурыз_сәуір_мамыр_маусым_шілде_тамыз_қыркүйек_қазан_қараша_желтоқсан".split("_"),monthsShort:"қаң_ақп_нау_сәу_мам_мау_шіл_там_қыр_қаз_қар_жел".split("_"),weekdays:"жексенбі_дүйсенбі_сейсенбі_сәрсенбі_бейсенбі_жұма_сенбі".split("_"),weekdaysShort:"жек_дүй_сей_сәр_бей_жұм_сен".split("_"),weekdaysMin:"жк_дй_сй_ср_бй_жм_сн".split("_"),longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD.MM.YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd, D MMMM YYYY HH:mm"},calendar:{sameDay:"[Бүгін сағат] LT",nextDay:"[Ертең сағат] LT",nextWeek:"dddd [сағат] LT",lastDay:"[Кеше сағат] LT",lastWeek:"[Өткен аптаның] dddd [сағат] LT",sameElse:"L"},relativeTime:{future:"%s ішінде",past:"%s бұрын",s:"бірнеше секунд",m:"бір минут",mm:"%d минут",h:"бір сағат",hh:"%d сағат",d:"бір күн",dd:"%d күн",M:"бір ай",MM:"%d ай",y:"бір жыл",yy:"%d жыл"},ordinalParse:/\d{1,2}-(ші|шы)/,ordinal:function(a){var t=a%10,n=a>=100?100:null;return a+(e[a]||e[t]||e[n])},week:{dow:1,doy:7}});return t}(),e.fullCalendar.datepickerLocale("kk","kk",{closeText:"Жабу",prevText:"&#x3C;Алдыңғы",nextText:"Келесі&#x3E;",currentText:"Бүгін",monthNames:["Қаңтар","Ақпан","Наурыз","Сәуір","Мамыр","Маусым","Шілде","Тамыз","Қыркүйек","Қазан","Қараша","Желтоқсан"],monthNamesShort:["Қаң","Ақп","Нау","Сәу","Мам","Мау","Шіл","Там","Қыр","Қаз","Қар","Жел"],dayNames:["Жексенбі","Дүйсенбі","Сейсенбі","Сәрсенбі","Бейсенбі","Жұма","Сенбі"],dayNamesShort:["жкс","дсн","ссн","срс","бсн","жма","снб"],dayNamesMin:["Жк","Дс","Сс","Ср","Бс","Жм","Сн"],weekHeader:"Не",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("kk",{buttonText:{month:"Ай",week:"Апта",day:"Күн",list:"Күн тәртібі"},allDayText:"Күні бойы",eventLimitText:function(e){return"+ тағы "+e},noEventsMessage:"Көрсету үшін оқиғалар жоқ"})}(),function(){!function(){var e=a.defineLocale("ko",{months:"1월_2월_3월_4월_5월_6월_7월_8월_9월_10월_11월_12월".split("_"),monthsShort:"1월_2월_3월_4월_5월_6월_7월_8월_9월_10월_11월_12월".split("_"),weekdays:"일요일_월요일_화요일_수요일_목요일_금요일_토요일".split("_"),weekdaysShort:"일_월_화_수_목_금_토".split("_"),weekdaysMin:"일_월_화_수_목_금_토".split("_"),longDateFormat:{LT:"A h시 m분",LTS:"A h시 m분 s초",L:"YYYY.MM.DD",LL:"YYYY년 MMMM D일",LLL:"YYYY년 MMMM D일 A h시 m분",LLLL:"YYYY년 MMMM D일 dddd A h시 m분"},calendar:{sameDay:"오늘 LT",nextDay:"내일 LT",nextWeek:"dddd LT",lastDay:"어제 LT",lastWeek:"지난주 dddd LT",sameElse:"L"},relativeTime:{future:"%s 후",past:"%s 전",s:"몇 초",ss:"%d초",m:"일분",mm:"%d분",h:"한 시간",hh:"%d시간",d:"하루",dd:"%d일",M:"한 달",MM:"%d달",y:"일 년",yy:"%d년"},ordinalParse:/\d{1,2}일/,ordinal:"%d일",meridiemParse:/오전|오후/,isPM:function(e){return"오후"===e},meridiem:function(e,a,t){return e<12?"오전":"오후"}});return e}(),e.fullCalendar.datepickerLocale("ko","ko",{closeText:"닫기",prevText:"이전달",nextText:"다음달",currentText:"오늘",monthNames:["1월","2월","3월","4월","5월","6월","7월","8월","9월","10월","11월","12월"],monthNamesShort:["1월","2월","3월","4월","5월","6월","7월","8월","9월","10월","11월","12월"],dayNames:["일요일","월요일","화요일","수요일","목요일","금요일","토요일"],dayNamesShort:["일","월","화","수","목","금","토"],dayNamesMin:["일","월","화","수","목","금","토"],weekHeader:"주",dateFormat:"yy. m. d.",firstDay:0,isRTL:!1,showMonthAfterYear:!0,yearSuffix:"년"}),e.fullCalendar.locale("ko",{buttonText:{month:"월",week:"주",day:"일",list:"일정목록"},allDayText:"종일",eventLimitText:"개",noEventsMessage:"일정이 표시 없습니다"})}(),function(){!function(){function e(e,a,t,n){var r={m:["eng Minutt","enger Minutt"],h:["eng Stonn","enger Stonn"],d:["een Dag","engem Dag"],M:["ee Mount","engem Mount"],y:["ee Joer","engem Joer"]};return a?r[t][0]:r[t][1]}function t(e){var a=e.substr(0,e.indexOf(" "));return r(a)?"a "+e:"an "+e}function n(e){var a=e.substr(0,e.indexOf(" "));return r(a)?"viru "+e:"virun "+e}function r(e){if(e=parseInt(e,10),isNaN(e))return!1;if(e<0)return!0;if(e<10)return 4<=e&&e<=7;if(e<100){var a=e%10,t=e/10;return r(0===a?t:a)}if(e<1e4){for(;e>=10;)e/=10;return r(e)}return e/=1e3,r(e)}var s=a.defineLocale("lb",{months:"Januar_Februar_Mäerz_Abrëll_Mee_Juni_Juli_August_September_Oktober_November_Dezember".split("_"),monthsShort:"Jan._Febr._Mrz._Abr._Mee_Jun._Jul._Aug._Sept._Okt._Nov._Dez.".split("_"),monthsParseExact:!0,weekdays:"Sonndeg_Méindeg_Dënschdeg_Mëttwoch_Donneschdeg_Freideg_Samschdeg".split("_"),weekdaysShort:"So._Mé._Dë._Më._Do._Fr._Sa.".split("_"),weekdaysMin:"So_Mé_Dë_Më_Do_Fr_Sa".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"H:mm [Auer]",LTS:"H:mm:ss [Auer]",L:"DD.MM.YYYY",LL:"D. MMMM YYYY",LLL:"D. MMMM YYYY H:mm [Auer]",LLLL:"dddd, D. MMMM YYYY H:mm [Auer]"},calendar:{sameDay:"[Haut um] LT",sameElse:"L",nextDay:"[Muer um] LT",nextWeek:"dddd [um] LT",lastDay:"[Gëschter um] LT",lastWeek:function(){switch(this.day()){case 2:case 4:return"[Leschten] dddd [um] LT";default:return"[Leschte] dddd [um] LT"}}},relativeTime:{future:t,past:n,s:"e puer Sekonnen",m:e,mm:"%d Minutten",h:e,hh:"%d Stonnen",d:e,dd:"%d Deeg",M:e,MM:"%d Méint",y:e,yy:"%d Joer"},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:4}});return s}(),e.fullCalendar.datepickerLocale("lb","lb",{closeText:"Fäerdeg",prevText:"Zréck",nextText:"Weider",currentText:"Haut",monthNames:["Januar","Februar","Mäerz","Abrëll","Mee","Juni","Juli","August","September","Oktober","November","Dezember"],monthNamesShort:["Jan","Feb","Mäe","Abr","Mee","Jun","Jul","Aug","Sep","Okt","Nov","Dez"],dayNames:["Sonndeg","Méindeg","Dënschdeg","Mëttwoch","Donneschdeg","Freideg","Samschdeg"],dayNamesShort:["Son","Méi","Dën","Mët","Don","Fre","Sam"],dayNamesMin:["So","Mé","Dë","Më","Do","Fr","Sa"],weekHeader:"W",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("lb",{buttonText:{month:"Mount",week:"Woch",day:"Dag",list:"Terminiwwersiicht"},allDayText:"Ganzen Dag",eventLimitText:"méi",noEventsMessage:"Nee Evenementer ze affichéieren"})}(),function(){!function(){function e(e,a,t,n){return a?"kelios sekundės":n?"kelių sekundžių":"kelias sekundes"}function t(e,a,t,n){return a?r(t)[0]:n?r(t)[1]:r(t)[2]}function n(e){return e%10===0||e>10&&e<20}function r(e){return d[e].split("_")}function s(e,a,s,d){var i=e+" ";return 1===e?i+t(e,a,s[0],d):a?i+(n(e)?r(s)[1]:r(s)[0]):d?i+r(s)[1]:i+(n(e)?r(s)[1]:r(s)[2])}var d={m:"minutė_minutės_minutę",mm:"minutės_minučių_minutes",h:"valanda_valandos_valandą",hh:"valandos_valandų_valandas",d:"diena_dienos_dieną",dd:"dienos_dienų_dienas",M:"mėnuo_mėnesio_mėnesį",MM:"mėnesiai_mėnesių_mėnesius",y:"metai_metų_metus",yy:"metai_metų_metus"},i=a.defineLocale("lt",{months:{format:"sausio_vasario_kovo_balandžio_gegužės_birželio_liepos_rugpjūčio_rugsėjo_spalio_lapkričio_gruodžio".split("_"),standalone:"sausis_vasaris_kovas_balandis_gegužė_birželis_liepa_rugpjūtis_rugsėjis_spalis_lapkritis_gruodis".split("_"),isFormat:/D[oD]?(\[[^\[\]]*\]|\s)+MMMM?|MMMM?(\[[^\[\]]*\]|\s)+D[oD]?/},monthsShort:"sau_vas_kov_bal_geg_bir_lie_rgp_rgs_spa_lap_grd".split("_"),weekdays:{format:"sekmadienį_pirmadienį_antradienį_trečiadienį_ketvirtadienį_penktadienį_šeštadienį".split("_"),standalone:"sekmadienis_pirmadienis_antradienis_trečiadienis_ketvirtadienis_penktadienis_šeštadienis".split("_"),isFormat:/dddd HH:mm/},weekdaysShort:"Sek_Pir_Ant_Tre_Ket_Pen_Šeš".split("_"),weekdaysMin:"S_P_A_T_K_Pn_Š".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"YYYY-MM-DD",LL:"YYYY [m.] MMMM D [d.]",LLL:"YYYY [m.] MMMM D [d.], HH:mm [val.]",LLLL:"YYYY [m.] MMMM D [d.], dddd, HH:mm [val.]",l:"YYYY-MM-DD",ll:"YYYY [m.] MMMM D [d.]",lll:"YYYY [m.] MMMM D [d.], HH:mm [val.]",llll:"YYYY [m.] MMMM D [d.], ddd, HH:mm [val.]"},calendar:{sameDay:"[Šiandien] LT",nextDay:"[Rytoj] LT",nextWeek:"dddd LT",lastDay:"[Vakar] LT",lastWeek:"[Praėjusį] dddd LT",sameElse:"L"},relativeTime:{future:"po %s",past:"prieš %s",s:e,m:t,mm:s,h:t,hh:s,d:t,dd:s,M:t,MM:s,y:t,yy:s},ordinalParse:/\d{1,2}-oji/,ordinal:function(e){return e+"-oji"},week:{dow:1,doy:4}});return i}(),e.fullCalendar.datepickerLocale("lt","lt",{closeText:"Uždaryti",prevText:"&#x3C;Atgal",nextText:"Pirmyn&#x3E;",currentText:"Šiandien",monthNames:["Sausis","Vasaris","Kovas","Balandis","Gegužė","Birželis","Liepa","Rugpjūtis","Rugsėjis","Spalis","Lapkritis","Gruodis"],monthNamesShort:["Sau","Vas","Kov","Bal","Geg","Bir","Lie","Rugp","Rugs","Spa","Lap","Gru"],dayNames:["sekmadienis","pirmadienis","antradienis","trečiadienis","ketvirtadienis","penktadienis","šeštadienis"],dayNamesShort:["sek","pir","ant","tre","ket","pen","šeš"],dayNamesMin:["Se","Pr","An","Tr","Ke","Pe","Še"],weekHeader:"SAV",dateFormat:"yy-mm-dd",firstDay:1,isRTL:!1,showMonthAfterYear:!0,yearSuffix:""}),e.fullCalendar.locale("lt",{buttonText:{month:"Mėnuo",week:"Savaitė",day:"Diena",list:"Darbotvarkė"},allDayText:"Visą dieną",eventLimitText:"daugiau",noEventsMessage:"Nėra įvykių rodyti"})}(),function(){!function(){function e(e,a,t){return t?a%10===1&&a%100!==11?e[2]:e[3]:a%10===1&&a%100!==11?e[0]:e[1]}function t(a,t,n){return a+" "+e(s[n],a,t)}function n(a,t,n){return e(s[n],a,t)}function r(e,a){return a?"dažas sekundes":"dažām sekundēm"}var s={m:"minūtes_minūtēm_minūte_minūtes".split("_"),mm:"minūtes_minūtēm_minūte_minūtes".split("_"),h:"stundas_stundām_stunda_stundas".split("_"),hh:"stundas_stundām_stunda_stundas".split("_"),d:"dienas_dienām_diena_dienas".split("_"),dd:"dienas_dienām_diena_dienas".split("_"),M:"mēneša_mēnešiem_mēnesis_mēneši".split("_"),MM:"mēneša_mēnešiem_mēnesis_mēneši".split("_"),y:"gada_gadiem_gads_gadi".split("_"),yy:"gada_gadiem_gads_gadi".split("_")},d=a.defineLocale("lv",{months:"janvāris_februāris_marts_aprīlis_maijs_jūnijs_jūlijs_augusts_septembris_oktobris_novembris_decembris".split("_"),monthsShort:"jan_feb_mar_apr_mai_jūn_jūl_aug_sep_okt_nov_dec".split("_"),weekdays:"svētdiena_pirmdiena_otrdiena_trešdiena_ceturtdiena_piektdiena_sestdiena".split("_"),weekdaysShort:"Sv_P_O_T_C_Pk_S".split("_"),weekdaysMin:"Sv_P_O_T_C_Pk_S".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD.MM.YYYY.",LL:"YYYY. [gada] D. MMMM",LLL:"YYYY. [gada] D. MMMM, HH:mm",LLLL:"YYYY. [gada] D. MMMM, dddd, HH:mm"},calendar:{sameDay:"[Šodien pulksten] LT",nextDay:"[Rīt pulksten] LT",nextWeek:"dddd [pulksten] LT",lastDay:"[Vakar pulksten] LT",lastWeek:"[Pagājušā] dddd [pulksten] LT",sameElse:"L"},relativeTime:{future:"pēc %s",past:"pirms %s",s:r,m:n,mm:t,h:n,hh:t,d:n,dd:t,M:n,MM:t,y:n,yy:t},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:4}});return d}(),e.fullCalendar.datepickerLocale("lv","lv",{closeText:"Aizvērt",prevText:"Iepr.",nextText:"Nāk.",currentText:"Šodien",monthNames:["Janvāris","Februāris","Marts","Aprīlis","Maijs","Jūnijs","Jūlijs","Augusts","Septembris","Oktobris","Novembris","Decembris"],monthNamesShort:["Jan","Feb","Mar","Apr","Mai","Jūn","Jūl","Aug","Sep","Okt","Nov","Dec"],dayNames:["svētdiena","pirmdiena","otrdiena","trešdiena","ceturtdiena","piektdiena","sestdiena"],dayNamesShort:["svt","prm","otr","tre","ctr","pkt","sst"],dayNamesMin:["Sv","Pr","Ot","Tr","Ct","Pk","Ss"],weekHeader:"Ned.",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("lv",{buttonText:{month:"Mēnesis",week:"Nedēļa",day:"Diena",list:"Dienas kārtība"},allDayText:"Visu dienu",eventLimitText:function(e){return"+vēl "+e},noEventsMessage:"Nav notikumu, lai parādītu"})}(),function(){!function(){var e=a.defineLocale("mk",{months:"јануари_февруари_март_април_мај_јуни_јули_август_септември_октомври_ноември_декември".split("_"),monthsShort:"јан_фев_мар_апр_мај_јун_јул_авг_сеп_окт_ное_дек".split("_"),weekdays:"недела_понеделник_вторник_среда_четврток_петок_сабота".split("_"),weekdaysShort:"нед_пон_вто_сре_чет_пет_саб".split("_"),weekdaysMin:"нe_пo_вт_ср_че_пе_сa".split("_"),longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"D.MM.YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY H:mm",LLLL:"dddd, D MMMM YYYY H:mm"},calendar:{sameDay:"[Денес во] LT",nextDay:"[Утре во] LT",nextWeek:"[Во] dddd [во] LT",lastDay:"[Вчера во] LT",lastWeek:function(){switch(this.day()){case 0:case 3:case 6:return"[Изминатата] dddd [во] LT";case 1:case 2:case 4:case 5:return"[Изминатиот] dddd [во] LT"}},sameElse:"L"},relativeTime:{future:"после %s",past:"пред %s",s:"неколку секунди",m:"минута",mm:"%d минути",h:"час",hh:"%d часа",d:"ден",dd:"%d дена",M:"месец",MM:"%d месеци",y:"година",yy:"%d години"},ordinalParse:/\d{1,2}-(ев|ен|ти|ви|ри|ми)/,ordinal:function(e){var a=e%10,t=e%100;return 0===e?e+"-ев":0===t?e+"-ен":t>10&&t<20?e+"-ти":1===a?e+"-ви":2===a?e+"-ри":7===a||8===a?e+"-ми":e+"-ти"},week:{dow:1,doy:7}});return e}(),e.fullCalendar.datepickerLocale("mk","mk",{closeText:"Затвори",prevText:"&#x3C;",nextText:"&#x3E;",currentText:"Денес",monthNames:["Јануари","Февруари","Март","Април","Мај","Јуни","Јули","Август","Септември","Октомври","Ноември","Декември"],monthNamesShort:["Јан","Фев","Мар","Апр","Мај","Јун","Јул","Авг","Сеп","Окт","Ное","Дек"],dayNames:["Недела","Понеделник","Вторник","Среда","Четврток","Петок","Сабота"],dayNamesShort:["Нед","Пон","Вто","Сре","Чет","Пет","Саб"],dayNamesMin:["Не","По","Вт","Ср","Че","Пе","Са"],weekHeader:"Сед",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("mk",{buttonText:{month:"Месец",week:"Недела",day:"Ден",list:"График"},allDayText:"Цел ден",eventLimitText:function(e){return"+повеќе "+e},noEventsMessage:"Нема настани за прикажување"})}(),function(){!function(){var e=a.defineLocale("ms",{months:"Januari_Februari_Mac_April_Mei_Jun_Julai_Ogos_September_Oktober_November_Disember".split("_"),monthsShort:"Jan_Feb_Mac_Apr_Mei_Jun_Jul_Ogs_Sep_Okt_Nov_Dis".split("_"),weekdays:"Ahad_Isnin_Selasa_Rabu_Khamis_Jumaat_Sabtu".split("_"),weekdaysShort:"Ahd_Isn_Sel_Rab_Kha_Jum_Sab".split("_"),weekdaysMin:"Ah_Is_Sl_Rb_Km_Jm_Sb".split("_"),longDateFormat:{LT:"HH.mm",LTS:"HH.mm.ss",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY [pukul] HH.mm",LLLL:"dddd, D MMMM YYYY [pukul] HH.mm"},meridiemParse:/pagi|tengahari|petang|malam/,meridiemHour:function(e,a){return 12===e&&(e=0),"pagi"===a?e:"tengahari"===a?e>=11?e:e+12:"petang"===a||"malam"===a?e+12:void 0},meridiem:function(e,a,t){return e<11?"pagi":e<15?"tengahari":e<19?"petang":"malam"},calendar:{sameDay:"[Hari ini pukul] LT",nextDay:"[Esok pukul] LT",nextWeek:"dddd [pukul] LT",lastDay:"[Kelmarin pukul] LT",lastWeek:"dddd [lepas pukul] LT",sameElse:"L"},relativeTime:{future:"dalam %s",past:"%s yang lepas",s:"beberapa saat",m:"seminit",mm:"%d minit",h:"sejam",hh:"%d jam",d:"sehari",dd:"%d hari",M:"sebulan",MM:"%d bulan",y:"setahun",yy:"%d tahun"},week:{dow:1,doy:7}});return e}(),e.fullCalendar.datepickerLocale("ms","ms",{closeText:"Tutup",prevText:"&#x3C;Sebelum",nextText:"Selepas&#x3E;",currentText:"hari ini",monthNames:["Januari","Februari","Mac","April","Mei","Jun","Julai","Ogos","September","Oktober","November","Disember"],monthNamesShort:["Jan","Feb","Mac","Apr","Mei","Jun","Jul","Ogo","Sep","Okt","Nov","Dis"],dayNames:["Ahad","Isnin","Selasa","Rabu","Khamis","Jumaat","Sabtu"],dayNamesShort:["Aha","Isn","Sel","Rab","kha","Jum","Sab"],dayNamesMin:["Ah","Is","Se","Ra","Kh","Ju","Sa"],weekHeader:"Mg",dateFormat:"dd/mm/yy",firstDay:0,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("ms",{buttonText:{month:"Bulan",week:"Minggu",day:"Hari",list:"Agenda"},allDayText:"Sepanjang hari",eventLimitText:function(e){return"masih ada "+e+" acara"},noEventsMessage:"Tiada peristiwa untuk dipaparkan"})}(),function(){!function(){var e=a.defineLocale("ms-my",{months:"Januari_Februari_Mac_April_Mei_Jun_Julai_Ogos_September_Oktober_November_Disember".split("_"),monthsShort:"Jan_Feb_Mac_Apr_Mei_Jun_Jul_Ogs_Sep_Okt_Nov_Dis".split("_"),weekdays:"Ahad_Isnin_Selasa_Rabu_Khamis_Jumaat_Sabtu".split("_"),weekdaysShort:"Ahd_Isn_Sel_Rab_Kha_Jum_Sab".split("_"),weekdaysMin:"Ah_Is_Sl_Rb_Km_Jm_Sb".split("_"),longDateFormat:{LT:"HH.mm",LTS:"HH.mm.ss",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY [pukul] HH.mm",LLLL:"dddd, D MMMM YYYY [pukul] HH.mm"},meridiemParse:/pagi|tengahari|petang|malam/,meridiemHour:function(e,a){return 12===e&&(e=0),"pagi"===a?e:"tengahari"===a?e>=11?e:e+12:"petang"===a||"malam"===a?e+12:void 0},meridiem:function(e,a,t){return e<11?"pagi":e<15?"tengahari":e<19?"petang":"malam"},calendar:{sameDay:"[Hari ini pukul] LT",nextDay:"[Esok pukul] LT",nextWeek:"dddd [pukul] LT",lastDay:"[Kelmarin pukul] LT",lastWeek:"dddd [lepas pukul] LT",sameElse:"L"},relativeTime:{future:"dalam %s",past:"%s yang lepas",s:"beberapa saat",m:"seminit",mm:"%d minit",h:"sejam",hh:"%d jam",d:"sehari",dd:"%d hari",M:"sebulan",MM:"%d bulan",y:"setahun",yy:"%d tahun"},week:{dow:1,doy:7}});return e}(),e.fullCalendar.datepickerLocale("ms-my","ms",{closeText:"Tutup",prevText:"&#x3C;Sebelum",nextText:"Selepas&#x3E;",currentText:"hari ini",monthNames:["Januari","Februari","Mac","April","Mei","Jun","Julai","Ogos","September","Oktober","November","Disember"],monthNamesShort:["Jan","Feb","Mac","Apr","Mei","Jun","Jul","Ogo","Sep","Okt","Nov","Dis"],dayNames:["Ahad","Isnin","Selasa","Rabu","Khamis","Jumaat","Sabtu"],dayNamesShort:["Aha","Isn","Sel","Rab","kha","Jum","Sab"],dayNamesMin:["Ah","Is","Se","Ra","Kh","Ju","Sa"],weekHeader:"Mg",dateFormat:"dd/mm/yy",firstDay:0,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("ms-my",{buttonText:{month:"Bulan",week:"Minggu",day:"Hari",list:"Agenda"},allDayText:"Sepanjang hari",eventLimitText:function(e){return"masih ada "+e+" acara"},noEventsMessage:"Tiada peristiwa untuk dipaparkan"})}(),function(){!function(){var e=a.defineLocale("nb",{months:"januar_februar_mars_april_mai_juni_juli_august_september_oktober_november_desember".split("_"),monthsShort:"jan._feb._mars_april_mai_juni_juli_aug._sep._okt._nov._des.".split("_"),monthsParseExact:!0,weekdays:"søndag_mandag_tirsdag_onsdag_torsdag_fredag_lørdag".split("_"),weekdaysShort:"sø._ma._ti._on._to._fr._lø.".split("_"),weekdaysMin:"sø_ma_ti_on_to_fr_lø".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD.MM.YYYY",LL:"D. MMMM YYYY",LLL:"D. MMMM YYYY [kl.] HH:mm",LLLL:"dddd D. MMMM YYYY [kl.] HH:mm"},calendar:{sameDay:"[i dag kl.] LT",nextDay:"[i morgen kl.] LT",nextWeek:"dddd [kl.] LT",lastDay:"[i går kl.] LT",lastWeek:"[forrige] dddd [kl.] LT",sameElse:"L"},relativeTime:{future:"om %s",past:"%s siden",s:"noen sekunder",m:"ett minutt",mm:"%d minutter",h:"en time",hh:"%d timer",d:"en dag",dd:"%d dager",M:"en måned",MM:"%d måneder",y:"ett år",yy:"%d år"},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("nb","nb",{closeText:"Lukk",prevText:"&#xAB;Forrige",nextText:"Neste&#xBB;",currentText:"I dag",monthNames:["januar","februar","mars","april","mai","juni","juli","august","september","oktober","november","desember"],monthNamesShort:["jan","feb","mar","apr","mai","jun","jul","aug","sep","okt","nov","des"],dayNamesShort:["søn","man","tir","ons","tor","fre","lør"],dayNames:["søndag","mandag","tirsdag","onsdag","torsdag","fredag","lørdag"],dayNamesMin:["sø","ma","ti","on","to","fr","lø"],weekHeader:"Uke",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("nb",{buttonText:{month:"Måned",week:"Uke",day:"Dag",list:"Agenda"},allDayText:"Hele dagen",eventLimitText:"til",noEventsMessage:"Ingen hendelser å vise"})}(),function(){!function(){var e="jan._feb._mrt._apr._mei_jun._jul._aug._sep._okt._nov._dec.".split("_"),t="jan_feb_mrt_apr_mei_jun_jul_aug_sep_okt_nov_dec".split("_"),n=[/^jan/i,/^feb/i,/^maart|mrt.?$/i,/^apr/i,/^mei$/i,/^jun[i.]?$/i,/^jul[i.]?$/i,/^aug/i,/^sep/i,/^okt/i,/^nov/i,/^dec/i],r=/^(januari|februari|maart|april|mei|april|ju[nl]i|augustus|september|oktober|november|december|jan\.?|feb\.?|mrt\.?|apr\.?|ju[nl]\.?|aug\.?|sep\.?|okt\.?|nov\.?|dec\.?)/i,s=a.defineLocale("nl",{months:"januari_februari_maart_april_mei_juni_juli_augustus_september_oktober_november_december".split("_"),monthsShort:function(a,n){return/-MMM-/.test(n)?t[a.month()]:e[a.month()]},monthsRegex:r,monthsShortRegex:r,monthsStrictRegex:/^(januari|februari|maart|mei|ju[nl]i|april|augustus|september|oktober|november|december)/i,monthsShortStrictRegex:/^(jan\.?|feb\.?|mrt\.?|apr\.?|mei|ju[nl]\.?|aug\.?|sep\.?|okt\.?|nov\.?|dec\.?)/i,monthsParse:n,longMonthsParse:n,shortMonthsParse:n,weekdays:"zondag_maandag_dinsdag_woensdag_donderdag_vrijdag_zaterdag".split("_"),weekdaysShort:"zo._ma._di._wo._do._vr._za.".split("_"),weekdaysMin:"Zo_Ma_Di_Wo_Do_Vr_Za".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD-MM-YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd D MMMM YYYY HH:mm"},calendar:{sameDay:"[vandaag om] LT",nextDay:"[morgen om] LT",nextWeek:"dddd [om] LT",
+lastDay:"[gisteren om] LT",lastWeek:"[afgelopen] dddd [om] LT",sameElse:"L"},relativeTime:{future:"over %s",past:"%s geleden",s:"een paar seconden",m:"één minuut",mm:"%d minuten",h:"één uur",hh:"%d uur",d:"één dag",dd:"%d dagen",M:"één maand",MM:"%d maanden",y:"één jaar",yy:"%d jaar"},ordinalParse:/\d{1,2}(ste|de)/,ordinal:function(e){return e+(1===e||8===e||e>=20?"ste":"de")},week:{dow:1,doy:4}});return s}(),e.fullCalendar.datepickerLocale("nl","nl",{closeText:"Sluiten",prevText:"←",nextText:"→",currentText:"Vandaag",monthNames:["januari","februari","maart","april","mei","juni","juli","augustus","september","oktober","november","december"],monthNamesShort:["jan","feb","mrt","apr","mei","jun","jul","aug","sep","okt","nov","dec"],dayNames:["zondag","maandag","dinsdag","woensdag","donderdag","vrijdag","zaterdag"],dayNamesShort:["zon","maa","din","woe","don","vri","zat"],dayNamesMin:["zo","ma","di","wo","do","vr","za"],weekHeader:"Wk",dateFormat:"dd-mm-yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("nl",{buttonText:{month:"Maand",week:"Week",day:"Dag",list:"Agenda"},allDayText:"Hele dag",eventLimitText:"extra",noEventsMessage:"Geen evenementen om te laten zien"})}(),function(){!function(){var e="jan._feb._mrt._apr._mei_jun._jul._aug._sep._okt._nov._dec.".split("_"),t="jan_feb_mrt_apr_mei_jun_jul_aug_sep_okt_nov_dec".split("_"),n=[/^jan/i,/^feb/i,/^maart|mrt.?$/i,/^apr/i,/^mei$/i,/^jun[i.]?$/i,/^jul[i.]?$/i,/^aug/i,/^sep/i,/^okt/i,/^nov/i,/^dec/i],r=/^(januari|februari|maart|april|mei|april|ju[nl]i|augustus|september|oktober|november|december|jan\.?|feb\.?|mrt\.?|apr\.?|ju[nl]\.?|aug\.?|sep\.?|okt\.?|nov\.?|dec\.?)/i,s=a.defineLocale("nl-be",{months:"januari_februari_maart_april_mei_juni_juli_augustus_september_oktober_november_december".split("_"),monthsShort:function(a,n){return/-MMM-/.test(n)?t[a.month()]:e[a.month()]},monthsRegex:r,monthsShortRegex:r,monthsStrictRegex:/^(januari|februari|maart|mei|ju[nl]i|april|augustus|september|oktober|november|december)/i,monthsShortStrictRegex:/^(jan\.?|feb\.?|mrt\.?|apr\.?|mei|ju[nl]\.?|aug\.?|sep\.?|okt\.?|nov\.?|dec\.?)/i,monthsParse:n,longMonthsParse:n,shortMonthsParse:n,weekdays:"zondag_maandag_dinsdag_woensdag_donderdag_vrijdag_zaterdag".split("_"),weekdaysShort:"zo._ma._di._wo._do._vr._za.".split("_"),weekdaysMin:"Zo_Ma_Di_Wo_Do_Vr_Za".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd D MMMM YYYY HH:mm"},calendar:{sameDay:"[vandaag om] LT",nextDay:"[morgen om] LT",nextWeek:"dddd [om] LT",lastDay:"[gisteren om] LT",lastWeek:"[afgelopen] dddd [om] LT",sameElse:"L"},relativeTime:{future:"over %s",past:"%s geleden",s:"een paar seconden",m:"één minuut",mm:"%d minuten",h:"één uur",hh:"%d uur",d:"één dag",dd:"%d dagen",M:"één maand",MM:"%d maanden",y:"één jaar",yy:"%d jaar"},ordinalParse:/\d{1,2}(ste|de)/,ordinal:function(e){return e+(1===e||8===e||e>=20?"ste":"de")},week:{dow:1,doy:4}});return s}(),e.fullCalendar.datepickerLocale("nl-be","nl-BE",{closeText:"Sluiten",prevText:"←",nextText:"→",currentText:"Vandaag",monthNames:["januari","februari","maart","april","mei","juni","juli","augustus","september","oktober","november","december"],monthNamesShort:["jan","feb","mrt","apr","mei","jun","jul","aug","sep","okt","nov","dec"],dayNames:["zondag","maandag","dinsdag","woensdag","donderdag","vrijdag","zaterdag"],dayNamesShort:["zon","maa","din","woe","don","vri","zat"],dayNamesMin:["zo","ma","di","wo","do","vr","za"],weekHeader:"Wk",dateFormat:"dd/mm/yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("nl-be",{buttonText:{month:"Maand",week:"Week",day:"Dag",list:"Agenda"},allDayText:"Hele dag",eventLimitText:"extra",noEventsMessage:"Geen evenementen om te laten zien"})}(),function(){!function(){var e=a.defineLocale("nn",{months:"januar_februar_mars_april_mai_juni_juli_august_september_oktober_november_desember".split("_"),monthsShort:"jan_feb_mar_apr_mai_jun_jul_aug_sep_okt_nov_des".split("_"),weekdays:"sundag_måndag_tysdag_onsdag_torsdag_fredag_laurdag".split("_"),weekdaysShort:"sun_mån_tys_ons_tor_fre_lau".split("_"),weekdaysMin:"su_må_ty_on_to_fr_lø".split("_"),longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD.MM.YYYY",LL:"D. MMMM YYYY",LLL:"D. MMMM YYYY [kl.] H:mm",LLLL:"dddd D. MMMM YYYY [kl.] HH:mm"},calendar:{sameDay:"[I dag klokka] LT",nextDay:"[I morgon klokka] LT",nextWeek:"dddd [klokka] LT",lastDay:"[I går klokka] LT",lastWeek:"[Føregåande] dddd [klokka] LT",sameElse:"L"},relativeTime:{future:"om %s",past:"%s sidan",s:"nokre sekund",m:"eit minutt",mm:"%d minutt",h:"ein time",hh:"%d timar",d:"ein dag",dd:"%d dagar",M:"ein månad",MM:"%d månader",y:"eit år",yy:"%d år"},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("nn","nn",{closeText:"Lukk",prevText:"&#xAB;Førre",nextText:"Neste&#xBB;",currentText:"I dag",monthNames:["januar","februar","mars","april","mai","juni","juli","august","september","oktober","november","desember"],monthNamesShort:["jan","feb","mar","apr","mai","jun","jul","aug","sep","okt","nov","des"],dayNamesShort:["sun","mån","tys","ons","tor","fre","lau"],dayNames:["sundag","måndag","tysdag","onsdag","torsdag","fredag","laurdag"],dayNamesMin:["su","må","ty","on","to","fr","la"],weekHeader:"Veke",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("nn",{buttonText:{month:"Månad",week:"Veke",day:"Dag",list:"Agenda"},allDayText:"Heile dagen",eventLimitText:"til",noEventsMessage:"Ingen hendelser å vise"})}(),function(){!function(){function e(e){return e%10<5&&e%10>1&&~~(e/10)%10!==1}function t(a,t,n){var r=a+" ";switch(n){case"m":return t?"minuta":"minutę";case"mm":return r+(e(a)?"minuty":"minut");case"h":return t?"godzina":"godzinę";case"hh":return r+(e(a)?"godziny":"godzin");case"MM":return r+(e(a)?"miesiące":"miesięcy");case"yy":return r+(e(a)?"lata":"lat")}}var n="styczeń_luty_marzec_kwiecień_maj_czerwiec_lipiec_sierpień_wrzesień_październik_listopad_grudzień".split("_"),r="stycznia_lutego_marca_kwietnia_maja_czerwca_lipca_sierpnia_września_października_listopada_grudnia".split("_"),s=a.defineLocale("pl",{months:function(e,a){return""===a?"("+r[e.month()]+"|"+n[e.month()]+")":/D MMMM/.test(a)?r[e.month()]:n[e.month()]},monthsShort:"sty_lut_mar_kwi_maj_cze_lip_sie_wrz_paź_lis_gru".split("_"),weekdays:"niedziela_poniedziałek_wtorek_środa_czwartek_piątek_sobota".split("_"),weekdaysShort:"ndz_pon_wt_śr_czw_pt_sob".split("_"),weekdaysMin:"Nd_Pn_Wt_Śr_Cz_Pt_So".split("_"),longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD.MM.YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd, D MMMM YYYY HH:mm"},calendar:{sameDay:"[Dziś o] LT",nextDay:"[Jutro o] LT",nextWeek:"[W] dddd [o] LT",lastDay:"[Wczoraj o] LT",lastWeek:function(){switch(this.day()){case 0:return"[W zeszłą niedzielę o] LT";case 3:return"[W zeszłą środę o] LT";case 6:return"[W zeszłą sobotę o] LT";default:return"[W zeszły] dddd [o] LT"}},sameElse:"L"},relativeTime:{future:"za %s",past:"%s temu",s:"kilka sekund",m:t,mm:t,h:t,hh:t,d:"1 dzień",dd:"%d dni",M:"miesiąc",MM:t,y:"rok",yy:t},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:4}});return s}(),e.fullCalendar.datepickerLocale("pl","pl",{closeText:"Zamknij",prevText:"&#x3C;Poprzedni",nextText:"Następny&#x3E;",currentText:"Dziś",monthNames:["Styczeń","Luty","Marzec","Kwiecień","Maj","Czerwiec","Lipiec","Sierpień","Wrzesień","Październik","Listopad","Grudzień"],monthNamesShort:["Sty","Lu","Mar","Kw","Maj","Cze","Lip","Sie","Wrz","Pa","Lis","Gru"],dayNames:["Niedziela","Poniedziałek","Wtorek","Środa","Czwartek","Piątek","Sobota"],dayNamesShort:["Nie","Pn","Wt","Śr","Czw","Pt","So"],dayNamesMin:["N","Pn","Wt","Śr","Cz","Pt","So"],weekHeader:"Tydz",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("pl",{buttonText:{month:"Miesiąc",week:"Tydzień",day:"Dzień",list:"Plan dnia"},allDayText:"Cały dzień",eventLimitText:"więcej",noEventsMessage:"Brak wydarzeń do wyświetlenia"})}(),function(){!function(){var e=a.defineLocale("pt",{months:"Janeiro_Fevereiro_Março_Abril_Maio_Junho_Julho_Agosto_Setembro_Outubro_Novembro_Dezembro".split("_"),monthsShort:"Jan_Fev_Mar_Abr_Mai_Jun_Jul_Ago_Set_Out_Nov_Dez".split("_"),weekdays:"Domingo_Segunda-Feira_Terça-Feira_Quarta-Feira_Quinta-Feira_Sexta-Feira_Sábado".split("_"),weekdaysShort:"Dom_Seg_Ter_Qua_Qui_Sex_Sáb".split("_"),weekdaysMin:"Dom_2ª_3ª_4ª_5ª_6ª_Sáb".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D [de] MMMM [de] YYYY",LLL:"D [de] MMMM [de] YYYY HH:mm",LLLL:"dddd, D [de] MMMM [de] YYYY HH:mm"},calendar:{sameDay:"[Hoje às] LT",nextDay:"[Amanhã às] LT",nextWeek:"dddd [às] LT",lastDay:"[Ontem às] LT",lastWeek:function(){return 0===this.day()||6===this.day()?"[Último] dddd [às] LT":"[Última] dddd [às] LT"},sameElse:"L"},relativeTime:{future:"em %s",past:"há %s",s:"segundos",m:"um minuto",mm:"%d minutos",h:"uma hora",hh:"%d horas",d:"um dia",dd:"%d dias",M:"um mês",MM:"%d meses",y:"um ano",yy:"%d anos"},ordinalParse:/\d{1,2}º/,ordinal:"%dº",week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("pt","pt",{closeText:"Fechar",prevText:"Anterior",nextText:"Seguinte",currentText:"Hoje",monthNames:["Janeiro","Fevereiro","Março","Abril","Maio","Junho","Julho","Agosto","Setembro","Outubro","Novembro","Dezembro"],monthNamesShort:["Jan","Fev","Mar","Abr","Mai","Jun","Jul","Ago","Set","Out","Nov","Dez"],dayNames:["Domingo","Segunda-feira","Terça-feira","Quarta-feira","Quinta-feira","Sexta-feira","Sábado"],dayNamesShort:["Dom","Seg","Ter","Qua","Qui","Sex","Sáb"],dayNamesMin:["Dom","Seg","Ter","Qua","Qui","Sex","Sáb"],weekHeader:"Sem",dateFormat:"dd/mm/yy",firstDay:0,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("pt",{buttonText:{month:"Mês",week:"Semana",day:"Dia",list:"Agenda"},allDayText:"Todo o dia",eventLimitText:"mais",noEventsMessage:"Não há eventos para mostrar"})}(),function(){!function(){var e=a.defineLocale("pt-br",{months:"Janeiro_Fevereiro_Março_Abril_Maio_Junho_Julho_Agosto_Setembro_Outubro_Novembro_Dezembro".split("_"),monthsShort:"Jan_Fev_Mar_Abr_Mai_Jun_Jul_Ago_Set_Out_Nov_Dez".split("_"),weekdays:"Domingo_Segunda-feira_Terça-feira_Quarta-feira_Quinta-feira_Sexta-feira_Sábado".split("_"),weekdaysShort:"Dom_Seg_Ter_Qua_Qui_Sex_Sáb".split("_"),weekdaysMin:"Dom_2ª_3ª_4ª_5ª_6ª_Sáb".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D [de] MMMM [de] YYYY",LLL:"D [de] MMMM [de] YYYY [às] HH:mm",LLLL:"dddd, D [de] MMMM [de] YYYY [às] HH:mm"},calendar:{sameDay:"[Hoje às] LT",nextDay:"[Amanhã às] LT",nextWeek:"dddd [às] LT",lastDay:"[Ontem às] LT",lastWeek:function(){return 0===this.day()||6===this.day()?"[Último] dddd [às] LT":"[Última] dddd [às] LT"},sameElse:"L"},relativeTime:{future:"em %s",past:"%s atrás",s:"poucos segundos",m:"um minuto",mm:"%d minutos",h:"uma hora",hh:"%d horas",d:"um dia",dd:"%d dias",M:"um mês",MM:"%d meses",y:"um ano",yy:"%d anos"},ordinalParse:/\d{1,2}º/,ordinal:"%dº"});return e}(),e.fullCalendar.datepickerLocale("pt-br","pt-BR",{closeText:"Fechar",prevText:"&#x3C;Anterior",nextText:"Próximo&#x3E;",currentText:"Hoje",monthNames:["Janeiro","Fevereiro","Março","Abril","Maio","Junho","Julho","Agosto","Setembro","Outubro","Novembro","Dezembro"],monthNamesShort:["Jan","Fev","Mar","Abr","Mai","Jun","Jul","Ago","Set","Out","Nov","Dez"],dayNames:["Domingo","Segunda-feira","Terça-feira","Quarta-feira","Quinta-feira","Sexta-feira","Sábado"],dayNamesShort:["Dom","Seg","Ter","Qua","Qui","Sex","Sáb"],dayNamesMin:["Dom","Seg","Ter","Qua","Qui","Sex","Sáb"],weekHeader:"Sm",dateFormat:"dd/mm/yy",firstDay:0,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("pt-br",{buttonText:{month:"Mês",week:"Semana",day:"Dia",list:"Compromissos"},allDayText:"dia inteiro",eventLimitText:function(e){return"mais +"+e},noEventsMessage:"Não há eventos para mostrar"})}(),function(){!function(){function e(e,a,t){var n={mm:"minute",hh:"ore",dd:"zile",MM:"luni",yy:"ani"},r=" ";return(e%100>=20||e>=100&&e%100===0)&&(r=" de "),e+r+n[t]}var t=a.defineLocale("ro",{months:"ianuarie_februarie_martie_aprilie_mai_iunie_iulie_august_septembrie_octombrie_noiembrie_decembrie".split("_"),monthsShort:"ian._febr._mart._apr._mai_iun._iul._aug._sept._oct._nov._dec.".split("_"),monthsParseExact:!0,weekdays:"duminică_luni_marți_miercuri_joi_vineri_sâmbătă".split("_"),weekdaysShort:"Dum_Lun_Mar_Mie_Joi_Vin_Sâm".split("_"),weekdaysMin:"Du_Lu_Ma_Mi_Jo_Vi_Sâ".split("_"),longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"DD.MM.YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY H:mm",LLLL:"dddd, D MMMM YYYY H:mm"},calendar:{sameDay:"[azi la] LT",nextDay:"[mâine la] LT",nextWeek:"dddd [la] LT",lastDay:"[ieri la] LT",lastWeek:"[fosta] dddd [la] LT",sameElse:"L"},relativeTime:{future:"peste %s",past:"%s în urmă",s:"câteva secunde",m:"un minut",mm:e,h:"o oră",hh:e,d:"o zi",dd:e,M:"o lună",MM:e,y:"un an",yy:e},week:{dow:1,doy:7}});return t}(),e.fullCalendar.datepickerLocale("ro","ro",{closeText:"Închide",prevText:"&#xAB; Luna precedentă",nextText:"Luna următoare &#xBB;",currentText:"Azi",monthNames:["Ianuarie","Februarie","Martie","Aprilie","Mai","Iunie","Iulie","August","Septembrie","Octombrie","Noiembrie","Decembrie"],monthNamesShort:["Ian","Feb","Mar","Apr","Mai","Iun","Iul","Aug","Sep","Oct","Nov","Dec"],dayNames:["Duminică","Luni","Marţi","Miercuri","Joi","Vineri","Sâmbătă"],dayNamesShort:["Dum","Lun","Mar","Mie","Joi","Vin","Sâm"],dayNamesMin:["Du","Lu","Ma","Mi","Jo","Vi","Sâ"],weekHeader:"Săpt",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("ro",{buttonText:{prev:"precedentă",next:"următoare",month:"Lună",week:"Săptămână",day:"Zi",list:"Agendă"},allDayText:"Toată ziua",eventLimitText:function(e){return"+alte "+e},noEventsMessage:"Nu există evenimente de afișat"})}(),function(){!function(){function e(e,a){var t=e.split("_");return a%10===1&&a%100!==11?t[0]:a%10>=2&&a%10<=4&&(a%100<10||a%100>=20)?t[1]:t[2]}function t(a,t,n){var r={mm:t?"минута_минуты_минут":"минуту_минуты_минут",hh:"час_часа_часов",dd:"день_дня_дней",MM:"месяц_месяца_месяцев",yy:"год_года_лет"};return"m"===n?t?"минута":"минуту":a+" "+e(r[n],+a)}var n=[/^янв/i,/^фев/i,/^мар/i,/^апр/i,/^ма[йя]/i,/^июн/i,/^июл/i,/^авг/i,/^сен/i,/^окт/i,/^ноя/i,/^дек/i],r=a.defineLocale("ru",{months:{format:"января_февраля_марта_апреля_мая_июня_июля_августа_сентября_октября_ноября_декабря".split("_"),standalone:"январь_февраль_март_апрель_май_июнь_июль_август_сентябрь_октябрь_ноябрь_декабрь".split("_")},monthsShort:{format:"янв._февр._мар._апр._мая_июня_июля_авг._сент._окт._нояб._дек.".split("_"),standalone:"янв._февр._март_апр._май_июнь_июль_авг._сент._окт._нояб._дек.".split("_")},weekdays:{standalone:"воскресенье_понедельник_вторник_среда_четверг_пятница_суббота".split("_"),format:"воскресенье_понедельник_вторник_среду_четверг_пятницу_субботу".split("_"),isFormat:/\[ ?[Вв] ?(?:прошлую|следующую|эту)? ?\] ?dddd/},weekdaysShort:"вс_пн_вт_ср_чт_пт_сб".split("_"),weekdaysMin:"вс_пн_вт_ср_чт_пт_сб".split("_"),monthsParse:n,longMonthsParse:n,shortMonthsParse:n,monthsRegex:/^(январ[ья]|янв\.?|феврал[ья]|февр?\.?|марта?|мар\.?|апрел[ья]|апр\.?|ма[йя]|июн[ья]|июн\.?|июл[ья]|июл\.?|августа?|авг\.?|сентябр[ья]|сент?\.?|октябр[ья]|окт\.?|ноябр[ья]|нояб?\.?|декабр[ья]|дек\.?)/i,monthsShortRegex:/^(январ[ья]|янв\.?|феврал[ья]|февр?\.?|марта?|мар\.?|апрел[ья]|апр\.?|ма[йя]|июн[ья]|июн\.?|июл[ья]|июл\.?|августа?|авг\.?|сентябр[ья]|сент?\.?|октябр[ья]|окт\.?|ноябр[ья]|нояб?\.?|декабр[ья]|дек\.?)/i,monthsStrictRegex:/^(январ[яь]|феврал[яь]|марта?|апрел[яь]|ма[яй]|июн[яь]|июл[яь]|августа?|сентябр[яь]|октябр[яь]|ноябр[яь]|декабр[яь])/i,monthsShortStrictRegex:/^(янв\.|февр?\.|мар[т.]|апр\.|ма[яй]|июн[ья.]|июл[ья.]|авг\.|сент?\.|окт\.|нояб?\.|дек\.)/i,longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD.MM.YYYY",LL:"D MMMM YYYY г.",LLL:"D MMMM YYYY г., HH:mm",LLLL:"dddd, D MMMM YYYY г., HH:mm"},calendar:{sameDay:"[Сегодня в] LT",nextDay:"[Завтра в] LT",lastDay:"[Вчера в] LT",nextWeek:function(e){if(e.week()===this.week())return 2===this.day()?"[Во] dddd [в] LT":"[В] dddd [в] LT";switch(this.day()){case 0:return"[В следующее] dddd [в] LT";case 1:case 2:case 4:return"[В следующий] dddd [в] LT";case 3:case 5:case 6:return"[В следующую] dddd [в] LT"}},lastWeek:function(e){if(e.week()===this.week())return 2===this.day()?"[Во] dddd [в] LT":"[В] dddd [в] LT";switch(this.day()){case 0:return"[В прошлое] dddd [в] LT";case 1:case 2:case 4:return"[В прошлый] dddd [в] LT";case 3:case 5:case 6:return"[В прошлую] dddd [в] LT"}},sameElse:"L"},relativeTime:{future:"через %s",past:"%s назад",s:"несколько секунд",m:t,mm:t,h:"час",hh:t,d:"день",dd:t,M:"месяц",MM:t,y:"год",yy:t},meridiemParse:/ночи|утра|дня|вечера/i,isPM:function(e){return/^(дня|вечера)$/.test(e)},meridiem:function(e,a,t){return e<4?"ночи":e<12?"утра":e<17?"дня":"вечера"},ordinalParse:/\d{1,2}-(й|го|я)/,ordinal:function(e,a){switch(a){case"M":case"d":case"DDD":return e+"-й";case"D":return e+"-го";case"w":case"W":return e+"-я";default:return e}},week:{dow:1,doy:7}});return r}(),e.fullCalendar.datepickerLocale("ru","ru",{closeText:"Закрыть",prevText:"&#x3C;Пред",nextText:"След&#x3E;",currentText:"Сегодня",monthNames:["Январь","Февраль","Март","Апрель","Май","Июнь","Июль","Август","Сентябрь","Октябрь","Ноябрь","Декабрь"],monthNamesShort:["Янв","Фев","Мар","Апр","Май","Июн","Июл","Авг","Сен","Окт","Ноя","Дек"],dayNames:["воскресенье","понедельник","вторник","среда","четверг","пятница","суббота"],dayNamesShort:["вск","пнд","втр","срд","чтв","птн","сбт"],dayNamesMin:["Вс","Пн","Вт","Ср","Чт","Пт","Сб"],weekHeader:"Нед",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("ru",{buttonText:{month:"Месяц",week:"Неделя",day:"День",list:"Повестка дня"},allDayText:"Весь день",eventLimitText:function(e){return"+ ещё "+e},noEventsMessage:"Нет событий для отображения"})}(),function(){!function(){function e(e){return e>1&&e<5}function t(a,t,n,r){var s=a+" ";switch(n){case"s":return t||r?"pár sekúnd":"pár sekundami";case"m":return t?"minúta":r?"minútu":"minútou";case"mm":return t||r?s+(e(a)?"minúty":"minút"):s+"minútami";case"h":return t?"hodina":r?"hodinu":"hodinou";case"hh":return t||r?s+(e(a)?"hodiny":"hodín"):s+"hodinami";case"d":return t||r?"deň":"dňom";case"dd":return t||r?s+(e(a)?"dni":"dní"):s+"dňami";case"M":return t||r?"mesiac":"mesiacom";case"MM":return t||r?s+(e(a)?"mesiace":"mesiacov"):s+"mesiacmi";case"y":return t||r?"rok":"rokom";case"yy":return t||r?s+(e(a)?"roky":"rokov"):s+"rokmi"}}var n="január_február_marec_apríl_máj_jún_júl_august_september_október_november_december".split("_"),r="jan_feb_mar_apr_máj_jún_júl_aug_sep_okt_nov_dec".split("_"),s=a.defineLocale("sk",{months:n,monthsShort:r,weekdays:"nedeľa_pondelok_utorok_streda_štvrtok_piatok_sobota".split("_"),weekdaysShort:"ne_po_ut_st_št_pi_so".split("_"),weekdaysMin:"ne_po_ut_st_št_pi_so".split("_"),longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"DD.MM.YYYY",LL:"D. MMMM YYYY",LLL:"D. MMMM YYYY H:mm",LLLL:"dddd D. MMMM YYYY H:mm"},calendar:{sameDay:"[dnes o] LT",nextDay:"[zajtra o] LT",nextWeek:function(){switch(this.day()){case 0:return"[v nedeľu o] LT";case 1:case 2:return"[v] dddd [o] LT";case 3:return"[v stredu o] LT";case 4:return"[vo štvrtok o] LT";case 5:return"[v piatok o] LT";case 6:return"[v sobotu o] LT"}},lastDay:"[včera o] LT",lastWeek:function(){switch(this.day()){case 0:return"[minulú nedeľu o] LT";case 1:case 2:return"[minulý] dddd [o] LT";case 3:return"[minulú stredu o] LT";case 4:case 5:return"[minulý] dddd [o] LT";case 6:return"[minulú sobotu o] LT"}},sameElse:"L"},relativeTime:{future:"za %s",past:"pred %s",s:t,m:t,mm:t,h:t,hh:t,d:t,dd:t,M:t,MM:t,y:t,yy:t},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:4}});return s}(),e.fullCalendar.datepickerLocale("sk","sk",{closeText:"Zavrieť",prevText:"&#x3C;Predchádzajúci",nextText:"Nasledujúci&#x3E;",currentText:"Dnes",monthNames:["január","február","marec","apríl","máj","jún","júl","august","september","október","november","december"],monthNamesShort:["Jan","Feb","Mar","Apr","Máj","Jún","Júl","Aug","Sep","Okt","Nov","Dec"],dayNames:["nedeľa","pondelok","utorok","streda","štvrtok","piatok","sobota"],dayNamesShort:["Ned","Pon","Uto","Str","Štv","Pia","Sob"],dayNamesMin:["Ne","Po","Ut","St","Št","Pia","So"],weekHeader:"Ty",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("sk",{buttonText:{month:"Mesiac",week:"Týždeň",day:"Deň",list:"Rozvrh"},allDayText:"Celý deň",eventLimitText:function(e){return"+ďalšie: "+e},noEventsMessage:"Žiadne akcie na zobrazenie"})}(),function(){!function(){function e(e,a,t,n){var r=e+" ";switch(t){case"s":return a||n?"nekaj sekund":"nekaj sekundami";case"m":return a?"ena minuta":"eno minuto";case"mm":return r+=1===e?a?"minuta":"minuto":2===e?a||n?"minuti":"minutama":e<5?a||n?"minute":"minutami":a||n?"minut":"minutami";case"h":return a?"ena ura":"eno uro";case"hh":return r+=1===e?a?"ura":"uro":2===e?a||n?"uri":"urama":e<5?a||n?"ure":"urami":a||n?"ur":"urami";case"d":return a||n?"en dan":"enim dnem";case"dd":return r+=1===e?a||n?"dan":"dnem":2===e?a||n?"dni":"dnevoma":a||n?"dni":"dnevi";case"M":return a||n?"en mesec":"enim mesecem";case"MM":return r+=1===e?a||n?"mesec":"mesecem":2===e?a||n?"meseca":"mesecema":e<5?a||n?"mesece":"meseci":a||n?"mesecev":"meseci";case"y":return a||n?"eno leto":"enim letom";case"yy":return r+=1===e?a||n?"leto":"letom":2===e?a||n?"leti":"letoma":e<5?a||n?"leta":"leti":a||n?"let":"leti"}}var t=a.defineLocale("sl",{months:"januar_februar_marec_april_maj_junij_julij_avgust_september_oktober_november_december".split("_"),monthsShort:"jan._feb._mar._apr._maj._jun._jul._avg._sep._okt._nov._dec.".split("_"),monthsParseExact:!0,weekdays:"nedelja_ponedeljek_torek_sreda_četrtek_petek_sobota".split("_"),weekdaysShort:"ned._pon._tor._sre._čet._pet._sob.".split("_"),weekdaysMin:"ne_po_to_sr_če_pe_so".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"DD.MM.YYYY",LL:"D. MMMM YYYY",LLL:"D. MMMM YYYY H:mm",LLLL:"dddd, D. MMMM YYYY H:mm"},calendar:{sameDay:"[danes ob] LT",nextDay:"[jutri ob] LT",nextWeek:function(){switch(this.day()){case 0:return"[v] [nedeljo] [ob] LT";case 3:return"[v] [sredo] [ob] LT";case 6:return"[v] [soboto] [ob] LT";case 1:case 2:case 4:case 5:return"[v] dddd [ob] LT"}},lastDay:"[včeraj ob] LT",lastWeek:function(){switch(this.day()){case 0:return"[prejšnjo] [nedeljo] [ob] LT";case 3:return"[prejšnjo] [sredo] [ob] LT";case 6:return"[prejšnjo] [soboto] [ob] LT";case 1:case 2:case 4:case 5:return"[prejšnji] dddd [ob] LT"}},sameElse:"L"},relativeTime:{future:"čez %s",past:"pred %s",s:e,m:e,mm:e,h:e,hh:e,d:e,dd:e,M:e,MM:e,y:e,yy:e},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:7}});return t}(),e.fullCalendar.datepickerLocale("sl","sl",{closeText:"Zapri",prevText:"&#x3C;Prejšnji",nextText:"Naslednji&#x3E;",currentText:"Trenutni",monthNames:["Januar","Februar","Marec","April","Maj","Junij","Julij","Avgust","September","Oktober","November","December"],monthNamesShort:["Jan","Feb","Mar","Apr","Maj","Jun","Jul","Avg","Sep","Okt","Nov","Dec"],dayNames:["Nedelja","Ponedeljek","Torek","Sreda","Četrtek","Petek","Sobota"],dayNamesShort:["Ned","Pon","Tor","Sre","Čet","Pet","Sob"],dayNamesMin:["Ne","Po","To","Sr","Če","Pe","So"],weekHeader:"Teden",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("sl",{buttonText:{month:"Mesec",week:"Teden",day:"Dan",list:"Dnevni red"},allDayText:"Ves dan",eventLimitText:"več",noEventsMessage:"Ni dogodkov za prikaz"})}(),function(){!function(){var e={words:{m:["jedan minut","jedne minute"],mm:["minut","minute","minuta"],h:["jedan sat","jednog sata"],hh:["sat","sata","sati"],dd:["dan","dana","dana"],MM:["mesec","meseca","meseci"],yy:["godina","godine","godina"]},correctGrammaticalCase:function(e,a){return 1===e?a[0]:e>=2&&e<=4?a[1]:a[2]},translate:function(a,t,n){var r=e.words[n];return 1===n.length?t?r[0]:r[1]:a+" "+e.correctGrammaticalCase(a,r)}},t=a.defineLocale("sr",{months:"januar_februar_mart_april_maj_jun_jul_avgust_septembar_oktobar_novembar_decembar".split("_"),monthsShort:"jan._feb._mar._apr._maj_jun_jul_avg._sep._okt._nov._dec.".split("_"),monthsParseExact:!0,weekdays:"nedelja_ponedeljak_utorak_sreda_četvrtak_petak_subota".split("_"),weekdaysShort:"ned._pon._uto._sre._čet._pet._sub.".split("_"),weekdaysMin:"ne_po_ut_sr_če_pe_su".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"DD.MM.YYYY",LL:"D. MMMM YYYY",LLL:"D. MMMM YYYY H:mm",LLLL:"dddd, D. MMMM YYYY H:mm"},calendar:{sameDay:"[danas u] LT",nextDay:"[sutra u] LT",nextWeek:function(){switch(this.day()){case 0:return"[u] [nedelju] [u] LT";case 3:return"[u] [sredu] [u] LT";case 6:return"[u] [subotu] [u] LT";case 1:case 2:case 4:case 5:return"[u] dddd [u] LT"}},lastDay:"[juče u] LT",lastWeek:function(){var e=["[prošle] [nedelje] [u] LT","[prošlog] [ponedeljka] [u] LT","[prošlog] [utorka] [u] LT","[prošle] [srede] [u] LT","[prošlog] [četvrtka] [u] LT","[prošlog] [petka] [u] LT","[prošle] [subote] [u] LT"];return e[this.day()]},sameElse:"L"},relativeTime:{future:"za %s",past:"pre %s",s:"nekoliko sekundi",m:e.translate,mm:e.translate,h:e.translate,hh:e.translate,d:"dan",dd:e.translate,M:"mesec",MM:e.translate,y:"godinu",yy:e.translate},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:7}});return t}(),e.fullCalendar.datepickerLocale("sr","sr",{closeText:"Затвори",prevText:"&#x3C;",nextText:"&#x3E;",currentText:"Данас",monthNames:["Јануар","Фебруар","Март","Април","Мај","Јун","Јул","Август","Септембар","Октобар","Новембар","Децембар"],monthNamesShort:["Јан","Феб","Мар","Апр","Мај","Јун","Јул","Авг","Сеп","Окт","Нов","Дец"],dayNames:["Недеља","Понедељак","Уторак","Среда","Четвртак","Петак","Субота"],dayNamesShort:["Нед","Пон","Уто","Сре","Чет","Пет","Суб"],dayNamesMin:["Не","По","Ут","Ср","Че","Пе","Су"],weekHeader:"Сед",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("sr",{buttonText:{month:"Месец",week:"Недеља",day:"Дан",list:"Планер"},allDayText:"Цео дан",eventLimitText:function(e){return"+ још "+e},noEventsMessage:"Нема догађаја за приказ"})}(),function(){!function(){var e={words:{m:["један минут","једне минуте"],mm:["минут","минуте","минута"],h:["један сат","једног сата"],hh:["сат","сата","сати"],dd:["дан","дана","дана"],MM:["месец","месеца","месеци"],yy:["година","године","година"]},correctGrammaticalCase:function(e,a){return 1===e?a[0]:e>=2&&e<=4?a[1]:a[2]},translate:function(a,t,n){var r=e.words[n];return 1===n.length?t?r[0]:r[1]:a+" "+e.correctGrammaticalCase(a,r)}},t=a.defineLocale("sr-cyrl",{months:"јануар_фебруар_март_април_мај_јун_јул_август_септембар_октобар_новембар_децембар".split("_"),monthsShort:"јан._феб._мар._апр._мај_јун_јул_авг._сеп._окт._нов._дец.".split("_"),monthsParseExact:!0,weekdays:"недеља_понедељак_уторак_среда_четвртак_петак_субота".split("_"),weekdaysShort:"нед._пон._уто._сре._чет._пет._суб.".split("_"),weekdaysMin:"не_по_ут_ср_че_пе_су".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"DD.MM.YYYY",LL:"D. MMMM YYYY",LLL:"D. MMMM YYYY H:mm",LLLL:"dddd, D. MMMM YYYY H:mm"},calendar:{sameDay:"[данас у] LT",nextDay:"[сутра у] LT",nextWeek:function(){switch(this.day()){case 0:return"[у] [недељу] [у] LT";case 3:return"[у] [среду] [у] LT";case 6:return"[у] [суботу] [у] LT";case 1:case 2:case 4:case 5:return"[у] dddd [у] LT"}},lastDay:"[јуче у] LT",lastWeek:function(){var e=["[прошле] [недеље] [у] LT","[прошлог] [понедељка] [у] LT","[прошлог] [уторка] [у] LT","[прошле] [среде] [у] LT","[прошлог] [четвртка] [у] LT","[прошлог] [петка] [у] LT","[прошле] [суботе] [у] LT"];return e[this.day()]},sameElse:"L"},relativeTime:{future:"за %s",past:"пре %s",s:"неколико секунди",m:e.translate,mm:e.translate,h:e.translate,hh:e.translate,d:"дан",dd:e.translate,M:"месец",MM:e.translate,y:"годину",yy:e.translate},ordinalParse:/\d{1,2}\./,ordinal:"%d.",week:{dow:1,doy:7}});return t}(),e.fullCalendar.datepickerLocale("sr-cyrl","sr",{closeText:"Затвори",prevText:"&#x3C;",nextText:"&#x3E;",currentText:"Данас",monthNames:["Јануар","Фебруар","Март","Април","Мај","Јун","Јул","Август","Септембар","Октобар","Новембар","Децембар"],monthNamesShort:["Јан","Феб","Мар","Апр","Мај","Јун","Јул","Авг","Сеп","Окт","Нов","Дец"],dayNames:["Недеља","Понедељак","Уторак","Среда","Четвртак","Петак","Субота"],dayNamesShort:["Нед","Пон","Уто","Сре","Чет","Пет","Суб"],dayNamesMin:["Не","По","Ут","Ср","Че","Пе","Су"],weekHeader:"Сед",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("sr-cyrl",{buttonText:{month:"Месец",week:"Недеља",day:"Дан",list:"Планер"},allDayText:"Цео дан",eventLimitText:function(e){return"+ још "+e},noEventsMessage:"Нема догађаја за приказ"})}(),function(){!function(){var e=a.defineLocale("sv",{months:"januari_februari_mars_april_maj_juni_juli_augusti_september_oktober_november_december".split("_"),monthsShort:"jan_feb_mar_apr_maj_jun_jul_aug_sep_okt_nov_dec".split("_"),weekdays:"söndag_måndag_tisdag_onsdag_torsdag_fredag_lördag".split("_"),weekdaysShort:"sön_mån_tis_ons_tor_fre_lör".split("_"),weekdaysMin:"sö_må_ti_on_to_fr_lö".split("_"),longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"YYYY-MM-DD",LL:"D MMMM YYYY",LLL:"D MMMM YYYY [kl.] HH:mm",LLLL:"dddd D MMMM YYYY [kl.] HH:mm",lll:"D MMM YYYY HH:mm",llll:"ddd D MMM YYYY HH:mm"},calendar:{sameDay:"[Idag] LT",nextDay:"[Imorgon] LT",lastDay:"[Igår] LT",nextWeek:"[På] dddd LT",lastWeek:"[I] dddd[s] LT",sameElse:"L"},relativeTime:{future:"om %s",past:"för %s sedan",s:"några sekunder",m:"en minut",mm:"%d minuter",h:"en timme",hh:"%d timmar",d:"en dag",dd:"%d dagar",M:"en månad",MM:"%d månader",y:"ett år",yy:"%d år"},ordinalParse:/\d{1,2}(e|a)/,ordinal:function(e){var a=e%10,t=1===~~(e%100/10)?"e":1===a?"a":2===a?"a":"e";return e+t},week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("sv","sv",{closeText:"Stäng",prevText:"&#xAB;Förra",nextText:"Nästa&#xBB;",currentText:"Idag",monthNames:["Januari","Februari","Mars","April","Maj","Juni","Juli","Augusti","September","Oktober","November","December"],monthNamesShort:["Jan","Feb","Mar","Apr","Maj","Jun","Jul","Aug","Sep","Okt","Nov","Dec"],dayNamesShort:["Sön","Mån","Tis","Ons","Tor","Fre","Lör"],dayNames:["Söndag","Måndag","Tisdag","Onsdag","Torsdag","Fredag","Lördag"],dayNamesMin:["Sö","Må","Ti","On","To","Fr","Lö"],weekHeader:"Ve",dateFormat:"yy-mm-dd",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("sv",{buttonText:{month:"Månad",week:"Vecka",day:"Dag",list:"Program"},allDayText:"Heldag",eventLimitText:"till",noEventsMessage:"Inga händelser att visa"})}(),function(){!function(){var e=a.defineLocale("th",{months:"มกราคม_กุมภาพันธ์_มีนาคม_เมษายน_พฤษภาคม_มิถุนายน_กรกฎาคม_สิงหาคม_กันยายน_ตุลาคม_พฤศจิกายน_ธันวาคม".split("_"),monthsShort:"ม.ค._ก.พ._มี.ค._เม.ย._พ.ค._มิ.ย._ก.ค._ส.ค._ก.ย._ต.ค._พ.ย._ธ.ค.".split("_"),monthsParseExact:!0,weekdays:"อาทิตย์_จันทร์_อังคาร_พุธ_พฤหัสบดี_ศุกร์_เสาร์".split("_"),weekdaysShort:"อาทิตย์_จันทร์_อังคาร_พุธ_พฤหัส_ศุกร์_เสาร์".split("_"),weekdaysMin:"อา._จ._อ._พ._พฤ._ศ._ส.".split("_"),weekdaysParseExact:!0,longDateFormat:{LT:"H:mm",LTS:"H:mm:ss",L:"YYYY/MM/DD",LL:"D MMMM YYYY",LLL:"D MMMM YYYY เวลา H:mm",LLLL:"วันddddที่ D MMMM YYYY เวลา H:mm"},meridiemParse:/ก่อนเที่ยง|หลังเที่ยง/,isPM:function(e){return"หลังเที่ยง"===e},meridiem:function(e,a,t){return e<12?"ก่อนเที่ยง":"หลังเที่ยง"},calendar:{sameDay:"[วันนี้ เวลา] LT",nextDay:"[พรุ่งนี้ เวลา] LT",nextWeek:"dddd[หน้า เวลา] LT",lastDay:"[เมื่อวานนี้ เวลา] LT",lastWeek:"[วัน]dddd[ที่แล้ว เวลา] LT",sameElse:"L"},relativeTime:{future:"อีก %s",past:"%sที่แล้ว",s:"ไม่กี่วินาที",m:"1 นาที",mm:"%d นาที",h:"1 ชั่วโมง",hh:"%d ชั่วโมง",d:"1 วัน",dd:"%d วัน",M:"1 เดือน",MM:"%d เดือน",
+y:"1 ปี",yy:"%d ปี"}});return e}(),e.fullCalendar.datepickerLocale("th","th",{closeText:"ปิด",prevText:"&#xAB;&#xA0;ย้อน",nextText:"ถัดไป&#xA0;&#xBB;",currentText:"วันนี้",monthNames:["มกราคม","กุมภาพันธ์","มีนาคม","เมษายน","พฤษภาคม","มิถุนายน","กรกฎาคม","สิงหาคม","กันยายน","ตุลาคม","พฤศจิกายน","ธันวาคม"],monthNamesShort:["ม.ค.","ก.พ.","มี.ค.","เม.ย.","พ.ค.","มิ.ย.","ก.ค.","ส.ค.","ก.ย.","ต.ค.","พ.ย.","ธ.ค."],dayNames:["อาทิตย์","จันทร์","อังคาร","พุธ","พฤหัสบดี","ศุกร์","เสาร์"],dayNamesShort:["อา.","จ.","อ.","พ.","พฤ.","ศ.","ส."],dayNamesMin:["อา.","จ.","อ.","พ.","พฤ.","ศ.","ส."],weekHeader:"Wk",dateFormat:"dd/mm/yy",firstDay:0,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("th",{buttonText:{month:"เดือน",week:"สัปดาห์",day:"วัน",list:"แผนงาน"},allDayText:"ตลอดวัน",eventLimitText:"เพิ่มเติม",noEventsMessage:"ไม่มีกิจกรรมที่จะแสดง"})}(),function(){!function(){var e={1:"'inci",5:"'inci",8:"'inci",70:"'inci",80:"'inci",2:"'nci",7:"'nci",20:"'nci",50:"'nci",3:"'üncü",4:"'üncü",100:"'üncü",6:"'ncı",9:"'uncu",10:"'uncu",30:"'uncu",60:"'ıncı",90:"'ıncı"},t=a.defineLocale("tr",{months:"Ocak_Şubat_Mart_Nisan_Mayıs_Haziran_Temmuz_Ağustos_Eylül_Ekim_Kasım_Aralık".split("_"),monthsShort:"Oca_Şub_Mar_Nis_May_Haz_Tem_Ağu_Eyl_Eki_Kas_Ara".split("_"),weekdays:"Pazar_Pazartesi_Salı_Çarşamba_Perşembe_Cuma_Cumartesi".split("_"),weekdaysShort:"Paz_Pts_Sal_Çar_Per_Cum_Cts".split("_"),weekdaysMin:"Pz_Pt_Sa_Ça_Pe_Cu_Ct".split("_"),longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD.MM.YYYY",LL:"D MMMM YYYY",LLL:"D MMMM YYYY HH:mm",LLLL:"dddd, D MMMM YYYY HH:mm"},calendar:{sameDay:"[bugün saat] LT",nextDay:"[yarın saat] LT",nextWeek:"[haftaya] dddd [saat] LT",lastDay:"[dün] LT",lastWeek:"[geçen hafta] dddd [saat] LT",sameElse:"L"},relativeTime:{future:"%s sonra",past:"%s önce",s:"birkaç saniye",m:"bir dakika",mm:"%d dakika",h:"bir saat",hh:"%d saat",d:"bir gün",dd:"%d gün",M:"bir ay",MM:"%d ay",y:"bir yıl",yy:"%d yıl"},ordinalParse:/\d{1,2}'(inci|nci|üncü|ncı|uncu|ıncı)/,ordinal:function(a){if(0===a)return a+"'ıncı";var t=a%10,n=a%100-t,r=a>=100?100:null;return a+(e[t]||e[n]||e[r])},week:{dow:1,doy:7}});return t}(),e.fullCalendar.datepickerLocale("tr","tr",{closeText:"kapat",prevText:"&#x3C;geri",nextText:"ileri&#x3e",currentText:"bugün",monthNames:["Ocak","Şubat","Mart","Nisan","Mayıs","Haziran","Temmuz","Ağustos","Eylül","Ekim","Kasım","Aralık"],monthNamesShort:["Oca","Şub","Mar","Nis","May","Haz","Tem","Ağu","Eyl","Eki","Kas","Ara"],dayNames:["Pazar","Pazartesi","Salı","Çarşamba","Perşembe","Cuma","Cumartesi"],dayNamesShort:["Pz","Pt","Sa","Ça","Pe","Cu","Ct"],dayNamesMin:["Pz","Pt","Sa","Ça","Pe","Cu","Ct"],weekHeader:"Hf",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("tr",{buttonText:{next:"ileri",month:"Ay",week:"Hafta",day:"Gün",list:"Ajanda"},allDayText:"Tüm gün",eventLimitText:"daha fazla",noEventsMessage:"Herhangi bir etkinlik görüntülemek için"})}(),function(){!function(){function e(e,a){var t=e.split("_");return a%10===1&&a%100!==11?t[0]:a%10>=2&&a%10<=4&&(a%100<10||a%100>=20)?t[1]:t[2]}function t(a,t,n){var r={mm:t?"хвилина_хвилини_хвилин":"хвилину_хвилини_хвилин",hh:t?"година_години_годин":"годину_години_годин",dd:"день_дні_днів",MM:"місяць_місяці_місяців",yy:"рік_роки_років"};return"m"===n?t?"хвилина":"хвилину":"h"===n?t?"година":"годину":a+" "+e(r[n],+a)}function n(e,a){var t={nominative:"неділя_понеділок_вівторок_середа_четвер_п’ятниця_субота".split("_"),accusative:"неділю_понеділок_вівторок_середу_четвер_п’ятницю_суботу".split("_"),genitive:"неділі_понеділка_вівторка_середи_четверга_п’ятниці_суботи".split("_")},n=/(\[[ВвУу]\]) ?dddd/.test(a)?"accusative":/\[?(?:минулої|наступної)? ?\] ?dddd/.test(a)?"genitive":"nominative";return t[n][e.day()]}function r(e){return function(){return e+"о"+(11===this.hours()?"б":"")+"] LT"}}var s=a.defineLocale("uk",{months:{format:"січня_лютого_березня_квітня_травня_червня_липня_серпня_вересня_жовтня_листопада_грудня".split("_"),standalone:"січень_лютий_березень_квітень_травень_червень_липень_серпень_вересень_жовтень_листопад_грудень".split("_")},monthsShort:"січ_лют_бер_квіт_трав_черв_лип_серп_вер_жовт_лист_груд".split("_"),weekdays:n,weekdaysShort:"нд_пн_вт_ср_чт_пт_сб".split("_"),weekdaysMin:"нд_пн_вт_ср_чт_пт_сб".split("_"),longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD.MM.YYYY",LL:"D MMMM YYYY р.",LLL:"D MMMM YYYY р., HH:mm",LLLL:"dddd, D MMMM YYYY р., HH:mm"},calendar:{sameDay:r("[Сьогодні "),nextDay:r("[Завтра "),lastDay:r("[Вчора "),nextWeek:r("[У] dddd ["),lastWeek:function(){switch(this.day()){case 0:case 3:case 5:case 6:return r("[Минулої] dddd [").call(this);case 1:case 2:case 4:return r("[Минулого] dddd [").call(this)}},sameElse:"L"},relativeTime:{future:"за %s",past:"%s тому",s:"декілька секунд",m:t,mm:t,h:"годину",hh:t,d:"день",dd:t,M:"місяць",MM:t,y:"рік",yy:t},meridiemParse:/ночі|ранку|дня|вечора/,isPM:function(e){return/^(дня|вечора)$/.test(e)},meridiem:function(e,a,t){return e<4?"ночі":e<12?"ранку":e<17?"дня":"вечора"},ordinalParse:/\d{1,2}-(й|го)/,ordinal:function(e,a){switch(a){case"M":case"d":case"DDD":case"w":case"W":return e+"-й";case"D":return e+"-го";default:return e}},week:{dow:1,doy:7}});return s}(),e.fullCalendar.datepickerLocale("uk","uk",{closeText:"Закрити",prevText:"&#x3C;",nextText:"&#x3E;",currentText:"Сьогодні",monthNames:["Січень","Лютий","Березень","Квітень","Травень","Червень","Липень","Серпень","Вересень","Жовтень","Листопад","Грудень"],monthNamesShort:["Січ","Лют","Бер","Кві","Тра","Чер","Лип","Сер","Вер","Жов","Лис","Гру"],dayNames:["неділя","понеділок","вівторок","середа","четвер","п’ятниця","субота"],dayNamesShort:["нед","пнд","вів","срд","чтв","птн","сбт"],dayNamesMin:["Нд","Пн","Вт","Ср","Чт","Пт","Сб"],weekHeader:"Тиж",dateFormat:"dd.mm.yy",firstDay:1,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("uk",{buttonText:{month:"Місяць",week:"Тиждень",day:"День",list:"Порядок денний"},allDayText:"Увесь день",eventLimitText:function(e){return"+ще "+e+"..."},noEventsMessage:"Немає подій для відображення"})}(),function(){!function(){var e=a.defineLocale("vi",{months:"tháng 1_tháng 2_tháng 3_tháng 4_tháng 5_tháng 6_tháng 7_tháng 8_tháng 9_tháng 10_tháng 11_tháng 12".split("_"),monthsShort:"Th01_Th02_Th03_Th04_Th05_Th06_Th07_Th08_Th09_Th10_Th11_Th12".split("_"),monthsParseExact:!0,weekdays:"chủ nhật_thứ hai_thứ ba_thứ tư_thứ năm_thứ sáu_thứ bảy".split("_"),weekdaysShort:"CN_T2_T3_T4_T5_T6_T7".split("_"),weekdaysMin:"CN_T2_T3_T4_T5_T6_T7".split("_"),weekdaysParseExact:!0,meridiemParse:/sa|ch/i,isPM:function(e){return/^ch$/i.test(e)},meridiem:function(e,a,t){return e<12?t?"sa":"SA":t?"ch":"CH"},longDateFormat:{LT:"HH:mm",LTS:"HH:mm:ss",L:"DD/MM/YYYY",LL:"D MMMM [năm] YYYY",LLL:"D MMMM [năm] YYYY HH:mm",LLLL:"dddd, D MMMM [năm] YYYY HH:mm",l:"DD/M/YYYY",ll:"D MMM YYYY",lll:"D MMM YYYY HH:mm",llll:"ddd, D MMM YYYY HH:mm"},calendar:{sameDay:"[Hôm nay lúc] LT",nextDay:"[Ngày mai lúc] LT",nextWeek:"dddd [tuần tới lúc] LT",lastDay:"[Hôm qua lúc] LT",lastWeek:"dddd [tuần rồi lúc] LT",sameElse:"L"},relativeTime:{future:"%s tới",past:"%s trước",s:"vài giây",m:"một phút",mm:"%d phút",h:"một giờ",hh:"%d giờ",d:"một ngày",dd:"%d ngày",M:"một tháng",MM:"%d tháng",y:"một năm",yy:"%d năm"},ordinalParse:/\d{1,2}/,ordinal:function(e){return e},week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("vi","vi",{closeText:"Đóng",prevText:"&#x3C;Trước",nextText:"Tiếp&#x3E;",currentText:"Hôm nay",monthNames:["Tháng Một","Tháng Hai","Tháng Ba","Tháng Tư","Tháng Năm","Tháng Sáu","Tháng Bảy","Tháng Tám","Tháng Chín","Tháng Mười","Tháng Mười Một","Tháng Mười Hai"],monthNamesShort:["Tháng 1","Tháng 2","Tháng 3","Tháng 4","Tháng 5","Tháng 6","Tháng 7","Tháng 8","Tháng 9","Tháng 10","Tháng 11","Tháng 12"],dayNames:["Chủ Nhật","Thứ Hai","Thứ Ba","Thứ Tư","Thứ Năm","Thứ Sáu","Thứ Bảy"],dayNamesShort:["CN","T2","T3","T4","T5","T6","T7"],dayNamesMin:["CN","T2","T3","T4","T5","T6","T7"],weekHeader:"Tu",dateFormat:"dd/mm/yy",firstDay:0,isRTL:!1,showMonthAfterYear:!1,yearSuffix:""}),e.fullCalendar.locale("vi",{buttonText:{month:"Tháng",week:"Tuần",day:"Ngày",list:"Lịch biểu"},allDayText:"Cả ngày",eventLimitText:function(e){return"+ thêm "+e},noEventsMessage:"Không có sự kiện để hiển thị"})}(),function(){!function(){var e=a.defineLocale("zh-cn",{months:"一月_二月_三月_四月_五月_六月_七月_八月_九月_十月_十一月_十二月".split("_"),monthsShort:"1月_2月_3月_4月_5月_6月_7月_8月_9月_10月_11月_12月".split("_"),weekdays:"星期日_星期一_星期二_星期三_星期四_星期五_星期六".split("_"),weekdaysShort:"周日_周一_周二_周三_周四_周五_周六".split("_"),weekdaysMin:"日_一_二_三_四_五_六".split("_"),longDateFormat:{LT:"Ah点mm分",LTS:"Ah点m分s秒",L:"YYYY-MM-DD",LL:"YYYY年MMMD日",LLL:"YYYY年MMMD日Ah点mm分",LLLL:"YYYY年MMMD日ddddAh点mm分",l:"YYYY-MM-DD",ll:"YYYY年MMMD日",lll:"YYYY年MMMD日Ah点mm分",llll:"YYYY年MMMD日ddddAh点mm分"},meridiemParse:/凌晨|早上|上午|中午|下午|晚上/,meridiemHour:function(e,a){return 12===e&&(e=0),"凌晨"===a||"早上"===a||"上午"===a?e:"下午"===a||"晚上"===a?e+12:e>=11?e:e+12},meridiem:function(e,a,t){var n=100*e+a;return n<600?"凌晨":n<900?"早上":n<1130?"上午":n<1230?"中午":n<1800?"下午":"晚上"},calendar:{sameDay:function(){return 0===this.minutes()?"[今天]Ah[点整]":"[今天]LT"},nextDay:function(){return 0===this.minutes()?"[明天]Ah[点整]":"[明天]LT"},lastDay:function(){return 0===this.minutes()?"[昨天]Ah[点整]":"[昨天]LT"},nextWeek:function(){var e,t;return e=a().startOf("week"),t=this.diff(e,"days")>=7?"[下]":"[本]",0===this.minutes()?t+"dddAh点整":t+"dddAh点mm"},lastWeek:function(){var e,t;return e=a().startOf("week"),t=this.unix()<e.unix()?"[上]":"[本]",0===this.minutes()?t+"dddAh点整":t+"dddAh点mm"},sameElse:"LL"},ordinalParse:/\d{1,2}(日|月|周)/,ordinal:function(e,a){switch(a){case"d":case"D":case"DDD":return e+"日";case"M":return e+"月";case"w":case"W":return e+"周";default:return e}},relativeTime:{future:"%s内",past:"%s前",s:"几秒",m:"1 分钟",mm:"%d 分钟",h:"1 小时",hh:"%d 小时",d:"1 天",dd:"%d 天",M:"1 个月",MM:"%d 个月",y:"1 年",yy:"%d 年"},week:{dow:1,doy:4}});return e}(),e.fullCalendar.datepickerLocale("zh-cn","zh-CN",{closeText:"关闭",prevText:"&#x3C;上月",nextText:"下月&#x3E;",currentText:"今天",monthNames:["一月","二月","三月","四月","五月","六月","七月","八月","九月","十月","十一月","十二月"],monthNamesShort:["一月","二月","三月","四月","五月","六月","七月","八月","九月","十月","十一月","十二月"],dayNames:["星期日","星期一","星期二","星期三","星期四","星期五","星期六"],dayNamesShort:["周日","周一","周二","周三","周四","周五","周六"],dayNamesMin:["日","一","二","三","四","五","六"],weekHeader:"周",dateFormat:"yy-mm-dd",firstDay:1,isRTL:!1,showMonthAfterYear:!0,yearSuffix:"年"}),e.fullCalendar.locale("zh-cn",{buttonText:{month:"月",week:"周",day:"日",list:"日程"},allDayText:"全天",eventLimitText:function(e){return"另外 "+e+" 个"},noEventsMessage:"没有事件显示"})}(),function(){!function(){var e=a.defineLocale("zh-tw",{months:"一月_二月_三月_四月_五月_六月_七月_八月_九月_十月_十一月_十二月".split("_"),monthsShort:"1月_2月_3月_4月_5月_6月_7月_8月_9月_10月_11月_12月".split("_"),weekdays:"星期日_星期一_星期二_星期三_星期四_星期五_星期六".split("_"),weekdaysShort:"週日_週一_週二_週三_週四_週五_週六".split("_"),weekdaysMin:"日_一_二_三_四_五_六".split("_"),longDateFormat:{LT:"Ah點mm分",LTS:"Ah點m分s秒",L:"YYYY年MMMD日",LL:"YYYY年MMMD日",LLL:"YYYY年MMMD日Ah點mm分",LLLL:"YYYY年MMMD日ddddAh點mm分",l:"YYYY年MMMD日",ll:"YYYY年MMMD日",lll:"YYYY年MMMD日Ah點mm分",llll:"YYYY年MMMD日ddddAh點mm分"},meridiemParse:/凌晨|早上|上午|中午|下午|晚上/,meridiemHour:function(e,a){return 12===e&&(e=0),"凌晨"===a||"早上"===a||"上午"===a?e:"中午"===a?e>=11?e:e+12:"下午"===a||"晚上"===a?e+12:void 0},meridiem:function(e,a,t){var n=100*e+a;return n<600?"凌晨":n<900?"早上":n<1130?"上午":n<1230?"中午":n<1800?"下午":"晚上"},calendar:{sameDay:"[今天]LT",nextDay:"[明天]LT",nextWeek:"[下]ddddLT",lastDay:"[昨天]LT",lastWeek:"[上]ddddLT",sameElse:"L"},ordinalParse:/\d{1,2}(日|月|週)/,ordinal:function(e,a){switch(a){case"d":case"D":case"DDD":return e+"日";case"M":return e+"月";case"w":case"W":return e+"週";default:return e}},relativeTime:{future:"%s內",past:"%s前",s:"幾秒",m:"1 分鐘",mm:"%d 分鐘",h:"1 小時",hh:"%d 小時",d:"1 天",dd:"%d 天",M:"1 個月",MM:"%d 個月",y:"1 年",yy:"%d 年"}});return e}(),e.fullCalendar.datepickerLocale("zh-tw","zh-TW",{closeText:"關閉",prevText:"&#x3C;上月",nextText:"下月&#x3E;",currentText:"今天",monthNames:["一月","二月","三月","四月","五月","六月","七月","八月","九月","十月","十一月","十二月"],monthNamesShort:["一月","二月","三月","四月","五月","六月","七月","八月","九月","十月","十一月","十二月"],dayNames:["星期日","星期一","星期二","星期三","星期四","星期五","星期六"],dayNamesShort:["周日","周一","周二","周三","周四","周五","周六"],dayNamesMin:["日","一","二","三","四","五","六"],weekHeader:"周",dateFormat:"yy/mm/dd",firstDay:1,isRTL:!1,showMonthAfterYear:!0,yearSuffix:"年"}),e.fullCalendar.locale("zh-tw",{buttonText:{month:"月",week:"週",day:"天",list:"活動列表"},allDayText:"整天",eventLimitText:"顯示更多",noEventsMessage:"没有任何活動"})}(),a.locale("en"),e.fullCalendar.locale("en"),e.datepicker&&e.datepicker.setDefaults(e.datepicker.regional[""])}); \ No newline at end of file
diff --git a/library/htmlpurifier-4.6.0-lite/INSTALL b/library/htmlpurifier-4.6.0-lite/INSTALL
deleted file mode 100644
index 677c04aa0..000000000
--- a/library/htmlpurifier-4.6.0-lite/INSTALL
+++ /dev/null
@@ -1,374 +0,0 @@
-
-Install
- How to install HTML Purifier
-
-HTML Purifier is designed to run out of the box, so actually using the
-library is extremely easy. (Although... if you were looking for a
-step-by-step installation GUI, you've downloaded the wrong software!)
-
-While the impatient can get going immediately with some of the sample
-code at the bottom of this library, it's well worth reading this entire
-document--most of the other documentation assumes that you are familiar
-with these contents.
-
-
----------------------------------------------------------------------------
-1. Compatibility
-
-HTML Purifier is PHP 5 only, and is actively tested from PHP 5.0.5 and
-up. It has no core dependencies with other libraries. PHP
-4 support was deprecated on December 31, 2007 with HTML Purifier 3.0.0.
-HTML Purifier is not compatible with zend.ze1_compatibility_mode.
-
-These optional extensions can enhance the capabilities of HTML Purifier:
-
- * iconv : Converts text to and from non-UTF-8 encodings
- * bcmath : Used for unit conversion and imagecrash protection
- * tidy : Used for pretty-printing HTML
-
-These optional libraries can enhance the capabilities of HTML Purifier:
-
- * CSSTidy : Clean CSS stylesheets using %Core.ExtractStyleBlocks
- * Net_IDNA2 (PEAR) : IRI support using %Core.EnableIDNA
-
----------------------------------------------------------------------------
-2. Reconnaissance
-
-A big plus of HTML Purifier is its inerrant support of standards, so
-your web-pages should be standards-compliant. (They should also use
-semantic markup, but that's another issue altogether, one HTML Purifier
-cannot fix without reading your mind.)
-
-HTML Purifier can process these doctypes:
-
-* XHTML 1.0 Transitional (default)
-* XHTML 1.0 Strict
-* HTML 4.01 Transitional
-* HTML 4.01 Strict
-* XHTML 1.1
-
-...and these character encodings:
-
-* UTF-8 (default)
-* Any encoding iconv supports (with crippled internationalization support)
-
-These defaults reflect what my choices would be if I were authoring an
-HTML document, however, what you choose depends on the nature of your
-codebase. If you don't know what doctype you are using, you can determine
-the doctype from this identifier at the top of your source code:
-
- <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
- "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
-
-...and the character encoding from this code:
-
- <meta http-equiv="Content-type" content="text/html;charset=ENCODING">
-
-If the character encoding declaration is missing, STOP NOW, and
-read 'docs/enduser-utf8.html' (web accessible at
-http://htmlpurifier.org/docs/enduser-utf8.html). In fact, even if it is
-present, read this document anyway, as many websites specify their
-document's character encoding incorrectly.
-
-
----------------------------------------------------------------------------
-3. Including the library
-
-The procedure is quite simple:
-
- require_once '/path/to/library/HTMLPurifier.auto.php';
-
-This will setup an autoloader, so the library's files are only included
-when you use them.
-
-Only the contents in the library/ folder are necessary, so you can remove
-everything else when using HTML Purifier in a production environment.
-
-If you installed HTML Purifier via PEAR, all you need to do is:
-
- require_once 'HTMLPurifier.auto.php';
-
-Please note that the usual PEAR practice of including just the classes you
-want will not work with HTML Purifier's autoloading scheme.
-
-Advanced users, read on; other users can skip to section 4.
-
-Autoload compatibility
-----------------------
-
- HTML Purifier attempts to be as smart as possible when registering an
- autoloader, but there are some cases where you will need to change
- your own code to accomodate HTML Purifier. These are those cases:
-
- PHP VERSION IS LESS THAN 5.1.2, AND YOU'VE DEFINED __autoload
- Because spl_autoload_register() doesn't exist in early versions
- of PHP 5, HTML Purifier has no way of adding itself to the autoload
- stack. Modify your __autoload function to test
- HTMLPurifier_Bootstrap::autoload($class)
-
- For example, suppose your autoload function looks like this:
-
- function __autoload($class) {
- require str_replace('_', '/', $class) . '.php';
- return true;
- }
-
- A modified version with HTML Purifier would look like this:
-
- function __autoload($class) {
- if (HTMLPurifier_Bootstrap::autoload($class)) return true;
- require str_replace('_', '/', $class) . '.php';
- return true;
- }
-
- Note that there *is* some custom behavior in our autoloader; the
- original autoloader in our example would work for 99% of the time,
- but would fail when including language files.
-
- AN __autoload FUNCTION IS DECLARED AFTER OUR AUTOLOADER IS REGISTERED
- spl_autoload_register() has the curious behavior of disabling
- the existing __autoload() handler. Users need to explicitly
- spl_autoload_register('__autoload'). Because we use SPL when it
- is available, __autoload() will ALWAYS be disabled. If __autoload()
- is declared before HTML Purifier is loaded, this is not a problem:
- HTML Purifier will register the function for you. But if it is
- declared afterwards, it will mysteriously not work. This
- snippet of code (after your autoloader is defined) will fix it:
-
- spl_autoload_register('__autoload')
-
- Users should also be on guard if they use a version of PHP previous
- to 5.1.2 without an autoloader--HTML Purifier will define __autoload()
- for you, which can collide with an autoloader that was added by *you*
- later.
-
-
-For better performance
-----------------------
-
- Opcode caches, which greatly speed up PHP initialization for scripts
- with large amounts of code (HTML Purifier included), don't like
- autoloaders. We offer an include file that includes all of HTML Purifier's
- files in one go in an opcode cache friendly manner:
-
- // If /path/to/library isn't already in your include path, uncomment
- // the below line:
- // require '/path/to/library/HTMLPurifier.path.php';
-
- require 'HTMLPurifier.includes.php';
-
- Optional components still need to be included--you'll know if you try to
- use a feature and you get a class doesn't exists error! The autoloader
- can be used in conjunction with this approach to catch classes that are
- missing. Simply add this afterwards:
-
- require 'HTMLPurifier.autoload.php';
-
-Standalone version
-------------------
-
- HTML Purifier has a standalone distribution; you can also generate
- a standalone file from the full version by running the script
- maintenance/generate-standalone.php . The standalone version has the
- benefit of having most of its code in one file, so parsing is much
- faster and the library is easier to manage.
-
- If HTMLPurifier.standalone.php exists in the library directory, you
- can use it like this:
-
- require '/path/to/HTMLPurifier.standalone.php';
-
- This is equivalent to including HTMLPurifier.includes.php, except that
- the contents of standalone/ will be added to your path. To override this
- behavior, specify a new HTMLPURIFIER_PREFIX where standalone files can
- be found (usually, this will be one directory up, the "true" library
- directory in full distributions). Don't forget to set your path too!
-
- The autoloader can be added to the end to ensure the classes are
- loaded when necessary; otherwise you can manually include them.
- To use the autoloader, use this:
-
- require 'HTMLPurifier.autoload.php';
-
-For advanced users
-------------------
-
- HTMLPurifier.auto.php performs a number of operations that can be done
- individually. These are:
-
- HTMLPurifier.path.php
- Puts /path/to/library in the include path. For high performance,
- this should be done in php.ini.
-
- HTMLPurifier.autoload.php
- Registers our autoload handler HTMLPurifier_Bootstrap::autoload($class).
-
- You can do these operations by yourself--in fact, you must modify your own
- autoload handler if you are using a version of PHP earlier than PHP 5.1.2
- (See "Autoload compatibility" above).
-
-
----------------------------------------------------------------------------
-4. Configuration
-
-HTML Purifier is designed to run out-of-the-box, but occasionally HTML
-Purifier needs to be told what to do. If you answer no to any of these
-questions, read on; otherwise, you can skip to the next section (or, if you're
-into configuring things just for the heck of it, skip to 4.3).
-
-* Am I using UTF-8?
-* Am I using XHTML 1.0 Transitional?
-
-If you answered no to any of these questions, instantiate a configuration
-object and read on:
-
- $config = HTMLPurifier_Config::createDefault();
-
-
-4.1. Setting a different character encoding
-
-You really shouldn't use any other encoding except UTF-8, especially if you
-plan to support multilingual websites (read section three for more details).
-However, switching to UTF-8 is not always immediately feasible, so we can
-adapt.
-
-HTML Purifier uses iconv to support other character encodings, as such,
-any encoding that iconv supports <http://www.gnu.org/software/libiconv/>
-HTML Purifier supports with this code:
-
- $config->set('Core.Encoding', /* put your encoding here */);
-
-An example usage for Latin-1 websites (the most common encoding for English
-websites):
-
- $config->set('Core.Encoding', 'ISO-8859-1');
-
-Note that HTML Purifier's support for non-Unicode encodings is crippled by the
-fact that any character not supported by that encoding will be silently
-dropped, EVEN if it is ampersand escaped. If you want to work around
-this, you are welcome to read docs/enduser-utf8.html for a fix,
-but please be cognizant of the issues the "solution" creates (for this
-reason, I do not include the solution in this document).
-
-
-4.2. Setting a different doctype
-
-For those of you using HTML 4.01 Transitional, you can disable
-XHTML output like this:
-
- $config->set('HTML.Doctype', 'HTML 4.01 Transitional');
-
-Other supported doctypes include:
-
- * HTML 4.01 Strict
- * HTML 4.01 Transitional
- * XHTML 1.0 Strict
- * XHTML 1.0 Transitional
- * XHTML 1.1
-
-
-4.3. Other settings
-
-There are more configuration directives which can be read about
-here: <http://htmlpurifier.org/live/configdoc/plain.html> They're a bit boring,
-but they can help out for those of you who like to exert maximum control over
-your code. Some of the more interesting ones are configurable at the
-demo <http://htmlpurifier.org/demo.php> and are well worth looking into
-for your own system.
-
-For example, you can fine tune allowed elements and attributes, convert
-relative URLs to absolute ones, and even autoparagraph input text! These
-are, respectively, %HTML.Allowed, %URI.MakeAbsolute and %URI.Base, and
-%AutoFormat.AutoParagraph. The %Namespace.Directive naming convention
-translates to:
-
- $config->set('Namespace.Directive', $value);
-
-E.g.
-
- $config->set('HTML.Allowed', 'p,b,a[href],i');
- $config->set('URI.Base', 'http://www.example.com');
- $config->set('URI.MakeAbsolute', true);
- $config->set('AutoFormat.AutoParagraph', true);
-
-
----------------------------------------------------------------------------
-5. Caching
-
-HTML Purifier generates some cache files (generally one or two) to speed up
-its execution. For maximum performance, make sure that
-library/HTMLPurifier/DefinitionCache/Serializer is writeable by the webserver.
-
-If you are in the library/ folder of HTML Purifier, you can set the
-appropriate permissions using:
-
- chmod -R 0755 HTMLPurifier/DefinitionCache/Serializer
-
-If the above command doesn't work, you may need to assign write permissions
-to all. This may be necessary if your webserver runs as nobody, but is
-not recommended since it means any other user can write files in the
-directory. Use:
-
- chmod -R 0777 HTMLPurifier/DefinitionCache/Serializer
-
-You can also chmod files via your FTP client; this option
-is usually accessible by right clicking the corresponding directory and
-then selecting "chmod" or "file permissions".
-
-Starting with 2.0.1, HTML Purifier will generate friendly error messages
-that will tell you exactly what you have to chmod the directory to, if in doubt,
-follow its advice.
-
-If you are unable or unwilling to give write permissions to the cache
-directory, you can either disable the cache (and suffer a performance
-hit):
-
- $config->set('Core.DefinitionCache', null);
-
-Or move the cache directory somewhere else (no trailing slash):
-
- $config->set('Cache.SerializerPath', '/home/user/absolute/path');
-
-
----------------------------------------------------------------------------
-6. Using the code
-
-The interface is mind-numbingly simple:
-
- $purifier = new HTMLPurifier($config);
- $clean_html = $purifier->purify( $dirty_html );
-
-That's it! For more examples, check out docs/examples/ (they aren't very
-different though). Also, docs/enduser-slow.html gives advice on what to
-do if HTML Purifier is slowing down your application.
-
-
----------------------------------------------------------------------------
-7. Quick install
-
-First, make sure library/HTMLPurifier/DefinitionCache/Serializer is
-writable by the webserver (see Section 5: Caching above for details).
-If your website is in UTF-8 and XHTML Transitional, use this code:
-
-<?php
- require_once '/path/to/htmlpurifier/library/HTMLPurifier.auto.php';
-
- $config = HTMLPurifier_Config::createDefault();
- $purifier = new HTMLPurifier($config);
- $clean_html = $purifier->purify($dirty_html);
-?>
-
-If your website is in a different encoding or doctype, use this code:
-
-<?php
- require_once '/path/to/htmlpurifier/library/HTMLPurifier.auto.php';
-
- $config = HTMLPurifier_Config::createDefault();
- $config->set('Core.Encoding', 'ISO-8859-1'); // replace with your encoding
- $config->set('HTML.Doctype', 'HTML 4.01 Transitional'); // replace with your doctype
- $purifier = new HTMLPurifier($config);
-
- $clean_html = $purifier->purify($dirty_html);
-?>
-
- vim: et sw=4 sts=4
diff --git a/library/htmlpurifier-4.6.0-lite/NEWS b/library/htmlpurifier-4.6.0-lite/NEWS
deleted file mode 100644
index 90a054620..000000000
--- a/library/htmlpurifier-4.6.0-lite/NEWS
+++ /dev/null
@@ -1,1078 +0,0 @@
-NEWS ( CHANGELOG and HISTORY ) HTMLPurifier
-|||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
-
-= KEY ====================
- # Breaks back-compat
- ! Feature
- - Bugfix
- + Sub-comment
- . Internal change
-==========================
-
-4.6.0, released 2013-11-30
-# Secure URI munge hashing algorithm has changed to hash_hmac("sha256", $url, $secret).
- Please update any verification scripts you may have.
-# URI parsing algorithm was made more strict, so only prefixes which
- looks like schemes will actually be schemes. Thanks
- Michael Gusev <mgusev@sugarcrm.com> for fixing.
-# %Core.EscapeInvalidChildren is no longer supported, and no longer does
- anything.
-! New directive %Core.AllowHostnameUnderscore which allows underscores
- in hostnames.
-- Eliminate quadratic behavior in DOMLex by using a proper queue.
- Thanks Ole Laursen for noticing this.
-- Rewritten MakeWellFormed/FixNesting implementation eliminates quadratic
- behavior in the rest of the purificaiton pipeline. Thanks Chedburn
- Networks for sponsoring this work.
-- Made Linkify URL parser a bit less permissive, so that non-breaking
- spaces and commas are not included as part of URL. Thanks nAS for fixing.
-- Fix some bad interactions with %HTML.Allowed and injectors. Thanks
- David Hirtz for reporting.
-- Fix infinite loop in DirectLex. Thanks Ashar Javed (@soaj1664ashar)
- for reporting.
-
-4.5.0, released 2013-02-17
-# Fix bug where stacked attribute transforms clobber each other;
- this also means it's no longer possible to override attribute
- transforms in later modules. No internal code was using this
- but this may break some clients.
-# We now use SHA-1 to identify cached definitions, instead of MD5.
-! Support display:inline-block
-! Support for more white-space CSS values.
-! Permit underscores in font families
-! Support for page-break-* CSS3 properties when proprietary properties
- are enabled.
-! New directive %Core.DisableExcludes; can be set to 'true' to turn off
- SGML excludes checking. If HTML Purifier is removing too much text
- and you don't care about full standards compliance, try setting this to
- 'true'.
-- Use prepend for SPL autoloading on PHP 5.3 and later.
-- Fix bug with nofollow transform when pre-existing rel exists.
-- Fix bug where background:url() always gets lower-cased
- (but not background-image:url())
-- Fix bug with non lower-case color names in HTML
-- Fix bug where data URI validation doesn't remove temporary files.
- Thanks Javier Marín Ros <javiermarinros@gmail.com> for reporting.
-- Don't remove certain empty tags on RemoveEmpty.
-
-4.4.0, released 2012-01-18
-# Removed PEARSax3 handler.
-# URI.Munge now munges URIs inside the same host that go from https
- to http. Reported by Neike Taika-Tessaro.
-# Core.EscapeNonASCIICharacters now always transforms entities to
- entities, even if target encoding is UTF-8.
-# Tighten up selector validation in ExtractStyleBlocks.
- Non-syntactically valid selectors are now rejected, along with
- some of the more obscure ones such as attribute selectors, the
- :lang pseudoselector, and anything not in CSS2.1. Furthermore,
- ID and class selectors now work properly with the relevant
- configuration attributes. Also, mute errors when parsing CSS
- with CSS Tidy. Reported by Mario Heiderich and Norman Hippert.
-! Added support for 'scope' attribute on tables.
-! Added %HTML.TargetBlank, which adds target="blank" to all outgoing links.
-! Properly handle sub-lists directly nested inside of lists in
- a standards compliant way, by moving them into the preceding <li>
-! Added %HTML.AllowedComments and %HTML.AllowedCommentsRegexp for
- limited allowed comments in untrusted situations.
-! Implement iframes, and allow them to be used in untrusted mode with
- %HTML.SafeIframe and %URI.SafeIframeRegexp. Thanks Bradley M. Froehle
- <brad.froehle@gmail.com> for submitting an initial version of the patch.
-! The Forms module now works properly for transitional doctypes.
-! Added support for internationalized domain names. You need the PEAR
- Net_IDNA2 module to be in your path; if it is installed, ensure the
- class can be loaded and then set %Core.EnableIDNA to true.
-- Color keywords are now case insensitive. Thanks Yzmir Ramirez
- <yramirez-htmlpurifier@adicio.com> for reporting.
-- Explicitly initialize anonModule variable to null.
-- Do not duplicate nofollow if already present. Thanks 178
- for reporting.
-- Do not add nofollow if hostname matches our current host. Thanks 178
- for reporting, and Neike Taika-Tessaro for helping diagnose.
-- Do not unset parser variable; this fixes intermittent serialization
- problems. Thanks Neike Taika-Tessaro for reporting, bill
- <10010tiger@gmail.com> for diagnosing.
-- Fix iconv truncation bug, where non-UTF-8 target encodings see
- output truncated after around 8000 characters. Thanks Jörg Ludwig
- <joerg.ludwig@iserv.eu> for reporting.
-- Fix broken table content model for XHTML1.1 (and also earlier
- versions, although the W3C validator doesn't catch those violations).
- Thanks GlitchMr <glitch.mr@gmail.com> for reporting.
-
-4.3.0, released 2011-03-27
-# Fixed broken caching of customized raw definitions, but requires an
- API change. The old API still works but will emit a warning,
- see http://htmlpurifier.org/docs/enduser-customize.html#optimized
- for how to upgrade your code.
-# Protect against Internet Explorer innerHTML behavior by specially
- treating attributes with backticks but no angled brackets, quotes or
- spaces. This constitutes a slight semantic change, which can be
- reverted using %Output.FixInnerHTML. Reported by Neike Taika-Tessaro
- and Mario Heiderich.
-# Protect against cssText/innerHTML by restricting allowed characters
- used in fonts further than mandated by the specification and encoding
- some extra special characters in URLs. Reported by Neike
- Taika-Tessaro and Mario Heiderich.
-! Added %HTML.Nofollow to add rel="nofollow" to external links.
-! More types of SPL autoloaders allowed on later versions of PHP.
-! Implementations for position, top, left, right, bottom, z-index
- when %CSS.Trusted is on.
-! Add %Cache.SerializerPermissions option for custom serializer
- directory/file permissions
-! Fix longstanding bug in Flash support for non-IE browsers, and
- allow more wmode attributes.
-! Add %CSS.AllowedFonts to restrict permissible font names.
-- Switch to an iterative traversal of the DOM, which prevents us
- from running out of stack space for deeply nested documents.
- Thanks Maxim Krizhanovsky for contributing a patch.
-- Make removal of conditional IE comments ungreedy; thanks Bernd
- for reporting.
-- Escape CDATA before removing Internet Explorer comments.
-- Fix removal of id attributes under certain conditions by ensuring
- armor attributes are preserved when recreating tags.
-- Check if schema.ser was corrupted.
-- Check if zend.ze1_compatibility_mode is on, and error out if it is.
- This safety check is only done for HTMLPurifier.auto.php; if you
- are using standalone or the specialized includes files, you're
- expected to know what you're doing.
-- Stop repeatedly writing the cache file after I'm done customizing a
- raw definition. Reported by ajh.
-- Switch to using require_once in the Bootstrap to work around bad
- interaction with Zend Debugger and APC. Reported by Antonio Parraga.
-- Fix URI handling when hostname is missing but scheme is present.
- Reported by Neike Taika-Tessaro.
-- Fix missing numeric entities on DirectLex; thanks Neike Taika-Tessaro
- for reporting.
-- Fix harmless notice from indexing into empty string. Thanks Matthijs
- Kooijman <matthijs@stdin.nl> for reporting.
-- Don't autoclose no parent elements are able to support the element
- that triggered the autoclose. In particular fixes strange behavior
- of stray <li> tags. Thanks pkuliga@gmail.com for reporting and
- Neike Taika-Tessaro <pinkgothic@gmail.com> for debugging assistance.
-
-4.2.0, released 2010-09-15
-! Added %Core.RemoveProcessingInstructions, which lets you remove
- <? ... ?> statements.
-! Added %URI.DisableResources functionality; the directive originally
- did nothing. Thanks David Rothstein for reporting.
-! Add documentation about configuration directive types.
-! Add %CSS.ForbiddenProperties configuration directive.
-! Add %HTML.FlashAllowFullScreen to permit embedded Flash objects
- to utilize full-screen mode.
-! Add optional support for the <code>file</code> URI scheme, enable
- by explicitly setting %URI.AllowedSchemes.
-! Add %Core.NormalizeNewlines options to allow turning off newline
- normalization.
-- Fix improper handling of Internet Explorer conditional comments
- by parser. Thanks zmonteca for reporting.
-- Fix missing attributes bug when running on Mac Snow Leopard and APC.
- Thanks sidepodcast for the fix.
-- Warn if an element is allowed, but an attribute it requires is
- not allowed.
-
-4.1.1, released 2010-05-31
-- Fix undefined index warnings in maintenance scripts.
-- Fix bug in DirectLex for parsing elements with a single attribute
- with entities.
-- Rewrite CSS output logic for font-family and url(). Thanks Mario
- Heiderich <mario.heiderich@googlemail.com> for reporting and Takeshi
- Terada <t-terada@violet.plala.or.jp> for suggesting the fix.
-- Emit an error for CollectErrors if a body is extracted
-- Fix bug where in background-position for center keyword handling.
-- Fix infinite loop when a wrapper element is inserted in a context
- where it's not allowed. Thanks Lars <lars@renoz.dk> for reporting.
-- Remove +x bit and shebang from index.php; only supported mode is to
- explicitly call it with php.
-- Make test script less chatty when log_errors is on.
-
-4.1.0, released 2010-04-26
-! Support proprietary height attribute on table element
-! Support YouTube slideshows that contain /cp/ in their URL.
-! Support for data: URI scheme; not enabled by default, add it using
- %URI.AllowedSchemes
-! Support flashvars when using %HTML.SafeObject and %HTML.SafeEmbed.
-! Support for Internet Explorer compatibility with %HTML.SafeObject
- using %Output.FlashCompat.
-! Handle <ol><ol> properly, by inserting the necessary <li> tag.
-- Always quote the insides of url(...) in CSS.
-
-4.0.0, released 2009-07-07
-# APIs for ConfigSchema subsystem have substantially changed. See
- docs/dev-config-bcbreaks.txt for details; in essence, anything that
- had both namespace and directive now have a single unified key.
-# Some configuration directives were renamed, specifically:
- %AutoFormatParam.PurifierLinkifyDocURL -> %AutoFormat.PurifierLinkify.DocURL
- %FilterParam.ExtractStyleBlocksEscaping -> %Filter.ExtractStyleBlocks.Escaping
- %FilterParam.ExtractStyleBlocksScope -> %Filter.ExtractStyleBlocks.Scope
- %FilterParam.ExtractStyleBlocksTidyImpl -> %Filter.ExtractStyleBlocks.TidyImpl
- As usual, the old directive names will still work, but will throw E_NOTICE
- errors.
-# The allowed values for class have been relaxed to allow all of CDATA for
- doctypes that are not XHTML 1.1 or XHTML 2.0. For old behavior, set
- %Attr.ClassUseCDATA to false.
-# Instead of appending the content model to an old content model, a blank
- element will replace the old content model. You can use #SUPER to get
- the old content model.
-! More robust support for name="" and id=""
-! HTMLPurifier_Config::inherit($config) allows you to inherit one
- configuration, and have changes to that configuration be propagated
- to all of its children.
-! Implement %HTML.Attr.Name.UseCDATA, which relaxes validation rules on
- the name attribute when set. Use with care. Thanks Ian Cook for
- sponsoring.
-! Implement %AutoFormat.RemoveEmpty.RemoveNbsp, which removes empty
- tags that contain non-breaking spaces as well other whitespace. You
- can also modify which tags should have &nbsp; maintained with
- %AutoFormat.RemoveEmpty.RemoveNbsp.Exceptions.
-! Implement %Attr.AllowedClasses, which allows administrators to restrict
- classes users can use to a specified finite set of classes, and
- %Attr.ForbiddenClasses, which is the logical inverse.
-! You can now maintain your own configuration schema directories by
- creating a config-schema.php file or passing an extra argument. Check
- docs/dev-config-schema.html for more details.
-! Added HTMLPurifier_Config->serialize() method, which lets you save away
- your configuration in a compact serial file, which you can unserialize
- and use directly without having to go through the overhead of setup.
-- Fix bug where URIDefinition would not get cleared if it's directives got
- changed.
-- Fix fatal error in HTMLPurifier_Encoder on certain platforms (probably NetBSD 5.0)
-- Fix bug in Linkify autoformatter involving <a><span>http://foo</span></a>
-- Make %URI.Munge not apply to links that have the same host as your host.
-- Prevent stray </body> tag from truncating output, if a second </body>
- is present.
-. Created script maintenance/rename-config.php for renaming a configuration
- directive while maintaining its alias. This script does not change source code.
-. Implement namespace locking for definition construction, to prevent
- bugs where a directive is used for definition construction but is not
- used to construct the cache hash.
-
-3.3.0, released 2009-02-16
-! Implement CSS property 'overflow' when %CSS.AllowTricky is true.
-! Implement generic property list classess
-- Fix bug with testEncodingSupportsASCII() algorithm when iconv() implementation
- does not do the "right thing" with characters not supported in the output
- set.
-- Spellcheck UTF-8: The Secret To Character Encoding
-- Fix improper removal of the contents of elements with only whitespace. Thanks
- Eric Wald for reporting.
-- Fix broken test suite in versions of PHP without spl_autoload_register()
-- Fix degenerate case with YouTube filter involving double hyphens.
- Thanks Pierre Attar for reporting.
-- Fix YouTube rendering problem on certain versions of Firefox.
-- Fix CSSDefinition Printer problems with decorators
-- Add text parameter to unit tests, forces text output
-. Add verbose mode to command line test runner, use (--verbose)
-. Turn on unit tests for UnitConverter
-. Fix missing version number in configuration %Attr.DefaultImageAlt (added 3.2.0)
-. Fix newline errors that caused spurious failures when CRLF HTML Purifier was
- tested on Linux.
-. Removed trailing whitespace from all text files, see
- remote-trailing-whitespace.php maintenance script.
-. Convert configuration to use property list backend.
-
-3.2.0, released 2008-10-31
-# Using %Core.CollectErrors forces line number/column tracking on, whereas
- previously you could theoretically turn it off.
-# HTMLPurifier_Injector->notifyEnd() is formally deprecated. Please
- use handleEnd() instead.
-! %Output.AttrSort for when you need your attributes in alphabetical order to
- deal with a bug in FCKEditor. Requested by frank farmer.
-! Enable HTML comments when %HTML.Trusted is on. Requested by Waldo Jaquith.
-! Proper support for name attribute. It is now allowed and equivalent to the id
- attribute in a and img tags, and is only converted to id when %HTML.TidyLevel
- is heavy (for all doctypes).
-! %AutoFormat.RemoveEmpty to remove some empty tags from documents. Please don't
- use on hand-written HTML.
-! Add error-cases for unsupported elements in MakeWellFormed. This enables
- the strategy to be used, standalone, on untrusted input.
-! %Core.AggressivelyFixLt is on by default. This causes more sensible
- processing of left angled brackets in smileys and other whatnot.
-! Test scripts now have a 'type' parameter, which lets you say 'htmlpurifier',
- 'phpt', 'vtest', etc. in order to only execute those tests. This supercedes
- the --only-phpt parameter, although for backwards-compatibility the flag
- will still work.
-! AutoParagraph auto-formatter will now preserve double-newlines upon output.
- Users who are not performing inbound filtering, this may seem a little
- useless, but as a bonus, the test suite and handling of edge cases is also
- improved.
-! Experimental implementation of forms for %HTML.Trusted
-! Track column numbers when maintain line numbers is on
-! Proprietary 'background' attribute on table-related elements converted into
- corresponding CSS. Thanks Fusemail for sponsoring this feature!
-! Add forward(), forwardUntilEndToken(), backward() and current() to Injector
- supertype.
-! HTMLPurifier_Injector->handleEnd() permits modification to end tokens. The
- time of operation varies slightly from notifyEnd() as *all* end tokens are
- processed by the injector before they are subject to the well-formedness rules.
-! %Attr.DefaultImageAlt allows overriding default behavior of setting alt to
- basename of image when not present.
-! %AutoFormat.DisplayLinkURI neuters <a> tags into plain text URLs.
-- Fix two bugs in %URI.MakeAbsolute; one involving empty paths in base URLs,
- the other involving an undefined $is_folder error.
-- Throw error when %Core.Encoding is set to a spurious value. Previously,
- this errored silently and returned false.
-- Redirected stderr to stdout for flush error output.
-- %URI.DisableExternal will now use the host in %URI.Base if %URI.Host is not
- available.
-- Do not re-munge URL if the output URL has the same host as the input URL.
- Requested by Chris.
-- Fix error in documentation regarding %Filter.ExtractStyleBlocks
-- Prevent <![CDATA[<body></body>]]> from triggering %Core.ConvertDocumentToFragment
-- Fix bug with inline elements in blockquotes conflicting with strict doctype
-- Detect if HTML support is disabled for DOM by checking for loadHTML() method.
-- Fix bug where dots and double-dots in absolute URLs without hostname were
- not collapsed by URIFilter_MakeAbsolute.
-- Fix bug with anonymous modules operating on SafeEmbed or SafeObject elements
- by reordering their addition.
-- Will now throw exception on many error conditions during lexer creation; also
- throw an exception when MaintainLineNumbers is true, but a non-tracksLineNumbers
- is being used.
-- Detect if domxml extension is loaded, and use DirectLEx accordingly.
-- Improve handling of big numbers with floating point arithmetic in UnitConverter.
- Reported by David Morton.
-. Strategy_MakeWellFormed now operates in-place, saving memory and allowing
- for more interesting filter-backtracking
-. New HTMLPurifier_Injector->rewind() functionality, allows injectors to rewind
- index to reprocess tokens.
-. StringHashParser now allows for multiline sections with "empty" content;
- previously the section would remain undefined.
-. Added --quick option to multitest.php, which tests only the most recent
- release for each series.
-. Added --distro option to multitest.php, which accepts either 'normal' or
- 'standalone'. This supercedes --exclude-normal and --exclude-standalone
-
-3.1.1, released 2008-06-19
-# %URI.Munge now, by default, does not munge resources (for example, <img src="">)
- In order to enable this again, please set %URI.MungeResources to true.
-! More robust imagecrash protection with height/width CSS with %CSS.MaxImgLength,
- and height/width HTML with %HTML.MaxImgLength.
-! %URI.MungeSecretKey for secure URI munging. Thanks Chris
- for sponsoring this feature. Check out the corresponding documentation
- for details. (Att Nightly testers: The API for this feature changed before
- the general release. Namely, rename your directives %URI.SecureMungeSecretKey =>
- %URI.MungeSecretKey and and %URI.SecureMunge => %URI.Munge)
-! Implemented post URI filtering. Set member variable $post to true to set
- a URIFilter as such.
-! Allow modules to define injectors via $info_injector. Injectors are
- automatically disabled if injector's needed elements are not found.
-! Support for "safe" objects added, use %HTML.SafeObject and %HTML.SafeEmbed.
- Thanks Chris for sponsoring. If you've been using ad hoc code from the
- forums, PLEASE use this instead.
-! Added substitutions for %e, %n, %a and %p in %URI.Munge (in order,
- embedded, tag name, attribute name, CSS property name). See %URI.Munge
- for more details. Requested by Jochem Blok.
-- Disable percent height/width attributes for img.
-- AttrValidator operations are now atomic; updates to attributes are not
- manifest in token until end of operations. This prevents naughty internal
- code from directly modifying CurrentToken when they're not supposed to.
- This semantics change was requested by frank farmer.
-- Percent encoding checks enabled for URI query and fragment
-- Fix stray backslashes in font-family; CSS Unicode character escapes are
- now properly resolved (although *only* in font-family). Thanks Takeshi Terada
- for reporting.
-- Improve parseCDATA algorithm to take into account newline normalization
-- Account for browser confusion between Yen character and backslash in
- Shift_JIS encoding. This fix generalizes to any other encoding which is not
- a strict superset of printable ASCII. Thanks Takeshi Terada for reporting.
-- Fix missing configuration parameter in Generator calls. Thanks vs for the
- partial patch.
-- Improved adherence to Unicode by checking for non-character codepoints.
- Thanks Geoffrey Sneddon for reporting. This may result in degraded
- performance for extremely large inputs.
-- Allow CSS property-value pair ''text-decoration: none''. Thanks Jochem Blok
- for reporting.
-. Added HTMLPurifier_UnitConverter and HTMLPurifier_Length for convenient
- handling of CSS-style lengths. HTMLPurifier_AttrDef_CSS_Length now uses
- this class.
-. API of HTMLPurifier_AttrDef_CSS_Length changed from __construct($disable_negative)
- to __construct($min, $max). __construct(true) is equivalent to
- __construct('0').
-. Added HTMLPurifier_AttrDef_Switch class
-. Rename HTMLPurifier_HTMLModule_Tidy->construct() to setup() and bubble method
- up inheritance hierarchy to HTMLPurifier_HTMLModule. All HTMLModules
- get this called with the configuration object. All modules now
- use this rather than __construct(), although legacy code using constructors
- will still work--the new format, however, lets modules access the
- configuration object for HTML namespace dependant tweaks.
-. AttrDef_HTML_Pixels now takes a single construction parameter, pixels.
-. ConfigSchema data-structure heavily optimized; on average it uses a third
- the memory it did previously. The interface has changed accordingly,
- consult changes to HTMLPurifier_Config for details.
-. Variable parsing types now are magic integers instead of strings
-. Added benchmark for ConfigSchema
-. HTMLPurifier_Generator requires $config and $context parameters. If you
- don't know what they should be, use HTMLPurifier_Config::createDefault()
- and new HTMLPurifier_Context().
-. Printers now properly distinguish between output configuration, and
- target configuration. This is not applicable to scripts using
- the Printers for HTML Purifier related tasks.
-. HTML/CSS Printers must be primed with prepareGenerator($gen_config), otherwise
- fatal errors will ensue.
-. URIFilter->prepare can return false in order to abort loading of the filter
-. Factory for AttrDef_URI implemented, URI#embedded to indicate URI that embeds
- an external resource.
-. %URI.Munge functionality factored out into a post-filter class.
-. Added CurrentCSSProperty context variable during CSS validation
-
-3.1.0, released 2008-05-18
-# Unnecessary references to objects (vestiges of PHP4) removed from method
- signatures. The following methods do not need references when assigning from
- them and will result in E_STRICT errors if you try:
- + HTMLPurifier_Config->get*Definition() [* = HTML, CSS]
- + HTMLPurifier_ConfigSchema::instance()
- + HTMLPurifier_DefinitionCacheFactory::instance()
- + HTMLPurifier_DefinitionCacheFactory->create()
- + HTMLPurifier_DoctypeRegistry->register()
- + HTMLPurifier_DoctypeRegistry->get()
- + HTMLPurifier_HTMLModule->addElement()
- + HTMLPurifier_HTMLModule->addBlankElement()
- + HTMLPurifier_LanguageFactory::instance()
-# Printer_ConfigForm's get*() functions were static-ified
-# %HTML.ForbiddenAttributes requires attribute declarations to be in the
- form of tag@attr, NOT tag.attr (which will throw an error and won't do
- anything). This is for forwards compatibility with XML; you'd do best
- to migrate an %HTML.AllowedAttributes directives to this syntax too.
-! Allow index to be false for config from form creation
-! Added HTMLPurifier::VERSION constant
-! Commas, not dashes, used for serializer IDs. This change is forwards-compatible
- and allows for version numbers like "3.1.0-dev".
-! %HTML.Allowed deals gracefully with whitespace anywhere, anytime!
-! HTML Purifier's URI handling is a lot more robust, with much stricter
- validation checks and better percent encoding handling. Thanks Gareth Heyes
- for indicating security vulnerabilities from lax percent encoding.
-! Bootstrap autoloader deals more robustly with classes that don't exist,
- preventing class_exists($class, true) from barfing.
-- InterchangeBuilder now alphabetizes its lists
-- Validation error in configdoc output fixed
-- Iconv and other encoding errors muted even with custom error handlers that
- do not honor error_reporting
-- Add protection against imagecrash attack with CSS height/width
-- HTMLPurifier::instance() created for consistency, is equivalent to getInstance()
-- Fixed and revamped broken ConfigForm smoketest
-- Bug with bool/null fields in Printer_ConfigForm fixed
-- Bug with global forbidden attributes fixed
-- Improved error messages for allowed and forbidden HTML elements and attributes
-- Missing (or null) in configdoc documentation restored
-- If DOM throws and exception during parsing with PH5P (occurs in newer versions
- of DOM), HTML Purifier punts to DirectLex
-- Fatal error with unserialization of ScriptRequired
-- Created directories are now chmod'ed properly
-- Fixed bug with fallback languages in LanguageFactory
-- Standalone testing setup properly with autoload
-. Out-of-date documentation revised
-. UTF-8 encoding check optimization as suggested by Diego
-. HTMLPurifier_Error removed in favor of exceptions
-. More copy() function removed; should use clone instead
-. More extensive unit tests for HTMLDefinition
-. assertPurification moved to central harness
-. HTMLPurifier_Generator accepts $config and $context parameters during
- instantiation, not runtime
-. Double-quotes outside of attribute values are now unescaped
-
-3.1.0rc1, released 2008-04-22
-# Autoload support added. Internal require_once's removed in favor of an
- explicit require list or autoloading. To use HTML Purifier,
- you must now either use HTMLPurifier.auto.php
- or HTMLPurifier.includes.php; setting the include path and including
- HTMLPurifier.php is insufficient--in such cases include HTMLPurifier.autoload.php
- as well to register our autoload handler (or modify your autoload function
- to check HTMLPurifier_Bootstrap::getPath($class)). You can also use
- HTMLPurifier.safe-includes.php for a less performance friendly but more
- user-friendly library load.
-# HTMLPurifier_ConfigSchema static functions are officially deprecated. Schema
- information is stored in the ConfigSchema directory, and the
- maintenance/generate-schema-cache.php generates the schema.ser file, which
- is now instantiated. Support for userland schema changes coming soon!
-# HTMLPurifier_Config will now throw E_USER_NOTICE when you use a directive
- alias; to get rid of these errors just modify your configuration to use
- the new directive name.
-# HTMLPurifier->addFilter is deprecated; built-in filters can now be
- enabled using %Filter.$filter_name or by setting your own filters using
- %Filter.Custom
-# Directive-level safety properties superceded in favor of module-level
- safety. Internal method HTMLModule->addElement() has changed, although
- the externally visible HTMLDefinition->addElement has *not* changed.
-! Extra utility classes for testing and non-library operations can
- be found in extras/. Specifically, these are FSTools and ConfigDoc.
- You may find a use for these in your own project, but right now they
- are highly experimental and volatile.
-! Integration with PHPT allows for automated smoketests
-! Limited support for proprietary HTML elements, namely <marquee>, sponsored
- by Chris. You can enable them with %HTML.Proprietary if your client
- demands them.
-! Support for !important CSS cascade modifier. By default, this will be stripped
- from CSS, but you can enable it using %CSS.AllowImportant
-! Support for display and visibility CSS properties added, set %CSS.AllowTricky
- to true to use them.
-! HTML Purifier now has its own Exception hierarchy under HTMLPurifier_Exception.
- Developer error (not enduser error) can cause these to be triggered.
-! Experimental kses() wrapper introduced with HTMLPurifier.kses.php
-! Finally %CSS.AllowedProperties for tweaking allowed CSS properties without
- mucking around with HTMLPurifier_CSSDefinition
-! ConfigDoc output has been enhanced with version and deprecation info.
-! %HTML.ForbiddenAttributes and %HTML.ForbiddenElements implemented.
-- Autoclose now operates iteratively, i.e. <span><span><div> now has
- both span tags closed.
-- Various HTMLPurifier_Config convenience functions now accept another parameter
- $schema which defines what HTMLPurifier_ConfigSchema to use besides the
- global default.
-- Fix bug with trusted script handling in libxml versions later than 2.6.28.
-- Fix bug in ExtractStyleBlocks with comments in style tags
-- Fix bug in comment parsing for DirectLex
-- Flush output now displayed when in command line mode for unit tester
-- Fix bug with rgb(0, 1, 2) color syntax with spaces inside shorthand syntax
-- HTMLPurifier_HTMLDefinition->addAttribute can now be called multiple times
- on the same element without emitting errors.
-- Fixed fatal error in PH5P lexer with invalid tag names
-. Plugins now get their own changelogs according to project conventions.
-. Convert tokens to use instanceof, reducing memory footprint and
- improving comparison speed.
-. Dry runs now supported in SimpleTest; testing facilities improved
-. Bootstrap class added for handling autoloading functionality
-. Implemented recursive glob at FSTools->globr
-. ConfigSchema now has instance methods for all corresponding define*
- static methods.
-. A couple of new historical maintenance scripts were added.
-. HTMLPurifier/HTMLModule/Tidy/XHTMLAndHTML4.php split into two files
-. tests/index.php can now be run from any directory.
-. HTMLPurifier_Token subclasses split into seperate files
-. HTMLPURIFIER_PREFIX now is defined in Bootstrap.php, NOT HTMLPurifier.php
-. HTMLPURIFIER_PREFIX can now be defined outside of HTML Purifier
-. New --php=php flag added, allows PHP executable to be specified (command
- line only!)
-. htmlpurifier_add_test() preferred method to translate test files in to
- classes, because it handles PHPT files too.
-. Debugger class is deprecated and will be removed soon.
-. Command line argument parsing for testing scripts revamped, now --opt value
- format is supported.
-. Smoketests now cleanup after magic quotes
-. Generator now can output comments (however, comments are still stripped
- from HTML Purifier output)
-. HTMLPurifier_ConfigSchema->validate() deprecated in favor of
- HTMLPurifier_VarParser->parse()
-. Integers auto-cast into float type by VarParser.
-. HTMLPURIFIER_STRICT removed; no validation is performed on runtime, only
- during cache generation
-. Reordered script calls in maintenance/flush.php
-. Command line scripts now honor exit codes
-. When --flush fails in unit testers, abort tests and print message
-. Improved documentation in docs/dev-flush.html about the maintenance scripts
-. copy() methods removed in favor of clone keyword
-
-3.0.0, released 2008-01-06
-# HTML Purifier is PHP 5 only! The 2.1.x branch will be maintained
- until PHP 4 is completely deprecated, but no new features will be added
- to it.
- + Visibility declarations added
- + Constructor methods renamed to __construct()
- + PHP4 reference cruft removed (in progress)
-! CSS properties are now case-insensitive
-! DefinitionCacheFactory now can register new implementations
-! New HTMLPurifier_Filter_ExtractStyleBlocks for extracting <style> from
- documents and cleaning their contents up. Requires the CSSTidy library
- <http://csstidy.sourceforge.net/>. You can access the blocks with the
- 'StyleBlocks' Context variable ($purifier->context->get('StyleBlocks')).
- The output CSS can also be "scoped" for a specific element, use:
- %Filter.ExtractStyleBlocksScope
-! Experimental support for some proprietary CSS attributes allowed:
- opacity (and all of the browser-specific equivalents) and scrollbar colors.
- Enable by setting %CSS.Proprietary to true.
-- Colors missing # but in hex form will be corrected
-- CSS Number algorithm improved
-- Unit testing and multi-testing now on steroids: command lines,
- XML output, and other goodies now added.
-. Unit tests for Injector improved
-. New classes:
- + HTMLPurifier_AttrDef_CSS_AlphaValue
- + HTMLPurifier_AttrDef_CSS_Filter
-. Multitest now has a file docblock
-
-2.1.3, released 2007-11-05
-! tests/multitest.php allows you to test multiple versions by running
- tests/index.php through multiple interpreters using `phpv` shell
- script (you must provide this script!)
-- Fixed poor include ordering for Email URI AttrDefs, causes fatal errors
- on some systems.
-- Injector algorithm further refined: off-by-one error regarding skip
- counts for dormant injectors fixed
-- Corrective blockquote definition now enabled for HTML 4.01 Strict
-- Fatal error when <img> tag (or any other element with required attributes)
- has 'id' attribute fixed, thanks NykO18 for reporting
-- Fix warning emitted when a non-supported URI scheme is passed to the
- MakeAbsolute URIFilter, thanks NykO18 (again)
-- Further refine AutoParagraph injector. Behavior inside of elements
- allowing paragraph tags clarified: only inline content delimeted by
- double newlines (not block elements) are paragraphed.
-- Buggy treatment of end tags of elements that have required attributes
- fixed (does not manifest on default tag-set)
-- Spurious internal content reorganization error suppressed
-- HTMLDefinition->addElement now returns a reference to the created
- element object, as implied by the documentation
-- Phorum mod's HTML Purifier help message expanded (unreleased elsewhere)
-- Fix a theoretical class of infinite loops from DirectLex reported
- by Nate Abele
-- Work around unnecessary DOMElement type-cast in PH5P that caused errors
- in PHP 5.1
-- Work around PHP 4 SimpleTest lack-of-error complaining for one-time-only
- HTMLDefinition errors, this may indicate problems with error-collecting
- facilities in PHP 5
-- Make ErrorCollectorEMock work in both PHP 4 and PHP 5
-- Make PH5P work with PHP 5.0 by removing unnecessary array parameter typedef
-. %Core.AcceptFullDocuments renamed to %Core.ConvertDocumentToFragment
- to better communicate its purpose
-. Error unit tests can now specify the expectation of no errors. Future
- iterations of the harness will be extremely strict about what errors
- are allowed
-. Extend Injector hooks to allow for more powerful injector routines
-. HTMLDefinition->addBlankElement created, as according to the HTMLModule
- method
-. Doxygen configuration file updated, with minor improvements
-. Test runner now checks for similarly named files in conf/ directory too.
-. Minor cosmetic change to flush-definition-cache.php: trailing newline is
- outputted
-. Maintenance script for generating PH5P patch added, original PH5P source
- file also added under version control
-. Full unit test runner script title made more descriptive with PHP version
-. Updated INSTALL file to state that 4.3.7 is the earliest version we
- are actively testing
-
-2.1.2, released 2007-09-03
-! Implemented Object module for trusted users
-! Implemented experimental HTML5 parsing mode using PH5P. To use, add
- this to your code:
- require_once 'HTMLPurifier/Lexer/PH5P.php';
- $config->set('Core', 'LexerImpl', 'PH5P');
- Note that this Lexer introduces some classes not in the HTMLPurifier
- namespace. Also, this is PHP5 only.
-! CSS property border-spacing implemented
-- Fix non-visible parsing error in DirectLex with empty tags that have
- slashes inside attribute values.
-- Fix typo in CSS definition: border-collapse:seperate; was incorrectly
- accepted as valid CSS. Usually non-visible, because this styling is the
- default for tables in most browsers. Thanks Brett Zamir for pointing
- this out.
-- Fix validation errors in configuration form
-- Hammer out a bunch of edge-case bugs in the standalone distribution
-- Inclusion reflection removed from URISchemeRegistry; you must manually
- include any new schema files you wish to use
-- Numerous typo fixes in documentation thanks to Brett Zamir
-. Unit test refactoring for one logical test per test function
-. Config and context parameters in ComplexHarness deprecated: instead, edit
- the $config and $context member variables
-. HTML wrapper in DOMLex now takes DTD identifiers into account; doesn't
- really make a difference, but is good for completeness sake
-. merge-library.php script refactored for greater code reusability and
- PHP4 compatibility
-
-2.1.1, released 2007-08-04
-- Fix show-stopper bug in %URI.MakeAbsolute functionality
-- Fix PHP4 syntax error in standalone version
-. Add prefix directory to include path for standalone, this prevents
- other installations from clobbering the standalone's URI schemes
-. Single test methods can be invoked by prefixing with __only
-
-2.1.0, released 2007-08-02
-# flush-htmldefinition-cache.php superseded in favor of a generic
- flush-definition-cache.php script, you can clear a specific cache
- by passing its name as a parameter to the script
-! Phorum mod implemented for HTML Purifier
-! With %Core.AggressivelyFixLt, <3 and similar emoticons no longer
- trigger HTML removal in PHP5 (DOMLex). This directive is not necessary
- for PHP4 (DirectLex).
-! Standalone file now available, which greatly reduces the amount of
- includes (although there are still a few files that reside in the
- standalone folder)
-! Relative URIs can now be transformed into their absolute equivalents
- using %URI.Base and %URI.MakeAbsolute
-! Ruby implemented for XHTML 1.1
-! You can now define custom URI filtering behavior, see enduser-uri-filter.html
- for more details
-! UTF-8 font names now supported in CSS
-- AutoFormatters emit friendly error messages if tags or attributes they
- need are not allowed
-- ConfigForm's compactification of directive names is now configurable
-- AutoParagraph autoformatter algorithm refined after field-testing
-- XHTML 1.1 now applies XHTML 1.0 Strict cleanup routines, namely
- blockquote wrapping
-- Contents of <style> tags removed by default when tags are removed
-. HTMLPurifier_Config->getSerial() implemented, this is extremely useful
- for output cache invalidation
-. ConfigForm printer now can retrieve CSS and JS files as strings, in
- case HTML Purifier's directory is not publically accessible
-. Introduce new text/itext configuration directive values: these represent
- longer strings that would be more appropriately edited with a textarea
-. Allow newlines to act as separators for lists, hashes, lookups and
- %HTML.Allowed
-. ConfigForm generates textareas instead of text inputs for lists, hashes,
- lookups, text and itext fields
-. Hidden element content removal genericized: %Core.HiddenElements can
- be used to customize this behavior, by default <script> and <style> are
- hidden
-. Added HTMLPURIFIER_PREFIX constant, should be used instead of dirname(__FILE__)
-. Custom ChildDef added to default include list
-. URIScheme reflection improved: will not attempt to include file if class
- already exists. May clobber autoload, so I need to keep an eye on it
-. ConfigSchema heavily optimized, will only collect information and validate
- definitions when HTMLPURIFIER_SCHEMA_STRICT is true.
-. AttrDef_URI unit tests and implementation refactored
-. benchmarks/ directory now protected from public view with .htaccess file;
- run the tests via command line
-. URI scheme is munged off if there is no authority and the scheme is the
- default one
-. All unit tests inherit from HTMLPurifier_Harness, not UnitTestCase
-. Interface for URIScheme changed
-. Generic URI object to hold components of URI added, most systems involved
- in URI validation have been migrated to use it
-. Custom filtering for URIs factored out to URIDefinition interface for
- maximum extensibility
-
-2.0.1, released 2007-06-27
-! Tag auto-closing now based on a ChildDef heuristic rather than a
- manually set auto_close array; some behavior may change
-! Experimental AutoFormat functionality added: auto-paragraph and
- linkify your HTML input by setting %AutoFormat.AutoParagraph and
- %AutoFormat.Linkify to true
-! Newlines normalized internally, and then converted back to the
- value of PHP_EOL. If this is not desired, set your newline format
- using %Output.Newline.
-! Beta error collection, messages are implemented for the most generic
- cases involving Lexing or Strategies
-- Clean up special case code for <script> tags
-- Reorder includes for DefinitionCache decorators, fixes a possible
- missing class error
-- Fixed bug where manually modified definitions were not saved via cache
- (mostly harmless, except for the fact that it would be a little slower)
-- Configuration objects with different serials do not clobber each
- others when revision numbers are unequal
-- Improve Serializer DefinitionCache directory permissions checks
-- DefinitionCache no longer throws errors when it encounters old
- serial files that do not conform to the current style
-- Stray xmlns attributes removed from configuration documentation
-- configForm.php smoketest no longer has XSS vulnerability due to
- unescaped print_r output
-- Printer adheres to configuration's directives on output format
-- Fix improperly named form field in ConfigForm printer
-. Rewire some test-cases to swallow errors rather than expect them
-. HTMLDefinition printer updated with some of the new attributes
-. DefinitionCache keys reordered to reflect precedence: version number,
- hash, then revision number
-. %Core.DefinitionCache renamed to %Cache.DefinitionImpl
-. Interlinking in configuration documentation added using
- Injector_PurifierLinkify
-. Directives now keep track of aliases to themselves
-. Error collector now requires a severity to be passed, use PHP's internal
- error constants for this
-. HTMLPurifier_Config::getAllowedDirectivesForForm implemented, allows
- much easier selective embedding of configuration values
-. Doctype objects now accept public and system DTD identifiers
-. %HTML.Doctype is now constrained by specific values, to specify a custom
- doctype use new %HTML.CustomDoctype
-. ConfigForm truncates long directives to keep the form small, and does
- not re-output namespaces
-
-2.0.0, released 2007-06-20
-# Completely refactored HTMLModuleManager, decentralizing safety
- information
-# Transform modules changed to Tidy modules, which offer more flexibility
- and better modularization
-# Configuration object now finalizes itself when a read operation is
- performed on it, ensuring that its internal state stays consistent.
- To revert this behavior, you can set the $autoFinalize member variable
- off, but it's not recommended.
-# New compact syntax for AttrDef objects that can be used to instantiate
- new objects via make()
-# Definitions (esp. HTMLDefinition) are now cached for a significant
- performance boost. You can disable caching by setting %Core.DefinitionCache
- to null. You CANNOT edit raw definitions without setting the corresponding
- DefinitionID directive (%HTML.DefinitionID for HTMLDefinition).
-# Contents between <script> tags are now completely removed if <script>
- is not allowed
-# Prototype-declarations for Lexer removed in favor of configuration
- determination of Lexer implementations.
-! HTML Purifier now works in PHP 4.3.2.
-! Configuration form-editing API makes tweaking HTMLPurifier_Config a
- breeze!
-! Configuration directives that accept hashes now allow new string
- format: key1:value1,key2:value2
-! ConfigDoc now factored into OOP design
-! All deprecated elements now natively supported
-! Implement TinyMCE styled whitelist specification format in
- %HTML.Allowed
-! Config object gives more friendly error messages when things go wrong
-! Advanced API implemented: easy functions for creating elements (addElement)
- and attributes (addAttribute) on HTMLDefinition
-! Add native support for required attributes
-- Deprecated and removed EnableRedundantUTF8Cleaning. It didn't even work!
-- DOMLex will not emit errors when a custom error handler that does not
- honor error_reporting is used
-- StrictBlockquote child definition refrains from wrapping whitespace
- in tags now.
-- Bug resulting from tag transforms to non-allowed elements fixed
-- ChildDef_Custom's regex generation has been improved, removing several
- false positives
-. Unit test for ElementDef created, ElementDef behavior modified to
- be more flexible
-. Added convenience functions for HTMLModule constructors
-. AttrTypes now has accessor functions that should be used instead
- of directly manipulating info
-. TagTransform_Center deprecated in favor of generic TagTransform_Simple
-. Add extra protection in AttrDef_URI against phantom Schemes
-. Doctype object added to HTMLDefinition which describes certain aspects
- of the operational document type
-. Lexer is now pre-emptively included, with a conditional include for the
- PHP5 only version.
-. HTMLDefinition and CSSDefinition have a common parent class: Definition.
-. DirectLex can now track line-numbers
-. Preliminary error collector is in place, although no code actually reports
- errors yet
-. Factor out most of ValidateAttributes to new AttrValidator class
-
-1.6.1, released 2007-05-05
-! Support for more deprecated attributes via transformations:
- + hspace and vspace in img
- + size and noshade in hr
- + nowrap in td
- + clear in br
- + align in caption, table, img and hr
- + type in ul, ol and li
-! DirectLex now preserves text in which a < bracket is followed by
- a non-alphanumeric character. This means that certain emoticons
- are now preserved.
-! %Core.RemoveInvalidImg is now operational, when set to false invalid
- images will hang around with an empty src
-! target attribute in a tag supported, use %Attr.AllowedFrameTargets
- to enable
-! CSS property white-space now allows nowrap (supported in all modern
- browsers) but not others (which have spotty browser implementations)
-! XHTML 1.1 mode now sort-of works without any fatal errors, and
- lang is now moved over to xml:lang.
-! Attribute transformation smoketest available at smoketests/attrTransform.php
-! Transformation of font's size attribute now handles super-large numbers
-- Possibly fatal bug with __autoload() fixed in module manager
-- Invert HTMLModuleManager->addModule() processing order to check
- prefixes first and then the literal module
-- Empty strings get converted to empty arrays instead of arrays with
- an empty string in them.
-- Merging in attribute lists now works.
-. Demo script removed: it has been added to the website's repository
-. Basic.php script modified to work out of the box
-. Refactor AttrTransform classes to reduce duplication
-. AttrTransform_TextAlign axed in favor of a more general
- AttrTransform_EnumToCSS, refer to HTMLModule/TransformToStrict.php to
- see how the new equivalent is implemented
-. Unit tests now use exclusively assertIdentical
-
-1.6.0, released 2007-04-01
-! Support for most common deprecated attributes via transformations:
- + bgcolor in td, th, tr and table
- + border in img
- + name in a and img
- + width in td, th and hr
- + height in td, th
-! Support for CSS attribute 'height' added
-! Support for rel and rev attributes in a tags added, use %Attr.AllowedRel
- and %Attr.AllowedRev to activate
-- You can define ID blacklists using regular expressions via
- %Attr.IDBlacklistRegexp
-- Error messages are emitted when you attempt to "allow" elements or
- attributes that HTML Purifier does not support
-- Fix segfault in unit test. The problem is not very reproduceable and
- I don't know what causes it, but a six line patch fixed it.
-
-1.5.0, released 2007-03-23
-! Added a rudimentary I18N and L10N system modeled off MediaWiki. It
- doesn't actually do anything yet, but keep your eyes peeled.
-! docs/enduser-utf8.html explains how to use UTF-8 and HTML Purifier
-! Newly structured HTMLDefinition modeled off of XHTML 1.1 modules.
- I am loathe to release beta quality APIs, but this is exactly that;
- don't use the internal interfaces if you're not willing to do migration
- later on.
-- Allow 'x' subtag in language codes
-- Fixed buggy chameleon-support for ins and del
-. Added support for IDREF attributes (i.e. for)
-. Renamed HTMLPurifier_AttrDef_Class to HTMLPurifier_AttrDef_Nmtokens
-. Removed context variable ParentType, replaced with IsInline, which
- is false when you're not inline and an integer of the parent that
- caused you to become inline when you are (so possibly zero)
-. Removed ElementDef->type in favor of ElementDef->descendants_are_inline
- and HTMLDefinition->content_sets
-. StrictBlockquote now reports what elements its supposed to allow,
- rather than what it does allow
-. Removed HTMLDefinition->info_flow_elements in favor of
- HTMLDefinition->content_sets['Flow']
-. Removed redundant "exclusionary" definitions from DTD roster
-. StrictBlockquote now requires a construction parameter as if it
- were an Required ChildDef, this is the "real" set of allowed elements
-. AttrDef partitioned into HTML, CSS and URI segments
-. Modify Youtube filter regexp to be multiline
-. Require both PHP5 and DOM extension in order to use DOMLex, fixes
- some edge cases where a DOMDocument class exists in a PHP4 environment
- due to DOM XML extension.
-
-1.4.1, released 2007-01-21
-! docs/enduser-youtube.html updated according to new functionality
-- YouTube IDs can have underscores and dashes
-
-1.4.0, released 2007-01-21
-! Implemented list-style-image, URIs now allowed in list-style
-! Implemented background-image, background-repeat, background-attachment
- and background-position CSS properties. Shorthand property background
- supports all of these properties.
-! Configuration documentation looks nicer
-! Added %Core.EscapeNonASCIICharacters to workaround loss of Unicode
- characters while %Core.Encoding is set to a non-UTF-8 encoding.
-! Support for configuration directive aliases added
-! Config object can now be instantiated from ini files
-! YouTube preservation code added to the core, with two lines of code
- you can add it as a filter to your code. See smoketests/preserveYouTube.php
- for sample code.
-! Moved SLOW to docs/enduser-slow.html and added code examples
-- Replaced version check with functionality check for DOM (thanks Stephen
- Khoo)
-. Added smoketest 'all.php', which loads all other smoketests via frames
-. Implemented AttrDef_CSSURI for url(http://google.com) style declarations
-. Added convenient single test selector form on test runner
-
-1.3.2, released 2006-12-25
-! HTMLPurifier object now accepts configuration arrays, no need to manually
- instantiate a configuration object
-! Context object now accessible to outside
-! Added enduser-youtube.html, explains how to embed YouTube videos. See
- also corresponding smoketest preserveYouTube.php.
-! Added purifyArray(), which takes a list of HTML and purifies it all
-! Added static member variable $version to HTML Purifier with PHP-compatible
- version number string.
-- Fixed fatal error thrown by upper-cased language attributes
-- printDefinition.php: added labels, added better clarification
-. HTMLPurifier_Config::create() added, takes mixed variable and converts into
- a HTMLPurifier_Config object.
-
-1.3.1, released 2006-12-06
-! Added HTMLPurifier.func.php stub for a convenient function to call the library
-- Fixed bug in RemoveInvalidImg code that caused all images to be dropped
- (thanks to .mario for reporting this)
-. Standardized all attribute handling variables to attr, made it plural
-
-1.3.0, released 2006-11-26
-# Invalid images are now removed, rather than replaced with a dud
- <img src="" alt="Invalid image" />. Previous behavior can be restored
- with new directive %Core.RemoveInvalidImg set to false.
-! (X)HTML Strict now supported
- + Transparently handles inline elements in block context (blockquote)
-! Added GET method to demo for easier validation, added 50kb max input size
-! New directive %HTML.BlockWrapper, for block-ifying inline elements
-! New directive %HTML.Parent, allows you to only allow inline content
-! New directives %HTML.AllowedElements and %HTML.AllowedAttributes to let
- users narrow the set of allowed tags
-! <li value="4"> and <ul start="2"> now allowed in loose mode
-! New directives %URI.DisableExternalResources and %URI.DisableResources
-! New directive %Attr.DisableURI, which eliminates all hyperlinking
-! New directive %URI.Munge, munges URI so you can use some sort of redirector
- service to avoid PageRank leaks or warn users that they are exiting your site.
-! Added spiffy new smoketest printDefinition.php, which lets you twiddle with
- the configuration settings and see how the internal rules are affected.
-! New directive %URI.HostBlacklist for blocking links to bad hosts.
- xssAttacks.php smoketest updated accordingly.
-- Added missing type to ChildDef_Chameleon
-- Remove Tidy option from demo if there is not Tidy available
-. ChildDef_Required guards against empty tags
-. Lookup table HTMLDefinition->info_flow_elements added
-. Added peace-of-mind variable initialization to Strategy_FixNesting
-. Added HTMLPurifier->info_parent_def, parent child processing made special
-. Added internal documents briefly summarizing future progression of HTML
-. HTMLPurifier_Config->getBatch($namespace) added
-. More lenient casting to bool from string in HTMLPurifier_ConfigSchema
-. Refactored ChildDef classes into their own files
-
-1.2.0, released 2006-11-19
-# ID attributes now disabled by default. New directives:
- + %HTML.EnableAttrID - restores old behavior by allowing IDs
- + %Attr.IDPrefix - %Attr.IDBlacklist alternative that munges all user IDs
- so that they don't collide with your IDs
- + %Attr.IDPrefixLocal - Same as above, but for when there are multiple
- instances of user content on the page
- + Profuse documentation on how to use these available in docs/enduser-id.txt
-! Added MODx plugin <http://modxcms.com/forums/index.php/topic,6604.0.html>
-! Added percent encoding normalization
-! XSS attacks smoketest given facelift
-! Configuration documentation now has table of contents
-! Added %URI.DisableExternal, which prevents links to external websites. You
- can also use %URI.Host to permit absolute linking to subdomains
-! Non-accessible resources (ex. mailto) blocked from embedded URIs (img src)
-- Type variable in HTMLDefinition was not being set properly, fixed
-- Documentation updated
- + TODO added request Phalanger
- + TODO added request Native compression
- + TODO added request Remove redundant tags
- + TODO added possible plaintext formatter for HTML Purifier documentation
- + Updated ConfigDoc TODO
- + Improved inline comments in AttrDef/Class.php, AttrDef/CSS.php
- and AttrDef/Host.php
- + Revamped documentation into HTML, along with misc updates
-- HTMLPurifier_Context doesn't throw a variable reference error if you attempt
- to retrieve a non-existent variable
-. Switched to purify()-wide Context object registry
-. Refactored unit tests to minimize duplication
-. XSS attack sheet updated
-. configdoc.xml now has xml:space attached to default value nodes
-. Allow configuration directives to permit null values
-. Cleaned up test-cases to remove unnecessary swallowErrors()
-
-1.1.2, released 2006-09-30
-! Add HTMLPurifier.auto.php stub file that configures include_path
-- Documentation updated
- + INSTALL document rewritten
- + TODO added semi-lossy conversion
- + API Doxygen docs' file exclusions updated
- + Added notes on HTML versus XML attribute whitespace handling
- + Noted that HTMLPurifier_ChildDef_Custom isn't being used
- + Noted that config object's definitions are cached versions
-- Fixed lack of attribute parsing in HTMLPurifier_Lexer_PEARSax3
-- ftp:// URIs now have their typecodes checked
-- Hooked up HTMLPurifier_ChildDef_Custom's unit tests (they weren't being run)
-. Line endings standardized throughout project (svn:eol-style standardized)
-. Refactored parseData() to general Lexer class
-. Tester named "HTML Purifier" not "HTMLPurifier"
-
-1.1.1, released 2006-09-24
-! Configuration option to optionally Tidy up output for indentation to make up
- for dropped whitespace by DOMLex (pretty-printing for the entire application
- should be done by a page-wide Tidy)
-- Various documentation updates
-- Fixed parse error in configuration documentation script
-- Fixed fatal error in benchmark scripts, slightly augmented
-- As far as possible, whitespace is preserved in-between table children
-- Sample test-settings.php file included
-
-1.1.0, released 2006-09-16
-! Directive documentation generation using XSLT
-! XHTML can now be turned off, output becomes <br>
-- Made URI validator more forgiving: will ignore leading and trailing
- quotes, apostrophes and less than or greater than signs.
-- Enforce alphanumeric namespace and directive names for configuration.
-- Table child definition made more flexible, will fix up poorly ordered elements
-. Renamed ConfigDef to ConfigSchema
-
-1.0.1, released 2006-09-04
-- Fixed slight bug in DOMLex attribute parsing
-- Fixed rejection of case-insensitive configuration values when there is a
- set of allowed values. This manifested in %Core.Encoding.
-- Fixed rejection of inline style declarations that had lots of extra
- space in them. This manifested in TinyMCE.
-
-1.0.0, released 2006-09-01
-! Shorthand CSS properties implemented: font, border, background, list-style
-! Basic color keywords translated into hexadecimal values
-! Table CSS properties implemented
-! Support for charsets other than UTF-8 (defined by iconv)
-! Malformed UTF-8 and non-SGML character detection and cleaning implemented
-- Fixed broken numeric entity conversion
-- API documentation completed
-. (HTML|CSS)Definition de-singleton-ized
-
-1.0.0beta, released 2006-08-16
-! First public release, most functionality implemented. Notable omissions are:
- + Shorthand CSS properties
- + Table CSS properties
- + Deprecated attribute transformations
-
- vim: et sw=4 sts=4
diff --git a/library/jquery-textcomplete/LICENSE b/library/jquery-textcomplete/LICENSE
deleted file mode 100644
index 4848bd637..000000000
--- a/library/jquery-textcomplete/LICENSE
+++ /dev/null
@@ -1,21 +0,0 @@
-The MIT License (MIT)
-
-Copyright (c) 2013-2014 Yuku Takahashi
-
-Permission is hereby granted, free of charge, to any person obtaining a copy
-of this software and associated documentation files (the "Software"), to deal
-in the Software without restriction, including without limitation the rights
-to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
-copies of the Software, and to permit persons to whom the Software is
-furnished to do so, subject to the following conditions:
-
-The above copyright notice and this permission notice shall be included in
-all copies or substantial portions of the Software.
-
-THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
-IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
-FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
-AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
-LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
-OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
-THE SOFTWARE.
diff --git a/library/jquery-textcomplete/jquery.textcomplete.js b/library/jquery-textcomplete/jquery.textcomplete.js
index 95e75149c..0dd9fd827 100644
--- a/library/jquery-textcomplete/jquery.textcomplete.js
+++ b/library/jquery-textcomplete/jquery.textcomplete.js
@@ -136,10 +136,6 @@ if (typeof jQuery === 'undefined') {
return Object.prototype.toString.call(obj) === '[object String]';
};
- var isFunction = function (obj) {
- return Object.prototype.toString.call(obj) === '[object Function]';
- };
-
var uniqueId = 0;
function Completer(element, option) {
@@ -147,33 +143,47 @@ if (typeof jQuery === 'undefined') {
this.id = 'textcomplete' + uniqueId++;
this.strategies = [];
this.views = [];
- this.option = $.extend({}, Completer._getDefaults(), option);
+ this.option = $.extend({}, Completer.defaults, option);
if (!this.$el.is('input[type=text]') && !this.$el.is('input[type=search]') && !this.$el.is('textarea') && !element.isContentEditable && element.contentEditable != 'true') {
throw new Error('textcomplete must be called on a Textarea or a ContentEditable.');
}
- if (element === document.activeElement) {
+ // use ownerDocument to fix iframe / IE issues
+ if (element === element.ownerDocument.activeElement) {
// element has already been focused. Initialize view objects immediately.
this.initialize()
} else {
// Initialize view objects lazily.
var self = this;
this.$el.one('focus.' + this.id, function () { self.initialize(); });
- }
- }
- Completer._getDefaults = function () {
- if (!Completer.DEFAULTS) {
- Completer.DEFAULTS = {
- appendTo: $('body'),
- zIndex: '100'
- };
+ // Special handling for CKEditor: lazy init on instance load
+ if ((!this.option.adapter || this.option.adapter == 'CKEditor') && typeof CKEDITOR != 'undefined' && (this.$el.is('textarea'))) {
+ CKEDITOR.on("instanceReady", function(event) {
+ event.editor.once("focus", function(event2) {
+ // replace the element with the Iframe element and flag it as CKEditor
+ self.$el = $(event.editor.editable().$);
+ if (!self.option.adapter) {
+ self.option.adapter = $.fn.textcomplete['CKEditor'];
+ self.option.ckeditor_instance = event.editor;
+ }
+ self.initialize();
+ });
+ });
+ }
}
-
- return Completer.DEFAULTS;
}
+ Completer.defaults = {
+ appendTo: 'body',
+ className: '', // deprecated option
+ dropdownClassName: 'dropdown-menu textcomplete-dropdown',
+ maxCount: 10,
+ zIndex: '100',
+ rightEdgeOffset: 30
+ };
+
$.extend(Completer.prototype, {
// Public properties
// -----------------
@@ -184,12 +194,26 @@ if (typeof jQuery === 'undefined') {
adapter: null,
dropdown: null,
$el: null,
+ $iframe: null,
// Public methods
// --------------
initialize: function () {
var element = this.$el.get(0);
+
+ // check if we are in an iframe
+ // we need to alter positioning logic if using an iframe
+ if (this.$el.prop('ownerDocument') !== document && window.frames.length) {
+ for (var iframeIndex = 0; iframeIndex < window.frames.length; iframeIndex++) {
+ if (this.$el.prop('ownerDocument') === window.frames[iframeIndex].document) {
+ this.$iframe = $(window.frames[iframeIndex].frameElement);
+ break;
+ }
+ }
+ }
+
+
// Initialize view objects.
this.dropdown = new $.fn.textcomplete.Dropdown(element, this, this.option);
var Adapter, viewName;
@@ -281,7 +305,7 @@ if (typeof jQuery === 'undefined') {
var strategy = this.strategies[i];
var context = strategy.context(text);
if (context || context === '') {
- var matchRegexp = isFunction(strategy.match) ? strategy.match(text) : strategy.match;
+ var matchRegexp = $.isFunction(strategy.match) ? strategy.match(text) : strategy.match;
if (isString(context)) { text = context; }
var match = text.match(matchRegexp);
if (match) { return [strategy, match[strategy.index], match]; }
@@ -399,7 +423,7 @@ if (typeof jQuery === 'undefined') {
var $parent = option.appendTo;
if (!($parent instanceof $)) { $parent = $($parent); }
var $el = $('<ul></ul>')
- .addClass('dropdown-menu textcomplete-dropdown')
+ .addClass(option.dropdownClassName)
.attr('id', 'textcomplete-dropdown-' + option._oid)
.css({
display: 'none',
@@ -422,7 +446,7 @@ if (typeof jQuery === 'undefined') {
footer: null,
header: null,
id: null,
- maxCount: 10,
+ maxCount: null,
placement: '',
shown: false,
data: [], // Shown zipped data.
@@ -445,8 +469,8 @@ if (typeof jQuery === 'undefined') {
render: function (zippedData) {
var contentsHtml = this._buildContents(zippedData);
- var unzippedData = $.map(this.data, function (d) { return d.value; });
- if (this.data.length) {
+ var unzippedData = $.map(zippedData, function (d) { return d.value; });
+ if (zippedData.length) {
var strategy = zippedData[0].strategy;
if (strategy.id) {
this.$el.attr('data-strategy', strategy.id);
@@ -480,7 +504,7 @@ if (typeof jQuery === 'undefined') {
return false;
if($(this).css('position') === 'fixed') {
pos.top -= $window.scrollTop();
- pos.left -= $window.scrollLeft();
+ pos.left -= $window.scrollLeft();
position = 'fixed';
return false;
}
@@ -785,7 +809,10 @@ if (typeof jQuery === 'undefined') {
var windowScrollBottom = $window.scrollTop() + $window.height();
var height = this.$el.height();
if ((this.$el.position().top + height) > windowScrollBottom) {
- this.$el.offset({top: windowScrollBottom - height});
+ // only do this if we are not in an iframe
+ if (!this.completer.$iframe) {
+ this.$el.offset({top: windowScrollBottom - height});
+ }
}
},
@@ -794,7 +821,7 @@ if (typeof jQuery === 'undefined') {
// to the document width so we don't know if we would have overrun it. As a heuristic to avoid that clipping
// (which makes our elements wrap onto the next line and corrupt the next item), if we're close to the right
// edge, move left. We don't know how far to move left, so just keep nudging a bit.
- var tolerance = 30; // pixels. Make wider than vertical scrollbar because we might not be able to use that space.
+ var tolerance = this.option.rightEdgeOffset; // pixels. Make wider than vertical scrollbar because we might not be able to use that space.
var lastOffset = this.$el.offset().left, offset;
var width = this.$el.width();
var maxLeft = $window.width() - tolerance;
@@ -1005,8 +1032,14 @@ if (typeof jQuery === 'undefined') {
switch (clickEvent.keyCode) {
case 9: // TAB
case 13: // ENTER
+ case 16: // SHIFT
+ case 17: // CTRL
+ case 18: // ALT
+ case 33: // PAGEUP
+ case 34: // PAGEDOWN
case 40: // DOWN
case 38: // UP
+ case 27: // ESC
return true;
}
if (clickEvent.ctrlKey) switch (clickEvent.keyCode) {
@@ -1040,12 +1073,14 @@ if (typeof jQuery === 'undefined') {
var pre = this.getTextFromHeadToCaret();
var post = this.el.value.substring(this.el.selectionEnd);
var newSubstr = strategy.replace(value, e);
+ var regExp;
if (typeof newSubstr !== 'undefined') {
if ($.isArray(newSubstr)) {
post = newSubstr[1] + post;
newSubstr = newSubstr[0];
}
- pre = pre.replace(strategy.match, newSubstr);
+ regExp = $.isFunction(strategy.match) ? strategy.match(pre) : strategy.match;
+ pre = pre.replace(regExp, newSubstr);
this.$el.val(pre + post);
this.el.selectionStart = this.el.selectionEnd = pre.length;
}
@@ -1062,7 +1097,8 @@ if (typeof jQuery === 'undefined') {
var p = $.fn.textcomplete.getCaretCoordinates(this.el, this.el.selectionStart);
return {
top: p.top + this._calculateLineHeight() - this.$el.scrollTop(),
- left: p.left - this.$el.scrollLeft()
+ left: p.left - this.$el.scrollLeft(),
+ lineHeight: this._calculateLineHeight()
};
},
@@ -1111,12 +1147,14 @@ if (typeof jQuery === 'undefined') {
var pre = this.getTextFromHeadToCaret();
var post = this.el.value.substring(pre.length);
var newSubstr = strategy.replace(value, e);
+ var regExp;
if (typeof newSubstr !== 'undefined') {
if ($.isArray(newSubstr)) {
post = newSubstr[1] + post;
newSubstr = newSubstr[0];
}
- pre = pre.replace(strategy.match, newSubstr);
+ regExp = $.isFunction(strategy.match) ? strategy.match(pre) : strategy.match;
+ pre = pre.replace(regExp, newSubstr);
this.$el.val(pre + post);
this.el.focus();
var range = this.el.createTextRange();
@@ -1162,30 +1200,35 @@ if (typeof jQuery === 'undefined') {
// When an dropdown item is selected, it is executed.
select: function (value, strategy, e) {
var pre = this.getTextFromHeadToCaret();
- var sel = window.getSelection()
+ // use ownerDocument instead of window to support iframes
+ var sel = this.el.ownerDocument.getSelection();
+
var range = sel.getRangeAt(0);
var selection = range.cloneRange();
selection.selectNodeContents(range.startContainer);
var content = selection.toString();
var post = content.substring(range.startOffset);
var newSubstr = strategy.replace(value, e);
+ var regExp;
if (typeof newSubstr !== 'undefined') {
if ($.isArray(newSubstr)) {
post = newSubstr[1] + post;
newSubstr = newSubstr[0];
}
- pre = pre.replace(strategy.match, newSubstr);
+ regExp = $.isFunction(strategy.match) ? strategy.match(pre) : strategy.match;
+ pre = pre.replace(regExp, newSubstr)
+ .replace(/ $/, "&nbsp"); // &nbsp necessary at least for CKeditor to not eat spaces
range.selectNodeContents(range.startContainer);
range.deleteContents();
// create temporary elements
- var preWrapper = document.createElement("div");
+ var preWrapper = this.el.ownerDocument.createElement("div");
preWrapper.innerHTML = pre;
- var postWrapper = document.createElement("div");
+ var postWrapper = this.el.ownerDocument.createElement("div");
postWrapper.innerHTML = post;
// create the fragment thats inserted
- var fragment = document.createDocumentFragment();
+ var fragment = this.el.ownerDocument.createDocumentFragment();
var childNode;
var lastOfPre;
while (childNode = preWrapper.firstChild) {
@@ -1218,8 +1261,8 @@ if (typeof jQuery === 'undefined') {
//
// Dropdown's position will be decided using the result.
_getCaretRelativePosition: function () {
- var range = window.getSelection().getRangeAt(0).cloneRange();
- var node = document.createElement('span');
+ var range = this.el.ownerDocument.getSelection().getRangeAt(0).cloneRange();
+ var node = this.el.ownerDocument.createElement('span');
range.insertNode(node);
range.selectNodeContents(node);
range.deleteContents();
@@ -1228,6 +1271,17 @@ if (typeof jQuery === 'undefined') {
position.left -= this.$el.offset().left;
position.top += $node.height() - this.$el.offset().top;
position.lineHeight = $node.height();
+
+ // special positioning logic for iframes
+ // this is typically used for contenteditables such as tinymce or ckeditor
+ if (this.completer.$iframe) {
+ var iframePosition = this.completer.$iframe.offset();
+ position.top += iframePosition.top;
+ position.left += iframePosition.left;
+ //subtract scrollTop from element in iframe
+ position.top -= this.$el.scrollTop();
+ }
+
$node.remove();
return position;
},
@@ -1241,7 +1295,7 @@ if (typeof jQuery === 'undefined') {
// this.getTextFromHeadToCaret()
// // => ' wor' // not '<b>hello</b> wor'
getTextFromHeadToCaret: function () {
- var range = window.getSelection().getRangeAt(0);
+ var range = this.el.ownerDocument.getSelection().getRangeAt(0);
var selection = range.cloneRange();
selection.selectNodeContents(range.startContainer);
return selection.toString().substring(0, range.startOffset);
@@ -1251,6 +1305,39 @@ if (typeof jQuery === 'undefined') {
$.fn.textcomplete.ContentEditable = ContentEditable;
}(jQuery);
+// NOTE: TextComplete plugin has contenteditable support but it does not work
+// fine especially on old IEs.
+// Any pull requests are REALLY welcome.
+
++function ($) {
+ 'use strict';
+
+ // CKEditor adapter
+ // =======================
+ //
+ // Adapter for CKEditor, based on contenteditable elements.
+ function CKEditor (element, completer, option) {
+ this.initialize(element, completer, option);
+ }
+
+ $.extend(CKEditor.prototype, $.fn.textcomplete.ContentEditable.prototype, {
+ _bindEvents: function () {
+ var $this = this;
+ this.option.ckeditor_instance.on('key', function(event) {
+ var domEvent = event.data;
+ $this._onKeyup(domEvent);
+ if ($this.completer.dropdown.shown && $this._skipSearch(domEvent)) {
+ return false;
+ }
+ }, null, null, 1); // 1 = Priority = Important!
+ // we actually also need the native event, as the CKEditor one is happening to late
+ this.$el.on('keyup.' + this.id, $.proxy(this._onKeyup, this));
+ },
+});
+
+ $.fn.textcomplete.CKEditor = CKEditor;
+}(jQuery);
+
// The MIT License (MIT)
//
// Copyright (c) 2015 Jonathan Ong me@jongleberry.com
diff --git a/library/jquery-textcomplete/jquery.textcomplete.min.js b/library/jquery-textcomplete/jquery.textcomplete.min.js
index d3a427f27..d8f67a804 100644
--- a/library/jquery-textcomplete/jquery.textcomplete.min.js
+++ b/library/jquery-textcomplete/jquery.textcomplete.min.js
@@ -1,3 +1,3 @@
-/*! jquery-textcomplete - v1.3.4 - 2016-04-19 */
-!function(a){if("function"==typeof define&&define.amd)define(["jquery"],a);else if("object"==typeof module&&module.exports){var b=require("jquery");module.exports=a(b)}else a(jQuery)}(function(a){if("undefined"==typeof a)throw new Error("jQuery.textcomplete requires jQuery");return+function(a){"use strict";var b=function(a){console.warn&&console.warn(a)},c=1;a.fn.textcomplete=function(d,e){var f=Array.prototype.slice.call(arguments);return this.each(function(){var g=this,h=a(this),i=h.data("textComplete");if(i||(e||(e={}),e._oid=c++,i=new a.fn.textcomplete.Completer(this,e),h.data("textComplete",i)),"string"==typeof d){if(!i)return;f.shift(),i[d].apply(i,f),"destroy"===d&&h.removeData("textComplete")}else a.each(d,function(c){a.each(["header","footer","placement","maxCount"],function(a){c[a]&&(i.option[a]=c[a],b(a+"as a strategy param is deprecated. Use option."),delete c[a])})}),i.register(a.fn.textcomplete.Strategy.parse(d,{el:g,$el:h}))})}}(a),+function(a){"use strict";function b(c,d){if(this.$el=a(c),this.id="textcomplete"+f++,this.strategies=[],this.views=[],this.option=a.extend({},b._getDefaults(),d),!(this.$el.is("input[type=text]")||this.$el.is("input[type=search]")||this.$el.is("textarea")||c.isContentEditable||"true"==c.contentEditable))throw new Error("textcomplete must be called on a Textarea or a ContentEditable.");if(c===document.activeElement)this.initialize();else{var e=this;this.$el.one("focus."+this.id,function(){e.initialize()})}}var c=function(a){var b,c;return function(){var d=Array.prototype.slice.call(arguments);if(b)return void(c=d);b=!0;var e=this;d.unshift(function f(){if(c){var d=c;c=void 0,d.unshift(f),a.apply(e,d)}else b=!1}),a.apply(this,d)}},d=function(a){return"[object String]"===Object.prototype.toString.call(a)},e=function(a){return"[object Function]"===Object.prototype.toString.call(a)},f=0;b._getDefaults=function(){return b.DEFAULTS||(b.DEFAULTS={appendTo:a("body"),zIndex:"100"}),b.DEFAULTS},a.extend(b.prototype,{id:null,option:null,strategies:null,adapter:null,dropdown:null,$el:null,initialize:function(){var b=this.$el.get(0);this.dropdown=new a.fn.textcomplete.Dropdown(b,this,this.option);var c,d;this.option.adapter?c=this.option.adapter:(d=this.$el.is("textarea")||this.$el.is("input[type=text]")||this.$el.is("input[type=search]")?"number"==typeof b.selectionEnd?"Textarea":"IETextarea":"ContentEditable",c=a.fn.textcomplete[d]),this.adapter=new c(b,this,this.option)},destroy:function(){this.$el.off("."+this.id),this.adapter&&this.adapter.destroy(),this.dropdown&&this.dropdown.destroy(),this.$el=this.adapter=this.dropdown=null},deactivate:function(){this.dropdown&&this.dropdown.deactivate()},trigger:function(a,b){this.dropdown||this.initialize(),null!=a||(a=this.adapter.getTextFromHeadToCaret());var c=this._extractSearchQuery(a);if(c.length){var d=c[1];if(b&&this._term===d&&""!==d)return;this._term=d,this._search.apply(this,c)}else this._term=null,this.dropdown.deactivate()},fire:function(a){var b=Array.prototype.slice.call(arguments,1);return this.$el.trigger(a,b),this},register:function(a){Array.prototype.push.apply(this.strategies,a)},select:function(a,b,c){this._term=null,this.adapter.select(a,b,c),this.fire("change").fire("textComplete:select",a,b),this.adapter.focus()},_clearAtNext:!0,_term:null,_extractSearchQuery:function(a){for(var b=0;b<this.strategies.length;b++){var c=this.strategies[b],f=c.context(a);if(f||""===f){var g=e(c.match)?c.match(a):c.match;d(f)&&(a=f);var h=a.match(g);if(h)return[c,h[c.index],h]}}return[]},_search:c(function(a,b,c,d){var e=this;b.search(c,function(d,f){e.dropdown.shown||e.dropdown.activate(),e._clearAtNext&&(e.dropdown.clear(),e._clearAtNext=!1),e.dropdown.setPosition(e.adapter.getCaretPosition()),e.dropdown.render(e._zip(d,b,c)),f||(a(),e._clearAtNext=!0)},d)}),_zip:function(b,c,d){return a.map(b,function(a){return{value:a,strategy:c,term:d}})}}),a.fn.textcomplete.Completer=b}(a),+function(a){"use strict";function b(c,d,f){this.$el=b.createElement(f),this.completer=d,this.id=d.id+"dropdown",this._data=[],this.$inputEl=a(c),this.option=f,f.listPosition&&(this.setPosition=f.listPosition),f.height&&this.$el.height(f.height);var g=this;a.each(["maxCount","placement","footer","header","noResultsMessage","className"],function(a,b){null!=f[b]&&(g[b]=f[b])}),this._bindEvents(c),e[this.id]=this}var c=a(window),d=function(a,b){var c,d,e=b.strategy.idProperty;for(c=0;c<a.length;c++)if(d=a[c],d.strategy===b.strategy)if(e){if(d.value[e]===b.value[e])return!0}else if(d.value===b.value)return!0;return!1},e={};a(document).on("click",function(b){var c=b.originalEvent&&b.originalEvent.keepTextCompleteDropdown;a.each(e,function(a,b){a!==c&&b.deactivate()})});var f={SKIP_DEFAULT:0,KEY_UP:1,KEY_DOWN:2,KEY_ENTER:3,KEY_PAGEUP:4,KEY_PAGEDOWN:5,KEY_ESCAPE:6};a.extend(b,{createElement:function(b){var c=b.appendTo;c instanceof a||(c=a(c));var d=a("<ul></ul>").addClass("dropdown-menu textcomplete-dropdown").attr("id","textcomplete-dropdown-"+b._oid).css({display:"none",left:0,position:"absolute",zIndex:b.zIndex}).appendTo(c);return d}}),a.extend(b.prototype,{$el:null,$inputEl:null,completer:null,footer:null,header:null,id:null,maxCount:10,placement:"",shown:!1,data:[],className:"",destroy:function(){this.deactivate(),this.$el.off("."+this.id),this.$inputEl.off("."+this.id),this.clear(),this.$el.remove(),this.$el=this.$inputEl=this.completer=null,delete e[this.id]},render:function(b){var c=this._buildContents(b),d=a.map(this.data,function(a){return a.value});if(this.data.length){var e=b[0].strategy;e.id?this.$el.attr("data-strategy",e.id):this.$el.removeAttr("data-strategy"),this._renderHeader(d),this._renderFooter(d),c&&(this._renderContents(c),this._fitToBottom(),this._fitToRight(),this._activateIndexedItem()),this._setScroll()}else this.noResultsMessage?this._renderNoResultsMessage(d):this.shown&&this.deactivate()},setPosition:function(b){var d="absolute";return this.$inputEl.add(this.$inputEl.parents()).each(function(){return"absolute"===a(this).css("position")?!1:"fixed"===a(this).css("position")?(b.top-=c.scrollTop(),b.left-=c.scrollLeft(),d="fixed",!1):void 0}),this.$el.css(this._applyPlacement(b)),this.$el.css({position:d}),this},clear:function(){this.$el.html(""),this.data=[],this._index=0,this._$header=this._$footer=this._$noResultsMessage=null},activate:function(){return this.shown||(this.clear(),this.$el.show(),this.className&&this.$el.addClass(this.className),this.completer.fire("textComplete:show"),this.shown=!0),this},deactivate:function(){return this.shown&&(this.$el.hide(),this.className&&this.$el.removeClass(this.className),this.completer.fire("textComplete:hide"),this.shown=!1),this},isUp:function(a){return 38===a.keyCode||a.ctrlKey&&80===a.keyCode},isDown:function(a){return 40===a.keyCode||a.ctrlKey&&78===a.keyCode},isEnter:function(a){var b=a.ctrlKey||a.altKey||a.metaKey||a.shiftKey;return!b&&(13===a.keyCode||9===a.keyCode||this.option.completeOnSpace===!0&&32===a.keyCode)},isPageup:function(a){return 33===a.keyCode},isPagedown:function(a){return 34===a.keyCode},isEscape:function(a){return 27===a.keyCode},_data:null,_index:null,_$header:null,_$noResultsMessage:null,_$footer:null,_bindEvents:function(){this.$el.on("mousedown."+this.id,".textcomplete-item",a.proxy(this._onClick,this)),this.$el.on("touchstart."+this.id,".textcomplete-item",a.proxy(this._onClick,this)),this.$el.on("mouseover."+this.id,".textcomplete-item",a.proxy(this._onMouseover,this)),this.$inputEl.on("keydown."+this.id,a.proxy(this._onKeydown,this))},_onClick:function(b){var c=a(b.target);b.preventDefault(),b.originalEvent.keepTextCompleteDropdown=this.id,c.hasClass("textcomplete-item")||(c=c.closest(".textcomplete-item"));var d=this.data[parseInt(c.data("index"),10)];this.completer.select(d.value,d.strategy,b);var e=this;setTimeout(function(){e.deactivate(),"touchstart"===b.type&&e.$inputEl.focus()},0)},_onMouseover:function(b){var c=a(b.target);b.preventDefault(),c.hasClass("textcomplete-item")||(c=c.closest(".textcomplete-item")),this._index=parseInt(c.data("index"),10),this._activateIndexedItem()},_onKeydown:function(b){if(this.shown){var c;switch(a.isFunction(this.option.onKeydown)&&(c=this.option.onKeydown(b,f)),null==c&&(c=this._defaultKeydown(b)),c){case f.KEY_UP:b.preventDefault(),this._up();break;case f.KEY_DOWN:b.preventDefault(),this._down();break;case f.KEY_ENTER:b.preventDefault(),this._enter(b);break;case f.KEY_PAGEUP:b.preventDefault(),this._pageup();break;case f.KEY_PAGEDOWN:b.preventDefault(),this._pagedown();break;case f.KEY_ESCAPE:b.preventDefault(),this.deactivate()}}},_defaultKeydown:function(a){return this.isUp(a)?f.KEY_UP:this.isDown(a)?f.KEY_DOWN:this.isEnter(a)?f.KEY_ENTER:this.isPageup(a)?f.KEY_PAGEUP:this.isPagedown(a)?f.KEY_PAGEDOWN:this.isEscape(a)?f.KEY_ESCAPE:void 0},_up:function(){0===this._index?this._index=this.data.length-1:this._index-=1,this._activateIndexedItem(),this._setScroll()},_down:function(){this._index===this.data.length-1?this._index=0:this._index+=1,this._activateIndexedItem(),this._setScroll()},_enter:function(a){var b=this.data[parseInt(this._getActiveElement().data("index"),10)];this.completer.select(b.value,b.strategy,a),this.deactivate()},_pageup:function(){var b=0,c=this._getActiveElement().position().top-this.$el.innerHeight();this.$el.children().each(function(d){return a(this).position().top+a(this).outerHeight()>c?(b=d,!1):void 0}),this._index=b,this._activateIndexedItem(),this._setScroll()},_pagedown:function(){var b=this.data.length-1,c=this._getActiveElement().position().top+this.$el.innerHeight();this.$el.children().each(function(d){return a(this).position().top>c?(b=d,!1):void 0}),this._index=b,this._activateIndexedItem(),this._setScroll()},_activateIndexedItem:function(){this.$el.find(".textcomplete-item.active").removeClass("active"),this._getActiveElement().addClass("active")},_getActiveElement:function(){return this.$el.children(".textcomplete-item:nth("+this._index+")")},_setScroll:function(){var a=this._getActiveElement(),b=a.position().top,c=a.outerHeight(),d=this.$el.innerHeight(),e=this.$el.scrollTop();0===this._index||this._index==this.data.length-1||0>b?this.$el.scrollTop(b+e):b+c>d&&this.$el.scrollTop(b+c+e-d)},_buildContents:function(a){var b,c,e,f="";for(c=0;c<a.length&&this.data.length!==this.maxCount;c++)b=a[c],d(this.data,b)||(e=this.data.length,this.data.push(b),f+='<li class="textcomplete-item" data-index="'+e+'"><a>',f+=b.strategy.template(b.value,b.term),f+="</a></li>");return f},_renderHeader:function(b){if(this.header){this._$header||(this._$header=a('<li class="textcomplete-header"></li>').prependTo(this.$el));var c=a.isFunction(this.header)?this.header(b):this.header;this._$header.html(c)}},_renderFooter:function(b){if(this.footer){this._$footer||(this._$footer=a('<li class="textcomplete-footer"></li>').appendTo(this.$el));var c=a.isFunction(this.footer)?this.footer(b):this.footer;this._$footer.html(c)}},_renderNoResultsMessage:function(b){if(this.noResultsMessage){this._$noResultsMessage||(this._$noResultsMessage=a('<li class="textcomplete-no-results-message"></li>').appendTo(this.$el));var c=a.isFunction(this.noResultsMessage)?this.noResultsMessage(b):this.noResultsMessage;this._$noResultsMessage.html(c)}},_renderContents:function(a){this._$footer?this._$footer.before(a):this.$el.append(a)},_fitToBottom:function(){var a=c.scrollTop()+c.height(),b=this.$el.height();this.$el.position().top+b>a&&this.$el.offset({top:a-b})},_fitToRight:function(){for(var a,b=30,d=this.$el.offset().left,e=this.$el.width(),f=c.width()-b;d+e>f&&(this.$el.offset({left:d-b}),a=this.$el.offset().left,!(a>=d));)d=a},_applyPlacement:function(a){return-1!==this.placement.indexOf("top")?a={top:"auto",bottom:this.$el.parent().height()-a.top+a.lineHeight,left:a.left}:(a.bottom="auto",delete a.lineHeight),-1!==this.placement.indexOf("absleft")?a.left=0:-1!==this.placement.indexOf("absright")&&(a.right=0,a.left="auto"),a}}),a.fn.textcomplete.Dropdown=b,a.extend(a.fn.textcomplete,f)}(a),+function(a){"use strict";function b(b){a.extend(this,b),this.cache&&(this.search=c(this.search))}var c=function(a){var b={};return function(c,d){b[c]?d(b[c]):a.call(this,c,function(a){b[c]=(b[c]||[]).concat(a),d.apply(null,arguments)})}};b.parse=function(c,d){return a.map(c,function(a){var c=new b(a);return c.el=d.el,c.$el=d.$el,c})},a.extend(b.prototype,{match:null,replace:null,search:null,id:null,cache:!1,context:function(){return!0},index:2,template:function(a){return a},idProperty:null}),a.fn.textcomplete.Strategy=b}(a),+function(a){"use strict";function b(){}var c=Date.now||function(){return(new Date).getTime()},d=function(a,b){var d,e,f,g,h,i=function(){var j=c()-g;b>j?d=setTimeout(i,b-j):(d=null,h=a.apply(f,e),f=e=null)};return function(){return f=this,e=arguments,g=c(),d||(d=setTimeout(i,b)),h}};a.extend(b.prototype,{id:null,completer:null,el:null,$el:null,option:null,initialize:function(b,c,e){this.el=b,this.$el=a(b),this.id=c.id+this.constructor.name,this.completer=c,this.option=e,this.option.debounce&&(this._onKeyup=d(this._onKeyup,this.option.debounce)),this._bindEvents()},destroy:function(){this.$el.off("."+this.id),this.$el=this.el=this.completer=null},select:function(){throw new Error("Not implemented")},getCaretPosition:function(){var b=this._getCaretRelativePosition(),c=this.$el.offset(),d=this.option.appendTo;if(d){d instanceof a||(d=a(d));var e=d.offsetParent().offset();c.top-=e.top,c.left-=e.left}return b.top+=c.top,b.left+=c.left,b},focus:function(){this.$el.focus()},_bindEvents:function(){this.$el.on("keyup."+this.id,a.proxy(this._onKeyup,this))},_onKeyup:function(a){this._skipSearch(a)||this.completer.trigger(this.getTextFromHeadToCaret(),!0)},_skipSearch:function(a){switch(a.keyCode){case 9:case 13:case 40:case 38:return!0}if(a.ctrlKey)switch(a.keyCode){case 78:case 80:return!0}}}),a.fn.textcomplete.Adapter=b}(a),+function(a){"use strict";function b(a,b,c){this.initialize(a,b,c)}a.extend(b.prototype,a.fn.textcomplete.Adapter.prototype,{select:function(b,c,d){var e=this.getTextFromHeadToCaret(),f=this.el.value.substring(this.el.selectionEnd),g=c.replace(b,d);"undefined"!=typeof g&&(a.isArray(g)&&(f=g[1]+f,g=g[0]),e=e.replace(c.match,g),this.$el.val(e+f),this.el.selectionStart=this.el.selectionEnd=e.length)},getTextFromHeadToCaret:function(){return this.el.value.substring(0,this.el.selectionEnd)},_getCaretRelativePosition:function(){var b=a.fn.textcomplete.getCaretCoordinates(this.el,this.el.selectionStart);return{top:b.top+this._calculateLineHeight()-this.$el.scrollTop(),left:b.left-this.$el.scrollLeft()}},_calculateLineHeight:function(){var a=parseInt(this.$el.css("line-height"),10);if(isNaN(a)){var b=this.el.parentNode,c=document.createElement(this.el.nodeName),d=this.el.style;c.setAttribute("style","margin:0px;padding:0px;font-family:"+d.fontFamily+";font-size:"+d.fontSize),c.innerHTML="test",b.appendChild(c),a=c.clientHeight,b.removeChild(c)}return a}}),a.fn.textcomplete.Textarea=b}(a),+function(a){"use strict";function b(b,d,e){this.initialize(b,d,e),a("<span>"+c+"</span>").css({position:"absolute",top:-9999,left:-9999}).insertBefore(b)}var c="吶";a.extend(b.prototype,a.fn.textcomplete.Textarea.prototype,{select:function(b,c,d){var e=this.getTextFromHeadToCaret(),f=this.el.value.substring(e.length),g=c.replace(b,d);if("undefined"!=typeof g){a.isArray(g)&&(f=g[1]+f,g=g[0]),e=e.replace(c.match,g),this.$el.val(e+f),this.el.focus();var h=this.el.createTextRange();h.collapse(!0),h.moveEnd("character",e.length),h.moveStart("character",e.length),h.select()}},getTextFromHeadToCaret:function(){this.el.focus();var a=document.selection.createRange();a.moveStart("character",-this.el.value.length);var b=a.text.split(c);return 1===b.length?b[0]:b[1]}}),a.fn.textcomplete.IETextarea=b}(a),+function(a){"use strict";function b(a,b,c){this.initialize(a,b,c)}a.extend(b.prototype,a.fn.textcomplete.Adapter.prototype,{select:function(b,c,d){var e=this.getTextFromHeadToCaret(),f=window.getSelection(),g=f.getRangeAt(0),h=g.cloneRange();h.selectNodeContents(g.startContainer);var i=h.toString(),j=i.substring(g.startOffset),k=c.replace(b,d);if("undefined"!=typeof k){a.isArray(k)&&(j=k[1]+j,k=k[0]),e=e.replace(c.match,k),g.selectNodeContents(g.startContainer),g.deleteContents();var l=document.createElement("div");l.innerHTML=e;var m=document.createElement("div");m.innerHTML=j;for(var n,o,p=document.createDocumentFragment();n=l.firstChild;)o=p.appendChild(n);for(;n=m.firstChild;)p.appendChild(n);g.insertNode(p),g.setStartAfter(o),g.collapse(!0),f.removeAllRanges(),f.addRange(g)}},_getCaretRelativePosition:function(){var b=window.getSelection().getRangeAt(0).cloneRange(),c=document.createElement("span");b.insertNode(c),b.selectNodeContents(c),b.deleteContents();var d=a(c),e=d.offset();return e.left-=this.$el.offset().left,e.top+=d.height()-this.$el.offset().top,e.lineHeight=d.height(),d.remove(),e},getTextFromHeadToCaret:function(){var a=window.getSelection().getRangeAt(0),b=a.cloneRange();return b.selectNodeContents(a.startContainer),b.toString().substring(0,a.startOffset)}}),a.fn.textcomplete.ContentEditable=b}(a),function(a){function b(a,b,f){if(!d)throw new Error("textarea-caret-position#getCaretCoordinates should only be called in a browser");var g=f&&f.debug||!1;if(g){var h=document.querySelector("#input-textarea-caret-position-mirror-div");h&&h.parentNode.removeChild(h)}var i=document.createElement("div");i.id="input-textarea-caret-position-mirror-div",document.body.appendChild(i);var j=i.style,k=window.getComputedStyle?getComputedStyle(a):a.currentStyle;j.whiteSpace="pre-wrap","INPUT"!==a.nodeName&&(j.wordWrap="break-word"),j.position="absolute",g||(j.visibility="hidden"),c.forEach(function(a){j[a]=k[a]}),e?a.scrollHeight>parseInt(k.height)&&(j.overflowY="scroll"):j.overflow="hidden",i.textContent=a.value.substring(0,b),"INPUT"===a.nodeName&&(i.textContent=i.textContent.replace(/\s/g," "));var l=document.createElement("span");l.textContent=a.value.substring(b)||".",i.appendChild(l);var m={top:l.offsetTop+parseInt(k.borderTopWidth),left:l.offsetLeft+parseInt(k.borderLeftWidth)};return g?l.style.backgroundColor="#aaa":document.body.removeChild(i),m}var c=["direction","boxSizing","width","height","overflowX","overflowY","borderTopWidth","borderRightWidth","borderBottomWidth","borderLeftWidth","borderStyle","paddingTop","paddingRight","paddingBottom","paddingLeft","fontStyle","fontVariant","fontWeight","fontStretch","fontSize","fontSizeAdjust","lineHeight","fontFamily","textAlign","textTransform","textIndent","textDecoration","letterSpacing","wordSpacing","tabSize","MozTabSize"],d="undefined"!=typeof window,e=d&&null!=window.mozInnerScreenX;a.fn.textcomplete.getCaretCoordinates=b}(a),a});
+/*! jquery-textcomplete - v1.8.0 - 2016-11-15 */
+!function(a){if("function"==typeof define&&define.amd)define(["jquery"],a);else if("object"==typeof module&&module.exports){var b=require("jquery");module.exports=a(b)}else a(jQuery)}(function(a){if("undefined"==typeof a)throw new Error("jQuery.textcomplete requires jQuery");return+function(a){"use strict";var b=function(a){console.warn&&console.warn(a)},c=1;a.fn.textcomplete=function(d,e){var f=Array.prototype.slice.call(arguments);return this.each(function(){var g=this,h=a(this),i=h.data("textComplete");if(i||(e||(e={}),e._oid=c++,i=new a.fn.textcomplete.Completer(this,e),h.data("textComplete",i)),"string"==typeof d){if(!i)return;f.shift(),i[d].apply(i,f),"destroy"===d&&h.removeData("textComplete")}else a.each(d,function(c){a.each(["header","footer","placement","maxCount"],function(a){c[a]&&(i.option[a]=c[a],b(a+"as a strategy param is deprecated. Use option."),delete c[a])})}),i.register(a.fn.textcomplete.Strategy.parse(d,{el:g,$el:h}))})}}(a),+function(a){"use strict";function b(c,d){if(this.$el=a(c),this.id="textcomplete"+e++,this.strategies=[],this.views=[],this.option=a.extend({},b.defaults,d),!(this.$el.is("input[type=text]")||this.$el.is("input[type=search]")||this.$el.is("textarea")||c.isContentEditable||"true"==c.contentEditable))throw new Error("textcomplete must be called on a Textarea or a ContentEditable.");if(c===c.ownerDocument.activeElement)this.initialize();else{var f=this;this.$el.one("focus."+this.id,function(){f.initialize()}),this.option.adapter&&"CKEditor"!=this.option.adapter||"undefined"==typeof CKEDITOR||!this.$el.is("textarea")||CKEDITOR.on("instanceReady",function(b){b.editor.once("focus",function(c){f.$el=a(b.editor.editable().$),f.option.adapter||(f.option.adapter=a.fn.textcomplete.CKEditor,f.option.ckeditor_instance=b.editor),f.initialize()})})}}var c=function(a){var b,c;return function(){var d=Array.prototype.slice.call(arguments);if(b)return void(c=d);b=!0;var e=this;d.unshift(function f(){if(c){var d=c;c=void 0,d.unshift(f),a.apply(e,d)}else b=!1}),a.apply(this,d)}},d=function(a){return"[object String]"===Object.prototype.toString.call(a)},e=0;b.defaults={appendTo:"body",className:"",dropdownClassName:"dropdown-menu textcomplete-dropdown",maxCount:10,zIndex:"100",rightEdgeOffset:30},a.extend(b.prototype,{id:null,option:null,strategies:null,adapter:null,dropdown:null,$el:null,$iframe:null,initialize:function(){var b=this.$el.get(0);if(this.$el.prop("ownerDocument")!==document&&window.frames.length)for(var c=0;c<window.frames.length;c++)if(this.$el.prop("ownerDocument")===window.frames[c].document){this.$iframe=a(window.frames[c].frameElement);break}this.dropdown=new a.fn.textcomplete.Dropdown(b,this,this.option);var d,e;this.option.adapter?d=this.option.adapter:(e=this.$el.is("textarea")||this.$el.is("input[type=text]")||this.$el.is("input[type=search]")?"number"==typeof b.selectionEnd?"Textarea":"IETextarea":"ContentEditable",d=a.fn.textcomplete[e]),this.adapter=new d(b,this,this.option)},destroy:function(){this.$el.off("."+this.id),this.adapter&&this.adapter.destroy(),this.dropdown&&this.dropdown.destroy(),this.$el=this.adapter=this.dropdown=null},deactivate:function(){this.dropdown&&this.dropdown.deactivate()},trigger:function(a,b){this.dropdown||this.initialize(),null!=a||(a=this.adapter.getTextFromHeadToCaret());var c=this._extractSearchQuery(a);if(c.length){var d=c[1];if(b&&this._term===d&&""!==d)return;this._term=d,this._search.apply(this,c)}else this._term=null,this.dropdown.deactivate()},fire:function(a){var b=Array.prototype.slice.call(arguments,1);return this.$el.trigger(a,b),this},register:function(a){Array.prototype.push.apply(this.strategies,a)},select:function(a,b,c){this._term=null,this.adapter.select(a,b,c),this.fire("change").fire("textComplete:select",a,b),this.adapter.focus()},_clearAtNext:!0,_term:null,_extractSearchQuery:function(b){for(var c=0;c<this.strategies.length;c++){var e=this.strategies[c],f=e.context(b);if(f||""===f){var g=a.isFunction(e.match)?e.match(b):e.match;d(f)&&(b=f);var h=b.match(g);if(h)return[e,h[e.index],h]}}return[]},_search:c(function(a,b,c,d){var e=this;b.search(c,function(d,f){e.dropdown.shown||e.dropdown.activate(),e._clearAtNext&&(e.dropdown.clear(),e._clearAtNext=!1),e.dropdown.setPosition(e.adapter.getCaretPosition()),e.dropdown.render(e._zip(d,b,c)),f||(a(),e._clearAtNext=!0)},d)}),_zip:function(b,c,d){return a.map(b,function(a){return{value:a,strategy:c,term:d}})}}),a.fn.textcomplete.Completer=b}(a),+function(a){"use strict";function b(c,d,f){this.$el=b.createElement(f),this.completer=d,this.id=d.id+"dropdown",this._data=[],this.$inputEl=a(c),this.option=f,f.listPosition&&(this.setPosition=f.listPosition),f.height&&this.$el.height(f.height);var g=this;a.each(["maxCount","placement","footer","header","noResultsMessage","className"],function(a,b){null!=f[b]&&(g[b]=f[b])}),this._bindEvents(c),e[this.id]=this}var c=a(window),d=function(a,b){var c,d,e=b.strategy.idProperty;for(c=0;c<a.length;c++)if(d=a[c],d.strategy===b.strategy)if(e){if(d.value[e]===b.value[e])return!0}else if(d.value===b.value)return!0;return!1},e={};a(document).on("click",function(b){var c=b.originalEvent&&b.originalEvent.keepTextCompleteDropdown;a.each(e,function(a,b){a!==c&&b.deactivate()})});var f={SKIP_DEFAULT:0,KEY_UP:1,KEY_DOWN:2,KEY_ENTER:3,KEY_PAGEUP:4,KEY_PAGEDOWN:5,KEY_ESCAPE:6};a.extend(b,{createElement:function(b){var c=b.appendTo;c instanceof a||(c=a(c));var d=a("<ul></ul>").addClass(b.dropdownClassName).attr("id","textcomplete-dropdown-"+b._oid).css({display:"none",left:0,position:"absolute",zIndex:b.zIndex}).appendTo(c);return d}}),a.extend(b.prototype,{$el:null,$inputEl:null,completer:null,footer:null,header:null,id:null,maxCount:null,placement:"",shown:!1,data:[],className:"",destroy:function(){this.deactivate(),this.$el.off("."+this.id),this.$inputEl.off("."+this.id),this.clear(),this.$el.remove(),this.$el=this.$inputEl=this.completer=null,delete e[this.id]},render:function(b){var c=this._buildContents(b),d=a.map(b,function(a){return a.value});if(b.length){var e=b[0].strategy;e.id?this.$el.attr("data-strategy",e.id):this.$el.removeAttr("data-strategy"),this._renderHeader(d),this._renderFooter(d),c&&(this._renderContents(c),this._fitToBottom(),this._fitToRight(),this._activateIndexedItem()),this._setScroll()}else this.noResultsMessage?this._renderNoResultsMessage(d):this.shown&&this.deactivate()},setPosition:function(b){var d="absolute";return this.$inputEl.add(this.$inputEl.parents()).each(function(){return"absolute"===a(this).css("position")?!1:"fixed"===a(this).css("position")?(b.top-=c.scrollTop(),b.left-=c.scrollLeft(),d="fixed",!1):void 0}),this.$el.css(this._applyPlacement(b)),this.$el.css({position:d}),this},clear:function(){this.$el.html(""),this.data=[],this._index=0,this._$header=this._$footer=this._$noResultsMessage=null},activate:function(){return this.shown||(this.clear(),this.$el.show(),this.className&&this.$el.addClass(this.className),this.completer.fire("textComplete:show"),this.shown=!0),this},deactivate:function(){return this.shown&&(this.$el.hide(),this.className&&this.$el.removeClass(this.className),this.completer.fire("textComplete:hide"),this.shown=!1),this},isUp:function(a){return 38===a.keyCode||a.ctrlKey&&80===a.keyCode},isDown:function(a){return 40===a.keyCode||a.ctrlKey&&78===a.keyCode},isEnter:function(a){var b=a.ctrlKey||a.altKey||a.metaKey||a.shiftKey;return!b&&(13===a.keyCode||9===a.keyCode||this.option.completeOnSpace===!0&&32===a.keyCode)},isPageup:function(a){return 33===a.keyCode},isPagedown:function(a){return 34===a.keyCode},isEscape:function(a){return 27===a.keyCode},_data:null,_index:null,_$header:null,_$noResultsMessage:null,_$footer:null,_bindEvents:function(){this.$el.on("mousedown."+this.id,".textcomplete-item",a.proxy(this._onClick,this)),this.$el.on("touchstart."+this.id,".textcomplete-item",a.proxy(this._onClick,this)),this.$el.on("mouseover."+this.id,".textcomplete-item",a.proxy(this._onMouseover,this)),this.$inputEl.on("keydown."+this.id,a.proxy(this._onKeydown,this))},_onClick:function(b){var c=a(b.target);b.preventDefault(),b.originalEvent.keepTextCompleteDropdown=this.id,c.hasClass("textcomplete-item")||(c=c.closest(".textcomplete-item"));var d=this.data[parseInt(c.data("index"),10)];this.completer.select(d.value,d.strategy,b);var e=this;setTimeout(function(){e.deactivate(),"touchstart"===b.type&&e.$inputEl.focus()},0)},_onMouseover:function(b){var c=a(b.target);b.preventDefault(),c.hasClass("textcomplete-item")||(c=c.closest(".textcomplete-item")),this._index=parseInt(c.data("index"),10),this._activateIndexedItem()},_onKeydown:function(b){if(this.shown){var c;switch(a.isFunction(this.option.onKeydown)&&(c=this.option.onKeydown(b,f)),null==c&&(c=this._defaultKeydown(b)),c){case f.KEY_UP:b.preventDefault(),this._up();break;case f.KEY_DOWN:b.preventDefault(),this._down();break;case f.KEY_ENTER:b.preventDefault(),this._enter(b);break;case f.KEY_PAGEUP:b.preventDefault(),this._pageup();break;case f.KEY_PAGEDOWN:b.preventDefault(),this._pagedown();break;case f.KEY_ESCAPE:b.preventDefault(),this.deactivate()}}},_defaultKeydown:function(a){return this.isUp(a)?f.KEY_UP:this.isDown(a)?f.KEY_DOWN:this.isEnter(a)?f.KEY_ENTER:this.isPageup(a)?f.KEY_PAGEUP:this.isPagedown(a)?f.KEY_PAGEDOWN:this.isEscape(a)?f.KEY_ESCAPE:void 0},_up:function(){0===this._index?this._index=this.data.length-1:this._index-=1,this._activateIndexedItem(),this._setScroll()},_down:function(){this._index===this.data.length-1?this._index=0:this._index+=1,this._activateIndexedItem(),this._setScroll()},_enter:function(a){var b=this.data[parseInt(this._getActiveElement().data("index"),10)];this.completer.select(b.value,b.strategy,a),this.deactivate()},_pageup:function(){var b=0,c=this._getActiveElement().position().top-this.$el.innerHeight();this.$el.children().each(function(d){return a(this).position().top+a(this).outerHeight()>c?(b=d,!1):void 0}),this._index=b,this._activateIndexedItem(),this._setScroll()},_pagedown:function(){var b=this.data.length-1,c=this._getActiveElement().position().top+this.$el.innerHeight();this.$el.children().each(function(d){return a(this).position().top>c?(b=d,!1):void 0}),this._index=b,this._activateIndexedItem(),this._setScroll()},_activateIndexedItem:function(){this.$el.find(".textcomplete-item.active").removeClass("active"),this._getActiveElement().addClass("active")},_getActiveElement:function(){return this.$el.children(".textcomplete-item:nth("+this._index+")")},_setScroll:function(){var a=this._getActiveElement(),b=a.position().top,c=a.outerHeight(),d=this.$el.innerHeight(),e=this.$el.scrollTop();0===this._index||this._index==this.data.length-1||0>b?this.$el.scrollTop(b+e):b+c>d&&this.$el.scrollTop(b+c+e-d)},_buildContents:function(a){var b,c,e,f="";for(c=0;c<a.length&&this.data.length!==this.maxCount;c++)b=a[c],d(this.data,b)||(e=this.data.length,this.data.push(b),f+='<li class="textcomplete-item" data-index="'+e+'"><a>',f+=b.strategy.template(b.value,b.term),f+="</a></li>");return f},_renderHeader:function(b){if(this.header){this._$header||(this._$header=a('<li class="textcomplete-header"></li>').prependTo(this.$el));var c=a.isFunction(this.header)?this.header(b):this.header;this._$header.html(c)}},_renderFooter:function(b){if(this.footer){this._$footer||(this._$footer=a('<li class="textcomplete-footer"></li>').appendTo(this.$el));var c=a.isFunction(this.footer)?this.footer(b):this.footer;this._$footer.html(c)}},_renderNoResultsMessage:function(b){if(this.noResultsMessage){this._$noResultsMessage||(this._$noResultsMessage=a('<li class="textcomplete-no-results-message"></li>').appendTo(this.$el));var c=a.isFunction(this.noResultsMessage)?this.noResultsMessage(b):this.noResultsMessage;this._$noResultsMessage.html(c)}},_renderContents:function(a){this._$footer?this._$footer.before(a):this.$el.append(a)},_fitToBottom:function(){var a=c.scrollTop()+c.height(),b=this.$el.height();this.$el.position().top+b>a&&(this.completer.$iframe||this.$el.offset({top:a-b}))},_fitToRight:function(){for(var a,b=this.option.rightEdgeOffset,d=this.$el.offset().left,e=this.$el.width(),f=c.width()-b;d+e>f&&(this.$el.offset({left:d-b}),a=this.$el.offset().left,!(a>=d));)d=a},_applyPlacement:function(a){return-1!==this.placement.indexOf("top")?a={top:"auto",bottom:this.$el.parent().height()-a.top+a.lineHeight,left:a.left}:(a.bottom="auto",delete a.lineHeight),-1!==this.placement.indexOf("absleft")?a.left=0:-1!==this.placement.indexOf("absright")&&(a.right=0,a.left="auto"),a}}),a.fn.textcomplete.Dropdown=b,a.extend(a.fn.textcomplete,f)}(a),+function(a){"use strict";function b(b){a.extend(this,b),this.cache&&(this.search=c(this.search))}var c=function(a){var b={};return function(c,d){b[c]?d(b[c]):a.call(this,c,function(a){b[c]=(b[c]||[]).concat(a),d.apply(null,arguments)})}};b.parse=function(c,d){return a.map(c,function(a){var c=new b(a);return c.el=d.el,c.$el=d.$el,c})},a.extend(b.prototype,{match:null,replace:null,search:null,id:null,cache:!1,context:function(){return!0},index:2,template:function(a){return a},idProperty:null}),a.fn.textcomplete.Strategy=b}(a),+function(a){"use strict";function b(){}var c=Date.now||function(){return(new Date).getTime()},d=function(a,b){var d,e,f,g,h,i=function(){var j=c()-g;b>j?d=setTimeout(i,b-j):(d=null,h=a.apply(f,e),f=e=null)};return function(){return f=this,e=arguments,g=c(),d||(d=setTimeout(i,b)),h}};a.extend(b.prototype,{id:null,completer:null,el:null,$el:null,option:null,initialize:function(b,c,e){this.el=b,this.$el=a(b),this.id=c.id+this.constructor.name,this.completer=c,this.option=e,this.option.debounce&&(this._onKeyup=d(this._onKeyup,this.option.debounce)),this._bindEvents()},destroy:function(){this.$el.off("."+this.id),this.$el=this.el=this.completer=null},select:function(){throw new Error("Not implemented")},getCaretPosition:function(){var b=this._getCaretRelativePosition(),c=this.$el.offset(),d=this.option.appendTo;if(d){d instanceof a||(d=a(d));var e=d.offsetParent().offset();c.top-=e.top,c.left-=e.left}return b.top+=c.top,b.left+=c.left,b},focus:function(){this.$el.focus()},_bindEvents:function(){this.$el.on("keyup."+this.id,a.proxy(this._onKeyup,this))},_onKeyup:function(a){this._skipSearch(a)||this.completer.trigger(this.getTextFromHeadToCaret(),!0)},_skipSearch:function(a){switch(a.keyCode){case 9:case 13:case 16:case 17:case 18:case 33:case 34:case 40:case 38:case 27:return!0}if(a.ctrlKey)switch(a.keyCode){case 78:case 80:return!0}}}),a.fn.textcomplete.Adapter=b}(a),+function(a){"use strict";function b(a,b,c){this.initialize(a,b,c)}a.extend(b.prototype,a.fn.textcomplete.Adapter.prototype,{select:function(b,c,d){var e,f=this.getTextFromHeadToCaret(),g=this.el.value.substring(this.el.selectionEnd),h=c.replace(b,d);"undefined"!=typeof h&&(a.isArray(h)&&(g=h[1]+g,h=h[0]),e=a.isFunction(c.match)?c.match(f):c.match,f=f.replace(e,h),this.$el.val(f+g),this.el.selectionStart=this.el.selectionEnd=f.length)},getTextFromHeadToCaret:function(){return this.el.value.substring(0,this.el.selectionEnd)},_getCaretRelativePosition:function(){var b=a.fn.textcomplete.getCaretCoordinates(this.el,this.el.selectionStart);return{top:b.top+this._calculateLineHeight()-this.$el.scrollTop(),left:b.left-this.$el.scrollLeft(),lineHeight:this._calculateLineHeight()}},_calculateLineHeight:function(){var a=parseInt(this.$el.css("line-height"),10);if(isNaN(a)){var b=this.el.parentNode,c=document.createElement(this.el.nodeName),d=this.el.style;c.setAttribute("style","margin:0px;padding:0px;font-family:"+d.fontFamily+";font-size:"+d.fontSize),c.innerHTML="test",b.appendChild(c),a=c.clientHeight,b.removeChild(c)}return a}}),a.fn.textcomplete.Textarea=b}(a),+function(a){"use strict";function b(b,d,e){this.initialize(b,d,e),a("<span>"+c+"</span>").css({position:"absolute",top:-9999,left:-9999}).insertBefore(b)}var c="吶";a.extend(b.prototype,a.fn.textcomplete.Textarea.prototype,{select:function(b,c,d){var e,f=this.getTextFromHeadToCaret(),g=this.el.value.substring(f.length),h=c.replace(b,d);if("undefined"!=typeof h){a.isArray(h)&&(g=h[1]+g,h=h[0]),e=a.isFunction(c.match)?c.match(f):c.match,f=f.replace(e,h),this.$el.val(f+g),this.el.focus();var i=this.el.createTextRange();i.collapse(!0),i.moveEnd("character",f.length),i.moveStart("character",f.length),i.select()}},getTextFromHeadToCaret:function(){this.el.focus();var a=document.selection.createRange();a.moveStart("character",-this.el.value.length);var b=a.text.split(c);return 1===b.length?b[0]:b[1]}}),a.fn.textcomplete.IETextarea=b}(a),+function(a){"use strict";function b(a,b,c){this.initialize(a,b,c)}a.extend(b.prototype,a.fn.textcomplete.Adapter.prototype,{select:function(b,c,d){var e=this.getTextFromHeadToCaret(),f=this.el.ownerDocument.getSelection(),g=f.getRangeAt(0),h=g.cloneRange();h.selectNodeContents(g.startContainer);var i,j=h.toString(),k=j.substring(g.startOffset),l=c.replace(b,d);if("undefined"!=typeof l){a.isArray(l)&&(k=l[1]+k,l=l[0]),i=a.isFunction(c.match)?c.match(e):c.match,e=e.replace(i,l).replace(/ $/,"&nbsp"),g.selectNodeContents(g.startContainer),g.deleteContents();var m=this.el.ownerDocument.createElement("div");m.innerHTML=e;var n=this.el.ownerDocument.createElement("div");n.innerHTML=k;for(var o,p,q=this.el.ownerDocument.createDocumentFragment();o=m.firstChild;)p=q.appendChild(o);for(;o=n.firstChild;)q.appendChild(o);g.insertNode(q),g.setStartAfter(p),g.collapse(!0),f.removeAllRanges(),f.addRange(g)}},_getCaretRelativePosition:function(){var b=this.el.ownerDocument.getSelection().getRangeAt(0).cloneRange(),c=this.el.ownerDocument.createElement("span");b.insertNode(c),b.selectNodeContents(c),b.deleteContents();var d=a(c),e=d.offset();if(e.left-=this.$el.offset().left,e.top+=d.height()-this.$el.offset().top,e.lineHeight=d.height(),this.completer.$iframe){var f=this.completer.$iframe.offset();e.top+=f.top,e.left+=f.left,e.top-=this.$el.scrollTop()}return d.remove(),e},getTextFromHeadToCaret:function(){var a=this.el.ownerDocument.getSelection().getRangeAt(0),b=a.cloneRange();return b.selectNodeContents(a.startContainer),b.toString().substring(0,a.startOffset)}}),a.fn.textcomplete.ContentEditable=b}(a),+function(a){"use strict";function b(a,b,c){this.initialize(a,b,c)}a.extend(b.prototype,a.fn.textcomplete.ContentEditable.prototype,{_bindEvents:function(){var b=this;this.option.ckeditor_instance.on("key",function(a){var c=a.data;return b._onKeyup(c),b.completer.dropdown.shown&&b._skipSearch(c)?!1:void 0},null,null,1),this.$el.on("keyup."+this.id,a.proxy(this._onKeyup,this))}}),a.fn.textcomplete.CKEditor=b}(a),function(a){function b(a,b,f){if(!d)throw new Error("textarea-caret-position#getCaretCoordinates should only be called in a browser");var g=f&&f.debug||!1;if(g){var h=document.querySelector("#input-textarea-caret-position-mirror-div");h&&h.parentNode.removeChild(h)}var i=document.createElement("div");i.id="input-textarea-caret-position-mirror-div",document.body.appendChild(i);var j=i.style,k=window.getComputedStyle?getComputedStyle(a):a.currentStyle;j.whiteSpace="pre-wrap","INPUT"!==a.nodeName&&(j.wordWrap="break-word"),j.position="absolute",g||(j.visibility="hidden"),c.forEach(function(a){j[a]=k[a]}),e?a.scrollHeight>parseInt(k.height)&&(j.overflowY="scroll"):j.overflow="hidden",i.textContent=a.value.substring(0,b),"INPUT"===a.nodeName&&(i.textContent=i.textContent.replace(/\s/g," "));var l=document.createElement("span");l.textContent=a.value.substring(b)||".",i.appendChild(l);var m={top:l.offsetTop+parseInt(k.borderTopWidth),left:l.offsetLeft+parseInt(k.borderLeftWidth)};return g?l.style.backgroundColor="#aaa":document.body.removeChild(i),m}var c=["direction","boxSizing","width","height","overflowX","overflowY","borderTopWidth","borderRightWidth","borderBottomWidth","borderLeftWidth","borderStyle","paddingTop","paddingRight","paddingBottom","paddingLeft","fontStyle","fontVariant","fontWeight","fontStretch","fontSize","fontSizeAdjust","lineHeight","fontFamily","textAlign","textTransform","textIndent","textDecoration","letterSpacing","wordSpacing","tabSize","MozTabSize"],d="undefined"!=typeof window,e=d&&null!=window.mozInnerScreenX;a.fn.textcomplete.getCaretCoordinates=b}(a),a});
//# sourceMappingURL=dist/jquery.textcomplete.min.map \ No newline at end of file
diff --git a/library/jquery-textcomplete/jquery.textcomplete.min.map b/library/jquery-textcomplete/jquery.textcomplete.min.map
new file mode 100644
index 000000000..0e249c1c4
--- /dev/null
+++ b/library/jquery-textcomplete/jquery.textcomplete.min.map
@@ -0,0 +1 @@
+{"version":3,"file":"dist/jquery.textcomplete.min.js","sources":["dist/jquery.textcomplete.js"],"names":["factory","define","amd","module","exports","$","require","jQuery","Error","warn","message","console","id","fn","textcomplete","strategies","option","args","Array","prototype","slice","call","arguments","this","each","self","$this","completer","data","_oid","Completer","shift","apply","removeData","obj","name","register","Strategy","parse","el","$el","element","uniqueId","views","extend","defaults","is","isContentEditable","contentEditable","ownerDocument","activeElement","initialize","one","adapter","CKEDITOR","on","event","editor","once","event2","editable","ckeditor_instance","lock","func","locked","queuedArgsToReplay","unshift","replayOrFree","replayArgs","undefined","isString","Object","toString","appendTo","className","dropdownClassName","maxCount","zIndex","rightEdgeOffset","dropdown","$iframe","get","prop","document","window","frames","length","iframeIndex","frameElement","Dropdown","Adapter","viewName","selectionEnd","destroy","off","deactivate","trigger","text","skipUnchangedTerm","getTextFromHeadToCaret","searchQuery","_extractSearchQuery","term","_term","_search","fire","eventName","push","select","value","strategy","e","focus","_clearAtNext","i","context","matchRegexp","isFunction","match","index","free","search","stillSearching","shown","activate","clear","setPosition","getCaretPosition","render","_zip","map","createElement","_data","$inputEl","listPosition","height","_i","_bindEvents","dropdownViews","$window","include","zippedData","datum","elem","idProperty","originalEvent","keepTextCompleteDropdown","key","view","commands","SKIP_DEFAULT","KEY_UP","KEY_DOWN","KEY_ENTER","KEY_PAGEUP","KEY_PAGEDOWN","KEY_ESCAPE","$parent","addClass","attr","css","display","left","position","footer","header","placement","remove","contentsHtml","_buildContents","unzippedData","d","removeAttr","_renderHeader","_renderFooter","_renderContents","_fitToBottom","_fitToRight","_activateIndexedItem","_setScroll","noResultsMessage","_renderNoResultsMessage","pos","add","parents","top","scrollTop","scrollLeft","_applyPlacement","html","_index","_$header","_$footer","_$noResultsMessage","show","hide","removeClass","isUp","keyCode","ctrlKey","isDown","isEnter","modifiers","altKey","metaKey","shiftKey","completeOnSpace","isPageup","isPagedown","isEscape","proxy","_onClick","_onMouseover","_onKeydown","target","preventDefault","hasClass","closest","parseInt","setTimeout","type","command","onKeydown","_defaultKeydown","_up","_down","_enter","_pageup","_pagedown","_getActiveElement","threshold","innerHeight","children","outerHeight","find","$activeEl","itemTop","itemHeight","visibleHeight","visibleTop","template","prependTo","before","append","windowScrollBottom","offset","tolerance","lastOffset","width","maxLeft","indexOf","bottom","parent","lineHeight","right","options","cache","memoize","memo","callback","concat","strategiesArray","params","strategyObj","replace","now","Date","getTime","debounce","wait","timeout","timestamp","result","later","last","constructor","_onKeyup","_getCaretRelativePosition","parentOffset","offsetParent","_skipSearch","clickEvent","Textarea","regExp","pre","post","substring","newSubstr","isArray","val","selectionStart","p","getCaretCoordinates","_calculateLineHeight","isNaN","parentNode","temp","nodeName","style","setAttribute","fontFamily","fontSize","innerHTML","appendChild","clientHeight","removeChild","IETextarea","sentinelChar","insertBefore","range","createTextRange","collapse","moveEnd","moveStart","selection","createRange","arr","split","ContentEditable","sel","getSelection","getRangeAt","cloneRange","selectNodeContents","startContainer","content","startOffset","deleteContents","preWrapper","postWrapper","childNode","lastOfPre","fragment","createDocumentFragment","firstChild","insertNode","setStartAfter","removeAllRanges","addRange","node","$node","iframePosition","CKEditor","domEvent","isBrowser","debug","querySelector","div","body","computed","getComputedStyle","currentStyle","whiteSpace","wordWrap","visibility","properties","forEach","isFirefox","scrollHeight","overflowY","overflow","textContent","span","coordinates","offsetTop","offsetLeft","backgroundColor","mozInnerScreenX"],"mappings":";CAAC,SAAUA,GACT,GAAsB,kBAAXC,SAAyBA,OAAOC,IAEzCD,QAAQ,UAAWD,OACd,IAAsB,gBAAXG,SAAuBA,OAAOC,QAAS,CACvD,GAAIC,GAAIC,QAAQ,SAChBH,QAAOC,QAAUJ,EAAQK,OAGzBL,GAAQO,SAEV,SAAUA,GAUZ,GAAsB,mBAAXA,GACT,KAAM,IAAIC,OAAM,sCAw7ClB,QAr7CC,SAAUH,GACT,YAEA,IAAII,GAAO,SAAUC,GACfC,QAAQF,MAAQE,QAAQF,KAAKC,IAG/BE,EAAK,CAETP,GAAEQ,GAAGC,aAAe,SAAUC,EAAYC,GACxC,GAAIC,GAAOC,MAAMC,UAAUC,MAAMC,KAAKC,UACtC,OAAOC,MAAKC,KAAK,WACf,GAAIC,GAAOF,KACPG,EAAQrB,EAAEkB,MACVI,EAAYD,EAAME,KAAK,eAO3B,IANKD,IACHX,IAAWA,MACXA,EAAOa,KAAOjB,IACde,EAAY,GAAItB,GAAEQ,GAAGC,aAAagB,UAAUP,KAAMP,GAClDU,EAAME,KAAK,eAAgBD,IAEH,gBAAfZ,GAAyB,CAClC,IAAKY,EAAW,MAChBV,GAAKc,QACLJ,EAAUZ,GAAYiB,MAAML,EAAWV,GACpB,YAAfF,GACFW,EAAMO,WAAW,oBAKnB5B,GAAEmB,KAAKT,EAAY,SAAUmB,GAC3B7B,EAAEmB,MAAM,SAAU,SAAU,YAAa,YAAa,SAAUW,GAC1DD,EAAIC,KACNR,EAAUX,OAAOmB,GAAQD,EAAIC,GAC7B1B,EAAK0B,EAAO,wDACLD,GAAIC,QAIjBR,EAAUS,SAAS/B,EAAEQ,GAAGC,aAAauB,SAASC,MAAMvB,GAClDwB,GAAId,EACJe,IAAKd,SAMbnB,IAED,SAAUF,GACT,YAgEA,SAASyB,GAAUW,EAASzB,GAO1B,GANAO,KAAKiB,IAAanC,EAAEoC,GACpBlB,KAAKX,GAAa,eAAiB8B,IACnCnB,KAAKR,cACLQ,KAAKoB,SACLpB,KAAKP,OAAaX,EAAEuC,UAAWd,EAAUe,SAAU7B,KAE9CO,KAAKiB,IAAIM,GAAG,qBAAwBvB,KAAKiB,IAAIM,GAAG,uBAA0BvB,KAAKiB,IAAIM,GAAG,aAAgBL,EAAQM,mBAAgD,QAA3BN,EAAQO,iBAC9I,KAAM,IAAIxC,OAAM,kEAIlB,IAAIiC,IAAYA,EAAQQ,cAAcC,cAEpC3B,KAAK4B,iBACA,CAEL,GAAI1B,GAAOF,IACXA,MAAKiB,IAAIY,IAAI,SAAW7B,KAAKX,GAAI,WAAca,EAAK0B,eAG9C5B,KAAKP,OAAOqC,SAAkC,YAAvB9B,KAAKP,OAAOqC,SAA6C,mBAAZC,YAA4B/B,KAAKiB,IAAIM,GAAG,aAChHQ,SAASC,GAAG,gBAAiB,SAASC,GACpCA,EAAMC,OAAOC,KAAK,QAAS,SAASC,GAElClC,EAAKe,IAAMnC,EAAEmD,EAAMC,OAAOG,WAAWvD,GAChCoB,EAAKT,OAAOqC,UACf5B,EAAKT,OAAOqC,QAAUhD,EAAEQ,GAAGC,aAAuB,SAClDW,EAAKT,OAAO6C,kBAAoBL,EAAMC,QAExChC,EAAK0B,kBAtEf,GAAIW,GAAO,SAAUC,GACnB,GAAIC,GAAQC,CAEZ,OAAO,YAEL,GAAIhD,GAAOC,MAAMC,UAAUC,MAAMC,KAAKC,UACtC,IAAI0C,EAKF,YADAC,EAAqBhD,EAGvB+C,IAAS,CACT,IAAIvC,GAAOF,IACXN,GAAKiD,QAAQ,QAASC,KACpB,GAAIF,EAAoB,CAMtB,GAAIG,GAAaH,CACjBA,GAAqBI,OACrBD,EAAWF,QAAQC,GACnBJ,EAAK/B,MAAMP,EAAM2C,OAEjBJ,IAAS,IAGbD,EAAK/B,MAAMT,KAAMN,KAIjBqD,EAAW,SAAUpC,GACvB,MAA+C,oBAAxCqC,OAAOpD,UAAUqD,SAASnD,KAAKa,IAGpCQ,EAAW,CAuCfZ,GAAUe,UACR4B,SAAU,OACVC,UAAW,GACXC,kBAAmB,sCACnBC,SAAU,GACVC,OAAQ,MACRC,gBAAiB,IAGnBzE,EAAEuC,OAAOd,EAAUX,WAIjBP,GAAY,KACZI,OAAY,KACZD,WAAY,KACZsC,QAAY,KACZ0B,SAAY,KACZvC,IAAY,KACZwC,QAAY,KAKZ7B,WAAY,WACV,GAAIV,GAAUlB,KAAKiB,IAAIyC,IAAI,EAI3B,IAAI1D,KAAKiB,IAAI0C,KAAK,mBAAqBC,UAAYC,OAAOC,OAAOC,OAC/D,IAAK,GAAIC,GAAc,EAAGA,EAAcH,OAAOC,OAAOC,OAAQC,IAC5D,GAAIhE,KAAKiB,IAAI0C,KAAK,mBAAqBE,OAAOC,OAAOE,GAAaJ,SAAU,CAC1E5D,KAAKyD,QAAU3E,EAAE+E,OAAOC,OAAOE,GAAaC,aAC5C,OAONjE,KAAKwD,SAAW,GAAI1E,GAAEQ,GAAGC,aAAa2E,SAAShD,EAASlB,KAAMA,KAAKP,OACnE,IAAI0E,GAASC,CACTpE,MAAKP,OAAOqC,QACdqC,EAAUnE,KAAKP,OAAOqC,SAGpBsC,EADEpE,KAAKiB,IAAIM,GAAG,aAAevB,KAAKiB,IAAIM,GAAG,qBAAuBvB,KAAKiB,IAAIM,GAAG,sBACjC,gBAAzBL,GAAQmD,aAA4B,WAAa,aAExD,kBAEbF,EAAUrF,EAAEQ,GAAGC,aAAa6E,IAE9BpE,KAAK8B,QAAU,GAAIqC,GAAQjD,EAASlB,KAAMA,KAAKP,SAGjD6E,QAAS,WACPtE,KAAKiB,IAAIsD,IAAI,IAAMvE,KAAKX,IACpBW,KAAK8B,SACP9B,KAAK8B,QAAQwC,UAEXtE,KAAKwD,UACPxD,KAAKwD,SAASc,UAEhBtE,KAAKiB,IAAMjB,KAAK8B,QAAU9B,KAAKwD,SAAW,MAG5CgB,WAAY,WACNxE,KAAKwD,UACPxD,KAAKwD,SAASgB,cAKlBC,QAAS,SAAUC,EAAMC,GAClB3E,KAAKwD,UAAYxD,KAAK4B,aACnB,MAAR8C,IAAiBA,EAAO1E,KAAK8B,QAAQ8C,yBACrC,IAAIC,GAAc7E,KAAK8E,oBAAoBJ,EAC3C,IAAIG,EAAYd,OAAQ,CACtB,GAAIgB,GAAOF,EAAY,EAEvB,IAAIF,GAAqB3E,KAAKgF,QAAUD,GAAiB,KAATA,EAAe,MAC/D/E,MAAKgF,MAAQD,EACb/E,KAAKiF,QAAQxE,MAAMT,KAAM6E,OAEzB7E,MAAKgF,MAAQ,KACbhF,KAAKwD,SAASgB,cAIlBU,KAAM,SAAUC,GACd,GAAIzF,GAAOC,MAAMC,UAAUC,MAAMC,KAAKC,UAAW,EAEjD,OADAC,MAAKiB,IAAIwD,QAAQU,EAAWzF,GACrBM,MAGTa,SAAU,SAAUrB,GAClBG,MAAMC,UAAUwF,KAAK3E,MAAMT,KAAKR,WAAYA,IAS9C6F,OAAQ,SAAUC,EAAOC,EAAUC,GACjCxF,KAAKgF,MAAQ,KACbhF,KAAK8B,QAAQuD,OAAOC,EAAOC,EAAUC,GACrCxF,KAAKkF,KAAK,UAAUA,KAAK,sBAAuBI,EAAOC,GACvDvF,KAAK8B,QAAQ2D,SAMfC,cAAc,EACdV,MAAc,KASdF,oBAAqB,SAAUJ,GAC7B,IAAK,GAAIiB,GAAI,EAAGA,EAAI3F,KAAKR,WAAWuE,OAAQ4B,IAAK,CAC/C,GAAIJ,GAAWvF,KAAKR,WAAWmG,GAC3BC,EAAUL,EAASK,QAAQlB,EAC/B,IAAIkB,GAAuB,KAAZA,EAAgB,CAC7B,GAAIC,GAAc/G,EAAEgH,WAAWP,EAASQ,OAASR,EAASQ,MAAMrB,GAAQa,EAASQ,KAC7EhD,GAAS6C,KAAYlB,EAAOkB,EAChC,IAAIG,GAAQrB,EAAKqB,MAAMF,EACvB,IAAIE,EAAS,OAAQR,EAAUQ,EAAMR,EAASS,OAAQD,IAG1D,UAIFd,QAAS1C,EAAK,SAAU0D,EAAMV,EAAUR,EAAMgB,GAC5C,GAAI7F,GAAOF,IACXuF,GAASW,OAAOnB,EAAM,SAAU1E,EAAM8F,GAC/BjG,EAAKsD,SAAS4C,OACjBlG,EAAKsD,SAAS6C,WAEZnG,EAAKwF,eAEPxF,EAAKsD,SAAS8C,QACdpG,EAAKwF,cAAe,GAEtBxF,EAAKsD,SAAS+C,YAAYrG,EAAK4B,QAAQ0E,oBACvCtG,EAAKsD,SAASiD,OAAOvG,EAAKwG,KAAKrG,EAAMkF,EAAUR,IAC1CoB,IAEHF,IACA/F,EAAKwF,cAAe,IAErBK,KASLW,KAAM,SAAUrG,EAAMkF,EAAUR,GAC9B,MAAOjG,GAAE6H,IAAItG,EAAM,SAAUiF,GAC3B,OAASA,MAAOA,EAAOC,SAAUA,EAAUR,KAAMA,QAKvDjG,EAAEQ,GAAGC,aAAagB,UAAYA,GAC9BvB,IAED,SAAUF,GACT,YA2CA,SAASoF,GAAShD,EAASd,EAAWX,GACpCO,KAAKiB,IAAYiD,EAAS0C,cAAcnH,GACxCO,KAAKI,UAAYA,EACjBJ,KAAKX,GAAYe,EAAUf,GAAK,WAChCW,KAAK6G,SACL7G,KAAK8G,SAAYhI,EAAEoC,GACnBlB,KAAKP,OAAYA,EAGbA,EAAOsH,eAAgB/G,KAAKuG,YAAc9G,EAAOsH,cACjDtH,EAAOuH,QAAUhH,KAAKiB,IAAI+F,OAAOvH,EAAOuH,OAC5C,IAAI9G,GAAOF,IACXlB,GAAEmB,MAAM,WAAY,YAAa,SAAU,SAAU,mBAAoB,aAAc,SAAUgH,EAAIrG,GAC/E,MAAhBnB,EAAOmB,KAAiBV,EAAKU,GAAQnB,EAAOmB,MAElDZ,KAAKkH,YAAYhG,GACjBiG,EAAcnH,KAAKX,IAAMW,KAzD3B,GAAIoH,GAAUtI,EAAE+E,QAEZwD,EAAU,SAAUC,EAAYC,GAClC,GAAI5B,GAAG6B,EACHC,EAAaF,EAAMhC,SAASkC,UAChC,KAAK9B,EAAI,EAAGA,EAAI2B,EAAWvD,OAAQ4B,IAEjC,GADA6B,EAAOF,EAAW3B,GACd6B,EAAKjC,WAAagC,EAAMhC,SAC5B,GAAIkC,GACF,GAAID,EAAKlC,MAAMmC,KAAgBF,EAAMjC,MAAMmC,GAAa,OAAO,MAE/D,IAAID,EAAKlC,QAAUiC,EAAMjC,MAAO,OAAO,CAG3C,QAAO,GAGL6B,IACJrI,GAAE8E,UAAU5B,GAAG,QAAS,SAAUwD,GAChC,GAAInG,GAAKmG,EAAEkC,eAAiBlC,EAAEkC,cAAcC,wBAC5C7I,GAAEmB,KAAKkH,EAAe,SAAUS,EAAKC,GAC/BD,IAAQvI,GAAMwI,EAAKrD,gBAI3B,IAAIsD,IACFC,aAAc,EACdC,OAAQ,EACRC,SAAU,EACVC,UAAW,EACXC,WAAY,EACZC,aAAc,EACdC,WAAY,EA4BdvJ,GAAEuC,OAAO6C,GAIP0C,cAAe,SAAUnH,GACvB,GAAI6I,GAAU7I,EAAOyD,QACfoF,aAAmBxJ,KAAMwJ,EAAUxJ,EAAEwJ,GAC3C,IAAIrH,GAAMnC,EAAE,aACTyJ,SAAS9I,EAAO2D,mBAChBoF,KAAK,KAAM,yBAA2B/I,EAAOa,MAC7CmI,KACCC,QAAS,OACTC,KAAM,EACNC,SAAU,WACVtF,OAAQ7D,EAAO6D,SAEhBJ,SAASoF,EACZ,OAAOrH,MAIXnC,EAAEuC,OAAO6C,EAAStE,WAIhBqB,IAAW,KACX6F,SAAW,KACX1G,UAAW,KACXyI,OAAW,KACXC,OAAW,KACXzJ,GAAW,KACXgE,SAAW,KACX0F,UAAW,GACX3C,OAAW,EACX/F,QACA8C,UAAW,GAKXmB,QAAS,WAEPtE,KAAKwE,aAELxE,KAAKiB,IAAIsD,IAAI,IAAMvE,KAAKX,IACxBW,KAAK8G,SAASvC,IAAI,IAAMvE,KAAKX,IAC7BW,KAAKsG,QACLtG,KAAKiB,IAAI+H,SACThJ,KAAKiB,IAAMjB,KAAK8G,SAAW9G,KAAKI,UAAY,WACrC+G,GAAcnH,KAAKX,KAG5BoH,OAAQ,SAAUa,GAChB,GAAI2B,GAAejJ,KAAKkJ,eAAe5B,GACnC6B,EAAerK,EAAE6H,IAAIW,EAAY,SAAU8B,GAAK,MAAOA,GAAE9D,OAC7D,IAAIgC,EAAWvD,OAAQ,CACrB,GAAIwB,GAAW+B,EAAW,GAAG/B,QACzBA,GAASlG,GACXW,KAAKiB,IAAIuH,KAAK,gBAAiBjD,EAASlG,IAExCW,KAAKiB,IAAIoI,WAAW,iBAEtBrJ,KAAKsJ,cAAcH,GACnBnJ,KAAKuJ,cAAcJ,GACfF,IACFjJ,KAAKwJ,gBAAgBP,GACrBjJ,KAAKyJ,eACLzJ,KAAK0J,cACL1J,KAAK2J,wBAEP3J,KAAK4J,iBACI5J,MAAK6J,iBACd7J,KAAK8J,wBAAwBX,GACpBnJ,KAAKoG,OACdpG,KAAKwE,cAIT+B,YAAa,SAAUwD,GAIrB,GAAInB,GAAW,UAef,OAbA5I,MAAK8G,SAASkD,IAAIhK,KAAK8G,SAASmD,WAAWhK,KAAK,WAC9C,MAA+B,aAA5BnB,EAAEkB,MAAMyI,IAAI,aACN,EACsB,UAA5B3J,EAAEkB,MAAMyI,IAAI,aACbsB,EAAIG,KAAO9C,EAAQ+C,YACnBJ,EAAIpB,MAAQvB,EAAQgD,aACpBxB,EAAW,SACJ,GAJT,SAOF5I,KAAKiB,IAAIwH,IAAIzI,KAAKqK,gBAAgBN,IAClC/J,KAAKiB,IAAIwH,KAAMG,SAAUA,IAElB5I,MAGTsG,MAAO,WACLtG,KAAKiB,IAAIqJ,KAAK,IACdtK,KAAKK,QACLL,KAAKuK,OAAS,EACdvK,KAAKwK,SAAWxK,KAAKyK,SAAWzK,KAAK0K,mBAAqB,MAG5DrE,SAAU,WAQR,MAPKrG,MAAKoG,QACRpG,KAAKsG,QACLtG,KAAKiB,IAAI0J,OACL3K,KAAKmD,WAAanD,KAAKiB,IAAIsH,SAASvI,KAAKmD,WAC7CnD,KAAKI,UAAU8E,KAAK,qBACpBlF,KAAKoG,OAAQ,GAERpG,MAGTwE,WAAY,WAOV,MANIxE,MAAKoG,QACPpG,KAAKiB,IAAI2J,OACL5K,KAAKmD,WAAanD,KAAKiB,IAAI4J,YAAY7K,KAAKmD,WAChDnD,KAAKI,UAAU8E,KAAK,qBACpBlF,KAAKoG,OAAQ,GAERpG,MAGT8K,KAAM,SAAUtF,GACd,MAAqB,MAAdA,EAAEuF,SAAmBvF,EAAEwF,SAAyB,KAAdxF,EAAEuF,SAG7CE,OAAQ,SAAUzF,GAChB,MAAqB,MAAdA,EAAEuF,SAAmBvF,EAAEwF,SAAyB,KAAdxF,EAAEuF,SAG7CG,QAAS,SAAU1F,GACjB,GAAI2F,GAAY3F,EAAEwF,SAAWxF,EAAE4F,QAAU5F,EAAE6F,SAAW7F,EAAE8F,QACxD,QAAQH,IAA4B,KAAd3F,EAAEuF,SAAgC,IAAdvF,EAAEuF,SAAkB/K,KAAKP,OAAO8L,mBAAoB,GAAsB,KAAd/F,EAAEuF,UAG1GS,SAAU,SAAUhG,GAClB,MAAqB,MAAdA,EAAEuF,SAGXU,WAAY,SAAUjG,GACpB,MAAqB,MAAdA,EAAEuF,SAGXW,SAAU,SAAUlG,GAClB,MAAqB,MAAdA,EAAEuF,SAMXlE,MAAU,KACV0D,OAAU,KACVC,SAAU,KACVE,mBAAoB,KACpBD,SAAU,KAKVvD,YAAa,WACXlH,KAAKiB,IAAIe,GAAG,aAAehC,KAAKX,GAAI,qBAAsBP,EAAE6M,MAAM3L,KAAK4L,SAAU5L,OACjFA,KAAKiB,IAAIe,GAAG,cAAgBhC,KAAKX,GAAI,qBAAsBP,EAAE6M,MAAM3L,KAAK4L,SAAU5L,OAClFA,KAAKiB,IAAIe,GAAG,aAAehC,KAAKX,GAAI,qBAAsBP,EAAE6M,MAAM3L,KAAK6L,aAAc7L,OACrFA,KAAK8G,SAAS9E,GAAG,WAAahC,KAAKX,GAAIP,EAAE6M,MAAM3L,KAAK8L,WAAY9L,QAGlE4L,SAAU,SAAUpG,GAClB,GAAIvE,GAAMnC,EAAE0G,EAAEuG,OACdvG,GAAEwG,iBACFxG,EAAEkC,cAAcC,yBAA2B3H,KAAKX,GAC3C4B,EAAIgL,SAAS,uBAChBhL,EAAMA,EAAIiL,QAAQ,sBAEpB,IAAI3E,GAAQvH,KAAKK,KAAK8L,SAASlL,EAAIZ,KAAK,SAAU,IAClDL,MAAKI,UAAUiF,OAAOkC,EAAMjC,MAAOiC,EAAMhC,SAAUC,EACnD,IAAItF,GAAOF,IAGXoM,YAAW,WACTlM,EAAKsE,aACU,eAAXgB,EAAE6G,MACJnM,EAAK4G,SAASrB,SAEf,IAILoG,aAAc,SAAUrG,GACtB,GAAIvE,GAAMnC,EAAE0G,EAAEuG,OACdvG,GAAEwG,iBACG/K,EAAIgL,SAAS,uBAChBhL,EAAMA,EAAIiL,QAAQ,uBAEpBlM,KAAKuK,OAAS4B,SAASlL,EAAIZ,KAAK,SAAU,IAC1CL,KAAK2J,wBAGPmC,WAAY,SAAUtG,GACpB,GAAKxF,KAAKoG,MAAV,CAEA,GAAIkG,EAUJ,QARIxN,EAAEgH,WAAW9F,KAAKP,OAAO8M,aAC3BD,EAAUtM,KAAKP,OAAO8M,UAAU/G,EAAGsC,IAGtB,MAAXwE,IACFA,EAAUtM,KAAKwM,gBAAgBhH,IAGzB8G,GACN,IAAKxE,GAASE,OACZxC,EAAEwG,iBACFhM,KAAKyM,KACL,MACF,KAAK3E,GAASG,SACZzC,EAAEwG,iBACFhM,KAAK0M,OACL,MACF,KAAK5E,GAASI,UACZ1C,EAAEwG,iBACFhM,KAAK2M,OAAOnH,EACZ,MACF,KAAKsC,GAASK,WACZ3C,EAAEwG,iBACFhM,KAAK4M,SACL,MACF,KAAK9E,GAASM,aACZ5C,EAAEwG,iBACFhM,KAAK6M,WACL,MACF,KAAK/E,GAASO,WACZ7C,EAAEwG,iBACFhM,KAAKwE,gBAKXgI,gBAAiB,SAAUhH,GACzB,MAAIxF,MAAK8K,KAAKtF,GACLsC,EAASE,OACPhI,KAAKiL,OAAOzF,GACdsC,EAASG,SACPjI,KAAKkL,QAAQ1F,GACfsC,EAASI,UACPlI,KAAKwL,SAAShG,GAChBsC,EAASK,WACPnI,KAAKyL,WAAWjG,GAClBsC,EAASM,aACPpI,KAAK0L,SAASlG,GAChBsC,EAASO,WADX,QAKToE,IAAK,WACiB,IAAhBzM,KAAKuK,OACPvK,KAAKuK,OAASvK,KAAKK,KAAK0D,OAAS,EAEjC/D,KAAKuK,QAAU,EAEjBvK,KAAK2J,uBACL3J,KAAK4J,cAGP8C,MAAO,WACD1M,KAAKuK,SAAWvK,KAAKK,KAAK0D,OAAS,EACrC/D,KAAKuK,OAAS,EAEdvK,KAAKuK,QAAU,EAEjBvK,KAAK2J,uBACL3J,KAAK4J,cAGP+C,OAAQ,SAAUnH,GAChB,GAAI+B,GAAQvH,KAAKK,KAAK8L,SAASnM,KAAK8M,oBAAoBzM,KAAK,SAAU,IACvEL,MAAKI,UAAUiF,OAAOkC,EAAMjC,MAAOiC,EAAMhC,SAAUC,GACnDxF,KAAKwE,cAGPoI,QAAS,WACP,GAAIb,GAAS,EACTgB,EAAY/M,KAAK8M,oBAAoBlE,WAAWsB,IAAMlK,KAAKiB,IAAI+L,aACnEhN,MAAKiB,IAAIgM,WAAWhN,KAAK,SAAU0F,GACjC,MAAI7G,GAAEkB,MAAM4I,WAAWsB,IAAMpL,EAAEkB,MAAMkN,cAAgBH,GACnDhB,EAASpG,GACF,GAFT,SAKF3F,KAAKuK,OAASwB,EACd/L,KAAK2J,uBACL3J,KAAK4J,cAGPiD,UAAW,WACT,GAAId,GAAS/L,KAAKK,KAAK0D,OAAS,EAC5BgJ,EAAY/M,KAAK8M,oBAAoBlE,WAAWsB,IAAMlK,KAAKiB,IAAI+L,aACnEhN,MAAKiB,IAAIgM,WAAWhN,KAAK,SAAU0F,GACjC,MAAI7G,GAAEkB,MAAM4I,WAAWsB,IAAM6C,GAC3BhB,EAASpG,GACF,GAFT,SAKF3F,KAAKuK,OAASwB,EACd/L,KAAK2J,uBACL3J,KAAK4J,cAGPD,qBAAsB,WACpB3J,KAAKiB,IAAIkM,KAAK,6BAA6BtC,YAAY,UACvD7K,KAAK8M,oBAAoBvE,SAAS,WAGpCuE,kBAAmB,WACjB,MAAO9M,MAAKiB,IAAIgM,SAAS,0BAA4BjN,KAAKuK,OAAS,MAGrEX,WAAY,WACV,GAAIwD,GAAYpN,KAAK8M,oBACjBO,EAAUD,EAAUxE,WAAWsB,IAC/BoD,EAAaF,EAAUF,cACvBK,EAAgBvN,KAAKiB,IAAI+L,cACzBQ,EAAaxN,KAAKiB,IAAIkJ,WACN,KAAhBnK,KAAKuK,QAAgBvK,KAAKuK,QAAUvK,KAAKK,KAAK0D,OAAS,GAAe,EAAVsJ,EAC9DrN,KAAKiB,IAAIkJ,UAAUkD,EAAUG,GACpBH,EAAUC,EAAaC,GAChCvN,KAAKiB,IAAIkJ,UAAUkD,EAAUC,EAAaE,EAAaD,IAI3DrE,eAAgB,SAAU5B,GACxB,GAAIC,GAAO5B,EAAGK,EACVsE,EAAO,EACX,KAAK3E,EAAI,EAAGA,EAAI2B,EAAWvD,QACrB/D,KAAKK,KAAK0D,SAAW/D,KAAKqD,SADGsC,IAEjC4B,EAAQD,EAAW3B,GACf0B,EAAQrH,KAAKK,KAAMkH,KACvBvB,EAAQhG,KAAKK,KAAK0D,OAClB/D,KAAKK,KAAK+E,KAAKmC,GACf+C,GAAQ,6CAA+CtE,EAAQ,QAC/DsE,GAAU/C,EAAMhC,SAASkI,SAASlG,EAAMjC,MAAOiC,EAAMxC,MACrDuF,GAAQ,YAEV,OAAOA,IAGThB,cAAe,SAAUH,GACvB,GAAInJ,KAAK8I,OAAQ,CACV9I,KAAKwK,WACRxK,KAAKwK,SAAW1L,EAAE,yCAAyC4O,UAAU1N,KAAKiB,KAE5E,IAAIqJ,GAAOxL,EAAEgH,WAAW9F,KAAK8I,QAAU9I,KAAK8I,OAAOK,GAAgBnJ,KAAK8I,MACxE9I,MAAKwK,SAASF,KAAKA,KAIvBf,cAAe,SAAUJ,GACvB,GAAInJ,KAAK6I,OAAQ,CACV7I,KAAKyK,WACRzK,KAAKyK,SAAW3L,EAAE,yCAAyCoE,SAASlD,KAAKiB,KAE3E,IAAIqJ,GAAOxL,EAAEgH,WAAW9F,KAAK6I,QAAU7I,KAAK6I,OAAOM,GAAgBnJ,KAAK6I,MACxE7I,MAAKyK,SAASH,KAAKA,KAIvBR,wBAAyB,SAAUX,GACjC,GAAInJ,KAAK6J,iBAAkB,CACpB7J,KAAK0K,qBACR1K,KAAK0K,mBAAqB5L,EAAE,qDAAqDoE,SAASlD,KAAKiB,KAEjG,IAAIqJ,GAAOxL,EAAEgH,WAAW9F,KAAK6J,kBAAoB7J,KAAK6J,iBAAiBV,GAAgBnJ,KAAK6J,gBAC5F7J,MAAK0K,mBAAmBJ,KAAKA,KAIjCd,gBAAiB,SAAUc,GACrBtK,KAAKyK,SACPzK,KAAKyK,SAASkD,OAAOrD,GAErBtK,KAAKiB,IAAI2M,OAAOtD,IAIpBb,aAAc,WACZ,GAAIoE,GAAqBzG,EAAQ+C,YAAc/C,EAAQJ,SACnDA,EAAShH,KAAKiB,IAAI+F,QACjBhH,MAAKiB,IAAI2H,WAAWsB,IAAMlD,EAAU6G,IAElC7N,KAAKI,UAAUqD,SAClBzD,KAAKiB,IAAI6M,QAAQ5D,IAAK2D,EAAqB7G,MAKjD0C,YAAa,WASX,IAJA,GACyCoE,GADrCC,EAAY/N,KAAKP,OAAO8D,gBACxByK,EAAahO,KAAKiB,IAAI6M,SAASnF,KAC/BsF,EAAQjO,KAAKiB,IAAIgN,QACjBC,EAAU9G,EAAQ6G,QAAUF,EACzBC,EAAaC,EAAQC,IAC1BlO,KAAKiB,IAAI6M,QAAQnF,KAAMqF,EAAaD,IACpCD,EAAS9N,KAAKiB,IAAI6M,SAASnF,OACvBmF,GAAUE,KACdA,EAAaF,GAIjBzD,gBAAiB,SAAUzB,GAmBzB,MAjBsC,KAAlC5I,KAAK+I,UAAUoF,QAAQ,OAEzBvF,GACEsB,IAAK,OACLkE,OAAQpO,KAAKiB,IAAIoN,SAASrH,SAAW4B,EAASsB,IAAMtB,EAAS0F,WAC7D3F,KAAMC,EAASD,OAGjBC,EAASwF,OAAS,aACXxF,GAAS0F,YAEwB,KAAtCtO,KAAK+I,UAAUoF,QAAQ,WACzBvF,EAASD,KAAO,EACgC,KAAvC3I,KAAK+I,UAAUoF,QAAQ,cAChCvF,EAAS2F,MAAQ,EACjB3F,EAASD,KAAO,QAEXC,KAIX9J,EAAEQ,GAAGC,aAAa2E,SAAWA,EAC7BpF,EAAEuC,OAAOvC,EAAEQ,GAAGC,aAAcuI,IAC5B9I,IAED,SAAUF,GACT,YAiBA,SAASgC,GAAS0N,GAChB1P,EAAEuC,OAAOrB,KAAMwO,GACXxO,KAAKyO,QAASzO,KAAKkG,OAASwI,EAAQ1O,KAAKkG,SAhB/C,GAAIwI,GAAU,SAAUlM,GACtB,GAAImM,KACJ,OAAO,UAAU5J,EAAM6J,GACjBD,EAAK5J,GACP6J,EAASD,EAAK5J,IAEdvC,EAAK1C,KAAKE,KAAM+E,EAAM,SAAU1E,GAC9BsO,EAAK5J,IAAS4J,EAAK5J,QAAa8J,OAAOxO,GACvCuO,EAASnO,MAAM,KAAMV,cAW7Be,GAASC,MAAQ,SAAU+N,EAAiBC,GAC1C,MAAOjQ,GAAE6H,IAAImI,EAAiB,SAAUvJ,GACtC,GAAIyJ,GAAc,GAAIlO,GAASyE,EAG/B,OAFAyJ,GAAYhO,GAAK+N,EAAO/N,GACxBgO,EAAY/N,IAAM8N,EAAO9N,IAClB+N,KAIXlQ,EAAEuC,OAAOP,EAASlB,WAKhBmG,MAAY,KACZkJ,QAAY,KACZ/I,OAAY,KAGZ7G,GAAY,KACZoP,OAAY,EACZ7I,QAAY,WAAc,OAAO,GACjCI,MAAY,EACZyH,SAAY,SAAU9M,GAAO,MAAOA,IACpC8G,WAAY,OAGd3I,EAAEQ,GAAGC,aAAauB,SAAWA,GAE7B9B,IAED,SAAUF,GACT,YAiCA,SAASqF,MA/BT,GAAI+K,GAAMC,KAAKD,KAAO,WAAc,OAAO,GAAIC,OAAOC,WAOlDC,EAAW,SAAU7M,EAAM8M,GAC7B,GAAIC,GAAS7P,EAAMkG,EAAS4J,EAAWC,EACnCC,EAAQ,WACV,GAAIC,GAAOT,IAAQM,CACRF,GAAPK,EACFJ,EAAUnD,WAAWsD,EAAOJ,EAAOK,IAEnCJ,EAAU,KACVE,EAASjN,EAAK/B,MAAMmF,EAASlG,GAC7BkG,EAAUlG,EAAO,MAIrB,OAAO,YAOL,MANAkG,GAAU5F,KACVN,EAAOK,UACPyP,EAAYN,IACPK,IACHA,EAAUnD,WAAWsD,EAAOJ,IAEvBG,GAMX3Q,GAAEuC,OAAO8C,EAAQvE,WAIfP,GAAW,KACXe,UAAW,KACXY,GAAW,KACXC,IAAW,KACXxB,OAAW,KAKXmC,WAAY,SAAUV,EAASd,EAAWX,GACxCO,KAAKgB,GAAYE,EACjBlB,KAAKiB,IAAYnC,EAAEoC,GACnBlB,KAAKX,GAAYe,EAAUf,GAAKW,KAAK4P,YAAYhP,KACjDZ,KAAKI,UAAYA,EACjBJ,KAAKP,OAAYA,EAEbO,KAAKP,OAAO4P,WACdrP,KAAK6P,SAAWR,EAASrP,KAAK6P,SAAU7P,KAAKP,OAAO4P,WAGtDrP,KAAKkH,eAGP5C,QAAS,WACPtE,KAAKiB,IAAIsD,IAAI,IAAMvE,KAAKX,IACxBW,KAAKiB,IAAMjB,KAAKgB,GAAKhB,KAAKI,UAAY,MAQxCiF,OAAQ,WACN,KAAM,IAAIpG,OAAM,oBAIlBuH,iBAAkB,WAChB,GAAIoC,GAAW5I,KAAK8P,4BAChBhC,EAAS9N,KAAKiB,IAAI6M,SAGlBxF,EAAUtI,KAAKP,OAAOyD,QAC1B,IAAIoF,EAAS,CACJA,YAAmBxJ,KAAMwJ,EAAUxJ,EAAEwJ,GAC3C,IAAIyH,GAAezH,EAAQ0H,eAAelC,QAC1CA,GAAO5D,KAAO6F,EAAa7F,IAC3B4D,EAAOnF,MAAQoH,EAAapH,KAK/B,MAFAC,GAASsB,KAAO4D,EAAO5D,IACvBtB,EAASD,MAAQmF,EAAOnF,KACjBC,GAITnD,MAAO,WACLzF,KAAKiB,IAAIwE,SAMXyB,YAAa,WACXlH,KAAKiB,IAAIe,GAAG,SAAWhC,KAAKX,GAAIP,EAAE6M,MAAM3L,KAAK6P,SAAU7P,QAGzD6P,SAAU,SAAUrK,GACdxF,KAAKiQ,YAAYzK,IACrBxF,KAAKI,UAAUqE,QAAQzE,KAAK4E,0BAA0B,IAIxDqL,YAAa,SAAUC,GACrB,OAAQA,EAAWnF,SACjB,IAAK,GACL,IAAK,IACL,IAAK,IACL,IAAK,IACL,IAAK,IACL,IAAK,IACL,IAAK,IACL,IAAK,IACL,IAAK,IACL,IAAK,IACH,OAAO,EAEX,GAAImF,EAAWlF,QAAS,OAAQkF,EAAWnF,SACzC,IAAK,IACL,IAAK,IACH,OAAO,MAKfjM,EAAEQ,GAAGC,aAAa4E,QAAUA,GAC5BnF,IAED,SAAUF,GACT,YAMA,SAASqR,GAASjP,EAASd,EAAWX,GACpCO,KAAK4B,WAAWV,EAASd,EAAWX,GAGtCX,EAAEuC,OAAO8O,EAASvQ,UAAWd,EAAEQ,GAAGC,aAAa4E,QAAQvE,WAKrDyF,OAAQ,SAAUC,EAAOC,EAAUC,GACjC,GAGI4K,GAHAC,EAAMrQ,KAAK4E,yBACX0L,EAAOtQ,KAAKgB,GAAGsE,MAAMiL,UAAUvQ,KAAKgB,GAAGqD,cACvCmM,EAAYjL,EAAS0J,QAAQ3J,EAAOE,EAEf,oBAAdgL,KACL1R,EAAE2R,QAAQD,KACZF,EAAOE,EAAU,GAAKF,EACtBE,EAAYA,EAAU,IAExBJ,EAAStR,EAAEgH,WAAWP,EAASQ,OAASR,EAASQ,MAAMsK,GAAO9K,EAASQ,MACvEsK,EAAMA,EAAIpB,QAAQmB,EAAQI,GAC1BxQ,KAAKiB,IAAIyP,IAAIL,EAAMC,GACnBtQ,KAAKgB,GAAG2P,eAAiB3Q,KAAKgB,GAAGqD,aAAegM,EAAItM,SAIxDa,uBAAwB,WACtB,MAAO5E,MAAKgB,GAAGsE,MAAMiL,UAAU,EAAGvQ,KAAKgB,GAAGqD,eAM5CyL,0BAA2B,WACzB,GAAIc,GAAI9R,EAAEQ,GAAGC,aAAasR,oBAAoB7Q,KAAKgB,GAAIhB,KAAKgB,GAAG2P,eAC/D,QACEzG,IAAK0G,EAAE1G,IAAMlK,KAAK8Q,uBAAyB9Q,KAAKiB,IAAIkJ,YACpDxB,KAAMiI,EAAEjI,KAAO3I,KAAKiB,IAAImJ,aACxBkE,WAAYtO,KAAK8Q,yBAIrBA,qBAAsB,WACpB,GAAIxC,GAAanC,SAASnM,KAAKiB,IAAIwH,IAAI,eAAgB,GACvD,IAAIsI,MAAMzC,GAAa,CAErB,GAAI0C,GAAahR,KAAKgB,GAAGgQ,WACrBC,EAAOrN,SAASgD,cAAc5G,KAAKgB,GAAGkQ,UACtCC,EAAQnR,KAAKgB,GAAGmQ,KACpBF,GAAKG,aACH,QACA,sCAAwCD,EAAME,WAAa,cAAgBF,EAAMG,UAEnFL,EAAKM,UAAY,OACjBP,EAAWQ,YAAYP,GACvB3C,EAAa2C,EAAKQ,aAClBT,EAAWU,YAAYT,GAEzB,MAAO3C,MAIXxP,EAAEQ,GAAGC,aAAa4Q,SAAWA,GAC7BnR,IAED,SAAUF,GACT,YAIA,SAAS6S,GAAWzQ,EAASd,EAAWX,GACtCO,KAAK4B,WAAWV,EAASd,EAAWX,GACpCX,EAAE,SAAW8S,EAAe,WAAWnJ,KACrCG,SAAU,WACVsB,IAAK,MACLvB,KAAM,QACLkJ,aAAa3Q,GARlB,GAAI0Q,GAAe,GAWnB9S,GAAEuC,OAAOsQ,EAAW/R,UAAWd,EAAEQ,GAAGC,aAAa4Q,SAASvQ,WAIxDyF,OAAQ,SAAUC,EAAOC,EAAUC,GACjC,GAGI4K,GAHAC,EAAMrQ,KAAK4E,yBACX0L,EAAOtQ,KAAKgB,GAAGsE,MAAMiL,UAAUF,EAAItM,QACnCyM,EAAYjL,EAAS0J,QAAQ3J,EAAOE,EAExC,IAAyB,mBAAdgL,GAA2B,CAChC1R,EAAE2R,QAAQD,KACZF,EAAOE,EAAU,GAAKF,EACtBE,EAAYA,EAAU,IAExBJ,EAAStR,EAAEgH,WAAWP,EAASQ,OAASR,EAASQ,MAAMsK,GAAO9K,EAASQ,MACvEsK,EAAMA,EAAIpB,QAAQmB,EAAQI,GAC1BxQ,KAAKiB,IAAIyP,IAAIL,EAAMC,GACnBtQ,KAAKgB,GAAGyE,OACR,IAAIqM,GAAQ9R,KAAKgB,GAAG+Q,iBACpBD,GAAME,UAAS,GACfF,EAAMG,QAAQ,YAAa5B,EAAItM,QAC/B+N,EAAMI,UAAU,YAAa7B,EAAItM,QACjC+N,EAAMzM,WAIVT,uBAAwB,WACtB5E,KAAKgB,GAAGyE,OACR,IAAIqM,GAAQlO,SAASuO,UAAUC,aAC/BN,GAAMI,UAAU,aAAclS,KAAKgB,GAAGsE,MAAMvB,OAC5C,IAAIsO,GAAMP,EAAMpN,KAAK4N,MAAMV,EAC3B,OAAsB,KAAfS,EAAItO,OAAesO,EAAI,GAAKA,EAAI,MAI3CvT,EAAEQ,GAAGC,aAAaoS,WAAaA,GAC/B3S,IAMD,SAAUF,GACT,YAMA,SAASyT,GAAiBrR,EAASd,EAAWX,GAC5CO,KAAK4B,WAAWV,EAASd,EAAWX,GAGtCX,EAAEuC,OAAOkR,EAAgB3S,UAAWd,EAAEQ,GAAGC,aAAa4E,QAAQvE,WAM5DyF,OAAQ,SAAUC,EAAOC,EAAUC,GACjC,GAAI6K,GAAMrQ,KAAK4E,yBAEX4N,EAAMxS,KAAKgB,GAAGU,cAAc+Q,eAE5BX,EAAQU,EAAIE,WAAW,GACvBP,EAAYL,EAAMa,YACtBR,GAAUS,mBAAmBd,EAAMe,eACnC,IAGIzC,GAHA0C,EAAUX,EAAUlP,WACpBqN,EAAOwC,EAAQvC,UAAUuB,EAAMiB,aAC/BvC,EAAYjL,EAAS0J,QAAQ3J,EAAOE,EAExC,IAAyB,mBAAdgL,GAA2B,CAChC1R,EAAE2R,QAAQD,KACZF,EAAOE,EAAU,GAAKF,EACtBE,EAAYA,EAAU,IAExBJ,EAAStR,EAAEgH,WAAWP,EAASQ,OAASR,EAASQ,MAAMsK,GAAO9K,EAASQ,MACvEsK,EAAMA,EAAIpB,QAAQmB,EAAQI,GACrBvB,QAAQ,KAAM,SACnB6C,EAAMc,mBAAmBd,EAAMe,gBAC/Bf,EAAMkB,gBAGN,IAAIC,GAAajT,KAAKgB,GAAGU,cAAckF,cAAc,MACrDqM,GAAW1B,UAAYlB,CACvB,IAAI6C,GAAclT,KAAKgB,GAAGU,cAAckF,cAAc,MACtDsM,GAAY3B,UAAYjB,CAMxB,KAHA,GACI6C,GACAC,EAFAC,EAAWrT,KAAKgB,GAAGU,cAAc4R,yBAG9BH,EAAYF,EAAWM,YAC7BH,EAAYC,EAAS7B,YAAY2B,EAElC,MAAOA,EAAYD,EAAYK,YAC9BF,EAAS7B,YAAY2B,EAItBrB,GAAM0B,WAAWH,GACjBvB,EAAM2B,cAAcL,GAEpBtB,EAAME,UAAS,GACfQ,EAAIkB,kBACJlB,EAAImB,SAAS7B,KAgBjBhC,0BAA2B,WACzB,GAAIgC,GAAQ9R,KAAKgB,GAAGU,cAAc+Q,eAAeC,WAAW,GAAGC,aAC3DiB,EAAO5T,KAAKgB,GAAGU,cAAckF,cAAc,OAC/CkL,GAAM0B,WAAWI,GACjB9B,EAAMc,mBAAmBgB,GACzB9B,EAAMkB,gBACN,IAAIa,GAAQ/U,EAAE8U,GACVhL,EAAWiL,EAAM/F,QAOrB,IANAlF,EAASD,MAAQ3I,KAAKiB,IAAI6M,SAASnF,KACnCC,EAASsB,KAAO2J,EAAM7M,SAAWhH,KAAKiB,IAAI6M,SAAS5D,IACnDtB,EAAS0F,WAAauF,EAAM7M,SAIxBhH,KAAKI,UAAUqD,QAAS,CAC1B,GAAIqQ,GAAiB9T,KAAKI,UAAUqD,QAAQqK,QAC5ClF,GAASsB,KAAO4J,EAAe5J,IAC/BtB,EAASD,MAAQmL,EAAenL,KAEhCC,EAASsB,KAAOlK,KAAKiB,IAAIkJ,YAI3B,MADA0J,GAAM7K,SACCJ,GAWThE,uBAAwB,WACtB,GAAIkN,GAAQ9R,KAAKgB,GAAGU,cAAc+Q,eAAeC,WAAW,GACxDP,EAAYL,EAAMa,YAEtB,OADAR,GAAUS,mBAAmBd,EAAMe,gBAC5BV,EAAUlP,WAAWsN,UAAU,EAAGuB,EAAMiB,gBAInDjU,EAAEQ,GAAGC,aAAagT,gBAAkBA,GACpCvT,IAMD,SAAUF,GACT,YAMA,SAASiV,GAAU7S,EAASd,EAAWX,GACrCO,KAAK4B,WAAWV,EAASd,EAAWX,GAGtCX,EAAEuC,OAAO0S,EAASnU,UAAWd,EAAEQ,GAAGC,aAAagT,gBAAgB3S,WAC7DsH,YAAa,WACX,GAAI/G,GAAQH,IACZA,MAAKP,OAAO6C,kBAAkBN,GAAG,MAAO,SAASC,GAC/C,GAAI+R,GAAW/R,EAAM5B,IAErB,OADAF,GAAM0P,SAASmE,GACX7T,EAAMC,UAAUoD,SAAS4C,OAASjG,EAAM8P,YAAY+D,IAC/C,EADT,QAGC,KAAM,KAAM,GAEfhU,KAAKiB,IAAIe,GAAG,SAAWhC,KAAKX,GAAIP,EAAE6M,MAAM3L,KAAK6P,SAAU7P,UAI3DlB,EAAEQ,GAAGC,aAAawU,SAAWA,GAC7B/U,GAuBD,SAAUF,GAmDX,QAAS+R,GAAoB3P,EAAS0H,EAAU4F,GAC9C,IAAIyF,EACF,KAAM,IAAIhV,OAAM,iFAGlB,IAAIiV,GAAQ1F,GAAWA,EAAQ0F,QAAS,CACxC,IAAIA,EAAO,CACT,GAAIlT,GAAK4C,SAASuQ,cAAc,4CAC3BnT,IAAOA,EAAGgQ,WAAWU,YAAY1Q,GAIxC,GAAIoT,GAAMxQ,SAASgD,cAAc,MACjCwN,GAAI/U,GAAK,2CACTuE,SAASyQ,KAAK7C,YAAY4C,EAE1B,IAAIjD,GAAQiD,EAAIjD,MACZmD,EAAWzQ,OAAO0Q,iBAAkBA,iBAAiBrT,GAAWA,EAAQsT,YAG5ErD,GAAMsD,WAAa,WACM,UAArBvT,EAAQgQ,WACVC,EAAMuD,SAAW,cAGnBvD,EAAMvI,SAAW,WACZsL,IACH/C,EAAMwD,WAAa,UAGrBC,EAAWC,QAAQ,SAAUlR,GAC3BwN,EAAMxN,GAAQ2Q,EAAS3Q,KAGrBmR,EAEE5T,EAAQ6T,aAAe5I,SAASmI,EAAStN,UAC3CmK,EAAM6D,UAAY,UAEpB7D,EAAM8D,SAAW,SAGnBb,EAAIc,YAAchU,EAAQoE,MAAMiL,UAAU,EAAG3H,GAEpB,UAArB1H,EAAQgQ,WACVkD,EAAIc,YAAcd,EAAIc,YAAYjG,QAAQ,MAAO,KAEnD,IAAIkG,GAAOvR,SAASgD,cAAc,OAMlCuO,GAAKD,YAAchU,EAAQoE,MAAMiL,UAAU3H,IAAa,IACxDwL,EAAI5C,YAAY2D,EAEhB,IAAIC,IACFlL,IAAKiL,EAAKE,UAAYlJ,SAASmI,EAAyB,gBACxD3L,KAAMwM,EAAKG,WAAanJ,SAASmI,EAA0B,iBAS7D,OANIJ,GACFiB,EAAKhE,MAAMoE,gBAAkB,OAE7B3R,SAASyQ,KAAK3C,YAAY0C,GAGrBgB,EAhHT,GAAIR,IACF,YACA,YACA,QACA,SACA,YACA,YAEA,iBACA,mBACA,oBACA,kBACA,cAEA,aACA,eACA,gBACA,cAGA,YACA,cACA,aACA,cACA,WACA,iBACA,aACA,aAEA,YACA,gBACA,aACA,iBAEA,gBACA,cAEA,UACA,cAIEX,EAA+B,mBAAXpQ,QACpBiR,EAAab,GAAuC,MAA1BpQ,OAAO2R,eAwErC1W,GAAEQ,GAAGC,aAAasR,oBAAsBA,GAEtC7R,GAEKA"} \ No newline at end of file
diff --git a/library/jquery_ac/friendica.complete.js b/library/jquery_ac/friendica.complete.js
index 73a6e91d5..3012a754b 100644
--- a/library/jquery_ac/friendica.complete.js
+++ b/library/jquery_ac/friendica.complete.js
@@ -243,7 +243,7 @@
} else if (!this.isBadQuery(q)) {
me = this;
me.options.params.query = q;
- $('#nav-search-spinner').spin('tiny');
+ $('#nav-search-spinner').show();
$.get(this.serviceUrl, me.options.params, function(txt) { me.processResponse(txt); }, 'text');
}
},
@@ -306,7 +306,7 @@
this.data = response.data;
this.suggest();
}
- $('#nav-search-spinner').spin(false);
+ $('#nav-search-spinner').hide();
},
activate: function(index) {
diff --git a/library/jsonld/LICENSE b/library/jsonld/LICENSE
new file mode 100644
index 000000000..bd572d3e0
--- /dev/null
+++ b/library/jsonld/LICENSE
@@ -0,0 +1,30 @@
+BSD 3-Clause License
+Copyright (c) 2011, Digital Bazaar, Inc.
+All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are met:
+
+Redistributions of source code must retain the above copyright notice,
+this list of conditions and the following disclaimer.
+
+Redistributions in binary form must reproduce the above copyright
+notice, this list of conditions and the following disclaimer in the
+documentation and/or other materials provided with the distribution.
+
+Neither the name of the Digital Bazaar, Inc. nor the names of its
+contributors may be used to endorse or promote products derived from
+this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
+IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
+TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
+PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
+TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+
diff --git a/library/jsonld/README.md b/library/jsonld/README.md
new file mode 100644
index 000000000..5853c94bf
--- /dev/null
+++ b/library/jsonld/README.md
@@ -0,0 +1,193 @@
+php-json-ld
+===========
+
+[![Build Status][travis-ci-png]][travis-ci-site]
+[travis-ci-png]: https://travis-ci.org/digitalbazaar/php-json-ld.png?branch=master
+[travis-ci-site]: https://travis-ci.org/digitalbazaar/php-json-ld
+
+Introduction
+------------
+
+This library is an implementation of the [JSON-LD][] specification in [PHP][].
+
+JSON, as specified in [RFC7159][], is a simple language for representing
+objects on the Web. Linked Data is a way of describing content across
+different documents or Web sites. Web resources are described using
+IRIs, and typically are dereferencable entities that may be used to find
+more information, creating a "Web of Knowledge". [JSON-LD][] is intended
+to be a simple publishing method for expressing not only Linked Data in
+JSON, but for adding semantics to existing JSON.
+
+JSON-LD is designed as a light-weight syntax that can be used to express
+Linked Data. It is primarily intended to be a way to express Linked Data
+in JavaScript and other Web-based programming environments. It is also
+useful when building interoperable Web Services and when storing Linked
+Data in JSON-based document storage engines. It is practical and
+designed to be as simple as possible, utilizing the large number of JSON
+parsers and existing code that is in use today. It is designed to be
+able to express key-value pairs, RDF data, [RDFa][] data,
+[Microformats][] data, and [Microdata][]. That is, it supports every
+major Web-based structured data model in use today.
+
+The syntax does not require many applications to change their JSON, but
+easily add meaning by adding context in a way that is either in-band or
+out-of-band. The syntax is designed to not disturb already deployed
+systems running on JSON, but provide a smooth migration path from JSON
+to JSON with added semantics. Finally, the format is intended to be fast
+to parse, fast to generate, stream-based and document-based processing
+compatible, and require a very small memory footprint in order to operate.
+
+## Quick Examples
+
+```php
+$doc = (object)array(
+ "http://schema.org/name" => "Manu Sporny",
+ "http://schema.org/url" => (object)array("@id" => "http://manu.sporny.org/"),
+ "http://schema.org/image" => (object)array("@id" => "http://manu.sporny.org/images/manu.png")
+);
+
+$context = (object)array(
+ "name" => "http://schema.org/name",
+ "homepage" => (object)array("@id" => "http://schema.org/url", "@type" => "@id"),
+ "image" => (object)array("@id" => "http://schema.org/image", "@type" => "@id")
+);
+
+// compact a document according to a particular context
+// see: http://json-ld.org/spec/latest/json-ld/#compacted-document-form
+$compacted = jsonld_compact($doc, $context);
+
+echo json_encode($compacted, JSON_PRETTY_PRINT | JSON_UNESCAPED_SLASHES);
+/* Output:
+{
+ "@context": {...},
+ "image": "http://manu.sporny.org/images/manu.png",
+ "homepage": "http://manu.sporny.org/",
+ "name": "Manu Sporny"
+}
+*/
+
+// compact using URLs
+jsonld_compact('http://example.org/doc', 'http://example.org/context');
+
+// expand a document, removing its context
+// see: http://json-ld.org/spec/latest/json-ld/#expanded-document-form
+$expanded = jsonld_expand($compacted) {
+echo json_encode($expanded, JSON_PRETTY_PRINT | JSON_UNESCAPED_SLASHES);
+/* Output:
+{
+ "http://schema.org/image": [{"@id": "http://manu.sporny.org/images/manu.png"}],
+ "http://schema.org/name": [{"@value": "Manu Sporny"}],
+ "http://schema.org/url": [{"@id": "http://manu.sporny.org/"}]
+}
+*/
+
+// expand using URLs
+jsonld_expand('http://example.org/doc');
+
+// flatten a document
+// see: http://json-ld.org/spec/latest/json-ld/#flattened-document-form
+$flattened = jsonld_flatten($doc);
+// all deep-level trees flattened to the top-level
+
+// frame a document
+// see: http://json-ld.org/spec/latest/json-ld-framing/#introduction
+$framed = jsonld_frame($doc, $frame);
+// document transformed into a particular tree structure per the given frame
+
+// normalize a document using the RDF Dataset Normalization Algorithm
+// (URDNA2015), see: http://json-ld.github.io/normalization/spec/
+$normalized = jsonld_normalize(
+ $doc, array('algorithm' => 'URDNA2015', 'format' => 'application/nquads'));
+// normalized is a string that is a canonical representation of the document
+// that can be used for hashing, comparison, etc.
+
+// force HTTPS-only context loading:
+// use built-in secure document loader
+jsonld_set_document_loader('jsonld_default_secure_document_loader');
+
+// set a default custom document loader
+jsonld_set_document_loader('my_custom_doc_loader');
+
+// a custom loader that demonstrates using a simple in-memory mock for
+// certain contexts before falling back to the default loader
+// note: if you want to set this loader as the new default, you'll need to
+// store the previous default in another variable first and access that inside
+// the loader
+global $mocks;
+$mocks = array('http://example.com/mycontext' => (object)array(
+ 'hombre' => 'http://schema.org/name'));
+function mock_load($url) {
+ global $jsonld_default_load_document, $mocks;
+ if(isset($mocks[$url])) {
+ // return a "RemoteDocument", it has these three properties:
+ return (object)array(
+ 'contextUrl' => null,
+ 'document' => $mocks[$url],
+ 'documentUrl' => $url);
+ }
+ // use default loader
+ return call_user_func($jsonld_default_load_document, $url);
+}
+
+// use the mock loader for just this call, witout modifying the default one
+$compacted = jsonld_compact($foo, 'http://example.com/mycontext', array(
+ 'documentLoader' => 'mock_load'));
+
+// a custom loader that uses a simplistic in-memory cache (no invalidation)
+global $cache;
+$cache = array();
+function cache_load($url) {
+ global $jsonld_default_load_document, $cache;
+ if(isset($cache[$url])) {
+ return $cache[$url];
+ }
+ // use default loader
+ $doc = call_user_func($jsonld_default_load_document, $url);
+ $cache[$url] = $doc;
+ return $doc;
+}
+
+// use the cache loader for just this call, witout modifying the default one
+$compacted = jsonld_compact($foo, 'http://schema.org', array(
+ 'documentLoader' => 'cache_load'));
+```
+
+Commercial Support
+------------------
+
+Commercial support for this library is available upon request from
+[Digital Bazaar][]: support@digitalbazaar.com
+
+Source
+------
+
+The source code for the PHP implementation of the JSON-LD API
+is available at:
+
+http://github.com/digitalbazaar/php-json-ld
+
+Tests
+-----
+
+This library includes a sample testing utility which may be used to verify
+that changes to the processor maintain the correct output.
+
+To run the sample tests you will need to get the test suite files by cloning
+the `json-ld.org` and `normalization` repositories hosted on GitHub:
+
+- https://github.com/json-ld/json-ld.org
+- https://github.com/json-ld/normalization
+
+Then run the PHPUnit test.php application and point it at the directories
+containing the tests:
+
+ phpunit --group json-ld.org test.php -d {PATH_TO_JSON_LD_ORG/test-suite}
+ phpunit --group normalization test.php -d {PATH_TO_NORMALIZATION/tests}
+
+[Digital Bazaar]: http://digitalbazaar.com/
+[JSON-LD]: http://json-ld.org/
+[Microdata]: http://www.w3.org/TR/microdata/
+[Microformats]: http://microformats.org/
+[PHP]: http://php.net
+[RDFa]: http://www.w3.org/TR/rdfa-core/
+[RFC7159]: http://tools.ietf.org/html/rfc7159
diff --git a/library/jsonld/composer.json b/library/jsonld/composer.json
new file mode 100644
index 000000000..cc985b23e
--- /dev/null
+++ b/library/jsonld/composer.json
@@ -0,0 +1,29 @@
+{
+ "name": "digitalbazaar/json-ld",
+ "type": "library",
+ "description": "A JSON-LD Processor and API implementation in PHP.",
+ "keywords": [
+ "JSON",
+ "Linked Data",
+ "JSON-LD",
+ "RDF",
+ "Semantic Web",
+ "jsonld"
+ ],
+ "homepage": "https://github.com/digitalbazaar/php-json-ld",
+ "license": "BSD-3-Clause",
+ "authors": [
+ {
+ "name": "Digital Bazaar, Inc.",
+ "email": "support@digitalbazaar.com",
+ "url": "http://digitalbazaar.com/"
+ }
+ ],
+ "require": {
+ "php": ">=5.3.0",
+ "ext-json": "*"
+ },
+ "autoload": {
+ "files": [ "jsonld.php" ]
+ }
+}
diff --git a/library/jsonld/jsonld.php b/library/jsonld/jsonld.php
new file mode 100644
index 000000000..28b3e7ce3
--- /dev/null
+++ b/library/jsonld/jsonld.php
@@ -0,0 +1,6038 @@
+<?php
+/**
+ * PHP implementation of the JSON-LD API.
+ * Version: 0.4.8-dev
+ *
+ * @author Dave Longley
+ *
+ * BSD 3-Clause License
+ * Copyright (c) 2011-2014 Digital Bazaar, Inc.
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are met:
+ *
+ * Redistributions of source code must retain the above copyright notice,
+ * this list of conditions and the following disclaimer.
+ *
+ * Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * Neither the name of the Digital Bazaar, Inc. nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
+ * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
+ * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
+ * PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ * HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
+ * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+/**
+ * Performs JSON-LD compaction.
+ *
+ * @param mixed $input the JSON-LD object to compact.
+ * @param mixed $ctx the context to compact with.
+ * @param assoc [$options] options to use:
+ * [base] the base IRI to use.
+ * [graph] true to always output a top-level graph (default: false).
+ * [documentLoader(url)] the document loader.
+ *
+ * @return mixed the compacted JSON-LD output.
+ */
+function jsonld_compact($input, $ctx, $options=array()) {
+ $p = new JsonLdProcessor();
+ return $p->compact($input, $ctx, $options);
+}
+
+/**
+ * Performs JSON-LD expansion.
+ *
+ * @param mixed $input the JSON-LD object to expand.
+ * @param assoc[$options] the options to use:
+ * [base] the base IRI to use.
+ * [documentLoader(url)] the document loader.
+ *
+ * @return array the expanded JSON-LD output.
+ */
+function jsonld_expand($input, $options=array()) {
+ $p = new JsonLdProcessor();
+ return $p->expand($input, $options);
+}
+
+/**
+ * Performs JSON-LD flattening.
+ *
+ * @param mixed $input the JSON-LD to flatten.
+ * @param mixed $ctx the context to use to compact the flattened output, or
+ * null.
+ * @param [options] the options to use:
+ * [base] the base IRI to use.
+ * [documentLoader(url)] the document loader.
+ *
+ * @return mixed the flattened JSON-LD output.
+ */
+function jsonld_flatten($input, $ctx, $options=array()) {
+ $p = new JsonLdProcessor();
+ return $p->flatten($input, $ctx, $options);
+}
+
+/**
+ * Performs JSON-LD framing.
+ *
+ * @param mixed $input the JSON-LD object to frame.
+ * @param stdClass $frame the JSON-LD frame to use.
+ * @param assoc [$options] the framing options.
+ * [base] the base IRI to use.
+ * [embed] default @embed flag (default: true).
+ * [explicit] default @explicit flag (default: false).
+ * [requireAll] default @requireAll flag (default: true).
+ * [omitDefault] default @omitDefault flag (default: false).
+ * [documentLoader(url)] the document loader.
+ *
+ * @return stdClass the framed JSON-LD output.
+ */
+function jsonld_frame($input, $frame, $options=array()) {
+ $p = new JsonLdProcessor();
+ return $p->frame($input, $frame, $options);
+}
+
+/**
+ * **Experimental**
+ *
+ * Links a JSON-LD document's nodes in memory.
+ *
+ * @param mixed $input the JSON-LD document to link.
+ * @param mixed $ctx the JSON-LD context to apply or null.
+ * @param assoc [$options] the options to use:
+ * [base] the base IRI to use.
+ * [expandContext] a context to expand with.
+ * [documentLoader(url)] the document loader.
+ *
+ * @return the linked JSON-LD output.
+ */
+function jsonld_link($input, $ctx, $options) {
+ // API matches running frame with a wildcard frame and embed: '@link'
+ // get arguments
+ $frame = new stdClass();
+ if($ctx) {
+ $frame->{'@context'} = $ctx;
+ }
+ $frame->{'@embed'} = '@link';
+ return jsonld_frame($input, $frame, $options);
+};
+
+/**
+ * Performs RDF dataset normalization on the given input. The input is
+ * JSON-LD unless the 'inputFormat' option is used. The output is an RDF
+ * dataset unless the 'format' option is used.
+ *
+ * @param mixed $input the JSON-LD object to normalize.
+ * @param assoc [$options] the options to use:
+ * [base] the base IRI to use.
+ * [intputFormat] the format if input is not JSON-LD:
+ * 'application/nquads' for N-Quads.
+ * [format] the format if output is a string:
+ * 'application/nquads' for N-Quads.
+ * [documentLoader(url)] the document loader.
+ *
+ * @return mixed the normalized output.
+ */
+function jsonld_normalize($input, $options=array()) {
+ $p = new JsonLdProcessor();
+ return $p->normalize($input, $options);
+}
+
+/**
+ * Converts an RDF dataset to JSON-LD.
+ *
+ * @param mixed $input a serialized string of RDF in a format specified
+ * by the format option or an RDF dataset to convert.
+ * @param assoc [$options] the options to use:
+ * [format] the format if input not an array:
+ * 'application/nquads' for N-Quads (default).
+ * [useRdfType] true to use rdf:type, false to use @type
+ * (default: false).
+ * [useNativeTypes] true to convert XSD types into native types
+ * (boolean, integer, double), false not to (default: false).
+ *
+ * @return array the JSON-LD output.
+ */
+function jsonld_from_rdf($input, $options=array()) {
+ $p = new JsonLdProcessor();
+ return $p->fromRDF($input, $options);
+}
+
+/**
+ * Outputs the RDF dataset found in the given JSON-LD object.
+ *
+ * @param mixed $input the JSON-LD object.
+ * @param assoc [$options] the options to use:
+ * [base] the base IRI to use.
+ * [format] the format to use to output a string:
+ * 'application/nquads' for N-Quads.
+ * [produceGeneralizedRdf] true to output generalized RDF, false
+ * to produce only standard RDF (default: false).
+ * [documentLoader(url)] the document loader.
+ *
+ * @return mixed the resulting RDF dataset (or a serialization of it).
+ */
+function jsonld_to_rdf($input, $options=array()) {
+ $p = new JsonLdProcessor();
+ return $p->toRDF($input, $options);
+}
+
+/**
+ * JSON-encodes (with unescaped slashes) the given stdClass or array.
+ *
+ * @param mixed $input the native PHP stdClass or array which will be
+ * converted to JSON by json_encode().
+ * @param int $options the options to use.
+ * [JSON_PRETTY_PRINT] pretty print.
+ * @param int $depth the maximum depth to use.
+ *
+ * @return the encoded JSON data.
+ */
+function jsonld_encode($input, $options=0, $depth=512) {
+ // newer PHP has a flag to avoid escaped '/'
+ if(defined('JSON_UNESCAPED_SLASHES')) {
+ return json_encode($input, JSON_UNESCAPED_SLASHES | $options, $depth);
+ }
+ // use a simple string replacement of '\/' to '/'.
+ return str_replace('\\/', '/', json_encode($input, $options, $depth));
+}
+
+/**
+ * Decodes a serialized JSON-LD object.
+ *
+ * @param string $input the JSON-LD input.
+ *
+ * @return mixed the resolved JSON-LD object, null on error.
+ */
+function jsonld_decode($input) {
+ return json_decode($input);
+}
+
+/**
+ * Parses a link header. The results will be key'd by the value of "rel".
+ *
+ * Link: <http://json-ld.org/contexts/person.jsonld>; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"
+ *
+ * Parses as: {
+ * 'http://www.w3.org/ns/json-ld#context': {
+ * target: http://json-ld.org/contexts/person.jsonld,
+ * type: 'application/ld+json'
+ * }
+ * }
+ *
+ * If there is more than one "rel" with the same IRI, then entries in the
+ * resulting map for that "rel" will be arrays of objects, otherwise they will
+ * be single objects.
+ *
+ * @param string $header the link header to parse.
+ *
+ * @return assoc the parsed result.
+ */
+function jsonld_parse_link_header($header) {
+ $rval = array();
+ // split on unbracketed/unquoted commas
+ if(!preg_match_all(
+ '/(?:<[^>]*?>|"[^"]*?"|[^,])+/', $header, $entries, PREG_SET_ORDER)) {
+ return $rval;
+ }
+ $r_link_header = '/\s*<([^>]*?)>\s*(?:;\s*(.*))?/';
+ foreach($entries as $entry) {
+ if(!preg_match($r_link_header, $entry[0], $match)) {
+ continue;
+ }
+ $result = (object)array('target' => $match[1]);
+ $params = $match[2];
+ $r_params = '/(.*?)=(?:(?:"([^"]*?)")|([^"]*?))\s*(?:(?:;\s*)|$)/';
+ preg_match_all($r_params, $params, $matches, PREG_SET_ORDER);
+ foreach($matches as $match) {
+ $result->{$match[1]} = $match[2] ?: $match[3];
+ }
+ $rel = property_exists($result, 'rel') ? $result->rel : '';
+ if(!isset($rval[$rel])) {
+ $rval[$rel] = $result;
+ } else if(is_array($rval[$rel])) {
+ $rval[$rel][] = $result;
+ } else {
+ $rval[$rel] = array($rval[$rel], $result);
+ }
+ }
+ return $rval;
+}
+
+/**
+ * Relabels all blank nodes in the given JSON-LD input.
+ *
+ * @param mixed input the JSON-LD input.
+ */
+function jsonld_relabel_blank_nodes($input) {
+ $p = new JsonLdProcessor();
+ return $p->_labelBlankNodes(new UniqueNamer('_:b'), $input);
+}
+
+/** JSON-LD shared in-memory cache. */
+global $jsonld_cache;
+$jsonld_cache = new stdClass();
+
+/** The default active context cache. */
+$jsonld_cache->activeCtx = new ActiveContextCache();
+
+/** Stores the default JSON-LD document loader. */
+global $jsonld_default_load_document;
+$jsonld_default_load_document = 'jsonld_default_document_loader';
+
+/**
+ * Sets the default JSON-LD document loader.
+ *
+ * @param callable load_document(url) the document loader.
+ */
+function jsonld_set_document_loader($load_document) {
+ global $jsonld_default_load_document;
+ $jsonld_default_load_document = $load_document;
+}
+
+/**
+ * Retrieves JSON-LD at the given URL.
+ *
+ * @param string $url the URL to retrieve.
+ *
+ * @return the JSON-LD.
+ */
+function jsonld_get_url($url) {
+ global $jsonld_default_load_document;
+ if($jsonld_default_load_document !== null) {
+ $document_loader = $jsonld_default_load_document;
+ } else {
+ $document_loader = 'jsonld_default_document_loader';
+ }
+
+ $remote_doc = call_user_func($document_loader, $url);
+ if($remote_doc) {
+ return $remote_doc->document;
+ }
+ return null;
+}
+
+/**
+ * The default implementation to retrieve JSON-LD at the given URL.
+ *
+ * @param string $url the URL to to retrieve.
+ *
+ * @return stdClass the RemoteDocument object.
+ */
+function jsonld_default_document_loader($url) {
+ $doc = (object)array(
+ 'contextUrl' => null, 'document' => null, 'documentUrl' => $url);
+ $redirects = array();
+
+ $opts = array(
+ 'http' => array(
+ 'method' => 'GET',
+ 'header' =>
+ "Accept: application/ld+json\r\n"),
+ /* Note: Use jsonld_default_secure_document_loader for security. */
+ 'ssl' => array(
+ 'verify_peer' => false,
+ 'allow_self_signed' => true)
+ );
+
+ $context = stream_context_create($opts);
+ $content_type = null;
+ stream_context_set_params($context, array('notification' =>
+ function($notification_code, $severity, $message) use (
+ &$redirects, &$content_type) {
+ switch($notification_code) {
+ case STREAM_NOTIFY_REDIRECTED:
+ $redirects[] = $message;
+ break;
+ case STREAM_NOTIFY_MIME_TYPE_IS:
+ $content_type = $message;
+ break;
+ };
+ }));
+ $result = @file_get_contents($url, false, $context);
+ if($result === false) {
+ throw new JsonLdException(
+ 'Could not retrieve a JSON-LD document from the URL: ' . $url,
+ 'jsonld.LoadDocumentError', 'loading document failed');
+ }
+ $link_header = array();
+ foreach($http_response_header as $header) {
+ if(strpos($header, 'link') === 0) {
+ $value = explode(': ', $header);
+ if(count($value) > 1) {
+ $link_header[] = $value[1];
+ }
+ }
+ }
+ $link_header = jsonld_parse_link_header(join(',', $link_header));
+ if(isset($link_header['http://www.w3.org/ns/json-ld#context'])) {
+ $link_header = $link_header['http://www.w3.org/ns/json-ld#context'];
+ } else {
+ $link_header = null;
+ }
+ if($link_header && $content_type !== 'application/ld+json') {
+ // only 1 related link header permitted
+ if(is_array($link_header)) {
+ throw new JsonLdException(
+ 'URL could not be dereferenced, it has more than one ' .
+ 'associated HTTP Link Header.', 'jsonld.LoadDocumentError',
+ 'multiple context link headers', array('url' => $url));
+ }
+ $doc->{'contextUrl'} = $link_header->target;
+ }
+
+ // update document url based on redirects
+ $redirs = count($redirects);
+ if($redirs > 0) {
+ $url = $redirects[$redirs - 1];
+ }
+ $doc->document = $result;
+ $doc->documentUrl = $url;
+ return $doc;
+}
+
+/**
+ * The default implementation to retrieve JSON-LD at the given secure URL.
+ *
+ * @param string $url the secure URL to to retrieve.
+ *
+ * @return stdClass the RemoteDocument object.
+ */
+function jsonld_default_secure_document_loader($url) {
+ if(strpos($url, 'https') !== 0) {
+ throw new JsonLdException(
+ "Could not GET url: '$url'; 'https' is required.",
+ 'jsonld.LoadDocumentError', 'loading document failed');
+ }
+
+ $doc = (object)array(
+ 'contextUrl' => null, 'document' => null, 'documentUrl' => $url);
+ $redirects = array();
+
+ // default JSON-LD https GET implementation
+ $opts = array(
+ 'http' => array(
+ 'method' => 'GET',
+ 'header' =>
+ "Accept: application/ld+json\r\n"),
+ 'ssl' => array(
+ 'verify_peer' => true,
+ 'allow_self_signed' => false,
+ 'cafile' => '/etc/ssl/certs/ca-certificates.crt'));
+ $context = stream_context_create($opts);
+ $content_type = null;
+ stream_context_set_params($context, array('notification' =>
+ function($notification_code, $severity, $message) use (
+ &$redirects, &$content_type) {
+ switch($notification_code) {
+ case STREAM_NOTIFY_REDIRECTED:
+ $redirects[] = $message;
+ break;
+ case STREAM_NOTIFY_MIME_TYPE_IS:
+ $content_type = $message;
+ break;
+ };
+ }));
+ $result = @file_get_contents($url, false, $context);
+ if($result === false) {
+ throw new JsonLdException(
+ 'Could not retrieve a JSON-LD document from the URL: ' + $url,
+ 'jsonld.LoadDocumentError', 'loading document failed');
+ }
+ $link_header = array();
+ foreach($http_response_header as $header) {
+ if(strpos($header, 'link') === 0) {
+ $value = explode(': ', $header);
+ if(count($value) > 1) {
+ $link_header[] = $value[1];
+ }
+ }
+ }
+ $link_header = jsonld_parse_link_header(join(',', $link_header));
+ if(isset($link_header['http://www.w3.org/ns/json-ld#context'])) {
+ $link_header = $link_header['http://www.w3.org/ns/json-ld#context'];
+ } else {
+ $link_header = null;
+ }
+ if($link_header && $content_type !== 'application/ld+json') {
+ // only 1 related link header permitted
+ if(is_array($link_header)) {
+ throw new JsonLdException(
+ 'URL could not be dereferenced, it has more than one ' .
+ 'associated HTTP Link Header.', 'jsonld.LoadDocumentError',
+ 'multiple context link headers', array('url' => $url));
+ }
+ $doc->{'contextUrl'} = $link_header->target;
+ }
+
+ // update document url based on redirects
+ foreach($redirects as $redirect) {
+ if(strpos($redirect, 'https') !== 0) {
+ throw new JsonLdException(
+ "Could not GET redirected url: '$redirect'; 'https' is required.",
+ 'jsonld.LoadDocumentError', 'loading document failed');
+ }
+ $url = $redirect;
+ }
+ $doc->document = $result;
+ $doc->documentUrl = $url;
+ return $doc;
+}
+
+/** Registered global RDF dataset parsers hashed by content-type. */
+global $jsonld_rdf_parsers;
+$jsonld_rdf_parsers = new stdClass();
+
+/**
+ * Registers a global RDF dataset parser by content-type, for use with
+ * jsonld_from_rdf. Global parsers will be used by JsonLdProcessors that do
+ * not register their own parsers.
+ *
+ * @param string $content_type the content-type for the parser.
+ * @param callable $parser(input) the parser function (takes a string as
+ * a parameter and returns an RDF dataset).
+ */
+function jsonld_register_rdf_parser($content_type, $parser) {
+ global $jsonld_rdf_parsers;
+ $jsonld_rdf_parsers->{$content_type} = $parser;
+}
+
+/**
+ * Unregisters a global RDF dataset parser by content-type.
+ *
+ * @param string $content_type the content-type for the parser.
+ */
+function jsonld_unregister_rdf_parser($content_type) {
+ global $jsonld_rdf_parsers;
+ if(property_exists($jsonld_rdf_parsers, $content_type)) {
+ unset($jsonld_rdf_parsers->{$content_type});
+ }
+}
+
+/**
+ * Parses a URL into its component parts.
+ *
+ * @param string $url the URL to parse.
+ *
+ * @return assoc the parsed URL.
+ */
+function jsonld_parse_url($url) {
+ if($url === null) {
+ $url = '';
+ }
+
+ $keys = array(
+ 'href', 'protocol', 'scheme', '?authority', 'authority',
+ '?auth', 'auth', 'user', 'pass', 'host', '?port', 'port', 'path',
+ '?query', 'query', '?fragment', 'fragment');
+ $regex = "/^(([^:\/?#]+):)?(\/\/(((([^:@]*)(?::([^:@]*))?)?@)?([^:\/?#]*)(:(\d*))?))?([^?#]*)(\?([^#]*))?(#(.*))?/";
+ preg_match($regex, $url, $match);
+
+ $rval = array();
+ $flags = array();
+ $len = count($keys);
+ for($i = 0; $i < $len; ++$i) {
+ $key = $keys[$i];
+ if(strpos($key, '?') === 0) {
+ $flags[substr($key, 1)] = !empty($match[$i]);
+ } else if(!isset($match[$i])) {
+ $rval[$key] = null;
+ } else {
+ $rval[$key] = $match[$i];
+ }
+ }
+
+ if(!$flags['authority']) {
+ $rval['authority'] = null;
+ }
+ if(!$flags['auth']) {
+ $rval['auth'] = $rval['user'] = $rval['pass'] = null;
+ }
+ if(!$flags['port']) {
+ $rval['port'] = null;
+ }
+ if(!$flags['query']) {
+ $rval['query'] = null;
+ }
+ if(!$flags['fragment']) {
+ $rval['fragment'] = null;
+ }
+
+ $rval['normalizedPath'] = jsonld_remove_dot_segments(
+ $rval['path'], !!$rval['authority']);
+
+ return $rval;
+}
+
+/**
+ * Removes dot segments from a URL path.
+ *
+ * @param string $path the path to remove dot segments from.
+ * @param bool $has_authority true if the URL has an authority, false if not.
+ */
+function jsonld_remove_dot_segments($path, $has_authority) {
+ $rval = '';
+
+ if(strpos($path, '/') === 0) {
+ $rval = '/';
+ }
+
+ // RFC 3986 5.2.4 (reworked)
+ $input = explode('/', $path);
+ $output = array();
+ while(count($input) > 0) {
+ if($input[0] === '.' || ($input[0] === '' && count($input) > 1)) {
+ array_shift($input);
+ continue;
+ }
+ if($input[0] === '..') {
+ array_shift($input);
+ if($has_authority ||
+ (count($output) > 0 && $output[count($output) - 1] !== '..')) {
+ array_pop($output);
+ } else {
+ // leading relative URL '..'
+ $output[] = '..';
+ }
+ continue;
+ }
+ $output[] = array_shift($input);
+ }
+
+ return $rval . implode('/', $output);
+}
+
+/**
+ * Prepends a base IRI to the given relative IRI.
+ *
+ * @param mixed $base a string or the parsed base IRI.
+ * @param string $iri the relative IRI.
+ *
+ * @return string the absolute IRI.
+ */
+function jsonld_prepend_base($base, $iri) {
+ // skip IRI processing
+ if($base === null) {
+ return $iri;
+ }
+
+ // already an absolute IRI
+ if(strpos($iri, ':') !== false) {
+ return $iri;
+ }
+
+ // parse base if it is a string
+ if(is_string($base)) {
+ $base = jsonld_parse_url($base);
+ }
+
+ // parse given IRI
+ $rel = jsonld_parse_url($iri);
+
+ // per RFC3986 5.2.2
+ $transform = array('protocol' => $base['protocol']);
+
+ if($rel['authority'] !== null) {
+ $transform['authority'] = $rel['authority'];
+ $transform['path'] = $rel['path'];
+ $transform['query'] = $rel['query'];
+ } else {
+ $transform['authority'] = $base['authority'];
+
+ if($rel['path'] === '') {
+ $transform['path'] = $base['path'];
+ if($rel['query'] !== null) {
+ $transform['query'] = $rel['query'];
+ } else {
+ $transform['query'] = $base['query'];
+ }
+ } else {
+ if(strpos($rel['path'], '/') === 0) {
+ // IRI represents an absolute path
+ $transform['path'] = $rel['path'];
+ } else {
+ // merge paths
+ $path = $base['path'];
+
+ // append relative path to the end of the last directory from base
+ if($rel['path'] !== '') {
+ $idx = strrpos($path, '/');
+ $idx = ($idx === false) ? 0 : $idx + 1;
+ $path = substr($path, 0, $idx);
+ if(strlen($path) > 0 && substr($path, -1) !== '/') {
+ $path .= '/';
+ }
+ $path .= $rel['path'];
+ }
+
+ $transform['path'] = $path;
+ }
+ $transform['query'] = $rel['query'];
+ }
+ }
+
+ // remove slashes and dots in path
+ $transform['path'] = jsonld_remove_dot_segments(
+ $transform['path'], !!$transform['authority']);
+
+ // construct URL
+ $rval = $transform['protocol'];
+ if($transform['authority'] !== null) {
+ $rval .= '//' . $transform['authority'];
+ }
+ $rval .= $transform['path'];
+ if($transform['query'] !== null) {
+ $rval .= '?' . $transform['query'];
+ }
+ if($rel['fragment'] !== null) {
+ $rval .= '#' . $rel['fragment'];
+ }
+
+ // handle empty base
+ if($rval === '') {
+ $rval = './';
+ }
+
+ return $rval;
+}
+
+/**
+ * Removes a base IRI from the given absolute IRI.
+ *
+ * @param mixed $base the base IRI.
+ * @param string $iri the absolute IRI.
+ *
+ * @return string the relative IRI if relative to base, otherwise the absolute
+ * IRI.
+ */
+function jsonld_remove_base($base, $iri) {
+ // skip IRI processing
+ if($base === null) {
+ return $iri;
+ }
+
+ if(is_string($base)) {
+ $base = jsonld_parse_url($base);
+ }
+
+ // establish base root
+ $root = '';
+ if($base['href'] !== '') {
+ $root .= "{$base['protocol']}//{$base['authority']}";
+ } else if(strpos($iri, '//') === false) {
+ // support network-path reference with empty base
+ $root .= '//';
+ }
+
+ // IRI not relative to base
+ if($root === '' || strpos($iri, $root) !== 0) {
+ return $iri;
+ }
+
+ // remove root from IRI
+ $rel = jsonld_parse_url(substr($iri, strlen($root)));
+
+ // remove path segments that match (do not remove last segment unless there
+ // is a hash or query)
+ $base_segments = explode('/', $base['normalizedPath']);
+ $iri_segments = explode('/', $rel['normalizedPath']);
+ $last = ($rel['query'] || $rel['fragment']) ? 0 : 1;
+ while(count($base_segments) > 0 && count($iri_segments) > $last) {
+ if($base_segments[0] !== $iri_segments[0]) {
+ break;
+ }
+ array_shift($base_segments);
+ array_shift($iri_segments);
+ }
+
+ // use '../' for each non-matching base segment
+ $rval = '';
+ if(count($base_segments) > 0) {
+ // don't count the last segment (if it ends with '/' last path doesn't
+ // count and if it doesn't end with '/' it isn't a path)
+ array_pop($base_segments);
+ foreach($base_segments as $segment) {
+ $rval .= '../';
+ }
+ }
+
+ // prepend remaining segments
+ $rval .= implode('/', $iri_segments);
+
+ // add query and hash
+ if($rel['query'] !== null) {
+ $rval .= "?{$rel['query']}";
+ }
+ if($rel['fragment'] !== null) {
+ $rval .= "#{$rel['fragment']}";
+ }
+
+ if($rval === '') {
+ $rval = './';
+ }
+
+ return $rval;
+}
+
+
+/**
+ * A JSON-LD processor.
+ */
+class JsonLdProcessor {
+ /** XSD constants */
+ const XSD_BOOLEAN = 'http://www.w3.org/2001/XMLSchema#boolean';
+ const XSD_DOUBLE = 'http://www.w3.org/2001/XMLSchema#double';
+ const XSD_INTEGER = 'http://www.w3.org/2001/XMLSchema#integer';
+ const XSD_STRING = 'http://www.w3.org/2001/XMLSchema#string';
+
+ /** RDF constants */
+ const RDF_LIST = 'http://www.w3.org/1999/02/22-rdf-syntax-ns#List';
+ const RDF_FIRST = 'http://www.w3.org/1999/02/22-rdf-syntax-ns#first';
+ const RDF_REST = 'http://www.w3.org/1999/02/22-rdf-syntax-ns#rest';
+ const RDF_NIL = 'http://www.w3.org/1999/02/22-rdf-syntax-ns#nil';
+ const RDF_TYPE = 'http://www.w3.org/1999/02/22-rdf-syntax-ns#type';
+ const RDF_LANGSTRING =
+ 'http://www.w3.org/1999/02/22-rdf-syntax-ns#langString';
+
+ /** Restraints */
+ const MAX_CONTEXT_URLS = 10;
+
+ /** Processor-specific RDF dataset parsers. */
+ protected $rdfParsers = null;
+
+ /**
+ * Constructs a JSON-LD processor.
+ */
+ public function __construct() {}
+
+ /**
+ * Performs JSON-LD compaction.
+ *
+ * @param mixed $input the JSON-LD object to compact.
+ * @param mixed $ctx the context to compact with.
+ * @param assoc $options the compaction options.
+ * [base] the base IRI to use.
+ * [compactArrays] true to compact arrays to single values when
+ * appropriate, false not to (default: true).
+ * [graph] true to always output a top-level graph (default: false).
+ * [skipExpansion] true to assume the input is expanded and skip
+ * expansion, false not to, defaults to false.
+ * [activeCtx] true to also return the active context used.
+ * [documentLoader(url)] the document loader.
+ *
+ * @return mixed the compacted JSON-LD output.
+ */
+ public function compact($input, $ctx, $options) {
+ global $jsonld_default_load_document;
+
+ if($ctx === null) {
+ throw new JsonLdException(
+ 'The compaction context must not be null.',
+ 'jsonld.CompactError', 'invalid local context');
+ }
+
+ // nothing to compact
+ if($input === null) {
+ return null;
+ }
+
+ self::setdefaults($options, array(
+ 'base' => is_string($input) ? $input : '',
+ 'compactArrays' => true,
+ 'graph' => false,
+ 'skipExpansion' => false,
+ 'activeCtx' => false,
+ 'documentLoader' => $jsonld_default_load_document,
+ 'link' => false));
+ if($options['link']) {
+ // force skip expansion when linking, "link" is not part of the
+ // public API, it should only be called from framing
+ $options['skipExpansion'] = true;
+ }
+
+ if($options['skipExpansion'] === true) {
+ $expanded = $input;
+ } else {
+ // expand input
+ try {
+ $expanded = $this->expand($input, $options);
+ } catch(JsonLdException $e) {
+ throw new JsonLdException(
+ 'Could not expand input before compaction.',
+ 'jsonld.CompactError', null, null, $e);
+ }
+ }
+
+ // process context
+ $active_ctx = $this->_getInitialContext($options);
+ try {
+ $active_ctx = $this->processContext($active_ctx, $ctx, $options);
+ } catch(JsonLdException $e) {
+ throw new JsonLdException(
+ 'Could not process context before compaction.',
+ 'jsonld.CompactError', null, null, $e);
+ }
+
+ // do compaction
+ $compacted = $this->_compact($active_ctx, null, $expanded, $options);
+
+ if($options['compactArrays'] &&
+ !$options['graph'] && is_array($compacted)) {
+ if(count($compacted) === 1) {
+ // simplify to a single item
+ $compacted = $compacted[0];
+ } else if(count($compacted) === 0) {
+ // simplify to an empty object
+ $compacted = new stdClass();
+ }
+ } else if($options['graph']) {
+ // always use array if graph option is on
+ $compacted = self::arrayify($compacted);
+ }
+
+ // follow @context key
+ if(is_object($ctx) && property_exists($ctx, '@context')) {
+ $ctx = $ctx->{'@context'};
+ }
+
+ // build output context
+ $ctx = self::copy($ctx);
+ $ctx = self::arrayify($ctx);
+
+ // remove empty contexts
+ $tmp = $ctx;
+ $ctx = array();
+ foreach($tmp as $v) {
+ if(!is_object($v) || count(array_keys((array)$v)) > 0) {
+ $ctx[] = $v;
+ }
+ }
+
+ // remove array if only one context
+ $ctx_length = count($ctx);
+ $has_context = ($ctx_length > 0);
+ if($ctx_length === 1) {
+ $ctx = $ctx[0];
+ }
+
+ // add context and/or @graph
+ if(is_array($compacted)) {
+ // use '@graph' keyword
+ $kwgraph = $this->_compactIri($active_ctx, '@graph');
+ $graph = $compacted;
+ $compacted = new stdClass();
+ if($has_context) {
+ $compacted->{'@context'} = $ctx;
+ }
+ $compacted->{$kwgraph} = $graph;
+ } else if(is_object($compacted) && $has_context) {
+ // reorder keys so @context is first
+ $graph = $compacted;
+ $compacted = new stdClass();
+ $compacted->{'@context'} = $ctx;
+ foreach($graph as $k => $v) {
+ $compacted->{$k} = $v;
+ }
+ }
+
+ if($options['activeCtx']) {
+ return array('compacted' => $compacted, 'activeCtx' => $active_ctx);
+ }
+
+ return $compacted;
+ }
+
+ /**
+ * Performs JSON-LD expansion.
+ *
+ * @param mixed $input the JSON-LD object to expand.
+ * @param assoc $options the options to use:
+ * [base] the base IRI to use.
+ * [expandContext] a context to expand with.
+ * [keepFreeFloatingNodes] true to keep free-floating nodes,
+ * false not to, defaults to false.
+ * [documentLoader(url)] the document loader.
+ *
+ * @return array the expanded JSON-LD output.
+ */
+ public function expand($input, $options) {
+ global $jsonld_default_load_document;
+ self::setdefaults($options, array(
+ 'keepFreeFloatingNodes' => false,
+ 'documentLoader' => $jsonld_default_load_document));
+
+ // if input is a string, attempt to dereference remote document
+ if(is_string($input)) {
+ $remote_doc = call_user_func($options['documentLoader'], $input);
+ } else {
+ $remote_doc = (object)array(
+ 'contextUrl' => null,
+ 'documentUrl' => null,
+ 'document' => $input);
+ }
+
+ try {
+ if($remote_doc->document === null) {
+ throw new JsonLdException(
+ 'No remote document found at the given URL.',
+ 'jsonld.NullRemoteDocument');
+ }
+ if(is_string($remote_doc->document)) {
+ $remote_doc->document = self::_parse_json($remote_doc->document);
+ }
+ } catch(Exception $e) {
+ throw new JsonLdException(
+ 'Could not retrieve a JSON-LD document from the URL.',
+ 'jsonld.LoadDocumentError', 'loading document failed',
+ array('remoteDoc' => $remote_doc), $e);
+ }
+
+ // set default base
+ self::setdefault($options, 'base', $remote_doc->documentUrl ?: '');
+
+ // build meta-object and retrieve all @context urls
+ $input = (object)array(
+ 'document' => self::copy($remote_doc->document),
+ 'remoteContext' => (object)array(
+ '@context' => $remote_doc->contextUrl));
+ if(isset($options['expandContext'])) {
+ $expand_context = self::copy($options['expandContext']);
+ if(is_object($expand_context) &&
+ property_exists($expand_context, '@context')) {
+ $input->expandContext = $expand_context;
+ } else {
+ $input->expandContext = (object)array('@context' => $expand_context);
+ }
+ }
+
+ // retrieve all @context URLs in the input
+ try {
+ $this->_retrieveContextUrls(
+ $input, new stdClass(), $options['documentLoader'], $options['base']);
+ } catch(Exception $e) {
+ throw new JsonLdException(
+ 'Could not perform JSON-LD expansion.',
+ 'jsonld.ExpandError', null, null, $e);
+ }
+
+ $active_ctx = $this->_getInitialContext($options);
+ $document = $input->document;
+ $remote_context = $input->remoteContext->{'@context'};
+
+ // process optional expandContext
+ if(property_exists($input, 'expandContext')) {
+ $active_ctx = self::_processContext(
+ $active_ctx, $input->expandContext, $options);
+ }
+
+ // process remote context from HTTP Link Header
+ if($remote_context) {
+ $active_ctx = self::_processContext(
+ $active_ctx, $remote_context, $options);
+ }
+
+ // do expansion
+ $expanded = $this->_expand($active_ctx, null, $document, $options, false);
+
+ // optimize away @graph with no other properties
+ if(is_object($expanded) && property_exists($expanded, '@graph') &&
+ count(array_keys((array)$expanded)) === 1) {
+ $expanded = $expanded->{'@graph'};
+ } else if($expanded === null) {
+ $expanded = array();
+ }
+ // normalize to an array
+ return self::arrayify($expanded);
+ }
+
+ /**
+ * Performs JSON-LD flattening.
+ *
+ * @param mixed $input the JSON-LD to flatten.
+ * @param ctx the context to use to compact the flattened output, or null.
+ * @param assoc $options the options to use:
+ * [base] the base IRI to use.
+ * [expandContext] a context to expand with.
+ * [documentLoader(url)] the document loader.
+ *
+ * @return array the flattened output.
+ */
+ public function flatten($input, $ctx, $options) {
+ global $jsonld_default_load_document;
+ self::setdefaults($options, array(
+ 'base' => is_string($input) ? $input : '',
+ 'documentLoader' => $jsonld_default_load_document));
+
+ try {
+ // expand input
+ $expanded = $this->expand($input, $options);
+ } catch(Exception $e) {
+ throw new JsonLdException(
+ 'Could not expand input before flattening.',
+ 'jsonld.FlattenError', null, null, $e);
+ }
+
+ // do flattening
+ $flattened = $this->_flatten($expanded);
+
+ if($ctx === null) {
+ return $flattened;
+ }
+
+ // compact result (force @graph option to true, skip expansion)
+ $options['graph'] = true;
+ $options['skipExpansion'] = true;
+ try {
+ $compacted = $this->compact($flattened, $ctx, $options);
+ } catch(Exception $e) {
+ throw new JsonLdException(
+ 'Could not compact flattened output.',
+ 'jsonld.FlattenError', null, null, $e);
+ }
+
+ return $compacted;
+ }
+
+ /**
+ * Performs JSON-LD framing.
+ *
+ * @param mixed $input the JSON-LD object to frame.
+ * @param stdClass $frame the JSON-LD frame to use.
+ * @param $options the framing options.
+ * [base] the base IRI to use.
+ * [expandContext] a context to expand with.
+ * [embed] default @embed flag: '@last', '@always', '@never', '@link'
+ * (default: '@last').
+ * [explicit] default @explicit flag (default: false).
+ * [requireAll] default @requireAll flag (default: true).
+ * [omitDefault] default @omitDefault flag (default: false).
+ * [documentLoader(url)] the document loader.
+ *
+ * @return stdClass the framed JSON-LD output.
+ */
+ public function frame($input, $frame, $options) {
+ global $jsonld_default_load_document;
+ self::setdefaults($options, array(
+ 'base' => is_string($input) ? $input : '',
+ 'compactArrays' => true,
+ 'embed' => '@last',
+ 'explicit' => false,
+ 'requireAll' => true,
+ 'omitDefault' => false,
+ 'documentLoader' => $jsonld_default_load_document));
+
+ // if frame is a string, attempt to dereference remote document
+ if(is_string($frame)) {
+ $remote_frame = call_user_func($options['documentLoader'], $frame);
+ } else {
+ $remote_frame = (object)array(
+ 'contextUrl' => null,
+ 'documentUrl' => null,
+ 'document' => $frame);
+ }
+
+ try {
+ if($remote_frame->document === null) {
+ throw new JsonLdException(
+ 'No remote document found at the given URL.',
+ 'jsonld.NullRemoteDocument');
+ }
+ if(is_string($remote_frame->document)) {
+ $remote_frame->document = self::_parse_json($remote_frame->document);
+ }
+ } catch(Exception $e) {
+ throw new JsonLdException(
+ 'Could not retrieve a JSON-LD document from the URL.',
+ 'jsonld.LoadDocumentError', 'loading document failed',
+ array('remoteDoc' => $remote_frame), $e);
+ }
+
+ // preserve frame context
+ $frame = $remote_frame->document;
+ if($frame !== null) {
+ $ctx = (property_exists($frame, '@context') ?
+ $frame->{'@context'} : new stdClass());
+ if($remote_frame->contextUrl !== null) {
+ if($ctx !== null) {
+ $ctx = $remote_frame->contextUrl;
+ } else {
+ $ctx = self::arrayify($ctx);
+ $ctx[] = $remote_frame->contextUrl;
+ }
+ $frame->{'@context'} = $ctx;
+ }
+ }
+
+ try {
+ // expand input
+ $expanded = $this->expand($input, $options);
+ } catch(Exception $e) {
+ throw new JsonLdException(
+ 'Could not expand input before framing.',
+ 'jsonld.FrameError', null, null, $e);
+ }
+
+ try {
+ // expand frame
+ $opts = $options;
+ $opts['keepFreeFloatingNodes'] = true;
+ $expanded_frame = $this->expand($frame, $opts);
+ } catch(Exception $e) {
+ throw new JsonLdException(
+ 'Could not expand frame before framing.',
+ 'jsonld.FrameError', null, null, $e);
+ }
+
+ // do framing
+ $framed = $this->_frame($expanded, $expanded_frame, $options);
+
+ try {
+ // compact result (force @graph option to true, skip expansion, check
+ // for linked embeds)
+ $options['graph'] = true;
+ $options['skipExpansion'] = true;
+ $options['link'] = new ArrayObject();
+ $options['activeCtx'] = true;
+ $result = $this->compact($framed, $ctx, $options);
+ } catch(Exception $e) {
+ throw new JsonLdException(
+ 'Could not compact framed output.',
+ 'jsonld.FrameError', null, null, $e);
+ }
+
+ $compacted = $result['compacted'];
+ $active_ctx = $result['activeCtx'];
+
+ // get graph alias
+ $graph = $this->_compactIri($active_ctx, '@graph');
+ // remove @preserve from results
+ $options['link'] = new ArrayObject();
+ $compacted->{$graph} = $this->_removePreserve(
+ $active_ctx, $compacted->{$graph}, $options);
+ return $compacted;
+ }
+
+ /**
+ * Performs JSON-LD normalization.
+ *
+ * @param mixed $input the JSON-LD object to normalize.
+ * @param assoc $options the options to use:
+ * [base] the base IRI to use.
+ * [expandContext] a context to expand with.
+ * [inputFormat] the format if input is not JSON-LD:
+ * 'application/nquads' for N-Quads.
+ * [format] the format if output is a string:
+ * 'application/nquads' for N-Quads.
+ * [documentLoader(url)] the document loader.
+ *
+ * @return mixed the normalized output.
+ */
+ public function normalize($input, $options) {
+ global $jsonld_default_load_document;
+ self::setdefaults($options, array(
+ 'base' => is_string($input) ? $input : '',
+ 'documentLoader' => $jsonld_default_load_document));
+
+ if(isset($options['inputFormat'])) {
+ if($options['inputFormat'] != 'application/nquads') {
+ throw new JsonLdException(
+ 'Unknown normalization input format.', 'jsonld.NormalizeError');
+ }
+ $dataset = $this->parseNQuads($input);
+ } else {
+ try {
+ // convert to RDF dataset then do normalization
+ $opts = $options;
+ if(isset($opts['format'])) {
+ unset($opts['format']);
+ }
+ $opts['produceGeneralizedRdf'] = false;
+ $dataset = $this->toRDF($input, $opts);
+ } catch(Exception $e) {
+ throw new JsonLdException(
+ 'Could not convert input to RDF dataset before normalization.',
+ 'jsonld.NormalizeError', null, null, $e);
+ }
+ }
+
+ // do normalization
+ return $this->_normalize($dataset, $options);
+ }
+
+ /**
+ * Converts an RDF dataset to JSON-LD.
+ *
+ * @param mixed $dataset a serialized string of RDF in a format specified
+ * by the format option or an RDF dataset to convert.
+ * @param assoc $options the options to use:
+ * [format] the format if input is a string:
+ * 'application/nquads' for N-Quads (default).
+ * [useRdfType] true to use rdf:type, false to use @type
+ * (default: false).
+ * [useNativeTypes] true to convert XSD types into native types
+ * (boolean, integer, double), false not to (default: false).
+ *
+ * @return array the JSON-LD output.
+ */
+ public function fromRDF($dataset, $options) {
+ global $jsonld_rdf_parsers;
+
+ self::setdefaults($options, array(
+ 'useRdfType' => false,
+ 'useNativeTypes' => false));
+
+ if(!isset($options['format']) && is_string($dataset)) {
+ // set default format to nquads
+ $options['format'] = 'application/nquads';
+ }
+
+ // handle special format
+ if(isset($options['format']) && $options['format']) {
+ // supported formats (processor-specific and global)
+ if(($this->rdfParsers !== null &&
+ !property_exists($this->rdfParsers, $options['format'])) ||
+ $this->rdfParsers === null &&
+ !property_exists($jsonld_rdf_parsers, $options['format'])) {
+ throw new JsonLdException(
+ 'Unknown input format.',
+ 'jsonld.UnknownFormat', null, array('format' => $options['format']));
+ }
+ if($this->rdfParsers !== null) {
+ $callable = $this->rdfParsers->{$options['format']};
+ } else {
+ $callable = $jsonld_rdf_parsers->{$options['format']};
+ }
+ $dataset = call_user_func($callable, $dataset);
+ }
+
+ // convert from RDF
+ return $this->_fromRDF($dataset, $options);
+ }
+
+ /**
+ * Outputs the RDF dataset found in the given JSON-LD object.
+ *
+ * @param mixed $input the JSON-LD object.
+ * @param assoc $options the options to use:
+ * [base] the base IRI to use.
+ * [expandContext] a context to expand with.
+ * [format] the format to use to output a string:
+ * 'application/nquads' for N-Quads.
+ * [produceGeneralizedRdf] true to output generalized RDF, false
+ * to produce only standard RDF (default: false).
+ * [documentLoader(url)] the document loader.
+ *
+ * @return mixed the resulting RDF dataset (or a serialization of it).
+ */
+ public function toRDF($input, $options) {
+ global $jsonld_default_load_document;
+ self::setdefaults($options, array(
+ 'base' => is_string($input) ? $input : '',
+ 'produceGeneralizedRdf' => false,
+ 'documentLoader' => $jsonld_default_load_document));
+
+ try {
+ // expand input
+ $expanded = $this->expand($input, $options);
+ } catch(JsonLdException $e) {
+ throw new JsonLdException(
+ 'Could not expand input before serialization to RDF.',
+ 'jsonld.RdfError', null, null, $e);
+ }
+
+ // create node map for default graph (and any named graphs)
+ $namer = new UniqueNamer('_:b');
+ $node_map = (object)array('@default' => new stdClass());
+ $this->_createNodeMap($expanded, $node_map, '@default', $namer);
+
+ // output RDF dataset
+ $dataset = new stdClass();
+ $graph_names = array_keys((array)$node_map);
+ sort($graph_names);
+ foreach($graph_names as $graph_name) {
+ $graph = $node_map->{$graph_name};
+ // skip relative IRIs
+ if($graph_name === '@default' || self::_isAbsoluteIri($graph_name)) {
+ $dataset->{$graph_name} = $this->_graphToRDF($graph, $namer, $options);
+ }
+ }
+
+ $rval = $dataset;
+
+ // convert to output format
+ if(isset($options['format']) && $options['format']) {
+ // supported formats
+ if($options['format'] === 'application/nquads') {
+ $rval = self::toNQuads($dataset);
+ } else {
+ throw new JsonLdException(
+ 'Unknown output format.', 'jsonld.UnknownFormat',
+ null, array('format' => $options['format']));
+ }
+ }
+
+ return $rval;
+ }
+
+ /**
+ * Processes a local context, resolving any URLs as necessary, and returns a
+ * new active context in its callback.
+ *
+ * @param stdClass $active_ctx the current active context.
+ * @param mixed $local_ctx the local context to process.
+ * @param assoc $options the options to use:
+ * [documentLoader(url)] the document loader.
+ *
+ * @return stdClass the new active context.
+ */
+ public function processContext($active_ctx, $local_ctx, $options) {
+ global $jsonld_default_load_document;
+ self::setdefaults($options, array(
+ 'base' => '',
+ 'documentLoader' => $jsonld_default_load_document));
+
+ // return initial context early for null context
+ if($local_ctx === null) {
+ return $this->_getInitialContext($options);
+ }
+
+ // retrieve URLs in local_ctx
+ $local_ctx = self::copy($local_ctx);
+ if(is_string($local_ctx) or (
+ is_object($local_ctx) && !property_exists($local_ctx, '@context'))) {
+ $local_ctx = (object)array('@context' => $local_ctx);
+ }
+ try {
+ $this->_retrieveContextUrls(
+ $local_ctx, new stdClass(),
+ $options['documentLoader'], $options['base']);
+ } catch(Exception $e) {
+ throw new JsonLdException(
+ 'Could not process JSON-LD context.',
+ 'jsonld.ContextError', null, null, $e);
+ }
+
+ // process context
+ return $this->_processContext($active_ctx, $local_ctx, $options);
+ }
+
+ /**
+ * Returns true if the given subject has the given property.
+ *
+ * @param stdClass $subject the subject to check.
+ * @param string $property the property to look for.
+ *
+ * @return bool true if the subject has the given property, false if not.
+ */
+ public static function hasProperty($subject, $property) {
+ $rval = false;
+ if(property_exists($subject, $property)) {
+ $value = $subject->{$property};
+ $rval = (!is_array($value) || count($value) > 0);
+ }
+ return $rval;
+ }
+
+ /**
+ * Determines if the given value is a property of the given subject.
+ *
+ * @param stdClass $subject the subject to check.
+ * @param string $property the property to check.
+ * @param mixed $value the value to check.
+ *
+ * @return bool true if the value exists, false if not.
+ */
+ public static function hasValue($subject, $property, $value) {
+ $rval = false;
+ if(self::hasProperty($subject, $property)) {
+ $val = $subject->{$property};
+ $is_list = self::_isList($val);
+ if(is_array($val) || $is_list) {
+ if($is_list) {
+ $val = $val->{'@list'};
+ }
+ foreach($val as $v) {
+ if(self::compareValues($value, $v)) {
+ $rval = true;
+ break;
+ }
+ }
+ } else if(!is_array($value)) {
+ // avoid matching the set of values with an array value parameter
+ $rval = self::compareValues($value, $val);
+ }
+ }
+ return $rval;
+ }
+
+ /**
+ * Adds a value to a subject. If the value is an array, all values in the
+ * array will be added.
+ *
+ * Note: If the value is a subject that already exists as a property of the
+ * given subject, this method makes no attempt to deeply merge properties.
+ * Instead, the value will not be added.
+ *
+ * @param stdClass $subject the subject to add the value to.
+ * @param string $property the property that relates the value to the subject.
+ * @param mixed $value the value to add.
+ * @param assoc [$options] the options to use:
+ * [propertyIsArray] true if the property is always an array, false
+ * if not (default: false).
+ * [allowDuplicate] true to allow duplicates, false not to (uses a
+ * simple shallow comparison of subject ID or value)
+ * (default: true).
+ */
+ public static function addValue(
+ $subject, $property, $value, $options=array()) {
+ self::setdefaults($options, array(
+ 'allowDuplicate' => true,
+ 'propertyIsArray' => false));
+
+ if(is_array($value)) {
+ if(count($value) === 0 && $options['propertyIsArray'] &&
+ !property_exists($subject, $property)) {
+ $subject->{$property} = array();
+ }
+ foreach($value as $v) {
+ self::addValue($subject, $property, $v, $options);
+ }
+ } else if(property_exists($subject, $property)) {
+ // check if subject already has value if duplicates not allowed
+ $has_value = (!$options['allowDuplicate'] &&
+ self::hasValue($subject, $property, $value));
+
+ // make property an array if value not present or always an array
+ if(!is_array($subject->{$property}) &&
+ (!$has_value || $options['propertyIsArray'])) {
+ $subject->{$property} = array($subject->{$property});
+ }
+
+ // add new value
+ if(!$has_value) {
+ $subject->{$property}[] = $value;
+ }
+ } else {
+ // add new value as set or single value
+ $subject->{$property} = ($options['propertyIsArray'] ?
+ array($value) : $value);
+ }
+ }
+
+ /**
+ * Gets all of the values for a subject's property as an array.
+ *
+ * @param stdClass $subject the subject.
+ * @param string $property the property.
+ *
+ * @return array all of the values for a subject's property as an array.
+ */
+ public static function getValues($subject, $property) {
+ $rval = (property_exists($subject, $property) ?
+ $subject->{$property} : array());
+ return self::arrayify($rval);
+ }
+
+ /**
+ * Removes a property from a subject.
+ *
+ * @param stdClass $subject the subject.
+ * @param string $property the property.
+ */
+ public static function removeProperty($subject, $property) {
+ unset($subject->{$property});
+ }
+
+ /**
+ * Removes a value from a subject.
+ *
+ * @param stdClass $subject the subject.
+ * @param string $property the property that relates the value to the subject.
+ * @param mixed $value the value to remove.
+ * @param assoc [$options] the options to use:
+ * [propertyIsArray] true if the property is always an array,
+ * false if not (default: false).
+ */
+ public static function removeValue(
+ $subject, $property, $value, $options=array()) {
+ self::setdefaults($options, array(
+ 'propertyIsArray' => false));
+
+ // filter out value
+ $filter = function($e) use ($value) {
+ return !self::compareValues($e, $value);
+ };
+ $values = self::getValues($subject, $property);
+ $values = array_values(array_filter($values, $filter));
+
+ if(count($values) === 0) {
+ self::removeProperty($subject, $property);
+ } else if(count($values) === 1 && !$options['propertyIsArray']) {
+ $subject->{$property} = $values[0];
+ } else {
+ $subject->{$property} = $values;
+ }
+ }
+
+ /**
+ * Compares two JSON-LD values for equality. Two JSON-LD values will be
+ * considered equal if:
+ *
+ * 1. They are both primitives of the same type and value.
+ * 2. They are both @values with the same @value, @type, @language,
+ * and @index, OR
+ * 3. They both have @ids that are the same.
+ *
+ * @param mixed $v1 the first value.
+ * @param mixed $v2 the second value.
+ *
+ * @return bool true if v1 and v2 are considered equal, false if not.
+ */
+ public static function compareValues($v1, $v2) {
+ // 1. equal primitives
+ if($v1 === $v2) {
+ return true;
+ }
+
+ // 2. equal @values
+ if(self::_isValue($v1) && self::_isValue($v2)) {
+ return (
+ self::_compareKeyValues($v1, $v2, '@value') &&
+ self::_compareKeyValues($v1, $v2, '@type') &&
+ self::_compareKeyValues($v1, $v2, '@language') &&
+ self::_compareKeyValues($v1, $v2, '@index'));
+ }
+
+ // 3. equal @ids
+ if(is_object($v1) && property_exists($v1, '@id') &&
+ is_object($v2) && property_exists($v2, '@id')) {
+ return $v1->{'@id'} === $v2->{'@id'};
+ }
+
+ return false;
+ }
+
+ /**
+ * Gets the value for the given active context key and type, null if none is
+ * set.
+ *
+ * @param stdClass $ctx the active context.
+ * @param string $key the context key.
+ * @param string [$type] the type of value to get (eg: '@id', '@type'), if not
+ * specified gets the entire entry for a key, null if not found.
+ *
+ * @return mixed the value.
+ */
+ public static function getContextValue($ctx, $key, $type) {
+ $rval = null;
+
+ // return null for invalid key
+ if($key === null) {
+ return $rval;
+ }
+
+ // get default language
+ if($type === '@language' && property_exists($ctx, $type)) {
+ $rval = $ctx->{$type};
+ }
+
+ // get specific entry information
+ if(property_exists($ctx->mappings, $key)) {
+ $entry = $ctx->mappings->{$key};
+ if($entry === null) {
+ return null;
+ }
+
+ if($type === null) {
+ // return whole entry
+ $rval = $entry;
+ } else if(property_exists($entry, $type)) {
+ // return entry value for type
+ $rval = $entry->{$type};
+ }
+ }
+
+ return $rval;
+ }
+
+ /**
+ * Parses RDF in the form of N-Quads.
+ *
+ * @param string $input the N-Quads input to parse.
+ *
+ * @return stdClass an RDF dataset.
+ */
+ public static function parseNQuads($input) {
+ // define partial regexes
+ $iri = '(?:<([^:]+:[^>]*)>)';
+ $bnode = '(_:(?:[A-Za-z][A-Za-z0-9]*))';
+ $plain = '"([^"\\\\]*(?:\\\\.[^"\\\\]*)*)"';
+ $datatype = "(?:\\^\\^$iri)";
+ $language = '(?:@([a-z]+(?:-[a-z0-9]+)*))';
+ $literal = "(?:$plain(?:$datatype|$language)?)";
+ $ws = '[ \\t]';
+ $eoln = '/(?:\r\n)|(?:\n)|(?:\r)/';
+ $empty = "/^$ws*$/";
+
+ // define quad part regexes
+ $subject = "(?:$iri|$bnode)$ws+";
+ $property = "$iri$ws+";
+ $object = "(?:$iri|$bnode|$literal)$ws*";
+ $graph_name = "(?:\\.|(?:(?:$iri|$bnode)$ws*\\.))";
+
+ // full quad regex
+ $quad = "/^$ws*$subject$property$object$graph_name$ws*$/";
+
+ // build RDF dataset
+ $dataset = new stdClass();
+
+ // split N-Quad input into lines
+ $lines = preg_split($eoln, $input);
+ $line_number = 0;
+ foreach($lines as $line) {
+ $line_number += 1;
+
+ // skip empty lines
+ if(preg_match($empty, $line)) {
+ continue;
+ }
+
+ // parse quad
+ if(!preg_match($quad, $line, $match)) {
+ throw new JsonLdException(
+ 'Error while parsing N-Quads; invalid quad.',
+ 'jsonld.ParseError', null, array('line' => $line_number));
+ }
+
+ // create RDF triple
+ $triple = (object)array(
+ 'subject' => new stdClass(),
+ 'predicate' => new stdClass(),
+ 'object' => new stdClass());
+
+ // get subject
+ if($match[1] !== '') {
+ $triple->subject->type = 'IRI';
+ $triple->subject->value = $match[1];
+ } else {
+ $triple->subject->type = 'blank node';
+ $triple->subject->value = $match[2];
+ }
+
+ // get predicate
+ $triple->predicate->type = 'IRI';
+ $triple->predicate->value = $match[3];
+
+ // get object
+ if($match[4] !== '') {
+ $triple->object->type = 'IRI';
+ $triple->object->value = $match[4];
+ } else if($match[5] !== '') {
+ $triple->object->type = 'blank node';
+ $triple->object->value = $match[5];
+ } else {
+ $triple->object->type = 'literal';
+ $unescaped = str_replace(
+ array('\"', '\t', '\n', '\r', '\\\\'),
+ array('"', "\t", "\n", "\r", '\\'),
+ $match[6]);
+ if(isset($match[7]) && $match[7] !== '') {
+ $triple->object->datatype = $match[7];
+ } else if(isset($match[8]) && $match[8] !== '') {
+ $triple->object->datatype = self::RDF_LANGSTRING;
+ $triple->object->language = $match[8];
+ } else {
+ $triple->object->datatype = self::XSD_STRING;
+ }
+ $triple->object->value = $unescaped;
+ }
+
+ // get graph name ('@default' is used for the default graph)
+ $name = '@default';
+ if(isset($match[9]) && $match[9] !== '') {
+ $name = $match[9];
+ } else if(isset($match[10]) && $match[10] !== '') {
+ $name = $match[10];
+ }
+
+ // initialize graph in dataset
+ if(!property_exists($dataset, $name)) {
+ $dataset->{$name} = array($triple);
+ } else {
+ // add triple if unique to its graph
+ $unique = true;
+ $triples = &$dataset->{$name};
+ foreach($triples as $t) {
+ if(self::_compareRDFTriples($t, $triple)) {
+ $unique = false;
+ break;
+ }
+ }
+ if($unique) {
+ $triples[] = $triple;
+ }
+ }
+ }
+
+ return $dataset;
+ }
+
+ /**
+ * Converts an RDF dataset to N-Quads.
+ *
+ * @param stdClass $dataset the RDF dataset to convert.
+ *
+ * @return string the N-Quads string.
+ */
+ public static function toNQuads($dataset) {
+ $quads = array();
+ foreach($dataset as $graph_name => $triples) {
+ foreach($triples as $triple) {
+ if($graph_name === '@default') {
+ $graph_name = null;
+ }
+ $quads[] = self::toNQuad($triple, $graph_name);
+ }
+ }
+ sort($quads);
+ return implode($quads);
+ }
+
+ /**
+ * Converts an RDF triple and graph name to an N-Quad string (a single quad).
+ *
+ * @param stdClass $triple the RDF triple to convert.
+ * @param mixed $graph_name the name of the graph containing the triple, null
+ * for the default graph.
+ * @param string $bnode the bnode the quad is mapped to (optional, for
+ * use during normalization only).
+ *
+ * @return string the N-Quad string.
+ */
+ public static function toNQuad($triple, $graph_name, $bnode=null) {
+ $s = $triple->subject;
+ $p = $triple->predicate;
+ $o = $triple->object;
+ $g = $graph_name;
+
+ $quad = '';
+
+ // subject is an IRI
+ if($s->type === 'IRI') {
+ $quad .= "<{$s->value}>";
+ } else if($bnode !== null) {
+ // bnode normalization mode
+ $quad .= ($s->value === $bnode) ? '_:a' : '_:z';
+ } else {
+ // bnode normal mode
+ $quad .= $s->value;
+ }
+ $quad .= ' ';
+
+ // predicate is an IRI
+ if($p->type === 'IRI') {
+ $quad .= "<{$p->value}>";
+ } else if($bnode !== null) {
+ // FIXME: TBD what to do with bnode predicates during normalization
+ // bnode normalization mode
+ $quad .= '_:p';
+ } else {
+ // bnode normal mode
+ $quad .= $p->value;
+ }
+ $quad .= ' ';
+
+ // object is IRI, bnode, or literal
+ if($o->type === 'IRI') {
+ $quad .= "<{$o->value}>";
+ } else if($o->type === 'blank node') {
+ if($bnode !== null) {
+ // normalization mode
+ $quad .= ($o->value === $bnode) ? '_:a' : '_:z';
+ } else {
+ // normal mode
+ $quad .= $o->value;
+ }
+ } else {
+ $escaped = str_replace(
+ array('\\', "\t", "\n", "\r", '"'),
+ array('\\\\', '\t', '\n', '\r', '\"'),
+ $o->value);
+ $quad .= '"' . $escaped . '"';
+ if($o->datatype === self::RDF_LANGSTRING) {
+ if($o->language) {
+ $quad .= "@{$o->language}";
+ }
+ } else if($o->datatype !== self::XSD_STRING) {
+ $quad .= "^^<{$o->datatype}>";
+ }
+ }
+
+ // graph
+ if($g !== null) {
+ if(strpos($g, '_:') !== 0) {
+ $quad .= " <$g>";
+ } else if($bnode) {
+ $quad .= ' _:g';
+ } else {
+ $quad .= " $g";
+ }
+ }
+
+ $quad .= " .\n";
+ return $quad;
+ }
+
+ /**
+ * Registers a processor-specific RDF dataset parser by content-type.
+ * Global parsers will no longer be used by this processor.
+ *
+ * @param string $content_type the content-type for the parser.
+ * @param callable $parser(input) the parser function (takes a string as
+ * a parameter and returns an RDF dataset).
+ */
+ public function registerRDFParser($content_type, $parser) {
+ if($this->rdfParsers === null) {
+ $this->rdfParsers = new stdClass();
+ }
+ $this->rdfParsers->{$content_type} = $parser;
+ }
+
+ /**
+ * Unregisters a process-specific RDF dataset parser by content-type. If
+ * there are no remaining processor-specific parsers, then the global
+ * parsers will be re-enabled.
+ *
+ * @param string $content_type the content-type for the parser.
+ */
+ public function unregisterRDFParser($content_type) {
+ if($this->rdfParsers !== null &&
+ property_exists($this->rdfParsers, $content_type)) {
+ unset($this->rdfParsers->{$content_type});
+ if(count(get_object_vars($content_type)) === 0) {
+ $this->rdfParsers = null;
+ }
+ }
+ }
+
+ /**
+ * If $value is an array, returns $value, otherwise returns an array
+ * containing $value as the only element.
+ *
+ * @param mixed $value the value.
+ *
+ * @return array an array.
+ */
+ public static function arrayify($value) {
+ return is_array($value) ? $value : array($value);
+ }
+
+ /**
+ * Clones an object, array, or string/number.
+ *
+ * @param mixed $value the value to clone.
+ *
+ * @return mixed the cloned value.
+ */
+ public static function copy($value) {
+ if(is_object($value) || is_array($value)) {
+ return unserialize(serialize($value));
+ }
+ return $value;
+ }
+
+ /**
+ * Sets the value of a key for the given array if that property
+ * has not already been set.
+ *
+ * @param &assoc $arr the object to update.
+ * @param string $key the key to update.
+ * @param mixed $value the value to set.
+ */
+ public static function setdefault(&$arr, $key, $value) {
+ isset($arr[$key]) or $arr[$key] = $value;
+ }
+
+ /**
+ * Sets default values for keys in the given array.
+ *
+ * @param &assoc $arr the object to update.
+ * @param assoc $defaults the default keys and values.
+ */
+ public static function setdefaults(&$arr, $defaults) {
+ foreach($defaults as $key => $value) {
+ self::setdefault($arr, $key, $value);
+ }
+ }
+
+ /**
+ * Recursively compacts an element using the given active context. All values
+ * must be in expanded form before this method is called.
+ *
+ * @param stdClass $active_ctx the active context to use.
+ * @param mixed $active_property the compacted property with the element
+ * to compact, null for none.
+ * @param mixed $element the element to compact.
+ * @param assoc $options the compaction options.
+ *
+ * @return mixed the compacted value.
+ */
+ protected function _compact(
+ $active_ctx, $active_property, $element, $options) {
+ // recursively compact array
+ if(is_array($element)) {
+ $rval = array();
+ foreach($element as $e) {
+ // compact, dropping any null values
+ $compacted = $this->_compact(
+ $active_ctx, $active_property, $e, $options);
+ if($compacted !== null) {
+ $rval[] = $compacted;
+ }
+ }
+ if($options['compactArrays'] && count($rval) === 1) {
+ // use single element if no container is specified
+ $container = self::getContextValue(
+ $active_ctx, $active_property, '@container');
+ if($container === null) {
+ $rval = $rval[0];
+ }
+ }
+ return $rval;
+ }
+
+ // recursively compact object
+ if(is_object($element)) {
+ if($options['link'] && property_exists($element, '@id') &&
+ isset($options['link'][$element->{'@id'}])) {
+ // check for a linked element to reuse
+ $linked = $options['link'][$element->{'@id'}];
+ foreach($linked as $link) {
+ if($link['expanded'] === $element) {
+ return $link['compacted'];
+ }
+ }
+ }
+
+ // do value compaction on @values and subject references
+ if(self::_isValue($element) || self::_isSubjectReference($element)) {
+ $rval = $this->_compactValue($active_ctx, $active_property, $element);
+ if($options['link'] && self::_isSubjectReference($element)) {
+ // store linked element
+ if(!isset($options['link'][$element->{'@id'}])) {
+ $options['link'][$element->{'@id'}] = array();
+ }
+ $options['link'][$element->{'@id'}][] = array(
+ 'expanded' => $element, 'compacted' => $rval);
+ }
+ return $rval;
+ }
+
+ // FIXME: avoid misuse of active property as an expanded property?
+ $inside_reverse = ($active_property === '@reverse');
+
+ $rval = new stdClass();
+
+ if($options['link'] && property_exists($element, '@id')) {
+ // store linked element
+ if(!isset($options['link'][$element->{'@id'}])) {
+ $options['link'][$element->{'@id'}] = array();
+ }
+ $options['link'][$element->{'@id'}][] = array(
+ 'expanded' => $element, 'compacted' => $rval);
+ }
+
+ // process element keys in order
+ $keys = array_keys((array)$element);
+ sort($keys);
+ foreach($keys as $expanded_property) {
+ $expanded_value = $element->{$expanded_property};
+
+ // compact @id and @type(s)
+ if($expanded_property === '@id' || $expanded_property === '@type') {
+ if(is_string($expanded_value)) {
+ // compact single @id
+ $compacted_value = $this->_compactIri(
+ $active_ctx, $expanded_value, null,
+ array('vocab' => ($expanded_property === '@type')));
+ } else {
+ // expanded value must be a @type array
+ $compacted_value = array();
+ foreach($expanded_value as $ev) {
+ $compacted_value[] = $this->_compactIri(
+ $active_ctx, $ev, null, array('vocab' => true));
+ }
+ }
+
+ // use keyword alias and add value
+ $alias = $this->_compactIri($active_ctx, $expanded_property);
+ $is_array = (is_array($compacted_value) &&
+ count($expanded_value) === 0);
+ self::addValue(
+ $rval, $alias, $compacted_value,
+ array('propertyIsArray' => $is_array));
+ continue;
+ }
+
+ // handle @reverse
+ if($expanded_property === '@reverse') {
+ // recursively compact expanded value
+ $compacted_value = $this->_compact(
+ $active_ctx, '@reverse', $expanded_value, $options);
+
+ // handle double-reversed properties
+ foreach($compacted_value as $compacted_property => $value) {
+ if(property_exists($active_ctx->mappings, $compacted_property) &&
+ $active_ctx->mappings->{$compacted_property} &&
+ $active_ctx->mappings->{$compacted_property}->reverse) {
+ $container = self::getContextValue(
+ $active_ctx, $compacted_property, '@container');
+ $use_array = ($container === '@set' ||
+ !$options['compactArrays']);
+ self::addValue(
+ $rval, $compacted_property, $value,
+ array('propertyIsArray' => $use_array));
+ unset($compacted_value->{$compacted_property});
+ }
+ }
+
+ if(count(array_keys((array)$compacted_value)) > 0) {
+ // use keyword alias and add value
+ $alias = $this->_compactIri($active_ctx, $expanded_property);
+ self::addValue($rval, $alias, $compacted_value);
+ }
+
+ continue;
+ }
+
+ // handle @index property
+ if($expanded_property === '@index') {
+ // drop @index if inside an @index container
+ $container = self::getContextValue(
+ $active_ctx, $active_property, '@container');
+ if($container === '@index') {
+ continue;
+ }
+
+ // use keyword alias and add value
+ $alias = $this->_compactIri($active_ctx, $expanded_property);
+ self::addValue($rval, $alias, $expanded_value);
+ continue;
+ }
+
+ // skip array processing for keywords that aren't @graph or @list
+ if($expanded_property !== '@graph' && $expanded_property !== '@list' &&
+ self::_isKeyword($expanded_property)) {
+ // use keyword alias and add value as is
+ $alias = $this->_compactIri($active_ctx, $expanded_property);
+ self::addValue($rval, $alias, $expanded_value);
+ continue;
+ }
+
+ // Note: expanded value must be an array due to expansion algorithm.
+
+ // preserve empty arrays
+ if(count($expanded_value) === 0) {
+ $item_active_property = $this->_compactIri(
+ $active_ctx, $expanded_property, $expanded_value,
+ array('vocab' => true), $inside_reverse);
+ self::addValue(
+ $rval, $item_active_property, array(),
+ array('propertyIsArray' => true));
+ }
+
+ // recusively process array values
+ foreach($expanded_value as $expanded_item) {
+ // compact property and get container type
+ $item_active_property = $this->_compactIri(
+ $active_ctx, $expanded_property, $expanded_item,
+ array('vocab' => true), $inside_reverse);
+ $container = self::getContextValue(
+ $active_ctx, $item_active_property, '@container');
+
+ // get @list value if appropriate
+ $is_list = self::_isList($expanded_item);
+ $list = null;
+ if($is_list) {
+ $list = $expanded_item->{'@list'};
+ }
+
+ // recursively compact expanded item
+ $compacted_item = $this->_compact(
+ $active_ctx, $item_active_property,
+ $is_list ? $list : $expanded_item, $options);
+
+ // handle @list
+ if($is_list) {
+ // ensure @list value is an array
+ $compacted_item = self::arrayify($compacted_item);
+
+ if($container !== '@list') {
+ // wrap using @list alias
+ $compacted_item = (object)array(
+ $this->_compactIri($active_ctx, '@list') => $compacted_item);
+
+ // include @index from expanded @list, if any
+ if(property_exists($expanded_item, '@index')) {
+ $compacted_item->{$this->_compactIri($active_ctx, '@index')} =
+ $expanded_item->{'@index'};
+ }
+ } else if(property_exists($rval, $item_active_property)) {
+ // can't use @list container for more than 1 list
+ throw new JsonLdException(
+ 'JSON-LD compact error; property has a "@list" @container ' .
+ 'rule but there is more than a single @list that matches ' .
+ 'the compacted term in the document. Compaction might mix ' .
+ 'unwanted items into the list.', 'jsonld.SyntaxError',
+ 'compaction to list of lists');
+ }
+ }
+
+ // handle language and index maps
+ if($container === '@language' || $container === '@index') {
+ // get or create the map object
+ if(property_exists($rval, $item_active_property)) {
+ $map_object = $rval->{$item_active_property};
+ } else {
+ $rval->{$item_active_property} = $map_object = new stdClass();
+ }
+
+ // if container is a language map, simplify compacted value to
+ // a simple string
+ if($container === '@language' && self::_isValue($compacted_item)) {
+ $compacted_item = $compacted_item->{'@value'};
+ }
+
+ // add compact value to map object using key from expanded value
+ // based on the container type
+ self::addValue(
+ $map_object, $expanded_item->{$container}, $compacted_item);
+ } else {
+ // use an array if: compactArrays flag is false,
+ // @container is @set or @list, value is an empty
+ // array, or key is @graph
+ $is_array = (!$options['compactArrays'] ||
+ $container === '@set' || $container === '@list' ||
+ (is_array($compacted_item) && count($compacted_item) === 0) ||
+ $expanded_property === '@list' ||
+ $expanded_property === '@graph');
+
+ // add compact value
+ self::addValue(
+ $rval, $item_active_property, $compacted_item,
+ array('propertyIsArray' => $is_array));
+ }
+ }
+ }
+
+ return $rval;
+ }
+
+ // only primitives remain which are already compact
+ return $element;
+ }
+
+ /**
+ * Recursively expands an element using the given context. Any context in
+ * the element will be removed. All context URLs must have been retrieved
+ * before calling this method.
+ *
+ * @param stdClass $active_ctx the active context to use.
+ * @param mixed $active_property the property for the element, null for none.
+ * @param mixed $element the element to expand.
+ * @param assoc $options the expansion options.
+ * @param bool $inside_list true if the property is a list, false if not.
+ *
+ * @return mixed the expanded value.
+ */
+ protected function _expand(
+ $active_ctx, $active_property, $element, $options, $inside_list) {
+ // nothing to expand
+ if($element === null) {
+ return $element;
+ }
+
+ // recursively expand array
+ if(is_array($element)) {
+ $rval = array();
+ $container = self::getContextValue(
+ $active_ctx, $active_property, '@container');
+ $inside_list = $inside_list || $container === '@list';
+ foreach($element as $e) {
+ // expand element
+ $e = $this->_expand(
+ $active_ctx, $active_property, $e, $options, $inside_list);
+ if($inside_list && (is_array($e) || self::_isList($e))) {
+ // lists of lists are illegal
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; lists of lists are not permitted.',
+ 'jsonld.SyntaxError', 'list of lists');
+ }
+ // drop null values
+ if($e !== null) {
+ if(is_array($e)) {
+ $rval = array_merge($rval, $e);
+ } else {
+ $rval[] = $e;
+ }
+ }
+ }
+ return $rval;
+ }
+
+ if(!is_object($element)) {
+ // drop free-floating scalars that are not in lists
+ if(!$inside_list &&
+ ($active_property === null ||
+ $this->_expandIri($active_ctx, $active_property,
+ array('vocab' => true)) === '@graph')) {
+ return null;
+ }
+
+ // expand element according to value expansion rules
+ return $this->_expandValue($active_ctx, $active_property, $element);
+ }
+
+ // recursively expand object:
+
+ // if element has a context, process it
+ if(property_exists($element, '@context')) {
+ $active_ctx = $this->_processContext(
+ $active_ctx, $element->{'@context'}, $options);
+ }
+
+ // expand the active property
+ $expanded_active_property = $this->_expandIri(
+ $active_ctx, $active_property, array('vocab' => true));
+
+ $rval = new stdClass();
+ $keys = array_keys((array)$element);
+ sort($keys);
+ foreach($keys as $key) {
+ $value = $element->{$key};
+
+ if($key === '@context') {
+ continue;
+ }
+
+ // expand key to IRI
+ $expanded_property = $this->_expandIri(
+ $active_ctx, $key, array('vocab' => true));
+
+ // drop non-absolute IRI keys that aren't keywords
+ if($expanded_property === null ||
+ !(self::_isAbsoluteIri($expanded_property) ||
+ self::_isKeyword($expanded_property))) {
+ continue;
+ }
+
+ if(self::_isKeyword($expanded_property)) {
+ if($expanded_active_property === '@reverse') {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; a keyword cannot be used as a @reverse ' .
+ 'property.', 'jsonld.SyntaxError', 'invalid reverse property map',
+ array('value' => $value));
+ }
+ if(property_exists($rval, $expanded_property)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; colliding keywords detected.',
+ 'jsonld.SyntaxError', 'colliding keywords',
+ array('keyword' => $expanded_property));
+ }
+ }
+
+ // syntax error if @id is not a string
+ if($expanded_property === '@id' && !is_string($value)) {
+ if(!isset($options['isFrame']) || !$options['isFrame']) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; "@id" value must a string.',
+ 'jsonld.SyntaxError', 'invalid @id value',
+ array('value' => $value));
+ }
+ if(!is_object($value)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; "@id" value must a string or an object.',
+ 'jsonld.SyntaxError', 'invalid @id value',
+ array('value' => $value));
+ }
+ }
+
+ // validate @type value
+ if($expanded_property === '@type') {
+ $this->_validateTypeValue($value);
+ }
+
+ // @graph must be an array or an object
+ if($expanded_property === '@graph' &&
+ !(is_object($value) || is_array($value))) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; "@graph" value must not be an ' .
+ 'object or an array.', 'jsonld.SyntaxError',
+ 'invalid @graph value', array('value' => $value));
+ }
+
+ // @value must not be an object or an array
+ if($expanded_property === '@value' &&
+ (is_object($value) || is_array($value))) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; "@value" value must not be an ' .
+ 'object or an array.', 'jsonld.SyntaxError',
+ 'invalid value object value', array('value' => $value));
+ }
+
+ // @language must be a string
+ if($expanded_property === '@language') {
+ if($value === null) {
+ // drop null @language values, they expand as if they didn't exist
+ continue;
+ }
+ if(!is_string($value)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; "@language" value must not be a string.',
+ 'jsonld.SyntaxError', 'invalid language-tagged string',
+ array('value' => $value));
+ }
+ // ensure language value is lowercase
+ $value = strtolower($value);
+ }
+
+ // @index must be a string
+ if($expanded_property === '@index') {
+ if(!is_string($value)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; "@index" value must be a string.',
+ 'jsonld.SyntaxError', 'invalid @index value',
+ array('value' => $value));
+ }
+ }
+
+ // @reverse must be an object
+ if($expanded_property === '@reverse') {
+ if(!is_object($value)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; "@reverse" value must be an object.',
+ 'jsonld.SyntaxError', 'invalid @reverse value',
+ array('value' => $value));
+ }
+
+ $expanded_value = $this->_expand(
+ $active_ctx, '@reverse', $value, $options, $inside_list);
+
+ // properties double-reversed
+ if(property_exists($expanded_value, '@reverse')) {
+ foreach($expanded_value->{'@reverse'} as $rproperty => $rvalue) {
+ self::addValue(
+ $rval, $rproperty, $rvalue, array('propertyIsArray' => true));
+ }
+ }
+
+ // FIXME: can this be merged with code below to simplify?
+ // merge in all reversed properties
+ if(property_exists($rval, '@reverse')) {
+ $reverse_map = $rval->{'@reverse'};
+ } else {
+ $reverse_map = null;
+ }
+ foreach($expanded_value as $property => $items) {
+ if($property === '@reverse') {
+ continue;
+ }
+ if($reverse_map === null) {
+ $reverse_map = $rval->{'@reverse'} = new stdClass();
+ }
+ self::addValue(
+ $reverse_map, $property, array(),
+ array('propertyIsArray' => true));
+ foreach($items as $item) {
+ if(self::_isValue($item) || self::_isList($item)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; "@reverse" value must not be a ' +
+ '@value or an @list.', 'jsonld.SyntaxError',
+ 'invalid reverse property value',
+ array('value' => $expanded_value));
+ }
+ self::addValue(
+ $reverse_map, $property, $item,
+ array('propertyIsArray' => true));
+ }
+ }
+
+ continue;
+ }
+
+ $container = self::getContextValue($active_ctx, $key, '@container');
+
+ if($container === '@language' && is_object($value)) {
+ // handle language map container (skip if value is not an object)
+ $expanded_value = $this->_expandLanguageMap($value);
+ } else if($container === '@index' && is_object($value)) {
+ // handle index container (skip if value is not an object)
+ $expanded_value = array();
+ $value_keys = array_keys((array)$value);
+ sort($value_keys);
+ foreach($value_keys as $value_key) {
+ $val = $value->{$value_key};
+ $val = self::arrayify($val);
+ $val = $this->_expand($active_ctx, $key, $val, $options, false);
+ foreach($val as $item) {
+ if(!property_exists($item, '@index')) {
+ $item->{'@index'} = $value_key;
+ }
+ $expanded_value[] = $item;
+ }
+ }
+ } else {
+ // recurse into @list or @set
+ $is_list = ($expanded_property === '@list');
+ if($is_list || $expanded_property === '@set') {
+ $next_active_property = $active_property;
+ if($is_list && $expanded_active_property === '@graph') {
+ $next_active_property = null;
+ }
+ $expanded_value = $this->_expand(
+ $active_ctx, $next_active_property, $value, $options, $is_list);
+ if($is_list && self::_isList($expanded_value)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; lists of lists are not permitted.',
+ 'jsonld.SyntaxError', 'list of lists');
+ }
+ } else {
+ // recursively expand value with key as new active property
+ $expanded_value = $this->_expand(
+ $active_ctx, $key, $value, $options, false);
+ }
+ }
+
+ // drop null values if property is not @value
+ if($expanded_value === null && $expanded_property !== '@value') {
+ continue;
+ }
+
+ // convert expanded value to @list if container specifies it
+ if($expanded_property !== '@list' && !self::_isList($expanded_value) &&
+ $container === '@list') {
+ // ensure expanded value is an array
+ $expanded_value = (object)array(
+ '@list' => self::arrayify($expanded_value));
+ }
+
+ // FIXME: can this be merged with code above to simplify?
+ // merge in reverse properties
+ if(property_exists($active_ctx->mappings, $key) &&
+ $active_ctx->mappings->{$key} &&
+ $active_ctx->mappings->{$key}->reverse) {
+ if(property_exists($rval, '@reverse')) {
+ $reverse_map = $rval->{'@reverse'};
+ } else {
+ $reverse_map = $rval->{'@reverse'} = new stdClass();
+ }
+ $expanded_value = self::arrayify($expanded_value);
+ foreach($expanded_value as $item) {
+ if(self::_isValue($item) || self::_isList($item)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; "@reverse" value must not be a ' +
+ '@value or an @list.', 'jsonld.SyntaxError',
+ 'invalid reverse property value',
+ array('value' => $expanded_value));
+ }
+ self::addValue(
+ $reverse_map, $expanded_property, $item,
+ array('propertyIsArray' => true));
+ }
+ continue;
+ }
+
+ // add value for property
+ // use an array except for certain keywords
+ $use_array = (!in_array(
+ $expanded_property, array(
+ '@index', '@id', '@type', '@value', '@language')));
+ self::addValue(
+ $rval, $expanded_property, $expanded_value,
+ array('propertyIsArray' => $use_array));
+ }
+
+ // get property count on expanded output
+ $keys = array_keys((array)$rval);
+ $count = count($keys);
+
+ // @value must only have @language or @type
+ if(property_exists($rval, '@value')) {
+ // @value must only have @language or @type
+ if(property_exists($rval, '@type') &&
+ property_exists($rval, '@language')) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; an element containing "@value" may not ' .
+ 'contain both "@type" and "@language".',
+ 'jsonld.SyntaxError', 'invalid value object',
+ array('element' => $rval));
+ }
+ $valid_count = $count - 1;
+ if(property_exists($rval, '@type')) {
+ $valid_count -= 1;
+ }
+ if(property_exists($rval, '@index')) {
+ $valid_count -= 1;
+ }
+ if(property_exists($rval, '@language')) {
+ $valid_count -= 1;
+ }
+ if($valid_count !== 0) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; an element containing "@value" may only ' .
+ 'have an "@index" property and at most one other property ' .
+ 'which can be "@type" or "@language".',
+ 'jsonld.SyntaxError', 'invalid value object',
+ array('element' => $rval));
+ }
+ // drop null @values
+ if($rval->{'@value'} === null) {
+ $rval = null;
+ } else if(property_exists($rval, '@language') &&
+ !is_string($rval->{'@value'})) {
+ // if @language is present, @value must be a string
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; only strings may be language-tagged.',
+ 'jsonld.SyntaxError', 'invalid language-tagged value',
+ array('element' => $rval));
+ } else if(property_exists($rval, '@type') &&
+ (!self::_isAbsoluteIri($rval->{'@type'}) ||
+ strpos($rval->{'@type'}, '_:') === 0)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; an element containing "@value" ' .
+ 'and "@type" must have an absolute IRI for the value ' .
+ 'of "@type".', 'jsonld.SyntaxError', 'invalid typed value',
+ array('element' => $rval));
+ }
+ } else if(property_exists($rval, '@type') && !is_array($rval->{'@type'})) {
+ // convert @type to an array
+ $rval->{'@type'} = array($rval->{'@type'});
+ } else if(property_exists($rval, '@set') ||
+ property_exists($rval, '@list')) {
+ // handle @set and @list
+ if($count > 1 && !($count === 2 && property_exists($rval, '@index'))) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; if an element has the property "@set" ' .
+ 'or "@list", then it can have at most one other property that is ' .
+ '"@index".', 'jsonld.SyntaxError', 'invalid set or list object',
+ array('element' => $rval));
+ }
+ // optimize away @set
+ if(property_exists($rval, '@set')) {
+ $rval = $rval->{'@set'};
+ $keys = array_keys((array)$rval);
+ $count = count($keys);
+ }
+ } else if($count === 1 && property_exists($rval, '@language')) {
+ // drop objects with only @language
+ $rval = null;
+ }
+
+ // drop certain top-level objects that do not occur in lists
+ if(is_object($rval) &&
+ !$options['keepFreeFloatingNodes'] && !$inside_list &&
+ ($active_property === null || $expanded_active_property === '@graph')) {
+ // drop empty object or top-level @value/@list, or object with only @id
+ if($count === 0 || property_exists($rval, '@value') ||
+ property_exists($rval, '@list') ||
+ ($count === 1 && property_exists($rval, '@id'))) {
+ $rval = null;
+ }
+ }
+
+ return $rval;
+ }
+
+ /**
+ * Performs JSON-LD flattening.
+ *
+ * @param array $input the expanded JSON-LD to flatten.
+ *
+ * @return array the flattened output.
+ */
+ protected function _flatten($input) {
+ // produce a map of all subjects and name each bnode
+ $namer = new UniqueNamer('_:b');
+ $graphs = (object)array('@default' => new stdClass());
+ $this->_createNodeMap($input, $graphs, '@default', $namer);
+
+ // add all non-default graphs to default graph
+ $default_graph = $graphs->{'@default'};
+ $graph_names = array_keys((array)$graphs);
+ foreach($graph_names as $graph_name) {
+ if($graph_name === '@default') {
+ continue;
+ }
+ $node_map = $graphs->{$graph_name};
+ if(!property_exists($default_graph, $graph_name)) {
+ $default_graph->{$graph_name} = (object)array(
+ '@id' => $graph_name, '@graph' => array());
+ }
+ $subject = $default_graph->{$graph_name};
+ if(!property_exists($subject, '@graph')) {
+ $subject->{'@graph'} = array();
+ }
+ $ids = array_keys((array)$node_map);
+ sort($ids);
+ foreach($ids as $id) {
+ $node = $node_map->{$id};
+ // only add full subjects
+ if(!self::_isSubjectReference($node)) {
+ $subject->{'@graph'}[] = $node;
+ }
+ }
+ }
+
+ // produce flattened output
+ $flattened = array();
+ $keys = array_keys((array)$default_graph);
+ sort($keys);
+ foreach($keys as $key) {
+ $node = $default_graph->{$key};
+ // only add full subjects to top-level
+ if(!self::_isSubjectReference($node)) {
+ $flattened[] = $node;
+ }
+ }
+ return $flattened;
+ }
+
+ /**
+ * Performs JSON-LD framing.
+ *
+ * @param array $input the expanded JSON-LD to frame.
+ * @param array $frame the expanded JSON-LD frame to use.
+ * @param assoc $options the framing options.
+ *
+ * @return array the framed output.
+ */
+ protected function _frame($input, $frame, $options) {
+ // create framing state
+ $state = (object)array(
+ 'options' => $options,
+ 'graphs' => (object)array(
+ '@default' => new stdClass(),
+ '@merged' => new stdClass()),
+ 'subjectStack' => array(),
+ 'link' => new stdClass());
+
+ // produce a map of all graphs and name each bnode
+ // FIXME: currently uses subjects from @merged graph only
+ $namer = new UniqueNamer('_:b');
+ $this->_createNodeMap($input, $state->graphs, '@merged', $namer);
+ $state->subjects = $state->graphs->{'@merged'};
+
+ // frame the subjects
+ $framed = new ArrayObject();
+ $keys = array_keys((array)$state->subjects);
+ sort($keys);
+ $this->_matchFrame($state, $keys, $frame, $framed, null);
+ return (array)$framed;
+ }
+
+ /**
+ * Performs normalization on the given RDF dataset.
+ *
+ * @param stdClass $dataset the RDF dataset to normalize.
+ * @param assoc $options the normalization options.
+ *
+ * @return mixed the normalized output.
+ */
+ protected function _normalize($dataset, $options) {
+ // create quads and map bnodes to their associated quads
+ $quads = array();
+ $bnodes = new stdClass();
+ foreach($dataset as $graph_name => $triples) {
+ if($graph_name === '@default') {
+ $graph_name = null;
+ }
+ foreach($triples as $triple) {
+ $quad = $triple;
+ if($graph_name !== null) {
+ if(strpos($graph_name, '_:') === 0) {
+ $quad->name = (object)array(
+ 'type' => 'blank node', 'value' => $graph_name);
+ } else {
+ $quad->name = (object)array(
+ 'type' => 'IRI', 'value' => $graph_name);
+ }
+ }
+ $quads[] = $quad;
+
+ foreach(array('subject', 'object', 'name') as $attr) {
+ if(property_exists($quad, $attr) &&
+ $quad->{$attr}->type === 'blank node') {
+ $id = $quad->{$attr}->value;
+ if(property_exists($bnodes, $id)) {
+ $bnodes->{$id}->quads[] = $quad;
+ } else {
+ $bnodes->{$id} = (object)array('quads' => array($quad));
+ }
+ }
+ }
+ }
+ }
+
+ // mapping complete, start canonical naming
+ $namer = new UniqueNamer('_:c14n');
+
+ // continue to hash bnode quads while bnodes are assigned names
+ $unnamed = null;
+ $nextUnnamed = array_keys((array)$bnodes);
+ $duplicates = null;
+ do {
+ $unnamed = $nextUnnamed;
+ $nextUnnamed = array();
+ $duplicates = new stdClass();
+ $unique = new stdClass();
+ foreach($unnamed as $bnode) {
+ // hash quads for each unnamed bnode
+ $hash = $this->_hashQuads($bnode, $bnodes, $namer);
+
+ // store hash as unique or a duplicate
+ if(property_exists($duplicates, $hash)) {
+ $duplicates->{$hash}[] = $bnode;
+ $nextUnnamed[] = $bnode;
+ } else if(property_exists($unique, $hash)) {
+ $duplicates->{$hash} = array($unique->{$hash}, $bnode);
+ $nextUnnamed[] = $unique->{$hash};
+ $nextUnnamed[] = $bnode;
+ unset($unique->{$hash});
+ } else {
+ $unique->{$hash} = $bnode;
+ }
+ }
+
+ // name unique bnodes in sorted hash order
+ $hashes = array_keys((array)$unique);
+ sort($hashes);
+ foreach($hashes as $hash) {
+ $namer->getName($unique->{$hash});
+ }
+ }
+ while(count($unnamed) > count($nextUnnamed));
+
+ // enumerate duplicate hash groups in sorted order
+ $hashes = array_keys((array)$duplicates);
+ sort($hashes);
+ foreach($hashes as $hash) {
+ // process group
+ $group = $duplicates->{$hash};
+ $results = array();
+ foreach($group as $bnode) {
+ // skip already-named bnodes
+ if($namer->isNamed($bnode)) {
+ continue;
+ }
+
+ // hash bnode paths
+ $path_namer = new UniqueNamer('_:b');
+ $path_namer->getName($bnode);
+ $results[] = $this->_hashPaths($bnode, $bnodes, $namer, $path_namer);
+ }
+
+ // name bnodes in hash order
+ usort($results, function($a, $b) {
+ $a = $a->hash;
+ $b = $b->hash;
+ return ($a < $b) ? -1 : (($a > $b) ? 1 : 0);
+ });
+ foreach($results as $result) {
+ // name all bnodes in path namer in key-entry order
+ foreach($result->pathNamer->order as $bnode) {
+ $namer->getName($bnode);
+ }
+ }
+ }
+
+ // create normalized array
+ $normalized = array();
+
+ /* Note: At this point all bnodes in the set of RDF quads have been
+ assigned canonical names, which have been stored in the 'namer' object.
+ Here each quad is updated by assigning each of its bnodes its new name
+ via the 'namer' object. */
+
+ // update bnode names in each quad and serialize
+ foreach($quads as $quad) {
+ foreach(array('subject', 'object', 'name') as $attr) {
+ if(property_exists($quad, $attr) &&
+ $quad->{$attr}->type === 'blank node' &&
+ strpos($quad->{$attr}->value, '_:c14n') !== 0) {
+ $quad->{$attr}->value = $namer->getName($quad->{$attr}->value);
+ }
+ }
+ $normalized[] = $this->toNQuad($quad, property_exists($quad, 'name') ?
+ $quad->name->value : null);
+ }
+
+ // sort normalized output
+ sort($normalized);
+
+ // handle output format
+ if(isset($options['format']) && $options['format']) {
+ if($options['format'] === 'application/nquads') {
+ return implode($normalized);
+ }
+ throw new JsonLdException(
+ 'Unknown output format.',
+ 'jsonld.UnknownFormat', null, array('format' => $options['format']));
+ }
+
+ // return RDF dataset
+ return $this->parseNQuads(implode($normalized));
+ }
+
+ /**
+ * Converts an RDF dataset to JSON-LD.
+ *
+ * @param stdClass $dataset the RDF dataset.
+ * @param assoc $options the RDF serialization options.
+ *
+ * @return array the JSON-LD output.
+ */
+ protected function _fromRDF($dataset, $options) {
+ $default_graph = new stdClass();
+ $graph_map = (object)array('@default' => $default_graph);
+ $referenced_once = (object)array();
+
+ foreach($dataset as $name => $graph) {
+ if(!property_exists($graph_map, $name)) {
+ $graph_map->{$name} = new stdClass();
+ }
+ if($name !== '@default' && !property_exists($default_graph, $name)) {
+ $default_graph->{$name} = (object)array('@id' => $name);
+ }
+ $node_map = $graph_map->{$name};
+ foreach($graph as $triple) {
+ // get subject, predicate, object
+ $s = $triple->subject->value;
+ $p = $triple->predicate->value;
+ $o = $triple->object;
+
+ if(!property_exists($node_map, $s)) {
+ $node_map->{$s} = (object)array('@id' => $s);
+ }
+ $node = $node_map->{$s};
+
+ $object_is_id = ($o->type === 'IRI' || $o->type === 'blank node');
+ if($object_is_id && !property_exists($node_map, $o->value)) {
+ $node_map->{$o->value} = (object)array('@id' => $o->value);
+ }
+
+ if($p === self::RDF_TYPE && !$options['useRdfType'] && $object_is_id) {
+ self::addValue(
+ $node, '@type', $o->value, array('propertyIsArray' => true));
+ continue;
+ }
+
+ $value = self::_RDFToObject($o, $options['useNativeTypes']);
+ self::addValue($node, $p, $value, array('propertyIsArray' => true));
+
+ // object may be an RDF list/partial list node but we can't know
+ // easily until all triples are read
+ if($object_is_id) {
+ if($o->value === self::RDF_NIL) {
+ $object = $node_map->{$o->value};
+ if(!property_exists($object, 'usages')) {
+ $object->usages = array();
+ }
+ $object->usages[] = (object)array(
+ 'node' => $node,
+ 'property' => $p,
+ 'value' => $value);
+ } else if(property_exists($referenced_once, $o->value)) {
+ // object referenced more than once
+ $referenced_once->{$o->value} = false;
+ } else {
+ // track single reference
+ $referenced_once->{$o->value} = (object)array(
+ 'node' => $node,
+ 'property' => $p,
+ 'value' => $value);
+ }
+ }
+ }
+ }
+
+ // convert linked lists to @list arrays
+ foreach($graph_map as $name => $graph_object) {
+ // no @lists to be converted, continue
+ if(!property_exists($graph_object, self::RDF_NIL)) {
+ continue;
+ }
+
+ // iterate backwards through each RDF list
+ $nil = $graph_object->{self::RDF_NIL};
+ foreach($nil->usages as $usage) {
+ $node = $usage->node;
+ $property = $usage->property;
+ $head = $usage->value;
+ $list = array();
+ $list_nodes = array();
+
+ // ensure node is a well-formed list node; it must:
+ // 1. Be referenced only once.
+ // 2. Have an array for rdf:first that has 1 item.
+ // 3. Have an array for rdf:rest that has 1 item.
+ // 4. Have no keys other than: @id, rdf:first, rdf:rest, and,
+ // optionally, @type where the value is rdf:List.
+ $node_key_count = count(array_keys((array)$node));
+ while($property === self::RDF_REST &&
+ property_exists($referenced_once, $node->{'@id'}) &&
+ is_object($referenced_once->{$node->{'@id'}}) &&
+ property_exists($node, self::RDF_FIRST) &&
+ property_exists($node, self::RDF_REST) &&
+ is_array($node->{self::RDF_FIRST}) &&
+ is_array($node->{self::RDF_REST}) &&
+ count($node->{self::RDF_FIRST}) === 1 &&
+ count($node->{self::RDF_REST}) === 1 &&
+ ($node_key_count === 3 || ($node_key_count === 4 &&
+ property_exists($node, '@type') && is_array($node->{'@type'}) &&
+ count($node->{'@type'}) === 1 &&
+ $node->{'@type'}[0] === self::RDF_LIST))) {
+ $list[] = $node->{self::RDF_FIRST}[0];
+ $list_nodes[] = $node->{'@id'};
+
+ // get next node, moving backwards through list
+ $usage = $referenced_once->{$node->{'@id'}};
+ $node = $usage->node;
+ $property = $usage->property;
+ $head = $usage->value;
+ $node_key_count = count(array_keys((array)$node));
+
+ // if node is not a blank node, then list head found
+ if(strpos($node->{'@id'}, '_:') !== 0) {
+ break;
+ }
+ }
+
+ // list is nested in another list
+ if($property === self::RDF_FIRST) {
+ // empty list
+ if($node->{'@id'} === self::RDF_NIL) {
+ // can't convert rdf:nil to a @list object because it would
+ // result in a list of lists which isn't supported
+ continue;
+ }
+
+ // preserve list head
+ $head = $graph_object->{$head->{'@id'}}->{self::RDF_REST}[0];
+ array_pop($list);
+ array_pop($list_nodes);
+ }
+
+ // transform list into @list object
+ unset($head->{'@id'});
+ $head->{'@list'} = array_reverse($list);
+ foreach($list_nodes as $list_node) {
+ unset($graph_object->{$list_node});
+ }
+ }
+
+ unset($nil->usages);
+ }
+
+ $result = array();
+ $subjects = array_keys((array)$default_graph);
+ sort($subjects);
+ foreach($subjects as $subject) {
+ $node = $default_graph->{$subject};
+ if(property_exists($graph_map, $subject)) {
+ $node->{'@graph'} = array();
+ $graph_object = $graph_map->{$subject};
+ $subjects_ = array_keys((array)$graph_object);
+ sort($subjects_);
+ foreach($subjects_ as $subject_) {
+ $node_ = $graph_object->{$subject_};
+ // only add full subjects to top-level
+ if(!self::_isSubjectReference($node_)) {
+ $node->{'@graph'}[] = $node_;
+ }
+ }
+ }
+ // only add full subjects to top-level
+ if(!self::_isSubjectReference($node)) {
+ $result[] = $node;
+ }
+ }
+
+ return $result;
+ }
+
+ /**
+ * Processes a local context and returns a new active context.
+ *
+ * @param stdClass $active_ctx the current active context.
+ * @param mixed $local_ctx the local context to process.
+ * @param assoc $options the context processing options.
+ *
+ * @return stdClass the new active context.
+ */
+ protected function _processContext($active_ctx, $local_ctx, $options) {
+ global $jsonld_cache;
+
+ // normalize local context to an array
+ if(is_object($local_ctx) && property_exists($local_ctx, '@context') &&
+ is_array($local_ctx->{'@context'})) {
+ $local_ctx = $local_ctx->{'@context'};
+ }
+ $ctxs = self::arrayify($local_ctx);
+
+ // no contexts in array, clone existing context
+ if(count($ctxs) === 0) {
+ return self::_cloneActiveContext($active_ctx);
+ }
+
+ // process each context in order, update active context
+ // on each iteration to ensure proper caching
+ $rval = $active_ctx;
+ foreach($ctxs as $ctx) {
+ // reset to initial context
+ if($ctx === null) {
+ $rval = $active_ctx = $this->_getInitialContext($options);
+ continue;
+ }
+
+ // dereference @context key if present
+ if(is_object($ctx) && property_exists($ctx, '@context')) {
+ $ctx = $ctx->{'@context'};
+ }
+
+ // context must be an object by now, all URLs retrieved before this call
+ if(!is_object($ctx)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; @context must be an object.',
+ 'jsonld.SyntaxError', 'invalid local context',
+ array('context' => $ctx));
+ }
+
+ // get context from cache if available
+ if(property_exists($jsonld_cache, 'activeCtx')) {
+ $cached = $jsonld_cache->activeCtx->get($active_ctx, $ctx);
+ if($cached) {
+ $rval = $active_ctx = $cached;
+ $must_clone = true;
+ continue;
+ }
+ }
+
+ // update active context and clone new one before updating
+ $active_ctx = $rval;
+ $rval = self::_cloneActiveContext($rval);
+
+ // define context mappings for keys in local context
+ $defined = new stdClass();
+
+ // handle @base
+ if(property_exists($ctx, '@base')) {
+ $base = $ctx->{'@base'};
+ if($base === null) {
+ $base = null;
+ } else if(!is_string($base)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; the value of "@base" in a ' .
+ '@context must be a string or null.',
+ 'jsonld.SyntaxError', 'invalid base IRI', array('context' => $ctx));
+ } else if($base !== '' && !self::_isAbsoluteIri($base)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; the value of "@base" in a ' .
+ '@context must be an absolute IRI or the empty string.',
+ 'jsonld.SyntaxError', 'invalid base IRI', array('context' => $ctx));
+ }
+ if($base !== null) {
+ $base = jsonld_parse_url($base);
+ }
+ $rval->{'@base'} = $base;
+ $defined->{'@base'} = true;
+ }
+
+ // handle @vocab
+ if(property_exists($ctx, '@vocab')) {
+ $value = $ctx->{'@vocab'};
+ if($value === null) {
+ unset($rval->{'@vocab'});
+ } else if(!is_string($value)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; the value of "@vocab" in a ' .
+ '@context must be a string or null.',
+ 'jsonld.SyntaxError', 'invalid vocab mapping',
+ array('context' => $ctx));
+ } else if(!self::_isAbsoluteIri($value)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; the value of "@vocab" in a ' .
+ '@context must be an absolute IRI.',
+ 'jsonld.SyntaxError', 'invalid vocab mapping',
+ array('context' => $ctx));
+ } else {
+ $rval->{'@vocab'} = $value;
+ }
+ $defined->{'@vocab'} = true;
+ }
+
+ // handle @language
+ if(property_exists($ctx, '@language')) {
+ $value = $ctx->{'@language'};
+ if($value === null) {
+ unset($rval->{'@language'});
+ } else if(!is_string($value)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; the value of "@language" in a ' .
+ '@context must be a string or null.',
+ 'jsonld.SyntaxError', 'invalid default language',
+ array('context' => $ctx));
+ } else {
+ $rval->{'@language'} = strtolower($value);
+ }
+ $defined->{'@language'} = true;
+ }
+
+ // process all other keys
+ foreach($ctx as $k => $v) {
+ $this->_createTermDefinition($rval, $ctx, $k, $defined);
+ }
+
+ // cache result
+ if(property_exists($jsonld_cache, 'activeCtx')) {
+ $jsonld_cache->activeCtx->set($active_ctx, $ctx, $rval);
+ }
+ }
+
+ return $rval;
+ }
+
+ /**
+ * Expands a language map.
+ *
+ * @param stdClass $language_map the language map to expand.
+ *
+ * @return array the expanded language map.
+ */
+ protected function _expandLanguageMap($language_map) {
+ $rval = array();
+ $keys = array_keys((array)$language_map);
+ sort($keys);
+ foreach($keys as $key) {
+ $values = $language_map->{$key};
+ $values = self::arrayify($values);
+ foreach($values as $item) {
+ if($item === null) {
+ continue;
+ }
+ if(!is_string($item)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; language map values must be strings.',
+ 'jsonld.SyntaxError', 'invalid language map value',
+ array('languageMap', $language_map));
+ }
+ $rval[] = (object)array(
+ '@value' => $item,
+ '@language' => strtolower($key));
+ }
+ }
+ return $rval;
+ }
+
+ /**
+ * Labels the blank nodes in the given value using the given UniqueNamer.
+ *
+ * @param UniqueNamer $namer the UniqueNamer to use.
+ * @param mixed $element the element with blank nodes to rename.
+ *
+ * @return mixed the element.
+ */
+ public function _labelBlankNodes($namer, $element) {
+ if(is_array($element)) {
+ $length = count($element);
+ for($i = 0; $i < $length; ++$i) {
+ $element[$i] = $this->_labelBlankNodes($namer, $element[$i]);
+ }
+ } else if(self::_isList($element)) {
+ $element->{'@list'} = $this->_labelBlankNodes(
+ $namer, $element->{'@list'});
+ } else if(is_object($element)) {
+ // rename blank node
+ if(self::_isBlankNode($element)) {
+ $name = null;
+ if(property_exists($element, '@id')) {
+ $name = $element->{'@id'};
+ }
+ $element->{'@id'} = $namer->getName($name);
+ }
+
+ // recursively apply to all keys
+ $keys = array_keys((array)$element);
+ sort($keys);
+ foreach($keys as $key) {
+ if($key !== '@id') {
+ $element->{$key} = $this->_labelBlankNodes($namer, $element->{$key});
+ }
+ }
+ }
+
+ return $element;
+ }
+
+ /**
+ * Expands the given value by using the coercion and keyword rules in the
+ * given context.
+ *
+ * @param stdClass $active_ctx the active context to use.
+ * @param string $active_property the property the value is associated with.
+ * @param mixed $value the value to expand.
+ *
+ * @return mixed the expanded value.
+ */
+ protected function _expandValue($active_ctx, $active_property, $value) {
+ // nothing to expand
+ if($value === null) {
+ return null;
+ }
+
+ // special-case expand @id and @type (skips '@id' expansion)
+ $expanded_property = $this->_expandIri(
+ $active_ctx, $active_property, array('vocab' => true));
+ if($expanded_property === '@id') {
+ return $this->_expandIri($active_ctx, $value, array('base' => true));
+ } else if($expanded_property === '@type') {
+ return $this->_expandIri(
+ $active_ctx, $value, array('vocab' => true, 'base' => true));
+ }
+
+ // get type definition from context
+ $type = self::getContextValue($active_ctx, $active_property, '@type');
+
+ // do @id expansion (automatic for @graph)
+ if($type === '@id' || ($expanded_property === '@graph' &&
+ is_string($value))) {
+ return (object)array('@id' => $this->_expandIri(
+ $active_ctx, $value, array('base' => true)));
+ }
+ // do @id expansion w/vocab
+ if($type === '@vocab') {
+ return (object)array('@id' => $this->_expandIri(
+ $active_ctx, $value, array('vocab' => true, 'base' => true)));
+ }
+
+ // do not expand keyword values
+ if(self::_isKeyword($expanded_property)) {
+ return $value;
+ }
+
+ $rval = new stdClass();
+
+ // other type
+ if($type !== null) {
+ $rval->{'@type'} = $type;
+ } else if(is_string($value)) {
+ // check for language tagging for strings
+ $language = self::getContextValue(
+ $active_ctx, $active_property, '@language');
+ if($language !== null) {
+ $rval->{'@language'} = $language;
+ }
+ }
+ $rval->{'@value'} = $value;
+
+ return $rval;
+ }
+
+ /**
+ * Creates an array of RDF triples for the given graph.
+ *
+ * @param stdClass $graph the graph to create RDF triples for.
+ * @param UniqueNamer $namer for assigning bnode names.
+ * @param assoc $options the RDF serialization options.
+ *
+ * @return array the array of RDF triples for the given graph.
+ */
+ protected function _graphToRDF($graph, $namer, $options) {
+ $rval = array();
+
+ $ids = array_keys((array)$graph);
+ sort($ids);
+ foreach($ids as $id) {
+ $node = $graph->{$id};
+ if($id === '"') {
+ $id = '';
+ }
+ $properties = array_keys((array)$node);
+ sort($properties);
+ foreach($properties as $property) {
+ $items = $node->{$property};
+ if($property === '@type') {
+ $property = self::RDF_TYPE;
+ } else if(self::_isKeyword($property)) {
+ continue;
+ }
+
+ foreach($items as $item) {
+ // skip relative IRI subjects and predicates
+ if(!(self::_isAbsoluteIri($id) && self::_isAbsoluteIri($property))) {
+ continue;
+ }
+
+ // RDF subject
+ $subject = new stdClass();
+ $subject->type = (strpos($id, '_:') === 0) ? 'blank node' : 'IRI';
+ $subject->value = $id;
+
+ // RDF predicate
+ $predicate = new stdClass();
+ $predicate->type = (strpos($property, '_:') === 0 ?
+ 'blank node' : 'IRI');
+ $predicate->value = $property;
+
+ // skip bnode predicates unless producing generalized RDF
+ if($predicate->type === 'blank node' &&
+ !$options['produceGeneralizedRdf']) {
+ continue;
+ }
+
+ if(self::_isList($item)) {
+ // convert @list to triples
+ $this->_listToRDF(
+ $item->{'@list'}, $namer, $subject, $predicate, $rval);
+ } else {
+ // convert value or node object to triple
+ $object = $this->_objectToRDF($item);
+ // skip null objects (they are relative IRIs)
+ if($object) {
+ $rval[] = (object)array(
+ 'subject' => $subject,
+ 'predicate' => $predicate,
+ 'object' => $object);
+ }
+ }
+ }
+ }
+ }
+
+ return $rval;
+ }
+
+ /**
+ * Converts a @list value into linked list of blank node RDF triples
+ * (an RDF collection).
+ *
+ * @param array $list the @list value.
+ * @param UniqueNamer $namer for assigning blank node names.
+ * @param stdClass $subject the subject for the head of the list.
+ * @param stdClass $predicate the predicate for the head of the list.
+ * @param &array $triples the array of triples to append to.
+ */
+ protected function _listToRDF(
+ $list, $namer, $subject, $predicate, &$triples) {
+ $first = (object)array('type' => 'IRI', 'value' => self::RDF_FIRST);
+ $rest = (object)array('type' => 'IRI', 'value' => self::RDF_REST);
+ $nil = (object)array('type' => 'IRI', 'value' => self::RDF_NIL);
+
+ foreach($list as $item) {
+ $blank_node = (object)array(
+ 'type' => 'blank node', 'value' => $namer->getName());
+ $triples[] = (object)array(
+ 'subject' => $subject,
+ 'predicate' => $predicate,
+ 'object' => $blank_node);
+
+ $subject = $blank_node;
+ $predicate = $first;
+ $object = $this->_objectToRDF($item);
+ // skip null objects (they are relative IRIs)
+ if($object) {
+ $triples[] = (object)array(
+ 'subject' => $subject,
+ 'predicate' => $predicate,
+ 'object' => $object);
+ }
+
+ $predicate = $rest;
+ }
+
+ $triples[] = (object)array(
+ 'subject' => $subject, 'predicate' => $predicate, 'object' => $nil);
+ }
+
+ /**
+ * Converts a JSON-LD value object to an RDF literal or a JSON-LD string or
+ * node object to an RDF resource.
+ *
+ * @param mixed $item the JSON-LD value or node object.
+ *
+ * @return stdClass the RDF literal or RDF resource.
+ */
+ protected function _objectToRDF($item) {
+ $object = new stdClass();
+
+ if(self::_isValue($item)) {
+ $object->type = 'literal';
+ $value = $item->{'@value'};
+ $datatype = property_exists($item, '@type') ? $item->{'@type'} : null;
+
+ // convert to XSD datatypes as appropriate
+ if(is_bool($value)) {
+ $object->value = ($value ? 'true' : 'false');
+ $object->datatype = $datatype ? $datatype : self::XSD_BOOLEAN;
+ } else if(is_double($value) || $datatype == self::XSD_DOUBLE) {
+ // canonical double representation
+ $object->value = preg_replace(
+ '/(\d)0*E\+?/', '$1E', sprintf('%1.15E', $value));
+ $object->datatype = $datatype ? $datatype : self::XSD_DOUBLE;
+ } else if(is_integer($value)) {
+ $object->value = strval($value);
+ $object->datatype = $datatype ? $datatype : self::XSD_INTEGER;
+ } else if(property_exists($item, '@language')) {
+ $object->value = $value;
+ $object->datatype = $datatype ? $datatype : self::RDF_LANGSTRING;
+ $object->language = $item->{'@language'};
+ } else {
+ $object->value = $value;
+ $object->datatype = $datatype ? $datatype : self::XSD_STRING;
+ }
+ } else {
+ // convert string/node object to RDF
+ $id = is_object($item) ? $item->{'@id'} : $item;
+ $object->type = (strpos($id, '_:') === 0) ? 'blank node' : 'IRI';
+ $object->value = $id;
+ }
+
+ // skip relative IRIs
+ if($object->type === 'IRI' && !self::_isAbsoluteIri($object->value)) {
+ return null;
+ }
+
+ return $object;
+ }
+
+ /**
+ * Converts an RDF triple object to a JSON-LD object.
+ *
+ * @param stdClass $o the RDF triple object to convert.
+ * @param bool $use_native_types true to output native types, false not to.
+ *
+ * @return stdClass the JSON-LD object.
+ */
+ protected function _RDFToObject($o, $use_native_types) {
+ // convert IRI/blank node object to JSON-LD
+ if($o->type === 'IRI' || $o->type === 'blank node') {
+ return (object)array('@id' => $o->value);
+ }
+
+ // convert literal object to JSON-LD
+ $rval = (object)array('@value' => $o->value);
+
+ if(property_exists($o, 'language')) {
+ // add language
+ $rval->{'@language'} = $o->language;
+ } else {
+ // add datatype
+ $type = $o->datatype;
+ // use native types for certain xsd types
+ if($use_native_types) {
+ if($type === self::XSD_BOOLEAN) {
+ if($rval->{'@value'} === 'true') {
+ $rval->{'@value'} = true;
+ } else if($rval->{'@value'} === 'false') {
+ $rval->{'@value'} = false;
+ }
+ } else if(is_numeric($rval->{'@value'})) {
+ if($type === self::XSD_INTEGER) {
+ $i = intval($rval->{'@value'});
+ if(strval($i) === $rval->{'@value'}) {
+ $rval->{'@value'} = $i;
+ }
+ } else if($type === self::XSD_DOUBLE) {
+ $rval->{'@value'} = doubleval($rval->{'@value'});
+ }
+ }
+ // do not add native type
+ if(!in_array($type, array(
+ self::XSD_BOOLEAN, self::XSD_INTEGER, self::XSD_DOUBLE,
+ self::XSD_STRING))) {
+ $rval->{'@type'} = $type;
+ }
+ } else if($type !== self::XSD_STRING) {
+ $rval->{'@type'} = $type;
+ }
+ }
+
+ return $rval;
+ }
+
+ /**
+ * Recursively flattens the subjects in the given JSON-LD expanded input
+ * into a node map.
+ *
+ * @param mixed $input the JSON-LD expanded input.
+ * @param stdClass $graphs a map of graph name to subject map.
+ * @param string $graph the name of the current graph.
+ * @param UniqueNamer $namer the blank node namer.
+ * @param mixed $name the name assigned to the current input if it is a bnode.
+ * @param mixed $list the list to append to, null for none.
+ */
+ protected function _createNodeMap(
+ $input, $graphs, $graph, $namer, $name=null, $list=null) {
+ // recurse through array
+ if(is_array($input)) {
+ foreach($input as $e) {
+ $this->_createNodeMap($e, $graphs, $graph, $namer, null, $list);
+ }
+ return;
+ }
+
+ // add non-object to list
+ if(!is_object($input)) {
+ if($list !== null) {
+ $list[] = $input;
+ }
+ return;
+ }
+
+ // add values to list
+ if(self::_isValue($input)) {
+ if(property_exists($input, '@type')) {
+ $type = $input->{'@type'};
+ // rename @type blank node
+ if(strpos($type, '_:') === 0) {
+ $type = $input->{'@type'} = $namer->getName($type);
+ }
+ }
+ if($list !== null) {
+ $list[] = $input;
+ }
+ return;
+ }
+
+ // Note: At this point, input must be a subject.
+
+ // spec requires @type to be named first, so assign names early
+ if(property_exists($input, '@type')) {
+ foreach($input->{'@type'} as $type) {
+ if(strpos($type, '_:') === 0) {
+ $namer->getName($type);
+ }
+ }
+ }
+
+ // get name for subject
+ if($name === null) {
+ if(property_exists($input, '@id')) {
+ $name = $input->{'@id'};
+ }
+ if(self::_isBlankNode($input)) {
+ $name = $namer->getName($name);
+ }
+ }
+
+ // add subject reference to list
+ if($list !== null) {
+ $list[] = (object)array('@id' => $name);
+ }
+
+ // create new subject or merge into existing one
+ if(!property_exists($graphs, $graph)) {
+ $graphs->{$graph} = new stdClass();
+ }
+ $subjects = $graphs->{$graph};
+ if(!property_exists($subjects, $name)) {
+ if($name === '') {
+ $subjects->{'"'} = new stdClass();
+ } else {
+ $subjects->{$name} = new stdClass();
+ }
+ }
+ if($name === '') {
+ $subject = $subjects->{'"'};
+ } else {
+ $subject = $subjects->{$name};
+ }
+ $subject->{'@id'} = $name;
+ $properties = array_keys((array)$input);
+ sort($properties);
+ foreach($properties as $property) {
+ // skip @id
+ if($property === '@id') {
+ continue;
+ }
+
+ // handle reverse properties
+ if($property === '@reverse') {
+ $referenced_node = (object)array('@id' => $name);
+ $reverse_map = $input->{'@reverse'};
+ foreach($reverse_map as $reverse_property => $items) {
+ foreach($items as $item) {
+ $item_name = null;
+ if(property_exists($item, '@id')) {
+ $item_name = $item->{'@id'};
+ }
+ if(self::_isBlankNode($item)) {
+ $item_name = $namer->getName($item_name);
+ }
+ $this->_createNodeMap($item, $graphs, $graph, $namer, $item_name);
+ if($item_name === '') {
+ $item_name = '"';
+ }
+ self::addValue(
+ $subjects->{$item_name}, $reverse_property, $referenced_node,
+ array('propertyIsArray' => true, 'allowDuplicate' => false));
+ }
+ }
+ continue;
+ }
+
+ // recurse into graph
+ if($property === '@graph') {
+ // add graph subjects map entry
+ if(!property_exists($graphs, $name)) {
+ // FIXME: temporary hack to avoid empty property bug
+ if(!$name) {
+ $name = '"';
+ }
+ $graphs->{$name} = new stdClass();
+ }
+ $g = ($graph === '@merged') ? $graph : $name;
+ $this->_createNodeMap(
+ $input->{$property}, $graphs, $g, $namer, null, null);
+ continue;
+ }
+
+ // copy non-@type keywords
+ if($property !== '@type' && self::_isKeyword($property)) {
+ if($property === '@index' && property_exists($subject, '@index') &&
+ ($input->{'@index'} !== $subject->{'@index'} ||
+ $input->{'@index'}->{'@id'} !== $subject->{'@index'}->{'@id'})) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; conflicting @index property detected.',
+ 'jsonld.SyntaxError', 'conflicting indexes',
+ array('subject' => $subject));
+ }
+ $subject->{$property} = $input->{$property};
+ continue;
+ }
+
+ // iterate over objects
+ $objects = $input->{$property};
+
+ // if property is a bnode, assign it a new id
+ if(strpos($property, '_:') === 0) {
+ $property = $namer->getName($property);
+ }
+
+ // ensure property is added for empty arrays
+ if(count($objects) === 0) {
+ self::addValue(
+ $subject, $property, array(), array('propertyIsArray' => true));
+ continue;
+ }
+ foreach($objects as $o) {
+ if($property === '@type') {
+ // rename @type blank nodes
+ $o = (strpos($o, '_:') === 0) ? $namer->getName($o) : $o;
+ }
+
+ // handle embedded subject or subject reference
+ if(self::_isSubject($o) || self::_isSubjectReference($o)) {
+ // rename blank node @id
+ $id = property_exists($o, '@id') ? $o->{'@id'} : null;
+ if(self::_isBlankNode($o)) {
+ $id = $namer->getName($id);
+ }
+
+ // add reference and recurse
+ self::addValue(
+ $subject, $property, (object)array('@id' => $id),
+ array('propertyIsArray' => true, 'allowDuplicate' => false));
+ $this->_createNodeMap($o, $graphs, $graph, $namer, $id, null);
+ } else if(self::_isList($o)) {
+ // handle @list
+ $_list = new ArrayObject();
+ $this->_createNodeMap(
+ $o->{'@list'}, $graphs, $graph, $namer, $name, $_list);
+ $o = (object)array('@list' => (array)$_list);
+ self::addValue(
+ $subject, $property, $o,
+ array('propertyIsArray' => true, 'allowDuplicate' => false));
+ } else {
+ // handle @value
+ $this->_createNodeMap($o, $graphs, $graph, $namer, $name, null);
+ self::addValue(
+ $subject, $property, $o,
+ array('propertyIsArray' => true, 'allowDuplicate' => false));
+ }
+ }
+ }
+ }
+
+ /**
+ * Frames subjects according to the given frame.
+ *
+ * @param stdClass $state the current framing state.
+ * @param array $subjects the subjects to filter.
+ * @param array $frame the frame.
+ * @param mixed $parent the parent subject or top-level array.
+ * @param mixed $property the parent property, initialized to null.
+ */
+ protected function _matchFrame(
+ $state, $subjects, $frame, $parent, $property) {
+ // validate the frame
+ $this->_validateFrame($frame);
+ $frame = $frame[0];
+
+ // get flags for current frame
+ $options = $state->options;
+ $flags = array(
+ 'embed' => $this->_getFrameFlag($frame, $options, 'embed'),
+ 'explicit' => $this->_getFrameFlag($frame, $options, 'explicit'),
+ 'requireAll' => $this->_getFrameFlag($frame, $options, 'requireAll'));
+
+ // filter out subjects that match the frame
+ $matches = $this->_filterSubjects($state, $subjects, $frame, $flags);
+
+ // add matches to output
+ foreach($matches as $id => $subject) {
+ if($flags['embed'] === '@link' && property_exists($state->link, $id)) {
+ // TODO: may want to also match an existing linked subject against
+ // the current frame ... so different frames could produce different
+ // subjects that are only shared in-memory when the frames are the same
+
+ // add existing linked subject
+ $this->_addFrameOutput($parent, $property, $state->link->{$id});
+ continue;
+ }
+
+ /* Note: In order to treat each top-level match as a compartmentalized
+ result, clear the unique embedded subjects map when the property is null,
+ which only occurs at the top-level. */
+ if($property === null) {
+ $state->uniqueEmbeds = new stdClass();
+ }
+
+ // start output for subject
+ $output = new stdClass();
+ $output->{'@id'} = $id;
+ $state->link->{$id} = $output;
+
+ // if embed is @never or if a circular reference would be created by an
+ // embed, the subject cannot be embedded, just add the reference;
+ // note that a circular reference won't occur when the embed flag is
+ // `@link` as the above check will short-circuit before reaching this point
+ if($flags['embed'] === '@never' ||
+ $this->_createsCircularReference($subject, $state->subjectStack)) {
+ $this->_addFrameOutput($parent, $property, $output);
+ continue;
+ }
+
+ // if only the last match should be embedded
+ if($flags['embed'] === '@last') {
+ // remove any existing embed
+ if(property_exists($state->uniqueEmbeds, $id)) {
+ $this->_removeEmbed($state, $id);
+ }
+ $state->uniqueEmbeds->{$id} = array(
+ 'parent' => $parent, 'property' => $property);
+ }
+
+ // push matching subject onto stack to enable circular embed checks
+ $state->subjectStack[] = $subject;
+
+ // iterate over subject properties
+ $props = array_keys((array)$subject);
+ sort($props);
+ foreach($props as $prop) {
+ // copy keywords to output
+ if(self::_isKeyword($prop)) {
+ $output->{$prop} = self::copy($subject->{$prop});
+ continue;
+ }
+
+ // explicit is on and property isn't in the frame, skip processing
+ if($flags['explicit'] && !property_exists($frame, $prop)) {
+ continue;
+ }
+
+ // add objects
+ $objects = $subject->{$prop};
+ foreach($objects as $o) {
+ // recurse into list
+ if(self::_isList($o)) {
+ // add empty list
+ $list = (object)array('@list' => array());
+ $this->_addFrameOutput($output, $prop, $list);
+
+ // add list objects
+ $src = $o->{'@list'};
+ foreach($src as $o) {
+ if(self::_isSubjectReference($o)) {
+ // recurse into subject reference
+ $subframe = (property_exists($frame, $prop) ?
+ $frame->{$prop}[0]->{'@list'} :
+ $this->_createImplicitFrame($flags));
+ $this->_matchFrame(
+ $state, array($o->{'@id'}), $subframe, $list, '@list');
+ } else {
+ // include other values automatically
+ $this->_addFrameOutput($list, '@list', self::copy($o));
+ }
+ }
+ continue;
+ }
+
+ if(self::_isSubjectReference($o)) {
+ // recurse into subject reference
+ $subframe = (property_exists($frame, $prop) ?
+ $frame->{$prop} : $this->_createImplicitFrame($flags));
+ $this->_matchFrame(
+ $state, array($o->{'@id'}), $subframe, $output, $prop);
+ } else {
+ // include other values automatically
+ $this->_addFrameOutput($output, $prop, self::copy($o));
+ }
+ }
+ }
+
+ // handle defaults
+ $props = array_keys((array)$frame);
+ sort($props);
+ foreach($props as $prop) {
+ // skip keywords
+ if(self::_isKeyword($prop)) {
+ continue;
+ }
+
+ // if omit default is off, then include default values for properties
+ // that appear in the next frame but are not in the matching subject
+ $next = $frame->{$prop}[0];
+ $omit_default_on = $this->_getFrameFlag(
+ $next, $options, 'omitDefault');
+ if(!$omit_default_on && !property_exists($output, $prop)) {
+ $preserve = '@null';
+ if(property_exists($next, '@default')) {
+ $preserve = self::copy($next->{'@default'});
+ }
+ $preserve = self::arrayify($preserve);
+ $output->{$prop} = array((object)array('@preserve' => $preserve));
+ }
+ }
+
+ // add output to parent
+ $this->_addFrameOutput($parent, $property, $output);
+
+ // pop matching subject from circular ref-checking stack
+ array_pop($state->subjectStack);
+ }
+ }
+
+ /**
+ * Creates an implicit frame when recursing through subject matches. If
+ * a frame doesn't have an explicit frame for a particular property, then
+ * a wildcard child frame will be created that uses the same flags that the
+ * parent frame used.
+ *
+ * @param assoc flags the current framing flags.
+ *
+ * @return array the implicit frame.
+ */
+ function _createImplicitFrame($flags) {
+ $frame = new stdClass();
+ foreach($flags as $key => $value) {
+ $frame->{'@' . $key} = array($flags[$key]);
+ }
+ return array($frame);
+ }
+
+ /**
+ * Checks the current subject stack to see if embedding the given subject
+ * would cause a circular reference.
+ *
+ * @param stdClass subject_to_embed the subject to embed.
+ * @param assoc subject_stack the current stack of subjects.
+ *
+ * @return bool true if a circular reference would be created, false if not.
+ */
+ function _createsCircularReference($subject_to_embed, $subject_stack) {
+ for($i = count($subject_stack) - 1; $i >= 0; --$i) {
+ if($subject_stack[$i]->{'@id'} === $subject_to_embed->{'@id'}) {
+ return true;
+ }
+ }
+ return false;
+ }
+
+ /**
+ * Gets the frame flag value for the given flag name.
+ *
+ * @param stdClass $frame the frame.
+ * @param stdClass $options the framing options.
+ * @param string $name the flag name.
+ *
+ * @return mixed $the flag value.
+ */
+ protected function _getFrameFlag($frame, $options, $name) {
+ $flag = "@$name";
+ $rval = (property_exists($frame, $flag) ?
+ $frame->{$flag}[0] : $options[$name]);
+ if($name === 'embed') {
+ // default is "@last"
+ // backwards-compatibility support for "embed" maps:
+ // true => "@last"
+ // false => "@never"
+ if($rval === true) {
+ $rval = '@last';
+ } else if($rval === false) {
+ $rval = '@never';
+ } else if($rval !== '@always' && $rval !== '@never' &&
+ $rval !== '@link') {
+ $rval = '@last';
+ }
+ }
+ return $rval;
+ }
+
+ /**
+ * Validates a JSON-LD frame, throwing an exception if the frame is invalid.
+ *
+ * @param array $frame the frame to validate.
+ */
+ protected function _validateFrame($frame) {
+ if(!is_array($frame) || count($frame) !== 1 || !is_object($frame[0])) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; a JSON-LD frame must be a single object.',
+ 'jsonld.SyntaxError', null, array('frame' => $frame));
+ }
+ }
+
+ /**
+ * Returns a map of all of the subjects that match a parsed frame.
+ *
+ * @param stdClass $state the current framing state.
+ * @param array $subjects the set of subjects to filter.
+ * @param stdClass $frame the parsed frame.
+ * @param assoc $flags the frame flags.
+ *
+ * @return stdClass all of the matched subjects.
+ */
+ protected function _filterSubjects($state, $subjects, $frame, $flags) {
+ $rval = new stdClass();
+ sort($subjects);
+ foreach($subjects as $id) {
+ $subject = $state->subjects->{$id};
+ if($this->_filterSubject($subject, $frame, $flags)) {
+ $rval->{$id} = $subject;
+ }
+ }
+ return $rval;
+ }
+
+ /**
+ * Returns true if the given subject matches the given frame.
+ *
+ * @param stdClass $subject the subject to check.
+ * @param stdClass $frame the frame to check.
+ * @param assoc $flags the frame flags.
+ *
+ * @return bool true if the subject matches, false if not.
+ */
+ protected function _filterSubject($subject, $frame, $flags) {
+ // check @type (object value means 'any' type, fall through to ducktyping)
+ if(property_exists($frame, '@type') &&
+ !(count($frame->{'@type'}) === 1 && is_object($frame->{'@type'}[0]))) {
+ $types = $frame->{'@type'};
+ foreach($types as $type) {
+ // any matching @type is a match
+ if(self::hasValue($subject, '@type', $type)) {
+ return true;
+ }
+ }
+ return false;
+ }
+
+ // check ducktype
+ $wildcard = true;
+ $matches_some = false;
+ foreach($frame as $k => $v) {
+ if(self::_isKeyword($k)) {
+ // skip non-@id and non-@type
+ if($k !== '@id' && $k !== '@type') {
+ continue;
+ }
+ $wildcard = false;
+
+ // check @id for a specific @id value
+ if($k === '@id' && is_string($v)) {
+ if(!property_exists($subject, $k) || $subject->{$k} !== $v) {
+ return false;
+ }
+ $matches_some = true;
+ continue;
+ }
+ }
+
+ $wildcard = false;
+
+ if(property_exists($subject, $k)) {
+ // $v === [] means do not match if property is present
+ if(is_array($v) && count($v) === 0) {
+ return false;
+ }
+ $matches_some = true;
+ continue;
+ }
+
+ // all properties must match to be a duck unless a @default is specified
+ $has_default = (is_array($v) && count($v) === 1 && is_object($v[0]) &&
+ property_exists($v[0], '@default'));
+ if($flags['requireAll'] && !$has_default) {
+ return false;
+ }
+ }
+
+ // return true if wildcard or subject matches some properties
+ return $wildcard || $matches_some;
+ }
+
+ /**
+ * Removes an existing embed.
+ *
+ * @param stdClass $state the current framing state.
+ * @param string $id the @id of the embed to remove.
+ */
+ protected function _removeEmbed($state, $id) {
+ // get existing embed
+ $embeds = $state->uniqueEmbeds;
+ $embed = $embeds->{$id};
+ $property = $embed['property'];
+
+ // create reference to replace embed
+ $subject = (object)array('@id' => $id);
+
+ // remove existing embed
+ if(is_array($embed->parent)) {
+ // replace subject with reference
+ foreach($embed->parent as $i => $parent) {
+ if(self::compareValues($parent, $subject)) {
+ $embed->parent[$i] = $subject;
+ break;
+ }
+ }
+ } else {
+ // replace subject with reference
+ $use_array = is_array($embed->parent->{$property});
+ self::removeValue($embed->parent, $property, $subject,
+ array('propertyIsArray' => $use_array));
+ self::addValue($embed->parent, $property, $subject,
+ array('propertyIsArray' => $use_array));
+ }
+
+ // recursively remove dependent dangling embeds
+ $removeDependents = function($id) {
+ // get embed keys as a separate array to enable deleting keys in map
+ $ids = array_keys((array)$embeds);
+ foreach($ids as $next) {
+ if(property_exists($embeds, $next) &&
+ is_object($embeds->{$next}->parent) &&
+ $embeds->{$next}->parent->{'@id'} === $id) {
+ unset($embeds->{$next});
+ $removeDependents($next);
+ }
+ }
+ };
+ $removeDependents($id);
+ }
+
+ /**
+ * Adds framing output to the given parent.
+ *
+ * @param mixed $parent the parent to add to.
+ * @param string $property the parent property.
+ * @param mixed $output the output to add.
+ */
+ protected function _addFrameOutput($parent, $property, $output) {
+ if(is_object($parent) && !($parent instanceof ArrayObject)) {
+ self::addValue(
+ $parent, $property, $output, array('propertyIsArray' => true));
+ } else {
+ $parent[] = $output;
+ }
+ }
+
+ /**
+ * Removes the @preserve keywords as the last step of the framing algorithm.
+ *
+ * @param stdClass $ctx the active context used to compact the input.
+ * @param mixed $input the framed, compacted output.
+ * @param assoc $options the compaction options used.
+ *
+ * @return mixed the resulting output.
+ */
+ protected function _removePreserve($ctx, $input, $options) {
+ // recurse through arrays
+ if(is_array($input)) {
+ $output = array();
+ foreach($input as $e) {
+ $result = $this->_removePreserve($ctx, $e, $options);
+ // drop nulls from arrays
+ if($result !== null) {
+ $output[] = $result;
+ }
+ }
+ $input = $output;
+ } else if(is_object($input)) {
+ // remove @preserve
+ if(property_exists($input, '@preserve')) {
+ if($input->{'@preserve'} === '@null') {
+ return null;
+ }
+ return $input->{'@preserve'};
+ }
+
+ // skip @values
+ if(self::_isValue($input)) {
+ return $input;
+ }
+
+ // recurse through @lists
+ if(self::_isList($input)) {
+ $input->{'@list'} = $this->_removePreserve(
+ $ctx, $input->{'@list'}, $options);
+ return $input;
+ }
+
+ // handle in-memory linked nodes
+ $id_alias = $this->_compactIri($ctx, '@id');
+ if(property_exists($input, $id_alias)) {
+ $id = $input->{$id_alias};
+ if(isset($options['link'][$id])) {
+ $idx = array_search($input, $options['link'][$id]);
+ if($idx === false) {
+ // prevent circular visitation
+ $options['link'][$id][] = $input;
+ } else {
+ // already visited
+ return $options['link'][$id][$idx];
+ }
+ } else {
+ // prevent circular visitation
+ $options['link'][$id] = array($input);
+ }
+ }
+
+ // recurse through properties
+ foreach($input as $prop => $v) {
+ $result = $this->_removePreserve($ctx, $v, $options);
+ $container = self::getContextValue($ctx, $prop, '@container');
+ if($options['compactArrays'] &&
+ is_array($result) && count($result) === 1 &&
+ $container !== '@set' && $container !== '@list') {
+ $result = $result[0];
+ }
+ $input->{$prop} = $result;
+ }
+ }
+ return $input;
+ }
+
+ /**
+ * Compares two RDF triples for equality.
+ *
+ * @param stdClass $t1 the first triple.
+ * @param stdClass $t2 the second triple.
+ *
+ * @return true if the triples are the same, false if not.
+ */
+ protected static function _compareRDFTriples($t1, $t2) {
+ foreach(array('subject', 'predicate', 'object') as $attr) {
+ if($t1->{$attr}->type !== $t2->{$attr}->type ||
+ $t1->{$attr}->value !== $t2->{$attr}->value) {
+ return false;
+ }
+ }
+ if(property_exists($t1->object, 'language') !==
+ property_exists($t1->object, 'language')) {
+ return false;
+ }
+ if(property_exists($t1->object, 'language') &&
+ $t1->object->language !== $t2->object->language) {
+ return false;
+ }
+ if(property_exists($t1->object, 'datatype') &&
+ $t1->object->datatype !== $t2->object->datatype) {
+ return false;
+ }
+ return true;
+ }
+
+ /**
+ * Hashes all of the quads about a blank node.
+ *
+ * @param string $id the ID of the bnode to hash quads for.
+ * @param stdClass $bnodes the mapping of bnodes to quads.
+ * @param UniqueNamer $namer the canonical bnode namer.
+ *
+ * @return string the new hash.
+ */
+ protected function _hashQuads($id, $bnodes, $namer) {
+ // return cached hash
+ if(property_exists($bnodes->{$id}, 'hash')) {
+ return $bnodes->{$id}->hash;
+ }
+
+ // serialize all of bnode's quads
+ $quads = $bnodes->{$id}->quads;
+ $nquads = array();
+ foreach($quads as $quad) {
+ $nquads[] = $this->toNQuad($quad, property_exists($quad, 'name') ?
+ $quad->name->value : null, $id);
+ }
+
+ // sort serialized quads
+ sort($nquads);
+
+ // cache and return hashed quads
+ $hash = $bnodes->{$id}->hash = sha1(implode($nquads));
+ return $hash;
+ }
+
+ /**
+ * Produces a hash for the paths of adjacent bnodes for a bnode,
+ * incorporating all information about its subgraph of bnodes. This
+ * method will recursively pick adjacent bnode permutations that produce the
+ * lexicographically-least 'path' serializations.
+ *
+ * @param string $id the ID of the bnode to hash paths for.
+ * @param stdClass $bnodes the map of bnode quads.
+ * @param UniqueNamer $namer the canonical bnode namer.
+ * @param UniqueNamer $path_namer the namer used to assign names to adjacent
+ * bnodes.
+ *
+ * @return stdClass the hash and path namer used.
+ */
+ protected function _hashPaths($id, $bnodes, $namer, $path_namer) {
+ // create SHA-1 digest
+ $md = hash_init('sha1');
+
+ // group adjacent bnodes by hash, keep properties and references separate
+ $groups = new stdClass();
+ $quads = $bnodes->{$id}->quads;
+ foreach($quads as $quad) {
+ // get adjacent bnode
+ $bnode = $this->_getAdjacentBlankNodeName($quad->subject, $id);
+ if($bnode !== null) {
+ // normal property
+ $direction = 'p';
+ } else {
+ $bnode = $this->_getAdjacentBlankNodeName($quad->object, $id);
+ if($bnode !== null) {
+ // reverse property
+ $direction = 'r';
+ }
+ }
+ if($bnode !== null) {
+ // get bnode name (try canonical, path, then hash)
+ if($namer->isNamed($bnode)) {
+ $name = $namer->getName($bnode);
+ } else if($path_namer->isNamed($bnode)) {
+ $name = $path_namer->getName($bnode);
+ } else {
+ $name = $this->_hashQuads($bnode, $bnodes, $namer);
+ }
+
+ // hash direction, property, and bnode name/hash
+ $group_md = hash_init('sha1');
+ hash_update($group_md, $direction);
+ hash_update($group_md, $quad->predicate->value);
+ hash_update($group_md, $name);
+ $group_hash = hash_final($group_md);
+
+ // add bnode to hash group
+ if(property_exists($groups, $group_hash)) {
+ $groups->{$group_hash}[] = $bnode;
+ } else {
+ $groups->{$group_hash} = array($bnode);
+ }
+ }
+ }
+
+ // iterate over groups in sorted hash order
+ $group_hashes = array_keys((array)$groups);
+ sort($group_hashes);
+ foreach($group_hashes as $group_hash) {
+ // digest group hash
+ hash_update($md, $group_hash);
+
+ // choose a path and namer from the permutations
+ $chosen_path = null;
+ $chosen_namer = null;
+ $permutator = new Permutator($groups->{$group_hash});
+ while($permutator->hasNext()) {
+ $permutation = $permutator->next();
+ $path_namer_copy = clone $path_namer;
+
+ // build adjacent path
+ $path = '';
+ $skipped = false;
+ $recurse = array();
+ foreach($permutation as $bnode) {
+ // use canonical name if available
+ if($namer->isNamed($bnode)) {
+ $path .= $namer->getName($bnode);
+ } else {
+ // recurse if bnode isn't named in the path yet
+ if(!$path_namer_copy->isNamed($bnode)) {
+ $recurse[] = $bnode;
+ }
+ $path .= $path_namer_copy->getName($bnode);
+ }
+
+ // skip permutation if path is already >= chosen path
+ if($chosen_path !== null && strlen($path) >= strlen($chosen_path) &&
+ $path > $chosen_path) {
+ $skipped = true;
+ break;
+ }
+ }
+
+ // recurse
+ if(!$skipped) {
+ foreach($recurse as $bnode) {
+ $result = $this->_hashPaths(
+ $bnode, $bnodes, $namer, $path_namer_copy);
+ $path .= $path_namer_copy->getName($bnode);
+ $path .= "<{$result->hash}>";
+ $path_namer_copy = $result->pathNamer;
+
+ // skip permutation if path is already >= chosen path
+ if($chosen_path !== null &&
+ strlen($path) >= strlen($chosen_path) && $path > $chosen_path) {
+ $skipped = true;
+ break;
+ }
+ }
+ }
+
+ if(!$skipped && ($chosen_path === null || $path < $chosen_path)) {
+ $chosen_path = $path;
+ $chosen_namer = $path_namer_copy;
+ }
+ }
+
+ // digest chosen path and update namer
+ hash_update($md, $chosen_path);
+ $path_namer = $chosen_namer;
+ }
+
+ // return SHA-1 hash and path namer
+ return (object)array(
+ 'hash' => hash_final($md), 'pathNamer' => $path_namer);
+ }
+
+ /**
+ * A helper function that gets the blank node name from an RDF quad
+ * node (subject or object). If the node is not a blank node or its
+ * value does not match the given blank node ID, it will be returned.
+ *
+ * @param stdClass $node the RDF quad node.
+ * @param string $id the ID of the blank node to look next to.
+ *
+ * @return mixed the adjacent blank node name or null if none was found.
+ */
+ protected function _getAdjacentBlankNodeName($node, $id) {
+ if($node->type === 'blank node' && $node->value !== $id) {
+ return $node->value;
+ }
+ return null;
+ }
+
+ /**
+ * Compares two strings first based on length and then lexicographically.
+ *
+ * @param string $a the first string.
+ * @param string $b the second string.
+ *
+ * @return integer -1 if a < b, 1 if a > b, 0 if a == b.
+ */
+ protected function _compareShortestLeast($a, $b) {
+ $len_a = strlen($a);
+ $len_b = strlen($b);
+ if($len_a < $len_b) {
+ return -1;
+ }
+ if($len_b < $len_a) {
+ return 1;
+ }
+ if($a === $b) {
+ return 0;
+ }
+ return ($a < $b) ? -1 : 1;
+ }
+
+ /**
+ * Picks the preferred compaction term from the given inverse context entry.
+ *
+ * @param active_ctx the active context.
+ * @param iri the IRI to pick the term for.
+ * @param value the value to pick the term for.
+ * @param containers the preferred containers.
+ * @param type_or_language either '@type' or '@language'.
+ * @param type_or_language_value the preferred value for '@type' or
+ * '@language'.
+ *
+ * @return mixed the preferred term.
+ */
+ protected function _selectTerm(
+ $active_ctx, $iri, $value, $containers,
+ $type_or_language, $type_or_language_value) {
+ if($type_or_language_value === null) {
+ $type_or_language_value = '@null';
+ }
+
+ // options for the value of @type or @language
+ $prefs = array();
+
+ // determine prefs for @id based on whether or not value compacts to a term
+ if(($type_or_language_value === '@id' ||
+ $type_or_language_value === '@reverse') &&
+ self::_isSubjectReference($value)) {
+ // prefer @reverse first
+ if($type_or_language_value === '@reverse') {
+ $prefs[] = '@reverse';
+ }
+ // try to compact value to a term
+ $term = $this->_compactIri(
+ $active_ctx, $value->{'@id'}, null, array('vocab' => true));
+ if(property_exists($active_ctx->mappings, $term) &&
+ $active_ctx->mappings->{$term} &&
+ $active_ctx->mappings->{$term}->{'@id'} === $value->{'@id'}) {
+ // prefer @vocab
+ array_push($prefs, '@vocab', '@id');
+ } else {
+ // prefer @id
+ array_push($prefs, '@id', '@vocab');
+ }
+ } else {
+ $prefs[] = $type_or_language_value;
+ }
+ $prefs[] = '@none';
+
+ $container_map = $active_ctx->inverse->{$iri};
+ foreach($containers as $container) {
+ // if container not available in the map, continue
+ if(!property_exists($container_map, $container)) {
+ continue;
+ }
+
+ $type_or_language_value_map =
+ $container_map->{$container}->{$type_or_language};
+ foreach($prefs as $pref) {
+ // if type/language option not available in the map, continue
+ if(!property_exists($type_or_language_value_map, $pref)) {
+ continue;
+ }
+
+ // select term
+ return $type_or_language_value_map->{$pref};
+ }
+ }
+ return null;
+ }
+
+ /**
+ * Compacts an IRI or keyword into a term or prefix if it can be. If the
+ * IRI has an associated value it may be passed.
+ *
+ * @param stdClass $active_ctx the active context to use.
+ * @param string $iri the IRI to compact.
+ * @param mixed $value the value to check or null.
+ * @param assoc $relative_to options for how to compact IRIs:
+ * vocab: true to split after @vocab, false not to.
+ * @param bool $reverse true if a reverse property is being compacted, false
+ * if not.
+ *
+ * @return string the compacted term, prefix, keyword alias, or original IRI.
+ */
+ protected function _compactIri(
+ $active_ctx, $iri, $value=null, $relative_to=array(), $reverse=false) {
+ // can't compact null
+ if($iri === null) {
+ return $iri;
+ }
+
+ $inverse_ctx = $this->_getInverseContext($active_ctx);
+
+ if(self::_isKeyword($iri)) {
+ // a keyword can only be compacted to simple alias
+ if(property_exists($inverse_ctx, $iri)) {
+ return $inverse_ctx->$iri->{'@none'}->{'@type'}->{'@none'};
+ }
+ return $iri;
+ }
+
+ if(!isset($relative_to['vocab'])) {
+ $relative_to['vocab'] = false;
+ }
+
+ // use inverse context to pick a term if iri is relative to vocab
+ if($relative_to['vocab'] && property_exists($inverse_ctx, $iri)) {
+ $default_language = '@none';
+ if(property_exists($active_ctx, '@language')) {
+ $default_language = $active_ctx->{'@language'};
+ }
+
+ // prefer @index if available in value
+ $containers = array();
+ if(is_object($value) && property_exists($value, '@index')) {
+ $containers[] = '@index';
+ }
+
+ // defaults for term selection based on type/language
+ $type_or_language = '@language';
+ $type_or_language_value = '@null';
+
+ if($reverse) {
+ $type_or_language = '@type';
+ $type_or_language_value = '@reverse';
+ $containers[] = '@set';
+ } else if(self::_isList($value)) {
+ // choose the most specific term that works for all elements in @list
+ // only select @list containers if @index is NOT in value
+ if(!property_exists($value, '@index')) {
+ $containers[] = '@list';
+ }
+ $list = $value->{'@list'};
+ $common_language = (count($list) === 0) ? $default_language : null;
+ $common_type = null;
+ foreach($list as $item) {
+ $item_language = '@none';
+ $item_type = '@none';
+ if(self::_isValue($item)) {
+ if(property_exists($item, '@language')) {
+ $item_language = $item->{'@language'};
+ } else if(property_exists($item, '@type')) {
+ $item_type = $item->{'@type'};
+ } else {
+ // plain literal
+ $item_language = '@null';
+ }
+ } else {
+ $item_type = '@id';
+ }
+ if($common_language === null) {
+ $common_language = $item_language;
+ } else if($item_language !== $common_language &&
+ self::_isValue($item)) {
+ $common_language = '@none';
+ }
+ if($common_type === null) {
+ $common_type = $item_type;
+ } else if($item_type !== $common_type) {
+ $common_type = '@none';
+ }
+ // there are different languages and types in the list, so choose
+ // the most generic term, no need to keep iterating the list
+ if($common_language === '@none' && $common_type === '@none') {
+ break;
+ }
+ }
+ if($common_language === null) {
+ $common_language = '@none';
+ }
+ if($common_type === null) {
+ $common_type = '@none';
+ }
+ if($common_type !== '@none') {
+ $type_or_language = '@type';
+ $type_or_language_value = $common_type;
+ } else {
+ $type_or_language_value = $common_language;
+ }
+ } else {
+ if(self::_isValue($value)) {
+ if(property_exists($value, '@language') &&
+ !property_exists($value, '@index')) {
+ $containers[] = '@language';
+ $type_or_language_value = $value->{'@language'};
+ } else if(property_exists($value, '@type')) {
+ $type_or_language = '@type';
+ $type_or_language_value = $value->{'@type'};
+ }
+ } else {
+ $type_or_language = '@type';
+ $type_or_language_value = '@id';
+ }
+ $containers[] = '@set';
+ }
+
+ // do term selection
+ $containers[] = '@none';
+ $term = $this->_selectTerm(
+ $active_ctx, $iri, $value,
+ $containers, $type_or_language, $type_or_language_value);
+ if($term !== null) {
+ return $term;
+ }
+ }
+
+ // no term match, use @vocab if available
+ if($relative_to['vocab']) {
+ if(property_exists($active_ctx, '@vocab')) {
+ // determine if vocab is a prefix of the iri
+ $vocab = $active_ctx->{'@vocab'};
+ if(strpos($iri, $vocab) === 0 && $iri !== $vocab) {
+ // use suffix as relative iri if it is not a term in the active
+ // context
+ $suffix = substr($iri, strlen($vocab));
+ if(!property_exists($active_ctx->mappings, $suffix)) {
+ return $suffix;
+ }
+ }
+ }
+ }
+
+ // no term or @vocab match, check for possible CURIEs
+ $choice = null;
+ $idx = 0;
+ $partial_matches = array();
+ $iri_map = $active_ctx->fast_curie_map;
+ // check for partial matches of against `iri`, which means look until
+ // iri.length - 1, not full length
+ $max_partial_length = strlen($iri) - 1;
+ for(; $idx < $max_partial_length && isset($iri_map[$iri[$idx]]); ++$idx) {
+ $iri_map = $iri_map[$iri[$idx]];
+ if(isset($iri_map[''])) {
+ $entry = $iri_map[''][0];
+ $entry->iri_length = $idx + 1;
+ $partial_matches[] = $entry;
+ }
+ }
+ // check partial matches in reverse order to prefer longest ones first
+ $partial_matches = array_reverse($partial_matches);
+ foreach($partial_matches as $entry) {
+ $terms = $entry->terms;
+ foreach($terms as $term) {
+ // a CURIE is usable if:
+ // 1. it has no mapping, OR
+ // 2. value is null, which means we're not compacting an @value, AND
+ // the mapping matches the IRI
+ $curie = $term . ':' . substr($iri, $entry->iri_length);
+ $is_usable_curie = (!property_exists($active_ctx->mappings, $curie) ||
+ ($value === null &&
+ $active_ctx->mappings->{$curie}->{'@id'} === $iri));
+
+ // select curie if it is shorter or the same length but
+ // lexicographically less than the current choice
+ if($is_usable_curie && ($choice === null ||
+ self::_compareShortestLeast($curie, $choice) < 0)) {
+ $choice = $curie;
+ }
+ }
+ }
+
+ // return chosen curie
+ if($choice !== null) {
+ return $choice;
+ }
+
+ // compact IRI relative to base
+ if(!$relative_to['vocab']) {
+ return jsonld_remove_base($active_ctx->{'@base'}, $iri);
+ }
+
+ // return IRI as is
+ return $iri;
+ }
+
+ /**
+ * Performs value compaction on an object with '@value' or '@id' as the only
+ * property.
+ *
+ * @param stdClass $active_ctx the active context.
+ * @param string $active_property the active property that points to the
+ * value.
+ * @param mixed $value the value to compact.
+ *
+ * @return mixed the compaction result.
+ */
+ protected function _compactValue($active_ctx, $active_property, $value) {
+ // value is a @value
+ if(self::_isValue($value)) {
+ // get context rules
+ $type = self::getContextValue($active_ctx, $active_property, '@type');
+ $language = self::getContextValue(
+ $active_ctx, $active_property, '@language');
+ $container = self::getContextValue(
+ $active_ctx, $active_property, '@container');
+
+ // whether or not the value has an @index that must be preserved
+ $preserve_index = (property_exists($value, '@index') &&
+ $container !== '@index');
+
+ // if there's no @index to preserve
+ if(!$preserve_index) {
+ // matching @type or @language specified in context, compact value
+ if(self::_hasKeyValue($value, '@type', $type) ||
+ self::_hasKeyValue($value, '@language', $language)) {
+ return $value->{'@value'};
+ }
+ }
+
+ // return just the value of @value if all are true:
+ // 1. @value is the only key or @index isn't being preserved
+ // 2. there is no default language or @value is not a string or
+ // the key has a mapping with a null @language
+ $key_count = count(array_keys((array)$value));
+ $is_value_only_key = ($key_count === 1 ||
+ ($key_count === 2 && property_exists($value, '@index') &&
+ !$preserve_index));
+ $has_default_language = property_exists($active_ctx, '@language');
+ $is_value_string = is_string($value->{'@value'});
+ $has_null_mapping = (
+ property_exists($active_ctx->mappings, $active_property) &&
+ $active_ctx->mappings->{$active_property} !== null &&
+ self::_hasKeyValue(
+ $active_ctx->mappings->{$active_property}, '@language', null));
+ if($is_value_only_key &&
+ (!$has_default_language || !$is_value_string || $has_null_mapping)) {
+ return $value->{'@value'};
+ }
+
+ $rval = new stdClass();
+
+ // preserve @index
+ if($preserve_index) {
+ $rval->{$this->_compactIri($active_ctx, '@index')} = $value->{'@index'};
+ }
+
+ // compact @type IRI
+ if(property_exists($value, '@type')) {
+ $rval->{$this->_compactIri($active_ctx, '@type')} = $this->_compactIri(
+ $active_ctx, $value->{'@type'}, null, array('vocab' => true));
+ } else if(property_exists($value, '@language')) {
+ // alias @language
+ $rval->{$this->_compactIri($active_ctx, '@language')} =
+ $value->{'@language'};
+ }
+
+ // alias @value
+ $rval->{$this->_compactIri($active_ctx, '@value')} = $value->{'@value'};
+
+ return $rval;
+ }
+
+ // value is a subject reference
+ $expanded_property = $this->_expandIri(
+ $active_ctx, $active_property, array('vocab' => true));
+ $type = self::getContextValue($active_ctx, $active_property, '@type');
+ $compacted = $this->_compactIri(
+ $active_ctx, $value->{'@id'}, null,
+ array('vocab' => ($type === '@vocab')));
+
+ // compact to scalar
+ if($type === '@id' || $type === '@vocab' ||
+ $expanded_property === '@graph') {
+ return $compacted;
+ }
+
+ $rval = (object)array(
+ $this->_compactIri($active_ctx, '@id') => $compacted);
+ return $rval;
+ }
+
+ /**
+ * Creates a term definition during context processing.
+ *
+ * @param stdClass $active_ctx the current active context.
+ * @param stdClass $local_ctx the local context being processed.
+ * @param string $term the key in the local context to define the mapping for.
+ * @param stdClass $defined a map of defining/defined keys to detect cycles
+ * and prevent double definitions.
+ */
+ protected function _createTermDefinition(
+ $active_ctx, $local_ctx, $term, $defined) {
+ if(property_exists($defined, $term)) {
+ // term already defined
+ if($defined->{$term}) {
+ return;
+ }
+ // cycle detected
+ throw new JsonLdException(
+ 'Cyclical context definition detected.',
+ 'jsonld.CyclicalContext', 'cyclic IRI mapping',
+ array('context' => $local_ctx, 'term' => $term));
+ }
+
+ // now defining term
+ $defined->{$term} = false;
+
+ if(self::_isKeyword($term)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; keywords cannot be overridden.',
+ 'jsonld.SyntaxError', 'keyword redefinition',
+ array('context' => $local_ctx, 'term' => $term));
+ }
+
+ // remove old mapping
+ if(property_exists($active_ctx->mappings, $term)) {
+ unset($active_ctx->mappings->{$term});
+ }
+
+ // get context term value
+ $value = $local_ctx->{$term};
+
+ // clear context entry
+ if($value === null || (is_object($value) &&
+ self::_hasKeyValue($value, '@id', null))) {
+ $active_ctx->mappings->{$term} = null;
+ $defined->{$term} = true;
+ return;
+ }
+
+ // convert short-hand value to object w/@id
+ if(is_string($value)) {
+ $value = (object)array('@id' => $value);
+ }
+
+ if(!is_object($value)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; @context property values must be ' .
+ 'strings or objects.', 'jsonld.SyntaxError', 'invalid term definition',
+ array('context' => $local_ctx));
+ }
+
+ // create new mapping
+ $mapping = $active_ctx->mappings->{$term} = new stdClass();
+ $mapping->reverse = false;
+
+ if(property_exists($value, '@reverse')) {
+ if(property_exists($value, '@id')) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; a @reverse term definition must not ' +
+ 'contain @id.', 'jsonld.SyntaxError', 'invalid reverse property',
+ array('context' => $local_ctx));
+ }
+ $reverse = $value->{'@reverse'};
+ if(!is_string($reverse)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; a @context @reverse value must be a string.',
+ 'jsonld.SyntaxError', 'invalid IRI mapping',
+ array('context' => $local_ctx));
+ }
+
+ // expand and add @id mapping
+ $id = $this->_expandIri(
+ $active_ctx, $reverse, array('vocab' => true, 'base' => false),
+ $local_ctx, $defined);
+ if(!self::_isAbsoluteIri($id)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; @context @reverse value must be ' .
+ 'an absolute IRI or a blank node identifier.',
+ 'jsonld.SyntaxError', 'invalid IRI mapping',
+ array('context' => $local_ctx));
+ }
+ $mapping->{'@id'} = $id;
+ $mapping->reverse = true;
+ } else if(property_exists($value, '@id')) {
+ $id = $value->{'@id'};
+ if(!is_string($id)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; @context @id value must be a string.',
+ 'jsonld.SyntaxError', 'invalid IRI mapping',
+ array('context' => $local_ctx));
+ }
+ if($id !== $term) {
+ // add @id to mapping
+ $id = $this->_expandIri(
+ $active_ctx, $id, array('vocab' => true, 'base' => false),
+ $local_ctx, $defined);
+ if(!self::_isAbsoluteIri($id) && !self::_isKeyword($id)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; @context @id value must be an ' .
+ 'absolute IRI, a blank node identifier, or a keyword.',
+ 'jsonld.SyntaxError', 'invalid IRI mapping',
+ array('context' => $local_ctx));
+ }
+ $mapping->{'@id'} = $id;
+ }
+ }
+
+ // always compute whether term has a colon as an optimization for
+ // _compactIri
+ $colon = strpos($term, ':');
+ $mapping->_term_has_colon = ($colon !== false);
+
+ if(!property_exists($mapping, '@id')) {
+ // see if the term has a prefix
+ if($mapping->_term_has_colon) {
+ $prefix = substr($term, 0, $colon);
+ if(property_exists($local_ctx, $prefix)) {
+ // define parent prefix
+ $this->_createTermDefinition(
+ $active_ctx, $local_ctx, $prefix, $defined);
+ }
+
+ if(property_exists($active_ctx->mappings, $prefix) &&
+ $active_ctx->mappings->{$prefix}) {
+ // set @id based on prefix parent
+ $suffix = substr($term, $colon + 1);
+ $mapping->{'@id'} = $active_ctx->mappings->{$prefix}->{'@id'} .
+ $suffix;
+ } else {
+ // term is an absolute IRI
+ $mapping->{'@id'} = $term;
+ }
+ } else {
+ // non-IRIs *must* define @ids if @vocab is not available
+ if(!property_exists($active_ctx, '@vocab')) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; @context terms must define an @id.',
+ 'jsonld.SyntaxError', 'invalid IRI mapping',
+ array('context' => $local_ctx, 'term' => $term));
+ }
+ // prepend vocab to term
+ $mapping->{'@id'} = $active_ctx->{'@vocab'} . $term;
+ }
+ }
+
+ // optimization to store length of @id once for _compactIri
+ $mapping->_id_length = strlen($mapping->{'@id'});
+
+ // IRI mapping now defined
+ $defined->{$term} = true;
+
+ if(property_exists($value, '@type')) {
+ $type = $value->{'@type'};
+ if(!is_string($type)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; @context @type values must be strings.',
+ 'jsonld.SyntaxError', 'invalid type mapping',
+ array('context' => $local_ctx));
+ }
+
+ if($type !== '@id' && $type !== '@vocab') {
+ // expand @type to full IRI
+ $type = $this->_expandIri(
+ $active_ctx, $type, array('vocab' => true), $local_ctx, $defined);
+ if(!self::_isAbsoluteIri($type)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; an @context @type value must ' .
+ 'be an absolute IRI.', 'jsonld.SyntaxError',
+ 'invalid type mapping', array('context' => $local_ctx));
+ }
+ if(strpos($type, '_:') === 0) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; an @context @type values must ' .
+ 'be an IRI, not a blank node identifier.',
+ 'jsonld.SyntaxError', 'invalid type mapping',
+ array('context' => $local_ctx));
+ }
+ }
+
+ // add @type to mapping
+ $mapping->{'@type'} = $type;
+ }
+
+ if(property_exists($value, '@container')) {
+ $container = $value->{'@container'};
+ if($container !== '@list' && $container !== '@set' &&
+ $container !== '@index' && $container !== '@language') {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; @context @container value must be ' .
+ 'one of the following: @list, @set, @index, or @language.',
+ 'jsonld.SyntaxError', 'invalid container mapping',
+ array('context' => $local_ctx));
+ }
+ if($mapping->reverse && $container !== '@index' &&
+ $container !== '@set' && $container !== null) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; @context @container value for a @reverse ' +
+ 'type definition must be @index or @set.',
+ 'jsonld.SyntaxError', 'invalid reverse property',
+ array('context' => $local_ctx));
+ }
+
+ // add @container to mapping
+ $mapping->{'@container'} = $container;
+ }
+
+ if(property_exists($value, '@language') &&
+ !property_exists($value, '@type')) {
+ $language = $value->{'@language'};
+ if($language !== null && !is_string($language)) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; @context @language value must be ' .
+ 'a string or null.', 'jsonld.SyntaxError',
+ 'invalid language mapping', array('context' => $local_ctx));
+ }
+
+ // add @language to mapping
+ if($language !== null) {
+ $language = strtolower($language);
+ }
+ $mapping->{'@language'} = $language;
+ }
+
+ // disallow aliasing @context and @preserve
+ $id = $mapping->{'@id'};
+ if($id === '@context' || $id === '@preserve') {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; @context and @preserve cannot be aliased.',
+ 'jsonld.SyntaxError', 'invalid keyword alias',
+ array('context' => $local_ctx));
+ }
+ }
+
+ /**
+ * Expands a string to a full IRI. The string may be a term, a prefix, a
+ * relative IRI, or an absolute IRI. The associated absolute IRI will be
+ * returned.
+ *
+ * @param stdClass $active_ctx the current active context.
+ * @param string $value the string to expand.
+ * @param assoc $relative_to options for how to resolve relative IRIs:
+ * base: true to resolve against the base IRI, false not to.
+ * vocab: true to concatenate after @vocab, false not to.
+ * @param stdClass $local_ctx the local context being processed (only given
+ * if called during document processing).
+ * @param defined a map for tracking cycles in context definitions (only given
+ * if called during document processing).
+ *
+ * @return mixed the expanded value.
+ */
+ function _expandIri(
+ $active_ctx, $value, $relative_to=array(), $local_ctx=null, $defined=null) {
+ // already expanded
+ if($value === null || self::_isKeyword($value)) {
+ return $value;
+ }
+
+ // define term dependency if not defined
+ if($local_ctx !== null && property_exists($local_ctx, $value) &&
+ !self::_hasKeyValue($defined, $value, true)) {
+ $this->_createTermDefinition($active_ctx, $local_ctx, $value, $defined);
+ }
+
+ if(isset($relative_to['vocab']) && $relative_to['vocab']) {
+ if(property_exists($active_ctx->mappings, $value)) {
+ $mapping = $active_ctx->mappings->{$value};
+
+ // value is explicitly ignored with a null mapping
+ if($mapping === null) {
+ return null;
+ }
+
+ // value is a term
+ return $mapping->{'@id'};
+ }
+ }
+
+ // split value into prefix:suffix
+ $colon = strpos($value, ':');
+ if($colon !== false) {
+ $prefix = substr($value, 0, $colon);
+ $suffix = substr($value, $colon + 1);
+
+ // do not expand blank nodes (prefix of '_') or already-absolute
+ // IRIs (suffix of '//')
+ if($prefix === '_' || strpos($suffix, '//') === 0) {
+ return $value;
+ }
+
+ // prefix dependency not defined, define it
+ if($local_ctx !== null && property_exists($local_ctx, $prefix)) {
+ $this->_createTermDefinition(
+ $active_ctx, $local_ctx, $prefix, $defined);
+ }
+
+ // use mapping if prefix is defined
+ if(property_exists($active_ctx->mappings, $prefix)) {
+ $mapping = $active_ctx->mappings->{$prefix};
+ if($mapping) {
+ return $mapping->{'@id'} . $suffix;
+ }
+ }
+
+ // already absolute IRI
+ return $value;
+ }
+
+ // prepend vocab
+ if(isset($relative_to['vocab']) && $relative_to['vocab'] &&
+ property_exists($active_ctx, '@vocab')) {
+ return $active_ctx->{'@vocab'} . $value;
+ }
+
+ // prepend base
+ $rval = $value;
+ if(isset($relative_to['base']) && $relative_to['base']) {
+ $rval = jsonld_prepend_base($active_ctx->{'@base'}, $rval);
+ }
+
+ return $rval;
+ }
+
+ /**
+ * Finds all @context URLs in the given JSON-LD input.
+ *
+ * @param mixed $input the JSON-LD input.
+ * @param stdClass $urls a map of URLs (url => false/@contexts).
+ * @param bool $replace true to replace the URLs in the given input with
+ * the @contexts from the urls map, false not to.
+ * @param string $base the base URL to resolve relative URLs with.
+ */
+ protected function _findContextUrls($input, $urls, $replace, $base) {
+ if(is_array($input)) {
+ foreach($input as $e) {
+ $this->_findContextUrls($e, $urls, $replace, $base);
+ }
+ } else if(is_object($input)) {
+ foreach($input as $k => &$v) {
+ if($k !== '@context') {
+ $this->_findContextUrls($v, $urls, $replace, $base);
+ continue;
+ }
+
+ // array @context
+ if(is_array($v)) {
+ $length = count($v);
+ for($i = 0; $i < $length; ++$i) {
+ if(is_string($v[$i])) {
+ $url = jsonld_prepend_base($base, $v[$i]);
+ // replace w/@context if requested
+ if($replace) {
+ $ctx = $urls->{$url};
+ if(is_array($ctx)) {
+ // add flattened context
+ array_splice($v, $i, 1, $ctx);
+ $i += count($ctx) - 1;
+ $length = count($v);
+ } else {
+ $v[$i] = $ctx;
+ }
+ } else if(!property_exists($urls, $url)) {
+ // @context URL found
+ $urls->{$url} = false;
+ }
+ }
+ }
+ } else if(is_string($v)) {
+ // string @context
+ $v = jsonld_prepend_base($base, $v);
+ // replace w/@context if requested
+ if($replace) {
+ $input->{$k} = $urls->{$v};
+ } else if(!property_exists($urls, $v)) {
+ // @context URL found
+ $urls->{$v} = false;
+ }
+ }
+ }
+ }
+ }
+
+ /**
+ * Retrieves external @context URLs using the given document loader. Each
+ * instance of @context in the input that refers to a URL will be replaced
+ * with the JSON @context found at that URL.
+ *
+ * @param mixed $input the JSON-LD input with possible contexts.
+ * @param stdClass $cycles an object for tracking context cycles.
+ * @param callable $load_document(url) the document loader.
+ * @param base $base the base URL to resolve relative URLs against.
+ *
+ * @return mixed the result.
+ */
+ protected function _retrieveContextUrls(
+ &$input, $cycles, $load_document, $base='') {
+ if(count(get_object_vars($cycles)) > self::MAX_CONTEXT_URLS) {
+ throw new JsonLdException(
+ 'Maximum number of @context URLs exceeded.',
+ 'jsonld.ContextUrlError', 'loading remote context failed',
+ array('max' => self::MAX_CONTEXT_URLS));
+ }
+
+ // for tracking the URLs to retrieve
+ $urls = new stdClass();
+
+ // regex for validating URLs
+ $regex = '/(http|https):\/\/(\w+:{0,1}\w*@)?(\S+)(:[0-9]+)?(\/|\/([\w#!:.?+=&%@!\-\/]))?/';
+
+ // find all URLs in the given input
+ $this->_findContextUrls($input, $urls, false, $base);
+
+ // queue all unretrieved URLs
+ $queue = array();
+ foreach($urls as $url => $ctx) {
+ if($ctx === false) {
+ // validate URL
+ if(!preg_match($regex, $url)) {
+ throw new JsonLdException(
+ 'Malformed or unsupported URL.', 'jsonld.InvalidUrl',
+ 'loading remote context failed', array('url' => $url));
+ }
+ $queue[] = $url;
+ }
+ }
+
+ // retrieve URLs in queue
+ foreach($queue as $url) {
+ // check for context URL cycle
+ if(property_exists($cycles, $url)) {
+ throw new JsonLdException(
+ 'Cyclical @context URLs detected.',
+ 'jsonld.ContextUrlError', 'recursive context inclusion',
+ array('url' => $url));
+ }
+ $_cycles = self::copy($cycles);
+ $_cycles->{$url} = true;
+
+ // retrieve URL
+ $remote_doc = call_user_func($load_document, $url);
+ $ctx = $remote_doc->document;
+
+ // parse string context as JSON
+ if(is_string($ctx)) {
+ try {
+ $ctx = self::_parse_json($ctx);
+ } catch(Exception $e) {
+ throw new JsonLdException(
+ 'Could not parse JSON from URL.',
+ 'jsonld.ParseError', 'loading remote context failed',
+ array('url' => $url), $e);
+ }
+ }
+
+ // ensure ctx is an object
+ if(!is_object($ctx)) {
+ throw new JsonLdException(
+ 'Derefencing a URL did not result in a valid JSON-LD object.',
+ 'jsonld.InvalidUrl', 'invalid remote context', array('url' => $url));
+ }
+
+ // use empty context if no @context key is present
+ if(!property_exists($ctx, '@context')) {
+ $ctx = (object)array('@context' => new stdClass());
+ } else {
+ $ctx = (object)array('@context' => $ctx->{'@context'});
+ }
+
+ // append context URL to context if given
+ if($remote_doc->contextUrl !== null) {
+ $ctx->{'@context'} = self::arrayify($ctx->{'@context'});
+ $ctx->{'@context'}[] = $remote_doc->contextUrl;
+ }
+
+ // recurse
+ $this->_retrieveContextUrls($ctx, $_cycles, $load_document, $url);
+ $urls->{$url} = $ctx->{'@context'};
+ }
+
+ // replace all URLS in the input
+ $this->_findContextUrls($input, $urls, true, $base);
+ }
+
+ /**
+ * Gets the initial context.
+ *
+ * @param assoc $options the options to use.
+ * base the document base IRI.
+ *
+ * @return stdClass the initial context.
+ */
+ protected function _getInitialContext($options) {
+ return (object)array(
+ '@base' => jsonld_parse_url($options['base']),
+ 'mappings' => new stdClass(),
+ 'inverse' => null);
+ }
+
+ /**
+ * Generates an inverse context for use in the compaction algorithm, if
+ * not already generated for the given active context.
+ *
+ * @param stdClass $active_ctx the active context to use.
+ *
+ * @return stdClass the inverse context.
+ */
+ protected function _getInverseContext($active_ctx) {
+ // inverse context already generated
+ if($active_ctx->inverse) {
+ return $active_ctx->inverse;
+ }
+
+ $inverse = $active_ctx->inverse = new stdClass();
+
+ // variables for building fast CURIE map
+ $fast_curie_map = $active_ctx->fast_curie_map = new ArrayObject();
+ $iris_to_terms = array();
+
+ // handle default language
+ $default_language = '@none';
+ if(property_exists($active_ctx, '@language')) {
+ $default_language = $active_ctx->{'@language'};
+ }
+
+ // create term selections for each mapping in the context, ordered by
+ // shortest and then lexicographically least
+ $mappings = $active_ctx->mappings;
+ $terms = array_keys((array)$mappings);
+ usort($terms, array($this, '_compareShortestLeast'));
+ foreach($terms as $term) {
+ $mapping = $mappings->{$term};
+ if($mapping === null) {
+ continue;
+ }
+
+ // add term selection where it applies
+ if(property_exists($mapping, '@container')) {
+ $container = $mapping->{'@container'};
+ } else {
+ $container = '@none';
+ }
+
+ // iterate over every IRI in the mapping
+ $iris = $mapping->{'@id'};
+ $iris = self::arrayify($iris);
+ foreach($iris as $iri) {
+ $is_keyword = self::_isKeyword($iri);
+
+ // initialize container map
+ if(!property_exists($inverse, $iri)) {
+ $inverse->{$iri} = new stdClass();
+ if(!$is_keyword && !$mapping->_term_has_colon) {
+ // init IRI to term map and fast CURIE map
+ $iris_to_terms[$iri] = new ArrayObject();
+ $iris_to_terms[$iri][] = $term;
+ $fast_curie_entry = (object)array(
+ 'iri' => $iri, 'terms' => $iris_to_terms[$iri]);
+ if(!array_key_exists($iri[0], (array)$fast_curie_map)) {
+ $fast_curie_map[$iri[0]] = new ArrayObject();
+ }
+ $fast_curie_map[$iri[0]][] = $fast_curie_entry;
+ }
+ } else if(!$is_keyword && !$mapping->_term_has_colon) {
+ // add IRI to term match
+ $iris_to_terms[$iri][] = $term;
+ }
+ $container_map = $inverse->{$iri};
+
+ // add new entry
+ if(!property_exists($container_map, $container)) {
+ $container_map->{$container} = (object)array(
+ '@language' => new stdClass(),
+ '@type' => new stdClass());
+ }
+ $entry = $container_map->{$container};
+
+ if($mapping->reverse) {
+ // term is preferred for values using @reverse
+ $this->_addPreferredTerm(
+ $mapping, $term, $entry->{'@type'}, '@reverse');
+ } else if(property_exists($mapping, '@type')) {
+ // term is preferred for values using specific type
+ $this->_addPreferredTerm(
+ $mapping, $term, $entry->{'@type'}, $mapping->{'@type'});
+ } else if(property_exists($mapping, '@language')) {
+ // term is preferred for values using specific language
+ $language = $mapping->{'@language'};
+ if($language === null) {
+ $language = '@null';
+ }
+ $this->_addPreferredTerm(
+ $mapping, $term, $entry->{'@language'}, $language);
+ } else {
+ // term is preferred for values w/default language or no type and
+ // no language
+ // add an entry for the default language
+ $this->_addPreferredTerm(
+ $mapping, $term, $entry->{'@language'}, $default_language);
+
+ // add entries for no type and no language
+ $this->_addPreferredTerm(
+ $mapping, $term, $entry->{'@type'}, '@none');
+ $this->_addPreferredTerm(
+ $mapping, $term, $entry->{'@language'}, '@none');
+ }
+ }
+ }
+
+ // build fast CURIE map
+ foreach($fast_curie_map as $key => $value) {
+ $this->_buildIriMap($fast_curie_map, $key, 1);
+ }
+
+ return $inverse;
+ }
+
+ /**
+ * Runs a recursive algorithm to build a lookup map for quickly finding
+ * potential CURIEs.
+ *
+ * @param ArrayObject $iri_map the map to build.
+ * @param string $key the current key in the map to work on.
+ * @param int $idx the index into the IRI to compare.
+ */
+ function _buildIriMap($iri_map, $key, $idx) {
+ $entries = $iri_map[$key];
+ $next = $iri_map[$key] = new ArrayObject();
+
+ foreach($entries as $entry) {
+ $iri = $entry->iri;
+ if($idx >= strlen($iri)) {
+ $letter = '';
+ } else {
+ $letter = $iri[$idx];
+ }
+ if(!isset($next[$letter])) {
+ $next[$letter] = new ArrayObject();
+ }
+ $next[$letter][] = $entry;
+ }
+
+ foreach($next as $key => $value) {
+ if($key === '') {
+ continue;
+ }
+ $this->_buildIriMap($next, $key, $idx + 1);
+ }
+ }
+
+ /**
+ * Adds the term for the given entry if not already added.
+ *
+ * @param stdClass $mapping the term mapping.
+ * @param string $term the term to add.
+ * @param stdClass $entry the inverse context type_or_language entry to
+ * add to.
+ * @param string $type_or_language_value the key in the entry to add to.
+ */
+ function _addPreferredTerm($mapping, $term, $entry, $type_or_language_value) {
+ if(!property_exists($entry, $type_or_language_value)) {
+ $entry->{$type_or_language_value} = $term;
+ }
+ }
+
+ /**
+ * Clones an active context, creating a child active context.
+ *
+ * @return stdClass a clone (child) of the active context.
+ */
+ protected function _cloneActiveContext($active_ctx) {
+ $child = new stdClass();
+ $child->{'@base'} = $active_ctx->{'@base'};
+ $child->mappings = self::copy($active_ctx->mappings);
+ $child->inverse = null;
+ if(property_exists($active_ctx, '@language')) {
+ $child->{'@language'} = $active_ctx->{'@language'};
+ }
+ if(property_exists($active_ctx, '@vocab')) {
+ $child->{'@vocab'} = $active_ctx->{'@vocab'};
+ }
+ return $child;
+ }
+
+ /**
+ * Returns whether or not the given value is a keyword.
+ *
+ * @param string $v the value to check.
+ *
+ * @return bool true if the value is a keyword, false if not.
+ */
+ protected static function _isKeyword($v) {
+ if(!is_string($v)) {
+ return false;
+ }
+ switch($v) {
+ case '@base':
+ case '@context':
+ case '@container':
+ case '@default':
+ case '@embed':
+ case '@explicit':
+ case '@graph':
+ case '@id':
+ case '@index':
+ case '@language':
+ case '@list':
+ case '@omitDefault':
+ case '@preserve':
+ case '@requireAll':
+ case '@reverse':
+ case '@set':
+ case '@type':
+ case '@value':
+ case '@vocab':
+ return true;
+ }
+ return false;
+ }
+
+ /**
+ * Returns true if the given value is an empty Object.
+ *
+ * @param mixed $v the value to check.
+ *
+ * @return bool true if the value is an empty Object, false if not.
+ */
+ protected static function _isEmptyObject($v) {
+ return is_object($v) && count(get_object_vars($v)) === 0;
+ }
+
+ /**
+ * Throws an exception if the given value is not a valid @type value.
+ *
+ * @param mixed $v the value to check.
+ */
+ protected static function _validateTypeValue($v) {
+ // must be a string or empty object
+ if(is_string($v) || self::_isEmptyObject($v)) {
+ return;
+ }
+
+ // must be an array
+ $is_valid = false;
+ if(is_array($v)) {
+ // must contain only strings
+ $is_valid = true;
+ foreach($v as $e) {
+ if(!(is_string($e))) {
+ $is_valid = false;
+ break;
+ }
+ }
+ }
+
+ if(!$is_valid) {
+ throw new JsonLdException(
+ 'Invalid JSON-LD syntax; "@type" value must a string, an array ' .
+ 'of strings, or an empty object.',
+ 'jsonld.SyntaxError', 'invalid type value', array('value' => $v));
+ }
+ }
+
+ /**
+ * Returns true if the given value is a subject with properties.
+ *
+ * @param mixed $v the value to check.
+ *
+ * @return bool true if the value is a subject with properties, false if not.
+ */
+ protected static function _isSubject($v) {
+ // Note: A value is a subject if all of these hold true:
+ // 1. It is an Object.
+ // 2. It is not a @value, @set, or @list.
+ // 3. It has more than 1 key OR any existing key is not @id.
+ $rval = false;
+ if(is_object($v) &&
+ !property_exists($v, '@value') &&
+ !property_exists($v, '@set') &&
+ !property_exists($v, '@list')) {
+ $count = count(get_object_vars($v));
+ $rval = ($count > 1 || !property_exists($v, '@id'));
+ }
+ return $rval;
+ }
+
+ /**
+ * Returns true if the given value is a subject reference.
+ *
+ * @param mixed $v the value to check.
+ *
+ * @return bool true if the value is a subject reference, false if not.
+ */
+ protected static function _isSubjectReference($v) {
+ // Note: A value is a subject reference if all of these hold true:
+ // 1. It is an Object.
+ // 2. It has a single key: @id.
+ return (is_object($v) && count(get_object_vars($v)) === 1 &&
+ property_exists($v, '@id'));
+ }
+
+ /**
+ * Returns true if the given value is a @value.
+ *
+ * @param mixed $v the value to check.
+ *
+ * @return bool true if the value is a @value, false if not.
+ */
+ protected static function _isValue($v) {
+ // Note: A value is a @value if all of these hold true:
+ // 1. It is an Object.
+ // 2. It has the @value property.
+ return is_object($v) && property_exists($v, '@value');
+ }
+
+ /**
+ * Returns true if the given value is a @list.
+ *
+ * @param mixed $v the value to check.
+ *
+ * @return bool true if the value is a @list, false if not.
+ */
+ protected static function _isList($v) {
+ // Note: A value is a @list if all of these hold true:
+ // 1. It is an Object.
+ // 2. It has the @list property.
+ return is_object($v) && property_exists($v, '@list');
+ }
+
+ /**
+ * Returns true if the given value is a blank node.
+ *
+ * @param mixed $v the value to check.
+ *
+ * @return bool true if the value is a blank node, false if not.
+ */
+ protected static function _isBlankNode($v) {
+ // Note: A value is a blank node if all of these hold true:
+ // 1. It is an Object.
+ // 2. If it has an @id key its value begins with '_:'.
+ // 3. It has no keys OR is not a @value, @set, or @list.
+ $rval = false;
+ if(is_object($v)) {
+ if(property_exists($v, '@id')) {
+ $rval = (strpos($v->{'@id'}, '_:') === 0);
+ } else {
+ $rval = (count(get_object_vars($v)) === 0 ||
+ !(property_exists($v, '@value') ||
+ property_exists($v, '@set') ||
+ property_exists($v, '@list')));
+ }
+ }
+ return $rval;
+ }
+
+ /**
+ * Returns true if the given value is an absolute IRI, false if not.
+ *
+ * @param string $v the value to check.
+ *
+ * @return bool true if the value is an absolute IRI, false if not.
+ */
+ protected static function _isAbsoluteIri($v) {
+ return strpos($v, ':') !== false;
+ }
+
+ /**
+ * Returns true if the given target has the given key and its
+ * value equals is the given value.
+ *
+ * @param stdClass $target the target object.
+ * @param string key the key to check.
+ * @param mixed $value the value to check.
+ *
+ * @return bool true if the target has the given key and its value matches.
+ */
+ protected static function _hasKeyValue($target, $key, $value) {
+ return (property_exists($target, $key) && $target->{$key} === $value);
+ }
+
+ /**
+ * Returns true if both of the given objects have the same value for the
+ * given key or if neither of the objects contain the given key.
+ *
+ * @param stdClass $o1 the first object.
+ * @param stdClass $o2 the second object.
+ * @param string key the key to check.
+ *
+ * @return bool true if both objects have the same value for the key or
+ * neither has the key.
+ */
+ protected static function _compareKeyValues($o1, $o2, $key) {
+ if(property_exists($o1, $key)) {
+ return property_exists($o2, $key) && $o1->{$key} === $o2->{$key};
+ }
+ return !property_exists($o2, $key);
+ }
+
+ /**
+ * Parses JSON and sets an appropriate exception message on error.
+ *
+ * @param string $json the JSON to parse.
+ *
+ * @return mixed the parsed JSON object or array.
+ */
+ protected static function _parse_json($json) {
+ $rval = json_decode($json);
+ $error = json_last_error();
+ if($error === JSON_ERROR_NONE && $rval === null) {
+ $error = JSON_ERROR_SYNTAX;
+ }
+ switch($error) {
+ case JSON_ERROR_NONE:
+ break;
+ case JSON_ERROR_DEPTH:
+ throw new JsonLdException(
+ 'Could not parse JSON; the maximum stack depth has been exceeded.',
+ 'jsonld.ParseError');
+ case JSON_ERROR_STATE_MISMATCH:
+ throw new JsonLdException(
+ 'Could not parse JSON; invalid or malformed JSON.',
+ 'jsonld.ParseError');
+ case JSON_ERROR_CTRL_CHAR:
+ case JSON_ERROR_SYNTAX:
+ throw new JsonLdException(
+ 'Could not parse JSON; syntax error, malformed JSON.',
+ 'jsonld.ParseError');
+ case JSON_ERROR_UTF8:
+ throw new JsonLdException(
+ 'Could not parse JSON from URL; malformed UTF-8 characters.',
+ 'jsonld.ParseError');
+ default:
+ throw new JsonLdException(
+ 'Could not parse JSON from URL; unknown error.',
+ 'jsonld.ParseError');
+ }
+ return $rval;
+ }
+}
+
+// register the N-Quads RDF parser
+jsonld_register_rdf_parser(
+ 'application/nquads', array('JsonLdProcessor', 'parseNQuads'));
+
+/**
+ * A JSON-LD Exception.
+ */
+class JsonLdException extends Exception {
+ public function __construct(
+ $msg, $type, $code='error', $details=null, $previous=null) {
+ $this->type = $type;
+ $this->code = $code;
+ $this->details = $details;
+ $this->cause = $previous;
+ parent::__construct($msg, 0, $previous);
+ }
+ public function __toString() {
+ $rval = __CLASS__ . ": [{$this->type}]: {$this->message}\n";
+ if($this->code) {
+ $rval .= 'Code: ' . $this->code . "\n";
+ }
+ if($this->details) {
+ $rval .= 'Details: ' . print_r($this->details, true) . "\n";
+ }
+ if($this->cause) {
+ $rval .= 'Cause: ' . $this->cause;
+ }
+ $rval .= $this->getTraceAsString() . "\n";
+ return $rval;
+ }
+};
+
+/**
+ * A UniqueNamer issues unique names, keeping track of any previously issued
+ * names.
+ */
+class UniqueNamer {
+ /**
+ * Constructs a new UniqueNamer.
+ *
+ * @param prefix the prefix to use ('<prefix><counter>').
+ */
+ public function __construct($prefix) {
+ $this->prefix = $prefix;
+ $this->counter = 0;
+ $this->existing = new stdClass();
+ $this->order = array();
+ }
+
+ /**
+ * Clones this UniqueNamer.
+ */
+ public function __clone() {
+ $this->existing = clone $this->existing;
+ }
+
+ /**
+ * Gets the new name for the given old name, where if no old name is given
+ * a new name will be generated.
+ *
+ * @param mixed [$old_name] the old name to get the new name for.
+ *
+ * @return string the new name.
+ */
+ public function getName($old_name=null) {
+ // return existing old name
+ if($old_name && property_exists($this->existing, $old_name)) {
+ return $this->existing->{$old_name};
+ }
+
+ // get next name
+ $name = $this->prefix . $this->counter;
+ $this->counter += 1;
+
+ // save mapping
+ if($old_name !== null) {
+ $this->existing->{$old_name} = $name;
+ $this->order[] = $old_name;
+ }
+
+ return $name;
+ }
+
+ /**
+ * Returns true if the given old name has already been assigned a new name.
+ *
+ * @param string $old_name the old name to check.
+ *
+ * @return true if the old name has been assigned a new name, false if not.
+ */
+ public function isNamed($old_name) {
+ return property_exists($this->existing, $old_name);
+ }
+}
+
+/**
+ * A Permutator iterates over all possible permutations of the given array
+ * of elements.
+ */
+class Permutator {
+ /**
+ * Constructs a new Permutator.
+ *
+ * @param array $list the array of elements to iterate over.
+ */
+ public function __construct($list) {
+ // original array
+ $this->list = $list;
+ sort($this->list);
+ // indicates whether there are more permutations
+ $this->done = false;
+ // directional info for permutation algorithm
+ $this->left = new stdClass();
+ foreach($list as $v) {
+ $this->left->{$v} = true;
+ }
+ }
+
+ /**
+ * Returns true if there is another permutation.
+ *
+ * @return bool true if there is another permutation, false if not.
+ */
+ public function hasNext() {
+ return !$this->done;
+ }
+
+ /**
+ * Gets the next permutation. Call hasNext() to ensure there is another one
+ * first.
+ *
+ * @return array the next permutation.
+ */
+ public function next() {
+ // copy current permutation
+ $rval = $this->list;
+
+ /* Calculate the next permutation using the Steinhaus-Johnson-Trotter
+ permutation algorithm. */
+
+ // get largest mobile element k
+ // (mobile: element is greater than the one it is looking at)
+ $k = null;
+ $pos = 0;
+ $length = count($this->list);
+ for($i = 0; $i < $length; ++$i) {
+ $element = $this->list[$i];
+ $left = $this->left->{$element};
+ if(($k === null || $element > $k) &&
+ (($left && $i > 0 && $element > $this->list[$i - 1]) ||
+ (!$left && $i < ($length - 1) && $element > $this->list[$i + 1]))) {
+ $k = $element;
+ $pos = $i;
+ }
+ }
+
+ // no more permutations
+ if($k === null) {
+ $this->done = true;
+ } else {
+ // swap k and the element it is looking at
+ $swap = $this->left->{$k} ? $pos - 1 : $pos + 1;
+ $this->list[$pos] = $this->list[$swap];
+ $this->list[$swap] = $k;
+
+ // reverse the direction of all elements larger than k
+ for($i = 0; $i < $length; ++$i) {
+ if($this->list[$i] > $k) {
+ $this->left->{$this->list[$i]} = !$this->left->{$this->list[$i]};
+ }
+ }
+ }
+
+ return $rval;
+ }
+}
+
+/**
+ * An ActiveContextCache caches active contexts so they can be reused without
+ * the overhead of recomputing them.
+ */
+class ActiveContextCache {
+ /**
+ * Constructs a new ActiveContextCache.
+ *
+ * @param int size the maximum size of the cache, defaults to 100.
+ */
+ public function __construct($size=100) {
+ $this->order = array();
+ $this->cache = new stdClass();
+ $this->size = $size;
+ }
+
+ /**
+ * Gets an active context from the cache based on the current active
+ * context and the new local context.
+ *
+ * @param stdClass $active_ctx the current active context.
+ * @param stdClass $local_ctx the new local context.
+ *
+ * @return mixed a shared copy of the cached active context or null.
+ */
+ public function get($active_ctx, $local_ctx) {
+ $key1 = serialize($active_ctx);
+ $key2 = serialize($local_ctx);
+ if(property_exists($this->cache, $key1)) {
+ $level1 = $this->cache->{$key1};
+ if(property_exists($level1, $key2)) {
+ return $level1->{$key2};
+ }
+ }
+ return null;
+ }
+
+ /**
+ * Sets an active context in the cache based on the previous active
+ * context and the just-processed local context.
+ *
+ * @param stdClass $active_ctx the previous active context.
+ * @param stdClass $local_ctx the just-processed local context.
+ * @param stdClass $result the resulting active context.
+ */
+ public function set($active_ctx, $local_ctx, $result) {
+ if(count($this->order) === $this->size) {
+ $entry = array_shift($this->order);
+ unset($this->cache->{$entry->activeCtx}->{$entry->localCtx});
+ }
+ $key1 = serialize($active_ctx);
+ $key2 = serialize($local_ctx);
+ $this->order[] = (object)array(
+ 'activeCtx' => $key1, 'localCtx' => $key2);
+ if(!property_exists($this->cache, $key1)) {
+ $this->cache->{$key1} = new stdClass();
+ }
+ $this->cache->{$key1}->{$key2} = JsonLdProcessor::copy($result);
+ }
+}
+
+/* end of file, omit ?> */
diff --git a/library/jsonld/test.php b/library/jsonld/test.php
new file mode 100644
index 000000000..11b72ac09
--- /dev/null
+++ b/library/jsonld/test.php
@@ -0,0 +1,765 @@
+<?php
+/**
+ * PHP unit tests for JSON-LD.
+ *
+ * @author Dave Longley
+ *
+ * Copyright (c) 2013-2014 Digital Bazaar, Inc. All rights reserved.
+ */
+require_once('jsonld.php');
+
+class JsonLdTestCase extends PHPUnit_Framework_TestCase {
+ /**
+ * Runs this test case. Overridden to attach to EARL report w/o need for
+ * an external XML configuration file.
+ *
+ * @param PHPUnit_Framework_TestResult $result the test result.
+ */
+ public function run(PHPUnit_Framework_TestResult $result = NULL) {
+ global $EARL;
+ $EARL->attach($result);
+ $this->result = $result;
+ parent::run($result);
+ }
+
+ /**
+ * Tests expansion.
+ *
+ * @param JsonLdTest $test the test to run.
+ *
+ * @group expand
+ * @group json-ld.org
+ * @dataProvider expandProvider
+ */
+ public function testExpand($test) {
+ $this->test = $test;
+ $input = $test->readUrl('input');
+ $options = $test->createOptions();
+ $test->run('jsonld_expand', array($input, $options));
+ }
+
+ /**
+ * Tests compaction.
+ *
+ * @param JsonLdTest $test the test to run.
+ *
+ * @group compact
+ * @group json-ld.org
+ * @dataProvider compactProvider
+ */
+ public function testCompact($test) {
+ $this->test = $test;
+ $input = $test->readUrl('input');
+ $context = $test->readProperty('context');
+ $options = $test->createOptions();
+ $test->run('jsonld_compact', array($input, $context, $options));
+ }
+
+ /**
+ * Tests flatten.
+ *
+ * @param JsonLdTest $test the test to run.
+ *
+ * @group flatten
+ * @group json-ld.org
+ * @dataProvider flattenProvider
+ */
+ public function testFlatten($test) {
+ $this->test = $test;
+ $input = $test->readUrl('input');
+ $context = $test->readProperty('context');
+ $options = $test->createOptions();
+ $test->run('jsonld_flatten', array($input, $context, $options));
+ }
+
+ /**
+ * Tests serialization to RDF.
+ *
+ * @param JsonLdTest $test the test to run.
+ *
+ * @group toRdf
+ * @group json-ld.org
+ * @dataProvider toRdfProvider
+ */
+ public function testToRdf($test) {
+ $this->test = $test;
+ $input = $test->readUrl('input');
+ $options = $test->createOptions(array('format' => 'application/nquads'));
+ $test->run('jsonld_to_rdf', array($input, $options));
+ }
+
+ /**
+ * Tests deserialization from RDF.
+ *
+ * @param JsonLdTest $test the test to run.
+ *
+ * @group fromRdf
+ * @group json-ld.org
+ * @dataProvider fromRdfProvider
+ */
+ public function testFromRdf($test) {
+ $this->test = $test;
+ $input = $test->readProperty('input');
+ $options = $test->createOptions(array('format' => 'application/nquads'));
+ $test->run('jsonld_from_rdf', array($input, $options));
+ }
+
+ /**
+ * Tests framing.
+ *
+ * @param JsonLdTest $test the test to run.
+ *
+ * @group frame
+ * @group json-ld.org
+ * @dataProvider frameProvider
+ */
+ public function testFrame($test) {
+ $this->test = $test;
+ $input = $test->readUrl('input');
+ $frame = $test->readProperty('frame');
+ $options = $test->createOptions();
+ $test->run('jsonld_frame', array($input, $frame, $options));
+ }
+
+ /**
+ * Tests normalization.
+ *
+ * @param JsonLdTest $test the test to run.
+ *
+ * @group normalize
+ * @group json-ld.org
+ * @dataProvider normalizeProvider
+ */
+ public function testNormalize($test) {
+ $this->test = $test;
+ $input = $test->readUrl('input');
+ $options = $test->createOptions(array('format' => 'application/nquads'));
+ $test->run('jsonld_normalize', array($input, $options));
+ }
+
+ /**
+ * Tests URGNA2012 normalization.
+ *
+ * @param JsonLdTest $test the test to run.
+ *
+ * @group normalize
+ * @group normalization
+ * @dataProvider urgna2012Provider
+ */
+ public function testUrgna2012($test) {
+ $this->test = $test;
+ $input = $test->readProperty('action');
+ $options = $test->createOptions(array(
+ 'algorithm' => 'URGNA2012',
+ 'inputFormat' => 'application/nquads',
+ 'format' => 'application/nquads'));
+ $test->run('jsonld_normalize', array($input, $options));
+ }
+
+ /**
+ * Tests URDNA2015 normalization.
+ *
+ * @param JsonLdTest $test the test to run.
+ *
+ * @group normalize
+ * @group normalization
+ * @dataProvider urdna2015Provider
+ */
+ public function testUrdna2015($test) {
+ $this->test = $test;
+ $input = $test->readProperty('action');
+ $options = $test->createOptions(array(
+ 'algorithm' => 'URDNA2015',
+ 'inputFormat' => 'application/nquads',
+ 'format' => 'application/nquads'));
+ $test->run('jsonld_normalize', array($input, $options));
+ }
+
+ public function expandProvider() {
+ return new JsonLdTestIterator('jld:ExpandTest');
+ }
+
+ public function compactProvider() {
+ return new JsonLdTestIterator('jld:CompactTest');
+ }
+
+ public function flattenProvider() {
+ return new JsonLdTestIterator('jld:FlattenTest');
+ }
+
+ public function toRdfProvider() {
+ return new JsonLdTestIterator('jld:ToRDFTest');
+ }
+
+ public function fromRdfProvider() {
+ return new JsonLdTestIterator('jld:FromRDFTest');
+ }
+
+ public function normalizeProvider() {
+ return new JsonLdTestIterator('jld:NormalizeTest');
+ }
+
+ public function frameProvider() {
+ return new JsonLdTestIterator('jld:FrameTest');
+ }
+
+ public function urgna2012Provider() {
+ return new JsonLdTestIterator('rdfn:Urgna2012EvalTest');
+ }
+
+ public function urdna2015Provider() {
+ return new JsonLdTestIterator('rdfn:Urdna2015EvalTest');
+ }
+}
+
+class JsonLdManifest {
+ public function __construct($data, $filename) {
+ $this->data = $data;
+ $this->filename = $filename;
+ $this->dirname = dirname($filename);
+ }
+
+ public function load(&$tests) {
+ $entries = array_merge(
+ JsonLdProcessor::getValues($this->data, 'sequence'),
+ JsonLdProcessor::getValues($this->data, 'entries'));
+ $includes = JsonLdProcessor::getValues($this->data, 'include');
+ foreach($includes as $include) {
+ array_push($entries, $include . '.jsonld');
+ }
+ foreach($entries as $entry) {
+ if(is_string($entry)) {
+ $filename = join(
+ DIRECTORY_SEPARATOR, array($this->dirname, $entry));
+ $entry = Util::readJson($filename);
+ } else {
+ $filename = $this->filename;
+ }
+
+ if(JsonLdProcessor::hasValue($entry, '@type', 'mf:Manifest') ||
+ JsonLdProcessor::hasValue($entry, 'type', 'mf:Manifest')) {
+ // entry is another manifest
+ $manifest = new JsonLdManifest($entry, $filename);
+ $manifest->load($tests);
+ } else {
+ // assume entry is a test
+ $test = new JsonLdTest($this, $entry, $filename);
+ $types = array_merge(
+ JsonLdProcessor::getValues($test->data, '@type'),
+ JsonLdProcessor::getValues($test->data, 'type'));
+ foreach($types as $type) {
+ if(!isset($tests[$type])) {
+ $tests[$type] = array();
+ }
+ $tests[$type][] = $test;
+ }
+ }
+ }
+ }
+}
+
+class JsonLdTest {
+ public function __construct($manifest, $data, $filename) {
+ $this->manifest = $manifest;
+ $this->data = $data;
+ $this->filename = $filename;
+ $this->dirname = dirname($filename);
+ $this->isPositive =
+ JsonLdProcessor::hasValue(
+ $data, '@type', 'jld:PositiveEvaluationTest') ||
+ JsonLdProcessor::hasValue(
+ $data, 'type', 'jld:PositiveEvaluationTest');
+ $this->isNegative =
+ JsonLdProcessor::hasValue(
+ $data, '@type', 'jld:NegativeEvaluationTest') ||
+ JsonLdProcessor::hasValue(
+ $data, 'type', 'jld:NegativeEvaluationTest');
+
+ // generate test name
+ if(isset($manifest->data->name)) {
+ $manifestLabel = $manifest->data->name;
+ } else if(isset($manifest->data->label)) {
+ $manifestLabel = $manifest->data->label;
+ } else {
+ $manifestLabel = 'UNNAMED';
+ }
+ if(isset($this->data->id)) {
+ $testId = $this->data->id;
+ } else {
+ $testId = $this->data->{'@id'};
+ }
+ if(isset($this->data->name)) {
+ $testLabel = $this->data->name;
+ } else if(isset($this->data->label)) {
+ $testLabel = $this->data->label;
+ } else {
+ $testLabel = 'UNNAMED';
+ }
+
+ $this->name = $manifestLabel . ' ' . $testId . ' - ' . $testLabel;
+
+ // expand @id and input base
+ if(isset($manifest->data->baseIri)) {
+ $data->{'@id'} = ($manifest->data->baseIri .
+ basename($manifest->filename) . $data->{'@id'});
+ $this->base = $manifest->data->baseIri . $data->input;
+ }
+ }
+
+ private function _getResultProperty() {
+ if(isset($this->data->expect)) {
+ return 'expect';
+ } else if(isset($this->data->result)) {
+ return 'result';
+ } else {
+ throw new Exception('No test result property found.');
+ }
+ }
+
+ public function run($fn, $params) {
+ // read expected data
+ if($this->isNegative) {
+ $this->expected = $this->data->expect;
+ } else {
+ $this->expected = $this->readProperty($this->_getResultProperty());
+ }
+
+ try {
+ $this->actual = call_user_func_array($fn, $params);
+ if($this->isNegative) {
+ throw new Exception('Expected an error; one was not raised.');
+ }
+ PHPUnit_Framework_TestCase::assertEquals($this->expected, $this->actual);
+ } catch(Exception $e) {
+ // assume positive test
+ if($this->isNegative) {
+ $this->actual = $this->getJsonLdErrorCode($e);
+ PHPUnit_Framework_TestCase::assertEquals(
+ $this->expected, $this->actual);
+ } else {
+ throw $e;
+ }
+ }
+ }
+
+ public function readUrl($property) {
+ if(!property_exists($this->data, $property)) {
+ return null;
+ }
+ return $this->manifest->data->baseIri . $this->data->{$property};
+ }
+
+ public function readProperty($property) {
+ $data = $this->data;
+ if(!property_exists($data, $property)) {
+ return null;
+ }
+ $filename = join(
+ DIRECTORY_SEPARATOR, array($this->dirname, $data->{$property}));
+ $extension = pathinfo($filename, PATHINFO_EXTENSION);
+ if($extension === 'jsonld') {
+ return Util::readJson($filename);
+ }
+ return Util::readFile($filename);
+ }
+
+ public function createOptions($opts=array()) {
+ $http_options = array(
+ 'contentType', 'httpLink', 'httpStatus', 'redirectTo');
+ $test_options = (property_exists($this->data, 'option') ?
+ $this->data->option : array());
+ $options = array();
+ foreach($test_options as $k => $v) {
+ if(!in_array($k, $http_options)) {
+ $options[$k] = $v;
+ }
+ }
+ $options['documentLoader'] = $this->createDocumentLoader();
+ $options = array_merge($options, $opts);
+ if(isset($options['expandContext'])) {
+ $filename = join(
+ DIRECTORY_SEPARATOR, array($this->dirname, $options['expandContext']));
+ $options['expandContext'] = Util::readJson($filename);
+ }
+ return $options;
+ }
+
+ public function createDocumentLoader() {
+ $base = 'http://json-ld.org/test-suite';
+ $test = $this;
+
+ $load_locally = function($url) use ($test, $base) {
+ $doc = (object)array(
+ 'contextUrl' => null, 'documentUrl' => $url, 'document' => null);
+ $options = (property_exists($test->data, 'option') ?
+ $test->data->option : null);
+ if($options and $url === $test->base) {
+ if(property_exists($options, 'redirectTo') &&
+ property_exists($options, 'httpStatus') &&
+ $options->httpStatus >= '300') {
+ $doc->documentUrl = ($test->manifest->data->baseIri .
+ $options->redirectTo);
+ } else if(property_exists($options, 'httpLink')) {
+ $content_type = (property_exists($options, 'contentType') ?
+ $options->contentType : null);
+ $extension = pathinfo($url, PATHINFO_EXTENSION);
+ if(!$content_type && $extension === 'jsonld') {
+ $content_type = 'application/ld+json';
+ }
+ $link_header = $options->httpLink;
+ if(is_array($link_header)) {
+ $link_header = join(',', $link_header);
+ }
+ $link_header = jsonld_parse_link_header($link_header);
+ if(isset($link_header['http://www.w3.org/ns/json-ld#context'])) {
+ $link_header = $link_header['http://www.w3.org/ns/json-ld#context'];
+ } else {
+ $link_header = null;
+ }
+ if($link_header && $content_type !== 'application/ld+json') {
+ if(is_array($link_header)) {
+ throw new Exception('multiple context link headers');
+ }
+ $doc->contextUrl = $link_header->target;
+ }
+ }
+ }
+ global $ROOT_MANIFEST_DIR;
+ if(strpos($doc->documentUrl, ':') === false) {
+ $filename = join(
+ DIRECTORY_SEPARATOR, array(
+ $ROOT_MANIFEST_DIR, $doc->documentUrl));
+ $doc->documentUrl = 'file://' . $filename;
+ } else {
+ $filename = join(
+ DIRECTORY_SEPARATOR, array(
+ $ROOT_MANIFEST_DIR, substr($doc->documentUrl, strlen($base))));
+ }
+ try {
+ $doc->document = Util::readJson($filename);
+ } catch(Exception $e) {
+ throw new Exception('loading document failed');
+ }
+ return $doc;
+ };
+
+ $local_loader = function($url) use ($test, $base, $load_locally) {
+ // always load remote-doc and non-base tests remotely
+ if((strpos($url, $base) !== 0 && strpos($url, ':') !== false) ||
+ $test->manifest->data->name === 'Remote document') {
+ return call_user_func('jsonld_default_document_loader', $url);
+ }
+
+ // attempt to load locally
+ return call_user_func($load_locally, $url);
+ };
+
+ return $local_loader;
+ }
+
+ public function getJsonLdErrorCode($err) {
+ if($err instanceof JsonLdException) {
+ if($err->getCode()) {
+ return $err->getCode();
+ }
+ if($err->cause) {
+ return $this->getJsonLdErrorCode($err->cause);
+ }
+ }
+ return $err->getMessage();
+ }
+}
+
+class JsonLdTestIterator implements Iterator {
+ /**
+ * The current test index.
+ */
+ protected $index = 0;
+
+ /**
+ * The total number of tests.
+ */
+ protected $count = 0;
+
+ /**
+ * Creates a TestIterator.
+ *
+ * @param string $type the type of tests to iterate over.
+ */
+ public function __construct($type) {
+ global $TESTS;
+ if(isset($TESTS[$type])) {
+ $this->tests = $TESTS[$type];
+ } else {
+ $this->tests = array();
+ }
+ $this->count = count($this->tests);
+ }
+
+ /**
+ * Gets the parameters for the next test.
+ *
+ * @return assoc the parameters for the next test.
+ */
+ public function current() {
+ return array('test' => $this->tests[$this->index]);
+ }
+
+ /**
+ * Gets the current test number.
+ *
+ * @return int the current test number.
+ */
+ public function key() {
+ return $this->index;
+ }
+
+ /**
+ * Proceeds to the next test.
+ */
+ public function next() {
+ $this->index += 1;
+ }
+
+ /**
+ * Rewinds to the first test.
+ */
+ public function rewind() {
+ $this->index = 0;
+ }
+
+ /**
+ * Returns true if there are more tests to be run.
+ *
+ * @return bool true if there are more tests to be run.
+ */
+ public function valid() {
+ return $this->index < $this->count;
+ }
+}
+
+class EarlReport extends PHPUnit_Util_Printer
+ implements PHPUnit_Framework_TestListener {
+ public function __construct() {
+ $this->filename = null;
+ $this->attached = false;
+ $this->report = (object)array(
+ '@context' => (object)array(
+ 'doap' => 'http://usefulinc.com/ns/doap#',
+ 'foaf' => 'http://xmlns.com/foaf/0.1/',
+ 'dc' => 'http://purl.org/dc/terms/',
+ 'earl' => 'http://www.w3.org/ns/earl#',
+ 'xsd' => 'http://www.w3.org/2001/XMLSchema#',
+ 'doap:homepage' => (object)array('@type' => '@id'),
+ 'doap:license' => (object)array('@type' => '@id'),
+ 'dc:creator' => (object)array('@type' => '@id'),
+ 'foaf:homepage' => (object)array('@type' => '@id'),
+ 'subjectOf' => (object)array('@reverse' => 'earl:subject'),
+ 'earl:assertedBy' => (object)array('@type' => '@id'),
+ 'earl:mode' => (object)array('@type' => '@id'),
+ 'earl:test' => (object)array('@type' => '@id'),
+ 'earl:outcome' => (object)array('@type' => '@id'),
+ 'dc:date' => (object)array('@type' => 'xsd:date')
+ ),
+ '@id' => 'https://github.com/digitalbazaar/php-json-ld',
+ '@type' => array('doap:Project', 'earl:TestSubject', 'earl:Software'),
+ 'doap:name' => 'php-json-ld',
+ 'dc:title' => 'php-json-ld',
+ 'doap:homepage' => 'https://github.com/digitalbazaar/php-json-ld',
+ 'doap:license' => 'https://github.com/digitalbazaar/php-json-ld/blob/master/LICENSE',
+ 'doap:description' => 'A JSON-LD processor for PHP',
+ 'doap:programming-language' => 'PHP',
+ 'dc:creator' => 'https://github.com/dlongley',
+ 'doap:developer' => (object)array(
+ '@id' => 'https://github.com/dlongley',
+ '@type' => array('foaf:Person', 'earl:Assertor'),
+ 'foaf:name' => 'Dave Longley',
+ 'foaf:homepage' => 'https://github.com/dlongley'
+ ),
+ 'dc:date' => array(
+ '@value' => gmdate('Y-m-d'),
+ '@type' => 'xsd:date'
+ ),
+ 'subjectOf' => array()
+ );
+ }
+
+ /**
+ * Attaches to the given test result, if not yet attached.
+ *
+ * @param PHPUnit_Framework_Test $result the result to attach to.
+ */
+ public function attach(PHPUnit_Framework_TestResult $result) {
+ if(!$this->attached && $this->filename) {
+ $this->attached = true;
+ $result->addListener($this);
+ }
+ }
+
+ /**
+ * Adds an assertion to this EARL report.
+ *
+ * @param JsonLdTest $test the JsonLdTest for the assertion is for.
+ * @param bool $passed whether or not the test passed.
+ */
+ public function addAssertion($test, $passed) {
+ $this->report->{'subjectOf'}[] = (object)array(
+ '@type' => 'earl:Assertion',
+ 'earl:assertedBy' => $this->report->{'doap:developer'}->{'@id'},
+ 'earl:mode' => 'earl:automatic',
+ 'earl:test' => $test->data->{'@id'},
+ 'earl:result' => (object)array(
+ '@type' => 'earl:TestResult',
+ 'dc:date' => gmdate(DateTime::ISO8601),
+ 'earl:outcome' => $passed ? 'earl:passed' : 'earl:failed'
+ )
+ );
+ return $this;
+ }
+
+ /**
+ * Writes this EARL report to a file.
+ */
+ public function flush() {
+ if($this->filename) {
+ printf("\nWriting EARL report to: %s\n", $this->filename);
+ $fd = fopen($this->filename, 'w');
+ fwrite($fd, Util::jsonldEncode($this->report));
+ fclose($fd);
+ }
+ }
+
+ public function endTest(PHPUnit_Framework_Test $test, $time) {
+ $this->addAssertion($test->test, true);
+ }
+
+ public function addError(
+ PHPUnit_Framework_Test $test, Exception $e, $time) {
+ $this->addAssertion($test->test, false);
+ }
+
+ public function addFailure(
+ PHPUnit_Framework_Test $test,
+ PHPUnit_Framework_AssertionFailedError $e, $time) {
+ $this->addAssertion($test->test, false);
+ if($test->result->shouldStop()) {
+ if(isset($test->test->name)) {
+ $name = $test->test->name;
+ } else if(isset($test->test->label)) {
+ $name = $test->test->label;
+ } else {
+ $name = 'UNNAMED';
+ }
+ printf("\n\nFAILED\n");
+ printf("Test: %s\n", $name);
+ printf("Purpose: %s\n", $test->test->data->purpose);
+ printf("EXPECTED: %s\n", Util::jsonldEncode($test->test->expected));
+ printf("ACTUAL: %s\n", Util::jsonldEncode($test->test->actual));
+ }
+ }
+
+ public function addIncompleteTest(
+ PHPUnit_Framework_Test $test, Exception $e, $time) {
+ $this->addAssertion($test->test, false);
+ }
+
+ public function addRiskyTest(
+ PHPUnit_Framework_Test $test, Exception $e, $time) {}
+ public function addSkippedTest(
+ PHPUnit_Framework_Test $test, Exception $e, $time) {}
+ public function startTest(PHPUnit_Framework_Test $test) {}
+ public function startTestSuite(PHPUnit_Framework_TestSuite $suite) {}
+ public function endTestSuite(PHPUnit_Framework_TestSuite $suite) {}
+}
+
+class Util {
+ public static function readFile($filename) {
+ $rval = @file_get_contents($filename);
+ if($rval === false) {
+ throw new Exception('File read error: ' . $filename);
+ }
+ return $rval;
+ }
+
+ public static function readJson($filename) {
+ $rval = json_decode(self::readFile($filename));
+ if($rval === null) {
+ throw new Exception('JSON parse error');
+ }
+ return $rval;
+ }
+
+ public static function readNQuads($filename) {
+ return self::readFile($filename);
+ }
+
+ public static function jsonldEncode($input) {
+ // newer PHP has a flag to avoid escaped '/'
+ if(defined('JSON_UNESCAPED_SLASHES')) {
+ $options = JSON_UNESCAPED_SLASHES;
+ if(defined('JSON_PRETTY_PRINT')) {
+ $options |= JSON_PRETTY_PRINT;
+ }
+ $json = json_encode($input, $options);
+ } else {
+ // use a simple string replacement of '\/' to '/'.
+ $json = str_replace('\\/', '/', json_encode($input));
+ }
+ return $json;
+ }
+}
+
+// tests to skip
+$SKIP_TESTS = array();
+
+// root manifest directory
+$ROOT_MANIFEST_DIR;
+
+// parsed tests; keyed by type
+$TESTS = array();
+
+// parsed command line options
+$OPTIONS = array();
+
+// parse command line options
+global $argv;
+$args = $argv;
+$total = count($args);
+$start = false;
+for($i = 0; $i < $total; ++$i) {
+ $arg = $args[$i];
+ if(!$start) {
+ if(realpath($arg) === realpath(__FILE__)) {
+ $start = true;
+ }
+ continue;
+ }
+ if($arg[0] !== '-') {
+ break;
+ }
+ $i += 1;
+ $OPTIONS[$arg] = $args[$i];
+}
+if(!isset($OPTIONS['-d'])) {
+ $dvar = 'path to json-ld.org/test-suite';
+ $evar = 'file to write EARL report to';
+ echo "php-json-ld Tests\n";
+ echo "Usage: phpunit test.php -d <$dvar> [-e <$evar>]\n\n";
+ exit(0);
+}
+
+// EARL Report
+$EARL = new EarlReport();
+if(isset($OPTIONS['-e'])) {
+ $EARL->filename = $OPTIONS['-e'];
+}
+
+// load root manifest
+$ROOT_MANIFEST_DIR = realpath($OPTIONS['-d']);
+$filename = join(
+ DIRECTORY_SEPARATOR, array($ROOT_MANIFEST_DIR, 'manifest.jsonld'));
+$root_manifest = Util::readJson($filename);
+$manifest = new JsonLdManifest($root_manifest, $filename);
+$manifest->load($TESTS);
+
+/* end of file, omit ?> */
diff --git a/library/markdown.php b/library/markdown.php
deleted file mode 100644
index 0e3275ff2..000000000
--- a/library/markdown.php
+++ /dev/null
@@ -1,2932 +0,0 @@
-<?php
-#
-# Markdown Extra - A text-to-HTML conversion tool for web writers
-#
-# PHP Markdown & Extra
-# Copyright (c) 2004-2012 Michel Fortin
-# <http://michelf.com/projects/php-markdown/>
-#
-# Original Markdown
-# Copyright (c) 2004-2006 John Gruber
-# <http://daringfireball.net/projects/markdown/>
-#
-
-
-define( 'MARKDOWN_VERSION', "1.0.1o" ); # Sun 8 Jan 2012
-define( 'MARKDOWNEXTRA_VERSION', "1.2.5" ); # Sun 8 Jan 2012
-
-
-#
-# Global default settings:
-#
-
-# Change to ">" for HTML output
-@define( 'MARKDOWN_EMPTY_ELEMENT_SUFFIX', " />");
-
-# Define the width of a tab for code blocks.
-@define( 'MARKDOWN_TAB_WIDTH', 4 );
-
-# Optional title attribute for footnote links and backlinks.
-@define( 'MARKDOWN_FN_LINK_TITLE', "" );
-@define( 'MARKDOWN_FN_BACKLINK_TITLE', "" );
-
-# Optional class attribute for footnote links and backlinks.
-@define( 'MARKDOWN_FN_LINK_CLASS', "" );
-@define( 'MARKDOWN_FN_BACKLINK_CLASS', "" );
-
-
-#
-# WordPress settings:
-#
-
-# Change to false to remove Markdown from posts and/or comments.
-@define( 'MARKDOWN_WP_POSTS', true );
-@define( 'MARKDOWN_WP_COMMENTS', true );
-
-
-
-### Standard Function Interface ###
-
-@define( 'MARKDOWN_PARSER_CLASS', 'MarkdownExtra_Parser' );
-
-function Markdown($text) {
-#
-# Initialize the parser and return the result of its transform method.
-#
- # Setup static parser variable.
- static $parser;
- if (!isset($parser)) {
- $parser_class = MARKDOWN_PARSER_CLASS;
- $parser = new $parser_class;
- }
-
- # Transform text using parser.
- return $parser->transform($text);
-}
-
-
-### WordPress Plugin Interface ###
-
-/*
-Plugin Name: Markdown Extra
-Plugin URI: http://michelf.com/projects/php-markdown/
-Description: <a href="http://daringfireball.net/projects/markdown/syntax">Markdown syntax</a> allows you to write using an easy-to-read, easy-to-write plain text format. Based on the original Perl version by <a href="http://daringfireball.net/">John Gruber</a>. <a href="http://michelf.com/projects/php-markdown/">More...</a>
-Version: 1.2.5
-Author: Michel Fortin
-Author URI: http://michelf.com/
-*/
-
-if (isset($wp_version)) {
- # More details about how it works here:
- # <http://michelf.com/weblog/2005/wordpress-text-flow-vs-markdown/>
-
- # Post content and excerpts
- # - Remove WordPress paragraph generator.
- # - Run Markdown on excerpt, then remove all tags.
- # - Add paragraph tag around the excerpt, but remove it for the excerpt rss.
- if (MARKDOWN_WP_POSTS) {
- remove_filter('the_content', 'wpautop');
- remove_filter('the_content_rss', 'wpautop');
- remove_filter('the_excerpt', 'wpautop');
- add_filter('the_content', 'mdwp_MarkdownPost', 6);
- add_filter('the_content_rss', 'mdwp_MarkdownPost', 6);
- add_filter('get_the_excerpt', 'mdwp_MarkdownPost', 6);
- add_filter('get_the_excerpt', 'trim', 7);
- add_filter('the_excerpt', 'mdwp_add_p');
- add_filter('the_excerpt_rss', 'mdwp_strip_p');
-
- remove_filter('content_save_pre', 'balanceTags', 50);
- remove_filter('excerpt_save_pre', 'balanceTags', 50);
- add_filter('the_content', 'balanceTags', 50);
- add_filter('get_the_excerpt', 'balanceTags', 9);
- }
-
- # Add a footnote id prefix to posts when inside a loop.
- function mdwp_MarkdownPost($text) {
- static $parser;
- if (!$parser) {
- $parser_class = MARKDOWN_PARSER_CLASS;
- $parser = new $parser_class;
- }
- if (is_single() || is_page() || is_feed()) {
- $parser->fn_id_prefix = "";
- } else {
- $parser->fn_id_prefix = get_the_ID() . ".";
- }
- return $parser->transform($text);
- }
-
- # Comments
- # - Remove WordPress paragraph generator.
- # - Remove WordPress auto-link generator.
- # - Scramble important tags before passing them to the kses filter.
- # - Run Markdown on excerpt then remove paragraph tags.
- if (MARKDOWN_WP_COMMENTS) {
- remove_filter('comment_text', 'wpautop', 30);
- remove_filter('comment_text', 'make_clickable');
- add_filter('pre_comment_content', 'Markdown', 6);
- add_filter('pre_comment_content', 'mdwp_hide_tags', 8);
- add_filter('pre_comment_content', 'mdwp_show_tags', 12);
- add_filter('get_comment_text', 'Markdown', 6);
- add_filter('get_comment_excerpt', 'Markdown', 6);
- add_filter('get_comment_excerpt', 'mdwp_strip_p', 7);
-
- global $mdwp_hidden_tags, $mdwp_placeholders;
- $mdwp_hidden_tags = explode(' ',
- '<p> </p> <pre> </pre> <ol> </ol> <ul> </ul> <li> </li>');
- $mdwp_placeholders = explode(' ', str_rot13(
- 'pEj07ZbbBZ U1kqgh4w4p pre2zmeN6K QTi31t9pre ol0MP1jzJR '.
- 'ML5IjmbRol ulANi1NsGY J7zRLJqPul liA8ctl16T K9nhooUHli'));
- }
-
- function mdwp_add_p($text) {
- if (!preg_match('{^$|^<(p|ul|ol|dl|pre|blockquote)>}i', $text)) {
- $text = '<p>'.$text.'</p>';
- $text = preg_replace('{\n{2,}}', "</p>\n\n<p>", $text);
- }
- return $text;
- }
-
- function mdwp_strip_p($t) { return preg_replace('{</?p>}i', '', $t); }
-
- function mdwp_hide_tags($text) {
- global $mdwp_hidden_tags, $mdwp_placeholders;
- return str_replace($mdwp_hidden_tags, $mdwp_placeholders, $text);
- }
- function mdwp_show_tags($text) {
- global $mdwp_hidden_tags, $mdwp_placeholders;
- return str_replace($mdwp_placeholders, $mdwp_hidden_tags, $text);
- }
-}
-
-
-### bBlog Plugin Info ###
-
-function identify_modifier_markdown() {
- return array(
- 'name' => 'markdown',
- 'type' => 'modifier',
- 'nicename' => 'PHP Markdown Extra',
- 'description' => 'A text-to-HTML conversion tool for web writers',
- 'authors' => 'Michel Fortin and John Gruber',
- 'licence' => 'GPL',
- 'version' => MARKDOWNEXTRA_VERSION,
- 'help' => '<a href="http://daringfireball.net/projects/markdown/syntax">Markdown syntax</a> allows you to write using an easy-to-read, easy-to-write plain text format. Based on the original Perl version by <a href="http://daringfireball.net/">John Gruber</a>. <a href="http://michelf.com/projects/php-markdown/">More...</a>',
- );
-}
-
-
-### Smarty Modifier Interface ###
-
-function smarty_modifier_markdown($text) {
- return Markdown($text);
-}
-
-
-### Textile Compatibility Mode ###
-
-# Rename this file to "classTextile.php" and it can replace Textile everywhere.
-
-if (strcasecmp(substr(__FILE__, -16), "classTextile.php") == 0) {
- # Try to include PHP SmartyPants. Should be in the same directory.
- @include_once 'smartypants.php';
- # Fake Textile class. It calls Markdown instead.
- class Textile {
- function TextileThis($text, $lite='', $encode='') {
- if ($lite == '' && $encode == '') $text = Markdown($text);
- if (function_exists('SmartyPants')) $text = SmartyPants($text);
- return $text;
- }
- # Fake restricted version: restrictions are not supported for now.
- function TextileRestricted($text, $lite='', $noimage='') {
- return $this->TextileThis($text, $lite);
- }
- # Workaround to ensure compatibility with TextPattern 4.0.3.
- function blockLite($text) { return $text; }
- }
-}
-
-
-
-#
-# Markdown Parser Class
-#
-
-class Markdown_Parser {
-
- # Regex to match balanced [brackets].
- # Needed to insert a maximum bracked depth while converting to PHP.
- var $nested_brackets_depth = 6;
- var $nested_brackets_re;
-
- var $nested_url_parenthesis_depth = 4;
- var $nested_url_parenthesis_re;
-
- # Table of hash values for escaped characters:
- var $escape_chars = '\`*_{}[]()>#+-.!';
- var $escape_chars_re;
-
- # Change to ">" for HTML output.
- var $empty_element_suffix = MARKDOWN_EMPTY_ELEMENT_SUFFIX;
- var $tab_width = MARKDOWN_TAB_WIDTH;
-
- # Change to `true` to disallow markup or entities.
- var $no_markup = false;
- var $no_entities = false;
-
- # Predefined urls and titles for reference links and images.
- var $predef_urls = array();
- var $predef_titles = array();
-
-
- function Markdown_Parser() {
- #
- # Constructor function. Initialize appropriate member variables.
- #
- $this->_initDetab();
- $this->prepareItalicsAndBold();
-
- $this->nested_brackets_re =
- str_repeat('(?>[^\[\]]+|\[', $this->nested_brackets_depth).
- str_repeat('\])*', $this->nested_brackets_depth);
-
- $this->nested_url_parenthesis_re =
- str_repeat('(?>[^()\s]+|\(', $this->nested_url_parenthesis_depth).
- str_repeat('(?>\)))*', $this->nested_url_parenthesis_depth);
-
- $this->escape_chars_re = '['.preg_quote($this->escape_chars).']';
-
- # Sort document, block, and span gamut in ascendent priority order.
- asort($this->document_gamut);
- asort($this->block_gamut);
- asort($this->span_gamut);
- }
-
-
- # Internal hashes used during transformation.
- var $urls = array();
- var $titles = array();
- var $html_hashes = array();
-
- # Status flag to avoid invalid nesting.
- var $in_anchor = false;
-
-
- function setup() {
- #
- # Called before the transformation process starts to setup parser
- # states.
- #
- # Clear global hashes.
- $this->urls = $this->predef_urls;
- $this->titles = $this->predef_titles;
- $this->html_hashes = array();
-
- $in_anchor = false;
- }
-
- function teardown() {
- #
- # Called after the transformation process to clear any variable
- # which may be taking up memory unnecessarly.
- #
- $this->urls = array();
- $this->titles = array();
- $this->html_hashes = array();
- }
-
-
- function transform($text) {
- #
- # Main function. Performs some preprocessing on the input text
- # and pass it through the document gamut.
- #
- $this->setup();
-
- # Remove UTF-8 BOM and marker character in input, if present.
- $text = preg_replace('{^\xEF\xBB\xBF|\x1A}', '', $text);
-
- # Standardize line endings:
- # DOS to Unix and Mac to Unix
- $text = preg_replace('{\r\n?}', "\n", $text);
-
- # Make sure $text ends with a couple of newlines:
- $text .= "\n\n";
-
- # Convert all tabs to spaces.
- $text = $this->detab($text);
-
- # Turn block-level HTML blocks into hash entries
- $text = $this->hashHTMLBlocks($text);
-
- # Strip any lines consisting only of spaces and tabs.
- # This makes subsequent regexen easier to write, because we can
- # match consecutive blank lines with /\n+/ instead of something
- # contorted like /[ ]*\n+/ .
- $text = preg_replace('/^[ ]+$/m', '', $text);
-
- # Run document gamut methods.
- foreach ($this->document_gamut as $method => $priority) {
- $text = $this->$method($text);
- }
-
- $this->teardown();
-
- return $text . "\n";
- }
-
- var $document_gamut = array(
- # Strip link definitions, store in hashes.
- "stripLinkDefinitions" => 20,
-
- "runBasicBlockGamut" => 30,
- );
-
-
- function stripLinkDefinitions($text) {
- #
- # Strips link definitions from text, stores the URLs and titles in
- # hash references.
- #
- $less_than_tab = $this->tab_width - 1;
-
- # Link defs are in the form: ^[id]: url "optional title"
- $text = preg_replace_callback('{
- ^[ ]{0,'.$less_than_tab.'}\[(.+)\][ ]?: # id = $1
- [ ]*
- \n? # maybe *one* newline
- [ ]*
- (?:
- <(.+?)> # url = $2
- |
- (\S+?) # url = $3
- )
- [ ]*
- \n? # maybe one newline
- [ ]*
- (?:
- (?<=\s) # lookbehind for whitespace
- ["(]
- (.*?) # title = $4
- [")]
- [ ]*
- )? # title is optional
- (?:\n+|\Z)
- }xm',
- array(&$this, '_stripLinkDefinitions_callback'),
- $text);
- return $text;
- }
- function _stripLinkDefinitions_callback($matches) {
- $link_id = strtolower($matches[1]);
- $url = $matches[2] == '' ? $matches[3] : $matches[2];
- $this->urls[$link_id] = $url;
- $this->titles[$link_id] =& $matches[4];
- return ''; # String that will replace the block
- }
-
-
- function hashHTMLBlocks($text) {
- if ($this->no_markup) return $text;
-
- $less_than_tab = $this->tab_width - 1;
-
- # Hashify HTML blocks:
- # We only want to do this for block-level HTML tags, such as headers,
- # lists, and tables. That's because we still want to wrap <p>s around
- # "paragraphs" that are wrapped in non-block-level tags, such as anchors,
- # phrase emphasis, and spans. The list of tags we're looking for is
- # hard-coded:
- #
- # * List "a" is made of tags which can be both inline or block-level.
- # These will be treated block-level when the start tag is alone on
- # its line, otherwise they're not matched here and will be taken as
- # inline later.
- # * List "b" is made of tags which are always block-level;
- #
- $block_tags_a_re = 'ins|del';
- $block_tags_b_re = 'p|div|h[1-6]|blockquote|pre|table|dl|ol|ul|address|'.
- 'script|noscript|form|fieldset|iframe|math';
-
- # Regular expression for the content of a block tag.
- $nested_tags_level = 4;
- $attr = '
- (?> # optional tag attributes
- \s # starts with whitespace
- (?>
- [^>"/]+ # text outside quotes
- |
- /+(?!>) # slash not followed by ">"
- |
- "[^"]*" # text inside double quotes (tolerate ">")
- |
- \'[^\']*\' # text inside single quotes (tolerate ">")
- )*
- )?
- ';
- $content =
- str_repeat('
- (?>
- [^<]+ # content without tag
- |
- <\2 # nested opening tag
- '.$attr.' # attributes
- (?>
- />
- |
- >', $nested_tags_level). # end of opening tag
- '.*?'. # last level nested tag content
- str_repeat('
- </\2\s*> # closing nested tag
- )
- |
- <(?!/\2\s*> # other tags with a different name
- )
- )*',
- $nested_tags_level);
- $content2 = str_replace('\2', '\3', $content);
-
- # First, look for nested blocks, e.g.:
- # <div>
- # <div>
- # tags for inner block must be indented.
- # </div>
- # </div>
- #
- # The outermost tags must start at the left margin for this to match, and
- # the inner nested divs must be indented.
- # We need to do this before the next, more liberal match, because the next
- # match will start at the first `<div>` and stop at the first `</div>`.
- $text = preg_replace_callback('{(?>
- (?>
- (?<=\n\n) # Starting after a blank line
- | # or
- \A\n? # the beginning of the doc
- )
- ( # save in $1
-
- # Match from `\n<tag>` to `</tag>\n`, handling nested tags
- # in between.
-
- [ ]{0,'.$less_than_tab.'}
- <('.$block_tags_b_re.')# start tag = $2
- '.$attr.'> # attributes followed by > and \n
- '.$content.' # content, support nesting
- </\2> # the matching end tag
- [ ]* # trailing spaces/tabs
- (?=\n+|\Z) # followed by a newline or end of document
-
- | # Special version for tags of group a.
-
- [ ]{0,'.$less_than_tab.'}
- <('.$block_tags_a_re.')# start tag = $3
- '.$attr.'>[ ]*\n # attributes followed by >
- '.$content2.' # content, support nesting
- </\3> # the matching end tag
- [ ]* # trailing spaces/tabs
- (?=\n+|\Z) # followed by a newline or end of document
-
- | # Special case just for <hr />. It was easier to make a special
- # case than to make the other regex more complicated.
-
- [ ]{0,'.$less_than_tab.'}
- <(hr) # start tag = $2
- '.$attr.' # attributes
- /?> # the matching end tag
- [ ]*
- (?=\n{2,}|\Z) # followed by a blank line or end of document
-
- | # Special case for standalone HTML comments:
-
- [ ]{0,'.$less_than_tab.'}
- (?s:
- <!-- .*? -->
- )
- [ ]*
- (?=\n{2,}|\Z) # followed by a blank line or end of document
-
- | # PHP and ASP-style processor instructions (<? and <%)
-
- [ ]{0,'.$less_than_tab.'}
- (?s:
- <([?%]) # $2
- .*?
- \2>
- )
- [ ]*
- (?=\n{2,}|\Z) # followed by a blank line or end of document
-
- )
- )}Sxmi',
- array(&$this, '_hashHTMLBlocks_callback'),
- $text);
-
- return $text;
- }
- function _hashHTMLBlocks_callback($matches) {
- $text = $matches[1];
- $key = $this->hashBlock($text);
- return "\n\n$key\n\n";
- }
-
-
- function hashPart($text, $boundary = 'X') {
- #
- # Called whenever a tag must be hashed when a function insert an atomic
- # element in the text stream. Passing $text to through this function gives
- # a unique text-token which will be reverted back when calling unhash.
- #
- # The $boundary argument specify what character should be used to surround
- # the token. By convension, "B" is used for block elements that needs not
- # to be wrapped into paragraph tags at the end, ":" is used for elements
- # that are word separators and "X" is used in the general case.
- #
- # Swap back any tag hash found in $text so we do not have to `unhash`
- # multiple times at the end.
- $text = $this->unhash($text);
-
- # Then hash the block.
- static $i = 0;
- $key = "$boundary\x1A" . ++$i . $boundary;
- $this->html_hashes[$key] = $text;
- return $key; # String that will replace the tag.
- }
-
-
- function hashBlock($text) {
- #
- # Shortcut function for hashPart with block-level boundaries.
- #
- return $this->hashPart($text, 'B');
- }
-
-
- var $block_gamut = array(
- #
- # These are all the transformations that form block-level
- # tags like paragraphs, headers, and list items.
- #
- "doHeaders" => 10,
- "doHorizontalRules" => 20,
-
- "doLists" => 40,
- "doCodeBlocks" => 50,
- "doBlockQuotes" => 60,
- );
-
- function runBlockGamut($text) {
- #
- # Run block gamut tranformations.
- #
- # We need to escape raw HTML in Markdown source before doing anything
- # else. This need to be done for each block, and not only at the
- # begining in the Markdown function since hashed blocks can be part of
- # list items and could have been indented. Indented blocks would have
- # been seen as a code block in a previous pass of hashHTMLBlocks.
- $text = $this->hashHTMLBlocks($text);
-
- return $this->runBasicBlockGamut($text);
- }
-
- function runBasicBlockGamut($text) {
- #
- # Run block gamut tranformations, without hashing HTML blocks. This is
- # useful when HTML blocks are known to be already hashed, like in the first
- # whole-document pass.
- #
- foreach ($this->block_gamut as $method => $priority) {
- $text = $this->$method($text);
- }
-
- # Finally form paragraph and restore hashed blocks.
- $text = $this->formParagraphs($text);
-
- return $text;
- }
-
-
- function doHorizontalRules($text) {
- # Do Horizontal Rules:
- return preg_replace(
- '{
- ^[ ]{0,3} # Leading space
- ([-*_]) # $1: First marker
- (?> # Repeated marker group
- [ ]{0,2} # Zero, one, or two spaces.
- \1 # Marker character
- ){2,} # Group repeated at least twice
- [ ]* # Tailing spaces
- $ # End of line.
- }mx',
- "\n".$this->hashBlock("<hr$this->empty_element_suffix")."\n",
- $text);
- }
-
-
- var $span_gamut = array(
- #
- # These are all the transformations that occur *within* block-level
- # tags like paragraphs, headers, and list items.
- #
- # Process character escapes, code spans, and inline HTML
- # in one shot.
- "parseSpan" => -30,
-
- # Process anchor and image tags. Images must come first,
- # because ![foo][f] looks like an anchor.
- "doImages" => 10,
- "doAnchors" => 20,
-
- # Make links out of things like `<http://example.com/>`
- # Must come after doAnchors, because you can use < and >
- # delimiters in inline links like [this](<url>).
- "doAutoLinks" => 30,
- "encodeAmpsAndAngles" => 40,
-
- "doItalicsAndBold" => 50,
- "doHardBreaks" => 60,
- );
-
- function runSpanGamut($text) {
- #
- # Run span gamut tranformations.
- #
- foreach ($this->span_gamut as $method => $priority) {
- $text = $this->$method($text);
- }
-
- return $text;
- }
-
-
- function doHardBreaks($text) {
- # Do hard breaks:
- return preg_replace_callback('/ {2,}\n/',
- array(&$this, '_doHardBreaks_callback'), $text);
- }
- function _doHardBreaks_callback($matches) {
- return $this->hashPart("<br$this->empty_element_suffix\n");
- }
-
-
- function doAnchors($text) {
- #
- # Turn Markdown link shortcuts into XHTML <a> tags.
- #
- if ($this->in_anchor) return $text;
- $this->in_anchor = true;
-
- #
- # First, handle reference-style links: [link text] [id]
- #
- $text = preg_replace_callback('{
- ( # wrap whole match in $1
- \[
- ('.$this->nested_brackets_re.') # link text = $2
- \]
-
- [ ]? # one optional space
- (?:\n[ ]*)? # one optional newline followed by spaces
-
- \[
- (.*?) # id = $3
- \]
- )
- }xs',
- array(&$this, '_doAnchors_reference_callback'), $text);
-
- #
- # Next, inline-style links: [link text](url "optional title")
- #
- $text = preg_replace_callback('{
- ( # wrap whole match in $1
- \[
- ('.$this->nested_brackets_re.') # link text = $2
- \]
- \( # literal paren
- [ \n]*
- (?:
- <(.+?)> # href = $3
- |
- ('.$this->nested_url_parenthesis_re.') # href = $4
- )
- [ \n]*
- ( # $5
- ([\'"]) # quote char = $6
- (.*?) # Title = $7
- \6 # matching quote
- [ \n]* # ignore any spaces/tabs between closing quote and )
- )? # title is optional
- \)
- )
- }xs',
- array(&$this, '_doAnchors_inline_callback'), $text);
-
- #
- # Last, handle reference-style shortcuts: [link text]
- # These must come last in case you've also got [link text][1]
- # or [link text](/foo)
- #
- $text = preg_replace_callback('{
- ( # wrap whole match in $1
- \[
- ([^\[\]]+) # link text = $2; can\'t contain [ or ]
- \]
- )
- }xs',
- array(&$this, '_doAnchors_reference_callback'), $text);
-
- $this->in_anchor = false;
- return $text;
- }
- function _doAnchors_reference_callback($matches) {
- $whole_match = $matches[1];
- $link_text = $matches[2];
- $link_id =& $matches[3];
-
- if ($link_id == "") {
- # for shortcut links like [this][] or [this].
- $link_id = $link_text;
- }
-
- # lower-case and turn embedded newlines into spaces
- $link_id = strtolower($link_id);
- $link_id = preg_replace('{[ ]?\n}', ' ', $link_id);
-
- if (isset($this->urls[$link_id])) {
- $url = $this->urls[$link_id];
- $url = $this->encodeAttribute($url);
-
- $result = "<a href=\"$url\"";
- if ( isset( $this->titles[$link_id] ) ) {
- $title = $this->titles[$link_id];
- $title = $this->encodeAttribute($title);
- $result .= " title=\"$title\"";
- }
-
- $link_text = $this->runSpanGamut($link_text);
- $result .= ">$link_text</a>";
- $result = $this->hashPart($result);
- }
- else {
- $result = $whole_match;
- }
- return $result;
- }
- function _doAnchors_inline_callback($matches) {
- $whole_match = $matches[1];
- $link_text = $this->runSpanGamut($matches[2]);
- $url = $matches[3] == '' ? $matches[4] : $matches[3];
- $title =& $matches[7];
-
- $url = $this->encodeAttribute($url);
-
- $result = "<a href=\"$url\"";
- if (isset($title)) {
- $title = $this->encodeAttribute($title);
- $result .= " title=\"$title\"";
- }
-
- $link_text = $this->runSpanGamut($link_text);
- $result .= ">$link_text</a>";
-
- return $this->hashPart($result);
- }
-
-
- function doImages($text) {
- #
- # Turn Markdown image shortcuts into <img> tags.
- #
- #
- # First, handle reference-style labeled images: ![alt text][id]
- #
- $text = preg_replace_callback('{
- ( # wrap whole match in $1
- !\[
- ('.$this->nested_brackets_re.') # alt text = $2
- \]
-
- [ ]? # one optional space
- (?:\n[ ]*)? # one optional newline followed by spaces
-
- \[
- (.*?) # id = $3
- \]
-
- )
- }xs',
- array(&$this, '_doImages_reference_callback'), $text);
-
- #
- # Next, handle inline images: ![alt text](url "optional title")
- # Don't forget: encode * and _
- #
- $text = preg_replace_callback('{
- ( # wrap whole match in $1
- !\[
- ('.$this->nested_brackets_re.') # alt text = $2
- \]
- \s? # One optional whitespace character
- \( # literal paren
- [ \n]*
- (?:
- <(\S*)> # src url = $3
- |
- ('.$this->nested_url_parenthesis_re.') # src url = $4
- )
- [ \n]*
- ( # $5
- ([\'"]) # quote char = $6
- (.*?) # title = $7
- \6 # matching quote
- [ \n]*
- )? # title is optional
- \)
- )
- }xs',
- array(&$this, '_doImages_inline_callback'), $text);
-
- return $text;
- }
- function _doImages_reference_callback($matches) {
- $whole_match = $matches[1];
- $alt_text = $matches[2];
- $link_id = strtolower($matches[3]);
-
- if ($link_id == "") {
- $link_id = strtolower($alt_text); # for shortcut links like ![this][].
- }
-
- $alt_text = $this->encodeAttribute($alt_text);
- if (isset($this->urls[$link_id])) {
- $url = $this->encodeAttribute($this->urls[$link_id]);
- $result = "<img src=\"$url\" alt=\"$alt_text\"";
- if (isset($this->titles[$link_id])) {
- $title = $this->titles[$link_id];
- $title = $this->encodeAttribute($title);
- $result .= " title=\"$title\"";
- }
- $result .= $this->empty_element_suffix;
- $result = $this->hashPart($result);
- }
- else {
- # If there's no such link ID, leave intact:
- $result = $whole_match;
- }
-
- return $result;
- }
- function _doImages_inline_callback($matches) {
- $whole_match = $matches[1];
- $alt_text = $matches[2];
- $url = $matches[3] == '' ? $matches[4] : $matches[3];
- $title =& $matches[7];
-
- $alt_text = $this->encodeAttribute($alt_text);
- $url = $this->encodeAttribute($url);
- $result = "<img src=\"$url\" alt=\"$alt_text\"";
- if (isset($title)) {
- $title = $this->encodeAttribute($title);
- $result .= " title=\"$title\""; # $title already quoted
- }
- $result .= $this->empty_element_suffix;
-
- return $this->hashPart($result);
- }
-
-
- function doHeaders($text) {
- # Setext-style headers:
- # Header 1
- # ========
- #
- # Header 2
- # --------
- #
- $text = preg_replace_callback('{ ^(.+?)[ ]*\n(=+|-+)[ ]*\n+ }mx',
- array(&$this, '_doHeaders_callback_setext'), $text);
-
- # atx-style headers:
- # # Header 1
- # ## Header 2
- # ## Header 2 with closing hashes ##
- # ...
- # ###### Header 6
- #
- $text = preg_replace_callback('{
- ^(\#{1,6}) # $1 = string of #\'s
- [ ]*
- (.+?) # $2 = Header text
- [ ]*
- \#* # optional closing #\'s (not counted)
- \n+
- }xm',
- array(&$this, '_doHeaders_callback_atx'), $text);
-
- return $text;
- }
- function _doHeaders_callback_setext($matches) {
- # Terrible hack to check we haven't found an empty list item.
- if ($matches[2] == '-' && preg_match('{^-(?: |$)}', $matches[1]))
- return $matches[0];
-
- $level = $matches[2]{0} == '=' ? 1 : 2;
- $block = "<h$level>".$this->runSpanGamut($matches[1])."</h$level>";
- return "\n" . $this->hashBlock($block) . "\n\n";
- }
- function _doHeaders_callback_atx($matches) {
- $level = strlen($matches[1]);
- $block = "<h$level>".$this->runSpanGamut($matches[2])."</h$level>";
- return "\n" . $this->hashBlock($block) . "\n\n";
- }
-
-
- function doLists($text) {
- #
- # Form HTML ordered (numbered) and unordered (bulleted) lists.
- #
- $less_than_tab = $this->tab_width - 1;
-
- # Re-usable patterns to match list item bullets and number markers:
- $marker_ul_re = '[*+-]';
- $marker_ol_re = '\d+[\.]';
- $marker_any_re = "(?:$marker_ul_re|$marker_ol_re)";
-
- $markers_relist = array(
- $marker_ul_re => $marker_ol_re,
- $marker_ol_re => $marker_ul_re,
- );
-
- foreach ($markers_relist as $marker_re => $other_marker_re) {
- # Re-usable pattern to match any entirel ul or ol list:
- $whole_list_re = '
- ( # $1 = whole list
- ( # $2
- ([ ]{0,'.$less_than_tab.'}) # $3 = number of spaces
- ('.$marker_re.') # $4 = first list item marker
- [ ]+
- )
- (?s:.+?)
- ( # $5
- \z
- |
- \n{2,}
- (?=\S)
- (?! # Negative lookahead for another list item marker
- [ ]*
- '.$marker_re.'[ ]+
- )
- |
- (?= # Lookahead for another kind of list
- \n
- \3 # Must have the same indentation
- '.$other_marker_re.'[ ]+
- )
- )
- )
- '; // mx
-
- # We use a different prefix before nested lists than top-level lists.
- # See extended comment in _ProcessListItems().
-
- if ($this->list_level) {
- $text = preg_replace_callback('{
- ^
- '.$whole_list_re.'
- }mx',
- array(&$this, '_doLists_callback'), $text);
- }
- else {
- $text = preg_replace_callback('{
- (?:(?<=\n)\n|\A\n?) # Must eat the newline
- '.$whole_list_re.'
- }mx',
- array(&$this, '_doLists_callback'), $text);
- }
- }
-
- return $text;
- }
- function _doLists_callback($matches) {
- # Re-usable patterns to match list item bullets and number markers:
- $marker_ul_re = '[*+-]';
- $marker_ol_re = '\d+[\.]';
- $marker_any_re = "(?:$marker_ul_re|$marker_ol_re)";
-
- $list = $matches[1];
- $list_type = preg_match("/$marker_ul_re/", $matches[4]) ? "ul" : "ol";
-
- $marker_any_re = ( $list_type == "ul" ? $marker_ul_re : $marker_ol_re );
-
- $list .= "\n";
- $result = $this->processListItems($list, $marker_any_re);
-
- $result = $this->hashBlock("<$list_type>\n" . $result . "</$list_type>");
- return "\n". $result ."\n\n";
- }
-
- var $list_level = 0;
-
- function processListItems($list_str, $marker_any_re) {
- #
- # Process the contents of a single ordered or unordered list, splitting it
- # into individual list items.
- #
- # The $this->list_level global keeps track of when we're inside a list.
- # Each time we enter a list, we increment it; when we leave a list,
- # we decrement. If it's zero, we're not in a list anymore.
- #
- # We do this because when we're not inside a list, we want to treat
- # something like this:
- #
- # I recommend upgrading to version
- # 8. Oops, now this line is treated
- # as a sub-list.
- #
- # As a single paragraph, despite the fact that the second line starts
- # with a digit-period-space sequence.
- #
- # Whereas when we're inside a list (or sub-list), that line will be
- # treated as the start of a sub-list. What a kludge, huh? This is
- # an aspect of Markdown's syntax that's hard to parse perfectly
- # without resorting to mind-reading. Perhaps the solution is to
- # change the syntax rules such that sub-lists must start with a
- # starting cardinal number; e.g. "1." or "a.".
-
- $this->list_level++;
-
- # trim trailing blank lines:
- $list_str = preg_replace("/\n{2,}\\z/", "\n", $list_str);
-
- $list_str = preg_replace_callback('{
- (\n)? # leading line = $1
- (^[ ]*) # leading whitespace = $2
- ('.$marker_any_re.' # list marker and space = $3
- (?:[ ]+|(?=\n)) # space only required if item is not empty
- )
- ((?s:.*?)) # list item text = $4
- (?:(\n+(?=\n))|\n) # tailing blank line = $5
- (?= \n* (\z | \2 ('.$marker_any_re.') (?:[ ]+|(?=\n))))
- }xm',
- array(&$this, '_processListItems_callback'), $list_str);
-
- $this->list_level--;
- return $list_str;
- }
- function _processListItems_callback($matches) {
- $item = $matches[4];
- $leading_line =& $matches[1];
- $leading_space =& $matches[2];
- $marker_space = $matches[3];
- $tailing_blank_line =& $matches[5];
-
- if ($leading_line || $tailing_blank_line ||
- preg_match('/\n{2,}/', $item))
- {
- # Replace marker with the appropriate whitespace indentation
- $item = $leading_space . str_repeat(' ', strlen($marker_space)) . $item;
- $item = $this->runBlockGamut($this->outdent($item)."\n");
- }
- else {
- # Recursion for sub-lists:
- $item = $this->doLists($this->outdent($item));
- $item = preg_replace('/\n+$/', '', $item);
- $item = $this->runSpanGamut($item);
- }
-
- return "<li>" . $item . "</li>\n";
- }
-
-
- function doCodeBlocks($text) {
- #
- # Process Markdown `<pre><code>` blocks.
- #
- $text = preg_replace_callback('{
- (?:\n\n|\A\n?)
- ( # $1 = the code block -- one or more lines, starting with a space/tab
- (?>
- [ ]{'.$this->tab_width.'} # Lines must start with a tab or a tab-width of spaces
- .*\n+
- )+
- )
- ((?=^[ ]{0,'.$this->tab_width.'}\S)|\Z) # Lookahead for non-space at line-start, or end of doc
- }xm',
- array(&$this, '_doCodeBlocks_callback'), $text);
-
- return $text;
- }
- function _doCodeBlocks_callback($matches) {
- $codeblock = $matches[1];
-
- $codeblock = $this->outdent($codeblock);
- $codeblock = htmlspecialchars($codeblock, ENT_NOQUOTES);
-
- # trim leading newlines and trailing newlines
- $codeblock = preg_replace('/\A\n+|\n+\z/', '', $codeblock);
-
- $codeblock = "<pre><code>$codeblock\n</code></pre>";
- return "\n\n".$this->hashBlock($codeblock)."\n\n";
- }
-
-
- function makeCodeSpan($code) {
- #
- # Create a code span markup for $code. Called from handleSpanToken.
- #
- $code = htmlspecialchars(trim($code), ENT_NOQUOTES);
- return $this->hashPart("<code class=\"inline-code\">$code</code>");
- }
-
-
- var $em_relist = array(
- '' => '(?:(?<!\*)\*(?!\*)|(?<!_)_(?!_))(?=\S|$)(?![\.,:;]\s)',
- '*' => '(?<=\S|^)(?<!\*)\*(?!\*)',
- '_' => '(?<=\S|^)(?<!_)_(?!_)',
- );
- var $strong_relist = array(
- '' => '(?:(?<!\*)\*\*(?!\*)|(?<!_)__(?!_))(?=\S|$)(?![\.,:;]\s)',
- '**' => '(?<=\S|^)(?<!\*)\*\*(?!\*)',
- '__' => '(?<=\S|^)(?<!_)__(?!_)',
- );
- var $em_strong_relist = array(
- '' => '(?:(?<!\*)\*\*\*(?!\*)|(?<!_)___(?!_))(?=\S|$)(?![\.,:;]\s)',
- '***' => '(?<=\S|^)(?<!\*)\*\*\*(?!\*)',
- '___' => '(?<=\S|^)(?<!_)___(?!_)',
- );
- var $em_strong_prepared_relist;
-
- function prepareItalicsAndBold() {
- #
- # Prepare regular expressions for searching emphasis tokens in any
- # context.
- #
- foreach ($this->em_relist as $em => $em_re) {
- foreach ($this->strong_relist as $strong => $strong_re) {
- # Construct list of allowed token expressions.
- $token_relist = array();
- if (isset($this->em_strong_relist["$em$strong"])) {
- $token_relist[] = $this->em_strong_relist["$em$strong"];
- }
- $token_relist[] = $em_re;
- $token_relist[] = $strong_re;
-
- # Construct master expression from list.
- $token_re = '{('. implode('|', $token_relist) .')}';
- $this->em_strong_prepared_relist["$em$strong"] = $token_re;
- }
- }
- }
-
- function doItalicsAndBold($text) {
- $token_stack = array('');
- $text_stack = array('');
- $em = '';
- $strong = '';
- $tree_char_em = false;
-
- while (1) {
- #
- # Get prepared regular expression for seraching emphasis tokens
- # in current context.
- #
- $token_re = $this->em_strong_prepared_relist["$em$strong"];
-
- #
- # Each loop iteration search for the next emphasis token.
- # Each token is then passed to handleSpanToken.
- #
- $parts = preg_split($token_re, $text, 2, PREG_SPLIT_DELIM_CAPTURE);
- $text_stack[0] .= $parts[0];
- $token =& $parts[1];
- $text =& $parts[2];
-
- if (empty($token)) {
- # Reached end of text span: empty stack without emitting.
- # any more emphasis.
- while ($token_stack[0]) {
- $text_stack[1] .= array_shift($token_stack);
- $text_stack[0] .= array_shift($text_stack);
- }
- break;
- }
-
- $token_len = strlen($token);
- if ($tree_char_em) {
- # Reached closing marker while inside a three-char emphasis.
- if ($token_len == 3) {
- # Three-char closing marker, close em and strong.
- array_shift($token_stack);
- $span = array_shift($text_stack);
- $span = $this->runSpanGamut($span);
- $span = "<strong><em>$span</em></strong>";
- $text_stack[0] .= $this->hashPart($span);
- $em = '';
- $strong = '';
- } else {
- # Other closing marker: close one em or strong and
- # change current token state to match the other
- $token_stack[0] = str_repeat($token{0}, 3-$token_len);
- $tag = $token_len == 2 ? "strong" : "em";
- $span = $text_stack[0];
- $span = $this->runSpanGamut($span);
- $span = "<$tag>$span</$tag>";
- $text_stack[0] = $this->hashPart($span);
- $$tag = ''; # $$tag stands for $em or $strong
- }
- $tree_char_em = false;
- } else if ($token_len == 3) {
- if ($em) {
- # Reached closing marker for both em and strong.
- # Closing strong marker:
- for ($i = 0; $i < 2; ++$i) {
- $shifted_token = array_shift($token_stack);
- $tag = strlen($shifted_token) == 2 ? "strong" : "em";
- $span = array_shift($text_stack);
- $span = $this->runSpanGamut($span);
- $span = "<$tag>$span</$tag>";
- $text_stack[0] .= $this->hashPart($span);
- $$tag = ''; # $$tag stands for $em or $strong
- }
- } else {
- # Reached opening three-char emphasis marker. Push on token
- # stack; will be handled by the special condition above.
- $em = $token{0};
- $strong = "$em$em";
- array_unshift($token_stack, $token);
- array_unshift($text_stack, '');
- $tree_char_em = true;
- }
- } else if ($token_len == 2) {
- if ($strong) {
- # Unwind any dangling emphasis marker:
- if (strlen($token_stack[0]) == 1) {
- $text_stack[1] .= array_shift($token_stack);
- $text_stack[0] .= array_shift($text_stack);
- }
- # Closing strong marker:
- array_shift($token_stack);
- $span = array_shift($text_stack);
- $span = $this->runSpanGamut($span);
- $span = "<strong>$span</strong>";
- $text_stack[0] .= $this->hashPart($span);
- $strong = '';
- } else {
- array_unshift($token_stack, $token);
- array_unshift($text_stack, '');
- $strong = $token;
- }
- } else {
- # Here $token_len == 1
- if ($em) {
- if (strlen($token_stack[0]) == 1) {
- # Closing emphasis marker:
- array_shift($token_stack);
- $span = array_shift($text_stack);
- $span = $this->runSpanGamut($span);
- $span = "<em>$span</em>";
- $text_stack[0] .= $this->hashPart($span);
- $em = '';
- } else {
- $text_stack[0] .= $token;
- }
- } else {
- array_unshift($token_stack, $token);
- array_unshift($text_stack, '');
- $em = $token;
- }
- }
- }
- return $text_stack[0];
- }
-
-
- function doBlockQuotes($text) {
- $text = preg_replace_callback('/
- ( # Wrap whole match in $1
- (?>
- ^[ ]*>[ ]? # ">" at the start of a line
- .+\n # rest of the first line
- (.+\n)* # subsequent consecutive lines
- \n* # blanks
- )+
- )
- /xm',
- array(&$this, '_doBlockQuotes_callback'), $text);
-
- return $text;
- }
- function _doBlockQuotes_callback($matches) {
- $bq = $matches[1];
- # trim one level of quoting - trim whitespace-only lines
- $bq = preg_replace('/^[ ]*>[ ]?|^[ ]+$/m', '', $bq);
- $bq = $this->runBlockGamut($bq); # recurse
-
- $bq = preg_replace('/^/m', " ", $bq);
- # These leading spaces cause problem with <pre> content,
- # so we need to fix that:
- $bq = preg_replace_callback('{(\s*<pre>.+?</pre>)}sx',
- array(&$this, '_doBlockQuotes_callback2'), $bq);
-
- return "\n". $this->hashBlock("<blockquote>\n$bq\n</blockquote>")."\n\n";
- }
- function _doBlockQuotes_callback2($matches) {
- $pre = $matches[1];
- $pre = preg_replace('/^ /m', '', $pre);
- return $pre;
- }
-
-
- function formParagraphs($text) {
- #
- # Params:
- # $text - string to process with html <p> tags
- #
- # Strip leading and trailing lines:
- $text = preg_replace('/\A\n+|\n+\z/', '', $text);
-
- $grafs = preg_split('/\n{2,}/', $text, -1, PREG_SPLIT_NO_EMPTY);
-
- #
- # Wrap <p> tags and unhashify HTML blocks
- #
- foreach ($grafs as $key => $value) {
- if (!preg_match('/^B\x1A[0-9]+B$/', $value)) {
- # Is a paragraph.
- $value = $this->runSpanGamut($value);
- $value = preg_replace('/^([ ]*)/', "<p>", $value);
- $value .= "</p>";
- $grafs[$key] = $this->unhash($value);
- }
- else {
- # Is a block.
- # Modify elements of @grafs in-place...
- $graf = $value;
- $block = $this->html_hashes[$graf];
- $graf = $block;
-// if (preg_match('{
-// \A
-// ( # $1 = <div> tag
-// <div \s+
-// [^>]*
-// \b
-// markdown\s*=\s* ([\'"]) # $2 = attr quote char
-// 1
-// \2
-// [^>]*
-// >
-// )
-// ( # $3 = contents
-// .*
-// )
-// (</div>) # $4 = closing tag
-// \z
-// }xs', $block, $matches))
-// {
-// list(, $div_open, , $div_content, $div_close) = $matches;
-//
-// # We can't call Markdown(), because that resets the hash;
-// # that initialization code should be pulled into its own sub, though.
-// $div_content = $this->hashHTMLBlocks($div_content);
-//
-// # Run document gamut methods on the content.
-// foreach ($this->document_gamut as $method => $priority) {
-// $div_content = $this->$method($div_content);
-// }
-//
-// $div_open = preg_replace(
-// '{\smarkdown\s*=\s*([\'"]).+?\1}', '', $div_open);
-//
-// $graf = $div_open . "\n" . $div_content . "\n" . $div_close;
-// }
- $grafs[$key] = $graf;
- }
- }
-
- return implode("\n\n", $grafs);
- }
-
-
- function encodeAttribute($text) {
- #
- # Encode text for a double-quoted HTML attribute. This function
- # is *not* suitable for attributes enclosed in single quotes.
- #
- $text = $this->encodeAmpsAndAngles($text);
- $text = str_replace('"', '&quot;', $text);
- return $text;
- }
-
-
- function encodeAmpsAndAngles($text) {
- #
- # Smart processing for ampersands and angle brackets that need to
- # be encoded. Valid character entities are left alone unless the
- # no-entities mode is set.
- #
- if ($this->no_entities) {
- $text = str_replace('&', '&amp;', $text);
- } else {
- # Ampersand-encoding based entirely on Nat Irons's Amputator
- # MT plugin: <http://bumppo.net/projects/amputator/>
- $text = preg_replace('/&(?!#?[xX]?(?:[0-9a-fA-F]+|\w+);)/',
- '&amp;', $text);;
- }
- # Encode remaining <'s
- $text = str_replace('<', '&lt;', $text);
-
- return $text;
- }
-
-
- function doAutoLinks($text) {
- $text = preg_replace_callback('{<((https?|ftp|dict):[^\'">\s]+)>}i',
- array(&$this, '_doAutoLinks_url_callback'), $text);
-
- # Email addresses: <address@domain.foo>
- $text = preg_replace_callback('{
- <
- (?:mailto:)?
- (
- (?:
- [-!#$%&\'*+/=?^_`.{|}~\w\x80-\xFF]+
- |
- ".*?"
- )
- \@
- (?:
- [-a-z0-9\x80-\xFF]+(\.[-a-z0-9\x80-\xFF]+)*\.[a-z]+
- |
- \[[\d.a-fA-F:]+\] # IPv4 & IPv6
- )
- )
- >
- }xi',
- array(&$this, '_doAutoLinks_email_callback'), $text);
-
- return $text;
- }
- function _doAutoLinks_url_callback($matches) {
- $url = $this->encodeAttribute($matches[1]);
- $link = "<a href=\"$url\">$url</a>";
- return $this->hashPart($link);
- }
- function _doAutoLinks_email_callback($matches) {
- $address = $matches[1];
- $link = $this->encodeEmailAddress($address);
- return $this->hashPart($link);
- }
-
-
- function encodeEmailAddress($addr) {
- #
- # Input: an email address, e.g. "foo@example.com"
- #
- # Output: the email address as a mailto link, with each character
- # of the address encoded as either a decimal or hex entity, in
- # the hopes of foiling most address harvesting spam bots. E.g.:
- #
- # <p><a href="&#109;&#x61;&#105;&#x6c;&#116;&#x6f;&#58;&#x66;o&#111;
- # &#x40;&#101;&#x78;&#97;&#x6d;&#112;&#x6c;&#101;&#46;&#x63;&#111;
- # &#x6d;">&#x66;o&#111;&#x40;&#101;&#x78;&#97;&#x6d;&#112;&#x6c;
- # &#101;&#46;&#x63;&#111;&#x6d;</a></p>
- #
- # Based by a filter by Matthew Wickline, posted to BBEdit-Talk.
- # With some optimizations by Milian Wolff.
- #
- $addr = "mailto:" . $addr;
- $chars = preg_split('/(?<!^)(?!$)/', $addr);
- $seed = (int)abs(crc32($addr) / strlen($addr)); # Deterministic seed.
-
- foreach ($chars as $key => $char) {
- $ord = ord($char);
- # Ignore non-ascii chars.
- if ($ord < 128) {
- $r = ($seed * (1 + $key)) % 100; # Pseudo-random function.
- # roughly 10% raw, 45% hex, 45% dec
- # '@' *must* be encoded. I insist.
- if ($r > 90 && $char != '@') /* do nothing */;
- else if ($r < 45) $chars[$key] = '&#x'.dechex($ord).';';
- else $chars[$key] = '&#'.$ord.';';
- }
- }
-
- $addr = implode('', $chars);
- $text = implode('', array_slice($chars, 7)); # text without `mailto:`
- $addr = "<a href=\"$addr\">$text</a>";
-
- return $addr;
- }
-
-
- function parseSpan($str) {
- #
- # Take the string $str and parse it into tokens, hashing embeded HTML,
- # escaped characters and handling code spans.
- #
- $output = '';
-
- $span_re = '{
- (
- \\\\'.$this->escape_chars_re.'
- |
- (?<![`\\\\])
- `+ # code span marker
- '.( $this->no_markup ? '' : '
- |
- <!-- .*? --> # comment
- |
- <\?.*?\?> | <%.*?%> # processing instruction
- |
- <[/!$]?[-a-zA-Z0-9:_]+ # regular tags
- (?>
- \s
- (?>[^"\'>]+|"[^"]*"|\'[^\']*\')*
- )?
- >
- ').'
- )
- }xs';
-
- while (1) {
- #
- # Each loop iteration seach for either the next tag, the next
- # openning code span marker, or the next escaped character.
- # Each token is then passed to handleSpanToken.
- #
- $parts = preg_split($span_re, $str, 2, PREG_SPLIT_DELIM_CAPTURE);
-
- # Create token from text preceding tag.
- if ($parts[0] != "") {
- $output .= $parts[0];
- }
-
- # Check if we reach the end.
- if (isset($parts[1])) {
- $output .= $this->handleSpanToken($parts[1], $parts[2]);
- $str = $parts[2];
- }
- else {
- break;
- }
- }
-
- return $output;
- }
-
-
- function handleSpanToken($token, &$str) {
- #
- # Handle $token provided by parseSpan by determining its nature and
- # returning the corresponding value that should replace it.
- #
- switch ($token{0}) {
- case "\\":
- return $this->hashPart("&#". ord($token{1}). ";");
- case "`":
- # Search for end marker in remaining text.
- if (preg_match('/^(.*?[^`])'.preg_quote($token).'(?!`)(.*)$/sm',
- $str, $matches))
- {
- $str = $matches[2];
- $codespan = $this->makeCodeSpan($matches[1]);
- return $this->hashPart($codespan);
- }
- return $token; // return as text since no ending marker found.
- default:
- return $this->hashPart($token);
- }
- }
-
-
- function outdent($text) {
- #
- # Remove one level of line-leading tabs or spaces
- #
- return preg_replace('/^(\t|[ ]{1,'.$this->tab_width.'})/m', '', $text);
- }
-
-
- # String length function for detab. `_initDetab` will create a function to
- # hanlde UTF-8 if the default function does not exist.
- var $utf8_strlen = 'mb_strlen';
-
- function detab($text) {
- #
- # Replace tabs with the appropriate amount of space.
- #
- # For each line we separate the line in blocks delemited by
- # tab characters. Then we reconstruct every line by adding the
- # appropriate number of space between each blocks.
-
- $text = preg_replace_callback('/^.*\t.*$/m',
- array(&$this, '_detab_callback'), $text);
-
- return $text;
- }
- function _detab_callback($matches) {
- $line = $matches[0];
- $strlen = $this->utf8_strlen; # strlen function for UTF-8.
-
- # Split in blocks.
- $blocks = explode("\t", $line);
- # Add each blocks to the line.
- $line = $blocks[0];
- unset($blocks[0]); # Do not add first block twice.
- foreach ($blocks as $block) {
- # Calculate amount of space, insert spaces, insert block.
- $amount = $this->tab_width -
- $strlen($line, 'UTF-8') % $this->tab_width;
- $line .= str_repeat(" ", $amount) . $block;
- }
- return $line;
- }
- function _initDetab() {
- #
- # Check for the availability of the function in the `utf8_strlen` property
- # (initially `mb_strlen`). If the function is not available, create a
- # function that will loosely count the number of UTF-8 characters with a
- # regular expression.
- #
- if (function_exists($this->utf8_strlen)) return;
- $this->utf8_strlen = create_function('$text', 'return preg_match_all(
- "/[\\\\x00-\\\\xBF]|[\\\\xC0-\\\\xFF][\\\\x80-\\\\xBF]*/",
- $text, $m);');
- }
-
-
- function unhash($text) {
- #
- # Swap back in all the tags hashed by _HashHTMLBlocks.
- #
- return preg_replace_callback('/(.)\x1A[0-9]+\1/',
- array(&$this, '_unhash_callback'), $text);
- }
- function _unhash_callback($matches) {
- return $this->html_hashes[$matches[0]];
- }
-
-}
-
-
-#
-# Markdown Extra Parser Class
-#
-
-class MarkdownExtra_Parser extends Markdown_Parser {
-
- # Prefix for footnote ids.
- var $fn_id_prefix = "";
-
- # Optional title attribute for footnote links and backlinks.
- var $fn_link_title = MARKDOWN_FN_LINK_TITLE;
- var $fn_backlink_title = MARKDOWN_FN_BACKLINK_TITLE;
-
- # Optional class attribute for footnote links and backlinks.
- var $fn_link_class = MARKDOWN_FN_LINK_CLASS;
- var $fn_backlink_class = MARKDOWN_FN_BACKLINK_CLASS;
-
- # Predefined abbreviations.
- var $predef_abbr = array();
-
-
- function MarkdownExtra_Parser() {
- #
- # Constructor function. Initialize the parser object.
- #
- # Add extra escapable characters before parent constructor
- # initialize the table.
- $this->escape_chars .= ':|';
-
- # Insert extra document, block, and span transformations.
- # Parent constructor will do the sorting.
- $this->document_gamut += array(
- "doFencedCodeBlocks" => 5,
- "stripFootnotes" => 15,
- "stripAbbreviations" => 25,
- "appendFootnotes" => 50,
- );
- $this->block_gamut += array(
- "doFencedCodeBlocks" => 5,
- "doTables" => 15,
- "doDefLists" => 45,
- );
- $this->span_gamut += array(
- "doFootnotes" => 5,
- "doAbbreviations" => 70,
- );
-
- parent::Markdown_Parser();
- }
-
-
- # Extra variables used during extra transformations.
- var $footnotes = array();
- var $footnotes_ordered = array();
- var $abbr_desciptions = array();
- var $abbr_word_re = '';
-
- # Give the current footnote number.
- var $footnote_counter = 1;
-
-
- function setup() {
- #
- # Setting up Extra-specific variables.
- #
- parent::setup();
-
- $this->footnotes = array();
- $this->footnotes_ordered = array();
- $this->abbr_desciptions = array();
- $this->abbr_word_re = '';
- $this->footnote_counter = 1;
-
- foreach ($this->predef_abbr as $abbr_word => $abbr_desc) {
- if ($this->abbr_word_re)
- $this->abbr_word_re .= '|';
- $this->abbr_word_re .= preg_quote($abbr_word);
- $this->abbr_desciptions[$abbr_word] = trim($abbr_desc);
- }
- }
-
- function teardown() {
- #
- # Clearing Extra-specific variables.
- #
- $this->footnotes = array();
- $this->footnotes_ordered = array();
- $this->abbr_desciptions = array();
- $this->abbr_word_re = '';
-
- parent::teardown();
- }
-
-
- ### HTML Block Parser ###
-
- # Tags that are always treated as block tags:
- var $block_tags_re = 'p|div|h[1-6]|blockquote|pre|table|dl|ol|ul|address|form|fieldset|iframe|hr|legend';
-
- # Tags treated as block tags only if the opening tag is alone on it's line:
- var $context_block_tags_re = 'script|noscript|math|ins|del';
-
- # Tags where markdown="1" default to span mode:
- var $contain_span_tags_re = 'p|h[1-6]|li|dd|dt|td|th|legend|address';
-
- # Tags which must not have their contents modified, no matter where
- # they appear:
- var $clean_tags_re = 'script|math';
-
- # Tags that do not need to be closed.
- var $auto_close_tags_re = 'hr|img';
-
-
- function hashHTMLBlocks($text) {
- #
- # Hashify HTML Blocks and "clean tags".
- #
- # We only want to do this for block-level HTML tags, such as headers,
- # lists, and tables. That's because we still want to wrap <p>s around
- # "paragraphs" that are wrapped in non-block-level tags, such as anchors,
- # phrase emphasis, and spans. The list of tags we're looking for is
- # hard-coded.
- #
- # This works by calling _HashHTMLBlocks_InMarkdown, which then calls
- # _HashHTMLBlocks_InHTML when it encounter block tags. When the markdown="1"
- # attribute is found whitin a tag, _HashHTMLBlocks_InHTML calls back
- # _HashHTMLBlocks_InMarkdown to handle the Markdown syntax within the tag.
- # These two functions are calling each other. It's recursive!
- #
- #
- # Call the HTML-in-Markdown hasher.
- #
- list($text, ) = $this->_hashHTMLBlocks_inMarkdown($text);
-
- return $text;
- }
- function _hashHTMLBlocks_inMarkdown($text, $indent = 0,
- $enclosing_tag_re = '', $span = false)
- {
- #
- # Parse markdown text, calling _HashHTMLBlocks_InHTML for block tags.
- #
- # * $indent is the number of space to be ignored when checking for code
- # blocks. This is important because if we don't take the indent into
- # account, something like this (which looks right) won't work as expected:
- #
- # <div>
- # <div markdown="1">
- # Hello World. <-- Is this a Markdown code block or text?
- # </div> <-- Is this a Markdown code block or a real tag?
- # <div>
- #
- # If you don't like this, just don't indent the tag on which
- # you apply the markdown="1" attribute.
- #
- # * If $enclosing_tag_re is not empty, stops at the first unmatched closing
- # tag with that name. Nested tags supported.
- #
- # * If $span is true, text inside must treated as span. So any double
- # newline will be replaced by a single newline so that it does not create
- # paragraphs.
- #
- # Returns an array of that form: ( processed text , remaining text )
- #
- if ($text === '') return array('', '');
-
- # Regex to check for the presense of newlines around a block tag.
- $newline_before_re = '/(?:^\n?|\n\n)*$/';
- $newline_after_re =
- '{
- ^ # Start of text following the tag.
- (?>[ ]*<!--.*?-->)? # Optional comment.
- [ ]*\n # Must be followed by newline.
- }xs';
-
- # Regex to match any tag.
- $block_tag_re =
- '{
- ( # $2: Capture hole tag.
- </? # Any opening or closing tag.
- (?> # Tag name.
- '.$this->block_tags_re.' |
- '.$this->context_block_tags_re.' |
- '.$this->clean_tags_re.' |
- (?!\s)'.$enclosing_tag_re.'
- )
- (?:
- (?=[\s"\'/a-zA-Z0-9]) # Allowed characters after tag name.
- (?>
- ".*?" | # Double quotes (can contain `>`)
- \'.*?\' | # Single quotes (can contain `>`)
- .+? # Anything but quotes and `>`.
- )*?
- )?
- > # End of tag.
- |
- <!-- .*? --> # HTML Comment
- |
- <\?.*?\?> | <%.*?%> # Processing instruction
- |
- <!\[CDATA\[.*?\]\]> # CData Block
- |
- # Code span marker
- `+
- '. ( !$span ? ' # If not in span.
- |
- # Indented code block
- (?: ^[ ]*\n | ^ | \n[ ]*\n )
- [ ]{'.($indent+4).'}[^\n]* \n
- (?>
- (?: [ ]{'.($indent+4).'}[^\n]* | [ ]* ) \n
- )*
- |
- # Fenced code block marker
- (?> ^ | \n )
- [ ]{0,'.($indent).'}~~~+[ ]*\n
- ' : '' ). ' # End (if not is span).
- )
- }xs';
-
-
- $depth = 0; # Current depth inside the tag tree.
- $parsed = ""; # Parsed text that will be returned.
-
- #
- # Loop through every tag until we find the closing tag of the parent
- # or loop until reaching the end of text if no parent tag specified.
- #
- do {
- #
- # Split the text using the first $tag_match pattern found.
- # Text before pattern will be first in the array, text after
- # pattern will be at the end, and between will be any catches made
- # by the pattern.
- #
- $parts = preg_split($block_tag_re, $text, 2,
- PREG_SPLIT_DELIM_CAPTURE);
-
- # If in Markdown span mode, add a empty-string span-level hash
- # after each newline to prevent triggering any block element.
- if ($span) {
- $void = $this->hashPart("", ':');
- $newline = "$void\n";
- $parts[0] = $void . str_replace("\n", $newline, $parts[0]) . $void;
- }
-
- $parsed .= $parts[0]; # Text before current tag.
-
- # If end of $text has been reached. Stop loop.
- if (count($parts) < 3) {
- $text = "";
- break;
- }
-
- $tag = $parts[1]; # Tag to handle.
- $text = $parts[2]; # Remaining text after current tag.
- $tag_re = preg_quote($tag); # For use in a regular expression.
-
- #
- # Check for: Code span marker
- #
- if ($tag{0} == "`") {
- # Find corresponding end marker.
- $tag_re = preg_quote($tag);
- if (preg_match('{^(?>.+?|\n(?!\n))*?(?<!`)'.$tag_re.'(?!`)}',
- $text, $matches))
- {
- # End marker found: pass text unchanged until marker.
- $parsed .= $tag . $matches[0];
- $text = substr($text, strlen($matches[0]));
- }
- else {
- # Unmatched marker: just skip it.
- $parsed .= $tag;
- }
- }
- #
- # Check for: Fenced code block marker.
- #
- else if (preg_match('{^\n?[ ]{0,'.($indent+3).'}~}', $tag)) {
- # Fenced code block marker: find matching end marker.
- $tag_re = preg_quote(trim($tag));
- if (preg_match('{^(?>.*\n)+?[ ]{0,'.($indent).'}'.$tag_re.'[ ]*\n}', $text,
- $matches))
- {
- # End marker found: pass text unchanged until marker.
- $parsed .= $tag . $matches[0];
- $text = substr($text, strlen($matches[0]));
- }
- else {
- # No end marker: just skip it.
- $parsed .= $tag;
- }
- }
- #
- # Check for: Indented code block.
- #
- else if ($tag{0} == "\n" || $tag{0} == " ") {
- # Indented code block: pass it unchanged, will be handled
- # later.
- $parsed .= $tag;
- }
- #
- # Check for: Opening Block level tag or
- # Opening Context Block tag (like ins and del)
- # used as a block tag (tag is alone on it's line).
- #
- else if (preg_match('{^<(?:'.$this->block_tags_re.')\b}', $tag) ||
- ( preg_match('{^<(?:'.$this->context_block_tags_re.')\b}', $tag) &&
- preg_match($newline_before_re, $parsed) &&
- preg_match($newline_after_re, $text) )
- )
- {
- # Need to parse tag and following text using the HTML parser.
- list($block_text, $text) =
- $this->_hashHTMLBlocks_inHTML($tag . $text, "hashBlock", true);
-
- # Make sure it stays outside of any paragraph by adding newlines.
- $parsed .= "\n\n$block_text\n\n";
- }
- #
- # Check for: Clean tag (like script, math)
- # HTML Comments, processing instructions.
- #
- else if (preg_match('{^<(?:'.$this->clean_tags_re.')\b}', $tag) ||
- $tag{1} == '!' || $tag{1} == '?')
- {
- # Need to parse tag and following text using the HTML parser.
- # (don't check for markdown attribute)
- list($block_text, $text) =
- $this->_hashHTMLBlocks_inHTML($tag . $text, "hashClean", false);
-
- $parsed .= $block_text;
- }
- #
- # Check for: Tag with same name as enclosing tag.
- #
- else if ($enclosing_tag_re !== '' &&
- # Same name as enclosing tag.
- preg_match('{^</?(?:'.$enclosing_tag_re.')\b}', $tag))
- {
- #
- # Increase/decrease nested tag count.
- #
- if ($tag{1} == '/') $depth--;
- else if ($tag{strlen($tag)-2} != '/') $depth++;
-
- if ($depth < 0) {
- #
- # Going out of parent element. Clean up and break so we
- # return to the calling function.
- #
- $text = $tag . $text;
- break;
- }
-
- $parsed .= $tag;
- }
- else {
- $parsed .= $tag;
- }
- } while ($depth >= 0);
-
- return array($parsed, $text);
- }
- function _hashHTMLBlocks_inHTML($text, $hash_method, $md_attr) {
- #
- # Parse HTML, calling _HashHTMLBlocks_InMarkdown for block tags.
- #
- # * Calls $hash_method to convert any blocks.
- # * Stops when the first opening tag closes.
- # * $md_attr indicate if the use of the `markdown="1"` attribute is allowed.
- # (it is not inside clean tags)
- #
- # Returns an array of that form: ( processed text , remaining text )
- #
- if ($text === '') return array('', '');
-
- # Regex to match `markdown` attribute inside of a tag.
- $markdown_attr_re = '
- {
- \s* # Eat whitespace before the `markdown` attribute
- markdown
- \s*=\s*
- (?>
- (["\']) # $1: quote delimiter
- (.*?) # $2: attribute value
- \1 # matching delimiter
- |
- ([^\s>]*) # $3: unquoted attribute value
- )
- () # $4: make $3 always defined (avoid warnings)
- }xs';
-
- # Regex to match any tag.
- $tag_re = '{
- ( # $2: Capture hole tag.
- </? # Any opening or closing tag.
- [\w:$]+ # Tag name.
- (?:
- (?=[\s"\'/a-zA-Z0-9]) # Allowed characters after tag name.
- (?>
- ".*?" | # Double quotes (can contain `>`)
- \'.*?\' | # Single quotes (can contain `>`)
- .+? # Anything but quotes and `>`.
- )*?
- )?
- > # End of tag.
- |
- <!-- .*? --> # HTML Comment
- |
- <\?.*?\?> | <%.*?%> # Processing instruction
- |
- <!\[CDATA\[.*?\]\]> # CData Block
- )
- }xs';
-
- $original_text = $text; # Save original text in case of faliure.
-
- $depth = 0; # Current depth inside the tag tree.
- $block_text = ""; # Temporary text holder for current text.
- $parsed = ""; # Parsed text that will be returned.
-
- #
- # Get the name of the starting tag.
- # (This pattern makes $base_tag_name_re safe without quoting.)
- #
- if (preg_match('/^<([\w:$]*)\b/', $text, $matches))
- $base_tag_name_re = $matches[1];
-
- #
- # Loop through every tag until we find the corresponding closing tag.
- #
- do {
- #
- # Split the text using the first $tag_match pattern found.
- # Text before pattern will be first in the array, text after
- # pattern will be at the end, and between will be any catches made
- # by the pattern.
- #
- $parts = preg_split($tag_re, $text, 2, PREG_SPLIT_DELIM_CAPTURE);
-
- if (count($parts) < 3) {
- #
- # End of $text reached with unbalenced tag(s).
- # In that case, we return original text unchanged and pass the
- # first character as filtered to prevent an infinite loop in the
- # parent function.
- #
- return array($original_text{0}, substr($original_text, 1));
- }
-
- $block_text .= $parts[0]; # Text before current tag.
- $tag = $parts[1]; # Tag to handle.
- $text = $parts[2]; # Remaining text after current tag.
-
- #
- # Check for: Auto-close tag (like <hr/>)
- # Comments and Processing Instructions.
- #
- if (preg_match('{^</?(?:'.$this->auto_close_tags_re.')\b}', $tag) ||
- $tag{1} == '!' || $tag{1} == '?')
- {
- # Just add the tag to the block as if it was text.
- $block_text .= $tag;
- }
- else {
- #
- # Increase/decrease nested tag count. Only do so if
- # the tag's name match base tag's.
- #
- if (preg_match('{^</?'.$base_tag_name_re.'\b}', $tag)) {
- if ($tag{1} == '/') $depth--;
- else if ($tag{strlen($tag)-2} != '/') $depth++;
- }
-
- #
- # Check for `markdown="1"` attribute and handle it.
- #
- if ($md_attr &&
- preg_match($markdown_attr_re, $tag, $attr_m) &&
- preg_match('/^1|block|span$/', $attr_m[2] . $attr_m[3]))
- {
- # Remove `markdown` attribute from opening tag.
- $tag = preg_replace($markdown_attr_re, '', $tag);
-
- # Check if text inside this tag must be parsed in span mode.
- $this->mode = $attr_m[2] . $attr_m[3];
- $span_mode = $this->mode == 'span' || $this->mode != 'block' &&
- preg_match('{^<(?:'.$this->contain_span_tags_re.')\b}', $tag);
-
- # Calculate indent before tag.
- if (preg_match('/(?:^|\n)( *?)(?! ).*?$/', $block_text, $matches)) {
- $strlen = $this->utf8_strlen;
- $indent = $strlen($matches[1], 'UTF-8');
- } else {
- $indent = 0;
- }
-
- # End preceding block with this tag.
- $block_text .= $tag;
- $parsed .= $this->$hash_method($block_text);
-
- # Get enclosing tag name for the ParseMarkdown function.
- # (This pattern makes $tag_name_re safe without quoting.)
- preg_match('/^<([\w:$]*)\b/', $tag, $matches);
- $tag_name_re = $matches[1];
-
- # Parse the content using the HTML-in-Markdown parser.
- list ($block_text, $text)
- = $this->_hashHTMLBlocks_inMarkdown($text, $indent,
- $tag_name_re, $span_mode);
-
- # Outdent markdown text.
- if ($indent > 0) {
- $block_text = preg_replace("/^[ ]{1,$indent}/m", "",
- $block_text);
- }
-
- # Append tag content to parsed text.
- if (!$span_mode) $parsed .= "\n\n$block_text\n\n";
- else $parsed .= "$block_text";
-
- # Start over a new block.
- $block_text = "";
- }
- else $block_text .= $tag;
- }
-
- } while ($depth > 0);
-
- #
- # Hash last block text that wasn't processed inside the loop.
- #
- $parsed .= $this->$hash_method($block_text);
-
- return array($parsed, $text);
- }
-
-
- function hashClean($text) {
- #
- # Called whenever a tag must be hashed when a function insert a "clean" tag
- # in $text, it pass through this function and is automaticaly escaped,
- # blocking invalid nested overlap.
- #
- return $this->hashPart($text, 'C');
- }
-
-
- function doHeaders($text) {
- #
- # Redefined to add id attribute support.
- #
- # Setext-style headers:
- # Header 1 {#header1}
- # ========
- #
- # Header 2 {#header2}
- # --------
- #
- $text = preg_replace_callback(
- '{
- (^.+?) # $1: Header text
- (?:[ ]+\{\#([-_:a-zA-Z0-9]+)\})? # $2: Id attribute
- [ ]*\n(=+|-+)[ ]*\n+ # $3: Header footer
- }mx',
- array(&$this, '_doHeaders_callback_setext'), $text);
-
- # atx-style headers:
- # # Header 1 {#header1}
- # ## Header 2 {#header2}
- # ## Header 2 with closing hashes ## {#header3}
- # ...
- # ###### Header 6 {#header2}
- #
- $text = preg_replace_callback('{
- ^(\#{1,6}) # $1 = string of #\'s
- [ ]*
- (.+?) # $2 = Header text
- [ ]*
- \#* # optional closing #\'s (not counted)
- (?:[ ]+\{\#([-_:a-zA-Z0-9]+)\})? # id attribute
- [ ]*
- \n+
- }xm',
- array(&$this, '_doHeaders_callback_atx'), $text);
-
- return $text;
- }
- function _doHeaders_attr($attr) {
- if (empty($attr)) return "";
- return " id=\"$attr\"";
- }
- function _doHeaders_callback_setext($matches) {
- if ($matches[3] == '-' && preg_match('{^- }', $matches[1]))
- return $matches[0];
- $level = $matches[3]{0} == '=' ? 1 : 2;
- $attr = $this->_doHeaders_attr($id =& $matches[2]);
- $block = "<h$level$attr>".$this->runSpanGamut($matches[1])."</h$level>";
- return "\n" . $this->hashBlock($block) . "\n\n";
- }
- function _doHeaders_callback_atx($matches) {
- $level = strlen($matches[1]);
- $attr = $this->_doHeaders_attr($id =& $matches[3]);
- $block = "<h$level$attr>".$this->runSpanGamut($matches[2])."</h$level>";
- return "\n" . $this->hashBlock($block) . "\n\n";
- }
-
-
- function doTables($text) {
- #
- # Form HTML tables.
- #
- $less_than_tab = $this->tab_width - 1;
- #
- # Find tables with leading pipe.
- #
- # | Header 1 | Header 2
- # | -------- | --------
- # | Cell 1 | Cell 2
- # | Cell 3 | Cell 4
- #
- $text = preg_replace_callback('
- {
- ^ # Start of a line
- [ ]{0,'.$less_than_tab.'} # Allowed whitespace.
- [|] # Optional leading pipe (present)
- (.+) \n # $1: Header row (at least one pipe)
-
- [ ]{0,'.$less_than_tab.'} # Allowed whitespace.
- [|] ([ ]*[-:]+[-| :]*) \n # $2: Header underline
-
- ( # $3: Cells
- (?>
- [ ]* # Allowed whitespace.
- [|] .* \n # Row content.
- )*
- )
- (?=\n|\Z) # Stop at final double newline.
- }xm',
- array(&$this, '_doTable_leadingPipe_callback'), $text);
-
- #
- # Find tables without leading pipe.
- #
- # Header 1 | Header 2
- # -------- | --------
- # Cell 1 | Cell 2
- # Cell 3 | Cell 4
- #
- $text = preg_replace_callback('
- {
- ^ # Start of a line
- [ ]{0,'.$less_than_tab.'} # Allowed whitespace.
- (\S.*[|].*) \n # $1: Header row (at least one pipe)
-
- [ ]{0,'.$less_than_tab.'} # Allowed whitespace.
- ([-:]+[ ]*[|][-| :]*) \n # $2: Header underline
-
- ( # $3: Cells
- (?>
- .* [|] .* \n # Row content
- )*
- )
- (?=\n|\Z) # Stop at final double newline.
- }xm',
- array(&$this, '_DoTable_callback'), $text);
-
- return $text;
- }
- function _doTable_leadingPipe_callback($matches) {
- $head = $matches[1];
- $underline = $matches[2];
- $content = $matches[3];
-
- # Remove leading pipe for each row.
- $content = preg_replace('/^ *[|]/m', '', $content);
-
- return $this->_doTable_callback(array($matches[0], $head, $underline, $content));
- }
- function _doTable_callback($matches) {
- $head = $matches[1];
- $underline = $matches[2];
- $content = $matches[3];
-
- # Remove any tailing pipes for each line.
- $head = preg_replace('/[|] *$/m', '', $head);
- $underline = preg_replace('/[|] *$/m', '', $underline);
- $content = preg_replace('/[|] *$/m', '', $content);
-
- # Reading alignement from header underline.
- $separators = preg_split('/ *[|] */', $underline);
- foreach ($separators as $n => $s) {
- if (preg_match('/^ *-+: *$/', $s)) $attr[$n] = ' align="right"';
- else if (preg_match('/^ *:-+: *$/', $s))$attr[$n] = ' align="center"';
- else if (preg_match('/^ *:-+ *$/', $s)) $attr[$n] = ' align="left"';
- else $attr[$n] = '';
- }
-
- # Parsing span elements, including code spans, character escapes,
- # and inline HTML tags, so that pipes inside those gets ignored.
- $head = $this->parseSpan($head);
- $headers = preg_split('/ *[|] */', $head);
- $col_count = count($headers);
-
- # Write column headers.
- $text = "<table>\n";
- $text .= "<thead>\n";
- $text .= "<tr>\n";
- foreach ($headers as $n => $header)
- $text .= " <th$attr[$n]>".$this->runSpanGamut(trim($header))."</th>\n";
- $text .= "</tr>\n";
- $text .= "</thead>\n";
-
- # Split content by row.
- $rows = explode("\n", trim($content, "\n"));
-
- $text .= "<tbody>\n";
- foreach ($rows as $row) {
- # Parsing span elements, including code spans, character escapes,
- # and inline HTML tags, so that pipes inside those gets ignored.
- $row = $this->parseSpan($row);
-
- # Split row by cell.
- $row_cells = preg_split('/ *[|] */', $row, $col_count);
- $row_cells = array_pad($row_cells, $col_count, '');
-
- $text .= "<tr>\n";
- foreach ($row_cells as $n => $cell)
- $text .= " <td$attr[$n]>".$this->runSpanGamut(trim($cell))."</td>\n";
- $text .= "</tr>\n";
- }
- $text .= "</tbody>\n";
- $text .= "</table>";
-
- return $this->hashBlock($text) . "\n";
- }
-
-
- function doDefLists($text) {
- #
- # Form HTML definition lists.
- #
- $less_than_tab = $this->tab_width - 1;
-
- # Re-usable pattern to match any entire dl list:
- $whole_list_re = '(?>
- ( # $1 = whole list
- ( # $2
- [ ]{0,'.$less_than_tab.'}
- ((?>.*\S.*\n)+) # $3 = defined term
- \n?
- [ ]{0,'.$less_than_tab.'}:[ ]+ # colon starting definition
- )
- (?s:.+?)
- ( # $4
- \z
- |
- \n{2,}
- (?=\S)
- (?! # Negative lookahead for another term
- [ ]{0,'.$less_than_tab.'}
- (?: \S.*\n )+? # defined term
- \n?
- [ ]{0,'.$less_than_tab.'}:[ ]+ # colon starting definition
- )
- (?! # Negative lookahead for another definition
- [ ]{0,'.$less_than_tab.'}:[ ]+ # colon starting definition
- )
- )
- )
- )'; // mx
-
- $text = preg_replace_callback('{
- (?>\A\n?|(?<=\n\n))
- '.$whole_list_re.'
- }mx',
- array(&$this, '_doDefLists_callback'), $text);
-
- return $text;
- }
- function _doDefLists_callback($matches) {
- # Re-usable patterns to match list item bullets and number markers:
- $list = $matches[1];
-
- # Turn double returns into triple returns, so that we can make a
- # paragraph for the last item in a list, if necessary:
- $result = trim($this->processDefListItems($list));
- $result = "<dl>\n" . $result . "\n</dl>";
- return $this->hashBlock($result) . "\n\n";
- }
-
-
- function processDefListItems($list_str) {
- #
- # Process the contents of a single definition list, splitting it
- # into individual term and definition list items.
- #
- $less_than_tab = $this->tab_width - 1;
-
- # trim trailing blank lines:
- $list_str = preg_replace("/\n{2,}\\z/", "\n", $list_str);
-
- # Process definition terms.
- $list_str = preg_replace_callback('{
- (?>\A\n?|\n\n+) # leading line
- ( # definition terms = $1
- [ ]{0,'.$less_than_tab.'} # leading whitespace
- (?![:][ ]|[ ]) # negative lookahead for a definition
- # mark (colon) or more whitespace.
- (?> \S.* \n)+? # actual term (not whitespace).
- )
- (?=\n?[ ]{0,3}:[ ]) # lookahead for following line feed
- # with a definition mark.
- }xm',
- array(&$this, '_processDefListItems_callback_dt'), $list_str);
-
- # Process actual definitions.
- $list_str = preg_replace_callback('{
- \n(\n+)? # leading line = $1
- ( # marker space = $2
- [ ]{0,'.$less_than_tab.'} # whitespace before colon
- [:][ ]+ # definition mark (colon)
- )
- ((?s:.+?)) # definition text = $3
- (?= \n+ # stop at next definition mark,
- (?: # next term or end of text
- [ ]{0,'.$less_than_tab.'} [:][ ] |
- <dt> | \z
- )
- )
- }xm',
- array(&$this, '_processDefListItems_callback_dd'), $list_str);
-
- return $list_str;
- }
- function _processDefListItems_callback_dt($matches) {
- $terms = explode("\n", trim($matches[1]));
- $text = '';
- foreach ($terms as $term) {
- $term = $this->runSpanGamut(trim($term));
- $text .= "\n<dt>" . $term . "</dt>";
- }
- return $text . "\n";
- }
- function _processDefListItems_callback_dd($matches) {
- $leading_line = $matches[1];
- $marker_space = $matches[2];
- $def = $matches[3];
-
- if ($leading_line || preg_match('/\n{2,}/', $def)) {
- # Replace marker with the appropriate whitespace indentation
- $def = str_repeat(' ', strlen($marker_space)) . $def;
- $def = $this->runBlockGamut($this->outdent($def . "\n\n"));
- $def = "\n". $def ."\n";
- }
- else {
- $def = rtrim($def);
- $def = $this->runSpanGamut($this->outdent($def));
- }
-
- return "\n<dd>" . $def . "</dd>\n";
- }
-
-
- function doFencedCodeBlocks($text) {
- #
- # Adding the fenced code block syntax to regular Markdown:
- #
- # ~~~
- # Code block
- # ~~~
- #
- $less_than_tab = $this->tab_width;
-
- $text = preg_replace_callback('{
- (?:\n|\A)
- # 1: Opening marker
- (
- ~{3,} # Marker: three tilde or more.
- )
- [ ]* \n # Whitespace and newline following marker.
-
- # 2: Content
- (
- (?>
- (?!\1 [ ]* \n) # Not a closing marker.
- .*\n+
- )+
- )
-
- # Closing marker.
- \1 [ ]* \n
- }xm',
- array(&$this, '_doFencedCodeBlocks_callback'), $text);
-
- return $text;
- }
- function _doFencedCodeBlocks_callback($matches) {
- $codeblock = $matches[2];
- $codeblock = htmlspecialchars($codeblock, ENT_NOQUOTES);
- $codeblock = preg_replace_callback('/^\n+/',
- array(&$this, '_doFencedCodeBlocks_newlines'), $codeblock);
- $codeblock = "<pre><code>$codeblock</code></pre>";
- return "\n\n".$this->hashBlock($codeblock)."\n\n";
- }
- function _doFencedCodeBlocks_newlines($matches) {
- return str_repeat("<br$this->empty_element_suffix",
- strlen($matches[0]));
- }
-
-
- #
- # Redefining emphasis markers so that emphasis by underscore does not
- # work in the middle of a word.
- #
- var $em_relist = array(
- '' => '(?:(?<!\*)\*(?!\*)|(?<![a-zA-Z0-9_])_(?!_))(?=\S|$)(?![\.,:;]\s)',
- '*' => '(?<=\S|^)(?<!\*)\*(?!\*)',
- '_' => '(?<=\S|^)(?<!_)_(?![a-zA-Z0-9_])',
- );
- var $strong_relist = array(
- '' => '(?:(?<!\*)\*\*(?!\*)|(?<![a-zA-Z0-9_])__(?!_))(?=\S|$)(?![\.,:;]\s)',
- '**' => '(?<=\S|^)(?<!\*)\*\*(?!\*)',
- '__' => '(?<=\S|^)(?<!_)__(?![a-zA-Z0-9_])',
- );
- var $em_strong_relist = array(
- '' => '(?:(?<!\*)\*\*\*(?!\*)|(?<![a-zA-Z0-9_])___(?!_))(?=\S|$)(?![\.,:;]\s)',
- '***' => '(?<=\S|^)(?<!\*)\*\*\*(?!\*)',
- '___' => '(?<=\S|^)(?<!_)___(?![a-zA-Z0-9_])',
- );
-
-
- function formParagraphs($text) {
- #
- # Params:
- # $text - string to process with html <p> tags
- #
- # Strip leading and trailing lines:
- $text = preg_replace('/\A\n+|\n+\z/', '', $text);
-
- $grafs = preg_split('/\n{2,}/', $text, -1, PREG_SPLIT_NO_EMPTY);
-
- #
- # Wrap <p> tags and unhashify HTML blocks
- #
- foreach ($grafs as $key => $value) {
- $value = trim($this->runSpanGamut($value));
-
- # Check if this should be enclosed in a paragraph.
- # Clean tag hashes & block tag hashes are left alone.
- $is_p = !preg_match('/^B\x1A[0-9]+B|^C\x1A[0-9]+C$/', $value);
-
- if ($is_p) {
- $value = "<p>$value</p>";
- }
- $grafs[$key] = $value;
- }
-
- # Join grafs in one text, then unhash HTML tags.
- $text = implode("\n\n", $grafs);
-
- # Finish by removing any tag hashes still present in $text.
- $text = $this->unhash($text);
-
- return $text;
- }
-
-
- ### Footnotes
-
- function stripFootnotes($text) {
- #
- # Strips link definitions from text, stores the URLs and titles in
- # hash references.
- #
- $less_than_tab = $this->tab_width - 1;
-
- # Link defs are in the form: [^id]: url "optional title"
- $text = preg_replace_callback('{
- ^[ ]{0,'.$less_than_tab.'}\[\^(.+?)\][ ]?: # note_id = $1
- [ ]*
- \n? # maybe *one* newline
- ( # text = $2 (no blank lines allowed)
- (?:
- .+ # actual text
- |
- \n # newlines but
- (?!\[\^.+?\]:\s)# negative lookahead for footnote marker.
- (?!\n+[ ]{0,3}\S)# ensure line is not blank and followed
- # by non-indented content
- )*
- )
- }xm',
- array(&$this, '_stripFootnotes_callback'),
- $text);
- return $text;
- }
- function _stripFootnotes_callback($matches) {
- $note_id = $this->fn_id_prefix . $matches[1];
- $this->footnotes[$note_id] = $this->outdent($matches[2]);
- return ''; # String that will replace the block
- }
-
-
- function doFootnotes($text) {
- #
- # Replace footnote references in $text [^id] with a special text-token
- # which will be replaced by the actual footnote marker in appendFootnotes.
- #
- if (!$this->in_anchor) {
- $text = preg_replace('{\[\^(.+?)\]}', "F\x1Afn:\\1\x1A:", $text);
- }
- return $text;
- }
-
-
- function appendFootnotes($text) {
- #
- # Append footnote list to text.
- #
- $text = preg_replace_callback('{F\x1Afn:(.*?)\x1A:}',
- array(&$this, '_appendFootnotes_callback'), $text);
-
- if (!empty($this->footnotes_ordered)) {
- $text .= "\n\n";
- $text .= "<div class=\"footnotes\">\n";
- $text .= "<hr". $this->empty_element_suffix ."\n";
- $text .= "<ol>\n\n";
-
- $attr = " rev=\"footnote\"";
- if ($this->fn_backlink_class != "") {
- $class = $this->fn_backlink_class;
- $class = $this->encodeAttribute($class);
- $attr .= " class=\"$class\"";
- }
- if ($this->fn_backlink_title != "") {
- $title = $this->fn_backlink_title;
- $title = $this->encodeAttribute($title);
- $attr .= " title=\"$title\"";
- }
- $num = 0;
-
- while (!empty($this->footnotes_ordered)) {
- $footnote = reset($this->footnotes_ordered);
- $note_id = key($this->footnotes_ordered);
- unset($this->footnotes_ordered[$note_id]);
-
- $footnote .= "\n"; # Need to append newline before parsing.
- $footnote = $this->runBlockGamut("$footnote\n");
- $footnote = preg_replace_callback('{F\x1Afn:(.*?)\x1A:}',
- array(&$this, '_appendFootnotes_callback'), $footnote);
-
- $attr = str_replace("%%", ++$num, $attr);
- $note_id = $this->encodeAttribute($note_id);
-
- # Add backlink to last paragraph; create new paragraph if needed.
- $backlink = "<a href=\"#fnref:$note_id\"$attr>&#8617;</a>";
- if (preg_match('{</p>$}', $footnote)) {
- $footnote = substr($footnote, 0, -4) . "&#160;$backlink</p>";
- } else {
- $footnote .= "\n\n<p>$backlink</p>";
- }
-
- $text .= "<li id=\"fn:$note_id\">\n";
- $text .= $footnote . "\n";
- $text .= "</li>\n\n";
- }
-
- $text .= "</ol>\n";
- $text .= "</div>";
- }
- return $text;
- }
- function _appendFootnotes_callback($matches) {
- $node_id = $this->fn_id_prefix . $matches[1];
-
- # Create footnote marker only if it has a corresponding footnote *and*
- # the footnote hasn't been used by another marker.
- if (isset($this->footnotes[$node_id])) {
- # Transfert footnote content to the ordered list.
- $this->footnotes_ordered[$node_id] = $this->footnotes[$node_id];
- unset($this->footnotes[$node_id]);
-
- $num = $this->footnote_counter++;
- $attr = " rel=\"footnote\"";
- if ($this->fn_link_class != "") {
- $class = $this->fn_link_class;
- $class = $this->encodeAttribute($class);
- $attr .= " class=\"$class\"";
- }
- if ($this->fn_link_title != "") {
- $title = $this->fn_link_title;
- $title = $this->encodeAttribute($title);
- $attr .= " title=\"$title\"";
- }
-
- $attr = str_replace("%%", $num, $attr);
- $node_id = $this->encodeAttribute($node_id);
-
- return
- "<sup id=\"fnref:$node_id\">".
- "<a href=\"#fn:$node_id\"$attr>$num</a>".
- "</sup>";
- }
-
- return "[^".$matches[1]."]";
- }
-
-
- ### Abbreviations ###
-
- function stripAbbreviations($text) {
- #
- # Strips abbreviations from text, stores titles in hash references.
- #
- $less_than_tab = $this->tab_width - 1;
-
- # Link defs are in the form: [id]*: url "optional title"
- $text = preg_replace_callback('{
- ^[ ]{0,'.$less_than_tab.'}\*\[(.+?)\][ ]?: # abbr_id = $1
- (.*) # text = $2 (no blank lines allowed)
- }xm',
- array(&$this, '_stripAbbreviations_callback'),
- $text);
- return $text;
- }
- function _stripAbbreviations_callback($matches) {
- $abbr_word = $matches[1];
- $abbr_desc = $matches[2];
- if ($this->abbr_word_re)
- $this->abbr_word_re .= '|';
- $this->abbr_word_re .= preg_quote($abbr_word);
- $this->abbr_desciptions[$abbr_word] = trim($abbr_desc);
- return ''; # String that will replace the block
- }
-
-
- function doAbbreviations($text) {
- #
- # Find defined abbreviations in text and wrap them in <abbr> elements.
- #
- if ($this->abbr_word_re) {
- // cannot use the /x modifier because abbr_word_re may
- // contain significant spaces:
- $text = preg_replace_callback('{'.
- '(?<![\w\x1A])'.
- '(?:'.$this->abbr_word_re.')'.
- '(?![\w\x1A])'.
- '}',
- array(&$this, '_doAbbreviations_callback'), $text);
- }
- return $text;
- }
- function _doAbbreviations_callback($matches) {
- $abbr = $matches[0];
- if (isset($this->abbr_desciptions[$abbr])) {
- $desc = $this->abbr_desciptions[$abbr];
- if (empty($desc)) {
- return $this->hashPart("<abbr>$abbr</abbr>");
- } else {
- $desc = $this->encodeAttribute($desc);
- return $this->hashPart("<abbr title=\"$desc\">$abbr</abbr>");
- }
- } else {
- return $matches[0];
- }
- }
-
-}
-
-
-/*
-
-PHP Markdown Extra
-==================
-
-Description
------------
-
-This is a PHP port of the original Markdown formatter written in Perl
-by John Gruber. This special "Extra" version of PHP Markdown features
-further enhancements to the syntax for making additional constructs
-such as tables and definition list.
-
-Markdown is a text-to-HTML filter; it translates an easy-to-read /
-easy-to-write structured text format into HTML. Markdown's text format
-is most similar to that of plain text email, and supports features such
-as headers, *emphasis*, code blocks, blockquotes, and links.
-
-Markdown's syntax is designed not as a generic markup language, but
-specifically to serve as a front-end to (X)HTML. You can use span-level
-HTML tags anywhere in a Markdown document, and you can use block level
-HTML tags (like <div> and <table> as well).
-
-For more information about Markdown's syntax, see:
-
-<http://daringfireball.net/projects/markdown/>
-
-
-Bugs
-----
-
-To file bug reports please send email to:
-
-<michel.fortin@michelf.com>
-
-Please include with your report: (1) the example input; (2) the output you
-expected; (3) the output Markdown actually produced.
-
-
-Version History
----------------
-
-See the readme file for detailed release notes for this version.
-
-
-Copyright and License
----------------------
-
-PHP Markdown & Extra
-Copyright (c) 2004-2009 Michel Fortin
-<http://michelf.com/>
-All rights reserved.
-
-Based on Markdown
-Copyright (c) 2003-2006 John Gruber
-<http://daringfireball.net/>
-All rights reserved.
-
-Redistribution and use in source and binary forms, with or without
-modification, are permitted provided that the following conditions are
-met:
-
-* Redistributions of source code must retain the above copyright notice,
- this list of conditions and the following disclaimer.
-
-* Redistributions in binary form must reproduce the above copyright
- notice, this list of conditions and the following disclaimer in the
- documentation and/or other materials provided with the distribution.
-
-* Neither the name "Markdown" nor the names of its contributors may
- be used to endorse or promote products derived from this software
- without specific prior written permission.
-
-This software is provided by the copyright holders and contributors "as
-is" and any express or implied warranties, including, but not limited
-to, the implied warranties of merchantability and fitness for a
-particular purpose are disclaimed. In no event shall the copyright owner
-or contributors be liable for any direct, indirect, incidental, special,
-exemplary, or consequential damages (including, but not limited to,
-procurement of substitute goods or services; loss of use, data, or
-profits; or business interruption) however caused and on any theory of
-liability, whether in contract, strict liability, or tort (including
-negligence or otherwise) arising in any way out of the use of this
-software, even if advised of the possibility of such damage.
-
-*/
-?> \ No newline at end of file
diff --git a/library/markdownify/LICENSE_LGPL.txt b/library/markdownify/LICENSE_LGPL.txt
deleted file mode 100644
index 5ab7695ab..000000000
--- a/library/markdownify/LICENSE_LGPL.txt
+++ /dev/null
@@ -1,504 +0,0 @@
- GNU LESSER GENERAL PUBLIC LICENSE
- Version 2.1, February 1999
-
- Copyright (C) 1991, 1999 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.
-
-[This is the first released version of the Lesser GPL. It also counts
- as the successor of the GNU Library Public License, version 2, hence
- the version number 2.1.]
-
- Preamble
-
- The licenses for most software are designed to take away your
-freedom to share and change it. By contrast, the GNU General Public
-Licenses are intended to guarantee your freedom to share and change
-free software--to make sure the software is free for all its users.
-
- This license, the Lesser General Public License, applies to some
-specially designated software packages--typically libraries--of the
-Free Software Foundation and other authors who decide to use it. You
-can use it too, but we suggest you first think carefully about whether
-this license or the ordinary General Public License is the better
-strategy to use in any particular case, based on the explanations below.
-
- When we speak of free software, we are referring to freedom of use,
-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 and use pieces of
-it in new free programs; and that you are informed that you can do
-these things.
-
- To protect your rights, we need to make restrictions that forbid
-distributors to deny you these rights or to ask you to surrender these
-rights. These restrictions translate to certain responsibilities for
-you if you distribute copies of the library or if you modify it.
-
- For example, if you distribute copies of the library, whether gratis
-or for a fee, you must give the recipients all the rights that we gave
-you. You must make sure that they, too, receive or can get the source
-code. If you link other code with the library, you must provide
-complete object files to the recipients, so that they can relink them
-with the library after making changes to the library and recompiling
-it. And you must show them these terms so they know their rights.
-
- We protect your rights with a two-step method: (1) we copyright the
-library, and (2) we offer you this license, which gives you legal
-permission to copy, distribute and/or modify the library.
-
- To protect each distributor, we want to make it very clear that
-there is no warranty for the free library. Also, if the library is
-modified by someone else and passed on, the recipients should know
-that what they have is not the original version, so that the original
-author's reputation will not be affected by problems that might be
-introduced by others.
-
- Finally, software patents pose a constant threat to the existence of
-any free program. We wish to make sure that a company cannot
-effectively restrict the users of a free program by obtaining a
-restrictive license from a patent holder. Therefore, we insist that
-any patent license obtained for a version of the library must be
-consistent with the full freedom of use specified in this license.
-
- Most GNU software, including some libraries, is covered by the
-ordinary GNU General Public License. This license, the GNU Lesser
-General Public License, applies to certain designated libraries, and
-is quite different from the ordinary General Public License. We use
-this license for certain libraries in order to permit linking those
-libraries into non-free programs.
-
- When a program is linked with a library, whether statically or using
-a shared library, the combination of the two is legally speaking a
-combined work, a derivative of the original library. The ordinary
-General Public License therefore permits such linking only if the
-entire combination fits its criteria of freedom. The Lesser General
-Public License permits more lax criteria for linking other code with
-the library.
-
- We call this license the "Lesser" General Public License because it
-does Less to protect the user's freedom than the ordinary General
-Public License. It also provides other free software developers Less
-of an advantage over competing non-free programs. These disadvantages
-are the reason we use the ordinary General Public License for many
-libraries. However, the Lesser license provides advantages in certain
-special circumstances.
-
- For example, on rare occasions, there may be a special need to
-encourage the widest possible use of a certain library, so that it becomes
-a de-facto standard. To achieve this, non-free programs must be
-allowed to use the library. A more frequent case is that a free
-library does the same job as widely used non-free libraries. In this
-case, there is little to gain by limiting the free library to free
-software only, so we use the Lesser General Public License.
-
- In other cases, permission to use a particular library in non-free
-programs enables a greater number of people to use a large body of
-free software. For example, permission to use the GNU C Library in
-non-free programs enables many more people to use the whole GNU
-operating system, as well as its variant, the GNU/Linux operating
-system.
-
- Although the Lesser General Public License is Less protective of the
-users' freedom, it does ensure that the user of a program that is
-linked with the Library has the freedom and the wherewithal to run
-that program using a modified version of the Library.
-
- The precise terms and conditions for copying, distribution and
-modification follow. Pay close attention to the difference between a
-"work based on the library" and a "work that uses the library". The
-former contains code derived from the library, whereas the latter must
-be combined with the library in order to run.
-
- GNU LESSER GENERAL PUBLIC LICENSE
- TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
-
- 0. This License Agreement applies to any software library or other
-program which contains a notice placed by the copyright holder or
-other authorized party saying it may be distributed under the terms of
-this Lesser General Public License (also called "this License").
-Each licensee is addressed as "you".
-
- A "library" means a collection of software functions and/or data
-prepared so as to be conveniently linked with application programs
-(which use some of those functions and data) to form executables.
-
- The "Library", below, refers to any such software library or work
-which has been distributed under these terms. A "work based on the
-Library" means either the Library or any derivative work under
-copyright law: that is to say, a work containing the Library or a
-portion of it, either verbatim or with modifications and/or translated
-straightforwardly into another language. (Hereinafter, translation is
-included without limitation in the term "modification".)
-
- "Source code" for a work means the preferred form of the work for
-making modifications to it. For a library, 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 library.
-
- Activities other than copying, distribution and modification are not
-covered by this License; they are outside its scope. The act of
-running a program using the Library is not restricted, and output from
-such a program is covered only if its contents constitute a work based
-on the Library (independent of the use of the Library in a tool for
-writing it). Whether that is true depends on what the Library does
-and what the program that uses the Library does.
-
- 1. You may copy and distribute verbatim copies of the Library's
-complete 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 distribute a copy of this License along with the
-Library.
-
- 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 Library or any portion
-of it, thus forming a work based on the Library, 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) The modified work must itself be a software library.
-
- b) You must cause the files modified to carry prominent notices
- stating that you changed the files and the date of any change.
-
- c) You must cause the whole of the work to be licensed at no
- charge to all third parties under the terms of this License.
-
- d) If a facility in the modified Library refers to a function or a
- table of data to be supplied by an application program that uses
- the facility, other than as an argument passed when the facility
- is invoked, then you must make a good faith effort to ensure that,
- in the event an application does not supply such function or
- table, the facility still operates, and performs whatever part of
- its purpose remains meaningful.
-
- (For example, a function in a library to compute square roots has
- a purpose that is entirely well-defined independent of the
- application. Therefore, Subsection 2d requires that any
- application-supplied function or table used by this function must
- be optional: if the application does not supply it, the square
- root function must still compute square roots.)
-
-These requirements apply to the modified work as a whole. If
-identifiable sections of that work are not derived from the Library,
-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 Library, 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 Library.
-
-In addition, mere aggregation of another work not based on the Library
-with the Library (or with a work based on the Library) on a volume of
-a storage or distribution medium does not bring the other work under
-the scope of this License.
-
- 3. You may opt to apply the terms of the ordinary GNU General Public
-License instead of this License to a given copy of the Library. To do
-this, you must alter all the notices that refer to this License, so
-that they refer to the ordinary GNU General Public License, version 2,
-instead of to this License. (If a newer version than version 2 of the
-ordinary GNU General Public License has appeared, then you can specify
-that version instead if you wish.) Do not make any other change in
-these notices.
-
- Once this change is made in a given copy, it is irreversible for
-that copy, so the ordinary GNU General Public License applies to all
-subsequent copies and derivative works made from that copy.
-
- This option is useful when you wish to copy part of the code of
-the Library into a program that is not a library.
-
- 4. You may copy and distribute the Library (or a portion or
-derivative of it, under Section 2) in object code or executable form
-under the terms of Sections 1 and 2 above provided that you 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.
-
- If distribution of 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 satisfies the requirement to
-distribute the source code, even though third parties are not
-compelled to copy the source along with the object code.
-
- 5. A program that contains no derivative of any portion of the
-Library, but is designed to work with the Library by being compiled or
-linked with it, is called a "work that uses the Library". Such a
-work, in isolation, is not a derivative work of the Library, and
-therefore falls outside the scope of this License.
-
- However, linking a "work that uses the Library" with the Library
-creates an executable that is a derivative of the Library (because it
-contains portions of the Library), rather than a "work that uses the
-library". The executable is therefore covered by this License.
-Section 6 states terms for distribution of such executables.
-
- When a "work that uses the Library" uses material from a header file
-that is part of the Library, the object code for the work may be a
-derivative work of the Library even though the source code is not.
-Whether this is true is especially significant if the work can be
-linked without the Library, or if the work is itself a library. The
-threshold for this to be true is not precisely defined by law.
-
- If such an object file uses only numerical parameters, data
-structure layouts and accessors, and small macros and small inline
-functions (ten lines or less in length), then the use of the object
-file is unrestricted, regardless of whether it is legally a derivative
-work. (Executables containing this object code plus portions of the
-Library will still fall under Section 6.)
-
- Otherwise, if the work is a derivative of the Library, you may
-distribute the object code for the work under the terms of Section 6.
-Any executables containing that work also fall under Section 6,
-whether or not they are linked directly with the Library itself.
-
- 6. As an exception to the Sections above, you may also combine or
-link a "work that uses the Library" with the Library to produce a
-work containing portions of the Library, and distribute that work
-under terms of your choice, provided that the terms permit
-modification of the work for the customer's own use and reverse
-engineering for debugging such modifications.
-
- You must give prominent notice with each copy of the work that the
-Library is used in it and that the Library and its use are covered by
-this License. You must supply a copy of this License. If the work
-during execution displays copyright notices, you must include the
-copyright notice for the Library among them, as well as a reference
-directing the user to the copy of this License. Also, you must do one
-of these things:
-
- a) Accompany the work with the complete corresponding
- machine-readable source code for the Library including whatever
- changes were used in the work (which must be distributed under
- Sections 1 and 2 above); and, if the work is an executable linked
- with the Library, with the complete machine-readable "work that
- uses the Library", as object code and/or source code, so that the
- user can modify the Library and then relink to produce a modified
- executable containing the modified Library. (It is understood
- that the user who changes the contents of definitions files in the
- Library will not necessarily be able to recompile the application
- to use the modified definitions.)
-
- b) Use a suitable shared library mechanism for linking with the
- Library. A suitable mechanism is one that (1) uses at run time a
- copy of the library already present on the user's computer system,
- rather than copying library functions into the executable, and (2)
- will operate properly with a modified version of the library, if
- the user installs one, as long as the modified version is
- interface-compatible with the version that the work was made with.
-
- c) Accompany the work with a written offer, valid for at
- least three years, to give the same user the materials
- specified in Subsection 6a, above, for a charge no more
- than the cost of performing this distribution.
-
- d) If distribution of the work is made by offering access to copy
- from a designated place, offer equivalent access to copy the above
- specified materials from the same place.
-
- e) Verify that the user has already received a copy of these
- materials or that you have already sent this user a copy.
-
- For an executable, the required form of the "work that uses the
-Library" must include any data and utility programs needed for
-reproducing the executable from it. However, as a special exception,
-the materials to be 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.
-
- It may happen that this requirement contradicts the license
-restrictions of other proprietary libraries that do not normally
-accompany the operating system. Such a contradiction means you cannot
-use both them and the Library together in an executable that you
-distribute.
-
- 7. You may place library facilities that are a work based on the
-Library side-by-side in a single library together with other library
-facilities not covered by this License, and distribute such a combined
-library, provided that the separate distribution of the work based on
-the Library and of the other library facilities is otherwise
-permitted, and provided that you do these two things:
-
- a) Accompany the combined library with a copy of the same work
- based on the Library, uncombined with any other library
- facilities. This must be distributed under the terms of the
- Sections above.
-
- b) Give prominent notice with the combined library of the fact
- that part of it is a work based on the Library, and explaining
- where to find the accompanying uncombined form of the same work.
-
- 8. You may not copy, modify, sublicense, link with, or distribute
-the Library except as expressly provided under this License. Any
-attempt otherwise to copy, modify, sublicense, link with, or
-distribute the Library 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.
-
- 9. 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 Library or its derivative works. These actions are
-prohibited by law if you do not accept this License. Therefore, by
-modifying or distributing the Library (or any work based on the
-Library), you indicate your acceptance of this License to do so, and
-all its terms and conditions for copying, distributing or modifying
-the Library or works based on it.
-
- 10. Each time you redistribute the Library (or any work based on the
-Library), the recipient automatically receives a license from the
-original licensor to copy, distribute, link with or modify the Library
-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 with
-this License.
-
- 11. 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 Library at all. For example, if a patent
-license would not permit royalty-free redistribution of the Library 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 Library.
-
-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.
-
- 12. If the distribution and/or use of the Library is restricted in
-certain countries either by patents or by copyrighted interfaces, the
-original copyright holder who places the Library 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.
-
- 13. The Free Software Foundation may publish revised and/or new
-versions of the Lesser 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 Library
-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 Library does not specify a
-license version number, you may choose any version ever published by
-the Free Software Foundation.
-
- 14. If you wish to incorporate parts of the Library into other free
-programs whose distribution conditions are incompatible with these,
-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
-
- 15. BECAUSE THE LIBRARY IS LICENSED FREE OF CHARGE, THERE IS NO
-WARRANTY FOR THE LIBRARY, TO THE EXTENT PERMITTED BY APPLICABLE LAW.
-EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR
-OTHER PARTIES PROVIDE THE LIBRARY "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
-LIBRARY IS WITH YOU. SHOULD THE LIBRARY PROVE DEFECTIVE, YOU ASSUME
-THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION.
-
- 16. 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 LIBRARY 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
-LIBRARY (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 LIBRARY TO OPERATE WITH ANY OTHER SOFTWARE), 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 Libraries
-
- If you develop a new library, and you want it to be of the greatest
-possible use to the public, we recommend making it free software that
-everyone can redistribute and change. You can do so by permitting
-redistribution under these terms (or, alternatively, under the terms of the
-ordinary General Public License).
-
- To apply these terms, attach the following notices to the library. 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.
-
- <one line to give the library's name and a brief idea of what it does.>
- Copyright (C) <year> <name of author>
-
- This library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- This library 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
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with this library; 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.
-
-You should also get your employer (if you work as a programmer) or your
-school, if any, to sign a "copyright disclaimer" for the library, if
-necessary. Here is a sample; alter the names:
-
- Yoyodyne, Inc., hereby disclaims all copyright interest in the
- library `Frob' (a library for tweaking knobs) written by James Random Hacker.
-
- <signature of Ty Coon>, 1 April 1990
- Ty Coon, President of Vice
-
-That's all there is to it!
-
-
diff --git a/library/markdownify/TODO b/library/markdownify/TODO
deleted file mode 100644
index 06ec8508b..000000000
--- a/library/markdownify/TODO
+++ /dev/null
@@ -1,29 +0,0 @@
-Markdownify
-===========
-* handle non-markdownifiable lists (i.e. `<ul><li id="foobar">asdf</li></ul>`)
-* organize methods better (i.e. flushlinebreaks & setlinebreaks close to each other)
-* take a look at function names etc.
-* is the new (in rev. 93) lastclosedtag property needed?
-* word wrapping (some work is done but it's still very buggy)
-
-
-Markdownify Extra
-=================
-
-* handle table alignment with KEEP_HTML=false
-* handle tables without headings when KEEP_HTML=false is set
-* handle Markdown inside non-markdownable tags
-
-
-Implementation Thoughts
-=======================
-* non-markdownifiable lists and markdown inside non-markdownable tags as well as the current
- table implementation could be rewritten by using a rollback mechanism.
-
- example:
-
- <ul><li>asdf</li><li id="foobar">asdf</li></ul>
-
- we come to `<ul>`, know that this might fail and create a snapshot of our current parser
- we keep on parsing and when we reach `<li id="foobar">` we gotta rollback and keep this
- list in HTML format.
diff --git a/library/markdownify/example.php b/library/markdownify/example.php
deleted file mode 100644
index ef86dca83..000000000
--- a/library/markdownify/example.php
+++ /dev/null
@@ -1,51 +0,0 @@
-<?php
- error_reporting(E_ALL);
- if (!empty($_POST['input'])) {
- include 'markdownify_extra.php';
- if (!isset($_POST['leap'])) {
- $leap = MDFY_LINKS_EACH_PARAGRAPH;
- } else {
- $leap = $_POST['leap'];
- }
-
- if (!isset($_POST['keepHTML'])) {
- $keephtml = MDFY_KEEPHTML;
- } else {
- $keephtml = $_POST['keepHTML'];
- }
- if (!empty($_POST['extra'])) {
- $md = new Markdownify_Extra($leap, MDFY_BODYWIDTH, $keephtml);
- } else {
- $md = new Markdownify($leap, MDFY_BODYWIDTH, $keephtml);
- }
- if (ini_get('magic_quotes_gpc')) {
- $_POST['input'] = stripslashes($_POST['input']);
- }
- $output = $md->parseString($_POST['input']);
- } else {
- $_POST['input'] = '';
- }
-?><!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en-US" lang="en-US">
- <head>
- <meta http-equiv="Content-Type" content="text/html; charset=UTF-8"/>
- <title>HTML to Markdown Converter</title>
- </head>
- <body>
- <?php if (empty($_POST['input'])): ?>
- <form action="<?php echo $_SERVER['PHP_SELF']; ?>" method="post">
- <fieldset>
- <legend>HTML Input</legend>
- <textarea style="width:100%;" cols="85" rows="40" name="input"><?php echo htmlspecialchars($_POST['input'], ENT_NOQUOTES, 'UTF-8'); ?></textarea>
- </fieldset>
- <label for="extra">Markdownify Extra: <input name="extra" checked="checked" id="extra" type="checkbox" value="1" /></label>
- <label for="leap">Links after each block elem: <input name="leap" id="leap" type="checkbox" value="1" /></label>
- <label for="keepHTML">keep HTML: <input name="keepHTML" id="keepHTML" type="checkbox" value="1" checked="checked" /></label>
- <input type="submit" name="submit" value="submit" />
- </form>
- <?php else: ?>
- <h1 style="text-align:right;"><a href="<?php echo $_SERVER['PHP_SELF']; ?>">BACK</a></h1>
- <pre><?php echo htmlspecialchars($output, ENT_NOQUOTES, 'UTF-8'); ?></pre>
- <?php endif; ?>
- </body>
-</html> \ No newline at end of file
diff --git a/library/markdownify/markdownify.php b/library/markdownify/markdownify.php
deleted file mode 100644
index 0d4429a01..000000000
--- a/library/markdownify/markdownify.php
+++ /dev/null
@@ -1,1197 +0,0 @@
-<?php
-/**
- * Markdownify converts HTML Markup to [Markdown][1] (by [John Gruber][2]. It
- * also supports [Markdown Extra][3] by [Michel Fortin][4] via Markdownify_Extra.
- *
- * It all started as `html2text.php` - a port of [Aaron Swartz'][5] [`html2text.py`][6] - but
- * got a long way since. This is far more than a mere port now!
- * Starting with version 2.0.0 this is a complete rewrite and cannot be
- * compared to Aaron Swatz' `html2text.py` anylonger. I'm now using a HTML parser
- * (see `parsehtml.php` which I also wrote) which makes most of the evil
- * RegEx magic go away and additionally it gives a much cleaner class
- * structure. Also notably is the fact that I now try to prevent regressions by
- * utilizing testcases of Michel Fortin's [MDTest][7].
- *
- * [1]: http://daringfireball.com/projects/markdown
- * [2]: http://daringfireball.com/
- * [3]: http://www.michelf.com/projects/php-markdown/extra/
- * [4]: http://www.michelf.com/
- * [5]: http://www.aaronsw.com/
- * [6]: http://www.aaronsw.com/2002/html2text/
- * [7]: http://article.gmane.org/gmane.text.markdown.general/2540
- *
- * @version 2.0.0 alpha
- * @author Milian Wolff (<mail@milianw.de>, <http://milianw.de>)
- * @license LGPL, see LICENSE_LGPL.txt and the summary below
- * @copyright (C) 2007 Milian Wolff
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2.1 of the License, or (at your option) any later version.
- *
- * This library 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
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
- */
-
-/**
- * HTML Parser, see http://sf.net/projects/parseHTML
- */
-require_once dirname(__FILE__).'/parsehtml/parsehtml.php';
-
-/**
- * default configuration
- */
-define('MDFY_LINKS_EACH_PARAGRAPH', false);
-define('MDFY_BODYWIDTH', false);
-define('MDFY_KEEPHTML', true);
-
-/**
- * HTML to Markdown converter class
- */
-class Markdownify {
- /**
- * html parser object
- *
- * @var parseHTML
- */
- var $parser;
- /**
- * markdown output
- *
- * @var string
- */
- var $output;
- /**
- * stack with tags which where not converted to html
- *
- * @var array<string>
- */
- var $notConverted = array();
- /**
- * skip conversion to markdown
- *
- * @var bool
- */
- var $skipConversion = false;
- /* options */
- /**
- * keep html tags which cannot be converted to markdown
- *
- * @var bool
- */
- var $keepHTML = false;
- /**
- * wrap output, set to 0 to skip wrapping
- *
- * @var int
- */
- var $bodyWidth = 0;
- /**
- * minimum body width
- *
- * @var int
- */
- var $minBodyWidth = 25;
- /**
- * display links after each paragraph
- *
- * @var bool
- */
- var $linksAfterEachParagraph = false;
- /**
- * constructor, set options, setup parser
- *
- * @param bool $linksAfterEachParagraph wether or not to flush stacked links after each paragraph
- * defaults to false
- * @param int $bodyWidth wether or not to wrap the output to the given width
- * defaults to false
- * @param bool $keepHTML wether to keep non markdownable HTML or to discard it
- * defaults to true (HTML will be kept)
- * @return void
- */
- function Markdownify($linksAfterEachParagraph = MDFY_LINKS_EACH_PARAGRAPH, $bodyWidth = MDFY_BODYWIDTH, $keepHTML = MDFY_KEEPHTML) {
- $this->linksAfterEachParagraph = $linksAfterEachParagraph;
- $this->keepHTML = $keepHTML;
-
- if ($bodyWidth > $this->minBodyWidth) {
- $this->bodyWidth = intval($bodyWidth);
- } else {
- $this->bodyWidth = false;
- }
-
- $this->parser = new parseHTML;
- $this->parser->noTagsInCode = true;
-
- # we don't have to do this every time
- $search = array();
- $replace = array();
- foreach ($this->escapeInText as $s => $r) {
- array_push($search, '#(?<!\\\)'.$s.'#U');
- array_push($replace, $r);
- }
- $this->escapeInText = array(
- 'search' => $search,
- 'replace' => $replace
- );
- }
- /**
- * parse a HTML string
- *
- * @param string $html
- * @return string markdown formatted
- */
- function parseString($html) {
- $this->parser->html = $html;
- $this->parse();
- return $this->output;
- }
- /**
- * tags with elements which can be handled by markdown
- *
- * @var array<string>
- */
- var $isMarkdownable = array(
- 'p' => array(),
- 'ul' => array(),
- 'ol' => array(),
- 'li' => array(),
- 'br' => array(),
- 'blockquote' => array(),
- 'code' => array(),
- 'pre' => array(),
- 'a' => array(
- 'href' => 'required',
- 'title' => 'optional',
- ),
- 'strong' => array(),
- 'b' => array(),
- 'em' => array(),
- 'i' => array(),
- 'img' => array(
- 'src' => 'required',
- 'alt' => 'optional',
- 'title' => 'optional',
- ),
- 'h1' => array(),
- 'h2' => array(),
- 'h3' => array(),
- 'h4' => array(),
- 'h5' => array(),
- 'h6' => array(),
- 'hr' => array(),
- );
- /**
- * html tags to be ignored (contents will be parsed)
- *
- * @var array<string>
- */
- var $ignore = array(
- 'html',
- 'body',
- );
- /**
- * html tags to be dropped (contents will not be parsed!)
- *
- * @var array<string>
- */
- var $drop = array(
- 'script',
- 'head',
- 'style',
- 'form',
- 'area',
- 'object',
- 'param',
- 'iframe',
- );
- /**
- * Markdown indents which could be wrapped
- * @note: use strings in regex format
- *
- * @var array<string>
- */
- var $wrappableIndents = array(
- '\* ', # ul
- '\d. ', # ol
- '\d\d. ', # ol
- '> ', # blockquote
- '', # p
- );
- /**
- * list of chars which have to be escaped in normal text
- * @note: use strings in regex format
- *
- * @var array
- *
- * TODO: what's with block chars / sequences at the beginning of a block?
- */
- var $escapeInText = array(
- '([-*_])([ ]{0,2}\1){2,}' => '\\\\$0|', # hr
- '\*\*([^*\s]+)\*\*' => '\*\*$1\*\*', # strong
- '\*([^*\s]+)\*' => '\*$1\*', # em
- '__(?! |_)(.+)(?!<_| )__' => '\_\_$1\_\_', # em
- '_(?! |_)(.+)(?!<_| )_' => '\_$1\_', # em
- '`(.+)`' => '\`$1\`', # code
- '\[(.+)\](\s*\()' => '\[$1\]$2', # links: [text] (url) => [text\] (url)
- '\[(.+)\](\s*)\[(.*)\]' => '\[$1\]$2\[$3\]', # links: [text][id] => [text\][id\]
- );
- /**
- * wether last processed node was a block tag or not
- *
- * @var bool
- */
- var $lastWasBlockTag = false;
- /**
- * name of last closed tag
- *
- * @var string
- */
- var $lastClosedTag = '';
- /**
- * iterate through the nodes and decide what we
- * shall do with the current node
- *
- * @param void
- * @return void
- */
- function parse() {
- $this->output = '';
- # drop tags
- $this->parser->html = preg_replace('#<('.implode('|', $this->drop).')[^>]*>.*</\\1>#sU', '', $this->parser->html);
- while ($this->parser->nextNode()) {
- switch ($this->parser->nodeType) {
- case 'doctype':
- break;
- case 'pi':
- case 'comment':
- if ($this->keepHTML) {
- $this->flushLinebreaks();
- $this->out($this->parser->node);
- $this->setLineBreaks(2);
- }
- # else drop
- break;
- case 'text':
- $this->handleText();
- break;
- case 'tag':
- if (in_array($this->parser->tagName, $this->ignore)) {
- break;
- }
- if ($this->parser->isStartTag) {
- $this->flushLinebreaks();
- }
- if ($this->skipConversion) {
- $this->isMarkdownable(); # update notConverted
- $this->handleTagToText();
- continue;
- }
- if (!$this->parser->keepWhitespace && $this->parser->isBlockElement && $this->parser->isStartTag) {
- $this->parser->html = ltrim($this->parser->html);
- }
- if ($this->isMarkdownable()) {
- if ($this->parser->isBlockElement && $this->parser->isStartTag && !$this->lastWasBlockTag && !empty($this->output)) {
- if (!empty($this->buffer)) {
- $str =& $this->buffer[count($this->buffer) -1];
- } else {
- $str =& $this->output;
- }
- if (substr($str, -strlen($this->indent)-1) != "\n".$this->indent) {
- $str .= "\n".$this->indent;
- }
- }
- $func = 'handleTag_'.$this->parser->tagName;
- $this->$func();
- if ($this->linksAfterEachParagraph && $this->parser->isBlockElement && !$this->parser->isStartTag && empty($this->parser->openTags)) {
- $this->flushStacked();
- }
- if (!$this->parser->isStartTag) {
- $this->lastClosedTag = $this->parser->tagName;
- }
- } else {
- $this->handleTagToText();
- $this->lastClosedTag = '';
- }
- break;
- default:
- trigger_error('invalid node type', E_USER_ERROR);
- break;
- }
- $this->lastWasBlockTag = $this->parser->nodeType == 'tag' && $this->parser->isStartTag && $this->parser->isBlockElement;
- }
- if (!empty($this->buffer)) {
- trigger_error('buffer was not flushed, this is a bug. please report!', E_USER_WARNING);
- while (!empty($this->buffer)) {
- $this->out($this->unbuffer());
- }
- }
- ### cleanup
- $this->output = rtrim(str_replace('&amp;', '&', str_replace('&lt;', '<', str_replace('&gt;', '>', $this->output))));
- # end parsing, flush stacked tags
- $this->flushStacked();
- $this->stack = array();
- }
- /**
- * check if current tag can be converted to Markdown
- *
- * @param void
- * @return bool
- */
- function isMarkdownable() {
- if (!isset($this->isMarkdownable[$this->parser->tagName])) {
- # simply not markdownable
- return false;
- }
- if ($this->parser->isStartTag) {
- $return = true;
- if ($this->keepHTML) {
- $diff = array_diff(array_keys($this->parser->tagAttributes), array_keys($this->isMarkdownable[$this->parser->tagName]));
- if (!empty($diff)) {
- # non markdownable attributes given
- $return = false;
- }
- }
- if ($return) {
- foreach ($this->isMarkdownable[$this->parser->tagName] as $attr => $type) {
- if ($type == 'required' && !isset($this->parser->tagAttributes[$attr])) {
- # required markdown attribute not given
- $return = false;
- break;
- }
- }
- }
- if (!$return) {
- array_push($this->notConverted, $this->parser->tagName.'::'.implode('/', $this->parser->openTags));
- }
- return $return;
- } else {
- if (!empty($this->notConverted) && end($this->notConverted) === $this->parser->tagName.'::'.implode('/', $this->parser->openTags)) {
- array_pop($this->notConverted);
- return false;
- }
- return true;
- }
- }
- /**
- * output all stacked tags
- *
- * @param void
- * @return void
- */
- function flushStacked() {
- # links
- foreach ($this->stack as $tag => $a) {
- if (!empty($a)) {
- call_user_func(array(&$this, 'flushStacked_'.$tag));
- }
- }
- }
- /**
- * output link references (e.g. [1]: http://example.com "title");
- *
- * @param void
- * @return void
- */
- function flushStacked_a() {
- $out = false;
- foreach ($this->stack['a'] as $k => $tag) {
- if (!isset($tag['unstacked'])) {
- if (!$out) {
- $out = true;
- $this->out("\n\n", true);
- } else {
- $this->out("\n", true);
- }
- $this->out(' ['.$tag['linkID'].']: '.$tag['href'].(isset($tag['title']) ? ' "'.$tag['title'].'"' : ''), true);
- $tag['unstacked'] = true;
- $this->stack['a'][$k] = $tag;
- }
- }
- }
- /**
- * flush enqued linebreaks
- *
- * @param void
- * @return void
- */
- function flushLinebreaks() {
- if ($this->lineBreaks && !empty($this->output)) {
- $this->out(str_repeat("\n".$this->indent, $this->lineBreaks), true);
- }
- $this->lineBreaks = 0;
- }
- /**
- * handle non Markdownable tags
- *
- * @param void
- * @return void
- */
- function handleTagToText() {
- if (!$this->keepHTML) {
- if (!$this->parser->isStartTag && $this->parser->isBlockElement) {
- $this->setLineBreaks(2);
- }
- } else {
- # dont convert to markdown inside this tag
- /** TODO: markdown extra **/
- if (!$this->parser->isEmptyTag) {
- if ($this->parser->isStartTag) {
- if (!$this->skipConversion) {
- $this->skipConversion = $this->parser->tagName.'::'.implode('/', $this->parser->openTags);
- }
- } else {
- if ($this->skipConversion == $this->parser->tagName.'::'.implode('/', $this->parser->openTags)) {
- $this->skipConversion = false;
- }
- }
- }
-
- if ($this->parser->isBlockElement) {
- if ($this->parser->isStartTag) {
- if (in_array($this->parent(), array('ins', 'del'))) {
- # looks like ins or del are block elements now
- $this->out("\n", true);
- $this->indent(' ');
- }
- if ($this->parser->tagName != 'pre') {
- $this->out($this->parser->node."\n".$this->indent);
- if (!$this->parser->isEmptyTag) {
- $this->indent(' ');
- } else {
- $this->setLineBreaks(1);
- }
- $this->parser->html = ltrim($this->parser->html);
- } else {
- # don't indent inside <pre> tags
- $this->out($this->parser->node);
- static $indent;
- $indent = $this->indent;
- $this->indent = '';
- }
- } else {
- if (!$this->parser->keepWhitespace) {
- $this->output = rtrim($this->output);
- }
- if ($this->parser->tagName != 'pre') {
- $this->indent(' ');
- $this->out("\n".$this->indent.$this->parser->node);
- } else {
- # reset indentation
- $this->out($this->parser->node);
- static $indent;
- $this->indent = $indent;
- }
-
- if (in_array($this->parent(), array('ins', 'del'))) {
- # ins or del was block element
- $this->out("\n");
- $this->indent(' ');
- }
- if ($this->parser->tagName == 'li') {
- $this->setLineBreaks(1);
- } else {
- $this->setLineBreaks(2);
- }
- }
- } else {
- $this->out($this->parser->node);
- }
- if (in_array($this->parser->tagName, array('code', 'pre'))) {
- if ($this->parser->isStartTag) {
- $this->buffer();
- } else {
- # add stuff so cleanup just reverses this
- $this->out(str_replace('&lt;', '&amp;lt;', str_replace('&gt;', '&amp;gt;', $this->unbuffer())));
- }
- }
- }
- }
- /**
- * handle plain text
- *
- * @param void
- * @return void
- */
- function handleText() {
- if ($this->hasParent('pre') && strpos($this->parser->node, "\n") !== false) {
- $this->parser->node = str_replace("\n", "\n".$this->indent, $this->parser->node);
- }
- if (!$this->hasParent('code') && !$this->hasParent('pre')) {
- # entity decode
- $this->parser->node = $this->decode($this->parser->node);
- if (!$this->skipConversion) {
- # escape some chars in normal Text
- $this->parser->node = preg_replace($this->escapeInText['search'], $this->escapeInText['replace'], $this->parser->node);
- }
- } else {
- $this->parser->node = str_replace(array('&quot;', '&apos'), array('"', '\''), $this->parser->node);
- }
- $this->out($this->parser->node);
- $this->lastClosedTag = '';
- }
- /**
- * handle <em> and <i> tags
- *
- * @param void
- * @return void
- */
- function handleTag_em() {
- $this->out('*', true);
- }
- function handleTag_i() {
- $this->handleTag_em();
- }
- /**
- * handle <strong> and <b> tags
- *
- * @param void
- * @return void
- */
- function handleTag_strong() {
- $this->out('**', true);
- }
- function handleTag_b() {
- $this->handleTag_strong();
- }
- /**
- * handle <h1> tags
- *
- * @param void
- * @return void
- */
- function handleTag_h1() {
- $this->handleHeader(1);
- }
- /**
- * handle <h2> tags
- *
- * @param void
- * @return void
- */
- function handleTag_h2() {
- $this->handleHeader(2);
- }
- /**
- * handle <h3> tags
- *
- * @param void
- * @return void
- */
- function handleTag_h3() {
- $this->handleHeader(3);
- }
- /**
- * handle <h4> tags
- *
- * @param void
- * @return void
- */
- function handleTag_h4() {
- $this->handleHeader(4);
- }
- /**
- * handle <h5> tags
- *
- * @param void
- * @return void
- */
- function handleTag_h5() {
- $this->handleHeader(5);
- }
- /**
- * handle <h6> tags
- *
- * @param void
- * @return void
- */
- function handleTag_h6() {
- $this->handleHeader(6);
- }
- /**
- * number of line breaks before next inline output
- */
- var $lineBreaks = 0;
- /**
- * handle header tags (<h1> - <h6>)
- *
- * @param int $level 1-6
- * @return void
- */
- function handleHeader($level) {
- if ($this->parser->isStartTag) {
- $this->out(str_repeat('#', $level).' ', true);
- } else {
- $this->setLineBreaks(2);
- }
- }
- /**
- * handle <p> tags
- *
- * @param void
- * @return void
- */
- function handleTag_p() {
- if (!$this->parser->isStartTag) {
- $this->setLineBreaks(2);
- }
- }
- /**
- * handle <a> tags
- *
- * @param void
- * @return void
- */
- function handleTag_a() {
- if ($this->parser->isStartTag) {
- $this->buffer();
- if (isset($this->parser->tagAttributes['title'])) {
- $this->parser->tagAttributes['title'] = $this->decode($this->parser->tagAttributes['title']);
- } else {
- $this->parser->tagAttributes['title'] = null;
- }
- $this->parser->tagAttributes['href'] = $this->decode(trim($this->parser->tagAttributes['href']));
- $this->stack();
- } else {
- $tag = $this->unstack();
- $buffer = $this->unbuffer();
-
- if (empty($tag['href']) && empty($tag['title'])) {
- # empty links... testcase mania, who would possibly do anything like that?!
- $this->out('['.$buffer.']()', true);
- return;
- }
-
- if ($buffer == $tag['href'] && empty($tag['title'])) {
- # <http://example.com>
- $this->out('<'.$buffer.'>', true);
- return;
- }
-
- $bufferDecoded = $this->decode(trim($buffer));
- if (substr($tag['href'], 0, 7) == 'mailto:' && 'mailto:'.$bufferDecoded == $tag['href']) {
- if (is_null($tag['title'])) {
- # <mail@example.com>
- $this->out('<'.$bufferDecoded.'>', true);
- return;
- }
- # [mail@example.com][1]
- # ...
- # [1]: mailto:mail@example.com Title
- $tag['href'] = 'mailto:'.$bufferDecoded;
- }
-
- $this->out('['.$buffer.']('.$tag['href'].' "'.$tag['title'].'")', true);
-
-/*
- # [This link][id]
- foreach ($this->stack['a'] as $tag2) {
- if ($tag2['href'] == $tag['href'] && $tag2['title'] === $tag['title']) {
- $tag['linkID'] = $tag2['linkID'];
- break;
- }
- }
- if (!isset($tag['linkID'])) {
- $tag['linkID'] = count($this->stack['a']) + 1;
- array_push($this->stack['a'], $tag);
- }
-
- $this->out('['.$buffer.']['.$tag['linkID'].']', true);
-*/
- }
- }
- /**
- * handle <img /> tags
- *
- * @param void
- * @return void
- */
- function handleTag_img() {
- if (!$this->parser->isStartTag) {
- return; # just to be sure this is really an empty tag...
- }
-
- if (isset($this->parser->tagAttributes['title'])) {
- $this->parser->tagAttributes['title'] = $this->decode($this->parser->tagAttributes['title']);
- } else {
- $this->parser->tagAttributes['title'] = null;
- }
- if (isset($this->parser->tagAttributes['alt'])) {
- $this->parser->tagAttributes['alt'] = $this->decode($this->parser->tagAttributes['alt']);
- } else {
- $this->parser->tagAttributes['alt'] = null;
- }
-
- if (empty($this->parser->tagAttributes['src'])) {
- # support for "empty" images... dunno if this is really needed
- # but there are some testcases which do that...
- if (!empty($this->parser->tagAttributes['title'])) {
- $this->parser->tagAttributes['title'] = ' '.$this->parser->tagAttributes['title'].' ';
- }
- $this->out('!['.$this->parser->tagAttributes['alt'].']('.$this->parser->tagAttributes['title'].')', true);
- return;
- } else {
- $this->parser->tagAttributes['src'] = $this->decode($this->parser->tagAttributes['src']);
- }
-
-// ![Alt text](/path/to/img.jpg "Optional title")
- if ($this->parser->tagAttributes['title'] != "")
- $this->out('!['.$this->parser->tagAttributes['alt'].']('.$this->parser->tagAttributes['src'].' "'.$this->parser->tagAttributes['title'].'")', true);
- else
- $this->out('!['.$this->parser->tagAttributes['alt'].']('.$this->parser->tagAttributes['src'].')', true);
-
-/*
- # [This link][id]
- $link_id = false;
- if (!empty($this->stack['a'])) {
- foreach ($this->stack['a'] as $tag) {
- if ($tag['href'] == $this->parser->tagAttributes['src']
- && $tag['title'] === $this->parser->tagAttributes['title']) {
- $link_id = $tag['linkID'];
- break;
- }
- }
- } else {
- $this->stack['a'] = array();
- }
- if (!$link_id) {
- $link_id = count($this->stack['a']) + 1;
- $tag = array(
- 'href' => $this->parser->tagAttributes['src'],
- 'linkID' => $link_id,
- 'title' => $this->parser->tagAttributes['title']
- );
- array_push($this->stack['a'], $tag);
- }
-
- $this->out('!['.$this->parser->tagAttributes['alt'].']['.$link_id.']', true);
-*/
- }
- /**
- * handle <code> tags
- *
- * @param void
- * @return void
- */
- function handleTag_code() {
- if ($this->hasParent('pre')) {
- # ignore code blocks inside <pre>
- return;
- }
- if ($this->parser->isStartTag) {
- $this->buffer();
- } else {
- $buffer = $this->unbuffer();
- # use as many backticks as needed
- preg_match_all('#`+#', $buffer, $matches);
- if (!empty($matches[0])) {
- rsort($matches[0]);
-
- $ticks = '`';
- while (true) {
- if (!in_array($ticks, $matches[0])) {
- break;
- }
- $ticks .= '`';
- }
- } else {
- $ticks = '`';
- }
- if ($buffer[0] == '`' || substr($buffer, -1) == '`') {
- $buffer = ' '.$buffer.' ';
- }
- $this->out($ticks.$buffer.$ticks, true);
- }
- }
- /**
- * handle <pre> tags
- *
- * @param void
- * @return void
- */
- function handleTag_pre() {
- if ($this->keepHTML && $this->parser->isStartTag) {
- # check if a simple <code> follows
- if (!preg_match('#^\s*<code\s*>#Us', $this->parser->html)) {
- # this is no standard markdown code block
- $this->handleTagToText();
- return;
- }
- }
- $this->indent(' ');
- if (!$this->parser->isStartTag) {
- $this->setLineBreaks(2);
- } else {
- $this->parser->html = ltrim($this->parser->html);
- }
- }
- /**
- * handle <blockquote> tags
- *
- * @param void
- * @return void
- */
- function handleTag_blockquote() {
- $this->indent('> ');
- }
- /**
- * handle <ul> tags
- *
- * @param void
- * @return void
- */
- function handleTag_ul() {
- if ($this->parser->isStartTag) {
- $this->stack();
- if (!$this->keepHTML && $this->lastClosedTag == $this->parser->tagName) {
- $this->out("\n".$this->indent.'<!-- -->'."\n".$this->indent."\n".$this->indent);
- }
- } else {
- $this->unstack();
- if ($this->parent() != 'li' || preg_match('#^\s*(</li\s*>\s*<li\s*>\s*)?<(p|blockquote)\s*>#sU', $this->parser->html)) {
- # dont make Markdown add unneeded paragraphs
- $this->setLineBreaks(2);
- }
- }
- }
- /**
- * handle <ul> tags
- *
- * @param void
- * @return void
- */
- function handleTag_ol() {
- # same as above
- $this->parser->tagAttributes['num'] = 0;
- $this->handleTag_ul();
- }
- /**
- * handle <li> tags
- *
- * @param void
- * @return void
- */
- function handleTag_li() {
- if ($this->parent() == 'ol') {
- $parent =& $this->getStacked('ol');
- if ($this->parser->isStartTag) {
- $parent['num']++;
- $this->out($parent['num'].'.'.str_repeat(' ', 3 - strlen($parent['num'])), true);
- }
- $this->indent(' ', false);
- } else {
- if ($this->parser->isStartTag) {
- $this->out('* ', true);
- }
- $this->indent(' ', false);
- }
- if (!$this->parser->isStartTag) {
- $this->setLineBreaks(1);
- }
- }
- /**
- * handle <hr /> tags
- *
- * @param void
- * @return void
- */
- function handleTag_hr() {
- if (!$this->parser->isStartTag) {
- return; # just to be sure this really is an empty tag
- }
- $this->out('* * *', true);
- $this->setLineBreaks(2);
- }
- /**
- * handle <br /> tags
- *
- * @param void
- * @return void
- */
- function handleTag_br() {
- $this->out(" \n".$this->indent, true);
- $this->parser->html = ltrim($this->parser->html);
- }
- /**
- * node stack, e.g. for <a> and <abbr> tags
- *
- * @var array<array>
- */
- var $stack = array();
- /**
- * add current node to the stack
- * this only stores the attributes
- *
- * @param void
- * @return void
- */
- function stack() {
- if (!isset($this->stack[$this->parser->tagName])) {
- $this->stack[$this->parser->tagName] = array();
- }
- array_push($this->stack[$this->parser->tagName], $this->parser->tagAttributes);
- }
- /**
- * remove current tag from stack
- *
- * @param void
- * @return array
- */
- function unstack() {
- if (!isset($this->stack[$this->parser->tagName]) || !is_array($this->stack[$this->parser->tagName])) {
- trigger_error('Trying to unstack from empty stack. This must not happen.', E_USER_ERROR);
- }
- return array_pop($this->stack[$this->parser->tagName]);
- }
- /**
- * get last stacked element of type $tagName
- *
- * @param string $tagName
- * @return array
- */
- function & getStacked($tagName) {
- // no end() so it can be referenced
- return $this->stack[$tagName][count($this->stack[$tagName])-1];
- }
- /**
- * set number of line breaks before next start tag
- *
- * @param int $number
- * @return void
- */
- function setLineBreaks($number) {
- if ($this->lineBreaks < $number) {
- $this->lineBreaks = $number;
- }
- }
- /**
- * stores current buffers
- *
- * @var array<string>
- */
- var $buffer = array();
- /**
- * buffer next parser output until unbuffer() is called
- *
- * @param void
- * @return void
- */
- function buffer() {
- array_push($this->buffer, '');
- }
- /**
- * end current buffer and return buffered output
- *
- * @param void
- * @return string
- */
- function unbuffer() {
- return array_pop($this->buffer);
- }
- /**
- * append string to the correct var, either
- * directly to $this->output or to the current
- * buffers
- *
- * @param string $put
- * @return void
- */
- function out($put, $nowrap = false) {
- if (empty($put)) {
- return;
- }
- if (!empty($this->buffer)) {
- $this->buffer[count($this->buffer) - 1] .= $put;
- } else {
- if ($this->bodyWidth && !$this->parser->keepWhitespace) { # wrap lines
- // get last line
- $pos = strrpos($this->output, "\n");
- if ($pos === false) {
- $line = $this->output;
- } else {
- $line = substr($this->output, $pos);
- }
-
- if ($nowrap) {
- if ($put[0] != "\n" && $this->strlen($line) + $this->strlen($put) > $this->bodyWidth) {
- $this->output .= "\n".$this->indent.$put;
- } else {
- $this->output .= $put;
- }
- return;
- } else {
- $put .= "\n"; # make sure we get all lines in the while below
- $lineLen = $this->strlen($line);
- while ($pos = strpos($put, "\n")) {
- $putLine = substr($put, 0, $pos+1);
- $put = substr($put, $pos+1);
- $putLen = $this->strlen($putLine);
- if ($lineLen + $putLen < $this->bodyWidth) {
- $this->output .= $putLine;
- $lineLen = $putLen;
- } else {
- $split = preg_split('#^(.{0,'.($this->bodyWidth - $lineLen).'})\b#', $putLine, 2, PREG_SPLIT_OFFSET_CAPTURE | PREG_SPLIT_DELIM_CAPTURE);
- $this->output .= rtrim($split[1][0])."\n".$this->indent.$this->wordwrap(ltrim($split[2][0]), $this->bodyWidth, "\n".$this->indent, false);
- }
- }
- $this->output = substr($this->output, 0, -1);
- return;
- }
- } else {
- $this->output .= $put;
- }
- }
- }
- /**
- * current indentation
- *
- * @var string
- */
- var $indent = '';
- /**
- * indent next output (start tag) or unindent (end tag)
- *
- * @param string $str indentation
- * @param bool $output add indendation to output
- * @return void
- */
- function indent($str, $output = true) {
- if ($this->parser->isStartTag) {
- $this->indent .= $str;
- if ($output) {
- $this->out($str, true);
- }
- } else {
- $this->indent = substr($this->indent, 0, -strlen($str));
- }
- }
- /**
- * decode email addresses
- *
- * @author derernst@gmx.ch <http://www.php.net/manual/en/function.html-entity-decode.php#68536>
- * @author Milian Wolff <http://milianw.de>
- */
- function decode($text, $quote_style = ENT_QUOTES) {
- if (version_compare(PHP_VERSION, '5', '>=')) {
- # UTF-8 is only supported in PHP 5.x.x and above
- $text = html_entity_decode($text, $quote_style, 'UTF-8');
- } else {
- if (function_exists('html_entity_decode')) {
- $text = html_entity_decode($text, $quote_style, 'ISO-8859-1');
- } else {
- static $trans_tbl;
- if (!isset($trans_tbl)) {
- $trans_tbl = array_flip(get_html_translation_table(HTML_ENTITIES, $quote_style));
- }
- $text = strtr($text, $trans_tbl);
- }
- $text = preg_replace_callback('~&#x([0-9a-f]+);~i', array(&$this, '_decode_hex'), $text);
- $text = preg_replace_callback('~&#(\d{2,5});~', array(&$this, '_decode_numeric'), $text);
- }
- return $text;
- }
- /**
- * callback for decode() which converts a hexadecimal entity to UTF-8
- *
- * @param array $matches
- * @return string UTF-8 encoded
- */
- function _decode_hex($matches) {
- return $this->unichr(hexdec($matches[1]));
- }
- /**
- * callback for decode() which converts a numerical entity to UTF-8
- *
- * @param array $matches
- * @return string UTF-8 encoded
- */
- function _decode_numeric($matches) {
- return $this->unichr($matches[1]);
- }
- /**
- * UTF-8 chr() which supports numeric entities
- *
- * @author grey - greywyvern - com <http://www.php.net/manual/en/function.chr.php#55978>
- * @param array $matches
- * @return string UTF-8 encoded
- */
- function unichr($dec) {
- if ($dec < 128) {
- $utf = chr($dec);
- } else if ($dec < 2048) {
- $utf = chr(192 + (($dec - ($dec % 64)) / 64));
- $utf .= chr(128 + ($dec % 64));
- } else {
- $utf = chr(224 + (($dec - ($dec % 4096)) / 4096));
- $utf .= chr(128 + ((($dec % 4096) - ($dec % 64)) / 64));
- $utf .= chr(128 + ($dec % 64));
- }
- return $utf;
- }
- /**
- * UTF-8 strlen()
- *
- * @param string $str
- * @return int
- *
- * @author dtorop 932 at hotmail dot com <http://www.php.net/manual/en/function.strlen.php#37975>
- * @author Milian Wolff <http://milianw.de>
- */
- function strlen($str) {
- if (function_exists('mb_strlen')) {
- return mb_strlen($str, 'UTF-8');
- } else {
- return preg_match_all('/[\x00-\x7F\xC0-\xFD]/', $str, $var_empty);
- }
- }
- /**
- * wordwrap for utf8 encoded strings
- *
- * @param string $str
- * @param integer $len
- * @param string $what
- * @return string
- */
- function wordwrap($str, $width, $break, $cut = false){
- if (!$cut) {
- $regexp = '#^(?:[\x00-\x7F]|[\xC0-\xFF][\x80-\xBF]+){1,'.$width.'}\b#';
- } else {
- $regexp = '#^(?:[\x00-\x7F]|[\xC0-\xFF][\x80-\xBF]+){'.$width.'}#';
- }
- $return = '';
- while (preg_match($regexp, $str, $matches)) {
- $string = $matches[0];
- $str = ltrim(substr($str, strlen($string)));
- if (!$cut && isset($str[0]) && in_array($str[0], array('.', '!', ';', ':', '?', ','))) {
- $string .= $str[0];
- $str = ltrim(substr($str, 1));
- }
- $return .= $string.$break;
- }
- return $return.ltrim($str);
- }
- /**
- * check if current node has a $tagName as parent (somewhere, not only the direct parent)
- *
- * @param string $tagName
- * @return bool
- */
- function hasParent($tagName) {
- return in_array($tagName, $this->parser->openTags);
- }
- /**
- * get tagName of direct parent tag
- *
- * @param void
- * @return string $tagName
- */
- function parent() {
- return end($this->parser->openTags);
- }
-}
diff --git a/library/markdownify/markdownify_cli.php b/library/markdownify/markdownify_cli.php
deleted file mode 100755
index b3fffbd5c..000000000
--- a/library/markdownify/markdownify_cli.php
+++ /dev/null
@@ -1,33 +0,0 @@
-#!/usr/bin/php
-<?php
-require dirname(__FILE__) .'/markdownify_extra.php';
-
-function param($name, $default = false) {
- if (!in_array('--'.$name, $_SERVER['argv']))
- return $default;
- reset($_SERVER['argv']);
- while (each($_SERVER['argv'])) {
- if (current($_SERVER['argv']) == '--'.$name)
- break;
- }
- $value = next($_SERVER['argv']);
- if ($value === false || substr($value, 0, 2) == '--')
- return true;
- else
- return $value;
-}
-
-
-$input = stream_get_contents(STDIN);
-
-$linksAfterEachParagraph = param('links');
-$bodyWidth = param('width');
-$keepHTML = param('html', true);
-
-if (param('no_extra')) {
- $parser = new Markdownify($linksAfterEachParagraph, $bodyWidth, $keepHTML);
-} else {
- $parser = new Markdownify_Extra($linksAfterEachParagraph, $bodyWidth, $keepHTML);
-}
-
-echo $parser->parseString($input) ."\n"; \ No newline at end of file
diff --git a/library/markdownify/markdownify_extra.php b/library/markdownify/markdownify_extra.php
deleted file mode 100644
index e978a1c8a..000000000
--- a/library/markdownify/markdownify_extra.php
+++ /dev/null
@@ -1,489 +0,0 @@
-<?php
-/**
- * Class to convert HTML to Markdown with PHP Markdown Extra syntax support.
- *
- * @version 1.0.0 alpha
- * @author Milian Wolff (<mail@milianw.de>, <http://milianw.de>)
- * @license LGPL, see LICENSE_LGPL.txt and the summary below
- * @copyright (C) 2007 Milian Wolff
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2.1 of the License, or (at your option) any later version.
- *
- * This library 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
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
- */
-
-/**
- * standard Markdownify class
- */
-require_once dirname(__FILE__).'/markdownify.php';
-
-class Markdownify_Extra extends Markdownify {
- /**
- * table data, including rows with content and the maximum width of each col
- *
- * @var array
- */
- var $table = array();
- /**
- * current col
- *
- * @var int
- */
- var $col = -1;
- /**
- * current row
- *
- * @var int
- */
- var $row = 0;
- /**
- * constructor, see Markdownify::Markdownify() for more information
- */
- function Markdownify_Extra($linksAfterEachParagraph = MDFY_LINKS_EACH_PARAGRAPH, $bodyWidth = MDFY_BODYWIDTH, $keepHTML = MDFY_KEEPHTML) {
- parent::Markdownify($linksAfterEachParagraph, $bodyWidth, $keepHTML);
-
- ### new markdownable tags & attributes
- # header ids: # foo {bar}
- $this->isMarkdownable['h1']['id'] = 'optional';
- $this->isMarkdownable['h2']['id'] = 'optional';
- $this->isMarkdownable['h3']['id'] = 'optional';
- $this->isMarkdownable['h4']['id'] = 'optional';
- $this->isMarkdownable['h5']['id'] = 'optional';
- $this->isMarkdownable['h6']['id'] = 'optional';
- # tables
- $this->isMarkdownable['table'] = array();
- $this->isMarkdownable['th'] = array(
- 'align' => 'optional',
- );
- $this->isMarkdownable['td'] = array(
- 'align' => 'optional',
- );
- $this->isMarkdownable['tr'] = array();
- array_push($this->ignore, 'thead');
- array_push($this->ignore, 'tbody');
- array_push($this->ignore, 'tfoot');
- # definition lists
- $this->isMarkdownable['dl'] = array();
- $this->isMarkdownable['dd'] = array();
- $this->isMarkdownable['dt'] = array();
- # footnotes
- $this->isMarkdownable['fnref'] = array(
- 'target' => 'required',
- );
- $this->isMarkdownable['footnotes'] = array();
- $this->isMarkdownable['fn'] = array(
- 'name' => 'required',
- );
- $this->parser->blockElements['fnref'] = false;
- $this->parser->blockElements['fn'] = true;
- $this->parser->blockElements['footnotes'] = true;
- # abbr
- $this->isMarkdownable['abbr'] = array(
- 'title' => 'required',
- );
- # build RegEx lookahead to decide wether table can pe parsed or not
- $inlineTags = array_keys($this->parser->blockElements, false);
- $colContents = '(?:[^<]|<(?:'.implode('|', $inlineTags).'|[^a-z]))+';
- $this->tableLookaheadHeader = '{
- ^\s*(?:<thead\s*>)?\s* # open optional thead
- <tr\s*>\s*(?: # start required row with headers
- <th(?:\s+align=("|\')(?:left|center|right)\1)?\s*> # header with optional align
- \s*'.$colContents.'\s* # contents
- </th>\s* # close header
- )+</tr> # close row with headers
- \s*(?:</thead>)? # close optional thead
- }sxi';
- $this->tdSubstitute = '\s*'.$colContents.'\s* # contents
- </td>\s*';
- $this->tableLookaheadBody = '{
- \s*(?:<tbody\s*>)?\s* # open optional tbody
- (?:<tr\s*>\s* # start row
- %s # cols to be substituted
- </tr>)+ # close row
- \s*(?:</tbody>)? # close optional tbody
- \s*</table> # close table
- }sxi';
- }
- /**
- * handle header tags (<h1> - <h6>)
- *
- * @param int $level 1-6
- * @return void
- */
- function handleHeader($level) {
- static $id = null;
- if ($this->parser->isStartTag) {
- if (isset($this->parser->tagAttributes['id'])) {
- $id = $this->parser->tagAttributes['id'];
- }
- } else {
- if (!is_null($id)) {
- $this->out(' {#'.$id.'}');
- $id = null;
- }
- }
- parent::handleHeader($level);
- }
- /**
- * handle <abbr> tags
- *
- * @param void
- * @return void
- */
- function handleTag_abbr() {
- if ($this->parser->isStartTag) {
- $this->stack();
- $this->buffer();
- } else {
- $tag = $this->unstack();
- $tag['text'] = $this->unbuffer();
- $add = true;
- foreach ($this->stack['abbr'] as $stacked) {
- if ($stacked['text'] == $tag['text']) {
- /** TODO: differing abbr definitions, i.e. different titles for same text **/
- $add = false;
- break;
- }
- }
- $this->out($tag['text']);
- if ($add) {
- array_push($this->stack['abbr'], $tag);
- }
- }
- }
- /**
- * flush stacked abbr tags
- *
- * @param void
- * @return void
- */
- function flushStacked_abbr() {
- $out = array();
- foreach ($this->stack['abbr'] as $k => $tag) {
- if (!isset($tag['unstacked'])) {
- array_push($out, ' *['.$tag['text'].']: '.$tag['title']);
- $tag['unstacked'] = true;
- $this->stack['abbr'][$k] = $tag;
- }
- }
- if (!empty($out)) {
- $this->out("\n\n".implode("\n", $out));
- }
- }
- /**
- * handle <table> tags
- *
- * @param void
- * @return void
- */
- function handleTag_table() {
- if ($this->parser->isStartTag) {
- # check if upcoming table can be converted
- if ($this->keepHTML) {
- if (preg_match($this->tableLookaheadHeader, $this->parser->html, $matches)) {
- # header seems good, now check body
- # get align & number of cols
- preg_match_all('#<th(?:\s+align=("|\')(left|right|center)\1)?\s*>#si', $matches[0], $cols);
- $regEx = '';
- $i = 1;
- $aligns = array();
- foreach ($cols[2] as $align) {
- $align = strtolower($align);
- array_push($aligns, $align);
- if (empty($align)) {
- $align = 'left'; # default value
- }
- $td = '\s+align=("|\')'.$align.'\\'.$i;
- $i++;
- if ($align == 'left') {
- # look for empty align or left
- $td = '(?:'.$td.')?';
- }
- $td = '<td'.$td.'\s*>';
- $regEx .= $td.$this->tdSubstitute;
- }
- $regEx = sprintf($this->tableLookaheadBody, $regEx);
- if (preg_match($regEx, $this->parser->html, $matches, null, strlen($matches[0]))) {
- # this is a markdownable table tag!
- $this->table = array(
- 'rows' => array(),
- 'col_widths' => array(),
- 'aligns' => $aligns,
- );
- $this->row = 0;
- } else {
- # non markdownable table
- $this->handleTagToText();
- }
- } else {
- # non markdownable table
- $this->handleTagToText();
- }
- } else {
- $this->table = array(
- 'rows' => array(),
- 'col_widths' => array(),
- 'aligns' => array(),
- );
- $this->row = 0;
- }
- } else {
- # finally build the table in Markdown Extra syntax
- $separator = array();
- # seperator with correct align identifikators
- foreach($this->table['aligns'] as $col => $align) {
- if (!$this->keepHTML && !isset($this->table['col_widths'][$col])) {
- break;
- }
- $left = ' ';
- $right = ' ';
- switch ($align) {
- case 'left':
- $left = ':';
- break;
- case 'center':
- $right = ':';
- $left = ':';
- case 'right':
- $right = ':';
- break;
- }
- array_push($separator, $left.str_repeat('-', $this->table['col_widths'][$col]).$right);
- }
- $separator = '|'.implode('|', $separator).'|';
-
- $rows = array();
- # add padding
- array_walk_recursive($this->table['rows'], array(&$this, 'alignTdContent'));
- $header = array_shift($this->table['rows']);
- array_push($rows, '| '.implode(' | ', $header).' |');
- array_push($rows, $separator);
- foreach ($this->table['rows'] as $row) {
- array_push($rows, '| '.implode(' | ', $row).' |');
- }
- $this->out(implode("\n".$this->indent, $rows));
- $this->table = array();
- $this->setLineBreaks(2);
- }
- }
- /**
- * properly pad content so it is aligned as whished
- * should be used with array_walk_recursive on $this->table['rows']
- *
- * @param string &$content
- * @param int $col
- * @return void
- */
- function alignTdContent(&$content, $col) {
- switch ($this->table['aligns'][$col]) {
- default:
- case 'left':
- $content .= str_repeat(' ', $this->table['col_widths'][$col] - $this->strlen($content));
- break;
- case 'right':
- $content = str_repeat(' ', $this->table['col_widths'][$col] - $this->strlen($content)).$content;
- break;
- case 'center':
- $paddingNeeded = $this->table['col_widths'][$col] - $this->strlen($content);
- $left = floor($paddingNeeded / 2);
- $right = $paddingNeeded - $left;
- $content = str_repeat(' ', $left).$content.str_repeat(' ', $right);
- break;
- }
- }
- /**
- * handle <tr> tags
- *
- * @param void
- * @return void
- */
- function handleTag_tr() {
- if ($this->parser->isStartTag) {
- $this->col = -1;
- } else {
- $this->row++;
- }
- }
- /**
- * handle <td> tags
- *
- * @param void
- * @return void
- */
- function handleTag_td() {
- if ($this->parser->isStartTag) {
- $this->col++;
- if (!isset($this->table['col_widths'][$this->col])) {
- $this->table['col_widths'][$this->col] = 0;
- }
- $this->buffer();
- } else {
- $buffer = trim($this->unbuffer());
- $this->table['col_widths'][$this->col] = max($this->table['col_widths'][$this->col], $this->strlen($buffer));
- $this->table['rows'][$this->row][$this->col] = $buffer;
- }
- }
- /**
- * handle <th> tags
- *
- * @param void
- * @return void
- */
- function handleTag_th() {
- if (!$this->keepHTML && !isset($this->table['rows'][1]) && !isset($this->table['aligns'][$this->col+1])) {
- if (isset($this->parser->tagAttributes['align'])) {
- $this->table['aligns'][$this->col+1] = $this->parser->tagAttributes['align'];
- } else {
- $this->table['aligns'][$this->col+1] = '';
- }
- }
- $this->handleTag_td();
- }
- /**
- * handle <dl> tags
- *
- * @param void
- * @return void
- */
- function handleTag_dl() {
- if (!$this->parser->isStartTag) {
- $this->setLineBreaks(2);
- }
- }
- /**
- * handle <dt> tags
- *
- * @param void
- * @return void
- **/
- function handleTag_dt() {
- if (!$this->parser->isStartTag) {
- $this->setLineBreaks(1);
- }
- }
- /**
- * handle <dd> tags
- *
- * @param void
- * @return void
- */
- function handleTag_dd() {
- if ($this->parser->isStartTag) {
- if (substr(ltrim($this->parser->html), 0, 3) == '<p>') {
- # next comes a paragraph, so we'll need an extra line
- $this->out("\n".$this->indent);
- } elseif (substr($this->output, -2) == "\n\n") {
- $this->output = substr($this->output, 0, -1);
- }
- $this->out(': ');
- $this->indent(' ', false);
- } else {
- # lookahead for next dt
- if (substr(ltrim($this->parser->html), 0, 4) == '<dt>') {
- $this->setLineBreaks(2);
- } else {
- $this->setLineBreaks(1);
- }
- $this->indent(' ');
- }
- }
- /**
- * handle <fnref /> tags (custom footnote references, see markdownify_extra::parseString())
- *
- * @param void
- * @return void
- */
- function handleTag_fnref() {
- $this->out('[^'.$this->parser->tagAttributes['target'].']');
- }
- /**
- * handle <fn> tags (custom footnotes, see markdownify_extra::parseString()
- * and markdownify_extra::_makeFootnotes())
- *
- * @param void
- * @return void
- */
- function handleTag_fn() {
- if ($this->parser->isStartTag) {
- $this->out('[^'.$this->parser->tagAttributes['name'].']:');
- $this->setLineBreaks(1);
- } else {
- $this->setLineBreaks(2);
- }
- $this->indent(' ');
- }
- /**
- * handle <footnotes> tag (custom footnotes, see markdownify_extra::parseString()
- * and markdownify_extra::_makeFootnotes())
- *
- * @param void
- * @return void
- */
- function handleTag_footnotes() {
- if (!$this->parser->isStartTag) {
- $this->setLineBreaks(2);
- }
- }
- /**
- * parse a HTML string, clean up footnotes prior
- *
- * @param string $HTML input
- * @return string Markdown formatted output
- */
- function parseString($html) {
- /** TODO: custom markdown-extra options, e.g. titles & classes **/
- # <sup id="fnref:..."><a href"#fn..." rel="footnote">...</a></sup>
- # => <fnref target="..." />
- $html = preg_replace('@<sup id="fnref:([^"]+)">\s*<a href="#fn:\1" rel="footnote">\s*\d+\s*</a>\s*</sup>@Us', '<fnref target="$1" />', $html);
- # <div class="footnotes">
- # <hr />
- # <ol>
- #
- # <li id="fn:...">...</li>
- # ...
- #
- # </ol>
- # </div>
- # =>
- # <footnotes>
- # <fn name="...">...</fn>
- # ...
- # </footnotes>
- $html = preg_replace_callback('#<div class="footnotes">\s*<hr />\s*<ol>\s*(.+)\s*</ol>\s*</div>#Us', array(&$this, '_makeFootnotes'), $html);
- return parent::parseString($html);
- }
- /**
- * replace HTML representation of footnotes with something more easily parsable
- *
- * @note this is a callback to be used in parseString()
- *
- * @param array $matches
- * @return string
- */
- function _makeFootnotes($matches) {
- # <li id="fn:1">
- # ...
- # <a href="#fnref:block" rev="footnote">&#8617;</a></p>
- # </li>
- # => <fn name="1">...</fn>
- # remove footnote link
- $fns = preg_replace('@\s*(&#160;\s*)?<a href="#fnref:[^"]+" rev="footnote"[^>]*>&#8617;</a>\s*@s', '', $matches[1]);
- # remove empty paragraph
- $fns = preg_replace('@<p>\s*</p>@s', '', $fns);
- # <li id="fn:1">...</li> -> <footnote nr="1">...</footnote>
- $fns = str_replace('<li id="fn:', '<fn name="', $fns);
-
- $fns = '<footnotes>'.$fns.'</footnotes>';
- return preg_replace('#</li>\s*(?=(?:<fn|</footnotes>))#s', '</fn>$1', $fns);
- }
-} \ No newline at end of file
diff --git a/library/markdownify/parsehtml/parsehtml.php b/library/markdownify/parsehtml/parsehtml.php
deleted file mode 100644
index 1a8ecacda..000000000
--- a/library/markdownify/parsehtml/parsehtml.php
+++ /dev/null
@@ -1,618 +0,0 @@
-<?php
-/**
- * parseHTML is a HTML parser which works with PHP 4 and above.
- * It tries to handle invalid HTML to some degree.
- *
- * @version 1.0 beta
- * @author Milian Wolff (mail@milianw.de, http://milianw.de)
- * @license LGPL, see LICENSE_LGPL.txt and the summary below
- * @copyright (C) 2007 Milian Wolff
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2.1 of the License, or (at your option) any later version.
- *
- * This library 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
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
- */
-class parseHTML {
- /**
- * tags which are always empty (<br /> etc.)
- *
- * @var array<string>
- */
- var $emptyTags = array(
- 'br',
- 'hr',
- 'input',
- 'img',
- 'area',
- 'link',
- 'meta',
- 'param',
- );
- /**
- * tags with preformatted text
- * whitespaces wont be touched in them
- *
- * @var array<string>
- */
- var $preformattedTags = array(
- 'script',
- 'style',
- 'pre',
- 'code',
- );
- /**
- * supress HTML tags inside preformatted tags (see above)
- *
- * @var bool
- */
- var $noTagsInCode = false;
- /**
- * html to be parsed
- *
- * @var string
- */
- var $html = '';
- /**
- * node type:
- *
- * - tag (see isStartTag)
- * - text (includes cdata)
- * - comment
- * - doctype
- * - pi (processing instruction)
- *
- * @var string
- */
- var $nodeType = '';
- /**
- * current node content, i.e. either a
- * simple string (text node), or something like
- * <tag attrib="value"...>
- *
- * @var string
- */
- var $node = '';
- /**
- * wether current node is an opening tag (<a>) or not (</a>)
- * set to NULL if current node is not a tag
- * NOTE: empty tags (<br />) set this to true as well!
- *
- * @var bool | null
- */
- var $isStartTag = null;
- /**
- * wether current node is an empty tag (<br />) or not (<a></a>)
- *
- * @var bool | null
- */
- var $isEmptyTag = null;
- /**
- * tag name
- *
- * @var string | null
- */
- var $tagName = '';
- /**
- * attributes of current tag
- *
- * @var array (attribName=>value) | null
- */
- var $tagAttributes = null;
- /**
- * wether the current tag is a block element
- *
- * @var bool | null
- */
- var $isBlockElement = null;
-
- /**
- * keep whitespace
- *
- * @var int
- */
- var $keepWhitespace = 0;
- /**
- * list of open tags
- * count this to get current depth
- *
- * @var array
- */
- var $openTags = array();
- /**
- * list of block elements
- *
- * @var array
- * TODO: what shall we do with <del> and <ins> ?!
- */
- var $blockElements = array (
- # tag name => <bool> is block
- # block elements
- 'address' => true,
- 'blockquote' => true,
- 'center' => true,
- 'del' => true,
- 'dir' => true,
- 'div' => true,
- 'dl' => true,
- 'fieldset' => true,
- 'form' => true,
- 'h1' => true,
- 'h2' => true,
- 'h3' => true,
- 'h4' => true,
- 'h5' => true,
- 'h6' => true,
- 'hr' => true,
- 'ins' => true,
- 'isindex' => true,
- 'menu' => true,
- 'noframes' => true,
- 'noscript' => true,
- 'ol' => true,
- 'p' => true,
- 'pre' => true,
- 'table' => true,
- 'ul' => true,
- # set table elements and list items to block as well
- 'thead' => true,
- 'tbody' => true,
- 'tfoot' => true,
- 'td' => true,
- 'tr' => true,
- 'th' => true,
- 'li' => true,
- 'dd' => true,
- 'dt' => true,
- # header items and html / body as well
- 'html' => true,
- 'body' => true,
- 'head' => true,
- 'meta' => true,
- 'link' => true,
- 'style' => true,
- 'title' => true,
- # unfancy media tags, when indented should be rendered as block
- 'map' => true,
- 'object' => true,
- 'param' => true,
- 'embed' => true,
- 'area' => true,
- # inline elements
- 'a' => false,
- 'abbr' => false,
- 'acronym' => false,
- 'applet' => false,
- 'b' => false,
- 'basefont' => false,
- 'bdo' => false,
- 'big' => false,
- 'br' => false,
- 'button' => false,
- 'cite' => false,
- 'code' => false,
- 'del' => false,
- 'dfn' => false,
- 'em' => false,
- 'font' => false,
- 'i' => false,
- 'img' => false,
- 'ins' => false,
- 'input' => false,
- 'iframe' => false,
- 'kbd' => false,
- 'label' => false,
- 'q' => false,
- 'samp' => false,
- 'script' => false,
- 'select' => false,
- 'small' => false,
- 'span' => false,
- 'strong' => false,
- 'sub' => false,
- 'sup' => false,
- 'textarea' => false,
- 'tt' => false,
- 'var' => false,
- );
- /**
- * get next node, set $this->html prior!
- *
- * @param void
- * @return bool
- */
- function nextNode() {
- if (empty($this->html)) {
- # we are done with parsing the html string
- return false;
- }
- static $skipWhitespace = true;
- if ($this->isStartTag && !$this->isEmptyTag) {
- array_push($this->openTags, $this->tagName);
- if (in_array($this->tagName, $this->preformattedTags)) {
- # dont truncate whitespaces for <code> or <pre> contents
- $this->keepWhitespace++;
- }
- }
-
- if ($this->html[0] == '<') {
- $token = substr($this->html, 0, 9);
- if (substr($token, 0, 2) == '<?') {
- # xml prolog or other pi's
- /** TODO **/
- #trigger_error('this might need some work', E_USER_NOTICE);
- $pos = strpos($this->html, '>');
- $this->setNode('pi', $pos + 1);
- return true;
- }
- if (substr($token, 0, 4) == '<!--') {
- # comment
- $pos = strpos($this->html, '-->');
- if ($pos === false) {
- # could not find a closing -->, use next gt instead
- # this is firefox' behaviour
- $pos = strpos($this->html, '>') + 1;
- } else {
- $pos += 3;
- }
- $this->setNode('comment', $pos);
-
- $skipWhitespace = true;
- return true;
- }
- if ($token == '<!DOCTYPE') {
- # doctype
- $this->setNode('doctype', strpos($this->html, '>')+1);
-
- $skipWhitespace = true;
- return true;
- }
- if ($token == '<![CDATA[') {
- # cdata, use text node
-
- # remove leading <![CDATA[
- $this->html = substr($this->html, 9);
-
- $this->setNode('text', strpos($this->html, ']]>')+3);
-
- # remove trailing ]]> and trim
- $this->node = substr($this->node, 0, -3);
- $this->handleWhitespaces();
-
- $skipWhitespace = true;
- return true;
- }
- if ($this->parseTag()) {
- # seems to be a tag
- # handle whitespaces
- if ($this->isBlockElement) {
- $skipWhitespace = true;
- } else {
- $skipWhitespace = false;
- }
- return true;
- }
- }
- if ($this->keepWhitespace) {
- $skipWhitespace = false;
- }
- # when we get here it seems to be a text node
- $pos = strpos($this->html, '<');
- if ($pos === false) {
- $pos = strlen($this->html);
- }
- $this->setNode('text', $pos);
- $this->handleWhitespaces();
- if ($skipWhitespace && $this->node == ' ') {
- return $this->nextNode();
- }
- $skipWhitespace = false;
- return true;
- }
- /**
- * parse tag, set tag name and attributes, see if it's a closing tag and so forth...
- *
- * @param void
- * @return bool
- */
- function parseTag() {
- static $a_ord, $z_ord, $special_ords;
- if (!isset($a_ord)) {
- $a_ord = ord('a');
- $z_ord = ord('z');
- $special_ords = array(
- ord(':'), // for xml:lang
- ord('-'), // for http-equiv
- );
- }
-
- $tagName = '';
-
- $pos = 1;
- $isStartTag = $this->html[$pos] != '/';
- if (!$isStartTag) {
- $pos++;
- }
- # get tagName
- while (isset($this->html[$pos])) {
- $pos_ord = ord(strtolower($this->html[$pos]));
- if (($pos_ord >= $a_ord && $pos_ord <= $z_ord) || (!empty($tagName) && is_numeric($this->html[$pos]))) {
- $tagName .= $this->html[$pos];
- $pos++;
- } else {
- $pos--;
- break;
- }
- }
-
- $tagName = strtolower($tagName);
- if (empty($tagName) || !isset($this->blockElements[$tagName])) {
- # something went wrong => invalid tag
- $this->invalidTag();
- return false;
- }
- if ($this->noTagsInCode && end($this->openTags) == 'code' && !($tagName == 'code' && !$isStartTag)) {
- # we supress all HTML tags inside code tags
- $this->invalidTag();
- return false;
- }
-
- # get tag attributes
- /** TODO: in html 4 attributes do not need to be quoted **/
- $isEmptyTag = false;
- $attributes = array();
- $currAttrib = '';
- while (isset($this->html[$pos+1])) {
- $pos++;
- # close tag
- if ($this->html[$pos] == '>' || $this->html[$pos].$this->html[$pos+1] == '/>') {
- if ($this->html[$pos] == '/') {
- $isEmptyTag = true;
- $pos++;
- }
- break;
- }
-
- $pos_ord = ord(strtolower($this->html[$pos]));
- if ( ($pos_ord >= $a_ord && $pos_ord <= $z_ord) || in_array($pos_ord, $special_ords)) {
- # attribute name
- $currAttrib .= $this->html[$pos];
- } elseif (in_array($this->html[$pos], array(' ', "\t", "\n"))) {
- # drop whitespace
- } elseif (in_array($this->html[$pos].$this->html[$pos+1], array('="', "='"))) {
- # get attribute value
- $pos++;
- $await = $this->html[$pos]; # single or double quote
- $pos++;
- $value = '';
- while (isset($this->html[$pos]) && $this->html[$pos] != $await) {
- $value .= $this->html[$pos];
- $pos++;
- }
- $attributes[$currAttrib] = $value;
- $currAttrib = '';
- } else {
- $this->invalidTag();
- return false;
- }
- }
- if ($this->html[$pos] != '>') {
- $this->invalidTag();
- return false;
- }
-
- if (!empty($currAttrib)) {
- # html 4 allows something like <option selected> instead of <option selected="selected">
- $attributes[$currAttrib] = $currAttrib;
- }
- if (!$isStartTag) {
- if (!empty($attributes) || $tagName != end($this->openTags)) {
- # end tags must not contain any attributes
- # or maybe we did not expect a different tag to be closed
- $this->invalidTag();
- return false;
- }
- array_pop($this->openTags);
- if (in_array($tagName, $this->preformattedTags)) {
- $this->keepWhitespace--;
- }
- }
- $pos++;
- $this->node = substr($this->html, 0, $pos);
- $this->html = substr($this->html, $pos);
- $this->tagName = $tagName;
- $this->tagAttributes = $attributes;
- $this->isStartTag = $isStartTag;
- $this->isEmptyTag = $isEmptyTag || in_array($tagName, $this->emptyTags);
- if ($this->isEmptyTag) {
- # might be not well formed
- $this->node = preg_replace('# */? *>$#', ' />', $this->node);
- }
- $this->nodeType = 'tag';
- $this->isBlockElement = $this->blockElements[$tagName];
- return true;
- }
- /**
- * handle invalid tags
- *
- * @param void
- * @return void
- */
- function invalidTag() {
- $this->html = substr_replace($this->html, '&lt;', 0, 1);
- }
- /**
- * update all vars and make $this->html shorter
- *
- * @param string $type see description for $this->nodeType
- * @param int $pos to which position shall we cut?
- * @return void
- */
- function setNode($type, $pos) {
- if ($this->nodeType == 'tag') {
- # set tag specific vars to null
- # $type == tag should not be called here
- # see this::parseTag() for more
- $this->tagName = null;
- $this->tagAttributes = null;
- $this->isStartTag = null;
- $this->isEmptyTag = null;
- $this->isBlockElement = null;
-
- }
- $this->nodeType = $type;
- $this->node = substr($this->html, 0, $pos);
- $this->html = substr($this->html, $pos);
- }
- /**
- * check if $this->html begins with $str
- *
- * @param string $str
- * @return bool
- */
- function match($str) {
- return substr($this->html, 0, strlen($str)) == $str;
- }
- /**
- * truncate whitespaces
- *
- * @param void
- * @return void
- */
- function handleWhitespaces() {
- if ($this->keepWhitespace) {
- # <pre> or <code> before...
- return;
- }
- # truncate multiple whitespaces to a single one
- $this->node = preg_replace('#\s+#s', ' ', $this->node);
- }
- /**
- * normalize self::node
- *
- * @param void
- * @return void
- */
- function normalizeNode() {
- $this->node = '<';
- if (!$this->isStartTag) {
- $this->node .= '/'.$this->tagName.'>';
- return;
- }
- $this->node .= $this->tagName;
- foreach ($this->tagAttributes as $name => $value) {
- $this->node .= ' '.$name.'="'.str_replace('"', '&quot;', $value).'"';
- }
- if ($this->isEmptyTag) {
- $this->node .= ' /';
- }
- $this->node .= '>';
- }
-}
-
-/**
- * indent a HTML string properly
- *
- * @param string $html
- * @param string $indent optional
- * @return string
- */
-function indentHTML($html, $indent = " ", $noTagsInCode = false) {
- $parser = new parseHTML;
- $parser->noTagsInCode = $noTagsInCode;
- $parser->html = $html;
- $html = '';
- $last = true; # last tag was block elem
- $indent_a = array();
- while($parser->nextNode()) {
- if ($parser->nodeType == 'tag') {
- $parser->normalizeNode();
- }
- if ($parser->nodeType == 'tag' && $parser->isBlockElement) {
- $isPreOrCode = in_array($parser->tagName, array('code', 'pre'));
- if (!$parser->keepWhitespace && !$last && !$isPreOrCode) {
- $html = rtrim($html)."\n";
- }
- if ($parser->isStartTag) {
- $html .= implode($indent_a);
- if (!$parser->isEmptyTag) {
- array_push($indent_a, $indent);
- }
- } else {
- array_pop($indent_a);
- if (!$isPreOrCode) {
- $html .= implode($indent_a);
- }
- }
- $html .= $parser->node;
- if (!$parser->keepWhitespace && !($isPreOrCode && $parser->isStartTag)) {
- $html .= "\n";
- }
- $last = true;
- } else {
- if ($parser->nodeType == 'tag' && $parser->tagName == 'br') {
- $html .= $parser->node."\n";
- $last = true;
- continue;
- } elseif ($last && !$parser->keepWhitespace) {
- $html .= implode($indent_a);
- $parser->node = ltrim($parser->node);
- }
- $html .= $parser->node;
-
- if (in_array($parser->nodeType, array('comment', 'pi', 'doctype'))) {
- $html .= "\n";
- } else {
- $last = false;
- }
- }
- }
- return $html;
-}
-/*
-# testcase / example
-error_reporting(E_ALL);
-
-$html = '<p>Simple block on one line:</p>
-
-<div>foo</div>
-
-<p>And nested without indentation:</p>
-
-<div>
-<div>
-<div>
-foo
-</div>
-<div style=">"/>
-</div>
-<div>bar</div>
-</div>
-
-<p>And with attributes:</p>
-
-<div>
- <div id="foo">
- </div>
-</div>
-
-<p>This was broken in 1.0.2b7:</p>
-
-<div class="inlinepage">
-<div class="toggleableend">
-foo
-</div>
-</div>';
-#$html = '<a href="asdfasdf" title=\'asdf\' foo="bar">asdf</a>';
-echo indentHTML($html);
-die();
-*/
diff --git a/library/oauth2/.gitignore b/library/oauth2/.gitignore
deleted file mode 100644
index c43a667d4..000000000
--- a/library/oauth2/.gitignore
+++ /dev/null
@@ -1,5 +0,0 @@
-# Test Files #
-test/config/test.sqlite
-vendor
-composer.lock
-.idea
diff --git a/library/oauth2/.travis.yml b/library/oauth2/.travis.yml
deleted file mode 100644
index dd4aae4a6..000000000
--- a/library/oauth2/.travis.yml
+++ /dev/null
@@ -1,30 +0,0 @@
-language: php
-sudo: false
-cache:
- directories:
- - $HOME/.composer/cache
- - vendor
-php:
-- 5.3
-- 5.4
-- 5.5
-- 5.6
-- 7
-- hhvm
-env:
- global:
- - SKIP_MONGO_TESTS=1
- - secure: Bc5ZqvZ1YYpoPZNNuU2eCB8DS6vBYrAdfBtTenBs5NSxzb+Vjven4kWakbzaMvZjb/Ib7Uph7DGuOtJXpmxnvBXPLd707LZ89oFWN/yqQlZKCcm8iErvJCB5XL+/ONHj2iPdR242HJweMcat6bMCwbVWoNDidjtWMH0U2mYFy3M=
- - secure: R3bXlymyFiY2k2jf7+fv/J8i34wtXTkmD4mCr5Ps/U+vn9axm2VtvR2Nj+r7LbRjn61gzFE/xIVjYft/wOyBOYwysrfriydrnRVS0owh6y+7EyOyQWbRX11vVQMf8o31QCQE5BY58V5AJZW3MjoOL0FVlTgySJiJvdw6Pv18v+E=
-services:
-- mongodb
-- redis-server
-- cassandra
-before_install:
-- phpenv config-rm xdebug.ini || return 0
-install:
-- composer install --no-interaction
-before_script:
-- psql -c 'create database oauth2_server_php;' -U postgres
-after_script:
-- php test/cleanup.php
diff --git a/library/oauth2/CHANGELOG.md b/library/oauth2/CHANGELOG.md
deleted file mode 100644
index 03d925e06..000000000
--- a/library/oauth2/CHANGELOG.md
+++ /dev/null
@@ -1,152 +0,0 @@
-CHANGELOG for 1.x
-=================
-
-This changelog references the relevant changes (bug and security fixes) done
-in 1.x minor versions.
-
-To see the files changed for a given bug, go to https://github.com/bshaffer/oauth2-server-php/issues/### where ### is the bug number
-To get the diff between two versions, go to https://github.com/bshaffer/oauth2-server-php/compare/v1.0...v1.1
-To get the diff for a specific change, go to https://github.com/bshaffer/oauth2-server-php/commit/XXX where XXX is the change hash
-
-* 1.8.0 (2015-09-18)
-
- PR: https://github.com/bshaffer/oauth2-server-php/pull/643
-
- * bug #594 - adds jti
- * bug #598 - fixes lifetime configurations for JWTs
- * bug #634 - fixes travis builds, upgrade to containers
- * bug #586 - support for revoking tokens
- * bug #636 - Adds FirebaseJWT bridge
- * bug #639 - Mongo HHVM compatibility
-
-* 1.7.0 (2015-04-23)
-
- PR: https://github.com/bshaffer/oauth2-server-php/pull/572
-
- * bug #500 - PDO fetch mode changed from FETCH_BOTH to FETCH_ASSOC
- * bug #508 - Case insensitive for Bearer token header name ba716d4
- * bug #512 - validateRedirectUri is now public
- * bug #530 - Add PublicKeyInterface, UserClaimsInterface to Cassandra Storage
- * bug #505 - DynamoDB storage fixes
- * bug #556 - adds "code id_token" return type to openid connect
- * bug #563 - Include "issuer" config key for JwtAccessToken
- * bug #564 - Fixes JWT vulnerability
- * bug #571 - Added unset_refresh_token_after_use option
-
-* 1.6 (2015-01-16)
-
- PR: https://github.com/bshaffer/oauth2-server-php/pull/496
-
- * bug 437 - renames CryptoToken to JwtAccessToken / use_crypto_tokens to use_jwt_access_tokens
- * bug 447 - Adds a Couchbase storage implementation
- * bug 460 - Rename JWT claims to match spec
- * bug 470 - order does not matter for multi-valued response types
- * bug 471 - Make validateAuthorizeRequest available for POST in addition to GET
- * bug 475 - Adds JTI table definitiion
- * bug 481 - better randomness for generating access tokens
- * bug 480 - Use hash_equals() for signature verification (prevents remote timing attacks)
- * bugs 489, 491, 498 - misc other fixes
-
-* 1.5 (2014-08-27)
-
- PR: https://github.com/bshaffer/oauth2-server-php/pull/446
-
- * bug #399 - Add DynamoDB Support
- * bug #404 - renamed error name for malformed/expired tokens
- * bug #412 - Openid connect: fixes for claims with more than one scope / Add support for the prompt parameter ('consent' and 'none')
- * bug #411 - fixes xml output
- * bug #413 - fixes invalid format error
- * bug #401 - fixes code standards / whitespace
- * bug #354 - bundles PDO SQL with the library
- * [BC] bug #397 - refresh tokens should not be encrypted
- * bug #423 - makes "scope" optional for refresh token storage
-
-* 1.4 (2014-06-12)
-
- PR: https://github.com/bshaffer/oauth2-server-php/pull/392
-
- * bug #189 Storage\PDO - allows DSN string in constructor
- * bug #233 Bearer Tokens - allows token in request body for PUT requests
- * bug #346 Fixes open_basedir warning
- * bug #351 Adds OpenID Connect support
- * bug #355 Adds php 5.6 and HHVM to travis.ci testing
- * [BC] bug #358 Adds `getQuerystringIdentifier()` to the GrantType interface
- * bug #363 Encryption\JWT - Allows for subclassing JWT Headers
- * bug #349 Bearer Tokens - adds requestHasToken method for when access tokens are optional
- * bug #301 Encryption\JWT - fixes urlSafeB64Encode(): ensures newlines are replaced as expected
- * bug #323 ResourceController - client_id is no longer required to be returned when calling getAccessToken
- * bug #367 Storage\PDO - adds Postgres support
- * bug #368 Access Tokens - use mcrypt_create_iv or openssl_random_pseudo_bytes to create token string
- * bug #376 Request - allows case insensitive headers
- * bug #384 Storage\PDO - can pass in PDO options in constructor of PDO storage
- * misc fixes #361, #292, #373, #374, #379, #396
-* 1.3 (2014-02-27)
-
- PR: https://github.com/bshaffer/oauth2-server-php/pull/325
-
- * bug #311 adds cassandra storage
- * bug #298 fixes response code for user credentials grant type
- * bug #318 adds 'use_crypto_tokens' config to Server class for better DX
- * [BC] bug #320 pass client_id to getDefaultScope
- * bug #324 better feedback when running tests
- * bug #335 adds support for non-expiring refresh tokens
- * bug #333 fixes Pdo storage for getClientKey
- * bug #336 fixes Redis storage for expireAuthorizationCode
-
-* 1.2 (2014-01-03)
-
- PR: https://github.com/bshaffer/oauth2-server-php/pull/288
-
- * bug #285 changed response header from 200 to 401 when empty token received
- * bug #286 adds documentation and links to spec for not including error messages when no token is supplied
- * bug #280 ensures PHP warnings do not get thrown as a result of an invalid argument to $jwt->decode()
- * bug #279 predis wrong number of arguments
- * bug #277 Securing JS WebApp client secret w/ password grant type
-
-* 1.1 (2013-12-17)
-
- PR: https://github.com/bshaffer/oauth2-server-php/pull/276
-
- * bug #278 adds refresh token configuration to Server class
- * bug #274 Supplying a null client_id and client_secret grants API access
- * bug #244 [MongoStorage] More detailed implementation info
- * bug #268 Implement jti for JWT Bearer tokens to prevent replay attacks.
- * bug #266 Removing unused argument to getAccessTokenData
- * bug #247 Make Bearer token type consistent
- * bug #253 Fixing CryptoToken refresh token lifetime
- * bug #246 refactors public key logic to be more intuitive
- * bug #245 adds support for JSON crypto tokens
- * bug #230 Remove unused columns in oauth_clients
- * bug #215 makes Redis Scope Storage obey the same paradigm as PDO
- * bug #228 removes scope group
- * bug #227 squelches open basedir restriction error
- * bug #223 Updated docblocks for RefreshTokenInterface.php
- * bug #224 Adds protected properties
- * bug #217 Implement ScopeInterface for PDO, Redis
-
-* 1.0 (2013-08-12)
-
- * bug #203 Add redirect\_status_code config param for AuthorizeController
- * bug #205 ensures unnecessary ? is not set when ** bug
- * bug #204 Fixed call to LogicException
- * bug #202 Add explode to checkRestrictedGrant in PDO Storage
- * bug #197 adds support for 'false' default scope ** bug
- * bug #192 reference errors and adds tests
- * bug #194 makes some appropriate properties ** bug
- * bug #191 passes config to HttpBasic
- * bug #190 validates client credentials before ** bug
- * bug #171 Fix wrong redirect following authorization step
- * bug #187 client_id is now passed to getDefaultScope().
- * bug #176 Require refresh_token in getRefreshToken response
- * bug #174 make user\_id not required for refresh_token grant
- * bug #173 Duplication in JwtBearer Grant
- * bug #168 user\_id not required for authorization_code grant
- * bug #133 hardens default security for user object
- * bug #163 allows redirect\_uri on authorization_code to be NULL in docs example
- * bug #162 adds getToken on ResourceController for convenience
- * bug #161 fixes fatal error
- * bug #163 Invalid redirect_uri handling
- * bug #156 user\_id in OAuth2\_Storage_AuthorizationCodeInterface::getAuthorizationCode() response
- * bug #157 Fix for extending access and refresh tokens
- * bug #154 ResponseInterface: getParameter method is used in the library but not defined in the interface
- * bug #148 Add more detail to examples in Readme.md
diff --git a/library/oauth2/phpunit.xml b/library/oauth2/phpunit.xml
deleted file mode 100644
index e36403f0a..000000000
--- a/library/oauth2/phpunit.xml
+++ /dev/null
@@ -1,25 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-
-<phpunit backupGlobals="false"
- backupStaticAttributes="false"
- colors="true"
- convertErrorsToExceptions="true"
- convertNoticesToExceptions="true"
- convertWarningsToExceptions="true"
- processIsolation="false"
- stopOnFailure="false"
- syntaxCheck="false"
- bootstrap="test/bootstrap.php"
->
- <testsuites>
- <testsuite name="Oauth2 Test Suite">
- <directory>./test/OAuth2/</directory>
- </testsuite>
- </testsuites>
-
- <filter>
- <whitelist>
- <directory suffix=".php">./src/OAuth2/</directory>
- </whitelist>
- </filter>
-</phpunit>
diff --git a/library/oauth2/src/OAuth2/Controller/AuthorizeController.php b/library/oauth2/src/OAuth2/Controller/AuthorizeController.php
deleted file mode 100644
index a9a722587..000000000
--- a/library/oauth2/src/OAuth2/Controller/AuthorizeController.php
+++ /dev/null
@@ -1,388 +0,0 @@
-<?php
-
-namespace OAuth2\Controller;
-
-use OAuth2\Storage\ClientInterface;
-use OAuth2\ScopeInterface;
-use OAuth2\RequestInterface;
-use OAuth2\ResponseInterface;
-use OAuth2\Scope;
-
-/**
- * @see OAuth2\Controller\AuthorizeControllerInterface
- */
-class AuthorizeController implements AuthorizeControllerInterface
-{
- private $scope;
- private $state;
- private $client_id;
- private $redirect_uri;
- private $response_type;
-
- protected $clientStorage;
- protected $responseTypes;
- protected $config;
- protected $scopeUtil;
-
- /**
- * @param OAuth2\Storage\ClientInterface $clientStorage REQUIRED Instance of OAuth2\Storage\ClientInterface to retrieve client information
- * @param array $responseTypes OPTIONAL Array of OAuth2\ResponseType\ResponseTypeInterface objects. Valid array
- * keys are "code" and "token"
- * @param array $config OPTIONAL Configuration options for the server
- * <code>
- * $config = array(
- * 'allow_implicit' => false, // if the controller should allow the "implicit" grant type
- * 'enforce_state' => true // if the controller should require the "state" parameter
- * 'require_exact_redirect_uri' => true, // if the controller should require an exact match on the "redirect_uri" parameter
- * 'redirect_status_code' => 302, // HTTP status code to use for redirect responses
- * );
- * </code>
- * @param OAuth2\ScopeInterface $scopeUtil OPTIONAL Instance of OAuth2\ScopeInterface to validate the requested scope
- */
- public function __construct(ClientInterface $clientStorage, array $responseTypes = array(), array $config = array(), ScopeInterface $scopeUtil = null)
- {
- $this->clientStorage = $clientStorage;
- $this->responseTypes = $responseTypes;
- $this->config = array_merge(array(
- 'allow_implicit' => false,
- 'enforce_state' => true,
- 'require_exact_redirect_uri' => true,
- 'redirect_status_code' => 302,
- ), $config);
-
- if (is_null($scopeUtil)) {
- $scopeUtil = new Scope();
- }
- $this->scopeUtil = $scopeUtil;
- }
-
- public function handleAuthorizeRequest(RequestInterface $request, ResponseInterface $response, $is_authorized, $user_id = null)
- {
- if (!is_bool($is_authorized)) {
- throw new \InvalidArgumentException('Argument "is_authorized" must be a boolean. This method must know if the user has granted access to the client.');
- }
-
- // We repeat this, because we need to re-validate. The request could be POSTed
- // by a 3rd-party (because we are not internally enforcing NONCEs, etc)
- if (!$this->validateAuthorizeRequest($request, $response)) {
- return;
- }
-
- // If no redirect_uri is passed in the request, use client's registered one
- if (empty($this->redirect_uri)) {
- $clientData = $this->clientStorage->getClientDetails($this->client_id);
- $registered_redirect_uri = $clientData['redirect_uri'];
- }
-
- // the user declined access to the client's application
- if ($is_authorized === false) {
- $redirect_uri = $this->redirect_uri ?: $registered_redirect_uri;
- $this->setNotAuthorizedResponse($request, $response, $redirect_uri, $user_id);
-
- return;
- }
-
- // build the parameters to set in the redirect URI
- if (!$params = $this->buildAuthorizeParameters($request, $response, $user_id)) {
- return;
- }
-
- $authResult = $this->responseTypes[$this->response_type]->getAuthorizeResponse($params, $user_id);
-
- list($redirect_uri, $uri_params) = $authResult;
-
- if (empty($redirect_uri) && !empty($registered_redirect_uri)) {
- $redirect_uri = $registered_redirect_uri;
- }
-
- $uri = $this->buildUri($redirect_uri, $uri_params);
-
- // return redirect response
- $response->setRedirect($this->config['redirect_status_code'], $uri);
- }
-
- protected function setNotAuthorizedResponse(RequestInterface $request, ResponseInterface $response, $redirect_uri, $user_id = null)
- {
- $error = 'access_denied';
- $error_message = 'The user denied access to your application';
- $response->setRedirect($this->config['redirect_status_code'], $redirect_uri, $this->state, $error, $error_message);
- }
-
- /*
- * We have made this protected so this class can be extended to add/modify
- * these parameters
- */
- protected function buildAuthorizeParameters($request, $response, $user_id)
- {
- // @TODO: we should be explicit with this in the future
- $params = array(
- 'scope' => $this->scope,
- 'state' => $this->state,
- 'client_id' => $this->client_id,
- 'redirect_uri' => $this->redirect_uri,
- 'response_type' => $this->response_type,
- );
-
- return $params;
- }
-
- public function validateAuthorizeRequest(RequestInterface $request, ResponseInterface $response)
- {
- // Make sure a valid client id was supplied (we can not redirect because we were unable to verify the URI)
- if (!$client_id = $request->query('client_id', $request->request('client_id'))) {
- // We don't have a good URI to use
- $response->setError(400, 'invalid_client', "No client id supplied");
-
- return false;
- }
-
- // Get client details
- if (!$clientData = $this->clientStorage->getClientDetails($client_id)) {
- $response->setError(400, 'invalid_client', 'The client id supplied is invalid');
-
- return false;
- }
-
- $registered_redirect_uri = isset($clientData['redirect_uri']) ? $clientData['redirect_uri'] : '';
-
- // Make sure a valid redirect_uri was supplied. If specified, it must match the clientData URI.
- // @see http://tools.ietf.org/html/rfc6749#section-3.1.2
- // @see http://tools.ietf.org/html/rfc6749#section-4.1.2.1
- // @see http://tools.ietf.org/html/rfc6749#section-4.2.2.1
- if ($supplied_redirect_uri = $request->query('redirect_uri', $request->request('redirect_uri'))) {
- // validate there is no fragment supplied
- $parts = parse_url($supplied_redirect_uri);
- if (isset($parts['fragment']) && $parts['fragment']) {
- $response->setError(400, 'invalid_uri', 'The redirect URI must not contain a fragment');
-
- return false;
- }
-
- // validate against the registered redirect uri(s) if available
- if ($registered_redirect_uri && !$this->validateRedirectUri($supplied_redirect_uri, $registered_redirect_uri)) {
- $response->setError(400, 'redirect_uri_mismatch', 'The redirect URI provided is missing or does not match', '#section-3.1.2');
-
- return false;
- }
- $redirect_uri = $supplied_redirect_uri;
- } else {
- // use the registered redirect_uri if none has been supplied, if possible
- if (!$registered_redirect_uri) {
- $response->setError(400, 'invalid_uri', 'No redirect URI was supplied or stored');
-
- return false;
- }
-
- if (count(explode(' ', $registered_redirect_uri)) > 1) {
- $response->setError(400, 'invalid_uri', 'A redirect URI must be supplied when multiple redirect URIs are registered', '#section-3.1.2.3');
-
- return false;
- }
- $redirect_uri = $registered_redirect_uri;
- }
-
- // Select the redirect URI
- $response_type = $request->query('response_type', $request->request('response_type'));
-
- // for multiple-valued response types - make them alphabetical
- if (false !== strpos($response_type, ' ')) {
- $types = explode(' ', $response_type);
- sort($types);
- $response_type = ltrim(implode(' ', $types));
- }
-
- $state = $request->query('state', $request->request('state'));
-
- // type and client_id are required
- if (!$response_type || !in_array($response_type, $this->getValidResponseTypes())) {
- $response->setRedirect($this->config['redirect_status_code'], $redirect_uri, $state, 'invalid_request', 'Invalid or missing response type', null);
-
- return false;
- }
-
- if ($response_type == self::RESPONSE_TYPE_AUTHORIZATION_CODE) {
- if (!isset($this->responseTypes['code'])) {
- $response->setRedirect($this->config['redirect_status_code'], $redirect_uri, $state, 'unsupported_response_type', 'authorization code grant type not supported', null);
-
- return false;
- }
- if (!$this->clientStorage->checkRestrictedGrantType($client_id, 'authorization_code')) {
- $response->setRedirect($this->config['redirect_status_code'], $redirect_uri, $state, 'unauthorized_client', 'The grant type is unauthorized for this client_id', null);
-
- return false;
- }
- if ($this->responseTypes['code']->enforceRedirect() && !$redirect_uri) {
- $response->setError(400, 'redirect_uri_mismatch', 'The redirect URI is mandatory and was not supplied');
-
- return false;
- }
- } else {
- if (!$this->config['allow_implicit']) {
- $response->setRedirect($this->config['redirect_status_code'], $redirect_uri, $state, 'unsupported_response_type', 'implicit grant type not supported', null);
-
- return false;
- }
- if (!$this->clientStorage->checkRestrictedGrantType($client_id, 'implicit')) {
- $response->setRedirect($this->config['redirect_status_code'], $redirect_uri, $state, 'unauthorized_client', 'The grant type is unauthorized for this client_id', null);
-
- return false;
- }
- }
-
- // validate requested scope if it exists
- $requestedScope = $this->scopeUtil->getScopeFromRequest($request);
-
- if ($requestedScope) {
- // restrict scope by client specific scope if applicable,
- // otherwise verify the scope exists
- $clientScope = $this->clientStorage->getClientScope($client_id);
- if ((empty($clientScope) && !$this->scopeUtil->scopeExists($requestedScope))
- || (!empty($clientScope) && !$this->scopeUtil->checkScope($requestedScope, $clientScope))) {
- $response->setRedirect($this->config['redirect_status_code'], $redirect_uri, $state, 'invalid_scope', 'An unsupported scope was requested', null);
-
- return false;
- }
- } else {
- // use a globally-defined default scope
- $defaultScope = $this->scopeUtil->getDefaultScope($client_id);
-
- if (false === $defaultScope) {
- $response->setRedirect($this->config['redirect_status_code'], $redirect_uri, $state, 'invalid_client', 'This application requires you specify a scope parameter', null);
-
- return false;
- }
-
- $requestedScope = $defaultScope;
- }
-
- // Validate state parameter exists (if configured to enforce this)
- if ($this->config['enforce_state'] && !$state) {
- $response->setRedirect($this->config['redirect_status_code'], $redirect_uri, null, 'invalid_request', 'The state parameter is required');
-
- return false;
- }
-
- // save the input data and return true
- $this->scope = $requestedScope;
- $this->state = $state;
- $this->client_id = $client_id;
- // Only save the SUPPLIED redirect URI (@see http://tools.ietf.org/html/rfc6749#section-4.1.3)
- $this->redirect_uri = $supplied_redirect_uri;
- $this->response_type = $response_type;
-
- return true;
- }
-
- /**
- * Build the absolute URI based on supplied URI and parameters.
- *
- * @param $uri An absolute URI.
- * @param $params Parameters to be append as GET.
- *
- * @return
- * An absolute URI with supplied parameters.
- *
- * @ingroup oauth2_section_4
- */
- private function buildUri($uri, $params)
- {
- $parse_url = parse_url($uri);
-
- // Add our params to the parsed uri
- foreach ($params as $k => $v) {
- if (isset($parse_url[$k])) {
- $parse_url[$k] .= "&" . http_build_query($v, '', '&');
- } else {
- $parse_url[$k] = http_build_query($v, '', '&');
- }
- }
-
- // Put humpty dumpty back together
- return
- ((isset($parse_url["scheme"])) ? $parse_url["scheme"] . "://" : "")
- . ((isset($parse_url["user"])) ? $parse_url["user"]
- . ((isset($parse_url["pass"])) ? ":" . $parse_url["pass"] : "") . "@" : "")
- . ((isset($parse_url["host"])) ? $parse_url["host"] : "")
- . ((isset($parse_url["port"])) ? ":" . $parse_url["port"] : "")
- . ((isset($parse_url["path"])) ? $parse_url["path"] : "")
- . ((isset($parse_url["query"]) && !empty($parse_url['query'])) ? "?" . $parse_url["query"] : "")
- . ((isset($parse_url["fragment"])) ? "#" . $parse_url["fragment"] : "")
- ;
- }
-
- protected function getValidResponseTypes()
- {
- return array(
- self::RESPONSE_TYPE_ACCESS_TOKEN,
- self::RESPONSE_TYPE_AUTHORIZATION_CODE,
- );
- }
-
- /**
- * Internal method for validating redirect URI supplied
- *
- * @param string $inputUri The submitted URI to be validated
- * @param string $registeredUriString The allowed URI(s) to validate against. Can be a space-delimited string of URIs to
- * allow for multiple URIs
- *
- * @see http://tools.ietf.org/html/rfc6749#section-3.1.2
- */
- protected function validateRedirectUri($inputUri, $registeredUriString)
- {
- if (!$inputUri || !$registeredUriString) {
- return false; // if either one is missing, assume INVALID
- }
-
- $registered_uris = explode(' ', $registeredUriString);
- foreach ($registered_uris as $registered_uri) {
- if ($this->config['require_exact_redirect_uri']) {
- // the input uri is validated against the registered uri using exact match
- if (strcmp($inputUri, $registered_uri) === 0) {
- return true;
- }
- } else {
- $registered_uri_length = strlen($registered_uri);
- if ($registered_uri_length === 0) {
- return false;
- }
-
- // the input uri is validated against the registered uri using case-insensitive match of the initial string
- // i.e. additional query parameters may be applied
- if (strcasecmp(substr($inputUri, 0, $registered_uri_length), $registered_uri) === 0) {
- return true;
- }
- }
- }
-
- return false;
- }
-
- /**
- * Convenience methods to access the parameters derived from the validated request
- */
-
- public function getScope()
- {
- return $this->scope;
- }
-
- public function getState()
- {
- return $this->state;
- }
-
- public function getClientId()
- {
- return $this->client_id;
- }
-
- public function getRedirectUri()
- {
- return $this->redirect_uri;
- }
-
- public function getResponseType()
- {
- return $this->response_type;
- }
-}
diff --git a/library/oauth2/src/OAuth2/Controller/ResourceController.php b/library/oauth2/src/OAuth2/Controller/ResourceController.php
deleted file mode 100644
index e8588188f..000000000
--- a/library/oauth2/src/OAuth2/Controller/ResourceController.php
+++ /dev/null
@@ -1,111 +0,0 @@
-<?php
-
-namespace OAuth2\Controller;
-
-use OAuth2\TokenType\TokenTypeInterface;
-use OAuth2\Storage\AccessTokenInterface;
-use OAuth2\ScopeInterface;
-use OAuth2\RequestInterface;
-use OAuth2\ResponseInterface;
-use OAuth2\Scope;
-
-/**
- * @see OAuth2\Controller\ResourceControllerInterface
- */
-class ResourceController implements ResourceControllerInterface
-{
- private $token;
-
- protected $tokenType;
- protected $tokenStorage;
- protected $config;
- protected $scopeUtil;
-
- public function __construct(TokenTypeInterface $tokenType, AccessTokenInterface $tokenStorage, $config = array(), ScopeInterface $scopeUtil = null)
- {
- $this->tokenType = $tokenType;
- $this->tokenStorage = $tokenStorage;
-
- $this->config = array_merge(array(
- 'www_realm' => 'Service',
- ), $config);
-
- if (is_null($scopeUtil)) {
- $scopeUtil = new Scope();
- }
- $this->scopeUtil = $scopeUtil;
- }
-
- public function verifyResourceRequest(RequestInterface $request, ResponseInterface $response, $scope = null)
- {
- $token = $this->getAccessTokenData($request, $response);
-
- // Check if we have token data
- if (is_null($token)) {
- return false;
- }
-
- /**
- * Check scope, if provided
- * If token doesn't have a scope, it's null/empty, or it's insufficient, then throw 403
- * @see http://tools.ietf.org/html/rfc6750#section-3.1
- */
- if ($scope && (!isset($token["scope"]) || !$token["scope"] || !$this->scopeUtil->checkScope($scope, $token["scope"]))) {
- $response->setError(403, 'insufficient_scope', 'The request requires higher privileges than provided by the access token');
- $response->addHttpHeaders(array(
- 'WWW-Authenticate' => sprintf('%s realm="%s", scope="%s", error="%s", error_description="%s"',
- $this->tokenType->getTokenType(),
- $this->config['www_realm'],
- $scope,
- $response->getParameter('error'),
- $response->getParameter('error_description')
- )
- ));
-
- return false;
- }
-
- // allow retrieval of the token
- $this->token = $token;
-
- return (bool) $token;
- }
-
- public function getAccessTokenData(RequestInterface $request, ResponseInterface $response)
- {
- // Get the token parameter
- if ($token_param = $this->tokenType->getAccessTokenParameter($request, $response)) {
- // Get the stored token data (from the implementing subclass)
- // Check we have a well formed token
- // Check token expiration (expires is a mandatory paramter)
- if (!$token = $this->tokenStorage->getAccessToken($token_param)) {
- $response->setError(401, 'invalid_token', 'The access token provided is invalid');
- } elseif (!isset($token["expires"]) || !isset($token["client_id"])) {
- $response->setError(401, 'malformed_token', 'Malformed token (missing "expires")');
- } elseif (time() > $token["expires"]) {
- $response->setError(401, 'expired_token', 'The access token provided has expired');
- } else {
- return $token;
- }
- }
-
- $authHeader = sprintf('%s realm="%s"', $this->tokenType->getTokenType(), $this->config['www_realm']);
-
- if ($error = $response->getParameter('error')) {
- $authHeader = sprintf('%s, error="%s"', $authHeader, $error);
- if ($error_description = $response->getParameter('error_description')) {
- $authHeader = sprintf('%s, error_description="%s"', $authHeader, $error_description);
- }
- }
-
- $response->addHttpHeaders(array('WWW-Authenticate' => $authHeader));
-
- return null;
- }
-
- // convenience method to allow retrieval of the token
- public function getToken()
- {
- return $this->token;
- }
-}
diff --git a/library/oauth2/src/OAuth2/Controller/TokenController.php b/library/oauth2/src/OAuth2/Controller/TokenController.php
deleted file mode 100644
index 42dab892f..000000000
--- a/library/oauth2/src/OAuth2/Controller/TokenController.php
+++ /dev/null
@@ -1,278 +0,0 @@
-<?php
-
-namespace OAuth2\Controller;
-
-use OAuth2\ResponseType\AccessTokenInterface;
-use OAuth2\ClientAssertionType\ClientAssertionTypeInterface;
-use OAuth2\GrantType\GrantTypeInterface;
-use OAuth2\ScopeInterface;
-use OAuth2\Scope;
-use OAuth2\Storage\ClientInterface;
-use OAuth2\RequestInterface;
-use OAuth2\ResponseInterface;
-
-/**
- * @see OAuth2\Controller\TokenControllerInterface
- */
-class TokenController implements TokenControllerInterface
-{
- protected $accessToken;
- protected $grantTypes;
- protected $clientAssertionType;
- protected $scopeUtil;
- protected $clientStorage;
-
- public function __construct(AccessTokenInterface $accessToken, ClientInterface $clientStorage, array $grantTypes = array(), ClientAssertionTypeInterface $clientAssertionType = null, ScopeInterface $scopeUtil = null)
- {
- if (is_null($clientAssertionType)) {
- foreach ($grantTypes as $grantType) {
- if (!$grantType instanceof ClientAssertionTypeInterface) {
- throw new \InvalidArgumentException('You must supply an instance of OAuth2\ClientAssertionType\ClientAssertionTypeInterface or only use grant types which implement OAuth2\ClientAssertionType\ClientAssertionTypeInterface');
- }
- }
- }
- $this->clientAssertionType = $clientAssertionType;
- $this->accessToken = $accessToken;
- $this->clientStorage = $clientStorage;
- foreach ($grantTypes as $grantType) {
- $this->addGrantType($grantType);
- }
-
- if (is_null($scopeUtil)) {
- $scopeUtil = new Scope();
- }
- $this->scopeUtil = $scopeUtil;
- }
-
- public function handleTokenRequest(RequestInterface $request, ResponseInterface $response)
- {
- if ($token = $this->grantAccessToken($request, $response)) {
- // @see http://tools.ietf.org/html/rfc6749#section-5.1
- // server MUST disable caching in headers when tokens are involved
- $response->setStatusCode(200);
- $response->addParameters($token);
- $response->addHttpHeaders(array(
- 'Cache-Control' => 'no-store',
- 'Pragma' => 'no-cache',
- 'Content-Type' => 'application/json'
- ));
- }
- }
-
- /**
- * Grant or deny a requested access token.
- * This would be called from the "/token" endpoint as defined in the spec.
- * You can call your endpoint whatever you want.
- *
- * @param $request - RequestInterface
- * Request object to grant access token
- *
- * @throws InvalidArgumentException
- * @throws LogicException
- *
- * @see http://tools.ietf.org/html/rfc6749#section-4
- * @see http://tools.ietf.org/html/rfc6749#section-10.6
- * @see http://tools.ietf.org/html/rfc6749#section-4.1.3
- *
- * @ingroup oauth2_section_4
- */
- public function grantAccessToken(RequestInterface $request, ResponseInterface $response)
- {
- if (strtolower($request->server('REQUEST_METHOD')) != 'post') {
- $response->setError(405, 'invalid_request', 'The request method must be POST when requesting an access token', '#section-3.2');
- $response->addHttpHeaders(array('Allow' => 'POST'));
-
- return null;
- }
-
- /**
- * Determine grant type from request
- * and validate the request for that grant type
- */
- if (!$grantTypeIdentifier = $request->request('grant_type')) {
- $response->setError(400, 'invalid_request', 'The grant type was not specified in the request');
-
- return null;
- }
-
- if (!isset($this->grantTypes[$grantTypeIdentifier])) {
- /* TODO: If this is an OAuth2 supported grant type that we have chosen not to implement, throw a 501 Not Implemented instead */
- $response->setError(400, 'unsupported_grant_type', sprintf('Grant type "%s" not supported', $grantTypeIdentifier));
-
- return null;
- }
-
- $grantType = $this->grantTypes[$grantTypeIdentifier];
-
- /**
- * Retrieve the client information from the request
- * ClientAssertionTypes allow for grant types which also assert the client data
- * in which case ClientAssertion is handled in the validateRequest method
- *
- * @see OAuth2\GrantType\JWTBearer
- * @see OAuth2\GrantType\ClientCredentials
- */
- if (!$grantType instanceof ClientAssertionTypeInterface) {
- if (!$this->clientAssertionType->validateRequest($request, $response)) {
- return null;
- }
- $clientId = $this->clientAssertionType->getClientId();
- }
-
- /**
- * Retrieve the grant type information from the request
- * The GrantTypeInterface object handles all validation
- * If the object is an instance of ClientAssertionTypeInterface,
- * That logic is handled here as well
- */
- if (!$grantType->validateRequest($request, $response)) {
- return null;
- }
-
- if ($grantType instanceof ClientAssertionTypeInterface) {
- $clientId = $grantType->getClientId();
- } else {
- // validate the Client ID (if applicable)
- if (!is_null($storedClientId = $grantType->getClientId()) && $storedClientId != $clientId) {
- $response->setError(400, 'invalid_grant', sprintf('%s doesn\'t exist or is invalid for the client', $grantTypeIdentifier));
-
- return null;
- }
- }
-
- /**
- * Validate the client can use the requested grant type
- */
- if (!$this->clientStorage->checkRestrictedGrantType($clientId, $grantTypeIdentifier)) {
- $response->setError(400, 'unauthorized_client', 'The grant type is unauthorized for this client_id');
-
- return false;
- }
-
- /**
- * Validate the scope of the token
- *
- * requestedScope - the scope specified in the token request
- * availableScope - the scope associated with the grant type
- * ex: in the case of the "Authorization Code" grant type,
- * the scope is specified in the authorize request
- *
- * @see http://tools.ietf.org/html/rfc6749#section-3.3
- */
-
- $requestedScope = $this->scopeUtil->getScopeFromRequest($request);
- $availableScope = $grantType->getScope();
-
- if ($requestedScope) {
- // validate the requested scope
- if ($availableScope) {
- if (!$this->scopeUtil->checkScope($requestedScope, $availableScope)) {
- $response->setError(400, 'invalid_scope', 'The scope requested is invalid for this request');
-
- return null;
- }
- } else {
- // validate the client has access to this scope
- if ($clientScope = $this->clientStorage->getClientScope($clientId)) {
- if (!$this->scopeUtil->checkScope($requestedScope, $clientScope)) {
- $response->setError(400, 'invalid_scope', 'The scope requested is invalid for this client');
-
- return false;
- }
- } elseif (!$this->scopeUtil->scopeExists($requestedScope)) {
- $response->setError(400, 'invalid_scope', 'An unsupported scope was requested');
-
- return null;
- }
- }
- } elseif ($availableScope) {
- // use the scope associated with this grant type
- $requestedScope = $availableScope;
- } else {
- // use a globally-defined default scope
- $defaultScope = $this->scopeUtil->getDefaultScope($clientId);
-
- // "false" means default scopes are not allowed
- if (false === $defaultScope) {
- $response->setError(400, 'invalid_scope', 'This application requires you specify a scope parameter');
-
- return null;
- }
-
- $requestedScope = $defaultScope;
- }
-
- return $grantType->createAccessToken($this->accessToken, $clientId, $grantType->getUserId(), $requestedScope);
- }
-
- /**
- * addGrantType
- *
- * @param grantType - OAuth2\GrantTypeInterface
- * the grant type to add for the specified identifier
- * @param identifier - string
- * a string passed in as "grant_type" in the response that will call this grantType
- */
- public function addGrantType(GrantTypeInterface $grantType, $identifier = null)
- {
- if (is_null($identifier) || is_numeric($identifier)) {
- $identifier = $grantType->getQuerystringIdentifier();
- }
-
- $this->grantTypes[$identifier] = $grantType;
- }
-
- public function handleRevokeRequest(RequestInterface $request, ResponseInterface $response)
- {
- if ($this->revokeToken($request, $response)) {
- $response->setStatusCode(200);
- $response->addParameters(array('revoked' => true));
- }
- }
-
- /**
- * Revoke a refresh or access token. Returns true on success and when tokens are invalid
- *
- * Note: invalid tokens do not cause an error response since the client
- * cannot handle such an error in a reasonable way. Moreover, the
- * purpose of the revocation request, invalidating the particular token,
- * is already achieved.
- *
- * @param RequestInterface $request
- * @param ResponseInterface $response
- * @return bool|null
- */
- public function revokeToken(RequestInterface $request, ResponseInterface $response)
- {
- if (strtolower($request->server('REQUEST_METHOD')) != 'post') {
- $response->setError(405, 'invalid_request', 'The request method must be POST when revoking an access token', '#section-3.2');
- $response->addHttpHeaders(array('Allow' => 'POST'));
-
- return null;
- }
-
- $token_type_hint = $request->request('token_type_hint');
- if (!in_array($token_type_hint, array(null, 'access_token', 'refresh_token'), true)) {
- $response->setError(400, 'invalid_request', 'Token type hint must be either \'access_token\' or \'refresh_token\'');
-
- return null;
- }
-
- $token = $request->request('token');
- if ($token === null) {
- $response->setError(400, 'invalid_request', 'Missing token parameter to revoke');
-
- return null;
- }
-
- // @todo remove this check for v2.0
- if (!method_exists($this->accessToken, 'revokeToken')) {
- $class = get_class($this->accessToken);
- throw new \RuntimeException("AccessToken {$class} does not implement required revokeToken method");
- }
-
- $this->accessToken->revokeToken($token, $token_type_hint);
-
- return true;
- }
-}
diff --git a/library/oauth2/src/OAuth2/GrantType/AuthorizationCode.php b/library/oauth2/src/OAuth2/GrantType/AuthorizationCode.php
deleted file mode 100644
index e8995204c..000000000
--- a/library/oauth2/src/OAuth2/GrantType/AuthorizationCode.php
+++ /dev/null
@@ -1,100 +0,0 @@
-<?php
-
-namespace OAuth2\GrantType;
-
-use OAuth2\Storage\AuthorizationCodeInterface;
-use OAuth2\ResponseType\AccessTokenInterface;
-use OAuth2\RequestInterface;
-use OAuth2\ResponseInterface;
-
-/**
- *
- * @author Brent Shaffer <bshafs at gmail dot com>
- */
-class AuthorizationCode implements GrantTypeInterface
-{
- protected $storage;
- protected $authCode;
-
- /**
- * @param OAuth2\Storage\AuthorizationCodeInterface $storage REQUIRED Storage class for retrieving authorization code information
- */
- public function __construct(AuthorizationCodeInterface $storage)
- {
- $this->storage = $storage;
- }
-
- public function getQuerystringIdentifier()
- {
- return 'authorization_code';
- }
-
- public function validateRequest(RequestInterface $request, ResponseInterface $response)
- {
- if (!$request->request('code')) {
- $response->setError(400, 'invalid_request', 'Missing parameter: "code" is required');
-
- return false;
- }
-
- $code = $request->request('code');
- if (!$authCode = $this->storage->getAuthorizationCode($code)) {
- $response->setError(400, 'invalid_grant', 'Authorization code doesn\'t exist or is invalid for the client');
-
- return false;
- }
-
- /*
- * 4.1.3 - ensure that the "redirect_uri" parameter is present if the "redirect_uri" parameter was included in the initial authorization request
- * @uri - http://tools.ietf.org/html/rfc6749#section-4.1.3
- */
- if (isset($authCode['redirect_uri']) && $authCode['redirect_uri']) {
- if (!$request->request('redirect_uri') || urldecode($request->request('redirect_uri')) != $authCode['redirect_uri']) {
- $response->setError(400, 'redirect_uri_mismatch', "The redirect URI is missing or do not match", "#section-4.1.3");
-
- return false;
- }
- }
-
- if (!isset($authCode['expires'])) {
- throw new \Exception('Storage must return authcode with a value for "expires"');
- }
-
- if ($authCode["expires"] < time()) {
- $response->setError(400, 'invalid_grant', "The authorization code has expired");
-
- return false;
- }
-
- if (!isset($authCode['code'])) {
- $authCode['code'] = $code; // used to expire the code after the access token is granted
- }
-
- $this->authCode = $authCode;
-
- return true;
- }
-
- public function getClientId()
- {
- return $this->authCode['client_id'];
- }
-
- public function getScope()
- {
- return isset($this->authCode['scope']) ? $this->authCode['scope'] : null;
- }
-
- public function getUserId()
- {
- return isset($this->authCode['user_id']) ? $this->authCode['user_id'] : null;
- }
-
- public function createAccessToken(AccessTokenInterface $accessToken, $client_id, $user_id, $scope)
- {
- $token = $accessToken->createAccessToken($client_id, $user_id, $scope);
- $this->storage->expireAuthorizationCode($this->authCode['code']);
-
- return $token;
- }
-}
diff --git a/library/oauth2/src/OAuth2/Response.php b/library/oauth2/src/OAuth2/Response.php
deleted file mode 100644
index d8eabe79e..000000000
--- a/library/oauth2/src/OAuth2/Response.php
+++ /dev/null
@@ -1,369 +0,0 @@
-<?php
-
-namespace OAuth2;
-
-/**
- * Class to handle OAuth2 Responses in a graceful way. Use this interface
- * to output the proper OAuth2 responses.
- *
- * @see OAuth2\ResponseInterface
- *
- * This class borrows heavily from the Symfony2 Framework and is part of the symfony package
- * @see Symfony\Component\HttpFoundation\Request (https://github.com/symfony/symfony)
- */
-class Response implements ResponseInterface
-{
- public $version;
- protected $statusCode = 200;
- protected $statusText;
- protected $parameters = array();
- protected $httpHeaders = array();
-
- public static $statusTexts = array(
- 100 => 'Continue',
- 101 => 'Switching Protocols',
- 200 => 'OK',
- 201 => 'Created',
- 202 => 'Accepted',
- 203 => 'Non-Authoritative Information',
- 204 => 'No Content',
- 205 => 'Reset Content',
- 206 => 'Partial Content',
- 300 => 'Multiple Choices',
- 301 => 'Moved Permanently',
- 302 => 'Found',
- 303 => 'See Other',
- 304 => 'Not Modified',
- 305 => 'Use Proxy',
- 307 => 'Temporary Redirect',
- 400 => 'Bad Request',
- 401 => 'Unauthorized',
- 402 => 'Payment Required',
- 403 => 'Forbidden',
- 404 => 'Not Found',
- 405 => 'Method Not Allowed',
- 406 => 'Not Acceptable',
- 407 => 'Proxy Authentication Required',
- 408 => 'Request Timeout',
- 409 => 'Conflict',
- 410 => 'Gone',
- 411 => 'Length Required',
- 412 => 'Precondition Failed',
- 413 => 'Request Entity Too Large',
- 414 => 'Request-URI Too Long',
- 415 => 'Unsupported Media Type',
- 416 => 'Requested Range Not Satisfiable',
- 417 => 'Expectation Failed',
- 418 => 'I\'m a teapot',
- 500 => 'Internal Server Error',
- 501 => 'Not Implemented',
- 502 => 'Bad Gateway',
- 503 => 'Service Unavailable',
- 504 => 'Gateway Timeout',
- 505 => 'HTTP Version Not Supported',
- );
-
- public function __construct($parameters = array(), $statusCode = 200, $headers = array())
- {
- $this->setParameters($parameters);
- $this->setStatusCode($statusCode);
- $this->setHttpHeaders($headers);
- $this->version = '1.1';
- }
-
- /**
- * Converts the response object to string containing all headers and the response content.
- *
- * @return string The response with headers and content
- */
- public function __toString()
- {
- $headers = array();
- foreach ($this->httpHeaders as $name => $value) {
- $headers[$name] = (array) $value;
- }
-
- return
- sprintf('HTTP/%s %s %s', $this->version, $this->statusCode, $this->statusText)."\r\n".
- $this->getHttpHeadersAsString($headers)."\r\n".
- $this->getResponseBody();
- }
-
- /**
- * Returns the build header line.
- *
- * @param string $name The header name
- * @param string $value The header value
- *
- * @return string The built header line
- */
- protected function buildHeader($name, $value)
- {
- return sprintf("%s: %s\n", $name, $value);
- }
-
- public function getStatusCode()
- {
- return $this->statusCode;
- }
-
- public function setStatusCode($statusCode, $text = null)
- {
- $this->statusCode = (int) $statusCode;
- if ($this->isInvalid()) {
- throw new \InvalidArgumentException(sprintf('The HTTP status code "%s" is not valid.', $statusCode));
- }
-
- $this->statusText = false === $text ? '' : (null === $text ? self::$statusTexts[$this->statusCode] : $text);
- }
-
- public function getStatusText()
- {
- return $this->statusText;
- }
-
- public function getParameters()
- {
- return $this->parameters;
- }
-
- public function setParameters(array $parameters)
- {
- $this->parameters = $parameters;
- }
-
- public function addParameters(array $parameters)
- {
- $this->parameters = array_merge($this->parameters, $parameters);
- }
-
- public function getParameter($name, $default = null)
- {
- return isset($this->parameters[$name]) ? $this->parameters[$name] : $default;
- }
-
- public function setParameter($name, $value)
- {
- $this->parameters[$name] = $value;
- }
-
- public function setHttpHeaders(array $httpHeaders)
- {
- $this->httpHeaders = $httpHeaders;
- }
-
- public function setHttpHeader($name, $value)
- {
- $this->httpHeaders[$name] = $value;
- }
-
- public function addHttpHeaders(array $httpHeaders)
- {
- $this->httpHeaders = array_merge($this->httpHeaders, $httpHeaders);
- }
-
- public function getHttpHeaders()
- {
- return $this->httpHeaders;
- }
-
- public function getHttpHeader($name, $default = null)
- {
- return isset($this->httpHeaders[$name]) ? $this->httpHeaders[$name] : $default;
- }
-
- public function getResponseBody($format = 'json')
- {
- switch ($format) {
- case 'json':
- return json_encode($this->parameters);
- case 'xml':
- // this only works for single-level arrays
- $xml = new \SimpleXMLElement('<response/>');
- foreach ($this->parameters as $key => $param) {
- $xml->addChild($key, $param);
- }
-
- return $xml->asXML();
- }
-
- throw new \InvalidArgumentException(sprintf('The format %s is not supported', $format));
-
- }
-
- public function send($format = 'json')
- {
- // headers have already been sent by the developer
- if (headers_sent()) {
- return;
- }
-
- switch ($format) {
- case 'json':
- $this->setHttpHeader('Content-Type', 'application/json');
- break;
- case 'xml':
- $this->setHttpHeader('Content-Type', 'text/xml');
- break;
- }
- // status
- header(sprintf('HTTP/%s %s %s', $this->version, $this->statusCode, $this->statusText));
-
- foreach ($this->getHttpHeaders() as $name => $header) {
- header(sprintf('%s: %s', $name, $header));
- }
- echo $this->getResponseBody($format);
- }
-
- public function setError($statusCode, $error, $errorDescription = null, $errorUri = null)
- {
- $parameters = array(
- 'error' => $error,
- 'error_description' => $errorDescription,
- );
-
- if (!is_null($errorUri)) {
- if (strlen($errorUri) > 0 && $errorUri[0] == '#') {
- // we are referencing an oauth bookmark (for brevity)
- $errorUri = 'http://tools.ietf.org/html/rfc6749' . $errorUri;
- }
- $parameters['error_uri'] = $errorUri;
- }
-
- $httpHeaders = array(
- 'Cache-Control' => 'no-store'
- );
-
- $this->setStatusCode($statusCode);
- $this->addParameters($parameters);
- $this->addHttpHeaders($httpHeaders);
-
- if (!$this->isClientError() && !$this->isServerError()) {
- throw new \InvalidArgumentException(sprintf('The HTTP status code is not an error ("%s" given).', $statusCode));
- }
- }
-
- public function setRedirect($statusCode, $url, $state = null, $error = null, $errorDescription = null, $errorUri = null)
- {
- if (empty($url)) {
- throw new \InvalidArgumentException('Cannot redirect to an empty URL.');
- }
-
- $parameters = array();
-
- if (!is_null($state)) {
- $parameters['state'] = $state;
- }
-
- if (!is_null($error)) {
- $this->setError(400, $error, $errorDescription, $errorUri);
- }
- $this->setStatusCode($statusCode);
- $this->addParameters($parameters);
-
- if (count($this->parameters) > 0) {
- // add parameters to URL redirection
- $parts = parse_url($url);
- $sep = isset($parts['query']) && count($parts['query']) > 0 ? '&' : '?';
- $url .= $sep . http_build_query($this->parameters);
- }
-
- $this->addHttpHeaders(array('Location' => $url));
-
- if (!$this->isRedirection()) {
- throw new \InvalidArgumentException(sprintf('The HTTP status code is not a redirect ("%s" given).', $statusCode));
- }
- }
-
- // http://www.w3.org/Protocols/rfc2616/rfc2616-sec10.html
- /**
- * @return Boolean
- *
- * @api
- */
- public function isInvalid()
- {
- return $this->statusCode < 100 || $this->statusCode >= 600;
- }
-
- /**
- * @return Boolean
- *
- * @api
- */
- public function isInformational()
- {
- return $this->statusCode >= 100 && $this->statusCode < 200;
- }
-
- /**
- * @return Boolean
- *
- * @api
- */
- public function isSuccessful()
- {
- return $this->statusCode >= 200 && $this->statusCode < 300;
- }
-
- /**
- * @return Boolean
- *
- * @api
- */
- public function isRedirection()
- {
- return $this->statusCode >= 300 && $this->statusCode < 400;
- }
-
- /**
- * @return Boolean
- *
- * @api
- */
- public function isClientError()
- {
- return $this->statusCode >= 400 && $this->statusCode < 500;
- }
-
- /**
- * @return Boolean
- *
- * @api
- */
- public function isServerError()
- {
- return $this->statusCode >= 500 && $this->statusCode < 600;
- }
-
- /*
- * Functions from Symfony2 HttpFoundation - output pretty header
- */
- private function getHttpHeadersAsString($headers)
- {
- if (count($headers) == 0) {
- return '';
- }
-
- $max = max(array_map('strlen', array_keys($headers))) + 1;
- $content = '';
- ksort($headers);
- foreach ($headers as $name => $values) {
- foreach ($values as $value) {
- $content .= sprintf("%-{$max}s %s\r\n", $this->beautifyHeaderName($name).':', $value);
- }
- }
-
- return $content;
- }
-
- private function beautifyHeaderName($name)
- {
- return preg_replace_callback('/\-(.)/', array($this, 'beautifyCallback'), ucfirst($name));
- }
-
- private function beautifyCallback($match)
- {
- return '-'.strtoupper($match[1]);
- }
-}
diff --git a/library/oauth2/src/OAuth2/ResponseType/AccessToken.php b/library/oauth2/src/OAuth2/ResponseType/AccessToken.php
deleted file mode 100644
index b235ad0c5..000000000
--- a/library/oauth2/src/OAuth2/ResponseType/AccessToken.php
+++ /dev/null
@@ -1,194 +0,0 @@
-<?php
-
-namespace OAuth2\ResponseType;
-
-use OAuth2\Storage\AccessTokenInterface as AccessTokenStorageInterface;
-use OAuth2\Storage\RefreshTokenInterface;
-
-/**
- *
- * @author Brent Shaffer <bshafs at gmail dot com>
- */
-class AccessToken implements AccessTokenInterface
-{
- protected $tokenStorage;
- protected $refreshStorage;
- protected $config;
-
- /**
- * @param OAuth2\Storage\AccessTokenInterface $tokenStorage REQUIRED Storage class for saving access token information
- * @param OAuth2\Storage\RefreshTokenInterface $refreshStorage OPTIONAL Storage class for saving refresh token information
- * @param array $config OPTIONAL Configuration options for the server
- * <code>
- * $config = array(
- * 'token_type' => 'bearer', // token type identifier
- * 'access_lifetime' => 3600, // time before access token expires
- * 'refresh_token_lifetime' => 1209600, // time before refresh token expires
- * );
- * </endcode>
- */
- public function __construct(AccessTokenStorageInterface $tokenStorage, RefreshTokenInterface $refreshStorage = null, array $config = array())
- {
- $this->tokenStorage = $tokenStorage;
- $this->refreshStorage = $refreshStorage;
-
- $this->config = array_merge(array(
- 'token_type' => 'bearer',
- 'access_lifetime' => 3600,
- 'refresh_token_lifetime' => 1209600,
- ), $config);
- }
-
- public function getAuthorizeResponse($params, $user_id = null)
- {
- // build the URL to redirect to
- $result = array('query' => array());
-
- $params += array('scope' => null, 'state' => null);
-
- /*
- * a refresh token MUST NOT be included in the fragment
- *
- * @see http://tools.ietf.org/html/rfc6749#section-4.2.2
- */
- $includeRefreshToken = false;
- $result["fragment"] = $this->createAccessToken($params['client_id'], $user_id, $params['scope'], $includeRefreshToken);
-
- if (isset($params['state'])) {
- $result["fragment"]["state"] = $params['state'];
- }
-
- return array($params['redirect_uri'], $result);
- }
-
- /**
- * Handle the creation of access token, also issue refresh token if supported / desirable.
- *
- * @param $client_id client identifier related to the access token.
- * @param $user_id user ID associated with the access token
- * @param $scope OPTIONAL scopes to be stored in space-separated string.
- * @param bool $includeRefreshToken if true, a new refresh_token will be added to the response
- *
- * @see http://tools.ietf.org/html/rfc6749#section-5
- * @ingroup oauth2_section_5
- */
- public function createAccessToken($client_id, $user_id, $scope = null, $includeRefreshToken = true)
- {
- $token = array(
- "access_token" => $this->generateAccessToken(),
- "expires_in" => $this->config['access_lifetime'],
- "token_type" => $this->config['token_type'],
- "scope" => $scope
- );
-
- $this->tokenStorage->setAccessToken($token["access_token"], $client_id, $user_id, $this->config['access_lifetime'] ? time() + $this->config['access_lifetime'] : null, $scope);
-
- /*
- * Issue a refresh token also, if we support them
- *
- * Refresh Tokens are considered supported if an instance of OAuth2\Storage\RefreshTokenInterface
- * is supplied in the constructor
- */
- if ($includeRefreshToken && $this->refreshStorage) {
- $token["refresh_token"] = $this->generateRefreshToken();
- $expires = 0;
- if ($this->config['refresh_token_lifetime'] > 0) {
- $expires = time() + $this->config['refresh_token_lifetime'];
- }
- $this->refreshStorage->setRefreshToken($token['refresh_token'], $client_id, $user_id, $expires, $scope);
- }
-
- return $token;
- }
-
- /**
- * Generates an unique access token.
- *
- * Implementing classes may want to override this function to implement
- * other access token generation schemes.
- *
- * @return
- * An unique access token.
- *
- * @ingroup oauth2_section_4
- */
- protected function generateAccessToken()
- {
- if (function_exists('mcrypt_create_iv')) {
- $randomData = mcrypt_create_iv(20, MCRYPT_DEV_URANDOM);
- if ($randomData !== false && strlen($randomData) === 20) {
- return bin2hex($randomData);
- }
- }
- if (function_exists('openssl_random_pseudo_bytes')) {
- $randomData = openssl_random_pseudo_bytes(20);
- if ($randomData !== false && strlen($randomData) === 20) {
- return bin2hex($randomData);
- }
- }
- if (@file_exists('/dev/urandom')) { // Get 100 bytes of random data
- $randomData = file_get_contents('/dev/urandom', false, null, 0, 20);
- if ($randomData !== false && strlen($randomData) === 20) {
- return bin2hex($randomData);
- }
- }
- // Last resort which you probably should just get rid of:
- $randomData = mt_rand() . mt_rand() . mt_rand() . mt_rand() . microtime(true) . uniqid(mt_rand(), true);
-
- return substr(hash('sha512', $randomData), 0, 40);
- }
-
- /**
- * Generates an unique refresh token
- *
- * Implementing classes may want to override this function to implement
- * other refresh token generation schemes.
- *
- * @return
- * An unique refresh.
- *
- * @ingroup oauth2_section_4
- * @see OAuth2::generateAccessToken()
- */
- protected function generateRefreshToken()
- {
- return $this->generateAccessToken(); // let's reuse the same scheme for token generation
- }
-
- /**
- * Handle the revoking of refresh tokens, and access tokens if supported / desirable
- * RFC7009 specifies that "If the server is unable to locate the token using
- * the given hint, it MUST extend its search across all of its supported token types"
- *
- * @param $token
- * @param null $tokenTypeHint
- * @return boolean
- */
- public function revokeToken($token, $tokenTypeHint = null)
- {
- if ($tokenTypeHint == 'refresh_token') {
- if ($this->refreshStorage && $revoked = $this->refreshStorage->unsetRefreshToken($token)) {
- return true;
- }
- }
-
- /** @TODO remove in v2 */
- if (!method_exists($this->tokenStorage, 'unsetAccessToken')) {
- throw new \RuntimeException(
- sprintf('Token storage %s must implement unsetAccessToken method', get_class($this->tokenStorage)
- ));
- }
-
- $revoked = $this->tokenStorage->unsetAccessToken($token);
-
- // if a typehint is supplied and fails, try other storages
- // @see https://tools.ietf.org/html/rfc7009#section-2.1
- if (!$revoked && $tokenTypeHint != 'refresh_token') {
- if ($this->refreshStorage) {
- $revoked = $this->refreshStorage->unsetRefreshToken($token);
- }
- }
-
- return $revoked;
- }
-}
diff --git a/library/oauth2/src/OAuth2/ResponseType/AuthorizationCode.php b/library/oauth2/src/OAuth2/ResponseType/AuthorizationCode.php
deleted file mode 100644
index 6a305fd75..000000000
--- a/library/oauth2/src/OAuth2/ResponseType/AuthorizationCode.php
+++ /dev/null
@@ -1,100 +0,0 @@
-<?php
-
-namespace OAuth2\ResponseType;
-
-use OAuth2\Storage\AuthorizationCodeInterface as AuthorizationCodeStorageInterface;
-
-/**
- *
- * @author Brent Shaffer <bshafs at gmail dot com>
- */
-class AuthorizationCode implements AuthorizationCodeInterface
-{
- protected $storage;
- protected $config;
-
- public function __construct(AuthorizationCodeStorageInterface $storage, array $config = array())
- {
- $this->storage = $storage;
- $this->config = array_merge(array(
- 'enforce_redirect' => false,
- 'auth_code_lifetime' => 30,
- ), $config);
- }
-
- public function getAuthorizeResponse($params, $user_id = null)
- {
- // build the URL to redirect to
- $result = array('query' => array());
-
- $params += array('scope' => null, 'state' => null);
-
- $result['query']['code'] = $this->createAuthorizationCode($params['client_id'], $user_id, $params['redirect_uri'], $params['scope']);
-
- if (isset($params['state'])) {
- $result['query']['state'] = $params['state'];
- }
-
- return array($params['redirect_uri'], $result);
- }
-
- /**
- * Handle the creation of the authorization code.
- *
- * @param $client_id
- * Client identifier related to the authorization code
- * @param $user_id
- * User ID associated with the authorization code
- * @param $redirect_uri
- * An absolute URI to which the authorization server will redirect the
- * user-agent to when the end-user authorization step is completed.
- * @param $scope
- * (optional) Scopes to be stored in space-separated string.
- *
- * @see http://tools.ietf.org/html/rfc6749#section-4
- * @ingroup oauth2_section_4
- */
- public function createAuthorizationCode($client_id, $user_id, $redirect_uri, $scope = null)
- {
- $code = $this->generateAuthorizationCode();
- $this->storage->setAuthorizationCode($code, $client_id, $user_id, $redirect_uri, time() + $this->config['auth_code_lifetime'], $scope);
-
- return $code;
- }
-
- /**
- * @return
- * TRUE if the grant type requires a redirect_uri, FALSE if not
- */
- public function enforceRedirect()
- {
- return $this->config['enforce_redirect'];
- }
-
- /**
- * Generates an unique auth code.
- *
- * Implementing classes may want to override this function to implement
- * other auth code generation schemes.
- *
- * @return
- * An unique auth code.
- *
- * @ingroup oauth2_section_4
- */
- protected function generateAuthorizationCode()
- {
- $tokenLen = 40;
- if (function_exists('mcrypt_create_iv')) {
- $randomData = mcrypt_create_iv(100, MCRYPT_DEV_URANDOM);
- } elseif (function_exists('openssl_random_pseudo_bytes')) {
- $randomData = openssl_random_pseudo_bytes(100);
- } elseif (@file_exists('/dev/urandom')) { // Get 100 bytes of random data
- $randomData = file_get_contents('/dev/urandom', false, null, 0, 100) . uniqid(mt_rand(), true);
- } else {
- $randomData = mt_rand() . mt_rand() . mt_rand() . mt_rand() . microtime(true) . uniqid(mt_rand(), true);
- }
-
- return substr(hash('sha512', $randomData), 0, $tokenLen);
- }
-}
diff --git a/library/oauth2/src/OAuth2/Server.php b/library/oauth2/src/OAuth2/Server.php
deleted file mode 100644
index 171a4f069..000000000
--- a/library/oauth2/src/OAuth2/Server.php
+++ /dev/null
@@ -1,832 +0,0 @@
-<?php
-
-namespace OAuth2;
-
-use OAuth2\Controller\ResourceControllerInterface;
-use OAuth2\Controller\ResourceController;
-use OAuth2\OpenID\Controller\UserInfoControllerInterface;
-use OAuth2\OpenID\Controller\UserInfoController;
-use OAuth2\OpenID\Controller\AuthorizeController as OpenIDAuthorizeController;
-use OAuth2\OpenID\ResponseType\AuthorizationCode as OpenIDAuthorizationCodeResponseType;
-use OAuth2\OpenID\Storage\AuthorizationCodeInterface as OpenIDAuthorizationCodeInterface;
-use OAuth2\OpenID\GrantType\AuthorizationCode as OpenIDAuthorizationCodeGrantType;
-use OAuth2\Controller\AuthorizeControllerInterface;
-use OAuth2\Controller\AuthorizeController;
-use OAuth2\Controller\TokenControllerInterface;
-use OAuth2\Controller\TokenController;
-use OAuth2\ClientAssertionType\ClientAssertionTypeInterface;
-use OAuth2\ClientAssertionType\HttpBasic;
-use OAuth2\ResponseType\ResponseTypeInterface;
-use OAuth2\ResponseType\AuthorizationCode as AuthorizationCodeResponseType;
-use OAuth2\ResponseType\AccessToken;
-use OAuth2\ResponseType\JwtAccessToken;
-use OAuth2\OpenID\ResponseType\CodeIdToken;
-use OAuth2\OpenID\ResponseType\IdToken;
-use OAuth2\OpenID\ResponseType\IdTokenToken;
-use OAuth2\TokenType\TokenTypeInterface;
-use OAuth2\TokenType\Bearer;
-use OAuth2\GrantType\GrantTypeInterface;
-use OAuth2\GrantType\UserCredentials;
-use OAuth2\GrantType\ClientCredentials;
-use OAuth2\GrantType\RefreshToken;
-use OAuth2\GrantType\AuthorizationCode;
-use OAuth2\Storage\JwtAccessToken as JwtAccessTokenStorage;
-use OAuth2\Storage\JwtAccessTokenInterface;
-
-/**
-* Server class for OAuth2
-* This class serves as a convience class which wraps the other Controller classes
-*
-* @see OAuth2\Controller\ResourceController
-* @see OAuth2\Controller\AuthorizeController
-* @see OAuth2\Controller\TokenController
-*/
-class Server implements ResourceControllerInterface,
- AuthorizeControllerInterface,
- TokenControllerInterface,
- UserInfoControllerInterface
-{
- // misc properties
- protected $response;
- protected $config;
- protected $storages;
-
- // servers
- protected $authorizeController;
- protected $tokenController;
- protected $resourceController;
- protected $userInfoController;
-
- // config classes
- protected $grantTypes;
- protected $responseTypes;
- protected $tokenType;
- protected $scopeUtil;
- protected $clientAssertionType;
-
- protected $storageMap = array(
- 'access_token' => 'OAuth2\Storage\AccessTokenInterface',
- 'authorization_code' => 'OAuth2\Storage\AuthorizationCodeInterface',
- 'client_credentials' => 'OAuth2\Storage\ClientCredentialsInterface',
- 'client' => 'OAuth2\Storage\ClientInterface',
- 'refresh_token' => 'OAuth2\Storage\RefreshTokenInterface',
- 'user_credentials' => 'OAuth2\Storage\UserCredentialsInterface',
- 'user_claims' => 'OAuth2\OpenID\Storage\UserClaimsInterface',
- 'public_key' => 'OAuth2\Storage\PublicKeyInterface',
- 'jwt_bearer' => 'OAuth2\Storage\JWTBearerInterface',
- 'scope' => 'OAuth2\Storage\ScopeInterface',
- );
-
- protected $responseTypeMap = array(
- 'token' => 'OAuth2\ResponseType\AccessTokenInterface',
- 'code' => 'OAuth2\ResponseType\AuthorizationCodeInterface',
- 'id_token' => 'OAuth2\OpenID\ResponseType\IdTokenInterface',
- 'id_token token' => 'OAuth2\OpenID\ResponseType\IdTokenTokenInterface',
- 'code id_token' => 'OAuth2\OpenID\ResponseType\CodeIdTokenInterface',
- );
-
- /**
- * @param mixed $storage (array or OAuth2\Storage) - single object or array of objects implementing the
- * required storage types (ClientCredentialsInterface and AccessTokenInterface as a minimum)
- * @param array $config specify a different token lifetime, token header name, etc
- * @param array $grantTypes An array of OAuth2\GrantType\GrantTypeInterface to use for granting access tokens
- * @param array $responseTypes Response types to use. array keys should be "code" and and "token" for
- * Access Token and Authorization Code response types
- * @param OAuth2\TokenType\TokenTypeInterface $tokenType The token type object to use. Valid token types are "bearer" and "mac"
- * @param OAuth2\ScopeInterface $scopeUtil The scope utility class to use to validate scope
- * @param OAuth2\ClientAssertionType\ClientAssertionTypeInterface $clientAssertionType The method in which to verify the client identity. Default is HttpBasic
- *
- * @ingroup oauth2_section_7
- */
- public function __construct($storage = array(), array $config = array(), array $grantTypes = array(), array $responseTypes = array(), TokenTypeInterface $tokenType = null, ScopeInterface $scopeUtil = null, ClientAssertionTypeInterface $clientAssertionType = null)
- {
- $storage = is_array($storage) ? $storage : array($storage);
- $this->storages = array();
- foreach ($storage as $key => $service) {
- $this->addStorage($service, $key);
- }
-
- // merge all config values. These get passed to our controller objects
- $this->config = array_merge(array(
- 'use_jwt_access_tokens' => false,
- 'store_encrypted_token_string' => true,
- 'use_openid_connect' => false,
- 'id_lifetime' => 3600,
- 'access_lifetime' => 3600,
- 'www_realm' => 'Service',
- 'token_param_name' => 'access_token',
- 'token_bearer_header_name' => 'Bearer',
- 'enforce_state' => true,
- 'require_exact_redirect_uri' => true,
- 'allow_implicit' => false,
- 'allow_credentials_in_request_body' => true,
- 'allow_public_clients' => true,
- 'always_issue_new_refresh_token' => false,
- 'unset_refresh_token_after_use' => true,
- ), $config);
-
- foreach ($grantTypes as $key => $grantType) {
- $this->addGrantType($grantType, $key);
- }
-
- foreach ($responseTypes as $key => $responseType) {
- $this->addResponseType($responseType, $key);
- }
-
- $this->tokenType = $tokenType;
- $this->scopeUtil = $scopeUtil;
- $this->clientAssertionType = $clientAssertionType;
-
- if ($this->config['use_openid_connect']) {
- $this->validateOpenIdConnect();
- }
- }
-
- public function getAuthorizeController()
- {
- if (is_null($this->authorizeController)) {
- $this->authorizeController = $this->createDefaultAuthorizeController();
- }
-
- return $this->authorizeController;
- }
-
- public function getTokenController()
- {
- if (is_null($this->tokenController)) {
- $this->tokenController = $this->createDefaultTokenController();
- }
-
- return $this->tokenController;
- }
-
- public function getResourceController()
- {
- if (is_null($this->resourceController)) {
- $this->resourceController = $this->createDefaultResourceController();
- }
-
- return $this->resourceController;
- }
-
- public function getUserInfoController()
- {
- if (is_null($this->userInfoController)) {
- $this->userInfoController = $this->createDefaultUserInfoController();
- }
-
- return $this->userInfoController;
- }
-
- /**
- * every getter deserves a setter
- */
- public function setAuthorizeController(AuthorizeControllerInterface $authorizeController)
- {
- $this->authorizeController = $authorizeController;
- }
-
- /**
- * every getter deserves a setter
- */
- public function setTokenController(TokenControllerInterface $tokenController)
- {
- $this->tokenController = $tokenController;
- }
-
- /**
- * every getter deserves a setter
- */
- public function setResourceController(ResourceControllerInterface $resourceController)
- {
- $this->resourceController = $resourceController;
- }
-
- /**
- * every getter deserves a setter
- */
- public function setUserInfoController(UserInfoControllerInterface $userInfoController)
- {
- $this->userInfoController = $userInfoController;
- }
-
- /**
- * Return claims about the authenticated end-user.
- * This would be called from the "/UserInfo" endpoint as defined in the spec.
- *
- * @param $request - OAuth2\RequestInterface
- * Request object to grant access token
- *
- * @param $response - OAuth2\ResponseInterface
- * Response object containing error messages (failure) or user claims (success)
- *
- * @throws InvalidArgumentException
- * @throws LogicException
- *
- * @see http://openid.net/specs/openid-connect-core-1_0.html#UserInfo
- */
- public function handleUserInfoRequest(RequestInterface $request, ResponseInterface $response = null)
- {
- $this->response = is_null($response) ? new Response() : $response;
- $this->getUserInfoController()->handleUserInfoRequest($request, $this->response);
-
- return $this->response;
- }
-
- /**
- * Grant or deny a requested access token.
- * This would be called from the "/token" endpoint as defined in the spec.
- * Obviously, you can call your endpoint whatever you want.
- *
- * @param $request - OAuth2\RequestInterface
- * Request object to grant access token
- *
- * @param $response - OAuth2\ResponseInterface
- * Response object containing error messages (failure) or access token (success)
- *
- * @throws InvalidArgumentException
- * @throws LogicException
- *
- * @see http://tools.ietf.org/html/rfc6749#section-4
- * @see http://tools.ietf.org/html/rfc6749#section-10.6
- * @see http://tools.ietf.org/html/rfc6749#section-4.1.3
- *
- * @ingroup oauth2_section_4
- */
- public function handleTokenRequest(RequestInterface $request, ResponseInterface $response = null)
- {
- $this->response = is_null($response) ? new Response() : $response;
- $this->getTokenController()->handleTokenRequest($request, $this->response);
-
- return $this->response;
- }
-
- public function grantAccessToken(RequestInterface $request, ResponseInterface $response = null)
- {
- $this->response = is_null($response) ? new Response() : $response;
- $value = $this->getTokenController()->grantAccessToken($request, $this->response);
-
- return $value;
- }
-
- /**
- * Handle a revoke token request
- * This would be called from the "/revoke" endpoint as defined in the draft Token Revocation spec
- *
- * @see https://tools.ietf.org/html/rfc7009#section-2
- *
- * @param RequestInterface $request
- * @param ResponseInterface $response
- * @return Response|ResponseInterface
- */
- public function handleRevokeRequest(RequestInterface $request, ResponseInterface $response = null)
- {
- $this->response = is_null($response) ? new Response() : $response;
- $this->getTokenController()->handleRevokeRequest($request, $this->response);
-
- return $this->response;
- }
-
- /**
- * Redirect the user appropriately after approval.
- *
- * After the user has approved or denied the resource request the
- * authorization server should call this function to redirect the user
- * appropriately.
- *
- * @param $request
- * The request should have the follow parameters set in the querystring:
- * - response_type: The requested response: an access token, an
- * authorization code, or both.
- * - client_id: The client identifier as described in Section 2.
- * - redirect_uri: An absolute URI to which the authorization server
- * will redirect the user-agent to when the end-user authorization
- * step is completed.
- * - scope: (optional) The scope of the resource request expressed as a
- * list of space-delimited strings.
- * - state: (optional) An opaque value used by the client to maintain
- * state between the request and callback.
- * @param $is_authorized
- * TRUE or FALSE depending on whether the user authorized the access.
- * @param $user_id
- * Identifier of user who authorized the client
- *
- * @see http://tools.ietf.org/html/rfc6749#section-4
- *
- * @ingroup oauth2_section_4
- */
- public function handleAuthorizeRequest(RequestInterface $request, ResponseInterface $response, $is_authorized, $user_id = null)
- {
- $this->response = $response;
- $this->getAuthorizeController()->handleAuthorizeRequest($request, $this->response, $is_authorized, $user_id);
-
- return $this->response;
- }
-
- /**
- * Pull the authorization request data out of the HTTP request.
- * - The redirect_uri is OPTIONAL as per draft 20. But your implementation can enforce it
- * by setting $config['enforce_redirect'] to true.
- * - The state is OPTIONAL but recommended to enforce CSRF. Draft 21 states, however, that
- * CSRF protection is MANDATORY. You can enforce this by setting the $config['enforce_state'] to true.
- *
- * The draft specifies that the parameters should be retrieved from GET, override the Response
- * object to change this
- *
- * @return
- * The authorization parameters so the authorization server can prompt
- * the user for approval if valid.
- *
- * @see http://tools.ietf.org/html/rfc6749#section-4.1.1
- * @see http://tools.ietf.org/html/rfc6749#section-10.12
- *
- * @ingroup oauth2_section_3
- */
- public function validateAuthorizeRequest(RequestInterface $request, ResponseInterface $response = null)
- {
- $this->response = is_null($response) ? new Response() : $response;
- $value = $this->getAuthorizeController()->validateAuthorizeRequest($request, $this->response);
-
- return $value;
- }
-
- public function verifyResourceRequest(RequestInterface $request, ResponseInterface $response = null, $scope = null)
- {
- $this->response = is_null($response) ? new Response() : $response;
- $value = $this->getResourceController()->verifyResourceRequest($request, $this->response, $scope);
-
- return $value;
- }
-
- public function getAccessTokenData(RequestInterface $request, ResponseInterface $response = null)
- {
- $this->response = is_null($response) ? new Response() : $response;
- $value = $this->getResourceController()->getAccessTokenData($request, $this->response);
-
- return $value;
- }
-
- public function addGrantType(GrantTypeInterface $grantType, $identifier = null)
- {
- if (!is_string($identifier)) {
- $identifier = $grantType->getQuerystringIdentifier();
- }
-
- $this->grantTypes[$identifier] = $grantType;
-
- // persist added grant type down to TokenController
- if (!is_null($this->tokenController)) {
- $this->getTokenController()->addGrantType($grantType, $identifier);
- }
- }
-
- /**
- * Set a storage object for the server
- *
- * @param $storage
- * An object implementing one of the Storage interfaces
- * @param $key
- * If null, the storage is set to the key of each storage interface it implements
- *
- * @see storageMap
- */
- public function addStorage($storage, $key = null)
- {
- // if explicitly set to a valid key, do not "magically" set below
- if (isset($this->storageMap[$key])) {
- if (!is_null($storage) && !$storage instanceof $this->storageMap[$key]) {
- throw new \InvalidArgumentException(sprintf('storage of type "%s" must implement interface "%s"', $key, $this->storageMap[$key]));
- }
- $this->storages[$key] = $storage;
-
- // special logic to handle "client" and "client_credentials" strangeness
- if ($key === 'client' && !isset($this->storages['client_credentials'])) {
- if ($storage instanceof \OAuth2\Storage\ClientCredentialsInterface) {
- $this->storages['client_credentials'] = $storage;
- }
- } elseif ($key === 'client_credentials' && !isset($this->storages['client'])) {
- if ($storage instanceof \OAuth2\Storage\ClientInterface) {
- $this->storages['client'] = $storage;
- }
- }
- } elseif (!is_null($key) && !is_numeric($key)) {
- throw new \InvalidArgumentException(sprintf('unknown storage key "%s", must be one of [%s]', $key, implode(', ', array_keys($this->storageMap))));
- } else {
- $set = false;
- foreach ($this->storageMap as $type => $interface) {
- if ($storage instanceof $interface) {
- $this->storages[$type] = $storage;
- $set = true;
- }
- }
-
- if (!$set) {
- throw new \InvalidArgumentException(sprintf('storage of class "%s" must implement one of [%s]', get_class($storage), implode(', ', $this->storageMap)));
- }
- }
- }
-
- public function addResponseType(ResponseTypeInterface $responseType, $key = null)
- {
- $key = $this->normalizeResponseType($key);
-
- if (isset($this->responseTypeMap[$key])) {
- if (!$responseType instanceof $this->responseTypeMap[$key]) {
- throw new \InvalidArgumentException(sprintf('responseType of type "%s" must implement interface "%s"', $key, $this->responseTypeMap[$key]));
- }
- $this->responseTypes[$key] = $responseType;
- } elseif (!is_null($key) && !is_numeric($key)) {
- throw new \InvalidArgumentException(sprintf('unknown responseType key "%s", must be one of [%s]', $key, implode(', ', array_keys($this->responseTypeMap))));
- } else {
- $set = false;
- foreach ($this->responseTypeMap as $type => $interface) {
- if ($responseType instanceof $interface) {
- $this->responseTypes[$type] = $responseType;
- $set = true;
- }
- }
-
- if (!$set) {
- throw new \InvalidArgumentException(sprintf('Unknown response type %s. Please implement one of [%s]', get_class($responseType), implode(', ', $this->responseTypeMap)));
- }
- }
- }
-
- public function getScopeUtil()
- {
- if (!$this->scopeUtil) {
- $storage = isset($this->storages['scope']) ? $this->storages['scope'] : null;
- $this->scopeUtil = new Scope($storage);
- }
-
- return $this->scopeUtil;
- }
-
- /**
- * every getter deserves a setter
- */
- public function setScopeUtil($scopeUtil)
- {
- $this->scopeUtil = $scopeUtil;
- }
-
- protected function createDefaultAuthorizeController()
- {
- if (!isset($this->storages['client'])) {
- throw new \LogicException("You must supply a storage object implementing OAuth2\Storage\ClientInterface to use the authorize server");
- }
- if (0 == count($this->responseTypes)) {
- $this->responseTypes = $this->getDefaultResponseTypes();
- }
- if ($this->config['use_openid_connect'] && !isset($this->responseTypes['id_token'])) {
- $this->responseTypes['id_token'] = $this->createDefaultIdTokenResponseType();
- if ($this->config['allow_implicit']) {
- $this->responseTypes['id_token token'] = $this->createDefaultIdTokenTokenResponseType();
- }
- }
-
- $config = array_intersect_key($this->config, array_flip(explode(' ', 'allow_implicit enforce_state require_exact_redirect_uri')));
-
- if ($this->config['use_openid_connect']) {
- return new OpenIDAuthorizeController($this->storages['client'], $this->responseTypes, $config, $this->getScopeUtil());
- }
-
- return new AuthorizeController($this->storages['client'], $this->responseTypes, $config, $this->getScopeUtil());
- }
-
- protected function createDefaultTokenController()
- {
- if (0 == count($this->grantTypes)) {
- $this->grantTypes = $this->getDefaultGrantTypes();
- }
-
- if (is_null($this->clientAssertionType)) {
- // see if HttpBasic assertion type is requred. If so, then create it from storage classes.
- foreach ($this->grantTypes as $grantType) {
- if (!$grantType instanceof ClientAssertionTypeInterface) {
- if (!isset($this->storages['client_credentials'])) {
- throw new \LogicException("You must supply a storage object implementing OAuth2\Storage\ClientCredentialsInterface to use the token server");
- }
- $config = array_intersect_key($this->config, array_flip(explode(' ', 'allow_credentials_in_request_body allow_public_clients')));
- $this->clientAssertionType = new HttpBasic($this->storages['client_credentials'], $config);
- break;
- }
- }
- }
-
- if (!isset($this->storages['client'])) {
- throw new \LogicException("You must supply a storage object implementing OAuth2\Storage\ClientInterface to use the token server");
- }
-
- $accessTokenResponseType = $this->getAccessTokenResponseType();
-
- return new TokenController($accessTokenResponseType, $this->storages['client'], $this->grantTypes, $this->clientAssertionType, $this->getScopeUtil());
- }
-
- protected function createDefaultResourceController()
- {
- if ($this->config['use_jwt_access_tokens']) {
- // overwrites access token storage with crypto token storage if "use_jwt_access_tokens" is set
- if (!isset($this->storages['access_token']) || !$this->storages['access_token'] instanceof JwtAccessTokenInterface) {
- $this->storages['access_token'] = $this->createDefaultJwtAccessTokenStorage();
- }
- } elseif (!isset($this->storages['access_token'])) {
- throw new \LogicException("You must supply a storage object implementing OAuth2\Storage\AccessTokenInterface or use JwtAccessTokens to use the resource server");
- }
-
- if (!$this->tokenType) {
- $this->tokenType = $this->getDefaultTokenType();
- }
-
- $config = array_intersect_key($this->config, array('www_realm' => ''));
-
- return new ResourceController($this->tokenType, $this->storages['access_token'], $config, $this->getScopeUtil());
- }
-
- protected function createDefaultUserInfoController()
- {
- if ($this->config['use_jwt_access_tokens']) {
- // overwrites access token storage with crypto token storage if "use_jwt_access_tokens" is set
- if (!isset($this->storages['access_token']) || !$this->storages['access_token'] instanceof JwtAccessTokenInterface) {
- $this->storages['access_token'] = $this->createDefaultJwtAccessTokenStorage();
- }
- } elseif (!isset($this->storages['access_token'])) {
- throw new \LogicException("You must supply a storage object implementing OAuth2\Storage\AccessTokenInterface or use JwtAccessTokens to use the UserInfo server");
- }
-
- if (!isset($this->storages['user_claims'])) {
- throw new \LogicException("You must supply a storage object implementing OAuth2\OpenID\Storage\UserClaimsInterface to use the UserInfo server");
- }
-
- if (!$this->tokenType) {
- $this->tokenType = $this->getDefaultTokenType();
- }
-
- $config = array_intersect_key($this->config, array('www_realm' => ''));
-
- return new UserInfoController($this->tokenType, $this->storages['access_token'], $this->storages['user_claims'], $config, $this->getScopeUtil());
- }
-
- protected function getDefaultTokenType()
- {
- $config = array_intersect_key($this->config, array_flip(explode(' ', 'token_param_name token_bearer_header_name')));
-
- return new Bearer($config);
- }
-
- protected function getDefaultResponseTypes()
- {
- $responseTypes = array();
-
- if ($this->config['allow_implicit']) {
- $responseTypes['token'] = $this->getAccessTokenResponseType();
- }
-
- if ($this->config['use_openid_connect']) {
- $responseTypes['id_token'] = $this->getIdTokenResponseType();
- if ($this->config['allow_implicit']) {
- $responseTypes['id_token token'] = $this->getIdTokenTokenResponseType();
- }
- }
-
- if (isset($this->storages['authorization_code'])) {
- $config = array_intersect_key($this->config, array_flip(explode(' ', 'enforce_redirect auth_code_lifetime')));
- if ($this->config['use_openid_connect']) {
- if (!$this->storages['authorization_code'] instanceof OpenIDAuthorizationCodeInterface) {
- throw new \LogicException("Your authorization_code storage must implement OAuth2\OpenID\Storage\AuthorizationCodeInterface to work when 'use_openid_connect' is true");
- }
- $responseTypes['code'] = new OpenIDAuthorizationCodeResponseType($this->storages['authorization_code'], $config);
- $responseTypes['code id_token'] = new CodeIdToken($responseTypes['code'], $responseTypes['id_token']);
- } else {
- $responseTypes['code'] = new AuthorizationCodeResponseType($this->storages['authorization_code'], $config);
- }
- }
-
- if (count($responseTypes) == 0) {
- throw new \LogicException("You must supply an array of response_types in the constructor or implement a OAuth2\Storage\AuthorizationCodeInterface storage object or set 'allow_implicit' to true and implement a OAuth2\Storage\AccessTokenInterface storage object");
- }
-
- return $responseTypes;
- }
-
- protected function getDefaultGrantTypes()
- {
- $grantTypes = array();
-
- if (isset($this->storages['user_credentials'])) {
- $grantTypes['password'] = new UserCredentials($this->storages['user_credentials']);
- }
-
- if (isset($this->storages['client_credentials'])) {
- $config = array_intersect_key($this->config, array('allow_credentials_in_request_body' => ''));
- $grantTypes['client_credentials'] = new ClientCredentials($this->storages['client_credentials'], $config);
- }
-
- if (isset($this->storages['refresh_token'])) {
- $config = array_intersect_key($this->config, array_flip(explode(' ', 'always_issue_new_refresh_token unset_refresh_token_after_use')));
- $grantTypes['refresh_token'] = new RefreshToken($this->storages['refresh_token'], $config);
- }
-
- if (isset($this->storages['authorization_code'])) {
- if ($this->config['use_openid_connect']) {
- if (!$this->storages['authorization_code'] instanceof OpenIDAuthorizationCodeInterface) {
- throw new \LogicException("Your authorization_code storage must implement OAuth2\OpenID\Storage\AuthorizationCodeInterface to work when 'use_openid_connect' is true");
- }
- $grantTypes['authorization_code'] = new OpenIDAuthorizationCodeGrantType($this->storages['authorization_code']);
- } else {
- $grantTypes['authorization_code'] = new AuthorizationCode($this->storages['authorization_code']);
- }
- }
-
- if (count($grantTypes) == 0) {
- throw new \LogicException("Unable to build default grant types - You must supply an array of grant_types in the constructor");
- }
-
- return $grantTypes;
- }
-
- protected function getAccessTokenResponseType()
- {
- if (isset($this->responseTypes['token'])) {
- return $this->responseTypes['token'];
- }
-
- if ($this->config['use_jwt_access_tokens']) {
- return $this->createDefaultJwtAccessTokenResponseType();
- }
-
- return $this->createDefaultAccessTokenResponseType();
- }
-
- protected function getIdTokenResponseType()
- {
- if (isset($this->responseTypes['id_token'])) {
- return $this->responseTypes['id_token'];
- }
-
- return $this->createDefaultIdTokenResponseType();
- }
-
- protected function getIdTokenTokenResponseType()
- {
- if (isset($this->responseTypes['id_token token'])) {
- return $this->responseTypes['id_token token'];
- }
-
- return $this->createDefaultIdTokenTokenResponseType();
- }
-
- /**
- * For Resource Controller
- */
- protected function createDefaultJwtAccessTokenStorage()
- {
- if (!isset($this->storages['public_key'])) {
- throw new \LogicException("You must supply a storage object implementing OAuth2\Storage\PublicKeyInterface to use crypto tokens");
- }
- $tokenStorage = null;
- if (!empty($this->config['store_encrypted_token_string']) && isset($this->storages['access_token'])) {
- $tokenStorage = $this->storages['access_token'];
- }
- // wrap the access token storage as required.
- return new JwtAccessTokenStorage($this->storages['public_key'], $tokenStorage);
- }
-
- /**
- * For Authorize and Token Controllers
- */
- protected function createDefaultJwtAccessTokenResponseType()
- {
- if (!isset($this->storages['public_key'])) {
- throw new \LogicException("You must supply a storage object implementing OAuth2\Storage\PublicKeyInterface to use crypto tokens");
- }
-
- $tokenStorage = null;
- if (isset($this->storages['access_token'])) {
- $tokenStorage = $this->storages['access_token'];
- }
-
- $refreshStorage = null;
- if (isset($this->storages['refresh_token'])) {
- $refreshStorage = $this->storages['refresh_token'];
- }
-
- $config = array_intersect_key($this->config, array_flip(explode(' ', 'store_encrypted_token_string issuer access_lifetime refresh_token_lifetime')));
-
- return new JwtAccessToken($this->storages['public_key'], $tokenStorage, $refreshStorage, $config);
- }
-
- protected function createDefaultAccessTokenResponseType()
- {
- if (!isset($this->storages['access_token'])) {
- throw new \LogicException("You must supply a response type implementing OAuth2\ResponseType\AccessTokenInterface, or a storage object implementing OAuth2\Storage\AccessTokenInterface to use the token server");
- }
-
- $refreshStorage = null;
- if (isset($this->storages['refresh_token'])) {
- $refreshStorage = $this->storages['refresh_token'];
- }
-
- $config = array_intersect_key($this->config, array_flip(explode(' ', 'access_lifetime refresh_token_lifetime')));
- $config['token_type'] = $this->tokenType ? $this->tokenType->getTokenType() : $this->getDefaultTokenType()->getTokenType();
-
- return new AccessToken($this->storages['access_token'], $refreshStorage, $config);
- }
-
- protected function createDefaultIdTokenResponseType()
- {
- if (!isset($this->storages['user_claims'])) {
- throw new \LogicException("You must supply a storage object implementing OAuth2\OpenID\Storage\UserClaimsInterface to use openid connect");
- }
- if (!isset($this->storages['public_key'])) {
- throw new \LogicException("You must supply a storage object implementing OAuth2\Storage\PublicKeyInterface to use openid connect");
- }
-
- $config = array_intersect_key($this->config, array_flip(explode(' ', 'issuer id_lifetime')));
-
- return new IdToken($this->storages['user_claims'], $this->storages['public_key'], $config);
- }
-
- protected function createDefaultIdTokenTokenResponseType()
- {
- return new IdTokenToken($this->getAccessTokenResponseType(), $this->getIdTokenResponseType());
- }
-
- protected function validateOpenIdConnect()
- {
- $authCodeGrant = $this->getGrantType('authorization_code');
- if (!empty($authCodeGrant) && !$authCodeGrant instanceof OpenIDAuthorizationCodeGrantType) {
- throw new \InvalidArgumentException('You have enabled OpenID Connect, but supplied a grant type that does not support it.');
- }
- }
-
- protected function normalizeResponseType($name)
- {
- // for multiple-valued response types - make them alphabetical
- if (!empty($name) && false !== strpos($name, ' ')) {
- $types = explode(' ', $name);
- sort($types);
- $name = implode(' ', $types);
- }
-
- return $name;
- }
-
- public function getResponse()
- {
- return $this->response;
- }
-
- public function getStorages()
- {
- return $this->storages;
- }
-
- public function getStorage($name)
- {
- return isset($this->storages[$name]) ? $this->storages[$name] : null;
- }
-
- public function getGrantTypes()
- {
- return $this->grantTypes;
- }
-
- public function getGrantType($name)
- {
- return isset($this->grantTypes[$name]) ? $this->grantTypes[$name] : null;
- }
-
- public function getResponseTypes()
- {
- return $this->responseTypes;
- }
-
- public function getResponseType($name)
- {
- // for multiple-valued response types - make them alphabetical
- $name = $this->normalizeResponseType($name);
-
- return isset($this->responseTypes[$name]) ? $this->responseTypes[$name] : null;
- }
-
- public function getTokenType()
- {
- return $this->tokenType;
- }
-
- public function getClientAssertionType()
- {
- return $this->clientAssertionType;
- }
-
- public function setConfig($name, $value)
- {
- $this->config[$name] = $value;
- }
-
- public function getConfig($name, $default = null)
- {
- return isset($this->config[$name]) ? $this->config[$name] : $default;
- }
-}
diff --git a/library/oauth2/src/OAuth2/Storage/AuthorizationCodeInterface.php b/library/oauth2/src/OAuth2/Storage/AuthorizationCodeInterface.php
deleted file mode 100644
index 3beb0e437..000000000
--- a/library/oauth2/src/OAuth2/Storage/AuthorizationCodeInterface.php
+++ /dev/null
@@ -1,86 +0,0 @@
-<?php
-
-namespace OAuth2\Storage;
-
-/**
- * Implement this interface to specify where the OAuth2 Server
- * should get/save authorization codes for the "Authorization Code"
- * grant type
- *
- * @author Brent Shaffer <bshafs at gmail dot com>
- */
-interface AuthorizationCodeInterface
-{
- /**
- * The Authorization Code grant type supports a response type of "code".
- *
- * @var string
- * @see http://tools.ietf.org/html/rfc6749#section-1.4.1
- * @see http://tools.ietf.org/html/rfc6749#section-4.2
- */
- const RESPONSE_TYPE_CODE = "code";
-
- /**
- * Fetch authorization code data (probably the most common grant type).
- *
- * Retrieve the stored data for the given authorization code.
- *
- * Required for OAuth2::GRANT_TYPE_AUTH_CODE.
- *
- * @param $code
- * Authorization code to be check with.
- *
- * @return
- * An associative array as below, and NULL if the code is invalid
- * @code
- * return array(
- * "client_id" => CLIENT_ID, // REQUIRED Stored client identifier
- * "user_id" => USER_ID, // REQUIRED Stored user identifier
- * "expires" => EXPIRES, // REQUIRED Stored expiration in unix timestamp
- * "redirect_uri" => REDIRECT_URI, // REQUIRED Stored redirect URI
- * "scope" => SCOPE, // OPTIONAL Stored scope values in space-separated string
- * );
- * @endcode
- *
- * @see http://tools.ietf.org/html/rfc6749#section-4.1
- *
- * @ingroup oauth2_section_4
- */
- public function getAuthorizationCode($code);
-
- /**
- * Take the provided authorization code values and store them somewhere.
- *
- * This function should be the storage counterpart to getAuthCode().
- *
- * If storage fails for some reason, we're not currently checking for
- * any sort of success/failure, so you should bail out of the script
- * and provide a descriptive fail message.
- *
- * Required for OAuth2::GRANT_TYPE_AUTH_CODE.
- *
- * @param string $code Authorization code to be stored.
- * @param mixed $client_id Client identifier to be stored.
- * @param mixed $user_id User identifier to be stored.
- * @param string $redirect_uri Redirect URI(s) to be stored in a space-separated string.
- * @param int $expires Expiration to be stored as a Unix timestamp.
- * @param string $scope OPTIONAL Scopes to be stored in space-separated string.
- *
- * @ingroup oauth2_section_4
- */
- public function setAuthorizationCode($code, $client_id, $user_id, $redirect_uri, $expires, $scope = null);
-
- /**
- * once an Authorization Code is used, it must be exipired
- *
- * @see http://tools.ietf.org/html/rfc6749#section-4.1.2
- *
- * The client MUST NOT use the authorization code
- * more than once. If an authorization code is used more than
- * once, the authorization server MUST deny the request and SHOULD
- * revoke (when possible) all tokens previously issued based on
- * that authorization code
- *
- */
- public function expireAuthorizationCode($code);
-}
diff --git a/library/oauth2/src/OAuth2/Storage/Cassandra.php b/library/oauth2/src/OAuth2/Storage/Cassandra.php
deleted file mode 100644
index 602e8a058..000000000
--- a/library/oauth2/src/OAuth2/Storage/Cassandra.php
+++ /dev/null
@@ -1,480 +0,0 @@
-<?php
-
-namespace OAuth2\Storage;
-
-use phpcassa\ColumnFamily;
-use phpcassa\ColumnSlice;
-use phpcassa\Connection\ConnectionPool;
-use OAuth2\OpenID\Storage\UserClaimsInterface;
-use OAuth2\OpenID\Storage\AuthorizationCodeInterface as OpenIDAuthorizationCodeInterface;
-
-/**
- * Cassandra storage for all storage types
- *
- * To use, install "thobbs/phpcassa" via composer
- * <code>
- * composer require thobbs/phpcassa:dev-master
- * </code>
- *
- * Once this is done, instantiate the
- * <code>
- * $cassandra = new \phpcassa\Connection\ConnectionPool('oauth2_server', array('127.0.0.1:9160'));
- * </code>
- *
- * Then, register the storage client:
- * <code>
- * $storage = new OAuth2\Storage\Cassandra($cassandra);
- * $storage->setClientDetails($client_id, $client_secret, $redirect_uri);
- * </code>
- *
- * @see test/lib/OAuth2/Storage/Bootstrap::getCassandraStorage
- */
-class Cassandra implements AuthorizationCodeInterface,
- AccessTokenInterface,
- ClientCredentialsInterface,
- UserCredentialsInterface,
- RefreshTokenInterface,
- JwtBearerInterface,
- ScopeInterface,
- PublicKeyInterface,
- UserClaimsInterface,
- OpenIDAuthorizationCodeInterface
-{
-
- private $cache;
-
- /* The cassandra client */
- protected $cassandra;
-
- /* Configuration array */
- protected $config;
-
- /**
- * Cassandra Storage! uses phpCassa
- *
- * @param \phpcassa\ConnectionPool $cassandra
- * @param array $config
- */
- public function __construct($connection = array(), array $config = array())
- {
- if ($connection instanceof ConnectionPool) {
- $this->cassandra = $connection;
- } else {
- if (!is_array($connection)) {
- throw new \InvalidArgumentException('First argument to OAuth2\Storage\Cassandra must be an instance of phpcassa\Connection\ConnectionPool or a configuration array');
- }
- $connection = array_merge(array(
- 'keyspace' => 'oauth2',
- 'servers' => null,
- ), $connection);
-
- $this->cassandra = new ConnectionPool($connection['keyspace'], $connection['servers']);
- }
-
- $this->config = array_merge(array(
- // cassandra config
- 'column_family' => 'auth',
-
- // key names
- 'client_key' => 'oauth_clients:',
- 'access_token_key' => 'oauth_access_tokens:',
- 'refresh_token_key' => 'oauth_refresh_tokens:',
- 'code_key' => 'oauth_authorization_codes:',
- 'user_key' => 'oauth_users:',
- 'jwt_key' => 'oauth_jwt:',
- 'scope_key' => 'oauth_scopes:',
- 'public_key_key' => 'oauth_public_keys:',
- ), $config);
- }
-
- protected function getValue($key)
- {
- if (isset($this->cache[$key])) {
- return $this->cache[$key];
- }
- $cf = new ColumnFamily($this->cassandra, $this->config['column_family']);
-
- try {
- $value = $cf->get($key, new ColumnSlice("", ""));
- $value = array_shift($value);
- } catch (\cassandra\NotFoundException $e) {
- return false;
- }
-
- return json_decode($value, true);
- }
-
- protected function setValue($key, $value, $expire = 0)
- {
- $this->cache[$key] = $value;
-
- $cf = new ColumnFamily($this->cassandra, $this->config['column_family']);
-
- $str = json_encode($value);
- if ($expire > 0) {
- try {
- $seconds = $expire - time();
- // __data key set as C* requires a field, note: max TTL can only be 630720000 seconds
- $cf->insert($key, array('__data' => $str), null, $seconds);
- } catch (\Exception $e) {
- return false;
- }
- } else {
- try {
- // __data key set as C* requires a field
- $cf->insert($key, array('__data' => $str));
- } catch (\Exception $e) {
- return false;
- }
- }
-
- return true;
- }
-
- protected function expireValue($key)
- {
- unset($this->cache[$key]);
-
- $cf = new ColumnFamily($this->cassandra, $this->config['column_family']);
-
- if ($cf->get_count($key) > 0) {
- try {
- // __data key set as C* requires a field
- $cf->remove($key, array('__data'));
- } catch (\Exception $e) {
- return false;
- }
-
- return true;
- }
-
- return false;
- }
-
- /* AuthorizationCodeInterface */
- public function getAuthorizationCode($code)
- {
- return $this->getValue($this->config['code_key'] . $code);
- }
-
- public function setAuthorizationCode($authorization_code, $client_id, $user_id, $redirect_uri, $expires, $scope = null, $id_token = null)
- {
- return $this->setValue(
- $this->config['code_key'] . $authorization_code,
- compact('authorization_code', 'client_id', 'user_id', 'redirect_uri', 'expires', 'scope', 'id_token'),
- $expires
- );
- }
-
- public function expireAuthorizationCode($code)
- {
- $key = $this->config['code_key'] . $code;
- unset($this->cache[$key]);
-
- return $this->expireValue($key);
- }
-
- /* UserCredentialsInterface */
- public function checkUserCredentials($username, $password)
- {
- if ($user = $this->getUser($username)) {
- return $this->checkPassword($user, $password);
- }
-
- return false;
- }
-
- // plaintext passwords are bad! Override this for your application
- protected function checkPassword($user, $password)
- {
- return $user['password'] == $this->hashPassword($password);
- }
-
- // use a secure hashing algorithm when storing passwords. Override this for your application
- protected function hashPassword($password)
- {
- return sha1($password);
- }
-
- public function getUserDetails($username)
- {
- return $this->getUser($username);
- }
-
- public function getUser($username)
- {
- if (!$userInfo = $this->getValue($this->config['user_key'] . $username)) {
- return false;
- }
-
- // the default behavior is to use "username" as the user_id
- return array_merge(array(
- 'user_id' => $username,
- ), $userInfo);
- }
-
- public function setUser($username, $password, $first_name = null, $last_name = null)
- {
- $password = $this->hashPassword($password);
-
- return $this->setValue(
- $this->config['user_key'] . $username,
- compact('username', 'password', 'first_name', 'last_name')
- );
- }
-
- /* ClientCredentialsInterface */
- public function checkClientCredentials($client_id, $client_secret = null)
- {
- if (!$client = $this->getClientDetails($client_id)) {
- return false;
- }
-
- return isset($client['client_secret'])
- && $client['client_secret'] == $client_secret;
- }
-
- public function isPublicClient($client_id)
- {
- if (!$client = $this->getClientDetails($client_id)) {
- return false;
- }
-
- return empty($client['client_secret']);;
- }
-
- /* ClientInterface */
- public function getClientDetails($client_id)
- {
- return $this->getValue($this->config['client_key'] . $client_id);
- }
-
- public function setClientDetails($client_id, $client_secret = null, $redirect_uri = null, $grant_types = null, $scope = null, $user_id = null)
- {
- return $this->setValue(
- $this->config['client_key'] . $client_id,
- compact('client_id', 'client_secret', 'redirect_uri', 'grant_types', 'scope', 'user_id')
- );
- }
-
- public function checkRestrictedGrantType($client_id, $grant_type)
- {
- $details = $this->getClientDetails($client_id);
- if (isset($details['grant_types'])) {
- $grant_types = explode(' ', $details['grant_types']);
-
- return in_array($grant_type, (array) $grant_types);
- }
-
- // if grant_types are not defined, then none are restricted
- return true;
- }
-
- /* RefreshTokenInterface */
- public function getRefreshToken($refresh_token)
- {
- return $this->getValue($this->config['refresh_token_key'] . $refresh_token);
- }
-
- public function setRefreshToken($refresh_token, $client_id, $user_id, $expires, $scope = null)
- {
- return $this->setValue(
- $this->config['refresh_token_key'] . $refresh_token,
- compact('refresh_token', 'client_id', 'user_id', 'expires', 'scope'),
- $expires
- );
- }
-
- public function unsetRefreshToken($refresh_token)
- {
- return $this->expireValue($this->config['refresh_token_key'] . $refresh_token);
- }
-
- /* AccessTokenInterface */
- public function getAccessToken($access_token)
- {
- return $this->getValue($this->config['access_token_key'].$access_token);
- }
-
- public function setAccessToken($access_token, $client_id, $user_id, $expires, $scope = null)
- {
- return $this->setValue(
- $this->config['access_token_key'].$access_token,
- compact('access_token', 'client_id', 'user_id', 'expires', 'scope'),
- $expires
- );
- }
-
- public function unsetAccessToken($access_token)
- {
- return $this->expireValue($this->config['access_token_key'] . $access_token);
- }
-
- /* ScopeInterface */
- public function scopeExists($scope)
- {
- $scope = explode(' ', $scope);
-
- $result = $this->getValue($this->config['scope_key'].'supported:global');
-
- $supportedScope = explode(' ', (string) $result);
-
- return (count(array_diff($scope, $supportedScope)) == 0);
- }
-
- public function getDefaultScope($client_id = null)
- {
- if (is_null($client_id) || !$result = $this->getValue($this->config['scope_key'].'default:'.$client_id)) {
- $result = $this->getValue($this->config['scope_key'].'default:global');
- }
-
- return $result;
- }
-
- public function setScope($scope, $client_id = null, $type = 'supported')
- {
- if (!in_array($type, array('default', 'supported'))) {
- throw new \InvalidArgumentException('"$type" must be one of "default", "supported"');
- }
-
- if (is_null($client_id)) {
- $key = $this->config['scope_key'].$type.':global';
- } else {
- $key = $this->config['scope_key'].$type.':'.$client_id;
- }
-
- return $this->setValue($key, $scope);
- }
-
- /*JWTBearerInterface */
- public function getClientKey($client_id, $subject)
- {
- if (!$jwt = $this->getValue($this->config['jwt_key'] . $client_id)) {
- return false;
- }
-
- if (isset($jwt['subject']) && $jwt['subject'] == $subject ) {
- return $jwt['key'];
- }
-
- return null;
- }
-
- public function setClientKey($client_id, $key, $subject = null)
- {
- return $this->setValue($this->config['jwt_key'] . $client_id, array(
- 'key' => $key,
- 'subject' => $subject
- ));
- }
-
- /*ScopeInterface */
- public function getClientScope($client_id)
- {
- if (!$clientDetails = $this->getClientDetails($client_id)) {
- return false;
- }
-
- if (isset($clientDetails['scope'])) {
- return $clientDetails['scope'];
- }
-
- return null;
- }
-
- public function getJti($client_id, $subject, $audience, $expiration, $jti)
- {
- //TODO: Needs cassandra implementation.
- throw new \Exception('getJti() for the Cassandra driver is currently unimplemented.');
- }
-
- public function setJti($client_id, $subject, $audience, $expiration, $jti)
- {
- //TODO: Needs cassandra implementation.
- throw new \Exception('setJti() for the Cassandra driver is currently unimplemented.');
- }
-
- /* PublicKeyInterface */
- public function getPublicKey($client_id = '')
- {
- $public_key = $this->getValue($this->config['public_key_key'] . $client_id);
- if (is_array($public_key)) {
- return $public_key['public_key'];
- }
- $public_key = $this->getValue($this->config['public_key_key']);
- if (is_array($public_key)) {
- return $public_key['public_key'];
- }
- }
-
- public function getPrivateKey($client_id = '')
- {
- $public_key = $this->getValue($this->config['public_key_key'] . $client_id);
- if (is_array($public_key)) {
- return $public_key['private_key'];
- }
- $public_key = $this->getValue($this->config['public_key_key']);
- if (is_array($public_key)) {
- return $public_key['private_key'];
- }
- }
-
- public function getEncryptionAlgorithm($client_id = null)
- {
- $public_key = $this->getValue($this->config['public_key_key'] . $client_id);
- if (is_array($public_key)) {
- return $public_key['encryption_algorithm'];
- }
- $public_key = $this->getValue($this->config['public_key_key']);
- if (is_array($public_key)) {
- return $public_key['encryption_algorithm'];
- }
-
- return 'RS256';
- }
-
- /* UserClaimsInterface */
- public function getUserClaims($user_id, $claims)
- {
- $userDetails = $this->getUserDetails($user_id);
- if (!is_array($userDetails)) {
- return false;
- }
-
- $claims = explode(' ', trim($claims));
- $userClaims = array();
-
- // for each requested claim, if the user has the claim, set it in the response
- $validClaims = explode(' ', self::VALID_CLAIMS);
- foreach ($validClaims as $validClaim) {
- if (in_array($validClaim, $claims)) {
- if ($validClaim == 'address') {
- // address is an object with subfields
- $userClaims['address'] = $this->getUserClaim($validClaim, $userDetails['address'] ?: $userDetails);
- } else {
- $userClaims = array_merge($userClaims, $this->getUserClaim($validClaim, $userDetails));
- }
- }
- }
-
- return $userClaims;
- }
-
- protected function getUserClaim($claim, $userDetails)
- {
- $userClaims = array();
- $claimValuesString = constant(sprintf('self::%s_CLAIM_VALUES', strtoupper($claim)));
- $claimValues = explode(' ', $claimValuesString);
-
- foreach ($claimValues as $value) {
- if ($value == 'email_verified') {
- $userClaims[$value] = $userDetails[$value]=='true' ? true : false;
- } else {
- $userClaims[$value] = isset($userDetails[$value]) ? $userDetails[$value] : null;
- }
- }
-
- return $userClaims;
- }
-
-}
diff --git a/library/oauth2/src/OAuth2/Storage/Mongo.php b/library/oauth2/src/OAuth2/Storage/Mongo.php
deleted file mode 100644
index cef35e5e9..000000000
--- a/library/oauth2/src/OAuth2/Storage/Mongo.php
+++ /dev/null
@@ -1,339 +0,0 @@
-<?php
-
-namespace OAuth2\Storage;
-
-use OAuth2\OpenID\Storage\AuthorizationCodeInterface as OpenIDAuthorizationCodeInterface;
-
-/**
- * Simple MongoDB storage for all storage types
- *
- * NOTE: This class is meant to get users started
- * quickly. If your application requires further
- * customization, extend this class or create your own.
- *
- * NOTE: Passwords are stored in plaintext, which is never
- * a good idea. Be sure to override this for your application
- *
- * @author Julien Chaumond <chaumond@gmail.com>
- */
-class Mongo implements AuthorizationCodeInterface,
- AccessTokenInterface,
- ClientCredentialsInterface,
- UserCredentialsInterface,
- RefreshTokenInterface,
- JwtBearerInterface,
- OpenIDAuthorizationCodeInterface
-{
- protected $db;
- protected $config;
-
- public function __construct($connection, $config = array())
- {
- if ($connection instanceof \MongoDB) {
- $this->db = $connection;
- } else {
- if (!is_array($connection)) {
- throw new \InvalidArgumentException('First argument to OAuth2\Storage\Mongo must be an instance of MongoDB or a configuration array');
- }
- $server = sprintf('mongodb://%s:%d', $connection['host'], $connection['port']);
- $m = new \MongoClient($server);
- $this->db = $m->{$connection['database']};
- }
-
- $this->config = array_merge(array(
- 'client_table' => 'oauth_clients',
- 'access_token_table' => 'oauth_access_tokens',
- 'refresh_token_table' => 'oauth_refresh_tokens',
- 'code_table' => 'oauth_authorization_codes',
- 'user_table' => 'oauth_users',
- 'jwt_table' => 'oauth_jwt',
- ), $config);
- }
-
- // Helper function to access a MongoDB collection by `type`:
- protected function collection($name)
- {
- return $this->db->{$this->config[$name]};
- }
-
- /* ClientCredentialsInterface */
- public function checkClientCredentials($client_id, $client_secret = null)
- {
- if ($result = $this->collection('client_table')->findOne(array('client_id' => $client_id))) {
- return $result['client_secret'] == $client_secret;
- }
-
- return false;
- }
-
- public function isPublicClient($client_id)
- {
- if (!$result = $this->collection('client_table')->findOne(array('client_id' => $client_id))) {
- return false;
- }
-
- return empty($result['client_secret']);
- }
-
- /* ClientInterface */
- public function getClientDetails($client_id)
- {
- $result = $this->collection('client_table')->findOne(array('client_id' => $client_id));
-
- return is_null($result) ? false : $result;
- }
-
- public function setClientDetails($client_id, $client_secret = null, $redirect_uri = null, $grant_types = null, $scope = null, $user_id = null)
- {
- if ($this->getClientDetails($client_id)) {
- $this->collection('client_table')->update(
- array('client_id' => $client_id),
- array('$set' => array(
- 'client_secret' => $client_secret,
- 'redirect_uri' => $redirect_uri,
- 'grant_types' => $grant_types,
- 'scope' => $scope,
- 'user_id' => $user_id,
- ))
- );
- } else {
- $client = array(
- 'client_id' => $client_id,
- 'client_secret' => $client_secret,
- 'redirect_uri' => $redirect_uri,
- 'grant_types' => $grant_types,
- 'scope' => $scope,
- 'user_id' => $user_id,
- );
- $this->collection('client_table')->insert($client);
- }
-
- return true;
- }
-
- public function checkRestrictedGrantType($client_id, $grant_type)
- {
- $details = $this->getClientDetails($client_id);
- if (isset($details['grant_types'])) {
- $grant_types = explode(' ', $details['grant_types']);
-
- return in_array($grant_type, $grant_types);
- }
-
- // if grant_types are not defined, then none are restricted
- return true;
- }
-
- /* AccessTokenInterface */
- public function getAccessToken($access_token)
- {
- $token = $this->collection('access_token_table')->findOne(array('access_token' => $access_token));
-
- return is_null($token) ? false : $token;
- }
-
- public function setAccessToken($access_token, $client_id, $user_id, $expires, $scope = null)
- {
- // if it exists, update it.
- if ($this->getAccessToken($access_token)) {
- $this->collection('access_token_table')->update(
- array('access_token' => $access_token),
- array('$set' => array(
- 'client_id' => $client_id,
- 'expires' => $expires,
- 'user_id' => $user_id,
- 'scope' => $scope
- ))
- );
- } else {
- $token = array(
- 'access_token' => $access_token,
- 'client_id' => $client_id,
- 'expires' => $expires,
- 'user_id' => $user_id,
- 'scope' => $scope
- );
- $this->collection('access_token_table')->insert($token);
- }
-
- return true;
- }
-
- public function unsetAccessToken($access_token)
- {
- $result = $this->collection('access_token_table')->remove(array(
- 'access_token' => $access_token
- ), array('w' => 1));
-
- return $result['n'] > 0;
- }
-
-
- /* AuthorizationCodeInterface */
- public function getAuthorizationCode($code)
- {
- $code = $this->collection('code_table')->findOne(array('authorization_code' => $code));
-
- return is_null($code) ? false : $code;
- }
-
- public function setAuthorizationCode($code, $client_id, $user_id, $redirect_uri, $expires, $scope = null, $id_token = null)
- {
- // if it exists, update it.
- if ($this->getAuthorizationCode($code)) {
- $this->collection('code_table')->update(
- array('authorization_code' => $code),
- array('$set' => array(
- 'client_id' => $client_id,
- 'user_id' => $user_id,
- 'redirect_uri' => $redirect_uri,
- 'expires' => $expires,
- 'scope' => $scope,
- 'id_token' => $id_token,
- ))
- );
- } else {
- $token = array(
- 'authorization_code' => $code,
- 'client_id' => $client_id,
- 'user_id' => $user_id,
- 'redirect_uri' => $redirect_uri,
- 'expires' => $expires,
- 'scope' => $scope,
- 'id_token' => $id_token,
- );
- $this->collection('code_table')->insert($token);
- }
-
- return true;
- }
-
- public function expireAuthorizationCode($code)
- {
- $this->collection('code_table')->remove(array('authorization_code' => $code));
-
- return true;
- }
-
- /* UserCredentialsInterface */
- public function checkUserCredentials($username, $password)
- {
- if ($user = $this->getUser($username)) {
- return $this->checkPassword($user, $password);
- }
-
- return false;
- }
-
- public function getUserDetails($username)
- {
- if ($user = $this->getUser($username)) {
- $user['user_id'] = $user['username'];
- }
-
- return $user;
- }
-
- /* RefreshTokenInterface */
- public function getRefreshToken($refresh_token)
- {
- $token = $this->collection('refresh_token_table')->findOne(array('refresh_token' => $refresh_token));
-
- return is_null($token) ? false : $token;
- }
-
- public function setRefreshToken($refresh_token, $client_id, $user_id, $expires, $scope = null)
- {
- $token = array(
- 'refresh_token' => $refresh_token,
- 'client_id' => $client_id,
- 'user_id' => $user_id,
- 'expires' => $expires,
- 'scope' => $scope
- );
- $this->collection('refresh_token_table')->insert($token);
-
- return true;
- }
-
- public function unsetRefreshToken($refresh_token)
- {
- $result = $this->collection('refresh_token_table')->remove(array(
- 'refresh_token' => $refresh_token
- ), array('w' => 1));
-
- return $result['n'] > 0;
- }
-
- // plaintext passwords are bad! Override this for your application
- protected function checkPassword($user, $password)
- {
- return $user['password'] == $password;
- }
-
- public function getUser($username)
- {
- $result = $this->collection('user_table')->findOne(array('username' => $username));
-
- return is_null($result) ? false : $result;
- }
-
- public function setUser($username, $password, $firstName = null, $lastName = null)
- {
- if ($this->getUser($username)) {
- $this->collection('user_table')->update(
- array('username' => $username),
- array('$set' => array(
- 'password' => $password,
- 'first_name' => $firstName,
- 'last_name' => $lastName
- ))
- );
- } else {
- $user = array(
- 'username' => $username,
- 'password' => $password,
- 'first_name' => $firstName,
- 'last_name' => $lastName
- );
- $this->collection('user_table')->insert($user);
- }
-
- return true;
- }
-
- public function getClientKey($client_id, $subject)
- {
- $result = $this->collection('jwt_table')->findOne(array(
- 'client_id' => $client_id,
- 'subject' => $subject
- ));
-
- return is_null($result) ? false : $result['key'];
- }
-
- public function getClientScope($client_id)
- {
- if (!$clientDetails = $this->getClientDetails($client_id)) {
- return false;
- }
-
- if (isset($clientDetails['scope'])) {
- return $clientDetails['scope'];
- }
-
- return null;
- }
-
- public function getJti($client_id, $subject, $audience, $expiration, $jti)
- {
- //TODO: Needs mongodb implementation.
- throw new \Exception('getJti() for the MongoDB driver is currently unimplemented.');
- }
-
- public function setJti($client_id, $subject, $audience, $expiration, $jti)
- {
- //TODO: Needs mongodb implementation.
- throw new \Exception('setJti() for the MongoDB driver is currently unimplemented.');
- }
-}
diff --git a/library/oauth2/src/OAuth2/Storage/RefreshTokenInterface.php b/library/oauth2/src/OAuth2/Storage/RefreshTokenInterface.php
deleted file mode 100644
index 0273f2125..000000000
--- a/library/oauth2/src/OAuth2/Storage/RefreshTokenInterface.php
+++ /dev/null
@@ -1,82 +0,0 @@
-<?php
-
-namespace OAuth2\Storage;
-
-/**
- * Implement this interface to specify where the OAuth2 Server
- * should get/save refresh tokens for the "Refresh Token"
- * grant type
- *
- * @author Brent Shaffer <bshafs at gmail dot com>
- */
-interface RefreshTokenInterface
-{
- /**
- * Grant refresh access tokens.
- *
- * Retrieve the stored data for the given refresh token.
- *
- * Required for OAuth2::GRANT_TYPE_REFRESH_TOKEN.
- *
- * @param $refresh_token
- * Refresh token to be check with.
- *
- * @return
- * An associative array as below, and NULL if the refresh_token is
- * invalid:
- * - refresh_token: Refresh token identifier.
- * - client_id: Client identifier.
- * - user_id: User identifier.
- * - expires: Expiration unix timestamp, or 0 if the token doesn't expire.
- * - scope: (optional) Scope values in space-separated string.
- *
- * @see http://tools.ietf.org/html/rfc6749#section-6
- *
- * @ingroup oauth2_section_6
- */
- public function getRefreshToken($refresh_token);
-
- /**
- * Take the provided refresh token values and store them somewhere.
- *
- * This function should be the storage counterpart to getRefreshToken().
- *
- * If storage fails for some reason, we're not currently checking for
- * any sort of success/failure, so you should bail out of the script
- * and provide a descriptive fail message.
- *
- * Required for OAuth2::GRANT_TYPE_REFRESH_TOKEN.
- *
- * @param $refresh_token
- * Refresh token to be stored.
- * @param $client_id
- * Client identifier to be stored.
- * @param $user_id
- * User identifier to be stored.
- * @param $expires
- * Expiration timestamp to be stored. 0 if the token doesn't expire.
- * @param $scope
- * (optional) Scopes to be stored in space-separated string.
- *
- * @ingroup oauth2_section_6
- */
- public function setRefreshToken($refresh_token, $client_id, $user_id, $expires, $scope = null);
-
- /**
- * Expire a used refresh token.
- *
- * This is not explicitly required in the spec, but is almost implied.
- * After granting a new refresh token, the old one is no longer useful and
- * so should be forcibly expired in the data store so it can't be used again.
- *
- * If storage fails for some reason, we're not currently checking for
- * any sort of success/failure, so you should bail out of the script
- * and provide a descriptive fail message.
- *
- * @param $refresh_token
- * Refresh token to be expirse.
- *
- * @ingroup oauth2_section_6
- */
- public function unsetRefreshToken($refresh_token);
-}
diff --git a/library/oauth2/test/OAuth2/Controller/ResourceControllerTest.php b/library/oauth2/test/OAuth2/Controller/ResourceControllerTest.php
deleted file mode 100644
index ee6d96ff8..000000000
--- a/library/oauth2/test/OAuth2/Controller/ResourceControllerTest.php
+++ /dev/null
@@ -1,175 +0,0 @@
-<?php
-
-namespace OAuth2\Controller;
-
-use OAuth2\Storage\Bootstrap;
-use OAuth2\Server;
-use OAuth2\GrantType\AuthorizationCode;
-use OAuth2\Request;
-use OAuth2\Response;
-
-class ResourceControllerTest extends \PHPUnit_Framework_TestCase
-{
- public function testNoAccessToken()
- {
- $server = $this->getTestServer();
- $request = Request::createFromGlobals();
- $allow = $server->verifyResourceRequest($request, $response = new Response());
- $this->assertFalse($allow);
-
- $this->assertEquals($response->getStatusCode(), 401);
- $this->assertNull($response->getParameter('error'));
- $this->assertNull($response->getParameter('error_description'));
- }
-
- public function testMalformedHeader()
- {
- $server = $this->getTestServer();
- $request = Request::createFromGlobals();
- $request->headers['AUTHORIZATION'] = 'tH1s i5 B0gU5';
- $allow = $server->verifyResourceRequest($request, $response = new Response());
- $this->assertFalse($allow);
-
- $this->assertEquals($response->getStatusCode(), 400);
- $this->assertEquals($response->getParameter('error'), 'invalid_request');
- $this->assertEquals($response->getParameter('error_description'), 'Malformed auth header');
- }
-
- public function testMultipleTokensSubmitted()
- {
- $server = $this->getTestServer();
- $request = Request::createFromGlobals();
- $request->request['access_token'] = 'TEST';
- $request->query['access_token'] = 'TEST';
- $allow = $server->verifyResourceRequest($request, $response = new Response());
- $this->assertFalse($allow);
-
- $this->assertEquals($response->getStatusCode(), 400);
- $this->assertEquals($response->getParameter('error'), 'invalid_request');
- $this->assertEquals($response->getParameter('error_description'), 'Only one method may be used to authenticate at a time (Auth header, GET or POST)');
- }
-
- public function testInvalidRequestMethod()
- {
- $server = $this->getTestServer();
- $request = Request::createFromGlobals();
- $request->server['REQUEST_METHOD'] = 'GET';
- $request->request['access_token'] = 'TEST';
- $allow = $server->verifyResourceRequest($request, $response = new Response());
- $this->assertFalse($allow);
-
- $this->assertEquals($response->getStatusCode(), 400);
- $this->assertEquals($response->getParameter('error'), 'invalid_request');
- $this->assertEquals($response->getParameter('error_description'), 'When putting the token in the body, the method must be POST or PUT');
- }
-
- public function testInvalidContentType()
- {
- $server = $this->getTestServer();
- $request = Request::createFromGlobals();
- $request->server['REQUEST_METHOD'] = 'POST';
- $request->server['CONTENT_TYPE'] = 'application/json';
- $request->request['access_token'] = 'TEST';
- $allow = $server->verifyResourceRequest($request, $response = new Response());
- $this->assertFalse($allow);
-
- $this->assertEquals($response->getStatusCode(), 400);
- $this->assertEquals($response->getParameter('error'), 'invalid_request');
- $this->assertEquals($response->getParameter('error_description'), 'The content type for POST requests must be "application/x-www-form-urlencoded"');
- }
-
- public function testInvalidToken()
- {
- $server = $this->getTestServer();
- $request = Request::createFromGlobals();
- $request->headers['AUTHORIZATION'] = 'Bearer TESTTOKEN';
- $allow = $server->verifyResourceRequest($request, $response = new Response());
- $this->assertFalse($allow);
-
- $this->assertEquals($response->getStatusCode(), 401);
- $this->assertEquals($response->getParameter('error'), 'invalid_token');
- $this->assertEquals($response->getParameter('error_description'), 'The access token provided is invalid');
- }
-
- public function testExpiredToken()
- {
- $server = $this->getTestServer();
- $request = Request::createFromGlobals();
- $request->headers['AUTHORIZATION'] = 'Bearer accesstoken-expired';
- $allow = $server->verifyResourceRequest($request, $response = new Response());
- $this->assertFalse($allow);
-
- $this->assertEquals($response->getStatusCode(), 401);
- $this->assertEquals($response->getParameter('error'), 'expired_token');
- $this->assertEquals($response->getParameter('error_description'), 'The access token provided has expired');
- }
-
- public function testOutOfScopeToken()
- {
- $server = $this->getTestServer();
- $request = Request::createFromGlobals();
- $request->headers['AUTHORIZATION'] = 'Bearer accesstoken-scope';
- $scope = 'outofscope';
- $allow = $server->verifyResourceRequest($request, $response = new Response(), $scope);
- $this->assertFalse($allow);
-
- $this->assertEquals($response->getStatusCode(), 403);
- $this->assertEquals($response->getParameter('error'), 'insufficient_scope');
- $this->assertEquals($response->getParameter('error_description'), 'The request requires higher privileges than provided by the access token');
-
- // verify the "scope" has been set in the "WWW-Authenticate" header
- preg_match('/scope="(.*?)"/', $response->getHttpHeader('WWW-Authenticate'), $matches);
- $this->assertEquals(2, count($matches));
- $this->assertEquals($matches[1], 'outofscope');
- }
-
- public function testMalformedToken()
- {
- $server = $this->getTestServer();
- $request = Request::createFromGlobals();
- $request->headers['AUTHORIZATION'] = 'Bearer accesstoken-malformed';
- $allow = $server->verifyResourceRequest($request, $response = new Response());
- $this->assertFalse($allow);
-
- $this->assertEquals($response->getStatusCode(), 401);
- $this->assertEquals($response->getParameter('error'), 'malformed_token');
- $this->assertEquals($response->getParameter('error_description'), 'Malformed token (missing "expires")');
- }
-
- public function testValidToken()
- {
- $server = $this->getTestServer();
- $request = Request::createFromGlobals();
- $request->headers['AUTHORIZATION'] = 'Bearer accesstoken-scope';
- $allow = $server->verifyResourceRequest($request, $response = new Response());
- $this->assertTrue($allow);
- }
-
- public function testValidTokenWithScopeParam()
- {
- $server = $this->getTestServer();
- $request = Request::createFromGlobals();
- $request->headers['AUTHORIZATION'] = 'Bearer accesstoken-scope';
- $request->query['scope'] = 'testscope';
- $allow = $server->verifyResourceRequest($request, $response = new Response());
- $this->assertTrue($allow);
- }
-
- public function testCreateController()
- {
- $storage = Bootstrap::getInstance()->getMemoryStorage();
- $tokenType = new \OAuth2\TokenType\Bearer();
- $controller = new ResourceController($tokenType, $storage);
- }
-
- private function getTestServer($config = array())
- {
- $storage = Bootstrap::getInstance()->getMemoryStorage();
- $server = new Server($storage, $config);
-
- // Add the two types supported for authorization grant
- $server->addGrantType(new AuthorizationCode($storage));
-
- return $server;
- }
-}
diff --git a/library/oauth2/test/OAuth2/GrantType/AuthorizationCodeTest.php b/library/oauth2/test/OAuth2/GrantType/AuthorizationCodeTest.php
deleted file mode 100644
index 740989635..000000000
--- a/library/oauth2/test/OAuth2/GrantType/AuthorizationCodeTest.php
+++ /dev/null
@@ -1,207 +0,0 @@
-<?php
-
-namespace OAuth2\GrantType;
-
-use OAuth2\Storage\Bootstrap;
-use OAuth2\Server;
-use OAuth2\Request\TestRequest;
-use OAuth2\Response;
-
-class AuthorizationCodeTest extends \PHPUnit_Framework_TestCase
-{
- public function testNoCode()
- {
- $server = $this->getTestServer();
- $request = TestRequest::createPost(array(
- 'grant_type' => 'authorization_code', // valid grant type
- 'client_id' => 'Test Client ID', // valid client id
- 'client_secret' => 'TestSecret', // valid client secret
- ));
- $server->handleTokenRequest($request, $response = new Response());
-
- $this->assertEquals($response->getStatusCode(), 400);
- $this->assertEquals($response->getParameter('error'), 'invalid_request');
- $this->assertEquals($response->getParameter('error_description'), 'Missing parameter: "code" is required');
- }
-
- public function testInvalidCode()
- {
- $server = $this->getTestServer();
- $request = TestRequest::createPost(array(
- 'grant_type' => 'authorization_code', // valid grant type
- 'client_id' => 'Test Client ID', // valid client id
- 'client_secret' => 'TestSecret', // valid client secret
- 'code' => 'InvalidCode', // invalid authorization code
- ));
- $server->handleTokenRequest($request, $response = new Response());
-
- $this->assertEquals($response->getStatusCode(), 400);
- $this->assertEquals($response->getParameter('error'), 'invalid_grant');
- $this->assertEquals($response->getParameter('error_description'), 'Authorization code doesn\'t exist or is invalid for the client');
- }
-
- public function testCodeCannotBeUsedTwice()
- {
- $server = $this->getTestServer();
- $request = TestRequest::createPost(array(
- 'grant_type' => 'authorization_code', // valid grant type
- 'client_id' => 'Test Client ID', // valid client id
- 'client_secret' => 'TestSecret', // valid client secret
- 'code' => 'testcode', // valid code
- ));
- $server->handleTokenRequest($request, $response = new Response());
-
- $this->assertEquals($response->getStatusCode(), 200);
- $this->assertNotNull($response->getParameter('access_token'));
-
- // try to use the same code again
- $server->handleTokenRequest($request, $response = new Response());
-
- $this->assertEquals($response->getStatusCode(), 400);
- $this->assertEquals($response->getParameter('error'), 'invalid_grant');
- $this->assertEquals($response->getParameter('error_description'), 'Authorization code doesn\'t exist or is invalid for the client');
- }
-
- public function testExpiredCode()
- {
- $server = $this->getTestServer();
- $request = TestRequest::createPost(array(
- 'grant_type' => 'authorization_code', // valid grant type
- 'client_id' => 'Test Client ID', // valid client id
- 'client_secret' => 'TestSecret', // valid client secret
- 'code' => 'testcode-expired', // expired authorization code
- ));
- $server->handleTokenRequest($request, $response = new Response());
-
- $this->assertEquals($response->getStatusCode(), 400);
- $this->assertEquals($response->getParameter('error'), 'invalid_grant');
- $this->assertEquals($response->getParameter('error_description'), 'The authorization code has expired');
- }
-
- public function testValidCode()
- {
- $server = $this->getTestServer();
- $request = TestRequest::createPost(array(
- 'grant_type' => 'authorization_code', // valid grant type
- 'client_id' => 'Test Client ID', // valid client id
- 'client_secret' => 'TestSecret', // valid client secret
- 'code' => 'testcode', // valid code
- ));
- $token = $server->grantAccessToken($request, new Response());
-
- $this->assertNotNull($token);
- $this->assertArrayHasKey('access_token', $token);
- }
-
- public function testValidCodeNoScope()
- {
- $server = $this->getTestServer();
- $request = TestRequest::createPost(array(
- 'grant_type' => 'authorization_code', // valid grant type
- 'client_id' => 'Test Client ID', // valid client id
- 'client_secret' => 'TestSecret', // valid client secret
- 'code' => 'testcode-with-scope', // valid code
- ));
- $token = $server->grantAccessToken($request, new Response());
-
- $this->assertNotNull($token);
- $this->assertArrayHasKey('access_token', $token);
- $this->assertArrayHasKey('scope', $token);
- $this->assertEquals($token['scope'], 'scope1 scope2');
- }
-
- public function testValidCodeSameScope()
- {
- $server = $this->getTestServer();
- $request = TestRequest::createPost(array(
- 'grant_type' => 'authorization_code', // valid grant type
- 'client_id' => 'Test Client ID', // valid client id
- 'client_secret' => 'TestSecret', // valid client secret
- 'code' => 'testcode-with-scope', // valid code
- 'scope' => 'scope2 scope1',
- ));
- $token = $server->grantAccessToken($request, new Response());
-
- $this->assertNotNull($token);
- $this->assertArrayHasKey('access_token', $token);
- $this->assertArrayHasKey('scope', $token);
- $this->assertEquals($token['scope'], 'scope2 scope1');
- }
-
- public function testValidCodeLessScope()
- {
- $server = $this->getTestServer();
- $request = TestRequest::createPost(array(
- 'grant_type' => 'authorization_code', // valid grant type
- 'client_id' => 'Test Client ID', // valid client id
- 'client_secret' => 'TestSecret', // valid client secret
- 'code' => 'testcode-with-scope', // valid code
- 'scope' => 'scope1',
- ));
- $token = $server->grantAccessToken($request, new Response());
-
- $this->assertNotNull($token);
- $this->assertArrayHasKey('access_token', $token);
- $this->assertArrayHasKey('scope', $token);
- $this->assertEquals($token['scope'], 'scope1');
- }
-
- public function testValidCodeDifferentScope()
- {
- $server = $this->getTestServer();
- $request = TestRequest::createPost(array(
- 'grant_type' => 'authorization_code', // valid grant type
- 'client_id' => 'Test Client ID', // valid client id
- 'client_secret' => 'TestSecret', // valid client secret
- 'code' => 'testcode-with-scope', // valid code
- 'scope' => 'scope3',
- ));
- $token = $server->grantAccessToken($request, $response = new Response());
-
- $this->assertEquals($response->getStatusCode(), 400);
- $this->assertEquals($response->getParameter('error'), 'invalid_scope');
- $this->assertEquals($response->getParameter('error_description'), 'The scope requested is invalid for this request');
- }
-
- public function testValidCodeInvalidScope()
- {
- $server = $this->getTestServer();
- $request = TestRequest::createPost(array(
- 'grant_type' => 'authorization_code', // valid grant type
- 'client_id' => 'Test Client ID', // valid client id
- 'client_secret' => 'TestSecret', // valid client secret
- 'code' => 'testcode-with-scope', // valid code
- 'scope' => 'invalid-scope',
- ));
- $token = $server->grantAccessToken($request, $response = new Response());
-
- $this->assertEquals($response->getStatusCode(), 400);
- $this->assertEquals($response->getParameter('error'), 'invalid_scope');
- $this->assertEquals($response->getParameter('error_description'), 'The scope requested is invalid for this request');
- }
-
- public function testValidClientDifferentCode()
- {
- $server = $this->getTestServer();
- $request = TestRequest::createPost(array(
- 'grant_type' => 'authorization_code', // valid grant type
- 'client_id' => 'Test Some Other Client', // valid client id
- 'client_secret' => 'TestSecret3', // valid client secret
- 'code' => 'testcode', // valid code
- ));
- $token = $server->grantAccessToken($request, $response = new Response());
-
- $this->assertEquals($response->getStatusCode(), 400);
- $this->assertEquals($response->getParameter('error'), 'invalid_grant');
- $this->assertEquals($response->getParameter('error_description'), 'authorization_code doesn\'t exist or is invalid for the client');
- }
-
- private function getTestServer()
- {
- $storage = Bootstrap::getInstance()->getMemoryStorage();
- $server = new Server($storage);
- $server->addGrantType(new AuthorizationCode($storage));
-
- return $server;
- }
-}
diff --git a/library/oauth2/test/config/storage.json b/library/oauth2/test/config/storage.json
deleted file mode 100644
index a31d3bca2..000000000
--- a/library/oauth2/test/config/storage.json
+++ /dev/null
@@ -1,181 +0,0 @@
-{
- "authorization_codes": {
- "testcode": {
- "client_id": "Test Client ID",
- "user_id": "",
- "redirect_uri": "",
- "expires": "9999999999",
- "id_token": "IDTOKEN"
- },
- "testcode-with-scope": {
- "client_id": "Test Client ID",
- "user_id": "",
- "redirect_uri": "",
- "expires": "9999999999",
- "scope": "scope1 scope2"
- },
- "testcode-expired": {
- "client_id": "Test Client ID",
- "user_id": "",
- "redirect_uri": "",
- "expires": "1356998400"
- },
- "testcode-empty-secret": {
- "client_id": "Test Client ID Empty Secret",
- "user_id": "",
- "redirect_uri": "",
- "expires": "9999999999"
- },
- "testcode-openid": {
- "client_id": "Test Client ID",
- "user_id": "",
- "redirect_uri": "",
- "expires": "9999999999",
- "id_token": "test_id_token"
- }
- },
- "client_credentials" : {
- "Test Client ID": {
- "client_secret": "TestSecret"
- },
- "Test Client ID with Redirect Uri": {
- "client_secret": "TestSecret2",
- "redirect_uri": "http://brentertainment.com"
- },
- "Test Client ID with Buggy Redirect Uri": {
- "client_secret": "TestSecret2",
- "redirect_uri": " http://brentertainment.com"
- },
- "Test Client ID with Multiple Redirect Uris": {
- "client_secret": "TestSecret3",
- "redirect_uri": "http://brentertainment.com http://morehazards.com"
- },
- "Test Client ID with Redirect Uri Parts": {
- "client_secret": "TestSecret4",
- "redirect_uri": "http://user:pass@brentertainment.com:2222/authorize/cb?auth_type=oauth&test=true"
- },
- "Test Some Other Client": {
- "client_secret": "TestSecret3"
- },
- "Test Client ID Empty Secret": {
- "client_secret": ""
- },
- "Test Client ID For Password Grant": {
- "grant_types": "password",
- "client_secret": ""
- },
- "Client ID With User ID": {
- "client_secret": "TestSecret",
- "user_id": "brent@brentertainment.com"
- },
- "oauth_test_client": {
- "client_secret": "testpass",
- "grant_types": "implicit password"
- }
- },
- "user_credentials" : {
- "test-username": {
- "password": "testpass"
- },
- "testusername": {
- "password": "testpass"
- },
- "testuser": {
- "password": "password",
- "email": "testuser@test.com",
- "email_verified": true
- },
- "johndoe": {
- "password": "password"
- }
- },
- "refresh_tokens" : {
- "test-refreshtoken": {
- "refresh_token": "test-refreshtoken",
- "client_id": "Test Client ID",
- "user_id": "test-username",
- "expires": 0,
- "scope": null
- },
- "test-refreshtoken-with-scope": {
- "refresh_token": "test-refreshtoken",
- "client_id": "Test Client ID",
- "user_id": "test-username",
- "expires": 0,
- "scope": "scope1 scope2"
- }
- },
- "access_tokens" : {
- "accesstoken-expired": {
- "access_token": "accesstoken-expired",
- "client_id": "Test Client ID",
- "expires": 1234567,
- "scope": null
- },
- "accesstoken-scope": {
- "access_token": "accesstoken-scope",
- "client_id": "Test Client ID",
- "expires": 99999999900,
- "scope": "testscope"
- },
- "accesstoken-openid-connect": {
- "access_token": "accesstoken-openid-connect",
- "client_id": "Test Client ID",
- "user_id": "testuser",
- "expires": 99999999900,
- "scope": "openid email"
- },
- "accesstoken-malformed": {
- "access_token": "accesstoken-mallformed",
- "expires": 99999999900,
- "scope": "testscope"
- }
- },
- "jwt": {
- "Test Client ID": {
- "key": "-----BEGIN PUBLIC KEY-----\nMIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQC5/SxVlE8gnpFqCxgl2wjhzY7u\ncEi00s0kUg3xp7lVEvgLgYcAnHiWp+gtSjOFfH2zsvpiWm6Lz5f743j/FEzHIO1o\nwR0p4d9pOaJK07d01+RzoQLOIQAgXrr4T1CCWUesncwwPBVCyy2Mw3Nmhmr9MrF8\nUlvdRKBxriRnlP3qJQIDAQAB\n-----END PUBLIC KEY-----",
- "subject": "testuser@ourdomain.com"
- },
- "Test Client ID PHP-5.2": {
- "key": "mysecretkey",
- "subject": "testuser@ourdomain.com"
- },
- "Missing Key Client": {
- "key": null,
- "subject": "testuser@ourdomain.com"
- },
- "Missing Key Client PHP-5.2": {
- "key": null,
- "subject": "testuser@ourdomain.com"
- },
- "oauth_test_client": {
- "key": "-----BEGIN CERTIFICATE-----\nMIICiDCCAfGgAwIBAgIBADANBgkqhkiG9w0BAQQFADA9MQswCQYDVQQGEwJVUzEL\nMAkGA1UECBMCVVQxITAfBgNVBAoTGFZpZ25ldHRlIENvcnBvcmF0aW9uIFNCWDAe\nFw0xMTEwMTUwMzE4MjdaFw0zMTEwMTAwMzE4MjdaMD0xCzAJBgNVBAYTAlVTMQsw\nCQYDVQQIEwJVVDEhMB8GA1UEChMYVmlnbmV0dGUgQ29ycG9yYXRpb24gU0JYMIGf\nMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQC8fpi06NfVYHAOAnxNMVnTXr/ptsLs\nNjP+uAt2eO0cc5J9H5XV8lFVujOrRu/JWi1TDmAvOaf/6A3BphIA1Pwp0AAqlZdw\nizIum8j0KzpsGYH5qReNQDwF3oUSKMsQCCGCDHrDYifG/pRi9bN1ZVjEXPr35HJu\nBe+FQpZTs8DewwIDAQABo4GXMIGUMB0GA1UdDgQWBBRe8hrEXm+Yim4YlD5Nx+1K\nvCYs9DBlBgNVHSMEXjBcgBRe8hrEXm+Yim4YlD5Nx+1KvCYs9KFBpD8wPTELMAkG\nA1UEBhMCVVMxCzAJBgNVBAgTAlVUMSEwHwYDVQQKExhWaWduZXR0ZSBDb3Jwb3Jh\ndGlvbiBTQliCAQAwDAYDVR0TBAUwAwEB/zANBgkqhkiG9w0BAQQFAAOBgQBjhyRD\nlM7vnLn6drgQVftW5V9nDFAyPAuiGvMIKFSbiAf1PxXCRn5sfJquwWKsJUi4ZGNl\naViXdFmN6/F13PSM+yg63tpKy0fYqMbTM+Oe5WuSHkSW1VuYNHV+24adgNk/FRDL\nFRrlM1f6s9VTLWvwGItjfrof0Ba8Uq7ZDSb9Xg==\n-----END CERTIFICATE-----",
- "subject": "test_subject"
- }
- },
- "jti": [
- {
- "issuer": "Test Client ID",
- "subject": "testuser@ourdomain.com",
- "audience": "http://myapp.com/oauth/auth",
- "expires": 99999999900,
- "jti": "used_jti"
- }
- ],
- "supported_scopes" : [
- "scope1",
- "scope2",
- "scope3",
- "clientscope1",
- "clientscope2",
- "clientscope3",
- "supportedscope1",
- "supportedscope2",
- "supportedscope3",
- "supportedscope4"
- ],
- "keys": {
- "public_key": "-----BEGIN CERTIFICATE-----\nMIICiDCCAfGgAwIBAgIBADANBgkqhkiG9w0BAQQFADA9MQswCQYDVQQGEwJVUzEL\nMAkGA1UECBMCVVQxITAfBgNVBAoTGFZpZ25ldHRlIENvcnBvcmF0aW9uIFNCWDAe\nFw0xMTEwMTUwMzE4MjdaFw0zMTEwMTAwMzE4MjdaMD0xCzAJBgNVBAYTAlVTMQsw\nCQYDVQQIEwJVVDEhMB8GA1UEChMYVmlnbmV0dGUgQ29ycG9yYXRpb24gU0JYMIGf\nMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQC8fpi06NfVYHAOAnxNMVnTXr/ptsLs\nNjP+uAt2eO0cc5J9H5XV8lFVujOrRu/JWi1TDmAvOaf/6A3BphIA1Pwp0AAqlZdw\nizIum8j0KzpsGYH5qReNQDwF3oUSKMsQCCGCDHrDYifG/pRi9bN1ZVjEXPr35HJu\nBe+FQpZTs8DewwIDAQABo4GXMIGUMB0GA1UdDgQWBBRe8hrEXm+Yim4YlD5Nx+1K\nvCYs9DBlBgNVHSMEXjBcgBRe8hrEXm+Yim4YlD5Nx+1KvCYs9KFBpD8wPTELMAkG\nA1UEBhMCVVMxCzAJBgNVBAgTAlVUMSEwHwYDVQQKExhWaWduZXR0ZSBDb3Jwb3Jh\ndGlvbiBTQliCAQAwDAYDVR0TBAUwAwEB/zANBgkqhkiG9w0BAQQFAAOBgQBjhyRD\nlM7vnLn6drgQVftW5V9nDFAyPAuiGvMIKFSbiAf1PxXCRn5sfJquwWKsJUi4ZGNl\naViXdFmN6/F13PSM+yg63tpKy0fYqMbTM+Oe5WuSHkSW1VuYNHV+24adgNk/FRDL\nFRrlM1f6s9VTLWvwGItjfrof0Ba8Uq7ZDSb9Xg==\n-----END CERTIFICATE-----",
- "private_key": "-----BEGIN RSA PRIVATE KEY-----\nMIICXQIBAAKBgQC8fpi06NfVYHAOAnxNMVnTXr/ptsLsNjP+uAt2eO0cc5J9H5XV\n8lFVujOrRu/JWi1TDmAvOaf/6A3BphIA1Pwp0AAqlZdwizIum8j0KzpsGYH5qReN\nQDwF3oUSKMsQCCGCDHrDYifG/pRi9bN1ZVjEXPr35HJuBe+FQpZTs8DewwIDAQAB\nAoGARfNxNknmtx/n1bskZ/01iZRzAge6BLEE0LV6Q4gS7mkRZu/Oyiv39Sl5vUlA\n+WdGxLjkBwKNjxGN8Vxw9/ASd8rSsqeAUYIwAeifXrHhj5DBPQT/pDPkeFnp9B1w\nC6jo+3AbBQ4/b0ONSIEnCL2xGGglSIAxO17T1ViXp7lzXPECQQDe63nkRdWM0OCb\noaHQPT3E26224maIstrGFUdt9yw3yJf4bOF7TtiPLlLuHsTTge3z+fG6ntC0xG56\n1cl37C3ZAkEA2HdVcRGugNp/qmVz4LJTpD+WZKi73PLAO47wDOrYh9Pn2I6fcEH0\nCPnggt1ko4ujvGzFTvRH64HXa6aPCv1j+wJBAMQMah3VQPNf/DlDVFEUmw9XeBZg\nVHaifX851aEjgXLp6qVj9IYCmLiLsAmVa9rr6P7p8asD418nZlaHUHE0eDkCQQCr\nuxis6GMx1Ka971jcJX2X696LoxXPd0KsvXySMupv79yagKPa8mgBiwPjrnK+EPVo\ncj6iochA/bSCshP/mwFrAkBHEKPi6V6gb94JinCT7x3weahbdp6bJ6/nzBH/p9VA\nHoT1JtwNFhGv9BCjmDydshQHfSWpY9NxlccBKL7ITm8R\n-----END RSA PRIVATE KEY-----"
- }
-}
diff --git a/library/oauth2/test/lib/OAuth2/Storage/BaseTest.php b/library/oauth2/test/lib/OAuth2/Storage/BaseTest.php
deleted file mode 100755
index 921d52500..000000000
--- a/library/oauth2/test/lib/OAuth2/Storage/BaseTest.php
+++ /dev/null
@@ -1,34 +0,0 @@
-<?php
-
-namespace OAuth2\Storage;
-
-abstract class BaseTest extends \PHPUnit_Framework_TestCase
-{
- public function provideStorage()
- {
- $memory = Bootstrap::getInstance()->getMemoryStorage();
- $sqlite = Bootstrap::getInstance()->getSqlitePdo();
- $mysql = Bootstrap::getInstance()->getMysqlPdo();
- $postgres = Bootstrap::getInstance()->getPostgresPdo();
- $mongo = Bootstrap::getInstance()->getMongo();
- $redis = Bootstrap::getInstance()->getRedisStorage();
- $cassandra = Bootstrap::getInstance()->getCassandraStorage();
- $dynamodb = Bootstrap::getInstance()->getDynamoDbStorage();
- $couchbase = Bootstrap::getInstance()->getCouchbase();
-
- /* hack until we can fix "default_scope" dependencies in other tests */
- $memory->defaultScope = 'defaultscope1 defaultscope2';
-
- return array(
- array($memory),
- array($sqlite),
- array($mysql),
- array($postgres),
- array($mongo),
- array($redis),
- array($cassandra),
- array($dynamodb),
- array($couchbase),
- );
- }
-}
diff --git a/library/oauth2/test/lib/OAuth2/Storage/Bootstrap.php b/library/oauth2/test/lib/OAuth2/Storage/Bootstrap.php
deleted file mode 100755
index 4ac9022b1..000000000
--- a/library/oauth2/test/lib/OAuth2/Storage/Bootstrap.php
+++ /dev/null
@@ -1,888 +0,0 @@
-<?php
-
-namespace OAuth2\Storage;
-
-class Bootstrap
-{
- const DYNAMODB_PHP_VERSION = 'none';
-
- protected static $instance;
- private $mysql;
- private $sqlite;
- private $postgres;
- private $mongo;
- private $redis;
- private $cassandra;
- private $configDir;
- private $dynamodb;
- private $couchbase;
-
- public function __construct()
- {
- $this->configDir = __DIR__.'/../../../config';
- }
-
- public static function getInstance()
- {
- if (!self::$instance) {
- self::$instance = new self();
- }
-
- return self::$instance;
- }
-
- public function getSqlitePdo()
- {
- if (!$this->sqlite) {
- $this->removeSqliteDb();
- $pdo = new \PDO(sprintf('sqlite://%s', $this->getSqliteDir()));
- $pdo->setAttribute(\PDO::ATTR_ERRMODE, \PDO::ERRMODE_EXCEPTION);
- $this->createSqliteDb($pdo);
-
- $this->sqlite = new Pdo($pdo);
- }
-
- return $this->sqlite;
- }
-
- public function getPostgresPdo()
- {
- if (!$this->postgres) {
- if (in_array('pgsql', \PDO::getAvailableDrivers())) {
- $this->removePostgresDb();
- $this->createPostgresDb();
- if ($pdo = $this->getPostgresDriver()) {
- $pdo->setAttribute(\PDO::ATTR_ERRMODE, \PDO::ERRMODE_EXCEPTION);
- $this->populatePostgresDb($pdo);
- $this->postgres = new Pdo($pdo);
- }
- } else {
- $this->postgres = new NullStorage('Postgres', 'Missing postgres PDO extension.');
- }
- }
-
- return $this->postgres;
- }
-
- public function getPostgresDriver()
- {
- try {
- $pdo = new \PDO('pgsql:host=localhost;dbname=oauth2_server_php', 'postgres');
-
- return $pdo;
- } catch (\PDOException $e) {
- $this->postgres = new NullStorage('Postgres', $e->getMessage());
- }
- }
-
- public function getMemoryStorage()
- {
- return new Memory(json_decode(file_get_contents($this->configDir. '/storage.json'), true));
- }
-
- public function getRedisStorage()
- {
- if (!$this->redis) {
- if (class_exists('Predis\Client')) {
- $redis = new \Predis\Client();
- if ($this->testRedisConnection($redis)) {
- $redis->flushdb();
- $this->redis = new Redis($redis);
- $this->createRedisDb($this->redis);
- } else {
- $this->redis = new NullStorage('Redis', 'Unable to connect to redis server on port 6379');
- }
- } else {
- $this->redis = new NullStorage('Redis', 'Missing redis library. Please run "composer.phar require predis/predis:dev-master"');
- }
- }
-
- return $this->redis;
- }
-
- private function testRedisConnection(\Predis\Client $redis)
- {
- try {
- $redis->connect();
- } catch (\Predis\CommunicationException $exception) {
- // we were unable to connect to the redis server
- return false;
- }
-
- return true;
- }
-
- public function getMysqlPdo()
- {
- if (!$this->mysql) {
- $pdo = null;
- try {
- $pdo = new \PDO('mysql:host=localhost;', 'root');
- } catch (\PDOException $e) {
- $this->mysql = new NullStorage('MySQL', 'Unable to connect to MySQL on root@localhost');
- }
-
- if ($pdo) {
- $pdo->setAttribute(\PDO::ATTR_ERRMODE, \PDO::ERRMODE_EXCEPTION);
- $this->removeMysqlDb($pdo);
- $this->createMysqlDb($pdo);
-
- $this->mysql = new Pdo($pdo);
- }
- }
-
- return $this->mysql;
- }
-
- public function getMongo()
- {
- if (!$this->mongo) {
- $skipMongo = $this->getEnvVar('SKIP_MONGO_TESTS');
- if (!$skipMongo && class_exists('MongoClient')) {
- $mongo = new \MongoClient('mongodb://localhost:27017', array('connect' => false));
- if ($this->testMongoConnection($mongo)) {
- $db = $mongo->oauth2_server_php;
- $this->removeMongoDb($db);
- $this->createMongoDb($db);
-
- $this->mongo = new Mongo($db);
- } else {
- $this->mongo = new NullStorage('Mongo', 'Unable to connect to mongo server on "localhost:27017"');
- }
- } else {
- $this->mongo = new NullStorage('Mongo', 'Missing mongo php extension. Please install mongo.so');
- }
- }
-
- return $this->mongo;
- }
-
- private function testMongoConnection(\MongoClient $mongo)
- {
- try {
- $mongo->connect();
- } catch (\MongoConnectionException $e) {
- return false;
- }
-
- return true;
- }
-
- public function getCouchbase()
- {
- if (!$this->couchbase) {
- if ($this->getEnvVar('SKIP_COUCHBASE_TESTS')) {
- $this->couchbase = new NullStorage('Couchbase', 'Skipping Couchbase tests');
- } elseif (!class_exists('Couchbase')) {
- $this->couchbase = new NullStorage('Couchbase', 'Missing Couchbase php extension. Please install couchbase.so');
- } else {
- // round-about way to make sure couchbase is working
- // this is required because it throws a "floating point exception" otherwise
- $code = "new \Couchbase(array('localhost:8091'), '', '', 'auth', false);";
- $exec = sprintf('php -r "%s"', $code);
- $ret = exec($exec, $test, $var);
- if ($ret != 0) {
- $couchbase = new \Couchbase(array('localhost:8091'), '', '', 'auth', false);
- if ($this->testCouchbaseConnection($couchbase)) {
- $this->clearCouchbase($couchbase);
- $this->createCouchbaseDB($couchbase);
-
- $this->couchbase = new CouchbaseDB($couchbase);
- } else {
- $this->couchbase = new NullStorage('Couchbase', 'Unable to connect to Couchbase server on "localhost:8091"');
- }
- } else {
- $this->couchbase = new NullStorage('Couchbase', 'Error while trying to connect to Couchbase');
- }
- }
- }
-
- return $this->couchbase;
- }
-
- private function testCouchbaseConnection(\Couchbase $couchbase)
- {
- try {
- if (count($couchbase->getServers()) > 0) {
- return true;
- }
- } catch (\CouchbaseException $e) {
- return false;
- }
-
- return true;
- }
-
- public function getCassandraStorage()
- {
- if (!$this->cassandra) {
- if (class_exists('phpcassa\ColumnFamily')) {
- $cassandra = new \phpcassa\Connection\ConnectionPool('oauth2_test', array('127.0.0.1:9160'));
- if ($this->testCassandraConnection($cassandra)) {
- $this->removeCassandraDb();
- $this->cassandra = new Cassandra($cassandra);
- $this->createCassandraDb($this->cassandra);
- } else {
- $this->cassandra = new NullStorage('Cassandra', 'Unable to connect to cassandra server on "127.0.0.1:9160"');
- }
- } else {
- $this->cassandra = new NullStorage('Cassandra', 'Missing cassandra library. Please run "composer.phar require thobbs/phpcassa:dev-master"');
- }
- }
-
- return $this->cassandra;
- }
-
- private function testCassandraConnection(\phpcassa\Connection\ConnectionPool $cassandra)
- {
- try {
- new \phpcassa\SystemManager('localhost:9160');
- } catch (\Exception $e) {
- return false;
- }
-
- return true;
- }
-
- private function removeCassandraDb()
- {
- $sys = new \phpcassa\SystemManager('localhost:9160');
-
- try {
- $sys->drop_keyspace('oauth2_test');
- } catch (\cassandra\InvalidRequestException $e) {
-
- }
- }
-
- private function createCassandraDb(Cassandra $storage)
- {
- // create the cassandra keyspace and column family
- $sys = new \phpcassa\SystemManager('localhost:9160');
-
- $sys->create_keyspace('oauth2_test', array(
- "strategy_class" => \phpcassa\Schema\StrategyClass::SIMPLE_STRATEGY,
- "strategy_options" => array('replication_factor' => '1')
- ));
-
- $sys->create_column_family('oauth2_test', 'auth');
- $cassandra = new \phpcassa\Connection\ConnectionPool('oauth2_test', array('127.0.0.1:9160'));
- $cf = new \phpcassa\ColumnFamily($cassandra, 'auth');
-
- // populate the data
- $storage->setClientDetails("oauth_test_client", "testpass", "http://example.com", 'implicit password');
- $storage->setAccessToken("testtoken", "Some Client", '', time() + 1000);
- $storage->setAuthorizationCode("testcode", "Some Client", '', '', time() + 1000);
-
- $storage->setScope('supportedscope1 supportedscope2 supportedscope3 supportedscope4');
- $storage->setScope('defaultscope1 defaultscope2', null, 'default');
-
- $storage->setScope('clientscope1 clientscope2', 'Test Client ID');
- $storage->setScope('clientscope1 clientscope2', 'Test Client ID', 'default');
-
- $storage->setScope('clientscope1 clientscope2 clientscope3', 'Test Client ID 2');
- $storage->setScope('clientscope1 clientscope2', 'Test Client ID 2', 'default');
-
- $storage->setScope('clientscope1 clientscope2', 'Test Default Scope Client ID');
- $storage->setScope('clientscope1 clientscope2', 'Test Default Scope Client ID', 'default');
-
- $storage->setScope('clientscope1 clientscope2 clientscope3', 'Test Default Scope Client ID 2');
- $storage->setScope('clientscope3', 'Test Default Scope Client ID 2', 'default');
-
- $storage->setClientKey('oauth_test_client', $this->getTestPublicKey(), 'test_subject');
-
- $cf->insert("oauth_public_keys:ClientID_One", array('__data' => json_encode(array("public_key" => "client_1_public", "private_key" => "client_1_private", "encryption_algorithm" => "RS256"))));
- $cf->insert("oauth_public_keys:ClientID_Two", array('__data' => json_encode(array("public_key" => "client_2_public", "private_key" => "client_2_private", "encryption_algorithm" => "RS256"))));
- $cf->insert("oauth_public_keys:", array('__data' => json_encode(array("public_key" => $this->getTestPublicKey(), "private_key" => $this->getTestPrivateKey(), "encryption_algorithm" => "RS256"))));
-
- $cf->insert("oauth_users:testuser", array('__data' =>json_encode(array("password" => "password", "email" => "testuser@test.com", "email_verified" => true))));
-
- }
-
- private function createSqliteDb(\PDO $pdo)
- {
- $this->runPdoSql($pdo);
- }
-
- private function removeSqliteDb()
- {
- if (file_exists($this->getSqliteDir())) {
- unlink($this->getSqliteDir());
- }
- }
-
- private function createMysqlDb(\PDO $pdo)
- {
- $pdo->exec('CREATE DATABASE oauth2_server_php');
- $pdo->exec('USE oauth2_server_php');
- $this->runPdoSql($pdo);
- }
-
- private function removeMysqlDb(\PDO $pdo)
- {
- $pdo->exec('DROP DATABASE IF EXISTS oauth2_server_php');
- }
-
- private function createPostgresDb()
- {
- if (!`psql postgres -tAc "SELECT 1 FROM pg_roles WHERE rolname='postgres'"`) {
- `createuser -s -r postgres`;
- }
-
- `createdb -O postgres oauth2_server_php`;
- }
-
- private function populatePostgresDb(\PDO $pdo)
- {
- $this->runPdoSql($pdo);
- }
-
- private function removePostgresDb()
- {
- if (trim(`psql -l | grep oauth2_server_php | wc -l`)) {
- `dropdb oauth2_server_php`;
- }
- }
-
- public function runPdoSql(\PDO $pdo)
- {
- $storage = new Pdo($pdo);
- foreach (explode(';', $storage->getBuildSql()) as $statement) {
- $result = $pdo->exec($statement);
- }
-
- // set up scopes
- $sql = 'INSERT INTO oauth_scopes (scope) VALUES (?)';
- foreach (explode(' ', 'supportedscope1 supportedscope2 supportedscope3 supportedscope4 clientscope1 clientscope2 clientscope3') as $supportedScope) {
- $pdo->prepare($sql)->execute(array($supportedScope));
- }
-
- $sql = 'INSERT INTO oauth_scopes (scope, is_default) VALUES (?, ?)';
- foreach (array('defaultscope1', 'defaultscope2') as $defaultScope) {
- $pdo->prepare($sql)->execute(array($defaultScope, true));
- }
-
- // set up clients
- $sql = 'INSERT INTO oauth_clients (client_id, client_secret, scope, grant_types) VALUES (?, ?, ?, ?)';
- $pdo->prepare($sql)->execute(array('Test Client ID', 'TestSecret', 'clientscope1 clientscope2', null));
- $pdo->prepare($sql)->execute(array('Test Client ID 2', 'TestSecret', 'clientscope1 clientscope2 clientscope3', null));
- $pdo->prepare($sql)->execute(array('Test Default Scope Client ID', 'TestSecret', 'clientscope1 clientscope2', null));
- $pdo->prepare($sql)->execute(array('oauth_test_client', 'testpass', null, 'implicit password'));
-
- // set up misc
- $sql = 'INSERT INTO oauth_access_tokens (access_token, client_id, expires, user_id) VALUES (?, ?, ?, ?)';
- $pdo->prepare($sql)->execute(array('testtoken', 'Some Client', date('Y-m-d H:i:s', strtotime('+1 hour')), null));
- $pdo->prepare($sql)->execute(array('accesstoken-openid-connect', 'Some Client', date('Y-m-d H:i:s', strtotime('+1 hour')), 'testuser'));
-
- $sql = 'INSERT INTO oauth_authorization_codes (authorization_code, client_id, expires) VALUES (?, ?, ?)';
- $pdo->prepare($sql)->execute(array('testcode', 'Some Client', date('Y-m-d H:i:s', strtotime('+1 hour'))));
-
- $sql = 'INSERT INTO oauth_users (username, password, email, email_verified) VALUES (?, ?, ?, ?)';
- $pdo->prepare($sql)->execute(array('testuser', 'password', 'testuser@test.com', true));
-
- $sql = 'INSERT INTO oauth_public_keys (client_id, public_key, private_key, encryption_algorithm) VALUES (?, ?, ?, ?)';
- $pdo->prepare($sql)->execute(array('ClientID_One', 'client_1_public', 'client_1_private', 'RS256'));
- $pdo->prepare($sql)->execute(array('ClientID_Two', 'client_2_public', 'client_2_private', 'RS256'));
-
- $sql = 'INSERT INTO oauth_public_keys (client_id, public_key, private_key, encryption_algorithm) VALUES (?, ?, ?, ?)';
- $pdo->prepare($sql)->execute(array(null, $this->getTestPublicKey(), $this->getTestPrivateKey(), 'RS256'));
-
- $sql = 'INSERT INTO oauth_jwt (client_id, subject, public_key) VALUES (?, ?, ?)';
- $pdo->prepare($sql)->execute(array('oauth_test_client', 'test_subject', $this->getTestPublicKey()));
- }
-
- public function getSqliteDir()
- {
- return $this->configDir. '/test.sqlite';
- }
-
- public function getConfigDir()
- {
- return $this->configDir;
- }
-
- private function createCouchbaseDB(\Couchbase $db)
- {
- $db->set('oauth_clients-oauth_test_client',json_encode(array(
- 'client_id' => "oauth_test_client",
- 'client_secret' => "testpass",
- 'redirect_uri' => "http://example.com",
- 'grant_types' => 'implicit password'
- )));
-
- $db->set('oauth_access_tokens-testtoken',json_encode(array(
- 'access_token' => "testtoken",
- 'client_id' => "Some Client"
- )));
-
- $db->set('oauth_authorization_codes-testcode',json_encode(array(
- 'access_token' => "testcode",
- 'client_id' => "Some Client"
- )));
-
- $db->set('oauth_users-testuser',json_encode(array(
- 'username' => 'testuser',
- 'password' => 'password',
- 'email' => 'testuser@test.com',
- 'email_verified' => true,
- )));
-
- $db->set('oauth_jwt-oauth_test_client',json_encode(array(
- 'client_id' => 'oauth_test_client',
- 'key' => $this->getTestPublicKey(),
- 'subject' => 'test_subject',
- )));
- }
-
- private function clearCouchbase(\Couchbase $cb)
- {
- $cb->delete('oauth_authorization_codes-new-openid-code');
- $cb->delete('oauth_access_tokens-newtoken');
- $cb->delete('oauth_authorization_codes-newcode');
- $cb->delete('oauth_refresh_tokens-refreshtoken');
- }
-
- private function createMongoDb(\MongoDB $db)
- {
- $db->oauth_clients->insert(array(
- 'client_id' => "oauth_test_client",
- 'client_secret' => "testpass",
- 'redirect_uri' => "http://example.com",
- 'grant_types' => 'implicit password'
- ));
-
- $db->oauth_access_tokens->insert(array(
- 'access_token' => "testtoken",
- 'client_id' => "Some Client"
- ));
-
- $db->oauth_authorization_codes->insert(array(
- 'authorization_code' => "testcode",
- 'client_id' => "Some Client"
- ));
-
- $db->oauth_users->insert(array(
- 'username' => 'testuser',
- 'password' => 'password',
- 'email' => 'testuser@test.com',
- 'email_verified' => true,
- ));
-
- $db->oauth_jwt->insert(array(
- 'client_id' => 'oauth_test_client',
- 'key' => $this->getTestPublicKey(),
- 'subject' => 'test_subject',
- ));
- }
-
- private function createRedisDb(Redis $storage)
- {
- $storage->setClientDetails("oauth_test_client", "testpass", "http://example.com", 'implicit password');
- $storage->setAccessToken("testtoken", "Some Client", '', time() + 1000);
- $storage->setAuthorizationCode("testcode", "Some Client", '', '', time() + 1000);
- $storage->setUser("testuser", "password");
-
- $storage->setScope('supportedscope1 supportedscope2 supportedscope3 supportedscope4');
- $storage->setScope('defaultscope1 defaultscope2', null, 'default');
-
- $storage->setScope('clientscope1 clientscope2', 'Test Client ID');
- $storage->setScope('clientscope1 clientscope2', 'Test Client ID', 'default');
-
- $storage->setScope('clientscope1 clientscope2 clientscope3', 'Test Client ID 2');
- $storage->setScope('clientscope1 clientscope2', 'Test Client ID 2', 'default');
-
- $storage->setScope('clientscope1 clientscope2', 'Test Default Scope Client ID');
- $storage->setScope('clientscope1 clientscope2', 'Test Default Scope Client ID', 'default');
-
- $storage->setScope('clientscope1 clientscope2 clientscope3', 'Test Default Scope Client ID 2');
- $storage->setScope('clientscope3', 'Test Default Scope Client ID 2', 'default');
-
- $storage->setClientKey('oauth_test_client', $this->getTestPublicKey(), 'test_subject');
- }
-
- public function removeMongoDb(\MongoDB $db)
- {
- $db->drop();
- }
-
- public function getTestPublicKey()
- {
- return file_get_contents(__DIR__.'/../../../config/keys/id_rsa.pub');
- }
-
- private function getTestPrivateKey()
- {
- return file_get_contents(__DIR__.'/../../../config/keys/id_rsa');
- }
-
- public function getDynamoDbStorage()
- {
- if (!$this->dynamodb) {
- // only run once per travis build
- if (true == $this->getEnvVar('TRAVIS')) {
- if (self::DYNAMODB_PHP_VERSION != $this->getEnvVar('TRAVIS_PHP_VERSION')) {
- $this->dynamodb = new NullStorage('DynamoDb', 'Skipping for travis.ci - only run once per build');
-
- return;
- }
- }
- if (class_exists('\Aws\DynamoDb\DynamoDbClient')) {
- if ($client = $this->getDynamoDbClient()) {
- // travis runs a unique set of tables per build, to avoid conflict
- $prefix = '';
- if ($build_id = $this->getEnvVar('TRAVIS_JOB_NUMBER')) {
- $prefix = sprintf('build_%s_', $build_id);
- } else {
- if (!$this->deleteDynamoDb($client, $prefix, true)) {
- return $this->dynamodb = new NullStorage('DynamoDb', 'Timed out while waiting for DynamoDB deletion (30 seconds)');
- }
- }
- $this->createDynamoDb($client, $prefix);
- $this->populateDynamoDb($client, $prefix);
- $config = array(
- 'client_table' => $prefix.'oauth_clients',
- 'access_token_table' => $prefix.'oauth_access_tokens',
- 'refresh_token_table' => $prefix.'oauth_refresh_tokens',
- 'code_table' => $prefix.'oauth_authorization_codes',
- 'user_table' => $prefix.'oauth_users',
- 'jwt_table' => $prefix.'oauth_jwt',
- 'scope_table' => $prefix.'oauth_scopes',
- 'public_key_table' => $prefix.'oauth_public_keys',
- );
- $this->dynamodb = new DynamoDB($client, $config);
- } elseif (!$this->dynamodb) {
- $this->dynamodb = new NullStorage('DynamoDb', 'unable to connect to DynamoDB');
- }
- } else {
- $this->dynamodb = new NullStorage('DynamoDb', 'Missing DynamoDB library. Please run "composer.phar require aws/aws-sdk-php:dev-master');
- }
- }
-
- return $this->dynamodb;
- }
-
- private function getDynamoDbClient()
- {
- $config = array();
- // check for environment variables
- if (($key = $this->getEnvVar('AWS_ACCESS_KEY_ID')) && ($secret = $this->getEnvVar('AWS_SECRET_KEY'))) {
- $config['key'] = $key;
- $config['secret'] = $secret;
- } else {
- // fall back on ~/.aws/credentials file
- // @see http://docs.aws.amazon.com/aws-sdk-php/guide/latest/credentials.html#credential-profiles
- if (!file_exists($this->getEnvVar('HOME') . '/.aws/credentials')) {
- $this->dynamodb = new NullStorage('DynamoDb', 'No aws credentials file found, and no AWS_ACCESS_KEY_ID or AWS_SECRET_KEY environment variable set');
-
- return;
- }
-
- // set profile in AWS_PROFILE environment variable, defaults to "default"
- $config['profile'] = $this->getEnvVar('AWS_PROFILE', 'default');
- }
-
- // set region in AWS_REGION environment variable, defaults to "us-east-1"
- $config['region'] = $this->getEnvVar('AWS_REGION', \Aws\Common\Enum\Region::US_EAST_1);
-
- return \Aws\DynamoDb\DynamoDbClient::factory($config);
- }
-
- private function deleteDynamoDb(\Aws\DynamoDb\DynamoDbClient $client, $prefix = null, $waitForDeletion = false)
- {
- $tablesList = explode(' ', 'oauth_access_tokens oauth_authorization_codes oauth_clients oauth_jwt oauth_public_keys oauth_refresh_tokens oauth_scopes oauth_users');
- $nbTables = count($tablesList);
-
- // Delete all table.
- foreach ($tablesList as $key => $table) {
- try {
- $client->deleteTable(array('TableName' => $prefix.$table));
- } catch (\Aws\DynamoDb\Exception\DynamoDbException $e) {
- // Table does not exist : nothing to do
- }
- }
-
- // Wait for deleting
- if ($waitForDeletion) {
- $retries = 5;
- $nbTableDeleted = 0;
- while ($nbTableDeleted != $nbTables) {
- $nbTableDeleted = 0;
- foreach ($tablesList as $key => $table) {
- try {
- $result = $client->describeTable(array('TableName' => $prefix.$table));
- } catch (\Aws\DynamoDb\Exception\DynamoDbException $e) {
- // Table does not exist : nothing to do
- $nbTableDeleted++;
- }
- }
- if ($nbTableDeleted != $nbTables) {
- if ($retries < 0) {
- // we are tired of waiting
- return false;
- }
- sleep(5);
- echo "Sleeping 5 seconds for DynamoDB ($retries more retries)...\n";
- $retries--;
- }
- }
- }
-
- return true;
- }
-
- private function createDynamoDb(\Aws\DynamoDb\DynamoDbClient $client, $prefix = null)
- {
- $tablesList = explode(' ', 'oauth_access_tokens oauth_authorization_codes oauth_clients oauth_jwt oauth_public_keys oauth_refresh_tokens oauth_scopes oauth_users');
- $nbTables = count($tablesList);
- $client->createTable(array(
- 'TableName' => $prefix.'oauth_access_tokens',
- 'AttributeDefinitions' => array(
- array('AttributeName' => 'access_token','AttributeType' => 'S')
- ),
- 'KeySchema' => array(array('AttributeName' => 'access_token','KeyType' => 'HASH')),
- 'ProvisionedThroughput' => array('ReadCapacityUnits' => 1,'WriteCapacityUnits' => 1)
- ));
-
- $client->createTable(array(
- 'TableName' => $prefix.'oauth_authorization_codes',
- 'AttributeDefinitions' => array(
- array('AttributeName' => 'authorization_code','AttributeType' => 'S')
- ),
- 'KeySchema' => array(array('AttributeName' => 'authorization_code','KeyType' => 'HASH')),
- 'ProvisionedThroughput' => array('ReadCapacityUnits' => 1,'WriteCapacityUnits' => 1)
- ));
-
- $client->createTable(array(
- 'TableName' => $prefix.'oauth_clients',
- 'AttributeDefinitions' => array(
- array('AttributeName' => 'client_id','AttributeType' => 'S')
- ),
- 'KeySchema' => array(array('AttributeName' => 'client_id','KeyType' => 'HASH')),
- 'ProvisionedThroughput' => array('ReadCapacityUnits' => 1,'WriteCapacityUnits' => 1)
- ));
-
- $client->createTable(array(
- 'TableName' => $prefix.'oauth_jwt',
- 'AttributeDefinitions' => array(
- array('AttributeName' => 'client_id','AttributeType' => 'S'),
- array('AttributeName' => 'subject','AttributeType' => 'S')
- ),
- 'KeySchema' => array(
- array('AttributeName' => 'client_id','KeyType' => 'HASH'),
- array('AttributeName' => 'subject','KeyType' => 'RANGE')
- ),
- 'ProvisionedThroughput' => array('ReadCapacityUnits' => 1,'WriteCapacityUnits' => 1)
- ));
-
- $client->createTable(array(
- 'TableName' => $prefix.'oauth_public_keys',
- 'AttributeDefinitions' => array(
- array('AttributeName' => 'client_id','AttributeType' => 'S')
- ),
- 'KeySchema' => array(array('AttributeName' => 'client_id','KeyType' => 'HASH')),
- 'ProvisionedThroughput' => array('ReadCapacityUnits' => 1,'WriteCapacityUnits' => 1)
- ));
-
- $client->createTable(array(
- 'TableName' => $prefix.'oauth_refresh_tokens',
- 'AttributeDefinitions' => array(
- array('AttributeName' => 'refresh_token','AttributeType' => 'S')
- ),
- 'KeySchema' => array(array('AttributeName' => 'refresh_token','KeyType' => 'HASH')),
- 'ProvisionedThroughput' => array('ReadCapacityUnits' => 1,'WriteCapacityUnits' => 1)
- ));
-
- $client->createTable(array(
- 'TableName' => $prefix.'oauth_scopes',
- 'AttributeDefinitions' => array(
- array('AttributeName' => 'scope','AttributeType' => 'S'),
- array('AttributeName' => 'is_default','AttributeType' => 'S')
- ),
- 'KeySchema' => array(array('AttributeName' => 'scope','KeyType' => 'HASH')),
- 'GlobalSecondaryIndexes' => array(
- array(
- 'IndexName' => 'is_default-index',
- 'KeySchema' => array(array('AttributeName' => 'is_default', 'KeyType' => 'HASH')),
- 'Projection' => array('ProjectionType' => 'ALL'),
- 'ProvisionedThroughput' => array('ReadCapacityUnits' => 1,'WriteCapacityUnits' => 1)
- ),
- ),
- 'ProvisionedThroughput' => array('ReadCapacityUnits' => 1,'WriteCapacityUnits' => 1)
- ));
-
- $client->createTable(array(
- 'TableName' => $prefix.'oauth_users',
- 'AttributeDefinitions' => array(array('AttributeName' => 'username','AttributeType' => 'S')),
- 'KeySchema' => array(array('AttributeName' => 'username','KeyType' => 'HASH')),
- 'ProvisionedThroughput' => array('ReadCapacityUnits' => 1,'WriteCapacityUnits' => 1)
- ));
-
- // Wait for creation
- $nbTableCreated = 0;
- while ($nbTableCreated != $nbTables) {
- $nbTableCreated = 0;
- foreach ($tablesList as $key => $table) {
- try {
- $result = $client->describeTable(array('TableName' => $prefix.$table));
- if ($result['Table']['TableStatus'] == 'ACTIVE') {
- $nbTableCreated++;
- }
- } catch (\Aws\DynamoDb\Exception\DynamoDbException $e) {
- // Table does not exist : nothing to do
- $nbTableCreated++;
- }
- }
- if ($nbTableCreated != $nbTables) {
- sleep(1);
- }
- }
- }
-
- private function populateDynamoDb($client, $prefix = null)
- {
- // set up scopes
- foreach (explode(' ', 'supportedscope1 supportedscope2 supportedscope3 supportedscope4 clientscope1 clientscope2 clientscope3') as $supportedScope) {
- $client->putItem(array(
- 'TableName' => $prefix.'oauth_scopes',
- 'Item' => array('scope' => array('S' => $supportedScope))
- ));
- }
-
- foreach (array('defaultscope1', 'defaultscope2') as $defaultScope) {
- $client->putItem(array(
- 'TableName' => $prefix.'oauth_scopes',
- 'Item' => array('scope' => array('S' => $defaultScope), 'is_default' => array('S' => "true"))
- ));
- }
-
- $client->putItem(array(
- 'TableName' => $prefix.'oauth_clients',
- 'Item' => array(
- 'client_id' => array('S' => 'Test Client ID'),
- 'client_secret' => array('S' => 'TestSecret'),
- 'scope' => array('S' => 'clientscope1 clientscope2')
- )
- ));
-
- $client->putItem(array(
- 'TableName' => $prefix.'oauth_clients',
- 'Item' => array(
- 'client_id' => array('S' => 'Test Client ID 2'),
- 'client_secret' => array('S' => 'TestSecret'),
- 'scope' => array('S' => 'clientscope1 clientscope2 clientscope3')
- )
- ));
-
- $client->putItem(array(
- 'TableName' => $prefix.'oauth_clients',
- 'Item' => array(
- 'client_id' => array('S' => 'Test Default Scope Client ID'),
- 'client_secret' => array('S' => 'TestSecret'),
- 'scope' => array('S' => 'clientscope1 clientscope2')
- )
- ));
-
- $client->putItem(array(
- 'TableName' => $prefix.'oauth_clients',
- 'Item' => array(
- 'client_id' => array('S' => 'oauth_test_client'),
- 'client_secret' => array('S' => 'testpass'),
- 'grant_types' => array('S' => 'implicit password')
- )
- ));
-
- $client->putItem(array(
- 'TableName' => $prefix.'oauth_access_tokens',
- 'Item' => array(
- 'access_token' => array('S' => 'testtoken'),
- 'client_id' => array('S' => 'Some Client'),
- )
- ));
-
- $client->putItem(array(
- 'TableName' => $prefix.'oauth_access_tokens',
- 'Item' => array(
- 'access_token' => array('S' => 'accesstoken-openid-connect'),
- 'client_id' => array('S' => 'Some Client'),
- 'user_id' => array('S' => 'testuser'),
- )
- ));
-
- $client->putItem(array(
- 'TableName' => $prefix.'oauth_authorization_codes',
- 'Item' => array(
- 'authorization_code' => array('S' => 'testcode'),
- 'client_id' => array('S' => 'Some Client'),
- )
- ));
-
- $client->putItem(array(
- 'TableName' => $prefix.'oauth_users',
- 'Item' => array(
- 'username' => array('S' => 'testuser'),
- 'password' => array('S' => 'password'),
- 'email' => array('S' => 'testuser@test.com'),
- 'email_verified' => array('S' => 'true'),
- )
- ));
-
- $client->putItem(array(
- 'TableName' => $prefix.'oauth_public_keys',
- 'Item' => array(
- 'client_id' => array('S' => 'ClientID_One'),
- 'public_key' => array('S' => 'client_1_public'),
- 'private_key' => array('S' => 'client_1_private'),
- 'encryption_algorithm' => array('S' => 'RS256'),
- )
- ));
-
- $client->putItem(array(
- 'TableName' => $prefix.'oauth_public_keys',
- 'Item' => array(
- 'client_id' => array('S' => 'ClientID_Two'),
- 'public_key' => array('S' => 'client_2_public'),
- 'private_key' => array('S' => 'client_2_private'),
- 'encryption_algorithm' => array('S' => 'RS256'),
- )
- ));
-
- $client->putItem(array(
- 'TableName' => $prefix.'oauth_public_keys',
- 'Item' => array(
- 'client_id' => array('S' => '0'),
- 'public_key' => array('S' => $this->getTestPublicKey()),
- 'private_key' => array('S' => $this->getTestPrivateKey()),
- 'encryption_algorithm' => array('S' => 'RS256'),
- )
- ));
-
- $client->putItem(array(
- 'TableName' => $prefix.'oauth_jwt',
- 'Item' => array(
- 'client_id' => array('S' => 'oauth_test_client'),
- 'subject' => array('S' => 'test_subject'),
- 'public_key' => array('S' => $this->getTestPublicKey()),
- )
- ));
- }
-
- public function cleanupTravisDynamoDb($prefix = null)
- {
- if (is_null($prefix)) {
- // skip this when not applicable
- if (!$this->getEnvVar('TRAVIS') || self::DYNAMODB_PHP_VERSION != $this->getEnvVar('TRAVIS_PHP_VERSION')) {
- return;
- }
-
- $prefix = sprintf('build_%s_', $this->getEnvVar('TRAVIS_JOB_NUMBER'));
- }
-
- $client = $this->getDynamoDbClient();
- $this->deleteDynamoDb($client, $prefix);
- }
-
- private function getEnvVar($var, $default = null)
- {
- return isset($_SERVER[$var]) ? $_SERVER[$var] : (getenv($var) ?: $default);
- }
-}
diff --git a/library/popper/popper.min.js b/library/popper/popper.min.js
new file mode 100644
index 000000000..ce33a863d
--- /dev/null
+++ b/library/popper/popper.min.js
@@ -0,0 +1,4 @@
+/*
+ Copyright (C) Federico Zivolo 2017
+ Distributed under the MIT License (license terms are at http://opensource.org/licenses/MIT).
+ */(function(e,t){'object'==typeof exports&&'undefined'!=typeof module?module.exports=t():'function'==typeof define&&define.amd?define(t):e.Popper=t()})(this,function(){'use strict';function e(e){return e&&'[object Function]'==={}.toString.call(e)}function t(e,t){if(1!==e.nodeType)return[];var o=window.getComputedStyle(e,null);return t?o[t]:o}function o(e){return'HTML'===e.nodeName?e:e.parentNode||e.host}function n(e){if(!e||-1!==['HTML','BODY','#document'].indexOf(e.nodeName))return window.document.body;var i=t(e),r=i.overflow,p=i.overflowX,s=i.overflowY;return /(auto|scroll)/.test(r+s+p)?e:n(o(e))}function r(e){var o=e&&e.offsetParent,i=o&&o.nodeName;return i&&'BODY'!==i&&'HTML'!==i?-1!==['TD','TABLE'].indexOf(o.nodeName)&&'static'===t(o,'position')?r(o):o:window.document.documentElement}function p(e){var t=e.nodeName;return'BODY'!==t&&('HTML'===t||r(e.firstElementChild)===e)}function s(e){return null===e.parentNode?e:s(e.parentNode)}function d(e,t){if(!e||!e.nodeType||!t||!t.nodeType)return window.document.documentElement;var o=e.compareDocumentPosition(t)&Node.DOCUMENT_POSITION_FOLLOWING,i=o?e:t,n=o?t:e,a=document.createRange();a.setStart(i,0),a.setEnd(n,0);var f=a.commonAncestorContainer;if(e!==f&&t!==f||i.contains(n))return p(f)?f:r(f);var l=s(e);return l.host?d(l.host,t):d(e,s(t).host)}function a(e){var t=1<arguments.length&&void 0!==arguments[1]?arguments[1]:'top',o='top'===t?'scrollTop':'scrollLeft',i=e.nodeName;if('BODY'===i||'HTML'===i){var n=window.document.documentElement,r=window.document.scrollingElement||n;return r[o]}return e[o]}function f(e,t){var o=2<arguments.length&&void 0!==arguments[2]&&arguments[2],i=a(t,'top'),n=a(t,'left'),r=o?-1:1;return e.top+=i*r,e.bottom+=i*r,e.left+=n*r,e.right+=n*r,e}function l(e,t){var o='x'===t?'Left':'Top',i='Left'==o?'Right':'Bottom';return+e['border'+o+'Width'].split('px')[0]+ +e['border'+i+'Width'].split('px')[0]}function m(e,t,o,i){return _(t['offset'+e],o['client'+e],o['offset'+e],ie()?o['offset'+e]+i['margin'+('Height'===e?'Top':'Left')]+i['margin'+('Height'===e?'Bottom':'Right')]:0)}function h(){var e=window.document.body,t=window.document.documentElement,o=ie()&&window.getComputedStyle(t);return{height:m('Height',e,t,o),width:m('Width',e,t,o)}}function c(e){return se({},e,{right:e.left+e.width,bottom:e.top+e.height})}function g(e){var o={};if(ie())try{o=e.getBoundingClientRect();var i=a(e,'top'),n=a(e,'left');o.top+=i,o.left+=n,o.bottom+=i,o.right+=n}catch(e){}else o=e.getBoundingClientRect();var r={left:o.left,top:o.top,width:o.right-o.left,height:o.bottom-o.top},p='HTML'===e.nodeName?h():{},s=p.width||e.clientWidth||r.right-r.left,d=p.height||e.clientHeight||r.bottom-r.top,f=e.offsetWidth-s,m=e.offsetHeight-d;if(f||m){var g=t(e);f-=l(g,'x'),m-=l(g,'y'),r.width-=f,r.height-=m}return c(r)}function u(e,o){var i=ie(),r='HTML'===o.nodeName,p=g(e),s=g(o),d=n(e),a=t(o),l=+a.borderTopWidth.split('px')[0],m=+a.borderLeftWidth.split('px')[0],h=c({top:p.top-s.top-l,left:p.left-s.left-m,width:p.width,height:p.height});if(h.marginTop=0,h.marginLeft=0,!i&&r){var u=+a.marginTop.split('px')[0],b=+a.marginLeft.split('px')[0];h.top-=l-u,h.bottom-=l-u,h.left-=m-b,h.right-=m-b,h.marginTop=u,h.marginLeft=b}return(i?o.contains(d):o===d&&'BODY'!==d.nodeName)&&(h=f(h,o)),h}function b(e){var t=window.document.documentElement,o=u(e,t),i=_(t.clientWidth,window.innerWidth||0),n=_(t.clientHeight,window.innerHeight||0),r=a(t),p=a(t,'left'),s={top:r-o.top+o.marginTop,left:p-o.left+o.marginLeft,width:i,height:n};return c(s)}function y(e){var i=e.nodeName;return'BODY'===i||'HTML'===i?!1:'fixed'===t(e,'position')||y(o(e))}function w(e,t,i,r){var p={top:0,left:0},s=d(e,t);if('viewport'===r)p=b(s);else{var a;'scrollParent'===r?(a=n(o(e)),'BODY'===a.nodeName&&(a=window.document.documentElement)):'window'===r?a=window.document.documentElement:a=r;var f=u(a,s);if('HTML'===a.nodeName&&!y(s)){var l=h(),m=l.height,c=l.width;p.top+=f.top-f.marginTop,p.bottom=m+f.top,p.left+=f.left-f.marginLeft,p.right=c+f.left}else p=f}return p.left+=i,p.top+=i,p.right-=i,p.bottom-=i,p}function v(e){var t=e.width,o=e.height;return t*o}function E(e,t,o,i,n){var r=5<arguments.length&&void 0!==arguments[5]?arguments[5]:0;if(-1===e.indexOf('auto'))return e;var p=w(o,i,r,n),s={top:{width:p.width,height:t.top-p.top},right:{width:p.right-t.right,height:p.height},bottom:{width:p.width,height:p.bottom-t.bottom},left:{width:t.left-p.left,height:p.height}},d=Object.keys(s).map(function(e){return se({key:e},s[e],{area:v(s[e])})}).sort(function(e,t){return t.area-e.area}),a=d.filter(function(e){var t=e.width,i=e.height;return t>=o.clientWidth&&i>=o.clientHeight}),f=0<a.length?a[0].key:d[0].key,l=e.split('-')[1];return f+(l?'-'+l:'')}function x(e,t,o){var i=d(t,o);return u(o,i)}function O(e){var t=window.getComputedStyle(e),o=parseFloat(t.marginTop)+parseFloat(t.marginBottom),i=parseFloat(t.marginLeft)+parseFloat(t.marginRight),n={width:e.offsetWidth+i,height:e.offsetHeight+o};return n}function L(e){var t={left:'right',right:'left',bottom:'top',top:'bottom'};return e.replace(/left|right|bottom|top/g,function(e){return t[e]})}function S(e,t,o){o=o.split('-')[0];var i=O(e),n={width:i.width,height:i.height},r=-1!==['right','left'].indexOf(o),p=r?'top':'left',s=r?'left':'top',d=r?'height':'width',a=r?'width':'height';return n[p]=t[p]+t[d]/2-i[d]/2,n[s]=o===s?t[s]-i[a]:t[L(s)],n}function T(e,t){return Array.prototype.find?e.find(t):e.filter(t)[0]}function C(e,t,o){if(Array.prototype.findIndex)return e.findIndex(function(e){return e[t]===o});var i=T(e,function(e){return e[t]===o});return e.indexOf(i)}function N(t,o,i){var n=void 0===i?t:t.slice(0,C(t,'name',i));return n.forEach(function(t){t.function&&console.warn('`modifier.function` is deprecated, use `modifier.fn`!');var i=t.function||t.fn;t.enabled&&e(i)&&(o.offsets.popper=c(o.offsets.popper),o.offsets.reference=c(o.offsets.reference),o=i(o,t))}),o}function k(){if(!this.state.isDestroyed){var e={instance:this,styles:{},attributes:{},flipped:!1,offsets:{}};e.offsets.reference=x(this.state,this.popper,this.reference),e.placement=E(this.options.placement,e.offsets.reference,this.popper,this.reference,this.options.modifiers.flip.boundariesElement,this.options.modifiers.flip.padding),e.originalPlacement=e.placement,e.offsets.popper=S(this.popper,e.offsets.reference,e.placement),e.offsets.popper.position='absolute',e=N(this.modifiers,e),this.state.isCreated?this.options.onUpdate(e):(this.state.isCreated=!0,this.options.onCreate(e))}}function W(e,t){return e.some(function(e){var o=e.name,i=e.enabled;return i&&o===t})}function B(e){for(var t=[!1,'ms','Webkit','Moz','O'],o=e.charAt(0).toUpperCase()+e.slice(1),n=0;n<t.length-1;n++){var i=t[n],r=i?''+i+o:e;if('undefined'!=typeof window.document.body.style[r])return r}return null}function D(){return this.state.isDestroyed=!0,W(this.modifiers,'applyStyle')&&(this.popper.removeAttribute('x-placement'),this.popper.style.left='',this.popper.style.position='',this.popper.style.top='',this.popper.style[B('transform')]=''),this.disableEventListeners(),this.options.removeOnDestroy&&this.popper.parentNode.removeChild(this.popper),this}function H(e,t,o,i){var r='BODY'===e.nodeName,p=r?window:e;p.addEventListener(t,o,{passive:!0}),r||H(n(p.parentNode),t,o,i),i.push(p)}function P(e,t,o,i){o.updateBound=i,window.addEventListener('resize',o.updateBound,{passive:!0});var r=n(e);return H(r,'scroll',o.updateBound,o.scrollParents),o.scrollElement=r,o.eventsEnabled=!0,o}function A(){this.state.eventsEnabled||(this.state=P(this.reference,this.options,this.state,this.scheduleUpdate))}function M(e,t){return window.removeEventListener('resize',t.updateBound),t.scrollParents.forEach(function(e){e.removeEventListener('scroll',t.updateBound)}),t.updateBound=null,t.scrollParents=[],t.scrollElement=null,t.eventsEnabled=!1,t}function I(){this.state.eventsEnabled&&(window.cancelAnimationFrame(this.scheduleUpdate),this.state=M(this.reference,this.state))}function R(e){return''!==e&&!isNaN(parseFloat(e))&&isFinite(e)}function U(e,t){Object.keys(t).forEach(function(o){var i='';-1!==['width','height','top','right','bottom','left'].indexOf(o)&&R(t[o])&&(i='px'),e.style[o]=t[o]+i})}function Y(e,t){Object.keys(t).forEach(function(o){var i=t[o];!1===i?e.removeAttribute(o):e.setAttribute(o,t[o])})}function F(e,t,o){var i=T(e,function(e){var o=e.name;return o===t}),n=!!i&&e.some(function(e){return e.name===o&&e.enabled&&e.order<i.order});if(!n){var r='`'+t+'`';console.warn('`'+o+'`'+' modifier is required by '+r+' modifier in order to work, be sure to include it before '+r+'!')}return n}function j(e){return'end'===e?'start':'start'===e?'end':e}function K(e){var t=1<arguments.length&&void 0!==arguments[1]&&arguments[1],o=ae.indexOf(e),i=ae.slice(o+1).concat(ae.slice(0,o));return t?i.reverse():i}function q(e,t,o,i){var n=e.match(/((?:\-|\+)?\d*\.?\d*)(.*)/),r=+n[1],p=n[2];if(!r)return e;if(0===p.indexOf('%')){var s;switch(p){case'%p':s=o;break;case'%':case'%r':default:s=i;}var d=c(s);return d[t]/100*r}if('vh'===p||'vw'===p){var a;return a='vh'===p?_(document.documentElement.clientHeight,window.innerHeight||0):_(document.documentElement.clientWidth,window.innerWidth||0),a/100*r}return r}function G(e,t,o,i){var n=[0,0],r=-1!==['right','left'].indexOf(i),p=e.split(/(\+|\-)/).map(function(e){return e.trim()}),s=p.indexOf(T(p,function(e){return-1!==e.search(/,|\s/)}));p[s]&&-1===p[s].indexOf(',')&&console.warn('Offsets separated by white space(s) are deprecated, use a comma (,) instead.');var d=/\s*,\s*|\s+/,a=-1===s?[p]:[p.slice(0,s).concat([p[s].split(d)[0]]),[p[s].split(d)[1]].concat(p.slice(s+1))];return a=a.map(function(e,i){var n=(1===i?!r:r)?'height':'width',p=!1;return e.reduce(function(e,t){return''===e[e.length-1]&&-1!==['+','-'].indexOf(t)?(e[e.length-1]=t,p=!0,e):p?(e[e.length-1]+=t,p=!1,e):e.concat(t)},[]).map(function(e){return q(e,n,t,o)})}),a.forEach(function(e,t){e.forEach(function(o,i){R(o)&&(n[t]+=o*('-'===e[i-1]?-1:1))})}),n}for(var z=Math.min,V=Math.floor,_=Math.max,X=['native code','[object MutationObserverConstructor]'],Q=function(e){return X.some(function(t){return-1<(e||'').toString().indexOf(t)})},J='undefined'!=typeof window,Z=['Edge','Trident','Firefox'],$=0,ee=0;ee<Z.length;ee+=1)if(J&&0<=navigator.userAgent.indexOf(Z[ee])){$=1;break}var i,te=J&&Q(window.MutationObserver),oe=te?function(e){var t=!1,o=0,i=document.createElement('span'),n=new MutationObserver(function(){e(),t=!1});return n.observe(i,{attributes:!0}),function(){t||(t=!0,i.setAttribute('x-index',o),++o)}}:function(e){var t=!1;return function(){t||(t=!0,setTimeout(function(){t=!1,e()},$))}},ie=function(){return void 0==i&&(i=-1!==navigator.appVersion.indexOf('MSIE 10')),i},ne=function(e,t){if(!(e instanceof t))throw new TypeError('Cannot call a class as a function')},re=function(){function e(e,t){for(var o,n=0;n<t.length;n++)o=t[n],o.enumerable=o.enumerable||!1,o.configurable=!0,'value'in o&&(o.writable=!0),Object.defineProperty(e,o.key,o)}return function(t,o,i){return o&&e(t.prototype,o),i&&e(t,i),t}}(),pe=function(e,t,o){return t in e?Object.defineProperty(e,t,{value:o,enumerable:!0,configurable:!0,writable:!0}):e[t]=o,e},se=Object.assign||function(e){for(var t,o=1;o<arguments.length;o++)for(var i in t=arguments[o],t)Object.prototype.hasOwnProperty.call(t,i)&&(e[i]=t[i]);return e},de=['auto-start','auto','auto-end','top-start','top','top-end','right-start','right','right-end','bottom-end','bottom','bottom-start','left-end','left','left-start'],ae=de.slice(3),fe={FLIP:'flip',CLOCKWISE:'clockwise',COUNTERCLOCKWISE:'counterclockwise'},le=function(){function t(o,i){var n=this,r=2<arguments.length&&void 0!==arguments[2]?arguments[2]:{};ne(this,t),this.scheduleUpdate=function(){return requestAnimationFrame(n.update)},this.update=oe(this.update.bind(this)),this.options=se({},t.Defaults,r),this.state={isDestroyed:!1,isCreated:!1,scrollParents:[]},this.reference=o.jquery?o[0]:o,this.popper=i.jquery?i[0]:i,this.options.modifiers={},Object.keys(se({},t.Defaults.modifiers,r.modifiers)).forEach(function(e){n.options.modifiers[e]=se({},t.Defaults.modifiers[e]||{},r.modifiers?r.modifiers[e]:{})}),this.modifiers=Object.keys(this.options.modifiers).map(function(e){return se({name:e},n.options.modifiers[e])}).sort(function(e,t){return e.order-t.order}),this.modifiers.forEach(function(t){t.enabled&&e(t.onLoad)&&t.onLoad(n.reference,n.popper,n.options,t,n.state)}),this.update();var p=this.options.eventsEnabled;p&&this.enableEventListeners(),this.state.eventsEnabled=p}return re(t,[{key:'update',value:function(){return k.call(this)}},{key:'destroy',value:function(){return D.call(this)}},{key:'enableEventListeners',value:function(){return A.call(this)}},{key:'disableEventListeners',value:function(){return I.call(this)}}]),t}();return le.Utils=('undefined'==typeof window?global:window).PopperUtils,le.placements=de,le.Defaults={placement:'bottom',eventsEnabled:!0,removeOnDestroy:!1,onCreate:function(){},onUpdate:function(){},modifiers:{shift:{order:100,enabled:!0,fn:function(e){var t=e.placement,o=t.split('-')[0],i=t.split('-')[1];if(i){var n=e.offsets,r=n.reference,p=n.popper,s=-1!==['bottom','top'].indexOf(o),d=s?'left':'top',a=s?'width':'height',f={start:pe({},d,r[d]),end:pe({},d,r[d]+r[a]-p[a])};e.offsets.popper=se({},p,f[i])}return e}},offset:{order:200,enabled:!0,fn:function(e,t){var o,i=t.offset,n=e.placement,r=e.offsets,p=r.popper,s=r.reference,d=n.split('-')[0];return o=R(+i)?[+i,0]:G(i,p,s,d),'left'===d?(p.top+=o[0],p.left-=o[1]):'right'===d?(p.top+=o[0],p.left+=o[1]):'top'===d?(p.left+=o[0],p.top-=o[1]):'bottom'===d&&(p.left+=o[0],p.top+=o[1]),e.popper=p,e},offset:0},preventOverflow:{order:300,enabled:!0,fn:function(e,t){var o=t.boundariesElement||r(e.instance.popper);e.instance.reference===o&&(o=r(o));var i=w(e.instance.popper,e.instance.reference,t.padding,o);t.boundaries=i;var n=t.priority,p=e.offsets.popper,s={primary:function(e){var o=p[e];return p[e]<i[e]&&!t.escapeWithReference&&(o=_(p[e],i[e])),pe({},e,o)},secondary:function(e){var o='right'===e?'left':'top',n=p[o];return p[e]>i[e]&&!t.escapeWithReference&&(n=z(p[o],i[e]-('right'===e?p.width:p.height))),pe({},o,n)}};return n.forEach(function(e){var t=-1===['left','top'].indexOf(e)?'secondary':'primary';p=se({},p,s[t](e))}),e.offsets.popper=p,e},priority:['left','right','top','bottom'],padding:5,boundariesElement:'scrollParent'},keepTogether:{order:400,enabled:!0,fn:function(e){var t=e.offsets,o=t.popper,i=t.reference,n=e.placement.split('-')[0],r=V,p=-1!==['top','bottom'].indexOf(n),s=p?'right':'bottom',d=p?'left':'top',a=p?'width':'height';return o[s]<r(i[d])&&(e.offsets.popper[d]=r(i[d])-o[a]),o[d]>r(i[s])&&(e.offsets.popper[d]=r(i[s])),e}},arrow:{order:500,enabled:!0,fn:function(e,t){if(!F(e.instance.modifiers,'arrow','keepTogether'))return e;var o=t.element;if('string'==typeof o){if(o=e.instance.popper.querySelector(o),!o)return e;}else if(!e.instance.popper.contains(o))return console.warn('WARNING: `arrow.element` must be child of its popper element!'),e;var i=e.placement.split('-')[0],n=e.offsets,r=n.popper,p=n.reference,s=-1!==['left','right'].indexOf(i),d=s?'height':'width',a=s?'top':'left',f=s?'left':'top',l=s?'bottom':'right',m=O(o)[d];p[l]-m<r[a]&&(e.offsets.popper[a]-=r[a]-(p[l]-m)),p[a]+m>r[l]&&(e.offsets.popper[a]+=p[a]+m-r[l]);var h=p[a]+p[d]/2-m/2,g=h-c(e.offsets.popper)[a];return g=_(z(r[d]-m,g),0),e.arrowElement=o,e.offsets.arrow={},e.offsets.arrow[a]=Math.round(g),e.offsets.arrow[f]='',e},element:'[x-arrow]'},flip:{order:600,enabled:!0,fn:function(e,t){if(W(e.instance.modifiers,'inner'))return e;if(e.flipped&&e.placement===e.originalPlacement)return e;var o=w(e.instance.popper,e.instance.reference,t.padding,t.boundariesElement),i=e.placement.split('-')[0],n=L(i),r=e.placement.split('-')[1]||'',p=[];switch(t.behavior){case fe.FLIP:p=[i,n];break;case fe.CLOCKWISE:p=K(i);break;case fe.COUNTERCLOCKWISE:p=K(i,!0);break;default:p=t.behavior;}return p.forEach(function(s,d){if(i!==s||p.length===d+1)return e;i=e.placement.split('-')[0],n=L(i);var a=e.offsets.popper,f=e.offsets.reference,l=V,m='left'===i&&l(a.right)>l(f.left)||'right'===i&&l(a.left)<l(f.right)||'top'===i&&l(a.bottom)>l(f.top)||'bottom'===i&&l(a.top)<l(f.bottom),h=l(a.left)<l(o.left),c=l(a.right)>l(o.right),g=l(a.top)<l(o.top),u=l(a.bottom)>l(o.bottom),b='left'===i&&h||'right'===i&&c||'top'===i&&g||'bottom'===i&&u,y=-1!==['top','bottom'].indexOf(i),w=!!t.flipVariations&&(y&&'start'===r&&h||y&&'end'===r&&c||!y&&'start'===r&&g||!y&&'end'===r&&u);(m||b||w)&&(e.flipped=!0,(m||b)&&(i=p[d+1]),w&&(r=j(r)),e.placement=i+(r?'-'+r:''),e.offsets.popper=se({},e.offsets.popper,S(e.instance.popper,e.offsets.reference,e.placement)),e=N(e.instance.modifiers,e,'flip'))}),e},behavior:'flip',padding:5,boundariesElement:'viewport'},inner:{order:700,enabled:!1,fn:function(e){var t=e.placement,o=t.split('-')[0],i=e.offsets,n=i.popper,r=i.reference,p=-1!==['left','right'].indexOf(o),s=-1===['top','left'].indexOf(o);return n[p?'left':'top']=r[t]-(s?n[p?'width':'height']:0),e.placement=L(t),e.offsets.popper=c(n),e}},hide:{order:800,enabled:!0,fn:function(e){if(!F(e.instance.modifiers,'hide','preventOverflow'))return e;var t=e.offsets.reference,o=T(e.instance.modifiers,function(e){return'preventOverflow'===e.name}).boundaries;if(t.bottom<o.top||t.left>o.right||t.top>o.bottom||t.right<o.left){if(!0===e.hide)return e;e.hide=!0,e.attributes['x-out-of-boundaries']=''}else{if(!1===e.hide)return e;e.hide=!1,e.attributes['x-out-of-boundaries']=!1}return e}},computeStyle:{order:850,enabled:!0,fn:function(e,t){var o=t.x,i=t.y,n=e.offsets.popper,p=T(e.instance.modifiers,function(e){return'applyStyle'===e.name}).gpuAcceleration;void 0!==p&&console.warn('WARNING: `gpuAcceleration` option moved to `computeStyle` modifier and will not be supported in future versions of Popper.js!');var s,d,a=void 0===p?t.gpuAcceleration:p,f=r(e.instance.popper),l=g(f),m={position:n.position},h={left:V(n.left),top:V(n.top),bottom:V(n.bottom),right:V(n.right)},c='bottom'===o?'top':'bottom',u='right'===i?'left':'right',b=B('transform');if(d='bottom'==c?-l.height+h.bottom:h.top,s='right'==u?-l.width+h.right:h.left,a&&b)m[b]='translate3d('+s+'px, '+d+'px, 0)',m[c]=0,m[u]=0,m.willChange='transform';else{var y='bottom'==c?-1:1,w='right'==u?-1:1;m[c]=d*y,m[u]=s*w,m.willChange=c+', '+u}var v={"x-placement":e.placement};return e.attributes=se({},v,e.attributes),e.styles=se({},m,e.styles),e},gpuAcceleration:!0,x:'bottom',y:'right'},applyStyle:{order:900,enabled:!0,fn:function(e){return U(e.instance.popper,e.styles),Y(e.instance.popper,e.attributes),e.offsets.arrow&&U(e.arrowElement,e.offsets.arrow),e},onLoad:function(e,t,o,i,n){var r=x(n,t,e),p=E(o.placement,r,t,e,o.modifiers.flip.boundariesElement,o.modifiers.flip.padding);return t.setAttribute('x-placement',p),U(t,{position:'absolute'}),o},gpuAcceleration:void 0}}},le});
diff --git a/library/simplepie/README.markdown b/library/simplepie/README.markdown
deleted file mode 100644
index e5ca021ce..000000000
--- a/library/simplepie/README.markdown
+++ /dev/null
@@ -1,53 +0,0 @@
-# SimplePie
-
-## Authors and contributors
-
-* [Ryan Parman](http://ryanparman.com)
-* [Geoffrey Sneddon](http://gsnedders.com)
-* [Ryan McCue](http://ryanmccue.info)
-* [Michael Shipley](http://michaelpshipley.com)
-* [Steve Minutillo](http://minutillo.com/steve/)
-
-
-## License
-
-[New BSD license](http://www.opensource.org/licenses/bsd-license.php)
-
-
-## Project status
-
-SimplePie is currently maintained by Ryan McCue.
-
-At the moment, there isn't a lot of active development happening. If the community decides that SimplePie is a valuable tool, then the community will come together to maintain it into the future.
-
-If you're interested in getting involved with SimplePie, please get in touch with Ryan McCue.
-
-
-## What comes in the package?
-
-1. `simplepie.inc` - The SimplePie library. This is all that's required for your pages.
-2. `README.markdown` - This document.
-3. `LICENSE.txt` - A copy of the BSD license.
-4. `compatibility_test/` - The SimplePie compatibility test that checks your server for required settings.
-5. `demo/` - A basic feed reader demo that shows off some of SimplePie's more noticable features.
-6. `idn/` - A third-party library that SimplePie can optionally use to understand Internationalized Domain Names (IDNs).
-7. `test/` - SimplePie's unit test suite.
-
-
-## To start the demo
-
-1. Upload this package to your webserver.
-2. Make sure that the cache folder inside of the demo folder is server-writable.
-3. Navigate your browser to the demo folder.
-
-
-## Need support?
-
-For further setup and install documentation, function references, etc., visit:
-[http://simplepie.org/wiki/](http://simplepie.org/wiki/)
-
-For bug reports and feature requests, visit:
-[http://github.com/rmccue/simplepie/issues](http://github.com/rmccue/simplepie/issues)
-
-Support mailing list -- powered by users, for users.
-[http://tech.groups.yahoo.com/group/simplepie-support/](http://tech.groups.yahoo.com/group/simplepie-support/)
diff --git a/library/simplepie/compatibility_test/COMPATIBILITY README.txt b/library/simplepie/compatibility_test/COMPATIBILITY README.txt
deleted file mode 100644
index 5b2498992..000000000
--- a/library/simplepie/compatibility_test/COMPATIBILITY README.txt
+++ /dev/null
@@ -1,7 +0,0 @@
-SIMPLEPIE COMPATIBILITY TEST
-
-1) Upload sp_compatibility_test.php to the web-accessible root of your website.
-For example, if your website is www.example.com, upload it so that you can get
-to it at www.example.com/sp_compatibility_test.php
-
-2) Open your web browser and go to the page you just uploaded. \ No newline at end of file
diff --git a/library/simplepie/compatibility_test/sp_compatibility_test.php b/library/simplepie/compatibility_test/sp_compatibility_test.php
deleted file mode 100644
index a7a7f5fde..000000000
--- a/library/simplepie/compatibility_test/sp_compatibility_test.php
+++ /dev/null
@@ -1,330 +0,0 @@
-<?php
-if (isset($_GET['logopng']))
-{
- $data='iVBORw0KGgoAAAANSUhEUgAAAZAAAAAtCAYAAACAnD3TAAAABHNCSVQICAgIfAhkiAAAAAlwSFlzAAALEgAACxIB0t1+/AAAABZ0RVh0Q3JlYXRpb24gVGltZQAwMi8wMy8wNnKU/JIAAAAfdEVYdFNvZnR3YXJlAE1hY3JvbWVkaWEgRmlyZXdvcmtzIDi1aNJ4AAAR6ElEQVR4nO1dzYrrSJb+TtP79Buk5gnSRbvp1ZC6q4GB4bqWvbq+m1kMDDdr0dCLGcoJDTXUpnxp6Fle52pWQ/syMNAwUEoaLhTtppxPUPITtL0vV8wiTthy6IQUkkOynKkPhDOl+DmKv3Pi/IRIKYUePXr06NGjKn5+bgK6DiKKAEwAbAAslFLpGcm5KBBRDCAGkEK33eac9PQIAyKaAIgArJRSi0BlRqg4z4howHkGnGcVgpYeFaCUepEX9KCL+Ro60gyhB7TiKz033SXvNIZerFXmis9Ey8SiY37mtolMf5+7ny75AjC3+nXC9wcAEuvZ1LNM5zwDMLWeqUx9K6u+6Nzt89KuF7UDIaIhgDvohfbKegYAa+hJMFVaArqz0l0T0VB1V9K5A3AdqjCW8O4cjzfQE3il5J3F1Pp/HIouX2TonyDTLtzXjwDuOtyXnQPvEt5Yt8fQTGUC4LZm0UXz7EtHnjGAG+HerCYNwVAyb3yQKqXmgchpFEcMhP46+hbAR/WLZdBOoL+OIhwkwCG09HDDvwYrAFv+TQAk6hfLYCoP3nZ/KEl2DT1B3hDRZ0yzjYFw77liAvcE3oOIHnBgugY2I7tCi2BhYSHQYXALzeRaZ2xdREaFtIdSamoli4SsA+u3DorKrZ0no0I1aGthHsJj3hTgEZopN4oQ7XO8A/lJb/HpL6Mb9cvl29qE/WWUVQ+9htzZNob8ewvgHZeTAHgAsFC/rM9MiGiMcuZh4yUxChd82+ANgDERxV2Q6FkCLGIeBn0fH5Ag317T9skIA2aI31q3W1mYLwGh2sdmIAYT+m40BPC5+tUy9Sbqu9EEWqJ7XYWIAsR8fUPfjd4DmKlf1WIkVXdUZieUq0spldSo/yXgCsCCVQ8b6DbM7joeW6RlhoCqvBcCn/aS5l4SoO4686yMlqg+OS8CUYhCfnb03+7oGmKHH+jTaE6fRs7K6NNoSJ9GM/o0+ht2+IAdXlvlhLgG2OFLpqeSbpG3adLk2AJ4D+AVX5/z/2tog+8GWorN4n2Vup8xnhz3r3FQg9ht14pu2qGnN9hCMzJDf9I8Rc8HvLtcZ25tEUairzPP7DxPz0i4S89NgC+OdyA7MY22Cfx5lOJgZB5Aq5xsO0bTGAD4hv48eg3grfp7r91R7LovqFsWAO5YBQKl1JwNrmMAiVLq7Aa6DuBeKTXlNkqRt21MoJnFHfQuLoZmyEHcPT0wddx/gDaab4A9o+lRHTF03w4AzFQAt/Y680wplRLRKxxcf6en0hEQK2ih1IatMoKU7pIYoQ8DMYj4qutpERIxgO8pGb1V8bLOwvRYpKvPehWxUWleo45nDaXUhojmYHtVBjfmOTQjaZvpSkbxR6XUJHsjxML3EpHxTgxd7hwV5xkvtEloWk4Fj/3Evs9M0k6bS3dJOFZh/XhR1wA/4o/0f6NJjfcelifp4YFUuskeUK2D1ZWSt9e0XUp69HgZsHcgK1ze4vqB/jSC+ofl3PFcMrZdscdQEpIQVotEADauHQ4vcoA7fkLKY1yfK+XzLDtGAb0lcOWppdY8kRZAVleu6/QzEUVVdyms1hsCbsky05epb/mZcYUq+WyaiuhqGuYdLl3ibhuZvq8073kuBV0rJNgMpNHKGsQH+t9Rqv5xmQjPpHuAlkrjsoLZBTjLVOdmAnNsSczXtZUP0Hr3KbRaZQIr8ImItmC7S7ajedCM+cqpDInoCVr/PC+jX8hbFFwnxXPUAtczRsbbw44raIAWSfhJfDMT0TRLC9Nh+ihHC0/SMXT/230LcLAi05XzTuQ0H7nsVea+aTtTth30uoZW98yscRMz/REcquZM2xo7xkRKx2mnmX9TtlVETNcge99RxIDLuDPvkHnniUW7c54V0Gfa1SDh3xiyl1Fkv5OQLrGZnEBbo/Ek3I93yI+XNfRYydVNRGYeSeNwC902c2iBOoZf++TaIlevUofDFOl/Rt/CY1HtKDYAPlP/lDesE1EK2RPriyKDHRHNkNfxv1JKJUS0QbjguEelVMx1TuEfhPSQ1e0TUYL8wvHKDAJemBLkI3iz2EIf7ZI6aLk3jIAHusswOLPrUUrtlcBVaSlIswcRrYTyCvu4Ii17xwsiWiCcu/oWWjrf8GI1h9/YemKaNryw/1Chzkfod/Yda4/QC9TKou1RKRVXHLeA9poaAqXzLHfaq1KKuJ3+aD26h16/TrHTvldK7W08jgDko3nnC9e7WGmk+pw0eo7dLGz3+iLs57oLthvvqgEX3LauAXbOhnc1wrTEG6dInRcysvo2YzeIK+R7Y0kMZZijfKBdwd+YWdQ+ZfWEpsVVp486bOFJS9ZhI6T34RUOO4Eh/MfWTYamqGKdtzXyRAg37m94sQTqqc1DqNold3S73EhIU1fFWgheA3wCnt9lVOE5Qa0EQU+EsBnIpgOM4JQrpv8e5bxweMsnBbLZi8I5IXkP+WDvdlwEHnC+EvOtp5urq97CCdYQLS4UqmV5EfOVWK8zi15o1O3/28xiUhVV8iU16yhC3XcOhalwz2YgEqNqhIGgmsfihH+bbMOkLIHNQJIOMIFTL3srbDCB3r7ZuOEtdAh8Aa2+eRCebTPPJcmniAk8cL574dkV/AaR5HppypXo8SkzFu6tPQx3wWlxeX55GORD0mLyfeF4bgJXpfFR1P9POAS7SpgIumoTNGkuF4qeZ/PXWTSfAPwdgM8gz724RpllWOE4WDQLu01WOA6MBLSDTZT5P9cvTTgC8Pi1BZktdJ9L42nMeVw7irc4BEm/hR5zJnjat33SMrptI3pphgtATP81GqpfL48GPOv07yBvEd8R0eLUgWF07Wy4sqOhV5nnM4GOoi353Pi8E5GkZ/bZztsS/xZsvGc1mK1PLtzVOAY84CepBqWlQpoj8EIhbf+nPF6kfooLisz20zf2w4zeOkV+fBSpIfZjk4gekW930/9voXdcic3EOWbHrnOesWdJ+vnYKiO205Rg/10PthnZ9V/57J6rINPGMfL2uZXwTolAV4TD4mm3dVNH8kiCycwE4PLONztGruAe84+Cof3of9/2KcPRDkT9erl+BmosYCerR7hRPzraYhF6MBcgPSGvNIALGYhj4mdd/KQdg5QH0CqzBMD3jufzFmk5FVK524zRPhWe2xJqZZzo5ZYI90zw5lwp5fpw1yl1hoCr/hC2jFMg7axiYG+g9kkfArFwL8n8Xbarz2LY1lr2s9ydH5F0IEjw1CsueOcJ8ttWoFv2kNAIqce9gttm8Oixi2tTp1yGSLi3cvxdlq/HZULq44h/2xyrdeuSBOLW1rI8A3kedpDY9cIsnU0cj29ZzXVpKDMCS9JIFYnGB0/ws5u0QYsv4qKHTQdhhcQJhvS2kJybAAkOgccs5pHwrCkGkrNleI4/l/32ltWWjUJiIIsOMIDTrwLwoJEM0kC5a+8loo6aoMri+REcj9ABWtrAudUuThDRgIjmRJQSkeIrweXGd7UBWy1sbA2RdX/bxPduXA4gHtjwWiY5ZQDazb9RgTj3SVv1z8s1/edohQ5PkhDgE2XHyBsvr6A9cy5xJ+KCJPUP2WA9RLXt8xoHfXYCbSitMqlC0tIEUo80bdnKKqEgqKwLB6B2GStYbcRCpD0WmxqH0nja8pwYMB25PszMuzscTke38Q0RbZqKnJe/ib7DDJd9Aq1vR08gG4MnuCwGUscz5DXqRVLvPXcCoi4tTSA9NwF1wFHbU1QLKuuhkSAfCR8hv7AnLdBicAXPyH72Xowhf14BAD4Q0aqJ3VNehQUYNdYle2N5NRQ3qLT9O9nT5hngXIZtCbVpeWH9OBHuGd9+KQ6jTcRnrr8I0vgaIq/C6tKcOIrjYPVxDHc/J014ZokMRL1bbrHDrAOMoO5VxQPBlTaqUMZzwxrdmSxetBR4f0UV64s90qQVy2wczCil897G7NvvMraeFV04nZfdqm3PzAHy7dmVOQEI6xYLxBNH+is0MAZkFRZg1Fh36Ki+twCp+s3SFeshoUuDoi7SGnnMYXorHIzUR0eFk/ABnIZQSssJiAKUYSNtoMxTsIbjPbuwQF8IVjhmGJH1fH2Gj5DdQ8+H/RpV1p9KqQURfQEgF8gKPjsv5Hs4GYj6zXJL/zGaoqOSSwGmFdN3zcOnDJJBNK1RTtKALaMuQtGyRl5qjFHTnneCd0yTiIV7acs01IHUlk1FdddBgmM7nO2S3rqgWXdOKKVm7CAkrRVDBBwvsg3EEPLb5Xv8hBV+Ai7kStRvly6XNhfiiunPhgIdZlqSNQlLyUlIGiw7Fe6NC9qtbFGom69JSDSljrRdWqAj4V6Xdv82LbYxujFaG9olugT/oEJRIQMBAOwwuRCD+gY7OZCNiGbSKaq8sEwdb96lwW0QO+6X0SrtspxBfw0HpTVJSyLcu4I2IEaZMo3bsERL5PjbwOewyEbA47XKkfWdcN8tOHMsaZWQAngs4mXPT0XO+M27iBw41qeMEbQyRt02EIb69+UTfTmaoNvHfGwAxOp+6fJAeAfsP9aUQEtsA+iFSzI8rtk1LjihNWGkTmlArT3c86TnN5n2APRiOeQ6ronos+pkeqEWLZ4uiK40NwB+EPpTCia9Jtp/zjYWnifCvaZR1P+AnptR6Eoz7XAqJJf4rTkosEVEJc+lgyoNmhYoc7Eo0EHNwIEZxNDz4jV08O6YAwU30GrgNJN3UlCPC1EVggEPBgIA6n75kf5tNEE3Y0M08/jdUjqe2JZgr5E/eVPC/HSygmLOJ7jWkuI4RkD6EtmXcPuaN+I80SQtbECs8sU1V7lzxymtwHkEqXcFpx+v+eRgUeLkU3CLvHP25SAvTM34K48x9DhL/EkGoA/ejCHT3bRtNRXuXfMJyxvo9rCPwZcWcUB/PbFpiX4h1H2D/MnUBmbs3uHwCeYt9DsM4Z4DCf+mwrOy9smhXIXFUL9bPmCHYcfUWQvsELmYByP2fUfGFt1zHLiCO0DMl9Z5GFKCYN5g2VX6bgM5DugWMjN7OoPUbOCSjGfAPg5AOiT0NfS7SDvtJPN3WpC3ztcLAffBm2s0PMcKdk7vcGiPyHqWOPK0oc5eoF6sTrZfTXu7mMeDYYQ12ycHbwYCAOqr5RN2iHD+Axc32GGivlp+rr5yqq0MqkgOW2i/+UvxzHqoEF06RbUB2qQH0hTN0TKD/LEcCWlFWiYV6GgDa+t779MTyipjjNEJZWfR5hwrc+ePrP9dc6lxBsILehWmOqzoJfiEvCqxavvkUImBAID6erlVXy9fsXE9PQPjmGKHSH3t523FE+y9R9JH6AMBk4I0W7gZUtmilZ74XKpP0i1nsT+3KhOpKkmpNh7h3iWkPsQ5aEFgWnLIlF3WH/f8/YwUuh2LmMgWwOclzHqL4rYpe1eftrDrO7KJ8HlHvl6IDzheGOcobjPXu6f8m6CcET9Bz7GyBblonhV5lqXW/9MSmo7o4LEgpW+KgRz1Obvt+qxV5gNsK/j193vIh51OUaF9JJBSuQ+RVQLdjd4wIdFJBRVjBc2dF2pWuuMQwZ4gMQ4G2gH0gEtR/UDAxsC6d3vb/xbHBw0uoM+kqiXFsXeHKS/bDivojzuldcrtGi0soY1xOJDOlLuwy+XxMUbeUH1SW1cFOxPY6rP30LQb2lbQX6tLHWWY945wmJeJ+XUJSezlNYGeJ0bHnnKeuSf9pj+zbW7KEOttEtyvExyrss0YyNEjzT+lVKveNJmxGOEw5xNwUKFNtzDON9DvmEK/p3PsVm2fXP5TGci+oH8d3WYIiQIUmUBP3oX6/bKqdHaxcDCQV31E8cuAg4Hcdyjo81lDmH+PVT/z+pLg5YXlA/X7pfkQO+hfRjc4SJWGg8ZCthTHW2DNYf+w7FIAVI8ePV4ObLtCJzQTXUUwBpKF+sPyCVrfWTUqvEePHj1agR3nwsHGtgdT0iJJF4dGGEiPHj16dBlsN/ieiMxBngPkvwlyjmDHi0LPQHr06PESEfPvLdwxNj3zKEFlN94ePXr0eAYoO91gi9Pial4EegbSo0ePl4g53DEQJtgxbY2aC0Wvwuoe7DNxHnEZ33voEQYJdGCjMeY+ofcECg4+P8zETwyhQw9M/MS8Zx5+CBYH0qNHjx49Xhb+H6JWCt7+7okIAAAAAElFTkSuQmCC';
- header('Content-type: image/png');
- echo base64_decode($data);
- exit;
-}
-else if (isset($_GET['background']))
-{
- $data='R0lGODlhMAEeAeYAAP///8ni6cTf5+72+PD3+c3k6+nz9ufy9ev099Pn7bnZ48bg6LfY4uHv8/r8/f3+/v7//7bX4cjh6fj7/Mvj6vz9/rva4+z19/X6+/f7/Pn8/fb6+7jZ4vv9/bra473b5Lzb5LXX4b7c5b/c5e31+NTo7tvs8dfq7/H3+bjY4tnq79Hm7c/l69nr8PL4+t7t8sDd5cLe5uPw9Nvr8Mri6fP4+tLn7er099Hm7O/2+dDm7OTw9OXx9Nbp7tbp7+Lv8+Du8szj6sXg57bY4d3s8djq7+jz9tzs8cPe58fh6M7k68Pf5+by9fz+/sDd5vT5+vT5+97t8bbY4trr8P7+/v7+/+Pw8+Xx9dXo7sHe5vH4+fP5+sHd5t/u8s/l7AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAACH5BAAAAAAALAAAAAAwAR4BAAf/gCGCg4SFhoeIiYqLjI2Oj5CRkpOUlZaXmJmam5ydnp+goaKNEaWmp6ipqqusra6vsLGys7S1tre4ubq7vL2+v8DBwsPExbBDyMnKy8zNzs/Q0dLT1NXW19jZ2tvc3d7KUuHi4+Tl5ufo6err7O3u7/Dx8vP09fb34wz6+/z9/v8AAwocSLCgwYMIEypcyLChw4cQI0qcSLGixYsYM2osmKKjx48gQ4ocSbKkyZMoU6pcybKly5cwY8qc+ZGDzZs4c+rcybOnz59AgwodSrSo0aNIkypdyrSp06dQo0qdSrWq1aAKsmrdyrWr169gw4odS7as2bNo06pdy7at27dw/+PKnUu3rt27ePOS9cC3r9+/gAMLHky4sOHDiBMrXsy4sePHkCNLnky5suXLmDNr3sz5sIXPoEOLHk26tOnTqFOrXs26tevXsGPLnk27tu3buHPr3s27t+/fqkEIH068uPHjyJMrX868ufPn0KNLn069uvXr2LNr3869u/fv4MOLb/6hvPnz6NOrX8++vfv38OPLn0+/vv37+PPr38+/v///AAYo4IAEFgifCAgmqOCCDDbo4IMQRijhhBRWaOGFGGao4YYcdujhhyCGKOKIJJZo4okoTjjCiiy26OKLMMYo44w01mjjjTjmqOOOPPbo449ABinkkEQWaeSRSCap5P+SNsLg5JNQRinllFRWaeWVWGap5ZZcdunll2CGKeaYZELpxJlopqnmmmy26eabcMYp55x01mnnnXjmqeeefPaZJheABirooIQWauihiCaq6KKMNuroo5BGKumklFZqqaBZZKrpppx26umnoIYq6qiklmrqqaimquqqrLbq6qubxiDrrLTWauutuOaq66689urrr8AGK+ywxBZr7LHI0orEssw26+yz0EYr7bTUVmvttdhmq+223Hbr7bfghtvsEuSWa+656Kar7rrstuvuu/DGK++89NZr77345quvuQL06++/AAcs8MAEF2zwwQgnrPDCDDfs8MMQRyzxxBRXbPH/xRhnrPHGHHeMsBAghyzyyCSXbPLJKKes8sost+zyyzDHLPPMNNdss8gL5Kzzzjz37PPPQAct9NBEF2300UgnrfTSTDft9NNQRy311FRXbfXVWGdNdBJcd+3112CHLfbYZJdt9tlop6322my37fbbcMctt9cS1G333XjnrffefPft99+ABy744IQXbvjhiCeu+OKMN+7445BHLvnklFcOeACYZ6755px37vnnoIcu+uikl2766ainrvrqrLfu+uuwxy777LTXbvvtuI9Ow+689+7778AHL/zwxBdv/PHIJ6/88sw37/zz0EffOwXUV2/99dhnr/323Hfv/ffghy/+//jkl2/++einr/767Lfv/vvwxy///PR/H8T9+Oev//789+///wAMoAAHSMACGvCACEygAhfIwAbmrwAQjKAEJ0jBClrwghjMoAY3yMEOevCDIAyhCEdIwhKa8IQoTKEKV8jCFrrwhTDcoBJmSMMa2vCGOMyhDnfIwx768IdADKIQh0jEIhrxiEhMYg1ZwMQmOvGJUIyiFKdIxSpa8YpYzKIWt8jFLnrxi2AMoxid6IUymvGMaEyjGtfIxja68Y1wjKMc50jHOtrxjnjMox73eEYd+PGPgAykIAdJyEIa8pCITKQiF8nIRjrykZCMpCQnSUlA4uCSmMykJjfJyU568v+ToAylKEdJylKa8pSoTKUqV8nKVmZyBbCMpSxnScta2vKWuMylLnfJy1768pfADKYwh0nMYhpTljZIpjKXycxmOvOZ0IymNKdJzWpa85rYzKY2t8nNbnrzm8tMgDjHSc5ymvOc6EynOtfJzna6853wjKc850nPetrznvjMpz73yc9++vOfAA2oQNtZgoIa9KAITahCF8rQhjr0oRCNqEQnStGKWvSiGM2oRjd6UCx49KMgDalIR0rSkpr0pChNqUpXytKWuvSlMI2pTGdKU5D24KY4zalOd8rTnvr0p0ANqlCHStSiGvWoSE2qUpfK1Kbm1AdQjapUp0rVqlr1qlj/zapWt8rVrnr1q2ANq1jHStaymlWqJ0irWtfK1ra69a1wjatc50rXutr1rnjNq173yte++vWvay2CYAdL2MIa9rCITaxiF8vYxjr2sZCNrGQnS9nKWvaymCWsCjbL2c569rOgDa1oR0va0pr2tKhNrWpXy9rWuva1sI1tZ1tA29ra9ra4za1ud8vb3vr2t8ANrnCHS9ziGve4yE2ucm07heY697nQja50p0vd6lr3utjNrna3y93ueve74A2veMf73BmY97zoTa9618ve9rr3vfCNr3znS9/62ve++M2vfvfLX/Sa4L8ADrCAB0zgAhv4wAhOsIIXzOAGO/jBEI6w/4QnTOEKB/gIGM6whjfM4Q57+MMgDrGIR0ziEpv4xChOsYpXzOIWu1jDRIixjGdM4xrb+MY4zrGOd8zjHvv4x0AOspCHTOQiG/nIM46CkpfM5CY7+clQjrKUp0zlKlv5yljOspa3zOUue/nLYGbyC8ZM5jKb+cxoTrOa18zmNrv5zXCOs5znTOc62/nOeM5zmbvA5z77+c+ADrSgB03oQhv60IhOtKIXzehGO/rRkI60pP0MhEpb+tKYzrSmN83pTnv606AOtahHTepSm/rUqE61qld96Qa4+tWwjrWsZ03rWtv61rjOta53zete+/rXwA62sIdN7GIb+9jITrayl//N7GY7O9c/iLa0p03talv72tjOtra3ze1ue/vb4A63uMdN7nKb+9zTtoK6183udrv73fCOt7znTe962/ve+M63vvfN7377+98AZ7cMBk7wghv84AhPuMIXzvCGO/zhEI+4xCdO8Ypb/OIYz3jBd8Dxjnv84yAPuchHTvKSm/zkKE+5ylfO8pa7/OUwj7nMPc6Dmtv85jjPuc53zvOe+/znQA+60IdO9KIb/ehIT7rSl37zKzj96VCPutSnTvWqW/3qWM+61rfO9a57/etgD7vYx052qDPh7GhPu9rXzva2u/3tcI+73OdO97rb/e54z7ve9873vqf9AIAPvOAHT/j/whv+8IhPvOIXz/jGO/7xkI+85CdP+cpb/vKYz7zmN8/5znv+86BfvBFGT/rSm/70qE+96lfP+ta7/vWwj73sZ0/72tv+9rjPfekNwPve+/73wA++8IdP/OIb//jIT77yl8/85jv/+dCPvvSnT/3qW//62M++9rfP/ePf4PvgD7/4x0/+8pv//OhPv/rXz/72u//98I+//OdP//qHHwH4z7/+98///vv//wAYgAI4gARYgAZ4gAiYgAq4gAzYgA74gBAYgRI4gRRYgRZ4gRg4gBewgRzYgR74gSAYgiI4giRYgiZ4giiYgiq4gizYgi74gjAYgzI4gzRYgzZ4gziY/4M6uIMmSAI++INAGIRCOIREWIRGeIRImIRKuIRM2IRO+IRQGIVSOIVUCIQDcIVYmIVauIVc2IVe+IVgGIZiOIZkWIZmeIZomIZquIZs2IZu+IZwGIdyOId0WId2eIdimAN6uId82Id++IeAGIiCOIiEWIiGeIiImIiKuIiM2IiO+IiQyIcEMImUWImWeImYmImauImc2Ime+ImgGIqiOIqkWIqmeIqomIqquIqs2Iqu+IqwGIuyOIueiAK2eIu4mIu6uIu82Iu++IvAGIzCOIzEWIzGeIzImIzKuIzMiIta8IzQGI3SOI3UWI3WeI3YmI3auI3c2I3e+I3gGI7iOP+O5FiO0egC6JiO6riO7NiO7viO8BiP8jiP9FiP9niP+JiP+riP/NiP/qiONRCQAjmQBFmQBnmQCJmQCrmQDNmQDvmQEBmREjmRFFmRFnmRA7kFGrmRHNmRHvmRIBmSIjmSJFmSJnmSKJmSKrmSLNmSLvmSMMmRTzCTNFmTNnmTOJmTOrmTPNmTPvmTQBmUQjmURFmURnmUSJmUNQkFTNmUTvmUUBmVUjmVVFmVVnmVWJmVWrmVXNmVXvmVYBmWYumUGFCWZnmWaJmWarmWbNmWbvmWcBmXcjmXdFmXdnmXeJmXermXfNmXfvmXgBmYgjmYhFmYcLkBiJmYirmYjNn/mI75mJAZmZI5mZRZmZZ5mZiZmZq5mZzZmZ75maAZmqI5mqRZmqZ5mqg5mRmwmqzZmq75mrAZm7I5m7RZm7Z5m7iZm7q5m7zZm775m8AZnMI5nMRZnMZ5nMiZnMq5nLY5Ac75nNAZndI5ndRZndZ5ndiZndq5ndzZnd75neAZnuI5nuRZnuZ5nuiZnuq5nuzZnu6ZnRoQn/I5n/RZn/Z5n/iZn/q5n/zZn/75nwAaoAI6oARaoAZ6oAiaoAq6oAzaoA76oBAaofzpABRaoRZ6oRiaoRq6oRzaoR76oSAaoiI6oiRaoiZ6oiiaoiq6oizaoi76ojAaozI6ozT6oR1w/6M4mqM6uqM82qM++qNAGqRCOqREWqRGeqRImqRKuqRM2qRO+qRQGqVSOqVUWqVWeqVCWgFauqVc2qVe+qVgGqZiOqZkWqZmeqZomqZquqZs2qZu+qZwGqdyOqd0Wqd2eqd4mqd6WqZN0Kd++qeAGqiCOqiEWqiGeqiImqiKuqiM2qiO+qiQGqmSOql/+gCWeqmYmqmauqmc2qme+qmgGqqiOqqkWqqmeqqomqqquqqs2qqu+qqwGquyOqu0Wqu2GqpUkKu6uqu82qu++qvAGqzCOqzEWqzGeqzImqzKuqzM2qzO+qy7WgXSOq3UWq3Weq3Ymq3auq3c2q3e+q3gGv+u4jqu5Fqu5nqu6EqtELCu7Nqu7vqu8Bqv8jqv9Fqv9nqv+Jqv+rqv/Nqv/vqvABuwAjuwBFuwBnuwCJuwCruw9goADvuwEBuxEjuxFFuxFnuxGJuxGruxHNuxHvuxIBuyIjuyJFuyJnuyKJuyKruyLNuyLvuyMBuzMjuzNFuzNnuzOJuzOruzPNuzPvuzQBu0Qju0RFu0Rnu0SJu0Sru0TNu0Tvu0UBu1Uju1VFu1Vnu1WJu1Wru1XNu1Xvu1YBu2Yju2ZFu2Znu2aJu2aru2bNu2bvu2cBu3cju3dFu3dnu3eJu3eru3fNu3fvu3gBu4gju4hFu4hnu4iJu4irv/uIzbuI77uJAbuZI7uZRbuZZ7uZibuZq7uZzbuZ77uaAbuqI7uqRbuqZ7uqibuqq7uqzbuq77urAbu7I7u7Rbu7Z7u7ibu7q7u7zbu777u8AbvMI7vMRbvMZ7vMibvMq7vMzbvM77vNAbvdI7vdRbvdZ7vdibvdq7vdzbvd77veAbvuI7vuRbvuZ7vuibvuq7vuzbvu77vvAbv/I7v/Rbv/Z7v/ibv/q7v/zbv/77vwAcwAI8wARcwAZ8wAicwAq8wAzcwA78wBAcwRI8wRRcwRZ8wRicwRq8wRzcwR78wSAcwiI8wiRcwiZ8wiicwiq8wizcwi78wjAcwzI8wzRcFcM2fMM4nMM6vMM83MM+/MNArLmBAAA7';
- header('Content-type: image/gif');
- echo base64_decode($data);
- exit;
-}
-
-$php_ok = (function_exists('version_compare') && version_compare(phpversion(), '4.3.0', '>='));
-$pcre_ok = extension_loaded('pcre');
-$curl_ok = function_exists('curl_exec');
-$zlib_ok = extension_loaded('zlib');
-$mbstring_ok = extension_loaded('mbstring');
-$iconv_ok = extension_loaded('iconv');
-if (extension_loaded('xmlreader'))
-{
- $xml_ok = true;
-}
-elseif (extension_loaded('xml'))
-{
- $parser_check = xml_parser_create();
- xml_parse_into_struct($parser_check, '<foo>&amp;</foo>', $values);
- xml_parser_free($parser_check);
- $xml_ok = isset($values[0]['value']);
-}
-else
-{
- $xml_ok = false;
-}
-
-header('Content-type: text/html; charset=UTF-8');
-
-?><!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN">
-
-<html lang="en">
-<head>
-<title>SimplePie: Server Compatibility Test 1.2</title>
-
-<style type="text/css">
-body {
- font:14px/1.4em "Lucida Grande", Verdana, Arial, Helvetica, Clean, Sans, sans-serif;
- letter-spacing:0px;
- color:#333;
- margin:0;
- padding:0;
- background:#fff url(<?php echo pathinfo(__FILE__, PATHINFO_BASENAME); ?>?background) repeat-x top left;
-}
-
-div#site {
- width:550px;
- margin:20px auto 0 auto;
-}
-
-a {
- color:#000;
- text-decoration:underline;
- padding:0 1px;
-}
-
-a:hover {
- color:#fff;
- background-color:#333;
- text-decoration:none;
- padding:0 1px;
-}
-
-p {
- margin:0;
- padding:5px 0;
-}
-
-em {
- font-style:normal;
- background-color:#ffc;
-}
-
-ul, ol {
- margin:10px 0 10px 20px;
- padding:0 0 0 15px;
-}
-
-ul li, ol li {
- margin:0 0 7px 0;
- padding:0 0 0 3px;
-}
-
-h2 {
- font-size:18px;
- padding:0;
- margin:30px 0 10px 0;
-}
-
-h3 {
- font-size:16px;
- padding:0;
- margin:20px 0 5px 0;
-}
-
-h4 {
- font-size:14px;
- padding:0;
- margin:15px 0 5px 0;
-}
-
-code {
- font-size:1.1em;
- background-color:#f3f3ff;
- color:#000;
-}
-
-em strong {
- text-transform: uppercase;
-}
-
-table#chart {
- border-collapse:collapse;
-}
-
-table#chart th {
- background-color:#eee;
- padding:2px 3px;
- border:1px solid #fff;
-}
-
-table#chart td {
- text-align:center;
- padding:2px 3px;
- border:1px solid #eee;
-}
-
-table#chart tr.enabled td {
- /* Leave this alone */
-}
-
-table#chart tr.disabled td,
-table#chart tr.disabled td a {
- color:#999;
- font-style:italic;
-}
-
-table#chart tr.disabled td a {
- text-decoration:underline;
-}
-
-div.chunk {
- margin:20px 0 0 0;
- padding:0 0 10px 0;
- border-bottom:1px solid #ccc;
-}
-
-.footnote,
-.footnote a {
- font:10px/12px verdana, sans-serif;
- color:#aaa;
-}
-
-.footnote em {
- background-color:transparent;
- font-style:italic;
-}
-</style>
-
-<script type="text/javascript">
-// Sleight - Alpha transparency PNG's in Internet Explorer 5.5/6.0
-// (c) 2001, Aaron Boodman; http://www.youngpup.net
-
-if (navigator.platform == "Win32" && navigator.appName == "Microsoft Internet Explorer" && window.attachEvent) {
- document.writeln('<style type="text/css">img, input.image { visibility:hidden; } </style>');
- window.attachEvent("onload", fnLoadPngs);
-}
-
-function fnLoadPngs() {
- var rslt = navigator.appVersion.match(/MSIE (\d+\.\d+)/, '');
- var itsAllGood = (rslt != null && Number(rslt[1]) >= 5.5);
-
- for (var i = document.images.length - 1, img = null; (img = document.images[i]); i--) {
- if (itsAllGood && img.src.match(/\png$/i) != null) {
- var src = img.src;
- var div = document.createElement("DIV");
- div.style.filter = "progid:DXImageTransform.Microsoft.AlphaImageLoader(src='" + src + "', sizing='scale')";
- div.style.width = img.width + "px";
- div.style.height = img.height + "px";
- img.replaceNode(div);
- }
- img.style.visibility = "visible";
- }
-}
-</script>
-
-</head>
-
-<body>
-
-<div id="site">
- <div id="content">
-
- <div class="chunk">
- <h2 style="text-align:center;"><img src="<?php echo pathinfo(__FILE__, PATHINFO_BASENAME); ?>?logopng" alt="SimplePie Compatibility Test" title="SimplePie Compatibility Test" /></h2>
- <table cellpadding="0" cellspacing="0" border="0" width="100%" id="chart">
- <thead>
- <tr>
- <th>Test</th>
- <th>Should Be</th>
- <th>What You Have</th>
- </tr>
- </thead>
- <tbody>
- <tr class="<?php echo ($php_ok) ? 'enabled' : 'disabled'; ?>">
- <td>PHP&sup1;</td>
- <td>4.3.0 or higher</td>
- <td><?php echo phpversion(); ?></td>
- </tr>
- <tr class="<?php echo ($xml_ok) ? 'enabled, and sane' : 'disabled, or broken'; ?>">
- <td><a href="http://php.net/xml">XML</a></td>
- <td>Enabled</td>
- <td><?php echo ($xml_ok) ? 'Enabled, and sane' : 'Disabled, or broken'; ?></td>
- </tr>
- <tr class="<?php echo ($pcre_ok) ? 'enabled' : 'disabled'; ?>">
- <td><a href="http://php.net/pcre">PCRE</a>&sup2;</td>
- <td>Enabled</td>
- <td><?php echo ($pcre_ok) ? 'Enabled' : 'Disabled'; ?></td>
- </tr>
- <tr class="<?php echo ($curl_ok) ? 'enabled' : 'disabled'; ?>">
- <td><a href="http://php.net/curl">cURL</a></td>
- <td>Enabled</td>
- <td><?php echo (extension_loaded('curl')) ? 'Enabled' : 'Disabled'; ?></td>
- </tr>
- <tr class="<?php echo ($zlib_ok) ? 'enabled' : 'disabled'; ?>">
- <td><a href="http://php.net/zlib">Zlib</a></td>
- <td>Enabled</td>
- <td><?php echo ($zlib_ok) ? 'Enabled' : 'Disabled'; ?></td>
- </tr>
- <tr class="<?php echo ($mbstring_ok) ? 'enabled' : 'disabled'; ?>">
- <td><a href="http://php.net/mbstring">mbstring</a></td>
- <td>Enabled</td>
- <td><?php echo ($mbstring_ok) ? 'Enabled' : 'Disabled'; ?></td>
- </tr>
- <tr class="<?php echo ($iconv_ok) ? 'enabled' : 'disabled'; ?>">
- <td><a href="http://php.net/iconv">iconv</a></td>
- <td>Enabled</td>
- <td><?php echo ($iconv_ok) ? 'Enabled' : 'Disabled'; ?></td>
- </tr>
- </tbody>
- </table>
- </div>
-
- <div class="chunk">
- <h3>What does this mean?</h3>
- <ol>
- <?php if ($php_ok && $xml_ok && $pcre_ok && $mbstring_ok && $iconv_ok && $curl_ok && $zlib_ok): ?>
- <li><em>You have everything you need to run SimplePie properly! Congratulations!</em></li>
- <?php else: ?>
- <?php if ($php_ok): ?>
- <li><strong>PHP:</strong> You are running a supported version of PHP. <em>No problems here.</em></li>
- <?php if ($xml_ok): ?>
- <li><strong>XML:</strong> You have XMLReader support or a version of XML support that isn't broken installed. <em>No problems here.</em></li>
- <?php if ($pcre_ok): ?>
- <li><strong>PCRE:</strong> You have PCRE support installed. <em>No problems here.</em></li>
- <?php if ($curl_ok): ?>
- <li><strong>cURL:</strong> You have <code>cURL</code> support installed. <em>No problems here.</em></li>
- <?php else: ?>
- <li><strong>cURL:</strong> The <code>cURL</code> extension is not available. SimplePie will use <code>fsockopen()</code> instead.</li>
- <?php endif; ?>
-
- <?php if ($zlib_ok): ?>
- <li><strong>Zlib:</strong> You have <code>Zlib</code> enabled. This allows SimplePie to support GZIP-encoded feeds. <em>No problems here.</em></li>
- <?php else: ?>
- <li><strong>Zlib:</strong> The <code>Zlib</code> extension is not available. SimplePie will ignore any GZIP-encoding, and instead handle feeds as uncompressed text.</li>
- <?php endif; ?>
-
- <?php if ($mbstring_ok && $iconv_ok): ?>
- <li><strong>mbstring and iconv:</strong> You have both <code>mbstring</code> and <code>iconv</code> installed! This will allow SimplePie to handle the greatest number of languages. Check the <a href="http://simplepie.org/wiki/faq/supported_character_encodings">Supported Character Encodings</a> chart to see what's supported on your webhost.</li>
- <?php elseif ($mbstring_ok): ?>
- <li><strong>mbstring:</strong> <code>mbstring</code> is installed, but <code>iconv</code> is not. Check the <a href="http://simplepie.org/wiki/faq/supported_character_encodings">Supported Character Encodings</a> chart to see what's supported on your webhost.</li>
- <?php elseif ($iconv_ok): ?>
- <li><strong>iconv:</strong> <code>iconv</code> is installed, but <code>mbstring</code> is not. Check the <a href="http://simplepie.org/wiki/faq/supported_character_encodings">Supported Character Encodings</a> chart to see what's supported on your webhost.</li>
- <?php else: ?>
- <li><strong>mbstring and iconv:</strong> <em>You do not have either of the extensions installed.</em> This will significantly impair your ability to read non-English feeds, as well as even some English ones. Check the <a href="http://simplepie.org/wiki/faq/supported_character_encodings">Supported Character Encodings</a> chart to see what's supported on your webhost.</li>
- <?php endif; ?>
- <?php else: ?>
- <li><strong>PCRE:</strong> Your PHP installation doesn't support Perl-Compatible Regular Expressions. <em>SimplePie is a no-go at the moment.</em></li>
- <?php endif; ?>
- <?php else: ?>
- <li><strong>XML:</strong> Your PHP installation doesn't support XML parsing. <em>SimplePie is a no-go at the moment.</em></li>
- <?php endif; ?>
- <?php else: ?>
- <li><strong>PHP:</strong> You are running an unsupported version of PHP. <em>SimplePie is a no-go at the moment.</em></li>
- <?php endif; ?>
- <?php endif; ?>
- </ol>
- </div>
-
- <div class="chunk">
- <?php if ($php_ok && $xml_ok && $pcre_ok && $mbstring_ok && $iconv_ok) { ?>
- <h3>Bottom Line: Yes, you can!</h3>
- <p><em>Your webhost has its act together!</em></p>
- <p>You can download the latest version of SimplePie from <a href="http://simplepie.org/downloads/">SimplePie.org</a> and install it by <a href="http://simplepie.org/wiki/setup/start">following the instructions</a>. You can find example uses with <a href="http://simplepie.org/ideas/">SimplePie Ideas</a>.</p>
- <p>Take the time to read <a href="http://simplepie.org/wiki/setup/start">Requirements and Getting Started</a> to make sure you're prepared to use SimplePie. No seriously, read them.</p>
- <p class="footnote"><em><strong>Note</strong></em>: Passing this test does not guarantee that SimplePie will run on your webhost &mdash; it only ensures that the basic requirements have been addressed.</p>
- <?php } else if ($php_ok && $xml_ok && $pcre_ok) { ?>
- <h3>Bottom Line: Yes, you can!</h3>
- <p><em>For most feeds, it'll run with no problems.</em> There are <a href="http://simplepie.org/wiki/faq/supported_character_encodings">certain languages</a> that you might have a hard time with though.</p>
- <p>You can download the latest version of SimplePie from <a href="http://simplepie.org/downloads/">SimplePie.org</a> and install it by <a href="http://simplepie.org/wiki/setup/start">following the instructions</a>. You can find example uses with <a href="http://simplepie.org/ideas/">SimplePie Ideas</a>.</p>
- <p>Take the time to read <a href="http://simplepie.org/wiki/setup/start">Requirements and Getting Started</a> to make sure you're prepared to use SimplePie. No seriously, read them.</p>
- <p class="footnote"><em><strong>Note</strong></em>: Passing this test does not guarantee that SimplePie will run on your webhost &mdash; it only ensures that the basic requirements have been addressed.</p>
- <?php } else { ?>
- <h3>Bottom Line: We're sorry…</h3>
- <p><em>Your webhost does not support the minimum requirements for SimplePie.</em> It may be a good idea to contact your webhost, and ask them to install a more recent version of PHP as well as the <code>xmlreader</code>, <code>xml</code>, <code>mbstring</code>, <code>iconv</code>, <code>curl</code>, and <code>zlib</code> extensions.</p>
- <?php } ?>
- </div>
-
- <div class="chunk">
- <p class="footnote">&sup1; &mdash; SimplePie 2 will not support PHP 4.x. The core PHP team has discontinued PHP 4.x patches and support. <a href="http://simplepie.org/blog/2007/07/13/simplepie-is-going-php5-only/">Read the announcement.</a></p>
- <p class="footnote">&sup2; &mdash; Some recent versions of the PCRE (PERL-Compatible Regular Expression) engine compiled into PHP have been buggy, and are the source of PHP segmentation faults (e.g. crashes) which cause random things like blank, white screens. Check the <a href="http://simplepie.org/support/">Support Forums</a> for the latest information on patches and ongoing fixes.</p>
- </div>
-
- </div>
-
-</div>
-
-</body>
-</html> \ No newline at end of file
diff --git a/library/simplepie/create.php b/library/simplepie/create.php
deleted file mode 100644
index 908ed182b..000000000
--- a/library/simplepie/create.php
+++ /dev/null
@@ -1,178 +0,0 @@
-<?php
-
-require_once 'simplepie.inc';
-
-function normalize_character_set($charset)
-{
- return strtolower(preg_replace('/(?:[^a-zA-Z0-9]+|([^0-9])0+)/', '\1', $charset));
-}
-
-function build_character_set_list()
-{
- $file = new SimplePie_File('http://www.iana.org/assignments/character-sets');
- if (!$file->success && !($file->method & SIMPLEPIE_FILE_SOURCE_REMOTE === 0 || ($file->status_code === 200 || $file->status_code > 206 && $file->status_code < 300)))
- {
- return false;
- }
- else
- {
- $data = explode("\n", $file->body);
- unset($file);
-
- foreach ($data as $line)
- {
- // New character set
- if (substr($line, 0, 5) === 'Name:')
- {
- // If we already have one, push it on to the array
- if (isset($aliases))
- {
- for ($i = 0, $count = count($aliases); $i < $count; $i++)
- {
- $aliases[$i] = normalize_character_set($aliases[$i]);
- }
- $charsets[$preferred] = array_unique($aliases);
- natsort($charsets[$preferred]);
- }
-
- $start = 5 + strspn($line, "\x09\x0A\x0B\xC\x0D\x20", 5);
- $chars = strcspn($line, "\x09\x0A\x0B\xC\x0D\x20", $start);
- $aliases = array(substr($line, $start, $chars));
- $preferred = end($aliases);
- }
- // Another alias
- elseif(substr($line, 0, 6) === 'Alias:')
- {
- $start = 7 + strspn($line, "\x09\x0A\x0B\xC\x0D\x20", 7);
- $chars = strcspn($line, "\x09\x0A\x0B\xC\x0D\x20", $start);
- $aliases[] = substr($line, $start, $chars);
-
- if (end($aliases) === 'None')
- {
- array_pop($aliases);
- }
- elseif (substr($line, 7 + $chars + 1, 21) === '(preferred MIME name)')
- {
- $preferred = end($aliases);
- }
- }
- }
-
- // Compatibility replacements
- $compat = array(
- 'EUC-KR' => 'windows-949',
- 'GB2312' => 'GBK',
- 'GB_2312-80' => 'GBK',
- 'ISO-8859-1' => 'windows-1252',
- 'ISO-8859-9' => 'windows-1254',
- 'ISO-8859-11' => 'windows-874',
- 'KS_C_5601-1987' => 'windows-949',
- 'TIS-620' => 'windows-874',
- //'US-ASCII' => 'windows-1252',
- 'x-x-big5' => 'Big5',
- );
-
- foreach ($compat as $real => $replace)
- {
- if (isset($charsets[$real]) && isset($charsets[$replace]))
- {
- $charsets[$replace] = array_merge($charsets[$replace], $charsets[$real]);
- unset($charsets[$real]);
- }
- elseif (isset($charsets[$real]))
- {
- $charsets[$replace] = $charsets[$real];
- $charsets[$replace][] = normalize_character_set($replace);
- unset($charsets[$real]);
- }
- else
- {
- $charsets[$replace][] = normalize_character_set($real);
- }
- $charsets[$replace] = array_unique($charsets[$replace]);
- natsort($charsets[$replace]);
- }
-
- // Sort it
- uksort($charsets, 'strnatcasecmp');
-
- // Check that nothing matches more than one
- $all = call_user_func_array('array_merge', $charsets);
- $all_count = array_count_values($all);
- if (max($all_count) > 1)
- {
- echo "Duplicated charsets:\n";
- foreach ($all_count as $charset => $count)
- {
- if ($count > 1)
- {
- echo "$charset\n";
- }
- }
- }
-
- // And we're done!
- return $charsets;
- }
-}
-
-function charset($charset)
-{
- $normalized_charset = normalize_character_set($charset);
- if ($charsets = build_character_set_list())
- {
- foreach ($charsets as $preferred => $aliases)
- {
- if (in_array($normalized_charset, $aliases))
- {
- return $preferred;
- }
- }
- return $charset;
- }
- else
- {
- return false;
- }
-}
-
-function build_function()
-{
- if ($charsets = build_character_set_list())
- {
- $return = <<<EOF
-function charset(\$charset)
-{
- // Normalization from UTS #22
- switch (strtolower(preg_replace('/(?:[^a-zA-Z0-9]+|([^0-9])0+)/', '\\1', \$charset)))
- {
-
-EOF;
- foreach ($charsets as $preferred => $aliases)
- {
- foreach ($aliases as $alias)
- {
- $return .= "\t\tcase " . var_export($alias, true) . ":\n";
- }
- $return .= "\t\t\treturn " . var_export($preferred, true) . ";\n\n";
- }
- $return .= <<<EOF
- default:
- return \$charset;
- }
-}
-EOF;
- return $return;
- }
- else
- {
- return false;
- }
-}
-
-if (php_sapi_name() === 'cli' && realpath($_SERVER['argv'][0]) === __FILE__)
-{
- echo build_function();
-}
-
-?> \ No newline at end of file
diff --git a/library/simplepie/db.sql b/library/simplepie/db.sql
deleted file mode 100644
index 13f504c21..000000000
--- a/library/simplepie/db.sql
+++ /dev/null
@@ -1,38 +0,0 @@
-/* SQLite */
-CREATE TABLE cache_data (
- id TEXT NOT NULL,
- items SMALLINT NOT NULL DEFAULT 0,
- data BLOB NOT NULL,
- mtime INTEGER UNSIGNED NOT NULL
-);
-CREATE UNIQUE INDEX id ON cache_data(id);
-
-CREATE TABLE items (
- feed_id TEXT NOT NULL,
- id TEXT NOT NULL,
- data TEXT NOT NULL,
- posted INTEGER UNSIGNED NOT NULL
-);
-CREATE INDEX feed_id ON items(feed_id);
-
-
-/* MySQL */
-CREATE TABLE `cache_data` (
- `id` TEXT CHARACTER SET utf8 NOT NULL,
- `items` SMALLINT NOT NULL DEFAULT 0,
- `data` BLOB NOT NULL,
- `mtime` INT UNSIGNED NOT NULL,
- UNIQUE (
- `id`(125)
- )
-);
-
-CREATE TABLE `items` (
- `feed_id` TEXT CHARACTER SET utf8 NOT NULL,
- `id` TEXT CHARACTER SET utf8 NOT NULL,
- `data` TEXT CHARACTER SET utf8 NOT NULL,
- `posted` INT UNSIGNED NOT NULL,
- INDEX `feed_id` (
- `feed_id`(125)
- )
-); \ No newline at end of file
diff --git a/library/simplepie/demo/cli_test.php b/library/simplepie/demo/cli_test.php
deleted file mode 100644
index ec933c5ad..000000000
--- a/library/simplepie/demo/cli_test.php
+++ /dev/null
@@ -1,23 +0,0 @@
-#!/usr/bin/php
-<?php
-include_once('../simplepie.inc');
-
-// Parse it
-$feed = new SimplePie();
-if (isset($argv[1]) && $argv[1] !== '')
-{
- $feed->set_feed_url($argv[1]);
- $feed->enable_cache(false);
- $feed->init();
-}
-
-$items = $feed->get_items();
-
-foreach ($items as $item)
-{
- echo $item->get_title() . "\n";
-}
-
-var_dump($feed->get_item_quantity());
-
-?> \ No newline at end of file
diff --git a/library/simplepie/demo/for_the_demo/alternate_favicon.png b/library/simplepie/demo/for_the_demo/alternate_favicon.png
deleted file mode 100644
index 063fb2805..000000000
--- a/library/simplepie/demo/for_the_demo/alternate_favicon.png
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/background_blockquote.png b/library/simplepie/demo/for_the_demo/background_blockquote.png
deleted file mode 100644
index 8267e23a2..000000000
--- a/library/simplepie/demo/for_the_demo/background_blockquote.png
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/background_menuitem.gif b/library/simplepie/demo/for_the_demo/background_menuitem.gif
deleted file mode 100644
index fa765d670..000000000
--- a/library/simplepie/demo/for_the_demo/background_menuitem.gif
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/background_menuitem_off.gif b/library/simplepie/demo/for_the_demo/background_menuitem_off.gif
deleted file mode 100644
index 236cf406d..000000000
--- a/library/simplepie/demo/for_the_demo/background_menuitem_off.gif
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/background_menuitem_shadow.gif b/library/simplepie/demo/for_the_demo/background_menuitem_shadow.gif
deleted file mode 100644
index 95cfb820d..000000000
--- a/library/simplepie/demo/for_the_demo/background_menuitem_shadow.gif
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/favicons/alternate.png b/library/simplepie/demo/for_the_demo/favicons/alternate.png
deleted file mode 100644
index 063fb2805..000000000
--- a/library/simplepie/demo/for_the_demo/favicons/alternate.png
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/favicons/blinklist.png b/library/simplepie/demo/for_the_demo/favicons/blinklist.png
deleted file mode 100644
index 53200b3c6..000000000
--- a/library/simplepie/demo/for_the_demo/favicons/blinklist.png
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/favicons/blogmarks.png b/library/simplepie/demo/for_the_demo/favicons/blogmarks.png
deleted file mode 100644
index c5372614a..000000000
--- a/library/simplepie/demo/for_the_demo/favicons/blogmarks.png
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/favicons/delicious.png b/library/simplepie/demo/for_the_demo/favicons/delicious.png
deleted file mode 100644
index 2e6021d26..000000000
--- a/library/simplepie/demo/for_the_demo/favicons/delicious.png
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/favicons/digg.png b/library/simplepie/demo/for_the_demo/favicons/digg.png
deleted file mode 100644
index 3aa96770e..000000000
--- a/library/simplepie/demo/for_the_demo/favicons/digg.png
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/favicons/magnolia.png b/library/simplepie/demo/for_the_demo/favicons/magnolia.png
deleted file mode 100644
index da519f5ab..000000000
--- a/library/simplepie/demo/for_the_demo/favicons/magnolia.png
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/favicons/myweb2.png b/library/simplepie/demo/for_the_demo/favicons/myweb2.png
deleted file mode 100644
index 2a12968d5..000000000
--- a/library/simplepie/demo/for_the_demo/favicons/myweb2.png
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/favicons/newsvine.png b/library/simplepie/demo/for_the_demo/favicons/newsvine.png
deleted file mode 100644
index 5cdbb31c6..000000000
--- a/library/simplepie/demo/for_the_demo/favicons/newsvine.png
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/favicons/reddit.png b/library/simplepie/demo/for_the_demo/favicons/reddit.png
deleted file mode 100644
index 65c38867c..000000000
--- a/library/simplepie/demo/for_the_demo/favicons/reddit.png
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/favicons/segnalo.png b/library/simplepie/demo/for_the_demo/favicons/segnalo.png
deleted file mode 100644
index 748149b37..000000000
--- a/library/simplepie/demo/for_the_demo/favicons/segnalo.png
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/favicons/simpy.png b/library/simplepie/demo/for_the_demo/favicons/simpy.png
deleted file mode 100644
index 30b23c1a5..000000000
--- a/library/simplepie/demo/for_the_demo/favicons/simpy.png
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/favicons/spurl.png b/library/simplepie/demo/for_the_demo/favicons/spurl.png
deleted file mode 100644
index f5be3963d..000000000
--- a/library/simplepie/demo/for_the_demo/favicons/spurl.png
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/favicons/technorati.png b/library/simplepie/demo/for_the_demo/favicons/technorati.png
deleted file mode 100644
index 0f19e824e..000000000
--- a/library/simplepie/demo/for_the_demo/favicons/technorati.png
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/favicons/wists.png b/library/simplepie/demo/for_the_demo/favicons/wists.png
deleted file mode 100644
index 2e2d294d1..000000000
--- a/library/simplepie/demo/for_the_demo/favicons/wists.png
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/feed.png b/library/simplepie/demo/for_the_demo/feed.png
deleted file mode 100644
index e23c50c85..000000000
--- a/library/simplepie/demo/for_the_demo/feed.png
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/logo_simplepie_demo.png b/library/simplepie/demo/for_the_demo/logo_simplepie_demo.png
deleted file mode 100644
index eda2d868b..000000000
--- a/library/simplepie/demo/for_the_demo/logo_simplepie_demo.png
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/lucida-grande-bold.swf b/library/simplepie/demo/for_the_demo/lucida-grande-bold.swf
deleted file mode 100644
index 0a41e15eb..000000000
--- a/library/simplepie/demo/for_the_demo/lucida-grande-bold.swf
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/mediaplayer.swf b/library/simplepie/demo/for_the_demo/mediaplayer.swf
deleted file mode 100644
index bf78fd919..000000000
--- a/library/simplepie/demo/for_the_demo/mediaplayer.swf
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/mediaplayer_readme.htm b/library/simplepie/demo/for_the_demo/mediaplayer_readme.htm
deleted file mode 100644
index 56e12c309..000000000
--- a/library/simplepie/demo/for_the_demo/mediaplayer_readme.htm
+++ /dev/null
@@ -1,5 +0,0 @@
-<html>
-<head>
-<meta http-equiv="refresh" content="0;url=http://www.jeroenwijering.com/extras/readme.html">
-</head>
-</html> \ No newline at end of file
diff --git a/library/simplepie/demo/for_the_demo/mini_podcast.png b/library/simplepie/demo/for_the_demo/mini_podcast.png
deleted file mode 100644
index fd6faf2a3..000000000
--- a/library/simplepie/demo/for_the_demo/mini_podcast.png
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/place_audio.png b/library/simplepie/demo/for_the_demo/place_audio.png
deleted file mode 100644
index 560ea0039..000000000
--- a/library/simplepie/demo/for_the_demo/place_audio.png
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/place_video.png b/library/simplepie/demo/for_the_demo/place_video.png
deleted file mode 100644
index be5ec8219..000000000
--- a/library/simplepie/demo/for_the_demo/place_video.png
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/sIFR-print.css b/library/simplepie/demo/for_the_demo/sIFR-print.css
deleted file mode 100644
index ec89b1961..000000000
--- a/library/simplepie/demo/for_the_demo/sIFR-print.css
+++ /dev/null
@@ -1,35 +0,0 @@
-/*=:project
- scalable Inman Flash Replacement (sIFR) version 3.
-
- =:file
- Copyright: 2006 Mark Wubben.
- Author: Mark Wubben, <http://novemberborn.net/>
-
- =:history
- * IFR: Shaun Inman
- * sIFR 1: Mike Davidson, Shaun Inman and Tomas Jogin
- * sIFR 2: Mike Davidson, Shaun Inman, Tomas Jogin and Mark Wubben
-
- =:license
- This software is licensed and provided under the CC-GNU LGPL.
- See <http://creativecommons.org/licenses/LGPL/2.1/>
-*/
-
-
-/* This is the print stylesheet to hide the Flash headlines from the browser... regular browser text headlines will now print as normal */
-
-.sIFR-flash {
- display: none !important;
- height: 0;
- width: 0;
- position: absolute;
- overflow: hidden;
-}
-
-.sIFR-alternate {
- visibility: visible !important;
- display: block !important;
- position: static !important;
- left: auto !important;
- top: auto !important;
-} \ No newline at end of file
diff --git a/library/simplepie/demo/for_the_demo/sIFR-screen.css b/library/simplepie/demo/for_the_demo/sIFR-screen.css
deleted file mode 100644
index 778e09d2b..000000000
--- a/library/simplepie/demo/for_the_demo/sIFR-screen.css
+++ /dev/null
@@ -1,39 +0,0 @@
-/*=:project
- scalable Inman Flash Replacement (sIFR) version 3.
-
- =:file
- Copyright: 2006 Mark Wubben.
- Author: Mark Wubben, <http://novemberborn.net/>
-
- =:history
- * IFR: Shaun Inman
- * sIFR 1: Mike Davidson, Shaun Inman and Tomas Jogin
- * sIFR 2: Mike Davidson, Shaun Inman, Tomas Jogin and Mark Wubben
-
- =:license
- This software is licensed and provided under the CC-GNU LGPL.
- See <http://creativecommons.org/licenses/LGPL/2.1/>
-*/
-
-/*---- sIFR ---*/
-.sIFR-flash {
- visibility: visible !important;
- margin: 0;
- padding: 0;
-}
-
-.sIFR-replaced {
- visibility: visible !important;
-}
-
-.sIFR-alternate {
- position: absolute;
- left: 0;
- top: 0;
- width: 0;
- height: 0;
- display: block;
- overflow: hidden;
-}
-
-/*---- Header styling ---*/
diff --git a/library/simplepie/demo/for_the_demo/sifr-config.js b/library/simplepie/demo/for_the_demo/sifr-config.js
deleted file mode 100644
index e7066b361..000000000
--- a/library/simplepie/demo/for_the_demo/sifr-config.js
+++ /dev/null
@@ -1,40 +0,0 @@
-var yanone_kaffeesatz = {
- src: './for_the_demo/yanone-kaffeesatz-bold.swf'
-};
-
-var lucida_grande = {
- src: './for_the_demo/lucida-grande-bold.swf'
-};
-
-sIFR.activate(yanone_kaffeesatz);
-//sIFR.activate(lucida_grande);
-
-sIFR.replace(yanone_kaffeesatz, {
-//sIFR.replace(lucida_grande, {
-
- selector: 'h3.header',
- wmode: 'transparent',
- css: {
- '.sIFR-root': {
- 'text-align': 'center',
- 'color': '#000000',
- 'font-weight': 'bold',
- 'background-color': '#EEFFEE',
-
- 'font-size': '50px', // For Yanone Kaffeesatz
- //'font-size': '40px', // For Lucida Grande
-
- 'letter-spacing': '0' // For Yanone Kaffeesatz
- //'letter-spacing': '-4' // For Lucida Grande
-
- },
- 'a': {
- 'text-decoration': 'none',
- 'color': '#000000'
- },
- 'a:hover': {
- 'text-decoration': 'none',
- 'color': '#666666'
- }
- }
-});
diff --git a/library/simplepie/demo/for_the_demo/sifr.js b/library/simplepie/demo/for_the_demo/sifr.js
deleted file mode 100644
index 0a8b1b6dc..000000000
--- a/library/simplepie/demo/for_the_demo/sifr.js
+++ /dev/null
@@ -1,19 +0,0 @@
-/*=:project
- scalable Inman Flash Replacement (sIFR) version 3, revision 245
-
- =:file
- Copyright: 2006 Mark Wubben.
- Author: Mark Wubben, <http://novemberborn.net/>
-
- =:history
- * IFR: Shaun Inman
- * sIFR 1: Mike Davidson, Shaun Inman and Tomas Jogin
- * sIFR 2: Mike Davidson, Shaun Inman, Tomas Jogin and Mark Wubben
-
- =:license
- This software is licensed and provided under the CC-GNU LGPL.
- See <http://creativecommons.org/licenses/LGPL/2.1/>
-*/
-
-var parseSelector=(function(){var _1=/\s*,\s*/;var _2=/\s*([\s>+~(),]|^|$)\s*/g;var _3=/([\s>+~,]|[^(]\+|^)([#.:@])/g;var _4=/^[^\s>+~]/;var _5=/[\s#.:>+~()@]|[^\s#.:>+~()@]+/g;function parseSelector(_6,_7){_7=_7||document.documentElement;var _8=_6.split(_1),_9=[];for(var i=0;i<_8.length;i++){var _b=[_7],_c=toStream(_8[i]);for(var j=0;j<_c.length;){var _e=_c[j++],_f=_c[j++],_10="";if(_c[j]=="("){while(_c[j++]!=")"&&j<_c.length){_10+=_c[j]}_10=_10.slice(0,-1)}_b=select(_b,_e,_f,_10)}_9=_9.concat(_b)}return _9}function toStream(_11){var _12=_11.replace(_2,"$1").replace(_3,"$1*$2");if(_4.test(_12)){_12=" "+_12}return _12.match(_5)||[]}function select(_13,_14,_15,_16){return (_17[_14])?_17[_14](_13,_15,_16):[]}var _18={toArray:function(_19){var a=[];for(var i=0;i<_19.length;i++){a.push(_19[i])}return a}};var dom={isTag:function(_1d,tag){return (tag=="*")||(tag.toLowerCase()==_1d.nodeName.toLowerCase())},previousSiblingElement:function(_1f){do{_1f=_1f.previousSibling}while(_1f&&_1f.nodeType!=1);return _1f},nextSiblingElement:function(_20){do{_20=_20.nextSibling}while(_20&&_20.nodeType!=1);return _20},hasClass:function(_21,_22){return (_22.className||"").match("(^|\\s)"+_21+"(\\s|$)")},getByTag:function(tag,_24){return _24.getElementsByTagName(tag)}};var _17={"#":function(_25,_26){for(var i=0;i<_25.length;i++){if(_25[i].getAttribute("id")==_26){return [_25[i]]}}return []}," ":function(_28,_29){var _2a=[];for(var i=0;i<_28.length;i++){_2a=_2a.concat(_18.toArray(dom.getByTag(_29,_28[i])))}return _2a},">":function(_2c,_2d){var _2e=[];for(var i=0,_30;i<_2c.length;i++){_30=_2c[i];for(var j=0,_32;j<_30.childNodes.length;j++){_32=_30.childNodes[j];if(_32.nodeType==1&&dom.isTag(_32,_2d)){_2e.push(_32)}}}return _2e},".":function(_33,_34){var _35=[];for(var i=0,_37;i<_33.length;i++){_37=_33[i];if(dom.hasClass([_34],_37)){_35.push(_37)}}return _35},":":function(_38,_39,_3a){return (pseudoClasses[_39])?pseudoClasses[_39](_38,_3a):[]}};parseSelector.selectors=_17;parseSelector.pseudoClasses={};parseSelector.util=_18;parseSelector.dom=dom;return parseSelector})();
-var sIFR=new function(){var _3b=this;var _3c="sIFR-active";var _3d="sIFR-replaced";var _3e="sIFR-replacing";var _3f="sIFR-flash";var _40="sIFR-ignore";var _41="sIFR-alternate";var _42="sIFR-class";var _43="sIFR-layout";var _44=6;var _45=126;var _46=8;var _47="SIFR-PREFETCHED";var _48=[10,1.55,19,1.45,32,1.35,71,1.3,1.25];var _49=5;this.isActive=false;this.isEnabled=true;this.hideElements=true;this.preserveSingleWhitespace=false;this.fixWrap=true;this.fixHover=true;this.registerEvents=true;this.setPrefetchCookie=true;this.cookiePath="/";this.domains=[];this.fromLocal=true;this.forceClear=false;this.forceWidth=false;this.fitExactly=false;this.forceTextTransform=true;this.useDomContentLoaded=true;this.debugMode=false;this.hasFlashClassSet=false;this.delayCss=false;this.callbacks=[];var _4a=0;var _4b=false,_4c=false;var dom=new function(){var _4e="http://www.w3.org/1999/xhtml";this.getBody=function(){var _4f=document.getElementsByTagName("body");if(_4f.length==1){return _4f[0]}return null};this.addClass=function(_50,_51){if(_51){_51.className=((_51.className||"")==""?"":_51.className+" ")+_50}};this.removeClass=function(_52,_53){if(_53){_53.className=_53.className.replace(new RegExp("(^|\\s)"+_52+"(\\s|$)"),"").replace(/^\s+|(\s)\s+/g,"$1")}};this.hasClass=function(_54,_55){return new RegExp("(^|\\s)"+_54+"(\\s|$)").test(_55.className)};this.hasOneOfClassses=function(_56,_57){for(var i=0;i<_56.length;i++){if(this.hasClass(_56[i],_57)){return true}}return false};this.create=function(_59){if(document.createElementNS){return document.createElementNS(_4e,_59)}return document.createElement(_59)};this.setInnerHtml=function(_5a,_5b){if(ua.innerHtmlSupport){_5a.innerHTML=_5b}else{if(ua.xhtmlSupport){_5b=["<root xmlns=\"",_4e,"\">",_5b,"</root>"].join("");var xml=(new DOMParser()).parseFromString(_5b,"text/xml");xml=document.importNode(xml.documentElement,true);while(_5a.firstChild){_5a.removeChild(_5a.firstChild)}while(xml.firstChild){_5a.appendChild(xml.firstChild)}}}};this.nodeFromHtml=function(_5d){var _5e=this.create("div");_5e.innerHTML=_5d;return _5e.firstChild};this.getComputedStyle=function(_5f,_60){var _61;if(document.defaultView&&document.defaultView.getComputedStyle){_61=document.defaultView.getComputedStyle(_5f,null)[_60]}else{if(_5f.currentStyle){_61=_5f.currentStyle[_60]}}return _61||""};this.getStyleAsInt=function(_62,_63,_64){var _65=this.getComputedStyle(_62,_63);if(_64&&!/px$/.test(_65)){return 0}_65=parseInt(_65);return isNaN(_65)?0:_65};this.getZoom=function(){return _66.zoom.getLatest()}};this.dom=dom;var ua=new function(){var ua=navigator.userAgent.toLowerCase();var _69=(navigator.product||"").toLowerCase();this.macintosh=ua.indexOf("mac")>-1;this.windows=ua.indexOf("windows")>-1;this.quicktime=false;this.opera=ua.indexOf("opera")>-1;this.konqueror=_69.indexOf("konqueror")>-1;this.ie=false/*@cc_on || true @*/;this.ieSupported=this.ie&&!/ppc|smartphone|iemobile|msie\s5\.5/.test(ua)/*@cc_on && @_jscript_version >= 5.5 @*/;this.ieWin=this.ie&&this.windows/*@cc_on && @_jscript_version >= 5.1 @*/;this.windows=this.windows&&(!this.ie||this.ieWin);this.ieMac=this.ie&&this.macintosh/*@cc_on && @_jscript_version < 5.1 @*/;this.macintosh=this.macintosh&&(!this.ie||this.ieMac);this.safari=ua.indexOf("safari")>-1;this.webkit=ua.indexOf("applewebkit")>-1&&!this.konqueror;this.khtml=this.webkit||this.konqueror;this.gecko=!this.webkit&&_69=="gecko";this.operaVersion=this.opera&&/.*opera(\s|\/)(\d+\.\d+)/.exec(ua)?parseInt(RegExp.$2):0;this.webkitVersion=this.webkit&&/.*applewebkit\/(\d+).*/.exec(ua)?parseInt(RegExp.$1):0;this.geckoBuildDate=this.gecko&&/.*gecko\/(\d{8}).*/.exec(ua)?parseInt(RegExp.$1):0;this.konquerorVersion=this.konqueror&&/.*konqueror\/(\d\.\d).*/.exec(ua)?parseInt(RegExp.$1):0;this.flashVersion=0;if(this.ieWin){var axo;var _6b=false;try{axo=new ActiveXObject("ShockwaveFlash.ShockwaveFlash.7")}catch(e){try{axo=new ActiveXObject("ShockwaveFlash.ShockwaveFlash.6");this.flashVersion=6;axo.AllowScriptAccess="always"}catch(e){_6b=this.flashVersion==6}if(!_6b){try{axo=new ActiveXObject("ShockwaveFlash.ShockwaveFlash")}catch(e){}}}if(!_6b&&axo){this.flashVersion=parseFloat(/([\d,?]+)/.exec(axo.GetVariable("$version"))[1].replace(/,/g,"."))}}else{if(navigator.plugins&&navigator.plugins["Shockwave Flash"]){var _6c=navigator.plugins["Shockwave Flash"];this.flashVersion=parseFloat(/(\d+\.?\d*)/.exec(_6c.description)[1]);var i=0;while(this.flashVersion>=_46&&i<navigator.mimeTypes.length){var _6e=navigator.mimeTypes[i];if(_6e.type=="application/x-shockwave-flash"&&_6e.enabledPlugin.description.toLowerCase().indexOf("quicktime")>-1){this.flashVersion=0;this.quicktime=true}i++}}}this.flash=this.flashVersion>=_46;this.transparencySupport=this.macintosh||this.windows;this.computedStyleSupport=this.ie||document.defaultView&&document.defaultView.getComputedStyle&&(!this.gecko||this.geckoBuildDate>=20030624);this.css=true;if(this.computedStyleSupport){try{var _6f=document.getElementsByTagName("head")[0];_6f.style.backgroundColor="#FF0000";var _70=dom.getComputedStyle(_6f,"backgroundColor");this.css=!_70||/\#F{2}0{4}|rgb\(255,\s?0,\s?0\)/i.test(_70);_6f.style.backgroundColor="";_6f=null}catch(e){}}this.xhtmlSupport=!!window.DOMParser&&!!document.importNode;try{var n=dom.create("span");if(!this.ieMac){n.innerHTML="x"}this.innerHtmlSupport=n.innerHTML=="x"}catch(e){this.innerHtmlSupport=false}this.zoomSupport=!!(this.opera&&document.documentElement);this.geckoXml=this.gecko&&(document.contentType||"").indexOf("xml")>-1;this.requiresPrefetch=this.ieWin||this.khtml;this.verifiedKonqueror=false;this.supported=this.flash&&this.css&&(!this.ie||this.ieSupported)&&(!this.opera||this.operaVersion>=8)&&(!this.webkit||this.webkitVersion>=412)&&(!this.konqueror||this.konquerorVersion>3.5)&&this.computedStyleSupport&&(this.innerHtmlSupport||!this.khtml&&this.xhtmlSupport)};this.ua=ua;var _72=new function(){var _73={leading:true,"margin-left":true,"margin-right":true,"text-indent":true};var _74=" ";function capitalize($){return $.toUpperCase()}this.normalize=function(str){if(_3b.preserveSingleWhitespace){return str.replace(/\s/g,_74)}return str.replace(/(\s)\s+/g,"$1").replace(/\xA0/,_74)};this.textTransform=function(_77,str){switch(_77){case "uppercase":str=str.toUpperCase();break;case "lowercase":str=str.toLowerCase();break;case "capitalize":var _79=str;str=str.replace(/^\w|\s\w/g,capitalize);if(str.indexOf("function capitalize")!=-1){var _7a=_79.replace(/(^|\s)(\w)/g,"$1$1$2$2").split(/^\w|\s\w/g);str="";for(var i=0;i<_7a.length;i++){str+=_7a[i].charAt(0).toUpperCase()+_7a[i].substring(1)}}break}return str};this.toHexString=function(str){if(typeof (str)!="string"||!str.charAt(0)=="#"||str.length!=4&&str.length!=7){return str}str=str.replace(/#/,"");if(str.length==3){str=str.replace(/(.)(.)(.)/,"$1$1$2$2$3$3")}return "0x"+str};this.toJson=function(obj){var _7e="";switch(typeof (obj)){case "string":_7e="\""+obj+"\"";break;case "number":case "boolean":_7e=obj.toString();break;case "object":_7e=[];for(var _7f in obj){if(obj[_7f]==Object.prototype[_7f]){continue}_7e.push("\""+_7f+"\":"+_72.toJson(obj[_7f]))}_7e="{"+_7e.join(",")+"}";break}return _7e};this.convertCssArg=function(arg){if(!arg){return {}}if(typeof (arg)=="object"){if(arg.constructor==Array){arg=arg.join("")}else{return arg}}var obj={};var _82=arg.split("}");for(var i=0;i<_82.length;i++){var $=_82[i].match(/([^\s{]+)\s*\{(.+)\s*;?\s*/);if(!$||$.length!=3){continue}if(!obj[$[1]]){obj[$[1]]={}}var _85=$[2].split(";");for(var j=0;j<_85.length;j++){var $2=_85[j].match(/\s*([^:\s]+)\s*\:\s*([^\s;]+)/);if(!$2||$2.length!=3){continue}obj[$[1]][$2[1]]=$2[2]}}return obj};this.extractFromCss=function(css,_89,_8a,_8b){var _8c=null;if(css&&css[_89]&&css[_89][_8a]){_8c=css[_89][_8a];if(_8b){delete css[_89][_8a]}}return _8c};this.cssToString=function(arg){var css=[];for(var _8f in arg){var _90=arg[_8f];if(_90==Object.prototype[_8f]){continue}css.push(_8f,"{");for(var _91 in _90){if(_90[_91]==Object.prototype[_91]){continue}var _92=_90[_91];if(_73[_91]){_92=parseInt(_92,10)}css.push(_91,":",_92,";")}css.push("}")}return escape(css.join(""))};this.bind=function(_93,_94){return function(){_93[_94].apply(_93,arguments)}}};this.util=_72;var _66={};_66.fragmentIdentifier=new function(){this.fix=true;var _95;this.cache=function(){_95=document.title};function doFix(){document.title=_95}this.restore=function(){if(this.fix){setTimeout(doFix,0)}}};_66.synchronizer=new function(){this.isBlocked=false;this.block=function(){this.isBlocked=true};this.unblock=function(){this.isBlocked=false;_96.replaceAll()}};_66.zoom=new function(){var _97=100;this.getLatest=function(){return _97};if(ua.zoomSupport&&ua.opera){var _98=document.createElement("div");_98.style.position="fixed";_98.style.left="-65536px";_98.style.top="0";_98.style.height="100%";_98.style.width="1px";_98.style.zIndex="-32";document.documentElement.appendChild(_98);function updateZoom(){if(!_98){return}var _99=window.innerHeight/_98.offsetHeight;var _9a=Math.round(_99*100)%10;if(_9a>5){_99=Math.round(_99*100)+10-_9a}else{_99=Math.round(_99*100)-_9a}_97=isNaN(_99)?100:_99;_66.synchronizer.unblock();document.documentElement.removeChild(_98);_98=null}_66.synchronizer.block();setTimeout(updateZoom,54)}};this.hacks=_66;var _9b={kwargs:[],replaceAll:function(){for(var i=0;i<this.kwargs.length;i++){_3b.replace(this.kwargs[i])}this.kwargs=[]}};var _96={kwargs:[],replaceAll:_9b.replaceAll};function isValidDomain(){if(_3b.domains.length==0){return true}var _9d="";try{_9d=document.domain}catch(e){}if(_3b.fromLocal&&sIFR.domains[0]!="localhost"){sIFR.domains.unshift("localhost")}for(var i=0;i<_3b.domains.length;i++){var _9f=_3b.domains[i];if(_9f=="*"||_9f==_9d){return true}var _a0=_9f.lastIndexOf("*");if(_a0>-1){_9f=_9f.substr(_a0+1);var _a1=_9d.lastIndexOf(_9f);if(_a1>-1&&(_a1+_9f.length)==_9d.length){return true}}}return false}this.activate=function(){if(!ua.supported||!this.isEnabled||this.isActive||!isValidDomain()){return}if(arguments.length>0){this.prefetch.apply(this,arguments)}this.isActive=true;if(this.hideElements){this.setFlashClass()}if(ua.ieWin&&_66.fragmentIdentifier.fix&&window.location.hash!=""){_66.fragmentIdentifier.cache()}else{_66.fragmentIdentifier.fix=false}if(!this.registerEvents){return}function handler(evt){_3b.initialize();if(evt&&evt.type=="load"){if(document.removeEventListener){document.removeEventListener("DOMContentLoaded",handler,false)}if(window.removeEventListener){window.removeEventListener("load",handler,false)}}}if(window.addEventListener){if(_3b.useDomContentLoaded&&ua.gecko){document.addEventListener("DOMContentLoaded",handler,false)}window.addEventListener("load",handler,false)}else{if(ua.ieWin){if(_3b.useDomContentLoaded){document.write("<scr"+"ipt id=__sifr_ie_onload defer src=//:></script>");document.getElementById("__sifr_ie_onload").onreadystatechange=function(){if(this.readyState=="complete"){handler();this.removeNode()}}}window.attachEvent("onload",handler)}}};this.setFlashClass=function(){if(this.hasFlashClassSet){return}dom.addClass(_3c,dom.getBody()||document.documentElement);this.hasFlashClassSet=true};this.removeFlashClass=function(){if(!this.hasFlashClassSet){return}dom.removeClass(_3c,dom.getBody());dom.removeClass(_3c,document.documentElement);this.hasFlashClassSet=false};this.initialize=function(){if(_4c||!this.isActive||!this.isEnabled){return}_4c=true;_9b.replaceAll();clearPrefetch()};function getSource(src){if(typeof (src)!="string"){if(src.src){src=src.src}if(typeof (src)!="string"){var _a4=[];for(var _a5 in src){if(src[_a5]!=Object.prototype[_a5]){_a4.push(_a5)}}_a4.sort().reverse();var _a6="";var i=-1;while(!_a6&&++i<_a4.length){if(parseFloat(_a4[i])<=ua.flashVersion){_a6=src[_a4[i]]}}src=_a6}}if(!src&&_3b.debugMode){throw new Error("sIFR: Could not determine appropriate source")}if(ua.ie&&src.charAt(0)=="/"){src=window.location.toString().replace(/([^:]+)(:\/?\/?)([^\/]+).*/,"$1$2$3")+src}return src}this.prefetch=function(){if(!ua.requiresPrefetch||!ua.supported||!this.isEnabled||!isValidDomain()){return}if(this.setPrefetchCookie&&new RegExp(";?"+_47+"=true;?").test(document.cookie)){return}try{_4b=true;if(ua.ieWin){prefetchIexplore(arguments)}else{prefetchLight(arguments)}if(this.setPrefetchCookie){document.cookie=_47+"=true;path="+this.cookiePath}}catch(e){if(_3b.debugMode){throw e}}};function prefetchIexplore(_a8){for(var i=0;i<_a8.length;i++){document.write("<script defer type=\"sifr/prefetch\" src=\""+getSource(_a8[i])+"\"></script>")}}function prefetchLight(_aa){for(var i=0;i<_aa.length;i++){new Image().src=getSource(_aa[i])}}function clearPrefetch(){if(!ua.ieWin||!_4b){return}try{var _ac=document.getElementsByTagName("script");for(var i=_ac.length-1;i>=0;i--){var _ae=_ac[i];if(_ae.type=="sifr/prefetch"){_ae.parentNode.removeChild(_ae)}}}catch(e){}}function getRatio(_af,_b0){for(var i=0;i<_b0.length;i+=2){if(_af<=_b0[i]){return _b0[i+1]}}return _b0[_b0.length-1]}function getFilters(obj){var _b3=[];for(var _b4 in obj){if(obj[_b4]==Object.prototype[_b4]){continue}var _b5=obj[_b4];_b4=[_b4.replace(/filter/i,"")+"Filter"];for(var _b6 in _b5){if(_b5[_b6]==Object.prototype[_b6]){continue}_b4.push(_b6+":"+escape(_72.toJson(_72.toHexString(_b5[_b6]))))}_b3.push(_b4.join(","))}return _b3.join(";")}function calculate(_b7){var _b8,_b9;if(!ua.ie){_b8=dom.getStyleAsInt(_b7,"lineHeight");_b9=Math.floor(dom.getStyleAsInt(_b7,"height")/_b8)}else{if(ua.ie){var _ba=_b7.innerHTML;_b7.style.visibility="visible";_b7.style.overflow="visible";_b7.style.position="static";_b7.style.zoom="normal";_b7.style.writingMode="lr-tb";_b7.style.width=_b7.style.height="auto";_b7.style.maxWidth=_b7.style.maxHeight=_b7.style.styleFloat="none";var _bb=_b7;var _bc=_b7.currentStyle.hasLayout;if(_bc){dom.setInnerHtml(_b7,"<div class=\""+_43+"\">X<br />X<br />X</div>");_bb=_b7.firstChild}else{dom.setInnerHtml(_b7,"X<br />X<br />X")}var _bd=_bb.getClientRects();_b8=_bd[1].bottom-_bd[1].top;_b8=Math.ceil(_b8*0.8);if(_bc){dom.setInnerHtml(_b7,"<div class=\""+_43+"\">"+_ba+"</div>");_bb=_b7.firstChild}else{dom.setInnerHtml(_b7,_ba)}_bd=_bb.getClientRects();_b9=_bd.length;if(_bc){dom.setInnerHtml(_b7,_ba)}_b7.style.visibility=_b7.style.width=_b7.style.height=_b7.style.maxWidth=_b7.style.maxHeight=_b7.style.overflow=_b7.style.styleFloat=_b7.style.position=_b7.style.zoom=_b7.style.writingMode=""}}return {lineHeight:_b8,lines:_b9}}this.replace=function(_be,_bf){if(!ua.supported){return}if(_bf){for(var _c0 in _be){if(typeof (_bf[_c0])=="undefined"){_bf[_c0]=_be[_c0]}}_be=_bf}if(!_4c){return _9b.kwargs.push(_be)}if(_66.synchronizer.isBlocked){return _96.kwargs.push(_be)}var _c1=_be.elements;if(!_c1&&parseSelector){_c1=parseSelector(_be.selector)}if(_c1.length==0){return}this.setFlashClass();var src=getSource(_be.src);var css=_72.convertCssArg(_be.css);var _c4=getFilters(_be.filters);var _c5=(_be.forceClear==null)?_3b.forceClear:_be.forceClear;var _c6=(_be.fitExactly==null)?_3b.fitExactly:_be.fitExactly;var _c7=_c6||(_be.forceWidth==null?_3b.forceWidth:_be.forceWidth);var _c8=parseInt(_72.extractFromCss(css,".sIFR-root","leading"))||0;var _c9=_72.extractFromCss(css,".sIFR-root","font-size",true)||0;var _ca=_72.extractFromCss(css,".sIFR-root","background-color",true)||"#FFFFFF";var _cb=_72.extractFromCss(css,".sIFR-root","kerning",true)||"";var _cc=_be.gridFitType||_72.extractFromCss(css,".sIFR-root","text-align")=="right"?"subpixel":"pixel";var _cd=_3b.forceTextTransform?_72.extractFromCss(css,".sIFR-root","text-transform",true)||"none":"none";var _ce=_72.extractFromCss(css,".sIFR-root","opacity",true)||"100";var _cf=_be.pixelFont||false;var _d0=_be.ratios||_48;if(parseInt(_c9).toString()!=_c9&&_c9.indexOf("px")==-1){_c9=0}else{_c9=parseInt(_c9)}if(parseFloat(_ce)<1){_ce=100*parseFloat(_ce)}var _d1=null;var _d2="";if(_c6){_72.extractFromCss(css,".sIFR-root","text-align",true)}if(!_be.modifyCss){_d2=_72.cssToString(css);_d1=_3b.fixHover&&_d2.indexOf("%3Ahover")>-1}var _d3=!ua.opera&&_3b.delayCss;var _d4=_be.wmode||"";if(!_d4){if(_be.transparent){_d4="transparent"}else{if(_be.opaque){_d4="opaque"}}}if(_d4=="transparent"){if(!ua.transparencySupport){_d4="opaque"}else{_ca="transparent"}}for(var i=0;i<_c1.length;i++){var _d6=_c1[i];if(!ua.verifiedKonqueror){if(dom.getComputedStyle(_d6,"lineHeight").match(/e\+08px/)){ua.supported=_3b.isEnabled=false;this.removeFlashClass();return}ua.verifiedKonqueror=true}if(dom.hasOneOfClassses([_3d,_3e,_40,_41],_d6)){continue}var _d7=_d6.offsetHeight;var _d8=_d6.offsetWidth;var _d9=dom.getComputedStyle(_d6,"display");if(!_d7||!_d8||_d9==null||_d9=="none"){continue}if(_c5&&ua.gecko){_d6.style.clear="both"}var _da=null;if(_3b.fixWrap&&ua.ie&&_d9=="block"){_da=_d6.innerHTML;dom.setInnerHtml(_d6,"X")}_d8=dom.getStyleAsInt(_d6,"width",ua.ie);if(_d8==0){var _db=dom.getStyleAsInt(_d6,"paddingRight",true);var _dc=dom.getStyleAsInt(_d6,"paddingLeft",true);var _dd=dom.getStyleAsInt(_d6,"borderRightWidth",true);var _de=dom.getStyleAsInt(_d6,"borderLeftWidth",true);_d8=_d6.offsetWidth-_dc-_db-_de-_dd}if(_da&&_3b.fixWrap&&ua.ie){dom.setInnerHtml(_d6,_da)}var _df,_e0;if(!_c9){var _e1=calculate(_d6);_df=Math.min(_45,Math.max(_44,_e1.lineHeight));if(_cf){_df=Math.max(8,8*Math.round(_df/8))}_e0=_e1.lines;if(isNaN(_e0)||!isFinite(_e0)||_e0==0){_e0=1}if(_e0>1&&_c8){_d7+=Math.round((_e0-1)*_c8)}}else{_df=_c9;_e0=1}_d7=Math.round(_e0*_df);if(_c5&&ua.gecko){_d6.style.clear=""}var _e2=dom.create("span");_e2.className=_41;var _e3=_d6.cloneNode(true);for(var j=0,l=_e3.childNodes.length;j<l;j++){_e2.appendChild(_e3.childNodes[j].cloneNode(true))}if(_be.modifyContent){_be.modifyContent(_e3,_be.selector)}if(_be.modifyCss){_d2=_be.modifyCss(css,_e3,_be.selector)}if(_d1==null){_d1=_3b.fixHover&&_d2.indexOf("%3Ahover")>-1}var _e6=handleContent(_e3,_cd);if(_be.modifyContentString){_e6=_be.modifyContentString(_e6,_be.selector)}if(_e6==""){continue}var _e7=["content="+_e6,"width="+_d8,"height="+_d7,"fitexactly="+(_c6?"true":""),"tunewidth="+(_be.tuneWidth||""),"tuneheight="+(_be.tuneHeight||""),"offsetleft="+(_be.offsetLeft||""),"offsettop="+(_be.offsetTop||""),"thickness="+(_be.thickness||""),"sharpness="+(_be.sharpness||""),"kerning="+_cb,"gridfittype="+_cc,"zoomsupport="+ua.zoomSupport,"flashfilters="+_c4,"opacity="+_ce,"blendmode="+(_be.blendMode||""),"size="+_df,"zoom="+dom.getZoom(),"css="+_d2,"selectable="+(_be.selectable==null?"true":_be.selectable),"lines="+_e0];var _e8=encodeURI(_e7.join("&amp;"));var _e9="sIFR_callback_"+_4a++;var _ea=new CallbackInfo(_e9,_e7,_be.onReplacement,_d1);window[_e9+"_DoFSCommand"]=(function(_eb){return function(_ec,arg){_eb.handle(_ec,arg)}})(_ea);_d7=Math.round(_e0*getRatio(_df,_d0)*_df)+_49;var _ee=_c7?_d8:"100%";var _ef;if(ua.ie){_ef=["<object classid=\"clsid:D27CDB6E-AE6D-11cf-96B8-444553540000\" id=\"",_e9,"\" sifr=\"true\" width=\"",_ee,"\" height=\"",_d7,"\" class=\"",_3f,"\">","<param name=\"movie\" value=\"",src,"\"></param>","<param name=\"flashvars\" value=\"",_e8,"\"></param>","<param name=\"allowScriptAccess\" value=\"always\"></param>","<param name=\"quality\" value=\"best\"></param>","<param name=\"wmode\" value=\"",_d4,"\"></param>","<param name=\"bgcolor\" value=\"",_ca,"\"></param>","<param name=\"name\" value=\"",_e9,"\"></param>","</object>","<scr","ipt event=FSCommand(info,args) for=",_e9,">",_e9,"_DoFSCommand(info, args);","</","script>"].join("")}else{_ef=["<embed type=\"application/x-shockwave-flash\"",(_d3?" class=\""+_3f+"\"":"")," src=\"",src,"\" quality=\"best\" flashvars=\"",_e8,"\" width=\"",_ee,"\" height=\"",_d7,"\" wmode=\"",_d4,"\" bgcolor=\"",_ca,"\" name=\"",_e9,"\" id=\"",_e9,"\" allowScriptAccess=\"always\" sifr=\"true\"></embed>"].join("")}dom.setInnerHtml(_d6,_ef);_ea.flashNode=_d6.firstChild;_ea.html=_ef;_3b.callbacks.push(_ea);if(_be.selector){if(!_3b.callbacks[_be.selector]){_3b.callbacks[_be.selector]=[_ea]}else{_3b.callbacks[_be.selector].push(_ea)}}_d6.appendChild(_e2);dom.addClass(_d3?_3e:_3d,_d6);_ea.setupFixHover()}_66.fragmentIdentifier.restore()};this.getCallbackByFlashElement=function(_f0){for(var i=0;i<_3b.callbacks.length;i++){if(_3b.callbacks[i].id==_f0.getAttribute("id")){return _3b.callbacks[i]}}};function handleContent(_f2,_f3){var _f4=[],_f5=[];var _f6=_f2.childNodes;var i=0;while(i<_f6.length){var _f8=_f6[i];if(_f8.nodeType==3){var _f9=_72.normalize(_f8.nodeValue);_f9=_72.textTransform(_f3,_f9);_f5.push(_f9.replace(/\%/g,"%25").replace(/\&/g,"%26").replace(/\,/g,"%2C").replace(/\+/g,"%2B"))}if(_f8.nodeType==1){var _fa=[];var _fb=_f8.nodeName.toLowerCase();var _fc=_f8.className||"";if(/\s+/.test(_fc)){if(_fc.indexOf(_42)>-1){_fc=_fc.match("(\\s|^)"+_42+"-([^\\s$]*)(\\s|$)")[2]}else{_fc=_fc.match(/^([^\s]+)/)[1]}}if(_fc!=""){_fa.push("class=\""+_fc+"\"")}if(_fb=="a"){var _fd=_f8.getAttribute("href")||"";var _fe=_f8.getAttribute("target")||"";_fa.push("href=\""+_fd+"\"","target=\""+_fe+"\"")}_f5.push("<"+_fb+(_fa.length>0?" ":"")+escape(_fa.join(" "))+">");if(_f8.hasChildNodes()){_f4.push(i);i=0;_f6=_f8.childNodes;continue}else{if(!/^(br|img)$/i.test(_f8.nodeName)){_f5.push("</",_f8.nodeName.toLowerCase(),">")}}}if(_f4.length>0&&!_f8.nextSibling){do{i=_f4.pop();_f6=_f8.parentNode.parentNode.childNodes;_f8=_f6[i];if(_f8){_f5.push("</",_f8.nodeName.toLowerCase(),">")}}while(i==_f6.length-1&&_f4.length>0)}i++}return _f5.join("").replace(/\n|\r/g,"")}function CallbackInfo(id,vars,_101,_102){this.id=id;this.vars=vars;this._replacementHandler=_101;this._firedReplacementEvent=!(this._replacementHandler!=null);this._fixHover=_102;this._setClasses=!_3b.delayCss;this.html="";this._pings=0}CallbackInfo.prototype.getFlashElement=function(){return document.getElementById(this.id)};CallbackInfo.prototype.handle=function(info,arg){if(/(FSCommand\:)?resize/.test(info)){var _105=this.getFlashElement();var $=arg.split(/\:|,/);_105.setAttribute($[0],$[1]);if($.length>2){_105.setAttribute($[2],$[3])}if(!this._setClasses){if(!ua.ie&&!ua.opera){dom.addClass(_3f,_105)}dom.removeClass(_3e,_105.parentNode);dom.addClass(_3d,_105.parentNode);this._setClasses=true}if(ua.khtml){var _107=_105.offsetHeight}if(!this._firedReplacementEvent){this._replacementHandler(this);this._firedReplacementEvent=true}}else{if(/(FSCommand\:)?resetmovie/.test(info)){this.resetMovie()}else{if(/(FSCommand\:)?ping/.test(info)){if(this._pings>0){this.setupFixHover()}this._pings++}else{if(this.debugHandler&&/(FSCommand\:)?debug/.test(info)){this.debugHandler(info,arg)}}}}};CallbackInfo.prototype.call=function(type,_109){var _10a=this.getFlashElement();if(!_10a){return}_10a.SetVariable("callbackType",type);_10a.SetVariable("callbackValue",_109);_10a.SetVariable("callbackTrigger",true)};CallbackInfo.prototype.replaceText=function(_10b){_10b=escape(_10b);this.call("replacetext",_10b);this.vars[0]="content="+_10b;this.html=this.html.replace(/(flashvars(=|\"\svalue=)\")[^\"]+/,"$1"+encodeURI(this.vars.join("&amp;")))};CallbackInfo.prototype.resetMovie=function(){var _10c=this.getFlashElement();var node=_10c.parentNode;node.replaceChild(dom.nodeFromHtml(this.html),_10c);this.setupFixHover()};CallbackInfo.prototype.setupFixHover=function(){var _10e=this.getFlashElement();if(!this._fixHover||!_10e){return}var node=_10e.parentNode;if(node.addEventListener){node.addEventListener("mouseout",_72.bind(this,"fixHover"),false)}else{if(node.attachEvent){node.attachEvent("onmouseout",_72.bind(this,"fixHover"))}}};CallbackInfo.prototype.fixHover=function(){this.call("resettext")}}; \ No newline at end of file
diff --git a/library/simplepie/demo/for_the_demo/simplepie.css b/library/simplepie/demo/for_the_demo/simplepie.css
deleted file mode 100644
index 3753cb96d..000000000
--- a/library/simplepie/demo/for_the_demo/simplepie.css
+++ /dev/null
@@ -1,397 +0,0 @@
-/*
-Theme Name: SimplePie
-Theme URI: http://simplepie.org
-Description: A simple, yet beautiful theme inspired by several cleanly designed websites.
-Version: 1.4
-Author: Ryan Parman
-Author URI: http://skyzyx.com
-Updated: 21 June 2007
-*/
-
-
-/*********************************************
-HYPERLINK STYLES
-*********************************************/
-a {
- color:#369;
- text-decoration:underline;
- padding:0 1px;
-}
-
-a:hover {
- color:#fff !important;
- background-color:#333;
- text-decoration:none;
- padding:0 1px;
-}
-
-a.nohover {
- text-decoration:none;
- border:none;
-}
-
-a.nohover:hover {
- background-color:transparent;
- border:none;
-}
-
-a.namelink {
- padding:0;
- margin:0;
- overflow:hidden;
- height:1px;
-}
-
-h4 a,
-.sample_feeds a {
- color:#000;
-}
-
-
-/*********************************************
-GENERAL STYLES
-*********************************************/
-body {
- /*font:12px/18px Verdana, sans-serif;*/
- font:14px/1.5em "Lucida Grande", Tahoma, sans-serif;
- letter-spacing:0px;
- color:#333;
- background-color:#fff;
- margin:0;
- padding:0;
-}
-
-div#site {
- width:600px;
- margin:50px auto 0 auto;
-}
-
-h1#logo {
- margin:0;
- padding:0;
- text-align:center;
-}
-
-h1#logo a,
-h1#logo a:hover {
- background-color:transparent;
- text-decoration:none;
- padding:0;
-}
-
-h2.image {
- margin:0;
- padding:0;
- text-align:center;
-}
-
-h3 {
- margin:20px 0 0 0;
- padding:0;
- font-size:1.5em;
-}
-
-h4 {
- margin:20px 0 0 0;
- padding:0;
- font-size:1.2em;
- letter-spacing:-1px;
-}
-
-h5 {
- margin:10px 0 0 0;
- padding:0;
- font-size:1em;
- font-weight:bold;
-}
-
-em {
- font-style:normal;
- background-color:#ffc;
-}
-
-p {
- margin:0;
- padding:5px 0;
-}
-
-ul, ol {
- margin:10px 0 10px 20px;
- padding:0 0 0 15px;
-}
-
-ul li, ol li {
- margin:0 0 7px 0;
- padding:0 0 0 3px;
-}
-
-form {
- margin:0;
- padding:0;
-}
-
-code {
- font-size:1em;
- background-color:#f3f3ff;
- color:#000;
-}
-
-div#site pre {
- background-color:#f3f3ff;
- color:#000080;
- border:1px dotted #000080;
- overflow:auto;
- padding:3px 5px;
-}
-
-blockquote {
- font-size:1em;
- color:#666;
- border-left:4px solid #666;
- margin:10px 0 10px 30px;
- padding:0 5px 0 10px;
- background:#f3f3f3 url(background_blockquote.png) repeat top left;
-}
-
-input, select, textarea {
- font-size:12px;
- line-height:1.2em;
- padding:2px;
-}
-
-input[type=text], select, textarea {
- background-color:#e9f5ff;
- border:1px solid #333;
-}
-
-input[type=text]:focus, select:focus, textarea:focus {
- background-color:#ffe;
-}
-
-.clearLeft {clear:left;}
-.clearRight {clear:right;}
-.clearBoth {clear:both;}
-.hide {display:none;}
-
-
-/*********************************************
-NAVIGATION STYLES
-*********************************************/
-div#header {
- background:#fff url(top_gradient.gif) repeat-x top left;
- margin:0;
- padding:0;
-}
-
-div#header form {
- margin:0;
- padding:0;
-}
-
-div#header div#headerInner {
- margin:0;
- padding:0;
-}
-
-div#header div#headerInner div#logoContainer {}
-
-div#header div#headerInner div#logoContainerInner {
- width:550px;
- margin:0 auto;
- padding:20px;
-}
-
-div#header div#headerInner div#logoContainer div#logo {
- float:left;
- width:200px;
-}
-
-div#header div#headerInner div#logoContainer div#logo a,
-div#header div#headerInner div#logoContainer div#logo a:hover {
- border:none;
- background:none;
-}
-
-div#header div#headerInner div#logoContainer div#feed {
- float:right;
- width:300px;
- text-align:right;
- padding:10px 0 0 0;
-}
-
-div#header div#headerInner div#logoContainer div#feed input.text {
- width:60%;
-}
-
-div#header div#headerInner div#menu {
- background:#eee url(background_menuitem_shadow.gif) repeat-x top left;
- border-top:2px solid #ccc;
- border-bottom:1px solid #ddd;
- text-align:center;
-}
-
-div#header div#headerInner div#menu table {
- width:auto;
- margin:0 auto;
-}
-
-div#header div#headerInner div#menu ul {
- display:block;
- width:100%;
- margin:0 auto;
- padding:0;
- font-size:12px;
-}
-
-div#header div#headerInner div#menu ul li {
- display:block;
- float:left;
-}
-
-div#header div#headerInner div#menu ul li a {
- display:block;
- margin:-2px 0 0 0;
- padding:5px 7px 8px 7px;
- text-decoration:none;
- color:#666 !important;
- background-color:transparent;
-}
-
-div#header div#headerInner div#menu ul li a:hover {
- display:block;
- margin:-2px 0 0 0;
- padding:5px 7px 8px 7px;
- text-decoration:none;
- color:#666;
- background:#fff url(background_menuitem_off.gif) no-repeat bottom right;
-}
-
-body#bodydemo div#header div#headerInner div#menu ul li#demo a {
- display:block;
- margin:-2px 0 0 0;
- padding:5px 7px 8px 7px;
- text-decoration:none;
- color:#333;
- font-weight:bold;
- background:#fff url(background_menuitem.gif) no-repeat bottom right;
-}
-
-
-/*********************************************
-CONTENT STYLES
-*********************************************/
-div.chunk {
- margin:20px 0 0 0;
- padding:0 0 10px 0;
- border-bottom:1px solid #ccc;
-}
-
-div.topchunk {
- margin:0 !important;
-}
-
-.footnote,
-.footnote a {
- font-size:12px;
- line-height:1.3em;
- color:#aaa;
-}
-
-.footnote em {
- background-color:transparent;
- font-style:italic;
-}
-
-.footnote code {
- background-color:transparent;
- font:11px/14px monospace;
- color:#aaa;
-}
-
-p.subscribe {
- background-color:#f3f3f3;
- font-size:12px;
- text-align:center;
-}
-
-p.highlight {
- background-color:#ffc;
- font-size:12px;
- text-align:center;
-}
-
-p.sample_feeds {
- font-size:12px;
- line-height:1.2em;
-}
-
-div.sp_errors {
- background-color:#eee;
- padding:5px;
- text-align:center;
- font-size:12px;
-}
-
-.noborder {
- border:none !important;
-}
-
-img.favicon {
- margin:0 4px -2px 0;
- width:16px;
- height:16px;
-}
-
-p.favicons a,
-p.favicons a:hover {
- border:none;
- background-color:transparent;
-}
-
-p.favicons img {
- border:none;
-}
-
-
-/*********************************************
-DEMO STYLES
-*********************************************/
-div#sp_input {
- background-color:#ffc;
- border:2px solid #f90;
- padding:5px;
- text-align:center;
-}
-
-div#sp_input input.text {
- border:1px solid #999;
- background:#e9f5ff url(feed.png) no-repeat 4px 50%;
- width:75%;
- padding:2px 2px 2px 28px;
- font:18px/22px "Lucida Grande", Verdana, sans-serif;
- font-weight:bold;
- letter-spacing:-1px;
-}
-
-form#sp_form {
- margin:15px 0;
-}
-
-div.focus {
- margin:0;
- padding:10px 20px;
- background-color:#efe;
-}
-
-p.sample_feeds {
- text-align:justify;
-}
-
-
-/*********************************************
-SIFR STYLES
-*********************************************/
-.sIFR-active h3.header {
- visibility:hidden;
- line-height:1em;
-}
diff --git a/library/simplepie/demo/for_the_demo/sleight.js b/library/simplepie/demo/for_the_demo/sleight.js
deleted file mode 100644
index 4b5058e9a..000000000
--- a/library/simplepie/demo/for_the_demo/sleight.js
+++ /dev/null
@@ -1,31 +0,0 @@
-/**********************************************************
-Sleight
-(c) 2001, Aaron Boodman
-http://www.youngpup.net
-**********************************************************/
-
-if (navigator.platform == "Win32" && navigator.appName == "Microsoft Internet Explorer" && window.attachEvent)
-{
- document.writeln('<style type="text/css">img { visibility:hidden; } </style>');
- window.attachEvent("onload", fnLoadPngs);
-}
-
-function fnLoadPngs()
-{
- var rslt = navigator.appVersion.match(/MSIE (\d+\.\d+)/, '');
- var itsAllGood = (rslt != null && Number(rslt[1]) >= 5.5);
-
- for (var i = document.images.length - 1, img = null; (img = document.images[i]); i--)
- {
- if (itsAllGood && img.src.match(/\.png$/i) != null)
- {
- var src = img.src;
- var div = document.createElement("DIV");
- div.style.filter = "progid:DXImageTransform.Microsoft.AlphaImageLoader(src='" + src + "', sizing='scale')"
- div.style.width = img.width + "px";
- div.style.height = img.height + "px";
- img.replaceNode(div);
- }
- img.style.visibility = "visible";
- }
-}
diff --git a/library/simplepie/demo/for_the_demo/source_files/place_audio_fireworksfile.png b/library/simplepie/demo/for_the_demo/source_files/place_audio_fireworksfile.png
deleted file mode 100644
index 2bfd87d0c..000000000
--- a/library/simplepie/demo/for_the_demo/source_files/place_audio_fireworksfile.png
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/source_files/place_video_fireworksfile.png b/library/simplepie/demo/for_the_demo/source_files/place_video_fireworksfile.png
deleted file mode 100644
index d0629769c..000000000
--- a/library/simplepie/demo/for_the_demo/source_files/place_video_fireworksfile.png
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/source_files/sIFR-r245/SifrStyleSheet.as b/library/simplepie/demo/for_the_demo/source_files/sIFR-r245/SifrStyleSheet.as
deleted file mode 100644
index 6a98ca552..000000000
--- a/library/simplepie/demo/for_the_demo/source_files/sIFR-r245/SifrStyleSheet.as
+++ /dev/null
@@ -1,71 +0,0 @@
-/*=:project
- scalable Inman Flash Replacement (sIFR) version 3.
-
- =:file
- Copyright: 2006 Mark Wubben.
- Author: Mark Wubben, <http://novemberborn.net/>
-
- =:history
- * IFR: Shaun Inman
- * sIFR 1: Mike Davidson, Shaun Inman and Tomas Jogin
- * sIFR 2: Mike Davidson, Shaun Inman, Tomas Jogin and Mark Wubben
-
- =:license
- This software is licensed and provided under the CC-GNU LGPL.
- See <http://creativecommons.org/licenses/LGPL/2.1/>
-*/
-
-import TextField.StyleSheet;
-
-class SifrStyleSheet extends TextField.StyleSheet {
- public var fontSize;
- public var latestLeading = 0;
-
- public function parseCSS(cssText:String) {
- var native = new TextField.StyleSheet();
- var parsed = native.parseCSS(cssText);
-
- if(!parsed) return false;
-
- var selectors = native.getStyleNames();
- for(var i = selectors.length - 1; i >= 0; i--) {
- var selector = selectors[i];
- var nativeStyle = native.getStyle(selector);
- var style = this.getStyle(selector) || nativeStyle;
- if(style != nativeStyle) {
- for(var property in nativeStyle) style[property] = nativeStyle[property];
- }
- this.setStyle(selector, style);
- }
-
- return true;
- }
-
- // Apply leading to the textFormat. Much thanks to <http://www.blog.lessrain.com/?p=98>.
- private function applyLeading(format, leading) {
- this.latestLeading = leading;
-
- if(leading >= 0) {
- format.leading = leading;
- return format;
- }
-
- // Workaround for negative leading, which is ignored otherwise.
- var newFormat = new TextFormat(null, null, null, null, null, null, null, null, null, null, null, null, leading);
- for(var property in format) if(property != 'leading') newFormat[property] = format[property];
-
- return newFormat;
- }
-
- public function transform(style) {
- var format = super.transform(style);
- if(style.leading) format = applyLeading(format, style.leading);
- if(style.letterSpacing) format.letterSpacing = style.letterSpacing;
- // Support font sizes relative to the size of .sIFR-root.
- if(this.fontSize && style.fontSize && style.fontSize.indexOf('%')) {
- format.size = this.fontSize * parseInt(style.fontSize) / 100;
- }
- format.kerning = _root.kerning == 'true' || !(_root.kerning == 'false') || sIFR.defaultKerning;
- return format;
- }
-} \ No newline at end of file
diff --git a/library/simplepie/demo/for_the_demo/source_files/sIFR-r245/_README_.txt b/library/simplepie/demo/for_the_demo/source_files/sIFR-r245/_README_.txt
deleted file mode 100644
index 2b9d32d20..000000000
--- a/library/simplepie/demo/for_the_demo/source_files/sIFR-r245/_README_.txt
+++ /dev/null
@@ -1,12 +0,0 @@
-This is a pre-release nightly of sIFR 3 (r245 to be exact). We (the SimplePie team) will be updating the
-sIFR code and font files from time to time as new releases of sIFR 3 are made available.
-
-In this folder you'll find a few Flash 8 files. The only one of you might want to mess with is sifr.fla.
- * Open it up
- * Double-click the rectangle in the middle
- * Select all
- * Change the font
-
-More information about sIFR 3 can be found here:
- * http://dev.novemberborn.net/sifr3/
- * http://wiki.novemberborn.net/sifr3/ \ No newline at end of file
diff --git a/library/simplepie/demo/for_the_demo/source_files/sIFR-r245/options.as b/library/simplepie/demo/for_the_demo/source_files/sIFR-r245/options.as
deleted file mode 100644
index 4d371954b..000000000
--- a/library/simplepie/demo/for_the_demo/source_files/sIFR-r245/options.as
+++ /dev/null
@@ -1,12 +0,0 @@
-// MTASC only parses as-files with class definitions, so here goes...
-class Options {
- public static function apply() {
- sIFR.fromLocal = true;
- sIFR.domains = ['*'];
-
- // Parsing `p.foo` might not work, see: <http://livedocs.macromedia.com/flash/mx2004/main_7_2/wwhelp/wwhimpl/common/html/wwhelp.htm?context=Flash_MX_2004&file=00001766.html>
- // Appearantly you have to use hex color codes as well, names are not supported!
-
- sIFR.styles.parseCSS('.foo { text-decoration: underline; }');
- }
-}
diff --git a/library/simplepie/demo/for_the_demo/source_files/sIFR-r245/sIFR.as b/library/simplepie/demo/for_the_demo/source_files/sIFR-r245/sIFR.as
deleted file mode 100644
index 4902e003f..000000000
--- a/library/simplepie/demo/for_the_demo/source_files/sIFR-r245/sIFR.as
+++ /dev/null
@@ -1,359 +0,0 @@
-/*=:project
- scalable Inman Flash Replacement (sIFR) version 3.
-
- =:file
- Copyright: 2006 Mark Wubben.
- Author: Mark Wubben, <http://novemberborn.net/>
-
- =:history
- * IFR: Shaun Inman
- * sIFR 1: Mike Davidson, Shaun Inman and Tomas Jogin
- * sIFR 2: Mike Davidson, Shaun Inman, Tomas Jogin and Mark Wubben
-
- =:license
- This software is licensed and provided under the CC-GNU LGPL.
- See <http://creativecommons.org/licenses/LGPL/2.1/>
-*/
-
-import SifrStyleSheet;
-
-class sIFR {
- public static var DEFAULT_TEXT = 'Rendered with sIFR 3, revision 245';
- public static var CSS_ROOT_CLASS = 'sIFR-root';
- public static var DEFAULT_WIDTH = 300;
- public static var DEFAULT_HEIGHT = 100;
- public static var DEFAULT_ANTI_ALIAS_TYPE = 'advanced';
- public static var MARGIN_LEFT = -3;
- public static var PADDING_BOTTOM = 5; // Extra padding to make sure the movie is high enough in most cases.
- public static var LEADING_REMAINDER = 2; // Flash uses the specified leading minus 2 as the applied leading.
-
- public static var MAX_FONT_SIZE = 126;
- public static var ALIASING_MAX_FONT_SIZE = 48;
-
- //= Holds CSS properties and other rendering properties for the Flash movie.
- // *Don't overwrite!*
- public static var styles:SifrStyleSheet = new SifrStyleSheet();
- //= Allow sIFR to be run from localhost
- public static var fromLocal:Boolean = true;
- //= Array containing domains for which sIFR may render text. Used to prevent
- // hotlinking. Use `*` to allow all domains.
- public static var domains:Array = [];
- //= Whether kerning is enabled by default. This can be overriden from the client side.
- // See also <http://livedocs.macromedia.com/flash/8/main/wwhelp/wwhimpl/common/html/wwhelp.htm?context=LiveDocs_Parts&file=00002811.html>.
- public static var defaultKerning:Boolean = true;
- //= Default value which can be overriden from the client side.
- // See also <http://livedocs.macromedia.com/flash/8/main/wwhelp/wwhimpl/common/html/wwhelp.htm?context=LiveDocs_Parts&file=00002788.html>.
- public static var defaultSharpness:Number = 0;
- //= Default value which can be overriden from the client side.
- // See also <http://livedocs.macromedia.com/flash/8/main/wwhelp/wwhimpl/common/html/wwhelp.htm?context=LiveDocs_Parts&file=00002787.html>.
- public static var defaultThickness:Number = 0;
- //= Default value which can be overriden from the client side.
- // See also <http://livedocs.macromedia.com/flash/8/main/wwhelp/wwhimpl/common/html/wwhelp.htm?context=LiveDocs_Parts&file=00002732.html>.
- public static var defaultOpacity:Number = -1; // Use client settings
- //= Default value which can be overriden from the client side.
- // See also <http://livedocs.macromedia.com/flash/8/main/wwhelp/wwhimpl/common/html/wwhelp.htm?context=LiveDocs_Parts&file=00002788.html>.
- public static var defaultBlendMode:Number = -1; // Use cliest settings
- //= Overrides the grid fit type as defined on the client side.
- // See also <http://livedocs.macromedia.com/flash/8/main/wwhelp/wwhimpl/common/html/wwhelp.htm?context=LiveDocs_Parts&file=00002444.html>.
- public static var enforcedGridFitType:String = null;
- //= If `true` sIFR won't override the anti aliasing set in the Flash IDE when exporting.
- // Thickness and sharpness won't be affected either.
- public static var preserveAntiAlias:Boolean = false;
- //= If `true` sIFR will disable anti-aliasing if the font size is larger than `ALIASING_MAX_FONT_SIZE`.
- // This setting is *independent* from `preserveAntiAlias`.
- public static var conditionalAntiAlias:Boolean = true;
- //= Sets the anti alias type. By default it's `DEFAULT_ANTI_ALIAS_TYPE`.
- // See also <http://livedocs.macromedia.com/flash/8/main/wwhelp/wwhimpl/common/html/wwhelp.htm?context=LiveDocs_Parts&file=00002733.html>.
- public static var antiAliasType:String = null;
- //= Flash filters can be added to this array and will be applied to the text field.
- public static var filters:Array = [];
- //= A mapping from the names of the filters to their actual objecs, used when transforming
- // filters defined on the client. You can add additional filters here so they'll be supported
- // when defined on the client.
- public static var filterMap:Object = {
- DisplacementMapFilter : flash.filters.DisplacementMapFilter,
- ColorMatrixFilter : flash.filters.ColorMatrixFilter,
- ConvolutionFilter : flash.filters.ConvolutionFilter,
- GradientBevelFilter : flash.filters.GradientBevelFilter,
- GradientGlowFilter : flash.filters.GradientGlowFilter,
- BevelFilter : flash.filters.BevelFilter,
- GlowFilter : flash.filters.GlowFilter,
- BlurFilter : flash.filters.BlurFilter,
- DropShadowFilter : flash.filters.DropShadowFilter
- };
-
- private static var instance;
-
- private var textField;
- private var content;
- private var realHeight;
- private var originalHeight;
- private var currentHeight;
- private var fontSize;
- private var tuneWidth;
- private var tuneHeight;
-
-
-
- //= Sets the default styles for `sIFR.styles`. This method is called
- // directly in `sifr.fla`, before options are applied.
- public static function setDefaultStyles() {
- sIFR.styles.parseCSS([
- '.', CSS_ROOT_CLASS, ' { color: #000000; }',
- 'strong { display: inline; font-weight: bold; } ',
- 'em { display: inline; font-style: italic; }',
- 'a { color: #0000FF; text-decoration: underline; }',
- 'a:hover { color: #0000FF; text-decoration: none; }'
- ].join(''));
- }
-
- //= Validates the domain sIFR is being used on.
- // Returns `true` if the domain is valid, `false` otherwise.
- public static function checkDomain():Boolean {
- if(sIFR.domains.length == 0) return true;
-
- var domain = (new LocalConnection()).domain();
- if(sIFR.fromLocal) sIFR.domains.push('localhost');
-
- for(var i = 0; i < sIFR.domains.length; i++) {
- var match = sIFR.domains[i];
- if(match == '*' || match == domain) return true;
-
- var wildcard = match.lastIndexOf('*');
- if(wildcard > -1) {
- match = match.substr(wildcard + 1);
- var matchPosition = domain.lastIndexOf(match);
- if(matchPosition > -1 && (matchPosition + match.length) == domain.length) return true;
- }
- }
-
- return false;
- }
-
- //= Runs sIFR. Called automatically.
- public static function run() {
- var holder = _root.holder;
- var content = checkDomain() ? unescape(_root.content) : DEFAULT_TEXT
- if(content == 'undefined' || content == '') {
- content = DEFAULT_TEXT;
- fscommand('resetmovie', '');
- } else fscommand('ping', '');
-
- // Sets stage parameters
- Stage.scaleMode = 'noscale';
- Stage.align = 'TL';
- Stage.showMenu = false;
-
- // Other parameters
- var opacity = parseInt(_root.opacity);
- if(!isNaN(opacity)) holder._alpha = sIFR.defaultOpacity == -1 ? opacity : sIFR.defaultOpacity;
- else holder._alpha = 100;
- _root.blendMode = sIFR.defaultBlendMode == -1 ? _root.blendmode : sIFR.defaultBlendMode;
-
- sIFR.instance = new sIFR(holder.txtF, content);
- // This should ignore resizes from the callback. Disabled for now.
-/* if(_root.zoomsupport == 'true') Stage.addListener({onResize: function() { sIFR.instance.scale() }});*/
-
- // Setup callbacks
- _root.watch('callbackTrigger', function() {
- sIFR.callback();
- return false;
- });
- }
-
- private static function eval(str) {
- var as;
-
- if(str.charAt(0) == '{') { // Ah, we need to create an object
- as = {};
- str = str.substring(1, str.length - 1);
- var $ = str.split(',');
- for(var i = 0; i < $.length; i++) {
- var $1 = $[i].split(':');
- as[$1[0]] = sIFR.eval($1[1]);
- }
- } else if(str.charAt(0) == '"') { // String
- as = str.substring(1, str.length - 1);
- } else if(str == 'true' || str == 'false') { // Boolean
- as = str == 'true';
- } else { // Float
- as = parseFloat(str);
- }
-
- return as;
- }
-
- private function applyFilters() {
- var $filters = this.textField.filters;
- $filters = $filters.concat(sIFR.filters);
-
- var $ = _root.flashfilters.split(';'); // name,prop:value,...;
- for(var i = 0; i < $.length; i++) {
- var $1 = $[i].split(',');
-
- var newFilter = new sIFR.filterMap[$1[0]]();
- for(var j = 1; j < $1.length; j++) {
- var $2 = $1[j].split(':');
- newFilter[$2[0]] = sIFR.eval(unescape($2[1]));
- }
-
- $filters.push(newFilter);
- }
-
- this.textField.filters = $filters;
- }
-
- private function sIFR(textField, content) {
- this.textField = textField;
- this.content = content;
-
- var offsetLeft = parseInt(_root.offsetleft);
- textField._x = MARGIN_LEFT + (isNaN(offsetLeft) ? 0 : offsetLeft);
- var offsetTop = parseInt(_root.offsettop);
- if(!isNaN(offsetTop)) textField._y += offsetTop;
-
- tuneWidth = parseInt(_root.tunewidth);
- if(isNaN(tuneWidth)) tuneWidth = 0;
- tuneHeight = parseInt(_root.tuneheight);
- if(isNaN(tuneHeight)) tuneHeight = 0;
-
- textField._width = tuneWidth + (isNaN(parseInt(_root.width)) ? DEFAULT_WIDTH : parseInt(_root.width));
- textField._height = tuneHeight + (isNaN(parseInt(_root.height)) ? DEFAULT_HEIGHT : parseInt(_root.height));
- textField.wordWrap = true;
- textField.selectable = _root.selectable == 'true';
- textField.gridFitType = sIFR.enforcedGridFitType || _root.gridfittype;
- this.applyFilters();
-
- // Determine font-size and the number of lines
- this.fontSize = parseInt(_root.size);
- if(isNaN(this.fontSize)) this.fontSize = 26;
- styles.fontSize = this.fontSize;
-
- if(!sIFR.preserveAntiAlias && (sIFR.conditionalAntiAlias && this.fontSize < ALIASING_MAX_FONT_SIZE
- || !sIFR.conditionalAntiAlias)) {
- textField.antiAliasType = sIFR.antiAliasType || DEFAULT_ANTI_ALIAS_TYPE;
- }
-
- if(!sIFR.preserveAntiAlias || !isNaN(parseInt(_root.sharpness))) {
- textField.sharpness = parseInt(_root.sharpness);
- }
- if(isNaN(textField.sharpness)) textField.sharpness = sIFR.defaultSharpness;
-
- if(!sIFR.preserveAntiAlias || !isNaN(parseInt(_root.thickness))) {
- textField.thickness = parseInt(_root.thickness);
- }
- if(isNaN(textField.thickness)) textField.thickness = sIFR.defaultThickness;
-
- // Set font-size and other styles
- sIFR.styles.parseCSS(unescape(_root.css));
-
- var rootStyle = styles.getStyle('.sIFR-root') || {};
- rootStyle.fontSize = this.fontSize; // won't go higher than 126!
- styles.setStyle('.sIFR-root', rootStyle);
- textField.styleSheet = styles;
-
- this.write(content);
- this.repaint();
- }
-
- private function repaint() {
- var leadingFix = this.isSingleLine() ? sIFR.styles.latestLeading : 0;
- if(leadingFix > 0) leadingFix -= LEADING_REMAINDER;
-
- // Flash wants to scroll the movie by one line, by adding the fontSize to the
- // textField height this is no longer happens. We also add the absolute tuneHeight,
- // to prevent a negative value from triggering the bug. We won't send the fake
- // value to the JavaScript side, though.
- textField._height = textField.textHeight + PADDING_BOTTOM + this.fontSize + Math.abs(tuneHeight) + tuneHeight - leadingFix;
- this.realHeight = textField._height - this.fontSize - Math.abs(tuneHeight);
- var arg = 'height:' + this.realHeight;
- if(_root.fitexactly == 'true') arg += ',width:' + (textField.textWidth + tuneWidth);
- fscommand('resize', arg);
-
- this.originalHeight = textField._height;
- this.currentHeight = Stage.height;
-
- textField._xscale = textField._yscale = parseInt(_root.zoom);
- }
-
- private function write(content) {
- this.textField.htmlText = ['<p class="', CSS_ROOT_CLASS, '">',
- content, '</p>'
- ].join('');
- }
-
- private function isSingleLine() {
- return Math.round((this.textField.textHeight - sIFR.styles.latestLeading) / this.fontSize) == 1;
- }
-
- //= Scales the text field to the new scale of the Flash movie itself.
- public function scale() {
- this.currentHeight = Stage.height;
- var scale = 100 * Math.round(this.currentHeight / this.originalHeight);
- textField._xscale = textField._yscale = scale;
- }
-
- private function calculateRatios() {
- var strings = ['X', 'X<br>X', 'X<br>X<br>X', 'X<br>X<br>X<br>X'];
- var results = {};
-
- for(var i = 1; i <= strings.length; i++) {
- var size = 6;
-
- this.write(strings[i - 1]);
- while(size < MAX_FONT_SIZE) {
- var rootStyle = sIFR.styles.getStyle('.sIFR-root') || {};
- rootStyle.fontSize = size;
- sIFR.styles.setStyle('.sIFR-root', rootStyle);
- this.textField.styleSheet = sIFR.styles;
- this.repaint();
- var ratio = (this.realHeight - PADDING_BOTTOM) / i / size;
- if(!results[size]) results[size] = ratio;
- else results[size] = ((i - 1) * results[size] + ratio) / i;
- size++;
- }
- }
-
- var sizes = [], ratios = [];
- var ratiosToSizes = {}, sizesToRatios = {};
-
- for(var size in results) {
- if(results[size] == Object.prototype[size]) continue;
- var ratio = results[size];
- ratiosToSizes[ratio] = Math.max(ratio, parseInt(size));
- }
-
- for(var ratio in ratiosToSizes) {
- if(ratiosToSizes[ratio] == Object.prototype[ratio]) continue;
- sizesToRatios[ratiosToSizes[ratio]] = roundDecimals(ratio, 2);
- sizes.push(ratiosToSizes[ratio]);
- }
-
- sizes.sort(function(a, b) { return a - b; });
- for(var j = 0; j < sizes.length - 1; j++) ratios.push(sizes[j], sizesToRatios[sizes[j]]);
- ratios.push(sizesToRatios[sizes[sizes.length - 1]]);
-
- fscommand('debug:ratios', '[' + ratios.join(',') + ']');
- }
-
- private function roundDecimals(value, decimals) {
- return Math.round(value * Math.pow(10, decimals)) / Math.pow(10, decimals);
- }
-
- public static function callback() {
- switch(_root.callbackType) {
- case 'replacetext':
- sIFR.instance.content = _root.callbackValue;
- sIFR.instance.write(_root.callbackValue);
- sIFR.instance.repaint();
- break;
- case 'resettext':
- sIFR.instance.write('');
- sIFR.instance.write(sIFR.instance.content);
- break;
- case 'ratios':
- sIFR.instance.calculateRatios();
- break;
- }
- }
-}
diff --git a/library/simplepie/demo/for_the_demo/source_files/sIFR-r245/sifr.fla b/library/simplepie/demo/for_the_demo/source_files/sIFR-r245/sifr.fla
deleted file mode 100644
index 2aa3f647f..000000000
--- a/library/simplepie/demo/for_the_demo/source_files/sIFR-r245/sifr.fla
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/top_gradient.gif b/library/simplepie/demo/for_the_demo/top_gradient.gif
deleted file mode 100644
index f77bd38f9..000000000
--- a/library/simplepie/demo/for_the_demo/top_gradient.gif
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/verdana.swf b/library/simplepie/demo/for_the_demo/verdana.swf
deleted file mode 100644
index baf035047..000000000
--- a/library/simplepie/demo/for_the_demo/verdana.swf
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/for_the_demo/yanone-kaffeesatz-bold.swf b/library/simplepie/demo/for_the_demo/yanone-kaffeesatz-bold.swf
deleted file mode 100644
index c812a79dc..000000000
--- a/library/simplepie/demo/for_the_demo/yanone-kaffeesatz-bold.swf
+++ /dev/null
Binary files differ
diff --git a/library/simplepie/demo/handler_image.php b/library/simplepie/demo/handler_image.php
deleted file mode 100644
index 49c3ec89b..000000000
--- a/library/simplepie/demo/handler_image.php
+++ /dev/null
@@ -1,6 +0,0 @@
-<?php
-// This should be modifed as your own use warrants.
-
-require_once('../simplepie.inc');
-SimplePie_Misc::display_cached_file($_GET['i'], './cache', 'spi');
-?>
diff --git a/library/simplepie/demo/index.php b/library/simplepie/demo/index.php
deleted file mode 100644
index 1481ba917..000000000
--- a/library/simplepie/demo/index.php
+++ /dev/null
@@ -1,295 +0,0 @@
-<?php
-// Start counting time for the page load
-$starttime = explode(' ', microtime());
-$starttime = $starttime[1] + $starttime[0];
-
-// Include SimplePie
-// Located in the parent directory
-include_once('../simplepie.inc');
-include_once('../idn/idna_convert.class.php');
-
-// Create a new instance of the SimplePie object
-$feed = new SimplePie();
-
-//$feed->force_fsockopen(true);
-
-// Make sure that page is getting passed a URL
-if (isset($_GET['feed']) && $_GET['feed'] !== '')
-{
- // Strip slashes if magic quotes is enabled (which automatically escapes certain characters)
- if (function_exists('get_magic_quotes_gpc') && get_magic_quotes_gpc())
- {
- $_GET['feed'] = stripslashes($_GET['feed']);
- }
-
- // Use the URL that was passed to the page in SimplePie
- $feed->set_feed_url($_GET['feed']);
-
- // XML dump
- $feed->enable_xml_dump(isset($_GET['xmldump']) ? true : false);
-}
-
-// Allow us to change the input encoding from the URL string if we want to. (optional)
-if (!empty($_GET['input']))
-{
- $feed->set_input_encoding($_GET['input']);
-}
-
-// Allow us to choose to not re-order the items by date. (optional)
-if (!empty($_GET['orderbydate']) && $_GET['orderbydate'] == 'false')
-{
- $feed->enable_order_by_date(false);
-}
-
-// Allow us to cache images in feeds. This will also bypass any hotlink blocking put in place by the website.
-if (!empty($_GET['image']) && $_GET['image'] == 'true')
-{
- $feed->set_image_handler('./handler_image.php');
-}
-
-// We'll enable the discovering and caching of favicons.
-$feed->set_favicon_handler('./handler_image.php');
-
-// Initialize the whole SimplePie object. Read the feed, process it, parse it, cache it, and
-// all that other good stuff. The feed's information will not be available to SimplePie before
-// this is called.
-$success = $feed->init();
-
-// We'll make sure that the right content type and character encoding gets set automatically.
-// This function will grab the proper character encoding, as well as set the content type to text/html.
-$feed->handle_content_type();
-
-// When we end our PHP block, we want to make sure our DOCTYPE is on the top line to make
-// sure that the browser snaps into Standards Mode.
-?><!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
-
-<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en-US" lang="en-US">
-<head>
-<title>SimplePie: Demo</title>
-
-<link rel="stylesheet" href="./for_the_demo/sIFR-screen.css" type="text/css" media="screen">
-<link rel="stylesheet" href="./for_the_demo/sIFR-print.css" type="text/css" media="print">
-<link rel="stylesheet" href="./for_the_demo/simplepie.css" type="text/css" media="screen, projector" />
-
-<script type="text/javascript" src="./for_the_demo/sifr.js"></script>
-<script type="text/javascript" src="./for_the_demo/sifr-config.js"></script>
-<script type="text/javascript" src="./for_the_demo/sleight.js"></script>
-
-</head>
-
-<body id="bodydemo">
-
-<div id="header">
- <div id="headerInner">
- <div id="logoContainer">
- <div id="logoContainerInner">
- <div align="center"><a href="http://simplepie.org"><img src="./for_the_demo/logo_simplepie_demo.png" alt="SimplePie Demo: PHP-based RSS and Atom feed handling" title="SimplePie Demo: PHP-based RSS and Atom feed handling" border="0" /></a></div>
- <div class="clearLeft"></div>
- </div>
-
- </div>
- <div id="menu">
- <!-- I know, I know, I know... tables for layout, I know. If a web standards evangelist (like me) has to resort
- to using tables for something, it's because no other possible solution could be found. This issue? No way to
- do centered floats purely with CSS. The table box model allows for a dynamic width while centered, while the
- CSS box model for DIVs doesn't allow for it. :( -->
- <table cellpadding="0" cellspacing="0" border="0"><tbody><tr><td>
-<ul><li id="demo"><a href="./">SimplePie Demo</a></li><li><a href="http://simplepie.org/wiki/faq/start">FAQ/Troubleshooting</a></li><li><a href="http://simplepie.org/support/">Support Forums</a></li><li><a href="http://simplepie.org/wiki/reference/start">API Reference</a></li><li><a href="http://simplepie.org/blog/">Weblog</a></li><li><a href="../test/test.php">Unit Tests</a></li></ul>
-
- <div class="clearLeft"></div>
- </td></tr></tbody></table>
- </div>
- </div>
-</div>
-
-<div id="site">
-
- <div id="content">
-
- <div class="chunk">
- <form action="" method="get" name="sp_form" id="sp_form">
- <div id="sp_input">
-
-
- <!-- If a feed has already been passed through the form, then make sure that the URL remains in the form field. -->
- <p><input type="text" name="feed" value="<?php if ($feed->subscribe_url()) echo $feed->subscribe_url(); ?>" class="text" id="feed_input" />&nbsp;<input type="submit" value="Read" class="button" /></p>
-
-
- </div>
- </form>
-
-
- <?php
- // Check to see if there are more than zero errors (i.e. if there are any errors at all)
- if ($feed->error())
- {
- // If so, start a <div> element with a classname so we can style it.
- echo '<div class="sp_errors">' . "\r\n";
-
- // ... and display it.
- echo '<p>' . htmlspecialchars($feed->error()) . "</p>\r\n";
-
- // Close the <div> element we opened.
- echo '</div>' . "\r\n";
- }
- ?>
-
- <!-- Here are some sample feeds. -->
- <p class="sample_feeds"><strong>Or try one of the following:</strong>
- <a href="?feed=http://www.詹姆斯.com/atomtests/iri/everything.atom" title="Test: International Domain Name support">詹姆斯.com</a>,
- <a href="?feed=http://www.adultswim.com/williams/podcast/tools/xml/video_rss.xml" title="Humor from the people who make [adult swim] cartoons.">adult swim</a>,
- <a href="?feed=http://afterdawn.com/news/afterdawn_rss.xml" title="Ripping, Burning, DRM, and the Dark Side of Consumer Electronics Media">Afterdawn</a>,
- <a href="?feed=http://feeds.feedburner.com/ajaxian" title="AJAX and Scripting News">Ajaxian</a>,
- <a href="?feed=http://www.andybudd.com/index.rdf&amp;image=true" title="Test: Bypass Image Hotlink Blocking">Andy Budd</a>,
- <a href="?feed=http://feeds.feedburner.com/AskANinja" title="Test: Embedded Enclosures">Ask a Ninja</a>,
- <a href="?feed=http://www.atomenabled.org/atom.xml" title="Test: Atom 1.0 Support">AtomEnabled.org</a>,
- <a href="?feed=http://newsrss.bbc.co.uk/rss/newsonline_world_edition/front_page/rss.xml" title="World News">BBC News</a>,
- <a href="?feed=http://newsrss.bbc.co.uk/rss/arabic/news/rss.xml" title="Test: Windows-1256 Encoding">BBC Arabic</a>,
- <a href="?feed=http://newsrss.bbc.co.uk/rss/chinese/simp/news/rss.xml" title="Test: GB2312 Encoding">BBC China</a>,
- <a href="?feed=http://newsrss.bbc.co.uk/rss/russian/news/rss.xml" title="Test: Windows-1251 Encoding">BBC Russia</a>,
- <a href="?feed=http://inessential.com/xml/rss.xml" title="Developer of NetNewsWire">Brent Simmons</a>,
- <a href="?feed=http://www.channelfrederator.com/rss" title="Test: Embedded Enclosures">Channel Frederator</a>,
- <a href="?feed=http://rss.cnn.com/rss/cnn_topstories.rss" title="World News">CNN</a>,
- <a href="?feed=http://digg.com/rss/index.xml" title="Tech news. Better than Slashdot.">Digg</a>,
- <a href="?feed=http://revision3.com/diggnation/feed/quicktime-large" title="Tech and industry videocast.">Diggnation</a>,
- <a href="?feed=http://www.flickr.com/services/feeds/photos_public.gne?format=rss2" title="Flickr Photos">Flickr</a>,
- <a href="?feed=http://news.google.com/?output=rss" title="World News">Google News</a>,
- <a href="?feed=http://video.google.com/videofeed?type=top100new&num=20&output=rss" title="Test: Media RSS Support">Google Video</a>,
- <a href="?feed=http://blogs.law.harvard.edu/home/feed/rdf/" title="Test: Tag Stripping">Harvard Law</a>,
- <a href="?feed=http://hagada.org.il/hagada/html/backend.php" title="Test: Window-1255 Encoding">Hebrew Language</a>,
- <a href="?feed=http://www.infoworld.com/rss/news.xml" title="Test: Ad Stripping">InfoWorld</a>,
- <a href="?feed=http://phobos.apple.com/WebObjects/MZStore.woa/wpa/MRSS/topsongs/limit=10/rss.xml&orderbydate=false" title="Test: Tag Stripping">iTunes</a>,
- <a href="?feed=http://blog.japan.cnet.com/lessig/index.rdf" title="Test: EUC-JP Encoding">Japanese Language</a>,
- <a href="?feed=http://nurapt.kaist.ac.kr/~jamaica/htmls/blog/rss.php&amp;input=EUC-KR" title="Test: EUC-KR Encoding">Korean Language</a>,
- <a href="?feed=http://mir.aculo.us/xml/rss/feed.xml" title="Weblog for the developer of Scriptaculous">mir.aculo.us</a>,
- <a href="?feed=http://images.apple.com/trailers/rss/newtrailers.rss" title="Apple's QuickTime movie trailer site">Movie Trailers</a>,
- <a href="?feed=http://www.newspond.com/rss/main.xml" title="Tech and Science News">Newspond</a>,
- <a href="?feed=http://nick.typepad.com/blog/index.rss" title="Developer of TopStyle and FeedDemon">Nick Bradbury</a>,
- <a href="?feed=http://feeds.feedburner.com/ok-cancel" title="Usability comics and commentary">OK/Cancel</a>,
- <a href="?feed=http://osnews.com/files/recent.rdf" title="News about every OS ever">OS News</a>,
- <a href="?feed=http://weblog.philringnalda.com/feed/" title="Test: Atom 1.0 Support">Phil Ringnalda</a>,
- <a href="?feed=http://kabili.libsyn.com/rss" title="Test: Improved enclosure type sniffing">Photoshop Videocast</a>,
- <a href="?feed=http://www.pariurisportive.com/blog/xmlsrv/rss2.php?blog=2" title="Test: ISO-8859-1 Encoding">Romanian Language</a>,
- <a href="?feed=http://www.erased.info/rss2.php" title="Test: KOI8-R Encoding">Russian Language</a>,
- <a href="?feed=http://www.upsaid.com/isis/index.rdf" title="Test: BIG5 Encoding">Traditional Chinese Language</a>,
- <a href="?feed=http://technorati.com/watchlists/rss.html?wid=29290" title="Technorati watch for SimplePie">Technorati</a>,
- <a href="?feed=http://www.tbray.org/ongoing/ongoing.atom" title="Test: Atom 1.0 Support">Tim Bray</a>,
- <a href="?feed=http://tuaw.com/rss.xml" title="Apple News">TUAW</a>,
- <a href="?feed=http://www.tvgasm.com/atom.xml&amp;image=true" title="Test: Bypass Image Hotlink Blocking">TVgasm</a>,
- <a href="?feed=http://uneasysilence.com/feed/" title="Interesting tech randomness">UNEASYsilence</a>,
- <a href="?feed=http://feeds.feedburner.com/web20Show" title="Test: Embedded Enclosures">Web 2.0 Show</a>,
- <a href="?feed=http://windowsvistablog.com/blogs/MainFeed.aspx" title="Test: Tag Stripping">Windows Vista Blog</a>,
- <a href="?feed=http://xkcd.com/rss.xml" title="Test: LightHTTPd and GZipping">XKCD</a>,
- <a href="?feed=http://rss.news.yahoo.com/rss/topstories" title="World News">Yahoo! News</a>,
- <a href="?feed=http://youtube.com/rss/global/top_favorites.rss" title="Funny user-submitted videos">You Tube</a>,
- <a href="?feed=http://zeldman.com/rss/" title="The father of the web standards movement">Zeldman</a></p>
-
- </div>
-
- <div id="sp_results">
-
- <!-- As long as the feed has data to work with... -->
- <?php if ($success): ?>
- <div class="chunk focus" align="center">
-
- <!-- If the feed has a link back to the site that publishes it (which 99% of them do), link the feed's title to it. -->
- <h3 class="header"><?php if ($feed->get_link()) echo '<a href="' . $feed->get_link() . '">'; echo $feed->get_title(); if ($feed->get_link()) echo '</a>'; ?></h3>
-
- <!-- If the feed has a description, display it. -->
- <?php echo $feed->get_description(); ?>
-
- </div>
-
- <!-- Add subscribe links for several different aggregation services -->
- <p class="subscribe"><strong>Subscribe:</strong> <a href="<?php echo $feed->subscribe_bloglines(); ?>">Bloglines</a>, <a href="<?php echo $feed->subscribe_google(); ?>">Google Reader</a>, <a href="<?php echo $feed->subscribe_msn(); ?>">My MSN</a>, <a href="<?php echo $feed->subscribe_netvibes(); ?>">Netvibes</a>, <a href="<?php echo $feed->subscribe_newsburst(); ?>">Newsburst</a><br /><a href="<?php echo $feed->subscribe_newsgator(); ?>">Newsgator</a>, <a href="<?php echo $feed->subscribe_odeo(); ?>">Odeo</a>, <a href="<?php echo $feed->subscribe_podnova(); ?>">Podnova</a>, <a href="<?php echo $feed->subscribe_rojo(); ?>">Rojo</a>, <a href="<?php echo $feed->subscribe_yahoo(); ?>">My Yahoo!</a>, <a href="<?php echo $feed->subscribe_feed(); ?>">Desktop Reader</a></p>
-
-
- <!-- Let's begin looping through each individual news item in the feed. -->
- <?php foreach($feed->get_items() as $item): ?>
- <div class="chunk">
-
- <?php
- // Let's add a favicon for each item. If one doesn't exist, we'll use an alternate one.
- if (!$favicon = $feed->get_favicon())
- {
- $favicon = './for_the_demo/favicons/alternate.png';
- }
- ?>
-
- <!-- If the item has a permalink back to the original post (which 99% of them do), link the item's title to it. -->
- <h4><img src="<?php echo $favicon; ?>" alt="Favicon" class="favicon" /><?php if ($item->get_permalink()) echo '<a href="' . $item->get_permalink() . '">'; echo $item->get_title(); if ($item->get_permalink()) echo '</a>'; ?>&nbsp;<span class="footnote"><?php echo $item->get_date('j M Y, g:i a'); ?></span></h4>
-
- <!-- Display the item's primary content. -->
- <?php echo $item->get_content(); ?>
-
- <?php
- // Check for enclosures. If an item has any, set the first one to the $enclosure variable.
- if ($enclosure = $item->get_enclosure(0))
- {
- // Use the embed() method to embed the enclosure into the page inline.
- echo '<div align="center">';
- echo '<p>' . $enclosure->embed(array(
- 'audio' => './for_the_demo/place_audio.png',
- 'video' => './for_the_demo/place_video.png',
- 'mediaplayer' => './for_the_demo/mediaplayer.swf',
- 'altclass' => 'download'
- )) . '</p>';
-
- if ($enclosure->get_link() && $enclosure->get_type())
- {
- echo '<p class="footnote" align="center">(' . $enclosure->get_type();
- if ($enclosure->get_size())
- {
- echo '; ' . $enclosure->get_size() . ' MB';
- }
- echo ')</p>';
- }
- if ($enclosure->get_thumbnail())
- {
- echo '<div><img src="' . $enclosure->get_thumbnail() . '" alt="" /></div>';
- }
- echo '</div>';
- }
- ?>
-
- <!-- Add links to add this post to one of a handful of services. -->
- <p class="footnote favicons" align="center">
- <a href="<?php echo $item->add_to_blinklist(); ?>" title="Add post to Blinklist"><img src="./for_the_demo/favicons/blinklist.png" alt="Blinklist" /></a>
- <a href="<?php echo $item->add_to_blogmarks(); ?>" title="Add post to Blogmarks"><img src="./for_the_demo/favicons/blogmarks.png" alt="Blogmarks" /></a>
- <a href="<?php echo $item->add_to_delicious(); ?>" title="Add post to del.icio.us"><img src="./for_the_demo/favicons/delicious.png" alt="del.icio.us" /></a>
- <a href="<?php echo $item->add_to_digg(); ?>" title="Digg this!"><img src="./for_the_demo/favicons/digg.png" alt="Digg" /></a>
- <a href="<?php echo $item->add_to_magnolia(); ?>" title="Add post to Ma.gnolia"><img src="./for_the_demo/favicons/magnolia.png" alt="Ma.gnolia" /></a>
- <a href="<?php echo $item->add_to_myweb20(); ?>" title="Add post to My Web 2.0"><img src="./for_the_demo/favicons/myweb2.png" alt="My Web 2.0" /></a>
- <a href="<?php echo $item->add_to_newsvine(); ?>" title="Add post to Newsvine"><img src="./for_the_demo/favicons/newsvine.png" alt="Newsvine" /></a>
- <a href="<?php echo $item->add_to_reddit(); ?>" title="Add post to Reddit"><img src="./for_the_demo/favicons/reddit.png" alt="Reddit" /></a>
- <a href="<?php echo $item->add_to_segnalo(); ?>" title="Add post to Segnalo"><img src="./for_the_demo/favicons/segnalo.png" alt="Segnalo" /></a>
- <a href="<?php echo $item->add_to_simpy(); ?>" title="Add post to Simpy"><img src="./for_the_demo/favicons/simpy.png" alt="Simpy" /></a>
- <a href="<?php echo $item->add_to_spurl(); ?>" title="Add post to Spurl"><img src="./for_the_demo/favicons/spurl.png" alt="Spurl" /></a>
- <a href="<?php echo $item->add_to_wists(); ?>" title="Add post to Wists"><img src="./for_the_demo/favicons/wists.png" alt="Wists" /></a>
- <a href="<?php echo $item->search_technorati(); ?>" title="Who's linking to this post?"><img src="./for_the_demo/favicons/technorati.png" alt="Technorati" /></a>
- </p>
-
- </div>
-
- <!-- Stop looping through each item once we've gone through all of them. -->
- <?php endforeach; ?>
-
- <!-- From here on, we're no longer using data from the feed. -->
- <?php endif; ?>
-
- </div>
-
- <div>
- <!-- Display how fast the page was rendered. -->
- <p class="footnote">Page processed in <?php $mtime = explode(' ', microtime()); echo round($mtime[0] + $mtime[1] - $starttime, 3); ?> seconds.</p>
-
- <!-- Display the version of SimplePie being loaded. -->
- <p class="footnote">Powered by <a href="<?php echo SIMPLEPIE_URL; ?>"><?php echo SIMPLEPIE_NAME . ' ' . SIMPLEPIE_VERSION . ', Build ' . SIMPLEPIE_BUILD; ?></a>. Run the <a href="../compatibility_test/sp_compatibility_test.php">SimplePie Compatibility Test</a>. SimplePie is &copy; 2004&ndash;<?php echo date('Y'); ?>, Ryan Parman and Geoffrey Sneddon, and licensed under the <a href="http://www.opensource.org/licenses/bsd-license.php">BSD License</a>.</p>
- </div>
-
- </div>
-
-</div>
-
-</body>
-</html>
diff --git a/library/simplepie/demo/minimalistic.php b/library/simplepie/demo/minimalistic.php
deleted file mode 100644
index 56509c00c..000000000
--- a/library/simplepie/demo/minimalistic.php
+++ /dev/null
@@ -1,137 +0,0 @@
-<?php
-
-function microtime_float()
-{
- if (version_compare(phpversion(), '5.0.0', '>='))
- {
- return microtime(true);
- }
- else
- {
- list($usec, $sec) = explode(' ', microtime());
- return ((float) $usec + (float) $sec);
- }
-}
-
-$start = microtime_float();
-
-include('../simplepie.inc');
-
-// Parse it
-$feed = new SimplePie();
-if (!empty($_GET['feed']))
-{
- if (get_magic_quotes_gpc())
- {
- $_GET['feed'] = stripslashes($_GET['feed']);
- }
- $feed->set_feed_url($_GET['feed']);
- $feed->init();
-}
-$feed->handle_content_type();
-
-?><!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
-
-<html xmlns="http://www.w3.org/1999/xhtml">
-<head>
-<title><?php echo (empty($_GET['feed'])) ? 'SimplePie' : 'SimplePie: ' . $feed->get_title(); ?></title>
-
-<!-- META HTTP-EQUIV -->
-<meta http-equiv="content-type" content="text/html; charset=<?php echo ($feed->get_encoding()) ? $feed->get_encoding() : 'UTF-8'; ?>" />
-<meta http-equiv="imagetoolbar" content="false" />
-
-<style type="text/css">
-html, body {
- height:100%;
- margin:0;
- padding:0;
-}
-
-h1 {
- background-color:#333;
- color:#fff;
- font-size:3em;
- margin:0;
- padding:5px 15px;
- text-align:center;
-}
-
-div#footer {
- padding:5px 0;
-}
-
-div#footer,
-div#footer a {
- text-align:center;
- font-size:0.7em;
-}
-
-div#footer a {
- text-decoration:underline;
-}
-
-code {
- background-color:#f3f3ff;
- color:#000;
-}
-
-pre {
- background-color:#f3f3ff;
- color:#000080;
- border:1px dotted #000080;
- padding:3px 5px;
-}
-
-form {
- margin:0;
- padding:0;
-}
-
-div.chunk {
- border-bottom:1px solid #ccc;
-}
-
-form#sp_form {
- text-align:center;
- margin:0;
- padding:0;
-}
-
-form#sp_form input.text {
- width:85%;
-}
-</style>
-
-</head>
-
-<body>
- <h1><?php echo (empty($_GET['feed'])) ? 'SimplePie' : 'SimplePie: ' . $feed->get_title(); ?></h1>
-
- <form action="" method="get" name="sp_form" id="sp_form">
- <p><input type="text" name="feed" value="<?php echo ($feed->subscribe_url()) ? htmlspecialchars($feed->subscribe_url()) : 'http://'; ?>" class="text" id="feed_input" />&nbsp;<input type="submit" value="Read" class="button" /></p>
- </form>
-
- <div id="sp_results">
- <?php if ($feed->data): ?>
- <?php $items = $feed->get_items(); ?>
- <p align="center"><span style="background-color:#ffc;">Displaying <?php echo $feed->get_item_quantity(); ?> most recent entries.</span></p>
- <?php foreach($items as $item): ?>
- <div class="chunk" style="padding:0 5px;">
- <h4><a href="<?php echo $item->get_permalink(); ?>"><?php echo $item->get_title(); ?></a> <?php echo $item->get_date('j M Y'); ?></h4>
- <?php echo $item->get_content(); ?>
- <?php
- if ($enclosure = $item->get_enclosure(0))
- echo '<p><a href="' . $enclosure->get_link() . '" class="download"><img src="./for_the_demo/mini_podcast.png" alt="Podcast" title="Download the Podcast" border="0" /></a></p>';
- ?>
- </div>
- <?php endforeach; ?>
- </div>
- <?php endif; ?>
- </div>
-
- <div id="footer">
- Powered by <?php echo SIMPLEPIE_LINKBACK; ?>, a product of <a href="http://www.skyzyx.com">Skyzyx Technologies</a>.<br />
- Page created in <?php echo round(microtime_float()-$start, 3); ?> seconds.
- </div>
-</body>
-</html>
diff --git a/library/simplepie/demo/multifeeds.php b/library/simplepie/demo/multifeeds.php
deleted file mode 100644
index b23d792a2..000000000
--- a/library/simplepie/demo/multifeeds.php
+++ /dev/null
@@ -1,108 +0,0 @@
-<?php
-/********************************************************************
-MULTIFEEDS TEST PAGE
-
-Nothing too exciting here. Just a sample page that demos integrated
-Multifeeds support as well as cached favicons and perhaps a few other
-things.
-
-Lots of this code is commented to help explain some of the new stuff.
-Code was tested in PHP 5.2.2, but *should* also work with earlier
-versions of PHP, as supported by SimplePie (PHP 4.1).
-
-********************************************************************/
-
-// Include the SimplePie library, and the one that handles internationalized domain names.
-require_once('../simplepie.inc');
-require_once('../idn/idna_convert.class.php');
-
-// Initialize some feeds for use.
-$feed = new SimplePie();
-$feed->set_feed_url(array(
- 'http://rss.news.yahoo.com/rss/topstories',
- 'http://news.google.com/?output=atom',
- 'http://rss.cnn.com/rss/cnn_topstories.rss'
-));
-
-// When we set these, we need to make sure that the handler_image.php file is also trying to read from the same cache directory that we are.
-$feed->set_favicon_handler('./handler_image.php');
-$feed->set_image_handler('./handler_image.php');
-
-// Initialize the feed.
-$feed->init();
-
-// Make sure the page is being served with the UTF-8 headers.
-$feed->handle_content_type();
-
-// Begin the (X)HTML page.
-?><!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
- "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
-<head>
- <title>Multifeeds Test page</title>
- <link rel="stylesheet" href="../demo/for_the_demo/simplepie.css" type="text/css" media="screen" title="SimplePie Styles" charset="utf-8" />
- <style type="text/css">
- div#site {
- width:600px;
- }
- span.footnote {
- white-space:nowrap;
- }
- h1 {
- line-height:1.4em;
- }
- h4 {
- padding-left:20px;
- background-color:transparent;
- background-repeat:no-repeat;
- background-position:0 1px;
- }
- .clearBoth {
- clear:both;
- }
- </style>
-</head>
-<body>
-<div id="site">
-
- <?php if ($feed->error): ?>
- <p><?=$feed->error()?></p>
- <?php endif ?>
-
- <div class="chunk">
- <h1>Quick-n-Dirty Multifeeds Demo</a></h1>
- </div>
-
- <?php
- // Let's loop through each item in the feed.
- foreach($feed->get_items() as $item):
-
- // Let's give ourselves a reference to the parent $feed object for this particular item.
- $feed = $item->get_feed();
- ?>
-
- <div class="chunk">
- <h4 style="background-image:url(<?php echo $feed->get_favicon(); ?>);"><a href="<?php echo $item->get_permalink(); ?>"><?php echo html_entity_decode($item->get_title(), ENT_QUOTES, 'UTF-8'); ?></a></h4>
-
- <!-- get_content() prefers full content over summaries -->
- <?php echo $item->get_content(); ?>
-
- <?php if ($enclosure = $item->get_enclosure()): ?>
- <div>
- <?php echo $enclosure->native_embed(array(
- // New 'mediaplayer' attribute shows off Flash-based MP3 and FLV playback.
- 'mediaplayer' => '../demo/for_the_demo/mediaplayer.swf'
- )); ?>
- </div>
- <?php endif; ?>
-
- <p class="footnote">Source: <a href="<?php echo $feed->get_permalink(); ?>"><?php echo $feed->get_title(); ?></a> | <?php echo $item->get_date('j M Y | g:i a'); ?></p>
- </div>
-
- <?php endforeach ?>
-
- <p class="footnote">This is a test of the emergency broadcast system. This is only a test&hellip; beeeeeeeeeeeeeeeeeeeeeeeeeep!</p>
-
-</div>
-</body>
-</html> \ No newline at end of file
diff --git a/library/simplepie/demo/test.php b/library/simplepie/demo/test.php
deleted file mode 100644
index 5b9943abb..000000000
--- a/library/simplepie/demo/test.php
+++ /dev/null
@@ -1,62 +0,0 @@
-<?php
-include_once('../simplepie.inc');
-include_once('../idn/idna_convert.class.php');
-
-// Parse it
-$feed = new SimplePie();
-if (isset($_GET['feed']) && $_GET['feed'] !== '')
-{
- if (get_magic_quotes_gpc())
- {
- $_GET['feed'] = stripslashes($_GET['feed']);
- }
- $feed->set_feed_url($_GET['feed']);
- $feed->enable_cache(false);
- $starttime = explode(' ', microtime());
- $starttime = $starttime[1] + $starttime[0];
- $feed->init();
- $endtime = explode(' ', microtime());
- $endtime = $endtime[1] + $endtime[0];
- $time = $endtime - $starttime;
-}
-else
-{
- $time = 'null';
-}
-
-$feed->handle_content_type();
-
-?>
-<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01//EN">
-<title>SimplePie Test</title>
-<pre>
-<?php
-
-// memory_get_peak_usage() only exists on PHP 5.2 and higher if PHP is compiled with the --enable-memory-limit configuration option or on PHP 5.2.1 and higher (which runs as if --enable-memory-limit was on, with no option)
-if (function_exists('memory_get_peak_usage'))
-{
- var_dump($time, memory_get_usage(), memory_get_peak_usage());
-}
-// memory_get_usage() only exists if PHP is compiled with the --enable-memory-limit configuration option or on PHP 5.2.1 and higher (which runs as if --enable-memory-limit was on, with no option)
-else if (function_exists('memory_get_usage'))
-{
- var_dump($time, memory_get_usage());
-}
-else
-{
- var_dump($time);
-}
-
-// Output buffer
-function callable_htmlspecialchars($string)
-{
- return htmlspecialchars($string);
-}
-ob_start('callable_htmlspecialchars');
-
-// Output
-print_r($feed);
-ob_end_flush();
-
-?>
-</pre> \ No newline at end of file
diff --git a/library/simplepie/idn/idna_convert.class.php b/library/simplepie/idn/idna_convert.class.php
deleted file mode 100644
index ed2bae26d..000000000
--- a/library/simplepie/idn/idna_convert.class.php
+++ /dev/null
@@ -1,969 +0,0 @@
-<?php
-// {{{ license
-
-/* vim: set expandtab tabstop=4 shiftwidth=4 softtabstop=4 foldmethod=marker: */
-//
-// +----------------------------------------------------------------------+
-// | This library is free software; you can redistribute it and/or modify |
-// | it under the terms of the GNU Lesser General Public License as |
-// | published by the Free Software Foundation; either version 2.1 of the |
-// | License, or (at your option) any later version. |
-// | |
-// | This library 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 |
-// | Lesser General Public License for more details. |
-// | |
-// | You should have received a copy of the GNU Lesser General Public |
-// | License along with this library; if not, write to the Free Software |
-// | Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 |
-// | USA. |
-// +----------------------------------------------------------------------+
-//
-
-// }}}
-
-/**
- * Encode/decode Internationalized Domain Names.
- *
- * The class allows to convert internationalized domain names
- * (see RFC 3490 for details) as they can be used with various registries worldwide
- * to be translated between their original (localized) form and their encoded form
- * as it will be used in the DNS (Domain Name System).
- *
- * The class provides two public methods, encode() and decode(), which do exactly
- * what you would expect them to do. You are allowed to use complete domain names,
- * simple strings and complete email addresses as well. That means, that you might
- * use any of the following notations:
- *
- * - www.nörgler.com
- * - xn--nrgler-wxa
- * - xn--brse-5qa.xn--knrz-1ra.info
- *
- * Unicode input might be given as either UTF-8 string, UCS-4 string or UCS-4
- * array. Unicode output is available in the same formats.
- * You can select your preferred format via {@link set_paramter()}.
- *
- * ACE input and output is always expected to be ASCII.
- *
- * @author Matthias Sommerfeld <mso@phlylabs.de>
- * @copyright 2004-2007 phlyLabs Berlin, http://phlylabs.de
- * @version 0.5.1
- *
- */
-class idna_convert
-{
- /**
- * Holds all relevant mapping tables, loaded from a seperate file on construct
- * See RFC3454 for details
- *
- * @var array
- * @access private
- */
- var $NP = array();
-
- // Internal settings, do not mess with them
- var $_punycode_prefix = 'xn--';
- var $_invalid_ucs = 0x80000000;
- var $_max_ucs = 0x10FFFF;
- var $_base = 36;
- var $_tmin = 1;
- var $_tmax = 26;
- var $_skew = 38;
- var $_damp = 700;
- var $_initial_bias = 72;
- var $_initial_n = 0x80;
- var $_sbase = 0xAC00;
- var $_lbase = 0x1100;
- var $_vbase = 0x1161;
- var $_tbase = 0x11A7;
- var $_lcount = 19;
- var $_vcount = 21;
- var $_tcount = 28;
- var $_ncount = 588; // _vcount * _tcount
- var $_scount = 11172; // _lcount * _tcount * _vcount
- var $_error = false;
-
- // See {@link set_paramter()} for details of how to change the following
- // settings from within your script / application
- var $_api_encoding = 'utf8'; // Default input charset is UTF-8
- var $_allow_overlong = false; // Overlong UTF-8 encodings are forbidden
- var $_strict_mode = false; // Behave strict or not
-
- // The constructor
- function idna_convert($options = false)
- {
- $this->slast = $this->_sbase + $this->_lcount * $this->_vcount * $this->_tcount;
- if (function_exists('file_get_contents')) {
- $this->NP = unserialize(file_get_contents(dirname(__FILE__).'/npdata.ser'));
- } else {
- $this->NP = unserialize(join('', file(dirname(__FILE__).'/npdata.ser')));
- }
- // If parameters are given, pass these to the respective method
- if (is_array($options)) {
- return $this->set_parameter($options);
- }
- return true;
- }
-
- /**
- * Sets a new option value. Available options and values:
- * [encoding - Use either UTF-8, UCS4 as array or UCS4 as string as input ('utf8' for UTF-8,
- * 'ucs4_string' and 'ucs4_array' respectively for UCS4); The output is always UTF-8]
- * [overlong - Unicode does not allow unnecessarily long encodings of chars,
- * to allow this, set this parameter to true, else to false;
- * default is false.]
- * [strict - true: strict mode, good for registration purposes - Causes errors
- * on failures; false: loose mode, ideal for "wildlife" applications
- * by silently ignoring errors and returning the original input instead
- *
- * @param mixed Parameter to set (string: single parameter; array of Parameter => Value pairs)
- * @param string Value to use (if parameter 1 is a string)
- * @return boolean true on success, false otherwise
- * @access public
- */
- function set_parameter($option, $value = false)
- {
- if (!is_array($option)) {
- $option = array($option => $value);
- }
- foreach ($option as $k => $v) {
- switch ($k) {
- case 'encoding':
- switch ($v) {
- case 'utf8':
- case 'ucs4_string':
- case 'ucs4_array':
- $this->_api_encoding = $v;
- break;
- default:
- $this->_error('Set Parameter: Unknown parameter '.$v.' for option '.$k);
- return false;
- }
- break;
- case 'overlong':
- $this->_allow_overlong = ($v) ? true : false;
- break;
- case 'strict':
- $this->_strict_mode = ($v) ? true : false;
- break;
- default:
- $this->_error('Set Parameter: Unknown option '.$k);
- return false;
- }
- }
- return true;
- }
-
- /**
- * Decode a given ACE domain name
- * @param string Domain name (ACE string)
- * [@param string Desired output encoding, see {@link set_parameter}]
- * @return string Decoded Domain name (UTF-8 or UCS-4)
- * @access public
- */
- function decode($input, $one_time_encoding = false)
- {
- // Optionally set
- if ($one_time_encoding) {
- switch ($one_time_encoding) {
- case 'utf8':
- case 'ucs4_string':
- case 'ucs4_array':
- break;
- default:
- $this->_error('Unknown encoding '.$one_time_encoding);
- return false;
- }
- }
- // Make sure to drop any newline characters around
- $input = trim($input);
-
- // Negotiate input and try to determine, whether it is a plain string,
- // an email address or something like a complete URL
- if (strpos($input, '@')) { // Maybe it is an email address
- // No no in strict mode
- if ($this->_strict_mode) {
- $this->_error('Only simple domain name parts can be handled in strict mode');
- return false;
- }
- list ($email_pref, $input) = explode('@', $input, 2);
- $arr = explode('.', $input);
- foreach ($arr as $k => $v) {
- if (preg_match('!^'.preg_quote($this->_punycode_prefix, '!').'!', $v)) {
- $conv = $this->_decode($v);
- if ($conv) $arr[$k] = $conv;
- }
- }
- $input = join('.', $arr);
- $arr = explode('.', $email_pref);
- foreach ($arr as $k => $v) {
- if (preg_match('!^'.preg_quote($this->_punycode_prefix, '!').'!', $v)) {
- $conv = $this->_decode($v);
- if ($conv) $arr[$k] = $conv;
- }
- }
- $email_pref = join('.', $arr);
- $return = $email_pref . '@' . $input;
- } elseif (preg_match('![:\./]!', $input)) { // Or a complete domain name (with or without paths / parameters)
- // No no in strict mode
- if ($this->_strict_mode) {
- $this->_error('Only simple domain name parts can be handled in strict mode');
- return false;
- }
- $parsed = parse_url($input);
- if (isset($parsed['host'])) {
- $arr = explode('.', $parsed['host']);
- foreach ($arr as $k => $v) {
- $conv = $this->_decode($v);
- if ($conv) $arr[$k] = $conv;
- }
- $parsed['host'] = join('.', $arr);
- $return =
- (empty($parsed['scheme']) ? '' : $parsed['scheme'].(strtolower($parsed['scheme']) == 'mailto' ? ':' : '://'))
- .(empty($parsed['user']) ? '' : $parsed['user'].(empty($parsed['pass']) ? '' : ':'.$parsed['pass']).'@')
- .$parsed['host']
- .(empty($parsed['port']) ? '' : ':'.$parsed['port'])
- .(empty($parsed['path']) ? '' : $parsed['path'])
- .(empty($parsed['query']) ? '' : '?'.$parsed['query'])
- .(empty($parsed['fragment']) ? '' : '#'.$parsed['fragment']);
- } else { // parse_url seems to have failed, try without it
- $arr = explode('.', $input);
- foreach ($arr as $k => $v) {
- $conv = $this->_decode($v);
- $arr[$k] = ($conv) ? $conv : $v;
- }
- $return = join('.', $arr);
- }
- } else { // Otherwise we consider it being a pure domain name string
- $return = $this->_decode($input);
- if (!$return) $return = $input;
- }
- // The output is UTF-8 by default, other output formats need conversion here
- // If one time encoding is given, use this, else the objects property
- switch (($one_time_encoding) ? $one_time_encoding : $this->_api_encoding) {
- case 'utf8':
- return $return;
- break;
- case 'ucs4_string':
- return $this->_ucs4_to_ucs4_string($this->_utf8_to_ucs4($return));
- break;
- case 'ucs4_array':
- return $this->_utf8_to_ucs4($return);
- break;
- default:
- $this->_error('Unsupported output format');
- return false;
- }
- }
-
- /**
- * Encode a given UTF-8 domain name
- * @param string Domain name (UTF-8 or UCS-4)
- * [@param string Desired input encoding, see {@link set_parameter}]
- * @return string Encoded Domain name (ACE string)
- * @access public
- */
- function encode($decoded, $one_time_encoding = false)
- {
- // Forcing conversion of input to UCS4 array
- // If one time encoding is given, use this, else the objects property
- switch ($one_time_encoding ? $one_time_encoding : $this->_api_encoding) {
- case 'utf8':
- $decoded = $this->_utf8_to_ucs4($decoded);
- break;
- case 'ucs4_string':
- $decoded = $this->_ucs4_string_to_ucs4($decoded);
- case 'ucs4_array':
- break;
- default:
- $this->_error('Unsupported input format: '.($one_time_encoding ? $one_time_encoding : $this->_api_encoding));
- return false;
- }
-
- // No input, no output, what else did you expect?
- if (empty($decoded)) return '';
-
- // Anchors for iteration
- $last_begin = 0;
- // Output string
- $output = '';
- foreach ($decoded as $k => $v) {
- // Make sure to use just the plain dot
- switch($v) {
- case 0x3002:
- case 0xFF0E:
- case 0xFF61:
- $decoded[$k] = 0x2E;
- // Right, no break here, the above are converted to dots anyway
- // Stumbling across an anchoring character
- case 0x2E:
- case 0x2F:
- case 0x3A:
- case 0x3F:
- case 0x40:
- // Neither email addresses nor URLs allowed in strict mode
- if ($this->_strict_mode) {
- $this->_error('Neither email addresses nor URLs are allowed in strict mode.');
- return false;
- } else {
- // Skip first char
- if ($k) {
- $encoded = '';
- $encoded = $this->_encode(array_slice($decoded, $last_begin, (($k)-$last_begin)));
- if ($encoded) {
- $output .= $encoded;
- } else {
- $output .= $this->_ucs4_to_utf8(array_slice($decoded, $last_begin, (($k)-$last_begin)));
- }
- $output .= chr($decoded[$k]);
- }
- $last_begin = $k + 1;
- }
- }
- }
- // Catch the rest of the string
- if ($last_begin) {
- $inp_len = sizeof($decoded);
- $encoded = '';
- $encoded = $this->_encode(array_slice($decoded, $last_begin, (($inp_len)-$last_begin)));
- if ($encoded) {
- $output .= $encoded;
- } else {
- $output .= $this->_ucs4_to_utf8(array_slice($decoded, $last_begin, (($inp_len)-$last_begin)));
- }
- return $output;
- } else {
- if ($output = $this->_encode($decoded)) {
- return $output;
- } else {
- return $this->_ucs4_to_utf8($decoded);
- }
- }
- }
-
- /**
- * Use this method to get the last error ocurred
- * @param void
- * @return string The last error, that occured
- * @access public
- */
- function get_last_error()
- {
- return $this->_error;
- }
-
- /**
- * The actual decoding algorithm
- * @access private
- */
- function _decode($encoded)
- {
- // We do need to find the Punycode prefix
- if (!preg_match('!^'.preg_quote($this->_punycode_prefix, '!').'!', $encoded)) {
- $this->_error('This is not a punycode string');
- return false;
- }
- $encode_test = preg_replace('!^'.preg_quote($this->_punycode_prefix, '!').'!', '', $encoded);
- // If nothing left after removing the prefix, it is hopeless
- if (!$encode_test) {
- $this->_error('The given encoded string was empty');
- return false;
- }
- // Find last occurence of the delimiter
- $delim_pos = strrpos($encoded, '-');
- if ($delim_pos > strlen($this->_punycode_prefix)) {
- for ($k = strlen($this->_punycode_prefix); $k < $delim_pos; ++$k) {
- $decoded[] = ord($encoded{$k});
- }
- } else {
- $decoded = array();
- }
- $deco_len = count($decoded);
- $enco_len = strlen($encoded);
-
- // Wandering through the strings; init
- $is_first = true;
- $bias = $this->_initial_bias;
- $idx = 0;
- $char = $this->_initial_n;
-
- for ($enco_idx = ($delim_pos) ? ($delim_pos + 1) : 0; $enco_idx < $enco_len; ++$deco_len) {
- for ($old_idx = $idx, $w = 1, $k = $this->_base; 1 ; $k += $this->_base) {
- $digit = $this->_decode_digit($encoded{$enco_idx++});
- $idx += $digit * $w;
- $t = ($k <= $bias) ? $this->_tmin :
- (($k >= $bias + $this->_tmax) ? $this->_tmax : ($k - $bias));
- if ($digit < $t) break;
- $w = (int) ($w * ($this->_base - $t));
- }
- $bias = $this->_adapt($idx - $old_idx, $deco_len + 1, $is_first);
- $is_first = false;
- $char += (int) ($idx / ($deco_len + 1));
- $idx %= ($deco_len + 1);
- if ($deco_len > 0) {
- // Make room for the decoded char
- for ($i = $deco_len; $i > $idx; $i--) {
- $decoded[$i] = $decoded[($i - 1)];
- }
- }
- $decoded[$idx++] = $char;
- }
- return $this->_ucs4_to_utf8($decoded);
- }
-
- /**
- * The actual encoding algorithm
- * @access private
- */
- function _encode($decoded)
- {
- // We cannot encode a domain name containing the Punycode prefix
- $extract = strlen($this->_punycode_prefix);
- $check_pref = $this->_utf8_to_ucs4($this->_punycode_prefix);
- $check_deco = array_slice($decoded, 0, $extract);
-
- if ($check_pref == $check_deco) {
- $this->_error('This is already a punycode string');
- return false;
- }
- // We will not try to encode strings consisting of basic code points only
- $encodable = false;
- foreach ($decoded as $k => $v) {
- if ($v > 0x7a) {
- $encodable = true;
- break;
- }
- }
- if (!$encodable) {
- $this->_error('The given string does not contain encodable chars');
- return false;
- }
-
- // Do NAMEPREP
- $decoded = $this->_nameprep($decoded);
- if (!$decoded || !is_array($decoded)) return false; // NAMEPREP failed
-
- $deco_len = count($decoded);
- if (!$deco_len) return false; // Empty array
-
- $codecount = 0; // How many chars have been consumed
-
- $encoded = '';
- // Copy all basic code points to output
- for ($i = 0; $i < $deco_len; ++$i) {
- $test = $decoded[$i];
- // Will match [-0-9a-zA-Z]
- if ((0x2F < $test && $test < 0x40) || (0x40 < $test && $test < 0x5B)
- || (0x60 < $test && $test <= 0x7B) || (0x2D == $test)) {
- $encoded .= chr($decoded[$i]);
- $codecount++;
- }
- }
- if ($codecount == $deco_len) return $encoded; // All codepoints were basic ones
-
- // Start with the prefix; copy it to output
- $encoded = $this->_punycode_prefix.$encoded;
-
- // If we have basic code points in output, add an hyphen to the end
- if ($codecount) $encoded .= '-';
-
- // Now find and encode all non-basic code points
- $is_first = true;
- $cur_code = $this->_initial_n;
- $bias = $this->_initial_bias;
- $delta = 0;
- while ($codecount < $deco_len) {
- // Find the smallest code point >= the current code point and
- // remember the last ouccrence of it in the input
- for ($i = 0, $next_code = $this->_max_ucs; $i < $deco_len; $i++) {
- if ($decoded[$i] >= $cur_code && $decoded[$i] <= $next_code) {
- $next_code = $decoded[$i];
- }
- }
-
- $delta += ($next_code - $cur_code) * ($codecount + 1);
- $cur_code = $next_code;
-
- // Scan input again and encode all characters whose code point is $cur_code
- for ($i = 0; $i < $deco_len; $i++) {
- if ($decoded[$i] < $cur_code) {
- $delta++;
- } elseif ($decoded[$i] == $cur_code) {
- for ($q = $delta, $k = $this->_base; 1; $k += $this->_base) {
- $t = ($k <= $bias) ? $this->_tmin :
- (($k >= $bias + $this->_tmax) ? $this->_tmax : $k - $bias);
- if ($q < $t) break;
- $encoded .= $this->_encode_digit(intval($t + (($q - $t) % ($this->_base - $t)))); //v0.4.5 Changed from ceil() to intval()
- $q = (int) (($q - $t) / ($this->_base - $t));
- }
- $encoded .= $this->_encode_digit($q);
- $bias = $this->_adapt($delta, $codecount+1, $is_first);
- $codecount++;
- $delta = 0;
- $is_first = false;
- }
- }
- $delta++;
- $cur_code++;
- }
- return $encoded;
- }
-
- /**
- * Adapt the bias according to the current code point and position
- * @access private
- */
- function _adapt($delta, $npoints, $is_first)
- {
- $delta = intval($is_first ? ($delta / $this->_damp) : ($delta / 2));
- $delta += intval($delta / $npoints);
- for ($k = 0; $delta > (($this->_base - $this->_tmin) * $this->_tmax) / 2; $k += $this->_base) {
- $delta = intval($delta / ($this->_base - $this->_tmin));
- }
- return intval($k + ($this->_base - $this->_tmin + 1) * $delta / ($delta + $this->_skew));
- }
-
- /**
- * Encoding a certain digit
- * @access private
- */
- function _encode_digit($d)
- {
- return chr($d + 22 + 75 * ($d < 26));
- }
-
- /**
- * Decode a certain digit
- * @access private
- */
- function _decode_digit($cp)
- {
- $cp = ord($cp);
- return ($cp - 48 < 10) ? $cp - 22 : (($cp - 65 < 26) ? $cp - 65 : (($cp - 97 < 26) ? $cp - 97 : $this->_base));
- }
-
- /**
- * Internal error handling method
- * @access private
- */
- function _error($error = '')
- {
- $this->_error = $error;
- }
-
- /**
- * Do Nameprep according to RFC3491 and RFC3454
- * @param array Unicode Characters
- * @return string Unicode Characters, Nameprep'd
- * @access private
- */
- function _nameprep($input)
- {
- $output = array();
- $error = false;
- //
- // Mapping
- // Walking through the input array, performing the required steps on each of
- // the input chars and putting the result into the output array
- // While mapping required chars we apply the cannonical ordering
- foreach ($input as $v) {
- // Map to nothing == skip that code point
- if (in_array($v, $this->NP['map_nothing'])) continue;
-
- // Try to find prohibited input
- if (in_array($v, $this->NP['prohibit']) || in_array($v, $this->NP['general_prohibited'])) {
- $this->_error('NAMEPREP: Prohibited input U+'.sprintf('%08X', $v));
- return false;
- }
- foreach ($this->NP['prohibit_ranges'] as $range) {
- if ($range[0] <= $v && $v <= $range[1]) {
- $this->_error('NAMEPREP: Prohibited input U+'.sprintf('%08X', $v));
- return false;
- }
- }
- //
- // Hangul syllable decomposition
- if (0xAC00 <= $v && $v <= 0xD7AF) {
- foreach ($this->_hangul_decompose($v) as $out) {
- $output[] = (int) $out;
- }
- // There's a decomposition mapping for that code point
- } elseif (isset($this->NP['replacemaps'][$v])) {
- foreach ($this->_apply_cannonical_ordering($this->NP['replacemaps'][$v]) as $out) {
- $output[] = (int) $out;
- }
- } else {
- $output[] = (int) $v;
- }
- }
- // Before applying any Combining, try to rearrange any Hangul syllables
- $output = $this->_hangul_compose($output);
- //
- // Combine code points
- //
- $last_class = 0;
- $last_starter = 0;
- $out_len = count($output);
- for ($i = 0; $i < $out_len; ++$i) {
- $class = $this->_get_combining_class($output[$i]);
- if ((!$last_class || $last_class > $class) && $class) {
- // Try to match
- $seq_len = $i - $last_starter;
- $out = $this->_combine(array_slice($output, $last_starter, $seq_len));
- // On match: Replace the last starter with the composed character and remove
- // the now redundant non-starter(s)
- if ($out) {
- $output[$last_starter] = $out;
- if (count($out) != $seq_len) {
- for ($j = $i+1; $j < $out_len; ++$j) {
- $output[$j-1] = $output[$j];
- }
- unset($output[$out_len]);
- }
- // Rewind the for loop by one, since there can be more possible compositions
- $i--;
- $out_len--;
- $last_class = ($i == $last_starter) ? 0 : $this->_get_combining_class($output[$i-1]);
- continue;
- }
- }
- // The current class is 0
- if (!$class) $last_starter = $i;
- $last_class = $class;
- }
- return $output;
- }
-
- /**
- * Decomposes a Hangul syllable
- * (see http://www.unicode.org/unicode/reports/tr15/#Hangul
- * @param integer 32bit UCS4 code point
- * @return array Either Hangul Syllable decomposed or original 32bit value as one value array
- * @access private
- */
- function _hangul_decompose($char)
- {
- $sindex = (int) $char - $this->_sbase;
- if ($sindex < 0 || $sindex >= $this->_scount) {
- return array($char);
- }
- $result = array();
- $result[] = (int) $this->_lbase + $sindex / $this->_ncount;
- $result[] = (int) $this->_vbase + ($sindex % $this->_ncount) / $this->_tcount;
- $T = intval($this->_tbase + $sindex % $this->_tcount);
- if ($T != $this->_tbase) $result[] = $T;
- return $result;
- }
- /**
- * Ccomposes a Hangul syllable
- * (see http://www.unicode.org/unicode/reports/tr15/#Hangul
- * @param array Decomposed UCS4 sequence
- * @return array UCS4 sequence with syllables composed
- * @access private
- */
- function _hangul_compose($input)
- {
- $inp_len = count($input);
- if (!$inp_len) return array();
- $result = array();
- $last = (int) $input[0];
- $result[] = $last; // copy first char from input to output
-
- for ($i = 1; $i < $inp_len; ++$i) {
- $char = (int) $input[$i];
- $sindex = $last - $this->_sbase;
- $lindex = $last - $this->_lbase;
- $vindex = $char - $this->_vbase;
- $tindex = $char - $this->_tbase;
- // Find out, whether two current characters are LV and T
- if (0 <= $sindex && $sindex < $this->_scount && ($sindex % $this->_tcount == 0)
- && 0 <= $tindex && $tindex <= $this->_tcount) {
- // create syllable of form LVT
- $last += $tindex;
- $result[(count($result) - 1)] = $last; // reset last
- continue; // discard char
- }
- // Find out, whether two current characters form L and V
- if (0 <= $lindex && $lindex < $this->_lcount && 0 <= $vindex && $vindex < $this->_vcount) {
- // create syllable of form LV
- $last = (int) $this->_sbase + ($lindex * $this->_vcount + $vindex) * $this->_tcount;
- $result[(count($result) - 1)] = $last; // reset last
- continue; // discard char
- }
- // if neither case was true, just add the character
- $last = $char;
- $result[] = $char;
- }
- return $result;
- }
-
- /**
- * Returns the combining class of a certain wide char
- * @param integer Wide char to check (32bit integer)
- * @return integer Combining class if found, else 0
- * @access private
- */
- function _get_combining_class($char)
- {
- return isset($this->NP['norm_combcls'][$char]) ? $this->NP['norm_combcls'][$char] : 0;
- }
-
- /**
- * Apllies the cannonical ordering of a decomposed UCS4 sequence
- * @param array Decomposed UCS4 sequence
- * @return array Ordered USC4 sequence
- * @access private
- */
- function _apply_cannonical_ordering($input)
- {
- $swap = true;
- $size = count($input);
- while ($swap) {
- $swap = false;
- $last = $this->_get_combining_class(intval($input[0]));
- for ($i = 0; $i < $size-1; ++$i) {
- $next = $this->_get_combining_class(intval($input[$i+1]));
- if ($next != 0 && $last > $next) {
- // Move item leftward until it fits
- for ($j = $i + 1; $j > 0; --$j) {
- if ($this->_get_combining_class(intval($input[$j-1])) <= $next) break;
- $t = intval($input[$j]);
- $input[$j] = intval($input[$j-1]);
- $input[$j-1] = $t;
- $swap = true;
- }
- // Reentering the loop looking at the old character again
- $next = $last;
- }
- $last = $next;
- }
- }
- return $input;
- }
-
- /**
- * Do composition of a sequence of starter and non-starter
- * @param array UCS4 Decomposed sequence
- * @return array Ordered USC4 sequence
- * @access private
- */
- function _combine($input)
- {
- $inp_len = count($input);
- foreach ($this->NP['replacemaps'] as $np_src => $np_target) {
- if ($np_target[0] != $input[0]) continue;
- if (count($np_target) != $inp_len) continue;
- $hit = false;
- foreach ($input as $k2 => $v2) {
- if ($v2 == $np_target[$k2]) {
- $hit = true;
- } else {
- $hit = false;
- break;
- }
- }
- if ($hit) return $np_src;
- }
- return false;
- }
-
- /**
- * This converts an UTF-8 encoded string to its UCS-4 representation
- * By talking about UCS-4 "strings" we mean arrays of 32bit integers representing
- * each of the "chars". This is due to PHP not being able to handle strings with
- * bit depth different from 8. This apllies to the reverse method _ucs4_to_utf8(), too.
- * The following UTF-8 encodings are supported:
- * bytes bits representation
- * 1 7 0xxxxxxx
- * 2 11 110xxxxx 10xxxxxx
- * 3 16 1110xxxx 10xxxxxx 10xxxxxx
- * 4 21 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx
- * 5 26 111110xx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
- * 6 31 1111110x 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
- * Each x represents a bit that can be used to store character data.
- * The five and six byte sequences are part of Annex D of ISO/IEC 10646-1:2000
- * @access private
- */
- function _utf8_to_ucs4($input)
- {
- $output = array();
- $out_len = 0;
- $inp_len = strlen($input);
- $mode = 'next';
- $test = 'none';
- for ($k = 0; $k < $inp_len; ++$k) {
- $v = ord($input{$k}); // Extract byte from input string
-
- if ($v < 128) { // We found an ASCII char - put into stirng as is
- $output[$out_len] = $v;
- ++$out_len;
- if ('add' == $mode) {
- $this->_error('Conversion from UTF-8 to UCS-4 failed: malformed input at byte '.$k);
- return false;
- }
- continue;
- }
- if ('next' == $mode) { // Try to find the next start byte; determine the width of the Unicode char
- $start_byte = $v;
- $mode = 'add';
- $test = 'range';
- if ($v >> 5 == 6) { // &110xxxxx 10xxxxx
- $next_byte = 0; // Tells, how many times subsequent bitmasks must rotate 6bits to the left
- $v = ($v - 192) << 6;
- } elseif ($v >> 4 == 14) { // &1110xxxx 10xxxxxx 10xxxxxx
- $next_byte = 1;
- $v = ($v - 224) << 12;
- } elseif ($v >> 3 == 30) { // &11110xxx 10xxxxxx 10xxxxxx 10xxxxxx
- $next_byte = 2;
- $v = ($v - 240) << 18;
- } elseif ($v >> 2 == 62) { // &111110xx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
- $next_byte = 3;
- $v = ($v - 248) << 24;
- } elseif ($v >> 1 == 126) { // &1111110x 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
- $next_byte = 4;
- $v = ($v - 252) << 30;
- } else {
- $this->_error('This might be UTF-8, but I don\'t understand it at byte '.$k);
- return false;
- }
- if ('add' == $mode) {
- $output[$out_len] = (int) $v;
- ++$out_len;
- continue;
- }
- }
- if ('add' == $mode) {
- if (!$this->_allow_overlong && $test == 'range') {
- $test = 'none';
- if (($v < 0xA0 && $start_byte == 0xE0) || ($v < 0x90 && $start_byte == 0xF0) || ($v > 0x8F && $start_byte == 0xF4)) {
- $this->_error('Bogus UTF-8 character detected (out of legal range) at byte '.$k);
- return false;
- }
- }
- if ($v >> 6 == 2) { // Bit mask must be 10xxxxxx
- $v = ($v - 128) << ($next_byte * 6);
- $output[($out_len - 1)] += $v;
- --$next_byte;
- } else {
- $this->_error('Conversion from UTF-8 to UCS-4 failed: malformed input at byte '.$k);
- return false;
- }
- if ($next_byte < 0) {
- $mode = 'next';
- }
- }
- } // for
- return $output;
- }
-
- /**
- * Convert UCS-4 string into UTF-8 string
- * See _utf8_to_ucs4() for details
- * @access private
- */
- function _ucs4_to_utf8($input)
- {
- $output = '';
- $k = 0;
- foreach ($input as $v) {
- ++$k;
- // $v = ord($v);
- if ($v < 128) { // 7bit are transferred literally
- $output .= chr($v);
- } elseif ($v < (1 << 11)) { // 2 bytes
- $output .= chr(192 + ($v >> 6)) . chr(128 + ($v & 63));
- } elseif ($v < (1 << 16)) { // 3 bytes
- $output .= chr(224 + ($v >> 12)) . chr(128 + (($v >> 6) & 63)) . chr(128 + ($v & 63));
- } elseif ($v < (1 << 21)) { // 4 bytes
- $output .= chr(240 + ($v >> 18)) . chr(128 + (($v >> 12) & 63))
- . chr(128 + (($v >> 6) & 63)) . chr(128 + ($v & 63));
- } elseif ($v < (1 << 26)) { // 5 bytes
- $output .= chr(248 + ($v >> 24)) . chr(128 + (($v >> 18) & 63))
- . chr(128 + (($v >> 12) & 63)) . chr(128 + (($v >> 6) & 63))
- . chr(128 + ($v & 63));
- } elseif ($v < (1 << 31)) { // 6 bytes
- $output .= chr(252 + ($v >> 30)) . chr(128 + (($v >> 24) & 63))
- . chr(128 + (($v >> 18) & 63)) . chr(128 + (($v >> 12) & 63))
- . chr(128 + (($v >> 6) & 63)) . chr(128 + ($v & 63));
- } else {
- $this->_error('Conversion from UCS-4 to UTF-8 failed: malformed input at byte '.$k);
- return false;
- }
- }
- return $output;
- }
-
- /**
- * Convert UCS-4 array into UCS-4 string
- *
- * @access private
- */
- function _ucs4_to_ucs4_string($input)
- {
- $output = '';
- // Take array values and split output to 4 bytes per value
- // The bit mask is 255, which reads &11111111
- foreach ($input as $v) {
- $output .= chr(($v >> 24) & 255).chr(($v >> 16) & 255).chr(($v >> 8) & 255).chr($v & 255);
- }
- return $output;
- }
-
- /**
- * Convert UCS-4 strin into UCS-4 garray
- *
- * @access private
- */
- function _ucs4_string_to_ucs4($input)
- {
- $output = array();
- $inp_len = strlen($input);
- // Input length must be dividable by 4
- if ($inp_len % 4) {
- $this->_error('Input UCS4 string is broken');
- return false;
- }
- // Empty input - return empty output
- if (!$inp_len) return $output;
- for ($i = 0, $out_len = -1; $i < $inp_len; ++$i) {
- // Increment output position every 4 input bytes
- if (!($i % 4)) {
- $out_len++;
- $output[$out_len] = 0;
- }
- $output[$out_len] += ord($input{$i}) << (8 * (3 - ($i % 4) ) );
- }
- return $output;
- }
-}
-
-/**
-* Adapter class for aligning the API of idna_convert with that of Net_IDNA
-* @author Matthias Sommerfeld <mso@phlylabs.de>
-*/
-class Net_IDNA_php4 extends idna_convert
-{
- /**
- * Sets a new option value. Available options and values:
- * [encoding - Use either UTF-8, UCS4 as array or UCS4 as string as input ('utf8' for UTF-8,
- * 'ucs4_string' and 'ucs4_array' respectively for UCS4); The output is always UTF-8]
- * [overlong - Unicode does not allow unnecessarily long encodings of chars,
- * to allow this, set this parameter to true, else to false;
- * default is false.]
- * [strict - true: strict mode, good for registration purposes - Causes errors
- * on failures; false: loose mode, ideal for "wildlife" applications
- * by silently ignoring errors and returning the original input instead
- *
- * @param mixed Parameter to set (string: single parameter; array of Parameter => Value pairs)
- * @param string Value to use (if parameter 1 is a string)
- * @return boolean true on success, false otherwise
- * @access public
- */
- function setParams($option, $param = false)
- {
- return $this->IC->set_parameters($option, $param);
- }
-}
-
-?> \ No newline at end of file
diff --git a/library/simplepie/simplepie.inc b/library/simplepie/simplepie.inc
deleted file mode 100644
index 96ad06678..000000000
--- a/library/simplepie/simplepie.inc
+++ /dev/null
@@ -1,15150 +0,0 @@
-<?php
-/**
- * SimplePie
- *
- * A PHP-Based RSS and Atom Feed Framework.
- * Takes the hard work out of managing a complete RSS/Atom solution.
- *
- * Copyright (c) 2004-2009, Ryan Parman and Geoffrey Sneddon
- * All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without modification, are
- * permitted provided that the following conditions are met:
- *
- * * Redistributions of source code must retain the above copyright notice, this list of
- * conditions and the following disclaimer.
- *
- * * Redistributions in binary form must reproduce the above copyright notice, this list
- * of conditions and the following disclaimer in the documentation and/or other materials
- * provided with the distribution.
- *
- * * Neither the name of the SimplePie Team nor the names of its contributors may be used
- * to endorse or promote products derived from this software without specific prior
- * written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
- * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
- * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
- * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
- * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
- * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
- * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
- * POSSIBILITY OF SUCH DAMAGE.
- *
- * @package SimplePie
- * @version 1.2.1-dev
- * @copyright 2004-2009 Ryan Parman, Geoffrey Sneddon
- * @author Ryan Parman
- * @author Geoffrey Sneddon
- * @link http://simplepie.org/ SimplePie
- * @link http://simplepie.org/support/ Please submit all bug reports and feature requests to the SimplePie forums
- * @license http://www.opensource.org/licenses/bsd-license.php BSD License
- * @todo phpDoc comments
- */
-
-/**
- * SimplePie Name
- */
-define('SIMPLEPIE_NAME', 'SimplePie');
-
-/**
- * SimplePie Version
- */
-define('SIMPLEPIE_VERSION', '1.2.1-dev');
-
-/**
- * SimplePie Build
- * @todo Hardcode for release (there's no need to have to call SimplePie_Misc::parse_date() only every load of simplepie.inc)
- */
-define('SIMPLEPIE_BUILD', gmdate('YmdHis', SimplePie_Misc::parse_date(substr('$Date$', 7, 25)) ? SimplePie_Misc::parse_date(substr('$Date$', 7, 25)) : filemtime(__FILE__)));
-
-/**
- * SimplePie Website URL
- */
-define('SIMPLEPIE_URL', 'http://simplepie.org');
-
-/**
- * SimplePie Useragent
- * @see SimplePie::set_useragent()
- */
-define('SIMPLEPIE_USERAGENT', SIMPLEPIE_NAME . '/' . SIMPLEPIE_VERSION . ' (Feed Parser; ' . SIMPLEPIE_URL . '; Allow like Gecko) Build/' . SIMPLEPIE_BUILD);
-
-/**
- * SimplePie Linkback
- */
-define('SIMPLEPIE_LINKBACK', '<a href="' . SIMPLEPIE_URL . '" title="' . SIMPLEPIE_NAME . ' ' . SIMPLEPIE_VERSION . '">' . SIMPLEPIE_NAME . '</a>');
-
-/**
- * No Autodiscovery
- * @see SimplePie::set_autodiscovery_level()
- */
-define('SIMPLEPIE_LOCATOR_NONE', 0);
-
-/**
- * Feed Link Element Autodiscovery
- * @see SimplePie::set_autodiscovery_level()
- */
-define('SIMPLEPIE_LOCATOR_AUTODISCOVERY', 1);
-
-/**
- * Local Feed Extension Autodiscovery
- * @see SimplePie::set_autodiscovery_level()
- */
-define('SIMPLEPIE_LOCATOR_LOCAL_EXTENSION', 2);
-
-/**
- * Local Feed Body Autodiscovery
- * @see SimplePie::set_autodiscovery_level()
- */
-define('SIMPLEPIE_LOCATOR_LOCAL_BODY', 4);
-
-/**
- * Remote Feed Extension Autodiscovery
- * @see SimplePie::set_autodiscovery_level()
- */
-define('SIMPLEPIE_LOCATOR_REMOTE_EXTENSION', 8);
-
-/**
- * Remote Feed Body Autodiscovery
- * @see SimplePie::set_autodiscovery_level()
- */
-define('SIMPLEPIE_LOCATOR_REMOTE_BODY', 16);
-
-/**
- * All Feed Autodiscovery
- * @see SimplePie::set_autodiscovery_level()
- */
-define('SIMPLEPIE_LOCATOR_ALL', 31);
-
-/**
- * No known feed type
- */
-define('SIMPLEPIE_TYPE_NONE', 0);
-
-/**
- * RSS 0.90
- */
-define('SIMPLEPIE_TYPE_RSS_090', 1);
-
-/**
- * RSS 0.91 (Netscape)
- */
-define('SIMPLEPIE_TYPE_RSS_091_NETSCAPE', 2);
-
-/**
- * RSS 0.91 (Userland)
- */
-define('SIMPLEPIE_TYPE_RSS_091_USERLAND', 4);
-
-/**
- * RSS 0.91 (both Netscape and Userland)
- */
-define('SIMPLEPIE_TYPE_RSS_091', 6);
-
-/**
- * RSS 0.92
- */
-define('SIMPLEPIE_TYPE_RSS_092', 8);
-
-/**
- * RSS 0.93
- */
-define('SIMPLEPIE_TYPE_RSS_093', 16);
-
-/**
- * RSS 0.94
- */
-define('SIMPLEPIE_TYPE_RSS_094', 32);
-
-/**
- * RSS 1.0
- */
-define('SIMPLEPIE_TYPE_RSS_10', 64);
-
-/**
- * RSS 2.0
- */
-define('SIMPLEPIE_TYPE_RSS_20', 128);
-
-/**
- * RDF-based RSS
- */
-define('SIMPLEPIE_TYPE_RSS_RDF', 65);
-
-/**
- * Non-RDF-based RSS (truly intended as syndication format)
- */
-define('SIMPLEPIE_TYPE_RSS_SYNDICATION', 190);
-
-/**
- * All RSS
- */
-define('SIMPLEPIE_TYPE_RSS_ALL', 255);
-
-/**
- * Atom 0.3
- */
-define('SIMPLEPIE_TYPE_ATOM_03', 256);
-
-/**
- * Atom 1.0
- */
-define('SIMPLEPIE_TYPE_ATOM_10', 512);
-
-/**
- * All Atom
- */
-define('SIMPLEPIE_TYPE_ATOM_ALL', 768);
-
-/**
- * All feed types
- */
-define('SIMPLEPIE_TYPE_ALL', 1023);
-
-/**
- * No construct
- */
-define('SIMPLEPIE_CONSTRUCT_NONE', 0);
-
-/**
- * Text construct
- */
-define('SIMPLEPIE_CONSTRUCT_TEXT', 1);
-
-/**
- * HTML construct
- */
-define('SIMPLEPIE_CONSTRUCT_HTML', 2);
-
-/**
- * XHTML construct
- */
-define('SIMPLEPIE_CONSTRUCT_XHTML', 4);
-
-/**
- * base64-encoded construct
- */
-define('SIMPLEPIE_CONSTRUCT_BASE64', 8);
-
-/**
- * IRI construct
- */
-define('SIMPLEPIE_CONSTRUCT_IRI', 16);
-
-/**
- * A construct that might be HTML
- */
-define('SIMPLEPIE_CONSTRUCT_MAYBE_HTML', 32);
-
-/**
- * All constructs
- */
-define('SIMPLEPIE_CONSTRUCT_ALL', 63);
-
-/**
- * Don't change case
- */
-define('SIMPLEPIE_SAME_CASE', 1);
-
-/**
- * Change to lowercase
- */
-define('SIMPLEPIE_LOWERCASE', 2);
-
-/**
- * Change to uppercase
- */
-define('SIMPLEPIE_UPPERCASE', 4);
-
-/**
- * PCRE for HTML attributes
- */
-define('SIMPLEPIE_PCRE_HTML_ATTRIBUTE', '((?:[\x09\x0A\x0B\x0C\x0D\x20]+[^\x09\x0A\x0B\x0C\x0D\x20\x2F\x3E][^\x09\x0A\x0B\x0C\x0D\x20\x2F\x3D\x3E]*(?:[\x09\x0A\x0B\x0C\x0D\x20]*=[\x09\x0A\x0B\x0C\x0D\x20]*(?:"(?:[^"]*)"|\'(?:[^\']*)\'|(?:[^\x09\x0A\x0B\x0C\x0D\x20\x22\x27\x3E][^\x09\x0A\x0B\x0C\x0D\x20\x3E]*)?))?)*)[\x09\x0A\x0B\x0C\x0D\x20]*');
-
-/**
- * PCRE for XML attributes
- */
-define('SIMPLEPIE_PCRE_XML_ATTRIBUTE', '((?:\s+(?:(?:[^\s:]+:)?[^\s:]+)\s*=\s*(?:"(?:[^"]*)"|\'(?:[^\']*)\'))*)\s*');
-
-/**
- * XML Namespace
- */
-define('SIMPLEPIE_NAMESPACE_XML', 'http://www.w3.org/XML/1998/namespace');
-
-/**
- * Atom 1.0 Namespace
- */
-define('SIMPLEPIE_NAMESPACE_ATOM_10', 'http://www.w3.org/2005/Atom');
-
-/**
- * Atom 0.3 Namespace
- */
-define('SIMPLEPIE_NAMESPACE_ATOM_03', 'http://purl.org/atom/ns#');
-
-/**
- * RDF Namespace
- */
-define('SIMPLEPIE_NAMESPACE_RDF', 'http://www.w3.org/1999/02/22-rdf-syntax-ns#');
-
-/**
- * RSS 0.90 Namespace
- */
-define('SIMPLEPIE_NAMESPACE_RSS_090', 'http://my.netscape.com/rdf/simple/0.9/');
-
-/**
- * RSS 1.0 Namespace
- */
-define('SIMPLEPIE_NAMESPACE_RSS_10', 'http://purl.org/rss/1.0/');
-
-/**
- * RSS 1.0 Content Module Namespace
- */
-define('SIMPLEPIE_NAMESPACE_RSS_10_MODULES_CONTENT', 'http://purl.org/rss/1.0/modules/content/');
-
-/**
- * RSS 2.0 Namespace
- * (Stupid, I know, but I'm certain it will confuse people less with support.)
- */
-define('SIMPLEPIE_NAMESPACE_RSS_20', '');
-
-/**
- * DC 1.0 Namespace
- */
-define('SIMPLEPIE_NAMESPACE_DC_10', 'http://purl.org/dc/elements/1.0/');
-
-/**
- * DC 1.1 Namespace
- */
-define('SIMPLEPIE_NAMESPACE_DC_11', 'http://purl.org/dc/elements/1.1/');
-
-/**
- * W3C Basic Geo (WGS84 lat/long) Vocabulary Namespace
- */
-define('SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO', 'http://www.w3.org/2003/01/geo/wgs84_pos#');
-
-/**
- * GeoRSS Namespace
- */
-define('SIMPLEPIE_NAMESPACE_GEORSS', 'http://www.georss.org/georss');
-
-/**
- * Media RSS Namespace
- */
-define('SIMPLEPIE_NAMESPACE_MEDIARSS', 'http://search.yahoo.com/mrss/');
-
-/**
- * Wrong Media RSS Namespace
- */
-define('SIMPLEPIE_NAMESPACE_MEDIARSS_WRONG', 'http://search.yahoo.com/mrss');
-
-/**
- * iTunes RSS Namespace
- */
-define('SIMPLEPIE_NAMESPACE_ITUNES', 'http://www.itunes.com/dtds/podcast-1.0.dtd');
-
-/**
- * XHTML Namespace
- */
-define('SIMPLEPIE_NAMESPACE_XHTML', 'http://www.w3.org/1999/xhtml');
-
-/**
- * IANA Link Relations Registry
- */
-define('SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY', 'http://www.iana.org/assignments/relation/');
-
-/**
- * Whether we're running on PHP5
- */
-define('SIMPLEPIE_PHP5', version_compare(PHP_VERSION, '5.0.0', '>='));
-
-/**
- * No file source
- */
-define('SIMPLEPIE_FILE_SOURCE_NONE', 0);
-
-/**
- * Remote file source
- */
-define('SIMPLEPIE_FILE_SOURCE_REMOTE', 1);
-
-/**
- * Local file source
- */
-define('SIMPLEPIE_FILE_SOURCE_LOCAL', 2);
-
-/**
- * fsockopen() file source
- */
-define('SIMPLEPIE_FILE_SOURCE_FSOCKOPEN', 4);
-
-/**
- * cURL file source
- */
-define('SIMPLEPIE_FILE_SOURCE_CURL', 8);
-
-/**
- * file_get_contents() file source
- */
-define('SIMPLEPIE_FILE_SOURCE_FILE_GET_CONTENTS', 16);
-
-/**
- * SimplePie
- *
- * @package SimplePie
- */
-class SimplePie
-{
- /**
- * @var array Raw data
- * @access private
- */
- var $data = array();
-
- /**
- * @var mixed Error string
- * @access private
- */
- var $error;
-
- /**
- * @var object Instance of SimplePie_Sanitize (or other class)
- * @see SimplePie::set_sanitize_class()
- * @access private
- */
- var $sanitize;
-
- /**
- * @var string SimplePie Useragent
- * @see SimplePie::set_useragent()
- * @access private
- */
- var $useragent = SIMPLEPIE_USERAGENT;
-
- /**
- * @var string Feed URL
- * @see SimplePie::set_feed_url()
- * @access private
- */
- var $feed_url;
-
- /**
- * @var object Instance of SimplePie_File to use as a feed
- * @see SimplePie::set_file()
- * @access private
- */
- var $file;
-
- /**
- * @var string Raw feed data
- * @see SimplePie::set_raw_data()
- * @access private
- */
- var $raw_data;
-
- /**
- * @var int Timeout for fetching remote files
- * @see SimplePie::set_timeout()
- * @access private
- */
- var $timeout = 10;
-
- /**
- * @var bool Forces fsockopen() to be used for remote files instead
- * of cURL, even if a new enough version is installed
- * @see SimplePie::force_fsockopen()
- * @access private
- */
- var $force_fsockopen = false;
-
- /**
- * @var bool Force the given data/URL to be treated as a feed no matter what
- * it appears like
- * @see SimplePie::force_feed()
- * @access private
- */
- var $force_feed = false;
-
- /**
- * @var bool Enable/Disable XML dump
- * @see SimplePie::enable_xml_dump()
- * @access private
- */
- var $xml_dump = false;
-
- /**
- * @var bool Enable/Disable Caching
- * @see SimplePie::enable_cache()
- * @access private
- */
- var $cache = true;
-
- /**
- * @var int Cache duration (in seconds)
- * @see SimplePie::set_cache_duration()
- * @access private
- */
- var $cache_duration = 3600;
-
- /**
- * @var int Auto-discovery cache duration (in seconds)
- * @see SimplePie::set_autodiscovery_cache_duration()
- * @access private
- */
- var $autodiscovery_cache_duration = 604800; // 7 Days.
-
- /**
- * @var string Cache location (relative to executing script)
- * @see SimplePie::set_cache_location()
- * @access private
- */
- var $cache_location = './cache';
-
- /**
- * @var string Function that creates the cache filename
- * @see SimplePie::set_cache_name_function()
- * @access private
- */
- var $cache_name_function = 'md5';
-
- /**
- * @var bool Reorder feed by date descending
- * @see SimplePie::enable_order_by_date()
- * @access private
- */
- var $order_by_date = true;
-
- /**
- * @var mixed Force input encoding to be set to the follow value
- * (false, or anything type-cast to false, disables this feature)
- * @see SimplePie::set_input_encoding()
- * @access private
- */
- var $input_encoding = false;
-
- /**
- * @var int Feed Autodiscovery Level
- * @see SimplePie::set_autodiscovery_level()
- * @access private
- */
- var $autodiscovery = SIMPLEPIE_LOCATOR_ALL;
-
- /**
- * @var string Class used for caching feeds
- * @see SimplePie::set_cache_class()
- * @access private
- */
- var $cache_class = 'SimplePie_Cache';
-
- /**
- * @var string Class used for locating feeds
- * @see SimplePie::set_locator_class()
- * @access private
- */
- var $locator_class = 'SimplePie_Locator';
-
- /**
- * @var string Class used for parsing feeds
- * @see SimplePie::set_parser_class()
- * @access private
- */
- var $parser_class = 'SimplePie_Parser';
-
- /**
- * @var string Class used for fetching feeds
- * @see SimplePie::set_file_class()
- * @access private
- */
- var $file_class = 'SimplePie_File';
-
- /**
- * @var string Class used for items
- * @see SimplePie::set_item_class()
- * @access private
- */
- var $item_class = 'SimplePie_Item';
-
- /**
- * @var string Class used for authors
- * @see SimplePie::set_author_class()
- * @access private
- */
- var $author_class = 'SimplePie_Author';
-
- /**
- * @var string Class used for categories
- * @see SimplePie::set_category_class()
- * @access private
- */
- var $category_class = 'SimplePie_Category';
-
- /**
- * @var string Class used for enclosures
- * @see SimplePie::set_enclosures_class()
- * @access private
- */
- var $enclosure_class = 'SimplePie_Enclosure';
-
- /**
- * @var string Class used for Media RSS <media:text> captions
- * @see SimplePie::set_caption_class()
- * @access private
- */
- var $caption_class = 'SimplePie_Caption';
-
- /**
- * @var string Class used for Media RSS <media:copyright>
- * @see SimplePie::set_copyright_class()
- * @access private
- */
- var $copyright_class = 'SimplePie_Copyright';
-
- /**
- * @var string Class used for Media RSS <media:credit>
- * @see SimplePie::set_credit_class()
- * @access private
- */
- var $credit_class = 'SimplePie_Credit';
-
- /**
- * @var string Class used for Media RSS <media:rating>
- * @see SimplePie::set_rating_class()
- * @access private
- */
- var $rating_class = 'SimplePie_Rating';
-
- /**
- * @var string Class used for Media RSS <media:restriction>
- * @see SimplePie::set_restriction_class()
- * @access private
- */
- var $restriction_class = 'SimplePie_Restriction';
-
- /**
- * @var string Class used for content-type sniffing
- * @see SimplePie::set_content_type_sniffer_class()
- * @access private
- */
- var $content_type_sniffer_class = 'SimplePie_Content_Type_Sniffer';
-
- /**
- * @var string Class used for item sources.
- * @see SimplePie::set_source_class()
- * @access private
- */
- var $source_class = 'SimplePie_Source';
-
- /**
- * @var mixed Set javascript query string parameter (false, or
- * anything type-cast to false, disables this feature)
- * @see SimplePie::set_javascript()
- * @access private
- */
- var $javascript = 'js';
-
- /**
- * @var int Maximum number of feeds to check with autodiscovery
- * @see SimplePie::set_max_checked_feeds()
- * @access private
- */
- var $max_checked_feeds = 10;
-
- /**
- * @var array All the feeds found during the autodiscovery process
- * @see SimplePie::get_all_discovered_feeds()
- * @access private
- */
- var $all_discovered_feeds = array();
-
- /**
- * @var string Web-accessible path to the handler_favicon.php file.
- * @see SimplePie::set_favicon_handler()
- * @access private
- */
- var $favicon_handler = '';
-
- /**
- * @var string Web-accessible path to the handler_image.php file.
- * @see SimplePie::set_image_handler()
- * @access private
- */
- var $image_handler = '';
-
- /**
- * @var array Stores the URLs when multiple feeds are being initialized.
- * @see SimplePie::set_feed_url()
- * @access private
- */
- var $multifeed_url = array();
-
- /**
- * @var array Stores SimplePie objects when multiple feeds initialized.
- * @access private
- */
- var $multifeed_objects = array();
-
- /**
- * @var array Stores the get_object_vars() array for use with multifeeds.
- * @see SimplePie::set_feed_url()
- * @access private
- */
- var $config_settings = null;
-
- /**
- * @var integer Stores the number of items to return per-feed with multifeeds.
- * @see SimplePie::set_item_limit()
- * @access private
- */
- var $item_limit = 0;
-
- /**
- * @var array Stores the default attributes to be stripped by strip_attributes().
- * @see SimplePie::strip_attributes()
- * @access private
- */
- var $strip_attributes = array('bgsound', 'class', 'expr', 'id', 'style', 'onclick', 'onerror', 'onfinish', 'onmouseover', 'onmouseout', 'onfocus', 'onblur', 'lowsrc', 'dynsrc');
-
- /**
- * @var array Stores the default tags to be stripped by strip_htmltags().
- * @see SimplePie::strip_htmltags()
- * @access private
- */
- var $strip_htmltags = array('base', 'blink', 'body', 'doctype', 'embed', 'font', 'form', 'frame', 'frameset', 'html', 'input', 'marquee', 'meta', 'noscript', 'object', 'param', 'script', 'style');
-
- /**
- * The SimplePie class contains feed level data and options
- *
- * There are two ways that you can create a new SimplePie object. The first
- * is by passing a feed URL as a parameter to the SimplePie constructor
- * (as well as optionally setting the cache location and cache expiry). This
- * will initialise the whole feed with all of the default settings, and you
- * can begin accessing methods and properties immediately.
- *
- * The second way is to create the SimplePie object with no parameters
- * at all. This will enable you to set configuration options. After setting
- * them, you must initialise the feed using $feed->init(). At that point the
- * object's methods and properties will be available to you. This format is
- * what is used throughout this documentation.
- *
- * @access public
- * @since 1.0 Preview Release
- * @param string $feed_url This is the URL you want to parse.
- * @param string $cache_location This is where you want the cache to be stored.
- * @param int $cache_duration This is the number of seconds that you want to store the cache file for.
- */
- function SimplePie($feed_url = null, $cache_location = null, $cache_duration = null)
- {
- // Other objects, instances created here so we can set options on them
- $this->sanitize = new SimplePie_Sanitize;
-
- // Set options if they're passed to the constructor
- if ($cache_location !== null)
- {
- $this->set_cache_location($cache_location);
- }
-
- if ($cache_duration !== null)
- {
- $this->set_cache_duration($cache_duration);
- }
-
- // Only init the script if we're passed a feed URL
- if ($feed_url !== null)
- {
- $this->set_feed_url($feed_url);
- $this->init();
- }
- }
-
- /**
- * Used for converting object to a string
- */
- function __toString()
- {
- return md5(serialize($this->data));
- }
-
- /**
- * Remove items that link back to this before destroying this object
- */
- function __destruct()
- {
- if ((version_compare(PHP_VERSION, '5.3', '<') || !gc_enabled()) && !ini_get('zend.ze1_compatibility_mode'))
- {
- if (!empty($this->data['items']))
- {
- foreach ($this->data['items'] as $item)
- {
- $item->__destruct();
- }
- unset($item, $this->data['items']);
- }
- if (!empty($this->data['ordered_items']))
- {
- foreach ($this->data['ordered_items'] as $item)
- {
- $item->__destruct();
- }
- unset($item, $this->data['ordered_items']);
- }
- }
- }
-
- /**
- * Force the given data/URL to be treated as a feed no matter what it
- * appears like
- *
- * @access public
- * @since 1.1
- * @param bool $enable Force the given data/URL to be treated as a feed
- */
- function force_feed($enable = false)
- {
- $this->force_feed = (bool) $enable;
- }
-
- /**
- * This is the URL of the feed you want to parse.
- *
- * This allows you to enter the URL of the feed you want to parse, or the
- * website you want to try to use auto-discovery on. This takes priority
- * over any set raw data.
- *
- * You can set multiple feeds to mash together by passing an array instead
- * of a string for the $url. Remember that with each additional feed comes
- * additional processing and resources.
- *
- * @access public
- * @since 1.0 Preview Release
- * @param mixed $url This is the URL (or array of URLs) that you want to parse.
- * @see SimplePie::set_raw_data()
- */
- function set_feed_url($url)
- {
- if (is_array($url))
- {
- $this->multifeed_url = array();
- foreach ($url as $value)
- {
- $this->multifeed_url[] = SimplePie_Misc::fix_protocol($value, 1);
- }
- }
- else
- {
- $this->feed_url = SimplePie_Misc::fix_protocol($url, 1);
- }
- }
-
- /**
- * Provides an instance of SimplePie_File to use as a feed
- *
- * @access public
- * @param object &$file Instance of SimplePie_File (or subclass)
- * @return bool True on success, false on failure
- */
- function set_file(&$file)
- {
- if (is_a($file, 'SimplePie_File'))
- {
- $this->feed_url = $file->url;
- $this->file =& $file;
- return true;
- }
- return false;
- }
-
- /**
- * Allows you to use a string of RSS/Atom data instead of a remote feed.
- *
- * If you have a feed available as a string in PHP, you can tell SimplePie
- * to parse that data string instead of a remote feed. Any set feed URL
- * takes precedence.
- *
- * @access public
- * @since 1.0 Beta 3
- * @param string $data RSS or Atom data as a string.
- * @see SimplePie::set_feed_url()
- */
- function set_raw_data($data)
- {
- $this->raw_data = $data;
- }
-
- /**
- * Allows you to override the default timeout for fetching remote feeds.
- *
- * This allows you to change the maximum time the feed's server to respond
- * and send the feed back.
- *
- * @access public
- * @since 1.0 Beta 3
- * @param int $timeout The maximum number of seconds to spend waiting to retrieve a feed.
- */
- function set_timeout($timeout = 10)
- {
- $this->timeout = (int) $timeout;
- }
-
- /**
- * Forces SimplePie to use fsockopen() instead of the preferred cURL
- * functions.
- *
- * @access public
- * @since 1.0 Beta 3
- * @param bool $enable Force fsockopen() to be used
- */
- function force_fsockopen($enable = false)
- {
- $this->force_fsockopen = (bool) $enable;
- }
-
- /**
- * Outputs the raw XML content of the feed, after it has gone through
- * SimplePie's filters.
- *
- * Used only for debugging, this function will output the XML content as
- * text/xml. When SimplePie reads in a feed, it does a bit of cleaning up
- * before trying to parse it. Many parts of the feed are re-written in
- * memory, and in the end, you have a parsable feed. XML dump shows you the
- * actual XML that SimplePie tries to parse, which may or may not be very
- * different from the original feed.
- *
- * @access public
- * @since 1.0 Preview Release
- * @param bool $enable Enable XML dump
- */
- function enable_xml_dump($enable = false)
- {
- $this->xml_dump = (bool) $enable;
- }
-
- /**
- * Enables/disables caching in SimplePie.
- *
- * This option allows you to disable caching all-together in SimplePie.
- * However, disabling the cache can lead to longer load times.
- *
- * @access public
- * @since 1.0 Preview Release
- * @param bool $enable Enable caching
- */
- function enable_cache($enable = true)
- {
- $this->cache = (bool) $enable;
- }
-
- /**
- * Set the length of time (in seconds) that the contents of a feed
- * will be cached.
- *
- * @access public
- * @param int $seconds The feed content cache duration.
- */
- function set_cache_duration($seconds = 3600)
- {
- $this->cache_duration = (int) $seconds;
- }
-
- /**
- * Set the length of time (in seconds) that the autodiscovered feed
- * URL will be cached.
- *
- * @access public
- * @param int $seconds The autodiscovered feed URL cache duration.
- */
- function set_autodiscovery_cache_duration($seconds = 604800)
- {
- $this->autodiscovery_cache_duration = (int) $seconds;
- }
-
- /**
- * Set the file system location where the cached files should be stored.
- *
- * @access public
- * @param string $location The file system location.
- */
- function set_cache_location($location = './cache')
- {
- $this->cache_location = (string) $location;
- }
-
- /**
- * Determines whether feed items should be sorted into reverse chronological order.
- *
- * @access public
- * @param bool $enable Sort as reverse chronological order.
- */
- function enable_order_by_date($enable = true)
- {
- $this->order_by_date = (bool) $enable;
- }
-
- /**
- * Allows you to override the character encoding reported by the feed.
- *
- * @access public
- * @param string $encoding Character encoding.
- */
- function set_input_encoding($encoding = false)
- {
- if ($encoding)
- {
- $this->input_encoding = (string) $encoding;
- }
- else
- {
- $this->input_encoding = false;
- }
- }
-
- /**
- * Set how much feed autodiscovery to do
- *
- * @access public
- * @see SIMPLEPIE_LOCATOR_NONE
- * @see SIMPLEPIE_LOCATOR_AUTODISCOVERY
- * @see SIMPLEPIE_LOCATOR_LOCAL_EXTENSION
- * @see SIMPLEPIE_LOCATOR_LOCAL_BODY
- * @see SIMPLEPIE_LOCATOR_REMOTE_EXTENSION
- * @see SIMPLEPIE_LOCATOR_REMOTE_BODY
- * @see SIMPLEPIE_LOCATOR_ALL
- * @param int $level Feed Autodiscovery Level (level can be a
- * combination of the above constants, see bitwise OR operator)
- */
- function set_autodiscovery_level($level = SIMPLEPIE_LOCATOR_ALL)
- {
- $this->autodiscovery = (int) $level;
- }
-
- /**
- * Allows you to change which class SimplePie uses for caching.
- * Useful when you are overloading or extending SimplePie's default classes.
- *
- * @access public
- * @param string $class Name of custom class.
- * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation
- * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation
- */
- function set_cache_class($class = 'SimplePie_Cache')
- {
- if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Cache'))
- {
- $this->cache_class = $class;
- return true;
- }
- return false;
- }
-
- /**
- * Allows you to change which class SimplePie uses for auto-discovery.
- * Useful when you are overloading or extending SimplePie's default classes.
- *
- * @access public
- * @param string $class Name of custom class.
- * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation
- * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation
- */
- function set_locator_class($class = 'SimplePie_Locator')
- {
- if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Locator'))
- {
- $this->locator_class = $class;
- return true;
- }
- return false;
- }
-
- /**
- * Allows you to change which class SimplePie uses for XML parsing.
- * Useful when you are overloading or extending SimplePie's default classes.
- *
- * @access public
- * @param string $class Name of custom class.
- * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation
- * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation
- */
- function set_parser_class($class = 'SimplePie_Parser')
- {
- if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Parser'))
- {
- $this->parser_class = $class;
- return true;
- }
- return false;
- }
-
- /**
- * Allows you to change which class SimplePie uses for remote file fetching.
- * Useful when you are overloading or extending SimplePie's default classes.
- *
- * @access public
- * @param string $class Name of custom class.
- * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation
- * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation
- */
- function set_file_class($class = 'SimplePie_File')
- {
- if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_File'))
- {
- $this->file_class = $class;
- return true;
- }
- return false;
- }
-
- /**
- * Allows you to change which class SimplePie uses for data sanitization.
- * Useful when you are overloading or extending SimplePie's default classes.
- *
- * @access public
- * @param string $class Name of custom class.
- * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation
- * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation
- */
- function set_sanitize_class($class = 'SimplePie_Sanitize')
- {
- if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Sanitize'))
- {
- $this->sanitize = new $class;
- return true;
- }
- return false;
- }
-
- /**
- * Allows you to change which class SimplePie uses for handling feed items.
- * Useful when you are overloading or extending SimplePie's default classes.
- *
- * @access public
- * @param string $class Name of custom class.
- * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation
- * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation
- */
- function set_item_class($class = 'SimplePie_Item')
- {
- if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Item'))
- {
- $this->item_class = $class;
- return true;
- }
- return false;
- }
-
- /**
- * Allows you to change which class SimplePie uses for handling author data.
- * Useful when you are overloading or extending SimplePie's default classes.
- *
- * @access public
- * @param string $class Name of custom class.
- * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation
- * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation
- */
- function set_author_class($class = 'SimplePie_Author')
- {
- if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Author'))
- {
- $this->author_class = $class;
- return true;
- }
- return false;
- }
-
- /**
- * Allows you to change which class SimplePie uses for handling category data.
- * Useful when you are overloading or extending SimplePie's default classes.
- *
- * @access public
- * @param string $class Name of custom class.
- * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation
- * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation
- */
- function set_category_class($class = 'SimplePie_Category')
- {
- if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Category'))
- {
- $this->category_class = $class;
- return true;
- }
- return false;
- }
-
- /**
- * Allows you to change which class SimplePie uses for feed enclosures.
- * Useful when you are overloading or extending SimplePie's default classes.
- *
- * @access public
- * @param string $class Name of custom class.
- * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation
- * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation
- */
- function set_enclosure_class($class = 'SimplePie_Enclosure')
- {
- if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Enclosure'))
- {
- $this->enclosure_class = $class;
- return true;
- }
- return false;
- }
-
- /**
- * Allows you to change which class SimplePie uses for <media:text> captions
- * Useful when you are overloading or extending SimplePie's default classes.
- *
- * @access public
- * @param string $class Name of custom class.
- * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation
- * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation
- */
- function set_caption_class($class = 'SimplePie_Caption')
- {
- if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Caption'))
- {
- $this->caption_class = $class;
- return true;
- }
- return false;
- }
-
- /**
- * Allows you to change which class SimplePie uses for <media:copyright>
- * Useful when you are overloading or extending SimplePie's default classes.
- *
- * @access public
- * @param string $class Name of custom class.
- * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation
- * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation
- */
- function set_copyright_class($class = 'SimplePie_Copyright')
- {
- if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Copyright'))
- {
- $this->copyright_class = $class;
- return true;
- }
- return false;
- }
-
- /**
- * Allows you to change which class SimplePie uses for <media:credit>
- * Useful when you are overloading or extending SimplePie's default classes.
- *
- * @access public
- * @param string $class Name of custom class.
- * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation
- * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation
- */
- function set_credit_class($class = 'SimplePie_Credit')
- {
- if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Credit'))
- {
- $this->credit_class = $class;
- return true;
- }
- return false;
- }
-
- /**
- * Allows you to change which class SimplePie uses for <media:rating>
- * Useful when you are overloading or extending SimplePie's default classes.
- *
- * @access public
- * @param string $class Name of custom class.
- * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation
- * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation
- */
- function set_rating_class($class = 'SimplePie_Rating')
- {
- if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Rating'))
- {
- $this->rating_class = $class;
- return true;
- }
- return false;
- }
-
- /**
- * Allows you to change which class SimplePie uses for <media:restriction>
- * Useful when you are overloading or extending SimplePie's default classes.
- *
- * @access public
- * @param string $class Name of custom class.
- * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation
- * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation
- */
- function set_restriction_class($class = 'SimplePie_Restriction')
- {
- if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Restriction'))
- {
- $this->restriction_class = $class;
- return true;
- }
- return false;
- }
-
- /**
- * Allows you to change which class SimplePie uses for content-type sniffing.
- * Useful when you are overloading or extending SimplePie's default classes.
- *
- * @access public
- * @param string $class Name of custom class.
- * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation
- * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation
- */
- function set_content_type_sniffer_class($class = 'SimplePie_Content_Type_Sniffer')
- {
- if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Content_Type_Sniffer'))
- {
- $this->content_type_sniffer_class = $class;
- return true;
- }
- return false;
- }
-
- /**
- * Allows you to change which class SimplePie uses item sources.
- * Useful when you are overloading or extending SimplePie's default classes.
- *
- * @access public
- * @param string $class Name of custom class.
- * @link http://php.net/manual/en/keyword.extends.php PHP4 extends documentation
- * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation
- */
- function set_source_class($class = 'SimplePie_Source')
- {
- if (SimplePie_Misc::is_subclass_of($class, 'SimplePie_Source'))
- {
- $this->source_class = $class;
- return true;
- }
- return false;
- }
-
- /**
- * Allows you to override the default user agent string.
- *
- * @access public
- * @param string $ua New user agent string.
- */
- function set_useragent($ua = SIMPLEPIE_USERAGENT)
- {
- $this->useragent = (string) $ua;
- }
-
- /**
- * Set callback function to create cache filename with
- *
- * @access public
- * @param mixed $function Callback function
- */
- function set_cache_name_function($function = 'md5')
- {
- if (is_callable($function))
- {
- $this->cache_name_function = $function;
- }
- }
-
- /**
- * Set javascript query string parameter
- *
- * @access public
- * @param mixed $get Javascript query string parameter
- */
- function set_javascript($get = 'js')
- {
- if ($get)
- {
- $this->javascript = (string) $get;
- }
- else
- {
- $this->javascript = false;
- }
- }
-
- /**
- * Set options to make SP as fast as possible. Forgoes a
- * substantial amount of data sanitization in favor of speed.
- *
- * @access public
- * @param bool $set Whether to set them or not
- */
- function set_stupidly_fast($set = false)
- {
- if ($set)
- {
- $this->enable_order_by_date(false);
- $this->remove_div(false);
- $this->strip_comments(false);
- $this->strip_htmltags(false);
- $this->strip_attributes(false);
- $this->set_image_handler(false);
- }
- }
-
- /**
- * Set maximum number of feeds to check with autodiscovery
- *
- * @access public
- * @param int $max Maximum number of feeds to check
- */
- function set_max_checked_feeds($max = 10)
- {
- $this->max_checked_feeds = (int) $max;
- }
-
- function remove_div($enable = true)
- {
- $this->sanitize->remove_div($enable);
- }
-
- function strip_htmltags($tags = '', $encode = null)
- {
- if ($tags === '')
- {
- $tags = $this->strip_htmltags;
- }
- $this->sanitize->strip_htmltags($tags);
- if ($encode !== null)
- {
- $this->sanitize->encode_instead_of_strip($tags);
- }
- }
-
- function encode_instead_of_strip($enable = true)
- {
- $this->sanitize->encode_instead_of_strip($enable);
- }
-
- function strip_attributes($attribs = '')
- {
- if ($attribs === '')
- {
- $attribs = $this->strip_attributes;
- }
- $this->sanitize->strip_attributes($attribs);
- }
-
- function set_output_encoding($encoding = 'UTF-8')
- {
- $this->sanitize->set_output_encoding($encoding);
- }
-
- function strip_comments($strip = false)
- {
- $this->sanitize->strip_comments($strip);
- }
-
- /**
- * Set element/attribute key/value pairs of HTML attributes
- * containing URLs that need to be resolved relative to the feed
- *
- * @access public
- * @since 1.0
- * @param array $element_attribute Element/attribute key/value pairs
- */
- function set_url_replacements($element_attribute = array('a' => 'href', 'area' => 'href', 'blockquote' => 'cite', 'del' => 'cite', 'form' => 'action', 'img' => array('longdesc', 'src'), 'input' => 'src', 'ins' => 'cite', 'q' => 'cite'))
- {
- $this->sanitize->set_url_replacements($element_attribute);
- }
-
- /**
- * Set the handler to enable the display of cached favicons.
- *
- * @access public
- * @param str $page Web-accessible path to the handler_favicon.php file.
- * @param str $qs The query string that the value should be passed to.
- */
- function set_favicon_handler($page = false, $qs = 'i')
- {
- if ($page !== false)
- {
- $this->favicon_handler = $page . '?' . $qs . '=';
- }
- else
- {
- $this->favicon_handler = '';
- }
- }
-
- /**
- * Set the handler to enable the display of cached images.
- *
- * @access public
- * @param str $page Web-accessible path to the handler_image.php file.
- * @param str $qs The query string that the value should be passed to.
- */
- function set_image_handler($page = false, $qs = 'i')
- {
- if ($page !== false)
- {
- $this->sanitize->set_image_handler($page . '?' . $qs . '=');
- }
- else
- {
- $this->image_handler = '';
- }
- }
-
- /**
- * Set the limit for items returned per-feed with multifeeds.
- *
- * @access public
- * @param integer $limit The maximum number of items to return.
- */
- function set_item_limit($limit = 0)
- {
- $this->item_limit = (int) $limit;
- }
-
- function init()
- {
- // Check absolute bare minimum requirements.
- if ((function_exists('version_compare') && version_compare(PHP_VERSION, '4.3.0', '<')) || !extension_loaded('xml') || !extension_loaded('pcre'))
- {
- return false;
- }
- // Then check the xml extension is sane (i.e., libxml 2.7.x issue on PHP < 5.2.9 and libxml 2.7.0 to 2.7.2 on any version) if we don't have xmlreader.
- elseif (!extension_loaded('xmlreader'))
- {
- static $xml_is_sane = null;
- if ($xml_is_sane === null)
- {
- $parser_check = xml_parser_create();
- xml_parse_into_struct($parser_check, '<foo>&amp;</foo>', $values);
- xml_parser_free($parser_check);
- $xml_is_sane = isset($values[0]['value']);
- }
- if (!$xml_is_sane)
- {
- return false;
- }
- }
-
- if (isset($_GET[$this->javascript]))
- {
- SimplePie_Misc::output_javascript();
- exit;
- }
-
- // Pass whatever was set with config options over to the sanitizer.
- $this->sanitize->pass_cache_data($this->cache, $this->cache_location, $this->cache_name_function, $this->cache_class);
- $this->sanitize->pass_file_data($this->file_class, $this->timeout, $this->useragent, $this->force_fsockopen);
-
- if ($this->feed_url !== null || $this->raw_data !== null)
- {
- $this->data = array();
- $this->multifeed_objects = array();
- $cache = false;
-
- if ($this->feed_url !== null)
- {
- $parsed_feed_url = SimplePie_Misc::parse_url($this->feed_url);
- // Decide whether to enable caching
- if ($this->cache && $parsed_feed_url['scheme'] !== '')
- {
- $cache = call_user_func(array($this->cache_class, 'create'), $this->cache_location, call_user_func($this->cache_name_function, $this->feed_url), 'spc');
- }
- // If it's enabled and we don't want an XML dump, use the cache
- if ($cache && !$this->xml_dump)
- {
- // Load the Cache
- $this->data = $cache->load();
- if (!empty($this->data))
- {
- // If the cache is for an outdated build of SimplePie
- if (!isset($this->data['build']) || $this->data['build'] !== SIMPLEPIE_BUILD)
- {
- $cache->unlink();
- $this->data = array();
- }
- // If we've hit a collision just rerun it with caching disabled
- elseif (isset($this->data['url']) && $this->data['url'] !== $this->feed_url)
- {
- $cache = false;
- $this->data = array();
- }
- // If we've got a non feed_url stored (if the page isn't actually a feed, or is a redirect) use that URL.
- elseif (isset($this->data['feed_url']))
- {
- // If the autodiscovery cache is still valid use it.
- if ($cache->mtime() + $this->autodiscovery_cache_duration > time())
- {
- // Do not need to do feed autodiscovery yet.
- if ($this->data['feed_url'] === $this->data['url'])
- {
- $cache->unlink();
- $this->data = array();
- }
- else
- {
- $this->set_feed_url($this->data['feed_url']);
- return $this->init();
- }
- }
- }
- // Check if the cache has been updated
- elseif ($cache->mtime() + $this->cache_duration < time())
- {
- // If we have last-modified and/or etag set
- if (isset($this->data['headers']['last-modified']) || isset($this->data['headers']['etag']))
- {
- $headers = array();
- if (isset($this->data['headers']['last-modified']))
- {
- $headers['if-modified-since'] = $this->data['headers']['last-modified'];
- }
- if (isset($this->data['headers']['etag']))
- {
- $headers['if-none-match'] = '"' . $this->data['headers']['etag'] . '"';
- }
- $file = new $this->file_class($this->feed_url, $this->timeout/10, 5, $headers, $this->useragent, $this->force_fsockopen);
- if ($file->success)
- {
- if ($file->status_code === 304)
- {
- $cache->touch();
- return true;
- }
- else
- {
- $headers = $file->headers;
- }
- }
- else
- {
- unset($file);
- }
- }
- }
- // If the cache is still valid, just return true
- else
- {
- return true;
- }
- }
- // If the cache is empty, delete it
- else
- {
- $cache->unlink();
- $this->data = array();
- }
- }
- // If we don't already have the file (it'll only exist if we've opened it to check if the cache has been modified), open it.
- if (!isset($file))
- {
- if (is_a($this->file, 'SimplePie_File') && $this->file->url === $this->feed_url)
- {
- $file =& $this->file;
- }
- else
- {
- $file = new $this->file_class($this->feed_url, $this->timeout, 5, null, $this->useragent, $this->force_fsockopen);
- }
- }
- // If the file connection has an error, set SimplePie::error to that and quit
- if (!$file->success && !($file->method & SIMPLEPIE_FILE_SOURCE_REMOTE === 0 || ($file->status_code === 200 || $file->status_code > 206 && $file->status_code < 300)))
- {
- $this->error = $file->error;
- if (!empty($this->data))
- {
- return true;
- }
- else
- {
- return false;
- }
- }
-
- if (!$this->force_feed)
- {
- // Check if the supplied URL is a feed, if it isn't, look for it.
- $locate = new $this->locator_class($file, $this->timeout, $this->useragent, $this->file_class, $this->max_checked_feeds, $this->content_type_sniffer_class);
- if (!$locate->is_feed($file))
- {
- // We need to unset this so that if SimplePie::set_file() has been called that object is untouched
- unset($file);
- if ($file = $locate->find($this->autodiscovery, $this->all_discovered_feeds))
- {
- if ($cache)
- {
- $this->data = array('url' => $this->feed_url, 'feed_url' => $file->url, 'build' => SIMPLEPIE_BUILD);
- if (!$cache->save($this))
- {
- trigger_error("$this->cache_location is not writeable. Make sure you've set the correct relative or absolute path, and that the location is server-writable.", E_USER_WARNING);
- }
- $cache = call_user_func(array($this->cache_class, 'create'), $this->cache_location, call_user_func($this->cache_name_function, $file->url), 'spc');
- }
- $this->feed_url = $file->url;
- }
- else
- {
- $this->error = "A feed could not be found at $this->feed_url. A feed with an invalid mime type may fall victim to this error, or " . SIMPLEPIE_NAME . " was unable to auto-discover it.. Use force_feed() if you are certain this URL is a real feed.";
- SimplePie_Misc::error($this->error, E_USER_NOTICE, __FILE__, __LINE__);
- return false;
- }
- }
- $locate = null;
- }
-
- $headers = $file->headers;
- $data = $file->body;
- $sniffer = new $this->content_type_sniffer_class($file);
- $sniffed = $sniffer->get_type();
- }
- else
- {
- $data = $this->raw_data;
- }
-
- // Set up array of possible encodings
- $encodings = array();
-
- // First check to see if input has been overridden.
- if ($this->input_encoding !== false)
- {
- $encodings[] = $this->input_encoding;
- }
-
- $application_types = array('application/xml', 'application/xml-dtd', 'application/xml-external-parsed-entity');
- $text_types = array('text/xml', 'text/xml-external-parsed-entity');
-
- // RFC 3023 (only applies to sniffed content)
- if (isset($sniffed))
- {
- if (in_array($sniffed, $application_types) || substr($sniffed, 0, 12) === 'application/' && substr($sniffed, -4) === '+xml')
- {
- if (isset($headers['content-type']) && preg_match('/;\x20?charset=([^;]*)/i', $headers['content-type'], $charset))
- {
- $encodings[] = strtoupper($charset[1]);
- }
- $encodings = array_merge($encodings, SimplePie_Misc::xml_encoding($data));
- $encodings[] = 'UTF-8';
- }
- elseif (in_array($sniffed, $text_types) || substr($sniffed, 0, 5) === 'text/' && substr($sniffed, -4) === '+xml')
- {
- if (isset($headers['content-type']) && preg_match('/;\x20?charset=([^;]*)/i', $headers['content-type'], $charset))
- {
- $encodings[] = $charset[1];
- }
- $encodings[] = 'US-ASCII';
- }
- // Text MIME-type default
- elseif (substr($sniffed, 0, 5) === 'text/')
- {
- $encodings[] = 'US-ASCII';
- }
- }
-
- // Fallback to XML 1.0 Appendix F.1/UTF-8/ISO-8859-1
- $encodings = array_merge($encodings, SimplePie_Misc::xml_encoding($data));
- $encodings[] = 'UTF-8';
- $encodings[] = 'ISO-8859-1';
-
- // There's no point in trying an encoding twice
- $encodings = array_unique($encodings);
-
- // If we want the XML, just output that with the most likely encoding and quit
- if ($this->xml_dump)
- {
- header('Content-type: text/xml; charset=' . $encodings[0]);
- echo $data;
- exit;
- }
-
- // Loop through each possible encoding, till we return something, or run out of possibilities
- foreach ($encodings as $encoding)
- {
- // Change the encoding to UTF-8 (as we always use UTF-8 internally)
- if ($utf8_data = SimplePie_Misc::change_encoding($data, $encoding, 'UTF-8'))
- {
- // Create new parser
- $parser = new $this->parser_class();
-
- // If it's parsed fine
- if ($parser->parse($utf8_data, 'UTF-8'))
- {
- $this->data = $parser->get_data();
- if ($this->get_type() & ~SIMPLEPIE_TYPE_NONE)
- {
- if (isset($headers))
- {
- $this->data['headers'] = $headers;
- }
- $this->data['build'] = SIMPLEPIE_BUILD;
-
- // Cache the file if caching is enabled
- if ($cache && !$cache->save($this))
- {
- trigger_error("$this->cache_location is not writeable. Make sure you've set the correct relative or absolute path, and that the location is server-writable.", E_USER_WARNING);
- }
- return true;
- }
- else
- {
- $this->error = "A feed could not be found at $this->feed_url. This does not appear to be a valid RSS or Atom feed.";
- SimplePie_Misc::error($this->error, E_USER_NOTICE, __FILE__, __LINE__);
- return false;
- }
- }
- }
- }
- if (isset($parser))
- {
- // We have an error, just set SimplePie_Misc::error to it and quit
- $this->error = sprintf('This XML document is invalid, likely due to invalid characters. XML error: %s at line %d, column %d', $parser->get_error_string(), $parser->get_current_line(), $parser->get_current_column());
- }
- else
- {
- $this->error = 'The data could not be converted to UTF-8. You MUST have either the iconv or mbstring extension installed. Upgrading to PHP 5.x (which includes iconv) is highly recommended.';
- }
- SimplePie_Misc::error($this->error, E_USER_NOTICE, __FILE__, __LINE__);
- return false;
- }
- elseif (!empty($this->multifeed_url))
- {
- $i = 0;
- $success = 0;
- $this->multifeed_objects = array();
- foreach ($this->multifeed_url as $url)
- {
- if (SIMPLEPIE_PHP5)
- {
- // This keyword needs to defy coding standards for PHP4 compatibility
- $this->multifeed_objects[$i] = clone($this);
- }
- else
- {
- $this->multifeed_objects[$i] = $this;
- }
- $this->multifeed_objects[$i]->set_feed_url($url);
- $success |= $this->multifeed_objects[$i]->init();
- $i++;
- }
- return (bool) $success;
- }
- else
- {
- return false;
- }
- }
-
- /**
- * Return the error message for the occured error
- *
- * @access public
- * @return string Error message
- */
- function error()
- {
- return $this->error;
- }
-
- function get_encoding()
- {
- return $this->sanitize->output_encoding;
- }
-
- function handle_content_type($mime = 'text/html')
- {
- if (!headers_sent())
- {
- $header = "Content-type: $mime;";
- if ($this->get_encoding())
- {
- $header .= ' charset=' . $this->get_encoding();
- }
- else
- {
- $header .= ' charset=UTF-8';
- }
- header($header);
- }
- }
-
- function get_type()
- {
- if (!isset($this->data['type']))
- {
- $this->data['type'] = SIMPLEPIE_TYPE_ALL;
- if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed']))
- {
- $this->data['type'] &= SIMPLEPIE_TYPE_ATOM_10;
- }
- elseif (isset($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed']))
- {
- $this->data['type'] &= SIMPLEPIE_TYPE_ATOM_03;
- }
- elseif (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF']))
- {
- if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_10]['channel'])
- || isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_10]['image'])
- || isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_10]['item'])
- || isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_10]['textinput']))
- {
- $this->data['type'] &= SIMPLEPIE_TYPE_RSS_10;
- }
- if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_090]['channel'])
- || isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_090]['image'])
- || isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_090]['item'])
- || isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_090]['textinput']))
- {
- $this->data['type'] &= SIMPLEPIE_TYPE_RSS_090;
- }
- }
- elseif (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss']))
- {
- $this->data['type'] &= SIMPLEPIE_TYPE_RSS_ALL;
- if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['attribs']['']['version']))
- {
- switch (trim($this->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['attribs']['']['version']))
- {
- case '0.91':
- $this->data['type'] &= SIMPLEPIE_TYPE_RSS_091;
- if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_20]['skiphours']['hour'][0]['data']))
- {
- switch (trim($this->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_20]['skiphours']['hour'][0]['data']))
- {
- case '0':
- $this->data['type'] &= SIMPLEPIE_TYPE_RSS_091_NETSCAPE;
- break;
-
- case '24':
- $this->data['type'] &= SIMPLEPIE_TYPE_RSS_091_USERLAND;
- break;
- }
- }
- break;
-
- case '0.92':
- $this->data['type'] &= SIMPLEPIE_TYPE_RSS_092;
- break;
-
- case '0.93':
- $this->data['type'] &= SIMPLEPIE_TYPE_RSS_093;
- break;
-
- case '0.94':
- $this->data['type'] &= SIMPLEPIE_TYPE_RSS_094;
- break;
-
- case '2.0':
- $this->data['type'] &= SIMPLEPIE_TYPE_RSS_20;
- break;
- }
- }
- }
- else
- {
- $this->data['type'] = SIMPLEPIE_TYPE_NONE;
- }
- }
- return $this->data['type'];
- }
-
- /**
- * Returns the URL for the favicon of the feed's website.
- *
- * @todo Cache atom:icon
- * @access public
- * @since 1.0
- */
- function get_favicon()
- {
- if ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'icon'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0]));
- }
- elseif (($url = $this->get_link()) !== null && preg_match('/^http(s)?:\/\//i', $url))
- {
- $favicon = SimplePie_Misc::absolutize_url('/favicon.ico', $url);
-
- if ($this->cache && $this->favicon_handler)
- {
- $favicon_filename = call_user_func($this->cache_name_function, $favicon);
- $cache = call_user_func(array($this->cache_class, 'create'), $this->cache_location, $favicon_filename, 'spi');
-
- if ($cache->load())
- {
- return $this->sanitize($this->favicon_handler . $favicon_filename, SIMPLEPIE_CONSTRUCT_IRI);
- }
- else
- {
- $file = new $this->file_class($favicon, $this->timeout / 10, 5, array('X-FORWARDED-FOR' => $_SERVER['REMOTE_ADDR']), $this->useragent, $this->force_fsockopen);
-
- if ($file->success && ($file->method & SIMPLEPIE_FILE_SOURCE_REMOTE === 0 || ($file->status_code === 200 || $file->status_code > 206 && $file->status_code < 300)) && strlen($file->body) > 0)
- {
- $sniffer = new $this->content_type_sniffer_class($file);
- if (substr($sniffer->get_type(), 0, 6) === 'image/')
- {
- if ($cache->save(array('headers' => $file->headers, 'body' => $file->body)))
- {
- return $this->sanitize($this->favicon_handler . $favicon_filename, SIMPLEPIE_CONSTRUCT_IRI);
- }
- else
- {
- trigger_error("$cache->name is not writeable. Make sure you've set the correct relative or absolute path, and that the location is server-writable.", E_USER_WARNING);
- return $this->sanitize($favicon, SIMPLEPIE_CONSTRUCT_IRI);
- }
- }
- // not an image
- else
- {
- return false;
- }
- }
- }
- }
- else
- {
- return $this->sanitize($favicon, SIMPLEPIE_CONSTRUCT_IRI);
- }
- }
- return false;
- }
-
- /**
- * @todo If we have a perm redirect we should return the new URL
- * @todo When we make the above change, let's support <itunes:new-feed-url> as well
- * @todo Also, |atom:link|@rel=self
- */
- function subscribe_url()
- {
- if ($this->feed_url !== null)
- {
- return $this->sanitize($this->feed_url, SIMPLEPIE_CONSTRUCT_IRI);
- }
- else
- {
- return null;
- }
- }
-
- function subscribe_feed()
- {
- if ($this->feed_url !== null)
- {
- return $this->sanitize(SimplePie_Misc::fix_protocol($this->feed_url, 2), SIMPLEPIE_CONSTRUCT_IRI);
- }
- else
- {
- return null;
- }
- }
-
- function subscribe_outlook()
- {
- if ($this->feed_url !== null)
- {
- return $this->sanitize('outlook' . SimplePie_Misc::fix_protocol($this->feed_url, 2), SIMPLEPIE_CONSTRUCT_IRI);
- }
- else
- {
- return null;
- }
- }
-
- function subscribe_podcast()
- {
- if ($this->feed_url !== null)
- {
- return $this->sanitize(SimplePie_Misc::fix_protocol($this->feed_url, 3), SIMPLEPIE_CONSTRUCT_IRI);
- }
- else
- {
- return null;
- }
- }
-
- function subscribe_itunes()
- {
- if ($this->feed_url !== null)
- {
- return $this->sanitize(SimplePie_Misc::fix_protocol($this->feed_url, 4), SIMPLEPIE_CONSTRUCT_IRI);
- }
- else
- {
- return null;
- }
- }
-
- /**
- * Creates the subscribe_* methods' return data
- *
- * @access private
- * @param string $feed_url String to prefix to the feed URL
- * @param string $site_url String to prefix to the site URL (and
- * suffix to the feed URL)
- * @return mixed URL if feed exists, false otherwise
- */
- function subscribe_service($feed_url, $site_url = null)
- {
- if ($this->subscribe_url())
- {
- $return = $feed_url . rawurlencode($this->feed_url);
- if ($site_url !== null && $this->get_link() !== null)
- {
- $return .= $site_url . rawurlencode($this->get_link());
- }
- return $this->sanitize($return, SIMPLEPIE_CONSTRUCT_IRI);
- }
- else
- {
- return null;
- }
- }
-
- function subscribe_aol()
- {
- return $this->subscribe_service('http://feeds.my.aol.com/add.jsp?url=');
- }
-
- function subscribe_bloglines()
- {
- return $this->subscribe_service('http://www.bloglines.com/sub/');
- }
-
- function subscribe_eskobo()
- {
- return $this->subscribe_service('http://www.eskobo.com/?AddToMyPage=');
- }
-
- function subscribe_feedfeeds()
- {
- return $this->subscribe_service('http://www.feedfeeds.com/add?feed=');
- }
-
- function subscribe_feedster()
- {
- return $this->subscribe_service('http://www.feedster.com/myfeedster.php?action=addrss&confirm=no&rssurl=');
- }
-
- function subscribe_google()
- {
- return $this->subscribe_service('http://fusion.google.com/add?feedurl=');
- }
-
- function subscribe_gritwire()
- {
- return $this->subscribe_service('http://my.gritwire.com/feeds/addExternalFeed.aspx?FeedUrl=');
- }
-
- function subscribe_msn()
- {
- return $this->subscribe_service('http://my.msn.com/addtomymsn.armx?id=rss&ut=', '&ru=');
- }
-
- function subscribe_netvibes()
- {
- return $this->subscribe_service('http://www.netvibes.com/subscribe.php?url=');
- }
-
- function subscribe_newsburst()
- {
- return $this->subscribe_service('http://www.newsburst.com/Source/?add=');
- }
-
- function subscribe_newsgator()
- {
- return $this->subscribe_service('http://www.newsgator.com/ngs/subscriber/subext.aspx?url=');
- }
-
- function subscribe_odeo()
- {
- return $this->subscribe_service('http://www.odeo.com/listen/subscribe?feed=');
- }
-
- function subscribe_podnova()
- {
- return $this->subscribe_service('http://www.podnova.com/index_your_podcasts.srf?action=add&url=');
- }
-
- function subscribe_rojo()
- {
- return $this->subscribe_service('http://www.rojo.com/add-subscription?resource=');
- }
-
- function subscribe_yahoo()
- {
- return $this->subscribe_service('http://add.my.yahoo.com/rss?url=');
- }
-
- function get_feed_tags($namespace, $tag)
- {
- $type = $this->get_type();
- if ($type & SIMPLEPIE_TYPE_ATOM_10)
- {
- if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0]['child'][$namespace][$tag]))
- {
- return $this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0]['child'][$namespace][$tag];
- }
- }
- if ($type & SIMPLEPIE_TYPE_ATOM_03)
- {
- if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0]['child'][$namespace][$tag]))
- {
- return $this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0]['child'][$namespace][$tag];
- }
- }
- if ($type & SIMPLEPIE_TYPE_RSS_RDF)
- {
- if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][$namespace][$tag]))
- {
- return $this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][$namespace][$tag];
- }
- }
- if ($type & SIMPLEPIE_TYPE_RSS_SYNDICATION)
- {
- if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['child'][$namespace][$tag]))
- {
- return $this->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['child'][$namespace][$tag];
- }
- }
- return null;
- }
-
- function get_channel_tags($namespace, $tag)
- {
- $type = $this->get_type();
- if ($type & SIMPLEPIE_TYPE_ATOM_ALL)
- {
- if ($return = $this->get_feed_tags($namespace, $tag))
- {
- return $return;
- }
- }
- if ($type & SIMPLEPIE_TYPE_RSS_10)
- {
- if ($channel = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'channel'))
- {
- if (isset($channel[0]['child'][$namespace][$tag]))
- {
- return $channel[0]['child'][$namespace][$tag];
- }
- }
- }
- if ($type & SIMPLEPIE_TYPE_RSS_090)
- {
- if ($channel = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'channel'))
- {
- if (isset($channel[0]['child'][$namespace][$tag]))
- {
- return $channel[0]['child'][$namespace][$tag];
- }
- }
- }
- if ($type & SIMPLEPIE_TYPE_RSS_SYNDICATION)
- {
- if ($channel = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'channel'))
- {
- if (isset($channel[0]['child'][$namespace][$tag]))
- {
- return $channel[0]['child'][$namespace][$tag];
- }
- }
- }
- return null;
- }
-
- function get_image_tags($namespace, $tag)
- {
- $type = $this->get_type();
- if ($type & SIMPLEPIE_TYPE_RSS_10)
- {
- if ($image = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'image'))
- {
- if (isset($image[0]['child'][$namespace][$tag]))
- {
- return $image[0]['child'][$namespace][$tag];
- }
- }
- }
- if ($type & SIMPLEPIE_TYPE_RSS_090)
- {
- if ($image = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'image'))
- {
- if (isset($image[0]['child'][$namespace][$tag]))
- {
- return $image[0]['child'][$namespace][$tag];
- }
- }
- }
- if ($type & SIMPLEPIE_TYPE_RSS_SYNDICATION)
- {
- if ($image = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'image'))
- {
- if (isset($image[0]['child'][$namespace][$tag]))
- {
- return $image[0]['child'][$namespace][$tag];
- }
- }
- }
- return null;
- }
-
- function get_base($element = array())
- {
- if (!($this->get_type() & SIMPLEPIE_TYPE_RSS_SYNDICATION) && !empty($element['xml_base_explicit']) && isset($element['xml_base']))
- {
- return $element['xml_base'];
- }
- elseif ($this->get_link() !== null)
- {
- return $this->get_link();
- }
- else
- {
- return $this->subscribe_url();
- }
- }
-
- function sanitize($data, $type, $base = '')
- {
- return $this->sanitize->sanitize($data, $type, $base);
- }
-
- function get_title()
- {
- if ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'title'))
- {
- return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_10_construct_type($return[0]['attribs']), $this->get_base($return[0]));
- }
- elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'title'))
- {
- return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_03_construct_type($return[0]['attribs']), $this->get_base($return[0]));
- }
- elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'title'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'title'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'title'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_11, 'title'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_10, 'title'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- return null;
- }
- }
-
- function get_category($key = 0)
- {
- $categories = $this->get_categories();
- if (isset($categories[$key]))
- {
- return $categories[$key];
- }
- else
- {
- return null;
- }
- }
-
- function get_categories()
- {
- $categories = array();
-
- foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'category') as $category)
- {
- $term = null;
- $scheme = null;
- $label = null;
- if (isset($category['attribs']['']['term']))
- {
- $term = $this->sanitize($category['attribs']['']['term'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($category['attribs']['']['scheme']))
- {
- $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($category['attribs']['']['label']))
- {
- $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $categories[] = new $this->category_class($term, $scheme, $label);
- }
- foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'category') as $category)
- {
- // This is really the label, but keep this as the term also for BC.
- // Label will also work on retrieving because that falls back to term.
- $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- if (isset($category['attribs']['']['domain']))
- {
- $scheme = $this->sanitize($category['attribs']['']['domain'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $scheme = null;
- }
- $categories[] = new $this->category_class($term, $scheme, null);
- }
- foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_11, 'subject') as $category)
- {
- $categories[] = new $this->category_class($this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null);
- }
- foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_10, 'subject') as $category)
- {
- $categories[] = new $this->category_class($this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null);
- }
-
- if (!empty($categories))
- {
- return SimplePie_Misc::array_unique($categories);
- }
- else
- {
- return null;
- }
- }
-
- function get_author($key = 0)
- {
- $authors = $this->get_authors();
- if (isset($authors[$key]))
- {
- return $authors[$key];
- }
- else
- {
- return null;
- }
- }
-
- function get_authors()
- {
- $authors = array();
- foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'author') as $author)
- {
- $name = null;
- $uri = null;
- $email = null;
- $avatar = null;
- $name_date = null;
- $uri_date = null;
- $avatar_date = null;
-
- if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data']))
- {
- $name = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data']))
- {
- $uri = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]));
- }
- if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data']))
- {
- $email = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($author['child']['http://purl.org/macgirvin/dfrn/1.0']['avatar'][0]['data']))
- {
- $avatar = $this->sanitize($author['child']['http://purl.org/macgirvin/dfrn/1.0']['avatar'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($author['child']['http://purl.org/macgirvin/dfrn/1.0']['avatar'][0]));
- }
- if (isset($author['child']['http://purl.org/macgirvin/dfrn/1.0']['name-updated'][0]['data']))
- {
- $name_date = $author['child']['http://purl.org/macgirvin/dfrn/1.0']['name-updated'][0]['data'];
- }
- if (isset($author['child']['http://purl.org/macgirvin/dfrn/1.0']['uri-updated'][0]['data']))
- {
- $uri_date = $author['child']['http://purl.org/macgirvin/dfrn/1.0']['uri-updated'][0]['data'];
- }
- if (isset($author['child']['http://purl.org/macgirvin/dfrn/1.0']['avatar-updated'][0]['data']))
- {
- $avatar_date = $author['child']['http://purl.org/macgirvin/dfrn/1.0']['avatar-updated'][0]['data'];
- }
-
- if ($name !== null || $email !== null || $uri !== null || $avatar !== null || $name_date !== null || $uri_date !== null || $avatar_date !== null )
- {
- $authors[] = new $this->author_class($name, $uri, $email, $avatar, $name_date, $uri_date, $avatar_date);
- }
- }
- if ($author = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'author'))
- {
- $name = null;
- $url = null;
- $email = null;
- if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data']))
- {
- $name = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data']))
- {
- $url = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]));
- }
- if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data']))
- {
- $email = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if ($name !== null || $email !== null || $url !== null)
- {
- $authors[] = new $this->author_class($name, $url, $email);
- }
- }
- foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_11, 'creator') as $author)
- {
- $authors[] = new $this->author_class($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null);
- }
- foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_10, 'creator') as $author)
- {
- $authors[] = new $this->author_class($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null);
- }
- foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'author') as $author)
- {
- $authors[] = new $this->author_class($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null);
- }
-
- if (!empty($authors))
- {
- return SimplePie_Misc::array_unique($authors);
- }
- else
- {
- return null;
- }
- }
-
- function get_contributor($key = 0)
- {
- $contributors = $this->get_contributors();
- if (isset($contributors[$key]))
- {
- return $contributors[$key];
- }
- else
- {
- return null;
- }
- }
-
- function get_contributors()
- {
- $contributors = array();
- foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'contributor') as $contributor)
- {
- $name = null;
- $uri = null;
- $email = null;
- if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data']))
- {
- $name = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data']))
- {
- $uri = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]));
- }
- if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data']))
- {
- $email = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if ($name !== null || $email !== null || $uri !== null)
- {
- $contributors[] = new $this->author_class($name, $uri, $email);
- }
- }
- foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'contributor') as $contributor)
- {
- $name = null;
- $url = null;
- $email = null;
- if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data']))
- {
- $name = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data']))
- {
- $url = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]));
- }
- if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data']))
- {
- $email = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if ($name !== null || $email !== null || $url !== null)
- {
- $contributors[] = new $this->author_class($name, $url, $email);
- }
- }
-
- if (!empty($contributors))
- {
- return SimplePie_Misc::array_unique($contributors);
- }
- else
- {
- return null;
- }
- }
-
- function get_link($key = 0, $rel = 'alternate')
- {
- $links = $this->get_links($rel);
- if (isset($links[$key]))
- {
- return $links[$key];
- }
- else
- {
- return null;
- }
- }
-
- /**
- * Added for parity between the parent-level and the item/entry-level.
- */
- function get_permalink()
- {
- return $this->get_link(0);
- }
-
- function get_links($rel = 'alternate')
- {
- if (!isset($this->data['links']))
- {
- $this->data['links'] = array();
- if ($links = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'link'))
- {
- foreach ($links as $link)
- {
- if (isset($link['attribs']['']['href']))
- {
- $link_rel = (isset($link['attribs']['']['rel'])) ? $link['attribs']['']['rel'] : 'alternate';
- $this->data['links'][$link_rel][] = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link));
- }
- }
- }
- if ($links = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'link'))
- {
- foreach ($links as $link)
- {
- if (isset($link['attribs']['']['href']))
- {
- $link_rel = (isset($link['attribs']['']['rel'])) ? $link['attribs']['']['rel'] : 'alternate';
- $this->data['links'][$link_rel][] = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link));
-
- }
- }
- }
- if ($links = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'link'))
- {
- $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0]));
- }
- if ($links = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'link'))
- {
- $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0]));
- }
- if ($links = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'link'))
- {
- $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0]));
- }
-
- $keys = array_keys($this->data['links']);
- foreach ($keys as $key)
- {
- if (SimplePie_Misc::is_isegment_nz_nc($key))
- {
- if (isset($this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key]))
- {
- $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key] = array_merge($this->data['links'][$key], $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key]);
- $this->data['links'][$key] =& $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key];
- }
- else
- {
- $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key] =& $this->data['links'][$key];
- }
- }
- elseif (substr($key, 0, 41) === SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY)
- {
- $this->data['links'][substr($key, 41)] =& $this->data['links'][$key];
- }
- $this->data['links'][$key] = array_unique($this->data['links'][$key]);
- }
- }
-
- if (isset($this->data['links'][$rel]))
- {
- return $this->data['links'][$rel];
- }
- else
- {
- return null;
- }
- }
-
- function get_all_discovered_feeds()
- {
- return $this->all_discovered_feeds;
- }
-
- function get_description()
- {
- if ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'subtitle'))
- {
- return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_10_construct_type($return[0]['attribs']), $this->get_base($return[0]));
- }
- elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'tagline'))
- {
- return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_03_construct_type($return[0]['attribs']), $this->get_base($return[0]));
- }
- elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'description'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'description'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'description'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_11, 'description'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_10, 'description'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'summary'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'subtitle'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($return[0]));
- }
- else
- {
- return null;
- }
- }
-
- function get_copyright()
- {
- if ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'rights'))
- {
- return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_10_construct_type($return[0]['attribs']), $this->get_base($return[0]));
- }
- elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'copyright'))
- {
- return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_03_construct_type($return[0]['attribs']), $this->get_base($return[0]));
- }
- elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'copyright'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_11, 'rights'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_10, 'rights'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- return null;
- }
- }
-
- function get_language()
- {
- if ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'language'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_11, 'language'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_10, 'language'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif (isset($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0]['xml_lang']))
- {
- return $this->sanitize($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0]['xml_lang'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif (isset($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0]['xml_lang']))
- {
- return $this->sanitize($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0]['xml_lang'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['xml_lang']))
- {
- return $this->sanitize($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['xml_lang'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif (isset($this->data['headers']['content-language']))
- {
- return $this->sanitize($this->data['headers']['content-language'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- return null;
- }
- }
-
- function get_latitude()
- {
-
- if ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'lat'))
- {
- return (float) $return[0]['data'];
- }
- elseif (($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_GEORSS, 'point')) && preg_match('/^((?:-)?[0-9]+(?:\.[0-9]+)) ((?:-)?[0-9]+(?:\.[0-9]+))$/', trim($return[0]['data']), $match))
- {
- return (float) $match[1];
- }
- else
- {
- return null;
- }
- }
-
- function get_longitude()
- {
- if ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'long'))
- {
- return (float) $return[0]['data'];
- }
- elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'lon'))
- {
- return (float) $return[0]['data'];
- }
- elseif (($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_GEORSS, 'point')) && preg_match('/^((?:-)?[0-9]+(?:\.[0-9]+)) ((?:-)?[0-9]+(?:\.[0-9]+))$/', trim($return[0]['data']), $match))
- {
- return (float) $match[2];
- }
- else
- {
- return null;
- }
- }
-
- function get_image_title()
- {
- if ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'title'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'title'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'title'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_DC_11, 'title'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_DC_10, 'title'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- return null;
- }
- }
-
- function get_image_url()
- {
- if ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'image'))
- {
- return $this->sanitize($return[0]['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI);
- }
- elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'logo'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'icon'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'url'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'url'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'url'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0]));
- }
- else
- {
- return null;
- }
- }
-
- function get_image_link()
- {
- if ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'link'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'link'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'link'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0]));
- }
- else
- {
- return null;
- }
- }
-
- function get_image_width()
- {
- if ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'width'))
- {
- return round($return[0]['data']);
- }
- elseif ($this->get_type() & SIMPLEPIE_TYPE_RSS_SYNDICATION && $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'url'))
- {
- return 88.0;
- }
- else
- {
- return null;
- }
- }
-
- function get_image_height()
- {
- if ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'height'))
- {
- return round($return[0]['data']);
- }
- elseif ($this->get_type() & SIMPLEPIE_TYPE_RSS_SYNDICATION && $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'url'))
- {
- return 31.0;
- }
- else
- {
- return null;
- }
- }
-
- function get_item_quantity($max = 0)
- {
- $max = (int) $max;
- $qty = count($this->get_items());
- if ($max === 0)
- {
- return $qty;
- }
- else
- {
- return ($qty > $max) ? $max : $qty;
- }
- }
-
- function get_item($key = 0)
- {
- $items = $this->get_items();
- if (isset($items[$key]))
- {
- return $items[$key];
- }
- else
- {
- return null;
- }
- }
-
- function get_items($start = 0, $end = 0)
- {
- if (!isset($this->data['items']))
- {
- if (!empty($this->multifeed_objects))
- {
- $this->data['items'] = SimplePie::merge_items($this->multifeed_objects, $start, $end, $this->item_limit);
- }
- else
- {
- $this->data['items'] = array();
- if ($items = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'entry'))
- {
- $keys = array_keys($items);
- foreach ($keys as $key)
- {
- $this->data['items'][] = new $this->item_class($this, $items[$key]);
- }
- }
- if ($items = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'entry'))
- {
- $keys = array_keys($items);
- foreach ($keys as $key)
- {
- $this->data['items'][] = new $this->item_class($this, $items[$key]);
- }
- }
- if ($items = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'item'))
- {
- $keys = array_keys($items);
- foreach ($keys as $key)
- {
- $this->data['items'][] = new $this->item_class($this, $items[$key]);
- }
- }
- if ($items = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'item'))
- {
- $keys = array_keys($items);
- foreach ($keys as $key)
- {
- $this->data['items'][] = new $this->item_class($this, $items[$key]);
- }
- }
- if ($items = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'item'))
- {
- $keys = array_keys($items);
- foreach ($keys as $key)
- {
- $this->data['items'][] = new $this->item_class($this, $items[$key]);
- }
- }
- }
- }
-
- if (!empty($this->data['items']))
- {
- // If we want to order it by date, check if all items have a date, and then sort it
- if ($this->order_by_date && empty($this->multifeed_objects))
- {
- if (!isset($this->data['ordered_items']))
- {
- $do_sort = true;
- foreach ($this->data['items'] as $item)
- {
- if (!$item->get_date('U'))
- {
- $do_sort = false;
- break;
- }
- }
- $item = null;
- $this->data['ordered_items'] = $this->data['items'];
- if ($do_sort)
- {
- usort($this->data['ordered_items'], array(&$this, 'sort_items'));
- }
- }
- $items = $this->data['ordered_items'];
- }
- else
- {
- $items = $this->data['items'];
- }
-
- // Slice the data as desired
- if ($end === 0)
- {
- return array_slice($items, $start);
- }
- else
- {
- return array_slice($items, $start, $end);
- }
- }
- else
- {
- return array();
- }
- }
-
- /**
- * @static
- */
- function sort_items($a, $b)
- {
- return $a->get_date('U') <= $b->get_date('U');
- }
-
- /**
- * @static
- */
- function merge_items($urls, $start = 0, $end = 0, $limit = 0)
- {
- if (is_array($urls) && sizeof($urls) > 0)
- {
- $items = array();
- foreach ($urls as $arg)
- {
- if (is_a($arg, 'SimplePie'))
- {
- $items = array_merge($items, $arg->get_items(0, $limit));
- }
- else
- {
- trigger_error('Arguments must be SimplePie objects', E_USER_WARNING);
- }
- }
-
- $do_sort = true;
- foreach ($items as $item)
- {
- if (!$item->get_date('U'))
- {
- $do_sort = false;
- break;
- }
- }
- $item = null;
- if ($do_sort)
- {
- usort($items, array('SimplePie', 'sort_items'));
- }
-
- if ($end === 0)
- {
- return array_slice($items, $start);
- }
- else
- {
- return array_slice($items, $start, $end);
- }
- }
- else
- {
- trigger_error('Cannot merge zero SimplePie objects', E_USER_WARNING);
- return array();
- }
- }
-}
-
-class SimplePie_Item
-{
- var $feed;
- var $data = array();
-
- function SimplePie_Item($feed, $data)
- {
- $this->feed = $feed;
- $this->data = $data;
- }
-
- function __toString()
- {
- return md5(serialize($this->data));
- }
-
- /**
- * Remove items that link back to this before destroying this object
- */
- function __destruct()
- {
- if ((version_compare(PHP_VERSION, '5.3', '<') || !gc_enabled()) && !ini_get('zend.ze1_compatibility_mode'))
- {
- unset($this->feed);
- }
- }
-
- function get_item_tags($namespace, $tag)
- {
- if (isset($this->data['child'][$namespace][$tag]))
- {
- return $this->data['child'][$namespace][$tag];
- }
- else
- {
- return null;
- }
- }
-
- function get_base($element = array())
- {
- return $this->feed->get_base($element);
- }
-
- function sanitize($data, $type, $base = '')
- {
- return $this->feed->sanitize($data, $type, $base);
- }
-
- function get_feed()
- {
- return $this->feed;
- }
-
- function get_id($hash = false)
- {
- if (!$hash)
- {
- if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'id'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'id'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'guid'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_11, 'identifier'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_10, 'identifier'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif (($return = $this->get_permalink()) !== null)
- {
- return $return;
- }
- elseif (($return = $this->get_title()) !== null)
- {
- return $return;
- }
- }
- if ($this->get_permalink() !== null || $this->get_title() !== null)
- {
- return md5($this->get_permalink() . $this->get_title());
- }
- else
- {
- return md5(serialize($this->data));
- }
- }
-
- function get_title()
- {
- if (!isset($this->data['title']))
- {
- if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'title'))
- {
- $this->data['title'] = $this->sanitize($return[0]['data'], SimplePie_Misc::atom_10_construct_type($return[0]['attribs']), $this->get_base($return[0]));
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'title'))
- {
- $this->data['title'] = $this->sanitize($return[0]['data'], SimplePie_Misc::atom_03_construct_type($return[0]['attribs']), $this->get_base($return[0]));
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'title'))
- {
- $this->data['title'] = $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'title'))
- {
- $this->data['title'] = $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'title'))
- {
- $this->data['title'] = $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_11, 'title'))
- {
- $this->data['title'] = $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_10, 'title'))
- {
- $this->data['title'] = $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $this->data['title'] = null;
- }
- }
- return $this->data['title'];
- }
-
- function get_description($description_only = false)
- {
- if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'summary'))
- {
- return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_10_construct_type($return[0]['attribs']), $this->get_base($return[0]));
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'summary'))
- {
- return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_03_construct_type($return[0]['attribs']), $this->get_base($return[0]));
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'description'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'description'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_11, 'description'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_10, 'description'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'summary'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'subtitle'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif (!$description_only)
- {
- return $this->get_content(true);
- }
- else
- {
- return null;
- }
- }
-
- function get_content($content_only = false)
- {
- if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'content'))
- {
- return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_10_content_construct_type($return[0]['attribs']), $this->get_base($return[0]));
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'content'))
- {
- return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_03_construct_type($return[0]['attribs']), $this->get_base($return[0]));
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_10_MODULES_CONTENT, 'encoded'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($return[0]));
- }
- elseif (!$content_only)
- {
- return $this->get_description(true);
- }
- else
- {
- return null;
- }
- }
-
- function get_category($key = 0)
- {
- $categories = $this->get_categories();
- if (isset($categories[$key]))
- {
- return $categories[$key];
- }
- else
- {
- return null;
- }
- }
-
- function get_categories()
- {
- $categories = array();
-
- foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'category') as $category)
- {
- $term = null;
- $scheme = null;
- $label = null;
- if (isset($category['attribs']['']['term']))
- {
- $term = $this->sanitize($category['attribs']['']['term'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($category['attribs']['']['scheme']))
- {
- $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($category['attribs']['']['label']))
- {
- $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $categories[] = new $this->feed->category_class($term, $scheme, $label);
- }
- foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'category') as $category)
- {
- // This is really the label, but keep this as the term also for BC.
- // Label will also work on retrieving because that falls back to term.
- $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- if (isset($category['attribs']['']['domain']))
- {
- $scheme = $this->sanitize($category['attribs']['']['domain'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $scheme = null;
- }
- $categories[] = new $this->feed->category_class($term, $scheme, null);
- }
- foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_11, 'subject') as $category)
- {
- $categories[] = new $this->feed->category_class($this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null);
- }
- foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_10, 'subject') as $category)
- {
- $categories[] = new $this->feed->category_class($this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null);
- }
-
- if (!empty($categories))
- {
- return SimplePie_Misc::array_unique($categories);
- }
- else
- {
- return null;
- }
- }
-
- function get_author($key = 0)
- {
- $authors = $this->get_authors();
- if (isset($authors[$key]))
- {
- return $authors[$key];
- }
- else
- {
- return null;
- }
- }
-
- function get_contributor($key = 0)
- {
- $contributors = $this->get_contributors();
- if (isset($contributors[$key]))
- {
- return $contributors[$key];
- }
- else
- {
- return null;
- }
- }
-
- function get_contributors()
- {
- $contributors = array();
- foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'contributor') as $contributor)
- {
- $name = null;
- $uri = null;
- $email = null;
- if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data']))
- {
- $name = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data']))
- {
- $uri = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]));
- }
- if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data']))
- {
- $email = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if ($name !== null || $email !== null || $uri !== null)
- {
- $contributors[] = new $this->feed->author_class($name, $uri, $email);
- }
- }
- foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'contributor') as $contributor)
- {
- $name = null;
- $url = null;
- $email = null;
- if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data']))
- {
- $name = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data']))
- {
- $url = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]));
- }
- if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data']))
- {
- $email = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if ($name !== null || $email !== null || $url !== null)
- {
- $contributors[] = new $this->feed->author_class($name, $url, $email);
- }
- }
-
- if (!empty($contributors))
- {
- return SimplePie_Misc::array_unique($contributors);
- }
- else
- {
- return null;
- }
- }
-
- function get_authors()
- {
- $authors = array();
- foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'author') as $author)
- {
- $name = null;
- $uri = null;
- $email = null;
- $avatar = null;
- $name_date = null;
- $uri_date = null;
- $avatar_date = null;
- if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data']))
- {
- $name = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data']))
- {
- $uri = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]));
- }
- if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data']))
- {
- $email = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($author['child']['http://purl.org/macgirvin/dfrn/1.0']['avatar'][0]['data']))
- {
- $avatar = $this->sanitize($author['child']['http://purl.org/macgirvin/dfrn/1.0']['avatar'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($author['child']['http://purl.org/macgirvin/dfrn/1.0']['avatar'][0]));
- }
- if (isset($author['child']['http://purl.org/macgirvin/dfrn/1.0']['name-updated'][0]['data']))
- {
- $name_date = $author['child']['http://purl.org/macgirvin/dfrn/1.0']['name-updated'][0]['data'];
- }
- if (isset($author['child']['http://purl.org/macgirvin/dfrn/1.0']['uri-updated'][0]['data']))
- {
- $uri_date = $author['child']['http://purl.org/macgirvin/dfrn/1.0']['uri-updated'][0]['data'];
- }
- if (isset($author['child']['http://purl.org/macgirvin/dfrn/1.0']['avatar-updated'][0]['data']))
- {
- $avatar_date = $author['child']['http://purl.org/macgirvin/dfrn/1.0']['avatar-updated'][0]['data'];
- }
-
- if ($name !== null || $email !== null || $uri !== null || $avatar !== null || $name_date !== null || $uri_date !== null || $avatar_date !== null )
- {
- $authors[] = new $this->feed->author_class($name, $uri, $email, $avatar, $name_date, $uri_date, $avatar_date);
- }
- }
- if ($author = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'author'))
- {
- $name = null;
- $url = null;
- $email = null;
- if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data']))
- {
- $name = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data']))
- {
- $url = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]));
- }
- if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data']))
- {
- $email = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if ($name !== null || $email !== null || $url !== null)
- {
- $authors[] = new $this->feed->author_class($name, $url, $email);
- }
- }
- if ($author = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'author'))
- {
- $authors[] = new $this->feed->author_class(null, null, $this->sanitize($author[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT));
- }
- foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_11, 'creator') as $author)
- {
- $authors[] = new $this->feed->author_class($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null);
- }
- foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_10, 'creator') as $author)
- {
- $authors[] = new $this->feed->author_class($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null);
- }
- foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'author') as $author)
- {
- $authors[] = new $this->feed->author_class($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null);
- }
-
- if (!empty($authors))
- {
- return SimplePie_Misc::array_unique($authors);
- }
- elseif (($source = $this->get_source()) && ($authors = $source->get_authors()))
- {
- return $authors;
- }
- elseif ($authors = $this->feed->get_authors())
- {
- return $authors;
- }
- else
- {
- return null;
- }
- }
-
- function get_copyright()
- {
- if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'rights'))
- {
- return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_10_construct_type($return[0]['attribs']), $this->get_base($return[0]));
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_11, 'rights'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_10, 'rights'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- return null;
- }
- }
-
- function get_date($date_format = 'j F Y, g:i a')
- {
- if (!isset($this->data['date']))
- {
- if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'published'))
- {
- $this->data['date']['raw'] = $return[0]['data'];
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'updated'))
- {
- $this->data['date']['raw'] = $return[0]['data'];
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'issued'))
- {
- $this->data['date']['raw'] = $return[0]['data'];
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'created'))
- {
- $this->data['date']['raw'] = $return[0]['data'];
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'modified'))
- {
- $this->data['date']['raw'] = $return[0]['data'];
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'pubDate'))
- {
- $this->data['date']['raw'] = $return[0]['data'];
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_11, 'date'))
- {
- $this->data['date']['raw'] = $return[0]['data'];
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_10, 'date'))
- {
- $this->data['date']['raw'] = $return[0]['data'];
- }
-
- if (!empty($this->data['date']['raw']))
- {
- $parser = SimplePie_Parse_Date::get();
- $this->data['date']['parsed'] = $parser->parse($this->data['date']['raw']);
- }
- else
- {
- $this->data['date'] = null;
- }
- }
- if ($this->data['date'])
- {
- $date_format = (string) $date_format;
- switch ($date_format)
- {
- case '':
- return $this->sanitize($this->data['date']['raw'], SIMPLEPIE_CONSTRUCT_TEXT);
-
- case 'U':
- return $this->data['date']['parsed'];
-
- default:
- return date($date_format, $this->data['date']['parsed']);
- }
- }
- else
- {
- return null;
- }
- }
-
- function get_local_date($date_format = '%c')
- {
- if (!$date_format)
- {
- return $this->sanitize($this->get_date(''), SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif (($date = $this->get_date('U')) !== null)
- {
- return strftime($date_format, $date);
- }
- else
- {
- return null;
- }
- }
-
- function get_permalink()
- {
- $link = $this->get_link();
- $enclosure = $this->get_enclosure(0);
- if ($link !== null)
- {
- return $link;
- }
- elseif ($enclosure !== null)
- {
- return $enclosure->get_link();
- }
- else
- {
- return null;
- }
- }
-
- function get_link($key = 0, $rel = 'alternate')
- {
- $links = $this->get_links($rel);
- if ($links[$key] !== null)
- {
- return $links[$key];
- }
- else
- {
- return null;
- }
- }
-
- function get_links($rel = 'alternate')
- {
- if (!isset($this->data['links']))
- {
- $this->data['links'] = array();
- foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'link') as $link)
- {
- if (isset($link['attribs']['']['href']))
- {
- $link_rel = (isset($link['attribs']['']['rel'])) ? $link['attribs']['']['rel'] : 'alternate';
- $this->data['links'][$link_rel][] = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link));
-
- }
- }
- foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'link') as $link)
- {
- if (isset($link['attribs']['']['href']))
- {
- $link_rel = (isset($link['attribs']['']['rel'])) ? $link['attribs']['']['rel'] : 'alternate';
- $this->data['links'][$link_rel][] = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link));
- }
- }
- if ($links = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'link'))
- {
- $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0]));
- }
- if ($links = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'link'))
- {
- $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0]));
- }
- if ($links = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'link'))
- {
- $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0]));
- }
- if ($links = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'guid'))
- {
- if (!isset($links[0]['attribs']['']['isPermaLink']) || strtolower(trim($links[0]['attribs']['']['isPermaLink'])) === 'true')
- {
- $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0]));
- }
- }
-
- $keys = array_keys($this->data['links']);
- foreach ($keys as $key)
- {
- if (SimplePie_Misc::is_isegment_nz_nc($key))
- {
- if (isset($this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key]))
- {
- $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key] = array_merge($this->data['links'][$key], $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key]);
- $this->data['links'][$key] =& $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key];
- }
- else
- {
- $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key] =& $this->data['links'][$key];
- }
- }
- elseif (substr($key, 0, 41) === SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY)
- {
- $this->data['links'][substr($key, 41)] =& $this->data['links'][$key];
- }
- $this->data['links'][$key] = array_unique($this->data['links'][$key]);
- }
- }
- if (isset($this->data['links'][$rel]))
- {
- return $this->data['links'][$rel];
- }
- else
- {
- return null;
- }
- }
-
- /**
- * @todo Add ability to prefer one type of content over another (in a media group).
- */
- function get_enclosure($key = 0, $prefer = null)
- {
- $enclosures = $this->get_enclosures();
- if (isset($enclosures[$key]))
- {
- return $enclosures[$key];
- }
- else
- {
- return null;
- }
- }
-
- /**
- * Grabs all available enclosures (podcasts, etc.)
- *
- * Supports the <enclosure> RSS tag, as well as Media RSS and iTunes RSS.
- *
- * At this point, we're pretty much assuming that all enclosures for an item are the same content. Anything else is too complicated to properly support.
- *
- * @todo Add support for end-user defined sorting of enclosures by type/handler (so we can prefer the faster-loading FLV over MP4).
- * @todo If an element exists at a level, but it's value is empty, we should fall back to the value from the parent (if it exists).
- */
- function get_enclosures()
- {
- if (!isset($this->data['enclosures']))
- {
- $this->data['enclosures'] = array();
-
- // Elements
- $captions_parent = null;
- $categories_parent = null;
- $copyrights_parent = null;
- $credits_parent = null;
- $description_parent = null;
- $duration_parent = null;
- $hashes_parent = null;
- $keywords_parent = null;
- $player_parent = null;
- $ratings_parent = null;
- $restrictions_parent = null;
- $thumbnails_parent = null;
- $title_parent = null;
-
- // Let's do the channel and item-level ones first, and just re-use them if we need to.
- $parent = $this->get_feed();
-
- // CAPTIONS
- if ($captions = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'text'))
- {
- foreach ($captions as $caption)
- {
- $caption_type = null;
- $caption_lang = null;
- $caption_startTime = null;
- $caption_endTime = null;
- $caption_text = null;
- if (isset($caption['attribs']['']['type']))
- {
- $caption_type = $this->sanitize($caption['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($caption['attribs']['']['lang']))
- {
- $caption_lang = $this->sanitize($caption['attribs']['']['lang'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($caption['attribs']['']['start']))
- {
- $caption_startTime = $this->sanitize($caption['attribs']['']['start'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($caption['attribs']['']['end']))
- {
- $caption_endTime = $this->sanitize($caption['attribs']['']['end'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($caption['data']))
- {
- $caption_text = $this->sanitize($caption['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $captions_parent[] = new $this->feed->caption_class($caption_type, $caption_lang, $caption_startTime, $caption_endTime, $caption_text);
- }
- }
- elseif ($captions = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'text'))
- {
- foreach ($captions as $caption)
- {
- $caption_type = null;
- $caption_lang = null;
- $caption_startTime = null;
- $caption_endTime = null;
- $caption_text = null;
- if (isset($caption['attribs']['']['type']))
- {
- $caption_type = $this->sanitize($caption['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($caption['attribs']['']['lang']))
- {
- $caption_lang = $this->sanitize($caption['attribs']['']['lang'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($caption['attribs']['']['start']))
- {
- $caption_startTime = $this->sanitize($caption['attribs']['']['start'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($caption['attribs']['']['end']))
- {
- $caption_endTime = $this->sanitize($caption['attribs']['']['end'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($caption['data']))
- {
- $caption_text = $this->sanitize($caption['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $captions_parent[] = new $this->feed->caption_class($caption_type, $caption_lang, $caption_startTime, $caption_endTime, $caption_text);
- }
- }
- if (is_array($captions_parent))
- {
- $captions_parent = array_values(SimplePie_Misc::array_unique($captions_parent));
- }
-
- // CATEGORIES
- foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'category') as $category)
- {
- $term = null;
- $scheme = null;
- $label = null;
- if (isset($category['data']))
- {
- $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($category['attribs']['']['scheme']))
- {
- $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $scheme = 'http://search.yahoo.com/mrss/category_schema';
- }
- if (isset($category['attribs']['']['label']))
- {
- $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $categories_parent[] = new $this->feed->category_class($term, $scheme, $label);
- }
- foreach ((array) $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'category') as $category)
- {
- $term = null;
- $scheme = null;
- $label = null;
- if (isset($category['data']))
- {
- $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($category['attribs']['']['scheme']))
- {
- $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $scheme = 'http://search.yahoo.com/mrss/category_schema';
- }
- if (isset($category['attribs']['']['label']))
- {
- $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $categories_parent[] = new $this->feed->category_class($term, $scheme, $label);
- }
- foreach ((array) $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'category') as $category)
- {
- $term = null;
- $scheme = 'http://www.itunes.com/dtds/podcast-1.0.dtd';
- $label = null;
- if (isset($category['attribs']['']['text']))
- {
- $label = $this->sanitize($category['attribs']['']['text'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $categories_parent[] = new $this->feed->category_class($term, $scheme, $label);
-
- if (isset($category['child'][SIMPLEPIE_NAMESPACE_ITUNES]['category']))
- {
- foreach ((array) $category['child'][SIMPLEPIE_NAMESPACE_ITUNES]['category'] as $subcategory)
- {
- if (isset($subcategory['attribs']['']['text']))
- {
- $label = $this->sanitize($subcategory['attribs']['']['text'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $categories_parent[] = new $this->feed->category_class($term, $scheme, $label);
- }
- }
- }
- if (is_array($categories_parent))
- {
- $categories_parent = array_values(SimplePie_Misc::array_unique($categories_parent));
- }
-
- // COPYRIGHT
- if ($copyright = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'copyright'))
- {
- $copyright_url = null;
- $copyright_label = null;
- if (isset($copyright[0]['attribs']['']['url']))
- {
- $copyright_url = $this->sanitize($copyright[0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($copyright[0]['data']))
- {
- $copyright_label = $this->sanitize($copyright[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $copyrights_parent = new $this->feed->copyright_class($copyright_url, $copyright_label);
- }
- elseif ($copyright = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'copyright'))
- {
- $copyright_url = null;
- $copyright_label = null;
- if (isset($copyright[0]['attribs']['']['url']))
- {
- $copyright_url = $this->sanitize($copyright[0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($copyright[0]['data']))
- {
- $copyright_label = $this->sanitize($copyright[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $copyrights_parent = new $this->feed->copyright_class($copyright_url, $copyright_label);
- }
-
- // CREDITS
- if ($credits = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'credit'))
- {
- foreach ($credits as $credit)
- {
- $credit_role = null;
- $credit_scheme = null;
- $credit_name = null;
- if (isset($credit['attribs']['']['role']))
- {
- $credit_role = $this->sanitize($credit['attribs']['']['role'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($credit['attribs']['']['scheme']))
- {
- $credit_scheme = $this->sanitize($credit['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $credit_scheme = 'urn:ebu';
- }
- if (isset($credit['data']))
- {
- $credit_name = $this->sanitize($credit['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $credits_parent[] = new $this->feed->credit_class($credit_role, $credit_scheme, $credit_name);
- }
- }
- elseif ($credits = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'credit'))
- {
- foreach ($credits as $credit)
- {
- $credit_role = null;
- $credit_scheme = null;
- $credit_name = null;
- if (isset($credit['attribs']['']['role']))
- {
- $credit_role = $this->sanitize($credit['attribs']['']['role'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($credit['attribs']['']['scheme']))
- {
- $credit_scheme = $this->sanitize($credit['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $credit_scheme = 'urn:ebu';
- }
- if (isset($credit['data']))
- {
- $credit_name = $this->sanitize($credit['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $credits_parent[] = new $this->feed->credit_class($credit_role, $credit_scheme, $credit_name);
- }
- }
- if (is_array($credits_parent))
- {
- $credits_parent = array_values(SimplePie_Misc::array_unique($credits_parent));
- }
-
- // DESCRIPTION
- if ($description_parent = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'description'))
- {
- if (isset($description_parent[0]['data']))
- {
- $description_parent = $this->sanitize($description_parent[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- }
- elseif ($description_parent = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'description'))
- {
- if (isset($description_parent[0]['data']))
- {
- $description_parent = $this->sanitize($description_parent[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- }
-
- // DURATION
- if ($duration_parent = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'duration'))
- {
- $seconds = null;
- $minutes = null;
- $hours = null;
- if (isset($duration_parent[0]['data']))
- {
- $temp = explode(':', $this->sanitize($duration_parent[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT));
- if (sizeof($temp) > 0)
- {
- (int) $seconds = array_pop($temp);
- }
- if (sizeof($temp) > 0)
- {
- (int) $minutes = array_pop($temp);
- $seconds += $minutes * 60;
- }
- if (sizeof($temp) > 0)
- {
- (int) $hours = array_pop($temp);
- $seconds += $hours * 3600;
- }
- unset($temp);
- $duration_parent = $seconds;
- }
- }
-
- // HASHES
- if ($hashes_iterator = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'hash'))
- {
- foreach ($hashes_iterator as $hash)
- {
- $value = null;
- $algo = null;
- if (isset($hash['data']))
- {
- $value = $this->sanitize($hash['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($hash['attribs']['']['algo']))
- {
- $algo = $this->sanitize($hash['attribs']['']['algo'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $algo = 'md5';
- }
- $hashes_parent[] = $algo.':'.$value;
- }
- }
- elseif ($hashes_iterator = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'hash'))
- {
- foreach ($hashes_iterator as $hash)
- {
- $value = null;
- $algo = null;
- if (isset($hash['data']))
- {
- $value = $this->sanitize($hash['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($hash['attribs']['']['algo']))
- {
- $algo = $this->sanitize($hash['attribs']['']['algo'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $algo = 'md5';
- }
- $hashes_parent[] = $algo.':'.$value;
- }
- }
- if (is_array($hashes_parent))
- {
- $hashes_parent = array_values(SimplePie_Misc::array_unique($hashes_parent));
- }
-
- // KEYWORDS
- if ($keywords = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'keywords'))
- {
- if (isset($keywords[0]['data']))
- {
- $temp = explode(',', $this->sanitize($keywords[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT));
- foreach ($temp as $word)
- {
- $keywords_parent[] = trim($word);
- }
- }
- unset($temp);
- }
- elseif ($keywords = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'keywords'))
- {
- if (isset($keywords[0]['data']))
- {
- $temp = explode(',', $this->sanitize($keywords[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT));
- foreach ($temp as $word)
- {
- $keywords_parent[] = trim($word);
- }
- }
- unset($temp);
- }
- elseif ($keywords = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'keywords'))
- {
- if (isset($keywords[0]['data']))
- {
- $temp = explode(',', $this->sanitize($keywords[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT));
- foreach ($temp as $word)
- {
- $keywords_parent[] = trim($word);
- }
- }
- unset($temp);
- }
- elseif ($keywords = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'keywords'))
- {
- if (isset($keywords[0]['data']))
- {
- $temp = explode(',', $this->sanitize($keywords[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT));
- foreach ($temp as $word)
- {
- $keywords_parent[] = trim($word);
- }
- }
- unset($temp);
- }
- if (is_array($keywords_parent))
- {
- $keywords_parent = array_values(SimplePie_Misc::array_unique($keywords_parent));
- }
-
- // PLAYER
- if ($player_parent = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'player'))
- {
- if (isset($player_parent[0]['attribs']['']['url']))
- {
- $player_parent = $this->sanitize($player_parent[0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
- }
- }
- elseif ($player_parent = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'player'))
- {
- if (isset($player_parent[0]['attribs']['']['url']))
- {
- $player_parent = $this->sanitize($player_parent[0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
- }
- }
-
- // RATINGS
- if ($ratings = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'rating'))
- {
- foreach ($ratings as $rating)
- {
- $rating_scheme = null;
- $rating_value = null;
- if (isset($rating['attribs']['']['scheme']))
- {
- $rating_scheme = $this->sanitize($rating['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $rating_scheme = 'urn:simple';
- }
- if (isset($rating['data']))
- {
- $rating_value = $this->sanitize($rating['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $ratings_parent[] = new $this->feed->rating_class($rating_scheme, $rating_value);
- }
- }
- elseif ($ratings = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'explicit'))
- {
- foreach ($ratings as $rating)
- {
- $rating_scheme = 'urn:itunes';
- $rating_value = null;
- if (isset($rating['data']))
- {
- $rating_value = $this->sanitize($rating['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $ratings_parent[] = new $this->feed->rating_class($rating_scheme, $rating_value);
- }
- }
- elseif ($ratings = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'rating'))
- {
- foreach ($ratings as $rating)
- {
- $rating_scheme = null;
- $rating_value = null;
- if (isset($rating['attribs']['']['scheme']))
- {
- $rating_scheme = $this->sanitize($rating['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $rating_scheme = 'urn:simple';
- }
- if (isset($rating['data']))
- {
- $rating_value = $this->sanitize($rating['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $ratings_parent[] = new $this->feed->rating_class($rating_scheme, $rating_value);
- }
- }
- elseif ($ratings = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'explicit'))
- {
- foreach ($ratings as $rating)
- {
- $rating_scheme = 'urn:itunes';
- $rating_value = null;
- if (isset($rating['data']))
- {
- $rating_value = $this->sanitize($rating['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $ratings_parent[] = new $this->feed->rating_class($rating_scheme, $rating_value);
- }
- }
- if (is_array($ratings_parent))
- {
- $ratings_parent = array_values(SimplePie_Misc::array_unique($ratings_parent));
- }
-
- // RESTRICTIONS
- if ($restrictions = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'restriction'))
- {
- foreach ($restrictions as $restriction)
- {
- $restriction_relationship = null;
- $restriction_type = null;
- $restriction_value = null;
- if (isset($restriction['attribs']['']['relationship']))
- {
- $restriction_relationship = $this->sanitize($restriction['attribs']['']['relationship'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($restriction['attribs']['']['type']))
- {
- $restriction_type = $this->sanitize($restriction['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($restriction['data']))
- {
- $restriction_value = $this->sanitize($restriction['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $restrictions_parent[] = new $this->feed->restriction_class($restriction_relationship, $restriction_type, $restriction_value);
- }
- }
- elseif ($restrictions = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'block'))
- {
- foreach ($restrictions as $restriction)
- {
- $restriction_relationship = 'allow';
- $restriction_type = null;
- $restriction_value = 'itunes';
- if (isset($restriction['data']) && strtolower($restriction['data']) === 'yes')
- {
- $restriction_relationship = 'deny';
- }
- $restrictions_parent[] = new $this->feed->restriction_class($restriction_relationship, $restriction_type, $restriction_value);
- }
- }
- elseif ($restrictions = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'restriction'))
- {
- foreach ($restrictions as $restriction)
- {
- $restriction_relationship = null;
- $restriction_type = null;
- $restriction_value = null;
- if (isset($restriction['attribs']['']['relationship']))
- {
- $restriction_relationship = $this->sanitize($restriction['attribs']['']['relationship'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($restriction['attribs']['']['type']))
- {
- $restriction_type = $this->sanitize($restriction['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($restriction['data']))
- {
- $restriction_value = $this->sanitize($restriction['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $restrictions_parent[] = new $this->feed->restriction_class($restriction_relationship, $restriction_type, $restriction_value);
- }
- }
- elseif ($restrictions = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'block'))
- {
- foreach ($restrictions as $restriction)
- {
- $restriction_relationship = 'allow';
- $restriction_type = null;
- $restriction_value = 'itunes';
- if (isset($restriction['data']) && strtolower($restriction['data']) === 'yes')
- {
- $restriction_relationship = 'deny';
- }
- $restrictions_parent[] = new $this->feed->restriction_class($restriction_relationship, $restriction_type, $restriction_value);
- }
- }
- if (is_array($restrictions_parent))
- {
- $restrictions_parent = array_values(SimplePie_Misc::array_unique($restrictions_parent));
- }
-
- // THUMBNAILS
- if ($thumbnails = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'thumbnail'))
- {
- foreach ($thumbnails as $thumbnail)
- {
- if (isset($thumbnail['attribs']['']['url']))
- {
- $thumbnails_parent[] = $this->sanitize($thumbnail['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
- }
- }
- }
- elseif ($thumbnails = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'thumbnail'))
- {
- foreach ($thumbnails as $thumbnail)
- {
- if (isset($thumbnail['attribs']['']['url']))
- {
- $thumbnails_parent[] = $this->sanitize($thumbnail['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
- }
- }
- }
-
- // TITLES
- if ($title_parent = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'title'))
- {
- if (isset($title_parent[0]['data']))
- {
- $title_parent = $this->sanitize($title_parent[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- }
- elseif ($title_parent = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'title'))
- {
- if (isset($title_parent[0]['data']))
- {
- $title_parent = $this->sanitize($title_parent[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- }
-
- // Clear the memory
- unset($parent);
-
- // Attributes
- $bitrate = null;
- $channels = null;
- $duration = null;
- $expression = null;
- $framerate = null;
- $height = null;
- $javascript = null;
- $lang = null;
- $length = null;
- $medium = null;
- $samplingrate = null;
- $type = null;
- $url = null;
- $width = null;
-
- // Elements
- $captions = null;
- $categories = null;
- $copyrights = null;
- $credits = null;
- $description = null;
- $hashes = null;
- $keywords = null;
- $player = null;
- $ratings = null;
- $restrictions = null;
- $thumbnails = null;
- $title = null;
-
- // If we have media:group tags, loop through them.
- foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'group') as $group)
- {
- if(isset($group['child']) && isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['content']))
- {
- // If we have media:content tags, loop through them.
- foreach ((array) $group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['content'] as $content)
- {
- if (isset($content['attribs']['']['url']))
- {
- // Attributes
- $bitrate = null;
- $channels = null;
- $duration = null;
- $expression = null;
- $framerate = null;
- $height = null;
- $javascript = null;
- $lang = null;
- $length = null;
- $medium = null;
- $samplingrate = null;
- $type = null;
- $url = null;
- $width = null;
-
- // Elements
- $captions = null;
- $categories = null;
- $copyrights = null;
- $credits = null;
- $description = null;
- $hashes = null;
- $keywords = null;
- $player = null;
- $ratings = null;
- $restrictions = null;
- $thumbnails = null;
- $title = null;
-
- // Start checking the attributes of media:content
- if (isset($content['attribs']['']['bitrate']))
- {
- $bitrate = $this->sanitize($content['attribs']['']['bitrate'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($content['attribs']['']['channels']))
- {
- $channels = $this->sanitize($content['attribs']['']['channels'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($content['attribs']['']['duration']))
- {
- $duration = $this->sanitize($content['attribs']['']['duration'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $duration = $duration_parent;
- }
- if (isset($content['attribs']['']['expression']))
- {
- $expression = $this->sanitize($content['attribs']['']['expression'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($content['attribs']['']['framerate']))
- {
- $framerate = $this->sanitize($content['attribs']['']['framerate'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($content['attribs']['']['height']))
- {
- $height = $this->sanitize($content['attribs']['']['height'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($content['attribs']['']['lang']))
- {
- $lang = $this->sanitize($content['attribs']['']['lang'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($content['attribs']['']['fileSize']))
- {
- $length = ceil($content['attribs']['']['fileSize']);
- }
- if (isset($content['attribs']['']['medium']))
- {
- $medium = $this->sanitize($content['attribs']['']['medium'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($content['attribs']['']['samplingrate']))
- {
- $samplingrate = $this->sanitize($content['attribs']['']['samplingrate'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($content['attribs']['']['type']))
- {
- $type = $this->sanitize($content['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($content['attribs']['']['width']))
- {
- $width = $this->sanitize($content['attribs']['']['width'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $url = $this->sanitize($content['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
-
- // Checking the other optional media: elements. Priority: media:content, media:group, item, channel
-
- // CAPTIONS
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['text']))
- {
- foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['text'] as $caption)
- {
- $caption_type = null;
- $caption_lang = null;
- $caption_startTime = null;
- $caption_endTime = null;
- $caption_text = null;
- if (isset($caption['attribs']['']['type']))
- {
- $caption_type = $this->sanitize($caption['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($caption['attribs']['']['lang']))
- {
- $caption_lang = $this->sanitize($caption['attribs']['']['lang'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($caption['attribs']['']['start']))
- {
- $caption_startTime = $this->sanitize($caption['attribs']['']['start'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($caption['attribs']['']['end']))
- {
- $caption_endTime = $this->sanitize($caption['attribs']['']['end'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($caption['data']))
- {
- $caption_text = $this->sanitize($caption['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $captions[] = new $this->feed->caption_class($caption_type, $caption_lang, $caption_startTime, $caption_endTime, $caption_text);
- }
- if (is_array($captions))
- {
- $captions = array_values(SimplePie_Misc::array_unique($captions));
- }
- }
- elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['text']))
- {
- foreach ($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['text'] as $caption)
- {
- $caption_type = null;
- $caption_lang = null;
- $caption_startTime = null;
- $caption_endTime = null;
- $caption_text = null;
- if (isset($caption['attribs']['']['type']))
- {
- $caption_type = $this->sanitize($caption['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($caption['attribs']['']['lang']))
- {
- $caption_lang = $this->sanitize($caption['attribs']['']['lang'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($caption['attribs']['']['start']))
- {
- $caption_startTime = $this->sanitize($caption['attribs']['']['start'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($caption['attribs']['']['end']))
- {
- $caption_endTime = $this->sanitize($caption['attribs']['']['end'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($caption['data']))
- {
- $caption_text = $this->sanitize($caption['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $captions[] = new $this->feed->caption_class($caption_type, $caption_lang, $caption_startTime, $caption_endTime, $caption_text);
- }
- if (is_array($captions))
- {
- $captions = array_values(SimplePie_Misc::array_unique($captions));
- }
- }
- else
- {
- $captions = $captions_parent;
- }
-
- // CATEGORIES
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['category']))
- {
- foreach ((array) $content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['category'] as $category)
- {
- $term = null;
- $scheme = null;
- $label = null;
- if (isset($category['data']))
- {
- $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($category['attribs']['']['scheme']))
- {
- $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $scheme = 'http://search.yahoo.com/mrss/category_schema';
- }
- if (isset($category['attribs']['']['label']))
- {
- $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $categories[] = new $this->feed->category_class($term, $scheme, $label);
- }
- }
- if (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['category']))
- {
- foreach ((array) $group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['category'] as $category)
- {
- $term = null;
- $scheme = null;
- $label = null;
- if (isset($category['data']))
- {
- $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($category['attribs']['']['scheme']))
- {
- $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $scheme = 'http://search.yahoo.com/mrss/category_schema';
- }
- if (isset($category['attribs']['']['label']))
- {
- $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $categories[] = new $this->feed->category_class($term, $scheme, $label);
- }
- }
- if (is_array($categories) && is_array($categories_parent))
- {
- $categories = array_values(SimplePie_Misc::array_unique(array_merge($categories, $categories_parent)));
- }
- elseif (is_array($categories))
- {
- $categories = array_values(SimplePie_Misc::array_unique($categories));
- }
- elseif (is_array($categories_parent))
- {
- $categories = array_values(SimplePie_Misc::array_unique($categories_parent));
- }
-
- // COPYRIGHTS
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright']))
- {
- $copyright_url = null;
- $copyright_label = null;
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['attribs']['']['url']))
- {
- $copyright_url = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['data']))
- {
- $copyright_label = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $copyrights = new $this->feed->copyright_class($copyright_url, $copyright_label);
- }
- elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright']))
- {
- $copyright_url = null;
- $copyright_label = null;
- if (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['attribs']['']['url']))
- {
- $copyright_url = $this->sanitize($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['data']))
- {
- $copyright_label = $this->sanitize($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $copyrights = new $this->feed->copyright_class($copyright_url, $copyright_label);
- }
- else
- {
- $copyrights = $copyrights_parent;
- }
-
- // CREDITS
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['credit']))
- {
- foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['credit'] as $credit)
- {
- $credit_role = null;
- $credit_scheme = null;
- $credit_name = null;
- if (isset($credit['attribs']['']['role']))
- {
- $credit_role = $this->sanitize($credit['attribs']['']['role'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($credit['attribs']['']['scheme']))
- {
- $credit_scheme = $this->sanitize($credit['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $credit_scheme = 'urn:ebu';
- }
- if (isset($credit['data']))
- {
- $credit_name = $this->sanitize($credit['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $credits[] = new $this->feed->credit_class($credit_role, $credit_scheme, $credit_name);
- }
- if (is_array($credits))
- {
- $credits = array_values(SimplePie_Misc::array_unique($credits));
- }
- }
- elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['credit']))
- {
- foreach ($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['credit'] as $credit)
- {
- $credit_role = null;
- $credit_scheme = null;
- $credit_name = null;
- if (isset($credit['attribs']['']['role']))
- {
- $credit_role = $this->sanitize($credit['attribs']['']['role'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($credit['attribs']['']['scheme']))
- {
- $credit_scheme = $this->sanitize($credit['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $credit_scheme = 'urn:ebu';
- }
- if (isset($credit['data']))
- {
- $credit_name = $this->sanitize($credit['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $credits[] = new $this->feed->credit_class($credit_role, $credit_scheme, $credit_name);
- }
- if (is_array($credits))
- {
- $credits = array_values(SimplePie_Misc::array_unique($credits));
- }
- }
- else
- {
- $credits = $credits_parent;
- }
-
- // DESCRIPTION
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['description']))
- {
- $description = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['description'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['description']))
- {
- $description = $this->sanitize($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['description'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $description = $description_parent;
- }
-
- // HASHES
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['hash']))
- {
- foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['hash'] as $hash)
- {
- $value = null;
- $algo = null;
- if (isset($hash['data']))
- {
- $value = $this->sanitize($hash['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($hash['attribs']['']['algo']))
- {
- $algo = $this->sanitize($hash['attribs']['']['algo'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $algo = 'md5';
- }
- $hashes[] = $algo.':'.$value;
- }
- if (is_array($hashes))
- {
- $hashes = array_values(SimplePie_Misc::array_unique($hashes));
- }
- }
- elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['hash']))
- {
- foreach ($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['hash'] as $hash)
- {
- $value = null;
- $algo = null;
- if (isset($hash['data']))
- {
- $value = $this->sanitize($hash['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($hash['attribs']['']['algo']))
- {
- $algo = $this->sanitize($hash['attribs']['']['algo'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $algo = 'md5';
- }
- $hashes[] = $algo.':'.$value;
- }
- if (is_array($hashes))
- {
- $hashes = array_values(SimplePie_Misc::array_unique($hashes));
- }
- }
- else
- {
- $hashes = $hashes_parent;
- }
-
- // KEYWORDS
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords']))
- {
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords'][0]['data']))
- {
- $temp = explode(',', $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT));
- foreach ($temp as $word)
- {
- $keywords[] = trim($word);
- }
- unset($temp);
- }
- if (is_array($keywords))
- {
- $keywords = array_values(SimplePie_Misc::array_unique($keywords));
- }
- }
- elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords']))
- {
- if (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords'][0]['data']))
- {
- $temp = explode(',', $this->sanitize($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT));
- foreach ($temp as $word)
- {
- $keywords[] = trim($word);
- }
- unset($temp);
- }
- if (is_array($keywords))
- {
- $keywords = array_values(SimplePie_Misc::array_unique($keywords));
- }
- }
- else
- {
- $keywords = $keywords_parent;
- }
-
- // PLAYER
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['player']))
- {
- $player = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['player'][0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
- }
- elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['player']))
- {
- $player = $this->sanitize($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['player'][0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
- }
- else
- {
- $player = $player_parent;
- }
-
- // RATINGS
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['rating']))
- {
- foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['rating'] as $rating)
- {
- $rating_scheme = null;
- $rating_value = null;
- if (isset($rating['attribs']['']['scheme']))
- {
- $rating_scheme = $this->sanitize($rating['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $rating_scheme = 'urn:simple';
- }
- if (isset($rating['data']))
- {
- $rating_value = $this->sanitize($rating['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $ratings[] = new $this->feed->rating_class($rating_scheme, $rating_value);
- }
- if (is_array($ratings))
- {
- $ratings = array_values(SimplePie_Misc::array_unique($ratings));
- }
- }
- elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['rating']))
- {
- foreach ($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['rating'] as $rating)
- {
- $rating_scheme = null;
- $rating_value = null;
- if (isset($rating['attribs']['']['scheme']))
- {
- $rating_scheme = $this->sanitize($rating['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $rating_scheme = 'urn:simple';
- }
- if (isset($rating['data']))
- {
- $rating_value = $this->sanitize($rating['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $ratings[] = new $this->feed->rating_class($rating_scheme, $rating_value);
- }
- if (is_array($ratings))
- {
- $ratings = array_values(SimplePie_Misc::array_unique($ratings));
- }
- }
- else
- {
- $ratings = $ratings_parent;
- }
-
- // RESTRICTIONS
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['restriction']))
- {
- foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['restriction'] as $restriction)
- {
- $restriction_relationship = null;
- $restriction_type = null;
- $restriction_value = null;
- if (isset($restriction['attribs']['']['relationship']))
- {
- $restriction_relationship = $this->sanitize($restriction['attribs']['']['relationship'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($restriction['attribs']['']['type']))
- {
- $restriction_type = $this->sanitize($restriction['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($restriction['data']))
- {
- $restriction_value = $this->sanitize($restriction['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $restrictions[] = new $this->feed->restriction_class($restriction_relationship, $restriction_type, $restriction_value);
- }
- if (is_array($restrictions))
- {
- $restrictions = array_values(SimplePie_Misc::array_unique($restrictions));
- }
- }
- elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['restriction']))
- {
- foreach ($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['restriction'] as $restriction)
- {
- $restriction_relationship = null;
- $restriction_type = null;
- $restriction_value = null;
- if (isset($restriction['attribs']['']['relationship']))
- {
- $restriction_relationship = $this->sanitize($restriction['attribs']['']['relationship'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($restriction['attribs']['']['type']))
- {
- $restriction_type = $this->sanitize($restriction['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($restriction['data']))
- {
- $restriction_value = $this->sanitize($restriction['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $restrictions[] = new $this->feed->restriction_class($restriction_relationship, $restriction_type, $restriction_value);
- }
- if (is_array($restrictions))
- {
- $restrictions = array_values(SimplePie_Misc::array_unique($restrictions));
- }
- }
- else
- {
- $restrictions = $restrictions_parent;
- }
-
- // THUMBNAILS
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['thumbnail']))
- {
- foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['thumbnail'] as $thumbnail)
- {
- $thumbnails[] = $this->sanitize($thumbnail['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
- }
- if (is_array($thumbnails))
- {
- $thumbnails = array_values(SimplePie_Misc::array_unique($thumbnails));
- }
- }
- elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['thumbnail']))
- {
- foreach ($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['thumbnail'] as $thumbnail)
- {
- $thumbnails[] = $this->sanitize($thumbnail['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
- }
- if (is_array($thumbnails))
- {
- $thumbnails = array_values(SimplePie_Misc::array_unique($thumbnails));
- }
- }
- else
- {
- $thumbnails = $thumbnails_parent;
- }
-
- // TITLES
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['title']))
- {
- $title = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['title'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['title']))
- {
- $title = $this->sanitize($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['title'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $title = $title_parent;
- }
-
- $this->data['enclosures'][] = new $this->feed->enclosure_class($url, $type, $length, $this->feed->javascript, $bitrate, $captions, $categories, $channels, $copyrights, $credits, $description, $duration, $expression, $framerate, $hashes, $height, $keywords, $lang, $medium, $player, $ratings, $restrictions, $samplingrate, $thumbnails, $title, $width);
- }
- }
- }
- }
-
- // If we have standalone media:content tags, loop through them.
- if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['content']))
- {
- foreach ((array) $this->data['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['content'] as $content)
- {
- if (isset($content['attribs']['']['url']))
- {
- // Attributes
- $bitrate = null;
- $channels = null;
- $duration = null;
- $expression = null;
- $framerate = null;
- $height = null;
- $javascript = null;
- $lang = null;
- $length = null;
- $medium = null;
- $samplingrate = null;
- $type = null;
- $url = null;
- $width = null;
-
- // Elements
- $captions = null;
- $categories = null;
- $copyrights = null;
- $credits = null;
- $description = null;
- $hashes = null;
- $keywords = null;
- $player = null;
- $ratings = null;
- $restrictions = null;
- $thumbnails = null;
- $title = null;
-
- // Start checking the attributes of media:content
- if (isset($content['attribs']['']['bitrate']))
- {
- $bitrate = $this->sanitize($content['attribs']['']['bitrate'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($content['attribs']['']['channels']))
- {
- $channels = $this->sanitize($content['attribs']['']['channels'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($content['attribs']['']['duration']))
- {
- $duration = $this->sanitize($content['attribs']['']['duration'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $duration = $duration_parent;
- }
- if (isset($content['attribs']['']['expression']))
- {
- $expression = $this->sanitize($content['attribs']['']['expression'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($content['attribs']['']['framerate']))
- {
- $framerate = $this->sanitize($content['attribs']['']['framerate'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($content['attribs']['']['height']))
- {
- $height = $this->sanitize($content['attribs']['']['height'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($content['attribs']['']['lang']))
- {
- $lang = $this->sanitize($content['attribs']['']['lang'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($content['attribs']['']['fileSize']))
- {
- $length = ceil($content['attribs']['']['fileSize']);
- }
- if (isset($content['attribs']['']['medium']))
- {
- $medium = $this->sanitize($content['attribs']['']['medium'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($content['attribs']['']['samplingrate']))
- {
- $samplingrate = $this->sanitize($content['attribs']['']['samplingrate'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($content['attribs']['']['type']))
- {
- $type = $this->sanitize($content['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($content['attribs']['']['width']))
- {
- $width = $this->sanitize($content['attribs']['']['width'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $url = $this->sanitize($content['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
-
- // Checking the other optional media: elements. Priority: media:content, media:group, item, channel
-
- // CAPTIONS
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['text']))
- {
- foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['text'] as $caption)
- {
- $caption_type = null;
- $caption_lang = null;
- $caption_startTime = null;
- $caption_endTime = null;
- $caption_text = null;
- if (isset($caption['attribs']['']['type']))
- {
- $caption_type = $this->sanitize($caption['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($caption['attribs']['']['lang']))
- {
- $caption_lang = $this->sanitize($caption['attribs']['']['lang'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($caption['attribs']['']['start']))
- {
- $caption_startTime = $this->sanitize($caption['attribs']['']['start'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($caption['attribs']['']['end']))
- {
- $caption_endTime = $this->sanitize($caption['attribs']['']['end'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($caption['data']))
- {
- $caption_text = $this->sanitize($caption['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $captions[] = new $this->feed->caption_class($caption_type, $caption_lang, $caption_startTime, $caption_endTime, $caption_text);
- }
- if (is_array($captions))
- {
- $captions = array_values(SimplePie_Misc::array_unique($captions));
- }
- }
- else
- {
- $captions = $captions_parent;
- }
-
- // CATEGORIES
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['category']))
- {
- foreach ((array) $content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['category'] as $category)
- {
- $term = null;
- $scheme = null;
- $label = null;
- if (isset($category['data']))
- {
- $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($category['attribs']['']['scheme']))
- {
- $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $scheme = 'http://search.yahoo.com/mrss/category_schema';
- }
- if (isset($category['attribs']['']['label']))
- {
- $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $categories[] = new $this->feed->category_class($term, $scheme, $label);
- }
- }
- if (is_array($categories) && is_array($categories_parent))
- {
- $categories = array_values(SimplePie_Misc::array_unique(array_merge($categories, $categories_parent)));
- }
- elseif (is_array($categories))
- {
- $categories = array_values(SimplePie_Misc::array_unique($categories));
- }
- elseif (is_array($categories_parent))
- {
- $categories = array_values(SimplePie_Misc::array_unique($categories_parent));
- }
- else
- {
- $categories = null;
- }
-
- // COPYRIGHTS
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright']))
- {
- $copyright_url = null;
- $copyright_label = null;
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['attribs']['']['url']))
- {
- $copyright_url = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['data']))
- {
- $copyright_label = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $copyrights = new $this->feed->copyright_class($copyright_url, $copyright_label);
- }
- else
- {
- $copyrights = $copyrights_parent;
- }
-
- // CREDITS
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['credit']))
- {
- foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['credit'] as $credit)
- {
- $credit_role = null;
- $credit_scheme = null;
- $credit_name = null;
- if (isset($credit['attribs']['']['role']))
- {
- $credit_role = $this->sanitize($credit['attribs']['']['role'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($credit['attribs']['']['scheme']))
- {
- $credit_scheme = $this->sanitize($credit['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $credit_scheme = 'urn:ebu';
- }
- if (isset($credit['data']))
- {
- $credit_name = $this->sanitize($credit['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $credits[] = new $this->feed->credit_class($credit_role, $credit_scheme, $credit_name);
- }
- if (is_array($credits))
- {
- $credits = array_values(SimplePie_Misc::array_unique($credits));
- }
- }
- else
- {
- $credits = $credits_parent;
- }
-
- // DESCRIPTION
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['description']))
- {
- $description = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['description'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $description = $description_parent;
- }
-
- // HASHES
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['hash']))
- {
- foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['hash'] as $hash)
- {
- $value = null;
- $algo = null;
- if (isset($hash['data']))
- {
- $value = $this->sanitize($hash['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($hash['attribs']['']['algo']))
- {
- $algo = $this->sanitize($hash['attribs']['']['algo'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $algo = 'md5';
- }
- $hashes[] = $algo.':'.$value;
- }
- if (is_array($hashes))
- {
- $hashes = array_values(SimplePie_Misc::array_unique($hashes));
- }
- }
- else
- {
- $hashes = $hashes_parent;
- }
-
- // KEYWORDS
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords']))
- {
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords'][0]['data']))
- {
- $temp = explode(',', $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT));
- foreach ($temp as $word)
- {
- $keywords[] = trim($word);
- }
- unset($temp);
- }
- if (is_array($keywords))
- {
- $keywords = array_values(SimplePie_Misc::array_unique($keywords));
- }
- }
- else
- {
- $keywords = $keywords_parent;
- }
-
- // PLAYER
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['player']))
- {
- $player = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['player'][0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
- }
- else
- {
- $player = $player_parent;
- }
-
- // RATINGS
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['rating']))
- {
- foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['rating'] as $rating)
- {
- $rating_scheme = null;
- $rating_value = null;
- if (isset($rating['attribs']['']['scheme']))
- {
- $rating_scheme = $this->sanitize($rating['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $rating_scheme = 'urn:simple';
- }
- if (isset($rating['data']))
- {
- $rating_value = $this->sanitize($rating['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $ratings[] = new $this->feed->rating_class($rating_scheme, $rating_value);
- }
- if (is_array($ratings))
- {
- $ratings = array_values(SimplePie_Misc::array_unique($ratings));
- }
- }
- else
- {
- $ratings = $ratings_parent;
- }
-
- // RESTRICTIONS
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['restriction']))
- {
- foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['restriction'] as $restriction)
- {
- $restriction_relationship = null;
- $restriction_type = null;
- $restriction_value = null;
- if (isset($restriction['attribs']['']['relationship']))
- {
- $restriction_relationship = $this->sanitize($restriction['attribs']['']['relationship'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($restriction['attribs']['']['type']))
- {
- $restriction_type = $this->sanitize($restriction['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($restriction['data']))
- {
- $restriction_value = $this->sanitize($restriction['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $restrictions[] = new $this->feed->restriction_class($restriction_relationship, $restriction_type, $restriction_value);
- }
- if (is_array($restrictions))
- {
- $restrictions = array_values(SimplePie_Misc::array_unique($restrictions));
- }
- }
- else
- {
- $restrictions = $restrictions_parent;
- }
-
- // THUMBNAILS
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['thumbnail']))
- {
- foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['thumbnail'] as $thumbnail)
- {
- $thumbnails[] = $this->sanitize($thumbnail['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
- }
- if (is_array($thumbnails))
- {
- $thumbnails = array_values(SimplePie_Misc::array_unique($thumbnails));
- }
- }
- else
- {
- $thumbnails = $thumbnails_parent;
- }
-
- // TITLES
- if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['title']))
- {
- $title = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['title'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $title = $title_parent;
- }
-
- $this->data['enclosures'][] = new $this->feed->enclosure_class($url, $type, $length, $this->feed->javascript, $bitrate, $captions, $categories, $channels, $copyrights, $credits, $description, $duration, $expression, $framerate, $hashes, $height, $keywords, $lang, $medium, $player, $ratings, $restrictions, $samplingrate, $thumbnails, $title, $width);
- }
- }
- }
-
- foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'link') as $link)
- {
- if (isset($link['attribs']['']['href']) && !empty($link['attribs']['']['rel']) && $link['attribs']['']['rel'] === 'enclosure')
- {
- // Attributes
- $bitrate = null;
- $channels = null;
- $duration = null;
- $expression = null;
- $framerate = null;
- $height = null;
- $javascript = null;
- $lang = null;
- $length = null;
- $medium = null;
- $samplingrate = null;
- $type = null;
- $url = null;
- $width = null;
- $title = $title_parent;
-
- $url = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link));
- if (isset($link['attribs']['']['type']))
- {
- $type = $this->sanitize($link['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($link['attribs']['']['length']))
- {
- $length = ceil($link['attribs']['']['length']);
- }
- if (isset($link['attribs']['']['title']))
- {
- $title = $this->sanitize($link['attribs']['']['title'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
-
- // Since we don't have group or content for these, we'll just pass the '*_parent' variables directly to the constructor
- $this->data['enclosures'][] = new $this->feed->enclosure_class($url, $type, $length, $this->feed->javascript, $bitrate, $captions_parent, $categories_parent, $channels, $copyrights_parent, $credits_parent, $description_parent, $duration_parent, $expression, $framerate, $hashes_parent, $height, $keywords_parent, $lang, $medium, $player_parent, $ratings_parent, $restrictions_parent, $samplingrate, $thumbnails_parent, $title, $width);
- }
- }
-
- foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'link') as $link)
- {
- if (isset($link['attribs']['']['href']) && !empty($link['attribs']['']['rel']) && $link['attribs']['']['rel'] === 'enclosure')
- {
- // Attributes
- $bitrate = null;
- $channels = null;
- $duration = null;
- $expression = null;
- $framerate = null;
- $height = null;
- $javascript = null;
- $lang = null;
- $length = null;
- $medium = null;
- $samplingrate = null;
- $type = null;
- $url = null;
- $width = null;
-
- $url = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link));
- if (isset($link['attribs']['']['type']))
- {
- $type = $this->sanitize($link['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($link['attribs']['']['length']))
- {
- $length = ceil($link['attribs']['']['length']);
- }
-
- // Since we don't have group or content for these, we'll just pass the '*_parent' variables directly to the constructor
- $this->data['enclosures'][] = new $this->feed->enclosure_class($url, $type, $length, $this->feed->javascript, $bitrate, $captions_parent, $categories_parent, $channels, $copyrights_parent, $credits_parent, $description_parent, $duration_parent, $expression, $framerate, $hashes_parent, $height, $keywords_parent, $lang, $medium, $player_parent, $ratings_parent, $restrictions_parent, $samplingrate, $thumbnails_parent, $title_parent, $width);
- }
- }
-
- if ($enclosure = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'enclosure'))
- {
- if (isset($enclosure[0]['attribs']['']['url']))
- {
- // Attributes
- $bitrate = null;
- $channels = null;
- $duration = null;
- $expression = null;
- $framerate = null;
- $height = null;
- $javascript = null;
- $lang = null;
- $length = null;
- $medium = null;
- $samplingrate = null;
- $type = null;
- $url = null;
- $width = null;
-
- $url = $this->sanitize($enclosure[0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($enclosure[0]));
- if (isset($enclosure[0]['attribs']['']['type']))
- {
- $type = $this->sanitize($enclosure[0]['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($enclosure[0]['attribs']['']['length']))
- {
- $length = ceil($enclosure[0]['attribs']['']['length']);
- }
-
- // Since we don't have group or content for these, we'll just pass the '*_parent' variables directly to the constructor
- $this->data['enclosures'][] = new $this->feed->enclosure_class($url, $type, $length, $this->feed->javascript, $bitrate, $captions_parent, $categories_parent, $channels, $copyrights_parent, $credits_parent, $description_parent, $duration_parent, $expression, $framerate, $hashes_parent, $height, $keywords_parent, $lang, $medium, $player_parent, $ratings_parent, $restrictions_parent, $samplingrate, $thumbnails_parent, $title_parent, $width);
- }
- }
-
- if (sizeof($this->data['enclosures']) === 0 && ($url || $type || $length || $bitrate || $captions_parent || $categories_parent || $channels || $copyrights_parent || $credits_parent || $description_parent || $duration_parent || $expression || $framerate || $hashes_parent || $height || $keywords_parent || $lang || $medium || $player_parent || $ratings_parent || $restrictions_parent || $samplingrate || $thumbnails_parent || $title_parent || $width))
- {
- // Since we don't have group or content for these, we'll just pass the '*_parent' variables directly to the constructor
- $this->data['enclosures'][] = new $this->feed->enclosure_class($url, $type, $length, $this->feed->javascript, $bitrate, $captions_parent, $categories_parent, $channels, $copyrights_parent, $credits_parent, $description_parent, $duration_parent, $expression, $framerate, $hashes_parent, $height, $keywords_parent, $lang, $medium, $player_parent, $ratings_parent, $restrictions_parent, $samplingrate, $thumbnails_parent, $title_parent, $width);
- }
-
- $this->data['enclosures'] = array_values(SimplePie_Misc::array_unique($this->data['enclosures']));
- }
- if (!empty($this->data['enclosures']))
- {
- return $this->data['enclosures'];
- }
- else
- {
- return null;
- }
- }
-
- function get_latitude()
- {
- if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'lat'))
- {
- return (float) $return[0]['data'];
- }
- elseif (($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_GEORSS, 'point')) && preg_match('/^((?:-)?[0-9]+(?:\.[0-9]+)) ((?:-)?[0-9]+(?:\.[0-9]+))$/', trim($return[0]['data']), $match))
- {
- return (float) $match[1];
- }
- else
- {
- return null;
- }
- }
-
- function get_longitude()
- {
- if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'long'))
- {
- return (float) $return[0]['data'];
- }
- elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'lon'))
- {
- return (float) $return[0]['data'];
- }
- elseif (($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_GEORSS, 'point')) && preg_match('/^((?:-)?[0-9]+(?:\.[0-9]+)) ((?:-)?[0-9]+(?:\.[0-9]+))$/', trim($return[0]['data']), $match))
- {
- return (float) $match[2];
- }
- else
- {
- return null;
- }
- }
-
- function get_source()
- {
- if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'source'))
- {
- return new $this->feed->source_class($this, $return[0]);
- }
- else
- {
- return null;
- }
- }
-
- /**
- * Creates the add_to_* methods' return data
- *
- * @access private
- * @param string $item_url String to prefix to the item permalink
- * @param string $title_url String to prefix to the item title
- * (and suffix to the item permalink)
- * @return mixed URL if feed exists, false otherwise
- */
- function add_to_service($item_url, $title_url = null, $summary_url = null)
- {
- if ($this->get_permalink() !== null)
- {
- $return = $item_url . rawurlencode($this->get_permalink());
- if ($title_url !== null && $this->get_title() !== null)
- {
- $return .= $title_url . rawurlencode($this->get_title());
- }
- if ($summary_url !== null && $this->get_description() !== null)
- {
- $return .= $summary_url . rawurlencode($this->get_description());
- }
- return $this->sanitize($return, SIMPLEPIE_CONSTRUCT_IRI);
- }
- else
- {
- return null;
- }
- }
-
- function add_to_blinklist()
- {
- return $this->add_to_service('http://www.blinklist.com/index.php?Action=Blink/addblink.php&Description=&Url=', '&Title=');
- }
-
- function add_to_blogmarks()
- {
- return $this->add_to_service('http://blogmarks.net/my/new.php?mini=1&simple=1&url=', '&title=');
- }
-
- function add_to_delicious()
- {
- return $this->add_to_service('http://del.icio.us/post/?v=4&url=', '&title=');
- }
-
- function add_to_digg()
- {
- return $this->add_to_service('http://digg.com/submit?url=', '&title=', '&bodytext=');
- }
-
- function add_to_furl()
- {
- return $this->add_to_service('http://www.furl.net/storeIt.jsp?u=', '&t=');
- }
-
- function add_to_magnolia()
- {
- return $this->add_to_service('http://ma.gnolia.com/bookmarklet/add?url=', '&title=');
- }
-
- function add_to_myweb20()
- {
- return $this->add_to_service('http://myweb2.search.yahoo.com/myresults/bookmarklet?u=', '&t=');
- }
-
- function add_to_newsvine()
- {
- return $this->add_to_service('http://www.newsvine.com/_wine/save?u=', '&h=');
- }
-
- function add_to_reddit()
- {
- return $this->add_to_service('http://reddit.com/submit?url=', '&title=');
- }
-
- function add_to_segnalo()
- {
- return $this->add_to_service('http://segnalo.com/post.html.php?url=', '&title=');
- }
-
- function add_to_simpy()
- {
- return $this->add_to_service('http://www.simpy.com/simpy/LinkAdd.do?href=', '&title=');
- }
-
- function add_to_spurl()
- {
- return $this->add_to_service('http://www.spurl.net/spurl.php?v=3&url=', '&title=');
- }
-
- function add_to_wists()
- {
- return $this->add_to_service('http://wists.com/r.php?c=&r=', '&title=');
- }
-
- function search_technorati()
- {
- return $this->add_to_service('http://www.technorati.com/search/');
- }
-}
-
-class SimplePie_Source
-{
- var $item;
- var $data = array();
-
- function SimplePie_Source($item, $data)
- {
- $this->item = $item;
- $this->data = $data;
- }
-
- function __toString()
- {
- return md5(serialize($this->data));
- }
-
- function get_source_tags($namespace, $tag)
- {
- if (isset($this->data['child'][$namespace][$tag]))
- {
- return $this->data['child'][$namespace][$tag];
- }
- else
- {
- return null;
- }
- }
-
- function get_base($element = array())
- {
- return $this->item->get_base($element);
- }
-
- function sanitize($data, $type, $base = '')
- {
- return $this->item->sanitize($data, $type, $base);
- }
-
- function get_item()
- {
- return $this->item;
- }
-
- function get_title()
- {
- if ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'title'))
- {
- return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_10_construct_type($return[0]['attribs']), $this->get_base($return[0]));
- }
- elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'title'))
- {
- return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_03_construct_type($return[0]['attribs']), $this->get_base($return[0]));
- }
- elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'title'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'title'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'title'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_11, 'title'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_10, 'title'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- return null;
- }
- }
-
- function get_category($key = 0)
- {
- $categories = $this->get_categories();
- if (isset($categories[$key]))
- {
- return $categories[$key];
- }
- else
- {
- return null;
- }
- }
-
- function get_categories()
- {
- $categories = array();
-
- foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'category') as $category)
- {
- $term = null;
- $scheme = null;
- $label = null;
- if (isset($category['attribs']['']['term']))
- {
- $term = $this->sanitize($category['attribs']['']['term'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($category['attribs']['']['scheme']))
- {
- $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($category['attribs']['']['label']))
- {
- $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- $categories[] = new $this->item->feed->category_class($term, $scheme, $label);
- }
- foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'category') as $category)
- {
- // This is really the label, but keep this as the term also for BC.
- // Label will also work on retrieving because that falls back to term.
- $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- if (isset($category['attribs']['']['domain']))
- {
- $scheme = $this->sanitize($category['attribs']['']['domain'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- $scheme = null;
- }
- $categories[] = new $this->item->feed->category_class($term, $scheme, null);
- }
- foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_11, 'subject') as $category)
- {
- $categories[] = new $this->item->feed->category_class($this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null);
- }
- foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_10, 'subject') as $category)
- {
- $categories[] = new $this->item->feed->category_class($this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null);
- }
-
- if (!empty($categories))
- {
- return SimplePie_Misc::array_unique($categories);
- }
- else
- {
- return null;
- }
- }
-
- function get_author($key = 0)
- {
- $authors = $this->get_authors();
- if (isset($authors[$key]))
- {
- return $authors[$key];
- }
- else
- {
- return null;
- }
- }
-
- function get_authors()
- {
- $authors = array();
- foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'author') as $author)
- {
- $name = null;
- $uri = null;
- $email = null;
- $avatar = null;
- $name_date = null;
- $uri_date = null;
- $avatar_date = null;
-
- if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data']))
- {
- $name = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data']))
- {
- $uri = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]));
- }
- if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data']))
- {
- $email = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($author['child']['http://purl.org/macgirvin/dfrn/1.0']['avatar'][0]['data']))
- {
- $avatar = $this->sanitize($author['child']['http://purl.org/macgirvin/dfrn/1.0']['avatar'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($author['child']['http://purl.org/macgirvin/dfrn/1.0']['avatar'][0]));
- }
- if (isset($author['child']['http://purl.org/macgirvin/dfrn/1.0']['name-updated'][0]['data']))
- {
- $name_date = $author['child']['http://purl.org/macgirvin/dfrn/1.0']['name-updated'][0]['data'];
- }
- if (isset($author['child']['http://purl.org/macgirvin/dfrn/1.0']['uri-updated'][0]['data']))
- {
- $uri_date = $author['child']['http://purl.org/macgirvin/dfrn/1.0']['uri-updated'][0]['data'];
- }
- if (isset($author['child']['http://purl.org/macgirvin/dfrn/1.0']['avatar-updated'][0]['data']))
- {
- $avatar_date = $author['child']['http://purl.org/macgirvin/dfrn/1.0']['avatar-updated'][0]['data'];
- }
-
- if ($name !== null || $email !== null || $uri !== null || $avatar !== null || $name_date !== null || $uri_date !== null || $avatar_date !== null )
- {
- $authors[] = new $this->item->feed->author_class($name, $uri, $email, $avatar, $name_date, $uri_date, $avatar_date);
- }
- }
- if ($author = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'author'))
- {
- $name = null;
- $url = null;
- $email = null;
- if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data']))
- {
- $name = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data']))
- {
- $url = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]));
- }
- if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data']))
- {
- $email = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if ($name !== null || $email !== null || $url !== null)
- {
- $authors[] = new $this->item->feed->author_class($name, $url, $email);
- }
- }
- foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_11, 'creator') as $author)
- {
- $authors[] = new $this->item->feed->author_class($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null);
- }
- foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_10, 'creator') as $author)
- {
- $authors[] = new $this->item->feed->author_class($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null);
- }
- foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'author') as $author)
- {
- $authors[] = new $this->item->feed->author_class($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null);
- }
-
- if (!empty($authors))
- {
- return SimplePie_Misc::array_unique($authors);
- }
- else
- {
- return null;
- }
- }
-
- function get_contributor($key = 0)
- {
- $contributors = $this->get_contributors();
- if (isset($contributors[$key]))
- {
- return $contributors[$key];
- }
- else
- {
- return null;
- }
- }
-
- function get_contributors()
- {
- $contributors = array();
- foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'contributor') as $contributor)
- {
- $name = null;
- $uri = null;
- $email = null;
- if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data']))
- {
- $name = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data']))
- {
- $uri = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]));
- }
- if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data']))
- {
- $email = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if ($name !== null || $email !== null || $uri !== null)
- {
- $contributors[] = new $this->item->feed->author_class($name, $uri, $email);
- }
- }
- foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'contributor') as $contributor)
- {
- $name = null;
- $url = null;
- $email = null;
- if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data']))
- {
- $name = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data']))
- {
- $url = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]));
- }
- if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data']))
- {
- $email = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- if ($name !== null || $email !== null || $url !== null)
- {
- $contributors[] = new $this->item->feed->author_class($name, $url, $email);
- }
- }
-
- if (!empty($contributors))
- {
- return SimplePie_Misc::array_unique($contributors);
- }
- else
- {
- return null;
- }
- }
-
- function get_link($key = 0, $rel = 'alternate')
- {
- $links = $this->get_links($rel);
- if (isset($links[$key]))
- {
- return $links[$key];
- }
- else
- {
- return null;
- }
- }
-
- /**
- * Added for parity between the parent-level and the item/entry-level.
- */
- function get_permalink()
- {
- return $this->get_link(0);
- }
-
- function get_links($rel = 'alternate')
- {
- if (!isset($this->data['links']))
- {
- $this->data['links'] = array();
- if ($links = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'link'))
- {
- foreach ($links as $link)
- {
- if (isset($link['attribs']['']['href']))
- {
- $link_rel = (isset($link['attribs']['']['rel'])) ? $link['attribs']['']['rel'] : 'alternate';
- $this->data['links'][$link_rel][] = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link));
- }
- }
- }
- if ($links = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'link'))
- {
- foreach ($links as $link)
- {
- if (isset($link['attribs']['']['href']))
- {
- $link_rel = (isset($link['attribs']['']['rel'])) ? $link['attribs']['']['rel'] : 'alternate';
- $this->data['links'][$link_rel][] = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link));
-
- }
- }
- }
- if ($links = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'link'))
- {
- $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0]));
- }
- if ($links = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'link'))
- {
- $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0]));
- }
- if ($links = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'link'))
- {
- $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0]));
- }
-
- $keys = array_keys($this->data['links']);
- foreach ($keys as $key)
- {
- if (SimplePie_Misc::is_isegment_nz_nc($key))
- {
- if (isset($this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key]))
- {
- $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key] = array_merge($this->data['links'][$key], $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key]);
- $this->data['links'][$key] =& $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key];
- }
- else
- {
- $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key] =& $this->data['links'][$key];
- }
- }
- elseif (substr($key, 0, 41) === SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY)
- {
- $this->data['links'][substr($key, 41)] =& $this->data['links'][$key];
- }
- $this->data['links'][$key] = array_unique($this->data['links'][$key]);
- }
- }
-
- if (isset($this->data['links'][$rel]))
- {
- return $this->data['links'][$rel];
- }
- else
- {
- return null;
- }
- }
-
- function get_description()
- {
- if ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'subtitle'))
- {
- return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_10_construct_type($return[0]['attribs']), $this->get_base($return[0]));
- }
- elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'tagline'))
- {
- return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_03_construct_type($return[0]['attribs']), $this->get_base($return[0]));
- }
- elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'description'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'description'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'description'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_11, 'description'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_10, 'description'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'summary'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'subtitle'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($return[0]));
- }
- else
- {
- return null;
- }
- }
-
- function get_copyright()
- {
- if ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'rights'))
- {
- return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_10_construct_type($return[0]['attribs']), $this->get_base($return[0]));
- }
- elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'copyright'))
- {
- return $this->sanitize($return[0]['data'], SimplePie_Misc::atom_03_construct_type($return[0]['attribs']), $this->get_base($return[0]));
- }
- elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'copyright'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_11, 'rights'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_10, 'rights'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- return null;
- }
- }
-
- function get_language()
- {
- if ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'language'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_11, 'language'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_10, 'language'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- elseif (isset($this->data['xml_lang']))
- {
- return $this->sanitize($this->data['xml_lang'], SIMPLEPIE_CONSTRUCT_TEXT);
- }
- else
- {
- return null;
- }
- }
-
- function get_latitude()
- {
- if ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'lat'))
- {
- return (float) $return[0]['data'];
- }
- elseif (($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_GEORSS, 'point')) && preg_match('/^((?:-)?[0-9]+(?:\.[0-9]+)) ((?:-)?[0-9]+(?:\.[0-9]+))$/', trim($return[0]['data']), $match))
- {
- return (float) $match[1];
- }
- else
- {
- return null;
- }
- }
-
- function get_longitude()
- {
- if ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'long'))
- {
- return (float) $return[0]['data'];
- }
- elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'lon'))
- {
- return (float) $return[0]['data'];
- }
- elseif (($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_GEORSS, 'point')) && preg_match('/^((?:-)?[0-9]+(?:\.[0-9]+)) ((?:-)?[0-9]+(?:\.[0-9]+))$/', trim($return[0]['data']), $match))
- {
- return (float) $match[2];
- }
- else
- {
- return null;
- }
- }
-
- function get_image_url()
- {
- if ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'image'))
- {
- return $this->sanitize($return[0]['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI);
- }
- elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'logo'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0]));
- }
- elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'icon'))
- {
- return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0]));
- }
- else
- {
- return null;
- }
- }
-}
-
-class SimplePie_Author
-{
- var $name;
- var $link;
- var $email;
- var $avatar;
- var $name_date;
- var $uri_date;
- var $avatar_date;
-
- // Constructor, used to input the data
- function SimplePie_Author($name = null, $link = null, $email = null, $avatar = null, $name_date = null, $uri_date = null, $avatar_date = null)
- {
- $this->name = $name;
- $this->link = $link;
- $this->email = $email;
- $this->avatar = $avatar;
- $this->name_date = $name_date;
- $this->uri_date = $uri_date;
- $this->avatar_date = $avatar_date;
- }
-
- function __toString()
- {
- // There is no $this->data here
- return md5(serialize($this));
- }
-
- function get_name()
- {
- if ($this->name !== null)
- {
- return $this->name;
- }
- else
- {
- return null;
- }
- }
-
- function get_link()
- {
- if ($this->link !== null)
- {
- return $this->link;
- }
- else
- {
- return null;
- }
- }
-
- function get_email()
- {
- if ($this->email !== null)
- {
- return $this->email;
- }
- else
- {
- return null;
- }
- }
-
- function get_avatar()
- {
- if ($this->avatar !== null)
- {
- return $this->avatar;
- }
- else
- {
- return null;
- }
- }
-
- function get_name_date()
- {
- if ($this->name_date !== null)
- {
- return $this->name_date;
- }
- else
- {
- return null;
- }
- }
- function get_uri_date()
- {
- if ($this->uri_date !== null)
- {
- return $this->uri_date;
- }
- else
- {
- return null;
- }
- }
- function get_avatar_date()
- {
- if ($this->avatar_date !== null)
- {
- return $this->avatar_date;
- }
- else
- {
- return null;
- }
- }
-
-
-}
-
-class SimplePie_Category
-{
- var $term;
- var $scheme;
- var $label;
-
- // Constructor, used to input the data
- function SimplePie_Category($term = null, $scheme = null, $label = null)
- {
- $this->term = $term;
- $this->scheme = $scheme;
- $this->label = $label;
- }
-
- function __toString()
- {
- // There is no $this->data here
- return md5(serialize($this));
- }
-
- function get_term()
- {
- if ($this->term !== null)
- {
- return $this->term;
- }
- else
- {
- return null;
- }
- }
-
- function get_scheme()
- {
- if ($this->scheme !== null)
- {
- return $this->scheme;
- }
- else
- {
- return null;
- }
- }
-
- function get_label()
- {
- if ($this->label !== null)
- {
- return $this->label;
- }
- else
- {
- return $this->get_term();
- }
- }
-}
-
-class SimplePie_Enclosure
-{
- var $bitrate;
- var $captions;
- var $categories;
- var $channels;
- var $copyright;
- var $credits;
- var $description;
- var $duration;
- var $expression;
- var $framerate;
- var $handler;
- var $hashes;
- var $height;
- var $javascript;
- var $keywords;
- var $lang;
- var $length;
- var $link;
- var $medium;
- var $player;
- var $ratings;
- var $restrictions;
- var $samplingrate;
- var $thumbnails;
- var $title;
- var $type;
- var $width;
-
- // Constructor, used to input the data
- function SimplePie_Enclosure($link = null, $type = null, $length = null, $javascript = null, $bitrate = null, $captions = null, $categories = null, $channels = null, $copyright = null, $credits = null, $description = null, $duration = null, $expression = null, $framerate = null, $hashes = null, $height = null, $keywords = null, $lang = null, $medium = null, $player = null, $ratings = null, $restrictions = null, $samplingrate = null, $thumbnails = null, $title = null, $width = null)
- {
- $this->bitrate = $bitrate;
- $this->captions = $captions;
- $this->categories = $categories;
- $this->channels = $channels;
- $this->copyright = $copyright;
- $this->credits = $credits;
- $this->description = $description;
- $this->duration = $duration;
- $this->expression = $expression;
- $this->framerate = $framerate;
- $this->hashes = $hashes;
- $this->height = $height;
- $this->javascript = $javascript;
- $this->keywords = $keywords;
- $this->lang = $lang;
- $this->length = $length;
- $this->link = $link;
- $this->medium = $medium;
- $this->player = $player;
- $this->ratings = $ratings;
- $this->restrictions = $restrictions;
- $this->samplingrate = $samplingrate;
- $this->thumbnails = $thumbnails;
- $this->title = $title;
- $this->type = $type;
- $this->width = $width;
- if (class_exists('idna_convert'))
- {
- $idn = new idna_convert;
- $parsed = SimplePie_Misc::parse_url($link);
- $this->link = SimplePie_Misc::compress_parse_url($parsed['scheme'], $idn->encode($parsed['authority']), $parsed['path'], $parsed['query'], $parsed['fragment']);
- }
- $this->handler = $this->get_handler(); // Needs to load last
- }
-
- function __toString()
- {
- // There is no $this->data here
- return md5(serialize($this));
- }
-
- function get_bitrate()
- {
- if ($this->bitrate !== null)
- {
- return $this->bitrate;
- }
- else
- {
- return null;
- }
- }
-
- function get_caption($key = 0)
- {
- $captions = $this->get_captions();
- if (isset($captions[$key]))
- {
- return $captions[$key];
- }
- else
- {
- return null;
- }
- }
-
- function get_captions()
- {
- if ($this->captions !== null)
- {
- return $this->captions;
- }
- else
- {
- return null;
- }
- }
-
- function get_category($key = 0)
- {
- $categories = $this->get_categories();
- if (isset($categories[$key]))
- {
- return $categories[$key];
- }
- else
- {
- return null;
- }
- }
-
- function get_categories()
- {
- if ($this->categories !== null)
- {
- return $this->categories;
- }
- else
- {
- return null;
- }
- }
-
- function get_channels()
- {
- if ($this->channels !== null)
- {
- return $this->channels;
- }
- else
- {
- return null;
- }
- }
-
- function get_copyright()
- {
- if ($this->copyright !== null)
- {
- return $this->copyright;
- }
- else
- {
- return null;
- }
- }
-
- function get_credit($key = 0)
- {
- $credits = $this->get_credits();
- if (isset($credits[$key]))
- {
- return $credits[$key];
- }
- else
- {
- return null;
- }
- }
-
- function get_credits()
- {
- if ($this->credits !== null)
- {
- return $this->credits;
- }
- else
- {
- return null;
- }
- }
-
- function get_description()
- {
- if ($this->description !== null)
- {
- return $this->description;
- }
- else
- {
- return null;
- }
- }
-
- function get_duration($convert = false)
- {
- if ($this->duration !== null)
- {
- if ($convert)
- {
- $time = SimplePie_Misc::time_hms($this->duration);
- return $time;
- }
- else
- {
- return $this->duration;
- }
- }
- else
- {
- return null;
- }
- }
-
- function get_expression()
- {
- if ($this->expression !== null)
- {
- return $this->expression;
- }
- else
- {
- return 'full';
- }
- }
-
- function get_extension()
- {
- if ($this->link !== null)
- {
- $url = SimplePie_Misc::parse_url($this->link);
- if ($url['path'] !== '')
- {
- return pathinfo($url['path'], PATHINFO_EXTENSION);
- }
- }
- return null;
- }
-
- function get_framerate()
- {
- if ($this->framerate !== null)
- {
- return $this->framerate;
- }
- else
- {
- return null;
- }
- }
-
- function get_handler()
- {
- return $this->get_real_type(true);
- }
-
- function get_hash($key = 0)
- {
- $hashes = $this->get_hashes();
- if (isset($hashes[$key]))
- {
- return $hashes[$key];
- }
- else
- {
- return null;
- }
- }
-
- function get_hashes()
- {
- if ($this->hashes !== null)
- {
- return $this->hashes;
- }
- else
- {
- return null;
- }
- }
-
- function get_height()
- {
- if ($this->height !== null)
- {
- return $this->height;
- }
- else
- {
- return null;
- }
- }
-
- function get_language()
- {
- if ($this->lang !== null)
- {
- return $this->lang;
- }
- else
- {
- return null;
- }
- }
-
- function get_keyword($key = 0)
- {
- $keywords = $this->get_keywords();
- if (isset($keywords[$key]))
- {
- return $keywords[$key];
- }
- else
- {
- return null;
- }
- }
-
- function get_keywords()
- {
- if ($this->keywords !== null)
- {
- return $this->keywords;
- }
- else
- {
- return null;
- }
- }
-
- function get_length()
- {
- if ($this->length !== null)
- {
- return $this->length;
- }
- else
- {
- return null;
- }
- }
-
- function get_link()
- {
- if ($this->link !== null)
- {
- return urldecode($this->link);
- }
- else
- {
- return null;
- }
- }
-
- function get_medium()
- {
- if ($this->medium !== null)
- {
- return $this->medium;
- }
- else
- {
- return null;
- }
- }
-
- function get_player()
- {
- if ($this->player !== null)
- {
- return $this->player;
- }
- else
- {
- return null;
- }
- }
-
- function get_rating($key = 0)
- {
- $ratings = $this->get_ratings();
- if (isset($ratings[$key]))
- {
- return $ratings[$key];
- }
- else
- {
- return null;
- }
- }
-
- function get_ratings()
- {
- if ($this->ratings !== null)
- {
- return $this->ratings;
- }
- else
- {
- return null;
- }
- }
-
- function get_restriction($key = 0)
- {
- $restrictions = $this->get_restrictions();
- if (isset($restrictions[$key]))
- {
- return $restrictions[$key];
- }
- else
- {
- return null;
- }
- }
-
- function get_restrictions()
- {
- if ($this->restrictions !== null)
- {
- return $this->restrictions;
- }
- else
- {
- return null;
- }
- }
-
- function get_sampling_rate()
- {
- if ($this->samplingrate !== null)
- {
- return $this->samplingrate;
- }
- else
- {
- return null;
- }
- }
-
- function get_size()
- {
- $length = $this->get_length();
- if ($length !== null)
- {
- return round($length/1048576, 2);
- }
- else
- {
- return null;
- }
- }
-
- function get_thumbnail($key = 0)
- {
- $thumbnails = $this->get_thumbnails();
- if (isset($thumbnails[$key]))
- {
- return $thumbnails[$key];
- }
- else
- {
- return null;
- }
- }
-
- function get_thumbnails()
- {
- if ($this->thumbnails !== null)
- {
- return $this->thumbnails;
- }
- else
- {
- return null;
- }
- }
-
- function get_title()
- {
- if ($this->title !== null)
- {
- return $this->title;
- }
- else
- {
- return null;
- }
- }
-
- function get_type()
- {
- if ($this->type !== null)
- {
- return $this->type;
- }
- else
- {
- return null;
- }
- }
-
- function get_width()
- {
- if ($this->width !== null)
- {
- return $this->width;
- }
- else
- {
- return null;
- }
- }
-
- function native_embed($options='')
- {
- return $this->embed($options, true);
- }
-
- /**
- * @todo If the dimensions for media:content are defined, use them when width/height are set to 'auto'.
- */
- function embed($options = '', $native = false)
- {
- // Set up defaults
- $audio = '';
- $video = '';
- $alt = '';
- $altclass = '';
- $loop = 'false';
- $width = 'auto';
- $height = 'auto';
- $bgcolor = '#ffffff';
- $mediaplayer = '';
- $widescreen = false;
- $handler = $this->get_handler();
- $type = $this->get_real_type();
-
- // Process options and reassign values as necessary
- if (is_array($options))
- {
- extract($options);
- }
- else
- {
- $options = explode(',', $options);
- foreach($options as $option)
- {
- $opt = explode(':', $option, 2);
- if (isset($opt[0], $opt[1]))
- {
- $opt[0] = trim($opt[0]);
- $opt[1] = trim($opt[1]);
- switch ($opt[0])
- {
- case 'audio':
- $audio = $opt[1];
- break;
-
- case 'video':
- $video = $opt[1];
- break;
-
- case 'alt':
- $alt = $opt[1];
- break;
-
- case 'altclass':
- $altclass = $opt[1];
- break;
-
- case 'loop':
- $loop = $opt[1];
- break;
-
- case 'width':
- $width = $opt[1];
- break;
-
- case 'height':
- $height = $opt[1];
- break;
-
- case 'bgcolor':
- $bgcolor = $opt[1];
- break;
-
- case 'mediaplayer':
- $mediaplayer = $opt[1];
- break;
-
- case 'widescreen':
- $widescreen = $opt[1];
- break;
- }
- }
- }
- }
-
- $mime = explode('/', $type, 2);
- $mime = $mime[0];
-
- // Process values for 'auto'
- if ($width === 'auto')
- {
- if ($mime === 'video')
- {
- if ($height === 'auto')
- {
- $width = 480;
- }
- elseif ($widescreen)
- {
- $width = round((intval($height)/9)*16);
- }
- else
- {
- $width = round((intval($height)/3)*4);
- }
- }
- else
- {
- $width = '100%';
- }
- }
-
- if ($height === 'auto')
- {
- if ($mime === 'audio')
- {
- $height = 0;
- }
- elseif ($mime === 'video')
- {
- if ($width === 'auto')
- {
- if ($widescreen)
- {
- $height = 270;
- }
- else
- {
- $height = 360;
- }
- }
- elseif ($widescreen)
- {
- $height = round((intval($width)/16)*9);
- }
- else
- {
- $height = round((intval($width)/4)*3);
- }
- }
- else
- {
- $height = 376;
- }
- }
- elseif ($mime === 'audio')
- {
- $height = 0;
- }
-
- // Set proper placeholder value
- if ($mime === 'audio')
- {
- $placeholder = $audio;
- }
- elseif ($mime === 'video')
- {
- $placeholder = $video;
- }
-
- $embed = '';
-
- // Make sure the JS library is included
- if (!$native)
- {
- static $javascript_outputted = null;
- if (!$javascript_outputted && $this->javascript)
- {
- $embed .= '<script type="text/javascript" src="?' . htmlspecialchars($this->javascript) . '"></script>';
- $javascript_outputted = true;
- }
- }
-
- // Odeo Feed MP3's
- if ($handler === 'odeo')
- {
- if ($native)
- {
- $embed .= '<embed src="http://odeo.com/flash/audio_player_fullsize.swf" pluginspage="http://adobe.com/go/getflashplayer" type="application/x-shockwave-flash" quality="high" width="440" height="80" wmode="transparent" allowScriptAccess="any" flashvars="valid_sample_rate=true&external_url=' . $this->get_link() . '"></embed>';
- }
- else
- {
- $embed .= '<script type="text/javascript">embed_odeo("' . $this->get_link() . '");</script>';
- }
- }
-
- // Flash
- elseif ($handler === 'flash')
- {
- if ($native)
- {
- $embed .= "<embed src=\"" . $this->get_link() . "\" pluginspage=\"http://adobe.com/go/getflashplayer\" type=\"$type\" quality=\"high\" width=\"$width\" height=\"$height\" bgcolor=\"$bgcolor\" loop=\"$loop\"></embed>";
- }
- else
- {
- $embed .= "<script type='text/javascript'>embed_flash('$bgcolor', '$width', '$height', '" . $this->get_link() . "', '$loop', '$type');</script>";
- }
- }
-
- // Flash Media Player file types.
- // Preferred handler for MP3 file types.
- elseif ($handler === 'fmedia' || ($handler === 'mp3' && $mediaplayer !== ''))
- {
- $height += 20;
- if ($native)
- {
- $embed .= "<embed src=\"$mediaplayer\" pluginspage=\"http://adobe.com/go/getflashplayer\" type=\"application/x-shockwave-flash\" quality=\"high\" width=\"$width\" height=\"$height\" wmode=\"transparent\" flashvars=\"file=" . rawurlencode($this->get_link().'?file_extension=.'.$this->get_extension()) . "&autostart=false&repeat=$loop&showdigits=true&showfsbutton=false\"></embed>";
- }
- else
- {
- $embed .= "<script type='text/javascript'>embed_flv('$width', '$height', '" . rawurlencode($this->get_link().'?file_extension=.'.$this->get_extension()) . "', '$placeholder', '$loop', '$mediaplayer');</script>";
- }
- }
-
- // QuickTime 7 file types. Need to test with QuickTime 6.
- // Only handle MP3's if the Flash Media Player is not present.
- elseif ($handler === 'quicktime' || ($handler === 'mp3' && $mediaplayer === ''))
- {
- $height += 16;
- if ($native)
- {
- if ($placeholder !== '')
- {
- $embed .= "<embed type=\"$type\" style=\"cursor:hand; cursor:pointer;\" href=\"" . $this->get_link() . "\" src=\"$placeholder\" width=\"$width\" height=\"$height\" autoplay=\"false\" target=\"myself\" controller=\"false\" loop=\"$loop\" scale=\"aspect\" bgcolor=\"$bgcolor\" pluginspage=\"http://apple.com/quicktime/download/\"></embed>";
- }
- else
- {
- $embed .= "<embed type=\"$type\" style=\"cursor:hand; cursor:pointer;\" src=\"" . $this->get_link() . "\" width=\"$width\" height=\"$height\" autoplay=\"false\" target=\"myself\" controller=\"true\" loop=\"$loop\" scale=\"aspect\" bgcolor=\"$bgcolor\" pluginspage=\"http://apple.com/quicktime/download/\"></embed>";
- }
- }
- else
- {
- $embed .= "<script type='text/javascript'>embed_quicktime('$type', '$bgcolor', '$width', '$height', '" . $this->get_link() . "', '$placeholder', '$loop');</script>";
- }
- }
-
- // Windows Media
- elseif ($handler === 'wmedia')
- {
- $height += 45;
- if ($native)
- {
- $embed .= "<embed type=\"application/x-mplayer2\" src=\"" . $this->get_link() . "\" autosize=\"1\" width=\"$width\" height=\"$height\" showcontrols=\"1\" showstatusbar=\"0\" showdisplay=\"0\" autostart=\"0\"></embed>";
- }
- else
- {
- $embed .= "<script type='text/javascript'>embed_wmedia('$width', '$height', '" . $this->get_link() . "');</script>";
- }
- }
-
- // Everything else
- else $embed .= '<a href="' . $this->get_link() . '" class="' . $altclass . '">' . $alt . '</a>';
-
- return $embed;
- }
-
- function get_real_type($find_handler = false)
- {
- // If it's Odeo, let's get it out of the way.
- if (substr(strtolower($this->get_link()), 0, 15) === 'http://odeo.com')
- {
- return 'odeo';
- }
-
- // Mime-types by handler.
- $types_flash = array('application/x-shockwave-flash', 'application/futuresplash'); // Flash
- $types_fmedia = array('video/flv', 'video/x-flv','flv-application/octet-stream'); // Flash Media Player
- $types_quicktime = array('audio/3gpp', 'audio/3gpp2', 'audio/aac', 'audio/x-aac', 'audio/aiff', 'audio/x-aiff', 'audio/mid', 'audio/midi', 'audio/x-midi', 'audio/mp4', 'audio/m4a', 'audio/x-m4a', 'audio/wav', 'audio/x-wav', 'video/3gpp', 'video/3gpp2', 'video/m4v', 'video/x-m4v', 'video/mp4', 'video/mpeg', 'video/x-mpeg', 'video/quicktime', 'video/sd-video'); // QuickTime
- $types_wmedia = array('application/asx', 'application/x-mplayer2', 'audio/x-ms-wma', 'audio/x-ms-wax', 'video/x-ms-asf-plugin', 'video/x-ms-asf', 'video/x-ms-wm', 'video/x-ms-wmv', 'video/x-ms-wvx'); // Windows Media
- $types_mp3 = array('audio/mp3', 'audio/x-mp3', 'audio/mpeg', 'audio/x-mpeg'); // MP3
-
- if ($this->get_type() !== null)
- {
- $type = strtolower($this->type);
- }
- else
- {
- $type = null;
- }
-
- // If we encounter an unsupported mime-type, check the file extension and guess intelligently.
- if (!in_array($type, array_merge($types_flash, $types_fmedia, $types_quicktime, $types_wmedia, $types_mp3)))
- {
- switch (strtolower($this->get_extension()))
- {
- // Audio mime-types
- case 'aac':
- case 'adts':
- $type = 'audio/acc';
- break;
-
- case 'aif':
- case 'aifc':
- case 'aiff':
- case 'cdda':
- $type = 'audio/aiff';
- break;
-
- case 'bwf':
- $type = 'audio/wav';
- break;
-
- case 'kar':
- case 'mid':
- case 'midi':
- case 'smf':
- $type = 'audio/midi';
- break;
-
- case 'm4a':
- $type = 'audio/x-m4a';
- break;
-
- case 'mp3':
- case 'swa':
- $type = 'audio/mp3';
- break;
-
- case 'wav':
- $type = 'audio/wav';
- break;
-
- case 'wax':
- $type = 'audio/x-ms-wax';
- break;
-
- case 'wma':
- $type = 'audio/x-ms-wma';
- break;
-
- // Video mime-types
- case '3gp':
- case '3gpp':
- $type = 'video/3gpp';
- break;
-
- case '3g2':
- case '3gp2':
- $type = 'video/3gpp2';
- break;
-
- case 'asf':
- $type = 'video/x-ms-asf';
- break;
-
- case 'flv':
- $type = 'video/x-flv';
- break;
-
- case 'm1a':
- case 'm1s':
- case 'm1v':
- case 'm15':
- case 'm75':
- case 'mp2':
- case 'mpa':
- case 'mpeg':
- case 'mpg':
- case 'mpm':
- case 'mpv':
- $type = 'video/mpeg';
- break;
-
- case 'm4v':
- $type = 'video/x-m4v';
- break;
-
- case 'mov':
- case 'qt':
- $type = 'video/quicktime';
- break;
-
- case 'mp4':
- case 'mpg4':
- $type = 'video/mp4';
- break;
-
- case 'sdv':
- $type = 'video/sd-video';
- break;
-
- case 'wm':
- $type = 'video/x-ms-wm';
- break;
-
- case 'wmv':
- $type = 'video/x-ms-wmv';
- break;
-
- case 'wvx':
- $type = 'video/x-ms-wvx';
- break;
-
- // Flash mime-types
- case 'spl':
- $type = 'application/futuresplash';
- break;
-
- case 'swf':
- $type = 'application/x-shockwave-flash';
- break;
- }
- }
-
- if ($find_handler)
- {
- if (in_array($type, $types_flash))
- {
- return 'flash';
- }
- elseif (in_array($type, $types_fmedia))
- {
- return 'fmedia';
- }
- elseif (in_array($type, $types_quicktime))
- {
- return 'quicktime';
- }
- elseif (in_array($type, $types_wmedia))
- {
- return 'wmedia';
- }
- elseif (in_array($type, $types_mp3))
- {
- return 'mp3';
- }
- else
- {
- return null;
- }
- }
- else
- {
- return $type;
- }
- }
-}
-
-class SimplePie_Caption
-{
- var $type;
- var $lang;
- var $startTime;
- var $endTime;
- var $text;
-
- // Constructor, used to input the data
- function SimplePie_Caption($type = null, $lang = null, $startTime = null, $endTime = null, $text = null)
- {
- $this->type = $type;
- $this->lang = $lang;
- $this->startTime = $startTime;
- $this->endTime = $endTime;
- $this->text = $text;
- }
-
- function __toString()
- {
- // There is no $this->data here
- return md5(serialize($this));
- }
-
- function get_endtime()
- {
- if ($this->endTime !== null)
- {
- return $this->endTime;
- }
- else
- {
- return null;
- }
- }
-
- function get_language()
- {
- if ($this->lang !== null)
- {
- return $this->lang;
- }
- else
- {
- return null;
- }
- }
-
- function get_starttime()
- {
- if ($this->startTime !== null)
- {
- return $this->startTime;
- }
- else
- {
- return null;
- }
- }
-
- function get_text()
- {
- if ($this->text !== null)
- {
- return $this->text;
- }
- else
- {
- return null;
- }
- }
-
- function get_type()
- {
- if ($this->type !== null)
- {
- return $this->type;
- }
- else
- {
- return null;
- }
- }
-}
-
-class SimplePie_Credit
-{
- var $role;
- var $scheme;
- var $name;
-
- // Constructor, used to input the data
- function SimplePie_Credit($role = null, $scheme = null, $name = null)
- {
- $this->role = $role;
- $this->scheme = $scheme;
- $this->name = $name;
- }
-
- function __toString()
- {
- // There is no $this->data here
- return md5(serialize($this));
- }
-
- function get_role()
- {
- if ($this->role !== null)
- {
- return $this->role;
- }
- else
- {
- return null;
- }
- }
-
- function get_scheme()
- {
- if ($this->scheme !== null)
- {
- return $this->scheme;
- }
- else
- {
- return null;
- }
- }
-
- function get_name()
- {
- if ($this->name !== null)
- {
- return $this->name;
- }
- else
- {
- return null;
- }
- }
-}
-
-class SimplePie_Copyright
-{
- var $url;
- var $label;
-
- // Constructor, used to input the data
- function SimplePie_Copyright($url = null, $label = null)
- {
- $this->url = $url;
- $this->label = $label;
- }
-
- function __toString()
- {
- // There is no $this->data here
- return md5(serialize($this));
- }
-
- function get_url()
- {
- if ($this->url !== null)
- {
- return $this->url;
- }
- else
- {
- return null;
- }
- }
-
- function get_attribution()
- {
- if ($this->label !== null)
- {
- return $this->label;
- }
- else
- {
- return null;
- }
- }
-}
-
-class SimplePie_Rating
-{
- var $scheme;
- var $value;
-
- // Constructor, used to input the data
- function SimplePie_Rating($scheme = null, $value = null)
- {
- $this->scheme = $scheme;
- $this->value = $value;
- }
-
- function __toString()
- {
- // There is no $this->data here
- return md5(serialize($this));
- }
-
- function get_scheme()
- {
- if ($this->scheme !== null)
- {
- return $this->scheme;
- }
- else
- {
- return null;
- }
- }
-
- function get_value()
- {
- if ($this->value !== null)
- {
- return $this->value;
- }
- else
- {
- return null;
- }
- }
-}
-
-class SimplePie_Restriction
-{
- var $relationship;
- var $type;
- var $value;
-
- // Constructor, used to input the data
- function SimplePie_Restriction($relationship = null, $type = null, $value = null)
- {
- $this->relationship = $relationship;
- $this->type = $type;
- $this->value = $value;
- }
-
- function __toString()
- {
- // There is no $this->data here
- return md5(serialize($this));
- }
-
- function get_relationship()
- {
- if ($this->relationship !== null)
- {
- return $this->relationship;
- }
- else
- {
- return null;
- }
- }
-
- function get_type()
- {
- if ($this->type !== null)
- {
- return $this->type;
- }
- else
- {
- return null;
- }
- }
-
- function get_value()
- {
- if ($this->value !== null)
- {
- return $this->value;
- }
- else
- {
- return null;
- }
- }
-}
-
-/**
- * @todo Move to properly supporting RFC2616 (HTTP/1.1)
- */
-class SimplePie_File
-{
- var $url;
- var $useragent;
- var $success = true;
- var $headers = array();
- var $body;
- var $status_code;
- var $redirects = 0;
- var $error;
- var $method = SIMPLEPIE_FILE_SOURCE_NONE;
-
- function SimplePie_File($url, $timeout = 10, $redirects = 5, $headers = null, $useragent = null, $force_fsockopen = false)
- {
- if (class_exists('idna_convert'))
- {
- $idn = new idna_convert;
- $parsed = SimplePie_Misc::parse_url($url);
- $url = SimplePie_Misc::compress_parse_url($parsed['scheme'], $idn->encode($parsed['authority']), $parsed['path'], $parsed['query'], $parsed['fragment']);
- }
- $this->url = $url;
- $this->useragent = $useragent;
- if (preg_match('/^http(s)?:\/\//i', $url))
- {
- if ($useragent === null)
- {
- $useragent = ini_get('user_agent');
- $this->useragent = $useragent;
- }
- if (!is_array($headers))
- {
- $headers = array();
- }
- if (!$force_fsockopen && function_exists('curl_exec'))
- {
- $this->method = SIMPLEPIE_FILE_SOURCE_REMOTE | SIMPLEPIE_FILE_SOURCE_CURL;
- $fp = curl_init();
- $headers2 = array();
- foreach ($headers as $key => $value)
- {
- $headers2[] = "$key: $value";
- }
- if (version_compare(SimplePie_Misc::get_curl_version(), '7.10.5', '>='))
- {
- curl_setopt($fp, CURLOPT_ENCODING, '');
- }
- curl_setopt($fp, CURLOPT_URL, $url);
- curl_setopt($fp, CURLOPT_HEADER, 1);
- curl_setopt($fp, CURLOPT_RETURNTRANSFER, 1);
- curl_setopt($fp, CURLOPT_TIMEOUT, $timeout);
- curl_setopt($fp, CURLOPT_CONNECTTIMEOUT, $timeout);
- curl_setopt($fp, CURLOPT_REFERER, $url);
- curl_setopt($fp, CURLOPT_USERAGENT, $useragent);
- curl_setopt($fp, CURLOPT_HTTPHEADER, $headers2);
- if (!ini_get('open_basedir') && !ini_get('safe_mode') && version_compare(SimplePie_Misc::get_curl_version(), '7.15.2', '>='))
- {
- curl_setopt($fp, CURLOPT_FOLLOWLOCATION, 1);
- curl_setopt($fp, CURLOPT_MAXREDIRS, $redirects);
- }
-
- $this->headers = curl_exec($fp);
- if (curl_errno($fp) === 23 || curl_errno($fp) === 61)
- {
- curl_setopt($fp, CURLOPT_ENCODING, 'none');
- $this->headers = curl_exec($fp);
- }
- if (curl_errno($fp))
- {
- $this->error = 'cURL error ' . curl_errno($fp) . ': ' . curl_error($fp);
- $this->success = false;
- }
- else
- {
- $info = curl_getinfo($fp);
- curl_close($fp);
- $this->headers = explode("\r\n\r\n", $this->headers, $info['redirect_count'] + 1);
- $this->headers = array_pop($this->headers);
- $parser = new SimplePie_HTTP_Parser($this->headers);
- if ($parser->parse())
- {
- $this->headers = $parser->headers;
- $this->body = $parser->body;
- $this->status_code = $parser->status_code;
- if ((in_array($this->status_code, array(300, 301, 302, 303, 307)) || $this->status_code > 307 && $this->status_code < 400) && isset($this->headers['location']) && $this->redirects < $redirects)
- {
- $this->redirects++;
- $location = SimplePie_Misc::absolutize_url($this->headers['location'], $url);
- return $this->SimplePie_File($location, $timeout, $redirects, $headers, $useragent, $force_fsockopen);
- }
- }
- }
- }
- else
- {
- $this->method = SIMPLEPIE_FILE_SOURCE_REMOTE | SIMPLEPIE_FILE_SOURCE_FSOCKOPEN;
- $url_parts = parse_url($url);
- if (isset($url_parts['scheme']) && strtolower($url_parts['scheme']) === 'https')
- {
- $url_parts['host'] = "ssl://$url_parts[host]";
- $url_parts['port'] = 443;
- }
- if (!isset($url_parts['port']))
- {
- $url_parts['port'] = 80;
- }
- $fp = @fsockopen($url_parts['host'], $url_parts['port'], $errno, $errstr, $timeout);
- if (!$fp)
- {
- $this->error = 'fsockopen error: ' . $errstr;
- $this->success = false;
- }
- else
- {
- stream_set_timeout($fp, $timeout);
- if (isset($url_parts['path']))
- {
- if (isset($url_parts['query']))
- {
- $get = "$url_parts[path]?$url_parts[query]";
- }
- else
- {
- $get = $url_parts['path'];
- }
- }
- else
- {
- $get = '/';
- }
- $out = "GET $get HTTP/1.0\r\n";
- $out .= "Host: $url_parts[host]\r\n";
- $out .= "User-Agent: $useragent\r\n";
- if (extension_loaded('zlib'))
- {
- $out .= "Accept-Encoding: x-gzip,gzip,deflate\r\n";
- }
-
- if (isset($url_parts['user']) && isset($url_parts['pass']))
- {
- $out .= "Authorization: Basic " . base64_encode("$url_parts[user]:$url_parts[pass]") . "\r\n";
- }
- foreach ($headers as $key => $value)
- {
- $out .= "$key: $value\r\n";
- }
- $out .= "Connection: Close\r\n\r\n";
- fwrite($fp, $out);
-
- $info = stream_get_meta_data($fp);
-
- $this->headers = '';
- while (!$info['eof'] && !$info['timed_out'])
- {
- $this->headers .= fread($fp, 1160);
- $info = stream_get_meta_data($fp);
- }
- if (!$info['timed_out'])
- {
- $parser = new SimplePie_HTTP_Parser($this->headers);
- if ($parser->parse())
- {
- $this->headers = $parser->headers;
- $this->body = $parser->body;
- $this->status_code = $parser->status_code;
- if ((in_array($this->status_code, array(300, 301, 302, 303, 307)) || $this->status_code > 307 && $this->status_code < 400) && isset($this->headers['location']) && $this->redirects < $redirects)
- {
- $this->redirects++;
- $location = SimplePie_Misc::absolutize_url($this->headers['location'], $url);
- return $this->SimplePie_File($location, $timeout, $redirects, $headers, $useragent, $force_fsockopen);
- }
- if (isset($this->headers['content-encoding']))
- {
- // Hey, we act dumb elsewhere, so let's do that here too
- switch (strtolower(trim($this->headers['content-encoding'], "\x09\x0A\x0D\x20")))
- {
- case 'gzip':
- case 'x-gzip':
- $decoder = new SimplePie_gzdecode($this->body);
- if (!$decoder->parse())
- {
- $this->error = 'Unable to decode HTTP "gzip" stream';
- $this->success = false;
- }
- else
- {
- $this->body = $decoder->data;
- }
- break;
-
- case 'deflate':
- if (($body = gzuncompress($this->body)) === false)
- {
- if (($body = gzinflate($this->body)) === false)
- {
- $this->error = 'Unable to decode HTTP "deflate" stream';
- $this->success = false;
- }
- }
- $this->body = $body;
- break;
-
- default:
- $this->error = 'Unknown content coding';
- $this->success = false;
- }
- }
- }
- }
- else
- {
- $this->error = 'fsocket timed out';
- $this->success = false;
- }
- fclose($fp);
- }
- }
- }
- else
- {
- $this->method = SIMPLEPIE_FILE_SOURCE_LOCAL | SIMPLEPIE_FILE_SOURCE_FILE_GET_CONTENTS;
- if (!$this->body = file_get_contents($url))
- {
- $this->error = 'file_get_contents could not read the file';
- $this->success = false;
- }
- }
- }
-}
-
-/**
- * HTTP Response Parser
- *
- * @package SimplePie
- */
-class SimplePie_HTTP_Parser
-{
- /**
- * HTTP Version
- *
- * @access public
- * @var float
- */
- var $http_version = 0.0;
-
- /**
- * Status code
- *
- * @access public
- * @var int
- */
- var $status_code = 0;
-
- /**
- * Reason phrase
- *
- * @access public
- * @var string
- */
- var $reason = '';
-
- /**
- * Key/value pairs of the headers
- *
- * @access public
- * @var array
- */
- var $headers = array();
-
- /**
- * Body of the response
- *
- * @access public
- * @var string
- */
- var $body = '';
-
- /**
- * Current state of the state machine
- *
- * @access private
- * @var string
- */
- var $state = 'http_version';
-
- /**
- * Input data
- *
- * @access private
- * @var string
- */
- var $data = '';
-
- /**
- * Input data length (to avoid calling strlen() everytime this is needed)
- *
- * @access private
- * @var int
- */
- var $data_length = 0;
-
- /**
- * Current position of the pointer
- *
- * @var int
- * @access private
- */
- var $position = 0;
-
- /**
- * Name of the hedaer currently being parsed
- *
- * @access private
- * @var string
- */
- var $name = '';
-
- /**
- * Value of the hedaer currently being parsed
- *
- * @access private
- * @var string
- */
- var $value = '';
-
- /**
- * Create an instance of the class with the input data
- *
- * @access public
- * @param string $data Input data
- */
- function SimplePie_HTTP_Parser($data)
- {
- $this->data = $data;
- $this->data_length = strlen($this->data);
- }
-
- /**
- * Parse the input data
- *
- * @access public
- * @return bool true on success, false on failure
- */
- function parse()
- {
- while ($this->state && $this->state !== 'emit' && $this->has_data())
- {
- $state = $this->state;
- $this->$state();
- }
- $this->data = '';
- if ($this->state === 'emit' || $this->state === 'body')
- {
- return true;
- }
- else
- {
- $this->http_version = '';
- $this->status_code = '';
- $this->reason = '';
- $this->headers = array();
- $this->body = '';
- return false;
- }
- }
-
- /**
- * Check whether there is data beyond the pointer
- *
- * @access private
- * @return bool true if there is further data, false if not
- */
- function has_data()
- {
- return (bool) ($this->position < $this->data_length);
- }
-
- /**
- * See if the next character is LWS
- *
- * @access private
- * @return bool true if the next character is LWS, false if not
- */
- function is_linear_whitespace()
- {
- return (bool) ($this->data[$this->position] === "\x09"
- || $this->data[$this->position] === "\x20"
- || ($this->data[$this->position] === "\x0A"
- && isset($this->data[$this->position + 1])
- && ($this->data[$this->position + 1] === "\x09" || $this->data[$this->position + 1] === "\x20")));
- }
-
- /**
- * Parse the HTTP version
- *
- * @access private
- */
- function http_version()
- {
- if (strpos($this->data, "\x0A") !== false && strtoupper(substr($this->data, 0, 5)) === 'HTTP/')
- {
- $len = strspn($this->data, '0123456789.', 5);
- $this->http_version = substr($this->data, 5, $len);
- $this->position += 5 + $len;
- if (substr_count($this->http_version, '.') <= 1)
- {
- $this->http_version = (float) $this->http_version;
- $this->position += strspn($this->data, "\x09\x20", $this->position);
- $this->state = 'status';
- }
- else
- {
- $this->state = false;
- }
- }
- else
- {
- $this->state = false;
- }
- }
-
- /**
- * Parse the status code
- *
- * @access private
- */
- function status()
- {
- if ($len = strspn($this->data, '0123456789', $this->position))
- {
- $this->status_code = (int) substr($this->data, $this->position, $len);
- $this->position += $len;
- $this->state = 'reason';
- }
- else
- {
- $this->state = false;
- }
- }
-
- /**
- * Parse the reason phrase
- *
- * @access private
- */
- function reason()
- {
- $len = strcspn($this->data, "\x0A", $this->position);
- $this->reason = trim(substr($this->data, $this->position, $len), "\x09\x0D\x20");
- $this->position += $len + 1;
- $this->state = 'new_line';
- }
-
- /**
- * Deal with a new line, shifting data around as needed
- *
- * @access private
- */
- function new_line()
- {
- $this->value = trim($this->value, "\x0D\x20");
- if ($this->name !== '' && $this->value !== '')
- {
- $this->name = strtolower($this->name);
- if (isset($this->headers[$this->name]))
- {
- $this->headers[$this->name] .= ', ' . $this->value;
- }
- else
- {
- $this->headers[$this->name] = $this->value;
- }
- }
- $this->name = '';
- $this->value = '';
- if (substr($this->data[$this->position], 0, 2) === "\x0D\x0A")
- {
- $this->position += 2;
- $this->state = 'body';
- }
- elseif ($this->data[$this->position] === "\x0A")
- {
- $this->position++;
- $this->state = 'body';
- }
- else
- {
- $this->state = 'name';
- }
- }
-
- /**
- * Parse a header name
- *
- * @access private
- */
- function name()
- {
- $len = strcspn($this->data, "\x0A:", $this->position);
- if (isset($this->data[$this->position + $len]))
- {
- if ($this->data[$this->position + $len] === "\x0A")
- {
- $this->position += $len;
- $this->state = 'new_line';
- }
- else
- {
- $this->name = substr($this->data, $this->position, $len);
- $this->position += $len + 1;
- $this->state = 'value';
- }
- }
- else
- {
- $this->state = false;
- }
- }
-
- /**
- * Parse LWS, replacing consecutive LWS characters with a single space
- *
- * @access private
- */
- function linear_whitespace()
- {
- do
- {
- if (substr($this->data, $this->position, 2) === "\x0D\x0A")
- {
- $this->position += 2;
- }
- elseif ($this->data[$this->position] === "\x0A")
- {
- $this->position++;
- }
- $this->position += strspn($this->data, "\x09\x20", $this->position);
- } while ($this->has_data() && $this->is_linear_whitespace());
- $this->value .= "\x20";
- }
-
- /**
- * See what state to move to while within non-quoted header values
- *
- * @access private
- */
- function value()
- {
- if ($this->is_linear_whitespace())
- {
- $this->linear_whitespace();
- }
- else
- {
- switch ($this->data[$this->position])
- {
- case '"':
- $this->position++;
- $this->state = 'quote';
- break;
-
- case "\x0A":
- $this->position++;
- $this->state = 'new_line';
- break;
-
- default:
- $this->state = 'value_char';
- break;
- }
- }
- }
-
- /**
- * Parse a header value while outside quotes
- *
- * @access private
- */
- function value_char()
- {
- $len = strcspn($this->data, "\x09\x20\x0A\"", $this->position);
- $this->value .= substr($this->data, $this->position, $len);
- $this->position += $len;
- $this->state = 'value';
- }
-
- /**
- * See what state to move to while within quoted header values
- *
- * @access private
- */
- function quote()
- {
- if ($this->is_linear_whitespace())
- {
- $this->linear_whitespace();
- }
- else
- {
- switch ($this->data[$this->position])
- {
- case '"':
- $this->position++;
- $this->state = 'value';
- break;
-
- case "\x0A":
- $this->position++;
- $this->state = 'new_line';
- break;
-
- case '\\':
- $this->position++;
- $this->state = 'quote_escaped';
- break;
-
- default:
- $this->state = 'quote_char';
- break;
- }
- }
- }
-
- /**
- * Parse a header value while within quotes
- *
- * @access private
- */
- function quote_char()
- {
- $len = strcspn($this->data, "\x09\x20\x0A\"\\", $this->position);
- $this->value .= substr($this->data, $this->position, $len);
- $this->position += $len;
- $this->state = 'value';
- }
-
- /**
- * Parse an escaped character within quotes
- *
- * @access private
- */
- function quote_escaped()
- {
- $this->value .= $this->data[$this->position];
- $this->position++;
- $this->state = 'quote';
- }
-
- /**
- * Parse the body
- *
- * @access private
- */
- function body()
- {
- $this->body = substr($this->data, $this->position);
- $this->state = 'emit';
- }
-}
-
-/**
- * gzdecode
- *
- * @package SimplePie
- */
-class SimplePie_gzdecode
-{
- /**
- * Compressed data
- *
- * @access private
- * @see gzdecode::$data
- */
- var $compressed_data;
-
- /**
- * Size of compressed data
- *
- * @access private
- */
- var $compressed_size;
-
- /**
- * Minimum size of a valid gzip string
- *
- * @access private
- */
- var $min_compressed_size = 18;
-
- /**
- * Current position of pointer
- *
- * @access private
- */
- var $position = 0;
-
- /**
- * Flags (FLG)
- *
- * @access private
- */
- var $flags;
-
- /**
- * Uncompressed data
- *
- * @access public
- * @see gzdecode::$compressed_data
- */
- var $data;
-
- /**
- * Modified time
- *
- * @access public
- */
- var $MTIME;
-
- /**
- * Extra Flags
- *
- * @access public
- */
- var $XFL;
-
- /**
- * Operating System
- *
- * @access public
- */
- var $OS;
-
- /**
- * Subfield ID 1
- *
- * @access public
- * @see gzdecode::$extra_field
- * @see gzdecode::$SI2
- */
- var $SI1;
-
- /**
- * Subfield ID 2
- *
- * @access public
- * @see gzdecode::$extra_field
- * @see gzdecode::$SI1
- */
- var $SI2;
-
- /**
- * Extra field content
- *
- * @access public
- * @see gzdecode::$SI1
- * @see gzdecode::$SI2
- */
- var $extra_field;
-
- /**
- * Original filename
- *
- * @access public
- */
- var $filename;
-
- /**
- * Human readable comment
- *
- * @access public
- */
- var $comment;
-
- /**
- * Don't allow anything to be set
- *
- * @access public
- */
- function __set($name, $value)
- {
- trigger_error("Cannot write property $name", E_USER_ERROR);
- }
-
- /**
- * Set the compressed string and related properties
- *
- * @access public
- */
- function SimplePie_gzdecode($data)
- {
- $this->compressed_data = $data;
- $this->compressed_size = strlen($data);
- }
-
- /**
- * Decode the GZIP stream
- *
- * @access public
- */
- function parse()
- {
- if ($this->compressed_size >= $this->min_compressed_size)
- {
- // Check ID1, ID2, and CM
- if (substr($this->compressed_data, 0, 3) !== "\x1F\x8B\x08")
- {
- return false;
- }
-
- // Get the FLG (FLaGs)
- $this->flags = ord($this->compressed_data[3]);
-
- // FLG bits above (1 << 4) are reserved
- if ($this->flags > 0x1F)
- {
- return false;
- }
-
- // Advance the pointer after the above
- $this->position += 4;
-
- // MTIME
- $mtime = substr($this->compressed_data, $this->position, 4);
- // Reverse the string if we're on a big-endian arch because l is the only signed long and is machine endianness
- if (current(unpack('S', "\x00\x01")) === 1)
- {
- $mtime = strrev($mtime);
- }
- $this->MTIME = current(unpack('l', $mtime));
- $this->position += 4;
-
- // Get the XFL (eXtra FLags)
- $this->XFL = ord($this->compressed_data[$this->position++]);
-
- // Get the OS (Operating System)
- $this->OS = ord($this->compressed_data[$this->position++]);
-
- // Parse the FEXTRA
- if ($this->flags & 4)
- {
- // Read subfield IDs
- $this->SI1 = $this->compressed_data[$this->position++];
- $this->SI2 = $this->compressed_data[$this->position++];
-
- // SI2 set to zero is reserved for future use
- if ($this->SI2 === "\x00")
- {
- return false;
- }
-
- // Get the length of the extra field
- $len = current(unpack('v', substr($this->compressed_data, $this->position, 2)));
- $position += 2;
-
- // Check the length of the string is still valid
- $this->min_compressed_size += $len + 4;
- if ($this->compressed_size >= $this->min_compressed_size)
- {
- // Set the extra field to the given data
- $this->extra_field = substr($this->compressed_data, $this->position, $len);
- $this->position += $len;
- }
- else
- {
- return false;
- }
- }
-
- // Parse the FNAME
- if ($this->flags & 8)
- {
- // Get the length of the filename
- $len = strcspn($this->compressed_data, "\x00", $this->position);
-
- // Check the length of the string is still valid
- $this->min_compressed_size += $len + 1;
- if ($this->compressed_size >= $this->min_compressed_size)
- {
- // Set the original filename to the given string
- $this->filename = substr($this->compressed_data, $this->position, $len);
- $this->position += $len + 1;
- }
- else
- {
- return false;
- }
- }
-
- // Parse the FCOMMENT
- if ($this->flags & 16)
- {
- // Get the length of the comment
- $len = strcspn($this->compressed_data, "\x00", $this->position);
-
- // Check the length of the string is still valid
- $this->min_compressed_size += $len + 1;
- if ($this->compressed_size >= $this->min_compressed_size)
- {
- // Set the original comment to the given string
- $this->comment = substr($this->compressed_data, $this->position, $len);
- $this->position += $len + 1;
- }
- else
- {
- return false;
- }
- }
-
- // Parse the FHCRC
- if ($this->flags & 2)
- {
- // Check the length of the string is still valid
- $this->min_compressed_size += $len + 2;
- if ($this->compressed_size >= $this->min_compressed_size)
- {
- // Read the CRC
- $crc = current(unpack('v', substr($this->compressed_data, $this->position, 2)));
-
- // Check the CRC matches
- if ((crc32(substr($this->compressed_data, 0, $this->position)) & 0xFFFF) === $crc)
- {
- $this->position += 2;
- }
- else
- {
- return false;
- }
- }
- else
- {
- return false;
- }
- }
-
- // Decompress the actual data
- if (($this->data = gzinflate(substr($this->compressed_data, $this->position, -8))) === false)
- {
- return false;
- }
- else
- {
- $this->position = $this->compressed_size - 8;
- }
-
- // Check CRC of data
- $crc = current(unpack('V', substr($this->compressed_data, $this->position, 4)));
- $this->position += 4;
- /*if (extension_loaded('hash') && sprintf('%u', current(unpack('V', hash('crc32b', $this->data)))) !== sprintf('%u', $crc))
- {
- return false;
- }*/
-
- // Check ISIZE of data
- $isize = current(unpack('V', substr($this->compressed_data, $this->position, 4)));
- $this->position += 4;
- if (sprintf('%u', strlen($this->data) & 0xFFFFFFFF) !== sprintf('%u', $isize))
- {
- return false;
- }
-
- // Wow, against all odds, we've actually got a valid gzip string
- return true;
- }
- else
- {
- return false;
- }
- }
-}
-
-class SimplePie_Cache
-{
- /**
- * Don't call the constructor. Please.
- *
- * @access private
- */
- function SimplePie_Cache()
- {
- trigger_error('Please call SimplePie_Cache::create() instead of the constructor', E_USER_ERROR);
- }
-
- /**
- * Create a new SimplePie_Cache object
- *
- * @static
- * @access public
- */
- function create($location, $filename, $extension)
- {
- $location_iri = new SimplePie_IRI($location);
- switch ($location_iri->get_scheme())
- {
- case 'mysql':
- if (extension_loaded('mysql'))
- {
- return new SimplePie_Cache_MySQL($location_iri, $filename, $extension);
- }
- break;
-
- default:
- return new SimplePie_Cache_File($location, $filename, $extension);
- }
- }
-}
-
-class SimplePie_Cache_File
-{
- var $location;
- var $filename;
- var $extension;
- var $name;
-
- function SimplePie_Cache_File($location, $filename, $extension)
- {
- $this->location = $location;
- $this->filename = $filename;
- $this->extension = $extension;
- $this->name = "$this->location/$this->filename.$this->extension";
- }
-
- function save($data)
- {
- if (file_exists($this->name) && is_writeable($this->name) || file_exists($this->location) && is_writeable($this->location))
- {
- if (is_a($data, 'SimplePie'))
- {
- $data = $data->data;
- }
-
- $data = serialize($data);
-
- if (function_exists('file_put_contents'))
- {
- return (bool) file_put_contents($this->name, $data);
- }
- else
- {
- $fp = fopen($this->name, 'wb');
- if ($fp)
- {
- fwrite($fp, $data);
- fclose($fp);
- return true;
- }
- }
- }
- return false;
- }
-
- function load()
- {
- if (file_exists($this->name) && is_readable($this->name))
- {
- return unserialize(file_get_contents($this->name));
- }
- return false;
- }
-
- function mtime()
- {
- if (file_exists($this->name))
- {
- return filemtime($this->name);
- }
- return false;
- }
-
- function touch()
- {
- if (file_exists($this->name))
- {
- return touch($this->name);
- }
- return false;
- }
-
- function unlink()
- {
- if (file_exists($this->name))
- {
- return unlink($this->name);
- }
- return false;
- }
-}
-
-class SimplePie_Cache_DB
-{
- function prepare_simplepie_object_for_cache($data)
- {
- $items = $data->get_items();
- $items_by_id = array();
-
- if (!empty($items))
- {
- foreach ($items as $item)
- {
- $items_by_id[$item->get_id()] = $item;
- }
-
- if (count($items_by_id) !== count($items))
- {
- $items_by_id = array();
- foreach ($items as $item)
- {
- $items_by_id[$item->get_id(true)] = $item;
- }
- }
-
- if (isset($data->data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0]))
- {
- $channel =& $data->data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0];
- }
- elseif (isset($data->data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0]))
- {
- $channel =& $data->data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0];
- }
- elseif (isset($data->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]))
- {
- $channel =& $data->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0];
- }
- elseif (isset($data->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_20]['channel'][0]))
- {
- $channel =& $data->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_20]['channel'][0];
- }
- else
- {
- $channel = null;
- }
-
- if ($channel !== null)
- {
- if (isset($channel['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['entry']))
- {
- unset($channel['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['entry']);
- }
- if (isset($channel['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['entry']))
- {
- unset($channel['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['entry']);
- }
- if (isset($channel['child'][SIMPLEPIE_NAMESPACE_RSS_10]['item']))
- {
- unset($channel['child'][SIMPLEPIE_NAMESPACE_RSS_10]['item']);
- }
- if (isset($channel['child'][SIMPLEPIE_NAMESPACE_RSS_090]['item']))
- {
- unset($channel['child'][SIMPLEPIE_NAMESPACE_RSS_090]['item']);
- }
- if (isset($channel['child'][SIMPLEPIE_NAMESPACE_RSS_20]['item']))
- {
- unset($channel['child'][SIMPLEPIE_NAMESPACE_RSS_20]['item']);
- }
- }
- if (isset($data->data['items']))
- {
- unset($data->data['items']);
- }
- if (isset($data->data['ordered_items']))
- {
- unset($data->data['ordered_items']);
- }
- }
- return array(serialize($data->data), $items_by_id);
- }
-}
-
-class SimplePie_Cache_MySQL extends SimplePie_Cache_DB
-{
- var $mysql;
- var $options;
- var $id;
-
- function SimplePie_Cache_MySQL($mysql_location, $name, $extension)
- {
- $host = $mysql_location->get_host();
- if (SimplePie_Misc::stripos($host, 'unix(') === 0 && substr($host, -1) === ')')
- {
- $server = ':' . substr($host, 5, -1);
- }
- else
- {
- $server = $host;
- if ($mysql_location->get_port() !== null)
- {
- $server .= ':' . $mysql_location->get_port();
- }
- }
-
- if (strpos($mysql_location->get_userinfo(), ':') !== false)
- {
- list($username, $password) = explode(':', $mysql_location->get_userinfo(), 2);
- }
- else
- {
- $username = $mysql_location->get_userinfo();
- $password = null;
- }
-
- if ($this->mysql = mysql_connect($server, $username, $password))
- {
- $this->id = $name . $extension;
- $this->options = SimplePie_Misc::parse_str($mysql_location->get_query());
- if (!isset($this->options['prefix'][0]))
- {
- $this->options['prefix'][0] = '';
- }
-
- if (mysql_select_db(ltrim($mysql_location->get_path(), '/'))
- && mysql_query('SET NAMES utf8')
- && ($query = mysql_unbuffered_query('SHOW TABLES')))
- {
- $db = array();
- while ($row = mysql_fetch_row($query))
- {
- $db[] = $row[0];
- }
-
- if (!in_array($this->options['prefix'][0] . 'cache_data', $db))
- {
- if (!mysql_query('CREATE TABLE `' . $this->options['prefix'][0] . 'cache_data` (`id` TEXT CHARACTER SET utf8 NOT NULL, `items` SMALLINT NOT NULL DEFAULT 0, `data` BLOB NOT NULL, `mtime` INT UNSIGNED NOT NULL, UNIQUE (`id`(125)))'))
- {
- $this->mysql = null;
- }
- }
-
- if (!in_array($this->options['prefix'][0] . 'items', $db))
- {
- if (!mysql_query('CREATE TABLE `' . $this->options['prefix'][0] . 'items` (`feed_id` TEXT CHARACTER SET utf8 NOT NULL, `id` TEXT CHARACTER SET utf8 NOT NULL, `data` TEXT CHARACTER SET utf8 NOT NULL, `posted` INT UNSIGNED NOT NULL, INDEX `feed_id` (`feed_id`(125)))'))
- {
- $this->mysql = null;
- }
- }
- }
- else
- {
- $this->mysql = null;
- }
- }
- }
-
- function save($data)
- {
- if ($this->mysql)
- {
- $feed_id = "'" . mysql_real_escape_string($this->id) . "'";
-
- if (is_a($data, 'SimplePie'))
- {
- if (SIMPLEPIE_PHP5)
- {
- // This keyword needs to defy coding standards for PHP4 compatibility
- $data = clone($data);
- }
-
- $prepared = $this->prepare_simplepie_object_for_cache($data);
-
- if ($query = mysql_query('SELECT `id` FROM `' . $this->options['prefix'][0] . 'cache_data` WHERE `id` = ' . $feed_id, $this->mysql))
- {
- if (mysql_num_rows($query))
- {
- $items = count($prepared[1]);
- if ($items)
- {
- $sql = 'UPDATE `' . $this->options['prefix'][0] . 'cache_data` SET `items` = ' . $items . ', `data` = \'' . mysql_real_escape_string($prepared[0]) . '\', `mtime` = ' . time() . ' WHERE `id` = ' . $feed_id;
- }
- else
- {
- $sql = 'UPDATE `' . $this->options['prefix'][0] . 'cache_data` SET `data` = \'' . mysql_real_escape_string($prepared[0]) . '\', `mtime` = ' . time() . ' WHERE `id` = ' . $feed_id;
- }
-
- if (!mysql_query($sql, $this->mysql))
- {
- return false;
- }
- }
- elseif (!mysql_query('INSERT INTO `' . $this->options['prefix'][0] . 'cache_data` (`id`, `items`, `data`, `mtime`) VALUES(' . $feed_id . ', ' . count($prepared[1]) . ', \'' . mysql_real_escape_string($prepared[0]) . '\', ' . time() . ')', $this->mysql))
- {
- return false;
- }
-
- $ids = array_keys($prepared[1]);
- if (!empty($ids))
- {
- foreach ($ids as $id)
- {
- $database_ids[] = mysql_real_escape_string($id);
- }
-
- if ($query = mysql_unbuffered_query('SELECT `id` FROM `' . $this->options['prefix'][0] . 'items` WHERE `id` = \'' . implode('\' OR `id` = \'', $database_ids) . '\' AND `feed_id` = ' . $feed_id, $this->mysql))
- {
- $existing_ids = array();
- while ($row = mysql_fetch_row($query))
- {
- $existing_ids[] = $row[0];
- }
-
- $new_ids = array_diff($ids, $existing_ids);
-
- foreach ($new_ids as $new_id)
- {
- if (!($date = $prepared[1][$new_id]->get_date('U')))
- {
- $date = time();
- }
-
- if (!mysql_query('INSERT INTO `' . $this->options['prefix'][0] . 'items` (`feed_id`, `id`, `data`, `posted`) VALUES(' . $feed_id . ', \'' . mysql_real_escape_string($new_id) . '\', \'' . mysql_real_escape_string(serialize($prepared[1][$new_id]->data)) . '\', ' . $date . ')', $this->mysql))
- {
- return false;
- }
- }
- return true;
- }
- }
- else
- {
- return true;
- }
- }
- }
- elseif ($query = mysql_query('SELECT `id` FROM `' . $this->options['prefix'][0] . 'cache_data` WHERE `id` = ' . $feed_id, $this->mysql))
- {
- if (mysql_num_rows($query))
- {
- if (mysql_query('UPDATE `' . $this->options['prefix'][0] . 'cache_data` SET `items` = 0, `data` = \'' . mysql_real_escape_string(serialize($data)) . '\', `mtime` = ' . time() . ' WHERE `id` = ' . $feed_id, $this->mysql))
- {
- return true;
- }
- }
- elseif (mysql_query('INSERT INTO `' . $this->options['prefix'][0] . 'cache_data` (`id`, `items`, `data`, `mtime`) VALUES(\'' . mysql_real_escape_string($this->id) . '\', 0, \'' . mysql_real_escape_string(serialize($data)) . '\', ' . time() . ')', $this->mysql))
- {
- return true;
- }
- }
- }
- return false;
- }
-
- function load()
- {
- if ($this->mysql && ($query = mysql_query('SELECT `items`, `data` FROM `' . $this->options['prefix'][0] . 'cache_data` WHERE `id` = \'' . mysql_real_escape_string($this->id) . "'", $this->mysql)) && ($row = mysql_fetch_row($query)))
- {
- $data = unserialize($row[1]);
-
- if (isset($this->options['items'][0]))
- {
- $items = (int) $this->options['items'][0];
- }
- else
- {
- $items = (int) $row[0];
- }
-
- if ($items !== 0)
- {
- if (isset($data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0]))
- {
- $feed =& $data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0];
- }
- elseif (isset($data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0]))
- {
- $feed =& $data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0];
- }
- elseif (isset($data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]))
- {
- $feed =& $data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0];
- }
- elseif (isset($data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]))
- {
- $feed =& $data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0];
- }
- else
- {
- $feed = null;
- }
-
- if ($feed !== null)
- {
- $sql = 'SELECT `data` FROM `' . $this->options['prefix'][0] . 'items` WHERE `feed_id` = \'' . mysql_real_escape_string($this->id) . '\' ORDER BY `posted` DESC';
- if ($items > 0)
- {
- $sql .= ' LIMIT ' . $items;
- }
-
- if ($query = mysql_unbuffered_query($sql, $this->mysql))
- {
- while ($row = mysql_fetch_row($query))
- {
- $feed['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['entry'][] = unserialize($row[0]);
- }
- }
- else
- {
- return false;
- }
- }
- }
- return $data;
- }
- return false;
- }
-
- function mtime()
- {
- if ($this->mysql && ($query = mysql_query('SELECT `mtime` FROM `' . $this->options['prefix'][0] . 'cache_data` WHERE `id` = \'' . mysql_real_escape_string($this->id) . "'", $this->mysql)) && ($row = mysql_fetch_row($query)))
- {
- return $row[0];
- }
- else
- {
- return false;
- }
- }
-
- function touch()
- {
- if ($this->mysql && ($query = mysql_query('UPDATE `' . $this->options['prefix'][0] . 'cache_data` SET `mtime` = ' . time() . ' WHERE `id` = \'' . mysql_real_escape_string($this->id) . "'", $this->mysql)) && mysql_affected_rows($this->mysql))
- {
- return true;
- }
- else
- {
- return false;
- }
- }
-
- function unlink()
- {
- if ($this->mysql && ($query = mysql_query('DELETE FROM `' . $this->options['prefix'][0] . 'cache_data` WHERE `id` = \'' . mysql_real_escape_string($this->id) . "'", $this->mysql)) && ($query2 = mysql_query('DELETE FROM `' . $this->options['prefix'][0] . 'items` WHERE `feed_id` = \'' . mysql_real_escape_string($this->id) . "'", $this->mysql)))
- {
- return true;
- }
- else
- {
- return false;
- }
- }
-}
-
-class SimplePie_Misc
-{
- function time_hms($seconds)
- {
- $time = '';
-
- $hours = floor($seconds / 3600);
- $remainder = $seconds % 3600;
- if ($hours > 0)
- {
- $time .= $hours.':';
- }
-
- $minutes = floor($remainder / 60);
- $seconds = $remainder % 60;
- if ($minutes < 10 && $hours > 0)
- {
- $minutes = '0' . $minutes;
- }
- if ($seconds < 10)
- {
- $seconds = '0' . $seconds;
- }
-
- $time .= $minutes.':';
- $time .= $seconds;
-
- return $time;
- }
-
- function absolutize_url($relative, $base)
- {
-return $relative;
- $iri = SimplePie_IRI::absolutize(new SimplePie_IRI($base), $relative);
- return $iri->get_iri();
- }
-
- function remove_dot_segments($input)
- {
- $output = '';
- while (strpos($input, './') !== false || strpos($input, '/.') !== false || $input === '.' || $input === '..')
- {
- // A: If the input buffer begins with a prefix of "../" or "./", then remove that prefix from the input buffer; otherwise,
- if (strpos($input, '../') === 0)
- {
- $input = substr($input, 3);
- }
- elseif (strpos($input, './') === 0)
- {
- $input = substr($input, 2);
- }
- // B: if the input buffer begins with a prefix of "/./" or "/.", where "." is a complete path segment, then replace that prefix with "/" in the input buffer; otherwise,
- elseif (strpos($input, '/./') === 0)
- {
- $input = substr_replace($input, '/', 0, 3);
- }
- elseif ($input === '/.')
- {
- $input = '/';
- }
- // C: if the input buffer begins with a prefix of "/../" or "/..", where ".." is a complete path segment, then replace that prefix with "/" in the input buffer and remove the last segment and its preceding "/" (if any) from the output buffer; otherwise,
- elseif (strpos($input, '/../') === 0)
- {
- $input = substr_replace($input, '/', 0, 4);
- $output = substr_replace($output, '', strrpos($output, '/'));
- }
- elseif ($input === '/..')
- {
- $input = '/';
- $output = substr_replace($output, '', strrpos($output, '/'));
- }
- // D: if the input buffer consists only of "." or "..", then remove that from the input buffer; otherwise,
- elseif ($input === '.' || $input === '..')
- {
- $input = '';
- }
- // E: move the first path segment in the input buffer to the end of the output buffer, including the initial "/" character (if any) and any subsequent characters up to, but not including, the next "/" character or the end of the input buffer
- elseif (($pos = strpos($input, '/', 1)) !== false)
- {
- $output .= substr($input, 0, $pos);
- $input = substr_replace($input, '', 0, $pos);
- }
- else
- {
- $output .= $input;
- $input = '';
- }
- }
- return $output . $input;
- }
-
- function get_element($realname, $string)
- {
- $return = array();
- $name = preg_quote($realname, '/');
- if (preg_match_all("/<($name)" . SIMPLEPIE_PCRE_HTML_ATTRIBUTE . "(>(.*)<\/$name>|(\/)?>)/siU", $string, $matches, PREG_SET_ORDER | PREG_OFFSET_CAPTURE))
- {
- for ($i = 0, $total_matches = count($matches); $i < $total_matches; $i++)
- {
- $return[$i]['tag'] = $realname;
- $return[$i]['full'] = $matches[$i][0][0];
- $return[$i]['offset'] = $matches[$i][0][1];
- if (strlen($matches[$i][3][0]) <= 2)
- {
- $return[$i]['self_closing'] = true;
- }
- else
- {
- $return[$i]['self_closing'] = false;
- $return[$i]['content'] = $matches[$i][4][0];
- }
- $return[$i]['attribs'] = array();
- if (isset($matches[$i][2][0]) && preg_match_all('/[\x09\x0A\x0B\x0C\x0D\x20]+([^\x09\x0A\x0B\x0C\x0D\x20\x2F\x3E][^\x09\x0A\x0B\x0C\x0D\x20\x2F\x3D\x3E]*)(?:[\x09\x0A\x0B\x0C\x0D\x20]*=[\x09\x0A\x0B\x0C\x0D\x20]*(?:"([^"]*)"|\'([^\']*)\'|([^\x09\x0A\x0B\x0C\x0D\x20\x22\x27\x3E][^\x09\x0A\x0B\x0C\x0D\x20\x3E]*)?))?/', ' ' . $matches[$i][2][0] . ' ', $attribs, PREG_SET_ORDER))
- {
- for ($j = 0, $total_attribs = count($attribs); $j < $total_attribs; $j++)
- {
- if (count($attribs[$j]) === 2)
- {
- $attribs[$j][2] = $attribs[$j][1];
- }
- $return[$i]['attribs'][strtolower($attribs[$j][1])]['data'] = SimplePie_Misc::entities_decode(end($attribs[$j]), 'UTF-8');
- }
- }
- }
- }
- return $return;
- }
-
- function element_implode($element)
- {
- $full = "<$element[tag]";
- foreach ($element['attribs'] as $key => $value)
- {
- $key = strtolower($key);
- $full .= " $key=\"" . htmlspecialchars($value['data']) . '"';
- }
- if ($element['self_closing'])
- {
- $full .= ' />';
- }
- else
- {
- $full .= ">$element[content]</$element[tag]>";
- }
- return $full;
- }
-
- function error($message, $level, $file, $line)
- {
- if ((ini_get('error_reporting') & $level) > 0)
- {
- switch ($level)
- {
- case E_USER_ERROR:
- $note = 'PHP Error';
- break;
- case E_USER_WARNING:
- $note = 'PHP Warning';
- break;
- case E_USER_NOTICE:
- $note = 'PHP Notice';
- break;
- default:
- $note = 'Unknown Error';
- break;
- }
-
- $log_error = true;
- if (!function_exists('error_log'))
- {
- $log_error = false;
- }
-
- $log_file = @ini_get('error_log');
- if (!empty($log_file) && ('syslog' != $log_file) && !@is_writable($log_file))
- {
- $log_error = false;
- }
-
- if ($log_error)
- {
- @error_log("$note: $message in $file on line $line", 0);
- }
- }
-
- return $message;
- }
-
- /**
- * If a file has been cached, retrieve and display it.
- *
- * This is most useful for caching images (get_favicon(), etc.),
- * however it works for all cached files. This WILL NOT display ANY
- * file/image/page/whatever, but rather only display what has already
- * been cached by SimplePie.
- *
- * @access public
- * @see SimplePie::get_favicon()
- * @param str $identifier_url URL that is used to identify the content.
- * This may or may not be the actual URL of the live content.
- * @param str $cache_location Location of SimplePie's cache. Defaults
- * to './cache'.
- * @param str $cache_extension The file extension that the file was
- * cached with. Defaults to 'spc'.
- * @param str $cache_class Name of the cache-handling class being used
- * in SimplePie. Defaults to 'SimplePie_Cache', and should be left
- * as-is unless you've overloaded the class.
- * @param str $cache_name_function Obsolete. Exists for backwards
- * compatibility reasons only.
- */
- function display_cached_file($identifier_url, $cache_location = './cache', $cache_extension = 'spc', $cache_class = 'SimplePie_Cache', $cache_name_function = 'md5')
- {
- $cache = call_user_func(array($cache_class, 'create'), $cache_location, $identifier_url, $cache_extension);
-
- if ($file = $cache->load())
- {
- if (isset($file['headers']['content-type']))
- {
- header('Content-type:' . $file['headers']['content-type']);
- }
- else
- {
- header('Content-type: application/octet-stream');
- }
- header('Expires: ' . gmdate('D, d M Y H:i:s', time() + 604800) . ' GMT'); // 7 days
- echo $file['body'];
- exit;
- }
-
- die('Cached file for ' . $identifier_url . ' cannot be found.');
- }
-
- function fix_protocol($url, $http = 1)
- {
- $url = SimplePie_Misc::normalize_url($url);
- $parsed = SimplePie_Misc::parse_url($url);
- if ($parsed['scheme'] !== '' && $parsed['scheme'] !== 'http' && $parsed['scheme'] !== 'https')
- {
- return SimplePie_Misc::fix_protocol(SimplePie_Misc::compress_parse_url('http', $parsed['authority'], $parsed['path'], $parsed['query'], $parsed['fragment']), $http);
- }
-
- if ($parsed['scheme'] === '' && $parsed['authority'] === '' && !file_exists($url))
- {
- return SimplePie_Misc::fix_protocol(SimplePie_Misc::compress_parse_url('http', $parsed['path'], '', $parsed['query'], $parsed['fragment']), $http);
- }
-
- if ($http === 2 && $parsed['scheme'] !== '')
- {
- return "feed:$url";
- }
- elseif ($http === 3 && strtolower($parsed['scheme']) === 'http')
- {
- return substr_replace($url, 'podcast', 0, 4);
- }
- elseif ($http === 4 && strtolower($parsed['scheme']) === 'http')
- {
- return substr_replace($url, 'itpc', 0, 4);
- }
- else
- {
- return $url;
- }
- }
-
- function parse_url($url)
- {
- $iri = new SimplePie_IRI($url);
- return array(
- 'scheme' => (string) $iri->get_scheme(),
- 'authority' => (string) $iri->get_authority(),
- 'path' => (string) $iri->get_path(),
- 'query' => (string) $iri->get_query(),
- 'fragment' => (string) $iri->get_fragment()
- );
- }
-
- function compress_parse_url($scheme = '', $authority = '', $path = '', $query = '', $fragment = '')
- {
- $iri = new SimplePie_IRI('');
- $iri->set_scheme($scheme);
- $iri->set_authority($authority);
- $iri->set_path($path);
- $iri->set_query($query);
- $iri->set_fragment($fragment);
- return $iri->get_iri();
- }
-
- function normalize_url($url)
- {
- $iri = new SimplePie_IRI($url);
- return $iri->get_iri();
- }
-
- function percent_encoding_normalization($match)
- {
- $integer = hexdec($match[1]);
- if ($integer >= 0x41 && $integer <= 0x5A || $integer >= 0x61 && $integer <= 0x7A || $integer >= 0x30 && $integer <= 0x39 || $integer === 0x2D || $integer === 0x2E || $integer === 0x5F || $integer === 0x7E)
- {
- return chr($integer);
- }
- else
- {
- return strtoupper($match[0]);
- }
- }
-
- /**
- * Remove bad UTF-8 bytes
- *
- * PCRE Pattern to locate bad bytes in a UTF-8 string comes from W3C
- * FAQ: Multilingual Forms (modified to include full ASCII range)
- *
- * @author Geoffrey Sneddon
- * @see http://www.w3.org/International/questions/qa-forms-utf-8
- * @param string $str String to remove bad UTF-8 bytes from
- * @return string UTF-8 string
- */
- function utf8_bad_replace($str)
- {
- if (function_exists('iconv') && ($return = @iconv('UTF-8', 'UTF-8//IGNORE', $str)))
- {
- return $return;
- }
- elseif (function_exists('mb_convert_encoding') && ($return = @mb_convert_encoding($str, 'UTF-8', 'UTF-8')))
- {
- return $return;
- }
- elseif (preg_match_all('/(?:[\x00-\x7F]|[\xC2-\xDF][\x80-\xBF]|\xE0[\xA0-\xBF][\x80-\xBF]|[\xE1-\xEC\xEE\xEF][\x80-\xBF]{2}|\xED[\x80-\x9F][\x80-\xBF]|\xF0[\x90-\xBF][\x80-\xBF]{2}|[\xF1-\xF3][\x80-\xBF]{3}|\xF4[\x80-\x8F][\x80-\xBF]{2})+/', $str, $matches))
- {
- return implode("\xEF\xBF\xBD", $matches[0]);
- }
- elseif ($str !== '')
- {
- return "\xEF\xBF\xBD";
- }
- else
- {
- return '';
- }
- }
-
- /**
- * Converts a Windows-1252 encoded string to a UTF-8 encoded string
- *
- * @static
- * @access public
- * @param string $string Windows-1252 encoded string
- * @return string UTF-8 encoded string
- */
- function windows_1252_to_utf8($string)
- {
- static $convert_table = array("\x80" => "\xE2\x82\xAC", "\x81" => "\xEF\xBF\xBD", "\x82" => "\xE2\x80\x9A", "\x83" => "\xC6\x92", "\x84" => "\xE2\x80\x9E", "\x85" => "\xE2\x80\xA6", "\x86" => "\xE2\x80\xA0", "\x87" => "\xE2\x80\xA1", "\x88" => "\xCB\x86", "\x89" => "\xE2\x80\xB0", "\x8A" => "\xC5\xA0", "\x8B" => "\xE2\x80\xB9", "\x8C" => "\xC5\x92", "\x8D" => "\xEF\xBF\xBD", "\x8E" => "\xC5\xBD", "\x8F" => "\xEF\xBF\xBD", "\x90" => "\xEF\xBF\xBD", "\x91" => "\xE2\x80\x98", "\x92" => "\xE2\x80\x99", "\x93" => "\xE2\x80\x9C", "\x94" => "\xE2\x80\x9D", "\x95" => "\xE2\x80\xA2", "\x96" => "\xE2\x80\x93", "\x97" => "\xE2\x80\x94", "\x98" => "\xCB\x9C", "\x99" => "\xE2\x84\xA2", "\x9A" => "\xC5\xA1", "\x9B" => "\xE2\x80\xBA", "\x9C" => "\xC5\x93", "\x9D" => "\xEF\xBF\xBD", "\x9E" => "\xC5\xBE", "\x9F" => "\xC5\xB8", "\xA0" => "\xC2\xA0", "\xA1" => "\xC2\xA1", "\xA2" => "\xC2\xA2", "\xA3" => "\xC2\xA3", "\xA4" => "\xC2\xA4", "\xA5" => "\xC2\xA5", "\xA6" => "\xC2\xA6", "\xA7" => "\xC2\xA7", "\xA8" => "\xC2\xA8", "\xA9" => "\xC2\xA9", "\xAA" => "\xC2\xAA", "\xAB" => "\xC2\xAB", "\xAC" => "\xC2\xAC", "\xAD" => "\xC2\xAD", "\xAE" => "\xC2\xAE", "\xAF" => "\xC2\xAF", "\xB0" => "\xC2\xB0", "\xB1" => "\xC2\xB1", "\xB2" => "\xC2\xB2", "\xB3" => "\xC2\xB3", "\xB4" => "\xC2\xB4", "\xB5" => "\xC2\xB5", "\xB6" => "\xC2\xB6", "\xB7" => "\xC2\xB7", "\xB8" => "\xC2\xB8", "\xB9" => "\xC2\xB9", "\xBA" => "\xC2\xBA", "\xBB" => "\xC2\xBB", "\xBC" => "\xC2\xBC", "\xBD" => "\xC2\xBD", "\xBE" => "\xC2\xBE", "\xBF" => "\xC2\xBF", "\xC0" => "\xC3\x80", "\xC1" => "\xC3\x81", "\xC2" => "\xC3\x82", "\xC3" => "\xC3\x83", "\xC4" => "\xC3\x84", "\xC5" => "\xC3\x85", "\xC6" => "\xC3\x86", "\xC7" => "\xC3\x87", "\xC8" => "\xC3\x88", "\xC9" => "\xC3\x89", "\xCA" => "\xC3\x8A", "\xCB" => "\xC3\x8B", "\xCC" => "\xC3\x8C", "\xCD" => "\xC3\x8D", "\xCE" => "\xC3\x8E", "\xCF" => "\xC3\x8F", "\xD0" => "\xC3\x90", "\xD1" => "\xC3\x91", "\xD2" => "\xC3\x92", "\xD3" => "\xC3\x93", "\xD4" => "\xC3\x94", "\xD5" => "\xC3\x95", "\xD6" => "\xC3\x96", "\xD7" => "\xC3\x97", "\xD8" => "\xC3\x98", "\xD9" => "\xC3\x99", "\xDA" => "\xC3\x9A", "\xDB" => "\xC3\x9B", "\xDC" => "\xC3\x9C", "\xDD" => "\xC3\x9D", "\xDE" => "\xC3\x9E", "\xDF" => "\xC3\x9F", "\xE0" => "\xC3\xA0", "\xE1" => "\xC3\xA1", "\xE2" => "\xC3\xA2", "\xE3" => "\xC3\xA3", "\xE4" => "\xC3\xA4", "\xE5" => "\xC3\xA5", "\xE6" => "\xC3\xA6", "\xE7" => "\xC3\xA7", "\xE8" => "\xC3\xA8", "\xE9" => "\xC3\xA9", "\xEA" => "\xC3\xAA", "\xEB" => "\xC3\xAB", "\xEC" => "\xC3\xAC", "\xED" => "\xC3\xAD", "\xEE" => "\xC3\xAE", "\xEF" => "\xC3\xAF", "\xF0" => "\xC3\xB0", "\xF1" => "\xC3\xB1", "\xF2" => "\xC3\xB2", "\xF3" => "\xC3\xB3", "\xF4" => "\xC3\xB4", "\xF5" => "\xC3\xB5", "\xF6" => "\xC3\xB6", "\xF7" => "\xC3\xB7", "\xF8" => "\xC3\xB8", "\xF9" => "\xC3\xB9", "\xFA" => "\xC3\xBA", "\xFB" => "\xC3\xBB", "\xFC" => "\xC3\xBC", "\xFD" => "\xC3\xBD", "\xFE" => "\xC3\xBE", "\xFF" => "\xC3\xBF");
-
- return strtr($string, $convert_table);
- }
-
- function change_encoding($data, $input, $output)
- {
- $input = SimplePie_Misc::encoding($input);
- $output = SimplePie_Misc::encoding($output);
-
- // We fail to fail on non US-ASCII bytes
- if ($input === 'US-ASCII')
- {
- static $non_ascii_octects = '';
- if (!$non_ascii_octects)
- {
- for ($i = 0x80; $i <= 0xFF; $i++)
- {
- $non_ascii_octects .= chr($i);
- }
- }
- $data = substr($data, 0, strcspn($data, $non_ascii_octects));
- }
-
- // This is first, as behaviour of this is completely predictable
- if ($input === 'Windows-1252' && $output === 'UTF-8')
- {
- return SimplePie_Misc::windows_1252_to_utf8($data);
- }
- // This is second, as behaviour of this varies only with PHP version (the middle part of this expression checks the encoding is supported).
- elseif (function_exists('mb_convert_encoding') && @mb_convert_encoding("\x80", 'UTF-16BE', $input) !== "\x00\x80" && ($return = @mb_convert_encoding($data, $output, $input)))
- {
- return $return;
- }
- // This is last, as behaviour of this varies with OS userland and PHP version
- elseif (function_exists('iconv') && ($return = @iconv($input, $output, $data)))
- {
- return $return;
- }
- // If we can't do anything, just fail
- else
- {
- return false;
- }
- }
-
- function encoding($charset)
- {
- // Normalization from UTS #22
- switch (strtolower(preg_replace('/(?:[^a-zA-Z0-9]+|([^0-9])0+)/', '\1', $charset)))
- {
- case 'adobestandardencoding':
- case 'csadobestandardencoding':
- return 'Adobe-Standard-Encoding';
-
- case 'adobesymbolencoding':
- case 'cshppsmath':
- return 'Adobe-Symbol-Encoding';
-
- case 'ami1251':
- case 'amiga1251':
- return 'Amiga-1251';
-
- case 'ansix31101983':
- case 'csat5001983':
- case 'csiso99naplps':
- case 'isoir99':
- case 'naplps':
- return 'ANSI_X3.110-1983';
-
- case 'arabic7':
- case 'asmo449':
- case 'csiso89asmo449':
- case 'iso9036':
- case 'isoir89':
- return 'ASMO_449';
-
- case 'big5':
- case 'csbig5':
- case 'xxbig5':
- return 'Big5';
-
- case 'big5hkscs':
- return 'Big5-HKSCS';
-
- case 'bocu1':
- case 'csbocu1':
- return 'BOCU-1';
-
- case 'brf':
- case 'csbrf':
- return 'BRF';
-
- case 'bs4730':
- case 'csiso4unitedkingdom':
- case 'gb':
- case 'iso646gb':
- case 'isoir4':
- case 'uk':
- return 'BS_4730';
-
- case 'bsviewdata':
- case 'csiso47bsviewdata':
- case 'isoir47':
- return 'BS_viewdata';
-
- case 'cesu8':
- case 'cscesu8':
- return 'CESU-8';
-
- case 'ca':
- case 'csa71':
- case 'csaz243419851':
- case 'csiso121canadian1':
- case 'iso646ca':
- case 'isoir121':
- return 'CSA_Z243.4-1985-1';
-
- case 'csa72':
- case 'csaz243419852':
- case 'csiso122canadian2':
- case 'iso646ca2':
- case 'isoir122':
- return 'CSA_Z243.4-1985-2';
-
- case 'csaz24341985gr':
- case 'csiso123csaz24341985gr':
- case 'isoir123':
- return 'CSA_Z243.4-1985-gr';
-
- case 'csiso139csn369103':
- case 'csn369103':
- case 'isoir139':
- return 'CSN_369103';
-
- case 'csdecmcs':
- case 'dec':
- case 'decmcs':
- return 'DEC-MCS';
-
- case 'csiso21german':
- case 'de':
- case 'din66003':
- case 'iso646de':
- case 'isoir21':
- return 'DIN_66003';
-
- case 'csdkus':
- case 'dkus':
- return 'dk-us';
-
- case 'csiso646danish':
- case 'dk':
- case 'ds2089':
- case 'iso646dk':
- return 'DS_2089';
-
- case 'csibmebcdicatde':
- case 'ebcdicatde':
- return 'EBCDIC-AT-DE';
-
- case 'csebcdicatdea':
- case 'ebcdicatdea':
- return 'EBCDIC-AT-DE-A';
-
- case 'csebcdiccafr':
- case 'ebcdiccafr':
- return 'EBCDIC-CA-FR';
-
- case 'csebcdicdkno':
- case 'ebcdicdkno':
- return 'EBCDIC-DK-NO';
-
- case 'csebcdicdknoa':
- case 'ebcdicdknoa':
- return 'EBCDIC-DK-NO-A';
-
- case 'csebcdices':
- case 'ebcdices':
- return 'EBCDIC-ES';
-
- case 'csebcdicesa':
- case 'ebcdicesa':
- return 'EBCDIC-ES-A';
-
- case 'csebcdicess':
- case 'ebcdicess':
- return 'EBCDIC-ES-S';
-
- case 'csebcdicfise':
- case 'ebcdicfise':
- return 'EBCDIC-FI-SE';
-
- case 'csebcdicfisea':
- case 'ebcdicfisea':
- return 'EBCDIC-FI-SE-A';
-
- case 'csebcdicfr':
- case 'ebcdicfr':
- return 'EBCDIC-FR';
-
- case 'csebcdicit':
- case 'ebcdicit':
- return 'EBCDIC-IT';
-
- case 'csebcdicpt':
- case 'ebcdicpt':
- return 'EBCDIC-PT';
-
- case 'csebcdicuk':
- case 'ebcdicuk':
- return 'EBCDIC-UK';
-
- case 'csebcdicus':
- case 'ebcdicus':
- return 'EBCDIC-US';
-
- case 'csiso111ecmacyrillic':
- case 'ecmacyrillic':
- case 'isoir111':
- case 'koi8e':
- return 'ECMA-cyrillic';
-
- case 'csiso17spanish':
- case 'es':
- case 'iso646es':
- case 'isoir17':
- return 'ES';
-
- case 'csiso85spanish2':
- case 'es2':
- case 'iso646es2':
- case 'isoir85':
- return 'ES2';
-
- case 'cseucfixwidjapanese':
- case 'extendedunixcodefixedwidthforjapanese':
- return 'Extended_UNIX_Code_Fixed_Width_for_Japanese';
-
- case 'cseucpkdfmtjapanese':
- case 'eucjp':
- case 'extendedunixcodepackedformatforjapanese':
- return 'Extended_UNIX_Code_Packed_Format_for_Japanese';
-
- case 'gb18030':
- return 'GB18030';
-
- case 'chinese':
- case 'cp936':
- case 'csgb2312':
- case 'csiso58gb231280':
- case 'gb2312':
- case 'gb231280':
- case 'gbk':
- case 'isoir58':
- case 'ms936':
- case 'windows936':
- return 'GBK';
-
- case 'cn':
- case 'csiso57gb1988':
- case 'gb198880':
- case 'iso646cn':
- case 'isoir57':
- return 'GB_1988-80';
-
- case 'csiso153gost1976874':
- case 'gost1976874':
- case 'isoir153':
- case 'stsev35888':
- return 'GOST_19768-74';
-
- case 'csiso150':
- case 'csiso150greekccitt':
- case 'greekccitt':
- case 'isoir150':
- return 'greek-ccitt';
-
- case 'csiso88greek7':
- case 'greek7':
- case 'isoir88':
- return 'greek7';
-
- case 'csiso18greek7old':
- case 'greek7old':
- case 'isoir18':
- return 'greek7-old';
-
- case 'cshpdesktop':
- case 'hpdesktop':
- return 'HP-DeskTop';
-
- case 'cshplegal':
- case 'hplegal':
- return 'HP-Legal';
-
- case 'cshpmath8':
- case 'hpmath8':
- return 'HP-Math8';
-
- case 'cshppifont':
- case 'hppifont':
- return 'HP-Pi-font';
-
- case 'cshproman8':
- case 'hproman8':
- case 'r8':
- case 'roman8':
- return 'hp-roman8';
-
- case 'hzgb2312':
- return 'HZ-GB-2312';
-
- case 'csibmsymbols':
- case 'ibmsymbols':
- return 'IBM-Symbols';
-
- case 'csibmthai':
- case 'ibmthai':
- return 'IBM-Thai';
-
- case 'ccsid858':
- case 'cp858':
- case 'ibm858':
- case 'pcmultilingual850euro':
- return 'IBM00858';
-
- case 'ccsid924':
- case 'cp924':
- case 'ebcdiclatin9euro':
- case 'ibm924':
- return 'IBM00924';
-
- case 'ccsid1140':
- case 'cp1140':
- case 'ebcdicus37euro':
- case 'ibm1140':
- return 'IBM01140';
-
- case 'ccsid1141':
- case 'cp1141':
- case 'ebcdicde273euro':
- case 'ibm1141':
- return 'IBM01141';
-
- case 'ccsid1142':
- case 'cp1142':
- case 'ebcdicdk277euro':
- case 'ebcdicno277euro':
- case 'ibm1142':
- return 'IBM01142';
-
- case 'ccsid1143':
- case 'cp1143':
- case 'ebcdicfi278euro':
- case 'ebcdicse278euro':
- case 'ibm1143':
- return 'IBM01143';
-
- case 'ccsid1144':
- case 'cp1144':
- case 'ebcdicit280euro':
- case 'ibm1144':
- return 'IBM01144';
-
- case 'ccsid1145':
- case 'cp1145':
- case 'ebcdices284euro':
- case 'ibm1145':
- return 'IBM01145';
-
- case 'ccsid1146':
- case 'cp1146':
- case 'ebcdicgb285euro':
- case 'ibm1146':
- return 'IBM01146';
-
- case 'ccsid1147':
- case 'cp1147':
- case 'ebcdicfr297euro':
- case 'ibm1147':
- return 'IBM01147';
-
- case 'ccsid1148':
- case 'cp1148':
- case 'ebcdicinternational500euro':
- case 'ibm1148':
- return 'IBM01148';
-
- case 'ccsid1149':
- case 'cp1149':
- case 'ebcdicis871euro':
- case 'ibm1149':
- return 'IBM01149';
-
- case 'cp37':
- case 'csibm37':
- case 'ebcdiccpca':
- case 'ebcdiccpnl':
- case 'ebcdiccpus':
- case 'ebcdiccpwt':
- case 'ibm37':
- return 'IBM037';
-
- case 'cp38':
- case 'csibm38':
- case 'ebcdicint':
- case 'ibm38':
- return 'IBM038';
-
- case 'cp273':
- case 'csibm273':
- case 'ibm273':
- return 'IBM273';
-
- case 'cp274':
- case 'csibm274':
- case 'ebcdicbe':
- case 'ibm274':
- return 'IBM274';
-
- case 'cp275':
- case 'csibm275':
- case 'ebcdicbr':
- case 'ibm275':
- return 'IBM275';
-
- case 'csibm277':
- case 'ebcdiccpdk':
- case 'ebcdiccpno':
- case 'ibm277':
- return 'IBM277';
-
- case 'cp278':
- case 'csibm278':
- case 'ebcdiccpfi':
- case 'ebcdiccpse':
- case 'ibm278':
- return 'IBM278';
-
- case 'cp280':
- case 'csibm280':
- case 'ebcdiccpit':
- case 'ibm280':
- return 'IBM280';
-
- case 'cp281':
- case 'csibm281':
- case 'ebcdicjpe':
- case 'ibm281':
- return 'IBM281';
-
- case 'cp284':
- case 'csibm284':
- case 'ebcdiccpes':
- case 'ibm284':
- return 'IBM284';
-
- case 'cp285':
- case 'csibm285':
- case 'ebcdiccpgb':
- case 'ibm285':
- return 'IBM285';
-
- case 'cp290':
- case 'csibm290':
- case 'ebcdicjpkana':
- case 'ibm290':
- return 'IBM290';
-
- case 'cp297':
- case 'csibm297':
- case 'ebcdiccpfr':
- case 'ibm297':
- return 'IBM297';
-
- case 'cp420':
- case 'csibm420':
- case 'ebcdiccpar1':
- case 'ibm420':
- return 'IBM420';
-
- case 'cp423':
- case 'csibm423':
- case 'ebcdiccpgr':
- case 'ibm423':
- return 'IBM423';
-
- case 'cp424':
- case 'csibm424':
- case 'ebcdiccphe':
- case 'ibm424':
- return 'IBM424';
-
- case '437':
- case 'cp437':
- case 'cspc8codepage437':
- case 'ibm437':
- return 'IBM437';
-
- case 'cp500':
- case 'csibm500':
- case 'ebcdiccpbe':
- case 'ebcdiccpch':
- case 'ibm500':
- return 'IBM500';
-
- case 'cp775':
- case 'cspc775baltic':
- case 'ibm775':
- return 'IBM775';
-
- case '850':
- case 'cp850':
- case 'cspc850multilingual':
- case 'ibm850':
- return 'IBM850';
-
- case '851':
- case 'cp851':
- case 'csibm851':
- case 'ibm851':
- return 'IBM851';
-
- case '852':
- case 'cp852':
- case 'cspcp852':
- case 'ibm852':
- return 'IBM852';
-
- case '855':
- case 'cp855':
- case 'csibm855':
- case 'ibm855':
- return 'IBM855';
-
- case '857':
- case 'cp857':
- case 'csibm857':
- case 'ibm857':
- return 'IBM857';
-
- case '860':
- case 'cp860':
- case 'csibm860':
- case 'ibm860':
- return 'IBM860';
-
- case '861':
- case 'cp861':
- case 'cpis':
- case 'csibm861':
- case 'ibm861':
- return 'IBM861';
-
- case '862':
- case 'cp862':
- case 'cspc862latinhebrew':
- case 'ibm862':
- return 'IBM862';
-
- case '863':
- case 'cp863':
- case 'csibm863':
- case 'ibm863':
- return 'IBM863';
-
- case 'cp864':
- case 'csibm864':
- case 'ibm864':
- return 'IBM864';
-
- case '865':
- case 'cp865':
- case 'csibm865':
- case 'ibm865':
- return 'IBM865';
-
- case '866':
- case 'cp866':
- case 'csibm866':
- case 'ibm866':
- return 'IBM866';
-
- case 'cp868':
- case 'cpar':
- case 'csibm868':
- case 'ibm868':
- return 'IBM868';
-
- case '869':
- case 'cp869':
- case 'cpgr':
- case 'csibm869':
- case 'ibm869':
- return 'IBM869';
-
- case 'cp870':
- case 'csibm870':
- case 'ebcdiccproece':
- case 'ebcdiccpyu':
- case 'ibm870':
- return 'IBM870';
-
- case 'cp871':
- case 'csibm871':
- case 'ebcdiccpis':
- case 'ibm871':
- return 'IBM871';
-
- case 'cp880':
- case 'csibm880':
- case 'ebcdiccyrillic':
- case 'ibm880':
- return 'IBM880';
-
- case 'cp891':
- case 'csibm891':
- case 'ibm891':
- return 'IBM891';
-
- case 'cp903':
- case 'csibm903':
- case 'ibm903':
- return 'IBM903';
-
- case '904':
- case 'cp904':
- case 'csibbm904':
- case 'ibm904':
- return 'IBM904';
-
- case 'cp905':
- case 'csibm905':
- case 'ebcdiccptr':
- case 'ibm905':
- return 'IBM905';
-
- case 'cp918':
- case 'csibm918':
- case 'ebcdiccpar2':
- case 'ibm918':
- return 'IBM918';
-
- case 'cp1026':
- case 'csibm1026':
- case 'ibm1026':
- return 'IBM1026';
-
- case 'ibm1047':
- return 'IBM1047';
-
- case 'csiso143iecp271':
- case 'iecp271':
- case 'isoir143':
- return 'IEC_P27-1';
-
- case 'csiso49inis':
- case 'inis':
- case 'isoir49':
- return 'INIS';
-
- case 'csiso50inis8':
- case 'inis8':
- case 'isoir50':
- return 'INIS-8';
-
- case 'csiso51iniscyrillic':
- case 'iniscyrillic':
- case 'isoir51':
- return 'INIS-cyrillic';
-
- case 'csinvariant':
- case 'invariant':
- return 'INVARIANT';
-
- case 'iso2022cn':
- return 'ISO-2022-CN';
-
- case 'iso2022cnext':
- return 'ISO-2022-CN-EXT';
-
- case 'csiso2022jp':
- case 'iso2022jp':
- return 'ISO-2022-JP';
-
- case 'csiso2022jp2':
- case 'iso2022jp2':
- return 'ISO-2022-JP-2';
-
- case 'csiso2022kr':
- case 'iso2022kr':
- return 'ISO-2022-KR';
-
- case 'cswindows30latin1':
- case 'iso88591windows30latin1':
- return 'ISO-8859-1-Windows-3.0-Latin-1';
-
- case 'cswindows31latin1':
- case 'iso88591windows31latin1':
- return 'ISO-8859-1-Windows-3.1-Latin-1';
-
- case 'csisolatin2':
- case 'iso88592':
- case 'iso885921987':
- case 'isoir101':
- case 'l2':
- case 'latin2':
- return 'ISO-8859-2';
-
- case 'cswindows31latin2':
- case 'iso88592windowslatin2':
- return 'ISO-8859-2-Windows-Latin-2';
-
- case 'csisolatin3':
- case 'iso88593':
- case 'iso885931988':
- case 'isoir109':
- case 'l3':
- case 'latin3':
- return 'ISO-8859-3';
-
- case 'csisolatin4':
- case 'iso88594':
- case 'iso885941988':
- case 'isoir110':
- case 'l4':
- case 'latin4':
- return 'ISO-8859-4';
-
- case 'csisolatincyrillic':
- case 'cyrillic':
- case 'iso88595':
- case 'iso885951988':
- case 'isoir144':
- return 'ISO-8859-5';
-
- case 'arabic':
- case 'asmo708':
- case 'csisolatinarabic':
- case 'ecma114':
- case 'iso88596':
- case 'iso885961987':
- case 'isoir127':
- return 'ISO-8859-6';
-
- case 'csiso88596e':
- case 'iso88596e':
- return 'ISO-8859-6-E';
-
- case 'csiso88596i':
- case 'iso88596i':
- return 'ISO-8859-6-I';
-
- case 'csisolatingreek':
- case 'ecma118':
- case 'elot928':
- case 'greek':
- case 'greek8':
- case 'iso88597':
- case 'iso885971987':
- case 'isoir126':
- return 'ISO-8859-7';
-
- case 'csisolatinhebrew':
- case 'hebrew':
- case 'iso88598':
- case 'iso885981988':
- case 'isoir138':
- return 'ISO-8859-8';
-
- case 'csiso88598e':
- case 'iso88598e':
- return 'ISO-8859-8-E';
-
- case 'csiso88598i':
- case 'iso88598i':
- return 'ISO-8859-8-I';
-
- case 'cswindows31latin5':
- case 'iso88599windowslatin5':
- return 'ISO-8859-9-Windows-Latin-5';
-
- case 'csisolatin6':
- case 'iso885910':
- case 'iso8859101992':
- case 'isoir157':
- case 'l6':
- case 'latin6':
- return 'ISO-8859-10';
-
- case 'iso885913':
- return 'ISO-8859-13';
-
- case 'iso885914':
- case 'iso8859141998':
- case 'isoceltic':
- case 'isoir199':
- case 'l8':
- case 'latin8':
- return 'ISO-8859-14';
-
- case 'iso885915':
- case 'latin9':
- return 'ISO-8859-15';
-
- case 'iso885916':
- case 'iso8859162001':
- case 'isoir226':
- case 'l10':
- case 'latin10':
- return 'ISO-8859-16';
-
- case 'iso10646j1':
- return 'ISO-10646-J-1';
-
- case 'csunicode':
- case 'iso10646ucs2':
- return 'ISO-10646-UCS-2';
-
- case 'csucs4':
- case 'iso10646ucs4':
- return 'ISO-10646-UCS-4';
-
- case 'csunicodeascii':
- case 'iso10646ucsbasic':
- return 'ISO-10646-UCS-Basic';
-
- case 'csunicodelatin1':
- case 'iso10646':
- case 'iso10646unicodelatin1':
- return 'ISO-10646-Unicode-Latin1';
-
- case 'csiso10646utf1':
- case 'iso10646utf1':
- return 'ISO-10646-UTF-1';
-
- case 'csiso115481':
- case 'iso115481':
- case 'isotr115481':
- return 'ISO-11548-1';
-
- case 'csiso90':
- case 'isoir90':
- return 'iso-ir-90';
-
- case 'csunicodeibm1261':
- case 'isounicodeibm1261':
- return 'ISO-Unicode-IBM-1261';
-
- case 'csunicodeibm1264':
- case 'isounicodeibm1264':
- return 'ISO-Unicode-IBM-1264';
-
- case 'csunicodeibm1265':
- case 'isounicodeibm1265':
- return 'ISO-Unicode-IBM-1265';
-
- case 'csunicodeibm1268':
- case 'isounicodeibm1268':
- return 'ISO-Unicode-IBM-1268';
-
- case 'csunicodeibm1276':
- case 'isounicodeibm1276':
- return 'ISO-Unicode-IBM-1276';
-
- case 'csiso646basic1983':
- case 'iso646basic1983':
- case 'ref':
- return 'ISO_646.basic:1983';
-
- case 'csiso2intlrefversion':
- case 'irv':
- case 'iso646irv1983':
- case 'isoir2':
- return 'ISO_646.irv:1983';
-
- case 'csiso2033':
- case 'e13b':
- case 'iso20331983':
- case 'isoir98':
- return 'ISO_2033-1983';
-
- case 'csiso5427cyrillic':
- case 'iso5427':
- case 'isoir37':
- return 'ISO_5427';
-
- case 'iso5427cyrillic1981':
- case 'iso54271981':
- case 'isoir54':
- return 'ISO_5427:1981';
-
- case 'csiso5428greek':
- case 'iso54281980':
- case 'isoir55':
- return 'ISO_5428:1980';
-
- case 'csiso6937add':
- case 'iso6937225':
- case 'isoir152':
- return 'ISO_6937-2-25';
-
- case 'csisotextcomm':
- case 'iso69372add':
- case 'isoir142':
- return 'ISO_6937-2-add';
-
- case 'csiso8859supp':
- case 'iso8859supp':
- case 'isoir154':
- case 'latin125':
- return 'ISO_8859-supp';
-
- case 'csiso10367box':
- case 'iso10367box':
- case 'isoir155':
- return 'ISO_10367-box';
-
- case 'csiso15italian':
- case 'iso646it':
- case 'isoir15':
- case 'it':
- return 'IT';
-
- case 'csiso13jisc6220jp':
- case 'isoir13':
- case 'jisc62201969':
- case 'jisc62201969jp':
- case 'katakana':
- case 'x2017':
- return 'JIS_C6220-1969-jp';
-
- case 'csiso14jisc6220ro':
- case 'iso646jp':
- case 'isoir14':
- case 'jisc62201969ro':
- case 'jp':
- return 'JIS_C6220-1969-ro';
-
- case 'csiso42jisc62261978':
- case 'isoir42':
- case 'jisc62261978':
- return 'JIS_C6226-1978';
-
- case 'csiso87jisx208':
- case 'isoir87':
- case 'jisc62261983':
- case 'jisx2081983':
- case 'x208':
- return 'JIS_C6226-1983';
-
- case 'csiso91jisc62291984a':
- case 'isoir91':
- case 'jisc62291984a':
- case 'jpocra':
- return 'JIS_C6229-1984-a';
-
- case 'csiso92jisc62991984b':
- case 'iso646jpocrb':
- case 'isoir92':
- case 'jisc62291984b':
- case 'jpocrb':
- return 'JIS_C6229-1984-b';
-
- case 'csiso93jis62291984badd':
- case 'isoir93':
- case 'jisc62291984badd':
- case 'jpocrbadd':
- return 'JIS_C6229-1984-b-add';
-
- case 'csiso94jis62291984hand':
- case 'isoir94':
- case 'jisc62291984hand':
- case 'jpocrhand':
- return 'JIS_C6229-1984-hand';
-
- case 'csiso95jis62291984handadd':
- case 'isoir95':
- case 'jisc62291984handadd':
- case 'jpocrhandadd':
- return 'JIS_C6229-1984-hand-add';
-
- case 'csiso96jisc62291984kana':
- case 'isoir96':
- case 'jisc62291984kana':
- return 'JIS_C6229-1984-kana';
-
- case 'csjisencoding':
- case 'jisencoding':
- return 'JIS_Encoding';
-
- case 'cshalfwidthkatakana':
- case 'jisx201':
- case 'x201':
- return 'JIS_X0201';
-
- case 'csiso159jisx2121990':
- case 'isoir159':
- case 'jisx2121990':
- case 'x212':
- return 'JIS_X0212-1990';
-
- case 'csiso141jusib1002':
- case 'iso646yu':
- case 'isoir141':
- case 'js':
- case 'jusib1002':
- case 'yu':
- return 'JUS_I.B1.002';
-
- case 'csiso147macedonian':
- case 'isoir147':
- case 'jusib1003mac':
- case 'macedonian':
- return 'JUS_I.B1.003-mac';
-
- case 'csiso146serbian':
- case 'isoir146':
- case 'jusib1003serb':
- case 'serbian':
- return 'JUS_I.B1.003-serb';
-
- case 'koi7switched':
- return 'KOI7-switched';
-
- case 'cskoi8r':
- case 'koi8r':
- return 'KOI8-R';
-
- case 'koi8u':
- return 'KOI8-U';
-
- case 'csksc5636':
- case 'iso646kr':
- case 'ksc5636':
- return 'KSC5636';
-
- case 'cskz1048':
- case 'kz1048':
- case 'rk1048':
- case 'strk10482002':
- return 'KZ-1048';
-
- case 'csiso19latingreek':
- case 'isoir19':
- case 'latingreek':
- return 'latin-greek';
-
- case 'csiso27latingreek1':
- case 'isoir27':
- case 'latingreek1':
- return 'Latin-greek-1';
-
- case 'csiso158lap':
- case 'isoir158':
- case 'lap':
- case 'latinlap':
- return 'latin-lap';
-
- case 'csmacintosh':
- case 'mac':
- case 'macintosh':
- return 'macintosh';
-
- case 'csmicrosoftpublishing':
- case 'microsoftpublishing':
- return 'Microsoft-Publishing';
-
- case 'csmnem':
- case 'mnem':
- return 'MNEM';
-
- case 'csmnemonic':
- case 'mnemonic':
- return 'MNEMONIC';
-
- case 'csiso86hungarian':
- case 'hu':
- case 'iso646hu':
- case 'isoir86':
- case 'msz77953':
- return 'MSZ_7795.3';
-
- case 'csnatsdano':
- case 'isoir91':
- case 'natsdano':
- return 'NATS-DANO';
-
- case 'csnatsdanoadd':
- case 'isoir92':
- case 'natsdanoadd':
- return 'NATS-DANO-ADD';
-
- case 'csnatssefi':
- case 'isoir81':
- case 'natssefi':
- return 'NATS-SEFI';
-
- case 'csnatssefiadd':
- case 'isoir82':
- case 'natssefiadd':
- return 'NATS-SEFI-ADD';
-
- case 'csiso151cuba':
- case 'cuba':
- case 'iso646cu':
- case 'isoir151':
- case 'ncnc1081':
- return 'NC_NC00-10:81';
-
- case 'csiso69french':
- case 'fr':
- case 'iso646fr':
- case 'isoir69':
- case 'nfz62010':
- return 'NF_Z_62-010';
-
- case 'csiso25french':
- case 'iso646fr1':
- case 'isoir25':
- case 'nfz620101973':
- return 'NF_Z_62-010_(1973)';
-
- case 'csiso60danishnorwegian':
- case 'csiso60norwegian1':
- case 'iso646no':
- case 'isoir60':
- case 'no':
- case 'ns45511':
- return 'NS_4551-1';
-
- case 'csiso61norwegian2':
- case 'iso646no2':
- case 'isoir61':
- case 'no2':
- case 'ns45512':
- return 'NS_4551-2';
-
- case 'osdebcdicdf3irv':
- return 'OSD_EBCDIC_DF03_IRV';
-
- case 'osdebcdicdf41':
- return 'OSD_EBCDIC_DF04_1';
-
- case 'osdebcdicdf415':
- return 'OSD_EBCDIC_DF04_15';
-
- case 'cspc8danishnorwegian':
- case 'pc8danishnorwegian':
- return 'PC8-Danish-Norwegian';
-
- case 'cspc8turkish':
- case 'pc8turkish':
- return 'PC8-Turkish';
-
- case 'csiso16portuguese':
- case 'iso646pt':
- case 'isoir16':
- case 'pt':
- return 'PT';
-
- case 'csiso84portuguese2':
- case 'iso646pt2':
- case 'isoir84':
- case 'pt2':
- return 'PT2';
-
- case 'cp154':
- case 'csptcp154':
- case 'cyrillicasian':
- case 'pt154':
- case 'ptcp154':
- return 'PTCP154';
-
- case 'scsu':
- return 'SCSU';
-
- case 'csiso10swedish':
- case 'fi':
- case 'iso646fi':
- case 'iso646se':
- case 'isoir10':
- case 'se':
- case 'sen850200b':
- return 'SEN_850200_B';
-
- case 'csiso11swedishfornames':
- case 'iso646se2':
- case 'isoir11':
- case 'se2':
- case 'sen850200c':
- return 'SEN_850200_C';
-
- case 'csshiftjis':
- case 'mskanji':
- case 'shiftjis':
- return 'Shift_JIS';
-
- case 'csiso102t617bit':
- case 'isoir102':
- case 't617bit':
- return 'T.61-7bit';
-
- case 'csiso103t618bit':
- case 'isoir103':
- case 't61':
- case 't618bit':
- return 'T.61-8bit';
-
- case 'csiso128t101g2':
- case 'isoir128':
- case 't101g2':
- return 'T.101-G2';
-
- case 'cstscii':
- case 'tscii':
- return 'TSCII';
-
- case 'csunicode11':
- case 'unicode11':
- return 'UNICODE-1-1';
-
- case 'csunicode11utf7':
- case 'unicode11utf7':
- return 'UNICODE-1-1-UTF-7';
-
- case 'csunknown8bit':
- case 'unknown8bit':
- return 'UNKNOWN-8BIT';
-
- case 'ansix341968':
- case 'ansix341986':
- case 'ascii':
- case 'cp367':
- case 'csascii':
- case 'ibm367':
- case 'iso646irv1991':
- case 'iso646us':
- case 'isoir6':
- case 'us':
- case 'usascii':
- return 'US-ASCII';
-
- case 'csusdk':
- case 'usdk':
- return 'us-dk';
-
- case 'utf7':
- return 'UTF-7';
-
- case 'utf8':
- return 'UTF-8';
-
- case 'utf16':
- return 'UTF-16';
-
- case 'utf16be':
- return 'UTF-16BE';
-
- case 'utf16le':
- return 'UTF-16LE';
-
- case 'utf32':
- return 'UTF-32';
-
- case 'utf32be':
- return 'UTF-32BE';
-
- case 'utf32le':
- return 'UTF-32LE';
-
- case 'csventurainternational':
- case 'venturainternational':
- return 'Ventura-International';
-
- case 'csventuramath':
- case 'venturamath':
- return 'Ventura-Math';
-
- case 'csventuraus':
- case 'venturaus':
- return 'Ventura-US';
-
- case 'csiso70videotexsupp1':
- case 'isoir70':
- case 'videotexsuppl':
- return 'videotex-suppl';
-
- case 'csviqr':
- case 'viqr':
- return 'VIQR';
-
- case 'csviscii':
- case 'viscii':
- return 'VISCII';
-
- case 'cswindows31j':
- case 'windows31j':
- return 'Windows-31J';
-
- case 'iso885911':
- case 'tis620':
- return 'windows-874';
-
- case 'cseuckr':
- case 'csksc56011987':
- case 'euckr':
- case 'isoir149':
- case 'korean':
- case 'ksc5601':
- case 'ksc56011987':
- case 'ksc56011989':
- case 'windows949':
- return 'windows-949';
-
- case 'windows1250':
- return 'windows-1250';
-
- case 'windows1251':
- return 'windows-1251';
-
- case 'cp819':
- case 'csisolatin1':
- case 'ibm819':
- case 'iso88591':
- case 'iso885911987':
- case 'isoir100':
- case 'l1':
- case 'latin1':
- case 'windows1252':
- return 'windows-1252';
-
- case 'windows1253':
- return 'windows-1253';
-
- case 'csisolatin5':
- case 'iso88599':
- case 'iso885991989':
- case 'isoir148':
- case 'l5':
- case 'latin5':
- case 'windows1254':
- return 'windows-1254';
-
- case 'windows1255':
- return 'windows-1255';
-
- case 'windows1256':
- return 'windows-1256';
-
- case 'windows1257':
- return 'windows-1257';
-
- case 'windows1258':
- return 'windows-1258';
-
- default:
- return $charset;
- }
- }
-
- function get_curl_version()
- {
- if (is_array($curl = curl_version()))
- {
- $curl = $curl['version'];
- }
- elseif (substr($curl, 0, 5) === 'curl/')
- {
- $curl = substr($curl, 5, strcspn($curl, "\x09\x0A\x0B\x0C\x0D", 5));
- }
- elseif (substr($curl, 0, 8) === 'libcurl/')
- {
- $curl = substr($curl, 8, strcspn($curl, "\x09\x0A\x0B\x0C\x0D", 8));
- }
- else
- {
- $curl = 0;
- }
- return $curl;
- }
-
- function is_subclass_of($class1, $class2)
- {
- if (func_num_args() !== 2)
- {
- trigger_error('Wrong parameter count for SimplePie_Misc::is_subclass_of()', E_USER_WARNING);
- }
- elseif (version_compare(PHP_VERSION, '5.0.3', '>=') || is_object($class1))
- {
- return is_subclass_of($class1, $class2);
- }
- elseif (is_string($class1) && is_string($class2))
- {
- if (class_exists($class1))
- {
- if (class_exists($class2))
- {
- $class2 = strtolower($class2);
- while ($class1 = strtolower(get_parent_class($class1)))
- {
- if ($class1 === $class2)
- {
- return true;
- }
- }
- }
- }
- else
- {
- trigger_error('Unknown class passed as parameter', E_USER_WARNNG);
- }
- }
- return false;
- }
-
- /**
- * Strip HTML comments
- *
- * @access public
- * @param string $data Data to strip comments from
- * @return string Comment stripped string
- */
- function strip_comments($data)
- {
- $output = '';
- while (($start = strpos($data, '<!--')) !== false)
- {
- $output .= substr($data, 0, $start);
- if (($end = strpos($data, '-->', $start)) !== false)
- {
- $data = substr_replace($data, '', 0, $end + 3);
- }
- else
- {
- $data = '';
- }
- }
- return $output . $data;
- }
-
- function parse_date($dt)
- {
- $parser = SimplePie_Parse_Date::get();
- return $parser->parse($dt);
- }
-
- /**
- * Decode HTML entities
- *
- * @static
- * @access public
- * @param string $data Input data
- * @return string Output data
- */
- function entities_decode($data)
- {
- $decoder = new SimplePie_Decode_HTML_Entities($data);
- return $decoder->parse();
- }
-
- /**
- * Remove RFC822 comments
- *
- * @access public
- * @param string $data Data to strip comments from
- * @return string Comment stripped string
- */
- function uncomment_rfc822($string)
- {
- $string = (string) $string;
- $position = 0;
- $length = strlen($string);
- $depth = 0;
-
- $output = '';
-
- while ($position < $length && ($pos = strpos($string, '(', $position)) !== false)
- {
- $output .= substr($string, $position, $pos - $position);
- $position = $pos + 1;
- if ($string[$pos - 1] !== '\\')
- {
- $depth++;
- while ($depth && $position < $length)
- {
- $position += strcspn($string, '()', $position);
- if ($string[$position - 1] === '\\')
- {
- $position++;
- continue;
- }
- elseif (isset($string[$position]))
- {
- switch ($string[$position])
- {
- case '(':
- $depth++;
- break;
-
- case ')':
- $depth--;
- break;
- }
- $position++;
- }
- else
- {
- break;
- }
- }
- }
- else
- {
- $output .= '(';
- }
- }
- $output .= substr($string, $position);
-
- return $output;
- }
-
- function parse_mime($mime)
- {
- if (($pos = strpos($mime, ';')) === false)
- {
- return trim($mime);
- }
- else
- {
- return trim(substr($mime, 0, $pos));
- }
- }
-
- function htmlspecialchars_decode($string, $quote_style)
- {
- if (function_exists('htmlspecialchars_decode'))
- {
- return htmlspecialchars_decode($string, $quote_style);
- }
- else
- {
- return strtr($string, array_flip(get_html_translation_table(HTML_SPECIALCHARS, $quote_style)));
- }
- }
-
- function atom_03_construct_type($attribs)
- {
- if (isset($attribs['']['mode']) && strtolower(trim($attribs['']['mode']) === 'base64'))
- {
- $mode = SIMPLEPIE_CONSTRUCT_BASE64;
- }
- else
- {
- $mode = SIMPLEPIE_CONSTRUCT_NONE;
- }
- if (isset($attribs['']['type']))
- {
- switch (strtolower(trim($attribs['']['type'])))
- {
- case 'text':
- case 'text/plain':
- return SIMPLEPIE_CONSTRUCT_TEXT | $mode;
-
- case 'html':
- case 'text/html':
- return SIMPLEPIE_CONSTRUCT_HTML | $mode;
-
- case 'xhtml':
- case 'application/xhtml+xml':
- return SIMPLEPIE_CONSTRUCT_XHTML | $mode;
-
- default:
- return SIMPLEPIE_CONSTRUCT_NONE | $mode;
- }
- }
- else
- {
- return SIMPLEPIE_CONSTRUCT_TEXT | $mode;
- }
- }
-
- function atom_10_construct_type($attribs)
- {
- if (isset($attribs['']['type']))
- {
- switch (strtolower(trim($attribs['']['type'])))
- {
- case 'text':
- return SIMPLEPIE_CONSTRUCT_TEXT;
-
- case 'html':
- return SIMPLEPIE_CONSTRUCT_HTML;
-
- case 'xhtml':
- return SIMPLEPIE_CONSTRUCT_XHTML;
-
- default:
- return SIMPLEPIE_CONSTRUCT_NONE;
- }
- }
- return SIMPLEPIE_CONSTRUCT_TEXT;
- }
-
- function atom_10_content_construct_type($attribs)
- {
- if (isset($attribs['']['type']))
- {
- $type = strtolower(trim($attribs['']['type']));
- switch ($type)
- {
- case 'text':
- return SIMPLEPIE_CONSTRUCT_TEXT;
-
- case 'html':
- return SIMPLEPIE_CONSTRUCT_HTML;
-
- case 'xhtml':
- return SIMPLEPIE_CONSTRUCT_XHTML;
- }
- if (in_array(substr($type, -4), array('+xml', '/xml')) || substr($type, 0, 5) === 'text/')
- {
- return SIMPLEPIE_CONSTRUCT_NONE;
- }
- else
- {
- return SIMPLEPIE_CONSTRUCT_BASE64;
- }
- }
- else
- {
- return SIMPLEPIE_CONSTRUCT_TEXT;
- }
- }
-
- function is_isegment_nz_nc($string)
- {
- return (bool) preg_match('/^([A-Za-z0-9\-._~\x{A0}-\x{D7FF}\x{F900}-\x{FDCF}\x{FDF0}-\x{FFEF}\x{10000}-\x{1FFFD}\x{20000}-\x{2FFFD}\x{30000}-\x{3FFFD}\x{40000}-\x{4FFFD}\x{50000}-\x{5FFFD}\x{60000}-\x{6FFFD}\x{70000}-\x{7FFFD}\x{80000}-\x{8FFFD}\x{90000}-\x{9FFFD}\x{A0000}-\x{AFFFD}\x{B0000}-\x{BFFFD}\x{C0000}-\x{CFFFD}\x{D0000}-\x{DFFFD}\x{E1000}-\x{EFFFD}!$&\'()*+,;=@]|(%[0-9ABCDEF]{2}))+$/u', $string);
- }
-
- function space_seperated_tokens($string)
- {
- $space_characters = "\x20\x09\x0A\x0B\x0C\x0D";
- $string_length = strlen($string);
-
- $position = strspn($string, $space_characters);
- $tokens = array();
-
- while ($position < $string_length)
- {
- $len = strcspn($string, $space_characters, $position);
- $tokens[] = substr($string, $position, $len);
- $position += $len;
- $position += strspn($string, $space_characters, $position);
- }
-
- return $tokens;
- }
-
- function array_unique($array)
- {
- if (version_compare(PHP_VERSION, '5.2', '>='))
- {
- return array_unique($array);
- }
- else
- {
- $array = (array) $array;
- $new_array = array();
- $new_array_strings = array();
- foreach ($array as $key => $value)
- {
- if (is_object($value))
- {
- if (method_exists($value, '__toString'))
- {
- $cmp = $value->__toString();
- }
- else
- {
- trigger_error('Object of class ' . get_class($value) . ' could not be converted to string', E_USER_ERROR);
- }
- }
- elseif (is_array($value))
- {
- $cmp = (string) reset($value);
- }
- else
- {
- $cmp = (string) $value;
- }
- if (!in_array($cmp, $new_array_strings))
- {
- $new_array[$key] = $value;
- $new_array_strings[] = $cmp;
- }
- }
- return $new_array;
- }
- }
-
- /**
- * Converts a unicode codepoint to a UTF-8 character
- *
- * @static
- * @access public
- * @param int $codepoint Unicode codepoint
- * @return string UTF-8 character
- */
- function codepoint_to_utf8($codepoint)
- {
- $codepoint = (int) $codepoint;
- if ($codepoint < 0)
- {
- return false;
- }
- else if ($codepoint <= 0x7f)
- {
- return chr($codepoint);
- }
- else if ($codepoint <= 0x7ff)
- {
- return chr(0xc0 | ($codepoint >> 6)) . chr(0x80 | ($codepoint & 0x3f));
- }
- else if ($codepoint <= 0xffff)
- {
- return chr(0xe0 | ($codepoint >> 12)) . chr(0x80 | (($codepoint >> 6) & 0x3f)) . chr(0x80 | ($codepoint & 0x3f));
- }
- else if ($codepoint <= 0x10ffff)
- {
- return chr(0xf0 | ($codepoint >> 18)) . chr(0x80 | (($codepoint >> 12) & 0x3f)) . chr(0x80 | (($codepoint >> 6) & 0x3f)) . chr(0x80 | ($codepoint & 0x3f));
- }
- else
- {
- // U+FFFD REPLACEMENT CHARACTER
- return "\xEF\xBF\xBD";
- }
- }
-
- /**
- * Re-implementation of PHP 5's stripos()
- *
- * Returns the numeric position of the first occurrence of needle in the
- * haystack string.
- *
- * @static
- * @access string
- * @param object $haystack
- * @param string $needle Note that the needle may be a string of one or more
- * characters. If needle is not a string, it is converted to an integer
- * and applied as the ordinal value of a character.
- * @param int $offset The optional offset parameter allows you to specify which
- * character in haystack to start searching. The position returned is still
- * relative to the beginning of haystack.
- * @return bool If needle is not found, stripos() will return boolean false.
- */
- function stripos($haystack, $needle, $offset = 0)
- {
- if (function_exists('stripos'))
- {
- return stripos($haystack, $needle, $offset);
- }
- else
- {
- if (is_string($needle))
- {
- $needle = strtolower($needle);
- }
- elseif (is_int($needle) || is_bool($needle) || is_double($needle))
- {
- $needle = strtolower(chr($needle));
- }
- else
- {
- trigger_error('needle is not a string or an integer', E_USER_WARNING);
- return false;
- }
-
- return strpos(strtolower($haystack), $needle, $offset);
- }
- }
-
- /**
- * Similar to parse_str()
- *
- * Returns an associative array of name/value pairs, where the value is an
- * array of values that have used the same name
- *
- * @static
- * @access string
- * @param string $str The input string.
- * @return array
- */
- function parse_str($str)
- {
- $return = array();
- $str = explode('&', $str);
-
- foreach ($str as $section)
- {
- if (strpos($section, '=') !== false)
- {
- list($name, $value) = explode('=', $section, 2);
- $return[urldecode($name)][] = urldecode($value);
- }
- else
- {
- $return[urldecode($section)][] = null;
- }
- }
-
- return $return;
- }
-
- /**
- * Detect XML encoding, as per XML 1.0 Appendix F.1
- *
- * @todo Add support for EBCDIC
- * @param string $data XML data
- * @return array Possible encodings
- */
- function xml_encoding($data)
- {
- // UTF-32 Big Endian BOM
- if (substr($data, 0, 4) === "\x00\x00\xFE\xFF")
- {
- $encoding[] = 'UTF-32BE';
- }
- // UTF-32 Little Endian BOM
- elseif (substr($data, 0, 4) === "\xFF\xFE\x00\x00")
- {
- $encoding[] = 'UTF-32LE';
- }
- // UTF-16 Big Endian BOM
- elseif (substr($data, 0, 2) === "\xFE\xFF")
- {
- $encoding[] = 'UTF-16BE';
- }
- // UTF-16 Little Endian BOM
- elseif (substr($data, 0, 2) === "\xFF\xFE")
- {
- $encoding[] = 'UTF-16LE';
- }
- // UTF-8 BOM
- elseif (substr($data, 0, 3) === "\xEF\xBB\xBF")
- {
- $encoding[] = 'UTF-8';
- }
- // UTF-32 Big Endian Without BOM
- elseif (substr($data, 0, 20) === "\x00\x00\x00\x3C\x00\x00\x00\x3F\x00\x00\x00\x78\x00\x00\x00\x6D\x00\x00\x00\x6C")
- {
- if ($pos = strpos($data, "\x00\x00\x00\x3F\x00\x00\x00\x3E"))
- {
- $parser = new SimplePie_XML_Declaration_Parser(SimplePie_Misc::change_encoding(substr($data, 20, $pos - 20), 'UTF-32BE', 'UTF-8'));
- if ($parser->parse())
- {
- $encoding[] = $parser->encoding;
- }
- }
- $encoding[] = 'UTF-32BE';
- }
- // UTF-32 Little Endian Without BOM
- elseif (substr($data, 0, 20) === "\x3C\x00\x00\x00\x3F\x00\x00\x00\x78\x00\x00\x00\x6D\x00\x00\x00\x6C\x00\x00\x00")
- {
- if ($pos = strpos($data, "\x3F\x00\x00\x00\x3E\x00\x00\x00"))
- {
- $parser = new SimplePie_XML_Declaration_Parser(SimplePie_Misc::change_encoding(substr($data, 20, $pos - 20), 'UTF-32LE', 'UTF-8'));
- if ($parser->parse())
- {
- $encoding[] = $parser->encoding;
- }
- }
- $encoding[] = 'UTF-32LE';
- }
- // UTF-16 Big Endian Without BOM
- elseif (substr($data, 0, 10) === "\x00\x3C\x00\x3F\x00\x78\x00\x6D\x00\x6C")
- {
- if ($pos = strpos($data, "\x00\x3F\x00\x3E"))
- {
- $parser = new SimplePie_XML_Declaration_Parser(SimplePie_Misc::change_encoding(substr($data, 20, $pos - 10), 'UTF-16BE', 'UTF-8'));
- if ($parser->parse())
- {
- $encoding[] = $parser->encoding;
- }
- }
- $encoding[] = 'UTF-16BE';
- }
- // UTF-16 Little Endian Without BOM
- elseif (substr($data, 0, 10) === "\x3C\x00\x3F\x00\x78\x00\x6D\x00\x6C\x00")
- {
- if ($pos = strpos($data, "\x3F\x00\x3E\x00"))
- {
- $parser = new SimplePie_XML_Declaration_Parser(SimplePie_Misc::change_encoding(substr($data, 20, $pos - 10), 'UTF-16LE', 'UTF-8'));
- if ($parser->parse())
- {
- $encoding[] = $parser->encoding;
- }
- }
- $encoding[] = 'UTF-16LE';
- }
- // US-ASCII (or superset)
- elseif (substr($data, 0, 5) === "\x3C\x3F\x78\x6D\x6C")
- {
- if ($pos = strpos($data, "\x3F\x3E"))
- {
- $parser = new SimplePie_XML_Declaration_Parser(substr($data, 5, $pos - 5));
- if ($parser->parse())
- {
- $encoding[] = $parser->encoding;
- }
- }
- $encoding[] = 'UTF-8';
- }
- // Fallback to UTF-8
- else
- {
- $encoding[] = 'UTF-8';
- }
- return $encoding;
- }
-
- function output_javascript()
- {
- if (function_exists('ob_gzhandler'))
- {
- ob_start('ob_gzhandler');
- }
- header('Content-type: text/javascript; charset: UTF-8');
- header('Cache-Control: must-revalidate');
- header('Expires: ' . gmdate('D, d M Y H:i:s', time() + 604800) . ' GMT'); // 7 days
- ?>
-function embed_odeo(link) {
- document.writeln('<embed src="http://odeo.com/flash/audio_player_fullsize.swf" pluginspage="http://www.macromedia.com/go/getflashplayer" type="application/x-shockwave-flash" quality="high" width="440" height="80" wmode="transparent" allowScriptAccess="any" flashvars="valid_sample_rate=true&external_url='+link+'"></embed>');
-}
-
-function embed_quicktime(type, bgcolor, width, height, link, placeholder, loop) {
- if (placeholder != '') {
- document.writeln('<embed type="'+type+'" style="cursor:hand; cursor:pointer;" href="'+link+'" src="'+placeholder+'" width="'+width+'" height="'+height+'" autoplay="false" target="myself" controller="false" loop="'+loop+'" scale="aspect" bgcolor="'+bgcolor+'" pluginspage="http://www.apple.com/quicktime/download/"></embed>');
- }
- else {
- document.writeln('<embed type="'+type+'" style="cursor:hand; cursor:pointer;" src="'+link+'" width="'+width+'" height="'+height+'" autoplay="false" target="myself" controller="true" loop="'+loop+'" scale="aspect" bgcolor="'+bgcolor+'" pluginspage="http://www.apple.com/quicktime/download/"></embed>');
- }
-}
-
-function embed_flash(bgcolor, width, height, link, loop, type) {
- document.writeln('<embed src="'+link+'" pluginspage="http://www.macromedia.com/go/getflashplayer" type="'+type+'" quality="high" width="'+width+'" height="'+height+'" bgcolor="'+bgcolor+'" loop="'+loop+'"></embed>');
-}
-
-function embed_flv(width, height, link, placeholder, loop, player) {
- document.writeln('<embed src="'+player+'" pluginspage="http://www.macromedia.com/go/getflashplayer" type="application/x-shockwave-flash" quality="high" width="'+width+'" height="'+height+'" wmode="transparent" flashvars="file='+link+'&autostart=false&repeat='+loop+'&showdigits=true&showfsbutton=false"></embed>');
-}
-
-function embed_wmedia(width, height, link) {
- document.writeln('<embed type="application/x-mplayer2" src="'+link+'" autosize="1" width="'+width+'" height="'+height+'" showcontrols="1" showstatusbar="0" showdisplay="0" autostart="0"></embed>');
-}
- <?php
- }
-}
-
-/**
- * Decode HTML Entities
- *
- * This implements HTML5 as of revision 967 (2007-06-28)
- *
- * @package SimplePie
- */
-class SimplePie_Decode_HTML_Entities
-{
- /**
- * Data to be parsed
- *
- * @access private
- * @var string
- */
- var $data = '';
-
- /**
- * Currently consumed bytes
- *
- * @access private
- * @var string
- */
- var $consumed = '';
-
- /**
- * Position of the current byte being parsed
- *
- * @access private
- * @var int
- */
- var $position = 0;
-
- /**
- * Create an instance of the class with the input data
- *
- * @access public
- * @param string $data Input data
- */
- function SimplePie_Decode_HTML_Entities($data)
- {
- $this->data = $data;
- }
-
- /**
- * Parse the input data
- *
- * @access public
- * @return string Output data
- */
- function parse()
- {
- while (($this->position = strpos($this->data, '&', $this->position)) !== false)
- {
- $this->consume();
- $this->entity();
- $this->consumed = '';
- }
- return $this->data;
- }
-
- /**
- * Consume the next byte
- *
- * @access private
- * @return mixed The next byte, or false, if there is no more data
- */
- function consume()
- {
- if (isset($this->data[$this->position]))
- {
- $this->consumed .= $this->data[$this->position];
- return $this->data[$this->position++];
- }
- else
- {
- return false;
- }
- }
-
- /**
- * Consume a range of characters
- *
- * @access private
- * @param string $chars Characters to consume
- * @return mixed A series of characters that match the range, or false
- */
- function consume_range($chars)
- {
- if ($len = strspn($this->data, $chars, $this->position))
- {
- $data = substr($this->data, $this->position, $len);
- $this->consumed .= $data;
- $this->position += $len;
- return $data;
- }
- else
- {
- return false;
- }
- }
-
- /**
- * Unconsume one byte
- *
- * @access private
- */
- function unconsume()
- {
- $this->consumed = substr($this->consumed, 0, -1);
- $this->position--;
- }
-
- /**
- * Decode an entity
- *
- * @access private
- */
- function entity()
- {
- switch ($this->consume())
- {
- case "\x09":
- case "\x0A":
- case "\x0B":
- case "\x0B":
- case "\x0C":
- case "\x20":
- case "\x3C":
- case "\x26":
- case false:
- break;
-
- case "\x23":
- switch ($this->consume())
- {
- case "\x78":
- case "\x58":
- $range = '0123456789ABCDEFabcdef';
- $hex = true;
- break;
-
- default:
- $range = '0123456789';
- $hex = false;
- $this->unconsume();
- break;
- }
-
- if ($codepoint = $this->consume_range($range))
- {
- static $windows_1252_specials = array(0x0D => "\x0A", 0x80 => "\xE2\x82\xAC", 0x81 => "\xEF\xBF\xBD", 0x82 => "\xE2\x80\x9A", 0x83 => "\xC6\x92", 0x84 => "\xE2\x80\x9E", 0x85 => "\xE2\x80\xA6", 0x86 => "\xE2\x80\xA0", 0x87 => "\xE2\x80\xA1", 0x88 => "\xCB\x86", 0x89 => "\xE2\x80\xB0", 0x8A => "\xC5\xA0", 0x8B => "\xE2\x80\xB9", 0x8C => "\xC5\x92", 0x8D => "\xEF\xBF\xBD", 0x8E => "\xC5\xBD", 0x8F => "\xEF\xBF\xBD", 0x90 => "\xEF\xBF\xBD", 0x91 => "\xE2\x80\x98", 0x92 => "\xE2\x80\x99", 0x93 => "\xE2\x80\x9C", 0x94 => "\xE2\x80\x9D", 0x95 => "\xE2\x80\xA2", 0x96 => "\xE2\x80\x93", 0x97 => "\xE2\x80\x94", 0x98 => "\xCB\x9C", 0x99 => "\xE2\x84\xA2", 0x9A => "\xC5\xA1", 0x9B => "\xE2\x80\xBA", 0x9C => "\xC5\x93", 0x9D => "\xEF\xBF\xBD", 0x9E => "\xC5\xBE", 0x9F => "\xC5\xB8");
-
- if ($hex)
- {
- $codepoint = hexdec($codepoint);
- }
- else
- {
- $codepoint = intval($codepoint);
- }
-
- if (isset($windows_1252_specials[$codepoint]))
- {
- $replacement = $windows_1252_specials[$codepoint];
- }
- else
- {
- $replacement = SimplePie_Misc::codepoint_to_utf8($codepoint);
- }
-
- if (!in_array($this->consume(), array(';', false), true))
- {
- $this->unconsume();
- }
-
- $consumed_length = strlen($this->consumed);
- $this->data = substr_replace($this->data, $replacement, $this->position - $consumed_length, $consumed_length);
- $this->position += strlen($replacement) - $consumed_length;
- }
- break;
-
- default:
- static $entities = array('Aacute' => "\xC3\x81", 'aacute' => "\xC3\xA1", 'Aacute;' => "\xC3\x81", 'aacute;' => "\xC3\xA1", 'Acirc' => "\xC3\x82", 'acirc' => "\xC3\xA2", 'Acirc;' => "\xC3\x82", 'acirc;' => "\xC3\xA2", 'acute' => "\xC2\xB4", 'acute;' => "\xC2\xB4", 'AElig' => "\xC3\x86", 'aelig' => "\xC3\xA6", 'AElig;' => "\xC3\x86", 'aelig;' => "\xC3\xA6", 'Agrave' => "\xC3\x80", 'agrave' => "\xC3\xA0", 'Agrave;' => "\xC3\x80", 'agrave;' => "\xC3\xA0", 'alefsym;' => "\xE2\x84\xB5", 'Alpha;' => "\xCE\x91", 'alpha;' => "\xCE\xB1", 'AMP' => "\x26", 'amp' => "\x26", 'AMP;' => "\x26", 'amp;' => "\x26", 'and;' => "\xE2\x88\xA7", 'ang;' => "\xE2\x88\xA0", 'apos;' => "\x27", 'Aring' => "\xC3\x85", 'aring' => "\xC3\xA5", 'Aring;' => "\xC3\x85", 'aring;' => "\xC3\xA5", 'asymp;' => "\xE2\x89\x88", 'Atilde' => "\xC3\x83", 'atilde' => "\xC3\xA3", 'Atilde;' => "\xC3\x83", 'atilde;' => "\xC3\xA3", 'Auml' => "\xC3\x84", 'auml' => "\xC3\xA4", 'Auml;' => "\xC3\x84", 'auml;' => "\xC3\xA4", 'bdquo;' => "\xE2\x80\x9E", 'Beta;' => "\xCE\x92", 'beta;' => "\xCE\xB2", 'brvbar' => "\xC2\xA6", 'brvbar;' => "\xC2\xA6", 'bull;' => "\xE2\x80\xA2", 'cap;' => "\xE2\x88\xA9", 'Ccedil' => "\xC3\x87", 'ccedil' => "\xC3\xA7", 'Ccedil;' => "\xC3\x87", 'ccedil;' => "\xC3\xA7", 'cedil' => "\xC2\xB8", 'cedil;' => "\xC2\xB8", 'cent' => "\xC2\xA2", 'cent;' => "\xC2\xA2", 'Chi;' => "\xCE\xA7", 'chi;' => "\xCF\x87", 'circ;' => "\xCB\x86", 'clubs;' => "\xE2\x99\xA3", 'cong;' => "\xE2\x89\x85", 'COPY' => "\xC2\xA9", 'copy' => "\xC2\xA9", 'COPY;' => "\xC2\xA9", 'copy;' => "\xC2\xA9", 'crarr;' => "\xE2\x86\xB5", 'cup;' => "\xE2\x88\xAA", 'curren' => "\xC2\xA4", 'curren;' => "\xC2\xA4", 'Dagger;' => "\xE2\x80\xA1", 'dagger;' => "\xE2\x80\xA0", 'dArr;' => "\xE2\x87\x93", 'darr;' => "\xE2\x86\x93", 'deg' => "\xC2\xB0", 'deg;' => "\xC2\xB0", 'Delta;' => "\xCE\x94", 'delta;' => "\xCE\xB4", 'diams;' => "\xE2\x99\xA6", 'divide' => "\xC3\xB7", 'divide;' => "\xC3\xB7", 'Eacute' => "\xC3\x89", 'eacute' => "\xC3\xA9", 'Eacute;' => "\xC3\x89", 'eacute;' => "\xC3\xA9", 'Ecirc' => "\xC3\x8A", 'ecirc' => "\xC3\xAA", 'Ecirc;' => "\xC3\x8A", 'ecirc;' => "\xC3\xAA", 'Egrave' => "\xC3\x88", 'egrave' => "\xC3\xA8", 'Egrave;' => "\xC3\x88", 'egrave;' => "\xC3\xA8", 'empty;' => "\xE2\x88\x85", 'emsp;' => "\xE2\x80\x83", 'ensp;' => "\xE2\x80\x82", 'Epsilon;' => "\xCE\x95", 'epsilon;' => "\xCE\xB5", 'equiv;' => "\xE2\x89\xA1", 'Eta;' => "\xCE\x97", 'eta;' => "\xCE\xB7", 'ETH' => "\xC3\x90", 'eth' => "\xC3\xB0", 'ETH;' => "\xC3\x90", 'eth;' => "\xC3\xB0", 'Euml' => "\xC3\x8B", 'euml' => "\xC3\xAB", 'Euml;' => "\xC3\x8B", 'euml;' => "\xC3\xAB", 'euro;' => "\xE2\x82\xAC", 'exist;' => "\xE2\x88\x83", 'fnof;' => "\xC6\x92", 'forall;' => "\xE2\x88\x80", 'frac12' => "\xC2\xBD", 'frac12;' => "\xC2\xBD", 'frac14' => "\xC2\xBC", 'frac14;' => "\xC2\xBC", 'frac34' => "\xC2\xBE", 'frac34;' => "\xC2\xBE", 'frasl;' => "\xE2\x81\x84", 'Gamma;' => "\xCE\x93", 'gamma;' => "\xCE\xB3", 'ge;' => "\xE2\x89\xA5", 'GT' => "\x3E", 'gt' => "\x3E", 'GT;' => "\x3E", 'gt;' => "\x3E", 'hArr;' => "\xE2\x87\x94", 'harr;' => "\xE2\x86\x94", 'hearts;' => "\xE2\x99\xA5", 'hellip;' => "\xE2\x80\xA6", 'Iacute' => "\xC3\x8D", 'iacute' => "\xC3\xAD", 'Iacute;' => "\xC3\x8D", 'iacute;' => "\xC3\xAD", 'Icirc' => "\xC3\x8E", 'icirc' => "\xC3\xAE", 'Icirc;' => "\xC3\x8E", 'icirc;' => "\xC3\xAE", 'iexcl' => "\xC2\xA1", 'iexcl;' => "\xC2\xA1", 'Igrave' => "\xC3\x8C", 'igrave' => "\xC3\xAC", 'Igrave;' => "\xC3\x8C", 'igrave;' => "\xC3\xAC", 'image;' => "\xE2\x84\x91", 'infin;' => "\xE2\x88\x9E", 'int;' => "\xE2\x88\xAB", 'Iota;' => "\xCE\x99", 'iota;' => "\xCE\xB9", 'iquest' => "\xC2\xBF", 'iquest;' => "\xC2\xBF", 'isin;' => "\xE2\x88\x88", 'Iuml' => "\xC3\x8F", 'iuml' => "\xC3\xAF", 'Iuml;' => "\xC3\x8F", 'iuml;' => "\xC3\xAF", 'Kappa;' => "\xCE\x9A", 'kappa;' => "\xCE\xBA", 'Lambda;' => "\xCE\x9B", 'lambda;' => "\xCE\xBB", 'lang;' => "\xE3\x80\x88", 'laquo' => "\xC2\xAB", 'laquo;' => "\xC2\xAB", 'lArr;' => "\xE2\x87\x90", 'larr;' => "\xE2\x86\x90", 'lceil;' => "\xE2\x8C\x88", 'ldquo;' => "\xE2\x80\x9C", 'le;' => "\xE2\x89\xA4", 'lfloor;' => "\xE2\x8C\x8A", 'lowast;' => "\xE2\x88\x97", 'loz;' => "\xE2\x97\x8A", 'lrm;' => "\xE2\x80\x8E", 'lsaquo;' => "\xE2\x80\xB9", 'lsquo;' => "\xE2\x80\x98", 'LT' => "\x3C", 'lt' => "\x3C", 'LT;' => "\x3C", 'lt;' => "\x3C", 'macr' => "\xC2\xAF", 'macr;' => "\xC2\xAF", 'mdash;' => "\xE2\x80\x94", 'micro' => "\xC2\xB5", 'micro;' => "\xC2\xB5", 'middot' => "\xC2\xB7", 'middot;' => "\xC2\xB7", 'minus;' => "\xE2\x88\x92", 'Mu;' => "\xCE\x9C", 'mu;' => "\xCE\xBC", 'nabla;' => "\xE2\x88\x87", 'nbsp' => "\xC2\xA0", 'nbsp;' => "\xC2\xA0", 'ndash;' => "\xE2\x80\x93", 'ne;' => "\xE2\x89\xA0", 'ni;' => "\xE2\x88\x8B", 'not' => "\xC2\xAC", 'not;' => "\xC2\xAC", 'notin;' => "\xE2\x88\x89", 'nsub;' => "\xE2\x8A\x84", 'Ntilde' => "\xC3\x91", 'ntilde' => "\xC3\xB1", 'Ntilde;' => "\xC3\x91", 'ntilde;' => "\xC3\xB1", 'Nu;' => "\xCE\x9D", 'nu;' => "\xCE\xBD", 'Oacute' => "\xC3\x93", 'oacute' => "\xC3\xB3", 'Oacute;' => "\xC3\x93", 'oacute;' => "\xC3\xB3", 'Ocirc' => "\xC3\x94", 'ocirc' => "\xC3\xB4", 'Ocirc;' => "\xC3\x94", 'ocirc;' => "\xC3\xB4", 'OElig;' => "\xC5\x92", 'oelig;' => "\xC5\x93", 'Ograve' => "\xC3\x92", 'ograve' => "\xC3\xB2", 'Ograve;' => "\xC3\x92", 'ograve;' => "\xC3\xB2", 'oline;' => "\xE2\x80\xBE", 'Omega;' => "\xCE\xA9", 'omega;' => "\xCF\x89", 'Omicron;' => "\xCE\x9F", 'omicron;' => "\xCE\xBF", 'oplus;' => "\xE2\x8A\x95", 'or;' => "\xE2\x88\xA8", 'ordf' => "\xC2\xAA", 'ordf;' => "\xC2\xAA", 'ordm' => "\xC2\xBA", 'ordm;' => "\xC2\xBA", 'Oslash' => "\xC3\x98", 'oslash' => "\xC3\xB8", 'Oslash;' => "\xC3\x98", 'oslash;' => "\xC3\xB8", 'Otilde' => "\xC3\x95", 'otilde' => "\xC3\xB5", 'Otilde;' => "\xC3\x95", 'otilde;' => "\xC3\xB5", 'otimes;' => "\xE2\x8A\x97", 'Ouml' => "\xC3\x96", 'ouml' => "\xC3\xB6", 'Ouml;' => "\xC3\x96", 'ouml;' => "\xC3\xB6", 'para' => "\xC2\xB6", 'para;' => "\xC2\xB6", 'part;' => "\xE2\x88\x82", 'permil;' => "\xE2\x80\xB0", 'perp;' => "\xE2\x8A\xA5", 'Phi;' => "\xCE\xA6", 'phi;' => "\xCF\x86", 'Pi;' => "\xCE\xA0", 'pi;' => "\xCF\x80", 'piv;' => "\xCF\x96", 'plusmn' => "\xC2\xB1", 'plusmn;' => "\xC2\xB1", 'pound' => "\xC2\xA3", 'pound;' => "\xC2\xA3", 'Prime;' => "\xE2\x80\xB3", 'prime;' => "\xE2\x80\xB2", 'prod;' => "\xE2\x88\x8F", 'prop;' => "\xE2\x88\x9D", 'Psi;' => "\xCE\xA8", 'psi;' => "\xCF\x88", 'QUOT' => "\x22", 'quot' => "\x22", 'QUOT;' => "\x22", 'quot;' => "\x22", 'radic;' => "\xE2\x88\x9A", 'rang;' => "\xE3\x80\x89", 'raquo' => "\xC2\xBB", 'raquo;' => "\xC2\xBB", 'rArr;' => "\xE2\x87\x92", 'rarr;' => "\xE2\x86\x92", 'rceil;' => "\xE2\x8C\x89", 'rdquo;' => "\xE2\x80\x9D", 'real;' => "\xE2\x84\x9C", 'REG' => "\xC2\xAE", 'reg' => "\xC2\xAE", 'REG;' => "\xC2\xAE", 'reg;' => "\xC2\xAE", 'rfloor;' => "\xE2\x8C\x8B", 'Rho;' => "\xCE\xA1", 'rho;' => "\xCF\x81", 'rlm;' => "\xE2\x80\x8F", 'rsaquo;' => "\xE2\x80\xBA", 'rsquo;' => "\xE2\x80\x99", 'sbquo;' => "\xE2\x80\x9A", 'Scaron;' => "\xC5\xA0", 'scaron;' => "\xC5\xA1", 'sdot;' => "\xE2\x8B\x85", 'sect' => "\xC2\xA7", 'sect;' => "\xC2\xA7", 'shy' => "\xC2\xAD", 'shy;' => "\xC2\xAD", 'Sigma;' => "\xCE\xA3", 'sigma;' => "\xCF\x83", 'sigmaf;' => "\xCF\x82", 'sim;' => "\xE2\x88\xBC", 'spades;' => "\xE2\x99\xA0", 'sub;' => "\xE2\x8A\x82", 'sube;' => "\xE2\x8A\x86", 'sum;' => "\xE2\x88\x91", 'sup;' => "\xE2\x8A\x83", 'sup1' => "\xC2\xB9", 'sup1;' => "\xC2\xB9", 'sup2' => "\xC2\xB2", 'sup2;' => "\xC2\xB2", 'sup3' => "\xC2\xB3", 'sup3;' => "\xC2\xB3", 'supe;' => "\xE2\x8A\x87", 'szlig' => "\xC3\x9F", 'szlig;' => "\xC3\x9F", 'Tau;' => "\xCE\xA4", 'tau;' => "\xCF\x84", 'there4;' => "\xE2\x88\xB4", 'Theta;' => "\xCE\x98", 'theta;' => "\xCE\xB8", 'thetasym;' => "\xCF\x91", 'thinsp;' => "\xE2\x80\x89", 'THORN' => "\xC3\x9E", 'thorn' => "\xC3\xBE", 'THORN;' => "\xC3\x9E", 'thorn;' => "\xC3\xBE", 'tilde;' => "\xCB\x9C", 'times' => "\xC3\x97", 'times;' => "\xC3\x97", 'TRADE;' => "\xE2\x84\xA2", 'trade;' => "\xE2\x84\xA2", 'Uacute' => "\xC3\x9A", 'uacute' => "\xC3\xBA", 'Uacute;' => "\xC3\x9A", 'uacute;' => "\xC3\xBA", 'uArr;' => "\xE2\x87\x91", 'uarr;' => "\xE2\x86\x91", 'Ucirc' => "\xC3\x9B", 'ucirc' => "\xC3\xBB", 'Ucirc;' => "\xC3\x9B", 'ucirc;' => "\xC3\xBB", 'Ugrave' => "\xC3\x99", 'ugrave' => "\xC3\xB9", 'Ugrave;' => "\xC3\x99", 'ugrave;' => "\xC3\xB9", 'uml' => "\xC2\xA8", 'uml;' => "\xC2\xA8", 'upsih;' => "\xCF\x92", 'Upsilon;' => "\xCE\xA5", 'upsilon;' => "\xCF\x85", 'Uuml' => "\xC3\x9C", 'uuml' => "\xC3\xBC", 'Uuml;' => "\xC3\x9C", 'uuml;' => "\xC3\xBC", 'weierp;' => "\xE2\x84\x98", 'Xi;' => "\xCE\x9E", 'xi;' => "\xCE\xBE", 'Yacute' => "\xC3\x9D", 'yacute' => "\xC3\xBD", 'Yacute;' => "\xC3\x9D", 'yacute;' => "\xC3\xBD", 'yen' => "\xC2\xA5", 'yen;' => "\xC2\xA5", 'yuml' => "\xC3\xBF", 'Yuml;' => "\xC5\xB8", 'yuml;' => "\xC3\xBF", 'Zeta;' => "\xCE\x96", 'zeta;' => "\xCE\xB6", 'zwj;' => "\xE2\x80\x8D", 'zwnj;' => "\xE2\x80\x8C");
-
- for ($i = 0, $match = null; $i < 9 && $this->consume() !== false; $i++)
- {
- $consumed = substr($this->consumed, 1);
- if (isset($entities[$consumed]))
- {
- $match = $consumed;
- }
- }
-
- if ($match !== null)
- {
- $this->data = substr_replace($this->data, $entities[$match], $this->position - strlen($consumed) - 1, strlen($match) + 1);
- $this->position += strlen($entities[$match]) - strlen($consumed) - 1;
- }
- break;
- }
- }
-}
-
-/**
- * IRI parser/serialiser
- *
- * @package SimplePie
- */
-class SimplePie_IRI
-{
- /**
- * Scheme
- *
- * @access private
- * @var string
- */
- var $scheme;
-
- /**
- * User Information
- *
- * @access private
- * @var string
- */
- var $userinfo;
-
- /**
- * Host
- *
- * @access private
- * @var string
- */
- var $host;
-
- /**
- * Port
- *
- * @access private
- * @var string
- */
- var $port;
-
- /**
- * Path
- *
- * @access private
- * @var string
- */
- var $path;
-
- /**
- * Query
- *
- * @access private
- * @var string
- */
- var $query;
-
- /**
- * Fragment
- *
- * @access private
- * @var string
- */
- var $fragment;
-
- /**
- * Whether the object represents a valid IRI
- *
- * @access private
- * @var array
- */
- var $valid = array();
-
- /**
- * Return the entire IRI when you try and read the object as a string
- *
- * @access public
- * @return string
- */
- function __toString()
- {
- return $this->get_iri();
- }
-
- /**
- * Create a new IRI object, from a specified string
- *
- * @access public
- * @param string $iri
- * @return SimplePie_IRI
- */
- function SimplePie_IRI($iri)
- {
- $iri = (string) $iri;
- if ($iri !== '')
- {
- $parsed = $this->parse_iri($iri);
- $this->set_scheme($parsed['scheme']);
- $this->set_authority($parsed['authority']);
- $this->set_path($parsed['path']);
- $this->set_query($parsed['query']);
- $this->set_fragment($parsed['fragment']);
- }
- }
-
- /**
- * Create a new IRI object by resolving a relative IRI
- *
- * @static
- * @access public
- * @param SimplePie_IRI $base Base IRI
- * @param string $relative Relative IRI
- * @return SimplePie_IRI
- */
- function absolutize($base, $relative)
- {
- $relative = (string) $relative;
- if ($relative !== '')
- {
- $relative = new SimplePie_IRI($relative);
- if ($relative->get_scheme() !== null)
- {
- $target = $relative;
- }
- elseif ($base->get_iri() !== null)
- {
- if ($relative->get_authority() !== null)
- {
- $target = $relative;
- $target->set_scheme($base->get_scheme());
- }
- else
- {
- $target = new SimplePie_IRI('');
- $target->set_scheme($base->get_scheme());
- $target->set_userinfo($base->get_userinfo());
- $target->set_host($base->get_host());
- $target->set_port($base->get_port());
- if ($relative->get_path() !== null)
- {
- if (strpos($relative->get_path(), '/') === 0)
- {
- $target->set_path($relative->get_path());
- }
- elseif (($base->get_userinfo() !== null || $base->get_host() !== null || $base->get_port() !== null) && $base->get_path() === null)
- {
- $target->set_path('/' . $relative->get_path());
- }
- elseif (($last_segment = strrpos($base->get_path(), '/')) !== false)
- {
- $target->set_path(substr($base->get_path(), 0, $last_segment + 1) . $relative->get_path());
- }
- else
- {
- $target->set_path($relative->get_path());
- }
- $target->set_query($relative->get_query());
- }
- else
- {
- $target->set_path($base->get_path());
- if ($relative->get_query() !== null)
- {
- $target->set_query($relative->get_query());
- }
- elseif ($base->get_query() !== null)
- {
- $target->set_query($base->get_query());
- }
- }
- }
- $target->set_fragment($relative->get_fragment());
- }
- else
- {
- // No base URL, just return the relative URL
- $target = $relative;
- }
- }
- else
- {
- $target = $base;
- }
- return $target;
- }
-
- /**
- * Parse an IRI into scheme/authority/path/query/fragment segments
- *
- * @access private
- * @param string $iri
- * @return array
- */
- function parse_iri($iri)
- {
- preg_match('/^(([^:\/?#]+):)?(\/\/([^\/?#]*))?([^?#]*)(\?([^#]*))?(#(.*))?$/', $iri, $match);
- for ($i = count($match); $i <= 9; $i++)
- {
- $match[$i] = '';
- }
- return array('scheme' => $match[2], 'authority' => $match[4], 'path' => $match[5], 'query' => $match[7], 'fragment' => $match[9]);
- }
-
- /**
- * Remove dot segments from a path
- *
- * @access private
- * @param string $input
- * @return string
- */
- function remove_dot_segments($input)
- {
- $output = '';
- while (strpos($input, './') !== false || strpos($input, '/.') !== false || $input === '.' || $input === '..')
- {
- // A: If the input buffer begins with a prefix of "../" or "./", then remove that prefix from the input buffer; otherwise,
- if (strpos($input, '../') === 0)
- {
- $input = substr($input, 3);
- }
- elseif (strpos($input, './') === 0)
- {
- $input = substr($input, 2);
- }
- // B: if the input buffer begins with a prefix of "/./" or "/.", where "." is a complete path segment, then replace that prefix with "/" in the input buffer; otherwise,
- elseif (strpos($input, '/./') === 0)
- {
- $input = substr_replace($input, '/', 0, 3);
- }
- elseif ($input === '/.')
- {
- $input = '/';
- }
- // C: if the input buffer begins with a prefix of "/../" or "/..", where ".." is a complete path segment, then replace that prefix with "/" in the input buffer and remove the last segment and its preceding "/" (if any) from the output buffer; otherwise,
- elseif (strpos($input, '/../') === 0)
- {
- $input = substr_replace($input, '/', 0, 4);
- $output = substr_replace($output, '', strrpos($output, '/'));
- }
- elseif ($input === '/..')
- {
- $input = '/';
- $output = substr_replace($output, '', strrpos($output, '/'));
- }
- // D: if the input buffer consists only of "." or "..", then remove that from the input buffer; otherwise,
- elseif ($input === '.' || $input === '..')
- {
- $input = '';
- }
- // E: move the first path segment in the input buffer to the end of the output buffer, including the initial "/" character (if any) and any subsequent characters up to, but not including, the next "/" character or the end of the input buffer
- elseif (($pos = strpos($input, '/', 1)) !== false)
- {
- $output .= substr($input, 0, $pos);
- $input = substr_replace($input, '', 0, $pos);
- }
- else
- {
- $output .= $input;
- $input = '';
- }
- }
- return $output . $input;
- }
-
- /**
- * Replace invalid character with percent encoding
- *
- * @access private
- * @param string $string Input string
- * @param string $valid_chars Valid characters
- * @param int $case Normalise case
- * @return string
- */
- function replace_invalid_with_pct_encoding($string, $valid_chars, $case = SIMPLEPIE_SAME_CASE)
- {
- // Normalise case
- if ($case & SIMPLEPIE_LOWERCASE)
- {
- $string = strtolower($string);
- }
- elseif ($case & SIMPLEPIE_UPPERCASE)
- {
- $string = strtoupper($string);
- }
-
- // Store position and string length (to avoid constantly recalculating this)
- $position = 0;
- $strlen = strlen($string);
-
- // Loop as long as we have invalid characters, advancing the position to the next invalid character
- while (($position += strspn($string, $valid_chars, $position)) < $strlen)
- {
- // If we have a % character
- if ($string[$position] === '%')
- {
- // If we have a pct-encoded section
- if ($position + 2 < $strlen && strspn($string, '0123456789ABCDEFabcdef', $position + 1, 2) === 2)
- {
- // Get the the represented character
- $chr = chr(hexdec(substr($string, $position + 1, 2)));
-
- // If the character is valid, replace the pct-encoded with the actual character while normalising case
- if (strpos($valid_chars, $chr) !== false)
- {
- if ($case & SIMPLEPIE_LOWERCASE)
- {
- $chr = strtolower($chr);
- }
- elseif ($case & SIMPLEPIE_UPPERCASE)
- {
- $chr = strtoupper($chr);
- }
- $string = substr_replace($string, $chr, $position, 3);
- $strlen -= 2;
- $position++;
- }
-
- // Otherwise just normalise the pct-encoded to uppercase
- else
- {
- $string = substr_replace($string, strtoupper(substr($string, $position + 1, 2)), $position + 1, 2);
- $position += 3;
- }
- }
- // If we don't have a pct-encoded section, just replace the % with its own esccaped form
- else
- {
- $string = substr_replace($string, '%25', $position, 1);
- $strlen += 2;
- $position += 3;
- }
- }
- // If we have an invalid character, change into its pct-encoded form
- else
- {
- $replacement = sprintf("%%%02X", ord($string[$position]));
- $string = str_replace($string[$position], $replacement, $string);
- $strlen = strlen($string);
- }
- }
- return $string;
- }
-
- /**
- * Check if the object represents a valid IRI
- *
- * @access public
- * @return bool
- */
- function is_valid()
- {
- return array_sum($this->valid) === count($this->valid);
- }
-
- /**
- * Set the scheme. Returns true on success, false on failure (if there are
- * any invalid characters).
- *
- * @access public
- * @param string $scheme
- * @return bool
- */
- function set_scheme($scheme)
- {
- if ($scheme === null || $scheme === '')
- {
- $this->scheme = null;
- }
- else
- {
- $len = strlen($scheme);
- switch (true)
- {
- case $len > 1:
- if (!strspn($scheme, 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+-.', 1))
- {
- $this->scheme = null;
- $this->valid[__FUNCTION__] = false;
- return false;
- }
-
- case $len > 0:
- if (!strspn($scheme, 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz', 0, 1))
- {
- $this->scheme = null;
- $this->valid[__FUNCTION__] = false;
- return false;
- }
- }
- $this->scheme = strtolower($scheme);
- }
- $this->valid[__FUNCTION__] = true;
- return true;
- }
-
- /**
- * Set the authority. Returns true on success, false on failure (if there are
- * any invalid characters).
- *
- * @access public
- * @param string $authority
- * @return bool
- */
- function set_authority($authority)
- {
- if (($userinfo_end = strrpos($authority, '@')) !== false)
- {
- $userinfo = substr($authority, 0, $userinfo_end);
- $authority = substr($authority, $userinfo_end + 1);
- }
- else
- {
- $userinfo = null;
- }
-
- if (($port_start = strpos($authority, ':')) !== false)
- {
- $port = substr($authority, $port_start + 1);
- $authority = substr($authority, 0, $port_start);
- }
- else
- {
- $port = null;
- }
-
- return $this->set_userinfo($userinfo) && $this->set_host($authority) && $this->set_port($port);
- }
-
- /**
- * Set the userinfo.
- *
- * @access public
- * @param string $userinfo
- * @return bool
- */
- function set_userinfo($userinfo)
- {
- if ($userinfo === null || $userinfo === '')
- {
- $this->userinfo = null;
- }
- else
- {
- $this->userinfo = $this->replace_invalid_with_pct_encoding($userinfo, 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-._~!$&\'()*+,;=:');
- }
- $this->valid[__FUNCTION__] = true;
- return true;
- }
-
- /**
- * Set the host. Returns true on success, false on failure (if there are
- * any invalid characters).
- *
- * @access public
- * @param string $host
- * @return bool
- */
- function set_host($host)
- {
- if ($host === null || $host === '')
- {
- $this->host = null;
- $this->valid[__FUNCTION__] = true;
- return true;
- }
- elseif ($host[0] === '[' && substr($host, -1) === ']')
- {
- if (Net_IPv6::checkIPv6(substr($host, 1, -1)))
- {
- $this->host = $host;
- $this->valid[__FUNCTION__] = true;
- return true;
- }
- else
- {
- $this->host = null;
- $this->valid[__FUNCTION__] = false;
- return false;
- }
- }
- else
- {
- $this->host = $this->replace_invalid_with_pct_encoding($host, 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-._~!$&\'()*+,;=', SIMPLEPIE_LOWERCASE);
- $this->valid[__FUNCTION__] = true;
- return true;
- }
- }
-
- /**
- * Set the port. Returns true on success, false on failure (if there are
- * any invalid characters).
- *
- * @access public
- * @param string $port
- * @return bool
- */
- function set_port($port)
- {
- if ($port === null || $port === '')
- {
- $this->port = null;
- $this->valid[__FUNCTION__] = true;
- return true;
- }
- elseif (strspn($port, '0123456789') === strlen($port))
- {
- $this->port = (int) $port;
- $this->valid[__FUNCTION__] = true;
- return true;
- }
- else
- {
- $this->port = null;
- $this->valid[__FUNCTION__] = false;
- return false;
- }
- }
-
- /**
- * Set the path.
- *
- * @access public
- * @param string $path
- * @return bool
- */
- function set_path($path)
- {
- if ($path === null || $path === '')
- {
- $this->path = null;
- $this->valid[__FUNCTION__] = true;
- return true;
- }
- elseif (substr($path, 0, 2) === '//' && $this->userinfo === null && $this->host === null && $this->port === null)
- {
- $this->path = null;
- $this->valid[__FUNCTION__] = false;
- return false;
- }
- else
- {
- $this->path = $this->replace_invalid_with_pct_encoding($path, 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-._~!$&\'()*+,;=@/');
- if ($this->scheme !== null)
- {
- $this->path = $this->remove_dot_segments($this->path);
- }
- $this->valid[__FUNCTION__] = true;
- return true;
- }
- }
-
- /**
- * Set the query.
- *
- * @access public
- * @param string $query
- * @return bool
- */
- function set_query($query)
- {
- if ($query === null || $query === '')
- {
- $this->query = null;
- }
- else
- {
- $this->query = $this->replace_invalid_with_pct_encoding($query, 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-._~!$\'()*+,;:@/?');
- }
- $this->valid[__FUNCTION__] = true;
- return true;
- }
-
- /**
- * Set the fragment.
- *
- * @access public
- * @param string $fragment
- * @return bool
- */
- function set_fragment($fragment)
- {
- if ($fragment === null || $fragment === '')
- {
- $this->fragment = null;
- }
- else
- {
- $this->fragment = $this->replace_invalid_with_pct_encoding($fragment, 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-._~!$&\'()*+,;=:@/?');
- }
- $this->valid[__FUNCTION__] = true;
- return true;
- }
-
- /**
- * Get the complete IRI
- *
- * @access public
- * @return string
- */
- function get_iri()
- {
- $iri = '';
- if ($this->scheme !== null)
- {
- $iri .= $this->scheme . ':';
- }
- if (($authority = $this->get_authority()) !== null)
- {
- $iri .= '//' . $authority;
- }
- if ($this->path !== null)
- {
- $iri .= $this->path;
- }
- if ($this->query !== null)
- {
- $iri .= '?' . $this->query;
- }
- if ($this->fragment !== null)
- {
- $iri .= '#' . $this->fragment;
- }
-
- if ($iri !== '')
- {
- return $iri;
- }
- else
- {
- return null;
- }
- }
-
- /**
- * Get the scheme
- *
- * @access public
- * @return string
- */
- function get_scheme()
- {
- return $this->scheme;
- }
-
- /**
- * Get the complete authority
- *
- * @access public
- * @return string
- */
- function get_authority()
- {
- $authority = '';
- if ($this->userinfo !== null)
- {
- $authority .= $this->userinfo . '@';
- }
- if ($this->host !== null)
- {
- $authority .= $this->host;
- }
- if ($this->port !== null)
- {
- $authority .= ':' . $this->port;
- }
-
- if ($authority !== '')
- {
- return $authority;
- }
- else
- {
- return null;
- }
- }
-
- /**
- * Get the user information
- *
- * @access public
- * @return string
- */
- function get_userinfo()
- {
- return $this->userinfo;
- }
-
- /**
- * Get the host
- *
- * @access public
- * @return string
- */
- function get_host()
- {
- return $this->host;
- }
-
- /**
- * Get the port
- *
- * @access public
- * @return string
- */
- function get_port()
- {
- return $this->port;
- }
-
- /**
- * Get the path
- *
- * @access public
- * @return string
- */
- function get_path()
- {
- return $this->path;
- }
-
- /**
- * Get the query
- *
- * @access public
- * @return string
- */
- function get_query()
- {
- return $this->query;
- }
-
- /**
- * Get the fragment
- *
- * @access public
- * @return string
- */
- function get_fragment()
- {
- return $this->fragment;
- }
-}
-
-/**
- * Class to validate and to work with IPv6 addresses.
- *
- * @package SimplePie
- * @copyright 2003-2005 The PHP Group
- * @license http://www.opensource.org/licenses/bsd-license.php
- * @link http://pear.php.net/package/Net_IPv6
- * @author Alexander Merz <alexander.merz@web.de>
- * @author elfrink at introweb dot nl
- * @author Josh Peck <jmp at joshpeck dot org>
- * @author Geoffrey Sneddon <geoffers@gmail.com>
- */
-class SimplePie_Net_IPv6
-{
- /**
- * Removes a possible existing netmask specification of an IP address.
- *
- * @param string $ip the (compressed) IP as Hex representation
- * @return string the IP the without netmask
- * @since 1.1.0
- * @access public
- * @static
- */
- function removeNetmaskSpec($ip)
- {
- if (strpos($ip, '/') !== false)
- {
- list($addr, $nm) = explode('/', $ip);
- }
- else
- {
- $addr = $ip;
- }
- return $addr;
- }
-
- /**
- * Uncompresses an IPv6 address
- *
- * RFC 2373 allows you to compress zeros in an address to '::'. This
- * function expects an valid IPv6 address and expands the '::' to
- * the required zeros.
- *
- * Example: FF01::101 -> FF01:0:0:0:0:0:0:101
- * ::1 -> 0:0:0:0:0:0:0:1
- *
- * @access public
- * @static
- * @param string $ip a valid IPv6-address (hex format)
- * @return string the uncompressed IPv6-address (hex format)
- */
- function Uncompress($ip)
- {
- $uip = SimplePie_Net_IPv6::removeNetmaskSpec($ip);
- $c1 = -1;
- $c2 = -1;
- if (strpos($ip, '::') !== false)
- {
- list($ip1, $ip2) = explode('::', $ip);
- if ($ip1 === '')
- {
- $c1 = -1;
- }
- else
- {
- $pos = 0;
- if (($pos = substr_count($ip1, ':')) > 0)
- {
- $c1 = $pos;
- }
- else
- {
- $c1 = 0;
- }
- }
- if ($ip2 === '')
- {
- $c2 = -1;
- }
- else
- {
- $pos = 0;
- if (($pos = substr_count($ip2, ':')) > 0)
- {
- $c2 = $pos;
- }
- else
- {
- $c2 = 0;
- }
- }
- if (strstr($ip2, '.'))
- {
- $c2++;
- }
- // ::
- if ($c1 === -1 && $c2 === -1)
- {
- $uip = '0:0:0:0:0:0:0:0';
- }
- // ::xxx
- else if ($c1 === -1)
- {
- $fill = str_repeat('0:', 7 - $c2);
- $uip = str_replace('::', $fill, $uip);
- }
- // xxx::
- else if ($c2 === -1)
- {
- $fill = str_repeat(':0', 7 - $c1);
- $uip = str_replace('::', $fill, $uip);
- }
- // xxx::xxx
- else
- {
- $fill = str_repeat(':0:', 6 - $c2 - $c1);
- $uip = str_replace('::', $fill, $uip);
- $uip = str_replace('::', ':', $uip);
- }
- }
- return $uip;
- }
-
- /**
- * Splits an IPv6 address into the IPv6 and a possible IPv4 part
- *
- * RFC 2373 allows you to note the last two parts of an IPv6 address as
- * an IPv4 compatible address
- *
- * Example: 0:0:0:0:0:0:13.1.68.3
- * 0:0:0:0:0:FFFF:129.144.52.38
- *
- * @access public
- * @static
- * @param string $ip a valid IPv6-address (hex format)
- * @return array [0] contains the IPv6 part, [1] the IPv4 part (hex format)
- */
- function SplitV64($ip)
- {
- $ip = SimplePie_Net_IPv6::Uncompress($ip);
- if (strstr($ip, '.'))
- {
- $pos = strrpos($ip, ':');
- $ip[$pos] = '_';
- $ipPart = explode('_', $ip);
- return $ipPart;
- }
- else
- {
- return array($ip, '');
- }
- }
-
- /**
- * Checks an IPv6 address
- *
- * Checks if the given IP is IPv6-compatible
- *
- * @access public
- * @static
- * @param string $ip a valid IPv6-address
- * @return bool true if $ip is an IPv6 address
- */
- function checkIPv6($ip)
- {
- $ipPart = SimplePie_Net_IPv6::SplitV64($ip);
- $count = 0;
- if (!empty($ipPart[0]))
- {
- $ipv6 = explode(':', $ipPart[0]);
- for ($i = 0; $i < count($ipv6); $i++)
- {
- $dec = hexdec($ipv6[$i]);
- $hex = strtoupper(preg_replace('/^[0]{1,3}(.*[0-9a-fA-F])$/', '\\1', $ipv6[$i]));
- if ($ipv6[$i] >= 0 && $dec <= 65535 && $hex === strtoupper(dechex($dec)))
- {
- $count++;
- }
- }
- if ($count === 8)
- {
- return true;
- }
- elseif ($count === 6 && !empty($ipPart[1]))
- {
- $ipv4 = explode('.', $ipPart[1]);
- $count = 0;
- foreach ($ipv4 as $ipv4_part)
- {
- if ($ipv4_part >= 0 && $ipv4_part <= 255 && preg_match('/^\d{1,3}$/', $ipv4_part))
- {
- $count++;
- }
- }
- if ($count === 4)
- {
- return true;
- }
- }
- else
- {
- return false;
- }
-
- }
- else
- {
- return false;
- }
- }
-}
-
-/**
- * Date Parser
- *
- * @package SimplePie
- */
-class SimplePie_Parse_Date
-{
- /**
- * Input data
- *
- * @access protected
- * @var string
- */
- var $date;
-
- /**
- * List of days, calendar day name => ordinal day number in the week
- *
- * @access protected
- * @var array
- */
- var $day = array(
- // English
- 'mon' => 1,
- 'monday' => 1,
- 'tue' => 2,
- 'tuesday' => 2,
- 'wed' => 3,
- 'wednesday' => 3,
- 'thu' => 4,
- 'thursday' => 4,
- 'fri' => 5,
- 'friday' => 5,
- 'sat' => 6,
- 'saturday' => 6,
- 'sun' => 7,
- 'sunday' => 7,
- // Dutch
- 'maandag' => 1,
- 'dinsdag' => 2,
- 'woensdag' => 3,
- 'donderdag' => 4,
- 'vrijdag' => 5,
- 'zaterdag' => 6,
- 'zondag' => 7,
- // French
- 'lundi' => 1,
- 'mardi' => 2,
- 'mercredi' => 3,
- 'jeudi' => 4,
- 'vendredi' => 5,
- 'samedi' => 6,
- 'dimanche' => 7,
- // German
- 'montag' => 1,
- 'dienstag' => 2,
- 'mittwoch' => 3,
- 'donnerstag' => 4,
- 'freitag' => 5,
- 'samstag' => 6,
- 'sonnabend' => 6,
- 'sonntag' => 7,
- // Italian
- 'lunedì' => 1,
- 'martedì' => 2,
- 'mercoledì' => 3,
- 'giovedì' => 4,
- 'venerdì' => 5,
- 'sabato' => 6,
- 'domenica' => 7,
- // Spanish
- 'lunes' => 1,
- 'martes' => 2,
- 'miércoles' => 3,
- 'jueves' => 4,
- 'viernes' => 5,
- 'sábado' => 6,
- 'domingo' => 7,
- // Finnish
- 'maanantai' => 1,
- 'tiistai' => 2,
- 'keskiviikko' => 3,
- 'torstai' => 4,
- 'perjantai' => 5,
- 'lauantai' => 6,
- 'sunnuntai' => 7,
- // Hungarian
- 'hétfő' => 1,
- 'kedd' => 2,
- 'szerda' => 3,
- 'csütörtok' => 4,
- 'péntek' => 5,
- 'szombat' => 6,
- 'vasárnap' => 7,
- // Greek
- 'Δευ' => 1,
- 'Τρι' => 2,
- 'Τετ' => 3,
- 'Πεμ' => 4,
- 'Παρ' => 5,
- 'Σαβ' => 6,
- 'Κυρ' => 7,
- );
-
- /**
- * List of months, calendar month name => calendar month number
- *
- * @access protected
- * @var array
- */
- var $month = array(
- // English
- 'jan' => 1,
- 'january' => 1,
- 'feb' => 2,
- 'february' => 2,
- 'mar' => 3,
- 'march' => 3,
- 'apr' => 4,
- 'april' => 4,
- 'may' => 5,
- // No long form of May
- 'jun' => 6,
- 'june' => 6,
- 'jul' => 7,
- 'july' => 7,
- 'aug' => 8,
- 'august' => 8,
- 'sep' => 9,
- 'september' => 8,
- 'oct' => 10,
- 'october' => 10,
- 'nov' => 11,
- 'november' => 11,
- 'dec' => 12,
- 'december' => 12,
- // Dutch
- 'januari' => 1,
- 'februari' => 2,
- 'maart' => 3,
- 'april' => 4,
- 'mei' => 5,
- 'juni' => 6,
- 'juli' => 7,
- 'augustus' => 8,
- 'september' => 9,
- 'oktober' => 10,
- 'november' => 11,
- 'december' => 12,
- // French
- 'janvier' => 1,
- 'février' => 2,
- 'mars' => 3,
- 'avril' => 4,
- 'mai' => 5,
- 'juin' => 6,
- 'juillet' => 7,
- 'août' => 8,
- 'septembre' => 9,
- 'octobre' => 10,
- 'novembre' => 11,
- 'décembre' => 12,
- // German
- 'januar' => 1,
- 'februar' => 2,
- 'märz' => 3,
- 'april' => 4,
- 'mai' => 5,
- 'juni' => 6,
- 'juli' => 7,
- 'august' => 8,
- 'september' => 9,
- 'oktober' => 10,
- 'november' => 11,
- 'dezember' => 12,
- // Italian
- 'gennaio' => 1,
- 'febbraio' => 2,
- 'marzo' => 3,
- 'aprile' => 4,
- 'maggio' => 5,
- 'giugno' => 6,
- 'luglio' => 7,
- 'agosto' => 8,
- 'settembre' => 9,
- 'ottobre' => 10,
- 'novembre' => 11,
- 'dicembre' => 12,
- // Spanish
- 'enero' => 1,
- 'febrero' => 2,
- 'marzo' => 3,
- 'abril' => 4,
- 'mayo' => 5,
- 'junio' => 6,
- 'julio' => 7,
- 'agosto' => 8,
- 'septiembre' => 9,
- 'setiembre' => 9,
- 'octubre' => 10,
- 'noviembre' => 11,
- 'diciembre' => 12,
- // Finnish
- 'tammikuu' => 1,
- 'helmikuu' => 2,
- 'maaliskuu' => 3,
- 'huhtikuu' => 4,
- 'toukokuu' => 5,
- 'kesäkuu' => 6,
- 'heinäkuu' => 7,
- 'elokuu' => 8,
- 'suuskuu' => 9,
- 'lokakuu' => 10,
- 'marras' => 11,
- 'joulukuu' => 12,
- // Hungarian
- 'január' => 1,
- 'február' => 2,
- 'március' => 3,
- 'április' => 4,
- 'május' => 5,
- 'június' => 6,
- 'július' => 7,
- 'augusztus' => 8,
- 'szeptember' => 9,
- 'október' => 10,
- 'november' => 11,
- 'december' => 12,
- // Greek
- 'Ιαν' => 1,
- 'Φεβ' => 2,
- 'Μάώ' => 3,
- 'Μαώ' => 3,
- 'Απρ' => 4,
- 'Μάι' => 5,
- 'Μαϊ' => 5,
- 'Μαι' => 5,
- 'Ιούν' => 6,
- 'Ιον' => 6,
- 'Ιούλ' => 7,
- 'Ιολ' => 7,
- 'Αύγ' => 8,
- 'Αυγ' => 8,
- 'Σεπ' => 9,
- 'Οκτ' => 10,
- 'Νοέ' => 11,
- 'Δεκ' => 12,
- );
-
- /**
- * List of timezones, abbreviation => offset from UTC
- *
- * @access protected
- * @var array
- */
- var $timezone = array(
- 'ACDT' => 37800,
- 'ACIT' => 28800,
- 'ACST' => 34200,
- 'ACT' => -18000,
- 'ACWDT' => 35100,
- 'ACWST' => 31500,
- 'AEDT' => 39600,
- 'AEST' => 36000,
- 'AFT' => 16200,
- 'AKDT' => -28800,
- 'AKST' => -32400,
- 'AMDT' => 18000,
- 'AMT' => -14400,
- 'ANAST' => 46800,
- 'ANAT' => 43200,
- 'ART' => -10800,
- 'AZOST' => -3600,
- 'AZST' => 18000,
- 'AZT' => 14400,
- 'BIOT' => 21600,
- 'BIT' => -43200,
- 'BOT' => -14400,
- 'BRST' => -7200,
- 'BRT' => -10800,
- 'BST' => 3600,
- 'BTT' => 21600,
- 'CAST' => 18000,
- 'CAT' => 7200,
- 'CCT' => 23400,
- 'CDT' => -18000,
- 'CEDT' => 7200,
- 'CET' => 3600,
- 'CGST' => -7200,
- 'CGT' => -10800,
- 'CHADT' => 49500,
- 'CHAST' => 45900,
- 'CIST' => -28800,
- 'CKT' => -36000,
- 'CLDT' => -10800,
- 'CLST' => -14400,
- 'COT' => -18000,
- 'CST' => -21600,
- 'CVT' => -3600,
- 'CXT' => 25200,
- 'DAVT' => 25200,
- 'DTAT' => 36000,
- 'EADT' => -18000,
- 'EAST' => -21600,
- 'EAT' => 10800,
- 'ECT' => -18000,
- 'EDT' => -14400,
- 'EEST' => 10800,
- 'EET' => 7200,
- 'EGT' => -3600,
- 'EKST' => 21600,
- 'EST' => -18000,
- 'FJT' => 43200,
- 'FKDT' => -10800,
- 'FKST' => -14400,
- 'FNT' => -7200,
- 'GALT' => -21600,
- 'GEDT' => 14400,
- 'GEST' => 10800,
- 'GFT' => -10800,
- 'GILT' => 43200,
- 'GIT' => -32400,
- 'GST' => 14400,
- 'GST' => -7200,
- 'GYT' => -14400,
- 'HAA' => -10800,
- 'HAC' => -18000,
- 'HADT' => -32400,
- 'HAE' => -14400,
- 'HAP' => -25200,
- 'HAR' => -21600,
- 'HAST' => -36000,
- 'HAT' => -9000,
- 'HAY' => -28800,
- 'HKST' => 28800,
- 'HMT' => 18000,
- 'HNA' => -14400,
- 'HNC' => -21600,
- 'HNE' => -18000,
- 'HNP' => -28800,
- 'HNR' => -25200,
- 'HNT' => -12600,
- 'HNY' => -32400,
- 'IRDT' => 16200,
- 'IRKST' => 32400,
- 'IRKT' => 28800,
- 'IRST' => 12600,
- 'JFDT' => -10800,
- 'JFST' => -14400,
- 'JST' => 32400,
- 'KGST' => 21600,
- 'KGT' => 18000,
- 'KOST' => 39600,
- 'KOVST' => 28800,
- 'KOVT' => 25200,
- 'KRAST' => 28800,
- 'KRAT' => 25200,
- 'KST' => 32400,
- 'LHDT' => 39600,
- 'LHST' => 37800,
- 'LINT' => 50400,
- 'LKT' => 21600,
- 'MAGST' => 43200,
- 'MAGT' => 39600,
- 'MAWT' => 21600,
- 'MDT' => -21600,
- 'MESZ' => 7200,
- 'MEZ' => 3600,
- 'MHT' => 43200,
- 'MIT' => -34200,
- 'MNST' => 32400,
- 'MSDT' => 14400,
- 'MSST' => 10800,
- 'MST' => -25200,
- 'MUT' => 14400,
- 'MVT' => 18000,
- 'MYT' => 28800,
- 'NCT' => 39600,
- 'NDT' => -9000,
- 'NFT' => 41400,
- 'NMIT' => 36000,
- 'NOVST' => 25200,
- 'NOVT' => 21600,
- 'NPT' => 20700,
- 'NRT' => 43200,
- 'NST' => -12600,
- 'NUT' => -39600,
- 'NZDT' => 46800,
- 'NZST' => 43200,
- 'OMSST' => 25200,
- 'OMST' => 21600,
- 'PDT' => -25200,
- 'PET' => -18000,
- 'PETST' => 46800,
- 'PETT' => 43200,
- 'PGT' => 36000,
- 'PHOT' => 46800,
- 'PHT' => 28800,
- 'PKT' => 18000,
- 'PMDT' => -7200,
- 'PMST' => -10800,
- 'PONT' => 39600,
- 'PST' => -28800,
- 'PWT' => 32400,
- 'PYST' => -10800,
- 'PYT' => -14400,
- 'RET' => 14400,
- 'ROTT' => -10800,
- 'SAMST' => 18000,
- 'SAMT' => 14400,
- 'SAST' => 7200,
- 'SBT' => 39600,
- 'SCDT' => 46800,
- 'SCST' => 43200,
- 'SCT' => 14400,
- 'SEST' => 3600,
- 'SGT' => 28800,
- 'SIT' => 28800,
- 'SRT' => -10800,
- 'SST' => -39600,
- 'SYST' => 10800,
- 'SYT' => 7200,
- 'TFT' => 18000,
- 'THAT' => -36000,
- 'TJT' => 18000,
- 'TKT' => -36000,
- 'TMT' => 18000,
- 'TOT' => 46800,
- 'TPT' => 32400,
- 'TRUT' => 36000,
- 'TVT' => 43200,
- 'TWT' => 28800,
- 'UYST' => -7200,
- 'UYT' => -10800,
- 'UZT' => 18000,
- 'VET' => -14400,
- 'VLAST' => 39600,
- 'VLAT' => 36000,
- 'VOST' => 21600,
- 'VUT' => 39600,
- 'WAST' => 7200,
- 'WAT' => 3600,
- 'WDT' => 32400,
- 'WEST' => 3600,
- 'WFT' => 43200,
- 'WIB' => 25200,
- 'WIT' => 32400,
- 'WITA' => 28800,
- 'WKST' => 18000,
- 'WST' => 28800,
- 'YAKST' => 36000,
- 'YAKT' => 32400,
- 'YAPT' => 36000,
- 'YEKST' => 21600,
- 'YEKT' => 18000,
- );
-
- /**
- * Cached PCRE for SimplePie_Parse_Date::$day
- *
- * @access protected
- * @var string
- */
- var $day_pcre;
-
- /**
- * Cached PCRE for SimplePie_Parse_Date::$month
- *
- * @access protected
- * @var string
- */
- var $month_pcre;
-
- /**
- * Array of user-added callback methods
- *
- * @access private
- * @var array
- */
- var $built_in = array();
-
- /**
- * Array of user-added callback methods
- *
- * @access private
- * @var array
- */
- var $user = array();
-
- /**
- * Create new SimplePie_Parse_Date object, and set self::day_pcre,
- * self::month_pcre, and self::built_in
- *
- * @access private
- */
- function SimplePie_Parse_Date()
- {
- $this->day_pcre = '(' . implode(array_keys($this->day), '|') . ')';
- $this->month_pcre = '(' . implode(array_keys($this->month), '|') . ')';
-
- static $cache;
- if (!isset($cache[get_class($this)]))
- {
- $all_methods = get_class_methods($this);
-
- foreach ($all_methods as $method)
- {
- if (strtolower(substr($method, 0, 5)) === 'date_')
- {
- $cache[get_class($this)][] = $method;
- }
- }
- }
-
- foreach ($cache[get_class($this)] as $method)
- {
- $this->built_in[] = $method;
- }
- }
-
- /**
- * Get the object
- *
- * @access public
- */
- function get()
- {
- static $object;
- if (!$object)
- {
- $object = new SimplePie_Parse_Date;
- }
- return $object;
- }
-
- /**
- * Parse a date
- *
- * @final
- * @access public
- * @param string $date Date to parse
- * @return int Timestamp corresponding to date string, or false on failure
- */
- function parse($date)
- {
- foreach ($this->user as $method)
- {
- if (($returned = call_user_func($method, $date)) !== false)
- {
- return $returned;
- }
- }
-
- foreach ($this->built_in as $method)
- {
- if (($returned = call_user_func(array(&$this, $method), $date)) !== false)
- {
- return $returned;
- }
- }
-
- return false;
- }
-
- /**
- * Add a callback method to parse a date
- *
- * @final
- * @access public
- * @param callback $callback
- */
- function add_callback($callback)
- {
- if (is_callable($callback))
- {
- $this->user[] = $callback;
- }
- else
- {
- trigger_error('User-supplied function must be a valid callback', E_USER_WARNING);
- }
- }
-
- /**
- * Parse a superset of W3C-DTF (allows hyphens and colons to be omitted, as
- * well as allowing any of upper or lower case "T", horizontal tabs, or
- * spaces to be used as the time seperator (including more than one))
- *
- * @access protected
- * @return int Timestamp
- */
- function date_w3cdtf($date)
- {
- static $pcre;
- if (!$pcre)
- {
- $year = '([0-9]{4})';
- $month = $day = $hour = $minute = $second = '([0-9]{2})';
- $decimal = '([0-9]*)';
- $zone = '(?:(Z)|([+\-])([0-9]{1,2}):?([0-9]{1,2}))';
- $pcre = '/^' . $year . '(?:-?' . $month . '(?:-?' . $day . '(?:[Tt\x09\x20]+' . $hour . '(?::?' . $minute . '(?::?' . $second . '(?:.' . $decimal . ')?)?)?' . $zone . ')?)?)?$/';
- }
- if (preg_match($pcre, $date, $match))
- {
- /*
- Capturing subpatterns:
- 1: Year
- 2: Month
- 3: Day
- 4: Hour
- 5: Minute
- 6: Second
- 7: Decimal fraction of a second
- 8: Zulu
- 9: Timezone ±
- 10: Timezone hours
- 11: Timezone minutes
- */
-
- // Fill in empty matches
- for ($i = count($match); $i <= 3; $i++)
- {
- $match[$i] = '1';
- }
-
- for ($i = count($match); $i <= 7; $i++)
- {
- $match[$i] = '0';
- }
-
- // Numeric timezone
- if (isset($match[9]) && $match[9] !== '')
- {
- $timezone = $match[10] * 3600;
- $timezone += $match[11] * 60;
- if ($match[9] === '-')
- {
- $timezone = 0 - $timezone;
- }
- }
- else
- {
- $timezone = 0;
- }
-
- // Convert the number of seconds to an integer, taking decimals into account
- $second = round($match[6] + $match[7] / pow(10, strlen($match[7])));
-
- return gmmktime($match[4], $match[5], $second, $match[2], $match[3], $match[1]) - $timezone;
- }
- else
- {
- return false;
- }
- }
-
- /**
- * Remove RFC822 comments
- *
- * @access protected
- * @param string $data Data to strip comments from
- * @return string Comment stripped string
- */
- function remove_rfc2822_comments($string)
- {
- $string = (string) $string;
- $position = 0;
- $length = strlen($string);
- $depth = 0;
-
- $output = '';
-
- while ($position < $length && ($pos = strpos($string, '(', $position)) !== false)
- {
- $output .= substr($string, $position, $pos - $position);
- $position = $pos + 1;
- if ($string[$pos - 1] !== '\\')
- {
- $depth++;
- while ($depth && $position < $length)
- {
- $position += strcspn($string, '()', $position);
- if ($string[$position - 1] === '\\')
- {
- $position++;
- continue;
- }
- elseif (isset($string[$position]))
- {
- switch ($string[$position])
- {
- case '(':
- $depth++;
- break;
-
- case ')':
- $depth--;
- break;
- }
- $position++;
- }
- else
- {
- break;
- }
- }
- }
- else
- {
- $output .= '(';
- }
- }
- $output .= substr($string, $position);
-
- return $output;
- }
-
- /**
- * Parse RFC2822's date format
- *
- * @access protected
- * @return int Timestamp
- */
- function date_rfc2822($date)
- {
- static $pcre;
- if (!$pcre)
- {
- $wsp = '[\x09\x20]';
- $fws = '(?:' . $wsp . '+|' . $wsp . '*(?:\x0D\x0A' . $wsp . '+)+)';
- $optional_fws = $fws . '?';
- $day_name = $this->day_pcre;
- $month = $this->month_pcre;
- $day = '([0-9]{1,2})';
- $hour = $minute = $second = '([0-9]{2})';
- $year = '([0-9]{2,4})';
- $num_zone = '([+\-])([0-9]{2})([0-9]{2})';
- $character_zone = '([A-Z]{1,5})';
- $zone = '(?:' . $num_zone . '|' . $character_zone . ')';
- $pcre = '/(?:' . $optional_fws . $day_name . $optional_fws . ',)?' . $optional_fws . $day . $fws . $month . $fws . $year . $fws . $hour . $optional_fws . ':' . $optional_fws . $minute . '(?:' . $optional_fws . ':' . $optional_fws . $second . ')?' . $fws . $zone . '/i';
- }
- if (preg_match($pcre, $this->remove_rfc2822_comments($date), $match))
- {
- /*
- Capturing subpatterns:
- 1: Day name
- 2: Day
- 3: Month
- 4: Year
- 5: Hour
- 6: Minute
- 7: Second
- 8: Timezone ±
- 9: Timezone hours
- 10: Timezone minutes
- 11: Alphabetic timezone
- */
-
- // Find the month number
- $month = $this->month[strtolower($match[3])];
-
- // Numeric timezone
- if ($match[8] !== '')
- {
- $timezone = $match[9] * 3600;
- $timezone += $match[10] * 60;
- if ($match[8] === '-')
- {
- $timezone = 0 - $timezone;
- }
- }
- // Character timezone
- elseif (isset($this->timezone[strtoupper($match[11])]))
- {
- $timezone = $this->timezone[strtoupper($match[11])];
- }
- // Assume everything else to be -0000
- else
- {
- $timezone = 0;
- }
-
- // Deal with 2/3 digit years
- if ($match[4] < 50)
- {
- $match[4] += 2000;
- }
- elseif ($match[4] < 1000)
- {
- $match[4] += 1900;
- }
-
- // Second is optional, if it is empty set it to zero
- if ($match[7] !== '')
- {
- $second = $match[7];
- }
- else
- {
- $second = 0;
- }
-
- return gmmktime($match[5], $match[6], $second, $month, $match[2], $match[4]) - $timezone;
- }
- else
- {
- return false;
- }
- }
-
- /**
- * Parse RFC850's date format
- *
- * @access protected
- * @return int Timestamp
- */
- function date_rfc850($date)
- {
- static $pcre;
- if (!$pcre)
- {
- $space = '[\x09\x20]+';
- $day_name = $this->day_pcre;
- $month = $this->month_pcre;
- $day = '([0-9]{1,2})';
- $year = $hour = $minute = $second = '([0-9]{2})';
- $zone = '([A-Z]{1,5})';
- $pcre = '/^' . $day_name . ',' . $space . $day . '-' . $month . '-' . $year . $space . $hour . ':' . $minute . ':' . $second . $space . $zone . '$/i';
- }
- if (preg_match($pcre, $date, $match))
- {
- /*
- Capturing subpatterns:
- 1: Day name
- 2: Day
- 3: Month
- 4: Year
- 5: Hour
- 6: Minute
- 7: Second
- 8: Timezone
- */
-
- // Month
- $month = $this->month[strtolower($match[3])];
-
- // Character timezone
- if (isset($this->timezone[strtoupper($match[8])]))
- {
- $timezone = $this->timezone[strtoupper($match[8])];
- }
- // Assume everything else to be -0000
- else
- {
- $timezone = 0;
- }
-
- // Deal with 2 digit year
- if ($match[4] < 50)
- {
- $match[4] += 2000;
- }
- else
- {
- $match[4] += 1900;
- }
-
- return gmmktime($match[5], $match[6], $match[7], $month, $match[2], $match[4]) - $timezone;
- }
- else
- {
- return false;
- }
- }
-
- /**
- * Parse C99's asctime()'s date format
- *
- * @access protected
- * @return int Timestamp
- */
- function date_asctime($date)
- {
- static $pcre;
- if (!$pcre)
- {
- $space = '[\x09\x20]+';
- $wday_name = $this->day_pcre;
- $mon_name = $this->month_pcre;
- $day = '([0-9]{1,2})';
- $hour = $sec = $min = '([0-9]{2})';
- $year = '([0-9]{4})';
- $terminator = '\x0A?\x00?';
- $pcre = '/^' . $wday_name . $space . $mon_name . $space . $day . $space . $hour . ':' . $min . ':' . $sec . $space . $year . $terminator . '$/i';
- }
- if (preg_match($pcre, $date, $match))
- {
- /*
- Capturing subpatterns:
- 1: Day name
- 2: Month
- 3: Day
- 4: Hour
- 5: Minute
- 6: Second
- 7: Year
- */
-
- $month = $this->month[strtolower($match[2])];
- return gmmktime($match[4], $match[5], $match[6], $month, $match[3], $match[7]);
- }
- else
- {
- return false;
- }
- }
-
- /**
- * Parse dates using strtotime()
- *
- * @access protected
- * @return int Timestamp
- */
- function date_strtotime($date)
- {
- $strtotime = strtotime($date);
- if ($strtotime === -1 || $strtotime === false)
- {
- return false;
- }
- else
- {
- return $strtotime;
- }
- }
-}
-
-/**
- * Content-type sniffing
- *
- * @package SimplePie
- */
-class SimplePie_Content_Type_Sniffer
-{
- /**
- * File object
- *
- * @var SimplePie_File
- * @access private
- */
- var $file;
-
- /**
- * Create an instance of the class with the input file
- *
- * @access public
- * @param SimplePie_Content_Type_Sniffer $file Input file
- */
- function SimplePie_Content_Type_Sniffer($file)
- {
- $this->file = $file;
- }
-
- /**
- * Get the Content-Type of the specified file
- *
- * @access public
- * @return string Actual Content-Type
- */
- function get_type()
- {
- if (isset($this->file->headers['content-type']))
- {
- if (!isset($this->file->headers['content-encoding'])
- && ($this->file->headers['content-type'] === 'text/plain'
- || $this->file->headers['content-type'] === 'text/plain; charset=ISO-8859-1'
- || $this->file->headers['content-type'] === 'text/plain; charset=iso-8859-1'))
- {
- return $this->text_or_binary();
- }
-
- if (($pos = strpos($this->file->headers['content-type'], ';')) !== false)
- {
- $official = substr($this->file->headers['content-type'], 0, $pos);
- }
- else
- {
- $official = $this->file->headers['content-type'];
- }
- $official = strtolower($official);
-
- if ($official === 'unknown/unknown'
- || $official === 'application/unknown')
- {
- return $this->unknown();
- }
- elseif (substr($official, -4) === '+xml'
- || $official === 'text/xml'
- || $official === 'application/xml')
- {
- return $official;
- }
- elseif (substr($official, 0, 6) === 'image/')
- {
- if ($return = $this->image())
- {
- return $return;
- }
- else
- {
- return $official;
- }
- }
- elseif ($official === 'text/html')
- {
- return $this->feed_or_html();
- }
- else
- {
- return $official;
- }
- }
- else
- {
- return $this->unknown();
- }
- }
-
- /**
- * Sniff text or binary
- *
- * @access private
- * @return string Actual Content-Type
- */
- function text_or_binary()
- {
- if (substr($this->file->body, 0, 2) === "\xFE\xFF"
- || substr($this->file->body, 0, 2) === "\xFF\xFE"
- || substr($this->file->body, 0, 4) === "\x00\x00\xFE\xFF"
- || substr($this->file->body, 0, 3) === "\xEF\xBB\xBF")
- {
- return 'text/plain';
- }
- elseif (preg_match('/[\x00-\x08\x0E-\x1A\x1C-\x1F]/', $this->file->body))
- {
- return 'application/octect-stream';
- }
- else
- {
- return 'text/plain';
- }
- }
-
- /**
- * Sniff unknown
- *
- * @access private
- * @return string Actual Content-Type
- */
- function unknown()
- {
- $ws = strspn($this->file->body, "\x09\x0A\x0B\x0C\x0D\x20");
- if (strtolower(substr($this->file->body, $ws, 14)) === '<!doctype html'
- || strtolower(substr($this->file->body, $ws, 5)) === '<html'
- || strtolower(substr($this->file->body, $ws, 7)) === '<script')
- {
- return 'text/html';
- }
- elseif (substr($this->file->body, 0, 5) === '%PDF-')
- {
- return 'application/pdf';
- }
- elseif (substr($this->file->body, 0, 11) === '%!PS-Adobe-')
- {
- return 'application/postscript';
- }
- elseif (substr($this->file->body, 0, 6) === 'GIF87a'
- || substr($this->file->body, 0, 6) === 'GIF89a')
- {
- return 'image/gif';
- }
- elseif (substr($this->file->body, 0, 8) === "\x89\x50\x4E\x47\x0D\x0A\x1A\x0A")
- {
- return 'image/png';
- }
- elseif (substr($this->file->body, 0, 3) === "\xFF\xD8\xFF")
- {
- return 'image/jpeg';
- }
- elseif (substr($this->file->body, 0, 2) === "\x42\x4D")
- {
- return 'image/bmp';
- }
- else
- {
- return $this->text_or_binary();
- }
- }
-
- /**
- * Sniff images
- *
- * @access private
- * @return string Actual Content-Type
- */
- function image()
- {
- if (substr($this->file->body, 0, 6) === 'GIF87a'
- || substr($this->file->body, 0, 6) === 'GIF89a')
- {
- return 'image/gif';
- }
- elseif (substr($this->file->body, 0, 8) === "\x89\x50\x4E\x47\x0D\x0A\x1A\x0A")
- {
- return 'image/png';
- }
- elseif (substr($this->file->body, 0, 3) === "\xFF\xD8\xFF")
- {
- return 'image/jpeg';
- }
- elseif (substr($this->file->body, 0, 2) === "\x42\x4D")
- {
- return 'image/bmp';
- }
- else
- {
- return false;
- }
- }
-
- /**
- * Sniff HTML
- *
- * @access private
- * @return string Actual Content-Type
- */
- function feed_or_html()
- {
- $len = strlen($this->file->body);
- $pos = strspn($this->file->body, "\x09\x0A\x0D\x20");
-
- while ($pos < $len)
- {
- switch ($this->file->body[$pos])
- {
- case "\x09":
- case "\x0A":
- case "\x0D":
- case "\x20":
- $pos += strspn($this->file->body, "\x09\x0A\x0D\x20", $pos);
- continue 2;
-
- case '<':
- $pos++;
- break;
-
- default:
- return 'text/html';
- }
-
- if (substr($this->file->body, $pos, 3) === '!--')
- {
- $pos += 3;
- if ($pos < $len && ($pos = strpos($this->file->body, '-->', $pos)) !== false)
- {
- $pos += 3;
- }
- else
- {
- return 'text/html';
- }
- }
- elseif (substr($this->file->body, $pos, 1) === '!')
- {
- if ($pos < $len && ($pos = strpos($this->file->body, '>', $pos)) !== false)
- {
- $pos++;
- }
- else
- {
- return 'text/html';
- }
- }
- elseif (substr($this->file->body, $pos, 1) === '?')
- {
- if ($pos < $len && ($pos = strpos($this->file->body, '?>', $pos)) !== false)
- {
- $pos += 2;
- }
- else
- {
- return 'text/html';
- }
- }
- elseif (substr($this->file->body, $pos, 3) === 'rss'
- || substr($this->file->body, $pos, 7) === 'rdf:RDF')
- {
- return 'application/rss+xml';
- }
- elseif (substr($this->file->body, $pos, 4) === 'feed')
- {
- return 'application/atom+xml';
- }
- else
- {
- return 'text/html';
- }
- }
-
- return 'text/html';
- }
-}
-
-/**
- * Parses the XML Declaration
- *
- * @package SimplePie
- */
-class SimplePie_XML_Declaration_Parser
-{
- /**
- * XML Version
- *
- * @access public
- * @var string
- */
- var $version = '1.0';
-
- /**
- * Encoding
- *
- * @access public
- * @var string
- */
- var $encoding = 'UTF-8';
-
- /**
- * Standalone
- *
- * @access public
- * @var bool
- */
- var $standalone = false;
-
- /**
- * Current state of the state machine
- *
- * @access private
- * @var string
- */
- var $state = 'before_version_name';
-
- /**
- * Input data
- *
- * @access private
- * @var string
- */
- var $data = '';
-
- /**
- * Input data length (to avoid calling strlen() everytime this is needed)
- *
- * @access private
- * @var int
- */
- var $data_length = 0;
-
- /**
- * Current position of the pointer
- *
- * @var int
- * @access private
- */
- var $position = 0;
-
- /**
- * Create an instance of the class with the input data
- *
- * @access public
- * @param string $data Input data
- */
- function SimplePie_XML_Declaration_Parser($data)
- {
- $this->data = $data;
- $this->data_length = strlen($this->data);
- }
-
- /**
- * Parse the input data
- *
- * @access public
- * @return bool true on success, false on failure
- */
- function parse()
- {
- while ($this->state && $this->state !== 'emit' && $this->has_data())
- {
- $state = $this->state;
- $this->$state();
- }
- $this->data = '';
- if ($this->state === 'emit')
- {
- return true;
- }
- else
- {
- $this->version = '';
- $this->encoding = '';
- $this->standalone = '';
- return false;
- }
- }
-
- /**
- * Check whether there is data beyond the pointer
- *
- * @access private
- * @return bool true if there is further data, false if not
- */
- function has_data()
- {
- return (bool) ($this->position < $this->data_length);
- }
-
- /**
- * Advance past any whitespace
- *
- * @return int Number of whitespace characters passed
- */
- function skip_whitespace()
- {
- $whitespace = strspn($this->data, "\x09\x0A\x0D\x20", $this->position);
- $this->position += $whitespace;
- return $whitespace;
- }
-
- /**
- * Read value
- */
- function get_value()
- {
- $quote = substr($this->data, $this->position, 1);
- if ($quote === '"' || $quote === "'")
- {
- $this->position++;
- $len = strcspn($this->data, $quote, $this->position);
- if ($this->has_data())
- {
- $value = substr($this->data, $this->position, $len);
- $this->position += $len + 1;
- return $value;
- }
- }
- return false;
- }
-
- function before_version_name()
- {
- if ($this->skip_whitespace())
- {
- $this->state = 'version_name';
- }
- else
- {
- $this->state = false;
- }
- }
-
- function version_name()
- {
- if (substr($this->data, $this->position, 7) === 'version')
- {
- $this->position += 7;
- $this->skip_whitespace();
- $this->state = 'version_equals';
- }
- else
- {
- $this->state = false;
- }
- }
-
- function version_equals()
- {
- if (substr($this->data, $this->position, 1) === '=')
- {
- $this->position++;
- $this->skip_whitespace();
- $this->state = 'version_value';
- }
- else
- {
- $this->state = false;
- }
- }
-
- function version_value()
- {
- if ($this->version = $this->get_value())
- {
- $this->skip_whitespace();
- if ($this->has_data())
- {
- $this->state = 'encoding_name';
- }
- else
- {
- $this->state = 'emit';
- }
- }
- else
- {
- $this->state = false;
- }
- }
-
- function encoding_name()
- {
- if (substr($this->data, $this->position, 8) === 'encoding')
- {
- $this->position += 8;
- $this->skip_whitespace();
- $this->state = 'encoding_equals';
- }
- else
- {
- $this->state = 'standalone_name';
- }
- }
-
- function encoding_equals()
- {
- if (substr($this->data, $this->position, 1) === '=')
- {
- $this->position++;
- $this->skip_whitespace();
- $this->state = 'encoding_value';
- }
- else
- {
- $this->state = false;
- }
- }
-
- function encoding_value()
- {
- if ($this->encoding = $this->get_value())
- {
- $this->skip_whitespace();
- if ($this->has_data())
- {
- $this->state = 'standalone_name';
- }
- else
- {
- $this->state = 'emit';
- }
- }
- else
- {
- $this->state = false;
- }
- }
-
- function standalone_name()
- {
- if (substr($this->data, $this->position, 10) === 'standalone')
- {
- $this->position += 10;
- $this->skip_whitespace();
- $this->state = 'standalone_equals';
- }
- else
- {
- $this->state = false;
- }
- }
-
- function standalone_equals()
- {
- if (substr($this->data, $this->position, 1) === '=')
- {
- $this->position++;
- $this->skip_whitespace();
- $this->state = 'standalone_value';
- }
- else
- {
- $this->state = false;
- }
- }
-
- function standalone_value()
- {
- if ($standalone = $this->get_value())
- {
- switch ($standalone)
- {
- case 'yes':
- $this->standalone = true;
- break;
-
- case 'no':
- $this->standalone = false;
- break;
-
- default:
- $this->state = false;
- return;
- }
-
- $this->skip_whitespace();
- if ($this->has_data())
- {
- $this->state = false;
- }
- else
- {
- $this->state = 'emit';
- }
- }
- else
- {
- $this->state = false;
- }
- }
-}
-
-class SimplePie_Locator
-{
- var $useragent;
- var $timeout;
- var $file;
- var $local = array();
- var $elsewhere = array();
- var $file_class = 'SimplePie_File';
- var $cached_entities = array();
- var $http_base;
- var $base;
- var $base_location = 0;
- var $checked_feeds = 0;
- var $max_checked_feeds = 10;
- var $content_type_sniffer_class = 'SimplePie_Content_Type_Sniffer';
-
- function SimplePie_Locator(&$file, $timeout = 10, $useragent = null, $file_class = 'SimplePie_File', $max_checked_feeds = 10, $content_type_sniffer_class = 'SimplePie_Content_Type_Sniffer')
- {
- $this->file =& $file;
- $this->file_class = $file_class;
- $this->useragent = $useragent;
- $this->timeout = $timeout;
- $this->max_checked_feeds = $max_checked_feeds;
- $this->content_type_sniffer_class = $content_type_sniffer_class;
- }
-
- function find($type = SIMPLEPIE_LOCATOR_ALL, &$working)
- {
- if ($this->is_feed($this->file))
- {
- return $this->file;
- }
-
- if ($this->file->method & SIMPLEPIE_FILE_SOURCE_REMOTE)
- {
- $sniffer = new $this->content_type_sniffer_class($this->file);
- if ($sniffer->get_type() !== 'text/html')
- {
- return null;
- }
- }
-
- if ($type & ~SIMPLEPIE_LOCATOR_NONE)
- {
- $this->get_base();
- }
-
- if ($type & SIMPLEPIE_LOCATOR_AUTODISCOVERY && $working = $this->autodiscovery())
- {
- return $working[0];
- }
-
- if ($type & (SIMPLEPIE_LOCATOR_LOCAL_EXTENSION | SIMPLEPIE_LOCATOR_LOCAL_BODY | SIMPLEPIE_LOCATOR_REMOTE_EXTENSION | SIMPLEPIE_LOCATOR_REMOTE_BODY) && $this->get_links())
- {
- if ($type & SIMPLEPIE_LOCATOR_LOCAL_EXTENSION && $working = $this->extension($this->local))
- {
- return $working;
- }
-
- if ($type & SIMPLEPIE_LOCATOR_LOCAL_BODY && $working = $this->body($this->local))
- {
- return $working;
- }
-
- if ($type & SIMPLEPIE_LOCATOR_REMOTE_EXTENSION && $working = $this->extension($this->elsewhere))
- {
- return $working;
- }
-
- if ($type & SIMPLEPIE_LOCATOR_REMOTE_BODY && $working = $this->body($this->elsewhere))
- {
- return $working;
- }
- }
- return null;
- }
-
- function is_feed(&$file)
- {
- if ($file->method & SIMPLEPIE_FILE_SOURCE_REMOTE)
- {
- $sniffer = new $this->content_type_sniffer_class($file);
- $sniffed = $sniffer->get_type();
- if (in_array($sniffed, array('application/rss+xml', 'application/rdf+xml', 'text/rdf', 'application/atom+xml', 'text/xml', 'application/xml')))
- {
- return true;
- }
- else
- {
- return false;
- }
- }
- elseif ($file->method & SIMPLEPIE_FILE_SOURCE_LOCAL)
- {
- return true;
- }
- else
- {
- return false;
- }
- }
-
- function get_base()
- {
- $this->http_base = $this->file->url;
- $this->base = $this->http_base;
- $elements = SimplePie_Misc::get_element('base', $this->file->body);
- foreach ($elements as $element)
- {
- if ($element['attribs']['href']['data'] !== '')
- {
- $this->base = SimplePie_Misc::absolutize_url(trim($element['attribs']['href']['data']), $this->http_base);
- $this->base_location = $element['offset'];
- break;
- }
- }
- }
-
- function autodiscovery()
- {
- $links = array_merge(SimplePie_Misc::get_element('link', $this->file->body), SimplePie_Misc::get_element('a', $this->file->body), SimplePie_Misc::get_element('area', $this->file->body));
- $done = array();
- $feeds = array();
- foreach ($links as $link)
- {
- if ($this->checked_feeds === $this->max_checked_feeds)
- {
- break;
- }
- if (isset($link['attribs']['href']['data']) && isset($link['attribs']['rel']['data']))
- {
- $rel = array_unique(SimplePie_Misc::space_seperated_tokens(strtolower($link['attribs']['rel']['data'])));
-
- if ($this->base_location < $link['offset'])
- {
- $href = SimplePie_Misc::absolutize_url(trim($link['attribs']['href']['data']), $this->base);
- }
- else
- {
- $href = SimplePie_Misc::absolutize_url(trim($link['attribs']['href']['data']), $this->http_base);
- }
-
- if (!in_array($href, $done) && in_array('feed', $rel) || (in_array('alternate', $rel) && !empty($link['attribs']['type']['data']) && in_array(strtolower(SimplePie_Misc::parse_mime($link['attribs']['type']['data'])), array('application/rss+xml', 'application/atom+xml'))) && !isset($feeds[$href]))
- {
- $this->checked_feeds++;
- $feed = new $this->file_class($href, $this->timeout, 5, null, $this->useragent);
- if ($feed->success && ($feed->method & SIMPLEPIE_FILE_SOURCE_REMOTE === 0 || ($feed->status_code === 200 || $feed->status_code > 206 && $feed->status_code < 300)) && $this->is_feed($feed))
- {
- $feeds[$href] = $feed;
- }
- }
- $done[] = $href;
- }
- }
-
- if (!empty($feeds))
- {
- return array_values($feeds);
- }
- else {
- return null;
- }
- }
-
- function get_links()
- {
- $links = SimplePie_Misc::get_element('a', $this->file->body);
- foreach ($links as $link)
- {
- if (isset($link['attribs']['href']['data']))
- {
- $href = trim($link['attribs']['href']['data']);
- $parsed = SimplePie_Misc::parse_url($href);
- if ($parsed['scheme'] === '' || preg_match('/^(http(s)|feed)?$/i', $parsed['scheme']))
- {
- if ($this->base_location < $link['offset'])
- {
- $href = SimplePie_Misc::absolutize_url(trim($link['attribs']['href']['data']), $this->base);
- }
- else
- {
- $href = SimplePie_Misc::absolutize_url(trim($link['attribs']['href']['data']), $this->http_base);
- }
-
- $current = SimplePie_Misc::parse_url($this->file->url);
-
- if ($parsed['authority'] === '' || $parsed['authority'] === $current['authority'])
- {
- $this->local[] = $href;
- }
- else
- {
- $this->elsewhere[] = $href;
- }
- }
- }
- }
- $this->local = array_unique($this->local);
- $this->elsewhere = array_unique($this->elsewhere);
- if (!empty($this->local) || !empty($this->elsewhere))
- {
- return true;
- }
- return null;
- }
-
- function extension(&$array)
- {
- foreach ($array as $key => $value)
- {
- if ($this->checked_feeds === $this->max_checked_feeds)
- {
- break;
- }
- if (in_array(strtolower(strrchr($value, '.')), array('.rss', '.rdf', '.atom', '.xml')))
- {
- $this->checked_feeds++;
- $feed = new $this->file_class($value, $this->timeout, 5, null, $this->useragent);
- if ($feed->success && ($feed->method & SIMPLEPIE_FILE_SOURCE_REMOTE === 0 || ($feed->status_code === 200 || $feed->status_code > 206 && $feed->status_code < 300)) && $this->is_feed($feed))
- {
- return $feed;
- }
- else
- {
- unset($array[$key]);
- }
- }
- }
- return null;
- }
-
- function body(&$array)
- {
- foreach ($array as $key => $value)
- {
- if ($this->checked_feeds === $this->max_checked_feeds)
- {
- break;
- }
- if (preg_match('/(rss|rdf|atom|xml)/i', $value))
- {
- $this->checked_feeds++;
- $feed = new $this->file_class($value, $this->timeout, 5, null, $this->useragent);
- if ($feed->success && ($feed->method & SIMPLEPIE_FILE_SOURCE_REMOTE === 0 || ($feed->status_code === 200 || $feed->status_code > 206 && $feed->status_code < 300)) && $this->is_feed($feed))
- {
- return $feed;
- }
- else
- {
- unset($array[$key]);
- }
- }
- }
- return null;
- }
-}
-
-class SimplePie_Parser
-{
- var $error_code;
- var $error_string;
- var $current_line;
- var $current_column;
- var $current_byte;
- var $separator = ' ';
- var $namespace = array('');
- var $element = array('');
- var $xml_base = array('');
- var $xml_base_explicit = array(false);
- var $xml_lang = array('');
- var $data = array();
- var $datas = array(array());
- var $current_xhtml_construct = -1;
- var $encoding;
-
- function parse(&$data, $encoding)
- {
- // Use UTF-8 if we get passed US-ASCII, as every US-ASCII character is a UTF-8 character
- if (strtoupper($encoding) === 'US-ASCII')
- {
- $this->encoding = 'UTF-8';
- }
- else
- {
- $this->encoding = $encoding;
- }
-
- // Strip BOM:
- // UTF-32 Big Endian BOM
- if (substr($data, 0, 4) === "\x00\x00\xFE\xFF")
- {
- $data = substr($data, 4);
- }
- // UTF-32 Little Endian BOM
- elseif (substr($data, 0, 4) === "\xFF\xFE\x00\x00")
- {
- $data = substr($data, 4);
- }
- // UTF-16 Big Endian BOM
- elseif (substr($data, 0, 2) === "\xFE\xFF")
- {
- $data = substr($data, 2);
- }
- // UTF-16 Little Endian BOM
- elseif (substr($data, 0, 2) === "\xFF\xFE")
- {
- $data = substr($data, 2);
- }
- // UTF-8 BOM
- elseif (substr($data, 0, 3) === "\xEF\xBB\xBF")
- {
- $data = substr($data, 3);
- }
-
- if (substr($data, 0, 5) === '<?xml' && strspn(substr($data, 5, 1), "\x09\x0A\x0D\x20") && ($pos = strpos($data, '?>')) !== false)
- {
- $declaration = new SimplePie_XML_Declaration_Parser(substr($data, 5, $pos - 5));
- if ($declaration->parse())
- {
- $data = substr($data, $pos + 2);
- $data = '<?xml version="' . $declaration->version . '" encoding="' . $encoding . '" standalone="' . (($declaration->standalone) ? 'yes' : 'no') . '"?>' . $data;
- }
- else
- {
- $this->error_string = 'SimplePie bug! Please report this!';
- return false;
- }
- }
-
- $return = true;
-
- static $xml_is_sane = null;
- if ($xml_is_sane === null)
- {
- $parser_check = xml_parser_create();
- xml_parse_into_struct($parser_check, '<foo>&amp;</foo>', $values);
- xml_parser_free($parser_check);
- $xml_is_sane = isset($values[0]['value']);
- }
-
- // Create the parser
- if ($xml_is_sane)
- {
- $xml = xml_parser_create_ns($this->encoding, $this->separator);
- xml_parser_set_option($xml, XML_OPTION_SKIP_WHITE, 1);
- xml_parser_set_option($xml, XML_OPTION_CASE_FOLDING, 0);
- xml_set_object($xml, $this);
- xml_set_character_data_handler($xml, 'cdata');
- xml_set_element_handler($xml, 'tag_open', 'tag_close');
-
- // Parse!
- if (!xml_parse($xml, $data, true))
- {
- $this->error_code = xml_get_error_code($xml);
- $this->error_string = xml_error_string($this->error_code);
- $return = false;
- }
- $this->current_line = xml_get_current_line_number($xml);
- $this->current_column = xml_get_current_column_number($xml);
- $this->current_byte = xml_get_current_byte_index($xml);
- xml_parser_free($xml);
- return $return;
- }
- else
- {
- libxml_clear_errors();
- $xml = new XMLReader();
- $xml->xml($data);
- while (@$xml->read())
- {
- switch ($xml->nodeType)
- {
-
- case constant('XMLReader::END_ELEMENT'):
- if ($xml->namespaceURI !== '')
- {
- $tagName = "{$xml->namespaceURI}{$this->separator}{$xml->localName}";
- }
- else
- {
- $tagName = $xml->localName;
- }
- $this->tag_close(null, $tagName);
- break;
- case constant('XMLReader::ELEMENT'):
- $empty = $xml->isEmptyElement;
- if ($xml->namespaceURI !== '')
- {
- $tagName = "{$xml->namespaceURI}{$this->separator}{$xml->localName}";
- }
- else
- {
- $tagName = $xml->localName;
- }
- $attributes = array();
- while ($xml->moveToNextAttribute())
- {
- if ($xml->namespaceURI !== '')
- {
- $attrName = "{$xml->namespaceURI}{$this->separator}{$xml->localName}";
- }
- else
- {
- $attrName = $xml->localName;
- }
- $attributes[$attrName] = $xml->value;
- }
- $this->tag_open(null, $tagName, $attributes);
- if ($empty)
- {
- $this->tag_close(null, $tagName);
- }
- break;
- case constant('XMLReader::TEXT'):
-
- case constant('XMLReader::CDATA'):
- $this->cdata(null, $xml->value);
- break;
- }
- }
- if ($error = libxml_get_last_error())
- {
- $this->error_code = $error->code;
- $this->error_string = $error->message;
- $this->current_line = $error->line;
- $this->current_column = $error->column;
- return false;
- }
- else
- {
- return true;
- }
- }
- }
-
- function get_error_code()
- {
- return $this->error_code;
- }
-
- function get_error_string()
- {
- return $this->error_string;
- }
-
- function get_current_line()
- {
- return $this->current_line;
- }
-
- function get_current_column()
- {
- return $this->current_column;
- }
-
- function get_current_byte()
- {
- return $this->current_byte;
- }
-
- function get_data()
- {
- return $this->data;
- }
-
- function tag_open($parser, $tag, $attributes)
- {
- list($this->namespace[], $this->element[]) = $this->split_ns($tag);
-
- $attribs = array();
- foreach ($attributes as $name => $value)
- {
- list($attrib_namespace, $attribute) = $this->split_ns($name);
- $attribs[$attrib_namespace][$attribute] = $value;
- }
-
- if (isset($attribs[SIMPLEPIE_NAMESPACE_XML]['base']))
- {
- $this->xml_base[] = SimplePie_Misc::absolutize_url($attribs[SIMPLEPIE_NAMESPACE_XML]['base'], end($this->xml_base));
- $this->xml_base_explicit[] = true;
- }
- else
- {
- $this->xml_base[] = end($this->xml_base);
- $this->xml_base_explicit[] = end($this->xml_base_explicit);
- }
-
- if (isset($attribs[SIMPLEPIE_NAMESPACE_XML]['lang']))
- {
- $this->xml_lang[] = $attribs[SIMPLEPIE_NAMESPACE_XML]['lang'];
- }
- else
- {
- $this->xml_lang[] = end($this->xml_lang);
- }
-
- if ($this->current_xhtml_construct >= 0)
- {
- $this->current_xhtml_construct++;
- if (end($this->namespace) === SIMPLEPIE_NAMESPACE_XHTML)
- {
- $this->data['data'] .= '<' . end($this->element);
- if (isset($attribs['']))
- {
- foreach ($attribs[''] as $name => $value)
- {
- $this->data['data'] .= ' ' . $name . '="' . htmlspecialchars($value, ENT_COMPAT, $this->encoding) . '"';
- }
- }
- $this->data['data'] .= '>';
- }
- }
- else
- {
- $this->datas[] =& $this->data;
- $this->data =& $this->data['child'][end($this->namespace)][end($this->element)][];
- $this->data = array('data' => '', 'attribs' => $attribs, 'xml_base' => end($this->xml_base), 'xml_base_explicit' => end($this->xml_base_explicit), 'xml_lang' => end($this->xml_lang));
- if ((end($this->namespace) === SIMPLEPIE_NAMESPACE_ATOM_03 && in_array(end($this->element), array('title', 'tagline', 'copyright', 'info', 'summary', 'content')) && isset($attribs['']['mode']) && $attribs['']['mode'] === 'xml')
- || (end($this->namespace) === SIMPLEPIE_NAMESPACE_ATOM_10 && in_array(end($this->element), array('rights', 'subtitle', 'summary', 'info', 'title', 'content')) && isset($attribs['']['type']) && $attribs['']['type'] === 'xhtml'))
- {
- $this->current_xhtml_construct = 0;
- }
- }
- }
-
- function cdata($parser, $cdata)
- {
- if ($this->current_xhtml_construct >= 0)
- {
- $this->data['data'] .= htmlspecialchars($cdata, ENT_QUOTES, $this->encoding);
- }
- else
- {
- $this->data['data'] .= $cdata;
- }
- }
-
- function tag_close($parser, $tag)
- {
- if ($this->current_xhtml_construct >= 0)
- {
- $this->current_xhtml_construct--;
- if (end($this->namespace) === SIMPLEPIE_NAMESPACE_XHTML && !in_array(end($this->element), array('area', 'base', 'basefont', 'br', 'col', 'frame', 'hr', 'img', 'input', 'isindex', 'link', 'meta', 'param')))
- {
- $this->data['data'] .= '</' . end($this->element) . '>';
- }
- }
- if ($this->current_xhtml_construct === -1)
- {
- $this->data =& $this->datas[count($this->datas) - 1];
- array_pop($this->datas);
- }
-
- array_pop($this->element);
- array_pop($this->namespace);
- array_pop($this->xml_base);
- array_pop($this->xml_base_explicit);
- array_pop($this->xml_lang);
- }
-
- function split_ns($string)
- {
- static $cache = array();
- if (!isset($cache[$string]))
- {
- if ($pos = strpos($string, $this->separator))
- {
- static $separator_length;
- if (!$separator_length)
- {
- $separator_length = strlen($this->separator);
- }
- $namespace = substr($string, 0, $pos);
- $local_name = substr($string, $pos + $separator_length);
- if (strtolower($namespace) === SIMPLEPIE_NAMESPACE_ITUNES)
- {
- $namespace = SIMPLEPIE_NAMESPACE_ITUNES;
- }
-
- // Normalize the Media RSS namespaces
- if ($namespace === SIMPLEPIE_NAMESPACE_MEDIARSS_WRONG)
- {
- $namespace = SIMPLEPIE_NAMESPACE_MEDIARSS;
- }
- $cache[$string] = array($namespace, $local_name);
- }
- else
- {
- $cache[$string] = array('', $string);
- }
- }
- return $cache[$string];
- }
-}
-
-/**
- * @todo Move to using an actual HTML parser (this will allow tags to be properly stripped, and to switch between HTML and XHTML), this will also make it easier to shorten a string while preserving HTML tags
- */
-class SimplePie_Sanitize
-{
- // Private vars
- var $base;
-
- // Options
- var $remove_div = true;
- var $image_handler = '';
- var $strip_htmltags = array('base', 'blink', 'body', 'doctype', 'embed', 'font', 'form', 'frame', 'frameset', 'html', 'input', 'marquee', 'meta', 'noscript', 'object', 'param', 'script', 'style');
- var $encode_instead_of_strip = false;
- var $strip_attributes = array('bgsound', 'class', 'expr', 'id', 'style', 'onclick', 'onerror', 'onfinish', 'onmouseover', 'onmouseout', 'onfocus', 'onblur', 'lowsrc', 'dynsrc');
- var $strip_comments = false;
- var $output_encoding = 'UTF-8';
- var $enable_cache = true;
- var $cache_location = './cache';
- var $cache_name_function = 'md5';
- var $cache_class = 'SimplePie_Cache';
- var $file_class = 'SimplePie_File';
- var $timeout = 10;
- var $useragent = '';
- var $force_fsockopen = false;
-
- var $replace_url_attributes = array(
- 'a' => 'href',
- 'area' => 'href',
- 'blockquote' => 'cite',
- 'del' => 'cite',
- 'form' => 'action',
- 'img' => array('longdesc', 'src'),
- 'input' => 'src',
- 'ins' => 'cite',
- 'q' => 'cite'
- );
-
- function remove_div($enable = true)
- {
- $this->remove_div = (bool) $enable;
- }
-
- function set_image_handler($page = false)
- {
- if ($page)
- {
- $this->image_handler = (string) $page;
- }
- else
- {
- $this->image_handler = false;
- }
- }
-
- function pass_cache_data($enable_cache = true, $cache_location = './cache', $cache_name_function = 'md5', $cache_class = 'SimplePie_Cache')
- {
- if (isset($enable_cache))
- {
- $this->enable_cache = (bool) $enable_cache;
- }
-
- if ($cache_location)
- {
- $this->cache_location = (string) $cache_location;
- }
-
- if ($cache_name_function)
- {
- $this->cache_name_function = (string) $cache_name_function;
- }
-
- if ($cache_class)
- {
- $this->cache_class = (string) $cache_class;
- }
- }
-
- function pass_file_data($file_class = 'SimplePie_File', $timeout = 10, $useragent = '', $force_fsockopen = false)
- {
- if ($file_class)
- {
- $this->file_class = (string) $file_class;
- }
-
- if ($timeout)
- {
- $this->timeout = (string) $timeout;
- }
-
- if ($useragent)
- {
- $this->useragent = (string) $useragent;
- }
-
- if ($force_fsockopen)
- {
- $this->force_fsockopen = (string) $force_fsockopen;
- }
- }
-
- function strip_htmltags($tags = array('base', 'blink', 'body', 'doctype', 'embed', 'font', 'form', 'frame', 'frameset', 'html', 'input', 'marquee', 'meta', 'noscript', 'object', 'param', 'script', 'style'))
- {
- if ($tags)
- {
- if (is_array($tags))
- {
- $this->strip_htmltags = $tags;
- }
- else
- {
- $this->strip_htmltags = explode(',', $tags);
- }
- }
- else
- {
- $this->strip_htmltags = false;
- }
- }
-
- function encode_instead_of_strip($encode = false)
- {
- $this->encode_instead_of_strip = (bool) $encode;
- }
-
- function strip_attributes($attribs = array('bgsound', 'class', 'expr', 'id', 'style', 'onclick', 'onerror', 'onfinish', 'onmouseover', 'onmouseout', 'onfocus', 'onblur', 'lowsrc', 'dynsrc'))
- {
- if ($attribs)
- {
- if (is_array($attribs))
- {
- $this->strip_attributes = $attribs;
- }
- else
- {
- $this->strip_attributes = explode(',', $attribs);
- }
- }
- else
- {
- $this->strip_attributes = false;
- }
- }
-
- function strip_comments($strip = false)
- {
- $this->strip_comments = (bool) $strip;
- }
-
- function set_output_encoding($encoding = 'UTF-8')
- {
- $this->output_encoding = (string) $encoding;
- }
-
- /**
- * Set element/attribute key/value pairs of HTML attributes
- * containing URLs that need to be resolved relative to the feed
- *
- * @access public
- * @since 1.0
- * @param array $element_attribute Element/attribute key/value pairs
- */
- function set_url_replacements($element_attribute = array('a' => 'href', 'area' => 'href', 'blockquote' => 'cite', 'del' => 'cite', 'form' => 'action', 'img' => array('longdesc', 'src'), 'input' => 'src', 'ins' => 'cite', 'q' => 'cite'))
- {
- $this->replace_url_attributes = (array) $element_attribute;
- }
-
- function sanitize($data, $type, $base = '')
- {
- $data = trim($data);
- if ($data !== '' || $type & SIMPLEPIE_CONSTRUCT_IRI)
- {
- if ($type & SIMPLEPIE_CONSTRUCT_MAYBE_HTML)
- {
- if (preg_match('/(&(#(x[0-9a-fA-F]+|[0-9]+)|[a-zA-Z0-9]+)|<\/[A-Za-z][^\x09\x0A\x0B\x0C\x0D\x20\x2F\x3E]*' . SIMPLEPIE_PCRE_HTML_ATTRIBUTE . '>)/', $data))
- {
- $type |= SIMPLEPIE_CONSTRUCT_HTML;
- }
- else
- {
- $type |= SIMPLEPIE_CONSTRUCT_TEXT;
- }
- }
-
- if ($type & SIMPLEPIE_CONSTRUCT_BASE64)
- {
- $data = base64_decode($data);
- }
-
- if ($type & SIMPLEPIE_CONSTRUCT_XHTML)
- {
- if ($this->remove_div)
- {
- $data = preg_replace('/^<div' . SIMPLEPIE_PCRE_XML_ATTRIBUTE . '>/', '', $data);
- $data = preg_replace('/<\/div>$/', '', $data);
- }
- else
- {
- $data = preg_replace('/^<div' . SIMPLEPIE_PCRE_XML_ATTRIBUTE . '>/', '<div>', $data);
- }
- }
-
- if ($type & (SIMPLEPIE_CONSTRUCT_HTML | SIMPLEPIE_CONSTRUCT_XHTML))
- {
- // Strip comments
- if ($this->strip_comments)
- {
- $data = SimplePie_Misc::strip_comments($data);
- }
-
- // Strip out HTML tags and attributes that might cause various security problems.
- // Based on recommendations by Mark Pilgrim at:
- // http://diveintomark.org/archives/2003/06/12/how_to_consume_rss_safely
- if ($this->strip_htmltags)
- {
- foreach ($this->strip_htmltags as $tag)
- {
- $pcre = "/<($tag)" . SIMPLEPIE_PCRE_HTML_ATTRIBUTE . "(>(.*)<\/$tag" . SIMPLEPIE_PCRE_HTML_ATTRIBUTE . '>|(\/)?>)/siU';
- while (preg_match($pcre, $data))
- {
- $data = preg_replace_callback($pcre, array(&$this, 'do_strip_htmltags'), $data);
- }
- }
- }
-
- if ($this->strip_attributes)
- {
- foreach ($this->strip_attributes as $attrib)
- {
- $data = preg_replace('/(<[A-Za-z][^\x09\x0A\x0B\x0C\x0D\x20\x2F\x3E]*)' . SIMPLEPIE_PCRE_HTML_ATTRIBUTE . trim($attrib) . '(?:\s*=\s*(?:"(?:[^"]*)"|\'(?:[^\']*)\'|(?:[^\x09\x0A\x0B\x0C\x0D\x20\x22\x27\x3E][^\x09\x0A\x0B\x0C\x0D\x20\x3E]*)?))?' . SIMPLEPIE_PCRE_HTML_ATTRIBUTE . '>/', '\1\2\3>', $data);
- }
- }
-
- // Replace relative URLs
- $this->base = $base;
- foreach ($this->replace_url_attributes as $element => $attributes)
- {
- $data = $this->replace_urls($data, $element, $attributes);
- }
-
- // If image handling (caching, etc.) is enabled, cache and rewrite all the image tags.
- if (isset($this->image_handler) && ((string) $this->image_handler) !== '' && $this->enable_cache)
- {
- $images = SimplePie_Misc::get_element('img', $data);
- foreach ($images as $img)
- {
- if (isset($img['attribs']['src']['data']))
- {
- $image_url = call_user_func($this->cache_name_function, $img['attribs']['src']['data']);
- $cache = call_user_func(array($this->cache_class, 'create'), $this->cache_location, $image_url, 'spi');
-
- if ($cache->load())
- {
- $img['attribs']['src']['data'] = $this->image_handler . $image_url;
- $data = str_replace($img['full'], SimplePie_Misc::element_implode($img), $data);
- }
- else
- {
- $file = new $this->file_class($img['attribs']['src']['data'], $this->timeout, 5, array('X-FORWARDED-FOR' => $_SERVER['REMOTE_ADDR']), $this->useragent, $this->force_fsockopen);
- $headers = $file->headers;
-
- if ($file->success && ($file->method & SIMPLEPIE_FILE_SOURCE_REMOTE === 0 || ($file->status_code === 200 || $file->status_code > 206 && $file->status_code < 300)))
- {
- if ($cache->save(array('headers' => $file->headers, 'body' => $file->body)))
- {
- $img['attribs']['src']['data'] = $this->image_handler . $image_url;
- $data = str_replace($img['full'], SimplePie_Misc::element_implode($img), $data);
- }
- else
- {
- trigger_error("$this->cache_location is not writeable. Make sure you've set the correct relative or absolute path, and that the location is server-writable.", E_USER_WARNING);
- }
- }
- }
- }
- }
- }
-
- // Having (possibly) taken stuff out, there may now be whitespace at the beginning/end of the data
- $data = trim($data);
- }
-
- if ($type & SIMPLEPIE_CONSTRUCT_IRI)
- {
- $data = SimplePie_Misc::absolutize_url($data, $base);
- }
-
- if ($type & (SIMPLEPIE_CONSTRUCT_TEXT | SIMPLEPIE_CONSTRUCT_IRI))
- {
- $data = htmlspecialchars($data, ENT_COMPAT, 'UTF-8');
- }
-
- if ($this->output_encoding !== 'UTF-8')
- {
- $data = SimplePie_Misc::change_encoding($data, 'UTF-8', $this->output_encoding);
- }
- }
- return $data;
- }
-
- function replace_urls($data, $tag, $attributes)
- {
- if (!is_array($this->strip_htmltags) || !in_array($tag, $this->strip_htmltags))
- {
- $elements = SimplePie_Misc::get_element($tag, $data);
- foreach ($elements as $element)
- {
- if (is_array($attributes))
- {
- foreach ($attributes as $attribute)
- {
- if (isset($element['attribs'][$attribute]['data']))
- {
- $element['attribs'][$attribute]['data'] = SimplePie_Misc::absolutize_url($element['attribs'][$attribute]['data'], $this->base);
- $new_element = SimplePie_Misc::element_implode($element);
- $data = str_replace($element['full'], $new_element, $data);
- $element['full'] = $new_element;
- }
- }
- }
- elseif (isset($element['attribs'][$attributes]['data']))
- {
- $element['attribs'][$attributes]['data'] = SimplePie_Misc::absolutize_url($element['attribs'][$attributes]['data'], $this->base);
- $data = str_replace($element['full'], SimplePie_Misc::element_implode($element), $data);
- }
- }
- }
- return $data;
- }
-
- function do_strip_htmltags($match)
- {
- if ($this->encode_instead_of_strip)
- {
- if (isset($match[4]) && !in_array(strtolower($match[1]), array('script', 'style')))
- {
- $match[1] = htmlspecialchars($match[1], ENT_COMPAT, 'UTF-8');
- $match[2] = htmlspecialchars($match[2], ENT_COMPAT, 'UTF-8');
- return "&lt;$match[1]$match[2]&gt;$match[3]&lt;/$match[1]&gt;";
- }
- else
- {
- return htmlspecialchars($match[0], ENT_COMPAT, 'UTF-8');
- }
- }
- elseif (isset($match[4]) && !in_array(strtolower($match[1]), array('script', 'style')))
- {
- return $match[4];
- }
- else
- {
- return '';
- }
- }
-}
-
-?>
diff --git a/library/sticky-kit/sticky-kit.js b/library/sticky-kit/sticky-kit.js
index eb2ea8a26..00b1ea2ff 100644
--- a/library/sticky-kit/sticky-kit.js
+++ b/library/sticky-kit/sticky-kit.js
@@ -77,7 +77,7 @@
padding_top = parseInt(parent.css("padding-top"), 10);
padding_bottom = parseInt(parent.css("padding-bottom"), 10);
parent_top = parent.offset().top + border_top + padding_top;
- parent_height = parent.outerHeight(true);
+ parent_height = parent.height();
if (fixed) {
fixed = false;
bottomed = false;
diff --git a/tests/phpunit-mariadb.xml b/tests/phpunit-mariadb.xml
new file mode 120000
index 000000000..63656b78b
--- /dev/null
+++ b/tests/phpunit-mariadb.xml
@@ -0,0 +1 @@
+phpunit-mysql.xml \ No newline at end of file
diff --git a/tests/phpunit-mysql.xml b/tests/phpunit-mysql.xml
new file mode 100644
index 000000000..171211094
--- /dev/null
+++ b/tests/phpunit-mysql.xml
@@ -0,0 +1,37 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<phpunit xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:noNamespaceSchemaLocation="https://schema.phpunit.de/6.0/phpunit.xsd"
+ bootstrap="../boot.php"
+ forceCoversAnnotation="false"
+ beStrictAboutCoversAnnotation="true"
+ beStrictAboutOutputDuringTests="true"
+ beStrictAboutTodoAnnotatedTests="true"
+ verbose="true">
+ <testsuite name="Hubzilla default Test Suite">
+ <directory suffix="Test.php">./unit/</directory>
+ </testsuite>
+ <testsuite name="API Test Suite">
+ <directory suffix="Test.php" prefix="API">./unit/</directory>
+ </testsuite>
+ <testsuite name="Ex-/Import Test Suite">
+ <directory suffix="Test.php">./unit/eximport/</directory>
+ </testsuite>
+ <groups>
+ <exclude>
+ <group>postgresql</group>
+ </exclude>
+ </groups>
+ <!--cover reporting-->
+ <filter>
+ <whitelist processUncoveredFilesFromWhitelist="true">
+ <directory suffix=".php">../Zotlabs/</directory>
+ <directory suffix=".php">../include/</directory>
+ </whitelist>
+ </filter>
+ <logging>
+ <log type="junit" target="./results/junit.xml" logIncompleteSkipped="false"/>
+ <log type="coverage-clover" target="./results/coverage-clover.xml"/>
+ <log type="coverage-html" target="./results/coverage-report/" lowUpperBound="35"
+ highLowerBound="70"/>
+ </logging>
+</phpunit>
diff --git a/tests/phpunit-pgsql.xml b/tests/phpunit-pgsql.xml
new file mode 100644
index 000000000..ace14e196
--- /dev/null
+++ b/tests/phpunit-pgsql.xml
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<phpunit xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:noNamespaceSchemaLocation="https://schema.phpunit.de/6.0/phpunit.xsd"
+ bootstrap="../boot.php"
+ forceCoversAnnotation="false"
+ beStrictAboutCoversAnnotation="true"
+ beStrictAboutOutputDuringTests="true"
+ beStrictAboutTodoAnnotatedTests="true"
+ verbose="true">
+ <testsuite name="Hubzilla default Test Suite">
+ <directory suffix="Test.php">./unit/</directory>
+ </testsuite>
+ <testsuite name="API Test Suite">
+ <directory suffix="Test.php" prefix="API">./unit/</directory>
+ </testsuite>
+ <groups>
+ <exclude>
+ <group>mysql</group>
+ </exclude>
+ </groups>
+ <!--cover reporting-->
+ <filter>
+ <whitelist processUncoveredFilesFromWhitelist="true">
+ <directory suffix=".php">../Zotlabs/</directory>
+ <directory suffix=".php">../include/</directory>
+ </whitelist>
+ </filter>
+ <logging>
+ <log type="junit" target="./results/junit.xml" logIncompleteSkipped="false"/>
+ <log type="coverage-clover" target="./results/coverage-clover.xml"/>
+ <log type="coverage-html" target="./results/coverage-report/" lowUpperBound="35"
+ highLowerBound="70"/>
+ </logging>
+</phpunit>
diff --git a/tests/travis/gen_apidocs.sh b/tests/travis/gen_apidocs.sh
new file mode 100755
index 000000000..e5938e1e8
--- /dev/null
+++ b/tests/travis/gen_apidocs.sh
@@ -0,0 +1,69 @@
+#!/usr/bin/env bash
+
+#
+# Copyright (c) 2016 Hubzilla
+#
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
+#
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
+#
+# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+# SOFTWARE.
+#
+
+# Exit if anything fails
+set -e
+
+# Only create and deploy API documentation once, on first build job.
+# Waiting for upcoming 'Build Stages' Q1/Q2 2017 to make this cleaner.
+# https://github.com/travis-ci/travis-ci/issues/929
+if [[ "$TRAVIS_JOB_NUMBER" != "${TRAVIS_BUILD_NUMBER}.1" ]]; then
+ echo "Not the first build job. Creating API documentation only once is enough."
+ echo "We are finished ..."
+ exit
+fi
+
+echo "Doxygen version >= 1.8 is required"
+doxygen --version
+
+# Check if newer version of Doxygen should be used
+if [ ! -z "$DOXY_VER" ]; then
+ export DOXY_BINPATH=$HOME/doxygen/doxygen-$DOXY_VER/bin
+ if [ ! -e "$DOXY_BINPATH/doxygen" ]; then
+ echo "Installing newer Doxygen $DOXY_VER ..."
+ mkdir -p $HOME/doxygen && cd $HOME/doxygen
+ wget -O - http://ftp.stack.nl/pub/users/dimitri/doxygen-$DOXY_VER.linux.bin.tar.gz | tar xz
+ export PATH=$DOXY_BINPATH:$PATH
+ fi
+ echo "Doxygen version"
+ doxygen --version
+fi
+
+echo "Generating Doxygen API documentation ..."
+cd $TRAVIS_BUILD_DIR
+mkdir -p ./doc/html
+# Redirect stderr and stdout to log file and console to be able to review documentation errors
+doxygen $DOXYFILE 2>&1 | tee ./doc/html/doxygen.log
+
+# Check if Doxygen successfully created the documentation
+if [ -d "doc/html" ] && [ -f "doc/html/index.html" ]; then
+ echo "API documentation generated"
+ if [ -n "${TRAVIS_TAG}" ]; then
+ echo "Generate API documentation archive for release deployment ..."
+ zip -9 -r -q doc/hubzilla-api-documentation.zip doc/html/
+ fi
+else
+ echo "No API documentation files have been found" >&2
+ exit 1
+fi
diff --git a/tests/travis/prepare.sh b/tests/travis/prepare.sh
new file mode 100755
index 000000000..267b4ec46
--- /dev/null
+++ b/tests/travis/prepare.sh
@@ -0,0 +1,35 @@
+#!/usr/bin/env bash
+
+#
+# Copyright (c) 2016 Hubzilla
+#
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
+#
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
+#
+# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+# SOFTWARE.
+#
+
+# Exit if anything fails
+set -e
+
+# gd is required, show some info about the used one
+php -r "var_dump(gd_info());"
+
+
+echo "Creating required folders for Hubzilla ..."
+mkdir -p ./store/\[data\]/smarty3
+
+echo "TODO: create .htconfig"
diff --git a/tests/travis/prepare_mysql.sh b/tests/travis/prepare_mysql.sh
new file mode 100755
index 000000000..095ad7e25
--- /dev/null
+++ b/tests/travis/prepare_mysql.sh
@@ -0,0 +1,53 @@
+#!/usr/bin/env bash
+
+#
+# Copyright (c) 2016 Hubzilla
+#
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
+#
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
+#
+# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+# SOFTWARE.
+#
+
+# Exit if anything fails
+set -e
+
+echo "Preparing for MySQL ..."
+
+if [[ "$MYSQL_VERSION" == "5.7" ]]; then
+ echo "Using MySQL 5.7 in Docker container, need to use TCP"
+ export PROTO="--protocol=TCP"
+fi
+
+# Print out some MySQL information
+mysql --version
+mysql $PROTO -e "SELECT VERSION();"
+mysql $PROTO -e "SHOW VARIABLES LIKE 'max_allowed_packet';"
+mysql $PROTO -e "SHOW VARIABLES LIKE 'collation_%';"
+mysql $PROTO -e "SHOW VARIABLES LIKE 'character_set%';"
+mysql $PROTO -e "SELECT @@sql_mode;"
+
+# Create Hubzilla database
+mysql $PROTO -u root -e "CREATE DATABASE IF NOT EXISTS hubzilla;";
+mysql $PROTO -u root -e "CREATE USER 'hubzilla'@'localhost' IDENTIFIED BY 'hubzilla';"
+mysql $PROTO -u root -e "GRANT ALL ON hubzilla.* TO 'hubzilla'@'localhost';"
+
+# Import table structure
+mysql $PROTO -u root hubzilla < ./install/schema_mysql.sql
+
+# Show databases and tables
+mysql $PROTO -u root -e "SHOW DATABASES;"
+mysql $PROTO -u root -e "USE hubzilla; SHOW TABLES;"
diff --git a/tests/travis/prepare_pgsql.sh b/tests/travis/prepare_pgsql.sh
new file mode 100755
index 000000000..63c7388cb
--- /dev/null
+++ b/tests/travis/prepare_pgsql.sh
@@ -0,0 +1,44 @@
+#!/usr/bin/env bash
+
+#
+# Copyright (c) 2016 Hubzilla
+#
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
+#
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
+#
+# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+# SOFTWARE.
+#
+
+# Exit if anything fails
+set -e
+
+echo "Preparing for PostgreSQL ..."
+
+# Print out some PostgreSQL information
+psql --version
+# Why does this hang further execution of the job?
+psql -U postgres -c "SELECT VERSION();"
+
+# Create Hubzilla database
+psql -U postgres -c "DROP DATABASE IF EXISTS hubzilla;"
+psql -U postgres -c "CREATE DATABASE hubzilla;"
+
+# Import table structure
+psql -U postgres -v ON_ERROR_STOP=1 hubzilla < ./install/schema_postgres.sql
+
+# Show databases and tables
+psql -U postgres -l
+psql -U postgres -d hubzilla -c "\dt;"
diff --git a/tests/unit/Access/AccessListTest.php b/tests/unit/Access/AccessListTest.php
new file mode 100644
index 000000000..3dbe5cd65
--- /dev/null
+++ b/tests/unit/Access/AccessListTest.php
@@ -0,0 +1,189 @@
+<?php
+/*
+ * Copyright (c) 2017 Hubzilla
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ */
+
+namespace Zotlabs\Tests\Unit\Access;
+
+use Zotlabs\Tests\Unit\UnitTestCase;
+use Zotlabs\Access\AccessList;
+
+/**
+ * @brief Unit Test case for AccessList class.
+ *
+ * @covers Zotlabs\Access\AccessList
+ */
+class AccessListTest extends UnitTestCase {
+
+ /**
+ * @brief Expected result for most tests.
+ * @var array
+ */
+ protected $expectedResult = [
+ 'allow_cid' => '<acid><acid2>',
+ 'allow_gid' => '<agid>',
+ 'deny_cid' => '',
+ 'deny_gid' => '<dgid><dgid2>'
+ ];
+
+
+
+ public function testConstructor() {
+ $channel = [
+ 'channel_allow_cid' => '<acid><acid2>',
+ 'channel_allow_gid' => '<agid>',
+ 'channel_deny_cid' => '',
+ 'channel_deny_gid' => '<dgid><dgid2>'
+ ];
+
+ $accessList = new AccessList($channel);
+
+ $this->assertEquals($this->expectedResult, $accessList->get());
+ $this->assertFalse($accessList->get_explicit());
+ }
+
+ /**
+ * @expectedException PHPUnit\Framework\Error\Error
+ */
+ public function testPHPErrorOnInvalidConstructor() {
+ $accessList = new AccessList('invalid');
+ // Causes: "Illegal string offset 'channel_allow_cid'"
+ }
+
+ public function testDefaultGetExplicit() {
+ $accessList = new AccessList([]);
+
+ $this->assertFalse($accessList->get_explicit());
+ }
+
+ public function testDefaultGet() {
+ $arr = [
+ 'allow_cid' => '',
+ 'allow_gid' => '',
+ 'deny_cid' => '',
+ 'deny_gid' => ''
+ ];
+
+ $accessList = new AccessList([]);
+
+ $this->assertEquals($arr, $accessList->get());
+ }
+
+ public function testSet() {
+ $arr = [
+ 'allow_cid' => '<acid><acid2>',
+ 'allow_gid' => '<agid>',
+ 'deny_cid' => '',
+ 'deny_gid' => '<dgid><dgid2>'
+ ];
+ $accessList = new AccessList([]);
+
+ // default explicit true
+ $accessList->set($arr);
+
+ $this->assertEquals($this->expectedResult, $accessList->get());
+ $this->assertTrue($accessList->get_explicit());
+
+ // set explicit false
+ $accessList->set($arr, false);
+
+ $this->assertEquals($this->expectedResult, $accessList->get());
+ $this->assertFalse($accessList->get_explicit());
+ }
+
+ /**
+ * @expectedException PHPUnit\Framework\Error\Error
+ */
+ public function testPHPErrorOnInvalidSet() {
+ $accessList = new AccessList([]);
+
+ $accessList->set('invalid');
+ // Causes: "Illegal string offset 'allow_cid'"
+ }
+
+ /**
+ * set_from_array() calls some other functions, too which are not yet unit tested.
+ * @uses ::perms2str()
+ */
+ public function testSetFromArray() {
+ // array
+ $arraySetFromArray = [
+ 'contact_allow' => ['acid', 'acid2'],
+ 'group_allow' => ['agid'],
+ 'contact_deny' => [],
+ 'group_deny' => ['dgid', 'dgid2']
+ ];
+ $accessList = new AccessList([]);
+ $accessList->set_from_array($arraySetFromArray);
+
+ $this->assertEquals($this->expectedResult, $accessList->get());
+ $this->assertTrue($accessList->get_explicit());
+
+
+ // string
+ $stringSetFromArray = [
+ 'contact_allow' => 'acid,acid2',
+ 'group_allow' => 'agid',
+ 'contact_deny' => '',
+ 'group_deny' => 'dgid, dgid2'
+ ];
+ $accessList2 = new AccessList([]);
+ $accessList2->set_from_array($stringSetFromArray, false);
+
+ $this->assertEquals($this->expectedResult, $accessList2->get());
+ $this->assertFalse($accessList2->get_explicit());
+ }
+
+ /**
+ * @dataProvider isprivateProvider
+ */
+ public function testIsPrivate($channel) {
+ $accessListPublic = new AccessList([]);
+ $this->assertFalse($accessListPublic->is_private());
+
+ $accessListPrivate = new AccessList($channel);
+ $this->assertTrue($accessListPrivate->is_private());
+ }
+
+ public function isprivateProvider() {
+ return [
+ 'all set' => [[
+ 'channel_allow_cid' => '<acid>',
+ 'channel_allow_gid' => '<agid>',
+ 'channel_deny_cid' => '<dcid>',
+ 'channel_deny_gid' => '<dgid>'
+ ]],
+ 'only one set' => [[
+ 'channel_allow_cid' => '<acid>',
+ 'channel_allow_gid' => '',
+ 'channel_deny_cid' => '',
+ 'channel_deny_gid' => ''
+ ]],
+ 'acid+null' => [[
+ 'channel_allow_cid' => '<acid>',
+ 'channel_allow_gid' => null,
+ 'channel_deny_cid' => '',
+ 'channel_deny_gid' => ''
+ ]]
+ ];
+ }
+
+} \ No newline at end of file
diff --git a/tests/unit/Access/PermissionsTest.php b/tests/unit/Access/PermissionsTest.php
new file mode 100644
index 000000000..93c641fb1
--- /dev/null
+++ b/tests/unit/Access/PermissionsTest.php
@@ -0,0 +1,148 @@
+<?php
+/*
+ * Copyright (c) 2017 Hubzilla
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ */
+
+namespace Zotlabs\Tests\Unit\Access;
+
+use Zotlabs\Tests\Unit\UnitTestCase;
+use Zotlabs\Access\Permissions;
+
+/**
+ * @brief Unit Test case for Permissions class.
+ *
+ * @covers Zotlabs\Access\Permissions
+ */
+class PermissionsTest extends UnitTestCase {
+
+ /**
+ * @dataProvider FilledPermsProvider
+ */
+ public function testFilledPerms($permarr, $expected) {
+ $this->markTestIncomplete(
+ 'Need to mock static function Permissions::Perms() ...'
+ );
+ //$this->assertEquals($expected, Permissions::FilledPerms($permarr));
+
+/* $perms = $this->getMockBuilder(Permissions::class)
+ ->setMethods(['Perms'])
+ ->getMock();
+ $perms->expects($this->once())
+ ->method('Perms');
+ // still calls the static self::Perms()
+ $perms->FilledPerms($permarr);
+*/
+ }
+ public function FilledPermsProvider() {
+ return [
+ 'empty' => [
+ [],
+ ['perm1' => 0, 'perm2' => 0]
+ ],
+ 'valild' => [
+ [['perm1' => 1]],
+ ['perm1' => 1, 'perm2' => 0]
+ ]
+ ];
+ }
+/* public function testFilledPermsNull() {
+ // need to mock global function btlogger();
+ Permissions::FilledPerms(null);
+ }
+*/
+ /**
+ * @dataProvider OPermsProvider
+ *
+ * @param array $permarr
+ * @param array $expected
+ */
+ public function testOPerms($permarr, $expected) {
+ $this->assertEquals($expected, Permissions::OPerms($permarr));
+ }
+ /**
+ * @return Associative array with test values for OPerms()
+ * * \e array Array to test
+ * * \e array Expect array
+ */
+ public function OPermsProvider() {
+ return [
+ 'empty' => [
+ [],
+ []
+ ],
+ 'valid' => [
+ ['perm1' => 1, 'perm2' => 0],
+ [['name' => 'perm1', 'value' => 1], ['name' => 'perm2', 'value' => 0]]
+ ],
+ 'null array' => [
+ null,
+ []
+ ]
+ ];
+ }
+
+
+ /**
+ * @dataProvider permsCompareProvider
+ *
+ * @param array $p1
+ * @param array $p2
+ * @param boolean $expectedresult
+ */
+ public function testPermsCompare($p1, $p2, $expectedresult) {
+ $this->assertEquals($expectedresult, Permissions::PermsCompare($p1, $p2));
+ }
+ /**
+ * @return Associative array with test values for PermsCompare()
+ * * \e array 1st array
+ * * \e array 2nd array
+ * * \e boolean expected result for the test
+ */
+ public function permsCompareProvider() {
+ return [
+ 'equal' => [
+ ['perm1' => 1, 'perm2' => 0],
+ ['perm1' => 1, 'perm2' => 0],
+ true
+ ],
+ 'different values' => [
+ ['perm1' => 1, 'perm2' => 0],
+ ['perm1' => 0, 'perm2' => 1],
+ false
+ ],
+ 'different order' => [
+ ['perm1' => 1, 'perm2' => 0],
+ ['perm2' => 0, 'perm1' => 1],
+ true
+ ],
+ 'partial first in second' => [
+ ['perm1' => 1],
+ ['perm1' => 1, 'perm2' => 0],
+ true
+ ],
+ 'partial second in first' => [
+ ['perm1' => 1, 'perm2' => 0],
+ ['perm1' => 1],
+ false
+ ]
+ ];
+ }
+} \ No newline at end of file
diff --git a/tests/unit/Lib/PermissionDescriptionTest.php b/tests/unit/Lib/PermissionDescriptionTest.php
index b1da5a0fd..96c381d0c 100644
--- a/tests/unit/Lib/PermissionDescriptionTest.php
+++ b/tests/unit/Lib/PermissionDescriptionTest.php
@@ -1,6 +1,6 @@
<?php
/*
- * Copyright (c) 2016 Hubzilla
+ * Copyright (c) 2016-2017 Hubzilla
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
@@ -21,90 +21,77 @@
* SOFTWARE.
*/
-// Global namespace for fully qualified \App class.
-namespace {
- // General channel permissions in boot.php
- // 0 = Only you
- define ( 'PERMS_PUBLIC' , 0x0001 ); // anybody
- define ( 'PERMS_NETWORK' , 0x0002 ); // anybody in this network
- define ( 'PERMS_SITE' , 0x0004 ); // anybody on this site
- define ( 'PERMS_CONTACTS' , 0x0008 ); // any of my connections
- define ( 'PERMS_SPECIFIC' , 0x0080 ); // only specific connections
- define ( 'PERMS_AUTHED' , 0x0100 ); // anybody authenticated (could include visitors from other networks)
- define ( 'PERMS_PENDING' , 0x0200 ); // any connections including those who haven't yet been approved
- // log levels in boot.php
- define ( 'LOGGER_DEBUG', 2 );
+namespace Zotlabs\Tests\Unit\Lib;
- // Stub global fully qualified \App class for static function calls
- class App {
- // Stub get_hostname()
- public static function get_hostname() {
- return 'phpunit';
- }
- }
-}
+use phpmock\phpunit\PHPMock;
+use Zotlabs\Tests\Unit\UnitTestCase;
+use Zotlabs\Lib\PermissionDescription;
-// Stub global functions used in PermissionDescription with the help of
-// PHP's namespace resolution rules.
-namespace Zotlabs\Lib {
- // Stub global translate function t()
- function t($s) {
- return $s;
- }
- // Stub global log function logger()
- function logger($msg, $level = LOGGER_NORMAL, $priority = LOG_INFO) {
- // doesn't matter
- }
-}
+/**
+ * @brief Unit Test case for PermissionDescription class.
+ *
+ * @covers Zotlabs\Lib\PermissionDescription
+ */
+class PermissionDescriptionTest extends UnitTestCase {
-// regular namespace for this unit test
-namespace Zotlabs\Tests\Unit\Lib {
+ use PHPMock;
- use Zotlabs\Tests\Unit\UnitTestCase;
- use Zotlabs\Lib\PermissionDescription;
+ public function testFromDescription() {
+ $permDesc = PermissionDescription::fromDescription('test');
+ $permDesc2 = PermissionDescription::fromDescription('test');
+ $permDesc3 = PermissionDescription::fromDescription('test2');
- /**
- * @brief Unit Test case for ConnectionPool class.
- */
- class PermissionDescriptionTest extends UnitTestCase {
+ $this->assertEquals($permDesc, $permDesc2);
+ $this->assertNotEquals($permDesc, $permDesc3);
+ }
- public function testFromDescription() {
- $permDesc = PermissionDescription::fromDescription('test');
- $permDesc2 = PermissionDescription::fromDescription('test');
- $permDesc3 = PermissionDescription::fromDescription('test2');
+ public function testFromStandalonePermission() {
+ // Create a stub for global function t()
+ $t = $this->getFunctionMock('Zotlabs\Lib', 't');
+ $t->expects($this->atLeastOnce())->willReturnCallback(
+ function ($string) {
+ return $string;
+ }
+ );
+ // Create a mock for global function logger()
+ $this->getFunctionMock('Zotlabs\Lib', 'logger');
- $this->assertEquals($permDesc, $permDesc2);
- $this->assertNotEquals($permDesc, $permDesc3);
- }
+ $permDescUnknown = PermissionDescription::fromStandalonePermission(-1);
+ $permDescSelf = PermissionDescription::fromStandalonePermission(0);
- public function testFromStandalonePermission() {
- $permDescUnknown = PermissionDescription::fromStandalonePermission(-1);
- $permDescSelf = PermissionDescription::fromStandalonePermission(0);
+ $this->assertNull($permDescUnknown);
+ $this->assertNotNull($permDescSelf);
+ }
- $this->assertNull($permDescUnknown);
- $this->assertNotNull($permDescSelf);
- }
+ public function testFromGlobalPermission() {
+ //$permDesc = PermissionDescription::fromGlobalPermission('view_profile');
- public function testFromGlobalPermission() {
- //$permDesc = PermissionDescription::fromGlobalPermission('view_profile');
+ $this->markTestIncomplete(
+ 'The method fromGlobalPermission() is not yet testable ...'
+ );
+ }
- $this->markTestIncomplete(
- 'For this test we need more stubs...'
- );
- }
+ public function testGetPermissionDescription() {
+ // Create a stub for global function t()
+ $t = $this->getFunctionMock('Zotlabs\Lib', 't');
+ $t->expects($this->atLeastOnce())->willReturnCallback(
+ function ($string) {
+ return $string;
+ }
+ );
+ // Create a mock for global function logger()
+ $this->getFunctionMock('Zotlabs\Lib', 'logger');
- public function testGetPermissionDescription() {
+ // Create a stub for the PermissionDescription class
+ $stub = $this->createMock(PermissionDescription::class);
+ $stub->method('get_permission_description')
+ ->will($this->returnArgument(0));
- // fromStandalonePermission uses get_permission_description(), so that will not help
- //$permDescSelf = PermissionDescription::fromStandalonePermission(0);
- //$permDescPublic = PermissionDescription::fromStandalonePermission(PERMS_PUBLIC);
+ $permDescSelf = PermissionDescription::fromStandalonePermission(0);
+ $this->assertInstanceOf(PermissionDescription::class, $permDescSelf);
+ $this->assertEquals($permDescSelf->get_permission_description(), 'Only me');
- $this->markTestIncomplete(
- 'For this test we need a mock of PermissionDescription...'
- );
- //$permDescSelf =
- //$this->assertEquals($permDescSelf->, 'Only me');
- //$this->assertEquals($permDescPublic, 'Public');
- }
+ $permDescPublic = PermissionDescription::fromStandalonePermission(PERMS_PUBLIC);
+ $this->assertEquals($permDescPublic->get_permission_description(), 'Public');
}
}
diff --git a/tests/unit/TextTest.php b/tests/unit/TextTest.php
deleted file mode 100644
index 48c04bc54..000000000
--- a/tests/unit/TextTest.php
+++ /dev/null
@@ -1,33 +0,0 @@
-<?php
-/**
- * this file contains tests for text.php
- *
- * @package test.util
- */
-
-use PHPUnit\Framework\TestCase;
-
-/** required, it is the file under test */
-require_once('include/text.php');
-
-/**
- * TestCase for the texter
- *
- * @author ken restivo
- * @package test.util
- */
-class TextTest extends TestCase {
- public function testGoodEmail() {
- $this->assertTrue(valid_email_regex('ken@spaz.org'));
- }
- public function testGoodEmail2() {
- $this->assertTrue(valid_email_regex('ken@restivo.org'));
- }
- public function testGoodEmail3() {
- $this->assertTrue(valid_email_regex('nobody@hubzilla.com'));
- }
- public function testBadEmail() {
- $this->assertFalse(valid_email_regex('nobody!uses!these!any.more'));
- }
-
-} \ No newline at end of file
diff --git a/tests/unit/includes/FeedutilsText.php b/tests/unit/includes/FeedutilsText.php
new file mode 100644
index 000000000..932a1b3a1
--- /dev/null
+++ b/tests/unit/includes/FeedutilsText.php
@@ -0,0 +1,55 @@
+<?php
+
+namespace Zotlabs\Tests\Unit\includes;
+
+use Zotlabs\Tests\Unit\UnitTestCase;
+
+/**
+ * @brief Unit Test case for include/feedutils.php file.
+ */
+class FeedutilsTest extends UnitTestCase {
+
+ public function test_normalise_id() {
+ $this->assertEquals('id', normalise_id('id'));
+ $this->assertEquals('id', normalise_id('X-ZOT:id'));
+ $this->assertEquals('id id2', normalise_id('X-ZOT:id X-ZOT:id2'));
+ $this->assertEmpty(normalise_id(''));
+ }
+
+ public function test_encode_rel_links() {
+ // invalid params return empty array
+ $this->assertEquals([], encode_rel_links('string'));
+ $this->assertEquals([], encode_rel_links([]));
+
+ $b = ['attribs' => ['' => [
+ 'rel' => 'rel_value',
+ 'type' => 'type_value',
+ 'href' => 'href_value'
+ ]]];
+ $blink1 = ['link1' => $b];
+ $bresult[] = $b['attribs'][''];
+ $this->assertEquals($bresult, encode_rel_links($blink1));
+ }
+
+/* public function test_encode_rel_links_fail() {
+ $a = [ 'key' => 'value'];
+ $this->assertFalse(encode_rel_links($a));
+ //Illegal string offset 'attribs'
+ }*/
+
+ public function test_atom_author() {
+ $this->assertEquals('', atom_author('', 'nick', 'name', 'uri', 72, 72, 'png', 'photourl'));
+
+ $a = '<tag>
+ <id>uri</id>
+ <name>nick</name>
+ <uri>uri</uri>
+ <link rel="photo" type="png" media:width="72" media:height="72" href="http://photourl" />
+ <link rel="avatar" type="png" media:width="72" media:height="72" href="http://photourl" />
+ <poco:preferredUsername>nick</poco:preferredUsername>
+ <poco:displayName>name<poco:displayName>
+</tag>';
+
+ $this->assertXmlStringEqualsXmlString($a, atom_author('tag', 'nick', 'name', 'uri', 72, 72, 'png', 'http://photourl'));
+ }
+}
diff --git a/tests/unit/includes/MarkdownTest.php b/tests/unit/includes/MarkdownTest.php
new file mode 100644
index 000000000..3026c633a
--- /dev/null
+++ b/tests/unit/includes/MarkdownTest.php
@@ -0,0 +1,149 @@
+<?php
+/*
+ * Copyright (c) 2017 Hubzilla
+*
+* Permission is hereby granted, free of charge, to any person obtaining a copy
+* of this software and associated documentation files (the "Software"), to deal
+* in the Software without restriction, including without limitation the rights
+* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+* copies of the Software, and to permit persons to whom the Software is
+* furnished to do so, subject to the following conditions:
+*
+* The above copyright notice and this permission notice shall be included in
+* all copies or substantial portions of the Software.
+*
+* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+* SOFTWARE.
+*/
+
+namespace Zotlabs\Tests\Unit\includes;
+
+use Zotlabs\Tests\Unit\UnitTestCase;
+use phpmock\phpunit\PHPMock;
+
+require_once 'include/markdown.php';
+
+/**
+ * @brief Unit Test case for markdown functions.
+ */
+class MarkdownTest extends UnitTestCase {
+ use PHPMock;
+
+ /**
+ * @covers ::html2markdown
+ * @dataProvider html2markdownProvider
+ */
+ public function testHtml2markdown($html, $markdown) {
+ $this->assertEquals($markdown, html2markdown($html));
+ }
+
+ public function html2markdownProvider() {
+ return [
+ 'empty text' => [
+ '',
+ ''
+ ],
+ 'space and nbsp only' => [
+ ' &nbsp;',
+ ''
+ ],
+ 'strong, b, em, i, bib' => [
+ '<strong>strong</strong> <b>bold</b> <em>em</em> <i>italic</i> <b>bo<i>italic</i>ld</b>',
+ '**strong** **bold** _em_ _italic_ **bo_italic_ld**'
+ ],
+ 'empty tags' => [
+ 'text1 <b></b> text2 <i></i>',
+ 'text1 text2'
+ ],
+ 'HTML entities, lt does not work' => [
+ '& gt > lt <',
+ '& gt > lt'
+ ],
+ 'escaped HTML entities' => [
+ '&amp; lt &lt; gt &gt;',
+ '& lt < gt >'
+ ],
+ 'our escaped HTML entities' => [
+ '&_lt_; &_gt_; &_amp_;',
+ '&\_lt\_; &\_gt\_; &\_amp\_;'
+ ],
+ 'linebreak' => [
+ "line1<br>line2\nline3",
+ "line1 \nline2 line3"
+ ],
+ 'headlines' => [
+ '<h1>header1</h1><h3>Header 3</h3>',
+ "header1\n=======\n\n### Header 3"
+ ],
+ 'unordered list' => [
+ '<ul><li>Item 1</li><li>Item 2</li><li>Item <b>3</b></li></ul>',
+ "- Item 1\n- Item 2\n- Item **3**"
+ ],
+ 'ordered list' => [
+ '<ol><li>Item 1</li><li>Item 2</li><li>Item <b>3</b></li></ol>',
+ "1. Item 1\n2. Item 2\n3. Item **3**"
+ ],
+ 'nested lists' => [
+ '<ul><li>Item 1<ol><li>Item 1a</li><li>Item <b>1b</b></ol></li><li>Item 2</li></ul>',
+ "- Item 1\n 1. Item 1a\n 2. Item **1b**\n- Item 2"
+ ],
+ 'img' => [
+ '<img src="/path/to/img.png" alt="alt text" title="title text">',
+ '![alt text](/path/to/img.png "title text")'
+ ],
+ 'link' => [
+ '<a href="http://hubzilla.org" title="Hubzilla">link</a>',
+ '[link](http://hubzilla.org "Hubzilla")'
+ ],
+ 'img link' => [
+ '<a href="http://hubzilla.org" title="Hubzilla"><img src="/img/hubzilla.png" alt="alt img text" title="img title"></a>',
+ '[![alt img text](/img/hubzilla.png "img title")](http://hubzilla.org "Hubzilla")'
+ ],
+ 'script' => [
+ "<script>alert('test');</script>",
+ "<script>alert('test');</script>"
+ ],
+ 'blockquote, issue #793' => [
+ '<blockquote>something</blockquote>blah',
+ "> something\n\nblah"
+ ],
+ 'code' => [
+ '<code>&lt;p&gt;HTML text&lt;/p&gt;</code>',
+ '`<p>HTML text</p>`'
+ ],
+ 'pre' => [
+ '<pre> line with spaces </pre>',
+ '` line with spaces `'
+ ],
+ 'div p' => [
+ '<div>div</div><div><p>p</p></div>',
+ "<div>div</div><div>p\n\n</div>"
+ ]
+ ];
+ }
+
+ /*public function testHtml2markdownException() {
+ //$this->expectException(\InvalidArgumentException::class);
+ // need to stub logger() for this to work
+ $this->assertEquals('', html2markdown('<<invalid'));
+ }*/
+
+/* public function testBB2diasporaMardown() {
+ //stub bbcode() and return our HTML, we just need to test the HTML2Markdown library.
+ $html1 = 'test<b>bold</b><br><i>i</i><ul><li>li1</li><li>li2</li></ul><br>';
+ $bb1 = 'test';
+
+ // php-mock can not mock global functions which is called by a global function.
+ // If the calling function is in a namespace it does work.
+ $bbc = $this->getFunctionMock(__NAMESPACE__, "bbcode");
+ $bbc->expects($this->once())->willReturn('test<b>bold</b><br><i>i</i><ul><li>li1</li><li>li2</li></ul><br>');
+
+ $this->assertEquals($bb1, bb2diaspora($html1));
+ }
+*/
+} \ No newline at end of file
diff --git a/tests/unit/includes/TextTest.php b/tests/unit/includes/TextTest.php
new file mode 100644
index 000000000..acc490001
--- /dev/null
+++ b/tests/unit/includes/TextTest.php
@@ -0,0 +1,82 @@
+<?php
+
+namespace Zotlabs\Tests\Unit\includes;
+
+use Zotlabs\Tests\Unit\UnitTestCase;
+
+/**
+ * @brief Unit Test case for include/texter.php file.
+ *
+ * @author ken restivo
+ */
+class TextTest extends UnitTestCase {
+
+
+ public function testPurifyHTML() {
+ // linebreaks
+ $htmlbr = 'first line<br />
+ one tab preserved
+
+empty line above';
+ $this->assertEquals($htmlbr, purify_html($htmlbr));
+
+ // HTML5 is not supported by HTMLPurifier yet, test our own configuration
+ $html5elements = '<section>section<nav>navigation</nav><article>main<a href="http://hubzilla.org/">hubzilla.org</a></article></section><footer>footer</footer>';
+ $this->assertEquals($html5elements, purify_html($html5elements));
+ $this->assertEquals('<button>button label</button>', purify_html('<button>button label</button>'));
+
+ // unsupported HTML5 elements
+ $this->assertEquals('Your HTML parser does not support HTML5 video.', purify_html('<video controls><source src="movie.ogg" type="video/ogg">Your HTML parser does not support HTML5 video.</video>'));
+ $this->assertEquals('Your HTML parser does not support HTML5 audio.', purify_html('<audio controls><source src="movie.ogg" "type="audio/ogg">Your HTML parser does not support HTML5 audio.</audio>'));
+
+ // preserve f6 and bootstrap additional data attributes from our own configuration
+ $this->assertEquals('<div data-title="title">text</div>', purify_html('<div data-title="title">text</div>'));
+ $this->assertEquals('<ul data-accordion-menu=""><li>item1</li></ul>', purify_html('<ul data-accordion-menu><li>item1</li></ul>'));
+ $this->assertEquals('<ul><li>item1</li></ul>', purify_html('<ul data-accordion-menu-unknown><li>item1</li></ul>'));
+ }
+
+ /**
+ * @covers ::purify_html
+ */
+ public function testPurifyHTML_html() {
+ $this->assertEquals('<div id="id01"><p class="class01">ids und classes</p></div>', purify_html('<div id="id01"><p class="class01">ids und classes</p></div>'));
+ $this->assertEquals('<div><p>close missing tags</p></div>', purify_html('<div><p>close missing tags'));
+ $this->assertEquals('<center>deprecated tag</center>', purify_html('<center>deprecated tag</center>'));
+ $this->assertEquals('<span></span><div>illegal nesting</div>', purify_html('<span><div>illegal nesting</div></span>'));
+ $this->assertEquals('<a href="#">link with target</a>', purify_html('<a href="#" target="_blank">link with target</a>'));
+ $this->assertEquals('<a href="#">link with rel="nofollow"</a>', purify_html('<a href="#" rel="nofollow">link with rel="nofollow"</a>'));
+ $this->assertEquals('a b', purify_html('a&nbsp;b'));
+ $this->assertEquals('ä ä € €', purify_html('ä &auml; &euro; &#8364;'));
+ $this->assertEquals('<img src="picture.png" alt="text" />', purify_html('<img src="picture.png" alt="text">'));
+ $this->assertEquals('', purify_html('<iframe width="560" height="315" src="https://www.youtube.com/embed/kiNGx5oL7hk" frameborder="0" allowfullscreen></iframe>'));
+ }
+
+ /**
+ * @covers ::purify_html
+ */
+ public function testPurifyHTML_js() {
+ $this->assertEquals('<div></div>', purify_html('<div><img src="javascript:evil();" onload="evil();"></div>'));
+ $this->assertEquals('<a href="#">link</a>', purify_html('<a href="#" onclick="alert(\'xss\')">link</a>'));
+ $this->assertEquals('', purify_html('<IMG SRC="javascript:alert(&#039;XSS&#039;);">'));
+ $this->assertEquals('', purify_html('<script>alter("42")</script>'));
+ }
+
+ /**
+ * @covers ::purify_html
+ */
+ public function testPurifyHTML_css() {
+ $this->assertEquals('<p style="color:#FF0000;background-color:#fff;">red</p>', purify_html('<p style="color:red; background-color:#fff">red</p>'));
+ $this->assertEquals('<p>invalid color</p>', purify_html('<p style="color:invalid; background-color:#jjkkmm">invalid color</p>'));
+ $this->assertEquals('<p>invalid style</p>', purify_html('<p style="foo:bar">invalid style</p>'));
+
+ // test our own CSS configuration
+ $this->assertEquals('<div>position removed</div>', purify_html('<div style="position:absolut">position removed</div>'));
+ $this->assertEquals('<div style="position:fixed;">position preserved</div>', purify_html('<div style="position:fixed">position preserved</div>', true));
+ $this->assertEquals('<div>invalid position removed</div>', purify_html('<div style="position:invalid">invalid position removed</div>', true));
+
+ $this->assertEquals('<div>position removed</div>', purify_html('<div style="top:10px; left:3em;">position removed</div>'));
+ $this->assertEquals('<div style="top:10px;left:3em;right:50%;">position preserved</div>', purify_html('<div style="top:10px; left:3em; right:50%;">position preserved</div>', true));
+ $this->assertEquals('<div>invalid position removed</div>', purify_html('<div style="top:10p">invalid position removed</div>', true));
+ }
+
+}
diff --git a/tests/unit/template_test.php b/tests/unit/template_test.php
index 1f9f80531..dfaecb4a1 100644
--- a/tests/unit/template_test.php
+++ b/tests/unit/template_test.php
@@ -25,12 +25,6 @@ function x($s,$k = NULL) {
}
}
-if(!function_exists('get_app')) {
-function get_app() {
- return new TemplateMockApp();
-}
-}
-
/**
* TestCase for the template engine
*
diff --git a/util/Doxyfile b/util/Doxyfile
index f6c0692ee..7be774a81 100644
--- a/util/Doxyfile
+++ b/util/Doxyfile
@@ -23,3 +23,15 @@ ALIASES += "TODO=\todo"
ALIASES += "BUG=\bug"
ALIASES += "hooks=\xrefitem hooks \"Hooks\" \"Hooks List\""
ALIASES += "HOOKS=\hooks"
+# Output
+QUIET = YES
+WARNINGS = YES
+# Dot tool config
+HAVE_DOT = YES
+DOT_IMAGE_FORMAT = svg
+INTERACTIVE_SVG = YES
+CLASS_GRAPH = YES
+COLLABORATION_GRAPH = NO
+# fix @var (https://bugzilla.gnome.org/show_bug.cgi?id=626105)
+#INPUT_FILTER = "sed -e 's/@var\s/@see /'"
+INPUT_FILTER = "php util/Doxygen_phpvarfilter.php"
diff --git a/util/Doxygen_phpvarfilter.php b/util/Doxygen_phpvarfilter.php
new file mode 100644
index 000000000..da6cf1666
--- /dev/null
+++ b/util/Doxygen_phpvarfilter.php
@@ -0,0 +1,18 @@
+<?php
+/**
+ * @file Doxygen_phpvarfilter.php
+ * @brief A Doxygen INPUT_FILTER to parse \@var member variable documentation.
+ *
+ * An input filter for Doxygen to parse \@var class member variable documentation,
+ * so it is a bit more compatible how anybody else interpretes it.
+ *
+ * @see http://stackoverflow.com/questions/4325224/doxygen-how-to-describe-class-member-variables-in-php/8472180#8472180
+ */
+
+$source = file_get_contents($argv[1]);
+
+$regexp = '#\@var\s+([^\s]+)([^/]+)/\s+(var|public|protected|private)\s+(\$[^\s;=]+)#';
+$replac = '${2} */ ${3} ${1} ${4}';
+$source = preg_replace($regexp, $replac, $source);
+
+echo $source;
diff --git a/util/db_update.php b/util/db_update.php
index ceef061c1..8fc7c7616 100644
--- a/util/db_update.php
+++ b/util/db_update.php
@@ -9,6 +9,7 @@ require_once('boot.php');
require_once('include/cli_startup.php');
cli_startup();
+$build = get_config('system','db_version');
echo "Old DB VERSION: " . $build . "\n";
echo "New DB VERSION: " . DB_UPDATE_VERSION . "\n";
@@ -16,7 +17,7 @@ echo "New DB VERSION: " . DB_UPDATE_VERSION . "\n";
if($build != DB_UPDATE_VERSION) {
echo "Updating database...";
- check_config($a);
+ check_config();
echo "Done\n";
}
diff --git a/util/dcp b/util/dcp
new file mode 100755
index 000000000..2817ad4f1
--- /dev/null
+++ b/util/dcp
@@ -0,0 +1,143 @@
+#!/usr/bin/env php
+<?php
+
+// file import to DAV utility
+
+if(!file_exists('include/cli_startup.php')) {
+ echo 'Run dcp from the top level Hubzilla web directory, as util/dcp <args>' . PHP_EOL;
+ exit(1);
+}
+
+require_once('include/cli_startup.php');
+require_once('include/attach.php');
+
+cli_startup();
+
+
+if($argc <= 3) {
+ echo "Usage: " . $argv[0] . ' src dstdir' . "\n";
+ echo 'Always run from the toplevel web directory.' . "\n";
+ echo 'destination should begin with store/$nickname/desired/path or $nickname/desired/path' . "\n";
+ echo 'Example: util/dcp /etc/motd store/joe/etc' . "\n";
+ exit;
+}
+
+ $recursive = false;
+ $dstfile = $argv[$argc - 1];
+
+ if(strpos($dstfile,'store/') === 0)
+ $dstfile = substr($dstfile,6);
+
+ $nick = substr($dstfile,0,strpos($dstfile,'/'));
+
+ $dstfile = substr($dstfile,strlen($nick)+1);
+
+ $channel = channelx_by_nick($nick);
+ if(! $channel)
+ return;
+
+ for($x = 1; $x < ($argc - 1); $x ++) {
+ if(($argv[$x] === '-r') || ($argv[$x] === '-R')) {
+ $recursive = true;
+ break;
+ }
+ }
+
+
+ $isadir = false;
+
+ if(($recursive) || ($argc > 3))
+ $isadir = true;
+
+
+ $r = q("select * from attach where display_path = '%s' and uid = %d limit 1",
+ dbesc($dstfile),
+ intval($channel['channel_id'])
+ );
+
+ if($r && $r[0]['is_dir']) {
+ $isadir = true;
+ $basepath = $dstfile;
+ $folder = $r[0]['hash'];
+ }
+ else {
+ $pathname = (($isadir) ? $dstfile : dirname($dstfile));
+ $arr = [
+ 'pathname' => $pathname,
+ 'allow_cid' => $channel['channel_allow_cid'],
+ 'allow_gid' => $channel['channel_allow_gid'],
+ 'deny_cid' => $channel['channel_deny_cid'],
+ 'deny_gid' => $channel['channel_deny_gid'],
+ ];
+
+ $folder = '';
+ if($pathname && $isadir) {
+ $x = attach_mkdirp($channel,$channel['channel_hash'],$arr);
+ if($x['success'])
+ $folder = $x['data']['hash'];
+ }
+ }
+
+ for($x = 1; $x < ($argc - 1); $x ++) {
+ if(($argv[$x] === '-r') || ($argv[$x] === '-R')) {
+ continue;
+ }
+
+ if(is_dir($argv[$x])) {
+ if($recursive) {
+ dcp_recurse($channel,$argv[$x],$basepath,$folder);
+ }
+ else {
+ continue;
+ }
+ }
+ else {
+ $dstname = (($isadir) ? '' : basename($dstfile));
+ $cmd = [ 'Importfile', $channel['channel_id'], $argv[$x], $folder, $dstname ];
+ \Zotlabs\Daemon\Master::Summon($cmd);
+ }
+ }
+
+
+ function dcp_recurse($channel,$src,$basepath,$folder) {
+ $dir = opendir($src);
+ if($dir) {
+ while(($entry = readdir($dir)) !== false) {
+ if($entry === '.' || $entry === '..')
+ continue;
+
+ $dstfile = $basepath . '/' . $entry;
+ if(is_dir($src . '/' . $entry)) {
+ $r = q("select * from attach where display_path = '%s' and uid = %d limit 1",
+ dbesc($dstfile),
+ intval($channel['channel_id'])
+ );
+
+ if($r && $r[0]['is_dir']) {
+ $folder = $r[0]['hash'];
+ }
+ else {
+
+ $arr = [
+ 'pathname' => $dstfile,
+ 'allow_cid' => $channel['channel_allow_cid'],
+ 'allow_gid' => $channel['channel_allow_gid'],
+ 'deny_cid' => $channel['channel_deny_cid'],
+ 'deny_gid' => $channel['channel_deny_gid'],
+ ];
+
+ $folder = '';
+ $x = attach_mkdirp($channel,$channel['channel_hash'],$arr);
+ if($x['success'])
+ $folder = $x['data']['hash'];
+ }
+ dcp_recurse($channel,$src . '/' . $entry,$dstfile,$folder);
+ }
+ else {
+ $cmd = [ 'Importfile', $channel['channel_id'], $src . '/' . $entry, $folder ];
+ \Zotlabs\Daemon\Master::Summon($cmd);
+ }
+ }
+ closedir($dir);
+ }
+ }
diff --git a/util/dmkdir b/util/dmkdir
new file mode 100755
index 000000000..72ab22431
--- /dev/null
+++ b/util/dmkdir
@@ -0,0 +1,57 @@
+#!/usr/bin/env php
+<?php
+
+// file import to DAV utility
+
+if(!file_exists('include/cli_startup.php')) {
+ echo 'Run dmkdir from the top level Hubzilla web directory, as util/dmkdir <args>' . PHP_EOL;
+ exit(1);
+}
+
+require_once('include/cli_startup.php');
+require_once('include/attach.php');
+
+cli_startup();
+
+$dstfile = $argv[1];
+
+if($argc != 2) {
+ echo "Usage: " . $argv[0] . ' directory' . "\n";
+ echo 'Always run from the toplevel web directory.' . "\n";
+ echo 'directory should begin with store/$nickname/desired/path or $nickname/desired/path' . "\n";
+ echo 'Example: util/dmkdir store/bob/photos/2017' . "\n";
+ exit;
+}
+
+
+
+ if(strpos($dstfile,'store/') === 0)
+ $dstfile = substr($dstfile,6);
+
+ $nick = substr($dstfile,0,strpos($dstfile,'/'));
+
+ $dstfile = substr($dstfile,strlen($nick)+1);
+
+ $channel = channelx_by_nick($nick);
+ if(! $channel)
+ return;
+
+
+ $arr = [
+ 'pathname' => $dstfile,
+ 'allow_cid' => $channel['channel_allow_cid'],
+ 'allow_gid' => $channel['channel_allow_gid'],
+ 'deny_cid' => $channel['channel_deny_cid'],
+ 'deny_gid' => $channel['channel_deny_gid'],
+ ];
+
+ $x = attach_mkdirp($channel,$channel['channel_hash'],$arr);
+
+ if($x['success']) {
+ $hash = $x['data']['hash'];
+
+ $sync = attach_export_data($channel,$hash);
+ if($sync) {
+ build_sync_packet($channel['channel_id'],array('file' => array($sync)));
+ }
+ } \ No newline at end of file
diff --git a/util/fresh b/util/fresh
index 7f57931aa..0482d1215 100755
--- a/util/fresh
+++ b/util/fresh
@@ -44,8 +44,6 @@ fresh_main($argc,$argv);
function process_command($line) {
- $a = get_app();
-
// split args
App::$cmd = $line;
diff --git a/util/hmessages.po b/util/hmessages.po
index f9f817747..8a2eb961f 100644
--- a/util/hmessages.po
+++ b/util/hmessages.po
@@ -6,9 +6,9 @@
#, fuzzy
msgid ""
msgstr ""
-"Project-Id-Version: 2.1\n"
+"Project-Id-Version: 2.9\n"
"Report-Msgid-Bugs-To: \n"
-"POT-Creation-Date: 2017-02-10 00:05-0800\n"
+"POT-Creation-Date: 2017-10-19 12:01+0200\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
@@ -17,2016 +17,2287 @@ msgstr ""
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
+#: ../../Zotlabs/Access/Permissions.php:53
+msgid "Can view my channel stream and posts"
+msgstr ""
+
+#: ../../Zotlabs/Access/Permissions.php:54
+msgid "Can send me their channel stream and posts"
+msgstr ""
+
+#: ../../Zotlabs/Access/Permissions.php:55
+msgid "Can view my default channel profile"
+msgstr ""
+
+#: ../../Zotlabs/Access/Permissions.php:56
+msgid "Can view my connections"
+msgstr ""
+
+#: ../../Zotlabs/Access/Permissions.php:57
+msgid "Can view my file storage and photos"
+msgstr ""
+
+#: ../../Zotlabs/Access/Permissions.php:58
+msgid "Can upload/modify my file storage and photos"
+msgstr ""
+
+#: ../../Zotlabs/Access/Permissions.php:59
+msgid "Can view my channel webpages"
+msgstr ""
+
+#: ../../Zotlabs/Access/Permissions.php:60
+msgid "Can view my wiki pages"
+msgstr ""
+
+#: ../../Zotlabs/Access/Permissions.php:61
+msgid "Can create/edit my channel webpages"
+msgstr ""
+
+#: ../../Zotlabs/Access/Permissions.php:62
+msgid "Can write to my wiki pages"
+msgstr ""
+
+#: ../../Zotlabs/Access/Permissions.php:63
+msgid "Can post on my channel (wall) page"
+msgstr ""
+
+#: ../../Zotlabs/Access/Permissions.php:64
+msgid "Can comment on or like my posts"
+msgstr ""
+
+#: ../../Zotlabs/Access/Permissions.php:65
+msgid "Can send me private mail messages"
+msgstr ""
+
+#: ../../Zotlabs/Access/Permissions.php:66
+msgid "Can like/dislike profiles and profile things"
+msgstr ""
+
+#: ../../Zotlabs/Access/Permissions.php:67
+msgid "Can forward to all my channel connections via @+ mentions in posts"
+msgstr ""
+
+#: ../../Zotlabs/Access/Permissions.php:68
+msgid "Can chat with me"
+msgstr ""
+
+#: ../../Zotlabs/Access/Permissions.php:69
+msgid "Can source my public posts in derived channels"
+msgstr ""
+
+#: ../../Zotlabs/Access/Permissions.php:70
+msgid "Can administer my channel"
+msgstr ""
+
#: ../../Zotlabs/Access/PermissionRoles.php:248
-#: ../../include/permissions.php:945
msgid "Social Networking"
msgstr ""
#: ../../Zotlabs/Access/PermissionRoles.php:249
-#: ../../include/permissions.php:945
msgid "Social - Mostly Public"
msgstr ""
#: ../../Zotlabs/Access/PermissionRoles.php:250
-#: ../../include/permissions.php:945
msgid "Social - Restricted"
msgstr ""
#: ../../Zotlabs/Access/PermissionRoles.php:251
-#: ../../include/permissions.php:945
msgid "Social - Private"
msgstr ""
#: ../../Zotlabs/Access/PermissionRoles.php:254
-#: ../../include/permissions.php:946
msgid "Community Forum"
msgstr ""
#: ../../Zotlabs/Access/PermissionRoles.php:255
-#: ../../include/permissions.php:946
msgid "Forum - Mostly Public"
msgstr ""
#: ../../Zotlabs/Access/PermissionRoles.php:256
-#: ../../include/permissions.php:946
msgid "Forum - Restricted"
msgstr ""
#: ../../Zotlabs/Access/PermissionRoles.php:257
-#: ../../include/permissions.php:946
msgid "Forum - Private"
msgstr ""
#: ../../Zotlabs/Access/PermissionRoles.php:260
-#: ../../include/permissions.php:947
msgid "Feed Republish"
msgstr ""
#: ../../Zotlabs/Access/PermissionRoles.php:261
-#: ../../include/permissions.php:947
msgid "Feed - Mostly Public"
msgstr ""
#: ../../Zotlabs/Access/PermissionRoles.php:262
-#: ../../include/permissions.php:947
msgid "Feed - Restricted"
msgstr ""
#: ../../Zotlabs/Access/PermissionRoles.php:265
-#: ../../include/permissions.php:948
msgid "Special Purpose"
msgstr ""
#: ../../Zotlabs/Access/PermissionRoles.php:266
-#: ../../include/permissions.php:948
msgid "Special - Celebrity/Soapbox"
msgstr ""
#: ../../Zotlabs/Access/PermissionRoles.php:267
-#: ../../include/permissions.php:948
msgid "Special - Group Repository"
msgstr ""
#: ../../Zotlabs/Access/PermissionRoles.php:270
-#: ../../Zotlabs/Module/Register.php:213 ../../Zotlabs/Module/Connedit.php:887
-#: ../../Zotlabs/Module/New_channel.php:132
-#: ../../Zotlabs/Module/Settings/Channel.php:447
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1148
-#: ../../extend/addon/addon/cdav/cdav.php:277
-#: ../../extend/addon/addon/cdav/cdav.php:284 ../../include/selectors.php:49
+#: ../../Zotlabs/Module/Cdav.php:1182 ../../Zotlabs/Module/New_channel.php:132
+#: ../../Zotlabs/Module/Settings/Channel.php:467
+#: ../../Zotlabs/Module/Connedit.php:936 ../../Zotlabs/Module/Profiles.php:798
+#: ../../Zotlabs/Module/Register.php:213 ../../include/selectors.php:49
#: ../../include/selectors.php:66 ../../include/selectors.php:104
-#: ../../include/selectors.php:140 ../../include/connections.php:901
-#: ../../include/connections.php:908 ../../include/permissions.php:949
+#: ../../include/selectors.php:140 ../../include/event.php:1297
+#: ../../include/event.php:1304 ../../include/connections.php:689
+#: ../../include/connections.php:696
msgid "Other"
msgstr ""
#: ../../Zotlabs/Access/PermissionRoles.php:271
-#: ../../include/permissions.php:949
msgid "Custom/Expert Mode"
msgstr ""
-#: ../../Zotlabs/Access/Permissions.php:46
-msgid "Can view my channel stream and posts"
+#: ../../Zotlabs/Module/Blocks.php:33 ../../Zotlabs/Module/Editlayout.php:31
+#: ../../Zotlabs/Module/Connect.php:17 ../../Zotlabs/Module/Achievements.php:15
+#: ../../Zotlabs/Module/Hcard.php:12 ../../Zotlabs/Module/Editblock.php:31
+#: ../../Zotlabs/Module/Profile.php:20 ../../Zotlabs/Module/Layouts.php:31
+#: ../../Zotlabs/Module/Editwebpage.php:32 ../../Zotlabs/Module/Cards.php:29
+#: ../../Zotlabs/Module/Webpages.php:33 ../../Zotlabs/Module/Filestorage.php:51
+#: ../../include/channel.php:1163
+msgid "Requested profile is not available."
msgstr ""
-#: ../../Zotlabs/Access/Permissions.php:47 ../../include/permissions.php:42
-msgid "Can send me their channel stream and posts"
+#: ../../Zotlabs/Module/Blocks.php:73 ../../Zotlabs/Module/Blocks.php:80
+#: ../../Zotlabs/Module/Invite.php:17 ../../Zotlabs/Module/Invite.php:94
+#: ../../Zotlabs/Module/Editlayout.php:67
+#: ../../Zotlabs/Module/Editlayout.php:90 ../../Zotlabs/Module/Channel.php:110
+#: ../../Zotlabs/Module/Channel.php:248 ../../Zotlabs/Module/Channel.php:288
+#: ../../Zotlabs/Module/Settings.php:59 ../../Zotlabs/Module/Locs.php:87
+#: ../../Zotlabs/Module/Mitem.php:115 ../../Zotlabs/Module/Events.php:271
+#: ../../Zotlabs/Module/Appman.php:82 ../../Zotlabs/Module/Regmod.php:21
+#: ../../Zotlabs/Module/New_channel.php:77
+#: ../../Zotlabs/Module/New_channel.php:104
+#: ../../Zotlabs/Module/Sharedwithme.php:16 ../../Zotlabs/Module/Setup.php:209
+#: ../../Zotlabs/Module/Moderate.php:13
+#: ../../Zotlabs/Module/Achievements.php:34 ../../Zotlabs/Module/Thing.php:275
+#: ../../Zotlabs/Module/Thing.php:295 ../../Zotlabs/Module/Thing.php:336
+#: ../../Zotlabs/Module/Api.php:24 ../../Zotlabs/Module/Editblock.php:67
+#: ../../Zotlabs/Module/Profile.php:85 ../../Zotlabs/Module/Profile.php:101
+#: ../../Zotlabs/Module/Mood.php:116 ../../Zotlabs/Module/Connections.php:29
+#: ../../Zotlabs/Module/Viewsrc.php:19 ../../Zotlabs/Module/Bookmarks.php:64
+#: ../../Zotlabs/Module/Photos.php:69 ../../Zotlabs/Module/Wiki.php:50
+#: ../../Zotlabs/Module/Wiki.php:273 ../../Zotlabs/Module/Wiki.php:388
+#: ../../Zotlabs/Module/Pdledit.php:29 ../../Zotlabs/Module/Poke.php:149
+#: ../../Zotlabs/Module/Profile_photo.php:288
+#: ../../Zotlabs/Module/Profile_photo.php:301
+#: ../../Zotlabs/Module/Authtest.php:16 ../../Zotlabs/Module/Item.php:223
+#: ../../Zotlabs/Module/Item.php:240 ../../Zotlabs/Module/Item.php:250
+#: ../../Zotlabs/Module/Item.php:1102 ../../Zotlabs/Module/Page.php:34
+#: ../../Zotlabs/Module/Page.php:125 ../../Zotlabs/Module/Connedit.php:389
+#: ../../Zotlabs/Module/Chat.php:100 ../../Zotlabs/Module/Chat.php:105
+#: ../../Zotlabs/Module/Menu.php:78 ../../Zotlabs/Module/Layouts.php:71
+#: ../../Zotlabs/Module/Layouts.php:78 ../../Zotlabs/Module/Layouts.php:89
+#: ../../Zotlabs/Module/Group.php:13 ../../Zotlabs/Module/Profiles.php:198
+#: ../../Zotlabs/Module/Profiles.php:635
+#: ../../Zotlabs/Module/Editwebpage.php:68
+#: ../../Zotlabs/Module/Editwebpage.php:89
+#: ../../Zotlabs/Module/Editwebpage.php:107
+#: ../../Zotlabs/Module/Editwebpage.php:121 ../../Zotlabs/Module/Manage.php:10
+#: ../../Zotlabs/Module/Cards.php:68 ../../Zotlabs/Module/Webpages.php:118
+#: ../../Zotlabs/Module/Block.php:24 ../../Zotlabs/Module/Block.php:74
+#: ../../Zotlabs/Module/Editpost.php:17 ../../Zotlabs/Module/Sources.php:74
+#: ../../Zotlabs/Module/Like.php:181 ../../Zotlabs/Module/Suggest.php:28
+#: ../../Zotlabs/Module/Message.php:18 ../../Zotlabs/Module/Mail.php:146
+#: ../../Zotlabs/Module/Register.php:77
+#: ../../Zotlabs/Module/Cover_photo.php:281
+#: ../../Zotlabs/Module/Cover_photo.php:294
+#: ../../Zotlabs/Module/Display.php:343 ../../Zotlabs/Module/Network.php:15
+#: ../../Zotlabs/Module/Filestorage.php:15
+#: ../../Zotlabs/Module/Filestorage.php:70
+#: ../../Zotlabs/Module/Filestorage.php:85
+#: ../../Zotlabs/Module/Filestorage.php:112 ../../Zotlabs/Module/Common.php:38
+#: ../../Zotlabs/Module/Viewconnections.php:28
+#: ../../Zotlabs/Module/Viewconnections.php:33
+#: ../../Zotlabs/Module/Service_limits.php:11 ../../Zotlabs/Module/Rate.php:113
+#: ../../Zotlabs/Module/Card_edit.php:51
+#: ../../Zotlabs/Module/Notifications.php:11 ../../Zotlabs/Lib/Chatroom.php:137
+#: ../../Zotlabs/Web/WebServer.php:169 ../../addon/keepout/keepout.php:36
+#: ../../addon/openid/Mod_Id.php:53 ../../addon/gitwiki/Mod_Gitwiki.php:196
+#: ../../addon/gitwiki/Mod_Gitwiki.php:292 ../../addon/pumpio/pumpio.php:40
+#: ../../include/attach.php:144 ../../include/attach.php:191
+#: ../../include/attach.php:255 ../../include/attach.php:269
+#: ../../include/attach.php:276 ../../include/attach.php:344
+#: ../../include/attach.php:358 ../../include/attach.php:365
+#: ../../include/attach.php:443 ../../include/attach.php:924
+#: ../../include/attach.php:998 ../../include/attach.php:1163
+#: ../../include/items.php:3489 ../../include/photos.php:28
+msgid "Permission denied."
msgstr ""
-#: ../../Zotlabs/Access/Permissions.php:48 ../../include/permissions.php:36
-msgid "Can view my default channel profile"
+#: ../../Zotlabs/Module/Blocks.php:97 ../../Zotlabs/Module/Blocks.php:155
+#: ../../Zotlabs/Module/Editblock.php:113
+msgid "Block Name"
msgstr ""
-#: ../../Zotlabs/Access/Permissions.php:49 ../../include/permissions.php:37
-msgid "Can view my connections"
+#: ../../Zotlabs/Module/Blocks.php:154 ../../include/text.php:2288
+msgid "Blocks"
msgstr ""
-#: ../../Zotlabs/Access/Permissions.php:50 ../../include/permissions.php:38
-msgid "Can view my file storage and photos"
+#: ../../Zotlabs/Module/Blocks.php:156
+msgid "Block Title"
msgstr ""
-#: ../../Zotlabs/Access/Permissions.php:51
-msgid "Can upload/modify my file storage and photos"
+#: ../../Zotlabs/Module/Blocks.php:157 ../../Zotlabs/Module/Menu.php:114
+#: ../../Zotlabs/Module/Layouts.php:191 ../../Zotlabs/Module/Webpages.php:251
+msgid "Created"
msgstr ""
-#: ../../Zotlabs/Access/Permissions.php:52
-msgid "Can view my channel webpages"
+#: ../../Zotlabs/Module/Blocks.php:158 ../../Zotlabs/Module/Menu.php:115
+#: ../../Zotlabs/Module/Layouts.php:192 ../../Zotlabs/Module/Webpages.php:252
+msgid "Edited"
msgstr ""
-#: ../../Zotlabs/Access/Permissions.php:53
-msgid "Can view my wiki pages"
+#: ../../Zotlabs/Module/Blocks.php:159 ../../Zotlabs/Module/Cdav.php:1185
+#: ../../Zotlabs/Module/New_channel.php:147
+#: ../../Zotlabs/Module/Connedit.php:939 ../../Zotlabs/Module/Menu.php:118
+#: ../../Zotlabs/Module/Layouts.php:185 ../../Zotlabs/Module/Profiles.php:801
+#: ../../Zotlabs/Module/Cards.php:96 ../../Zotlabs/Module/Webpages.php:239
+#: ../../Zotlabs/Storage/Browser.php:229 ../../Zotlabs/Storage/Browser.php:335
+#: ../../Zotlabs/Widget/Cdav.php:127 ../../Zotlabs/Widget/Cdav.php:164
+msgid "Create"
msgstr ""
-#: ../../Zotlabs/Access/Permissions.php:54
-msgid "Can create/edit my channel webpages"
+#: ../../Zotlabs/Module/Blocks.php:160 ../../Zotlabs/Module/Editlayout.php:114
+#: ../../Zotlabs/Module/Admin/Profs.php:154
+#: ../../Zotlabs/Module/Settings/Oauth.php:149
+#: ../../Zotlabs/Module/Thing.php:261 ../../Zotlabs/Module/Editblock.php:114
+#: ../../Zotlabs/Module/Connections.php:260
+#: ../../Zotlabs/Module/Connections.php:297
+#: ../../Zotlabs/Module/Connections.php:317 ../../Zotlabs/Module/Wiki.php:202
+#: ../../Zotlabs/Module/Wiki.php:346 ../../Zotlabs/Module/Menu.php:112
+#: ../../Zotlabs/Module/Layouts.php:193
+#: ../../Zotlabs/Module/Editwebpage.php:142
+#: ../../Zotlabs/Module/Webpages.php:240 ../../Zotlabs/Module/Editpost.php:85
+#: ../../Zotlabs/Module/Card_edit.php:99 ../../Zotlabs/Lib/Apps.php:399
+#: ../../Zotlabs/Lib/ThreadItem.php:111 ../../Zotlabs/Storage/Browser.php:239
+#: ../../Zotlabs/Widget/Cdav.php:125 ../../Zotlabs/Widget/Cdav.php:161
+#: ../../addon/gitwiki/Mod_Gitwiki.php:151
+#: ../../addon/gitwiki/Mod_Gitwiki.php:252 ../../include/channel.php:1262
+#: ../../include/channel.php:1266 ../../include/menu.php:113
+msgid "Edit"
msgstr ""
-#: ../../Zotlabs/Access/Permissions.php:55
-msgid "Can write to my wiki pages"
+#: ../../Zotlabs/Module/Blocks.php:161 ../../Zotlabs/Module/Photos.php:1049
+#: ../../Zotlabs/Module/Layouts.php:194 ../../Zotlabs/Module/Webpages.php:241
+#: ../../Zotlabs/Widget/Cdav.php:123 ../../include/conversation.php:1346
+msgid "Share"
msgstr ""
-#: ../../Zotlabs/Access/Permissions.php:56
-msgid "Can post on my channel (wall) page"
+#: ../../Zotlabs/Module/Blocks.php:162 ../../Zotlabs/Module/Editlayout.php:138
+#: ../../Zotlabs/Module/Cdav.php:897 ../../Zotlabs/Module/Cdav.php:1187
+#: ../../Zotlabs/Module/Admin/Accounts.php:173
+#: ../../Zotlabs/Module/Admin/Channels.php:149
+#: ../../Zotlabs/Module/Admin/Profs.php:155
+#: ../../Zotlabs/Module/Settings/Oauth.php:150
+#: ../../Zotlabs/Module/Thing.php:262 ../../Zotlabs/Module/Editblock.php:139
+#: ../../Zotlabs/Module/Connections.php:268
+#: ../../Zotlabs/Module/Photos.php:1150 ../../Zotlabs/Module/Connedit.php:654
+#: ../../Zotlabs/Module/Connedit.php:941 ../../Zotlabs/Module/Group.php:179
+#: ../../Zotlabs/Module/Profiles.php:803
+#: ../../Zotlabs/Module/Editwebpage.php:167
+#: ../../Zotlabs/Module/Webpages.php:242 ../../Zotlabs/Module/Card_edit.php:129
+#: ../../Zotlabs/Lib/Apps.php:400 ../../Zotlabs/Lib/ThreadItem.php:131
+#: ../../Zotlabs/Storage/Browser.php:240 ../../include/conversation.php:674
+#: ../../include/conversation.php:717
+msgid "Delete"
msgstr ""
-#: ../../Zotlabs/Access/Permissions.php:57 ../../include/permissions.php:44
-msgid "Can comment on or like my posts"
+#: ../../Zotlabs/Module/Blocks.php:166 ../../Zotlabs/Module/Events.php:694
+#: ../../Zotlabs/Module/Wiki.php:204 ../../Zotlabs/Module/Layouts.php:198
+#: ../../Zotlabs/Module/Webpages.php:246 ../../Zotlabs/Module/Pubsites.php:60
+#: ../../addon/gitwiki/Mod_Gitwiki.php:153
+msgid "View"
msgstr ""
-#: ../../Zotlabs/Access/Permissions.php:58 ../../include/permissions.php:45
-msgid "Can send me private mail messages"
+#: ../../Zotlabs/Module/Invite.php:29
+msgid "Total invitation limit exceeded."
msgstr ""
-#: ../../Zotlabs/Access/Permissions.php:59
-msgid "Can like/dislike profiles and profile things"
+#: ../../Zotlabs/Module/Invite.php:53
+#, php-format
+msgid "%s : Not a valid email address."
msgstr ""
-#: ../../Zotlabs/Access/Permissions.php:60
-msgid "Can forward to all my channel connections via @+ mentions in posts"
+#: ../../Zotlabs/Module/Invite.php:67
+msgid "Please join us on $Projectname"
msgstr ""
-#: ../../Zotlabs/Access/Permissions.php:61
-msgid "Can chat with me"
+#: ../../Zotlabs/Module/Invite.php:77
+msgid "Invitation limit exceeded. Please contact your site administrator."
msgstr ""
-#: ../../Zotlabs/Access/Permissions.php:62 ../../include/permissions.php:53
-msgid "Can source my public posts in derived channels"
+#: ../../Zotlabs/Module/Invite.php:82
+#, php-format
+msgid "%s : Message delivery failed."
msgstr ""
-#: ../../Zotlabs/Access/Permissions.php:63
-msgid "Can administer my channel"
+#: ../../Zotlabs/Module/Invite.php:86
+#, php-format
+msgid "%d message sent."
+msgid_plural "%d messages sent."
+msgstr[0] ""
+msgstr[1] ""
+
+#: ../../Zotlabs/Module/Invite.php:107
+msgid "You have no more invitations available"
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:106 ../../Zotlabs/Storage/Browser.php:237
-msgid "parent"
+#: ../../Zotlabs/Module/Invite.php:138
+msgid "Send invitations"
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:130 ../../include/text.php:2698
-msgid "Collection"
+#: ../../Zotlabs/Module/Invite.php:139
+msgid "Enter email addresses, one per line:"
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:133
-msgid "Principal"
+#: ../../Zotlabs/Module/Invite.php:140 ../../Zotlabs/Module/Mail.php:285
+msgid "Your message:"
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:136
-msgid "Addressbook"
+#: ../../Zotlabs/Module/Invite.php:141
+msgid "Please join my community on $Projectname."
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:139
-msgid "Calendar"
+#: ../../Zotlabs/Module/Invite.php:143
+msgid "You will need to supply this invitation code:"
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:142
-msgid "Schedule Inbox"
+#: ../../Zotlabs/Module/Invite.php:144
+msgid "1. Register at any $Projectname location (they are all inter-connected)"
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:145
-msgid "Schedule Outbox"
+#: ../../Zotlabs/Module/Invite.php:146
+msgid "2. Enter my $Projectname network address into the site searchbar."
+msgstr ""
+
+#: ../../Zotlabs/Module/Invite.php:147
+msgid "or visit"
+msgstr ""
+
+#: ../../Zotlabs/Module/Invite.php:149
+msgid "3. Click [Connect]"
+msgstr ""
+
+#: ../../Zotlabs/Module/Invite.php:151 ../../Zotlabs/Module/Locs.php:121
+#: ../../Zotlabs/Module/Mitem.php:243 ../../Zotlabs/Module/Events.php:493
+#: ../../Zotlabs/Module/Appman.php:148
+#: ../../Zotlabs/Module/Import_items.php:129 ../../Zotlabs/Module/Setup.php:308
+#: ../../Zotlabs/Module/Setup.php:349 ../../Zotlabs/Module/Connect.php:98
+#: ../../Zotlabs/Module/Admin/Features.php:66
+#: ../../Zotlabs/Module/Admin/Plugins.php:438
+#: ../../Zotlabs/Module/Admin/Accounts.php:166
+#: ../../Zotlabs/Module/Admin/Logs.php:84
+#: ../../Zotlabs/Module/Admin/Channels.php:147
+#: ../../Zotlabs/Module/Admin/Themes.php:158
+#: ../../Zotlabs/Module/Admin/Site.php:273
+#: ../../Zotlabs/Module/Admin/Profs.php:157
+#: ../../Zotlabs/Module/Admin/Account_edit.php:74
+#: ../../Zotlabs/Module/Admin/Security.php:104
+#: ../../Zotlabs/Module/Settings/Permcats.php:110
+#: ../../Zotlabs/Module/Settings/Channel.php:480
+#: ../../Zotlabs/Module/Settings/Features.php:47
+#: ../../Zotlabs/Module/Settings/Tokens.php:168
+#: ../../Zotlabs/Module/Settings/Account.php:118
+#: ../../Zotlabs/Module/Settings/Featured.php:52
+#: ../../Zotlabs/Module/Settings/Display.php:207
+#: ../../Zotlabs/Module/Settings/Oauth.php:87
+#: ../../Zotlabs/Module/Thing.php:321 ../../Zotlabs/Module/Thing.php:374
+#: ../../Zotlabs/Module/Import.php:529 ../../Zotlabs/Module/Cal.php:343
+#: ../../Zotlabs/Module/Mood.php:139 ../../Zotlabs/Module/Photos.php:659
+#: ../../Zotlabs/Module/Photos.php:1029 ../../Zotlabs/Module/Photos.php:1069
+#: ../../Zotlabs/Module/Photos.php:1187 ../../Zotlabs/Module/Wiki.php:206
+#: ../../Zotlabs/Module/Pdledit.php:94 ../../Zotlabs/Module/Poke.php:200
+#: ../../Zotlabs/Module/Connedit.php:904 ../../Zotlabs/Module/Chat.php:196
+#: ../../Zotlabs/Module/Chat.php:242 ../../Zotlabs/Module/Pconfig.php:107
+#: ../../Zotlabs/Module/Group.php:87 ../../Zotlabs/Module/Profiles.php:726
+#: ../../Zotlabs/Module/Sources.php:114 ../../Zotlabs/Module/Sources.php:149
+#: ../../Zotlabs/Module/Xchan.php:15 ../../Zotlabs/Module/Mail.php:431
+#: ../../Zotlabs/Module/Filestorage.php:155 ../../Zotlabs/Module/Rate.php:166
+#: ../../Zotlabs/Lib/ThreadItem.php:743 ../../Zotlabs/Widget/Eventstools.php:16
+#: ../../Zotlabs/Widget/Wiki_pages.php:61
+#: ../../view/theme/redbasic_c/php/config.php:95
+#: ../../view/theme/redbasic/php/config.php:93
+#: ../../addon/skeleton/skeleton.php:65 ../../addon/gnusoc/gnusoc.php:269
+#: ../../addon/planets/planets.php:153
+#: ../../addon/openclipatar/openclipatar.php:53
+#: ../../addon/wppost/wppost.php:113 ../../addon/nsfw/nsfw.php:92
+#: ../../addon/ijpost/ijpost.php:89 ../../addon/dwpost/dwpost.php:89
+#: ../../addon/mailhost/mailhost.php:40
+#: ../../addon/likebanner/likebanner.php:57
+#: ../../addon/redphotos/redphotos.php:136 ../../addon/irc/irc.php:53
+#: ../../addon/ljpost/ljpost.php:86 ../../addon/startpage/startpage.php:113
+#: ../../addon/diaspora/diaspora.php:807
+#: ../../addon/gitwiki/Mod_Gitwiki.php:155
+#: ../../addon/rainbowtag/rainbowtag.php:85 ../../addon/visage/visage.php:170
+#: ../../addon/nsabait/nsabait.php:161 ../../addon/mailtest/mailtest.php:100
+#: ../../addon/openstreetmap/openstreetmap.php:168
+#: ../../addon/rtof/rtof.php:101 ../../addon/jappixmini/jappixmini.php:371
+#: ../../addon/superblock/superblock.php:120 ../../addon/nofed/nofed.php:80
+#: ../../addon/redred/redred.php:119 ../../addon/logrot/logrot.php:35
+#: ../../addon/frphotos/frphotos.php:96 ../../addon/pubcrawl/pubcrawl.php:1049
+#: ../../addon/chords/Mod_Chords.php:60 ../../addon/libertree/libertree.php:85
+#: ../../addon/flattrwidget/flattrwidget.php:124
+#: ../../addon/statusnet/statusnet.php:322
+#: ../../addon/statusnet/statusnet.php:380
+#: ../../addon/statusnet/statusnet.php:432
+#: ../../addon/statusnet/statusnet.php:899 ../../addon/twitter/twitter.php:217
+#: ../../addon/twitter/twitter.php:259
+#: ../../addon/smileybutton/smileybutton.php:219 ../../addon/piwik/piwik.php:95
+#: ../../addon/pageheader/pageheader.php:48
+#: ../../addon/authchoose/authchoose.php:71 ../../addon/xmpp/xmpp.php:69
+#: ../../addon/pumpio/pumpio.php:237 ../../addon/redfiles/redfiles.php:124
+#: ../../addon/hubwall/hubwall.php:95 ../../include/js_strings.php:22
+msgid "Submit"
+msgstr ""
+
+#: ../../Zotlabs/Module/Editlayout.php:79 ../../Zotlabs/Module/Editblock.php:79
+#: ../../Zotlabs/Module/Editblock.php:95
+#: ../../Zotlabs/Module/Editwebpage.php:80 ../../Zotlabs/Module/Editpost.php:24
+#: ../../Zotlabs/Module/Card_edit.php:17 ../../Zotlabs/Module/Card_edit.php:33
+msgid "Item not found"
+msgstr ""
+
+#: ../../Zotlabs/Module/Editlayout.php:128 ../../Zotlabs/Module/Layouts.php:129
+#: ../../Zotlabs/Module/Layouts.php:189
+msgid "Layout Name"
+msgstr ""
+
+#: ../../Zotlabs/Module/Editlayout.php:129 ../../Zotlabs/Module/Layouts.php:132
+msgid "Layout Description (Optional)"
+msgstr ""
+
+#: ../../Zotlabs/Module/Editlayout.php:137
+msgid "Edit Layout"
+msgstr ""
+
+#: ../../Zotlabs/Module/Profperm.php:28 ../../Zotlabs/Module/Subthread.php:62
+#: ../../Zotlabs/Module/Import_items.php:120 ../../Zotlabs/Module/Group.php:74
+#: ../../Zotlabs/Module/Dreport.php:10 ../../Zotlabs/Module/Dreport.php:68
+#: ../../Zotlabs/Module/Like.php:283 ../../Zotlabs/Web/WebServer.php:168
+#: ../../addon/redphotos/redphotos.php:119 ../../addon/frphotos/frphotos.php:81
+#: ../../addon/redfiles/redfiles.php:109 ../../include/items.php:346
+msgid "Permission denied"
+msgstr ""
+
+#: ../../Zotlabs/Module/Profperm.php:34 ../../Zotlabs/Module/Profperm.php:63
+msgid "Invalid profile identifier."
+msgstr ""
+
+#: ../../Zotlabs/Module/Profperm.php:111
+msgid "Profile Visibility Editor"
+msgstr ""
+
+#: ../../Zotlabs/Module/Profperm.php:113 ../../include/channel.php:1585
+msgid "Profile"
+msgstr ""
+
+#: ../../Zotlabs/Module/Profperm.php:115
+msgid "Click on a contact to add or remove."
+msgstr ""
+
+#: ../../Zotlabs/Module/Profperm.php:124
+msgid "Visible To"
+msgstr ""
+
+#: ../../Zotlabs/Module/Profperm.php:140
+#: ../../Zotlabs/Module/Connections.php:140
+msgid "All Connections"
+msgstr ""
+
+#: ../../Zotlabs/Module/Cdav.php:785
+msgid "INVALID EVENT DISMISSED!"
+msgstr ""
+
+#: ../../Zotlabs/Module/Cdav.php:786
+msgid "Summary: "
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:163 ../../Zotlabs/Module/Photos.php:784
-#: ../../Zotlabs/Module/Photos.php:1244
-#: ../../Zotlabs/Module/Embedphotos.php:145 ../../Zotlabs/Lib/Apps.php:559
-#: ../../Zotlabs/Lib/Apps.php:637
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:745
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:746
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:753
-#: ../../include/conversation.php:1177 ../../include/widgets.php:1714
+#: ../../Zotlabs/Module/Cdav.php:786 ../../Zotlabs/Module/Cdav.php:787
+#: ../../Zotlabs/Module/Cdav.php:794 ../../Zotlabs/Module/Embedphotos.php:146
+#: ../../Zotlabs/Module/Photos.php:764 ../../Zotlabs/Module/Photos.php:1220
+#: ../../Zotlabs/Lib/Apps.php:727 ../../Zotlabs/Lib/Apps.php:805
+#: ../../Zotlabs/Storage/Browser.php:164 ../../Zotlabs/Widget/Portfolio.php:86
+#: ../../Zotlabs/Widget/Album.php:84 ../../addon/pubcrawl/as.php:841
+#: ../../include/conversation.php:1143
msgid "Unknown"
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:224 ../../Zotlabs/Module/Fbrowser.php:85
-#: ../../Zotlabs/Lib/Apps.php:224 ../../include/conversation.php:1843
-msgid "Files"
+#: ../../Zotlabs/Module/Cdav.php:787
+msgid "Date: "
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:225
-msgid "Total"
+#: ../../Zotlabs/Module/Cdav.php:788 ../../Zotlabs/Module/Cdav.php:795
+msgid "Reason: "
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:227
-msgid "Shared"
+#: ../../Zotlabs/Module/Cdav.php:793
+msgid "INVALID CARD DISMISSED!"
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:228 ../../Zotlabs/Storage/Browser.php:321
-#: ../../Zotlabs/Module/Menu.php:118 ../../Zotlabs/Module/Connedit.php:890
-#: ../../Zotlabs/Module/New_channel.php:147
-#: ../../Zotlabs/Module/Blocks.php:159 ../../Zotlabs/Module/Layouts.php:184
-#: ../../Zotlabs/Module/Webpages.php:243
-#: ../../extend/addon/addon/cdav/include/widgets.php:127
-#: ../../extend/addon/addon/cdav/include/widgets.php:164
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1151
-msgid "Create"
+#: ../../Zotlabs/Module/Cdav.php:794
+msgid "Name: "
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:229 ../../Zotlabs/Storage/Browser.php:323
-#: ../../Zotlabs/Module/Photos.php:811 ../../Zotlabs/Module/Photos.php:1368
-#: ../../Zotlabs/Module/Cover_photo.php:357
-#: ../../Zotlabs/Module/Profile_photo.php:410
-#: ../../Zotlabs/Module/Embedphotos.php:157
-#: ../../extend/addon/addon/cdav/include/widgets.php:132
-#: ../../extend/addon/addon/cdav/include/widgets.php:168
-#: ../../include/widgets.php:1727
-msgid "Upload"
+#: ../../Zotlabs/Module/Cdav.php:868 ../../Zotlabs/Module/Events.php:460
+msgid "Event title"
+msgstr ""
+
+#: ../../Zotlabs/Module/Cdav.php:869 ../../Zotlabs/Module/Events.php:466
+msgid "Start date and time"
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:233
+#: ../../Zotlabs/Module/Cdav.php:869 ../../Zotlabs/Module/Cdav.php:870
+msgid "Example: YYYY-MM-DD HH:mm"
+msgstr ""
+
+#: ../../Zotlabs/Module/Cdav.php:870
+msgid "End date and time"
+msgstr ""
+
+#: ../../Zotlabs/Module/Cdav.php:871 ../../Zotlabs/Module/Events.php:473
+#: ../../Zotlabs/Module/Appman.php:138 ../../Zotlabs/Module/Rbmark.php:101
+#: ../../addon/rendezvous/rendezvous.php:173
+msgid "Description"
+msgstr ""
+
+#: ../../Zotlabs/Module/Cdav.php:872 ../../Zotlabs/Module/Locs.php:117
+#: ../../Zotlabs/Module/Events.php:475 ../../Zotlabs/Module/Profiles.php:509
+#: ../../Zotlabs/Module/Profiles.php:737 ../../Zotlabs/Module/Pubsites.php:52
+#: ../../include/js_strings.php:25
+msgid "Location"
+msgstr ""
+
+#: ../../Zotlabs/Module/Cdav.php:879 ../../Zotlabs/Module/Events.php:689
+#: ../../Zotlabs/Module/Events.php:698 ../../Zotlabs/Module/Cal.php:337
+#: ../../Zotlabs/Module/Cal.php:344 ../../Zotlabs/Module/Photos.php:918
+msgid "Previous"
+msgstr ""
+
+#: ../../Zotlabs/Module/Cdav.php:880 ../../Zotlabs/Module/Events.php:690
+#: ../../Zotlabs/Module/Events.php:699 ../../Zotlabs/Module/Setup.php:263
+#: ../../Zotlabs/Module/Cal.php:338 ../../Zotlabs/Module/Cal.php:345
+#: ../../Zotlabs/Module/Photos.php:927
+msgid "Next"
+msgstr ""
+
+#: ../../Zotlabs/Module/Cdav.php:881 ../../Zotlabs/Module/Events.php:700
+#: ../../Zotlabs/Module/Cal.php:346
+msgid "Today"
+msgstr ""
+
+#: ../../Zotlabs/Module/Cdav.php:882 ../../Zotlabs/Module/Events.php:695
+msgid "Month"
+msgstr ""
+
+#: ../../Zotlabs/Module/Cdav.php:883 ../../Zotlabs/Module/Events.php:696
+msgid "Week"
+msgstr ""
+
+#: ../../Zotlabs/Module/Cdav.php:884 ../../Zotlabs/Module/Events.php:697
+msgid "Day"
+msgstr ""
+
+#: ../../Zotlabs/Module/Cdav.php:885
+msgid "List month"
+msgstr ""
+
+#: ../../Zotlabs/Module/Cdav.php:886
+msgid "List week"
+msgstr ""
+
+#: ../../Zotlabs/Module/Cdav.php:887
+msgid "List day"
+msgstr ""
+
+#: ../../Zotlabs/Module/Cdav.php:894
+msgid "More"
+msgstr ""
+
+#: ../../Zotlabs/Module/Cdav.php:895
+msgid "Less"
+msgstr ""
+
+#: ../../Zotlabs/Module/Cdav.php:896
+msgid "Select calendar"
+msgstr ""
+
+#: ../../Zotlabs/Module/Cdav.php:898
+msgid "Delete all"
+msgstr ""
+
+#: ../../Zotlabs/Module/Cdav.php:899 ../../Zotlabs/Module/Cdav.php:1188
+#: ../../Zotlabs/Module/Admin/Plugins.php:423
+#: ../../Zotlabs/Module/Settings/Oauth.php:88
+#: ../../Zotlabs/Module/Settings/Oauth.php:114
+#: ../../Zotlabs/Module/Wiki.php:333 ../../Zotlabs/Module/Wiki.php:363
+#: ../../Zotlabs/Module/Connedit.php:942 ../../Zotlabs/Module/Fbrowser.php:66
+#: ../../Zotlabs/Module/Fbrowser.php:88 ../../Zotlabs/Module/Profiles.php:804
+#: ../../Zotlabs/Module/Filer.php:55 ../../Zotlabs/Module/Tagrm.php:15
+#: ../../Zotlabs/Module/Tagrm.php:138 ../../addon/js_upload/js_upload.php:46
+#: ../../addon/gitwiki/Mod_Gitwiki.php:244
+#: ../../addon/gitwiki/Mod_Gitwiki.php:267 ../../include/conversation.php:1369
+#: ../../include/conversation.php:1418
+msgid "Cancel"
+msgstr ""
+
+#: ../../Zotlabs/Module/Cdav.php:900
+msgid "Sorry! Editing of recurrent events is not yet implemented."
+msgstr ""
+
+#: ../../Zotlabs/Module/Cdav.php:1170 ../../Zotlabs/Module/Sharedwithme.php:105
#: ../../Zotlabs/Module/Admin/Channels.php:159
-#: ../../Zotlabs/Module/Connedit.php:875
-#: ../../Zotlabs/Module/Sharedwithme.php:99 ../../Zotlabs/Module/Wiki.php:170
#: ../../Zotlabs/Module/Settings/Oauth.php:89
#: ../../Zotlabs/Module/Settings/Oauth.php:115
-#: ../../Zotlabs/Module/Chat.php:250
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1136
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:172
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:156
-#: ../../include/widgets.php:990
+#: ../../Zotlabs/Module/Wiki.php:209 ../../Zotlabs/Module/Connedit.php:924
+#: ../../Zotlabs/Module/Chat.php:251 ../../Zotlabs/Lib/NativeWikiPage.php:554
+#: ../../Zotlabs/Storage/Browser.php:234
+#: ../../Zotlabs/Widget/Wiki_page_history.php:22
+#: ../../addon/rendezvous/rendezvous.php:172
+#: ../../addon/gitwiki/Mod_Gitwiki.php:158
msgid "Name"
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:234 ../../Zotlabs/Module/Wiki.php:171
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:157
-msgid "Type"
+#: ../../Zotlabs/Module/Cdav.php:1171 ../../Zotlabs/Module/Connedit.php:925
+msgid "Organisation"
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:235
-#: ../../Zotlabs/Module/Sharedwithme.php:101 ../../include/text.php:1406
-msgid "Size"
+#: ../../Zotlabs/Module/Cdav.php:1172 ../../Zotlabs/Module/Connedit.php:926
+msgid "Title"
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:236
-#: ../../Zotlabs/Module/Sharedwithme.php:102
-msgid "Last Modified"
+#: ../../Zotlabs/Module/Cdav.php:1173 ../../Zotlabs/Module/Connedit.php:927
+#: ../../Zotlabs/Module/Profiles.php:789
+msgid "Phone"
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:238 ../../Zotlabs/Module/Editpost.php:85
-#: ../../Zotlabs/Module/Editblock.php:109
-#: ../../Zotlabs/Module/Connections.php:300
-#: ../../Zotlabs/Module/Connections.php:320
-#: ../../Zotlabs/Module/Admin/Profs.php:154
-#: ../../Zotlabs/Module/Editlayout.php:114
-#: ../../Zotlabs/Module/Editwebpage.php:145 ../../Zotlabs/Module/Menu.php:112
-#: ../../Zotlabs/Module/Blocks.php:160 ../../Zotlabs/Module/Layouts.php:192
-#: ../../Zotlabs/Module/Webpages.php:244 ../../Zotlabs/Module/Wiki.php:163
-#: ../../Zotlabs/Module/Wiki.php:273
-#: ../../Zotlabs/Module/Settings/Oauth.php:149
-#: ../../Zotlabs/Module/Thing.php:260 ../../Zotlabs/Lib/ThreadItem.php:106
-#: ../../Zotlabs/Lib/Apps.php:357
-#: ../../extend/addon/addon/cdav/include/widgets.php:125
-#: ../../extend/addon/addon/cdav/include/widgets.php:161
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:149
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:251
-#: ../../include/menu.php:113 ../../include/channel.php:1044
-#: ../../include/channel.php:1048 ../../include/page_widgets.php:9
-#: ../../include/page_widgets.php:39
-msgid "Edit"
+#: ../../Zotlabs/Module/Cdav.php:1174
+#: ../../Zotlabs/Module/Admin/Accounts.php:169
+#: ../../Zotlabs/Module/Admin/Accounts.php:181
+#: ../../Zotlabs/Module/Connedit.php:928 ../../Zotlabs/Module/Profiles.php:790
+#: ../../addon/openid/MysqlProvider.php:56
+#: ../../addon/openid/MysqlProvider.php:57 ../../addon/rtof/rtof.php:93
+#: ../../addon/redred/redred.php:107 ../../include/network.php:1706
+msgid "Email"
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:239 ../../Zotlabs/Module/Photos.php:1174
-#: ../../Zotlabs/Module/Editblock.php:134
-#: ../../Zotlabs/Module/Connections.php:271
-#: ../../Zotlabs/Module/Admin/Profs.php:155
-#: ../../Zotlabs/Module/Admin/Accounts.php:173
-#: ../../Zotlabs/Module/Admin/Channels.php:149
-#: ../../Zotlabs/Module/Editlayout.php:137
-#: ../../Zotlabs/Module/Editwebpage.php:170
-#: ../../Zotlabs/Module/Connedit.php:634 ../../Zotlabs/Module/Connedit.php:892
-#: ../../Zotlabs/Module/Group.php:177 ../../Zotlabs/Module/Blocks.php:162
-#: ../../Zotlabs/Module/Webpages.php:246
-#: ../../Zotlabs/Module/Settings/Oauth.php:150
-#: ../../Zotlabs/Module/Thing.php:261 ../../Zotlabs/Lib/ThreadItem.php:126
-#: ../../Zotlabs/Lib/Apps.php:358
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:864
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1153
-#: ../../include/conversation.php:656
-msgid "Delete"
+#: ../../Zotlabs/Module/Cdav.php:1175 ../../Zotlabs/Module/Connedit.php:929
+#: ../../Zotlabs/Module/Profiles.php:791
+msgid "Instant messenger"
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:299
-#, php-format
-msgid "You are using %1$s of your available file storage."
+#: ../../Zotlabs/Module/Cdav.php:1176 ../../Zotlabs/Module/Connedit.php:930
+#: ../../Zotlabs/Module/Profiles.php:792
+msgid "Website"
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:304
-#, php-format
-msgid "You are using %1$s of %2$s available file storage. (%3$s&#37;)"
+#: ../../Zotlabs/Module/Cdav.php:1177 ../../Zotlabs/Module/Locs.php:118
+#: ../../Zotlabs/Module/Admin/Channels.php:160
+#: ../../Zotlabs/Module/Connedit.php:931 ../../Zotlabs/Module/Profiles.php:502
+#: ../../Zotlabs/Module/Profiles.php:793
+msgid "Address"
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:315
-msgid "WARNING:"
+#: ../../Zotlabs/Module/Cdav.php:1178 ../../Zotlabs/Module/Connedit.php:932
+#: ../../Zotlabs/Module/Profiles.php:794
+msgid "Note"
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:320
-msgid "Create new folder"
+#: ../../Zotlabs/Module/Cdav.php:1179 ../../Zotlabs/Module/Connedit.php:933
+#: ../../Zotlabs/Module/Profiles.php:795 ../../include/event.php:1290
+#: ../../include/connections.php:682
+msgid "Mobile"
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:322
-msgid "Upload file"
+#: ../../Zotlabs/Module/Cdav.php:1180 ../../Zotlabs/Module/Connedit.php:934
+#: ../../Zotlabs/Module/Profiles.php:796 ../../include/event.php:1291
+#: ../../include/connections.php:683
+msgid "Home"
msgstr ""
-#: ../../Zotlabs/Storage/Browser.php:335
-msgid "Drop files here to immediately upload"
+#: ../../Zotlabs/Module/Cdav.php:1181 ../../Zotlabs/Module/Connedit.php:935
+#: ../../Zotlabs/Module/Profiles.php:797 ../../include/event.php:1294
+#: ../../include/connections.php:686
+msgid "Work"
msgstr ""
-#: ../../Zotlabs/Web/WebServer.php:127 ../../Zotlabs/Module/Like.php:283
-#: ../../Zotlabs/Module/Group.php:72 ../../Zotlabs/Module/Dreport.php:10
-#: ../../Zotlabs/Module/Dreport.php:68
-#: ../../Zotlabs/Module/Import_items.php:114
-#: ../../Zotlabs/Module/Profperm.php:28 ../../Zotlabs/Module/Subthread.php:62
-#: ../../extend/addon/addon/frphotos/frphotos.php:81
-#: ../../extend/addon/addon/redfiles/redfiles.php:109
-#: ../../extend/addon/addon/redphotos/redphotos.php:119
-#: ../../include/items.php:327
-msgid "Permission denied"
+#: ../../Zotlabs/Module/Cdav.php:1183 ../../Zotlabs/Module/Connedit.php:937
+#: ../../Zotlabs/Module/Profiles.php:799
+#: ../../addon/jappixmini/jappixmini.php:368
+msgid "Add Contact"
msgstr ""
-#: ../../Zotlabs/Web/WebServer.php:128 ../../Zotlabs/Web/Router.php:67
-#: ../../Zotlabs/Module/Achievements.php:34
-#: ../../Zotlabs/Module/Register.php:77 ../../Zotlabs/Module/Photos.php:73
-#: ../../Zotlabs/Module/Editpost.php:17 ../../Zotlabs/Module/Authtest.php:16
-#: ../../Zotlabs/Module/Bookmarks.php:61 ../../Zotlabs/Module/Editblock.php:67
-#: ../../Zotlabs/Module/Page.php:35 ../../Zotlabs/Module/Page.php:91
-#: ../../Zotlabs/Module/Connections.php:33
-#: ../../Zotlabs/Module/Cover_photo.php:277
-#: ../../Zotlabs/Module/Cover_photo.php:290
-#: ../../Zotlabs/Module/Editlayout.php:67
-#: ../../Zotlabs/Module/Editlayout.php:90
-#: ../../Zotlabs/Module/Editwebpage.php:68
-#: ../../Zotlabs/Module/Editwebpage.php:89
-#: ../../Zotlabs/Module/Editwebpage.php:104
-#: ../../Zotlabs/Module/Editwebpage.php:126 ../../Zotlabs/Module/Like.php:181
-#: ../../Zotlabs/Module/Network.php:15 ../../Zotlabs/Module/Menu.php:78
-#: ../../Zotlabs/Module/Locs.php:87 ../../Zotlabs/Module/Connedit.php:396
-#: ../../Zotlabs/Module/Filestorage.php:23
-#: ../../Zotlabs/Module/Filestorage.php:78
-#: ../../Zotlabs/Module/Filestorage.php:93
-#: ../../Zotlabs/Module/Filestorage.php:120
-#: ../../Zotlabs/Module/Settings.php:59 ../../Zotlabs/Module/Group.php:13
-#: ../../Zotlabs/Module/Block.php:26 ../../Zotlabs/Module/Block.php:76
-#: ../../Zotlabs/Module/Manage.php:10 ../../Zotlabs/Module/Mitem.php:115
-#: ../../Zotlabs/Module/Appman.php:81 ../../Zotlabs/Module/Mood.php:116
-#: ../../Zotlabs/Module/Profiles.php:198 ../../Zotlabs/Module/Profiles.php:636
-#: ../../Zotlabs/Module/Api.php:24 ../../Zotlabs/Module/Invite.php:17
-#: ../../Zotlabs/Module/Invite.php:94 ../../Zotlabs/Module/New_channel.php:77
-#: ../../Zotlabs/Module/New_channel.php:104 ../../Zotlabs/Module/Setup.php:212
-#: ../../Zotlabs/Module/Notifications.php:11 ../../Zotlabs/Module/Poke.php:137
-#: ../../Zotlabs/Module/Item.php:220 ../../Zotlabs/Module/Item.php:230
-#: ../../Zotlabs/Module/Item.php:1067 ../../Zotlabs/Module/Profile.php:70
-#: ../../Zotlabs/Module/Profile.php:87 ../../Zotlabs/Module/Blocks.php:73
-#: ../../Zotlabs/Module/Blocks.php:80 ../../Zotlabs/Module/Layouts.php:71
-#: ../../Zotlabs/Module/Layouts.php:78 ../../Zotlabs/Module/Layouts.php:89
-#: ../../Zotlabs/Module/Rate.php:113
-#: ../../Zotlabs/Module/Profile_photo.php:273
-#: ../../Zotlabs/Module/Profile_photo.php:286
-#: ../../Zotlabs/Module/Events.php:271 ../../Zotlabs/Module/Common.php:39
-#: ../../Zotlabs/Module/Channel.php:107 ../../Zotlabs/Module/Channel.php:237
-#: ../../Zotlabs/Module/Channel.php:277 ../../Zotlabs/Module/Regmod.php:21
-#: ../../Zotlabs/Module/Pdledit.php:29 ../../Zotlabs/Module/Message.php:18
-#: ../../Zotlabs/Module/Service_limits.php:11
-#: ../../Zotlabs/Module/Webpages.php:116
-#: ../../Zotlabs/Module/Sharedwithme.php:11 ../../Zotlabs/Module/Wiki.php:49
-#: ../../Zotlabs/Module/Wiki.php:214 ../../Zotlabs/Module/Wiki.php:313
-#: ../../Zotlabs/Module/Wiki.php:318 ../../Zotlabs/Module/Sources.php:74
-#: ../../Zotlabs/Module/Suggest.php:30 ../../Zotlabs/Module/Thing.php:274
-#: ../../Zotlabs/Module/Thing.php:294 ../../Zotlabs/Module/Thing.php:335
-#: ../../Zotlabs/Module/Mail.php:164
-#: ../../Zotlabs/Module/Viewconnections.php:28
-#: ../../Zotlabs/Module/Viewconnections.php:33
-#: ../../Zotlabs/Module/Viewsrc.php:18 ../../Zotlabs/Module/Chat.php:100
-#: ../../Zotlabs/Module/Chat.php:105 ../../Zotlabs/Lib/Chatroom.php:137
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:55
-#: ../../extend/addon/addon/keepout/keepout.php:36
-#: ../../extend/addon/addon/pumpio/pumpio.php:40
-#: ../../extend/addon/addon/openid/Mod_Id.php:53
-#: ../../extend/addon/addon/diaspora_reconnect/diaspora_reconnect.php:58
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:194
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:291
-#: ../../include/attach.php:142 ../../include/attach.php:189
-#: ../../include/attach.php:253 ../../include/attach.php:267
-#: ../../include/attach.php:274 ../../include/attach.php:341
-#: ../../include/attach.php:355 ../../include/attach.php:362
-#: ../../include/attach.php:439 ../../include/attach.php:906
-#: ../../include/attach.php:977 ../../include/attach.php:1135
-#: ../../include/photos.php:27 ../../include/items.php:3445
-msgid "Permission denied."
+#: ../../Zotlabs/Module/Cdav.php:1184 ../../Zotlabs/Module/Connedit.php:938
+#: ../../Zotlabs/Module/Profiles.php:800
+msgid "Add Field"
msgstr ""
-#: ../../Zotlabs/Web/Router.php:152 ../../Zotlabs/Module/Display.php:124
-#: ../../Zotlabs/Module/Page.php:94 ../../Zotlabs/Module/Block.php:79
-#: ../../Zotlabs/Lib/NativeWikiPage.php:502 ../../include/help.php:66
-msgid "Page not found."
+#: ../../Zotlabs/Module/Cdav.php:1186
+#: ../../Zotlabs/Module/Admin/Plugins.php:453
+#: ../../Zotlabs/Module/Settings/Oauth.php:42
+#: ../../Zotlabs/Module/Settings/Oauth.php:113
+#: ../../Zotlabs/Module/Connedit.php:940 ../../Zotlabs/Module/Profiles.php:802
+#: ../../Zotlabs/Lib/Apps.php:383
+msgid "Update"
msgstr ""
-#: ../../Zotlabs/Zot/Auth.php:138
-msgid ""
-"Remote authentication blocked. You are logged into this site locally. Please "
-"logout and retry."
+#: ../../Zotlabs/Module/Cdav.php:1189 ../../Zotlabs/Module/Connedit.php:943
+msgid "P.O. Box"
msgstr ""
-#: ../../Zotlabs/Zot/Auth.php:250
-#: ../../extend/addon/addon/openid/Mod_Openid.php:76
-#: ../../extend/addon/addon/openid/Mod_Openid.php:178
-#, php-format
-msgid "Welcome %s. Remote authentication successful."
+#: ../../Zotlabs/Module/Cdav.php:1190 ../../Zotlabs/Module/Connedit.php:944
+msgid "Additional"
msgstr ""
-#: ../../Zotlabs/Module/Achievements.php:15
-#: ../../Zotlabs/Module/Connect.php:17 ../../Zotlabs/Module/Editblock.php:31
-#: ../../Zotlabs/Module/Editlayout.php:31
-#: ../../Zotlabs/Module/Editwebpage.php:32
-#: ../../Zotlabs/Module/Filestorage.php:59 ../../Zotlabs/Module/Hcard.php:12
-#: ../../Zotlabs/Module/Profile.php:20 ../../Zotlabs/Module/Blocks.php:33
-#: ../../Zotlabs/Module/Layouts.php:31 ../../Zotlabs/Module/Webpages.php:33
-#: ../../include/channel.php:945
-msgid "Requested profile is not available."
+#: ../../Zotlabs/Module/Cdav.php:1191 ../../Zotlabs/Module/Connedit.php:945
+msgid "Street"
msgstr ""
-#: ../../Zotlabs/Module/Achievements.php:38
-msgid "Some blurb about what to do when you're new here"
+#: ../../Zotlabs/Module/Cdav.php:1192 ../../Zotlabs/Module/Connedit.php:946
+msgid "Locality"
msgstr ""
-#: ../../Zotlabs/Module/Display.php:17 ../../Zotlabs/Module/Photos.php:508
-#: ../../Zotlabs/Module/Search.php:17 ../../Zotlabs/Module/Ratings.php:83
-#: ../../Zotlabs/Module/Directory.php:64
-#: ../../Zotlabs/Module/Viewconnections.php:23
-#: ../../extend/addon/addon/friendica/dfrn_request.php:794
-msgid "Public access denied."
+#: ../../Zotlabs/Module/Cdav.php:1193 ../../Zotlabs/Module/Connedit.php:947
+msgid "Region"
msgstr ""
-#: ../../Zotlabs/Module/Display.php:38 ../../Zotlabs/Module/Admin.php:60
-#: ../../Zotlabs/Module/Admin/Themes.php:69
-#: ../../Zotlabs/Module/Admin/Plugins.php:254
-#: ../../Zotlabs/Module/Filestorage.php:32 ../../Zotlabs/Module/Thing.php:89
-#: ../../Zotlabs/Module/Viewsrc.php:24 ../../include/items.php:3366
-msgid "Item not found."
+#: ../../Zotlabs/Module/Cdav.php:1194 ../../Zotlabs/Module/Connedit.php:948
+msgid "ZIP Code"
msgstr ""
-#: ../../Zotlabs/Module/Register.php:49
-msgid "Maximum daily site registrations exceeded. Please try again tomorrow."
+#: ../../Zotlabs/Module/Cdav.php:1195 ../../Zotlabs/Module/Connedit.php:949
+#: ../../Zotlabs/Module/Profiles.php:760
+msgid "Country"
msgstr ""
-#: ../../Zotlabs/Module/Register.php:55
-msgid ""
-"Please indicate acceptance of the Terms of Service. Registration failed."
+#: ../../Zotlabs/Module/Cdav.php:1242
+msgid "Default Calendar"
msgstr ""
-#: ../../Zotlabs/Module/Register.php:89
-msgid "Passwords do not match."
+#: ../../Zotlabs/Module/Cdav.php:1252
+msgid "Default Addressbook"
msgstr ""
-#: ../../Zotlabs/Module/Register.php:131
-msgid ""
-"Registration successful. Please check your email for validation instructions."
+#: ../../Zotlabs/Module/Regdir.php:49 ../../Zotlabs/Module/Dirsearch.php:25
+msgid "This site is not a directory server"
msgstr ""
-#: ../../Zotlabs/Module/Register.php:137
-msgid "Your registration is pending approval by the site owner."
+#: ../../Zotlabs/Module/Channel.php:32 ../../Zotlabs/Module/Chat.php:25
+#: ../../addon/gitwiki/Mod_Gitwiki.php:28 ../../addon/chess/chess.php:431
+msgid "You must be logged in to see this page."
msgstr ""
-#: ../../Zotlabs/Module/Register.php:140
-msgid "Your registration can not be processed."
+#: ../../Zotlabs/Module/Channel.php:47 ../../Zotlabs/Module/Hcard.php:37
+#: ../../Zotlabs/Module/Profile.php:45
+msgid "Posts and comments"
msgstr ""
-#: ../../Zotlabs/Module/Register.php:184
-msgid "Registration on this hub is disabled."
+#: ../../Zotlabs/Module/Channel.php:54 ../../Zotlabs/Module/Hcard.php:44
+#: ../../Zotlabs/Module/Profile.php:52
+msgid "Only posts"
msgstr ""
-#: ../../Zotlabs/Module/Register.php:193
-msgid "Registration on this hub is by approval only."
+#: ../../Zotlabs/Module/Channel.php:107
+msgid "Insufficient permissions. Request redirected to profile page."
msgstr ""
-#: ../../Zotlabs/Module/Register.php:194
-msgid "<a href=\"pubsites\">Register at another affiliated hub.</a>"
+#: ../../Zotlabs/Module/Uexport.php:57 ../../Zotlabs/Module/Uexport.php:58
+msgid "Export Channel"
msgstr ""
-#: ../../Zotlabs/Module/Register.php:204
+#: ../../Zotlabs/Module/Uexport.php:59
msgid ""
-"This site has exceeded the number of allowed daily account registrations. "
-"Please try again tomorrow."
+"Export your basic channel information to a file. This acts as a backup of "
+"your connections, permissions, profile and basic data, which can be used to "
+"import your data to a new server hub, but does not contain your content."
msgstr ""
-#: ../../Zotlabs/Module/Register.php:221 ../../Zotlabs/Module/Siteinfo.php:27
-msgid "Terms of Service"
+#: ../../Zotlabs/Module/Uexport.php:60
+msgid "Export Content"
msgstr ""
-#: ../../Zotlabs/Module/Register.php:227
-#, php-format
-msgid "I accept the %s for this website"
+#: ../../Zotlabs/Module/Uexport.php:61
+msgid ""
+"Export your channel information and recent content to a JSON backup that can "
+"be restored or imported to another server hub. This backs up all of your "
+"connections, permissions, profile data and several months of posts. This "
+"file may be VERY large. Please be patient - it may take several minutes for "
+"this download to begin."
msgstr ""
-#: ../../Zotlabs/Module/Register.php:229
-#, php-format
-msgid "I am over 13 years of age and accept the %s for this website"
+#: ../../Zotlabs/Module/Uexport.php:63
+msgid "Export your posts from a given year."
msgstr ""
-#: ../../Zotlabs/Module/Register.php:233
-msgid "Your email address"
+#: ../../Zotlabs/Module/Uexport.php:65
+msgid ""
+"You may also export your posts and conversations for a particular year or "
+"month. Adjust the date in your browser location bar to select other dates. "
+"If the export fails (possibly due to memory exhaustion on your server hub), "
+"please try again selecting a more limited date range."
msgstr ""
-#: ../../Zotlabs/Module/Register.php:234
-msgid "Choose a password"
+#: ../../Zotlabs/Module/Uexport.php:66
+#, php-format
+msgid ""
+"To select all posts for a given year, such as this year, visit <a href=\"%1$s"
+"\">%2$s</a>"
msgstr ""
-#: ../../Zotlabs/Module/Register.php:235
-msgid "Please re-enter your password"
+#: ../../Zotlabs/Module/Uexport.php:67
+#, php-format
+msgid ""
+"To select all posts for a given month, such as January of this year, visit "
+"<a href=\"%1$s\">%2$s</a>"
msgstr ""
-#: ../../Zotlabs/Module/Register.php:236
-msgid "Please enter your invitation code"
+#: ../../Zotlabs/Module/Uexport.php:68
+#, php-format
+msgid ""
+"These content files may be imported or restored by visiting <a href=\"%1$s\">"
+"%2$s</a> on any site containing your channel. For best results please import "
+"or restore these in date order (oldest first)."
msgstr ""
-#: ../../Zotlabs/Module/Register.php:237
-#: ../../Zotlabs/Module/New_channel.php:134
-msgid "Name or caption"
+#: ../../Zotlabs/Module/Search.php:17 ../../Zotlabs/Module/Photos.php:490
+#: ../../Zotlabs/Module/Ratings.php:83 ../../Zotlabs/Module/Directory.php:63
+#: ../../Zotlabs/Module/Display.php:21
+#: ../../Zotlabs/Module/Viewconnections.php:23
+msgid "Public access denied."
msgstr ""
-#: ../../Zotlabs/Module/Register.php:237
-#: ../../Zotlabs/Module/New_channel.php:134
-msgid ""
-"Examples: \"Bob Jameson\", \"Lisa and her Horses\", \"Soccer\", \"Aviation "
-"Group\""
+#: ../../Zotlabs/Module/Search.php:44 ../../Zotlabs/Module/Connections.php:313
+#: ../../Zotlabs/Lib/Apps.php:250 ../../Zotlabs/Widget/Sitesearch.php:31
+#: ../../include/text.php:1029 ../../include/text.php:1041
+#: ../../include/acl_selectors.php:213 ../../include/nav.php:204
+msgid "Search"
msgstr ""
-#: ../../Zotlabs/Module/Register.php:239
-#: ../../Zotlabs/Module/New_channel.php:136
-msgid "Choose a short nickname"
+#: ../../Zotlabs/Module/Search.php:225
+#, php-format
+msgid "Items tagged with: %s"
msgstr ""
-#: ../../Zotlabs/Module/Register.php:239
-#: ../../Zotlabs/Module/New_channel.php:136
+#: ../../Zotlabs/Module/Search.php:227
#, php-format
-msgid ""
-"Your nickname will be used to create an easy to remember channel address e."
-"g. nickname%s"
+msgid "Search results for: %s"
msgstr ""
-#: ../../Zotlabs/Module/Register.php:240
-#: ../../Zotlabs/Module/New_channel.php:137
-msgid "Channel role and privacy"
+#: ../../Zotlabs/Module/Pubstream.php:38
+#: ../../Zotlabs/Widget/Notifications.php:128
+msgid "Public Stream"
msgstr ""
-#: ../../Zotlabs/Module/Register.php:240
-#: ../../Zotlabs/Module/New_channel.php:137
-msgid "Select a channel role with your privacy requirements."
+#: ../../Zotlabs/Module/Locs.php:25 ../../Zotlabs/Module/Locs.php:54
+msgid "Location not found."
msgstr ""
-#: ../../Zotlabs/Module/Register.php:240
-#: ../../Zotlabs/Module/New_channel.php:137
-msgid "Read more about roles"
+#: ../../Zotlabs/Module/Locs.php:62
+msgid "Location lookup failed."
msgstr ""
-#: ../../Zotlabs/Module/Register.php:241
-msgid "no"
+#: ../../Zotlabs/Module/Locs.php:66
+msgid ""
+"Please select another location to become primary before removing the primary "
+"location."
msgstr ""
-#: ../../Zotlabs/Module/Register.php:241
-msgid "yes"
+#: ../../Zotlabs/Module/Locs.php:95
+msgid "Syncing locations"
msgstr ""
-#: ../../Zotlabs/Module/Register.php:253
-#: ../../Zotlabs/Module/Admin/Site.php:261
-msgid "Registration"
+#: ../../Zotlabs/Module/Locs.php:105
+msgid "No locations found."
msgstr ""
-#: ../../Zotlabs/Module/Register.php:258
-msgid "Membership on this site is by invitation only."
+#: ../../Zotlabs/Module/Locs.php:116
+msgid "Manage Channel Locations"
msgstr ""
-#: ../../Zotlabs/Module/Register.php:270 ../../include/nav.php:162
-#: ../../boot.php:1713
-msgid "Register"
+#: ../../Zotlabs/Module/Locs.php:119 ../../Zotlabs/Module/Admin.php:111
+msgid "Primary"
msgstr ""
-#: ../../Zotlabs/Module/Register.php:271
-msgid ""
-"This site may require email verification after submitting this form. If you "
-"are returned to a login page, please check your email for instructions."
+#: ../../Zotlabs/Module/Locs.php:120 ../../Zotlabs/Module/Menu.php:113
+msgid "Drop"
msgstr ""
-#: ../../Zotlabs/Module/Probe.php:28 ../../Zotlabs/Module/Probe.php:32
-#, php-format
-msgid "Fetching URL returns error: %1$s"
+#: ../../Zotlabs/Module/Locs.php:122
+msgid "Sync Now"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:82
-msgid "Page owner information could not be retrieved."
+#: ../../Zotlabs/Module/Locs.php:123
+msgid "Please wait several minutes between consecutive operations."
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:97 ../../Zotlabs/Module/Photos.php:729
-#: ../../Zotlabs/Module/Profile_photo.php:115
-#: ../../Zotlabs/Module/Profile_photo.php:219
-#: ../../include/photo/photo_driver.php:730
-msgid "Profile Photos"
+#: ../../Zotlabs/Module/Locs.php:124
+msgid ""
+"When possible, drop a location by logging into that website/hub and removing "
+"your channel."
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:103 ../../Zotlabs/Module/Photos.php:129
-msgid "Album not found."
+#: ../../Zotlabs/Module/Locs.php:125
+msgid "Use this form to drop the location if the hub is no longer operating."
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:112
-msgid "Delete Album"
+#: ../../Zotlabs/Module/Apporder.php:39
+msgid "Change Order of Navigation Apps"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:133
-msgid ""
-"Multiple storage folders exist with this album name, but within different "
-"directories. Please remove the desired folder or folders using the Files "
-"manager"
+#: ../../Zotlabs/Module/Apporder.php:40
+msgid "Use arrows to move the corresponding app up or down in the display list"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:190 ../../Zotlabs/Module/Photos.php:1054
-msgid "Delete Photo"
+#: ../../Zotlabs/Module/Mitem.php:28 ../../Zotlabs/Module/Menu.php:144
+msgid "Menu not found."
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:519
-msgid "No photos selected"
+#: ../../Zotlabs/Module/Mitem.php:52
+msgid "Unable to create element."
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:568
-msgid "Access to this item is restricted."
+#: ../../Zotlabs/Module/Mitem.php:76
+msgid "Unable to update menu element."
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:607
-#, php-format
-msgid "%1$.2f MB of %2$.2f MB photo storage used."
+#: ../../Zotlabs/Module/Mitem.php:92
+msgid "Unable to add menu element."
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:610
-#, php-format
-msgid "%1$.2f MB photo storage used."
+#: ../../Zotlabs/Module/Mitem.php:120 ../../Zotlabs/Module/Menu.php:166
+#: ../../Zotlabs/Module/Xchan.php:41
+msgid "Not found."
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:646
-msgid "Upload Photos"
+#: ../../Zotlabs/Module/Mitem.php:153 ../../Zotlabs/Module/Mitem.php:230
+msgid "Menu Item Permissions"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:650
-msgid "Enter an album name"
+#: ../../Zotlabs/Module/Mitem.php:154 ../../Zotlabs/Module/Mitem.php:231
+#: ../../Zotlabs/Module/Settings/Channel.php:513
+msgid "(click to open/close)"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:651
-msgid "or select an existing album (doubleclick)"
+#: ../../Zotlabs/Module/Mitem.php:160 ../../Zotlabs/Module/Mitem.php:176
+msgid "Link Name"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:652
-msgid "Create a status post for this upload"
+#: ../../Zotlabs/Module/Mitem.php:161 ../../Zotlabs/Module/Mitem.php:239
+msgid "Link or Submenu Target"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:652 ../../Zotlabs/Module/Admin/Site.php:218
-#: ../../Zotlabs/Module/Menu.php:100 ../../Zotlabs/Module/Menu.php:157
-#: ../../Zotlabs/Module/Connedit.php:410 ../../Zotlabs/Module/Connedit.php:748
-#: ../../Zotlabs/Module/Filestorage.php:160
-#: ../../Zotlabs/Module/Filestorage.php:168 ../../Zotlabs/Module/Mitem.php:162
-#: ../../Zotlabs/Module/Mitem.php:163 ../../Zotlabs/Module/Mitem.php:240
-#: ../../Zotlabs/Module/Mitem.php:241 ../../Zotlabs/Module/Profiles.php:682
-#: ../../Zotlabs/Module/Api.php:97 ../../Zotlabs/Module/Events.php:470
-#: ../../Zotlabs/Module/Events.php:471 ../../Zotlabs/Module/Removeme.php:63
-#: ../../Zotlabs/Module/Wiki.php:178
-#: ../../Zotlabs/Module/Settings/Channel.php:291
+#: ../../Zotlabs/Module/Mitem.php:161
+msgid "Enter URL of the link or select a menu name to create a submenu"
+msgstr ""
+
+#: ../../Zotlabs/Module/Mitem.php:162 ../../Zotlabs/Module/Mitem.php:240
+msgid "Use magic-auth if available"
+msgstr ""
+
+#: ../../Zotlabs/Module/Mitem.php:162 ../../Zotlabs/Module/Mitem.php:163
+#: ../../Zotlabs/Module/Mitem.php:240 ../../Zotlabs/Module/Mitem.php:241
+#: ../../Zotlabs/Module/Events.php:470 ../../Zotlabs/Module/Events.php:471
+#: ../../Zotlabs/Module/Removeme.php:63 ../../Zotlabs/Module/Admin/Site.php:237
+#: ../../Zotlabs/Module/Settings/Channel.php:298
#: ../../Zotlabs/Module/Settings/Display.php:103
-#: ../../extend/addon/addon/dwpost/dwpost.php:73
-#: ../../extend/addon/addon/dwpost/dwpost.php:85
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:120
-#: ../../extend/addon/addon/friendica/dfrn_request.php:865
-#: ../../extend/addon/addon/ijpost/ijpost.php:73
-#: ../../extend/addon/addon/ijpost/ijpost.php:85
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:309
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:313
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:343
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:351
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:355
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:359
-#: ../../extend/addon/addon/libertree/libertree.php:69
-#: ../../extend/addon/addon/libertree/libertree.php:81
-#: ../../extend/addon/addon/ljpost/ljpost.php:70
-#: ../../extend/addon/addon/ljpost/ljpost.php:82
-#: ../../extend/addon/addon/nofed/nofed.php:72
-#: ../../extend/addon/addon/nofed/nofed.php:76
-#: ../../extend/addon/addon/nsabait/nsabait.php:157
-#: ../../extend/addon/addon/nsfw/nsfw.php:84
-#: ../../extend/addon/addon/planets/planets.php:153
-#: ../../extend/addon/addon/pumpio/pumpio.php:219
-#: ../../extend/addon/addon/pumpio/pumpio.php:223
-#: ../../extend/addon/addon/pumpio/pumpio.php:227
-#: ../../extend/addon/addon/pumpio/pumpio.php:231
-#: ../../extend/addon/addon/rainbowtag/rainbowtag.php:81
-#: ../../extend/addon/addon/redred/redred.php:95
-#: ../../extend/addon/addon/redred/redred.php:99
-#: ../../extend/addon/addon/rtof/rtof.php:81
-#: ../../extend/addon/addon/rtof/rtof.php:85
-#: ../../extend/addon/addon/smileybutton/smileybutton.php:273
-#: ../../extend/addon/addon/smileybutton/smileybutton.php:277
-#: ../../extend/addon/addon/statusnet/statusnet.php:389
-#: ../../extend/addon/addon/statusnet/statusnet.php:411
-#: ../../extend/addon/addon/statusnet/statusnet.php:415
-#: ../../extend/addon/addon/statusnet/statusnet.php:424
-#: ../../extend/addon/addon/twitter/twitter.php:242
-#: ../../extend/addon/addon/twitter/twitter.php:246
-#: ../../extend/addon/addon/twitter/twitter.php:255
-#: ../../extend/addon/addon/visage/visage.php:166
-#: ../../extend/addon/addon/wppost/wppost.php:82
-#: ../../extend/addon/addon/wppost/wppost.php:105
-#: ../../extend/addon/addon/wppost/wppost.php:109
-#: ../../extend/addon/addon/xmpp/xmpp.php:53
-#: ../../extend/addon/addon/cdav/cdav.php:234
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:164
+#: ../../Zotlabs/Module/Api.php:97 ../../Zotlabs/Module/Photos.php:644
+#: ../../Zotlabs/Module/Wiki.php:218 ../../Zotlabs/Module/Wiki.php:219
+#: ../../Zotlabs/Module/Connedit.php:396 ../../Zotlabs/Module/Connedit.php:779
+#: ../../Zotlabs/Module/Menu.php:100 ../../Zotlabs/Module/Menu.php:157
+#: ../../Zotlabs/Module/Profiles.php:681
+#: ../../Zotlabs/Module/Filestorage.php:150
+#: ../../Zotlabs/Module/Filestorage.php:158
+#: ../../Zotlabs/Storage/Browser.php:351 ../../boot.php:1644
+#: ../../view/theme/redbasic_c/php/config.php:100
+#: ../../view/theme/redbasic_c/php/config.php:115
+#: ../../view/theme/redbasic/php/config.php:98
+#: ../../addon/planets/planets.php:149 ../../addon/wppost/wppost.php:82
+#: ../../addon/wppost/wppost.php:105 ../../addon/wppost/wppost.php:109
+#: ../../addon/nsfw/nsfw.php:84 ../../addon/ijpost/ijpost.php:73
+#: ../../addon/ijpost/ijpost.php:85 ../../addon/dwpost/dwpost.php:73
+#: ../../addon/dwpost/dwpost.php:85 ../../addon/ljpost/ljpost.php:70
+#: ../../addon/ljpost/ljpost.php:82 ../../addon/gitwiki/Mod_Gitwiki.php:166
+#: ../../addon/rainbowtag/rainbowtag.php:81 ../../addon/visage/visage.php:166
+#: ../../addon/nsabait/nsabait.php:157 ../../addon/rtof/rtof.php:81
+#: ../../addon/rtof/rtof.php:85 ../../addon/jappixmini/jappixmini.php:309
+#: ../../addon/jappixmini/jappixmini.php:313
+#: ../../addon/jappixmini/jappixmini.php:343
+#: ../../addon/jappixmini/jappixmini.php:351
+#: ../../addon/jappixmini/jappixmini.php:355
+#: ../../addon/jappixmini/jappixmini.php:359 ../../addon/nofed/nofed.php:72
+#: ../../addon/nofed/nofed.php:76 ../../addon/redred/redred.php:95
+#: ../../addon/redred/redred.php:99 ../../addon/libertree/libertree.php:69
+#: ../../addon/libertree/libertree.php:81
+#: ../../addon/flattrwidget/flattrwidget.php:120
+#: ../../addon/statusnet/statusnet.php:389
+#: ../../addon/statusnet/statusnet.php:411
+#: ../../addon/statusnet/statusnet.php:415
+#: ../../addon/statusnet/statusnet.php:424 ../../addon/twitter/twitter.php:242
+#: ../../addon/twitter/twitter.php:246 ../../addon/twitter/twitter.php:255
+#: ../../addon/smileybutton/smileybutton.php:211
+#: ../../addon/smileybutton/smileybutton.php:215
+#: ../../addon/authchoose/authchoose.php:67 ../../addon/xmpp/xmpp.php:53
+#: ../../addon/pumpio/pumpio.php:219 ../../addon/pumpio/pumpio.php:223
+#: ../../addon/pumpio/pumpio.php:227 ../../addon/pumpio/pumpio.php:231
#: ../../include/dir_fns.php:143 ../../include/dir_fns.php:144
-#: ../../include/dir_fns.php:145 ../../view/theme/redbasic/php/config.php:111
-#: ../../view/theme/redbasic/php/config.php:136 ../../boot.php:1736
+#: ../../include/dir_fns.php:145
msgid "No"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:652 ../../Zotlabs/Module/Admin/Site.php:220
-#: ../../Zotlabs/Module/Menu.php:100 ../../Zotlabs/Module/Menu.php:157
-#: ../../Zotlabs/Module/Connedit.php:410
-#: ../../Zotlabs/Module/Filestorage.php:160
-#: ../../Zotlabs/Module/Filestorage.php:168 ../../Zotlabs/Module/Mitem.php:162
-#: ../../Zotlabs/Module/Mitem.php:163 ../../Zotlabs/Module/Mitem.php:240
-#: ../../Zotlabs/Module/Mitem.php:241 ../../Zotlabs/Module/Profiles.php:682
-#: ../../Zotlabs/Module/Api.php:96 ../../Zotlabs/Module/Events.php:470
-#: ../../Zotlabs/Module/Events.php:471 ../../Zotlabs/Module/Removeme.php:63
-#: ../../Zotlabs/Module/Wiki.php:178
-#: ../../Zotlabs/Module/Settings/Channel.php:291
+#: ../../Zotlabs/Module/Mitem.php:162 ../../Zotlabs/Module/Mitem.php:163
+#: ../../Zotlabs/Module/Mitem.php:240 ../../Zotlabs/Module/Mitem.php:241
+#: ../../Zotlabs/Module/Events.php:470 ../../Zotlabs/Module/Events.php:471
+#: ../../Zotlabs/Module/Removeme.php:63 ../../Zotlabs/Module/Admin/Site.php:239
+#: ../../Zotlabs/Module/Settings/Channel.php:298
#: ../../Zotlabs/Module/Settings/Display.php:103
-#: ../../extend/addon/addon/dwpost/dwpost.php:73
-#: ../../extend/addon/addon/dwpost/dwpost.php:85
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:120
-#: ../../extend/addon/addon/friendica/dfrn_request.php:865
-#: ../../extend/addon/addon/ijpost/ijpost.php:73
-#: ../../extend/addon/addon/ijpost/ijpost.php:85
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:309
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:313
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:343
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:351
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:355
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:359
-#: ../../extend/addon/addon/libertree/libertree.php:69
-#: ../../extend/addon/addon/libertree/libertree.php:81
-#: ../../extend/addon/addon/ljpost/ljpost.php:70
-#: ../../extend/addon/addon/ljpost/ljpost.php:82
-#: ../../extend/addon/addon/nofed/nofed.php:72
-#: ../../extend/addon/addon/nofed/nofed.php:76
-#: ../../extend/addon/addon/nsabait/nsabait.php:157
-#: ../../extend/addon/addon/nsfw/nsfw.php:84
-#: ../../extend/addon/addon/planets/planets.php:153
-#: ../../extend/addon/addon/pumpio/pumpio.php:219
-#: ../../extend/addon/addon/pumpio/pumpio.php:223
-#: ../../extend/addon/addon/pumpio/pumpio.php:227
-#: ../../extend/addon/addon/pumpio/pumpio.php:231
-#: ../../extend/addon/addon/rainbowtag/rainbowtag.php:81
-#: ../../extend/addon/addon/redred/redred.php:95
-#: ../../extend/addon/addon/redred/redred.php:99
-#: ../../extend/addon/addon/rtof/rtof.php:81
-#: ../../extend/addon/addon/rtof/rtof.php:85
-#: ../../extend/addon/addon/smileybutton/smileybutton.php:273
-#: ../../extend/addon/addon/smileybutton/smileybutton.php:277
-#: ../../extend/addon/addon/statusnet/statusnet.php:389
-#: ../../extend/addon/addon/statusnet/statusnet.php:411
-#: ../../extend/addon/addon/statusnet/statusnet.php:415
-#: ../../extend/addon/addon/statusnet/statusnet.php:424
-#: ../../extend/addon/addon/twitter/twitter.php:242
-#: ../../extend/addon/addon/twitter/twitter.php:246
-#: ../../extend/addon/addon/twitter/twitter.php:255
-#: ../../extend/addon/addon/visage/visage.php:166
-#: ../../extend/addon/addon/wppost/wppost.php:82
-#: ../../extend/addon/addon/wppost/wppost.php:105
-#: ../../extend/addon/addon/wppost/wppost.php:109
-#: ../../extend/addon/addon/xmpp/xmpp.php:53
-#: ../../extend/addon/addon/cdav/cdav.php:234
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:164
+#: ../../Zotlabs/Module/Api.php:96 ../../Zotlabs/Module/Photos.php:644
+#: ../../Zotlabs/Module/Wiki.php:218 ../../Zotlabs/Module/Wiki.php:219
+#: ../../Zotlabs/Module/Connedit.php:396 ../../Zotlabs/Module/Menu.php:100
+#: ../../Zotlabs/Module/Menu.php:157 ../../Zotlabs/Module/Profiles.php:681
+#: ../../Zotlabs/Module/Filestorage.php:150
+#: ../../Zotlabs/Module/Filestorage.php:158
+#: ../../Zotlabs/Storage/Browser.php:351 ../../boot.php:1644
+#: ../../view/theme/redbasic_c/php/config.php:100
+#: ../../view/theme/redbasic_c/php/config.php:115
+#: ../../view/theme/redbasic/php/config.php:98
+#: ../../addon/planets/planets.php:149 ../../addon/wppost/wppost.php:82
+#: ../../addon/wppost/wppost.php:105 ../../addon/wppost/wppost.php:109
+#: ../../addon/nsfw/nsfw.php:84 ../../addon/ijpost/ijpost.php:73
+#: ../../addon/ijpost/ijpost.php:85 ../../addon/dwpost/dwpost.php:73
+#: ../../addon/dwpost/dwpost.php:85 ../../addon/ljpost/ljpost.php:70
+#: ../../addon/ljpost/ljpost.php:82 ../../addon/gitwiki/Mod_Gitwiki.php:166
+#: ../../addon/rainbowtag/rainbowtag.php:81 ../../addon/visage/visage.php:166
+#: ../../addon/nsabait/nsabait.php:157 ../../addon/rtof/rtof.php:81
+#: ../../addon/rtof/rtof.php:85 ../../addon/jappixmini/jappixmini.php:309
+#: ../../addon/jappixmini/jappixmini.php:313
+#: ../../addon/jappixmini/jappixmini.php:343
+#: ../../addon/jappixmini/jappixmini.php:351
+#: ../../addon/jappixmini/jappixmini.php:355
+#: ../../addon/jappixmini/jappixmini.php:359 ../../addon/nofed/nofed.php:72
+#: ../../addon/nofed/nofed.php:76 ../../addon/redred/redred.php:95
+#: ../../addon/redred/redred.php:99 ../../addon/libertree/libertree.php:69
+#: ../../addon/libertree/libertree.php:81
+#: ../../addon/flattrwidget/flattrwidget.php:120
+#: ../../addon/statusnet/statusnet.php:389
+#: ../../addon/statusnet/statusnet.php:411
+#: ../../addon/statusnet/statusnet.php:415
+#: ../../addon/statusnet/statusnet.php:424 ../../addon/twitter/twitter.php:242
+#: ../../addon/twitter/twitter.php:246 ../../addon/twitter/twitter.php:255
+#: ../../addon/smileybutton/smileybutton.php:211
+#: ../../addon/smileybutton/smileybutton.php:215
+#: ../../addon/authchoose/authchoose.php:67 ../../addon/xmpp/xmpp.php:53
+#: ../../addon/pumpio/pumpio.php:219 ../../addon/pumpio/pumpio.php:223
+#: ../../addon/pumpio/pumpio.php:227 ../../addon/pumpio/pumpio.php:231
#: ../../include/dir_fns.php:143 ../../include/dir_fns.php:144
-#: ../../include/dir_fns.php:145 ../../view/theme/redbasic/php/config.php:111
-#: ../../view/theme/redbasic/php/config.php:136 ../../boot.php:1736
+#: ../../include/dir_fns.php:145
msgid "Yes"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:653
-msgid "Caption (optional):"
+#: ../../Zotlabs/Module/Mitem.php:163 ../../Zotlabs/Module/Mitem.php:241
+msgid "Open link in new window"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:654
-msgid "Description (optional):"
+#: ../../Zotlabs/Module/Mitem.php:164 ../../Zotlabs/Module/Mitem.php:242
+msgid "Order in list"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:657 ../../Zotlabs/Module/Photos.php:1042
-#: ../../Zotlabs/Module/Connedit.php:645
-#: ../../Zotlabs/Module/Filestorage.php:152 ../../Zotlabs/Module/Thing.php:313
-#: ../../Zotlabs/Module/Thing.php:363 ../../Zotlabs/Module/Chat.php:234
-#: ../../include/acl_selectors.php:208
-msgid "Permissions"
+#: ../../Zotlabs/Module/Mitem.php:164 ../../Zotlabs/Module/Mitem.php:242
+msgid "Higher numbers will sink to bottom of listing"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:667 ../../Zotlabs/Module/Photos.php:1053
-#: ../../Zotlabs/Module/Photos.php:1093 ../../Zotlabs/Module/Photos.php:1211
-#: ../../Zotlabs/Module/Connect.php:98
-#: ../../Zotlabs/Module/Admin/Features.php:66
-#: ../../Zotlabs/Module/Admin/Logs.php:84
-#: ../../Zotlabs/Module/Admin/Profs.php:157
-#: ../../Zotlabs/Module/Admin/Security.php:104
-#: ../../Zotlabs/Module/Admin/Themes.php:156
-#: ../../Zotlabs/Module/Admin/Account_edit.php:74
-#: ../../Zotlabs/Module/Admin/Accounts.php:166
-#: ../../Zotlabs/Module/Admin/Channels.php:147
-#: ../../Zotlabs/Module/Admin/Site.php:260
-#: ../../Zotlabs/Module/Admin/Plugins.php:433
-#: ../../Zotlabs/Module/Locs.php:121 ../../Zotlabs/Module/Connedit.php:855
-#: ../../Zotlabs/Module/Filestorage.php:165 ../../Zotlabs/Module/Cal.php:342
-#: ../../Zotlabs/Module/Group.php:85 ../../Zotlabs/Module/Import_items.php:122
-#: ../../Zotlabs/Module/Import.php:507 ../../Zotlabs/Module/Mitem.php:243
-#: ../../Zotlabs/Module/Appman.php:133 ../../Zotlabs/Module/Mood.php:139
-#: ../../Zotlabs/Module/Profiles.php:722 ../../Zotlabs/Module/Invite.php:149
-#: ../../Zotlabs/Module/Setup.php:309 ../../Zotlabs/Module/Setup.php:357
-#: ../../Zotlabs/Module/Poke.php:186 ../../Zotlabs/Module/Pconfig.php:107
-#: ../../Zotlabs/Module/Rate.php:166 ../../Zotlabs/Module/Events.php:493
-#: ../../Zotlabs/Module/Pdledit.php:74 ../../Zotlabs/Module/Wiki.php:167
-#: ../../Zotlabs/Module/Sources.php:114 ../../Zotlabs/Module/Sources.php:149
-#: ../../Zotlabs/Module/Settings/Features.php:47
-#: ../../Zotlabs/Module/Settings/Oauth.php:87
-#: ../../Zotlabs/Module/Settings/Account.php:118
-#: ../../Zotlabs/Module/Settings/Tokens.php:168
-#: ../../Zotlabs/Module/Settings/Featured.php:50
-#: ../../Zotlabs/Module/Settings/Channel.php:460
-#: ../../Zotlabs/Module/Settings/Display.php:196
-#: ../../Zotlabs/Module/Settings/Permcats.php:112
-#: ../../Zotlabs/Module/Thing.php:320 ../../Zotlabs/Module/Thing.php:370
-#: ../../Zotlabs/Module/Mail.php:413 ../../Zotlabs/Module/Chat.php:196
-#: ../../Zotlabs/Module/Chat.php:241 ../../Zotlabs/Module/Xchan.php:15
-#: ../../Zotlabs/Lib/ThreadItem.php:731
-#: ../../extend/addon/addon/chords/Mod_Chords.php:60
-#: ../../extend/addon/addon/diaspora/diaspora.php:714
-#: ../../extend/addon/addon/dwpost/dwpost.php:89
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:124
-#: ../../extend/addon/addon/friendica/friendica.php:128
-#: ../../extend/addon/addon/frphotos/frphotos.php:96
-#: ../../extend/addon/addon/hubwall/hubwall.php:95
-#: ../../extend/addon/addon/ijpost/ijpost.php:89
-#: ../../extend/addon/addon/irc/irc.php:53
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:371
-#: ../../extend/addon/addon/libertree/libertree.php:85
-#: ../../extend/addon/addon/ljpost/ljpost.php:86
-#: ../../extend/addon/addon/logrot/logrot.php:35
-#: ../../extend/addon/addon/mailhost/mailhost.php:40
-#: ../../extend/addon/addon/nofed/nofed.php:80
-#: ../../extend/addon/addon/nsabait/nsabait.php:161
-#: ../../extend/addon/addon/nsfw/nsfw.php:92
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:53
-#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:168
-#: ../../extend/addon/addon/pageheader/pageheader.php:48
-#: ../../extend/addon/addon/piwik/piwik.php:95
-#: ../../extend/addon/addon/planets/planets.php:157
-#: ../../extend/addon/addon/pumpio/pumpio.php:237
-#: ../../extend/addon/addon/rainbowtag/rainbowtag.php:85
-#: ../../extend/addon/addon/redfiles/redfiles.php:124
-#: ../../extend/addon/addon/redphotos/redphotos.php:136
-#: ../../extend/addon/addon/redred/redred.php:119
-#: ../../extend/addon/addon/rtof/rtof.php:101
-#: ../../extend/addon/addon/skeleton/skeleton.php:65
-#: ../../extend/addon/addon/smileybutton/smileybutton.php:281
-#: ../../extend/addon/addon/startpage/startpage.php:113
-#: ../../extend/addon/addon/statusnet/statusnet.php:322
-#: ../../extend/addon/addon/statusnet/statusnet.php:380
-#: ../../extend/addon/addon/statusnet/statusnet.php:432
-#: ../../extend/addon/addon/statusnet/statusnet.php:899
-#: ../../extend/addon/addon/superblock/superblock.php:118
-#: ../../extend/addon/addon/twitter/twitter.php:217
-#: ../../extend/addon/addon/twitter/twitter.php:259
-#: ../../extend/addon/addon/visage/visage.php:170
-#: ../../extend/addon/addon/wppost/wppost.php:113
-#: ../../extend/addon/addon/xmpp/xmpp.php:69
-#: ../../extend/addon/addon/cdav/cdav.php:246
-#: ../../extend/addon/addon/likebanner/likebanner.php:57
-#: ../../extend/addon/addon/mailtest/mailtest.php:100
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:153
-#: ../../extend/addon/addon/gnusoc/gnusoc.php:133
-#: ../../include/widgets.php:815 ../../include/js_strings.php:22
-#: ../../view/theme/redbasic/php/config.php:106
-msgid "Submit"
+#: ../../Zotlabs/Module/Mitem.php:165
+msgid "Submit and finish"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:685
-msgid "Album name could not be decoded"
+#: ../../Zotlabs/Module/Mitem.php:166
+msgid "Submit and continue"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:729
-msgid "Contact Photos"
+#: ../../Zotlabs/Module/Mitem.php:174
+msgid "Menu:"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:752
-msgid "Show Newest First"
+#: ../../Zotlabs/Module/Mitem.php:177
+msgid "Link Target"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:754
-msgid "Show Oldest First"
+#: ../../Zotlabs/Module/Mitem.php:180
+msgid "Edit menu"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:778 ../../Zotlabs/Module/Photos.php:1335
-#: ../../Zotlabs/Module/Embedphotos.php:139 ../../include/widgets.php:1708
-msgid "View Photo"
+#: ../../Zotlabs/Module/Mitem.php:183
+msgid "Edit element"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:809
-#: ../../Zotlabs/Module/Embedphotos.php:155 ../../include/widgets.php:1725
-msgid "Edit Album"
+#: ../../Zotlabs/Module/Mitem.php:184
+msgid "Drop element"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:856
-msgid "Permission denied. Access to this item may be restricted."
+#: ../../Zotlabs/Module/Mitem.php:185
+msgid "New element"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:858
-msgid "Photo not available"
+#: ../../Zotlabs/Module/Mitem.php:186
+msgid "Edit this menu container"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:916
-msgid "Use as profile photo"
+#: ../../Zotlabs/Module/Mitem.php:187
+msgid "Add menu element"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:917
-msgid "Use as cover photo"
+#: ../../Zotlabs/Module/Mitem.php:188
+msgid "Delete this menu item"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:924
-msgid "Private Photo"
+#: ../../Zotlabs/Module/Mitem.php:189
+msgid "Edit this menu item"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:935 ../../Zotlabs/Module/Cal.php:336
-#: ../../Zotlabs/Module/Cal.php:343 ../../Zotlabs/Module/Events.php:689
-#: ../../Zotlabs/Module/Events.php:698
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:846
-msgid "Previous"
+#: ../../Zotlabs/Module/Mitem.php:206
+msgid "Menu item not found."
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:939
-msgid "View Full Size"
+#: ../../Zotlabs/Module/Mitem.php:219
+msgid "Menu item deleted."
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:944 ../../Zotlabs/Module/Cal.php:337
-#: ../../Zotlabs/Module/Cal.php:344 ../../Zotlabs/Module/Setup.php:264
-#: ../../Zotlabs/Module/Events.php:690 ../../Zotlabs/Module/Events.php:699
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:847
-msgid "Next"
+#: ../../Zotlabs/Module/Mitem.php:221
+msgid "Menu item could not be deleted."
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:984
-#: ../../Zotlabs/Module/Admin/Plugins.php:450
-#: ../../Zotlabs/Module/Tagrm.php:137
-#: ../../extend/addon/addon/superblock/superblock.php:114
-msgid "Remove"
+#: ../../Zotlabs/Module/Mitem.php:228
+msgid "Edit Menu Element"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1028
-msgid "Edit photo"
+#: ../../Zotlabs/Module/Mitem.php:238
+msgid "Link text"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1030
-msgid "Rotate CW (right)"
+#: ../../Zotlabs/Module/Events.php:25
+msgid "Calendar entries imported."
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1031
-msgid "Rotate CCW (left)"
+#: ../../Zotlabs/Module/Events.php:27
+msgid "No calendar entries found."
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1034
-msgid "Move photo to album"
+#: ../../Zotlabs/Module/Events.php:110
+msgid "Event can not end before it has started."
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1035
-msgid "Enter a new album name"
+#: ../../Zotlabs/Module/Events.php:112 ../../Zotlabs/Module/Events.php:121
+#: ../../Zotlabs/Module/Events.php:143
+msgid "Unable to generate preview."
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1036
-msgid "or select an existing one (doubleclick)"
+#: ../../Zotlabs/Module/Events.php:119
+msgid "Event title and start time are required."
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1039
-msgid "Caption"
+#: ../../Zotlabs/Module/Events.php:141 ../../Zotlabs/Module/Events.php:265
+msgid "Event not found."
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1041
-msgid "Add a Tag"
+#: ../../Zotlabs/Module/Events.php:260 ../../Zotlabs/Module/Tagger.php:51
+#: ../../Zotlabs/Module/Like.php:372 ../../include/conversation.php:119
+#: ../../include/text.php:1941 ../../include/event.php:1145
+msgid "event"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1049
-msgid "Example: @bob, @Barbara_Jensen, @jim@example.com"
+#: ../../Zotlabs/Module/Events.php:460
+msgid "Edit event title"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1052
-msgid "Flag as adult in album view"
+#: ../../Zotlabs/Module/Events.php:460 ../../Zotlabs/Module/Events.php:465
+#: ../../Zotlabs/Module/Appman.php:136 ../../Zotlabs/Module/Appman.php:137
+#: ../../Zotlabs/Module/Profiles.php:748 ../../Zotlabs/Module/Profiles.php:752
+#: ../../include/datetime.php:259
+msgid "Required"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1071 ../../Zotlabs/Lib/ThreadItem.php:268
-msgid "I like this (toggle)"
+#: ../../Zotlabs/Module/Events.php:462
+msgid "Categories (comma-separated list)"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1072 ../../Zotlabs/Lib/ThreadItem.php:269
-msgid "I don't like this (toggle)"
+#: ../../Zotlabs/Module/Events.php:463
+msgid "Edit Category"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1073 ../../Zotlabs/Module/Blocks.php:161
-#: ../../Zotlabs/Module/Layouts.php:193 ../../Zotlabs/Module/Webpages.php:245
-#: ../../extend/addon/addon/cdav/include/widgets.php:123
-#: ../../include/conversation.php:1378
-msgid "Share"
+#: ../../Zotlabs/Module/Events.php:463
+msgid "Category"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1074 ../../Zotlabs/Lib/ThreadItem.php:411
-#: ../../include/conversation.php:738
-msgid "Please wait"
+#: ../../Zotlabs/Module/Events.php:466
+msgid "Edit start date and time"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1090 ../../Zotlabs/Module/Photos.php:1208
-#: ../../Zotlabs/Lib/ThreadItem.php:728
-msgid "This is you"
+#: ../../Zotlabs/Module/Events.php:467 ../../Zotlabs/Module/Events.php:470
+msgid "Finish date and time are not known or not relevant"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1092 ../../Zotlabs/Module/Photos.php:1210
-#: ../../Zotlabs/Lib/ThreadItem.php:730 ../../include/js_strings.php:6
-msgid "Comment"
+#: ../../Zotlabs/Module/Events.php:469
+msgid "Edit finish date and time"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1094 ../../Zotlabs/Module/Events.php:478
-#: ../../Zotlabs/Module/Webpages.php:251 ../../Zotlabs/Lib/ThreadItem.php:740
-#: ../../include/conversation.php:1347 ../../include/page_widgets.php:43
-msgid "Preview"
+#: ../../Zotlabs/Module/Events.php:469
+msgid "Finish date and time"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1108 ../../include/conversation.php:577
-msgctxt "title"
-msgid "Likes"
+#: ../../Zotlabs/Module/Events.php:471 ../../Zotlabs/Module/Events.php:472
+msgid "Adjust for viewer timezone"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1108 ../../include/conversation.php:577
-msgctxt "title"
-msgid "Dislikes"
+#: ../../Zotlabs/Module/Events.php:471
+msgid ""
+"Important for events that happen in a particular place. Not practical for "
+"global holidays."
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1109 ../../include/conversation.php:578
-msgctxt "title"
-msgid "Agree"
+#: ../../Zotlabs/Module/Events.php:473
+msgid "Edit Description"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1109 ../../include/conversation.php:578
-msgctxt "title"
-msgid "Disagree"
+#: ../../Zotlabs/Module/Events.php:475
+msgid "Edit Location"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1109 ../../include/conversation.php:578
-msgctxt "title"
-msgid "Abstain"
+#: ../../Zotlabs/Module/Events.php:478 ../../Zotlabs/Module/Photos.php:1070
+#: ../../Zotlabs/Module/Webpages.php:247 ../../Zotlabs/Lib/ThreadItem.php:753
+#: ../../include/conversation.php:1313
+msgid "Preview"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1110 ../../include/conversation.php:579
-msgctxt "title"
-msgid "Attending"
+#: ../../Zotlabs/Module/Events.php:479 ../../include/conversation.php:1385
+msgid "Permission settings"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1110 ../../include/conversation.php:579
-msgctxt "title"
-msgid "Not attending"
+#: ../../Zotlabs/Module/Events.php:489
+msgid "Timezone:"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1110 ../../include/conversation.php:579
-msgctxt "title"
-msgid "Might attend"
+#: ../../Zotlabs/Module/Events.php:494
+msgid "Advanced Options"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1127 ../../Zotlabs/Module/Photos.php:1139
-#: ../../Zotlabs/Lib/ThreadItem.php:186 ../../Zotlabs/Lib/ThreadItem.php:198
-#: ../../include/conversation.php:1928
-msgid "View all"
+#: ../../Zotlabs/Module/Events.php:605 ../../Zotlabs/Module/Cal.php:264
+msgid "l, F j"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1131 ../../Zotlabs/Lib/ThreadItem.php:190
-#: ../../include/taxonomy.php:403 ../../include/conversation.php:1952
-#: ../../include/channel.php:1273
-msgctxt "noun"
-msgid "Like"
-msgid_plural "Likes"
-msgstr[0] ""
-msgstr[1] ""
+#: ../../Zotlabs/Module/Events.php:633
+msgid "Edit event"
+msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1136 ../../Zotlabs/Lib/ThreadItem.php:195
-#: ../../include/conversation.php:1955
-msgctxt "noun"
-msgid "Dislike"
-msgid_plural "Dislikes"
-msgstr[0] ""
-msgstr[1] ""
+#: ../../Zotlabs/Module/Events.php:635
+msgid "Delete event"
+msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1236
-msgid "Photo Tools"
+#: ../../Zotlabs/Module/Events.php:660 ../../Zotlabs/Module/Cal.php:313
+#: ../../include/text.php:1760
+msgid "Link to Source"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1245
-msgid "In This Photo:"
+#: ../../Zotlabs/Module/Events.php:669
+msgid "calendar"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1250
-msgid "Map"
+#: ../../Zotlabs/Module/Events.php:688 ../../Zotlabs/Module/Cal.php:336
+msgid "Edit Event"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1258 ../../Zotlabs/Lib/ThreadItem.php:400
-msgctxt "noun"
-msgid "Likes"
+#: ../../Zotlabs/Module/Events.php:688 ../../Zotlabs/Module/Cal.php:336
+msgid "Create Event"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1259 ../../Zotlabs/Lib/ThreadItem.php:401
-msgctxt "noun"
-msgid "Dislikes"
+#: ../../Zotlabs/Module/Events.php:691 ../../Zotlabs/Module/Cal.php:339
+#: ../../include/channel.php:1588
+msgid "Export"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1264 ../../Zotlabs/Lib/ThreadItem.php:406
-#: ../../include/acl_selectors.php:210
-msgid "Close"
+#: ../../Zotlabs/Module/Events.php:731
+msgid "Event removed"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1341
-msgid "View Album"
+#: ../../Zotlabs/Module/Events.php:734
+msgid "Failed to remove event"
msgstr ""
-#: ../../Zotlabs/Module/Photos.php:1352 ../../Zotlabs/Module/Photos.php:1365
-#: ../../Zotlabs/Module/Photos.php:1366
-msgid "Recent Photos"
+#: ../../Zotlabs/Module/Appman.php:38 ../../Zotlabs/Module/Appman.php:55
+msgid "App installed."
msgstr ""
-#: ../../Zotlabs/Module/Editpost.php:24 ../../Zotlabs/Module/Editblock.php:79
-#: ../../Zotlabs/Module/Editblock.php:95
-#: ../../Zotlabs/Module/Editlayout.php:79
-#: ../../Zotlabs/Module/Editwebpage.php:80
-msgid "Item not found"
+#: ../../Zotlabs/Module/Appman.php:48
+msgid "Malformed app."
msgstr ""
-#: ../../Zotlabs/Module/Editpost.php:35
-msgid "Item is not editable"
+#: ../../Zotlabs/Module/Appman.php:125
+msgid "Embed code"
msgstr ""
-#: ../../Zotlabs/Module/Editpost.php:108 ../../Zotlabs/Module/Rpost.php:138
-msgid "Edit post"
+#: ../../Zotlabs/Module/Appman.php:131
+msgid "Edit App"
msgstr ""
-#: ../../Zotlabs/Module/Acl.php:313
-msgid "network"
+#: ../../Zotlabs/Module/Appman.php:131
+msgid "Create App"
msgstr ""
-#: ../../Zotlabs/Module/Acl.php:323
-msgid "RSS"
+#: ../../Zotlabs/Module/Appman.php:136
+msgid "Name of app"
msgstr ""
-#: ../../Zotlabs/Module/Help.php:23
-msgid "Documentation Search"
+#: ../../Zotlabs/Module/Appman.php:137
+msgid "Location (URL) of app"
msgstr ""
-#: ../../Zotlabs/Module/Help.php:80 ../../include/conversation.php:1827
-msgid "About"
+#: ../../Zotlabs/Module/Appman.php:139
+msgid "Photo icon URL"
msgstr ""
-#: ../../Zotlabs/Module/Help.php:81 ../../Zotlabs/Module/Group.php:197
-msgid "Members"
+#: ../../Zotlabs/Module/Appman.php:139
+msgid "80 x 80 pixels - optional"
msgstr ""
-#: ../../Zotlabs/Module/Help.php:82
-msgid "Administrators"
+#: ../../Zotlabs/Module/Appman.php:140
+msgid "Categories (optional, comma separated list)"
msgstr ""
-#: ../../Zotlabs/Module/Help.php:83
-msgid "Developers"
+#: ../../Zotlabs/Module/Appman.php:141
+msgid "Version ID"
msgstr ""
-#: ../../Zotlabs/Module/Help.php:84
-msgid "Tutorials"
+#: ../../Zotlabs/Module/Appman.php:142
+msgid "Price of app"
msgstr ""
-#: ../../Zotlabs/Module/Help.php:93
-msgid "$Projectname Documentation"
+#: ../../Zotlabs/Module/Appman.php:143
+msgid "Location (URL) to purchase app"
msgstr ""
-#: ../../Zotlabs/Module/Help.php:94
-msgid "Contents"
+#: ../../Zotlabs/Module/Regmod.php:15
+msgid "Please login."
msgstr ""
-#: ../../Zotlabs/Module/Bookmarks.php:53
-msgid "Bookmark added"
+#: ../../Zotlabs/Module/Magic.php:72
+msgid "Hub not found."
msgstr ""
-#: ../../Zotlabs/Module/Bookmarks.php:75
-msgid "My Bookmarks"
+#: ../../Zotlabs/Module/Subthread.php:87 ../../Zotlabs/Module/Tagger.php:47
+#: ../../Zotlabs/Module/Like.php:370
+#: ../../addon/redphotos/redphotohelper.php:71
+#: ../../addon/diaspora/Receiver.php:1424 ../../addon/pubcrawl/as.php:1288
+#: ../../include/conversation.php:116 ../../include/text.php:1938
+msgid "photo"
msgstr ""
-#: ../../Zotlabs/Module/Bookmarks.php:86
-msgid "My Connections Bookmarks"
+#: ../../Zotlabs/Module/Subthread.php:87 ../../Zotlabs/Module/Like.php:370
+#: ../../addon/diaspora/Receiver.php:1424 ../../addon/pubcrawl/as.php:1288
+#: ../../include/conversation.php:144 ../../include/text.php:1944
+msgid "status"
msgstr ""
-#: ../../Zotlabs/Module/Connect.php:61 ../../Zotlabs/Module/Connect.php:109
-msgid "Continue"
+#: ../../Zotlabs/Module/Subthread.php:118
+#, php-format
+msgid "%1$s is following %2$s's %3$s"
msgstr ""
-#: ../../Zotlabs/Module/Connect.php:90
-msgid "Premium Channel Setup"
+#: ../../Zotlabs/Module/Subthread.php:120
+#, php-format
+msgid "%1$s stopped following %2$s's %3$s"
msgstr ""
-#: ../../Zotlabs/Module/Connect.php:92
-msgid "Enable premium channel connection restrictions"
+#: ../../Zotlabs/Module/Import_items.php:48 ../../Zotlabs/Module/Import.php:64
+msgid "Nothing to import."
msgstr ""
-#: ../../Zotlabs/Module/Connect.php:93
-msgid ""
-"Please enter your restrictions or conditions, such as paypal receipt, usage "
-"guidelines, etc."
+#: ../../Zotlabs/Module/Import_items.php:72 ../../Zotlabs/Module/Import.php:79
+#: ../../Zotlabs/Module/Import.php:95
+msgid "Unable to download data from old server"
msgstr ""
-#: ../../Zotlabs/Module/Connect.php:95 ../../Zotlabs/Module/Connect.php:115
-msgid ""
-"This channel may require additional steps or acknowledgement of the "
-"following conditions prior to connecting:"
+#: ../../Zotlabs/Module/Import_items.php:77 ../../Zotlabs/Module/Import.php:102
+msgid "Imported file is empty."
msgstr ""
-#: ../../Zotlabs/Module/Connect.php:96
-msgid ""
-"Potential connections will then see the following text before proceeding:"
+#: ../../Zotlabs/Module/Import_items.php:93 ../../Zotlabs/Module/Import.php:121
+#, php-format
+msgid "Warning: Database versions differ by %1$d updates."
msgstr ""
-#: ../../Zotlabs/Module/Connect.php:97 ../../Zotlabs/Module/Connect.php:118
-msgid ""
-"By continuing, I certify that I have complied with any instructions provided "
-"on this page."
+#: ../../Zotlabs/Module/Import_items.php:108
+msgid "Import completed"
msgstr ""
-#: ../../Zotlabs/Module/Connect.php:106
-msgid "(No specific instructions have been provided by the channel owner.)"
+#: ../../Zotlabs/Module/Import_items.php:125
+msgid "Import Items"
msgstr ""
-#: ../../Zotlabs/Module/Connect.php:114
-msgid "Restricted or Premium Channel"
+#: ../../Zotlabs/Module/Import_items.php:126
+msgid "Use this form to import existing posts and content from an export file."
msgstr ""
-#: ../../Zotlabs/Module/Admin.php:94
-msgid "# Accounts"
+#: ../../Zotlabs/Module/Import_items.php:127
+#: ../../Zotlabs/Module/Import.php:516
+msgid "File to Upload"
msgstr ""
-#: ../../Zotlabs/Module/Admin.php:95
-msgid "# blocked accounts"
+#: ../../Zotlabs/Module/New_channel.php:121 ../../Zotlabs/Module/Manage.php:138
+#, php-format
+msgid "You have created %1$.0f of %2$.0f allowed channels."
msgstr ""
-#: ../../Zotlabs/Module/Admin.php:96
-msgid "# expired accounts"
+#: ../../Zotlabs/Module/New_channel.php:134
+#: ../../Zotlabs/Module/Register.php:237
+msgid "Name or caption"
msgstr ""
-#: ../../Zotlabs/Module/Admin.php:97
-msgid "# expiring accounts"
+#: ../../Zotlabs/Module/New_channel.php:134
+#: ../../Zotlabs/Module/Register.php:237
+msgid ""
+"Examples: \"Bob Jameson\", \"Lisa and her Horses\", \"Soccer\", \"Aviation "
+"Group\""
msgstr ""
-#: ../../Zotlabs/Module/Admin.php:108
-msgid "# Channels"
+#: ../../Zotlabs/Module/New_channel.php:136
+#: ../../Zotlabs/Module/Register.php:239
+msgid "Choose a short nickname"
msgstr ""
-#: ../../Zotlabs/Module/Admin.php:109
-msgid "# primary"
+#: ../../Zotlabs/Module/New_channel.php:136
+#: ../../Zotlabs/Module/Register.php:239
+#, php-format
+msgid ""
+"Your nickname will be used to create an easy to remember channel address e."
+"g. nickname%s"
msgstr ""
-#: ../../Zotlabs/Module/Admin.php:110
-msgid "# clones"
+#: ../../Zotlabs/Module/New_channel.php:137
+#: ../../Zotlabs/Module/Register.php:240
+msgid "Channel role and privacy"
msgstr ""
-#: ../../Zotlabs/Module/Admin.php:116
-msgid "Message queues"
+#: ../../Zotlabs/Module/New_channel.php:137
+#: ../../Zotlabs/Module/Register.php:240
+msgid "Select a channel role with your privacy requirements."
msgstr ""
-#: ../../Zotlabs/Module/Admin.php:133
-msgid "Your software should be updated"
+#: ../../Zotlabs/Module/New_channel.php:137
+#: ../../Zotlabs/Module/Register.php:240
+msgid "Read more about roles"
msgstr ""
-#: ../../Zotlabs/Module/Admin.php:137 ../../Zotlabs/Module/Admin/Logs.php:82
-#: ../../Zotlabs/Module/Admin/Security.php:86
-#: ../../Zotlabs/Module/Admin/Themes.php:120
-#: ../../Zotlabs/Module/Admin/Themes.php:154
-#: ../../Zotlabs/Module/Admin/Accounts.php:164
-#: ../../Zotlabs/Module/Admin/Channels.php:145
-#: ../../Zotlabs/Module/Admin/Site.php:258
-#: ../../Zotlabs/Module/Admin/Plugins.php:336
-#: ../../Zotlabs/Module/Admin/Plugins.php:431
-msgid "Administration"
+#: ../../Zotlabs/Module/New_channel.php:140
+msgid "Create Channel"
msgstr ""
-#: ../../Zotlabs/Module/Admin.php:138
-msgid "Summary"
+#: ../../Zotlabs/Module/New_channel.php:141
+msgid ""
+"A channel is your identity on this network. It can represent a person, a "
+"blog, or a forum to name a few. Channels can make connections with other "
+"channels to share information with highly detailed permissions."
msgstr ""
-#: ../../Zotlabs/Module/Admin.php:141
-msgid "Registered accounts"
+#: ../../Zotlabs/Module/New_channel.php:142
+msgid ""
+"or <a href=\"import\">import an existing channel</a> from another location."
msgstr ""
-#: ../../Zotlabs/Module/Admin.php:142
-msgid "Pending registrations"
+#: ../../Zotlabs/Module/Removeme.php:35
+msgid ""
+"Channel removals are not allowed within 48 hours of changing the account "
+"password."
msgstr ""
-#: ../../Zotlabs/Module/Admin.php:143
-msgid "Registered channels"
+#: ../../Zotlabs/Module/Removeme.php:60
+msgid "Remove This Channel"
msgstr ""
-#: ../../Zotlabs/Module/Admin.php:144
-msgid "Active plugins"
+#: ../../Zotlabs/Module/Removeme.php:61
+#: ../../Zotlabs/Module/Removeaccount.php:58
+#: ../../Zotlabs/Module/Changeaddr.php:78
+msgid "WARNING: "
msgstr ""
-#: ../../Zotlabs/Module/Admin.php:145
-msgid "Version"
+#: ../../Zotlabs/Module/Removeme.php:61
+msgid "This channel will be completely removed from the network. "
msgstr ""
-#: ../../Zotlabs/Module/Admin.php:146
-msgid "Repository version (master)"
+#: ../../Zotlabs/Module/Removeme.php:61
+#: ../../Zotlabs/Module/Removeaccount.php:58
+msgid "This action is permanent and can not be undone!"
msgstr ""
-#: ../../Zotlabs/Module/Admin.php:147
-msgid "Repository version (dev)"
+#: ../../Zotlabs/Module/Removeme.php:62
+#: ../../Zotlabs/Module/Removeaccount.php:59
+#: ../../Zotlabs/Module/Changeaddr.php:79
+msgid "Please enter your password for verification:"
msgstr ""
-#: ../../Zotlabs/Module/Editblock.php:108 ../../Zotlabs/Module/Blocks.php:97
-#: ../../Zotlabs/Module/Blocks.php:155
-msgid "Block Name"
+#: ../../Zotlabs/Module/Removeme.php:63
+msgid "Remove this channel and all its clones from the network"
msgstr ""
-#: ../../Zotlabs/Module/Editblock.php:111
-#: ../../Zotlabs/Module/Editwebpage.php:146 ../../Zotlabs/Module/Mail.php:287
-#: ../../Zotlabs/Module/Mail.php:412 ../../Zotlabs/Module/Chat.php:207
-#: ../../include/conversation.php:1295
-msgid "Insert web link"
+#: ../../Zotlabs/Module/Removeme.php:63
+msgid ""
+"By default only the instance of the channel located on this hub will be "
+"removed from the network"
msgstr ""
-#: ../../Zotlabs/Module/Editblock.php:124 ../../include/conversation.php:1406
-msgid "Title (optional)"
+#: ../../Zotlabs/Module/Removeme.php:64
+#: ../../Zotlabs/Module/Settings/Channel.php:580
+msgid "Remove Channel"
msgstr ""
-#: ../../Zotlabs/Module/Editblock.php:133
-msgid "Edit Block"
+#: ../../Zotlabs/Module/Sharedwithme.php:104
+msgid "Files: shared with me"
msgstr ""
-#: ../../Zotlabs/Module/Page.php:40 ../../Zotlabs/Module/Block.php:31
-msgid "Invalid item."
+#: ../../Zotlabs/Module/Sharedwithme.php:106
+msgid "NEW"
msgstr ""
-#: ../../Zotlabs/Module/Page.php:56 ../../Zotlabs/Module/Cal.php:62
-#: ../../Zotlabs/Module/Block.php:43 ../../Zotlabs/Module/Chanview.php:96
-#: ../../Zotlabs/Module/Wall_upload.php:31
-msgid "Channel not found."
+#: ../../Zotlabs/Module/Sharedwithme.php:107
+#: ../../Zotlabs/Storage/Browser.php:236 ../../include/text.php:1394
+msgid "Size"
msgstr ""
-#: ../../Zotlabs/Module/Page.php:131
-msgid ""
-"Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod "
-"tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, "
-"quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo "
-"consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse "
-"cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat "
-"non proident, sunt in culpa qui officia deserunt mollit anim id est laborum."
+#: ../../Zotlabs/Module/Sharedwithme.php:108
+#: ../../Zotlabs/Storage/Browser.php:237
+msgid "Last Modified"
msgstr ""
-#: ../../Zotlabs/Module/Filer.php:52
-msgid "Save to Folder:"
+#: ../../Zotlabs/Module/Sharedwithme.php:109
+msgid "Remove all files"
msgstr ""
-#: ../../Zotlabs/Module/Filer.php:52
-msgid "- select -"
+#: ../../Zotlabs/Module/Sharedwithme.php:110
+msgid "Remove this file"
msgstr ""
-#: ../../Zotlabs/Module/Filer.php:53 ../../Zotlabs/Module/Admin/Profs.php:74
-#: ../../Zotlabs/Module/Admin/Profs.php:94 ../../Zotlabs/Module/Rbmark.php:32
-#: ../../Zotlabs/Module/Rbmark.php:104 ../../include/widgets.php:202
-#: ../../include/text.php:1003 ../../include/text.php:1015
-msgid "Save"
+#: ../../Zotlabs/Module/Setup.php:170
+msgid "$Projectname Server - Setup"
msgstr ""
-#: ../../Zotlabs/Module/Ping.php:254
-msgid "sent you a private message"
+#: ../../Zotlabs/Module/Setup.php:174
+msgid "Could not connect to database."
msgstr ""
-#: ../../Zotlabs/Module/Ping.php:302
-msgid "added your channel"
+#: ../../Zotlabs/Module/Setup.php:178
+msgid ""
+"Could not connect to specified site URL. Possible SSL certificate or DNS "
+"issue."
msgstr ""
-#: ../../Zotlabs/Module/Ping.php:312
-msgid "g A l F d"
+#: ../../Zotlabs/Module/Setup.php:185
+msgid "Could not create table."
msgstr ""
-#: ../../Zotlabs/Module/Ping.php:330
-msgid "[today]"
+#: ../../Zotlabs/Module/Setup.php:191
+msgid "Your site database has been installed."
msgstr ""
-#: ../../Zotlabs/Module/Ping.php:339
-msgid "posted an event"
+#: ../../Zotlabs/Module/Setup.php:197
+msgid ""
+"You may need to import the file \"install/schema_xxx.sql\" manually using a "
+"database client."
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:56
-#: ../../Zotlabs/Module/Connections.php:161
-#: ../../Zotlabs/Module/Connections.php:250
-msgid "Blocked"
+#: ../../Zotlabs/Module/Setup.php:198 ../../Zotlabs/Module/Setup.php:262
+#: ../../Zotlabs/Module/Setup.php:745
+msgid "Please see the file \"install/INSTALL.txt\"."
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:61
-#: ../../Zotlabs/Module/Connections.php:168
-#: ../../Zotlabs/Module/Connections.php:249
-msgid "Ignored"
+#: ../../Zotlabs/Module/Setup.php:259
+msgid "System check"
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:66
-#: ../../Zotlabs/Module/Connections.php:182
-#: ../../Zotlabs/Module/Connections.php:248
-msgid "Hidden"
+#: ../../Zotlabs/Module/Setup.php:264
+msgid "Check again"
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:71
-#: ../../Zotlabs/Module/Connections.php:175
-#: ../../Zotlabs/Module/Connections.php:247
-msgid "Archived"
+#: ../../Zotlabs/Module/Setup.php:286
+msgid "Database connection"
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:76
-#: ../../Zotlabs/Module/Connections.php:86 ../../Zotlabs/Module/Menu.php:116
-#: ../../include/conversation.php:1724
-msgid "New"
+#: ../../Zotlabs/Module/Setup.php:287
+msgid ""
+"In order to install $Projectname we need to know how to connect to your "
+"database."
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:92
-#: ../../Zotlabs/Module/Connections.php:107
-#: ../../Zotlabs/Module/Connedit.php:682 ../../include/widgets.php:544
-msgid "All"
+#: ../../Zotlabs/Module/Setup.php:288
+msgid ""
+"Please contact your hosting provider or site administrator if you have "
+"questions about these settings."
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:138
-msgid "New Connections"
+#: ../../Zotlabs/Module/Setup.php:289
+msgid ""
+"The database you specify below should already exist. If it does not, please "
+"create it before continuing."
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:141
-msgid "Show pending (new) connections"
+#: ../../Zotlabs/Module/Setup.php:293
+msgid "Database Server Name"
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:145
-#: ../../Zotlabs/Module/Profperm.php:144
-msgid "All Connections"
+#: ../../Zotlabs/Module/Setup.php:293
+msgid "Default is 127.0.0.1"
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:148
-msgid "Show all connections"
+#: ../../Zotlabs/Module/Setup.php:294
+msgid "Database Port"
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:164
-msgid "Only show blocked connections"
+#: ../../Zotlabs/Module/Setup.php:294
+msgid "Communication port number - use 0 for default"
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:171
-msgid "Only show ignored connections"
+#: ../../Zotlabs/Module/Setup.php:295
+msgid "Database Login Name"
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:178
-msgid "Only show archived connections"
+#: ../../Zotlabs/Module/Setup.php:296
+msgid "Database Login Password"
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:185
-msgid "Only show hidden connections"
+#: ../../Zotlabs/Module/Setup.php:297
+msgid "Database Name"
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:246
-msgid "Pending approval"
+#: ../../Zotlabs/Module/Setup.php:298
+msgid "Database Type"
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:262
-#, php-format
-msgid "%1$s [%2$s]"
+#: ../../Zotlabs/Module/Setup.php:300 ../../Zotlabs/Module/Setup.php:341
+msgid "Site administrator email address"
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:263
-msgid "Edit connection"
+#: ../../Zotlabs/Module/Setup.php:300 ../../Zotlabs/Module/Setup.php:341
+msgid ""
+"Your account email address must match this in order to use the web admin "
+"panel."
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:264
-msgid "Delete connection"
+#: ../../Zotlabs/Module/Setup.php:301 ../../Zotlabs/Module/Setup.php:343
+msgid "Website URL"
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:273
-msgid "Channel address"
+#: ../../Zotlabs/Module/Setup.php:301 ../../Zotlabs/Module/Setup.php:343
+msgid "Please use SSL (https) URL if available."
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:275
-msgid "Network"
+#: ../../Zotlabs/Module/Setup.php:302 ../../Zotlabs/Module/Setup.php:345
+msgid "Please select a default timezone for your website"
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:278
-msgid "Call"
+#: ../../Zotlabs/Module/Setup.php:330
+msgid "Site settings"
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:280
-msgid "Status"
+#: ../../Zotlabs/Module/Setup.php:384
+msgid "PHP version 5.5 or greater is required."
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:282
-msgid "Connected"
+#: ../../Zotlabs/Module/Setup.php:385
+msgid "PHP version"
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:284
-msgid "Approve connection"
+#: ../../Zotlabs/Module/Setup.php:401
+msgid "Could not find a command line version of PHP in the web server PATH."
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:285
-#: ../../Zotlabs/Module/Admin/Accounts.php:171
-msgid "Approve"
+#: ../../Zotlabs/Module/Setup.php:402
+msgid ""
+"If you don't have a command line version of PHP installed on server, you "
+"will not be able to run background polling via cron."
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:286
-msgid "Ignore connection"
+#: ../../Zotlabs/Module/Setup.php:406
+msgid "PHP executable path"
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:287
-#: ../../Zotlabs/Module/Connedit.php:610
-msgid "Ignore"
+#: ../../Zotlabs/Module/Setup.php:406
+msgid ""
+"Enter full path to php executable. You can leave this blank to continue the "
+"installation."
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:288
-msgid "Recent activity"
+#: ../../Zotlabs/Module/Setup.php:411
+msgid "Command line PHP"
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:312 ../../Zotlabs/Lib/Apps.php:216
-#: ../../include/text.php:932 ../../include/nav.php:203
-msgid "Connections"
+#: ../../Zotlabs/Module/Setup.php:421
+msgid ""
+"Unable to check command line PHP, as shell_exec() is disabled. This is "
+"required."
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:316 ../../Zotlabs/Module/Search.php:44
-#: ../../Zotlabs/Lib/Apps.php:237 ../../include/acl_selectors.php:203
-#: ../../include/widgets.php:316 ../../include/text.php:1002
-#: ../../include/text.php:1014 ../../include/nav.php:180
-msgid "Search"
+#: ../../Zotlabs/Module/Setup.php:424
+msgid ""
+"The command line version of PHP on your system does not have "
+"\"register_argc_argv\" enabled."
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:317
-msgid "Search your connections"
+#: ../../Zotlabs/Module/Setup.php:425
+msgid "This is required for message delivery to work."
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:318
-msgid "Connections search"
+#: ../../Zotlabs/Module/Setup.php:428
+msgid "PHP register_argc_argv"
msgstr ""
-#: ../../Zotlabs/Module/Connections.php:319
-#: ../../Zotlabs/Module/Directory.php:392
-#: ../../Zotlabs/Module/Directory.php:397 ../../include/contact_widgets.php:23
-msgid "Find"
+#: ../../Zotlabs/Module/Setup.php:446
+#, php-format
+msgid ""
+"Your max allowed total upload size is set to %s. Maximum size of one file to "
+"upload is set to %s. You are allowed to upload up to %d files at once."
msgstr ""
-#: ../../Zotlabs/Module/Cover_photo.php:58
-#: ../../Zotlabs/Module/Profile_photo.php:61
-msgid "Image uploaded but image cropping failed."
+#: ../../Zotlabs/Module/Setup.php:451
+msgid "You can adjust these settings in the server php.ini file."
msgstr ""
-#: ../../Zotlabs/Module/Cover_photo.php:134
-#: ../../Zotlabs/Module/Cover_photo.php:181
-msgid "Cover Photos"
+#: ../../Zotlabs/Module/Setup.php:453
+msgid "PHP upload limits"
msgstr ""
-#: ../../Zotlabs/Module/Cover_photo.php:154
-#: ../../Zotlabs/Module/Profile_photo.php:135
-msgid "Image resize failed."
+#: ../../Zotlabs/Module/Setup.php:476
+msgid ""
+"Error: the \"openssl_pkey_new\" function on this system is not able to "
+"generate encryption keys"
msgstr ""
-#: ../../Zotlabs/Module/Cover_photo.php:168
-#: ../../Zotlabs/Module/Profile_photo.php:196 ../../include/photos.php:149
-msgid "Unable to process image"
+#: ../../Zotlabs/Module/Setup.php:477
+msgid ""
+"If running under Windows, please see \"http://www.php.net/manual/en/openssl."
+"installation.php\"."
msgstr ""
-#: ../../Zotlabs/Module/Cover_photo.php:192
-#: ../../Zotlabs/Module/Profile_photo.php:231
-msgid "Image upload failed."
+#: ../../Zotlabs/Module/Setup.php:480
+msgid "Generate encryption keys"
msgstr ""
-#: ../../Zotlabs/Module/Cover_photo.php:210
-#: ../../Zotlabs/Module/Profile_photo.php:250
-msgid "Unable to process image."
+#: ../../Zotlabs/Module/Setup.php:497
+msgid "libCurl PHP module"
msgstr ""
-#: ../../Zotlabs/Module/Cover_photo.php:233 ../../include/items.php:4276
-msgid "female"
+#: ../../Zotlabs/Module/Setup.php:498
+msgid "GD graphics PHP module"
msgstr ""
-#: ../../Zotlabs/Module/Cover_photo.php:234 ../../include/items.php:4277
-#, php-format
-msgid "%1$s updated her %2$s"
+#: ../../Zotlabs/Module/Setup.php:499
+msgid "OpenSSL PHP module"
msgstr ""
-#: ../../Zotlabs/Module/Cover_photo.php:235 ../../include/items.php:4278
-msgid "male"
+#: ../../Zotlabs/Module/Setup.php:500
+msgid "PDO database PHP module"
msgstr ""
-#: ../../Zotlabs/Module/Cover_photo.php:236 ../../include/items.php:4279
-#, php-format
-msgid "%1$s updated his %2$s"
+#: ../../Zotlabs/Module/Setup.php:501
+msgid "mb_string PHP module"
msgstr ""
-#: ../../Zotlabs/Module/Cover_photo.php:238 ../../include/items.php:4281
-#, php-format
-msgid "%1$s updated their %2$s"
+#: ../../Zotlabs/Module/Setup.php:502
+msgid "xml PHP module"
msgstr ""
-#: ../../Zotlabs/Module/Cover_photo.php:240 ../../include/channel.php:1764
-msgid "cover photo"
+#: ../../Zotlabs/Module/Setup.php:503
+msgid "zip PHP module"
msgstr ""
-#: ../../Zotlabs/Module/Cover_photo.php:303
-#: ../../Zotlabs/Module/Cover_photo.php:318
-#: ../../Zotlabs/Module/Profile_photo.php:311
-#: ../../Zotlabs/Module/Profile_photo.php:352
-msgid "Photo not available."
+#: ../../Zotlabs/Module/Setup.php:507 ../../Zotlabs/Module/Setup.php:509
+msgid "Apache mod_rewrite module"
msgstr ""
-#: ../../Zotlabs/Module/Cover_photo.php:354
-#: ../../Zotlabs/Module/Profile_photo.php:407
-msgid "Upload File:"
+#: ../../Zotlabs/Module/Setup.php:507
+msgid ""
+"Error: Apache webserver mod-rewrite module is required but not installed."
msgstr ""
-#: ../../Zotlabs/Module/Cover_photo.php:355
-#: ../../Zotlabs/Module/Profile_photo.php:408
-msgid "Select a profile:"
+#: ../../Zotlabs/Module/Setup.php:513 ../../Zotlabs/Module/Setup.php:516
+msgid "exec"
msgstr ""
-#: ../../Zotlabs/Module/Cover_photo.php:356
-msgid "Upload Cover Photo"
+#: ../../Zotlabs/Module/Setup.php:513
+msgid ""
+"Error: exec is required but is either not installed or has been disabled in "
+"php.ini"
msgstr ""
-#: ../../Zotlabs/Module/Cover_photo.php:361
-#: ../../Zotlabs/Module/Profile_photo.php:416
-#: ../../Zotlabs/Module/Settings/Channel.php:401
-msgid "or"
+#: ../../Zotlabs/Module/Setup.php:519 ../../Zotlabs/Module/Setup.php:522
+msgid "shell_exec"
msgstr ""
-#: ../../Zotlabs/Module/Cover_photo.php:361
-#: ../../Zotlabs/Module/Profile_photo.php:416
-msgid "skip this step"
+#: ../../Zotlabs/Module/Setup.php:519
+msgid ""
+"Error: shell_exec is required but is either not installed or has been "
+"disabled in php.ini"
msgstr ""
-#: ../../Zotlabs/Module/Cover_photo.php:361
-#: ../../Zotlabs/Module/Profile_photo.php:416
-msgid "select a photo from your photo albums"
+#: ../../Zotlabs/Module/Setup.php:527
+msgid "Error: libCURL PHP module required but not installed."
msgstr ""
-#: ../../Zotlabs/Module/Cover_photo.php:377
-#: ../../Zotlabs/Module/Profile_photo.php:435
-msgid "Crop Image"
+#: ../../Zotlabs/Module/Setup.php:531
+msgid ""
+"Error: GD graphics PHP module with JPEG support required but not installed."
msgstr ""
-#: ../../Zotlabs/Module/Cover_photo.php:378
-#: ../../Zotlabs/Module/Profile_photo.php:436
-msgid "Please adjust the image cropping for optimum viewing."
+#: ../../Zotlabs/Module/Setup.php:535
+msgid "Error: openssl PHP module required but not installed."
msgstr ""
-#: ../../Zotlabs/Module/Cover_photo.php:380
-#: ../../Zotlabs/Module/Profile_photo.php:438
-msgid "Done Editing"
+#: ../../Zotlabs/Module/Setup.php:539
+msgid "Error: PDO database PHP module required but not installed."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Features.php:55
-#: ../../Zotlabs/Module/Admin/Features.php:56
-#: ../../Zotlabs/Module/Settings/Features.php:38
-msgid "Off"
+#: ../../Zotlabs/Module/Setup.php:543
+msgid "Error: mb_string PHP module required but not installed."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Features.php:55
-#: ../../Zotlabs/Module/Admin/Features.php:56
-#: ../../Zotlabs/Module/Settings/Features.php:38
-msgid "On"
+#: ../../Zotlabs/Module/Setup.php:547
+msgid "Error: xml PHP module required for DAV but not installed."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Features.php:56
-#, php-format
-msgid "Lock feature %s"
+#: ../../Zotlabs/Module/Setup.php:551
+msgid "Error: zip PHP module required but not installed."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Features.php:64
-msgid "Manage Additional Features"
+#: ../../Zotlabs/Module/Setup.php:569
+msgid ""
+"The web installer needs to be able to create a file called \".htconfig.php\" "
+"in the top folder of your web server and it is unable to do so."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Logs.php:28
-msgid "Log settings updated."
+#: ../../Zotlabs/Module/Setup.php:570
+msgid ""
+"This is most often a permission setting, as the web server may not be able "
+"to write files in your folder - even if you can."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Logs.php:83 ../../include/widgets.php:1618
-#: ../../include/widgets.php:1628
-msgid "Logs"
+#: ../../Zotlabs/Module/Setup.php:571
+msgid ""
+"At the end of this procedure, we will give you a text to save in a file "
+"named .htconfig.php in your Red top folder."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Logs.php:85
-msgid "Clear"
+#: ../../Zotlabs/Module/Setup.php:572
+msgid ""
+"You can alternatively skip this procedure and perform a manual installation. "
+"Please see the file \"install/INSTALL.txt\" for instructions."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Logs.php:91
-msgid "Debugging"
+#: ../../Zotlabs/Module/Setup.php:575
+msgid ".htconfig.php is writable"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Logs.php:92
-msgid "Log file"
+#: ../../Zotlabs/Module/Setup.php:589
+msgid ""
+"This software uses the Smarty3 template engine to render its web views. "
+"Smarty3 compiles templates to PHP to speed up rendering."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Logs.php:92
+#: ../../Zotlabs/Module/Setup.php:590
+#, php-format
msgid ""
-"Must be writable by web server. Relative to your top-level webserver "
-"directory."
+"In order to store these compiled templates, the web server needs to have "
+"write access to the directory %s under the top level web folder."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Logs.php:93
-msgid "Log level"
+#: ../../Zotlabs/Module/Setup.php:591 ../../Zotlabs/Module/Setup.php:612
+msgid ""
+"Please ensure that the user that your web server runs as (e.g. www-data) has "
+"write access to this folder."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Profs.php:69
-msgid "New Profile Field"
+#: ../../Zotlabs/Module/Setup.php:592
+#, php-format
+msgid ""
+"Note: as a security measure, you should give the web server write access to "
+"%s only--not the template files (.tpl) that it contains."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Profs.php:70
-#: ../../Zotlabs/Module/Admin/Profs.php:90
-msgid "Field nickname"
+#: ../../Zotlabs/Module/Setup.php:595
+#, php-format
+msgid "%s is writable"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Profs.php:70
-#: ../../Zotlabs/Module/Admin/Profs.php:90
-msgid "System name of field"
+#: ../../Zotlabs/Module/Setup.php:611
+msgid ""
+"This software uses the store directory to save uploaded files. The web "
+"server needs to have write access to the store directory under the top level "
+"web folder"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Profs.php:71
-#: ../../Zotlabs/Module/Admin/Profs.php:91
-msgid "Input type"
+#: ../../Zotlabs/Module/Setup.php:615
+msgid "store is writable"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Profs.php:72
-#: ../../Zotlabs/Module/Admin/Profs.php:92
-msgid "Field Name"
+#: ../../Zotlabs/Module/Setup.php:647
+msgid ""
+"SSL certificate cannot be validated. Fix certificate or disable https access "
+"to this site."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Profs.php:72
-#: ../../Zotlabs/Module/Admin/Profs.php:92
-msgid "Label on profile pages"
+#: ../../Zotlabs/Module/Setup.php:648
+msgid ""
+"If you have https access to your website or allow connections to TCP port "
+"443 (the https: port), you MUST use a browser-valid certificate. You MUST "
+"NOT use self-signed certificates!"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Profs.php:73
-#: ../../Zotlabs/Module/Admin/Profs.php:93
-msgid "Help text"
+#: ../../Zotlabs/Module/Setup.php:649
+msgid ""
+"This restriction is incorporated because public posts from you may for "
+"example contain references to images on your own hub."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Profs.php:73
-#: ../../Zotlabs/Module/Admin/Profs.php:93
-msgid "Additional info (optional)"
+#: ../../Zotlabs/Module/Setup.php:650
+msgid ""
+"If your certificate is not recognized, members of other sites (who may "
+"themselves have valid certificates) will get a warning message on their own "
+"site complaining about security issues."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Profs.php:83
-msgid "Field definition not found"
+#: ../../Zotlabs/Module/Setup.php:651
+msgid ""
+"This can cause usability issues elsewhere (not just on your own site) so we "
+"must insist on this requirement."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Profs.php:89
-msgid "Edit Profile Field"
+#: ../../Zotlabs/Module/Setup.php:652
+msgid ""
+"Providers are available that issue free certificates which are browser-valid."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Profs.php:147 ../../include/widgets.php:1599
-msgid "Profile Fields"
+#: ../../Zotlabs/Module/Setup.php:654
+msgid ""
+"If you are confident that the certificate is valid and signed by a trusted "
+"authority, check to see if you have failed to install an intermediate cert. "
+"These are not normally required by browsers, but are required for server-to-"
+"server communications."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Profs.php:148
-msgid "Basic Profile Fields"
+#: ../../Zotlabs/Module/Setup.php:656
+msgid "SSL certificate validation"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Profs.php:149
-msgid "Advanced Profile Fields"
+#: ../../Zotlabs/Module/Setup.php:662
+msgid ""
+"Url rewrite in .htaccess is not working. Check your server configuration."
+"Test: "
msgstr ""
-#: ../../Zotlabs/Module/Admin/Profs.php:149
-msgid "(In addition to basic fields)"
+#: ../../Zotlabs/Module/Setup.php:665
+msgid "Url rewrite is working"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Profs.php:151
-msgid "All available fields"
+#: ../../Zotlabs/Module/Setup.php:679
+msgid ""
+"The database configuration file \".htconfig.php\" could not be written. "
+"Please use the enclosed text to create a configuration file in your web "
+"server root."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Profs.php:152
-msgid "Custom Fields"
+#: ../../Zotlabs/Module/Setup.php:703 ../../addon/rendezvous/rendezvous.php:401
+msgid "Errors encountered creating database tables."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Profs.php:156
-msgid "Create Custom Field"
+#: ../../Zotlabs/Module/Setup.php:743
+msgid "<h1>What next?</h1>"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Security.php:77
+#: ../../Zotlabs/Module/Setup.php:744
msgid ""
-"By default, unfiltered HTML is allowed in embedded media. This is inherently "
-"insecure."
+"IMPORTANT: You will need to [manually] setup a scheduled task for the poller."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Security.php:80
+#: ../../Zotlabs/Module/Connect.php:61 ../../Zotlabs/Module/Connect.php:109
+msgid "Continue"
+msgstr ""
+
+#: ../../Zotlabs/Module/Connect.php:90
+msgid "Premium Channel Setup"
+msgstr ""
+
+#: ../../Zotlabs/Module/Connect.php:92
+msgid "Enable premium channel connection restrictions"
+msgstr ""
+
+#: ../../Zotlabs/Module/Connect.php:93
msgid ""
-"The recommended setting is to only allow unfiltered HTML from the following "
-"sites:"
+"Please enter your restrictions or conditions, such as paypal receipt, usage "
+"guidelines, etc."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Security.php:81
+#: ../../Zotlabs/Module/Connect.php:95 ../../Zotlabs/Module/Connect.php:115
msgid ""
-"https://youtube.com/<br />https://www.youtube.com/<br />https://youtu.be/"
-"<br />https://vimeo.com/<br />https://soundcloud.com/<br />"
+"This channel may require additional steps or acknowledgement of the "
+"following conditions prior to connecting:"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Security.php:82
+#: ../../Zotlabs/Module/Connect.php:96
msgid ""
-"All other embedded content will be filtered, <strong>unless</strong> "
-"embedded content from that site is explicitly blocked."
+"Potential connections will then see the following text before proceeding:"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Security.php:87 ../../include/widgets.php:1594
-msgid "Security"
+#: ../../Zotlabs/Module/Connect.php:97 ../../Zotlabs/Module/Connect.php:118
+msgid ""
+"By continuing, I certify that I have complied with any instructions provided "
+"on this page."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Security.php:89
-msgid "Block public"
+#: ../../Zotlabs/Module/Connect.php:106
+msgid "(No specific instructions have been provided by the channel owner.)"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Security.php:89
-msgid ""
-"Check to block public access to all otherwise public personal pages on this "
-"site unless you are currently authenticated."
+#: ../../Zotlabs/Module/Connect.php:114
+msgid "Restricted or Premium Channel"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Security.php:90
-msgid "Set \"Transport Security\" HTTP header"
+#: ../../Zotlabs/Module/Admin/Queue.php:35
+msgid "Queue Statistics"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Security.php:91
-msgid "Set \"Content Security Policy\" HTTP header"
+#: ../../Zotlabs/Module/Admin/Queue.php:36
+msgid "Total Entries"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Security.php:92
-msgid "Allowed email domains"
+#: ../../Zotlabs/Module/Admin/Queue.php:37
+msgid "Priority"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Security.php:92
-msgid ""
-"Comma separated list of domains which are allowed in email addresses for "
-"registrations to this site. Wildcards are accepted. Empty to allow any "
-"domains"
+#: ../../Zotlabs/Module/Admin/Queue.php:38
+msgid "Destination URL"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Security.php:93
-msgid "Not allowed email domains"
+#: ../../Zotlabs/Module/Admin/Queue.php:39
+msgid "Mark hub permanently offline"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Security.php:93
-msgid ""
-"Comma separated list of domains which are not allowed in email addresses for "
-"registrations to this site. Wildcards are accepted. Empty to allow any "
-"domains, unless allowed domains have been defined."
+#: ../../Zotlabs/Module/Admin/Queue.php:40
+msgid "Empty queue for this hub"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Security.php:94
-msgid "Allow communications only from these sites"
+#: ../../Zotlabs/Module/Admin/Queue.php:41
+msgid "Last known contact"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Security.php:94
-msgid ""
-"One site per line. Leave empty to allow communication from anywhere by "
-"default"
+#: ../../Zotlabs/Module/Admin/Features.php:55
+#: ../../Zotlabs/Module/Admin/Features.php:56
+#: ../../Zotlabs/Module/Settings/Features.php:38
+msgid "Off"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Security.php:95
-msgid "Block communications from these sites"
+#: ../../Zotlabs/Module/Admin/Features.php:55
+#: ../../Zotlabs/Module/Admin/Features.php:56
+#: ../../Zotlabs/Module/Settings/Features.php:38
+msgid "On"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Security.php:96
-msgid "Allow communications only from these channels"
+#: ../../Zotlabs/Module/Admin/Features.php:56
+#, php-format
+msgid "Lock feature %s"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Security.php:96
-msgid ""
-"One channel (hash) per line. Leave empty to allow from any channel by default"
+#: ../../Zotlabs/Module/Admin/Features.php:64
+msgid "Manage Additional Features"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Security.php:97
-msgid "Block communications from these channels"
+#: ../../Zotlabs/Module/Admin/Dbsync.php:19
+msgid "Update has been marked successful"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Security.php:98
-msgid "Only allow embeds from secure (SSL) websites and links."
+#: ../../Zotlabs/Module/Admin/Dbsync.php:29
+#, php-format
+msgid "Executing %s failed. Check system logs."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Security.php:99
-msgid "Allow unfiltered embedded HTML content only from these domains"
+#: ../../Zotlabs/Module/Admin/Dbsync.php:32
+#, php-format
+msgid "Update %s was successfully applied."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Security.php:99
-msgid "One site per line. By default embedded content is filtered."
+#: ../../Zotlabs/Module/Admin/Dbsync.php:36
+#, php-format
+msgid "Update %s did not return a status. Unknown if it succeeded."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Security.php:100
-msgid "Block embedded HTML from these domains"
+#: ../../Zotlabs/Module/Admin/Dbsync.php:39
+#, php-format
+msgid "Update function %s could not be found."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Themes.php:18
-msgid "Theme settings updated."
+#: ../../Zotlabs/Module/Admin/Dbsync.php:55
+msgid "No failed updates."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Themes.php:58
-msgid "No themes found."
+#: ../../Zotlabs/Module/Admin/Dbsync.php:59
+msgid "Failed Updates"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Themes.php:93
-#: ../../Zotlabs/Module/Admin/Plugins.php:305
-msgid "Disable"
+#: ../../Zotlabs/Module/Admin/Dbsync.php:61
+msgid "Mark success (if update was manually applied)"
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Dbsync.php:62
+msgid "Attempt to execute this update step automatically"
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:259
+#: ../../Zotlabs/Module/Admin/Themes.php:72 ../../Zotlabs/Module/Thing.php:89
+#: ../../Zotlabs/Module/Viewsrc.php:25 ../../Zotlabs/Module/Display.php:33
+#: ../../Zotlabs/Module/Display.php:347 ../../Zotlabs/Module/Filestorage.php:24
+#: ../../Zotlabs/Module/Admin.php:62 ../../include/items.php:3410
+msgid "Item not found."
msgstr ""
+#: ../../Zotlabs/Module/Admin/Plugins.php:289
+#, php-format
+msgid "Plugin %s disabled."
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:294
+#, php-format
+msgid "Plugin %s enabled."
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:310
#: ../../Zotlabs/Module/Admin/Themes.php:95
-#: ../../Zotlabs/Module/Admin/Plugins.php:308
+msgid "Disable"
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:313
+#: ../../Zotlabs/Module/Admin/Themes.php:97
msgid "Enable"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Themes.php:114
-msgid "Screenshot"
+#: ../../Zotlabs/Module/Admin/Plugins.php:341
+#: ../../Zotlabs/Module/Admin/Plugins.php:436
+#: ../../Zotlabs/Module/Admin/Accounts.php:164
+#: ../../Zotlabs/Module/Admin/Logs.php:82
+#: ../../Zotlabs/Module/Admin/Channels.php:145
+#: ../../Zotlabs/Module/Admin/Themes.php:122
+#: ../../Zotlabs/Module/Admin/Themes.php:156
+#: ../../Zotlabs/Module/Admin/Site.php:271
+#: ../../Zotlabs/Module/Admin/Security.php:86
+#: ../../Zotlabs/Module/Admin.php:136
+msgid "Administration"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Themes.php:121
-#: ../../Zotlabs/Module/Admin/Themes.php:155 ../../include/widgets.php:1597
-msgid "Themes"
+#: ../../Zotlabs/Module/Admin/Plugins.php:342
+#: ../../Zotlabs/Module/Admin/Plugins.php:437 ../../Zotlabs/Widget/Admin.php:27
+msgid "Plugins"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Themes.php:122
-#: ../../Zotlabs/Module/Admin/Plugins.php:338
+#: ../../Zotlabs/Module/Admin/Plugins.php:343
+#: ../../Zotlabs/Module/Admin/Themes.php:124
msgid "Toggle"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Themes.php:123
-#: ../../Zotlabs/Module/Admin/Plugins.php:339 ../../Zotlabs/Lib/Apps.php:223
-#: ../../include/widgets.php:699 ../../include/nav.php:225
+#: ../../Zotlabs/Module/Admin/Plugins.php:344
+#: ../../Zotlabs/Module/Admin/Themes.php:125 ../../Zotlabs/Lib/Apps.php:236
+#: ../../Zotlabs/Widget/Settings_menu.php:133 ../../include/nav.php:132
+#: ../../include/nav.php:217
msgid "Settings"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Themes.php:132
-#: ../../Zotlabs/Module/Admin/Plugins.php:346
+#: ../../Zotlabs/Module/Admin/Plugins.php:351
+#: ../../Zotlabs/Module/Admin/Themes.php:134
msgid "Author: "
msgstr ""
-#: ../../Zotlabs/Module/Admin/Themes.php:133
-#: ../../Zotlabs/Module/Admin/Plugins.php:347
+#: ../../Zotlabs/Module/Admin/Plugins.php:352
+#: ../../Zotlabs/Module/Admin/Themes.php:135
msgid "Maintainer: "
msgstr ""
-#: ../../Zotlabs/Module/Admin/Themes.php:160
-msgid "[Experimental]"
+#: ../../Zotlabs/Module/Admin/Plugins.php:353
+msgid "Minimum project version: "
msgstr ""
-#: ../../Zotlabs/Module/Admin/Themes.php:161
-msgid "[Unsupported]"
+#: ../../Zotlabs/Module/Admin/Plugins.php:354
+msgid "Maximum project version: "
msgstr ""
-#: ../../Zotlabs/Module/Admin/Account_edit.php:29
-#, php-format
-msgid "Password changed for account %d."
+#: ../../Zotlabs/Module/Admin/Plugins.php:355
+msgid "Minimum PHP version: "
msgstr ""
-#: ../../Zotlabs/Module/Admin/Account_edit.php:46
-msgid "Account settings updated."
+#: ../../Zotlabs/Module/Admin/Plugins.php:356
+msgid "Compatible Server Roles: "
msgstr ""
-#: ../../Zotlabs/Module/Admin/Account_edit.php:61
-msgid "Account not found."
+#: ../../Zotlabs/Module/Admin/Plugins.php:357
+msgid "Requires: "
msgstr ""
-#: ../../Zotlabs/Module/Admin/Account_edit.php:68
-msgid "Account Edit"
+#: ../../Zotlabs/Module/Admin/Plugins.php:358
+#: ../../Zotlabs/Module/Admin/Plugins.php:442
+msgid "Disabled - version incompatibility"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Account_edit.php:69
-msgid "New Password"
+#: ../../Zotlabs/Module/Admin/Plugins.php:411
+msgid "Enter the public git repository URL of the plugin repo."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Account_edit.php:70
-msgid "New Password again"
+#: ../../Zotlabs/Module/Admin/Plugins.php:412
+msgid "Plugin repo git URL"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Account_edit.php:71
-msgid "Technical skill level"
+#: ../../Zotlabs/Module/Admin/Plugins.php:413
+msgid "Custom repo name"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Account_edit.php:72
-msgid "Account language (for emails)"
+#: ../../Zotlabs/Module/Admin/Plugins.php:413
+msgid "(optional)"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Account_edit.php:73
-msgid "Service class"
+#: ../../Zotlabs/Module/Admin/Plugins.php:414
+msgid "Download Plugin Repo"
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:421
+msgid "Install new repo"
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:422 ../../Zotlabs/Lib/Apps.php:383
+msgid "Install"
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:445
+msgid "Manage Repos"
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:446
+msgid "Installed Plugin Repositories"
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:447
+msgid "Install a New Plugin Repository"
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:454
+msgid "Switch branch"
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:455
+#: ../../Zotlabs/Module/Photos.php:967 ../../Zotlabs/Module/Tagrm.php:137
+#: ../../addon/superblock/superblock.php:116
+msgid "Remove"
msgstr ""
#: ../../Zotlabs/Module/Admin/Accounts.php:36
@@ -2047,7 +2318,7 @@ msgstr[1] ""
msgid "Account not found"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Accounts.php:90
+#: ../../Zotlabs/Module/Admin/Accounts.php:90 ../../include/channel.php:2357
#, php-format
msgid "Account '%s' deleted"
msgstr ""
@@ -2063,7 +2334,8 @@ msgid "Account '%s' unblocked"
msgstr ""
#: ../../Zotlabs/Module/Admin/Accounts.php:165
-#: ../../Zotlabs/Module/Admin/Accounts.php:178 ../../include/widgets.php:1592
+#: ../../Zotlabs/Module/Admin/Accounts.php:178
+#: ../../Zotlabs/Module/Admin.php:96 ../../Zotlabs/Widget/Admin.php:23
msgid "Accounts"
msgstr ""
@@ -2080,33 +2352,26 @@ msgstr ""
msgid "Request date"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Accounts.php:169
-#: ../../Zotlabs/Module/Admin/Accounts.php:181
-#: ../../Zotlabs/Module/Connedit.php:879
-#: ../../extend/addon/addon/redred/redred.php:107
-#: ../../extend/addon/addon/rtof/rtof.php:93
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1140
-#: ../../extend/addon/addon/openid/MysqlProvider.php:56
-#: ../../extend/addon/addon/openid/MysqlProvider.php:57
-#: ../../include/network.php:2247
-msgid "Email"
-msgstr ""
-
#: ../../Zotlabs/Module/Admin/Accounts.php:170
msgid "No registrations."
msgstr ""
+#: ../../Zotlabs/Module/Admin/Accounts.php:171
+#: ../../Zotlabs/Module/Connections.php:282 ../../include/conversation.php:716
+msgid "Approve"
+msgstr ""
+
#: ../../Zotlabs/Module/Admin/Accounts.php:172
msgid "Deny"
msgstr ""
#: ../../Zotlabs/Module/Admin/Accounts.php:174
-#: ../../Zotlabs/Module/Connedit.php:602
+#: ../../Zotlabs/Module/Connedit.php:622
msgid "Block"
msgstr ""
#: ../../Zotlabs/Module/Admin/Accounts.php:175
-#: ../../Zotlabs/Module/Connedit.php:602
+#: ../../Zotlabs/Module/Connedit.php:622
msgid "Unblock"
msgstr ""
@@ -2114,7 +2379,7 @@ msgstr ""
msgid "ID"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Accounts.php:182 ../../include/group.php:267
+#: ../../Zotlabs/Module/Admin/Accounts.php:182 ../../include/group.php:288
msgid "All Channels"
msgstr ""
@@ -2146,6 +2411,37 @@ msgid ""
"this site will be permanently deleted!\\n\\nAre you sure?"
msgstr ""
+#: ../../Zotlabs/Module/Admin/Logs.php:28
+msgid "Log settings updated."
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Logs.php:83 ../../Zotlabs/Widget/Admin.php:48
+#: ../../Zotlabs/Widget/Admin.php:58
+msgid "Logs"
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Logs.php:85
+msgid "Clear"
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Logs.php:91
+msgid "Debugging"
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Logs.php:92
+msgid "Log file"
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Logs.php:92
+msgid ""
+"Must be writable by web server. Relative to your top-level webserver "
+"directory."
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Logs.php:93
+msgid "Log level"
+msgstr ""
+
#: ../../Zotlabs/Module/Admin/Channels.php:31
#, php-format
msgid "%s channel censored/uncensored"
@@ -2196,7 +2492,8 @@ msgstr ""
msgid "Channel '%s' code disallowed"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Channels.php:146 ../../include/widgets.php:1593
+#: ../../Zotlabs/Module/Admin/Channels.php:146
+#: ../../Zotlabs/Module/Admin.php:110 ../../Zotlabs/Widget/Admin.php:24
msgid "Channels"
msgstr ""
@@ -2217,7 +2514,7 @@ msgid "Disallow Code"
msgstr ""
#: ../../Zotlabs/Module/Admin/Channels.php:154
-#: ../../include/conversation.php:1815
+#: ../../include/conversation.php:1791 ../../include/nav.php:399
msgid "Channel"
msgstr ""
@@ -2225,13 +2522,6 @@ msgstr ""
msgid "UID"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Channels.php:160
-#: ../../Zotlabs/Module/Locs.php:118 ../../Zotlabs/Module/Connedit.php:882
-#: ../../Zotlabs/Module/Profiles.php:503
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1143
-msgid "Address"
-msgstr ""
-
#: ../../Zotlabs/Module/Admin/Channels.php:162
msgid ""
"Selected channels will be deleted!\\n\\nEverything that was posted in these "
@@ -2244,3848 +2534,3783 @@ msgid ""
"channel on this site will be permanently deleted!\\n\\nAre you sure?"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Dbsync.php:19
-msgid "Update has been marked successful"
-msgstr ""
-
-#: ../../Zotlabs/Module/Admin/Dbsync.php:29
-#, php-format
-msgid "Executing %s failed. Check system logs."
-msgstr ""
-
-#: ../../Zotlabs/Module/Admin/Dbsync.php:32
-#, php-format
-msgid "Update %s was successfully applied."
-msgstr ""
-
-#: ../../Zotlabs/Module/Admin/Dbsync.php:36
-#, php-format
-msgid "Update %s did not return a status. Unknown if it succeeded."
+#: ../../Zotlabs/Module/Admin/Themes.php:26
+msgid "Theme settings updated."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Dbsync.php:39
-#, php-format
-msgid "Update function %s could not be found."
+#: ../../Zotlabs/Module/Admin/Themes.php:61
+msgid "No themes found."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Dbsync.php:55
-msgid "No failed updates."
+#: ../../Zotlabs/Module/Admin/Themes.php:116
+msgid "Screenshot"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Dbsync.php:59
-msgid "Failed Updates"
+#: ../../Zotlabs/Module/Admin/Themes.php:123
+#: ../../Zotlabs/Module/Admin/Themes.php:157 ../../Zotlabs/Widget/Admin.php:28
+msgid "Themes"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Dbsync.php:61
-msgid "Mark success (if update was manually applied)"
+#: ../../Zotlabs/Module/Admin/Themes.php:162
+msgid "[Experimental]"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Dbsync.php:62
-msgid "Attempt to execute this update step automatically"
+#: ../../Zotlabs/Module/Admin/Themes.php:163
+msgid "[Unsupported]"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:133
+#: ../../Zotlabs/Module/Admin/Site.php:144
msgid "Site settings updated."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:159 ../../include/text.php:2934
+#: ../../Zotlabs/Module/Admin/Site.php:170
+#: ../../view/theme/redbasic_c/php/config.php:15
+#: ../../view/theme/redbasic/php/config.php:15 ../../include/text.php:2943
msgid "Default"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:169
-#: ../../Zotlabs/Module/Settings/Display.php:143
+#: ../../Zotlabs/Module/Admin/Site.php:181
+#: ../../Zotlabs/Module/Settings/Display.php:137
+#, php-format
+msgid "%s - (Incompatible)"
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Site.php:188
+#: ../../Zotlabs/Module/Settings/Display.php:151
msgid "mobile"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:171
+#: ../../Zotlabs/Module/Admin/Site.php:190
msgid "experimental"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:173
+#: ../../Zotlabs/Module/Admin/Site.php:192
msgid "unsupported"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:219
+#: ../../Zotlabs/Module/Admin/Site.php:238
msgid "Yes - with approval"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:225
+#: ../../Zotlabs/Module/Admin/Site.php:244
msgid "My site is not a public server"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:226
+#: ../../Zotlabs/Module/Admin/Site.php:245
msgid "My site has paid access only"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:227
+#: ../../Zotlabs/Module/Admin/Site.php:246
msgid "My site has free access only"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:228
+#: ../../Zotlabs/Module/Admin/Site.php:247
msgid "My site offers free accounts with optional paid upgrades"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:239 ../../Zotlabs/Module/Setup.php:328
-msgid "Basic/Minimal Social Networking"
-msgstr ""
-
-#: ../../Zotlabs/Module/Admin/Site.php:240 ../../Zotlabs/Module/Setup.php:329
-msgid "Standard Configuration (default)"
-msgstr ""
-
-#: ../../Zotlabs/Module/Admin/Site.php:241 ../../Zotlabs/Module/Setup.php:330
-msgid "Professional"
-msgstr ""
-
-#: ../../Zotlabs/Module/Admin/Site.php:245 ../../Zotlabs/Lib/Techlevels.php:10
+#: ../../Zotlabs/Module/Admin/Site.php:258
msgid "Beginner/Basic"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:246 ../../Zotlabs/Lib/Techlevels.php:11
+#: ../../Zotlabs/Module/Admin/Site.php:259
msgid "Novice - not skilled but willing to learn"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:247 ../../Zotlabs/Lib/Techlevels.php:12
+#: ../../Zotlabs/Module/Admin/Site.php:260
msgid "Intermediate - somewhat comfortable"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:248 ../../Zotlabs/Lib/Techlevels.php:13
+#: ../../Zotlabs/Module/Admin/Site.php:261
msgid "Advanced - very comfortable"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:249 ../../Zotlabs/Lib/Techlevels.php:14
+#: ../../Zotlabs/Module/Admin/Site.php:262
msgid "Expert - I can write computer code"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:250 ../../Zotlabs/Lib/Techlevels.php:15
+#: ../../Zotlabs/Module/Admin/Site.php:263
msgid "Wizard - I probably know more than you do"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:259 ../../include/widgets.php:1591
+#: ../../Zotlabs/Module/Admin/Site.php:272 ../../Zotlabs/Widget/Admin.php:22
msgid "Site"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:262
+#: ../../Zotlabs/Module/Admin/Site.php:274
+#: ../../Zotlabs/Module/Register.php:251
+msgid "Registration"
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Site.php:275
msgid "File upload"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:263
+#: ../../Zotlabs/Module/Admin/Site.php:276
msgid "Policies"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:264
-#: ../../include/contact_widgets.php:16
+#: ../../Zotlabs/Module/Admin/Site.php:277 ../../include/contact_widgets.php:16
msgid "Advanced"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:268
-#: ../../extend/addon/addon/statusnet/statusnet.php:890
+#: ../../Zotlabs/Module/Admin/Site.php:281
+#: ../../addon/statusnet/statusnet.php:890
msgid "Site name"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:270 ../../Zotlabs/Module/Setup.php:351
-msgid "Server Configuration/Role"
-msgstr ""
-
-#: ../../Zotlabs/Module/Admin/Site.php:272
+#: ../../Zotlabs/Module/Admin/Site.php:283
msgid "Site default technical skill level"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:272
+#: ../../Zotlabs/Module/Admin/Site.php:283
msgid "Used to provide a member experience matched to technical comfort level"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:274
+#: ../../Zotlabs/Module/Admin/Site.php:285
msgid "Lock the technical skill level setting"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:274
+#: ../../Zotlabs/Module/Admin/Site.php:285
msgid "Members can set their own technical comfort level by default"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:276
+#: ../../Zotlabs/Module/Admin/Site.php:287
msgid "Banner/Logo"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:277
+#: ../../Zotlabs/Module/Admin/Site.php:288
msgid "Administrator Information"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:277
+#: ../../Zotlabs/Module/Admin/Site.php:288
msgid ""
"Contact information for site administrators. Displayed on siteinfo page. "
"BBCode can be used here"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:278
-#: ../../Zotlabs/Module/Siteinfo.php:23
+#: ../../Zotlabs/Module/Admin/Site.php:289 ../../Zotlabs/Module/Siteinfo.php:22
msgid "Site Information"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:278
+#: ../../Zotlabs/Module/Admin/Site.php:289
msgid ""
"Publicly visible description of this site. Displayed on siteinfo page. "
"BBCode can be used here"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:279
+#: ../../Zotlabs/Module/Admin/Site.php:290
msgid "System language"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:280
+#: ../../Zotlabs/Module/Admin/Site.php:291
msgid "System theme"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:280
+#: ../../Zotlabs/Module/Admin/Site.php:291
msgid ""
"Default system theme - may be over-ridden by user profiles - <a href='#' "
"id='cnftheme'>change theme settings</a>"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:281
+#: ../../Zotlabs/Module/Admin/Site.php:292
msgid "Mobile system theme"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:281
+#: ../../Zotlabs/Module/Admin/Site.php:292
msgid "Theme for mobile devices"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:283
+#: ../../Zotlabs/Module/Admin/Site.php:294
msgid "Allow Feeds as Connections"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:283
+#: ../../Zotlabs/Module/Admin/Site.php:294
msgid "(Heavy system resource usage)"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:284
+#: ../../Zotlabs/Module/Admin/Site.php:295
msgid "Maximum image size"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:284
+#: ../../Zotlabs/Module/Admin/Site.php:295
msgid ""
"Maximum size in bytes of uploaded images. Default is 0, which means no "
"limits."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:285
+#: ../../Zotlabs/Module/Admin/Site.php:296
msgid "Does this site allow new member registration?"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:286
+#: ../../Zotlabs/Module/Admin/Site.php:297
msgid "Invitation only"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:286
+#: ../../Zotlabs/Module/Admin/Site.php:297
msgid ""
"Only allow new member registrations with an invitation code. Above register "
"policy must be set to Yes."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:287
+#: ../../Zotlabs/Module/Admin/Site.php:298
msgid "Which best describes the types of account offered by this hub?"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:288
+#: ../../Zotlabs/Module/Admin/Site.php:299
msgid "Register text"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:288
+#: ../../Zotlabs/Module/Admin/Site.php:299
msgid "Will be displayed prominently on the registration page."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:289
+#: ../../Zotlabs/Module/Admin/Site.php:300
msgid "Site homepage to show visitors (default: login box)"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:289
+#: ../../Zotlabs/Module/Admin/Site.php:300
msgid ""
"example: 'public' to show public stream, 'page/sys/home' to show a system "
"webpage called 'home' or 'include:home.html' to include a file."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:290
+#: ../../Zotlabs/Module/Admin/Site.php:301
msgid "Preserve site homepage URL"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:290
+#: ../../Zotlabs/Module/Admin/Site.php:301
msgid ""
"Present the site homepage in a frame at the original location instead of "
"redirecting"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:291
+#: ../../Zotlabs/Module/Admin/Site.php:302
msgid "Accounts abandoned after x days"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:291
+#: ../../Zotlabs/Module/Admin/Site.php:302
msgid ""
"Will not waste system resources polling external sites for abandonded "
"accounts. Enter 0 for no time limit."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:292
+#: ../../Zotlabs/Module/Admin/Site.php:303
msgid "Allowed friend domains"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:292
+#: ../../Zotlabs/Module/Admin/Site.php:303
msgid ""
"Comma separated list of domains which are allowed to establish friendships "
"with this site. Wildcards are accepted. Empty to allow any domains"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:293
+#: ../../Zotlabs/Module/Admin/Site.php:304
msgid "Verify Email Addresses"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:293
+#: ../../Zotlabs/Module/Admin/Site.php:304
msgid ""
"Check to verify email addresses used in account registration (recommended)."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:294
+#: ../../Zotlabs/Module/Admin/Site.php:305
msgid "Force publish"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:294
+#: ../../Zotlabs/Module/Admin/Site.php:305
msgid ""
"Check to force all profiles on this site to be listed in the site directory."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:295
+#: ../../Zotlabs/Module/Admin/Site.php:306
msgid "Import Public Streams"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:295
+#: ../../Zotlabs/Module/Admin/Site.php:306
msgid ""
"Import and allow access to public content pulled from other sites. Warning: "
"this content is unmoderated."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:296
+#: ../../Zotlabs/Module/Admin/Site.php:307
msgid "Login on Homepage"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:296
+#: ../../Zotlabs/Module/Admin/Site.php:307
msgid ""
"Present a login box to visitors on the home page if no other content has "
"been configured."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:297
+#: ../../Zotlabs/Module/Admin/Site.php:308
msgid "Enable context help"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:297
+#: ../../Zotlabs/Module/Admin/Site.php:308
msgid ""
"Display contextual help for the current page when the help button is pressed."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:299
+#: ../../Zotlabs/Module/Admin/Site.php:310
+msgid "Reply-to email address for system generated email."
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Site.php:311
+msgid "Sender (From) email address for system generated email."
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Site.php:312
+msgid "Name of email sender for system generated email."
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Site.php:314
msgid "Directory Server URL"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:299
+#: ../../Zotlabs/Module/Admin/Site.php:314
msgid "Default directory server"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:301
+#: ../../Zotlabs/Module/Admin/Site.php:316
msgid "Proxy user"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:302
+#: ../../Zotlabs/Module/Admin/Site.php:317
msgid "Proxy URL"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:303
+#: ../../Zotlabs/Module/Admin/Site.php:318
msgid "Network timeout"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:303
+#: ../../Zotlabs/Module/Admin/Site.php:318
msgid "Value is in seconds. Set to 0 for unlimited (not recommended)."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:304
+#: ../../Zotlabs/Module/Admin/Site.php:319
msgid "Delivery interval"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:304
+#: ../../Zotlabs/Module/Admin/Site.php:319
msgid ""
"Delay background delivery processes by this many seconds to reduce system "
"load. Recommend: 4-5 for shared hosts, 2-3 for virtual private servers. 0-1 "
"for large dedicated servers."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:305
+#: ../../Zotlabs/Module/Admin/Site.php:320
msgid "Deliveries per process"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:305
+#: ../../Zotlabs/Module/Admin/Site.php:320
msgid ""
"Number of deliveries to attempt in a single operating system process. Adjust "
"if necessary to tune system performance. Recommend: 1-5."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:306
+#: ../../Zotlabs/Module/Admin/Site.php:321
msgid "Poll interval"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:306
+#: ../../Zotlabs/Module/Admin/Site.php:321
msgid ""
"Delay background polling processes by this many seconds to reduce system "
"load. If 0, use delivery interval."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:307
+#: ../../Zotlabs/Module/Admin/Site.php:322
+msgid "Path to ImageMagick convert program"
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Site.php:322
+msgid ""
+"If set, use this program to generate photo thumbnails for huge images ( > "
+"4000 pixels in either dimension), otherwise memory exhaustion may occur. "
+"Example: /usr/bin/convert"
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Site.php:323
msgid "Maximum Load Average"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:307
+#: ../../Zotlabs/Module/Admin/Site.php:323
msgid ""
"Maximum system load before delivery and poll processes are deferred - "
"default 50."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:308
+#: ../../Zotlabs/Module/Admin/Site.php:324
msgid "Expiration period in days for imported (grid/network) content"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Site.php:308
+#: ../../Zotlabs/Module/Admin/Site.php:324
msgid "0 for no expiration of imported content"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Plugins.php:284
-#, php-format
-msgid "Plugin %s disabled."
+#: ../../Zotlabs/Module/Admin/Profs.php:69
+msgid "New Profile Field"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Plugins.php:289
-#, php-format
-msgid "Plugin %s enabled."
+#: ../../Zotlabs/Module/Admin/Profs.php:70
+#: ../../Zotlabs/Module/Admin/Profs.php:90
+msgid "Field nickname"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Plugins.php:337
-#: ../../Zotlabs/Module/Admin/Plugins.php:432 ../../include/widgets.php:1596
-msgid "Plugins"
+#: ../../Zotlabs/Module/Admin/Profs.php:70
+#: ../../Zotlabs/Module/Admin/Profs.php:90
+msgid "System name of field"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Plugins.php:348
-msgid "Minimum project version: "
+#: ../../Zotlabs/Module/Admin/Profs.php:71
+#: ../../Zotlabs/Module/Admin/Profs.php:91
+msgid "Input type"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Plugins.php:349
-msgid "Maximum project version: "
+#: ../../Zotlabs/Module/Admin/Profs.php:72
+#: ../../Zotlabs/Module/Admin/Profs.php:92
+msgid "Field Name"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Plugins.php:350
-msgid "Minimum PHP version: "
+#: ../../Zotlabs/Module/Admin/Profs.php:72
+#: ../../Zotlabs/Module/Admin/Profs.php:92
+msgid "Label on profile pages"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Plugins.php:351
-msgid "Compatible Server Roles: "
+#: ../../Zotlabs/Module/Admin/Profs.php:73
+#: ../../Zotlabs/Module/Admin/Profs.php:93
+msgid "Help text"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Plugins.php:352
-msgid "Requires: "
+#: ../../Zotlabs/Module/Admin/Profs.php:73
+#: ../../Zotlabs/Module/Admin/Profs.php:93
+msgid "Additional info (optional)"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Plugins.php:353
-#: ../../Zotlabs/Module/Admin/Plugins.php:437
-msgid "Disabled - version incompatibility"
+#: ../../Zotlabs/Module/Admin/Profs.php:74
+#: ../../Zotlabs/Module/Admin/Profs.php:94 ../../Zotlabs/Module/Rbmark.php:32
+#: ../../Zotlabs/Module/Rbmark.php:104 ../../Zotlabs/Module/Filer.php:53
+#: ../../Zotlabs/Widget/Notes.php:18 ../../include/text.php:1030
+#: ../../include/text.php:1042
+msgid "Save"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Plugins.php:406
-msgid "Enter the public git repository URL of the plugin repo."
+#: ../../Zotlabs/Module/Admin/Profs.php:83
+msgid "Field definition not found"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Plugins.php:407
-msgid "Plugin repo git URL"
+#: ../../Zotlabs/Module/Admin/Profs.php:89
+msgid "Edit Profile Field"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Plugins.php:408
-msgid "Custom repo name"
+#: ../../Zotlabs/Module/Admin/Profs.php:147 ../../Zotlabs/Widget/Admin.php:30
+msgid "Profile Fields"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Plugins.php:408
-msgid "(optional)"
+#: ../../Zotlabs/Module/Admin/Profs.php:148
+msgid "Basic Profile Fields"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Plugins.php:409
-msgid "Download Plugin Repo"
+#: ../../Zotlabs/Module/Admin/Profs.php:149
+msgid "Advanced Profile Fields"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Plugins.php:416
-msgid "Install new repo"
+#: ../../Zotlabs/Module/Admin/Profs.php:149
+msgid "(In addition to basic fields)"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Plugins.php:417 ../../Zotlabs/Lib/Apps.php:348
-msgid "Install"
+#: ../../Zotlabs/Module/Admin/Profs.php:151
+msgid "All available fields"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Plugins.php:418
-#: ../../Zotlabs/Module/Connedit.php:893 ../../Zotlabs/Module/Fbrowser.php:66
-#: ../../Zotlabs/Module/Fbrowser.php:88 ../../Zotlabs/Module/Wiki.php:263
-#: ../../Zotlabs/Module/Wiki.php:288
-#: ../../Zotlabs/Module/Settings/Oauth.php:88
-#: ../../Zotlabs/Module/Settings/Oauth.php:114
-#: ../../Zotlabs/Module/Tagrm.php:15 ../../Zotlabs/Module/Tagrm.php:138
-#: ../../extend/addon/addon/friendica/dfrn_request.php:879
-#: ../../extend/addon/addon/js_upload/js_upload.php:46
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:866
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1154
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:243
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:266
-#: ../../include/conversation.php:1394 ../../include/conversation.php:1443
-msgid "Cancel"
+#: ../../Zotlabs/Module/Admin/Profs.php:152
+msgid "Custom Fields"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Plugins.php:440
-msgid "Manage Repos"
+#: ../../Zotlabs/Module/Admin/Profs.php:156
+msgid "Create Custom Field"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Plugins.php:441
-msgid "Installed Plugin Repositories"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:29
+#, php-format
+msgid "Password changed for account %d."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Plugins.php:442
-msgid "Install a New Plugin Repository"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:46
+msgid "Account settings updated."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Plugins.php:448
-#: ../../Zotlabs/Module/Connedit.php:891
-#: ../../Zotlabs/Module/Settings/Oauth.php:42
-#: ../../Zotlabs/Module/Settings/Oauth.php:113 ../../Zotlabs/Lib/Apps.php:348
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1152
-msgid "Update"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:61
+msgid "Account not found."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Plugins.php:449
-msgid "Switch branch"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:68
+msgid "Account Edit"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Queue.php:35
-msgid "Queue Statistics"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:69
+msgid "New Password"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Queue.php:36
-msgid "Total Entries"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:70
+msgid "New Password again"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Queue.php:37
-msgid "Priority"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:71
+msgid "Technical skill level"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Queue.php:38
-msgid "Destination URL"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:72
+msgid "Account language (for emails)"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Queue.php:39
-msgid "Mark hub permanently offline"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:73
+msgid "Service class"
msgstr ""
-#: ../../Zotlabs/Module/Admin/Queue.php:40
-msgid "Empty queue for this hub"
+#: ../../Zotlabs/Module/Admin/Security.php:77
+msgid ""
+"By default, unfiltered HTML is allowed in embedded media. This is inherently "
+"insecure."
msgstr ""
-#: ../../Zotlabs/Module/Admin/Queue.php:41
-msgid "Last known contact"
+#: ../../Zotlabs/Module/Admin/Security.php:80
+msgid ""
+"The recommended setting is to only allow unfiltered HTML from the following "
+"sites:"
msgstr ""
-#: ../../Zotlabs/Module/Search.php:223
-#, php-format
-msgid "Items tagged with: %s"
+#: ../../Zotlabs/Module/Admin/Security.php:81
+msgid ""
+"https://youtube.com/<br />https://www.youtube.com/<br />https://youtu.be/"
+"<br />https://vimeo.com/<br />https://soundcloud.com/<br />"
msgstr ""
-#: ../../Zotlabs/Module/Search.php:225
-#, php-format
-msgid "Search results for: %s"
+#: ../../Zotlabs/Module/Admin/Security.php:82
+msgid ""
+"All other embedded content will be filtered, <strong>unless</strong> "
+"embedded content from that site is explicitly blocked."
msgstr ""
-#: ../../Zotlabs/Module/Editlayout.php:127
-#: ../../Zotlabs/Module/Layouts.php:128 ../../Zotlabs/Module/Layouts.php:188
-msgid "Layout Name"
+#: ../../Zotlabs/Module/Admin/Security.php:87 ../../Zotlabs/Widget/Admin.php:25
+msgid "Security"
msgstr ""
-#: ../../Zotlabs/Module/Editlayout.php:128
-#: ../../Zotlabs/Module/Layouts.php:131
-msgid "Layout Description (Optional)"
+#: ../../Zotlabs/Module/Admin/Security.php:89
+msgid "Block public"
msgstr ""
-#: ../../Zotlabs/Module/Editlayout.php:136
-msgid "Edit Layout"
+#: ../../Zotlabs/Module/Admin/Security.php:89
+msgid ""
+"Check to block public access to all otherwise public personal pages on this "
+"site unless you are currently authenticated."
msgstr ""
-#: ../../Zotlabs/Module/Editwebpage.php:142
-msgid "Page link"
+#: ../../Zotlabs/Module/Admin/Security.php:90
+msgid "Set \"Transport Security\" HTTP header"
msgstr ""
-#: ../../Zotlabs/Module/Editwebpage.php:169
-msgid "Edit Webpage"
+#: ../../Zotlabs/Module/Admin/Security.php:91
+msgid "Set \"Content Security Policy\" HTTP header"
msgstr ""
-#: ../../Zotlabs/Module/Like.php:19
-msgid "Like/Dislike"
+#: ../../Zotlabs/Module/Admin/Security.php:92
+msgid "Allowed email domains"
msgstr ""
-#: ../../Zotlabs/Module/Like.php:24
-msgid "This action is restricted to members."
+#: ../../Zotlabs/Module/Admin/Security.php:92
+msgid ""
+"Comma separated list of domains which are allowed in email addresses for "
+"registrations to this site. Wildcards are accepted. Empty to allow any "
+"domains"
msgstr ""
-#: ../../Zotlabs/Module/Like.php:25
+#: ../../Zotlabs/Module/Admin/Security.php:93
+msgid "Not allowed email domains"
+msgstr ""
+
+#: ../../Zotlabs/Module/Admin/Security.php:93
msgid ""
-"Please <a href=\"rmagic\">login with your $Projectname ID</a> or <a href="
-"\"register\">register as a new $Projectname member</a> to continue."
+"Comma separated list of domains which are not allowed in email addresses for "
+"registrations to this site. Wildcards are accepted. Empty to allow any "
+"domains, unless allowed domains have been defined."
msgstr ""
-#: ../../Zotlabs/Module/Like.php:105 ../../Zotlabs/Module/Like.php:131
-#: ../../Zotlabs/Module/Like.php:169
-msgid "Invalid request."
+#: ../../Zotlabs/Module/Admin/Security.php:94
+msgid "Allow communications only from these sites"
msgstr ""
-#: ../../Zotlabs/Module/Like.php:117 ../../include/conversation.php:126
-msgid "channel"
+#: ../../Zotlabs/Module/Admin/Security.php:94
+msgid ""
+"One site per line. Leave empty to allow communication from anywhere by "
+"default"
msgstr ""
-#: ../../Zotlabs/Module/Like.php:146
-msgid "thing"
+#: ../../Zotlabs/Module/Admin/Security.php:95
+msgid "Block communications from these sites"
msgstr ""
-#: ../../Zotlabs/Module/Like.php:192
-msgid "Channel unavailable."
+#: ../../Zotlabs/Module/Admin/Security.php:96
+msgid "Allow communications only from these channels"
msgstr ""
-#: ../../Zotlabs/Module/Like.php:240
-msgid "Previous action reversed."
+#: ../../Zotlabs/Module/Admin/Security.php:96
+msgid ""
+"One channel (hash) per line. Leave empty to allow from any channel by default"
msgstr ""
-#: ../../Zotlabs/Module/Like.php:370 ../../Zotlabs/Module/Subthread.php:87
-#: ../../Zotlabs/Module/Tagger.php:47
-#: ../../extend/addon/addon/diaspora/inbound.php:1781
-#: ../../extend/addon/addon/redphotos/redphotohelper.php:74
-#: ../../include/conversation.php:120 ../../include/text.php:1956
-msgid "photo"
+#: ../../Zotlabs/Module/Admin/Security.php:97
+msgid "Block communications from these channels"
msgstr ""
-#: ../../Zotlabs/Module/Like.php:370 ../../Zotlabs/Module/Subthread.php:87
-#: ../../extend/addon/addon/diaspora/inbound.php:1781
-#: ../../include/conversation.php:148 ../../include/text.php:1962
-msgid "status"
+#: ../../Zotlabs/Module/Admin/Security.php:98
+msgid "Only allow embeds from secure (SSL) websites and links."
msgstr ""
-#: ../../Zotlabs/Module/Like.php:372 ../../Zotlabs/Module/Events.php:260
-#: ../../Zotlabs/Module/Tagger.php:51 ../../include/conversation.php:123
-#: ../../include/text.php:1959 ../../include/event.php:1000
-msgid "event"
+#: ../../Zotlabs/Module/Admin/Security.php:99
+msgid "Allow unfiltered embedded HTML content only from these domains"
msgstr ""
-#: ../../Zotlabs/Module/Like.php:419
-#: ../../extend/addon/addon/diaspora/inbound.php:1810
-#: ../../include/conversation.php:164
-#, php-format
-msgid "%1$s likes %2$s's %3$s"
+#: ../../Zotlabs/Module/Admin/Security.php:99
+msgid "One site per line. By default embedded content is filtered."
msgstr ""
-#: ../../Zotlabs/Module/Like.php:421 ../../include/conversation.php:167
-#, php-format
-msgid "%1$s doesn't like %2$s's %3$s"
+#: ../../Zotlabs/Module/Admin/Security.php:100
+msgid "Block embedded HTML from these domains"
msgstr ""
-#: ../../Zotlabs/Module/Like.php:423
-#, php-format
-msgid "%1$s agrees with %2$s's %3$s"
+#: ../../Zotlabs/Module/Lockview.php:75
+msgid "Remote privacy information not available."
msgstr ""
-#: ../../Zotlabs/Module/Like.php:425
-#, php-format
-msgid "%1$s doesn't agree with %2$s's %3$s"
+#: ../../Zotlabs/Module/Lockview.php:96
+msgid "Visible to:"
msgstr ""
-#: ../../Zotlabs/Module/Like.php:427
-#, php-format
-msgid "%1$s abstains from a decision on %2$s's %3$s"
+#: ../../Zotlabs/Module/Lockview.php:117 ../../Zotlabs/Module/Lockview.php:153
+#: ../../Zotlabs/Module/Acl.php:118 ../../include/acl_selectors.php:183
+msgctxt "acl"
+msgid "Profile"
msgstr ""
-#: ../../Zotlabs/Module/Like.php:429
-#, php-format
-msgid "%1$s is attending %2$s's %3$s"
+#: ../../Zotlabs/Module/Moderate.php:55
+msgid "Comment approved"
msgstr ""
-#: ../../Zotlabs/Module/Like.php:431
-#, php-format
-msgid "%1$s is not attending %2$s's %3$s"
+#: ../../Zotlabs/Module/Moderate.php:59
+msgid "Comment deleted"
msgstr ""
-#: ../../Zotlabs/Module/Like.php:433
-#, php-format
-msgid "%1$s may attend %2$s's %3$s"
+#: ../../Zotlabs/Module/Settings/Permcats.php:37
+msgid "Permission category saved."
msgstr ""
-#: ../../Zotlabs/Module/Like.php:538
-msgid "Action completed."
+#: ../../Zotlabs/Module/Settings/Permcats.php:61
+msgid ""
+"Use this form to create permission rules for various classes of people or "
+"connections."
msgstr ""
-#: ../../Zotlabs/Module/Like.php:539
-msgid "Thank you."
+#: ../../Zotlabs/Module/Settings/Permcats.php:94
+msgid "Permission Categories"
msgstr ""
-#: ../../Zotlabs/Module/Dirsearch.php:25 ../../Zotlabs/Module/Regdir.php:49
-msgid "This site is not a directory server"
+#: ../../Zotlabs/Module/Settings/Permcats.php:102
+msgid "Permission Name"
msgstr ""
-#: ../../Zotlabs/Module/Dirsearch.php:33
-msgid "This directory server requires an access token"
+#: ../../Zotlabs/Module/Settings/Permcats.php:103
+#: ../../Zotlabs/Module/Settings/Tokens.php:161
+#: ../../Zotlabs/Module/Connedit.php:908
+msgid "My Settings"
msgstr ""
-#: ../../Zotlabs/Module/Network.php:96
-msgid "No such group"
+#: ../../Zotlabs/Module/Settings/Permcats.php:105
+#: ../../Zotlabs/Module/Settings/Tokens.php:163
+#: ../../Zotlabs/Module/Connedit.php:903
+msgid "inherited"
msgstr ""
-#: ../../Zotlabs/Module/Network.php:136
-msgid "No such channel"
+#: ../../Zotlabs/Module/Settings/Permcats.php:108
+#: ../../Zotlabs/Module/Settings/Tokens.php:166
+#: ../../Zotlabs/Module/Connedit.php:910
+msgid "Individual Permissions"
msgstr ""
-#: ../../Zotlabs/Module/Network.php:141
-msgid "forum"
+#: ../../Zotlabs/Module/Settings/Permcats.php:109
+#: ../../Zotlabs/Module/Settings/Tokens.php:167
+#: ../../Zotlabs/Module/Connedit.php:911
+msgid ""
+"Some permissions may be inherited from your channel's <a href=\"settings"
+"\"><strong>privacy settings</strong></a>, which have higher priority than "
+"individual settings. You can <strong>not</strong> change those settings here."
msgstr ""
-#: ../../Zotlabs/Module/Network.php:153
-msgid "Search Results For:"
+#: ../../Zotlabs/Module/Settings/Channel.php:62
+#: ../../Zotlabs/Module/Settings/Channel.php:66
+#: ../../Zotlabs/Module/Settings/Channel.php:67
+#: ../../Zotlabs/Module/Settings/Channel.php:70
+#: ../../Zotlabs/Module/Settings/Channel.php:81
+#: ../../Zotlabs/Module/Connedit.php:711 ../../Zotlabs/Widget/Affinity.php:28
+#: ../../include/selectors.php:123 ../../include/channel.php:423
+#: ../../include/channel.php:424 ../../include/channel.php:431
+msgid "Friends"
msgstr ""
-#: ../../Zotlabs/Module/Network.php:221
-msgid "Privacy group is empty"
+#: ../../Zotlabs/Module/Settings/Channel.php:255
+#: ../../addon/rendezvous/rendezvous.php:82
+#: ../../addon/openstreetmap/openstreetmap.php:184
+#: ../../addon/msgfooter/msgfooter.php:54 ../../addon/logrot/logrot.php:54
+#: ../../addon/twitter/twitter.php:766 ../../addon/piwik/piwik.php:116
+#: ../../addon/xmpp/xmpp.php:102
+msgid "Settings updated."
msgstr ""
-#: ../../Zotlabs/Module/Network.php:230
-msgid "Privacy group: "
+#: ../../Zotlabs/Module/Settings/Channel.php:316
+msgid "Nobody except yourself"
msgstr ""
-#: ../../Zotlabs/Module/Network.php:256
-msgid "Invalid connection."
+#: ../../Zotlabs/Module/Settings/Channel.php:317
+msgid "Only those you specifically allow"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:49
-msgid "Unable to update menu."
+#: ../../Zotlabs/Module/Settings/Channel.php:318
+msgid "Approved connections"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:60
-msgid "Unable to create menu."
+#: ../../Zotlabs/Module/Settings/Channel.php:319
+msgid "Any connections"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:98 ../../Zotlabs/Module/Menu.php:110
-msgid "Menu Name"
+#: ../../Zotlabs/Module/Settings/Channel.php:320
+msgid "Anybody on this website"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:98
-msgid "Unique name (not visible on webpage) - required"
+#: ../../Zotlabs/Module/Settings/Channel.php:321
+msgid "Anybody in this network"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:99 ../../Zotlabs/Module/Menu.php:111
-msgid "Menu Title"
+#: ../../Zotlabs/Module/Settings/Channel.php:322
+msgid "Anybody authenticated"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:99
-msgid "Visible on webpage - leave empty for no title"
+#: ../../Zotlabs/Module/Settings/Channel.php:323
+msgid "Anybody on the internet"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:100
-msgid "Allow Bookmarks"
+#: ../../Zotlabs/Module/Settings/Channel.php:399
+msgid "Publish your default profile in the network directory"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:100 ../../Zotlabs/Module/Menu.php:157
-msgid "Menu may be used to store saved bookmarks"
+#: ../../Zotlabs/Module/Settings/Channel.php:404
+msgid "Allow us to suggest you as a potential friend to new members?"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:101 ../../Zotlabs/Module/Menu.php:159
-msgid "Submit and proceed"
+#: ../../Zotlabs/Module/Settings/Channel.php:408
+#: ../../Zotlabs/Module/Profile_photo.php:437
+#: ../../Zotlabs/Module/Cover_photo.php:365
+msgid "or"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:107 ../../include/text.php:2287
-msgid "Menus"
+#: ../../Zotlabs/Module/Settings/Channel.php:413
+msgid "Your channel address is"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:113 ../../Zotlabs/Module/Locs.php:120
-msgid "Drop"
+#: ../../Zotlabs/Module/Settings/Channel.php:416
+msgid "Your files/photos are accessible via WebDAV at"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:114 ../../Zotlabs/Module/Blocks.php:157
-#: ../../Zotlabs/Module/Layouts.php:190 ../../Zotlabs/Module/Webpages.php:255
-#: ../../include/page_widgets.php:47
-msgid "Created"
+#: ../../Zotlabs/Module/Settings/Channel.php:478
+msgid "Channel Settings"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:115 ../../Zotlabs/Module/Blocks.php:158
-#: ../../Zotlabs/Module/Layouts.php:191 ../../Zotlabs/Module/Webpages.php:256
-#: ../../include/page_widgets.php:48
-msgid "Edited"
+#: ../../Zotlabs/Module/Settings/Channel.php:485
+msgid "Basic Settings"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:117
-msgid "Bookmarks allowed"
+#: ../../Zotlabs/Module/Settings/Channel.php:486 ../../include/channel.php:1473
+msgid "Full Name:"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:119
-msgid "Delete this menu"
+#: ../../Zotlabs/Module/Settings/Channel.php:487
+#: ../../Zotlabs/Module/Settings/Account.php:119
+msgid "Email Address:"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:120 ../../Zotlabs/Module/Menu.php:154
-msgid "Edit menu contents"
+#: ../../Zotlabs/Module/Settings/Channel.php:488
+msgid "Your Timezone:"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:121
-msgid "Edit this menu"
+#: ../../Zotlabs/Module/Settings/Channel.php:489
+msgid "Default Post Location:"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:136
-msgid "Menu could not be deleted."
+#: ../../Zotlabs/Module/Settings/Channel.php:489
+msgid "Geographical location to display on your posts"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:144 ../../Zotlabs/Module/Mitem.php:28
-msgid "Menu not found."
+#: ../../Zotlabs/Module/Settings/Channel.php:490
+msgid "Use Browser Location:"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:149
-msgid "Edit Menu"
+#: ../../Zotlabs/Module/Settings/Channel.php:492
+msgid "Adult Content"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:153
-msgid "Add or remove entries to this menu"
+#: ../../Zotlabs/Module/Settings/Channel.php:492
+msgid ""
+"This channel frequently or regularly publishes adult content. (Please tag "
+"any adult material and/or nudity with #NSFW)"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:155
-msgid "Menu name"
+#: ../../Zotlabs/Module/Settings/Channel.php:494
+msgid "Security and Privacy Settings"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:155
-msgid "Must be unique, only seen by you"
+#: ../../Zotlabs/Module/Settings/Channel.php:496
+msgid "Your permissions are already configured. Click to view/adjust"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:156
-msgid "Menu title"
+#: ../../Zotlabs/Module/Settings/Channel.php:498
+msgid "Hide my online presence"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:156
-msgid "Menu title as seen by others"
+#: ../../Zotlabs/Module/Settings/Channel.php:498
+msgid "Prevents displaying in your profile that you are online"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:157
-msgid "Allow bookmarks"
+#: ../../Zotlabs/Module/Settings/Channel.php:500
+msgid "Simple Privacy Settings:"
msgstr ""
-#: ../../Zotlabs/Module/Menu.php:166 ../../Zotlabs/Module/Mitem.php:120
-#: ../../Zotlabs/Module/Xchan.php:41
-msgid "Not found."
+#: ../../Zotlabs/Module/Settings/Channel.php:501
+msgid ""
+"Very Public - <em>extremely permissive (should be used with caution)</em>"
msgstr ""
-#: ../../Zotlabs/Module/Locs.php:25 ../../Zotlabs/Module/Locs.php:54
-msgid "Location not found."
+#: ../../Zotlabs/Module/Settings/Channel.php:502
+msgid ""
+"Typical - <em>default public, privacy when desired (similar to social "
+"network permissions but with improved privacy)</em>"
msgstr ""
-#: ../../Zotlabs/Module/Locs.php:62
-msgid "Location lookup failed."
+#: ../../Zotlabs/Module/Settings/Channel.php:503
+msgid "Private - <em>default private, never open or public</em>"
msgstr ""
-#: ../../Zotlabs/Module/Locs.php:66
+#: ../../Zotlabs/Module/Settings/Channel.php:504
+msgid "Blocked - <em>default blocked to/from everybody</em>"
+msgstr ""
+
+#: ../../Zotlabs/Module/Settings/Channel.php:506
+msgid "Allow others to tag your posts"
+msgstr ""
+
+#: ../../Zotlabs/Module/Settings/Channel.php:506
msgid ""
-"Please select another location to become primary before removing the primary "
-"location."
+"Often used by the community to retro-actively flag inappropriate content"
msgstr ""
-#: ../../Zotlabs/Module/Locs.php:95
-msgid "Syncing locations"
+#: ../../Zotlabs/Module/Settings/Channel.php:508
+msgid "Channel Permission Limits"
msgstr ""
-#: ../../Zotlabs/Module/Locs.php:105
-msgid "No locations found."
+#: ../../Zotlabs/Module/Settings/Channel.php:510
+msgid "Expire other channel content after this many days"
msgstr ""
-#: ../../Zotlabs/Module/Locs.php:116
-msgid "Manage Channel Locations"
+#: ../../Zotlabs/Module/Settings/Channel.php:510
+msgid "0 or blank to use the website limit."
msgstr ""
-#: ../../Zotlabs/Module/Locs.php:117 ../../Zotlabs/Module/Pubsites.php:51
-#: ../../Zotlabs/Module/Profiles.php:510 ../../Zotlabs/Module/Profiles.php:733
-#: ../../Zotlabs/Module/Events.php:475
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:839
-#: ../../include/js_strings.php:25
-msgid "Location"
+#: ../../Zotlabs/Module/Settings/Channel.php:510
+#, php-format
+msgid "This website expires after %d days."
msgstr ""
-#: ../../Zotlabs/Module/Locs.php:119
-msgid "Primary"
+#: ../../Zotlabs/Module/Settings/Channel.php:510
+msgid "This website does not expire imported content."
msgstr ""
-#: ../../Zotlabs/Module/Locs.php:122
-msgid "Sync Now"
+#: ../../Zotlabs/Module/Settings/Channel.php:510
+msgid "The website limit takes precedence if lower than your limit."
msgstr ""
-#: ../../Zotlabs/Module/Locs.php:123
-msgid "Please wait several minutes between consecutive operations."
+#: ../../Zotlabs/Module/Settings/Channel.php:511
+msgid "Maximum Friend Requests/Day:"
msgstr ""
-#: ../../Zotlabs/Module/Locs.php:124
-msgid ""
-"When possible, drop a location by logging into that website/hub and removing "
-"your channel."
+#: ../../Zotlabs/Module/Settings/Channel.php:511
+msgid "May reduce spam activity"
msgstr ""
-#: ../../Zotlabs/Module/Locs.php:125
-msgid "Use this form to drop the location if the hub is no longer operating."
+#: ../../Zotlabs/Module/Settings/Channel.php:512
+msgid "Default Privacy Group"
msgstr ""
-#: ../../Zotlabs/Module/Pubsites.php:24 ../../include/widgets.php:1415
-msgid "Public Hubs"
+#: ../../Zotlabs/Module/Settings/Channel.php:514
+msgid "Use my default audience setting for the type of object published"
msgstr ""
-#: ../../Zotlabs/Module/Pubsites.php:27
-msgid ""
-"The listed hubs allow public registration for the $Projectname network. All "
-"hubs in the network are interlinked so membership on any of them conveys "
-"membership in the network as a whole. Some hubs may require subscription or "
-"provide tiered service plans. The hub itself <strong>may</strong> provide "
-"additional details."
+#: ../../Zotlabs/Module/Settings/Channel.php:521
+msgid "Channel permissions category:"
msgstr ""
-#: ../../Zotlabs/Module/Pubsites.php:33
-msgid "Hub URL"
+#: ../../Zotlabs/Module/Settings/Channel.php:522
+msgid "Default Permissions Group"
msgstr ""
-#: ../../Zotlabs/Module/Pubsites.php:33
-msgid "Access Type"
+#: ../../Zotlabs/Module/Settings/Channel.php:528
+msgid "Maximum private messages per day from unknown people:"
msgstr ""
-#: ../../Zotlabs/Module/Pubsites.php:33
-msgid "Registration Policy"
+#: ../../Zotlabs/Module/Settings/Channel.php:528
+msgid "Useful to reduce spamming"
msgstr ""
-#: ../../Zotlabs/Module/Pubsites.php:33
-msgid "Stats"
+#: ../../Zotlabs/Module/Settings/Channel.php:531
+msgid "Notification Settings"
msgstr ""
-#: ../../Zotlabs/Module/Pubsites.php:33
-msgid "Software"
+#: ../../Zotlabs/Module/Settings/Channel.php:532
+msgid "By default post a status message when:"
msgstr ""
-#: ../../Zotlabs/Module/Pubsites.php:35 ../../Zotlabs/Module/Ratings.php:97
-#: ../../include/conversation.php:941 ../../include/conversation.php:1099
-msgid "Ratings"
+#: ../../Zotlabs/Module/Settings/Channel.php:533
+msgid "accepting a friend request"
msgstr ""
-#: ../../Zotlabs/Module/Pubsites.php:48
-msgid "Rate"
+#: ../../Zotlabs/Module/Settings/Channel.php:534
+msgid "joining a forum/community"
msgstr ""
-#: ../../Zotlabs/Module/Pubsites.php:59 ../../Zotlabs/Module/Blocks.php:166
-#: ../../Zotlabs/Module/Layouts.php:197 ../../Zotlabs/Module/Events.php:694
-#: ../../Zotlabs/Module/Webpages.php:250 ../../Zotlabs/Module/Wiki.php:165
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:151
-#: ../../include/page_widgets.php:42
-msgid "View"
+#: ../../Zotlabs/Module/Settings/Channel.php:535
+msgid "making an <em>interesting</em> profile change"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:82
-msgid "Could not access contact record."
+#: ../../Zotlabs/Module/Settings/Channel.php:536
+msgid "Send a notification email when:"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:112
-msgid "Could not locate selected profile."
+#: ../../Zotlabs/Module/Settings/Channel.php:537
+msgid "You receive a connection request"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:257
-msgid "Connection updated."
+#: ../../Zotlabs/Module/Settings/Channel.php:538
+msgid "Your connections are confirmed"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:259
-msgid "Failed to update connection record."
+#: ../../Zotlabs/Module/Settings/Channel.php:539
+msgid "Someone writes on your profile wall"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:309
-msgid "is now connected to"
+#: ../../Zotlabs/Module/Settings/Channel.php:540
+msgid "Someone writes a followup comment"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:442
-msgid "Could not access address book record."
+#: ../../Zotlabs/Module/Settings/Channel.php:541
+msgid "You receive a private message"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:462
-msgid "Refresh failed - channel is currently unavailable."
+#: ../../Zotlabs/Module/Settings/Channel.php:542
+msgid "You receive a friend suggestion"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:477 ../../Zotlabs/Module/Connedit.php:486
-#: ../../Zotlabs/Module/Connedit.php:495 ../../Zotlabs/Module/Connedit.php:504
-#: ../../Zotlabs/Module/Connedit.php:517
-msgid "Unable to set address book parameters."
+#: ../../Zotlabs/Module/Settings/Channel.php:543
+msgid "You are tagged in a post"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:541
-msgid "Connection has been removed."
+#: ../../Zotlabs/Module/Settings/Channel.php:544
+msgid "You are poked/prodded/etc. in a post"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:581 ../../Zotlabs/Lib/Apps.php:228
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:57
-#: ../../include/conversation.php:936 ../../include/conversation.php:1049
-#: ../../include/nav.php:103
-msgid "View Profile"
+#: ../../Zotlabs/Module/Settings/Channel.php:546
+msgid "Someone likes your post/comment"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:584
-#, php-format
-msgid "View %s's profile"
+#: ../../Zotlabs/Module/Settings/Channel.php:549
+msgid "Show visual notifications including:"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:588
-msgid "Refresh Permissions"
+#: ../../Zotlabs/Module/Settings/Channel.php:551
+msgid "Unseen grid activity"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:591
-msgid "Fetch updated permissions"
+#: ../../Zotlabs/Module/Settings/Channel.php:552
+msgid "Unseen channel activity"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:595
-msgid "Recent Activity"
+#: ../../Zotlabs/Module/Settings/Channel.php:553
+msgid "Unseen private messages"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:598
-msgid "View recent posts and comments"
+#: ../../Zotlabs/Module/Settings/Channel.php:553
+#: ../../Zotlabs/Module/Settings/Channel.php:558
+#: ../../Zotlabs/Module/Settings/Channel.php:559
+#: ../../Zotlabs/Module/Settings/Channel.php:560
+#: ../../addon/jappixmini/jappixmini.php:343
+msgid "Recommended"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:605
-msgid "Block (or Unblock) all communications with this connection"
+#: ../../Zotlabs/Module/Settings/Channel.php:554
+msgid "Upcoming events"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:606
-msgid "This connection is blocked!"
+#: ../../Zotlabs/Module/Settings/Channel.php:555
+msgid "Events today"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:610
-msgid "Unignore"
+#: ../../Zotlabs/Module/Settings/Channel.php:556
+msgid "Upcoming birthdays"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:613
-msgid "Ignore (or Unignore) all inbound communications from this connection"
+#: ../../Zotlabs/Module/Settings/Channel.php:556
+msgid "Not available in all themes"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:614
-msgid "This connection is ignored!"
+#: ../../Zotlabs/Module/Settings/Channel.php:557
+msgid "System (personal) notifications"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:618
-msgid "Unarchive"
+#: ../../Zotlabs/Module/Settings/Channel.php:558
+msgid "System info messages"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:618
-msgid "Archive"
+#: ../../Zotlabs/Module/Settings/Channel.php:559
+msgid "System critical alerts"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:621
-msgid ""
-"Archive (or Unarchive) this connection - mark channel dead but keep content"
+#: ../../Zotlabs/Module/Settings/Channel.php:560
+msgid "New connections"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:622
-msgid "This connection is archived!"
+#: ../../Zotlabs/Module/Settings/Channel.php:561
+msgid "System Registrations"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:626
-msgid "Unhide"
+#: ../../Zotlabs/Module/Settings/Channel.php:562
+msgid "Unseen shared files"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:626
-msgid "Hide"
+#: ../../Zotlabs/Module/Settings/Channel.php:563
+msgid "Unseen public activity"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:629
-msgid "Hide or Unhide this connection from your other connections"
+#: ../../Zotlabs/Module/Settings/Channel.php:564
+msgid ""
+"Also show new wall posts, private messages and connections under Notices"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:630
-msgid "This connection is hidden!"
+#: ../../Zotlabs/Module/Settings/Channel.php:566
+msgid "Notify me of events this many days in advance"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:637
-msgid "Delete this connection"
+#: ../../Zotlabs/Module/Settings/Channel.php:566
+msgid "Must be greater than 0"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:648
-msgid "Open Individual Permissions section by default"
+#: ../../Zotlabs/Module/Settings/Channel.php:572
+msgid "Advanced Account/Page Type Settings"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:671
-msgid "Affinity"
+#: ../../Zotlabs/Module/Settings/Channel.php:573
+msgid "Change the behaviour of this account for special situations"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:674
-msgid "Open Set Affinity section by default"
+#: ../../Zotlabs/Module/Settings/Channel.php:575
+msgid "Miscellaneous Settings"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:678 ../../include/widgets.php:540
-msgid "Me"
+#: ../../Zotlabs/Module/Settings/Channel.php:576
+msgid "Default photo upload folder"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:679 ../../include/widgets.php:541
-msgid "Family"
+#: ../../Zotlabs/Module/Settings/Channel.php:576
+#: ../../Zotlabs/Module/Settings/Channel.php:577
+msgid "%Y - current year, %m - current month"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:680
-#: ../../Zotlabs/Module/Settings/Channel.php:61
-#: ../../Zotlabs/Module/Settings/Channel.php:65
-#: ../../Zotlabs/Module/Settings/Channel.php:66
-#: ../../Zotlabs/Module/Settings/Channel.php:69
-#: ../../Zotlabs/Module/Settings/Channel.php:80
-#: ../../include/selectors.php:123 ../../include/widgets.php:542
-#: ../../include/channel.php:408 ../../include/channel.php:409
-#: ../../include/channel.php:416
-msgid "Friends"
+#: ../../Zotlabs/Module/Settings/Channel.php:577
+msgid "Default file upload folder"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:681 ../../include/widgets.php:543
-msgid "Acquaintances"
+#: ../../Zotlabs/Module/Settings/Channel.php:579
+msgid "Personal menu to display in your channel pages"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:708
-msgid "Filter"
+#: ../../Zotlabs/Module/Settings/Channel.php:581
+msgid "Remove this channel."
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:711
-msgid "Open Custom Filter section by default"
+#: ../../Zotlabs/Module/Settings/Channel.php:582
+msgid "Firefox Share $Projectname provider"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:748
-msgid "Approve this connection"
+#: ../../Zotlabs/Module/Settings/Channel.php:583
+msgid "Start calendar week on Monday"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:748
-msgid "Accept connection to allow communication"
+#: ../../Zotlabs/Module/Settings/Features.php:45
+msgid "Additional Features"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:753
-msgid "Set Affinity"
+#: ../../Zotlabs/Module/Settings/Tokens.php:31
+#, php-format
+msgid "This channel is limited to %d tokens"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:756
-msgid "Set Profile"
+#: ../../Zotlabs/Module/Settings/Tokens.php:37
+msgid "Name and Password are required."
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:759
-msgid "Set Affinity & Profile"
+#: ../../Zotlabs/Module/Settings/Tokens.php:77
+msgid "Token saved."
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:817
-msgid "none"
+#: ../../Zotlabs/Module/Settings/Tokens.php:113
+msgid ""
+"Use this form to create temporary access identifiers to share things with "
+"non-members. These identities may be used in Access Control Lists and "
+"visitors may login using these credentials to access private content."
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:820 ../../include/widgets.php:675
-msgid "Connection Default Permissions"
+#: ../../Zotlabs/Module/Settings/Tokens.php:115
+msgid ""
+"You may also provide <em>dropbox</em> style access links to friends and "
+"associates by adding the Login Password to any specific site URL as shown. "
+"Examples:"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:820 ../../include/items.php:3932
-#, php-format
-msgid "Connection: %s"
+#: ../../Zotlabs/Module/Settings/Tokens.php:150
+#: ../../Zotlabs/Widget/Settings_menu.php:92
+msgid "Guest Access Tokens"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:821
-msgid "Apply these permissions automatically"
+#: ../../Zotlabs/Module/Settings/Tokens.php:157
+msgid "Login Name"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:821
-msgid "Connection requests will be approved without your interaction"
+#: ../../Zotlabs/Module/Settings/Tokens.php:158
+msgid "Login Password"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:822
-msgid "Permission role"
+#: ../../Zotlabs/Module/Settings/Tokens.php:159
+msgid "Expires (yyyy-mm-dd)"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:823
-msgid "Add permission role"
+#: ../../Zotlabs/Module/Settings/Tokens.php:160
+#: ../../Zotlabs/Module/Connedit.php:907
+msgid "Their Settings"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:829
-msgid "This connection's primary address is"
+#: ../../Zotlabs/Module/Settings/Account.php:20
+msgid "Not valid email."
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:830
-msgid "Available locations:"
+#: ../../Zotlabs/Module/Settings/Account.php:23
+msgid "Protected email address. Cannot change to that email."
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:834
-msgid ""
-"The permissions indicated on this page will be applied to all new "
-"connections."
+#: ../../Zotlabs/Module/Settings/Account.php:32
+msgid "System failure storing new email. Please try again."
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:835
-msgid "Connection Tools"
+#: ../../Zotlabs/Module/Settings/Account.php:40
+msgid "Technical skill level updated"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:837
-msgid "Slide to adjust your degree of friendship"
+#: ../../Zotlabs/Module/Settings/Account.php:56
+msgid "Password verification failed."
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:838 ../../Zotlabs/Module/Rate.php:155
-#: ../../include/js_strings.php:20
-msgid "Rating"
+#: ../../Zotlabs/Module/Settings/Account.php:63
+msgid "Passwords do not match. Password unchanged."
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:839
-msgid "Slide to adjust your rating"
+#: ../../Zotlabs/Module/Settings/Account.php:67
+msgid "Empty passwords are not allowed. Password unchanged."
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:840 ../../Zotlabs/Module/Connedit.php:845
-msgid "Optionally explain your rating"
+#: ../../Zotlabs/Module/Settings/Account.php:81
+msgid "Password changed."
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:842
-msgid "Custom Filter"
+#: ../../Zotlabs/Module/Settings/Account.php:83
+msgid "Password update failed. Please try again."
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:843
-msgid "Only import posts with this text"
+#: ../../Zotlabs/Module/Settings/Account.php:112
+msgid "Account Settings"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:843 ../../Zotlabs/Module/Connedit.php:844
-msgid ""
-"words one per line or #tags or /patterns/ or lang=xx, leave blank to import "
-"all posts"
+#: ../../Zotlabs/Module/Settings/Account.php:113
+msgid "Current Password"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:844
-msgid "Do not import posts with this text"
+#: ../../Zotlabs/Module/Settings/Account.php:114
+msgid "Enter New Password"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:846
-msgid "This information is public!"
+#: ../../Zotlabs/Module/Settings/Account.php:115
+msgid "Confirm New Password"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:851
-msgid "Connection Pending Approval"
+#: ../../Zotlabs/Module/Settings/Account.php:115
+msgid "Leave password fields blank unless changing"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:854
-#: ../../Zotlabs/Module/Settings/Tokens.php:163
-#: ../../Zotlabs/Module/Settings/Permcats.php:107
-msgid "inherited"
+#: ../../Zotlabs/Module/Settings/Account.php:116
+msgid "Your technical skill level"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:856
-#, php-format
-msgid ""
-"Please choose the profile you would like to display to %s when viewing your "
-"profile securely."
+#: ../../Zotlabs/Module/Settings/Account.php:116
+msgid "Used to provide a member experience matched to your comfort level"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:858
-#: ../../Zotlabs/Module/Settings/Tokens.php:160
-msgid "Their Settings"
+#: ../../Zotlabs/Module/Settings/Account.php:120
+#: ../../Zotlabs/Module/Removeaccount.php:61
+msgid "Remove Account"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:859
-#: ../../Zotlabs/Module/Settings/Tokens.php:161
-#: ../../Zotlabs/Module/Settings/Permcats.php:105
-msgid "My Settings"
+#: ../../Zotlabs/Module/Settings/Account.php:121
+msgid "Remove this account including all its channels"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:861
-#: ../../Zotlabs/Module/Settings/Tokens.php:166
-#: ../../Zotlabs/Module/Settings/Permcats.php:110
-msgid "Individual Permissions"
+#: ../../Zotlabs/Module/Settings/Featured.php:21
+msgid "Affinity Slider settings updated."
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:862
-#: ../../Zotlabs/Module/Settings/Tokens.php:167
-#: ../../Zotlabs/Module/Settings/Permcats.php:111
-msgid ""
-"Some permissions may be inherited from your channel's <a href=\"settings"
-"\"><strong>privacy settings</strong></a>, which have higher priority than "
-"individual settings. You can <strong>not</strong> change those settings here."
+#: ../../Zotlabs/Module/Settings/Featured.php:36
+msgid "No feature settings configured"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:863
-msgid ""
-"Some permissions may be inherited from your channel's <a href=\"settings"
-"\"><strong>privacy settings</strong></a>, which have higher priority than "
-"individual settings. You can change those settings here but they wont have "
-"any impact unless the inherited setting changes."
+#: ../../Zotlabs/Module/Settings/Featured.php:43
+msgid "Default maximum affinity level"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:864
-msgid "Last update:"
+#: ../../Zotlabs/Module/Settings/Featured.php:48
+msgid "Default minimum affinity level"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:873
-msgid "Details"
+#: ../../Zotlabs/Module/Settings/Featured.php:52
+msgid "Affinity Slider Settings"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:876
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1137
-msgid "Organisation"
+#: ../../Zotlabs/Module/Settings/Featured.php:62
+msgid "Feature/Addon Settings"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:877
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1138
-#: ../../include/page_widgets.php:46
-msgid "Title"
+#: ../../Zotlabs/Module/Settings/Display.php:145
+msgid "No special theme for mobile devices"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:878
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1139
-msgid "Phone"
+#: ../../Zotlabs/Module/Settings/Display.php:148
+#, php-format
+msgid "%s - (Experimental)"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:880
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1141
-msgid "Instant messenger"
+#: ../../Zotlabs/Module/Settings/Display.php:202
+msgid "Display Settings"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:881
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1142
-msgid "Website"
+#: ../../Zotlabs/Module/Settings/Display.php:203
+msgid "Theme Settings"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:883
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1144
-msgid "Note"
+#: ../../Zotlabs/Module/Settings/Display.php:204
+msgid "Custom Theme Settings"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:884
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1145
-#: ../../extend/addon/addon/cdav/cdav.php:270
-#: ../../include/connections.php:894
-msgid "Mobile"
+#: ../../Zotlabs/Module/Settings/Display.php:205
+msgid "Content Settings"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:885
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1146
-#: ../../extend/addon/addon/cdav/cdav.php:271
-#: ../../include/connections.php:895
-msgid "Home"
+#: ../../Zotlabs/Module/Settings/Display.php:211
+msgid "Display Theme:"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:886
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1147
-#: ../../extend/addon/addon/cdav/cdav.php:274
-#: ../../include/connections.php:898
-msgid "Work"
+#: ../../Zotlabs/Module/Settings/Display.php:212
+msgid "Select scheme"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:888
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:368
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1149
-msgid "Add Contact"
+#: ../../Zotlabs/Module/Settings/Display.php:214
+msgid "Mobile Theme:"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:889
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1150
-msgid "Add Field"
+#: ../../Zotlabs/Module/Settings/Display.php:215
+msgid "Preload images before rendering the page"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:894
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1155
-msgid "P.O. Box"
+#: ../../Zotlabs/Module/Settings/Display.php:215
+msgid ""
+"The subjective page load time will be longer but the page will be ready when "
+"displayed"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:895
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1156
-msgid "Additional"
+#: ../../Zotlabs/Module/Settings/Display.php:216
+msgid "Enable user zoom on mobile devices"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:896
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1157
-msgid "Street"
+#: ../../Zotlabs/Module/Settings/Display.php:217
+msgid "Update browser every xx seconds"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:897
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1158
-msgid "Locality"
+#: ../../Zotlabs/Module/Settings/Display.php:217
+msgid "Minimum of 10 seconds, no maximum"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:898
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1159
-msgid "Region"
+#: ../../Zotlabs/Module/Settings/Display.php:218
+msgid "Maximum number of conversations to load at any time:"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:899
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1160
-msgid "ZIP Code"
+#: ../../Zotlabs/Module/Settings/Display.php:218
+msgid "Maximum of 100 items"
msgstr ""
-#: ../../Zotlabs/Module/Connedit.php:900 ../../Zotlabs/Module/Profiles.php:756
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1161
-msgid "Country"
+#: ../../Zotlabs/Module/Settings/Display.php:219
+msgid "Show emoticons (smilies) as images"
msgstr ""
-#: ../../Zotlabs/Module/Home.php:74 ../../Zotlabs/Module/Home.php:82
-#: ../../extend/addon/addon/opensearch/opensearch.php:42
-msgid "$Projectname"
+#: ../../Zotlabs/Module/Settings/Display.php:220
+msgid "Manual conversation updates"
msgstr ""
-#: ../../Zotlabs/Module/Home.php:92
-#, php-format
-msgid "Welcome to %s"
+#: ../../Zotlabs/Module/Settings/Display.php:220
+msgid "Default is on, turning this off may increase screen jumping"
msgstr ""
-#: ../../Zotlabs/Module/Filestorage.php:87
-msgid "Permission Denied."
+#: ../../Zotlabs/Module/Settings/Display.php:221
+msgid "Link post titles to source"
msgstr ""
-#: ../../Zotlabs/Module/Filestorage.php:103
-msgid "File not found."
+#: ../../Zotlabs/Module/Settings/Display.php:222
+msgid "System Page Layout Editor - (advanced)"
msgstr ""
-#: ../../Zotlabs/Module/Filestorage.php:146
-msgid "Edit file permissions"
+#: ../../Zotlabs/Module/Settings/Display.php:225
+msgid "Use blog/list mode on channel page"
msgstr ""
-#: ../../Zotlabs/Module/Filestorage.php:159
-msgid "Set/edit permissions"
+#: ../../Zotlabs/Module/Settings/Display.php:225
+#: ../../Zotlabs/Module/Settings/Display.php:226
+msgid "(comments displayed separately)"
msgstr ""
-#: ../../Zotlabs/Module/Filestorage.php:160
-msgid "Include all files and sub folders"
+#: ../../Zotlabs/Module/Settings/Display.php:226
+msgid "Use blog/list mode on grid page"
msgstr ""
-#: ../../Zotlabs/Module/Filestorage.php:161
-msgid "Return to file list"
+#: ../../Zotlabs/Module/Settings/Display.php:227
+msgid "Channel page max height of content (in pixels)"
msgstr ""
-#: ../../Zotlabs/Module/Filestorage.php:163
-msgid "Copy/paste this code to attach file to a post"
+#: ../../Zotlabs/Module/Settings/Display.php:227
+#: ../../Zotlabs/Module/Settings/Display.php:228
+msgid "click to expand content exceeding this height"
msgstr ""
-#: ../../Zotlabs/Module/Filestorage.php:164
-msgid "Copy/paste this URL to link file from a web page"
+#: ../../Zotlabs/Module/Settings/Display.php:228
+msgid "Grid page max height of content (in pixels)"
msgstr ""
-#: ../../Zotlabs/Module/Filestorage.php:166
-msgid "Share this file"
+#: ../../Zotlabs/Module/Settings/Oauth.php:34
+msgid "Name is required"
msgstr ""
-#: ../../Zotlabs/Module/Filestorage.php:167
-msgid "Show URL to this file"
+#: ../../Zotlabs/Module/Settings/Oauth.php:38
+msgid "Key and Secret are required"
msgstr ""
-#: ../../Zotlabs/Module/Filestorage.php:168
-msgid "Notify your contacts about this file"
+#: ../../Zotlabs/Module/Settings/Oauth.php:86
+#: ../../Zotlabs/Module/Settings/Oauth.php:112
+#: ../../Zotlabs/Module/Settings/Oauth.php:148
+msgid "Add application"
msgstr ""
-#: ../../Zotlabs/Module/Fbrowser.php:29 ../../Zotlabs/Lib/Apps.php:229
-#: ../../include/conversation.php:1836
-msgid "Photos"
+#: ../../Zotlabs/Module/Settings/Oauth.php:89
+msgid "Name of application"
msgstr ""
-#: ../../Zotlabs/Module/Apps.php:45 ../../include/widgets.php:102
-#: ../../include/nav.php:178
-msgid "Apps"
+#: ../../Zotlabs/Module/Settings/Oauth.php:90
+#: ../../Zotlabs/Module/Settings/Oauth.php:116
+#: ../../addon/statusnet/statusnet.php:893 ../../addon/twitter/twitter.php:775
+msgid "Consumer Key"
msgstr ""
-#: ../../Zotlabs/Module/Cal.php:69
-msgid "Permissions denied."
+#: ../../Zotlabs/Module/Settings/Oauth.php:90
+#: ../../Zotlabs/Module/Settings/Oauth.php:91
+msgid "Automatically generated - change if desired. Max length 20"
msgstr ""
-#: ../../Zotlabs/Module/Cal.php:263 ../../Zotlabs/Module/Events.php:605
-msgid "l, F j"
+#: ../../Zotlabs/Module/Settings/Oauth.php:91
+#: ../../Zotlabs/Module/Settings/Oauth.php:117
+#: ../../addon/statusnet/statusnet.php:892 ../../addon/twitter/twitter.php:776
+msgid "Consumer Secret"
msgstr ""
-#: ../../Zotlabs/Module/Cal.php:312 ../../Zotlabs/Module/Events.php:660
-#: ../../include/text.php:1764
-msgid "Link to Source"
+#: ../../Zotlabs/Module/Settings/Oauth.php:92
+#: ../../Zotlabs/Module/Settings/Oauth.php:118
+msgid "Redirect"
msgstr ""
-#: ../../Zotlabs/Module/Cal.php:335 ../../Zotlabs/Module/Events.php:688
-msgid "Edit Event"
+#: ../../Zotlabs/Module/Settings/Oauth.php:92
+msgid ""
+"Redirect URI - leave blank unless your application specifically requires this"
msgstr ""
-#: ../../Zotlabs/Module/Cal.php:335 ../../Zotlabs/Module/Events.php:688
-msgid "Create Event"
+#: ../../Zotlabs/Module/Settings/Oauth.php:93
+#: ../../Zotlabs/Module/Settings/Oauth.php:119
+msgid "Icon url"
msgstr ""
-#: ../../Zotlabs/Module/Cal.php:338 ../../Zotlabs/Module/Events.php:691
-#: ../../include/channel.php:1370
-msgid "Export"
+#: ../../Zotlabs/Module/Settings/Oauth.php:93
+#: ../../Zotlabs/Module/Sources.php:112 ../../Zotlabs/Module/Sources.php:147
+msgid "Optional"
msgstr ""
-#: ../../Zotlabs/Module/Cal.php:341 ../../include/text.php:2310
-msgid "Import"
+#: ../../Zotlabs/Module/Settings/Oauth.php:104
+msgid "Application not found."
msgstr ""
-#: ../../Zotlabs/Module/Cal.php:345 ../../Zotlabs/Module/Events.php:700
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:848
-msgid "Today"
+#: ../../Zotlabs/Module/Settings/Oauth.php:147
+msgid "Connected Apps"
msgstr ""
-#: ../../Zotlabs/Module/Group.php:24
-msgid "Privacy group created."
+#: ../../Zotlabs/Module/Settings/Oauth.php:151
+msgid "Client key starts with"
msgstr ""
-#: ../../Zotlabs/Module/Group.php:30
-msgid "Could not create privacy group."
+#: ../../Zotlabs/Module/Settings/Oauth.php:152
+msgid "No name"
msgstr ""
-#: ../../Zotlabs/Module/Group.php:42 ../../Zotlabs/Module/Group.php:141
-#: ../../include/items.php:3899
-msgid "Privacy group not found."
+#: ../../Zotlabs/Module/Settings/Oauth.php:153
+msgid "Remove authorization"
msgstr ""
-#: ../../Zotlabs/Module/Group.php:58
-msgid "Privacy group updated."
+#: ../../Zotlabs/Module/Embedphotos.php:140 ../../Zotlabs/Module/Photos.php:758
+#: ../../Zotlabs/Module/Photos.php:1297 ../../Zotlabs/Widget/Portfolio.php:78
+#: ../../Zotlabs/Widget/Album.php:78
+msgid "View Photo"
msgstr ""
-#: ../../Zotlabs/Module/Group.php:90
-msgid "Create a group of channels."
+#: ../../Zotlabs/Module/Embedphotos.php:156 ../../Zotlabs/Module/Photos.php:789
+#: ../../Zotlabs/Widget/Portfolio.php:97 ../../Zotlabs/Widget/Album.php:95
+msgid "Edit Album"
msgstr ""
-#: ../../Zotlabs/Module/Group.php:91 ../../Zotlabs/Module/Group.php:184
-msgid "Privacy group name: "
+#: ../../Zotlabs/Module/Embedphotos.php:158 ../../Zotlabs/Module/Photos.php:791
+#: ../../Zotlabs/Module/Photos.php:1328
+#: ../../Zotlabs/Module/Profile_photo.php:431
+#: ../../Zotlabs/Module/Cover_photo.php:361
+#: ../../Zotlabs/Storage/Browser.php:230 ../../Zotlabs/Storage/Browser.php:337
+#: ../../Zotlabs/Widget/Cdav.php:132 ../../Zotlabs/Widget/Cdav.php:168
+#: ../../Zotlabs/Widget/Portfolio.php:99 ../../Zotlabs/Widget/Album.php:97
+msgid "Upload"
msgstr ""
-#: ../../Zotlabs/Module/Group.php:93 ../../Zotlabs/Module/Group.php:187
-msgid "Members are visible to other channels"
+#: ../../Zotlabs/Module/Achievements.php:38
+msgid "Some blurb about what to do when you're new here"
msgstr ""
-#: ../../Zotlabs/Module/Group.php:111
-msgid "Privacy group removed."
+#: ../../Zotlabs/Module/Thing.php:115
+msgid "Thing updated"
msgstr ""
-#: ../../Zotlabs/Module/Group.php:113
-msgid "Unable to remove privacy group."
+#: ../../Zotlabs/Module/Thing.php:167
+msgid "Object store: failed"
msgstr ""
-#: ../../Zotlabs/Module/Group.php:183
-msgid "Privacy group editor"
+#: ../../Zotlabs/Module/Thing.php:171
+msgid "Thing added"
msgstr ""
-#: ../../Zotlabs/Module/Group.php:199
-msgid "All Connected Channels"
+#: ../../Zotlabs/Module/Thing.php:197
+#, php-format
+msgid "OBJ: %1$s %2$s %3$s"
msgstr ""
-#: ../../Zotlabs/Module/Group.php:231
-msgid "Click on a channel to add or remove."
+#: ../../Zotlabs/Module/Thing.php:260
+msgid "Show Thing"
msgstr ""
-#: ../../Zotlabs/Module/Dreport.php:45
-msgid "Invalid message"
+#: ../../Zotlabs/Module/Thing.php:267
+msgid "item not found."
msgstr ""
-#: ../../Zotlabs/Module/Dreport.php:78
-msgid "no results"
+#: ../../Zotlabs/Module/Thing.php:300
+msgid "Edit Thing"
msgstr ""
-#: ../../Zotlabs/Module/Dreport.php:93
-msgid "channel sync processed"
+#: ../../Zotlabs/Module/Thing.php:302 ../../Zotlabs/Module/Thing.php:359
+msgid "Select a profile"
msgstr ""
-#: ../../Zotlabs/Module/Dreport.php:97
-msgid "queued"
+#: ../../Zotlabs/Module/Thing.php:306 ../../Zotlabs/Module/Thing.php:362
+msgid "Post an activity"
msgstr ""
-#: ../../Zotlabs/Module/Dreport.php:101
-msgid "posted"
+#: ../../Zotlabs/Module/Thing.php:306 ../../Zotlabs/Module/Thing.php:362
+msgid "Only sends to viewers of the applicable profile"
msgstr ""
-#: ../../Zotlabs/Module/Dreport.php:105
-msgid "accepted for delivery"
+#: ../../Zotlabs/Module/Thing.php:308 ../../Zotlabs/Module/Thing.php:364
+msgid "Name of thing e.g. something"
msgstr ""
-#: ../../Zotlabs/Module/Dreport.php:109
-msgid "updated"
+#: ../../Zotlabs/Module/Thing.php:310 ../../Zotlabs/Module/Thing.php:365
+msgid "URL of thing (optional)"
msgstr ""
-#: ../../Zotlabs/Module/Dreport.php:112
-msgid "update ignored"
+#: ../../Zotlabs/Module/Thing.php:312 ../../Zotlabs/Module/Thing.php:366
+msgid "URL for photo of thing (optional)"
msgstr ""
-#: ../../Zotlabs/Module/Dreport.php:115
-msgid "permission denied"
+#: ../../Zotlabs/Module/Thing.php:314 ../../Zotlabs/Module/Thing.php:367
+#: ../../Zotlabs/Module/Photos.php:649 ../../Zotlabs/Module/Photos.php:1018
+#: ../../Zotlabs/Module/Connedit.php:676 ../../Zotlabs/Module/Chat.php:235
+#: ../../Zotlabs/Module/Filestorage.php:142 ../../include/acl_selectors.php:218
+msgid "Permissions"
msgstr ""
-#: ../../Zotlabs/Module/Dreport.php:119
-msgid "recipient not found"
+#: ../../Zotlabs/Module/Thing.php:357
+msgid "Add Thing to your Profile"
msgstr ""
-#: ../../Zotlabs/Module/Dreport.php:122
-msgid "mail recalled"
+#: ../../Zotlabs/Module/Notify.php:61 ../../Zotlabs/Module/Notifications.php:38
+msgid "No more system notifications."
msgstr ""
-#: ../../Zotlabs/Module/Dreport.php:125
-msgid "duplicate mail received"
+#: ../../Zotlabs/Module/Notify.php:65 ../../Zotlabs/Module/Notifications.php:42
+msgid "System Notifications"
msgstr ""
-#: ../../Zotlabs/Module/Dreport.php:128
-msgid "mail delivered"
+#: ../../Zotlabs/Module/Follow.php:31
+msgid "Channel added."
msgstr ""
-#: ../../Zotlabs/Module/Dreport.php:148
+#: ../../Zotlabs/Module/Import.php:143
#, php-format
-msgid "Delivery report for %1$s"
+msgid "Your service plan only allows %d channels."
msgstr ""
-#: ../../Zotlabs/Module/Dreport.php:151
-msgid "Options"
+#: ../../Zotlabs/Module/Import.php:157
+msgid "No channel. Import failed."
msgstr ""
-#: ../../Zotlabs/Module/Dreport.php:152
-msgid "Redeliver"
+#: ../../Zotlabs/Module/Import.php:481
+#: ../../addon/diaspora/import_diaspora.php:142
+msgid "Import completed."
msgstr ""
-#: ../../Zotlabs/Module/Impel.php:41 ../../include/bbcode.php:203
-msgid "webpage"
+#: ../../Zotlabs/Module/Import.php:509
+msgid "You must be logged in to use this feature."
msgstr ""
-#: ../../Zotlabs/Module/Impel.php:46 ../../include/bbcode.php:209
-msgid "block"
+#: ../../Zotlabs/Module/Import.php:514
+msgid "Import Channel"
msgstr ""
-#: ../../Zotlabs/Module/Impel.php:51 ../../include/bbcode.php:206
-msgid "layout"
+#: ../../Zotlabs/Module/Import.php:515
+msgid ""
+"Use this form to import an existing channel from a different server/hub. You "
+"may retrieve the channel identity from the old server/hub via the network or "
+"provide an export file."
msgstr ""
-#: ../../Zotlabs/Module/Impel.php:58 ../../include/bbcode.php:212
-msgid "menu"
+#: ../../Zotlabs/Module/Import.php:517
+msgid "Or provide the old server/hub details"
msgstr ""
-#: ../../Zotlabs/Module/Impel.php:191
-#, php-format
-msgid "%s element installed"
+#: ../../Zotlabs/Module/Import.php:518
+msgid "Your old identity address (xyz@example.com)"
msgstr ""
-#: ../../Zotlabs/Module/Impel.php:194
-#, php-format
-msgid "%s element installation failed"
+#: ../../Zotlabs/Module/Import.php:519
+msgid "Your old login email address"
msgstr ""
-#: ../../Zotlabs/Module/Import_items.php:42 ../../Zotlabs/Module/Import.php:57
-msgid "Nothing to import."
+#: ../../Zotlabs/Module/Import.php:520
+msgid "Your old login password"
msgstr ""
-#: ../../Zotlabs/Module/Import_items.php:66 ../../Zotlabs/Module/Import.php:69
-#: ../../Zotlabs/Module/Import.php:84
-msgid "Unable to download data from old server"
+#: ../../Zotlabs/Module/Import.php:521
+msgid ""
+"For either option, please choose whether to make this hub your new primary "
+"address, or whether your old location should continue this role. You will be "
+"able to post from either location, but only one can be marked as the primary "
+"location for files, photos, and media."
msgstr ""
-#: ../../Zotlabs/Module/Import_items.php:72 ../../Zotlabs/Module/Import.php:91
-msgid "Imported file is empty."
+#: ../../Zotlabs/Module/Import.php:522
+msgid "Make this hub my primary location"
msgstr ""
-#: ../../Zotlabs/Module/Import_items.php:88
-#: ../../Zotlabs/Module/Import.php:111
-#, php-format
-msgid "Warning: Database versions differ by %1$d updates."
+#: ../../Zotlabs/Module/Import.php:523
+msgid "Move this channel (disable all previous locations)"
msgstr ""
-#: ../../Zotlabs/Module/Import_items.php:104
-msgid "Import completed"
+#: ../../Zotlabs/Module/Import.php:524
+msgid "Import a few months of posts if possible (limited by available memory"
msgstr ""
-#: ../../Zotlabs/Module/Import_items.php:119
-msgid "Import Items"
+#: ../../Zotlabs/Module/Import.php:525
+msgid ""
+"This process may take several minutes to complete. Please submit the form "
+"only once and leave this page open until finished."
msgstr ""
-#: ../../Zotlabs/Module/Import_items.php:120
-msgid "Use this form to import existing posts and content from an export file."
+#: ../../Zotlabs/Module/Rmagic.php:35
+msgid "Authentication failed."
msgstr ""
-#: ../../Zotlabs/Module/Import_items.php:121
-#: ../../Zotlabs/Module/Import.php:495
-msgid "File to Upload"
+#: ../../Zotlabs/Module/Rmagic.php:75 ../../boot.php:1640
+#: ../../include/channel.php:2204
+msgid "Remote Authentication"
msgstr ""
-#: ../../Zotlabs/Module/Manage.php:136
-#: ../../Zotlabs/Module/New_channel.php:121
-#, php-format
-msgid "You have created %1$.0f of %2$.0f allowed channels."
+#: ../../Zotlabs/Module/Rmagic.php:76 ../../include/channel.php:2205
+msgid "Enter your channel address (e.g. channel@example.com)"
msgstr ""
-#: ../../Zotlabs/Module/Manage.php:143
-msgid "Create a new channel"
+#: ../../Zotlabs/Module/Rmagic.php:77 ../../include/channel.php:2206
+msgid "Authenticate"
msgstr ""
-#: ../../Zotlabs/Module/Manage.php:143 ../../Zotlabs/Module/Profiles.php:813
-#: ../../Zotlabs/Module/Wiki.php:166 ../../Zotlabs/Module/Chat.php:255
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:152
-msgid "Create New"
+#: ../../Zotlabs/Module/Cal.php:62 ../../Zotlabs/Module/Chanview.php:96
+#: ../../Zotlabs/Module/Page.php:75 ../../Zotlabs/Module/Wall_upload.php:31
+#: ../../Zotlabs/Module/Block.php:41 ../../Zotlabs/Module/Card_edit.php:44
+msgid "Channel not found."
msgstr ""
-#: ../../Zotlabs/Module/Manage.php:164 ../../Zotlabs/Lib/Apps.php:221
-#: ../../include/nav.php:223
-msgid "Channel Manager"
+#: ../../Zotlabs/Module/Cal.php:69
+msgid "Permissions denied."
msgstr ""
-#: ../../Zotlabs/Module/Manage.php:165
-msgid "Current Channel"
+#: ../../Zotlabs/Module/Cal.php:342 ../../include/text.php:2312
+msgid "Import"
msgstr ""
-#: ../../Zotlabs/Module/Manage.php:167
-msgid "Switch to one of your channels by selecting it."
+#: ../../Zotlabs/Module/Api.php:72 ../../Zotlabs/Module/Api.php:93
+msgid "Authorize application connection"
msgstr ""
-#: ../../Zotlabs/Module/Manage.php:168
-msgid "Default Channel"
+#: ../../Zotlabs/Module/Api.php:73
+msgid "Return to your app and insert this Security Code:"
msgstr ""
-#: ../../Zotlabs/Module/Manage.php:169
-msgid "Make Default"
+#: ../../Zotlabs/Module/Api.php:83
+msgid "Please login to continue."
msgstr ""
-#: ../../Zotlabs/Module/Manage.php:172
-#, php-format
-msgid "%d new messages"
+#: ../../Zotlabs/Module/Api.php:95
+msgid ""
+"Do you want to authorize this application to access your posts and contacts, "
+"and/or create new posts for you?"
msgstr ""
-#: ../../Zotlabs/Module/Manage.php:173
-#, php-format
-msgid "%d new introductions"
+#: ../../Zotlabs/Module/Attach.php:13
+msgid "Item not available."
msgstr ""
-#: ../../Zotlabs/Module/Manage.php:175
-msgid "Delegated Channel"
+#: ../../Zotlabs/Module/Editblock.php:116 ../../Zotlabs/Module/Chat.php:207
+#: ../../Zotlabs/Module/Editwebpage.php:143 ../../Zotlabs/Module/Mail.php:288
+#: ../../Zotlabs/Module/Mail.php:430 ../../Zotlabs/Module/Card_edit.php:101
+#: ../../include/conversation.php:1261
+msgid "Insert web link"
+msgstr ""
+
+#: ../../Zotlabs/Module/Editblock.php:129
+#: ../../Zotlabs/Module/Card_edit.php:117 ../../include/conversation.php:1381
+msgid "Title (optional)"
+msgstr ""
+
+#: ../../Zotlabs/Module/Editblock.php:138
+msgid "Edit Block"
+msgstr ""
+
+#: ../../Zotlabs/Module/Profile.php:93
+msgid "vcard"
+msgstr ""
+
+#: ../../Zotlabs/Module/Apps.php:47 ../../Zotlabs/Lib/Apps.php:223
+msgid "Apps"
+msgstr ""
+
+#: ../../Zotlabs/Module/Apps.php:50
+msgid "Manage apps"
msgstr ""
-#: ../../Zotlabs/Module/Import.php:134
+#: ../../Zotlabs/Module/Apps.php:51
+msgid "Create new app"
+msgstr ""
+
+#: ../../Zotlabs/Module/Mood.php:67 ../../include/conversation.php:256
#, php-format
-msgid "Your service plan only allows %d channels."
+msgctxt "mood"
+msgid "%1$s is %2$s"
msgstr ""
-#: ../../Zotlabs/Module/Import.php:149
-msgid "No channel. Import failed."
+#: ../../Zotlabs/Module/Mood.php:135 ../../Zotlabs/Lib/Apps.php:247
+msgid "Mood"
msgstr ""
-#: ../../Zotlabs/Module/Import.php:467
-#: ../../extend/addon/addon/diaspora/import_diaspora.php:142
-msgid "Import completed."
+#: ../../Zotlabs/Module/Mood.php:136
+msgid "Set your current mood and tell your friends"
msgstr ""
-#: ../../Zotlabs/Module/Import.php:488
-msgid "You must be logged in to use this feature."
+#: ../../Zotlabs/Module/Connections.php:54
+#: ../../Zotlabs/Module/Connections.php:156
+#: ../../Zotlabs/Module/Connections.php:245
+msgid "Blocked"
msgstr ""
-#: ../../Zotlabs/Module/Import.php:493
-msgid "Import Channel"
+#: ../../Zotlabs/Module/Connections.php:59
+#: ../../Zotlabs/Module/Connections.php:163
+#: ../../Zotlabs/Module/Connections.php:244
+msgid "Ignored"
msgstr ""
-#: ../../Zotlabs/Module/Import.php:494
-msgid ""
-"Use this form to import an existing channel from a different server/hub. You "
-"may retrieve the channel identity from the old server/hub via the network or "
-"provide an export file."
+#: ../../Zotlabs/Module/Connections.php:64
+#: ../../Zotlabs/Module/Connections.php:177
+#: ../../Zotlabs/Module/Connections.php:243
+msgid "Hidden"
msgstr ""
-#: ../../Zotlabs/Module/Import.php:496
-msgid "Or provide the old server/hub details"
+#: ../../Zotlabs/Module/Connections.php:69
+#: ../../Zotlabs/Module/Connections.php:170
+msgid "Archived/Unreachable"
msgstr ""
-#: ../../Zotlabs/Module/Import.php:497
-msgid "Your old identity address (xyz@example.com)"
+#: ../../Zotlabs/Module/Connections.php:74
+#: ../../Zotlabs/Module/Connections.php:83 ../../Zotlabs/Module/Menu.php:116
+#: ../../include/conversation.php:1697
+msgid "New"
msgstr ""
-#: ../../Zotlabs/Module/Import.php:498
-msgid "Your old login email address"
+#: ../../Zotlabs/Module/Connections.php:88
+#: ../../Zotlabs/Module/Connections.php:102
+#: ../../Zotlabs/Module/Connedit.php:713 ../../Zotlabs/Widget/Affinity.php:30
+msgid "All"
msgstr ""
-#: ../../Zotlabs/Module/Import.php:499
-msgid "Your old login password"
+#: ../../Zotlabs/Module/Connections.php:133
+#: ../../Zotlabs/Widget/Notifications.php:80
+msgid "New Connections"
msgstr ""
-#: ../../Zotlabs/Module/Import.php:500
-msgid ""
-"For either option, please choose whether to make this hub your new primary "
-"address, or whether your old location should continue this role. You will be "
-"able to post from either location, but only one can be marked as the primary "
-"location for files, photos, and media."
+#: ../../Zotlabs/Module/Connections.php:136
+msgid "Show pending (new) connections"
msgstr ""
-#: ../../Zotlabs/Module/Import.php:501
-msgid "Make this hub my primary location"
+#: ../../Zotlabs/Module/Connections.php:143
+msgid "Show all connections"
msgstr ""
-#: ../../Zotlabs/Module/Import.php:502
-msgid "Move this channel (disable all previous locations)"
+#: ../../Zotlabs/Module/Connections.php:159
+msgid "Only show blocked connections"
msgstr ""
-#: ../../Zotlabs/Module/Import.php:503
-msgid "Import a few months of posts if possible (limited by available memory"
+#: ../../Zotlabs/Module/Connections.php:166
+msgid "Only show ignored connections"
msgstr ""
-#: ../../Zotlabs/Module/Import.php:504
-msgid ""
-"This process may take several minutes to complete. Please submit the form "
-"only once and leave this page open until finished."
+#: ../../Zotlabs/Module/Connections.php:173
+msgid "Only show archived/unreachable connections"
msgstr ""
-#: ../../Zotlabs/Module/Lockview.php:75
-msgid "Remote privacy information not available."
+#: ../../Zotlabs/Module/Connections.php:180
+msgid "Only show hidden connections"
msgstr ""
-#: ../../Zotlabs/Module/Lockview.php:96
-msgid "Visible to:"
+#: ../../Zotlabs/Module/Connections.php:241
+msgid "Pending approval"
msgstr ""
-#: ../../Zotlabs/Module/Magic.php:71
-msgid "Hub not found."
+#: ../../Zotlabs/Module/Connections.php:242
+msgid "Archived"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:52
-msgid "Unable to create element."
+#: ../../Zotlabs/Module/Connections.php:246
+msgid "Not connected at this location"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:76
-msgid "Unable to update menu element."
+#: ../../Zotlabs/Module/Connections.php:258
+#, php-format
+msgid "%1$s [%2$s]"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:92
-msgid "Unable to add menu element."
+#: ../../Zotlabs/Module/Connections.php:259
+msgid "Edit connection"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:153 ../../Zotlabs/Module/Mitem.php:230
-msgid "Menu Item Permissions"
+#: ../../Zotlabs/Module/Connections.php:261
+msgid "Delete connection"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:154 ../../Zotlabs/Module/Mitem.php:231
-#: ../../Zotlabs/Module/Settings/Channel.php:494
-msgid "(click to open/close)"
+#: ../../Zotlabs/Module/Connections.php:270
+msgid "Channel address"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:160 ../../Zotlabs/Module/Mitem.php:176
-msgid "Link Name"
+#: ../../Zotlabs/Module/Connections.php:272
+msgid "Network"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:161 ../../Zotlabs/Module/Mitem.php:239
-msgid "Link or Submenu Target"
+#: ../../Zotlabs/Module/Connections.php:275
+msgid "Call"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:161
-msgid "Enter URL of the link or select a menu name to create a submenu"
+#: ../../Zotlabs/Module/Connections.php:277
+msgid "Status"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:162 ../../Zotlabs/Module/Mitem.php:240
-msgid "Use magic-auth if available"
+#: ../../Zotlabs/Module/Connections.php:279
+msgid "Connected"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:163 ../../Zotlabs/Module/Mitem.php:241
-msgid "Open link in new window"
+#: ../../Zotlabs/Module/Connections.php:281
+msgid "Approve connection"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:164 ../../Zotlabs/Module/Mitem.php:242
-msgid "Order in list"
+#: ../../Zotlabs/Module/Connections.php:283
+msgid "Ignore connection"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:164 ../../Zotlabs/Module/Mitem.php:242
-msgid "Higher numbers will sink to bottom of listing"
+#: ../../Zotlabs/Module/Connections.php:284
+#: ../../Zotlabs/Module/Connedit.php:630
+msgid "Ignore"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:165
-msgid "Submit and finish"
+#: ../../Zotlabs/Module/Connections.php:285
+msgid "Recent activity"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:166
-msgid "Submit and continue"
+#: ../../Zotlabs/Module/Connections.php:309 ../../Zotlabs/Lib/Apps.php:229
+#: ../../include/text.php:959 ../../include/nav.php:107
+msgid "Connections"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:174
-msgid "Menu:"
+#: ../../Zotlabs/Module/Connections.php:314
+msgid "Search your connections"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:177
-msgid "Link Target"
+#: ../../Zotlabs/Module/Connections.php:315
+msgid "Connections search"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:180
-msgid "Edit menu"
+#: ../../Zotlabs/Module/Connections.php:316
+#: ../../Zotlabs/Module/Directory.php:391
+#: ../../Zotlabs/Module/Directory.php:396 ../../include/contact_widgets.php:23
+msgid "Find"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:183
-msgid "Edit element"
+#: ../../Zotlabs/Module/Viewsrc.php:43
+msgid "item"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:184
-msgid "Drop element"
+#: ../../Zotlabs/Module/Viewsrc.php:55
+msgid "Source of Item"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:185
-msgid "New element"
+#: ../../Zotlabs/Module/Bookmarks.php:56
+msgid "Bookmark added"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:186
-msgid "Edit this menu container"
+#: ../../Zotlabs/Module/Bookmarks.php:79
+msgid "My Bookmarks"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:187
-msgid "Add menu element"
+#: ../../Zotlabs/Module/Bookmarks.php:90
+msgid "My Connections Bookmarks"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:188
-msgid "Delete this menu item"
+#: ../../Zotlabs/Module/Removeaccount.php:35
+msgid ""
+"Account removals are not allowed within 48 hours of changing the account "
+"password."
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:189
-msgid "Edit this menu item"
+#: ../../Zotlabs/Module/Removeaccount.php:57
+msgid "Remove This Account"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:206
-msgid "Menu item not found."
+#: ../../Zotlabs/Module/Removeaccount.php:58
+msgid ""
+"This account and all its channels will be completely removed from the "
+"network. "
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:219
-msgid "Menu item deleted."
+#: ../../Zotlabs/Module/Removeaccount.php:60
+msgid ""
+"Remove this account, all its channels and all its channel clones from the "
+"network"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:221
-msgid "Menu item could not be deleted."
+#: ../../Zotlabs/Module/Removeaccount.php:60
+msgid ""
+"By default only the instances of the channels located on this hub will be "
+"removed from the network"
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:228
-msgid "Edit Menu Element"
+#: ../../Zotlabs/Module/Photos.php:78
+msgid "Page owner information could not be retrieved."
msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:238
-msgid "Link text"
+#: ../../Zotlabs/Module/Photos.php:94 ../../Zotlabs/Module/Photos.php:120
+msgid "Album not found."
msgstr ""
-#: ../../Zotlabs/Module/Appman.php:38 ../../Zotlabs/Module/Appman.php:54
-msgid "App installed."
+#: ../../Zotlabs/Module/Photos.php:103
+msgid "Delete Album"
msgstr ""
-#: ../../Zotlabs/Module/Appman.php:47
-msgid "Malformed app."
+#: ../../Zotlabs/Module/Photos.php:174 ../../Zotlabs/Module/Photos.php:1030
+msgid "Delete Photo"
msgstr ""
-#: ../../Zotlabs/Module/Appman.php:110
-msgid "Embed code"
+#: ../../Zotlabs/Module/Photos.php:501
+msgid "No photos selected"
msgstr ""
-#: ../../Zotlabs/Module/Appman.php:116
-msgid "Edit App"
+#: ../../Zotlabs/Module/Photos.php:550
+msgid "Access to this item is restricted."
msgstr ""
-#: ../../Zotlabs/Module/Appman.php:116
-msgid "Create App"
+#: ../../Zotlabs/Module/Photos.php:593
+#, php-format
+msgid "%1$.2f MB of %2$.2f MB photo storage used."
msgstr ""
-#: ../../Zotlabs/Module/Appman.php:121
-msgid "Name of app"
+#: ../../Zotlabs/Module/Photos.php:596
+#, php-format
+msgid "%1$.2f MB photo storage used."
msgstr ""
-#: ../../Zotlabs/Module/Appman.php:121 ../../Zotlabs/Module/Appman.php:122
-#: ../../Zotlabs/Module/Profiles.php:744 ../../Zotlabs/Module/Profiles.php:748
-#: ../../Zotlabs/Module/Events.php:460 ../../Zotlabs/Module/Events.php:465
-#: ../../include/datetime.php:259
-msgid "Required"
+#: ../../Zotlabs/Module/Photos.php:638
+msgid "Upload Photos"
msgstr ""
-#: ../../Zotlabs/Module/Appman.php:122
-msgid "Location (URL) of app"
+#: ../../Zotlabs/Module/Photos.php:642
+msgid "Enter an album name"
msgstr ""
-#: ../../Zotlabs/Module/Appman.php:123 ../../Zotlabs/Module/Events.php:473
-#: ../../Zotlabs/Module/Rbmark.php:101
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:838
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:173
-msgid "Description"
+#: ../../Zotlabs/Module/Photos.php:643
+msgid "or select an existing album (doubleclick)"
msgstr ""
-#: ../../Zotlabs/Module/Appman.php:124
-msgid "Photo icon URL"
+#: ../../Zotlabs/Module/Photos.php:644
+msgid "Create a status post for this upload"
msgstr ""
-#: ../../Zotlabs/Module/Appman.php:124
-msgid "80 x 80 pixels - optional"
+#: ../../Zotlabs/Module/Photos.php:645
+msgid "Caption (optional):"
msgstr ""
-#: ../../Zotlabs/Module/Appman.php:125
-msgid "Categories (optional, comma separated list)"
+#: ../../Zotlabs/Module/Photos.php:646
+msgid "Description (optional):"
msgstr ""
-#: ../../Zotlabs/Module/Appman.php:126
-msgid "Version ID"
+#: ../../Zotlabs/Module/Photos.php:732
+msgid "Show Newest First"
msgstr ""
-#: ../../Zotlabs/Module/Appman.php:127
-msgid "Price of app"
+#: ../../Zotlabs/Module/Photos.php:734
+msgid "Show Oldest First"
msgstr ""
-#: ../../Zotlabs/Module/Appman.php:128
-msgid "Location (URL) to purchase app"
+#: ../../Zotlabs/Module/Photos.php:839
+msgid "Permission denied. Access to this item may be restricted."
msgstr ""
-#: ../../Zotlabs/Module/Ratings.php:70
-msgid "No ratings"
+#: ../../Zotlabs/Module/Photos.php:841
+msgid "Photo not available"
msgstr ""
-#: ../../Zotlabs/Module/Ratings.php:98
-msgid "Rating: "
+#: ../../Zotlabs/Module/Photos.php:899
+msgid "Use as profile photo"
msgstr ""
-#: ../../Zotlabs/Module/Ratings.php:99
-msgid "Website: "
+#: ../../Zotlabs/Module/Photos.php:900
+msgid "Use as cover photo"
msgstr ""
-#: ../../Zotlabs/Module/Ratings.php:101
-msgid "Description: "
+#: ../../Zotlabs/Module/Photos.php:907
+msgid "Private Photo"
msgstr ""
-#: ../../Zotlabs/Module/Attach.php:13
-msgid "Item not available."
+#: ../../Zotlabs/Module/Photos.php:922
+msgid "View Full Size"
msgstr ""
-#: ../../Zotlabs/Module/Mood.php:67 ../../include/conversation.php:260
-#, php-format
-msgctxt "mood"
-msgid "%1$s is %2$s"
+#: ../../Zotlabs/Module/Photos.php:1004
+msgid "Edit photo"
msgstr ""
-#: ../../Zotlabs/Module/Mood.php:135 ../../Zotlabs/Lib/Apps.php:234
-msgid "Mood"
+#: ../../Zotlabs/Module/Photos.php:1006
+msgid "Rotate CW (right)"
msgstr ""
-#: ../../Zotlabs/Module/Mood.php:136
-msgid "Set your current mood and tell your friends"
+#: ../../Zotlabs/Module/Photos.php:1007
+msgid "Rotate CCW (left)"
msgstr ""
-#: ../../Zotlabs/Module/Notify.php:57
-#: ../../Zotlabs/Module/Notifications.php:38
-msgid "No more system notifications."
+#: ../../Zotlabs/Module/Photos.php:1010
+msgid "Move photo to album"
msgstr ""
-#: ../../Zotlabs/Module/Notify.php:61
-#: ../../Zotlabs/Module/Notifications.php:42
-msgid "System Notifications"
+#: ../../Zotlabs/Module/Photos.php:1011
+msgid "Enter a new album name"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:24 ../../Zotlabs/Module/Profiles.php:184
-#: ../../Zotlabs/Module/Profiles.php:241 ../../Zotlabs/Module/Profiles.php:660
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:62
-msgid "Profile not found."
+#: ../../Zotlabs/Module/Photos.php:1012
+msgid "or select an existing one (doubleclick)"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:44
-msgid "Profile deleted."
+#: ../../Zotlabs/Module/Photos.php:1015
+msgid "Caption"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:68 ../../Zotlabs/Module/Profiles.php:105
-msgid "Profile-"
+#: ../../Zotlabs/Module/Photos.php:1017
+msgid "Add a Tag"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:90 ../../Zotlabs/Module/Profiles.php:127
-msgid "New profile created."
+#: ../../Zotlabs/Module/Photos.php:1025
+msgid "Example: @bob, @Barbara_Jensen, @jim@example.com"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:111
-msgid "Profile unavailable to clone."
+#: ../../Zotlabs/Module/Photos.php:1028
+msgid "Flag as adult in album view"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:146
-msgid "Profile unavailable to export."
+#: ../../Zotlabs/Module/Photos.php:1047 ../../Zotlabs/Lib/ThreadItem.php:271
+msgid "I like this (toggle)"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:252
-msgid "Profile Name is required."
+#: ../../Zotlabs/Module/Photos.php:1048 ../../Zotlabs/Lib/ThreadItem.php:272
+msgid "I don't like this (toggle)"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:460
-msgid "Marital Status"
+#: ../../Zotlabs/Module/Photos.php:1050 ../../Zotlabs/Lib/ThreadItem.php:416
+#: ../../include/conversation.php:768
+msgid "Please wait"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:464
-msgid "Romantic Partner"
+#: ../../Zotlabs/Module/Photos.php:1066 ../../Zotlabs/Module/Photos.php:1184
+#: ../../Zotlabs/Lib/ThreadItem.php:740
+msgid "This is you"
+msgstr ""
+
+#: ../../Zotlabs/Module/Photos.php:1068 ../../Zotlabs/Module/Photos.php:1186
+#: ../../Zotlabs/Lib/ThreadItem.php:742 ../../include/js_strings.php:6
+msgid "Comment"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:468 ../../Zotlabs/Module/Profiles.php:771
+#: ../../Zotlabs/Module/Photos.php:1084 ../../include/conversation.php:594
+msgctxt "title"
msgid "Likes"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:472 ../../Zotlabs/Module/Profiles.php:772
+#: ../../Zotlabs/Module/Photos.php:1084 ../../include/conversation.php:594
+msgctxt "title"
msgid "Dislikes"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:476 ../../Zotlabs/Module/Profiles.php:779
-msgid "Work/Employment"
+#: ../../Zotlabs/Module/Photos.php:1085 ../../include/conversation.php:595
+msgctxt "title"
+msgid "Agree"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:479
-msgid "Religion"
+#: ../../Zotlabs/Module/Photos.php:1085 ../../include/conversation.php:595
+msgctxt "title"
+msgid "Disagree"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:483
-msgid "Political Views"
+#: ../../Zotlabs/Module/Photos.php:1085 ../../include/conversation.php:595
+msgctxt "title"
+msgid "Abstain"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:487
-#: ../../extend/addon/addon/openid/MysqlProvider.php:74
-msgid "Gender"
+#: ../../Zotlabs/Module/Photos.php:1086 ../../include/conversation.php:596
+msgctxt "title"
+msgid "Attending"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:491
-msgid "Sexual Preference"
+#: ../../Zotlabs/Module/Photos.php:1086 ../../include/conversation.php:596
+msgctxt "title"
+msgid "Not attending"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:495
-msgid "Homepage"
+#: ../../Zotlabs/Module/Photos.php:1086 ../../include/conversation.php:596
+msgctxt "title"
+msgid "Might attend"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:499
-msgid "Interests"
+#: ../../Zotlabs/Module/Photos.php:1103 ../../Zotlabs/Module/Photos.php:1115
+#: ../../Zotlabs/Lib/ThreadItem.php:191 ../../Zotlabs/Lib/ThreadItem.php:203
+msgid "View all"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:595
-msgid "Profile updated."
-msgstr ""
+#: ../../Zotlabs/Module/Photos.php:1107 ../../Zotlabs/Lib/ThreadItem.php:195
+#: ../../include/conversation.php:1950 ../../include/channel.php:1491
+#: ../../include/taxonomy.php:520
+msgctxt "noun"
+msgid "Like"
+msgid_plural "Likes"
+msgstr[0] ""
+msgstr[1] ""
-#: ../../Zotlabs/Module/Profiles.php:679
-msgid "Hide your connections list from viewers of this profile"
-msgstr ""
+#: ../../Zotlabs/Module/Photos.php:1112 ../../Zotlabs/Lib/ThreadItem.php:200
+#: ../../include/conversation.php:1953
+msgctxt "noun"
+msgid "Dislike"
+msgid_plural "Dislikes"
+msgstr[0] ""
+msgstr[1] ""
-#: ../../Zotlabs/Module/Profiles.php:721
-msgid "Edit Profile Details"
+#: ../../Zotlabs/Module/Photos.php:1212
+msgid "Photo Tools"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:723
-msgid "View this profile"
+#: ../../Zotlabs/Module/Photos.php:1221
+msgid "In This Photo:"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:724 ../../Zotlabs/Module/Profiles.php:806
-#: ../../include/channel.php:1066
-msgid "Edit visibility"
+#: ../../Zotlabs/Module/Photos.php:1226
+msgid "Map"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:725
-msgid "Profile Tools"
+#: ../../Zotlabs/Module/Photos.php:1234 ../../Zotlabs/Lib/ThreadItem.php:404
+msgctxt "noun"
+msgid "Likes"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:726
-msgid "Change cover photo"
+#: ../../Zotlabs/Module/Photos.php:1235 ../../Zotlabs/Lib/ThreadItem.php:405
+msgctxt "noun"
+msgid "Dislikes"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:727 ../../include/channel.php:1037
-msgid "Change profile photo"
+#: ../../Zotlabs/Module/Photos.php:1240 ../../Zotlabs/Lib/ThreadItem.php:410
+#: ../../include/acl_selectors.php:220
+msgid "Close"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:728
-msgid "Create a new profile using these settings"
+#: ../../Zotlabs/Module/Photos.php:1312 ../../Zotlabs/Module/Photos.php:1325
+#: ../../Zotlabs/Module/Photos.php:1326 ../../include/photos.php:601
+msgid "Recent Photos"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:729
-msgid "Clone this profile"
+#: ../../Zotlabs/Module/Wiki.php:30
+msgid "Profile Unavailable."
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:730
-msgid "Delete this profile"
+#: ../../Zotlabs/Module/Wiki.php:44 ../../addon/gitwiki/Mod_Gitwiki.php:42
+msgid "Not found"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:731
-msgid "Add profile things"
+#: ../../Zotlabs/Module/Wiki.php:68 ../../addon/gitwiki/Mod_Gitwiki.php:62
+msgid "Invalid channel"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:732 ../../include/conversation.php:1715
-#: ../../include/widgets.php:105
-msgid "Personal"
+#: ../../Zotlabs/Module/Wiki.php:124 ../../addon/gitwiki/Mod_Gitwiki.php:107
+msgid "Error retrieving wiki"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:734
-msgid "Relation"
+#: ../../Zotlabs/Module/Wiki.php:131 ../../addon/gitwiki/Mod_Gitwiki.php:114
+msgid "Error creating zip file export folder"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:735 ../../include/datetime.php:55
-msgid "Miscellaneous"
+#: ../../Zotlabs/Module/Wiki.php:182 ../../addon/gitwiki/Mod_Gitwiki.php:132
+msgid "Error downloading wiki: "
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:737
-msgid "Import profile from file"
+#: ../../Zotlabs/Module/Wiki.php:197 ../../addon/gitwiki/Mod_Gitwiki.php:146
+#: ../../include/conversation.php:1897 ../../include/nav.php:504
+msgid "Wikis"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:738
-msgid "Export profile to file"
+#: ../../Zotlabs/Module/Wiki.php:203 ../../addon/gitwiki/Mod_Gitwiki.php:152
+msgid "Download"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:739
-msgid "Your gender"
+#: ../../Zotlabs/Module/Wiki.php:205 ../../Zotlabs/Module/Chat.php:256
+#: ../../Zotlabs/Module/Profiles.php:834 ../../Zotlabs/Module/Manage.php:145
+#: ../../addon/gitwiki/Mod_Gitwiki.php:154
+msgid "Create New"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:740
-msgid "Marital status"
+#: ../../Zotlabs/Module/Wiki.php:207 ../../addon/gitwiki/Mod_Gitwiki.php:156
+msgid "Wiki name"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:741
-msgid "Sexual preference"
+#: ../../Zotlabs/Module/Wiki.php:208 ../../addon/gitwiki/Mod_Gitwiki.php:157
+msgid "Content type"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:744
-msgid "Profile name"
+#: ../../Zotlabs/Module/Wiki.php:208 ../../Zotlabs/Module/Wiki.php:336
+#: ../../Zotlabs/Widget/Wiki_pages.php:57 ../../include/text.php:1802
+msgid "Markdown"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:746
-msgid "This is your default profile."
+#: ../../Zotlabs/Module/Wiki.php:208 ../../Zotlabs/Module/Wiki.php:336
+#: ../../Zotlabs/Widget/Wiki_pages.php:57 ../../include/text.php:1800
+msgid "BBcode"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:748
-msgid "Your full name"
+#: ../../Zotlabs/Module/Wiki.php:208 ../../Zotlabs/Widget/Wiki_pages.php:57
+#: ../../include/text.php:1803
+msgid "Text"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:749
-msgid "Title/Description"
+#: ../../Zotlabs/Module/Wiki.php:210 ../../Zotlabs/Storage/Browser.php:235
+#: ../../addon/gitwiki/Mod_Gitwiki.php:159
+msgid "Type"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:752
-msgid "Street address"
+#: ../../Zotlabs/Module/Wiki.php:211
+msgid "Any&nbsp;type"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:753
-msgid "Locality/City"
+#: ../../Zotlabs/Module/Wiki.php:218
+msgid "Lock content type"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:754
-msgid "Region/State"
+#: ../../Zotlabs/Module/Wiki.php:219 ../../addon/gitwiki/Mod_Gitwiki.php:166
+msgid "Create a status post for this wiki"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:755
-msgid "Postal/Zip code"
+#: ../../Zotlabs/Module/Wiki.php:220
+msgid "Edit Wiki Name"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:761
-msgid "Who (if applicable)"
+#: ../../Zotlabs/Module/Wiki.php:262 ../../addon/gitwiki/Mod_Gitwiki.php:185
+msgid "Wiki not found"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:761
-msgid "Examples: cathy123, Cathy Williams, cathy@example.com"
+#: ../../Zotlabs/Module/Wiki.php:286 ../../addon/gitwiki/Mod_Gitwiki.php:210
+msgid "Rename page"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:762
-msgid "Since (date)"
+#: ../../Zotlabs/Module/Wiki.php:296 ../../addon/gitwiki/Mod_Gitwiki.php:214
+msgid "Error retrieving page content"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:765
-msgid "Tell us about yourself"
+#: ../../Zotlabs/Module/Wiki.php:302 ../../Zotlabs/Module/Wiki.php:304
+msgid "New page"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:766
-#: ../../extend/addon/addon/openid/MysqlProvider.php:68
-msgid "Homepage URL"
+#: ../../Zotlabs/Module/Wiki.php:331 ../../addon/gitwiki/Mod_Gitwiki.php:242
+msgid "Revision Comparison"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:767
-msgid "Hometown"
+#: ../../Zotlabs/Module/Wiki.php:332 ../../addon/gitwiki/Mod_Gitwiki.php:243
+msgid "Revert"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:768
-msgid "Political views"
+#: ../../Zotlabs/Module/Wiki.php:339
+msgid "Short description of your changes (optional)"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:769
-msgid "Religious views"
+#: ../../Zotlabs/Module/Wiki.php:346 ../../addon/gitwiki/Mod_Gitwiki.php:252
+msgid "Source"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:770
-msgid "Keywords used in directory listings"
+#: ../../Zotlabs/Module/Wiki.php:356 ../../addon/gitwiki/Mod_Gitwiki.php:260
+msgid "New page name"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:770
-msgid "Example: fishing photography software"
+#: ../../Zotlabs/Module/Wiki.php:361 ../../addon/gitwiki/Mod_Gitwiki.php:265
+#: ../../include/conversation.php:1265
+msgid "Embed image from photo albums"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:773
-msgid "Musical interests"
+#: ../../Zotlabs/Module/Wiki.php:362 ../../addon/gitwiki/Mod_Gitwiki.php:266
+#: ../../include/conversation.php:1368
+msgid "Embed an image from your albums"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:774
-msgid "Books, literature"
+#: ../../Zotlabs/Module/Wiki.php:364 ../../addon/gitwiki/Mod_Gitwiki.php:268
+#: ../../include/conversation.php:1370 ../../include/conversation.php:1417
+msgid "OK"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:775
-msgid "Television"
+#: ../../Zotlabs/Module/Wiki.php:365 ../../addon/gitwiki/Mod_Gitwiki.php:269
+#: ../../include/conversation.php:1301
+msgid "Choose images to embed"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:776
-msgid "Film/Dance/Culture/Entertainment"
+#: ../../Zotlabs/Module/Wiki.php:366 ../../addon/gitwiki/Mod_Gitwiki.php:270
+#: ../../include/conversation.php:1302
+msgid "Choose an album"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:777
-msgid "Hobbies/Interests"
+#: ../../Zotlabs/Module/Wiki.php:367 ../../addon/gitwiki/Mod_Gitwiki.php:271
+msgid "Choose a different album"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:778
-msgid "Love/Romance"
+#: ../../Zotlabs/Module/Wiki.php:368 ../../addon/gitwiki/Mod_Gitwiki.php:272
+#: ../../include/conversation.php:1304
+msgid "Error getting album list"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:780
-msgid "School/Education"
+#: ../../Zotlabs/Module/Wiki.php:369 ../../addon/gitwiki/Mod_Gitwiki.php:273
+#: ../../include/conversation.php:1305
+msgid "Error getting photo link"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:781
-msgid "Contact information and social networks"
+#: ../../Zotlabs/Module/Wiki.php:370 ../../addon/gitwiki/Mod_Gitwiki.php:274
+#: ../../include/conversation.php:1306
+msgid "Error getting album"
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:782
-msgid "My other channels"
+#: ../../Zotlabs/Module/Wiki.php:442 ../../addon/gitwiki/Mod_Gitwiki.php:337
+msgid "Error creating wiki. Invalid name."
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:802 ../../include/channel.php:1062
-msgid "Profile Image"
+#: ../../Zotlabs/Module/Wiki.php:449
+msgid "A wiki with this name already exists."
msgstr ""
-#: ../../Zotlabs/Module/Profiles.php:812 ../../include/channel.php:1044
-#: ../../include/nav.php:105
-msgid "Edit Profiles"
+#: ../../Zotlabs/Module/Wiki.php:462 ../../addon/gitwiki/Mod_Gitwiki.php:348
+msgid "Wiki created, but error creating Home page."
msgstr ""
-#: ../../Zotlabs/Module/Api.php:72 ../../Zotlabs/Module/Api.php:93
-msgid "Authorize application connection"
+#: ../../Zotlabs/Module/Wiki.php:469 ../../addon/gitwiki/Mod_Gitwiki.php:353
+msgid "Error creating wiki"
msgstr ""
-#: ../../Zotlabs/Module/Api.php:73
-msgid "Return to your app and insert this Security Code:"
+#: ../../Zotlabs/Module/Wiki.php:492
+msgid "Error updating wiki. Invalid name."
msgstr ""
-#: ../../Zotlabs/Module/Api.php:83
-msgid "Please login to continue."
+#: ../../Zotlabs/Module/Wiki.php:512
+msgid "Error updating wiki"
msgstr ""
-#: ../../Zotlabs/Module/Api.php:95
-msgid ""
-"Do you want to authorize this application to access your posts and contacts, "
-"and/or create new posts for you?"
+#: ../../Zotlabs/Module/Wiki.php:527
+msgid "Wiki delete permission denied."
msgstr ""
-#: ../../Zotlabs/Module/Invite.php:29
-msgid "Total invitation limit exceeded."
+#: ../../Zotlabs/Module/Wiki.php:537
+msgid "Error deleting wiki"
msgstr ""
-#: ../../Zotlabs/Module/Invite.php:53
-#, php-format
-msgid "%s : Not a valid email address."
+#: ../../Zotlabs/Module/Wiki.php:565 ../../addon/gitwiki/Mod_Gitwiki.php:400
+msgid "New page created"
msgstr ""
-#: ../../Zotlabs/Module/Invite.php:67
-msgid "Please join us on $Projectname"
+#: ../../Zotlabs/Module/Wiki.php:686
+msgid "Cannot delete Home"
msgstr ""
-#: ../../Zotlabs/Module/Invite.php:77
-msgid "Invitation limit exceeded. Please contact your site administrator."
+#: ../../Zotlabs/Module/Wiki.php:750
+msgid "Current Revision"
msgstr ""
-#: ../../Zotlabs/Module/Invite.php:82
-#, php-format
-msgid "%s : Message delivery failed."
+#: ../../Zotlabs/Module/Wiki.php:750
+msgid "Selected Revision"
msgstr ""
-#: ../../Zotlabs/Module/Invite.php:86
-#, php-format
-msgid "%d message sent."
-msgid_plural "%d messages sent."
-msgstr[0] ""
-msgstr[1] ""
+#: ../../Zotlabs/Module/Wiki.php:800
+msgid "You must be authenticated."
+msgstr ""
-#: ../../Zotlabs/Module/Invite.php:105
-msgid "You have no more invitations available"
+#: ../../Zotlabs/Module/Chanview.php:139
+msgid "toggle full screen mode"
msgstr ""
-#: ../../Zotlabs/Module/Invite.php:136
-msgid "Send invitations"
+#: ../../Zotlabs/Module/Pdledit.php:21
+msgid "Layout updated."
msgstr ""
-#: ../../Zotlabs/Module/Invite.php:137
-msgid "Enter email addresses, one per line:"
+#: ../../Zotlabs/Module/Pdledit.php:34 ../../Zotlabs/Module/Chat.php:219
+msgid "Feature disabled."
msgstr ""
-#: ../../Zotlabs/Module/Invite.php:138 ../../Zotlabs/Module/Mail.php:284
-msgid "Your message:"
+#: ../../Zotlabs/Module/Pdledit.php:47 ../../Zotlabs/Module/Pdledit.php:88
+msgid "Edit System Page Description"
msgstr ""
-#: ../../Zotlabs/Module/Invite.php:139
-msgid "Please join my community on $Projectname."
+#: ../../Zotlabs/Module/Pdledit.php:68
+msgid "(modified)"
msgstr ""
-#: ../../Zotlabs/Module/Invite.php:141
-msgid "You will need to supply this invitation code:"
+#: ../../Zotlabs/Module/Pdledit.php:68 ../../Zotlabs/Module/Lostpass.php:133
+msgid "Reset"
msgstr ""
-#: ../../Zotlabs/Module/Invite.php:142
-msgid "1. Register at any $Projectname location (they are all inter-connected)"
+#: ../../Zotlabs/Module/Pdledit.php:83
+msgid "Layout not found."
msgstr ""
-#: ../../Zotlabs/Module/Invite.php:144
-msgid "2. Enter my $Projectname network address into the site searchbar."
+#: ../../Zotlabs/Module/Pdledit.php:89
+msgid "Module Name:"
msgstr ""
-#: ../../Zotlabs/Module/Invite.php:145
-msgid "or visit"
+#: ../../Zotlabs/Module/Pdledit.php:90
+msgid "Layout Help"
msgstr ""
-#: ../../Zotlabs/Module/Invite.php:147
-msgid "3. Click [Connect]"
+#: ../../Zotlabs/Module/Pdledit.php:91
+msgid "Edit another layout"
msgstr ""
-#: ../../Zotlabs/Module/Siteinfo.php:20
-msgid "About this site"
+#: ../../Zotlabs/Module/Poke.php:182 ../../Zotlabs/Lib/Apps.php:248
+#: ../../include/conversation.php:1075
+msgid "Poke"
msgstr ""
-#: ../../Zotlabs/Module/Siteinfo.php:21
-msgid "Site Name"
+#: ../../Zotlabs/Module/Poke.php:183
+msgid "Poke somebody"
msgstr ""
-#: ../../Zotlabs/Module/Siteinfo.php:25 ../../include/network.php:1972
-msgid "Administrator"
+#: ../../Zotlabs/Module/Poke.php:186
+msgid "Poke/Prod"
msgstr ""
-#: ../../Zotlabs/Module/Siteinfo.php:28
-msgid "Software and Project information"
+#: ../../Zotlabs/Module/Poke.php:187
+msgid "Poke, prod or do other things to somebody"
msgstr ""
-#: ../../Zotlabs/Module/Siteinfo.php:29
-msgid "This site is powered by $Projectname"
+#: ../../Zotlabs/Module/Poke.php:194
+msgid "Recipient"
msgstr ""
-#: ../../Zotlabs/Module/Siteinfo.php:30
-msgid ""
-"Federated and decentralised networking and identity services provided by Zot"
+#: ../../Zotlabs/Module/Poke.php:195
+msgid "Choose what you wish to do to recipient"
msgstr ""
-#: ../../Zotlabs/Module/Siteinfo.php:32
-#, php-format
-msgid "Version %s"
+#: ../../Zotlabs/Module/Poke.php:198 ../../Zotlabs/Module/Poke.php:199
+msgid "Make this post private"
msgstr ""
-#: ../../Zotlabs/Module/Siteinfo.php:33
-msgid "Project homepage"
+#: ../../Zotlabs/Module/Profile_photo.php:61
+#: ../../Zotlabs/Module/Cover_photo.php:56
+msgid "Image uploaded but image cropping failed."
msgstr ""
-#: ../../Zotlabs/Module/Siteinfo.php:34
-msgid "Developer homepage"
+#: ../../Zotlabs/Module/Profile_photo.php:115
+#: ../../Zotlabs/Module/Profile_photo.php:234
+#: ../../include/photo/photo_driver.php:710
+msgid "Profile Photos"
msgstr ""
-#: ../../Zotlabs/Module/New_channel.php:140
-msgid "Create Channel"
+#: ../../Zotlabs/Module/Profile_photo.php:137
+#: ../../Zotlabs/Module/Cover_photo.php:159
+msgid "Image resize failed."
msgstr ""
-#: ../../Zotlabs/Module/New_channel.php:141
+#: ../../Zotlabs/Module/Profile_photo.php:204
+#: ../../addon/openclipatar/openclipatar.php:298
msgid ""
-"A channel is your identity on this network. It can represent a person, a "
-"blog, or a forum to name a few. Channels can make connections with other "
-"channels to share information with highly detailed permissions."
+"Shift-reload the page or clear browser cache if the new photo does not "
+"display immediately."
msgstr ""
-#: ../../Zotlabs/Module/New_channel.php:142
-msgid ""
-"or <a href=\"import\">import an existing channel</a> from another location."
+#: ../../Zotlabs/Module/Profile_photo.php:211
+#: ../../Zotlabs/Module/Cover_photo.php:173 ../../include/photos.php:156
+msgid "Unable to process image"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:176
-msgid "$Projectname Server - Setup"
+#: ../../Zotlabs/Module/Profile_photo.php:246
+#: ../../Zotlabs/Module/Cover_photo.php:197
+msgid "Image upload failed."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:180
-msgid "Could not connect to database."
+#: ../../Zotlabs/Module/Profile_photo.php:265
+#: ../../Zotlabs/Module/Cover_photo.php:214
+msgid "Unable to process image."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:184
-msgid ""
-"Could not connect to specified site URL. Possible SSL certificate or DNS "
-"issue."
+#: ../../Zotlabs/Module/Profile_photo.php:326
+#: ../../Zotlabs/Module/Profile_photo.php:373
+#: ../../Zotlabs/Module/Cover_photo.php:307
+#: ../../Zotlabs/Module/Cover_photo.php:322
+msgid "Photo not available."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:191
-msgid "Could not create table."
+#: ../../Zotlabs/Module/Profile_photo.php:428
+#: ../../Zotlabs/Module/Cover_photo.php:358
+msgid "Upload File:"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:196
-msgid "Your site database has been installed."
+#: ../../Zotlabs/Module/Profile_photo.php:429
+#: ../../Zotlabs/Module/Cover_photo.php:359
+msgid "Select a profile:"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:200
-msgid ""
-"You may need to import the file \"install/schema_xxx.sql\" manually using a "
-"database client."
+#: ../../Zotlabs/Module/Profile_photo.php:430
+msgid "Use Photo for Profile"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:201 ../../Zotlabs/Module/Setup.php:263
-#: ../../Zotlabs/Module/Setup.php:750
-msgid "Please see the file \"install/INSTALL.txt\"."
+#: ../../Zotlabs/Module/Profile_photo.php:430
+msgid "Upload Profile Photo"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:260
-msgid "System check"
+#: ../../Zotlabs/Module/Profile_photo.php:431
+#: ../../addon/openclipatar/openclipatar.php:182
+#: ../../addon/openclipatar/openclipatar.php:194
+msgid "Use"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:265
-msgid "Check again"
+#: ../../Zotlabs/Module/Profile_photo.php:437
+#: ../../Zotlabs/Module/Cover_photo.php:365
+msgid "skip this step"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:287
-msgid "Database connection"
+#: ../../Zotlabs/Module/Profile_photo.php:437
+#: ../../Zotlabs/Module/Cover_photo.php:365
+msgid "select a photo from your photo albums"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:288
-msgid ""
-"In order to install $Projectname we need to know how to connect to your "
-"database."
+#: ../../Zotlabs/Module/Profile_photo.php:456
+#: ../../Zotlabs/Module/Cover_photo.php:381
+msgid "Crop Image"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:289
-msgid ""
-"Please contact your hosting provider or site administrator if you have "
-"questions about these settings."
+#: ../../Zotlabs/Module/Profile_photo.php:457
+#: ../../Zotlabs/Module/Cover_photo.php:382
+msgid "Please adjust the image cropping for optimum viewing."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:290
-msgid ""
-"The database you specify below should already exist. If it does not, please "
-"create it before continuing."
+#: ../../Zotlabs/Module/Profile_photo.php:459
+#: ../../Zotlabs/Module/Cover_photo.php:384
+msgid "Done Editing"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:294
-msgid "Database Server Name"
+#: ../../Zotlabs/Module/Chatsvc.php:131
+msgid "Away"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:294
-msgid "Default is 127.0.0.1"
+#: ../../Zotlabs/Module/Chatsvc.php:136
+msgid "Online"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:295
-msgid "Database Port"
+#: ../../Zotlabs/Module/Item.php:185
+msgid "Unable to locate original post."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:295
-msgid "Communication port number - use 0 for default"
+#: ../../Zotlabs/Module/Item.php:470
+msgid "Empty post discarded."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:296
-msgid "Database Login Name"
+#: ../../Zotlabs/Module/Item.php:870
+msgid "Duplicate post suppressed."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:297
-msgid "Database Login Password"
+#: ../../Zotlabs/Module/Item.php:1015
+msgid "System error. Post not saved."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:298
-msgid "Database Name"
+#: ../../Zotlabs/Module/Item.php:1051
+msgid "Your comment is awaiting approval."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:299
-msgid "Database Type"
+#: ../../Zotlabs/Module/Item.php:1156
+msgid "Unable to obtain post information from database."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:301 ../../Zotlabs/Module/Setup.php:347
-msgid "Site administrator email address"
+#: ../../Zotlabs/Module/Item.php:1163
+#, php-format
+msgid "You have reached your limit of %1$.0f top level posts."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:301 ../../Zotlabs/Module/Setup.php:347
-msgid ""
-"Your account email address must match this in order to use the web admin "
-"panel."
+#: ../../Zotlabs/Module/Item.php:1170
+#, php-format
+msgid "You have reached your limit of %1$.0f webpages."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:302 ../../Zotlabs/Module/Setup.php:349
-msgid "Website URL"
+#: ../../Zotlabs/Module/Ping.php:318
+msgid "sent you a private message"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:302 ../../Zotlabs/Module/Setup.php:349
-msgid "Please use SSL (https) URL if available."
+#: ../../Zotlabs/Module/Ping.php:369
+msgid "added your channel"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:303 ../../Zotlabs/Module/Setup.php:353
-msgid "Please select a default timezone for your website"
+#: ../../Zotlabs/Module/Ping.php:393
+msgid "requires approval"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:336
-msgid "Site settings"
+#: ../../Zotlabs/Module/Ping.php:403
+msgid "g A l F d"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:392
-msgid "PHP version 5.5 or greater is required."
+#: ../../Zotlabs/Module/Ping.php:421
+msgid "[today]"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:393
-msgid "PHP version"
+#: ../../Zotlabs/Module/Ping.php:430
+msgid "posted an event"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:409
-msgid "Could not find a command line version of PHP in the web server PATH."
+#: ../../Zotlabs/Module/Ping.php:463
+msgid "shared a file with you"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:410
-msgid ""
-"If you don't have a command line version of PHP installed on server, you "
-"will not be able to run background polling via cron."
+#: ../../Zotlabs/Module/Page.php:39 ../../Zotlabs/Module/Block.php:29
+msgid "Invalid item."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:414
-msgid "PHP executable path"
+#: ../../Zotlabs/Module/Page.php:128 ../../Zotlabs/Module/Block.php:77
+#: ../../Zotlabs/Module/Display.php:120
+#: ../../Zotlabs/Lib/NativeWikiPage.php:515 ../../Zotlabs/Web/Router.php:158
+#: ../../include/help.php:81
+msgid "Page not found."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:414
+#: ../../Zotlabs/Module/Page.php:165
msgid ""
-"Enter full path to php executable. You can leave this blank to continue the "
-"installation."
+"Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod "
+"tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, "
+"quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo "
+"consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse "
+"cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat "
+"non proident, sunt in culpa qui officia deserunt mollit anim id est laborum."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:419
-msgid "Command line PHP"
+#: ../../Zotlabs/Module/Connedit.php:79
+msgid "Could not access contact record."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:429
-msgid ""
-"Unable to check command line PHP, as shell_exec() is disabled. This is "
-"required."
+#: ../../Zotlabs/Module/Connedit.php:109
+msgid "Could not locate selected profile."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:432
-msgid ""
-"The command line version of PHP on your system does not have "
-"\"register_argc_argv\" enabled."
+#: ../../Zotlabs/Module/Connedit.php:246
+msgid "Connection updated."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:433
-msgid "This is required for message delivery to work."
+#: ../../Zotlabs/Module/Connedit.php:248
+msgid "Failed to update connection record."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:436
-msgid "PHP register_argc_argv"
+#: ../../Zotlabs/Module/Connedit.php:302
+msgid "is now connected to"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:454
-#, php-format
-msgid ""
-"Your max allowed total upload size is set to %s. Maximum size of one file to "
-"upload is set to %s. You are allowed to upload up to %d files at once."
+#: ../../Zotlabs/Module/Connedit.php:427
+msgid "Could not access address book record."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:459
-msgid "You can adjust these settings in the server php.ini file."
+#: ../../Zotlabs/Module/Connedit.php:475
+msgid "Refresh failed - channel is currently unavailable."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:461
-msgid "PHP upload limits"
+#: ../../Zotlabs/Module/Connedit.php:490 ../../Zotlabs/Module/Connedit.php:499
+#: ../../Zotlabs/Module/Connedit.php:508 ../../Zotlabs/Module/Connedit.php:517
+#: ../../Zotlabs/Module/Connedit.php:530
+msgid "Unable to set address book parameters."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:484
-msgid ""
-"Error: the \"openssl_pkey_new\" function on this system is not able to "
-"generate encryption keys"
+#: ../../Zotlabs/Module/Connedit.php:554
+msgid "Connection has been removed."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:485
-msgid ""
-"If running under Windows, please see \"http://www.php.net/manual/en/openssl."
-"installation.php\"."
+#: ../../Zotlabs/Module/Connedit.php:594 ../../Zotlabs/Lib/Apps.php:241
+#: ../../addon/openclipatar/openclipatar.php:57
+#: ../../include/conversation.php:1015 ../../include/nav.php:141
+msgid "View Profile"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:488
-msgid "Generate encryption keys"
+#: ../../Zotlabs/Module/Connedit.php:597
+#, php-format
+msgid "View %s's profile"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:505
-msgid "libCurl PHP module"
+#: ../../Zotlabs/Module/Connedit.php:601
+msgid "Refresh Permissions"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:506
-msgid "GD graphics PHP module"
+#: ../../Zotlabs/Module/Connedit.php:604
+msgid "Fetch updated permissions"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:507
-msgid "OpenSSL PHP module"
+#: ../../Zotlabs/Module/Connedit.php:608
+msgid "Refresh Photo"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:508
-msgid "PDO database PHP module"
+#: ../../Zotlabs/Module/Connedit.php:611
+msgid "Fetch updated photo"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:509
-msgid "mb_string PHP module"
+#: ../../Zotlabs/Module/Connedit.php:615
+msgid "Recent Activity"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:510
-msgid "xml PHP module"
+#: ../../Zotlabs/Module/Connedit.php:618
+msgid "View recent posts and comments"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:514 ../../Zotlabs/Module/Setup.php:516
-msgid "Apache mod_rewrite module"
+#: ../../Zotlabs/Module/Connedit.php:625
+msgid "Block (or Unblock) all communications with this connection"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:514
-msgid ""
-"Error: Apache webserver mod-rewrite module is required but not installed."
+#: ../../Zotlabs/Module/Connedit.php:626
+msgid "This connection is blocked!"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:520 ../../Zotlabs/Module/Setup.php:523
-msgid "exec"
+#: ../../Zotlabs/Module/Connedit.php:630
+msgid "Unignore"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:520
-msgid ""
-"Error: exec is required but is either not installed or has been disabled in "
-"php.ini"
+#: ../../Zotlabs/Module/Connedit.php:633
+msgid "Ignore (or Unignore) all inbound communications from this connection"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:526 ../../Zotlabs/Module/Setup.php:529
-msgid "shell_exec"
+#: ../../Zotlabs/Module/Connedit.php:634
+msgid "This connection is ignored!"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:526
-msgid ""
-"Error: shell_exec is required but is either not installed or has been "
-"disabled in php.ini"
+#: ../../Zotlabs/Module/Connedit.php:638
+msgid "Unarchive"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:534
-msgid "Error: libCURL PHP module required but not installed."
+#: ../../Zotlabs/Module/Connedit.php:638
+msgid "Archive"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:538
+#: ../../Zotlabs/Module/Connedit.php:641
msgid ""
-"Error: GD graphics PHP module with JPEG support required but not installed."
+"Archive (or Unarchive) this connection - mark channel dead but keep content"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:542
-msgid "Error: openssl PHP module required but not installed."
+#: ../../Zotlabs/Module/Connedit.php:642
+msgid "This connection is archived!"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:546
-msgid "Error: PDO database PHP module required but not installed."
+#: ../../Zotlabs/Module/Connedit.php:646
+msgid "Unhide"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:550
-msgid "Error: mb_string PHP module required but not installed."
+#: ../../Zotlabs/Module/Connedit.php:646
+msgid "Hide"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:554
-msgid "Error: xml PHP module required for DAV but not installed."
+#: ../../Zotlabs/Module/Connedit.php:649
+msgid "Hide or Unhide this connection from your other connections"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:572
-msgid ""
-"The web installer needs to be able to create a file called \".htconfig.php\" "
-"in the top folder of your web server and it is unable to do so."
+#: ../../Zotlabs/Module/Connedit.php:650
+msgid "This connection is hidden!"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:573
-msgid ""
-"This is most often a permission setting, as the web server may not be able "
-"to write files in your folder - even if you can."
+#: ../../Zotlabs/Module/Connedit.php:657
+msgid "Delete this connection"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:574
-msgid ""
-"At the end of this procedure, we will give you a text to save in a file "
-"named .htconfig.php in your Red top folder."
+#: ../../Zotlabs/Module/Connedit.php:665
+msgid "Fetch Vcard"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:575
-msgid ""
-"You can alternatively skip this procedure and perform a manual installation. "
-"Please see the file \"install/INSTALL.txt\" for instructions."
+#: ../../Zotlabs/Module/Connedit.php:668
+msgid "Fetch electronic calling card for this connection"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:578
-msgid ".htconfig.php is writable"
+#: ../../Zotlabs/Module/Connedit.php:679
+msgid "Open Individual Permissions section by default"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:592
-msgid ""
-"This software uses the Smarty3 template engine to render its web views. "
-"Smarty3 compiles templates to PHP to speed up rendering."
+#: ../../Zotlabs/Module/Connedit.php:702
+msgid "Affinity"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:593
-#, php-format
-msgid ""
-"In order to store these compiled templates, the web server needs to have "
-"write access to the directory %s under the top level web folder."
+#: ../../Zotlabs/Module/Connedit.php:705
+msgid "Open Set Affinity section by default"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:594 ../../Zotlabs/Module/Setup.php:615
-msgid ""
-"Please ensure that the user that your web server runs as (e.g. www-data) has "
-"write access to this folder."
+#: ../../Zotlabs/Module/Connedit.php:709 ../../Zotlabs/Widget/Affinity.php:26
+msgid "Me"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:595
-#, php-format
-msgid ""
-"Note: as a security measure, you should give the web server write access to "
-"%s only--not the template files (.tpl) that it contains."
+#: ../../Zotlabs/Module/Connedit.php:710 ../../Zotlabs/Widget/Affinity.php:27
+msgid "Family"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:598
-#, php-format
-msgid "%s is writable"
+#: ../../Zotlabs/Module/Connedit.php:712 ../../Zotlabs/Widget/Affinity.php:29
+msgid "Acquaintances"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:614
-msgid ""
-"This software uses the store directory to save uploaded files. The web "
-"server needs to have write access to the store directory under the top level "
-"web folder"
+#: ../../Zotlabs/Module/Connedit.php:739
+msgid "Filter"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:618
-msgid "store is writable"
+#: ../../Zotlabs/Module/Connedit.php:742
+msgid "Open Custom Filter section by default"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:651
-msgid ""
-"SSL certificate cannot be validated. Fix certificate or disable https access "
-"to this site."
+#: ../../Zotlabs/Module/Connedit.php:779
+msgid "Approve this connection"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:652
-msgid ""
-"If you have https access to your website or allow connections to TCP port "
-"443 (the https: port), you MUST use a browser-valid certificate. You MUST "
-"NOT use self-signed certificates!"
+#: ../../Zotlabs/Module/Connedit.php:779
+msgid "Accept connection to allow communication"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:653
-msgid ""
-"This restriction is incorporated because public posts from you may for "
-"example contain references to images on your own hub."
+#: ../../Zotlabs/Module/Connedit.php:784
+msgid "Set Affinity"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:654
-msgid ""
-"If your certificate is not recognized, members of other sites (who may "
-"themselves have valid certificates) will get a warning message on their own "
-"site complaining about security issues."
+#: ../../Zotlabs/Module/Connedit.php:787
+msgid "Set Profile"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:655
-msgid ""
-"This can cause usability issues elsewhere (not just on your own site) so we "
-"must insist on this requirement."
+#: ../../Zotlabs/Module/Connedit.php:790
+msgid "Set Affinity & Profile"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:656
-msgid ""
-"Providers are available that issue free certificates which are browser-valid."
+#: ../../Zotlabs/Module/Connedit.php:855
+msgid "This connection is unreachable from this location."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:658
-msgid ""
-"If you are confident that the certificate is valid and signed by a trusted "
-"authority, check to see if you have failed to install an intermediate cert. "
-"These are not normally required by browsers, but are required for server-to-"
-"server communications."
+#: ../../Zotlabs/Module/Connedit.php:856
+msgid "This connection may be unreachable from other channel locations."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:660
-msgid "SSL certificate validation"
+#: ../../Zotlabs/Module/Connedit.php:858
+msgid "Location independence is not supported by their network."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:666
+#: ../../Zotlabs/Module/Connedit.php:864
msgid ""
-"Url rewrite in .htaccess is not working. Check your server configuration."
-"Test: "
+"This connection is unreachable from this location. Location independence is "
+"not supported by their network."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:669
-msgid "Url rewrite is working"
+#: ../../Zotlabs/Module/Connedit.php:867
+#: ../../Zotlabs/Widget/Settings_menu.php:109
+msgid "Connection Default Permissions"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:683
-msgid ""
-"The database configuration file \".htconfig.php\" could not be written. "
-"Please use the enclosed text to create a configuration file in your web "
-"server root."
+#: ../../Zotlabs/Module/Connedit.php:867 ../../include/items.php:3974
+#, php-format
+msgid "Connection: %s"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:707
-#: ../../extend/addon/addon/cdav/cdav.php:41
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:401
-msgid "Errors encountered creating database tables."
+#: ../../Zotlabs/Module/Connedit.php:868
+msgid "Apply these permissions automatically"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:748
-msgid "<h1>What next</h1>"
+#: ../../Zotlabs/Module/Connedit.php:868
+msgid "Connection requests will be approved without your interaction"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:749
-msgid ""
-"IMPORTANT: You will need to [manually] setup a scheduled task for the poller."
+#: ../../Zotlabs/Module/Connedit.php:869
+msgid "Permission role"
msgstr ""
-#: ../../Zotlabs/Module/Notifications.php:43 ../../include/nav.php:208
-msgid "Mark all system notifications seen"
+#: ../../Zotlabs/Module/Connedit.php:870
+msgid "Add permission role"
msgstr ""
-#: ../../Zotlabs/Module/Poke.php:168 ../../Zotlabs/Lib/Apps.php:235
-#: ../../include/conversation.php:942 ../../include/conversation.php:1109
-msgid "Poke"
+#: ../../Zotlabs/Module/Connedit.php:877
+msgid "This connection's primary address is"
msgstr ""
-#: ../../Zotlabs/Module/Poke.php:169
-msgid "Poke somebody"
+#: ../../Zotlabs/Module/Connedit.php:878
+msgid "Available locations:"
msgstr ""
-#: ../../Zotlabs/Module/Poke.php:172
-msgid "Poke/Prod"
+#: ../../Zotlabs/Module/Connedit.php:883
+msgid ""
+"The permissions indicated on this page will be applied to all new "
+"connections."
msgstr ""
-#: ../../Zotlabs/Module/Poke.php:173
-msgid "Poke, prod or do other things to somebody"
+#: ../../Zotlabs/Module/Connedit.php:884
+msgid "Connection Tools"
msgstr ""
-#: ../../Zotlabs/Module/Poke.php:180
-msgid "Recipient"
+#: ../../Zotlabs/Module/Connedit.php:886
+msgid "Slide to adjust your degree of friendship"
msgstr ""
-#: ../../Zotlabs/Module/Poke.php:181
-msgid "Choose what you wish to do to recipient"
+#: ../../Zotlabs/Module/Connedit.php:887 ../../Zotlabs/Module/Rate.php:155
+#: ../../include/js_strings.php:20
+msgid "Rating"
msgstr ""
-#: ../../Zotlabs/Module/Poke.php:184 ../../Zotlabs/Module/Poke.php:185
-msgid "Make this post private"
+#: ../../Zotlabs/Module/Connedit.php:888
+msgid "Slide to adjust your rating"
msgstr ""
-#: ../../Zotlabs/Module/Oexchange.php:27
-msgid "Unable to find your hub."
+#: ../../Zotlabs/Module/Connedit.php:889 ../../Zotlabs/Module/Connedit.php:894
+msgid "Optionally explain your rating"
msgstr ""
-#: ../../Zotlabs/Module/Oexchange.php:41
-msgid "Post successful."
+#: ../../Zotlabs/Module/Connedit.php:891
+msgid "Custom Filter"
msgstr ""
-#: ../../Zotlabs/Module/Item.php:184
-msgid "Unable to locate original post."
+#: ../../Zotlabs/Module/Connedit.php:892
+msgid "Only import posts with this text"
msgstr ""
-#: ../../Zotlabs/Module/Item.php:450
-msgid "Empty post discarded."
+#: ../../Zotlabs/Module/Connedit.php:892 ../../Zotlabs/Module/Connedit.php:893
+msgid ""
+"words one per line or #tags or /patterns/ or lang=xx, leave blank to import "
+"all posts"
msgstr ""
-#: ../../Zotlabs/Module/Item.php:492
-msgid "Executable content type not permitted to this channel."
+#: ../../Zotlabs/Module/Connedit.php:893
+msgid "Do not import posts with this text"
msgstr ""
-#: ../../Zotlabs/Module/Item.php:842
-msgid "Duplicate post suppressed."
+#: ../../Zotlabs/Module/Connedit.php:895
+msgid "This information is public!"
msgstr ""
-#: ../../Zotlabs/Module/Item.php:984
-msgid "System error. Post not saved."
+#: ../../Zotlabs/Module/Connedit.php:900
+msgid "Connection Pending Approval"
msgstr ""
-#: ../../Zotlabs/Module/Item.php:1114
-msgid "Unable to obtain post information from database."
+#: ../../Zotlabs/Module/Connedit.php:905
+#, php-format
+msgid ""
+"Please choose the profile you would like to display to %s when viewing your "
+"profile securely."
msgstr ""
-#: ../../Zotlabs/Module/Item.php:1121
-#, php-format
-msgid "You have reached your limit of %1$.0f top level posts."
+#: ../../Zotlabs/Module/Connedit.php:912
+msgid ""
+"Some permissions may be inherited from your channel's <a href=\"settings"
+"\"><strong>privacy settings</strong></a>, which have higher priority than "
+"individual settings. You can change those settings here but they wont have "
+"any impact unless the inherited setting changes."
msgstr ""
-#: ../../Zotlabs/Module/Item.php:1128
-#, php-format
-msgid "You have reached your limit of %1$.0f webpages."
+#: ../../Zotlabs/Module/Connedit.php:913
+msgid "Last update:"
msgstr ""
-#: ../../Zotlabs/Module/Pconfig.php:26 ../../Zotlabs/Module/Pconfig.php:59
-msgid "This setting requires special processing and editing has been blocked."
+#: ../../Zotlabs/Module/Connedit.php:922
+msgid "Details"
msgstr ""
-#: ../../Zotlabs/Module/Pconfig.php:48
-msgid "Configuration Editor"
+#: ../../Zotlabs/Module/Chat.php:181
+msgid "Room not found"
msgstr ""
-#: ../../Zotlabs/Module/Pconfig.php:49
-msgid ""
-"Warning: Changing some settings could render your channel inoperable. Please "
-"leave this page unless you are comfortable with and knowledgeable about how "
-"to correctly use this feature."
+#: ../../Zotlabs/Module/Chat.php:197
+msgid "Leave Room"
msgstr ""
-#: ../../Zotlabs/Module/Profile.php:78
-msgid "vcard"
+#: ../../Zotlabs/Module/Chat.php:198
+msgid "Delete Room"
msgstr ""
-#: ../../Zotlabs/Module/Blocks.php:154 ../../include/text.php:2286
-msgid "Blocks"
+#: ../../Zotlabs/Module/Chat.php:199
+msgid "I am away right now"
msgstr ""
-#: ../../Zotlabs/Module/Blocks.php:156
-msgid "Block Title"
+#: ../../Zotlabs/Module/Chat.php:200
+msgid "I am online"
msgstr ""
-#: ../../Zotlabs/Module/Layouts.php:183 ../../include/text.php:2288
-msgid "Layouts"
+#: ../../Zotlabs/Module/Chat.php:202
+msgid "Bookmark this room"
msgstr ""
-#: ../../Zotlabs/Module/Layouts.php:185 ../../Zotlabs/Lib/Apps.php:232
-#: ../../include/nav.php:174 ../../include/help.php:53
-#: ../../include/help.php:59
-msgid "Help"
+#: ../../Zotlabs/Module/Chat.php:205 ../../Zotlabs/Module/Mail.php:241
+#: ../../Zotlabs/Module/Mail.php:362 ../../include/conversation.php:1296
+msgid "Please enter a link URL:"
msgstr ""
-#: ../../Zotlabs/Module/Layouts.php:185
-msgid "Comanche page description language help"
+#: ../../Zotlabs/Module/Chat.php:206 ../../Zotlabs/Module/Mail.php:294
+#: ../../Zotlabs/Module/Mail.php:436 ../../Zotlabs/Lib/ThreadItem.php:757
+#: ../../include/conversation.php:1415
+msgid "Encrypt text"
msgstr ""
-#: ../../Zotlabs/Module/Layouts.php:189
-msgid "Layout Description"
+#: ../../Zotlabs/Module/Chat.php:232
+msgid "New Chatroom"
msgstr ""
-#: ../../Zotlabs/Module/Layouts.php:194
-msgid "Download PDL file"
+#: ../../Zotlabs/Module/Chat.php:233
+msgid "Chatroom name"
msgstr ""
-#: ../../Zotlabs/Module/Rate.php:156
-msgid "Website:"
+#: ../../Zotlabs/Module/Chat.php:234
+msgid "Expiration of chats (minutes)"
msgstr ""
-#: ../../Zotlabs/Module/Rate.php:159
+#: ../../Zotlabs/Module/Chat.php:250
#, php-format
-msgid "Remote Channel [%s] (not yet known on this site)"
+msgid "%1$s's Chatrooms"
msgstr ""
-#: ../../Zotlabs/Module/Rate.php:160
-msgid "Rating (this information is public)"
+#: ../../Zotlabs/Module/Chat.php:255
+msgid "No chatrooms available"
msgstr ""
-#: ../../Zotlabs/Module/Rate.php:161
-msgid "Optionally explain your rating (this information is public)"
+#: ../../Zotlabs/Module/Chat.php:259
+msgid "Expiration"
msgstr ""
-#: ../../Zotlabs/Module/Profile_photo.php:186
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:296
-msgid ""
-"Shift-reload the page or clear browser cache if the new photo does not "
-"display immediately."
+#: ../../Zotlabs/Module/Chat.php:260
+msgid "min"
msgstr ""
-#: ../../Zotlabs/Module/Profile_photo.php:409
-msgid "Use Photo for Profile"
+#: ../../Zotlabs/Module/Fbrowser.php:29 ../../Zotlabs/Lib/Apps.php:242
+#: ../../include/conversation.php:1814 ../../include/nav.php:422
+msgid "Photos"
msgstr ""
-#: ../../Zotlabs/Module/Profile_photo.php:409
-msgid "Upload Profile Photo"
+#: ../../Zotlabs/Module/Fbrowser.php:85 ../../Zotlabs/Lib/Apps.php:237
+#: ../../Zotlabs/Storage/Browser.php:225 ../../include/conversation.php:1822
+#: ../../include/nav.php:430
+msgid "Files"
msgstr ""
-#: ../../Zotlabs/Module/Profile_photo.php:410
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:182
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:194
-msgid "Use"
+#: ../../Zotlabs/Module/Menu.php:49
+msgid "Unable to update menu."
msgstr ""
-#: ../../Zotlabs/Module/Events.php:25
-msgid "Calendar entries imported."
+#: ../../Zotlabs/Module/Menu.php:60
+msgid "Unable to create menu."
msgstr ""
-#: ../../Zotlabs/Module/Events.php:27
-msgid "No calendar entries found."
+#: ../../Zotlabs/Module/Menu.php:98 ../../Zotlabs/Module/Menu.php:110
+msgid "Menu Name"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:110
-msgid "Event can not end before it has started."
+#: ../../Zotlabs/Module/Menu.php:98
+msgid "Unique name (not visible on webpage) - required"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:112 ../../Zotlabs/Module/Events.php:121
-#: ../../Zotlabs/Module/Events.php:143
-msgid "Unable to generate preview."
+#: ../../Zotlabs/Module/Menu.php:99 ../../Zotlabs/Module/Menu.php:111
+msgid "Menu Title"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:119
-msgid "Event title and start time are required."
+#: ../../Zotlabs/Module/Menu.php:99
+msgid "Visible on webpage - leave empty for no title"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:141 ../../Zotlabs/Module/Events.php:265
-msgid "Event not found."
+#: ../../Zotlabs/Module/Menu.php:100
+msgid "Allow Bookmarks"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:460
-msgid "Edit event title"
+#: ../../Zotlabs/Module/Menu.php:100 ../../Zotlabs/Module/Menu.php:157
+msgid "Menu may be used to store saved bookmarks"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:460
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:835
-msgid "Event title"
+#: ../../Zotlabs/Module/Menu.php:101 ../../Zotlabs/Module/Menu.php:159
+msgid "Submit and proceed"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:462
-msgid "Categories (comma-separated list)"
+#: ../../Zotlabs/Module/Menu.php:107 ../../include/text.php:2289
+msgid "Menus"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:463
-msgid "Edit Category"
+#: ../../Zotlabs/Module/Menu.php:117
+msgid "Bookmarks allowed"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:463
-msgid "Category"
+#: ../../Zotlabs/Module/Menu.php:119
+msgid "Delete this menu"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:466
-msgid "Edit start date and time"
+#: ../../Zotlabs/Module/Menu.php:120 ../../Zotlabs/Module/Menu.php:154
+msgid "Edit menu contents"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:466
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:836
-msgid "Start date and time"
+#: ../../Zotlabs/Module/Menu.php:121
+msgid "Edit this menu"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:467 ../../Zotlabs/Module/Events.php:470
-msgid "Finish date and time are not known or not relevant"
+#: ../../Zotlabs/Module/Menu.php:136
+msgid "Menu could not be deleted."
msgstr ""
-#: ../../Zotlabs/Module/Events.php:469
-msgid "Edit finish date and time"
+#: ../../Zotlabs/Module/Menu.php:149
+msgid "Edit Menu"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:469
-msgid "Finish date and time"
+#: ../../Zotlabs/Module/Menu.php:153
+msgid "Add or remove entries to this menu"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:471 ../../Zotlabs/Module/Events.php:472
-msgid "Adjust for viewer timezone"
+#: ../../Zotlabs/Module/Menu.php:155
+msgid "Menu name"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:471
-msgid ""
-"Important for events that happen in a particular place. Not practical for "
-"global holidays."
+#: ../../Zotlabs/Module/Menu.php:155
+msgid "Must be unique, only seen by you"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:473
-msgid "Edit Description"
+#: ../../Zotlabs/Module/Menu.php:156
+msgid "Menu title"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:475
-msgid "Edit Location"
+#: ../../Zotlabs/Module/Menu.php:156
+msgid "Menu title as seen by others"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:479 ../../include/conversation.php:1410
-msgid "Permission settings"
+#: ../../Zotlabs/Module/Menu.php:157
+msgid "Allow bookmarks"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:489
-msgid "Timezone:"
+#: ../../Zotlabs/Module/Layouts.php:184 ../../include/text.php:2290
+msgid "Layouts"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:494
-msgid "Advanced Options"
+#: ../../Zotlabs/Module/Layouts.php:186 ../../Zotlabs/Lib/Apps.php:245
+#: ../../include/nav.php:201 ../../include/nav.php:301
+#: ../../include/help.php:68 ../../include/help.php:74
+msgid "Help"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:633
-msgid "Edit event"
+#: ../../Zotlabs/Module/Layouts.php:186
+msgid "Comanche page description language help"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:635
-msgid "Delete event"
+#: ../../Zotlabs/Module/Layouts.php:190
+msgid "Layout Description"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:669
-msgid "calendar"
+#: ../../Zotlabs/Module/Layouts.php:195
+msgid "Download PDL file"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:695
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:849
-msgid "Month"
+#: ../../Zotlabs/Module/Tagger.php:55 ../../include/markdown.php:141
+#: ../../include/bbcode.php:333
+msgid "post"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:696
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:850
-msgid "Week"
+#: ../../Zotlabs/Module/Tagger.php:57 ../../include/conversation.php:146
+#: ../../include/text.php:1946
+msgid "comment"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:697
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:851
-msgid "Day"
+#: ../../Zotlabs/Module/Tagger.php:95
+#, php-format
+msgid "%1$s tagged %2$s's %3$s with %4$s"
msgstr ""
-#: ../../Zotlabs/Module/Events.php:731
-msgid "Event removed"
+#: ../../Zotlabs/Module/Pconfig.php:26 ../../Zotlabs/Module/Pconfig.php:59
+msgid "This setting requires special processing and editing has been blocked."
msgstr ""
-#: ../../Zotlabs/Module/Events.php:734
-msgid "Failed to remove event"
+#: ../../Zotlabs/Module/Pconfig.php:48
+msgid "Configuration Editor"
msgstr ""
-#: ../../Zotlabs/Module/Common.php:14
-msgid "No channel."
+#: ../../Zotlabs/Module/Pconfig.php:49
+msgid ""
+"Warning: Changing some settings could render your channel inoperable. Please "
+"leave this page unless you are comfortable with and knowledgeable about how "
+"to correctly use this feature."
msgstr ""
-#: ../../Zotlabs/Module/Common.php:43
-msgid "Common connections"
+#: ../../Zotlabs/Module/Group.php:24
+msgid "Privacy group created."
msgstr ""
-#: ../../Zotlabs/Module/Common.php:48
-msgid "No connections in common."
+#: ../../Zotlabs/Module/Group.php:30
+msgid "Could not create privacy group."
msgstr ""
-#: ../../Zotlabs/Module/Chanview.php:134
-msgid "toggle full screen mode"
+#: ../../Zotlabs/Module/Group.php:42 ../../Zotlabs/Module/Group.php:143
+#: ../../include/items.php:3941
+msgid "Privacy group not found."
msgstr ""
-#: ../../Zotlabs/Module/Profperm.php:34 ../../Zotlabs/Module/Profperm.php:63
-msgid "Invalid profile identifier."
+#: ../../Zotlabs/Module/Group.php:58
+msgid "Privacy group updated."
msgstr ""
-#: ../../Zotlabs/Module/Profperm.php:115
-msgid "Profile Visibility Editor"
+#: ../../Zotlabs/Module/Group.php:92
+msgid "Create a group of channels."
msgstr ""
-#: ../../Zotlabs/Module/Profperm.php:117 ../../include/channel.php:1367
-msgid "Profile"
+#: ../../Zotlabs/Module/Group.php:93 ../../Zotlabs/Module/Group.php:186
+msgid "Privacy group name: "
msgstr ""
-#: ../../Zotlabs/Module/Profperm.php:119
-msgid "Click on a contact to add or remove."
+#: ../../Zotlabs/Module/Group.php:95 ../../Zotlabs/Module/Group.php:189
+msgid "Members are visible to other channels"
msgstr ""
-#: ../../Zotlabs/Module/Profperm.php:128
-msgid "Visible To"
+#: ../../Zotlabs/Module/Group.php:113
+msgid "Privacy group removed."
msgstr ""
-#: ../../Zotlabs/Module/Channel.php:32 ../../Zotlabs/Module/Chat.php:25
-#: ../../extend/addon/addon/chess/chess.php:400
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:26
-msgid "You must be logged in to see this page."
+#: ../../Zotlabs/Module/Group.php:115
+msgid "Unable to remove privacy group."
msgstr ""
-#: ../../Zotlabs/Module/Channel.php:44
-msgid "Posts and comments"
+#: ../../Zotlabs/Module/Group.php:185
+msgid "Privacy group editor"
msgstr ""
-#: ../../Zotlabs/Module/Channel.php:45
-msgid "Only posts"
+#: ../../Zotlabs/Module/Group.php:199 ../../Zotlabs/Module/Help.php:81
+msgid "Members"
msgstr ""
-#: ../../Zotlabs/Module/Channel.php:104
-msgid "Insufficient permissions. Request redirected to profile page."
+#: ../../Zotlabs/Module/Group.php:201
+msgid "All Connected Channels"
msgstr ""
-#: ../../Zotlabs/Module/Lostpass.php:19
-msgid "No valid account found."
+#: ../../Zotlabs/Module/Group.php:233
+msgid "Click on a channel to add or remove."
msgstr ""
-#: ../../Zotlabs/Module/Lostpass.php:33
-msgid "Password reset request issued. Check your email."
+#: ../../Zotlabs/Module/Profiles.php:24 ../../Zotlabs/Module/Profiles.php:184
+#: ../../Zotlabs/Module/Profiles.php:241 ../../Zotlabs/Module/Profiles.php:659
+msgid "Profile not found."
msgstr ""
-#: ../../Zotlabs/Module/Lostpass.php:39 ../../Zotlabs/Module/Lostpass.php:108
-#, php-format
-msgid "Site Member (%s)"
+#: ../../Zotlabs/Module/Profiles.php:44
+msgid "Profile deleted."
msgstr ""
-#: ../../Zotlabs/Module/Lostpass.php:44 ../../Zotlabs/Module/Lostpass.php:49
-#, php-format
-msgid "Password reset requested at %s"
+#: ../../Zotlabs/Module/Profiles.php:68 ../../Zotlabs/Module/Profiles.php:105
+msgid "Profile-"
msgstr ""
-#: ../../Zotlabs/Module/Lostpass.php:68
-msgid ""
-"Request could not be verified. (You may have previously submitted it.) "
-"Password reset failed."
+#: ../../Zotlabs/Module/Profiles.php:90 ../../Zotlabs/Module/Profiles.php:127
+msgid "New profile created."
msgstr ""
-#: ../../Zotlabs/Module/Lostpass.php:91 ../../boot.php:1740
-msgid "Password Reset"
+#: ../../Zotlabs/Module/Profiles.php:111
+msgid "Profile unavailable to clone."
msgstr ""
-#: ../../Zotlabs/Module/Lostpass.php:92
-msgid "Your password has been reset as requested."
+#: ../../Zotlabs/Module/Profiles.php:146
+msgid "Profile unavailable to export."
msgstr ""
-#: ../../Zotlabs/Module/Lostpass.php:93
-msgid "Your new password is"
+#: ../../Zotlabs/Module/Profiles.php:252
+msgid "Profile Name is required."
msgstr ""
-#: ../../Zotlabs/Module/Lostpass.php:94
-msgid "Save or copy your new password - and then"
+#: ../../Zotlabs/Module/Profiles.php:459
+msgid "Marital Status"
msgstr ""
-#: ../../Zotlabs/Module/Lostpass.php:95
-msgid "click here to login"
+#: ../../Zotlabs/Module/Profiles.php:463
+msgid "Romantic Partner"
msgstr ""
-#: ../../Zotlabs/Module/Lostpass.php:96
-msgid ""
-"Your password may be changed from the <em>Settings</em> page after "
-"successful login."
+#: ../../Zotlabs/Module/Profiles.php:467 ../../Zotlabs/Module/Profiles.php:775
+msgid "Likes"
msgstr ""
-#: ../../Zotlabs/Module/Lostpass.php:117
-#, php-format
-msgid "Your password has changed at %s"
+#: ../../Zotlabs/Module/Profiles.php:471 ../../Zotlabs/Module/Profiles.php:776
+msgid "Dislikes"
msgstr ""
-#: ../../Zotlabs/Module/Lostpass.php:130
-msgid "Forgot your Password?"
+#: ../../Zotlabs/Module/Profiles.php:475 ../../Zotlabs/Module/Profiles.php:783
+msgid "Work/Employment"
msgstr ""
-#: ../../Zotlabs/Module/Lostpass.php:131
-msgid ""
-"Enter your email address and submit to have your password reset. Then check "
-"your email for further instructions."
+#: ../../Zotlabs/Module/Profiles.php:478
+msgid "Religion"
msgstr ""
-#: ../../Zotlabs/Module/Lostpass.php:132
-msgid "Email Address"
+#: ../../Zotlabs/Module/Profiles.php:482
+msgid "Political Views"
msgstr ""
-#: ../../Zotlabs/Module/Lostpass.php:133
-msgid "Reset"
+#: ../../Zotlabs/Module/Profiles.php:486
+#: ../../addon/openid/MysqlProvider.php:74
+msgid "Gender"
msgstr ""
-#: ../../Zotlabs/Module/Rbmark.php:94
-msgid "Select a bookmark folder"
+#: ../../Zotlabs/Module/Profiles.php:490
+msgid "Sexual Preference"
msgstr ""
-#: ../../Zotlabs/Module/Rbmark.php:99
-msgid "Save Bookmark"
+#: ../../Zotlabs/Module/Profiles.php:494
+msgid "Homepage"
msgstr ""
-#: ../../Zotlabs/Module/Rbmark.php:100
-msgid "URL of bookmark"
+#: ../../Zotlabs/Module/Profiles.php:498
+msgid "Interests"
msgstr ""
-#: ../../Zotlabs/Module/Rbmark.php:105
-msgid "Or enter new bookmark folder name"
+#: ../../Zotlabs/Module/Profiles.php:594
+msgid "Profile updated."
msgstr ""
-#: ../../Zotlabs/Module/Follow.php:31
-msgid "Channel added."
+#: ../../Zotlabs/Module/Profiles.php:678
+msgid "Hide your connections list from viewers of this profile"
msgstr ""
-#: ../../Zotlabs/Module/Rmagic.php:35
-msgid "Authentication failed."
+#: ../../Zotlabs/Module/Profiles.php:725
+msgid "Edit Profile Details"
msgstr ""
-#: ../../Zotlabs/Module/Rmagic.php:75 ../../include/channel.php:1991
-msgid "Remote Authentication"
+#: ../../Zotlabs/Module/Profiles.php:727
+msgid "View this profile"
msgstr ""
-#: ../../Zotlabs/Module/Rmagic.php:76 ../../include/channel.php:1992
-msgid "Enter your channel address (e.g. channel@example.com)"
+#: ../../Zotlabs/Module/Profiles.php:728 ../../Zotlabs/Module/Profiles.php:827
+#: ../../include/channel.php:1284
+msgid "Edit visibility"
msgstr ""
-#: ../../Zotlabs/Module/Rmagic.php:77 ../../include/channel.php:1993
-msgid "Authenticate"
+#: ../../Zotlabs/Module/Profiles.php:729
+msgid "Profile Tools"
msgstr ""
-#: ../../Zotlabs/Module/Regmod.php:15
-msgid "Please login."
+#: ../../Zotlabs/Module/Profiles.php:730
+msgid "Change cover photo"
msgstr ""
-#: ../../Zotlabs/Module/Removeaccount.php:35
-msgid ""
-"Account removals are not allowed within 48 hours of changing the account "
-"password."
+#: ../../Zotlabs/Module/Profiles.php:731 ../../include/channel.php:1255
+msgid "Change profile photo"
msgstr ""
-#: ../../Zotlabs/Module/Removeaccount.php:57
-msgid "Remove This Account"
+#: ../../Zotlabs/Module/Profiles.php:732
+msgid "Create a new profile using these settings"
msgstr ""
-#: ../../Zotlabs/Module/Removeaccount.php:58
-#: ../../Zotlabs/Module/Removeme.php:61
-msgid "WARNING: "
+#: ../../Zotlabs/Module/Profiles.php:733
+msgid "Clone this profile"
msgstr ""
-#: ../../Zotlabs/Module/Removeaccount.php:58
-msgid ""
-"This account and all its channels will be completely removed from the "
-"network. "
+#: ../../Zotlabs/Module/Profiles.php:734
+msgid "Delete this profile"
msgstr ""
-#: ../../Zotlabs/Module/Removeaccount.php:58
-#: ../../Zotlabs/Module/Removeme.php:61
-msgid "This action is permanent and can not be undone!"
+#: ../../Zotlabs/Module/Profiles.php:735
+msgid "Add profile things"
msgstr ""
-#: ../../Zotlabs/Module/Removeaccount.php:59
-#: ../../Zotlabs/Module/Removeme.php:62
-msgid "Please enter your password for verification:"
+#: ../../Zotlabs/Module/Profiles.php:736 ../../include/conversation.php:1688
+msgid "Personal"
msgstr ""
-#: ../../Zotlabs/Module/Removeaccount.php:60
-msgid ""
-"Remove this account, all its channels and all its channel clones from the "
-"network"
+#: ../../Zotlabs/Module/Profiles.php:738
+msgid "Relation"
msgstr ""
-#: ../../Zotlabs/Module/Removeaccount.php:60
-msgid ""
-"By default only the instances of the channels located on this hub will be "
-"removed from the network"
+#: ../../Zotlabs/Module/Profiles.php:739 ../../include/datetime.php:55
+msgid "Miscellaneous"
msgstr ""
-#: ../../Zotlabs/Module/Removeaccount.php:61
-#: ../../Zotlabs/Module/Settings/Account.php:120
-msgid "Remove Account"
+#: ../../Zotlabs/Module/Profiles.php:741
+msgid "Import profile from file"
msgstr ""
-#: ../../Zotlabs/Module/Pdledit.php:21
-msgid "Layout updated."
+#: ../../Zotlabs/Module/Profiles.php:742
+msgid "Export profile to file"
msgstr ""
-#: ../../Zotlabs/Module/Pdledit.php:34 ../../Zotlabs/Module/Chat.php:218
-msgid "Feature disabled."
+#: ../../Zotlabs/Module/Profiles.php:743
+msgid "Your gender"
msgstr ""
-#: ../../Zotlabs/Module/Pdledit.php:42 ../../Zotlabs/Module/Pdledit.php:69
-msgid "Edit System Page Description"
+#: ../../Zotlabs/Module/Profiles.php:744
+msgid "Marital status"
msgstr ""
-#: ../../Zotlabs/Module/Pdledit.php:64
-msgid "Layout not found."
+#: ../../Zotlabs/Module/Profiles.php:745
+msgid "Sexual preference"
msgstr ""
-#: ../../Zotlabs/Module/Pdledit.php:70
-msgid "Module Name:"
+#: ../../Zotlabs/Module/Profiles.php:748
+msgid "Profile name"
msgstr ""
-#: ../../Zotlabs/Module/Pdledit.php:71
-msgid "Layout Help"
+#: ../../Zotlabs/Module/Profiles.php:750
+msgid "This is your default profile."
msgstr ""
-#: ../../Zotlabs/Module/Uexport.php:57 ../../Zotlabs/Module/Uexport.php:58
-msgid "Export Channel"
+#: ../../Zotlabs/Module/Profiles.php:752
+msgid "Your full name"
msgstr ""
-#: ../../Zotlabs/Module/Uexport.php:59
-msgid ""
-"Export your basic channel information to a file. This acts as a backup of "
-"your connections, permissions, profile and basic data, which can be used to "
-"import your data to a new server hub, but does not contain your content."
+#: ../../Zotlabs/Module/Profiles.php:753
+msgid "Title/Description"
msgstr ""
-#: ../../Zotlabs/Module/Uexport.php:60
-msgid "Export Content"
+#: ../../Zotlabs/Module/Profiles.php:756
+msgid "Street address"
msgstr ""
-#: ../../Zotlabs/Module/Uexport.php:61
-msgid ""
-"Export your channel information and recent content to a JSON backup that can "
-"be restored or imported to another server hub. This backs up all of your "
-"connections, permissions, profile data and several months of posts. This "
-"file may be VERY large. Please be patient - it may take several minutes for "
-"this download to begin."
+#: ../../Zotlabs/Module/Profiles.php:757
+msgid "Locality/City"
msgstr ""
-#: ../../Zotlabs/Module/Uexport.php:63
-msgid "Export your posts from a given year."
+#: ../../Zotlabs/Module/Profiles.php:758
+msgid "Region/State"
msgstr ""
-#: ../../Zotlabs/Module/Uexport.php:65
-msgid ""
-"You may also export your posts and conversations for a particular year or "
-"month. Adjust the date in your browser location bar to select other dates. "
-"If the export fails (possibly due to memory exhaustion on your server hub), "
-"please try again selecting a more limited date range."
+#: ../../Zotlabs/Module/Profiles.php:759
+msgid "Postal/Zip code"
msgstr ""
-#: ../../Zotlabs/Module/Uexport.php:66
-#, php-format
-msgid ""
-"To select all posts for a given year, such as this year, visit <a href=\"%1$s"
-"\">%2$s</a>"
+#: ../../Zotlabs/Module/Profiles.php:765
+msgid "Who (if applicable)"
msgstr ""
-#: ../../Zotlabs/Module/Uexport.php:67
-#, php-format
-msgid ""
-"To select all posts for a given month, such as January of this year, visit "
-"<a href=\"%1$s\">%2$s</a>"
+#: ../../Zotlabs/Module/Profiles.php:765
+msgid "Examples: cathy123, Cathy Williams, cathy@example.com"
msgstr ""
-#: ../../Zotlabs/Module/Uexport.php:68
-#, php-format
-msgid ""
-"These content files may be imported or restored by visiting <a href=\"%1$s\">"
-"%2$s</a> on any site containing your channel. For best results please import "
-"or restore these in date order (oldest first)."
+#: ../../Zotlabs/Module/Profiles.php:766
+msgid "Since (date)"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:246
-#, php-format
-msgid "%d rating"
-msgid_plural "%d ratings"
-msgstr[0] ""
-msgstr[1] ""
-
-#: ../../Zotlabs/Module/Directory.php:257
-msgid "Gender: "
+#: ../../Zotlabs/Module/Profiles.php:769
+msgid "Tell us about yourself"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:259
-msgid "Status: "
+#: ../../Zotlabs/Module/Profiles.php:770
+#: ../../addon/openid/MysqlProvider.php:68
+msgid "Homepage URL"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:261
-msgid "Homepage: "
+#: ../../Zotlabs/Module/Profiles.php:771
+msgid "Hometown"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:310 ../../include/channel.php:1298
-msgid "Age:"
+#: ../../Zotlabs/Module/Profiles.php:772
+msgid "Political views"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:315 ../../include/markdown.php:561
-#: ../../include/channel.php:1134 ../../include/event.php:52
-#: ../../include/event.php:84
-msgid "Location:"
+#: ../../Zotlabs/Module/Profiles.php:773
+msgid "Religious views"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:321
-msgid "Description:"
+#: ../../Zotlabs/Module/Profiles.php:774
+msgid "Keywords used in directory listings"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:326 ../../include/channel.php:1314
-msgid "Hometown:"
+#: ../../Zotlabs/Module/Profiles.php:774
+msgid "Example: fishing photography software"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:328 ../../include/channel.php:1322
-msgid "About:"
+#: ../../Zotlabs/Module/Profiles.php:777
+msgid "Musical interests"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:329 ../../Zotlabs/Module/Suggest.php:56
-#: ../../include/connections.php:110 ../../include/conversation.php:938
-#: ../../include/conversation.php:1069 ../../include/widgets.php:148
-#: ../../include/widgets.php:185 ../../include/channel.php:1119
-msgid "Connect"
+#: ../../Zotlabs/Module/Profiles.php:778
+msgid "Books, literature"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:330
-msgid "Public Forum:"
+#: ../../Zotlabs/Module/Profiles.php:779
+msgid "Television"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:333
-msgid "Keywords: "
+#: ../../Zotlabs/Module/Profiles.php:780
+msgid "Film/Dance/Culture/Entertainment"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:336
-msgid "Don't suggest"
+#: ../../Zotlabs/Module/Profiles.php:781
+msgid "Hobbies/Interests"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:338
-msgid "Common connections:"
+#: ../../Zotlabs/Module/Profiles.php:782
+msgid "Love/Romance"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:387
-msgid "Global Directory"
+#: ../../Zotlabs/Module/Profiles.php:784
+msgid "School/Education"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:387
-msgid "Local Directory"
+#: ../../Zotlabs/Module/Profiles.php:785
+msgid "Contact information and social networks"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:393
-msgid "Finding:"
+#: ../../Zotlabs/Module/Profiles.php:786
+msgid "My other channels"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:396 ../../Zotlabs/Module/Suggest.php:64
-#: ../../include/contact_widgets.php:24
-msgid "Channel Suggestions"
+#: ../../Zotlabs/Module/Profiles.php:788
+msgid "Communications"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:398
-msgid "next page"
+#: ../../Zotlabs/Module/Profiles.php:823 ../../include/channel.php:1280
+msgid "Profile Image"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:398
-msgid "previous page"
+#: ../../Zotlabs/Module/Profiles.php:833 ../../include/channel.php:1262
+#: ../../include/nav.php:144
+msgid "Edit Profiles"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:399
-msgid "Sort options"
+#: ../../Zotlabs/Module/Editwebpage.php:139
+msgid "Page link"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:400
-msgid "Alphabetic"
+#: ../../Zotlabs/Module/Editwebpage.php:166
+msgid "Edit Webpage"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:401
-msgid "Reverse Alphabetic"
+#: ../../Zotlabs/Module/Manage.php:145
+msgid "Create a new channel"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:402
-msgid "Newest to Oldest"
+#: ../../Zotlabs/Module/Manage.php:170 ../../Zotlabs/Lib/Apps.php:234
+#: ../../include/nav.php:129 ../../include/nav.php:215
+msgid "Channel Manager"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:403
-msgid "Oldest to Newest"
+#: ../../Zotlabs/Module/Manage.php:171
+msgid "Current Channel"
msgstr ""
-#: ../../Zotlabs/Module/Directory.php:420
-msgid "No entries (some entries may be hidden)."
+#: ../../Zotlabs/Module/Manage.php:173
+msgid "Switch to one of your channels by selecting it."
msgstr ""
-#: ../../Zotlabs/Module/Chatsvc.php:131
-msgid "Away"
+#: ../../Zotlabs/Module/Manage.php:174
+msgid "Default Channel"
msgstr ""
-#: ../../Zotlabs/Module/Chatsvc.php:136
-msgid "Online"
+#: ../../Zotlabs/Module/Manage.php:175
+msgid "Make Default"
msgstr ""
-#: ../../Zotlabs/Module/Service_limits.php:23
-msgid "No service class restrictions found."
+#: ../../Zotlabs/Module/Manage.php:178
+#, php-format
+msgid "%d new messages"
msgstr ""
-#: ../../Zotlabs/Module/Webpages.php:52
-msgid "Import Webpage Elements"
+#: ../../Zotlabs/Module/Manage.php:179
+#, php-format
+msgid "%d new introductions"
msgstr ""
-#: ../../Zotlabs/Module/Webpages.php:53
-msgid "Import selected"
+#: ../../Zotlabs/Module/Manage.php:181
+msgid "Delegated Channel"
msgstr ""
-#: ../../Zotlabs/Module/Webpages.php:76
-msgid "Export Webpage Elements"
+#: ../../Zotlabs/Module/Cards.php:38 ../../Zotlabs/Module/Cards.php:178
+#: ../../Zotlabs/Lib/Apps.php:224 ../../include/conversation.php:1873
+#: ../../include/features.php:122 ../../include/nav.php:479
+msgid "Cards"
msgstr ""
-#: ../../Zotlabs/Module/Webpages.php:77
-msgid "Export selected"
+#: ../../Zotlabs/Module/Cards.php:95
+msgid "Add Card"
msgstr ""
-#: ../../Zotlabs/Module/Webpages.php:241 ../../Zotlabs/Lib/Apps.php:225
-#: ../../include/conversation.php:1889
-msgid "Webpages"
+#: ../../Zotlabs/Module/Dirsearch.php:33
+msgid "This directory server requires an access token"
msgstr ""
-#: ../../Zotlabs/Module/Webpages.php:252 ../../include/page_widgets.php:44
-msgid "Actions"
+#: ../../Zotlabs/Module/Siteinfo.php:19
+msgid "About this site"
msgstr ""
-#: ../../Zotlabs/Module/Webpages.php:253 ../../include/page_widgets.php:45
-msgid "Page Link"
+#: ../../Zotlabs/Module/Siteinfo.php:20
+msgid "Site Name"
msgstr ""
-#: ../../Zotlabs/Module/Webpages.php:254
-msgid "Page Title"
+#: ../../Zotlabs/Module/Siteinfo.php:24
+msgid "Administrator"
msgstr ""
-#: ../../Zotlabs/Module/Webpages.php:284
-msgid "Invalid file type."
+#: ../../Zotlabs/Module/Siteinfo.php:26 ../../Zotlabs/Module/Register.php:221
+msgid "Terms of Service"
msgstr ""
-#: ../../Zotlabs/Module/Webpages.php:296
-msgid "Error opening zip file"
+#: ../../Zotlabs/Module/Siteinfo.php:27
+msgid "Software and Project information"
msgstr ""
-#: ../../Zotlabs/Module/Webpages.php:307
-msgid "Invalid folder path."
+#: ../../Zotlabs/Module/Siteinfo.php:28
+msgid "This site is powered by $Projectname"
msgstr ""
-#: ../../Zotlabs/Module/Webpages.php:334
-msgid "No webpage elements detected."
+#: ../../Zotlabs/Module/Siteinfo.php:29
+msgid ""
+"Federated and decentralised networking and identity services provided by Zot"
msgstr ""
-#: ../../Zotlabs/Module/Webpages.php:409
-msgid "Import complete."
+#: ../../Zotlabs/Module/Siteinfo.php:31
+#, php-format
+msgid "Version %s"
msgstr ""
-#: ../../Zotlabs/Module/Removeme.php:35
-msgid ""
-"Channel removals are not allowed within 48 hours of changing the account "
-"password."
+#: ../../Zotlabs/Module/Siteinfo.php:32
+msgid "Project homepage"
msgstr ""
-#: ../../Zotlabs/Module/Removeme.php:60
-msgid "Remove This Channel"
+#: ../../Zotlabs/Module/Siteinfo.php:33
+msgid "Developer homepage"
msgstr ""
-#: ../../Zotlabs/Module/Removeme.php:61
-msgid "This channel will be completely removed from the network. "
+#: ../../Zotlabs/Module/Ratings.php:70
+msgid "No ratings"
msgstr ""
-#: ../../Zotlabs/Module/Removeme.php:63
-msgid "Remove this channel and all its clones from the network"
+#: ../../Zotlabs/Module/Ratings.php:97 ../../Zotlabs/Module/Pubsites.php:35
+#: ../../include/conversation.php:1065
+msgid "Ratings"
msgstr ""
-#: ../../Zotlabs/Module/Removeme.php:63
-msgid ""
-"By default only the instance of the channel located on this hub will be "
-"removed from the network"
+#: ../../Zotlabs/Module/Ratings.php:98
+msgid "Rating: "
msgstr ""
-#: ../../Zotlabs/Module/Removeme.php:64
-#: ../../Zotlabs/Module/Settings/Channel.php:558
-msgid "Remove Channel"
+#: ../../Zotlabs/Module/Ratings.php:99
+msgid "Website: "
msgstr ""
-#: ../../Zotlabs/Module/Sharedwithme.php:98
-msgid "Files: shared with me"
+#: ../../Zotlabs/Module/Ratings.php:101
+msgid "Description: "
msgstr ""
-#: ../../Zotlabs/Module/Sharedwithme.php:100
-msgid "NEW"
+#: ../../Zotlabs/Module/Webpages.php:54
+msgid "Import Webpage Elements"
msgstr ""
-#: ../../Zotlabs/Module/Sharedwithme.php:103
-msgid "Remove all files"
+#: ../../Zotlabs/Module/Webpages.php:55
+msgid "Import selected"
msgstr ""
-#: ../../Zotlabs/Module/Sharedwithme.php:104
-msgid "Remove this file"
+#: ../../Zotlabs/Module/Webpages.php:78
+msgid "Export Webpage Elements"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:29
-msgid "Profile Unavailable."
+#: ../../Zotlabs/Module/Webpages.php:79
+msgid "Export selected"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:43
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:40
-msgid "Not found"
+#: ../../Zotlabs/Module/Webpages.php:237 ../../Zotlabs/Lib/Apps.php:238
+#: ../../include/conversation.php:1884 ../../include/nav.php:491
+msgid "Webpages"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:67
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:60
-msgid "Invalid channel"
+#: ../../Zotlabs/Module/Webpages.php:248
+msgid "Actions"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:158
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:144
-#: ../../include/conversation.php:1900
-msgid "Wikis"
+#: ../../Zotlabs/Module/Webpages.php:249
+msgid "Page Link"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:164
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:150
-msgid "Download"
+#: ../../Zotlabs/Module/Webpages.php:250
+msgid "Page Title"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:168
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:154
-msgid "Wiki name"
+#: ../../Zotlabs/Module/Webpages.php:280
+msgid "Invalid file type."
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:169
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:155
-msgid "Content type"
+#: ../../Zotlabs/Module/Webpages.php:292
+msgid "Error opening zip file"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:178
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:164
-msgid "Create a status post for this wiki"
+#: ../../Zotlabs/Module/Webpages.php:303
+msgid "Invalid folder path."
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:203
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:183
-msgid "Wiki not found"
+#: ../../Zotlabs/Module/Webpages.php:330
+msgid "No webpage elements detected."
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:227
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:208
-msgid "Rename page"
+#: ../../Zotlabs/Module/Webpages.php:405
+msgid "Import complete."
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:231
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:212
-msgid "Error retrieving page content"
+#: ../../Zotlabs/Module/Changeaddr.php:35
+msgid ""
+"Channel name changes are not allowed within 48 hours of changing the account "
+"password."
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:261
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:241
-msgid "Revision Comparison"
+#: ../../Zotlabs/Module/Changeaddr.php:46 ../../include/channel.php:209
+#: ../../include/channel.php:579
+msgid "Reserved nickname. Please choose another."
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:262
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:242
-msgid "Revert"
+#: ../../Zotlabs/Module/Changeaddr.php:51 ../../include/channel.php:214
+#: ../../include/channel.php:584
+msgid ""
+"Nickname has unsupported characters or is already being used on this site."
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:266
-msgid "Short description of your changes (optional)"
+#: ../../Zotlabs/Module/Changeaddr.php:77
+msgid "Change channel nickname/address"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:273
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:251
-msgid "Source"
+#: ../../Zotlabs/Module/Changeaddr.php:78
+msgid "Any/all connections on other networks will be lost!"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:281
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:259
-msgid "New page name"
+#: ../../Zotlabs/Module/Changeaddr.php:80
+msgid "New channel address"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:286
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:264
-#: ../../include/conversation.php:1299
-msgid "Embed image from photo albums"
+#: ../../Zotlabs/Module/Changeaddr.php:81
+msgid "Rename Channel"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:287
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:265
-#: ../../include/conversation.php:1393
-msgid "Embed an image from your albums"
+#: ../../Zotlabs/Module/Editpost.php:38 ../../Zotlabs/Module/Editpost.php:43
+msgid "Item is not editable"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:289
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:267
-#: ../../include/conversation.php:1395 ../../include/conversation.php:1442
-msgid "OK"
+#: ../../Zotlabs/Module/Editpost.php:108 ../../Zotlabs/Module/Rpost.php:178
+msgid "Edit post"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:290
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:268
-#: ../../include/conversation.php:1335
-msgid "Choose images to embed"
+#: ../../Zotlabs/Module/Dreport.php:45
+msgid "Invalid message"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:291
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:269
-#: ../../include/conversation.php:1336
-msgid "Choose an album"
+#: ../../Zotlabs/Module/Dreport.php:78
+msgid "no results"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:292
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:270
-msgid "Choose a different album"
+#: ../../Zotlabs/Module/Dreport.php:93
+msgid "channel sync processed"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:293
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:271
-#: ../../include/conversation.php:1338
-msgid "Error getting album list"
+#: ../../Zotlabs/Module/Dreport.php:97
+msgid "queued"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:294
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:272
-#: ../../include/conversation.php:1339
-msgid "Error getting photo link"
+#: ../../Zotlabs/Module/Dreport.php:101
+msgid "posted"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:295
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:273
-#: ../../include/conversation.php:1340
-msgid "Error getting album"
+#: ../../Zotlabs/Module/Dreport.php:105
+msgid "accepted for delivery"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:364
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:337
-msgid "Error creating wiki. Invalid name."
+#: ../../Zotlabs/Module/Dreport.php:109
+msgid "updated"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:376
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:348
-msgid "Wiki created, but error creating Home page."
+#: ../../Zotlabs/Module/Dreport.php:112
+msgid "update ignored"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:383
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:353
-msgid "Error creating wiki"
+#: ../../Zotlabs/Module/Dreport.php:115
+msgid "permission denied"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:395
-msgid "Wiki delete permission denied."
+#: ../../Zotlabs/Module/Dreport.php:119
+msgid "recipient not found"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:405
-msgid "Error deleting wiki"
+#: ../../Zotlabs/Module/Dreport.php:122
+msgid "mail recalled"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:431
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:400
-msgid "New page created"
+#: ../../Zotlabs/Module/Dreport.php:125
+msgid "duplicate mail received"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:546
-msgid "Cannot delete Home"
+#: ../../Zotlabs/Module/Dreport.php:128
+msgid "mail delivered"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:610
-msgid "Current Revision"
+#: ../../Zotlabs/Module/Dreport.php:148
+#, php-format
+msgid "Delivery report for %1$s"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:610
-msgid "Selected Revision"
+#: ../../Zotlabs/Module/Dreport.php:151 ../../Zotlabs/Widget/Wiki_pages.php:60
+msgid "Options"
msgstr ""
-#: ../../Zotlabs/Module/Wiki.php:660
-msgid "You must be authenticated."
+#: ../../Zotlabs/Module/Dreport.php:152
+msgid "Redeliver"
msgstr ""
#: ../../Zotlabs/Module/Sources.php:37
@@ -6104,8 +6329,8 @@ msgstr ""
msgid "*"
msgstr ""
-#: ../../Zotlabs/Module/Sources.php:96 ../../include/widgets.php:691
-#: ../../include/features.php:213
+#: ../../Zotlabs/Module/Sources.php:96
+#: ../../Zotlabs/Widget/Settings_menu.php:125 ../../include/features.php:218
msgid "Channel Sources"
msgstr ""
@@ -6141,11 +6366,6 @@ msgid ""
"separated)"
msgstr ""
-#: ../../Zotlabs/Module/Sources.php:112 ../../Zotlabs/Module/Sources.php:147
-#: ../../Zotlabs/Module/Settings/Oauth.php:93
-msgid "Optional"
-msgstr ""
-
#: ../../Zotlabs/Module/Sources.php:133 ../../Zotlabs/Module/Sources.php:161
msgid "Source not found."
msgstr ""
@@ -6166,1013 +6386,1159 @@ msgstr ""
msgid "Unable to remove source."
msgstr ""
-#: ../../Zotlabs/Module/Subthread.php:118
+#: ../../Zotlabs/Module/Like.php:19
+msgid "Like/Dislike"
+msgstr ""
+
+#: ../../Zotlabs/Module/Like.php:24
+msgid "This action is restricted to members."
+msgstr ""
+
+#: ../../Zotlabs/Module/Like.php:25
+msgid ""
+"Please <a href=\"rmagic\">login with your $Projectname ID</a> or <a href="
+"\"register\">register as a new $Projectname member</a> to continue."
+msgstr ""
+
+#: ../../Zotlabs/Module/Like.php:105 ../../Zotlabs/Module/Like.php:131
+#: ../../Zotlabs/Module/Like.php:169
+msgid "Invalid request."
+msgstr ""
+
+#: ../../Zotlabs/Module/Like.php:117 ../../include/conversation.php:122
+msgid "channel"
+msgstr ""
+
+#: ../../Zotlabs/Module/Like.php:146
+msgid "thing"
+msgstr ""
+
+#: ../../Zotlabs/Module/Like.php:192
+msgid "Channel unavailable."
+msgstr ""
+
+#: ../../Zotlabs/Module/Like.php:240
+msgid "Previous action reversed."
+msgstr ""
+
+#: ../../Zotlabs/Module/Like.php:423 ../../addon/diaspora/Receiver.php:1453
+#: ../../addon/pubcrawl/as.php:1323 ../../include/conversation.php:160
#, php-format
-msgid "%1$s is following %2$s's %3$s"
+msgid "%1$s likes %2$s's %3$s"
msgstr ""
-#: ../../Zotlabs/Module/Subthread.php:120
+#: ../../Zotlabs/Module/Like.php:425 ../../addon/pubcrawl/as.php:1325
+#: ../../include/conversation.php:163
#, php-format
-msgid "%1$s stopped following %2$s's %3$s"
+msgid "%1$s doesn't like %2$s's %3$s"
msgstr ""
-#: ../../Zotlabs/Module/Suggest.php:39
-msgid ""
-"No suggestions available. If this is a new site, please try again in 24 "
-"hours."
+#: ../../Zotlabs/Module/Like.php:427
+#, php-format
+msgid "%1$s agrees with %2$s's %3$s"
msgstr ""
-#: ../../Zotlabs/Module/Suggest.php:58 ../../include/widgets.php:150
-msgid "Ignore/Hide"
+#: ../../Zotlabs/Module/Like.php:429
+#, php-format
+msgid "%1$s doesn't agree with %2$s's %3$s"
msgstr ""
-#: ../../Zotlabs/Module/Tagger.php:55 ../../include/bbcode.php:274
-msgid "post"
+#: ../../Zotlabs/Module/Like.php:431
+#, php-format
+msgid "%1$s abstains from a decision on %2$s's %3$s"
msgstr ""
-#: ../../Zotlabs/Module/Tagger.php:57 ../../include/conversation.php:150
-#: ../../include/text.php:1964
-msgid "comment"
+#: ../../Zotlabs/Module/Like.php:433
+#, php-format
+msgid "%1$s is attending %2$s's %3$s"
msgstr ""
-#: ../../Zotlabs/Module/Tagger.php:95
+#: ../../Zotlabs/Module/Like.php:435
#, php-format
-msgid "%1$s tagged %2$s's %3$s with %4$s"
+msgid "%1$s is not attending %2$s's %3$s"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Features.php:45
-msgid "Additional Features"
+#: ../../Zotlabs/Module/Like.php:437
+#, php-format
+msgid "%1$s may attend %2$s's %3$s"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Oauth.php:34
-msgid "Name is required"
+#: ../../Zotlabs/Module/Like.php:547
+msgid "Action completed."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Oauth.php:38
-msgid "Key and Secret are required"
+#: ../../Zotlabs/Module/Like.php:548
+msgid "Thank you."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Oauth.php:86
-#: ../../Zotlabs/Module/Settings/Oauth.php:112
-#: ../../Zotlabs/Module/Settings/Oauth.php:148
-msgid "Add application"
+#: ../../Zotlabs/Module/Directory.php:245
+#, php-format
+msgid "%d rating"
+msgid_plural "%d ratings"
+msgstr[0] ""
+msgstr[1] ""
+
+#: ../../Zotlabs/Module/Directory.php:256
+msgid "Gender: "
msgstr ""
-#: ../../Zotlabs/Module/Settings/Oauth.php:89
-msgid "Name of application"
+#: ../../Zotlabs/Module/Directory.php:258
+msgid "Status: "
msgstr ""
-#: ../../Zotlabs/Module/Settings/Oauth.php:90
-#: ../../Zotlabs/Module/Settings/Oauth.php:116
-#: ../../extend/addon/addon/statusnet/statusnet.php:893
-#: ../../extend/addon/addon/twitter/twitter.php:775
-msgid "Consumer Key"
+#: ../../Zotlabs/Module/Directory.php:260
+msgid "Homepage: "
msgstr ""
-#: ../../Zotlabs/Module/Settings/Oauth.php:90
-#: ../../Zotlabs/Module/Settings/Oauth.php:91
-msgid "Automatically generated - change if desired. Max length 20"
+#: ../../Zotlabs/Module/Directory.php:309 ../../include/channel.php:1516
+msgid "Age:"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Oauth.php:91
-#: ../../Zotlabs/Module/Settings/Oauth.php:117
-#: ../../extend/addon/addon/statusnet/statusnet.php:892
-#: ../../extend/addon/addon/twitter/twitter.php:776
-msgid "Consumer Secret"
+#: ../../Zotlabs/Module/Directory.php:314 ../../include/channel.php:1352
+#: ../../include/event.php:52 ../../include/event.php:84
+msgid "Location:"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Oauth.php:92
-#: ../../Zotlabs/Module/Settings/Oauth.php:118
-msgid "Redirect"
+#: ../../Zotlabs/Module/Directory.php:320
+msgid "Description:"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Oauth.php:92
-msgid ""
-"Redirect URI - leave blank unless your application specifically requires this"
+#: ../../Zotlabs/Module/Directory.php:325 ../../include/channel.php:1532
+msgid "Hometown:"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Oauth.php:93
-#: ../../Zotlabs/Module/Settings/Oauth.php:119
-msgid "Icon url"
+#: ../../Zotlabs/Module/Directory.php:327 ../../include/channel.php:1540
+msgid "About:"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Oauth.php:104
-msgid "Application not found."
+#: ../../Zotlabs/Module/Directory.php:328 ../../Zotlabs/Module/Suggest.php:56
+#: ../../Zotlabs/Widget/Follow.php:32 ../../Zotlabs/Widget/Suggestions.php:44
+#: ../../include/conversation.php:1035 ../../include/channel.php:1337
+#: ../../include/connections.php:111
+msgid "Connect"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Oauth.php:147
-msgid "Connected Apps"
+#: ../../Zotlabs/Module/Directory.php:329
+msgid "Public Forum:"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Oauth.php:151
-msgid "Client key starts with"
+#: ../../Zotlabs/Module/Directory.php:332
+msgid "Keywords: "
msgstr ""
-#: ../../Zotlabs/Module/Settings/Oauth.php:152
-msgid "No name"
+#: ../../Zotlabs/Module/Directory.php:335
+msgid "Don't suggest"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Oauth.php:153
-msgid "Remove authorization"
+#: ../../Zotlabs/Module/Directory.php:337
+msgid "Common connections:"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Account.php:20
-msgid "Not valid email."
+#: ../../Zotlabs/Module/Directory.php:386
+msgid "Global Directory"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Account.php:23
-msgid "Protected email address. Cannot change to that email."
+#: ../../Zotlabs/Module/Directory.php:386
+msgid "Local Directory"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Account.php:32
-msgid "System failure storing new email. Please try again."
+#: ../../Zotlabs/Module/Directory.php:392
+msgid "Finding:"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Account.php:40
-msgid "Technical skill level updated"
+#: ../../Zotlabs/Module/Directory.php:395 ../../Zotlabs/Module/Suggest.php:64
+#: ../../include/contact_widgets.php:24
+msgid "Channel Suggestions"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Account.php:56
-msgid "Password verification failed."
+#: ../../Zotlabs/Module/Directory.php:397
+msgid "next page"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Account.php:63
-msgid "Passwords do not match. Password unchanged."
+#: ../../Zotlabs/Module/Directory.php:397
+msgid "previous page"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Account.php:67
-msgid "Empty passwords are not allowed. Password unchanged."
+#: ../../Zotlabs/Module/Directory.php:398
+msgid "Sort options"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Account.php:81
-msgid "Password changed."
+#: ../../Zotlabs/Module/Directory.php:399
+msgid "Alphabetic"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Account.php:83
-msgid "Password update failed. Please try again."
+#: ../../Zotlabs/Module/Directory.php:400
+msgid "Reverse Alphabetic"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Account.php:112
-msgid "Account Settings"
+#: ../../Zotlabs/Module/Directory.php:401
+msgid "Newest to Oldest"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Account.php:113
-msgid "Current Password"
+#: ../../Zotlabs/Module/Directory.php:402
+msgid "Oldest to Newest"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Account.php:114
-msgid "Enter New Password"
+#: ../../Zotlabs/Module/Directory.php:419
+msgid "No entries (some entries may be hidden)."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Account.php:115
-msgid "Confirm New Password"
+#: ../../Zotlabs/Module/Xchan.php:10
+msgid "Xchan Lookup"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Account.php:115
-msgid "Leave password fields blank unless changing"
+#: ../../Zotlabs/Module/Xchan.php:13
+msgid "Lookup xchan beginning with (or webbie): "
msgstr ""
-#: ../../Zotlabs/Module/Settings/Account.php:116
-msgid "Your technical skill level"
+#: ../../Zotlabs/Module/Suggest.php:39
+msgid ""
+"No suggestions available. If this is a new site, please try again in 24 "
+"hours."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Account.php:116
-msgid "Used to provide a member experience matched to your comfort level"
+#: ../../Zotlabs/Module/Suggest.php:58 ../../Zotlabs/Widget/Suggestions.php:46
+msgid "Ignore/Hide"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Account.php:119
-#: ../../Zotlabs/Module/Settings/Channel.php:467
-msgid "Email Address:"
+#: ../../Zotlabs/Module/Oexchange.php:27
+msgid "Unable to find your hub."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Account.php:121
-msgid "Remove this account including all its channels"
+#: ../../Zotlabs/Module/Oexchange.php:41
+msgid "Post successful."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Tokens.php:31
-#, php-format
-msgid "This channel is limited to %d tokens"
+#: ../../Zotlabs/Module/Mail.php:73
+msgid "Unable to lookup recipient."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Tokens.php:37
-msgid "Name and Password are required."
+#: ../../Zotlabs/Module/Mail.php:80
+msgid "Unable to communicate with requested channel."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Tokens.php:77
-msgid "Token saved."
+#: ../../Zotlabs/Module/Mail.php:87
+msgid "Cannot verify requested channel."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Tokens.php:113
-msgid ""
-"Use this form to create temporary access identifiers to share things with "
-"non-members. These identities may be used in Access Control Lists and "
-"visitors may login using these credentials to access private content."
+#: ../../Zotlabs/Module/Mail.php:105
+msgid "Selected channel has private message restrictions. Send failed."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Tokens.php:115
-msgid ""
-"You may also provide <em>dropbox</em> style access links to friends and "
-"associates by adding the Login Password to any specific site URL as shown. "
-"Examples:"
+#: ../../Zotlabs/Module/Mail.php:160
+msgid "Messages"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Tokens.php:150 ../../include/widgets.php:658
-msgid "Guest Access Tokens"
+#: ../../Zotlabs/Module/Mail.php:173
+msgid "message"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Tokens.php:157
-msgid "Login Name"
+#: ../../Zotlabs/Module/Mail.php:214
+msgid "Message recalled."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Tokens.php:158
-msgid "Login Password"
+#: ../../Zotlabs/Module/Mail.php:227
+msgid "Conversation removed."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Tokens.php:159
-msgid "Expires (yyyy-mm-dd)"
+#: ../../Zotlabs/Module/Mail.php:242 ../../Zotlabs/Module/Mail.php:363
+msgid "Expires YYYY-MM-DD HH:MM"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Featured.php:20
-msgid "Affinity Slider settings updated."
+#: ../../Zotlabs/Module/Mail.php:270
+msgid "Requested channel is not in this network"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Featured.php:34
-msgid "No feature settings configured"
+#: ../../Zotlabs/Module/Mail.php:278
+msgid "Send Private Message"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Featured.php:41
-msgid "Default maximum affinity level"
+#: ../../Zotlabs/Module/Mail.php:279 ../../Zotlabs/Module/Mail.php:421
+msgid "To:"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Featured.php:46
-msgid "Default minimum affinity level"
+#: ../../Zotlabs/Module/Mail.php:282 ../../Zotlabs/Module/Mail.php:423
+msgid "Subject:"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Featured.php:50
-msgid "Affinity Slider Settings"
+#: ../../Zotlabs/Module/Mail.php:287 ../../Zotlabs/Module/Mail.php:429
+#: ../../include/conversation.php:1365
+msgid "Attach file"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Featured.php:60
-msgid "Feature/Addon Settings"
+#: ../../Zotlabs/Module/Mail.php:289
+msgid "Send"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:248
-#: ../../extend/addon/addon/logrot/logrot.php:54
-#: ../../extend/addon/addon/msgfooter/msgfooter.php:54
-#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:184
-#: ../../extend/addon/addon/piwik/piwik.php:116
-#: ../../extend/addon/addon/twitter/twitter.php:766
-#: ../../extend/addon/addon/xmpp/xmpp.php:102
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:82
-msgid "Settings updated."
+#: ../../Zotlabs/Module/Mail.php:292 ../../Zotlabs/Module/Mail.php:434
+#: ../../include/conversation.php:1410
+msgid "Set expiration date"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:309
-msgid "Nobody except yourself"
+#: ../../Zotlabs/Module/Mail.php:393
+msgid "Delete message"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:310
-msgid "Only those you specifically allow"
+#: ../../Zotlabs/Module/Mail.php:394
+msgid "Delivery report"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:311
-msgid "Approved connections"
+#: ../../Zotlabs/Module/Mail.php:395
+msgid "Recall message"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:312
-msgid "Any connections"
+#: ../../Zotlabs/Module/Mail.php:397
+msgid "Message has been recalled."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:313
-msgid "Anybody on this website"
+#: ../../Zotlabs/Module/Mail.php:414
+msgid "Delete Conversation"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:314
-msgid "Anybody in this network"
+#: ../../Zotlabs/Module/Mail.php:416
+msgid ""
+"No secure communications available. You <strong>may</strong> be able to "
+"respond from the sender's profile page."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:315
-msgid "Anybody authenticated"
+#: ../../Zotlabs/Module/Mail.php:420
+msgid "Send Reply"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:316
-msgid "Anybody on the internet"
+#: ../../Zotlabs/Module/Mail.php:425
+#, php-format
+msgid "Your message for %s (%s):"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:392
-msgid "Publish your default profile in the network directory"
+#: ../../Zotlabs/Module/Pubsites.php:24 ../../Zotlabs/Widget/Pubsites.php:12
+msgid "Public Hubs"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:397
-msgid "Allow us to suggest you as a potential friend to new members?"
+#: ../../Zotlabs/Module/Pubsites.php:27
+msgid ""
+"The listed hubs allow public registration for the $Projectname network. All "
+"hubs in the network are interlinked so membership on any of them conveys "
+"membership in the network as a whole. Some hubs may require subscription or "
+"provide tiered service plans. The hub itself <strong>may</strong> provide "
+"additional details."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:406
-msgid "Your channel address is"
+#: ../../Zotlabs/Module/Pubsites.php:33
+msgid "Hub URL"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:409
-msgid "Your files/photos are accessible via WebDAV at"
+#: ../../Zotlabs/Module/Pubsites.php:33
+msgid "Access Type"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:458
-msgid "Channel Settings"
+#: ../../Zotlabs/Module/Pubsites.php:33
+msgid "Registration Policy"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:465
-msgid "Basic Settings"
+#: ../../Zotlabs/Module/Pubsites.php:33
+msgid "Stats"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:466
-#: ../../include/channel.php:1255
-msgid "Full Name:"
+#: ../../Zotlabs/Module/Pubsites.php:33
+msgid "Software"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:468
-msgid "Your Timezone:"
+#: ../../Zotlabs/Module/Pubsites.php:49
+msgid "Rate"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:469
-msgid "Default Post Location:"
+#: ../../Zotlabs/Module/Impel.php:41 ../../include/bbcode.php:263
+msgid "webpage"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:469
-msgid "Geographical location to display on your posts"
+#: ../../Zotlabs/Module/Impel.php:46 ../../include/bbcode.php:269
+msgid "block"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:470
-msgid "Use Browser Location:"
+#: ../../Zotlabs/Module/Impel.php:51 ../../include/bbcode.php:266
+msgid "layout"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:472
-msgid "Adult Content"
+#: ../../Zotlabs/Module/Impel.php:58 ../../include/bbcode.php:272
+msgid "menu"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:472
-msgid ""
-"This channel frequently or regularly publishes adult content. (Please tag "
-"any adult material and/or nudity with #NSFW)"
+#: ../../Zotlabs/Module/Impel.php:181
+#, php-format
+msgid "%s element installed"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:474
-msgid "Security and Privacy Settings"
+#: ../../Zotlabs/Module/Impel.php:184
+#, php-format
+msgid "%s element installation failed"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:477
-msgid "Your permissions are already configured. Click to view/adjust"
+#: ../../Zotlabs/Module/Rbmark.php:94
+msgid "Select a bookmark folder"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:479
-msgid "Hide my online presence"
+#: ../../Zotlabs/Module/Rbmark.php:99
+msgid "Save Bookmark"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:479
-msgid "Prevents displaying in your profile that you are online"
+#: ../../Zotlabs/Module/Rbmark.php:100
+msgid "URL of bookmark"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:481
-msgid "Simple Privacy Settings:"
+#: ../../Zotlabs/Module/Rbmark.php:105
+msgid "Or enter new bookmark folder name"
+msgstr ""
+
+#: ../../Zotlabs/Module/Filer.php:52
+msgid "Enter a folder name"
+msgstr ""
+
+#: ../../Zotlabs/Module/Filer.php:52
+msgid "or select an existing folder (doubleclick)"
+msgstr ""
+
+#: ../../Zotlabs/Module/Filer.php:54 ../../Zotlabs/Lib/ThreadItem.php:141
+msgid "Save to Folder"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:482
+#: ../../Zotlabs/Module/Probe.php:30 ../../Zotlabs/Module/Probe.php:34
+#, php-format
+msgid "Fetching URL returns error: %1$s"
+msgstr ""
+
+#: ../../Zotlabs/Module/Register.php:49
+msgid "Maximum daily site registrations exceeded. Please try again tomorrow."
+msgstr ""
+
+#: ../../Zotlabs/Module/Register.php:55
msgid ""
-"Very Public - <em>extremely permissive (should be used with caution)</em>"
+"Please indicate acceptance of the Terms of Service. Registration failed."
+msgstr ""
+
+#: ../../Zotlabs/Module/Register.php:89
+msgid "Passwords do not match."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:483
+#: ../../Zotlabs/Module/Register.php:131
msgid ""
-"Typical - <em>default public, privacy when desired (similar to social "
-"network permissions but with improved privacy)</em>"
+"Registration successful. Please check your email for validation instructions."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:484
-msgid "Private - <em>default private, never open or public</em>"
+#: ../../Zotlabs/Module/Register.php:137
+msgid "Your registration is pending approval by the site owner."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:485
-msgid "Blocked - <em>default blocked to/from everybody</em>"
+#: ../../Zotlabs/Module/Register.php:140
+msgid "Your registration can not be processed."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:487
-msgid "Allow others to tag your posts"
+#: ../../Zotlabs/Module/Register.php:184
+msgid "Registration on this hub is disabled."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:487
-msgid ""
-"Often used by the community to retro-actively flag inappropriate content"
+#: ../../Zotlabs/Module/Register.php:193
+msgid "Registration on this hub is by approval only."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:489
-msgid "Channel Permission Limits"
+#: ../../Zotlabs/Module/Register.php:194
+msgid "<a href=\"pubsites\">Register at another affiliated hub.</a>"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:491
-msgid "Expire other channel content after this many days"
+#: ../../Zotlabs/Module/Register.php:204
+msgid ""
+"This site has exceeded the number of allowed daily account registrations. "
+"Please try again tomorrow."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:491
-msgid "0 or blank to use the website limit."
+#: ../../Zotlabs/Module/Register.php:227
+#, php-format
+msgid "I accept the %s for this website"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:491
+#: ../../Zotlabs/Module/Register.php:229
#, php-format
-msgid "This website expires after %d days."
+msgid "I am over 13 years of age and accept the %s for this website"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:491
-msgid "This website does not expire imported content."
+#: ../../Zotlabs/Module/Register.php:233
+msgid "Your email address"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:491
-msgid "The website limit takes precedence if lower than your limit."
+#: ../../Zotlabs/Module/Register.php:234
+msgid "Choose a password"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:492
-msgid "Maximum Friend Requests/Day:"
+#: ../../Zotlabs/Module/Register.php:235
+msgid "Please re-enter your password"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:492
-msgid "May reduce spam activity"
+#: ../../Zotlabs/Module/Register.php:236
+msgid "Please enter your invitation code"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:493
-msgid "Default Access Control List (ACL)"
+#: ../../Zotlabs/Module/Register.php:241
+msgid "no"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:495
-msgid "Use my default audience setting for the type of object published"
+#: ../../Zotlabs/Module/Register.php:241
+msgid "yes"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:502
-msgid "Channel permissions category:"
+#: ../../Zotlabs/Module/Register.php:256
+msgid "Membership on this site is by invitation only."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:508
-msgid "Maximum private messages per day from unknown people:"
+#: ../../Zotlabs/Module/Register.php:268 ../../boot.php:1620
+#: ../../include/nav.php:189
+msgid "Register"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:508
-msgid "Useful to reduce spamming"
+#: ../../Zotlabs/Module/Register.php:269
+msgid ""
+"This site may require email verification after submitting this form. If you "
+"are returned to a login page, please check your email for instructions."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:511
-msgid "Notification Settings"
+#: ../../Zotlabs/Module/Cover_photo.php:136
+#: ../../Zotlabs/Module/Cover_photo.php:186
+msgid "Cover Photos"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:512
-msgid "By default post a status message when:"
+#: ../../Zotlabs/Module/Cover_photo.php:237 ../../include/items.php:4320
+msgid "female"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:513
-msgid "accepting a friend request"
+#: ../../Zotlabs/Module/Cover_photo.php:238 ../../include/items.php:4321
+#, php-format
+msgid "%1$s updated her %2$s"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:514
-msgid "joining a forum/community"
+#: ../../Zotlabs/Module/Cover_photo.php:239 ../../include/items.php:4322
+msgid "male"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:515
-msgid "making an <em>interesting</em> profile change"
+#: ../../Zotlabs/Module/Cover_photo.php:240 ../../include/items.php:4323
+#, php-format
+msgid "%1$s updated his %2$s"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:516
-msgid "Send a notification email when:"
+#: ../../Zotlabs/Module/Cover_photo.php:242 ../../include/items.php:4325
+#, php-format
+msgid "%1$s updated their %2$s"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:517
-msgid "You receive a connection request"
+#: ../../Zotlabs/Module/Cover_photo.php:244 ../../include/channel.php:1980
+msgid "cover photo"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:518
-msgid "Your connections are confirmed"
+#: ../../Zotlabs/Module/Cover_photo.php:360
+msgid "Upload Cover Photo"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:519
-msgid "Someone writes on your profile wall"
+#: ../../Zotlabs/Module/Help.php:23
+msgid "Documentation Search"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:520
-msgid "Someone writes a followup comment"
+#: ../../Zotlabs/Module/Help.php:80 ../../include/conversation.php:1804
+#: ../../include/nav.php:412
+msgid "About"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:521
-msgid "You receive a private message"
+#: ../../Zotlabs/Module/Help.php:82
+msgid "Administrators"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:522
-msgid "You receive a friend suggestion"
+#: ../../Zotlabs/Module/Help.php:83
+msgid "Developers"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:523
-msgid "You are tagged in a post"
+#: ../../Zotlabs/Module/Help.php:84
+msgid "Tutorials"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:524
-msgid "You are poked/prodded/etc. in a post"
+#: ../../Zotlabs/Module/Help.php:95
+msgid "$Projectname Documentation"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:526
-msgid "Someone likes your post/comment"
+#: ../../Zotlabs/Module/Help.php:96
+msgid "Contents"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:529
-msgid "Show visual notifications including:"
+#: ../../Zotlabs/Module/Display.php:340
+msgid "Item has been removed."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:531
-msgid "Unseen grid activity"
+#: ../../Zotlabs/Module/Tagrm.php:48 ../../Zotlabs/Module/Tagrm.php:98
+msgid "Tag removed"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:532
-msgid "Unseen channel activity"
+#: ../../Zotlabs/Module/Tagrm.php:123
+msgid "Remove Item Tag"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:533
-msgid "Unseen private messages"
+#: ../../Zotlabs/Module/Tagrm.php:125
+msgid "Select a tag to remove: "
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:533
-#: ../../Zotlabs/Module/Settings/Channel.php:538
-#: ../../Zotlabs/Module/Settings/Channel.php:539
-#: ../../Zotlabs/Module/Settings/Channel.php:540
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:343
-msgid "Recommended"
+#: ../../Zotlabs/Module/Network.php:97
+msgid "No such group"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:534
-msgid "Upcoming events"
+#: ../../Zotlabs/Module/Network.php:136
+msgid "No such channel"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:535
-msgid "Events today"
+#: ../../Zotlabs/Module/Network.php:141
+msgid "forum"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:536
-msgid "Upcoming birthdays"
+#: ../../Zotlabs/Module/Network.php:153
+msgid "Search Results For:"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:536
-msgid "Not available in all themes"
+#: ../../Zotlabs/Module/Network.php:221
+msgid "Privacy group is empty"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:537
-msgid "System (personal) notifications"
+#: ../../Zotlabs/Module/Network.php:230
+msgid "Privacy group: "
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:538
-msgid "System info messages"
+#: ../../Zotlabs/Module/Network.php:256
+msgid "Invalid connection."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:539
-msgid "System critical alerts"
+#: ../../Zotlabs/Module/Network.php:275 ../../addon/redred/redred.php:65
+msgid "Invalid channel."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:540
-msgid "New connections"
+#: ../../Zotlabs/Module/Acl.php:351
+msgid "network"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:541
-msgid "System Registrations"
+#: ../../Zotlabs/Module/Home.php:74 ../../Zotlabs/Module/Home.php:82
+#: ../../addon/opensearch/opensearch.php:42
+msgid "$Projectname"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:542
-msgid ""
-"Also show new wall posts, private messages and connections under Notices"
+#: ../../Zotlabs/Module/Home.php:92
+#, php-format
+msgid "Welcome to %s"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:544
-msgid "Notify me of events this many days in advance"
+#: ../../Zotlabs/Module/Filestorage.php:79
+msgid "Permission Denied."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:544
-msgid "Must be greater than 0"
+#: ../../Zotlabs/Module/Filestorage.php:95
+msgid "File not found."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:550
-msgid "Advanced Account/Page Type Settings"
+#: ../../Zotlabs/Module/Filestorage.php:137
+msgid "Edit file permissions"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:551
-msgid "Change the behaviour of this account for special situations"
+#: ../../Zotlabs/Module/Filestorage.php:149
+msgid "Set/edit permissions"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:553
-msgid "Miscellaneous Settings"
+#: ../../Zotlabs/Module/Filestorage.php:150
+msgid "Include all files and sub folders"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:554
-msgid "Default photo upload folder"
+#: ../../Zotlabs/Module/Filestorage.php:151
+msgid "Return to file list"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:554
-#: ../../Zotlabs/Module/Settings/Channel.php:555
-msgid "%Y - current year, %m - current month"
+#: ../../Zotlabs/Module/Filestorage.php:153
+msgid "Copy/paste this code to attach file to a post"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:555
-msgid "Default file upload folder"
+#: ../../Zotlabs/Module/Filestorage.php:154
+msgid "Copy/paste this URL to link file from a web page"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:557
-msgid "Personal menu to display in your channel pages"
+#: ../../Zotlabs/Module/Filestorage.php:156
+msgid "Share this file"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:559
-msgid "Remove this channel."
+#: ../../Zotlabs/Module/Filestorage.php:157
+msgid "Show URL to this file"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:560
-msgid "Firefox Share $Projectname provider"
+#: ../../Zotlabs/Module/Filestorage.php:158
+#: ../../Zotlabs/Storage/Browser.php:351
+msgid "Show in your contacts shared folder"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Channel.php:561
-msgid "Start calendar week on monday"
+#: ../../Zotlabs/Module/Common.php:14
+msgid "No channel."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:137
-msgid "No special theme for mobile devices"
+#: ../../Zotlabs/Module/Common.php:45
+msgid "No connections in common."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:140
+#: ../../Zotlabs/Module/Common.php:65
+msgid "View Common Connections"
+msgstr ""
+
+#: ../../Zotlabs/Module/Viewconnections.php:65
+msgid "No connections."
+msgstr ""
+
+#: ../../Zotlabs/Module/Viewconnections.php:78
#, php-format
-msgid "%s - (Experimental)"
+msgid "Visit %s's profile [%s]"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:191
-msgid "Display Settings"
+#: ../../Zotlabs/Module/Viewconnections.php:107
+msgid "View Connections"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:192
-msgid "Theme Settings"
+#: ../../Zotlabs/Module/Admin.php:97
+msgid "Blocked accounts"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:193
-msgid "Custom Theme Settings"
+#: ../../Zotlabs/Module/Admin.php:98
+msgid "Expired accounts"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:194
-msgid "Content Settings"
+#: ../../Zotlabs/Module/Admin.php:99
+msgid "Expiring accounts"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:200
-msgid "Display Theme:"
+#: ../../Zotlabs/Module/Admin.php:112
+msgid "Clones"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:201
-msgid "Select scheme"
+#: ../../Zotlabs/Module/Admin.php:118
+msgid "Message queues"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:203
-msgid "Mobile Theme:"
+#: ../../Zotlabs/Module/Admin.php:132
+msgid "Your software should be updated"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:204
-msgid "Preload images before rendering the page"
+#: ../../Zotlabs/Module/Admin.php:137
+msgid "Summary"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:204
-msgid ""
-"The subjective page load time will be longer but the page will be ready when "
-"displayed"
+#: ../../Zotlabs/Module/Admin.php:140
+msgid "Registered accounts"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:205
-msgid "Enable user zoom on mobile devices"
+#: ../../Zotlabs/Module/Admin.php:141
+msgid "Pending registrations"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:206
-msgid "Update browser every xx seconds"
+#: ../../Zotlabs/Module/Admin.php:142
+msgid "Registered channels"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:206
-msgid "Minimum of 10 seconds, no maximum"
+#: ../../Zotlabs/Module/Admin.php:143
+msgid "Active plugins"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:207
-msgid "Maximum number of conversations to load at any time:"
+#: ../../Zotlabs/Module/Admin.php:144
+msgid "Version"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:207
-msgid "Maximum of 100 items"
+#: ../../Zotlabs/Module/Admin.php:145
+msgid "Repository version (master)"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:208
-msgid "Show emoticons (smilies) as images"
+#: ../../Zotlabs/Module/Admin.php:146
+msgid "Repository version (dev)"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:209
-msgid "Manual conversation updates"
+#: ../../Zotlabs/Module/Service_limits.php:23
+msgid "No service class restrictions found."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:209
-msgid "Default is on, turning this off may increase screen jumping"
+#: ../../Zotlabs/Module/Rate.php:156
+msgid "Website:"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:210
-msgid "Link post titles to source"
+#: ../../Zotlabs/Module/Rate.php:159
+#, php-format
+msgid "Remote Channel [%s] (not yet known on this site)"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:211
-msgid "System Page Layout Editor - (advanced)"
+#: ../../Zotlabs/Module/Rate.php:160
+msgid "Rating (this information is public)"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:214
-msgid "Use blog/list mode on channel page"
+#: ../../Zotlabs/Module/Rate.php:161
+msgid "Optionally explain your rating (this information is public)"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:214
-#: ../../Zotlabs/Module/Settings/Display.php:215
-msgid "(comments displayed separately)"
+#: ../../Zotlabs/Module/Card_edit.php:128
+msgid "Edit Card"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:215
-msgid "Use blog/list mode on grid page"
+#: ../../Zotlabs/Module/Lostpass.php:19
+msgid "No valid account found."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:216
-msgid "Channel page max height of content (in pixels)"
+#: ../../Zotlabs/Module/Lostpass.php:33
+msgid "Password reset request issued. Check your email."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:216
-#: ../../Zotlabs/Module/Settings/Display.php:217
-msgid "click to expand content exceeding this height"
+#: ../../Zotlabs/Module/Lostpass.php:39 ../../Zotlabs/Module/Lostpass.php:108
+#, php-format
+msgid "Site Member (%s)"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Display.php:217
-msgid "Grid page max height of content (in pixels)"
+#: ../../Zotlabs/Module/Lostpass.php:44 ../../Zotlabs/Module/Lostpass.php:49
+#, php-format
+msgid "Password reset requested at %s"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Permcats.php:37
-msgid "Permission category saved."
+#: ../../Zotlabs/Module/Lostpass.php:68
+msgid ""
+"Request could not be verified. (You may have previously submitted it.) "
+"Password reset failed."
+msgstr ""
+
+#: ../../Zotlabs/Module/Lostpass.php:91 ../../boot.php:1648
+msgid "Password Reset"
+msgstr ""
+
+#: ../../Zotlabs/Module/Lostpass.php:92
+msgid "Your password has been reset as requested."
+msgstr ""
+
+#: ../../Zotlabs/Module/Lostpass.php:93
+msgid "Your new password is"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Permcats.php:63
+#: ../../Zotlabs/Module/Lostpass.php:94
+msgid "Save or copy your new password - and then"
+msgstr ""
+
+#: ../../Zotlabs/Module/Lostpass.php:95
+msgid "click here to login"
+msgstr ""
+
+#: ../../Zotlabs/Module/Lostpass.php:96
msgid ""
-"Use this form to create permission rules for various classes of people or "
-"connections."
+"Your password may be changed from the <em>Settings</em> page after "
+"successful login."
msgstr ""
-#: ../../Zotlabs/Module/Settings/Permcats.php:96 ../../include/widgets.php:666
-msgid "Permission Categories"
+#: ../../Zotlabs/Module/Lostpass.php:117
+#, php-format
+msgid "Your password has changed at %s"
msgstr ""
-#: ../../Zotlabs/Module/Settings/Permcats.php:104
-msgid "Permission Name"
+#: ../../Zotlabs/Module/Lostpass.php:130
+msgid "Forgot your Password?"
msgstr ""
-#: ../../Zotlabs/Module/Tagrm.php:48 ../../Zotlabs/Module/Tagrm.php:98
-msgid "Tag removed"
+#: ../../Zotlabs/Module/Lostpass.php:131
+msgid ""
+"Enter your email address and submit to have your password reset. Then check "
+"your email for further instructions."
msgstr ""
-#: ../../Zotlabs/Module/Tagrm.php:123
-msgid "Remove Item Tag"
+#: ../../Zotlabs/Module/Lostpass.php:132
+msgid "Email Address"
msgstr ""
-#: ../../Zotlabs/Module/Tagrm.php:125
-msgid "Select a tag to remove: "
+#: ../../Zotlabs/Module/Notifications.php:43
+#: ../../Zotlabs/Lib/ThreadItem.php:397
+msgid "Mark all seen"
msgstr ""
-#: ../../Zotlabs/Module/Thing.php:114
-msgid "Thing updated"
+#: ../../Zotlabs/Lib/Techlevels.php:10
+msgid "0. Beginner/Basic"
msgstr ""
-#: ../../Zotlabs/Module/Thing.php:166
-msgid "Object store: failed"
+#: ../../Zotlabs/Lib/Techlevels.php:11
+msgid "1. Novice - not skilled but willing to learn"
msgstr ""
-#: ../../Zotlabs/Module/Thing.php:170
-msgid "Thing added"
+#: ../../Zotlabs/Lib/Techlevels.php:12
+msgid "2. Intermediate - somewhat comfortable"
msgstr ""
-#: ../../Zotlabs/Module/Thing.php:196
-#, php-format
-msgid "OBJ: %1$s %2$s %3$s"
+#: ../../Zotlabs/Lib/Techlevels.php:13
+msgid "3. Advanced - very comfortable"
msgstr ""
-#: ../../Zotlabs/Module/Thing.php:259
-msgid "Show Thing"
+#: ../../Zotlabs/Lib/Techlevels.php:14
+msgid "4. Expert - I can write computer code"
msgstr ""
-#: ../../Zotlabs/Module/Thing.php:266
-msgid "item not found."
+#: ../../Zotlabs/Lib/Techlevels.php:15
+msgid "5. Wizard - I probably know more than you do"
msgstr ""
-#: ../../Zotlabs/Module/Thing.php:299
-msgid "Edit Thing"
+#: ../../Zotlabs/Lib/Apps.php:225
+msgid "Site Admin"
msgstr ""
-#: ../../Zotlabs/Module/Thing.php:301 ../../Zotlabs/Module/Thing.php:355
-msgid "Select a profile"
+#: ../../Zotlabs/Lib/Apps.php:226 ../../addon/buglink/buglink.php:16
+msgid "Report Bug"
msgstr ""
-#: ../../Zotlabs/Module/Thing.php:305 ../../Zotlabs/Module/Thing.php:358
-msgid "Post an activity"
+#: ../../Zotlabs/Lib/Apps.php:227
+msgid "View Bookmarks"
msgstr ""
-#: ../../Zotlabs/Module/Thing.php:305 ../../Zotlabs/Module/Thing.php:358
-msgid "Only sends to viewers of the applicable profile"
+#: ../../Zotlabs/Lib/Apps.php:228
+msgid "My Chatrooms"
msgstr ""
-#: ../../Zotlabs/Module/Thing.php:307 ../../Zotlabs/Module/Thing.php:360
-msgid "Name of thing e.g. something"
+#: ../../Zotlabs/Lib/Apps.php:230
+msgid "Firefox Share"
msgstr ""
-#: ../../Zotlabs/Module/Thing.php:309 ../../Zotlabs/Module/Thing.php:361
-msgid "URL of thing (optional)"
+#: ../../Zotlabs/Lib/Apps.php:231
+msgid "Remote Diagnostics"
msgstr ""
-#: ../../Zotlabs/Module/Thing.php:311 ../../Zotlabs/Module/Thing.php:362
-msgid "URL for photo of thing (optional)"
+#: ../../Zotlabs/Lib/Apps.php:232 ../../include/features.php:342
+msgid "Suggest Channels"
msgstr ""
-#: ../../Zotlabs/Module/Thing.php:353
-msgid "Add Thing to your Profile"
+#: ../../Zotlabs/Lib/Apps.php:233 ../../boot.php:1639 ../../include/nav.php:153
+#: ../../include/nav.php:157
+msgid "Login"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:65
-msgid "Unable to lookup recipient."
+#: ../../Zotlabs/Lib/Apps.php:235 ../../include/nav.php:98
+msgid "Activity"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:72
-msgid "Unable to communicate with requested channel."
+#: ../../Zotlabs/Lib/Apps.php:239 ../../include/conversation.php:1900
+#: ../../include/features.php:95 ../../include/nav.php:507
+msgid "Wiki"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:79
-msgid "Cannot verify requested channel."
+#: ../../Zotlabs/Lib/Apps.php:240 ../../include/nav.php:102
+msgid "Channel Home"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:97
-msgid "Selected channel has private message restrictions. Send failed."
+#: ../../Zotlabs/Lib/Apps.php:243 ../../include/conversation.php:1833
+#: ../../include/conversation.php:1836 ../../include/nav.php:124
+#: ../../include/nav.php:441 ../../include/nav.php:444
+msgid "Events"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:178
-msgid "Messages"
+#: ../../Zotlabs/Lib/Apps.php:244
+msgid "Directory"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:213
-msgid "Message recalled."
+#: ../../Zotlabs/Lib/Apps.php:246 ../../include/nav.php:116
+msgid "Mail"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:226
-msgid "Conversation removed."
+#: ../../Zotlabs/Lib/Apps.php:249
+msgid "Chat"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:240 ../../Zotlabs/Module/Mail.php:349
-#: ../../Zotlabs/Module/Chat.php:205 ../../include/conversation.php:1330
-msgid "Please enter a link URL:"
+#: ../../Zotlabs/Lib/Apps.php:251
+msgid "Probe"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:241 ../../Zotlabs/Module/Mail.php:350
-msgid "Expires YYYY-MM-DD HH:MM"
+#: ../../Zotlabs/Lib/Apps.php:252
+msgid "Suggest"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:269
-msgid "Requested channel is not in this network"
+#: ../../Zotlabs/Lib/Apps.php:253
+msgid "Random Channel"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:277
-msgid "Send Private Message"
+#: ../../Zotlabs/Lib/Apps.php:254
+msgid "Invite"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:278 ../../Zotlabs/Module/Mail.php:403
-msgid "To:"
+#: ../../Zotlabs/Lib/Apps.php:255 ../../Zotlabs/Widget/Admin.php:26
+msgid "Features"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:281 ../../Zotlabs/Module/Mail.php:405
-msgid "Subject:"
+#: ../../Zotlabs/Lib/Apps.php:256 ../../addon/openid/MysqlProvider.php:69
+msgid "Language"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:286 ../../Zotlabs/Module/Mail.php:411
-#: ../../include/conversation.php:1390
-msgid "Attach file"
+#: ../../Zotlabs/Lib/Apps.php:257
+msgid "Post"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:288
-msgid "Send"
+#: ../../Zotlabs/Lib/Apps.php:258 ../../addon/openid/MysqlProvider.php:58
+#: ../../addon/openid/MysqlProvider.php:59
+#: ../../addon/openid/MysqlProvider.php:60
+msgid "Profile Photo"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:291 ../../Zotlabs/Module/Mail.php:416
-#: ../../include/conversation.php:1435
-msgid "Set expiration date"
+#: ../../Zotlabs/Lib/Apps.php:397
+msgid "Purchase"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:293 ../../Zotlabs/Module/Mail.php:418
-#: ../../Zotlabs/Module/Chat.php:206 ../../Zotlabs/Lib/ThreadItem.php:743
-#: ../../include/conversation.php:1440
-msgid "Encrypt text"
+#: ../../Zotlabs/Lib/Apps.php:401
+msgid "Undelete"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:375
-msgid "Delete message"
+#: ../../Zotlabs/Lib/Apps.php:407
+msgid "Add to app-tray"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:376
-msgid "Delivery report"
+#: ../../Zotlabs/Lib/Apps.php:408
+msgid "Remove from app-tray"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:377
-msgid "Recall message"
+#: ../../Zotlabs/Lib/Permcat.php:58
+msgctxt "permcat"
+msgid "default"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:379
-msgid "Message has been recalled."
+#: ../../Zotlabs/Lib/Permcat.php:96
+msgctxt "permcat"
+msgid "follower"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:396
-msgid "Delete Conversation"
+#: ../../Zotlabs/Lib/Permcat.php:100
+msgctxt "permcat"
+msgid "contributor"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:398
-msgid ""
-"No secure communications available. You <strong>may</strong> be able to "
-"respond from the sender's profile page."
+#: ../../Zotlabs/Lib/Permcat.php:104
+msgctxt "permcat"
+msgid "publisher"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:402
-msgid "Send Reply"
+#: ../../Zotlabs/Lib/NativeWikiPage.php:42
+#: ../../Zotlabs/Lib/NativeWikiPage.php:90
+msgid "(No Title)"
msgstr ""
-#: ../../Zotlabs/Module/Mail.php:407
-#, php-format
-msgid "Your message for %s (%s):"
+#: ../../Zotlabs/Lib/NativeWikiPage.php:104
+msgid "Wiki page create failed."
msgstr ""
-#: ../../Zotlabs/Module/Viewconnections.php:65
-msgid "No connections."
+#: ../../Zotlabs/Lib/NativeWikiPage.php:117
+msgid "Wiki not found."
msgstr ""
-#: ../../Zotlabs/Module/Viewconnections.php:78
-#, php-format
-msgid "Visit %s's profile [%s]"
+#: ../../Zotlabs/Lib/NativeWikiPage.php:128
+msgid "Destination name already exists"
msgstr ""
-#: ../../Zotlabs/Module/Viewconnections.php:107
-msgid "View Connections"
+#: ../../Zotlabs/Lib/NativeWikiPage.php:160
+#: ../../Zotlabs/Lib/NativeWikiPage.php:355
+msgid "Page not found"
msgstr ""
-#: ../../Zotlabs/Module/Viewsrc.php:44
-msgid "Source of Item"
+#: ../../Zotlabs/Lib/NativeWikiPage.php:191
+msgid "Error reading page content"
msgstr ""
-#: ../../Zotlabs/Module/Chat.php:181
-msgid "Room not found"
+#: ../../Zotlabs/Lib/NativeWikiPage.php:347
+#: ../../Zotlabs/Lib/NativeWikiPage.php:396
+#: ../../Zotlabs/Lib/NativeWikiPage.php:463
+#: ../../Zotlabs/Lib/NativeWikiPage.php:504
+msgid "Error reading wiki"
msgstr ""
-#: ../../Zotlabs/Module/Chat.php:197
-msgid "Leave Room"
+#: ../../Zotlabs/Lib/NativeWikiPage.php:384
+msgid "Page update failed."
msgstr ""
-#: ../../Zotlabs/Module/Chat.php:198
-msgid "Delete Room"
+#: ../../Zotlabs/Lib/NativeWikiPage.php:418
+msgid "Nothing deleted"
msgstr ""
-#: ../../Zotlabs/Module/Chat.php:199
-msgid "I am away right now"
+#: ../../Zotlabs/Lib/NativeWikiPage.php:484
+msgid "Compare: object not found."
msgstr ""
-#: ../../Zotlabs/Module/Chat.php:200
-msgid "I am online"
+#: ../../Zotlabs/Lib/NativeWikiPage.php:490
+msgid "Page updated"
msgstr ""
-#: ../../Zotlabs/Module/Chat.php:202
-msgid "Bookmark this room"
+#: ../../Zotlabs/Lib/NativeWikiPage.php:493
+msgid "Untitled"
msgstr ""
-#: ../../Zotlabs/Module/Chat.php:231
-msgid "New Chatroom"
+#: ../../Zotlabs/Lib/NativeWikiPage.php:499
+msgid "Wiki resource_id required for git commit"
msgstr ""
-#: ../../Zotlabs/Module/Chat.php:232
-msgid "Chatroom name"
+#: ../../Zotlabs/Lib/NativeWikiPage.php:555
+#: ../../Zotlabs/Widget/Wiki_page_history.php:23
+msgctxt "wiki_history"
+msgid "Message"
msgstr ""
-#: ../../Zotlabs/Module/Chat.php:233
-msgid "Expiration of chats (minutes)"
+#: ../../Zotlabs/Lib/NativeWikiPage.php:593
+#: ../../addon/gitwiki/gitwiki_backend.php:579 ../../include/bbcode.php:672
+#: ../../include/bbcode.php:818
+msgid "Different viewers will see this text differently"
+msgstr ""
+
+#: ../../Zotlabs/Lib/PermissionDescription.php:34
+#: ../../include/acl_selectors.php:128
+msgid "Visible to your default audience"
+msgstr ""
+
+#: ../../Zotlabs/Lib/PermissionDescription.php:107
+#: ../../include/acl_selectors.php:201
+msgid "Only me"
+msgstr ""
+
+#: ../../Zotlabs/Lib/PermissionDescription.php:108
+msgid "Public"
+msgstr ""
+
+#: ../../Zotlabs/Lib/PermissionDescription.php:109
+msgid "Anybody in the $Projectname network"
msgstr ""
-#: ../../Zotlabs/Module/Chat.php:249
+#: ../../Zotlabs/Lib/PermissionDescription.php:110
#, php-format
-msgid "%1$s's Chatrooms"
+msgid "Any account on %s"
msgstr ""
-#: ../../Zotlabs/Module/Chat.php:254
-msgid "No chatrooms available"
+#: ../../Zotlabs/Lib/PermissionDescription.php:111
+msgid "Any of my connections"
msgstr ""
-#: ../../Zotlabs/Module/Chat.php:258
-msgid "Expiration"
+#: ../../Zotlabs/Lib/PermissionDescription.php:112
+msgid "Only connections I specifically allow"
msgstr ""
-#: ../../Zotlabs/Module/Chat.php:259
-msgid "min"
+#: ../../Zotlabs/Lib/PermissionDescription.php:113
+msgid "Anybody authenticated (could include visitors from other networks)"
msgstr ""
-#: ../../Zotlabs/Module/Xchan.php:10
-msgid "Xchan Lookup"
+#: ../../Zotlabs/Lib/PermissionDescription.php:114
+msgid "Any connections including those who haven't yet been approved"
msgstr ""
-#: ../../Zotlabs/Module/Xchan.php:13
-msgid "Lookup xchan beginning with (or webbie): "
+#: ../../Zotlabs/Lib/PermissionDescription.php:150
+msgid ""
+"This is your default setting for the audience of your normal stream, and "
+"posts."
+msgstr ""
+
+#: ../../Zotlabs/Lib/PermissionDescription.php:151
+msgid ""
+"This is your default setting for who can view your default channel profile"
+msgstr ""
+
+#: ../../Zotlabs/Lib/PermissionDescription.php:152
+msgid "This is your default setting for who can view your connections"
+msgstr ""
+
+#: ../../Zotlabs/Lib/PermissionDescription.php:153
+msgid ""
+"This is your default setting for who can view your file storage and photos"
+msgstr ""
+
+#: ../../Zotlabs/Lib/PermissionDescription.php:154
+msgid "This is your default setting for the audience of your webpages"
msgstr ""
#: ../../Zotlabs/Lib/Chatroom.php:27
@@ -7195,22 +7561,20 @@ msgstr ""
msgid "Room is full"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:60 ../../include/network.php:1924
+#: ../../Zotlabs/Lib/Enotify.php:60
msgid "$Projectname Notification"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:61 ../../extend/addon/addon/diaspora/p.php:46
-#: ../../extend/addon/addon/diaspora/util.php:218
-#: ../../extend/addon/addon/diaspora/util.php:231
-#: ../../include/network.php:1925
+#: ../../Zotlabs/Lib/Enotify.php:61 ../../addon/diaspora/util.php:283
+#: ../../addon/diaspora/util.php:296 ../../addon/diaspora/p.php:48
msgid "$projectname"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:63 ../../include/network.php:1927
+#: ../../Zotlabs/Lib/Enotify.php:63
msgid "Thank You,"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:65 ../../include/network.php:1929
+#: ../../Zotlabs/Lib/Enotify.php:65 ../../addon/hubwall/hubwall.php:33
#, php-format
msgid "%s Administrator"
msgstr ""
@@ -7244,3768 +7608,3530 @@ msgstr ""
msgid "Please visit %s to view and/or reply to your private messages."
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:183
+#: ../../Zotlabs/Lib/Enotify.php:184
#, php-format
msgid "%1$s, %2$s commented on [zrl=%3$s]a %4$s[/zrl]"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:191
+#: ../../Zotlabs/Lib/Enotify.php:192
#, php-format
msgid "%1$s, %2$s commented on [zrl=%3$s]%4$s's %5$s[/zrl]"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:200
+#: ../../Zotlabs/Lib/Enotify.php:201
#, php-format
msgid "%1$s, %2$s commented on [zrl=%3$s]your %4$s[/zrl]"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:211
+#: ../../Zotlabs/Lib/Enotify.php:213
+#, php-format
+msgid "[$Projectname:Notify] Moderated Comment to conversation #%1$d by %2$s"
+msgstr ""
+
+#: ../../Zotlabs/Lib/Enotify.php:215
#, php-format
msgid "[$Projectname:Notify] Comment to conversation #%1$d by %2$s"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:212
+#: ../../Zotlabs/Lib/Enotify.php:216
#, php-format
msgid "%1$s, %2$s commented on an item/conversation you have been following."
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:215 ../../Zotlabs/Lib/Enotify.php:292
-#: ../../Zotlabs/Lib/Enotify.php:309 ../../Zotlabs/Lib/Enotify.php:335
-#: ../../Zotlabs/Lib/Enotify.php:353 ../../Zotlabs/Lib/Enotify.php:367
+#: ../../Zotlabs/Lib/Enotify.php:219 ../../Zotlabs/Lib/Enotify.php:301
+#: ../../Zotlabs/Lib/Enotify.php:318 ../../Zotlabs/Lib/Enotify.php:344
+#: ../../Zotlabs/Lib/Enotify.php:362 ../../Zotlabs/Lib/Enotify.php:376
#, php-format
msgid "Please visit %s to view and/or reply to the conversation."
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:273
+#: ../../Zotlabs/Lib/Enotify.php:223 ../../Zotlabs/Lib/Enotify.php:224
+#, php-format
+msgid "Please visit %s to approve or reject this comment."
+msgstr ""
+
+#: ../../Zotlabs/Lib/Enotify.php:282
#, php-format
msgid "%1$s, %2$s liked [zrl=%3$s]your %4$s[/zrl]"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:288
+#: ../../Zotlabs/Lib/Enotify.php:297
#, php-format
msgid "[$Projectname:Notify] Like received to conversation #%1$d by %2$s"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:289
+#: ../../Zotlabs/Lib/Enotify.php:298
#, php-format
msgid "%1$s, %2$s liked an item/conversation you created."
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:300
+#: ../../Zotlabs/Lib/Enotify.php:309
#, php-format
msgid "[$Projectname:Notify] %s posted to your profile wall"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:302
+#: ../../Zotlabs/Lib/Enotify.php:311
#, php-format
msgid "%1$s, %2$s posted to your profile wall at %3$s"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:304
+#: ../../Zotlabs/Lib/Enotify.php:313
#, php-format
msgid "%1$s, %2$s posted to [zrl=%3$s]your wall[/zrl]"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:328
+#: ../../Zotlabs/Lib/Enotify.php:337
#, php-format
msgid "[$Projectname:Notify] %s tagged you"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:329
+#: ../../Zotlabs/Lib/Enotify.php:338
#, php-format
msgid "%1$s, %2$s tagged you at %3$s"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:330
+#: ../../Zotlabs/Lib/Enotify.php:339
#, php-format
msgid "%1$s, %2$s [zrl=%3$s]tagged you[/zrl]."
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:342
+#: ../../Zotlabs/Lib/Enotify.php:351
#, php-format
msgid "[$Projectname:Notify] %1$s poked you"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:343
+#: ../../Zotlabs/Lib/Enotify.php:352
#, php-format
msgid "%1$s, %2$s poked you at %3$s"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:344
+#: ../../Zotlabs/Lib/Enotify.php:353
#, php-format
msgid "%1$s, %2$s [zrl=%2$s]poked you[/zrl]."
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:360
+#: ../../Zotlabs/Lib/Enotify.php:369
#, php-format
msgid "[$Projectname:Notify] %s tagged your post"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:361
+#: ../../Zotlabs/Lib/Enotify.php:370
#, php-format
msgid "%1$s, %2$s tagged your post at %3$s"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:362
+#: ../../Zotlabs/Lib/Enotify.php:371
#, php-format
msgid "%1$s, %2$s tagged [zrl=%3$s]your post[/zrl]"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:374
+#: ../../Zotlabs/Lib/Enotify.php:383
msgid "[$Projectname:Notify] Introduction received"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:375
+#: ../../Zotlabs/Lib/Enotify.php:384
#, php-format
msgid "%1$s, you've received an new connection request from '%2$s' at %3$s"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:376
+#: ../../Zotlabs/Lib/Enotify.php:385
#, php-format
msgid ""
"%1$s, you've received [zrl=%2$s]a new connection request[/zrl] from %3$s."
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:380 ../../Zotlabs/Lib/Enotify.php:399
+#: ../../Zotlabs/Lib/Enotify.php:389 ../../Zotlabs/Lib/Enotify.php:408
#, php-format
msgid "You may visit their profile at %s"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:382
+#: ../../Zotlabs/Lib/Enotify.php:391
#, php-format
msgid "Please visit %s to approve or reject the connection request."
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:389
+#: ../../Zotlabs/Lib/Enotify.php:398
msgid "[$Projectname:Notify] Friend suggestion received"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:390
+#: ../../Zotlabs/Lib/Enotify.php:399
#, php-format
msgid "%1$s, you've received a friend suggestion from '%2$s' at %3$s"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:391
+#: ../../Zotlabs/Lib/Enotify.php:400
#, php-format
msgid ""
"%1$s, you've received [zrl=%2$s]a friend suggestion[/zrl] for %3$s from %4$s."
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:397
+#: ../../Zotlabs/Lib/Enotify.php:406
msgid "Name:"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:398
+#: ../../Zotlabs/Lib/Enotify.php:407
msgid "Photo:"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:401
+#: ../../Zotlabs/Lib/Enotify.php:410
#, php-format
msgid "Please visit %s to approve or reject the suggestion."
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:619
+#: ../../Zotlabs/Lib/Enotify.php:629
msgid "[$Projectname:Notify]"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:779
+#: ../../Zotlabs/Lib/Enotify.php:789
msgid "created a new post"
msgstr ""
-#: ../../Zotlabs/Lib/Enotify.php:780
+#: ../../Zotlabs/Lib/Enotify.php:790
#, php-format
msgid "commented on %s's post"
msgstr ""
-#: ../../Zotlabs/Lib/PermissionDescription.php:34
-#: ../../include/acl_selectors.php:128
-msgid "Visible to your default audience"
-msgstr ""
-
-#: ../../Zotlabs/Lib/PermissionDescription.php:107
-#: ../../include/acl_selectors.php:191
-msgid "Only me"
-msgstr ""
-
-#: ../../Zotlabs/Lib/PermissionDescription.php:108
-msgid "Public"
+#: ../../Zotlabs/Lib/NativeWiki.php:151
+msgid "Wiki updated successfully"
msgstr ""
-#: ../../Zotlabs/Lib/PermissionDescription.php:109
-msgid "Anybody in the $Projectname network"
+#: ../../Zotlabs/Lib/NativeWiki.php:198
+msgid "Wiki files deleted successfully"
msgstr ""
-#: ../../Zotlabs/Lib/PermissionDescription.php:110
+#: ../../Zotlabs/Lib/DB_Upgrade.php:95
#, php-format
-msgid "Any account on %s"
-msgstr ""
-
-#: ../../Zotlabs/Lib/PermissionDescription.php:111
-msgid "Any of my connections"
-msgstr ""
-
-#: ../../Zotlabs/Lib/PermissionDescription.php:112
-msgid "Only connections I specifically allow"
-msgstr ""
-
-#: ../../Zotlabs/Lib/PermissionDescription.php:113
-msgid "Anybody authenticated (could include visitors from other networks)"
-msgstr ""
-
-#: ../../Zotlabs/Lib/PermissionDescription.php:114
-msgid "Any connections including those who haven't yet been approved"
-msgstr ""
-
-#: ../../Zotlabs/Lib/PermissionDescription.php:150
-msgid ""
-"This is your default setting for the audience of your normal stream, and "
-"posts."
-msgstr ""
-
-#: ../../Zotlabs/Lib/PermissionDescription.php:151
-msgid ""
-"This is your default setting for who can view your default channel profile"
-msgstr ""
-
-#: ../../Zotlabs/Lib/PermissionDescription.php:152
-msgid "This is your default setting for who can view your connections"
-msgstr ""
-
-#: ../../Zotlabs/Lib/PermissionDescription.php:153
-msgid ""
-"This is your default setting for who can view your file storage and photos"
+msgid "Update Error at %s"
msgstr ""
-#: ../../Zotlabs/Lib/PermissionDescription.php:154
-msgid "This is your default setting for the audience of your webpages"
+#: ../../Zotlabs/Lib/DB_Upgrade.php:101
+#, php-format
+msgid "Update %s failed. See error logs."
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:95 ../../include/conversation.php:663
+#: ../../Zotlabs/Lib/ThreadItem.php:97 ../../include/conversation.php:681
msgid "Private Message"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:132 ../../include/conversation.php:655
+#: ../../Zotlabs/Lib/ThreadItem.php:137 ../../include/conversation.php:673
msgid "Select"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:136
-msgid "Save to Folder"
-msgstr ""
-
-#: ../../Zotlabs/Lib/ThreadItem.php:157
+#: ../../Zotlabs/Lib/ThreadItem.php:162
msgid "I will attend"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:157
+#: ../../Zotlabs/Lib/ThreadItem.php:162
msgid "I will not attend"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:157
+#: ../../Zotlabs/Lib/ThreadItem.php:162
msgid "I might attend"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:167
+#: ../../Zotlabs/Lib/ThreadItem.php:172
msgid "I agree"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:167
+#: ../../Zotlabs/Lib/ThreadItem.php:172
msgid "I disagree"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:167
+#: ../../Zotlabs/Lib/ThreadItem.php:172
msgid "I abstain"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:223
+#: ../../Zotlabs/Lib/ThreadItem.php:228
msgid "Add Star"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:224
+#: ../../Zotlabs/Lib/ThreadItem.php:229
msgid "Remove Star"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:225
+#: ../../Zotlabs/Lib/ThreadItem.php:230
msgid "Toggle Star Status"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:229
+#: ../../Zotlabs/Lib/ThreadItem.php:234
msgid "starred"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:239 ../../include/conversation.php:670
+#: ../../Zotlabs/Lib/ThreadItem.php:244 ../../include/conversation.php:688
msgid "Message signature validated"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:240 ../../include/conversation.php:671
+#: ../../Zotlabs/Lib/ThreadItem.php:245 ../../include/conversation.php:689
msgid "Message signature incorrect"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:248
+#: ../../Zotlabs/Lib/ThreadItem.php:253
msgid "Add Tag"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:268 ../../include/taxonomy.php:316
+#: ../../Zotlabs/Lib/ThreadItem.php:271 ../../include/taxonomy.php:433
msgid "like"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:269 ../../include/taxonomy.php:317
+#: ../../Zotlabs/Lib/ThreadItem.php:272 ../../include/taxonomy.php:434
msgid "dislike"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:273
+#: ../../Zotlabs/Lib/ThreadItem.php:276
msgid "Share This"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:273
+#: ../../Zotlabs/Lib/ThreadItem.php:276
msgid "share"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:282
+#: ../../Zotlabs/Lib/ThreadItem.php:285
msgid "Delivery Report"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:300
+#: ../../Zotlabs/Lib/ThreadItem.php:303
#, php-format
msgid "%d comment"
msgid_plural "%d comments"
msgstr[0] ""
msgstr[1] ""
-#: ../../Zotlabs/Lib/ThreadItem.php:329 ../../Zotlabs/Lib/ThreadItem.php:330
+#: ../../Zotlabs/Lib/ThreadItem.php:333 ../../Zotlabs/Lib/ThreadItem.php:334
#, php-format
msgid "View %s's profile - %s"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:333
+#: ../../Zotlabs/Lib/ThreadItem.php:337
msgid "to"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:334
+#: ../../Zotlabs/Lib/ThreadItem.php:338
msgid "via"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:335
+#: ../../Zotlabs/Lib/ThreadItem.php:339
msgid "Wall-to-Wall"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:336
+#: ../../Zotlabs/Lib/ThreadItem.php:340
msgid "via Wall-To-Wall:"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:350 ../../include/conversation.php:717
+#: ../../Zotlabs/Lib/ThreadItem.php:353 ../../include/conversation.php:747
#, php-format
msgid "from %s"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:353 ../../include/conversation.php:720
+#: ../../Zotlabs/Lib/ThreadItem.php:356 ../../include/conversation.php:750
#, php-format
msgid "last edited: %s"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:354 ../../include/conversation.php:721
+#: ../../Zotlabs/Lib/ThreadItem.php:357 ../../include/conversation.php:751
#, php-format
msgid "Expires: %s"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:360
+#: ../../Zotlabs/Lib/ThreadItem.php:363
msgid "Attend"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:361
+#: ../../Zotlabs/Lib/ThreadItem.php:364
msgid "Attendance Options"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:362
+#: ../../Zotlabs/Lib/ThreadItem.php:365
msgid "Vote"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:363
+#: ../../Zotlabs/Lib/ThreadItem.php:366
msgid "Voting Options"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:383
-#: ../../extend/addon/addon/bookmarker/bookmarker.php:38
+#: ../../Zotlabs/Lib/ThreadItem.php:387
+#: ../../addon/bookmarker/bookmarker.php:38
msgid "Save Bookmarks"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:384
+#: ../../Zotlabs/Lib/ThreadItem.php:388
msgid "Add to Calendar"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:393
-msgid "Mark all seen"
+#: ../../Zotlabs/Lib/ThreadItem.php:415 ../../include/conversation.php:471
+msgid "This is an unsaved preview"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:442 ../../include/js_strings.php:7
+#: ../../Zotlabs/Lib/ThreadItem.php:447 ../../include/js_strings.php:7
#, php-format
msgid "%s show all"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:732 ../../include/conversation.php:1385
+#: ../../Zotlabs/Lib/ThreadItem.php:744 ../../include/conversation.php:1360
msgid "Bold"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:733 ../../include/conversation.php:1386
+#: ../../Zotlabs/Lib/ThreadItem.php:745 ../../include/conversation.php:1361
msgid "Italic"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:734 ../../include/conversation.php:1387
+#: ../../Zotlabs/Lib/ThreadItem.php:746 ../../include/conversation.php:1362
msgid "Underline"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:735 ../../include/conversation.php:1388
+#: ../../Zotlabs/Lib/ThreadItem.php:747 ../../include/conversation.php:1363
msgid "Quote"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:736 ../../include/conversation.php:1389
+#: ../../Zotlabs/Lib/ThreadItem.php:748 ../../include/conversation.php:1364
msgid "Code"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:737
+#: ../../Zotlabs/Lib/ThreadItem.php:749
msgid "Image"
msgstr ""
-#: ../../Zotlabs/Lib/ThreadItem.php:738
-msgid "Insert Link"
-msgstr ""
-
-#: ../../Zotlabs/Lib/ThreadItem.php:739
-msgid "Video"
+#: ../../Zotlabs/Lib/ThreadItem.php:750
+msgid "Attach File"
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:212
-msgid "Site Admin"
+#: ../../Zotlabs/Lib/ThreadItem.php:751
+msgid "Insert Link"
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:213
-#: ../../extend/addon/addon/buglink/buglink.php:16
-msgid "Report Bug"
+#: ../../Zotlabs/Lib/ThreadItem.php:752
+msgid "Video"
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:214
-msgid "View Bookmarks"
+#: ../../Zotlabs/Lib/ThreadItem.php:762
+msgid "Your full name (required)"
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:215
-msgid "My Chatrooms"
+#: ../../Zotlabs/Lib/ThreadItem.php:763
+msgid "Your email address (required)"
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:217
-msgid "Firefox Share"
+#: ../../Zotlabs/Lib/ThreadItem.php:764
+msgid "Your website URL (optional)"
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:218
-msgid "Remote Diagnostics"
+#: ../../Zotlabs/Zot/Auth.php:152
+msgid ""
+"Remote authentication blocked. You are logged into this site locally. Please "
+"logout and retry."
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:219 ../../include/features.php:337
-msgid "Suggest Channels"
+#: ../../Zotlabs/Zot/Auth.php:264 ../../addon/openid/Mod_Openid.php:76
+#: ../../addon/openid/Mod_Openid.php:178
+#, php-format
+msgid "Welcome %s. Remote authentication successful."
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:220 ../../include/nav.php:130
-#: ../../boot.php:1732
-msgid "Login"
+#: ../../Zotlabs/Storage/Browser.php:107 ../../Zotlabs/Storage/Browser.php:238
+msgid "parent"
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:222 ../../include/nav.php:194
-msgid "Grid"
+#: ../../Zotlabs/Storage/Browser.php:131 ../../include/text.php:2707
+msgid "Collection"
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:226 ../../include/conversation.php:1903
-#: ../../include/features.php:99
-msgid "Wiki"
+#: ../../Zotlabs/Storage/Browser.php:134
+msgid "Principal"
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:227 ../../include/nav.php:198
-msgid "Channel Home"
+#: ../../Zotlabs/Storage/Browser.php:137
+msgid "Addressbook"
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:230 ../../include/conversation.php:1853
-#: ../../include/conversation.php:1856 ../../include/nav.php:218
-msgid "Events"
+#: ../../Zotlabs/Storage/Browser.php:140
+msgid "Calendar"
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:231 ../../include/nav.php:182
-msgid "Directory"
+#: ../../Zotlabs/Storage/Browser.php:143
+msgid "Schedule Inbox"
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:233 ../../include/nav.php:210
-msgid "Mail"
+#: ../../Zotlabs/Storage/Browser.php:146
+msgid "Schedule Outbox"
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:236
-msgid "Chat"
+#: ../../Zotlabs/Storage/Browser.php:226
+msgid "Total"
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:238
-msgid "Probe"
+#: ../../Zotlabs/Storage/Browser.php:228
+msgid "Shared"
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:239
-msgid "Suggest"
+#: ../../Zotlabs/Storage/Browser.php:304
+#, php-format
+msgid "You are using %1$s of your available file storage."
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:240
-msgid "Random Channel"
+#: ../../Zotlabs/Storage/Browser.php:309
+#, php-format
+msgid "You are using %1$s of %2$s available file storage. (%3$s&#37;)"
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:241
-msgid "Invite"
+#: ../../Zotlabs/Storage/Browser.php:320
+msgid "WARNING:"
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:242 ../../include/widgets.php:1595
-msgid "Features"
+#: ../../Zotlabs/Storage/Browser.php:330
+msgid ""
+"Please use DAV to upload large (video, audio) files.<br>See <a class=\"zrl\" "
+"href=\"help/member/member_guide#Cloud_Desktop_Clients\">Cloud Desktop "
+"Clients</a>"
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:243
-#: ../../extend/addon/addon/openid/MysqlProvider.php:69
-msgid "Language"
+#: ../../Zotlabs/Storage/Browser.php:334
+msgid "Create new folder"
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:244
-msgid "Post"
+#: ../../Zotlabs/Storage/Browser.php:336
+msgid "Upload file"
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:245
-#: ../../extend/addon/addon/openid/MysqlProvider.php:58
-#: ../../extend/addon/addon/openid/MysqlProvider.php:59
-#: ../../extend/addon/addon/openid/MysqlProvider.php:60
-msgid "Profile Photo"
+#: ../../Zotlabs/Storage/Browser.php:350
+msgid "Drop files here to immediately upload"
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:355
-msgid "Purchase"
+#: ../../Zotlabs/Widget/Forums.php:85
+msgid "Forums"
msgstr ""
-#: ../../Zotlabs/Lib/Apps.php:359
-msgid "Undelete"
+#: ../../Zotlabs/Widget/Cdav.php:37
+msgid "Select Channel"
msgstr ""
-#: ../../Zotlabs/Lib/NativeWiki.php:126
-msgid "Wiki files deleted successfully"
+#: ../../Zotlabs/Widget/Cdav.php:42
+msgid "Read-write"
msgstr ""
-#: ../../Zotlabs/Lib/Permcat.php:58
-msgctxt "permcat"
-msgid "default"
+#: ../../Zotlabs/Widget/Cdav.php:43
+msgid "Read-only"
msgstr ""
-#: ../../Zotlabs/Lib/Permcat.php:96
-msgctxt "permcat"
-msgid "follower"
+#: ../../Zotlabs/Widget/Cdav.php:116
+msgid "My Calendars"
msgstr ""
-#: ../../Zotlabs/Lib/Permcat.php:100
-msgctxt "permcat"
-msgid "contributor"
+#: ../../Zotlabs/Widget/Cdav.php:118
+msgid "Shared Calendars"
msgstr ""
-#: ../../Zotlabs/Lib/Permcat.php:104
-msgctxt "permcat"
-msgid "publisher"
+#: ../../Zotlabs/Widget/Cdav.php:122
+msgid "Share this calendar"
msgstr ""
-#: ../../Zotlabs/Lib/NativeWikiPage.php:31
-#: ../../Zotlabs/Lib/NativeWikiPage.php:62
-msgid "(No Title)"
+#: ../../Zotlabs/Widget/Cdav.php:124
+msgid "Calendar name and color"
msgstr ""
-#: ../../Zotlabs/Lib/NativeWikiPage.php:76
-msgid "Wiki page create failed."
+#: ../../Zotlabs/Widget/Cdav.php:126
+msgid "Create new calendar"
msgstr ""
-#: ../../Zotlabs/Lib/NativeWikiPage.php:89
-msgid "Wiki not found."
+#: ../../Zotlabs/Widget/Cdav.php:128
+msgid "Calendar Name"
msgstr ""
-#: ../../Zotlabs/Lib/NativeWikiPage.php:100
-msgid "Destination name already exists"
+#: ../../Zotlabs/Widget/Cdav.php:129
+msgid "Calendar Tools"
msgstr ""
-#: ../../Zotlabs/Lib/NativeWikiPage.php:126
-#: ../../Zotlabs/Lib/NativeWikiPage.php:345
-msgid "Page not found"
+#: ../../Zotlabs/Widget/Cdav.php:130
+msgid "Import calendar"
msgstr ""
-#: ../../Zotlabs/Lib/NativeWikiPage.php:156
-msgid "Error reading page content"
+#: ../../Zotlabs/Widget/Cdav.php:131
+msgid "Select a calendar to import to"
msgstr ""
-#: ../../Zotlabs/Lib/NativeWikiPage.php:338
-#: ../../Zotlabs/Lib/NativeWikiPage.php:383
-#: ../../Zotlabs/Lib/NativeWikiPage.php:450
-#: ../../Zotlabs/Lib/NativeWikiPage.php:491
-msgid "Error reading wiki"
+#: ../../Zotlabs/Widget/Cdav.php:158
+msgid "Addressbooks"
msgstr ""
-#: ../../Zotlabs/Lib/NativeWikiPage.php:371
-msgid "Page update failed."
+#: ../../Zotlabs/Widget/Cdav.php:160
+msgid "Addressbook name"
msgstr ""
-#: ../../Zotlabs/Lib/NativeWikiPage.php:405
-msgid "Nothing deleted"
+#: ../../Zotlabs/Widget/Cdav.php:162
+msgid "Create new addressbook"
msgstr ""
-#: ../../Zotlabs/Lib/NativeWikiPage.php:471
-msgid "Compare: object not found."
+#: ../../Zotlabs/Widget/Cdav.php:163
+msgid "Addressbook Name"
msgstr ""
-#: ../../Zotlabs/Lib/NativeWikiPage.php:477
-msgid "Page updated"
+#: ../../Zotlabs/Widget/Cdav.php:165
+msgid "Addressbook Tools"
msgstr ""
-#: ../../Zotlabs/Lib/NativeWikiPage.php:480
-msgid "Untitled"
+#: ../../Zotlabs/Widget/Cdav.php:166
+msgid "Import addressbook"
msgstr ""
-#: ../../Zotlabs/Lib/NativeWikiPage.php:486
-msgid "Wiki resource_id required for git commit"
+#: ../../Zotlabs/Widget/Cdav.php:167
+msgid "Select an addressbook to import to"
msgstr ""
-#: ../../Zotlabs/Lib/NativeWikiPage.php:557
-#: ../../extend/addon/addon/gitwiki/gitwiki_backend.php:579
-#: ../../include/bbcode.php:610 ../../include/bbcode.php:756
-msgid "Different viewers will see this text differently"
+#: ../../Zotlabs/Widget/Appcategories.php:39
+#: ../../Zotlabs/Widget/Tagcloud.php:25 ../../include/contact_widgets.php:91
+#: ../../include/contact_widgets.php:132 ../../include/taxonomy.php:285
+#: ../../include/taxonomy.php:367 ../../include/taxonomy.php:387
+msgid "Categories"
msgstr ""
-#: ../../extend/addon/addon/adultphotoflag/adultphotoflag.php:24
-msgid "Flag Adult Photos"
+#: ../../Zotlabs/Widget/Appcategories.php:42 ../../Zotlabs/Widget/Filer.php:31
+#: ../../include/contact_widgets.php:56 ../../include/contact_widgets.php:94
+#: ../../include/contact_widgets.php:135
+msgid "Everything"
msgstr ""
-#: ../../extend/addon/addon/adultphotoflag/adultphotoflag.php:25
-msgid ""
-"Provide photo edit option to hide inappropriate photos from default album "
-"view"
+#: ../../Zotlabs/Widget/Eventstools.php:13
+msgid "Events Tools"
msgstr ""
-#: ../../extend/addon/addon/chords/Mod_Chords.php:44
-msgid ""
-"This is a fairly comprehensive and complete guitar chord dictionary which "
-"will list most of the available ways to play a certain chord, starting from "
-"the base of the fingerboard up to a few frets beyond the twelfth fret "
-"(beyond which everything repeats). A couple of non-standard tunings are "
-"provided for the benefit of slide players, etc."
+#: ../../Zotlabs/Widget/Eventstools.php:14
+msgid "Export Calendar"
msgstr ""
-#: ../../extend/addon/addon/chords/Mod_Chords.php:46
-msgid ""
-"Chord names start with a root note (A-G) and may include sharps (#) and "
-"flats (b). This software will parse most of the standard naming conventions "
-"such as maj, min, dim, sus(2 or 4), aug, with optional repeating elements."
+#: ../../Zotlabs/Widget/Eventstools.php:15
+msgid "Import Calendar"
msgstr ""
-#: ../../extend/addon/addon/chords/Mod_Chords.php:48
-msgid ""
-"Valid examples include A, A7, Am7, Amaj7, Amaj9, Ammaj7, Aadd4, Asus2Add4, "
-"E7b13b11 ..."
+#: ../../Zotlabs/Widget/Suggestedchats.php:32
+msgid "Suggested Chatrooms"
msgstr ""
-#: ../../extend/addon/addon/chords/Mod_Chords.php:51
-msgid "Guitar Chords"
+#: ../../Zotlabs/Widget/Mailmenu.php:13
+msgid "Private Mail Menu"
msgstr ""
-#: ../../extend/addon/addon/chords/Mod_Chords.php:52
-msgid "The complete online chord dictionary"
+#: ../../Zotlabs/Widget/Mailmenu.php:15
+msgid "Combined View"
msgstr ""
-#: ../../extend/addon/addon/chords/Mod_Chords.php:57
-msgid "Tuning"
+#: ../../Zotlabs/Widget/Mailmenu.php:20 ../../include/nav.php:119
+msgid "Inbox"
msgstr ""
-#: ../../extend/addon/addon/chords/Mod_Chords.php:58
-msgid "Chord name: example: Em7"
+#: ../../Zotlabs/Widget/Mailmenu.php:25 ../../include/nav.php:120
+msgid "Outbox"
msgstr ""
-#: ../../extend/addon/addon/chords/Mod_Chords.php:59
-msgid "Show for left handed stringing"
+#: ../../Zotlabs/Widget/Mailmenu.php:30 ../../include/nav.php:121
+msgid "New Message"
msgstr ""
-#: ../../extend/addon/addon/chords/chords.php:33
-msgid "Quick Reference"
+#: ../../Zotlabs/Widget/Chatroom_list.php:16
+#: ../../include/conversation.php:1847 ../../include/conversation.php:1850
+#: ../../include/nav.php:455 ../../include/nav.php:458
+msgid "Chatrooms"
msgstr ""
-#: ../../extend/addon/addon/diaspora/import_diaspora.php:16
-msgid "No username found in import file."
+#: ../../Zotlabs/Widget/Chatroom_list.php:20
+msgid "Overview"
msgstr ""
-#: ../../extend/addon/addon/diaspora/import_diaspora.php:41
-#: ../../include/import.php:51
-msgid "Unable to create a unique channel address. Import failed."
+#: ../../Zotlabs/Widget/Rating.php:51
+msgid "Rating Tools"
msgstr ""
-#: ../../extend/addon/addon/diaspora/diaspora.php:677
-msgid "Diaspora Protocol Settings updated."
+#: ../../Zotlabs/Widget/Rating.php:55 ../../Zotlabs/Widget/Rating.php:57
+msgid "Rate Me"
msgstr ""
-#: ../../extend/addon/addon/diaspora/diaspora.php:696
-msgid "Enable the Diaspora protocol for this channel"
+#: ../../Zotlabs/Widget/Rating.php:60
+msgid "View Ratings"
msgstr ""
-#: ../../extend/addon/addon/diaspora/diaspora.php:700
-msgid "Allow any Diaspora member to comment on your public posts"
+#: ../../Zotlabs/Widget/Activity.php:50
+msgctxt "widget"
+msgid "Activity"
msgstr ""
-#: ../../extend/addon/addon/diaspora/diaspora.php:704
-msgid "Prevent your hashtags from being redirected to other sites"
+#: ../../Zotlabs/Widget/Follow.php:22
+#, php-format
+msgid "You have %1$.0f of %2$.0f allowed connections."
msgstr ""
-#: ../../extend/addon/addon/diaspora/diaspora.php:709
-msgid "Followed hashtags (comma separated, do not include the #)"
+#: ../../Zotlabs/Widget/Follow.php:29
+msgid "Add New Connection"
msgstr ""
-#: ../../extend/addon/addon/diaspora/diaspora.php:714
-msgid "Diaspora Protocol Settings"
+#: ../../Zotlabs/Widget/Follow.php:30
+msgid "Enter channel address"
msgstr ""
-#: ../../extend/addon/addon/dirstats/dirstats.php:94
-msgid "Hubzilla Directory Stats"
+#: ../../Zotlabs/Widget/Follow.php:31
+msgid "Examples: bob@example.com, https://example.com/barbara"
msgstr ""
-#: ../../extend/addon/addon/dirstats/dirstats.php:95
-msgid "Total Hubs"
+#: ../../Zotlabs/Widget/Wiki_list.php:15 ../../addon/gitwiki/gitwiki.php:95
+msgid "Wiki List"
msgstr ""
-#: ../../extend/addon/addon/dirstats/dirstats.php:97
-msgid "Hubzilla Hubs"
+#: ../../Zotlabs/Widget/Archive.php:43
+msgid "Archives"
msgstr ""
-#: ../../extend/addon/addon/dirstats/dirstats.php:99
-msgid "Friendica Hubs"
+#: ../../Zotlabs/Widget/Conversations.php:17
+msgid "Received Messages"
msgstr ""
-#: ../../extend/addon/addon/dirstats/dirstats.php:101
-msgid "Diaspora Pods"
+#: ../../Zotlabs/Widget/Conversations.php:21
+msgid "Sent Messages"
msgstr ""
-#: ../../extend/addon/addon/dirstats/dirstats.php:103
-msgid "Hubzilla Channels"
+#: ../../Zotlabs/Widget/Conversations.php:25
+msgid "Conversations"
msgstr ""
-#: ../../extend/addon/addon/dirstats/dirstats.php:105
-msgid "Friendica Channels"
+#: ../../Zotlabs/Widget/Conversations.php:35
+msgid "No messages."
msgstr ""
-#: ../../extend/addon/addon/dirstats/dirstats.php:107
-msgid "Diaspora Channels"
+#: ../../Zotlabs/Widget/Conversations.php:55
+msgid "Delete conversation"
msgstr ""
-#: ../../extend/addon/addon/dirstats/dirstats.php:109
-msgid "Aged 35 and above"
+#: ../../Zotlabs/Widget/Chatroom_members.php:11
+msgid "Chat Members"
msgstr ""
-#: ../../extend/addon/addon/dirstats/dirstats.php:111
-msgid "Aged 34 and under"
+#: ../../Zotlabs/Widget/Photo.php:48 ../../Zotlabs/Widget/Photo_rand.php:58
+msgid "photo/image"
msgstr ""
-#: ../../extend/addon/addon/dirstats/dirstats.php:113
-msgid "Average Age"
+#: ../../Zotlabs/Widget/Savedsearch.php:75
+msgid "Remove term"
msgstr ""
-#: ../../extend/addon/addon/dirstats/dirstats.php:115
-msgid "Known Chatrooms"
+#: ../../Zotlabs/Widget/Savedsearch.php:83 ../../include/features.php:306
+msgid "Saved Searches"
msgstr ""
-#: ../../extend/addon/addon/dirstats/dirstats.php:117
-msgid "Known Tags"
+#: ../../Zotlabs/Widget/Savedsearch.php:84 ../../include/group.php:337
+msgid "add"
msgstr ""
-#: ../../extend/addon/addon/dirstats/dirstats.php:119
-msgid ""
-"Please note Diaspora and Friendica statistics are merely those **this "
-"directory** is aware of, and not all those known in the network. This also "
-"applies to chatrooms,"
+#: ../../Zotlabs/Widget/Notes.php:16
+msgid "Notes"
msgstr ""
-#: ../../extend/addon/addon/donate/donate.php:21
-msgid "Project Servers and Resources"
+#: ../../Zotlabs/Widget/Wiki_pages.php:47 ../../addon/gitwiki/gitwiki.php:76
+msgid "Wiki Pages"
msgstr ""
-#: ../../extend/addon/addon/donate/donate.php:22
-msgid "Project Creator and Tech Lead"
+#: ../../Zotlabs/Widget/Wiki_pages.php:53 ../../addon/gitwiki/gitwiki.php:81
+msgid "Add new page"
msgstr ""
-#: ../../extend/addon/addon/donate/donate.php:23
-msgid "Admin, developer, directorymin, support bloke"
+#: ../../Zotlabs/Widget/Wiki_pages.php:58 ../../addon/gitwiki/gitwiki.php:82
+msgid "Page name"
msgstr ""
-#: ../../extend/addon/addon/donate/donate.php:50
-msgid ""
-"And the hundreds of other people and organisations who helped make the "
-"Hubzilla possible."
+#: ../../Zotlabs/Widget/Affinity.php:49
+msgid "Refresh"
msgstr ""
-#: ../../extend/addon/addon/donate/donate.php:53
-msgid ""
-"The Redmatrix/Hubzilla projects are provided primarily by volunteers giving "
-"their time and expertise - and often paying out of pocket for services they "
-"share with others."
+#: ../../Zotlabs/Widget/Tasklist.php:23
+msgid "Tasks"
msgstr ""
-#: ../../extend/addon/addon/donate/donate.php:54
-msgid ""
-"There is no corporate funding and no ads, and we do not collect and sell "
-"your personal information. (We don't control your personal information - "
-"<strong>you do</strong>.)"
+#: ../../Zotlabs/Widget/Suggestions.php:51
+msgid "Suggestions"
msgstr ""
-#: ../../extend/addon/addon/donate/donate.php:55
-msgid ""
-"Help support our ground-breaking work in decentralisation, web identity, and "
-"privacy."
+#: ../../Zotlabs/Widget/Suggestions.php:52
+msgid "See more..."
msgstr ""
-#: ../../extend/addon/addon/donate/donate.php:57
-msgid ""
-"Your donations keep servers and services running and also helps us to "
-"provide innovative new features and continued development."
+#: ../../Zotlabs/Widget/Filer.php:28 ../../include/contact_widgets.php:53
+#: ../../include/features.php:395
+msgid "Saved Folders"
msgstr ""
-#: ../../extend/addon/addon/donate/donate.php:60
-msgid "Donate"
+#: ../../Zotlabs/Widget/Cover_photo.php:54
+msgid "Click to show more"
msgstr ""
-#: ../../extend/addon/addon/donate/donate.php:62
-msgid ""
-"Choose a project, developer, or public hub to support with a one-time "
-"donation"
+#: ../../Zotlabs/Widget/Admin.php:23 ../../Zotlabs/Widget/Admin.php:60
+msgid "Member registrations waiting for confirmation"
msgstr ""
-#: ../../extend/addon/addon/donate/donate.php:63
-msgid "Donate Now"
+#: ../../Zotlabs/Widget/Admin.php:29
+msgid "Inspect queue"
msgstr ""
-#: ../../extend/addon/addon/donate/donate.php:64
-msgid ""
-"<strong><em>Or</em></strong> become a project sponsor (Hubzilla Project only)"
+#: ../../Zotlabs/Widget/Admin.php:31
+msgid "DB updates"
msgstr ""
-#: ../../extend/addon/addon/donate/donate.php:65
-msgid ""
-"Please indicate if you would like your first name or full name (or nothing) "
-"to appear in our sponsor listing"
+#: ../../Zotlabs/Widget/Admin.php:55 ../../include/nav.php:224
+msgid "Admin"
msgstr ""
-#: ../../extend/addon/addon/donate/donate.php:66
-msgid "Sponsor"
+#: ../../Zotlabs/Widget/Admin.php:56
+msgid "Plugin Features"
msgstr ""
-#: ../../extend/addon/addon/donate/donate.php:69
-msgid "Special thanks to: "
+#: ../../Zotlabs/Widget/Settings_menu.php:35
+msgid "Account settings"
msgstr ""
-#: ../../extend/addon/addon/dwpost/dwpost.php:42
-msgid "Post to Dreamwidth"
+#: ../../Zotlabs/Widget/Settings_menu.php:41
+msgid "Channel settings"
msgstr ""
-#: ../../extend/addon/addon/dwpost/dwpost.php:73
-msgid "Enable Dreamwidth Post Plugin"
+#: ../../Zotlabs/Widget/Settings_menu.php:50
+msgid "Additional features"
msgstr ""
-#: ../../extend/addon/addon/dwpost/dwpost.php:77
-msgid "Dreamwidth username"
+#: ../../Zotlabs/Widget/Settings_menu.php:57
+msgid "Feature/Addon settings"
msgstr ""
-#: ../../extend/addon/addon/dwpost/dwpost.php:81
-msgid "Dreamwidth password"
+#: ../../Zotlabs/Widget/Settings_menu.php:63
+msgid "Display settings"
msgstr ""
-#: ../../extend/addon/addon/dwpost/dwpost.php:85
-msgid "Post to Dreamwidth by default"
+#: ../../Zotlabs/Widget/Settings_menu.php:70
+msgid "Manage locations"
msgstr ""
-#: ../../extend/addon/addon/dwpost/dwpost.php:89
-msgid "Dreamwidth Post Settings"
+#: ../../Zotlabs/Widget/Settings_menu.php:77
+msgid "Export channel"
msgstr ""
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:45
-msgid "Flattr this!"
+#: ../../Zotlabs/Widget/Settings_menu.php:84
+msgid "Connected apps"
msgstr ""
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:83
-msgid "Flattr widget settings updated."
+#: ../../Zotlabs/Widget/Settings_menu.php:100 ../../include/features.php:158
+msgid "Permission Groups"
msgstr ""
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:100
-msgid "Flattr user"
+#: ../../Zotlabs/Widget/Settings_menu.php:117
+msgid "Premium Channel Settings"
msgstr ""
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:104
-msgid "URL of the Thing to flattr"
+#: ../../Zotlabs/Widget/Bookmarkedchats.php:24
+msgid "Bookmarked Chatrooms"
msgstr ""
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:104
-msgid "If empty channel URL is used"
+#: ../../Zotlabs/Widget/Notifications.php:16
+msgid "New Network Activity"
msgstr ""
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:108
-msgid "Title of the Thing to flattr"
+#: ../../Zotlabs/Widget/Notifications.php:17
+msgid "New Network Activity Notifications"
msgstr ""
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:108
-msgid "If empty \"channel name on The Hubzilla\" will be used"
+#: ../../Zotlabs/Widget/Notifications.php:20 ../../include/nav.php:99
+msgid "View your network activity"
msgstr ""
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:112
-msgid "Static or dynamic flattr button"
+#: ../../Zotlabs/Widget/Notifications.php:24
+msgid "Mark all notifications read"
msgstr ""
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:112
-msgid "static"
+#: ../../Zotlabs/Widget/Notifications.php:32
+msgid "New Home Activity"
msgstr ""
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:112
-msgid "dynamic"
+#: ../../Zotlabs/Widget/Notifications.php:33
+msgid "New Home Activity Notifications"
msgstr ""
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:116
-msgid "Alignment of the widget"
+#: ../../Zotlabs/Widget/Notifications.php:36
+msgid "View your home activity"
msgstr ""
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:116
-msgid "left"
+#: ../../Zotlabs/Widget/Notifications.php:40
+#: ../../Zotlabs/Widget/Notifications.php:136
+msgid "Mark all notifications seen"
msgstr ""
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:116
-msgid "right"
+#: ../../Zotlabs/Widget/Notifications.php:48
+msgid "New Mails"
msgstr ""
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:120
-msgid "Enable Flattr widget"
+#: ../../Zotlabs/Widget/Notifications.php:49
+msgid "New Mails Notifications"
msgstr ""
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:124
-msgid "Flattr Widget Settings"
+#: ../../Zotlabs/Widget/Notifications.php:52
+msgid "View your private mails"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:118
-msgid "Contact not found."
+#: ../../Zotlabs/Widget/Notifications.php:56
+msgid "Mark all messages seen"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:119
-msgid ""
-"This may occasionally happen if contact was requested by both persons and it "
-"has already been approved."
+#: ../../Zotlabs/Widget/Notifications.php:64
+msgid "New Events"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:238
-msgid "Response from remote site was not understood."
+#: ../../Zotlabs/Widget/Notifications.php:65
+msgid "New Events Notifications"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:247
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:252
-msgid "Unexpected response from remote site: "
+#: ../../Zotlabs/Widget/Notifications.php:68 ../../include/nav.php:125
+msgid "View events"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:261
-msgid "Confirmation completed successfully."
+#: ../../Zotlabs/Widget/Notifications.php:72 ../../include/nav.php:126
+msgid "Mark all events seen"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:263
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:277
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:284
-msgid "Remote site reported: "
+#: ../../Zotlabs/Widget/Notifications.php:81
+msgid "New Connections Notifications"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:275
-msgid "Temporary failure. Please wait and try again."
+#: ../../Zotlabs/Widget/Notifications.php:84
+msgid "View all connections"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:282
-msgid "Introduction failed or was revoked."
+#: ../../Zotlabs/Widget/Notifications.php:92
+msgid "New Files"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:428
-msgid "Unable to set contact photo."
+#: ../../Zotlabs/Widget/Notifications.php:93
+msgid "New Files Notifications"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:485
-#, php-format
-msgid "%1$s is now friends with %2$s"
+#: ../../Zotlabs/Widget/Notifications.php:100
+#: ../../Zotlabs/Widget/Notifications.php:101 ../../include/nav.php:112
+msgid "Notices"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:570
-#, php-format
-msgid "No user record found for '%s' "
+#: ../../Zotlabs/Widget/Notifications.php:104
+msgid "View all notices"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:580
-msgid "Our site encryption key is apparently messed up."
+#: ../../Zotlabs/Widget/Notifications.php:108
+msgid "Mark all notices seen"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:591
-msgid "Empty site URL was provided or URL could not be decrypted by us."
+#: ../../Zotlabs/Widget/Notifications.php:118
+msgid "New Registrations"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:612
-msgid "Contact record was not found for you on our site."
+#: ../../Zotlabs/Widget/Notifications.php:119
+msgid "New Registrations Notifications"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:626
-#, php-format
-msgid "Site public key not available in contact record for URL %s."
+#: ../../Zotlabs/Widget/Notifications.php:129
+msgid "Public Stream Notifications"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:646
-msgid ""
-"The ID provided by your system is a duplicate on our system. It should work "
-"if you try again."
+#: ../../Zotlabs/Widget/Notifications.php:132
+msgid "View the public stream"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:657
-msgid "Unable to set your contact credentials on our system."
+#: ../../Zotlabs/Widget/Notifications.php:143
+#: ../../include/conversation.php:871 ../../include/nav.php:305
+msgid "Loading..."
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:724
-msgid "Unable to update your contact profile details on our system"
+#: ../../util/nconfig.php:34
+msgid "Source channel not found."
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:751
-#: ../../extend/addon/addon/friendica/dfrn_request.php:749
-msgid "[Name Withheld]"
+#: ../../boot.php:1619
+msgid "Create an account to access services and applications"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:796
-#, php-format
-msgid "%1$s has joined %2$s"
+#: ../../boot.php:1638 ../../include/nav.php:138 ../../include/nav.php:167
+#: ../../include/nav.php:184
+msgid "Logout"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_poll.php:103
-#: ../../extend/addon/addon/friendica/dfrn_poll.php:536
-#, php-format
-msgid "%1$s welcomes %2$s"
+#: ../../boot.php:1642
+msgid "Login/Email"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:102
-msgid "This introduction has already been accepted."
+#: ../../boot.php:1643
+msgid "Password"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:123
-#: ../../extend/addon/addon/friendica/dfrn_request.php:528
-msgid "Profile location is not valid or does not contain profile information."
+#: ../../boot.php:1644
+msgid "Remember me"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:128
-#: ../../extend/addon/addon/friendica/dfrn_request.php:533
-msgid "Warning: profile location has no identifiable owner name."
+#: ../../boot.php:1647
+msgid "Forgot your password?"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:130
-#: ../../extend/addon/addon/friendica/dfrn_request.php:535
-msgid "Warning: profile location has no profile photo."
+#: ../../boot.php:2191
+msgid "toggle mobile"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:133
-#: ../../extend/addon/addon/friendica/dfrn_request.php:538
+#: ../../boot.php:2344
#, php-format
-msgid "%d required parameter was not found at the given location"
-msgid_plural "%d required parameters were not found at the given location"
-msgstr[0] ""
-msgstr[1] ""
-
-#: ../../extend/addon/addon/friendica/dfrn_request.php:180
-msgid "Introduction complete."
-msgstr ""
-
-#: ../../extend/addon/addon/friendica/dfrn_request.php:224
-msgid "Unrecoverable protocol error."
+msgid "[$Projectname] Website SSL error for %s"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:252
-msgid "Profile unavailable."
+#: ../../boot.php:2349
+msgid "Website SSL certificate is not valid. Please correct."
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:277
+#: ../../boot.php:2468
#, php-format
-msgid "%s has received too many connection requests today."
+msgid "[$Projectname] Cron tasks not running on %s"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:278
-msgid "Spam protection measures have been invoked."
+#: ../../boot.php:2473
+msgid "Cron/Scheduled tasks not running."
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:279
-msgid "Friends are advised to please try again in 24 hours."
+#: ../../boot.php:2474 ../../include/datetime.php:286
+msgid "never"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:341
-msgid "Invalid locator"
+#: ../../view/theme/redbasic_c/php/config.php:16
+#: ../../view/theme/redbasic_c/php/config.php:19
+#: ../../view/theme/redbasic/php/config.php:16
+#: ../../view/theme/redbasic/php/config.php:19
+msgid "Focus (Hubzilla default)"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:350
-msgid "Invalid email address."
+#: ../../view/theme/redbasic_c/php/config.php:99
+#: ../../view/theme/redbasic/php/config.php:97
+msgid "Theme settings"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:377
-msgid "This account has not been configured for email. Request failed."
+#: ../../view/theme/redbasic_c/php/config.php:100
+#: ../../view/theme/redbasic/php/config.php:98
+msgid "Narrow navbar"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:473
-msgid "Unable to resolve your name at the provided location."
+#: ../../view/theme/redbasic_c/php/config.php:101
+#: ../../view/theme/redbasic/php/config.php:99
+msgid "Navigation bar background color"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:486
-msgid "You have already introduced yourself here."
+#: ../../view/theme/redbasic_c/php/config.php:102
+#: ../../view/theme/redbasic/php/config.php:100
+msgid "Navigation bar icon color "
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:490
-#, php-format
-msgid "Apparently you are already friends with %s."
+#: ../../view/theme/redbasic_c/php/config.php:103
+#: ../../view/theme/redbasic/php/config.php:101
+msgid "Navigation bar active icon color "
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:511
-msgid "Invalid profile URL."
+#: ../../view/theme/redbasic_c/php/config.php:104
+#: ../../view/theme/redbasic/php/config.php:102
+msgid "Link color"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:517
-msgid "Disallowed profile URL."
+#: ../../view/theme/redbasic_c/php/config.php:105
+#: ../../view/theme/redbasic/php/config.php:103
+msgid "Set font-color for banner"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:587
-msgid "Failed to update contact record."
+#: ../../view/theme/redbasic_c/php/config.php:106
+#: ../../view/theme/redbasic/php/config.php:104
+msgid "Set the background color"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:608
-msgid "Your introduction has been sent."
+#: ../../view/theme/redbasic_c/php/config.php:107
+#: ../../view/theme/redbasic/php/config.php:105
+msgid "Set the background image"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:662
-msgid "Please login to confirm introduction."
+#: ../../view/theme/redbasic_c/php/config.php:108
+#: ../../view/theme/redbasic/php/config.php:106
+msgid "Set the background color of items"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:676
-msgid ""
-"Incorrect identity currently logged in. Please login to <strong>this</"
-"strong> profile."
+#: ../../view/theme/redbasic_c/php/config.php:109
+#: ../../view/theme/redbasic/php/config.php:107
+msgid "Set the background color of comments"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:690
-#: ../../extend/addon/addon/friendica/dfrn_request.php:707
-msgid "Confirm"
+#: ../../view/theme/redbasic_c/php/config.php:110
+#: ../../view/theme/redbasic/php/config.php:108
+msgid "Set font-size for the entire application"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:702
-msgid "Hide this contact"
+#: ../../view/theme/redbasic_c/php/config.php:110
+#: ../../view/theme/redbasic/php/config.php:108
+msgid "Examples: 1rem, 100%, 16px"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:705
-#, php-format
-msgid "Welcome home %s."
+#: ../../view/theme/redbasic_c/php/config.php:111
+#: ../../view/theme/redbasic/php/config.php:109
+msgid "Set font-color for posts and comments"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:706
-#, php-format
-msgid "Please confirm your introduction/connection request to %s."
+#: ../../view/theme/redbasic_c/php/config.php:112
+#: ../../view/theme/redbasic/php/config.php:110
+msgid "Set radius of corners"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:836
-msgid ""
-"Please enter your 'Identity Address' from one of the following supported "
-"communications networks:"
+#: ../../view/theme/redbasic_c/php/config.php:112
+#: ../../view/theme/redbasic/php/config.php:110
+msgid "Example: 4px"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:857
-#, php-format
-msgid ""
-"If you are not yet a member of the free social web, <a href=\"%s/siteinfo"
-"\">follow this link to find a public Friendica site and join us today</a>."
+#: ../../view/theme/redbasic_c/php/config.php:113
+#: ../../view/theme/redbasic/php/config.php:111
+msgid "Set shadow depth of photos"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:862
-msgid "Friend/Connection Request"
+#: ../../view/theme/redbasic_c/php/config.php:114
+#: ../../view/theme/redbasic/php/config.php:112
+msgid "Set maximum width of content region in pixel"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:863
-msgid ""
-"Examples: jojo@demo.friendica.com, http://demo.friendica.com/profile/jojo, "
-"testuser@identi.ca"
+#: ../../view/theme/redbasic_c/php/config.php:114
+#: ../../view/theme/redbasic/php/config.php:112
+msgid "Leave empty for default width"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:864
-msgid "Please answer the following:"
+#: ../../view/theme/redbasic_c/php/config.php:115
+msgid "Left align page content"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:865
-#, php-format
-msgid "Does %s know you?"
+#: ../../view/theme/redbasic_c/php/config.php:116
+#: ../../view/theme/redbasic/php/config.php:113
+msgid "Set size of conversation author photo"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:869
-msgid "Add a personal note:"
+#: ../../view/theme/redbasic_c/php/config.php:117
+#: ../../view/theme/redbasic/php/config.php:114
+msgid "Set size of followup author photos"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:871
-#: ../../include/network.php:2242 ../../include/network.php:2243
-msgid "Friendica"
+#: ../../addon/rendezvous/rendezvous.php:57
+msgid "Errors encountered deleting database table "
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:872
-msgid "StatusNet/Federated Social Web"
+#: ../../addon/rendezvous/rendezvous.php:95 ../../addon/twitter/twitter.php:773
+msgid "Submit Settings"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:873
-#: ../../include/network.php:2248
-msgid "Diaspora"
+#: ../../addon/rendezvous/rendezvous.php:96
+msgid "Drop tables when uninstalling?"
msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_request.php:874
-#, php-format
+#: ../../addon/rendezvous/rendezvous.php:96
msgid ""
-" - please do not use this form. Instead, enter %s into your Diaspora search "
-"bar."
-msgstr ""
-
-#: ../../extend/addon/addon/friendica/dfrn_request.php:875
-msgid "Your Identity Address:"
-msgstr ""
-
-#: ../../extend/addon/addon/friendica/dfrn_request.php:878
-msgid "Submit Request"
-msgstr ""
-
-#: ../../extend/addon/addon/friendica/friendica.php:113
-#: ../../extend/addon/addon/gnusoc/gnusoc.php:118
-msgid "GNU-Social Protocol Settings updated."
+"If checked, the Rendezvous database tables will be deleted when the plugin "
+"is uninstalled."
msgstr ""
-#: ../../extend/addon/addon/friendica/friendica.php:124
-msgid "Enable the (experimental) GNU-Social protocol for this channel"
+#: ../../addon/rendezvous/rendezvous.php:97
+msgid "Mapbox Access Token"
msgstr ""
-#: ../../extend/addon/addon/friendica/friendica.php:128
-#: ../../extend/addon/addon/gnusoc/gnusoc.php:133
-msgid "GNU-Social Protocol Settings"
+#: ../../addon/rendezvous/rendezvous.php:97
+msgid ""
+"If you enter a Mapbox access token, it will be used to retrieve map tiles "
+"from Mapbox instead of the default OpenStreetMap tile server."
msgstr ""
-#: ../../extend/addon/addon/friendica/friendica.php:185
-#: ../../extend/addon/addon/gnusoc/gnusoc.php:323
-msgid "Follow"
+#: ../../addon/rendezvous/rendezvous.php:162
+msgid "Rendezvous"
msgstr ""
-#: ../../extend/addon/addon/friendica/friendica.php:188
-#: ../../extend/addon/addon/gnusoc/gnusoc.php:326
-#, php-format
-msgid "%1$s is now following %2$s"
+#: ../../addon/rendezvous/rendezvous.php:167
+msgid ""
+"This identity has been deleted by another member due to inactivity. Please "
+"press the \"New identity\" button or refresh the page to register a new "
+"identity. You may use the same name."
msgstr ""
-#: ../../extend/addon/addon/frphotos/frphotos.php:91
-msgid "Friendica Photo Album Import"
+#: ../../addon/rendezvous/rendezvous.php:168
+msgid "Welcome to Rendezvous!"
msgstr ""
-#: ../../extend/addon/addon/frphotos/frphotos.php:92
-msgid "This will import all your Friendica photo albums to this Red channel."
+#: ../../addon/rendezvous/rendezvous.php:169
+msgid ""
+"Enter your name to join this rendezvous. To begin sharing your location with "
+"the other members, tap the GPS control. When your location is discovered, a "
+"red dot will appear and others will be able to see you on the map."
msgstr ""
-#: ../../extend/addon/addon/frphotos/frphotos.php:93
-msgid "Friendica Server base URL"
+#: ../../addon/rendezvous/rendezvous.php:171
+msgid "Let's meet here"
msgstr ""
-#: ../../extend/addon/addon/frphotos/frphotos.php:94
-msgid "Friendica Login Username"
+#: ../../addon/rendezvous/rendezvous.php:174
+msgid "New marker"
msgstr ""
-#: ../../extend/addon/addon/frphotos/frphotos.php:95
-msgid "Friendica Login Password"
+#: ../../addon/rendezvous/rendezvous.php:175
+msgid "Edit marker"
msgstr ""
-#: ../../extend/addon/addon/hubwall/hubwall.php:19
-msgid "Send email to all members"
+#: ../../addon/rendezvous/rendezvous.php:176
+msgid "New identity"
msgstr ""
-#: ../../extend/addon/addon/hubwall/hubwall.php:33
-#, php-format
-msgid "$1%s Administrator"
+#: ../../addon/rendezvous/rendezvous.php:177
+msgid "Delete marker"
msgstr ""
-#: ../../extend/addon/addon/hubwall/hubwall.php:50
-#: ../../extend/addon/addon/mailtest/mailtest.php:50
-msgid "No recipients found."
+#: ../../addon/rendezvous/rendezvous.php:178
+msgid "Delete member"
msgstr ""
-#: ../../extend/addon/addon/hubwall/hubwall.php:73
-#, php-format
-msgid "%1$d of %2$d messages sent."
+#: ../../addon/rendezvous/rendezvous.php:179
+msgid "Edit proximity alert"
msgstr ""
-#: ../../extend/addon/addon/hubwall/hubwall.php:81
-msgid "Send email to all hub members."
+#: ../../addon/rendezvous/rendezvous.php:180
+msgid ""
+"A proximity alert will be issued when this member is within a certain radius "
+"of you.<br><br>Enter a radius in meters (0 to disable):"
msgstr ""
-#: ../../extend/addon/addon/hubwall/hubwall.php:92
-#: ../../extend/addon/addon/mailtest/mailtest.php:96
-msgid "Message subject"
+#: ../../addon/rendezvous/rendezvous.php:180
+#: ../../addon/rendezvous/rendezvous.php:185
+msgid "distance"
msgstr ""
-#: ../../extend/addon/addon/hubwall/hubwall.php:93
-msgid "Sender Email address"
+#: ../../addon/rendezvous/rendezvous.php:181
+msgid "Proximity alert distance (meters)"
msgstr ""
-#: ../../extend/addon/addon/hubwall/hubwall.php:94
-msgid "Test mode (only send to hub administrator)"
+#: ../../addon/rendezvous/rendezvous.php:182
+#: ../../addon/rendezvous/rendezvous.php:184
+msgid ""
+"A proximity alert will be issued when you are within a certain radius of the "
+"marker location.<br><br>Enter a radius in meters (0 to disable):"
msgstr ""
-#: ../../extend/addon/addon/ijpost/ijpost.php:42
-msgid "Post to Insanejournal"
+#: ../../addon/rendezvous/rendezvous.php:183
+msgid "Marker proximity alert"
msgstr ""
-#: ../../extend/addon/addon/ijpost/ijpost.php:73
-msgid "Enable InsaneJournal Post Plugin"
+#: ../../addon/rendezvous/rendezvous.php:186
+msgid "Reminder note"
msgstr ""
-#: ../../extend/addon/addon/ijpost/ijpost.php:77
-msgid "InsaneJournal username"
+#: ../../addon/rendezvous/rendezvous.php:187
+msgid ""
+"Enter a note to be displayed when you are within the specified proximity..."
msgstr ""
-#: ../../extend/addon/addon/ijpost/ijpost.php:81
-msgid "InsaneJournal password"
+#: ../../addon/rendezvous/rendezvous.php:199
+msgid "Add new rendezvous"
msgstr ""
-#: ../../extend/addon/addon/ijpost/ijpost.php:85
-msgid "Post to InsaneJournal by default"
+#: ../../addon/rendezvous/rendezvous.php:200
+msgid ""
+"Create a new rendezvous and share the access link with those you wish to "
+"invite to the group. Those who open the link become members of the "
+"rendezvous. They can view other member locations, add markers to the map, or "
+"share their own locations with the group."
msgstr ""
-#: ../../extend/addon/addon/ijpost/ijpost.php:89
-msgid "InsaneJournal Post Settings"
+#: ../../addon/skeleton/skeleton.php:59
+msgid "Some setting"
msgstr ""
-#: ../../extend/addon/addon/ijpost/ijpost.php:104
-msgid "Insane Journal Settings saved."
+#: ../../addon/skeleton/skeleton.php:61
+msgid "A setting"
msgstr ""
-#: ../../extend/addon/addon/irc/irc.php:45
-msgid "Channels to auto connect"
+#: ../../addon/skeleton/skeleton.php:64
+msgid "Skeleton Settings"
msgstr ""
-#: ../../extend/addon/addon/irc/irc.php:45
-#: ../../extend/addon/addon/irc/irc.php:49
-msgid "Comma separated list"
+#: ../../addon/gnusoc/gnusoc.php:243
+msgid "GNU-Social Protocol Settings updated."
msgstr ""
-#: ../../extend/addon/addon/irc/irc.php:49
-#: ../../extend/addon/addon/irc/irc.php:96
-msgid "Popular Channels"
+#: ../../addon/gnusoc/gnusoc.php:262
+msgid ""
+"The GNU-Social protocol does not support location independence. Connections "
+"you make within that network may be unreachable from alternate channel "
+"locations."
msgstr ""
-#: ../../extend/addon/addon/irc/irc.php:53
-msgid "IRC Settings"
+#: ../../addon/gnusoc/gnusoc.php:265
+msgid "Enable the GNU-Social protocol for this channel"
msgstr ""
-#: ../../extend/addon/addon/irc/irc.php:69
-msgid "IRC settings saved."
+#: ../../addon/gnusoc/gnusoc.php:269
+msgid "GNU-Social Protocol Settings"
msgstr ""
-#: ../../extend/addon/addon/irc/irc.php:74
-msgid "IRC Chatroom"
+#: ../../addon/gnusoc/gnusoc.php:460
+msgid "Follow"
msgstr ""
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:305
-#: ../../include/channel.php:1139 ../../include/channel.php:1301
-msgid "Status:"
+#: ../../addon/gnusoc/gnusoc.php:463
+#, php-format
+msgid "%1$s is now following %2$s"
msgstr ""
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:309
-msgid "Activate addon"
+#: ../../addon/planets/planets.php:121
+msgid "Planets Settings updated."
msgstr ""
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:313
-msgid "Hide Jappixmini Chat-Widget from the webinterface"
+#: ../../addon/planets/planets.php:149
+msgid "Enable Planets Plugin"
msgstr ""
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:318
-msgid "Jabber username"
+#: ../../addon/planets/planets.php:153
+msgid "Planets Settings"
msgstr ""
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:324
-msgid "Jabber server"
+#: ../../addon/openclipatar/openclipatar.php:50
+#: ../../addon/openclipatar/openclipatar.php:128
+msgid "System defaults:"
msgstr ""
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:330
-msgid "Jabber BOSH host URL"
+#: ../../addon/openclipatar/openclipatar.php:54
+msgid "Preferred Clipart IDs"
msgstr ""
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:337
-msgid "Jabber password"
+#: ../../addon/openclipatar/openclipatar.php:54
+msgid "List of preferred clipart ids. These will be shown first."
msgstr ""
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:343
-msgid "Encrypt Jabber password with Hubzilla password"
+#: ../../addon/openclipatar/openclipatar.php:55
+msgid "Default Search Term"
msgstr ""
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:347
-#: ../../extend/addon/addon/redred/redred.php:115
-msgid "Hubzilla password"
+#: ../../addon/openclipatar/openclipatar.php:55
+msgid "The default search term. These will be shown second."
msgstr ""
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:351
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:355
-msgid "Approve subscription requests from Hubzilla contacts automatically"
+#: ../../addon/openclipatar/openclipatar.php:56
+msgid "Return After"
msgstr ""
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:359
-msgid "Purge internal list of jabber addresses of contacts"
+#: ../../addon/openclipatar/openclipatar.php:56
+msgid "Page to load after image selection."
msgstr ""
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:364
-msgid "Configuration Help"
+#: ../../addon/openclipatar/openclipatar.php:58 ../../include/channel.php:1266
+#: ../../include/nav.php:146
+msgid "Edit Profile"
msgstr ""
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:371
-msgid "Jappix Mini Settings"
+#: ../../addon/openclipatar/openclipatar.php:59
+msgid "Profile List"
msgstr ""
-#: ../../extend/addon/addon/js_upload/js_upload.php:44
-msgid "Upload a file"
+#: ../../addon/openclipatar/openclipatar.php:61
+msgid "Order of Preferred"
msgstr ""
-#: ../../extend/addon/addon/js_upload/js_upload.php:45
-msgid "Drop files here to upload"
+#: ../../addon/openclipatar/openclipatar.php:61
+msgid "Sort order of preferred clipart ids."
msgstr ""
-#: ../../extend/addon/addon/js_upload/js_upload.php:47
-msgid "Failed"
+#: ../../addon/openclipatar/openclipatar.php:62
+#: ../../addon/openclipatar/openclipatar.php:68
+msgid "Newest first"
msgstr ""
-#: ../../extend/addon/addon/js_upload/js_upload.php:315
-msgid "No files were uploaded."
+#: ../../addon/openclipatar/openclipatar.php:65
+msgid "As entered"
msgstr ""
-#: ../../extend/addon/addon/js_upload/js_upload.php:322
-msgid "Uploaded file is empty"
+#: ../../addon/openclipatar/openclipatar.php:67
+msgid "Order of other"
msgstr ""
-#: ../../extend/addon/addon/js_upload/js_upload.php:335
-msgid "Image exceeds size limit of "
+#: ../../addon/openclipatar/openclipatar.php:67
+msgid "Sort order of other clipart ids."
msgstr ""
-#: ../../extend/addon/addon/js_upload/js_upload.php:347
-msgid "File has an invalid extension, it should be one of "
+#: ../../addon/openclipatar/openclipatar.php:69
+msgid "Most downloaded first"
msgstr ""
-#: ../../extend/addon/addon/js_upload/js_upload.php:359
-msgid "Upload was cancelled, or server error encountered"
+#: ../../addon/openclipatar/openclipatar.php:70
+msgid "Most liked first"
msgstr ""
-#: ../../extend/addon/addon/ldapauth/ldapauth.php:61
-msgid "An account has been created for you."
+#: ../../addon/openclipatar/openclipatar.php:72
+msgid "Preferred IDs Message"
msgstr ""
-#: ../../extend/addon/addon/ldapauth/ldapauth.php:68
-msgid "Authentication successful but rejected: account creation is disabled."
+#: ../../addon/openclipatar/openclipatar.php:72
+msgid "Message to display above preferred results."
msgstr ""
-#: ../../extend/addon/addon/libertree/libertree.php:38
-msgid "Post to Libertree"
+#: ../../addon/openclipatar/openclipatar.php:78
+msgid "Uploaded by: "
msgstr ""
-#: ../../extend/addon/addon/libertree/libertree.php:69
-msgid "Enable Libertree Post Plugin"
+#: ../../addon/openclipatar/openclipatar.php:78
+msgid "Drawn by: "
msgstr ""
-#: ../../extend/addon/addon/libertree/libertree.php:73
-msgid "Libertree API token"
+#: ../../addon/openclipatar/openclipatar.php:192
+msgid "Or select from a free OpenClipart.org image:"
msgstr ""
-#: ../../extend/addon/addon/libertree/libertree.php:77
-msgid "Libertree site URL"
+#: ../../addon/openclipatar/openclipatar.php:195
+msgid "Search Term"
msgstr ""
-#: ../../extend/addon/addon/libertree/libertree.php:81
-msgid "Post to Libertree by default"
+#: ../../addon/openclipatar/openclipatar.php:232
+msgid "Unknown error. Please try again later."
msgstr ""
-#: ../../extend/addon/addon/libertree/libertree.php:85
-msgid "Libertree Post Settings"
+#: ../../addon/openclipatar/openclipatar.php:308
+msgid "Profile photo updated successfully."
msgstr ""
-#: ../../extend/addon/addon/libertree/libertree.php:99
-msgid "Libertree Settings saved."
+#: ../../addon/zotvi/zot6.php:25 ../../include/zot.php:3983
+msgid "invalid target signature"
msgstr ""
-#: ../../extend/addon/addon/ljpost/ljpost.php:42
-msgid "Post to LiveJournal"
+#: ../../addon/adultphotoflag/adultphotoflag.php:24
+msgid "Flag Adult Photos"
msgstr ""
-#: ../../extend/addon/addon/ljpost/ljpost.php:70
-msgid "Enable LiveJournal Post Plugin"
+#: ../../addon/adultphotoflag/adultphotoflag.php:25
+msgid ""
+"Provide photo edit option to hide inappropriate photos from default album "
+"view"
msgstr ""
-#: ../../extend/addon/addon/ljpost/ljpost.php:74
-msgid "LiveJournal username"
+#: ../../addon/wppost/wppost.php:45
+msgid "Post to WordPress"
msgstr ""
-#: ../../extend/addon/addon/ljpost/ljpost.php:78
-msgid "LiveJournal password"
+#: ../../addon/wppost/wppost.php:82
+msgid "Enable WordPress Post Plugin"
msgstr ""
-#: ../../extend/addon/addon/ljpost/ljpost.php:82
-msgid "Post to LiveJournal by default"
+#: ../../addon/wppost/wppost.php:86
+msgid "WordPress username"
msgstr ""
-#: ../../extend/addon/addon/ljpost/ljpost.php:86
-msgid "LiveJournal Post Settings"
+#: ../../addon/wppost/wppost.php:90
+msgid "WordPress password"
msgstr ""
-#: ../../extend/addon/addon/ljpost/ljpost.php:101
-msgid "LiveJournal Settings saved."
+#: ../../addon/wppost/wppost.php:94
+msgid "WordPress API URL"
msgstr ""
-#: ../../extend/addon/addon/logrot/logrot.php:36
-msgid "Logfile archive directory"
+#: ../../addon/wppost/wppost.php:95
+msgid "Typically https://your-blog.tld/xmlrpc.php"
msgstr ""
-#: ../../extend/addon/addon/logrot/logrot.php:36
-msgid "Directory to store rotated logs"
+#: ../../addon/wppost/wppost.php:98
+msgid "WordPress blogid"
msgstr ""
-#: ../../extend/addon/addon/logrot/logrot.php:37
-msgid "Logfile size in bytes before rotating"
+#: ../../addon/wppost/wppost.php:99
+msgid "For multi-user sites such as wordpress.com, otherwise leave blank"
msgstr ""
-#: ../../extend/addon/addon/logrot/logrot.php:38
-msgid "Number of logfiles to retain"
+#: ../../addon/wppost/wppost.php:105
+msgid "Post to WordPress by default"
msgstr ""
-#: ../../extend/addon/addon/mailhost/mailhost.php:36
-msgid "Email notification hub"
+#: ../../addon/wppost/wppost.php:109
+msgid "Forward comments (requires hubzilla_wp plugin)"
msgstr ""
-#: ../../extend/addon/addon/mailhost/mailhost.php:36
-msgid "Hostname"
+#: ../../addon/wppost/wppost.php:113
+msgid "WordPress Post Settings"
msgstr ""
-#: ../../extend/addon/addon/mailhost/mailhost.php:40
-msgid "Mailhost Settings"
+#: ../../addon/wppost/wppost.php:129
+msgid "Wordpress Settings saved."
msgstr ""
-#: ../../extend/addon/addon/mailhost/mailhost.php:54
-msgid "MAILHOST Settings saved."
+#: ../../addon/nsfw/nsfw.php:80
+msgid ""
+"This plugin looks in posts for the words/text you specify below, and "
+"collapses any content containing those keywords so it is not displayed at "
+"inappropriate times, such as sexual innuendo that may be improper in a work "
+"setting. It is polite and recommended to tag any content containing nudity "
+"with #NSFW. This filter can also match any other word/text you specify, and "
+"can thereby be used as a general purpose content filter."
msgstr ""
-#: ../../extend/addon/addon/moremoods/moremoods.php:19
-msgid "lonely"
+#: ../../addon/nsfw/nsfw.php:84
+msgid "Enable Content filter"
msgstr ""
-#: ../../extend/addon/addon/moremoods/moremoods.php:20
-msgid "drunk"
+#: ../../addon/nsfw/nsfw.php:88
+msgid "Comma separated list of keywords to hide"
msgstr ""
-#: ../../extend/addon/addon/moremoods/moremoods.php:21
-msgid "horny"
+#: ../../addon/nsfw/nsfw.php:88
+msgid "Word, /regular-expression/, lang=xx, lang!=xx"
msgstr ""
-#: ../../extend/addon/addon/moremoods/moremoods.php:22
-msgid "stoned"
+#: ../../addon/nsfw/nsfw.php:92
+msgid "Not Safe For Work Settings"
msgstr ""
-#: ../../extend/addon/addon/moremoods/moremoods.php:23
-msgid "fucked up"
+#: ../../addon/nsfw/nsfw.php:92
+msgid "General Purpose Content Filter"
msgstr ""
-#: ../../extend/addon/addon/moremoods/moremoods.php:24
-msgid "clusterfucked"
+#: ../../addon/nsfw/nsfw.php:110
+msgid "NSFW Settings saved."
msgstr ""
-#: ../../extend/addon/addon/moremoods/moremoods.php:25
-msgid "crazy"
+#: ../../addon/nsfw/nsfw.php:207
+msgid "Possible adult content"
msgstr ""
-#: ../../extend/addon/addon/moremoods/moremoods.php:26
-msgid "hurt"
+#: ../../addon/nsfw/nsfw.php:211
+#, php-format
+msgid "%s - view"
msgstr ""
-#: ../../extend/addon/addon/moremoods/moremoods.php:27
-msgid "sleepy"
+#: ../../addon/ijpost/ijpost.php:42
+msgid "Post to Insanejournal"
msgstr ""
-#: ../../extend/addon/addon/moremoods/moremoods.php:28
-msgid "grumpy"
+#: ../../addon/ijpost/ijpost.php:73
+msgid "Enable InsaneJournal Post Plugin"
msgstr ""
-#: ../../extend/addon/addon/moremoods/moremoods.php:29
-msgid "high"
+#: ../../addon/ijpost/ijpost.php:77
+msgid "InsaneJournal username"
msgstr ""
-#: ../../extend/addon/addon/moremoods/moremoods.php:30
-msgid "semi-conscious"
+#: ../../addon/ijpost/ijpost.php:81
+msgid "InsaneJournal password"
msgstr ""
-#: ../../extend/addon/addon/moremoods/moremoods.php:31
-msgid "in love"
+#: ../../addon/ijpost/ijpost.php:85
+msgid "Post to InsaneJournal by default"
msgstr ""
-#: ../../extend/addon/addon/moremoods/moremoods.php:32
-msgid "in lust"
+#: ../../addon/ijpost/ijpost.php:89
+msgid "InsaneJournal Post Settings"
msgstr ""
-#: ../../extend/addon/addon/moremoods/moremoods.php:33
-msgid "naked"
+#: ../../addon/ijpost/ijpost.php:104
+msgid "Insane Journal Settings saved."
msgstr ""
-#: ../../extend/addon/addon/moremoods/moremoods.php:34
-msgid "stinky"
+#: ../../addon/js_upload/js_upload.php:44
+msgid "Upload a file"
msgstr ""
-#: ../../extend/addon/addon/moremoods/moremoods.php:35
-msgid "sweaty"
+#: ../../addon/js_upload/js_upload.php:45
+msgid "Drop files here to upload"
msgstr ""
-#: ../../extend/addon/addon/moremoods/moremoods.php:36
-msgid "bleeding out"
+#: ../../addon/js_upload/js_upload.php:47
+msgid "Failed"
msgstr ""
-#: ../../extend/addon/addon/moremoods/moremoods.php:37
-msgid "victorious"
+#: ../../addon/js_upload/js_upload.php:315
+msgid "No files were uploaded."
msgstr ""
-#: ../../extend/addon/addon/moremoods/moremoods.php:38
-msgid "defeated"
+#: ../../addon/js_upload/js_upload.php:322
+msgid "Uploaded file is empty"
msgstr ""
-#: ../../extend/addon/addon/moremoods/moremoods.php:39
-msgid "envious"
+#: ../../addon/js_upload/js_upload.php:335
+msgid "Image exceeds size limit of "
msgstr ""
-#: ../../extend/addon/addon/moremoods/moremoods.php:40
-msgid "jealous"
+#: ../../addon/js_upload/js_upload.php:347
+msgid "File has an invalid extension, it should be one of "
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:19
-msgid "bitchslap"
+#: ../../addon/js_upload/js_upload.php:359
+msgid "Upload was cancelled, or server error encountered"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:19
-msgid "bitchslapped"
+#: ../../addon/dwpost/dwpost.php:42
+msgid "Post to Dreamwidth"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:20
-msgid "shag"
+#: ../../addon/dwpost/dwpost.php:73
+msgid "Enable Dreamwidth Post Plugin"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:20
-msgid "shagged"
+#: ../../addon/dwpost/dwpost.php:77
+msgid "Dreamwidth username"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:21
-msgid "patent"
+#: ../../addon/dwpost/dwpost.php:81
+msgid "Dreamwidth password"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:21
-msgid "patented"
+#: ../../addon/dwpost/dwpost.php:85
+msgid "Post to Dreamwidth by default"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:22
-msgid "hug"
+#: ../../addon/dwpost/dwpost.php:89
+msgid "Dreamwidth Post Settings"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:22
-msgid "hugged"
+#: ../../addon/firefox/firefox.php:23
+msgid "Install Firefox Sharing Tools"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:23
-msgid "murder"
+#: ../../addon/firefox/firefox.php:34
+msgid "Share content from Firefox to $Projectname"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:23
-msgid "murdered"
+#: ../../addon/firefox/firefox.php:37
+msgid "Install Firefox Sharing Tools to this web browser"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:24
-msgid "worship"
+#: ../../addon/dirstats/dirstats.php:94
+msgid "Hubzilla Directory Stats"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:24
-msgid "worshipped"
+#: ../../addon/dirstats/dirstats.php:95
+msgid "Total Hubs"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:25
-msgid "kiss"
+#: ../../addon/dirstats/dirstats.php:97
+msgid "Hubzilla Hubs"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:25
-msgid "kissed"
+#: ../../addon/dirstats/dirstats.php:99
+msgid "Friendica Hubs"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:26
-msgid "tempt"
+#: ../../addon/dirstats/dirstats.php:101
+msgid "Diaspora Pods"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:26
-msgid "tempted"
+#: ../../addon/dirstats/dirstats.php:103
+msgid "Hubzilla Channels"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:27
-msgid "raise eyebrows at"
+#: ../../addon/dirstats/dirstats.php:105
+msgid "Friendica Channels"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:27
-msgid "raised their eyebrows at"
+#: ../../addon/dirstats/dirstats.php:107
+msgid "Diaspora Channels"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:28
-msgid "insult"
+#: ../../addon/dirstats/dirstats.php:109
+msgid "Aged 35 and above"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:28
-msgid "insulted"
+#: ../../addon/dirstats/dirstats.php:111
+msgid "Aged 34 and under"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:29
-msgid "praise"
+#: ../../addon/dirstats/dirstats.php:113
+msgid "Average Age"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:29
-msgid "praised"
+#: ../../addon/dirstats/dirstats.php:115
+msgid "Known Chatrooms"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:30
-msgid "be dubious of"
+#: ../../addon/dirstats/dirstats.php:117
+msgid "Known Tags"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:30
-msgid "was dubious of"
+#: ../../addon/dirstats/dirstats.php:119
+msgid ""
+"Please note Diaspora and Friendica statistics are merely those **this "
+"directory** is aware of, and not all those known in the network. This also "
+"applies to chatrooms,"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:31
-msgid "eat"
+#: ../../addon/mailhost/mailhost.php:36
+msgid "Email notification hub"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:31
-msgid "ate"
+#: ../../addon/mailhost/mailhost.php:36
+msgid "Hostname"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:32
-msgid "giggle and fawn at"
+#: ../../addon/mailhost/mailhost.php:40
+msgid "Mailhost Settings"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:32
-msgid "giggled and fawned at"
+#: ../../addon/mailhost/mailhost.php:54
+msgid "MAILHOST Settings saved."
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:33
-msgid "doubt"
+#: ../../addon/likebanner/likebanner.php:51
+msgid "Your Webbie:"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:33
-msgid "doubted"
+#: ../../addon/likebanner/likebanner.php:54
+msgid "Fontsize (px):"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:34
-msgid "glare"
+#: ../../addon/likebanner/likebanner.php:68
+msgid "Link:"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:34
-msgid "glared at"
+#: ../../addon/likebanner/likebanner.php:70
+msgid "Like us on Hubzilla"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:35
-msgid "fuck"
+#: ../../addon/likebanner/likebanner.php:72
+msgid "Embed:"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:35
-msgid "fucked"
+#: ../../addon/redphotos/redphotos.php:106
+msgid "Photos imported"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:36
-msgid "bonk"
+#: ../../addon/redphotos/redphotos.php:129
+msgid "Redmatrix Photo Album Import"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:36
-msgid "bonked"
+#: ../../addon/redphotos/redphotos.php:130
+msgid "This will import all your Redmatrix photo albums to this channel."
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:37
-msgid "declare undying love for"
+#: ../../addon/redphotos/redphotos.php:131
+#: ../../addon/redfiles/redfiles.php:121
+msgid "Redmatrix Server base URL"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:37
-msgid "declared undying love for"
+#: ../../addon/redphotos/redphotos.php:132
+#: ../../addon/redfiles/redfiles.php:122
+msgid "Redmatrix Login Username"
msgstr ""
-#: ../../extend/addon/addon/msgfooter/msgfooter.php:46
-#: ../../extend/addon/addon/xmpp/xmpp.php:91
-msgid "Save Settings"
+#: ../../addon/redphotos/redphotos.php:133
+#: ../../addon/redfiles/redfiles.php:123
+msgid "Redmatrix Login Password"
msgstr ""
-#: ../../extend/addon/addon/msgfooter/msgfooter.php:47
-msgid "text to include in all outgoing posts from this site"
+#: ../../addon/redphotos/redphotos.php:134
+msgid "Import just this album"
msgstr ""
-#: ../../extend/addon/addon/nofed/nofed.php:42
-msgid "Federate"
+#: ../../addon/redphotos/redphotos.php:134
+msgid "Leave blank to import all albums"
msgstr ""
-#: ../../extend/addon/addon/nofed/nofed.php:56
-msgid "nofed Settings saved."
+#: ../../addon/redphotos/redphotos.php:135
+msgid "Maximum count to import"
msgstr ""
-#: ../../extend/addon/addon/nofed/nofed.php:72
-msgid "Allow Federation Toggle"
+#: ../../addon/redphotos/redphotos.php:135
+msgid "0 or blank to import all available"
msgstr ""
-#: ../../extend/addon/addon/nofed/nofed.php:76
-msgid "Federate posts by default"
+#: ../../addon/irc/irc.php:45
+msgid "Channels to auto connect"
msgstr ""
-#: ../../extend/addon/addon/nofed/nofed.php:80
-msgid "NoFed Settings"
+#: ../../addon/irc/irc.php:45 ../../addon/irc/irc.php:49
+msgid "Comma separated list"
msgstr ""
-#: ../../extend/addon/addon/nsabait/nsabait.php:125
-msgid "Nsabait Settings updated."
+#: ../../addon/irc/irc.php:49 ../../addon/irc/irc.php:96
+msgid "Popular Channels"
msgstr ""
-#: ../../extend/addon/addon/nsabait/nsabait.php:157
-msgid "Enable NSAbait Plugin"
+#: ../../addon/irc/irc.php:53
+msgid "IRC Settings"
msgstr ""
-#: ../../extend/addon/addon/nsabait/nsabait.php:161
-msgid "NSAbait Settings"
+#: ../../addon/irc/irc.php:69
+msgid "IRC settings saved."
msgstr ""
-#: ../../extend/addon/addon/nsfw/nsfw.php:80
-msgid ""
-"This plugin looks in posts for the words/text you specify below, and "
-"collapses any content containing those keywords so it is not displayed at "
-"inappropriate times, such as sexual innuendo that may be improper in a work "
-"setting. It is polite and recommended to tag any content containing nudity "
-"with #NSFW. This filter can also match any other word/text you specify, and "
-"can thereby be used as a general purpose content filter."
+#: ../../addon/irc/irc.php:74
+msgid "IRC Chatroom"
msgstr ""
-#: ../../extend/addon/addon/nsfw/nsfw.php:84
-msgid "Enable Content filter"
+#: ../../addon/ljpost/ljpost.php:42
+msgid "Post to LiveJournal"
msgstr ""
-#: ../../extend/addon/addon/nsfw/nsfw.php:88
-msgid "Comma separated list of keywords to hide"
+#: ../../addon/ljpost/ljpost.php:70
+msgid "Enable LiveJournal Post Plugin"
msgstr ""
-#: ../../extend/addon/addon/nsfw/nsfw.php:88
-msgid "Word, /regular-expression/, lang=xx, lang!=xx"
+#: ../../addon/ljpost/ljpost.php:74
+msgid "LiveJournal username"
msgstr ""
-#: ../../extend/addon/addon/nsfw/nsfw.php:92
-msgid "Not Safe For Work Settings"
+#: ../../addon/ljpost/ljpost.php:78
+msgid "LiveJournal password"
msgstr ""
-#: ../../extend/addon/addon/nsfw/nsfw.php:92
-msgid "General Purpose Content Filter"
+#: ../../addon/ljpost/ljpost.php:82
+msgid "Post to LiveJournal by default"
msgstr ""
-#: ../../extend/addon/addon/nsfw/nsfw.php:110
-msgid "NSFW Settings saved."
+#: ../../addon/ljpost/ljpost.php:86
+msgid "LiveJournal Post Settings"
msgstr ""
-#: ../../extend/addon/addon/nsfw/nsfw.php:207
-msgid "Possible adult content"
+#: ../../addon/ljpost/ljpost.php:101
+msgid "LiveJournal Settings saved."
msgstr ""
-#: ../../extend/addon/addon/nsfw/nsfw.php:211
-#, php-format
-msgid "%s - click to open/close"
+#: ../../addon/openid/openid.php:49
+msgid ""
+"We encountered a problem while logging in with the OpenID you provided. "
+"Please check the correct spelling of the ID."
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:50
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:128
-msgid "System defaults:"
+#: ../../addon/openid/openid.php:49
+msgid "The error message was:"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:54
-msgid "Preferred Clipart IDs"
+#: ../../addon/openid/MysqlProvider.php:52
+msgid "First Name"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:54
-msgid "List of preferred clipart ids. These will be shown first."
+#: ../../addon/openid/MysqlProvider.php:53
+msgid "Last Name"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:55
-msgid "Default Search Term"
+#: ../../addon/openid/MysqlProvider.php:54 ../../addon/redred/redred.php:111
+msgid "Nickname"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:55
-msgid "The default search term. These will be shown second."
+#: ../../addon/openid/MysqlProvider.php:55
+msgid "Full Name"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:56
-msgid "Return After"
+#: ../../addon/openid/MysqlProvider.php:61
+msgid "Profile Photo 16px"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:56
-msgid "Page to load after image selection."
+#: ../../addon/openid/MysqlProvider.php:62
+msgid "Profile Photo 32px"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:58
-#: ../../include/channel.php:1048 ../../include/nav.php:107
-msgid "Edit Profile"
+#: ../../addon/openid/MysqlProvider.php:63
+msgid "Profile Photo 48px"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:59
-msgid "Profile List"
+#: ../../addon/openid/MysqlProvider.php:64
+msgid "Profile Photo 64px"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:61
-msgid "Order of Preferred"
+#: ../../addon/openid/MysqlProvider.php:65
+msgid "Profile Photo 80px"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:61
-msgid "Sort order of preferred clipart ids."
+#: ../../addon/openid/MysqlProvider.php:66
+msgid "Profile Photo 128px"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:62
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:68
-msgid "Newest first"
+#: ../../addon/openid/MysqlProvider.php:67
+msgid "Timezone"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:65
-msgid "As entered"
+#: ../../addon/openid/MysqlProvider.php:70
+msgid "Birth Year"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:67
-msgid "Order of other"
+#: ../../addon/openid/MysqlProvider.php:71
+msgid "Birth Month"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:67
-msgid "Sort order of other clipart ids."
+#: ../../addon/openid/MysqlProvider.php:72
+msgid "Birth Day"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:69
-msgid "Most downloaded first"
+#: ../../addon/openid/MysqlProvider.php:73
+msgid "Birthdate"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:70
-msgid "Most liked first"
+#: ../../addon/openid/Mod_Openid.php:30
+msgid "OpenID protocol error. No ID returned."
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:72
-msgid "Preferred IDs Message"
+#: ../../addon/openid/Mod_Openid.php:188 ../../include/auth.php:289
+msgid "Login failed."
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:72
-msgid "Message to display above preferred results."
+#: ../../addon/openid/Mod_Id.php:85 ../../include/selectors.php:49
+#: ../../include/selectors.php:66 ../../include/channel.php:1432
+msgid "Male"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:78
-msgid "Uploaded by: "
+#: ../../addon/openid/Mod_Id.php:87 ../../include/selectors.php:49
+#: ../../include/selectors.php:66 ../../include/channel.php:1430
+msgid "Female"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:78
-msgid "Drawn by: "
+#: ../../addon/randpost/randpost.php:97
+msgid "You're welcome."
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:192
-msgid "Or select from a free OpenClipart.org image:"
+#: ../../addon/randpost/randpost.php:98
+msgid "Ah shucks..."
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:195
-msgid "Search Term"
+#: ../../addon/randpost/randpost.php:99
+msgid "Don't mention it."
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:232
-msgid "Unknown error. Please try again later."
+#: ../../addon/randpost/randpost.php:100
+msgid "&lt;blush&gt;"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:306
-msgid "Profile photo updated successfully."
+#: ../../addon/startpage/startpage.php:109
+msgid "Page to load after login"
msgstr ""
-#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:146
-msgid "View Larger"
+#: ../../addon/startpage/startpage.php:109
+msgid ""
+"Examples: &quot;apps&quot;, &quot;network?f=&gid=37&quot; (privacy "
+"collection), &quot;channel&quot; or &quot;notifications/system&quot; (leave "
+"blank for default network page (grid)."
msgstr ""
-#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:169
-msgid "Tile Server URL"
+#: ../../addon/startpage/startpage.php:113
+msgid "Startpage Settings"
msgstr ""
-#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:169
-msgid ""
-"A list of <a href=\"http://wiki.openstreetmap.org/wiki/TMS\" target=\"_blank"
-"\">public tile servers</a>"
+#: ../../addon/morepokes/morepokes.php:19
+msgid "bitchslap"
msgstr ""
-#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:170
-msgid "Nominatim (reverse geocoding) Server URL"
+#: ../../addon/morepokes/morepokes.php:19
+msgid "bitchslapped"
msgstr ""
-#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:170
-msgid ""
-"A list of <a href=\"http://wiki.openstreetmap.org/wiki/Nominatim\" target="
-"\"_blank\">Nominatim servers</a>"
+#: ../../addon/morepokes/morepokes.php:20
+msgid "shag"
msgstr ""
-#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:171
-msgid "Default zoom"
+#: ../../addon/morepokes/morepokes.php:20
+msgid "shagged"
msgstr ""
-#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:171
-msgid ""
-"The default zoom level. (1:world, 18:highest, also depends on tile server)"
+#: ../../addon/morepokes/morepokes.php:21
+msgid "patent"
msgstr ""
-#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:172
-msgid "Include marker on map"
+#: ../../addon/morepokes/morepokes.php:21
+msgid "patented"
msgstr ""
-#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:172
-msgid "Include a marker on the map."
+#: ../../addon/morepokes/morepokes.php:22
+msgid "hug"
msgstr ""
-#: ../../extend/addon/addon/pageheader/pageheader.php:43
-msgid "Message to display on every page on this server"
+#: ../../addon/morepokes/morepokes.php:22
+msgid "hugged"
msgstr ""
-#: ../../extend/addon/addon/pageheader/pageheader.php:48
-msgid "Pageheader Settings"
+#: ../../addon/morepokes/morepokes.php:23
+msgid "murder"
msgstr ""
-#: ../../extend/addon/addon/pageheader/pageheader.php:64
-msgid "pageheader Settings saved."
+#: ../../addon/morepokes/morepokes.php:23
+msgid "murdered"
msgstr ""
-#: ../../extend/addon/addon/piwik/piwik.php:85
-msgid ""
-"This website is tracked using the <a href='http://www.piwik.org'>Piwik</a> "
-"analytics tool."
+#: ../../addon/morepokes/morepokes.php:24
+msgid "worship"
msgstr ""
-#: ../../extend/addon/addon/piwik/piwik.php:88
-#, php-format
-msgid ""
-"If you do not want that your visits are logged this way you <a href='%s'>can "
-"set a cookie to prevent Piwik from tracking further visits of the site</a> "
-"(opt-out)."
+#: ../../addon/morepokes/morepokes.php:24
+msgid "worshipped"
msgstr ""
-#: ../../extend/addon/addon/piwik/piwik.php:96
-msgid "Piwik Base URL"
+#: ../../addon/morepokes/morepokes.php:25
+msgid "kiss"
msgstr ""
-#: ../../extend/addon/addon/piwik/piwik.php:96
-msgid ""
-"Absolute path to your Piwik installation. (without protocol (http/s), with "
-"trailing slash)"
+#: ../../addon/morepokes/morepokes.php:25
+msgid "kissed"
msgstr ""
-#: ../../extend/addon/addon/piwik/piwik.php:97
-msgid "Site ID"
+#: ../../addon/morepokes/morepokes.php:26
+msgid "tempt"
msgstr ""
-#: ../../extend/addon/addon/piwik/piwik.php:98
-msgid "Show opt-out cookie link?"
+#: ../../addon/morepokes/morepokes.php:26
+msgid "tempted"
msgstr ""
-#: ../../extend/addon/addon/piwik/piwik.php:99
-msgid "Asynchronous tracking"
+#: ../../addon/morepokes/morepokes.php:27
+msgid "raise eyebrows at"
msgstr ""
-#: ../../extend/addon/addon/piwik/piwik.php:100
-msgid "Enable frontend JavaScript error tracking"
+#: ../../addon/morepokes/morepokes.php:27
+msgid "raised their eyebrows at"
msgstr ""
-#: ../../extend/addon/addon/piwik/piwik.php:100
-msgid "This feature requires Piwik >= 2.2.0"
+#: ../../addon/morepokes/morepokes.php:28
+msgid "insult"
msgstr ""
-#: ../../extend/addon/addon/planets/planets.php:121
-msgid "Planets Settings updated."
+#: ../../addon/morepokes/morepokes.php:28
+msgid "insulted"
msgstr ""
-#: ../../extend/addon/addon/planets/planets.php:153
-msgid "Enable Planets Plugin"
+#: ../../addon/morepokes/morepokes.php:29
+msgid "praise"
msgstr ""
-#: ../../extend/addon/addon/planets/planets.php:157
-msgid "Planets Settings"
+#: ../../addon/morepokes/morepokes.php:29
+msgid "praised"
msgstr ""
-#: ../../extend/addon/addon/pumpio/pumpio.php:148
-msgid "You are now authenticated to pumpio."
+#: ../../addon/morepokes/morepokes.php:30
+msgid "be dubious of"
msgstr ""
-#: ../../extend/addon/addon/pumpio/pumpio.php:149
-msgid "return to the featured settings page"
+#: ../../addon/morepokes/morepokes.php:30
+msgid "was dubious of"
msgstr ""
-#: ../../extend/addon/addon/pumpio/pumpio.php:163
-msgid "Post to Pump.io"
+#: ../../addon/morepokes/morepokes.php:31
+msgid "eat"
msgstr ""
-#: ../../extend/addon/addon/pumpio/pumpio.php:198
-msgid "Pump.io servername"
+#: ../../addon/morepokes/morepokes.php:31
+msgid "ate"
msgstr ""
-#: ../../extend/addon/addon/pumpio/pumpio.php:198
-msgid "Without \"http://\" or \"https://\""
+#: ../../addon/morepokes/morepokes.php:32
+msgid "giggle and fawn at"
msgstr ""
-#: ../../extend/addon/addon/pumpio/pumpio.php:202
-msgid "Pump.io username"
+#: ../../addon/morepokes/morepokes.php:32
+msgid "giggled and fawned at"
msgstr ""
-#: ../../extend/addon/addon/pumpio/pumpio.php:202
-msgid "Without the servername"
+#: ../../addon/morepokes/morepokes.php:33
+msgid "doubt"
msgstr ""
-#: ../../extend/addon/addon/pumpio/pumpio.php:213
-msgid "You are not authenticated to pumpio"
+#: ../../addon/morepokes/morepokes.php:33
+msgid "doubted"
msgstr ""
-#: ../../extend/addon/addon/pumpio/pumpio.php:215
-msgid "(Re-)Authenticate your pump.io connection"
+#: ../../addon/morepokes/morepokes.php:34
+msgid "glare"
msgstr ""
-#: ../../extend/addon/addon/pumpio/pumpio.php:219
-msgid "Enable pump.io Post Plugin"
+#: ../../addon/morepokes/morepokes.php:34
+msgid "glared at"
msgstr ""
-#: ../../extend/addon/addon/pumpio/pumpio.php:223
-msgid "Post to pump.io by default"
+#: ../../addon/morepokes/morepokes.php:35
+msgid "fuck"
msgstr ""
-#: ../../extend/addon/addon/pumpio/pumpio.php:227
-msgid "Should posts be public"
+#: ../../addon/morepokes/morepokes.php:35
+msgid "fucked"
msgstr ""
-#: ../../extend/addon/addon/pumpio/pumpio.php:231
-msgid "Mirror all public posts"
+#: ../../addon/morepokes/morepokes.php:36
+msgid "bonk"
msgstr ""
-#: ../../extend/addon/addon/pumpio/pumpio.php:237
-msgid "Pump.io Post Settings"
+#: ../../addon/morepokes/morepokes.php:36
+msgid "bonked"
msgstr ""
-#: ../../extend/addon/addon/pumpio/pumpio.php:266
-msgid "PumpIO Settings saved."
+#: ../../addon/morepokes/morepokes.php:37
+msgid "declare undying love for"
msgstr ""
-#: ../../extend/addon/addon/qrator/qrator.php:48
-msgid "QR code"
+#: ../../addon/morepokes/morepokes.php:37
+msgid "declared undying love for"
msgstr ""
-#: ../../extend/addon/addon/qrator/qrator.php:63
-msgid "QR Generator"
+#: ../../addon/diaspora/diaspora.php:763
+msgid "Diaspora Protocol Settings updated."
msgstr ""
-#: ../../extend/addon/addon/qrator/qrator.php:64
-msgid "Enter some text"
+#: ../../addon/diaspora/diaspora.php:782
+msgid ""
+"The Diaspora protocol does not support location independence. Connections "
+"you make within that network may be unreachable from alternate channel "
+"locations."
msgstr ""
-#: ../../extend/addon/addon/rainbowtag/rainbowtag.php:81
-msgid "Enable Rainbowtag"
+#: ../../addon/diaspora/diaspora.php:785
+msgid "Enable the Diaspora protocol for this channel"
msgstr ""
-#: ../../extend/addon/addon/rainbowtag/rainbowtag.php:85
-msgid "Rainbowtag Settings"
+#: ../../addon/diaspora/diaspora.php:789
+msgid "Allow any Diaspora member to comment on your public posts"
msgstr ""
-#: ../../extend/addon/addon/rainbowtag/rainbowtag.php:101
-msgid "Rainbowtag Settings saved."
+#: ../../addon/diaspora/diaspora.php:793
+msgid "Prevent your hashtags from being redirected to other sites"
msgstr ""
-#: ../../extend/addon/addon/randpost/randpost.php:97
-msgid "You're welcome."
+#: ../../addon/diaspora/diaspora.php:797
+msgid "Sign and forward posts and comments with no existing Diaspora signature"
msgstr ""
-#: ../../extend/addon/addon/randpost/randpost.php:98
-msgid "Ah shucks..."
+#: ../../addon/diaspora/diaspora.php:802
+msgid "Followed hashtags (comma separated, do not include the #)"
msgstr ""
-#: ../../extend/addon/addon/randpost/randpost.php:99
-msgid "Don't mention it."
+#: ../../addon/diaspora/diaspora.php:807
+msgid "Diaspora Protocol Settings"
msgstr ""
-#: ../../extend/addon/addon/randpost/randpost.php:100
-msgid "&lt;blush&gt;"
+#: ../../addon/diaspora/import_diaspora.php:16
+msgid "No username found in import file."
msgstr ""
-#: ../../extend/addon/addon/redfiles/redfiles.php:119
-msgid "Redmatrix File Storage Import"
+#: ../../addon/diaspora/import_diaspora.php:41 ../../include/import.php:62
+msgid "Unable to create a unique channel address. Import failed."
msgstr ""
-#: ../../extend/addon/addon/redfiles/redfiles.php:120
-msgid "This will import all your Redmatrix cloud files to this channel."
+#: ../../addon/testdrive/testdrive.php:104
+#, php-format
+msgid "Your account on %s will expire in a few days."
msgstr ""
-#: ../../extend/addon/addon/redfiles/redfiles.php:121
-#: ../../extend/addon/addon/redphotos/redphotos.php:131
-msgid "Redmatrix Server base URL"
+#: ../../addon/testdrive/testdrive.php:105
+msgid "Your $Productname test account is about to expire."
msgstr ""
-#: ../../extend/addon/addon/redfiles/redfiles.php:122
-#: ../../extend/addon/addon/redphotos/redphotos.php:132
-msgid "Redmatrix Login Username"
+#: ../../addon/rainbowtag/rainbowtag.php:81
+msgid "Enable Rainbowtag"
msgstr ""
-#: ../../extend/addon/addon/redfiles/redfiles.php:123
-#: ../../extend/addon/addon/redphotos/redphotos.php:133
-msgid "Redmatrix Login Password"
+#: ../../addon/rainbowtag/rainbowtag.php:85
+msgid "Rainbowtag Settings"
msgstr ""
-#: ../../extend/addon/addon/redfiles/redfilehelper.php:67
-msgid "file"
+#: ../../addon/rainbowtag/rainbowtag.php:101
+msgid "Rainbowtag Settings saved."
msgstr ""
-#: ../../extend/addon/addon/redphotos/redphotos.php:106
-msgid "Photos imported"
+#: ../../addon/upload_limits/upload_limits.php:25
+msgid "Show Upload Limits"
msgstr ""
-#: ../../extend/addon/addon/redphotos/redphotos.php:129
-msgid "Redmatrix Photo Album Import"
+#: ../../addon/upload_limits/upload_limits.php:27
+msgid "Hubzilla configured maximum size: "
msgstr ""
-#: ../../extend/addon/addon/redphotos/redphotos.php:130
-msgid "This will import all your Redmatrix photo albums to this channel."
+#: ../../addon/upload_limits/upload_limits.php:28
+msgid "PHP upload_max_filesize: "
msgstr ""
-#: ../../extend/addon/addon/redphotos/redphotos.php:134
-msgid "Import just this album"
+#: ../../addon/upload_limits/upload_limits.php:29
+msgid "PHP post_max_size (must be larger than upload_max_filesize): "
msgstr ""
-#: ../../extend/addon/addon/redphotos/redphotos.php:134
-msgid "Leave blank to import all albums"
+#: ../../addon/gravatar/gravatar.php:123
+msgid "generic profile image"
msgstr ""
-#: ../../extend/addon/addon/redphotos/redphotos.php:135
-msgid "Maximum count to import"
+#: ../../addon/gravatar/gravatar.php:124
+msgid "random geometric pattern"
msgstr ""
-#: ../../extend/addon/addon/redphotos/redphotos.php:135
-msgid "0 or blank to import all available"
+#: ../../addon/gravatar/gravatar.php:125
+msgid "monster face"
msgstr ""
-#: ../../extend/addon/addon/redred/redred.php:45
-msgid "Post to Red"
+#: ../../addon/gravatar/gravatar.php:126
+msgid "computer generated face"
msgstr ""
-#: ../../extend/addon/addon/redred/redred.php:60
-msgid "Channel is required."
+#: ../../addon/gravatar/gravatar.php:127
+msgid "retro arcade style face"
msgstr ""
-#: ../../extend/addon/addon/redred/redred.php:65
-msgid "Invalid channel."
+#: ../../addon/gravatar/gravatar.php:128
+msgid "Hub default profile photo"
msgstr ""
-#: ../../extend/addon/addon/redred/redred.php:76
-msgid "redred Settings saved."
+#: ../../addon/gravatar/gravatar.php:143
+msgid "Information"
msgstr ""
-#: ../../extend/addon/addon/redred/redred.php:95
-msgid "Allow posting to another Hubzilla Channel"
+#: ../../addon/gravatar/gravatar.php:143
+msgid ""
+"Libravatar addon is installed, too. Please disable Libravatar addon or this "
+"Gravatar addon.<br>The Libravatar addon will fall back to Gravatar if "
+"nothing was found at Libravatar."
msgstr ""
-#: ../../extend/addon/addon/redred/redred.php:99
-msgid "Send public postings to Hubzilla channel by default"
+#: ../../addon/gravatar/gravatar.php:150 ../../addon/msgfooter/msgfooter.php:46
+#: ../../addon/xmpp/xmpp.php:91
+msgid "Save Settings"
msgstr ""
-#: ../../extend/addon/addon/redred/redred.php:103
-msgid "Hubzilla API Path"
+#: ../../addon/gravatar/gravatar.php:151
+msgid "Default avatar image"
msgstr ""
-#: ../../extend/addon/addon/redred/redred.php:103
-#: ../../extend/addon/addon/rtof/rtof.php:89
-msgid "https://{sitename}/api"
+#: ../../addon/gravatar/gravatar.php:151
+msgid "Select default avatar image if none was found at Gravatar. See README"
msgstr ""
-#: ../../extend/addon/addon/redred/redred.php:107
-msgid "Hubzilla login name"
+#: ../../addon/gravatar/gravatar.php:152
+msgid "Rating of images"
msgstr ""
-#: ../../extend/addon/addon/redred/redred.php:111
-msgid "Hubzilla channel name"
+#: ../../addon/gravatar/gravatar.php:152
+msgid "Select the appropriate avatar rating for your site. See README"
msgstr ""
-#: ../../extend/addon/addon/redred/redred.php:111
-#: ../../extend/addon/addon/openid/MysqlProvider.php:54
-msgid "Nickname"
+#: ../../addon/gravatar/gravatar.php:165
+msgid "Gravatar settings updated."
msgstr ""
-#: ../../extend/addon/addon/redred/redred.php:119
-msgid "Hubzilla Crosspost Settings"
+#: ../../addon/visage/visage.php:93
+msgid "Recent Channel/Profile Viewers"
msgstr ""
-#: ../../extend/addon/addon/rtof/rtof.php:45
-msgid "Post to Friendica"
+#: ../../addon/visage/visage.php:98
+msgid "This plugin/addon has not been configured."
msgstr ""
-#: ../../extend/addon/addon/rtof/rtof.php:62
-msgid "rtof Settings saved."
+#: ../../addon/visage/visage.php:99
+#, php-format
+msgid "Please visit the Visage settings on %s"
msgstr ""
-#: ../../extend/addon/addon/rtof/rtof.php:81
-msgid "Allow posting to Friendica"
+#: ../../addon/visage/visage.php:99
+msgid "your feature settings page"
msgstr ""
-#: ../../extend/addon/addon/rtof/rtof.php:85
-msgid "Send public postings to Friendica by default"
+#: ../../addon/visage/visage.php:112
+msgid "No entries."
msgstr ""
-#: ../../extend/addon/addon/rtof/rtof.php:89
-msgid "Friendica API Path"
+#: ../../addon/visage/visage.php:166
+msgid "Enable Visage Visitor Logging"
msgstr ""
-#: ../../extend/addon/addon/rtof/rtof.php:93
-msgid "Friendica login name"
+#: ../../addon/visage/visage.php:170
+msgid "Visage Settings"
msgstr ""
-#: ../../extend/addon/addon/rtof/rtof.php:97
-msgid "Friendica password"
+#: ../../addon/nsabait/nsabait.php:125
+msgid "Nsabait Settings updated."
msgstr ""
-#: ../../extend/addon/addon/rtof/rtof.php:101
-msgid "Hubzilla to Friendica Post Settings"
+#: ../../addon/nsabait/nsabait.php:157
+msgid "Enable NSAbait Plugin"
msgstr ""
-#: ../../extend/addon/addon/sendzid/sendzid.php:25
-msgid "Extended Identity Sharing"
+#: ../../addon/nsabait/nsabait.php:161
+msgid "NSAbait Settings"
msgstr ""
-#: ../../extend/addon/addon/sendzid/sendzid.php:26
-msgid ""
-"Share your identity with all websites on the internet. When disabled, "
-"identity is only shared with sites in the matrix."
+#: ../../addon/mailtest/mailtest.php:19
+msgid "Send test email"
msgstr ""
-#: ../../extend/addon/addon/skeleton/skeleton.php:59
-msgid "Some setting"
+#: ../../addon/mailtest/mailtest.php:50 ../../addon/hubwall/hubwall.php:50
+msgid "No recipients found."
msgstr ""
-#: ../../extend/addon/addon/skeleton/skeleton.php:61
-msgid "A setting"
+#: ../../addon/mailtest/mailtest.php:66
+msgid "Mail sent."
msgstr ""
-#: ../../extend/addon/addon/skeleton/skeleton.php:64
-msgid "Skeleton Settings"
+#: ../../addon/mailtest/mailtest.php:68
+msgid "Sending of mail failed."
msgstr ""
-#: ../../extend/addon/addon/smileybutton/smileybutton.php:273
-msgid "Deactivate the feature"
+#: ../../addon/mailtest/mailtest.php:77
+msgid "Mail Test"
msgstr ""
-#: ../../extend/addon/addon/smileybutton/smileybutton.php:277
-msgid "Hide the button and show the smilies directly."
+#: ../../addon/mailtest/mailtest.php:96 ../../addon/hubwall/hubwall.php:92
+msgid "Message subject"
msgstr ""
-#: ../../extend/addon/addon/smileybutton/smileybutton.php:281
-msgid "Smileybutton Settings"
+#: ../../addon/openstreetmap/openstreetmap.php:146
+msgid "View Larger"
msgstr ""
-#: ../../extend/addon/addon/startpage/startpage.php:109
-msgid "Page to load after login"
+#: ../../addon/openstreetmap/openstreetmap.php:169
+msgid "Tile Server URL"
msgstr ""
-#: ../../extend/addon/addon/startpage/startpage.php:109
+#: ../../addon/openstreetmap/openstreetmap.php:169
msgid ""
-"Examples: &quot;apps&quot;, &quot;network?f=&gid=37&quot; (privacy "
-"collection), &quot;channel&quot; or &quot;notifications/system&quot; (leave "
-"blank for default network page (grid)."
-msgstr ""
-
-#: ../../extend/addon/addon/startpage/startpage.php:113
-msgid "Startpage Settings"
+"A list of <a href=\"http://wiki.openstreetmap.org/wiki/TMS\" target=\"_blank"
+"\">public tile servers</a>"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:143
-msgid "Post to GNU social"
+#: ../../addon/openstreetmap/openstreetmap.php:170
+msgid "Nominatim (reverse geocoding) Server URL"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:195
+#: ../../addon/openstreetmap/openstreetmap.php:170
msgid ""
-"Please contact your site administrator.<br />The provided API URL is not "
-"valid."
+"A list of <a href=\"http://wiki.openstreetmap.org/wiki/Nominatim\" target="
+"\"_blank\">Nominatim servers</a>"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:232
-msgid "We could not contact the GNU social API with the Path you entered."
+#: ../../addon/openstreetmap/openstreetmap.php:171
+msgid "Default zoom"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:266
-msgid "GNU social settings updated."
+#: ../../addon/openstreetmap/openstreetmap.php:171
+msgid ""
+"The default zoom level. (1:world, 18:highest, also depends on tile server)"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:310
-msgid "Globally Available GNU social OAuthKeys"
+#: ../../addon/openstreetmap/openstreetmap.php:172
+msgid "Include marker on map"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:312
-msgid ""
-"There are preconfigured OAuth key pairs for some GNU social servers "
-"available. If you are using one of them, please use these credentials.<br /"
-">If not feel free to connect to any other GNU social instance (see below)."
+#: ../../addon/openstreetmap/openstreetmap.php:172
+msgid "Include a marker on the map."
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:327
-msgid "Provide your own OAuth Credentials"
+#: ../../addon/msgfooter/msgfooter.php:47
+msgid "text to include in all outgoing posts from this site"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:329
-msgid ""
-"No consumer key pair for GNU social found. Register your Hubzilla Account as "
-"an desktop client on your GNU social account, copy the consumer key pair "
-"here and enter the API base root.<br />Before you register your own OAuth "
-"key pair ask the administrator if there is already a key pair for this "
-"Hubzilla installation at your favourite GNU social installation."
+#: ../../addon/rtof/rtof.php:45
+msgid "Post to Friendica"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:333
-msgid "OAuth Consumer Key"
+#: ../../addon/rtof/rtof.php:62
+msgid "rtof Settings saved."
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:337
-msgid "OAuth Consumer Secret"
+#: ../../addon/rtof/rtof.php:81
+msgid "Allow posting to Friendica"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:341
-msgid "Base API Path"
+#: ../../addon/rtof/rtof.php:85
+msgid "Send public postings to Friendica by default"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:341
-msgid "Remember the trailing /"
+#: ../../addon/rtof/rtof.php:89
+msgid "Friendica API Path"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:345
-msgid "GNU social application name"
+#: ../../addon/rtof/rtof.php:89 ../../addon/redred/redred.php:103
+msgid "https://{sitename}/api"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:368
-msgid ""
-"To connect to your GNU social account click the button below to get a "
-"security code from GNU social which you have to copy into the input box "
-"below and submit the form. Only your <strong>public</strong> posts will be "
-"posted to GNU social."
+#: ../../addon/rtof/rtof.php:93
+msgid "Friendica login name"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:370
-msgid "Log in with GNU social"
+#: ../../addon/rtof/rtof.php:97
+msgid "Friendica password"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:373
-msgid "Copy the security code from GNU social here"
+#: ../../addon/rtof/rtof.php:101
+msgid "Hubzilla to Friendica Post Settings"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:383
-msgid "Cancel Connection Process"
+#: ../../addon/jappixmini/jappixmini.php:305 ../../include/channel.php:1357
+#: ../../include/channel.php:1519
+msgid "Status:"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:385
-msgid "Current GNU social API is"
+#: ../../addon/jappixmini/jappixmini.php:309
+msgid "Activate addon"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:389
-msgid "Cancel GNU social Connection"
+#: ../../addon/jappixmini/jappixmini.php:313
+msgid "Hide Jappixmini Chat-Widget from the webinterface"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:401
-#: ../../extend/addon/addon/twitter/twitter.php:232
-msgid "Currently connected to: "
+#: ../../addon/jappixmini/jappixmini.php:318
+msgid "Jabber username"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:406
-msgid ""
-"<strong>Note</strong>: Due your privacy settings (<em>Hide your profile "
-"details from unknown viewers?</em>) the link potentially included in public "
-"postings relayed to GNU social will lead the visitor to a blank page "
-"informing the visitor that the access to your profile has been restricted."
+#: ../../addon/jappixmini/jappixmini.php:324
+msgid "Jabber server"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:411
-msgid "Allow posting to GNU social"
+#: ../../addon/jappixmini/jappixmini.php:330
+msgid "Jabber BOSH host URL"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:411
-msgid ""
-"If enabled your public postings can be posted to the associated GNU-social "
-"account"
+#: ../../addon/jappixmini/jappixmini.php:337
+msgid "Jabber password"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:415
-msgid "Post to GNU social by default"
+#: ../../addon/jappixmini/jappixmini.php:343
+msgid "Encrypt Jabber password with Hubzilla password"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:415
-msgid ""
-"If enabled your public postings will be posted to the associated GNU-social "
-"account by default"
+#: ../../addon/jappixmini/jappixmini.php:347 ../../addon/redred/redred.php:115
+msgid "Hubzilla password"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:424
-#: ../../extend/addon/addon/twitter/twitter.php:255
-msgid "Clear OAuth configuration"
+#: ../../addon/jappixmini/jappixmini.php:351
+#: ../../addon/jappixmini/jappixmini.php:355
+msgid "Approve subscription requests from Hubzilla contacts automatically"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:432
-msgid "GNU social Post Settings"
+#: ../../addon/jappixmini/jappixmini.php:359
+msgid "Purge internal list of jabber addresses of contacts"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:891
-msgid "API URL"
+#: ../../addon/jappixmini/jappixmini.php:364
+msgid "Configuration Help"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:894
-msgid "Application name"
+#: ../../addon/jappixmini/jappixmini.php:371
+msgid "Jappix Mini Settings"
msgstr ""
-#: ../../extend/addon/addon/superblock/superblock.php:110
+#: ../../addon/superblock/superblock.php:112
msgid "Currently blocked"
msgstr ""
-#: ../../extend/addon/addon/superblock/superblock.php:112
+#: ../../addon/superblock/superblock.php:114
msgid "No channels currently blocked"
msgstr ""
-#: ../../extend/addon/addon/superblock/superblock.php:118
+#: ../../addon/superblock/superblock.php:120
msgid "\"Superblock\" Settings"
msgstr ""
-#: ../../extend/addon/addon/superblock/superblock.php:322
+#: ../../addon/superblock/superblock.php:345
msgid "Block Completely"
msgstr ""
-#: ../../extend/addon/addon/superblock/superblock.php:371
+#: ../../addon/superblock/superblock.php:394
msgid "superblock settings updated"
msgstr ""
-#: ../../extend/addon/addon/testdrive/testdrive.php:104
-#, php-format
-msgid "Your account on %s will expire in a few days."
+#: ../../addon/nofed/nofed.php:42
+msgid "Federate"
msgstr ""
-#: ../../extend/addon/addon/testdrive/testdrive.php:105
-msgid "Your $Productname test account is about to expire."
+#: ../../addon/nofed/nofed.php:56
+msgid "nofed Settings saved."
msgstr ""
-#: ../../extend/addon/addon/tictac/tictac.php:21
-msgid "Three Dimensional Tic-Tac-Toe"
+#: ../../addon/nofed/nofed.php:72
+msgid "Allow Federation Toggle"
msgstr ""
-#: ../../extend/addon/addon/tictac/tictac.php:54
-msgid "3D Tic-Tac-Toe"
+#: ../../addon/nofed/nofed.php:76
+msgid "Federate posts by default"
msgstr ""
-#: ../../extend/addon/addon/tictac/tictac.php:59
-msgid "New game"
+#: ../../addon/nofed/nofed.php:80
+msgid "NoFed Settings"
msgstr ""
-#: ../../extend/addon/addon/tictac/tictac.php:60
-msgid "New game with handicap"
+#: ../../addon/redred/redred.php:45
+msgid "Post to Red"
msgstr ""
-#: ../../extend/addon/addon/tictac/tictac.php:61
-msgid ""
-"Three dimensional tic-tac-toe is just like the traditional game except that "
-"it is played on multiple levels simultaneously. "
+#: ../../addon/redred/redred.php:60
+msgid "Channel is required."
msgstr ""
-#: ../../extend/addon/addon/tictac/tictac.php:62
-msgid ""
-"In this case there are three levels. You win by getting three in a row on "
-"any level, as well as up, down, and diagonally across the different levels."
+#: ../../addon/redred/redred.php:76
+msgid "redred Settings saved."
msgstr ""
-#: ../../extend/addon/addon/tictac/tictac.php:64
-msgid ""
-"The handicap game disables the center position on the middle level because "
-"the player claiming this square often has an unfair advantage."
+#: ../../addon/redred/redred.php:95
+msgid "Allow posting to another Hubzilla Channel"
msgstr ""
-#: ../../extend/addon/addon/tictac/tictac.php:183
-msgid "You go first..."
+#: ../../addon/redred/redred.php:99
+msgid "Send public postings to Hubzilla channel by default"
msgstr ""
-#: ../../extend/addon/addon/tictac/tictac.php:188
-msgid "I'm going first this time..."
+#: ../../addon/redred/redred.php:103
+msgid "Hubzilla API Path"
msgstr ""
-#: ../../extend/addon/addon/tictac/tictac.php:194
-msgid "You won!"
+#: ../../addon/redred/redred.php:107
+msgid "Hubzilla login name"
msgstr ""
-#: ../../extend/addon/addon/tictac/tictac.php:200
-#: ../../extend/addon/addon/tictac/tictac.php:225
-msgid "\"Cat\" game!"
+#: ../../addon/redred/redred.php:111
+msgid "Hubzilla channel name"
msgstr ""
-#: ../../extend/addon/addon/tictac/tictac.php:223
-msgid "I won!"
+#: ../../addon/redred/redred.php:119
+msgid "Hubzilla Crosspost Settings"
msgstr ""
-#: ../../extend/addon/addon/tour/tour.php:75
-msgid "Edit your profile and change settings."
+#: ../../addon/logrot/logrot.php:36
+msgid "Logfile archive directory"
msgstr ""
-#: ../../extend/addon/addon/tour/tour.php:76
-msgid "Click here to see activity from your connections."
+#: ../../addon/logrot/logrot.php:36
+msgid "Directory to store rotated logs"
msgstr ""
-#: ../../extend/addon/addon/tour/tour.php:77
-msgid "Click here to see your channel home."
+#: ../../addon/logrot/logrot.php:37
+msgid "Logfile size in bytes before rotating"
msgstr ""
-#: ../../extend/addon/addon/tour/tour.php:78
-msgid "You can access your private messages from here."
+#: ../../addon/logrot/logrot.php:38
+msgid "Number of logfiles to retain"
msgstr ""
-#: ../../extend/addon/addon/tour/tour.php:79
-msgid "Create new events here."
+#: ../../addon/frphotos/frphotos.php:91
+msgid "Friendica Photo Album Import"
msgstr ""
-#: ../../extend/addon/addon/tour/tour.php:80
-msgid ""
-"You can accept new connections and change permissions for existing ones "
-"here. You can also e.g. create groups of contacts."
+#: ../../addon/frphotos/frphotos.php:92
+msgid "This will import all your Friendica photo albums to this Red channel."
msgstr ""
-#: ../../extend/addon/addon/tour/tour.php:81
-msgid "System notifications will arrive here"
+#: ../../addon/frphotos/frphotos.php:93
+msgid "Friendica Server base URL"
msgstr ""
-#: ../../extend/addon/addon/tour/tour.php:82
-msgid "Search for content and users"
+#: ../../addon/frphotos/frphotos.php:94
+msgid "Friendica Login Username"
msgstr ""
-#: ../../extend/addon/addon/tour/tour.php:83
-msgid "Browse for new contacts"
+#: ../../addon/frphotos/frphotos.php:95
+msgid "Friendica Login Password"
msgstr ""
-#: ../../extend/addon/addon/tour/tour.php:84
-msgid "Launch installed apps"
+#: ../../addon/pubcrawl/as.php:1076 ../../addon/pubcrawl/as.php:1160
+#: ../../addon/pubcrawl/as.php:1332 ../../include/network.php:1705
+msgid "ActivityPub"
msgstr ""
-#: ../../extend/addon/addon/tour/tour.php:85
-msgid "Looking for help? Click here."
+#: ../../addon/pubcrawl/pubcrawl.php:1032
+msgid "ActivityPub Protocol Settings updated."
msgstr ""
-#: ../../extend/addon/addon/tour/tour.php:86
+#: ../../addon/pubcrawl/pubcrawl.php:1041
msgid ""
-"New events have occurred in your network. Click here to see what has "
-"happened!"
-msgstr ""
-
-#: ../../extend/addon/addon/tour/tour.php:87
-msgid "You have received a new private message. Click here to see from who!"
-msgstr ""
-
-#: ../../extend/addon/addon/tour/tour.php:88
-msgid "There are events this week. Click here too see which!"
+"The ActivityPub protocol does not support location independence. Connections "
+"you make within that network may be unreachable from alternate channel "
+"locations."
msgstr ""
-#: ../../extend/addon/addon/tour/tour.php:89
-msgid "You have received a new introduction. Click here to see who!"
-msgstr ""
-
-#: ../../extend/addon/addon/tour/tour.php:90
-msgid ""
-"There is a new system notification. Click here to see what has happened!"
+#: ../../addon/pubcrawl/pubcrawl.php:1044
+msgid "Enable the ActivityPub protocol for this channel"
msgstr ""
-#: ../../extend/addon/addon/tour/tour.php:93
-msgid "Click here to share text, images, videos and sound."
+#: ../../addon/pubcrawl/pubcrawl.php:1049
+msgid "ActivityPub Protocol Settings"
msgstr ""
-#: ../../extend/addon/addon/tour/tour.php:94
-msgid "You can write an optional title for your update (good for long posts)."
+#: ../../addon/donate/donate.php:21
+msgid "Project Servers and Resources"
msgstr ""
-#: ../../extend/addon/addon/tour/tour.php:95
-msgid "Entering some categories here makes it easier to find your post later."
+#: ../../addon/donate/donate.php:22
+msgid "Project Creator and Tech Lead"
msgstr ""
-#: ../../extend/addon/addon/tour/tour.php:96
-msgid "Share photos, links, location, etc."
+#: ../../addon/donate/donate.php:23
+msgid "Admin, developer, directorymin, support bloke"
msgstr ""
-#: ../../extend/addon/addon/tour/tour.php:97
+#: ../../addon/donate/donate.php:50
msgid ""
-"Only want to share content for a while? Make it expire at a certain date."
-msgstr ""
-
-#: ../../extend/addon/addon/tour/tour.php:98
-msgid "You can password protect content."
-msgstr ""
-
-#: ../../extend/addon/addon/tour/tour.php:99
-msgid "Choose who you share with."
-msgstr ""
-
-#: ../../extend/addon/addon/tour/tour.php:101
-msgid "Click here when you are done."
-msgstr ""
-
-#: ../../extend/addon/addon/tour/tour.php:104
-msgid "Adjust from which channels posts should be displayed."
-msgstr ""
-
-#: ../../extend/addon/addon/tour/tour.php:105
-msgid "Only show posts from channels in the specified privacy group."
+"And the hundreds of other people and organisations who helped make the "
+"Hubzilla possible."
msgstr ""
-#: ../../extend/addon/addon/tour/tour.php:109
+#: ../../addon/donate/donate.php:53
msgid ""
-"Easily find posts containing tags (keywords preceded by the \"#\" symbol)."
-msgstr ""
-
-#: ../../extend/addon/addon/tour/tour.php:110
-msgid "Easily find posts in given category."
-msgstr ""
-
-#: ../../extend/addon/addon/tour/tour.php:111
-msgid "Easily find posts by date."
+"The Redmatrix/Hubzilla projects are provided primarily by volunteers giving "
+"their time and expertise - and often paying out of pocket for services they "
+"share with others."
msgstr ""
-#: ../../extend/addon/addon/tour/tour.php:112
+#: ../../addon/donate/donate.php:54
msgid ""
-"Suggested users who have volounteered to be shown as suggestions, and who we "
-"think you might find interesting."
-msgstr ""
-
-#: ../../extend/addon/addon/tour/tour.php:113
-msgid "Here you see channels you have connected to."
-msgstr ""
-
-#: ../../extend/addon/addon/tour/tour.php:114
-msgid "Save your search so you can repeat it at a later date."
+"There is no corporate funding and no ads, and we do not collect and sell "
+"your personal information. (We don't control your personal information - "
+"<strong>you do</strong>.)"
msgstr ""
-#: ../../extend/addon/addon/tour/tour.php:117
+#: ../../addon/donate/donate.php:55
msgid ""
-"If you see this icon you can be sure that the sender is who it say it is. It "
-"is normal that it is not always possible to verify the sender, so the icon "
-"will be missing sometimes. There is usually no need to worry about that."
+"Help support our ground-breaking work in decentralisation, web identity, and "
+"privacy."
msgstr ""
-#: ../../extend/addon/addon/tour/tour.php:118
+#: ../../addon/donate/donate.php:57
msgid ""
-"Danger! It seems someone tried to forge a message! This message is not "
-"necessarily from who it says it is from!"
+"Your donations keep servers and services running and also helps us to "
+"provide innovative new features and continued development."
msgstr ""
-#: ../../extend/addon/addon/tour/tour.php:125
-msgid ""
-"Welcome to Hubzilla! Would you like to see a tour of the UI?</p> <p>You can "
-"pause it at any time and continue where you left off by reloading the page, "
-"or navigting to another page.</p><p>You can also advance by pressing the "
-"return key"
+#: ../../addon/donate/donate.php:60
+msgid "Donate"
msgstr ""
-#: ../../extend/addon/addon/twitter/twitter.php:99
-msgid "Post to Twitter"
+#: ../../addon/donate/donate.php:62
+msgid ""
+"Choose a project, developer, or public hub to support with a one-time "
+"donation"
msgstr ""
-#: ../../extend/addon/addon/twitter/twitter.php:154
-msgid "Twitter settings updated."
+#: ../../addon/donate/donate.php:63
+msgid "Donate Now"
msgstr ""
-#: ../../extend/addon/addon/twitter/twitter.php:183
+#: ../../addon/donate/donate.php:64
msgid ""
-"No consumer key pair for Twitter found. Please contact your site "
-"administrator."
+"<strong><em>Or</em></strong> become a project sponsor (Hubzilla Project only)"
msgstr ""
-#: ../../extend/addon/addon/twitter/twitter.php:205
+#: ../../addon/donate/donate.php:65
msgid ""
-"At this Hubzilla instance the Twitter plugin was enabled but you have not "
-"yet connected your account to your Twitter account. To do so click the "
-"button below to get a PIN from Twitter which you have to copy into the input "
-"box below and submit the form. Only your <strong>public</strong> posts will "
-"be posted to Twitter."
+"Please indicate if you would like your first name or full name (or nothing) "
+"to appear in our sponsor listing"
msgstr ""
-#: ../../extend/addon/addon/twitter/twitter.php:207
-msgid "Log in with Twitter"
+#: ../../addon/donate/donate.php:66
+msgid "Sponsor"
msgstr ""
-#: ../../extend/addon/addon/twitter/twitter.php:210
-msgid "Copy the PIN from Twitter here"
+#: ../../addon/donate/donate.php:69
+msgid "Special thanks to: "
msgstr ""
-#: ../../extend/addon/addon/twitter/twitter.php:237
+#: ../../addon/chords/Mod_Chords.php:44
msgid ""
-"<strong>Note:</strong> Due your privacy settings (<em>Hide your profile "
-"details from unknown viewers?</em>) the link potentially included in public "
-"postings relayed to Twitter will lead the visitor to a blank page informing "
-"the visitor that the access to your profile has been restricted."
-msgstr ""
-
-#: ../../extend/addon/addon/twitter/twitter.php:242
-msgid "Allow posting to Twitter"
+"This is a fairly comprehensive and complete guitar chord dictionary which "
+"will list most of the available ways to play a certain chord, starting from "
+"the base of the fingerboard up to a few frets beyond the twelfth fret "
+"(beyond which everything repeats). A couple of non-standard tunings are "
+"provided for the benefit of slide players, etc."
msgstr ""
-#: ../../extend/addon/addon/twitter/twitter.php:242
+#: ../../addon/chords/Mod_Chords.php:46
msgid ""
-"If enabled your public postings can be posted to the associated Twitter "
-"account"
-msgstr ""
-
-#: ../../extend/addon/addon/twitter/twitter.php:246
-msgid "Send public postings to Twitter by default"
+"Chord names start with a root note (A-G) and may include sharps (#) and "
+"flats (b). This software will parse most of the standard naming conventions "
+"such as maj, min, dim, sus(2 or 4), aug, with optional repeating elements."
msgstr ""
-#: ../../extend/addon/addon/twitter/twitter.php:246
+#: ../../addon/chords/Mod_Chords.php:48
msgid ""
-"If enabled your public postings will be posted to the associated Twitter "
-"account by default"
+"Valid examples include A, A7, Am7, Amaj7, Amaj9, Ammaj7, Aadd4, Asus2Add4, "
+"E7b13b11 ..."
msgstr ""
-#: ../../extend/addon/addon/twitter/twitter.php:264
-msgid "Twitter Post Settings"
+#: ../../addon/chords/Mod_Chords.php:51
+msgid "Guitar Chords"
msgstr ""
-#: ../../extend/addon/addon/twitter/twitter.php:773
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:95
-msgid "Submit Settings"
+#: ../../addon/chords/Mod_Chords.php:52
+msgid "The complete online chord dictionary"
msgstr ""
-#: ../../extend/addon/addon/upload_limits/upload_limits.php:25
-msgid "Show Upload Limits"
+#: ../../addon/chords/Mod_Chords.php:57
+msgid "Tuning"
msgstr ""
-#: ../../extend/addon/addon/upload_limits/upload_limits.php:27
-msgid "Hubzilla configured maximum size: "
+#: ../../addon/chords/Mod_Chords.php:58
+msgid "Chord name: example: Em7"
msgstr ""
-#: ../../extend/addon/addon/upload_limits/upload_limits.php:28
-msgid "PHP upload_max_filesize: "
+#: ../../addon/chords/Mod_Chords.php:59
+msgid "Show for left handed stringing"
msgstr ""
-#: ../../extend/addon/addon/upload_limits/upload_limits.php:29
-msgid "PHP post_max_size (must be larger than upload_max_filesize): "
+#: ../../addon/chords/chords.php:33
+msgid "Quick Reference"
msgstr ""
-#: ../../extend/addon/addon/visage/visage.php:93
-msgid "Recent Channel/Profile Viewers"
+#: ../../addon/libertree/libertree.php:38
+msgid "Post to Libertree"
msgstr ""
-#: ../../extend/addon/addon/visage/visage.php:98
-msgid "This plugin/addon has not been configured."
+#: ../../addon/libertree/libertree.php:69
+msgid "Enable Libertree Post Plugin"
msgstr ""
-#: ../../extend/addon/addon/visage/visage.php:99
-#, php-format
-msgid "Please visit the Visage settings on %s"
+#: ../../addon/libertree/libertree.php:73
+msgid "Libertree API token"
msgstr ""
-#: ../../extend/addon/addon/visage/visage.php:99
-msgid "your feature settings page"
+#: ../../addon/libertree/libertree.php:77
+msgid "Libertree site URL"
msgstr ""
-#: ../../extend/addon/addon/visage/visage.php:112
-msgid "No entries."
+#: ../../addon/libertree/libertree.php:81
+msgid "Post to Libertree by default"
msgstr ""
-#: ../../extend/addon/addon/visage/visage.php:166
-msgid "Enable Visage Visitor Logging"
+#: ../../addon/libertree/libertree.php:85
+msgid "Libertree Post Settings"
msgstr ""
-#: ../../extend/addon/addon/visage/visage.php:170
-msgid "Visage Settings"
+#: ../../addon/libertree/libertree.php:99
+msgid "Libertree Settings saved."
msgstr ""
-#: ../../extend/addon/addon/wholikesme/wholikesme.php:29
-msgid "Who likes me?"
+#: ../../addon/flattrwidget/flattrwidget.php:45
+msgid "Flattr this!"
msgstr ""
-#: ../../extend/addon/addon/wppost/wppost.php:45
-msgid "Post to WordPress"
+#: ../../addon/flattrwidget/flattrwidget.php:83
+msgid "Flattr widget settings updated."
msgstr ""
-#: ../../extend/addon/addon/wppost/wppost.php:82
-msgid "Enable WordPress Post Plugin"
+#: ../../addon/flattrwidget/flattrwidget.php:100
+msgid "Flattr user"
msgstr ""
-#: ../../extend/addon/addon/wppost/wppost.php:86
-msgid "WordPress username"
+#: ../../addon/flattrwidget/flattrwidget.php:104
+msgid "URL of the Thing to flattr"
msgstr ""
-#: ../../extend/addon/addon/wppost/wppost.php:90
-msgid "WordPress password"
+#: ../../addon/flattrwidget/flattrwidget.php:104
+msgid "If empty channel URL is used"
msgstr ""
-#: ../../extend/addon/addon/wppost/wppost.php:94
-msgid "WordPress API URL"
+#: ../../addon/flattrwidget/flattrwidget.php:108
+msgid "Title of the Thing to flattr"
msgstr ""
-#: ../../extend/addon/addon/wppost/wppost.php:95
-msgid "Typically https://your-blog.tld/xmlrpc.php"
+#: ../../addon/flattrwidget/flattrwidget.php:108
+msgid "If empty \"channel name on The Hubzilla\" will be used"
msgstr ""
-#: ../../extend/addon/addon/wppost/wppost.php:98
-msgid "WordPress blogid"
+#: ../../addon/flattrwidget/flattrwidget.php:112
+msgid "Static or dynamic flattr button"
msgstr ""
-#: ../../extend/addon/addon/wppost/wppost.php:99
-msgid "For multi-user sites such as wordpress.com, otherwise leave blank"
+#: ../../addon/flattrwidget/flattrwidget.php:112
+msgid "static"
msgstr ""
-#: ../../extend/addon/addon/wppost/wppost.php:105
-msgid "Post to WordPress by default"
+#: ../../addon/flattrwidget/flattrwidget.php:112
+msgid "dynamic"
msgstr ""
-#: ../../extend/addon/addon/wppost/wppost.php:109
-msgid "Forward comments (requires hubzilla_wp plugin)"
+#: ../../addon/flattrwidget/flattrwidget.php:116
+msgid "Alignment of the widget"
msgstr ""
-#: ../../extend/addon/addon/wppost/wppost.php:113
-msgid "WordPress Post Settings"
+#: ../../addon/flattrwidget/flattrwidget.php:116
+msgid "left"
msgstr ""
-#: ../../extend/addon/addon/wppost/wppost.php:129
-msgid "Wordpress Settings saved."
+#: ../../addon/flattrwidget/flattrwidget.php:116
+msgid "right"
msgstr ""
-#: ../../extend/addon/addon/xmpp/xmpp.php:31
-msgid "XMPP settings updated."
+#: ../../addon/flattrwidget/flattrwidget.php:120
+msgid "Enable Flattr widget"
msgstr ""
-#: ../../extend/addon/addon/xmpp/xmpp.php:53
-msgid "Enable Chat"
+#: ../../addon/flattrwidget/flattrwidget.php:124
+msgid "Flattr Widget Settings"
msgstr ""
-#: ../../extend/addon/addon/xmpp/xmpp.php:58
-msgid "Individual credentials"
+#: ../../addon/statusnet/statusnet.php:143
+msgid "Post to GNU social"
msgstr ""
-#: ../../extend/addon/addon/xmpp/xmpp.php:64
-msgid "Jabber BOSH server"
+#: ../../addon/statusnet/statusnet.php:195
+msgid ""
+"Please contact your site administrator.<br />The provided API URL is not "
+"valid."
msgstr ""
-#: ../../extend/addon/addon/xmpp/xmpp.php:69
-msgid "XMPP Settings"
+#: ../../addon/statusnet/statusnet.php:232
+msgid "We could not contact the GNU social API with the Path you entered."
msgstr ""
-#: ../../extend/addon/addon/xmpp/xmpp.php:92
-msgid "Jabber BOSH host"
+#: ../../addon/statusnet/statusnet.php:266
+msgid "GNU social settings updated."
msgstr ""
-#: ../../extend/addon/addon/xmpp/xmpp.php:93
-msgid "Use central userbase"
+#: ../../addon/statusnet/statusnet.php:310
+msgid "Globally Available GNU social OAuthKeys"
msgstr ""
-#: ../../extend/addon/addon/xmpp/xmpp.php:93
+#: ../../addon/statusnet/statusnet.php:312
msgid ""
-"If enabled, members will automatically login to an ejabberd server that has "
-"to be installed on this machine with synchronized credentials via the "
-"\"auth_ejabberd.php\" script."
+"There are preconfigured OAuth key pairs for some GNU social servers "
+"available. If you are using one of them, please use these credentials.<br /"
+">If not feel free to connect to any other GNU social instance (see below)."
msgstr ""
-#: ../../extend/addon/addon/cdav/include/widgets.php:37
-msgid "Select Channel"
+#: ../../addon/statusnet/statusnet.php:327
+msgid "Provide your own OAuth Credentials"
msgstr ""
-#: ../../extend/addon/addon/cdav/include/widgets.php:42
-msgid "Read-write"
+#: ../../addon/statusnet/statusnet.php:329
+msgid ""
+"No consumer key pair for GNU social found. Register your Hubzilla Account as "
+"an desktop client on your GNU social account, copy the consumer key pair "
+"here and enter the API base root.<br />Before you register your own OAuth "
+"key pair ask the administrator if there is already a key pair for this "
+"Hubzilla installation at your favourite GNU social installation."
msgstr ""
-#: ../../extend/addon/addon/cdav/include/widgets.php:43
-msgid "Read-only"
+#: ../../addon/statusnet/statusnet.php:333
+msgid "OAuth Consumer Key"
msgstr ""
-#: ../../extend/addon/addon/cdav/include/widgets.php:116
-msgid "My Calendars"
+#: ../../addon/statusnet/statusnet.php:337
+msgid "OAuth Consumer Secret"
msgstr ""
-#: ../../extend/addon/addon/cdav/include/widgets.php:118
-msgid "Shared Calendars"
+#: ../../addon/statusnet/statusnet.php:341
+msgid "Base API Path"
msgstr ""
-#: ../../extend/addon/addon/cdav/include/widgets.php:122
-msgid "Share this calendar"
+#: ../../addon/statusnet/statusnet.php:341
+msgid "Remember the trailing /"
msgstr ""
-#: ../../extend/addon/addon/cdav/include/widgets.php:124
-msgid "Calendar name and color"
+#: ../../addon/statusnet/statusnet.php:345
+msgid "GNU social application name"
msgstr ""
-#: ../../extend/addon/addon/cdav/include/widgets.php:126
-msgid "Create new calendar"
+#: ../../addon/statusnet/statusnet.php:368
+msgid ""
+"To connect to your GNU social account click the button below to get a "
+"security code from GNU social which you have to copy into the input box "
+"below and submit the form. Only your <strong>public</strong> posts will be "
+"posted to GNU social."
msgstr ""
-#: ../../extend/addon/addon/cdav/include/widgets.php:128
-msgid "Calendar Name"
+#: ../../addon/statusnet/statusnet.php:370
+msgid "Log in with GNU social"
msgstr ""
-#: ../../extend/addon/addon/cdav/include/widgets.php:129
-msgid "Calendar Tools"
+#: ../../addon/statusnet/statusnet.php:373
+msgid "Copy the security code from GNU social here"
msgstr ""
-#: ../../extend/addon/addon/cdav/include/widgets.php:130
-msgid "Import calendar"
+#: ../../addon/statusnet/statusnet.php:383
+msgid "Cancel Connection Process"
msgstr ""
-#: ../../extend/addon/addon/cdav/include/widgets.php:131
-msgid "Select a calendar to import to"
+#: ../../addon/statusnet/statusnet.php:385
+msgid "Current GNU social API is"
msgstr ""
-#: ../../extend/addon/addon/cdav/include/widgets.php:158
-msgid "Addressbooks"
+#: ../../addon/statusnet/statusnet.php:389
+msgid "Cancel GNU social Connection"
msgstr ""
-#: ../../extend/addon/addon/cdav/include/widgets.php:160
-msgid "Addressbook name"
+#: ../../addon/statusnet/statusnet.php:401 ../../addon/twitter/twitter.php:232
+msgid "Currently connected to: "
msgstr ""
-#: ../../extend/addon/addon/cdav/include/widgets.php:162
-msgid "Create new addressbook"
+#: ../../addon/statusnet/statusnet.php:406
+msgid ""
+"<strong>Note</strong>: Due your privacy settings (<em>Hide your profile "
+"details from unknown viewers?</em>) the link potentially included in public "
+"postings relayed to GNU social will lead the visitor to a blank page "
+"informing the visitor that the access to your profile has been restricted."
msgstr ""
-#: ../../extend/addon/addon/cdav/include/widgets.php:163
-msgid "Addressbook Name"
+#: ../../addon/statusnet/statusnet.php:411
+msgid "Allow posting to GNU social"
msgstr ""
-#: ../../extend/addon/addon/cdav/include/widgets.php:165
-msgid "Addressbook Tools"
+#: ../../addon/statusnet/statusnet.php:411
+msgid ""
+"If enabled your public postings can be posted to the associated GNU-social "
+"account"
msgstr ""
-#: ../../extend/addon/addon/cdav/include/widgets.php:166
-msgid "Import addressbook"
+#: ../../addon/statusnet/statusnet.php:415
+msgid "Post to GNU social by default"
msgstr ""
-#: ../../extend/addon/addon/cdav/include/widgets.php:167
-msgid "Select an addressbook to import to"
+#: ../../addon/statusnet/statusnet.php:415
+msgid ""
+"If enabled your public postings will be posted to the associated GNU-social "
+"account by default"
msgstr ""
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:744
-msgid "INVALID EVENT DISMISSED!"
+#: ../../addon/statusnet/statusnet.php:424 ../../addon/twitter/twitter.php:255
+msgid "Clear OAuth configuration"
msgstr ""
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:745
-msgid "Summary: "
+#: ../../addon/statusnet/statusnet.php:432
+msgid "GNU social Post Settings"
msgstr ""
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:746
-msgid "Date: "
+#: ../../addon/statusnet/statusnet.php:891
+msgid "API URL"
msgstr ""
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:747
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:754
-msgid "Reason: "
+#: ../../addon/statusnet/statusnet.php:894
+msgid "Application name"
msgstr ""
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:752
-msgid "INVALID CARD DISMISSED!"
+#: ../../addon/qrator/qrator.php:48
+msgid "QR code"
msgstr ""
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:753
-msgid "Name: "
+#: ../../addon/qrator/qrator.php:63
+msgid "QR Generator"
msgstr ""
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:770
-msgid ""
-"You have to enable this plugin in Feature/Addon Settings > CalDAV/CardDAV "
-"Settings before you can use it."
+#: ../../addon/qrator/qrator.php:64
+msgid "Enter some text"
msgstr ""
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:836
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:837
-msgid "Example: YYYY-MM-DD HH:mm"
+#: ../../addon/chess/chess.php:278 ../../addon/chess/chess.php:465
+msgid "Invalid game."
msgstr ""
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:837
-msgid "End date and time"
+#: ../../addon/chess/chess.php:284 ../../addon/chess/chess.php:471
+msgid "You are not a player in this game."
msgstr ""
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:852
-msgid "List month"
+#: ../../addon/chess/chess.php:340
+msgid "You must be a local channel to create a game."
msgstr ""
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:853
-msgid "List week"
+#: ../../addon/chess/chess.php:358
+msgid "You must select one opponent that is not yourself."
msgstr ""
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:854
-msgid "List day"
+#: ../../addon/chess/chess.php:367
+msgid "You must select white or black."
msgstr ""
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:861
-msgid "More"
+#: ../../addon/chess/chess.php:375
+msgid "Error creating new game."
msgstr ""
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:862
-msgid "Less"
+#: ../../addon/chess/chess.php:409 ../../include/channel.php:1117
+msgid "Requested channel is not available."
msgstr ""
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:863
-msgid "Select calendar"
+#: ../../addon/chess/chess.php:423
+msgid "You must select a local channel /chess/channelname"
msgstr ""
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:865
-msgid "Delete all"
+#: ../../addon/chess/chess.php:969
+msgid "Enable notifications"
msgstr ""
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:867
-msgid "Sorry! Editing of recurrent events is not yet implemented."
+#: ../../addon/twitter/twitter.php:99
+msgid "Post to Twitter"
msgstr ""
-#: ../../extend/addon/addon/cdav/cdav.php:36
-msgid "Errors encountered creating database table: "
+#: ../../addon/twitter/twitter.php:154
+msgid "Twitter settings updated."
msgstr ""
-#: ../../extend/addon/addon/cdav/cdav.php:197
-msgid "Default Calendar"
+#: ../../addon/twitter/twitter.php:183
+msgid ""
+"No consumer key pair for Twitter found. Please contact your site "
+"administrator."
msgstr ""
-#: ../../extend/addon/addon/cdav/cdav.php:206
-msgid "Default Addressbook"
+#: ../../addon/twitter/twitter.php:205
+msgid ""
+"At this Hubzilla instance the Twitter plugin was enabled but you have not "
+"yet connected your account to your Twitter account. To do so click the "
+"button below to get a PIN from Twitter which you have to copy into the input "
+"box below and submit the form. Only your <strong>public</strong> posts will "
+"be posted to Twitter."
msgstr ""
-#: ../../extend/addon/addon/cdav/cdav.php:215
-msgid "CalDAV/CardDAV Settings saved."
+#: ../../addon/twitter/twitter.php:207
+msgid "Log in with Twitter"
msgstr ""
-#: ../../extend/addon/addon/cdav/cdav.php:234
-msgid "Enable CalDAV/CardDAV Server for this channel"
+#: ../../addon/twitter/twitter.php:210
+msgid "Copy the PIN from Twitter here"
msgstr ""
-#: ../../extend/addon/addon/cdav/cdav.php:237
-#, php-format
-msgid "Your CalDAV resources are located at %s "
+#: ../../addon/twitter/twitter.php:237
+msgid ""
+"<strong>Note:</strong> Due your privacy settings (<em>Hide your profile "
+"details from unknown viewers?</em>) the link potentially included in public "
+"postings relayed to Twitter will lead the visitor to a blank page informing "
+"the visitor that the access to your profile has been restricted."
msgstr ""
-#: ../../extend/addon/addon/cdav/cdav.php:240
-#, php-format
-msgid "Your CardDAV resources are located at %s "
+#: ../../addon/twitter/twitter.php:242
+msgid "Allow posting to Twitter"
msgstr ""
-#: ../../extend/addon/addon/cdav/cdav.php:246
-msgid "CalDAV/CardDAV Settings"
+#: ../../addon/twitter/twitter.php:242
+msgid ""
+"If enabled your public postings can be posted to the associated Twitter "
+"account"
msgstr ""
-#: ../../extend/addon/addon/cdav/cdav.php:272
-#: ../../include/connections.php:896
-msgid "Home, Voice"
+#: ../../addon/twitter/twitter.php:246
+msgid "Send public postings to Twitter by default"
msgstr ""
-#: ../../extend/addon/addon/cdav/cdav.php:273
-#: ../../include/connections.php:897
-msgid "Home, Fax"
+#: ../../addon/twitter/twitter.php:246
+msgid ""
+"If enabled your public postings will be posted to the associated Twitter "
+"account by default"
msgstr ""
-#: ../../extend/addon/addon/cdav/cdav.php:275
-#: ../../include/connections.php:899
-msgid "Work, Voice"
+#: ../../addon/twitter/twitter.php:264
+msgid "Twitter Post Settings"
msgstr ""
-#: ../../extend/addon/addon/cdav/cdav.php:276
-#: ../../include/connections.php:900
-msgid "Work, Fax"
+#: ../../addon/smileybutton/smileybutton.php:211
+msgid "Deactivate the feature"
msgstr ""
-#: ../../extend/addon/addon/chess/chess.php:276
-#: ../../extend/addon/addon/chess/chess.php:430
-msgid "Invalid game."
+#: ../../addon/smileybutton/smileybutton.php:215
+msgid "Hide the button and show the smilies directly."
msgstr ""
-#: ../../extend/addon/addon/chess/chess.php:282
-#: ../../extend/addon/addon/chess/chess.php:436
-msgid "You are not a player in this game."
+#: ../../addon/smileybutton/smileybutton.php:219
+msgid "Smileybutton Settings"
msgstr ""
-#: ../../extend/addon/addon/chess/chess.php:315
-msgid "You must be a local channel to create a game."
+#: ../../addon/piwik/piwik.php:85
+msgid ""
+"This website is tracked using the <a href='http://www.piwik.org'>Piwik</a> "
+"analytics tool."
msgstr ""
-#: ../../extend/addon/addon/chess/chess.php:333
-msgid "You must select one opponent that is not yourself."
+#: ../../addon/piwik/piwik.php:88
+#, php-format
+msgid ""
+"If you do not want that your visits are logged this way you <a href='%s'>can "
+"set a cookie to prevent Piwik from tracking further visits of the site</a> "
+"(opt-out)."
msgstr ""
-#: ../../extend/addon/addon/chess/chess.php:336
-msgid "Creating new game..."
+#: ../../addon/piwik/piwik.php:96
+msgid "Piwik Base URL"
msgstr ""
-#: ../../extend/addon/addon/chess/chess.php:342
-msgid "You must select white or black."
+#: ../../addon/piwik/piwik.php:96
+msgid ""
+"Absolute path to your Piwik installation. (without protocol (http/s), with "
+"trailing slash)"
msgstr ""
-#: ../../extend/addon/addon/chess/chess.php:349
-msgid "Error creating new game."
+#: ../../addon/piwik/piwik.php:97
+msgid "Site ID"
msgstr ""
-#: ../../extend/addon/addon/chess/chess.php:379 ../../include/channel.php:899
-msgid "Requested channel is not available."
+#: ../../addon/piwik/piwik.php:98
+msgid "Show opt-out cookie link?"
msgstr ""
-#: ../../extend/addon/addon/chess/chess.php:392
-msgid "You must select a local channel /chess/channelname"
+#: ../../addon/piwik/piwik.php:99
+msgid "Asynchronous tracking"
msgstr ""
-#: ../../extend/addon/addon/chess/chess.php:920
-msgid "Enable notifications"
+#: ../../addon/piwik/piwik.php:100
+msgid "Enable frontend JavaScript error tracking"
msgstr ""
-#: ../../extend/addon/addon/likebanner/likebanner.php:51
-msgid "Your Webbie:"
+#: ../../addon/piwik/piwik.php:100
+msgid "This feature requires Piwik >= 2.2.0"
msgstr ""
-#: ../../extend/addon/addon/likebanner/likebanner.php:54
-msgid "Fontsize (px):"
+#: ../../addon/tour/tour.php:75
+msgid "Edit your profile and change settings."
msgstr ""
-#: ../../extend/addon/addon/likebanner/likebanner.php:68
-msgid "Link:"
+#: ../../addon/tour/tour.php:76
+msgid "Click here to see activity from your connections."
msgstr ""
-#: ../../extend/addon/addon/likebanner/likebanner.php:70
-msgid "Like us on Hubzilla"
+#: ../../addon/tour/tour.php:77
+msgid "Click here to see your channel home."
msgstr ""
-#: ../../extend/addon/addon/likebanner/likebanner.php:72
-msgid "Embed:"
+#: ../../addon/tour/tour.php:78
+msgid "You can access your private messages from here."
msgstr ""
-#: ../../extend/addon/addon/openid/Mod_Id.php:85
-#: ../../include/selectors.php:49 ../../include/selectors.php:66
-msgid "Male"
+#: ../../addon/tour/tour.php:79
+msgid "Create new events here."
msgstr ""
-#: ../../extend/addon/addon/openid/Mod_Id.php:87
-#: ../../include/selectors.php:49 ../../include/selectors.php:66
-msgid "Female"
+#: ../../addon/tour/tour.php:80
+msgid ""
+"You can accept new connections and change permissions for existing ones "
+"here. You can also e.g. create groups of contacts."
msgstr ""
-#: ../../extend/addon/addon/openid/MysqlProvider.php:52
-msgid "First Name"
+#: ../../addon/tour/tour.php:81
+msgid "System notifications will arrive here"
msgstr ""
-#: ../../extend/addon/addon/openid/MysqlProvider.php:53
-msgid "Last Name"
+#: ../../addon/tour/tour.php:82
+msgid "Search for content and users"
msgstr ""
-#: ../../extend/addon/addon/openid/MysqlProvider.php:55
-msgid "Full Name"
+#: ../../addon/tour/tour.php:83
+msgid "Browse for new contacts"
msgstr ""
-#: ../../extend/addon/addon/openid/MysqlProvider.php:61
-msgid "Profile Photo 16px"
+#: ../../addon/tour/tour.php:84
+msgid "Launch installed apps"
msgstr ""
-#: ../../extend/addon/addon/openid/MysqlProvider.php:62
-msgid "Profile Photo 32px"
+#: ../../addon/tour/tour.php:85
+msgid "Looking for help? Click here."
msgstr ""
-#: ../../extend/addon/addon/openid/MysqlProvider.php:63
-msgid "Profile Photo 48px"
+#: ../../addon/tour/tour.php:86
+msgid ""
+"New events have occurred in your network. Click here to see what has "
+"happened!"
msgstr ""
-#: ../../extend/addon/addon/openid/MysqlProvider.php:64
-msgid "Profile Photo 64px"
+#: ../../addon/tour/tour.php:87
+msgid "You have received a new private message. Click here to see from who!"
msgstr ""
-#: ../../extend/addon/addon/openid/MysqlProvider.php:65
-msgid "Profile Photo 80px"
+#: ../../addon/tour/tour.php:88
+msgid "There are events this week. Click here too see which!"
msgstr ""
-#: ../../extend/addon/addon/openid/MysqlProvider.php:66
-msgid "Profile Photo 128px"
+#: ../../addon/tour/tour.php:89
+msgid "You have received a new introduction. Click here to see who!"
msgstr ""
-#: ../../extend/addon/addon/openid/MysqlProvider.php:67
-msgid "Timezone"
+#: ../../addon/tour/tour.php:90
+msgid ""
+"There is a new system notification. Click here to see what has happened!"
msgstr ""
-#: ../../extend/addon/addon/openid/MysqlProvider.php:70
-msgid "Birth Year"
+#: ../../addon/tour/tour.php:93
+msgid "Click here to share text, images, videos and sound."
msgstr ""
-#: ../../extend/addon/addon/openid/MysqlProvider.php:71
-msgid "Birth Month"
+#: ../../addon/tour/tour.php:94
+msgid "You can write an optional title for your update (good for long posts)."
msgstr ""
-#: ../../extend/addon/addon/openid/MysqlProvider.php:72
-msgid "Birth Day"
+#: ../../addon/tour/tour.php:95
+msgid "Entering some categories here makes it easier to find your post later."
msgstr ""
-#: ../../extend/addon/addon/openid/MysqlProvider.php:73
-msgid "Birthdate"
+#: ../../addon/tour/tour.php:96
+msgid "Share photos, links, location, etc."
msgstr ""
-#: ../../extend/addon/addon/openid/openid.php:49
+#: ../../addon/tour/tour.php:97
msgid ""
-"We encountered a problem while logging in with the OpenID you provided. "
-"Please check the correct spelling of the ID."
+"Only want to share content for a while? Make it expire at a certain date."
msgstr ""
-#: ../../extend/addon/addon/openid/openid.php:49
-msgid "The error message was:"
+#: ../../addon/tour/tour.php:98
+msgid "You can password protect content."
msgstr ""
-#: ../../extend/addon/addon/openid/Mod_Openid.php:30
-msgid "OpenID protocol error. No ID returned."
+#: ../../addon/tour/tour.php:99
+msgid "Choose who you share with."
msgstr ""
-#: ../../extend/addon/addon/openid/Mod_Openid.php:188
-#: ../../include/auth.php:286
-msgid "Login failed."
+#: ../../addon/tour/tour.php:101
+msgid "Click here when you are done."
msgstr ""
-#: ../../extend/addon/addon/diaspora_reconnect/diaspora_reconnect.php:44
-#, php-format
-msgid "Reconnecting %d connections"
+#: ../../addon/tour/tour.php:104
+msgid "Adjust from which channels posts should be displayed."
msgstr ""
-#: ../../extend/addon/addon/diaspora_reconnect/diaspora_reconnect.php:63
-msgid "Diaspora Reconnect"
+#: ../../addon/tour/tour.php:105
+msgid "Only show posts from channels in the specified privacy group."
msgstr ""
-#: ../../extend/addon/addon/diaspora_reconnect/diaspora_reconnect.php:65
+#: ../../addon/tour/tour.php:109
msgid ""
-"Use this form to re-establish Diaspora connections which were initially made "
-"from a different hub."
-msgstr ""
-
-#: ../../extend/addon/addon/diaspora_reconnect/diaspora_reconnect.php:70
-msgid "Reconnect"
-msgstr ""
-
-#: ../../extend/addon/addon/mailtest/mailtest.php:19
-msgid "Send test email"
+"Easily find posts containing tags (keywords preceded by the \"#\" symbol)."
msgstr ""
-#: ../../extend/addon/addon/mailtest/mailtest.php:66
-msgid "Mail sent."
+#: ../../addon/tour/tour.php:110
+msgid "Easily find posts in given category."
msgstr ""
-#: ../../extend/addon/addon/mailtest/mailtest.php:68
-msgid "Sending of mail failed."
+#: ../../addon/tour/tour.php:111
+msgid "Easily find posts by date."
msgstr ""
-#: ../../extend/addon/addon/mailtest/mailtest.php:77
-msgid "Mail Test"
+#: ../../addon/tour/tour.php:112
+msgid ""
+"Suggested users who have volounteered to be shown as suggestions, and who we "
+"think you might find interesting."
msgstr ""
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:57
-msgid "Errors encountered deleting database table "
+#: ../../addon/tour/tour.php:113
+msgid "Here you see channels you have connected to."
msgstr ""
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:96
-msgid "Drop tables when uninstalling?"
+#: ../../addon/tour/tour.php:114
+msgid "Save your search so you can repeat it at a later date."
msgstr ""
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:96
+#: ../../addon/tour/tour.php:117
msgid ""
-"If checked, the Rendezvous database tables will be deleted when the plugin "
-"is uninstalled."
-msgstr ""
-
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:97
-msgid "Mapbox Access Token"
+"If you see this icon you can be sure that the sender is who it say it is. It "
+"is normal that it is not always possible to verify the sender, so the icon "
+"will be missing sometimes. There is usually no need to worry about that."
msgstr ""
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:97
+#: ../../addon/tour/tour.php:118
msgid ""
-"If you enter a Mapbox access token, it will be used to retrieve map tiles "
-"from Mapbox instead of the default OpenStreetMap tile server."
-msgstr ""
-
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:162
-msgid "Rendezvous"
+"Danger! It seems someone tried to forge a message! This message is not "
+"necessarily from who it says it is from!"
msgstr ""
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:167
+#: ../../addon/tour/tour.php:125
msgid ""
-"This identity has been deleted by another member due to inactivity. Please "
-"press the \"New identity\" button or refresh the page to register a new "
-"identity. You may use the same name."
+"Welcome to Hubzilla! Would you like to see a tour of the UI?</p> <p>You can "
+"pause it at any time and continue where you left off by reloading the page, "
+"or navigting to another page.</p><p>You can also advance by pressing the "
+"return key"
msgstr ""
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:168
-msgid "Welcome to Rendezvous!"
+#: ../../addon/sendzid/sendzid.php:25
+msgid "Extended Identity Sharing"
msgstr ""
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:169
+#: ../../addon/sendzid/sendzid.php:26
msgid ""
-"Enter your name to join this rendezvous. To begin sharing your location with "
-"the other members, tap the GPS control. When your location is discovered, a "
-"red dot will appear and others will be able to see you on the map."
+"Share your identity with all websites on the internet. When disabled, "
+"identity is only shared with sites in the matrix."
msgstr ""
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:171
-msgid "Let's meet here"
+#: ../../addon/tictac/tictac.php:21
+msgid "Three Dimensional Tic-Tac-Toe"
msgstr ""
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:174
-msgid "New marker"
+#: ../../addon/tictac/tictac.php:54
+msgid "3D Tic-Tac-Toe"
msgstr ""
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:175
-msgid "Edit marker"
+#: ../../addon/tictac/tictac.php:59
+msgid "New game"
msgstr ""
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:176
-msgid "New identity"
+#: ../../addon/tictac/tictac.php:60
+msgid "New game with handicap"
msgstr ""
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:177
-msgid "Delete marker"
+#: ../../addon/tictac/tictac.php:61
+msgid ""
+"Three dimensional tic-tac-toe is just like the traditional game except that "
+"it is played on multiple levels simultaneously. "
msgstr ""
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:178
-msgid "Delete member"
+#: ../../addon/tictac/tictac.php:62
+msgid ""
+"In this case there are three levels. You win by getting three in a row on "
+"any level, as well as up, down, and diagonally across the different levels."
msgstr ""
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:179
-msgid "Edit proximity alert"
+#: ../../addon/tictac/tictac.php:64
+msgid ""
+"The handicap game disables the center position on the middle level because "
+"the player claiming this square often has an unfair advantage."
msgstr ""
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:180
-msgid ""
-"A proximity alert will be issued when this member is within a certain radius "
-"of you.<br><br>Enter a radius in meters (0 to disable):"
+#: ../../addon/tictac/tictac.php:183
+msgid "You go first..."
msgstr ""
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:180
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:185
-msgid "distance"
+#: ../../addon/tictac/tictac.php:188
+msgid "I'm going first this time..."
msgstr ""
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:181
-msgid "Proximity alert distance (meters)"
+#: ../../addon/tictac/tictac.php:194
+msgid "You won!"
msgstr ""
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:182
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:184
-msgid ""
-"A proximity alert will be issued when you are within a certain radius of the "
-"marker location.<br><br>Enter a radius in meters (0 to disable):"
+#: ../../addon/tictac/tictac.php:200 ../../addon/tictac/tictac.php:225
+msgid "\"Cat\" game!"
msgstr ""
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:183
-msgid "Marker proximity alert"
+#: ../../addon/tictac/tictac.php:223
+msgid "I won!"
msgstr ""
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:186
-msgid "Reminder note"
+#: ../../addon/pageheader/pageheader.php:43
+msgid "Message to display on every page on this server"
msgstr ""
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:187
-msgid ""
-"Enter a note to be displayed when you are within the specified proximity..."
+#: ../../addon/pageheader/pageheader.php:48
+msgid "Pageheader Settings"
msgstr ""
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:199
-msgid "Add new rendezvous"
+#: ../../addon/pageheader/pageheader.php:64
+msgid "pageheader Settings saved."
msgstr ""
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:200
-msgid ""
-"Create a new rendezvous and share the access link with those you wish to "
-"invite to the group. Those who open the link become members of the "
-"rendezvous. They can view other member locations, add markers to the map, or "
-"share their own locations with the group."
+#: ../../addon/authchoose/authchoose.php:67
+msgid "Only authenticate automatically to sites of your friends"
msgstr ""
-#: ../../extend/addon/addon/firefox/firefox.php:23
-msgid "Install Firefox Sharing Tools"
+#: ../../addon/authchoose/authchoose.php:67
+msgid "By default you are automatically authenticated anywhere in the network"
msgstr ""
-#: ../../extend/addon/addon/firefox/firefox.php:34
-msgid "Share content from Firefox to $Projectname"
+#: ../../addon/authchoose/authchoose.php:71
+msgid "Authchoose Settings"
msgstr ""
-#: ../../extend/addon/addon/firefox/firefox.php:37
-msgid "Install Firefox Sharing Tools to this web browser"
+#: ../../addon/authchoose/authchoose.php:85
+msgid "Atuhchoose Settings updated."
msgstr ""
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:105
-msgid "Error retrieving wiki"
+#: ../../addon/moremoods/moremoods.php:19
+msgid "lonely"
msgstr ""
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:112
-msgid "Error creating zip file export folder"
+#: ../../addon/moremoods/moremoods.php:20
+msgid "drunk"
msgstr ""
-#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:130
-msgid "Error downloading wiki: "
+#: ../../addon/moremoods/moremoods.php:21
+msgid "horny"
msgstr ""
-#: ../../extend/addon/addon/gitwiki/gitwiki.php:76
-#: ../../include/widgets.php:970
-msgid "Wiki Pages"
+#: ../../addon/moremoods/moremoods.php:22
+msgid "stoned"
msgstr ""
-#: ../../extend/addon/addon/gitwiki/gitwiki.php:81
-#: ../../include/widgets.php:976
-msgid "Add new page"
+#: ../../addon/moremoods/moremoods.php:23
+msgid "fucked up"
msgstr ""
-#: ../../extend/addon/addon/gitwiki/gitwiki.php:82
-#: ../../include/widgets.php:977
-msgid "Page name"
+#: ../../addon/moremoods/moremoods.php:24
+msgid "clusterfucked"
msgstr ""
-#: ../../extend/addon/addon/gitwiki/gitwiki.php:95
-#: ../../include/widgets.php:927
-msgid "Wiki List"
+#: ../../addon/moremoods/moremoods.php:25
+msgid "crazy"
msgstr ""
-#: ../../extend/addon/addon/gnusoc/gnusoc.php:129
-msgid "Enable the GNU-Social protocol for this channel"
+#: ../../addon/moremoods/moremoods.php:26
+msgid "hurt"
msgstr ""
-#: ../../extend/addon/addon/opensearch/opensearch.php:26 ../../boot.php:1187
-#, php-format
-msgctxt "opensearch"
-msgid "Search %1$s (%2$s)"
+#: ../../addon/moremoods/moremoods.php:27
+msgid "sleepy"
msgstr ""
-#: ../../extend/addon/addon/opensearch/opensearch.php:28 ../../boot.php:1187
-msgctxt "opensearch"
-msgid "$Projectname"
+#: ../../addon/moremoods/moremoods.php:28
+msgid "grumpy"
msgstr ""
-#: ../../extend/addon/addon/opensearch/opensearch.php:43
-msgid "Search $Projectname"
+#: ../../addon/moremoods/moremoods.php:29
+msgid "high"
msgstr ""
-#: ../../include/dba/dba_driver.php:187
-#, php-format
-msgid "Cannot locate DNS info for database server '%s'"
+#: ../../addon/moremoods/moremoods.php:30
+msgid "semi-conscious"
msgstr ""
-#: ../../include/language.php:367 ../../include/text.php:1786
-msgid "default"
+#: ../../addon/moremoods/moremoods.php:31
+msgid "in love"
msgstr ""
-#: ../../include/language.php:380
-msgid "Select an alternate language"
+#: ../../addon/moremoods/moremoods.php:32
+msgid "in lust"
msgstr ""
-#: ../../include/account.php:35
-msgid "Not a valid email address"
+#: ../../addon/moremoods/moremoods.php:33
+msgid "naked"
msgstr ""
-#: ../../include/account.php:37
-msgid "Your email domain is not among those allowed on this site"
+#: ../../addon/moremoods/moremoods.php:34
+msgid "stinky"
msgstr ""
-#: ../../include/account.php:43
-msgid "Your email address is already registered at this site."
+#: ../../addon/moremoods/moremoods.php:35
+msgid "sweaty"
msgstr ""
-#: ../../include/account.php:75
-msgid "An invitation is required."
+#: ../../addon/moremoods/moremoods.php:36
+msgid "bleeding out"
msgstr ""
-#: ../../include/account.php:79
-msgid "Invitation could not be verified."
+#: ../../addon/moremoods/moremoods.php:37
+msgid "victorious"
msgstr ""
-#: ../../include/account.php:130
-msgid "Please enter the required information."
+#: ../../addon/moremoods/moremoods.php:38
+msgid "defeated"
msgstr ""
-#: ../../include/account.php:198
-msgid "Failed to store account information."
+#: ../../addon/moremoods/moremoods.php:39
+msgid "envious"
msgstr ""
-#: ../../include/account.php:263
-#, php-format
-msgid "Registration confirmation for %s"
+#: ../../addon/moremoods/moremoods.php:40
+msgid "jealous"
msgstr ""
-#: ../../include/account.php:330
-#, php-format
-msgid "Registration request at %s"
+#: ../../addon/xmpp/xmpp.php:31
+msgid "XMPP settings updated."
msgstr ""
-#: ../../include/account.php:352
-msgid "your registration password"
+#: ../../addon/xmpp/xmpp.php:53
+msgid "Enable Chat"
msgstr ""
-#: ../../include/account.php:358 ../../include/account.php:420
-#, php-format
-msgid "Registration details for %s"
+#: ../../addon/xmpp/xmpp.php:58
+msgid "Individual credentials"
msgstr ""
-#: ../../include/account.php:431
-msgid "Account approved."
+#: ../../addon/xmpp/xmpp.php:64
+msgid "Jabber BOSH server"
msgstr ""
-#: ../../include/account.php:471
-#, php-format
-msgid "Registration revoked for %s"
+#: ../../addon/xmpp/xmpp.php:69
+msgid "XMPP Settings"
msgstr ""
-#: ../../include/account.php:756 ../../include/account.php:758
-msgid "Click here to upgrade."
+#: ../../addon/xmpp/xmpp.php:92
+msgid "Jabber BOSH host"
msgstr ""
-#: ../../include/account.php:764
-msgid "This action exceeds the limits set by your subscription plan."
+#: ../../addon/xmpp/xmpp.php:93
+msgid "Use central userbase"
msgstr ""
-#: ../../include/account.php:769
-msgid "This action is not available under your subscription plan."
+#: ../../addon/xmpp/xmpp.php:93
+msgid ""
+"If enabled, members will automatically login to an ejabberd server that has "
+"to be installed on this machine with synchronized credentials via the "
+"\"auth_ejabberd.php\" script."
msgstr ""
-#: ../../include/acl_selectors.php:198
-msgid "Who can see this?"
+#: ../../addon/wholikesme/wholikesme.php:29
+msgid "Who likes me?"
msgstr ""
-#: ../../include/acl_selectors.php:199
-msgid "Custom selection"
+#: ../../addon/pumpio/pumpio.php:148
+msgid "You are now authenticated to pumpio."
msgstr ""
-#: ../../include/acl_selectors.php:200
-msgid ""
-"Select \"Show\" to allow viewing. \"Don't show\" lets you override and limit "
-"the scope of \"Show\"."
+#: ../../addon/pumpio/pumpio.php:149
+msgid "return to the featured settings page"
msgstr ""
-#: ../../include/acl_selectors.php:201
-msgid "Show"
+#: ../../addon/pumpio/pumpio.php:163
+msgid "Post to Pump.io"
msgstr ""
-#: ../../include/acl_selectors.php:202
-msgid "Don't show"
+#: ../../addon/pumpio/pumpio.php:198
+msgid "Pump.io servername"
msgstr ""
-#: ../../include/acl_selectors.php:235
-#, php-format
-msgid ""
-"Post permissions %s cannot be changed %s after a post is shared.</br />These "
-"permissions set who is allowed to view the post."
+#: ../../addon/pumpio/pumpio.php:198
+msgid "Without \"http://\" or \"https://\""
msgstr ""
-#: ../../include/taxonomy.php:188 ../../include/taxonomy.php:270
-#: ../../include/widgets.php:46 ../../include/widgets.php:469
-#: ../../include/contact_widgets.php:91
-msgid "Categories"
+#: ../../addon/pumpio/pumpio.php:202
+msgid "Pump.io username"
msgstr ""
-#: ../../include/taxonomy.php:228 ../../include/taxonomy.php:249
-msgid "Tags"
+#: ../../addon/pumpio/pumpio.php:202
+msgid "Without the servername"
msgstr ""
-#: ../../include/taxonomy.php:293
-msgid "Keywords"
+#: ../../addon/pumpio/pumpio.php:213
+msgid "You are not authenticated to pumpio"
msgstr ""
-#: ../../include/taxonomy.php:314
-msgid "have"
+#: ../../addon/pumpio/pumpio.php:215
+msgid "(Re-)Authenticate your pump.io connection"
msgstr ""
-#: ../../include/taxonomy.php:314
-msgid "has"
+#: ../../addon/pumpio/pumpio.php:219
+msgid "Enable pump.io Post Plugin"
msgstr ""
-#: ../../include/taxonomy.php:315
-msgid "want"
+#: ../../addon/pumpio/pumpio.php:223
+msgid "Post to pump.io by default"
msgstr ""
-#: ../../include/taxonomy.php:315
-msgid "wants"
+#: ../../addon/pumpio/pumpio.php:227
+msgid "Should posts be public"
msgstr ""
-#: ../../include/taxonomy.php:316
-msgid "likes"
+#: ../../addon/pumpio/pumpio.php:231
+msgid "Mirror all public posts"
msgstr ""
-#: ../../include/taxonomy.php:317
-msgid "dislikes"
+#: ../../addon/pumpio/pumpio.php:237
+msgid "Pump.io Post Settings"
msgstr ""
-#: ../../include/markdown.php:444
-msgid "Attachments:"
+#: ../../addon/pumpio/pumpio.php:266
+msgid "PumpIO Settings saved."
msgstr ""
-#: ../../include/markdown.php:539 ../../include/event.php:22
-#: ../../include/event.php:69
-msgid "l F d, Y \\@ g:i A"
+#: ../../addon/ldapauth/ldapauth.php:61
+msgid "An account has been created for you."
msgstr ""
-#: ../../include/markdown.php:541
-msgid "$Projectname event notification:"
+#: ../../addon/ldapauth/ldapauth.php:68
+msgid "Authentication successful but rejected: account creation is disabled."
msgstr ""
-#: ../../include/markdown.php:545 ../../include/event.php:30
-#: ../../include/event.php:73
-msgid "Starts:"
+#: ../../addon/opensearch/opensearch.php:26
+#, php-format
+msgctxt "opensearch"
+msgid "Search %1$s (%2$s)"
msgstr ""
-#: ../../include/markdown.php:553 ../../include/event.php:40
-#: ../../include/event.php:77
-msgid "Finishes:"
+#: ../../addon/opensearch/opensearch.php:28
+msgctxt "opensearch"
+msgid "$Projectname"
msgstr ""
-#: ../../include/datetime.php:147
-msgid "Birthday"
+#: ../../addon/opensearch/opensearch.php:43
+msgid "Search $Projectname"
msgstr ""
-#: ../../include/datetime.php:149
-msgid "Age: "
+#: ../../addon/redfiles/redfiles.php:119
+msgid "Redmatrix File Storage Import"
msgstr ""
-#: ../../include/datetime.php:151
-msgid "YYYY-MM-DD or MM-DD"
+#: ../../addon/redfiles/redfiles.php:120
+msgid "This will import all your Redmatrix cloud files to this channel."
msgstr ""
-#: ../../include/datetime.php:286 ../../boot.php:2578
-msgid "never"
+#: ../../addon/redfiles/redfilehelper.php:64
+msgid "file"
msgstr ""
-#: ../../include/datetime.php:292
-msgid "less than a second ago"
+#: ../../addon/hubwall/hubwall.php:19
+msgid "Send email to all members"
msgstr ""
-#: ../../include/datetime.php:310
+#: ../../addon/hubwall/hubwall.php:73
#, php-format
-msgctxt "e.g. 22 hours ago, 1 minute ago"
-msgid "%1$d %2$s ago"
+msgid "%1$d of %2$d messages sent."
msgstr ""
-#: ../../include/datetime.php:321
-msgctxt "relative_date"
-msgid "year"
-msgid_plural "years"
-msgstr[0] ""
-msgstr[1] ""
-
-#: ../../include/datetime.php:324
-msgctxt "relative_date"
-msgid "month"
-msgid_plural "months"
-msgstr[0] ""
-msgstr[1] ""
-
-#: ../../include/datetime.php:327
-msgctxt "relative_date"
-msgid "week"
-msgid_plural "weeks"
-msgstr[0] ""
-msgstr[1] ""
-
-#: ../../include/datetime.php:330
-msgctxt "relative_date"
-msgid "day"
-msgid_plural "days"
-msgstr[0] ""
-msgstr[1] ""
-
-#: ../../include/datetime.php:333
-msgctxt "relative_date"
-msgid "hour"
-msgid_plural "hours"
-msgstr[0] ""
-msgstr[1] ""
-
-#: ../../include/datetime.php:336
-msgctxt "relative_date"
-msgid "minute"
-msgid_plural "minutes"
-msgstr[0] ""
-msgstr[1] ""
-
-#: ../../include/datetime.php:339
-msgctxt "relative_date"
-msgid "second"
-msgid_plural "seconds"
-msgstr[0] ""
-msgstr[1] ""
+#: ../../addon/hubwall/hubwall.php:81
+msgid "Send email to all hub members."
+msgstr ""
-#: ../../include/datetime.php:576
-#, php-format
-msgid "%1$s's birthday"
+#: ../../addon/hubwall/hubwall.php:93
+msgid "Sender Email address"
msgstr ""
-#: ../../include/datetime.php:577
-#, php-format
-msgid "Happy Birthday %1$s"
+#: ../../addon/hubwall/hubwall.php:94
+msgid "Test mode (only send to hub administrator)"
msgstr ""
#: ../../include/selectors.php:30
@@ -11064,11 +11190,11 @@ msgstr ""
msgid "Hermaphrodite"
msgstr ""
-#: ../../include/selectors.php:49
+#: ../../include/selectors.php:49 ../../include/channel.php:1436
msgid "Neuter"
msgstr ""
-#: ../../include/selectors.php:49
+#: ../../include/selectors.php:49 ../../include/channel.php:1438
msgid "Non-specific"
msgstr ""
@@ -11248,751 +11374,679 @@ msgstr ""
msgid "Ask me"
msgstr ""
-#: ../../include/connections.php:127
-msgid "New window"
-msgstr ""
-
-#: ../../include/connections.php:128
-msgid "Open the selected location in a different window or browser tab"
-msgstr ""
-
-#: ../../include/connections.php:246
-#, php-format
-msgid "User '%s' deleted"
-msgstr ""
-
-#: ../../include/conversation.php:204
+#: ../../include/conversation.php:200
#, php-format
msgid "%1$s is now connected with %2$s"
msgstr ""
-#: ../../include/conversation.php:239
+#: ../../include/conversation.php:235
#, php-format
msgid "%1$s poked %2$s"
msgstr ""
-#: ../../include/conversation.php:243 ../../include/text.php:1090
-#: ../../include/text.php:1095
+#: ../../include/conversation.php:239 ../../include/text.php:1104
+#: ../../include/text.php:1109
msgid "poked"
msgstr ""
-#: ../../include/conversation.php:690
+#: ../../include/conversation.php:720
#, php-format
msgid "View %s's profile @ %s"
msgstr ""
-#: ../../include/conversation.php:710
+#: ../../include/conversation.php:740
msgid "Categories:"
msgstr ""
-#: ../../include/conversation.php:711
+#: ../../include/conversation.php:741
msgid "Filed under:"
msgstr ""
-#: ../../include/conversation.php:736
+#: ../../include/conversation.php:766
msgid "View in context"
msgstr ""
-#: ../../include/conversation.php:832
+#: ../../include/conversation.php:867
msgid "remove"
msgstr ""
-#: ../../include/conversation.php:836 ../../include/nav.php:292
-msgid "Loading..."
-msgstr ""
-
-#: ../../include/conversation.php:837
+#: ../../include/conversation.php:872
msgid "Delete Selected Items"
msgstr ""
-#: ../../include/conversation.php:930 ../../include/conversation.php:972
+#: ../../include/conversation.php:915
msgid "View Source"
msgstr ""
-#: ../../include/conversation.php:931 ../../include/conversation.php:982
+#: ../../include/conversation.php:925
msgid "Follow Thread"
msgstr ""
-#: ../../include/conversation.php:932 ../../include/conversation.php:991
+#: ../../include/conversation.php:934
msgid "Unfollow Thread"
msgstr ""
-#: ../../include/conversation.php:937 ../../include/conversation.php:1059
+#: ../../include/conversation.php:1025
msgid "Activity/Posts"
msgstr ""
-#: ../../include/conversation.php:939 ../../include/conversation.php:1079
+#: ../../include/conversation.php:1045
msgid "Edit Connection"
msgstr ""
-#: ../../include/conversation.php:940 ../../include/conversation.php:1089
+#: ../../include/conversation.php:1055
msgid "Message"
msgstr ""
-#: ../../include/conversation.php:1223
+#: ../../include/conversation.php:1189
#, php-format
msgid "%s likes this."
msgstr ""
-#: ../../include/conversation.php:1223
+#: ../../include/conversation.php:1189
#, php-format
msgid "%s doesn't like this."
msgstr ""
-#: ../../include/conversation.php:1227
+#: ../../include/conversation.php:1193
#, php-format
msgid "<span %1$s>%2$d people</span> like this."
msgid_plural "<span %1$s>%2$d people</span> like this."
msgstr[0] ""
msgstr[1] ""
-#: ../../include/conversation.php:1229
+#: ../../include/conversation.php:1195
#, php-format
msgid "<span %1$s>%2$d people</span> don't like this."
msgid_plural "<span %1$s>%2$d people</span> don't like this."
msgstr[0] ""
msgstr[1] ""
-#: ../../include/conversation.php:1235
+#: ../../include/conversation.php:1201
msgid "and"
msgstr ""
-#: ../../include/conversation.php:1238
+#: ../../include/conversation.php:1204
#, php-format
msgid ", and %d other people"
msgid_plural ", and %d other people"
msgstr[0] ""
msgstr[1] ""
-#: ../../include/conversation.php:1239
+#: ../../include/conversation.php:1205
#, php-format
msgid "%s like this."
msgstr ""
-#: ../../include/conversation.php:1239
+#: ../../include/conversation.php:1205
#, php-format
msgid "%s don't like this."
msgstr ""
-#: ../../include/conversation.php:1282
+#: ../../include/conversation.php:1248
msgid "Set your location"
msgstr ""
-#: ../../include/conversation.php:1283
+#: ../../include/conversation.php:1249
msgid "Clear browser location"
msgstr ""
-#: ../../include/conversation.php:1331
+#: ../../include/conversation.php:1297
msgid "Tag term:"
msgstr ""
-#: ../../include/conversation.php:1332
+#: ../../include/conversation.php:1298
msgid "Where are you right now?"
msgstr ""
-#: ../../include/conversation.php:1337
+#: ../../include/conversation.php:1303
msgid "Choose a different album..."
msgstr ""
-#: ../../include/conversation.php:1341
+#: ../../include/conversation.php:1307
msgid "Comments enabled"
msgstr ""
-#: ../../include/conversation.php:1342
+#: ../../include/conversation.php:1308
msgid "Comments disabled"
msgstr ""
-#: ../../include/conversation.php:1380
+#: ../../include/conversation.php:1355
msgid "Page link name"
msgstr ""
-#: ../../include/conversation.php:1383
+#: ../../include/conversation.php:1358
msgid "Post as"
msgstr ""
-#: ../../include/conversation.php:1397
+#: ../../include/conversation.php:1372
msgid "Toggle voting"
msgstr ""
-#: ../../include/conversation.php:1400
+#: ../../include/conversation.php:1375
msgid "Disable comments"
msgstr ""
-#: ../../include/conversation.php:1401
+#: ../../include/conversation.php:1376
msgid "Toggle comments"
msgstr ""
-#: ../../include/conversation.php:1409
+#: ../../include/conversation.php:1384
msgid "Categories (optional, comma-separated list)"
msgstr ""
-#: ../../include/conversation.php:1432
+#: ../../include/conversation.php:1407
msgid "Other networks and post services"
msgstr ""
-#: ../../include/conversation.php:1438
+#: ../../include/conversation.php:1413
msgid "Set publish date"
msgstr ""
-#: ../../include/conversation.php:1692
-msgid "Discover"
-msgstr ""
-
-#: ../../include/conversation.php:1695
-msgid "Imported public streams"
-msgstr ""
-
-#: ../../include/conversation.php:1700
+#: ../../include/conversation.php:1673
msgid "Commented Order"
msgstr ""
-#: ../../include/conversation.php:1703
+#: ../../include/conversation.php:1676
msgid "Sort by Comment Date"
msgstr ""
-#: ../../include/conversation.php:1707
+#: ../../include/conversation.php:1680
msgid "Posted Order"
msgstr ""
-#: ../../include/conversation.php:1710
+#: ../../include/conversation.php:1683
msgid "Sort by Post Date"
msgstr ""
-#: ../../include/conversation.php:1718
+#: ../../include/conversation.php:1691
msgid "Posts that mention or involve you"
msgstr ""
-#: ../../include/conversation.php:1727
+#: ../../include/conversation.php:1700
msgid "Activity Stream - by date"
msgstr ""
-#: ../../include/conversation.php:1733
+#: ../../include/conversation.php:1706
msgid "Starred"
msgstr ""
-#: ../../include/conversation.php:1736
+#: ../../include/conversation.php:1709
msgid "Favourite Posts"
msgstr ""
-#: ../../include/conversation.php:1743
+#: ../../include/conversation.php:1716
msgid "Spam"
msgstr ""
-#: ../../include/conversation.php:1746
+#: ../../include/conversation.php:1719
msgid "Posts flagged as SPAM"
msgstr ""
-#: ../../include/conversation.php:1818
+#: ../../include/conversation.php:1794 ../../include/nav.php:402
msgid "Status Messages and Posts"
msgstr ""
-#: ../../include/conversation.php:1830
+#: ../../include/conversation.php:1807 ../../include/nav.php:415
msgid "Profile Details"
msgstr ""
-#: ../../include/conversation.php:1839 ../../include/photos.php:515
+#: ../../include/conversation.php:1817 ../../include/nav.php:425
+#: ../../include/photos.php:600
msgid "Photo Albums"
msgstr ""
-#: ../../include/conversation.php:1846
+#: ../../include/conversation.php:1825 ../../include/nav.php:433
msgid "Files and Storage"
msgstr ""
-#: ../../include/conversation.php:1866 ../../include/conversation.php:1869
-#: ../../include/widgets.php:902
-msgid "Chatrooms"
-msgstr ""
-
-#: ../../include/conversation.php:1879
+#: ../../include/conversation.php:1862 ../../include/nav.php:468
msgid "Bookmarks"
msgstr ""
-#: ../../include/conversation.php:1882
+#: ../../include/conversation.php:1865 ../../include/nav.php:471
msgid "Saved Bookmarks"
msgstr ""
-#: ../../include/conversation.php:1892
+#: ../../include/conversation.php:1876 ../../include/nav.php:482
+msgid "View Cards"
+msgstr ""
+
+#: ../../include/conversation.php:1887 ../../include/nav.php:494
msgid "View Webpages"
msgstr ""
-#: ../../include/conversation.php:1958
+#: ../../include/conversation.php:1956
msgctxt "noun"
msgid "Attending"
msgid_plural "Attending"
msgstr[0] ""
msgstr[1] ""
-#: ../../include/conversation.php:1961
+#: ../../include/conversation.php:1959
msgctxt "noun"
msgid "Not Attending"
msgid_plural "Not Attending"
msgstr[0] ""
msgstr[1] ""
-#: ../../include/conversation.php:1964
+#: ../../include/conversation.php:1962
msgctxt "noun"
msgid "Undecided"
msgid_plural "Undecided"
msgstr[0] ""
msgstr[1] ""
-#: ../../include/conversation.php:1967
+#: ../../include/conversation.php:1965
msgctxt "noun"
msgid "Agree"
msgid_plural "Agrees"
msgstr[0] ""
msgstr[1] ""
-#: ../../include/conversation.php:1970
+#: ../../include/conversation.php:1968
msgctxt "noun"
msgid "Disagree"
msgid_plural "Disagrees"
msgstr[0] ""
msgstr[1] ""
-#: ../../include/conversation.php:1973
+#: ../../include/conversation.php:1971
msgctxt "noun"
msgid "Abstain"
msgid_plural "Abstains"
msgstr[0] ""
msgstr[1] ""
-#: ../../include/import.php:30
-msgid ""
-"Cannot create a duplicate channel identifier on this system. Import failed."
-msgstr ""
-
-#: ../../include/import.php:90
-msgid "Channel clone failed. Import failed."
-msgstr ""
-
-#: ../../include/import.php:100
-msgid "Cloned channel not found. Import failed."
-msgstr ""
-
-#: ../../include/import.php:1373
-msgid "Unable to import element \""
-msgstr ""
-
-#: ../../include/message.php:32
-msgid "Unable to determine sender."
+#: ../../include/dir_fns.php:141
+msgid "Directory Options"
msgstr ""
-#: ../../include/message.php:69
-msgid "No recipient provided."
+#: ../../include/dir_fns.php:143
+msgid "Safe Mode"
msgstr ""
-#: ../../include/message.php:74
-msgid "[no subject]"
+#: ../../include/dir_fns.php:144
+msgid "Public Forums Only"
msgstr ""
-#: ../../include/message.php:225
-msgid "Stored post could not be verified."
+#: ../../include/dir_fns.php:145
+msgid "This Website Only"
msgstr ""
-#: ../../include/security.php:117
-msgid "guest:"
+#: ../../include/bookmarks.php:34
+#, php-format
+msgid "%1$s's bookmarks"
msgstr ""
-#: ../../include/security.php:532
+#: ../../include/import.php:41
msgid ""
-"The form security token was not correct. This probably happened because the "
-"form has been opened for too long (>3 hours) before submitting it."
-msgstr ""
-
-#: ../../include/widgets.php:103
-msgid "System"
-msgstr ""
-
-#: ../../include/widgets.php:106
-msgid "New App"
-msgstr ""
-
-#: ../../include/widgets.php:107
-msgid "Edit Apps"
-msgstr ""
-
-#: ../../include/widgets.php:155
-msgid "Suggestions"
-msgstr ""
-
-#: ../../include/widgets.php:156
-msgid "See more..."
-msgstr ""
-
-#: ../../include/widgets.php:176
-#, php-format
-msgid "You have %1$.0f of %2$.0f allowed connections."
+"Cannot create a duplicate channel identifier on this system. Import failed."
msgstr ""
-#: ../../include/widgets.php:182
-msgid "Add New Connection"
+#: ../../include/import.php:105
+msgid "Cloned channel not found. Import failed."
msgstr ""
-#: ../../include/widgets.php:183
-msgid "Enter channel address"
+#: ../../include/text.php:478
+msgid "prev"
msgstr ""
-#: ../../include/widgets.php:184
-msgid "Examples: bob@example.com, https://example.com/barbara"
+#: ../../include/text.php:480
+msgid "first"
msgstr ""
-#: ../../include/widgets.php:200
-msgid "Notes"
+#: ../../include/text.php:509
+msgid "last"
msgstr ""
-#: ../../include/widgets.php:276
-msgid "Remove term"
+#: ../../include/text.php:512
+msgid "next"
msgstr ""
-#: ../../include/widgets.php:284 ../../include/features.php:301
-msgid "Saved Searches"
+#: ../../include/text.php:523
+msgid "older"
msgstr ""
-#: ../../include/widgets.php:285 ../../include/group.php:316
-msgid "add"
+#: ../../include/text.php:525
+msgid "newer"
msgstr ""
-#: ../../include/widgets.php:347 ../../include/contact_widgets.php:53
-#: ../../include/features.php:390
-msgid "Saved Folders"
+#: ../../include/text.php:947
+msgid "No connections"
msgstr ""
-#: ../../include/widgets.php:350 ../../include/widgets.php:472
-#: ../../include/contact_widgets.php:56 ../../include/contact_widgets.php:94
-msgid "Everything"
+#: ../../include/text.php:972
+#, php-format
+msgid "View all %s connections"
msgstr ""
-#: ../../include/widgets.php:391
-msgid "Archives"
+#: ../../include/text.php:1104 ../../include/text.php:1109
+msgid "poke"
msgstr ""
-#: ../../include/widgets.php:563
-msgid "Refresh"
+#: ../../include/text.php:1110
+msgid "ping"
msgstr ""
-#: ../../include/widgets.php:603
-msgid "Account settings"
+#: ../../include/text.php:1110
+msgid "pinged"
msgstr ""
-#: ../../include/widgets.php:609
-msgid "Channel settings"
+#: ../../include/text.php:1111
+msgid "prod"
msgstr ""
-#: ../../include/widgets.php:618
-msgid "Additional features"
+#: ../../include/text.php:1111
+msgid "prodded"
msgstr ""
-#: ../../include/widgets.php:625
-msgid "Feature/Addon settings"
+#: ../../include/text.php:1112
+msgid "slap"
msgstr ""
-#: ../../include/widgets.php:631
-msgid "Display settings"
+#: ../../include/text.php:1112
+msgid "slapped"
msgstr ""
-#: ../../include/widgets.php:638
-msgid "Manage locations"
+#: ../../include/text.php:1113
+msgid "finger"
msgstr ""
-#: ../../include/widgets.php:645
-msgid "Export channel"
+#: ../../include/text.php:1113
+msgid "fingered"
msgstr ""
-#: ../../include/widgets.php:651
-msgid "Connected apps"
+#: ../../include/text.php:1114
+msgid "rebuff"
msgstr ""
-#: ../../include/widgets.php:683
-msgid "Premium Channel Settings"
+#: ../../include/text.php:1114
+msgid "rebuffed"
msgstr ""
-#: ../../include/widgets.php:712
-msgid "Private Mail Menu"
+#: ../../include/text.php:1126
+msgid "happy"
msgstr ""
-#: ../../include/widgets.php:714
-msgid "Combined View"
+#: ../../include/text.php:1127
+msgid "sad"
msgstr ""
-#: ../../include/widgets.php:719 ../../include/nav.php:213
-msgid "Inbox"
+#: ../../include/text.php:1128
+msgid "mellow"
msgstr ""
-#: ../../include/widgets.php:724 ../../include/nav.php:214
-msgid "Outbox"
+#: ../../include/text.php:1129
+msgid "tired"
msgstr ""
-#: ../../include/widgets.php:729 ../../include/nav.php:215
-msgid "New Message"
+#: ../../include/text.php:1130
+msgid "perky"
msgstr ""
-#: ../../include/widgets.php:746 ../../include/widgets.php:758
-msgid "Conversations"
+#: ../../include/text.php:1131
+msgid "angry"
msgstr ""
-#: ../../include/widgets.php:750
-msgid "Received Messages"
+#: ../../include/text.php:1132
+msgid "stupefied"
msgstr ""
-#: ../../include/widgets.php:754
-msgid "Sent Messages"
+#: ../../include/text.php:1133
+msgid "puzzled"
msgstr ""
-#: ../../include/widgets.php:768
-msgid "No messages."
+#: ../../include/text.php:1134
+msgid "interested"
msgstr ""
-#: ../../include/widgets.php:786
-msgid "Delete conversation"
+#: ../../include/text.php:1135
+msgid "bitter"
msgstr ""
-#: ../../include/widgets.php:812
-msgid "Events Tools"
+#: ../../include/text.php:1136
+msgid "cheerful"
msgstr ""
-#: ../../include/widgets.php:813
-msgid "Export Calendar"
+#: ../../include/text.php:1137
+msgid "alive"
msgstr ""
-#: ../../include/widgets.php:814
-msgid "Import Calendar"
+#: ../../include/text.php:1138
+msgid "annoyed"
msgstr ""
-#: ../../include/widgets.php:906
-msgid "Overview"
+#: ../../include/text.php:1139
+msgid "anxious"
msgstr ""
-#: ../../include/widgets.php:913
-msgid "Chat Members"
+#: ../../include/text.php:1140
+msgid "cranky"
msgstr ""
-#: ../../include/widgets.php:991
-msgctxt "wiki_history"
-msgid "Message"
+#: ../../include/text.php:1141
+msgid "disturbed"
msgstr ""
-#: ../../include/widgets.php:1013
-msgid "Bookmarked Chatrooms"
+#: ../../include/text.php:1142
+msgid "frustrated"
msgstr ""
-#: ../../include/widgets.php:1044
-msgid "Suggested Chatrooms"
+#: ../../include/text.php:1143
+msgid "depressed"
msgstr ""
-#: ../../include/widgets.php:1189 ../../include/widgets.php:1301
-msgid "photo/image"
+#: ../../include/text.php:1144
+msgid "motivated"
msgstr ""
-#: ../../include/widgets.php:1244
-msgid "Click to show more"
+#: ../../include/text.php:1145
+msgid "relaxed"
msgstr ""
-#: ../../include/widgets.php:1395
-msgid "Rating Tools"
+#: ../../include/text.php:1146
+msgid "surprised"
msgstr ""
-#: ../../include/widgets.php:1399 ../../include/widgets.php:1401
-msgid "Rate Me"
+#: ../../include/text.php:1320 ../../include/js_strings.php:70
+msgid "Monday"
msgstr ""
-#: ../../include/widgets.php:1404
-msgid "View Ratings"
+#: ../../include/text.php:1320 ../../include/js_strings.php:71
+msgid "Tuesday"
msgstr ""
-#: ../../include/widgets.php:1497
-msgid "Forums"
+#: ../../include/text.php:1320 ../../include/js_strings.php:72
+msgid "Wednesday"
msgstr ""
-#: ../../include/widgets.php:1526
-msgid "Tasks"
+#: ../../include/text.php:1320 ../../include/js_strings.php:73
+msgid "Thursday"
msgstr ""
-#: ../../include/widgets.php:1592 ../../include/widgets.php:1630
-msgid "Member registrations waiting for confirmation"
+#: ../../include/text.php:1320 ../../include/js_strings.php:74
+msgid "Friday"
msgstr ""
-#: ../../include/widgets.php:1598
-msgid "Inspect queue"
+#: ../../include/text.php:1320 ../../include/js_strings.php:75
+msgid "Saturday"
msgstr ""
-#: ../../include/widgets.php:1600
-msgid "DB updates"
+#: ../../include/text.php:1320 ../../include/js_strings.php:69
+msgid "Sunday"
msgstr ""
-#: ../../include/widgets.php:1625 ../../include/nav.php:233
-msgid "Admin"
+#: ../../include/text.php:1324 ../../include/js_strings.php:45
+msgid "January"
msgstr ""
-#: ../../include/widgets.php:1626
-msgid "Plugin Features"
+#: ../../include/text.php:1324 ../../include/js_strings.php:46
+msgid "February"
msgstr ""
-#: ../../include/zot.php:652
-msgid "Invalid data packet"
+#: ../../include/text.php:1324 ../../include/js_strings.php:47
+msgid "March"
msgstr ""
-#: ../../include/zot.php:668
-msgid "Unable to verify channel signature"
+#: ../../include/text.php:1324 ../../include/js_strings.php:48
+msgid "April"
msgstr ""
-#: ../../include/zot.php:2319
-#, php-format
-msgid "Unable to verify site signature for %s"
+#: ../../include/text.php:1324
+msgid "May"
msgstr ""
-#: ../../include/zot.php:3725
-msgid "invalid target signature"
+#: ../../include/text.php:1324 ../../include/js_strings.php:50
+msgid "June"
msgstr ""
-#: ../../include/channel.php:33
-msgid "Unable to obtain identity information from database"
+#: ../../include/text.php:1324 ../../include/js_strings.php:51
+msgid "July"
msgstr ""
-#: ../../include/channel.php:67
-msgid "Empty name"
+#: ../../include/text.php:1324 ../../include/js_strings.php:52
+msgid "August"
msgstr ""
-#: ../../include/channel.php:70
-msgid "Name too long"
+#: ../../include/text.php:1324 ../../include/js_strings.php:53
+msgid "September"
msgstr ""
-#: ../../include/channel.php:181
-msgid "No account identifier"
+#: ../../include/text.php:1324 ../../include/js_strings.php:54
+msgid "October"
msgstr ""
-#: ../../include/channel.php:193
-msgid "Nickname is required."
+#: ../../include/text.php:1324 ../../include/js_strings.php:55
+msgid "November"
msgstr ""
-#: ../../include/channel.php:207
-msgid "Reserved nickname. Please choose another."
+#: ../../include/text.php:1324 ../../include/js_strings.php:56
+msgid "December"
msgstr ""
-#: ../../include/channel.php:212
-msgid ""
-"Nickname has unsupported characters or is already being used on this site."
+#: ../../include/text.php:1388 ../../include/text.php:1392
+msgid "Unknown Attachment"
msgstr ""
-#: ../../include/channel.php:272
-msgid "Unable to retrieve created identity"
+#: ../../include/text.php:1394 ../../include/feedutils.php:780
+msgid "unknown"
msgstr ""
-#: ../../include/channel.php:344
-msgid "Default Profile"
+#: ../../include/text.php:1430
+msgid "remove category"
msgstr ""
-#: ../../include/channel.php:1045
-msgid "Create New Profile"
+#: ../../include/text.php:1504
+msgid "remove from file"
msgstr ""
-#: ../../include/channel.php:1065
-msgid "Visible to everybody"
+#: ../../include/text.php:1623 ../../include/message.php:12
+msgid "Download binary/encrypted content"
msgstr ""
-#: ../../include/channel.php:1138 ../../include/channel.php:1257
-msgid "Gender:"
+#: ../../include/text.php:1782 ../../include/language.php:367
+msgid "default"
msgstr ""
-#: ../../include/channel.php:1140 ../../include/channel.php:1312
-msgid "Homepage:"
+#: ../../include/text.php:1790
+msgid "Page layout"
msgstr ""
-#: ../../include/channel.php:1141
-msgid "Online Now"
+#: ../../include/text.php:1790
+msgid "You can create your own with the layouts tool"
msgstr ""
-#: ../../include/channel.php:1262
-msgid "Like this channel"
+#: ../../include/text.php:1801
+msgid "HTML"
msgstr ""
-#: ../../include/channel.php:1286
-msgid "j F, Y"
+#: ../../include/text.php:1804
+msgid "Comanche Layout"
msgstr ""
-#: ../../include/channel.php:1287
-msgid "j F"
+#: ../../include/text.php:1809
+msgid "PHP"
msgstr ""
-#: ../../include/channel.php:1294
-msgid "Birthday:"
+#: ../../include/text.php:1818
+msgid "Page content type"
msgstr ""
-#: ../../include/channel.php:1307
-#, php-format
-msgid "for %1$d %2$s"
+#: ../../include/text.php:1951
+msgid "activity"
msgstr ""
-#: ../../include/channel.php:1310
-msgid "Sexual Preference:"
+#: ../../include/text.php:2014
+msgid "a-z, 0-9, -, and _ only"
msgstr ""
-#: ../../include/channel.php:1316
-msgid "Tags:"
+#: ../../include/text.php:2285
+msgid "Design Tools"
msgstr ""
-#: ../../include/channel.php:1318
-msgid "Political Views:"
+#: ../../include/text.php:2291
+msgid "Pages"
msgstr ""
-#: ../../include/channel.php:1320
-msgid "Religion:"
+#: ../../include/text.php:2313
+msgid "Import website..."
msgstr ""
-#: ../../include/channel.php:1324
-msgid "Hobbies/Interests:"
+#: ../../include/text.php:2314
+msgid "Select folder to import"
msgstr ""
-#: ../../include/channel.php:1326
-msgid "Likes:"
+#: ../../include/text.php:2315
+msgid "Import from a zipped folder:"
msgstr ""
-#: ../../include/channel.php:1328
-msgid "Dislikes:"
+#: ../../include/text.php:2316
+msgid "Import from cloud files:"
msgstr ""
-#: ../../include/channel.php:1330
-msgid "Contact information and Social Networks:"
+#: ../../include/text.php:2317
+msgid "/cloud/channel/path/to/folder"
msgstr ""
-#: ../../include/channel.php:1332
-msgid "My other channels:"
+#: ../../include/text.php:2318
+msgid "Enter path to website files"
msgstr ""
-#: ../../include/channel.php:1334
-msgid "Musical interests:"
+#: ../../include/text.php:2319
+msgid "Select folder"
msgstr ""
-#: ../../include/channel.php:1336
-msgid "Books, literature:"
+#: ../../include/text.php:2320
+msgid "Export website..."
msgstr ""
-#: ../../include/channel.php:1338
-msgid "Television:"
+#: ../../include/text.php:2321
+msgid "Export to a zip file"
msgstr ""
-#: ../../include/channel.php:1340
-msgid "Film/dance/culture/entertainment:"
+#: ../../include/text.php:2322
+msgid "website.zip"
msgstr ""
-#: ../../include/channel.php:1342
-msgid "Love/Romance:"
+#: ../../include/text.php:2323
+msgid "Enter a name for the zip file."
msgstr ""
-#: ../../include/channel.php:1344
-msgid "Work/employment:"
+#: ../../include/text.php:2324
+msgid "Export to cloud files"
msgstr ""
-#: ../../include/channel.php:1346
-msgid "School/education:"
+#: ../../include/text.php:2325
+msgid "/path/to/export/folder"
msgstr ""
-#: ../../include/channel.php:1369
-msgid "Like this thing"
+#: ../../include/text.php:2326
+msgid "Enter a path to a cloud files destination."
msgstr ""
-#: ../../include/page_widgets.php:7
-msgid "New Page"
+#: ../../include/text.php:2327
+msgid "Specify folder"
msgstr ""
#: ../../include/contact_widgets.php:11
@@ -12030,15 +12084,50 @@ msgstr ""
msgid "Advanced example: name=fred and country=iceland"
msgstr ""
-#: ../../include/contact_widgets.php:122
+#: ../../include/contact_widgets.php:166
+msgid "Common Connections"
+msgstr ""
+
+#: ../../include/contact_widgets.php:171
#, php-format
-msgid "%d connection in common"
-msgid_plural "%d connections in common"
-msgstr[0] ""
-msgstr[1] ""
+msgid "View all %d common connections"
+msgstr ""
+
+#: ../../include/markdown.php:139 ../../include/bbcode.php:337
+#, php-format
+msgid "%1$s wrote the following %2$s %3$s"
+msgstr ""
+
+#: ../../include/follow.php:37
+msgid "Channel is blocked on this site."
+msgstr ""
+
+#: ../../include/follow.php:42
+msgid "Channel location missing."
+msgstr ""
+
+#: ../../include/follow.php:84
+msgid "Response from remote channel was incomplete."
+msgstr ""
+
+#: ../../include/follow.php:101
+msgid "Channel was deleted and no longer exists."
+msgstr ""
+
+#: ../../include/follow.php:156
+msgid "Remote channel or protocol unavailable."
+msgstr ""
+
+#: ../../include/follow.php:179
+msgid "Channel discovery failed."
+msgstr ""
-#: ../../include/contact_widgets.php:127
-msgid "show more"
+#: ../../include/follow.php:191
+msgid "Protocol disabled."
+msgstr ""
+
+#: ../../include/follow.php:202
+msgid "Cannot connect to yourself."
msgstr ""
#: ../../include/js_strings.php:5
@@ -12181,55 +12270,11 @@ msgstr ""
msgid "timeago.numbers"
msgstr ""
-#: ../../include/js_strings.php:45 ../../include/text.php:1323
-msgid "January"
-msgstr ""
-
-#: ../../include/js_strings.php:46 ../../include/text.php:1323
-msgid "February"
-msgstr ""
-
-#: ../../include/js_strings.php:47 ../../include/text.php:1323
-msgid "March"
-msgstr ""
-
-#: ../../include/js_strings.php:48 ../../include/text.php:1323
-msgid "April"
-msgstr ""
-
#: ../../include/js_strings.php:49
msgctxt "long"
msgid "May"
msgstr ""
-#: ../../include/js_strings.php:50 ../../include/text.php:1323
-msgid "June"
-msgstr ""
-
-#: ../../include/js_strings.php:51 ../../include/text.php:1323
-msgid "July"
-msgstr ""
-
-#: ../../include/js_strings.php:52 ../../include/text.php:1323
-msgid "August"
-msgstr ""
-
-#: ../../include/js_strings.php:53 ../../include/text.php:1323
-msgid "September"
-msgstr ""
-
-#: ../../include/js_strings.php:54 ../../include/text.php:1323
-msgid "October"
-msgstr ""
-
-#: ../../include/js_strings.php:55 ../../include/text.php:1323
-msgid "November"
-msgstr ""
-
-#: ../../include/js_strings.php:56 ../../include/text.php:1323
-msgid "December"
-msgstr ""
-
#: ../../include/js_strings.php:57
msgid "Jan"
msgstr ""
@@ -12279,34 +12324,6 @@ msgstr ""
msgid "Dec"
msgstr ""
-#: ../../include/js_strings.php:69 ../../include/text.php:1319
-msgid "Sunday"
-msgstr ""
-
-#: ../../include/js_strings.php:70 ../../include/text.php:1319
-msgid "Monday"
-msgstr ""
-
-#: ../../include/js_strings.php:71 ../../include/text.php:1319
-msgid "Tuesday"
-msgstr ""
-
-#: ../../include/js_strings.php:72 ../../include/text.php:1319
-msgid "Wednesday"
-msgstr ""
-
-#: ../../include/js_strings.php:73 ../../include/text.php:1319
-msgid "Thursday"
-msgstr ""
-
-#: ../../include/js_strings.php:74 ../../include/text.php:1319
-msgid "Friday"
-msgstr ""
-
-#: ../../include/js_strings.php:75 ../../include/text.php:1319
-msgid "Saturday"
-msgstr ""
-
#: ../../include/js_strings.php:76
msgid "Sun"
msgstr ""
@@ -12360,1356 +12377,1237 @@ msgctxt "calendar"
msgid "All day"
msgstr ""
-#: ../../include/dir_fns.php:141
-msgid "Directory Options"
+#: ../../include/message.php:40
+msgid "Unable to determine sender."
msgstr ""
-#: ../../include/dir_fns.php:143
-msgid "Safe Mode"
+#: ../../include/message.php:79
+msgid "No recipient provided."
msgstr ""
-#: ../../include/dir_fns.php:144
-msgid "Public Forums Only"
+#: ../../include/message.php:84
+msgid "[no subject]"
msgstr ""
-#: ../../include/dir_fns.php:145
-msgid "This Website Only"
+#: ../../include/message.php:214
+msgid "Stored post could not be verified."
+msgstr ""
+
+#: ../../include/activities.php:41
+msgid " and "
msgstr ""
-#: ../../include/attach.php:248 ../../include/attach.php:336
+#: ../../include/activities.php:49
+msgid "public profile"
+msgstr ""
+
+#: ../../include/activities.php:58
+#, php-format
+msgid "%1$s changed %2$s to &ldquo;%3$s&rdquo;"
+msgstr ""
+
+#: ../../include/activities.php:59
+#, php-format
+msgid "Visit %1$s's %2$s"
+msgstr ""
+
+#: ../../include/activities.php:62
+#, php-format
+msgid "%1$s has an updated %2$s, changing %3$s."
+msgstr ""
+
+#: ../../include/attach.php:250 ../../include/attach.php:339
msgid "Item was not found."
msgstr ""
-#: ../../include/attach.php:497
+#: ../../include/attach.php:505
msgid "No source file."
msgstr ""
-#: ../../include/attach.php:519
+#: ../../include/attach.php:527
msgid "Cannot locate file to replace"
msgstr ""
-#: ../../include/attach.php:537
+#: ../../include/attach.php:545
msgid "Cannot locate file to revise/update"
msgstr ""
-#: ../../include/attach.php:668
+#: ../../include/attach.php:680
#, php-format
msgid "File exceeds size limit of %d"
msgstr ""
-#: ../../include/attach.php:682
+#: ../../include/attach.php:694
#, php-format
msgid "You have reached your limit of %1$.0f Mbytes attachment storage."
msgstr ""
-#: ../../include/attach.php:852
+#: ../../include/attach.php:864
msgid "File upload failed. Possible system limit or action terminated."
msgstr ""
-#: ../../include/attach.php:865
+#: ../../include/attach.php:877
msgid "Stored file could not be verified. Upload failed."
msgstr ""
-#: ../../include/attach.php:920 ../../include/attach.php:936
+#: ../../include/attach.php:938 ../../include/attach.php:954
msgid "Path not available."
msgstr ""
-#: ../../include/attach.php:982 ../../include/attach.php:1140
+#: ../../include/attach.php:1003 ../../include/attach.php:1168
msgid "Empty pathname"
msgstr ""
-#: ../../include/attach.php:1008
+#: ../../include/attach.php:1029
msgid "duplicate filename or path"
msgstr ""
-#: ../../include/attach.php:1030
+#: ../../include/attach.php:1054
msgid "Path not found."
msgstr ""
-#: ../../include/attach.php:1094
+#: ../../include/attach.php:1122
msgid "mkdir failed."
msgstr ""
-#: ../../include/attach.php:1098
+#: ../../include/attach.php:1126
msgid "database storage failed."
msgstr ""
-#: ../../include/attach.php:1146
+#: ../../include/attach.php:1174
msgid "Empty path"
msgstr ""
-#: ../../include/network.php:733
-msgid "view full size"
-msgstr ""
-
-#: ../../include/network.php:1988
-msgid "No Subject"
-msgstr ""
-
-#: ../../include/network.php:2244
-msgid "OStatus"
-msgstr ""
-
-#: ../../include/network.php:2245
-msgid "GNU-Social"
-msgstr ""
-
-#: ../../include/network.php:2246
-msgid "RSS/Atom"
-msgstr ""
-
-#: ../../include/network.php:2249
-msgid "Facebook"
-msgstr ""
-
-#: ../../include/network.php:2250
-msgid "Zot"
-msgstr ""
-
-#: ../../include/network.php:2251
-msgid "LinkedIn"
-msgstr ""
-
-#: ../../include/network.php:2252
-msgid "XMPP/IM"
-msgstr ""
-
-#: ../../include/network.php:2253
-msgid "MySpace"
-msgstr ""
-
-#: ../../include/oembed.php:308
-msgid " by "
-msgstr ""
-
-#: ../../include/oembed.php:309
-msgid " on "
-msgstr ""
-
-#: ../../include/oembed.php:338
-msgid "Embedded content"
+#: ../../include/security.php:531
+msgid ""
+"The form security token was not correct. This probably happened because the "
+"form has been opened for too long (>3 hours) before submitting it."
msgstr ""
-#: ../../include/oembed.php:347
-msgid "Embedding disabled"
+#: ../../include/items.php:857 ../../include/items.php:909
+msgid "(Unknown)"
msgstr ""
-#: ../../include/photos.php:115
-#, php-format
-msgid "Image exceeds website size limit of %lu bytes"
+#: ../../include/items.php:1093
+msgid "Visible to anybody on the internet."
msgstr ""
-#: ../../include/photos.php:122
-msgid "Image file is empty."
+#: ../../include/items.php:1095
+msgid "Visible to you only."
msgstr ""
-#: ../../include/photos.php:260
-msgid "Photo storage failed."
+#: ../../include/items.php:1097
+msgid "Visible to anybody in this network."
msgstr ""
-#: ../../include/photos.php:300
-msgid "a new photo"
+#: ../../include/items.php:1099
+msgid "Visible to anybody authenticated."
msgstr ""
-#: ../../include/photos.php:304
+#: ../../include/items.php:1101
#, php-format
-msgctxt "photo_upload"
-msgid "%1$s posted %2$s to %3$s"
-msgstr ""
-
-#: ../../include/photos.php:519
-msgid "Upload New Photos"
-msgstr ""
-
-#: ../../include/text.php:460
-msgid "prev"
-msgstr ""
-
-#: ../../include/text.php:462
-msgid "first"
-msgstr ""
-
-#: ../../include/text.php:491
-msgid "last"
+msgid "Visible to anybody on %s."
msgstr ""
-#: ../../include/text.php:494
-msgid "next"
+#: ../../include/items.php:1103
+msgid "Visible to all connections."
msgstr ""
-#: ../../include/text.php:505
-msgid "older"
+#: ../../include/items.php:1105
+msgid "Visible to approved connections."
msgstr ""
-#: ../../include/text.php:507
-msgid "newer"
+#: ../../include/items.php:1107
+msgid "Visible to specific connections."
msgstr ""
-#: ../../include/text.php:920
-msgid "No connections"
+#: ../../include/items.php:3957
+msgid "Privacy group is empty."
msgstr ""
-#: ../../include/text.php:945
+#: ../../include/items.php:3964
#, php-format
-msgid "View all %s connections"
-msgstr ""
-
-#: ../../include/text.php:1090 ../../include/text.php:1095
-msgid "poke"
-msgstr ""
-
-#: ../../include/text.php:1096
-msgid "ping"
-msgstr ""
-
-#: ../../include/text.php:1096
-msgid "pinged"
-msgstr ""
-
-#: ../../include/text.php:1097
-msgid "prod"
-msgstr ""
-
-#: ../../include/text.php:1097
-msgid "prodded"
-msgstr ""
-
-#: ../../include/text.php:1098
-msgid "slap"
-msgstr ""
-
-#: ../../include/text.php:1098
-msgid "slapped"
-msgstr ""
-
-#: ../../include/text.php:1099
-msgid "finger"
-msgstr ""
-
-#: ../../include/text.php:1099
-msgid "fingered"
-msgstr ""
-
-#: ../../include/text.php:1100
-msgid "rebuff"
-msgstr ""
-
-#: ../../include/text.php:1100
-msgid "rebuffed"
-msgstr ""
-
-#: ../../include/text.php:1112
-msgid "happy"
-msgstr ""
-
-#: ../../include/text.php:1113
-msgid "sad"
-msgstr ""
-
-#: ../../include/text.php:1114
-msgid "mellow"
-msgstr ""
-
-#: ../../include/text.php:1115
-msgid "tired"
-msgstr ""
-
-#: ../../include/text.php:1116
-msgid "perky"
-msgstr ""
-
-#: ../../include/text.php:1117
-msgid "angry"
-msgstr ""
-
-#: ../../include/text.php:1118
-msgid "stupefied"
-msgstr ""
-
-#: ../../include/text.php:1119
-msgid "puzzled"
-msgstr ""
-
-#: ../../include/text.php:1120
-msgid "interested"
-msgstr ""
-
-#: ../../include/text.php:1121
-msgid "bitter"
-msgstr ""
-
-#: ../../include/text.php:1122
-msgid "cheerful"
-msgstr ""
-
-#: ../../include/text.php:1123
-msgid "alive"
-msgstr ""
-
-#: ../../include/text.php:1124
-msgid "annoyed"
-msgstr ""
-
-#: ../../include/text.php:1125
-msgid "anxious"
-msgstr ""
-
-#: ../../include/text.php:1126
-msgid "cranky"
-msgstr ""
-
-#: ../../include/text.php:1127
-msgid "disturbed"
-msgstr ""
-
-#: ../../include/text.php:1128
-msgid "frustrated"
-msgstr ""
-
-#: ../../include/text.php:1129
-msgid "depressed"
-msgstr ""
-
-#: ../../include/text.php:1130
-msgid "motivated"
-msgstr ""
-
-#: ../../include/text.php:1131
-msgid "relaxed"
-msgstr ""
-
-#: ../../include/text.php:1132
-msgid "surprised"
-msgstr ""
-
-#: ../../include/text.php:1323
-msgid "May"
-msgstr ""
-
-#: ../../include/text.php:1400 ../../include/text.php:1404
-msgid "Unknown Attachment"
-msgstr ""
-
-#: ../../include/text.php:1406
-msgid "unknown"
+msgid "Privacy group: %s"
msgstr ""
-#: ../../include/text.php:1442
-msgid "remove category"
+#: ../../include/items.php:3976
+msgid "Connection not found."
msgstr ""
-#: ../../include/text.php:1519
-msgid "remove from file"
+#: ../../include/items.php:4327
+msgid "profile photo"
msgstr ""
-#: ../../include/text.php:1794
-msgid "Page layout"
+#: ../../include/items.php:4520
+#, php-format
+msgid "[Edited %s]"
msgstr ""
-#: ../../include/text.php:1794
-msgid "You can create your own with the layouts tool"
+#: ../../include/items.php:4520
+msgctxt "edit_activity"
+msgid "Post"
msgstr ""
-#: ../../include/text.php:1836
-msgid "Page content type"
+#: ../../include/items.php:4520
+msgctxt "edit_activity"
+msgid "Comment"
msgstr ""
-#: ../../include/text.php:1969
-msgid "activity"
+#: ../../include/channel.php:34
+msgid "Unable to obtain identity information from database"
msgstr ""
-#: ../../include/text.php:2283
-msgid "Design Tools"
+#: ../../include/channel.php:69
+msgid "Empty name"
msgstr ""
-#: ../../include/text.php:2289
-msgid "Pages"
+#: ../../include/channel.php:72
+msgid "Name too long"
msgstr ""
-#: ../../include/text.php:2311
-msgid "Import website..."
+#: ../../include/channel.php:183
+msgid "No account identifier"
msgstr ""
-#: ../../include/text.php:2312
-msgid "Select folder to import"
+#: ../../include/channel.php:195
+msgid "Nickname is required."
msgstr ""
-#: ../../include/text.php:2313
-msgid "Import from a zipped folder:"
+#: ../../include/channel.php:273
+msgid "Unable to retrieve created identity"
msgstr ""
-#: ../../include/text.php:2314
-msgid "Import from cloud files:"
+#: ../../include/channel.php:359
+msgid "Default Profile"
msgstr ""
-#: ../../include/text.php:2315
-msgid "/cloud/channel/path/to/folder"
+#: ../../include/channel.php:512 ../../include/channel.php:601
+msgid "Unable to retrieve modified identity"
msgstr ""
-#: ../../include/text.php:2316
-msgid "Enter path to website files"
+#: ../../include/channel.php:1263
+msgid "Create New Profile"
msgstr ""
-#: ../../include/text.php:2317
-msgid "Select folder"
+#: ../../include/channel.php:1283
+msgid "Visible to everybody"
msgstr ""
-#: ../../include/text.php:2318
-msgid "Export website..."
+#: ../../include/channel.php:1356 ../../include/channel.php:1475
+msgid "Gender:"
msgstr ""
-#: ../../include/text.php:2319
-msgid "Export to a zip file"
+#: ../../include/channel.php:1358 ../../include/channel.php:1530
+msgid "Homepage:"
msgstr ""
-#: ../../include/text.php:2320
-msgid "website.zip"
+#: ../../include/channel.php:1359
+msgid "Online Now"
msgstr ""
-#: ../../include/text.php:2321
-msgid "Enter a name for the zip file."
+#: ../../include/channel.php:1434
+msgid "Trans"
msgstr ""
-#: ../../include/text.php:2322
-msgid "Export to cloud files"
+#: ../../include/channel.php:1480
+msgid "Like this channel"
msgstr ""
-#: ../../include/text.php:2323
-msgid "/path/to/export/folder"
+#: ../../include/channel.php:1504
+msgid "j F, Y"
msgstr ""
-#: ../../include/text.php:2324
-msgid "Enter a path to a cloud files destination."
+#: ../../include/channel.php:1505
+msgid "j F"
msgstr ""
-#: ../../include/text.php:2325
-msgid "Specify folder"
+#: ../../include/channel.php:1512
+msgid "Birthday:"
msgstr ""
-#: ../../include/nav.php:88
-msgid "Remote authentication"
+#: ../../include/channel.php:1525
+#, php-format
+msgid "for %1$d %2$s"
msgstr ""
-#: ../../include/nav.php:88
-msgid "Click to authenticate to your home hub"
+#: ../../include/channel.php:1528
+msgid "Sexual Preference:"
msgstr ""
-#: ../../include/nav.php:99 ../../include/nav.php:140 ../../boot.php:1731
-msgid "Logout"
+#: ../../include/channel.php:1534
+msgid "Tags:"
msgstr ""
-#: ../../include/nav.php:99 ../../include/nav.php:140
-msgid "End this session"
+#: ../../include/channel.php:1536
+msgid "Political Views:"
msgstr ""
-#: ../../include/nav.php:103
-msgid "Your profile page"
+#: ../../include/channel.php:1538
+msgid "Religion:"
msgstr ""
-#: ../../include/nav.php:105
-msgid "Manage/Edit profiles"
+#: ../../include/channel.php:1542
+msgid "Hobbies/Interests:"
msgstr ""
-#: ../../include/nav.php:107
-msgid "Edit your profile"
+#: ../../include/channel.php:1544
+msgid "Likes:"
msgstr ""
-#: ../../include/nav.php:130
-msgid "Sign in"
+#: ../../include/channel.php:1546
+msgid "Dislikes:"
msgstr ""
-#: ../../include/nav.php:155
-msgid "Get me home"
+#: ../../include/channel.php:1548
+msgid "Contact information and Social Networks:"
msgstr ""
-#: ../../include/nav.php:157
-msgid "Log me out of this site"
+#: ../../include/channel.php:1550
+msgid "My other channels:"
msgstr ""
-#: ../../include/nav.php:162
-msgid "Create an account"
+#: ../../include/channel.php:1552
+msgid "Musical interests:"
msgstr ""
-#: ../../include/nav.php:174
-msgid "Help and documentation"
+#: ../../include/channel.php:1554
+msgid "Books, literature:"
msgstr ""
-#: ../../include/nav.php:178
-msgid "Applications, utilities, links, games"
+#: ../../include/channel.php:1556
+msgid "Television:"
msgstr ""
-#: ../../include/nav.php:180
-msgid "Search site @name, #tag, ?docs, content"
+#: ../../include/channel.php:1558
+msgid "Film/dance/culture/entertainment:"
msgstr ""
-#: ../../include/nav.php:182
-msgid "Channel Directory"
+#: ../../include/channel.php:1560
+msgid "Love/Romance:"
msgstr ""
-#: ../../include/nav.php:194
-msgid "Your grid"
+#: ../../include/channel.php:1562
+msgid "Work/employment:"
msgstr ""
-#: ../../include/nav.php:195
-msgid "View your network/grid"
+#: ../../include/channel.php:1564
+msgid "School/education:"
msgstr ""
-#: ../../include/nav.php:196
-msgid "Mark all grid notifications seen"
+#: ../../include/channel.php:1587
+msgid "Like this thing"
msgstr ""
-#: ../../include/nav.php:198
-msgid "Channel home"
+#: ../../include/event.php:22 ../../include/event.php:69
+msgid "l F d, Y \\@ g:i A"
msgstr ""
-#: ../../include/nav.php:199
-msgid "View your channel home"
+#: ../../include/event.php:30 ../../include/event.php:73
+msgid "Starts:"
msgstr ""
-#: ../../include/nav.php:200
-msgid "Mark all channel notifications seen"
+#: ../../include/event.php:40 ../../include/event.php:77
+msgid "Finishes:"
msgstr ""
-#: ../../include/nav.php:206
-msgid "Notices"
+#: ../../include/event.php:1008
+msgid "This event has been added to your calendar."
msgstr ""
-#: ../../include/nav.php:206
-msgid "Notifications"
+#: ../../include/event.php:1208
+msgid "Not specified"
msgstr ""
-#: ../../include/nav.php:207
-msgid "View all notifications"
+#: ../../include/event.php:1209
+msgid "Needs Action"
msgstr ""
-#: ../../include/nav.php:210
-msgid "Private mail"
+#: ../../include/event.php:1210
+msgid "Completed"
msgstr ""
-#: ../../include/nav.php:211
-msgid "View your private messages"
+#: ../../include/event.php:1211
+msgid "In Process"
msgstr ""
-#: ../../include/nav.php:212
-msgid "Mark all private messages seen"
+#: ../../include/event.php:1212
+msgid "Cancelled"
msgstr ""
-#: ../../include/nav.php:218
-msgid "Event Calendar"
+#: ../../include/event.php:1292 ../../include/connections.php:684
+msgid "Home, Voice"
msgstr ""
-#: ../../include/nav.php:219
-msgid "View events"
+#: ../../include/event.php:1293 ../../include/connections.php:685
+msgid "Home, Fax"
msgstr ""
-#: ../../include/nav.php:220
-msgid "Mark all events seen"
+#: ../../include/event.php:1295 ../../include/connections.php:687
+msgid "Work, Voice"
msgstr ""
-#: ../../include/nav.php:223
-msgid "Manage Your Channels"
+#: ../../include/event.php:1296 ../../include/connections.php:688
+msgid "Work, Fax"
msgstr ""
-#: ../../include/nav.php:225
-msgid "Account/Channel Settings"
+#: ../../include/network.php:752
+msgid "view full size"
msgstr ""
-#: ../../include/nav.php:233
-msgid "Site Setup and Configuration"
+#: ../../include/network.php:1700 ../../include/network.php:1701
+msgid "Friendica"
msgstr ""
-#: ../../include/nav.php:288
-msgid "Documentation"
+#: ../../include/network.php:1702
+msgid "OStatus"
msgstr ""
-#: ../../include/nav.php:297
-msgid "@name, #tag, ?doc, content"
+#: ../../include/network.php:1703
+msgid "GNU-Social"
msgstr ""
-#: ../../include/nav.php:298
-msgid "Please wait..."
+#: ../../include/network.php:1704
+msgid "RSS/Atom"
msgstr ""
-#: ../../include/auth.php:148
-msgid "Logged out."
+#: ../../include/network.php:1707
+msgid "Diaspora"
msgstr ""
-#: ../../include/auth.php:275
-msgid "Failed authentication"
+#: ../../include/network.php:1708
+msgid "Facebook"
msgstr ""
-#: ../../include/follow.php:26
-msgid "Channel is blocked on this site."
+#: ../../include/network.php:1709
+msgid "Zot"
msgstr ""
-#: ../../include/follow.php:31
-msgid "Channel location missing."
+#: ../../include/network.php:1710
+msgid "LinkedIn"
msgstr ""
-#: ../../include/follow.php:73
-msgid "Response from remote channel was incomplete."
+#: ../../include/network.php:1711
+msgid "XMPP/IM"
msgstr ""
-#: ../../include/follow.php:90
-msgid "Channel was deleted and no longer exists."
+#: ../../include/network.php:1712
+msgid "MySpace"
msgstr ""
-#: ../../include/follow.php:140 ../../include/follow.php:175
-msgid "Protocol disabled."
+#: ../../include/language.php:380
+msgid "Select an alternate language"
msgstr ""
-#: ../../include/follow.php:163
-msgid "Channel discovery failed."
+#: ../../include/acl_selectors.php:208
+msgid "Who can see this?"
msgstr ""
-#: ../../include/follow.php:202
-msgid "Cannot connect to yourself."
+#: ../../include/acl_selectors.php:209
+msgid "Custom selection"
msgstr ""
-#: ../../include/activities.php:41
-msgid " and "
+#: ../../include/acl_selectors.php:210
+msgid ""
+"Select \"Show\" to allow viewing. \"Don't show\" lets you override and limit "
+"the scope of \"Show\"."
msgstr ""
-#: ../../include/activities.php:49
-msgid "public profile"
+#: ../../include/acl_selectors.php:211
+msgid "Show"
msgstr ""
-#: ../../include/activities.php:58
-#, php-format
-msgid "%1$s changed %2$s to &ldquo;%3$s&rdquo;"
+#: ../../include/acl_selectors.php:212
+msgid "Don't show"
msgstr ""
-#: ../../include/activities.php:59
+#: ../../include/acl_selectors.php:245
#, php-format
-msgid "Visit %1$s's %2$s"
+msgid ""
+"Post permissions %s cannot be changed %s after a post is shared.</br />These "
+"permissions set who is allowed to view the post."
msgstr ""
-#: ../../include/activities.php:62
+#: ../../include/dba/dba_driver.php:190
#, php-format
-msgid "%1$s has an updated %2$s, changing %3$s."
+msgid "Cannot locate DNS info for database server '%s'"
msgstr ""
-#: ../../include/bbcode.php:134 ../../include/bbcode.php:1040
-#: ../../include/bbcode.php:1043 ../../include/bbcode.php:1048
-#: ../../include/bbcode.php:1051 ../../include/bbcode.php:1054
-#: ../../include/bbcode.php:1057 ../../include/bbcode.php:1062
-#: ../../include/bbcode.php:1065 ../../include/bbcode.php:1070
-#: ../../include/bbcode.php:1073 ../../include/bbcode.php:1076
-#: ../../include/bbcode.php:1079
+#: ../../include/bbcode.php:194 ../../include/bbcode.php:1102
+#: ../../include/bbcode.php:1105 ../../include/bbcode.php:1110
+#: ../../include/bbcode.php:1113 ../../include/bbcode.php:1116
+#: ../../include/bbcode.php:1119 ../../include/bbcode.php:1124
+#: ../../include/bbcode.php:1127 ../../include/bbcode.php:1132
+#: ../../include/bbcode.php:1135 ../../include/bbcode.php:1138
+#: ../../include/bbcode.php:1141
msgid "Image/photo"
msgstr ""
-#: ../../include/bbcode.php:173 ../../include/bbcode.php:1090
+#: ../../include/bbcode.php:233 ../../include/bbcode.php:1152
msgid "Encrypted content"
msgstr ""
-#: ../../include/bbcode.php:189
+#: ../../include/bbcode.php:249
#, php-format
msgid "Install %s element: "
msgstr ""
-#: ../../include/bbcode.php:193
+#: ../../include/bbcode.php:253
#, php-format
msgid ""
"This post contains an installable %s element, however you lack permissions "
"to install it on this site."
msgstr ""
-#: ../../include/bbcode.php:272
-#, php-format
-msgid "%1$s wrote the following %2$s %3$s"
+#: ../../include/bbcode.php:331
+msgid "card"
msgstr ""
-#: ../../include/bbcode.php:349 ../../include/bbcode.php:357
+#: ../../include/bbcode.php:414 ../../include/bbcode.php:422
msgid "Click to open/close"
msgstr ""
-#: ../../include/bbcode.php:357
+#: ../../include/bbcode.php:422
msgid "spoiler"
msgstr ""
-#: ../../include/bbcode.php:1028
+#: ../../include/bbcode.php:1090
msgid "$1 wrote:"
msgstr ""
-#: ../../include/bookmarks.php:34
-#, php-format
-msgid "%1$s's bookmarks"
-msgstr ""
-
-#: ../../include/group.php:26
-msgid ""
-"A deleted group with this name was revived. Existing item permissions "
-"<strong>may</strong> apply to this group and any future members. If this is "
-"not what you intended, please create another group with a different name."
-msgstr ""
-
-#: ../../include/group.php:248
-msgid "Add new connections to this privacy group"
-msgstr ""
-
-#: ../../include/group.php:289
-msgid "edit"
-msgstr ""
-
-#: ../../include/group.php:311 ../../include/features.php:292
-msgid "Privacy Groups"
-msgstr ""
-
-#: ../../include/group.php:312
-msgid "Edit group"
-msgstr ""
-
-#: ../../include/group.php:313
-msgid "Add privacy group"
-msgstr ""
-
-#: ../../include/group.php:314
-msgid "Channels not in any privacy group"
-msgstr ""
-
-#: ../../include/event.php:863
-msgid "This event has been added to your calendar."
-msgstr ""
-
-#: ../../include/event.php:1063
-msgid "Not specified"
-msgstr ""
-
-#: ../../include/event.php:1064
-msgid "Needs Action"
-msgstr ""
-
-#: ../../include/event.php:1065
-msgid "Completed"
-msgstr ""
-
-#: ../../include/event.php:1066
-msgid "In Process"
-msgstr ""
-
-#: ../../include/event.php:1067
-msgid "Cancelled"
-msgstr ""
-
-#: ../../include/items.php:841 ../../include/items.php:888
-msgid "(Unknown)"
-msgstr ""
-
-#: ../../include/items.php:1089
-msgid "Visible to anybody on the internet."
-msgstr ""
-
-#: ../../include/items.php:1091
-msgid "Visible to you only."
-msgstr ""
-
-#: ../../include/items.php:1093
-msgid "Visible to anybody in this network."
-msgstr ""
-
-#: ../../include/items.php:1095
-msgid "Visible to anybody authenticated."
-msgstr ""
-
-#: ../../include/items.php:1097
-#, php-format
-msgid "Visible to anybody on %s."
-msgstr ""
-
-#: ../../include/items.php:1099
-msgid "Visible to all connections."
-msgstr ""
-
-#: ../../include/items.php:1101
-msgid "Visible to approved connections."
-msgstr ""
-
-#: ../../include/items.php:1103
-msgid "Visible to specific connections."
-msgstr ""
-
-#: ../../include/items.php:3915
-msgid "Privacy group is empty."
+#: ../../include/oembed.php:328
+msgid " by "
msgstr ""
-#: ../../include/items.php:3922
-#, php-format
-msgid "Privacy group: %s"
+#: ../../include/oembed.php:329
+msgid " on "
msgstr ""
-#: ../../include/items.php:3934
-msgid "Connection not found."
+#: ../../include/oembed.php:358
+msgid "Embedded content"
msgstr ""
-#: ../../include/items.php:4283
-msgid "profile photo"
+#: ../../include/oembed.php:367
+msgid "Embedding disabled"
msgstr ""
-#: ../../include/items.php:4479
+#: ../../include/zid.php:305
#, php-format
-msgid "[Edited %s]"
-msgstr ""
-
-#: ../../include/items.php:4479
-msgctxt "edit_activity"
-msgid "Post"
-msgstr ""
-
-#: ../../include/items.php:4479
-msgctxt "edit_activity"
-msgid "Comment"
-msgstr ""
-
-#: ../../include/permissions.php:35
-msgid "Can view my normal stream and posts"
-msgstr ""
-
-#: ../../include/permissions.php:39
-msgid "Can view my webpages"
-msgstr ""
-
-#: ../../include/permissions.php:43
-msgid "Can post on my channel page (\"wall\")"
-msgstr ""
-
-#: ../../include/permissions.php:46
-msgid "Can like/dislike stuff"
-msgstr ""
-
-#: ../../include/permissions.php:46
-msgid "Profiles and things other than posts/comments"
-msgstr ""
-
-#: ../../include/permissions.php:48
-msgid "Can forward to all my channel contacts via post @mentions"
-msgstr ""
-
-#: ../../include/permissions.php:48
-msgid "Advanced - useful for creating group forum channels"
-msgstr ""
-
-#: ../../include/permissions.php:49
-msgid "Can chat with me (when available)"
-msgstr ""
-
-#: ../../include/permissions.php:50
-msgid "Can write to my file storage and photos"
-msgstr ""
-
-#: ../../include/permissions.php:51
-msgid "Can edit my webpages"
-msgstr ""
-
-#: ../../include/permissions.php:53
-msgid "Somewhat advanced - very useful in open communities"
-msgstr ""
-
-#: ../../include/permissions.php:55
-msgid "Can administer my channel resources"
-msgstr ""
-
-#: ../../include/permissions.php:55
-msgid "Extremely advanced. Leave this alone unless you know what you are doing"
+msgid "OpenWebAuth: %1$s welcomes %2$s"
msgstr ""
-#: ../../include/features.php:58
+#: ../../include/features.php:54
msgid "General Features"
msgstr ""
-#: ../../include/features.php:63
+#: ../../include/features.php:59
msgid "Multiple Profiles"
msgstr ""
-#: ../../include/features.php:64
+#: ../../include/features.php:60
msgid "Ability to create multiple profiles"
msgstr ""
-#: ../../include/features.php:72
+#: ../../include/features.php:68
msgid "Advanced Profiles"
msgstr ""
-#: ../../include/features.php:73
+#: ../../include/features.php:69
msgid "Additional profile sections and selections"
msgstr ""
-#: ../../include/features.php:81
+#: ../../include/features.php:77
msgid "Profile Import/Export"
msgstr ""
-#: ../../include/features.php:82
+#: ../../include/features.php:78
msgid "Save and load profile details across sites/channels"
msgstr ""
-#: ../../include/features.php:90
+#: ../../include/features.php:86
msgid "Web Pages"
msgstr ""
-#: ../../include/features.php:91
+#: ../../include/features.php:87
msgid "Provide managed web pages on your channel"
msgstr ""
-#: ../../include/features.php:100
+#: ../../include/features.php:96
msgid "Provide a wiki for your channel"
msgstr ""
-#: ../../include/features.php:117
+#: ../../include/features.php:113
msgid "Private Notes"
msgstr ""
-#: ../../include/features.php:118
+#: ../../include/features.php:114
msgid "Enables a tool to store notes and reminders (note: not encrypted)"
msgstr ""
-#: ../../include/features.php:126
+#: ../../include/features.php:123
+msgid "Create personal planning cards"
+msgstr ""
+
+#: ../../include/features.php:131
msgid "Navigation Channel Select"
msgstr ""
-#: ../../include/features.php:127
+#: ../../include/features.php:132
msgid "Change channels directly from within the navigation dropdown menu"
msgstr ""
-#: ../../include/features.php:135
+#: ../../include/features.php:140
msgid "Photo Location"
msgstr ""
-#: ../../include/features.php:136
+#: ../../include/features.php:141
msgid "If location data is available on uploaded photos, link this to a map."
msgstr ""
-#: ../../include/features.php:144
+#: ../../include/features.php:149
msgid "Access Controlled Chatrooms"
msgstr ""
-#: ../../include/features.php:145
+#: ../../include/features.php:150
msgid "Provide chatrooms and chat services with access control."
msgstr ""
-#: ../../include/features.php:153
-msgid "Permission Groups"
-msgstr ""
-
-#: ../../include/features.php:154
+#: ../../include/features.php:159
msgid "Provide alternate connection permission roles."
msgstr ""
-#: ../../include/features.php:162
+#: ../../include/features.php:167
msgid "Smart Birthdays"
msgstr ""
-#: ../../include/features.php:163
+#: ../../include/features.php:168
msgid ""
"Make birthday events timezone aware in case your friends are scattered "
"across the planet."
msgstr ""
-#: ../../include/features.php:171
+#: ../../include/features.php:176
msgid "Event Timezone Selection"
msgstr ""
-#: ../../include/features.php:172
+#: ../../include/features.php:177
msgid "Allow event creation in timezones other than your own."
msgstr ""
-#: ../../include/features.php:180
+#: ../../include/features.php:185
msgid "Advanced Directory Search"
msgstr ""
-#: ../../include/features.php:181
+#: ../../include/features.php:186
msgid "Allows creation of complex directory search queries"
msgstr ""
-#: ../../include/features.php:189
+#: ../../include/features.php:194
msgid "Advanced Theme and Layout Settings"
msgstr ""
-#: ../../include/features.php:190
+#: ../../include/features.php:195
msgid "Allows fine tuning of themes and page layouts"
msgstr ""
-#: ../../include/features.php:200
+#: ../../include/features.php:205
msgid "Post Composition Features"
msgstr ""
-#: ../../include/features.php:204
+#: ../../include/features.php:209
msgid "Large Photos"
msgstr ""
-#: ../../include/features.php:205
+#: ../../include/features.php:210
msgid ""
"Include large (1024px) photo thumbnails in posts. If not enabled, use small "
"(640px) photo thumbnails"
msgstr ""
-#: ../../include/features.php:214
+#: ../../include/features.php:219
msgid "Automatically import channel content from other channels or feeds"
msgstr ""
-#: ../../include/features.php:222
+#: ../../include/features.php:227
msgid "Even More Encryption"
msgstr ""
-#: ../../include/features.php:223
+#: ../../include/features.php:228
msgid ""
"Allow optional encryption of content end-to-end with a shared secret key"
msgstr ""
-#: ../../include/features.php:231
+#: ../../include/features.php:236
msgid "Enable Voting Tools"
msgstr ""
-#: ../../include/features.php:232
+#: ../../include/features.php:237
msgid "Provide a class of post which others can vote on"
msgstr ""
-#: ../../include/features.php:240
+#: ../../include/features.php:245
msgid "Disable Comments"
msgstr ""
-#: ../../include/features.php:241
+#: ../../include/features.php:246
msgid "Provide the option to disable comments for a post"
msgstr ""
-#: ../../include/features.php:249
+#: ../../include/features.php:254
msgid "Delayed Posting"
msgstr ""
-#: ../../include/features.php:250
+#: ../../include/features.php:255
msgid "Allow posts to be published at a later date"
msgstr ""
-#: ../../include/features.php:258
+#: ../../include/features.php:263
msgid "Content Expiration"
msgstr ""
-#: ../../include/features.php:259
+#: ../../include/features.php:264
msgid "Remove posts/comments and/or private messages at a future time"
msgstr ""
-#: ../../include/features.php:267
+#: ../../include/features.php:272
msgid "Suppress Duplicate Posts/Comments"
msgstr ""
-#: ../../include/features.php:268
+#: ../../include/features.php:273
msgid ""
"Prevent posts with identical content to be published with less than two "
"minutes in between submissions."
msgstr ""
-#: ../../include/features.php:279
+#: ../../include/features.php:284
msgid "Network and Stream Filtering"
msgstr ""
-#: ../../include/features.php:283
+#: ../../include/features.php:288
msgid "Search by Date"
msgstr ""
-#: ../../include/features.php:284
+#: ../../include/features.php:289
msgid "Ability to select posts by date ranges"
msgstr ""
-#: ../../include/features.php:293
+#: ../../include/features.php:297 ../../include/group.php:332
+msgid "Privacy Groups"
+msgstr ""
+
+#: ../../include/features.php:298
msgid "Enable management and selection of privacy groups"
msgstr ""
-#: ../../include/features.php:302
+#: ../../include/features.php:307
msgid "Save search terms for re-use"
msgstr ""
-#: ../../include/features.php:310
+#: ../../include/features.php:315
msgid "Network Personal Tab"
msgstr ""
-#: ../../include/features.php:311
+#: ../../include/features.php:316
msgid "Enable tab to display only Network posts that you've interacted on"
msgstr ""
-#: ../../include/features.php:319
+#: ../../include/features.php:324
msgid "Network New Tab"
msgstr ""
-#: ../../include/features.php:320
+#: ../../include/features.php:325
msgid "Enable tab to display all new Network activity"
msgstr ""
-#: ../../include/features.php:328
+#: ../../include/features.php:333
msgid "Affinity Tool"
msgstr ""
-#: ../../include/features.php:329
+#: ../../include/features.php:334
msgid "Filter stream activity by depth of relationships"
msgstr ""
-#: ../../include/features.php:338
+#: ../../include/features.php:343
msgid "Show friend and connection suggestions"
msgstr ""
-#: ../../include/features.php:346
+#: ../../include/features.php:351
msgid "Connection Filtering"
msgstr ""
-#: ../../include/features.php:347
+#: ../../include/features.php:352
msgid "Filter incoming posts from connections based on keywords/content"
msgstr ""
-#: ../../include/features.php:359
+#: ../../include/features.php:364
msgid "Post/Comment Tools"
msgstr ""
-#: ../../include/features.php:363
+#: ../../include/features.php:368
msgid "Community Tagging"
msgstr ""
-#: ../../include/features.php:364
+#: ../../include/features.php:369
msgid "Ability to tag existing posts"
msgstr ""
-#: ../../include/features.php:372
+#: ../../include/features.php:377
msgid "Post Categories"
msgstr ""
-#: ../../include/features.php:373
+#: ../../include/features.php:378
msgid "Add categories to your posts"
msgstr ""
-#: ../../include/features.php:381
+#: ../../include/features.php:386
msgid "Emoji Reactions"
msgstr ""
-#: ../../include/features.php:382
+#: ../../include/features.php:387
msgid "Add emoji reaction ability to posts"
msgstr ""
-#: ../../include/features.php:391
+#: ../../include/features.php:396
msgid "Ability to file posts under folders"
msgstr ""
-#: ../../include/features.php:399
+#: ../../include/features.php:404
msgid "Dislike Posts"
msgstr ""
-#: ../../include/features.php:400
+#: ../../include/features.php:405
msgid "Ability to dislike posts/comments"
msgstr ""
-#: ../../include/features.php:408
+#: ../../include/features.php:413
msgid "Star Posts"
msgstr ""
-#: ../../include/features.php:409
+#: ../../include/features.php:414
msgid "Ability to mark special posts with a star indicator"
msgstr ""
-#: ../../include/features.php:417
+#: ../../include/features.php:422
msgid "Tag Cloud"
msgstr ""
-#: ../../include/features.php:418
+#: ../../include/features.php:423
msgid "Provide a personal tag cloud on your channel page"
msgstr ""
-#: ../../include/features.php:430
+#: ../../include/features.php:434
msgid "Premium Channel"
msgstr ""
-#: ../../include/features.php:431
+#: ../../include/features.php:435
msgid ""
"Allows you to set restrictions and terms on those that connect with your "
"channel"
msgstr ""
-#: ../../include/help.php:31
-msgid "Help:"
+#: ../../include/taxonomy.php:325 ../../include/taxonomy.php:346
+msgid "Tags"
msgstr ""
-#: ../../include/help.php:63
-msgid "Not Found"
+#: ../../include/taxonomy.php:410
+msgid "Keywords"
msgstr ""
-#: ../../util/nconfig.php:34
-msgid "Source channel not found."
+#: ../../include/taxonomy.php:431
+msgid "have"
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:9
-msgid "Focus (Hubzilla default)"
+#: ../../include/taxonomy.php:431
+msgid "has"
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:110
-msgid "Theme settings"
+#: ../../include/taxonomy.php:432
+msgid "want"
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:111
-msgid "Narrow navbar"
+#: ../../include/taxonomy.php:432
+msgid "wants"
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:112
-msgid "Navigation bar background color"
+#: ../../include/taxonomy.php:433
+msgid "likes"
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:113
-msgid "Navigation bar gradient top color"
+#: ../../include/taxonomy.php:434
+msgid "dislikes"
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:114
-msgid "Navigation bar gradient bottom color"
+#: ../../include/account.php:35
+msgid "Not a valid email address"
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:115
-msgid "Navigation active button gradient top color"
+#: ../../include/account.php:37
+msgid "Your email domain is not among those allowed on this site"
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:116
-msgid "Navigation active button gradient bottom color"
+#: ../../include/account.php:43
+msgid "Your email address is already registered at this site."
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:117
-msgid "Navigation bar border color "
+#: ../../include/account.php:75
+msgid "An invitation is required."
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:118
-msgid "Navigation bar icon color "
+#: ../../include/account.php:79
+msgid "Invitation could not be verified."
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:119
-msgid "Navigation bar active icon color "
+#: ../../include/account.php:157
+msgid "Please enter the required information."
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:120
-msgid "link color"
+#: ../../include/account.php:224
+msgid "Failed to store account information."
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:121
-msgid "Set font-color for banner"
+#: ../../include/account.php:291
+#, php-format
+msgid "Registration confirmation for %s"
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:122
-msgid "Set the background color"
+#: ../../include/account.php:360
+#, php-format
+msgid "Registration request at %s"
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:123
-msgid "Set the background image"
+#: ../../include/account.php:382
+msgid "your registration password"
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:124
-msgid "Set the background color of items"
+#: ../../include/account.php:388 ../../include/account.php:450
+#, php-format
+msgid "Registration details for %s"
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:125
-msgid "Set the background color of comments"
+#: ../../include/account.php:461
+msgid "Account approved."
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:126
-msgid "Set the border color of comments"
+#: ../../include/account.php:501
+#, php-format
+msgid "Registration revoked for %s"
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:127
-msgid "Set the indent for comments"
+#: ../../include/account.php:780 ../../include/account.php:782
+msgid "Click here to upgrade."
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:128
-msgid "Set the basic color for item icons"
+#: ../../include/account.php:788
+msgid "This action exceeds the limits set by your subscription plan."
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:129
-msgid "Set the hover color for item icons"
+#: ../../include/account.php:793
+msgid "This action is not available under your subscription plan."
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:130
-msgid "Set font-size for the entire application"
+#: ../../include/datetime.php:147
+msgid "Birthday"
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:130
-msgid "Example: 14px"
+#: ../../include/datetime.php:149
+msgid "Age: "
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:131
-msgid "Set font-size for posts and comments"
+#: ../../include/datetime.php:151
+msgid "YYYY-MM-DD or MM-DD"
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:132
-msgid "Set font-color for posts and comments"
+#: ../../include/datetime.php:292
+msgid "less than a second ago"
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:133
-msgid "Set radius of corners"
+#: ../../include/datetime.php:310
+#, php-format
+msgctxt "e.g. 22 hours ago, 1 minute ago"
+msgid "%1$d %2$s ago"
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:134
-msgid "Set shadow depth of photos"
+#: ../../include/datetime.php:321
+msgctxt "relative_date"
+msgid "year"
+msgid_plural "years"
+msgstr[0] ""
+msgstr[1] ""
+
+#: ../../include/datetime.php:324
+msgctxt "relative_date"
+msgid "month"
+msgid_plural "months"
+msgstr[0] ""
+msgstr[1] ""
+
+#: ../../include/datetime.php:327
+msgctxt "relative_date"
+msgid "week"
+msgid_plural "weeks"
+msgstr[0] ""
+msgstr[1] ""
+
+#: ../../include/datetime.php:330
+msgctxt "relative_date"
+msgid "day"
+msgid_plural "days"
+msgstr[0] ""
+msgstr[1] ""
+
+#: ../../include/datetime.php:333
+msgctxt "relative_date"
+msgid "hour"
+msgid_plural "hours"
+msgstr[0] ""
+msgstr[1] ""
+
+#: ../../include/datetime.php:336
+msgctxt "relative_date"
+msgid "minute"
+msgid_plural "minutes"
+msgstr[0] ""
+msgstr[1] ""
+
+#: ../../include/datetime.php:339
+msgctxt "relative_date"
+msgid "second"
+msgid_plural "seconds"
+msgstr[0] ""
+msgstr[1] ""
+
+#: ../../include/datetime.php:576
+#, php-format
+msgid "%1$s's birthday"
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:135
-msgid "Set maximum width of content region in pixel"
+#: ../../include/datetime.php:577
+#, php-format
+msgid "Happy Birthday %1$s"
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:135
-msgid "Leave empty for default width"
+#: ../../include/nav.php:91
+msgid "Remote authentication"
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:136
-msgid "Left align page content"
+#: ../../include/nav.php:91
+msgid "Click to authenticate to your home hub"
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:137
-msgid "Set minimum opacity of nav bar - to hide it"
+#: ../../include/nav.php:98
+msgid "Network Activity"
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:138
-msgid "Set size of conversation author photo"
+#: ../../include/nav.php:100
+msgid "Mark all activity notifications seen"
msgstr ""
-#: ../../view/theme/redbasic/php/config.php:139
-msgid "Set size of followup author photos"
+#: ../../include/nav.php:102
+msgid "Channel home"
msgstr ""
-#: ../../boot.php:1505
-#, php-format
-msgid "Update %s failed. See error logs."
+#: ../../include/nav.php:103
+msgid "View your channel home"
msgstr ""
-#: ../../boot.php:1508
-#, php-format
-msgid "Update Error at %s"
+#: ../../include/nav.php:104
+msgid "Mark all channel notifications seen"
msgstr ""
-#: ../../boot.php:1712
-msgid "Create an account to access services and applications"
+#: ../../include/nav.php:109
+msgid "Registrations"
msgstr ""
-#: ../../boot.php:1734
-msgid "Login/Email"
+#: ../../include/nav.php:112
+msgid "Notifications"
msgstr ""
-#: ../../boot.php:1735
-msgid "Password"
+#: ../../include/nav.php:113
+msgid "View all notifications"
msgstr ""
-#: ../../boot.php:1736
-msgid "Remember me"
+#: ../../include/nav.php:114
+msgid "Mark all system notifications seen"
msgstr ""
-#: ../../boot.php:1739
-msgid "Forgot your password?"
+#: ../../include/nav.php:116
+msgid "Private mail"
msgstr ""
-#: ../../boot.php:2300
-msgid "toggle mobile"
+#: ../../include/nav.php:117
+msgid "View your private messages"
msgstr ""
-#: ../../boot.php:2455
-msgid "Website SSL certificate is not valid. Please correct."
+#: ../../include/nav.php:118
+msgid "Mark all private messages seen"
+msgstr ""
+
+#: ../../include/nav.php:124
+msgid "Event Calendar"
+msgstr ""
+
+#: ../../include/nav.php:129 ../../include/nav.php:215
+msgid "Manage Your Channels"
+msgstr ""
+
+#: ../../include/nav.php:132 ../../include/nav.php:217
+msgid "Account/Channel Settings"
+msgstr ""
+
+#: ../../include/nav.php:138 ../../include/nav.php:167
+msgid "End this session"
msgstr ""
-#: ../../boot.php:2458
+#: ../../include/nav.php:141
+msgid "Your profile page"
+msgstr ""
+
+#: ../../include/nav.php:144
+msgid "Manage/Edit profiles"
+msgstr ""
+
+#: ../../include/nav.php:146
+msgid "Edit your profile"
+msgstr ""
+
+#: ../../include/nav.php:153 ../../include/nav.php:157
+msgid "Sign in"
+msgstr ""
+
+#: ../../include/nav.php:182
+msgid "Take me home"
+msgstr ""
+
+#: ../../include/nav.php:184
+msgid "Log me out of this site"
+msgstr ""
+
+#: ../../include/nav.php:189
+msgid "Create an account"
+msgstr ""
+
+#: ../../include/nav.php:201
+msgid "Help and documentation"
+msgstr ""
+
+#: ../../include/nav.php:204
+msgid "Search site @name, #tag, ?docs, content"
+msgstr ""
+
+#: ../../include/nav.php:224
+msgid "Site Setup and Configuration"
+msgstr ""
+
+#: ../../include/nav.php:311
+msgid "@name, #tag, ?doc, content"
+msgstr ""
+
+#: ../../include/nav.php:312
+msgid "Please wait..."
+msgstr ""
+
+#: ../../include/nav.php:318
+msgid "Add Apps"
+msgstr ""
+
+#: ../../include/nav.php:319
+msgid "Arrange Apps"
+msgstr ""
+
+#: ../../include/nav.php:320
+msgid "Toggle System Apps"
+msgstr ""
+
+#: ../../include/photos.php:123
#, php-format
-msgid "[hubzilla] Website SSL error for %s"
+msgid "Image exceeds website size limit of %lu bytes"
msgstr ""
-#: ../../boot.php:2577
-msgid "Cron/Scheduled tasks not running."
+#: ../../include/photos.php:130
+msgid "Image file is empty."
+msgstr ""
+
+#: ../../include/photos.php:268
+msgid "Photo storage failed."
+msgstr ""
+
+#: ../../include/photos.php:308
+msgid "a new photo"
+msgstr ""
+
+#: ../../include/photos.php:312
+#, php-format
+msgctxt "photo_upload"
+msgid "%1$s posted %2$s to %3$s"
+msgstr ""
+
+#: ../../include/photos.php:605
+msgid "Upload New Photos"
+msgstr ""
+
+#: ../../include/zot.php:654
+msgid "Invalid data packet"
+msgstr ""
+
+#: ../../include/zot.php:681
+msgid "Unable to verify channel signature"
msgstr ""
-#: ../../boot.php:2581
+#: ../../include/zot.php:2368
#, php-format
-msgid "[hubzilla] Cron tasks not running on %s"
+msgid "Unable to verify site signature for %s"
+msgstr ""
+
+#: ../../include/group.php:26
+msgid ""
+"A deleted group with this name was revived. Existing item permissions "
+"<strong>may</strong> apply to this group and any future members. If this is "
+"not what you intended, please create another group with a different name."
+msgstr ""
+
+#: ../../include/group.php:268
+msgid "Add new connections to this privacy group"
+msgstr ""
+
+#: ../../include/group.php:310
+msgid "edit"
+msgstr ""
+
+#: ../../include/group.php:333
+msgid "Edit group"
+msgstr ""
+
+#: ../../include/group.php:334
+msgid "Add privacy group"
+msgstr ""
+
+#: ../../include/group.php:335
+msgid "Channels not in any privacy group"
+msgstr ""
+
+#: ../../include/connections.php:128
+msgid "New window"
+msgstr ""
+
+#: ../../include/connections.php:129
+msgid "Open the selected location in a different window or browser tab"
+msgstr ""
+
+#: ../../include/auth.php:148
+msgid "Logged out."
+msgstr ""
+
+#: ../../include/auth.php:263
+msgid "Email validation is incomplete. Please check your email."
+msgstr ""
+
+#: ../../include/auth.php:278
+msgid "Failed authentication"
+msgstr ""
+
+#: ../../include/help.php:34
+msgid "Help:"
+msgstr ""
+
+#: ../../include/help.php:78
+msgid "Not Found"
msgstr ""
diff --git a/util/pconfig b/util/pconfig
index 1847a5a81..36d894fb5 100755
--- a/util/pconfig
+++ b/util/pconfig
@@ -73,8 +73,10 @@ if($argc == 4) {
if($argc == 3) {
load_pconfig($argv[1],$argv[2]);
- foreach(App::$config[$argv[1]][$argv[2]] as $k => $x) {
- echo "pconfig[{$argv[1]}][{$argv[2]}][{$k}] = " . $x . "\n";
+ if(App::$config[$argv[1]][$argv[2]]) {
+ foreach(App::$config[$argv[1]][$argv[2]] as $k => $x) {
+ echo "pconfig[{$argv[1]}][{$argv[2]}][{$k}] = " . $x . "\n";
+ }
}
}
diff --git a/util/typo.php b/util/typo.php
index f9c9e5353..e25e57601 100644
--- a/util/typo.php
+++ b/util/typo.php
@@ -12,7 +12,6 @@
App::init();
-// $a = new App();
echo "Directory: include\n";
$files = glob('include/*.php');
@@ -28,17 +27,18 @@
include_once($file);
}
- echo "Directory: include/RedDAV\n";
- $files = glob('include/RedDAV/*.php');
+ echo "Directory: include/photo\n";
+ $files = glob('include/photo/*.php');
foreach($files as $file) {
echo $file . "\n";
include_once($file);
}
+
echo "Directory: Zotlabs\n";
$files = glob('Zotlabs/*/*.php');
foreach($files as $file) {
- if(strpos($file,'SiteModule') === false) {
+ if((strpos($file,'SiteModule') === false) || (strpos($file,'SiteWidget') === false)) {
echo $file . "\n";
include_once($file);
}
@@ -51,21 +51,6 @@
include_once($file);
}
-
- echo "Directory: include/photo\n";
- $files = glob('include/photo/*.php');
- foreach($files as $file) {
- echo $file . "\n";
- include_once($file);
- }
-
-// echo "Directory: mod\n";
-// $files = glob('mod/*.php');
-// foreach($files as $file) {
-// echo $file . "\n";
-// include_once($file);
-// }
-
echo "Directory: addon\n";
$dirs = glob('addon/*');
@@ -93,6 +78,5 @@
foreach($files as $file) {
echo $file . "\n";
- passthru($phpath . ' util/typohelper.php ' . $file);
-// include_once($file);
+ passthru($phpath . ' util/typohelper.php ' . $file);
}
diff --git a/vendor/autoload.php b/vendor/autoload.php
index 063a1b7e1..8b4926c3d 100644
--- a/vendor/autoload.php
+++ b/vendor/autoload.php
@@ -2,6 +2,6 @@
// autoload.php @generated by Composer
-require_once __DIR__ . '/composer' . '/autoload_real.php';
+require_once __DIR__ . '/composer/autoload_real.php';
return ComposerAutoloaderInit7b34d7e50a62201ec5d5e526a5b8b35d::getLoader();
diff --git a/vendor/bin/html-to-markdown b/vendor/bin/html-to-markdown
new file mode 120000
index 000000000..6f8d9d2b1
--- /dev/null
+++ b/vendor/bin/html-to-markdown
@@ -0,0 +1 @@
+../league/html-to-markdown/bin/html-to-markdown \ No newline at end of file
diff --git a/vendor/bshaffer/oauth2-server-php/CHANGELOG.md b/vendor/bshaffer/oauth2-server-php/CHANGELOG.md
new file mode 100644
index 000000000..4fddd72c9
--- /dev/null
+++ b/vendor/bshaffer/oauth2-server-php/CHANGELOG.md
@@ -0,0 +1,182 @@
+CHANGELOG for 1.x
+=================
+
+This changelog references the relevant changes (bug and security fixes) done
+in 1.x minor versions.
+
+To see the files changed for a given bug, go to https://github.com/bshaffer/oauth2-server-php/issues/### where ### is the bug number
+To get the diff between two versions, go to https://github.com/bshaffer/oauth2-server-php/compare/v1.0...v1.1
+To get the diff for a specific change, go to https://github.com/bshaffer/oauth2-server-php/commit/XXX where XXX is the change hash
+
+* 1.9.0 (2016-01-06)
+
+ PR: https://github.com/bshaffer/oauth2-server-php/pull/788
+
+ * bug #645 - Allow null for client_secret
+ * bug #651 - Fix bug in isPublicClient of Cassandra Storage
+ * bug #670 - Bug in client's scope restriction
+ * bug #672 - Implemented method to override the password hashing algorithm
+ * bug #698 - Fix Token Response's Content-Type to application/json
+ * bug #729 - Ensures unsetAccessToken and unsetRefreshToken return a bool
+ * bug #749 - Fix UserClaims for CodeIdToken
+ * bug #784 - RFC6750 compatibility
+ * bug #776 - Fix "redirect_uri_mismatch" for URIs with encoded characters
+ * bug #759 - no access token supplied to resource controller results in empty request body
+ * bug #773 - Use OpenSSL random method before attempting Mcrypt's.
+ * bug #790 - Add mongo db
+
+* 1.8.0 (2015-09-18)
+
+ PR: https://github.com/bshaffer/oauth2-server-php/pull/643
+
+ * bug #594 - adds jti
+ * bug #598 - fixes lifetime configurations for JWTs
+ * bug #634 - fixes travis builds, upgrade to containers
+ * bug #586 - support for revoking tokens
+ * bug #636 - Adds FirebaseJWT bridge
+ * bug #639 - Mongo HHVM compatibility
+
+* 1.7.0 (2015-04-23)
+
+ PR: https://github.com/bshaffer/oauth2-server-php/pull/572
+
+ * bug #500 - PDO fetch mode changed from FETCH_BOTH to FETCH_ASSOC
+ * bug #508 - Case insensitive for Bearer token header name ba716d4
+ * bug #512 - validateRedirectUri is now public
+ * bug #530 - Add PublicKeyInterface, UserClaimsInterface to Cassandra Storage
+ * bug #505 - DynamoDB storage fixes
+ * bug #556 - adds "code id_token" return type to openid connect
+ * bug #563 - Include "issuer" config key for JwtAccessToken
+ * bug #564 - Fixes JWT vulnerability
+ * bug #571 - Added unset_refresh_token_after_use option
+
+* 1.6 (2015-01-16)
+
+ PR: https://github.com/bshaffer/oauth2-server-php/pull/496
+
+ * bug 437 - renames CryptoToken to JwtAccessToken / use_crypto_tokens to use_jwt_access_tokens
+ * bug 447 - Adds a Couchbase storage implementation
+ * bug 460 - Rename JWT claims to match spec
+ * bug 470 - order does not matter for multi-valued response types
+ * bug 471 - Make validateAuthorizeRequest available for POST in addition to GET
+ * bug 475 - Adds JTI table definitiion
+ * bug 481 - better randomness for generating access tokens
+ * bug 480 - Use hash_equals() for signature verification (prevents remote timing attacks)
+ * bugs 489, 491, 498 - misc other fixes
+
+* 1.5 (2014-08-27)
+
+ PR: https://github.com/bshaffer/oauth2-server-php/pull/446
+
+ * bug #399 - Add DynamoDB Support
+ * bug #404 - renamed error name for malformed/expired tokens
+ * bug #412 - Openid connect: fixes for claims with more than one scope / Add support for the prompt parameter ('consent' and 'none')
+ * bug #411 - fixes xml output
+ * bug #413 - fixes invalid format error
+ * bug #401 - fixes code standards / whitespace
+ * bug #354 - bundles PDO SQL with the library
+ * [BC] bug #397 - refresh tokens should not be encrypted
+ * bug #423 - makes "scope" optional for refresh token storage
+
+* 1.4 (2014-06-12)
+
+ PR: https://github.com/bshaffer/oauth2-server-php/pull/392
+
+ * bug #189 Storage\PDO - allows DSN string in constructor
+ * bug #233 Bearer Tokens - allows token in request body for PUT requests
+ * bug #346 Fixes open_basedir warning
+ * bug #351 Adds OpenID Connect support
+ * bug #355 Adds php 5.6 and HHVM to travis.ci testing
+ * [BC] bug #358 Adds `getQuerystringIdentifier()` to the GrantType interface
+ * bug #363 Encryption\JWT - Allows for subclassing JWT Headers
+ * bug #349 Bearer Tokens - adds requestHasToken method for when access tokens are optional
+ * bug #301 Encryption\JWT - fixes urlSafeB64Encode(): ensures newlines are replaced as expected
+ * bug #323 ResourceController - client_id is no longer required to be returned when calling getAccessToken
+ * bug #367 Storage\PDO - adds Postgres support
+ * bug #368 Access Tokens - use mcrypt_create_iv or openssl_random_pseudo_bytes to create token string
+ * bug #376 Request - allows case insensitive headers
+ * bug #384 Storage\PDO - can pass in PDO options in constructor of PDO storage
+ * misc fixes #361, #292, #373, #374, #379, #396
+* 1.3 (2014-02-27)
+
+ PR: https://github.com/bshaffer/oauth2-server-php/pull/325
+
+ * bug #311 adds cassandra storage
+ * bug #298 fixes response code for user credentials grant type
+ * bug #318 adds 'use_crypto_tokens' config to Server class for better DX
+ * [BC] bug #320 pass client_id to getDefaultScope
+ * bug #324 better feedback when running tests
+ * bug #335 adds support for non-expiring refresh tokens
+ * bug #333 fixes Pdo storage for getClientKey
+ * bug #336 fixes Redis storage for expireAuthorizationCode
+
+* 1.3 (2014-02-27)
+
+ PR: https://github.com/bshaffer/oauth2-server-php/pull/325
+
+ * bug #311 adds cassandra storage
+ * bug #298 fixes response code for user credentials grant type
+ * bug #318 adds 'use_crypto_tokens' config to Server class for better DX
+ * bug #320 pass client_id to getDefaultScope
+ * bug #324 better feedback when running tests
+ * bug #335 adds support for non-expiring refresh tokens
+ * bug #333 fixes Pdo storage for getClientKey
+ * bug #336 fixes Redis storage for expireAuthorizationCode
+
+* 1.2 (2014-01-03)
+
+ PR: https://github.com/bshaffer/oauth2-server-php/pull/288
+
+ * bug #285 changed response header from 200 to 401 when empty token received
+ * bug #286 adds documentation and links to spec for not including error messages when no token is supplied
+ * bug #280 ensures PHP warnings do not get thrown as a result of an invalid argument to $jwt->decode()
+ * bug #279 predis wrong number of arguments
+ * bug #277 Securing JS WebApp client secret w/ password grant type
+
+* 1.1 (2013-12-17)
+
+ PR: https://github.com/bshaffer/oauth2-server-php/pull/276
+
+ * bug #278 adds refresh token configuration to Server class
+ * bug #274 Supplying a null client_id and client_secret grants API access
+ * bug #244 [MongoStorage] More detailed implementation info
+ * bug #268 Implement jti for JWT Bearer tokens to prevent replay attacks.
+ * bug #266 Removing unused argument to getAccessTokenData
+ * bug #247 Make Bearer token type consistent
+ * bug #253 Fixing CryptoToken refresh token lifetime
+ * bug #246 refactors public key logic to be more intuitive
+ * bug #245 adds support for JSON crypto tokens
+ * bug #230 Remove unused columns in oauth_clients
+ * bug #215 makes Redis Scope Storage obey the same paradigm as PDO
+ * bug #228 removes scope group
+ * bug #227 squelches open basedir restriction error
+ * bug #223 Updated docblocks for RefreshTokenInterface.php
+ * bug #224 Adds protected properties
+ * bug #217 Implement ScopeInterface for PDO, Redis
+
+* 1.0 (2013-08-12)
+
+ * bug #203 Add redirect\_status_code config param for AuthorizeController
+ * bug #205 ensures unnecessary ? is not set when ** bug
+ * bug #204 Fixed call to LogicException
+ * bug #202 Add explode to checkRestrictedGrant in PDO Storage
+ * bug #197 adds support for 'false' default scope ** bug
+ * bug #192 reference errors and adds tests
+ * bug #194 makes some appropriate properties ** bug
+ * bug #191 passes config to HttpBasic
+ * bug #190 validates client credentials before ** bug
+ * bug #171 Fix wrong redirect following authorization step
+ * bug #187 client_id is now passed to getDefaultScope().
+ * bug #176 Require refresh_token in getRefreshToken response
+ * bug #174 make user\_id not required for refresh_token grant
+ * bug #173 Duplication in JwtBearer Grant
+ * bug #168 user\_id not required for authorization_code grant
+ * bug #133 hardens default security for user object
+ * bug #163 allows redirect\_uri on authorization_code to be NULL in docs example
+ * bug #162 adds getToken on ResourceController for convenience
+ * bug #161 fixes fatal error
+ * bug #163 Invalid redirect_uri handling
+ * bug #156 user\_id in OAuth2\_Storage_AuthorizationCodeInterface::getAuthorizationCode() response
+ * bug #157 Fix for extending access and refresh tokens
+ * bug #154 ResponseInterface: getParameter method is used in the library but not defined in the interface
+ * bug #148 Add more detail to examples in Readme.md
diff --git a/library/oauth2/LICENSE b/vendor/bshaffer/oauth2-server-php/LICENSE
index d7ece8467..d7ece8467 100644
--- a/library/oauth2/LICENSE
+++ b/vendor/bshaffer/oauth2-server-php/LICENSE
diff --git a/library/oauth2/README.md b/vendor/bshaffer/oauth2-server-php/README.md
index 4ceda6cf9..4ceda6cf9 100644
--- a/library/oauth2/README.md
+++ b/vendor/bshaffer/oauth2-server-php/README.md
diff --git a/vendor/bshaffer/oauth2-server-php/composer.json b/vendor/bshaffer/oauth2-server-php/composer.json
new file mode 100644
index 000000000..561699f5e
--- /dev/null
+++ b/vendor/bshaffer/oauth2-server-php/composer.json
@@ -0,0 +1,34 @@
+{
+ "name": "bshaffer/oauth2-server-php",
+ "description":"OAuth2 Server for PHP",
+ "keywords":["oauth","oauth2","auth"],
+ "type":"library",
+ "license":"MIT",
+ "authors":[
+ {
+ "name":"Brent Shaffer",
+ "email": "bshafs@gmail.com",
+ "homepage":"http://brentertainment.com"
+ }
+ ],
+ "homepage": "http://github.com/bshaffer/oauth2-server-php",
+ "autoload": {
+ "psr-0": { "OAuth2": "src/" }
+ },
+ "require":{
+ "php":">=5.3.9"
+ },
+ "require-dev": {
+ "aws/aws-sdk-php": "~2.8",
+ "firebase/php-jwt": "~2.2",
+ "predis/predis": "dev-master",
+ "thobbs/phpcassa": "dev-master",
+ "mongodb/mongodb": "^1.1"
+ },
+ "suggest": {
+ "predis/predis": "Required to use Redis storage",
+ "thobbs/phpcassa": "Required to use Cassandra storage",
+ "aws/aws-sdk-php": "~2.8 is required to use DynamoDB storage",
+ "firebase/php-jwt": "~1.1 is required to use MondoDB storage"
+ }
+}
diff --git a/library/oauth2/src/OAuth2/Autoloader.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Autoloader.php
index ecfb6ba75..ecfb6ba75 100644
--- a/library/oauth2/src/OAuth2/Autoloader.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Autoloader.php
diff --git a/library/oauth2/src/OAuth2/ClientAssertionType/ClientAssertionTypeInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/ClientAssertionType/ClientAssertionTypeInterface.php
index 29c7171b5..29c7171b5 100644
--- a/library/oauth2/src/OAuth2/ClientAssertionType/ClientAssertionTypeInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/ClientAssertionType/ClientAssertionTypeInterface.php
diff --git a/library/oauth2/src/OAuth2/ClientAssertionType/HttpBasic.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/ClientAssertionType/HttpBasic.php
index 0ecb7e18d..0ecb7e18d 100644
--- a/library/oauth2/src/OAuth2/ClientAssertionType/HttpBasic.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/ClientAssertionType/HttpBasic.php
diff --git a/vendor/bshaffer/oauth2-server-php/src/OAuth2/Controller/AuthorizeController.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Controller/AuthorizeController.php
new file mode 100644
index 000000000..ea7f54a87
--- /dev/null
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Controller/AuthorizeController.php
@@ -0,0 +1,393 @@
+<?php
+
+namespace OAuth2\Controller;
+
+use OAuth2\Storage\ClientInterface;
+use OAuth2\ScopeInterface;
+use OAuth2\RequestInterface;
+use OAuth2\ResponseInterface;
+use OAuth2\Scope;
+
+/**
+ * @see OAuth2\Controller\AuthorizeControllerInterface
+ */
+class AuthorizeController implements AuthorizeControllerInterface
+{
+ private $scope;
+ private $state;
+ private $client_id;
+ private $redirect_uri;
+ private $response_type;
+
+ protected $clientStorage;
+ protected $responseTypes;
+ protected $config;
+ protected $scopeUtil;
+
+ /**
+ * @param OAuth2\Storage\ClientInterface $clientStorage REQUIRED Instance of OAuth2\Storage\ClientInterface to retrieve client information
+ * @param array $responseTypes OPTIONAL Array of OAuth2\ResponseType\ResponseTypeInterface objects. Valid array
+ * keys are "code" and "token"
+ * @param array $config OPTIONAL Configuration options for the server
+ * <code>
+ * $config = array(
+ * 'allow_implicit' => false, // if the controller should allow the "implicit" grant type
+ * 'enforce_state' => true // if the controller should require the "state" parameter
+ * 'require_exact_redirect_uri' => true, // if the controller should require an exact match on the "redirect_uri" parameter
+ * 'redirect_status_code' => 302, // HTTP status code to use for redirect responses
+ * );
+ * </code>
+ * @param OAuth2\ScopeInterface $scopeUtil OPTIONAL Instance of OAuth2\ScopeInterface to validate the requested scope
+ */
+ public function __construct(ClientInterface $clientStorage, array $responseTypes = array(), array $config = array(), ScopeInterface $scopeUtil = null)
+ {
+ $this->clientStorage = $clientStorage;
+ $this->responseTypes = $responseTypes;
+ $this->config = array_merge(array(
+ 'allow_implicit' => false,
+ 'enforce_state' => true,
+ 'require_exact_redirect_uri' => true,
+ 'redirect_status_code' => 302,
+ ), $config);
+
+ if (is_null($scopeUtil)) {
+ $scopeUtil = new Scope();
+ }
+ $this->scopeUtil = $scopeUtil;
+ }
+
+ public function handleAuthorizeRequest(RequestInterface $request, ResponseInterface $response, $is_authorized, $user_id = null)
+ {
+ if (!is_bool($is_authorized)) {
+ throw new \InvalidArgumentException('Argument "is_authorized" must be a boolean. This method must know if the user has granted access to the client.');
+ }
+
+ // We repeat this, because we need to re-validate. The request could be POSTed
+ // by a 3rd-party (because we are not internally enforcing NONCEs, etc)
+ if (!$this->validateAuthorizeRequest($request, $response)) {
+ return;
+ }
+
+ // If no redirect_uri is passed in the request, use client's registered one
+ if (empty($this->redirect_uri)) {
+ $clientData = $this->clientStorage->getClientDetails($this->client_id);
+ $registered_redirect_uri = $clientData['redirect_uri'];
+ }
+
+ // the user declined access to the client's application
+ if ($is_authorized === false) {
+ $redirect_uri = $this->redirect_uri ?: $registered_redirect_uri;
+ $this->setNotAuthorizedResponse($request, $response, $redirect_uri, $user_id);
+
+ return;
+ }
+
+ // build the parameters to set in the redirect URI
+ if (!$params = $this->buildAuthorizeParameters($request, $response, $user_id)) {
+ return;
+ }
+
+ $authResult = $this->responseTypes[$this->response_type]->getAuthorizeResponse($params, $user_id);
+
+ list($redirect_uri, $uri_params) = $authResult;
+
+ if (empty($redirect_uri) && !empty($registered_redirect_uri)) {
+ $redirect_uri = $registered_redirect_uri;
+ }
+
+ $uri = $this->buildUri($redirect_uri, $uri_params);
+
+ // return redirect response
+ $response->setRedirect($this->config['redirect_status_code'], $uri);
+ }
+
+ protected function setNotAuthorizedResponse(RequestInterface $request, ResponseInterface $response, $redirect_uri, $user_id = null)
+ {
+ $error = 'access_denied';
+ $error_message = 'The user denied access to your application';
+ $response->setRedirect($this->config['redirect_status_code'], $redirect_uri, $this->state, $error, $error_message);
+ }
+
+ /*
+ * We have made this protected so this class can be extended to add/modify
+ * these parameters
+ */
+ protected function buildAuthorizeParameters($request, $response, $user_id)
+ {
+ // @TODO: we should be explicit with this in the future
+ $params = array(
+ 'scope' => $this->scope,
+ 'state' => $this->state,
+ 'client_id' => $this->client_id,
+ 'redirect_uri' => $this->redirect_uri,
+ 'response_type' => $this->response_type,
+ );
+
+ return $params;
+ }
+
+ /**
+ * @param RequestInterface $request
+ * @param ResponseInterface $response
+ * @return bool
+ */
+ public function validateAuthorizeRequest(RequestInterface $request, ResponseInterface $response)
+ {
+ // Make sure a valid client id was supplied (we can not redirect because we were unable to verify the URI)
+ if (!$client_id = $request->query('client_id', $request->request('client_id'))) {
+ // We don't have a good URI to use
+ $response->setError(400, 'invalid_client', "No client id supplied");
+
+ return false;
+ }
+
+ // Get client details
+ if (!$clientData = $this->clientStorage->getClientDetails($client_id)) {
+ $response->setError(400, 'invalid_client', 'The client id supplied is invalid');
+
+ return false;
+ }
+
+ $registered_redirect_uri = isset($clientData['redirect_uri']) ? $clientData['redirect_uri'] : '';
+
+ // Make sure a valid redirect_uri was supplied. If specified, it must match the clientData URI.
+ // @see http://tools.ietf.org/html/rfc6749#section-3.1.2
+ // @see http://tools.ietf.org/html/rfc6749#section-4.1.2.1
+ // @see http://tools.ietf.org/html/rfc6749#section-4.2.2.1
+ if ($supplied_redirect_uri = $request->query('redirect_uri', $request->request('redirect_uri'))) {
+ // validate there is no fragment supplied
+ $parts = parse_url($supplied_redirect_uri);
+ if (isset($parts['fragment']) && $parts['fragment']) {
+ $response->setError(400, 'invalid_uri', 'The redirect URI must not contain a fragment');
+
+ return false;
+ }
+
+ // validate against the registered redirect uri(s) if available
+ if ($registered_redirect_uri && !$this->validateRedirectUri($supplied_redirect_uri, $registered_redirect_uri)) {
+ $response->setError(400, 'redirect_uri_mismatch', 'The redirect URI provided is missing or does not match', '#section-3.1.2');
+
+ return false;
+ }
+ $redirect_uri = $supplied_redirect_uri;
+ } else {
+ // use the registered redirect_uri if none has been supplied, if possible
+ if (!$registered_redirect_uri) {
+ $response->setError(400, 'invalid_uri', 'No redirect URI was supplied or stored');
+
+ return false;
+ }
+
+ if (count(explode(' ', $registered_redirect_uri)) > 1) {
+ $response->setError(400, 'invalid_uri', 'A redirect URI must be supplied when multiple redirect URIs are registered', '#section-3.1.2.3');
+
+ return false;
+ }
+ $redirect_uri = $registered_redirect_uri;
+ }
+
+ // Select the redirect URI
+ $response_type = $request->query('response_type', $request->request('response_type'));
+
+ // for multiple-valued response types - make them alphabetical
+ if (false !== strpos($response_type, ' ')) {
+ $types = explode(' ', $response_type);
+ sort($types);
+ $response_type = ltrim(implode(' ', $types));
+ }
+
+ $state = $request->query('state', $request->request('state'));
+
+ // type and client_id are required
+ if (!$response_type || !in_array($response_type, $this->getValidResponseTypes())) {
+ $response->setRedirect($this->config['redirect_status_code'], $redirect_uri, $state, 'invalid_request', 'Invalid or missing response type', null);
+
+ return false;
+ }
+
+ if ($response_type == self::RESPONSE_TYPE_AUTHORIZATION_CODE) {
+ if (!isset($this->responseTypes['code'])) {
+ $response->setRedirect($this->config['redirect_status_code'], $redirect_uri, $state, 'unsupported_response_type', 'authorization code grant type not supported', null);
+
+ return false;
+ }
+ if (!$this->clientStorage->checkRestrictedGrantType($client_id, 'authorization_code')) {
+ $response->setRedirect($this->config['redirect_status_code'], $redirect_uri, $state, 'unauthorized_client', 'The grant type is unauthorized for this client_id', null);
+
+ return false;
+ }
+ if ($this->responseTypes['code']->enforceRedirect() && !$redirect_uri) {
+ $response->setError(400, 'redirect_uri_mismatch', 'The redirect URI is mandatory and was not supplied');
+
+ return false;
+ }
+ } else {
+ if (!$this->config['allow_implicit']) {
+ $response->setRedirect($this->config['redirect_status_code'], $redirect_uri, $state, 'unsupported_response_type', 'implicit grant type not supported', null);
+
+ return false;
+ }
+ if (!$this->clientStorage->checkRestrictedGrantType($client_id, 'implicit')) {
+ $response->setRedirect($this->config['redirect_status_code'], $redirect_uri, $state, 'unauthorized_client', 'The grant type is unauthorized for this client_id', null);
+
+ return false;
+ }
+ }
+
+ // validate requested scope if it exists
+ $requestedScope = $this->scopeUtil->getScopeFromRequest($request);
+
+ if ($requestedScope) {
+ // restrict scope by client specific scope if applicable,
+ // otherwise verify the scope exists
+ $clientScope = $this->clientStorage->getClientScope($client_id);
+ if ((empty($clientScope) && !$this->scopeUtil->scopeExists($requestedScope))
+ || (!empty($clientScope) && !$this->scopeUtil->checkScope($requestedScope, $clientScope))) {
+ $response->setRedirect($this->config['redirect_status_code'], $redirect_uri, $state, 'invalid_scope', 'An unsupported scope was requested', null);
+
+ return false;
+ }
+ } else {
+ // use a globally-defined default scope
+ $defaultScope = $this->scopeUtil->getDefaultScope($client_id);
+
+ if (false === $defaultScope) {
+ $response->setRedirect($this->config['redirect_status_code'], $redirect_uri, $state, 'invalid_client', 'This application requires you specify a scope parameter', null);
+
+ return false;
+ }
+
+ $requestedScope = $defaultScope;
+ }
+
+ // Validate state parameter exists (if configured to enforce this)
+ if ($this->config['enforce_state'] && !$state) {
+ $response->setRedirect($this->config['redirect_status_code'], $redirect_uri, null, 'invalid_request', 'The state parameter is required');
+
+ return false;
+ }
+
+ // save the input data and return true
+ $this->scope = $requestedScope;
+ $this->state = $state;
+ $this->client_id = $client_id;
+ // Only save the SUPPLIED redirect URI (@see http://tools.ietf.org/html/rfc6749#section-4.1.3)
+ $this->redirect_uri = $supplied_redirect_uri;
+ $this->response_type = $response_type;
+
+ return true;
+ }
+
+ /**
+ * Build the absolute URI based on supplied URI and parameters.
+ *
+ * @param $uri An absolute URI.
+ * @param $params Parameters to be append as GET.
+ *
+ * @return
+ * An absolute URI with supplied parameters.
+ *
+ * @ingroup oauth2_section_4
+ */
+ private function buildUri($uri, $params)
+ {
+ $parse_url = parse_url($uri);
+
+ // Add our params to the parsed uri
+ foreach ($params as $k => $v) {
+ if (isset($parse_url[$k])) {
+ $parse_url[$k] .= "&" . http_build_query($v, '', '&');
+ } else {
+ $parse_url[$k] = http_build_query($v, '', '&');
+ }
+ }
+
+ // Put humpty dumpty back together
+ return
+ ((isset($parse_url["scheme"])) ? $parse_url["scheme"] . "://" : "")
+ . ((isset($parse_url["user"])) ? $parse_url["user"]
+ . ((isset($parse_url["pass"])) ? ":" . $parse_url["pass"] : "") . "@" : "")
+ . ((isset($parse_url["host"])) ? $parse_url["host"] : "")
+ . ((isset($parse_url["port"])) ? ":" . $parse_url["port"] : "")
+ . ((isset($parse_url["path"])) ? $parse_url["path"] : "")
+ . ((isset($parse_url["query"]) && !empty($parse_url['query'])) ? "?" . $parse_url["query"] : "")
+ . ((isset($parse_url["fragment"])) ? "#" . $parse_url["fragment"] : "")
+ ;
+ }
+
+ protected function getValidResponseTypes()
+ {
+ return array(
+ self::RESPONSE_TYPE_ACCESS_TOKEN,
+ self::RESPONSE_TYPE_AUTHORIZATION_CODE,
+ );
+ }
+
+ /**
+ * Internal method for validating redirect URI supplied
+ *
+ * @param string $inputUri The submitted URI to be validated
+ * @param string $registeredUriString The allowed URI(s) to validate against. Can be a space-delimited string of URIs to
+ * allow for multiple URIs
+ *
+ * @see http://tools.ietf.org/html/rfc6749#section-3.1.2
+ */
+ protected function validateRedirectUri($inputUri, $registeredUriString)
+ {
+ if (!$inputUri || !$registeredUriString) {
+ return false; // if either one is missing, assume INVALID
+ }
+
+ $registered_uris = preg_split('/\s+/', $registeredUriString);
+ foreach ($registered_uris as $registered_uri) {
+ if ($this->config['require_exact_redirect_uri']) {
+ // the input uri is validated against the registered uri using exact match
+ if (strcmp($inputUri, $registered_uri) === 0) {
+ return true;
+ }
+ } else {
+ $registered_uri_length = strlen($registered_uri);
+ if ($registered_uri_length === 0) {
+ return false;
+ }
+
+ // the input uri is validated against the registered uri using case-insensitive match of the initial string
+ // i.e. additional query parameters may be applied
+ if (strcasecmp(substr($inputUri, 0, $registered_uri_length), $registered_uri) === 0) {
+ return true;
+ }
+ }
+ }
+
+ return false;
+ }
+
+ /**
+ * Convenience methods to access the parameters derived from the validated request
+ */
+
+ public function getScope()
+ {
+ return $this->scope;
+ }
+
+ public function getState()
+ {
+ return $this->state;
+ }
+
+ public function getClientId()
+ {
+ return $this->client_id;
+ }
+
+ public function getRedirectUri()
+ {
+ return $this->redirect_uri;
+ }
+
+ public function getResponseType()
+ {
+ return $this->response_type;
+ }
+}
diff --git a/library/oauth2/src/OAuth2/Controller/AuthorizeControllerInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Controller/AuthorizeControllerInterface.php
index fa07ae8d2..fa07ae8d2 100644
--- a/library/oauth2/src/OAuth2/Controller/AuthorizeControllerInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Controller/AuthorizeControllerInterface.php
diff --git a/vendor/bshaffer/oauth2-server-php/src/OAuth2/Controller/ResourceController.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Controller/ResourceController.php
new file mode 100644
index 000000000..3cfaaaf12
--- /dev/null
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Controller/ResourceController.php
@@ -0,0 +1,111 @@
+<?php
+
+namespace OAuth2\Controller;
+
+use OAuth2\TokenType\TokenTypeInterface;
+use OAuth2\Storage\AccessTokenInterface;
+use OAuth2\ScopeInterface;
+use OAuth2\RequestInterface;
+use OAuth2\ResponseInterface;
+use OAuth2\Scope;
+
+/**
+ * @see OAuth2\Controller\ResourceControllerInterface
+ */
+class ResourceController implements ResourceControllerInterface
+{
+ private $token;
+
+ protected $tokenType;
+ protected $tokenStorage;
+ protected $config;
+ protected $scopeUtil;
+
+ public function __construct(TokenTypeInterface $tokenType, AccessTokenInterface $tokenStorage, $config = array(), ScopeInterface $scopeUtil = null)
+ {
+ $this->tokenType = $tokenType;
+ $this->tokenStorage = $tokenStorage;
+
+ $this->config = array_merge(array(
+ 'www_realm' => 'Service',
+ ), $config);
+
+ if (is_null($scopeUtil)) {
+ $scopeUtil = new Scope();
+ }
+ $this->scopeUtil = $scopeUtil;
+ }
+
+ public function verifyResourceRequest(RequestInterface $request, ResponseInterface $response, $scope = null)
+ {
+ $token = $this->getAccessTokenData($request, $response);
+
+ // Check if we have token data
+ if (is_null($token)) {
+ return false;
+ }
+
+ /**
+ * Check scope, if provided
+ * If token doesn't have a scope, it's null/empty, or it's insufficient, then throw 403
+ * @see http://tools.ietf.org/html/rfc6750#section-3.1
+ */
+ if ($scope && (!isset($token["scope"]) || !$token["scope"] || !$this->scopeUtil->checkScope($scope, $token["scope"]))) {
+ $response->setError(403, 'insufficient_scope', 'The request requires higher privileges than provided by the access token');
+ $response->addHttpHeaders(array(
+ 'WWW-Authenticate' => sprintf('%s realm="%s", scope="%s", error="%s", error_description="%s"',
+ $this->tokenType->getTokenType(),
+ $this->config['www_realm'],
+ $scope,
+ $response->getParameter('error'),
+ $response->getParameter('error_description')
+ )
+ ));
+
+ return false;
+ }
+
+ // allow retrieval of the token
+ $this->token = $token;
+
+ return (bool) $token;
+ }
+
+ public function getAccessTokenData(RequestInterface $request, ResponseInterface $response)
+ {
+ // Get the token parameter
+ if ($token_param = $this->tokenType->getAccessTokenParameter($request, $response)) {
+ // Get the stored token data (from the implementing subclass)
+ // Check we have a well formed token
+ // Check token expiration (expires is a mandatory paramter)
+ if (!$token = $this->tokenStorage->getAccessToken($token_param)) {
+ $response->setError(401, 'invalid_token', 'The access token provided is invalid');
+ } elseif (!isset($token["expires"]) || !isset($token["client_id"])) {
+ $response->setError(401, 'malformed_token', 'Malformed token (missing "expires")');
+ } elseif (time() > $token["expires"]) {
+ $response->setError(401, 'invalid_token', 'The access token provided has expired');
+ } else {
+ return $token;
+ }
+ }
+
+ $authHeader = sprintf('%s realm="%s"', $this->tokenType->getTokenType(), $this->config['www_realm']);
+
+ if ($error = $response->getParameter('error')) {
+ $authHeader = sprintf('%s, error="%s"', $authHeader, $error);
+ if ($error_description = $response->getParameter('error_description')) {
+ $authHeader = sprintf('%s, error_description="%s"', $authHeader, $error_description);
+ }
+ }
+
+ $response->addHttpHeaders(array('WWW-Authenticate' => $authHeader));
+
+ return null;
+ }
+
+ // convenience method to allow retrieval of the token
+ public function getToken()
+ {
+ return $this->token;
+ }
+}
diff --git a/library/oauth2/src/OAuth2/Controller/ResourceControllerInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Controller/ResourceControllerInterface.php
index 611421935..611421935 100644
--- a/library/oauth2/src/OAuth2/Controller/ResourceControllerInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Controller/ResourceControllerInterface.php
diff --git a/vendor/bshaffer/oauth2-server-php/src/OAuth2/Controller/TokenController.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Controller/TokenController.php
new file mode 100644
index 000000000..5d2d731fe
--- /dev/null
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Controller/TokenController.php
@@ -0,0 +1,295 @@
+<?php
+
+namespace OAuth2\Controller;
+
+use OAuth2\ResponseType\AccessTokenInterface;
+use OAuth2\ClientAssertionType\ClientAssertionTypeInterface;
+use OAuth2\GrantType\GrantTypeInterface;
+use OAuth2\ScopeInterface;
+use OAuth2\Scope;
+use OAuth2\Storage\ClientInterface;
+use OAuth2\RequestInterface;
+use OAuth2\ResponseInterface;
+
+/**
+ * @see \OAuth2\Controller\TokenControllerInterface
+ */
+class TokenController implements TokenControllerInterface
+{
+ /**
+ * @var AccessTokenInterface
+ */
+ protected $accessToken;
+
+ /**
+ * @var array
+ */
+ protected $grantTypes;
+
+ /**
+ * @var ClientAssertionTypeInterface
+ */
+ protected $clientAssertionType;
+
+ /**
+ * @var Scope|ScopeInterface
+ */
+ protected $scopeUtil;
+
+ /**
+ * @var ClientInterface
+ */
+ protected $clientStorage;
+
+ public function __construct(AccessTokenInterface $accessToken, ClientInterface $clientStorage, array $grantTypes = array(), ClientAssertionTypeInterface $clientAssertionType = null, ScopeInterface $scopeUtil = null)
+ {
+ if (is_null($clientAssertionType)) {
+ foreach ($grantTypes as $grantType) {
+ if (!$grantType instanceof ClientAssertionTypeInterface) {
+ throw new \InvalidArgumentException('You must supply an instance of OAuth2\ClientAssertionType\ClientAssertionTypeInterface or only use grant types which implement OAuth2\ClientAssertionType\ClientAssertionTypeInterface');
+ }
+ }
+ }
+ $this->clientAssertionType = $clientAssertionType;
+ $this->accessToken = $accessToken;
+ $this->clientStorage = $clientStorage;
+ foreach ($grantTypes as $grantType) {
+ $this->addGrantType($grantType);
+ }
+
+ if (is_null($scopeUtil)) {
+ $scopeUtil = new Scope();
+ }
+ $this->scopeUtil = $scopeUtil;
+ }
+
+ public function handleTokenRequest(RequestInterface $request, ResponseInterface $response)
+ {
+ if ($token = $this->grantAccessToken($request, $response)) {
+ // @see http://tools.ietf.org/html/rfc6749#section-5.1
+ // server MUST disable caching in headers when tokens are involved
+ $response->setStatusCode(200);
+ $response->addParameters($token);
+ $response->addHttpHeaders(array(
+ 'Cache-Control' => 'no-store',
+ 'Pragma' => 'no-cache',
+ 'Content-Type' => 'application/json'
+ ));
+ }
+ }
+
+ /**
+ * Grant or deny a requested access token.
+ * This would be called from the "/token" endpoint as defined in the spec.
+ * You can call your endpoint whatever you want.
+ *
+ * @param RequestInterface $request Request object to grant access token
+ * @param ResponseInterface $response
+ *
+ * @throws \InvalidArgumentException
+ * @throws \LogicException
+ *
+ * @see http://tools.ietf.org/html/rfc6749#section-4
+ * @see http://tools.ietf.org/html/rfc6749#section-10.6
+ * @see http://tools.ietf.org/html/rfc6749#section-4.1.3
+ *
+ * @ingroup oauth2_section_4
+ */
+ public function grantAccessToken(RequestInterface $request, ResponseInterface $response)
+ {
+ if (strtolower($request->server('REQUEST_METHOD')) != 'post') {
+ $response->setError(405, 'invalid_request', 'The request method must be POST when requesting an access token', '#section-3.2');
+ $response->addHttpHeaders(array('Allow' => 'POST'));
+
+ return null;
+ }
+
+ /**
+ * Determine grant type from request
+ * and validate the request for that grant type
+ */
+ if (!$grantTypeIdentifier = $request->request('grant_type')) {
+ $response->setError(400, 'invalid_request', 'The grant type was not specified in the request');
+
+ return null;
+ }
+
+ if (!isset($this->grantTypes[$grantTypeIdentifier])) {
+ /* TODO: If this is an OAuth2 supported grant type that we have chosen not to implement, throw a 501 Not Implemented instead */
+ $response->setError(400, 'unsupported_grant_type', sprintf('Grant type "%s" not supported', $grantTypeIdentifier));
+
+ return null;
+ }
+
+ $grantType = $this->grantTypes[$grantTypeIdentifier];
+
+ /**
+ * Retrieve the client information from the request
+ * ClientAssertionTypes allow for grant types which also assert the client data
+ * in which case ClientAssertion is handled in the validateRequest method
+ *
+ * @see OAuth2\GrantType\JWTBearer
+ * @see OAuth2\GrantType\ClientCredentials
+ */
+ if (!$grantType instanceof ClientAssertionTypeInterface) {
+ if (!$this->clientAssertionType->validateRequest($request, $response)) {
+ return null;
+ }
+ $clientId = $this->clientAssertionType->getClientId();
+ }
+
+ /**
+ * Retrieve the grant type information from the request
+ * The GrantTypeInterface object handles all validation
+ * If the object is an instance of ClientAssertionTypeInterface,
+ * That logic is handled here as well
+ */
+ if (!$grantType->validateRequest($request, $response)) {
+ return null;
+ }
+
+ if ($grantType instanceof ClientAssertionTypeInterface) {
+ $clientId = $grantType->getClientId();
+ } else {
+ // validate the Client ID (if applicable)
+ if (!is_null($storedClientId = $grantType->getClientId()) && $storedClientId != $clientId) {
+ $response->setError(400, 'invalid_grant', sprintf('%s doesn\'t exist or is invalid for the client', $grantTypeIdentifier));
+
+ return null;
+ }
+ }
+
+ /**
+ * Validate the client can use the requested grant type
+ */
+ if (!$this->clientStorage->checkRestrictedGrantType($clientId, $grantTypeIdentifier)) {
+ $response->setError(400, 'unauthorized_client', 'The grant type is unauthorized for this client_id');
+
+ return false;
+ }
+
+ /**
+ * Validate the scope of the token
+ *
+ * requestedScope - the scope specified in the token request
+ * availableScope - the scope associated with the grant type
+ * ex: in the case of the "Authorization Code" grant type,
+ * the scope is specified in the authorize request
+ *
+ * @see http://tools.ietf.org/html/rfc6749#section-3.3
+ */
+
+ $requestedScope = $this->scopeUtil->getScopeFromRequest($request);
+ $availableScope = $grantType->getScope();
+
+ if ($requestedScope) {
+ // validate the requested scope
+ if ($availableScope) {
+ if (!$this->scopeUtil->checkScope($requestedScope, $availableScope)) {
+ $response->setError(400, 'invalid_scope', 'The scope requested is invalid for this request');
+
+ return null;
+ }
+ } else {
+ // validate the client has access to this scope
+ if ($clientScope = $this->clientStorage->getClientScope($clientId)) {
+ if (!$this->scopeUtil->checkScope($requestedScope, $clientScope)) {
+ $response->setError(400, 'invalid_scope', 'The scope requested is invalid for this client');
+
+ return false;
+ }
+ } elseif (!$this->scopeUtil->scopeExists($requestedScope)) {
+ $response->setError(400, 'invalid_scope', 'An unsupported scope was requested');
+
+ return null;
+ }
+ }
+ } elseif ($availableScope) {
+ // use the scope associated with this grant type
+ $requestedScope = $availableScope;
+ } else {
+ // use a globally-defined default scope
+ $defaultScope = $this->scopeUtil->getDefaultScope($clientId);
+
+ // "false" means default scopes are not allowed
+ if (false === $defaultScope) {
+ $response->setError(400, 'invalid_scope', 'This application requires you specify a scope parameter');
+
+ return null;
+ }
+
+ $requestedScope = $defaultScope;
+ }
+
+ return $grantType->createAccessToken($this->accessToken, $clientId, $grantType->getUserId(), $requestedScope);
+ }
+
+ /**
+ * addGrantType
+ *
+ * @param GrantTypeInterface $grantType the grant type to add for the specified identifier
+ * @param string $identifier a string passed in as "grant_type" in the response that will call this grantType
+ */
+ public function addGrantType(GrantTypeInterface $grantType, $identifier = null)
+ {
+ if (is_null($identifier) || is_numeric($identifier)) {
+ $identifier = $grantType->getQuerystringIdentifier();
+ }
+
+ $this->grantTypes[$identifier] = $grantType;
+ }
+
+ public function handleRevokeRequest(RequestInterface $request, ResponseInterface $response)
+ {
+ if ($this->revokeToken($request, $response)) {
+ $response->setStatusCode(200);
+ $response->addParameters(array('revoked' => true));
+ }
+ }
+
+ /**
+ * Revoke a refresh or access token. Returns true on success and when tokens are invalid
+ *
+ * Note: invalid tokens do not cause an error response since the client
+ * cannot handle such an error in a reasonable way. Moreover, the
+ * purpose of the revocation request, invalidating the particular token,
+ * is already achieved.
+ *
+ * @param RequestInterface $request
+ * @param ResponseInterface $response
+ * @return bool|null
+ */
+ public function revokeToken(RequestInterface $request, ResponseInterface $response)
+ {
+ if (strtolower($request->server('REQUEST_METHOD')) != 'post') {
+ $response->setError(405, 'invalid_request', 'The request method must be POST when revoking an access token', '#section-3.2');
+ $response->addHttpHeaders(array('Allow' => 'POST'));
+
+ return null;
+ }
+
+ $token_type_hint = $request->request('token_type_hint');
+ if (!in_array($token_type_hint, array(null, 'access_token', 'refresh_token'), true)) {
+ $response->setError(400, 'invalid_request', 'Token type hint must be either \'access_token\' or \'refresh_token\'');
+
+ return null;
+ }
+
+ $token = $request->request('token');
+ if ($token === null) {
+ $response->setError(400, 'invalid_request', 'Missing token parameter to revoke');
+
+ return null;
+ }
+
+ // @todo remove this check for v2.0
+ if (!method_exists($this->accessToken, 'revokeToken')) {
+ $class = get_class($this->accessToken);
+ throw new \RuntimeException("AccessToken {$class} does not implement required revokeToken method");
+ }
+
+ $this->accessToken->revokeToken($token, $token_type_hint);
+
+ return true;
+ }
+}
diff --git a/library/oauth2/src/OAuth2/Controller/TokenControllerInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Controller/TokenControllerInterface.php
index 72d72570f..72d72570f 100644
--- a/library/oauth2/src/OAuth2/Controller/TokenControllerInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Controller/TokenControllerInterface.php
diff --git a/library/oauth2/src/OAuth2/Encryption/EncryptionInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Encryption/EncryptionInterface.php
index 2d336c664..2d336c664 100644
--- a/library/oauth2/src/OAuth2/Encryption/EncryptionInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Encryption/EncryptionInterface.php
diff --git a/library/oauth2/src/OAuth2/Encryption/FirebaseJwt.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Encryption/FirebaseJwt.php
index 1b527e0a0..1b527e0a0 100644
--- a/library/oauth2/src/OAuth2/Encryption/FirebaseJwt.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Encryption/FirebaseJwt.php
diff --git a/library/oauth2/src/OAuth2/Encryption/Jwt.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Encryption/Jwt.php
index ee576e643..ee576e643 100644
--- a/library/oauth2/src/OAuth2/Encryption/Jwt.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Encryption/Jwt.php
diff --git a/vendor/bshaffer/oauth2-server-php/src/OAuth2/GrantType/AuthorizationCode.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/GrantType/AuthorizationCode.php
new file mode 100644
index 000000000..cae9f787d
--- /dev/null
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/GrantType/AuthorizationCode.php
@@ -0,0 +1,100 @@
+<?php
+
+namespace OAuth2\GrantType;
+
+use OAuth2\Storage\AuthorizationCodeInterface;
+use OAuth2\ResponseType\AccessTokenInterface;
+use OAuth2\RequestInterface;
+use OAuth2\ResponseInterface;
+
+/**
+ *
+ * @author Brent Shaffer <bshafs at gmail dot com>
+ */
+class AuthorizationCode implements GrantTypeInterface
+{
+ protected $storage;
+ protected $authCode;
+
+ /**
+ * @param \OAuth2\Storage\AuthorizationCodeInterface $storage REQUIRED Storage class for retrieving authorization code information
+ */
+ public function __construct(AuthorizationCodeInterface $storage)
+ {
+ $this->storage = $storage;
+ }
+
+ public function getQuerystringIdentifier()
+ {
+ return 'authorization_code';
+ }
+
+ public function validateRequest(RequestInterface $request, ResponseInterface $response)
+ {
+ if (!$request->request('code')) {
+ $response->setError(400, 'invalid_request', 'Missing parameter: "code" is required');
+
+ return false;
+ }
+
+ $code = $request->request('code');
+ if (!$authCode = $this->storage->getAuthorizationCode($code)) {
+ $response->setError(400, 'invalid_grant', 'Authorization code doesn\'t exist or is invalid for the client');
+
+ return false;
+ }
+
+ /*
+ * 4.1.3 - ensure that the "redirect_uri" parameter is present if the "redirect_uri" parameter was included in the initial authorization request
+ * @uri - http://tools.ietf.org/html/rfc6749#section-4.1.3
+ */
+ if (isset($authCode['redirect_uri']) && $authCode['redirect_uri']) {
+ if (!$request->request('redirect_uri') || urldecode($request->request('redirect_uri')) != urldecode($authCode['redirect_uri'])) {
+ $response->setError(400, 'redirect_uri_mismatch', "The redirect URI is missing or do not match", "#section-4.1.3");
+
+ return false;
+ }
+ }
+
+ if (!isset($authCode['expires'])) {
+ throw new \Exception('Storage must return authcode with a value for "expires"');
+ }
+
+ if ($authCode["expires"] < time()) {
+ $response->setError(400, 'invalid_grant', "The authorization code has expired");
+
+ return false;
+ }
+
+ if (!isset($authCode['code'])) {
+ $authCode['code'] = $code; // used to expire the code after the access token is granted
+ }
+
+ $this->authCode = $authCode;
+
+ return true;
+ }
+
+ public function getClientId()
+ {
+ return $this->authCode['client_id'];
+ }
+
+ public function getScope()
+ {
+ return isset($this->authCode['scope']) ? $this->authCode['scope'] : null;
+ }
+
+ public function getUserId()
+ {
+ return isset($this->authCode['user_id']) ? $this->authCode['user_id'] : null;
+ }
+
+ public function createAccessToken(AccessTokenInterface $accessToken, $client_id, $user_id, $scope)
+ {
+ $token = $accessToken->createAccessToken($client_id, $user_id, $scope);
+ $this->storage->expireAuthorizationCode($this->authCode['code']);
+
+ return $token;
+ }
+}
diff --git a/library/oauth2/src/OAuth2/GrantType/ClientCredentials.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/GrantType/ClientCredentials.php
index f953e4e8d..f953e4e8d 100644
--- a/library/oauth2/src/OAuth2/GrantType/ClientCredentials.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/GrantType/ClientCredentials.php
diff --git a/library/oauth2/src/OAuth2/GrantType/GrantTypeInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/GrantType/GrantTypeInterface.php
index 98489e9c1..98489e9c1 100644
--- a/library/oauth2/src/OAuth2/GrantType/GrantTypeInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/GrantType/GrantTypeInterface.php
diff --git a/library/oauth2/src/OAuth2/GrantType/JwtBearer.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/GrantType/JwtBearer.php
index bb11a6954..bb11a6954 100644
--- a/library/oauth2/src/OAuth2/GrantType/JwtBearer.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/GrantType/JwtBearer.php
diff --git a/library/oauth2/src/OAuth2/GrantType/RefreshToken.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/GrantType/RefreshToken.php
index e55385222..e55385222 100644
--- a/library/oauth2/src/OAuth2/GrantType/RefreshToken.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/GrantType/RefreshToken.php
diff --git a/library/oauth2/src/OAuth2/GrantType/UserCredentials.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/GrantType/UserCredentials.php
index f165538ba..f165538ba 100644
--- a/library/oauth2/src/OAuth2/GrantType/UserCredentials.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/GrantType/UserCredentials.php
diff --git a/library/oauth2/src/OAuth2/OpenID/Controller/AuthorizeController.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Controller/AuthorizeController.php
index c9b5c6af7..c9b5c6af7 100644
--- a/library/oauth2/src/OAuth2/OpenID/Controller/AuthorizeController.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Controller/AuthorizeController.php
diff --git a/library/oauth2/src/OAuth2/OpenID/Controller/AuthorizeControllerInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Controller/AuthorizeControllerInterface.php
index 1e231d844..1e231d844 100644
--- a/library/oauth2/src/OAuth2/OpenID/Controller/AuthorizeControllerInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Controller/AuthorizeControllerInterface.php
diff --git a/library/oauth2/src/OAuth2/OpenID/Controller/UserInfoController.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Controller/UserInfoController.php
index 30cb942d0..30cb942d0 100644
--- a/library/oauth2/src/OAuth2/OpenID/Controller/UserInfoController.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Controller/UserInfoController.php
diff --git a/library/oauth2/src/OAuth2/OpenID/Controller/UserInfoControllerInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Controller/UserInfoControllerInterface.php
index a89049d49..a89049d49 100644
--- a/library/oauth2/src/OAuth2/OpenID/Controller/UserInfoControllerInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Controller/UserInfoControllerInterface.php
diff --git a/library/oauth2/src/OAuth2/OpenID/GrantType/AuthorizationCode.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/GrantType/AuthorizationCode.php
index 8ed1edc26..8ed1edc26 100644
--- a/library/oauth2/src/OAuth2/OpenID/GrantType/AuthorizationCode.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/GrantType/AuthorizationCode.php
diff --git a/library/oauth2/src/OAuth2/OpenID/ResponseType/AuthorizationCode.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/AuthorizationCode.php
index 8971954c5..8971954c5 100644
--- a/library/oauth2/src/OAuth2/OpenID/ResponseType/AuthorizationCode.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/AuthorizationCode.php
diff --git a/library/oauth2/src/OAuth2/OpenID/ResponseType/AuthorizationCodeInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/AuthorizationCodeInterface.php
index ea4779255..ea4779255 100644
--- a/library/oauth2/src/OAuth2/OpenID/ResponseType/AuthorizationCodeInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/AuthorizationCodeInterface.php
diff --git a/library/oauth2/src/OAuth2/OpenID/ResponseType/CodeIdToken.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/CodeIdToken.php
index ac7764d6c..ac7764d6c 100644
--- a/library/oauth2/src/OAuth2/OpenID/ResponseType/CodeIdToken.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/CodeIdToken.php
diff --git a/library/oauth2/src/OAuth2/OpenID/ResponseType/CodeIdTokenInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/CodeIdTokenInterface.php
index 629adcca8..629adcca8 100644
--- a/library/oauth2/src/OAuth2/OpenID/ResponseType/CodeIdTokenInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/CodeIdTokenInterface.php
diff --git a/library/oauth2/src/OAuth2/OpenID/ResponseType/IdToken.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/IdToken.php
index 97777fbf2..97777fbf2 100644
--- a/library/oauth2/src/OAuth2/OpenID/ResponseType/IdToken.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/IdToken.php
diff --git a/library/oauth2/src/OAuth2/OpenID/ResponseType/IdTokenInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/IdTokenInterface.php
index 0bd2f8391..0bd2f8391 100644
--- a/library/oauth2/src/OAuth2/OpenID/ResponseType/IdTokenInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/IdTokenInterface.php
diff --git a/library/oauth2/src/OAuth2/OpenID/ResponseType/IdTokenToken.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/IdTokenToken.php
index f0c59799b..f0c59799b 100644
--- a/library/oauth2/src/OAuth2/OpenID/ResponseType/IdTokenToken.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/IdTokenToken.php
diff --git a/library/oauth2/src/OAuth2/OpenID/ResponseType/IdTokenTokenInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/IdTokenTokenInterface.php
index ac13e2032..ac13e2032 100644
--- a/library/oauth2/src/OAuth2/OpenID/ResponseType/IdTokenTokenInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/IdTokenTokenInterface.php
diff --git a/library/oauth2/src/OAuth2/OpenID/Storage/AuthorizationCodeInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Storage/AuthorizationCodeInterface.php
index 51dd867ec..51dd867ec 100644
--- a/library/oauth2/src/OAuth2/OpenID/Storage/AuthorizationCodeInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Storage/AuthorizationCodeInterface.php
diff --git a/library/oauth2/src/OAuth2/OpenID/Storage/UserClaimsInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Storage/UserClaimsInterface.php
index f230bef9e..f230bef9e 100644
--- a/library/oauth2/src/OAuth2/OpenID/Storage/UserClaimsInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Storage/UserClaimsInterface.php
diff --git a/library/oauth2/src/OAuth2/Request.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Request.php
index c92cee821..c92cee821 100644
--- a/library/oauth2/src/OAuth2/Request.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Request.php
diff --git a/library/oauth2/src/OAuth2/RequestInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/RequestInterface.php
index 8a70d5fad..8a70d5fad 100644
--- a/library/oauth2/src/OAuth2/RequestInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/RequestInterface.php
diff --git a/vendor/bshaffer/oauth2-server-php/src/OAuth2/Response.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Response.php
new file mode 100644
index 000000000..fc1e62a98
--- /dev/null
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Response.php
@@ -0,0 +1,369 @@
+<?php
+
+namespace OAuth2;
+
+/**
+ * Class to handle OAuth2 Responses in a graceful way. Use this interface
+ * to output the proper OAuth2 responses.
+ *
+ * @see OAuth2\ResponseInterface
+ *
+ * This class borrows heavily from the Symfony2 Framework and is part of the symfony package
+ * @see Symfony\Component\HttpFoundation\Request (https://github.com/symfony/symfony)
+ */
+class Response implements ResponseInterface
+{
+ public $version;
+ protected $statusCode = 200;
+ protected $statusText;
+ protected $parameters = array();
+ protected $httpHeaders = array();
+
+ public static $statusTexts = array(
+ 100 => 'Continue',
+ 101 => 'Switching Protocols',
+ 200 => 'OK',
+ 201 => 'Created',
+ 202 => 'Accepted',
+ 203 => 'Non-Authoritative Information',
+ 204 => 'No Content',
+ 205 => 'Reset Content',
+ 206 => 'Partial Content',
+ 300 => 'Multiple Choices',
+ 301 => 'Moved Permanently',
+ 302 => 'Found',
+ 303 => 'See Other',
+ 304 => 'Not Modified',
+ 305 => 'Use Proxy',
+ 307 => 'Temporary Redirect',
+ 400 => 'Bad Request',
+ 401 => 'Unauthorized',
+ 402 => 'Payment Required',
+ 403 => 'Forbidden',
+ 404 => 'Not Found',
+ 405 => 'Method Not Allowed',
+ 406 => 'Not Acceptable',
+ 407 => 'Proxy Authentication Required',
+ 408 => 'Request Timeout',
+ 409 => 'Conflict',
+ 410 => 'Gone',
+ 411 => 'Length Required',
+ 412 => 'Precondition Failed',
+ 413 => 'Request Entity Too Large',
+ 414 => 'Request-URI Too Long',
+ 415 => 'Unsupported Media Type',
+ 416 => 'Requested Range Not Satisfiable',
+ 417 => 'Expectation Failed',
+ 418 => 'I\'m a teapot',
+ 500 => 'Internal Server Error',
+ 501 => 'Not Implemented',
+ 502 => 'Bad Gateway',
+ 503 => 'Service Unavailable',
+ 504 => 'Gateway Timeout',
+ 505 => 'HTTP Version Not Supported',
+ );
+
+ public function __construct($parameters = array(), $statusCode = 200, $headers = array())
+ {
+ $this->setParameters($parameters);
+ $this->setStatusCode($statusCode);
+ $this->setHttpHeaders($headers);
+ $this->version = '1.1';
+ }
+
+ /**
+ * Converts the response object to string containing all headers and the response content.
+ *
+ * @return string The response with headers and content
+ */
+ public function __toString()
+ {
+ $headers = array();
+ foreach ($this->httpHeaders as $name => $value) {
+ $headers[$name] = (array) $value;
+ }
+
+ return
+ sprintf('HTTP/%s %s %s', $this->version, $this->statusCode, $this->statusText)."\r\n".
+ $this->getHttpHeadersAsString($headers)."\r\n".
+ $this->getResponseBody();
+ }
+
+ /**
+ * Returns the build header line.
+ *
+ * @param string $name The header name
+ * @param string $value The header value
+ *
+ * @return string The built header line
+ */
+ protected function buildHeader($name, $value)
+ {
+ return sprintf("%s: %s\n", $name, $value);
+ }
+
+ public function getStatusCode()
+ {
+ return $this->statusCode;
+ }
+
+ public function setStatusCode($statusCode, $text = null)
+ {
+ $this->statusCode = (int) $statusCode;
+ if ($this->isInvalid()) {
+ throw new \InvalidArgumentException(sprintf('The HTTP status code "%s" is not valid.', $statusCode));
+ }
+
+ $this->statusText = false === $text ? '' : (null === $text ? self::$statusTexts[$this->statusCode] : $text);
+ }
+
+ public function getStatusText()
+ {
+ return $this->statusText;
+ }
+
+ public function getParameters()
+ {
+ return $this->parameters;
+ }
+
+ public function setParameters(array $parameters)
+ {
+ $this->parameters = $parameters;
+ }
+
+ public function addParameters(array $parameters)
+ {
+ $this->parameters = array_merge($this->parameters, $parameters);
+ }
+
+ public function getParameter($name, $default = null)
+ {
+ return isset($this->parameters[$name]) ? $this->parameters[$name] : $default;
+ }
+
+ public function setParameter($name, $value)
+ {
+ $this->parameters[$name] = $value;
+ }
+
+ public function setHttpHeaders(array $httpHeaders)
+ {
+ $this->httpHeaders = $httpHeaders;
+ }
+
+ public function setHttpHeader($name, $value)
+ {
+ $this->httpHeaders[$name] = $value;
+ }
+
+ public function addHttpHeaders(array $httpHeaders)
+ {
+ $this->httpHeaders = array_merge($this->httpHeaders, $httpHeaders);
+ }
+
+ public function getHttpHeaders()
+ {
+ return $this->httpHeaders;
+ }
+
+ public function getHttpHeader($name, $default = null)
+ {
+ return isset($this->httpHeaders[$name]) ? $this->httpHeaders[$name] : $default;
+ }
+
+ public function getResponseBody($format = 'json')
+ {
+ switch ($format) {
+ case 'json':
+ return $this->parameters ? json_encode($this->parameters) : '';
+ case 'xml':
+ // this only works for single-level arrays
+ $xml = new \SimpleXMLElement('<response/>');
+ foreach ($this->parameters as $key => $param) {
+ $xml->addChild($key, $param);
+ }
+
+ return $xml->asXML();
+ }
+
+ throw new \InvalidArgumentException(sprintf('The format %s is not supported', $format));
+
+ }
+
+ public function send($format = 'json')
+ {
+ // headers have already been sent by the developer
+ if (headers_sent()) {
+ return;
+ }
+
+ switch ($format) {
+ case 'json':
+ $this->setHttpHeader('Content-Type', 'application/json');
+ break;
+ case 'xml':
+ $this->setHttpHeader('Content-Type', 'text/xml');
+ break;
+ }
+ // status
+ header(sprintf('HTTP/%s %s %s', $this->version, $this->statusCode, $this->statusText));
+
+ foreach ($this->getHttpHeaders() as $name => $header) {
+ header(sprintf('%s: %s', $name, $header));
+ }
+ echo $this->getResponseBody($format);
+ }
+
+ public function setError($statusCode, $error, $errorDescription = null, $errorUri = null)
+ {
+ $parameters = array(
+ 'error' => $error,
+ 'error_description' => $errorDescription,
+ );
+
+ if (!is_null($errorUri)) {
+ if (strlen($errorUri) > 0 && $errorUri[0] == '#') {
+ // we are referencing an oauth bookmark (for brevity)
+ $errorUri = 'http://tools.ietf.org/html/rfc6749' . $errorUri;
+ }
+ $parameters['error_uri'] = $errorUri;
+ }
+
+ $httpHeaders = array(
+ 'Cache-Control' => 'no-store'
+ );
+
+ $this->setStatusCode($statusCode);
+ $this->addParameters($parameters);
+ $this->addHttpHeaders($httpHeaders);
+
+ if (!$this->isClientError() && !$this->isServerError()) {
+ throw new \InvalidArgumentException(sprintf('The HTTP status code is not an error ("%s" given).', $statusCode));
+ }
+ }
+
+ public function setRedirect($statusCode, $url, $state = null, $error = null, $errorDescription = null, $errorUri = null)
+ {
+ if (empty($url)) {
+ throw new \InvalidArgumentException('Cannot redirect to an empty URL.');
+ }
+
+ $parameters = array();
+
+ if (!is_null($state)) {
+ $parameters['state'] = $state;
+ }
+
+ if (!is_null($error)) {
+ $this->setError(400, $error, $errorDescription, $errorUri);
+ }
+ $this->setStatusCode($statusCode);
+ $this->addParameters($parameters);
+
+ if (count($this->parameters) > 0) {
+ // add parameters to URL redirection
+ $parts = parse_url($url);
+ $sep = isset($parts['query']) && count($parts['query']) > 0 ? '&' : '?';
+ $url .= $sep . http_build_query($this->parameters);
+ }
+
+ $this->addHttpHeaders(array('Location' => $url));
+
+ if (!$this->isRedirection()) {
+ throw new \InvalidArgumentException(sprintf('The HTTP status code is not a redirect ("%s" given).', $statusCode));
+ }
+ }
+
+ // http://www.w3.org/Protocols/rfc2616/rfc2616-sec10.html
+ /**
+ * @return Boolean
+ *
+ * @api
+ */
+ public function isInvalid()
+ {
+ return $this->statusCode < 100 || $this->statusCode >= 600;
+ }
+
+ /**
+ * @return Boolean
+ *
+ * @api
+ */
+ public function isInformational()
+ {
+ return $this->statusCode >= 100 && $this->statusCode < 200;
+ }
+
+ /**
+ * @return Boolean
+ *
+ * @api
+ */
+ public function isSuccessful()
+ {
+ return $this->statusCode >= 200 && $this->statusCode < 300;
+ }
+
+ /**
+ * @return Boolean
+ *
+ * @api
+ */
+ public function isRedirection()
+ {
+ return $this->statusCode >= 300 && $this->statusCode < 400;
+ }
+
+ /**
+ * @return Boolean
+ *
+ * @api
+ */
+ public function isClientError()
+ {
+ return $this->statusCode >= 400 && $this->statusCode < 500;
+ }
+
+ /**
+ * @return Boolean
+ *
+ * @api
+ */
+ public function isServerError()
+ {
+ return $this->statusCode >= 500 && $this->statusCode < 600;
+ }
+
+ /*
+ * Functions from Symfony2 HttpFoundation - output pretty header
+ */
+ private function getHttpHeadersAsString($headers)
+ {
+ if (count($headers) == 0) {
+ return '';
+ }
+
+ $max = max(array_map('strlen', array_keys($headers))) + 1;
+ $content = '';
+ ksort($headers);
+ foreach ($headers as $name => $values) {
+ foreach ($values as $value) {
+ $content .= sprintf("%-{$max}s %s\r\n", $this->beautifyHeaderName($name).':', $value);
+ }
+ }
+
+ return $content;
+ }
+
+ private function beautifyHeaderName($name)
+ {
+ return preg_replace_callback('/\-(.)/', array($this, 'beautifyCallback'), ucfirst($name));
+ }
+
+ private function beautifyCallback($match)
+ {
+ return '-'.strtoupper($match[1]);
+ }
+}
diff --git a/library/oauth2/src/OAuth2/ResponseInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/ResponseInterface.php
index c99b5f7d1..c99b5f7d1 100644
--- a/library/oauth2/src/OAuth2/ResponseInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/ResponseInterface.php
diff --git a/vendor/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/AccessToken.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/AccessToken.php
new file mode 100644
index 000000000..98f51218f
--- /dev/null
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/AccessToken.php
@@ -0,0 +1,194 @@
+<?php
+
+namespace OAuth2\ResponseType;
+
+use OAuth2\Storage\AccessTokenInterface as AccessTokenStorageInterface;
+use OAuth2\Storage\RefreshTokenInterface;
+
+/**
+ *
+ * @author Brent Shaffer <bshafs at gmail dot com>
+ */
+class AccessToken implements AccessTokenInterface
+{
+ protected $tokenStorage;
+ protected $refreshStorage;
+ protected $config;
+
+ /**
+ * @param OAuth2\Storage\AccessTokenInterface $tokenStorage REQUIRED Storage class for saving access token information
+ * @param OAuth2\Storage\RefreshTokenInterface $refreshStorage OPTIONAL Storage class for saving refresh token information
+ * @param array $config OPTIONAL Configuration options for the server
+ * <code>
+ * $config = array(
+ * 'token_type' => 'bearer', // token type identifier
+ * 'access_lifetime' => 3600, // time before access token expires
+ * 'refresh_token_lifetime' => 1209600, // time before refresh token expires
+ * );
+ * </endcode>
+ */
+ public function __construct(AccessTokenStorageInterface $tokenStorage, RefreshTokenInterface $refreshStorage = null, array $config = array())
+ {
+ $this->tokenStorage = $tokenStorage;
+ $this->refreshStorage = $refreshStorage;
+
+ $this->config = array_merge(array(
+ 'token_type' => 'bearer',
+ 'access_lifetime' => 3600,
+ 'refresh_token_lifetime' => 1209600,
+ ), $config);
+ }
+
+ public function getAuthorizeResponse($params, $user_id = null)
+ {
+ // build the URL to redirect to
+ $result = array('query' => array());
+
+ $params += array('scope' => null, 'state' => null);
+
+ /*
+ * a refresh token MUST NOT be included in the fragment
+ *
+ * @see http://tools.ietf.org/html/rfc6749#section-4.2.2
+ */
+ $includeRefreshToken = false;
+ $result["fragment"] = $this->createAccessToken($params['client_id'], $user_id, $params['scope'], $includeRefreshToken);
+
+ if (isset($params['state'])) {
+ $result["fragment"]["state"] = $params['state'];
+ }
+
+ return array($params['redirect_uri'], $result);
+ }
+
+ /**
+ * Handle the creation of access token, also issue refresh token if supported / desirable.
+ *
+ * @param $client_id client identifier related to the access token.
+ * @param $user_id user ID associated with the access token
+ * @param $scope OPTIONAL scopes to be stored in space-separated string.
+ * @param bool $includeRefreshToken if true, a new refresh_token will be added to the response
+ *
+ * @see http://tools.ietf.org/html/rfc6749#section-5
+ * @ingroup oauth2_section_5
+ */
+ public function createAccessToken($client_id, $user_id, $scope = null, $includeRefreshToken = true)
+ {
+ $token = array(
+ "access_token" => $this->generateAccessToken(),
+ "expires_in" => $this->config['access_lifetime'],
+ "token_type" => $this->config['token_type'],
+ "scope" => $scope
+ );
+
+ $this->tokenStorage->setAccessToken($token["access_token"], $client_id, $user_id, $this->config['access_lifetime'] ? time() + $this->config['access_lifetime'] : null, $scope);
+
+ /*
+ * Issue a refresh token also, if we support them
+ *
+ * Refresh Tokens are considered supported if an instance of OAuth2\Storage\RefreshTokenInterface
+ * is supplied in the constructor
+ */
+ if ($includeRefreshToken && $this->refreshStorage) {
+ $token["refresh_token"] = $this->generateRefreshToken();
+ $expires = 0;
+ if ($this->config['refresh_token_lifetime'] > 0) {
+ $expires = time() + $this->config['refresh_token_lifetime'];
+ }
+ $this->refreshStorage->setRefreshToken($token['refresh_token'], $client_id, $user_id, $expires, $scope);
+ }
+
+ return $token;
+ }
+
+ /**
+ * Generates an unique access token.
+ *
+ * Implementing classes may want to override this function to implement
+ * other access token generation schemes.
+ *
+ * @return
+ * An unique access token.
+ *
+ * @ingroup oauth2_section_4
+ */
+ protected function generateAccessToken()
+ {
+ if (function_exists('openssl_random_pseudo_bytes')) {
+ $randomData = openssl_random_pseudo_bytes(20);
+ if ($randomData !== false && strlen($randomData) === 20) {
+ return bin2hex($randomData);
+ }
+ }
+ if (function_exists('mcrypt_create_iv')) {
+ $randomData = mcrypt_create_iv(20, MCRYPT_DEV_URANDOM);
+ if ($randomData !== false && strlen($randomData) === 20) {
+ return bin2hex($randomData);
+ }
+ }
+ if (@file_exists('/dev/urandom')) { // Get 100 bytes of random data
+ $randomData = file_get_contents('/dev/urandom', false, null, 0, 20);
+ if ($randomData !== false && strlen($randomData) === 20) {
+ return bin2hex($randomData);
+ }
+ }
+ // Last resort which you probably should just get rid of:
+ $randomData = mt_rand() . mt_rand() . mt_rand() . mt_rand() . microtime(true) . uniqid(mt_rand(), true);
+
+ return substr(hash('sha512', $randomData), 0, 40);
+ }
+
+ /**
+ * Generates an unique refresh token
+ *
+ * Implementing classes may want to override this function to implement
+ * other refresh token generation schemes.
+ *
+ * @return
+ * An unique refresh.
+ *
+ * @ingroup oauth2_section_4
+ * @see OAuth2::generateAccessToken()
+ */
+ protected function generateRefreshToken()
+ {
+ return $this->generateAccessToken(); // let's reuse the same scheme for token generation
+ }
+
+ /**
+ * Handle the revoking of refresh tokens, and access tokens if supported / desirable
+ * RFC7009 specifies that "If the server is unable to locate the token using
+ * the given hint, it MUST extend its search across all of its supported token types"
+ *
+ * @param $token
+ * @param null $tokenTypeHint
+ * @return boolean
+ */
+ public function revokeToken($token, $tokenTypeHint = null)
+ {
+ if ($tokenTypeHint == 'refresh_token') {
+ if ($this->refreshStorage && $revoked = $this->refreshStorage->unsetRefreshToken($token)) {
+ return true;
+ }
+ }
+
+ /** @TODO remove in v2 */
+ if (!method_exists($this->tokenStorage, 'unsetAccessToken')) {
+ throw new \RuntimeException(
+ sprintf('Token storage %s must implement unsetAccessToken method', get_class($this->tokenStorage)
+ ));
+ }
+
+ $revoked = $this->tokenStorage->unsetAccessToken($token);
+
+ // if a typehint is supplied and fails, try other storages
+ // @see https://tools.ietf.org/html/rfc7009#section-2.1
+ if (!$revoked && $tokenTypeHint != 'refresh_token') {
+ if ($this->refreshStorage) {
+ $revoked = $this->refreshStorage->unsetRefreshToken($token);
+ }
+ }
+
+ return $revoked;
+ }
+}
diff --git a/library/oauth2/src/OAuth2/ResponseType/AccessTokenInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/AccessTokenInterface.php
index 4bd3928d8..4bd3928d8 100644
--- a/library/oauth2/src/OAuth2/ResponseType/AccessTokenInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/AccessTokenInterface.php
diff --git a/vendor/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/AuthorizationCode.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/AuthorizationCode.php
new file mode 100644
index 000000000..52aeb4be5
--- /dev/null
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/AuthorizationCode.php
@@ -0,0 +1,100 @@
+<?php
+
+namespace OAuth2\ResponseType;
+
+use OAuth2\Storage\AuthorizationCodeInterface as AuthorizationCodeStorageInterface;
+
+/**
+ *
+ * @author Brent Shaffer <bshafs at gmail dot com>
+ */
+class AuthorizationCode implements AuthorizationCodeInterface
+{
+ protected $storage;
+ protected $config;
+
+ public function __construct(AuthorizationCodeStorageInterface $storage, array $config = array())
+ {
+ $this->storage = $storage;
+ $this->config = array_merge(array(
+ 'enforce_redirect' => false,
+ 'auth_code_lifetime' => 30,
+ ), $config);
+ }
+
+ public function getAuthorizeResponse($params, $user_id = null)
+ {
+ // build the URL to redirect to
+ $result = array('query' => array());
+
+ $params += array('scope' => null, 'state' => null);
+
+ $result['query']['code'] = $this->createAuthorizationCode($params['client_id'], $user_id, $params['redirect_uri'], $params['scope']);
+
+ if (isset($params['state'])) {
+ $result['query']['state'] = $params['state'];
+ }
+
+ return array($params['redirect_uri'], $result);
+ }
+
+ /**
+ * Handle the creation of the authorization code.
+ *
+ * @param $client_id
+ * Client identifier related to the authorization code
+ * @param $user_id
+ * User ID associated with the authorization code
+ * @param $redirect_uri
+ * An absolute URI to which the authorization server will redirect the
+ * user-agent to when the end-user authorization step is completed.
+ * @param $scope
+ * (optional) Scopes to be stored in space-separated string.
+ *
+ * @see http://tools.ietf.org/html/rfc6749#section-4
+ * @ingroup oauth2_section_4
+ */
+ public function createAuthorizationCode($client_id, $user_id, $redirect_uri, $scope = null)
+ {
+ $code = $this->generateAuthorizationCode();
+ $this->storage->setAuthorizationCode($code, $client_id, $user_id, $redirect_uri, time() + $this->config['auth_code_lifetime'], $scope);
+
+ return $code;
+ }
+
+ /**
+ * @return
+ * TRUE if the grant type requires a redirect_uri, FALSE if not
+ */
+ public function enforceRedirect()
+ {
+ return $this->config['enforce_redirect'];
+ }
+
+ /**
+ * Generates an unique auth code.
+ *
+ * Implementing classes may want to override this function to implement
+ * other auth code generation schemes.
+ *
+ * @return
+ * An unique auth code.
+ *
+ * @ingroup oauth2_section_4
+ */
+ protected function generateAuthorizationCode()
+ {
+ $tokenLen = 40;
+ if (function_exists('openssl_random_pseudo_bytes')) {
+ $randomData = openssl_random_pseudo_bytes(100);
+ } elseif (function_exists('mcrypt_create_iv')) {
+ $randomData = mcrypt_create_iv(100, MCRYPT_DEV_URANDOM);
+ } elseif (@file_exists('/dev/urandom')) { // Get 100 bytes of random data
+ $randomData = file_get_contents('/dev/urandom', false, null, 0, 100) . uniqid(mt_rand(), true);
+ } else {
+ $randomData = mt_rand() . mt_rand() . mt_rand() . mt_rand() . microtime(true) . uniqid(mt_rand(), true);
+ }
+
+ return substr(hash('sha512', $randomData), 0, $tokenLen);
+ }
+}
diff --git a/library/oauth2/src/OAuth2/ResponseType/AuthorizationCodeInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/AuthorizationCodeInterface.php
index df777e221..df777e221 100644
--- a/library/oauth2/src/OAuth2/ResponseType/AuthorizationCodeInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/AuthorizationCodeInterface.php
diff --git a/library/oauth2/src/OAuth2/ResponseType/JwtAccessToken.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/JwtAccessToken.php
index 3942fe41e..3942fe41e 100644
--- a/library/oauth2/src/OAuth2/ResponseType/JwtAccessToken.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/JwtAccessToken.php
diff --git a/library/oauth2/src/OAuth2/ResponseType/ResponseTypeInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/ResponseTypeInterface.php
index f8e26a5b0..f8e26a5b0 100644
--- a/library/oauth2/src/OAuth2/ResponseType/ResponseTypeInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/ResponseTypeInterface.php
diff --git a/library/oauth2/src/OAuth2/Scope.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Scope.php
index c44350bfd..c44350bfd 100644
--- a/library/oauth2/src/OAuth2/Scope.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Scope.php
diff --git a/library/oauth2/src/OAuth2/ScopeInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/ScopeInterface.php
index 5b60f9aee..5b60f9aee 100644
--- a/library/oauth2/src/OAuth2/ScopeInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/ScopeInterface.php
diff --git a/vendor/bshaffer/oauth2-server-php/src/OAuth2/Server.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Server.php
new file mode 100644
index 000000000..9cfcb83a5
--- /dev/null
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Server.php
@@ -0,0 +1,879 @@
+<?php
+
+namespace OAuth2;
+
+use OAuth2\Controller\ResourceControllerInterface;
+use OAuth2\Controller\ResourceController;
+use OAuth2\OpenID\Controller\UserInfoControllerInterface;
+use OAuth2\OpenID\Controller\UserInfoController;
+use OAuth2\OpenID\Controller\AuthorizeController as OpenIDAuthorizeController;
+use OAuth2\OpenID\ResponseType\AuthorizationCode as OpenIDAuthorizationCodeResponseType;
+use OAuth2\OpenID\Storage\AuthorizationCodeInterface as OpenIDAuthorizationCodeInterface;
+use OAuth2\OpenID\GrantType\AuthorizationCode as OpenIDAuthorizationCodeGrantType;
+use OAuth2\Controller\AuthorizeControllerInterface;
+use OAuth2\Controller\AuthorizeController;
+use OAuth2\Controller\TokenControllerInterface;
+use OAuth2\Controller\TokenController;
+use OAuth2\ClientAssertionType\ClientAssertionTypeInterface;
+use OAuth2\ClientAssertionType\HttpBasic;
+use OAuth2\ResponseType\ResponseTypeInterface;
+use OAuth2\ResponseType\AuthorizationCode as AuthorizationCodeResponseType;
+use OAuth2\ResponseType\AccessToken;
+use OAuth2\ResponseType\JwtAccessToken;
+use OAuth2\OpenID\ResponseType\CodeIdToken;
+use OAuth2\OpenID\ResponseType\IdToken;
+use OAuth2\OpenID\ResponseType\IdTokenToken;
+use OAuth2\TokenType\TokenTypeInterface;
+use OAuth2\TokenType\Bearer;
+use OAuth2\GrantType\GrantTypeInterface;
+use OAuth2\GrantType\UserCredentials;
+use OAuth2\GrantType\ClientCredentials;
+use OAuth2\GrantType\RefreshToken;
+use OAuth2\GrantType\AuthorizationCode;
+use OAuth2\Storage\JwtAccessToken as JwtAccessTokenStorage;
+use OAuth2\Storage\JwtAccessTokenInterface;
+
+/**
+* Server class for OAuth2
+* This class serves as a convience class which wraps the other Controller classes
+*
+* @see OAuth2\Controller\ResourceController
+* @see OAuth2\Controller\AuthorizeController
+* @see OAuth2\Controller\TokenController
+*/
+class Server implements ResourceControllerInterface,
+ AuthorizeControllerInterface,
+ TokenControllerInterface,
+ UserInfoControllerInterface
+{
+ // misc properties
+ /**
+ * @var Response
+ */
+ protected $response;
+
+ /**
+ * @var array
+ */
+ protected $config;
+
+ /**
+ * @var array
+ */
+ protected $storages;
+
+ // servers
+ /**
+ * @var AuthorizeControllerInterface
+ */
+ protected $authorizeController;
+
+ /**
+ * @var TokenControllerInterface
+ */
+ protected $tokenController;
+
+ /**
+ * @var ResourceControllerInterface
+ */
+ protected $resourceController;
+
+ /**
+ * @var UserInfoControllerInterface
+ */
+ protected $userInfoController;
+
+ // config classes
+ protected $grantTypes;
+ protected $responseTypes;
+ protected $tokenType;
+
+ /**
+ * @var ScopeInterface
+ */
+ protected $scopeUtil;
+ protected $clientAssertionType;
+
+ protected $storageMap = array(
+ 'access_token' => 'OAuth2\Storage\AccessTokenInterface',
+ 'authorization_code' => 'OAuth2\Storage\AuthorizationCodeInterface',
+ 'client_credentials' => 'OAuth2\Storage\ClientCredentialsInterface',
+ 'client' => 'OAuth2\Storage\ClientInterface',
+ 'refresh_token' => 'OAuth2\Storage\RefreshTokenInterface',
+ 'user_credentials' => 'OAuth2\Storage\UserCredentialsInterface',
+ 'user_claims' => 'OAuth2\OpenID\Storage\UserClaimsInterface',
+ 'public_key' => 'OAuth2\Storage\PublicKeyInterface',
+ 'jwt_bearer' => 'OAuth2\Storage\JWTBearerInterface',
+ 'scope' => 'OAuth2\Storage\ScopeInterface',
+ );
+
+ protected $responseTypeMap = array(
+ 'token' => 'OAuth2\ResponseType\AccessTokenInterface',
+ 'code' => 'OAuth2\ResponseType\AuthorizationCodeInterface',
+ 'id_token' => 'OAuth2\OpenID\ResponseType\IdTokenInterface',
+ 'id_token token' => 'OAuth2\OpenID\ResponseType\IdTokenTokenInterface',
+ 'code id_token' => 'OAuth2\OpenID\ResponseType\CodeIdTokenInterface',
+ );
+
+ /**
+ * @param mixed $storage (array or OAuth2\Storage) - single object or array of objects implementing the
+ * required storage types (ClientCredentialsInterface and AccessTokenInterface as a minimum)
+ * @param array $config specify a different token lifetime, token header name, etc
+ * @param array $grantTypes An array of OAuth2\GrantType\GrantTypeInterface to use for granting access tokens
+ * @param array $responseTypes Response types to use. array keys should be "code" and and "token" for
+ * Access Token and Authorization Code response types
+ * @param \OAuth2\TokenType\TokenTypeInterface $tokenType The token type object to use. Valid token types are "bearer" and "mac"
+ * @param \OAuth2\ScopeInterface $scopeUtil The scope utility class to use to validate scope
+ * @param \OAuth2\ClientAssertionType\ClientAssertionTypeInterface $clientAssertionType The method in which to verify the client identity. Default is HttpBasic
+ *
+ * @ingroup oauth2_section_7
+ */
+ public function __construct($storage = array(), array $config = array(), array $grantTypes = array(), array $responseTypes = array(), TokenTypeInterface $tokenType = null, ScopeInterface $scopeUtil = null, ClientAssertionTypeInterface $clientAssertionType = null)
+ {
+ $storage = is_array($storage) ? $storage : array($storage);
+ $this->storages = array();
+ foreach ($storage as $key => $service) {
+ $this->addStorage($service, $key);
+ }
+
+ // merge all config values. These get passed to our controller objects
+ $this->config = array_merge(array(
+ 'use_jwt_access_tokens' => false,
+ 'store_encrypted_token_string' => true,
+ 'use_openid_connect' => false,
+ 'id_lifetime' => 3600,
+ 'access_lifetime' => 3600,
+ 'www_realm' => 'Service',
+ 'token_param_name' => 'access_token',
+ 'token_bearer_header_name' => 'Bearer',
+ 'enforce_state' => true,
+ 'require_exact_redirect_uri' => true,
+ 'allow_implicit' => false,
+ 'allow_credentials_in_request_body' => true,
+ 'allow_public_clients' => true,
+ 'always_issue_new_refresh_token' => false,
+ 'unset_refresh_token_after_use' => true,
+ ), $config);
+
+ foreach ($grantTypes as $key => $grantType) {
+ $this->addGrantType($grantType, $key);
+ }
+
+ foreach ($responseTypes as $key => $responseType) {
+ $this->addResponseType($responseType, $key);
+ }
+
+ $this->tokenType = $tokenType;
+ $this->scopeUtil = $scopeUtil;
+ $this->clientAssertionType = $clientAssertionType;
+
+ if ($this->config['use_openid_connect']) {
+ $this->validateOpenIdConnect();
+ }
+ }
+
+ public function getAuthorizeController()
+ {
+ if (is_null($this->authorizeController)) {
+ $this->authorizeController = $this->createDefaultAuthorizeController();
+ }
+
+ return $this->authorizeController;
+ }
+
+ public function getTokenController()
+ {
+ if (is_null($this->tokenController)) {
+ $this->tokenController = $this->createDefaultTokenController();
+ }
+
+ return $this->tokenController;
+ }
+
+ public function getResourceController()
+ {
+ if (is_null($this->resourceController)) {
+ $this->resourceController = $this->createDefaultResourceController();
+ }
+
+ return $this->resourceController;
+ }
+
+ public function getUserInfoController()
+ {
+ if (is_null($this->userInfoController)) {
+ $this->userInfoController = $this->createDefaultUserInfoController();
+ }
+
+ return $this->userInfoController;
+ }
+
+ /**
+ * every getter deserves a setter
+ *
+ * @param AuthorizeControllerInterface $authorizeController
+ */
+ public function setAuthorizeController(AuthorizeControllerInterface $authorizeController)
+ {
+ $this->authorizeController = $authorizeController;
+ }
+
+ /**
+ * every getter deserves a setter
+ *
+ * @param TokenControllerInterface $tokenController
+ */
+ public function setTokenController(TokenControllerInterface $tokenController)
+ {
+ $this->tokenController = $tokenController;
+ }
+
+ /**
+ * every getter deserves a setter
+ *
+ * @param ResourceControllerInterface $resourceController
+ */
+ public function setResourceController(ResourceControllerInterface $resourceController)
+ {
+ $this->resourceController = $resourceController;
+ }
+
+ /**
+ * every getter deserves a setter
+ *
+ * @param UserInfoControllerInterface $userInfoController
+ */
+ public function setUserInfoController(UserInfoControllerInterface $userInfoController)
+ {
+ $this->userInfoController = $userInfoController;
+ }
+
+ /**
+ * Return claims about the authenticated end-user.
+ * This would be called from the "/UserInfo" endpoint as defined in the spec.
+ *
+ * @param $request - \OAuth2\RequestInterface
+ * Request object to grant access token
+ *
+ * @param $response - \OAuth2\ResponseInterface
+ * Response object containing error messages (failure) or user claims (success)
+ *
+ * @return ResponseInterface
+ *
+ * @throws \InvalidArgumentException
+ * @throws \LogicException
+ *
+ * @see http://openid.net/specs/openid-connect-core-1_0.html#UserInfo
+ */
+ public function handleUserInfoRequest(RequestInterface $request, ResponseInterface $response = null)
+ {
+ $this->response = is_null($response) ? new Response() : $response;
+ $this->getUserInfoController()->handleUserInfoRequest($request, $this->response);
+
+ return $this->response;
+ }
+
+ /**
+ * Grant or deny a requested access token.
+ * This would be called from the "/token" endpoint as defined in the spec.
+ * Obviously, you can call your endpoint whatever you want.
+ *
+ * @param $request - \OAuth2\RequestInterface
+ * Request object to grant access token
+ *
+ * @param $response - \OAuth2\ResponseInterface
+ * Response object containing error messages (failure) or access token (success)
+ *
+ * @return ResponseInterface
+ *
+ * @throws \InvalidArgumentException
+ * @throws \LogicException
+ *
+ * @see http://tools.ietf.org/html/rfc6749#section-4
+ * @see http://tools.ietf.org/html/rfc6749#section-10.6
+ * @see http://tools.ietf.org/html/rfc6749#section-4.1.3
+ *
+ * @ingroup oauth2_section_4
+ */
+ public function handleTokenRequest(RequestInterface $request, ResponseInterface $response = null)
+ {
+ $this->response = is_null($response) ? new Response() : $response;
+ $this->getTokenController()->handleTokenRequest($request, $this->response);
+
+ return $this->response;
+ }
+
+ public function grantAccessToken(RequestInterface $request, ResponseInterface $response = null)
+ {
+ $this->response = is_null($response) ? new Response() : $response;
+ $value = $this->getTokenController()->grantAccessToken($request, $this->response);
+
+ return $value;
+ }
+
+ /**
+ * Handle a revoke token request
+ * This would be called from the "/revoke" endpoint as defined in the draft Token Revocation spec
+ *
+ * @see https://tools.ietf.org/html/rfc7009#section-2
+ *
+ * @param RequestInterface $request
+ * @param ResponseInterface $response
+ * @return Response|ResponseInterface
+ */
+ public function handleRevokeRequest(RequestInterface $request, ResponseInterface $response = null)
+ {
+ $this->response = is_null($response) ? new Response() : $response;
+ $this->getTokenController()->handleRevokeRequest($request, $this->response);
+
+ return $this->response;
+ }
+
+ /**
+ * Redirect the user appropriately after approval.
+ *
+ * After the user has approved or denied the resource request the
+ * authorization server should call this function to redirect the user
+ * appropriately.
+ *
+ * @param $request
+ * The request should have the follow parameters set in the querystring:
+ * - response_type: The requested response: an access token, an
+ * authorization code, or both.
+ * - client_id: The client identifier as described in Section 2.
+ * - redirect_uri: An absolute URI to which the authorization server
+ * will redirect the user-agent to when the end-user authorization
+ * step is completed.
+ * - scope: (optional) The scope of the resource request expressed as a
+ * list of space-delimited strings.
+ * - state: (optional) An opaque value used by the client to maintain
+ * state between the request and callback.
+ * @param ResponseInterface $response
+ * @param $is_authorized
+ * TRUE or FALSE depending on whether the user authorized the access.
+ * @param $user_id
+ * Identifier of user who authorized the client
+ *
+ * @return Response
+ *
+ * @see http://tools.ietf.org/html/rfc6749#section-4
+ *
+ * @ingroup oauth2_section_4
+ */
+ public function handleAuthorizeRequest(RequestInterface $request, ResponseInterface $response, $is_authorized, $user_id = null)
+ {
+ $this->response = $response;
+ $this->getAuthorizeController()->handleAuthorizeRequest($request, $this->response, $is_authorized, $user_id);
+
+ return $this->response;
+ }
+
+ /**
+ * Pull the authorization request data out of the HTTP request.
+ * - The redirect_uri is OPTIONAL as per draft 20. But your implementation can enforce it
+ * by setting $config['enforce_redirect'] to true.
+ * - The state is OPTIONAL but recommended to enforce CSRF. Draft 21 states, however, that
+ * CSRF protection is MANDATORY. You can enforce this by setting the $config['enforce_state'] to true.
+ *
+ * The draft specifies that the parameters should be retrieved from GET, override the Response
+ * object to change this
+ *
+ * @return
+ * The authorization parameters so the authorization server can prompt
+ * the user for approval if valid.
+ *
+ * @see http://tools.ietf.org/html/rfc6749#section-4.1.1
+ * @see http://tools.ietf.org/html/rfc6749#section-10.12
+ *
+ * @ingroup oauth2_section_3
+ */
+ public function validateAuthorizeRequest(RequestInterface $request, ResponseInterface $response = null)
+ {
+ $this->response = is_null($response) ? new Response() : $response;
+ $value = $this->getAuthorizeController()->validateAuthorizeRequest($request, $this->response);
+
+ return $value;
+ }
+
+ public function verifyResourceRequest(RequestInterface $request, ResponseInterface $response = null, $scope = null)
+ {
+ $this->response = is_null($response) ? new Response() : $response;
+ $value = $this->getResourceController()->verifyResourceRequest($request, $this->response, $scope);
+
+ return $value;
+ }
+
+ public function getAccessTokenData(RequestInterface $request, ResponseInterface $response = null)
+ {
+ $this->response = is_null($response) ? new Response() : $response;
+ $value = $this->getResourceController()->getAccessTokenData($request, $this->response);
+
+ return $value;
+ }
+
+ public function addGrantType(GrantTypeInterface $grantType, $identifier = null)
+ {
+ if (!is_string($identifier)) {
+ $identifier = $grantType->getQuerystringIdentifier();
+ }
+
+ $this->grantTypes[$identifier] = $grantType;
+
+ // persist added grant type down to TokenController
+ if (!is_null($this->tokenController)) {
+ $this->getTokenController()->addGrantType($grantType, $identifier);
+ }
+ }
+
+ /**
+ * Set a storage object for the server
+ *
+ * @param $storage
+ * An object implementing one of the Storage interfaces
+ * @param $key
+ * If null, the storage is set to the key of each storage interface it implements
+ *
+ * @see storageMap
+ */
+ public function addStorage($storage, $key = null)
+ {
+ // if explicitly set to a valid key, do not "magically" set below
+ if (isset($this->storageMap[$key])) {
+ if (!is_null($storage) && !$storage instanceof $this->storageMap[$key]) {
+ throw new \InvalidArgumentException(sprintf('storage of type "%s" must implement interface "%s"', $key, $this->storageMap[$key]));
+ }
+ $this->storages[$key] = $storage;
+
+ // special logic to handle "client" and "client_credentials" strangeness
+ if ($key === 'client' && !isset($this->storages['client_credentials'])) {
+ if ($storage instanceof \OAuth2\Storage\ClientCredentialsInterface) {
+ $this->storages['client_credentials'] = $storage;
+ }
+ } elseif ($key === 'client_credentials' && !isset($this->storages['client'])) {
+ if ($storage instanceof \OAuth2\Storage\ClientInterface) {
+ $this->storages['client'] = $storage;
+ }
+ }
+ } elseif (!is_null($key) && !is_numeric($key)) {
+ throw new \InvalidArgumentException(sprintf('unknown storage key "%s", must be one of [%s]', $key, implode(', ', array_keys($this->storageMap))));
+ } else {
+ $set = false;
+ foreach ($this->storageMap as $type => $interface) {
+ if ($storage instanceof $interface) {
+ $this->storages[$type] = $storage;
+ $set = true;
+ }
+ }
+
+ if (!$set) {
+ throw new \InvalidArgumentException(sprintf('storage of class "%s" must implement one of [%s]', get_class($storage), implode(', ', $this->storageMap)));
+ }
+ }
+ }
+
+ public function addResponseType(ResponseTypeInterface $responseType, $key = null)
+ {
+ $key = $this->normalizeResponseType($key);
+
+ if (isset($this->responseTypeMap[$key])) {
+ if (!$responseType instanceof $this->responseTypeMap[$key]) {
+ throw new \InvalidArgumentException(sprintf('responseType of type "%s" must implement interface "%s"', $key, $this->responseTypeMap[$key]));
+ }
+ $this->responseTypes[$key] = $responseType;
+ } elseif (!is_null($key) && !is_numeric($key)) {
+ throw new \InvalidArgumentException(sprintf('unknown responseType key "%s", must be one of [%s]', $key, implode(', ', array_keys($this->responseTypeMap))));
+ } else {
+ $set = false;
+ foreach ($this->responseTypeMap as $type => $interface) {
+ if ($responseType instanceof $interface) {
+ $this->responseTypes[$type] = $responseType;
+ $set = true;
+ }
+ }
+
+ if (!$set) {
+ throw new \InvalidArgumentException(sprintf('Unknown response type %s. Please implement one of [%s]', get_class($responseType), implode(', ', $this->responseTypeMap)));
+ }
+ }
+ }
+
+ public function getScopeUtil()
+ {
+ if (!$this->scopeUtil) {
+ $storage = isset($this->storages['scope']) ? $this->storages['scope'] : null;
+ $this->scopeUtil = new Scope($storage);
+ }
+
+ return $this->scopeUtil;
+ }
+
+ /**
+ * every getter deserves a setter
+ *
+ * @param ScopeInterface $scopeUtil
+ */
+ public function setScopeUtil($scopeUtil)
+ {
+ $this->scopeUtil = $scopeUtil;
+ }
+
+ protected function createDefaultAuthorizeController()
+ {
+ if (!isset($this->storages['client'])) {
+ throw new \LogicException('You must supply a storage object implementing \OAuth2\Storage\ClientInterface to use the authorize server');
+ }
+ if (0 == count($this->responseTypes)) {
+ $this->responseTypes = $this->getDefaultResponseTypes();
+ }
+ if ($this->config['use_openid_connect'] && !isset($this->responseTypes['id_token'])) {
+ $this->responseTypes['id_token'] = $this->createDefaultIdTokenResponseType();
+ if ($this->config['allow_implicit']) {
+ $this->responseTypes['id_token token'] = $this->createDefaultIdTokenTokenResponseType();
+ }
+ }
+
+ $config = array_intersect_key($this->config, array_flip(explode(' ', 'allow_implicit enforce_state require_exact_redirect_uri')));
+
+ if ($this->config['use_openid_connect']) {
+ return new OpenIDAuthorizeController($this->storages['client'], $this->responseTypes, $config, $this->getScopeUtil());
+ }
+
+ return new AuthorizeController($this->storages['client'], $this->responseTypes, $config, $this->getScopeUtil());
+ }
+
+ protected function createDefaultTokenController()
+ {
+ if (0 == count($this->grantTypes)) {
+ $this->grantTypes = $this->getDefaultGrantTypes();
+ }
+
+ if (is_null($this->clientAssertionType)) {
+ // see if HttpBasic assertion type is requred. If so, then create it from storage classes.
+ foreach ($this->grantTypes as $grantType) {
+ if (!$grantType instanceof ClientAssertionTypeInterface) {
+ if (!isset($this->storages['client_credentials'])) {
+ throw new \LogicException('You must supply a storage object implementing OAuth2\Storage\ClientCredentialsInterface to use the token server');
+ }
+ $config = array_intersect_key($this->config, array_flip(explode(' ', 'allow_credentials_in_request_body allow_public_clients')));
+ $this->clientAssertionType = new HttpBasic($this->storages['client_credentials'], $config);
+ break;
+ }
+ }
+ }
+
+ if (!isset($this->storages['client'])) {
+ throw new \LogicException('You must supply a storage object implementing OAuth2\Storage\ClientInterface to use the token server');
+ }
+
+ $accessTokenResponseType = $this->getAccessTokenResponseType();
+
+ return new TokenController($accessTokenResponseType, $this->storages['client'], $this->grantTypes, $this->clientAssertionType, $this->getScopeUtil());
+ }
+
+ protected function createDefaultResourceController()
+ {
+ if ($this->config['use_jwt_access_tokens']) {
+ // overwrites access token storage with crypto token storage if "use_jwt_access_tokens" is set
+ if (!isset($this->storages['access_token']) || !$this->storages['access_token'] instanceof JwtAccessTokenInterface) {
+ $this->storages['access_token'] = $this->createDefaultJwtAccessTokenStorage();
+ }
+ } elseif (!isset($this->storages['access_token'])) {
+ throw new \LogicException('You must supply a storage object implementing OAuth2\Storage\AccessTokenInterface or use JwtAccessTokens to use the resource server');
+ }
+
+ if (!$this->tokenType) {
+ $this->tokenType = $this->getDefaultTokenType();
+ }
+
+ $config = array_intersect_key($this->config, array('www_realm' => ''));
+
+ return new ResourceController($this->tokenType, $this->storages['access_token'], $config, $this->getScopeUtil());
+ }
+
+ protected function createDefaultUserInfoController()
+ {
+ if ($this->config['use_jwt_access_tokens']) {
+ // overwrites access token storage with crypto token storage if "use_jwt_access_tokens" is set
+ if (!isset($this->storages['access_token']) || !$this->storages['access_token'] instanceof JwtAccessTokenInterface) {
+ $this->storages['access_token'] = $this->createDefaultJwtAccessTokenStorage();
+ }
+ } elseif (!isset($this->storages['access_token'])) {
+ throw new \LogicException('You must supply a storage object implementing OAuth2\Storage\AccessTokenInterface or use JwtAccessTokens to use the UserInfo server');
+ }
+
+ if (!isset($this->storages['user_claims'])) {
+ throw new \LogicException('You must supply a storage object implementing OAuth2\OpenID\Storage\UserClaimsInterface to use the UserInfo server');
+ }
+
+ if (!$this->tokenType) {
+ $this->tokenType = $this->getDefaultTokenType();
+ }
+
+ $config = array_intersect_key($this->config, array('www_realm' => ''));
+
+ return new UserInfoController($this->tokenType, $this->storages['access_token'], $this->storages['user_claims'], $config, $this->getScopeUtil());
+ }
+
+ protected function getDefaultTokenType()
+ {
+ $config = array_intersect_key($this->config, array_flip(explode(' ', 'token_param_name token_bearer_header_name')));
+
+ return new Bearer($config);
+ }
+
+ protected function getDefaultResponseTypes()
+ {
+ $responseTypes = array();
+
+ if ($this->config['allow_implicit']) {
+ $responseTypes['token'] = $this->getAccessTokenResponseType();
+ }
+
+ if ($this->config['use_openid_connect']) {
+ $responseTypes['id_token'] = $this->getIdTokenResponseType();
+ if ($this->config['allow_implicit']) {
+ $responseTypes['id_token token'] = $this->getIdTokenTokenResponseType();
+ }
+ }
+
+ if (isset($this->storages['authorization_code'])) {
+ $config = array_intersect_key($this->config, array_flip(explode(' ', 'enforce_redirect auth_code_lifetime')));
+ if ($this->config['use_openid_connect']) {
+ if (!$this->storages['authorization_code'] instanceof OpenIDAuthorizationCodeInterface) {
+ throw new \LogicException('Your authorization_code storage must implement OAuth2\OpenID\Storage\AuthorizationCodeInterface to work when "use_openid_connect" is true');
+ }
+ $responseTypes['code'] = new OpenIDAuthorizationCodeResponseType($this->storages['authorization_code'], $config);
+ $responseTypes['code id_token'] = new CodeIdToken($responseTypes['code'], $responseTypes['id_token']);
+ } else {
+ $responseTypes['code'] = new AuthorizationCodeResponseType($this->storages['authorization_code'], $config);
+ }
+ }
+
+ if (count($responseTypes) == 0) {
+ throw new \LogicException('You must supply an array of response_types in the constructor or implement a OAuth2\Storage\AuthorizationCodeInterface storage object or set "allow_implicit" to true and implement a OAuth2\Storage\AccessTokenInterface storage object');
+ }
+
+ return $responseTypes;
+ }
+
+ protected function getDefaultGrantTypes()
+ {
+ $grantTypes = array();
+
+ if (isset($this->storages['user_credentials'])) {
+ $grantTypes['password'] = new UserCredentials($this->storages['user_credentials']);
+ }
+
+ if (isset($this->storages['client_credentials'])) {
+ $config = array_intersect_key($this->config, array('allow_credentials_in_request_body' => ''));
+ $grantTypes['client_credentials'] = new ClientCredentials($this->storages['client_credentials'], $config);
+ }
+
+ if (isset($this->storages['refresh_token'])) {
+ $config = array_intersect_key($this->config, array_flip(explode(' ', 'always_issue_new_refresh_token unset_refresh_token_after_use')));
+ $grantTypes['refresh_token'] = new RefreshToken($this->storages['refresh_token'], $config);
+ }
+
+ if (isset($this->storages['authorization_code'])) {
+ if ($this->config['use_openid_connect']) {
+ if (!$this->storages['authorization_code'] instanceof OpenIDAuthorizationCodeInterface) {
+ throw new \LogicException('Your authorization_code storage must implement OAuth2\OpenID\Storage\AuthorizationCodeInterface to work when "use_openid_connect" is true');
+ }
+ $grantTypes['authorization_code'] = new OpenIDAuthorizationCodeGrantType($this->storages['authorization_code']);
+ } else {
+ $grantTypes['authorization_code'] = new AuthorizationCode($this->storages['authorization_code']);
+ }
+ }
+
+ if (count($grantTypes) == 0) {
+ throw new \LogicException('Unable to build default grant types - You must supply an array of grant_types in the constructor');
+ }
+
+ return $grantTypes;
+ }
+
+ protected function getAccessTokenResponseType()
+ {
+ if (isset($this->responseTypes['token'])) {
+ return $this->responseTypes['token'];
+ }
+
+ if ($this->config['use_jwt_access_tokens']) {
+ return $this->createDefaultJwtAccessTokenResponseType();
+ }
+
+ return $this->createDefaultAccessTokenResponseType();
+ }
+
+ protected function getIdTokenResponseType()
+ {
+ if (isset($this->responseTypes['id_token'])) {
+ return $this->responseTypes['id_token'];
+ }
+
+ return $this->createDefaultIdTokenResponseType();
+ }
+
+ protected function getIdTokenTokenResponseType()
+ {
+ if (isset($this->responseTypes['id_token token'])) {
+ return $this->responseTypes['id_token token'];
+ }
+
+ return $this->createDefaultIdTokenTokenResponseType();
+ }
+
+ /**
+ * For Resource Controller
+ */
+ protected function createDefaultJwtAccessTokenStorage()
+ {
+ if (!isset($this->storages['public_key'])) {
+ throw new \LogicException('You must supply a storage object implementing OAuth2\Storage\PublicKeyInterface to use crypto tokens');
+ }
+ $tokenStorage = null;
+ if (!empty($this->config['store_encrypted_token_string']) && isset($this->storages['access_token'])) {
+ $tokenStorage = $this->storages['access_token'];
+ }
+ // wrap the access token storage as required.
+ return new JwtAccessTokenStorage($this->storages['public_key'], $tokenStorage);
+ }
+
+ /**
+ * For Authorize and Token Controllers
+ */
+ protected function createDefaultJwtAccessTokenResponseType()
+ {
+ if (!isset($this->storages['public_key'])) {
+ throw new \LogicException('You must supply a storage object implementing OAuth2\Storage\PublicKeyInterface to use crypto tokens');
+ }
+
+ $tokenStorage = null;
+ if (isset($this->storages['access_token'])) {
+ $tokenStorage = $this->storages['access_token'];
+ }
+
+ $refreshStorage = null;
+ if (isset($this->storages['refresh_token'])) {
+ $refreshStorage = $this->storages['refresh_token'];
+ }
+
+ $config = array_intersect_key($this->config, array_flip(explode(' ', 'store_encrypted_token_string issuer access_lifetime refresh_token_lifetime')));
+
+ return new JwtAccessToken($this->storages['public_key'], $tokenStorage, $refreshStorage, $config);
+ }
+
+ protected function createDefaultAccessTokenResponseType()
+ {
+ if (!isset($this->storages['access_token'])) {
+ throw new \LogicException('You must supply a response type implementing OAuth2\ResponseType\AccessTokenInterface, or a storage object implementing OAuth2\Storage\AccessTokenInterface to use the token server');
+ }
+
+ $refreshStorage = null;
+ if (isset($this->storages['refresh_token'])) {
+ $refreshStorage = $this->storages['refresh_token'];
+ }
+
+ $config = array_intersect_key($this->config, array_flip(explode(' ', 'access_lifetime refresh_token_lifetime')));
+ $config['token_type'] = $this->tokenType ? $this->tokenType->getTokenType() : $this->getDefaultTokenType()->getTokenType();
+
+ return new AccessToken($this->storages['access_token'], $refreshStorage, $config);
+ }
+
+ protected function createDefaultIdTokenResponseType()
+ {
+ if (!isset($this->storages['user_claims'])) {
+ throw new \LogicException('You must supply a storage object implementing OAuth2\OpenID\Storage\UserClaimsInterface to use openid connect');
+ }
+ if (!isset($this->storages['public_key'])) {
+ throw new \LogicException('You must supply a storage object implementing OAuth2\Storage\PublicKeyInterface to use openid connect');
+ }
+
+ $config = array_intersect_key($this->config, array_flip(explode(' ', 'issuer id_lifetime')));
+
+ return new IdToken($this->storages['user_claims'], $this->storages['public_key'], $config);
+ }
+
+ protected function createDefaultIdTokenTokenResponseType()
+ {
+ return new IdTokenToken($this->getAccessTokenResponseType(), $this->getIdTokenResponseType());
+ }
+
+ protected function validateOpenIdConnect()
+ {
+ $authCodeGrant = $this->getGrantType('authorization_code');
+ if (!empty($authCodeGrant) && !$authCodeGrant instanceof OpenIDAuthorizationCodeGrantType) {
+ throw new \InvalidArgumentException('You have enabled OpenID Connect, but supplied a grant type that does not support it.');
+ }
+ }
+
+ protected function normalizeResponseType($name)
+ {
+ // for multiple-valued response types - make them alphabetical
+ if (!empty($name) && false !== strpos($name, ' ')) {
+ $types = explode(' ', $name);
+ sort($types);
+ $name = implode(' ', $types);
+ }
+
+ return $name;
+ }
+
+ public function getResponse()
+ {
+ return $this->response;
+ }
+
+ public function getStorages()
+ {
+ return $this->storages;
+ }
+
+ public function getStorage($name)
+ {
+ return isset($this->storages[$name]) ? $this->storages[$name] : null;
+ }
+
+ public function getGrantTypes()
+ {
+ return $this->grantTypes;
+ }
+
+ public function getGrantType($name)
+ {
+ return isset($this->grantTypes[$name]) ? $this->grantTypes[$name] : null;
+ }
+
+ public function getResponseTypes()
+ {
+ return $this->responseTypes;
+ }
+
+ public function getResponseType($name)
+ {
+ // for multiple-valued response types - make them alphabetical
+ $name = $this->normalizeResponseType($name);
+
+ return isset($this->responseTypes[$name]) ? $this->responseTypes[$name] : null;
+ }
+
+ public function getTokenType()
+ {
+ return $this->tokenType;
+ }
+
+ public function getClientAssertionType()
+ {
+ return $this->clientAssertionType;
+ }
+
+ public function setConfig($name, $value)
+ {
+ $this->config[$name] = $value;
+ }
+
+ public function getConfig($name, $default = null)
+ {
+ return isset($this->config[$name]) ? $this->config[$name] : $default;
+ }
+}
diff --git a/library/oauth2/src/OAuth2/Storage/AccessTokenInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/AccessTokenInterface.php
index 1819158af..1819158af 100644
--- a/library/oauth2/src/OAuth2/Storage/AccessTokenInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/AccessTokenInterface.php
diff --git a/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/AuthorizationCodeInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/AuthorizationCodeInterface.php
new file mode 100644
index 000000000..edc7c70e5
--- /dev/null
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/AuthorizationCodeInterface.php
@@ -0,0 +1,86 @@
+<?php
+
+namespace OAuth2\Storage;
+
+/**
+ * Implement this interface to specify where the OAuth2 Server
+ * should get/save authorization codes for the "Authorization Code"
+ * grant type
+ *
+ * @author Brent Shaffer <bshafs at gmail dot com>
+ */
+interface AuthorizationCodeInterface
+{
+ /**
+ * The Authorization Code grant type supports a response type of "code".
+ *
+ * @var string
+ * @see http://tools.ietf.org/html/rfc6749#section-1.4.1
+ * @see http://tools.ietf.org/html/rfc6749#section-4.2
+ */
+ const RESPONSE_TYPE_CODE = "code";
+
+ /**
+ * Fetch authorization code data (probably the most common grant type).
+ *
+ * Retrieve the stored data for the given authorization code.
+ *
+ * Required for OAuth2::GRANT_TYPE_AUTH_CODE.
+ *
+ * @param $code
+ * Authorization code to be check with.
+ *
+ * @return
+ * An associative array as below, and NULL if the code is invalid
+ * @code
+ * return array(
+ * "client_id" => CLIENT_ID, // REQUIRED Stored client identifier
+ * "user_id" => USER_ID, // REQUIRED Stored user identifier
+ * "expires" => EXPIRES, // REQUIRED Stored expiration in unix timestamp
+ * "redirect_uri" => REDIRECT_URI, // REQUIRED Stored redirect URI
+ * "scope" => SCOPE, // OPTIONAL Stored scope values in space-separated string
+ * );
+ * @endcode
+ *
+ * @see http://tools.ietf.org/html/rfc6749#section-4.1
+ *
+ * @ingroup oauth2_section_4
+ */
+ public function getAuthorizationCode($code);
+
+ /**
+ * Take the provided authorization code values and store them somewhere.
+ *
+ * This function should be the storage counterpart to getAuthCode().
+ *
+ * If storage fails for some reason, we're not currently checking for
+ * any sort of success/failure, so you should bail out of the script
+ * and provide a descriptive fail message.
+ *
+ * Required for OAuth2::GRANT_TYPE_AUTH_CODE.
+ *
+ * @param string $code Authorization code to be stored.
+ * @param mixed $client_id Client identifier to be stored.
+ * @param mixed $user_id User identifier to be stored.
+ * @param string $redirect_uri Redirect URI(s) to be stored in a space-separated string.
+ * @param int $expires Expiration to be stored as a Unix timestamp.
+ * @param string $scope OPTIONAL Scopes to be stored in space-separated string.
+ *
+ * @ingroup oauth2_section_4
+ */
+ public function setAuthorizationCode($code, $client_id, $user_id, $redirect_uri, $expires, $scope = null);
+
+ /**
+ * once an Authorization Code is used, it must be expired
+ *
+ * @see http://tools.ietf.org/html/rfc6749#section-4.1.2
+ *
+ * The client MUST NOT use the authorization code
+ * more than once. If an authorization code is used more than
+ * once, the authorization server MUST deny the request and SHOULD
+ * revoke (when possible) all tokens previously issued based on
+ * that authorization code
+ *
+ */
+ public function expireAuthorizationCode($code);
+}
diff --git a/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/Cassandra.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/Cassandra.php
new file mode 100644
index 000000000..c5048c08d
--- /dev/null
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/Cassandra.php
@@ -0,0 +1,480 @@
+<?php
+
+namespace OAuth2\Storage;
+
+use phpcassa\ColumnFamily;
+use phpcassa\ColumnSlice;
+use phpcassa\Connection\ConnectionPool;
+use OAuth2\OpenID\Storage\UserClaimsInterface;
+use OAuth2\OpenID\Storage\AuthorizationCodeInterface as OpenIDAuthorizationCodeInterface;
+
+/**
+ * Cassandra storage for all storage types
+ *
+ * To use, install "thobbs/phpcassa" via composer
+ * <code>
+ * composer require thobbs/phpcassa:dev-master
+ * </code>
+ *
+ * Once this is done, instantiate the
+ * <code>
+ * $cassandra = new \phpcassa\Connection\ConnectionPool('oauth2_server', array('127.0.0.1:9160'));
+ * </code>
+ *
+ * Then, register the storage client:
+ * <code>
+ * $storage = new OAuth2\Storage\Cassandra($cassandra);
+ * $storage->setClientDetails($client_id, $client_secret, $redirect_uri);
+ * </code>
+ *
+ * @see test/lib/OAuth2/Storage/Bootstrap::getCassandraStorage
+ */
+class Cassandra implements AuthorizationCodeInterface,
+ AccessTokenInterface,
+ ClientCredentialsInterface,
+ UserCredentialsInterface,
+ RefreshTokenInterface,
+ JwtBearerInterface,
+ ScopeInterface,
+ PublicKeyInterface,
+ UserClaimsInterface,
+ OpenIDAuthorizationCodeInterface
+{
+
+ private $cache;
+
+ /* The cassandra client */
+ protected $cassandra;
+
+ /* Configuration array */
+ protected $config;
+
+ /**
+ * Cassandra Storage! uses phpCassa
+ *
+ * @param \phpcassa\ConnectionPool $cassandra
+ * @param array $config
+ */
+ public function __construct($connection = array(), array $config = array())
+ {
+ if ($connection instanceof ConnectionPool) {
+ $this->cassandra = $connection;
+ } else {
+ if (!is_array($connection)) {
+ throw new \InvalidArgumentException('First argument to OAuth2\Storage\Cassandra must be an instance of phpcassa\Connection\ConnectionPool or a configuration array');
+ }
+ $connection = array_merge(array(
+ 'keyspace' => 'oauth2',
+ 'servers' => null,
+ ), $connection);
+
+ $this->cassandra = new ConnectionPool($connection['keyspace'], $connection['servers']);
+ }
+
+ $this->config = array_merge(array(
+ // cassandra config
+ 'column_family' => 'auth',
+
+ // key names
+ 'client_key' => 'oauth_clients:',
+ 'access_token_key' => 'oauth_access_tokens:',
+ 'refresh_token_key' => 'oauth_refresh_tokens:',
+ 'code_key' => 'oauth_authorization_codes:',
+ 'user_key' => 'oauth_users:',
+ 'jwt_key' => 'oauth_jwt:',
+ 'scope_key' => 'oauth_scopes:',
+ 'public_key_key' => 'oauth_public_keys:',
+ ), $config);
+ }
+
+ protected function getValue($key)
+ {
+ if (isset($this->cache[$key])) {
+ return $this->cache[$key];
+ }
+ $cf = new ColumnFamily($this->cassandra, $this->config['column_family']);
+
+ try {
+ $value = $cf->get($key, new ColumnSlice("", ""));
+ $value = array_shift($value);
+ } catch (\cassandra\NotFoundException $e) {
+ return false;
+ }
+
+ return json_decode($value, true);
+ }
+
+ protected function setValue($key, $value, $expire = 0)
+ {
+ $this->cache[$key] = $value;
+
+ $cf = new ColumnFamily($this->cassandra, $this->config['column_family']);
+
+ $str = json_encode($value);
+ if ($expire > 0) {
+ try {
+ $seconds = $expire - time();
+ // __data key set as C* requires a field, note: max TTL can only be 630720000 seconds
+ $cf->insert($key, array('__data' => $str), null, $seconds);
+ } catch (\Exception $e) {
+ return false;
+ }
+ } else {
+ try {
+ // __data key set as C* requires a field
+ $cf->insert($key, array('__data' => $str));
+ } catch (\Exception $e) {
+ return false;
+ }
+ }
+
+ return true;
+ }
+
+ protected function expireValue($key)
+ {
+ unset($this->cache[$key]);
+
+ $cf = new ColumnFamily($this->cassandra, $this->config['column_family']);
+
+ if ($cf->get_count($key) > 0) {
+ try {
+ // __data key set as C* requires a field
+ $cf->remove($key, array('__data'));
+ } catch (\Exception $e) {
+ return false;
+ }
+
+ return true;
+ }
+
+ return false;
+ }
+
+ /* AuthorizationCodeInterface */
+ public function getAuthorizationCode($code)
+ {
+ return $this->getValue($this->config['code_key'] . $code);
+ }
+
+ public function setAuthorizationCode($authorization_code, $client_id, $user_id, $redirect_uri, $expires, $scope = null, $id_token = null)
+ {
+ return $this->setValue(
+ $this->config['code_key'] . $authorization_code,
+ compact('authorization_code', 'client_id', 'user_id', 'redirect_uri', 'expires', 'scope', 'id_token'),
+ $expires
+ );
+ }
+
+ public function expireAuthorizationCode($code)
+ {
+ $key = $this->config['code_key'] . $code;
+ unset($this->cache[$key]);
+
+ return $this->expireValue($key);
+ }
+
+ /* UserCredentialsInterface */
+ public function checkUserCredentials($username, $password)
+ {
+ if ($user = $this->getUser($username)) {
+ return $this->checkPassword($user, $password);
+ }
+
+ return false;
+ }
+
+ // plaintext passwords are bad! Override this for your application
+ protected function checkPassword($user, $password)
+ {
+ return $user['password'] == $this->hashPassword($password);
+ }
+
+ // use a secure hashing algorithm when storing passwords. Override this for your application
+ protected function hashPassword($password)
+ {
+ return sha1($password);
+ }
+
+ public function getUserDetails($username)
+ {
+ return $this->getUser($username);
+ }
+
+ public function getUser($username)
+ {
+ if (!$userInfo = $this->getValue($this->config['user_key'] . $username)) {
+ return false;
+ }
+
+ // the default behavior is to use "username" as the user_id
+ return array_merge(array(
+ 'user_id' => $username,
+ ), $userInfo);
+ }
+
+ public function setUser($username, $password, $first_name = null, $last_name = null)
+ {
+ $password = $this->hashPassword($password);
+
+ return $this->setValue(
+ $this->config['user_key'] . $username,
+ compact('username', 'password', 'first_name', 'last_name')
+ );
+ }
+
+ /* ClientCredentialsInterface */
+ public function checkClientCredentials($client_id, $client_secret = null)
+ {
+ if (!$client = $this->getClientDetails($client_id)) {
+ return false;
+ }
+
+ return isset($client['client_secret'])
+ && $client['client_secret'] == $client_secret;
+ }
+
+ public function isPublicClient($client_id)
+ {
+ if (!$client = $this->getClientDetails($client_id)) {
+ return false;
+ }
+
+ return empty($client['client_secret']);
+ }
+
+ /* ClientInterface */
+ public function getClientDetails($client_id)
+ {
+ return $this->getValue($this->config['client_key'] . $client_id);
+ }
+
+ public function setClientDetails($client_id, $client_secret = null, $redirect_uri = null, $grant_types = null, $scope = null, $user_id = null)
+ {
+ return $this->setValue(
+ $this->config['client_key'] . $client_id,
+ compact('client_id', 'client_secret', 'redirect_uri', 'grant_types', 'scope', 'user_id')
+ );
+ }
+
+ public function checkRestrictedGrantType($client_id, $grant_type)
+ {
+ $details = $this->getClientDetails($client_id);
+ if (isset($details['grant_types'])) {
+ $grant_types = explode(' ', $details['grant_types']);
+
+ return in_array($grant_type, (array) $grant_types);
+ }
+
+ // if grant_types are not defined, then none are restricted
+ return true;
+ }
+
+ /* RefreshTokenInterface */
+ public function getRefreshToken($refresh_token)
+ {
+ return $this->getValue($this->config['refresh_token_key'] . $refresh_token);
+ }
+
+ public function setRefreshToken($refresh_token, $client_id, $user_id, $expires, $scope = null)
+ {
+ return $this->setValue(
+ $this->config['refresh_token_key'] . $refresh_token,
+ compact('refresh_token', 'client_id', 'user_id', 'expires', 'scope'),
+ $expires
+ );
+ }
+
+ public function unsetRefreshToken($refresh_token)
+ {
+ return $this->expireValue($this->config['refresh_token_key'] . $refresh_token);
+ }
+
+ /* AccessTokenInterface */
+ public function getAccessToken($access_token)
+ {
+ return $this->getValue($this->config['access_token_key'].$access_token);
+ }
+
+ public function setAccessToken($access_token, $client_id, $user_id, $expires, $scope = null)
+ {
+ return $this->setValue(
+ $this->config['access_token_key'].$access_token,
+ compact('access_token', 'client_id', 'user_id', 'expires', 'scope'),
+ $expires
+ );
+ }
+
+ public function unsetAccessToken($access_token)
+ {
+ return $this->expireValue($this->config['access_token_key'] . $access_token);
+ }
+
+ /* ScopeInterface */
+ public function scopeExists($scope)
+ {
+ $scope = explode(' ', $scope);
+
+ $result = $this->getValue($this->config['scope_key'].'supported:global');
+
+ $supportedScope = explode(' ', (string) $result);
+
+ return (count(array_diff($scope, $supportedScope)) == 0);
+ }
+
+ public function getDefaultScope($client_id = null)
+ {
+ if (is_null($client_id) || !$result = $this->getValue($this->config['scope_key'].'default:'.$client_id)) {
+ $result = $this->getValue($this->config['scope_key'].'default:global');
+ }
+
+ return $result;
+ }
+
+ public function setScope($scope, $client_id = null, $type = 'supported')
+ {
+ if (!in_array($type, array('default', 'supported'))) {
+ throw new \InvalidArgumentException('"$type" must be one of "default", "supported"');
+ }
+
+ if (is_null($client_id)) {
+ $key = $this->config['scope_key'].$type.':global';
+ } else {
+ $key = $this->config['scope_key'].$type.':'.$client_id;
+ }
+
+ return $this->setValue($key, $scope);
+ }
+
+ /*JWTBearerInterface */
+ public function getClientKey($client_id, $subject)
+ {
+ if (!$jwt = $this->getValue($this->config['jwt_key'] . $client_id)) {
+ return false;
+ }
+
+ if (isset($jwt['subject']) && $jwt['subject'] == $subject ) {
+ return $jwt['key'];
+ }
+
+ return null;
+ }
+
+ public function setClientKey($client_id, $key, $subject = null)
+ {
+ return $this->setValue($this->config['jwt_key'] . $client_id, array(
+ 'key' => $key,
+ 'subject' => $subject
+ ));
+ }
+
+ /*ScopeInterface */
+ public function getClientScope($client_id)
+ {
+ if (!$clientDetails = $this->getClientDetails($client_id)) {
+ return false;
+ }
+
+ if (isset($clientDetails['scope'])) {
+ return $clientDetails['scope'];
+ }
+
+ return null;
+ }
+
+ public function getJti($client_id, $subject, $audience, $expiration, $jti)
+ {
+ //TODO: Needs cassandra implementation.
+ throw new \Exception('getJti() for the Cassandra driver is currently unimplemented.');
+ }
+
+ public function setJti($client_id, $subject, $audience, $expiration, $jti)
+ {
+ //TODO: Needs cassandra implementation.
+ throw new \Exception('setJti() for the Cassandra driver is currently unimplemented.');
+ }
+
+ /* PublicKeyInterface */
+ public function getPublicKey($client_id = '')
+ {
+ $public_key = $this->getValue($this->config['public_key_key'] . $client_id);
+ if (is_array($public_key)) {
+ return $public_key['public_key'];
+ }
+ $public_key = $this->getValue($this->config['public_key_key']);
+ if (is_array($public_key)) {
+ return $public_key['public_key'];
+ }
+ }
+
+ public function getPrivateKey($client_id = '')
+ {
+ $public_key = $this->getValue($this->config['public_key_key'] . $client_id);
+ if (is_array($public_key)) {
+ return $public_key['private_key'];
+ }
+ $public_key = $this->getValue($this->config['public_key_key']);
+ if (is_array($public_key)) {
+ return $public_key['private_key'];
+ }
+ }
+
+ public function getEncryptionAlgorithm($client_id = null)
+ {
+ $public_key = $this->getValue($this->config['public_key_key'] . $client_id);
+ if (is_array($public_key)) {
+ return $public_key['encryption_algorithm'];
+ }
+ $public_key = $this->getValue($this->config['public_key_key']);
+ if (is_array($public_key)) {
+ return $public_key['encryption_algorithm'];
+ }
+
+ return 'RS256';
+ }
+
+ /* UserClaimsInterface */
+ public function getUserClaims($user_id, $claims)
+ {
+ $userDetails = $this->getUserDetails($user_id);
+ if (!is_array($userDetails)) {
+ return false;
+ }
+
+ $claims = explode(' ', trim($claims));
+ $userClaims = array();
+
+ // for each requested claim, if the user has the claim, set it in the response
+ $validClaims = explode(' ', self::VALID_CLAIMS);
+ foreach ($validClaims as $validClaim) {
+ if (in_array($validClaim, $claims)) {
+ if ($validClaim == 'address') {
+ // address is an object with subfields
+ $userClaims['address'] = $this->getUserClaim($validClaim, $userDetails['address'] ?: $userDetails);
+ } else {
+ $userClaims = array_merge($userClaims, $this->getUserClaim($validClaim, $userDetails));
+ }
+ }
+ }
+
+ return $userClaims;
+ }
+
+ protected function getUserClaim($claim, $userDetails)
+ {
+ $userClaims = array();
+ $claimValuesString = constant(sprintf('self::%s_CLAIM_VALUES', strtoupper($claim)));
+ $claimValues = explode(' ', $claimValuesString);
+
+ foreach ($claimValues as $value) {
+ if ($value == 'email_verified') {
+ $userClaims[$value] = $userDetails[$value]=='true' ? true : false;
+ } else {
+ $userClaims[$value] = isset($userDetails[$value]) ? $userDetails[$value] : null;
+ }
+ }
+
+ return $userClaims;
+ }
+
+}
diff --git a/library/oauth2/src/OAuth2/Storage/ClientCredentialsInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/ClientCredentialsInterface.php
index 3318c6966..3318c6966 100644
--- a/library/oauth2/src/OAuth2/Storage/ClientCredentialsInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/ClientCredentialsInterface.php
diff --git a/library/oauth2/src/OAuth2/Storage/ClientInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/ClientInterface.php
index 09a5bffc1..09a5bffc1 100644
--- a/library/oauth2/src/OAuth2/Storage/ClientInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/ClientInterface.php
diff --git a/library/oauth2/src/OAuth2/Storage/CouchbaseDB.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/CouchbaseDB.php
index 1eb55f027..1eb55f027 100755
--- a/library/oauth2/src/OAuth2/Storage/CouchbaseDB.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/CouchbaseDB.php
diff --git a/library/oauth2/src/OAuth2/Storage/DynamoDB.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/DynamoDB.php
index 8347ab258..8347ab258 100644
--- a/library/oauth2/src/OAuth2/Storage/DynamoDB.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/DynamoDB.php
diff --git a/library/oauth2/src/OAuth2/Storage/JwtAccessToken.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/JwtAccessToken.php
index 75b49d301..75b49d301 100644
--- a/library/oauth2/src/OAuth2/Storage/JwtAccessToken.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/JwtAccessToken.php
diff --git a/library/oauth2/src/OAuth2/Storage/JwtAccessTokenInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/JwtAccessTokenInterface.php
index 3abb2aa2d..3abb2aa2d 100644
--- a/library/oauth2/src/OAuth2/Storage/JwtAccessTokenInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/JwtAccessTokenInterface.php
diff --git a/library/oauth2/src/OAuth2/Storage/JwtBearerInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/JwtBearerInterface.php
index c83aa72ea..c83aa72ea 100644
--- a/library/oauth2/src/OAuth2/Storage/JwtBearerInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/JwtBearerInterface.php
diff --git a/library/oauth2/src/OAuth2/Storage/Memory.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/Memory.php
index 42d833ccb..42d833ccb 100644
--- a/library/oauth2/src/OAuth2/Storage/Memory.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/Memory.php
diff --git a/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/Mongo.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/Mongo.php
new file mode 100644
index 000000000..eea06e315
--- /dev/null
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/Mongo.php
@@ -0,0 +1,392 @@
+<?php
+
+namespace OAuth2\Storage;
+
+use OAuth2\OpenID\Storage\AuthorizationCodeInterface as OpenIDAuthorizationCodeInterface;
+
+/**
+ * Simple MongoDB storage for all storage types
+ *
+ * NOTE: This class is meant to get users started
+ * quickly. If your application requires further
+ * customization, extend this class or create your own.
+ *
+ * NOTE: Passwords are stored in plaintext, which is never
+ * a good idea. Be sure to override this for your application
+ *
+ * @author Julien Chaumond <chaumond@gmail.com>
+ */
+class Mongo implements AuthorizationCodeInterface,
+ AccessTokenInterface,
+ ClientCredentialsInterface,
+ UserCredentialsInterface,
+ RefreshTokenInterface,
+ JwtBearerInterface,
+ PublicKeyInterface,
+ OpenIDAuthorizationCodeInterface
+{
+ protected $db;
+ protected $config;
+
+ public function __construct($connection, $config = array())
+ {
+ if ($connection instanceof \MongoDB) {
+ $this->db = $connection;
+ } else {
+ if (!is_array($connection)) {
+ throw new \InvalidArgumentException('First argument to OAuth2\Storage\Mongo must be an instance of MongoDB or a configuration array');
+ }
+ $server = sprintf('mongodb://%s:%d', $connection['host'], $connection['port']);
+ $m = new \MongoClient($server);
+ $this->db = $m->{$connection['database']};
+ }
+
+ $this->config = array_merge(array(
+ 'client_table' => 'oauth_clients',
+ 'access_token_table' => 'oauth_access_tokens',
+ 'refresh_token_table' => 'oauth_refresh_tokens',
+ 'code_table' => 'oauth_authorization_codes',
+ 'user_table' => 'oauth_users',
+ 'key_table' => 'oauth_keys',
+ 'jwt_table' => 'oauth_jwt',
+ ), $config);
+ }
+
+ // Helper function to access a MongoDB collection by `type`:
+ protected function collection($name)
+ {
+ return $this->db->{$this->config[$name]};
+ }
+
+ /* ClientCredentialsInterface */
+ public function checkClientCredentials($client_id, $client_secret = null)
+ {
+ if ($result = $this->collection('client_table')->findOne(array('client_id' => $client_id))) {
+ return $result['client_secret'] == $client_secret;
+ }
+
+ return false;
+ }
+
+ public function isPublicClient($client_id)
+ {
+ if (!$result = $this->collection('client_table')->findOne(array('client_id' => $client_id))) {
+ return false;
+ }
+
+ return empty($result['client_secret']);
+ }
+
+ /* ClientInterface */
+ public function getClientDetails($client_id)
+ {
+ $result = $this->collection('client_table')->findOne(array('client_id' => $client_id));
+
+ return is_null($result) ? false : $result;
+ }
+
+ public function setClientDetails($client_id, $client_secret = null, $redirect_uri = null, $grant_types = null, $scope = null, $user_id = null)
+ {
+ if ($this->getClientDetails($client_id)) {
+ $this->collection('client_table')->update(
+ array('client_id' => $client_id),
+ array('$set' => array(
+ 'client_secret' => $client_secret,
+ 'redirect_uri' => $redirect_uri,
+ 'grant_types' => $grant_types,
+ 'scope' => $scope,
+ 'user_id' => $user_id,
+ ))
+ );
+ } else {
+ $client = array(
+ 'client_id' => $client_id,
+ 'client_secret' => $client_secret,
+ 'redirect_uri' => $redirect_uri,
+ 'grant_types' => $grant_types,
+ 'scope' => $scope,
+ 'user_id' => $user_id,
+ );
+ $this->collection('client_table')->insert($client);
+ }
+
+ return true;
+ }
+
+ public function checkRestrictedGrantType($client_id, $grant_type)
+ {
+ $details = $this->getClientDetails($client_id);
+ if (isset($details['grant_types'])) {
+ $grant_types = explode(' ', $details['grant_types']);
+
+ return in_array($grant_type, $grant_types);
+ }
+
+ // if grant_types are not defined, then none are restricted
+ return true;
+ }
+
+ /* AccessTokenInterface */
+ public function getAccessToken($access_token)
+ {
+ $token = $this->collection('access_token_table')->findOne(array('access_token' => $access_token));
+
+ return is_null($token) ? false : $token;
+ }
+
+ public function setAccessToken($access_token, $client_id, $user_id, $expires, $scope = null)
+ {
+ // if it exists, update it.
+ if ($this->getAccessToken($access_token)) {
+ $this->collection('access_token_table')->update(
+ array('access_token' => $access_token),
+ array('$set' => array(
+ 'client_id' => $client_id,
+ 'expires' => $expires,
+ 'user_id' => $user_id,
+ 'scope' => $scope
+ ))
+ );
+ } else {
+ $token = array(
+ 'access_token' => $access_token,
+ 'client_id' => $client_id,
+ 'expires' => $expires,
+ 'user_id' => $user_id,
+ 'scope' => $scope
+ );
+ $this->collection('access_token_table')->insert($token);
+ }
+
+ return true;
+ }
+
+ public function unsetAccessToken($access_token)
+ {
+ $result = $this->collection('access_token_table')->remove(array(
+ 'access_token' => $access_token
+ ), array('w' => 1));
+
+ return $result['n'] > 0;
+ }
+
+
+ /* AuthorizationCodeInterface */
+ public function getAuthorizationCode($code)
+ {
+ $code = $this->collection('code_table')->findOne(array('authorization_code' => $code));
+
+ return is_null($code) ? false : $code;
+ }
+
+ public function setAuthorizationCode($code, $client_id, $user_id, $redirect_uri, $expires, $scope = null, $id_token = null)
+ {
+ // if it exists, update it.
+ if ($this->getAuthorizationCode($code)) {
+ $this->collection('code_table')->update(
+ array('authorization_code' => $code),
+ array('$set' => array(
+ 'client_id' => $client_id,
+ 'user_id' => $user_id,
+ 'redirect_uri' => $redirect_uri,
+ 'expires' => $expires,
+ 'scope' => $scope,
+ 'id_token' => $id_token,
+ ))
+ );
+ } else {
+ $token = array(
+ 'authorization_code' => $code,
+ 'client_id' => $client_id,
+ 'user_id' => $user_id,
+ 'redirect_uri' => $redirect_uri,
+ 'expires' => $expires,
+ 'scope' => $scope,
+ 'id_token' => $id_token,
+ );
+ $this->collection('code_table')->insert($token);
+ }
+
+ return true;
+ }
+
+ public function expireAuthorizationCode($code)
+ {
+ $this->collection('code_table')->remove(array('authorization_code' => $code));
+
+ return true;
+ }
+
+ /* UserCredentialsInterface */
+ public function checkUserCredentials($username, $password)
+ {
+ if ($user = $this->getUser($username)) {
+ return $this->checkPassword($user, $password);
+ }
+
+ return false;
+ }
+
+ public function getUserDetails($username)
+ {
+ if ($user = $this->getUser($username)) {
+ $user['user_id'] = $user['username'];
+ }
+
+ return $user;
+ }
+
+ /* RefreshTokenInterface */
+ public function getRefreshToken($refresh_token)
+ {
+ $token = $this->collection('refresh_token_table')->findOne(array('refresh_token' => $refresh_token));
+
+ return is_null($token) ? false : $token;
+ }
+
+ public function setRefreshToken($refresh_token, $client_id, $user_id, $expires, $scope = null)
+ {
+ $token = array(
+ 'refresh_token' => $refresh_token,
+ 'client_id' => $client_id,
+ 'user_id' => $user_id,
+ 'expires' => $expires,
+ 'scope' => $scope
+ );
+ $this->collection('refresh_token_table')->insert($token);
+
+ return true;
+ }
+
+ public function unsetRefreshToken($refresh_token)
+ {
+ $result = $this->collection('refresh_token_table')->remove(array(
+ 'refresh_token' => $refresh_token
+ ), array('w' => 1));
+
+ return $result['n'] > 0;
+ }
+
+ // plaintext passwords are bad! Override this for your application
+ protected function checkPassword($user, $password)
+ {
+ return $user['password'] == $password;
+ }
+
+ public function getUser($username)
+ {
+ $result = $this->collection('user_table')->findOne(array('username' => $username));
+
+ return is_null($result) ? false : $result;
+ }
+
+ public function setUser($username, $password, $firstName = null, $lastName = null)
+ {
+ if ($this->getUser($username)) {
+ $this->collection('user_table')->update(
+ array('username' => $username),
+ array('$set' => array(
+ 'password' => $password,
+ 'first_name' => $firstName,
+ 'last_name' => $lastName
+ ))
+ );
+ } else {
+ $user = array(
+ 'username' => $username,
+ 'password' => $password,
+ 'first_name' => $firstName,
+ 'last_name' => $lastName
+ );
+ $this->collection('user_table')->insert($user);
+ }
+
+ return true;
+ }
+
+ public function getClientKey($client_id, $subject)
+ {
+ $result = $this->collection('jwt_table')->findOne(array(
+ 'client_id' => $client_id,
+ 'subject' => $subject
+ ));
+
+ return is_null($result) ? false : $result['key'];
+ }
+
+ public function getClientScope($client_id)
+ {
+ if (!$clientDetails = $this->getClientDetails($client_id)) {
+ return false;
+ }
+
+ if (isset($clientDetails['scope'])) {
+ return $clientDetails['scope'];
+ }
+
+ return null;
+ }
+
+ public function getJti($client_id, $subject, $audience, $expiration, $jti)
+ {
+ //TODO: Needs mongodb implementation.
+ throw new \Exception('getJti() for the MongoDB driver is currently unimplemented.');
+ }
+
+ public function setJti($client_id, $subject, $audience, $expiration, $jti)
+ {
+ //TODO: Needs mongodb implementation.
+ throw new \Exception('setJti() for the MongoDB driver is currently unimplemented.');
+ }
+
+ public function getPublicKey($client_id = null)
+ {
+ if ($client_id) {
+ $result = $this->collection('key_table')->findOne(array(
+ 'client_id' => $client_id
+ ));
+ if ($result) {
+ return $result['public_key'];
+ }
+ }
+
+ $result = $this->collection('key_table')->findOne(array(
+ 'client_id' => null
+ ));
+ return is_null($result) ? false : $result['public_key'];
+ }
+
+ public function getPrivateKey($client_id = null)
+ {
+ if ($client_id) {
+ $result = $this->collection('key_table')->findOne(array(
+ 'client_id' => $client_id
+ ));
+ if ($result) {
+ return $result['private_key'];
+ }
+ }
+
+ $result = $this->collection('key_table')->findOne(array(
+ 'client_id' => null
+ ));
+ return is_null($result) ? false : $result['private_key'];
+ }
+
+ public function getEncryptionAlgorithm($client_id = null)
+ {
+ if ($client_id) {
+ $result = $this->collection('key_table')->findOne(array(
+ 'client_id' => $client_id
+ ));
+ if ($result) {
+ return $result['encryption_algorithm'];
+ }
+ }
+
+ $result = $this->collection('key_table')->findOne(array(
+ 'client_id' => null
+ ));
+ return is_null($result) ? 'RS256' : $result['encryption_algorithm'];
+ }
+}
diff --git a/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/MongoDB.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/MongoDB.php
new file mode 100644
index 000000000..64f740fc1
--- /dev/null
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/MongoDB.php
@@ -0,0 +1,380 @@
+<?php
+
+namespace OAuth2\Storage;
+
+use MongoDB\Client;
+use MongoDB\Database;
+use OAuth2\OpenID\Storage\AuthorizationCodeInterface as OpenIDAuthorizationCodeInterface;
+
+/**
+ * Simple MongoDB storage for all storage types
+ *
+ * NOTE: This class is meant to get users started
+ * quickly. If your application requires further
+ * customization, extend this class or create your own.
+ *
+ * NOTE: Passwords are stored in plaintext, which is never
+ * a good idea. Be sure to override this for your application
+ *
+ * @author Julien Chaumond <chaumond@gmail.com>
+ */
+class MongoDB implements AuthorizationCodeInterface,
+ UserCredentialsInterface,
+ AccessTokenInterface,
+ ClientCredentialsInterface,
+ RefreshTokenInterface,
+ JwtBearerInterface,
+ PublicKeyInterface,
+ OpenIDAuthorizationCodeInterface
+{
+ protected $db;
+ protected $config;
+
+ public function __construct($connection, $config = array())
+ {
+ if ($connection instanceof Database) {
+ $this->db = $connection;
+ } else {
+ if (!is_array($connection)) {
+ throw new \InvalidArgumentException('First argument to OAuth2\Storage\Mongo must be an instance of MongoDB\Database or a configuration array');
+ }
+ $server = sprintf('mongodb://%s:%d', $connection['host'], $connection['port']);
+ $m = new Client($server);
+ $this->db = $m->selectDatabase($connection['database']);
+ }
+ $this->config = array_merge(array(
+ 'client_table' => 'oauth_clients',
+ 'access_token_table' => 'oauth_access_tokens',
+ 'refresh_token_table' => 'oauth_refresh_tokens',
+ 'code_table' => 'oauth_authorization_codes',
+ 'user_table' => 'oauth_users',
+ 'jwt_table' => 'oauth_jwt',
+ 'jti_table' => 'oauth_jti',
+ 'scope_table' => 'oauth_scopes',
+ 'key_table' => 'oauth_keys',
+ ), $config);
+ }
+
+ /* ClientCredentialsInterface */
+ public function checkClientCredentials($client_id, $client_secret = null)
+ {
+ if ($result = $this->collection('client_table')->findOne(array('client_id' => $client_id))) {
+ return $result['client_secret'] == $client_secret;
+ }
+ return false;
+ }
+
+ public function isPublicClient($client_id)
+ {
+ if (!$result = $this->collection('client_table')->findOne(array('client_id' => $client_id))) {
+ return false;
+ }
+ return empty($result['client_secret']);
+ }
+
+ /* ClientInterface */
+ public function getClientDetails($client_id)
+ {
+ $result = $this->collection('client_table')->findOne(array('client_id' => $client_id));
+ return is_null($result) ? false : $result;
+ }
+
+ public function setClientDetails($client_id, $client_secret = null, $redirect_uri = null, $grant_types = null, $scope = null, $user_id = null)
+ {
+ if ($this->getClientDetails($client_id)) {
+ $result = $this->collection('client_table')->updateOne(
+ array('client_id' => $client_id),
+ array('$set' => array(
+ 'client_secret' => $client_secret,
+ 'redirect_uri' => $redirect_uri,
+ 'grant_types' => $grant_types,
+ 'scope' => $scope,
+ 'user_id' => $user_id,
+ ))
+ );
+ return $result->getMatchedCount() > 0;
+ }
+ $client = array(
+ 'client_id' => $client_id,
+ 'client_secret' => $client_secret,
+ 'redirect_uri' => $redirect_uri,
+ 'grant_types' => $grant_types,
+ 'scope' => $scope,
+ 'user_id' => $user_id,
+ );
+ $result = $this->collection('client_table')->insertOne($client);
+ return $result->getInsertedCount() > 0;
+ }
+
+ public function checkRestrictedGrantType($client_id, $grant_type)
+ {
+ $details = $this->getClientDetails($client_id);
+ if (isset($details['grant_types'])) {
+ $grant_types = explode(' ', $details['grant_types']);
+ return in_array($grant_type, $grant_types);
+ }
+ // if grant_types are not defined, then none are restricted
+ return true;
+ }
+
+ /* AccessTokenInterface */
+ public function getAccessToken($access_token)
+ {
+ $token = $this->collection('access_token_table')->findOne(array('access_token' => $access_token));
+ return is_null($token) ? false : $token;
+ }
+
+ public function setAccessToken($access_token, $client_id, $user_id, $expires, $scope = null)
+ {
+ // if it exists, update it.
+ if ($this->getAccessToken($access_token)) {
+ $result = $this->collection('access_token_table')->updateOne(
+ array('access_token' => $access_token),
+ array('$set' => array(
+ 'client_id' => $client_id,
+ 'expires' => $expires,
+ 'user_id' => $user_id,
+ 'scope' => $scope
+ ))
+ );
+ return $result->getMatchedCount() > 0;
+ }
+ $token = array(
+ 'access_token' => $access_token,
+ 'client_id' => $client_id,
+ 'expires' => $expires,
+ 'user_id' => $user_id,
+ 'scope' => $scope
+ );
+ $result = $this->collection('access_token_table')->insertOne($token);
+ return $result->getInsertedCount() > 0;
+ }
+
+ public function unsetAccessToken($access_token)
+ {
+ $result = $this->collection('access_token_table')->deleteOne(array(
+ 'access_token' => $access_token
+ ));
+ return $result->getDeletedCount() > 0;
+ }
+
+ /* AuthorizationCodeInterface */
+ public function getAuthorizationCode($code)
+ {
+ $code = $this->collection('code_table')->findOne(array(
+ 'authorization_code' => $code
+ ));
+ return is_null($code) ? false : $code;
+ }
+
+ public function setAuthorizationCode($code, $client_id, $user_id, $redirect_uri, $expires, $scope = null, $id_token = null)
+ {
+ // if it exists, update it.
+ if ($this->getAuthorizationCode($code)) {
+ $result = $this->collection('code_table')->updateOne(
+ array('authorization_code' => $code),
+ array('$set' => array(
+ 'client_id' => $client_id,
+ 'user_id' => $user_id,
+ 'redirect_uri' => $redirect_uri,
+ 'expires' => $expires,
+ 'scope' => $scope,
+ 'id_token' => $id_token,
+ ))
+ );
+ return $result->getMatchedCount() > 0;
+ }
+ $token = array(
+ 'authorization_code' => $code,
+ 'client_id' => $client_id,
+ 'user_id' => $user_id,
+ 'redirect_uri' => $redirect_uri,
+ 'expires' => $expires,
+ 'scope' => $scope,
+ 'id_token' => $id_token,
+ );
+ $result = $this->collection('code_table')->insertOne($token);
+ return $result->getInsertedCount() > 0;
+ }
+
+ public function expireAuthorizationCode($code)
+ {
+ $result = $this->collection('code_table')->deleteOne(array(
+ 'authorization_code' => $code
+ ));
+ return $result->getDeletedCount() > 0;
+ }
+
+ /* UserCredentialsInterface */
+ public function checkUserCredentials($username, $password)
+ {
+ if ($user = $this->getUser($username)) {
+ return $this->checkPassword($user, $password);
+ }
+ return false;
+ }
+
+ public function getUserDetails($username)
+ {
+ if ($user = $this->getUser($username)) {
+ $user['user_id'] = $user['username'];
+ }
+ return $user;
+ }
+
+ /* RefreshTokenInterface */
+ public function getRefreshToken($refresh_token)
+ {
+ $token = $this->collection('refresh_token_table')->findOne(array(
+ 'refresh_token' => $refresh_token
+ ));
+ return is_null($token) ? false : $token;
+ }
+
+ public function setRefreshToken($refresh_token, $client_id, $user_id, $expires, $scope = null)
+ {
+ $token = array(
+ 'refresh_token' => $refresh_token,
+ 'client_id' => $client_id,
+ 'user_id' => $user_id,
+ 'expires' => $expires,
+ 'scope' => $scope
+ );
+ $result = $this->collection('refresh_token_table')->insertOne($token);
+ return $result->getInsertedCount() > 0;
+ }
+
+ public function unsetRefreshToken($refresh_token)
+ {
+ $result = $this->collection('refresh_token_table')->deleteOne(array(
+ 'refresh_token' => $refresh_token
+ ));
+ return $result->getDeletedCount() > 0;
+ }
+
+ // plaintext passwords are bad! Override this for your application
+ protected function checkPassword($user, $password)
+ {
+ return $user['password'] == $password;
+ }
+
+ public function getUser($username)
+ {
+ $result = $this->collection('user_table')->findOne(array('username' => $username));
+ return is_null($result) ? false : $result;
+ }
+
+ public function setUser($username, $password, $firstName = null, $lastName = null)
+ {
+ if ($this->getUser($username)) {
+ $result = $this->collection('user_table')->updateOne(
+ array('username' => $username),
+ array('$set' => array(
+ 'password' => $password,
+ 'first_name' => $firstName,
+ 'last_name' => $lastName
+ ))
+ );
+
+ return $result->getMatchedCount() > 0;
+ }
+
+ $user = array(
+ 'username' => $username,
+ 'password' => $password,
+ 'first_name' => $firstName,
+ 'last_name' => $lastName
+ );
+ $result = $this->collection('user_table')->insertOne($user);
+ return $result->getInsertedCount() > 0;
+ }
+
+ public function getClientKey($client_id, $subject)
+ {
+ $result = $this->collection('jwt_table')->findOne(array(
+ 'client_id' => $client_id,
+ 'subject' => $subject
+ ));
+ return is_null($result) ? false : $result['key'];
+ }
+
+ public function getClientScope($client_id)
+ {
+ if (!$clientDetails = $this->getClientDetails($client_id)) {
+ return false;
+ }
+ if (isset($clientDetails['scope'])) {
+ return $clientDetails['scope'];
+ }
+ return null;
+ }
+
+ public function getJti($client_id, $subject, $audience, $expires, $jti)
+ {
+ //TODO: Needs mongodb implementation.
+ throw new \Exception('getJti() for the MongoDB driver is currently unimplemented.');
+ }
+
+ public function setJti($client_id, $subject, $audience, $expires, $jti)
+ {
+ //TODO: Needs mongodb implementation.
+ throw new \Exception('setJti() for the MongoDB driver is currently unimplemented.');
+ }
+
+ public function getPublicKey($client_id = null)
+ {
+ if ($client_id) {
+ $result = $this->collection('key_table')->findOne(array(
+ 'client_id' => $client_id
+ ));
+ if ($result) {
+ return $result['public_key'];
+ }
+ }
+
+ $result = $this->collection('key_table')->findOne(array(
+ 'client_id' => null
+ ));
+ return is_null($result) ? false : $result['public_key'];
+ }
+
+ public function getPrivateKey($client_id = null)
+ {
+ if ($client_id) {
+ $result = $this->collection('key_table')->findOne(array(
+ 'client_id' => $client_id
+ ));
+ if ($result) {
+ return $result['private_key'];
+ }
+ }
+
+ $result = $this->collection('key_table')->findOne(array(
+ 'client_id' => null
+ ));
+ return is_null($result) ? false : $result['private_key'];
+ }
+
+ public function getEncryptionAlgorithm($client_id = null)
+ {
+ if ($client_id) {
+ $result = $this->collection('key_table')->findOne(array(
+ 'client_id' => $client_id
+ ));
+ if ($result) {
+ return $result['encryption_algorithm'];
+ }
+ }
+
+ $result = $this->collection('key_table')->findOne(array(
+ 'client_id' => null
+ ));
+ return is_null($result) ? 'RS256' : $result['encryption_algorithm'];
+ }
+
+ // Helper function to access a MongoDB collection by `type`:
+ protected function collection($name)
+ {
+ return $this->db->{$this->config[$name]};
+ }
+} \ No newline at end of file
diff --git a/library/oauth2/src/OAuth2/Storage/Pdo.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/Pdo.php
index ae5107e29..ae5107e29 100644
--- a/library/oauth2/src/OAuth2/Storage/Pdo.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/Pdo.php
diff --git a/library/oauth2/src/OAuth2/Storage/PublicKeyInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/PublicKeyInterface.php
index 108418d3a..108418d3a 100644
--- a/library/oauth2/src/OAuth2/Storage/PublicKeyInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/PublicKeyInterface.php
diff --git a/library/oauth2/src/OAuth2/Storage/Redis.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/Redis.php
index e6294e22d..e6294e22d 100644
--- a/library/oauth2/src/OAuth2/Storage/Redis.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/Redis.php
diff --git a/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/RefreshTokenInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/RefreshTokenInterface.php
new file mode 100644
index 000000000..e6407e440
--- /dev/null
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/RefreshTokenInterface.php
@@ -0,0 +1,82 @@
+<?php
+
+namespace OAuth2\Storage;
+
+/**
+ * Implement this interface to specify where the OAuth2 Server
+ * should get/save refresh tokens for the "Refresh Token"
+ * grant type
+ *
+ * @author Brent Shaffer <bshafs at gmail dot com>
+ */
+interface RefreshTokenInterface
+{
+ /**
+ * Grant refresh access tokens.
+ *
+ * Retrieve the stored data for the given refresh token.
+ *
+ * Required for OAuth2::GRANT_TYPE_REFRESH_TOKEN.
+ *
+ * @param $refresh_token
+ * Refresh token to be check with.
+ *
+ * @return
+ * An associative array as below, and NULL if the refresh_token is
+ * invalid:
+ * - refresh_token: Refresh token identifier.
+ * - client_id: Client identifier.
+ * - user_id: User identifier.
+ * - expires: Expiration unix timestamp, or 0 if the token doesn't expire.
+ * - scope: (optional) Scope values in space-separated string.
+ *
+ * @see http://tools.ietf.org/html/rfc6749#section-6
+ *
+ * @ingroup oauth2_section_6
+ */
+ public function getRefreshToken($refresh_token);
+
+ /**
+ * Take the provided refresh token values and store them somewhere.
+ *
+ * This function should be the storage counterpart to getRefreshToken().
+ *
+ * If storage fails for some reason, we're not currently checking for
+ * any sort of success/failure, so you should bail out of the script
+ * and provide a descriptive fail message.
+ *
+ * Required for OAuth2::GRANT_TYPE_REFRESH_TOKEN.
+ *
+ * @param $refresh_token
+ * Refresh token to be stored.
+ * @param $client_id
+ * Client identifier to be stored.
+ * @param $user_id
+ * User identifier to be stored.
+ * @param $expires
+ * Expiration timestamp to be stored. 0 if the token doesn't expire.
+ * @param $scope
+ * (optional) Scopes to be stored in space-separated string.
+ *
+ * @ingroup oauth2_section_6
+ */
+ public function setRefreshToken($refresh_token, $client_id, $user_id, $expires, $scope = null);
+
+ /**
+ * Expire a used refresh token.
+ *
+ * This is not explicitly required in the spec, but is almost implied.
+ * After granting a new refresh token, the old one is no longer useful and
+ * so should be forcibly expired in the data store so it can't be used again.
+ *
+ * If storage fails for some reason, we're not currently checking for
+ * any sort of success/failure, so you should bail out of the script
+ * and provide a descriptive fail message.
+ *
+ * @param $refresh_token
+ * Refresh token to be expired.
+ *
+ * @ingroup oauth2_section_6
+ */
+ public function unsetRefreshToken($refresh_token);
+}
diff --git a/library/oauth2/src/OAuth2/Storage/ScopeInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/ScopeInterface.php
index a8292269b..a8292269b 100644
--- a/library/oauth2/src/OAuth2/Storage/ScopeInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/ScopeInterface.php
diff --git a/library/oauth2/src/OAuth2/Storage/UserCredentialsInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/UserCredentialsInterface.php
index 6e0fd7bad..6e0fd7bad 100644
--- a/library/oauth2/src/OAuth2/Storage/UserCredentialsInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/Storage/UserCredentialsInterface.php
diff --git a/library/oauth2/src/OAuth2/TokenType/Bearer.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/TokenType/Bearer.php
index 8ac8596ac..8ac8596ac 100644
--- a/library/oauth2/src/OAuth2/TokenType/Bearer.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/TokenType/Bearer.php
diff --git a/library/oauth2/src/OAuth2/TokenType/Mac.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/TokenType/Mac.php
index fe6a86aa6..fe6a86aa6 100644
--- a/library/oauth2/src/OAuth2/TokenType/Mac.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/TokenType/Mac.php
diff --git a/library/oauth2/src/OAuth2/TokenType/TokenTypeInterface.php b/vendor/bshaffer/oauth2-server-php/src/OAuth2/TokenType/TokenTypeInterface.php
index ad77d4a25..ad77d4a25 100644
--- a/library/oauth2/src/OAuth2/TokenType/TokenTypeInterface.php
+++ b/vendor/bshaffer/oauth2-server-php/src/OAuth2/TokenType/TokenTypeInterface.php
diff --git a/library/oauth2/test/OAuth2/AutoloadTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/AutoloadTest.php
index 5901bdc42..5901bdc42 100644
--- a/library/oauth2/test/OAuth2/AutoloadTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/AutoloadTest.php
diff --git a/library/oauth2/test/OAuth2/Controller/AuthorizeControllerTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Controller/AuthorizeControllerTest.php
index 3bfc760e4..3bfc760e4 100644
--- a/library/oauth2/test/OAuth2/Controller/AuthorizeControllerTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Controller/AuthorizeControllerTest.php
diff --git a/vendor/bshaffer/oauth2-server-php/test/OAuth2/Controller/ResourceControllerTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Controller/ResourceControllerTest.php
new file mode 100644
index 000000000..b277514a5
--- /dev/null
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Controller/ResourceControllerTest.php
@@ -0,0 +1,176 @@
+<?php
+
+namespace OAuth2\Controller;
+
+use OAuth2\Storage\Bootstrap;
+use OAuth2\Server;
+use OAuth2\GrantType\AuthorizationCode;
+use OAuth2\Request;
+use OAuth2\Response;
+
+class ResourceControllerTest extends \PHPUnit_Framework_TestCase
+{
+ public function testNoAccessToken()
+ {
+ $server = $this->getTestServer();
+ $request = Request::createFromGlobals();
+ $allow = $server->verifyResourceRequest($request, $response = new Response());
+ $this->assertFalse($allow);
+
+ $this->assertEquals($response->getStatusCode(), 401);
+ $this->assertNull($response->getParameter('error'));
+ $this->assertNull($response->getParameter('error_description'));
+ $this->assertEquals('', $response->getResponseBody());
+ }
+
+ public function testMalformedHeader()
+ {
+ $server = $this->getTestServer();
+ $request = Request::createFromGlobals();
+ $request->headers['AUTHORIZATION'] = 'tH1s i5 B0gU5';
+ $allow = $server->verifyResourceRequest($request, $response = new Response());
+ $this->assertFalse($allow);
+
+ $this->assertEquals($response->getStatusCode(), 400);
+ $this->assertEquals($response->getParameter('error'), 'invalid_request');
+ $this->assertEquals($response->getParameter('error_description'), 'Malformed auth header');
+ }
+
+ public function testMultipleTokensSubmitted()
+ {
+ $server = $this->getTestServer();
+ $request = Request::createFromGlobals();
+ $request->request['access_token'] = 'TEST';
+ $request->query['access_token'] = 'TEST';
+ $allow = $server->verifyResourceRequest($request, $response = new Response());
+ $this->assertFalse($allow);
+
+ $this->assertEquals($response->getStatusCode(), 400);
+ $this->assertEquals($response->getParameter('error'), 'invalid_request');
+ $this->assertEquals($response->getParameter('error_description'), 'Only one method may be used to authenticate at a time (Auth header, GET or POST)');
+ }
+
+ public function testInvalidRequestMethod()
+ {
+ $server = $this->getTestServer();
+ $request = Request::createFromGlobals();
+ $request->server['REQUEST_METHOD'] = 'GET';
+ $request->request['access_token'] = 'TEST';
+ $allow = $server->verifyResourceRequest($request, $response = new Response());
+ $this->assertFalse($allow);
+
+ $this->assertEquals($response->getStatusCode(), 400);
+ $this->assertEquals($response->getParameter('error'), 'invalid_request');
+ $this->assertEquals($response->getParameter('error_description'), 'When putting the token in the body, the method must be POST or PUT');
+ }
+
+ public function testInvalidContentType()
+ {
+ $server = $this->getTestServer();
+ $request = Request::createFromGlobals();
+ $request->server['REQUEST_METHOD'] = 'POST';
+ $request->server['CONTENT_TYPE'] = 'application/json';
+ $request->request['access_token'] = 'TEST';
+ $allow = $server->verifyResourceRequest($request, $response = new Response());
+ $this->assertFalse($allow);
+
+ $this->assertEquals($response->getStatusCode(), 400);
+ $this->assertEquals($response->getParameter('error'), 'invalid_request');
+ $this->assertEquals($response->getParameter('error_description'), 'The content type for POST requests must be "application/x-www-form-urlencoded"');
+ }
+
+ public function testInvalidToken()
+ {
+ $server = $this->getTestServer();
+ $request = Request::createFromGlobals();
+ $request->headers['AUTHORIZATION'] = 'Bearer TESTTOKEN';
+ $allow = $server->verifyResourceRequest($request, $response = new Response());
+ $this->assertFalse($allow);
+
+ $this->assertEquals($response->getStatusCode(), 401);
+ $this->assertEquals($response->getParameter('error'), 'invalid_token');
+ $this->assertEquals($response->getParameter('error_description'), 'The access token provided is invalid');
+ }
+
+ public function testExpiredToken()
+ {
+ $server = $this->getTestServer();
+ $request = Request::createFromGlobals();
+ $request->headers['AUTHORIZATION'] = 'Bearer accesstoken-expired';
+ $allow = $server->verifyResourceRequest($request, $response = new Response());
+ $this->assertFalse($allow);
+
+ $this->assertEquals($response->getStatusCode(), 401);
+ $this->assertEquals($response->getParameter('error'), 'invalid_token');
+ $this->assertEquals($response->getParameter('error_description'), 'The access token provided has expired');
+ }
+
+ public function testOutOfScopeToken()
+ {
+ $server = $this->getTestServer();
+ $request = Request::createFromGlobals();
+ $request->headers['AUTHORIZATION'] = 'Bearer accesstoken-scope';
+ $scope = 'outofscope';
+ $allow = $server->verifyResourceRequest($request, $response = new Response(), $scope);
+ $this->assertFalse($allow);
+
+ $this->assertEquals($response->getStatusCode(), 403);
+ $this->assertEquals($response->getParameter('error'), 'insufficient_scope');
+ $this->assertEquals($response->getParameter('error_description'), 'The request requires higher privileges than provided by the access token');
+
+ // verify the "scope" has been set in the "WWW-Authenticate" header
+ preg_match('/scope="(.*?)"/', $response->getHttpHeader('WWW-Authenticate'), $matches);
+ $this->assertEquals(2, count($matches));
+ $this->assertEquals($matches[1], 'outofscope');
+ }
+
+ public function testMalformedToken()
+ {
+ $server = $this->getTestServer();
+ $request = Request::createFromGlobals();
+ $request->headers['AUTHORIZATION'] = 'Bearer accesstoken-malformed';
+ $allow = $server->verifyResourceRequest($request, $response = new Response());
+ $this->assertFalse($allow);
+
+ $this->assertEquals($response->getStatusCode(), 401);
+ $this->assertEquals($response->getParameter('error'), 'malformed_token');
+ $this->assertEquals($response->getParameter('error_description'), 'Malformed token (missing "expires")');
+ }
+
+ public function testValidToken()
+ {
+ $server = $this->getTestServer();
+ $request = Request::createFromGlobals();
+ $request->headers['AUTHORIZATION'] = 'Bearer accesstoken-scope';
+ $allow = $server->verifyResourceRequest($request, $response = new Response());
+ $this->assertTrue($allow);
+ }
+
+ public function testValidTokenWithScopeParam()
+ {
+ $server = $this->getTestServer();
+ $request = Request::createFromGlobals();
+ $request->headers['AUTHORIZATION'] = 'Bearer accesstoken-scope';
+ $request->query['scope'] = 'testscope';
+ $allow = $server->verifyResourceRequest($request, $response = new Response());
+ $this->assertTrue($allow);
+ }
+
+ public function testCreateController()
+ {
+ $storage = Bootstrap::getInstance()->getMemoryStorage();
+ $tokenType = new \OAuth2\TokenType\Bearer();
+ $controller = new ResourceController($tokenType, $storage);
+ }
+
+ private function getTestServer($config = array())
+ {
+ $storage = Bootstrap::getInstance()->getMemoryStorage();
+ $server = new Server($storage, $config);
+
+ // Add the two types supported for authorization grant
+ $server->addGrantType(new AuthorizationCode($storage));
+
+ return $server;
+ }
+}
diff --git a/library/oauth2/test/OAuth2/Controller/TokenControllerTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Controller/TokenControllerTest.php
index 4a217bd55..4a217bd55 100644
--- a/library/oauth2/test/OAuth2/Controller/TokenControllerTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Controller/TokenControllerTest.php
diff --git a/library/oauth2/test/OAuth2/Encryption/FirebaseJwtTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Encryption/FirebaseJwtTest.php
index d34136767..d34136767 100644
--- a/library/oauth2/test/OAuth2/Encryption/FirebaseJwtTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Encryption/FirebaseJwtTest.php
diff --git a/library/oauth2/test/OAuth2/Encryption/JwtTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Encryption/JwtTest.php
index 214eebac8..214eebac8 100644
--- a/library/oauth2/test/OAuth2/Encryption/JwtTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Encryption/JwtTest.php
diff --git a/vendor/bshaffer/oauth2-server-php/test/OAuth2/GrantType/AuthorizationCodeTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/GrantType/AuthorizationCodeTest.php
new file mode 100644
index 000000000..356b8e53c
--- /dev/null
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/GrantType/AuthorizationCodeTest.php
@@ -0,0 +1,223 @@
+<?php
+
+namespace OAuth2\GrantType;
+
+use OAuth2\Storage\Bootstrap;
+use OAuth2\Server;
+use OAuth2\Request\TestRequest;
+use OAuth2\Response;
+
+class AuthorizationCodeTest extends \PHPUnit_Framework_TestCase
+{
+ public function testNoCode()
+ {
+ $server = $this->getTestServer();
+ $request = TestRequest::createPost(array(
+ 'grant_type' => 'authorization_code', // valid grant type
+ 'client_id' => 'Test Client ID', // valid client id
+ 'client_secret' => 'TestSecret', // valid client secret
+ ));
+ $server->handleTokenRequest($request, $response = new Response());
+
+ $this->assertEquals($response->getStatusCode(), 400);
+ $this->assertEquals($response->getParameter('error'), 'invalid_request');
+ $this->assertEquals($response->getParameter('error_description'), 'Missing parameter: "code" is required');
+ }
+
+ public function testInvalidCode()
+ {
+ $server = $this->getTestServer();
+ $request = TestRequest::createPost(array(
+ 'grant_type' => 'authorization_code', // valid grant type
+ 'client_id' => 'Test Client ID', // valid client id
+ 'client_secret' => 'TestSecret', // valid client secret
+ 'code' => 'InvalidCode', // invalid authorization code
+ ));
+ $server->handleTokenRequest($request, $response = new Response());
+
+ $this->assertEquals($response->getStatusCode(), 400);
+ $this->assertEquals($response->getParameter('error'), 'invalid_grant');
+ $this->assertEquals($response->getParameter('error_description'), 'Authorization code doesn\'t exist or is invalid for the client');
+ }
+
+ public function testCodeCannotBeUsedTwice()
+ {
+ $server = $this->getTestServer();
+ $request = TestRequest::createPost(array(
+ 'grant_type' => 'authorization_code', // valid grant type
+ 'client_id' => 'Test Client ID', // valid client id
+ 'client_secret' => 'TestSecret', // valid client secret
+ 'code' => 'testcode', // valid code
+ ));
+ $server->handleTokenRequest($request, $response = new Response());
+
+ $this->assertEquals($response->getStatusCode(), 200);
+ $this->assertNotNull($response->getParameter('access_token'));
+
+ // try to use the same code again
+ $server->handleTokenRequest($request, $response = new Response());
+
+ $this->assertEquals($response->getStatusCode(), 400);
+ $this->assertEquals($response->getParameter('error'), 'invalid_grant');
+ $this->assertEquals($response->getParameter('error_description'), 'Authorization code doesn\'t exist or is invalid for the client');
+ }
+
+ public function testExpiredCode()
+ {
+ $server = $this->getTestServer();
+ $request = TestRequest::createPost(array(
+ 'grant_type' => 'authorization_code', // valid grant type
+ 'client_id' => 'Test Client ID', // valid client id
+ 'client_secret' => 'TestSecret', // valid client secret
+ 'code' => 'testcode-expired', // expired authorization code
+ ));
+ $server->handleTokenRequest($request, $response = new Response());
+
+ $this->assertEquals($response->getStatusCode(), 400);
+ $this->assertEquals($response->getParameter('error'), 'invalid_grant');
+ $this->assertEquals($response->getParameter('error_description'), 'The authorization code has expired');
+ }
+
+ public function testValidCode()
+ {
+ $server = $this->getTestServer();
+ $request = TestRequest::createPost(array(
+ 'grant_type' => 'authorization_code', // valid grant type
+ 'client_id' => 'Test Client ID', // valid client id
+ 'client_secret' => 'TestSecret', // valid client secret
+ 'code' => 'testcode', // valid code
+ ));
+ $token = $server->grantAccessToken($request, new Response());
+
+ $this->assertNotNull($token);
+ $this->assertArrayHasKey('access_token', $token);
+ }
+
+ public function testValidRedirectUri()
+ {
+ $server = $this->getTestServer();
+ $request = TestRequest::createPost(array(
+ 'grant_type' => 'authorization_code', // valid grant type
+ 'client_id' => 'Test Client ID', // valid client id
+ 'redirect_uri' => 'http://brentertainment.com/voil%C3%A0', // valid client id
+ 'client_secret' => 'TestSecret', // valid client secret
+ 'code' => 'testcode-redirect-uri', // valid code
+ ));
+ $token = $server->grantAccessToken($request, new Response());
+
+ $this->assertNotNull($token);
+ $this->assertArrayHasKey('access_token', $token);
+ }
+
+ public function testValidCodeNoScope()
+ {
+ $server = $this->getTestServer();
+ $request = TestRequest::createPost(array(
+ 'grant_type' => 'authorization_code', // valid grant type
+ 'client_id' => 'Test Client ID', // valid client id
+ 'client_secret' => 'TestSecret', // valid client secret
+ 'code' => 'testcode-with-scope', // valid code
+ ));
+ $token = $server->grantAccessToken($request, new Response());
+
+ $this->assertNotNull($token);
+ $this->assertArrayHasKey('access_token', $token);
+ $this->assertArrayHasKey('scope', $token);
+ $this->assertEquals($token['scope'], 'scope1 scope2');
+ }
+
+ public function testValidCodeSameScope()
+ {
+ $server = $this->getTestServer();
+ $request = TestRequest::createPost(array(
+ 'grant_type' => 'authorization_code', // valid grant type
+ 'client_id' => 'Test Client ID', // valid client id
+ 'client_secret' => 'TestSecret', // valid client secret
+ 'code' => 'testcode-with-scope', // valid code
+ 'scope' => 'scope2 scope1',
+ ));
+ $token = $server->grantAccessToken($request, new Response());
+
+ $this->assertNotNull($token);
+ $this->assertArrayHasKey('access_token', $token);
+ $this->assertArrayHasKey('scope', $token);
+ $this->assertEquals($token['scope'], 'scope2 scope1');
+ }
+
+ public function testValidCodeLessScope()
+ {
+ $server = $this->getTestServer();
+ $request = TestRequest::createPost(array(
+ 'grant_type' => 'authorization_code', // valid grant type
+ 'client_id' => 'Test Client ID', // valid client id
+ 'client_secret' => 'TestSecret', // valid client secret
+ 'code' => 'testcode-with-scope', // valid code
+ 'scope' => 'scope1',
+ ));
+ $token = $server->grantAccessToken($request, new Response());
+
+ $this->assertNotNull($token);
+ $this->assertArrayHasKey('access_token', $token);
+ $this->assertArrayHasKey('scope', $token);
+ $this->assertEquals($token['scope'], 'scope1');
+ }
+
+ public function testValidCodeDifferentScope()
+ {
+ $server = $this->getTestServer();
+ $request = TestRequest::createPost(array(
+ 'grant_type' => 'authorization_code', // valid grant type
+ 'client_id' => 'Test Client ID', // valid client id
+ 'client_secret' => 'TestSecret', // valid client secret
+ 'code' => 'testcode-with-scope', // valid code
+ 'scope' => 'scope3',
+ ));
+ $token = $server->grantAccessToken($request, $response = new Response());
+
+ $this->assertEquals($response->getStatusCode(), 400);
+ $this->assertEquals($response->getParameter('error'), 'invalid_scope');
+ $this->assertEquals($response->getParameter('error_description'), 'The scope requested is invalid for this request');
+ }
+
+ public function testValidCodeInvalidScope()
+ {
+ $server = $this->getTestServer();
+ $request = TestRequest::createPost(array(
+ 'grant_type' => 'authorization_code', // valid grant type
+ 'client_id' => 'Test Client ID', // valid client id
+ 'client_secret' => 'TestSecret', // valid client secret
+ 'code' => 'testcode-with-scope', // valid code
+ 'scope' => 'invalid-scope',
+ ));
+ $token = $server->grantAccessToken($request, $response = new Response());
+
+ $this->assertEquals($response->getStatusCode(), 400);
+ $this->assertEquals($response->getParameter('error'), 'invalid_scope');
+ $this->assertEquals($response->getParameter('error_description'), 'The scope requested is invalid for this request');
+ }
+
+ public function testValidClientDifferentCode()
+ {
+ $server = $this->getTestServer();
+ $request = TestRequest::createPost(array(
+ 'grant_type' => 'authorization_code', // valid grant type
+ 'client_id' => 'Test Some Other Client', // valid client id
+ 'client_secret' => 'TestSecret3', // valid client secret
+ 'code' => 'testcode', // valid code
+ ));
+ $token = $server->grantAccessToken($request, $response = new Response());
+
+ $this->assertEquals($response->getStatusCode(), 400);
+ $this->assertEquals($response->getParameter('error'), 'invalid_grant');
+ $this->assertEquals($response->getParameter('error_description'), 'authorization_code doesn\'t exist or is invalid for the client');
+ }
+
+ private function getTestServer()
+ {
+ $storage = Bootstrap::getInstance()->getMemoryStorage();
+ $server = new Server($storage);
+ $server->addGrantType(new AuthorizationCode($storage));
+
+ return $server;
+ }
+}
diff --git a/library/oauth2/test/OAuth2/GrantType/ClientCredentialsTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/GrantType/ClientCredentialsTest.php
index f0d46ccb3..f0d46ccb3 100644
--- a/library/oauth2/test/OAuth2/GrantType/ClientCredentialsTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/GrantType/ClientCredentialsTest.php
diff --git a/library/oauth2/test/OAuth2/GrantType/ImplicitTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/GrantType/ImplicitTest.php
index a47aae3e8..a47aae3e8 100644
--- a/library/oauth2/test/OAuth2/GrantType/ImplicitTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/GrantType/ImplicitTest.php
diff --git a/library/oauth2/test/OAuth2/GrantType/JwtBearerTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/GrantType/JwtBearerTest.php
index 0a6c4b827..0a6c4b827 100644
--- a/library/oauth2/test/OAuth2/GrantType/JwtBearerTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/GrantType/JwtBearerTest.php
diff --git a/library/oauth2/test/OAuth2/GrantType/RefreshTokenTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/GrantType/RefreshTokenTest.php
index a458aad8a..a458aad8a 100644
--- a/library/oauth2/test/OAuth2/GrantType/RefreshTokenTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/GrantType/RefreshTokenTest.php
diff --git a/library/oauth2/test/OAuth2/GrantType/UserCredentialsTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/GrantType/UserCredentialsTest.php
index 18943d055..18943d055 100644
--- a/library/oauth2/test/OAuth2/GrantType/UserCredentialsTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/GrantType/UserCredentialsTest.php
diff --git a/library/oauth2/test/OAuth2/OpenID/Controller/AuthorizeControllerTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/Controller/AuthorizeControllerTest.php
index 46de936d8..46de936d8 100644
--- a/library/oauth2/test/OAuth2/OpenID/Controller/AuthorizeControllerTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/Controller/AuthorizeControllerTest.php
diff --git a/library/oauth2/test/OAuth2/OpenID/Controller/UserInfoControllerTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/Controller/UserInfoControllerTest.php
index b1b687077..b1b687077 100644
--- a/library/oauth2/test/OAuth2/OpenID/Controller/UserInfoControllerTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/Controller/UserInfoControllerTest.php
diff --git a/library/oauth2/test/OAuth2/OpenID/GrantType/AuthorizationCodeTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/GrantType/AuthorizationCodeTest.php
index 776002d1e..776002d1e 100644
--- a/library/oauth2/test/OAuth2/OpenID/GrantType/AuthorizationCodeTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/GrantType/AuthorizationCodeTest.php
diff --git a/library/oauth2/test/OAuth2/OpenID/ResponseType/CodeIdTokenTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/ResponseType/CodeIdTokenTest.php
index b0311434a..b0311434a 100644
--- a/library/oauth2/test/OAuth2/OpenID/ResponseType/CodeIdTokenTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/ResponseType/CodeIdTokenTest.php
diff --git a/library/oauth2/test/OAuth2/OpenID/ResponseType/IdTokenTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/ResponseType/IdTokenTest.php
index e772f6be4..e772f6be4 100644
--- a/library/oauth2/test/OAuth2/OpenID/ResponseType/IdTokenTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/ResponseType/IdTokenTest.php
diff --git a/library/oauth2/test/OAuth2/OpenID/ResponseType/IdTokenTokenTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/ResponseType/IdTokenTokenTest.php
index bc564d37b..bc564d37b 100644
--- a/library/oauth2/test/OAuth2/OpenID/ResponseType/IdTokenTokenTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/ResponseType/IdTokenTokenTest.php
diff --git a/library/oauth2/test/OAuth2/OpenID/Storage/AuthorizationCodeTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/Storage/AuthorizationCodeTest.php
index bdfb085e3..bdfb085e3 100644
--- a/library/oauth2/test/OAuth2/OpenID/Storage/AuthorizationCodeTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/Storage/AuthorizationCodeTest.php
diff --git a/library/oauth2/test/OAuth2/OpenID/Storage/UserClaimsTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/Storage/UserClaimsTest.php
index 840f6c566..840f6c566 100644
--- a/library/oauth2/test/OAuth2/OpenID/Storage/UserClaimsTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/OpenID/Storage/UserClaimsTest.php
diff --git a/library/oauth2/test/OAuth2/RequestTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/RequestTest.php
index 10db3215c..10db3215c 100644
--- a/library/oauth2/test/OAuth2/RequestTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/RequestTest.php
diff --git a/library/oauth2/test/OAuth2/ResponseTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/ResponseTest.php
index b8149005d..b8149005d 100644
--- a/library/oauth2/test/OAuth2/ResponseTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/ResponseTest.php
diff --git a/library/oauth2/test/OAuth2/ResponseType/AccessTokenTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/ResponseType/AccessTokenTest.php
index 0ed1c82fc..0ed1c82fc 100644
--- a/library/oauth2/test/OAuth2/ResponseType/AccessTokenTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/ResponseType/AccessTokenTest.php
diff --git a/library/oauth2/test/OAuth2/ResponseType/JwtAccessTokenTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/ResponseType/JwtAccessTokenTest.php
index 51b01a927..51b01a927 100644
--- a/library/oauth2/test/OAuth2/ResponseType/JwtAccessTokenTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/ResponseType/JwtAccessTokenTest.php
diff --git a/library/oauth2/test/OAuth2/ScopeTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/ScopeTest.php
index 99f9cf6eb..99f9cf6eb 100644
--- a/library/oauth2/test/OAuth2/ScopeTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/ScopeTest.php
diff --git a/library/oauth2/test/OAuth2/ServerTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/ServerTest.php
index 747e120f5..747e120f5 100644
--- a/library/oauth2/test/OAuth2/ServerTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/ServerTest.php
diff --git a/library/oauth2/test/OAuth2/Storage/AccessTokenTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/AccessTokenTest.php
index b34e0bfc0..b34e0bfc0 100644
--- a/library/oauth2/test/OAuth2/Storage/AccessTokenTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/AccessTokenTest.php
diff --git a/library/oauth2/test/OAuth2/Storage/AuthorizationCodeTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/AuthorizationCodeTest.php
index 2d901b501..2d901b501 100644
--- a/library/oauth2/test/OAuth2/Storage/AuthorizationCodeTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/AuthorizationCodeTest.php
diff --git a/library/oauth2/test/OAuth2/Storage/ClientCredentialsTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/ClientCredentialsTest.php
index 15289af30..15289af30 100644
--- a/library/oauth2/test/OAuth2/Storage/ClientCredentialsTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/ClientCredentialsTest.php
diff --git a/library/oauth2/test/OAuth2/Storage/ClientTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/ClientTest.php
index 6a5cc0b49..6a5cc0b49 100644
--- a/library/oauth2/test/OAuth2/Storage/ClientTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/ClientTest.php
diff --git a/library/oauth2/test/OAuth2/Storage/DynamoDBTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/DynamoDBTest.php
index 2147f0914..2147f0914 100644
--- a/library/oauth2/test/OAuth2/Storage/DynamoDBTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/DynamoDBTest.php
diff --git a/library/oauth2/test/OAuth2/Storage/JwtAccessTokenTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/JwtAccessTokenTest.php
index a6acbea1f..a6acbea1f 100644
--- a/library/oauth2/test/OAuth2/Storage/JwtAccessTokenTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/JwtAccessTokenTest.php
diff --git a/library/oauth2/test/OAuth2/Storage/JwtBearerTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/JwtBearerTest.php
index d0ab9b899..d0ab9b899 100644
--- a/library/oauth2/test/OAuth2/Storage/JwtBearerTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/JwtBearerTest.php
diff --git a/library/oauth2/test/OAuth2/Storage/PdoTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/PdoTest.php
index 57eb39072..57eb39072 100644
--- a/library/oauth2/test/OAuth2/Storage/PdoTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/PdoTest.php
diff --git a/library/oauth2/test/OAuth2/Storage/PublicKeyTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/PublicKeyTest.php
index f85195870..f85195870 100644
--- a/library/oauth2/test/OAuth2/Storage/PublicKeyTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/PublicKeyTest.php
diff --git a/library/oauth2/test/OAuth2/Storage/RefreshTokenTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/RefreshTokenTest.php
index 314c93195..314c93195 100644
--- a/library/oauth2/test/OAuth2/Storage/RefreshTokenTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/RefreshTokenTest.php
diff --git a/library/oauth2/test/OAuth2/Storage/ScopeTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/ScopeTest.php
index fd1edeb93..fd1edeb93 100644
--- a/library/oauth2/test/OAuth2/Storage/ScopeTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/ScopeTest.php
diff --git a/library/oauth2/test/OAuth2/Storage/UserCredentialsTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/UserCredentialsTest.php
index 65655a6b2..65655a6b2 100644
--- a/library/oauth2/test/OAuth2/Storage/UserCredentialsTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/Storage/UserCredentialsTest.php
diff --git a/library/oauth2/test/OAuth2/TokenType/BearerTest.php b/vendor/bshaffer/oauth2-server-php/test/OAuth2/TokenType/BearerTest.php
index a2e000e22..a2e000e22 100644
--- a/library/oauth2/test/OAuth2/TokenType/BearerTest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/OAuth2/TokenType/BearerTest.php
diff --git a/library/oauth2/test/bootstrap.php b/vendor/bshaffer/oauth2-server-php/test/bootstrap.php
index 0a4af0716..0a4af0716 100644
--- a/library/oauth2/test/bootstrap.php
+++ b/vendor/bshaffer/oauth2-server-php/test/bootstrap.php
diff --git a/library/oauth2/test/cleanup.php b/vendor/bshaffer/oauth2-server-php/test/cleanup.php
index 8663a901b..8663a901b 100644
--- a/library/oauth2/test/cleanup.php
+++ b/vendor/bshaffer/oauth2-server-php/test/cleanup.php
diff --git a/library/oauth2/test/config/keys/id_rsa b/vendor/bshaffer/oauth2-server-php/test/config/keys/id_rsa
index e8b9eff2d..e8b9eff2d 100644
--- a/library/oauth2/test/config/keys/id_rsa
+++ b/vendor/bshaffer/oauth2-server-php/test/config/keys/id_rsa
diff --git a/library/oauth2/test/config/keys/id_rsa.pub b/vendor/bshaffer/oauth2-server-php/test/config/keys/id_rsa.pub
index 1ac15f5eb..1ac15f5eb 100644
--- a/library/oauth2/test/config/keys/id_rsa.pub
+++ b/vendor/bshaffer/oauth2-server-php/test/config/keys/id_rsa.pub
diff --git a/vendor/bshaffer/oauth2-server-php/test/config/storage.json b/vendor/bshaffer/oauth2-server-php/test/config/storage.json
new file mode 100644
index 000000000..52d3f2399
--- /dev/null
+++ b/vendor/bshaffer/oauth2-server-php/test/config/storage.json
@@ -0,0 +1,188 @@
+{
+ "authorization_codes": {
+ "testcode": {
+ "client_id": "Test Client ID",
+ "user_id": "",
+ "redirect_uri": "",
+ "expires": "9999999999",
+ "id_token": "IDTOKEN"
+ },
+ "testcode-with-scope": {
+ "client_id": "Test Client ID",
+ "user_id": "",
+ "redirect_uri": "",
+ "expires": "9999999999",
+ "scope": "scope1 scope2"
+ },
+ "testcode-expired": {
+ "client_id": "Test Client ID",
+ "user_id": "",
+ "redirect_uri": "",
+ "expires": "1356998400"
+ },
+ "testcode-empty-secret": {
+ "client_id": "Test Client ID Empty Secret",
+ "user_id": "",
+ "redirect_uri": "",
+ "expires": "9999999999"
+ },
+ "testcode-openid": {
+ "client_id": "Test Client ID",
+ "user_id": "",
+ "redirect_uri": "",
+ "expires": "9999999999",
+ "id_token": "test_id_token"
+ },
+ "testcode-redirect-uri": {
+ "client_id": "Test Client ID",
+ "user_id": "",
+ "redirect_uri": "http://brentertainment.com/voil%C3%A0",
+ "expires": "9999999999",
+ "id_token": "IDTOKEN"
+ }
+ },
+ "client_credentials" : {
+ "Test Client ID": {
+ "client_secret": "TestSecret"
+ },
+ "Test Client ID with Redirect Uri": {
+ "client_secret": "TestSecret2",
+ "redirect_uri": "http://brentertainment.com"
+ },
+ "Test Client ID with Buggy Redirect Uri": {
+ "client_secret": "TestSecret2",
+ "redirect_uri": " http://brentertainment.com"
+ },
+ "Test Client ID with Multiple Redirect Uris": {
+ "client_secret": "TestSecret3",
+ "redirect_uri": "http://brentertainment.com http://morehazards.com"
+ },
+ "Test Client ID with Redirect Uri Parts": {
+ "client_secret": "TestSecret4",
+ "redirect_uri": "http://user:pass@brentertainment.com:2222/authorize/cb?auth_type=oauth&test=true"
+ },
+ "Test Some Other Client": {
+ "client_secret": "TestSecret3"
+ },
+ "Test Client ID Empty Secret": {
+ "client_secret": ""
+ },
+ "Test Client ID For Password Grant": {
+ "grant_types": "password",
+ "client_secret": ""
+ },
+ "Client ID With User ID": {
+ "client_secret": "TestSecret",
+ "user_id": "brent@brentertainment.com"
+ },
+ "oauth_test_client": {
+ "client_secret": "testpass",
+ "grant_types": "implicit password"
+ }
+ },
+ "user_credentials" : {
+ "test-username": {
+ "password": "testpass"
+ },
+ "testusername": {
+ "password": "testpass"
+ },
+ "testuser": {
+ "password": "password",
+ "email": "testuser@test.com",
+ "email_verified": true
+ },
+ "johndoe": {
+ "password": "password"
+ }
+ },
+ "refresh_tokens" : {
+ "test-refreshtoken": {
+ "refresh_token": "test-refreshtoken",
+ "client_id": "Test Client ID",
+ "user_id": "test-username",
+ "expires": 0,
+ "scope": null
+ },
+ "test-refreshtoken-with-scope": {
+ "refresh_token": "test-refreshtoken",
+ "client_id": "Test Client ID",
+ "user_id": "test-username",
+ "expires": 0,
+ "scope": "scope1 scope2"
+ }
+ },
+ "access_tokens" : {
+ "accesstoken-expired": {
+ "access_token": "accesstoken-expired",
+ "client_id": "Test Client ID",
+ "expires": 1234567,
+ "scope": null
+ },
+ "accesstoken-scope": {
+ "access_token": "accesstoken-scope",
+ "client_id": "Test Client ID",
+ "expires": 99999999900,
+ "scope": "testscope"
+ },
+ "accesstoken-openid-connect": {
+ "access_token": "accesstoken-openid-connect",
+ "client_id": "Test Client ID",
+ "user_id": "testuser",
+ "expires": 99999999900,
+ "scope": "openid email"
+ },
+ "accesstoken-malformed": {
+ "access_token": "accesstoken-mallformed",
+ "expires": 99999999900,
+ "scope": "testscope"
+ }
+ },
+ "jwt": {
+ "Test Client ID": {
+ "key": "-----BEGIN PUBLIC KEY-----\nMIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQC5/SxVlE8gnpFqCxgl2wjhzY7u\ncEi00s0kUg3xp7lVEvgLgYcAnHiWp+gtSjOFfH2zsvpiWm6Lz5f743j/FEzHIO1o\nwR0p4d9pOaJK07d01+RzoQLOIQAgXrr4T1CCWUesncwwPBVCyy2Mw3Nmhmr9MrF8\nUlvdRKBxriRnlP3qJQIDAQAB\n-----END PUBLIC KEY-----",
+ "subject": "testuser@ourdomain.com"
+ },
+ "Test Client ID PHP-5.2": {
+ "key": "mysecretkey",
+ "subject": "testuser@ourdomain.com"
+ },
+ "Missing Key Client": {
+ "key": null,
+ "subject": "testuser@ourdomain.com"
+ },
+ "Missing Key Client PHP-5.2": {
+ "key": null,
+ "subject": "testuser@ourdomain.com"
+ },
+ "oauth_test_client": {
+ "key": "-----BEGIN CERTIFICATE-----\nMIICiDCCAfGgAwIBAgIBADANBgkqhkiG9w0BAQQFADA9MQswCQYDVQQGEwJVUzEL\nMAkGA1UECBMCVVQxITAfBgNVBAoTGFZpZ25ldHRlIENvcnBvcmF0aW9uIFNCWDAe\nFw0xMTEwMTUwMzE4MjdaFw0zMTEwMTAwMzE4MjdaMD0xCzAJBgNVBAYTAlVTMQsw\nCQYDVQQIEwJVVDEhMB8GA1UEChMYVmlnbmV0dGUgQ29ycG9yYXRpb24gU0JYMIGf\nMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQC8fpi06NfVYHAOAnxNMVnTXr/ptsLs\nNjP+uAt2eO0cc5J9H5XV8lFVujOrRu/JWi1TDmAvOaf/6A3BphIA1Pwp0AAqlZdw\nizIum8j0KzpsGYH5qReNQDwF3oUSKMsQCCGCDHrDYifG/pRi9bN1ZVjEXPr35HJu\nBe+FQpZTs8DewwIDAQABo4GXMIGUMB0GA1UdDgQWBBRe8hrEXm+Yim4YlD5Nx+1K\nvCYs9DBlBgNVHSMEXjBcgBRe8hrEXm+Yim4YlD5Nx+1KvCYs9KFBpD8wPTELMAkG\nA1UEBhMCVVMxCzAJBgNVBAgTAlVUMSEwHwYDVQQKExhWaWduZXR0ZSBDb3Jwb3Jh\ndGlvbiBTQliCAQAwDAYDVR0TBAUwAwEB/zANBgkqhkiG9w0BAQQFAAOBgQBjhyRD\nlM7vnLn6drgQVftW5V9nDFAyPAuiGvMIKFSbiAf1PxXCRn5sfJquwWKsJUi4ZGNl\naViXdFmN6/F13PSM+yg63tpKy0fYqMbTM+Oe5WuSHkSW1VuYNHV+24adgNk/FRDL\nFRrlM1f6s9VTLWvwGItjfrof0Ba8Uq7ZDSb9Xg==\n-----END CERTIFICATE-----",
+ "subject": "test_subject"
+ }
+ },
+ "jti": [
+ {
+ "issuer": "Test Client ID",
+ "subject": "testuser@ourdomain.com",
+ "audience": "http://myapp.com/oauth/auth",
+ "expires": 99999999900,
+ "jti": "used_jti"
+ }
+ ],
+ "supported_scopes" : [
+ "scope1",
+ "scope2",
+ "scope3",
+ "clientscope1",
+ "clientscope2",
+ "clientscope3",
+ "supportedscope1",
+ "supportedscope2",
+ "supportedscope3",
+ "supportedscope4"
+ ],
+ "keys": {
+ "public_key": "-----BEGIN CERTIFICATE-----\nMIICiDCCAfGgAwIBAgIBADANBgkqhkiG9w0BAQQFADA9MQswCQYDVQQGEwJVUzEL\nMAkGA1UECBMCVVQxITAfBgNVBAoTGFZpZ25ldHRlIENvcnBvcmF0aW9uIFNCWDAe\nFw0xMTEwMTUwMzE4MjdaFw0zMTEwMTAwMzE4MjdaMD0xCzAJBgNVBAYTAlVTMQsw\nCQYDVQQIEwJVVDEhMB8GA1UEChMYVmlnbmV0dGUgQ29ycG9yYXRpb24gU0JYMIGf\nMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQC8fpi06NfVYHAOAnxNMVnTXr/ptsLs\nNjP+uAt2eO0cc5J9H5XV8lFVujOrRu/JWi1TDmAvOaf/6A3BphIA1Pwp0AAqlZdw\nizIum8j0KzpsGYH5qReNQDwF3oUSKMsQCCGCDHrDYifG/pRi9bN1ZVjEXPr35HJu\nBe+FQpZTs8DewwIDAQABo4GXMIGUMB0GA1UdDgQWBBRe8hrEXm+Yim4YlD5Nx+1K\nvCYs9DBlBgNVHSMEXjBcgBRe8hrEXm+Yim4YlD5Nx+1KvCYs9KFBpD8wPTELMAkG\nA1UEBhMCVVMxCzAJBgNVBAgTAlVUMSEwHwYDVQQKExhWaWduZXR0ZSBDb3Jwb3Jh\ndGlvbiBTQliCAQAwDAYDVR0TBAUwAwEB/zANBgkqhkiG9w0BAQQFAAOBgQBjhyRD\nlM7vnLn6drgQVftW5V9nDFAyPAuiGvMIKFSbiAf1PxXCRn5sfJquwWKsJUi4ZGNl\naViXdFmN6/F13PSM+yg63tpKy0fYqMbTM+Oe5WuSHkSW1VuYNHV+24adgNk/FRDL\nFRrlM1f6s9VTLWvwGItjfrof0Ba8Uq7ZDSb9Xg==\n-----END CERTIFICATE-----",
+ "private_key": "-----BEGIN RSA PRIVATE KEY-----\nMIICXQIBAAKBgQC8fpi06NfVYHAOAnxNMVnTXr/ptsLsNjP+uAt2eO0cc5J9H5XV\n8lFVujOrRu/JWi1TDmAvOaf/6A3BphIA1Pwp0AAqlZdwizIum8j0KzpsGYH5qReN\nQDwF3oUSKMsQCCGCDHrDYifG/pRi9bN1ZVjEXPr35HJuBe+FQpZTs8DewwIDAQAB\nAoGARfNxNknmtx/n1bskZ/01iZRzAge6BLEE0LV6Q4gS7mkRZu/Oyiv39Sl5vUlA\n+WdGxLjkBwKNjxGN8Vxw9/ASd8rSsqeAUYIwAeifXrHhj5DBPQT/pDPkeFnp9B1w\nC6jo+3AbBQ4/b0ONSIEnCL2xGGglSIAxO17T1ViXp7lzXPECQQDe63nkRdWM0OCb\noaHQPT3E26224maIstrGFUdt9yw3yJf4bOF7TtiPLlLuHsTTge3z+fG6ntC0xG56\n1cl37C3ZAkEA2HdVcRGugNp/qmVz4LJTpD+WZKi73PLAO47wDOrYh9Pn2I6fcEH0\nCPnggt1ko4ujvGzFTvRH64HXa6aPCv1j+wJBAMQMah3VQPNf/DlDVFEUmw9XeBZg\nVHaifX851aEjgXLp6qVj9IYCmLiLsAmVa9rr6P7p8asD418nZlaHUHE0eDkCQQCr\nuxis6GMx1Ka971jcJX2X696LoxXPd0KsvXySMupv79yagKPa8mgBiwPjrnK+EPVo\ncj6iochA/bSCshP/mwFrAkBHEKPi6V6gb94JinCT7x3weahbdp6bJ6/nzBH/p9VA\nHoT1JtwNFhGv9BCjmDydshQHfSWpY9NxlccBKL7ITm8R\n-----END RSA PRIVATE KEY-----"
+ }
+}
diff --git a/library/oauth2/test/lib/OAuth2/Request/TestRequest.php b/vendor/bshaffer/oauth2-server-php/test/lib/OAuth2/Request/TestRequest.php
index 7bbce28a4..7bbce28a4 100644
--- a/library/oauth2/test/lib/OAuth2/Request/TestRequest.php
+++ b/vendor/bshaffer/oauth2-server-php/test/lib/OAuth2/Request/TestRequest.php
diff --git a/vendor/bshaffer/oauth2-server-php/test/lib/OAuth2/Storage/BaseTest.php b/vendor/bshaffer/oauth2-server-php/test/lib/OAuth2/Storage/BaseTest.php
new file mode 100755
index 000000000..f0b1274a2
--- /dev/null
+++ b/vendor/bshaffer/oauth2-server-php/test/lib/OAuth2/Storage/BaseTest.php
@@ -0,0 +1,36 @@
+<?php
+
+namespace OAuth2\Storage;
+
+abstract class BaseTest extends \PHPUnit_Framework_TestCase
+{
+ public function provideStorage()
+ {
+ $memory = Bootstrap::getInstance()->getMemoryStorage();
+ $sqlite = Bootstrap::getInstance()->getSqlitePdo();
+ $mysql = Bootstrap::getInstance()->getMysqlPdo();
+ $postgres = Bootstrap::getInstance()->getPostgresPdo();
+ $mongo = Bootstrap::getInstance()->getMongo();
+ $mongoDb = Bootstrap::getInstance()->getMongoDB();
+ $redis = Bootstrap::getInstance()->getRedisStorage();
+ $cassandra = Bootstrap::getInstance()->getCassandraStorage();
+ $dynamodb = Bootstrap::getInstance()->getDynamoDbStorage();
+ $couchbase = Bootstrap::getInstance()->getCouchbase();
+
+ /* hack until we can fix "default_scope" dependencies in other tests */
+ $memory->defaultScope = 'defaultscope1 defaultscope2';
+
+ return array(
+ array($memory),
+ array($sqlite),
+ array($mysql),
+ array($postgres),
+ array($mongo),
+ array($mongoDb),
+ array($redis),
+ array($cassandra),
+ array($dynamodb),
+ array($couchbase),
+ );
+ }
+}
diff --git a/vendor/bshaffer/oauth2-server-php/test/lib/OAuth2/Storage/Bootstrap.php b/vendor/bshaffer/oauth2-server-php/test/lib/OAuth2/Storage/Bootstrap.php
new file mode 100755
index 000000000..3d7bdd4e9
--- /dev/null
+++ b/vendor/bshaffer/oauth2-server-php/test/lib/OAuth2/Storage/Bootstrap.php
@@ -0,0 +1,967 @@
+<?php
+
+namespace OAuth2\Storage;
+
+class Bootstrap
+{
+ const DYNAMODB_PHP_VERSION = 'none';
+
+ protected static $instance;
+ private $mysql;
+ private $sqlite;
+ private $postgres;
+ private $mongo;
+ private $mongoDb;
+ private $redis;
+ private $cassandra;
+ private $configDir;
+ private $dynamodb;
+ private $couchbase;
+
+ public function __construct()
+ {
+ $this->configDir = __DIR__.'/../../../config';
+ }
+
+ public static function getInstance()
+ {
+ if (!self::$instance) {
+ self::$instance = new self();
+ }
+
+ return self::$instance;
+ }
+
+ public function getSqlitePdo()
+ {
+ if (!$this->sqlite) {
+ $this->removeSqliteDb();
+ $pdo = new \PDO(sprintf('sqlite://%s', $this->getSqliteDir()));
+ $pdo->setAttribute(\PDO::ATTR_ERRMODE, \PDO::ERRMODE_EXCEPTION);
+ $this->createSqliteDb($pdo);
+
+ $this->sqlite = new Pdo($pdo);
+ }
+
+ return $this->sqlite;
+ }
+
+ public function getPostgresPdo()
+ {
+ if (!$this->postgres) {
+ if (in_array('pgsql', \PDO::getAvailableDrivers())) {
+ $this->removePostgresDb();
+ $this->createPostgresDb();
+ if ($pdo = $this->getPostgresDriver()) {
+ $pdo->setAttribute(\PDO::ATTR_ERRMODE, \PDO::ERRMODE_EXCEPTION);
+ $this->populatePostgresDb($pdo);
+ $this->postgres = new Pdo($pdo);
+ }
+ } else {
+ $this->postgres = new NullStorage('Postgres', 'Missing postgres PDO extension.');
+ }
+ }
+
+ return $this->postgres;
+ }
+
+ public function getPostgresDriver()
+ {
+ try {
+ $pdo = new \PDO('pgsql:host=localhost;dbname=oauth2_server_php', 'postgres');
+
+ return $pdo;
+ } catch (\PDOException $e) {
+ $this->postgres = new NullStorage('Postgres', $e->getMessage());
+ }
+ }
+
+ public function getMemoryStorage()
+ {
+ return new Memory(json_decode(file_get_contents($this->configDir. '/storage.json'), true));
+ }
+
+ public function getRedisStorage()
+ {
+ if (!$this->redis) {
+ if (class_exists('Predis\Client')) {
+ $redis = new \Predis\Client();
+ if ($this->testRedisConnection($redis)) {
+ $redis->flushdb();
+ $this->redis = new Redis($redis);
+ $this->createRedisDb($this->redis);
+ } else {
+ $this->redis = new NullStorage('Redis', 'Unable to connect to redis server on port 6379');
+ }
+ } else {
+ $this->redis = new NullStorage('Redis', 'Missing redis library. Please run "composer.phar require predis/predis:dev-master"');
+ }
+ }
+
+ return $this->redis;
+ }
+
+ private function testRedisConnection(\Predis\Client $redis)
+ {
+ try {
+ $redis->connect();
+ } catch (\Predis\CommunicationException $exception) {
+ // we were unable to connect to the redis server
+ return false;
+ }
+
+ return true;
+ }
+
+ public function getMysqlPdo()
+ {
+ if (!$this->mysql) {
+ $pdo = null;
+ try {
+ $pdo = new \PDO('mysql:host=localhost;', 'root');
+ } catch (\PDOException $e) {
+ $this->mysql = new NullStorage('MySQL', 'Unable to connect to MySQL on root@localhost');
+ }
+
+ if ($pdo) {
+ $pdo->setAttribute(\PDO::ATTR_ERRMODE, \PDO::ERRMODE_EXCEPTION);
+ $this->removeMysqlDb($pdo);
+ $this->createMysqlDb($pdo);
+
+ $this->mysql = new Pdo($pdo);
+ }
+ }
+
+ return $this->mysql;
+ }
+
+ public function getMongo()
+ {
+ if (!$this->mongo) {
+ if (class_exists('MongoClient')) {
+ $mongo = new \MongoClient('mongodb://localhost:27017', array('connect' => false));
+ if ($this->testMongoConnection($mongo)) {
+ $db = $mongo->oauth2_server_php_legacy;
+ $this->removeMongo($db);
+ $this->createMongo($db);
+
+ $this->mongo = new Mongo($db);
+ } else {
+ $this->mongo = new NullStorage('Mongo', 'Unable to connect to mongo server on "localhost:27017"');
+ }
+ } else {
+ $this->mongo = new NullStorage('Mongo', 'Missing mongo php extension. Please install mongo.so');
+ }
+ }
+
+ return $this->mongo;
+ }
+
+ public function getMongoDb()
+ {
+ if (!$this->mongoDb) {
+ if (class_exists('MongoDB\Client')) {
+ $mongoDb = new \MongoDB\Client('mongodb://localhost:27017');
+ if ($this->testMongoDBConnection($mongoDb)) {
+ $db = $mongoDb->oauth2_server_php;
+ $this->removeMongoDb($db);
+ $this->createMongoDb($db);
+
+ $this->mongoDb = new MongoDB($db);
+ } else {
+ $this->mongoDb = new NullStorage('MongoDB', 'Unable to connect to mongo server on "localhost:27017"');
+ }
+ } else {
+ $this->mongoDb = new NullStorage('MongoDB', 'Missing MongoDB php extension. Please install mongodb.so');
+ }
+ }
+
+ return $this->mongoDb;
+ }
+
+ private function testMongoConnection(\MongoClient $mongo)
+ {
+ try {
+ $mongo->connect();
+ } catch (\MongoConnectionException $e) {
+ return false;
+ }
+
+ return true;
+ }
+
+ private function testMongoDBConnection(\MongoDB\Client $mongo)
+ {
+ return true;
+ }
+
+ public function getCouchbase()
+ {
+ if (!$this->couchbase) {
+ if ($this->getEnvVar('SKIP_COUCHBASE_TESTS')) {
+ $this->couchbase = new NullStorage('Couchbase', 'Skipping Couchbase tests');
+ } elseif (!class_exists('Couchbase')) {
+ $this->couchbase = new NullStorage('Couchbase', 'Missing Couchbase php extension. Please install couchbase.so');
+ } else {
+ // round-about way to make sure couchbase is working
+ // this is required because it throws a "floating point exception" otherwise
+ $code = "new \Couchbase(array('localhost:8091'), '', '', 'auth', false);";
+ $exec = sprintf('php -r "%s"', $code);
+ $ret = exec($exec, $test, $var);
+ if ($ret != 0) {
+ $couchbase = new \Couchbase(array('localhost:8091'), '', '', 'auth', false);
+ if ($this->testCouchbaseConnection($couchbase)) {
+ $this->clearCouchbase($couchbase);
+ $this->createCouchbaseDB($couchbase);
+
+ $this->couchbase = new CouchbaseDB($couchbase);
+ } else {
+ $this->couchbase = new NullStorage('Couchbase', 'Unable to connect to Couchbase server on "localhost:8091"');
+ }
+ } else {
+ $this->couchbase = new NullStorage('Couchbase', 'Error while trying to connect to Couchbase');
+ }
+ }
+ }
+
+ return $this->couchbase;
+ }
+
+ private function testCouchbaseConnection(\Couchbase $couchbase)
+ {
+ try {
+ if (count($couchbase->getServers()) > 0) {
+ return true;
+ }
+ } catch (\CouchbaseException $e) {
+ return false;
+ }
+
+ return true;
+ }
+
+ public function getCassandraStorage()
+ {
+ if (!$this->cassandra) {
+ if (class_exists('phpcassa\ColumnFamily')) {
+ $cassandra = new \phpcassa\Connection\ConnectionPool('oauth2_test', array('127.0.0.1:9160'));
+ if ($this->testCassandraConnection($cassandra)) {
+ $this->removeCassandraDb();
+ $this->cassandra = new Cassandra($cassandra);
+ $this->createCassandraDb($this->cassandra);
+ } else {
+ $this->cassandra = new NullStorage('Cassandra', 'Unable to connect to cassandra server on "127.0.0.1:9160"');
+ }
+ } else {
+ $this->cassandra = new NullStorage('Cassandra', 'Missing cassandra library. Please run "composer.phar require thobbs/phpcassa:dev-master"');
+ }
+ }
+
+ return $this->cassandra;
+ }
+
+ private function testCassandraConnection(\phpcassa\Connection\ConnectionPool $cassandra)
+ {
+ try {
+ new \phpcassa\SystemManager('localhost:9160');
+ } catch (\Exception $e) {
+ return false;
+ }
+
+ return true;
+ }
+
+ private function removeCassandraDb()
+ {
+ $sys = new \phpcassa\SystemManager('localhost:9160');
+
+ try {
+ $sys->drop_keyspace('oauth2_test');
+ } catch (\cassandra\InvalidRequestException $e) {
+
+ }
+ }
+
+ private function createCassandraDb(Cassandra $storage)
+ {
+ // create the cassandra keyspace and column family
+ $sys = new \phpcassa\SystemManager('localhost:9160');
+
+ $sys->create_keyspace('oauth2_test', array(
+ "strategy_class" => \phpcassa\Schema\StrategyClass::SIMPLE_STRATEGY,
+ "strategy_options" => array('replication_factor' => '1')
+ ));
+
+ $sys->create_column_family('oauth2_test', 'auth');
+ $cassandra = new \phpcassa\Connection\ConnectionPool('oauth2_test', array('127.0.0.1:9160'));
+ $cf = new \phpcassa\ColumnFamily($cassandra, 'auth');
+
+ // populate the data
+ $storage->setClientDetails("oauth_test_client", "testpass", "http://example.com", 'implicit password');
+ $storage->setAccessToken("testtoken", "Some Client", '', time() + 1000);
+ $storage->setAuthorizationCode("testcode", "Some Client", '', '', time() + 1000);
+
+ $storage->setScope('supportedscope1 supportedscope2 supportedscope3 supportedscope4');
+ $storage->setScope('defaultscope1 defaultscope2', null, 'default');
+
+ $storage->setScope('clientscope1 clientscope2', 'Test Client ID');
+ $storage->setScope('clientscope1 clientscope2', 'Test Client ID', 'default');
+
+ $storage->setScope('clientscope1 clientscope2 clientscope3', 'Test Client ID 2');
+ $storage->setScope('clientscope1 clientscope2', 'Test Client ID 2', 'default');
+
+ $storage->setScope('clientscope1 clientscope2', 'Test Default Scope Client ID');
+ $storage->setScope('clientscope1 clientscope2', 'Test Default Scope Client ID', 'default');
+
+ $storage->setScope('clientscope1 clientscope2 clientscope3', 'Test Default Scope Client ID 2');
+ $storage->setScope('clientscope3', 'Test Default Scope Client ID 2', 'default');
+
+ $storage->setClientKey('oauth_test_client', $this->getTestPublicKey(), 'test_subject');
+
+ $cf->insert("oauth_public_keys:ClientID_One", array('__data' => json_encode(array("public_key" => "client_1_public", "private_key" => "client_1_private", "encryption_algorithm" => "RS256"))));
+ $cf->insert("oauth_public_keys:ClientID_Two", array('__data' => json_encode(array("public_key" => "client_2_public", "private_key" => "client_2_private", "encryption_algorithm" => "RS256"))));
+ $cf->insert("oauth_public_keys:", array('__data' => json_encode(array("public_key" => $this->getTestPublicKey(), "private_key" => $this->getTestPrivateKey(), "encryption_algorithm" => "RS256"))));
+
+ $cf->insert("oauth_users:testuser", array('__data' =>json_encode(array("password" => "password", "email" => "testuser@test.com", "email_verified" => true))));
+
+ }
+
+ private function createSqliteDb(\PDO $pdo)
+ {
+ $this->runPdoSql($pdo);
+ }
+
+ private function removeSqliteDb()
+ {
+ if (file_exists($this->getSqliteDir())) {
+ unlink($this->getSqliteDir());
+ }
+ }
+
+ private function createMysqlDb(\PDO $pdo)
+ {
+ $pdo->exec('CREATE DATABASE oauth2_server_php');
+ $pdo->exec('USE oauth2_server_php');
+ $this->runPdoSql($pdo);
+ }
+
+ private function removeMysqlDb(\PDO $pdo)
+ {
+ $pdo->exec('DROP DATABASE IF EXISTS oauth2_server_php');
+ }
+
+ private function createPostgresDb()
+ {
+ if (!`psql postgres -tAc "SELECT 1 FROM pg_roles WHERE rolname='postgres'"`) {
+ `createuser -s -r postgres`;
+ }
+
+ `createdb -O postgres oauth2_server_php`;
+ }
+
+ private function populatePostgresDb(\PDO $pdo)
+ {
+ $this->runPdoSql($pdo);
+ }
+
+ private function removePostgresDb()
+ {
+ if (trim(`psql -l | grep oauth2_server_php | wc -l`)) {
+ `dropdb oauth2_server_php`;
+ }
+ }
+
+ public function runPdoSql(\PDO $pdo)
+ {
+ $storage = new Pdo($pdo);
+ foreach (explode(';', $storage->getBuildSql()) as $statement) {
+ $result = $pdo->exec($statement);
+ }
+
+ // set up scopes
+ $sql = 'INSERT INTO oauth_scopes (scope) VALUES (?)';
+ foreach (explode(' ', 'supportedscope1 supportedscope2 supportedscope3 supportedscope4 clientscope1 clientscope2 clientscope3') as $supportedScope) {
+ $pdo->prepare($sql)->execute(array($supportedScope));
+ }
+
+ $sql = 'INSERT INTO oauth_scopes (scope, is_default) VALUES (?, ?)';
+ foreach (array('defaultscope1', 'defaultscope2') as $defaultScope) {
+ $pdo->prepare($sql)->execute(array($defaultScope, true));
+ }
+
+ // set up clients
+ $sql = 'INSERT INTO oauth_clients (client_id, client_secret, scope, grant_types) VALUES (?, ?, ?, ?)';
+ $pdo->prepare($sql)->execute(array('Test Client ID', 'TestSecret', 'clientscope1 clientscope2', null));
+ $pdo->prepare($sql)->execute(array('Test Client ID 2', 'TestSecret', 'clientscope1 clientscope2 clientscope3', null));
+ $pdo->prepare($sql)->execute(array('Test Default Scope Client ID', 'TestSecret', 'clientscope1 clientscope2', null));
+ $pdo->prepare($sql)->execute(array('oauth_test_client', 'testpass', null, 'implicit password'));
+
+ // set up misc
+ $sql = 'INSERT INTO oauth_access_tokens (access_token, client_id, expires, user_id) VALUES (?, ?, ?, ?)';
+ $pdo->prepare($sql)->execute(array('testtoken', 'Some Client', date('Y-m-d H:i:s', strtotime('+1 hour')), null));
+ $pdo->prepare($sql)->execute(array('accesstoken-openid-connect', 'Some Client', date('Y-m-d H:i:s', strtotime('+1 hour')), 'testuser'));
+
+ $sql = 'INSERT INTO oauth_authorization_codes (authorization_code, client_id, expires) VALUES (?, ?, ?)';
+ $pdo->prepare($sql)->execute(array('testcode', 'Some Client', date('Y-m-d H:i:s', strtotime('+1 hour'))));
+
+ $sql = 'INSERT INTO oauth_users (username, password, email, email_verified) VALUES (?, ?, ?, ?)';
+ $pdo->prepare($sql)->execute(array('testuser', 'password', 'testuser@test.com', true));
+
+ $sql = 'INSERT INTO oauth_public_keys (client_id, public_key, private_key, encryption_algorithm) VALUES (?, ?, ?, ?)';
+ $pdo->prepare($sql)->execute(array('ClientID_One', 'client_1_public', 'client_1_private', 'RS256'));
+ $pdo->prepare($sql)->execute(array('ClientID_Two', 'client_2_public', 'client_2_private', 'RS256'));
+
+ $sql = 'INSERT INTO oauth_public_keys (client_id, public_key, private_key, encryption_algorithm) VALUES (?, ?, ?, ?)';
+ $pdo->prepare($sql)->execute(array(null, $this->getTestPublicKey(), $this->getTestPrivateKey(), 'RS256'));
+
+ $sql = 'INSERT INTO oauth_jwt (client_id, subject, public_key) VALUES (?, ?, ?)';
+ $pdo->prepare($sql)->execute(array('oauth_test_client', 'test_subject', $this->getTestPublicKey()));
+ }
+
+ public function getSqliteDir()
+ {
+ return $this->configDir. '/test.sqlite';
+ }
+
+ public function getConfigDir()
+ {
+ return $this->configDir;
+ }
+
+ private function createCouchbaseDB(\Couchbase $db)
+ {
+ $db->set('oauth_clients-oauth_test_client',json_encode(array(
+ 'client_id' => "oauth_test_client",
+ 'client_secret' => "testpass",
+ 'redirect_uri' => "http://example.com",
+ 'grant_types' => 'implicit password'
+ )));
+
+ $db->set('oauth_access_tokens-testtoken',json_encode(array(
+ 'access_token' => "testtoken",
+ 'client_id' => "Some Client"
+ )));
+
+ $db->set('oauth_authorization_codes-testcode',json_encode(array(
+ 'access_token' => "testcode",
+ 'client_id' => "Some Client"
+ )));
+
+ $db->set('oauth_users-testuser',json_encode(array(
+ 'username' => 'testuser',
+ 'password' => 'password',
+ 'email' => 'testuser@test.com',
+ 'email_verified' => true,
+ )));
+
+ $db->set('oauth_jwt-oauth_test_client',json_encode(array(
+ 'client_id' => 'oauth_test_client',
+ 'key' => $this->getTestPublicKey(),
+ 'subject' => 'test_subject',
+ )));
+ }
+
+ private function clearCouchbase(\Couchbase $cb)
+ {
+ $cb->delete('oauth_authorization_codes-new-openid-code');
+ $cb->delete('oauth_access_tokens-newtoken');
+ $cb->delete('oauth_authorization_codes-newcode');
+ $cb->delete('oauth_refresh_tokens-refreshtoken');
+ }
+
+ private function createMongo(\MongoDB $db)
+ {
+ $db->oauth_clients->insert(array(
+ 'client_id' => "oauth_test_client",
+ 'client_secret' => "testpass",
+ 'redirect_uri' => "http://example.com",
+ 'grant_types' => 'implicit password'
+ ));
+
+ $db->oauth_access_tokens->insert(array(
+ 'access_token' => "testtoken",
+ 'client_id' => "Some Client"
+ ));
+
+ $db->oauth_authorization_codes->insert(array(
+ 'authorization_code' => "testcode",
+ 'client_id' => "Some Client"
+ ));
+
+ $db->oauth_users->insert(array(
+ 'username' => 'testuser',
+ 'password' => 'password',
+ 'email' => 'testuser@test.com',
+ 'email_verified' => true,
+ ));
+
+ $db->oauth_keys->insert(array(
+ 'client_id' => null,
+ 'public_key' => $this->getTestPublicKey(),
+ 'private_key' => $this->getTestPrivateKey(),
+ 'encryption_algorithm' => 'RS256'
+ ));
+
+ $db->oauth_jwt->insert(array(
+ 'client_id' => 'oauth_test_client',
+ 'key' => $this->getTestPublicKey(),
+ 'subject' => 'test_subject',
+ ));
+ }
+
+ public function removeMongo(\MongoDB $db)
+ {
+ $db->drop();
+ }
+
+ private function createMongoDB(\MongoDB\Database $db)
+ {
+ $db->oauth_clients->insertOne(array(
+ 'client_id' => "oauth_test_client",
+ 'client_secret' => "testpass",
+ 'redirect_uri' => "http://example.com",
+ 'grant_types' => 'implicit password'
+ ));
+
+ $db->oauth_access_tokens->insertOne(array(
+ 'access_token' => "testtoken",
+ 'client_id' => "Some Client"
+ ));
+
+ $db->oauth_authorization_codes->insertOne(array(
+ 'authorization_code' => "testcode",
+ 'client_id' => "Some Client"
+ ));
+
+ $db->oauth_users->insertOne(array(
+ 'username' => 'testuser',
+ 'password' => 'password',
+ 'email' => 'testuser@test.com',
+ 'email_verified' => true,
+ ));
+
+ $db->oauth_keys->insertOne(array(
+ 'client_id' => null,
+ 'public_key' => $this->getTestPublicKey(),
+ 'private_key' => $this->getTestPrivateKey(),
+ 'encryption_algorithm' => 'RS256'
+ ));
+
+ $db->oauth_jwt->insertOne(array(
+ 'client_id' => 'oauth_test_client',
+ 'key' => $this->getTestPublicKey(),
+ 'subject' => 'test_subject',
+ ));
+ }
+
+ public function removeMongoDB(\MongoDB\Database $db)
+ {
+ $db->drop();
+ }
+
+ private function createRedisDb(Redis $storage)
+ {
+ $storage->setClientDetails("oauth_test_client", "testpass", "http://example.com", 'implicit password');
+ $storage->setAccessToken("testtoken", "Some Client", '', time() + 1000);
+ $storage->setAuthorizationCode("testcode", "Some Client", '', '', time() + 1000);
+ $storage->setUser("testuser", "password");
+
+ $storage->setScope('supportedscope1 supportedscope2 supportedscope3 supportedscope4');
+ $storage->setScope('defaultscope1 defaultscope2', null, 'default');
+
+ $storage->setScope('clientscope1 clientscope2', 'Test Client ID');
+ $storage->setScope('clientscope1 clientscope2', 'Test Client ID', 'default');
+
+ $storage->setScope('clientscope1 clientscope2 clientscope3', 'Test Client ID 2');
+ $storage->setScope('clientscope1 clientscope2', 'Test Client ID 2', 'default');
+
+ $storage->setScope('clientscope1 clientscope2', 'Test Default Scope Client ID');
+ $storage->setScope('clientscope1 clientscope2', 'Test Default Scope Client ID', 'default');
+
+ $storage->setScope('clientscope1 clientscope2 clientscope3', 'Test Default Scope Client ID 2');
+ $storage->setScope('clientscope3', 'Test Default Scope Client ID 2', 'default');
+
+ $storage->setClientKey('oauth_test_client', $this->getTestPublicKey(), 'test_subject');
+ }
+
+ public function getTestPublicKey()
+ {
+ return file_get_contents(__DIR__.'/../../../config/keys/id_rsa.pub');
+ }
+
+ private function getTestPrivateKey()
+ {
+ return file_get_contents(__DIR__.'/../../../config/keys/id_rsa');
+ }
+
+ public function getDynamoDbStorage()
+ {
+ if (!$this->dynamodb) {
+ // only run once per travis build
+ if (true == $this->getEnvVar('TRAVIS')) {
+ if (self::DYNAMODB_PHP_VERSION != $this->getEnvVar('TRAVIS_PHP_VERSION')) {
+ $this->dynamodb = new NullStorage('DynamoDb', 'Skipping for travis.ci - only run once per build');
+
+ return;
+ }
+ }
+ if (class_exists('\Aws\DynamoDb\DynamoDbClient')) {
+ if ($client = $this->getDynamoDbClient()) {
+ // travis runs a unique set of tables per build, to avoid conflict
+ $prefix = '';
+ if ($build_id = $this->getEnvVar('TRAVIS_JOB_NUMBER')) {
+ $prefix = sprintf('build_%s_', $build_id);
+ } else {
+ if (!$this->deleteDynamoDb($client, $prefix, true)) {
+ return $this->dynamodb = new NullStorage('DynamoDb', 'Timed out while waiting for DynamoDB deletion (30 seconds)');
+ }
+ }
+ $this->createDynamoDb($client, $prefix);
+ $this->populateDynamoDb($client, $prefix);
+ $config = array(
+ 'client_table' => $prefix.'oauth_clients',
+ 'access_token_table' => $prefix.'oauth_access_tokens',
+ 'refresh_token_table' => $prefix.'oauth_refresh_tokens',
+ 'code_table' => $prefix.'oauth_authorization_codes',
+ 'user_table' => $prefix.'oauth_users',
+ 'jwt_table' => $prefix.'oauth_jwt',
+ 'scope_table' => $prefix.'oauth_scopes',
+ 'public_key_table' => $prefix.'oauth_public_keys',
+ );
+ $this->dynamodb = new DynamoDB($client, $config);
+ } elseif (!$this->dynamodb) {
+ $this->dynamodb = new NullStorage('DynamoDb', 'unable to connect to DynamoDB');
+ }
+ } else {
+ $this->dynamodb = new NullStorage('DynamoDb', 'Missing DynamoDB library. Please run "composer.phar require aws/aws-sdk-php:dev-master');
+ }
+ }
+
+ return $this->dynamodb;
+ }
+
+ private function getDynamoDbClient()
+ {
+ $config = array();
+ // check for environment variables
+ if (($key = $this->getEnvVar('AWS_ACCESS_KEY_ID')) && ($secret = $this->getEnvVar('AWS_SECRET_KEY'))) {
+ $config['key'] = $key;
+ $config['secret'] = $secret;
+ } else {
+ // fall back on ~/.aws/credentials file
+ // @see http://docs.aws.amazon.com/aws-sdk-php/guide/latest/credentials.html#credential-profiles
+ if (!file_exists($this->getEnvVar('HOME') . '/.aws/credentials')) {
+ $this->dynamodb = new NullStorage('DynamoDb', 'No aws credentials file found, and no AWS_ACCESS_KEY_ID or AWS_SECRET_KEY environment variable set');
+
+ return;
+ }
+
+ // set profile in AWS_PROFILE environment variable, defaults to "default"
+ $config['profile'] = $this->getEnvVar('AWS_PROFILE', 'default');
+ }
+
+ // set region in AWS_REGION environment variable, defaults to "us-east-1"
+ $config['region'] = $this->getEnvVar('AWS_REGION', \Aws\Common\Enum\Region::US_EAST_1);
+
+ return \Aws\DynamoDb\DynamoDbClient::factory($config);
+ }
+
+ private function deleteDynamoDb(\Aws\DynamoDb\DynamoDbClient $client, $prefix = null, $waitForDeletion = false)
+ {
+ $tablesList = explode(' ', 'oauth_access_tokens oauth_authorization_codes oauth_clients oauth_jwt oauth_public_keys oauth_refresh_tokens oauth_scopes oauth_users');
+ $nbTables = count($tablesList);
+
+ // Delete all table.
+ foreach ($tablesList as $key => $table) {
+ try {
+ $client->deleteTable(array('TableName' => $prefix.$table));
+ } catch (\Aws\DynamoDb\Exception\DynamoDbException $e) {
+ // Table does not exist : nothing to do
+ }
+ }
+
+ // Wait for deleting
+ if ($waitForDeletion) {
+ $retries = 5;
+ $nbTableDeleted = 0;
+ while ($nbTableDeleted != $nbTables) {
+ $nbTableDeleted = 0;
+ foreach ($tablesList as $key => $table) {
+ try {
+ $result = $client->describeTable(array('TableName' => $prefix.$table));
+ } catch (\Aws\DynamoDb\Exception\DynamoDbException $e) {
+ // Table does not exist : nothing to do
+ $nbTableDeleted++;
+ }
+ }
+ if ($nbTableDeleted != $nbTables) {
+ if ($retries < 0) {
+ // we are tired of waiting
+ return false;
+ }
+ sleep(5);
+ echo "Sleeping 5 seconds for DynamoDB ($retries more retries)...\n";
+ $retries--;
+ }
+ }
+ }
+
+ return true;
+ }
+
+ private function createDynamoDb(\Aws\DynamoDb\DynamoDbClient $client, $prefix = null)
+ {
+ $tablesList = explode(' ', 'oauth_access_tokens oauth_authorization_codes oauth_clients oauth_jwt oauth_public_keys oauth_refresh_tokens oauth_scopes oauth_users');
+ $nbTables = count($tablesList);
+ $client->createTable(array(
+ 'TableName' => $prefix.'oauth_access_tokens',
+ 'AttributeDefinitions' => array(
+ array('AttributeName' => 'access_token','AttributeType' => 'S')
+ ),
+ 'KeySchema' => array(array('AttributeName' => 'access_token','KeyType' => 'HASH')),
+ 'ProvisionedThroughput' => array('ReadCapacityUnits' => 1,'WriteCapacityUnits' => 1)
+ ));
+
+ $client->createTable(array(
+ 'TableName' => $prefix.'oauth_authorization_codes',
+ 'AttributeDefinitions' => array(
+ array('AttributeName' => 'authorization_code','AttributeType' => 'S')
+ ),
+ 'KeySchema' => array(array('AttributeName' => 'authorization_code','KeyType' => 'HASH')),
+ 'ProvisionedThroughput' => array('ReadCapacityUnits' => 1,'WriteCapacityUnits' => 1)
+ ));
+
+ $client->createTable(array(
+ 'TableName' => $prefix.'oauth_clients',
+ 'AttributeDefinitions' => array(
+ array('AttributeName' => 'client_id','AttributeType' => 'S')
+ ),
+ 'KeySchema' => array(array('AttributeName' => 'client_id','KeyType' => 'HASH')),
+ 'ProvisionedThroughput' => array('ReadCapacityUnits' => 1,'WriteCapacityUnits' => 1)
+ ));
+
+ $client->createTable(array(
+ 'TableName' => $prefix.'oauth_jwt',
+ 'AttributeDefinitions' => array(
+ array('AttributeName' => 'client_id','AttributeType' => 'S'),
+ array('AttributeName' => 'subject','AttributeType' => 'S')
+ ),
+ 'KeySchema' => array(
+ array('AttributeName' => 'client_id','KeyType' => 'HASH'),
+ array('AttributeName' => 'subject','KeyType' => 'RANGE')
+ ),
+ 'ProvisionedThroughput' => array('ReadCapacityUnits' => 1,'WriteCapacityUnits' => 1)
+ ));
+
+ $client->createTable(array(
+ 'TableName' => $prefix.'oauth_public_keys',
+ 'AttributeDefinitions' => array(
+ array('AttributeName' => 'client_id','AttributeType' => 'S')
+ ),
+ 'KeySchema' => array(array('AttributeName' => 'client_id','KeyType' => 'HASH')),
+ 'ProvisionedThroughput' => array('ReadCapacityUnits' => 1,'WriteCapacityUnits' => 1)
+ ));
+
+ $client->createTable(array(
+ 'TableName' => $prefix.'oauth_refresh_tokens',
+ 'AttributeDefinitions' => array(
+ array('AttributeName' => 'refresh_token','AttributeType' => 'S')
+ ),
+ 'KeySchema' => array(array('AttributeName' => 'refresh_token','KeyType' => 'HASH')),
+ 'ProvisionedThroughput' => array('ReadCapacityUnits' => 1,'WriteCapacityUnits' => 1)
+ ));
+
+ $client->createTable(array(
+ 'TableName' => $prefix.'oauth_scopes',
+ 'AttributeDefinitions' => array(
+ array('AttributeName' => 'scope','AttributeType' => 'S'),
+ array('AttributeName' => 'is_default','AttributeType' => 'S')
+ ),
+ 'KeySchema' => array(array('AttributeName' => 'scope','KeyType' => 'HASH')),
+ 'GlobalSecondaryIndexes' => array(
+ array(
+ 'IndexName' => 'is_default-index',
+ 'KeySchema' => array(array('AttributeName' => 'is_default', 'KeyType' => 'HASH')),
+ 'Projection' => array('ProjectionType' => 'ALL'),
+ 'ProvisionedThroughput' => array('ReadCapacityUnits' => 1,'WriteCapacityUnits' => 1)
+ ),
+ ),
+ 'ProvisionedThroughput' => array('ReadCapacityUnits' => 1,'WriteCapacityUnits' => 1)
+ ));
+
+ $client->createTable(array(
+ 'TableName' => $prefix.'oauth_users',
+ 'AttributeDefinitions' => array(array('AttributeName' => 'username','AttributeType' => 'S')),
+ 'KeySchema' => array(array('AttributeName' => 'username','KeyType' => 'HASH')),
+ 'ProvisionedThroughput' => array('ReadCapacityUnits' => 1,'WriteCapacityUnits' => 1)
+ ));
+
+ // Wait for creation
+ $nbTableCreated = 0;
+ while ($nbTableCreated != $nbTables) {
+ $nbTableCreated = 0;
+ foreach ($tablesList as $key => $table) {
+ try {
+ $result = $client->describeTable(array('TableName' => $prefix.$table));
+ if ($result['Table']['TableStatus'] == 'ACTIVE') {
+ $nbTableCreated++;
+ }
+ } catch (\Aws\DynamoDb\Exception\DynamoDbException $e) {
+ // Table does not exist : nothing to do
+ $nbTableCreated++;
+ }
+ }
+ if ($nbTableCreated != $nbTables) {
+ sleep(1);
+ }
+ }
+ }
+
+ private function populateDynamoDb($client, $prefix = null)
+ {
+ // set up scopes
+ foreach (explode(' ', 'supportedscope1 supportedscope2 supportedscope3 supportedscope4 clientscope1 clientscope2 clientscope3') as $supportedScope) {
+ $client->putItem(array(
+ 'TableName' => $prefix.'oauth_scopes',
+ 'Item' => array('scope' => array('S' => $supportedScope))
+ ));
+ }
+
+ foreach (array('defaultscope1', 'defaultscope2') as $defaultScope) {
+ $client->putItem(array(
+ 'TableName' => $prefix.'oauth_scopes',
+ 'Item' => array('scope' => array('S' => $defaultScope), 'is_default' => array('S' => "true"))
+ ));
+ }
+
+ $client->putItem(array(
+ 'TableName' => $prefix.'oauth_clients',
+ 'Item' => array(
+ 'client_id' => array('S' => 'Test Client ID'),
+ 'client_secret' => array('S' => 'TestSecret'),
+ 'scope' => array('S' => 'clientscope1 clientscope2')
+ )
+ ));
+
+ $client->putItem(array(
+ 'TableName' => $prefix.'oauth_clients',
+ 'Item' => array(
+ 'client_id' => array('S' => 'Test Client ID 2'),
+ 'client_secret' => array('S' => 'TestSecret'),
+ 'scope' => array('S' => 'clientscope1 clientscope2 clientscope3')
+ )
+ ));
+
+ $client->putItem(array(
+ 'TableName' => $prefix.'oauth_clients',
+ 'Item' => array(
+ 'client_id' => array('S' => 'Test Default Scope Client ID'),
+ 'client_secret' => array('S' => 'TestSecret'),
+ 'scope' => array('S' => 'clientscope1 clientscope2')
+ )
+ ));
+
+ $client->putItem(array(
+ 'TableName' => $prefix.'oauth_clients',
+ 'Item' => array(
+ 'client_id' => array('S' => 'oauth_test_client'),
+ 'client_secret' => array('S' => 'testpass'),
+ 'grant_types' => array('S' => 'implicit password')
+ )
+ ));
+
+ $client->putItem(array(
+ 'TableName' => $prefix.'oauth_access_tokens',
+ 'Item' => array(
+ 'access_token' => array('S' => 'testtoken'),
+ 'client_id' => array('S' => 'Some Client'),
+ )
+ ));
+
+ $client->putItem(array(
+ 'TableName' => $prefix.'oauth_access_tokens',
+ 'Item' => array(
+ 'access_token' => array('S' => 'accesstoken-openid-connect'),
+ 'client_id' => array('S' => 'Some Client'),
+ 'user_id' => array('S' => 'testuser'),
+ )
+ ));
+
+ $client->putItem(array(
+ 'TableName' => $prefix.'oauth_authorization_codes',
+ 'Item' => array(
+ 'authorization_code' => array('S' => 'testcode'),
+ 'client_id' => array('S' => 'Some Client'),
+ )
+ ));
+
+ $client->putItem(array(
+ 'TableName' => $prefix.'oauth_users',
+ 'Item' => array(
+ 'username' => array('S' => 'testuser'),
+ 'password' => array('S' => 'password'),
+ 'email' => array('S' => 'testuser@test.com'),
+ 'email_verified' => array('S' => 'true'),
+ )
+ ));
+
+ $client->putItem(array(
+ 'TableName' => $prefix.'oauth_public_keys',
+ 'Item' => array(
+ 'client_id' => array('S' => 'ClientID_One'),
+ 'public_key' => array('S' => 'client_1_public'),
+ 'private_key' => array('S' => 'client_1_private'),
+ 'encryption_algorithm' => array('S' => 'RS256'),
+ )
+ ));
+
+ $client->putItem(array(
+ 'TableName' => $prefix.'oauth_public_keys',
+ 'Item' => array(
+ 'client_id' => array('S' => 'ClientID_Two'),
+ 'public_key' => array('S' => 'client_2_public'),
+ 'private_key' => array('S' => 'client_2_private'),
+ 'encryption_algorithm' => array('S' => 'RS256'),
+ )
+ ));
+
+ $client->putItem(array(
+ 'TableName' => $prefix.'oauth_public_keys',
+ 'Item' => array(
+ 'client_id' => array('S' => '0'),
+ 'public_key' => array('S' => $this->getTestPublicKey()),
+ 'private_key' => array('S' => $this->getTestPrivateKey()),
+ 'encryption_algorithm' => array('S' => 'RS256'),
+ )
+ ));
+
+ $client->putItem(array(
+ 'TableName' => $prefix.'oauth_jwt',
+ 'Item' => array(
+ 'client_id' => array('S' => 'oauth_test_client'),
+ 'subject' => array('S' => 'test_subject'),
+ 'public_key' => array('S' => $this->getTestPublicKey()),
+ )
+ ));
+ }
+
+ public function cleanupTravisDynamoDb($prefix = null)
+ {
+ if (is_null($prefix)) {
+ // skip this when not applicable
+ if (!$this->getEnvVar('TRAVIS') || self::DYNAMODB_PHP_VERSION != $this->getEnvVar('TRAVIS_PHP_VERSION')) {
+ return;
+ }
+
+ $prefix = sprintf('build_%s_', $this->getEnvVar('TRAVIS_JOB_NUMBER'));
+ }
+
+ $client = $this->getDynamoDbClient();
+ $this->deleteDynamoDb($client, $prefix);
+ }
+
+ private function getEnvVar($var, $default = null)
+ {
+ return isset($_SERVER[$var]) ? $_SERVER[$var] : (getenv($var) ?: $default);
+ }
+}
diff --git a/library/oauth2/test/lib/OAuth2/Storage/NullStorage.php b/vendor/bshaffer/oauth2-server-php/test/lib/OAuth2/Storage/NullStorage.php
index 6caa62068..6caa62068 100644
--- a/library/oauth2/test/lib/OAuth2/Storage/NullStorage.php
+++ b/vendor/bshaffer/oauth2-server-php/test/lib/OAuth2/Storage/NullStorage.php
diff --git a/vendor/composer/ClassLoader.php b/vendor/composer/ClassLoader.php
index ac67d302a..2c72175e7 100644
--- a/vendor/composer/ClassLoader.php
+++ b/vendor/composer/ClassLoader.php
@@ -55,6 +55,7 @@ class ClassLoader
private $classMap = array();
private $classMapAuthoritative = false;
private $missingClasses = array();
+ private $apcuPrefix;
public function getPrefixes()
{
@@ -272,6 +273,26 @@ class ClassLoader
}
/**
+ * APCu prefix to use to cache found/not-found classes, if the extension is enabled.
+ *
+ * @param string|null $apcuPrefix
+ */
+ public function setApcuPrefix($apcuPrefix)
+ {
+ $this->apcuPrefix = function_exists('apcu_fetch') && ini_get('apc.enabled') ? $apcuPrefix : null;
+ }
+
+ /**
+ * The APCu prefix in use, or null if APCu caching is not enabled.
+ *
+ * @return string|null
+ */
+ public function getApcuPrefix()
+ {
+ return $this->apcuPrefix;
+ }
+
+ /**
* Registers this instance as an autoloader.
*
* @param bool $prepend Whether to prepend the autoloader or not
@@ -313,11 +334,6 @@ class ClassLoader
*/
public function findFile($class)
{
- // work around for PHP 5.3.0 - 5.3.2 https://bugs.php.net/50731
- if ('\\' == $class[0]) {
- $class = substr($class, 1);
- }
-
// class map lookup
if (isset($this->classMap[$class])) {
return $this->classMap[$class];
@@ -325,6 +341,12 @@ class ClassLoader
if ($this->classMapAuthoritative || isset($this->missingClasses[$class])) {
return false;
}
+ if (null !== $this->apcuPrefix) {
+ $file = apcu_fetch($this->apcuPrefix.$class, $hit);
+ if ($hit) {
+ return $file;
+ }
+ }
$file = $this->findFileWithExtension($class, '.php');
@@ -333,6 +355,10 @@ class ClassLoader
$file = $this->findFileWithExtension($class, '.hh');
}
+ if (null !== $this->apcuPrefix) {
+ apcu_add($this->apcuPrefix.$class, $file);
+ }
+
if (false === $file) {
// Remember that this class does not exist.
$this->missingClasses[$class] = true;
@@ -348,9 +374,13 @@ class ClassLoader
$first = $class[0];
if (isset($this->prefixLengthsPsr4[$first])) {
- foreach ($this->prefixLengthsPsr4[$first] as $prefix => $length) {
- if (0 === strpos($class, $prefix)) {
- foreach ($this->prefixDirsPsr4[$prefix] as $dir) {
+ $subPath = $class;
+ while (false !== $lastPos = strrpos($subPath, '\\')) {
+ $subPath = substr($subPath, 0, $lastPos);
+ $search = $subPath.'\\';
+ if (isset($this->prefixDirsPsr4[$search])) {
+ foreach ($this->prefixDirsPsr4[$search] as $dir) {
+ $length = $this->prefixLengthsPsr4[$first][$search];
if (file_exists($file = $dir . DIRECTORY_SEPARATOR . substr($logicalPathPsr4, $length))) {
return $file;
}
diff --git a/vendor/composer/LICENSE b/vendor/composer/LICENSE
index 1a2812488..f27399a04 100644
--- a/vendor/composer/LICENSE
+++ b/vendor/composer/LICENSE
@@ -1,5 +1,5 @@
-Copyright (c) 2016 Nils Adermann, Jordi Boggiano
+Copyright (c) Nils Adermann, Jordi Boggiano
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
diff --git a/vendor/composer/autoload_classmap.php b/vendor/composer/autoload_classmap.php
index 54b09f68b..125c5c325 100644
--- a/vendor/composer/autoload_classmap.php
+++ b/vendor/composer/autoload_classmap.php
@@ -6,7 +6,335 @@ $vendorDir = dirname(dirname(__FILE__));
$baseDir = dirname($vendorDir);
return array(
+ 'HTMLPurifier' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier.php',
+ 'HTMLPurifier_Arborize' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Arborize.php',
+ 'HTMLPurifier_AttrCollections' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrCollections.php',
+ 'HTMLPurifier_AttrDef' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef.php',
+ 'HTMLPurifier_AttrDef_CSS' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS.php',
+ 'HTMLPurifier_AttrDef_CSS_AlphaValue' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/AlphaValue.php',
+ 'HTMLPurifier_AttrDef_CSS_Background' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Background.php',
+ 'HTMLPurifier_AttrDef_CSS_BackgroundPosition' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/BackgroundPosition.php',
+ 'HTMLPurifier_AttrDef_CSS_Border' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Border.php',
+ 'HTMLPurifier_AttrDef_CSS_Color' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Color.php',
+ 'HTMLPurifier_AttrDef_CSS_Composite' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Composite.php',
+ 'HTMLPurifier_AttrDef_CSS_DenyElementDecorator' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/DenyElementDecorator.php',
+ 'HTMLPurifier_AttrDef_CSS_Filter' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Filter.php',
+ 'HTMLPurifier_AttrDef_CSS_Font' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Font.php',
+ 'HTMLPurifier_AttrDef_CSS_FontFamily' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/FontFamily.php',
+ 'HTMLPurifier_AttrDef_CSS_Ident' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Ident.php',
+ 'HTMLPurifier_AttrDef_CSS_ImportantDecorator' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/ImportantDecorator.php',
+ 'HTMLPurifier_AttrDef_CSS_Length' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Length.php',
+ 'HTMLPurifier_AttrDef_CSS_ListStyle' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/ListStyle.php',
+ 'HTMLPurifier_AttrDef_CSS_Multiple' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Multiple.php',
+ 'HTMLPurifier_AttrDef_CSS_Number' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Number.php',
+ 'HTMLPurifier_AttrDef_CSS_Percentage' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Percentage.php',
+ 'HTMLPurifier_AttrDef_CSS_TextDecoration' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/TextDecoration.php',
+ 'HTMLPurifier_AttrDef_CSS_URI' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/URI.php',
+ 'HTMLPurifier_AttrDef_Clone' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Clone.php',
+ 'HTMLPurifier_AttrDef_Enum' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Enum.php',
+ 'HTMLPurifier_AttrDef_HTML_Bool' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Bool.php',
+ 'HTMLPurifier_AttrDef_HTML_Class' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Class.php',
+ 'HTMLPurifier_AttrDef_HTML_Color' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Color.php',
+ 'HTMLPurifier_AttrDef_HTML_FrameTarget' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/FrameTarget.php',
+ 'HTMLPurifier_AttrDef_HTML_ID' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/ID.php',
+ 'HTMLPurifier_AttrDef_HTML_Length' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Length.php',
+ 'HTMLPurifier_AttrDef_HTML_LinkTypes' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/LinkTypes.php',
+ 'HTMLPurifier_AttrDef_HTML_MultiLength' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/MultiLength.php',
+ 'HTMLPurifier_AttrDef_HTML_Nmtokens' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Nmtokens.php',
+ 'HTMLPurifier_AttrDef_HTML_Pixels' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Pixels.php',
+ 'HTMLPurifier_AttrDef_Integer' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Integer.php',
+ 'HTMLPurifier_AttrDef_Lang' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Lang.php',
+ 'HTMLPurifier_AttrDef_Switch' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Switch.php',
+ 'HTMLPurifier_AttrDef_Text' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Text.php',
+ 'HTMLPurifier_AttrDef_URI' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI.php',
+ 'HTMLPurifier_AttrDef_URI_Email' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/Email.php',
+ 'HTMLPurifier_AttrDef_URI_Email_SimpleCheck' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/Email/SimpleCheck.php',
+ 'HTMLPurifier_AttrDef_URI_Host' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/Host.php',
+ 'HTMLPurifier_AttrDef_URI_IPv4' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/IPv4.php',
+ 'HTMLPurifier_AttrDef_URI_IPv6' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/IPv6.php',
+ 'HTMLPurifier_AttrTransform' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform.php',
+ 'HTMLPurifier_AttrTransform_Background' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Background.php',
+ 'HTMLPurifier_AttrTransform_BdoDir' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/BdoDir.php',
+ 'HTMLPurifier_AttrTransform_BgColor' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/BgColor.php',
+ 'HTMLPurifier_AttrTransform_BoolToCSS' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/BoolToCSS.php',
+ 'HTMLPurifier_AttrTransform_Border' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Border.php',
+ 'HTMLPurifier_AttrTransform_EnumToCSS' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/EnumToCSS.php',
+ 'HTMLPurifier_AttrTransform_ImgRequired' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/ImgRequired.php',
+ 'HTMLPurifier_AttrTransform_ImgSpace' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/ImgSpace.php',
+ 'HTMLPurifier_AttrTransform_Input' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Input.php',
+ 'HTMLPurifier_AttrTransform_Lang' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Lang.php',
+ 'HTMLPurifier_AttrTransform_Length' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Length.php',
+ 'HTMLPurifier_AttrTransform_Name' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Name.php',
+ 'HTMLPurifier_AttrTransform_NameSync' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/NameSync.php',
+ 'HTMLPurifier_AttrTransform_Nofollow' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Nofollow.php',
+ 'HTMLPurifier_AttrTransform_SafeEmbed' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/SafeEmbed.php',
+ 'HTMLPurifier_AttrTransform_SafeObject' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/SafeObject.php',
+ 'HTMLPurifier_AttrTransform_SafeParam' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/SafeParam.php',
+ 'HTMLPurifier_AttrTransform_ScriptRequired' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/ScriptRequired.php',
+ 'HTMLPurifier_AttrTransform_TargetBlank' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/TargetBlank.php',
+ 'HTMLPurifier_AttrTransform_TargetNoopener' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/TargetNoopener.php',
+ 'HTMLPurifier_AttrTransform_TargetNoreferrer' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/TargetNoreferrer.php',
+ 'HTMLPurifier_AttrTransform_Textarea' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Textarea.php',
+ 'HTMLPurifier_AttrTypes' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTypes.php',
+ 'HTMLPurifier_AttrValidator' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrValidator.php',
+ 'HTMLPurifier_Bootstrap' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Bootstrap.php',
+ 'HTMLPurifier_CSSDefinition' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/CSSDefinition.php',
+ 'HTMLPurifier_ChildDef' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef.php',
+ 'HTMLPurifier_ChildDef_Chameleon' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Chameleon.php',
+ 'HTMLPurifier_ChildDef_Custom' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Custom.php',
+ 'HTMLPurifier_ChildDef_Empty' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Empty.php',
+ 'HTMLPurifier_ChildDef_List' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/List.php',
+ 'HTMLPurifier_ChildDef_Optional' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Optional.php',
+ 'HTMLPurifier_ChildDef_Required' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Required.php',
+ 'HTMLPurifier_ChildDef_StrictBlockquote' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/StrictBlockquote.php',
+ 'HTMLPurifier_ChildDef_Table' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Table.php',
+ 'HTMLPurifier_Config' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Config.php',
+ 'HTMLPurifier_ConfigSchema' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema.php',
+ 'HTMLPurifier_ConfigSchema_Builder_ConfigSchema' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Builder/ConfigSchema.php',
+ 'HTMLPurifier_ConfigSchema_Builder_Xml' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Builder/Xml.php',
+ 'HTMLPurifier_ConfigSchema_Exception' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Exception.php',
+ 'HTMLPurifier_ConfigSchema_Interchange' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Interchange.php',
+ 'HTMLPurifier_ConfigSchema_InterchangeBuilder' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/InterchangeBuilder.php',
+ 'HTMLPurifier_ConfigSchema_Interchange_Directive' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Interchange/Directive.php',
+ 'HTMLPurifier_ConfigSchema_Interchange_Id' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Interchange/Id.php',
+ 'HTMLPurifier_ConfigSchema_Validator' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Validator.php',
+ 'HTMLPurifier_ConfigSchema_ValidatorAtom' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/ValidatorAtom.php',
+ 'HTMLPurifier_ContentSets' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/ContentSets.php',
+ 'HTMLPurifier_Context' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Context.php',
+ 'HTMLPurifier_Definition' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Definition.php',
+ 'HTMLPurifier_DefinitionCache' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache.php',
+ 'HTMLPurifier_DefinitionCacheFactory' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCacheFactory.php',
+ 'HTMLPurifier_DefinitionCache_Decorator' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Decorator.php',
+ 'HTMLPurifier_DefinitionCache_Decorator_Cleanup' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Decorator/Cleanup.php',
+ 'HTMLPurifier_DefinitionCache_Decorator_Memory' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Decorator/Memory.php',
+ 'HTMLPurifier_DefinitionCache_Null' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Null.php',
+ 'HTMLPurifier_DefinitionCache_Serializer' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Serializer.php',
+ 'HTMLPurifier_Doctype' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Doctype.php',
+ 'HTMLPurifier_DoctypeRegistry' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/DoctypeRegistry.php',
+ 'HTMLPurifier_ElementDef' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/ElementDef.php',
+ 'HTMLPurifier_Encoder' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Encoder.php',
+ 'HTMLPurifier_EntityLookup' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/EntityLookup.php',
+ 'HTMLPurifier_EntityParser' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/EntityParser.php',
+ 'HTMLPurifier_ErrorCollector' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/ErrorCollector.php',
+ 'HTMLPurifier_ErrorStruct' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/ErrorStruct.php',
+ 'HTMLPurifier_Exception' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Exception.php',
+ 'HTMLPurifier_Filter' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Filter.php',
+ 'HTMLPurifier_Filter_ExtractStyleBlocks' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Filter/ExtractStyleBlocks.php',
+ 'HTMLPurifier_Filter_YouTube' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Filter/YouTube.php',
+ 'HTMLPurifier_Generator' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Generator.php',
+ 'HTMLPurifier_HTMLDefinition' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLDefinition.php',
+ 'HTMLPurifier_HTMLModule' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule.php',
+ 'HTMLPurifier_HTMLModuleManager' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModuleManager.php',
+ 'HTMLPurifier_HTMLModule_Bdo' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Bdo.php',
+ 'HTMLPurifier_HTMLModule_CommonAttributes' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/CommonAttributes.php',
+ 'HTMLPurifier_HTMLModule_Edit' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Edit.php',
+ 'HTMLPurifier_HTMLModule_Forms' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Forms.php',
+ 'HTMLPurifier_HTMLModule_Hypertext' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Hypertext.php',
+ 'HTMLPurifier_HTMLModule_Iframe' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Iframe.php',
+ 'HTMLPurifier_HTMLModule_Image' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Image.php',
+ 'HTMLPurifier_HTMLModule_Legacy' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Legacy.php',
+ 'HTMLPurifier_HTMLModule_List' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/List.php',
+ 'HTMLPurifier_HTMLModule_Name' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Name.php',
+ 'HTMLPurifier_HTMLModule_Nofollow' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Nofollow.php',
+ 'HTMLPurifier_HTMLModule_NonXMLCommonAttributes' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/NonXMLCommonAttributes.php',
+ 'HTMLPurifier_HTMLModule_Object' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Object.php',
+ 'HTMLPurifier_HTMLModule_Presentation' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Presentation.php',
+ 'HTMLPurifier_HTMLModule_Proprietary' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Proprietary.php',
+ 'HTMLPurifier_HTMLModule_Ruby' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Ruby.php',
+ 'HTMLPurifier_HTMLModule_SafeEmbed' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/SafeEmbed.php',
+ 'HTMLPurifier_HTMLModule_SafeObject' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/SafeObject.php',
+ 'HTMLPurifier_HTMLModule_SafeScripting' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/SafeScripting.php',
+ 'HTMLPurifier_HTMLModule_Scripting' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Scripting.php',
+ 'HTMLPurifier_HTMLModule_StyleAttribute' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/StyleAttribute.php',
+ 'HTMLPurifier_HTMLModule_Tables' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tables.php',
+ 'HTMLPurifier_HTMLModule_Target' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Target.php',
+ 'HTMLPurifier_HTMLModule_TargetBlank' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/TargetBlank.php',
+ 'HTMLPurifier_HTMLModule_TargetNoopener' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/TargetNoopener.php',
+ 'HTMLPurifier_HTMLModule_TargetNoreferrer' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/TargetNoreferrer.php',
+ 'HTMLPurifier_HTMLModule_Text' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Text.php',
+ 'HTMLPurifier_HTMLModule_Tidy' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy.php',
+ 'HTMLPurifier_HTMLModule_Tidy_Name' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/Name.php',
+ 'HTMLPurifier_HTMLModule_Tidy_Proprietary' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/Proprietary.php',
+ 'HTMLPurifier_HTMLModule_Tidy_Strict' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/Strict.php',
+ 'HTMLPurifier_HTMLModule_Tidy_Transitional' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/Transitional.php',
+ 'HTMLPurifier_HTMLModule_Tidy_XHTML' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/XHTML.php',
+ 'HTMLPurifier_HTMLModule_Tidy_XHTMLAndHTML4' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/XHTMLAndHTML4.php',
+ 'HTMLPurifier_HTMLModule_XMLCommonAttributes' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/XMLCommonAttributes.php',
+ 'HTMLPurifier_IDAccumulator' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/IDAccumulator.php',
+ 'HTMLPurifier_Injector' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Injector.php',
+ 'HTMLPurifier_Injector_AutoParagraph' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Injector/AutoParagraph.php',
+ 'HTMLPurifier_Injector_DisplayLinkURI' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Injector/DisplayLinkURI.php',
+ 'HTMLPurifier_Injector_Linkify' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Injector/Linkify.php',
+ 'HTMLPurifier_Injector_PurifierLinkify' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Injector/PurifierLinkify.php',
+ 'HTMLPurifier_Injector_RemoveEmpty' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Injector/RemoveEmpty.php',
+ 'HTMLPurifier_Injector_RemoveSpansWithoutAttributes' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Injector/RemoveSpansWithoutAttributes.php',
+ 'HTMLPurifier_Injector_SafeObject' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Injector/SafeObject.php',
+ 'HTMLPurifier_Language' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Language.php',
+ 'HTMLPurifier_LanguageFactory' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/LanguageFactory.php',
+ 'HTMLPurifier_Language_en_x_test' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Language/classes/en-x-test.php',
+ 'HTMLPurifier_Length' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Length.php',
+ 'HTMLPurifier_Lexer' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Lexer.php',
+ 'HTMLPurifier_Lexer_DOMLex' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Lexer/DOMLex.php',
+ 'HTMLPurifier_Lexer_DirectLex' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Lexer/DirectLex.php',
+ 'HTMLPurifier_Lexer_PH5P' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Lexer/PH5P.php',
+ 'HTMLPurifier_Node' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Node.php',
+ 'HTMLPurifier_Node_Comment' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Node/Comment.php',
+ 'HTMLPurifier_Node_Element' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Node/Element.php',
+ 'HTMLPurifier_Node_Text' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Node/Text.php',
+ 'HTMLPurifier_PercentEncoder' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/PercentEncoder.php',
+ 'HTMLPurifier_Printer' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Printer.php',
+ 'HTMLPurifier_Printer_CSSDefinition' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Printer/CSSDefinition.php',
+ 'HTMLPurifier_Printer_ConfigForm' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Printer/ConfigForm.php',
+ 'HTMLPurifier_Printer_ConfigForm_NullDecorator' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Printer/ConfigForm.php',
+ 'HTMLPurifier_Printer_ConfigForm_bool' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Printer/ConfigForm.php',
+ 'HTMLPurifier_Printer_ConfigForm_default' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Printer/ConfigForm.php',
+ 'HTMLPurifier_Printer_HTMLDefinition' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Printer/HTMLDefinition.php',
+ 'HTMLPurifier_PropertyList' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/PropertyList.php',
+ 'HTMLPurifier_PropertyListIterator' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/PropertyListIterator.php',
+ 'HTMLPurifier_Queue' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Queue.php',
+ 'HTMLPurifier_Strategy' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Strategy.php',
+ 'HTMLPurifier_Strategy_Composite' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/Composite.php',
+ 'HTMLPurifier_Strategy_Core' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/Core.php',
+ 'HTMLPurifier_Strategy_FixNesting' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/FixNesting.php',
+ 'HTMLPurifier_Strategy_MakeWellFormed' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/MakeWellFormed.php',
+ 'HTMLPurifier_Strategy_RemoveForeignElements' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/RemoveForeignElements.php',
+ 'HTMLPurifier_Strategy_ValidateAttributes' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/ValidateAttributes.php',
+ 'HTMLPurifier_StringHash' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/StringHash.php',
+ 'HTMLPurifier_StringHashParser' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/StringHashParser.php',
+ 'HTMLPurifier_TagTransform' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/TagTransform.php',
+ 'HTMLPurifier_TagTransform_Font' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/TagTransform/Font.php',
+ 'HTMLPurifier_TagTransform_Simple' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/TagTransform/Simple.php',
+ 'HTMLPurifier_Token' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Token.php',
+ 'HTMLPurifier_TokenFactory' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/TokenFactory.php',
+ 'HTMLPurifier_Token_Comment' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Token/Comment.php',
+ 'HTMLPurifier_Token_Empty' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Token/Empty.php',
+ 'HTMLPurifier_Token_End' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Token/End.php',
+ 'HTMLPurifier_Token_Start' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Token/Start.php',
+ 'HTMLPurifier_Token_Tag' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Token/Tag.php',
+ 'HTMLPurifier_Token_Text' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Token/Text.php',
+ 'HTMLPurifier_URI' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/URI.php',
+ 'HTMLPurifier_URIDefinition' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/URIDefinition.php',
+ 'HTMLPurifier_URIFilter' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter.php',
+ 'HTMLPurifier_URIFilter_DisableExternal' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/DisableExternal.php',
+ 'HTMLPurifier_URIFilter_DisableExternalResources' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/DisableExternalResources.php',
+ 'HTMLPurifier_URIFilter_DisableResources' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/DisableResources.php',
+ 'HTMLPurifier_URIFilter_HostBlacklist' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/HostBlacklist.php',
+ 'HTMLPurifier_URIFilter_MakeAbsolute' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/MakeAbsolute.php',
+ 'HTMLPurifier_URIFilter_Munge' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/Munge.php',
+ 'HTMLPurifier_URIFilter_SafeIframe' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/SafeIframe.php',
+ 'HTMLPurifier_URIParser' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/URIParser.php',
+ 'HTMLPurifier_URIScheme' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme.php',
+ 'HTMLPurifier_URISchemeRegistry' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/URISchemeRegistry.php',
+ 'HTMLPurifier_URIScheme_data' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/data.php',
+ 'HTMLPurifier_URIScheme_file' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/file.php',
+ 'HTMLPurifier_URIScheme_ftp' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/ftp.php',
+ 'HTMLPurifier_URIScheme_http' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/http.php',
+ 'HTMLPurifier_URIScheme_https' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/https.php',
+ 'HTMLPurifier_URIScheme_mailto' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/mailto.php',
+ 'HTMLPurifier_URIScheme_news' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/news.php',
+ 'HTMLPurifier_URIScheme_nntp' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/nntp.php',
+ 'HTMLPurifier_URIScheme_tel' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/tel.php',
+ 'HTMLPurifier_UnitConverter' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/UnitConverter.php',
+ 'HTMLPurifier_VarParser' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/VarParser.php',
+ 'HTMLPurifier_VarParserException' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/VarParserException.php',
+ 'HTMLPurifier_VarParser_Flexible' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/VarParser/Flexible.php',
+ 'HTMLPurifier_VarParser_Native' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/VarParser/Native.php',
+ 'HTMLPurifier_Zipper' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier/Zipper.php',
'Hubzilla\\Import\\Import' => $baseDir . '/include/Import/Importer.php',
+ 'League\\HTMLToMarkdown\\Configuration' => $vendorDir . '/league/html-to-markdown/src/Configuration.php',
+ 'League\\HTMLToMarkdown\\ConfigurationAwareInterface' => $vendorDir . '/league/html-to-markdown/src/ConfigurationAwareInterface.php',
+ 'League\\HTMLToMarkdown\\Converter\\BlockquoteConverter' => $vendorDir . '/league/html-to-markdown/src/Converter/BlockquoteConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\CodeConverter' => $vendorDir . '/league/html-to-markdown/src/Converter/CodeConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\CommentConverter' => $vendorDir . '/league/html-to-markdown/src/Converter/CommentConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\ConverterInterface' => $vendorDir . '/league/html-to-markdown/src/Converter/ConverterInterface.php',
+ 'League\\HTMLToMarkdown\\Converter\\DefaultConverter' => $vendorDir . '/league/html-to-markdown/src/Converter/DefaultConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\DivConverter' => $vendorDir . '/league/html-to-markdown/src/Converter/DivConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\EmphasisConverter' => $vendorDir . '/league/html-to-markdown/src/Converter/EmphasisConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\HardBreakConverter' => $vendorDir . '/league/html-to-markdown/src/Converter/HardBreakConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\HeaderConverter' => $vendorDir . '/league/html-to-markdown/src/Converter/HeaderConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\HorizontalRuleConverter' => $vendorDir . '/league/html-to-markdown/src/Converter/HorizontalRuleConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\ImageConverter' => $vendorDir . '/league/html-to-markdown/src/Converter/ImageConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\LinkConverter' => $vendorDir . '/league/html-to-markdown/src/Converter/LinkConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\ListBlockConverter' => $vendorDir . '/league/html-to-markdown/src/Converter/ListBlockConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\ListItemConverter' => $vendorDir . '/league/html-to-markdown/src/Converter/ListItemConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\ParagraphConverter' => $vendorDir . '/league/html-to-markdown/src/Converter/ParagraphConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\PreformattedConverter' => $vendorDir . '/league/html-to-markdown/src/Converter/PreformattedConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\TextConverter' => $vendorDir . '/league/html-to-markdown/src/Converter/TextConverter.php',
+ 'League\\HTMLToMarkdown\\Element' => $vendorDir . '/league/html-to-markdown/src/Element.php',
+ 'League\\HTMLToMarkdown\\ElementInterface' => $vendorDir . '/league/html-to-markdown/src/ElementInterface.php',
+ 'League\\HTMLToMarkdown\\Environment' => $vendorDir . '/league/html-to-markdown/src/Environment.php',
+ 'League\\HTMLToMarkdown\\HtmlConverter' => $vendorDir . '/league/html-to-markdown/src/HtmlConverter.php',
+ 'Michelf\\Markdown' => $vendorDir . '/michelf/php-markdown/Michelf/Markdown.php',
+ 'Michelf\\MarkdownExtra' => $vendorDir . '/michelf/php-markdown/Michelf/MarkdownExtra.php',
+ 'Michelf\\MarkdownInterface' => $vendorDir . '/michelf/php-markdown/Michelf/MarkdownInterface.php',
+ 'OAuth2\\Autoloader' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Autoloader.php',
+ 'OAuth2\\ClientAssertionType\\ClientAssertionTypeInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/ClientAssertionType/ClientAssertionTypeInterface.php',
+ 'OAuth2\\ClientAssertionType\\HttpBasic' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/ClientAssertionType/HttpBasic.php',
+ 'OAuth2\\Controller\\AuthorizeController' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Controller/AuthorizeController.php',
+ 'OAuth2\\Controller\\AuthorizeControllerInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Controller/AuthorizeControllerInterface.php',
+ 'OAuth2\\Controller\\ResourceController' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Controller/ResourceController.php',
+ 'OAuth2\\Controller\\ResourceControllerInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Controller/ResourceControllerInterface.php',
+ 'OAuth2\\Controller\\TokenController' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Controller/TokenController.php',
+ 'OAuth2\\Controller\\TokenControllerInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Controller/TokenControllerInterface.php',
+ 'OAuth2\\Encryption\\EncryptionInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Encryption/EncryptionInterface.php',
+ 'OAuth2\\Encryption\\FirebaseJwt' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Encryption/FirebaseJwt.php',
+ 'OAuth2\\Encryption\\Jwt' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Encryption/Jwt.php',
+ 'OAuth2\\GrantType\\AuthorizationCode' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/GrantType/AuthorizationCode.php',
+ 'OAuth2\\GrantType\\ClientCredentials' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/GrantType/ClientCredentials.php',
+ 'OAuth2\\GrantType\\GrantTypeInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/GrantType/GrantTypeInterface.php',
+ 'OAuth2\\GrantType\\JwtBearer' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/GrantType/JwtBearer.php',
+ 'OAuth2\\GrantType\\RefreshToken' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/GrantType/RefreshToken.php',
+ 'OAuth2\\GrantType\\UserCredentials' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/GrantType/UserCredentials.php',
+ 'OAuth2\\OpenID\\Controller\\AuthorizeController' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Controller/AuthorizeController.php',
+ 'OAuth2\\OpenID\\Controller\\AuthorizeControllerInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Controller/AuthorizeControllerInterface.php',
+ 'OAuth2\\OpenID\\Controller\\UserInfoController' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Controller/UserInfoController.php',
+ 'OAuth2\\OpenID\\Controller\\UserInfoControllerInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Controller/UserInfoControllerInterface.php',
+ 'OAuth2\\OpenID\\GrantType\\AuthorizationCode' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/GrantType/AuthorizationCode.php',
+ 'OAuth2\\OpenID\\ResponseType\\AuthorizationCode' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/AuthorizationCode.php',
+ 'OAuth2\\OpenID\\ResponseType\\AuthorizationCodeInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/AuthorizationCodeInterface.php',
+ 'OAuth2\\OpenID\\ResponseType\\CodeIdToken' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/CodeIdToken.php',
+ 'OAuth2\\OpenID\\ResponseType\\CodeIdTokenInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/CodeIdTokenInterface.php',
+ 'OAuth2\\OpenID\\ResponseType\\IdToken' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/IdToken.php',
+ 'OAuth2\\OpenID\\ResponseType\\IdTokenInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/IdTokenInterface.php',
+ 'OAuth2\\OpenID\\ResponseType\\IdTokenToken' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/IdTokenToken.php',
+ 'OAuth2\\OpenID\\ResponseType\\IdTokenTokenInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/IdTokenTokenInterface.php',
+ 'OAuth2\\OpenID\\Storage\\AuthorizationCodeInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Storage/AuthorizationCodeInterface.php',
+ 'OAuth2\\OpenID\\Storage\\UserClaimsInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Storage/UserClaimsInterface.php',
+ 'OAuth2\\Request' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Request.php',
+ 'OAuth2\\RequestInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/RequestInterface.php',
+ 'OAuth2\\Response' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Response.php',
+ 'OAuth2\\ResponseInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/ResponseInterface.php',
+ 'OAuth2\\ResponseType\\AccessToken' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/AccessToken.php',
+ 'OAuth2\\ResponseType\\AccessTokenInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/AccessTokenInterface.php',
+ 'OAuth2\\ResponseType\\AuthorizationCode' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/AuthorizationCode.php',
+ 'OAuth2\\ResponseType\\AuthorizationCodeInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/AuthorizationCodeInterface.php',
+ 'OAuth2\\ResponseType\\JwtAccessToken' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/JwtAccessToken.php',
+ 'OAuth2\\ResponseType\\ResponseTypeInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/ResponseTypeInterface.php',
+ 'OAuth2\\Scope' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Scope.php',
+ 'OAuth2\\ScopeInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/ScopeInterface.php',
+ 'OAuth2\\Server' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Server.php',
+ 'OAuth2\\Storage\\AccessTokenInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/AccessTokenInterface.php',
+ 'OAuth2\\Storage\\AuthorizationCodeInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/AuthorizationCodeInterface.php',
+ 'OAuth2\\Storage\\Cassandra' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/Cassandra.php',
+ 'OAuth2\\Storage\\ClientCredentialsInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/ClientCredentialsInterface.php',
+ 'OAuth2\\Storage\\ClientInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/ClientInterface.php',
+ 'OAuth2\\Storage\\CouchbaseDB' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/CouchbaseDB.php',
+ 'OAuth2\\Storage\\DynamoDB' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/DynamoDB.php',
+ 'OAuth2\\Storage\\JwtAccessToken' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/JwtAccessToken.php',
+ 'OAuth2\\Storage\\JwtAccessTokenInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/JwtAccessTokenInterface.php',
+ 'OAuth2\\Storage\\JwtBearerInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/JwtBearerInterface.php',
+ 'OAuth2\\Storage\\Memory' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/Memory.php',
+ 'OAuth2\\Storage\\Mongo' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/Mongo.php',
+ 'OAuth2\\Storage\\MongoDB' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/MongoDB.php',
+ 'OAuth2\\Storage\\Pdo' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/Pdo.php',
+ 'OAuth2\\Storage\\PublicKeyInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/PublicKeyInterface.php',
+ 'OAuth2\\Storage\\Redis' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/Redis.php',
+ 'OAuth2\\Storage\\RefreshTokenInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/RefreshTokenInterface.php',
+ 'OAuth2\\Storage\\ScopeInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/ScopeInterface.php',
+ 'OAuth2\\Storage\\UserCredentialsInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/UserCredentialsInterface.php',
+ 'OAuth2\\TokenType\\Bearer' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/TokenType/Bearer.php',
+ 'OAuth2\\TokenType\\Mac' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/TokenType/Mac.php',
+ 'OAuth2\\TokenType\\TokenTypeInterface' => $vendorDir . '/bshaffer/oauth2-server-php/src/OAuth2/TokenType/TokenTypeInterface.php',
'Psr\\Log\\AbstractLogger' => $vendorDir . '/psr/log/Psr/Log/AbstractLogger.php',
'Psr\\Log\\InvalidArgumentException' => $vendorDir . '/psr/log/Psr/Log/InvalidArgumentException.php',
'Psr\\Log\\LogLevel' => $vendorDir . '/psr/log/Psr/Log/LogLevel.php',
@@ -265,6 +593,7 @@ return array(
'Sabre\\HTTP\\URLUtil' => $vendorDir . '/sabre/http/lib/URLUtil.php',
'Sabre\\HTTP\\Util' => $vendorDir . '/sabre/http/lib/Util.php',
'Sabre\\HTTP\\Version' => $vendorDir . '/sabre/http/lib/Version.php',
+ 'Sabre\\Uri\\InvalidUriException' => $vendorDir . '/sabre/uri/lib/InvalidUriException.php',
'Sabre\\Uri\\Version' => $vendorDir . '/sabre/uri/lib/Version.php',
'Sabre\\VObject\\BirthdayCalendarGenerator' => $vendorDir . '/sabre/vobject/lib/BirthdayCalendarGenerator.php',
'Sabre\\VObject\\Cli' => $vendorDir . '/sabre/vobject/lib/Cli.php',
@@ -353,10 +682,46 @@ return array(
'Sabre\\Xml\\Writer' => $vendorDir . '/sabre/xml/lib/Writer.php',
'Sabre\\Xml\\XmlDeserializable' => $vendorDir . '/sabre/xml/lib/XmlDeserializable.php',
'Sabre\\Xml\\XmlSerializable' => $vendorDir . '/sabre/xml/lib/XmlSerializable.php',
+ 'SimplePie' => $vendorDir . '/simplepie/simplepie/library/SimplePie.php',
+ 'SimplePie_Author' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Author.php',
+ 'SimplePie_Cache' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Cache.php',
+ 'SimplePie_Cache_Base' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Cache/Base.php',
+ 'SimplePie_Cache_DB' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Cache/DB.php',
+ 'SimplePie_Cache_File' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Cache/File.php',
+ 'SimplePie_Cache_Memcache' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Cache/Memcache.php',
+ 'SimplePie_Cache_Memcached' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Cache/Memcached.php',
+ 'SimplePie_Cache_MySQL' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Cache/MySQL.php',
+ 'SimplePie_Cache_Redis' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Cache/Redis.php',
+ 'SimplePie_Caption' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Caption.php',
+ 'SimplePie_Category' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Category.php',
+ 'SimplePie_Content_Type_Sniffer' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Content/Type/Sniffer.php',
+ 'SimplePie_Copyright' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Copyright.php',
+ 'SimplePie_Core' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Core.php',
+ 'SimplePie_Credit' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Credit.php',
+ 'SimplePie_Decode_HTML_Entities' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Decode/HTML/Entities.php',
+ 'SimplePie_Enclosure' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Enclosure.php',
+ 'SimplePie_Exception' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Exception.php',
+ 'SimplePie_File' => $vendorDir . '/simplepie/simplepie/library/SimplePie/File.php',
+ 'SimplePie_HTTP_Parser' => $vendorDir . '/simplepie/simplepie/library/SimplePie/HTTP/Parser.php',
+ 'SimplePie_IRI' => $vendorDir . '/simplepie/simplepie/library/SimplePie/IRI.php',
+ 'SimplePie_Item' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Item.php',
+ 'SimplePie_Locator' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Locator.php',
+ 'SimplePie_Misc' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Misc.php',
+ 'SimplePie_Net_IPv6' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Net/IPv6.php',
+ 'SimplePie_Parse_Date' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Parse/Date.php',
+ 'SimplePie_Parser' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Parser.php',
+ 'SimplePie_Rating' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Rating.php',
+ 'SimplePie_Registry' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Registry.php',
+ 'SimplePie_Restriction' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Restriction.php',
+ 'SimplePie_Sanitize' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Sanitize.php',
+ 'SimplePie_Source' => $vendorDir . '/simplepie/simplepie/library/SimplePie/Source.php',
+ 'SimplePie_XML_Declaration_Parser' => $vendorDir . '/simplepie/simplepie/library/SimplePie/XML/Declaration/Parser.php',
+ 'SimplePie_gzdecode' => $vendorDir . '/simplepie/simplepie/library/SimplePie/gzdecode.php',
'Zotlabs\\Access\\AccessList' => $baseDir . '/Zotlabs/Access/AccessList.php',
'Zotlabs\\Access\\PermissionLimits' => $baseDir . '/Zotlabs/Access/PermissionLimits.php',
'Zotlabs\\Access\\PermissionRoles' => $baseDir . '/Zotlabs/Access/PermissionRoles.php',
'Zotlabs\\Access\\Permissions' => $baseDir . '/Zotlabs/Access/Permissions.php',
+ 'Zotlabs\\Daemon\\Addon' => $baseDir . '/Zotlabs/Daemon/Addon.php',
'Zotlabs\\Daemon\\Checksites' => $baseDir . '/Zotlabs/Daemon/Checksites.php',
'Zotlabs\\Daemon\\Cli_suggest' => $baseDir . '/Zotlabs/Daemon/Cli_suggest.php',
'Zotlabs\\Daemon\\Cron' => $baseDir . '/Zotlabs/Daemon/Cron.php',
@@ -371,6 +736,7 @@ return array(
'Zotlabs\\Daemon\\Externals' => $baseDir . '/Zotlabs/Daemon/Externals.php',
'Zotlabs\\Daemon\\Gprobe' => $baseDir . '/Zotlabs/Daemon/Gprobe.php',
'Zotlabs\\Daemon\\Importdoc' => $baseDir . '/Zotlabs/Daemon/Importdoc.php',
+ 'Zotlabs\\Daemon\\Importfile' => $baseDir . '/Zotlabs/Daemon/Importfile.php',
'Zotlabs\\Daemon\\Master' => $baseDir . '/Zotlabs/Daemon/Master.php',
'Zotlabs\\Daemon\\Notifier' => $baseDir . '/Zotlabs/Daemon/Notifier.php',
'Zotlabs\\Daemon\\Onedirsync' => $baseDir . '/Zotlabs/Daemon/Onedirsync.php',
@@ -383,17 +749,26 @@ return array(
'Zotlabs\\Identity\\ProfilePhoto\\ProfilePhoto' => $baseDir . '/Zotlabs/Identity/ProfilePhoto.php',
'Zotlabs\\Lib\\AConfig' => $baseDir . '/Zotlabs/Lib/AConfig.php',
'Zotlabs\\Lib\\AbConfig' => $baseDir . '/Zotlabs/Lib/AbConfig.php',
+ 'Zotlabs\\Lib\\ActivityStreams' => $baseDir . '/Zotlabs/Lib/ActivityStreams.php',
'Zotlabs\\Lib\\Api_router' => $baseDir . '/Zotlabs/Lib/Api_router.php',
'Zotlabs\\Lib\\Apps' => $baseDir . '/Zotlabs/Lib/Apps.php',
'Zotlabs\\Lib\\Cache' => $baseDir . '/Zotlabs/Lib/Cache.php',
'Zotlabs\\Lib\\Chatroom' => $baseDir . '/Zotlabs/Lib/Chatroom.php',
'Zotlabs\\Lib\\Config' => $baseDir . '/Zotlabs/Lib/Config.php',
+ 'Zotlabs\\Lib\\DB_Upgrade' => $baseDir . '/Zotlabs/Lib/DB_Upgrade.php',
'Zotlabs\\Lib\\Enotify' => $baseDir . '/Zotlabs/Lib/Enotify.php',
'Zotlabs\\Lib\\ExtendedZip' => $baseDir . '/Zotlabs/Lib/ExtendedZip.php',
'Zotlabs\\Lib\\IConfig' => $baseDir . '/Zotlabs/Lib/IConfig.php',
+ 'Zotlabs\\Lib\\JSalmon' => $baseDir . '/Zotlabs/Lib/JSalmon.php',
+ 'Zotlabs\\Lib\\LDSignatures' => $baseDir . '/Zotlabs/Lib/LDSignatures.php',
+ 'Zotlabs\\Lib\\MarkdownSoap' => $baseDir . '/Zotlabs/Lib/MarkdownSoap.php',
+ 'Zotlabs\\Lib\\NativeWiki' => $baseDir . '/Zotlabs/Lib/NativeWiki.php',
+ 'Zotlabs\\Lib\\NativeWikiPage' => $baseDir . '/Zotlabs/Lib/NativeWikiPage.php',
'Zotlabs\\Lib\\PConfig' => $baseDir . '/Zotlabs/Lib/PConfig.php',
+ 'Zotlabs\\Lib\\Permcat' => $baseDir . '/Zotlabs/Lib/Permcat.php',
'Zotlabs\\Lib\\PermissionDescription' => $baseDir . '/Zotlabs/Lib/PermissionDescription.php',
'Zotlabs\\Lib\\ProtoDriver' => $baseDir . '/Zotlabs/Lib/ProtoDriver.php',
+ 'Zotlabs\\Lib\\SConfig' => $baseDir . '/Zotlabs/Lib/SConfig.php',
'Zotlabs\\Lib\\SuperCurl' => $baseDir . '/Zotlabs/Lib/SuperCurl.php',
'Zotlabs\\Lib\\System' => $baseDir . '/Zotlabs/Lib/System.php',
'Zotlabs\\Lib\\Techlevels' => $baseDir . '/Zotlabs/Lib/Techlevels.php',
@@ -418,14 +793,20 @@ return array(
'Zotlabs\\Module\\Admin\\Themes' => $baseDir . '/Zotlabs/Module/Admin/Themes.php',
'Zotlabs\\Module\\Api' => $baseDir . '/Zotlabs/Module/Api.php',
'Zotlabs\\Module\\Appman' => $baseDir . '/Zotlabs/Module/Appman.php',
+ 'Zotlabs\\Module\\Apporder' => $baseDir . '/Zotlabs/Module/Apporder.php',
'Zotlabs\\Module\\Apps' => $baseDir . '/Zotlabs/Module/Apps.php',
'Zotlabs\\Module\\Attach' => $baseDir . '/Zotlabs/Module/Attach.php',
+ 'Zotlabs\\Module\\Authorize' => $baseDir . '/Zotlabs/Module/Authorize.php',
'Zotlabs\\Module\\Authtest' => $baseDir . '/Zotlabs/Module/Authtest.php',
'Zotlabs\\Module\\Block' => $baseDir . '/Zotlabs/Module/Block.php',
'Zotlabs\\Module\\Blocks' => $baseDir . '/Zotlabs/Module/Blocks.php',
'Zotlabs\\Module\\Bookmarks' => $baseDir . '/Zotlabs/Module/Bookmarks.php',
'Zotlabs\\Module\\Branchtopic' => $baseDir . '/Zotlabs/Module/Branchtopic.php',
'Zotlabs\\Module\\Cal' => $baseDir . '/Zotlabs/Module/Cal.php',
+ 'Zotlabs\\Module\\Card_edit' => $baseDir . '/Zotlabs/Module/Card_edit.php',
+ 'Zotlabs\\Module\\Cards' => $baseDir . '/Zotlabs/Module/Cards.php',
+ 'Zotlabs\\Module\\Cdav' => $baseDir . '/Zotlabs/Module/Cdav.php',
+ 'Zotlabs\\Module\\Changeaddr' => $baseDir . '/Zotlabs/Module/Changeaddr.php',
'Zotlabs\\Module\\Channel' => $baseDir . '/Zotlabs/Module/Channel.php',
'Zotlabs\\Module\\Chanview' => $baseDir . '/Zotlabs/Module/Chanview.php',
'Zotlabs\\Module\\Chat' => $baseDir . '/Zotlabs/Module/Chat.php',
@@ -474,14 +855,15 @@ return array(
'Zotlabs\\Module\\Lockview' => $baseDir . '/Zotlabs/Module/Lockview.php',
'Zotlabs\\Module\\Locs' => $baseDir . '/Zotlabs/Module/Locs.php',
'Zotlabs\\Module\\Login' => $baseDir . '/Zotlabs/Module/Login.php',
+ 'Zotlabs\\Module\\Logout' => $baseDir . '/Zotlabs/Module/Logout.php',
'Zotlabs\\Module\\Lostpass' => $baseDir . '/Zotlabs/Module/Lostpass.php',
'Zotlabs\\Module\\Magic' => $baseDir . '/Zotlabs/Module/Magic.php',
'Zotlabs\\Module\\Mail' => $baseDir . '/Zotlabs/Module/Mail.php',
'Zotlabs\\Module\\Manage' => $baseDir . '/Zotlabs/Module/Manage.php',
- 'Zotlabs\\Module\\Match' => $baseDir . '/Zotlabs/Module/Match.php',
'Zotlabs\\Module\\Menu' => $baseDir . '/Zotlabs/Module/Menu.php',
'Zotlabs\\Module\\Message' => $baseDir . '/Zotlabs/Module/Message.php',
'Zotlabs\\Module\\Mitem' => $baseDir . '/Zotlabs/Module/Mitem.php',
+ 'Zotlabs\\Module\\Moderate' => $baseDir . '/Zotlabs/Module/Moderate.php',
'Zotlabs\\Module\\Mood' => $baseDir . '/Zotlabs/Module/Mood.php',
'Zotlabs\\Module\\Network' => $baseDir . '/Zotlabs/Module/Network.php',
'Zotlabs\\Module\\New_channel' => $baseDir . '/Zotlabs/Module/New_channel.php',
@@ -492,10 +874,13 @@ return array(
'Zotlabs\\Module\\Oembed' => $baseDir . '/Zotlabs/Module/Oembed.php',
'Zotlabs\\Module\\Oep' => $baseDir . '/Zotlabs/Module/Oep.php',
'Zotlabs\\Module\\Oexchange' => $baseDir . '/Zotlabs/Module/Oexchange.php',
+ 'Zotlabs\\Module\\Ofeed' => $baseDir . '/Zotlabs/Module/Ofeed.php',
'Zotlabs\\Module\\Online' => $baseDir . '/Zotlabs/Module/Online.php',
+ 'Zotlabs\\Module\\Owa' => $baseDir . '/Zotlabs/Module/Owa.php',
'Zotlabs\\Module\\Page' => $baseDir . '/Zotlabs/Module/Page.php',
'Zotlabs\\Module\\Pconfig' => $baseDir . '/Zotlabs/Module/Pconfig.php',
'Zotlabs\\Module\\Pdledit' => $baseDir . '/Zotlabs/Module/Pdledit.php',
+ 'Zotlabs\\Module\\Permcat' => $baseDir . '/Zotlabs/Module/Permcat.php',
'Zotlabs\\Module\\Photo' => $baseDir . '/Zotlabs/Module/Photo.php',
'Zotlabs\\Module\\Photos' => $baseDir . '/Zotlabs/Module/Photos.php',
'Zotlabs\\Module\\Ping' => $baseDir . '/Zotlabs/Module/Ping.php',
@@ -525,7 +910,6 @@ return array(
'Zotlabs\\Module\\Removeme' => $baseDir . '/Zotlabs/Module/Removeme.php',
'Zotlabs\\Module\\Rmagic' => $baseDir . '/Zotlabs/Module/Rmagic.php',
'Zotlabs\\Module\\Rpost' => $baseDir . '/Zotlabs/Module/Rpost.php',
- 'Zotlabs\\Module\\Rsd_xml' => $baseDir . '/Zotlabs/Module/Rsd_xml.php',
'Zotlabs\\Module\\Search' => $baseDir . '/Zotlabs/Module/Search.php',
'Zotlabs\\Module\\Search_ac' => $baseDir . '/Zotlabs/Module/Search_ac.php',
'Zotlabs\\Module\\Service_limits' => $baseDir . '/Zotlabs/Module/Service_limits.php',
@@ -536,12 +920,12 @@ return array(
'Zotlabs\\Module\\Settings\\Featured' => $baseDir . '/Zotlabs/Module/Settings/Featured.php',
'Zotlabs\\Module\\Settings\\Features' => $baseDir . '/Zotlabs/Module/Settings/Features.php',
'Zotlabs\\Module\\Settings\\Oauth' => $baseDir . '/Zotlabs/Module/Settings/Oauth.php',
+ 'Zotlabs\\Module\\Settings\\Permcats' => $baseDir . '/Zotlabs/Module/Settings/Permcats.php',
'Zotlabs\\Module\\Settings\\Tokens' => $baseDir . '/Zotlabs/Module/Settings/Tokens.php',
'Zotlabs\\Module\\Setup' => $baseDir . '/Zotlabs/Module/Setup.php',
'Zotlabs\\Module\\Share' => $baseDir . '/Zotlabs/Module/Share.php',
'Zotlabs\\Module\\Sharedwithme' => $baseDir . '/Zotlabs/Module/Sharedwithme.php',
'Zotlabs\\Module\\Siteinfo' => $baseDir . '/Zotlabs/Module/Siteinfo.php',
- 'Zotlabs\\Module\\Siteinfo_json' => $baseDir . '/Zotlabs/Module/Siteinfo_json.php',
'Zotlabs\\Module\\Sitelist' => $baseDir . '/Zotlabs/Module/Sitelist.php',
'Zotlabs\\Module\\Smilies' => $baseDir . '/Zotlabs/Module/Smilies.php',
'Zotlabs\\Module\\Snap' => $baseDir . '/Zotlabs/Module/Snap.php',
@@ -557,7 +941,9 @@ return array(
'Zotlabs\\Module\\Thing' => $baseDir . '/Zotlabs/Module/Thing.php',
'Zotlabs\\Module\\Toggle_mobile' => $baseDir . '/Zotlabs/Module/Toggle_mobile.php',
'Zotlabs\\Module\\Toggle_safesearch' => $baseDir . '/Zotlabs/Module/Toggle_safesearch.php',
+ 'Zotlabs\\Module\\Token' => $baseDir . '/Zotlabs/Module/Token.php',
'Zotlabs\\Module\\Uexport' => $baseDir . '/Zotlabs/Module/Uexport.php',
+ 'Zotlabs\\Module\\Update_cards' => $baseDir . '/Zotlabs/Module/Update_cards.php',
'Zotlabs\\Module\\Update_channel' => $baseDir . '/Zotlabs/Module/Update_channel.php',
'Zotlabs\\Module\\Update_display' => $baseDir . '/Zotlabs/Module/Update_display.php',
'Zotlabs\\Module\\Update_home' => $baseDir . '/Zotlabs/Module/Update_home.php',
@@ -596,12 +982,70 @@ return array(
'Zotlabs\\Text\\Tagadelic' => $baseDir . '/Zotlabs/Text/Tagadelic.php',
'Zotlabs\\Web\\CheckJS' => $baseDir . '/Zotlabs/Web/CheckJS.php',
'Zotlabs\\Web\\Controller' => $baseDir . '/Zotlabs/Web/Controller.php',
+ 'Zotlabs\\Web\\HTTPHeaders' => $baseDir . '/Zotlabs/Web/HTTPHeaders.php',
+ 'Zotlabs\\Web\\HTTPSig' => $baseDir . '/Zotlabs/Web/HTTPSig.php',
'Zotlabs\\Web\\HttpMeta' => $baseDir . '/Zotlabs/Web/HttpMeta.php',
'Zotlabs\\Web\\Router' => $baseDir . '/Zotlabs/Web/Router.php',
'Zotlabs\\Web\\Session' => $baseDir . '/Zotlabs/Web/Session.php',
'Zotlabs\\Web\\SessionHandler' => $baseDir . '/Zotlabs/Web/SessionHandler.php',
'Zotlabs\\Web\\SubModule' => $baseDir . '/Zotlabs/Web/SubModule.php',
'Zotlabs\\Web\\WebServer' => $baseDir . '/Zotlabs/Web/WebServer.php',
+ 'Zotlabs\\Widget\\Activity' => $baseDir . '/Zotlabs/Widget/Activity.php',
+ 'Zotlabs\\Widget\\Admin' => $baseDir . '/Zotlabs/Widget/Admin.php',
+ 'Zotlabs\\Widget\\Affinity' => $baseDir . '/Zotlabs/Widget/Affinity.php',
+ 'Zotlabs\\Widget\\Album' => $baseDir . '/Zotlabs/Widget/Album.php',
+ 'Zotlabs\\Widget\\Appcategories' => $baseDir . '/Zotlabs/Widget/Appcategories.php',
+ 'Zotlabs\\Widget\\Appcloud' => $baseDir . '/Zotlabs/Widget/Appcloud.php',
+ 'Zotlabs\\Widget\\Archive' => $baseDir . '/Zotlabs/Widget/Archive.php',
+ 'Zotlabs\\Widget\\Bookmarkedchats' => $baseDir . '/Zotlabs/Widget/Bookmarkedchats.php',
+ 'Zotlabs\\Widget\\Catcloud_wall' => $baseDir . '/Zotlabs/Widget/Catcloud_wall.php',
+ 'Zotlabs\\Widget\\Categories' => $baseDir . '/Zotlabs/Widget/Categories.php',
+ 'Zotlabs\\Widget\\Cdav' => $baseDir . '/Zotlabs/Widget/Cdav.php',
+ 'Zotlabs\\Widget\\Chatroom_list' => $baseDir . '/Zotlabs/Widget/Chatroom_list.php',
+ 'Zotlabs\\Widget\\Chatroom_members' => $baseDir . '/Zotlabs/Widget/Chatroom_members.php',
+ 'Zotlabs\\Widget\\Clock' => $baseDir . '/Zotlabs/Widget/Clock.php',
+ 'Zotlabs\\Widget\\Collections' => $baseDir . '/Zotlabs/Widget/Collections.php',
+ 'Zotlabs\\Widget\\Common_friends' => $baseDir . '/Zotlabs/Widget/Common_friends.php',
+ 'Zotlabs\\Widget\\Conversations' => $baseDir . '/Zotlabs/Widget/Conversations.php',
+ 'Zotlabs\\Widget\\Cover_photo' => $baseDir . '/Zotlabs/Widget/Cover_photo.php',
+ 'Zotlabs\\Widget\\Design_tools' => $baseDir . '/Zotlabs/Widget/Design_tools.php',
+ 'Zotlabs\\Widget\\Dirsort' => $baseDir . '/Zotlabs/Widget/Dirsort.php',
+ 'Zotlabs\\Widget\\Dirtags' => $baseDir . '/Zotlabs/Widget/Dirtags.php',
+ 'Zotlabs\\Widget\\Eventstools' => $baseDir . '/Zotlabs/Widget/Eventstools.php',
+ 'Zotlabs\\Widget\\Filer' => $baseDir . '/Zotlabs/Widget/Filer.php',
+ 'Zotlabs\\Widget\\Findpeople' => $baseDir . '/Zotlabs/Widget/Findpeople.php',
+ 'Zotlabs\\Widget\\Follow' => $baseDir . '/Zotlabs/Widget/Follow.php',
+ 'Zotlabs\\Widget\\Forums' => $baseDir . '/Zotlabs/Widget/Forums.php',
+ 'Zotlabs\\Widget\\Fullprofile' => $baseDir . '/Zotlabs/Widget/Fullprofile.php',
+ 'Zotlabs\\Widget\\Helpindex' => $baseDir . '/Zotlabs/Widget/Helpindex.php',
+ 'Zotlabs\\Widget\\Item' => $baseDir . '/Zotlabs/Widget/Item.php',
+ 'Zotlabs\\Widget\\Mailmenu' => $baseDir . '/Zotlabs/Widget/Mailmenu.php',
+ 'Zotlabs\\Widget\\Menu_preview' => $baseDir . '/Zotlabs/Widget/Menu_preview.php',
+ 'Zotlabs\\Widget\\Notes' => $baseDir . '/Zotlabs/Widget/Notes.php',
+ 'Zotlabs\\Widget\\Notifications' => $baseDir . '/Zotlabs/Widget/Notifications.php',
+ 'Zotlabs\\Widget\\Photo' => $baseDir . '/Zotlabs/Widget/Photo.php',
+ 'Zotlabs\\Widget\\Photo_albums' => $baseDir . '/Zotlabs/Widget/Photo_albums.php',
+ 'Zotlabs\\Widget\\Photo_rand' => $baseDir . '/Zotlabs/Widget/Photo_rand.php',
+ 'Zotlabs\\Widget\\Portfolio' => $baseDir . '/Zotlabs/Widget/Portfolio.php',
+ 'Zotlabs\\Widget\\Profile' => $baseDir . '/Zotlabs/Widget/Profile.php',
+ 'Zotlabs\\Widget\\Pubsites' => $baseDir . '/Zotlabs/Widget/Pubsites.php',
+ 'Zotlabs\\Widget\\Random_block' => $baseDir . '/Zotlabs/Widget/Random_block.php',
+ 'Zotlabs\\Widget\\Rating' => $baseDir . '/Zotlabs/Widget/Rating.php',
+ 'Zotlabs\\Widget\\Savedsearch' => $baseDir . '/Zotlabs/Widget/Savedsearch.php',
+ 'Zotlabs\\Widget\\Settings_menu' => $baseDir . '/Zotlabs/Widget/Settings_menu.php',
+ 'Zotlabs\\Widget\\Shortprofile' => $baseDir . '/Zotlabs/Widget/Shortprofile.php',
+ 'Zotlabs\\Widget\\Sitesearch' => $baseDir . '/Zotlabs/Widget/Sitesearch.php',
+ 'Zotlabs\\Widget\\Suggestedchats' => $baseDir . '/Zotlabs/Widget/Suggestedchats.php',
+ 'Zotlabs\\Widget\\Suggestions' => $baseDir . '/Zotlabs/Widget/Suggestions.php',
+ 'Zotlabs\\Widget\\Tagcloud' => $baseDir . '/Zotlabs/Widget/Tagcloud.php',
+ 'Zotlabs\\Widget\\Tagcloud_wall' => $baseDir . '/Zotlabs/Widget/Tagcloud_wall.php',
+ 'Zotlabs\\Widget\\Tasklist' => $baseDir . '/Zotlabs/Widget/Tasklist.php',
+ 'Zotlabs\\Widget\\Vcard' => $baseDir . '/Zotlabs/Widget/Vcard.php',
+ 'Zotlabs\\Widget\\Website_portation_tools' => $baseDir . '/Zotlabs/Widget/Website_portation_tools.php',
+ 'Zotlabs\\Widget\\Wiki_list' => $baseDir . '/Zotlabs/Widget/Wiki_list.php',
+ 'Zotlabs\\Widget\\Wiki_page_history' => $baseDir . '/Zotlabs/Widget/Wiki_page_history.php',
+ 'Zotlabs\\Widget\\Wiki_pages' => $baseDir . '/Zotlabs/Widget/Wiki_pages.php',
+ 'Zotlabs\\Widget\\Zcard' => $baseDir . '/Zotlabs/Widget/Zcard.php',
'Zotlabs\\Zot\\Auth' => $baseDir . '/Zotlabs/Zot/Auth.php',
'Zotlabs\\Zot\\DReport' => $baseDir . '/Zotlabs/Zot/DReport.php',
'Zotlabs\\Zot\\Finger' => $baseDir . '/Zotlabs/Zot/Finger.php',
diff --git a/vendor/composer/autoload_files.php b/vendor/composer/autoload_files.php
index a78cbe6fb..bbe6fd553 100644
--- a/vendor/composer/autoload_files.php
+++ b/vendor/composer/autoload_files.php
@@ -13,4 +13,5 @@ return array(
'3569eecfeed3bcf0bad3c998a494ecb8' => $vendorDir . '/sabre/xml/lib/Deserializer/functions.php',
'93aa591bc4ca510c520999e34229ee79' => $vendorDir . '/sabre/xml/lib/Serializer/functions.php',
'ebdb698ed4152ae445614b69b5e4bb6a' => $vendorDir . '/sabre/http/lib/functions.php',
+ '2cffec82183ee1cea088009cef9a6fc3' => $vendorDir . '/ezyang/htmlpurifier/library/HTMLPurifier.composer.php',
);
diff --git a/vendor/composer/autoload_namespaces.php b/vendor/composer/autoload_namespaces.php
index b7fc0125d..d7070bbbf 100644
--- a/vendor/composer/autoload_namespaces.php
+++ b/vendor/composer/autoload_namespaces.php
@@ -6,4 +6,8 @@ $vendorDir = dirname(dirname(__FILE__));
$baseDir = dirname($vendorDir);
return array(
+ 'SimplePie' => array($vendorDir . '/simplepie/simplepie/library'),
+ 'OAuth2' => array($vendorDir . '/bshaffer/oauth2-server-php/src'),
+ 'Michelf' => array($vendorDir . '/michelf/php-markdown'),
+ 'HTMLPurifier' => array($vendorDir . '/ezyang/htmlpurifier/library'),
);
diff --git a/vendor/composer/autoload_psr4.php b/vendor/composer/autoload_psr4.php
index e8ea2ed78..48bc1158a 100644
--- a/vendor/composer/autoload_psr4.php
+++ b/vendor/composer/autoload_psr4.php
@@ -17,5 +17,6 @@ return array(
'Sabre\\CardDAV\\' => array($vendorDir . '/sabre/dav/lib/CardDAV'),
'Sabre\\CalDAV\\' => array($vendorDir . '/sabre/dav/lib/CalDAV'),
'Psr\\Log\\' => array($vendorDir . '/psr/log/Psr/Log'),
+ 'League\\HTMLToMarkdown\\' => array($vendorDir . '/league/html-to-markdown/src'),
'Hubzilla\\' => array($baseDir . '/include'),
);
diff --git a/vendor/composer/autoload_real.php b/vendor/composer/autoload_real.php
index 24b45085d..bcae78e29 100644
--- a/vendor/composer/autoload_real.php
+++ b/vendor/composer/autoload_real.php
@@ -23,7 +23,7 @@ class ComposerAutoloaderInit7b34d7e50a62201ec5d5e526a5b8b35d
self::$loader = $loader = new \Composer\Autoload\ClassLoader();
spl_autoload_unregister(array('ComposerAutoloaderInit7b34d7e50a62201ec5d5e526a5b8b35d', 'loadClassLoader'));
- $useStaticLoader = PHP_VERSION_ID >= 50600 && !defined('HHVM_VERSION');
+ $useStaticLoader = PHP_VERSION_ID >= 50600 && !defined('HHVM_VERSION') && (!function_exists('zend_loader_file_encoded') || !zend_loader_file_encoded());
if ($useStaticLoader) {
require_once __DIR__ . '/autoload_static.php';
diff --git a/vendor/composer/autoload_static.php b/vendor/composer/autoload_static.php
index 7f2551665..0374e7872 100644
--- a/vendor/composer/autoload_static.php
+++ b/vendor/composer/autoload_static.php
@@ -14,6 +14,7 @@ class ComposerStaticInit7b34d7e50a62201ec5d5e526a5b8b35d
'3569eecfeed3bcf0bad3c998a494ecb8' => __DIR__ . '/..' . '/sabre/xml/lib/Deserializer/functions.php',
'93aa591bc4ca510c520999e34229ee79' => __DIR__ . '/..' . '/sabre/xml/lib/Serializer/functions.php',
'ebdb698ed4152ae445614b69b5e4bb6a' => __DIR__ . '/..' . '/sabre/http/lib/functions.php',
+ '2cffec82183ee1cea088009cef9a6fc3' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier.composer.php',
);
public static $prefixLengthsPsr4 = array (
@@ -37,6 +38,10 @@ class ComposerStaticInit7b34d7e50a62201ec5d5e526a5b8b35d
array (
'Psr\\Log\\' => 8,
),
+ 'L' =>
+ array (
+ 'League\\HTMLToMarkdown\\' => 22,
+ ),
'H' =>
array (
'Hubzilla\\' => 9,
@@ -88,14 +93,377 @@ class ComposerStaticInit7b34d7e50a62201ec5d5e526a5b8b35d
array (
0 => __DIR__ . '/..' . '/psr/log/Psr/Log',
),
+ 'League\\HTMLToMarkdown\\' =>
+ array (
+ 0 => __DIR__ . '/..' . '/league/html-to-markdown/src',
+ ),
'Hubzilla\\' =>
array (
0 => __DIR__ . '/../..' . '/include',
),
);
+ public static $prefixesPsr0 = array (
+ 'S' =>
+ array (
+ 'SimplePie' =>
+ array (
+ 0 => __DIR__ . '/..' . '/simplepie/simplepie/library',
+ ),
+ ),
+ 'O' =>
+ array (
+ 'OAuth2' =>
+ array (
+ 0 => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src',
+ ),
+ ),
+ 'M' =>
+ array (
+ 'Michelf' =>
+ array (
+ 0 => __DIR__ . '/..' . '/michelf/php-markdown',
+ ),
+ ),
+ 'H' =>
+ array (
+ 'HTMLPurifier' =>
+ array (
+ 0 => __DIR__ . '/..' . '/ezyang/htmlpurifier/library',
+ ),
+ ),
+ );
+
public static $classMap = array (
+ 'HTMLPurifier' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier.php',
+ 'HTMLPurifier_Arborize' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Arborize.php',
+ 'HTMLPurifier_AttrCollections' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrCollections.php',
+ 'HTMLPurifier_AttrDef' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef.php',
+ 'HTMLPurifier_AttrDef_CSS' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS.php',
+ 'HTMLPurifier_AttrDef_CSS_AlphaValue' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/AlphaValue.php',
+ 'HTMLPurifier_AttrDef_CSS_Background' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Background.php',
+ 'HTMLPurifier_AttrDef_CSS_BackgroundPosition' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/BackgroundPosition.php',
+ 'HTMLPurifier_AttrDef_CSS_Border' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Border.php',
+ 'HTMLPurifier_AttrDef_CSS_Color' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Color.php',
+ 'HTMLPurifier_AttrDef_CSS_Composite' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Composite.php',
+ 'HTMLPurifier_AttrDef_CSS_DenyElementDecorator' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/DenyElementDecorator.php',
+ 'HTMLPurifier_AttrDef_CSS_Filter' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Filter.php',
+ 'HTMLPurifier_AttrDef_CSS_Font' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Font.php',
+ 'HTMLPurifier_AttrDef_CSS_FontFamily' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/FontFamily.php',
+ 'HTMLPurifier_AttrDef_CSS_Ident' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Ident.php',
+ 'HTMLPurifier_AttrDef_CSS_ImportantDecorator' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/ImportantDecorator.php',
+ 'HTMLPurifier_AttrDef_CSS_Length' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Length.php',
+ 'HTMLPurifier_AttrDef_CSS_ListStyle' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/ListStyle.php',
+ 'HTMLPurifier_AttrDef_CSS_Multiple' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Multiple.php',
+ 'HTMLPurifier_AttrDef_CSS_Number' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Number.php',
+ 'HTMLPurifier_AttrDef_CSS_Percentage' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Percentage.php',
+ 'HTMLPurifier_AttrDef_CSS_TextDecoration' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/TextDecoration.php',
+ 'HTMLPurifier_AttrDef_CSS_URI' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/URI.php',
+ 'HTMLPurifier_AttrDef_Clone' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Clone.php',
+ 'HTMLPurifier_AttrDef_Enum' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Enum.php',
+ 'HTMLPurifier_AttrDef_HTML_Bool' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Bool.php',
+ 'HTMLPurifier_AttrDef_HTML_Class' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Class.php',
+ 'HTMLPurifier_AttrDef_HTML_Color' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Color.php',
+ 'HTMLPurifier_AttrDef_HTML_FrameTarget' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/FrameTarget.php',
+ 'HTMLPurifier_AttrDef_HTML_ID' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/ID.php',
+ 'HTMLPurifier_AttrDef_HTML_Length' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Length.php',
+ 'HTMLPurifier_AttrDef_HTML_LinkTypes' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/LinkTypes.php',
+ 'HTMLPurifier_AttrDef_HTML_MultiLength' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/MultiLength.php',
+ 'HTMLPurifier_AttrDef_HTML_Nmtokens' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Nmtokens.php',
+ 'HTMLPurifier_AttrDef_HTML_Pixels' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Pixels.php',
+ 'HTMLPurifier_AttrDef_Integer' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Integer.php',
+ 'HTMLPurifier_AttrDef_Lang' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Lang.php',
+ 'HTMLPurifier_AttrDef_Switch' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Switch.php',
+ 'HTMLPurifier_AttrDef_Text' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Text.php',
+ 'HTMLPurifier_AttrDef_URI' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI.php',
+ 'HTMLPurifier_AttrDef_URI_Email' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/Email.php',
+ 'HTMLPurifier_AttrDef_URI_Email_SimpleCheck' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/Email/SimpleCheck.php',
+ 'HTMLPurifier_AttrDef_URI_Host' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/Host.php',
+ 'HTMLPurifier_AttrDef_URI_IPv4' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/IPv4.php',
+ 'HTMLPurifier_AttrDef_URI_IPv6' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/IPv6.php',
+ 'HTMLPurifier_AttrTransform' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform.php',
+ 'HTMLPurifier_AttrTransform_Background' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Background.php',
+ 'HTMLPurifier_AttrTransform_BdoDir' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/BdoDir.php',
+ 'HTMLPurifier_AttrTransform_BgColor' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/BgColor.php',
+ 'HTMLPurifier_AttrTransform_BoolToCSS' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/BoolToCSS.php',
+ 'HTMLPurifier_AttrTransform_Border' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Border.php',
+ 'HTMLPurifier_AttrTransform_EnumToCSS' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/EnumToCSS.php',
+ 'HTMLPurifier_AttrTransform_ImgRequired' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/ImgRequired.php',
+ 'HTMLPurifier_AttrTransform_ImgSpace' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/ImgSpace.php',
+ 'HTMLPurifier_AttrTransform_Input' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Input.php',
+ 'HTMLPurifier_AttrTransform_Lang' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Lang.php',
+ 'HTMLPurifier_AttrTransform_Length' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Length.php',
+ 'HTMLPurifier_AttrTransform_Name' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Name.php',
+ 'HTMLPurifier_AttrTransform_NameSync' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/NameSync.php',
+ 'HTMLPurifier_AttrTransform_Nofollow' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Nofollow.php',
+ 'HTMLPurifier_AttrTransform_SafeEmbed' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/SafeEmbed.php',
+ 'HTMLPurifier_AttrTransform_SafeObject' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/SafeObject.php',
+ 'HTMLPurifier_AttrTransform_SafeParam' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/SafeParam.php',
+ 'HTMLPurifier_AttrTransform_ScriptRequired' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/ScriptRequired.php',
+ 'HTMLPurifier_AttrTransform_TargetBlank' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/TargetBlank.php',
+ 'HTMLPurifier_AttrTransform_TargetNoopener' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/TargetNoopener.php',
+ 'HTMLPurifier_AttrTransform_TargetNoreferrer' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/TargetNoreferrer.php',
+ 'HTMLPurifier_AttrTransform_Textarea' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Textarea.php',
+ 'HTMLPurifier_AttrTypes' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrTypes.php',
+ 'HTMLPurifier_AttrValidator' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/AttrValidator.php',
+ 'HTMLPurifier_Bootstrap' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Bootstrap.php',
+ 'HTMLPurifier_CSSDefinition' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/CSSDefinition.php',
+ 'HTMLPurifier_ChildDef' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef.php',
+ 'HTMLPurifier_ChildDef_Chameleon' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Chameleon.php',
+ 'HTMLPurifier_ChildDef_Custom' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Custom.php',
+ 'HTMLPurifier_ChildDef_Empty' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Empty.php',
+ 'HTMLPurifier_ChildDef_List' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/List.php',
+ 'HTMLPurifier_ChildDef_Optional' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Optional.php',
+ 'HTMLPurifier_ChildDef_Required' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Required.php',
+ 'HTMLPurifier_ChildDef_StrictBlockquote' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/StrictBlockquote.php',
+ 'HTMLPurifier_ChildDef_Table' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Table.php',
+ 'HTMLPurifier_Config' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Config.php',
+ 'HTMLPurifier_ConfigSchema' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema.php',
+ 'HTMLPurifier_ConfigSchema_Builder_ConfigSchema' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Builder/ConfigSchema.php',
+ 'HTMLPurifier_ConfigSchema_Builder_Xml' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Builder/Xml.php',
+ 'HTMLPurifier_ConfigSchema_Exception' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Exception.php',
+ 'HTMLPurifier_ConfigSchema_Interchange' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Interchange.php',
+ 'HTMLPurifier_ConfigSchema_InterchangeBuilder' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/InterchangeBuilder.php',
+ 'HTMLPurifier_ConfigSchema_Interchange_Directive' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Interchange/Directive.php',
+ 'HTMLPurifier_ConfigSchema_Interchange_Id' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Interchange/Id.php',
+ 'HTMLPurifier_ConfigSchema_Validator' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Validator.php',
+ 'HTMLPurifier_ConfigSchema_ValidatorAtom' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/ValidatorAtom.php',
+ 'HTMLPurifier_ContentSets' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/ContentSets.php',
+ 'HTMLPurifier_Context' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Context.php',
+ 'HTMLPurifier_Definition' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Definition.php',
+ 'HTMLPurifier_DefinitionCache' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache.php',
+ 'HTMLPurifier_DefinitionCacheFactory' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCacheFactory.php',
+ 'HTMLPurifier_DefinitionCache_Decorator' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Decorator.php',
+ 'HTMLPurifier_DefinitionCache_Decorator_Cleanup' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Decorator/Cleanup.php',
+ 'HTMLPurifier_DefinitionCache_Decorator_Memory' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Decorator/Memory.php',
+ 'HTMLPurifier_DefinitionCache_Null' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Null.php',
+ 'HTMLPurifier_DefinitionCache_Serializer' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Serializer.php',
+ 'HTMLPurifier_Doctype' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Doctype.php',
+ 'HTMLPurifier_DoctypeRegistry' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/DoctypeRegistry.php',
+ 'HTMLPurifier_ElementDef' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/ElementDef.php',
+ 'HTMLPurifier_Encoder' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Encoder.php',
+ 'HTMLPurifier_EntityLookup' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/EntityLookup.php',
+ 'HTMLPurifier_EntityParser' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/EntityParser.php',
+ 'HTMLPurifier_ErrorCollector' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/ErrorCollector.php',
+ 'HTMLPurifier_ErrorStruct' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/ErrorStruct.php',
+ 'HTMLPurifier_Exception' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Exception.php',
+ 'HTMLPurifier_Filter' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Filter.php',
+ 'HTMLPurifier_Filter_ExtractStyleBlocks' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Filter/ExtractStyleBlocks.php',
+ 'HTMLPurifier_Filter_YouTube' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Filter/YouTube.php',
+ 'HTMLPurifier_Generator' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Generator.php',
+ 'HTMLPurifier_HTMLDefinition' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLDefinition.php',
+ 'HTMLPurifier_HTMLModule' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule.php',
+ 'HTMLPurifier_HTMLModuleManager' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModuleManager.php',
+ 'HTMLPurifier_HTMLModule_Bdo' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Bdo.php',
+ 'HTMLPurifier_HTMLModule_CommonAttributes' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/CommonAttributes.php',
+ 'HTMLPurifier_HTMLModule_Edit' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Edit.php',
+ 'HTMLPurifier_HTMLModule_Forms' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Forms.php',
+ 'HTMLPurifier_HTMLModule_Hypertext' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Hypertext.php',
+ 'HTMLPurifier_HTMLModule_Iframe' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Iframe.php',
+ 'HTMLPurifier_HTMLModule_Image' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Image.php',
+ 'HTMLPurifier_HTMLModule_Legacy' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Legacy.php',
+ 'HTMLPurifier_HTMLModule_List' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/List.php',
+ 'HTMLPurifier_HTMLModule_Name' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Name.php',
+ 'HTMLPurifier_HTMLModule_Nofollow' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Nofollow.php',
+ 'HTMLPurifier_HTMLModule_NonXMLCommonAttributes' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/NonXMLCommonAttributes.php',
+ 'HTMLPurifier_HTMLModule_Object' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Object.php',
+ 'HTMLPurifier_HTMLModule_Presentation' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Presentation.php',
+ 'HTMLPurifier_HTMLModule_Proprietary' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Proprietary.php',
+ 'HTMLPurifier_HTMLModule_Ruby' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Ruby.php',
+ 'HTMLPurifier_HTMLModule_SafeEmbed' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/SafeEmbed.php',
+ 'HTMLPurifier_HTMLModule_SafeObject' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/SafeObject.php',
+ 'HTMLPurifier_HTMLModule_SafeScripting' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/SafeScripting.php',
+ 'HTMLPurifier_HTMLModule_Scripting' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Scripting.php',
+ 'HTMLPurifier_HTMLModule_StyleAttribute' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/StyleAttribute.php',
+ 'HTMLPurifier_HTMLModule_Tables' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tables.php',
+ 'HTMLPurifier_HTMLModule_Target' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Target.php',
+ 'HTMLPurifier_HTMLModule_TargetBlank' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/TargetBlank.php',
+ 'HTMLPurifier_HTMLModule_TargetNoopener' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/TargetNoopener.php',
+ 'HTMLPurifier_HTMLModule_TargetNoreferrer' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/TargetNoreferrer.php',
+ 'HTMLPurifier_HTMLModule_Text' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Text.php',
+ 'HTMLPurifier_HTMLModule_Tidy' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy.php',
+ 'HTMLPurifier_HTMLModule_Tidy_Name' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/Name.php',
+ 'HTMLPurifier_HTMLModule_Tidy_Proprietary' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/Proprietary.php',
+ 'HTMLPurifier_HTMLModule_Tidy_Strict' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/Strict.php',
+ 'HTMLPurifier_HTMLModule_Tidy_Transitional' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/Transitional.php',
+ 'HTMLPurifier_HTMLModule_Tidy_XHTML' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/XHTML.php',
+ 'HTMLPurifier_HTMLModule_Tidy_XHTMLAndHTML4' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/XHTMLAndHTML4.php',
+ 'HTMLPurifier_HTMLModule_XMLCommonAttributes' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/XMLCommonAttributes.php',
+ 'HTMLPurifier_IDAccumulator' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/IDAccumulator.php',
+ 'HTMLPurifier_Injector' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Injector.php',
+ 'HTMLPurifier_Injector_AutoParagraph' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Injector/AutoParagraph.php',
+ 'HTMLPurifier_Injector_DisplayLinkURI' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Injector/DisplayLinkURI.php',
+ 'HTMLPurifier_Injector_Linkify' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Injector/Linkify.php',
+ 'HTMLPurifier_Injector_PurifierLinkify' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Injector/PurifierLinkify.php',
+ 'HTMLPurifier_Injector_RemoveEmpty' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Injector/RemoveEmpty.php',
+ 'HTMLPurifier_Injector_RemoveSpansWithoutAttributes' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Injector/RemoveSpansWithoutAttributes.php',
+ 'HTMLPurifier_Injector_SafeObject' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Injector/SafeObject.php',
+ 'HTMLPurifier_Language' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Language.php',
+ 'HTMLPurifier_LanguageFactory' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/LanguageFactory.php',
+ 'HTMLPurifier_Language_en_x_test' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Language/classes/en-x-test.php',
+ 'HTMLPurifier_Length' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Length.php',
+ 'HTMLPurifier_Lexer' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Lexer.php',
+ 'HTMLPurifier_Lexer_DOMLex' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Lexer/DOMLex.php',
+ 'HTMLPurifier_Lexer_DirectLex' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Lexer/DirectLex.php',
+ 'HTMLPurifier_Lexer_PH5P' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Lexer/PH5P.php',
+ 'HTMLPurifier_Node' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Node.php',
+ 'HTMLPurifier_Node_Comment' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Node/Comment.php',
+ 'HTMLPurifier_Node_Element' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Node/Element.php',
+ 'HTMLPurifier_Node_Text' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Node/Text.php',
+ 'HTMLPurifier_PercentEncoder' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/PercentEncoder.php',
+ 'HTMLPurifier_Printer' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Printer.php',
+ 'HTMLPurifier_Printer_CSSDefinition' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Printer/CSSDefinition.php',
+ 'HTMLPurifier_Printer_ConfigForm' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Printer/ConfigForm.php',
+ 'HTMLPurifier_Printer_ConfigForm_NullDecorator' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Printer/ConfigForm.php',
+ 'HTMLPurifier_Printer_ConfigForm_bool' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Printer/ConfigForm.php',
+ 'HTMLPurifier_Printer_ConfigForm_default' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Printer/ConfigForm.php',
+ 'HTMLPurifier_Printer_HTMLDefinition' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Printer/HTMLDefinition.php',
+ 'HTMLPurifier_PropertyList' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/PropertyList.php',
+ 'HTMLPurifier_PropertyListIterator' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/PropertyListIterator.php',
+ 'HTMLPurifier_Queue' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Queue.php',
+ 'HTMLPurifier_Strategy' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Strategy.php',
+ 'HTMLPurifier_Strategy_Composite' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/Composite.php',
+ 'HTMLPurifier_Strategy_Core' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/Core.php',
+ 'HTMLPurifier_Strategy_FixNesting' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/FixNesting.php',
+ 'HTMLPurifier_Strategy_MakeWellFormed' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/MakeWellFormed.php',
+ 'HTMLPurifier_Strategy_RemoveForeignElements' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/RemoveForeignElements.php',
+ 'HTMLPurifier_Strategy_ValidateAttributes' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/ValidateAttributes.php',
+ 'HTMLPurifier_StringHash' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/StringHash.php',
+ 'HTMLPurifier_StringHashParser' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/StringHashParser.php',
+ 'HTMLPurifier_TagTransform' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/TagTransform.php',
+ 'HTMLPurifier_TagTransform_Font' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/TagTransform/Font.php',
+ 'HTMLPurifier_TagTransform_Simple' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/TagTransform/Simple.php',
+ 'HTMLPurifier_Token' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Token.php',
+ 'HTMLPurifier_TokenFactory' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/TokenFactory.php',
+ 'HTMLPurifier_Token_Comment' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Token/Comment.php',
+ 'HTMLPurifier_Token_Empty' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Token/Empty.php',
+ 'HTMLPurifier_Token_End' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Token/End.php',
+ 'HTMLPurifier_Token_Start' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Token/Start.php',
+ 'HTMLPurifier_Token_Tag' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Token/Tag.php',
+ 'HTMLPurifier_Token_Text' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Token/Text.php',
+ 'HTMLPurifier_URI' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/URI.php',
+ 'HTMLPurifier_URIDefinition' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/URIDefinition.php',
+ 'HTMLPurifier_URIFilter' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter.php',
+ 'HTMLPurifier_URIFilter_DisableExternal' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/DisableExternal.php',
+ 'HTMLPurifier_URIFilter_DisableExternalResources' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/DisableExternalResources.php',
+ 'HTMLPurifier_URIFilter_DisableResources' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/DisableResources.php',
+ 'HTMLPurifier_URIFilter_HostBlacklist' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/HostBlacklist.php',
+ 'HTMLPurifier_URIFilter_MakeAbsolute' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/MakeAbsolute.php',
+ 'HTMLPurifier_URIFilter_Munge' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/Munge.php',
+ 'HTMLPurifier_URIFilter_SafeIframe' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/SafeIframe.php',
+ 'HTMLPurifier_URIParser' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/URIParser.php',
+ 'HTMLPurifier_URIScheme' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme.php',
+ 'HTMLPurifier_URISchemeRegistry' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/URISchemeRegistry.php',
+ 'HTMLPurifier_URIScheme_data' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/data.php',
+ 'HTMLPurifier_URIScheme_file' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/file.php',
+ 'HTMLPurifier_URIScheme_ftp' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/ftp.php',
+ 'HTMLPurifier_URIScheme_http' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/http.php',
+ 'HTMLPurifier_URIScheme_https' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/https.php',
+ 'HTMLPurifier_URIScheme_mailto' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/mailto.php',
+ 'HTMLPurifier_URIScheme_news' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/news.php',
+ 'HTMLPurifier_URIScheme_nntp' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/nntp.php',
+ 'HTMLPurifier_URIScheme_tel' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/tel.php',
+ 'HTMLPurifier_UnitConverter' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/UnitConverter.php',
+ 'HTMLPurifier_VarParser' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/VarParser.php',
+ 'HTMLPurifier_VarParserException' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/VarParserException.php',
+ 'HTMLPurifier_VarParser_Flexible' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/VarParser/Flexible.php',
+ 'HTMLPurifier_VarParser_Native' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/VarParser/Native.php',
+ 'HTMLPurifier_Zipper' => __DIR__ . '/..' . '/ezyang/htmlpurifier/library/HTMLPurifier/Zipper.php',
'Hubzilla\\Import\\Import' => __DIR__ . '/../..' . '/include/Import/Importer.php',
+ 'League\\HTMLToMarkdown\\Configuration' => __DIR__ . '/..' . '/league/html-to-markdown/src/Configuration.php',
+ 'League\\HTMLToMarkdown\\ConfigurationAwareInterface' => __DIR__ . '/..' . '/league/html-to-markdown/src/ConfigurationAwareInterface.php',
+ 'League\\HTMLToMarkdown\\Converter\\BlockquoteConverter' => __DIR__ . '/..' . '/league/html-to-markdown/src/Converter/BlockquoteConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\CodeConverter' => __DIR__ . '/..' . '/league/html-to-markdown/src/Converter/CodeConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\CommentConverter' => __DIR__ . '/..' . '/league/html-to-markdown/src/Converter/CommentConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\ConverterInterface' => __DIR__ . '/..' . '/league/html-to-markdown/src/Converter/ConverterInterface.php',
+ 'League\\HTMLToMarkdown\\Converter\\DefaultConverter' => __DIR__ . '/..' . '/league/html-to-markdown/src/Converter/DefaultConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\DivConverter' => __DIR__ . '/..' . '/league/html-to-markdown/src/Converter/DivConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\EmphasisConverter' => __DIR__ . '/..' . '/league/html-to-markdown/src/Converter/EmphasisConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\HardBreakConverter' => __DIR__ . '/..' . '/league/html-to-markdown/src/Converter/HardBreakConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\HeaderConverter' => __DIR__ . '/..' . '/league/html-to-markdown/src/Converter/HeaderConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\HorizontalRuleConverter' => __DIR__ . '/..' . '/league/html-to-markdown/src/Converter/HorizontalRuleConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\ImageConverter' => __DIR__ . '/..' . '/league/html-to-markdown/src/Converter/ImageConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\LinkConverter' => __DIR__ . '/..' . '/league/html-to-markdown/src/Converter/LinkConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\ListBlockConverter' => __DIR__ . '/..' . '/league/html-to-markdown/src/Converter/ListBlockConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\ListItemConverter' => __DIR__ . '/..' . '/league/html-to-markdown/src/Converter/ListItemConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\ParagraphConverter' => __DIR__ . '/..' . '/league/html-to-markdown/src/Converter/ParagraphConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\PreformattedConverter' => __DIR__ . '/..' . '/league/html-to-markdown/src/Converter/PreformattedConverter.php',
+ 'League\\HTMLToMarkdown\\Converter\\TextConverter' => __DIR__ . '/..' . '/league/html-to-markdown/src/Converter/TextConverter.php',
+ 'League\\HTMLToMarkdown\\Element' => __DIR__ . '/..' . '/league/html-to-markdown/src/Element.php',
+ 'League\\HTMLToMarkdown\\ElementInterface' => __DIR__ . '/..' . '/league/html-to-markdown/src/ElementInterface.php',
+ 'League\\HTMLToMarkdown\\Environment' => __DIR__ . '/..' . '/league/html-to-markdown/src/Environment.php',
+ 'League\\HTMLToMarkdown\\HtmlConverter' => __DIR__ . '/..' . '/league/html-to-markdown/src/HtmlConverter.php',
+ 'Michelf\\Markdown' => __DIR__ . '/..' . '/michelf/php-markdown/Michelf/Markdown.php',
+ 'Michelf\\MarkdownExtra' => __DIR__ . '/..' . '/michelf/php-markdown/Michelf/MarkdownExtra.php',
+ 'Michelf\\MarkdownInterface' => __DIR__ . '/..' . '/michelf/php-markdown/Michelf/MarkdownInterface.php',
+ 'OAuth2\\Autoloader' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Autoloader.php',
+ 'OAuth2\\ClientAssertionType\\ClientAssertionTypeInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/ClientAssertionType/ClientAssertionTypeInterface.php',
+ 'OAuth2\\ClientAssertionType\\HttpBasic' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/ClientAssertionType/HttpBasic.php',
+ 'OAuth2\\Controller\\AuthorizeController' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Controller/AuthorizeController.php',
+ 'OAuth2\\Controller\\AuthorizeControllerInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Controller/AuthorizeControllerInterface.php',
+ 'OAuth2\\Controller\\ResourceController' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Controller/ResourceController.php',
+ 'OAuth2\\Controller\\ResourceControllerInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Controller/ResourceControllerInterface.php',
+ 'OAuth2\\Controller\\TokenController' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Controller/TokenController.php',
+ 'OAuth2\\Controller\\TokenControllerInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Controller/TokenControllerInterface.php',
+ 'OAuth2\\Encryption\\EncryptionInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Encryption/EncryptionInterface.php',
+ 'OAuth2\\Encryption\\FirebaseJwt' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Encryption/FirebaseJwt.php',
+ 'OAuth2\\Encryption\\Jwt' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Encryption/Jwt.php',
+ 'OAuth2\\GrantType\\AuthorizationCode' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/GrantType/AuthorizationCode.php',
+ 'OAuth2\\GrantType\\ClientCredentials' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/GrantType/ClientCredentials.php',
+ 'OAuth2\\GrantType\\GrantTypeInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/GrantType/GrantTypeInterface.php',
+ 'OAuth2\\GrantType\\JwtBearer' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/GrantType/JwtBearer.php',
+ 'OAuth2\\GrantType\\RefreshToken' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/GrantType/RefreshToken.php',
+ 'OAuth2\\GrantType\\UserCredentials' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/GrantType/UserCredentials.php',
+ 'OAuth2\\OpenID\\Controller\\AuthorizeController' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Controller/AuthorizeController.php',
+ 'OAuth2\\OpenID\\Controller\\AuthorizeControllerInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Controller/AuthorizeControllerInterface.php',
+ 'OAuth2\\OpenID\\Controller\\UserInfoController' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Controller/UserInfoController.php',
+ 'OAuth2\\OpenID\\Controller\\UserInfoControllerInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Controller/UserInfoControllerInterface.php',
+ 'OAuth2\\OpenID\\GrantType\\AuthorizationCode' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/GrantType/AuthorizationCode.php',
+ 'OAuth2\\OpenID\\ResponseType\\AuthorizationCode' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/AuthorizationCode.php',
+ 'OAuth2\\OpenID\\ResponseType\\AuthorizationCodeInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/AuthorizationCodeInterface.php',
+ 'OAuth2\\OpenID\\ResponseType\\CodeIdToken' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/CodeIdToken.php',
+ 'OAuth2\\OpenID\\ResponseType\\CodeIdTokenInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/CodeIdTokenInterface.php',
+ 'OAuth2\\OpenID\\ResponseType\\IdToken' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/IdToken.php',
+ 'OAuth2\\OpenID\\ResponseType\\IdTokenInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/IdTokenInterface.php',
+ 'OAuth2\\OpenID\\ResponseType\\IdTokenToken' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/IdTokenToken.php',
+ 'OAuth2\\OpenID\\ResponseType\\IdTokenTokenInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/ResponseType/IdTokenTokenInterface.php',
+ 'OAuth2\\OpenID\\Storage\\AuthorizationCodeInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Storage/AuthorizationCodeInterface.php',
+ 'OAuth2\\OpenID\\Storage\\UserClaimsInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/OpenID/Storage/UserClaimsInterface.php',
+ 'OAuth2\\Request' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Request.php',
+ 'OAuth2\\RequestInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/RequestInterface.php',
+ 'OAuth2\\Response' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Response.php',
+ 'OAuth2\\ResponseInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/ResponseInterface.php',
+ 'OAuth2\\ResponseType\\AccessToken' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/AccessToken.php',
+ 'OAuth2\\ResponseType\\AccessTokenInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/AccessTokenInterface.php',
+ 'OAuth2\\ResponseType\\AuthorizationCode' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/AuthorizationCode.php',
+ 'OAuth2\\ResponseType\\AuthorizationCodeInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/AuthorizationCodeInterface.php',
+ 'OAuth2\\ResponseType\\JwtAccessToken' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/JwtAccessToken.php',
+ 'OAuth2\\ResponseType\\ResponseTypeInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/ResponseType/ResponseTypeInterface.php',
+ 'OAuth2\\Scope' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Scope.php',
+ 'OAuth2\\ScopeInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/ScopeInterface.php',
+ 'OAuth2\\Server' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Server.php',
+ 'OAuth2\\Storage\\AccessTokenInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/AccessTokenInterface.php',
+ 'OAuth2\\Storage\\AuthorizationCodeInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/AuthorizationCodeInterface.php',
+ 'OAuth2\\Storage\\Cassandra' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/Cassandra.php',
+ 'OAuth2\\Storage\\ClientCredentialsInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/ClientCredentialsInterface.php',
+ 'OAuth2\\Storage\\ClientInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/ClientInterface.php',
+ 'OAuth2\\Storage\\CouchbaseDB' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/CouchbaseDB.php',
+ 'OAuth2\\Storage\\DynamoDB' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/DynamoDB.php',
+ 'OAuth2\\Storage\\JwtAccessToken' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/JwtAccessToken.php',
+ 'OAuth2\\Storage\\JwtAccessTokenInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/JwtAccessTokenInterface.php',
+ 'OAuth2\\Storage\\JwtBearerInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/JwtBearerInterface.php',
+ 'OAuth2\\Storage\\Memory' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/Memory.php',
+ 'OAuth2\\Storage\\Mongo' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/Mongo.php',
+ 'OAuth2\\Storage\\MongoDB' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/MongoDB.php',
+ 'OAuth2\\Storage\\Pdo' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/Pdo.php',
+ 'OAuth2\\Storage\\PublicKeyInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/PublicKeyInterface.php',
+ 'OAuth2\\Storage\\Redis' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/Redis.php',
+ 'OAuth2\\Storage\\RefreshTokenInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/RefreshTokenInterface.php',
+ 'OAuth2\\Storage\\ScopeInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/ScopeInterface.php',
+ 'OAuth2\\Storage\\UserCredentialsInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/Storage/UserCredentialsInterface.php',
+ 'OAuth2\\TokenType\\Bearer' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/TokenType/Bearer.php',
+ 'OAuth2\\TokenType\\Mac' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/TokenType/Mac.php',
+ 'OAuth2\\TokenType\\TokenTypeInterface' => __DIR__ . '/..' . '/bshaffer/oauth2-server-php/src/OAuth2/TokenType/TokenTypeInterface.php',
'Psr\\Log\\AbstractLogger' => __DIR__ . '/..' . '/psr/log/Psr/Log/AbstractLogger.php',
'Psr\\Log\\InvalidArgumentException' => __DIR__ . '/..' . '/psr/log/Psr/Log/InvalidArgumentException.php',
'Psr\\Log\\LogLevel' => __DIR__ . '/..' . '/psr/log/Psr/Log/LogLevel.php',
@@ -354,6 +722,7 @@ class ComposerStaticInit7b34d7e50a62201ec5d5e526a5b8b35d
'Sabre\\HTTP\\URLUtil' => __DIR__ . '/..' . '/sabre/http/lib/URLUtil.php',
'Sabre\\HTTP\\Util' => __DIR__ . '/..' . '/sabre/http/lib/Util.php',
'Sabre\\HTTP\\Version' => __DIR__ . '/..' . '/sabre/http/lib/Version.php',
+ 'Sabre\\Uri\\InvalidUriException' => __DIR__ . '/..' . '/sabre/uri/lib/InvalidUriException.php',
'Sabre\\Uri\\Version' => __DIR__ . '/..' . '/sabre/uri/lib/Version.php',
'Sabre\\VObject\\BirthdayCalendarGenerator' => __DIR__ . '/..' . '/sabre/vobject/lib/BirthdayCalendarGenerator.php',
'Sabre\\VObject\\Cli' => __DIR__ . '/..' . '/sabre/vobject/lib/Cli.php',
@@ -442,10 +811,46 @@ class ComposerStaticInit7b34d7e50a62201ec5d5e526a5b8b35d
'Sabre\\Xml\\Writer' => __DIR__ . '/..' . '/sabre/xml/lib/Writer.php',
'Sabre\\Xml\\XmlDeserializable' => __DIR__ . '/..' . '/sabre/xml/lib/XmlDeserializable.php',
'Sabre\\Xml\\XmlSerializable' => __DIR__ . '/..' . '/sabre/xml/lib/XmlSerializable.php',
+ 'SimplePie' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie.php',
+ 'SimplePie_Author' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Author.php',
+ 'SimplePie_Cache' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Cache.php',
+ 'SimplePie_Cache_Base' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Cache/Base.php',
+ 'SimplePie_Cache_DB' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Cache/DB.php',
+ 'SimplePie_Cache_File' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Cache/File.php',
+ 'SimplePie_Cache_Memcache' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Cache/Memcache.php',
+ 'SimplePie_Cache_Memcached' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Cache/Memcached.php',
+ 'SimplePie_Cache_MySQL' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Cache/MySQL.php',
+ 'SimplePie_Cache_Redis' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Cache/Redis.php',
+ 'SimplePie_Caption' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Caption.php',
+ 'SimplePie_Category' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Category.php',
+ 'SimplePie_Content_Type_Sniffer' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Content/Type/Sniffer.php',
+ 'SimplePie_Copyright' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Copyright.php',
+ 'SimplePie_Core' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Core.php',
+ 'SimplePie_Credit' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Credit.php',
+ 'SimplePie_Decode_HTML_Entities' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Decode/HTML/Entities.php',
+ 'SimplePie_Enclosure' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Enclosure.php',
+ 'SimplePie_Exception' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Exception.php',
+ 'SimplePie_File' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/File.php',
+ 'SimplePie_HTTP_Parser' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/HTTP/Parser.php',
+ 'SimplePie_IRI' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/IRI.php',
+ 'SimplePie_Item' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Item.php',
+ 'SimplePie_Locator' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Locator.php',
+ 'SimplePie_Misc' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Misc.php',
+ 'SimplePie_Net_IPv6' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Net/IPv6.php',
+ 'SimplePie_Parse_Date' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Parse/Date.php',
+ 'SimplePie_Parser' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Parser.php',
+ 'SimplePie_Rating' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Rating.php',
+ 'SimplePie_Registry' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Registry.php',
+ 'SimplePie_Restriction' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Restriction.php',
+ 'SimplePie_Sanitize' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Sanitize.php',
+ 'SimplePie_Source' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/Source.php',
+ 'SimplePie_XML_Declaration_Parser' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/XML/Declaration/Parser.php',
+ 'SimplePie_gzdecode' => __DIR__ . '/..' . '/simplepie/simplepie/library/SimplePie/gzdecode.php',
'Zotlabs\\Access\\AccessList' => __DIR__ . '/../..' . '/Zotlabs/Access/AccessList.php',
'Zotlabs\\Access\\PermissionLimits' => __DIR__ . '/../..' . '/Zotlabs/Access/PermissionLimits.php',
'Zotlabs\\Access\\PermissionRoles' => __DIR__ . '/../..' . '/Zotlabs/Access/PermissionRoles.php',
'Zotlabs\\Access\\Permissions' => __DIR__ . '/../..' . '/Zotlabs/Access/Permissions.php',
+ 'Zotlabs\\Daemon\\Addon' => __DIR__ . '/../..' . '/Zotlabs/Daemon/Addon.php',
'Zotlabs\\Daemon\\Checksites' => __DIR__ . '/../..' . '/Zotlabs/Daemon/Checksites.php',
'Zotlabs\\Daemon\\Cli_suggest' => __DIR__ . '/../..' . '/Zotlabs/Daemon/Cli_suggest.php',
'Zotlabs\\Daemon\\Cron' => __DIR__ . '/../..' . '/Zotlabs/Daemon/Cron.php',
@@ -460,6 +865,7 @@ class ComposerStaticInit7b34d7e50a62201ec5d5e526a5b8b35d
'Zotlabs\\Daemon\\Externals' => __DIR__ . '/../..' . '/Zotlabs/Daemon/Externals.php',
'Zotlabs\\Daemon\\Gprobe' => __DIR__ . '/../..' . '/Zotlabs/Daemon/Gprobe.php',
'Zotlabs\\Daemon\\Importdoc' => __DIR__ . '/../..' . '/Zotlabs/Daemon/Importdoc.php',
+ 'Zotlabs\\Daemon\\Importfile' => __DIR__ . '/../..' . '/Zotlabs/Daemon/Importfile.php',
'Zotlabs\\Daemon\\Master' => __DIR__ . '/../..' . '/Zotlabs/Daemon/Master.php',
'Zotlabs\\Daemon\\Notifier' => __DIR__ . '/../..' . '/Zotlabs/Daemon/Notifier.php',
'Zotlabs\\Daemon\\Onedirsync' => __DIR__ . '/../..' . '/Zotlabs/Daemon/Onedirsync.php',
@@ -472,17 +878,26 @@ class ComposerStaticInit7b34d7e50a62201ec5d5e526a5b8b35d
'Zotlabs\\Identity\\ProfilePhoto\\ProfilePhoto' => __DIR__ . '/../..' . '/Zotlabs/Identity/ProfilePhoto.php',
'Zotlabs\\Lib\\AConfig' => __DIR__ . '/../..' . '/Zotlabs/Lib/AConfig.php',
'Zotlabs\\Lib\\AbConfig' => __DIR__ . '/../..' . '/Zotlabs/Lib/AbConfig.php',
+ 'Zotlabs\\Lib\\ActivityStreams' => __DIR__ . '/../..' . '/Zotlabs/Lib/ActivityStreams.php',
'Zotlabs\\Lib\\Api_router' => __DIR__ . '/../..' . '/Zotlabs/Lib/Api_router.php',
'Zotlabs\\Lib\\Apps' => __DIR__ . '/../..' . '/Zotlabs/Lib/Apps.php',
'Zotlabs\\Lib\\Cache' => __DIR__ . '/../..' . '/Zotlabs/Lib/Cache.php',
'Zotlabs\\Lib\\Chatroom' => __DIR__ . '/../..' . '/Zotlabs/Lib/Chatroom.php',
'Zotlabs\\Lib\\Config' => __DIR__ . '/../..' . '/Zotlabs/Lib/Config.php',
+ 'Zotlabs\\Lib\\DB_Upgrade' => __DIR__ . '/../..' . '/Zotlabs/Lib/DB_Upgrade.php',
'Zotlabs\\Lib\\Enotify' => __DIR__ . '/../..' . '/Zotlabs/Lib/Enotify.php',
'Zotlabs\\Lib\\ExtendedZip' => __DIR__ . '/../..' . '/Zotlabs/Lib/ExtendedZip.php',
'Zotlabs\\Lib\\IConfig' => __DIR__ . '/../..' . '/Zotlabs/Lib/IConfig.php',
+ 'Zotlabs\\Lib\\JSalmon' => __DIR__ . '/../..' . '/Zotlabs/Lib/JSalmon.php',
+ 'Zotlabs\\Lib\\LDSignatures' => __DIR__ . '/../..' . '/Zotlabs/Lib/LDSignatures.php',
+ 'Zotlabs\\Lib\\MarkdownSoap' => __DIR__ . '/../..' . '/Zotlabs/Lib/MarkdownSoap.php',
+ 'Zotlabs\\Lib\\NativeWiki' => __DIR__ . '/../..' . '/Zotlabs/Lib/NativeWiki.php',
+ 'Zotlabs\\Lib\\NativeWikiPage' => __DIR__ . '/../..' . '/Zotlabs/Lib/NativeWikiPage.php',
'Zotlabs\\Lib\\PConfig' => __DIR__ . '/../..' . '/Zotlabs/Lib/PConfig.php',
+ 'Zotlabs\\Lib\\Permcat' => __DIR__ . '/../..' . '/Zotlabs/Lib/Permcat.php',
'Zotlabs\\Lib\\PermissionDescription' => __DIR__ . '/../..' . '/Zotlabs/Lib/PermissionDescription.php',
'Zotlabs\\Lib\\ProtoDriver' => __DIR__ . '/../..' . '/Zotlabs/Lib/ProtoDriver.php',
+ 'Zotlabs\\Lib\\SConfig' => __DIR__ . '/../..' . '/Zotlabs/Lib/SConfig.php',
'Zotlabs\\Lib\\SuperCurl' => __DIR__ . '/../..' . '/Zotlabs/Lib/SuperCurl.php',
'Zotlabs\\Lib\\System' => __DIR__ . '/../..' . '/Zotlabs/Lib/System.php',
'Zotlabs\\Lib\\Techlevels' => __DIR__ . '/../..' . '/Zotlabs/Lib/Techlevels.php',
@@ -507,14 +922,20 @@ class ComposerStaticInit7b34d7e50a62201ec5d5e526a5b8b35d
'Zotlabs\\Module\\Admin\\Themes' => __DIR__ . '/../..' . '/Zotlabs/Module/Admin/Themes.php',
'Zotlabs\\Module\\Api' => __DIR__ . '/../..' . '/Zotlabs/Module/Api.php',
'Zotlabs\\Module\\Appman' => __DIR__ . '/../..' . '/Zotlabs/Module/Appman.php',
+ 'Zotlabs\\Module\\Apporder' => __DIR__ . '/../..' . '/Zotlabs/Module/Apporder.php',
'Zotlabs\\Module\\Apps' => __DIR__ . '/../..' . '/Zotlabs/Module/Apps.php',
'Zotlabs\\Module\\Attach' => __DIR__ . '/../..' . '/Zotlabs/Module/Attach.php',
+ 'Zotlabs\\Module\\Authorize' => __DIR__ . '/../..' . '/Zotlabs/Module/Authorize.php',
'Zotlabs\\Module\\Authtest' => __DIR__ . '/../..' . '/Zotlabs/Module/Authtest.php',
'Zotlabs\\Module\\Block' => __DIR__ . '/../..' . '/Zotlabs/Module/Block.php',
'Zotlabs\\Module\\Blocks' => __DIR__ . '/../..' . '/Zotlabs/Module/Blocks.php',
'Zotlabs\\Module\\Bookmarks' => __DIR__ . '/../..' . '/Zotlabs/Module/Bookmarks.php',
'Zotlabs\\Module\\Branchtopic' => __DIR__ . '/../..' . '/Zotlabs/Module/Branchtopic.php',
'Zotlabs\\Module\\Cal' => __DIR__ . '/../..' . '/Zotlabs/Module/Cal.php',
+ 'Zotlabs\\Module\\Card_edit' => __DIR__ . '/../..' . '/Zotlabs/Module/Card_edit.php',
+ 'Zotlabs\\Module\\Cards' => __DIR__ . '/../..' . '/Zotlabs/Module/Cards.php',
+ 'Zotlabs\\Module\\Cdav' => __DIR__ . '/../..' . '/Zotlabs/Module/Cdav.php',
+ 'Zotlabs\\Module\\Changeaddr' => __DIR__ . '/../..' . '/Zotlabs/Module/Changeaddr.php',
'Zotlabs\\Module\\Channel' => __DIR__ . '/../..' . '/Zotlabs/Module/Channel.php',
'Zotlabs\\Module\\Chanview' => __DIR__ . '/../..' . '/Zotlabs/Module/Chanview.php',
'Zotlabs\\Module\\Chat' => __DIR__ . '/../..' . '/Zotlabs/Module/Chat.php',
@@ -539,7 +960,6 @@ class ComposerStaticInit7b34d7e50a62201ec5d5e526a5b8b35d
'Zotlabs\\Module\\Events' => __DIR__ . '/../..' . '/Zotlabs/Module/Events.php',
'Zotlabs\\Module\\Fbrowser' => __DIR__ . '/../..' . '/Zotlabs/Module/Fbrowser.php',
'Zotlabs\\Module\\Feed' => __DIR__ . '/../..' . '/Zotlabs/Module/Feed.php',
- 'Zotlabs\\Module\\Ffsapi' => __DIR__ . '/../..' . '/Zotlabs/Module/Ffsapi.php',
'Zotlabs\\Module\\Fhublocs' => __DIR__ . '/../..' . '/Zotlabs/Module/Fhublocs.php',
'Zotlabs\\Module\\File_upload' => __DIR__ . '/../..' . '/Zotlabs/Module/File_upload.php',
'Zotlabs\\Module\\Filer' => __DIR__ . '/../..' . '/Zotlabs/Module/Filer.php',
@@ -564,14 +984,15 @@ class ComposerStaticInit7b34d7e50a62201ec5d5e526a5b8b35d
'Zotlabs\\Module\\Lockview' => __DIR__ . '/../..' . '/Zotlabs/Module/Lockview.php',
'Zotlabs\\Module\\Locs' => __DIR__ . '/../..' . '/Zotlabs/Module/Locs.php',
'Zotlabs\\Module\\Login' => __DIR__ . '/../..' . '/Zotlabs/Module/Login.php',
+ 'Zotlabs\\Module\\Logout' => __DIR__ . '/../..' . '/Zotlabs/Module/Logout.php',
'Zotlabs\\Module\\Lostpass' => __DIR__ . '/../..' . '/Zotlabs/Module/Lostpass.php',
'Zotlabs\\Module\\Magic' => __DIR__ . '/../..' . '/Zotlabs/Module/Magic.php',
'Zotlabs\\Module\\Mail' => __DIR__ . '/../..' . '/Zotlabs/Module/Mail.php',
'Zotlabs\\Module\\Manage' => __DIR__ . '/../..' . '/Zotlabs/Module/Manage.php',
- 'Zotlabs\\Module\\Match' => __DIR__ . '/../..' . '/Zotlabs/Module/Match.php',
'Zotlabs\\Module\\Menu' => __DIR__ . '/../..' . '/Zotlabs/Module/Menu.php',
'Zotlabs\\Module\\Message' => __DIR__ . '/../..' . '/Zotlabs/Module/Message.php',
'Zotlabs\\Module\\Mitem' => __DIR__ . '/../..' . '/Zotlabs/Module/Mitem.php',
+ 'Zotlabs\\Module\\Moderate' => __DIR__ . '/../..' . '/Zotlabs/Module/Moderate.php',
'Zotlabs\\Module\\Mood' => __DIR__ . '/../..' . '/Zotlabs/Module/Mood.php',
'Zotlabs\\Module\\Network' => __DIR__ . '/../..' . '/Zotlabs/Module/Network.php',
'Zotlabs\\Module\\New_channel' => __DIR__ . '/../..' . '/Zotlabs/Module/New_channel.php',
@@ -582,11 +1003,13 @@ class ComposerStaticInit7b34d7e50a62201ec5d5e526a5b8b35d
'Zotlabs\\Module\\Oembed' => __DIR__ . '/../..' . '/Zotlabs/Module/Oembed.php',
'Zotlabs\\Module\\Oep' => __DIR__ . '/../..' . '/Zotlabs/Module/Oep.php',
'Zotlabs\\Module\\Oexchange' => __DIR__ . '/../..' . '/Zotlabs/Module/Oexchange.php',
+ 'Zotlabs\\Module\\Ofeed' => __DIR__ . '/../..' . '/Zotlabs/Module/Ofeed.php',
'Zotlabs\\Module\\Online' => __DIR__ . '/../..' . '/Zotlabs/Module/Online.php',
- 'Zotlabs\\Module\\Opensearch' => __DIR__ . '/../..' . '/Zotlabs/Module/Opensearch.php',
+ 'Zotlabs\\Module\\Owa' => __DIR__ . '/../..' . '/Zotlabs/Module/Owa.php',
'Zotlabs\\Module\\Page' => __DIR__ . '/../..' . '/Zotlabs/Module/Page.php',
'Zotlabs\\Module\\Pconfig' => __DIR__ . '/../..' . '/Zotlabs/Module/Pconfig.php',
'Zotlabs\\Module\\Pdledit' => __DIR__ . '/../..' . '/Zotlabs/Module/Pdledit.php',
+ 'Zotlabs\\Module\\Permcat' => __DIR__ . '/../..' . '/Zotlabs/Module/Permcat.php',
'Zotlabs\\Module\\Photo' => __DIR__ . '/../..' . '/Zotlabs/Module/Photo.php',
'Zotlabs\\Module\\Photos' => __DIR__ . '/../..' . '/Zotlabs/Module/Photos.php',
'Zotlabs\\Module\\Ping' => __DIR__ . '/../..' . '/Zotlabs/Module/Ping.php',
@@ -616,7 +1039,6 @@ class ComposerStaticInit7b34d7e50a62201ec5d5e526a5b8b35d
'Zotlabs\\Module\\Removeme' => __DIR__ . '/../..' . '/Zotlabs/Module/Removeme.php',
'Zotlabs\\Module\\Rmagic' => __DIR__ . '/../..' . '/Zotlabs/Module/Rmagic.php',
'Zotlabs\\Module\\Rpost' => __DIR__ . '/../..' . '/Zotlabs/Module/Rpost.php',
- 'Zotlabs\\Module\\Rsd_xml' => __DIR__ . '/../..' . '/Zotlabs/Module/Rsd_xml.php',
'Zotlabs\\Module\\Search' => __DIR__ . '/../..' . '/Zotlabs/Module/Search.php',
'Zotlabs\\Module\\Search_ac' => __DIR__ . '/../..' . '/Zotlabs/Module/Search_ac.php',
'Zotlabs\\Module\\Service_limits' => __DIR__ . '/../..' . '/Zotlabs/Module/Service_limits.php',
@@ -627,12 +1049,12 @@ class ComposerStaticInit7b34d7e50a62201ec5d5e526a5b8b35d
'Zotlabs\\Module\\Settings\\Featured' => __DIR__ . '/../..' . '/Zotlabs/Module/Settings/Featured.php',
'Zotlabs\\Module\\Settings\\Features' => __DIR__ . '/../..' . '/Zotlabs/Module/Settings/Features.php',
'Zotlabs\\Module\\Settings\\Oauth' => __DIR__ . '/../..' . '/Zotlabs/Module/Settings/Oauth.php',
+ 'Zotlabs\\Module\\Settings\\Permcats' => __DIR__ . '/../..' . '/Zotlabs/Module/Settings/Permcats.php',
'Zotlabs\\Module\\Settings\\Tokens' => __DIR__ . '/../..' . '/Zotlabs/Module/Settings/Tokens.php',
'Zotlabs\\Module\\Setup' => __DIR__ . '/../..' . '/Zotlabs/Module/Setup.php',
'Zotlabs\\Module\\Share' => __DIR__ . '/../..' . '/Zotlabs/Module/Share.php',
'Zotlabs\\Module\\Sharedwithme' => __DIR__ . '/../..' . '/Zotlabs/Module/Sharedwithme.php',
'Zotlabs\\Module\\Siteinfo' => __DIR__ . '/../..' . '/Zotlabs/Module/Siteinfo.php',
- 'Zotlabs\\Module\\Siteinfo_json' => __DIR__ . '/../..' . '/Zotlabs/Module/Siteinfo_json.php',
'Zotlabs\\Module\\Sitelist' => __DIR__ . '/../..' . '/Zotlabs/Module/Sitelist.php',
'Zotlabs\\Module\\Smilies' => __DIR__ . '/../..' . '/Zotlabs/Module/Smilies.php',
'Zotlabs\\Module\\Snap' => __DIR__ . '/../..' . '/Zotlabs/Module/Snap.php',
@@ -648,7 +1070,9 @@ class ComposerStaticInit7b34d7e50a62201ec5d5e526a5b8b35d
'Zotlabs\\Module\\Thing' => __DIR__ . '/../..' . '/Zotlabs/Module/Thing.php',
'Zotlabs\\Module\\Toggle_mobile' => __DIR__ . '/../..' . '/Zotlabs/Module/Toggle_mobile.php',
'Zotlabs\\Module\\Toggle_safesearch' => __DIR__ . '/../..' . '/Zotlabs/Module/Toggle_safesearch.php',
+ 'Zotlabs\\Module\\Token' => __DIR__ . '/../..' . '/Zotlabs/Module/Token.php',
'Zotlabs\\Module\\Uexport' => __DIR__ . '/../..' . '/Zotlabs/Module/Uexport.php',
+ 'Zotlabs\\Module\\Update_cards' => __DIR__ . '/../..' . '/Zotlabs/Module/Update_cards.php',
'Zotlabs\\Module\\Update_channel' => __DIR__ . '/../..' . '/Zotlabs/Module/Update_channel.php',
'Zotlabs\\Module\\Update_display' => __DIR__ . '/../..' . '/Zotlabs/Module/Update_display.php',
'Zotlabs\\Module\\Update_home' => __DIR__ . '/../..' . '/Zotlabs/Module/Update_home.php',
@@ -687,12 +1111,70 @@ class ComposerStaticInit7b34d7e50a62201ec5d5e526a5b8b35d
'Zotlabs\\Text\\Tagadelic' => __DIR__ . '/../..' . '/Zotlabs/Text/Tagadelic.php',
'Zotlabs\\Web\\CheckJS' => __DIR__ . '/../..' . '/Zotlabs/Web/CheckJS.php',
'Zotlabs\\Web\\Controller' => __DIR__ . '/../..' . '/Zotlabs/Web/Controller.php',
+ 'Zotlabs\\Web\\HTTPHeaders' => __DIR__ . '/../..' . '/Zotlabs/Web/HTTPHeaders.php',
+ 'Zotlabs\\Web\\HTTPSig' => __DIR__ . '/../..' . '/Zotlabs/Web/HTTPSig.php',
'Zotlabs\\Web\\HttpMeta' => __DIR__ . '/../..' . '/Zotlabs/Web/HttpMeta.php',
'Zotlabs\\Web\\Router' => __DIR__ . '/../..' . '/Zotlabs/Web/Router.php',
'Zotlabs\\Web\\Session' => __DIR__ . '/../..' . '/Zotlabs/Web/Session.php',
'Zotlabs\\Web\\SessionHandler' => __DIR__ . '/../..' . '/Zotlabs/Web/SessionHandler.php',
'Zotlabs\\Web\\SubModule' => __DIR__ . '/../..' . '/Zotlabs/Web/SubModule.php',
'Zotlabs\\Web\\WebServer' => __DIR__ . '/../..' . '/Zotlabs/Web/WebServer.php',
+ 'Zotlabs\\Widget\\Activity' => __DIR__ . '/../..' . '/Zotlabs/Widget/Activity.php',
+ 'Zotlabs\\Widget\\Admin' => __DIR__ . '/../..' . '/Zotlabs/Widget/Admin.php',
+ 'Zotlabs\\Widget\\Affinity' => __DIR__ . '/../..' . '/Zotlabs/Widget/Affinity.php',
+ 'Zotlabs\\Widget\\Album' => __DIR__ . '/../..' . '/Zotlabs/Widget/Album.php',
+ 'Zotlabs\\Widget\\Appcategories' => __DIR__ . '/../..' . '/Zotlabs/Widget/Appcategories.php',
+ 'Zotlabs\\Widget\\Appcloud' => __DIR__ . '/../..' . '/Zotlabs/Widget/Appcloud.php',
+ 'Zotlabs\\Widget\\Archive' => __DIR__ . '/../..' . '/Zotlabs/Widget/Archive.php',
+ 'Zotlabs\\Widget\\Bookmarkedchats' => __DIR__ . '/../..' . '/Zotlabs/Widget/Bookmarkedchats.php',
+ 'Zotlabs\\Widget\\Catcloud_wall' => __DIR__ . '/../..' . '/Zotlabs/Widget/Catcloud_wall.php',
+ 'Zotlabs\\Widget\\Categories' => __DIR__ . '/../..' . '/Zotlabs/Widget/Categories.php',
+ 'Zotlabs\\Widget\\Cdav' => __DIR__ . '/../..' . '/Zotlabs/Widget/Cdav.php',
+ 'Zotlabs\\Widget\\Chatroom_list' => __DIR__ . '/../..' . '/Zotlabs/Widget/Chatroom_list.php',
+ 'Zotlabs\\Widget\\Chatroom_members' => __DIR__ . '/../..' . '/Zotlabs/Widget/Chatroom_members.php',
+ 'Zotlabs\\Widget\\Clock' => __DIR__ . '/../..' . '/Zotlabs/Widget/Clock.php',
+ 'Zotlabs\\Widget\\Collections' => __DIR__ . '/../..' . '/Zotlabs/Widget/Collections.php',
+ 'Zotlabs\\Widget\\Common_friends' => __DIR__ . '/../..' . '/Zotlabs/Widget/Common_friends.php',
+ 'Zotlabs\\Widget\\Conversations' => __DIR__ . '/../..' . '/Zotlabs/Widget/Conversations.php',
+ 'Zotlabs\\Widget\\Cover_photo' => __DIR__ . '/../..' . '/Zotlabs/Widget/Cover_photo.php',
+ 'Zotlabs\\Widget\\Design_tools' => __DIR__ . '/../..' . '/Zotlabs/Widget/Design_tools.php',
+ 'Zotlabs\\Widget\\Dirsort' => __DIR__ . '/../..' . '/Zotlabs/Widget/Dirsort.php',
+ 'Zotlabs\\Widget\\Dirtags' => __DIR__ . '/../..' . '/Zotlabs/Widget/Dirtags.php',
+ 'Zotlabs\\Widget\\Eventstools' => __DIR__ . '/../..' . '/Zotlabs/Widget/Eventstools.php',
+ 'Zotlabs\\Widget\\Filer' => __DIR__ . '/../..' . '/Zotlabs/Widget/Filer.php',
+ 'Zotlabs\\Widget\\Findpeople' => __DIR__ . '/../..' . '/Zotlabs/Widget/Findpeople.php',
+ 'Zotlabs\\Widget\\Follow' => __DIR__ . '/../..' . '/Zotlabs/Widget/Follow.php',
+ 'Zotlabs\\Widget\\Forums' => __DIR__ . '/../..' . '/Zotlabs/Widget/Forums.php',
+ 'Zotlabs\\Widget\\Fullprofile' => __DIR__ . '/../..' . '/Zotlabs/Widget/Fullprofile.php',
+ 'Zotlabs\\Widget\\Helpindex' => __DIR__ . '/../..' . '/Zotlabs/Widget/Helpindex.php',
+ 'Zotlabs\\Widget\\Item' => __DIR__ . '/../..' . '/Zotlabs/Widget/Item.php',
+ 'Zotlabs\\Widget\\Mailmenu' => __DIR__ . '/../..' . '/Zotlabs/Widget/Mailmenu.php',
+ 'Zotlabs\\Widget\\Menu_preview' => __DIR__ . '/../..' . '/Zotlabs/Widget/Menu_preview.php',
+ 'Zotlabs\\Widget\\Notes' => __DIR__ . '/../..' . '/Zotlabs/Widget/Notes.php',
+ 'Zotlabs\\Widget\\Notifications' => __DIR__ . '/../..' . '/Zotlabs/Widget/Notifications.php',
+ 'Zotlabs\\Widget\\Photo' => __DIR__ . '/../..' . '/Zotlabs/Widget/Photo.php',
+ 'Zotlabs\\Widget\\Photo_albums' => __DIR__ . '/../..' . '/Zotlabs/Widget/Photo_albums.php',
+ 'Zotlabs\\Widget\\Photo_rand' => __DIR__ . '/../..' . '/Zotlabs/Widget/Photo_rand.php',
+ 'Zotlabs\\Widget\\Portfolio' => __DIR__ . '/../..' . '/Zotlabs/Widget/Portfolio.php',
+ 'Zotlabs\\Widget\\Profile' => __DIR__ . '/../..' . '/Zotlabs/Widget/Profile.php',
+ 'Zotlabs\\Widget\\Pubsites' => __DIR__ . '/../..' . '/Zotlabs/Widget/Pubsites.php',
+ 'Zotlabs\\Widget\\Random_block' => __DIR__ . '/../..' . '/Zotlabs/Widget/Random_block.php',
+ 'Zotlabs\\Widget\\Rating' => __DIR__ . '/../..' . '/Zotlabs/Widget/Rating.php',
+ 'Zotlabs\\Widget\\Savedsearch' => __DIR__ . '/../..' . '/Zotlabs/Widget/Savedsearch.php',
+ 'Zotlabs\\Widget\\Settings_menu' => __DIR__ . '/../..' . '/Zotlabs/Widget/Settings_menu.php',
+ 'Zotlabs\\Widget\\Shortprofile' => __DIR__ . '/../..' . '/Zotlabs/Widget/Shortprofile.php',
+ 'Zotlabs\\Widget\\Sitesearch' => __DIR__ . '/../..' . '/Zotlabs/Widget/Sitesearch.php',
+ 'Zotlabs\\Widget\\Suggestedchats' => __DIR__ . '/../..' . '/Zotlabs/Widget/Suggestedchats.php',
+ 'Zotlabs\\Widget\\Suggestions' => __DIR__ . '/../..' . '/Zotlabs/Widget/Suggestions.php',
+ 'Zotlabs\\Widget\\Tagcloud' => __DIR__ . '/../..' . '/Zotlabs/Widget/Tagcloud.php',
+ 'Zotlabs\\Widget\\Tagcloud_wall' => __DIR__ . '/../..' . '/Zotlabs/Widget/Tagcloud_wall.php',
+ 'Zotlabs\\Widget\\Tasklist' => __DIR__ . '/../..' . '/Zotlabs/Widget/Tasklist.php',
+ 'Zotlabs\\Widget\\Vcard' => __DIR__ . '/../..' . '/Zotlabs/Widget/Vcard.php',
+ 'Zotlabs\\Widget\\Website_portation_tools' => __DIR__ . '/../..' . '/Zotlabs/Widget/Website_portation_tools.php',
+ 'Zotlabs\\Widget\\Wiki_list' => __DIR__ . '/../..' . '/Zotlabs/Widget/Wiki_list.php',
+ 'Zotlabs\\Widget\\Wiki_page_history' => __DIR__ . '/../..' . '/Zotlabs/Widget/Wiki_page_history.php',
+ 'Zotlabs\\Widget\\Wiki_pages' => __DIR__ . '/../..' . '/Zotlabs/Widget/Wiki_pages.php',
+ 'Zotlabs\\Widget\\Zcard' => __DIR__ . '/../..' . '/Zotlabs/Widget/Zcard.php',
'Zotlabs\\Zot\\Auth' => __DIR__ . '/../..' . '/Zotlabs/Zot/Auth.php',
'Zotlabs\\Zot\\DReport' => __DIR__ . '/../..' . '/Zotlabs/Zot/DReport.php',
'Zotlabs\\Zot\\Finger' => __DIR__ . '/../..' . '/Zotlabs/Zot/Finger.php',
@@ -707,6 +1189,7 @@ class ComposerStaticInit7b34d7e50a62201ec5d5e526a5b8b35d
return \Closure::bind(function () use ($loader) {
$loader->prefixLengthsPsr4 = ComposerStaticInit7b34d7e50a62201ec5d5e526a5b8b35d::$prefixLengthsPsr4;
$loader->prefixDirsPsr4 = ComposerStaticInit7b34d7e50a62201ec5d5e526a5b8b35d::$prefixDirsPsr4;
+ $loader->prefixesPsr0 = ComposerStaticInit7b34d7e50a62201ec5d5e526a5b8b35d::$prefixesPsr0;
$loader->classMap = ComposerStaticInit7b34d7e50a62201ec5d5e526a5b8b35d::$classMap;
}, null, ClassLoader::class);
diff --git a/vendor/composer/installed.json b/vendor/composer/installed.json
index 88acfc40c..4fa452db0 100644
--- a/vendor/composer/installed.json
+++ b/vendor/composer/installed.json
@@ -1,36 +1,38 @@
[
{
- "name": "sabre/uri",
- "version": "1.1.0",
- "version_normalized": "1.1.0.0",
+ "name": "sabre/event",
+ "version": "3.0.0",
+ "version_normalized": "3.0.0.0",
"source": {
"type": "git",
- "url": "https://github.com/fruux/sabre-uri.git",
- "reference": "9012116434d84ef6e5e37a89dfdbfbe2204a8704"
+ "url": "https://github.com/fruux/sabre-event.git",
+ "reference": "831d586f5a442dceacdcf5e9c4c36a4db99a3534"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/fruux/sabre-uri/zipball/9012116434d84ef6e5e37a89dfdbfbe2204a8704",
- "reference": "9012116434d84ef6e5e37a89dfdbfbe2204a8704",
+ "url": "https://api.github.com/repos/fruux/sabre-event/zipball/831d586f5a442dceacdcf5e9c4c36a4db99a3534",
+ "reference": "831d586f5a442dceacdcf5e9c4c36a4db99a3534",
"shasum": ""
},
"require": {
- "php": ">=5.4.7"
+ "php": ">=5.5"
},
"require-dev": {
"phpunit/phpunit": "*",
- "sabre/cs": "~0.0.1"
+ "sabre/cs": "~0.0.4"
},
- "time": "2016-03-08 02:29:27",
+ "time": "2015-11-05T20:14:39+00:00",
"type": "library",
"installation-source": "dist",
"autoload": {
- "files": [
- "lib/functions.php"
- ],
"psr-4": {
- "Sabre\\Uri\\": "lib/"
- }
+ "Sabre\\Event\\": "lib/"
+ },
+ "files": [
+ "lib/coroutine.php",
+ "lib/Loop/functions.php",
+ "lib/Promise/functions.php"
+ ]
},
"notification-url": "https://packagist.org/downloads/",
"license": [
@@ -44,57 +46,56 @@
"role": "Developer"
}
],
- "description": "Functions for making sense out of URIs.",
- "homepage": "http://sabre.io/uri/",
+ "description": "sabre/event is a library for lightweight event-based programming",
+ "homepage": "http://sabre.io/event/",
"keywords": [
- "rfc3986",
- "uri",
- "url"
+ "EventEmitter",
+ "async",
+ "events",
+ "hooks",
+ "plugin",
+ "promise",
+ "signal"
]
},
{
- "name": "sabre/vobject",
- "version": "4.1.1",
- "version_normalized": "4.1.1.0",
+ "name": "sabre/xml",
+ "version": "1.5.0",
+ "version_normalized": "1.5.0.0",
"source": {
"type": "git",
- "url": "https://github.com/fruux/sabre-vobject.git",
- "reference": "a3a59b06947f122af2d45d52b72172cdc1efd68f"
+ "url": "https://github.com/fruux/sabre-xml.git",
+ "reference": "59b20e5bbace9912607481634f97d05a776ffca7"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/fruux/sabre-vobject/zipball/a3a59b06947f122af2d45d52b72172cdc1efd68f",
- "reference": "a3a59b06947f122af2d45d52b72172cdc1efd68f",
+ "url": "https://api.github.com/repos/fruux/sabre-xml/zipball/59b20e5bbace9912607481634f97d05a776ffca7",
+ "reference": "59b20e5bbace9912607481634f97d05a776ffca7",
"shasum": ""
},
"require": {
- "ext-mbstring": "*",
- "php": ">=5.5",
- "sabre/xml": "~1.1"
+ "ext-dom": "*",
+ "ext-xmlreader": "*",
+ "ext-xmlwriter": "*",
+ "lib-libxml": ">=2.6.20",
+ "php": ">=5.5.5",
+ "sabre/uri": ">=1.0,<3.0.0"
},
"require-dev": {
"phpunit/phpunit": "*",
- "sabre/cs": "~0.0.3"
- },
- "suggest": {
- "hoa/bench": "If you would like to run the benchmark scripts"
+ "sabre/cs": "~1.0.0"
},
- "time": "2016-07-15 19:52:17",
- "bin": [
- "bin/vobject",
- "bin/generate_vcards"
- ],
+ "time": "2016-10-09T22:57:52+00:00",
"type": "library",
- "extra": {
- "branch-alias": {
- "dev-master": "4.0.x-dev"
- }
- },
"installation-source": "dist",
"autoload": {
"psr-4": {
- "Sabre\\VObject\\": "lib/"
- }
+ "Sabre\\Xml\\": "lib/"
+ },
+ "files": [
+ "lib/Deserializer/functions.php",
+ "lib/Serializer/functions.php"
+ ]
},
"notification-url": "https://packagist.org/downloads/",
"license": [
@@ -108,83 +109,99 @@
"role": "Developer"
},
{
- "name": "Dominik Tobschall",
- "email": "dominik@fruux.com",
- "homepage": "http://tobschall.de/",
- "role": "Developer"
- },
- {
- "name": "Ivan Enderlin",
- "email": "ivan.enderlin@hoa-project.net",
- "homepage": "http://mnt.io/",
+ "name": "Markus Staab",
+ "email": "markus.staab@redaxo.de",
"role": "Developer"
}
],
- "description": "The VObject library for PHP allows you to easily parse and manipulate iCalendar and vCard objects",
- "homepage": "http://sabre.io/vobject/",
+ "description": "sabre/xml is an XML library that you may not hate.",
+ "homepage": "https://sabre.io/xml/",
"keywords": [
- "availability",
- "freebusy",
- "iCalendar",
- "ical",
- "ics",
- "jCal",
- "jCard",
- "recurrence",
- "rfc2425",
- "rfc2426",
- "rfc2739",
- "rfc4770",
- "rfc5545",
- "rfc5546",
- "rfc6321",
- "rfc6350",
- "rfc6351",
- "rfc6474",
- "rfc6638",
- "rfc6715",
- "rfc6868",
- "vCalendar",
- "vCard",
- "vcf",
- "xCal",
- "xCard"
+ "XMLReader",
+ "XMLWriter",
+ "dom",
+ "xml"
]
},
{
- "name": "sabre/event",
- "version": "3.0.0",
- "version_normalized": "3.0.0.0",
+ "name": "psr/log",
+ "version": "1.0.2",
+ "version_normalized": "1.0.2.0",
"source": {
"type": "git",
- "url": "https://github.com/fruux/sabre-event.git",
- "reference": "831d586f5a442dceacdcf5e9c4c36a4db99a3534"
+ "url": "https://github.com/php-fig/log.git",
+ "reference": "4ebe3a8bf773a19edfe0a84b6585ba3d401b724d"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/fruux/sabre-event/zipball/831d586f5a442dceacdcf5e9c4c36a4db99a3534",
- "reference": "831d586f5a442dceacdcf5e9c4c36a4db99a3534",
+ "url": "https://api.github.com/repos/php-fig/log/zipball/4ebe3a8bf773a19edfe0a84b6585ba3d401b724d",
+ "reference": "4ebe3a8bf773a19edfe0a84b6585ba3d401b724d",
"shasum": ""
},
"require": {
- "php": ">=5.5"
- },
- "require-dev": {
- "phpunit/phpunit": "*",
- "sabre/cs": "~0.0.4"
+ "php": ">=5.3.0"
},
- "time": "2015-11-05 20:14:39",
+ "time": "2016-10-10T12:19:37+00:00",
"type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.0.x-dev"
+ }
+ },
"installation-source": "dist",
"autoload": {
"psr-4": {
- "Sabre\\Event\\": "lib/"
- },
- "files": [
- "lib/coroutine.php",
- "lib/Loop/functions.php",
- "lib/Promise/functions.php"
- ]
+ "Psr\\Log\\": "Psr/Log/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "PHP-FIG",
+ "homepage": "http://www.php-fig.org/"
+ }
+ ],
+ "description": "Common interface for logging libraries",
+ "homepage": "https://github.com/php-fig/log",
+ "keywords": [
+ "log",
+ "psr",
+ "psr-3"
+ ]
+ },
+ {
+ "name": "michelf/php-markdown",
+ "version": "1.7.0",
+ "version_normalized": "1.7.0.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/michelf/php-markdown.git",
+ "reference": "1f51cc520948f66cd2af8cbc45a5ee175e774220"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/michelf/php-markdown/zipball/1f51cc520948f66cd2af8cbc45a5ee175e774220",
+ "reference": "1f51cc520948f66cd2af8cbc45a5ee175e774220",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.3.0"
+ },
+ "time": "2016-10-29T18:58:20+00:00",
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-lib": "1.4.x-dev"
+ }
+ },
+ "installation-source": "dist",
+ "autoload": {
+ "psr-0": {
+ "Michelf": ""
+ }
},
"notification-url": "https://packagist.org/downloads/",
"license": [
@@ -192,94 +209,158 @@
],
"authors": [
{
- "name": "Evert Pot",
- "email": "me@evertpot.com",
- "homepage": "http://evertpot.com/",
+ "name": "Michel Fortin",
+ "email": "michel.fortin@michelf.ca",
+ "homepage": "https://michelf.ca/",
"role": "Developer"
+ },
+ {
+ "name": "John Gruber",
+ "homepage": "https://daringfireball.net/"
}
],
- "description": "sabre/event is a library for lightweight event-based programming",
- "homepage": "http://sabre.io/event/",
+ "description": "PHP Markdown",
+ "homepage": "https://michelf.ca/projects/php-markdown/",
"keywords": [
- "EventEmitter",
- "async",
- "events",
- "hooks",
- "plugin",
- "promise",
- "signal"
+ "markdown"
]
},
{
- "name": "sabre/http",
- "version": "4.2.1",
- "version_normalized": "4.2.1.0",
+ "name": "bshaffer/oauth2-server-php",
+ "version": "v1.9.0",
+ "version_normalized": "1.9.0.0",
"source": {
"type": "git",
- "url": "https://github.com/fruux/sabre-http.git",
- "reference": "2e93bc8321524c67be4ca5b8415daebd4c8bf85e"
+ "url": "https://github.com/bshaffer/oauth2-server-php.git",
+ "reference": "8856aed1a98d6da596ae3f9b8095b5c7a1581697"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/fruux/sabre-http/zipball/2e93bc8321524c67be4ca5b8415daebd4c8bf85e",
- "reference": "2e93bc8321524c67be4ca5b8415daebd4c8bf85e",
+ "url": "https://api.github.com/repos/bshaffer/oauth2-server-php/zipball/8856aed1a98d6da596ae3f9b8095b5c7a1581697",
+ "reference": "8856aed1a98d6da596ae3f9b8095b5c7a1581697",
"shasum": ""
},
"require": {
- "ext-mbstring": "*",
- "php": ">=5.4",
- "sabre/event": ">=1.0.0,<4.0.0",
- "sabre/uri": "~1.0"
+ "php": ">=5.3.9"
},
"require-dev": {
- "phpunit/phpunit": "~4.3",
- "sabre/cs": "~0.0.1"
+ "aws/aws-sdk-php": "~2.8",
+ "firebase/php-jwt": "~2.2",
+ "mongodb/mongodb": "^1.1",
+ "predis/predis": "dev-master",
+ "thobbs/phpcassa": "dev-master"
},
"suggest": {
- "ext-curl": " to make http requests with the Client class"
+ "aws/aws-sdk-php": "~2.8 is required to use DynamoDB storage",
+ "firebase/php-jwt": "~1.1 is required to use MondoDB storage",
+ "predis/predis": "Required to use Redis storage",
+ "thobbs/phpcassa": "Required to use Cassandra storage"
},
- "time": "2016-01-06 23:00:08",
+ "time": "2017-01-06T23:20:00+00:00",
"type": "library",
"installation-source": "dist",
"autoload": {
- "files": [
- "lib/functions.php"
- ],
- "psr-4": {
- "Sabre\\HTTP\\": "lib/"
+ "psr-0": {
+ "OAuth2": "src/"
}
},
"notification-url": "https://packagist.org/downloads/",
"license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Brent Shaffer",
+ "email": "bshafs@gmail.com",
+ "homepage": "http://brentertainment.com"
+ }
+ ],
+ "description": "OAuth2 Server for PHP",
+ "homepage": "http://github.com/bshaffer/oauth2-server-php",
+ "keywords": [
+ "auth",
+ "oauth",
+ "oauth2"
+ ]
+ },
+ {
+ "name": "simplepie/simplepie",
+ "version": "1.5",
+ "version_normalized": "1.5.0.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/simplepie/simplepie.git",
+ "reference": "5de5551953f95feef12cf355a7a26a70f94aa3ab"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/simplepie/simplepie/zipball/5de5551953f95feef12cf355a7a26a70f94aa3ab",
+ "reference": "5de5551953f95feef12cf355a7a26a70f94aa3ab",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.3.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "~4 || ~5"
+ },
+ "suggest": {
+ "mf2/mf2": "Microformat module that allows for parsing HTML for microformats"
+ },
+ "time": "2017-04-17T07:29:31+00:00",
+ "type": "library",
+ "installation-source": "source",
+ "autoload": {
+ "psr-0": {
+ "SimplePie": "library"
+ }
+ },
+ "license": [
"BSD-3-Clause"
],
"authors": [
{
- "name": "Evert Pot",
- "email": "me@evertpot.com",
- "homepage": "http://evertpot.com/",
+ "name": "Ryan Parman",
+ "homepage": "http://ryanparman.com/",
+ "role": "Creator, alumnus developer"
+ },
+ {
+ "name": "Geoffrey Sneddon",
+ "homepage": "http://gsnedders.com/",
+ "role": "Alumnus developer"
+ },
+ {
+ "name": "Ryan McCue",
+ "email": "me@ryanmccue.info",
+ "homepage": "http://ryanmccue.info/",
"role": "Developer"
}
],
- "description": "The sabre/http library provides utilities for dealing with http requests and responses. ",
- "homepage": "https://github.com/fruux/sabre-http",
+ "description": "A simple Atom/RSS parsing library for PHP",
+ "homepage": "http://simplepie.org/",
"keywords": [
- "http"
- ]
+ "atom",
+ "feeds",
+ "rss"
+ ],
+ "support": {
+ "source": "https://github.com/simplepie/simplepie/tree/1.5",
+ "issues": "https://github.com/simplepie/simplepie/issues"
+ }
},
{
"name": "sabre/dav",
- "version": "3.2.0",
- "version_normalized": "3.2.0.0",
+ "version": "3.2.2",
+ "version_normalized": "3.2.2.0",
"source": {
"type": "git",
"url": "https://github.com/fruux/sabre-dav.git",
- "reference": "5b9737cc2f0182e368d14c80df7f6b2d77dc1457"
+ "reference": "e987775e619728f12205606c9cc3ee565ffb1516"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/fruux/sabre-dav/zipball/5b9737cc2f0182e368d14c80df7f6b2d77dc1457",
- "reference": "5b9737cc2f0182e368d14c80df7f6b2d77dc1457",
+ "url": "https://api.github.com/repos/fruux/sabre-dav/zipball/e987775e619728f12205606c9cc3ee565ffb1516",
+ "reference": "e987775e619728f12205606c9cc3ee565ffb1516",
"shasum": ""
},
"require": {
@@ -303,14 +384,14 @@
"require-dev": {
"evert/phpdoc-md": "~0.1.0",
"monolog/monolog": "^1.18",
- "phpunit/phpunit": "> 4.8, <=6.0.0",
- "sabre/cs": "~0.0.5"
+ "phpunit/phpunit": "> 4.8, <6.0.0",
+ "sabre/cs": "^1.0.0"
},
"suggest": {
"ext-curl": "*",
"ext-pdo": "*"
},
- "time": "2016-06-28 02:44:05",
+ "time": "2017-02-15T03:06:08+00:00",
"bin": [
"bin/sabredav",
"bin/naturalselection"
@@ -353,43 +434,167 @@
]
},
{
- "name": "sabre/xml",
- "version": "1.5.0",
- "version_normalized": "1.5.0.0",
+ "name": "league/html-to-markdown",
+ "version": "4.4.1",
+ "version_normalized": "4.4.1.0",
"source": {
"type": "git",
- "url": "https://github.com/fruux/sabre-xml.git",
- "reference": "59b20e5bbace9912607481634f97d05a776ffca7"
+ "url": "https://github.com/thephpleague/html-to-markdown.git",
+ "reference": "82ea375b5b2b1da1da222644c0565c695bf88186"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/fruux/sabre-xml/zipball/59b20e5bbace9912607481634f97d05a776ffca7",
- "reference": "59b20e5bbace9912607481634f97d05a776ffca7",
+ "url": "https://api.github.com/repos/thephpleague/html-to-markdown/zipball/82ea375b5b2b1da1da222644c0565c695bf88186",
+ "reference": "82ea375b5b2b1da1da222644c0565c695bf88186",
"shasum": ""
},
"require": {
"ext-dom": "*",
- "ext-xmlreader": "*",
- "ext-xmlwriter": "*",
- "lib-libxml": ">=2.6.20",
- "php": ">=5.5.5",
- "sabre/uri": ">=1.0,<3.0.0"
+ "ext-xml": "*",
+ "php": ">=5.3.3"
},
"require-dev": {
- "phpunit/phpunit": "*",
- "sabre/cs": "~1.0.0"
+ "mikehaertl/php-shellcommand": "~1.1.0",
+ "phpunit/phpunit": "4.*",
+ "scrutinizer/ocular": "~1.1"
},
- "time": "2016-10-09 22:57:52",
+ "time": "2017-03-16T00:45:59+00:00",
+ "bin": [
+ "bin/html-to-markdown"
+ ],
"type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "4.5-dev"
+ }
+ },
"installation-source": "dist",
"autoload": {
"psr-4": {
- "Sabre\\Xml\\": "lib/"
+ "League\\HTMLToMarkdown\\": "src/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Colin O'Dell",
+ "email": "colinodell@gmail.com",
+ "homepage": "http://www.colinodell.com",
+ "role": "Lead Developer"
},
+ {
+ "name": "Nick Cernis",
+ "email": "nick@cern.is",
+ "homepage": "http://modernnerd.net",
+ "role": "Original Author"
+ }
+ ],
+ "description": "An HTML-to-markdown conversion helper for PHP",
+ "homepage": "https://github.com/thephpleague/html-to-markdown",
+ "keywords": [
+ "html",
+ "markdown"
+ ]
+ },
+ {
+ "name": "sabre/uri",
+ "version": "1.2.1",
+ "version_normalized": "1.2.1.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/fruux/sabre-uri.git",
+ "reference": "ada354d83579565949d80b2e15593c2371225e61"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/fruux/sabre-uri/zipball/ada354d83579565949d80b2e15593c2371225e61",
+ "reference": "ada354d83579565949d80b2e15593c2371225e61",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.4.7"
+ },
+ "require-dev": {
+ "phpunit/phpunit": ">=4.0,<6.0",
+ "sabre/cs": "~1.0.0"
+ },
+ "time": "2017-02-20T19:59:28+00:00",
+ "type": "library",
+ "installation-source": "dist",
+ "autoload": {
"files": [
- "lib/Deserializer/functions.php",
- "lib/Serializer/functions.php"
- ]
+ "lib/functions.php"
+ ],
+ "psr-4": {
+ "Sabre\\Uri\\": "lib/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Evert Pot",
+ "email": "me@evertpot.com",
+ "homepage": "http://evertpot.com/",
+ "role": "Developer"
+ }
+ ],
+ "description": "Functions for making sense out of URIs.",
+ "homepage": "http://sabre.io/uri/",
+ "keywords": [
+ "rfc3986",
+ "uri",
+ "url"
+ ]
+ },
+ {
+ "name": "sabre/vobject",
+ "version": "4.1.2",
+ "version_normalized": "4.1.2.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/fruux/sabre-vobject.git",
+ "reference": "d0fde2fafa2a3dad1f559c2d1c2591d4fd75ae3c"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/fruux/sabre-vobject/zipball/d0fde2fafa2a3dad1f559c2d1c2591d4fd75ae3c",
+ "reference": "d0fde2fafa2a3dad1f559c2d1c2591d4fd75ae3c",
+ "shasum": ""
+ },
+ "require": {
+ "ext-mbstring": "*",
+ "php": ">=5.5",
+ "sabre/xml": ">=1.5 <3.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "*",
+ "sabre/cs": "^1.0.0"
+ },
+ "suggest": {
+ "hoa/bench": "If you would like to run the benchmark scripts"
+ },
+ "time": "2016-12-06T04:14:09+00:00",
+ "bin": [
+ "bin/vobject",
+ "bin/generate_vcards"
+ ],
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "4.0.x-dev"
+ }
+ },
+ "installation-source": "dist",
+ "autoload": {
+ "psr-4": {
+ "Sabre\\VObject\\": "lib/"
+ }
},
"notification-url": "https://packagist.org/downloads/",
"license": [
@@ -403,67 +608,154 @@
"role": "Developer"
},
{
- "name": "Markus Staab",
- "email": "markus.staab@redaxo.de",
+ "name": "Dominik Tobschall",
+ "email": "dominik@fruux.com",
+ "homepage": "http://tobschall.de/",
+ "role": "Developer"
+ },
+ {
+ "name": "Ivan Enderlin",
+ "email": "ivan.enderlin@hoa-project.net",
+ "homepage": "http://mnt.io/",
"role": "Developer"
}
],
- "description": "sabre/xml is an XML library that you may not hate.",
- "homepage": "https://sabre.io/xml/",
+ "description": "The VObject library for PHP allows you to easily parse and manipulate iCalendar and vCard objects",
+ "homepage": "http://sabre.io/vobject/",
"keywords": [
- "XMLReader",
- "XMLWriter",
- "dom",
- "xml"
+ "availability",
+ "freebusy",
+ "iCalendar",
+ "ical",
+ "ics",
+ "jCal",
+ "jCard",
+ "recurrence",
+ "rfc2425",
+ "rfc2426",
+ "rfc2739",
+ "rfc4770",
+ "rfc5545",
+ "rfc5546",
+ "rfc6321",
+ "rfc6350",
+ "rfc6351",
+ "rfc6474",
+ "rfc6638",
+ "rfc6715",
+ "rfc6868",
+ "vCalendar",
+ "vCard",
+ "vcf",
+ "xCal",
+ "xCard"
]
},
{
- "name": "psr/log",
- "version": "1.0.2",
- "version_normalized": "1.0.2.0",
+ "name": "ezyang/htmlpurifier",
+ "version": "v4.9.3",
+ "version_normalized": "4.9.3.0",
"source": {
"type": "git",
- "url": "https://github.com/php-fig/log.git",
- "reference": "4ebe3a8bf773a19edfe0a84b6585ba3d401b724d"
+ "url": "https://github.com/ezyang/htmlpurifier.git",
+ "reference": "95e1bae3182efc0f3422896a3236e991049dac69"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/php-fig/log/zipball/4ebe3a8bf773a19edfe0a84b6585ba3d401b724d",
- "reference": "4ebe3a8bf773a19edfe0a84b6585ba3d401b724d",
+ "url": "https://api.github.com/repos/ezyang/htmlpurifier/zipball/95e1bae3182efc0f3422896a3236e991049dac69",
+ "reference": "95e1bae3182efc0f3422896a3236e991049dac69",
"shasum": ""
},
"require": {
- "php": ">=5.3.0"
+ "php": ">=5.2"
},
- "time": "2016-10-10 12:19:37",
+ "require-dev": {
+ "simpletest/simpletest": "^1.1"
+ },
+ "time": "2017-06-03T02:28:16+00:00",
"type": "library",
- "extra": {
- "branch-alias": {
- "dev-master": "1.0.x-dev"
+ "installation-source": "dist",
+ "autoload": {
+ "psr-0": {
+ "HTMLPurifier": "library/"
+ },
+ "files": [
+ "library/HTMLPurifier.composer.php"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "LGPL"
+ ],
+ "authors": [
+ {
+ "name": "Edward Z. Yang",
+ "email": "admin@htmlpurifier.org",
+ "homepage": "http://ezyang.com"
}
+ ],
+ "description": "Standards compliant HTML filter written in PHP",
+ "homepage": "http://htmlpurifier.org/",
+ "keywords": [
+ "html"
+ ]
+ },
+ {
+ "name": "sabre/http",
+ "version": "4.2.3",
+ "version_normalized": "4.2.3.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/fruux/sabre-http.git",
+ "reference": "0295f9a3ee39be97e0898592fc19e42421e0cd93"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/fruux/sabre-http/zipball/0295f9a3ee39be97e0898592fc19e42421e0cd93",
+ "reference": "0295f9a3ee39be97e0898592fc19e42421e0cd93",
+ "shasum": ""
+ },
+ "require": {
+ "ext-ctype": "*",
+ "ext-mbstring": "*",
+ "php": ">=5.4",
+ "sabre/event": ">=1.0.0,<4.0.0",
+ "sabre/uri": "~1.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "~4.3",
+ "sabre/cs": "~0.0.1"
+ },
+ "suggest": {
+ "ext-curl": " to make http requests with the Client class"
},
+ "time": "2017-06-12T07:53:04+00:00",
+ "type": "library",
"installation-source": "dist",
"autoload": {
+ "files": [
+ "lib/functions.php"
+ ],
"psr-4": {
- "Psr\\Log\\": "Psr/Log/"
+ "Sabre\\HTTP\\": "lib/"
}
},
"notification-url": "https://packagist.org/downloads/",
"license": [
- "MIT"
+ "BSD-3-Clause"
],
"authors": [
{
- "name": "PHP-FIG",
- "homepage": "http://www.php-fig.org/"
+ "name": "Evert Pot",
+ "email": "me@evertpot.com",
+ "homepage": "http://evertpot.com/",
+ "role": "Developer"
}
],
- "description": "Common interface for logging libraries",
- "homepage": "https://github.com/php-fig/log",
+ "description": "The sabre/http library provides utilities for dealing with http requests and responses. ",
+ "homepage": "https://github.com/fruux/sabre-http",
"keywords": [
- "log",
- "psr",
- "psr-3"
+ "http"
]
}
]
diff --git a/library/htmlpurifier-4.6.0-lite/CREDITS b/vendor/ezyang/htmlpurifier/CREDITS
index 7921b45af..7921b45af 100644
--- a/library/htmlpurifier-4.6.0-lite/CREDITS
+++ b/vendor/ezyang/htmlpurifier/CREDITS
diff --git a/vendor/ezyang/htmlpurifier/INSTALL b/vendor/ezyang/htmlpurifier/INSTALL
new file mode 100644
index 000000000..e6dd02afa
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/INSTALL
@@ -0,0 +1,373 @@
+
+Install
+ How to install HTML Purifier
+
+HTML Purifier is designed to run out of the box, so actually using the
+library is extremely easy. (Although... if you were looking for a
+step-by-step installation GUI, you've downloaded the wrong software!)
+
+While the impatient can get going immediately with some of the sample
+code at the bottom of this library, it's well worth reading this entire
+document--most of the other documentation assumes that you are familiar
+with these contents.
+
+
+---------------------------------------------------------------------------
+1. Compatibility
+
+HTML Purifier is PHP 5 and PHP 7, and is actively tested from PHP 5.0.5
+and up. It has no core dependencies with other libraries.
+
+These optional extensions can enhance the capabilities of HTML Purifier:
+
+ * iconv : Converts text to and from non-UTF-8 encodings
+ * bcmath : Used for unit conversion and imagecrash protection
+ * tidy : Used for pretty-printing HTML
+
+These optional libraries can enhance the capabilities of HTML Purifier:
+
+ * CSSTidy : Clean CSS stylesheets using %Core.ExtractStyleBlocks
+ Note: You should use the modernized fork of CSSTidy available
+ at https://github.com/Cerdic/CSSTidy
+ * Net_IDNA2 (PEAR) : IRI support using %Core.EnableIDNA
+ Note: This is not necessary for PHP 5.3 or later
+
+---------------------------------------------------------------------------
+2. Reconnaissance
+
+A big plus of HTML Purifier is its inerrant support of standards, so
+your web-pages should be standards-compliant. (They should also use
+semantic markup, but that's another issue altogether, one HTML Purifier
+cannot fix without reading your mind.)
+
+HTML Purifier can process these doctypes:
+
+* XHTML 1.0 Transitional (default)
+* XHTML 1.0 Strict
+* HTML 4.01 Transitional
+* HTML 4.01 Strict
+* XHTML 1.1
+
+...and these character encodings:
+
+* UTF-8 (default)
+* Any encoding iconv supports (with crippled internationalization support)
+
+These defaults reflect what my choices would be if I were authoring an
+HTML document, however, what you choose depends on the nature of your
+codebase. If you don't know what doctype you are using, you can determine
+the doctype from this identifier at the top of your source code:
+
+ <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
+
+...and the character encoding from this code:
+
+ <meta http-equiv="Content-type" content="text/html;charset=ENCODING">
+
+If the character encoding declaration is missing, STOP NOW, and
+read 'docs/enduser-utf8.html' (web accessible at
+http://htmlpurifier.org/docs/enduser-utf8.html). In fact, even if it is
+present, read this document anyway, as many websites specify their
+document's character encoding incorrectly.
+
+
+---------------------------------------------------------------------------
+3. Including the library
+
+The procedure is quite simple:
+
+ require_once '/path/to/library/HTMLPurifier.auto.php';
+
+This will setup an autoloader, so the library's files are only included
+when you use them.
+
+Only the contents in the library/ folder are necessary, so you can remove
+everything else when using HTML Purifier in a production environment.
+
+If you installed HTML Purifier via PEAR, all you need to do is:
+
+ require_once 'HTMLPurifier.auto.php';
+
+Please note that the usual PEAR practice of including just the classes you
+want will not work with HTML Purifier's autoloading scheme.
+
+Advanced users, read on; other users can skip to section 4.
+
+Autoload compatibility
+----------------------
+
+ HTML Purifier attempts to be as smart as possible when registering an
+ autoloader, but there are some cases where you will need to change
+ your own code to accomodate HTML Purifier. These are those cases:
+
+ PHP VERSION IS LESS THAN 5.1.2, AND YOU'VE DEFINED __autoload
+ Because spl_autoload_register() doesn't exist in early versions
+ of PHP 5, HTML Purifier has no way of adding itself to the autoload
+ stack. Modify your __autoload function to test
+ HTMLPurifier_Bootstrap::autoload($class)
+
+ For example, suppose your autoload function looks like this:
+
+ function __autoload($class) {
+ require str_replace('_', '/', $class) . '.php';
+ return true;
+ }
+
+ A modified version with HTML Purifier would look like this:
+
+ function __autoload($class) {
+ if (HTMLPurifier_Bootstrap::autoload($class)) return true;
+ require str_replace('_', '/', $class) . '.php';
+ return true;
+ }
+
+ Note that there *is* some custom behavior in our autoloader; the
+ original autoloader in our example would work for 99% of the time,
+ but would fail when including language files.
+
+ AN __autoload FUNCTION IS DECLARED AFTER OUR AUTOLOADER IS REGISTERED
+ spl_autoload_register() has the curious behavior of disabling
+ the existing __autoload() handler. Users need to explicitly
+ spl_autoload_register('__autoload'). Because we use SPL when it
+ is available, __autoload() will ALWAYS be disabled. If __autoload()
+ is declared before HTML Purifier is loaded, this is not a problem:
+ HTML Purifier will register the function for you. But if it is
+ declared afterwards, it will mysteriously not work. This
+ snippet of code (after your autoloader is defined) will fix it:
+
+ spl_autoload_register('__autoload')
+
+ Users should also be on guard if they use a version of PHP previous
+ to 5.1.2 without an autoloader--HTML Purifier will define __autoload()
+ for you, which can collide with an autoloader that was added by *you*
+ later.
+
+
+For better performance
+----------------------
+
+ Opcode caches, which greatly speed up PHP initialization for scripts
+ with large amounts of code (HTML Purifier included), don't like
+ autoloaders. We offer an include file that includes all of HTML Purifier's
+ files in one go in an opcode cache friendly manner:
+
+ // If /path/to/library isn't already in your include path, uncomment
+ // the below line:
+ // require '/path/to/library/HTMLPurifier.path.php';
+
+ require 'HTMLPurifier.includes.php';
+
+ Optional components still need to be included--you'll know if you try to
+ use a feature and you get a class doesn't exists error! The autoloader
+ can be used in conjunction with this approach to catch classes that are
+ missing. Simply add this afterwards:
+
+ require 'HTMLPurifier.autoload.php';
+
+Standalone version
+------------------
+
+ HTML Purifier has a standalone distribution; you can also generate
+ a standalone file from the full version by running the script
+ maintenance/generate-standalone.php . The standalone version has the
+ benefit of having most of its code in one file, so parsing is much
+ faster and the library is easier to manage.
+
+ If HTMLPurifier.standalone.php exists in the library directory, you
+ can use it like this:
+
+ require '/path/to/HTMLPurifier.standalone.php';
+
+ This is equivalent to including HTMLPurifier.includes.php, except that
+ the contents of standalone/ will be added to your path. To override this
+ behavior, specify a new HTMLPURIFIER_PREFIX where standalone files can
+ be found (usually, this will be one directory up, the "true" library
+ directory in full distributions). Don't forget to set your path too!
+
+ The autoloader can be added to the end to ensure the classes are
+ loaded when necessary; otherwise you can manually include them.
+ To use the autoloader, use this:
+
+ require 'HTMLPurifier.autoload.php';
+
+For advanced users
+------------------
+
+ HTMLPurifier.auto.php performs a number of operations that can be done
+ individually. These are:
+
+ HTMLPurifier.path.php
+ Puts /path/to/library in the include path. For high performance,
+ this should be done in php.ini.
+
+ HTMLPurifier.autoload.php
+ Registers our autoload handler HTMLPurifier_Bootstrap::autoload($class).
+
+ You can do these operations by yourself--in fact, you must modify your own
+ autoload handler if you are using a version of PHP earlier than PHP 5.1.2
+ (See "Autoload compatibility" above).
+
+
+---------------------------------------------------------------------------
+4. Configuration
+
+HTML Purifier is designed to run out-of-the-box, but occasionally HTML
+Purifier needs to be told what to do. If you answer no to any of these
+questions, read on; otherwise, you can skip to the next section (or, if you're
+into configuring things just for the heck of it, skip to 4.3).
+
+* Am I using UTF-8?
+* Am I using XHTML 1.0 Transitional?
+
+If you answered no to any of these questions, instantiate a configuration
+object and read on:
+
+ $config = HTMLPurifier_Config::createDefault();
+
+
+4.1. Setting a different character encoding
+
+You really shouldn't use any other encoding except UTF-8, especially if you
+plan to support multilingual websites (read section three for more details).
+However, switching to UTF-8 is not always immediately feasible, so we can
+adapt.
+
+HTML Purifier uses iconv to support other character encodings, as such,
+any encoding that iconv supports <http://www.gnu.org/software/libiconv/>
+HTML Purifier supports with this code:
+
+ $config->set('Core.Encoding', /* put your encoding here */);
+
+An example usage for Latin-1 websites (the most common encoding for English
+websites):
+
+ $config->set('Core.Encoding', 'ISO-8859-1');
+
+Note that HTML Purifier's support for non-Unicode encodings is crippled by the
+fact that any character not supported by that encoding will be silently
+dropped, EVEN if it is ampersand escaped. If you want to work around
+this, you are welcome to read docs/enduser-utf8.html for a fix,
+but please be cognizant of the issues the "solution" creates (for this
+reason, I do not include the solution in this document).
+
+
+4.2. Setting a different doctype
+
+For those of you using HTML 4.01 Transitional, you can disable
+XHTML output like this:
+
+ $config->set('HTML.Doctype', 'HTML 4.01 Transitional');
+
+Other supported doctypes include:
+
+ * HTML 4.01 Strict
+ * HTML 4.01 Transitional
+ * XHTML 1.0 Strict
+ * XHTML 1.0 Transitional
+ * XHTML 1.1
+
+
+4.3. Other settings
+
+There are more configuration directives which can be read about
+here: <http://htmlpurifier.org/live/configdoc/plain.html> They're a bit boring,
+but they can help out for those of you who like to exert maximum control over
+your code. Some of the more interesting ones are configurable at the
+demo <http://htmlpurifier.org/demo.php> and are well worth looking into
+for your own system.
+
+For example, you can fine tune allowed elements and attributes, convert
+relative URLs to absolute ones, and even autoparagraph input text! These
+are, respectively, %HTML.Allowed, %URI.MakeAbsolute and %URI.Base, and
+%AutoFormat.AutoParagraph. The %Namespace.Directive naming convention
+translates to:
+
+ $config->set('Namespace.Directive', $value);
+
+E.g.
+
+ $config->set('HTML.Allowed', 'p,b,a[href],i');
+ $config->set('URI.Base', 'http://www.example.com');
+ $config->set('URI.MakeAbsolute', true);
+ $config->set('AutoFormat.AutoParagraph', true);
+
+
+---------------------------------------------------------------------------
+5. Caching
+
+HTML Purifier generates some cache files (generally one or two) to speed up
+its execution. For maximum performance, make sure that
+library/HTMLPurifier/DefinitionCache/Serializer is writeable by the webserver.
+
+If you are in the library/ folder of HTML Purifier, you can set the
+appropriate permissions using:
+
+ chmod -R 0755 HTMLPurifier/DefinitionCache/Serializer
+
+If the above command doesn't work, you may need to assign write permissions
+to group:
+
+ chmod -R 0775 HTMLPurifier/DefinitionCache/Serializer
+
+You can also chmod files via your FTP client; this option
+is usually accessible by right clicking the corresponding directory and
+then selecting "chmod" or "file permissions".
+
+Starting with 2.0.1, HTML Purifier will generate friendly error messages
+that will tell you exactly what you have to chmod the directory to, if in doubt,
+follow its advice.
+
+If you are unable or unwilling to give write permissions to the cache
+directory, you can either disable the cache (and suffer a performance
+hit):
+
+ $config->set('Core.DefinitionCache', null);
+
+Or move the cache directory somewhere else (no trailing slash):
+
+ $config->set('Cache.SerializerPath', '/home/user/absolute/path');
+
+
+---------------------------------------------------------------------------
+6. Using the code
+
+The interface is mind-numbingly simple:
+
+ $purifier = new HTMLPurifier($config);
+ $clean_html = $purifier->purify( $dirty_html );
+
+That's it! For more examples, check out docs/examples/ (they aren't very
+different though). Also, docs/enduser-slow.html gives advice on what to
+do if HTML Purifier is slowing down your application.
+
+
+---------------------------------------------------------------------------
+7. Quick install
+
+First, make sure library/HTMLPurifier/DefinitionCache/Serializer is
+writable by the webserver (see Section 5: Caching above for details).
+If your website is in UTF-8 and XHTML Transitional, use this code:
+
+<?php
+ require_once '/path/to/htmlpurifier/library/HTMLPurifier.auto.php';
+
+ $config = HTMLPurifier_Config::createDefault();
+ $purifier = new HTMLPurifier($config);
+ $clean_html = $purifier->purify($dirty_html);
+?>
+
+If your website is in a different encoding or doctype, use this code:
+
+<?php
+ require_once '/path/to/htmlpurifier/library/HTMLPurifier.auto.php';
+
+ $config = HTMLPurifier_Config::createDefault();
+ $config->set('Core.Encoding', 'ISO-8859-1'); // replace with your encoding
+ $config->set('HTML.Doctype', 'HTML 4.01 Transitional'); // replace with your doctype
+ $purifier = new HTMLPurifier($config);
+
+ $clean_html = $purifier->purify($dirty_html);
+?>
+
+ vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/INSTALL.fr.utf8 b/vendor/ezyang/htmlpurifier/INSTALL.fr.utf8
new file mode 100644
index 000000000..95164abba
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/INSTALL.fr.utf8
@@ -0,0 +1,60 @@
+
+Installation
+ Comment installer HTML Purifier
+
+Attention : Ce document est encodé en UTF-8, si les lettres avec des accents
+ne s'affichent pas, prenez un meilleur éditeur de texte.
+
+L'installation de HTML Purifier est très simple, parce qu'il n'a pas besoin
+de configuration. Pour les utilisateurs impatients, le code se trouve dans le
+pied de page, mais je recommande de lire le document.
+
+1. Compatibilité
+
+HTML Purifier fonctionne avec PHP 5. PHP 5.0.5 est la dernière version testée.
+Il ne dépend pas d'autres librairies.
+
+Les extensions optionnelles sont iconv (généralement déjà installée) et tidy
+(répendue aussi). Si vous utilisez UTF-8 et que vous ne voulez pas l'indentation,
+vous pouvez utiliser HTML Purifier sans ces extensions.
+
+
+2. Inclure la librairie
+
+Quand vous devez l'utilisez, incluez le :
+
+ require_once('/path/to/library/HTMLPurifier.auto.php');
+
+Ne pas l'inclure si ce n'est pas nécessaire, car HTML Purifier est lourd.
+
+HTML Purifier utilise "autoload". Si vous avez défini la fonction __autoload,
+vous devez ajouter cette fonction :
+
+ spl_autoload_register('__autoload')
+
+Plus d'informations dans le document "INSTALL".
+
+3. Installation rapide
+
+Si votre site Web est en UTF-8 et XHTML Transitional, utilisez :
+
+<?php
+ require_once('/path/to/htmlpurifier/library/HTMLPurifier.auto.php');
+ $purificateur = new HTMLPurifier();
+ $html_propre = $purificateur->purify($html_a_purifier);
+?>
+
+Sinon, utilisez :
+
+<?php
+ require_once('/path/to/html/purifier/library/HTMLPurifier.auto.load');
+ $config = $HTMLPurifier_Config::createDefault();
+ $config->set('Core', 'Encoding', 'ISO-8859-1'); //Remplacez par votre
+ encodage
+ $config->set('Core', 'XHTML', true); //Remplacer par false si HTML 4.01
+ $purificateur = new HTMLPurifier($config);
+ $html_propre = $purificateur->purify($html_a_purifier);
+?>
+
+
+ vim: et sw=4 sts=4
diff --git a/library/htmlpurifier-4.6.0-lite/LICENSE b/vendor/ezyang/htmlpurifier/LICENSE
index 8c88a20d4..8c88a20d4 100644
--- a/library/htmlpurifier-4.6.0-lite/LICENSE
+++ b/vendor/ezyang/htmlpurifier/LICENSE
diff --git a/vendor/ezyang/htmlpurifier/NEWS b/vendor/ezyang/htmlpurifier/NEWS
new file mode 100644
index 000000000..fd5d56cf0
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/NEWS
@@ -0,0 +1,1176 @@
+NEWS ( CHANGELOG and HISTORY ) HTMLPurifier
+|||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
+
+= KEY ====================
+ # Breaks back-compat
+ ! Feature
+ - Bugfix
+ + Sub-comment
+ . Internal change
+==========================
+
+4.9.3, released 2017-06-02
+- Workaround PHP 7.1 infinite loop when opcode cache is enabled.
+ Thanks @Xiphin (#134, #135)
+- Don't use autoloader when testing for DOMDocument. Hypothetically,
+ this could cause your install to start using DirectLex if you had
+ previously been monkeypatching in a custom, autoloaded implementation
+ of DOMDocument. Don't do that. Thanks @Izumi-kun (#130)
+
+4.9.2, released 2017-03-12
+- Fixes PHP 5.3 compatibility
+- Fix breakage when decoding decimal entities. Thanks @rybakit (#129)
+
+4.9.1, released 2017-03-08
+! %URI.DefaultScheme can now be set to null, in which case
+ all relative paths are removed.
+! New CSS properties: min-width, max-width, min-height, max-height (#94)
+! Transparency (rgba) and hsl/hsla supported where color CSS is present.
+ Thanks @fxbt for contributing the patch. (#118)
+- When idn_to_ascii is defined, we might accept malformed
+ hostnames. Apply validation to the result in such cases.
+- Close directory when done in Serializer DefinitionCache (#100)
+- Deleted some asserts to avoid linters from choking (#97)
+- Rework Serializer cache behavior to avoid chmod'ing if possible (#32)
+- Embedded semicolons in strings in CSS are now handled correctly!
+- We accidentally dropped certain Unicode characters if there was
+ one or more invalid characters. This has been fixed, thanks
+ to mpyw <ryosuke_i_628@yahoo.co.jp>
+- Fix for "Don't truncate upon encountering </div> when using DOMLex"
+ caused a regression with HTML 4.01 Strict parsing with libxml 2.9.1
+ (and maybe later versions, but known OK with libxml 2.9.4). The
+ fix is to go about handling truncation a bit more cleverly so that
+ we can wrap with divs (sidestepping the bug) but slurping out the
+ rest of the text in case it ran off the end. (#78)
+- Fix PREG_BACKTRACK_LIMIT_ERROR in HTMLPurifier_Filter_ExtractStyle.
+ Thanks @breathbath for contributing the report and fix (#120)
+- Fix entity decoding algorithm to be more conservative about
+ decoding entities that are missing trailing semicolon.
+ To get old behavior, set %Core.LegacyEntityDecoder to true.
+ (#119)
+- Workaround libxml bug when HTML tags are embedded inside
+ script tags. To disable workaround set %Core.AggressivelyRemoveScript
+ to false. (#83)
+# By default, when a link has a target attribute associated
+ with it, we now also add rel="noopener" in order to
+ prevent the new window from being able to overwrite
+ the original frame. To disable this protection,
+ set %HTML.TargetNoopener to FALSE.
+
+4.9.0 was cut on Git but never properly released; when we did the
+real release we decided to skip this version number.
+
+4.8.0, released 2016-07-16
+# By default, when a link has a target attribute associated
+ with it, we now also add rel="noreferrer" in order to
+ prevent the new window from being able to overwrite
+ the original frame. To disable this protection,
+ set %HTML.TargetNoreferrer to FALSE.
+! Full PHP 7 compatibility, the test suite is ALL GO.
+! %CSS.AllowDuplicates permits duplicate CSS properties.
+! Support for 'tel' URIs.
+! Partial support for 'border-radius' properties when %CSS.AllowProprietary is true.
+ The slash syntax, i.e., 'border-radius: 2em 1em 4em / 0.5em 3em' is not
+ yet supported.
+! %Attr.ID.HTML5 turns on HTML5-style ID handling.
+- alt truncation could result in malformed UTF-8 sequence. Don't
+ truncate. Thanks Brandon Farber for reporting.
+- Linkify regex is smarter, based off of Gruber's regex.
+- IDNA supported natively on PHP 5.3 and later.
+- Non all-numeric top-level names (e.g., foo.1f, 1f) are now
+ allowed.
+- Minor bounds error fix to squash a PHP 7 notice.
+- Support non-/tmp temporary directories for data:// validation
+- Give a better error message when a user attempts to allow
+ ul/ol without allowing li.
+- On some versions of PHP, the Serializer DefinitionCache could
+ infinite loop when the directory exists but is not listable. (#49)
+- Don't match for <body> inside comments with
+ %Core.ConvertDocumentToFragment. (#67)
+- SafeObject is now less case sensitive. (#57)
+- AutoFormat.RemoveEmpty.Predicate now correctly renders in
+ web form. (#85)
+
+4.7.0, released 2015-08-04
+# opacity is now considered a "tricky" CSS property rather than a
+ proprietary one.
+! %AutoFormat.RemoveEmpty.Predicate for specifying exactly when
+ an element should be considered "empty" (maybe preserve if it
+ has attributes), and modify iframe support so that the iframe
+ is removed if it is missing a src attribute. Thanks meeva for
+ reporting.
+- Don't truncate upon encountering </div> when using DOMLex. Thanks
+ Myrto Christina for finally convincing me to fix this.
+- Update YouTube filter for new code.
+- Fix parsing of rgb() values with spaces in them for 'border'
+ attribute.
+- Don't remove foo="" attributes if foo is a boolean attribute. Thanks
+ valME for reporting.
+
+4.6.0, released 2013-11-30
+# Secure URI munge hashing algorithm has changed to hash_hmac("sha256", $url, $secret).
+ Please update any verification scripts you may have.
+# URI parsing algorithm was made more strict, so only prefixes which
+ looks like schemes will actually be schemes. Thanks
+ Michael Gusev <mgusev@sugarcrm.com> for fixing.
+# %Core.EscapeInvalidChildren is no longer supported, and no longer does
+ anything.
+! New directive %Core.AllowHostnameUnderscore which allows underscores
+ in hostnames.
+- Eliminate quadratic behavior in DOMLex by using a proper queue.
+ Thanks Ole Laursen for noticing this.
+- Rewritten MakeWellFormed/FixNesting implementation eliminates quadratic
+ behavior in the rest of the purificaiton pipeline. Thanks Chedburn
+ Networks for sponsoring this work.
+- Made Linkify URL parser a bit less permissive, so that non-breaking
+ spaces and commas are not included as part of URL. Thanks nAS for fixing.
+- Fix some bad interactions with %HTML.Allowed and injectors. Thanks
+ David Hirtz for reporting.
+- Fix infinite loop in DirectLex. Thanks Ashar Javed (@soaj1664ashar)
+ for reporting.
+
+4.5.0, released 2013-02-17
+# Fix bug where stacked attribute transforms clobber each other;
+ this also means it's no longer possible to override attribute
+ transforms in later modules. No internal code was using this
+ but this may break some clients.
+# We now use SHA-1 to identify cached definitions, instead of MD5.
+! Support display:inline-block
+! Support for more white-space CSS values.
+! Permit underscores in font families
+! Support for page-break-* CSS3 properties when proprietary properties
+ are enabled.
+! New directive %Core.DisableExcludes; can be set to 'true' to turn off
+ SGML excludes checking. If HTML Purifier is removing too much text
+ and you don't care about full standards compliance, try setting this to
+ 'true'.
+- Use prepend for SPL autoloading on PHP 5.3 and later.
+- Fix bug with nofollow transform when pre-existing rel exists.
+- Fix bug where background:url() always gets lower-cased
+ (but not background-image:url())
+- Fix bug with non lower-case color names in HTML
+- Fix bug where data URI validation doesn't remove temporary files.
+ Thanks Javier Marín Ros <javiermarinros@gmail.com> for reporting.
+- Don't remove certain empty tags on RemoveEmpty.
+
+4.4.0, released 2012-01-18
+# Removed PEARSax3 handler.
+# URI.Munge now munges URIs inside the same host that go from https
+ to http. Reported by Neike Taika-Tessaro.
+# Core.EscapeNonASCIICharacters now always transforms entities to
+ entities, even if target encoding is UTF-8.
+# Tighten up selector validation in ExtractStyleBlocks.
+ Non-syntactically valid selectors are now rejected, along with
+ some of the more obscure ones such as attribute selectors, the
+ :lang pseudoselector, and anything not in CSS2.1. Furthermore,
+ ID and class selectors now work properly with the relevant
+ configuration attributes. Also, mute errors when parsing CSS
+ with CSS Tidy. Reported by Mario Heiderich and Norman Hippert.
+! Added support for 'scope' attribute on tables.
+! Added %HTML.TargetBlank, which adds target="blank" to all outgoing links.
+! Properly handle sub-lists directly nested inside of lists in
+ a standards compliant way, by moving them into the preceding <li>
+! Added %HTML.AllowedComments and %HTML.AllowedCommentsRegexp for
+ limited allowed comments in untrusted situations.
+! Implement iframes, and allow them to be used in untrusted mode with
+ %HTML.SafeIframe and %URI.SafeIframeRegexp. Thanks Bradley M. Froehle
+ <brad.froehle@gmail.com> for submitting an initial version of the patch.
+! The Forms module now works properly for transitional doctypes.
+! Added support for internationalized domain names. You need the PEAR
+ Net_IDNA2 module to be in your path; if it is installed, ensure the
+ class can be loaded and then set %Core.EnableIDNA to true.
+- Color keywords are now case insensitive. Thanks Yzmir Ramirez
+ <yramirez-htmlpurifier@adicio.com> for reporting.
+- Explicitly initialize anonModule variable to null.
+- Do not duplicate nofollow if already present. Thanks 178
+ for reporting.
+- Do not add nofollow if hostname matches our current host. Thanks 178
+ for reporting, and Neike Taika-Tessaro for helping diagnose.
+- Do not unset parser variable; this fixes intermittent serialization
+ problems. Thanks Neike Taika-Tessaro for reporting, bill
+ <10010tiger@gmail.com> for diagnosing.
+- Fix iconv truncation bug, where non-UTF-8 target encodings see
+ output truncated after around 8000 characters. Thanks Jörg Ludwig
+ <joerg.ludwig@iserv.eu> for reporting.
+- Fix broken table content model for XHTML1.1 (and also earlier
+ versions, although the W3C validator doesn't catch those violations).
+ Thanks GlitchMr <glitch.mr@gmail.com> for reporting.
+
+4.3.0, released 2011-03-27
+# Fixed broken caching of customized raw definitions, but requires an
+ API change. The old API still works but will emit a warning,
+ see http://htmlpurifier.org/docs/enduser-customize.html#optimized
+ for how to upgrade your code.
+# Protect against Internet Explorer innerHTML behavior by specially
+ treating attributes with backticks but no angled brackets, quotes or
+ spaces. This constitutes a slight semantic change, which can be
+ reverted using %Output.FixInnerHTML. Reported by Neike Taika-Tessaro
+ and Mario Heiderich.
+# Protect against cssText/innerHTML by restricting allowed characters
+ used in fonts further than mandated by the specification and encoding
+ some extra special characters in URLs. Reported by Neike
+ Taika-Tessaro and Mario Heiderich.
+! Added %HTML.Nofollow to add rel="nofollow" to external links.
+! More types of SPL autoloaders allowed on later versions of PHP.
+! Implementations for position, top, left, right, bottom, z-index
+ when %CSS.Trusted is on.
+! Add %Cache.SerializerPermissions option for custom serializer
+ directory/file permissions
+! Fix longstanding bug in Flash support for non-IE browsers, and
+ allow more wmode attributes.
+! Add %CSS.AllowedFonts to restrict permissible font names.
+- Switch to an iterative traversal of the DOM, which prevents us
+ from running out of stack space for deeply nested documents.
+ Thanks Maxim Krizhanovsky for contributing a patch.
+- Make removal of conditional IE comments ungreedy; thanks Bernd
+ for reporting.
+- Escape CDATA before removing Internet Explorer comments.
+- Fix removal of id attributes under certain conditions by ensuring
+ armor attributes are preserved when recreating tags.
+- Check if schema.ser was corrupted.
+- Check if zend.ze1_compatibility_mode is on, and error out if it is.
+ This safety check is only done for HTMLPurifier.auto.php; if you
+ are using standalone or the specialized includes files, you're
+ expected to know what you're doing.
+- Stop repeatedly writing the cache file after I'm done customizing a
+ raw definition. Reported by ajh.
+- Switch to using require_once in the Bootstrap to work around bad
+ interaction with Zend Debugger and APC. Reported by Antonio Parraga.
+- Fix URI handling when hostname is missing but scheme is present.
+ Reported by Neike Taika-Tessaro.
+- Fix missing numeric entities on DirectLex; thanks Neike Taika-Tessaro
+ for reporting.
+- Fix harmless notice from indexing into empty string. Thanks Matthijs
+ Kooijman <matthijs@stdin.nl> for reporting.
+- Don't autoclose no parent elements are able to support the element
+ that triggered the autoclose. In particular fixes strange behavior
+ of stray <li> tags. Thanks pkuliga@gmail.com for reporting and
+ Neike Taika-Tessaro <pinkgothic@gmail.com> for debugging assistance.
+
+4.2.0, released 2010-09-15
+! Added %Core.RemoveProcessingInstructions, which lets you remove
+ <? ... ?> statements.
+! Added %URI.DisableResources functionality; the directive originally
+ did nothing. Thanks David Rothstein for reporting.
+! Add documentation about configuration directive types.
+! Add %CSS.ForbiddenProperties configuration directive.
+! Add %HTML.FlashAllowFullScreen to permit embedded Flash objects
+ to utilize full-screen mode.
+! Add optional support for the <code>file</code> URI scheme, enable
+ by explicitly setting %URI.AllowedSchemes.
+! Add %Core.NormalizeNewlines options to allow turning off newline
+ normalization.
+- Fix improper handling of Internet Explorer conditional comments
+ by parser. Thanks zmonteca for reporting.
+- Fix missing attributes bug when running on Mac Snow Leopard and APC.
+ Thanks sidepodcast for the fix.
+- Warn if an element is allowed, but an attribute it requires is
+ not allowed.
+
+4.1.1, released 2010-05-31
+- Fix undefined index warnings in maintenance scripts.
+- Fix bug in DirectLex for parsing elements with a single attribute
+ with entities.
+- Rewrite CSS output logic for font-family and url(). Thanks Mario
+ Heiderich <mario.heiderich@googlemail.com> for reporting and Takeshi
+ Terada <t-terada@violet.plala.or.jp> for suggesting the fix.
+- Emit an error for CollectErrors if a body is extracted
+- Fix bug where in background-position for center keyword handling.
+- Fix infinite loop when a wrapper element is inserted in a context
+ where it's not allowed. Thanks Lars <lars@renoz.dk> for reporting.
+- Remove +x bit and shebang from index.php; only supported mode is to
+ explicitly call it with php.
+- Make test script less chatty when log_errors is on.
+
+4.1.0, released 2010-04-26
+! Support proprietary height attribute on table element
+! Support YouTube slideshows that contain /cp/ in their URL.
+! Support for data: URI scheme; not enabled by default, add it using
+ %URI.AllowedSchemes
+! Support flashvars when using %HTML.SafeObject and %HTML.SafeEmbed.
+! Support for Internet Explorer compatibility with %HTML.SafeObject
+ using %Output.FlashCompat.
+! Handle <ol><ol> properly, by inserting the necessary <li> tag.
+- Always quote the insides of url(...) in CSS.
+
+4.0.0, released 2009-07-07
+# APIs for ConfigSchema subsystem have substantially changed. See
+ docs/dev-config-bcbreaks.txt for details; in essence, anything that
+ had both namespace and directive now have a single unified key.
+# Some configuration directives were renamed, specifically:
+ %AutoFormatParam.PurifierLinkifyDocURL -> %AutoFormat.PurifierLinkify.DocURL
+ %FilterParam.ExtractStyleBlocksEscaping -> %Filter.ExtractStyleBlocks.Escaping
+ %FilterParam.ExtractStyleBlocksScope -> %Filter.ExtractStyleBlocks.Scope
+ %FilterParam.ExtractStyleBlocksTidyImpl -> %Filter.ExtractStyleBlocks.TidyImpl
+ As usual, the old directive names will still work, but will throw E_NOTICE
+ errors.
+# The allowed values for class have been relaxed to allow all of CDATA for
+ doctypes that are not XHTML 1.1 or XHTML 2.0. For old behavior, set
+ %Attr.ClassUseCDATA to false.
+# Instead of appending the content model to an old content model, a blank
+ element will replace the old content model. You can use #SUPER to get
+ the old content model.
+! More robust support for name="" and id=""
+! HTMLPurifier_Config::inherit($config) allows you to inherit one
+ configuration, and have changes to that configuration be propagated
+ to all of its children.
+! Implement %HTML.Attr.Name.UseCDATA, which relaxes validation rules on
+ the name attribute when set. Use with care. Thanks Ian Cook for
+ sponsoring.
+! Implement %AutoFormat.RemoveEmpty.RemoveNbsp, which removes empty
+ tags that contain non-breaking spaces as well other whitespace. You
+ can also modify which tags should have &nbsp; maintained with
+ %AutoFormat.RemoveEmpty.RemoveNbsp.Exceptions.
+! Implement %Attr.AllowedClasses, which allows administrators to restrict
+ classes users can use to a specified finite set of classes, and
+ %Attr.ForbiddenClasses, which is the logical inverse.
+! You can now maintain your own configuration schema directories by
+ creating a config-schema.php file or passing an extra argument. Check
+ docs/dev-config-schema.html for more details.
+! Added HTMLPurifier_Config->serialize() method, which lets you save away
+ your configuration in a compact serial file, which you can unserialize
+ and use directly without having to go through the overhead of setup.
+- Fix bug where URIDefinition would not get cleared if it's directives got
+ changed.
+- Fix fatal error in HTMLPurifier_Encoder on certain platforms (probably NetBSD 5.0)
+- Fix bug in Linkify autoformatter involving <a><span>http://foo</span></a>
+- Make %URI.Munge not apply to links that have the same host as your host.
+- Prevent stray </body> tag from truncating output, if a second </body>
+ is present.
+. Created script maintenance/rename-config.php for renaming a configuration
+ directive while maintaining its alias. This script does not change source code.
+. Implement namespace locking for definition construction, to prevent
+ bugs where a directive is used for definition construction but is not
+ used to construct the cache hash.
+
+3.3.0, released 2009-02-16
+! Implement CSS property 'overflow' when %CSS.AllowTricky is true.
+! Implement generic property list classess
+- Fix bug with testEncodingSupportsASCII() algorithm when iconv() implementation
+ does not do the "right thing" with characters not supported in the output
+ set.
+- Spellcheck UTF-8: The Secret To Character Encoding
+- Fix improper removal of the contents of elements with only whitespace. Thanks
+ Eric Wald for reporting.
+- Fix broken test suite in versions of PHP without spl_autoload_register()
+- Fix degenerate case with YouTube filter involving double hyphens.
+ Thanks Pierre Attar for reporting.
+- Fix YouTube rendering problem on certain versions of Firefox.
+- Fix CSSDefinition Printer problems with decorators
+- Add text parameter to unit tests, forces text output
+. Add verbose mode to command line test runner, use (--verbose)
+. Turn on unit tests for UnitConverter
+. Fix missing version number in configuration %Attr.DefaultImageAlt (added 3.2.0)
+. Fix newline errors that caused spurious failures when CRLF HTML Purifier was
+ tested on Linux.
+. Removed trailing whitespace from all text files, see
+ remote-trailing-whitespace.php maintenance script.
+. Convert configuration to use property list backend.
+
+3.2.0, released 2008-10-31
+# Using %Core.CollectErrors forces line number/column tracking on, whereas
+ previously you could theoretically turn it off.
+# HTMLPurifier_Injector->notifyEnd() is formally deprecated. Please
+ use handleEnd() instead.
+! %Output.AttrSort for when you need your attributes in alphabetical order to
+ deal with a bug in FCKEditor. Requested by frank farmer.
+! Enable HTML comments when %HTML.Trusted is on. Requested by Waldo Jaquith.
+! Proper support for name attribute. It is now allowed and equivalent to the id
+ attribute in a and img tags, and is only converted to id when %HTML.TidyLevel
+ is heavy (for all doctypes).
+! %AutoFormat.RemoveEmpty to remove some empty tags from documents. Please don't
+ use on hand-written HTML.
+! Add error-cases for unsupported elements in MakeWellFormed. This enables
+ the strategy to be used, standalone, on untrusted input.
+! %Core.AggressivelyFixLt is on by default. This causes more sensible
+ processing of left angled brackets in smileys and other whatnot.
+! Test scripts now have a 'type' parameter, which lets you say 'htmlpurifier',
+ 'phpt', 'vtest', etc. in order to only execute those tests. This supercedes
+ the --only-phpt parameter, although for backwards-compatibility the flag
+ will still work.
+! AutoParagraph auto-formatter will now preserve double-newlines upon output.
+ Users who are not performing inbound filtering, this may seem a little
+ useless, but as a bonus, the test suite and handling of edge cases is also
+ improved.
+! Experimental implementation of forms for %HTML.Trusted
+! Track column numbers when maintain line numbers is on
+! Proprietary 'background' attribute on table-related elements converted into
+ corresponding CSS. Thanks Fusemail for sponsoring this feature!
+! Add forward(), forwardUntilEndToken(), backward() and current() to Injector
+ supertype.
+! HTMLPurifier_Injector->handleEnd() permits modification to end tokens. The
+ time of operation varies slightly from notifyEnd() as *all* end tokens are
+ processed by the injector before they are subject to the well-formedness rules.
+! %Attr.DefaultImageAlt allows overriding default behavior of setting alt to
+ basename of image when not present.
+! %AutoFormat.DisplayLinkURI neuters <a> tags into plain text URLs.
+- Fix two bugs in %URI.MakeAbsolute; one involving empty paths in base URLs,
+ the other involving an undefined $is_folder error.
+- Throw error when %Core.Encoding is set to a spurious value. Previously,
+ this errored silently and returned false.
+- Redirected stderr to stdout for flush error output.
+- %URI.DisableExternal will now use the host in %URI.Base if %URI.Host is not
+ available.
+- Do not re-munge URL if the output URL has the same host as the input URL.
+ Requested by Chris.
+- Fix error in documentation regarding %Filter.ExtractStyleBlocks
+- Prevent <![CDATA[<body></body>]]> from triggering %Core.ConvertDocumentToFragment
+- Fix bug with inline elements in blockquotes conflicting with strict doctype
+- Detect if HTML support is disabled for DOM by checking for loadHTML() method.
+- Fix bug where dots and double-dots in absolute URLs without hostname were
+ not collapsed by URIFilter_MakeAbsolute.
+- Fix bug with anonymous modules operating on SafeEmbed or SafeObject elements
+ by reordering their addition.
+- Will now throw exception on many error conditions during lexer creation; also
+ throw an exception when MaintainLineNumbers is true, but a non-tracksLineNumbers
+ is being used.
+- Detect if domxml extension is loaded, and use DirectLEx accordingly.
+- Improve handling of big numbers with floating point arithmetic in UnitConverter.
+ Reported by David Morton.
+. Strategy_MakeWellFormed now operates in-place, saving memory and allowing
+ for more interesting filter-backtracking
+. New HTMLPurifier_Injector->rewind() functionality, allows injectors to rewind
+ index to reprocess tokens.
+. StringHashParser now allows for multiline sections with "empty" content;
+ previously the section would remain undefined.
+. Added --quick option to multitest.php, which tests only the most recent
+ release for each series.
+. Added --distro option to multitest.php, which accepts either 'normal' or
+ 'standalone'. This supercedes --exclude-normal and --exclude-standalone
+
+3.1.1, released 2008-06-19
+# %URI.Munge now, by default, does not munge resources (for example, <img src="">)
+ In order to enable this again, please set %URI.MungeResources to true.
+! More robust imagecrash protection with height/width CSS with %CSS.MaxImgLength,
+ and height/width HTML with %HTML.MaxImgLength.
+! %URI.MungeSecretKey for secure URI munging. Thanks Chris
+ for sponsoring this feature. Check out the corresponding documentation
+ for details. (Att Nightly testers: The API for this feature changed before
+ the general release. Namely, rename your directives %URI.SecureMungeSecretKey =>
+ %URI.MungeSecretKey and and %URI.SecureMunge => %URI.Munge)
+! Implemented post URI filtering. Set member variable $post to true to set
+ a URIFilter as such.
+! Allow modules to define injectors via $info_injector. Injectors are
+ automatically disabled if injector's needed elements are not found.
+! Support for "safe" objects added, use %HTML.SafeObject and %HTML.SafeEmbed.
+ Thanks Chris for sponsoring. If you've been using ad hoc code from the
+ forums, PLEASE use this instead.
+! Added substitutions for %e, %n, %a and %p in %URI.Munge (in order,
+ embedded, tag name, attribute name, CSS property name). See %URI.Munge
+ for more details. Requested by Jochem Blok.
+- Disable percent height/width attributes for img.
+- AttrValidator operations are now atomic; updates to attributes are not
+ manifest in token until end of operations. This prevents naughty internal
+ code from directly modifying CurrentToken when they're not supposed to.
+ This semantics change was requested by frank farmer.
+- Percent encoding checks enabled for URI query and fragment
+- Fix stray backslashes in font-family; CSS Unicode character escapes are
+ now properly resolved (although *only* in font-family). Thanks Takeshi Terada
+ for reporting.
+- Improve parseCDATA algorithm to take into account newline normalization
+- Account for browser confusion between Yen character and backslash in
+ Shift_JIS encoding. This fix generalizes to any other encoding which is not
+ a strict superset of printable ASCII. Thanks Takeshi Terada for reporting.
+- Fix missing configuration parameter in Generator calls. Thanks vs for the
+ partial patch.
+- Improved adherence to Unicode by checking for non-character codepoints.
+ Thanks Geoffrey Sneddon for reporting. This may result in degraded
+ performance for extremely large inputs.
+- Allow CSS property-value pair ''text-decoration: none''. Thanks Jochem Blok
+ for reporting.
+. Added HTMLPurifier_UnitConverter and HTMLPurifier_Length for convenient
+ handling of CSS-style lengths. HTMLPurifier_AttrDef_CSS_Length now uses
+ this class.
+. API of HTMLPurifier_AttrDef_CSS_Length changed from __construct($disable_negative)
+ to __construct($min, $max). __construct(true) is equivalent to
+ __construct('0').
+. Added HTMLPurifier_AttrDef_Switch class
+. Rename HTMLPurifier_HTMLModule_Tidy->construct() to setup() and bubble method
+ up inheritance hierarchy to HTMLPurifier_HTMLModule. All HTMLModules
+ get this called with the configuration object. All modules now
+ use this rather than __construct(), although legacy code using constructors
+ will still work--the new format, however, lets modules access the
+ configuration object for HTML namespace dependant tweaks.
+. AttrDef_HTML_Pixels now takes a single construction parameter, pixels.
+. ConfigSchema data-structure heavily optimized; on average it uses a third
+ the memory it did previously. The interface has changed accordingly,
+ consult changes to HTMLPurifier_Config for details.
+. Variable parsing types now are magic integers instead of strings
+. Added benchmark for ConfigSchema
+. HTMLPurifier_Generator requires $config and $context parameters. If you
+ don't know what they should be, use HTMLPurifier_Config::createDefault()
+ and new HTMLPurifier_Context().
+. Printers now properly distinguish between output configuration, and
+ target configuration. This is not applicable to scripts using
+ the Printers for HTML Purifier related tasks.
+. HTML/CSS Printers must be primed with prepareGenerator($gen_config), otherwise
+ fatal errors will ensue.
+. URIFilter->prepare can return false in order to abort loading of the filter
+. Factory for AttrDef_URI implemented, URI#embedded to indicate URI that embeds
+ an external resource.
+. %URI.Munge functionality factored out into a post-filter class.
+. Added CurrentCSSProperty context variable during CSS validation
+
+3.1.0, released 2008-05-18
+# Unnecessary references to objects (vestiges of PHP4) removed from method
+ signatures. The following methods do not need references when assigning from
+ them and will result in E_STRICT errors if you try:
+ + HTMLPurifier_Config->get*Definition() [* = HTML, CSS]
+ + HTMLPurifier_ConfigSchema::instance()
+ + HTMLPurifier_DefinitionCacheFactory::instance()
+ + HTMLPurifier_DefinitionCacheFactory->create()
+ + HTMLPurifier_DoctypeRegistry->register()
+ + HTMLPurifier_DoctypeRegistry->get()
+ + HTMLPurifier_HTMLModule->addElement()
+ + HTMLPurifier_HTMLModule->addBlankElement()
+ + HTMLPurifier_LanguageFactory::instance()
+# Printer_ConfigForm's get*() functions were static-ified
+# %HTML.ForbiddenAttributes requires attribute declarations to be in the
+ form of tag@attr, NOT tag.attr (which will throw an error and won't do
+ anything). This is for forwards compatibility with XML; you'd do best
+ to migrate an %HTML.AllowedAttributes directives to this syntax too.
+! Allow index to be false for config from form creation
+! Added HTMLPurifier::VERSION constant
+! Commas, not dashes, used for serializer IDs. This change is forwards-compatible
+ and allows for version numbers like "3.1.0-dev".
+! %HTML.Allowed deals gracefully with whitespace anywhere, anytime!
+! HTML Purifier's URI handling is a lot more robust, with much stricter
+ validation checks and better percent encoding handling. Thanks Gareth Heyes
+ for indicating security vulnerabilities from lax percent encoding.
+! Bootstrap autoloader deals more robustly with classes that don't exist,
+ preventing class_exists($class, true) from barfing.
+- InterchangeBuilder now alphabetizes its lists
+- Validation error in configdoc output fixed
+- Iconv and other encoding errors muted even with custom error handlers that
+ do not honor error_reporting
+- Add protection against imagecrash attack with CSS height/width
+- HTMLPurifier::instance() created for consistency, is equivalent to getInstance()
+- Fixed and revamped broken ConfigForm smoketest
+- Bug with bool/null fields in Printer_ConfigForm fixed
+- Bug with global forbidden attributes fixed
+- Improved error messages for allowed and forbidden HTML elements and attributes
+- Missing (or null) in configdoc documentation restored
+- If DOM throws and exception during parsing with PH5P (occurs in newer versions
+ of DOM), HTML Purifier punts to DirectLex
+- Fatal error with unserialization of ScriptRequired
+- Created directories are now chmod'ed properly
+- Fixed bug with fallback languages in LanguageFactory
+- Standalone testing setup properly with autoload
+. Out-of-date documentation revised
+. UTF-8 encoding check optimization as suggested by Diego
+. HTMLPurifier_Error removed in favor of exceptions
+. More copy() function removed; should use clone instead
+. More extensive unit tests for HTMLDefinition
+. assertPurification moved to central harness
+. HTMLPurifier_Generator accepts $config and $context parameters during
+ instantiation, not runtime
+. Double-quotes outside of attribute values are now unescaped
+
+3.1.0rc1, released 2008-04-22
+# Autoload support added. Internal require_once's removed in favor of an
+ explicit require list or autoloading. To use HTML Purifier,
+ you must now either use HTMLPurifier.auto.php
+ or HTMLPurifier.includes.php; setting the include path and including
+ HTMLPurifier.php is insufficient--in such cases include HTMLPurifier.autoload.php
+ as well to register our autoload handler (or modify your autoload function
+ to check HTMLPurifier_Bootstrap::getPath($class)). You can also use
+ HTMLPurifier.safe-includes.php for a less performance friendly but more
+ user-friendly library load.
+# HTMLPurifier_ConfigSchema static functions are officially deprecated. Schema
+ information is stored in the ConfigSchema directory, and the
+ maintenance/generate-schema-cache.php generates the schema.ser file, which
+ is now instantiated. Support for userland schema changes coming soon!
+# HTMLPurifier_Config will now throw E_USER_NOTICE when you use a directive
+ alias; to get rid of these errors just modify your configuration to use
+ the new directive name.
+# HTMLPurifier->addFilter is deprecated; built-in filters can now be
+ enabled using %Filter.$filter_name or by setting your own filters using
+ %Filter.Custom
+# Directive-level safety properties superceded in favor of module-level
+ safety. Internal method HTMLModule->addElement() has changed, although
+ the externally visible HTMLDefinition->addElement has *not* changed.
+! Extra utility classes for testing and non-library operations can
+ be found in extras/. Specifically, these are FSTools and ConfigDoc.
+ You may find a use for these in your own project, but right now they
+ are highly experimental and volatile.
+! Integration with PHPT allows for automated smoketests
+! Limited support for proprietary HTML elements, namely <marquee>, sponsored
+ by Chris. You can enable them with %HTML.Proprietary if your client
+ demands them.
+! Support for !important CSS cascade modifier. By default, this will be stripped
+ from CSS, but you can enable it using %CSS.AllowImportant
+! Support for display and visibility CSS properties added, set %CSS.AllowTricky
+ to true to use them.
+! HTML Purifier now has its own Exception hierarchy under HTMLPurifier_Exception.
+ Developer error (not enduser error) can cause these to be triggered.
+! Experimental kses() wrapper introduced with HTMLPurifier.kses.php
+! Finally %CSS.AllowedProperties for tweaking allowed CSS properties without
+ mucking around with HTMLPurifier_CSSDefinition
+! ConfigDoc output has been enhanced with version and deprecation info.
+! %HTML.ForbiddenAttributes and %HTML.ForbiddenElements implemented.
+- Autoclose now operates iteratively, i.e. <span><span><div> now has
+ both span tags closed.
+- Various HTMLPurifier_Config convenience functions now accept another parameter
+ $schema which defines what HTMLPurifier_ConfigSchema to use besides the
+ global default.
+- Fix bug with trusted script handling in libxml versions later than 2.6.28.
+- Fix bug in ExtractStyleBlocks with comments in style tags
+- Fix bug in comment parsing for DirectLex
+- Flush output now displayed when in command line mode for unit tester
+- Fix bug with rgb(0, 1, 2) color syntax with spaces inside shorthand syntax
+- HTMLPurifier_HTMLDefinition->addAttribute can now be called multiple times
+ on the same element without emitting errors.
+- Fixed fatal error in PH5P lexer with invalid tag names
+. Plugins now get their own changelogs according to project conventions.
+. Convert tokens to use instanceof, reducing memory footprint and
+ improving comparison speed.
+. Dry runs now supported in SimpleTest; testing facilities improved
+. Bootstrap class added for handling autoloading functionality
+. Implemented recursive glob at FSTools->globr
+. ConfigSchema now has instance methods for all corresponding define*
+ static methods.
+. A couple of new historical maintenance scripts were added.
+. HTMLPurifier/HTMLModule/Tidy/XHTMLAndHTML4.php split into two files
+. tests/index.php can now be run from any directory.
+. HTMLPurifier_Token subclasses split into seperate files
+. HTMLPURIFIER_PREFIX now is defined in Bootstrap.php, NOT HTMLPurifier.php
+. HTMLPURIFIER_PREFIX can now be defined outside of HTML Purifier
+. New --php=php flag added, allows PHP executable to be specified (command
+ line only!)
+. htmlpurifier_add_test() preferred method to translate test files in to
+ classes, because it handles PHPT files too.
+. Debugger class is deprecated and will be removed soon.
+. Command line argument parsing for testing scripts revamped, now --opt value
+ format is supported.
+. Smoketests now cleanup after magic quotes
+. Generator now can output comments (however, comments are still stripped
+ from HTML Purifier output)
+. HTMLPurifier_ConfigSchema->validate() deprecated in favor of
+ HTMLPurifier_VarParser->parse()
+. Integers auto-cast into float type by VarParser.
+. HTMLPURIFIER_STRICT removed; no validation is performed on runtime, only
+ during cache generation
+. Reordered script calls in maintenance/flush.php
+. Command line scripts now honor exit codes
+. When --flush fails in unit testers, abort tests and print message
+. Improved documentation in docs/dev-flush.html about the maintenance scripts
+. copy() methods removed in favor of clone keyword
+
+3.0.0, released 2008-01-06
+# HTML Purifier is PHP 5 only! The 2.1.x branch will be maintained
+ until PHP 4 is completely deprecated, but no new features will be added
+ to it.
+ + Visibility declarations added
+ + Constructor methods renamed to __construct()
+ + PHP4 reference cruft removed (in progress)
+! CSS properties are now case-insensitive
+! DefinitionCacheFactory now can register new implementations
+! New HTMLPurifier_Filter_ExtractStyleBlocks for extracting <style> from
+ documents and cleaning their contents up. Requires the CSSTidy library
+ <http://csstidy.sourceforge.net/>. You can access the blocks with the
+ 'StyleBlocks' Context variable ($purifier->context->get('StyleBlocks')).
+ The output CSS can also be "scoped" for a specific element, use:
+ %Filter.ExtractStyleBlocksScope
+! Experimental support for some proprietary CSS attributes allowed:
+ opacity (and all of the browser-specific equivalents) and scrollbar colors.
+ Enable by setting %CSS.Proprietary to true.
+- Colors missing # but in hex form will be corrected
+- CSS Number algorithm improved
+- Unit testing and multi-testing now on steroids: command lines,
+ XML output, and other goodies now added.
+. Unit tests for Injector improved
+. New classes:
+ + HTMLPurifier_AttrDef_CSS_AlphaValue
+ + HTMLPurifier_AttrDef_CSS_Filter
+. Multitest now has a file docblock
+
+2.1.3, released 2007-11-05
+! tests/multitest.php allows you to test multiple versions by running
+ tests/index.php through multiple interpreters using `phpv` shell
+ script (you must provide this script!)
+- Fixed poor include ordering for Email URI AttrDefs, causes fatal errors
+ on some systems.
+- Injector algorithm further refined: off-by-one error regarding skip
+ counts for dormant injectors fixed
+- Corrective blockquote definition now enabled for HTML 4.01 Strict
+- Fatal error when <img> tag (or any other element with required attributes)
+ has 'id' attribute fixed, thanks NykO18 for reporting
+- Fix warning emitted when a non-supported URI scheme is passed to the
+ MakeAbsolute URIFilter, thanks NykO18 (again)
+- Further refine AutoParagraph injector. Behavior inside of elements
+ allowing paragraph tags clarified: only inline content delimeted by
+ double newlines (not block elements) are paragraphed.
+- Buggy treatment of end tags of elements that have required attributes
+ fixed (does not manifest on default tag-set)
+- Spurious internal content reorganization error suppressed
+- HTMLDefinition->addElement now returns a reference to the created
+ element object, as implied by the documentation
+- Phorum mod's HTML Purifier help message expanded (unreleased elsewhere)
+- Fix a theoretical class of infinite loops from DirectLex reported
+ by Nate Abele
+- Work around unnecessary DOMElement type-cast in PH5P that caused errors
+ in PHP 5.1
+- Work around PHP 4 SimpleTest lack-of-error complaining for one-time-only
+ HTMLDefinition errors, this may indicate problems with error-collecting
+ facilities in PHP 5
+- Make ErrorCollectorEMock work in both PHP 4 and PHP 5
+- Make PH5P work with PHP 5.0 by removing unnecessary array parameter typedef
+. %Core.AcceptFullDocuments renamed to %Core.ConvertDocumentToFragment
+ to better communicate its purpose
+. Error unit tests can now specify the expectation of no errors. Future
+ iterations of the harness will be extremely strict about what errors
+ are allowed
+. Extend Injector hooks to allow for more powerful injector routines
+. HTMLDefinition->addBlankElement created, as according to the HTMLModule
+ method
+. Doxygen configuration file updated, with minor improvements
+. Test runner now checks for similarly named files in conf/ directory too.
+. Minor cosmetic change to flush-definition-cache.php: trailing newline is
+ outputted
+. Maintenance script for generating PH5P patch added, original PH5P source
+ file also added under version control
+. Full unit test runner script title made more descriptive with PHP version
+. Updated INSTALL file to state that 4.3.7 is the earliest version we
+ are actively testing
+
+2.1.2, released 2007-09-03
+! Implemented Object module for trusted users
+! Implemented experimental HTML5 parsing mode using PH5P. To use, add
+ this to your code:
+ require_once 'HTMLPurifier/Lexer/PH5P.php';
+ $config->set('Core', 'LexerImpl', 'PH5P');
+ Note that this Lexer introduces some classes not in the HTMLPurifier
+ namespace. Also, this is PHP5 only.
+! CSS property border-spacing implemented
+- Fix non-visible parsing error in DirectLex with empty tags that have
+ slashes inside attribute values.
+- Fix typo in CSS definition: border-collapse:seperate; was incorrectly
+ accepted as valid CSS. Usually non-visible, because this styling is the
+ default for tables in most browsers. Thanks Brett Zamir for pointing
+ this out.
+- Fix validation errors in configuration form
+- Hammer out a bunch of edge-case bugs in the standalone distribution
+- Inclusion reflection removed from URISchemeRegistry; you must manually
+ include any new schema files you wish to use
+- Numerous typo fixes in documentation thanks to Brett Zamir
+. Unit test refactoring for one logical test per test function
+. Config and context parameters in ComplexHarness deprecated: instead, edit
+ the $config and $context member variables
+. HTML wrapper in DOMLex now takes DTD identifiers into account; doesn't
+ really make a difference, but is good for completeness sake
+. merge-library.php script refactored for greater code reusability and
+ PHP4 compatibility
+
+2.1.1, released 2007-08-04
+- Fix show-stopper bug in %URI.MakeAbsolute functionality
+- Fix PHP4 syntax error in standalone version
+. Add prefix directory to include path for standalone, this prevents
+ other installations from clobbering the standalone's URI schemes
+. Single test methods can be invoked by prefixing with __only
+
+2.1.0, released 2007-08-02
+# flush-htmldefinition-cache.php superseded in favor of a generic
+ flush-definition-cache.php script, you can clear a specific cache
+ by passing its name as a parameter to the script
+! Phorum mod implemented for HTML Purifier
+! With %Core.AggressivelyFixLt, <3 and similar emoticons no longer
+ trigger HTML removal in PHP5 (DOMLex). This directive is not necessary
+ for PHP4 (DirectLex).
+! Standalone file now available, which greatly reduces the amount of
+ includes (although there are still a few files that reside in the
+ standalone folder)
+! Relative URIs can now be transformed into their absolute equivalents
+ using %URI.Base and %URI.MakeAbsolute
+! Ruby implemented for XHTML 1.1
+! You can now define custom URI filtering behavior, see enduser-uri-filter.html
+ for more details
+! UTF-8 font names now supported in CSS
+- AutoFormatters emit friendly error messages if tags or attributes they
+ need are not allowed
+- ConfigForm's compactification of directive names is now configurable
+- AutoParagraph autoformatter algorithm refined after field-testing
+- XHTML 1.1 now applies XHTML 1.0 Strict cleanup routines, namely
+ blockquote wrapping
+- Contents of <style> tags removed by default when tags are removed
+. HTMLPurifier_Config->getSerial() implemented, this is extremely useful
+ for output cache invalidation
+. ConfigForm printer now can retrieve CSS and JS files as strings, in
+ case HTML Purifier's directory is not publically accessible
+. Introduce new text/itext configuration directive values: these represent
+ longer strings that would be more appropriately edited with a textarea
+. Allow newlines to act as separators for lists, hashes, lookups and
+ %HTML.Allowed
+. ConfigForm generates textareas instead of text inputs for lists, hashes,
+ lookups, text and itext fields
+. Hidden element content removal genericized: %Core.HiddenElements can
+ be used to customize this behavior, by default <script> and <style> are
+ hidden
+. Added HTMLPURIFIER_PREFIX constant, should be used instead of dirname(__FILE__)
+. Custom ChildDef added to default include list
+. URIScheme reflection improved: will not attempt to include file if class
+ already exists. May clobber autoload, so I need to keep an eye on it
+. ConfigSchema heavily optimized, will only collect information and validate
+ definitions when HTMLPURIFIER_SCHEMA_STRICT is true.
+. AttrDef_URI unit tests and implementation refactored
+. benchmarks/ directory now protected from public view with .htaccess file;
+ run the tests via command line
+. URI scheme is munged off if there is no authority and the scheme is the
+ default one
+. All unit tests inherit from HTMLPurifier_Harness, not UnitTestCase
+. Interface for URIScheme changed
+. Generic URI object to hold components of URI added, most systems involved
+ in URI validation have been migrated to use it
+. Custom filtering for URIs factored out to URIDefinition interface for
+ maximum extensibility
+
+2.0.1, released 2007-06-27
+! Tag auto-closing now based on a ChildDef heuristic rather than a
+ manually set auto_close array; some behavior may change
+! Experimental AutoFormat functionality added: auto-paragraph and
+ linkify your HTML input by setting %AutoFormat.AutoParagraph and
+ %AutoFormat.Linkify to true
+! Newlines normalized internally, and then converted back to the
+ value of PHP_EOL. If this is not desired, set your newline format
+ using %Output.Newline.
+! Beta error collection, messages are implemented for the most generic
+ cases involving Lexing or Strategies
+- Clean up special case code for <script> tags
+- Reorder includes for DefinitionCache decorators, fixes a possible
+ missing class error
+- Fixed bug where manually modified definitions were not saved via cache
+ (mostly harmless, except for the fact that it would be a little slower)
+- Configuration objects with different serials do not clobber each
+ others when revision numbers are unequal
+- Improve Serializer DefinitionCache directory permissions checks
+- DefinitionCache no longer throws errors when it encounters old
+ serial files that do not conform to the current style
+- Stray xmlns attributes removed from configuration documentation
+- configForm.php smoketest no longer has XSS vulnerability due to
+ unescaped print_r output
+- Printer adheres to configuration's directives on output format
+- Fix improperly named form field in ConfigForm printer
+. Rewire some test-cases to swallow errors rather than expect them
+. HTMLDefinition printer updated with some of the new attributes
+. DefinitionCache keys reordered to reflect precedence: version number,
+ hash, then revision number
+. %Core.DefinitionCache renamed to %Cache.DefinitionImpl
+. Interlinking in configuration documentation added using
+ Injector_PurifierLinkify
+. Directives now keep track of aliases to themselves
+. Error collector now requires a severity to be passed, use PHP's internal
+ error constants for this
+. HTMLPurifier_Config::getAllowedDirectivesForForm implemented, allows
+ much easier selective embedding of configuration values
+. Doctype objects now accept public and system DTD identifiers
+. %HTML.Doctype is now constrained by specific values, to specify a custom
+ doctype use new %HTML.CustomDoctype
+. ConfigForm truncates long directives to keep the form small, and does
+ not re-output namespaces
+
+2.0.0, released 2007-06-20
+# Completely refactored HTMLModuleManager, decentralizing safety
+ information
+# Transform modules changed to Tidy modules, which offer more flexibility
+ and better modularization
+# Configuration object now finalizes itself when a read operation is
+ performed on it, ensuring that its internal state stays consistent.
+ To revert this behavior, you can set the $autoFinalize member variable
+ off, but it's not recommended.
+# New compact syntax for AttrDef objects that can be used to instantiate
+ new objects via make()
+# Definitions (esp. HTMLDefinition) are now cached for a significant
+ performance boost. You can disable caching by setting %Core.DefinitionCache
+ to null. You CANNOT edit raw definitions without setting the corresponding
+ DefinitionID directive (%HTML.DefinitionID for HTMLDefinition).
+# Contents between <script> tags are now completely removed if <script>
+ is not allowed
+# Prototype-declarations for Lexer removed in favor of configuration
+ determination of Lexer implementations.
+! HTML Purifier now works in PHP 4.3.2.
+! Configuration form-editing API makes tweaking HTMLPurifier_Config a
+ breeze!
+! Configuration directives that accept hashes now allow new string
+ format: key1:value1,key2:value2
+! ConfigDoc now factored into OOP design
+! All deprecated elements now natively supported
+! Implement TinyMCE styled whitelist specification format in
+ %HTML.Allowed
+! Config object gives more friendly error messages when things go wrong
+! Advanced API implemented: easy functions for creating elements (addElement)
+ and attributes (addAttribute) on HTMLDefinition
+! Add native support for required attributes
+- Deprecated and removed EnableRedundantUTF8Cleaning. It didn't even work!
+- DOMLex will not emit errors when a custom error handler that does not
+ honor error_reporting is used
+- StrictBlockquote child definition refrains from wrapping whitespace
+ in tags now.
+- Bug resulting from tag transforms to non-allowed elements fixed
+- ChildDef_Custom's regex generation has been improved, removing several
+ false positives
+. Unit test for ElementDef created, ElementDef behavior modified to
+ be more flexible
+. Added convenience functions for HTMLModule constructors
+. AttrTypes now has accessor functions that should be used instead
+ of directly manipulating info
+. TagTransform_Center deprecated in favor of generic TagTransform_Simple
+. Add extra protection in AttrDef_URI against phantom Schemes
+. Doctype object added to HTMLDefinition which describes certain aspects
+ of the operational document type
+. Lexer is now pre-emptively included, with a conditional include for the
+ PHP5 only version.
+. HTMLDefinition and CSSDefinition have a common parent class: Definition.
+. DirectLex can now track line-numbers
+. Preliminary error collector is in place, although no code actually reports
+ errors yet
+. Factor out most of ValidateAttributes to new AttrValidator class
+
+1.6.1, released 2007-05-05
+! Support for more deprecated attributes via transformations:
+ + hspace and vspace in img
+ + size and noshade in hr
+ + nowrap in td
+ + clear in br
+ + align in caption, table, img and hr
+ + type in ul, ol and li
+! DirectLex now preserves text in which a < bracket is followed by
+ a non-alphanumeric character. This means that certain emoticons
+ are now preserved.
+! %Core.RemoveInvalidImg is now operational, when set to false invalid
+ images will hang around with an empty src
+! target attribute in a tag supported, use %Attr.AllowedFrameTargets
+ to enable
+! CSS property white-space now allows nowrap (supported in all modern
+ browsers) but not others (which have spotty browser implementations)
+! XHTML 1.1 mode now sort-of works without any fatal errors, and
+ lang is now moved over to xml:lang.
+! Attribute transformation smoketest available at smoketests/attrTransform.php
+! Transformation of font's size attribute now handles super-large numbers
+- Possibly fatal bug with __autoload() fixed in module manager
+- Invert HTMLModuleManager->addModule() processing order to check
+ prefixes first and then the literal module
+- Empty strings get converted to empty arrays instead of arrays with
+ an empty string in them.
+- Merging in attribute lists now works.
+. Demo script removed: it has been added to the website's repository
+. Basic.php script modified to work out of the box
+. Refactor AttrTransform classes to reduce duplication
+. AttrTransform_TextAlign axed in favor of a more general
+ AttrTransform_EnumToCSS, refer to HTMLModule/TransformToStrict.php to
+ see how the new equivalent is implemented
+. Unit tests now use exclusively assertIdentical
+
+1.6.0, released 2007-04-01
+! Support for most common deprecated attributes via transformations:
+ + bgcolor in td, th, tr and table
+ + border in img
+ + name in a and img
+ + width in td, th and hr
+ + height in td, th
+! Support for CSS attribute 'height' added
+! Support for rel and rev attributes in a tags added, use %Attr.AllowedRel
+ and %Attr.AllowedRev to activate
+- You can define ID blacklists using regular expressions via
+ %Attr.IDBlacklistRegexp
+- Error messages are emitted when you attempt to "allow" elements or
+ attributes that HTML Purifier does not support
+- Fix segfault in unit test. The problem is not very reproduceable and
+ I don't know what causes it, but a six line patch fixed it.
+
+1.5.0, released 2007-03-23
+! Added a rudimentary I18N and L10N system modeled off MediaWiki. It
+ doesn't actually do anything yet, but keep your eyes peeled.
+! docs/enduser-utf8.html explains how to use UTF-8 and HTML Purifier
+! Newly structured HTMLDefinition modeled off of XHTML 1.1 modules.
+ I am loathe to release beta quality APIs, but this is exactly that;
+ don't use the internal interfaces if you're not willing to do migration
+ later on.
+- Allow 'x' subtag in language codes
+- Fixed buggy chameleon-support for ins and del
+. Added support for IDREF attributes (i.e. for)
+. Renamed HTMLPurifier_AttrDef_Class to HTMLPurifier_AttrDef_Nmtokens
+. Removed context variable ParentType, replaced with IsInline, which
+ is false when you're not inline and an integer of the parent that
+ caused you to become inline when you are (so possibly zero)
+. Removed ElementDef->type in favor of ElementDef->descendants_are_inline
+ and HTMLDefinition->content_sets
+. StrictBlockquote now reports what elements its supposed to allow,
+ rather than what it does allow
+. Removed HTMLDefinition->info_flow_elements in favor of
+ HTMLDefinition->content_sets['Flow']
+. Removed redundant "exclusionary" definitions from DTD roster
+. StrictBlockquote now requires a construction parameter as if it
+ were an Required ChildDef, this is the "real" set of allowed elements
+. AttrDef partitioned into HTML, CSS and URI segments
+. Modify Youtube filter regexp to be multiline
+. Require both PHP5 and DOM extension in order to use DOMLex, fixes
+ some edge cases where a DOMDocument class exists in a PHP4 environment
+ due to DOM XML extension.
+
+1.4.1, released 2007-01-21
+! docs/enduser-youtube.html updated according to new functionality
+- YouTube IDs can have underscores and dashes
+
+1.4.0, released 2007-01-21
+! Implemented list-style-image, URIs now allowed in list-style
+! Implemented background-image, background-repeat, background-attachment
+ and background-position CSS properties. Shorthand property background
+ supports all of these properties.
+! Configuration documentation looks nicer
+! Added %Core.EscapeNonASCIICharacters to workaround loss of Unicode
+ characters while %Core.Encoding is set to a non-UTF-8 encoding.
+! Support for configuration directive aliases added
+! Config object can now be instantiated from ini files
+! YouTube preservation code added to the core, with two lines of code
+ you can add it as a filter to your code. See smoketests/preserveYouTube.php
+ for sample code.
+! Moved SLOW to docs/enduser-slow.html and added code examples
+- Replaced version check with functionality check for DOM (thanks Stephen
+ Khoo)
+. Added smoketest 'all.php', which loads all other smoketests via frames
+. Implemented AttrDef_CSSURI for url(http://google.com) style declarations
+. Added convenient single test selector form on test runner
+
+1.3.2, released 2006-12-25
+! HTMLPurifier object now accepts configuration arrays, no need to manually
+ instantiate a configuration object
+! Context object now accessible to outside
+! Added enduser-youtube.html, explains how to embed YouTube videos. See
+ also corresponding smoketest preserveYouTube.php.
+! Added purifyArray(), which takes a list of HTML and purifies it all
+! Added static member variable $version to HTML Purifier with PHP-compatible
+ version number string.
+- Fixed fatal error thrown by upper-cased language attributes
+- printDefinition.php: added labels, added better clarification
+. HTMLPurifier_Config::create() added, takes mixed variable and converts into
+ a HTMLPurifier_Config object.
+
+1.3.1, released 2006-12-06
+! Added HTMLPurifier.func.php stub for a convenient function to call the library
+- Fixed bug in RemoveInvalidImg code that caused all images to be dropped
+ (thanks to .mario for reporting this)
+. Standardized all attribute handling variables to attr, made it plural
+
+1.3.0, released 2006-11-26
+# Invalid images are now removed, rather than replaced with a dud
+ <img src="" alt="Invalid image" />. Previous behavior can be restored
+ with new directive %Core.RemoveInvalidImg set to false.
+! (X)HTML Strict now supported
+ + Transparently handles inline elements in block context (blockquote)
+! Added GET method to demo for easier validation, added 50kb max input size
+! New directive %HTML.BlockWrapper, for block-ifying inline elements
+! New directive %HTML.Parent, allows you to only allow inline content
+! New directives %HTML.AllowedElements and %HTML.AllowedAttributes to let
+ users narrow the set of allowed tags
+! <li value="4"> and <ul start="2"> now allowed in loose mode
+! New directives %URI.DisableExternalResources and %URI.DisableResources
+! New directive %Attr.DisableURI, which eliminates all hyperlinking
+! New directive %URI.Munge, munges URI so you can use some sort of redirector
+ service to avoid PageRank leaks or warn users that they are exiting your site.
+! Added spiffy new smoketest printDefinition.php, which lets you twiddle with
+ the configuration settings and see how the internal rules are affected.
+! New directive %URI.HostBlacklist for blocking links to bad hosts.
+ xssAttacks.php smoketest updated accordingly.
+- Added missing type to ChildDef_Chameleon
+- Remove Tidy option from demo if there is not Tidy available
+. ChildDef_Required guards against empty tags
+. Lookup table HTMLDefinition->info_flow_elements added
+. Added peace-of-mind variable initialization to Strategy_FixNesting
+. Added HTMLPurifier->info_parent_def, parent child processing made special
+. Added internal documents briefly summarizing future progression of HTML
+. HTMLPurifier_Config->getBatch($namespace) added
+. More lenient casting to bool from string in HTMLPurifier_ConfigSchema
+. Refactored ChildDef classes into their own files
+
+1.2.0, released 2006-11-19
+# ID attributes now disabled by default. New directives:
+ + %HTML.EnableAttrID - restores old behavior by allowing IDs
+ + %Attr.IDPrefix - %Attr.IDBlacklist alternative that munges all user IDs
+ so that they don't collide with your IDs
+ + %Attr.IDPrefixLocal - Same as above, but for when there are multiple
+ instances of user content on the page
+ + Profuse documentation on how to use these available in docs/enduser-id.txt
+! Added MODx plugin <http://modxcms.com/forums/index.php/topic,6604.0.html>
+! Added percent encoding normalization
+! XSS attacks smoketest given facelift
+! Configuration documentation now has table of contents
+! Added %URI.DisableExternal, which prevents links to external websites. You
+ can also use %URI.Host to permit absolute linking to subdomains
+! Non-accessible resources (ex. mailto) blocked from embedded URIs (img src)
+- Type variable in HTMLDefinition was not being set properly, fixed
+- Documentation updated
+ + TODO added request Phalanger
+ + TODO added request Native compression
+ + TODO added request Remove redundant tags
+ + TODO added possible plaintext formatter for HTML Purifier documentation
+ + Updated ConfigDoc TODO
+ + Improved inline comments in AttrDef/Class.php, AttrDef/CSS.php
+ and AttrDef/Host.php
+ + Revamped documentation into HTML, along with misc updates
+- HTMLPurifier_Context doesn't throw a variable reference error if you attempt
+ to retrieve a non-existent variable
+. Switched to purify()-wide Context object registry
+. Refactored unit tests to minimize duplication
+. XSS attack sheet updated
+. configdoc.xml now has xml:space attached to default value nodes
+. Allow configuration directives to permit null values
+. Cleaned up test-cases to remove unnecessary swallowErrors()
+
+1.1.2, released 2006-09-30
+! Add HTMLPurifier.auto.php stub file that configures include_path
+- Documentation updated
+ + INSTALL document rewritten
+ + TODO added semi-lossy conversion
+ + API Doxygen docs' file exclusions updated
+ + Added notes on HTML versus XML attribute whitespace handling
+ + Noted that HTMLPurifier_ChildDef_Custom isn't being used
+ + Noted that config object's definitions are cached versions
+- Fixed lack of attribute parsing in HTMLPurifier_Lexer_PEARSax3
+- ftp:// URIs now have their typecodes checked
+- Hooked up HTMLPurifier_ChildDef_Custom's unit tests (they weren't being run)
+. Line endings standardized throughout project (svn:eol-style standardized)
+. Refactored parseData() to general Lexer class
+. Tester named "HTML Purifier" not "HTMLPurifier"
+
+1.1.1, released 2006-09-24
+! Configuration option to optionally Tidy up output for indentation to make up
+ for dropped whitespace by DOMLex (pretty-printing for the entire application
+ should be done by a page-wide Tidy)
+- Various documentation updates
+- Fixed parse error in configuration documentation script
+- Fixed fatal error in benchmark scripts, slightly augmented
+- As far as possible, whitespace is preserved in-between table children
+- Sample test-settings.php file included
+
+1.1.0, released 2006-09-16
+! Directive documentation generation using XSLT
+! XHTML can now be turned off, output becomes <br>
+- Made URI validator more forgiving: will ignore leading and trailing
+ quotes, apostrophes and less than or greater than signs.
+- Enforce alphanumeric namespace and directive names for configuration.
+- Table child definition made more flexible, will fix up poorly ordered elements
+. Renamed ConfigDef to ConfigSchema
+
+1.0.1, released 2006-09-04
+- Fixed slight bug in DOMLex attribute parsing
+- Fixed rejection of case-insensitive configuration values when there is a
+ set of allowed values. This manifested in %Core.Encoding.
+- Fixed rejection of inline style declarations that had lots of extra
+ space in them. This manifested in TinyMCE.
+
+1.0.0, released 2006-09-01
+! Shorthand CSS properties implemented: font, border, background, list-style
+! Basic color keywords translated into hexadecimal values
+! Table CSS properties implemented
+! Support for charsets other than UTF-8 (defined by iconv)
+! Malformed UTF-8 and non-SGML character detection and cleaning implemented
+- Fixed broken numeric entity conversion
+- API documentation completed
+. (HTML|CSS)Definition de-singleton-ized
+
+1.0.0beta, released 2006-08-16
+! First public release, most functionality implemented. Notable omissions are:
+ + Shorthand CSS properties
+ + Table CSS properties
+ + Deprecated attribute transformations
+
+ vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/README.md b/vendor/ezyang/htmlpurifier/README.md
new file mode 100644
index 000000000..b321f2b69
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/README.md
@@ -0,0 +1,29 @@
+HTML Purifier [![Build Status](https://secure.travis-ci.org/ezyang/htmlpurifier.svg?branch=master)](http://travis-ci.org/ezyang/htmlpurifier)
+=============
+
+HTML Purifier is an HTML filtering solution that uses a unique combination
+of robust whitelists and agressive parsing to ensure that not only are
+XSS attacks thwarted, but the resulting HTML is standards compliant.
+
+HTML Purifier is oriented towards richly formatted documents from
+untrusted sources that require CSS and a full tag-set. This library can
+be configured to accept a more restrictive set of tags, but it won't be
+as efficient as more bare-bones parsers. It will, however, do the job
+right, which may be more important.
+
+Places to go:
+
+* See INSTALL for a quick installation guide
+* See docs/ for developer-oriented documentation, code examples and
+ an in-depth installation guide.
+* See WYSIWYG for information on editors like TinyMCE and FCKeditor
+
+HTML Purifier can be found on the web at: [http://htmlpurifier.org/](http://htmlpurifier.org/)
+
+## Installation
+
+Package available on [Composer](https://packagist.org/packages/ezyang/htmlpurifier).
+
+If you're using Composer to manage dependencies, you can use
+
+ $ composer require "ezyang/htmlpurifier": "dev-master"
diff --git a/vendor/ezyang/htmlpurifier/TODO b/vendor/ezyang/htmlpurifier/TODO
new file mode 100644
index 000000000..1afb33cbf
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/TODO
@@ -0,0 +1,150 @@
+
+TODO List
+
+= KEY ====================
+ # Flagship
+ - Regular
+ ? Maybe I'll Do It
+==========================
+
+If no interest is expressed for a feature that may require a considerable
+amount of effort to implement, it may get endlessly delayed. Do not be
+afraid to cast your vote for the next feature to be implemented!
+
+Things to do as soon as possible:
+
+ - http://htmlpurifier.org/phorum/read.php?3,5560,6307#msg-6307
+ - Think about allowing explicit order of operations hooks for transforms
+ - Fix "<.<" bug (trailing < is removed if not EOD)
+ - Build in better internal state dumps and debugging tools for remote
+ debugging
+ - Allowed/Allowed* have strange interactions when both set
+ ? Transform lone embeds into object tags
+ - Deprecated config options that emit warnings when you set them (with'
+ a way of muting the warning if you really want to)
+ - Make HTML.Trusted work with Output.FlashCompat
+ - HTML.Trusted and HTML.SafeObject have funny interaction; general
+ problem is what to do when a module "supersedes" another
+ (see also tables and basic tables.) This is a little dicier
+ because HTML.SafeObject has some extra functionality that
+ trusted might find useful. See http://htmlpurifier.org/phorum/read.php?3,5762,6100
+
+FUTURE VERSIONS
+---------------
+
+4.9 release [OMG CONFIG PONIES]
+ ! Fix Printer. It's from the old days when we didn't have decent XML classes
+ ! Factor demo.php into a set of Printer classes, and then create a stub
+ file for users here (inside the actual HTML Purifier library)
+ - Fix error handling with form construction
+ - Do encoding validation in Printers, or at least, where user data comes in
+ - Config: Add examples to everything (make built-in which also automatically
+ gives output)
+ - Add "register" field to config schemas to eliminate dependence on
+ naming conventions (try to remember why we ultimately decided on tihs)
+
+5.0 release [HTML 5]
+ # Swap out code to use html5lib tokenizer and tree-builder
+ ! Allow turning off of FixNesting and required attribute insertion
+
+5.1 release [It's All About Trust] (floating)
+ # Implement untrusted, dangerous elements/attributes
+ # Implement IDREF support (harder than it seems, since you cannot have
+ IDREFs to non-existent IDs)
+ - Implement <area> (client and server side image maps are blocking
+ on IDREF support)
+ # Frameset XHTML 1.0 and HTML 4.01 doctypes
+ - Figure out how to simultaneously set %CSS.Trusted and %HTML.Trusted (?)
+
+5.2 release [Error'ed]
+ # Error logging for filtering/cleanup procedures
+ # Additional support for poorly written HTML
+ - Microsoft Word HTML cleaning (i.e. MsoNormal, but research essential!)
+ - Friendly strict handling of <address> (block -> <br>)
+ - XSS-attempt detection--certain errors are flagged XSS-like
+ - Append something to duplicate IDs so they're still usable (impl. note: the
+ dupe detector would also need to detect the suffix as well)
+
+6.0 release [Beyond HTML]
+ # Legit token based CSS parsing (will require revamping almost every
+ AttrDef class). Probably will use CSSTidy
+ # More control over allowed CSS properties using a modularization
+ # IRI support (this includes IDN)
+ - Standardize token armor for all areas of processing
+
+7.0 release [To XML and Beyond]
+ - Extended HTML capabilities based on namespacing and tag transforms (COMPLEX)
+ - Hooks for adding custom processors to custom namespaced tags and
+ attributes, offer default implementation
+ - Lots of documentation and samples
+
+Ongoing
+ - More refactoring to take advantage of PHP5's facilities
+ - Refactor unit tests into lots of test methods
+ - Plugins for major CMSes (COMPLEX)
+ - phpBB
+ - Also, a FAQ for extension writers with HTML Purifier
+
+AutoFormat
+ - Smileys
+ - Syntax highlighting (with GeSHi) with <pre> and possibly <?php
+ - Look at http://drupal.org/project/Modules/category/63 for ideas
+
+Neat feature related
+ ! Support exporting configuration, so users can easily tweak settings
+ in the demo, and then copy-paste into their own setup
+ - Advanced URI filtering schemes (see docs/proposal-new-directives.txt)
+ - Allow scoped="scoped" attribute in <style> tags; may be troublesome
+ because regular CSS has no way of uniquely identifying nodes, so we'd
+ have to generate IDs
+ - Explain how to use HTML Purifier in non-PHP languages / create
+ a simple command line stub (or complicated?)
+ - Fixes for Firefox's inability to handle COL alignment props (Bug 915)
+ - Automatically add non-breaking spaces to empty table cells when
+ empty-cells:show is applied to have compatibility with Internet Explorer
+ - Table of Contents generation (XHTML Compiler might be reusable). May also
+ be out-of-band information.
+ - Full set of color keywords. Also, a way to add onto them without
+ finalizing the configuration object.
+ - Write a var_export and memcached DefinitionCache - Denis
+ - Built-in support for target="_blank" on all external links
+ - Convert RTL/LTR override characters to <bdo> tags, or vice versa on demand.
+ Also, enable disabling of directionality
+ ? Externalize inline CSS to promote clean HTML, proposed by Sander Tekelenburg
+ ? Remove redundant tags, ex. <u><u>Underlined</u></u>. Implementation notes:
+ 1. Analyzing which tags to remove duplicants
+ 2. Ensure attributes are merged into the parent tag
+ 3. Extend the tag exclusion system to specify whether or not the
+ contents should be dropped or not (currently, there's code that could do
+ something like this if it didn't drop the inner text too.)
+ ? Make AutoParagraph also support paragraph-izing double <br> tags, and not
+ just double newlines. This is kind of tough to do in the current framework,
+ though, and might be reasonably approximated by search replacing double <br>s
+ with newlines before running it through HTML Purifier.
+
+Maintenance related (slightly boring)
+ # CHMOD install script for PEAR installs
+ ! Factor out command line parser into its own class, and unit test it
+ - Reduce size of internal data-structures (esp. HTMLDefinition)
+ - Allow merging configurations. Thus,
+ a -> b -> default
+ c -> d -> default
+ becomes
+ a -> b -> c -> d -> default
+ Maybe allow more fine-grained tuning of this behavior. Alternatively,
+ encourage people to use short plist depths before building them up.
+ - Time PHPT tests
+
+ChildDef related (very boring)
+ - Abstract ChildDef_BlockQuote to work with all elements that only
+ allow blocks in them, required or optional
+ - Implement lenient <ruby> child validation
+
+Wontfix
+ - Non-lossy smart alternate character encoding transformations (unless
+ patch provided)
+ - Pretty-printing HTML: users can use Tidy on the output on entire page
+ - Native content compression, whitespace stripping: use gzip if this is
+ really important
+
+ vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/VERSION b/vendor/ezyang/htmlpurifier/VERSION
new file mode 100644
index 000000000..e94f14fa9
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/VERSION
@@ -0,0 +1 @@
+4.9.3 \ No newline at end of file
diff --git a/vendor/ezyang/htmlpurifier/WHATSNEW b/vendor/ezyang/htmlpurifier/WHATSNEW
new file mode 100644
index 000000000..810086f27
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/WHATSNEW
@@ -0,0 +1,13 @@
+HTML Purifier 4.9.x is a maintenance release, collecting a year
+of accumulated bug fixes plus a few new features. New features
+include support for min/max-width/height CSS, and rgba/hsl/hsla
+in color specifications. Major bugfixes include improvements
+in the Serializer cache to avoid chmod'ing directories, better
+entity decoding (we won't accidentally encode entities that occur
+in URLs) and rel="noopener" on links with target attributes,
+to prevent them from overwriting the original frame.
+
+4.9.3 works around an infinite loop bug in PHP 7.1 with the opcode
+cache (and has one other, minor bugfix, avoiding using autoloading
+when testing for DOMDocument presence). If these bugs do not
+affect you, you do not need to upgrade.
diff --git a/vendor/ezyang/htmlpurifier/WYSIWYG b/vendor/ezyang/htmlpurifier/WYSIWYG
new file mode 100644
index 000000000..c518aacdd
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/WYSIWYG
@@ -0,0 +1,20 @@
+
+WYSIWYG - What You See Is What You Get
+ HTML Purifier: A Pretty Good Fit for TinyMCE and FCKeditor
+
+Javascript-based WYSIWYG editors, simply stated, are quite amazing. But I've
+always been wary about using them due to security issues: they handle the
+client-side magic, but once you've been served a piping hot load of unfiltered
+HTML, what should be done then? In some situations, you can serve it uncleaned,
+since you only offer these facilities to trusted(?) authors.
+
+Unfortunantely, for blog comments and anonymous input, BBCode, Textile and
+other markup languages still reign supreme. Put simply: filtering HTML is
+hard work, and these WYSIWYG authors don't offer anything to alleviate that
+trouble. Therein lies the solution:
+
+HTML Purifier is perfect for filtering pure-HTML input from WYSIWYG editors.
+
+Enough said.
+
+ vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/composer.json b/vendor/ezyang/htmlpurifier/composer.json
new file mode 100644
index 000000000..80fee3db3
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/composer.json
@@ -0,0 +1,25 @@
+{
+ "name": "ezyang/htmlpurifier",
+ "description": "Standards compliant HTML filter written in PHP",
+ "type": "library",
+ "keywords": ["html"],
+ "homepage": "http://htmlpurifier.org/",
+ "license": "LGPL",
+ "authors": [
+ {
+ "name": "Edward Z. Yang",
+ "email": "admin@htmlpurifier.org",
+ "homepage": "http://ezyang.com"
+ }
+ ],
+ "require": {
+ "php": ">=5.2"
+ },
+ "require-dev": {
+ "simpletest/simpletest": "^1.1"
+ },
+ "autoload": {
+ "psr-0": { "HTMLPurifier": "library/" },
+ "files": ["library/HTMLPurifier.composer.php"]
+ }
+}
diff --git a/vendor/ezyang/htmlpurifier/extras/ConfigDoc/HTMLXSLTProcessor.php b/vendor/ezyang/htmlpurifier/extras/ConfigDoc/HTMLXSLTProcessor.php
new file mode 100644
index 000000000..1cfec5d76
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/extras/ConfigDoc/HTMLXSLTProcessor.php
@@ -0,0 +1,91 @@
+<?php
+
+/**
+ * Decorator/extender XSLT processor specifically for HTML documents.
+ */
+class ConfigDoc_HTMLXSLTProcessor
+{
+
+ /**
+ * Instance of XSLTProcessor
+ */
+ protected $xsltProcessor;
+
+ public function __construct($proc = false)
+ {
+ if ($proc === false) $proc = new XSLTProcessor();
+ $this->xsltProcessor = $proc;
+ }
+
+ /**
+ * @note Allows a string $xsl filename to be passed
+ */
+ public function importStylesheet($xsl)
+ {
+ if (is_string($xsl)) {
+ $xsl_file = $xsl;
+ $xsl = new DOMDocument();
+ $xsl->load($xsl_file);
+ }
+ return $this->xsltProcessor->importStylesheet($xsl);
+ }
+
+ /**
+ * Transforms an XML file into compatible XHTML based on the stylesheet
+ * @param $xml XML DOM tree, or string filename
+ * @return string HTML output
+ * @todo Rename to transformToXHTML, as transformToHTML is misleading
+ */
+ public function transformToHTML($xml)
+ {
+ if (is_string($xml)) {
+ $dom = new DOMDocument();
+ $dom->load($xml);
+ } else {
+ $dom = $xml;
+ }
+ $out = $this->xsltProcessor->transformToXML($dom);
+
+ // fudges for HTML backwards compatibility
+ // assumes that document is XHTML
+ $out = str_replace('/>', ' />', $out); // <br /> not <br/>
+ $out = str_replace(' xmlns=""', '', $out); // rm unnecessary xmlns
+
+ if (class_exists('Tidy')) {
+ // cleanup output
+ $config = array(
+ 'indent' => true,
+ 'output-xhtml' => true,
+ 'wrap' => 80
+ );
+ $tidy = new Tidy;
+ $tidy->parseString($out, $config, 'utf8');
+ $tidy->cleanRepair();
+ $out = (string) $tidy;
+ }
+
+ return $out;
+ }
+
+ /**
+ * Bulk sets parameters for the XSL stylesheet
+ * @param array $options Associative array of options to set
+ */
+ public function setParameters($options)
+ {
+ foreach ($options as $name => $value) {
+ $this->xsltProcessor->setParameter('', $name, $value);
+ }
+ }
+
+ /**
+ * Forward any other calls to the XSLT processor
+ */
+ public function __call($name, $arguments)
+ {
+ call_user_func_array(array($this->xsltProcessor, $name), $arguments);
+ }
+
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/extras/FSTools.php b/vendor/ezyang/htmlpurifier/extras/FSTools.php
new file mode 100644
index 000000000..ce0076316
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/extras/FSTools.php
@@ -0,0 +1,164 @@
+<?php
+
+/**
+ * Filesystem tools not provided by default; can recursively create, copy
+ * and delete folders. Some template methods are provided for extensibility.
+ *
+ * @note This class must be instantiated to be used, although it does
+ * not maintain state.
+ */
+class FSTools
+{
+
+ private static $singleton;
+
+ /**
+ * Returns a global instance of FSTools
+ */
+ public static function singleton()
+ {
+ if (empty(FSTools::$singleton)) FSTools::$singleton = new FSTools();
+ return FSTools::$singleton;
+ }
+
+ /**
+ * Sets our global singleton to something else; useful for overloading
+ * functions.
+ */
+ public static function setSingleton($singleton)
+ {
+ FSTools::$singleton = $singleton;
+ }
+
+ /**
+ * Recursively creates a directory
+ * @param string $folder Name of folder to create
+ * @note Adapted from the PHP manual comment 76612
+ */
+ public function mkdirr($folder)
+ {
+ $folders = preg_split("#[\\\\/]#", $folder);
+ $base = '';
+ for($i = 0, $c = count($folders); $i < $c; $i++) {
+ if(empty($folders[$i])) {
+ if (!$i) {
+ // special case for root level
+ $base .= DIRECTORY_SEPARATOR;
+ }
+ continue;
+ }
+ $base .= $folders[$i];
+ if(!is_dir($base)){
+ $this->mkdir($base);
+ }
+ $base .= DIRECTORY_SEPARATOR;
+ }
+ }
+
+ /**
+ * Copy a file, or recursively copy a folder and its contents; modified
+ * so that copied files, if PHP, have includes removed
+ * @note Adapted from http://aidanlister.com/repos/v/function.copyr.php
+ */
+ public function copyr($source, $dest)
+ {
+ // Simple copy for a file
+ if (is_file($source)) {
+ return $this->copy($source, $dest);
+ }
+ // Make destination directory
+ if (!is_dir($dest)) {
+ $this->mkdir($dest);
+ }
+ // Loop through the folder
+ $dir = $this->dir($source);
+ while ( false !== ($entry = $dir->read()) ) {
+ // Skip pointers
+ if ($entry == '.' || $entry == '..') {
+ continue;
+ }
+ if (!$this->copyable($entry)) {
+ continue;
+ }
+ // Deep copy directories
+ if ($dest !== "$source/$entry") {
+ $this->copyr("$source/$entry", "$dest/$entry");
+ }
+ }
+ // Clean up
+ $dir->close();
+ return true;
+ }
+
+ /**
+ * Overloadable function that tests a filename for copyability. By
+ * default, everything should be copied; you can restrict things to
+ * ignore hidden files, unreadable files, etc. This function
+ * applies to copyr().
+ */
+ public function copyable($file)
+ {
+ return true;
+ }
+
+ /**
+ * Delete a file, or a folder and its contents
+ * @note Adapted from http://aidanlister.com/repos/v/function.rmdirr.php
+ */
+ public function rmdirr($dirname)
+ {
+ // Sanity check
+ if (!$this->file_exists($dirname)) {
+ return false;
+ }
+
+ // Simple delete for a file
+ if ($this->is_file($dirname) || $this->is_link($dirname)) {
+ return $this->unlink($dirname);
+ }
+
+ // Loop through the folder
+ $dir = $this->dir($dirname);
+ while (false !== $entry = $dir->read()) {
+ // Skip pointers
+ if ($entry == '.' || $entry == '..') {
+ continue;
+ }
+ // Recurse
+ $this->rmdirr($dirname . DIRECTORY_SEPARATOR . $entry);
+ }
+
+ // Clean up
+ $dir->close();
+ return $this->rmdir($dirname);
+ }
+
+ /**
+ * Recursively globs a directory.
+ */
+ public function globr($dir, $pattern, $flags = NULL)
+ {
+ $files = $this->glob("$dir/$pattern", $flags);
+ if ($files === false) $files = array();
+ $sub_dirs = $this->glob("$dir/*", GLOB_ONLYDIR);
+ if ($sub_dirs === false) $sub_dirs = array();
+ foreach ($sub_dirs as $sub_dir) {
+ $sub_files = $this->globr($sub_dir, $pattern, $flags);
+ $files = array_merge($files, $sub_files);
+ }
+ return $files;
+ }
+
+ /**
+ * Allows for PHP functions to be called and be stubbed.
+ * @warning This function will not work for functions that need
+ * to pass references; manually define a stub function for those.
+ */
+ public function __call($name, $args)
+ {
+ return call_user_func_array($name, $args);
+ }
+
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/extras/FSTools/File.php b/vendor/ezyang/htmlpurifier/extras/FSTools/File.php
new file mode 100644
index 000000000..6453a7a45
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/extras/FSTools/File.php
@@ -0,0 +1,141 @@
+<?php
+
+/**
+ * Represents a file in the filesystem
+ *
+ * @warning Be sure to distinguish between get() and write() versus
+ * read() and put(), the former operates on the entire file, while
+ * the latter operates on a handle.
+ */
+class FSTools_File
+{
+
+ /** Filename of file this object represents */
+ protected $name;
+
+ /** Handle for the file */
+ protected $handle = false;
+
+ /** Instance of FSTools for interfacing with filesystem */
+ protected $fs;
+
+ /**
+ * Filename of file you wish to instantiate.
+ * @note This file need not exist
+ */
+ public function __construct($name, $fs = false)
+ {
+ $this->name = $name;
+ $this->fs = $fs ? $fs : FSTools::singleton();
+ }
+
+ /** Returns the filename of the file. */
+ public function getName() {return $this->name;}
+
+ /** Returns directory of the file without trailing slash */
+ public function getDirectory() {return $this->fs->dirname($this->name);}
+
+ /**
+ * Retrieves the contents of a file
+ * @todo Throw an exception if file doesn't exist
+ */
+ public function get()
+ {
+ return $this->fs->file_get_contents($this->name);
+ }
+
+ /** Writes contents to a file, creates new file if necessary */
+ public function write($contents)
+ {
+ return $this->fs->file_put_contents($this->name, $contents);
+ }
+
+ /** Deletes the file */
+ public function delete()
+ {
+ return $this->fs->unlink($this->name);
+ }
+
+ /** Returns true if file exists and is a file. */
+ public function exists()
+ {
+ return $this->fs->is_file($this->name);
+ }
+
+ /** Returns last file modification time */
+ public function getMTime()
+ {
+ return $this->fs->filemtime($this->name);
+ }
+
+ /**
+ * Chmod a file
+ * @note We ignore errors because of some weird owner trickery due
+ * to SVN duality
+ */
+ public function chmod($octal_code)
+ {
+ return @$this->fs->chmod($this->name, $octal_code);
+ }
+
+ /** Opens file's handle */
+ public function open($mode)
+ {
+ if ($this->handle) $this->close();
+ $this->handle = $this->fs->fopen($this->name, $mode);
+ return true;
+ }
+
+ /** Closes file's handle */
+ public function close()
+ {
+ if (!$this->handle) return false;
+ $status = $this->fs->fclose($this->handle);
+ $this->handle = false;
+ return $status;
+ }
+
+ /** Retrieves a line from an open file, with optional max length $length */
+ public function getLine($length = null)
+ {
+ if (!$this->handle) $this->open('r');
+ if ($length === null) return $this->fs->fgets($this->handle);
+ else return $this->fs->fgets($this->handle, $length);
+ }
+
+ /** Retrieves a character from an open file */
+ public function getChar()
+ {
+ if (!$this->handle) $this->open('r');
+ return $this->fs->fgetc($this->handle);
+ }
+
+ /** Retrieves an $length bytes of data from an open data */
+ public function read($length)
+ {
+ if (!$this->handle) $this->open('r');
+ return $this->fs->fread($this->handle, $length);
+ }
+
+ /** Writes to an open file */
+ public function put($string)
+ {
+ if (!$this->handle) $this->open('a');
+ return $this->fs->fwrite($this->handle, $string);
+ }
+
+ /** Returns TRUE if the end of the file has been reached */
+ public function eof()
+ {
+ if (!$this->handle) return true;
+ return $this->fs->feof($this->handle);
+ }
+
+ public function __destruct()
+ {
+ if ($this->handle) $this->close();
+ }
+
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/extras/HTMLPurifierExtras.auto.php b/vendor/ezyang/htmlpurifier/extras/HTMLPurifierExtras.auto.php
new file mode 100644
index 000000000..4016d8afd
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/extras/HTMLPurifierExtras.auto.php
@@ -0,0 +1,11 @@
+<?php
+
+/**
+ * This is a stub include that automatically configures the include path.
+ */
+
+set_include_path(dirname(__FILE__) . PATH_SEPARATOR . get_include_path() );
+require_once 'HTMLPurifierExtras.php';
+require_once 'HTMLPurifierExtras.autoload.php';
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/extras/HTMLPurifierExtras.autoload.php b/vendor/ezyang/htmlpurifier/extras/HTMLPurifierExtras.autoload.php
new file mode 100644
index 000000000..de4a8aaaf
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/extras/HTMLPurifierExtras.autoload.php
@@ -0,0 +1,26 @@
+<?php
+
+/**
+ * @file
+ * Convenience file that registers autoload handler for HTML Purifier.
+ *
+ * @warning
+ * This autoloader does not contain the compatibility code seen in
+ * HTMLPurifier_Bootstrap; the user is expected to make any necessary
+ * changes to use this library.
+ */
+
+if (function_exists('spl_autoload_register')) {
+ spl_autoload_register(array('HTMLPurifierExtras', 'autoload'));
+ if (function_exists('__autoload')) {
+ // Be polite and ensure that userland autoload gets retained
+ spl_autoload_register('__autoload');
+ }
+} elseif (!function_exists('__autoload')) {
+ function __autoload($class)
+ {
+ return HTMLPurifierExtras::autoload($class);
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/extras/HTMLPurifierExtras.php b/vendor/ezyang/htmlpurifier/extras/HTMLPurifierExtras.php
new file mode 100644
index 000000000..35c2ca7e7
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/extras/HTMLPurifierExtras.php
@@ -0,0 +1,31 @@
+<?php
+
+/**
+ * Meta-class for HTML Purifier's extra class hierarchies, similar to
+ * HTMLPurifier_Bootstrap.
+ */
+class HTMLPurifierExtras
+{
+
+ public static function autoload($class)
+ {
+ $path = HTMLPurifierExtras::getPath($class);
+ if (!$path) return false;
+ require $path;
+ return true;
+ }
+
+ public static function getPath($class)
+ {
+ if (
+ strncmp('FSTools', $class, 7) !== 0 &&
+ strncmp('ConfigDoc', $class, 9) !== 0
+ ) return false;
+ // Custom implementations can go here
+ // Standard implementation:
+ return str_replace('_', '/', $class) . '.php';
+ }
+
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/extras/README b/vendor/ezyang/htmlpurifier/extras/README
new file mode 100644
index 000000000..4bfece79e
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/extras/README
@@ -0,0 +1,32 @@
+
+HTML Purifier Extras
+ The Method Behind The Madness!
+
+The extras/ folder in HTML Purifier contains--you guessed it--extra things
+for HTML Purifier. Specifically, these are two extra libraries called
+FSTools and ConfigSchema. They're extra for a reason: you don't need them
+if you're using HTML Purifier for normal usage: filtering HTML. However,
+if you're a developer, and would like to test HTML Purifier, or need to
+use one of HTML Purifier's maintenance scripts, chances are they'll need
+these libraries. Who knows: maybe you'll find them useful too!
+
+Here are the libraries:
+
+
+FSTools
+-------
+
+Short for File System Tools, this is a poor-man's object-oriented wrapper for
+the filesystem. It currently consists of two classes:
+
+- FSTools: This is a singleton that contains a manner of useful functions
+ such as recursive glob, directory removal, etc, as well as the ability
+ to call arbitrary native PHP functions through it like $FS->fopen(...).
+ This makes it a lot simpler to mock these filesystem calls for unit testing.
+
+- FSTools_File: This object represents a single file, and has almost any
+ method imaginable one would need.
+
+Check the files themselves for more information.
+
+ vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier.auto.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier.auto.php
index 1960c399f..1960c399f 100644
--- a/library/HTMLPurifier.auto.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier.auto.php
diff --git a/library/HTMLPurifier.autoload.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier.autoload.php
index c3ea67e81..c3ea67e81 100644
--- a/library/HTMLPurifier.autoload.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier.autoload.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier.composer.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier.composer.php
new file mode 100644
index 000000000..52acc56b0
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier.composer.php
@@ -0,0 +1,4 @@
+<?php
+if (!defined('HTMLPURIFIER_PREFIX')) {
+ define('HTMLPURIFIER_PREFIX', dirname(__FILE__));
+}
diff --git a/library/HTMLPurifier.func.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier.func.php
index 64b140bec..64b140bec 100644
--- a/library/HTMLPurifier.func.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier.func.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier.includes.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier.includes.php
new file mode 100644
index 000000000..e8bce5c85
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier.includes.php
@@ -0,0 +1,234 @@
+<?php
+
+/**
+ * @file
+ * This file was auto-generated by generate-includes.php and includes all of
+ * the core files required by HTML Purifier. Use this if performance is a
+ * primary concern and you are using an opcode cache. PLEASE DO NOT EDIT THIS
+ * FILE, changes will be overwritten the next time the script is run.
+ *
+ * @version 4.9.3
+ *
+ * @warning
+ * You must *not* include any other HTML Purifier files before this file,
+ * because 'require' not 'require_once' is used.
+ *
+ * @warning
+ * This file requires that the include path contains the HTML Purifier
+ * library directory; this is not auto-set.
+ */
+
+require 'HTMLPurifier.php';
+require 'HTMLPurifier/Arborize.php';
+require 'HTMLPurifier/AttrCollections.php';
+require 'HTMLPurifier/AttrDef.php';
+require 'HTMLPurifier/AttrTransform.php';
+require 'HTMLPurifier/AttrTypes.php';
+require 'HTMLPurifier/AttrValidator.php';
+require 'HTMLPurifier/Bootstrap.php';
+require 'HTMLPurifier/Definition.php';
+require 'HTMLPurifier/CSSDefinition.php';
+require 'HTMLPurifier/ChildDef.php';
+require 'HTMLPurifier/Config.php';
+require 'HTMLPurifier/ConfigSchema.php';
+require 'HTMLPurifier/ContentSets.php';
+require 'HTMLPurifier/Context.php';
+require 'HTMLPurifier/DefinitionCache.php';
+require 'HTMLPurifier/DefinitionCacheFactory.php';
+require 'HTMLPurifier/Doctype.php';
+require 'HTMLPurifier/DoctypeRegistry.php';
+require 'HTMLPurifier/ElementDef.php';
+require 'HTMLPurifier/Encoder.php';
+require 'HTMLPurifier/EntityLookup.php';
+require 'HTMLPurifier/EntityParser.php';
+require 'HTMLPurifier/ErrorCollector.php';
+require 'HTMLPurifier/ErrorStruct.php';
+require 'HTMLPurifier/Exception.php';
+require 'HTMLPurifier/Filter.php';
+require 'HTMLPurifier/Generator.php';
+require 'HTMLPurifier/HTMLDefinition.php';
+require 'HTMLPurifier/HTMLModule.php';
+require 'HTMLPurifier/HTMLModuleManager.php';
+require 'HTMLPurifier/IDAccumulator.php';
+require 'HTMLPurifier/Injector.php';
+require 'HTMLPurifier/Language.php';
+require 'HTMLPurifier/LanguageFactory.php';
+require 'HTMLPurifier/Length.php';
+require 'HTMLPurifier/Lexer.php';
+require 'HTMLPurifier/Node.php';
+require 'HTMLPurifier/PercentEncoder.php';
+require 'HTMLPurifier/PropertyList.php';
+require 'HTMLPurifier/PropertyListIterator.php';
+require 'HTMLPurifier/Queue.php';
+require 'HTMLPurifier/Strategy.php';
+require 'HTMLPurifier/StringHash.php';
+require 'HTMLPurifier/StringHashParser.php';
+require 'HTMLPurifier/TagTransform.php';
+require 'HTMLPurifier/Token.php';
+require 'HTMLPurifier/TokenFactory.php';
+require 'HTMLPurifier/URI.php';
+require 'HTMLPurifier/URIDefinition.php';
+require 'HTMLPurifier/URIFilter.php';
+require 'HTMLPurifier/URIParser.php';
+require 'HTMLPurifier/URIScheme.php';
+require 'HTMLPurifier/URISchemeRegistry.php';
+require 'HTMLPurifier/UnitConverter.php';
+require 'HTMLPurifier/VarParser.php';
+require 'HTMLPurifier/VarParserException.php';
+require 'HTMLPurifier/Zipper.php';
+require 'HTMLPurifier/AttrDef/CSS.php';
+require 'HTMLPurifier/AttrDef/Clone.php';
+require 'HTMLPurifier/AttrDef/Enum.php';
+require 'HTMLPurifier/AttrDef/Integer.php';
+require 'HTMLPurifier/AttrDef/Lang.php';
+require 'HTMLPurifier/AttrDef/Switch.php';
+require 'HTMLPurifier/AttrDef/Text.php';
+require 'HTMLPurifier/AttrDef/URI.php';
+require 'HTMLPurifier/AttrDef/CSS/Number.php';
+require 'HTMLPurifier/AttrDef/CSS/AlphaValue.php';
+require 'HTMLPurifier/AttrDef/CSS/Background.php';
+require 'HTMLPurifier/AttrDef/CSS/BackgroundPosition.php';
+require 'HTMLPurifier/AttrDef/CSS/Border.php';
+require 'HTMLPurifier/AttrDef/CSS/Color.php';
+require 'HTMLPurifier/AttrDef/CSS/Composite.php';
+require 'HTMLPurifier/AttrDef/CSS/DenyElementDecorator.php';
+require 'HTMLPurifier/AttrDef/CSS/Filter.php';
+require 'HTMLPurifier/AttrDef/CSS/Font.php';
+require 'HTMLPurifier/AttrDef/CSS/FontFamily.php';
+require 'HTMLPurifier/AttrDef/CSS/Ident.php';
+require 'HTMLPurifier/AttrDef/CSS/ImportantDecorator.php';
+require 'HTMLPurifier/AttrDef/CSS/Length.php';
+require 'HTMLPurifier/AttrDef/CSS/ListStyle.php';
+require 'HTMLPurifier/AttrDef/CSS/Multiple.php';
+require 'HTMLPurifier/AttrDef/CSS/Percentage.php';
+require 'HTMLPurifier/AttrDef/CSS/TextDecoration.php';
+require 'HTMLPurifier/AttrDef/CSS/URI.php';
+require 'HTMLPurifier/AttrDef/HTML/Bool.php';
+require 'HTMLPurifier/AttrDef/HTML/Nmtokens.php';
+require 'HTMLPurifier/AttrDef/HTML/Class.php';
+require 'HTMLPurifier/AttrDef/HTML/Color.php';
+require 'HTMLPurifier/AttrDef/HTML/FrameTarget.php';
+require 'HTMLPurifier/AttrDef/HTML/ID.php';
+require 'HTMLPurifier/AttrDef/HTML/Pixels.php';
+require 'HTMLPurifier/AttrDef/HTML/Length.php';
+require 'HTMLPurifier/AttrDef/HTML/LinkTypes.php';
+require 'HTMLPurifier/AttrDef/HTML/MultiLength.php';
+require 'HTMLPurifier/AttrDef/URI/Email.php';
+require 'HTMLPurifier/AttrDef/URI/Host.php';
+require 'HTMLPurifier/AttrDef/URI/IPv4.php';
+require 'HTMLPurifier/AttrDef/URI/IPv6.php';
+require 'HTMLPurifier/AttrDef/URI/Email/SimpleCheck.php';
+require 'HTMLPurifier/AttrTransform/Background.php';
+require 'HTMLPurifier/AttrTransform/BdoDir.php';
+require 'HTMLPurifier/AttrTransform/BgColor.php';
+require 'HTMLPurifier/AttrTransform/BoolToCSS.php';
+require 'HTMLPurifier/AttrTransform/Border.php';
+require 'HTMLPurifier/AttrTransform/EnumToCSS.php';
+require 'HTMLPurifier/AttrTransform/ImgRequired.php';
+require 'HTMLPurifier/AttrTransform/ImgSpace.php';
+require 'HTMLPurifier/AttrTransform/Input.php';
+require 'HTMLPurifier/AttrTransform/Lang.php';
+require 'HTMLPurifier/AttrTransform/Length.php';
+require 'HTMLPurifier/AttrTransform/Name.php';
+require 'HTMLPurifier/AttrTransform/NameSync.php';
+require 'HTMLPurifier/AttrTransform/Nofollow.php';
+require 'HTMLPurifier/AttrTransform/SafeEmbed.php';
+require 'HTMLPurifier/AttrTransform/SafeObject.php';
+require 'HTMLPurifier/AttrTransform/SafeParam.php';
+require 'HTMLPurifier/AttrTransform/ScriptRequired.php';
+require 'HTMLPurifier/AttrTransform/TargetBlank.php';
+require 'HTMLPurifier/AttrTransform/TargetNoopener.php';
+require 'HTMLPurifier/AttrTransform/TargetNoreferrer.php';
+require 'HTMLPurifier/AttrTransform/Textarea.php';
+require 'HTMLPurifier/ChildDef/Chameleon.php';
+require 'HTMLPurifier/ChildDef/Custom.php';
+require 'HTMLPurifier/ChildDef/Empty.php';
+require 'HTMLPurifier/ChildDef/List.php';
+require 'HTMLPurifier/ChildDef/Required.php';
+require 'HTMLPurifier/ChildDef/Optional.php';
+require 'HTMLPurifier/ChildDef/StrictBlockquote.php';
+require 'HTMLPurifier/ChildDef/Table.php';
+require 'HTMLPurifier/DefinitionCache/Decorator.php';
+require 'HTMLPurifier/DefinitionCache/Null.php';
+require 'HTMLPurifier/DefinitionCache/Serializer.php';
+require 'HTMLPurifier/DefinitionCache/Decorator/Cleanup.php';
+require 'HTMLPurifier/DefinitionCache/Decorator/Memory.php';
+require 'HTMLPurifier/HTMLModule/Bdo.php';
+require 'HTMLPurifier/HTMLModule/CommonAttributes.php';
+require 'HTMLPurifier/HTMLModule/Edit.php';
+require 'HTMLPurifier/HTMLModule/Forms.php';
+require 'HTMLPurifier/HTMLModule/Hypertext.php';
+require 'HTMLPurifier/HTMLModule/Iframe.php';
+require 'HTMLPurifier/HTMLModule/Image.php';
+require 'HTMLPurifier/HTMLModule/Legacy.php';
+require 'HTMLPurifier/HTMLModule/List.php';
+require 'HTMLPurifier/HTMLModule/Name.php';
+require 'HTMLPurifier/HTMLModule/Nofollow.php';
+require 'HTMLPurifier/HTMLModule/NonXMLCommonAttributes.php';
+require 'HTMLPurifier/HTMLModule/Object.php';
+require 'HTMLPurifier/HTMLModule/Presentation.php';
+require 'HTMLPurifier/HTMLModule/Proprietary.php';
+require 'HTMLPurifier/HTMLModule/Ruby.php';
+require 'HTMLPurifier/HTMLModule/SafeEmbed.php';
+require 'HTMLPurifier/HTMLModule/SafeObject.php';
+require 'HTMLPurifier/HTMLModule/SafeScripting.php';
+require 'HTMLPurifier/HTMLModule/Scripting.php';
+require 'HTMLPurifier/HTMLModule/StyleAttribute.php';
+require 'HTMLPurifier/HTMLModule/Tables.php';
+require 'HTMLPurifier/HTMLModule/Target.php';
+require 'HTMLPurifier/HTMLModule/TargetBlank.php';
+require 'HTMLPurifier/HTMLModule/TargetNoopener.php';
+require 'HTMLPurifier/HTMLModule/TargetNoreferrer.php';
+require 'HTMLPurifier/HTMLModule/Text.php';
+require 'HTMLPurifier/HTMLModule/Tidy.php';
+require 'HTMLPurifier/HTMLModule/XMLCommonAttributes.php';
+require 'HTMLPurifier/HTMLModule/Tidy/Name.php';
+require 'HTMLPurifier/HTMLModule/Tidy/Proprietary.php';
+require 'HTMLPurifier/HTMLModule/Tidy/XHTMLAndHTML4.php';
+require 'HTMLPurifier/HTMLModule/Tidy/Strict.php';
+require 'HTMLPurifier/HTMLModule/Tidy/Transitional.php';
+require 'HTMLPurifier/HTMLModule/Tidy/XHTML.php';
+require 'HTMLPurifier/Injector/AutoParagraph.php';
+require 'HTMLPurifier/Injector/DisplayLinkURI.php';
+require 'HTMLPurifier/Injector/Linkify.php';
+require 'HTMLPurifier/Injector/PurifierLinkify.php';
+require 'HTMLPurifier/Injector/RemoveEmpty.php';
+require 'HTMLPurifier/Injector/RemoveSpansWithoutAttributes.php';
+require 'HTMLPurifier/Injector/SafeObject.php';
+require 'HTMLPurifier/Lexer/DOMLex.php';
+require 'HTMLPurifier/Lexer/DirectLex.php';
+require 'HTMLPurifier/Node/Comment.php';
+require 'HTMLPurifier/Node/Element.php';
+require 'HTMLPurifier/Node/Text.php';
+require 'HTMLPurifier/Strategy/Composite.php';
+require 'HTMLPurifier/Strategy/Core.php';
+require 'HTMLPurifier/Strategy/FixNesting.php';
+require 'HTMLPurifier/Strategy/MakeWellFormed.php';
+require 'HTMLPurifier/Strategy/RemoveForeignElements.php';
+require 'HTMLPurifier/Strategy/ValidateAttributes.php';
+require 'HTMLPurifier/TagTransform/Font.php';
+require 'HTMLPurifier/TagTransform/Simple.php';
+require 'HTMLPurifier/Token/Comment.php';
+require 'HTMLPurifier/Token/Tag.php';
+require 'HTMLPurifier/Token/Empty.php';
+require 'HTMLPurifier/Token/End.php';
+require 'HTMLPurifier/Token/Start.php';
+require 'HTMLPurifier/Token/Text.php';
+require 'HTMLPurifier/URIFilter/DisableExternal.php';
+require 'HTMLPurifier/URIFilter/DisableExternalResources.php';
+require 'HTMLPurifier/URIFilter/DisableResources.php';
+require 'HTMLPurifier/URIFilter/HostBlacklist.php';
+require 'HTMLPurifier/URIFilter/MakeAbsolute.php';
+require 'HTMLPurifier/URIFilter/Munge.php';
+require 'HTMLPurifier/URIFilter/SafeIframe.php';
+require 'HTMLPurifier/URIScheme/data.php';
+require 'HTMLPurifier/URIScheme/file.php';
+require 'HTMLPurifier/URIScheme/ftp.php';
+require 'HTMLPurifier/URIScheme/http.php';
+require 'HTMLPurifier/URIScheme/https.php';
+require 'HTMLPurifier/URIScheme/mailto.php';
+require 'HTMLPurifier/URIScheme/news.php';
+require 'HTMLPurifier/URIScheme/nntp.php';
+require 'HTMLPurifier/URIScheme/tel.php';
+require 'HTMLPurifier/VarParser/Flexible.php';
+require 'HTMLPurifier/VarParser/Native.php';
diff --git a/library/HTMLPurifier.kses.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier.kses.php
index 752290077..752290077 100644
--- a/library/HTMLPurifier.kses.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier.kses.php
diff --git a/library/HTMLPurifier.path.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier.path.php
index 39b1b6531..39b1b6531 100644
--- a/library/HTMLPurifier.path.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier.path.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier.php
new file mode 100644
index 000000000..b4605ebc6
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier.php
@@ -0,0 +1,292 @@
+<?php
+
+/*! @mainpage
+ *
+ * HTML Purifier is an HTML filter that will take an arbitrary snippet of
+ * HTML and rigorously test, validate and filter it into a version that
+ * is safe for output onto webpages. It achieves this by:
+ *
+ * -# Lexing (parsing into tokens) the document,
+ * -# Executing various strategies on the tokens:
+ * -# Removing all elements not in the whitelist,
+ * -# Making the tokens well-formed,
+ * -# Fixing the nesting of the nodes, and
+ * -# Validating attributes of the nodes; and
+ * -# Generating HTML from the purified tokens.
+ *
+ * However, most users will only need to interface with the HTMLPurifier
+ * and HTMLPurifier_Config.
+ */
+
+/*
+ HTML Purifier 4.9.3 - Standards Compliant HTML Filtering
+ Copyright (C) 2006-2008 Edward Z. Yang
+
+ This library is free software; you can redistribute it and/or
+ modify it under the terms of the GNU Lesser General Public
+ License as published by the Free Software Foundation; either
+ version 2.1 of the License, or (at your option) any later version.
+
+ This library 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
+ Lesser General Public License for more details.
+
+ You should have received a copy of the GNU Lesser General Public
+ License along with this library; if not, write to the Free Software
+ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
+ */
+
+/**
+ * Facade that coordinates HTML Purifier's subsystems in order to purify HTML.
+ *
+ * @note There are several points in which configuration can be specified
+ * for HTML Purifier. The precedence of these (from lowest to
+ * highest) is as follows:
+ * -# Instance: new HTMLPurifier($config)
+ * -# Invocation: purify($html, $config)
+ * These configurations are entirely independent of each other and
+ * are *not* merged (this behavior may change in the future).
+ *
+ * @todo We need an easier way to inject strategies using the configuration
+ * object.
+ */
+class HTMLPurifier
+{
+
+ /**
+ * Version of HTML Purifier.
+ * @type string
+ */
+ public $version = '4.9.3';
+
+ /**
+ * Constant with version of HTML Purifier.
+ */
+ const VERSION = '4.9.3';
+
+ /**
+ * Global configuration object.
+ * @type HTMLPurifier_Config
+ */
+ public $config;
+
+ /**
+ * Array of extra filter objects to run on HTML,
+ * for backwards compatibility.
+ * @type HTMLPurifier_Filter[]
+ */
+ private $filters = array();
+
+ /**
+ * Single instance of HTML Purifier.
+ * @type HTMLPurifier
+ */
+ private static $instance;
+
+ /**
+ * @type HTMLPurifier_Strategy_Core
+ */
+ protected $strategy;
+
+ /**
+ * @type HTMLPurifier_Generator
+ */
+ protected $generator;
+
+ /**
+ * Resultant context of last run purification.
+ * Is an array of contexts if the last called method was purifyArray().
+ * @type HTMLPurifier_Context
+ */
+ public $context;
+
+ /**
+ * Initializes the purifier.
+ *
+ * @param HTMLPurifier_Config|mixed $config Optional HTMLPurifier_Config object
+ * for all instances of the purifier, if omitted, a default
+ * configuration is supplied (which can be overridden on a
+ * per-use basis).
+ * The parameter can also be any type that
+ * HTMLPurifier_Config::create() supports.
+ */
+ public function __construct($config = null)
+ {
+ $this->config = HTMLPurifier_Config::create($config);
+ $this->strategy = new HTMLPurifier_Strategy_Core();
+ }
+
+ /**
+ * Adds a filter to process the output. First come first serve
+ *
+ * @param HTMLPurifier_Filter $filter HTMLPurifier_Filter object
+ */
+ public function addFilter($filter)
+ {
+ trigger_error(
+ 'HTMLPurifier->addFilter() is deprecated, use configuration directives' .
+ ' in the Filter namespace or Filter.Custom',
+ E_USER_WARNING
+ );
+ $this->filters[] = $filter;
+ }
+
+ /**
+ * Filters an HTML snippet/document to be XSS-free and standards-compliant.
+ *
+ * @param string $html String of HTML to purify
+ * @param HTMLPurifier_Config $config Config object for this operation,
+ * if omitted, defaults to the config object specified during this
+ * object's construction. The parameter can also be any type
+ * that HTMLPurifier_Config::create() supports.
+ *
+ * @return string Purified HTML
+ */
+ public function purify($html, $config = null)
+ {
+ // :TODO: make the config merge in, instead of replace
+ $config = $config ? HTMLPurifier_Config::create($config) : $this->config;
+
+ // implementation is partially environment dependant, partially
+ // configuration dependant
+ $lexer = HTMLPurifier_Lexer::create($config);
+
+ $context = new HTMLPurifier_Context();
+
+ // setup HTML generator
+ $this->generator = new HTMLPurifier_Generator($config, $context);
+ $context->register('Generator', $this->generator);
+
+ // set up global context variables
+ if ($config->get('Core.CollectErrors')) {
+ // may get moved out if other facilities use it
+ $language_factory = HTMLPurifier_LanguageFactory::instance();
+ $language = $language_factory->create($config, $context);
+ $context->register('Locale', $language);
+
+ $error_collector = new HTMLPurifier_ErrorCollector($context);
+ $context->register('ErrorCollector', $error_collector);
+ }
+
+ // setup id_accumulator context, necessary due to the fact that
+ // AttrValidator can be called from many places
+ $id_accumulator = HTMLPurifier_IDAccumulator::build($config, $context);
+ $context->register('IDAccumulator', $id_accumulator);
+
+ $html = HTMLPurifier_Encoder::convertToUTF8($html, $config, $context);
+
+ // setup filters
+ $filter_flags = $config->getBatch('Filter');
+ $custom_filters = $filter_flags['Custom'];
+ unset($filter_flags['Custom']);
+ $filters = array();
+ foreach ($filter_flags as $filter => $flag) {
+ if (!$flag) {
+ continue;
+ }
+ if (strpos($filter, '.') !== false) {
+ continue;
+ }
+ $class = "HTMLPurifier_Filter_$filter";
+ $filters[] = new $class;
+ }
+ foreach ($custom_filters as $filter) {
+ // maybe "HTMLPurifier_Filter_$filter", but be consistent with AutoFormat
+ $filters[] = $filter;
+ }
+ $filters = array_merge($filters, $this->filters);
+ // maybe prepare(), but later
+
+ for ($i = 0, $filter_size = count($filters); $i < $filter_size; $i++) {
+ $html = $filters[$i]->preFilter($html, $config, $context);
+ }
+
+ // purified HTML
+ $html =
+ $this->generator->generateFromTokens(
+ // list of tokens
+ $this->strategy->execute(
+ // list of un-purified tokens
+ $lexer->tokenizeHTML(
+ // un-purified HTML
+ $html,
+ $config,
+ $context
+ ),
+ $config,
+ $context
+ )
+ );
+
+ for ($i = $filter_size - 1; $i >= 0; $i--) {
+ $html = $filters[$i]->postFilter($html, $config, $context);
+ }
+
+ $html = HTMLPurifier_Encoder::convertFromUTF8($html, $config, $context);
+ $this->context =& $context;
+ return $html;
+ }
+
+ /**
+ * Filters an array of HTML snippets
+ *
+ * @param string[] $array_of_html Array of html snippets
+ * @param HTMLPurifier_Config $config Optional config object for this operation.
+ * See HTMLPurifier::purify() for more details.
+ *
+ * @return string[] Array of purified HTML
+ */
+ public function purifyArray($array_of_html, $config = null)
+ {
+ $context_array = array();
+ foreach ($array_of_html as $key => $html) {
+ $array_of_html[$key] = $this->purify($html, $config);
+ $context_array[$key] = $this->context;
+ }
+ $this->context = $context_array;
+ return $array_of_html;
+ }
+
+ /**
+ * Singleton for enforcing just one HTML Purifier in your system
+ *
+ * @param HTMLPurifier|HTMLPurifier_Config $prototype Optional prototype
+ * HTMLPurifier instance to overload singleton with,
+ * or HTMLPurifier_Config instance to configure the
+ * generated version with.
+ *
+ * @return HTMLPurifier
+ */
+ public static function instance($prototype = null)
+ {
+ if (!self::$instance || $prototype) {
+ if ($prototype instanceof HTMLPurifier) {
+ self::$instance = $prototype;
+ } elseif ($prototype) {
+ self::$instance = new HTMLPurifier($prototype);
+ } else {
+ self::$instance = new HTMLPurifier();
+ }
+ }
+ return self::$instance;
+ }
+
+ /**
+ * Singleton for enforcing just one HTML Purifier in your system
+ *
+ * @param HTMLPurifier|HTMLPurifier_Config $prototype Optional prototype
+ * HTMLPurifier instance to overload singleton with,
+ * or HTMLPurifier_Config instance to configure the
+ * generated version with.
+ *
+ * @return HTMLPurifier
+ * @note Backwards compatibility, see instance()
+ */
+ public static function getInstance($prototype = null)
+ {
+ return HTMLPurifier::instance($prototype);
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier.safe-includes.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier.safe-includes.php
new file mode 100644
index 000000000..a3261f8a3
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier.safe-includes.php
@@ -0,0 +1,228 @@
+<?php
+
+/**
+ * @file
+ * This file was auto-generated by generate-includes.php and includes all of
+ * the core files required by HTML Purifier. This is a convenience stub that
+ * includes all files using dirname(__FILE__) and require_once. PLEASE DO NOT
+ * EDIT THIS FILE, changes will be overwritten the next time the script is run.
+ *
+ * Changes to include_path are not necessary.
+ */
+
+$__dir = dirname(__FILE__);
+
+require_once $__dir . '/HTMLPurifier.php';
+require_once $__dir . '/HTMLPurifier/Arborize.php';
+require_once $__dir . '/HTMLPurifier/AttrCollections.php';
+require_once $__dir . '/HTMLPurifier/AttrDef.php';
+require_once $__dir . '/HTMLPurifier/AttrTransform.php';
+require_once $__dir . '/HTMLPurifier/AttrTypes.php';
+require_once $__dir . '/HTMLPurifier/AttrValidator.php';
+require_once $__dir . '/HTMLPurifier/Bootstrap.php';
+require_once $__dir . '/HTMLPurifier/Definition.php';
+require_once $__dir . '/HTMLPurifier/CSSDefinition.php';
+require_once $__dir . '/HTMLPurifier/ChildDef.php';
+require_once $__dir . '/HTMLPurifier/Config.php';
+require_once $__dir . '/HTMLPurifier/ConfigSchema.php';
+require_once $__dir . '/HTMLPurifier/ContentSets.php';
+require_once $__dir . '/HTMLPurifier/Context.php';
+require_once $__dir . '/HTMLPurifier/DefinitionCache.php';
+require_once $__dir . '/HTMLPurifier/DefinitionCacheFactory.php';
+require_once $__dir . '/HTMLPurifier/Doctype.php';
+require_once $__dir . '/HTMLPurifier/DoctypeRegistry.php';
+require_once $__dir . '/HTMLPurifier/ElementDef.php';
+require_once $__dir . '/HTMLPurifier/Encoder.php';
+require_once $__dir . '/HTMLPurifier/EntityLookup.php';
+require_once $__dir . '/HTMLPurifier/EntityParser.php';
+require_once $__dir . '/HTMLPurifier/ErrorCollector.php';
+require_once $__dir . '/HTMLPurifier/ErrorStruct.php';
+require_once $__dir . '/HTMLPurifier/Exception.php';
+require_once $__dir . '/HTMLPurifier/Filter.php';
+require_once $__dir . '/HTMLPurifier/Generator.php';
+require_once $__dir . '/HTMLPurifier/HTMLDefinition.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule.php';
+require_once $__dir . '/HTMLPurifier/HTMLModuleManager.php';
+require_once $__dir . '/HTMLPurifier/IDAccumulator.php';
+require_once $__dir . '/HTMLPurifier/Injector.php';
+require_once $__dir . '/HTMLPurifier/Language.php';
+require_once $__dir . '/HTMLPurifier/LanguageFactory.php';
+require_once $__dir . '/HTMLPurifier/Length.php';
+require_once $__dir . '/HTMLPurifier/Lexer.php';
+require_once $__dir . '/HTMLPurifier/Node.php';
+require_once $__dir . '/HTMLPurifier/PercentEncoder.php';
+require_once $__dir . '/HTMLPurifier/PropertyList.php';
+require_once $__dir . '/HTMLPurifier/PropertyListIterator.php';
+require_once $__dir . '/HTMLPurifier/Queue.php';
+require_once $__dir . '/HTMLPurifier/Strategy.php';
+require_once $__dir . '/HTMLPurifier/StringHash.php';
+require_once $__dir . '/HTMLPurifier/StringHashParser.php';
+require_once $__dir . '/HTMLPurifier/TagTransform.php';
+require_once $__dir . '/HTMLPurifier/Token.php';
+require_once $__dir . '/HTMLPurifier/TokenFactory.php';
+require_once $__dir . '/HTMLPurifier/URI.php';
+require_once $__dir . '/HTMLPurifier/URIDefinition.php';
+require_once $__dir . '/HTMLPurifier/URIFilter.php';
+require_once $__dir . '/HTMLPurifier/URIParser.php';
+require_once $__dir . '/HTMLPurifier/URIScheme.php';
+require_once $__dir . '/HTMLPurifier/URISchemeRegistry.php';
+require_once $__dir . '/HTMLPurifier/UnitConverter.php';
+require_once $__dir . '/HTMLPurifier/VarParser.php';
+require_once $__dir . '/HTMLPurifier/VarParserException.php';
+require_once $__dir . '/HTMLPurifier/Zipper.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/CSS.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/Clone.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/Enum.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/Integer.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/Lang.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/Switch.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/Text.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/URI.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/CSS/Number.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/CSS/AlphaValue.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/CSS/Background.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/CSS/BackgroundPosition.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/CSS/Border.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/CSS/Color.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/CSS/Composite.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/CSS/DenyElementDecorator.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/CSS/Filter.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/CSS/Font.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/CSS/FontFamily.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/CSS/Ident.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/CSS/ImportantDecorator.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/CSS/Length.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/CSS/ListStyle.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/CSS/Multiple.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/CSS/Percentage.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/CSS/TextDecoration.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/CSS/URI.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/HTML/Bool.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/HTML/Nmtokens.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/HTML/Class.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/HTML/Color.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/HTML/FrameTarget.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/HTML/ID.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/HTML/Pixels.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/HTML/Length.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/HTML/LinkTypes.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/HTML/MultiLength.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/URI/Email.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/URI/Host.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/URI/IPv4.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/URI/IPv6.php';
+require_once $__dir . '/HTMLPurifier/AttrDef/URI/Email/SimpleCheck.php';
+require_once $__dir . '/HTMLPurifier/AttrTransform/Background.php';
+require_once $__dir . '/HTMLPurifier/AttrTransform/BdoDir.php';
+require_once $__dir . '/HTMLPurifier/AttrTransform/BgColor.php';
+require_once $__dir . '/HTMLPurifier/AttrTransform/BoolToCSS.php';
+require_once $__dir . '/HTMLPurifier/AttrTransform/Border.php';
+require_once $__dir . '/HTMLPurifier/AttrTransform/EnumToCSS.php';
+require_once $__dir . '/HTMLPurifier/AttrTransform/ImgRequired.php';
+require_once $__dir . '/HTMLPurifier/AttrTransform/ImgSpace.php';
+require_once $__dir . '/HTMLPurifier/AttrTransform/Input.php';
+require_once $__dir . '/HTMLPurifier/AttrTransform/Lang.php';
+require_once $__dir . '/HTMLPurifier/AttrTransform/Length.php';
+require_once $__dir . '/HTMLPurifier/AttrTransform/Name.php';
+require_once $__dir . '/HTMLPurifier/AttrTransform/NameSync.php';
+require_once $__dir . '/HTMLPurifier/AttrTransform/Nofollow.php';
+require_once $__dir . '/HTMLPurifier/AttrTransform/SafeEmbed.php';
+require_once $__dir . '/HTMLPurifier/AttrTransform/SafeObject.php';
+require_once $__dir . '/HTMLPurifier/AttrTransform/SafeParam.php';
+require_once $__dir . '/HTMLPurifier/AttrTransform/ScriptRequired.php';
+require_once $__dir . '/HTMLPurifier/AttrTransform/TargetBlank.php';
+require_once $__dir . '/HTMLPurifier/AttrTransform/TargetNoopener.php';
+require_once $__dir . '/HTMLPurifier/AttrTransform/TargetNoreferrer.php';
+require_once $__dir . '/HTMLPurifier/AttrTransform/Textarea.php';
+require_once $__dir . '/HTMLPurifier/ChildDef/Chameleon.php';
+require_once $__dir . '/HTMLPurifier/ChildDef/Custom.php';
+require_once $__dir . '/HTMLPurifier/ChildDef/Empty.php';
+require_once $__dir . '/HTMLPurifier/ChildDef/List.php';
+require_once $__dir . '/HTMLPurifier/ChildDef/Required.php';
+require_once $__dir . '/HTMLPurifier/ChildDef/Optional.php';
+require_once $__dir . '/HTMLPurifier/ChildDef/StrictBlockquote.php';
+require_once $__dir . '/HTMLPurifier/ChildDef/Table.php';
+require_once $__dir . '/HTMLPurifier/DefinitionCache/Decorator.php';
+require_once $__dir . '/HTMLPurifier/DefinitionCache/Null.php';
+require_once $__dir . '/HTMLPurifier/DefinitionCache/Serializer.php';
+require_once $__dir . '/HTMLPurifier/DefinitionCache/Decorator/Cleanup.php';
+require_once $__dir . '/HTMLPurifier/DefinitionCache/Decorator/Memory.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Bdo.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/CommonAttributes.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Edit.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Forms.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Hypertext.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Iframe.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Image.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Legacy.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/List.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Name.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Nofollow.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/NonXMLCommonAttributes.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Object.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Presentation.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Proprietary.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Ruby.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/SafeEmbed.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/SafeObject.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/SafeScripting.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Scripting.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/StyleAttribute.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Tables.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Target.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/TargetBlank.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/TargetNoopener.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/TargetNoreferrer.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Text.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Tidy.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/XMLCommonAttributes.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Tidy/Name.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Tidy/Proprietary.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Tidy/XHTMLAndHTML4.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Tidy/Strict.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Tidy/Transitional.php';
+require_once $__dir . '/HTMLPurifier/HTMLModule/Tidy/XHTML.php';
+require_once $__dir . '/HTMLPurifier/Injector/AutoParagraph.php';
+require_once $__dir . '/HTMLPurifier/Injector/DisplayLinkURI.php';
+require_once $__dir . '/HTMLPurifier/Injector/Linkify.php';
+require_once $__dir . '/HTMLPurifier/Injector/PurifierLinkify.php';
+require_once $__dir . '/HTMLPurifier/Injector/RemoveEmpty.php';
+require_once $__dir . '/HTMLPurifier/Injector/RemoveSpansWithoutAttributes.php';
+require_once $__dir . '/HTMLPurifier/Injector/SafeObject.php';
+require_once $__dir . '/HTMLPurifier/Lexer/DOMLex.php';
+require_once $__dir . '/HTMLPurifier/Lexer/DirectLex.php';
+require_once $__dir . '/HTMLPurifier/Node/Comment.php';
+require_once $__dir . '/HTMLPurifier/Node/Element.php';
+require_once $__dir . '/HTMLPurifier/Node/Text.php';
+require_once $__dir . '/HTMLPurifier/Strategy/Composite.php';
+require_once $__dir . '/HTMLPurifier/Strategy/Core.php';
+require_once $__dir . '/HTMLPurifier/Strategy/FixNesting.php';
+require_once $__dir . '/HTMLPurifier/Strategy/MakeWellFormed.php';
+require_once $__dir . '/HTMLPurifier/Strategy/RemoveForeignElements.php';
+require_once $__dir . '/HTMLPurifier/Strategy/ValidateAttributes.php';
+require_once $__dir . '/HTMLPurifier/TagTransform/Font.php';
+require_once $__dir . '/HTMLPurifier/TagTransform/Simple.php';
+require_once $__dir . '/HTMLPurifier/Token/Comment.php';
+require_once $__dir . '/HTMLPurifier/Token/Tag.php';
+require_once $__dir . '/HTMLPurifier/Token/Empty.php';
+require_once $__dir . '/HTMLPurifier/Token/End.php';
+require_once $__dir . '/HTMLPurifier/Token/Start.php';
+require_once $__dir . '/HTMLPurifier/Token/Text.php';
+require_once $__dir . '/HTMLPurifier/URIFilter/DisableExternal.php';
+require_once $__dir . '/HTMLPurifier/URIFilter/DisableExternalResources.php';
+require_once $__dir . '/HTMLPurifier/URIFilter/DisableResources.php';
+require_once $__dir . '/HTMLPurifier/URIFilter/HostBlacklist.php';
+require_once $__dir . '/HTMLPurifier/URIFilter/MakeAbsolute.php';
+require_once $__dir . '/HTMLPurifier/URIFilter/Munge.php';
+require_once $__dir . '/HTMLPurifier/URIFilter/SafeIframe.php';
+require_once $__dir . '/HTMLPurifier/URIScheme/data.php';
+require_once $__dir . '/HTMLPurifier/URIScheme/file.php';
+require_once $__dir . '/HTMLPurifier/URIScheme/ftp.php';
+require_once $__dir . '/HTMLPurifier/URIScheme/http.php';
+require_once $__dir . '/HTMLPurifier/URIScheme/https.php';
+require_once $__dir . '/HTMLPurifier/URIScheme/mailto.php';
+require_once $__dir . '/HTMLPurifier/URIScheme/news.php';
+require_once $__dir . '/HTMLPurifier/URIScheme/nntp.php';
+require_once $__dir . '/HTMLPurifier/URIScheme/tel.php';
+require_once $__dir . '/HTMLPurifier/VarParser/Flexible.php';
+require_once $__dir . '/HTMLPurifier/VarParser/Native.php';
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Arborize.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Arborize.php
new file mode 100644
index 000000000..d2e9d22a2
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Arborize.php
@@ -0,0 +1,71 @@
+<?php
+
+/**
+ * Converts a stream of HTMLPurifier_Token into an HTMLPurifier_Node,
+ * and back again.
+ *
+ * @note This transformation is not an equivalence. We mutate the input
+ * token stream to make it so; see all [MUT] markers in code.
+ */
+class HTMLPurifier_Arborize
+{
+ public static function arborize($tokens, $config, $context) {
+ $definition = $config->getHTMLDefinition();
+ $parent = new HTMLPurifier_Token_Start($definition->info_parent);
+ $stack = array($parent->toNode());
+ foreach ($tokens as $token) {
+ $token->skip = null; // [MUT]
+ $token->carryover = null; // [MUT]
+ if ($token instanceof HTMLPurifier_Token_End) {
+ $token->start = null; // [MUT]
+ $r = array_pop($stack);
+ //assert($r->name === $token->name);
+ //assert(empty($token->attr));
+ $r->endCol = $token->col;
+ $r->endLine = $token->line;
+ $r->endArmor = $token->armor;
+ continue;
+ }
+ $node = $token->toNode();
+ $stack[count($stack)-1]->children[] = $node;
+ if ($token instanceof HTMLPurifier_Token_Start) {
+ $stack[] = $node;
+ }
+ }
+ //assert(count($stack) == 1);
+ return $stack[0];
+ }
+
+ public static function flatten($node, $config, $context) {
+ $level = 0;
+ $nodes = array($level => new HTMLPurifier_Queue(array($node)));
+ $closingTokens = array();
+ $tokens = array();
+ do {
+ while (!$nodes[$level]->isEmpty()) {
+ $node = $nodes[$level]->shift(); // FIFO
+ list($start, $end) = $node->toTokenPair();
+ if ($level > 0) {
+ $tokens[] = $start;
+ }
+ if ($end !== NULL) {
+ $closingTokens[$level][] = $end;
+ }
+ if ($node instanceof HTMLPurifier_Node_Element) {
+ $level++;
+ $nodes[$level] = new HTMLPurifier_Queue();
+ foreach ($node->children as $childNode) {
+ $nodes[$level]->push($childNode);
+ }
+ }
+ }
+ $level--;
+ if ($level && isset($closingTokens[$level])) {
+ while ($token = array_pop($closingTokens[$level])) {
+ $tokens[] = $token;
+ }
+ }
+ } while ($level > 0);
+ return $tokens;
+ }
+}
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrCollections.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrCollections.php
new file mode 100644
index 000000000..c7b17cf14
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrCollections.php
@@ -0,0 +1,148 @@
+<?php
+
+/**
+ * Defines common attribute collections that modules reference
+ */
+
+class HTMLPurifier_AttrCollections
+{
+
+ /**
+ * Associative array of attribute collections, indexed by name.
+ * @type array
+ */
+ public $info = array();
+
+ /**
+ * Performs all expansions on internal data for use by other inclusions
+ * It also collects all attribute collection extensions from
+ * modules
+ * @param HTMLPurifier_AttrTypes $attr_types HTMLPurifier_AttrTypes instance
+ * @param HTMLPurifier_HTMLModule[] $modules Hash array of HTMLPurifier_HTMLModule members
+ */
+ public function __construct($attr_types, $modules)
+ {
+ $this->doConstruct($attr_types, $modules);
+ }
+
+ public function doConstruct($attr_types, $modules)
+ {
+ // load extensions from the modules
+ foreach ($modules as $module) {
+ foreach ($module->attr_collections as $coll_i => $coll) {
+ if (!isset($this->info[$coll_i])) {
+ $this->info[$coll_i] = array();
+ }
+ foreach ($coll as $attr_i => $attr) {
+ if ($attr_i === 0 && isset($this->info[$coll_i][$attr_i])) {
+ // merge in includes
+ $this->info[$coll_i][$attr_i] = array_merge(
+ $this->info[$coll_i][$attr_i],
+ $attr
+ );
+ continue;
+ }
+ $this->info[$coll_i][$attr_i] = $attr;
+ }
+ }
+ }
+ // perform internal expansions and inclusions
+ foreach ($this->info as $name => $attr) {
+ // merge attribute collections that include others
+ $this->performInclusions($this->info[$name]);
+ // replace string identifiers with actual attribute objects
+ $this->expandIdentifiers($this->info[$name], $attr_types);
+ }
+ }
+
+ /**
+ * Takes a reference to an attribute associative array and performs
+ * all inclusions specified by the zero index.
+ * @param array &$attr Reference to attribute array
+ */
+ public function performInclusions(&$attr)
+ {
+ if (!isset($attr[0])) {
+ return;
+ }
+ $merge = $attr[0];
+ $seen = array(); // recursion guard
+ // loop through all the inclusions
+ for ($i = 0; isset($merge[$i]); $i++) {
+ if (isset($seen[$merge[$i]])) {
+ continue;
+ }
+ $seen[$merge[$i]] = true;
+ // foreach attribute of the inclusion, copy it over
+ if (!isset($this->info[$merge[$i]])) {
+ continue;
+ }
+ foreach ($this->info[$merge[$i]] as $key => $value) {
+ if (isset($attr[$key])) {
+ continue;
+ } // also catches more inclusions
+ $attr[$key] = $value;
+ }
+ if (isset($this->info[$merge[$i]][0])) {
+ // recursion
+ $merge = array_merge($merge, $this->info[$merge[$i]][0]);
+ }
+ }
+ unset($attr[0]);
+ }
+
+ /**
+ * Expands all string identifiers in an attribute array by replacing
+ * them with the appropriate values inside HTMLPurifier_AttrTypes
+ * @param array &$attr Reference to attribute array
+ * @param HTMLPurifier_AttrTypes $attr_types HTMLPurifier_AttrTypes instance
+ */
+ public function expandIdentifiers(&$attr, $attr_types)
+ {
+ // because foreach will process new elements we add, make sure we
+ // skip duplicates
+ $processed = array();
+
+ foreach ($attr as $def_i => $def) {
+ // skip inclusions
+ if ($def_i === 0) {
+ continue;
+ }
+
+ if (isset($processed[$def_i])) {
+ continue;
+ }
+
+ // determine whether or not attribute is required
+ if ($required = (strpos($def_i, '*') !== false)) {
+ // rename the definition
+ unset($attr[$def_i]);
+ $def_i = trim($def_i, '*');
+ $attr[$def_i] = $def;
+ }
+
+ $processed[$def_i] = true;
+
+ // if we've already got a literal object, move on
+ if (is_object($def)) {
+ // preserve previous required
+ $attr[$def_i]->required = ($required || $attr[$def_i]->required);
+ continue;
+ }
+
+ if ($def === false) {
+ unset($attr[$def_i]);
+ continue;
+ }
+
+ if ($t = $attr_types->get($def)) {
+ $attr[$def_i] = $t;
+ $attr[$def_i]->required = $required;
+ } else {
+ unset($attr[$def_i]);
+ }
+ }
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef.php
new file mode 100644
index 000000000..739646fa7
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef.php
@@ -0,0 +1,144 @@
+<?php
+
+/**
+ * Base class for all validating attribute definitions.
+ *
+ * This family of classes forms the core for not only HTML attribute validation,
+ * but also any sort of string that needs to be validated or cleaned (which
+ * means CSS properties and composite definitions are defined here too).
+ * Besides defining (through code) what precisely makes the string valid,
+ * subclasses are also responsible for cleaning the code if possible.
+ */
+
+abstract class HTMLPurifier_AttrDef
+{
+
+ /**
+ * Tells us whether or not an HTML attribute is minimized.
+ * Has no meaning in other contexts.
+ * @type bool
+ */
+ public $minimized = false;
+
+ /**
+ * Tells us whether or not an HTML attribute is required.
+ * Has no meaning in other contexts
+ * @type bool
+ */
+ public $required = false;
+
+ /**
+ * Validates and cleans passed string according to a definition.
+ *
+ * @param string $string String to be validated and cleaned.
+ * @param HTMLPurifier_Config $config Mandatory HTMLPurifier_Config object.
+ * @param HTMLPurifier_Context $context Mandatory HTMLPurifier_Context object.
+ */
+ abstract public function validate($string, $config, $context);
+
+ /**
+ * Convenience method that parses a string as if it were CDATA.
+ *
+ * This method process a string in the manner specified at
+ * <http://www.w3.org/TR/html4/types.html#h-6.2> by removing
+ * leading and trailing whitespace, ignoring line feeds, and replacing
+ * carriage returns and tabs with spaces. While most useful for HTML
+ * attributes specified as CDATA, it can also be applied to most CSS
+ * values.
+ *
+ * @note This method is not entirely standards compliant, as trim() removes
+ * more types of whitespace than specified in the spec. In practice,
+ * this is rarely a problem, as those extra characters usually have
+ * already been removed by HTMLPurifier_Encoder.
+ *
+ * @warning This processing is inconsistent with XML's whitespace handling
+ * as specified by section 3.3.3 and referenced XHTML 1.0 section
+ * 4.7. However, note that we are NOT necessarily
+ * parsing XML, thus, this behavior may still be correct. We
+ * assume that newlines have been normalized.
+ */
+ public function parseCDATA($string)
+ {
+ $string = trim($string);
+ $string = str_replace(array("\n", "\t", "\r"), ' ', $string);
+ return $string;
+ }
+
+ /**
+ * Factory method for creating this class from a string.
+ * @param string $string String construction info
+ * @return HTMLPurifier_AttrDef Created AttrDef object corresponding to $string
+ */
+ public function make($string)
+ {
+ // default implementation, return a flyweight of this object.
+ // If $string has an effect on the returned object (i.e. you
+ // need to overload this method), it is best
+ // to clone or instantiate new copies. (Instantiation is safer.)
+ return $this;
+ }
+
+ /**
+ * Removes spaces from rgb(0, 0, 0) so that shorthand CSS properties work
+ * properly. THIS IS A HACK!
+ * @param string $string a CSS colour definition
+ * @return string
+ */
+ protected function mungeRgb($string)
+ {
+ $p = '\s*(\d+(\.\d+)?([%]?))\s*';
+
+ if (preg_match('/(rgba|hsla)\(/', $string)) {
+ return preg_replace('/(rgba|hsla)\('.$p.','.$p.','.$p.','.$p.'\)/', '\1(\2,\5,\8,\11)', $string);
+ }
+
+ return preg_replace('/(rgb|hsl)\('.$p.','.$p.','.$p.'\)/', '\1(\2,\5,\8)', $string);
+ }
+
+ /**
+ * Parses a possibly escaped CSS string and returns the "pure"
+ * version of it.
+ */
+ protected function expandCSSEscape($string)
+ {
+ // flexibly parse it
+ $ret = '';
+ for ($i = 0, $c = strlen($string); $i < $c; $i++) {
+ if ($string[$i] === '\\') {
+ $i++;
+ if ($i >= $c) {
+ $ret .= '\\';
+ break;
+ }
+ if (ctype_xdigit($string[$i])) {
+ $code = $string[$i];
+ for ($a = 1, $i++; $i < $c && $a < 6; $i++, $a++) {
+ if (!ctype_xdigit($string[$i])) {
+ break;
+ }
+ $code .= $string[$i];
+ }
+ // We have to be extremely careful when adding
+ // new characters, to make sure we're not breaking
+ // the encoding.
+ $char = HTMLPurifier_Encoder::unichr(hexdec($code));
+ if (HTMLPurifier_Encoder::cleanUTF8($char) === '') {
+ continue;
+ }
+ $ret .= $char;
+ if ($i < $c && trim($string[$i]) !== '') {
+ $i--;
+ }
+ continue;
+ }
+ if ($string[$i] === "\n") {
+ continue;
+ }
+ }
+ $ret .= $string[$i];
+ }
+ return $ret;
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS.php
new file mode 100644
index 000000000..ad2cb90ad
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS.php
@@ -0,0 +1,136 @@
+<?php
+
+/**
+ * Validates the HTML attribute style, otherwise known as CSS.
+ * @note We don't implement the whole CSS specification, so it might be
+ * difficult to reuse this component in the context of validating
+ * actual stylesheet declarations.
+ * @note If we were really serious about validating the CSS, we would
+ * tokenize the styles and then parse the tokens. Obviously, we
+ * are not doing that. Doing that could seriously harm performance,
+ * but would make these components a lot more viable for a CSS
+ * filtering solution.
+ */
+class HTMLPurifier_AttrDef_CSS extends HTMLPurifier_AttrDef
+{
+
+ /**
+ * @param string $css
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return bool|string
+ */
+ public function validate($css, $config, $context)
+ {
+ $css = $this->parseCDATA($css);
+
+ $definition = $config->getCSSDefinition();
+ $allow_duplicates = $config->get("CSS.AllowDuplicates");
+
+
+ // According to the CSS2.1 spec, the places where a
+ // non-delimiting semicolon can appear are in strings
+ // escape sequences. So here is some dumb hack to
+ // handle quotes.
+ $len = strlen($css);
+ $accum = "";
+ $declarations = array();
+ $quoted = false;
+ for ($i = 0; $i < $len; $i++) {
+ $c = strcspn($css, ";'\"", $i);
+ $accum .= substr($css, $i, $c);
+ $i += $c;
+ if ($i == $len) break;
+ $d = $css[$i];
+ if ($quoted) {
+ $accum .= $d;
+ if ($d == $quoted) {
+ $quoted = false;
+ }
+ } else {
+ if ($d == ";") {
+ $declarations[] = $accum;
+ $accum = "";
+ } else {
+ $accum .= $d;
+ $quoted = $d;
+ }
+ }
+ }
+ if ($accum != "") $declarations[] = $accum;
+
+ $propvalues = array();
+ $new_declarations = '';
+
+ /**
+ * Name of the current CSS property being validated.
+ */
+ $property = false;
+ $context->register('CurrentCSSProperty', $property);
+
+ foreach ($declarations as $declaration) {
+ if (!$declaration) {
+ continue;
+ }
+ if (!strpos($declaration, ':')) {
+ continue;
+ }
+ list($property, $value) = explode(':', $declaration, 2);
+ $property = trim($property);
+ $value = trim($value);
+ $ok = false;
+ do {
+ if (isset($definition->info[$property])) {
+ $ok = true;
+ break;
+ }
+ if (ctype_lower($property)) {
+ break;
+ }
+ $property = strtolower($property);
+ if (isset($definition->info[$property])) {
+ $ok = true;
+ break;
+ }
+ } while (0);
+ if (!$ok) {
+ continue;
+ }
+ // inefficient call, since the validator will do this again
+ if (strtolower(trim($value)) !== 'inherit') {
+ // inherit works for everything (but only on the base property)
+ $result = $definition->info[$property]->validate(
+ $value,
+ $config,
+ $context
+ );
+ } else {
+ $result = 'inherit';
+ }
+ if ($result === false) {
+ continue;
+ }
+ if ($allow_duplicates) {
+ $new_declarations .= "$property:$result;";
+ } else {
+ $propvalues[$property] = $result;
+ }
+ }
+
+ $context->destroy('CurrentCSSProperty');
+
+ // procedure does not write the new CSS simultaneously, so it's
+ // slightly inefficient, but it's the only way of getting rid of
+ // duplicates. Perhaps config to optimize it, but not now.
+
+ foreach ($propvalues as $prop => $value) {
+ $new_declarations .= "$prop:$value;";
+ }
+
+ return $new_declarations ? $new_declarations : false;
+
+ }
+
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/AttrDef/CSS/AlphaValue.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/AlphaValue.php
index af2b83dff..af2b83dff 100644
--- a/library/HTMLPurifier/AttrDef/CSS/AlphaValue.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/AlphaValue.php
diff --git a/library/HTMLPurifier/AttrDef/CSS/Background.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Background.php
index 7f1ea3b0f..7f1ea3b0f 100644
--- a/library/HTMLPurifier/AttrDef/CSS/Background.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Background.php
diff --git a/library/HTMLPurifier/AttrDef/CSS/BackgroundPosition.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/BackgroundPosition.php
index 4580ef5a9..4580ef5a9 100644
--- a/library/HTMLPurifier/AttrDef/CSS/BackgroundPosition.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/BackgroundPosition.php
diff --git a/library/HTMLPurifier/AttrDef/CSS/Border.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Border.php
index 16243ba1e..16243ba1e 100644
--- a/library/HTMLPurifier/AttrDef/CSS/Border.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Border.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Color.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Color.php
new file mode 100644
index 000000000..d7287a00c
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Color.php
@@ -0,0 +1,161 @@
+<?php
+
+/**
+ * Validates Color as defined by CSS.
+ */
+class HTMLPurifier_AttrDef_CSS_Color extends HTMLPurifier_AttrDef
+{
+
+ /**
+ * @type HTMLPurifier_AttrDef_CSS_AlphaValue
+ */
+ protected $alpha;
+
+ public function __construct()
+ {
+ $this->alpha = new HTMLPurifier_AttrDef_CSS_AlphaValue();
+ }
+
+ /**
+ * @param string $color
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return bool|string
+ */
+ public function validate($color, $config, $context)
+ {
+ static $colors = null;
+ if ($colors === null) {
+ $colors = $config->get('Core.ColorKeywords');
+ }
+
+ $color = trim($color);
+ if ($color === '') {
+ return false;
+ }
+
+ $lower = strtolower($color);
+ if (isset($colors[$lower])) {
+ return $colors[$lower];
+ }
+
+ if (preg_match('#(rgb|rgba|hsl|hsla)\(#', $color, $matches) === 1) {
+ $length = strlen($color);
+ if (strpos($color, ')') !== $length - 1) {
+ return false;
+ }
+
+ // get used function : rgb, rgba, hsl or hsla
+ $function = $matches[1];
+
+ $parameters_size = 3;
+ $alpha_channel = false;
+ if (substr($function, -1) === 'a') {
+ $parameters_size = 4;
+ $alpha_channel = true;
+ }
+
+ /*
+ * Allowed types for values :
+ * parameter_position => [type => max_value]
+ */
+ $allowed_types = array(
+ 1 => array('percentage' => 100, 'integer' => 255),
+ 2 => array('percentage' => 100, 'integer' => 255),
+ 3 => array('percentage' => 100, 'integer' => 255),
+ );
+ $allow_different_types = false;
+
+ if (strpos($function, 'hsl') !== false) {
+ $allowed_types = array(
+ 1 => array('integer' => 360),
+ 2 => array('percentage' => 100),
+ 3 => array('percentage' => 100),
+ );
+ $allow_different_types = true;
+ }
+
+ $values = trim(str_replace($function, '', $color), ' ()');
+
+ $parts = explode(',', $values);
+ if (count($parts) !== $parameters_size) {
+ return false;
+ }
+
+ $type = false;
+ $new_parts = array();
+ $i = 0;
+
+ foreach ($parts as $part) {
+ $i++;
+ $part = trim($part);
+
+ if ($part === '') {
+ return false;
+ }
+
+ // different check for alpha channel
+ if ($alpha_channel === true && $i === count($parts)) {
+ $result = $this->alpha->validate($part, $config, $context);
+
+ if ($result === false) {
+ return false;
+ }
+
+ $new_parts[] = (string)$result;
+ continue;
+ }
+
+ if (substr($part, -1) === '%') {
+ $current_type = 'percentage';
+ } else {
+ $current_type = 'integer';
+ }
+
+ if (!array_key_exists($current_type, $allowed_types[$i])) {
+ return false;
+ }
+
+ if (!$type) {
+ $type = $current_type;
+ }
+
+ if ($allow_different_types === false && $type != $current_type) {
+ return false;
+ }
+
+ $max_value = $allowed_types[$i][$current_type];
+
+ if ($current_type == 'integer') {
+ // Return value between range 0 -> $max_value
+ $new_parts[] = (int)max(min($part, $max_value), 0);
+ } elseif ($current_type == 'percentage') {
+ $new_parts[] = (float)max(min(rtrim($part, '%'), $max_value), 0) . '%';
+ }
+ }
+
+ $new_values = implode(',', $new_parts);
+
+ $color = $function . '(' . $new_values . ')';
+ } else {
+ // hexadecimal handling
+ if ($color[0] === '#') {
+ $hex = substr($color, 1);
+ } else {
+ $hex = $color;
+ $color = '#' . $color;
+ }
+ $length = strlen($hex);
+ if ($length !== 3 && $length !== 6) {
+ return false;
+ }
+ if (!ctype_xdigit($hex)) {
+ return false;
+ }
+ }
+ return $color;
+ }
+
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/AttrDef/CSS/Composite.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Composite.php
index 9c1750554..9c1750554 100644
--- a/library/HTMLPurifier/AttrDef/CSS/Composite.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Composite.php
diff --git a/library/HTMLPurifier/AttrDef/CSS/DenyElementDecorator.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/DenyElementDecorator.php
index 9d77cc9aa..9d77cc9aa 100644
--- a/library/HTMLPurifier/AttrDef/CSS/DenyElementDecorator.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/DenyElementDecorator.php
diff --git a/library/HTMLPurifier/AttrDef/CSS/Filter.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Filter.php
index bde4c3301..bde4c3301 100644
--- a/library/HTMLPurifier/AttrDef/CSS/Filter.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Filter.php
diff --git a/library/HTMLPurifier/AttrDef/CSS/Font.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Font.php
index 579b97ef1..579b97ef1 100644
--- a/library/HTMLPurifier/AttrDef/CSS/Font.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Font.php
diff --git a/library/HTMLPurifier/AttrDef/CSS/FontFamily.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/FontFamily.php
index 74e24c881..74e24c881 100644
--- a/library/HTMLPurifier/AttrDef/CSS/FontFamily.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/FontFamily.php
diff --git a/library/HTMLPurifier/AttrDef/CSS/Ident.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Ident.php
index 973002c17..973002c17 100644
--- a/library/HTMLPurifier/AttrDef/CSS/Ident.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Ident.php
diff --git a/library/HTMLPurifier/AttrDef/CSS/ImportantDecorator.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/ImportantDecorator.php
index ffc989fe8..ffc989fe8 100644
--- a/library/HTMLPurifier/AttrDef/CSS/ImportantDecorator.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/ImportantDecorator.php
diff --git a/library/HTMLPurifier/AttrDef/CSS/Length.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Length.php
index f12453a04..f12453a04 100644
--- a/library/HTMLPurifier/AttrDef/CSS/Length.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Length.php
diff --git a/library/HTMLPurifier/AttrDef/CSS/ListStyle.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/ListStyle.php
index e74d42654..e74d42654 100644
--- a/library/HTMLPurifier/AttrDef/CSS/ListStyle.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/ListStyle.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Multiple.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Multiple.php
new file mode 100644
index 000000000..e707f871c
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Multiple.php
@@ -0,0 +1,71 @@
+<?php
+
+/**
+ * Framework class for strings that involve multiple values.
+ *
+ * Certain CSS properties such as border-width and margin allow multiple
+ * lengths to be specified. This class can take a vanilla border-width
+ * definition and multiply it, usually into a max of four.
+ *
+ * @note Even though the CSS specification isn't clear about it, inherit
+ * can only be used alone: it will never manifest as part of a multi
+ * shorthand declaration. Thus, this class does not allow inherit.
+ */
+class HTMLPurifier_AttrDef_CSS_Multiple extends HTMLPurifier_AttrDef
+{
+ /**
+ * Instance of component definition to defer validation to.
+ * @type HTMLPurifier_AttrDef
+ * @todo Make protected
+ */
+ public $single;
+
+ /**
+ * Max number of values allowed.
+ * @todo Make protected
+ */
+ public $max;
+
+ /**
+ * @param HTMLPurifier_AttrDef $single HTMLPurifier_AttrDef to multiply
+ * @param int $max Max number of values allowed (usually four)
+ */
+ public function __construct($single, $max = 4)
+ {
+ $this->single = $single;
+ $this->max = $max;
+ }
+
+ /**
+ * @param string $string
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return bool|string
+ */
+ public function validate($string, $config, $context)
+ {
+ $string = $this->mungeRgb($this->parseCDATA($string));
+ if ($string === '') {
+ return false;
+ }
+ $parts = explode(' ', $string); // parseCDATA replaced \r, \t and \n
+ $length = count($parts);
+ $final = '';
+ for ($i = 0, $num = 0; $i < $length && $num < $this->max; $i++) {
+ if (ctype_space($parts[$i])) {
+ continue;
+ }
+ $result = $this->single->validate($parts[$i], $config, $context);
+ if ($result !== false) {
+ $final .= $result . ' ';
+ $num++;
+ }
+ }
+ if ($final === '') {
+ return false;
+ }
+ return rtrim($final);
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/AttrDef/CSS/Number.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Number.php
index 8edc159e7..8edc159e7 100644
--- a/library/HTMLPurifier/AttrDef/CSS/Number.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Number.php
diff --git a/library/HTMLPurifier/AttrDef/CSS/Percentage.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Percentage.php
index f0f25c50a..f0f25c50a 100644
--- a/library/HTMLPurifier/AttrDef/CSS/Percentage.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/Percentage.php
diff --git a/library/HTMLPurifier/AttrDef/CSS/TextDecoration.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/TextDecoration.php
index 5fd4b7f7b..5fd4b7f7b 100644
--- a/library/HTMLPurifier/AttrDef/CSS/TextDecoration.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/TextDecoration.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/URI.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/URI.php
new file mode 100644
index 000000000..6617acace
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/CSS/URI.php
@@ -0,0 +1,77 @@
+<?php
+
+/**
+ * Validates a URI in CSS syntax, which uses url('http://example.com')
+ * @note While theoretically speaking a URI in a CSS document could
+ * be non-embedded, as of CSS2 there is no such usage so we're
+ * generalizing it. This may need to be changed in the future.
+ * @warning Since HTMLPurifier_AttrDef_CSS blindly uses semicolons as
+ * the separator, you cannot put a literal semicolon in
+ * in the URI. Try percent encoding it, in that case.
+ */
+class HTMLPurifier_AttrDef_CSS_URI extends HTMLPurifier_AttrDef_URI
+{
+
+ public function __construct()
+ {
+ parent::__construct(true); // always embedded
+ }
+
+ /**
+ * @param string $uri_string
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return bool|string
+ */
+ public function validate($uri_string, $config, $context)
+ {
+ // parse the URI out of the string and then pass it onto
+ // the parent object
+
+ $uri_string = $this->parseCDATA($uri_string);
+ if (strpos($uri_string, 'url(') !== 0) {
+ return false;
+ }
+ $uri_string = substr($uri_string, 4);
+ if (strlen($uri_string) == 0) {
+ return false;
+ }
+ $new_length = strlen($uri_string) - 1;
+ if ($uri_string[$new_length] != ')') {
+ return false;
+ }
+ $uri = trim(substr($uri_string, 0, $new_length));
+
+ if (!empty($uri) && ($uri[0] == "'" || $uri[0] == '"')) {
+ $quote = $uri[0];
+ $new_length = strlen($uri) - 1;
+ if ($uri[$new_length] !== $quote) {
+ return false;
+ }
+ $uri = substr($uri, 1, $new_length - 1);
+ }
+
+ $uri = $this->expandCSSEscape($uri);
+
+ $result = parent::validate($uri, $config, $context);
+
+ if ($result === false) {
+ return false;
+ }
+
+ // extra sanity check; should have been done by URI
+ $result = str_replace(array('"', "\\", "\n", "\x0c", "\r"), "", $result);
+
+ // suspicious characters are ()'; we're going to percent encode
+ // them for safety.
+ $result = str_replace(array('(', ')', "'"), array('%28', '%29', '%27'), $result);
+
+ // there's an extra bug where ampersands lose their escaping on
+ // an innerHTML cycle, so a very unlucky query parameter could
+ // then change the meaning of the URL. Unfortunately, there's
+ // not much we can do about that...
+ return "url(\"$result\")";
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/AttrDef/Clone.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Clone.php
index 6698a00c0..6698a00c0 100644
--- a/library/HTMLPurifier/AttrDef/Clone.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Clone.php
diff --git a/library/HTMLPurifier/AttrDef/Enum.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Enum.php
index 8abda7f6e..8abda7f6e 100644
--- a/library/HTMLPurifier/AttrDef/Enum.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Enum.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Bool.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Bool.php
new file mode 100644
index 000000000..dea15d2cd
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Bool.php
@@ -0,0 +1,48 @@
+<?php
+
+/**
+ * Validates a boolean attribute
+ */
+class HTMLPurifier_AttrDef_HTML_Bool extends HTMLPurifier_AttrDef
+{
+
+ /**
+ * @type bool
+ */
+ protected $name;
+
+ /**
+ * @type bool
+ */
+ public $minimized = true;
+
+ /**
+ * @param bool $name
+ */
+ public function __construct($name = false)
+ {
+ $this->name = $name;
+ }
+
+ /**
+ * @param string $string
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return bool|string
+ */
+ public function validate($string, $config, $context)
+ {
+ return $this->name;
+ }
+
+ /**
+ * @param string $string Name of attribute
+ * @return HTMLPurifier_AttrDef_HTML_Bool
+ */
+ public function make($string)
+ {
+ return new HTMLPurifier_AttrDef_HTML_Bool($string);
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/AttrDef/HTML/Class.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Class.php
index d5013488f..d5013488f 100644
--- a/library/HTMLPurifier/AttrDef/HTML/Class.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Class.php
diff --git a/library/HTMLPurifier/AttrDef/HTML/Color.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Color.php
index 946ebb782..946ebb782 100644
--- a/library/HTMLPurifier/AttrDef/HTML/Color.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Color.php
diff --git a/library/HTMLPurifier/AttrDef/HTML/FrameTarget.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/FrameTarget.php
index d79ba12b3..d79ba12b3 100644
--- a/library/HTMLPurifier/AttrDef/HTML/FrameTarget.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/FrameTarget.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/ID.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/ID.php
new file mode 100644
index 000000000..4ba45610f
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/ID.php
@@ -0,0 +1,113 @@
+<?php
+
+/**
+ * Validates the HTML attribute ID.
+ * @warning Even though this is the id processor, it
+ * will ignore the directive Attr:IDBlacklist, since it will only
+ * go according to the ID accumulator. Since the accumulator is
+ * automatically generated, it will have already absorbed the
+ * blacklist. If you're hacking around, make sure you use load()!
+ */
+
+class HTMLPurifier_AttrDef_HTML_ID extends HTMLPurifier_AttrDef
+{
+
+ // selector is NOT a valid thing to use for IDREFs, because IDREFs
+ // *must* target IDs that exist, whereas selector #ids do not.
+
+ /**
+ * Determines whether or not we're validating an ID in a CSS
+ * selector context.
+ * @type bool
+ */
+ protected $selector;
+
+ /**
+ * @param bool $selector
+ */
+ public function __construct($selector = false)
+ {
+ $this->selector = $selector;
+ }
+
+ /**
+ * @param string $id
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return bool|string
+ */
+ public function validate($id, $config, $context)
+ {
+ if (!$this->selector && !$config->get('Attr.EnableID')) {
+ return false;
+ }
+
+ $id = trim($id); // trim it first
+
+ if ($id === '') {
+ return false;
+ }
+
+ $prefix = $config->get('Attr.IDPrefix');
+ if ($prefix !== '') {
+ $prefix .= $config->get('Attr.IDPrefixLocal');
+ // prevent re-appending the prefix
+ if (strpos($id, $prefix) !== 0) {
+ $id = $prefix . $id;
+ }
+ } elseif ($config->get('Attr.IDPrefixLocal') !== '') {
+ trigger_error(
+ '%Attr.IDPrefixLocal cannot be used unless ' .
+ '%Attr.IDPrefix is set',
+ E_USER_WARNING
+ );
+ }
+
+ if (!$this->selector) {
+ $id_accumulator =& $context->get('IDAccumulator');
+ if (isset($id_accumulator->ids[$id])) {
+ return false;
+ }
+ }
+
+ // we purposely avoid using regex, hopefully this is faster
+
+ if ($config->get('Attr.ID.HTML5') === true) {
+ if (preg_match('/[\t\n\x0b\x0c ]/', $id)) {
+ return false;
+ }
+ } else {
+ if (ctype_alpha($id)) {
+ // OK
+ } else {
+ if (!ctype_alpha(@$id[0])) {
+ return false;
+ }
+ // primitive style of regexps, I suppose
+ $trim = trim(
+ $id,
+ 'A..Za..z0..9:-._'
+ );
+ if ($trim !== '') {
+ return false;
+ }
+ }
+ }
+
+ $regexp = $config->get('Attr.IDBlacklistRegexp');
+ if ($regexp && preg_match($regexp, $id)) {
+ return false;
+ }
+
+ if (!$this->selector) {
+ $id_accumulator->add($id);
+ }
+
+ // if no change was made to the ID, return the result
+ // else, return the new id if stripping whitespace made it
+ // valid, or return false.
+ return $id;
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/AttrDef/HTML/Length.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Length.php
index 1c4006fbb..1c4006fbb 100644
--- a/library/HTMLPurifier/AttrDef/HTML/Length.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Length.php
diff --git a/library/HTMLPurifier/AttrDef/HTML/LinkTypes.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/LinkTypes.php
index 63fa04c15..63fa04c15 100644
--- a/library/HTMLPurifier/AttrDef/HTML/LinkTypes.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/LinkTypes.php
diff --git a/library/HTMLPurifier/AttrDef/HTML/MultiLength.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/MultiLength.php
index bbb20f2f8..bbb20f2f8 100644
--- a/library/HTMLPurifier/AttrDef/HTML/MultiLength.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/MultiLength.php
diff --git a/library/HTMLPurifier/AttrDef/HTML/Nmtokens.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Nmtokens.php
index f79683b4f..f79683b4f 100644
--- a/library/HTMLPurifier/AttrDef/HTML/Nmtokens.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Nmtokens.php
diff --git a/library/HTMLPurifier/AttrDef/HTML/Pixels.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Pixels.php
index a1d019e09..a1d019e09 100644
--- a/library/HTMLPurifier/AttrDef/HTML/Pixels.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/HTML/Pixels.php
diff --git a/library/HTMLPurifier/AttrDef/Integer.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Integer.php
index 400e707d2..400e707d2 100644
--- a/library/HTMLPurifier/AttrDef/Integer.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Integer.php
diff --git a/library/HTMLPurifier/AttrDef/Lang.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Lang.php
index 2a55cea64..2a55cea64 100644
--- a/library/HTMLPurifier/AttrDef/Lang.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Lang.php
diff --git a/library/HTMLPurifier/AttrDef/Switch.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Switch.php
index c7eb3199a..c7eb3199a 100644
--- a/library/HTMLPurifier/AttrDef/Switch.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Switch.php
diff --git a/library/HTMLPurifier/AttrDef/Text.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Text.php
index 4553a4ea9..4553a4ea9 100644
--- a/library/HTMLPurifier/AttrDef/Text.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/Text.php
diff --git a/library/HTMLPurifier/AttrDef/URI.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI.php
index c1cd89772..c1cd89772 100644
--- a/library/HTMLPurifier/AttrDef/URI.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI.php
diff --git a/library/HTMLPurifier/AttrDef/URI/Email.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/Email.php
index daf32b764..daf32b764 100644
--- a/library/HTMLPurifier/AttrDef/URI/Email.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/Email.php
diff --git a/library/HTMLPurifier/AttrDef/URI/Email/SimpleCheck.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/Email/SimpleCheck.php
index 52c0d5968..52c0d5968 100644
--- a/library/HTMLPurifier/AttrDef/URI/Email/SimpleCheck.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/Email/SimpleCheck.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/Host.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/Host.php
new file mode 100644
index 000000000..3b4d18674
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/Host.php
@@ -0,0 +1,138 @@
+<?php
+
+/**
+ * Validates a host according to the IPv4, IPv6 and DNS (future) specifications.
+ */
+class HTMLPurifier_AttrDef_URI_Host extends HTMLPurifier_AttrDef
+{
+
+ /**
+ * IPv4 sub-validator.
+ * @type HTMLPurifier_AttrDef_URI_IPv4
+ */
+ protected $ipv4;
+
+ /**
+ * IPv6 sub-validator.
+ * @type HTMLPurifier_AttrDef_URI_IPv6
+ */
+ protected $ipv6;
+
+ public function __construct()
+ {
+ $this->ipv4 = new HTMLPurifier_AttrDef_URI_IPv4();
+ $this->ipv6 = new HTMLPurifier_AttrDef_URI_IPv6();
+ }
+
+ /**
+ * @param string $string
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return bool|string
+ */
+ public function validate($string, $config, $context)
+ {
+ $length = strlen($string);
+ // empty hostname is OK; it's usually semantically equivalent:
+ // the default host as defined by a URI scheme is used:
+ //
+ // If the URI scheme defines a default for host, then that
+ // default applies when the host subcomponent is undefined
+ // or when the registered name is empty (zero length).
+ if ($string === '') {
+ return '';
+ }
+ if ($length > 1 && $string[0] === '[' && $string[$length - 1] === ']') {
+ //IPv6
+ $ip = substr($string, 1, $length - 2);
+ $valid = $this->ipv6->validate($ip, $config, $context);
+ if ($valid === false) {
+ return false;
+ }
+ return '[' . $valid . ']';
+ }
+
+ // need to do checks on unusual encodings too
+ $ipv4 = $this->ipv4->validate($string, $config, $context);
+ if ($ipv4 !== false) {
+ return $ipv4;
+ }
+
+ // A regular domain name.
+
+ // This doesn't match I18N domain names, but we don't have proper IRI support,
+ // so force users to insert Punycode.
+
+ // There is not a good sense in which underscores should be
+ // allowed, since it's technically not! (And if you go as
+ // far to allow everything as specified by the DNS spec...
+ // well, that's literally everything, modulo some space limits
+ // for the components and the overall name (which, by the way,
+ // we are NOT checking!). So we (arbitrarily) decide this:
+ // let's allow underscores wherever we would have allowed
+ // hyphens, if they are enabled. This is a pretty good match
+ // for browser behavior, for example, a large number of browsers
+ // cannot handle foo_.example.com, but foo_bar.example.com is
+ // fairly well supported.
+ $underscore = $config->get('Core.AllowHostnameUnderscore') ? '_' : '';
+
+ // Based off of RFC 1738, but amended so that
+ // as per RFC 3696, the top label need only not be all numeric.
+ // The productions describing this are:
+ $a = '[a-z]'; // alpha
+ $an = '[a-z0-9]'; // alphanum
+ $and = "[a-z0-9-$underscore]"; // alphanum | "-"
+ // domainlabel = alphanum | alphanum *( alphanum | "-" ) alphanum
+ $domainlabel = "$an(?:$and*$an)?";
+ // AMENDED as per RFC 3696
+ // toplabel = alphanum | alphanum *( alphanum | "-" ) alphanum
+ // side condition: not all numeric
+ $toplabel = "$an(?:$and*$an)?";
+ // hostname = *( domainlabel "." ) toplabel [ "." ]
+ if (preg_match("/^(?:$domainlabel\.)*($toplabel)\.?$/i", $string, $matches)) {
+ if (!ctype_digit($matches[1])) {
+ return $string;
+ }
+ }
+
+ // PHP 5.3 and later support this functionality natively
+ if (function_exists('idn_to_ascii')) {
+ $string = idn_to_ascii($string);
+
+ // If we have Net_IDNA2 support, we can support IRIs by
+ // punycoding them. (This is the most portable thing to do,
+ // since otherwise we have to assume browsers support
+ } elseif ($config->get('Core.EnableIDNA')) {
+ $idna = new Net_IDNA2(array('encoding' => 'utf8', 'overlong' => false, 'strict' => true));
+ // we need to encode each period separately
+ $parts = explode('.', $string);
+ try {
+ $new_parts = array();
+ foreach ($parts as $part) {
+ $encodable = false;
+ for ($i = 0, $c = strlen($part); $i < $c; $i++) {
+ if (ord($part[$i]) > 0x7a) {
+ $encodable = true;
+ break;
+ }
+ }
+ if (!$encodable) {
+ $new_parts[] = $part;
+ } else {
+ $new_parts[] = $idna->encode($part);
+ }
+ }
+ $string = implode('.', $new_parts);
+ } catch (Exception $e) {
+ // XXX error reporting
+ }
+ }
+ // Try again
+ if (preg_match("/^($domainlabel\.)*$toplabel\.?$/i", $string)) {
+ return $string;
+ }
+ return false;
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/AttrDef/URI/IPv4.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/IPv4.php
index 30ac16c9e..30ac16c9e 100644
--- a/library/HTMLPurifier/AttrDef/URI/IPv4.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/IPv4.php
diff --git a/library/HTMLPurifier/AttrDef/URI/IPv6.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/IPv6.php
index f243793ee..f243793ee 100644
--- a/library/HTMLPurifier/AttrDef/URI/IPv6.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrDef/URI/IPv6.php
diff --git a/library/HTMLPurifier/AttrTransform.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform.php
index b428331f1..b428331f1 100644
--- a/library/HTMLPurifier/AttrTransform.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform.php
diff --git a/library/HTMLPurifier/AttrTransform/Background.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Background.php
index 2f72869a5..2f72869a5 100644
--- a/library/HTMLPurifier/AttrTransform/Background.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Background.php
diff --git a/library/HTMLPurifier/AttrTransform/BdoDir.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/BdoDir.php
index d66c04a5b..d66c04a5b 100644
--- a/library/HTMLPurifier/AttrTransform/BdoDir.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/BdoDir.php
diff --git a/library/HTMLPurifier/AttrTransform/BgColor.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/BgColor.php
index 0f51fd2ce..0f51fd2ce 100644
--- a/library/HTMLPurifier/AttrTransform/BgColor.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/BgColor.php
diff --git a/library/HTMLPurifier/AttrTransform/BoolToCSS.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/BoolToCSS.php
index f25cd0195..f25cd0195 100644
--- a/library/HTMLPurifier/AttrTransform/BoolToCSS.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/BoolToCSS.php
diff --git a/library/HTMLPurifier/AttrTransform/Border.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Border.php
index 057dc017f..057dc017f 100644
--- a/library/HTMLPurifier/AttrTransform/Border.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Border.php
diff --git a/library/HTMLPurifier/AttrTransform/EnumToCSS.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/EnumToCSS.php
index 7ccd0e3fb..7ccd0e3fb 100644
--- a/library/HTMLPurifier/AttrTransform/EnumToCSS.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/EnumToCSS.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/ImgRequired.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/ImgRequired.php
new file mode 100644
index 000000000..235ebb34b
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/ImgRequired.php
@@ -0,0 +1,47 @@
+<?php
+
+// must be called POST validation
+
+/**
+ * Transform that supplies default values for the src and alt attributes
+ * in img tags, as well as prevents the img tag from being removed
+ * because of a missing alt tag. This needs to be registered as both
+ * a pre and post attribute transform.
+ */
+class HTMLPurifier_AttrTransform_ImgRequired extends HTMLPurifier_AttrTransform
+{
+
+ /**
+ * @param array $attr
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return array
+ */
+ public function transform($attr, $config, $context)
+ {
+ $src = true;
+ if (!isset($attr['src'])) {
+ if ($config->get('Core.RemoveInvalidImg')) {
+ return $attr;
+ }
+ $attr['src'] = $config->get('Attr.DefaultInvalidImage');
+ $src = false;
+ }
+
+ if (!isset($attr['alt'])) {
+ if ($src) {
+ $alt = $config->get('Attr.DefaultImageAlt');
+ if ($alt === null) {
+ $attr['alt'] = basename($attr['src']);
+ } else {
+ $attr['alt'] = $alt;
+ }
+ } else {
+ $attr['alt'] = $config->get('Attr.DefaultInvalidImageAlt');
+ }
+ }
+ return $attr;
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/AttrTransform/ImgSpace.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/ImgSpace.php
index 350b3358f..350b3358f 100644
--- a/library/HTMLPurifier/AttrTransform/ImgSpace.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/ImgSpace.php
diff --git a/library/HTMLPurifier/AttrTransform/Input.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Input.php
index 3ab47ed8c..3ab47ed8c 100644
--- a/library/HTMLPurifier/AttrTransform/Input.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Input.php
diff --git a/library/HTMLPurifier/AttrTransform/Lang.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Lang.php
index 5b0aff0e4..5b0aff0e4 100644
--- a/library/HTMLPurifier/AttrTransform/Lang.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Lang.php
diff --git a/library/HTMLPurifier/AttrTransform/Length.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Length.php
index 853f33549..853f33549 100644
--- a/library/HTMLPurifier/AttrTransform/Length.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Length.php
diff --git a/library/HTMLPurifier/AttrTransform/Name.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Name.php
index 63cce6837..63cce6837 100644
--- a/library/HTMLPurifier/AttrTransform/Name.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Name.php
diff --git a/library/HTMLPurifier/AttrTransform/NameSync.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/NameSync.php
index 36079b786..36079b786 100644
--- a/library/HTMLPurifier/AttrTransform/NameSync.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/NameSync.php
diff --git a/library/HTMLPurifier/AttrTransform/Nofollow.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Nofollow.php
index 1057ebee1..1057ebee1 100644
--- a/library/HTMLPurifier/AttrTransform/Nofollow.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Nofollow.php
diff --git a/library/HTMLPurifier/AttrTransform/SafeEmbed.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/SafeEmbed.php
index 231c81a3f..231c81a3f 100644
--- a/library/HTMLPurifier/AttrTransform/SafeEmbed.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/SafeEmbed.php
diff --git a/library/HTMLPurifier/AttrTransform/SafeObject.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/SafeObject.php
index d1f3a4d2e..d1f3a4d2e 100644
--- a/library/HTMLPurifier/AttrTransform/SafeObject.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/SafeObject.php
diff --git a/library/HTMLPurifier/AttrTransform/SafeParam.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/SafeParam.php
index 1143b4b49..1143b4b49 100644
--- a/library/HTMLPurifier/AttrTransform/SafeParam.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/SafeParam.php
diff --git a/library/HTMLPurifier/AttrTransform/ScriptRequired.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/ScriptRequired.php
index b7057bbf8..b7057bbf8 100644
--- a/library/HTMLPurifier/AttrTransform/ScriptRequired.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/ScriptRequired.php
diff --git a/library/HTMLPurifier/AttrTransform/TargetBlank.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/TargetBlank.php
index dd63ea89c..dd63ea89c 100644
--- a/library/HTMLPurifier/AttrTransform/TargetBlank.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/TargetBlank.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/TargetNoopener.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/TargetNoopener.php
new file mode 100644
index 000000000..1db3c6c09
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/TargetNoopener.php
@@ -0,0 +1,37 @@
+<?php
+
+// must be called POST validation
+
+/**
+ * Adds rel="noopener" to any links which target a different window
+ * than the current one. This is used to prevent malicious websites
+ * from silently replacing the original window, which could be used
+ * to do phishing.
+ * This transform is controlled by %HTML.TargetNoopener.
+ */
+class HTMLPurifier_AttrTransform_TargetNoopener extends HTMLPurifier_AttrTransform
+{
+ /**
+ * @param array $attr
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return array
+ */
+ public function transform($attr, $config, $context)
+ {
+ if (isset($attr['rel'])) {
+ $rels = explode(' ', $attr['rel']);
+ } else {
+ $rels = array();
+ }
+ if (isset($attr['target']) && !in_array('noopener', $rels)) {
+ $rels[] = 'noopener';
+ }
+ if (!empty($rels) || isset($attr['rel'])) {
+ $attr['rel'] = implode(' ', $rels);
+ }
+
+ return $attr;
+ }
+}
+
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/TargetNoreferrer.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/TargetNoreferrer.php
new file mode 100644
index 000000000..587dc2e07
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/TargetNoreferrer.php
@@ -0,0 +1,37 @@
+<?php
+
+// must be called POST validation
+
+/**
+ * Adds rel="noreferrer" to any links which target a different window
+ * than the current one. This is used to prevent malicious websites
+ * from silently replacing the original window, which could be used
+ * to do phishing.
+ * This transform is controlled by %HTML.TargetNoreferrer.
+ */
+class HTMLPurifier_AttrTransform_TargetNoreferrer extends HTMLPurifier_AttrTransform
+{
+ /**
+ * @param array $attr
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return array
+ */
+ public function transform($attr, $config, $context)
+ {
+ if (isset($attr['rel'])) {
+ $rels = explode(' ', $attr['rel']);
+ } else {
+ $rels = array();
+ }
+ if (isset($attr['target']) && !in_array('noreferrer', $rels)) {
+ $rels[] = 'noreferrer';
+ }
+ if (!empty($rels) || isset($attr['rel'])) {
+ $attr['rel'] = implode(' ', $rels);
+ }
+
+ return $attr;
+ }
+}
+
diff --git a/library/HTMLPurifier/AttrTransform/Textarea.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Textarea.php
index 6a9f33a0c..6a9f33a0c 100644
--- a/library/HTMLPurifier/AttrTransform/Textarea.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTransform/Textarea.php
diff --git a/library/HTMLPurifier/AttrTypes.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTypes.php
index 3b70520b6..3b70520b6 100644
--- a/library/HTMLPurifier/AttrTypes.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrTypes.php
diff --git a/library/HTMLPurifier/AttrValidator.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrValidator.php
index f97dc93ed..f97dc93ed 100644
--- a/library/HTMLPurifier/AttrValidator.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/AttrValidator.php
diff --git a/library/HTMLPurifier/Bootstrap.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Bootstrap.php
index 707122bb2..707122bb2 100644
--- a/library/HTMLPurifier/Bootstrap.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Bootstrap.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/CSSDefinition.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/CSSDefinition.php
new file mode 100644
index 000000000..47dfd1f66
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/CSSDefinition.php
@@ -0,0 +1,491 @@
+<?php
+
+/**
+ * Defines allowed CSS attributes and what their values are.
+ * @see HTMLPurifier_HTMLDefinition
+ */
+class HTMLPurifier_CSSDefinition extends HTMLPurifier_Definition
+{
+
+ public $type = 'CSS';
+
+ /**
+ * Assoc array of attribute name to definition object.
+ * @type HTMLPurifier_AttrDef[]
+ */
+ public $info = array();
+
+ /**
+ * Constructs the info array. The meat of this class.
+ * @param HTMLPurifier_Config $config
+ */
+ protected function doSetup($config)
+ {
+ $this->info['text-align'] = new HTMLPurifier_AttrDef_Enum(
+ array('left', 'right', 'center', 'justify'),
+ false
+ );
+
+ $border_style =
+ $this->info['border-bottom-style'] =
+ $this->info['border-right-style'] =
+ $this->info['border-left-style'] =
+ $this->info['border-top-style'] = new HTMLPurifier_AttrDef_Enum(
+ array(
+ 'none',
+ 'hidden',
+ 'dotted',
+ 'dashed',
+ 'solid',
+ 'double',
+ 'groove',
+ 'ridge',
+ 'inset',
+ 'outset'
+ ),
+ false
+ );
+
+ $this->info['border-style'] = new HTMLPurifier_AttrDef_CSS_Multiple($border_style);
+
+ $this->info['clear'] = new HTMLPurifier_AttrDef_Enum(
+ array('none', 'left', 'right', 'both'),
+ false
+ );
+ $this->info['float'] = new HTMLPurifier_AttrDef_Enum(
+ array('none', 'left', 'right'),
+ false
+ );
+ $this->info['font-style'] = new HTMLPurifier_AttrDef_Enum(
+ array('normal', 'italic', 'oblique'),
+ false
+ );
+ $this->info['font-variant'] = new HTMLPurifier_AttrDef_Enum(
+ array('normal', 'small-caps'),
+ false
+ );
+
+ $uri_or_none = new HTMLPurifier_AttrDef_CSS_Composite(
+ array(
+ new HTMLPurifier_AttrDef_Enum(array('none')),
+ new HTMLPurifier_AttrDef_CSS_URI()
+ )
+ );
+
+ $this->info['list-style-position'] = new HTMLPurifier_AttrDef_Enum(
+ array('inside', 'outside'),
+ false
+ );
+ $this->info['list-style-type'] = new HTMLPurifier_AttrDef_Enum(
+ array(
+ 'disc',
+ 'circle',
+ 'square',
+ 'decimal',
+ 'lower-roman',
+ 'upper-roman',
+ 'lower-alpha',
+ 'upper-alpha',
+ 'none'
+ ),
+ false
+ );
+ $this->info['list-style-image'] = $uri_or_none;
+
+ $this->info['list-style'] = new HTMLPurifier_AttrDef_CSS_ListStyle($config);
+
+ $this->info['text-transform'] = new HTMLPurifier_AttrDef_Enum(
+ array('capitalize', 'uppercase', 'lowercase', 'none'),
+ false
+ );
+ $this->info['color'] = new HTMLPurifier_AttrDef_CSS_Color();
+
+ $this->info['background-image'] = $uri_or_none;
+ $this->info['background-repeat'] = new HTMLPurifier_AttrDef_Enum(
+ array('repeat', 'repeat-x', 'repeat-y', 'no-repeat')
+ );
+ $this->info['background-attachment'] = new HTMLPurifier_AttrDef_Enum(
+ array('scroll', 'fixed')
+ );
+ $this->info['background-position'] = new HTMLPurifier_AttrDef_CSS_BackgroundPosition();
+
+ $border_color =
+ $this->info['border-top-color'] =
+ $this->info['border-bottom-color'] =
+ $this->info['border-left-color'] =
+ $this->info['border-right-color'] =
+ $this->info['background-color'] = new HTMLPurifier_AttrDef_CSS_Composite(
+ array(
+ new HTMLPurifier_AttrDef_Enum(array('transparent')),
+ new HTMLPurifier_AttrDef_CSS_Color()
+ )
+ );
+
+ $this->info['background'] = new HTMLPurifier_AttrDef_CSS_Background($config);
+
+ $this->info['border-color'] = new HTMLPurifier_AttrDef_CSS_Multiple($border_color);
+
+ $border_width =
+ $this->info['border-top-width'] =
+ $this->info['border-bottom-width'] =
+ $this->info['border-left-width'] =
+ $this->info['border-right-width'] = new HTMLPurifier_AttrDef_CSS_Composite(
+ array(
+ new HTMLPurifier_AttrDef_Enum(array('thin', 'medium', 'thick')),
+ new HTMLPurifier_AttrDef_CSS_Length('0') //disallow negative
+ )
+ );
+
+ $this->info['border-width'] = new HTMLPurifier_AttrDef_CSS_Multiple($border_width);
+
+ $this->info['letter-spacing'] = new HTMLPurifier_AttrDef_CSS_Composite(
+ array(
+ new HTMLPurifier_AttrDef_Enum(array('normal')),
+ new HTMLPurifier_AttrDef_CSS_Length()
+ )
+ );
+
+ $this->info['word-spacing'] = new HTMLPurifier_AttrDef_CSS_Composite(
+ array(
+ new HTMLPurifier_AttrDef_Enum(array('normal')),
+ new HTMLPurifier_AttrDef_CSS_Length()
+ )
+ );
+
+ $this->info['font-size'] = new HTMLPurifier_AttrDef_CSS_Composite(
+ array(
+ new HTMLPurifier_AttrDef_Enum(
+ array(
+ 'xx-small',
+ 'x-small',
+ 'small',
+ 'medium',
+ 'large',
+ 'x-large',
+ 'xx-large',
+ 'larger',
+ 'smaller'
+ )
+ ),
+ new HTMLPurifier_AttrDef_CSS_Percentage(),
+ new HTMLPurifier_AttrDef_CSS_Length()
+ )
+ );
+
+ $this->info['line-height'] = new HTMLPurifier_AttrDef_CSS_Composite(
+ array(
+ new HTMLPurifier_AttrDef_Enum(array('normal')),
+ new HTMLPurifier_AttrDef_CSS_Number(true), // no negatives
+ new HTMLPurifier_AttrDef_CSS_Length('0'),
+ new HTMLPurifier_AttrDef_CSS_Percentage(true)
+ )
+ );
+
+ $margin =
+ $this->info['margin-top'] =
+ $this->info['margin-bottom'] =
+ $this->info['margin-left'] =
+ $this->info['margin-right'] = new HTMLPurifier_AttrDef_CSS_Composite(
+ array(
+ new HTMLPurifier_AttrDef_CSS_Length(),
+ new HTMLPurifier_AttrDef_CSS_Percentage(),
+ new HTMLPurifier_AttrDef_Enum(array('auto'))
+ )
+ );
+
+ $this->info['margin'] = new HTMLPurifier_AttrDef_CSS_Multiple($margin);
+
+ // non-negative
+ $padding =
+ $this->info['padding-top'] =
+ $this->info['padding-bottom'] =
+ $this->info['padding-left'] =
+ $this->info['padding-right'] = new HTMLPurifier_AttrDef_CSS_Composite(
+ array(
+ new HTMLPurifier_AttrDef_CSS_Length('0'),
+ new HTMLPurifier_AttrDef_CSS_Percentage(true)
+ )
+ );
+
+ $this->info['padding'] = new HTMLPurifier_AttrDef_CSS_Multiple($padding);
+
+ $this->info['text-indent'] = new HTMLPurifier_AttrDef_CSS_Composite(
+ array(
+ new HTMLPurifier_AttrDef_CSS_Length(),
+ new HTMLPurifier_AttrDef_CSS_Percentage()
+ )
+ );
+
+ $trusted_wh = new HTMLPurifier_AttrDef_CSS_Composite(
+ array(
+ new HTMLPurifier_AttrDef_CSS_Length('0'),
+ new HTMLPurifier_AttrDef_CSS_Percentage(true),
+ new HTMLPurifier_AttrDef_Enum(array('auto'))
+ )
+ );
+ $max = $config->get('CSS.MaxImgLength');
+
+ $this->info['min-width'] =
+ $this->info['max-width'] =
+ $this->info['min-height'] =
+ $this->info['max-height'] =
+ $this->info['width'] =
+ $this->info['height'] =
+ $max === null ?
+ $trusted_wh :
+ new HTMLPurifier_AttrDef_Switch(
+ 'img',
+ // For img tags:
+ new HTMLPurifier_AttrDef_CSS_Composite(
+ array(
+ new HTMLPurifier_AttrDef_CSS_Length('0', $max),
+ new HTMLPurifier_AttrDef_Enum(array('auto'))
+ )
+ ),
+ // For everyone else:
+ $trusted_wh
+ );
+
+ $this->info['text-decoration'] = new HTMLPurifier_AttrDef_CSS_TextDecoration();
+
+ $this->info['font-family'] = new HTMLPurifier_AttrDef_CSS_FontFamily();
+
+ // this could use specialized code
+ $this->info['font-weight'] = new HTMLPurifier_AttrDef_Enum(
+ array(
+ 'normal',
+ 'bold',
+ 'bolder',
+ 'lighter',
+ '100',
+ '200',
+ '300',
+ '400',
+ '500',
+ '600',
+ '700',
+ '800',
+ '900'
+ ),
+ false
+ );
+
+ // MUST be called after other font properties, as it references
+ // a CSSDefinition object
+ $this->info['font'] = new HTMLPurifier_AttrDef_CSS_Font($config);
+
+ // same here
+ $this->info['border'] =
+ $this->info['border-bottom'] =
+ $this->info['border-top'] =
+ $this->info['border-left'] =
+ $this->info['border-right'] = new HTMLPurifier_AttrDef_CSS_Border($config);
+
+ $this->info['border-collapse'] = new HTMLPurifier_AttrDef_Enum(
+ array('collapse', 'separate')
+ );
+
+ $this->info['caption-side'] = new HTMLPurifier_AttrDef_Enum(
+ array('top', 'bottom')
+ );
+
+ $this->info['table-layout'] = new HTMLPurifier_AttrDef_Enum(
+ array('auto', 'fixed')
+ );
+
+ $this->info['vertical-align'] = new HTMLPurifier_AttrDef_CSS_Composite(
+ array(
+ new HTMLPurifier_AttrDef_Enum(
+ array(
+ 'baseline',
+ 'sub',
+ 'super',
+ 'top',
+ 'text-top',
+ 'middle',
+ 'bottom',
+ 'text-bottom'
+ )
+ ),
+ new HTMLPurifier_AttrDef_CSS_Length(),
+ new HTMLPurifier_AttrDef_CSS_Percentage()
+ )
+ );
+
+ $this->info['border-spacing'] = new HTMLPurifier_AttrDef_CSS_Multiple(new HTMLPurifier_AttrDef_CSS_Length(), 2);
+
+ // These CSS properties don't work on many browsers, but we live
+ // in THE FUTURE!
+ $this->info['white-space'] = new HTMLPurifier_AttrDef_Enum(
+ array('nowrap', 'normal', 'pre', 'pre-wrap', 'pre-line')
+ );
+
+ if ($config->get('CSS.Proprietary')) {
+ $this->doSetupProprietary($config);
+ }
+
+ if ($config->get('CSS.AllowTricky')) {
+ $this->doSetupTricky($config);
+ }
+
+ if ($config->get('CSS.Trusted')) {
+ $this->doSetupTrusted($config);
+ }
+
+ $allow_important = $config->get('CSS.AllowImportant');
+ // wrap all attr-defs with decorator that handles !important
+ foreach ($this->info as $k => $v) {
+ $this->info[$k] = new HTMLPurifier_AttrDef_CSS_ImportantDecorator($v, $allow_important);
+ }
+
+ $this->setupConfigStuff($config);
+ }
+
+ /**
+ * @param HTMLPurifier_Config $config
+ */
+ protected function doSetupProprietary($config)
+ {
+ // Internet Explorer only scrollbar colors
+ $this->info['scrollbar-arrow-color'] = new HTMLPurifier_AttrDef_CSS_Color();
+ $this->info['scrollbar-base-color'] = new HTMLPurifier_AttrDef_CSS_Color();
+ $this->info['scrollbar-darkshadow-color'] = new HTMLPurifier_AttrDef_CSS_Color();
+ $this->info['scrollbar-face-color'] = new HTMLPurifier_AttrDef_CSS_Color();
+ $this->info['scrollbar-highlight-color'] = new HTMLPurifier_AttrDef_CSS_Color();
+ $this->info['scrollbar-shadow-color'] = new HTMLPurifier_AttrDef_CSS_Color();
+
+ // vendor specific prefixes of opacity
+ $this->info['-moz-opacity'] = new HTMLPurifier_AttrDef_CSS_AlphaValue();
+ $this->info['-khtml-opacity'] = new HTMLPurifier_AttrDef_CSS_AlphaValue();
+
+ // only opacity, for now
+ $this->info['filter'] = new HTMLPurifier_AttrDef_CSS_Filter();
+
+ // more CSS3
+ $this->info['page-break-after'] =
+ $this->info['page-break-before'] = new HTMLPurifier_AttrDef_Enum(
+ array(
+ 'auto',
+ 'always',
+ 'avoid',
+ 'left',
+ 'right'
+ )
+ );
+ $this->info['page-break-inside'] = new HTMLPurifier_AttrDef_Enum(array('auto', 'avoid'));
+
+ $border_radius = new HTMLPurifier_AttrDef_CSS_Composite(
+ array(
+ new HTMLPurifier_AttrDef_CSS_Percentage(true), // disallow negative
+ new HTMLPurifier_AttrDef_CSS_Length('0') // disallow negative
+ ));
+
+ $this->info['border-top-left-radius'] =
+ $this->info['border-top-right-radius'] =
+ $this->info['border-bottom-right-radius'] =
+ $this->info['border-bottom-left-radius'] = new HTMLPurifier_AttrDef_CSS_Multiple($border_radius, 2);
+ // TODO: support SLASH syntax
+ $this->info['border-radius'] = new HTMLPurifier_AttrDef_CSS_Multiple($border_radius, 4);
+
+ }
+
+ /**
+ * @param HTMLPurifier_Config $config
+ */
+ protected function doSetupTricky($config)
+ {
+ $this->info['display'] = new HTMLPurifier_AttrDef_Enum(
+ array(
+ 'inline',
+ 'block',
+ 'list-item',
+ 'run-in',
+ 'compact',
+ 'marker',
+ 'table',
+ 'inline-block',
+ 'inline-table',
+ 'table-row-group',
+ 'table-header-group',
+ 'table-footer-group',
+ 'table-row',
+ 'table-column-group',
+ 'table-column',
+ 'table-cell',
+ 'table-caption',
+ 'none'
+ )
+ );
+ $this->info['visibility'] = new HTMLPurifier_AttrDef_Enum(
+ array('visible', 'hidden', 'collapse')
+ );
+ $this->info['overflow'] = new HTMLPurifier_AttrDef_Enum(array('visible', 'hidden', 'auto', 'scroll'));
+ $this->info['opacity'] = new HTMLPurifier_AttrDef_CSS_AlphaValue();
+ }
+
+ /**
+ * @param HTMLPurifier_Config $config
+ */
+ protected function doSetupTrusted($config)
+ {
+ $this->info['position'] = new HTMLPurifier_AttrDef_Enum(
+ array('static', 'relative', 'absolute', 'fixed')
+ );
+ $this->info['top'] =
+ $this->info['left'] =
+ $this->info['right'] =
+ $this->info['bottom'] = new HTMLPurifier_AttrDef_CSS_Composite(
+ array(
+ new HTMLPurifier_AttrDef_CSS_Length(),
+ new HTMLPurifier_AttrDef_CSS_Percentage(),
+ new HTMLPurifier_AttrDef_Enum(array('auto')),
+ )
+ );
+ $this->info['z-index'] = new HTMLPurifier_AttrDef_CSS_Composite(
+ array(
+ new HTMLPurifier_AttrDef_Integer(),
+ new HTMLPurifier_AttrDef_Enum(array('auto')),
+ )
+ );
+ }
+
+ /**
+ * Performs extra config-based processing. Based off of
+ * HTMLPurifier_HTMLDefinition.
+ * @param HTMLPurifier_Config $config
+ * @todo Refactor duplicate elements into common class (probably using
+ * composition, not inheritance).
+ */
+ protected function setupConfigStuff($config)
+ {
+ // setup allowed elements
+ $support = "(for information on implementing this, see the " .
+ "support forums) ";
+ $allowed_properties = $config->get('CSS.AllowedProperties');
+ if ($allowed_properties !== null) {
+ foreach ($this->info as $name => $d) {
+ if (!isset($allowed_properties[$name])) {
+ unset($this->info[$name]);
+ }
+ unset($allowed_properties[$name]);
+ }
+ // emit errors
+ foreach ($allowed_properties as $name => $d) {
+ // :TODO: Is this htmlspecialchars() call really necessary?
+ $name = htmlspecialchars($name);
+ trigger_error("Style attribute '$name' is not supported $support", E_USER_WARNING);
+ }
+ }
+
+ $forbidden_properties = $config->get('CSS.ForbiddenProperties');
+ if ($forbidden_properties !== null) {
+ foreach ($this->info as $name => $d) {
+ if (isset($forbidden_properties[$name])) {
+ unset($this->info[$name]);
+ }
+ }
+ }
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/ChildDef.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef.php
index 8eb17b82e..8eb17b82e 100644
--- a/library/HTMLPurifier/ChildDef.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef.php
diff --git a/library/HTMLPurifier/ChildDef/Chameleon.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Chameleon.php
index 7439be26b..7439be26b 100644
--- a/library/HTMLPurifier/ChildDef/Chameleon.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Chameleon.php
diff --git a/library/HTMLPurifier/ChildDef/Custom.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Custom.php
index 128132e96..128132e96 100644
--- a/library/HTMLPurifier/ChildDef/Custom.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Custom.php
diff --git a/library/HTMLPurifier/ChildDef/Empty.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Empty.php
index a8a6cbdd2..a8a6cbdd2 100644
--- a/library/HTMLPurifier/ChildDef/Empty.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Empty.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/List.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/List.php
new file mode 100644
index 000000000..4fc70e0ef
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/List.php
@@ -0,0 +1,92 @@
+<?php
+
+/**
+ * Definition for list containers ul and ol.
+ *
+ * What does this do? The big thing is to handle ol/ul at the top
+ * level of list nodes, which should be handled specially by /folding/
+ * them into the previous list node. We generally shouldn't ever
+ * see other disallowed elements, because the autoclose behavior
+ * in MakeWellFormed handles it.
+ */
+class HTMLPurifier_ChildDef_List extends HTMLPurifier_ChildDef
+{
+ /**
+ * @type string
+ */
+ public $type = 'list';
+ /**
+ * @type array
+ */
+ // lying a little bit, so that we can handle ul and ol ourselves
+ // XXX: This whole business with 'wrap' is all a bit unsatisfactory
+ public $elements = array('li' => true, 'ul' => true, 'ol' => true);
+
+ /**
+ * @param array $children
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return array
+ */
+ public function validateChildren($children, $config, $context)
+ {
+ // Flag for subclasses
+ $this->whitespace = false;
+
+ // if there are no tokens, delete parent node
+ if (empty($children)) {
+ return false;
+ }
+
+ // if li is not allowed, delete parent node
+ if (!isset($config->getHTMLDefinition()->info['li'])) {
+ trigger_error("Cannot allow ul/ol without allowing li", E_USER_WARNING);
+ return false;
+ }
+
+ // the new set of children
+ $result = array();
+
+ // a little sanity check to make sure it's not ALL whitespace
+ $all_whitespace = true;
+
+ $current_li = null;
+
+ foreach ($children as $node) {
+ if (!empty($node->is_whitespace)) {
+ $result[] = $node;
+ continue;
+ }
+ $all_whitespace = false; // phew, we're not talking about whitespace
+
+ if ($node->name === 'li') {
+ // good
+ $current_li = $node;
+ $result[] = $node;
+ } else {
+ // we want to tuck this into the previous li
+ // Invariant: we expect the node to be ol/ul
+ // ToDo: Make this more robust in the case of not ol/ul
+ // by distinguishing between existing li and li created
+ // to handle non-list elements; non-list elements should
+ // not be appended to an existing li; only li created
+ // for non-list. This distinction is not currently made.
+ if ($current_li === null) {
+ $current_li = new HTMLPurifier_Node_Element('li');
+ $result[] = $current_li;
+ }
+ $current_li->children[] = $node;
+ $current_li->empty = false; // XXX fascinating! Check for this error elsewhere ToDo
+ }
+ }
+ if (empty($result)) {
+ return false;
+ }
+ if ($all_whitespace) {
+ return false;
+ }
+ return $result;
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/ChildDef/Optional.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Optional.php
index b9468063b..b9468063b 100644
--- a/library/HTMLPurifier/ChildDef/Optional.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Optional.php
diff --git a/library/HTMLPurifier/ChildDef/Required.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Required.php
index 0d1c8f5f3..0d1c8f5f3 100644
--- a/library/HTMLPurifier/ChildDef/Required.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Required.php
diff --git a/library/HTMLPurifier/ChildDef/StrictBlockquote.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/StrictBlockquote.php
index 3270a46e1..3270a46e1 100644
--- a/library/HTMLPurifier/ChildDef/StrictBlockquote.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/StrictBlockquote.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Table.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Table.php
new file mode 100644
index 000000000..cb6b3e6cd
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ChildDef/Table.php
@@ -0,0 +1,224 @@
+<?php
+
+/**
+ * Definition for tables. The general idea is to extract out all of the
+ * essential bits, and then reconstruct it later.
+ *
+ * This is a bit confusing, because the DTDs and the W3C
+ * validators seem to disagree on the appropriate definition. The
+ * DTD claims:
+ *
+ * (CAPTION?, (COL*|COLGROUP*), THEAD?, TFOOT?, TBODY+)
+ *
+ * But actually, the HTML4 spec then has this to say:
+ *
+ * The TBODY start tag is always required except when the table
+ * contains only one table body and no table head or foot sections.
+ * The TBODY end tag may always be safely omitted.
+ *
+ * So the DTD is kind of wrong. The validator is, unfortunately, kind
+ * of on crack.
+ *
+ * The definition changed again in XHTML1.1; and in my opinion, this
+ * formulation makes the most sense.
+ *
+ * caption?, ( col* | colgroup* ), (( thead?, tfoot?, tbody+ ) | ( tr+ ))
+ *
+ * Essentially, we have two modes: thead/tfoot/tbody mode, and tr mode.
+ * If we encounter a thead, tfoot or tbody, we are placed in the former
+ * mode, and we *must* wrap any stray tr segments with a tbody. But if
+ * we don't run into any of them, just have tr tags is OK.
+ */
+class HTMLPurifier_ChildDef_Table extends HTMLPurifier_ChildDef
+{
+ /**
+ * @type bool
+ */
+ public $allow_empty = false;
+
+ /**
+ * @type string
+ */
+ public $type = 'table';
+
+ /**
+ * @type array
+ */
+ public $elements = array(
+ 'tr' => true,
+ 'tbody' => true,
+ 'thead' => true,
+ 'tfoot' => true,
+ 'caption' => true,
+ 'colgroup' => true,
+ 'col' => true
+ );
+
+ public function __construct()
+ {
+ }
+
+ /**
+ * @param array $children
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return array
+ */
+ public function validateChildren($children, $config, $context)
+ {
+ if (empty($children)) {
+ return false;
+ }
+
+ // only one of these elements is allowed in a table
+ $caption = false;
+ $thead = false;
+ $tfoot = false;
+
+ // whitespace
+ $initial_ws = array();
+ $after_caption_ws = array();
+ $after_thead_ws = array();
+ $after_tfoot_ws = array();
+
+ // as many of these as you want
+ $cols = array();
+ $content = array();
+
+ $tbody_mode = false; // if true, then we need to wrap any stray
+ // <tr>s with a <tbody>.
+
+ $ws_accum =& $initial_ws;
+
+ foreach ($children as $node) {
+ if ($node instanceof HTMLPurifier_Node_Comment) {
+ $ws_accum[] = $node;
+ continue;
+ }
+ switch ($node->name) {
+ case 'tbody':
+ $tbody_mode = true;
+ // fall through
+ case 'tr':
+ $content[] = $node;
+ $ws_accum =& $content;
+ break;
+ case 'caption':
+ // there can only be one caption!
+ if ($caption !== false) break;
+ $caption = $node;
+ $ws_accum =& $after_caption_ws;
+ break;
+ case 'thead':
+ $tbody_mode = true;
+ // XXX This breaks rendering properties with
+ // Firefox, which never floats a <thead> to
+ // the top. Ever. (Our scheme will float the
+ // first <thead> to the top.) So maybe
+ // <thead>s that are not first should be
+ // turned into <tbody>? Very tricky, indeed.
+ if ($thead === false) {
+ $thead = $node;
+ $ws_accum =& $after_thead_ws;
+ } else {
+ // Oops, there's a second one! What
+ // should we do? Current behavior is to
+ // transmutate the first and last entries into
+ // tbody tags, and then put into content.
+ // Maybe a better idea is to *attach
+ // it* to the existing thead or tfoot?
+ // We don't do this, because Firefox
+ // doesn't float an extra tfoot to the
+ // bottom like it does for the first one.
+ $node->name = 'tbody';
+ $content[] = $node;
+ $ws_accum =& $content;
+ }
+ break;
+ case 'tfoot':
+ // see above for some aveats
+ $tbody_mode = true;
+ if ($tfoot === false) {
+ $tfoot = $node;
+ $ws_accum =& $after_tfoot_ws;
+ } else {
+ $node->name = 'tbody';
+ $content[] = $node;
+ $ws_accum =& $content;
+ }
+ break;
+ case 'colgroup':
+ case 'col':
+ $cols[] = $node;
+ $ws_accum =& $cols;
+ break;
+ case '#PCDATA':
+ // How is whitespace handled? We treat is as sticky to
+ // the *end* of the previous element. So all of the
+ // nonsense we have worked on is to keep things
+ // together.
+ if (!empty($node->is_whitespace)) {
+ $ws_accum[] = $node;
+ }
+ break;
+ }
+ }
+
+ if (empty($content)) {
+ return false;
+ }
+
+ $ret = $initial_ws;
+ if ($caption !== false) {
+ $ret[] = $caption;
+ $ret = array_merge($ret, $after_caption_ws);
+ }
+ if ($cols !== false) {
+ $ret = array_merge($ret, $cols);
+ }
+ if ($thead !== false) {
+ $ret[] = $thead;
+ $ret = array_merge($ret, $after_thead_ws);
+ }
+ if ($tfoot !== false) {
+ $ret[] = $tfoot;
+ $ret = array_merge($ret, $after_tfoot_ws);
+ }
+
+ if ($tbody_mode) {
+ // we have to shuffle tr into tbody
+ $current_tr_tbody = null;
+
+ foreach($content as $node) {
+ switch ($node->name) {
+ case 'tbody':
+ $current_tr_tbody = null;
+ $ret[] = $node;
+ break;
+ case 'tr':
+ if ($current_tr_tbody === null) {
+ $current_tr_tbody = new HTMLPurifier_Node_Element('tbody');
+ $ret[] = $current_tr_tbody;
+ }
+ $current_tr_tbody->children[] = $node;
+ break;
+ case '#PCDATA':
+ //assert($node->is_whitespace);
+ if ($current_tr_tbody === null) {
+ $ret[] = $node;
+ } else {
+ $current_tr_tbody->children[] = $node;
+ }
+ break;
+ }
+ }
+ } else {
+ $ret = array_merge($ret, $content);
+ }
+
+ return $ret;
+
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Config.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Config.php
new file mode 100644
index 000000000..3648364b3
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Config.php
@@ -0,0 +1,920 @@
+<?php
+
+/**
+ * Configuration object that triggers customizable behavior.
+ *
+ * @warning This class is strongly defined: that means that the class
+ * will fail if an undefined directive is retrieved or set.
+ *
+ * @note Many classes that could (although many times don't) use the
+ * configuration object make it a mandatory parameter. This is
+ * because a configuration object should always be forwarded,
+ * otherwise, you run the risk of missing a parameter and then
+ * being stumped when a configuration directive doesn't work.
+ *
+ * @todo Reconsider some of the public member variables
+ */
+class HTMLPurifier_Config
+{
+
+ /**
+ * HTML Purifier's version
+ * @type string
+ */
+ public $version = '4.9.3';
+
+ /**
+ * Whether or not to automatically finalize
+ * the object if a read operation is done.
+ * @type bool
+ */
+ public $autoFinalize = true;
+
+ // protected member variables
+
+ /**
+ * Namespace indexed array of serials for specific namespaces.
+ * @see getSerial() for more info.
+ * @type string[]
+ */
+ protected $serials = array();
+
+ /**
+ * Serial for entire configuration object.
+ * @type string
+ */
+ protected $serial;
+
+ /**
+ * Parser for variables.
+ * @type HTMLPurifier_VarParser_Flexible
+ */
+ protected $parser = null;
+
+ /**
+ * Reference HTMLPurifier_ConfigSchema for value checking.
+ * @type HTMLPurifier_ConfigSchema
+ * @note This is public for introspective purposes. Please don't
+ * abuse!
+ */
+ public $def;
+
+ /**
+ * Indexed array of definitions.
+ * @type HTMLPurifier_Definition[]
+ */
+ protected $definitions;
+
+ /**
+ * Whether or not config is finalized.
+ * @type bool
+ */
+ protected $finalized = false;
+
+ /**
+ * Property list containing configuration directives.
+ * @type array
+ */
+ protected $plist;
+
+ /**
+ * Whether or not a set is taking place due to an alias lookup.
+ * @type bool
+ */
+ private $aliasMode;
+
+ /**
+ * Set to false if you do not want line and file numbers in errors.
+ * (useful when unit testing). This will also compress some errors
+ * and exceptions.
+ * @type bool
+ */
+ public $chatty = true;
+
+ /**
+ * Current lock; only gets to this namespace are allowed.
+ * @type string
+ */
+ private $lock;
+
+ /**
+ * Constructor
+ * @param HTMLPurifier_ConfigSchema $definition ConfigSchema that defines
+ * what directives are allowed.
+ * @param HTMLPurifier_PropertyList $parent
+ */
+ public function __construct($definition, $parent = null)
+ {
+ $parent = $parent ? $parent : $definition->defaultPlist;
+ $this->plist = new HTMLPurifier_PropertyList($parent);
+ $this->def = $definition; // keep a copy around for checking
+ $this->parser = new HTMLPurifier_VarParser_Flexible();
+ }
+
+ /**
+ * Convenience constructor that creates a config object based on a mixed var
+ * @param mixed $config Variable that defines the state of the config
+ * object. Can be: a HTMLPurifier_Config() object,
+ * an array of directives based on loadArray(),
+ * or a string filename of an ini file.
+ * @param HTMLPurifier_ConfigSchema $schema Schema object
+ * @return HTMLPurifier_Config Configured object
+ */
+ public static function create($config, $schema = null)
+ {
+ if ($config instanceof HTMLPurifier_Config) {
+ // pass-through
+ return $config;
+ }
+ if (!$schema) {
+ $ret = HTMLPurifier_Config::createDefault();
+ } else {
+ $ret = new HTMLPurifier_Config($schema);
+ }
+ if (is_string($config)) {
+ $ret->loadIni($config);
+ } elseif (is_array($config)) $ret->loadArray($config);
+ return $ret;
+ }
+
+ /**
+ * Creates a new config object that inherits from a previous one.
+ * @param HTMLPurifier_Config $config Configuration object to inherit from.
+ * @return HTMLPurifier_Config object with $config as its parent.
+ */
+ public static function inherit(HTMLPurifier_Config $config)
+ {
+ return new HTMLPurifier_Config($config->def, $config->plist);
+ }
+
+ /**
+ * Convenience constructor that creates a default configuration object.
+ * @return HTMLPurifier_Config default object.
+ */
+ public static function createDefault()
+ {
+ $definition = HTMLPurifier_ConfigSchema::instance();
+ $config = new HTMLPurifier_Config($definition);
+ return $config;
+ }
+
+ /**
+ * Retrieves a value from the configuration.
+ *
+ * @param string $key String key
+ * @param mixed $a
+ *
+ * @return mixed
+ */
+ public function get($key, $a = null)
+ {
+ if ($a !== null) {
+ $this->triggerError(
+ "Using deprecated API: use \$config->get('$key.$a') instead",
+ E_USER_WARNING
+ );
+ $key = "$key.$a";
+ }
+ if (!$this->finalized) {
+ $this->autoFinalize();
+ }
+ if (!isset($this->def->info[$key])) {
+ // can't add % due to SimpleTest bug
+ $this->triggerError(
+ 'Cannot retrieve value of undefined directive ' . htmlspecialchars($key),
+ E_USER_WARNING
+ );
+ return;
+ }
+ if (isset($this->def->info[$key]->isAlias)) {
+ $d = $this->def->info[$key];
+ $this->triggerError(
+ 'Cannot get value from aliased directive, use real name ' . $d->key,
+ E_USER_ERROR
+ );
+ return;
+ }
+ if ($this->lock) {
+ list($ns) = explode('.', $key);
+ if ($ns !== $this->lock) {
+ $this->triggerError(
+ 'Cannot get value of namespace ' . $ns . ' when lock for ' .
+ $this->lock .
+ ' is active, this probably indicates a Definition setup method ' .
+ 'is accessing directives that are not within its namespace',
+ E_USER_ERROR
+ );
+ return;
+ }
+ }
+ return $this->plist->get($key);
+ }
+
+ /**
+ * Retrieves an array of directives to values from a given namespace
+ *
+ * @param string $namespace String namespace
+ *
+ * @return array
+ */
+ public function getBatch($namespace)
+ {
+ if (!$this->finalized) {
+ $this->autoFinalize();
+ }
+ $full = $this->getAll();
+ if (!isset($full[$namespace])) {
+ $this->triggerError(
+ 'Cannot retrieve undefined namespace ' .
+ htmlspecialchars($namespace),
+ E_USER_WARNING
+ );
+ return;
+ }
+ return $full[$namespace];
+ }
+
+ /**
+ * Returns a SHA-1 signature of a segment of the configuration object
+ * that uniquely identifies that particular configuration
+ *
+ * @param string $namespace Namespace to get serial for
+ *
+ * @return string
+ * @note Revision is handled specially and is removed from the batch
+ * before processing!
+ */
+ public function getBatchSerial($namespace)
+ {
+ if (empty($this->serials[$namespace])) {
+ $batch = $this->getBatch($namespace);
+ unset($batch['DefinitionRev']);
+ $this->serials[$namespace] = sha1(serialize($batch));
+ }
+ return $this->serials[$namespace];
+ }
+
+ /**
+ * Returns a SHA-1 signature for the entire configuration object
+ * that uniquely identifies that particular configuration
+ *
+ * @return string
+ */
+ public function getSerial()
+ {
+ if (empty($this->serial)) {
+ $this->serial = sha1(serialize($this->getAll()));
+ }
+ return $this->serial;
+ }
+
+ /**
+ * Retrieves all directives, organized by namespace
+ *
+ * @warning This is a pretty inefficient function, avoid if you can
+ */
+ public function getAll()
+ {
+ if (!$this->finalized) {
+ $this->autoFinalize();
+ }
+ $ret = array();
+ foreach ($this->plist->squash() as $name => $value) {
+ list($ns, $key) = explode('.', $name, 2);
+ $ret[$ns][$key] = $value;
+ }
+ return $ret;
+ }
+
+ /**
+ * Sets a value to configuration.
+ *
+ * @param string $key key
+ * @param mixed $value value
+ * @param mixed $a
+ */
+ public function set($key, $value, $a = null)
+ {
+ if (strpos($key, '.') === false) {
+ $namespace = $key;
+ $directive = $value;
+ $value = $a;
+ $key = "$key.$directive";
+ $this->triggerError("Using deprecated API: use \$config->set('$key', ...) instead", E_USER_NOTICE);
+ } else {
+ list($namespace) = explode('.', $key);
+ }
+ if ($this->isFinalized('Cannot set directive after finalization')) {
+ return;
+ }
+ if (!isset($this->def->info[$key])) {
+ $this->triggerError(
+ 'Cannot set undefined directive ' . htmlspecialchars($key) . ' to value',
+ E_USER_WARNING
+ );
+ return;
+ }
+ $def = $this->def->info[$key];
+
+ if (isset($def->isAlias)) {
+ if ($this->aliasMode) {
+ $this->triggerError(
+ 'Double-aliases not allowed, please fix '.
+ 'ConfigSchema bug with' . $key,
+ E_USER_ERROR
+ );
+ return;
+ }
+ $this->aliasMode = true;
+ $this->set($def->key, $value);
+ $this->aliasMode = false;
+ $this->triggerError("$key is an alias, preferred directive name is {$def->key}", E_USER_NOTICE);
+ return;
+ }
+
+ // Raw type might be negative when using the fully optimized form
+ // of stdClass, which indicates allow_null == true
+ $rtype = is_int($def) ? $def : $def->type;
+ if ($rtype < 0) {
+ $type = -$rtype;
+ $allow_null = true;
+ } else {
+ $type = $rtype;
+ $allow_null = isset($def->allow_null);
+ }
+
+ try {
+ $value = $this->parser->parse($value, $type, $allow_null);
+ } catch (HTMLPurifier_VarParserException $e) {
+ $this->triggerError(
+ 'Value for ' . $key . ' is of invalid type, should be ' .
+ HTMLPurifier_VarParser::getTypeName($type),
+ E_USER_WARNING
+ );
+ return;
+ }
+ if (is_string($value) && is_object($def)) {
+ // resolve value alias if defined
+ if (isset($def->aliases[$value])) {
+ $value = $def->aliases[$value];
+ }
+ // check to see if the value is allowed
+ if (isset($def->allowed) && !isset($def->allowed[$value])) {
+ $this->triggerError(
+ 'Value not supported, valid values are: ' .
+ $this->_listify($def->allowed),
+ E_USER_WARNING
+ );
+ return;
+ }
+ }
+ $this->plist->set($key, $value);
+
+ // reset definitions if the directives they depend on changed
+ // this is a very costly process, so it's discouraged
+ // with finalization
+ if ($namespace == 'HTML' || $namespace == 'CSS' || $namespace == 'URI') {
+ $this->definitions[$namespace] = null;
+ }
+
+ $this->serials[$namespace] = false;
+ }
+
+ /**
+ * Convenience function for error reporting
+ *
+ * @param array $lookup
+ *
+ * @return string
+ */
+ private function _listify($lookup)
+ {
+ $list = array();
+ foreach ($lookup as $name => $b) {
+ $list[] = $name;
+ }
+ return implode(', ', $list);
+ }
+
+ /**
+ * Retrieves object reference to the HTML definition.
+ *
+ * @param bool $raw Return a copy that has not been setup yet. Must be
+ * called before it's been setup, otherwise won't work.
+ * @param bool $optimized If true, this method may return null, to
+ * indicate that a cached version of the modified
+ * definition object is available and no further edits
+ * are necessary. Consider using
+ * maybeGetRawHTMLDefinition, which is more explicitly
+ * named, instead.
+ *
+ * @return HTMLPurifier_HTMLDefinition
+ */
+ public function getHTMLDefinition($raw = false, $optimized = false)
+ {
+ return $this->getDefinition('HTML', $raw, $optimized);
+ }
+
+ /**
+ * Retrieves object reference to the CSS definition
+ *
+ * @param bool $raw Return a copy that has not been setup yet. Must be
+ * called before it's been setup, otherwise won't work.
+ * @param bool $optimized If true, this method may return null, to
+ * indicate that a cached version of the modified
+ * definition object is available and no further edits
+ * are necessary. Consider using
+ * maybeGetRawCSSDefinition, which is more explicitly
+ * named, instead.
+ *
+ * @return HTMLPurifier_CSSDefinition
+ */
+ public function getCSSDefinition($raw = false, $optimized = false)
+ {
+ return $this->getDefinition('CSS', $raw, $optimized);
+ }
+
+ /**
+ * Retrieves object reference to the URI definition
+ *
+ * @param bool $raw Return a copy that has not been setup yet. Must be
+ * called before it's been setup, otherwise won't work.
+ * @param bool $optimized If true, this method may return null, to
+ * indicate that a cached version of the modified
+ * definition object is available and no further edits
+ * are necessary. Consider using
+ * maybeGetRawURIDefinition, which is more explicitly
+ * named, instead.
+ *
+ * @return HTMLPurifier_URIDefinition
+ */
+ public function getURIDefinition($raw = false, $optimized = false)
+ {
+ return $this->getDefinition('URI', $raw, $optimized);
+ }
+
+ /**
+ * Retrieves a definition
+ *
+ * @param string $type Type of definition: HTML, CSS, etc
+ * @param bool $raw Whether or not definition should be returned raw
+ * @param bool $optimized Only has an effect when $raw is true. Whether
+ * or not to return null if the result is already present in
+ * the cache. This is off by default for backwards
+ * compatibility reasons, but you need to do things this
+ * way in order to ensure that caching is done properly.
+ * Check out enduser-customize.html for more details.
+ * We probably won't ever change this default, as much as the
+ * maybe semantics is the "right thing to do."
+ *
+ * @throws HTMLPurifier_Exception
+ * @return HTMLPurifier_Definition
+ */
+ public function getDefinition($type, $raw = false, $optimized = false)
+ {
+ if ($optimized && !$raw) {
+ throw new HTMLPurifier_Exception("Cannot set optimized = true when raw = false");
+ }
+ if (!$this->finalized) {
+ $this->autoFinalize();
+ }
+ // temporarily suspend locks, so we can handle recursive definition calls
+ $lock = $this->lock;
+ $this->lock = null;
+ $factory = HTMLPurifier_DefinitionCacheFactory::instance();
+ $cache = $factory->create($type, $this);
+ $this->lock = $lock;
+ if (!$raw) {
+ // full definition
+ // ---------------
+ // check if definition is in memory
+ if (!empty($this->definitions[$type])) {
+ $def = $this->definitions[$type];
+ // check if the definition is setup
+ if ($def->setup) {
+ return $def;
+ } else {
+ $def->setup($this);
+ if ($def->optimized) {
+ $cache->add($def, $this);
+ }
+ return $def;
+ }
+ }
+ // check if definition is in cache
+ $def = $cache->get($this);
+ if ($def) {
+ // definition in cache, save to memory and return it
+ $this->definitions[$type] = $def;
+ return $def;
+ }
+ // initialize it
+ $def = $this->initDefinition($type);
+ // set it up
+ $this->lock = $type;
+ $def->setup($this);
+ $this->lock = null;
+ // save in cache
+ $cache->add($def, $this);
+ // return it
+ return $def;
+ } else {
+ // raw definition
+ // --------------
+ // check preconditions
+ $def = null;
+ if ($optimized) {
+ if (is_null($this->get($type . '.DefinitionID'))) {
+ // fatally error out if definition ID not set
+ throw new HTMLPurifier_Exception(
+ "Cannot retrieve raw version without specifying %$type.DefinitionID"
+ );
+ }
+ }
+ if (!empty($this->definitions[$type])) {
+ $def = $this->definitions[$type];
+ if ($def->setup && !$optimized) {
+ $extra = $this->chatty ?
+ " (try moving this code block earlier in your initialization)" :
+ "";
+ throw new HTMLPurifier_Exception(
+ "Cannot retrieve raw definition after it has already been setup" .
+ $extra
+ );
+ }
+ if ($def->optimized === null) {
+ $extra = $this->chatty ? " (try flushing your cache)" : "";
+ throw new HTMLPurifier_Exception(
+ "Optimization status of definition is unknown" . $extra
+ );
+ }
+ if ($def->optimized !== $optimized) {
+ $msg = $optimized ? "optimized" : "unoptimized";
+ $extra = $this->chatty ?
+ " (this backtrace is for the first inconsistent call, which was for a $msg raw definition)"
+ : "";
+ throw new HTMLPurifier_Exception(
+ "Inconsistent use of optimized and unoptimized raw definition retrievals" . $extra
+ );
+ }
+ }
+ // check if definition was in memory
+ if ($def) {
+ if ($def->setup) {
+ // invariant: $optimized === true (checked above)
+ return null;
+ } else {
+ return $def;
+ }
+ }
+ // if optimized, check if definition was in cache
+ // (because we do the memory check first, this formulation
+ // is prone to cache slamming, but I think
+ // guaranteeing that either /all/ of the raw
+ // setup code or /none/ of it is run is more important.)
+ if ($optimized) {
+ // This code path only gets run once; once we put
+ // something in $definitions (which is guaranteed by the
+ // trailing code), we always short-circuit above.
+ $def = $cache->get($this);
+ if ($def) {
+ // save the full definition for later, but don't
+ // return it yet
+ $this->definitions[$type] = $def;
+ return null;
+ }
+ }
+ // check invariants for creation
+ if (!$optimized) {
+ if (!is_null($this->get($type . '.DefinitionID'))) {
+ if ($this->chatty) {
+ $this->triggerError(
+ 'Due to a documentation error in previous version of HTML Purifier, your ' .
+ 'definitions are not being cached. If this is OK, you can remove the ' .
+ '%$type.DefinitionRev and %$type.DefinitionID declaration. Otherwise, ' .
+ 'modify your code to use maybeGetRawDefinition, and test if the returned ' .
+ 'value is null before making any edits (if it is null, that means that a ' .
+ 'cached version is available, and no raw operations are necessary). See ' .
+ '<a href="http://htmlpurifier.org/docs/enduser-customize.html#optimized">' .
+ 'Customize</a> for more details',
+ E_USER_WARNING
+ );
+ } else {
+ $this->triggerError(
+ "Useless DefinitionID declaration",
+ E_USER_WARNING
+ );
+ }
+ }
+ }
+ // initialize it
+ $def = $this->initDefinition($type);
+ $def->optimized = $optimized;
+ return $def;
+ }
+ throw new HTMLPurifier_Exception("The impossible happened!");
+ }
+
+ /**
+ * Initialise definition
+ *
+ * @param string $type What type of definition to create
+ *
+ * @return HTMLPurifier_CSSDefinition|HTMLPurifier_HTMLDefinition|HTMLPurifier_URIDefinition
+ * @throws HTMLPurifier_Exception
+ */
+ private function initDefinition($type)
+ {
+ // quick checks failed, let's create the object
+ if ($type == 'HTML') {
+ $def = new HTMLPurifier_HTMLDefinition();
+ } elseif ($type == 'CSS') {
+ $def = new HTMLPurifier_CSSDefinition();
+ } elseif ($type == 'URI') {
+ $def = new HTMLPurifier_URIDefinition();
+ } else {
+ throw new HTMLPurifier_Exception(
+ "Definition of $type type not supported"
+ );
+ }
+ $this->definitions[$type] = $def;
+ return $def;
+ }
+
+ public function maybeGetRawDefinition($name)
+ {
+ return $this->getDefinition($name, true, true);
+ }
+
+ /**
+ * @return HTMLPurifier_HTMLDefinition
+ */
+ public function maybeGetRawHTMLDefinition()
+ {
+ return $this->getDefinition('HTML', true, true);
+ }
+
+ /**
+ * @return HTMLPurifier_CSSDefinition
+ */
+ public function maybeGetRawCSSDefinition()
+ {
+ return $this->getDefinition('CSS', true, true);
+ }
+
+ /**
+ * @return HTMLPurifier_URIDefinition
+ */
+ public function maybeGetRawURIDefinition()
+ {
+ return $this->getDefinition('URI', true, true);
+ }
+
+ /**
+ * Loads configuration values from an array with the following structure:
+ * Namespace.Directive => Value
+ *
+ * @param array $config_array Configuration associative array
+ */
+ public function loadArray($config_array)
+ {
+ if ($this->isFinalized('Cannot load directives after finalization')) {
+ return;
+ }
+ foreach ($config_array as $key => $value) {
+ $key = str_replace('_', '.', $key);
+ if (strpos($key, '.') !== false) {
+ $this->set($key, $value);
+ } else {
+ $namespace = $key;
+ $namespace_values = $value;
+ foreach ($namespace_values as $directive => $value2) {
+ $this->set($namespace .'.'. $directive, $value2);
+ }
+ }
+ }
+ }
+
+ /**
+ * Returns a list of array(namespace, directive) for all directives
+ * that are allowed in a web-form context as per an allowed
+ * namespaces/directives list.
+ *
+ * @param array $allowed List of allowed namespaces/directives
+ * @param HTMLPurifier_ConfigSchema $schema Schema to use, if not global copy
+ *
+ * @return array
+ */
+ public static function getAllowedDirectivesForForm($allowed, $schema = null)
+ {
+ if (!$schema) {
+ $schema = HTMLPurifier_ConfigSchema::instance();
+ }
+ if ($allowed !== true) {
+ if (is_string($allowed)) {
+ $allowed = array($allowed);
+ }
+ $allowed_ns = array();
+ $allowed_directives = array();
+ $blacklisted_directives = array();
+ foreach ($allowed as $ns_or_directive) {
+ if (strpos($ns_or_directive, '.') !== false) {
+ // directive
+ if ($ns_or_directive[0] == '-') {
+ $blacklisted_directives[substr($ns_or_directive, 1)] = true;
+ } else {
+ $allowed_directives[$ns_or_directive] = true;
+ }
+ } else {
+ // namespace
+ $allowed_ns[$ns_or_directive] = true;
+ }
+ }
+ }
+ $ret = array();
+ foreach ($schema->info as $key => $def) {
+ list($ns, $directive) = explode('.', $key, 2);
+ if ($allowed !== true) {
+ if (isset($blacklisted_directives["$ns.$directive"])) {
+ continue;
+ }
+ if (!isset($allowed_directives["$ns.$directive"]) && !isset($allowed_ns[$ns])) {
+ continue;
+ }
+ }
+ if (isset($def->isAlias)) {
+ continue;
+ }
+ if ($directive == 'DefinitionID' || $directive == 'DefinitionRev') {
+ continue;
+ }
+ $ret[] = array($ns, $directive);
+ }
+ return $ret;
+ }
+
+ /**
+ * Loads configuration values from $_GET/$_POST that were posted
+ * via ConfigForm
+ *
+ * @param array $array $_GET or $_POST array to import
+ * @param string|bool $index Index/name that the config variables are in
+ * @param array|bool $allowed List of allowed namespaces/directives
+ * @param bool $mq_fix Boolean whether or not to enable magic quotes fix
+ * @param HTMLPurifier_ConfigSchema $schema Schema to use, if not global copy
+ *
+ * @return mixed
+ */
+ public static function loadArrayFromForm($array, $index = false, $allowed = true, $mq_fix = true, $schema = null)
+ {
+ $ret = HTMLPurifier_Config::prepareArrayFromForm($array, $index, $allowed, $mq_fix, $schema);
+ $config = HTMLPurifier_Config::create($ret, $schema);
+ return $config;
+ }
+
+ /**
+ * Merges in configuration values from $_GET/$_POST to object. NOT STATIC.
+ *
+ * @param array $array $_GET or $_POST array to import
+ * @param string|bool $index Index/name that the config variables are in
+ * @param array|bool $allowed List of allowed namespaces/directives
+ * @param bool $mq_fix Boolean whether or not to enable magic quotes fix
+ */
+ public function mergeArrayFromForm($array, $index = false, $allowed = true, $mq_fix = true)
+ {
+ $ret = HTMLPurifier_Config::prepareArrayFromForm($array, $index, $allowed, $mq_fix, $this->def);
+ $this->loadArray($ret);
+ }
+
+ /**
+ * Prepares an array from a form into something usable for the more
+ * strict parts of HTMLPurifier_Config
+ *
+ * @param array $array $_GET or $_POST array to import
+ * @param string|bool $index Index/name that the config variables are in
+ * @param array|bool $allowed List of allowed namespaces/directives
+ * @param bool $mq_fix Boolean whether or not to enable magic quotes fix
+ * @param HTMLPurifier_ConfigSchema $schema Schema to use, if not global copy
+ *
+ * @return array
+ */
+ public static function prepareArrayFromForm($array, $index = false, $allowed = true, $mq_fix = true, $schema = null)
+ {
+ if ($index !== false) {
+ $array = (isset($array[$index]) && is_array($array[$index])) ? $array[$index] : array();
+ }
+ $mq = $mq_fix && function_exists('get_magic_quotes_gpc') && get_magic_quotes_gpc();
+
+ $allowed = HTMLPurifier_Config::getAllowedDirectivesForForm($allowed, $schema);
+ $ret = array();
+ foreach ($allowed as $key) {
+ list($ns, $directive) = $key;
+ $skey = "$ns.$directive";
+ if (!empty($array["Null_$skey"])) {
+ $ret[$ns][$directive] = null;
+ continue;
+ }
+ if (!isset($array[$skey])) {
+ continue;
+ }
+ $value = $mq ? stripslashes($array[$skey]) : $array[$skey];
+ $ret[$ns][$directive] = $value;
+ }
+ return $ret;
+ }
+
+ /**
+ * Loads configuration values from an ini file
+ *
+ * @param string $filename Name of ini file
+ */
+ public function loadIni($filename)
+ {
+ if ($this->isFinalized('Cannot load directives after finalization')) {
+ return;
+ }
+ $array = parse_ini_file($filename, true);
+ $this->loadArray($array);
+ }
+
+ /**
+ * Checks whether or not the configuration object is finalized.
+ *
+ * @param string|bool $error String error message, or false for no error
+ *
+ * @return bool
+ */
+ public function isFinalized($error = false)
+ {
+ if ($this->finalized && $error) {
+ $this->triggerError($error, E_USER_ERROR);
+ }
+ return $this->finalized;
+ }
+
+ /**
+ * Finalizes configuration only if auto finalize is on and not
+ * already finalized
+ */
+ public function autoFinalize()
+ {
+ if ($this->autoFinalize) {
+ $this->finalize();
+ } else {
+ $this->plist->squash(true);
+ }
+ }
+
+ /**
+ * Finalizes a configuration object, prohibiting further change
+ */
+ public function finalize()
+ {
+ $this->finalized = true;
+ $this->parser = null;
+ }
+
+ /**
+ * Produces a nicely formatted error message by supplying the
+ * stack frame information OUTSIDE of HTMLPurifier_Config.
+ *
+ * @param string $msg An error message
+ * @param int $no An error number
+ */
+ protected function triggerError($msg, $no)
+ {
+ // determine previous stack frame
+ $extra = '';
+ if ($this->chatty) {
+ $trace = debug_backtrace();
+ // zip(tail(trace), trace) -- but PHP is not Haskell har har
+ for ($i = 0, $c = count($trace); $i < $c - 1; $i++) {
+ // XXX this is not correct on some versions of HTML Purifier
+ if ($trace[$i + 1]['class'] === 'HTMLPurifier_Config') {
+ continue;
+ }
+ $frame = $trace[$i];
+ $extra = " invoked on line {$frame['line']} in file {$frame['file']}";
+ break;
+ }
+ }
+ trigger_error($msg . $extra, $no);
+ }
+
+ /**
+ * Returns a serialized form of the configuration object that can
+ * be reconstituted.
+ *
+ * @return string
+ */
+ public function serialize()
+ {
+ $this->getDefinition('HTML');
+ $this->getDefinition('CSS');
+ $this->getDefinition('URI');
+ return serialize($this);
+ }
+
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema.php
new file mode 100644
index 000000000..655c0e97a
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema.php
@@ -0,0 +1,176 @@
+<?php
+
+/**
+ * Configuration definition, defines directives and their defaults.
+ */
+class HTMLPurifier_ConfigSchema
+{
+ /**
+ * Defaults of the directives and namespaces.
+ * @type array
+ * @note This shares the exact same structure as HTMLPurifier_Config::$conf
+ */
+ public $defaults = array();
+
+ /**
+ * The default property list. Do not edit this property list.
+ * @type array
+ */
+ public $defaultPlist;
+
+ /**
+ * Definition of the directives.
+ * The structure of this is:
+ *
+ * array(
+ * 'Namespace' => array(
+ * 'Directive' => new stdClass(),
+ * )
+ * )
+ *
+ * The stdClass may have the following properties:
+ *
+ * - If isAlias isn't set:
+ * - type: Integer type of directive, see HTMLPurifier_VarParser for definitions
+ * - allow_null: If set, this directive allows null values
+ * - aliases: If set, an associative array of value aliases to real values
+ * - allowed: If set, a lookup array of allowed (string) values
+ * - If isAlias is set:
+ * - namespace: Namespace this directive aliases to
+ * - name: Directive name this directive aliases to
+ *
+ * In certain degenerate cases, stdClass will actually be an integer. In
+ * that case, the value is equivalent to an stdClass with the type
+ * property set to the integer. If the integer is negative, type is
+ * equal to the absolute value of integer, and allow_null is true.
+ *
+ * This class is friendly with HTMLPurifier_Config. If you need introspection
+ * about the schema, you're better of using the ConfigSchema_Interchange,
+ * which uses more memory but has much richer information.
+ * @type array
+ */
+ public $info = array();
+
+ /**
+ * Application-wide singleton
+ * @type HTMLPurifier_ConfigSchema
+ */
+ protected static $singleton;
+
+ public function __construct()
+ {
+ $this->defaultPlist = new HTMLPurifier_PropertyList();
+ }
+
+ /**
+ * Unserializes the default ConfigSchema.
+ * @return HTMLPurifier_ConfigSchema
+ */
+ public static function makeFromSerial()
+ {
+ $contents = file_get_contents(HTMLPURIFIER_PREFIX . '/HTMLPurifier/ConfigSchema/schema.ser');
+ $r = unserialize($contents);
+ if (!$r) {
+ $hash = sha1($contents);
+ trigger_error("Unserialization of configuration schema failed, sha1 of file was $hash", E_USER_ERROR);
+ }
+ return $r;
+ }
+
+ /**
+ * Retrieves an instance of the application-wide configuration definition.
+ * @param HTMLPurifier_ConfigSchema $prototype
+ * @return HTMLPurifier_ConfigSchema
+ */
+ public static function instance($prototype = null)
+ {
+ if ($prototype !== null) {
+ HTMLPurifier_ConfigSchema::$singleton = $prototype;
+ } elseif (HTMLPurifier_ConfigSchema::$singleton === null || $prototype === true) {
+ HTMLPurifier_ConfigSchema::$singleton = HTMLPurifier_ConfigSchema::makeFromSerial();
+ }
+ return HTMLPurifier_ConfigSchema::$singleton;
+ }
+
+ /**
+ * Defines a directive for configuration
+ * @warning Will fail of directive's namespace is defined.
+ * @warning This method's signature is slightly different from the legacy
+ * define() static method! Beware!
+ * @param string $key Name of directive
+ * @param mixed $default Default value of directive
+ * @param string $type Allowed type of the directive. See
+ * HTMLPurifier_DirectiveDef::$type for allowed values
+ * @param bool $allow_null Whether or not to allow null values
+ */
+ public function add($key, $default, $type, $allow_null)
+ {
+ $obj = new stdClass();
+ $obj->type = is_int($type) ? $type : HTMLPurifier_VarParser::$types[$type];
+ if ($allow_null) {
+ $obj->allow_null = true;
+ }
+ $this->info[$key] = $obj;
+ $this->defaults[$key] = $default;
+ $this->defaultPlist->set($key, $default);
+ }
+
+ /**
+ * Defines a directive value alias.
+ *
+ * Directive value aliases are convenient for developers because it lets
+ * them set a directive to several values and get the same result.
+ * @param string $key Name of Directive
+ * @param array $aliases Hash of aliased values to the real alias
+ */
+ public function addValueAliases($key, $aliases)
+ {
+ if (!isset($this->info[$key]->aliases)) {
+ $this->info[$key]->aliases = array();
+ }
+ foreach ($aliases as $alias => $real) {
+ $this->info[$key]->aliases[$alias] = $real;
+ }
+ }
+
+ /**
+ * Defines a set of allowed values for a directive.
+ * @warning This is slightly different from the corresponding static
+ * method definition.
+ * @param string $key Name of directive
+ * @param array $allowed Lookup array of allowed values
+ */
+ public function addAllowedValues($key, $allowed)
+ {
+ $this->info[$key]->allowed = $allowed;
+ }
+
+ /**
+ * Defines a directive alias for backwards compatibility
+ * @param string $key Directive that will be aliased
+ * @param string $new_key Directive that the alias will be to
+ */
+ public function addAlias($key, $new_key)
+ {
+ $obj = new stdClass;
+ $obj->key = $new_key;
+ $obj->isAlias = true;
+ $this->info[$key] = $obj;
+ }
+
+ /**
+ * Replaces any stdClass that only has the type property with type integer.
+ */
+ public function postProcess()
+ {
+ foreach ($this->info as $key => $v) {
+ if (count((array) $v) == 1) {
+ $this->info[$key] = $v->type;
+ } elseif (count((array) $v) == 2 && isset($v->allow_null)) {
+ $this->info[$key] = -$v->type;
+ }
+ }
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/ConfigSchema/Builder/ConfigSchema.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Builder/ConfigSchema.php
index d5906cd46..d5906cd46 100644
--- a/library/HTMLPurifier/ConfigSchema/Builder/ConfigSchema.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Builder/ConfigSchema.php
diff --git a/library/HTMLPurifier/ConfigSchema/Builder/Xml.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Builder/Xml.php
index 5fa56f7dd..5fa56f7dd 100644
--- a/library/HTMLPurifier/ConfigSchema/Builder/Xml.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Builder/Xml.php
diff --git a/library/HTMLPurifier/ConfigSchema/Exception.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Exception.php
index 2671516c5..2671516c5 100644
--- a/library/HTMLPurifier/ConfigSchema/Exception.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Exception.php
diff --git a/library/HTMLPurifier/ConfigSchema/Interchange.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Interchange.php
index 0e08ae8fe..0e08ae8fe 100644
--- a/library/HTMLPurifier/ConfigSchema/Interchange.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Interchange.php
diff --git a/library/HTMLPurifier/ConfigSchema/Interchange/Directive.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Interchange/Directive.php
index 127a39a67..127a39a67 100644
--- a/library/HTMLPurifier/ConfigSchema/Interchange/Directive.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Interchange/Directive.php
diff --git a/library/HTMLPurifier/ConfigSchema/Interchange/Id.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Interchange/Id.php
index 126f09d95..126f09d95 100644
--- a/library/HTMLPurifier/ConfigSchema/Interchange/Id.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Interchange/Id.php
diff --git a/library/HTMLPurifier/ConfigSchema/InterchangeBuilder.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/InterchangeBuilder.php
index 655e6dd1b..655e6dd1b 100644
--- a/library/HTMLPurifier/ConfigSchema/InterchangeBuilder.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/InterchangeBuilder.php
diff --git a/library/HTMLPurifier/ConfigSchema/Validator.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Validator.php
index fb3127788..fb3127788 100644
--- a/library/HTMLPurifier/ConfigSchema/Validator.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/Validator.php
diff --git a/library/HTMLPurifier/ConfigSchema/ValidatorAtom.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/ValidatorAtom.php
index c9aa3644a..c9aa3644a 100644
--- a/library/HTMLPurifier/ConfigSchema/ValidatorAtom.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/ValidatorAtom.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema.ser b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema.ser
new file mode 100644
index 000000000..371e948f1
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema.ser
Binary files differ
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedClasses.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedClasses.txt
index 0517fed0a..0517fed0a 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedClasses.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedClasses.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedFrameTargets.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedFrameTargets.txt
index 249edd647..249edd647 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedFrameTargets.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedFrameTargets.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedRel.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedRel.txt
index 9a8fa6a2e..9a8fa6a2e 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedRel.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedRel.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedRev.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedRev.txt
index b01788348..b01788348 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedRev.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.AllowedRev.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Attr.ClassUseCDATA.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.ClassUseCDATA.txt
index e774b823b..e774b823b 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Attr.ClassUseCDATA.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.ClassUseCDATA.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultImageAlt.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultImageAlt.txt
index 533165e17..533165e17 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultImageAlt.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultImageAlt.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultInvalidImage.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultInvalidImage.txt
index 9eb7e3846..9eb7e3846 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultInvalidImage.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultInvalidImage.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultInvalidImageAlt.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultInvalidImageAlt.txt
index 2f17bf477..2f17bf477 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultInvalidImageAlt.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultInvalidImageAlt.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultTextDir.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultTextDir.txt
index 52654b53a..52654b53a 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultTextDir.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.DefaultTextDir.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Attr.EnableID.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.EnableID.txt
index 6440d2103..6440d2103 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Attr.EnableID.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.EnableID.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Attr.ForbiddenClasses.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.ForbiddenClasses.txt
index f31d226f5..f31d226f5 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Attr.ForbiddenClasses.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.ForbiddenClasses.txt
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.ID.HTML5.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.ID.HTML5.txt
new file mode 100644
index 000000000..735d4b7a1
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.ID.HTML5.txt
@@ -0,0 +1,10 @@
+Attr.ID.HTML5
+TYPE: bool/null
+DEFAULT: null
+VERSION: 4.8.0
+--DESCRIPTION--
+In HTML5, restrictions on the format of the id attribute have been significantly
+relaxed, such that any string is valid so long as it contains no spaces and
+is at least one character. In lieu of a general HTML5 compatibility flag,
+set this configuration directive to true to use the relaxed rules.
+--# vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Attr.IDBlacklist.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.IDBlacklist.txt
index 5f2b5e3d2..5f2b5e3d2 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Attr.IDBlacklist.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.IDBlacklist.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Attr.IDBlacklistRegexp.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.IDBlacklistRegexp.txt
index 6f5824586..6f5824586 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Attr.IDBlacklistRegexp.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.IDBlacklistRegexp.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Attr.IDPrefix.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.IDPrefix.txt
index cc49d43fd..cc49d43fd 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Attr.IDPrefix.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.IDPrefix.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Attr.IDPrefixLocal.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.IDPrefixLocal.txt
index 2c5924a7a..2c5924a7a 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Attr.IDPrefixLocal.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Attr.IDPrefixLocal.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.AutoParagraph.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.AutoParagraph.txt
index d5caa1bb9..d5caa1bb9 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.AutoParagraph.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.AutoParagraph.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.Custom.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.Custom.txt
index 2a476481a..2a476481a 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.Custom.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.Custom.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.DisplayLinkURI.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.DisplayLinkURI.txt
index 663064a34..663064a34 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.DisplayLinkURI.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.DisplayLinkURI.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.Linkify.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.Linkify.txt
index 3a48ba960..3a48ba960 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.Linkify.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.Linkify.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.PurifierLinkify.DocURL.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.PurifierLinkify.DocURL.txt
index db58b1346..db58b1346 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.PurifierLinkify.DocURL.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.PurifierLinkify.DocURL.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.PurifierLinkify.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.PurifierLinkify.txt
index 7996488be..7996488be 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.PurifierLinkify.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.PurifierLinkify.txt
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveEmpty.Predicate.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveEmpty.Predicate.txt
new file mode 100644
index 000000000..6367fe23c
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveEmpty.Predicate.txt
@@ -0,0 +1,14 @@
+AutoFormat.RemoveEmpty.Predicate
+TYPE: hash
+VERSION: 4.7.0
+DEFAULT: array('colgroup' => array(), 'th' => array(), 'td' => array(), 'iframe' => array('src'))
+--DESCRIPTION--
+<p>
+ Given that an element has no contents, it will be removed by default, unless
+ this predicate dictates otherwise. The predicate can either be an associative
+ map from tag name to list of attributes that must be present for the element
+ to be considered preserved: thus, the default always preserves <code>colgroup</code>,
+ <code>th</code> and <code>td</code>, and also <code>iframe</code> if it
+ has a <code>src</code>.
+</p>
+--# vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveEmpty.RemoveNbsp.Exceptions.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveEmpty.RemoveNbsp.Exceptions.txt
index 35c393b4e..35c393b4e 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveEmpty.RemoveNbsp.Exceptions.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveEmpty.RemoveNbsp.Exceptions.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveEmpty.RemoveNbsp.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveEmpty.RemoveNbsp.txt
index ca17eb1dc..ca17eb1dc 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveEmpty.RemoveNbsp.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveEmpty.RemoveNbsp.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveEmpty.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveEmpty.txt
index 34657ba47..34657ba47 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveEmpty.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveEmpty.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveSpansWithoutAttributes.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveSpansWithoutAttributes.txt
index dde990ab2..dde990ab2 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveSpansWithoutAttributes.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/AutoFormat.RemoveSpansWithoutAttributes.txt
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowDuplicates.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowDuplicates.txt
new file mode 100644
index 000000000..4d054b1f0
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowDuplicates.txt
@@ -0,0 +1,11 @@
+CSS.AllowDuplicates
+TYPE: bool
+DEFAULT: false
+VERSION: 4.8.0
+--DESCRIPTION--
+<p>
+ By default, HTML Purifier removes duplicate CSS properties,
+ like <code>color:red; color:blue</code>. If this is set to
+ true, duplicate properties are allowed.
+</p>
+--# vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowImportant.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowImportant.txt
index b324608f7..b324608f7 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowImportant.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowImportant.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowTricky.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowTricky.txt
index 748be0eec..748be0eec 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowTricky.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowTricky.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowedFonts.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowedFonts.txt
index 3fd465406..3fd465406 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowedFonts.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowedFonts.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowedProperties.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowedProperties.txt
index 460112ebe..460112ebe 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowedProperties.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.AllowedProperties.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/CSS.DefinitionRev.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.DefinitionRev.txt
index 5cb7dda3b..5cb7dda3b 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/CSS.DefinitionRev.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.DefinitionRev.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/CSS.ForbiddenProperties.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.ForbiddenProperties.txt
index f1f5c5f12..f1f5c5f12 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/CSS.ForbiddenProperties.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.ForbiddenProperties.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/CSS.MaxImgLength.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.MaxImgLength.txt
index 7a3291470..7a3291470 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/CSS.MaxImgLength.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.MaxImgLength.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/CSS.Proprietary.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.Proprietary.txt
index 148eedb8b..148eedb8b 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/CSS.Proprietary.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.Proprietary.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/CSS.Trusted.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.Trusted.txt
index e733a61e8..e733a61e8 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/CSS.Trusted.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/CSS.Trusted.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Cache.DefinitionImpl.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Cache.DefinitionImpl.txt
index c486724c8..c486724c8 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Cache.DefinitionImpl.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Cache.DefinitionImpl.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Cache.SerializerPath.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Cache.SerializerPath.txt
index 54036507d..54036507d 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Cache.SerializerPath.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Cache.SerializerPath.txt
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Cache.SerializerPermissions.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Cache.SerializerPermissions.txt
new file mode 100644
index 000000000..2e0cc8104
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Cache.SerializerPermissions.txt
@@ -0,0 +1,16 @@
+Cache.SerializerPermissions
+TYPE: int/null
+VERSION: 4.3.0
+DEFAULT: 0755
+--DESCRIPTION--
+
+<p>
+ Directory permissions of the files and directories created inside
+ the DefinitionCache/Serializer or other custom serializer path.
+</p>
+<p>
+ In HTML Purifier 4.8.0, this also supports <code>NULL</code>,
+ which means that no chmod'ing or directory creation shall
+ occur.
+</p>
+--# vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Core.AggressivelyFixLt.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.AggressivelyFixLt.txt
index 568cbf3b3..568cbf3b3 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Core.AggressivelyFixLt.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.AggressivelyFixLt.txt
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.AggressivelyRemoveScript.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.AggressivelyRemoveScript.txt
new file mode 100644
index 000000000..b2b6ab149
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.AggressivelyRemoveScript.txt
@@ -0,0 +1,16 @@
+Core.AggressivelyRemoveScript
+TYPE: bool
+VERSION: 4.9.0
+DEFAULT: true
+--DESCRIPTION--
+<p>
+ This directive enables aggressive pre-filter removal of
+ script tags. This is not necessary for security,
+ but it can help work around a bug in libxml where embedded
+ HTML elements inside script sections cause the parser to
+ choke. To revert to pre-4.9.0 behavior, set this to false.
+ This directive has no effect if %Core.Trusted is true,
+ %Core.RemoveScriptContents is false, or %Core.HiddenElements
+ does not contain script.
+</p>
+--# vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Core.AllowHostnameUnderscore.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.AllowHostnameUnderscore.txt
index 2c910cc7d..2c910cc7d 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Core.AllowHostnameUnderscore.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.AllowHostnameUnderscore.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Core.CollectErrors.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.CollectErrors.txt
index d7317911f..d7317911f 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Core.CollectErrors.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.CollectErrors.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Core.ColorKeywords.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.ColorKeywords.txt
index c572c14ec..c572c14ec 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Core.ColorKeywords.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.ColorKeywords.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Core.ConvertDocumentToFragment.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.ConvertDocumentToFragment.txt
index 64b114fce..64b114fce 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Core.ConvertDocumentToFragment.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.ConvertDocumentToFragment.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Core.DirectLexLineNumberSyncInterval.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.DirectLexLineNumberSyncInterval.txt
index 36f16e07e..36f16e07e 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Core.DirectLexLineNumberSyncInterval.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.DirectLexLineNumberSyncInterval.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Core.DisableExcludes.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.DisableExcludes.txt
index 1cd4c2c96..1cd4c2c96 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Core.DisableExcludes.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.DisableExcludes.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Core.EnableIDNA.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.EnableIDNA.txt
index ce243c35d..ce243c35d 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Core.EnableIDNA.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.EnableIDNA.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Core.Encoding.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.Encoding.txt
index 8bfb47c3a..8bfb47c3a 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Core.Encoding.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.Encoding.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Core.EscapeInvalidChildren.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.EscapeInvalidChildren.txt
index a3881be75..a3881be75 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Core.EscapeInvalidChildren.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.EscapeInvalidChildren.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Core.EscapeInvalidTags.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.EscapeInvalidTags.txt
index a7a5b249b..a7a5b249b 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Core.EscapeInvalidTags.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.EscapeInvalidTags.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Core.EscapeNonASCIICharacters.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.EscapeNonASCIICharacters.txt
index abb499948..abb499948 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Core.EscapeNonASCIICharacters.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.EscapeNonASCIICharacters.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Core.HiddenElements.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.HiddenElements.txt
index 915391edb..915391edb 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Core.HiddenElements.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.HiddenElements.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Core.Language.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.Language.txt
index 233fca14f..233fca14f 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Core.Language.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.Language.txt
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.LegacyEntityDecoder.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.LegacyEntityDecoder.txt
new file mode 100644
index 000000000..392b43649
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.LegacyEntityDecoder.txt
@@ -0,0 +1,36 @@
+Core.LegacyEntityDecoder
+TYPE: bool
+VERSION: 4.9.0
+DEFAULT: false
+--DESCRIPTION--
+<p>
+ Prior to HTML Purifier 4.9.0, entities were decoded by performing
+ a global search replace for all entities whose decoded versions
+ did not have special meanings under HTML, and replaced them with
+ their decoded versions. We would match all entities, even if they did
+ not have a trailing semicolon, but only if there weren't any trailing
+ alphanumeric characters.
+</p>
+<table>
+<tr><th>Original</th><th>Text</th><th>Attribute</th></tr>
+<tr><td>&amp;yen;</td><td>&yen;</td><td>&yen;</td></tr>
+<tr><td>&amp;yen</td><td>&yen;</td><td>&yen;</td></tr>
+<tr><td>&amp;yena</td><td>&amp;yena</td><td>&amp;yena</td></tr>
+<tr><td>&amp;yen=</td><td>&yen;=</td><td>&yen;=</td></tr>
+</table>
+<p>
+ In HTML Purifier 4.9.0, we changed the behavior of entity parsing
+ to match entities that had missing trailing semicolons in less
+ cases, to more closely match HTML5 parsing behavior:
+</p>
+<table>
+<tr><th>Original</th><th>Text</th><th>Attribute</th></tr>
+<tr><td>&amp;yen;</td><td>&yen;</td><td>&yen;</td></tr>
+<tr><td>&amp;yen</td><td>&yen;</td><td>&yen;</td></tr>
+<tr><td>&amp;yena</td><td>&yen;a</td><td>&amp;yena</td></tr>
+<tr><td>&amp;yen=</td><td>&yen;=</td><td>&amp;yen=</td></tr>
+</table>
+<p>
+ This flag reverts back to pre-HTML Purifier 4.9.0 behavior.
+</p>
+--# vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Core.LexerImpl.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.LexerImpl.txt
index 8983e2cca..8983e2cca 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Core.LexerImpl.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.LexerImpl.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Core.MaintainLineNumbers.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.MaintainLineNumbers.txt
index eb841a759..eb841a759 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Core.MaintainLineNumbers.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.MaintainLineNumbers.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Core.NormalizeNewlines.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.NormalizeNewlines.txt
index d77f5360d..d77f5360d 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Core.NormalizeNewlines.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.NormalizeNewlines.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Core.RemoveInvalidImg.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.RemoveInvalidImg.txt
index 4070c2a0d..4070c2a0d 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Core.RemoveInvalidImg.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.RemoveInvalidImg.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Core.RemoveProcessingInstructions.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.RemoveProcessingInstructions.txt
index 3397d9f71..3397d9f71 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Core.RemoveProcessingInstructions.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.RemoveProcessingInstructions.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Core.RemoveScriptContents.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.RemoveScriptContents.txt
index a4cd966df..a4cd966df 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Core.RemoveScriptContents.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Core.RemoveScriptContents.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Filter.Custom.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Filter.Custom.txt
index 3db50ef20..3db50ef20 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Filter.Custom.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Filter.Custom.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.Escaping.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.Escaping.txt
index 16829bcda..16829bcda 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.Escaping.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.Escaping.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.Scope.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.Scope.txt
index 7f95f54d1..7f95f54d1 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.Scope.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.Scope.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.TidyImpl.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.TidyImpl.txt
index 6c231b2d7..6c231b2d7 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.TidyImpl.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.TidyImpl.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.txt
index 078d08741..078d08741 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Filter.YouTube.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Filter.YouTube.txt
index 321eaa2d8..321eaa2d8 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Filter.YouTube.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Filter.YouTube.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.Allowed.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Allowed.txt
index 0b2c106da..0b2c106da 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.Allowed.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Allowed.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedAttributes.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedAttributes.txt
index fcf093f17..fcf093f17 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedAttributes.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedAttributes.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedComments.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedComments.txt
index 140e21423..140e21423 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedComments.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedComments.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedCommentsRegexp.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedCommentsRegexp.txt
index f22e977d4..f22e977d4 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedCommentsRegexp.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedCommentsRegexp.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedElements.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedElements.txt
index 1d3fa7907..1d3fa7907 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedElements.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedElements.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedModules.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedModules.txt
index 5a59a55c0..5a59a55c0 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedModules.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.AllowedModules.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.Attr.Name.UseCDATA.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Attr.Name.UseCDATA.txt
index 151fb7b82..151fb7b82 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.Attr.Name.UseCDATA.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Attr.Name.UseCDATA.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.BlockWrapper.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.BlockWrapper.txt
index 45ae469ec..45ae469ec 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.BlockWrapper.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.BlockWrapper.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.CoreModules.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.CoreModules.txt
index 524618879..524618879 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.CoreModules.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.CoreModules.txt
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.CustomDoctype.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.CustomDoctype.txt
new file mode 100644
index 000000000..6ed70b599
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.CustomDoctype.txt
@@ -0,0 +1,9 @@
+HTML.CustomDoctype
+TYPE: string/null
+VERSION: 2.0.1
+DEFAULT: NULL
+--DESCRIPTION--
+
+A custom doctype for power-users who defined their own document
+type. This directive only applies when %HTML.Doctype is blank.
+--# vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.DefinitionID.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.DefinitionID.txt
index 103db754a..103db754a 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.DefinitionID.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.DefinitionID.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.DefinitionRev.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.DefinitionRev.txt
index 229ae0267..229ae0267 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.DefinitionRev.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.DefinitionRev.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.Doctype.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Doctype.txt
index 9dab497f2..9dab497f2 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.Doctype.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Doctype.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.FlashAllowFullScreen.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.FlashAllowFullScreen.txt
index 7878dc0bf..7878dc0bf 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.FlashAllowFullScreen.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.FlashAllowFullScreen.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.ForbiddenAttributes.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.ForbiddenAttributes.txt
index 57358f9ba..57358f9ba 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.ForbiddenAttributes.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.ForbiddenAttributes.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.ForbiddenElements.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.ForbiddenElements.txt
index 93a53e14f..93a53e14f 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.ForbiddenElements.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.ForbiddenElements.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.MaxImgLength.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.MaxImgLength.txt
index e424c386e..e424c386e 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.MaxImgLength.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.MaxImgLength.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.Nofollow.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Nofollow.txt
index 700b30924..700b30924 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.Nofollow.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Nofollow.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.Parent.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Parent.txt
index 62e8e160c..62e8e160c 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.Parent.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Parent.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.Proprietary.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Proprietary.txt
index dfb720496..dfb720496 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.Proprietary.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Proprietary.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.SafeEmbed.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.SafeEmbed.txt
index cdda09a4c..cdda09a4c 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.SafeEmbed.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.SafeEmbed.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.SafeIframe.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.SafeIframe.txt
index 5eb6ec2b5..5eb6ec2b5 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.SafeIframe.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.SafeIframe.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.SafeObject.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.SafeObject.txt
index ceb342e22..ceb342e22 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.SafeObject.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.SafeObject.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.SafeScripting.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.SafeScripting.txt
index 5ebc7a19d..5ebc7a19d 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.SafeScripting.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.SafeScripting.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.Strict.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Strict.txt
index a8b1de56b..a8b1de56b 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.Strict.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Strict.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.TargetBlank.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.TargetBlank.txt
index 587a16778..587a16778 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.TargetBlank.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.TargetBlank.txt
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.TargetNoopener.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.TargetNoopener.txt
new file mode 100644
index 000000000..dd514c0de
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.TargetNoopener.txt
@@ -0,0 +1,10 @@
+--# vim: et sw=4 sts=4
+HTML.TargetNoopener
+TYPE: bool
+VERSION: 4.8.0
+DEFAULT: TRUE
+--DESCRIPTION--
+If enabled, noopener rel attributes are added to links which have
+a target attribute associated with them. This prevents malicious
+destinations from overwriting the original window.
+--# vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.TargetNoreferrer.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.TargetNoreferrer.txt
new file mode 100644
index 000000000..cb5a0b0e5
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.TargetNoreferrer.txt
@@ -0,0 +1,9 @@
+HTML.TargetNoreferrer
+TYPE: bool
+VERSION: 4.8.0
+DEFAULT: TRUE
+--DESCRIPTION--
+If enabled, noreferrer rel attributes are added to links which have
+a target attribute associated with them. This prevents malicious
+destinations from overwriting the original window.
+--# vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.TidyAdd.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.TidyAdd.txt
index b4c271b7f..b4c271b7f 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.TidyAdd.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.TidyAdd.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.TidyLevel.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.TidyLevel.txt
index 4186ccd0d..4186ccd0d 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.TidyLevel.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.TidyLevel.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.TidyRemove.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.TidyRemove.txt
index 996762bd1..996762bd1 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.TidyRemove.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.TidyRemove.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.Trusted.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Trusted.txt
index 1db9237e9..1db9237e9 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.Trusted.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.Trusted.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/HTML.XHTML.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.XHTML.txt
index 2a47e384f..2a47e384f 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/HTML.XHTML.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/HTML.XHTML.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Output.CommentScriptContents.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Output.CommentScriptContents.txt
index 08921fde7..08921fde7 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Output.CommentScriptContents.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Output.CommentScriptContents.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Output.FixInnerHTML.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Output.FixInnerHTML.txt
index d6f0d9f29..d6f0d9f29 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Output.FixInnerHTML.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Output.FixInnerHTML.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Output.FlashCompat.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Output.FlashCompat.txt
index 93398e859..93398e859 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Output.FlashCompat.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Output.FlashCompat.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Output.Newline.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Output.Newline.txt
index 79f8ad82c..79f8ad82c 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Output.Newline.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Output.Newline.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Output.SortAttr.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Output.SortAttr.txt
index 232b02362..232b02362 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Output.SortAttr.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Output.SortAttr.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Output.TidyFormat.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Output.TidyFormat.txt
index 06bab00a0..06bab00a0 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Output.TidyFormat.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Output.TidyFormat.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/Test.ForceNoIconv.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Test.ForceNoIconv.txt
index 071bc0295..071bc0295 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/Test.ForceNoIconv.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/Test.ForceNoIconv.txt
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.AllowedSchemes.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.AllowedSchemes.txt
new file mode 100644
index 000000000..eb97307e2
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.AllowedSchemes.txt
@@ -0,0 +1,18 @@
+URI.AllowedSchemes
+TYPE: lookup
+--DEFAULT--
+array (
+ 'http' => true,
+ 'https' => true,
+ 'mailto' => true,
+ 'ftp' => true,
+ 'nntp' => true,
+ 'news' => true,
+ 'tel' => true,
+)
+--DESCRIPTION--
+Whitelist that defines the schemes that a URI is allowed to have. This
+prevents XSS attacks from using pseudo-schemes like javascript or mocha.
+There is also support for the <code>data</code> and <code>file</code>
+URI schemes, but they are not enabled by default.
+--# vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/ConfigSchema/schema/URI.Base.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.Base.txt
index 876f0680c..876f0680c 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/URI.Base.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.Base.txt
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.DefaultScheme.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.DefaultScheme.txt
new file mode 100644
index 000000000..834bc08c0
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.DefaultScheme.txt
@@ -0,0 +1,15 @@
+URI.DefaultScheme
+TYPE: string/null
+DEFAULT: 'http'
+--DESCRIPTION--
+
+<p>
+ Defines through what scheme the output will be served, in order to
+ select the proper object validator when no scheme information is present.
+</p>
+
+<p>
+ Starting with HTML Purifier 4.9.0, the default scheme can be null, in
+ which case we reject all URIs which do not have explicit schemes.
+</p>
+--# vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/ConfigSchema/schema/URI.DefinitionID.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.DefinitionID.txt
index f05312ba8..f05312ba8 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/URI.DefinitionID.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.DefinitionID.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/URI.DefinitionRev.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.DefinitionRev.txt
index 80cfea93f..80cfea93f 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/URI.DefinitionRev.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.DefinitionRev.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/URI.Disable.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.Disable.txt
index 71ce025a2..71ce025a2 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/URI.Disable.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.Disable.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/URI.DisableExternal.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.DisableExternal.txt
index 13c122c8c..13c122c8c 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/URI.DisableExternal.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.DisableExternal.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/URI.DisableExternalResources.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.DisableExternalResources.txt
index abcc1efd6..abcc1efd6 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/URI.DisableExternalResources.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.DisableExternalResources.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/URI.DisableResources.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.DisableResources.txt
index f891de499..f891de499 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/URI.DisableResources.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.DisableResources.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/URI.Host.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.Host.txt
index ee83b121d..ee83b121d 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/URI.Host.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.Host.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/URI.HostBlacklist.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.HostBlacklist.txt
index 0b6df7625..0b6df7625 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/URI.HostBlacklist.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.HostBlacklist.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/URI.MakeAbsolute.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.MakeAbsolute.txt
index 4214900a5..4214900a5 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/URI.MakeAbsolute.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.MakeAbsolute.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/URI.Munge.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.Munge.txt
index 58c81dcc4..58c81dcc4 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/URI.Munge.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.Munge.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/URI.MungeResources.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.MungeResources.txt
index 6fce0fdc3..6fce0fdc3 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/URI.MungeResources.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.MungeResources.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/URI.MungeSecretKey.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.MungeSecretKey.txt
index 1e17c1d46..1e17c1d46 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/URI.MungeSecretKey.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.MungeSecretKey.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/URI.OverrideAllowedSchemes.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.OverrideAllowedSchemes.txt
index 23331a4e7..23331a4e7 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/URI.OverrideAllowedSchemes.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.OverrideAllowedSchemes.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/URI.SafeIframeRegexp.txt b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.SafeIframeRegexp.txt
index 79084832b..79084832b 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/URI.SafeIframeRegexp.txt
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/URI.SafeIframeRegexp.txt
diff --git a/library/HTMLPurifier/ConfigSchema/schema/info.ini b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/info.ini
index 5de4505e1..5de4505e1 100644
--- a/library/HTMLPurifier/ConfigSchema/schema/info.ini
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ConfigSchema/schema/info.ini
diff --git a/library/HTMLPurifier/ContentSets.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ContentSets.php
index 543e3f8f1..543e3f8f1 100644
--- a/library/HTMLPurifier/ContentSets.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ContentSets.php
diff --git a/library/HTMLPurifier/Context.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Context.php
index 00e509c85..00e509c85 100644
--- a/library/HTMLPurifier/Context.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Context.php
diff --git a/library/HTMLPurifier/Definition.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Definition.php
index bc6d43364..bc6d43364 100644
--- a/library/HTMLPurifier/Definition.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Definition.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache.php
new file mode 100644
index 000000000..9aa8ff354
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache.php
@@ -0,0 +1,129 @@
+<?php
+
+/**
+ * Abstract class representing Definition cache managers that implements
+ * useful common methods and is a factory.
+ * @todo Create a separate maintenance file advanced users can use to
+ * cache their custom HTMLDefinition, which can be loaded
+ * via a configuration directive
+ * @todo Implement memcached
+ */
+abstract class HTMLPurifier_DefinitionCache
+{
+ /**
+ * @type string
+ */
+ public $type;
+
+ /**
+ * @param string $type Type of definition objects this instance of the
+ * cache will handle.
+ */
+ public function __construct($type)
+ {
+ $this->type = $type;
+ }
+
+ /**
+ * Generates a unique identifier for a particular configuration
+ * @param HTMLPurifier_Config $config Instance of HTMLPurifier_Config
+ * @return string
+ */
+ public function generateKey($config)
+ {
+ return $config->version . ',' . // possibly replace with function calls
+ $config->getBatchSerial($this->type) . ',' .
+ $config->get($this->type . '.DefinitionRev');
+ }
+
+ /**
+ * Tests whether or not a key is old with respect to the configuration's
+ * version and revision number.
+ * @param string $key Key to test
+ * @param HTMLPurifier_Config $config Instance of HTMLPurifier_Config to test against
+ * @return bool
+ */
+ public function isOld($key, $config)
+ {
+ if (substr_count($key, ',') < 2) {
+ return true;
+ }
+ list($version, $hash, $revision) = explode(',', $key, 3);
+ $compare = version_compare($version, $config->version);
+ // version mismatch, is always old
+ if ($compare != 0) {
+ return true;
+ }
+ // versions match, ids match, check revision number
+ if ($hash == $config->getBatchSerial($this->type) &&
+ $revision < $config->get($this->type . '.DefinitionRev')) {
+ return true;
+ }
+ return false;
+ }
+
+ /**
+ * Checks if a definition's type jives with the cache's type
+ * @note Throws an error on failure
+ * @param HTMLPurifier_Definition $def Definition object to check
+ * @return bool true if good, false if not
+ */
+ public function checkDefType($def)
+ {
+ if ($def->type !== $this->type) {
+ trigger_error("Cannot use definition of type {$def->type} in cache for {$this->type}");
+ return false;
+ }
+ return true;
+ }
+
+ /**
+ * Adds a definition object to the cache
+ * @param HTMLPurifier_Definition $def
+ * @param HTMLPurifier_Config $config
+ */
+ abstract public function add($def, $config);
+
+ /**
+ * Unconditionally saves a definition object to the cache
+ * @param HTMLPurifier_Definition $def
+ * @param HTMLPurifier_Config $config
+ */
+ abstract public function set($def, $config);
+
+ /**
+ * Replace an object in the cache
+ * @param HTMLPurifier_Definition $def
+ * @param HTMLPurifier_Config $config
+ */
+ abstract public function replace($def, $config);
+
+ /**
+ * Retrieves a definition object from the cache
+ * @param HTMLPurifier_Config $config
+ */
+ abstract public function get($config);
+
+ /**
+ * Removes a definition object to the cache
+ * @param HTMLPurifier_Config $config
+ */
+ abstract public function remove($config);
+
+ /**
+ * Clears all objects from cache
+ * @param HTMLPurifier_Config $config
+ */
+ abstract public function flush($config);
+
+ /**
+ * Clears all expired (older version or revision) objects from cache
+ * @note Be careful implementing this method as flush. Flush must
+ * not interfere with other Definition types, and cleanup()
+ * should not be repeatedly called by userland code.
+ * @param HTMLPurifier_Config $config
+ */
+ abstract public function cleanup($config);
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/DefinitionCache/Decorator.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Decorator.php
index b57a51b6c..b57a51b6c 100644
--- a/library/HTMLPurifier/DefinitionCache/Decorator.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Decorator.php
diff --git a/library/HTMLPurifier/DefinitionCache/Decorator/Cleanup.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Decorator/Cleanup.php
index 4991777ce..4991777ce 100644
--- a/library/HTMLPurifier/DefinitionCache/Decorator/Cleanup.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Decorator/Cleanup.php
diff --git a/library/HTMLPurifier/DefinitionCache/Decorator/Memory.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Decorator/Memory.php
index d529dce48..d529dce48 100644
--- a/library/HTMLPurifier/DefinitionCache/Decorator/Memory.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Decorator/Memory.php
diff --git a/library/HTMLPurifier/DefinitionCache/Decorator/Template.php.in b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Decorator/Template.php.in
index b1fec8d36..b1fec8d36 100644
--- a/library/HTMLPurifier/DefinitionCache/Decorator/Template.php.in
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Decorator/Template.php.in
diff --git a/library/HTMLPurifier/DefinitionCache/Null.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Null.php
index d9a75ce22..d9a75ce22 100644
--- a/library/HTMLPurifier/DefinitionCache/Null.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Null.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Serializer.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Serializer.php
new file mode 100644
index 000000000..952e48d47
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Serializer.php
@@ -0,0 +1,306 @@
+<?php
+
+class HTMLPurifier_DefinitionCache_Serializer extends HTMLPurifier_DefinitionCache
+{
+
+ /**
+ * @param HTMLPurifier_Definition $def
+ * @param HTMLPurifier_Config $config
+ * @return int|bool
+ */
+ public function add($def, $config)
+ {
+ if (!$this->checkDefType($def)) {
+ return;
+ }
+ $file = $this->generateFilePath($config);
+ if (file_exists($file)) {
+ return false;
+ }
+ if (!$this->_prepareDir($config)) {
+ return false;
+ }
+ return $this->_write($file, serialize($def), $config);
+ }
+
+ /**
+ * @param HTMLPurifier_Definition $def
+ * @param HTMLPurifier_Config $config
+ * @return int|bool
+ */
+ public function set($def, $config)
+ {
+ if (!$this->checkDefType($def)) {
+ return;
+ }
+ $file = $this->generateFilePath($config);
+ if (!$this->_prepareDir($config)) {
+ return false;
+ }
+ return $this->_write($file, serialize($def), $config);
+ }
+
+ /**
+ * @param HTMLPurifier_Definition $def
+ * @param HTMLPurifier_Config $config
+ * @return int|bool
+ */
+ public function replace($def, $config)
+ {
+ if (!$this->checkDefType($def)) {
+ return;
+ }
+ $file = $this->generateFilePath($config);
+ if (!file_exists($file)) {
+ return false;
+ }
+ if (!$this->_prepareDir($config)) {
+ return false;
+ }
+ return $this->_write($file, serialize($def), $config);
+ }
+
+ /**
+ * @param HTMLPurifier_Config $config
+ * @return bool|HTMLPurifier_Config
+ */
+ public function get($config)
+ {
+ $file = $this->generateFilePath($config);
+ if (!file_exists($file)) {
+ return false;
+ }
+ return unserialize(file_get_contents($file));
+ }
+
+ /**
+ * @param HTMLPurifier_Config $config
+ * @return bool
+ */
+ public function remove($config)
+ {
+ $file = $this->generateFilePath($config);
+ if (!file_exists($file)) {
+ return false;
+ }
+ return unlink($file);
+ }
+
+ /**
+ * @param HTMLPurifier_Config $config
+ * @return bool
+ */
+ public function flush($config)
+ {
+ if (!$this->_prepareDir($config)) {
+ return false;
+ }
+ $dir = $this->generateDirectoryPath($config);
+ $dh = opendir($dir);
+ // Apparently, on some versions of PHP, readdir will return
+ // an empty string if you pass an invalid argument to readdir.
+ // So you need this test. See #49.
+ if (false === $dh) {
+ return false;
+ }
+ while (false !== ($filename = readdir($dh))) {
+ if (empty($filename)) {
+ continue;
+ }
+ if ($filename[0] === '.') {
+ continue;
+ }
+ unlink($dir . '/' . $filename);
+ }
+ closedir($dh);
+ return true;
+ }
+
+ /**
+ * @param HTMLPurifier_Config $config
+ * @return bool
+ */
+ public function cleanup($config)
+ {
+ if (!$this->_prepareDir($config)) {
+ return false;
+ }
+ $dir = $this->generateDirectoryPath($config);
+ $dh = opendir($dir);
+ // See #49 (and above).
+ if (false === $dh) {
+ return false;
+ }
+ while (false !== ($filename = readdir($dh))) {
+ if (empty($filename)) {
+ continue;
+ }
+ if ($filename[0] === '.') {
+ continue;
+ }
+ $key = substr($filename, 0, strlen($filename) - 4);
+ if ($this->isOld($key, $config)) {
+ unlink($dir . '/' . $filename);
+ }
+ }
+ closedir($dh);
+ return true;
+ }
+
+ /**
+ * Generates the file path to the serial file corresponding to
+ * the configuration and definition name
+ * @param HTMLPurifier_Config $config
+ * @return string
+ * @todo Make protected
+ */
+ public function generateFilePath($config)
+ {
+ $key = $this->generateKey($config);
+ return $this->generateDirectoryPath($config) . '/' . $key . '.ser';
+ }
+
+ /**
+ * Generates the path to the directory contain this cache's serial files
+ * @param HTMLPurifier_Config $config
+ * @return string
+ * @note No trailing slash
+ * @todo Make protected
+ */
+ public function generateDirectoryPath($config)
+ {
+ $base = $this->generateBaseDirectoryPath($config);
+ return $base . '/' . $this->type;
+ }
+
+ /**
+ * Generates path to base directory that contains all definition type
+ * serials
+ * @param HTMLPurifier_Config $config
+ * @return mixed|string
+ * @todo Make protected
+ */
+ public function generateBaseDirectoryPath($config)
+ {
+ $base = $config->get('Cache.SerializerPath');
+ $base = is_null($base) ? HTMLPURIFIER_PREFIX . '/HTMLPurifier/DefinitionCache/Serializer' : $base;
+ return $base;
+ }
+
+ /**
+ * Convenience wrapper function for file_put_contents
+ * @param string $file File name to write to
+ * @param string $data Data to write into file
+ * @param HTMLPurifier_Config $config
+ * @return int|bool Number of bytes written if success, or false if failure.
+ */
+ private function _write($file, $data, $config)
+ {
+ $result = file_put_contents($file, $data);
+ if ($result !== false) {
+ // set permissions of the new file (no execute)
+ $chmod = $config->get('Cache.SerializerPermissions');
+ if ($chmod !== null) {
+ chmod($file, $chmod & 0666);
+ }
+ }
+ return $result;
+ }
+
+ /**
+ * Prepares the directory that this type stores the serials in
+ * @param HTMLPurifier_Config $config
+ * @return bool True if successful
+ */
+ private function _prepareDir($config)
+ {
+ $directory = $this->generateDirectoryPath($config);
+ $chmod = $config->get('Cache.SerializerPermissions');
+ if ($chmod === null) {
+ // TODO: This races
+ if (is_dir($directory)) return true;
+ return mkdir($directory);
+ }
+ if (!is_dir($directory)) {
+ $base = $this->generateBaseDirectoryPath($config);
+ if (!is_dir($base)) {
+ trigger_error(
+ 'Base directory ' . $base . ' does not exist,
+ please create or change using %Cache.SerializerPath',
+ E_USER_WARNING
+ );
+ return false;
+ } elseif (!$this->_testPermissions($base, $chmod)) {
+ return false;
+ }
+ if (!mkdir($directory, $chmod)) {
+ trigger_error(
+ 'Could not create directory ' . $directory . '',
+ E_USER_WARNING
+ );
+ return false;
+ }
+ if (!$this->_testPermissions($directory, $chmod)) {
+ return false;
+ }
+ } elseif (!$this->_testPermissions($directory, $chmod)) {
+ return false;
+ }
+ return true;
+ }
+
+ /**
+ * Tests permissions on a directory and throws out friendly
+ * error messages and attempts to chmod it itself if possible
+ * @param string $dir Directory path
+ * @param int $chmod Permissions
+ * @return bool True if directory is writable
+ */
+ private function _testPermissions($dir, $chmod)
+ {
+ // early abort, if it is writable, everything is hunky-dory
+ if (is_writable($dir)) {
+ return true;
+ }
+ if (!is_dir($dir)) {
+ // generally, you'll want to handle this beforehand
+ // so a more specific error message can be given
+ trigger_error(
+ 'Directory ' . $dir . ' does not exist',
+ E_USER_WARNING
+ );
+ return false;
+ }
+ if (function_exists('posix_getuid') && $chmod !== null) {
+ // POSIX system, we can give more specific advice
+ if (fileowner($dir) === posix_getuid()) {
+ // we can chmod it ourselves
+ $chmod = $chmod | 0700;
+ if (chmod($dir, $chmod)) {
+ return true;
+ }
+ } elseif (filegroup($dir) === posix_getgid()) {
+ $chmod = $chmod | 0070;
+ } else {
+ // PHP's probably running as nobody, so we'll
+ // need to give global permissions
+ $chmod = $chmod | 0777;
+ }
+ trigger_error(
+ 'Directory ' . $dir . ' not writable, ' .
+ 'please chmod to ' . decoct($chmod),
+ E_USER_WARNING
+ );
+ } else {
+ // generic error message
+ trigger_error(
+ 'Directory ' . $dir . ' not writable, ' .
+ 'please alter file permissions',
+ E_USER_WARNING
+ );
+ }
+ return false;
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/DefinitionCache/Serializer/README b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Serializer/README
index 2e35c1c3d..2e35c1c3d 100644..100755
--- a/library/HTMLPurifier/DefinitionCache/Serializer/README
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCache/Serializer/README
diff --git a/library/HTMLPurifier/DefinitionCacheFactory.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCacheFactory.php
index fd1cc9be4..fd1cc9be4 100644
--- a/library/HTMLPurifier/DefinitionCacheFactory.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/DefinitionCacheFactory.php
diff --git a/library/HTMLPurifier/Doctype.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Doctype.php
index 4acd06e5b..4acd06e5b 100644
--- a/library/HTMLPurifier/Doctype.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Doctype.php
diff --git a/library/HTMLPurifier/DoctypeRegistry.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/DoctypeRegistry.php
index acc1d64a6..acc1d64a6 100644
--- a/library/HTMLPurifier/DoctypeRegistry.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/DoctypeRegistry.php
diff --git a/library/HTMLPurifier/ElementDef.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ElementDef.php
index d5311cedc..d5311cedc 100644
--- a/library/HTMLPurifier/ElementDef.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ElementDef.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Encoder.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Encoder.php
new file mode 100644
index 000000000..b94f17542
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Encoder.php
@@ -0,0 +1,617 @@
+<?php
+
+/**
+ * A UTF-8 specific character encoder that handles cleaning and transforming.
+ * @note All functions in this class should be static.
+ */
+class HTMLPurifier_Encoder
+{
+
+ /**
+ * Constructor throws fatal error if you attempt to instantiate class
+ */
+ private function __construct()
+ {
+ trigger_error('Cannot instantiate encoder, call methods statically', E_USER_ERROR);
+ }
+
+ /**
+ * Error-handler that mutes errors, alternative to shut-up operator.
+ */
+ public static function muteErrorHandler()
+ {
+ }
+
+ /**
+ * iconv wrapper which mutes errors, but doesn't work around bugs.
+ * @param string $in Input encoding
+ * @param string $out Output encoding
+ * @param string $text The text to convert
+ * @return string
+ */
+ public static function unsafeIconv($in, $out, $text)
+ {
+ set_error_handler(array('HTMLPurifier_Encoder', 'muteErrorHandler'));
+ $r = iconv($in, $out, $text);
+ restore_error_handler();
+ return $r;
+ }
+
+ /**
+ * iconv wrapper which mutes errors and works around bugs.
+ * @param string $in Input encoding
+ * @param string $out Output encoding
+ * @param string $text The text to convert
+ * @param int $max_chunk_size
+ * @return string
+ */
+ public static function iconv($in, $out, $text, $max_chunk_size = 8000)
+ {
+ $code = self::testIconvTruncateBug();
+ if ($code == self::ICONV_OK) {
+ return self::unsafeIconv($in, $out, $text);
+ } elseif ($code == self::ICONV_TRUNCATES) {
+ // we can only work around this if the input character set
+ // is utf-8
+ if ($in == 'utf-8') {
+ if ($max_chunk_size < 4) {
+ trigger_error('max_chunk_size is too small', E_USER_WARNING);
+ return false;
+ }
+ // split into 8000 byte chunks, but be careful to handle
+ // multibyte boundaries properly
+ if (($c = strlen($text)) <= $max_chunk_size) {
+ return self::unsafeIconv($in, $out, $text);
+ }
+ $r = '';
+ $i = 0;
+ while (true) {
+ if ($i + $max_chunk_size >= $c) {
+ $r .= self::unsafeIconv($in, $out, substr($text, $i));
+ break;
+ }
+ // wibble the boundary
+ if (0x80 != (0xC0 & ord($text[$i + $max_chunk_size]))) {
+ $chunk_size = $max_chunk_size;
+ } elseif (0x80 != (0xC0 & ord($text[$i + $max_chunk_size - 1]))) {
+ $chunk_size = $max_chunk_size - 1;
+ } elseif (0x80 != (0xC0 & ord($text[$i + $max_chunk_size - 2]))) {
+ $chunk_size = $max_chunk_size - 2;
+ } elseif (0x80 != (0xC0 & ord($text[$i + $max_chunk_size - 3]))) {
+ $chunk_size = $max_chunk_size - 3;
+ } else {
+ return false; // rather confusing UTF-8...
+ }
+ $chunk = substr($text, $i, $chunk_size); // substr doesn't mind overlong lengths
+ $r .= self::unsafeIconv($in, $out, $chunk);
+ $i += $chunk_size;
+ }
+ return $r;
+ } else {
+ return false;
+ }
+ } else {
+ return false;
+ }
+ }
+
+ /**
+ * Cleans a UTF-8 string for well-formedness and SGML validity
+ *
+ * It will parse according to UTF-8 and return a valid UTF8 string, with
+ * non-SGML codepoints excluded.
+ *
+ * Specifically, it will permit:
+ * \x{9}\x{A}\x{D}\x{20}-\x{7E}\x{A0}-\x{D7FF}\x{E000}-\x{FFFD}\x{10000}-\x{10FFFF}
+ * Source: https://www.w3.org/TR/REC-xml/#NT-Char
+ * Arguably this function should be modernized to the HTML5 set
+ * of allowed characters:
+ * https://www.w3.org/TR/html5/syntax.html#preprocessing-the-input-stream
+ * which simultaneously expand and restrict the set of allowed characters.
+ *
+ * @param string $str The string to clean
+ * @param bool $force_php
+ * @return string
+ *
+ * @note Just for reference, the non-SGML code points are 0 to 31 and
+ * 127 to 159, inclusive. However, we allow code points 9, 10
+ * and 13, which are the tab, line feed and carriage return
+ * respectively. 128 and above the code points map to multibyte
+ * UTF-8 representations.
+ *
+ * @note Fallback code adapted from utf8ToUnicode by Henri Sivonen and
+ * hsivonen@iki.fi at <http://iki.fi/hsivonen/php-utf8/> under the
+ * LGPL license. Notes on what changed are inside, but in general,
+ * the original code transformed UTF-8 text into an array of integer
+ * Unicode codepoints. Understandably, transforming that back to
+ * a string would be somewhat expensive, so the function was modded to
+ * directly operate on the string. However, this discourages code
+ * reuse, and the logic enumerated here would be useful for any
+ * function that needs to be able to understand UTF-8 characters.
+ * As of right now, only smart lossless character encoding converters
+ * would need that, and I'm probably not going to implement them.
+ */
+ public static function cleanUTF8($str, $force_php = false)
+ {
+ // UTF-8 validity is checked since PHP 4.3.5
+ // This is an optimization: if the string is already valid UTF-8, no
+ // need to do PHP stuff. 99% of the time, this will be the case.
+ if (preg_match(
+ '/^[\x{9}\x{A}\x{D}\x{20}-\x{7E}\x{A0}-\x{D7FF}\x{E000}-\x{FFFD}\x{10000}-\x{10FFFF}]*$/Du',
+ $str
+ )) {
+ return $str;
+ }
+
+ $mState = 0; // cached expected number of octets after the current octet
+ // until the beginning of the next UTF8 character sequence
+ $mUcs4 = 0; // cached Unicode character
+ $mBytes = 1; // cached expected number of octets in the current sequence
+
+ // original code involved an $out that was an array of Unicode
+ // codepoints. Instead of having to convert back into UTF-8, we've
+ // decided to directly append valid UTF-8 characters onto a string
+ // $out once they're done. $char accumulates raw bytes, while $mUcs4
+ // turns into the Unicode code point, so there's some redundancy.
+
+ $out = '';
+ $char = '';
+
+ $len = strlen($str);
+ for ($i = 0; $i < $len; $i++) {
+ $in = ord($str{$i});
+ $char .= $str[$i]; // append byte to char
+ if (0 == $mState) {
+ // When mState is zero we expect either a US-ASCII character
+ // or a multi-octet sequence.
+ if (0 == (0x80 & ($in))) {
+ // US-ASCII, pass straight through.
+ if (($in <= 31 || $in == 127) &&
+ !($in == 9 || $in == 13 || $in == 10) // save \r\t\n
+ ) {
+ // control characters, remove
+ } else {
+ $out .= $char;
+ }
+ // reset
+ $char = '';
+ $mBytes = 1;
+ } elseif (0xC0 == (0xE0 & ($in))) {
+ // First octet of 2 octet sequence
+ $mUcs4 = ($in);
+ $mUcs4 = ($mUcs4 & 0x1F) << 6;
+ $mState = 1;
+ $mBytes = 2;
+ } elseif (0xE0 == (0xF0 & ($in))) {
+ // First octet of 3 octet sequence
+ $mUcs4 = ($in);
+ $mUcs4 = ($mUcs4 & 0x0F) << 12;
+ $mState = 2;
+ $mBytes = 3;
+ } elseif (0xF0 == (0xF8 & ($in))) {
+ // First octet of 4 octet sequence
+ $mUcs4 = ($in);
+ $mUcs4 = ($mUcs4 & 0x07) << 18;
+ $mState = 3;
+ $mBytes = 4;
+ } elseif (0xF8 == (0xFC & ($in))) {
+ // First octet of 5 octet sequence.
+ //
+ // This is illegal because the encoded codepoint must be
+ // either:
+ // (a) not the shortest form or
+ // (b) outside the Unicode range of 0-0x10FFFF.
+ // Rather than trying to resynchronize, we will carry on
+ // until the end of the sequence and let the later error
+ // handling code catch it.
+ $mUcs4 = ($in);
+ $mUcs4 = ($mUcs4 & 0x03) << 24;
+ $mState = 4;
+ $mBytes = 5;
+ } elseif (0xFC == (0xFE & ($in))) {
+ // First octet of 6 octet sequence, see comments for 5
+ // octet sequence.
+ $mUcs4 = ($in);
+ $mUcs4 = ($mUcs4 & 1) << 30;
+ $mState = 5;
+ $mBytes = 6;
+ } else {
+ // Current octet is neither in the US-ASCII range nor a
+ // legal first octet of a multi-octet sequence.
+ $mState = 0;
+ $mUcs4 = 0;
+ $mBytes = 1;
+ $char = '';
+ }
+ } else {
+ // When mState is non-zero, we expect a continuation of the
+ // multi-octet sequence
+ if (0x80 == (0xC0 & ($in))) {
+ // Legal continuation.
+ $shift = ($mState - 1) * 6;
+ $tmp = $in;
+ $tmp = ($tmp & 0x0000003F) << $shift;
+ $mUcs4 |= $tmp;
+
+ if (0 == --$mState) {
+ // End of the multi-octet sequence. mUcs4 now contains
+ // the final Unicode codepoint to be output
+
+ // Check for illegal sequences and codepoints.
+
+ // From Unicode 3.1, non-shortest form is illegal
+ if (((2 == $mBytes) && ($mUcs4 < 0x0080)) ||
+ ((3 == $mBytes) && ($mUcs4 < 0x0800)) ||
+ ((4 == $mBytes) && ($mUcs4 < 0x10000)) ||
+ (4 < $mBytes) ||
+ // From Unicode 3.2, surrogate characters = illegal
+ (($mUcs4 & 0xFFFFF800) == 0xD800) ||
+ // Codepoints outside the Unicode range are illegal
+ ($mUcs4 > 0x10FFFF)
+ ) {
+
+ } elseif (0xFEFF != $mUcs4 && // omit BOM
+ // check for valid Char unicode codepoints
+ (
+ 0x9 == $mUcs4 ||
+ 0xA == $mUcs4 ||
+ 0xD == $mUcs4 ||
+ (0x20 <= $mUcs4 && 0x7E >= $mUcs4) ||
+ // 7F-9F is not strictly prohibited by XML,
+ // but it is non-SGML, and thus we don't allow it
+ (0xA0 <= $mUcs4 && 0xD7FF >= $mUcs4) ||
+ (0xE000 <= $mUcs4 && 0xFFFD >= $mUcs4) ||
+ (0x10000 <= $mUcs4 && 0x10FFFF >= $mUcs4)
+ )
+ ) {
+ $out .= $char;
+ }
+ // initialize UTF8 cache (reset)
+ $mState = 0;
+ $mUcs4 = 0;
+ $mBytes = 1;
+ $char = '';
+ }
+ } else {
+ // ((0xC0 & (*in) != 0x80) && (mState != 0))
+ // Incomplete multi-octet sequence.
+ // used to result in complete fail, but we'll reset
+ $mState = 0;
+ $mUcs4 = 0;
+ $mBytes = 1;
+ $char ='';
+ }
+ }
+ }
+ return $out;
+ }
+
+ /**
+ * Translates a Unicode codepoint into its corresponding UTF-8 character.
+ * @note Based on Feyd's function at
+ * <http://forums.devnetwork.net/viewtopic.php?p=191404#191404>,
+ * which is in public domain.
+ * @note While we're going to do code point parsing anyway, a good
+ * optimization would be to refuse to translate code points that
+ * are non-SGML characters. However, this could lead to duplication.
+ * @note This is very similar to the unichr function in
+ * maintenance/generate-entity-file.php (although this is superior,
+ * due to its sanity checks).
+ */
+
+ // +----------+----------+----------+----------+
+ // | 33222222 | 22221111 | 111111 | |
+ // | 10987654 | 32109876 | 54321098 | 76543210 | bit
+ // +----------+----------+----------+----------+
+ // | | | | 0xxxxxxx | 1 byte 0x00000000..0x0000007F
+ // | | | 110yyyyy | 10xxxxxx | 2 byte 0x00000080..0x000007FF
+ // | | 1110zzzz | 10yyyyyy | 10xxxxxx | 3 byte 0x00000800..0x0000FFFF
+ // | 11110www | 10wwzzzz | 10yyyyyy | 10xxxxxx | 4 byte 0x00010000..0x0010FFFF
+ // +----------+----------+----------+----------+
+ // | 00000000 | 00011111 | 11111111 | 11111111 | Theoretical upper limit of legal scalars: 2097151 (0x001FFFFF)
+ // | 00000000 | 00010000 | 11111111 | 11111111 | Defined upper limit of legal scalar codes
+ // +----------+----------+----------+----------+
+
+ public static function unichr($code)
+ {
+ if ($code > 1114111 or $code < 0 or
+ ($code >= 55296 and $code <= 57343) ) {
+ // bits are set outside the "valid" range as defined
+ // by UNICODE 4.1.0
+ return '';
+ }
+
+ $x = $y = $z = $w = 0;
+ if ($code < 128) {
+ // regular ASCII character
+ $x = $code;
+ } else {
+ // set up bits for UTF-8
+ $x = ($code & 63) | 128;
+ if ($code < 2048) {
+ $y = (($code & 2047) >> 6) | 192;
+ } else {
+ $y = (($code & 4032) >> 6) | 128;
+ if ($code < 65536) {
+ $z = (($code >> 12) & 15) | 224;
+ } else {
+ $z = (($code >> 12) & 63) | 128;
+ $w = (($code >> 18) & 7) | 240;
+ }
+ }
+ }
+ // set up the actual character
+ $ret = '';
+ if ($w) {
+ $ret .= chr($w);
+ }
+ if ($z) {
+ $ret .= chr($z);
+ }
+ if ($y) {
+ $ret .= chr($y);
+ }
+ $ret .= chr($x);
+
+ return $ret;
+ }
+
+ /**
+ * @return bool
+ */
+ public static function iconvAvailable()
+ {
+ static $iconv = null;
+ if ($iconv === null) {
+ $iconv = function_exists('iconv') && self::testIconvTruncateBug() != self::ICONV_UNUSABLE;
+ }
+ return $iconv;
+ }
+
+ /**
+ * Convert a string to UTF-8 based on configuration.
+ * @param string $str The string to convert
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return string
+ */
+ public static function convertToUTF8($str, $config, $context)
+ {
+ $encoding = $config->get('Core.Encoding');
+ if ($encoding === 'utf-8') {
+ return $str;
+ }
+ static $iconv = null;
+ if ($iconv === null) {
+ $iconv = self::iconvAvailable();
+ }
+ if ($iconv && !$config->get('Test.ForceNoIconv')) {
+ // unaffected by bugs, since UTF-8 support all characters
+ $str = self::unsafeIconv($encoding, 'utf-8//IGNORE', $str);
+ if ($str === false) {
+ // $encoding is not a valid encoding
+ trigger_error('Invalid encoding ' . $encoding, E_USER_ERROR);
+ return '';
+ }
+ // If the string is bjorked by Shift_JIS or a similar encoding
+ // that doesn't support all of ASCII, convert the naughty
+ // characters to their true byte-wise ASCII/UTF-8 equivalents.
+ $str = strtr($str, self::testEncodingSupportsASCII($encoding));
+ return $str;
+ } elseif ($encoding === 'iso-8859-1') {
+ $str = utf8_encode($str);
+ return $str;
+ }
+ $bug = HTMLPurifier_Encoder::testIconvTruncateBug();
+ if ($bug == self::ICONV_OK) {
+ trigger_error('Encoding not supported, please install iconv', E_USER_ERROR);
+ } else {
+ trigger_error(
+ 'You have a buggy version of iconv, see https://bugs.php.net/bug.php?id=48147 ' .
+ 'and http://sourceware.org/bugzilla/show_bug.cgi?id=13541',
+ E_USER_ERROR
+ );
+ }
+ }
+
+ /**
+ * Converts a string from UTF-8 based on configuration.
+ * @param string $str The string to convert
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return string
+ * @note Currently, this is a lossy conversion, with unexpressable
+ * characters being omitted.
+ */
+ public static function convertFromUTF8($str, $config, $context)
+ {
+ $encoding = $config->get('Core.Encoding');
+ if ($escape = $config->get('Core.EscapeNonASCIICharacters')) {
+ $str = self::convertToASCIIDumbLossless($str);
+ }
+ if ($encoding === 'utf-8') {
+ return $str;
+ }
+ static $iconv = null;
+ if ($iconv === null) {
+ $iconv = self::iconvAvailable();
+ }
+ if ($iconv && !$config->get('Test.ForceNoIconv')) {
+ // Undo our previous fix in convertToUTF8, otherwise iconv will barf
+ $ascii_fix = self::testEncodingSupportsASCII($encoding);
+ if (!$escape && !empty($ascii_fix)) {
+ $clear_fix = array();
+ foreach ($ascii_fix as $utf8 => $native) {
+ $clear_fix[$utf8] = '';
+ }
+ $str = strtr($str, $clear_fix);
+ }
+ $str = strtr($str, array_flip($ascii_fix));
+ // Normal stuff
+ $str = self::iconv('utf-8', $encoding . '//IGNORE', $str);
+ return $str;
+ } elseif ($encoding === 'iso-8859-1') {
+ $str = utf8_decode($str);
+ return $str;
+ }
+ trigger_error('Encoding not supported', E_USER_ERROR);
+ // You might be tempted to assume that the ASCII representation
+ // might be OK, however, this is *not* universally true over all
+ // encodings. So we take the conservative route here, rather
+ // than forcibly turn on %Core.EscapeNonASCIICharacters
+ }
+
+ /**
+ * Lossless (character-wise) conversion of HTML to ASCII
+ * @param string $str UTF-8 string to be converted to ASCII
+ * @return string ASCII encoded string with non-ASCII character entity-ized
+ * @warning Adapted from MediaWiki, claiming fair use: this is a common
+ * algorithm. If you disagree with this license fudgery,
+ * implement it yourself.
+ * @note Uses decimal numeric entities since they are best supported.
+ * @note This is a DUMB function: it has no concept of keeping
+ * character entities that the projected character encoding
+ * can allow. We could possibly implement a smart version
+ * but that would require it to also know which Unicode
+ * codepoints the charset supported (not an easy task).
+ * @note Sort of with cleanUTF8() but it assumes that $str is
+ * well-formed UTF-8
+ */
+ public static function convertToASCIIDumbLossless($str)
+ {
+ $bytesleft = 0;
+ $result = '';
+ $working = 0;
+ $len = strlen($str);
+ for ($i = 0; $i < $len; $i++) {
+ $bytevalue = ord($str[$i]);
+ if ($bytevalue <= 0x7F) { //0xxx xxxx
+ $result .= chr($bytevalue);
+ $bytesleft = 0;
+ } elseif ($bytevalue <= 0xBF) { //10xx xxxx
+ $working = $working << 6;
+ $working += ($bytevalue & 0x3F);
+ $bytesleft--;
+ if ($bytesleft <= 0) {
+ $result .= "&#" . $working . ";";
+ }
+ } elseif ($bytevalue <= 0xDF) { //110x xxxx
+ $working = $bytevalue & 0x1F;
+ $bytesleft = 1;
+ } elseif ($bytevalue <= 0xEF) { //1110 xxxx
+ $working = $bytevalue & 0x0F;
+ $bytesleft = 2;
+ } else { //1111 0xxx
+ $working = $bytevalue & 0x07;
+ $bytesleft = 3;
+ }
+ }
+ return $result;
+ }
+
+ /** No bugs detected in iconv. */
+ const ICONV_OK = 0;
+
+ /** Iconv truncates output if converting from UTF-8 to another
+ * character set with //IGNORE, and a non-encodable character is found */
+ const ICONV_TRUNCATES = 1;
+
+ /** Iconv does not support //IGNORE, making it unusable for
+ * transcoding purposes */
+ const ICONV_UNUSABLE = 2;
+
+ /**
+ * glibc iconv has a known bug where it doesn't handle the magic
+ * //IGNORE stanza correctly. In particular, rather than ignore
+ * characters, it will return an EILSEQ after consuming some number
+ * of characters, and expect you to restart iconv as if it were
+ * an E2BIG. Old versions of PHP did not respect the errno, and
+ * returned the fragment, so as a result you would see iconv
+ * mysteriously truncating output. We can work around this by
+ * manually chopping our input into segments of about 8000
+ * characters, as long as PHP ignores the error code. If PHP starts
+ * paying attention to the error code, iconv becomes unusable.
+ *
+ * @return int Error code indicating severity of bug.
+ */
+ public static function testIconvTruncateBug()
+ {
+ static $code = null;
+ if ($code === null) {
+ // better not use iconv, otherwise infinite loop!
+ $r = self::unsafeIconv('utf-8', 'ascii//IGNORE', "\xCE\xB1" . str_repeat('a', 9000));
+ if ($r === false) {
+ $code = self::ICONV_UNUSABLE;
+ } elseif (($c = strlen($r)) < 9000) {
+ $code = self::ICONV_TRUNCATES;
+ } elseif ($c > 9000) {
+ trigger_error(
+ 'Your copy of iconv is extremely buggy. Please notify HTML Purifier maintainers: ' .
+ 'include your iconv version as per phpversion()',
+ E_USER_ERROR
+ );
+ } else {
+ $code = self::ICONV_OK;
+ }
+ }
+ return $code;
+ }
+
+ /**
+ * This expensive function tests whether or not a given character
+ * encoding supports ASCII. 7/8-bit encodings like Shift_JIS will
+ * fail this test, and require special processing. Variable width
+ * encodings shouldn't ever fail.
+ *
+ * @param string $encoding Encoding name to test, as per iconv format
+ * @param bool $bypass Whether or not to bypass the precompiled arrays.
+ * @return Array of UTF-8 characters to their corresponding ASCII,
+ * which can be used to "undo" any overzealous iconv action.
+ */
+ public static function testEncodingSupportsASCII($encoding, $bypass = false)
+ {
+ // All calls to iconv here are unsafe, proof by case analysis:
+ // If ICONV_OK, no difference.
+ // If ICONV_TRUNCATE, all calls involve one character inputs,
+ // so bug is not triggered.
+ // If ICONV_UNUSABLE, this call is irrelevant
+ static $encodings = array();
+ if (!$bypass) {
+ if (isset($encodings[$encoding])) {
+ return $encodings[$encoding];
+ }
+ $lenc = strtolower($encoding);
+ switch ($lenc) {
+ case 'shift_jis':
+ return array("\xC2\xA5" => '\\', "\xE2\x80\xBE" => '~');
+ case 'johab':
+ return array("\xE2\x82\xA9" => '\\');
+ }
+ if (strpos($lenc, 'iso-8859-') === 0) {
+ return array();
+ }
+ }
+ $ret = array();
+ if (self::unsafeIconv('UTF-8', $encoding, 'a') === false) {
+ return false;
+ }
+ for ($i = 0x20; $i <= 0x7E; $i++) { // all printable ASCII chars
+ $c = chr($i); // UTF-8 char
+ $r = self::unsafeIconv('UTF-8', "$encoding//IGNORE", $c); // initial conversion
+ if ($r === '' ||
+ // This line is needed for iconv implementations that do not
+ // omit characters that do not exist in the target character set
+ ($r === $c && self::unsafeIconv($encoding, 'UTF-8//IGNORE', $r) !== $c)
+ ) {
+ // Reverse engineer: what's the UTF-8 equiv of this byte
+ // sequence? This assumes that there's no variable width
+ // encoding that doesn't support ASCII.
+ $ret[self::unsafeIconv($encoding, 'UTF-8//IGNORE', $c)] = $c;
+ }
+ }
+ $encodings[$encoding] = $ret;
+ return $ret;
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/EntityLookup.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/EntityLookup.php
index f12ff13a3..f12ff13a3 100644
--- a/library/HTMLPurifier/EntityLookup.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/EntityLookup.php
diff --git a/library/HTMLPurifier/EntityLookup/entities.ser b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/EntityLookup/entities.ser
index e8b08128b..e8b08128b 100644
--- a/library/HTMLPurifier/EntityLookup/entities.ser
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/EntityLookup/entities.ser
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/EntityParser.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/EntityParser.php
new file mode 100644
index 000000000..c372b5a6a
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/EntityParser.php
@@ -0,0 +1,285 @@
+<?php
+
+// if want to implement error collecting here, we'll need to use some sort
+// of global data (probably trigger_error) because it's impossible to pass
+// $config or $context to the callback functions.
+
+/**
+ * Handles referencing and derefencing character entities
+ */
+class HTMLPurifier_EntityParser
+{
+
+ /**
+ * Reference to entity lookup table.
+ * @type HTMLPurifier_EntityLookup
+ */
+ protected $_entity_lookup;
+
+ /**
+ * Callback regex string for entities in text.
+ * @type string
+ */
+ protected $_textEntitiesRegex;
+
+ /**
+ * Callback regex string for entities in attributes.
+ * @type string
+ */
+ protected $_attrEntitiesRegex;
+
+ /**
+ * Tests if the beginning of a string is a semi-optional regex
+ */
+ protected $_semiOptionalPrefixRegex;
+
+ public function __construct() {
+ // From
+ // http://stackoverflow.com/questions/15532252/why-is-reg-being-rendered-as-without-the-bounding-semicolon
+ $semi_optional = "quot|QUOT|lt|LT|gt|GT|amp|AMP|AElig|Aacute|Acirc|Agrave|Aring|Atilde|Auml|COPY|Ccedil|ETH|Eacute|Ecirc|Egrave|Euml|Iacute|Icirc|Igrave|Iuml|Ntilde|Oacute|Ocirc|Ograve|Oslash|Otilde|Ouml|REG|THORN|Uacute|Ucirc|Ugrave|Uuml|Yacute|aacute|acirc|acute|aelig|agrave|aring|atilde|auml|brvbar|ccedil|cedil|cent|copy|curren|deg|divide|eacute|ecirc|egrave|eth|euml|frac12|frac14|frac34|iacute|icirc|iexcl|igrave|iquest|iuml|laquo|macr|micro|middot|nbsp|not|ntilde|oacute|ocirc|ograve|ordf|ordm|oslash|otilde|ouml|para|plusmn|pound|raquo|reg|sect|shy|sup1|sup2|sup3|szlig|thorn|times|uacute|ucirc|ugrave|uml|uuml|yacute|yen|yuml";
+
+ // NB: three empty captures to put the fourth match in the right
+ // place
+ $this->_semiOptionalPrefixRegex = "/&()()()($semi_optional)/";
+
+ $this->_textEntitiesRegex =
+ '/&(?:'.
+ // hex
+ '[#]x([a-fA-F0-9]+);?|'.
+ // dec
+ '[#]0*(\d+);?|'.
+ // string (mandatory semicolon)
+ // NB: order matters: match semicolon preferentially
+ '([A-Za-z_:][A-Za-z0-9.\-_:]*);|'.
+ // string (optional semicolon)
+ "($semi_optional)".
+ ')/';
+
+ $this->_attrEntitiesRegex =
+ '/&(?:'.
+ // hex
+ '[#]x([a-fA-F0-9]+);?|'.
+ // dec
+ '[#]0*(\d+);?|'.
+ // string (mandatory semicolon)
+ // NB: order matters: match semicolon preferentially
+ '([A-Za-z_:][A-Za-z0-9.\-_:]*);|'.
+ // string (optional semicolon)
+ // don't match if trailing is equals or alphanumeric (URL
+ // like)
+ "($semi_optional)(?![=;A-Za-z0-9])".
+ ')/';
+
+ }
+
+ /**
+ * Substitute entities with the parsed equivalents. Use this on
+ * textual data in an HTML document (as opposed to attributes.)
+ *
+ * @param string $string String to have entities parsed.
+ * @return string Parsed string.
+ */
+ public function substituteTextEntities($string)
+ {
+ return preg_replace_callback(
+ $this->_textEntitiesRegex,
+ array($this, 'entityCallback'),
+ $string
+ );
+ }
+
+ /**
+ * Substitute entities with the parsed equivalents. Use this on
+ * attribute contents in documents.
+ *
+ * @param string $string String to have entities parsed.
+ * @return string Parsed string.
+ */
+ public function substituteAttrEntities($string)
+ {
+ return preg_replace_callback(
+ $this->_attrEntitiesRegex,
+ array($this, 'entityCallback'),
+ $string
+ );
+ }
+
+ /**
+ * Callback function for substituteNonSpecialEntities() that does the work.
+ *
+ * @param array $matches PCRE matches array, with 0 the entire match, and
+ * either index 1, 2 or 3 set with a hex value, dec value,
+ * or string (respectively).
+ * @return string Replacement string.
+ */
+
+ protected function entityCallback($matches)
+ {
+ $entity = $matches[0];
+ $hex_part = @$matches[1];
+ $dec_part = @$matches[2];
+ $named_part = empty($matches[3]) ? @$matches[4] : $matches[3];
+ if ($hex_part !== NULL && $hex_part !== "") {
+ return HTMLPurifier_Encoder::unichr(hexdec($hex_part));
+ } elseif ($dec_part !== NULL && $dec_part !== "") {
+ return HTMLPurifier_Encoder::unichr((int) $dec_part);
+ } else {
+ if (!$this->_entity_lookup) {
+ $this->_entity_lookup = HTMLPurifier_EntityLookup::instance();
+ }
+ if (isset($this->_entity_lookup->table[$named_part])) {
+ return $this->_entity_lookup->table[$named_part];
+ } else {
+ // exact match didn't match anything, so test if
+ // any of the semicolon optional match the prefix.
+ // Test that this is an EXACT match is important to
+ // prevent infinite loop
+ if (!empty($matches[3])) {
+ return preg_replace_callback(
+ $this->_semiOptionalPrefixRegex,
+ array($this, 'entityCallback'),
+ $entity
+ );
+ }
+ return $entity;
+ }
+ }
+ }
+
+ // LEGACY CODE BELOW
+
+ /**
+ * Callback regex string for parsing entities.
+ * @type string
+ */
+ protected $_substituteEntitiesRegex =
+ '/&(?:[#]x([a-fA-F0-9]+)|[#]0*(\d+)|([A-Za-z_:][A-Za-z0-9.\-_:]*));?/';
+ // 1. hex 2. dec 3. string (XML style)
+
+ /**
+ * Decimal to parsed string conversion table for special entities.
+ * @type array
+ */
+ protected $_special_dec2str =
+ array(
+ 34 => '"',
+ 38 => '&',
+ 39 => "'",
+ 60 => '<',
+ 62 => '>'
+ );
+
+ /**
+ * Stripped entity names to decimal conversion table for special entities.
+ * @type array
+ */
+ protected $_special_ent2dec =
+ array(
+ 'quot' => 34,
+ 'amp' => 38,
+ 'lt' => 60,
+ 'gt' => 62
+ );
+
+ /**
+ * Substitutes non-special entities with their parsed equivalents. Since
+ * running this whenever you have parsed character is t3h 5uck, we run
+ * it before everything else.
+ *
+ * @param string $string String to have non-special entities parsed.
+ * @return string Parsed string.
+ */
+ public function substituteNonSpecialEntities($string)
+ {
+ // it will try to detect missing semicolons, but don't rely on it
+ return preg_replace_callback(
+ $this->_substituteEntitiesRegex,
+ array($this, 'nonSpecialEntityCallback'),
+ $string
+ );
+ }
+
+ /**
+ * Callback function for substituteNonSpecialEntities() that does the work.
+ *
+ * @param array $matches PCRE matches array, with 0 the entire match, and
+ * either index 1, 2 or 3 set with a hex value, dec value,
+ * or string (respectively).
+ * @return string Replacement string.
+ */
+
+ protected function nonSpecialEntityCallback($matches)
+ {
+ // replaces all but big five
+ $entity = $matches[0];
+ $is_num = (@$matches[0][1] === '#');
+ if ($is_num) {
+ $is_hex = (@$entity[2] === 'x');
+ $code = $is_hex ? hexdec($matches[1]) : (int) $matches[2];
+ // abort for special characters
+ if (isset($this->_special_dec2str[$code])) {
+ return $entity;
+ }
+ return HTMLPurifier_Encoder::unichr($code);
+ } else {
+ if (isset($this->_special_ent2dec[$matches[3]])) {
+ return $entity;
+ }
+ if (!$this->_entity_lookup) {
+ $this->_entity_lookup = HTMLPurifier_EntityLookup::instance();
+ }
+ if (isset($this->_entity_lookup->table[$matches[3]])) {
+ return $this->_entity_lookup->table[$matches[3]];
+ } else {
+ return $entity;
+ }
+ }
+ }
+
+ /**
+ * Substitutes only special entities with their parsed equivalents.
+ *
+ * @notice We try to avoid calling this function because otherwise, it
+ * would have to be called a lot (for every parsed section).
+ *
+ * @param string $string String to have non-special entities parsed.
+ * @return string Parsed string.
+ */
+ public function substituteSpecialEntities($string)
+ {
+ return preg_replace_callback(
+ $this->_substituteEntitiesRegex,
+ array($this, 'specialEntityCallback'),
+ $string
+ );
+ }
+
+ /**
+ * Callback function for substituteSpecialEntities() that does the work.
+ *
+ * This callback has same syntax as nonSpecialEntityCallback().
+ *
+ * @param array $matches PCRE-style matches array, with 0 the entire match, and
+ * either index 1, 2 or 3 set with a hex value, dec value,
+ * or string (respectively).
+ * @return string Replacement string.
+ */
+ protected function specialEntityCallback($matches)
+ {
+ $entity = $matches[0];
+ $is_num = (@$matches[0][1] === '#');
+ if ($is_num) {
+ $is_hex = (@$entity[2] === 'x');
+ $int = $is_hex ? hexdec($matches[1]) : (int) $matches[2];
+ return isset($this->_special_dec2str[$int]) ?
+ $this->_special_dec2str[$int] :
+ $entity;
+ } else {
+ return isset($this->_special_ent2dec[$matches[3]]) ?
+ $this->_special_dec2str[$this->_special_ent2dec[$matches[3]]] :
+ $entity;
+ }
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/ErrorCollector.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ErrorCollector.php
index d47e3f2e2..d47e3f2e2 100644
--- a/library/HTMLPurifier/ErrorCollector.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ErrorCollector.php
diff --git a/library/HTMLPurifier/ErrorStruct.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ErrorStruct.php
index cf869d321..cf869d321 100644
--- a/library/HTMLPurifier/ErrorStruct.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/ErrorStruct.php
diff --git a/library/HTMLPurifier/Exception.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Exception.php
index be85b4c56..be85b4c56 100644
--- a/library/HTMLPurifier/Exception.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Exception.php
diff --git a/library/HTMLPurifier/Filter.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Filter.php
index c1f41ee16..c1f41ee16 100644
--- a/library/HTMLPurifier/Filter.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Filter.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Filter/ExtractStyleBlocks.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Filter/ExtractStyleBlocks.php
new file mode 100644
index 000000000..66f70b0fc
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Filter/ExtractStyleBlocks.php
@@ -0,0 +1,341 @@
+<?php
+
+// why is this a top level function? Because PHP 5.2.0 doesn't seem to
+// understand how to interpret this filter if it's a static method.
+// It's all really silly, but if we go this route it might be reasonable
+// to coalesce all of these methods into one.
+function htmlpurifier_filter_extractstyleblocks_muteerrorhandler()
+{
+}
+
+/**
+ * This filter extracts <style> blocks from input HTML, cleans them up
+ * using CSSTidy, and then places them in $purifier->context->get('StyleBlocks')
+ * so they can be used elsewhere in the document.
+ *
+ * @note
+ * See tests/HTMLPurifier/Filter/ExtractStyleBlocksTest.php for
+ * sample usage.
+ *
+ * @note
+ * This filter can also be used on stylesheets not included in the
+ * document--something purists would probably prefer. Just directly
+ * call HTMLPurifier_Filter_ExtractStyleBlocks->cleanCSS()
+ */
+class HTMLPurifier_Filter_ExtractStyleBlocks extends HTMLPurifier_Filter
+{
+ /**
+ * @type string
+ */
+ public $name = 'ExtractStyleBlocks';
+
+ /**
+ * @type array
+ */
+ private $_styleMatches = array();
+
+ /**
+ * @type csstidy
+ */
+ private $_tidy;
+
+ /**
+ * @type HTMLPurifier_AttrDef_HTML_ID
+ */
+ private $_id_attrdef;
+
+ /**
+ * @type HTMLPurifier_AttrDef_CSS_Ident
+ */
+ private $_class_attrdef;
+
+ /**
+ * @type HTMLPurifier_AttrDef_Enum
+ */
+ private $_enum_attrdef;
+
+ public function __construct()
+ {
+ $this->_tidy = new csstidy();
+ $this->_tidy->set_cfg('lowercase_s', false);
+ $this->_id_attrdef = new HTMLPurifier_AttrDef_HTML_ID(true);
+ $this->_class_attrdef = new HTMLPurifier_AttrDef_CSS_Ident();
+ $this->_enum_attrdef = new HTMLPurifier_AttrDef_Enum(
+ array(
+ 'first-child',
+ 'link',
+ 'visited',
+ 'active',
+ 'hover',
+ 'focus'
+ )
+ );
+ }
+
+ /**
+ * Save the contents of CSS blocks to style matches
+ * @param array $matches preg_replace style $matches array
+ */
+ protected function styleCallback($matches)
+ {
+ $this->_styleMatches[] = $matches[1];
+ }
+
+ /**
+ * Removes inline <style> tags from HTML, saves them for later use
+ * @param string $html
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return string
+ * @todo Extend to indicate non-text/css style blocks
+ */
+ public function preFilter($html, $config, $context)
+ {
+ $tidy = $config->get('Filter.ExtractStyleBlocks.TidyImpl');
+ if ($tidy !== null) {
+ $this->_tidy = $tidy;
+ }
+ // NB: this must be NON-greedy because if we have
+ // <style>foo</style> <style>bar</style>
+ // we must not grab foo</style> <style>bar
+ $html = preg_replace_callback('#<style(?:\s.*)?>(.*)<\/style>#isU', array($this, 'styleCallback'), $html);
+ $style_blocks = $this->_styleMatches;
+ $this->_styleMatches = array(); // reset
+ $context->register('StyleBlocks', $style_blocks); // $context must not be reused
+ if ($this->_tidy) {
+ foreach ($style_blocks as &$style) {
+ $style = $this->cleanCSS($style, $config, $context);
+ }
+ }
+ return $html;
+ }
+
+ /**
+ * Takes CSS (the stuff found in <style>) and cleans it.
+ * @warning Requires CSSTidy <http://csstidy.sourceforge.net/>
+ * @param string $css CSS styling to clean
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @throws HTMLPurifier_Exception
+ * @return string Cleaned CSS
+ */
+ public function cleanCSS($css, $config, $context)
+ {
+ // prepare scope
+ $scope = $config->get('Filter.ExtractStyleBlocks.Scope');
+ if ($scope !== null) {
+ $scopes = array_map('trim', explode(',', $scope));
+ } else {
+ $scopes = array();
+ }
+ // remove comments from CSS
+ $css = trim($css);
+ if (strncmp('<!--', $css, 4) === 0) {
+ $css = substr($css, 4);
+ }
+ if (strlen($css) > 3 && substr($css, -3) == '-->') {
+ $css = substr($css, 0, -3);
+ }
+ $css = trim($css);
+ set_error_handler('htmlpurifier_filter_extractstyleblocks_muteerrorhandler');
+ $this->_tidy->parse($css);
+ restore_error_handler();
+ $css_definition = $config->getDefinition('CSS');
+ $html_definition = $config->getDefinition('HTML');
+ $new_css = array();
+ foreach ($this->_tidy->css as $k => $decls) {
+ // $decls are all CSS declarations inside an @ selector
+ $new_decls = array();
+ foreach ($decls as $selector => $style) {
+ $selector = trim($selector);
+ if ($selector === '') {
+ continue;
+ } // should not happen
+ // Parse the selector
+ // Here is the relevant part of the CSS grammar:
+ //
+ // ruleset
+ // : selector [ ',' S* selector ]* '{' ...
+ // selector
+ // : simple_selector [ combinator selector | S+ [ combinator? selector ]? ]?
+ // combinator
+ // : '+' S*
+ // : '>' S*
+ // simple_selector
+ // : element_name [ HASH | class | attrib | pseudo ]*
+ // | [ HASH | class | attrib | pseudo ]+
+ // element_name
+ // : IDENT | '*'
+ // ;
+ // class
+ // : '.' IDENT
+ // ;
+ // attrib
+ // : '[' S* IDENT S* [ [ '=' | INCLUDES | DASHMATCH ] S*
+ // [ IDENT | STRING ] S* ]? ']'
+ // ;
+ // pseudo
+ // : ':' [ IDENT | FUNCTION S* [IDENT S*]? ')' ]
+ // ;
+ //
+ // For reference, here are the relevant tokens:
+ //
+ // HASH #{name}
+ // IDENT {ident}
+ // INCLUDES ==
+ // DASHMATCH |=
+ // STRING {string}
+ // FUNCTION {ident}\(
+ //
+ // And the lexical scanner tokens
+ //
+ // name {nmchar}+
+ // nmchar [_a-z0-9-]|{nonascii}|{escape}
+ // nonascii [\240-\377]
+ // escape {unicode}|\\[^\r\n\f0-9a-f]
+ // unicode \\{h}}{1,6}(\r\n|[ \t\r\n\f])?
+ // ident -?{nmstart}{nmchar*}
+ // nmstart [_a-z]|{nonascii}|{escape}
+ // string {string1}|{string2}
+ // string1 \"([^\n\r\f\\"]|\\{nl}|{escape})*\"
+ // string2 \'([^\n\r\f\\"]|\\{nl}|{escape})*\'
+ //
+ // We'll implement a subset (in order to reduce attack
+ // surface); in particular:
+ //
+ // - No Unicode support
+ // - No escapes support
+ // - No string support (by proxy no attrib support)
+ // - element_name is matched against allowed
+ // elements (some people might find this
+ // annoying...)
+ // - Pseudo-elements one of :first-child, :link,
+ // :visited, :active, :hover, :focus
+
+ // handle ruleset
+ $selectors = array_map('trim', explode(',', $selector));
+ $new_selectors = array();
+ foreach ($selectors as $sel) {
+ // split on +, > and spaces
+ $basic_selectors = preg_split('/\s*([+> ])\s*/', $sel, -1, PREG_SPLIT_DELIM_CAPTURE);
+ // even indices are chunks, odd indices are
+ // delimiters
+ $nsel = null;
+ $delim = null; // guaranteed to be non-null after
+ // two loop iterations
+ for ($i = 0, $c = count($basic_selectors); $i < $c; $i++) {
+ $x = $basic_selectors[$i];
+ if ($i % 2) {
+ // delimiter
+ if ($x === ' ') {
+ $delim = ' ';
+ } else {
+ $delim = ' ' . $x . ' ';
+ }
+ } else {
+ // simple selector
+ $components = preg_split('/([#.:])/', $x, -1, PREG_SPLIT_DELIM_CAPTURE);
+ $sdelim = null;
+ $nx = null;
+ for ($j = 0, $cc = count($components); $j < $cc; $j++) {
+ $y = $components[$j];
+ if ($j === 0) {
+ if ($y === '*' || isset($html_definition->info[$y = strtolower($y)])) {
+ $nx = $y;
+ } else {
+ // $nx stays null; this matters
+ // if we don't manage to find
+ // any valid selector content,
+ // in which case we ignore the
+ // outer $delim
+ }
+ } elseif ($j % 2) {
+ // set delimiter
+ $sdelim = $y;
+ } else {
+ $attrdef = null;
+ if ($sdelim === '#') {
+ $attrdef = $this->_id_attrdef;
+ } elseif ($sdelim === '.') {
+ $attrdef = $this->_class_attrdef;
+ } elseif ($sdelim === ':') {
+ $attrdef = $this->_enum_attrdef;
+ } else {
+ throw new HTMLPurifier_Exception('broken invariant sdelim and preg_split');
+ }
+ $r = $attrdef->validate($y, $config, $context);
+ if ($r !== false) {
+ if ($r !== true) {
+ $y = $r;
+ }
+ if ($nx === null) {
+ $nx = '';
+ }
+ $nx .= $sdelim . $y;
+ }
+ }
+ }
+ if ($nx !== null) {
+ if ($nsel === null) {
+ $nsel = $nx;
+ } else {
+ $nsel .= $delim . $nx;
+ }
+ } else {
+ // delimiters to the left of invalid
+ // basic selector ignored
+ }
+ }
+ }
+ if ($nsel !== null) {
+ if (!empty($scopes)) {
+ foreach ($scopes as $s) {
+ $new_selectors[] = "$s $nsel";
+ }
+ } else {
+ $new_selectors[] = $nsel;
+ }
+ }
+ }
+ if (empty($new_selectors)) {
+ continue;
+ }
+ $selector = implode(', ', $new_selectors);
+ foreach ($style as $name => $value) {
+ if (!isset($css_definition->info[$name])) {
+ unset($style[$name]);
+ continue;
+ }
+ $def = $css_definition->info[$name];
+ $ret = $def->validate($value, $config, $context);
+ if ($ret === false) {
+ unset($style[$name]);
+ } else {
+ $style[$name] = $ret;
+ }
+ }
+ $new_decls[$selector] = $style;
+ }
+ $new_css[$k] = $new_decls;
+ }
+ // remove stuff that shouldn't be used, could be reenabled
+ // after security risks are analyzed
+ $this->_tidy->css = $new_css;
+ $this->_tidy->import = array();
+ $this->_tidy->charset = null;
+ $this->_tidy->namespace = null;
+ $css = $this->_tidy->print->plain();
+ // we are going to escape any special characters <>& to ensure
+ // that no funny business occurs (i.e. </style> in a font-family prop).
+ if ($config->get('Filter.ExtractStyleBlocks.Escaping')) {
+ $css = str_replace(
+ array('<', '>', '&'),
+ array('\3C ', '\3E ', '\26 '),
+ $css
+ );
+ }
+ return $css;
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Filter/YouTube.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Filter/YouTube.php
new file mode 100644
index 000000000..276d8362f
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Filter/YouTube.php
@@ -0,0 +1,65 @@
+<?php
+
+class HTMLPurifier_Filter_YouTube extends HTMLPurifier_Filter
+{
+
+ /**
+ * @type string
+ */
+ public $name = 'YouTube';
+
+ /**
+ * @param string $html
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return string
+ */
+ public function preFilter($html, $config, $context)
+ {
+ $pre_regex = '#<object[^>]+>.+?' .
+ '(?:http:)?//www.youtube.com/((?:v|cp)/[A-Za-z0-9\-_=]+).+?</object>#s';
+ $pre_replace = '<span class="youtube-embed">\1</span>';
+ return preg_replace($pre_regex, $pre_replace, $html);
+ }
+
+ /**
+ * @param string $html
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return string
+ */
+ public function postFilter($html, $config, $context)
+ {
+ $post_regex = '#<span class="youtube-embed">((?:v|cp)/[A-Za-z0-9\-_=]+)</span>#';
+ return preg_replace_callback($post_regex, array($this, 'postFilterCallback'), $html);
+ }
+
+ /**
+ * @param $url
+ * @return string
+ */
+ protected function armorUrl($url)
+ {
+ return str_replace('--', '-&#45;', $url);
+ }
+
+ /**
+ * @param array $matches
+ * @return string
+ */
+ protected function postFilterCallback($matches)
+ {
+ $url = $this->armorUrl($matches[1]);
+ return '<object width="425" height="350" type="application/x-shockwave-flash" ' .
+ 'data="//www.youtube.com/' . $url . '">' .
+ '<param name="movie" value="//www.youtube.com/' . $url . '"></param>' .
+ '<!--[if IE]>' .
+ '<embed src="//www.youtube.com/' . $url . '"' .
+ 'type="application/x-shockwave-flash"' .
+ 'wmode="transparent" width="425" height="350" />' .
+ '<![endif]-->' .
+ '</object>';
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Generator.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Generator.php
new file mode 100644
index 000000000..eb56e2dfa
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Generator.php
@@ -0,0 +1,286 @@
+<?php
+
+/**
+ * Generates HTML from tokens.
+ * @todo Refactor interface so that configuration/context is determined
+ * upon instantiation, no need for messy generateFromTokens() calls
+ * @todo Make some of the more internal functions protected, and have
+ * unit tests work around that
+ */
+class HTMLPurifier_Generator
+{
+
+ /**
+ * Whether or not generator should produce XML output.
+ * @type bool
+ */
+ private $_xhtml = true;
+
+ /**
+ * :HACK: Whether or not generator should comment the insides of <script> tags.
+ * @type bool
+ */
+ private $_scriptFix = false;
+
+ /**
+ * Cache of HTMLDefinition during HTML output to determine whether or
+ * not attributes should be minimized.
+ * @type HTMLPurifier_HTMLDefinition
+ */
+ private $_def;
+
+ /**
+ * Cache of %Output.SortAttr.
+ * @type bool
+ */
+ private $_sortAttr;
+
+ /**
+ * Cache of %Output.FlashCompat.
+ * @type bool
+ */
+ private $_flashCompat;
+
+ /**
+ * Cache of %Output.FixInnerHTML.
+ * @type bool
+ */
+ private $_innerHTMLFix;
+
+ /**
+ * Stack for keeping track of object information when outputting IE
+ * compatibility code.
+ * @type array
+ */
+ private $_flashStack = array();
+
+ /**
+ * Configuration for the generator
+ * @type HTMLPurifier_Config
+ */
+ protected $config;
+
+ /**
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ */
+ public function __construct($config, $context)
+ {
+ $this->config = $config;
+ $this->_scriptFix = $config->get('Output.CommentScriptContents');
+ $this->_innerHTMLFix = $config->get('Output.FixInnerHTML');
+ $this->_sortAttr = $config->get('Output.SortAttr');
+ $this->_flashCompat = $config->get('Output.FlashCompat');
+ $this->_def = $config->getHTMLDefinition();
+ $this->_xhtml = $this->_def->doctype->xml;
+ }
+
+ /**
+ * Generates HTML from an array of tokens.
+ * @param HTMLPurifier_Token[] $tokens Array of HTMLPurifier_Token
+ * @return string Generated HTML
+ */
+ public function generateFromTokens($tokens)
+ {
+ if (!$tokens) {
+ return '';
+ }
+
+ // Basic algorithm
+ $html = '';
+ for ($i = 0, $size = count($tokens); $i < $size; $i++) {
+ if ($this->_scriptFix && $tokens[$i]->name === 'script'
+ && $i + 2 < $size && $tokens[$i+2] instanceof HTMLPurifier_Token_End) {
+ // script special case
+ // the contents of the script block must be ONE token
+ // for this to work.
+ $html .= $this->generateFromToken($tokens[$i++]);
+ $html .= $this->generateScriptFromToken($tokens[$i++]);
+ }
+ $html .= $this->generateFromToken($tokens[$i]);
+ }
+
+ // Tidy cleanup
+ if (extension_loaded('tidy') && $this->config->get('Output.TidyFormat')) {
+ $tidy = new Tidy;
+ $tidy->parseString(
+ $html,
+ array(
+ 'indent'=> true,
+ 'output-xhtml' => $this->_xhtml,
+ 'show-body-only' => true,
+ 'indent-spaces' => 2,
+ 'wrap' => 68,
+ ),
+ 'utf8'
+ );
+ $tidy->cleanRepair();
+ $html = (string) $tidy; // explicit cast necessary
+ }
+
+ // Normalize newlines to system defined value
+ if ($this->config->get('Core.NormalizeNewlines')) {
+ $nl = $this->config->get('Output.Newline');
+ if ($nl === null) {
+ $nl = PHP_EOL;
+ }
+ if ($nl !== "\n") {
+ $html = str_replace("\n", $nl, $html);
+ }
+ }
+ return $html;
+ }
+
+ /**
+ * Generates HTML from a single token.
+ * @param HTMLPurifier_Token $token HTMLPurifier_Token object.
+ * @return string Generated HTML
+ */
+ public function generateFromToken($token)
+ {
+ if (!$token instanceof HTMLPurifier_Token) {
+ trigger_error('Cannot generate HTML from non-HTMLPurifier_Token object', E_USER_WARNING);
+ return '';
+
+ } elseif ($token instanceof HTMLPurifier_Token_Start) {
+ $attr = $this->generateAttributes($token->attr, $token->name);
+ if ($this->_flashCompat) {
+ if ($token->name == "object") {
+ $flash = new stdClass();
+ $flash->attr = $token->attr;
+ $flash->param = array();
+ $this->_flashStack[] = $flash;
+ }
+ }
+ return '<' . $token->name . ($attr ? ' ' : '') . $attr . '>';
+
+ } elseif ($token instanceof HTMLPurifier_Token_End) {
+ $_extra = '';
+ if ($this->_flashCompat) {
+ if ($token->name == "object" && !empty($this->_flashStack)) {
+ // doesn't do anything for now
+ }
+ }
+ return $_extra . '</' . $token->name . '>';
+
+ } elseif ($token instanceof HTMLPurifier_Token_Empty) {
+ if ($this->_flashCompat && $token->name == "param" && !empty($this->_flashStack)) {
+ $this->_flashStack[count($this->_flashStack)-1]->param[$token->attr['name']] = $token->attr['value'];
+ }
+ $attr = $this->generateAttributes($token->attr, $token->name);
+ return '<' . $token->name . ($attr ? ' ' : '') . $attr .
+ ( $this->_xhtml ? ' /': '' ) // <br /> v. <br>
+ . '>';
+
+ } elseif ($token instanceof HTMLPurifier_Token_Text) {
+ return $this->escape($token->data, ENT_NOQUOTES);
+
+ } elseif ($token instanceof HTMLPurifier_Token_Comment) {
+ return '<!--' . $token->data . '-->';
+ } else {
+ return '';
+
+ }
+ }
+
+ /**
+ * Special case processor for the contents of script tags
+ * @param HTMLPurifier_Token $token HTMLPurifier_Token object.
+ * @return string
+ * @warning This runs into problems if there's already a literal
+ * --> somewhere inside the script contents.
+ */
+ public function generateScriptFromToken($token)
+ {
+ if (!$token instanceof HTMLPurifier_Token_Text) {
+ return $this->generateFromToken($token);
+ }
+ // Thanks <http://lachy.id.au/log/2005/05/script-comments>
+ $data = preg_replace('#//\s*$#', '', $token->data);
+ return '<!--//--><![CDATA[//><!--' . "\n" . trim($data) . "\n" . '//--><!]]>';
+ }
+
+ /**
+ * Generates attribute declarations from attribute array.
+ * @note This does not include the leading or trailing space.
+ * @param array $assoc_array_of_attributes Attribute array
+ * @param string $element Name of element attributes are for, used to check
+ * attribute minimization.
+ * @return string Generated HTML fragment for insertion.
+ */
+ public function generateAttributes($assoc_array_of_attributes, $element = '')
+ {
+ $html = '';
+ if ($this->_sortAttr) {
+ ksort($assoc_array_of_attributes);
+ }
+ foreach ($assoc_array_of_attributes as $key => $value) {
+ if (!$this->_xhtml) {
+ // Remove namespaced attributes
+ if (strpos($key, ':') !== false) {
+ continue;
+ }
+ // Check if we should minimize the attribute: val="val" -> val
+ if ($element && !empty($this->_def->info[$element]->attr[$key]->minimized)) {
+ $html .= $key . ' ';
+ continue;
+ }
+ }
+ // Workaround for Internet Explorer innerHTML bug.
+ // Essentially, Internet Explorer, when calculating
+ // innerHTML, omits quotes if there are no instances of
+ // angled brackets, quotes or spaces. However, when parsing
+ // HTML (for example, when you assign to innerHTML), it
+ // treats backticks as quotes. Thus,
+ // <img alt="``" />
+ // becomes
+ // <img alt=`` />
+ // becomes
+ // <img alt='' />
+ // Fortunately, all we need to do is trigger an appropriate
+ // quoting style, which we do by adding an extra space.
+ // This also is consistent with the W3C spec, which states
+ // that user agents may ignore leading or trailing
+ // whitespace (in fact, most don't, at least for attributes
+ // like alt, but an extra space at the end is barely
+ // noticeable). Still, we have a configuration knob for
+ // this, since this transformation is not necesary if you
+ // don't process user input with innerHTML or you don't plan
+ // on supporting Internet Explorer.
+ if ($this->_innerHTMLFix) {
+ if (strpos($value, '`') !== false) {
+ // check if correct quoting style would not already be
+ // triggered
+ if (strcspn($value, '"\' <>') === strlen($value)) {
+ // protect!
+ $value .= ' ';
+ }
+ }
+ }
+ $html .= $key.'="'.$this->escape($value).'" ';
+ }
+ return rtrim($html);
+ }
+
+ /**
+ * Escapes raw text data.
+ * @todo This really ought to be protected, but until we have a facility
+ * for properly generating HTML here w/o using tokens, it stays
+ * public.
+ * @param string $string String data to escape for HTML.
+ * @param int $quote Quoting style, like htmlspecialchars. ENT_NOQUOTES is
+ * permissible for non-attribute output.
+ * @return string escaped data.
+ */
+ public function escape($string, $quote = null)
+ {
+ // Workaround for APC bug on Mac Leopard reported by sidepodcast
+ // http://htmlpurifier.org/phorum/read.php?3,4823,4846
+ if ($quote === null) {
+ $quote = ENT_COMPAT;
+ }
+ return htmlspecialchars($string, $quote, 'UTF-8');
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/HTMLDefinition.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLDefinition.php
index 9b7b334dd..9b7b334dd 100644
--- a/library/HTMLPurifier/HTMLDefinition.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLDefinition.php
diff --git a/library/HTMLPurifier/HTMLModule.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule.php
index bb3a9230b..bb3a9230b 100644
--- a/library/HTMLPurifier/HTMLModule.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule.php
diff --git a/library/HTMLPurifier/HTMLModule/Bdo.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Bdo.php
index 1e67c790d..1e67c790d 100644
--- a/library/HTMLPurifier/HTMLModule/Bdo.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Bdo.php
diff --git a/library/HTMLPurifier/HTMLModule/CommonAttributes.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/CommonAttributes.php
index a96ab1bef..a96ab1bef 100644
--- a/library/HTMLPurifier/HTMLModule/CommonAttributes.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/CommonAttributes.php
diff --git a/library/HTMLPurifier/HTMLModule/Edit.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Edit.php
index a9042a357..a9042a357 100644
--- a/library/HTMLPurifier/HTMLModule/Edit.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Edit.php
diff --git a/library/HTMLPurifier/HTMLModule/Forms.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Forms.php
index 6f7ddbc05..6f7ddbc05 100644
--- a/library/HTMLPurifier/HTMLModule/Forms.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Forms.php
diff --git a/library/HTMLPurifier/HTMLModule/Hypertext.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Hypertext.php
index 72d7a31e6..72d7a31e6 100644
--- a/library/HTMLPurifier/HTMLModule/Hypertext.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Hypertext.php
diff --git a/library/HTMLPurifier/HTMLModule/Iframe.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Iframe.php
index f7e7c91c0..f7e7c91c0 100644
--- a/library/HTMLPurifier/HTMLModule/Iframe.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Iframe.php
diff --git a/library/HTMLPurifier/HTMLModule/Image.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Image.php
index 0f5fdb3ba..0f5fdb3ba 100644
--- a/library/HTMLPurifier/HTMLModule/Image.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Image.php
diff --git a/library/HTMLPurifier/HTMLModule/Legacy.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Legacy.php
index 86b529957..86b529957 100644
--- a/library/HTMLPurifier/HTMLModule/Legacy.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Legacy.php
diff --git a/library/HTMLPurifier/HTMLModule/List.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/List.php
index 7a20ff701..7a20ff701 100644
--- a/library/HTMLPurifier/HTMLModule/List.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/List.php
diff --git a/library/HTMLPurifier/HTMLModule/Name.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Name.php
index 60c054515..60c054515 100644
--- a/library/HTMLPurifier/HTMLModule/Name.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Name.php
diff --git a/library/HTMLPurifier/HTMLModule/Nofollow.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Nofollow.php
index dc9410a89..dc9410a89 100644
--- a/library/HTMLPurifier/HTMLModule/Nofollow.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Nofollow.php
diff --git a/library/HTMLPurifier/HTMLModule/NonXMLCommonAttributes.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/NonXMLCommonAttributes.php
index da722253a..da722253a 100644
--- a/library/HTMLPurifier/HTMLModule/NonXMLCommonAttributes.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/NonXMLCommonAttributes.php
diff --git a/library/HTMLPurifier/HTMLModule/Object.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Object.php
index 2f9efc5c8..2f9efc5c8 100644
--- a/library/HTMLPurifier/HTMLModule/Object.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Object.php
diff --git a/library/HTMLPurifier/HTMLModule/Presentation.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Presentation.php
index 6458ce9d8..6458ce9d8 100644
--- a/library/HTMLPurifier/HTMLModule/Presentation.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Presentation.php
diff --git a/library/HTMLPurifier/HTMLModule/Proprietary.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Proprietary.php
index 5ee3c8e67..5ee3c8e67 100644
--- a/library/HTMLPurifier/HTMLModule/Proprietary.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Proprietary.php
diff --git a/library/HTMLPurifier/HTMLModule/Ruby.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Ruby.php
index a0d48924d..a0d48924d 100644
--- a/library/HTMLPurifier/HTMLModule/Ruby.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Ruby.php
diff --git a/library/HTMLPurifier/HTMLModule/SafeEmbed.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/SafeEmbed.php
index 04e6689ea..04e6689ea 100644
--- a/library/HTMLPurifier/HTMLModule/SafeEmbed.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/SafeEmbed.php
diff --git a/library/HTMLPurifier/HTMLModule/SafeObject.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/SafeObject.php
index 1297f80a3..1297f80a3 100644
--- a/library/HTMLPurifier/HTMLModule/SafeObject.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/SafeObject.php
diff --git a/library/HTMLPurifier/HTMLModule/SafeScripting.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/SafeScripting.php
index 0330cd97f..0330cd97f 100644
--- a/library/HTMLPurifier/HTMLModule/SafeScripting.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/SafeScripting.php
diff --git a/library/HTMLPurifier/HTMLModule/Scripting.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Scripting.php
index 8b28a7b7e..8b28a7b7e 100644
--- a/library/HTMLPurifier/HTMLModule/Scripting.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Scripting.php
diff --git a/library/HTMLPurifier/HTMLModule/StyleAttribute.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/StyleAttribute.php
index 497b832ae..497b832ae 100644
--- a/library/HTMLPurifier/HTMLModule/StyleAttribute.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/StyleAttribute.php
diff --git a/library/HTMLPurifier/HTMLModule/Tables.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tables.php
index 8a0b3b461..8a0b3b461 100644
--- a/library/HTMLPurifier/HTMLModule/Tables.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tables.php
diff --git a/library/HTMLPurifier/HTMLModule/Target.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Target.php
index b188ac936..b188ac936 100644
--- a/library/HTMLPurifier/HTMLModule/Target.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Target.php
diff --git a/library/HTMLPurifier/HTMLModule/TargetBlank.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/TargetBlank.php
index 58ccc6894..58ccc6894 100644
--- a/library/HTMLPurifier/HTMLModule/TargetBlank.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/TargetBlank.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/TargetNoopener.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/TargetNoopener.php
new file mode 100644
index 000000000..b967ff566
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/TargetNoopener.php
@@ -0,0 +1,21 @@
+<?php
+
+/**
+ * Module adds the target-based noopener attribute transformation to a tags. It
+ * is enabled by HTML.TargetNoopener
+ */
+class HTMLPurifier_HTMLModule_TargetNoopener extends HTMLPurifier_HTMLModule
+{
+ /**
+ * @type string
+ */
+ public $name = 'TargetNoopener';
+
+ /**
+ * @param HTMLPurifier_Config $config
+ */
+ public function setup($config) {
+ $a = $this->addBlankElement('a');
+ $a->attr_transform_post[] = new HTMLPurifier_AttrTransform_TargetNoopener();
+ }
+}
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/TargetNoreferrer.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/TargetNoreferrer.php
new file mode 100644
index 000000000..32484d601
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/TargetNoreferrer.php
@@ -0,0 +1,21 @@
+<?php
+
+/**
+ * Module adds the target-based noreferrer attribute transformation to a tags. It
+ * is enabled by HTML.TargetNoreferrer
+ */
+class HTMLPurifier_HTMLModule_TargetNoreferrer extends HTMLPurifier_HTMLModule
+{
+ /**
+ * @type string
+ */
+ public $name = 'TargetNoreferrer';
+
+ /**
+ * @param HTMLPurifier_Config $config
+ */
+ public function setup($config) {
+ $a = $this->addBlankElement('a');
+ $a->attr_transform_post[] = new HTMLPurifier_AttrTransform_TargetNoreferrer();
+ }
+}
diff --git a/library/HTMLPurifier/HTMLModule/Text.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Text.php
index 7a65e0048..7a65e0048 100644
--- a/library/HTMLPurifier/HTMLModule/Text.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Text.php
diff --git a/library/HTMLPurifier/HTMLModule/Tidy.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy.php
index 08aa23247..08aa23247 100644
--- a/library/HTMLPurifier/HTMLModule/Tidy.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy.php
diff --git a/library/HTMLPurifier/HTMLModule/Tidy/Name.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/Name.php
index a995161b2..a995161b2 100644
--- a/library/HTMLPurifier/HTMLModule/Tidy/Name.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/Name.php
diff --git a/library/HTMLPurifier/HTMLModule/Tidy/Proprietary.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/Proprietary.php
index 332643821..332643821 100644
--- a/library/HTMLPurifier/HTMLModule/Tidy/Proprietary.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/Proprietary.php
diff --git a/library/HTMLPurifier/HTMLModule/Tidy/Strict.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/Strict.php
index 803c44fab..803c44fab 100644
--- a/library/HTMLPurifier/HTMLModule/Tidy/Strict.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/Strict.php
diff --git a/library/HTMLPurifier/HTMLModule/Tidy/Transitional.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/Transitional.php
index c095ad974..c095ad974 100644
--- a/library/HTMLPurifier/HTMLModule/Tidy/Transitional.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/Transitional.php
diff --git a/library/HTMLPurifier/HTMLModule/Tidy/XHTML.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/XHTML.php
index 3ecddc434..3ecddc434 100644
--- a/library/HTMLPurifier/HTMLModule/Tidy/XHTML.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/XHTML.php
diff --git a/library/HTMLPurifier/HTMLModule/Tidy/XHTMLAndHTML4.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/XHTMLAndHTML4.php
index c4f16a4dc..c4f16a4dc 100644
--- a/library/HTMLPurifier/HTMLModule/Tidy/XHTMLAndHTML4.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/Tidy/XHTMLAndHTML4.php
diff --git a/library/HTMLPurifier/HTMLModule/XMLCommonAttributes.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/XMLCommonAttributes.php
index 01dbe9deb..01dbe9deb 100644
--- a/library/HTMLPurifier/HTMLModule/XMLCommonAttributes.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModule/XMLCommonAttributes.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModuleManager.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModuleManager.php
new file mode 100644
index 000000000..38c058fe2
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/HTMLModuleManager.php
@@ -0,0 +1,467 @@
+<?php
+
+class HTMLPurifier_HTMLModuleManager
+{
+
+ /**
+ * @type HTMLPurifier_DoctypeRegistry
+ */
+ public $doctypes;
+
+ /**
+ * Instance of current doctype.
+ * @type string
+ */
+ public $doctype;
+
+ /**
+ * @type HTMLPurifier_AttrTypes
+ */
+ public $attrTypes;
+
+ /**
+ * Active instances of modules for the specified doctype are
+ * indexed, by name, in this array.
+ * @type HTMLPurifier_HTMLModule[]
+ */
+ public $modules = array();
+
+ /**
+ * Array of recognized HTMLPurifier_HTMLModule instances,
+ * indexed by module's class name. This array is usually lazy loaded, but a
+ * user can overload a module by pre-emptively registering it.
+ * @type HTMLPurifier_HTMLModule[]
+ */
+ public $registeredModules = array();
+
+ /**
+ * List of extra modules that were added by the user
+ * using addModule(). These get unconditionally merged into the current doctype, whatever
+ * it may be.
+ * @type HTMLPurifier_HTMLModule[]
+ */
+ public $userModules = array();
+
+ /**
+ * Associative array of element name to list of modules that have
+ * definitions for the element; this array is dynamically filled.
+ * @type array
+ */
+ public $elementLookup = array();
+
+ /**
+ * List of prefixes we should use for registering small names.
+ * @type array
+ */
+ public $prefixes = array('HTMLPurifier_HTMLModule_');
+
+ /**
+ * @type HTMLPurifier_ContentSets
+ */
+ public $contentSets;
+
+ /**
+ * @type HTMLPurifier_AttrCollections
+ */
+ public $attrCollections;
+
+ /**
+ * If set to true, unsafe elements and attributes will be allowed.
+ * @type bool
+ */
+ public $trusted = false;
+
+ public function __construct()
+ {
+ // editable internal objects
+ $this->attrTypes = new HTMLPurifier_AttrTypes();
+ $this->doctypes = new HTMLPurifier_DoctypeRegistry();
+
+ // setup basic modules
+ $common = array(
+ 'CommonAttributes', 'Text', 'Hypertext', 'List',
+ 'Presentation', 'Edit', 'Bdo', 'Tables', 'Image',
+ 'StyleAttribute',
+ // Unsafe:
+ 'Scripting', 'Object', 'Forms',
+ // Sorta legacy, but present in strict:
+ 'Name',
+ );
+ $transitional = array('Legacy', 'Target', 'Iframe');
+ $xml = array('XMLCommonAttributes');
+ $non_xml = array('NonXMLCommonAttributes');
+
+ // setup basic doctypes
+ $this->doctypes->register(
+ 'HTML 4.01 Transitional',
+ false,
+ array_merge($common, $transitional, $non_xml),
+ array('Tidy_Transitional', 'Tidy_Proprietary'),
+ array(),
+ '-//W3C//DTD HTML 4.01 Transitional//EN',
+ 'http://www.w3.org/TR/html4/loose.dtd'
+ );
+
+ $this->doctypes->register(
+ 'HTML 4.01 Strict',
+ false,
+ array_merge($common, $non_xml),
+ array('Tidy_Strict', 'Tidy_Proprietary', 'Tidy_Name'),
+ array(),
+ '-//W3C//DTD HTML 4.01//EN',
+ 'http://www.w3.org/TR/html4/strict.dtd'
+ );
+
+ $this->doctypes->register(
+ 'XHTML 1.0 Transitional',
+ true,
+ array_merge($common, $transitional, $xml, $non_xml),
+ array('Tidy_Transitional', 'Tidy_XHTML', 'Tidy_Proprietary', 'Tidy_Name'),
+ array(),
+ '-//W3C//DTD XHTML 1.0 Transitional//EN',
+ 'http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd'
+ );
+
+ $this->doctypes->register(
+ 'XHTML 1.0 Strict',
+ true,
+ array_merge($common, $xml, $non_xml),
+ array('Tidy_Strict', 'Tidy_XHTML', 'Tidy_Strict', 'Tidy_Proprietary', 'Tidy_Name'),
+ array(),
+ '-//W3C//DTD XHTML 1.0 Strict//EN',
+ 'http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd'
+ );
+
+ $this->doctypes->register(
+ 'XHTML 1.1',
+ true,
+ // Iframe is a real XHTML 1.1 module, despite being
+ // "transitional"!
+ array_merge($common, $xml, array('Ruby', 'Iframe')),
+ array('Tidy_Strict', 'Tidy_XHTML', 'Tidy_Proprietary', 'Tidy_Strict', 'Tidy_Name'), // Tidy_XHTML1_1
+ array(),
+ '-//W3C//DTD XHTML 1.1//EN',
+ 'http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd'
+ );
+
+ }
+
+ /**
+ * Registers a module to the recognized module list, useful for
+ * overloading pre-existing modules.
+ * @param $module Mixed: string module name, with or without
+ * HTMLPurifier_HTMLModule prefix, or instance of
+ * subclass of HTMLPurifier_HTMLModule.
+ * @param $overload Boolean whether or not to overload previous modules.
+ * If this is not set, and you do overload a module,
+ * HTML Purifier will complain with a warning.
+ * @note This function will not call autoload, you must instantiate
+ * (and thus invoke) autoload outside the method.
+ * @note If a string is passed as a module name, different variants
+ * will be tested in this order:
+ * - Check for HTMLPurifier_HTMLModule_$name
+ * - Check all prefixes with $name in order they were added
+ * - Check for literal object name
+ * - Throw fatal error
+ * If your object name collides with an internal class, specify
+ * your module manually. All modules must have been included
+ * externally: registerModule will not perform inclusions for you!
+ */
+ public function registerModule($module, $overload = false)
+ {
+ if (is_string($module)) {
+ // attempt to load the module
+ $original_module = $module;
+ $ok = false;
+ foreach ($this->prefixes as $prefix) {
+ $module = $prefix . $original_module;
+ if (class_exists($module)) {
+ $ok = true;
+ break;
+ }
+ }
+ if (!$ok) {
+ $module = $original_module;
+ if (!class_exists($module)) {
+ trigger_error(
+ $original_module . ' module does not exist',
+ E_USER_ERROR
+ );
+ return;
+ }
+ }
+ $module = new $module();
+ }
+ if (empty($module->name)) {
+ trigger_error('Module instance of ' . get_class($module) . ' must have name');
+ return;
+ }
+ if (!$overload && isset($this->registeredModules[$module->name])) {
+ trigger_error('Overloading ' . $module->name . ' without explicit overload parameter', E_USER_WARNING);
+ }
+ $this->registeredModules[$module->name] = $module;
+ }
+
+ /**
+ * Adds a module to the current doctype by first registering it,
+ * and then tacking it on to the active doctype
+ */
+ public function addModule($module)
+ {
+ $this->registerModule($module);
+ if (is_object($module)) {
+ $module = $module->name;
+ }
+ $this->userModules[] = $module;
+ }
+
+ /**
+ * Adds a class prefix that registerModule() will use to resolve a
+ * string name to a concrete class
+ */
+ public function addPrefix($prefix)
+ {
+ $this->prefixes[] = $prefix;
+ }
+
+ /**
+ * Performs processing on modules, after being called you may
+ * use getElement() and getElements()
+ * @param HTMLPurifier_Config $config
+ */
+ public function setup($config)
+ {
+ $this->trusted = $config->get('HTML.Trusted');
+
+ // generate
+ $this->doctype = $this->doctypes->make($config);
+ $modules = $this->doctype->modules;
+
+ // take out the default modules that aren't allowed
+ $lookup = $config->get('HTML.AllowedModules');
+ $special_cases = $config->get('HTML.CoreModules');
+
+ if (is_array($lookup)) {
+ foreach ($modules as $k => $m) {
+ if (isset($special_cases[$m])) {
+ continue;
+ }
+ if (!isset($lookup[$m])) {
+ unset($modules[$k]);
+ }
+ }
+ }
+
+ // custom modules
+ if ($config->get('HTML.Proprietary')) {
+ $modules[] = 'Proprietary';
+ }
+ if ($config->get('HTML.SafeObject')) {
+ $modules[] = 'SafeObject';
+ }
+ if ($config->get('HTML.SafeEmbed')) {
+ $modules[] = 'SafeEmbed';
+ }
+ if ($config->get('HTML.SafeScripting') !== array()) {
+ $modules[] = 'SafeScripting';
+ }
+ if ($config->get('HTML.Nofollow')) {
+ $modules[] = 'Nofollow';
+ }
+ if ($config->get('HTML.TargetBlank')) {
+ $modules[] = 'TargetBlank';
+ }
+ // NB: HTML.TargetNoreferrer and HTML.TargetNoopener must be AFTER HTML.TargetBlank
+ // so that its post-attr-transform gets run afterwards.
+ if ($config->get('HTML.TargetNoreferrer')) {
+ $modules[] = 'TargetNoreferrer';
+ }
+ if ($config->get('HTML.TargetNoopener')) {
+ $modules[] = 'TargetNoopener';
+ }
+
+ // merge in custom modules
+ $modules = array_merge($modules, $this->userModules);
+
+ foreach ($modules as $module) {
+ $this->processModule($module);
+ $this->modules[$module]->setup($config);
+ }
+
+ foreach ($this->doctype->tidyModules as $module) {
+ $this->processModule($module);
+ $this->modules[$module]->setup($config);
+ }
+
+ // prepare any injectors
+ foreach ($this->modules as $module) {
+ $n = array();
+ foreach ($module->info_injector as $injector) {
+ if (!is_object($injector)) {
+ $class = "HTMLPurifier_Injector_$injector";
+ $injector = new $class;
+ }
+ $n[$injector->name] = $injector;
+ }
+ $module->info_injector = $n;
+ }
+
+ // setup lookup table based on all valid modules
+ foreach ($this->modules as $module) {
+ foreach ($module->info as $name => $def) {
+ if (!isset($this->elementLookup[$name])) {
+ $this->elementLookup[$name] = array();
+ }
+ $this->elementLookup[$name][] = $module->name;
+ }
+ }
+
+ // note the different choice
+ $this->contentSets = new HTMLPurifier_ContentSets(
+ // content set assembly deals with all possible modules,
+ // not just ones deemed to be "safe"
+ $this->modules
+ );
+ $this->attrCollections = new HTMLPurifier_AttrCollections(
+ $this->attrTypes,
+ // there is no way to directly disable a global attribute,
+ // but using AllowedAttributes or simply not including
+ // the module in your custom doctype should be sufficient
+ $this->modules
+ );
+ }
+
+ /**
+ * Takes a module and adds it to the active module collection,
+ * registering it if necessary.
+ */
+ public function processModule($module)
+ {
+ if (!isset($this->registeredModules[$module]) || is_object($module)) {
+ $this->registerModule($module);
+ }
+ $this->modules[$module] = $this->registeredModules[$module];
+ }
+
+ /**
+ * Retrieves merged element definitions.
+ * @return Array of HTMLPurifier_ElementDef
+ */
+ public function getElements()
+ {
+ $elements = array();
+ foreach ($this->modules as $module) {
+ if (!$this->trusted && !$module->safe) {
+ continue;
+ }
+ foreach ($module->info as $name => $v) {
+ if (isset($elements[$name])) {
+ continue;
+ }
+ $elements[$name] = $this->getElement($name);
+ }
+ }
+
+ // remove dud elements, this happens when an element that
+ // appeared to be safe actually wasn't
+ foreach ($elements as $n => $v) {
+ if ($v === false) {
+ unset($elements[$n]);
+ }
+ }
+
+ return $elements;
+
+ }
+
+ /**
+ * Retrieves a single merged element definition
+ * @param string $name Name of element
+ * @param bool $trusted Boolean trusted overriding parameter: set to true
+ * if you want the full version of an element
+ * @return HTMLPurifier_ElementDef Merged HTMLPurifier_ElementDef
+ * @note You may notice that modules are getting iterated over twice (once
+ * in getElements() and once here). This
+ * is because
+ */
+ public function getElement($name, $trusted = null)
+ {
+ if (!isset($this->elementLookup[$name])) {
+ return false;
+ }
+
+ // setup global state variables
+ $def = false;
+ if ($trusted === null) {
+ $trusted = $this->trusted;
+ }
+
+ // iterate through each module that has registered itself to this
+ // element
+ foreach ($this->elementLookup[$name] as $module_name) {
+ $module = $this->modules[$module_name];
+
+ // refuse to create/merge from a module that is deemed unsafe--
+ // pretend the module doesn't exist--when trusted mode is not on.
+ if (!$trusted && !$module->safe) {
+ continue;
+ }
+
+ // clone is used because, ideally speaking, the original
+ // definition should not be modified. Usually, this will
+ // make no difference, but for consistency's sake
+ $new_def = clone $module->info[$name];
+
+ if (!$def && $new_def->standalone) {
+ $def = $new_def;
+ } elseif ($def) {
+ // This will occur even if $new_def is standalone. In practice,
+ // this will usually result in a full replacement.
+ $def->mergeIn($new_def);
+ } else {
+ // :TODO:
+ // non-standalone definitions that don't have a standalone
+ // to merge into could be deferred to the end
+ // HOWEVER, it is perfectly valid for a non-standalone
+ // definition to lack a standalone definition, even
+ // after all processing: this allows us to safely
+ // specify extra attributes for elements that may not be
+ // enabled all in one place. In particular, this might
+ // be the case for trusted elements. WARNING: care must
+ // be taken that the /extra/ definitions are all safe.
+ continue;
+ }
+
+ // attribute value expansions
+ $this->attrCollections->performInclusions($def->attr);
+ $this->attrCollections->expandIdentifiers($def->attr, $this->attrTypes);
+
+ // descendants_are_inline, for ChildDef_Chameleon
+ if (is_string($def->content_model) &&
+ strpos($def->content_model, 'Inline') !== false) {
+ if ($name != 'del' && $name != 'ins') {
+ // this is for you, ins/del
+ $def->descendants_are_inline = true;
+ }
+ }
+
+ $this->contentSets->generateChildDef($def, $module);
+ }
+
+ // This can occur if there is a blank definition, but no base to
+ // mix it in with
+ if (!$def) {
+ return false;
+ }
+
+ // add information on required attributes
+ foreach ($def->attr as $attr_name => $attr_def) {
+ if ($attr_def->required) {
+ $def->required_attr[] = $attr_name;
+ }
+ }
+ return $def;
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/IDAccumulator.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/IDAccumulator.php
index 65c902c07..65c902c07 100644
--- a/library/HTMLPurifier/IDAccumulator.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/IDAccumulator.php
diff --git a/library/HTMLPurifier/Injector.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector.php
index 5060eef9e..5060eef9e 100644
--- a/library/HTMLPurifier/Injector.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector.php
diff --git a/library/HTMLPurifier/Injector/AutoParagraph.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/AutoParagraph.php
index 4afdd128d..4afdd128d 100644
--- a/library/HTMLPurifier/Injector/AutoParagraph.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/AutoParagraph.php
diff --git a/library/HTMLPurifier/Injector/DisplayLinkURI.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/DisplayLinkURI.php
index c19b1bc27..c19b1bc27 100644
--- a/library/HTMLPurifier/Injector/DisplayLinkURI.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/DisplayLinkURI.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/Linkify.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/Linkify.php
new file mode 100644
index 000000000..74f83eaa7
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/Linkify.php
@@ -0,0 +1,64 @@
+<?php
+
+/**
+ * Injector that converts http, https and ftp text URLs to actual links.
+ */
+class HTMLPurifier_Injector_Linkify extends HTMLPurifier_Injector
+{
+ /**
+ * @type string
+ */
+ public $name = 'Linkify';
+
+ /**
+ * @type array
+ */
+ public $needed = array('a' => array('href'));
+
+ /**
+ * @param HTMLPurifier_Token $token
+ */
+ public function handleText(&$token)
+ {
+ if (!$this->allowsElement('a')) {
+ return;
+ }
+
+ if (strpos($token->data, '://') === false) {
+ // our really quick heuristic failed, abort
+ // this may not work so well if we want to match things like
+ // "google.com", but then again, most people don't
+ return;
+ }
+
+ // there is/are URL(s). Let's split the string.
+ // We use this regex:
+ // https://gist.github.com/gruber/249502
+ // but with @cscott's backtracking fix and also
+ // the Unicode characters un-Unicodified.
+ $bits = preg_split(
+ '/\\b((?:[a-z][\\w\\-]+:(?:\\/{1,3}|[a-z0-9%])|www\\d{0,3}[.]|[a-z0-9.\\-]+[.][a-z]{2,4}\\/)(?:[^\\s()<>]|\\((?:[^\\s()<>]|(?:\\([^\\s()<>]+\\)))*\\))+(?:\\((?:[^\\s()<>]|(?:\\([^\\s()<>]+\\)))*\\)|[^\\s`!()\\[\\]{};:\'".,<>?\x{00ab}\x{00bb}\x{201c}\x{201d}\x{2018}\x{2019}]))/iu',
+ $token->data, -1, PREG_SPLIT_DELIM_CAPTURE);
+
+
+ $token = array();
+
+ // $i = index
+ // $c = count
+ // $l = is link
+ for ($i = 0, $c = count($bits), $l = false; $i < $c; $i++, $l = !$l) {
+ if (!$l) {
+ if ($bits[$i] === '') {
+ continue;
+ }
+ $token[] = new HTMLPurifier_Token_Text($bits[$i]);
+ } else {
+ $token[] = new HTMLPurifier_Token_Start('a', array('href' => $bits[$i]));
+ $token[] = new HTMLPurifier_Token_Text($bits[$i]);
+ $token[] = new HTMLPurifier_Token_End('a');
+ }
+ }
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/Injector/PurifierLinkify.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/PurifierLinkify.php
index cb9046f33..cb9046f33 100644
--- a/library/HTMLPurifier/Injector/PurifierLinkify.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/PurifierLinkify.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/RemoveEmpty.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/RemoveEmpty.php
new file mode 100644
index 000000000..0ebc477c6
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/RemoveEmpty.php
@@ -0,0 +1,112 @@
+<?php
+
+class HTMLPurifier_Injector_RemoveEmpty extends HTMLPurifier_Injector
+{
+ /**
+ * @type HTMLPurifier_Context
+ */
+ private $context;
+
+ /**
+ * @type HTMLPurifier_Config
+ */
+ private $config;
+
+ /**
+ * @type HTMLPurifier_AttrValidator
+ */
+ private $attrValidator;
+
+ /**
+ * @type bool
+ */
+ private $removeNbsp;
+
+ /**
+ * @type bool
+ */
+ private $removeNbspExceptions;
+
+ /**
+ * Cached contents of %AutoFormat.RemoveEmpty.Predicate
+ * @type array
+ */
+ private $exclude;
+
+ /**
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return void
+ */
+ public function prepare($config, $context)
+ {
+ parent::prepare($config, $context);
+ $this->config = $config;
+ $this->context = $context;
+ $this->removeNbsp = $config->get('AutoFormat.RemoveEmpty.RemoveNbsp');
+ $this->removeNbspExceptions = $config->get('AutoFormat.RemoveEmpty.RemoveNbsp.Exceptions');
+ $this->exclude = $config->get('AutoFormat.RemoveEmpty.Predicate');
+ foreach ($this->exclude as $key => $attrs) {
+ if (!is_array($attrs)) {
+ // HACK, see HTMLPurifier/Printer/ConfigForm.php
+ $this->exclude[$key] = explode(';', $attrs);
+ }
+ }
+ $this->attrValidator = new HTMLPurifier_AttrValidator();
+ }
+
+ /**
+ * @param HTMLPurifier_Token $token
+ */
+ public function handleElement(&$token)
+ {
+ if (!$token instanceof HTMLPurifier_Token_Start) {
+ return;
+ }
+ $next = false;
+ $deleted = 1; // the current tag
+ for ($i = count($this->inputZipper->back) - 1; $i >= 0; $i--, $deleted++) {
+ $next = $this->inputZipper->back[$i];
+ if ($next instanceof HTMLPurifier_Token_Text) {
+ if ($next->is_whitespace) {
+ continue;
+ }
+ if ($this->removeNbsp && !isset($this->removeNbspExceptions[$token->name])) {
+ $plain = str_replace("\xC2\xA0", "", $next->data);
+ $isWsOrNbsp = $plain === '' || ctype_space($plain);
+ if ($isWsOrNbsp) {
+ continue;
+ }
+ }
+ }
+ break;
+ }
+ if (!$next || ($next instanceof HTMLPurifier_Token_End && $next->name == $token->name)) {
+ $this->attrValidator->validateToken($token, $this->config, $this->context);
+ $token->armor['ValidateAttributes'] = true;
+ if (isset($this->exclude[$token->name])) {
+ $r = true;
+ foreach ($this->exclude[$token->name] as $elem) {
+ if (!isset($token->attr[$elem])) $r = false;
+ }
+ if ($r) return;
+ }
+ if (isset($token->attr['id']) || isset($token->attr['name'])) {
+ return;
+ }
+ $token = $deleted + 1;
+ for ($b = 0, $c = count($this->inputZipper->front); $b < $c; $b++) {
+ $prev = $this->inputZipper->front[$b];
+ if ($prev instanceof HTMLPurifier_Token_Text && $prev->is_whitespace) {
+ continue;
+ }
+ break;
+ }
+ // This is safe because we removed the token that triggered this.
+ $this->rewindOffset($b+$deleted);
+ return;
+ }
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/Injector/RemoveSpansWithoutAttributes.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/RemoveSpansWithoutAttributes.php
index 9ee7aa84d..9ee7aa84d 100644
--- a/library/HTMLPurifier/Injector/RemoveSpansWithoutAttributes.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/RemoveSpansWithoutAttributes.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/SafeObject.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/SafeObject.php
new file mode 100644
index 000000000..317f7864d
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Injector/SafeObject.php
@@ -0,0 +1,124 @@
+<?php
+
+/**
+ * Adds important param elements to inside of object in order to make
+ * things safe.
+ */
+class HTMLPurifier_Injector_SafeObject extends HTMLPurifier_Injector
+{
+ /**
+ * @type string
+ */
+ public $name = 'SafeObject';
+
+ /**
+ * @type array
+ */
+ public $needed = array('object', 'param');
+
+ /**
+ * @type array
+ */
+ protected $objectStack = array();
+
+ /**
+ * @type array
+ */
+ protected $paramStack = array();
+
+ /**
+ * Keep this synchronized with AttrTransform/SafeParam.php.
+ * @type array
+ */
+ protected $addParam = array(
+ 'allowScriptAccess' => 'never',
+ 'allowNetworking' => 'internal',
+ );
+
+ /**
+ * These are all lower-case keys.
+ * @type array
+ */
+ protected $allowedParam = array(
+ 'wmode' => true,
+ 'movie' => true,
+ 'flashvars' => true,
+ 'src' => true,
+ 'allowfullscreen' => true, // if omitted, assume to be 'false'
+ );
+
+ /**
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return void
+ */
+ public function prepare($config, $context)
+ {
+ parent::prepare($config, $context);
+ }
+
+ /**
+ * @param HTMLPurifier_Token $token
+ */
+ public function handleElement(&$token)
+ {
+ if ($token->name == 'object') {
+ $this->objectStack[] = $token;
+ $this->paramStack[] = array();
+ $new = array($token);
+ foreach ($this->addParam as $name => $value) {
+ $new[] = new HTMLPurifier_Token_Empty('param', array('name' => $name, 'value' => $value));
+ }
+ $token = $new;
+ } elseif ($token->name == 'param') {
+ $nest = count($this->currentNesting) - 1;
+ if ($nest >= 0 && $this->currentNesting[$nest]->name === 'object') {
+ $i = count($this->objectStack) - 1;
+ if (!isset($token->attr['name'])) {
+ $token = false;
+ return;
+ }
+ $n = $token->attr['name'];
+ // We need this fix because YouTube doesn't supply a data
+ // attribute, which we need if a type is specified. This is
+ // *very* Flash specific.
+ if (!isset($this->objectStack[$i]->attr['data']) &&
+ ($token->attr['name'] == 'movie' || $token->attr['name'] == 'src')
+ ) {
+ $this->objectStack[$i]->attr['data'] = $token->attr['value'];
+ }
+ // Check if the parameter is the correct value but has not
+ // already been added
+ if (!isset($this->paramStack[$i][$n]) &&
+ isset($this->addParam[$n]) &&
+ $token->attr['name'] === $this->addParam[$n]) {
+ // keep token, and add to param stack
+ $this->paramStack[$i][$n] = true;
+ } elseif (isset($this->allowedParam[strtolower($n)])) {
+ // keep token, don't do anything to it
+ // (could possibly check for duplicates here)
+ // Note: In principle, parameters should be case sensitive.
+ // But it seems they are not really; so accept any case.
+ } else {
+ $token = false;
+ }
+ } else {
+ // not directly inside an object, DENY!
+ $token = false;
+ }
+ }
+ }
+
+ public function handleEnd(&$token)
+ {
+ // This is the WRONG way of handling the object and param stacks;
+ // we should be inserting them directly on the relevant object tokens
+ // so that the global stack handling handles it.
+ if ($token->name == 'object') {
+ array_pop($this->objectStack);
+ array_pop($this->paramStack);
+ }
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/Language.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Language.php
index 65277dd43..65277dd43 100644
--- a/library/HTMLPurifier/Language.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Language.php
diff --git a/library/HTMLPurifier/Language/classes/en-x-test.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Language/classes/en-x-test.php
index 8828f5cde..8828f5cde 100644
--- a/library/HTMLPurifier/Language/classes/en-x-test.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Language/classes/en-x-test.php
diff --git a/library/HTMLPurifier/Language/messages/en-x-test.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Language/messages/en-x-test.php
index 1c046f379..1c046f379 100644
--- a/library/HTMLPurifier/Language/messages/en-x-test.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Language/messages/en-x-test.php
diff --git a/library/HTMLPurifier/Language/messages/en-x-testmini.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Language/messages/en-x-testmini.php
index 806c83fbf..806c83fbf 100644
--- a/library/HTMLPurifier/Language/messages/en-x-testmini.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Language/messages/en-x-testmini.php
diff --git a/library/HTMLPurifier/Language/messages/en.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Language/messages/en.php
index c7f197e1e..c7f197e1e 100644
--- a/library/HTMLPurifier/Language/messages/en.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Language/messages/en.php
diff --git a/library/HTMLPurifier/LanguageFactory.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/LanguageFactory.php
index 4e35272d8..4e35272d8 100644
--- a/library/HTMLPurifier/LanguageFactory.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/LanguageFactory.php
diff --git a/library/HTMLPurifier/Length.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Length.php
index bbfbe6624..bbfbe6624 100644
--- a/library/HTMLPurifier/Length.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Length.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Lexer.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Lexer.php
new file mode 100644
index 000000000..e9da3ed5e
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Lexer.php
@@ -0,0 +1,382 @@
+<?php
+
+/**
+ * Forgivingly lexes HTML (SGML-style) markup into tokens.
+ *
+ * A lexer parses a string of SGML-style markup and converts them into
+ * corresponding tokens. It doesn't check for well-formedness, although its
+ * internal mechanism may make this automatic (such as the case of
+ * HTMLPurifier_Lexer_DOMLex). There are several implementations to choose
+ * from.
+ *
+ * A lexer is HTML-oriented: it might work with XML, but it's not
+ * recommended, as we adhere to a subset of the specification for optimization
+ * reasons. This might change in the future. Also, most tokenizers are not
+ * expected to handle DTDs or PIs.
+ *
+ * This class should not be directly instantiated, but you may use create() to
+ * retrieve a default copy of the lexer. Being a supertype, this class
+ * does not actually define any implementation, but offers commonly used
+ * convenience functions for subclasses.
+ *
+ * @note The unit tests will instantiate this class for testing purposes, as
+ * many of the utility functions require a class to be instantiated.
+ * This means that, even though this class is not runnable, it will
+ * not be declared abstract.
+ *
+ * @par
+ *
+ * @note
+ * We use tokens rather than create a DOM representation because DOM would:
+ *
+ * @par
+ * -# Require more processing and memory to create,
+ * -# Is not streamable, and
+ * -# Has the entire document structure (html and body not needed).
+ *
+ * @par
+ * However, DOM is helpful in that it makes it easy to move around nodes
+ * without a lot of lookaheads to see when a tag is closed. This is a
+ * limitation of the token system and some workarounds would be nice.
+ */
+class HTMLPurifier_Lexer
+{
+
+ /**
+ * Whether or not this lexer implements line-number/column-number tracking.
+ * If it does, set to true.
+ */
+ public $tracksLineNumbers = false;
+
+ // -- STATIC ----------------------------------------------------------
+
+ /**
+ * Retrieves or sets the default Lexer as a Prototype Factory.
+ *
+ * By default HTMLPurifier_Lexer_DOMLex will be returned. There are
+ * a few exceptions involving special features that only DirectLex
+ * implements.
+ *
+ * @note The behavior of this class has changed, rather than accepting
+ * a prototype object, it now accepts a configuration object.
+ * To specify your own prototype, set %Core.LexerImpl to it.
+ * This change in behavior de-singletonizes the lexer object.
+ *
+ * @param HTMLPurifier_Config $config
+ * @return HTMLPurifier_Lexer
+ * @throws HTMLPurifier_Exception
+ */
+ public static function create($config)
+ {
+ if (!($config instanceof HTMLPurifier_Config)) {
+ $lexer = $config;
+ trigger_error(
+ "Passing a prototype to
+ HTMLPurifier_Lexer::create() is deprecated, please instead
+ use %Core.LexerImpl",
+ E_USER_WARNING
+ );
+ } else {
+ $lexer = $config->get('Core.LexerImpl');
+ }
+
+ $needs_tracking =
+ $config->get('Core.MaintainLineNumbers') ||
+ $config->get('Core.CollectErrors');
+
+ $inst = null;
+ if (is_object($lexer)) {
+ $inst = $lexer;
+ } else {
+ if (is_null($lexer)) {
+ do {
+ // auto-detection algorithm
+ if ($needs_tracking) {
+ $lexer = 'DirectLex';
+ break;
+ }
+
+ if (class_exists('DOMDocument', false) &&
+ method_exists('DOMDocument', 'loadHTML') &&
+ !extension_loaded('domxml')
+ ) {
+ // check for DOM support, because while it's part of the
+ // core, it can be disabled compile time. Also, the PECL
+ // domxml extension overrides the default DOM, and is evil
+ // and nasty and we shan't bother to support it
+ $lexer = 'DOMLex';
+ } else {
+ $lexer = 'DirectLex';
+ }
+ } while (0);
+ } // do..while so we can break
+
+ // instantiate recognized string names
+ switch ($lexer) {
+ case 'DOMLex':
+ $inst = new HTMLPurifier_Lexer_DOMLex();
+ break;
+ case 'DirectLex':
+ $inst = new HTMLPurifier_Lexer_DirectLex();
+ break;
+ case 'PH5P':
+ $inst = new HTMLPurifier_Lexer_PH5P();
+ break;
+ default:
+ throw new HTMLPurifier_Exception(
+ "Cannot instantiate unrecognized Lexer type " .
+ htmlspecialchars($lexer)
+ );
+ }
+ }
+
+ if (!$inst) {
+ throw new HTMLPurifier_Exception('No lexer was instantiated');
+ }
+
+ // once PHP DOM implements native line numbers, or we
+ // hack out something using XSLT, remove this stipulation
+ if ($needs_tracking && !$inst->tracksLineNumbers) {
+ throw new HTMLPurifier_Exception(
+ 'Cannot use lexer that does not support line numbers with ' .
+ 'Core.MaintainLineNumbers or Core.CollectErrors (use DirectLex instead)'
+ );
+ }
+
+ return $inst;
+
+ }
+
+ // -- CONVENIENCE MEMBERS ---------------------------------------------
+
+ public function __construct()
+ {
+ $this->_entity_parser = new HTMLPurifier_EntityParser();
+ }
+
+ /**
+ * Most common entity to raw value conversion table for special entities.
+ * @type array
+ */
+ protected $_special_entity2str =
+ array(
+ '&quot;' => '"',
+ '&amp;' => '&',
+ '&lt;' => '<',
+ '&gt;' => '>',
+ '&#39;' => "'",
+ '&#039;' => "'",
+ '&#x27;' => "'"
+ );
+
+ public function parseText($string, $config) {
+ return $this->parseData($string, false, $config);
+ }
+
+ public function parseAttr($string, $config) {
+ return $this->parseData($string, true, $config);
+ }
+
+ /**
+ * Parses special entities into the proper characters.
+ *
+ * This string will translate escaped versions of the special characters
+ * into the correct ones.
+ *
+ * @param string $string String character data to be parsed.
+ * @return string Parsed character data.
+ */
+ public function parseData($string, $is_attr, $config)
+ {
+ // following functions require at least one character
+ if ($string === '') {
+ return '';
+ }
+
+ // subtracts amps that cannot possibly be escaped
+ $num_amp = substr_count($string, '&') - substr_count($string, '& ') -
+ ($string[strlen($string) - 1] === '&' ? 1 : 0);
+
+ if (!$num_amp) {
+ return $string;
+ } // abort if no entities
+ $num_esc_amp = substr_count($string, '&amp;');
+ $string = strtr($string, $this->_special_entity2str);
+
+ // code duplication for sake of optimization, see above
+ $num_amp_2 = substr_count($string, '&') - substr_count($string, '& ') -
+ ($string[strlen($string) - 1] === '&' ? 1 : 0);
+
+ if ($num_amp_2 <= $num_esc_amp) {
+ return $string;
+ }
+
+ // hmm... now we have some uncommon entities. Use the callback.
+ if ($config->get('Core.LegacyEntityDecoder')) {
+ $string = $this->_entity_parser->substituteSpecialEntities($string);
+ } else {
+ if ($is_attr) {
+ $string = $this->_entity_parser->substituteAttrEntities($string);
+ } else {
+ $string = $this->_entity_parser->substituteTextEntities($string);
+ }
+ }
+ return $string;
+ }
+
+ /**
+ * Lexes an HTML string into tokens.
+ * @param $string String HTML.
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return HTMLPurifier_Token[] array representation of HTML.
+ */
+ public function tokenizeHTML($string, $config, $context)
+ {
+ trigger_error('Call to abstract class', E_USER_ERROR);
+ }
+
+ /**
+ * Translates CDATA sections into regular sections (through escaping).
+ * @param string $string HTML string to process.
+ * @return string HTML with CDATA sections escaped.
+ */
+ protected static function escapeCDATA($string)
+ {
+ return preg_replace_callback(
+ '/<!\[CDATA\[(.+?)\]\]>/s',
+ array('HTMLPurifier_Lexer', 'CDATACallback'),
+ $string
+ );
+ }
+
+ /**
+ * Special CDATA case that is especially convoluted for <script>
+ * @param string $string HTML string to process.
+ * @return string HTML with CDATA sections escaped.
+ */
+ protected static function escapeCommentedCDATA($string)
+ {
+ return preg_replace_callback(
+ '#<!--//--><!\[CDATA\[//><!--(.+?)//--><!\]\]>#s',
+ array('HTMLPurifier_Lexer', 'CDATACallback'),
+ $string
+ );
+ }
+
+ /**
+ * Special Internet Explorer conditional comments should be removed.
+ * @param string $string HTML string to process.
+ * @return string HTML with conditional comments removed.
+ */
+ protected static function removeIEConditional($string)
+ {
+ return preg_replace(
+ '#<!--\[if [^>]+\]>.*?<!\[endif\]-->#si', // probably should generalize for all strings
+ '',
+ $string
+ );
+ }
+
+ /**
+ * Callback function for escapeCDATA() that does the work.
+ *
+ * @warning Though this is public in order to let the callback happen,
+ * calling it directly is not recommended.
+ * @param array $matches PCRE matches array, with index 0 the entire match
+ * and 1 the inside of the CDATA section.
+ * @return string Escaped internals of the CDATA section.
+ */
+ protected static function CDATACallback($matches)
+ {
+ // not exactly sure why the character set is needed, but whatever
+ return htmlspecialchars($matches[1], ENT_COMPAT, 'UTF-8');
+ }
+
+ /**
+ * Takes a piece of HTML and normalizes it by converting entities, fixing
+ * encoding, extracting bits, and other good stuff.
+ * @param string $html HTML.
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return string
+ * @todo Consider making protected
+ */
+ public function normalize($html, $config, $context)
+ {
+ // normalize newlines to \n
+ if ($config->get('Core.NormalizeNewlines')) {
+ $html = str_replace("\r\n", "\n", $html);
+ $html = str_replace("\r", "\n", $html);
+ }
+
+ if ($config->get('HTML.Trusted')) {
+ // escape convoluted CDATA
+ $html = $this->escapeCommentedCDATA($html);
+ }
+
+ // escape CDATA
+ $html = $this->escapeCDATA($html);
+
+ $html = $this->removeIEConditional($html);
+
+ // extract body from document if applicable
+ if ($config->get('Core.ConvertDocumentToFragment')) {
+ $e = false;
+ if ($config->get('Core.CollectErrors')) {
+ $e =& $context->get('ErrorCollector');
+ }
+ $new_html = $this->extractBody($html);
+ if ($e && $new_html != $html) {
+ $e->send(E_WARNING, 'Lexer: Extracted body');
+ }
+ $html = $new_html;
+ }
+
+ // expand entities that aren't the big five
+ if ($config->get('Core.LegacyEntityDecoder')) {
+ $html = $this->_entity_parser->substituteNonSpecialEntities($html);
+ }
+
+ // clean into wellformed UTF-8 string for an SGML context: this has
+ // to be done after entity expansion because the entities sometimes
+ // represent non-SGML characters (horror, horror!)
+ $html = HTMLPurifier_Encoder::cleanUTF8($html);
+
+ // if processing instructions are to removed, remove them now
+ if ($config->get('Core.RemoveProcessingInstructions')) {
+ $html = preg_replace('#<\?.+?\?>#s', '', $html);
+ }
+
+ $hidden_elements = $config->get('Core.HiddenElements');
+ if ($config->get('Core.AggressivelyRemoveScript') &&
+ !($config->get('HTML.Trusted') || !$config->get('Core.RemoveScriptContents')
+ || empty($hidden_elements["script"]))) {
+ $html = preg_replace('#<script[^>]*>.*?</script>#i', '', $html);
+ }
+
+ return $html;
+ }
+
+ /**
+ * Takes a string of HTML (fragment or document) and returns the content
+ * @todo Consider making protected
+ */
+ public function extractBody($html)
+ {
+ $matches = array();
+ $result = preg_match('|(.*?)<body[^>]*>(.*)</body>|is', $html, $matches);
+ if ($result) {
+ // Make sure it's not in a comment
+ $comment_start = strrpos($matches[1], '<!--');
+ $comment_end = strrpos($matches[1], '-->');
+ if ($comment_start === false ||
+ ($comment_end !== false && $comment_end > $comment_start)) {
+ return $matches[2];
+ }
+ }
+ return $html;
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Lexer/DOMLex.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Lexer/DOMLex.php
new file mode 100644
index 000000000..22ab5820c
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Lexer/DOMLex.php
@@ -0,0 +1,291 @@
+<?php
+
+/**
+ * Parser that uses PHP 5's DOM extension (part of the core).
+ *
+ * In PHP 5, the DOM XML extension was revamped into DOM and added to the core.
+ * It gives us a forgiving HTML parser, which we use to transform the HTML
+ * into a DOM, and then into the tokens. It is blazingly fast (for large
+ * documents, it performs twenty times faster than
+ * HTMLPurifier_Lexer_DirectLex,and is the default choice for PHP 5.
+ *
+ * @note Any empty elements will have empty tokens associated with them, even if
+ * this is prohibited by the spec. This is cannot be fixed until the spec
+ * comes into play.
+ *
+ * @note PHP's DOM extension does not actually parse any entities, we use
+ * our own function to do that.
+ *
+ * @warning DOM tends to drop whitespace, which may wreak havoc on indenting.
+ * If this is a huge problem, due to the fact that HTML is hand
+ * edited and you are unable to get a parser cache that caches the
+ * the output of HTML Purifier while keeping the original HTML lying
+ * around, you may want to run Tidy on the resulting output or use
+ * HTMLPurifier_DirectLex
+ */
+
+class HTMLPurifier_Lexer_DOMLex extends HTMLPurifier_Lexer
+{
+
+ /**
+ * @type HTMLPurifier_TokenFactory
+ */
+ private $factory;
+
+ public function __construct()
+ {
+ // setup the factory
+ parent::__construct();
+ $this->factory = new HTMLPurifier_TokenFactory();
+ }
+
+ /**
+ * @param string $html
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return HTMLPurifier_Token[]
+ */
+ public function tokenizeHTML($html, $config, $context)
+ {
+ $html = $this->normalize($html, $config, $context);
+
+ // attempt to armor stray angled brackets that cannot possibly
+ // form tags and thus are probably being used as emoticons
+ if ($config->get('Core.AggressivelyFixLt')) {
+ $char = '[^a-z!\/]';
+ $comment = "/<!--(.*?)(-->|\z)/is";
+ $html = preg_replace_callback($comment, array($this, 'callbackArmorCommentEntities'), $html);
+ do {
+ $old = $html;
+ $html = preg_replace("/<($char)/i", '&lt;\\1', $html);
+ } while ($html !== $old);
+ $html = preg_replace_callback($comment, array($this, 'callbackUndoCommentSubst'), $html); // fix comments
+ }
+
+ // preprocess html, essential for UTF-8
+ $html = $this->wrapHTML($html, $config, $context);
+
+ $doc = new DOMDocument();
+ $doc->encoding = 'UTF-8'; // theoretically, the above has this covered
+
+ set_error_handler(array($this, 'muteErrorHandler'));
+ $doc->loadHTML($html);
+ restore_error_handler();
+
+ $body = $doc->getElementsByTagName('html')->item(0)-> // <html>
+ getElementsByTagName('body')->item(0); // <body>
+
+ $div = $body->getElementsByTagName('div')->item(0); // <div>
+ $tokens = array();
+ $this->tokenizeDOM($div, $tokens, $config);
+ // If the div has a sibling, that means we tripped across
+ // a premature </div> tag. So remove the div we parsed,
+ // and then tokenize the rest of body. We can't tokenize
+ // the sibling directly as we'll lose the tags in that case.
+ if ($div->nextSibling) {
+ $body->removeChild($div);
+ $this->tokenizeDOM($body, $tokens, $config);
+ }
+ return $tokens;
+ }
+
+ /**
+ * Iterative function that tokenizes a node, putting it into an accumulator.
+ * To iterate is human, to recurse divine - L. Peter Deutsch
+ * @param DOMNode $node DOMNode to be tokenized.
+ * @param HTMLPurifier_Token[] $tokens Array-list of already tokenized tokens.
+ * @return HTMLPurifier_Token of node appended to previously passed tokens.
+ */
+ protected function tokenizeDOM($node, &$tokens, $config)
+ {
+ $level = 0;
+ $nodes = array($level => new HTMLPurifier_Queue(array($node)));
+ $closingNodes = array();
+ do {
+ while (!$nodes[$level]->isEmpty()) {
+ $node = $nodes[$level]->shift(); // FIFO
+ $collect = $level > 0 ? true : false;
+ $needEndingTag = $this->createStartNode($node, $tokens, $collect, $config);
+ if ($needEndingTag) {
+ $closingNodes[$level][] = $node;
+ }
+ if ($node->childNodes && $node->childNodes->length) {
+ $level++;
+ $nodes[$level] = new HTMLPurifier_Queue();
+ foreach ($node->childNodes as $childNode) {
+ $nodes[$level]->push($childNode);
+ }
+ }
+ }
+ $level--;
+ if ($level && isset($closingNodes[$level])) {
+ while ($node = array_pop($closingNodes[$level])) {
+ $this->createEndNode($node, $tokens);
+ }
+ }
+ } while ($level > 0);
+ }
+
+ /**
+ * @param DOMNode $node DOMNode to be tokenized.
+ * @param HTMLPurifier_Token[] $tokens Array-list of already tokenized tokens.
+ * @param bool $collect Says whether or start and close are collected, set to
+ * false at first recursion because it's the implicit DIV
+ * tag you're dealing with.
+ * @return bool if the token needs an endtoken
+ * @todo data and tagName properties don't seem to exist in DOMNode?
+ */
+ protected function createStartNode($node, &$tokens, $collect, $config)
+ {
+ // intercept non element nodes. WE MUST catch all of them,
+ // but we're not getting the character reference nodes because
+ // those should have been preprocessed
+ if ($node->nodeType === XML_TEXT_NODE) {
+ $tokens[] = $this->factory->createText($node->data);
+ return false;
+ } elseif ($node->nodeType === XML_CDATA_SECTION_NODE) {
+ // undo libxml's special treatment of <script> and <style> tags
+ $last = end($tokens);
+ $data = $node->data;
+ // (note $node->tagname is already normalized)
+ if ($last instanceof HTMLPurifier_Token_Start && ($last->name == 'script' || $last->name == 'style')) {
+ $new_data = trim($data);
+ if (substr($new_data, 0, 4) === '<!--') {
+ $data = substr($new_data, 4);
+ if (substr($data, -3) === '-->') {
+ $data = substr($data, 0, -3);
+ } else {
+ // Highly suspicious! Not sure what to do...
+ }
+ }
+ }
+ $tokens[] = $this->factory->createText($this->parseText($data, $config));
+ return false;
+ } elseif ($node->nodeType === XML_COMMENT_NODE) {
+ // this is code is only invoked for comments in script/style in versions
+ // of libxml pre-2.6.28 (regular comments, of course, are still
+ // handled regularly)
+ $tokens[] = $this->factory->createComment($node->data);
+ return false;
+ } elseif ($node->nodeType !== XML_ELEMENT_NODE) {
+ // not-well tested: there may be other nodes we have to grab
+ return false;
+ }
+
+ $attr = $node->hasAttributes() ? $this->transformAttrToAssoc($node->attributes) : array();
+
+ // We still have to make sure that the element actually IS empty
+ if (!$node->childNodes->length) {
+ if ($collect) {
+ $tokens[] = $this->factory->createEmpty($node->tagName, $attr);
+ }
+ return false;
+ } else {
+ if ($collect) {
+ $tokens[] = $this->factory->createStart(
+ $tag_name = $node->tagName, // somehow, it get's dropped
+ $attr
+ );
+ }
+ return true;
+ }
+ }
+
+ /**
+ * @param DOMNode $node
+ * @param HTMLPurifier_Token[] $tokens
+ */
+ protected function createEndNode($node, &$tokens)
+ {
+ $tokens[] = $this->factory->createEnd($node->tagName);
+ }
+
+
+ /**
+ * Converts a DOMNamedNodeMap of DOMAttr objects into an assoc array.
+ *
+ * @param DOMNamedNodeMap $node_map DOMNamedNodeMap of DOMAttr objects.
+ * @return array Associative array of attributes.
+ */
+ protected function transformAttrToAssoc($node_map)
+ {
+ // NamedNodeMap is documented very well, so we're using undocumented
+ // features, namely, the fact that it implements Iterator and
+ // has a ->length attribute
+ if ($node_map->length === 0) {
+ return array();
+ }
+ $array = array();
+ foreach ($node_map as $attr) {
+ $array[$attr->name] = $attr->value;
+ }
+ return $array;
+ }
+
+ /**
+ * An error handler that mutes all errors
+ * @param int $errno
+ * @param string $errstr
+ */
+ public function muteErrorHandler($errno, $errstr)
+ {
+ }
+
+ /**
+ * Callback function for undoing escaping of stray angled brackets
+ * in comments
+ * @param array $matches
+ * @return string
+ */
+ public function callbackUndoCommentSubst($matches)
+ {
+ return '<!--' . strtr($matches[1], array('&amp;' => '&', '&lt;' => '<')) . $matches[2];
+ }
+
+ /**
+ * Callback function that entity-izes ampersands in comments so that
+ * callbackUndoCommentSubst doesn't clobber them
+ * @param array $matches
+ * @return string
+ */
+ public function callbackArmorCommentEntities($matches)
+ {
+ return '<!--' . str_replace('&', '&amp;', $matches[1]) . $matches[2];
+ }
+
+ /**
+ * Wraps an HTML fragment in the necessary HTML
+ * @param string $html
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return string
+ */
+ protected function wrapHTML($html, $config, $context, $use_div = true)
+ {
+ $def = $config->getDefinition('HTML');
+ $ret = '';
+
+ if (!empty($def->doctype->dtdPublic) || !empty($def->doctype->dtdSystem)) {
+ $ret .= '<!DOCTYPE html ';
+ if (!empty($def->doctype->dtdPublic)) {
+ $ret .= 'PUBLIC "' . $def->doctype->dtdPublic . '" ';
+ }
+ if (!empty($def->doctype->dtdSystem)) {
+ $ret .= '"' . $def->doctype->dtdSystem . '" ';
+ }
+ $ret .= '>';
+ }
+
+ $ret .= '<html><head>';
+ $ret .= '<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />';
+ // No protection if $html contains a stray </div>!
+ $ret .= '</head><body>';
+ if ($use_div) $ret .= '<div>';
+ $ret .= $html;
+ if ($use_div) $ret .= '</div>';
+ $ret .= '</body></html>';
+ return $ret;
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Lexer/DirectLex.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Lexer/DirectLex.php
new file mode 100644
index 000000000..6f1308966
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Lexer/DirectLex.php
@@ -0,0 +1,539 @@
+<?php
+
+/**
+ * Our in-house implementation of a parser.
+ *
+ * A pure PHP parser, DirectLex has absolutely no dependencies, making
+ * it a reasonably good default for PHP4. Written with efficiency in mind,
+ * it can be four times faster than HTMLPurifier_Lexer_PEARSax3, although it
+ * pales in comparison to HTMLPurifier_Lexer_DOMLex.
+ *
+ * @todo Reread XML spec and document differences.
+ */
+class HTMLPurifier_Lexer_DirectLex extends HTMLPurifier_Lexer
+{
+ /**
+ * @type bool
+ */
+ public $tracksLineNumbers = true;
+
+ /**
+ * Whitespace characters for str(c)spn.
+ * @type string
+ */
+ protected $_whitespace = "\x20\x09\x0D\x0A";
+
+ /**
+ * Callback function for script CDATA fudge
+ * @param array $matches, in form of array(opening tag, contents, closing tag)
+ * @return string
+ */
+ protected function scriptCallback($matches)
+ {
+ return $matches[1] . htmlspecialchars($matches[2], ENT_COMPAT, 'UTF-8') . $matches[3];
+ }
+
+ /**
+ * @param String $html
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return array|HTMLPurifier_Token[]
+ */
+ public function tokenizeHTML($html, $config, $context)
+ {
+ // special normalization for script tags without any armor
+ // our "armor" heurstic is a < sign any number of whitespaces after
+ // the first script tag
+ if ($config->get('HTML.Trusted')) {
+ $html = preg_replace_callback(
+ '#(<script[^>]*>)(\s*[^<].+?)(</script>)#si',
+ array($this, 'scriptCallback'),
+ $html
+ );
+ }
+
+ $html = $this->normalize($html, $config, $context);
+
+ $cursor = 0; // our location in the text
+ $inside_tag = false; // whether or not we're parsing the inside of a tag
+ $array = array(); // result array
+
+ // This is also treated to mean maintain *column* numbers too
+ $maintain_line_numbers = $config->get('Core.MaintainLineNumbers');
+
+ if ($maintain_line_numbers === null) {
+ // automatically determine line numbering by checking
+ // if error collection is on
+ $maintain_line_numbers = $config->get('Core.CollectErrors');
+ }
+
+ if ($maintain_line_numbers) {
+ $current_line = 1;
+ $current_col = 0;
+ $length = strlen($html);
+ } else {
+ $current_line = false;
+ $current_col = false;
+ $length = false;
+ }
+ $context->register('CurrentLine', $current_line);
+ $context->register('CurrentCol', $current_col);
+ $nl = "\n";
+ // how often to manually recalculate. This will ALWAYS be right,
+ // but it's pretty wasteful. Set to 0 to turn off
+ $synchronize_interval = $config->get('Core.DirectLexLineNumberSyncInterval');
+
+ $e = false;
+ if ($config->get('Core.CollectErrors')) {
+ $e =& $context->get('ErrorCollector');
+ }
+
+ // for testing synchronization
+ $loops = 0;
+
+ while (++$loops) {
+ // $cursor is either at the start of a token, or inside of
+ // a tag (i.e. there was a < immediately before it), as indicated
+ // by $inside_tag
+
+ if ($maintain_line_numbers) {
+ // $rcursor, however, is always at the start of a token.
+ $rcursor = $cursor - (int)$inside_tag;
+
+ // Column number is cheap, so we calculate it every round.
+ // We're interested at the *end* of the newline string, so
+ // we need to add strlen($nl) == 1 to $nl_pos before subtracting it
+ // from our "rcursor" position.
+ $nl_pos = strrpos($html, $nl, $rcursor - $length);
+ $current_col = $rcursor - (is_bool($nl_pos) ? 0 : $nl_pos + 1);
+
+ // recalculate lines
+ if ($synchronize_interval && // synchronization is on
+ $cursor > 0 && // cursor is further than zero
+ $loops % $synchronize_interval === 0) { // time to synchronize!
+ $current_line = 1 + $this->substrCount($html, $nl, 0, $cursor);
+ }
+ }
+
+ $position_next_lt = strpos($html, '<', $cursor);
+ $position_next_gt = strpos($html, '>', $cursor);
+
+ // triggers on "<b>asdf</b>" but not "asdf <b></b>"
+ // special case to set up context
+ if ($position_next_lt === $cursor) {
+ $inside_tag = true;
+ $cursor++;
+ }
+
+ if (!$inside_tag && $position_next_lt !== false) {
+ // We are not inside tag and there still is another tag to parse
+ $token = new
+ HTMLPurifier_Token_Text(
+ $this->parseText(
+ substr(
+ $html,
+ $cursor,
+ $position_next_lt - $cursor
+ ), $config
+ )
+ );
+ if ($maintain_line_numbers) {
+ $token->rawPosition($current_line, $current_col);
+ $current_line += $this->substrCount($html, $nl, $cursor, $position_next_lt - $cursor);
+ }
+ $array[] = $token;
+ $cursor = $position_next_lt + 1;
+ $inside_tag = true;
+ continue;
+ } elseif (!$inside_tag) {
+ // We are not inside tag but there are no more tags
+ // If we're already at the end, break
+ if ($cursor === strlen($html)) {
+ break;
+ }
+ // Create Text of rest of string
+ $token = new
+ HTMLPurifier_Token_Text(
+ $this->parseText(
+ substr(
+ $html,
+ $cursor
+ ), $config
+ )
+ );
+ if ($maintain_line_numbers) {
+ $token->rawPosition($current_line, $current_col);
+ }
+ $array[] = $token;
+ break;
+ } elseif ($inside_tag && $position_next_gt !== false) {
+ // We are in tag and it is well formed
+ // Grab the internals of the tag
+ $strlen_segment = $position_next_gt - $cursor;
+
+ if ($strlen_segment < 1) {
+ // there's nothing to process!
+ $token = new HTMLPurifier_Token_Text('<');
+ $cursor++;
+ continue;
+ }
+
+ $segment = substr($html, $cursor, $strlen_segment);
+
+ if ($segment === false) {
+ // somehow, we attempted to access beyond the end of
+ // the string, defense-in-depth, reported by Nate Abele
+ break;
+ }
+
+ // Check if it's a comment
+ if (substr($segment, 0, 3) === '!--') {
+ // re-determine segment length, looking for -->
+ $position_comment_end = strpos($html, '-->', $cursor);
+ if ($position_comment_end === false) {
+ // uh oh, we have a comment that extends to
+ // infinity. Can't be helped: set comment
+ // end position to end of string
+ if ($e) {
+ $e->send(E_WARNING, 'Lexer: Unclosed comment');
+ }
+ $position_comment_end = strlen($html);
+ $end = true;
+ } else {
+ $end = false;
+ }
+ $strlen_segment = $position_comment_end - $cursor;
+ $segment = substr($html, $cursor, $strlen_segment);
+ $token = new
+ HTMLPurifier_Token_Comment(
+ substr(
+ $segment,
+ 3,
+ $strlen_segment - 3
+ )
+ );
+ if ($maintain_line_numbers) {
+ $token->rawPosition($current_line, $current_col);
+ $current_line += $this->substrCount($html, $nl, $cursor, $strlen_segment);
+ }
+ $array[] = $token;
+ $cursor = $end ? $position_comment_end : $position_comment_end + 3;
+ $inside_tag = false;
+ continue;
+ }
+
+ // Check if it's an end tag
+ $is_end_tag = (strpos($segment, '/') === 0);
+ if ($is_end_tag) {
+ $type = substr($segment, 1);
+ $token = new HTMLPurifier_Token_End($type);
+ if ($maintain_line_numbers) {
+ $token->rawPosition($current_line, $current_col);
+ $current_line += $this->substrCount($html, $nl, $cursor, $position_next_gt - $cursor);
+ }
+ $array[] = $token;
+ $inside_tag = false;
+ $cursor = $position_next_gt + 1;
+ continue;
+ }
+
+ // Check leading character is alnum, if not, we may
+ // have accidently grabbed an emoticon. Translate into
+ // text and go our merry way
+ if (!ctype_alpha($segment[0])) {
+ // XML: $segment[0] !== '_' && $segment[0] !== ':'
+ if ($e) {
+ $e->send(E_NOTICE, 'Lexer: Unescaped lt');
+ }
+ $token = new HTMLPurifier_Token_Text('<');
+ if ($maintain_line_numbers) {
+ $token->rawPosition($current_line, $current_col);
+ $current_line += $this->substrCount($html, $nl, $cursor, $position_next_gt - $cursor);
+ }
+ $array[] = $token;
+ $inside_tag = false;
+ continue;
+ }
+
+ // Check if it is explicitly self closing, if so, remove
+ // trailing slash. Remember, we could have a tag like <br>, so
+ // any later token processing scripts must convert improperly
+ // classified EmptyTags from StartTags.
+ $is_self_closing = (strrpos($segment, '/') === $strlen_segment - 1);
+ if ($is_self_closing) {
+ $strlen_segment--;
+ $segment = substr($segment, 0, $strlen_segment);
+ }
+
+ // Check if there are any attributes
+ $position_first_space = strcspn($segment, $this->_whitespace);
+
+ if ($position_first_space >= $strlen_segment) {
+ if ($is_self_closing) {
+ $token = new HTMLPurifier_Token_Empty($segment);
+ } else {
+ $token = new HTMLPurifier_Token_Start($segment);
+ }
+ if ($maintain_line_numbers) {
+ $token->rawPosition($current_line, $current_col);
+ $current_line += $this->substrCount($html, $nl, $cursor, $position_next_gt - $cursor);
+ }
+ $array[] = $token;
+ $inside_tag = false;
+ $cursor = $position_next_gt + 1;
+ continue;
+ }
+
+ // Grab out all the data
+ $type = substr($segment, 0, $position_first_space);
+ $attribute_string =
+ trim(
+ substr(
+ $segment,
+ $position_first_space
+ )
+ );
+ if ($attribute_string) {
+ $attr = $this->parseAttributeString(
+ $attribute_string,
+ $config,
+ $context
+ );
+ } else {
+ $attr = array();
+ }
+
+ if ($is_self_closing) {
+ $token = new HTMLPurifier_Token_Empty($type, $attr);
+ } else {
+ $token = new HTMLPurifier_Token_Start($type, $attr);
+ }
+ if ($maintain_line_numbers) {
+ $token->rawPosition($current_line, $current_col);
+ $current_line += $this->substrCount($html, $nl, $cursor, $position_next_gt - $cursor);
+ }
+ $array[] = $token;
+ $cursor = $position_next_gt + 1;
+ $inside_tag = false;
+ continue;
+ } else {
+ // inside tag, but there's no ending > sign
+ if ($e) {
+ $e->send(E_WARNING, 'Lexer: Missing gt');
+ }
+ $token = new
+ HTMLPurifier_Token_Text(
+ '<' .
+ $this->parseText(
+ substr($html, $cursor), $config
+ )
+ );
+ if ($maintain_line_numbers) {
+ $token->rawPosition($current_line, $current_col);
+ }
+ // no cursor scroll? Hmm...
+ $array[] = $token;
+ break;
+ }
+ break;
+ }
+
+ $context->destroy('CurrentLine');
+ $context->destroy('CurrentCol');
+ return $array;
+ }
+
+ /**
+ * PHP 5.0.x compatible substr_count that implements offset and length
+ * @param string $haystack
+ * @param string $needle
+ * @param int $offset
+ * @param int $length
+ * @return int
+ */
+ protected function substrCount($haystack, $needle, $offset, $length)
+ {
+ static $oldVersion;
+ if ($oldVersion === null) {
+ $oldVersion = version_compare(PHP_VERSION, '5.1', '<');
+ }
+ if ($oldVersion) {
+ $haystack = substr($haystack, $offset, $length);
+ return substr_count($haystack, $needle);
+ } else {
+ return substr_count($haystack, $needle, $offset, $length);
+ }
+ }
+
+ /**
+ * Takes the inside of an HTML tag and makes an assoc array of attributes.
+ *
+ * @param string $string Inside of tag excluding name.
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return array Assoc array of attributes.
+ */
+ public function parseAttributeString($string, $config, $context)
+ {
+ $string = (string)$string; // quick typecast
+
+ if ($string == '') {
+ return array();
+ } // no attributes
+
+ $e = false;
+ if ($config->get('Core.CollectErrors')) {
+ $e =& $context->get('ErrorCollector');
+ }
+
+ // let's see if we can abort as quickly as possible
+ // one equal sign, no spaces => one attribute
+ $num_equal = substr_count($string, '=');
+ $has_space = strpos($string, ' ');
+ if ($num_equal === 0 && !$has_space) {
+ // bool attribute
+ return array($string => $string);
+ } elseif ($num_equal === 1 && !$has_space) {
+ // only one attribute
+ list($key, $quoted_value) = explode('=', $string);
+ $quoted_value = trim($quoted_value);
+ if (!$key) {
+ if ($e) {
+ $e->send(E_ERROR, 'Lexer: Missing attribute key');
+ }
+ return array();
+ }
+ if (!$quoted_value) {
+ return array($key => '');
+ }
+ $first_char = @$quoted_value[0];
+ $last_char = @$quoted_value[strlen($quoted_value) - 1];
+
+ $same_quote = ($first_char == $last_char);
+ $open_quote = ($first_char == '"' || $first_char == "'");
+
+ if ($same_quote && $open_quote) {
+ // well behaved
+ $value = substr($quoted_value, 1, strlen($quoted_value) - 2);
+ } else {
+ // not well behaved
+ if ($open_quote) {
+ if ($e) {
+ $e->send(E_ERROR, 'Lexer: Missing end quote');
+ }
+ $value = substr($quoted_value, 1);
+ } else {
+ $value = $quoted_value;
+ }
+ }
+ if ($value === false) {
+ $value = '';
+ }
+ return array($key => $this->parseAttr($value, $config));
+ }
+
+ // setup loop environment
+ $array = array(); // return assoc array of attributes
+ $cursor = 0; // current position in string (moves forward)
+ $size = strlen($string); // size of the string (stays the same)
+
+ // if we have unquoted attributes, the parser expects a terminating
+ // space, so let's guarantee that there's always a terminating space.
+ $string .= ' ';
+
+ $old_cursor = -1;
+ while ($cursor < $size) {
+ if ($old_cursor >= $cursor) {
+ throw new Exception("Infinite loop detected");
+ }
+ $old_cursor = $cursor;
+
+ $cursor += ($value = strspn($string, $this->_whitespace, $cursor));
+ // grab the key
+
+ $key_begin = $cursor; //we're currently at the start of the key
+
+ // scroll past all characters that are the key (not whitespace or =)
+ $cursor += strcspn($string, $this->_whitespace . '=', $cursor);
+
+ $key_end = $cursor; // now at the end of the key
+
+ $key = substr($string, $key_begin, $key_end - $key_begin);
+
+ if (!$key) {
+ if ($e) {
+ $e->send(E_ERROR, 'Lexer: Missing attribute key');
+ }
+ $cursor += 1 + strcspn($string, $this->_whitespace, $cursor + 1); // prevent infinite loop
+ continue; // empty key
+ }
+
+ // scroll past all whitespace
+ $cursor += strspn($string, $this->_whitespace, $cursor);
+
+ if ($cursor >= $size) {
+ $array[$key] = $key;
+ break;
+ }
+
+ // if the next character is an equal sign, we've got a regular
+ // pair, otherwise, it's a bool attribute
+ $first_char = @$string[$cursor];
+
+ if ($first_char == '=') {
+ // key="value"
+
+ $cursor++;
+ $cursor += strspn($string, $this->_whitespace, $cursor);
+
+ if ($cursor === false) {
+ $array[$key] = '';
+ break;
+ }
+
+ // we might be in front of a quote right now
+
+ $char = @$string[$cursor];
+
+ if ($char == '"' || $char == "'") {
+ // it's quoted, end bound is $char
+ $cursor++;
+ $value_begin = $cursor;
+ $cursor = strpos($string, $char, $cursor);
+ $value_end = $cursor;
+ } else {
+ // it's not quoted, end bound is whitespace
+ $value_begin = $cursor;
+ $cursor += strcspn($string, $this->_whitespace, $cursor);
+ $value_end = $cursor;
+ }
+
+ // we reached a premature end
+ if ($cursor === false) {
+ $cursor = $size;
+ $value_end = $cursor;
+ }
+
+ $value = substr($string, $value_begin, $value_end - $value_begin);
+ if ($value === false) {
+ $value = '';
+ }
+ $array[$key] = $this->parseAttr($value, $config);
+ $cursor++;
+ } else {
+ // boolattr
+ if ($key !== '') {
+ $array[$key] = $key;
+ } else {
+ // purely theoretical
+ if ($e) {
+ $e->send(E_ERROR, 'Lexer: Missing attribute key');
+ }
+ }
+ }
+ }
+ return $array;
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Lexer/PH5P.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Lexer/PH5P.php
new file mode 100644
index 000000000..0b452d17f
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Lexer/PH5P.php
@@ -0,0 +1,4788 @@
+<?php
+
+/**
+ * Experimental HTML5-based parser using Jeroen van der Meer's PH5P library.
+ * Occupies space in the HTML5 pseudo-namespace, which may cause conflicts.
+ *
+ * @note
+ * Recent changes to PHP's DOM extension have resulted in some fatal
+ * error conditions with the original version of PH5P. Pending changes,
+ * this lexer will punt to DirectLex if DOM throws an exception.
+ */
+
+class HTMLPurifier_Lexer_PH5P extends HTMLPurifier_Lexer_DOMLex
+{
+ /**
+ * @param string $html
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return HTMLPurifier_Token[]
+ */
+ public function tokenizeHTML($html, $config, $context)
+ {
+ $new_html = $this->normalize($html, $config, $context);
+ $new_html = $this->wrapHTML($new_html, $config, $context, false /* no div */);
+ try {
+ $parser = new HTML5($new_html);
+ $doc = $parser->save();
+ } catch (DOMException $e) {
+ // Uh oh, it failed. Punt to DirectLex.
+ $lexer = new HTMLPurifier_Lexer_DirectLex();
+ $context->register('PH5PError', $e); // save the error, so we can detect it
+ return $lexer->tokenizeHTML($html, $config, $context); // use original HTML
+ }
+ $tokens = array();
+ $this->tokenizeDOM(
+ $doc->getElementsByTagName('html')->item(0)-> // <html>
+ getElementsByTagName('body')->item(0) // <body>
+ ,
+ $tokens, $config
+ );
+ return $tokens;
+ }
+}
+
+/*
+
+Copyright 2007 Jeroen van der Meer <http://jero.net/>
+
+Permission is hereby granted, free of charge, to any person obtaining a
+copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be included
+in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
+OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
+CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
+TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+*/
+
+class HTML5
+{
+ private $data;
+ private $char;
+ private $EOF;
+ private $state;
+ private $tree;
+ private $token;
+ private $content_model;
+ private $escape = false;
+ private $entities = array(
+ 'AElig;',
+ 'AElig',
+ 'AMP;',
+ 'AMP',
+ 'Aacute;',
+ 'Aacute',
+ 'Acirc;',
+ 'Acirc',
+ 'Agrave;',
+ 'Agrave',
+ 'Alpha;',
+ 'Aring;',
+ 'Aring',
+ 'Atilde;',
+ 'Atilde',
+ 'Auml;',
+ 'Auml',
+ 'Beta;',
+ 'COPY;',
+ 'COPY',
+ 'Ccedil;',
+ 'Ccedil',
+ 'Chi;',
+ 'Dagger;',
+ 'Delta;',
+ 'ETH;',
+ 'ETH',
+ 'Eacute;',
+ 'Eacute',
+ 'Ecirc;',
+ 'Ecirc',
+ 'Egrave;',
+ 'Egrave',
+ 'Epsilon;',
+ 'Eta;',
+ 'Euml;',
+ 'Euml',
+ 'GT;',
+ 'GT',
+ 'Gamma;',
+ 'Iacute;',
+ 'Iacute',
+ 'Icirc;',
+ 'Icirc',
+ 'Igrave;',
+ 'Igrave',
+ 'Iota;',
+ 'Iuml;',
+ 'Iuml',
+ 'Kappa;',
+ 'LT;',
+ 'LT',
+ 'Lambda;',
+ 'Mu;',
+ 'Ntilde;',
+ 'Ntilde',
+ 'Nu;',
+ 'OElig;',
+ 'Oacute;',
+ 'Oacute',
+ 'Ocirc;',
+ 'Ocirc',
+ 'Ograve;',
+ 'Ograve',
+ 'Omega;',
+ 'Omicron;',
+ 'Oslash;',
+ 'Oslash',
+ 'Otilde;',
+ 'Otilde',
+ 'Ouml;',
+ 'Ouml',
+ 'Phi;',
+ 'Pi;',
+ 'Prime;',
+ 'Psi;',
+ 'QUOT;',
+ 'QUOT',
+ 'REG;',
+ 'REG',
+ 'Rho;',
+ 'Scaron;',
+ 'Sigma;',
+ 'THORN;',
+ 'THORN',
+ 'TRADE;',
+ 'Tau;',
+ 'Theta;',
+ 'Uacute;',
+ 'Uacute',
+ 'Ucirc;',
+ 'Ucirc',
+ 'Ugrave;',
+ 'Ugrave',
+ 'Upsilon;',
+ 'Uuml;',
+ 'Uuml',
+ 'Xi;',
+ 'Yacute;',
+ 'Yacute',
+ 'Yuml;',
+ 'Zeta;',
+ 'aacute;',
+ 'aacute',
+ 'acirc;',
+ 'acirc',
+ 'acute;',
+ 'acute',
+ 'aelig;',
+ 'aelig',
+ 'agrave;',
+ 'agrave',
+ 'alefsym;',
+ 'alpha;',
+ 'amp;',
+ 'amp',
+ 'and;',
+ 'ang;',
+ 'apos;',
+ 'aring;',
+ 'aring',
+ 'asymp;',
+ 'atilde;',
+ 'atilde',
+ 'auml;',
+ 'auml',
+ 'bdquo;',
+ 'beta;',
+ 'brvbar;',
+ 'brvbar',
+ 'bull;',
+ 'cap;',
+ 'ccedil;',
+ 'ccedil',
+ 'cedil;',
+ 'cedil',
+ 'cent;',
+ 'cent',
+ 'chi;',
+ 'circ;',
+ 'clubs;',
+ 'cong;',
+ 'copy;',
+ 'copy',
+ 'crarr;',
+ 'cup;',
+ 'curren;',
+ 'curren',
+ 'dArr;',
+ 'dagger;',
+ 'darr;',
+ 'deg;',
+ 'deg',
+ 'delta;',
+ 'diams;',
+ 'divide;',
+ 'divide',
+ 'eacute;',
+ 'eacute',
+ 'ecirc;',
+ 'ecirc',
+ 'egrave;',
+ 'egrave',
+ 'empty;',
+ 'emsp;',
+ 'ensp;',
+ 'epsilon;',
+ 'equiv;',
+ 'eta;',
+ 'eth;',
+ 'eth',
+ 'euml;',
+ 'euml',
+ 'euro;',
+ 'exist;',
+ 'fnof;',
+ 'forall;',
+ 'frac12;',
+ 'frac12',
+ 'frac14;',
+ 'frac14',
+ 'frac34;',
+ 'frac34',
+ 'frasl;',
+ 'gamma;',
+ 'ge;',
+ 'gt;',
+ 'gt',
+ 'hArr;',
+ 'harr;',
+ 'hearts;',
+ 'hellip;',
+ 'iacute;',
+ 'iacute',
+ 'icirc;',
+ 'icirc',
+ 'iexcl;',
+ 'iexcl',
+ 'igrave;',
+ 'igrave',
+ 'image;',
+ 'infin;',
+ 'int;',
+ 'iota;',
+ 'iquest;',
+ 'iquest',
+ 'isin;',
+ 'iuml;',
+ 'iuml',
+ 'kappa;',
+ 'lArr;',
+ 'lambda;',
+ 'lang;',
+ 'laquo;',
+ 'laquo',
+ 'larr;',
+ 'lceil;',
+ 'ldquo;',
+ 'le;',
+ 'lfloor;',
+ 'lowast;',
+ 'loz;',
+ 'lrm;',
+ 'lsaquo;',
+ 'lsquo;',
+ 'lt;',
+ 'lt',
+ 'macr;',
+ 'macr',
+ 'mdash;',
+ 'micro;',
+ 'micro',
+ 'middot;',
+ 'middot',
+ 'minus;',
+ 'mu;',
+ 'nabla;',
+ 'nbsp;',
+ 'nbsp',
+ 'ndash;',
+ 'ne;',
+ 'ni;',
+ 'not;',
+ 'not',
+ 'notin;',
+ 'nsub;',
+ 'ntilde;',
+ 'ntilde',
+ 'nu;',
+ 'oacute;',
+ 'oacute',
+ 'ocirc;',
+ 'ocirc',
+ 'oelig;',
+ 'ograve;',
+ 'ograve',
+ 'oline;',
+ 'omega;',
+ 'omicron;',
+ 'oplus;',
+ 'or;',
+ 'ordf;',
+ 'ordf',
+ 'ordm;',
+ 'ordm',
+ 'oslash;',
+ 'oslash',
+ 'otilde;',
+ 'otilde',
+ 'otimes;',
+ 'ouml;',
+ 'ouml',
+ 'para;',
+ 'para',
+ 'part;',
+ 'permil;',
+ 'perp;',
+ 'phi;',
+ 'pi;',
+ 'piv;',
+ 'plusmn;',
+ 'plusmn',
+ 'pound;',
+ 'pound',
+ 'prime;',
+ 'prod;',
+ 'prop;',
+ 'psi;',
+ 'quot;',
+ 'quot',
+ 'rArr;',
+ 'radic;',
+ 'rang;',
+ 'raquo;',
+ 'raquo',
+ 'rarr;',
+ 'rceil;',
+ 'rdquo;',
+ 'real;',
+ 'reg;',
+ 'reg',
+ 'rfloor;',
+ 'rho;',
+ 'rlm;',
+ 'rsaquo;',
+ 'rsquo;',
+ 'sbquo;',
+ 'scaron;',
+ 'sdot;',
+ 'sect;',
+ 'sect',
+ 'shy;',
+ 'shy',
+ 'sigma;',
+ 'sigmaf;',
+ 'sim;',
+ 'spades;',
+ 'sub;',
+ 'sube;',
+ 'sum;',
+ 'sup1;',
+ 'sup1',
+ 'sup2;',
+ 'sup2',
+ 'sup3;',
+ 'sup3',
+ 'sup;',
+ 'supe;',
+ 'szlig;',
+ 'szlig',
+ 'tau;',
+ 'there4;',
+ 'theta;',
+ 'thetasym;',
+ 'thinsp;',
+ 'thorn;',
+ 'thorn',
+ 'tilde;',
+ 'times;',
+ 'times',
+ 'trade;',
+ 'uArr;',
+ 'uacute;',
+ 'uacute',
+ 'uarr;',
+ 'ucirc;',
+ 'ucirc',
+ 'ugrave;',
+ 'ugrave',
+ 'uml;',
+ 'uml',
+ 'upsih;',
+ 'upsilon;',
+ 'uuml;',
+ 'uuml',
+ 'weierp;',
+ 'xi;',
+ 'yacute;',
+ 'yacute',
+ 'yen;',
+ 'yen',
+ 'yuml;',
+ 'yuml',
+ 'zeta;',
+ 'zwj;',
+ 'zwnj;'
+ );
+
+ const PCDATA = 0;
+ const RCDATA = 1;
+ const CDATA = 2;
+ const PLAINTEXT = 3;
+
+ const DOCTYPE = 0;
+ const STARTTAG = 1;
+ const ENDTAG = 2;
+ const COMMENT = 3;
+ const CHARACTR = 4;
+ const EOF = 5;
+
+ public function __construct($data)
+ {
+ $this->data = $data;
+ $this->char = -1;
+ $this->EOF = strlen($data);
+ $this->tree = new HTML5TreeConstructer;
+ $this->content_model = self::PCDATA;
+
+ $this->state = 'data';
+
+ while ($this->state !== null) {
+ $this->{$this->state . 'State'}();
+ }
+ }
+
+ public function save()
+ {
+ return $this->tree->save();
+ }
+
+ private function char()
+ {
+ return ($this->char < $this->EOF)
+ ? $this->data[$this->char]
+ : false;
+ }
+
+ private function character($s, $l = 0)
+ {
+ if ($s + $l < $this->EOF) {
+ if ($l === 0) {
+ return $this->data[$s];
+ } else {
+ return substr($this->data, $s, $l);
+ }
+ }
+ }
+
+ private function characters($char_class, $start)
+ {
+ return preg_replace('#^([' . $char_class . ']+).*#s', '\\1', substr($this->data, $start));
+ }
+
+ private function dataState()
+ {
+ // Consume the next input character
+ $this->char++;
+ $char = $this->char();
+
+ if ($char === '&' && ($this->content_model === self::PCDATA || $this->content_model === self::RCDATA)) {
+ /* U+0026 AMPERSAND (&)
+ When the content model flag is set to one of the PCDATA or RCDATA
+ states: switch to the entity data state. Otherwise: treat it as per
+ the "anything else" entry below. */
+ $this->state = 'entityData';
+
+ } elseif ($char === '-') {
+ /* If the content model flag is set to either the RCDATA state or
+ the CDATA state, and the escape flag is false, and there are at
+ least three characters before this one in the input stream, and the
+ last four characters in the input stream, including this one, are
+ U+003C LESS-THAN SIGN, U+0021 EXCLAMATION MARK, U+002D HYPHEN-MINUS,
+ and U+002D HYPHEN-MINUS ("<!--"), then set the escape flag to true. */
+ if (($this->content_model === self::RCDATA || $this->content_model ===
+ self::CDATA) && $this->escape === false &&
+ $this->char >= 3 && $this->character($this->char - 4, 4) === '<!--'
+ ) {
+ $this->escape = true;
+ }
+
+ /* In any case, emit the input character as a character token. Stay
+ in the data state. */
+ $this->emitToken(
+ array(
+ 'type' => self::CHARACTR,
+ 'data' => $char
+ )
+ );
+
+ /* U+003C LESS-THAN SIGN (<) */
+ } elseif ($char === '<' && ($this->content_model === self::PCDATA ||
+ (($this->content_model === self::RCDATA ||
+ $this->content_model === self::CDATA) && $this->escape === false))
+ ) {
+ /* When the content model flag is set to the PCDATA state: switch
+ to the tag open state.
+
+ When the content model flag is set to either the RCDATA state or
+ the CDATA state and the escape flag is false: switch to the tag
+ open state.
+
+ Otherwise: treat it as per the "anything else" entry below. */
+ $this->state = 'tagOpen';
+
+ /* U+003E GREATER-THAN SIGN (>) */
+ } elseif ($char === '>') {
+ /* If the content model flag is set to either the RCDATA state or
+ the CDATA state, and the escape flag is true, and the last three
+ characters in the input stream including this one are U+002D
+ HYPHEN-MINUS, U+002D HYPHEN-MINUS, U+003E GREATER-THAN SIGN ("-->"),
+ set the escape flag to false. */
+ if (($this->content_model === self::RCDATA ||
+ $this->content_model === self::CDATA) && $this->escape === true &&
+ $this->character($this->char, 3) === '-->'
+ ) {
+ $this->escape = false;
+ }
+
+ /* In any case, emit the input character as a character token.
+ Stay in the data state. */
+ $this->emitToken(
+ array(
+ 'type' => self::CHARACTR,
+ 'data' => $char
+ )
+ );
+
+ } elseif ($this->char === $this->EOF) {
+ /* EOF
+ Emit an end-of-file token. */
+ $this->EOF();
+
+ } elseif ($this->content_model === self::PLAINTEXT) {
+ /* When the content model flag is set to the PLAINTEXT state
+ THIS DIFFERS GREATLY FROM THE SPEC: Get the remaining characters of
+ the text and emit it as a character token. */
+ $this->emitToken(
+ array(
+ 'type' => self::CHARACTR,
+ 'data' => substr($this->data, $this->char)
+ )
+ );
+
+ $this->EOF();
+
+ } else {
+ /* Anything else
+ THIS DIFFERS GREATLY FROM THE SPEC: Get as many character that
+ otherwise would also be treated as a character token and emit it
+ as a single character token. Stay in the data state. */
+ $len = strcspn($this->data, '<&', $this->char);
+ $char = substr($this->data, $this->char, $len);
+ $this->char += $len - 1;
+
+ $this->emitToken(
+ array(
+ 'type' => self::CHARACTR,
+ 'data' => $char
+ )
+ );
+
+ $this->state = 'data';
+ }
+ }
+
+ private function entityDataState()
+ {
+ // Attempt to consume an entity.
+ $entity = $this->entity();
+
+ // If nothing is returned, emit a U+0026 AMPERSAND character token.
+ // Otherwise, emit the character token that was returned.
+ $char = (!$entity) ? '&' : $entity;
+ $this->emitToken(
+ array(
+ 'type' => self::CHARACTR,
+ 'data' => $char
+ )
+ );
+
+ // Finally, switch to the data state.
+ $this->state = 'data';
+ }
+
+ private function tagOpenState()
+ {
+ switch ($this->content_model) {
+ case self::RCDATA:
+ case self::CDATA:
+ /* If the next input character is a U+002F SOLIDUS (/) character,
+ consume it and switch to the close tag open state. If the next
+ input character is not a U+002F SOLIDUS (/) character, emit a
+ U+003C LESS-THAN SIGN character token and switch to the data
+ state to process the next input character. */
+ if ($this->character($this->char + 1) === '/') {
+ $this->char++;
+ $this->state = 'closeTagOpen';
+
+ } else {
+ $this->emitToken(
+ array(
+ 'type' => self::CHARACTR,
+ 'data' => '<'
+ )
+ );
+
+ $this->state = 'data';
+ }
+ break;
+
+ case self::PCDATA:
+ // If the content model flag is set to the PCDATA state
+ // Consume the next input character:
+ $this->char++;
+ $char = $this->char();
+
+ if ($char === '!') {
+ /* U+0021 EXCLAMATION MARK (!)
+ Switch to the markup declaration open state. */
+ $this->state = 'markupDeclarationOpen';
+
+ } elseif ($char === '/') {
+ /* U+002F SOLIDUS (/)
+ Switch to the close tag open state. */
+ $this->state = 'closeTagOpen';
+
+ } elseif (preg_match('/^[A-Za-z]$/', $char)) {
+ /* U+0041 LATIN LETTER A through to U+005A LATIN LETTER Z
+ Create a new start tag token, set its tag name to the lowercase
+ version of the input character (add 0x0020 to the character's code
+ point), then switch to the tag name state. (Don't emit the token
+ yet; further details will be filled in before it is emitted.) */
+ $this->token = array(
+ 'name' => strtolower($char),
+ 'type' => self::STARTTAG,
+ 'attr' => array()
+ );
+
+ $this->state = 'tagName';
+
+ } elseif ($char === '>') {
+ /* U+003E GREATER-THAN SIGN (>)
+ Parse error. Emit a U+003C LESS-THAN SIGN character token and a
+ U+003E GREATER-THAN SIGN character token. Switch to the data state. */
+ $this->emitToken(
+ array(
+ 'type' => self::CHARACTR,
+ 'data' => '<>'
+ )
+ );
+
+ $this->state = 'data';
+
+ } elseif ($char === '?') {
+ /* U+003F QUESTION MARK (?)
+ Parse error. Switch to the bogus comment state. */
+ $this->state = 'bogusComment';
+
+ } else {
+ /* Anything else
+ Parse error. Emit a U+003C LESS-THAN SIGN character token and
+ reconsume the current input character in the data state. */
+ $this->emitToken(
+ array(
+ 'type' => self::CHARACTR,
+ 'data' => '<'
+ )
+ );
+
+ $this->char--;
+ $this->state = 'data';
+ }
+ break;
+ }
+ }
+
+ private function closeTagOpenState()
+ {
+ $next_node = strtolower($this->characters('A-Za-z', $this->char + 1));
+ $the_same = count($this->tree->stack) > 0 && $next_node === end($this->tree->stack)->nodeName;
+
+ if (($this->content_model === self::RCDATA || $this->content_model === self::CDATA) &&
+ (!$the_same || ($the_same && (!preg_match(
+ '/[\t\n\x0b\x0c >\/]/',
+ $this->character($this->char + 1 + strlen($next_node))
+ ) || $this->EOF === $this->char)))
+ ) {
+ /* If the content model flag is set to the RCDATA or CDATA states then
+ examine the next few characters. If they do not match the tag name of
+ the last start tag token emitted (case insensitively), or if they do but
+ they are not immediately followed by one of the following characters:
+ * U+0009 CHARACTER TABULATION
+ * U+000A LINE FEED (LF)
+ * U+000B LINE TABULATION
+ * U+000C FORM FEED (FF)
+ * U+0020 SPACE
+ * U+003E GREATER-THAN SIGN (>)
+ * U+002F SOLIDUS (/)
+ * EOF
+ ...then there is a parse error. Emit a U+003C LESS-THAN SIGN character
+ token, a U+002F SOLIDUS character token, and switch to the data state
+ to process the next input character. */
+ $this->emitToken(
+ array(
+ 'type' => self::CHARACTR,
+ 'data' => '</'
+ )
+ );
+
+ $this->state = 'data';
+
+ } else {
+ /* Otherwise, if the content model flag is set to the PCDATA state,
+ or if the next few characters do match that tag name, consume the
+ next input character: */
+ $this->char++;
+ $char = $this->char();
+
+ if (preg_match('/^[A-Za-z]$/', $char)) {
+ /* U+0041 LATIN LETTER A through to U+005A LATIN LETTER Z
+ Create a new end tag token, set its tag name to the lowercase version
+ of the input character (add 0x0020 to the character's code point), then
+ switch to the tag name state. (Don't emit the token yet; further details
+ will be filled in before it is emitted.) */
+ $this->token = array(
+ 'name' => strtolower($char),
+ 'type' => self::ENDTAG
+ );
+
+ $this->state = 'tagName';
+
+ } elseif ($char === '>') {
+ /* U+003E GREATER-THAN SIGN (>)
+ Parse error. Switch to the data state. */
+ $this->state = 'data';
+
+ } elseif ($this->char === $this->EOF) {
+ /* EOF
+ Parse error. Emit a U+003C LESS-THAN SIGN character token and a U+002F
+ SOLIDUS character token. Reconsume the EOF character in the data state. */
+ $this->emitToken(
+ array(
+ 'type' => self::CHARACTR,
+ 'data' => '</'
+ )
+ );
+
+ $this->char--;
+ $this->state = 'data';
+
+ } else {
+ /* Parse error. Switch to the bogus comment state. */
+ $this->state = 'bogusComment';
+ }
+ }
+ }
+
+ private function tagNameState()
+ {
+ // Consume the next input character:
+ $this->char++;
+ $char = $this->character($this->char);
+
+ if (preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
+ /* U+0009 CHARACTER TABULATION
+ U+000A LINE FEED (LF)
+ U+000B LINE TABULATION
+ U+000C FORM FEED (FF)
+ U+0020 SPACE
+ Switch to the before attribute name state. */
+ $this->state = 'beforeAttributeName';
+
+ } elseif ($char === '>') {
+ /* U+003E GREATER-THAN SIGN (>)
+ Emit the current tag token. Switch to the data state. */
+ $this->emitToken($this->token);
+ $this->state = 'data';
+
+ } elseif ($this->char === $this->EOF) {
+ /* EOF
+ Parse error. Emit the current tag token. Reconsume the EOF
+ character in the data state. */
+ $this->emitToken($this->token);
+
+ $this->char--;
+ $this->state = 'data';
+
+ } elseif ($char === '/') {
+ /* U+002F SOLIDUS (/)
+ Parse error unless this is a permitted slash. Switch to the before
+ attribute name state. */
+ $this->state = 'beforeAttributeName';
+
+ } else {
+ /* Anything else
+ Append the current input character to the current tag token's tag name.
+ Stay in the tag name state. */
+ $this->token['name'] .= strtolower($char);
+ $this->state = 'tagName';
+ }
+ }
+
+ private function beforeAttributeNameState()
+ {
+ // Consume the next input character:
+ $this->char++;
+ $char = $this->character($this->char);
+
+ if (preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
+ /* U+0009 CHARACTER TABULATION
+ U+000A LINE FEED (LF)
+ U+000B LINE TABULATION
+ U+000C FORM FEED (FF)
+ U+0020 SPACE
+ Stay in the before attribute name state. */
+ $this->state = 'beforeAttributeName';
+
+ } elseif ($char === '>') {
+ /* U+003E GREATER-THAN SIGN (>)
+ Emit the current tag token. Switch to the data state. */
+ $this->emitToken($this->token);
+ $this->state = 'data';
+
+ } elseif ($char === '/') {
+ /* U+002F SOLIDUS (/)
+ Parse error unless this is a permitted slash. Stay in the before
+ attribute name state. */
+ $this->state = 'beforeAttributeName';
+
+ } elseif ($this->char === $this->EOF) {
+ /* EOF
+ Parse error. Emit the current tag token. Reconsume the EOF
+ character in the data state. */
+ $this->emitToken($this->token);
+
+ $this->char--;
+ $this->state = 'data';
+
+ } else {
+ /* Anything else
+ Start a new attribute in the current tag token. Set that attribute's
+ name to the current input character, and its value to the empty string.
+ Switch to the attribute name state. */
+ $this->token['attr'][] = array(
+ 'name' => strtolower($char),
+ 'value' => null
+ );
+
+ $this->state = 'attributeName';
+ }
+ }
+
+ private function attributeNameState()
+ {
+ // Consume the next input character:
+ $this->char++;
+ $char = $this->character($this->char);
+
+ if (preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
+ /* U+0009 CHARACTER TABULATION
+ U+000A LINE FEED (LF)
+ U+000B LINE TABULATION
+ U+000C FORM FEED (FF)
+ U+0020 SPACE
+ Stay in the before attribute name state. */
+ $this->state = 'afterAttributeName';
+
+ } elseif ($char === '=') {
+ /* U+003D EQUALS SIGN (=)
+ Switch to the before attribute value state. */
+ $this->state = 'beforeAttributeValue';
+
+ } elseif ($char === '>') {
+ /* U+003E GREATER-THAN SIGN (>)
+ Emit the current tag token. Switch to the data state. */
+ $this->emitToken($this->token);
+ $this->state = 'data';
+
+ } elseif ($char === '/' && $this->character($this->char + 1) !== '>') {
+ /* U+002F SOLIDUS (/)
+ Parse error unless this is a permitted slash. Switch to the before
+ attribute name state. */
+ $this->state = 'beforeAttributeName';
+
+ } elseif ($this->char === $this->EOF) {
+ /* EOF
+ Parse error. Emit the current tag token. Reconsume the EOF
+ character in the data state. */
+ $this->emitToken($this->token);
+
+ $this->char--;
+ $this->state = 'data';
+
+ } else {
+ /* Anything else
+ Append the current input character to the current attribute's name.
+ Stay in the attribute name state. */
+ $last = count($this->token['attr']) - 1;
+ $this->token['attr'][$last]['name'] .= strtolower($char);
+
+ $this->state = 'attributeName';
+ }
+ }
+
+ private function afterAttributeNameState()
+ {
+ // Consume the next input character:
+ $this->char++;
+ $char = $this->character($this->char);
+
+ if (preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
+ /* U+0009 CHARACTER TABULATION
+ U+000A LINE FEED (LF)
+ U+000B LINE TABULATION
+ U+000C FORM FEED (FF)
+ U+0020 SPACE
+ Stay in the after attribute name state. */
+ $this->state = 'afterAttributeName';
+
+ } elseif ($char === '=') {
+ /* U+003D EQUALS SIGN (=)
+ Switch to the before attribute value state. */
+ $this->state = 'beforeAttributeValue';
+
+ } elseif ($char === '>') {
+ /* U+003E GREATER-THAN SIGN (>)
+ Emit the current tag token. Switch to the data state. */
+ $this->emitToken($this->token);
+ $this->state = 'data';
+
+ } elseif ($char === '/' && $this->character($this->char + 1) !== '>') {
+ /* U+002F SOLIDUS (/)
+ Parse error unless this is a permitted slash. Switch to the
+ before attribute name state. */
+ $this->state = 'beforeAttributeName';
+
+ } elseif ($this->char === $this->EOF) {
+ /* EOF
+ Parse error. Emit the current tag token. Reconsume the EOF
+ character in the data state. */
+ $this->emitToken($this->token);
+
+ $this->char--;
+ $this->state = 'data';
+
+ } else {
+ /* Anything else
+ Start a new attribute in the current tag token. Set that attribute's
+ name to the current input character, and its value to the empty string.
+ Switch to the attribute name state. */
+ $this->token['attr'][] = array(
+ 'name' => strtolower($char),
+ 'value' => null
+ );
+
+ $this->state = 'attributeName';
+ }
+ }
+
+ private function beforeAttributeValueState()
+ {
+ // Consume the next input character:
+ $this->char++;
+ $char = $this->character($this->char);
+
+ if (preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
+ /* U+0009 CHARACTER TABULATION
+ U+000A LINE FEED (LF)
+ U+000B LINE TABULATION
+ U+000C FORM FEED (FF)
+ U+0020 SPACE
+ Stay in the before attribute value state. */
+ $this->state = 'beforeAttributeValue';
+
+ } elseif ($char === '"') {
+ /* U+0022 QUOTATION MARK (")
+ Switch to the attribute value (double-quoted) state. */
+ $this->state = 'attributeValueDoubleQuoted';
+
+ } elseif ($char === '&') {
+ /* U+0026 AMPERSAND (&)
+ Switch to the attribute value (unquoted) state and reconsume
+ this input character. */
+ $this->char--;
+ $this->state = 'attributeValueUnquoted';
+
+ } elseif ($char === '\'') {
+ /* U+0027 APOSTROPHE (')
+ Switch to the attribute value (single-quoted) state. */
+ $this->state = 'attributeValueSingleQuoted';
+
+ } elseif ($char === '>') {
+ /* U+003E GREATER-THAN SIGN (>)
+ Emit the current tag token. Switch to the data state. */
+ $this->emitToken($this->token);
+ $this->state = 'data';
+
+ } else {
+ /* Anything else
+ Append the current input character to the current attribute's value.
+ Switch to the attribute value (unquoted) state. */
+ $last = count($this->token['attr']) - 1;
+ $this->token['attr'][$last]['value'] .= $char;
+
+ $this->state = 'attributeValueUnquoted';
+ }
+ }
+
+ private function attributeValueDoubleQuotedState()
+ {
+ // Consume the next input character:
+ $this->char++;
+ $char = $this->character($this->char);
+
+ if ($char === '"') {
+ /* U+0022 QUOTATION MARK (")
+ Switch to the before attribute name state. */
+ $this->state = 'beforeAttributeName';
+
+ } elseif ($char === '&') {
+ /* U+0026 AMPERSAND (&)
+ Switch to the entity in attribute value state. */
+ $this->entityInAttributeValueState('double');
+
+ } elseif ($this->char === $this->EOF) {
+ /* EOF
+ Parse error. Emit the current tag token. Reconsume the character
+ in the data state. */
+ $this->emitToken($this->token);
+
+ $this->char--;
+ $this->state = 'data';
+
+ } else {
+ /* Anything else
+ Append the current input character to the current attribute's value.
+ Stay in the attribute value (double-quoted) state. */
+ $last = count($this->token['attr']) - 1;
+ $this->token['attr'][$last]['value'] .= $char;
+
+ $this->state = 'attributeValueDoubleQuoted';
+ }
+ }
+
+ private function attributeValueSingleQuotedState()
+ {
+ // Consume the next input character:
+ $this->char++;
+ $char = $this->character($this->char);
+
+ if ($char === '\'') {
+ /* U+0022 QUOTATION MARK (')
+ Switch to the before attribute name state. */
+ $this->state = 'beforeAttributeName';
+
+ } elseif ($char === '&') {
+ /* U+0026 AMPERSAND (&)
+ Switch to the entity in attribute value state. */
+ $this->entityInAttributeValueState('single');
+
+ } elseif ($this->char === $this->EOF) {
+ /* EOF
+ Parse error. Emit the current tag token. Reconsume the character
+ in the data state. */
+ $this->emitToken($this->token);
+
+ $this->char--;
+ $this->state = 'data';
+
+ } else {
+ /* Anything else
+ Append the current input character to the current attribute's value.
+ Stay in the attribute value (single-quoted) state. */
+ $last = count($this->token['attr']) - 1;
+ $this->token['attr'][$last]['value'] .= $char;
+
+ $this->state = 'attributeValueSingleQuoted';
+ }
+ }
+
+ private function attributeValueUnquotedState()
+ {
+ // Consume the next input character:
+ $this->char++;
+ $char = $this->character($this->char);
+
+ if (preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
+ /* U+0009 CHARACTER TABULATION
+ U+000A LINE FEED (LF)
+ U+000B LINE TABULATION
+ U+000C FORM FEED (FF)
+ U+0020 SPACE
+ Switch to the before attribute name state. */
+ $this->state = 'beforeAttributeName';
+
+ } elseif ($char === '&') {
+ /* U+0026 AMPERSAND (&)
+ Switch to the entity in attribute value state. */
+ $this->entityInAttributeValueState();
+
+ } elseif ($char === '>') {
+ /* U+003E GREATER-THAN SIGN (>)
+ Emit the current tag token. Switch to the data state. */
+ $this->emitToken($this->token);
+ $this->state = 'data';
+
+ } else {
+ /* Anything else
+ Append the current input character to the current attribute's value.
+ Stay in the attribute value (unquoted) state. */
+ $last = count($this->token['attr']) - 1;
+ $this->token['attr'][$last]['value'] .= $char;
+
+ $this->state = 'attributeValueUnquoted';
+ }
+ }
+
+ private function entityInAttributeValueState()
+ {
+ // Attempt to consume an entity.
+ $entity = $this->entity();
+
+ // If nothing is returned, append a U+0026 AMPERSAND character to the
+ // current attribute's value. Otherwise, emit the character token that
+ // was returned.
+ $char = (!$entity)
+ ? '&'
+ : $entity;
+
+ $last = count($this->token['attr']) - 1;
+ $this->token['attr'][$last]['value'] .= $char;
+ }
+
+ private function bogusCommentState()
+ {
+ /* Consume every character up to the first U+003E GREATER-THAN SIGN
+ character (>) or the end of the file (EOF), whichever comes first. Emit
+ a comment token whose data is the concatenation of all the characters
+ starting from and including the character that caused the state machine
+ to switch into the bogus comment state, up to and including the last
+ consumed character before the U+003E character, if any, or up to the
+ end of the file otherwise. (If the comment was started by the end of
+ the file (EOF), the token is empty.) */
+ $data = $this->characters('^>', $this->char);
+ $this->emitToken(
+ array(
+ 'data' => $data,
+ 'type' => self::COMMENT
+ )
+ );
+
+ $this->char += strlen($data);
+
+ /* Switch to the data state. */
+ $this->state = 'data';
+
+ /* If the end of the file was reached, reconsume the EOF character. */
+ if ($this->char === $this->EOF) {
+ $this->char = $this->EOF - 1;
+ }
+ }
+
+ private function markupDeclarationOpenState()
+ {
+ /* If the next two characters are both U+002D HYPHEN-MINUS (-)
+ characters, consume those two characters, create a comment token whose
+ data is the empty string, and switch to the comment state. */
+ if ($this->character($this->char + 1, 2) === '--') {
+ $this->char += 2;
+ $this->state = 'comment';
+ $this->token = array(
+ 'data' => null,
+ 'type' => self::COMMENT
+ );
+
+ /* Otherwise if the next seven chacacters are a case-insensitive match
+ for the word "DOCTYPE", then consume those characters and switch to the
+ DOCTYPE state. */
+ } elseif (strtolower($this->character($this->char + 1, 7)) === 'doctype') {
+ $this->char += 7;
+ $this->state = 'doctype';
+
+ /* Otherwise, is is a parse error. Switch to the bogus comment state.
+ The next character that is consumed, if any, is the first character
+ that will be in the comment. */
+ } else {
+ $this->char++;
+ $this->state = 'bogusComment';
+ }
+ }
+
+ private function commentState()
+ {
+ /* Consume the next input character: */
+ $this->char++;
+ $char = $this->char();
+
+ /* U+002D HYPHEN-MINUS (-) */
+ if ($char === '-') {
+ /* Switch to the comment dash state */
+ $this->state = 'commentDash';
+
+ /* EOF */
+ } elseif ($this->char === $this->EOF) {
+ /* Parse error. Emit the comment token. Reconsume the EOF character
+ in the data state. */
+ $this->emitToken($this->token);
+ $this->char--;
+ $this->state = 'data';
+
+ /* Anything else */
+ } else {
+ /* Append the input character to the comment token's data. Stay in
+ the comment state. */
+ $this->token['data'] .= $char;
+ }
+ }
+
+ private function commentDashState()
+ {
+ /* Consume the next input character: */
+ $this->char++;
+ $char = $this->char();
+
+ /* U+002D HYPHEN-MINUS (-) */
+ if ($char === '-') {
+ /* Switch to the comment end state */
+ $this->state = 'commentEnd';
+
+ /* EOF */
+ } elseif ($this->char === $this->EOF) {
+ /* Parse error. Emit the comment token. Reconsume the EOF character
+ in the data state. */
+ $this->emitToken($this->token);
+ $this->char--;
+ $this->state = 'data';
+
+ /* Anything else */
+ } else {
+ /* Append a U+002D HYPHEN-MINUS (-) character and the input
+ character to the comment token's data. Switch to the comment state. */
+ $this->token['data'] .= '-' . $char;
+ $this->state = 'comment';
+ }
+ }
+
+ private function commentEndState()
+ {
+ /* Consume the next input character: */
+ $this->char++;
+ $char = $this->char();
+
+ if ($char === '>') {
+ $this->emitToken($this->token);
+ $this->state = 'data';
+
+ } elseif ($char === '-') {
+ $this->token['data'] .= '-';
+
+ } elseif ($this->char === $this->EOF) {
+ $this->emitToken($this->token);
+ $this->char--;
+ $this->state = 'data';
+
+ } else {
+ $this->token['data'] .= '--' . $char;
+ $this->state = 'comment';
+ }
+ }
+
+ private function doctypeState()
+ {
+ /* Consume the next input character: */
+ $this->char++;
+ $char = $this->char();
+
+ if (preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
+ $this->state = 'beforeDoctypeName';
+
+ } else {
+ $this->char--;
+ $this->state = 'beforeDoctypeName';
+ }
+ }
+
+ private function beforeDoctypeNameState()
+ {
+ /* Consume the next input character: */
+ $this->char++;
+ $char = $this->char();
+
+ if (preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
+ // Stay in the before DOCTYPE name state.
+
+ } elseif (preg_match('/^[a-z]$/', $char)) {
+ $this->token = array(
+ 'name' => strtoupper($char),
+ 'type' => self::DOCTYPE,
+ 'error' => true
+ );
+
+ $this->state = 'doctypeName';
+
+ } elseif ($char === '>') {
+ $this->emitToken(
+ array(
+ 'name' => null,
+ 'type' => self::DOCTYPE,
+ 'error' => true
+ )
+ );
+
+ $this->state = 'data';
+
+ } elseif ($this->char === $this->EOF) {
+ $this->emitToken(
+ array(
+ 'name' => null,
+ 'type' => self::DOCTYPE,
+ 'error' => true
+ )
+ );
+
+ $this->char--;
+ $this->state = 'data';
+
+ } else {
+ $this->token = array(
+ 'name' => $char,
+ 'type' => self::DOCTYPE,
+ 'error' => true
+ );
+
+ $this->state = 'doctypeName';
+ }
+ }
+
+ private function doctypeNameState()
+ {
+ /* Consume the next input character: */
+ $this->char++;
+ $char = $this->char();
+
+ if (preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
+ $this->state = 'AfterDoctypeName';
+
+ } elseif ($char === '>') {
+ $this->emitToken($this->token);
+ $this->state = 'data';
+
+ } elseif (preg_match('/^[a-z]$/', $char)) {
+ $this->token['name'] .= strtoupper($char);
+
+ } elseif ($this->char === $this->EOF) {
+ $this->emitToken($this->token);
+ $this->char--;
+ $this->state = 'data';
+
+ } else {
+ $this->token['name'] .= $char;
+ }
+
+ $this->token['error'] = ($this->token['name'] === 'HTML')
+ ? false
+ : true;
+ }
+
+ private function afterDoctypeNameState()
+ {
+ /* Consume the next input character: */
+ $this->char++;
+ $char = $this->char();
+
+ if (preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
+ // Stay in the DOCTYPE name state.
+
+ } elseif ($char === '>') {
+ $this->emitToken($this->token);
+ $this->state = 'data';
+
+ } elseif ($this->char === $this->EOF) {
+ $this->emitToken($this->token);
+ $this->char--;
+ $this->state = 'data';
+
+ } else {
+ $this->token['error'] = true;
+ $this->state = 'bogusDoctype';
+ }
+ }
+
+ private function bogusDoctypeState()
+ {
+ /* Consume the next input character: */
+ $this->char++;
+ $char = $this->char();
+
+ if ($char === '>') {
+ $this->emitToken($this->token);
+ $this->state = 'data';
+
+ } elseif ($this->char === $this->EOF) {
+ $this->emitToken($this->token);
+ $this->char--;
+ $this->state = 'data';
+
+ } else {
+ // Stay in the bogus DOCTYPE state.
+ }
+ }
+
+ private function entity()
+ {
+ $start = $this->char;
+
+ // This section defines how to consume an entity. This definition is
+ // used when parsing entities in text and in attributes.
+
+ // The behaviour depends on the identity of the next character (the
+ // one immediately after the U+0026 AMPERSAND character):
+
+ switch ($this->character($this->char + 1)) {
+ // U+0023 NUMBER SIGN (#)
+ case '#':
+
+ // The behaviour further depends on the character after the
+ // U+0023 NUMBER SIGN:
+ switch ($this->character($this->char + 1)) {
+ // U+0078 LATIN SMALL LETTER X
+ // U+0058 LATIN CAPITAL LETTER X
+ case 'x':
+ case 'X':
+ // Follow the steps below, but using the range of
+ // characters U+0030 DIGIT ZERO through to U+0039 DIGIT
+ // NINE, U+0061 LATIN SMALL LETTER A through to U+0066
+ // LATIN SMALL LETTER F, and U+0041 LATIN CAPITAL LETTER
+ // A, through to U+0046 LATIN CAPITAL LETTER F (in other
+ // words, 0-9, A-F, a-f).
+ $char = 1;
+ $char_class = '0-9A-Fa-f';
+ break;
+
+ // Anything else
+ default:
+ // Follow the steps below, but using the range of
+ // characters U+0030 DIGIT ZERO through to U+0039 DIGIT
+ // NINE (i.e. just 0-9).
+ $char = 0;
+ $char_class = '0-9';
+ break;
+ }
+
+ // Consume as many characters as match the range of characters
+ // given above.
+ $this->char++;
+ $e_name = $this->characters($char_class, $this->char + $char + 1);
+ $entity = $this->character($start, $this->char);
+ $cond = strlen($e_name) > 0;
+
+ // The rest of the parsing happens bellow.
+ break;
+
+ // Anything else
+ default:
+ // Consume the maximum number of characters possible, with the
+ // consumed characters case-sensitively matching one of the
+ // identifiers in the first column of the entities table.
+
+ $e_name = $this->characters('0-9A-Za-z;', $this->char + 1);
+ $len = strlen($e_name);
+
+ for ($c = 1; $c <= $len; $c++) {
+ $id = substr($e_name, 0, $c);
+ $this->char++;
+
+ if (in_array($id, $this->entities)) {
+ if ($e_name[$c - 1] !== ';') {
+ if ($c < $len && $e_name[$c] == ';') {
+ $this->char++; // consume extra semicolon
+ }
+ }
+ $entity = $id;
+ break;
+ }
+ }
+
+ $cond = isset($entity);
+ // The rest of the parsing happens bellow.
+ break;
+ }
+
+ if (!$cond) {
+ // If no match can be made, then this is a parse error. No
+ // characters are consumed, and nothing is returned.
+ $this->char = $start;
+ return false;
+ }
+
+ // Return a character token for the character corresponding to the
+ // entity name (as given by the second column of the entities table).
+ return html_entity_decode('&' . rtrim($entity, ';') . ';', ENT_QUOTES, 'UTF-8');
+ }
+
+ private function emitToken($token)
+ {
+ $emit = $this->tree->emitToken($token);
+
+ if (is_int($emit)) {
+ $this->content_model = $emit;
+
+ } elseif ($token['type'] === self::ENDTAG) {
+ $this->content_model = self::PCDATA;
+ }
+ }
+
+ private function EOF()
+ {
+ $this->state = null;
+ $this->tree->emitToken(
+ array(
+ 'type' => self::EOF
+ )
+ );
+ }
+}
+
+class HTML5TreeConstructer
+{
+ public $stack = array();
+
+ private $phase;
+ private $mode;
+ private $dom;
+ private $foster_parent = null;
+ private $a_formatting = array();
+
+ private $head_pointer = null;
+ private $form_pointer = null;
+
+ private $scoping = array('button', 'caption', 'html', 'marquee', 'object', 'table', 'td', 'th');
+ private $formatting = array(
+ 'a',
+ 'b',
+ 'big',
+ 'em',
+ 'font',
+ 'i',
+ 'nobr',
+ 's',
+ 'small',
+ 'strike',
+ 'strong',
+ 'tt',
+ 'u'
+ );
+ private $special = array(
+ 'address',
+ 'area',
+ 'base',
+ 'basefont',
+ 'bgsound',
+ 'blockquote',
+ 'body',
+ 'br',
+ 'center',
+ 'col',
+ 'colgroup',
+ 'dd',
+ 'dir',
+ 'div',
+ 'dl',
+ 'dt',
+ 'embed',
+ 'fieldset',
+ 'form',
+ 'frame',
+ 'frameset',
+ 'h1',
+ 'h2',
+ 'h3',
+ 'h4',
+ 'h5',
+ 'h6',
+ 'head',
+ 'hr',
+ 'iframe',
+ 'image',
+ 'img',
+ 'input',
+ 'isindex',
+ 'li',
+ 'link',
+ 'listing',
+ 'menu',
+ 'meta',
+ 'noembed',
+ 'noframes',
+ 'noscript',
+ 'ol',
+ 'optgroup',
+ 'option',
+ 'p',
+ 'param',
+ 'plaintext',
+ 'pre',
+ 'script',
+ 'select',
+ 'spacer',
+ 'style',
+ 'tbody',
+ 'textarea',
+ 'tfoot',
+ 'thead',
+ 'title',
+ 'tr',
+ 'ul',
+ 'wbr'
+ );
+
+ // The different phases.
+ const INIT_PHASE = 0;
+ const ROOT_PHASE = 1;
+ const MAIN_PHASE = 2;
+ const END_PHASE = 3;
+
+ // The different insertion modes for the main phase.
+ const BEFOR_HEAD = 0;
+ const IN_HEAD = 1;
+ const AFTER_HEAD = 2;
+ const IN_BODY = 3;
+ const IN_TABLE = 4;
+ const IN_CAPTION = 5;
+ const IN_CGROUP = 6;
+ const IN_TBODY = 7;
+ const IN_ROW = 8;
+ const IN_CELL = 9;
+ const IN_SELECT = 10;
+ const AFTER_BODY = 11;
+ const IN_FRAME = 12;
+ const AFTR_FRAME = 13;
+
+ // The different types of elements.
+ const SPECIAL = 0;
+ const SCOPING = 1;
+ const FORMATTING = 2;
+ const PHRASING = 3;
+
+ const MARKER = 0;
+
+ public function __construct()
+ {
+ $this->phase = self::INIT_PHASE;
+ $this->mode = self::BEFOR_HEAD;
+ $this->dom = new DOMDocument;
+
+ $this->dom->encoding = 'UTF-8';
+ $this->dom->preserveWhiteSpace = true;
+ $this->dom->substituteEntities = true;
+ $this->dom->strictErrorChecking = false;
+ }
+
+ // Process tag tokens
+ public function emitToken($token)
+ {
+ switch ($this->phase) {
+ case self::INIT_PHASE:
+ return $this->initPhase($token);
+ break;
+ case self::ROOT_PHASE:
+ return $this->rootElementPhase($token);
+ break;
+ case self::MAIN_PHASE:
+ return $this->mainPhase($token);
+ break;
+ case self::END_PHASE :
+ return $this->trailingEndPhase($token);
+ break;
+ }
+ }
+
+ private function initPhase($token)
+ {
+ /* Initially, the tree construction stage must handle each token
+ emitted from the tokenisation stage as follows: */
+
+ /* A DOCTYPE token that is marked as being in error
+ A comment token
+ A start tag token
+ An end tag token
+ A character token that is not one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE
+ An end-of-file token */
+ if ((isset($token['error']) && $token['error']) ||
+ $token['type'] === HTML5::COMMENT ||
+ $token['type'] === HTML5::STARTTAG ||
+ $token['type'] === HTML5::ENDTAG ||
+ $token['type'] === HTML5::EOF ||
+ ($token['type'] === HTML5::CHARACTR && isset($token['data']) &&
+ !preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data']))
+ ) {
+ /* This specification does not define how to handle this case. In
+ particular, user agents may ignore the entirety of this specification
+ altogether for such documents, and instead invoke special parse modes
+ with a greater emphasis on backwards compatibility. */
+
+ $this->phase = self::ROOT_PHASE;
+ return $this->rootElementPhase($token);
+
+ /* A DOCTYPE token marked as being correct */
+ } elseif (isset($token['error']) && !$token['error']) {
+ /* Append a DocumentType node to the Document node, with the name
+ attribute set to the name given in the DOCTYPE token (which will be
+ "HTML"), and the other attributes specific to DocumentType objects
+ set to null, empty lists, or the empty string as appropriate. */
+ $doctype = new DOMDocumentType(null, null, 'HTML');
+
+ /* Then, switch to the root element phase of the tree construction
+ stage. */
+ $this->phase = self::ROOT_PHASE;
+
+ /* A character token that is one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE */
+ } elseif (isset($token['data']) && preg_match(
+ '/^[\t\n\x0b\x0c ]+$/',
+ $token['data']
+ )
+ ) {
+ /* Append that character to the Document node. */
+ $text = $this->dom->createTextNode($token['data']);
+ $this->dom->appendChild($text);
+ }
+ }
+
+ private function rootElementPhase($token)
+ {
+ /* After the initial phase, as each token is emitted from the tokenisation
+ stage, it must be processed as described in this section. */
+
+ /* A DOCTYPE token */
+ if ($token['type'] === HTML5::DOCTYPE) {
+ // Parse error. Ignore the token.
+
+ /* A comment token */
+ } elseif ($token['type'] === HTML5::COMMENT) {
+ /* Append a Comment node to the Document object with the data
+ attribute set to the data given in the comment token. */
+ $comment = $this->dom->createComment($token['data']);
+ $this->dom->appendChild($comment);
+
+ /* A character token that is one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE */
+ } elseif ($token['type'] === HTML5::CHARACTR &&
+ preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])
+ ) {
+ /* Append that character to the Document node. */
+ $text = $this->dom->createTextNode($token['data']);
+ $this->dom->appendChild($text);
+
+ /* A character token that is not one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED
+ (FF), or U+0020 SPACE
+ A start tag token
+ An end tag token
+ An end-of-file token */
+ } elseif (($token['type'] === HTML5::CHARACTR &&
+ !preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])) ||
+ $token['type'] === HTML5::STARTTAG ||
+ $token['type'] === HTML5::ENDTAG ||
+ $token['type'] === HTML5::EOF
+ ) {
+ /* Create an HTMLElement node with the tag name html, in the HTML
+ namespace. Append it to the Document object. Switch to the main
+ phase and reprocess the current token. */
+ $html = $this->dom->createElement('html');
+ $this->dom->appendChild($html);
+ $this->stack[] = $html;
+
+ $this->phase = self::MAIN_PHASE;
+ return $this->mainPhase($token);
+ }
+ }
+
+ private function mainPhase($token)
+ {
+ /* Tokens in the main phase must be handled as follows: */
+
+ /* A DOCTYPE token */
+ if ($token['type'] === HTML5::DOCTYPE) {
+ // Parse error. Ignore the token.
+
+ /* A start tag token with the tag name "html" */
+ } elseif ($token['type'] === HTML5::STARTTAG && $token['name'] === 'html') {
+ /* If this start tag token was not the first start tag token, then
+ it is a parse error. */
+
+ /* For each attribute on the token, check to see if the attribute
+ is already present on the top element of the stack of open elements.
+ If it is not, add the attribute and its corresponding value to that
+ element. */
+ foreach ($token['attr'] as $attr) {
+ if (!$this->stack[0]->hasAttribute($attr['name'])) {
+ $this->stack[0]->setAttribute($attr['name'], $attr['value']);
+ }
+ }
+
+ /* An end-of-file token */
+ } elseif ($token['type'] === HTML5::EOF) {
+ /* Generate implied end tags. */
+ $this->generateImpliedEndTags();
+
+ /* Anything else. */
+ } else {
+ /* Depends on the insertion mode: */
+ switch ($this->mode) {
+ case self::BEFOR_HEAD:
+ return $this->beforeHead($token);
+ break;
+ case self::IN_HEAD:
+ return $this->inHead($token);
+ break;
+ case self::AFTER_HEAD:
+ return $this->afterHead($token);
+ break;
+ case self::IN_BODY:
+ return $this->inBody($token);
+ break;
+ case self::IN_TABLE:
+ return $this->inTable($token);
+ break;
+ case self::IN_CAPTION:
+ return $this->inCaption($token);
+ break;
+ case self::IN_CGROUP:
+ return $this->inColumnGroup($token);
+ break;
+ case self::IN_TBODY:
+ return $this->inTableBody($token);
+ break;
+ case self::IN_ROW:
+ return $this->inRow($token);
+ break;
+ case self::IN_CELL:
+ return $this->inCell($token);
+ break;
+ case self::IN_SELECT:
+ return $this->inSelect($token);
+ break;
+ case self::AFTER_BODY:
+ return $this->afterBody($token);
+ break;
+ case self::IN_FRAME:
+ return $this->inFrameset($token);
+ break;
+ case self::AFTR_FRAME:
+ return $this->afterFrameset($token);
+ break;
+ case self::END_PHASE:
+ return $this->trailingEndPhase($token);
+ break;
+ }
+ }
+ }
+
+ private function beforeHead($token)
+ {
+ /* Handle the token as follows: */
+
+ /* A character token that is one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE */
+ if ($token['type'] === HTML5::CHARACTR &&
+ preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])
+ ) {
+ /* Append the character to the current node. */
+ $this->insertText($token['data']);
+
+ /* A comment token */
+ } elseif ($token['type'] === HTML5::COMMENT) {
+ /* Append a Comment node to the current node with the data attribute
+ set to the data given in the comment token. */
+ $this->insertComment($token['data']);
+
+ /* A start tag token with the tag name "head" */
+ } elseif ($token['type'] === HTML5::STARTTAG && $token['name'] === 'head') {
+ /* Create an element for the token, append the new element to the
+ current node and push it onto the stack of open elements. */
+ $element = $this->insertElement($token);
+
+ /* Set the head element pointer to this new element node. */
+ $this->head_pointer = $element;
+
+ /* Change the insertion mode to "in head". */
+ $this->mode = self::IN_HEAD;
+
+ /* A start tag token whose tag name is one of: "base", "link", "meta",
+ "script", "style", "title". Or an end tag with the tag name "html".
+ Or a character token that is not one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE. Or any other start tag token */
+ } elseif ($token['type'] === HTML5::STARTTAG ||
+ ($token['type'] === HTML5::ENDTAG && $token['name'] === 'html') ||
+ ($token['type'] === HTML5::CHARACTR && !preg_match(
+ '/^[\t\n\x0b\x0c ]$/',
+ $token['data']
+ ))
+ ) {
+ /* Act as if a start tag token with the tag name "head" and no
+ attributes had been seen, then reprocess the current token. */
+ $this->beforeHead(
+ array(
+ 'name' => 'head',
+ 'type' => HTML5::STARTTAG,
+ 'attr' => array()
+ )
+ );
+
+ return $this->inHead($token);
+
+ /* Any other end tag */
+ } elseif ($token['type'] === HTML5::ENDTAG) {
+ /* Parse error. Ignore the token. */
+ }
+ }
+
+ private function inHead($token)
+ {
+ /* Handle the token as follows: */
+
+ /* A character token that is one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE.
+
+ THIS DIFFERS FROM THE SPEC: If the current node is either a title, style
+ or script element, append the character to the current node regardless
+ of its content. */
+ if (($token['type'] === HTML5::CHARACTR &&
+ preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])) || (
+ $token['type'] === HTML5::CHARACTR && in_array(
+ end($this->stack)->nodeName,
+ array('title', 'style', 'script')
+ ))
+ ) {
+ /* Append the character to the current node. */
+ $this->insertText($token['data']);
+
+ /* A comment token */
+ } elseif ($token['type'] === HTML5::COMMENT) {
+ /* Append a Comment node to the current node with the data attribute
+ set to the data given in the comment token. */
+ $this->insertComment($token['data']);
+
+ } elseif ($token['type'] === HTML5::ENDTAG &&
+ in_array($token['name'], array('title', 'style', 'script'))
+ ) {
+ array_pop($this->stack);
+ return HTML5::PCDATA;
+
+ /* A start tag with the tag name "title" */
+ } elseif ($token['type'] === HTML5::STARTTAG && $token['name'] === 'title') {
+ /* Create an element for the token and append the new element to the
+ node pointed to by the head element pointer, or, if that is null
+ (innerHTML case), to the current node. */
+ if ($this->head_pointer !== null) {
+ $element = $this->insertElement($token, false);
+ $this->head_pointer->appendChild($element);
+
+ } else {
+ $element = $this->insertElement($token);
+ }
+
+ /* Switch the tokeniser's content model flag to the RCDATA state. */
+ return HTML5::RCDATA;
+
+ /* A start tag with the tag name "style" */
+ } elseif ($token['type'] === HTML5::STARTTAG && $token['name'] === 'style') {
+ /* Create an element for the token and append the new element to the
+ node pointed to by the head element pointer, or, if that is null
+ (innerHTML case), to the current node. */
+ if ($this->head_pointer !== null) {
+ $element = $this->insertElement($token, false);
+ $this->head_pointer->appendChild($element);
+
+ } else {
+ $this->insertElement($token);
+ }
+
+ /* Switch the tokeniser's content model flag to the CDATA state. */
+ return HTML5::CDATA;
+
+ /* A start tag with the tag name "script" */
+ } elseif ($token['type'] === HTML5::STARTTAG && $token['name'] === 'script') {
+ /* Create an element for the token. */
+ $element = $this->insertElement($token, false);
+ $this->head_pointer->appendChild($element);
+
+ /* Switch the tokeniser's content model flag to the CDATA state. */
+ return HTML5::CDATA;
+
+ /* A start tag with the tag name "base", "link", or "meta" */
+ } elseif ($token['type'] === HTML5::STARTTAG && in_array(
+ $token['name'],
+ array('base', 'link', 'meta')
+ )
+ ) {
+ /* Create an element for the token and append the new element to the
+ node pointed to by the head element pointer, or, if that is null
+ (innerHTML case), to the current node. */
+ if ($this->head_pointer !== null) {
+ $element = $this->insertElement($token, false);
+ $this->head_pointer->appendChild($element);
+ array_pop($this->stack);
+
+ } else {
+ $this->insertElement($token);
+ }
+
+ /* An end tag with the tag name "head" */
+ } elseif ($token['type'] === HTML5::ENDTAG && $token['name'] === 'head') {
+ /* If the current node is a head element, pop the current node off
+ the stack of open elements. */
+ if ($this->head_pointer->isSameNode(end($this->stack))) {
+ array_pop($this->stack);
+
+ /* Otherwise, this is a parse error. */
+ } else {
+ // k
+ }
+
+ /* Change the insertion mode to "after head". */
+ $this->mode = self::AFTER_HEAD;
+
+ /* A start tag with the tag name "head" or an end tag except "html". */
+ } elseif (($token['type'] === HTML5::STARTTAG && $token['name'] === 'head') ||
+ ($token['type'] === HTML5::ENDTAG && $token['name'] !== 'html')
+ ) {
+ // Parse error. Ignore the token.
+
+ /* Anything else */
+ } else {
+ /* If the current node is a head element, act as if an end tag
+ token with the tag name "head" had been seen. */
+ if ($this->head_pointer->isSameNode(end($this->stack))) {
+ $this->inHead(
+ array(
+ 'name' => 'head',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+
+ /* Otherwise, change the insertion mode to "after head". */
+ } else {
+ $this->mode = self::AFTER_HEAD;
+ }
+
+ /* Then, reprocess the current token. */
+ return $this->afterHead($token);
+ }
+ }
+
+ private function afterHead($token)
+ {
+ /* Handle the token as follows: */
+
+ /* A character token that is one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE */
+ if ($token['type'] === HTML5::CHARACTR &&
+ preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])
+ ) {
+ /* Append the character to the current node. */
+ $this->insertText($token['data']);
+
+ /* A comment token */
+ } elseif ($token['type'] === HTML5::COMMENT) {
+ /* Append a Comment node to the current node with the data attribute
+ set to the data given in the comment token. */
+ $this->insertComment($token['data']);
+
+ /* A start tag token with the tag name "body" */
+ } elseif ($token['type'] === HTML5::STARTTAG && $token['name'] === 'body') {
+ /* Insert a body element for the token. */
+ $this->insertElement($token);
+
+ /* Change the insertion mode to "in body". */
+ $this->mode = self::IN_BODY;
+
+ /* A start tag token with the tag name "frameset" */
+ } elseif ($token['type'] === HTML5::STARTTAG && $token['name'] === 'frameset') {
+ /* Insert a frameset element for the token. */
+ $this->insertElement($token);
+
+ /* Change the insertion mode to "in frameset". */
+ $this->mode = self::IN_FRAME;
+
+ /* A start tag token whose tag name is one of: "base", "link", "meta",
+ "script", "style", "title" */
+ } elseif ($token['type'] === HTML5::STARTTAG && in_array(
+ $token['name'],
+ array('base', 'link', 'meta', 'script', 'style', 'title')
+ )
+ ) {
+ /* Parse error. Switch the insertion mode back to "in head" and
+ reprocess the token. */
+ $this->mode = self::IN_HEAD;
+ return $this->inHead($token);
+
+ /* Anything else */
+ } else {
+ /* Act as if a start tag token with the tag name "body" and no
+ attributes had been seen, and then reprocess the current token. */
+ $this->afterHead(
+ array(
+ 'name' => 'body',
+ 'type' => HTML5::STARTTAG,
+ 'attr' => array()
+ )
+ );
+
+ return $this->inBody($token);
+ }
+ }
+
+ private function inBody($token)
+ {
+ /* Handle the token as follows: */
+
+ switch ($token['type']) {
+ /* A character token */
+ case HTML5::CHARACTR:
+ /* Reconstruct the active formatting elements, if any. */
+ $this->reconstructActiveFormattingElements();
+
+ /* Append the token's character to the current node. */
+ $this->insertText($token['data']);
+ break;
+
+ /* A comment token */
+ case HTML5::COMMENT:
+ /* Append a Comment node to the current node with the data
+ attribute set to the data given in the comment token. */
+ $this->insertComment($token['data']);
+ break;
+
+ case HTML5::STARTTAG:
+ switch ($token['name']) {
+ /* A start tag token whose tag name is one of: "script",
+ "style" */
+ case 'script':
+ case 'style':
+ /* Process the token as if the insertion mode had been "in
+ head". */
+ return $this->inHead($token);
+ break;
+
+ /* A start tag token whose tag name is one of: "base", "link",
+ "meta", "title" */
+ case 'base':
+ case 'link':
+ case 'meta':
+ case 'title':
+ /* Parse error. Process the token as if the insertion mode
+ had been "in head". */
+ return $this->inHead($token);
+ break;
+
+ /* A start tag token with the tag name "body" */
+ case 'body':
+ /* Parse error. If the second element on the stack of open
+ elements is not a body element, or, if the stack of open
+ elements has only one node on it, then ignore the token.
+ (innerHTML case) */
+ if (count($this->stack) === 1 || $this->stack[1]->nodeName !== 'body') {
+ // Ignore
+
+ /* Otherwise, for each attribute on the token, check to see
+ if the attribute is already present on the body element (the
+ second element) on the stack of open elements. If it is not,
+ add the attribute and its corresponding value to that
+ element. */
+ } else {
+ foreach ($token['attr'] as $attr) {
+ if (!$this->stack[1]->hasAttribute($attr['name'])) {
+ $this->stack[1]->setAttribute($attr['name'], $attr['value']);
+ }
+ }
+ }
+ break;
+
+ /* A start tag whose tag name is one of: "address",
+ "blockquote", "center", "dir", "div", "dl", "fieldset",
+ "listing", "menu", "ol", "p", "ul" */
+ case 'address':
+ case 'blockquote':
+ case 'center':
+ case 'dir':
+ case 'div':
+ case 'dl':
+ case 'fieldset':
+ case 'listing':
+ case 'menu':
+ case 'ol':
+ case 'p':
+ case 'ul':
+ /* If the stack of open elements has a p element in scope,
+ then act as if an end tag with the tag name p had been
+ seen. */
+ if ($this->elementInScope('p')) {
+ $this->emitToken(
+ array(
+ 'name' => 'p',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+ }
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+ break;
+
+ /* A start tag whose tag name is "form" */
+ case 'form':
+ /* If the form element pointer is not null, ignore the
+ token with a parse error. */
+ if ($this->form_pointer !== null) {
+ // Ignore.
+
+ /* Otherwise: */
+ } else {
+ /* If the stack of open elements has a p element in
+ scope, then act as if an end tag with the tag name p
+ had been seen. */
+ if ($this->elementInScope('p')) {
+ $this->emitToken(
+ array(
+ 'name' => 'p',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+ }
+
+ /* Insert an HTML element for the token, and set the
+ form element pointer to point to the element created. */
+ $element = $this->insertElement($token);
+ $this->form_pointer = $element;
+ }
+ break;
+
+ /* A start tag whose tag name is "li", "dd" or "dt" */
+ case 'li':
+ case 'dd':
+ case 'dt':
+ /* If the stack of open elements has a p element in scope,
+ then act as if an end tag with the tag name p had been
+ seen. */
+ if ($this->elementInScope('p')) {
+ $this->emitToken(
+ array(
+ 'name' => 'p',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+ }
+
+ $stack_length = count($this->stack) - 1;
+
+ for ($n = $stack_length; 0 <= $n; $n--) {
+ /* 1. Initialise node to be the current node (the
+ bottommost node of the stack). */
+ $stop = false;
+ $node = $this->stack[$n];
+ $cat = $this->getElementCategory($node->tagName);
+
+ /* 2. If node is an li, dd or dt element, then pop all
+ the nodes from the current node up to node, including
+ node, then stop this algorithm. */
+ if ($token['name'] === $node->tagName || ($token['name'] !== 'li'
+ && ($node->tagName === 'dd' || $node->tagName === 'dt'))
+ ) {
+ for ($x = $stack_length; $x >= $n; $x--) {
+ array_pop($this->stack);
+ }
+
+ break;
+ }
+
+ /* 3. If node is not in the formatting category, and is
+ not in the phrasing category, and is not an address or
+ div element, then stop this algorithm. */
+ if ($cat !== self::FORMATTING && $cat !== self::PHRASING &&
+ $node->tagName !== 'address' && $node->tagName !== 'div'
+ ) {
+ break;
+ }
+ }
+
+ /* Finally, insert an HTML element with the same tag
+ name as the token's. */
+ $this->insertElement($token);
+ break;
+
+ /* A start tag token whose tag name is "plaintext" */
+ case 'plaintext':
+ /* If the stack of open elements has a p element in scope,
+ then act as if an end tag with the tag name p had been
+ seen. */
+ if ($this->elementInScope('p')) {
+ $this->emitToken(
+ array(
+ 'name' => 'p',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+ }
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+
+ return HTML5::PLAINTEXT;
+ break;
+
+ /* A start tag whose tag name is one of: "h1", "h2", "h3", "h4",
+ "h5", "h6" */
+ case 'h1':
+ case 'h2':
+ case 'h3':
+ case 'h4':
+ case 'h5':
+ case 'h6':
+ /* If the stack of open elements has a p element in scope,
+ then act as if an end tag with the tag name p had been seen. */
+ if ($this->elementInScope('p')) {
+ $this->emitToken(
+ array(
+ 'name' => 'p',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+ }
+
+ /* If the stack of open elements has in scope an element whose
+ tag name is one of "h1", "h2", "h3", "h4", "h5", or "h6", then
+ this is a parse error; pop elements from the stack until an
+ element with one of those tag names has been popped from the
+ stack. */
+ while ($this->elementInScope(array('h1', 'h2', 'h3', 'h4', 'h5', 'h6'))) {
+ array_pop($this->stack);
+ }
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+ break;
+
+ /* A start tag whose tag name is "a" */
+ case 'a':
+ /* If the list of active formatting elements contains
+ an element whose tag name is "a" between the end of the
+ list and the last marker on the list (or the start of
+ the list if there is no marker on the list), then this
+ is a parse error; act as if an end tag with the tag name
+ "a" had been seen, then remove that element from the list
+ of active formatting elements and the stack of open
+ elements if the end tag didn't already remove it (it
+ might not have if the element is not in table scope). */
+ $leng = count($this->a_formatting);
+
+ for ($n = $leng - 1; $n >= 0; $n--) {
+ if ($this->a_formatting[$n] === self::MARKER) {
+ break;
+
+ } elseif ($this->a_formatting[$n]->nodeName === 'a') {
+ $this->emitToken(
+ array(
+ 'name' => 'a',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+ break;
+ }
+ }
+
+ /* Reconstruct the active formatting elements, if any. */
+ $this->reconstructActiveFormattingElements();
+
+ /* Insert an HTML element for the token. */
+ $el = $this->insertElement($token);
+
+ /* Add that element to the list of active formatting
+ elements. */
+ $this->a_formatting[] = $el;
+ break;
+
+ /* A start tag whose tag name is one of: "b", "big", "em", "font",
+ "i", "nobr", "s", "small", "strike", "strong", "tt", "u" */
+ case 'b':
+ case 'big':
+ case 'em':
+ case 'font':
+ case 'i':
+ case 'nobr':
+ case 's':
+ case 'small':
+ case 'strike':
+ case 'strong':
+ case 'tt':
+ case 'u':
+ /* Reconstruct the active formatting elements, if any. */
+ $this->reconstructActiveFormattingElements();
+
+ /* Insert an HTML element for the token. */
+ $el = $this->insertElement($token);
+
+ /* Add that element to the list of active formatting
+ elements. */
+ $this->a_formatting[] = $el;
+ break;
+
+ /* A start tag token whose tag name is "button" */
+ case 'button':
+ /* If the stack of open elements has a button element in scope,
+ then this is a parse error; act as if an end tag with the tag
+ name "button" had been seen, then reprocess the token. (We don't
+ do that. Unnecessary.) */
+ if ($this->elementInScope('button')) {
+ $this->inBody(
+ array(
+ 'name' => 'button',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+ }
+
+ /* Reconstruct the active formatting elements, if any. */
+ $this->reconstructActiveFormattingElements();
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+
+ /* Insert a marker at the end of the list of active
+ formatting elements. */
+ $this->a_formatting[] = self::MARKER;
+ break;
+
+ /* A start tag token whose tag name is one of: "marquee", "object" */
+ case 'marquee':
+ case 'object':
+ /* Reconstruct the active formatting elements, if any. */
+ $this->reconstructActiveFormattingElements();
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+
+ /* Insert a marker at the end of the list of active
+ formatting elements. */
+ $this->a_formatting[] = self::MARKER;
+ break;
+
+ /* A start tag token whose tag name is "xmp" */
+ case 'xmp':
+ /* Reconstruct the active formatting elements, if any. */
+ $this->reconstructActiveFormattingElements();
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+
+ /* Switch the content model flag to the CDATA state. */
+ return HTML5::CDATA;
+ break;
+
+ /* A start tag whose tag name is "table" */
+ case 'table':
+ /* If the stack of open elements has a p element in scope,
+ then act as if an end tag with the tag name p had been seen. */
+ if ($this->elementInScope('p')) {
+ $this->emitToken(
+ array(
+ 'name' => 'p',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+ }
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+
+ /* Change the insertion mode to "in table". */
+ $this->mode = self::IN_TABLE;
+ break;
+
+ /* A start tag whose tag name is one of: "area", "basefont",
+ "bgsound", "br", "embed", "img", "param", "spacer", "wbr" */
+ case 'area':
+ case 'basefont':
+ case 'bgsound':
+ case 'br':
+ case 'embed':
+ case 'img':
+ case 'param':
+ case 'spacer':
+ case 'wbr':
+ /* Reconstruct the active formatting elements, if any. */
+ $this->reconstructActiveFormattingElements();
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+
+ /* Immediately pop the current node off the stack of open elements. */
+ array_pop($this->stack);
+ break;
+
+ /* A start tag whose tag name is "hr" */
+ case 'hr':
+ /* If the stack of open elements has a p element in scope,
+ then act as if an end tag with the tag name p had been seen. */
+ if ($this->elementInScope('p')) {
+ $this->emitToken(
+ array(
+ 'name' => 'p',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+ }
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+
+ /* Immediately pop the current node off the stack of open elements. */
+ array_pop($this->stack);
+ break;
+
+ /* A start tag whose tag name is "image" */
+ case 'image':
+ /* Parse error. Change the token's tag name to "img" and
+ reprocess it. (Don't ask.) */
+ $token['name'] = 'img';
+ return $this->inBody($token);
+ break;
+
+ /* A start tag whose tag name is "input" */
+ case 'input':
+ /* Reconstruct the active formatting elements, if any. */
+ $this->reconstructActiveFormattingElements();
+
+ /* Insert an input element for the token. */
+ $element = $this->insertElement($token, false);
+
+ /* If the form element pointer is not null, then associate the
+ input element with the form element pointed to by the form
+ element pointer. */
+ $this->form_pointer !== null
+ ? $this->form_pointer->appendChild($element)
+ : end($this->stack)->appendChild($element);
+
+ /* Pop that input element off the stack of open elements. */
+ array_pop($this->stack);
+ break;
+
+ /* A start tag whose tag name is "isindex" */
+ case 'isindex':
+ /* Parse error. */
+ // w/e
+
+ /* If the form element pointer is not null,
+ then ignore the token. */
+ if ($this->form_pointer === null) {
+ /* Act as if a start tag token with the tag name "form" had
+ been seen. */
+ $this->inBody(
+ array(
+ 'name' => 'body',
+ 'type' => HTML5::STARTTAG,
+ 'attr' => array()
+ )
+ );
+
+ /* Act as if a start tag token with the tag name "hr" had
+ been seen. */
+ $this->inBody(
+ array(
+ 'name' => 'hr',
+ 'type' => HTML5::STARTTAG,
+ 'attr' => array()
+ )
+ );
+
+ /* Act as if a start tag token with the tag name "p" had
+ been seen. */
+ $this->inBody(
+ array(
+ 'name' => 'p',
+ 'type' => HTML5::STARTTAG,
+ 'attr' => array()
+ )
+ );
+
+ /* Act as if a start tag token with the tag name "label"
+ had been seen. */
+ $this->inBody(
+ array(
+ 'name' => 'label',
+ 'type' => HTML5::STARTTAG,
+ 'attr' => array()
+ )
+ );
+
+ /* Act as if a stream of character tokens had been seen. */
+ $this->insertText(
+ 'This is a searchable index. ' .
+ 'Insert your search keywords here: '
+ );
+
+ /* Act as if a start tag token with the tag name "input"
+ had been seen, with all the attributes from the "isindex"
+ token, except with the "name" attribute set to the value
+ "isindex" (ignoring any explicit "name" attribute). */
+ $attr = $token['attr'];
+ $attr[] = array('name' => 'name', 'value' => 'isindex');
+
+ $this->inBody(
+ array(
+ 'name' => 'input',
+ 'type' => HTML5::STARTTAG,
+ 'attr' => $attr
+ )
+ );
+
+ /* Act as if a stream of character tokens had been seen
+ (see below for what they should say). */
+ $this->insertText(
+ 'This is a searchable index. ' .
+ 'Insert your search keywords here: '
+ );
+
+ /* Act as if an end tag token with the tag name "label"
+ had been seen. */
+ $this->inBody(
+ array(
+ 'name' => 'label',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+
+ /* Act as if an end tag token with the tag name "p" had
+ been seen. */
+ $this->inBody(
+ array(
+ 'name' => 'p',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+
+ /* Act as if a start tag token with the tag name "hr" had
+ been seen. */
+ $this->inBody(
+ array(
+ 'name' => 'hr',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+
+ /* Act as if an end tag token with the tag name "form" had
+ been seen. */
+ $this->inBody(
+ array(
+ 'name' => 'form',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+ }
+ break;
+
+ /* A start tag whose tag name is "textarea" */
+ case 'textarea':
+ $this->insertElement($token);
+
+ /* Switch the tokeniser's content model flag to the
+ RCDATA state. */
+ return HTML5::RCDATA;
+ break;
+
+ /* A start tag whose tag name is one of: "iframe", "noembed",
+ "noframes" */
+ case 'iframe':
+ case 'noembed':
+ case 'noframes':
+ $this->insertElement($token);
+
+ /* Switch the tokeniser's content model flag to the CDATA state. */
+ return HTML5::CDATA;
+ break;
+
+ /* A start tag whose tag name is "select" */
+ case 'select':
+ /* Reconstruct the active formatting elements, if any. */
+ $this->reconstructActiveFormattingElements();
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+
+ /* Change the insertion mode to "in select". */
+ $this->mode = self::IN_SELECT;
+ break;
+
+ /* A start or end tag whose tag name is one of: "caption", "col",
+ "colgroup", "frame", "frameset", "head", "option", "optgroup",
+ "tbody", "td", "tfoot", "th", "thead", "tr". */
+ case 'caption':
+ case 'col':
+ case 'colgroup':
+ case 'frame':
+ case 'frameset':
+ case 'head':
+ case 'option':
+ case 'optgroup':
+ case 'tbody':
+ case 'td':
+ case 'tfoot':
+ case 'th':
+ case 'thead':
+ case 'tr':
+ // Parse error. Ignore the token.
+ break;
+
+ /* A start or end tag whose tag name is one of: "event-source",
+ "section", "nav", "article", "aside", "header", "footer",
+ "datagrid", "command" */
+ case 'event-source':
+ case 'section':
+ case 'nav':
+ case 'article':
+ case 'aside':
+ case 'header':
+ case 'footer':
+ case 'datagrid':
+ case 'command':
+ // Work in progress!
+ break;
+
+ /* A start tag token not covered by the previous entries */
+ default:
+ /* Reconstruct the active formatting elements, if any. */
+ $this->reconstructActiveFormattingElements();
+
+ $this->insertElement($token, true, true);
+ break;
+ }
+ break;
+
+ case HTML5::ENDTAG:
+ switch ($token['name']) {
+ /* An end tag with the tag name "body" */
+ case 'body':
+ /* If the second element in the stack of open elements is
+ not a body element, this is a parse error. Ignore the token.
+ (innerHTML case) */
+ if (count($this->stack) < 2 || $this->stack[1]->nodeName !== 'body') {
+ // Ignore.
+
+ /* If the current node is not the body element, then this
+ is a parse error. */
+ } elseif (end($this->stack)->nodeName !== 'body') {
+ // Parse error.
+ }
+
+ /* Change the insertion mode to "after body". */
+ $this->mode = self::AFTER_BODY;
+ break;
+
+ /* An end tag with the tag name "html" */
+ case 'html':
+ /* Act as if an end tag with tag name "body" had been seen,
+ then, if that token wasn't ignored, reprocess the current
+ token. */
+ $this->inBody(
+ array(
+ 'name' => 'body',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+
+ return $this->afterBody($token);
+ break;
+
+ /* An end tag whose tag name is one of: "address", "blockquote",
+ "center", "dir", "div", "dl", "fieldset", "listing", "menu",
+ "ol", "pre", "ul" */
+ case 'address':
+ case 'blockquote':
+ case 'center':
+ case 'dir':
+ case 'div':
+ case 'dl':
+ case 'fieldset':
+ case 'listing':
+ case 'menu':
+ case 'ol':
+ case 'pre':
+ case 'ul':
+ /* If the stack of open elements has an element in scope
+ with the same tag name as that of the token, then generate
+ implied end tags. */
+ if ($this->elementInScope($token['name'])) {
+ $this->generateImpliedEndTags();
+
+ /* Now, if the current node is not an element with
+ the same tag name as that of the token, then this
+ is a parse error. */
+ // w/e
+
+ /* If the stack of open elements has an element in
+ scope with the same tag name as that of the token,
+ then pop elements from this stack until an element
+ with that tag name has been popped from the stack. */
+ for ($n = count($this->stack) - 1; $n >= 0; $n--) {
+ if ($this->stack[$n]->nodeName === $token['name']) {
+ $n = -1;
+ }
+
+ array_pop($this->stack);
+ }
+ }
+ break;
+
+ /* An end tag whose tag name is "form" */
+ case 'form':
+ /* If the stack of open elements has an element in scope
+ with the same tag name as that of the token, then generate
+ implied end tags. */
+ if ($this->elementInScope($token['name'])) {
+ $this->generateImpliedEndTags();
+
+ }
+
+ if (end($this->stack)->nodeName !== $token['name']) {
+ /* Now, if the current node is not an element with the
+ same tag name as that of the token, then this is a parse
+ error. */
+ // w/e
+
+ } else {
+ /* Otherwise, if the current node is an element with
+ the same tag name as that of the token pop that element
+ from the stack. */
+ array_pop($this->stack);
+ }
+
+ /* In any case, set the form element pointer to null. */
+ $this->form_pointer = null;
+ break;
+
+ /* An end tag whose tag name is "p" */
+ case 'p':
+ /* If the stack of open elements has a p element in scope,
+ then generate implied end tags, except for p elements. */
+ if ($this->elementInScope('p')) {
+ $this->generateImpliedEndTags(array('p'));
+
+ /* If the current node is not a p element, then this is
+ a parse error. */
+ // k
+
+ /* If the stack of open elements has a p element in
+ scope, then pop elements from this stack until the stack
+ no longer has a p element in scope. */
+ for ($n = count($this->stack) - 1; $n >= 0; $n--) {
+ if ($this->elementInScope('p')) {
+ array_pop($this->stack);
+
+ } else {
+ break;
+ }
+ }
+ }
+ break;
+
+ /* An end tag whose tag name is "dd", "dt", or "li" */
+ case 'dd':
+ case 'dt':
+ case 'li':
+ /* If the stack of open elements has an element in scope
+ whose tag name matches the tag name of the token, then
+ generate implied end tags, except for elements with the
+ same tag name as the token. */
+ if ($this->elementInScope($token['name'])) {
+ $this->generateImpliedEndTags(array($token['name']));
+
+ /* If the current node is not an element with the same
+ tag name as the token, then this is a parse error. */
+ // w/e
+
+ /* If the stack of open elements has an element in scope
+ whose tag name matches the tag name of the token, then
+ pop elements from this stack until an element with that
+ tag name has been popped from the stack. */
+ for ($n = count($this->stack) - 1; $n >= 0; $n--) {
+ if ($this->stack[$n]->nodeName === $token['name']) {
+ $n = -1;
+ }
+
+ array_pop($this->stack);
+ }
+ }
+ break;
+
+ /* An end tag whose tag name is one of: "h1", "h2", "h3", "h4",
+ "h5", "h6" */
+ case 'h1':
+ case 'h2':
+ case 'h3':
+ case 'h4':
+ case 'h5':
+ case 'h6':
+ $elements = array('h1', 'h2', 'h3', 'h4', 'h5', 'h6');
+
+ /* If the stack of open elements has in scope an element whose
+ tag name is one of "h1", "h2", "h3", "h4", "h5", or "h6", then
+ generate implied end tags. */
+ if ($this->elementInScope($elements)) {
+ $this->generateImpliedEndTags();
+
+ /* Now, if the current node is not an element with the same
+ tag name as that of the token, then this is a parse error. */
+ // w/e
+
+ /* If the stack of open elements has in scope an element
+ whose tag name is one of "h1", "h2", "h3", "h4", "h5", or
+ "h6", then pop elements from the stack until an element
+ with one of those tag names has been popped from the stack. */
+ while ($this->elementInScope($elements)) {
+ array_pop($this->stack);
+ }
+ }
+ break;
+
+ /* An end tag whose tag name is one of: "a", "b", "big", "em",
+ "font", "i", "nobr", "s", "small", "strike", "strong", "tt", "u" */
+ case 'a':
+ case 'b':
+ case 'big':
+ case 'em':
+ case 'font':
+ case 'i':
+ case 'nobr':
+ case 's':
+ case 'small':
+ case 'strike':
+ case 'strong':
+ case 'tt':
+ case 'u':
+ /* 1. Let the formatting element be the last element in
+ the list of active formatting elements that:
+ * is between the end of the list and the last scope
+ marker in the list, if any, or the start of the list
+ otherwise, and
+ * has the same tag name as the token.
+ */
+ while (true) {
+ for ($a = count($this->a_formatting) - 1; $a >= 0; $a--) {
+ if ($this->a_formatting[$a] === self::MARKER) {
+ break;
+
+ } elseif ($this->a_formatting[$a]->tagName === $token['name']) {
+ $formatting_element = $this->a_formatting[$a];
+ $in_stack = in_array($formatting_element, $this->stack, true);
+ $fe_af_pos = $a;
+ break;
+ }
+ }
+
+ /* If there is no such node, or, if that node is
+ also in the stack of open elements but the element
+ is not in scope, then this is a parse error. Abort
+ these steps. The token is ignored. */
+ if (!isset($formatting_element) || ($in_stack &&
+ !$this->elementInScope($token['name']))
+ ) {
+ break;
+
+ /* Otherwise, if there is such a node, but that node
+ is not in the stack of open elements, then this is a
+ parse error; remove the element from the list, and
+ abort these steps. */
+ } elseif (isset($formatting_element) && !$in_stack) {
+ unset($this->a_formatting[$fe_af_pos]);
+ $this->a_formatting = array_merge($this->a_formatting);
+ break;
+ }
+
+ /* 2. Let the furthest block be the topmost node in the
+ stack of open elements that is lower in the stack
+ than the formatting element, and is not an element in
+ the phrasing or formatting categories. There might
+ not be one. */
+ $fe_s_pos = array_search($formatting_element, $this->stack, true);
+ $length = count($this->stack);
+
+ for ($s = $fe_s_pos + 1; $s < $length; $s++) {
+ $category = $this->getElementCategory($this->stack[$s]->nodeName);
+
+ if ($category !== self::PHRASING && $category !== self::FORMATTING) {
+ $furthest_block = $this->stack[$s];
+ }
+ }
+
+ /* 3. If there is no furthest block, then the UA must
+ skip the subsequent steps and instead just pop all
+ the nodes from the bottom of the stack of open
+ elements, from the current node up to the formatting
+ element, and remove the formatting element from the
+ list of active formatting elements. */
+ if (!isset($furthest_block)) {
+ for ($n = $length - 1; $n >= $fe_s_pos; $n--) {
+ array_pop($this->stack);
+ }
+
+ unset($this->a_formatting[$fe_af_pos]);
+ $this->a_formatting = array_merge($this->a_formatting);
+ break;
+ }
+
+ /* 4. Let the common ancestor be the element
+ immediately above the formatting element in the stack
+ of open elements. */
+ $common_ancestor = $this->stack[$fe_s_pos - 1];
+
+ /* 5. If the furthest block has a parent node, then
+ remove the furthest block from its parent node. */
+ if ($furthest_block->parentNode !== null) {
+ $furthest_block->parentNode->removeChild($furthest_block);
+ }
+
+ /* 6. Let a bookmark note the position of the
+ formatting element in the list of active formatting
+ elements relative to the elements on either side
+ of it in the list. */
+ $bookmark = $fe_af_pos;
+
+ /* 7. Let node and last node be the furthest block.
+ Follow these steps: */
+ $node = $furthest_block;
+ $last_node = $furthest_block;
+
+ while (true) {
+ for ($n = array_search($node, $this->stack, true) - 1; $n >= 0; $n--) {
+ /* 7.1 Let node be the element immediately
+ prior to node in the stack of open elements. */
+ $node = $this->stack[$n];
+
+ /* 7.2 If node is not in the list of active
+ formatting elements, then remove node from
+ the stack of open elements and then go back
+ to step 1. */
+ if (!in_array($node, $this->a_formatting, true)) {
+ unset($this->stack[$n]);
+ $this->stack = array_merge($this->stack);
+
+ } else {
+ break;
+ }
+ }
+
+ /* 7.3 Otherwise, if node is the formatting
+ element, then go to the next step in the overall
+ algorithm. */
+ if ($node === $formatting_element) {
+ break;
+
+ /* 7.4 Otherwise, if last node is the furthest
+ block, then move the aforementioned bookmark to
+ be immediately after the node in the list of
+ active formatting elements. */
+ } elseif ($last_node === $furthest_block) {
+ $bookmark = array_search($node, $this->a_formatting, true) + 1;
+ }
+
+ /* 7.5 If node has any children, perform a
+ shallow clone of node, replace the entry for
+ node in the list of active formatting elements
+ with an entry for the clone, replace the entry
+ for node in the stack of open elements with an
+ entry for the clone, and let node be the clone. */
+ if ($node->hasChildNodes()) {
+ $clone = $node->cloneNode();
+ $s_pos = array_search($node, $this->stack, true);
+ $a_pos = array_search($node, $this->a_formatting, true);
+
+ $this->stack[$s_pos] = $clone;
+ $this->a_formatting[$a_pos] = $clone;
+ $node = $clone;
+ }
+
+ /* 7.6 Insert last node into node, first removing
+ it from its previous parent node if any. */
+ if ($last_node->parentNode !== null) {
+ $last_node->parentNode->removeChild($last_node);
+ }
+
+ $node->appendChild($last_node);
+
+ /* 7.7 Let last node be node. */
+ $last_node = $node;
+ }
+
+ /* 8. Insert whatever last node ended up being in
+ the previous step into the common ancestor node,
+ first removing it from its previous parent node if
+ any. */
+ if ($last_node->parentNode !== null) {
+ $last_node->parentNode->removeChild($last_node);
+ }
+
+ $common_ancestor->appendChild($last_node);
+
+ /* 9. Perform a shallow clone of the formatting
+ element. */
+ $clone = $formatting_element->cloneNode();
+
+ /* 10. Take all of the child nodes of the furthest
+ block and append them to the clone created in the
+ last step. */
+ while ($furthest_block->hasChildNodes()) {
+ $child = $furthest_block->firstChild;
+ $furthest_block->removeChild($child);
+ $clone->appendChild($child);
+ }
+
+ /* 11. Append that clone to the furthest block. */
+ $furthest_block->appendChild($clone);
+
+ /* 12. Remove the formatting element from the list
+ of active formatting elements, and insert the clone
+ into the list of active formatting elements at the
+ position of the aforementioned bookmark. */
+ $fe_af_pos = array_search($formatting_element, $this->a_formatting, true);
+ unset($this->a_formatting[$fe_af_pos]);
+ $this->a_formatting = array_merge($this->a_formatting);
+
+ $af_part1 = array_slice($this->a_formatting, 0, $bookmark - 1);
+ $af_part2 = array_slice($this->a_formatting, $bookmark, count($this->a_formatting));
+ $this->a_formatting = array_merge($af_part1, array($clone), $af_part2);
+
+ /* 13. Remove the formatting element from the stack
+ of open elements, and insert the clone into the stack
+ of open elements immediately after (i.e. in a more
+ deeply nested position than) the position of the
+ furthest block in that stack. */
+ $fe_s_pos = array_search($formatting_element, $this->stack, true);
+ $fb_s_pos = array_search($furthest_block, $this->stack, true);
+ unset($this->stack[$fe_s_pos]);
+
+ $s_part1 = array_slice($this->stack, 0, $fb_s_pos);
+ $s_part2 = array_slice($this->stack, $fb_s_pos + 1, count($this->stack));
+ $this->stack = array_merge($s_part1, array($clone), $s_part2);
+
+ /* 14. Jump back to step 1 in this series of steps. */
+ unset($formatting_element, $fe_af_pos, $fe_s_pos, $furthest_block);
+ }
+ break;
+
+ /* An end tag token whose tag name is one of: "button",
+ "marquee", "object" */
+ case 'button':
+ case 'marquee':
+ case 'object':
+ /* If the stack of open elements has an element in scope whose
+ tag name matches the tag name of the token, then generate implied
+ tags. */
+ if ($this->elementInScope($token['name'])) {
+ $this->generateImpliedEndTags();
+
+ /* Now, if the current node is not an element with the same
+ tag name as the token, then this is a parse error. */
+ // k
+
+ /* Now, if the stack of open elements has an element in scope
+ whose tag name matches the tag name of the token, then pop
+ elements from the stack until that element has been popped from
+ the stack, and clear the list of active formatting elements up
+ to the last marker. */
+ for ($n = count($this->stack) - 1; $n >= 0; $n--) {
+ if ($this->stack[$n]->nodeName === $token['name']) {
+ $n = -1;
+ }
+
+ array_pop($this->stack);
+ }
+
+ $marker = end(array_keys($this->a_formatting, self::MARKER, true));
+
+ for ($n = count($this->a_formatting) - 1; $n > $marker; $n--) {
+ array_pop($this->a_formatting);
+ }
+ }
+ break;
+
+ /* Or an end tag whose tag name is one of: "area", "basefont",
+ "bgsound", "br", "embed", "hr", "iframe", "image", "img",
+ "input", "isindex", "noembed", "noframes", "param", "select",
+ "spacer", "table", "textarea", "wbr" */
+ case 'area':
+ case 'basefont':
+ case 'bgsound':
+ case 'br':
+ case 'embed':
+ case 'hr':
+ case 'iframe':
+ case 'image':
+ case 'img':
+ case 'input':
+ case 'isindex':
+ case 'noembed':
+ case 'noframes':
+ case 'param':
+ case 'select':
+ case 'spacer':
+ case 'table':
+ case 'textarea':
+ case 'wbr':
+ // Parse error. Ignore the token.
+ break;
+
+ /* An end tag token not covered by the previous entries */
+ default:
+ for ($n = count($this->stack) - 1; $n >= 0; $n--) {
+ /* Initialise node to be the current node (the bottommost
+ node of the stack). */
+ $node = end($this->stack);
+
+ /* If node has the same tag name as the end tag token,
+ then: */
+ if ($token['name'] === $node->nodeName) {
+ /* Generate implied end tags. */
+ $this->generateImpliedEndTags();
+
+ /* If the tag name of the end tag token does not
+ match the tag name of the current node, this is a
+ parse error. */
+ // k
+
+ /* Pop all the nodes from the current node up to
+ node, including node, then stop this algorithm. */
+ for ($x = count($this->stack) - $n; $x >= $n; $x--) {
+ array_pop($this->stack);
+ }
+
+ } else {
+ $category = $this->getElementCategory($node);
+
+ if ($category !== self::SPECIAL && $category !== self::SCOPING) {
+ /* Otherwise, if node is in neither the formatting
+ category nor the phrasing category, then this is a
+ parse error. Stop this algorithm. The end tag token
+ is ignored. */
+ return false;
+ }
+ }
+ }
+ break;
+ }
+ break;
+ }
+ }
+
+ private function inTable($token)
+ {
+ $clear = array('html', 'table');
+
+ /* A character token that is one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE */
+ if ($token['type'] === HTML5::CHARACTR &&
+ preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])
+ ) {
+ /* Append the character to the current node. */
+ $text = $this->dom->createTextNode($token['data']);
+ end($this->stack)->appendChild($text);
+
+ /* A comment token */
+ } elseif ($token['type'] === HTML5::COMMENT) {
+ /* Append a Comment node to the current node with the data
+ attribute set to the data given in the comment token. */
+ $comment = $this->dom->createComment($token['data']);
+ end($this->stack)->appendChild($comment);
+
+ /* A start tag whose tag name is "caption" */
+ } elseif ($token['type'] === HTML5::STARTTAG &&
+ $token['name'] === 'caption'
+ ) {
+ /* Clear the stack back to a table context. */
+ $this->clearStackToTableContext($clear);
+
+ /* Insert a marker at the end of the list of active
+ formatting elements. */
+ $this->a_formatting[] = self::MARKER;
+
+ /* Insert an HTML element for the token, then switch the
+ insertion mode to "in caption". */
+ $this->insertElement($token);
+ $this->mode = self::IN_CAPTION;
+
+ /* A start tag whose tag name is "colgroup" */
+ } elseif ($token['type'] === HTML5::STARTTAG &&
+ $token['name'] === 'colgroup'
+ ) {
+ /* Clear the stack back to a table context. */
+ $this->clearStackToTableContext($clear);
+
+ /* Insert an HTML element for the token, then switch the
+ insertion mode to "in column group". */
+ $this->insertElement($token);
+ $this->mode = self::IN_CGROUP;
+
+ /* A start tag whose tag name is "col" */
+ } elseif ($token['type'] === HTML5::STARTTAG &&
+ $token['name'] === 'col'
+ ) {
+ $this->inTable(
+ array(
+ 'name' => 'colgroup',
+ 'type' => HTML5::STARTTAG,
+ 'attr' => array()
+ )
+ );
+
+ $this->inColumnGroup($token);
+
+ /* A start tag whose tag name is one of: "tbody", "tfoot", "thead" */
+ } elseif ($token['type'] === HTML5::STARTTAG && in_array(
+ $token['name'],
+ array('tbody', 'tfoot', 'thead')
+ )
+ ) {
+ /* Clear the stack back to a table context. */
+ $this->clearStackToTableContext($clear);
+
+ /* Insert an HTML element for the token, then switch the insertion
+ mode to "in table body". */
+ $this->insertElement($token);
+ $this->mode = self::IN_TBODY;
+
+ /* A start tag whose tag name is one of: "td", "th", "tr" */
+ } elseif ($token['type'] === HTML5::STARTTAG &&
+ in_array($token['name'], array('td', 'th', 'tr'))
+ ) {
+ /* Act as if a start tag token with the tag name "tbody" had been
+ seen, then reprocess the current token. */
+ $this->inTable(
+ array(
+ 'name' => 'tbody',
+ 'type' => HTML5::STARTTAG,
+ 'attr' => array()
+ )
+ );
+
+ return $this->inTableBody($token);
+
+ /* A start tag whose tag name is "table" */
+ } elseif ($token['type'] === HTML5::STARTTAG &&
+ $token['name'] === 'table'
+ ) {
+ /* Parse error. Act as if an end tag token with the tag name "table"
+ had been seen, then, if that token wasn't ignored, reprocess the
+ current token. */
+ $this->inTable(
+ array(
+ 'name' => 'table',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+
+ return $this->mainPhase($token);
+
+ /* An end tag whose tag name is "table" */
+ } elseif ($token['type'] === HTML5::ENDTAG &&
+ $token['name'] === 'table'
+ ) {
+ /* If the stack of open elements does not have an element in table
+ scope with the same tag name as the token, this is a parse error.
+ Ignore the token. (innerHTML case) */
+ if (!$this->elementInScope($token['name'], true)) {
+ return false;
+
+ /* Otherwise: */
+ } else {
+ /* Generate implied end tags. */
+ $this->generateImpliedEndTags();
+
+ /* Now, if the current node is not a table element, then this
+ is a parse error. */
+ // w/e
+
+ /* Pop elements from this stack until a table element has been
+ popped from the stack. */
+ while (true) {
+ $current = end($this->stack)->nodeName;
+ array_pop($this->stack);
+
+ if ($current === 'table') {
+ break;
+ }
+ }
+
+ /* Reset the insertion mode appropriately. */
+ $this->resetInsertionMode();
+ }
+
+ /* An end tag whose tag name is one of: "body", "caption", "col",
+ "colgroup", "html", "tbody", "td", "tfoot", "th", "thead", "tr" */
+ } elseif ($token['type'] === HTML5::ENDTAG && in_array(
+ $token['name'],
+ array(
+ 'body',
+ 'caption',
+ 'col',
+ 'colgroup',
+ 'html',
+ 'tbody',
+ 'td',
+ 'tfoot',
+ 'th',
+ 'thead',
+ 'tr'
+ )
+ )
+ ) {
+ // Parse error. Ignore the token.
+
+ /* Anything else */
+ } else {
+ /* Parse error. Process the token as if the insertion mode was "in
+ body", with the following exception: */
+
+ /* If the current node is a table, tbody, tfoot, thead, or tr
+ element, then, whenever a node would be inserted into the current
+ node, it must instead be inserted into the foster parent element. */
+ if (in_array(
+ end($this->stack)->nodeName,
+ array('table', 'tbody', 'tfoot', 'thead', 'tr')
+ )
+ ) {
+ /* The foster parent element is the parent element of the last
+ table element in the stack of open elements, if there is a
+ table element and it has such a parent element. If there is no
+ table element in the stack of open elements (innerHTML case),
+ then the foster parent element is the first element in the
+ stack of open elements (the html element). Otherwise, if there
+ is a table element in the stack of open elements, but the last
+ table element in the stack of open elements has no parent, or
+ its parent node is not an element, then the foster parent
+ element is the element before the last table element in the
+ stack of open elements. */
+ for ($n = count($this->stack) - 1; $n >= 0; $n--) {
+ if ($this->stack[$n]->nodeName === 'table') {
+ $table = $this->stack[$n];
+ break;
+ }
+ }
+
+ if (isset($table) && $table->parentNode !== null) {
+ $this->foster_parent = $table->parentNode;
+
+ } elseif (!isset($table)) {
+ $this->foster_parent = $this->stack[0];
+
+ } elseif (isset($table) && ($table->parentNode === null ||
+ $table->parentNode->nodeType !== XML_ELEMENT_NODE)
+ ) {
+ $this->foster_parent = $this->stack[$n - 1];
+ }
+ }
+
+ $this->inBody($token);
+ }
+ }
+
+ private function inCaption($token)
+ {
+ /* An end tag whose tag name is "caption" */
+ if ($token['type'] === HTML5::ENDTAG && $token['name'] === 'caption') {
+ /* If the stack of open elements does not have an element in table
+ scope with the same tag name as the token, this is a parse error.
+ Ignore the token. (innerHTML case) */
+ if (!$this->elementInScope($token['name'], true)) {
+ // Ignore
+
+ /* Otherwise: */
+ } else {
+ /* Generate implied end tags. */
+ $this->generateImpliedEndTags();
+
+ /* Now, if the current node is not a caption element, then this
+ is a parse error. */
+ // w/e
+
+ /* Pop elements from this stack until a caption element has
+ been popped from the stack. */
+ while (true) {
+ $node = end($this->stack)->nodeName;
+ array_pop($this->stack);
+
+ if ($node === 'caption') {
+ break;
+ }
+ }
+
+ /* Clear the list of active formatting elements up to the last
+ marker. */
+ $this->clearTheActiveFormattingElementsUpToTheLastMarker();
+
+ /* Switch the insertion mode to "in table". */
+ $this->mode = self::IN_TABLE;
+ }
+
+ /* A start tag whose tag name is one of: "caption", "col", "colgroup",
+ "tbody", "td", "tfoot", "th", "thead", "tr", or an end tag whose tag
+ name is "table" */
+ } elseif (($token['type'] === HTML5::STARTTAG && in_array(
+ $token['name'],
+ array(
+ 'caption',
+ 'col',
+ 'colgroup',
+ 'tbody',
+ 'td',
+ 'tfoot',
+ 'th',
+ 'thead',
+ 'tr'
+ )
+ )) || ($token['type'] === HTML5::ENDTAG &&
+ $token['name'] === 'table')
+ ) {
+ /* Parse error. Act as if an end tag with the tag name "caption"
+ had been seen, then, if that token wasn't ignored, reprocess the
+ current token. */
+ $this->inCaption(
+ array(
+ 'name' => 'caption',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+
+ return $this->inTable($token);
+
+ /* An end tag whose tag name is one of: "body", "col", "colgroup",
+ "html", "tbody", "td", "tfoot", "th", "thead", "tr" */
+ } elseif ($token['type'] === HTML5::ENDTAG && in_array(
+ $token['name'],
+ array(
+ 'body',
+ 'col',
+ 'colgroup',
+ 'html',
+ 'tbody',
+ 'tfoot',
+ 'th',
+ 'thead',
+ 'tr'
+ )
+ )
+ ) {
+ // Parse error. Ignore the token.
+
+ /* Anything else */
+ } else {
+ /* Process the token as if the insertion mode was "in body". */
+ $this->inBody($token);
+ }
+ }
+
+ private function inColumnGroup($token)
+ {
+ /* A character token that is one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE */
+ if ($token['type'] === HTML5::CHARACTR &&
+ preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])
+ ) {
+ /* Append the character to the current node. */
+ $text = $this->dom->createTextNode($token['data']);
+ end($this->stack)->appendChild($text);
+
+ /* A comment token */
+ } elseif ($token['type'] === HTML5::COMMENT) {
+ /* Append a Comment node to the current node with the data
+ attribute set to the data given in the comment token. */
+ $comment = $this->dom->createComment($token['data']);
+ end($this->stack)->appendChild($comment);
+
+ /* A start tag whose tag name is "col" */
+ } elseif ($token['type'] === HTML5::STARTTAG && $token['name'] === 'col') {
+ /* Insert a col element for the token. Immediately pop the current
+ node off the stack of open elements. */
+ $this->insertElement($token);
+ array_pop($this->stack);
+
+ /* An end tag whose tag name is "colgroup" */
+ } elseif ($token['type'] === HTML5::ENDTAG &&
+ $token['name'] === 'colgroup'
+ ) {
+ /* If the current node is the root html element, then this is a
+ parse error, ignore the token. (innerHTML case) */
+ if (end($this->stack)->nodeName === 'html') {
+ // Ignore
+
+ /* Otherwise, pop the current node (which will be a colgroup
+ element) from the stack of open elements. Switch the insertion
+ mode to "in table". */
+ } else {
+ array_pop($this->stack);
+ $this->mode = self::IN_TABLE;
+ }
+
+ /* An end tag whose tag name is "col" */
+ } elseif ($token['type'] === HTML5::ENDTAG && $token['name'] === 'col') {
+ /* Parse error. Ignore the token. */
+
+ /* Anything else */
+ } else {
+ /* Act as if an end tag with the tag name "colgroup" had been seen,
+ and then, if that token wasn't ignored, reprocess the current token. */
+ $this->inColumnGroup(
+ array(
+ 'name' => 'colgroup',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+
+ return $this->inTable($token);
+ }
+ }
+
+ private function inTableBody($token)
+ {
+ $clear = array('tbody', 'tfoot', 'thead', 'html');
+
+ /* A start tag whose tag name is "tr" */
+ if ($token['type'] === HTML5::STARTTAG && $token['name'] === 'tr') {
+ /* Clear the stack back to a table body context. */
+ $this->clearStackToTableContext($clear);
+
+ /* Insert a tr element for the token, then switch the insertion
+ mode to "in row". */
+ $this->insertElement($token);
+ $this->mode = self::IN_ROW;
+
+ /* A start tag whose tag name is one of: "th", "td" */
+ } elseif ($token['type'] === HTML5::STARTTAG &&
+ ($token['name'] === 'th' || $token['name'] === 'td')
+ ) {
+ /* Parse error. Act as if a start tag with the tag name "tr" had
+ been seen, then reprocess the current token. */
+ $this->inTableBody(
+ array(
+ 'name' => 'tr',
+ 'type' => HTML5::STARTTAG,
+ 'attr' => array()
+ )
+ );
+
+ return $this->inRow($token);
+
+ /* An end tag whose tag name is one of: "tbody", "tfoot", "thead" */
+ } elseif ($token['type'] === HTML5::ENDTAG &&
+ in_array($token['name'], array('tbody', 'tfoot', 'thead'))
+ ) {
+ /* If the stack of open elements does not have an element in table
+ scope with the same tag name as the token, this is a parse error.
+ Ignore the token. */
+ if (!$this->elementInScope($token['name'], true)) {
+ // Ignore
+
+ /* Otherwise: */
+ } else {
+ /* Clear the stack back to a table body context. */
+ $this->clearStackToTableContext($clear);
+
+ /* Pop the current node from the stack of open elements. Switch
+ the insertion mode to "in table". */
+ array_pop($this->stack);
+ $this->mode = self::IN_TABLE;
+ }
+
+ /* A start tag whose tag name is one of: "caption", "col", "colgroup",
+ "tbody", "tfoot", "thead", or an end tag whose tag name is "table" */
+ } elseif (($token['type'] === HTML5::STARTTAG && in_array(
+ $token['name'],
+ array('caption', 'col', 'colgroup', 'tbody', 'tfoor', 'thead')
+ )) ||
+ ($token['type'] === HTML5::STARTTAG && $token['name'] === 'table')
+ ) {
+ /* If the stack of open elements does not have a tbody, thead, or
+ tfoot element in table scope, this is a parse error. Ignore the
+ token. (innerHTML case) */
+ if (!$this->elementInScope(array('tbody', 'thead', 'tfoot'), true)) {
+ // Ignore.
+
+ /* Otherwise: */
+ } else {
+ /* Clear the stack back to a table body context. */
+ $this->clearStackToTableContext($clear);
+
+ /* Act as if an end tag with the same tag name as the current
+ node ("tbody", "tfoot", or "thead") had been seen, then
+ reprocess the current token. */
+ $this->inTableBody(
+ array(
+ 'name' => end($this->stack)->nodeName,
+ 'type' => HTML5::ENDTAG
+ )
+ );
+
+ return $this->mainPhase($token);
+ }
+
+ /* An end tag whose tag name is one of: "body", "caption", "col",
+ "colgroup", "html", "td", "th", "tr" */
+ } elseif ($token['type'] === HTML5::ENDTAG && in_array(
+ $token['name'],
+ array('body', 'caption', 'col', 'colgroup', 'html', 'td', 'th', 'tr')
+ )
+ ) {
+ /* Parse error. Ignore the token. */
+
+ /* Anything else */
+ } else {
+ /* Process the token as if the insertion mode was "in table". */
+ $this->inTable($token);
+ }
+ }
+
+ private function inRow($token)
+ {
+ $clear = array('tr', 'html');
+
+ /* A start tag whose tag name is one of: "th", "td" */
+ if ($token['type'] === HTML5::STARTTAG &&
+ ($token['name'] === 'th' || $token['name'] === 'td')
+ ) {
+ /* Clear the stack back to a table row context. */
+ $this->clearStackToTableContext($clear);
+
+ /* Insert an HTML element for the token, then switch the insertion
+ mode to "in cell". */
+ $this->insertElement($token);
+ $this->mode = self::IN_CELL;
+
+ /* Insert a marker at the end of the list of active formatting
+ elements. */
+ $this->a_formatting[] = self::MARKER;
+
+ /* An end tag whose tag name is "tr" */
+ } elseif ($token['type'] === HTML5::ENDTAG && $token['name'] === 'tr') {
+ /* If the stack of open elements does not have an element in table
+ scope with the same tag name as the token, this is a parse error.
+ Ignore the token. (innerHTML case) */
+ if (!$this->elementInScope($token['name'], true)) {
+ // Ignore.
+
+ /* Otherwise: */
+ } else {
+ /* Clear the stack back to a table row context. */
+ $this->clearStackToTableContext($clear);
+
+ /* Pop the current node (which will be a tr element) from the
+ stack of open elements. Switch the insertion mode to "in table
+ body". */
+ array_pop($this->stack);
+ $this->mode = self::IN_TBODY;
+ }
+
+ /* A start tag whose tag name is one of: "caption", "col", "colgroup",
+ "tbody", "tfoot", "thead", "tr" or an end tag whose tag name is "table" */
+ } elseif ($token['type'] === HTML5::STARTTAG && in_array(
+ $token['name'],
+ array('caption', 'col', 'colgroup', 'tbody', 'tfoot', 'thead', 'tr')
+ )
+ ) {
+ /* Act as if an end tag with the tag name "tr" had been seen, then,
+ if that token wasn't ignored, reprocess the current token. */
+ $this->inRow(
+ array(
+ 'name' => 'tr',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+
+ return $this->inCell($token);
+
+ /* An end tag whose tag name is one of: "tbody", "tfoot", "thead" */
+ } elseif ($token['type'] === HTML5::ENDTAG &&
+ in_array($token['name'], array('tbody', 'tfoot', 'thead'))
+ ) {
+ /* If the stack of open elements does not have an element in table
+ scope with the same tag name as the token, this is a parse error.
+ Ignore the token. */
+ if (!$this->elementInScope($token['name'], true)) {
+ // Ignore.
+
+ /* Otherwise: */
+ } else {
+ /* Otherwise, act as if an end tag with the tag name "tr" had
+ been seen, then reprocess the current token. */
+ $this->inRow(
+ array(
+ 'name' => 'tr',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+
+ return $this->inCell($token);
+ }
+
+ /* An end tag whose tag name is one of: "body", "caption", "col",
+ "colgroup", "html", "td", "th" */
+ } elseif ($token['type'] === HTML5::ENDTAG && in_array(
+ $token['name'],
+ array('body', 'caption', 'col', 'colgroup', 'html', 'td', 'th', 'tr')
+ )
+ ) {
+ /* Parse error. Ignore the token. */
+
+ /* Anything else */
+ } else {
+ /* Process the token as if the insertion mode was "in table". */
+ $this->inTable($token);
+ }
+ }
+
+ private function inCell($token)
+ {
+ /* An end tag whose tag name is one of: "td", "th" */
+ if ($token['type'] === HTML5::ENDTAG &&
+ ($token['name'] === 'td' || $token['name'] === 'th')
+ ) {
+ /* If the stack of open elements does not have an element in table
+ scope with the same tag name as that of the token, then this is a
+ parse error and the token must be ignored. */
+ if (!$this->elementInScope($token['name'], true)) {
+ // Ignore.
+
+ /* Otherwise: */
+ } else {
+ /* Generate implied end tags, except for elements with the same
+ tag name as the token. */
+ $this->generateImpliedEndTags(array($token['name']));
+
+ /* Now, if the current node is not an element with the same tag
+ name as the token, then this is a parse error. */
+ // k
+
+ /* Pop elements from this stack until an element with the same
+ tag name as the token has been popped from the stack. */
+ while (true) {
+ $node = end($this->stack)->nodeName;
+ array_pop($this->stack);
+
+ if ($node === $token['name']) {
+ break;
+ }
+ }
+
+ /* Clear the list of active formatting elements up to the last
+ marker. */
+ $this->clearTheActiveFormattingElementsUpToTheLastMarker();
+
+ /* Switch the insertion mode to "in row". (The current node
+ will be a tr element at this point.) */
+ $this->mode = self::IN_ROW;
+ }
+
+ /* A start tag whose tag name is one of: "caption", "col", "colgroup",
+ "tbody", "td", "tfoot", "th", "thead", "tr" */
+ } elseif ($token['type'] === HTML5::STARTTAG && in_array(
+ $token['name'],
+ array(
+ 'caption',
+ 'col',
+ 'colgroup',
+ 'tbody',
+ 'td',
+ 'tfoot',
+ 'th',
+ 'thead',
+ 'tr'
+ )
+ )
+ ) {
+ /* If the stack of open elements does not have a td or th element
+ in table scope, then this is a parse error; ignore the token.
+ (innerHTML case) */
+ if (!$this->elementInScope(array('td', 'th'), true)) {
+ // Ignore.
+
+ /* Otherwise, close the cell (see below) and reprocess the current
+ token. */
+ } else {
+ $this->closeCell();
+ return $this->inRow($token);
+ }
+
+ /* A start tag whose tag name is one of: "caption", "col", "colgroup",
+ "tbody", "td", "tfoot", "th", "thead", "tr" */
+ } elseif ($token['type'] === HTML5::STARTTAG && in_array(
+ $token['name'],
+ array(
+ 'caption',
+ 'col',
+ 'colgroup',
+ 'tbody',
+ 'td',
+ 'tfoot',
+ 'th',
+ 'thead',
+ 'tr'
+ )
+ )
+ ) {
+ /* If the stack of open elements does not have a td or th element
+ in table scope, then this is a parse error; ignore the token.
+ (innerHTML case) */
+ if (!$this->elementInScope(array('td', 'th'), true)) {
+ // Ignore.
+
+ /* Otherwise, close the cell (see below) and reprocess the current
+ token. */
+ } else {
+ $this->closeCell();
+ return $this->inRow($token);
+ }
+
+ /* An end tag whose tag name is one of: "body", "caption", "col",
+ "colgroup", "html" */
+ } elseif ($token['type'] === HTML5::ENDTAG && in_array(
+ $token['name'],
+ array('body', 'caption', 'col', 'colgroup', 'html')
+ )
+ ) {
+ /* Parse error. Ignore the token. */
+
+ /* An end tag whose tag name is one of: "table", "tbody", "tfoot",
+ "thead", "tr" */
+ } elseif ($token['type'] === HTML5::ENDTAG && in_array(
+ $token['name'],
+ array('table', 'tbody', 'tfoot', 'thead', 'tr')
+ )
+ ) {
+ /* If the stack of open elements does not have an element in table
+ scope with the same tag name as that of the token (which can only
+ happen for "tbody", "tfoot" and "thead", or, in the innerHTML case),
+ then this is a parse error and the token must be ignored. */
+ if (!$this->elementInScope($token['name'], true)) {
+ // Ignore.
+
+ /* Otherwise, close the cell (see below) and reprocess the current
+ token. */
+ } else {
+ $this->closeCell();
+ return $this->inRow($token);
+ }
+
+ /* Anything else */
+ } else {
+ /* Process the token as if the insertion mode was "in body". */
+ $this->inBody($token);
+ }
+ }
+
+ private function inSelect($token)
+ {
+ /* Handle the token as follows: */
+
+ /* A character token */
+ if ($token['type'] === HTML5::CHARACTR) {
+ /* Append the token's character to the current node. */
+ $this->insertText($token['data']);
+
+ /* A comment token */
+ } elseif ($token['type'] === HTML5::COMMENT) {
+ /* Append a Comment node to the current node with the data
+ attribute set to the data given in the comment token. */
+ $this->insertComment($token['data']);
+
+ /* A start tag token whose tag name is "option" */
+ } elseif ($token['type'] === HTML5::STARTTAG &&
+ $token['name'] === 'option'
+ ) {
+ /* If the current node is an option element, act as if an end tag
+ with the tag name "option" had been seen. */
+ if (end($this->stack)->nodeName === 'option') {
+ $this->inSelect(
+ array(
+ 'name' => 'option',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+ }
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+
+ /* A start tag token whose tag name is "optgroup" */
+ } elseif ($token['type'] === HTML5::STARTTAG &&
+ $token['name'] === 'optgroup'
+ ) {
+ /* If the current node is an option element, act as if an end tag
+ with the tag name "option" had been seen. */
+ if (end($this->stack)->nodeName === 'option') {
+ $this->inSelect(
+ array(
+ 'name' => 'option',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+ }
+
+ /* If the current node is an optgroup element, act as if an end tag
+ with the tag name "optgroup" had been seen. */
+ if (end($this->stack)->nodeName === 'optgroup') {
+ $this->inSelect(
+ array(
+ 'name' => 'optgroup',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+ }
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+
+ /* An end tag token whose tag name is "optgroup" */
+ } elseif ($token['type'] === HTML5::ENDTAG &&
+ $token['name'] === 'optgroup'
+ ) {
+ /* First, if the current node is an option element, and the node
+ immediately before it in the stack of open elements is an optgroup
+ element, then act as if an end tag with the tag name "option" had
+ been seen. */
+ $elements_in_stack = count($this->stack);
+
+ if ($this->stack[$elements_in_stack - 1]->nodeName === 'option' &&
+ $this->stack[$elements_in_stack - 2]->nodeName === 'optgroup'
+ ) {
+ $this->inSelect(
+ array(
+ 'name' => 'option',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+ }
+
+ /* If the current node is an optgroup element, then pop that node
+ from the stack of open elements. Otherwise, this is a parse error,
+ ignore the token. */
+ if ($this->stack[$elements_in_stack - 1] === 'optgroup') {
+ array_pop($this->stack);
+ }
+
+ /* An end tag token whose tag name is "option" */
+ } elseif ($token['type'] === HTML5::ENDTAG &&
+ $token['name'] === 'option'
+ ) {
+ /* If the current node is an option element, then pop that node
+ from the stack of open elements. Otherwise, this is a parse error,
+ ignore the token. */
+ if (end($this->stack)->nodeName === 'option') {
+ array_pop($this->stack);
+ }
+
+ /* An end tag whose tag name is "select" */
+ } elseif ($token['type'] === HTML5::ENDTAG &&
+ $token['name'] === 'select'
+ ) {
+ /* If the stack of open elements does not have an element in table
+ scope with the same tag name as the token, this is a parse error.
+ Ignore the token. (innerHTML case) */
+ if (!$this->elementInScope($token['name'], true)) {
+ // w/e
+
+ /* Otherwise: */
+ } else {
+ /* Pop elements from the stack of open elements until a select
+ element has been popped from the stack. */
+ while (true) {
+ $current = end($this->stack)->nodeName;
+ array_pop($this->stack);
+
+ if ($current === 'select') {
+ break;
+ }
+ }
+
+ /* Reset the insertion mode appropriately. */
+ $this->resetInsertionMode();
+ }
+
+ /* A start tag whose tag name is "select" */
+ } elseif ($token['name'] === 'select' &&
+ $token['type'] === HTML5::STARTTAG
+ ) {
+ /* Parse error. Act as if the token had been an end tag with the
+ tag name "select" instead. */
+ $this->inSelect(
+ array(
+ 'name' => 'select',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+
+ /* An end tag whose tag name is one of: "caption", "table", "tbody",
+ "tfoot", "thead", "tr", "td", "th" */
+ } elseif (in_array(
+ $token['name'],
+ array(
+ 'caption',
+ 'table',
+ 'tbody',
+ 'tfoot',
+ 'thead',
+ 'tr',
+ 'td',
+ 'th'
+ )
+ ) && $token['type'] === HTML5::ENDTAG
+ ) {
+ /* Parse error. */
+ // w/e
+
+ /* If the stack of open elements has an element in table scope with
+ the same tag name as that of the token, then act as if an end tag
+ with the tag name "select" had been seen, and reprocess the token.
+ Otherwise, ignore the token. */
+ if ($this->elementInScope($token['name'], true)) {
+ $this->inSelect(
+ array(
+ 'name' => 'select',
+ 'type' => HTML5::ENDTAG
+ )
+ );
+
+ $this->mainPhase($token);
+ }
+
+ /* Anything else */
+ } else {
+ /* Parse error. Ignore the token. */
+ }
+ }
+
+ private function afterBody($token)
+ {
+ /* Handle the token as follows: */
+
+ /* A character token that is one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE */
+ if ($token['type'] === HTML5::CHARACTR &&
+ preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])
+ ) {
+ /* Process the token as it would be processed if the insertion mode
+ was "in body". */
+ $this->inBody($token);
+
+ /* A comment token */
+ } elseif ($token['type'] === HTML5::COMMENT) {
+ /* Append a Comment node to the first element in the stack of open
+ elements (the html element), with the data attribute set to the
+ data given in the comment token. */
+ $comment = $this->dom->createComment($token['data']);
+ $this->stack[0]->appendChild($comment);
+
+ /* An end tag with the tag name "html" */
+ } elseif ($token['type'] === HTML5::ENDTAG && $token['name'] === 'html') {
+ /* If the parser was originally created in order to handle the
+ setting of an element's innerHTML attribute, this is a parse error;
+ ignore the token. (The element will be an html element in this
+ case.) (innerHTML case) */
+
+ /* Otherwise, switch to the trailing end phase. */
+ $this->phase = self::END_PHASE;
+
+ /* Anything else */
+ } else {
+ /* Parse error. Set the insertion mode to "in body" and reprocess
+ the token. */
+ $this->mode = self::IN_BODY;
+ return $this->inBody($token);
+ }
+ }
+
+ private function inFrameset($token)
+ {
+ /* Handle the token as follows: */
+
+ /* A character token that is one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ U+000D CARRIAGE RETURN (CR), or U+0020 SPACE */
+ if ($token['type'] === HTML5::CHARACTR &&
+ preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])
+ ) {
+ /* Append the character to the current node. */
+ $this->insertText($token['data']);
+
+ /* A comment token */
+ } elseif ($token['type'] === HTML5::COMMENT) {
+ /* Append a Comment node to the current node with the data
+ attribute set to the data given in the comment token. */
+ $this->insertComment($token['data']);
+
+ /* A start tag with the tag name "frameset" */
+ } elseif ($token['name'] === 'frameset' &&
+ $token['type'] === HTML5::STARTTAG
+ ) {
+ $this->insertElement($token);
+
+ /* An end tag with the tag name "frameset" */
+ } elseif ($token['name'] === 'frameset' &&
+ $token['type'] === HTML5::ENDTAG
+ ) {
+ /* If the current node is the root html element, then this is a
+ parse error; ignore the token. (innerHTML case) */
+ if (end($this->stack)->nodeName === 'html') {
+ // Ignore
+
+ } else {
+ /* Otherwise, pop the current node from the stack of open
+ elements. */
+ array_pop($this->stack);
+
+ /* If the parser was not originally created in order to handle
+ the setting of an element's innerHTML attribute (innerHTML case),
+ and the current node is no longer a frameset element, then change
+ the insertion mode to "after frameset". */
+ $this->mode = self::AFTR_FRAME;
+ }
+
+ /* A start tag with the tag name "frame" */
+ } elseif ($token['name'] === 'frame' &&
+ $token['type'] === HTML5::STARTTAG
+ ) {
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+
+ /* Immediately pop the current node off the stack of open elements. */
+ array_pop($this->stack);
+
+ /* A start tag with the tag name "noframes" */
+ } elseif ($token['name'] === 'noframes' &&
+ $token['type'] === HTML5::STARTTAG
+ ) {
+ /* Process the token as if the insertion mode had been "in body". */
+ $this->inBody($token);
+
+ /* Anything else */
+ } else {
+ /* Parse error. Ignore the token. */
+ }
+ }
+
+ private function afterFrameset($token)
+ {
+ /* Handle the token as follows: */
+
+ /* A character token that is one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ U+000D CARRIAGE RETURN (CR), or U+0020 SPACE */
+ if ($token['type'] === HTML5::CHARACTR &&
+ preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])
+ ) {
+ /* Append the character to the current node. */
+ $this->insertText($token['data']);
+
+ /* A comment token */
+ } elseif ($token['type'] === HTML5::COMMENT) {
+ /* Append a Comment node to the current node with the data
+ attribute set to the data given in the comment token. */
+ $this->insertComment($token['data']);
+
+ /* An end tag with the tag name "html" */
+ } elseif ($token['name'] === 'html' &&
+ $token['type'] === HTML5::ENDTAG
+ ) {
+ /* Switch to the trailing end phase. */
+ $this->phase = self::END_PHASE;
+
+ /* A start tag with the tag name "noframes" */
+ } elseif ($token['name'] === 'noframes' &&
+ $token['type'] === HTML5::STARTTAG
+ ) {
+ /* Process the token as if the insertion mode had been "in body". */
+ $this->inBody($token);
+
+ /* Anything else */
+ } else {
+ /* Parse error. Ignore the token. */
+ }
+ }
+
+ private function trailingEndPhase($token)
+ {
+ /* After the main phase, as each token is emitted from the tokenisation
+ stage, it must be processed as described in this section. */
+
+ /* A DOCTYPE token */
+ if ($token['type'] === HTML5::DOCTYPE) {
+ // Parse error. Ignore the token.
+
+ /* A comment token */
+ } elseif ($token['type'] === HTML5::COMMENT) {
+ /* Append a Comment node to the Document object with the data
+ attribute set to the data given in the comment token. */
+ $comment = $this->dom->createComment($token['data']);
+ $this->dom->appendChild($comment);
+
+ /* A character token that is one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE */
+ } elseif ($token['type'] === HTML5::CHARACTR &&
+ preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])
+ ) {
+ /* Process the token as it would be processed in the main phase. */
+ $this->mainPhase($token);
+
+ /* A character token that is not one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE. Or a start tag token. Or an end tag token. */
+ } elseif (($token['type'] === HTML5::CHARACTR &&
+ preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])) ||
+ $token['type'] === HTML5::STARTTAG || $token['type'] === HTML5::ENDTAG
+ ) {
+ /* Parse error. Switch back to the main phase and reprocess the
+ token. */
+ $this->phase = self::MAIN_PHASE;
+ return $this->mainPhase($token);
+
+ /* An end-of-file token */
+ } elseif ($token['type'] === HTML5::EOF) {
+ /* OMG DONE!! */
+ }
+ }
+
+ private function insertElement($token, $append = true, $check = false)
+ {
+ // Proprietary workaround for libxml2's limitations with tag names
+ if ($check) {
+ // Slightly modified HTML5 tag-name modification,
+ // removing anything that's not an ASCII letter, digit, or hyphen
+ $token['name'] = preg_replace('/[^a-z0-9-]/i', '', $token['name']);
+ // Remove leading hyphens and numbers
+ $token['name'] = ltrim($token['name'], '-0..9');
+ // In theory, this should ever be needed, but just in case
+ if ($token['name'] === '') {
+ $token['name'] = 'span';
+ } // arbitrary generic choice
+ }
+
+ $el = $this->dom->createElement($token['name']);
+
+ foreach ($token['attr'] as $attr) {
+ if (!$el->hasAttribute($attr['name'])) {
+ $el->setAttribute($attr['name'], $attr['value']);
+ }
+ }
+
+ $this->appendToRealParent($el);
+ $this->stack[] = $el;
+
+ return $el;
+ }
+
+ private function insertText($data)
+ {
+ $text = $this->dom->createTextNode($data);
+ $this->appendToRealParent($text);
+ }
+
+ private function insertComment($data)
+ {
+ $comment = $this->dom->createComment($data);
+ $this->appendToRealParent($comment);
+ }
+
+ private function appendToRealParent($node)
+ {
+ if ($this->foster_parent === null) {
+ end($this->stack)->appendChild($node);
+
+ } elseif ($this->foster_parent !== null) {
+ /* If the foster parent element is the parent element of the
+ last table element in the stack of open elements, then the new
+ node must be inserted immediately before the last table element
+ in the stack of open elements in the foster parent element;
+ otherwise, the new node must be appended to the foster parent
+ element. */
+ for ($n = count($this->stack) - 1; $n >= 0; $n--) {
+ if ($this->stack[$n]->nodeName === 'table' &&
+ $this->stack[$n]->parentNode !== null
+ ) {
+ $table = $this->stack[$n];
+ break;
+ }
+ }
+
+ if (isset($table) && $this->foster_parent->isSameNode($table->parentNode)) {
+ $this->foster_parent->insertBefore($node, $table);
+ } else {
+ $this->foster_parent->appendChild($node);
+ }
+
+ $this->foster_parent = null;
+ }
+ }
+
+ private function elementInScope($el, $table = false)
+ {
+ if (is_array($el)) {
+ foreach ($el as $element) {
+ if ($this->elementInScope($element, $table)) {
+ return true;
+ }
+ }
+
+ return false;
+ }
+
+ $leng = count($this->stack);
+
+ for ($n = 0; $n < $leng; $n++) {
+ /* 1. Initialise node to be the current node (the bottommost node of
+ the stack). */
+ $node = $this->stack[$leng - 1 - $n];
+
+ if ($node->tagName === $el) {
+ /* 2. If node is the target node, terminate in a match state. */
+ return true;
+
+ } elseif ($node->tagName === 'table') {
+ /* 3. Otherwise, if node is a table element, terminate in a failure
+ state. */
+ return false;
+
+ } elseif ($table === true && in_array(
+ $node->tagName,
+ array(
+ 'caption',
+ 'td',
+ 'th',
+ 'button',
+ 'marquee',
+ 'object'
+ )
+ )
+ ) {
+ /* 4. Otherwise, if the algorithm is the "has an element in scope"
+ variant (rather than the "has an element in table scope" variant),
+ and node is one of the following, terminate in a failure state. */
+ return false;
+
+ } elseif ($node === $node->ownerDocument->documentElement) {
+ /* 5. Otherwise, if node is an html element (root element), terminate
+ in a failure state. (This can only happen if the node is the topmost
+ node of the stack of open elements, and prevents the next step from
+ being invoked if there are no more elements in the stack.) */
+ return false;
+ }
+
+ /* Otherwise, set node to the previous entry in the stack of open
+ elements and return to step 2. (This will never fail, since the loop
+ will always terminate in the previous step if the top of the stack
+ is reached.) */
+ }
+ }
+
+ private function reconstructActiveFormattingElements()
+ {
+ /* 1. If there are no entries in the list of active formatting elements,
+ then there is nothing to reconstruct; stop this algorithm. */
+ $formatting_elements = count($this->a_formatting);
+
+ if ($formatting_elements === 0) {
+ return false;
+ }
+
+ /* 3. Let entry be the last (most recently added) element in the list
+ of active formatting elements. */
+ $entry = end($this->a_formatting);
+
+ /* 2. If the last (most recently added) entry in the list of active
+ formatting elements is a marker, or if it is an element that is in the
+ stack of open elements, then there is nothing to reconstruct; stop this
+ algorithm. */
+ if ($entry === self::MARKER || in_array($entry, $this->stack, true)) {
+ return false;
+ }
+
+ for ($a = $formatting_elements - 1; $a >= 0; true) {
+ /* 4. If there are no entries before entry in the list of active
+ formatting elements, then jump to step 8. */
+ if ($a === 0) {
+ $step_seven = false;
+ break;
+ }
+
+ /* 5. Let entry be the entry one earlier than entry in the list of
+ active formatting elements. */
+ $a--;
+ $entry = $this->a_formatting[$a];
+
+ /* 6. If entry is neither a marker nor an element that is also in
+ thetack of open elements, go to step 4. */
+ if ($entry === self::MARKER || in_array($entry, $this->stack, true)) {
+ break;
+ }
+ }
+
+ while (true) {
+ /* 7. Let entry be the element one later than entry in the list of
+ active formatting elements. */
+ if (isset($step_seven) && $step_seven === true) {
+ $a++;
+ $entry = $this->a_formatting[$a];
+ }
+
+ /* 8. Perform a shallow clone of the element entry to obtain clone. */
+ $clone = $entry->cloneNode();
+
+ /* 9. Append clone to the current node and push it onto the stack
+ of open elements so that it is the new current node. */
+ end($this->stack)->appendChild($clone);
+ $this->stack[] = $clone;
+
+ /* 10. Replace the entry for entry in the list with an entry for
+ clone. */
+ $this->a_formatting[$a] = $clone;
+
+ /* 11. If the entry for clone in the list of active formatting
+ elements is not the last entry in the list, return to step 7. */
+ if (end($this->a_formatting) !== $clone) {
+ $step_seven = true;
+ } else {
+ break;
+ }
+ }
+ }
+
+ private function clearTheActiveFormattingElementsUpToTheLastMarker()
+ {
+ /* When the steps below require the UA to clear the list of active
+ formatting elements up to the last marker, the UA must perform the
+ following steps: */
+
+ while (true) {
+ /* 1. Let entry be the last (most recently added) entry in the list
+ of active formatting elements. */
+ $entry = end($this->a_formatting);
+
+ /* 2. Remove entry from the list of active formatting elements. */
+ array_pop($this->a_formatting);
+
+ /* 3. If entry was a marker, then stop the algorithm at this point.
+ The list has been cleared up to the last marker. */
+ if ($entry === self::MARKER) {
+ break;
+ }
+ }
+ }
+
+ private function generateImpliedEndTags($exclude = array())
+ {
+ /* When the steps below require the UA to generate implied end tags,
+ then, if the current node is a dd element, a dt element, an li element,
+ a p element, a td element, a th element, or a tr element, the UA must
+ act as if an end tag with the respective tag name had been seen and
+ then generate implied end tags again. */
+ $node = end($this->stack);
+ $elements = array_diff(array('dd', 'dt', 'li', 'p', 'td', 'th', 'tr'), $exclude);
+
+ while (in_array(end($this->stack)->nodeName, $elements)) {
+ array_pop($this->stack);
+ }
+ }
+
+ private function getElementCategory($node)
+ {
+ $name = $node->tagName;
+ if (in_array($name, $this->special)) {
+ return self::SPECIAL;
+ } elseif (in_array($name, $this->scoping)) {
+ return self::SCOPING;
+ } elseif (in_array($name, $this->formatting)) {
+ return self::FORMATTING;
+ } else {
+ return self::PHRASING;
+ }
+ }
+
+ private function clearStackToTableContext($elements)
+ {
+ /* When the steps above require the UA to clear the stack back to a
+ table context, it means that the UA must, while the current node is not
+ a table element or an html element, pop elements from the stack of open
+ elements. If this causes any elements to be popped from the stack, then
+ this is a parse error. */
+ while (true) {
+ $node = end($this->stack)->nodeName;
+
+ if (in_array($node, $elements)) {
+ break;
+ } else {
+ array_pop($this->stack);
+ }
+ }
+ }
+
+ private function resetInsertionMode()
+ {
+ /* 1. Let last be false. */
+ $last = false;
+ $leng = count($this->stack);
+
+ for ($n = $leng - 1; $n >= 0; $n--) {
+ /* 2. Let node be the last node in the stack of open elements. */
+ $node = $this->stack[$n];
+
+ /* 3. If node is the first node in the stack of open elements, then
+ set last to true. If the element whose innerHTML attribute is being
+ set is neither a td element nor a th element, then set node to the
+ element whose innerHTML attribute is being set. (innerHTML case) */
+ if ($this->stack[0]->isSameNode($node)) {
+ $last = true;
+ }
+
+ /* 4. If node is a select element, then switch the insertion mode to
+ "in select" and abort these steps. (innerHTML case) */
+ if ($node->nodeName === 'select') {
+ $this->mode = self::IN_SELECT;
+ break;
+
+ /* 5. If node is a td or th element, then switch the insertion mode
+ to "in cell" and abort these steps. */
+ } elseif ($node->nodeName === 'td' || $node->nodeName === 'th') {
+ $this->mode = self::IN_CELL;
+ break;
+
+ /* 6. If node is a tr element, then switch the insertion mode to
+ "in row" and abort these steps. */
+ } elseif ($node->nodeName === 'tr') {
+ $this->mode = self::IN_ROW;
+ break;
+
+ /* 7. If node is a tbody, thead, or tfoot element, then switch the
+ insertion mode to "in table body" and abort these steps. */
+ } elseif (in_array($node->nodeName, array('tbody', 'thead', 'tfoot'))) {
+ $this->mode = self::IN_TBODY;
+ break;
+
+ /* 8. If node is a caption element, then switch the insertion mode
+ to "in caption" and abort these steps. */
+ } elseif ($node->nodeName === 'caption') {
+ $this->mode = self::IN_CAPTION;
+ break;
+
+ /* 9. If node is a colgroup element, then switch the insertion mode
+ to "in column group" and abort these steps. (innerHTML case) */
+ } elseif ($node->nodeName === 'colgroup') {
+ $this->mode = self::IN_CGROUP;
+ break;
+
+ /* 10. If node is a table element, then switch the insertion mode
+ to "in table" and abort these steps. */
+ } elseif ($node->nodeName === 'table') {
+ $this->mode = self::IN_TABLE;
+ break;
+
+ /* 11. If node is a head element, then switch the insertion mode
+ to "in body" ("in body"! not "in head"!) and abort these steps.
+ (innerHTML case) */
+ } elseif ($node->nodeName === 'head') {
+ $this->mode = self::IN_BODY;
+ break;
+
+ /* 12. If node is a body element, then switch the insertion mode to
+ "in body" and abort these steps. */
+ } elseif ($node->nodeName === 'body') {
+ $this->mode = self::IN_BODY;
+ break;
+
+ /* 13. If node is a frameset element, then switch the insertion
+ mode to "in frameset" and abort these steps. (innerHTML case) */
+ } elseif ($node->nodeName === 'frameset') {
+ $this->mode = self::IN_FRAME;
+ break;
+
+ /* 14. If node is an html element, then: if the head element
+ pointer is null, switch the insertion mode to "before head",
+ otherwise, switch the insertion mode to "after head". In either
+ case, abort these steps. (innerHTML case) */
+ } elseif ($node->nodeName === 'html') {
+ $this->mode = ($this->head_pointer === null)
+ ? self::BEFOR_HEAD
+ : self::AFTER_HEAD;
+
+ break;
+
+ /* 15. If last is true, then set the insertion mode to "in body"
+ and abort these steps. (innerHTML case) */
+ } elseif ($last) {
+ $this->mode = self::IN_BODY;
+ break;
+ }
+ }
+ }
+
+ private function closeCell()
+ {
+ /* If the stack of open elements has a td or th element in table scope,
+ then act as if an end tag token with that tag name had been seen. */
+ foreach (array('td', 'th') as $cell) {
+ if ($this->elementInScope($cell, true)) {
+ $this->inCell(
+ array(
+ 'name' => $cell,
+ 'type' => HTML5::ENDTAG
+ )
+ );
+
+ break;
+ }
+ }
+ }
+
+ public function save()
+ {
+ return $this->dom;
+ }
+}
diff --git a/library/HTMLPurifier/Node.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Node.php
index 3995fec9f..3995fec9f 100644
--- a/library/HTMLPurifier/Node.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Node.php
diff --git a/library/HTMLPurifier/Node/Comment.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Node/Comment.php
index 38ba19394..38ba19394 100644
--- a/library/HTMLPurifier/Node/Comment.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Node/Comment.php
diff --git a/library/HTMLPurifier/Node/Element.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Node/Element.php
index 6cbf56dad..6cbf56dad 100644
--- a/library/HTMLPurifier/Node/Element.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Node/Element.php
diff --git a/library/HTMLPurifier/Node/Text.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Node/Text.php
index aec916647..aec916647 100644
--- a/library/HTMLPurifier/Node/Text.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Node/Text.php
diff --git a/library/HTMLPurifier/PercentEncoder.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/PercentEncoder.php
index 18c8bbb00..18c8bbb00 100644
--- a/library/HTMLPurifier/PercentEncoder.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/PercentEncoder.php
diff --git a/library/HTMLPurifier/Printer.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Printer.php
index 549e4cea1..549e4cea1 100644
--- a/library/HTMLPurifier/Printer.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Printer.php
diff --git a/library/HTMLPurifier/Printer/CSSDefinition.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Printer/CSSDefinition.php
index 29505fe12..29505fe12 100644
--- a/library/HTMLPurifier/Printer/CSSDefinition.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Printer/CSSDefinition.php
diff --git a/library/HTMLPurifier/Printer/ConfigForm.css b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Printer/ConfigForm.css
index 3ff1a88aa..3ff1a88aa 100644
--- a/library/HTMLPurifier/Printer/ConfigForm.css
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Printer/ConfigForm.css
diff --git a/library/HTMLPurifier/Printer/ConfigForm.js b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Printer/ConfigForm.js
index cba00c9b8..cba00c9b8 100644
--- a/library/HTMLPurifier/Printer/ConfigForm.js
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Printer/ConfigForm.js
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Printer/ConfigForm.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Printer/ConfigForm.php
new file mode 100644
index 000000000..65a777904
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Printer/ConfigForm.php
@@ -0,0 +1,451 @@
+<?php
+
+/**
+ * @todo Rewrite to use Interchange objects
+ */
+class HTMLPurifier_Printer_ConfigForm extends HTMLPurifier_Printer
+{
+
+ /**
+ * Printers for specific fields.
+ * @type HTMLPurifier_Printer[]
+ */
+ protected $fields = array();
+
+ /**
+ * Documentation URL, can have fragment tagged on end.
+ * @type string
+ */
+ protected $docURL;
+
+ /**
+ * Name of form element to stuff config in.
+ * @type string
+ */
+ protected $name;
+
+ /**
+ * Whether or not to compress directive names, clipping them off
+ * after a certain amount of letters. False to disable or integer letters
+ * before clipping.
+ * @type bool
+ */
+ protected $compress = false;
+
+ /**
+ * @param string $name Form element name for directives to be stuffed into
+ * @param string $doc_url String documentation URL, will have fragment tagged on
+ * @param bool $compress Integer max length before compressing a directive name, set to false to turn off
+ */
+ public function __construct(
+ $name,
+ $doc_url = null,
+ $compress = false
+ ) {
+ parent::__construct();
+ $this->docURL = $doc_url;
+ $this->name = $name;
+ $this->compress = $compress;
+ // initialize sub-printers
+ $this->fields[0] = new HTMLPurifier_Printer_ConfigForm_default();
+ $this->fields[HTMLPurifier_VarParser::BOOL] = new HTMLPurifier_Printer_ConfigForm_bool();
+ }
+
+ /**
+ * Sets default column and row size for textareas in sub-printers
+ * @param $cols Integer columns of textarea, null to use default
+ * @param $rows Integer rows of textarea, null to use default
+ */
+ public function setTextareaDimensions($cols = null, $rows = null)
+ {
+ if ($cols) {
+ $this->fields['default']->cols = $cols;
+ }
+ if ($rows) {
+ $this->fields['default']->rows = $rows;
+ }
+ }
+
+ /**
+ * Retrieves styling, in case it is not accessible by webserver
+ */
+ public static function getCSS()
+ {
+ return file_get_contents(HTMLPURIFIER_PREFIX . '/HTMLPurifier/Printer/ConfigForm.css');
+ }
+
+ /**
+ * Retrieves JavaScript, in case it is not accessible by webserver
+ */
+ public static function getJavaScript()
+ {
+ return file_get_contents(HTMLPURIFIER_PREFIX . '/HTMLPurifier/Printer/ConfigForm.js');
+ }
+
+ /**
+ * Returns HTML output for a configuration form
+ * @param HTMLPurifier_Config|array $config Configuration object of current form state, or an array
+ * where [0] has an HTML namespace and [1] is being rendered.
+ * @param array|bool $allowed Optional namespace(s) and directives to restrict form to.
+ * @param bool $render_controls
+ * @return string
+ */
+ public function render($config, $allowed = true, $render_controls = true)
+ {
+ if (is_array($config) && isset($config[0])) {
+ $gen_config = $config[0];
+ $config = $config[1];
+ } else {
+ $gen_config = $config;
+ }
+
+ $this->config = $config;
+ $this->genConfig = $gen_config;
+ $this->prepareGenerator($gen_config);
+
+ $allowed = HTMLPurifier_Config::getAllowedDirectivesForForm($allowed, $config->def);
+ $all = array();
+ foreach ($allowed as $key) {
+ list($ns, $directive) = $key;
+ $all[$ns][$directive] = $config->get($ns . '.' . $directive);
+ }
+
+ $ret = '';
+ $ret .= $this->start('table', array('class' => 'hp-config'));
+ $ret .= $this->start('thead');
+ $ret .= $this->start('tr');
+ $ret .= $this->element('th', 'Directive', array('class' => 'hp-directive'));
+ $ret .= $this->element('th', 'Value', array('class' => 'hp-value'));
+ $ret .= $this->end('tr');
+ $ret .= $this->end('thead');
+ foreach ($all as $ns => $directives) {
+ $ret .= $this->renderNamespace($ns, $directives);
+ }
+ if ($render_controls) {
+ $ret .= $this->start('tbody');
+ $ret .= $this->start('tr');
+ $ret .= $this->start('td', array('colspan' => 2, 'class' => 'controls'));
+ $ret .= $this->elementEmpty('input', array('type' => 'submit', 'value' => 'Submit'));
+ $ret .= '[<a href="?">Reset</a>]';
+ $ret .= $this->end('td');
+ $ret .= $this->end('tr');
+ $ret .= $this->end('tbody');
+ }
+ $ret .= $this->end('table');
+ return $ret;
+ }
+
+ /**
+ * Renders a single namespace
+ * @param $ns String namespace name
+ * @param array $directives array of directives to values
+ * @return string
+ */
+ protected function renderNamespace($ns, $directives)
+ {
+ $ret = '';
+ $ret .= $this->start('tbody', array('class' => 'namespace'));
+ $ret .= $this->start('tr');
+ $ret .= $this->element('th', $ns, array('colspan' => 2));
+ $ret .= $this->end('tr');
+ $ret .= $this->end('tbody');
+ $ret .= $this->start('tbody');
+ foreach ($directives as $directive => $value) {
+ $ret .= $this->start('tr');
+ $ret .= $this->start('th');
+ if ($this->docURL) {
+ $url = str_replace('%s', urlencode("$ns.$directive"), $this->docURL);
+ $ret .= $this->start('a', array('href' => $url));
+ }
+ $attr = array('for' => "{$this->name}:$ns.$directive");
+
+ // crop directive name if it's too long
+ if (!$this->compress || (strlen($directive) < $this->compress)) {
+ $directive_disp = $directive;
+ } else {
+ $directive_disp = substr($directive, 0, $this->compress - 2) . '...';
+ $attr['title'] = $directive;
+ }
+
+ $ret .= $this->element(
+ 'label',
+ $directive_disp,
+ // component printers must create an element with this id
+ $attr
+ );
+ if ($this->docURL) {
+ $ret .= $this->end('a');
+ }
+ $ret .= $this->end('th');
+
+ $ret .= $this->start('td');
+ $def = $this->config->def->info["$ns.$directive"];
+ if (is_int($def)) {
+ $allow_null = $def < 0;
+ $type = abs($def);
+ } else {
+ $type = $def->type;
+ $allow_null = isset($def->allow_null);
+ }
+ if (!isset($this->fields[$type])) {
+ $type = 0;
+ } // default
+ $type_obj = $this->fields[$type];
+ if ($allow_null) {
+ $type_obj = new HTMLPurifier_Printer_ConfigForm_NullDecorator($type_obj);
+ }
+ $ret .= $type_obj->render($ns, $directive, $value, $this->name, array($this->genConfig, $this->config));
+ $ret .= $this->end('td');
+ $ret .= $this->end('tr');
+ }
+ $ret .= $this->end('tbody');
+ return $ret;
+ }
+
+}
+
+/**
+ * Printer decorator for directives that accept null
+ */
+class HTMLPurifier_Printer_ConfigForm_NullDecorator extends HTMLPurifier_Printer
+{
+ /**
+ * Printer being decorated
+ * @type HTMLPurifier_Printer
+ */
+ protected $obj;
+
+ /**
+ * @param HTMLPurifier_Printer $obj Printer to decorate
+ */
+ public function __construct($obj)
+ {
+ parent::__construct();
+ $this->obj = $obj;
+ }
+
+ /**
+ * @param string $ns
+ * @param string $directive
+ * @param string $value
+ * @param string $name
+ * @param HTMLPurifier_Config|array $config
+ * @return string
+ */
+ public function render($ns, $directive, $value, $name, $config)
+ {
+ if (is_array($config) && isset($config[0])) {
+ $gen_config = $config[0];
+ $config = $config[1];
+ } else {
+ $gen_config = $config;
+ }
+ $this->prepareGenerator($gen_config);
+
+ $ret = '';
+ $ret .= $this->start('label', array('for' => "$name:Null_$ns.$directive"));
+ $ret .= $this->element('span', "$ns.$directive:", array('class' => 'verbose'));
+ $ret .= $this->text(' Null/Disabled');
+ $ret .= $this->end('label');
+ $attr = array(
+ 'type' => 'checkbox',
+ 'value' => '1',
+ 'class' => 'null-toggle',
+ 'name' => "$name" . "[Null_$ns.$directive]",
+ 'id' => "$name:Null_$ns.$directive",
+ 'onclick' => "toggleWriteability('$name:$ns.$directive',checked)" // INLINE JAVASCRIPT!!!!
+ );
+ if ($this->obj instanceof HTMLPurifier_Printer_ConfigForm_bool) {
+ // modify inline javascript slightly
+ $attr['onclick'] =
+ "toggleWriteability('$name:Yes_$ns.$directive',checked);" .
+ "toggleWriteability('$name:No_$ns.$directive',checked)";
+ }
+ if ($value === null) {
+ $attr['checked'] = 'checked';
+ }
+ $ret .= $this->elementEmpty('input', $attr);
+ $ret .= $this->text(' or ');
+ $ret .= $this->elementEmpty('br');
+ $ret .= $this->obj->render($ns, $directive, $value, $name, array($gen_config, $config));
+ return $ret;
+ }
+}
+
+/**
+ * Swiss-army knife configuration form field printer
+ */
+class HTMLPurifier_Printer_ConfigForm_default extends HTMLPurifier_Printer
+{
+ /**
+ * @type int
+ */
+ public $cols = 18;
+
+ /**
+ * @type int
+ */
+ public $rows = 5;
+
+ /**
+ * @param string $ns
+ * @param string $directive
+ * @param string $value
+ * @param string $name
+ * @param HTMLPurifier_Config|array $config
+ * @return string
+ */
+ public function render($ns, $directive, $value, $name, $config)
+ {
+ if (is_array($config) && isset($config[0])) {
+ $gen_config = $config[0];
+ $config = $config[1];
+ } else {
+ $gen_config = $config;
+ }
+ $this->prepareGenerator($gen_config);
+ // this should probably be split up a little
+ $ret = '';
+ $def = $config->def->info["$ns.$directive"];
+ if (is_int($def)) {
+ $type = abs($def);
+ } else {
+ $type = $def->type;
+ }
+ if (is_array($value)) {
+ switch ($type) {
+ case HTMLPurifier_VarParser::LOOKUP:
+ $array = $value;
+ $value = array();
+ foreach ($array as $val => $b) {
+ $value[] = $val;
+ }
+ //TODO does this need a break?
+ case HTMLPurifier_VarParser::ALIST:
+ $value = implode(PHP_EOL, $value);
+ break;
+ case HTMLPurifier_VarParser::HASH:
+ $nvalue = '';
+ foreach ($value as $i => $v) {
+ if (is_array($v)) {
+ // HACK
+ $v = implode(";", $v);
+ }
+ $nvalue .= "$i:$v" . PHP_EOL;
+ }
+ $value = $nvalue;
+ break;
+ default:
+ $value = '';
+ }
+ }
+ if ($type === HTMLPurifier_VarParser::MIXED) {
+ return 'Not supported';
+ $value = serialize($value);
+ }
+ $attr = array(
+ 'name' => "$name" . "[$ns.$directive]",
+ 'id' => "$name:$ns.$directive"
+ );
+ if ($value === null) {
+ $attr['disabled'] = 'disabled';
+ }
+ if (isset($def->allowed)) {
+ $ret .= $this->start('select', $attr);
+ foreach ($def->allowed as $val => $b) {
+ $attr = array();
+ if ($value == $val) {
+ $attr['selected'] = 'selected';
+ }
+ $ret .= $this->element('option', $val, $attr);
+ }
+ $ret .= $this->end('select');
+ } elseif ($type === HTMLPurifier_VarParser::TEXT ||
+ $type === HTMLPurifier_VarParser::ITEXT ||
+ $type === HTMLPurifier_VarParser::ALIST ||
+ $type === HTMLPurifier_VarParser::HASH ||
+ $type === HTMLPurifier_VarParser::LOOKUP) {
+ $attr['cols'] = $this->cols;
+ $attr['rows'] = $this->rows;
+ $ret .= $this->start('textarea', $attr);
+ $ret .= $this->text($value);
+ $ret .= $this->end('textarea');
+ } else {
+ $attr['value'] = $value;
+ $attr['type'] = 'text';
+ $ret .= $this->elementEmpty('input', $attr);
+ }
+ return $ret;
+ }
+}
+
+/**
+ * Bool form field printer
+ */
+class HTMLPurifier_Printer_ConfigForm_bool extends HTMLPurifier_Printer
+{
+ /**
+ * @param string $ns
+ * @param string $directive
+ * @param string $value
+ * @param string $name
+ * @param HTMLPurifier_Config|array $config
+ * @return string
+ */
+ public function render($ns, $directive, $value, $name, $config)
+ {
+ if (is_array($config) && isset($config[0])) {
+ $gen_config = $config[0];
+ $config = $config[1];
+ } else {
+ $gen_config = $config;
+ }
+ $this->prepareGenerator($gen_config);
+ $ret = '';
+ $ret .= $this->start('div', array('id' => "$name:$ns.$directive"));
+
+ $ret .= $this->start('label', array('for' => "$name:Yes_$ns.$directive"));
+ $ret .= $this->element('span', "$ns.$directive:", array('class' => 'verbose'));
+ $ret .= $this->text(' Yes');
+ $ret .= $this->end('label');
+
+ $attr = array(
+ 'type' => 'radio',
+ 'name' => "$name" . "[$ns.$directive]",
+ 'id' => "$name:Yes_$ns.$directive",
+ 'value' => '1'
+ );
+ if ($value === true) {
+ $attr['checked'] = 'checked';
+ }
+ if ($value === null) {
+ $attr['disabled'] = 'disabled';
+ }
+ $ret .= $this->elementEmpty('input', $attr);
+
+ $ret .= $this->start('label', array('for' => "$name:No_$ns.$directive"));
+ $ret .= $this->element('span', "$ns.$directive:", array('class' => 'verbose'));
+ $ret .= $this->text(' No');
+ $ret .= $this->end('label');
+
+ $attr = array(
+ 'type' => 'radio',
+ 'name' => "$name" . "[$ns.$directive]",
+ 'id' => "$name:No_$ns.$directive",
+ 'value' => '0'
+ );
+ if ($value === false) {
+ $attr['checked'] = 'checked';
+ }
+ if ($value === null) {
+ $attr['disabled'] = 'disabled';
+ }
+ $ret .= $this->elementEmpty('input', $attr);
+
+ $ret .= $this->end('div');
+
+ return $ret;
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/Printer/HTMLDefinition.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Printer/HTMLDefinition.php
index 5f2f2f8a7..5f2f2f8a7 100644
--- a/library/HTMLPurifier/Printer/HTMLDefinition.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Printer/HTMLDefinition.php
diff --git a/library/HTMLPurifier/PropertyList.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/PropertyList.php
index 189348fd9..189348fd9 100644
--- a/library/HTMLPurifier/PropertyList.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/PropertyList.php
diff --git a/library/HTMLPurifier/PropertyListIterator.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/PropertyListIterator.php
index 15b330ea3..15b330ea3 100644
--- a/library/HTMLPurifier/PropertyListIterator.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/PropertyListIterator.php
diff --git a/library/HTMLPurifier/Queue.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Queue.php
index f58db9042..f58db9042 100644
--- a/library/HTMLPurifier/Queue.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Queue.php
diff --git a/library/HTMLPurifier/Strategy.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Strategy.php
index e1ff3b72d..e1ff3b72d 100644
--- a/library/HTMLPurifier/Strategy.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Strategy.php
diff --git a/library/HTMLPurifier/Strategy/Composite.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/Composite.php
index d7d35ce7d..d7d35ce7d 100644
--- a/library/HTMLPurifier/Strategy/Composite.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/Composite.php
diff --git a/library/HTMLPurifier/Strategy/Core.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/Core.php
index 4414c17d6..4414c17d6 100644
--- a/library/HTMLPurifier/Strategy/Core.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/Core.php
diff --git a/library/HTMLPurifier/Strategy/FixNesting.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/FixNesting.php
index 6fa673db9..6fa673db9 100644
--- a/library/HTMLPurifier/Strategy/FixNesting.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/FixNesting.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/MakeWellFormed.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/MakeWellFormed.php
new file mode 100644
index 000000000..a6eb09e45
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/MakeWellFormed.php
@@ -0,0 +1,659 @@
+<?php
+
+/**
+ * Takes tokens makes them well-formed (balance end tags, etc.)
+ *
+ * Specification of the armor attributes this strategy uses:
+ *
+ * - MakeWellFormed_TagClosedError: This armor field is used to
+ * suppress tag closed errors for certain tokens [TagClosedSuppress],
+ * in particular, if a tag was generated automatically by HTML
+ * Purifier, we may rely on our infrastructure to close it for us
+ * and shouldn't report an error to the user [TagClosedAuto].
+ */
+class HTMLPurifier_Strategy_MakeWellFormed extends HTMLPurifier_Strategy
+{
+
+ /**
+ * Array stream of tokens being processed.
+ * @type HTMLPurifier_Token[]
+ */
+ protected $tokens;
+
+ /**
+ * Current token.
+ * @type HTMLPurifier_Token
+ */
+ protected $token;
+
+ /**
+ * Zipper managing the true state.
+ * @type HTMLPurifier_Zipper
+ */
+ protected $zipper;
+
+ /**
+ * Current nesting of elements.
+ * @type array
+ */
+ protected $stack;
+
+ /**
+ * Injectors active in this stream processing.
+ * @type HTMLPurifier_Injector[]
+ */
+ protected $injectors;
+
+ /**
+ * Current instance of HTMLPurifier_Config.
+ * @type HTMLPurifier_Config
+ */
+ protected $config;
+
+ /**
+ * Current instance of HTMLPurifier_Context.
+ * @type HTMLPurifier_Context
+ */
+ protected $context;
+
+ /**
+ * @param HTMLPurifier_Token[] $tokens
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return HTMLPurifier_Token[]
+ * @throws HTMLPurifier_Exception
+ */
+ public function execute($tokens, $config, $context)
+ {
+ $definition = $config->getHTMLDefinition();
+
+ // local variables
+ $generator = new HTMLPurifier_Generator($config, $context);
+ $escape_invalid_tags = $config->get('Core.EscapeInvalidTags');
+ // used for autoclose early abortion
+ $global_parent_allowed_elements = $definition->info_parent_def->child->getAllowedElements($config);
+ $e = $context->get('ErrorCollector', true);
+ $i = false; // injector index
+ list($zipper, $token) = HTMLPurifier_Zipper::fromArray($tokens);
+ if ($token === NULL) {
+ return array();
+ }
+ $reprocess = false; // whether or not to reprocess the same token
+ $stack = array();
+
+ // member variables
+ $this->stack =& $stack;
+ $this->tokens =& $tokens;
+ $this->token =& $token;
+ $this->zipper =& $zipper;
+ $this->config = $config;
+ $this->context = $context;
+
+ // context variables
+ $context->register('CurrentNesting', $stack);
+ $context->register('InputZipper', $zipper);
+ $context->register('CurrentToken', $token);
+
+ // -- begin INJECTOR --
+
+ $this->injectors = array();
+
+ $injectors = $config->getBatch('AutoFormat');
+ $def_injectors = $definition->info_injector;
+ $custom_injectors = $injectors['Custom'];
+ unset($injectors['Custom']); // special case
+ foreach ($injectors as $injector => $b) {
+ // XXX: Fix with a legitimate lookup table of enabled filters
+ if (strpos($injector, '.') !== false) {
+ continue;
+ }
+ $injector = "HTMLPurifier_Injector_$injector";
+ if (!$b) {
+ continue;
+ }
+ $this->injectors[] = new $injector;
+ }
+ foreach ($def_injectors as $injector) {
+ // assumed to be objects
+ $this->injectors[] = $injector;
+ }
+ foreach ($custom_injectors as $injector) {
+ if (!$injector) {
+ continue;
+ }
+ if (is_string($injector)) {
+ $injector = "HTMLPurifier_Injector_$injector";
+ $injector = new $injector;
+ }
+ $this->injectors[] = $injector;
+ }
+
+ // give the injectors references to the definition and context
+ // variables for performance reasons
+ foreach ($this->injectors as $ix => $injector) {
+ $error = $injector->prepare($config, $context);
+ if (!$error) {
+ continue;
+ }
+ array_splice($this->injectors, $ix, 1); // rm the injector
+ trigger_error("Cannot enable {$injector->name} injector because $error is not allowed", E_USER_WARNING);
+ }
+
+ // -- end INJECTOR --
+
+ // a note on reprocessing:
+ // In order to reduce code duplication, whenever some code needs
+ // to make HTML changes in order to make things "correct", the
+ // new HTML gets sent through the purifier, regardless of its
+ // status. This means that if we add a start token, because it
+ // was totally necessary, we don't have to update nesting; we just
+ // punt ($reprocess = true; continue;) and it does that for us.
+
+ // isset is in loop because $tokens size changes during loop exec
+ for (;;
+ // only increment if we don't need to reprocess
+ $reprocess ? $reprocess = false : $token = $zipper->next($token)) {
+
+ // check for a rewind
+ if (is_int($i)) {
+ // possibility: disable rewinding if the current token has a
+ // rewind set on it already. This would offer protection from
+ // infinite loop, but might hinder some advanced rewinding.
+ $rewind_offset = $this->injectors[$i]->getRewindOffset();
+ if (is_int($rewind_offset)) {
+ for ($j = 0; $j < $rewind_offset; $j++) {
+ if (empty($zipper->front)) break;
+ $token = $zipper->prev($token);
+ // indicate that other injectors should not process this token,
+ // but we need to reprocess it. See Note [Injector skips]
+ unset($token->skip[$i]);
+ $token->rewind = $i;
+ if ($token instanceof HTMLPurifier_Token_Start) {
+ array_pop($this->stack);
+ } elseif ($token instanceof HTMLPurifier_Token_End) {
+ $this->stack[] = $token->start;
+ }
+ }
+ }
+ $i = false;
+ }
+
+ // handle case of document end
+ if ($token === NULL) {
+ // kill processing if stack is empty
+ if (empty($this->stack)) {
+ break;
+ }
+
+ // peek
+ $top_nesting = array_pop($this->stack);
+ $this->stack[] = $top_nesting;
+
+ // send error [TagClosedSuppress]
+ if ($e && !isset($top_nesting->armor['MakeWellFormed_TagClosedError'])) {
+ $e->send(E_NOTICE, 'Strategy_MakeWellFormed: Tag closed by document end', $top_nesting);
+ }
+
+ // append, don't splice, since this is the end
+ $token = new HTMLPurifier_Token_End($top_nesting->name);
+
+ // punt!
+ $reprocess = true;
+ continue;
+ }
+
+ //echo '<br>'; printZipper($zipper, $token);//printTokens($this->stack);
+ //flush();
+
+ // quick-check: if it's not a tag, no need to process
+ if (empty($token->is_tag)) {
+ if ($token instanceof HTMLPurifier_Token_Text) {
+ foreach ($this->injectors as $i => $injector) {
+ if (isset($token->skip[$i])) {
+ // See Note [Injector skips]
+ continue;
+ }
+ if ($token->rewind !== null && $token->rewind !== $i) {
+ continue;
+ }
+ // XXX fuckup
+ $r = $token;
+ $injector->handleText($r);
+ $token = $this->processToken($r, $i);
+ $reprocess = true;
+ break;
+ }
+ }
+ // another possibility is a comment
+ continue;
+ }
+
+ if (isset($definition->info[$token->name])) {
+ $type = $definition->info[$token->name]->child->type;
+ } else {
+ $type = false; // Type is unknown, treat accordingly
+ }
+
+ // quick tag checks: anything that's *not* an end tag
+ $ok = false;
+ if ($type === 'empty' && $token instanceof HTMLPurifier_Token_Start) {
+ // claims to be a start tag but is empty
+ $token = new HTMLPurifier_Token_Empty(
+ $token->name,
+ $token->attr,
+ $token->line,
+ $token->col,
+ $token->armor
+ );
+ $ok = true;
+ } elseif ($type && $type !== 'empty' && $token instanceof HTMLPurifier_Token_Empty) {
+ // claims to be empty but really is a start tag
+ // NB: this assignment is required
+ $old_token = $token;
+ $token = new HTMLPurifier_Token_End($token->name);
+ $token = $this->insertBefore(
+ new HTMLPurifier_Token_Start($old_token->name, $old_token->attr, $old_token->line, $old_token->col, $old_token->armor)
+ );
+ // punt (since we had to modify the input stream in a non-trivial way)
+ $reprocess = true;
+ continue;
+ } elseif ($token instanceof HTMLPurifier_Token_Empty) {
+ // real empty token
+ $ok = true;
+ } elseif ($token instanceof HTMLPurifier_Token_Start) {
+ // start tag
+
+ // ...unless they also have to close their parent
+ if (!empty($this->stack)) {
+
+ // Performance note: you might think that it's rather
+ // inefficient, recalculating the autoclose information
+ // for every tag that a token closes (since when we
+ // do an autoclose, we push a new token into the
+ // stream and then /process/ that, before
+ // re-processing this token.) But this is
+ // necessary, because an injector can make an
+ // arbitrary transformations to the autoclosing
+ // tokens we introduce, so things may have changed
+ // in the meantime. Also, doing the inefficient thing is
+ // "easy" to reason about (for certain perverse definitions
+ // of "easy")
+
+ $parent = array_pop($this->stack);
+ $this->stack[] = $parent;
+
+ $parent_def = null;
+ $parent_elements = null;
+ $autoclose = false;
+ if (isset($definition->info[$parent->name])) {
+ $parent_def = $definition->info[$parent->name];
+ $parent_elements = $parent_def->child->getAllowedElements($config);
+ $autoclose = !isset($parent_elements[$token->name]);
+ }
+
+ if ($autoclose && $definition->info[$token->name]->wrap) {
+ // Check if an element can be wrapped by another
+ // element to make it valid in a context (for
+ // example, <ul><ul> needs a <li> in between)
+ $wrapname = $definition->info[$token->name]->wrap;
+ $wrapdef = $definition->info[$wrapname];
+ $elements = $wrapdef->child->getAllowedElements($config);
+ if (isset($elements[$token->name]) && isset($parent_elements[$wrapname])) {
+ $newtoken = new HTMLPurifier_Token_Start($wrapname);
+ $token = $this->insertBefore($newtoken);
+ $reprocess = true;
+ continue;
+ }
+ }
+
+ $carryover = false;
+ if ($autoclose && $parent_def->formatting) {
+ $carryover = true;
+ }
+
+ if ($autoclose) {
+ // check if this autoclose is doomed to fail
+ // (this rechecks $parent, which his harmless)
+ $autoclose_ok = isset($global_parent_allowed_elements[$token->name]);
+ if (!$autoclose_ok) {
+ foreach ($this->stack as $ancestor) {
+ $elements = $definition->info[$ancestor->name]->child->getAllowedElements($config);
+ if (isset($elements[$token->name])) {
+ $autoclose_ok = true;
+ break;
+ }
+ if ($definition->info[$token->name]->wrap) {
+ $wrapname = $definition->info[$token->name]->wrap;
+ $wrapdef = $definition->info[$wrapname];
+ $wrap_elements = $wrapdef->child->getAllowedElements($config);
+ if (isset($wrap_elements[$token->name]) && isset($elements[$wrapname])) {
+ $autoclose_ok = true;
+ break;
+ }
+ }
+ }
+ }
+ if ($autoclose_ok) {
+ // errors need to be updated
+ $new_token = new HTMLPurifier_Token_End($parent->name);
+ $new_token->start = $parent;
+ // [TagClosedSuppress]
+ if ($e && !isset($parent->armor['MakeWellFormed_TagClosedError'])) {
+ if (!$carryover) {
+ $e->send(E_NOTICE, 'Strategy_MakeWellFormed: Tag auto closed', $parent);
+ } else {
+ $e->send(E_NOTICE, 'Strategy_MakeWellFormed: Tag carryover', $parent);
+ }
+ }
+ if ($carryover) {
+ $element = clone $parent;
+ // [TagClosedAuto]
+ $element->armor['MakeWellFormed_TagClosedError'] = true;
+ $element->carryover = true;
+ $token = $this->processToken(array($new_token, $token, $element));
+ } else {
+ $token = $this->insertBefore($new_token);
+ }
+ } else {
+ $token = $this->remove();
+ }
+ $reprocess = true;
+ continue;
+ }
+
+ }
+ $ok = true;
+ }
+
+ if ($ok) {
+ foreach ($this->injectors as $i => $injector) {
+ if (isset($token->skip[$i])) {
+ // See Note [Injector skips]
+ continue;
+ }
+ if ($token->rewind !== null && $token->rewind !== $i) {
+ continue;
+ }
+ $r = $token;
+ $injector->handleElement($r);
+ $token = $this->processToken($r, $i);
+ $reprocess = true;
+ break;
+ }
+ if (!$reprocess) {
+ // ah, nothing interesting happened; do normal processing
+ if ($token instanceof HTMLPurifier_Token_Start) {
+ $this->stack[] = $token;
+ } elseif ($token instanceof HTMLPurifier_Token_End) {
+ throw new HTMLPurifier_Exception(
+ 'Improper handling of end tag in start code; possible error in MakeWellFormed'
+ );
+ }
+ }
+ continue;
+ }
+
+ // sanity check: we should be dealing with a closing tag
+ if (!$token instanceof HTMLPurifier_Token_End) {
+ throw new HTMLPurifier_Exception('Unaccounted for tag token in input stream, bug in HTML Purifier');
+ }
+
+ // make sure that we have something open
+ if (empty($this->stack)) {
+ if ($escape_invalid_tags) {
+ if ($e) {
+ $e->send(E_WARNING, 'Strategy_MakeWellFormed: Unnecessary end tag to text');
+ }
+ $token = new HTMLPurifier_Token_Text($generator->generateFromToken($token));
+ } else {
+ if ($e) {
+ $e->send(E_WARNING, 'Strategy_MakeWellFormed: Unnecessary end tag removed');
+ }
+ $token = $this->remove();
+ }
+ $reprocess = true;
+ continue;
+ }
+
+ // first, check for the simplest case: everything closes neatly.
+ // Eventually, everything passes through here; if there are problems
+ // we modify the input stream accordingly and then punt, so that
+ // the tokens get processed again.
+ $current_parent = array_pop($this->stack);
+ if ($current_parent->name == $token->name) {
+ $token->start = $current_parent;
+ foreach ($this->injectors as $i => $injector) {
+ if (isset($token->skip[$i])) {
+ // See Note [Injector skips]
+ continue;
+ }
+ if ($token->rewind !== null && $token->rewind !== $i) {
+ continue;
+ }
+ $r = $token;
+ $injector->handleEnd($r);
+ $token = $this->processToken($r, $i);
+ $this->stack[] = $current_parent;
+ $reprocess = true;
+ break;
+ }
+ continue;
+ }
+
+ // okay, so we're trying to close the wrong tag
+
+ // undo the pop previous pop
+ $this->stack[] = $current_parent;
+
+ // scroll back the entire nest, trying to find our tag.
+ // (feature could be to specify how far you'd like to go)
+ $size = count($this->stack);
+ // -2 because -1 is the last element, but we already checked that
+ $skipped_tags = false;
+ for ($j = $size - 2; $j >= 0; $j--) {
+ if ($this->stack[$j]->name == $token->name) {
+ $skipped_tags = array_slice($this->stack, $j);
+ break;
+ }
+ }
+
+ // we didn't find the tag, so remove
+ if ($skipped_tags === false) {
+ if ($escape_invalid_tags) {
+ if ($e) {
+ $e->send(E_WARNING, 'Strategy_MakeWellFormed: Stray end tag to text');
+ }
+ $token = new HTMLPurifier_Token_Text($generator->generateFromToken($token));
+ } else {
+ if ($e) {
+ $e->send(E_WARNING, 'Strategy_MakeWellFormed: Stray end tag removed');
+ }
+ $token = $this->remove();
+ }
+ $reprocess = true;
+ continue;
+ }
+
+ // do errors, in REVERSE $j order: a,b,c with </a></b></c>
+ $c = count($skipped_tags);
+ if ($e) {
+ for ($j = $c - 1; $j > 0; $j--) {
+ // notice we exclude $j == 0, i.e. the current ending tag, from
+ // the errors... [TagClosedSuppress]
+ if (!isset($skipped_tags[$j]->armor['MakeWellFormed_TagClosedError'])) {
+ $e->send(E_NOTICE, 'Strategy_MakeWellFormed: Tag closed by element end', $skipped_tags[$j]);
+ }
+ }
+ }
+
+ // insert tags, in FORWARD $j order: c,b,a with </a></b></c>
+ $replace = array($token);
+ for ($j = 1; $j < $c; $j++) {
+ // ...as well as from the insertions
+ $new_token = new HTMLPurifier_Token_End($skipped_tags[$j]->name);
+ $new_token->start = $skipped_tags[$j];
+ array_unshift($replace, $new_token);
+ if (isset($definition->info[$new_token->name]) && $definition->info[$new_token->name]->formatting) {
+ // [TagClosedAuto]
+ $element = clone $skipped_tags[$j];
+ $element->carryover = true;
+ $element->armor['MakeWellFormed_TagClosedError'] = true;
+ $replace[] = $element;
+ }
+ }
+ $token = $this->processToken($replace);
+ $reprocess = true;
+ continue;
+ }
+
+ $context->destroy('CurrentToken');
+ $context->destroy('CurrentNesting');
+ $context->destroy('InputZipper');
+
+ unset($this->injectors, $this->stack, $this->tokens);
+ return $zipper->toArray($token);
+ }
+
+ /**
+ * Processes arbitrary token values for complicated substitution patterns.
+ * In general:
+ *
+ * If $token is an array, it is a list of tokens to substitute for the
+ * current token. These tokens then get individually processed. If there
+ * is a leading integer in the list, that integer determines how many
+ * tokens from the stream should be removed.
+ *
+ * If $token is a regular token, it is swapped with the current token.
+ *
+ * If $token is false, the current token is deleted.
+ *
+ * If $token is an integer, that number of tokens (with the first token
+ * being the current one) will be deleted.
+ *
+ * @param HTMLPurifier_Token|array|int|bool $token Token substitution value
+ * @param HTMLPurifier_Injector|int $injector Injector that performed the substitution; default is if
+ * this is not an injector related operation.
+ * @throws HTMLPurifier_Exception
+ */
+ protected function processToken($token, $injector = -1)
+ {
+ // Zend OpCache miscompiles $token = array($token), so
+ // avoid this pattern. See: https://github.com/ezyang/htmlpurifier/issues/108
+
+ // normalize forms of token
+ if (is_object($token)) {
+ $tmp = $token;
+ $token = array(1, $tmp);
+ }
+ if (is_int($token)) {
+ $tmp = $token;
+ $token = array($tmp);
+ }
+ if ($token === false) {
+ $token = array(1);
+ }
+ if (!is_array($token)) {
+ throw new HTMLPurifier_Exception('Invalid token type from injector');
+ }
+ if (!is_int($token[0])) {
+ array_unshift($token, 1);
+ }
+ if ($token[0] === 0) {
+ throw new HTMLPurifier_Exception('Deleting zero tokens is not valid');
+ }
+
+ // $token is now an array with the following form:
+ // array(number nodes to delete, new node 1, new node 2, ...)
+
+ $delete = array_shift($token);
+ list($old, $r) = $this->zipper->splice($this->token, $delete, $token);
+
+ if ($injector > -1) {
+ // See Note [Injector skips]
+ // Determine appropriate skips. Here's what the code does:
+ // *If* we deleted one or more tokens, copy the skips
+ // of those tokens into the skips of the new tokens (in $token).
+ // Also, mark the newly inserted tokens as having come from
+ // $injector.
+ $oldskip = isset($old[0]) ? $old[0]->skip : array();
+ foreach ($token as $object) {
+ $object->skip = $oldskip;
+ $object->skip[$injector] = true;
+ }
+ }
+
+ return $r;
+
+ }
+
+ /**
+ * Inserts a token before the current token. Cursor now points to
+ * this token. You must reprocess after this.
+ * @param HTMLPurifier_Token $token
+ */
+ private function insertBefore($token)
+ {
+ // NB not $this->zipper->insertBefore(), due to positioning
+ // differences
+ $splice = $this->zipper->splice($this->token, 0, array($token));
+
+ return $splice[1];
+ }
+
+ /**
+ * Removes current token. Cursor now points to new token occupying previously
+ * occupied space. You must reprocess after this.
+ */
+ private function remove()
+ {
+ return $this->zipper->delete();
+ }
+}
+
+// Note [Injector skips]
+// ~~~~~~~~~~~~~~~~~~~~~
+// When I originally designed this class, the idea behind the 'skip'
+// property of HTMLPurifier_Token was to help avoid infinite loops
+// in injector processing. For example, suppose you wrote an injector
+// that bolded swear words. Naively, you might write it so that
+// whenever you saw ****, you replaced it with <strong>****</strong>.
+//
+// When this happens, we will reprocess all of the tokens with the
+// other injectors. Now there is an opportunity for infinite loop:
+// if we rerun the swear-word injector on these tokens, we might
+// see **** and then reprocess again to get
+// <strong><strong>****</strong></strong> ad infinitum.
+//
+// Thus, the idea of a skip is that once we process a token with
+// an injector, we mark all of those tokens as having "come from"
+// the injector, and we never run the injector again on these
+// tokens.
+//
+// There were two more complications, however:
+//
+// - With HTMLPurifier_Injector_RemoveEmpty, we noticed that if
+// you had <b><i></i></b>, after you removed the <i></i>, you
+// really would like this injector to go back and reprocess
+// the <b> tag, discovering that it is now empty and can be
+// removed. So we reintroduced the possibility of infinite looping
+// by adding a "rewind" function, which let you go back to an
+// earlier point in the token stream and reprocess it with injectors.
+// Needless to say, we need to UN-skip the token so it gets
+// reprocessed.
+//
+// - Suppose that you successfuly process a token, replace it with
+// one with your skip mark, but now another injector wants to
+// process the skipped token with another token. Should you continue
+// to skip that new token, or reprocess it? If you reprocess,
+// you can end up with an infinite loop where one injector converts
+// <a> to <b>, and then another injector converts it back. So
+// we inherit the skips, but for some reason, I thought that we
+// should inherit the skip from the first token of the token
+// that we deleted. Why? Well, it seems to work OK.
+//
+// If I were to redesign this functionality, I would absolutely not
+// go about doing it this way: the semantics are just not very well
+// defined, and in any case you probably wanted to operate on trees,
+// not token streams.
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/Strategy/RemoveForeignElements.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/RemoveForeignElements.php
index 1a8149ecc..1a8149ecc 100644
--- a/library/HTMLPurifier/Strategy/RemoveForeignElements.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/RemoveForeignElements.php
diff --git a/library/HTMLPurifier/Strategy/ValidateAttributes.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/ValidateAttributes.php
index fbb3d27c8..fbb3d27c8 100644
--- a/library/HTMLPurifier/Strategy/ValidateAttributes.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Strategy/ValidateAttributes.php
diff --git a/library/HTMLPurifier/StringHash.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/StringHash.php
index c07370197..c07370197 100644
--- a/library/HTMLPurifier/StringHash.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/StringHash.php
diff --git a/library/HTMLPurifier/StringHashParser.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/StringHashParser.php
index 7c73f8083..7c73f8083 100644
--- a/library/HTMLPurifier/StringHashParser.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/StringHashParser.php
diff --git a/library/HTMLPurifier/TagTransform.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/TagTransform.php
index 7b8d83343..7b8d83343 100644
--- a/library/HTMLPurifier/TagTransform.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/TagTransform.php
diff --git a/library/HTMLPurifier/TagTransform/Font.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/TagTransform/Font.php
index 7853d90bc..7853d90bc 100644
--- a/library/HTMLPurifier/TagTransform/Font.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/TagTransform/Font.php
diff --git a/library/HTMLPurifier/TagTransform/Simple.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/TagTransform/Simple.php
index 71bf10b91..71bf10b91 100644
--- a/library/HTMLPurifier/TagTransform/Simple.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/TagTransform/Simple.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Token.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Token.php
new file mode 100644
index 000000000..84d3619a3
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Token.php
@@ -0,0 +1,100 @@
+<?php
+
+/**
+ * Abstract base token class that all others inherit from.
+ */
+abstract class HTMLPurifier_Token
+{
+ /**
+ * Line number node was on in source document. Null if unknown.
+ * @type int
+ */
+ public $line;
+
+ /**
+ * Column of line node was on in source document. Null if unknown.
+ * @type int
+ */
+ public $col;
+
+ /**
+ * Lookup array of processing that this token is exempt from.
+ * Currently, valid values are "ValidateAttributes" and
+ * "MakeWellFormed_TagClosedError"
+ * @type array
+ */
+ public $armor = array();
+
+ /**
+ * Used during MakeWellFormed. See Note [Injector skips]
+ * @type
+ */
+ public $skip;
+
+ /**
+ * @type
+ */
+ public $rewind;
+
+ /**
+ * @type
+ */
+ public $carryover;
+
+ /**
+ * @param string $n
+ * @return null|string
+ */
+ public function __get($n)
+ {
+ if ($n === 'type') {
+ trigger_error('Deprecated type property called; use instanceof', E_USER_NOTICE);
+ switch (get_class($this)) {
+ case 'HTMLPurifier_Token_Start':
+ return 'start';
+ case 'HTMLPurifier_Token_Empty':
+ return 'empty';
+ case 'HTMLPurifier_Token_End':
+ return 'end';
+ case 'HTMLPurifier_Token_Text':
+ return 'text';
+ case 'HTMLPurifier_Token_Comment':
+ return 'comment';
+ default:
+ return null;
+ }
+ }
+ }
+
+ /**
+ * Sets the position of the token in the source document.
+ * @param int $l
+ * @param int $c
+ */
+ public function position($l = null, $c = null)
+ {
+ $this->line = $l;
+ $this->col = $c;
+ }
+
+ /**
+ * Convenience function for DirectLex settings line/col position.
+ * @param int $l
+ * @param int $c
+ */
+ public function rawPosition($l, $c)
+ {
+ if ($c === -1) {
+ $l++;
+ }
+ $this->line = $l;
+ $this->col = $c;
+ }
+
+ /**
+ * Converts a token into its corresponding node.
+ */
+ abstract public function toNode();
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/Token/Comment.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Token/Comment.php
index 23453c705..23453c705 100644
--- a/library/HTMLPurifier/Token/Comment.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Token/Comment.php
diff --git a/library/HTMLPurifier/Token/Empty.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Token/Empty.php
index 78a95f555..78a95f555 100644
--- a/library/HTMLPurifier/Token/Empty.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Token/Empty.php
diff --git a/library/HTMLPurifier/Token/End.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Token/End.php
index 59b38fdc5..59b38fdc5 100644
--- a/library/HTMLPurifier/Token/End.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Token/End.php
diff --git a/library/HTMLPurifier/Token/Start.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Token/Start.php
index 019f317ad..019f317ad 100644
--- a/library/HTMLPurifier/Token/Start.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Token/Start.php
diff --git a/library/HTMLPurifier/Token/Tag.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Token/Tag.php
index d643fa64e..d643fa64e 100644
--- a/library/HTMLPurifier/Token/Tag.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Token/Tag.php
diff --git a/library/HTMLPurifier/Token/Text.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Token/Text.php
index f26a1c211..f26a1c211 100644
--- a/library/HTMLPurifier/Token/Text.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Token/Text.php
diff --git a/library/HTMLPurifier/TokenFactory.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/TokenFactory.php
index dea2446b9..dea2446b9 100644
--- a/library/HTMLPurifier/TokenFactory.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/TokenFactory.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URI.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URI.php
new file mode 100644
index 000000000..9c5be39d1
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URI.php
@@ -0,0 +1,316 @@
+<?php
+
+/**
+ * HTML Purifier's internal representation of a URI.
+ * @note
+ * Internal data-structures are completely escaped. If the data needs
+ * to be used in a non-URI context (which is very unlikely), be sure
+ * to decode it first. The URI may not necessarily be well-formed until
+ * validate() is called.
+ */
+class HTMLPurifier_URI
+{
+ /**
+ * @type string
+ */
+ public $scheme;
+
+ /**
+ * @type string
+ */
+ public $userinfo;
+
+ /**
+ * @type string
+ */
+ public $host;
+
+ /**
+ * @type int
+ */
+ public $port;
+
+ /**
+ * @type string
+ */
+ public $path;
+
+ /**
+ * @type string
+ */
+ public $query;
+
+ /**
+ * @type string
+ */
+ public $fragment;
+
+ /**
+ * @param string $scheme
+ * @param string $userinfo
+ * @param string $host
+ * @param int $port
+ * @param string $path
+ * @param string $query
+ * @param string $fragment
+ * @note Automatically normalizes scheme and port
+ */
+ public function __construct($scheme, $userinfo, $host, $port, $path, $query, $fragment)
+ {
+ $this->scheme = is_null($scheme) || ctype_lower($scheme) ? $scheme : strtolower($scheme);
+ $this->userinfo = $userinfo;
+ $this->host = $host;
+ $this->port = is_null($port) ? $port : (int)$port;
+ $this->path = $path;
+ $this->query = $query;
+ $this->fragment = $fragment;
+ }
+
+ /**
+ * Retrieves a scheme object corresponding to the URI's scheme/default
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return HTMLPurifier_URIScheme Scheme object appropriate for validating this URI
+ */
+ public function getSchemeObj($config, $context)
+ {
+ $registry = HTMLPurifier_URISchemeRegistry::instance();
+ if ($this->scheme !== null) {
+ $scheme_obj = $registry->getScheme($this->scheme, $config, $context);
+ if (!$scheme_obj) {
+ return false;
+ } // invalid scheme, clean it out
+ } else {
+ // no scheme: retrieve the default one
+ $def = $config->getDefinition('URI');
+ $scheme_obj = $def->getDefaultScheme($config, $context);
+ if (!$scheme_obj) {
+ if ($def->defaultScheme !== null) {
+ // something funky happened to the default scheme object
+ trigger_error(
+ 'Default scheme object "' . $def->defaultScheme . '" was not readable',
+ E_USER_WARNING
+ );
+ } // suppress error if it's null
+ return false;
+ }
+ }
+ return $scheme_obj;
+ }
+
+ /**
+ * Generic validation method applicable for all schemes. May modify
+ * this URI in order to get it into a compliant form.
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return bool True if validation/filtering succeeds, false if failure
+ */
+ public function validate($config, $context)
+ {
+ // ABNF definitions from RFC 3986
+ $chars_sub_delims = '!$&\'()*+,;=';
+ $chars_gen_delims = ':/?#[]@';
+ $chars_pchar = $chars_sub_delims . ':@';
+
+ // validate host
+ if (!is_null($this->host)) {
+ $host_def = new HTMLPurifier_AttrDef_URI_Host();
+ $this->host = $host_def->validate($this->host, $config, $context);
+ if ($this->host === false) {
+ $this->host = null;
+ }
+ }
+
+ // validate scheme
+ // NOTE: It's not appropriate to check whether or not this
+ // scheme is in our registry, since a URIFilter may convert a
+ // URI that we don't allow into one we do. So instead, we just
+ // check if the scheme can be dropped because there is no host
+ // and it is our default scheme.
+ if (!is_null($this->scheme) && is_null($this->host) || $this->host === '') {
+ // support for relative paths is pretty abysmal when the
+ // scheme is present, so axe it when possible
+ $def = $config->getDefinition('URI');
+ if ($def->defaultScheme === $this->scheme) {
+ $this->scheme = null;
+ }
+ }
+
+ // validate username
+ if (!is_null($this->userinfo)) {
+ $encoder = new HTMLPurifier_PercentEncoder($chars_sub_delims . ':');
+ $this->userinfo = $encoder->encode($this->userinfo);
+ }
+
+ // validate port
+ if (!is_null($this->port)) {
+ if ($this->port < 1 || $this->port > 65535) {
+ $this->port = null;
+ }
+ }
+
+ // validate path
+ $segments_encoder = new HTMLPurifier_PercentEncoder($chars_pchar . '/');
+ if (!is_null($this->host)) { // this catches $this->host === ''
+ // path-abempty (hier and relative)
+ // http://www.example.com/my/path
+ // //www.example.com/my/path (looks odd, but works, and
+ // recognized by most browsers)
+ // (this set is valid or invalid on a scheme by scheme
+ // basis, so we'll deal with it later)
+ // file:///my/path
+ // ///my/path
+ $this->path = $segments_encoder->encode($this->path);
+ } elseif ($this->path !== '') {
+ if ($this->path[0] === '/') {
+ // path-absolute (hier and relative)
+ // http:/my/path
+ // /my/path
+ if (strlen($this->path) >= 2 && $this->path[1] === '/') {
+ // This could happen if both the host gets stripped
+ // out
+ // http://my/path
+ // //my/path
+ $this->path = '';
+ } else {
+ $this->path = $segments_encoder->encode($this->path);
+ }
+ } elseif (!is_null($this->scheme)) {
+ // path-rootless (hier)
+ // http:my/path
+ // Short circuit evaluation means we don't need to check nz
+ $this->path = $segments_encoder->encode($this->path);
+ } else {
+ // path-noscheme (relative)
+ // my/path
+ // (once again, not checking nz)
+ $segment_nc_encoder = new HTMLPurifier_PercentEncoder($chars_sub_delims . '@');
+ $c = strpos($this->path, '/');
+ if ($c !== false) {
+ $this->path =
+ $segment_nc_encoder->encode(substr($this->path, 0, $c)) .
+ $segments_encoder->encode(substr($this->path, $c));
+ } else {
+ $this->path = $segment_nc_encoder->encode($this->path);
+ }
+ }
+ } else {
+ // path-empty (hier and relative)
+ $this->path = ''; // just to be safe
+ }
+
+ // qf = query and fragment
+ $qf_encoder = new HTMLPurifier_PercentEncoder($chars_pchar . '/?');
+
+ if (!is_null($this->query)) {
+ $this->query = $qf_encoder->encode($this->query);
+ }
+
+ if (!is_null($this->fragment)) {
+ $this->fragment = $qf_encoder->encode($this->fragment);
+ }
+ return true;
+ }
+
+ /**
+ * Convert URI back to string
+ * @return string URI appropriate for output
+ */
+ public function toString()
+ {
+ // reconstruct authority
+ $authority = null;
+ // there is a rendering difference between a null authority
+ // (http:foo-bar) and an empty string authority
+ // (http:///foo-bar).
+ if (!is_null($this->host)) {
+ $authority = '';
+ if (!is_null($this->userinfo)) {
+ $authority .= $this->userinfo . '@';
+ }
+ $authority .= $this->host;
+ if (!is_null($this->port)) {
+ $authority .= ':' . $this->port;
+ }
+ }
+
+ // Reconstruct the result
+ // One might wonder about parsing quirks from browsers after
+ // this reconstruction. Unfortunately, parsing behavior depends
+ // on what *scheme* was employed (file:///foo is handled *very*
+ // differently than http:///foo), so unfortunately we have to
+ // defer to the schemes to do the right thing.
+ $result = '';
+ if (!is_null($this->scheme)) {
+ $result .= $this->scheme . ':';
+ }
+ if (!is_null($authority)) {
+ $result .= '//' . $authority;
+ }
+ $result .= $this->path;
+ if (!is_null($this->query)) {
+ $result .= '?' . $this->query;
+ }
+ if (!is_null($this->fragment)) {
+ $result .= '#' . $this->fragment;
+ }
+
+ return $result;
+ }
+
+ /**
+ * Returns true if this URL might be considered a 'local' URL given
+ * the current context. This is true when the host is null, or
+ * when it matches the host supplied to the configuration.
+ *
+ * Note that this does not do any scheme checking, so it is mostly
+ * only appropriate for metadata that doesn't care about protocol
+ * security. isBenign is probably what you actually want.
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return bool
+ */
+ public function isLocal($config, $context)
+ {
+ if ($this->host === null) {
+ return true;
+ }
+ $uri_def = $config->getDefinition('URI');
+ if ($uri_def->host === $this->host) {
+ return true;
+ }
+ return false;
+ }
+
+ /**
+ * Returns true if this URL should be considered a 'benign' URL,
+ * that is:
+ *
+ * - It is a local URL (isLocal), and
+ * - It has a equal or better level of security
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return bool
+ */
+ public function isBenign($config, $context)
+ {
+ if (!$this->isLocal($config, $context)) {
+ return false;
+ }
+
+ $scheme_obj = $this->getSchemeObj($config, $context);
+ if (!$scheme_obj) {
+ return false;
+ } // conservative approach
+
+ $current_scheme_obj = $config->getDefinition('URI')->getDefaultScheme($config, $context);
+ if ($current_scheme_obj->secure) {
+ if (!$scheme_obj->secure) {
+ return false;
+ }
+ }
+ return true;
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/URIDefinition.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIDefinition.php
index e0bd8bcca..e0bd8bcca 100644
--- a/library/HTMLPurifier/URIDefinition.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIDefinition.php
diff --git a/library/HTMLPurifier/URIFilter.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter.php
index 09724e9f4..09724e9f4 100644
--- a/library/HTMLPurifier/URIFilter.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter.php
diff --git a/library/HTMLPurifier/URIFilter/DisableExternal.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/DisableExternal.php
index ced1b1376..ced1b1376 100644
--- a/library/HTMLPurifier/URIFilter/DisableExternal.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/DisableExternal.php
diff --git a/library/HTMLPurifier/URIFilter/DisableExternalResources.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/DisableExternalResources.php
index c6562169e..c6562169e 100644
--- a/library/HTMLPurifier/URIFilter/DisableExternalResources.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/DisableExternalResources.php
diff --git a/library/HTMLPurifier/URIFilter/DisableResources.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/DisableResources.php
index d5c412c44..d5c412c44 100644
--- a/library/HTMLPurifier/URIFilter/DisableResources.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/DisableResources.php
diff --git a/library/HTMLPurifier/URIFilter/HostBlacklist.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/HostBlacklist.php
index a6645c17e..a6645c17e 100644
--- a/library/HTMLPurifier/URIFilter/HostBlacklist.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/HostBlacklist.php
diff --git a/library/HTMLPurifier/URIFilter/MakeAbsolute.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/MakeAbsolute.php
index c507bbff8..c507bbff8 100644
--- a/library/HTMLPurifier/URIFilter/MakeAbsolute.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/MakeAbsolute.php
diff --git a/library/HTMLPurifier/URIFilter/Munge.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/Munge.php
index 6e03315a1..6e03315a1 100644
--- a/library/HTMLPurifier/URIFilter/Munge.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/Munge.php
diff --git a/library/HTMLPurifier/URIFilter/SafeIframe.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/SafeIframe.php
index f609c47a3..f609c47a3 100644
--- a/library/HTMLPurifier/URIFilter/SafeIframe.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIFilter/SafeIframe.php
diff --git a/library/HTMLPurifier/URIParser.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIParser.php
index 0e7381a07..0e7381a07 100644
--- a/library/HTMLPurifier/URIParser.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIParser.php
diff --git a/library/HTMLPurifier/URIScheme.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme.php
index fe9e82cf2..fe9e82cf2 100644
--- a/library/HTMLPurifier/URIScheme.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/data.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/data.php
new file mode 100644
index 000000000..41c49d553
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/data.php
@@ -0,0 +1,136 @@
+<?php
+
+/**
+ * Implements data: URI for base64 encoded images supported by GD.
+ */
+class HTMLPurifier_URIScheme_data extends HTMLPurifier_URIScheme
+{
+ /**
+ * @type bool
+ */
+ public $browsable = true;
+
+ /**
+ * @type array
+ */
+ public $allowed_types = array(
+ // you better write validation code for other types if you
+ // decide to allow them
+ 'image/jpeg' => true,
+ 'image/gif' => true,
+ 'image/png' => true,
+ );
+ // this is actually irrelevant since we only write out the path
+ // component
+ /**
+ * @type bool
+ */
+ public $may_omit_host = true;
+
+ /**
+ * @param HTMLPurifier_URI $uri
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return bool
+ */
+ public function doValidate(&$uri, $config, $context)
+ {
+ $result = explode(',', $uri->path, 2);
+ $is_base64 = false;
+ $charset = null;
+ $content_type = null;
+ if (count($result) == 2) {
+ list($metadata, $data) = $result;
+ // do some legwork on the metadata
+ $metas = explode(';', $metadata);
+ while (!empty($metas)) {
+ $cur = array_shift($metas);
+ if ($cur == 'base64') {
+ $is_base64 = true;
+ break;
+ }
+ if (substr($cur, 0, 8) == 'charset=') {
+ // doesn't match if there are arbitrary spaces, but
+ // whatever dude
+ if ($charset !== null) {
+ continue;
+ } // garbage
+ $charset = substr($cur, 8); // not used
+ } else {
+ if ($content_type !== null) {
+ continue;
+ } // garbage
+ $content_type = $cur;
+ }
+ }
+ } else {
+ $data = $result[0];
+ }
+ if ($content_type !== null && empty($this->allowed_types[$content_type])) {
+ return false;
+ }
+ if ($charset !== null) {
+ // error; we don't allow plaintext stuff
+ $charset = null;
+ }
+ $data = rawurldecode($data);
+ if ($is_base64) {
+ $raw_data = base64_decode($data);
+ } else {
+ $raw_data = $data;
+ }
+ if ( strlen($raw_data) < 12 ) {
+ // error; exif_imagetype throws exception with small files,
+ // and this likely indicates a corrupt URI/failed parse anyway
+ return false;
+ }
+ // XXX probably want to refactor this into a general mechanism
+ // for filtering arbitrary content types
+ if (function_exists('sys_get_temp_dir')) {
+ $file = tempnam(sys_get_temp_dir(), "");
+ } else {
+ $file = tempnam("/tmp", "");
+ }
+ file_put_contents($file, $raw_data);
+ if (function_exists('exif_imagetype')) {
+ $image_code = exif_imagetype($file);
+ unlink($file);
+ } elseif (function_exists('getimagesize')) {
+ set_error_handler(array($this, 'muteErrorHandler'));
+ $info = getimagesize($file);
+ restore_error_handler();
+ unlink($file);
+ if ($info == false) {
+ return false;
+ }
+ $image_code = $info[2];
+ } else {
+ trigger_error("could not find exif_imagetype or getimagesize functions", E_USER_ERROR);
+ }
+ $real_content_type = image_type_to_mime_type($image_code);
+ if ($real_content_type != $content_type) {
+ // we're nice guys; if the content type is something else we
+ // support, change it over
+ if (empty($this->allowed_types[$real_content_type])) {
+ return false;
+ }
+ $content_type = $real_content_type;
+ }
+ // ok, it's kosher, rewrite what we need
+ $uri->userinfo = null;
+ $uri->host = null;
+ $uri->port = null;
+ $uri->fragment = null;
+ $uri->query = null;
+ $uri->path = "$content_type;base64," . base64_encode($raw_data);
+ return true;
+ }
+
+ /**
+ * @param int $errno
+ * @param string $errstr
+ */
+ public function muteErrorHandler($errno, $errstr)
+ {
+ }
+}
diff --git a/library/HTMLPurifier/URIScheme/file.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/file.php
index 215be4ba8..215be4ba8 100644
--- a/library/HTMLPurifier/URIScheme/file.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/file.php
diff --git a/library/HTMLPurifier/URIScheme/ftp.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/ftp.php
index 1eb43ee5c..1eb43ee5c 100644
--- a/library/HTMLPurifier/URIScheme/ftp.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/ftp.php
diff --git a/library/HTMLPurifier/URIScheme/http.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/http.php
index ce69ec438..ce69ec438 100644
--- a/library/HTMLPurifier/URIScheme/http.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/http.php
diff --git a/library/HTMLPurifier/URIScheme/https.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/https.php
index 0e96882db..0e96882db 100644
--- a/library/HTMLPurifier/URIScheme/https.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/https.php
diff --git a/library/HTMLPurifier/URIScheme/mailto.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/mailto.php
index c3a6b602a..c3a6b602a 100644
--- a/library/HTMLPurifier/URIScheme/mailto.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/mailto.php
diff --git a/library/HTMLPurifier/URIScheme/news.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/news.php
index 7490927d6..7490927d6 100644
--- a/library/HTMLPurifier/URIScheme/news.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/news.php
diff --git a/library/HTMLPurifier/URIScheme/nntp.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/nntp.php
index f211d715e..f211d715e 100644
--- a/library/HTMLPurifier/URIScheme/nntp.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/nntp.php
diff --git a/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/tel.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/tel.php
new file mode 100644
index 000000000..8cd193352
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URIScheme/tel.php
@@ -0,0 +1,46 @@
+<?php
+
+/**
+ * Validates tel (for phone numbers).
+ *
+ * The relevant specifications for this protocol are RFC 3966 and RFC 5341,
+ * but this class takes a much simpler approach: we normalize phone
+ * numbers so that they only include (possibly) a leading plus,
+ * and then any number of digits and x'es.
+ */
+
+class HTMLPurifier_URIScheme_tel extends HTMLPurifier_URIScheme
+{
+ /**
+ * @type bool
+ */
+ public $browsable = false;
+
+ /**
+ * @type bool
+ */
+ public $may_omit_host = true;
+
+ /**
+ * @param HTMLPurifier_URI $uri
+ * @param HTMLPurifier_Config $config
+ * @param HTMLPurifier_Context $context
+ * @return bool
+ */
+ public function doValidate(&$uri, $config, $context)
+ {
+ $uri->userinfo = null;
+ $uri->host = null;
+ $uri->port = null;
+
+ // Delete all non-numeric characters, non-x characters
+ // from phone number, EXCEPT for a leading plus sign.
+ $uri->path = preg_replace('/(?!^\+)[^\dx]/', '',
+ // Normalize e(x)tension to lower-case
+ str_replace('X', 'x', $uri->path));
+
+ return true;
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/library/HTMLPurifier/URISchemeRegistry.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URISchemeRegistry.php
index 4ac8a0b76..4ac8a0b76 100644
--- a/library/HTMLPurifier/URISchemeRegistry.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/URISchemeRegistry.php
diff --git a/library/HTMLPurifier/UnitConverter.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/UnitConverter.php
index 166f3bf30..166f3bf30 100644
--- a/library/HTMLPurifier/UnitConverter.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/UnitConverter.php
diff --git a/library/HTMLPurifier/VarParser.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/VarParser.php
index 50cba6910..50cba6910 100644
--- a/library/HTMLPurifier/VarParser.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/VarParser.php
diff --git a/library/HTMLPurifier/VarParser/Flexible.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/VarParser/Flexible.php
index b15016c5b..b15016c5b 100644
--- a/library/HTMLPurifier/VarParser/Flexible.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/VarParser/Flexible.php
diff --git a/library/HTMLPurifier/VarParser/Native.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/VarParser/Native.php
index f11c318ef..f11c318ef 100644
--- a/library/HTMLPurifier/VarParser/Native.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/VarParser/Native.php
diff --git a/library/HTMLPurifier/VarParserException.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/VarParserException.php
index 5df341495..5df341495 100644
--- a/library/HTMLPurifier/VarParserException.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/VarParserException.php
diff --git a/library/HTMLPurifier/Zipper.php b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Zipper.php
index 6e21ea070..6e21ea070 100644
--- a/library/HTMLPurifier/Zipper.php
+++ b/vendor/ezyang/htmlpurifier/library/HTMLPurifier/Zipper.php
diff --git a/vendor/ezyang/htmlpurifier/maintenance/.htaccess b/vendor/ezyang/htmlpurifier/maintenance/.htaccess
new file mode 100644
index 000000000..3a4288278
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/maintenance/.htaccess
@@ -0,0 +1 @@
+Deny from all
diff --git a/vendor/ezyang/htmlpurifier/maintenance/PH5P.patch b/vendor/ezyang/htmlpurifier/maintenance/PH5P.patch
new file mode 100644
index 000000000..763709509
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/maintenance/PH5P.patch
@@ -0,0 +1,102 @@
+--- C:\Users\Edward\Webs\htmlpurifier\maintenance\PH5P.php 2008-07-07 09:12:12.000000000 -0400
++++ C:\Users\Edward\Webs\htmlpurifier\maintenance/PH5P.new.php 2008-12-06 02:29:34.988800000 -0500
+@@ -65,7 +65,7 @@
+
+ public function __construct($data) {
+ $data = str_replace("\r\n", "\n", $data);
+- $date = str_replace("\r", null, $data);
++ $data = str_replace("\r", null, $data);
+
+ $this->data = $data;
+ $this->char = -1;
+@@ -211,7 +211,10 @@
+ // If nothing is returned, emit a U+0026 AMPERSAND character token.
+ // Otherwise, emit the character token that was returned.
+ $char = (!$entity) ? '&' : $entity;
+- $this->emitToken($char);
++ $this->emitToken(array(
++ 'type' => self::CHARACTR,
++ 'data' => $char
++ ));
+
+ // Finally, switch to the data state.
+ $this->state = 'data';
+@@ -708,7 +711,7 @@
+ } elseif($char === '&') {
+ /* U+0026 AMPERSAND (&)
+ Switch to the entity in attribute value state. */
+- $this->entityInAttributeValueState('non');
++ $this->entityInAttributeValueState();
+
+ } elseif($char === '>') {
+ /* U+003E GREATER-THAN SIGN (>)
+@@ -738,7 +741,8 @@
+ ? '&'
+ : $entity;
+
+- $this->emitToken($char);
++ $last = count($this->token['attr']) - 1;
++ $this->token['attr'][$last]['value'] .= $char;
+ }
+
+ private function bogusCommentState() {
+@@ -1066,6 +1070,11 @@
+ $this->char++;
+
+ if(in_array($id, $this->entities)) {
++ if ($e_name[$c-1] !== ';') {
++ if ($c < $len && $e_name[$c] == ';') {
++ $this->char++; // consume extra semicolon
++ }
++ }
+ $entity = $id;
+ break;
+ }
+@@ -2084,7 +2093,7 @@
+ /* Reconstruct the active formatting elements, if any. */
+ $this->reconstructActiveFormattingElements();
+
+- $this->insertElement($token);
++ $this->insertElement($token, true, true);
+ break;
+ }
+ break;
+@@ -3465,7 +3474,18 @@
+ }
+ }
+
+- private function insertElement($token, $append = true) {
++ private function insertElement($token, $append = true, $check = false) {
++ // Proprietary workaround for libxml2's limitations with tag names
++ if ($check) {
++ // Slightly modified HTML5 tag-name modification,
++ // removing anything that's not an ASCII letter, digit, or hyphen
++ $token['name'] = preg_replace('/[^a-z0-9-]/i', '', $token['name']);
++ // Remove leading hyphens and numbers
++ $token['name'] = ltrim($token['name'], '-0..9');
++ // In theory, this should ever be needed, but just in case
++ if ($token['name'] === '') $token['name'] = 'span'; // arbitrary generic choice
++ }
++
+ $el = $this->dom->createElement($token['name']);
+
+ foreach($token['attr'] as $attr) {
+@@ -3659,7 +3679,7 @@
+ }
+ }
+
+- private function generateImpliedEndTags(array $exclude = array()) {
++ private function generateImpliedEndTags($exclude = array()) {
+ /* When the steps below require the UA to generate implied end tags,
+ then, if the current node is a dd element, a dt element, an li element,
+ a p element, a td element, a th element, or a tr element, the UA must
+@@ -3673,7 +3693,8 @@
+ }
+ }
+
+- private function getElementCategory($name) {
++ private function getElementCategory($node) {
++ $name = $node->tagName;
+ if(in_array($name, $this->special))
+ return self::SPECIAL;
+
diff --git a/vendor/ezyang/htmlpurifier/maintenance/PH5P.php b/vendor/ezyang/htmlpurifier/maintenance/PH5P.php
new file mode 100644
index 000000000..9d83dcbf5
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/maintenance/PH5P.php
@@ -0,0 +1,3889 @@
+<?php
+class HTML5
+{
+ private $data;
+ private $char;
+ private $EOF;
+ private $state;
+ private $tree;
+ private $token;
+ private $content_model;
+ private $escape = false;
+ private $entities = array('AElig;','AElig','AMP;','AMP','Aacute;','Aacute',
+ 'Acirc;','Acirc','Agrave;','Agrave','Alpha;','Aring;','Aring','Atilde;',
+ 'Atilde','Auml;','Auml','Beta;','COPY;','COPY','Ccedil;','Ccedil','Chi;',
+ 'Dagger;','Delta;','ETH;','ETH','Eacute;','Eacute','Ecirc;','Ecirc','Egrave;',
+ 'Egrave','Epsilon;','Eta;','Euml;','Euml','GT;','GT','Gamma;','Iacute;',
+ 'Iacute','Icirc;','Icirc','Igrave;','Igrave','Iota;','Iuml;','Iuml','Kappa;',
+ 'LT;','LT','Lambda;','Mu;','Ntilde;','Ntilde','Nu;','OElig;','Oacute;',
+ 'Oacute','Ocirc;','Ocirc','Ograve;','Ograve','Omega;','Omicron;','Oslash;',
+ 'Oslash','Otilde;','Otilde','Ouml;','Ouml','Phi;','Pi;','Prime;','Psi;',
+ 'QUOT;','QUOT','REG;','REG','Rho;','Scaron;','Sigma;','THORN;','THORN',
+ 'TRADE;','Tau;','Theta;','Uacute;','Uacute','Ucirc;','Ucirc','Ugrave;',
+ 'Ugrave','Upsilon;','Uuml;','Uuml','Xi;','Yacute;','Yacute','Yuml;','Zeta;',
+ 'aacute;','aacute','acirc;','acirc','acute;','acute','aelig;','aelig',
+ 'agrave;','agrave','alefsym;','alpha;','amp;','amp','and;','ang;','apos;',
+ 'aring;','aring','asymp;','atilde;','atilde','auml;','auml','bdquo;','beta;',
+ 'brvbar;','brvbar','bull;','cap;','ccedil;','ccedil','cedil;','cedil',
+ 'cent;','cent','chi;','circ;','clubs;','cong;','copy;','copy','crarr;',
+ 'cup;','curren;','curren','dArr;','dagger;','darr;','deg;','deg','delta;',
+ 'diams;','divide;','divide','eacute;','eacute','ecirc;','ecirc','egrave;',
+ 'egrave','empty;','emsp;','ensp;','epsilon;','equiv;','eta;','eth;','eth',
+ 'euml;','euml','euro;','exist;','fnof;','forall;','frac12;','frac12',
+ 'frac14;','frac14','frac34;','frac34','frasl;','gamma;','ge;','gt;','gt',
+ 'hArr;','harr;','hearts;','hellip;','iacute;','iacute','icirc;','icirc',
+ 'iexcl;','iexcl','igrave;','igrave','image;','infin;','int;','iota;',
+ 'iquest;','iquest','isin;','iuml;','iuml','kappa;','lArr;','lambda;','lang;',
+ 'laquo;','laquo','larr;','lceil;','ldquo;','le;','lfloor;','lowast;','loz;',
+ 'lrm;','lsaquo;','lsquo;','lt;','lt','macr;','macr','mdash;','micro;','micro',
+ 'middot;','middot','minus;','mu;','nabla;','nbsp;','nbsp','ndash;','ne;',
+ 'ni;','not;','not','notin;','nsub;','ntilde;','ntilde','nu;','oacute;',
+ 'oacute','ocirc;','ocirc','oelig;','ograve;','ograve','oline;','omega;',
+ 'omicron;','oplus;','or;','ordf;','ordf','ordm;','ordm','oslash;','oslash',
+ 'otilde;','otilde','otimes;','ouml;','ouml','para;','para','part;','permil;',
+ 'perp;','phi;','pi;','piv;','plusmn;','plusmn','pound;','pound','prime;',
+ 'prod;','prop;','psi;','quot;','quot','rArr;','radic;','rang;','raquo;',
+ 'raquo','rarr;','rceil;','rdquo;','real;','reg;','reg','rfloor;','rho;',
+ 'rlm;','rsaquo;','rsquo;','sbquo;','scaron;','sdot;','sect;','sect','shy;',
+ 'shy','sigma;','sigmaf;','sim;','spades;','sub;','sube;','sum;','sup1;',
+ 'sup1','sup2;','sup2','sup3;','sup3','sup;','supe;','szlig;','szlig','tau;',
+ 'there4;','theta;','thetasym;','thinsp;','thorn;','thorn','tilde;','times;',
+ 'times','trade;','uArr;','uacute;','uacute','uarr;','ucirc;','ucirc',
+ 'ugrave;','ugrave','uml;','uml','upsih;','upsilon;','uuml;','uuml','weierp;',
+ 'xi;','yacute;','yacute','yen;','yen','yuml;','yuml','zeta;','zwj;','zwnj;');
+
+ const PCDATA = 0;
+ const RCDATA = 1;
+ const CDATA = 2;
+ const PLAINTEXT = 3;
+
+ const DOCTYPE = 0;
+ const STARTTAG = 1;
+ const ENDTAG = 2;
+ const COMMENT = 3;
+ const CHARACTR = 4;
+ const EOF = 5;
+
+ public function __construct($data)
+ {
+ $data = str_replace("\r\n", "\n", $data);
+ $date = str_replace("\r", null, $data);
+
+ $this->data = $data;
+ $this->char = -1;
+ $this->EOF = strlen($data);
+ $this->tree = new HTML5TreeConstructer;
+ $this->content_model = self::PCDATA;
+
+ $this->state = 'data';
+
+ while($this->state !== null) {
+ $this->{$this->state.'State'}();
+ }
+ }
+
+ public function save()
+ {
+ return $this->tree->save();
+ }
+
+ private function char()
+ {
+ return ($this->char < $this->EOF)
+ ? $this->data[$this->char]
+ : false;
+ }
+
+ private function character($s, $l = 0)
+ {
+ if($s + $l < $this->EOF) {
+ if($l === 0) {
+ return $this->data[$s];
+ } else {
+ return substr($this->data, $s, $l);
+ }
+ }
+ }
+
+ private function characters($char_class, $start)
+ {
+ return preg_replace('#^(['.$char_class.']+).*#s', '\\1', substr($this->data, $start));
+ }
+
+ private function dataState()
+ {
+ // Consume the next input character
+ $this->char++;
+ $char = $this->char();
+
+ if($char === '&' && ($this->content_model === self::PCDATA || $this->content_model === self::RCDATA)) {
+ /* U+0026 AMPERSAND (&)
+ When the content model flag is set to one of the PCDATA or RCDATA
+ states: switch to the entity data state. Otherwise: treat it as per
+ the "anything else" entry below. */
+ $this->state = 'entityData';
+
+ } elseif($char === '-') {
+ /* If the content model flag is set to either the RCDATA state or
+ the CDATA state, and the escape flag is false, and there are at
+ least three characters before this one in the input stream, and the
+ last four characters in the input stream, including this one, are
+ U+003C LESS-THAN SIGN, U+0021 EXCLAMATION MARK, U+002D HYPHEN-MINUS,
+ and U+002D HYPHEN-MINUS ("<!--"), then set the escape flag to true. */
+ if(($this->content_model === self::RCDATA || $this->content_model ===
+ self::CDATA) && $this->escape === false &&
+ $this->char >= 3 && $this->character($this->char - 4, 4) === '<!--') {
+ $this->escape = true;
+ }
+
+ /* In any case, emit the input character as a character token. Stay
+ in the data state. */
+ $this->emitToken(array(
+ 'type' => self::CHARACTR,
+ 'data' => $char
+ ));
+
+ /* U+003C LESS-THAN SIGN (<) */
+ } elseif($char === '<' && ($this->content_model === self::PCDATA ||
+ (($this->content_model === self::RCDATA ||
+ $this->content_model === self::CDATA) && $this->escape === false))) {
+ /* When the content model flag is set to the PCDATA state: switch
+ to the tag open state.
+
+ When the content model flag is set to either the RCDATA state or
+ the CDATA state and the escape flag is false: switch to the tag
+ open state.
+
+ Otherwise: treat it as per the "anything else" entry below. */
+ $this->state = 'tagOpen';
+
+ /* U+003E GREATER-THAN SIGN (>) */
+ } elseif($char === '>') {
+ /* If the content model flag is set to either the RCDATA state or
+ the CDATA state, and the escape flag is true, and the last three
+ characters in the input stream including this one are U+002D
+ HYPHEN-MINUS, U+002D HYPHEN-MINUS, U+003E GREATER-THAN SIGN ("-->"),
+ set the escape flag to false. */
+ if(($this->content_model === self::RCDATA ||
+ $this->content_model === self::CDATA) && $this->escape === true &&
+ $this->character($this->char, 3) === '-->') {
+ $this->escape = false;
+ }
+
+ /* In any case, emit the input character as a character token.
+ Stay in the data state. */
+ $this->emitToken(array(
+ 'type' => self::CHARACTR,
+ 'data' => $char
+ ));
+
+ } elseif($this->char === $this->EOF) {
+ /* EOF
+ Emit an end-of-file token. */
+ $this->EOF();
+
+ } elseif($this->content_model === self::PLAINTEXT) {
+ /* When the content model flag is set to the PLAINTEXT state
+ THIS DIFFERS GREATLY FROM THE SPEC: Get the remaining characters of
+ the text and emit it as a character token. */
+ $this->emitToken(array(
+ 'type' => self::CHARACTR,
+ 'data' => substr($this->data, $this->char)
+ ));
+
+ $this->EOF();
+
+ } else {
+ /* Anything else
+ THIS DIFFERS GREATLY FROM THE SPEC: Get as many character that
+ otherwise would also be treated as a character token and emit it
+ as a single character token. Stay in the data state. */
+ $len = strcspn($this->data, '<&', $this->char);
+ $char = substr($this->data, $this->char, $len);
+ $this->char += $len - 1;
+
+ $this->emitToken(array(
+ 'type' => self::CHARACTR,
+ 'data' => $char
+ ));
+
+ $this->state = 'data';
+ }
+ }
+
+ private function entityDataState()
+ {
+ // Attempt to consume an entity.
+ $entity = $this->entity();
+
+ // If nothing is returned, emit a U+0026 AMPERSAND character token.
+ // Otherwise, emit the character token that was returned.
+ $char = (!$entity) ? '&' : $entity;
+ $this->emitToken($char);
+
+ // Finally, switch to the data state.
+ $this->state = 'data';
+ }
+
+ private function tagOpenState()
+ {
+ switch($this->content_model) {
+ case self::RCDATA:
+ case self::CDATA:
+ /* If the next input character is a U+002F SOLIDUS (/) character,
+ consume it and switch to the close tag open state. If the next
+ input character is not a U+002F SOLIDUS (/) character, emit a
+ U+003C LESS-THAN SIGN character token and switch to the data
+ state to process the next input character. */
+ if($this->character($this->char + 1) === '/') {
+ $this->char++;
+ $this->state = 'closeTagOpen';
+
+ } else {
+ $this->emitToken(array(
+ 'type' => self::CHARACTR,
+ 'data' => '<'
+ ));
+
+ $this->state = 'data';
+ }
+ break;
+
+ case self::PCDATA:
+ // If the content model flag is set to the PCDATA state
+ // Consume the next input character:
+ $this->char++;
+ $char = $this->char();
+
+ if($char === '!') {
+ /* U+0021 EXCLAMATION MARK (!)
+ Switch to the markup declaration open state. */
+ $this->state = 'markupDeclarationOpen';
+
+ } elseif($char === '/') {
+ /* U+002F SOLIDUS (/)
+ Switch to the close tag open state. */
+ $this->state = 'closeTagOpen';
+
+ } elseif(preg_match('/^[A-Za-z]$/', $char)) {
+ /* U+0041 LATIN LETTER A through to U+005A LATIN LETTER Z
+ Create a new start tag token, set its tag name to the lowercase
+ version of the input character (add 0x0020 to the character's code
+ point), then switch to the tag name state. (Don't emit the token
+ yet; further details will be filled in before it is emitted.) */
+ $this->token = array(
+ 'name' => strtolower($char),
+ 'type' => self::STARTTAG,
+ 'attr' => array()
+ );
+
+ $this->state = 'tagName';
+
+ } elseif($char === '>') {
+ /* U+003E GREATER-THAN SIGN (>)
+ Parse error. Emit a U+003C LESS-THAN SIGN character token and a
+ U+003E GREATER-THAN SIGN character token. Switch to the data state. */
+ $this->emitToken(array(
+ 'type' => self::CHARACTR,
+ 'data' => '<>'
+ ));
+
+ $this->state = 'data';
+
+ } elseif($char === '?') {
+ /* U+003F QUESTION MARK (?)
+ Parse error. Switch to the bogus comment state. */
+ $this->state = 'bogusComment';
+
+ } else {
+ /* Anything else
+ Parse error. Emit a U+003C LESS-THAN SIGN character token and
+ reconsume the current input character in the data state. */
+ $this->emitToken(array(
+ 'type' => self::CHARACTR,
+ 'data' => '<'
+ ));
+
+ $this->char--;
+ $this->state = 'data';
+ }
+ break;
+ }
+ }
+
+ private function closeTagOpenState()
+ {
+ $next_node = strtolower($this->characters('A-Za-z', $this->char + 1));
+ $the_same = count($this->tree->stack) > 0 && $next_node === end($this->tree->stack)->nodeName;
+
+ if(($this->content_model === self::RCDATA || $this->content_model === self::CDATA) &&
+ (!$the_same || ($the_same && (!preg_match('/[\t\n\x0b\x0c >\/]/',
+ $this->character($this->char + 1 + strlen($next_node))) || $this->EOF === $this->char)))) {
+ /* If the content model flag is set to the RCDATA or CDATA states then
+ examine the next few characters. If they do not match the tag name of
+ the last start tag token emitted (case insensitively), or if they do but
+ they are not immediately followed by one of the following characters:
+ * U+0009 CHARACTER TABULATION
+ * U+000A LINE FEED (LF)
+ * U+000B LINE TABULATION
+ * U+000C FORM FEED (FF)
+ * U+0020 SPACE
+ * U+003E GREATER-THAN SIGN (>)
+ * U+002F SOLIDUS (/)
+ * EOF
+ ...then there is a parse error. Emit a U+003C LESS-THAN SIGN character
+ token, a U+002F SOLIDUS character token, and switch to the data state
+ to process the next input character. */
+ $this->emitToken(array(
+ 'type' => self::CHARACTR,
+ 'data' => '</'
+ ));
+
+ $this->state = 'data';
+
+ } else {
+ /* Otherwise, if the content model flag is set to the PCDATA state,
+ or if the next few characters do match that tag name, consume the
+ next input character: */
+ $this->char++;
+ $char = $this->char();
+
+ if(preg_match('/^[A-Za-z]$/', $char)) {
+ /* U+0041 LATIN LETTER A through to U+005A LATIN LETTER Z
+ Create a new end tag token, set its tag name to the lowercase version
+ of the input character (add 0x0020 to the character's code point), then
+ switch to the tag name state. (Don't emit the token yet; further details
+ will be filled in before it is emitted.) */
+ $this->token = array(
+ 'name' => strtolower($char),
+ 'type' => self::ENDTAG
+ );
+
+ $this->state = 'tagName';
+
+ } elseif($char === '>') {
+ /* U+003E GREATER-THAN SIGN (>)
+ Parse error. Switch to the data state. */
+ $this->state = 'data';
+
+ } elseif($this->char === $this->EOF) {
+ /* EOF
+ Parse error. Emit a U+003C LESS-THAN SIGN character token and a U+002F
+ SOLIDUS character token. Reconsume the EOF character in the data state. */
+ $this->emitToken(array(
+ 'type' => self::CHARACTR,
+ 'data' => '</'
+ ));
+
+ $this->char--;
+ $this->state = 'data';
+
+ } else {
+ /* Parse error. Switch to the bogus comment state. */
+ $this->state = 'bogusComment';
+ }
+ }
+ }
+
+ private function tagNameState()
+ {
+ // Consume the next input character:
+ $this->char++;
+ $char = $this->character($this->char);
+
+ if(preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
+ /* U+0009 CHARACTER TABULATION
+ U+000A LINE FEED (LF)
+ U+000B LINE TABULATION
+ U+000C FORM FEED (FF)
+ U+0020 SPACE
+ Switch to the before attribute name state. */
+ $this->state = 'beforeAttributeName';
+
+ } elseif($char === '>') {
+ /* U+003E GREATER-THAN SIGN (>)
+ Emit the current tag token. Switch to the data state. */
+ $this->emitToken($this->token);
+ $this->state = 'data';
+
+ } elseif($this->char === $this->EOF) {
+ /* EOF
+ Parse error. Emit the current tag token. Reconsume the EOF
+ character in the data state. */
+ $this->emitToken($this->token);
+
+ $this->char--;
+ $this->state = 'data';
+
+ } elseif($char === '/') {
+ /* U+002F SOLIDUS (/)
+ Parse error unless this is a permitted slash. Switch to the before
+ attribute name state. */
+ $this->state = 'beforeAttributeName';
+
+ } else {
+ /* Anything else
+ Append the current input character to the current tag token's tag name.
+ Stay in the tag name state. */
+ $this->token['name'] .= strtolower($char);
+ $this->state = 'tagName';
+ }
+ }
+
+ private function beforeAttributeNameState()
+ {
+ // Consume the next input character:
+ $this->char++;
+ $char = $this->character($this->char);
+
+ if(preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
+ /* U+0009 CHARACTER TABULATION
+ U+000A LINE FEED (LF)
+ U+000B LINE TABULATION
+ U+000C FORM FEED (FF)
+ U+0020 SPACE
+ Stay in the before attribute name state. */
+ $this->state = 'beforeAttributeName';
+
+ } elseif($char === '>') {
+ /* U+003E GREATER-THAN SIGN (>)
+ Emit the current tag token. Switch to the data state. */
+ $this->emitToken($this->token);
+ $this->state = 'data';
+
+ } elseif($char === '/') {
+ /* U+002F SOLIDUS (/)
+ Parse error unless this is a permitted slash. Stay in the before
+ attribute name state. */
+ $this->state = 'beforeAttributeName';
+
+ } elseif($this->char === $this->EOF) {
+ /* EOF
+ Parse error. Emit the current tag token. Reconsume the EOF
+ character in the data state. */
+ $this->emitToken($this->token);
+
+ $this->char--;
+ $this->state = 'data';
+
+ } else {
+ /* Anything else
+ Start a new attribute in the current tag token. Set that attribute's
+ name to the current input character, and its value to the empty string.
+ Switch to the attribute name state. */
+ $this->token['attr'][] = array(
+ 'name' => strtolower($char),
+ 'value' => null
+ );
+
+ $this->state = 'attributeName';
+ }
+ }
+
+ private function attributeNameState()
+ {
+ // Consume the next input character:
+ $this->char++;
+ $char = $this->character($this->char);
+
+ if(preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
+ /* U+0009 CHARACTER TABULATION
+ U+000A LINE FEED (LF)
+ U+000B LINE TABULATION
+ U+000C FORM FEED (FF)
+ U+0020 SPACE
+ Stay in the before attribute name state. */
+ $this->state = 'afterAttributeName';
+
+ } elseif($char === '=') {
+ /* U+003D EQUALS SIGN (=)
+ Switch to the before attribute value state. */
+ $this->state = 'beforeAttributeValue';
+
+ } elseif($char === '>') {
+ /* U+003E GREATER-THAN SIGN (>)
+ Emit the current tag token. Switch to the data state. */
+ $this->emitToken($this->token);
+ $this->state = 'data';
+
+ } elseif($char === '/' && $this->character($this->char + 1) !== '>') {
+ /* U+002F SOLIDUS (/)
+ Parse error unless this is a permitted slash. Switch to the before
+ attribute name state. */
+ $this->state = 'beforeAttributeName';
+
+ } elseif($this->char === $this->EOF) {
+ /* EOF
+ Parse error. Emit the current tag token. Reconsume the EOF
+ character in the data state. */
+ $this->emitToken($this->token);
+
+ $this->char--;
+ $this->state = 'data';
+
+ } else {
+ /* Anything else
+ Append the current input character to the current attribute's name.
+ Stay in the attribute name state. */
+ $last = count($this->token['attr']) - 1;
+ $this->token['attr'][$last]['name'] .= strtolower($char);
+
+ $this->state = 'attributeName';
+ }
+ }
+
+ private function afterAttributeNameState()
+ {
+ // Consume the next input character:
+ $this->char++;
+ $char = $this->character($this->char);
+
+ if(preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
+ /* U+0009 CHARACTER TABULATION
+ U+000A LINE FEED (LF)
+ U+000B LINE TABULATION
+ U+000C FORM FEED (FF)
+ U+0020 SPACE
+ Stay in the after attribute name state. */
+ $this->state = 'afterAttributeName';
+
+ } elseif($char === '=') {
+ /* U+003D EQUALS SIGN (=)
+ Switch to the before attribute value state. */
+ $this->state = 'beforeAttributeValue';
+
+ } elseif($char === '>') {
+ /* U+003E GREATER-THAN SIGN (>)
+ Emit the current tag token. Switch to the data state. */
+ $this->emitToken($this->token);
+ $this->state = 'data';
+
+ } elseif($char === '/' && $this->character($this->char + 1) !== '>') {
+ /* U+002F SOLIDUS (/)
+ Parse error unless this is a permitted slash. Switch to the
+ before attribute name state. */
+ $this->state = 'beforeAttributeName';
+
+ } elseif($this->char === $this->EOF) {
+ /* EOF
+ Parse error. Emit the current tag token. Reconsume the EOF
+ character in the data state. */
+ $this->emitToken($this->token);
+
+ $this->char--;
+ $this->state = 'data';
+
+ } else {
+ /* Anything else
+ Start a new attribute in the current tag token. Set that attribute's
+ name to the current input character, and its value to the empty string.
+ Switch to the attribute name state. */
+ $this->token['attr'][] = array(
+ 'name' => strtolower($char),
+ 'value' => null
+ );
+
+ $this->state = 'attributeName';
+ }
+ }
+
+ private function beforeAttributeValueState()
+ {
+ // Consume the next input character:
+ $this->char++;
+ $char = $this->character($this->char);
+
+ if(preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
+ /* U+0009 CHARACTER TABULATION
+ U+000A LINE FEED (LF)
+ U+000B LINE TABULATION
+ U+000C FORM FEED (FF)
+ U+0020 SPACE
+ Stay in the before attribute value state. */
+ $this->state = 'beforeAttributeValue';
+
+ } elseif($char === '"') {
+ /* U+0022 QUOTATION MARK (")
+ Switch to the attribute value (double-quoted) state. */
+ $this->state = 'attributeValueDoubleQuoted';
+
+ } elseif($char === '&') {
+ /* U+0026 AMPERSAND (&)
+ Switch to the attribute value (unquoted) state and reconsume
+ this input character. */
+ $this->char--;
+ $this->state = 'attributeValueUnquoted';
+
+ } elseif($char === '\'') {
+ /* U+0027 APOSTROPHE (')
+ Switch to the attribute value (single-quoted) state. */
+ $this->state = 'attributeValueSingleQuoted';
+
+ } elseif($char === '>') {
+ /* U+003E GREATER-THAN SIGN (>)
+ Emit the current tag token. Switch to the data state. */
+ $this->emitToken($this->token);
+ $this->state = 'data';
+
+ } else {
+ /* Anything else
+ Append the current input character to the current attribute's value.
+ Switch to the attribute value (unquoted) state. */
+ $last = count($this->token['attr']) - 1;
+ $this->token['attr'][$last]['value'] .= $char;
+
+ $this->state = 'attributeValueUnquoted';
+ }
+ }
+
+ private function attributeValueDoubleQuotedState()
+ {
+ // Consume the next input character:
+ $this->char++;
+ $char = $this->character($this->char);
+
+ if($char === '"') {
+ /* U+0022 QUOTATION MARK (")
+ Switch to the before attribute name state. */
+ $this->state = 'beforeAttributeName';
+
+ } elseif($char === '&') {
+ /* U+0026 AMPERSAND (&)
+ Switch to the entity in attribute value state. */
+ $this->entityInAttributeValueState('double');
+
+ } elseif($this->char === $this->EOF) {
+ /* EOF
+ Parse error. Emit the current tag token. Reconsume the character
+ in the data state. */
+ $this->emitToken($this->token);
+
+ $this->char--;
+ $this->state = 'data';
+
+ } else {
+ /* Anything else
+ Append the current input character to the current attribute's value.
+ Stay in the attribute value (double-quoted) state. */
+ $last = count($this->token['attr']) - 1;
+ $this->token['attr'][$last]['value'] .= $char;
+
+ $this->state = 'attributeValueDoubleQuoted';
+ }
+ }
+
+ private function attributeValueSingleQuotedState()
+ {
+ // Consume the next input character:
+ $this->char++;
+ $char = $this->character($this->char);
+
+ if($char === '\'') {
+ /* U+0022 QUOTATION MARK (')
+ Switch to the before attribute name state. */
+ $this->state = 'beforeAttributeName';
+
+ } elseif($char === '&') {
+ /* U+0026 AMPERSAND (&)
+ Switch to the entity in attribute value state. */
+ $this->entityInAttributeValueState('single');
+
+ } elseif($this->char === $this->EOF) {
+ /* EOF
+ Parse error. Emit the current tag token. Reconsume the character
+ in the data state. */
+ $this->emitToken($this->token);
+
+ $this->char--;
+ $this->state = 'data';
+
+ } else {
+ /* Anything else
+ Append the current input character to the current attribute's value.
+ Stay in the attribute value (single-quoted) state. */
+ $last = count($this->token['attr']) - 1;
+ $this->token['attr'][$last]['value'] .= $char;
+
+ $this->state = 'attributeValueSingleQuoted';
+ }
+ }
+
+ private function attributeValueUnquotedState()
+ {
+ // Consume the next input character:
+ $this->char++;
+ $char = $this->character($this->char);
+
+ if(preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
+ /* U+0009 CHARACTER TABULATION
+ U+000A LINE FEED (LF)
+ U+000B LINE TABULATION
+ U+000C FORM FEED (FF)
+ U+0020 SPACE
+ Switch to the before attribute name state. */
+ $this->state = 'beforeAttributeName';
+
+ } elseif($char === '&') {
+ /* U+0026 AMPERSAND (&)
+ Switch to the entity in attribute value state. */
+ $this->entityInAttributeValueState('non');
+
+ } elseif($char === '>') {
+ /* U+003E GREATER-THAN SIGN (>)
+ Emit the current tag token. Switch to the data state. */
+ $this->emitToken($this->token);
+ $this->state = 'data';
+
+ } else {
+ /* Anything else
+ Append the current input character to the current attribute's value.
+ Stay in the attribute value (unquoted) state. */
+ $last = count($this->token['attr']) - 1;
+ $this->token['attr'][$last]['value'] .= $char;
+
+ $this->state = 'attributeValueUnquoted';
+ }
+ }
+
+ private function entityInAttributeValueState()
+ {
+ // Attempt to consume an entity.
+ $entity = $this->entity();
+
+ // If nothing is returned, append a U+0026 AMPERSAND character to the
+ // current attribute's value. Otherwise, emit the character token that
+ // was returned.
+ $char = (!$entity)
+ ? '&'
+ : $entity;
+
+ $this->emitToken($char);
+ }
+
+ private function bogusCommentState()
+ {
+ /* Consume every character up to the first U+003E GREATER-THAN SIGN
+ character (>) or the end of the file (EOF), whichever comes first. Emit
+ a comment token whose data is the concatenation of all the characters
+ starting from and including the character that caused the state machine
+ to switch into the bogus comment state, up to and including the last
+ consumed character before the U+003E character, if any, or up to the
+ end of the file otherwise. (If the comment was started by the end of
+ the file (EOF), the token is empty.) */
+ $data = $this->characters('^>', $this->char);
+ $this->emitToken(array(
+ 'data' => $data,
+ 'type' => self::COMMENT
+ ));
+
+ $this->char += strlen($data);
+
+ /* Switch to the data state. */
+ $this->state = 'data';
+
+ /* If the end of the file was reached, reconsume the EOF character. */
+ if($this->char === $this->EOF) {
+ $this->char = $this->EOF - 1;
+ }
+ }
+
+ private function markupDeclarationOpenState()
+ {
+ /* If the next two characters are both U+002D HYPHEN-MINUS (-)
+ characters, consume those two characters, create a comment token whose
+ data is the empty string, and switch to the comment state. */
+ if($this->character($this->char + 1, 2) === '--') {
+ $this->char += 2;
+ $this->state = 'comment';
+ $this->token = array(
+ 'data' => null,
+ 'type' => self::COMMENT
+ );
+
+ /* Otherwise if the next seven chacacters are a case-insensitive match
+ for the word "DOCTYPE", then consume those characters and switch to the
+ DOCTYPE state. */
+ } elseif(strtolower($this->character($this->char + 1, 7)) === 'doctype') {
+ $this->char += 7;
+ $this->state = 'doctype';
+
+ /* Otherwise, is is a parse error. Switch to the bogus comment state.
+ The next character that is consumed, if any, is the first character
+ that will be in the comment. */
+ } else {
+ $this->char++;
+ $this->state = 'bogusComment';
+ }
+ }
+
+ private function commentState()
+ {
+ /* Consume the next input character: */
+ $this->char++;
+ $char = $this->char();
+
+ /* U+002D HYPHEN-MINUS (-) */
+ if($char === '-') {
+ /* Switch to the comment dash state */
+ $this->state = 'commentDash';
+
+ /* EOF */
+ } elseif($this->char === $this->EOF) {
+ /* Parse error. Emit the comment token. Reconsume the EOF character
+ in the data state. */
+ $this->emitToken($this->token);
+ $this->char--;
+ $this->state = 'data';
+
+ /* Anything else */
+ } else {
+ /* Append the input character to the comment token's data. Stay in
+ the comment state. */
+ $this->token['data'] .= $char;
+ }
+ }
+
+ private function commentDashState()
+ {
+ /* Consume the next input character: */
+ $this->char++;
+ $char = $this->char();
+
+ /* U+002D HYPHEN-MINUS (-) */
+ if($char === '-') {
+ /* Switch to the comment end state */
+ $this->state = 'commentEnd';
+
+ /* EOF */
+ } elseif($this->char === $this->EOF) {
+ /* Parse error. Emit the comment token. Reconsume the EOF character
+ in the data state. */
+ $this->emitToken($this->token);
+ $this->char--;
+ $this->state = 'data';
+
+ /* Anything else */
+ } else {
+ /* Append a U+002D HYPHEN-MINUS (-) character and the input
+ character to the comment token's data. Switch to the comment state. */
+ $this->token['data'] .= '-'.$char;
+ $this->state = 'comment';
+ }
+ }
+
+ private function commentEndState()
+ {
+ /* Consume the next input character: */
+ $this->char++;
+ $char = $this->char();
+
+ if($char === '>') {
+ $this->emitToken($this->token);
+ $this->state = 'data';
+
+ } elseif($char === '-') {
+ $this->token['data'] .= '-';
+
+ } elseif($this->char === $this->EOF) {
+ $this->emitToken($this->token);
+ $this->char--;
+ $this->state = 'data';
+
+ } else {
+ $this->token['data'] .= '--'.$char;
+ $this->state = 'comment';
+ }
+ }
+
+ private function doctypeState()
+ {
+ /* Consume the next input character: */
+ $this->char++;
+ $char = $this->char();
+
+ if(preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
+ $this->state = 'beforeDoctypeName';
+
+ } else {
+ $this->char--;
+ $this->state = 'beforeDoctypeName';
+ }
+ }
+
+ private function beforeDoctypeNameState()
+ {
+ /* Consume the next input character: */
+ $this->char++;
+ $char = $this->char();
+
+ if(preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
+ // Stay in the before DOCTYPE name state.
+
+ } elseif(preg_match('/^[a-z]$/', $char)) {
+ $this->token = array(
+ 'name' => strtoupper($char),
+ 'type' => self::DOCTYPE,
+ 'error' => true
+ );
+
+ $this->state = 'doctypeName';
+
+ } elseif($char === '>') {
+ $this->emitToken(array(
+ 'name' => null,
+ 'type' => self::DOCTYPE,
+ 'error' => true
+ ));
+
+ $this->state = 'data';
+
+ } elseif($this->char === $this->EOF) {
+ $this->emitToken(array(
+ 'name' => null,
+ 'type' => self::DOCTYPE,
+ 'error' => true
+ ));
+
+ $this->char--;
+ $this->state = 'data';
+
+ } else {
+ $this->token = array(
+ 'name' => $char,
+ 'type' => self::DOCTYPE,
+ 'error' => true
+ );
+
+ $this->state = 'doctypeName';
+ }
+ }
+
+ private function doctypeNameState()
+ {
+ /* Consume the next input character: */
+ $this->char++;
+ $char = $this->char();
+
+ if(preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
+ $this->state = 'AfterDoctypeName';
+
+ } elseif($char === '>') {
+ $this->emitToken($this->token);
+ $this->state = 'data';
+
+ } elseif(preg_match('/^[a-z]$/', $char)) {
+ $this->token['name'] .= strtoupper($char);
+
+ } elseif($this->char === $this->EOF) {
+ $this->emitToken($this->token);
+ $this->char--;
+ $this->state = 'data';
+
+ } else {
+ $this->token['name'] .= $char;
+ }
+
+ $this->token['error'] = ($this->token['name'] === 'HTML')
+ ? false
+ : true;
+ }
+
+ private function afterDoctypeNameState()
+ {
+ /* Consume the next input character: */
+ $this->char++;
+ $char = $this->char();
+
+ if(preg_match('/^[\t\n\x0b\x0c ]$/', $char)) {
+ // Stay in the DOCTYPE name state.
+
+ } elseif($char === '>') {
+ $this->emitToken($this->token);
+ $this->state = 'data';
+
+ } elseif($this->char === $this->EOF) {
+ $this->emitToken($this->token);
+ $this->char--;
+ $this->state = 'data';
+
+ } else {
+ $this->token['error'] = true;
+ $this->state = 'bogusDoctype';
+ }
+ }
+
+ private function bogusDoctypeState()
+ {
+ /* Consume the next input character: */
+ $this->char++;
+ $char = $this->char();
+
+ if($char === '>') {
+ $this->emitToken($this->token);
+ $this->state = 'data';
+
+ } elseif($this->char === $this->EOF) {
+ $this->emitToken($this->token);
+ $this->char--;
+ $this->state = 'data';
+
+ } else {
+ // Stay in the bogus DOCTYPE state.
+ }
+ }
+
+ private function entity()
+ {
+ $start = $this->char;
+
+ // This section defines how to consume an entity. This definition is
+ // used when parsing entities in text and in attributes.
+
+ // The behaviour depends on the identity of the next character (the
+ // one immediately after the U+0026 AMPERSAND character):
+
+ switch($this->character($this->char + 1)) {
+ // U+0023 NUMBER SIGN (#)
+ case '#':
+
+ // The behaviour further depends on the character after the
+ // U+0023 NUMBER SIGN:
+ switch($this->character($this->char + 1)) {
+ // U+0078 LATIN SMALL LETTER X
+ // U+0058 LATIN CAPITAL LETTER X
+ case 'x':
+ case 'X':
+ // Follow the steps below, but using the range of
+ // characters U+0030 DIGIT ZERO through to U+0039 DIGIT
+ // NINE, U+0061 LATIN SMALL LETTER A through to U+0066
+ // LATIN SMALL LETTER F, and U+0041 LATIN CAPITAL LETTER
+ // A, through to U+0046 LATIN CAPITAL LETTER F (in other
+ // words, 0-9, A-F, a-f).
+ $char = 1;
+ $char_class = '0-9A-Fa-f';
+ break;
+
+ // Anything else
+ default:
+ // Follow the steps below, but using the range of
+ // characters U+0030 DIGIT ZERO through to U+0039 DIGIT
+ // NINE (i.e. just 0-9).
+ $char = 0;
+ $char_class = '0-9';
+ break;
+ }
+
+ // Consume as many characters as match the range of characters
+ // given above.
+ $this->char++;
+ $e_name = $this->characters($char_class, $this->char + $char + 1);
+ $entity = $this->character($start, $this->char);
+ $cond = strlen($e_name) > 0;
+
+ // The rest of the parsing happens bellow.
+ break;
+
+ // Anything else
+ default:
+ // Consume the maximum number of characters possible, with the
+ // consumed characters case-sensitively matching one of the
+ // identifiers in the first column of the entities table.
+ $e_name = $this->characters('0-9A-Za-z;', $this->char + 1);
+ $len = strlen($e_name);
+
+ for($c = 1; $c <= $len; $c++) {
+ $id = substr($e_name, 0, $c);
+ $this->char++;
+
+ if(in_array($id, $this->entities)) {
+ $entity = $id;
+ break;
+ }
+ }
+
+ $cond = isset($entity);
+ // The rest of the parsing happens bellow.
+ break;
+ }
+
+ if(!$cond) {
+ // If no match can be made, then this is a parse error. No
+ // characters are consumed, and nothing is returned.
+ $this->char = $start;
+ return false;
+ }
+
+ // Return a character token for the character corresponding to the
+ // entity name (as given by the second column of the entities table).
+ return html_entity_decode('&'.$entity.';', ENT_QUOTES, 'UTF-8');
+ }
+
+ private function emitToken($token)
+ {
+ $emit = $this->tree->emitToken($token);
+
+ if(is_int($emit)) {
+ $this->content_model = $emit;
+
+ } elseif($token['type'] === self::ENDTAG) {
+ $this->content_model = self::PCDATA;
+ }
+ }
+
+ private function EOF()
+ {
+ $this->state = null;
+ $this->tree->emitToken(array(
+ 'type' => self::EOF
+ ));
+ }
+}
+
+class HTML5TreeConstructer
+{
+ public $stack = array();
+
+ private $phase;
+ private $mode;
+ private $dom;
+ private $foster_parent = null;
+ private $a_formatting = array();
+
+ private $head_pointer = null;
+ private $form_pointer = null;
+
+ private $scoping = array('button','caption','html','marquee','object','table','td','th');
+ private $formatting = array('a','b','big','em','font','i','nobr','s','small','strike','strong','tt','u');
+ private $special = array('address','area','base','basefont','bgsound',
+ 'blockquote','body','br','center','col','colgroup','dd','dir','div','dl',
+ 'dt','embed','fieldset','form','frame','frameset','h1','h2','h3','h4','h5',
+ 'h6','head','hr','iframe','image','img','input','isindex','li','link',
+ 'listing','menu','meta','noembed','noframes','noscript','ol','optgroup',
+ 'option','p','param','plaintext','pre','script','select','spacer','style',
+ 'tbody','textarea','tfoot','thead','title','tr','ul','wbr');
+
+ // The different phases.
+ const INIT_PHASE = 0;
+ const ROOT_PHASE = 1;
+ const MAIN_PHASE = 2;
+ const END_PHASE = 3;
+
+ // The different insertion modes for the main phase.
+ const BEFOR_HEAD = 0;
+ const IN_HEAD = 1;
+ const AFTER_HEAD = 2;
+ const IN_BODY = 3;
+ const IN_TABLE = 4;
+ const IN_CAPTION = 5;
+ const IN_CGROUP = 6;
+ const IN_TBODY = 7;
+ const IN_ROW = 8;
+ const IN_CELL = 9;
+ const IN_SELECT = 10;
+ const AFTER_BODY = 11;
+ const IN_FRAME = 12;
+ const AFTR_FRAME = 13;
+
+ // The different types of elements.
+ const SPECIAL = 0;
+ const SCOPING = 1;
+ const FORMATTING = 2;
+ const PHRASING = 3;
+
+ const MARKER = 0;
+
+ public function __construct()
+ {
+ $this->phase = self::INIT_PHASE;
+ $this->mode = self::BEFOR_HEAD;
+ $this->dom = new DOMDocument;
+
+ $this->dom->encoding = 'UTF-8';
+ $this->dom->preserveWhiteSpace = true;
+ $this->dom->substituteEntities = true;
+ $this->dom->strictErrorChecking = false;
+ }
+
+ // Process tag tokens
+ public function emitToken($token)
+ {
+ switch($this->phase) {
+ case self::INIT_PHASE: return $this->initPhase($token); break;
+ case self::ROOT_PHASE: return $this->rootElementPhase($token); break;
+ case self::MAIN_PHASE: return $this->mainPhase($token); break;
+ case self::END_PHASE : return $this->trailingEndPhase($token); break;
+ }
+ }
+
+ private function initPhase($token)
+ {
+ /* Initially, the tree construction stage must handle each token
+ emitted from the tokenisation stage as follows: */
+
+ /* A DOCTYPE token that is marked as being in error
+ A comment token
+ A start tag token
+ An end tag token
+ A character token that is not one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE
+ An end-of-file token */
+ if((isset($token['error']) && $token['error']) ||
+ $token['type'] === HTML5::COMMENT ||
+ $token['type'] === HTML5::STARTTAG ||
+ $token['type'] === HTML5::ENDTAG ||
+ $token['type'] === HTML5::EOF ||
+ ($token['type'] === HTML5::CHARACTR && isset($token['data']) &&
+ !preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data']))) {
+ /* This specification does not define how to handle this case. In
+ particular, user agents may ignore the entirety of this specification
+ altogether for such documents, and instead invoke special parse modes
+ with a greater emphasis on backwards compatibility. */
+
+ $this->phase = self::ROOT_PHASE;
+ return $this->rootElementPhase($token);
+
+ /* A DOCTYPE token marked as being correct */
+ } elseif(isset($token['error']) && !$token['error']) {
+ /* Append a DocumentType node to the Document node, with the name
+ attribute set to the name given in the DOCTYPE token (which will be
+ "HTML"), and the other attributes specific to DocumentType objects
+ set to null, empty lists, or the empty string as appropriate. */
+ $doctype = new DOMDocumentType(null, null, 'HTML');
+
+ /* Then, switch to the root element phase of the tree construction
+ stage. */
+ $this->phase = self::ROOT_PHASE;
+
+ /* A character token that is one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE */
+ } elseif(isset($token['data']) && preg_match('/^[\t\n\x0b\x0c ]+$/',
+ $token['data'])) {
+ /* Append that character to the Document node. */
+ $text = $this->dom->createTextNode($token['data']);
+ $this->dom->appendChild($text);
+ }
+ }
+
+ private function rootElementPhase($token)
+ {
+ /* After the initial phase, as each token is emitted from the tokenisation
+ stage, it must be processed as described in this section. */
+
+ /* A DOCTYPE token */
+ if($token['type'] === HTML5::DOCTYPE) {
+ // Parse error. Ignore the token.
+
+ /* A comment token */
+ } elseif($token['type'] === HTML5::COMMENT) {
+ /* Append a Comment node to the Document object with the data
+ attribute set to the data given in the comment token. */
+ $comment = $this->dom->createComment($token['data']);
+ $this->dom->appendChild($comment);
+
+ /* A character token that is one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE */
+ } elseif($token['type'] === HTML5::CHARACTR &&
+ preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])) {
+ /* Append that character to the Document node. */
+ $text = $this->dom->createTextNode($token['data']);
+ $this->dom->appendChild($text);
+
+ /* A character token that is not one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED
+ (FF), or U+0020 SPACE
+ A start tag token
+ An end tag token
+ An end-of-file token */
+ } elseif(($token['type'] === HTML5::CHARACTR &&
+ !preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])) ||
+ $token['type'] === HTML5::STARTTAG ||
+ $token['type'] === HTML5::ENDTAG ||
+ $token['type'] === HTML5::EOF) {
+ /* Create an HTMLElement node with the tag name html, in the HTML
+ namespace. Append it to the Document object. Switch to the main
+ phase and reprocess the current token. */
+ $html = $this->dom->createElement('html');
+ $this->dom->appendChild($html);
+ $this->stack[] = $html;
+
+ $this->phase = self::MAIN_PHASE;
+ return $this->mainPhase($token);
+ }
+ }
+
+ private function mainPhase($token)
+ {
+ /* Tokens in the main phase must be handled as follows: */
+
+ /* A DOCTYPE token */
+ if($token['type'] === HTML5::DOCTYPE) {
+ // Parse error. Ignore the token.
+
+ /* A start tag token with the tag name "html" */
+ } elseif($token['type'] === HTML5::STARTTAG && $token['name'] === 'html') {
+ /* If this start tag token was not the first start tag token, then
+ it is a parse error. */
+
+ /* For each attribute on the token, check to see if the attribute
+ is already present on the top element of the stack of open elements.
+ If it is not, add the attribute and its corresponding value to that
+ element. */
+ foreach($token['attr'] as $attr) {
+ if(!$this->stack[0]->hasAttribute($attr['name'])) {
+ $this->stack[0]->setAttribute($attr['name'], $attr['value']);
+ }
+ }
+
+ /* An end-of-file token */
+ } elseif($token['type'] === HTML5::EOF) {
+ /* Generate implied end tags. */
+ $this->generateImpliedEndTags();
+
+ /* Anything else. */
+ } else {
+ /* Depends on the insertion mode: */
+ switch($this->mode) {
+ case self::BEFOR_HEAD: return $this->beforeHead($token); break;
+ case self::IN_HEAD: return $this->inHead($token); break;
+ case self::AFTER_HEAD: return $this->afterHead($token); break;
+ case self::IN_BODY: return $this->inBody($token); break;
+ case self::IN_TABLE: return $this->inTable($token); break;
+ case self::IN_CAPTION: return $this->inCaption($token); break;
+ case self::IN_CGROUP: return $this->inColumnGroup($token); break;
+ case self::IN_TBODY: return $this->inTableBody($token); break;
+ case self::IN_ROW: return $this->inRow($token); break;
+ case self::IN_CELL: return $this->inCell($token); break;
+ case self::IN_SELECT: return $this->inSelect($token); break;
+ case self::AFTER_BODY: return $this->afterBody($token); break;
+ case self::IN_FRAME: return $this->inFrameset($token); break;
+ case self::AFTR_FRAME: return $this->afterFrameset($token); break;
+ case self::END_PHASE: return $this->trailingEndPhase($token); break;
+ }
+ }
+ }
+
+ private function beforeHead($token)
+ {
+ /* Handle the token as follows: */
+
+ /* A character token that is one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE */
+ if($token['type'] === HTML5::CHARACTR &&
+ preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])) {
+ /* Append the character to the current node. */
+ $this->insertText($token['data']);
+
+ /* A comment token */
+ } elseif($token['type'] === HTML5::COMMENT) {
+ /* Append a Comment node to the current node with the data attribute
+ set to the data given in the comment token. */
+ $this->insertComment($token['data']);
+
+ /* A start tag token with the tag name "head" */
+ } elseif($token['type'] === HTML5::STARTTAG && $token['name'] === 'head') {
+ /* Create an element for the token, append the new element to the
+ current node and push it onto the stack of open elements. */
+ $element = $this->insertElement($token);
+
+ /* Set the head element pointer to this new element node. */
+ $this->head_pointer = $element;
+
+ /* Change the insertion mode to "in head". */
+ $this->mode = self::IN_HEAD;
+
+ /* A start tag token whose tag name is one of: "base", "link", "meta",
+ "script", "style", "title". Or an end tag with the tag name "html".
+ Or a character token that is not one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE. Or any other start tag token */
+ } elseif($token['type'] === HTML5::STARTTAG ||
+ ($token['type'] === HTML5::ENDTAG && $token['name'] === 'html') ||
+ ($token['type'] === HTML5::CHARACTR && !preg_match('/^[\t\n\x0b\x0c ]$/',
+ $token['data']))) {
+ /* Act as if a start tag token with the tag name "head" and no
+ attributes had been seen, then reprocess the current token. */
+ $this->beforeHead(array(
+ 'name' => 'head',
+ 'type' => HTML5::STARTTAG,
+ 'attr' => array()
+ ));
+
+ return $this->inHead($token);
+
+ /* Any other end tag */
+ } elseif($token['type'] === HTML5::ENDTAG) {
+ /* Parse error. Ignore the token. */
+ }
+ }
+
+ private function inHead($token)
+ {
+ /* Handle the token as follows: */
+
+ /* A character token that is one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE.
+
+ THIS DIFFERS FROM THE SPEC: If the current node is either a title, style
+ or script element, append the character to the current node regardless
+ of its content. */
+ if(($token['type'] === HTML5::CHARACTR &&
+ preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])) || (
+ $token['type'] === HTML5::CHARACTR && in_array(end($this->stack)->nodeName,
+ array('title', 'style', 'script')))) {
+ /* Append the character to the current node. */
+ $this->insertText($token['data']);
+
+ /* A comment token */
+ } elseif($token['type'] === HTML5::COMMENT) {
+ /* Append a Comment node to the current node with the data attribute
+ set to the data given in the comment token. */
+ $this->insertComment($token['data']);
+
+ } elseif($token['type'] === HTML5::ENDTAG &&
+ in_array($token['name'], array('title', 'style', 'script'))) {
+ array_pop($this->stack);
+ return HTML5::PCDATA;
+
+ /* A start tag with the tag name "title" */
+ } elseif($token['type'] === HTML5::STARTTAG && $token['name'] === 'title') {
+ /* Create an element for the token and append the new element to the
+ node pointed to by the head element pointer, or, if that is null
+ (innerHTML case), to the current node. */
+ if($this->head_pointer !== null) {
+ $element = $this->insertElement($token, false);
+ $this->head_pointer->appendChild($element);
+
+ } else {
+ $element = $this->insertElement($token);
+ }
+
+ /* Switch the tokeniser's content model flag to the RCDATA state. */
+ return HTML5::RCDATA;
+
+ /* A start tag with the tag name "style" */
+ } elseif($token['type'] === HTML5::STARTTAG && $token['name'] === 'style') {
+ /* Create an element for the token and append the new element to the
+ node pointed to by the head element pointer, or, if that is null
+ (innerHTML case), to the current node. */
+ if($this->head_pointer !== null) {
+ $element = $this->insertElement($token, false);
+ $this->head_pointer->appendChild($element);
+
+ } else {
+ $this->insertElement($token);
+ }
+
+ /* Switch the tokeniser's content model flag to the CDATA state. */
+ return HTML5::CDATA;
+
+ /* A start tag with the tag name "script" */
+ } elseif($token['type'] === HTML5::STARTTAG && $token['name'] === 'script') {
+ /* Create an element for the token. */
+ $element = $this->insertElement($token, false);
+ $this->head_pointer->appendChild($element);
+
+ /* Switch the tokeniser's content model flag to the CDATA state. */
+ return HTML5::CDATA;
+
+ /* A start tag with the tag name "base", "link", or "meta" */
+ } elseif($token['type'] === HTML5::STARTTAG && in_array($token['name'],
+ array('base', 'link', 'meta'))) {
+ /* Create an element for the token and append the new element to the
+ node pointed to by the head element pointer, or, if that is null
+ (innerHTML case), to the current node. */
+ if($this->head_pointer !== null) {
+ $element = $this->insertElement($token, false);
+ $this->head_pointer->appendChild($element);
+ array_pop($this->stack);
+
+ } else {
+ $this->insertElement($token);
+ }
+
+ /* An end tag with the tag name "head" */
+ } elseif($token['type'] === HTML5::ENDTAG && $token['name'] === 'head') {
+ /* If the current node is a head element, pop the current node off
+ the stack of open elements. */
+ if($this->head_pointer->isSameNode(end($this->stack))) {
+ array_pop($this->stack);
+
+ /* Otherwise, this is a parse error. */
+ } else {
+ // k
+ }
+
+ /* Change the insertion mode to "after head". */
+ $this->mode = self::AFTER_HEAD;
+
+ /* A start tag with the tag name "head" or an end tag except "html". */
+ } elseif(($token['type'] === HTML5::STARTTAG && $token['name'] === 'head') ||
+ ($token['type'] === HTML5::ENDTAG && $token['name'] !== 'html')) {
+ // Parse error. Ignore the token.
+
+ /* Anything else */
+ } else {
+ /* If the current node is a head element, act as if an end tag
+ token with the tag name "head" had been seen. */
+ if($this->head_pointer->isSameNode(end($this->stack))) {
+ $this->inHead(array(
+ 'name' => 'head',
+ 'type' => HTML5::ENDTAG
+ ));
+
+ /* Otherwise, change the insertion mode to "after head". */
+ } else {
+ $this->mode = self::AFTER_HEAD;
+ }
+
+ /* Then, reprocess the current token. */
+ return $this->afterHead($token);
+ }
+ }
+
+ private function afterHead($token)
+ {
+ /* Handle the token as follows: */
+
+ /* A character token that is one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE */
+ if($token['type'] === HTML5::CHARACTR &&
+ preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])) {
+ /* Append the character to the current node. */
+ $this->insertText($token['data']);
+
+ /* A comment token */
+ } elseif($token['type'] === HTML5::COMMENT) {
+ /* Append a Comment node to the current node with the data attribute
+ set to the data given in the comment token. */
+ $this->insertComment($token['data']);
+
+ /* A start tag token with the tag name "body" */
+ } elseif($token['type'] === HTML5::STARTTAG && $token['name'] === 'body') {
+ /* Insert a body element for the token. */
+ $this->insertElement($token);
+
+ /* Change the insertion mode to "in body". */
+ $this->mode = self::IN_BODY;
+
+ /* A start tag token with the tag name "frameset" */
+ } elseif($token['type'] === HTML5::STARTTAG && $token['name'] === 'frameset') {
+ /* Insert a frameset element for the token. */
+ $this->insertElement($token);
+
+ /* Change the insertion mode to "in frameset". */
+ $this->mode = self::IN_FRAME;
+
+ /* A start tag token whose tag name is one of: "base", "link", "meta",
+ "script", "style", "title" */
+ } elseif($token['type'] === HTML5::STARTTAG && in_array($token['name'],
+ array('base', 'link', 'meta', 'script', 'style', 'title'))) {
+ /* Parse error. Switch the insertion mode back to "in head" and
+ reprocess the token. */
+ $this->mode = self::IN_HEAD;
+ return $this->inHead($token);
+
+ /* Anything else */
+ } else {
+ /* Act as if a start tag token with the tag name "body" and no
+ attributes had been seen, and then reprocess the current token. */
+ $this->afterHead(array(
+ 'name' => 'body',
+ 'type' => HTML5::STARTTAG,
+ 'attr' => array()
+ ));
+
+ return $this->inBody($token);
+ }
+ }
+
+ private function inBody($token)
+ {
+ /* Handle the token as follows: */
+
+ switch($token['type']) {
+ /* A character token */
+ case HTML5::CHARACTR:
+ /* Reconstruct the active formatting elements, if any. */
+ $this->reconstructActiveFormattingElements();
+
+ /* Append the token's character to the current node. */
+ $this->insertText($token['data']);
+ break;
+
+ /* A comment token */
+ case HTML5::COMMENT:
+ /* Append a Comment node to the current node with the data
+ attribute set to the data given in the comment token. */
+ $this->insertComment($token['data']);
+ break;
+
+ case HTML5::STARTTAG:
+ switch($token['name']) {
+ /* A start tag token whose tag name is one of: "script",
+ "style" */
+ case 'script': case 'style':
+ /* Process the token as if the insertion mode had been "in
+ head". */
+ return $this->inHead($token);
+ break;
+
+ /* A start tag token whose tag name is one of: "base", "link",
+ "meta", "title" */
+ case 'base': case 'link': case 'meta': case 'title':
+ /* Parse error. Process the token as if the insertion mode
+ had been "in head". */
+ return $this->inHead($token);
+ break;
+
+ /* A start tag token with the tag name "body" */
+ case 'body':
+ /* Parse error. If the second element on the stack of open
+ elements is not a body element, or, if the stack of open
+ elements has only one node on it, then ignore the token.
+ (innerHTML case) */
+ if(count($this->stack) === 1 || $this->stack[1]->nodeName !== 'body') {
+ // Ignore
+
+ /* Otherwise, for each attribute on the token, check to see
+ if the attribute is already present on the body element (the
+ second element) on the stack of open elements. If it is not,
+ add the attribute and its corresponding value to that
+ element. */
+ } else {
+ foreach($token['attr'] as $attr) {
+ if(!$this->stack[1]->hasAttribute($attr['name'])) {
+ $this->stack[1]->setAttribute($attr['name'], $attr['value']);
+ }
+ }
+ }
+ break;
+
+ /* A start tag whose tag name is one of: "address",
+ "blockquote", "center", "dir", "div", "dl", "fieldset",
+ "listing", "menu", "ol", "p", "ul" */
+ case 'address': case 'blockquote': case 'center': case 'dir':
+ case 'div': case 'dl': case 'fieldset': case 'listing':
+ case 'menu': case 'ol': case 'p': case 'ul':
+ /* If the stack of open elements has a p element in scope,
+ then act as if an end tag with the tag name p had been
+ seen. */
+ if($this->elementInScope('p')) {
+ $this->emitToken(array(
+ 'name' => 'p',
+ 'type' => HTML5::ENDTAG
+ ));
+ }
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+ break;
+
+ /* A start tag whose tag name is "form" */
+ case 'form':
+ /* If the form element pointer is not null, ignore the
+ token with a parse error. */
+ if($this->form_pointer !== null) {
+ // Ignore.
+
+ /* Otherwise: */
+ } else {
+ /* If the stack of open elements has a p element in
+ scope, then act as if an end tag with the tag name p
+ had been seen. */
+ if($this->elementInScope('p')) {
+ $this->emitToken(array(
+ 'name' => 'p',
+ 'type' => HTML5::ENDTAG
+ ));
+ }
+
+ /* Insert an HTML element for the token, and set the
+ form element pointer to point to the element created. */
+ $element = $this->insertElement($token);
+ $this->form_pointer = $element;
+ }
+ break;
+
+ /* A start tag whose tag name is "li", "dd" or "dt" */
+ case 'li': case 'dd': case 'dt':
+ /* If the stack of open elements has a p element in scope,
+ then act as if an end tag with the tag name p had been
+ seen. */
+ if($this->elementInScope('p')) {
+ $this->emitToken(array(
+ 'name' => 'p',
+ 'type' => HTML5::ENDTAG
+ ));
+ }
+
+ $stack_length = count($this->stack) - 1;
+
+ for($n = $stack_length; 0 <= $n; $n--) {
+ /* 1. Initialise node to be the current node (the
+ bottommost node of the stack). */
+ $stop = false;
+ $node = $this->stack[$n];
+ $cat = $this->getElementCategory($node->tagName);
+
+ /* 2. If node is an li, dd or dt element, then pop all
+ the nodes from the current node up to node, including
+ node, then stop this algorithm. */
+ if($token['name'] === $node->tagName || ($token['name'] !== 'li'
+ && ($node->tagName === 'dd' || $node->tagName === 'dt'))) {
+ for($x = $stack_length; $x >= $n ; $x--) {
+ array_pop($this->stack);
+ }
+
+ break;
+ }
+
+ /* 3. If node is not in the formatting category, and is
+ not in the phrasing category, and is not an address or
+ div element, then stop this algorithm. */
+ if($cat !== self::FORMATTING && $cat !== self::PHRASING &&
+ $node->tagName !== 'address' && $node->tagName !== 'div') {
+ break;
+ }
+ }
+
+ /* Finally, insert an HTML element with the same tag
+ name as the token's. */
+ $this->insertElement($token);
+ break;
+
+ /* A start tag token whose tag name is "plaintext" */
+ case 'plaintext':
+ /* If the stack of open elements has a p element in scope,
+ then act as if an end tag with the tag name p had been
+ seen. */
+ if($this->elementInScope('p')) {
+ $this->emitToken(array(
+ 'name' => 'p',
+ 'type' => HTML5::ENDTAG
+ ));
+ }
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+
+ return HTML5::PLAINTEXT;
+ break;
+
+ /* A start tag whose tag name is one of: "h1", "h2", "h3", "h4",
+ "h5", "h6" */
+ case 'h1': case 'h2': case 'h3': case 'h4': case 'h5': case 'h6':
+ /* If the stack of open elements has a p element in scope,
+ then act as if an end tag with the tag name p had been seen. */
+ if($this->elementInScope('p')) {
+ $this->emitToken(array(
+ 'name' => 'p',
+ 'type' => HTML5::ENDTAG
+ ));
+ }
+
+ /* If the stack of open elements has in scope an element whose
+ tag name is one of "h1", "h2", "h3", "h4", "h5", or "h6", then
+ this is a parse error; pop elements from the stack until an
+ element with one of those tag names has been popped from the
+ stack. */
+ while($this->elementInScope(array('h1', 'h2', 'h3', 'h4', 'h5', 'h6'))) {
+ array_pop($this->stack);
+ }
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+ break;
+
+ /* A start tag whose tag name is "a" */
+ case 'a':
+ /* If the list of active formatting elements contains
+ an element whose tag name is "a" between the end of the
+ list and the last marker on the list (or the start of
+ the list if there is no marker on the list), then this
+ is a parse error; act as if an end tag with the tag name
+ "a" had been seen, then remove that element from the list
+ of active formatting elements and the stack of open
+ elements if the end tag didn't already remove it (it
+ might not have if the element is not in table scope). */
+ $leng = count($this->a_formatting);
+
+ for($n = $leng - 1; $n >= 0; $n--) {
+ if($this->a_formatting[$n] === self::MARKER) {
+ break;
+
+ } elseif($this->a_formatting[$n]->nodeName === 'a') {
+ $this->emitToken(array(
+ 'name' => 'a',
+ 'type' => HTML5::ENDTAG
+ ));
+ break;
+ }
+ }
+
+ /* Reconstruct the active formatting elements, if any. */
+ $this->reconstructActiveFormattingElements();
+
+ /* Insert an HTML element for the token. */
+ $el = $this->insertElement($token);
+
+ /* Add that element to the list of active formatting
+ elements. */
+ $this->a_formatting[] = $el;
+ break;
+
+ /* A start tag whose tag name is one of: "b", "big", "em", "font",
+ "i", "nobr", "s", "small", "strike", "strong", "tt", "u" */
+ case 'b': case 'big': case 'em': case 'font': case 'i':
+ case 'nobr': case 's': case 'small': case 'strike':
+ case 'strong': case 'tt': case 'u':
+ /* Reconstruct the active formatting elements, if any. */
+ $this->reconstructActiveFormattingElements();
+
+ /* Insert an HTML element for the token. */
+ $el = $this->insertElement($token);
+
+ /* Add that element to the list of active formatting
+ elements. */
+ $this->a_formatting[] = $el;
+ break;
+
+ /* A start tag token whose tag name is "button" */
+ case 'button':
+ /* If the stack of open elements has a button element in scope,
+ then this is a parse error; act as if an end tag with the tag
+ name "button" had been seen, then reprocess the token. (We don't
+ do that. Unnecessary.) */
+ if($this->elementInScope('button')) {
+ $this->inBody(array(
+ 'name' => 'button',
+ 'type' => HTML5::ENDTAG
+ ));
+ }
+
+ /* Reconstruct the active formatting elements, if any. */
+ $this->reconstructActiveFormattingElements();
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+
+ /* Insert a marker at the end of the list of active
+ formatting elements. */
+ $this->a_formatting[] = self::MARKER;
+ break;
+
+ /* A start tag token whose tag name is one of: "marquee", "object" */
+ case 'marquee': case 'object':
+ /* Reconstruct the active formatting elements, if any. */
+ $this->reconstructActiveFormattingElements();
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+
+ /* Insert a marker at the end of the list of active
+ formatting elements. */
+ $this->a_formatting[] = self::MARKER;
+ break;
+
+ /* A start tag token whose tag name is "xmp" */
+ case 'xmp':
+ /* Reconstruct the active formatting elements, if any. */
+ $this->reconstructActiveFormattingElements();
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+
+ /* Switch the content model flag to the CDATA state. */
+ return HTML5::CDATA;
+ break;
+
+ /* A start tag whose tag name is "table" */
+ case 'table':
+ /* If the stack of open elements has a p element in scope,
+ then act as if an end tag with the tag name p had been seen. */
+ if($this->elementInScope('p')) {
+ $this->emitToken(array(
+ 'name' => 'p',
+ 'type' => HTML5::ENDTAG
+ ));
+ }
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+
+ /* Change the insertion mode to "in table". */
+ $this->mode = self::IN_TABLE;
+ break;
+
+ /* A start tag whose tag name is one of: "area", "basefont",
+ "bgsound", "br", "embed", "img", "param", "spacer", "wbr" */
+ case 'area': case 'basefont': case 'bgsound': case 'br':
+ case 'embed': case 'img': case 'param': case 'spacer':
+ case 'wbr':
+ /* Reconstruct the active formatting elements, if any. */
+ $this->reconstructActiveFormattingElements();
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+
+ /* Immediately pop the current node off the stack of open elements. */
+ array_pop($this->stack);
+ break;
+
+ /* A start tag whose tag name is "hr" */
+ case 'hr':
+ /* If the stack of open elements has a p element in scope,
+ then act as if an end tag with the tag name p had been seen. */
+ if($this->elementInScope('p')) {
+ $this->emitToken(array(
+ 'name' => 'p',
+ 'type' => HTML5::ENDTAG
+ ));
+ }
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+
+ /* Immediately pop the current node off the stack of open elements. */
+ array_pop($this->stack);
+ break;
+
+ /* A start tag whose tag name is "image" */
+ case 'image':
+ /* Parse error. Change the token's tag name to "img" and
+ reprocess it. (Don't ask.) */
+ $token['name'] = 'img';
+ return $this->inBody($token);
+ break;
+
+ /* A start tag whose tag name is "input" */
+ case 'input':
+ /* Reconstruct the active formatting elements, if any. */
+ $this->reconstructActiveFormattingElements();
+
+ /* Insert an input element for the token. */
+ $element = $this->insertElement($token, false);
+
+ /* If the form element pointer is not null, then associate the
+ input element with the form element pointed to by the form
+ element pointer. */
+ $this->form_pointer !== null
+ ? $this->form_pointer->appendChild($element)
+ : end($this->stack)->appendChild($element);
+
+ /* Pop that input element off the stack of open elements. */
+ array_pop($this->stack);
+ break;
+
+ /* A start tag whose tag name is "isindex" */
+ case 'isindex':
+ /* Parse error. */
+ // w/e
+
+ /* If the form element pointer is not null,
+ then ignore the token. */
+ if($this->form_pointer === null) {
+ /* Act as if a start tag token with the tag name "form" had
+ been seen. */
+ $this->inBody(array(
+ 'name' => 'body',
+ 'type' => HTML5::STARTTAG,
+ 'attr' => array()
+ ));
+
+ /* Act as if a start tag token with the tag name "hr" had
+ been seen. */
+ $this->inBody(array(
+ 'name' => 'hr',
+ 'type' => HTML5::STARTTAG,
+ 'attr' => array()
+ ));
+
+ /* Act as if a start tag token with the tag name "p" had
+ been seen. */
+ $this->inBody(array(
+ 'name' => 'p',
+ 'type' => HTML5::STARTTAG,
+ 'attr' => array()
+ ));
+
+ /* Act as if a start tag token with the tag name "label"
+ had been seen. */
+ $this->inBody(array(
+ 'name' => 'label',
+ 'type' => HTML5::STARTTAG,
+ 'attr' => array()
+ ));
+
+ /* Act as if a stream of character tokens had been seen. */
+ $this->insertText('This is a searchable index. '.
+ 'Insert your search keywords here: ');
+
+ /* Act as if a start tag token with the tag name "input"
+ had been seen, with all the attributes from the "isindex"
+ token, except with the "name" attribute set to the value
+ "isindex" (ignoring any explicit "name" attribute). */
+ $attr = $token['attr'];
+ $attr[] = array('name' => 'name', 'value' => 'isindex');
+
+ $this->inBody(array(
+ 'name' => 'input',
+ 'type' => HTML5::STARTTAG,
+ 'attr' => $attr
+ ));
+
+ /* Act as if a stream of character tokens had been seen
+ (see below for what they should say). */
+ $this->insertText('This is a searchable index. '.
+ 'Insert your search keywords here: ');
+
+ /* Act as if an end tag token with the tag name "label"
+ had been seen. */
+ $this->inBody(array(
+ 'name' => 'label',
+ 'type' => HTML5::ENDTAG
+ ));
+
+ /* Act as if an end tag token with the tag name "p" had
+ been seen. */
+ $this->inBody(array(
+ 'name' => 'p',
+ 'type' => HTML5::ENDTAG
+ ));
+
+ /* Act as if a start tag token with the tag name "hr" had
+ been seen. */
+ $this->inBody(array(
+ 'name' => 'hr',
+ 'type' => HTML5::ENDTAG
+ ));
+
+ /* Act as if an end tag token with the tag name "form" had
+ been seen. */
+ $this->inBody(array(
+ 'name' => 'form',
+ 'type' => HTML5::ENDTAG
+ ));
+ }
+ break;
+
+ /* A start tag whose tag name is "textarea" */
+ case 'textarea':
+ $this->insertElement($token);
+
+ /* Switch the tokeniser's content model flag to the
+ RCDATA state. */
+ return HTML5::RCDATA;
+ break;
+
+ /* A start tag whose tag name is one of: "iframe", "noembed",
+ "noframes" */
+ case 'iframe': case 'noembed': case 'noframes':
+ $this->insertElement($token);
+
+ /* Switch the tokeniser's content model flag to the CDATA state. */
+ return HTML5::CDATA;
+ break;
+
+ /* A start tag whose tag name is "select" */
+ case 'select':
+ /* Reconstruct the active formatting elements, if any. */
+ $this->reconstructActiveFormattingElements();
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+
+ /* Change the insertion mode to "in select". */
+ $this->mode = self::IN_SELECT;
+ break;
+
+ /* A start or end tag whose tag name is one of: "caption", "col",
+ "colgroup", "frame", "frameset", "head", "option", "optgroup",
+ "tbody", "td", "tfoot", "th", "thead", "tr". */
+ case 'caption': case 'col': case 'colgroup': case 'frame':
+ case 'frameset': case 'head': case 'option': case 'optgroup':
+ case 'tbody': case 'td': case 'tfoot': case 'th': case 'thead':
+ case 'tr':
+ // Parse error. Ignore the token.
+ break;
+
+ /* A start or end tag whose tag name is one of: "event-source",
+ "section", "nav", "article", "aside", "header", "footer",
+ "datagrid", "command" */
+ case 'event-source': case 'section': case 'nav': case 'article':
+ case 'aside': case 'header': case 'footer': case 'datagrid':
+ case 'command':
+ // Work in progress!
+ break;
+
+ /* A start tag token not covered by the previous entries */
+ default:
+ /* Reconstruct the active formatting elements, if any. */
+ $this->reconstructActiveFormattingElements();
+
+ $this->insertElement($token);
+ break;
+ }
+ break;
+
+ case HTML5::ENDTAG:
+ switch($token['name']) {
+ /* An end tag with the tag name "body" */
+ case 'body':
+ /* If the second element in the stack of open elements is
+ not a body element, this is a parse error. Ignore the token.
+ (innerHTML case) */
+ if(count($this->stack) < 2 || $this->stack[1]->nodeName !== 'body') {
+ // Ignore.
+
+ /* If the current node is not the body element, then this
+ is a parse error. */
+ } elseif(end($this->stack)->nodeName !== 'body') {
+ // Parse error.
+ }
+
+ /* Change the insertion mode to "after body". */
+ $this->mode = self::AFTER_BODY;
+ break;
+
+ /* An end tag with the tag name "html" */
+ case 'html':
+ /* Act as if an end tag with tag name "body" had been seen,
+ then, if that token wasn't ignored, reprocess the current
+ token. */
+ $this->inBody(array(
+ 'name' => 'body',
+ 'type' => HTML5::ENDTAG
+ ));
+
+ return $this->afterBody($token);
+ break;
+
+ /* An end tag whose tag name is one of: "address", "blockquote",
+ "center", "dir", "div", "dl", "fieldset", "listing", "menu",
+ "ol", "pre", "ul" */
+ case 'address': case 'blockquote': case 'center': case 'dir':
+ case 'div': case 'dl': case 'fieldset': case 'listing':
+ case 'menu': case 'ol': case 'pre': case 'ul':
+ /* If the stack of open elements has an element in scope
+ with the same tag name as that of the token, then generate
+ implied end tags. */
+ if($this->elementInScope($token['name'])) {
+ $this->generateImpliedEndTags();
+
+ /* Now, if the current node is not an element with
+ the same tag name as that of the token, then this
+ is a parse error. */
+ // w/e
+
+ /* If the stack of open elements has an element in
+ scope with the same tag name as that of the token,
+ then pop elements from this stack until an element
+ with that tag name has been popped from the stack. */
+ for($n = count($this->stack) - 1; $n >= 0; $n--) {
+ if($this->stack[$n]->nodeName === $token['name']) {
+ $n = -1;
+ }
+
+ array_pop($this->stack);
+ }
+ }
+ break;
+
+ /* An end tag whose tag name is "form" */
+ case 'form':
+ /* If the stack of open elements has an element in scope
+ with the same tag name as that of the token, then generate
+ implied end tags. */
+ if($this->elementInScope($token['name'])) {
+ $this->generateImpliedEndTags();
+
+ }
+
+ if(end($this->stack)->nodeName !== $token['name']) {
+ /* Now, if the current node is not an element with the
+ same tag name as that of the token, then this is a parse
+ error. */
+ // w/e
+
+ } else {
+ /* Otherwise, if the current node is an element with
+ the same tag name as that of the token pop that element
+ from the stack. */
+ array_pop($this->stack);
+ }
+
+ /* In any case, set the form element pointer to null. */
+ $this->form_pointer = null;
+ break;
+
+ /* An end tag whose tag name is "p" */
+ case 'p':
+ /* If the stack of open elements has a p element in scope,
+ then generate implied end tags, except for p elements. */
+ if($this->elementInScope('p')) {
+ $this->generateImpliedEndTags(array('p'));
+
+ /* If the current node is not a p element, then this is
+ a parse error. */
+ // k
+
+ /* If the stack of open elements has a p element in
+ scope, then pop elements from this stack until the stack
+ no longer has a p element in scope. */
+ for($n = count($this->stack) - 1; $n >= 0; $n--) {
+ if($this->elementInScope('p')) {
+ array_pop($this->stack);
+
+ } else {
+ break;
+ }
+ }
+ }
+ break;
+
+ /* An end tag whose tag name is "dd", "dt", or "li" */
+ case 'dd': case 'dt': case 'li':
+ /* If the stack of open elements has an element in scope
+ whose tag name matches the tag name of the token, then
+ generate implied end tags, except for elements with the
+ same tag name as the token. */
+ if($this->elementInScope($token['name'])) {
+ $this->generateImpliedEndTags(array($token['name']));
+
+ /* If the current node is not an element with the same
+ tag name as the token, then this is a parse error. */
+ // w/e
+
+ /* If the stack of open elements has an element in scope
+ whose tag name matches the tag name of the token, then
+ pop elements from this stack until an element with that
+ tag name has been popped from the stack. */
+ for($n = count($this->stack) - 1; $n >= 0; $n--) {
+ if($this->stack[$n]->nodeName === $token['name']) {
+ $n = -1;
+ }
+
+ array_pop($this->stack);
+ }
+ }
+ break;
+
+ /* An end tag whose tag name is one of: "h1", "h2", "h3", "h4",
+ "h5", "h6" */
+ case 'h1': case 'h2': case 'h3': case 'h4': case 'h5': case 'h6':
+ $elements = array('h1', 'h2', 'h3', 'h4', 'h5', 'h6');
+
+ /* If the stack of open elements has in scope an element whose
+ tag name is one of "h1", "h2", "h3", "h4", "h5", or "h6", then
+ generate implied end tags. */
+ if($this->elementInScope($elements)) {
+ $this->generateImpliedEndTags();
+
+ /* Now, if the current node is not an element with the same
+ tag name as that of the token, then this is a parse error. */
+ // w/e
+
+ /* If the stack of open elements has in scope an element
+ whose tag name is one of "h1", "h2", "h3", "h4", "h5", or
+ "h6", then pop elements from the stack until an element
+ with one of those tag names has been popped from the stack. */
+ while($this->elementInScope($elements)) {
+ array_pop($this->stack);
+ }
+ }
+ break;
+
+ /* An end tag whose tag name is one of: "a", "b", "big", "em",
+ "font", "i", "nobr", "s", "small", "strike", "strong", "tt", "u" */
+ case 'a': case 'b': case 'big': case 'em': case 'font':
+ case 'i': case 'nobr': case 's': case 'small': case 'strike':
+ case 'strong': case 'tt': case 'u':
+ /* 1. Let the formatting element be the last element in
+ the list of active formatting elements that:
+ * is between the end of the list and the last scope
+ marker in the list, if any, or the start of the list
+ otherwise, and
+ * has the same tag name as the token.
+ */
+ while(true) {
+ for($a = count($this->a_formatting) - 1; $a >= 0; $a--) {
+ if($this->a_formatting[$a] === self::MARKER) {
+ break;
+
+ } elseif($this->a_formatting[$a]->tagName === $token['name']) {
+ $formatting_element = $this->a_formatting[$a];
+ $in_stack = in_array($formatting_element, $this->stack, true);
+ $fe_af_pos = $a;
+ break;
+ }
+ }
+
+ /* If there is no such node, or, if that node is
+ also in the stack of open elements but the element
+ is not in scope, then this is a parse error. Abort
+ these steps. The token is ignored. */
+ if(!isset($formatting_element) || ($in_stack &&
+ !$this->elementInScope($token['name']))) {
+ break;
+
+ /* Otherwise, if there is such a node, but that node
+ is not in the stack of open elements, then this is a
+ parse error; remove the element from the list, and
+ abort these steps. */
+ } elseif(isset($formatting_element) && !$in_stack) {
+ unset($this->a_formatting[$fe_af_pos]);
+ $this->a_formatting = array_merge($this->a_formatting);
+ break;
+ }
+
+ /* 2. Let the furthest block be the topmost node in the
+ stack of open elements that is lower in the stack
+ than the formatting element, and is not an element in
+ the phrasing or formatting categories. There might
+ not be one. */
+ $fe_s_pos = array_search($formatting_element, $this->stack, true);
+ $length = count($this->stack);
+
+ for($s = $fe_s_pos + 1; $s < $length; $s++) {
+ $category = $this->getElementCategory($this->stack[$s]->nodeName);
+
+ if($category !== self::PHRASING && $category !== self::FORMATTING) {
+ $furthest_block = $this->stack[$s];
+ }
+ }
+
+ /* 3. If there is no furthest block, then the UA must
+ skip the subsequent steps and instead just pop all
+ the nodes from the bottom of the stack of open
+ elements, from the current node up to the formatting
+ element, and remove the formatting element from the
+ list of active formatting elements. */
+ if(!isset($furthest_block)) {
+ for($n = $length - 1; $n >= $fe_s_pos; $n--) {
+ array_pop($this->stack);
+ }
+
+ unset($this->a_formatting[$fe_af_pos]);
+ $this->a_formatting = array_merge($this->a_formatting);
+ break;
+ }
+
+ /* 4. Let the common ancestor be the element
+ immediately above the formatting element in the stack
+ of open elements. */
+ $common_ancestor = $this->stack[$fe_s_pos - 1];
+
+ /* 5. If the furthest block has a parent node, then
+ remove the furthest block from its parent node. */
+ if($furthest_block->parentNode !== null) {
+ $furthest_block->parentNode->removeChild($furthest_block);
+ }
+
+ /* 6. Let a bookmark note the position of the
+ formatting element in the list of active formatting
+ elements relative to the elements on either side
+ of it in the list. */
+ $bookmark = $fe_af_pos;
+
+ /* 7. Let node and last node be the furthest block.
+ Follow these steps: */
+ $node = $furthest_block;
+ $last_node = $furthest_block;
+
+ while(true) {
+ for($n = array_search($node, $this->stack, true) - 1; $n >= 0; $n--) {
+ /* 7.1 Let node be the element immediately
+ prior to node in the stack of open elements. */
+ $node = $this->stack[$n];
+
+ /* 7.2 If node is not in the list of active
+ formatting elements, then remove node from
+ the stack of open elements and then go back
+ to step 1. */
+ if(!in_array($node, $this->a_formatting, true)) {
+ unset($this->stack[$n]);
+ $this->stack = array_merge($this->stack);
+
+ } else {
+ break;
+ }
+ }
+
+ /* 7.3 Otherwise, if node is the formatting
+ element, then go to the next step in the overall
+ algorithm. */
+ if($node === $formatting_element) {
+ break;
+
+ /* 7.4 Otherwise, if last node is the furthest
+ block, then move the aforementioned bookmark to
+ be immediately after the node in the list of
+ active formatting elements. */
+ } elseif($last_node === $furthest_block) {
+ $bookmark = array_search($node, $this->a_formatting, true) + 1;
+ }
+
+ /* 7.5 If node has any children, perform a
+ shallow clone of node, replace the entry for
+ node in the list of active formatting elements
+ with an entry for the clone, replace the entry
+ for node in the stack of open elements with an
+ entry for the clone, and let node be the clone. */
+ if($node->hasChildNodes()) {
+ $clone = $node->cloneNode();
+ $s_pos = array_search($node, $this->stack, true);
+ $a_pos = array_search($node, $this->a_formatting, true);
+
+ $this->stack[$s_pos] = $clone;
+ $this->a_formatting[$a_pos] = $clone;
+ $node = $clone;
+ }
+
+ /* 7.6 Insert last node into node, first removing
+ it from its previous parent node if any. */
+ if($last_node->parentNode !== null) {
+ $last_node->parentNode->removeChild($last_node);
+ }
+
+ $node->appendChild($last_node);
+
+ /* 7.7 Let last node be node. */
+ $last_node = $node;
+ }
+
+ /* 8. Insert whatever last node ended up being in
+ the previous step into the common ancestor node,
+ first removing it from its previous parent node if
+ any. */
+ if($last_node->parentNode !== null) {
+ $last_node->parentNode->removeChild($last_node);
+ }
+
+ $common_ancestor->appendChild($last_node);
+
+ /* 9. Perform a shallow clone of the formatting
+ element. */
+ $clone = $formatting_element->cloneNode();
+
+ /* 10. Take all of the child nodes of the furthest
+ block and append them to the clone created in the
+ last step. */
+ while($furthest_block->hasChildNodes()) {
+ $child = $furthest_block->firstChild;
+ $furthest_block->removeChild($child);
+ $clone->appendChild($child);
+ }
+
+ /* 11. Append that clone to the furthest block. */
+ $furthest_block->appendChild($clone);
+
+ /* 12. Remove the formatting element from the list
+ of active formatting elements, and insert the clone
+ into the list of active formatting elements at the
+ position of the aforementioned bookmark. */
+ $fe_af_pos = array_search($formatting_element, $this->a_formatting, true);
+ unset($this->a_formatting[$fe_af_pos]);
+ $this->a_formatting = array_merge($this->a_formatting);
+
+ $af_part1 = array_slice($this->a_formatting, 0, $bookmark - 1);
+ $af_part2 = array_slice($this->a_formatting, $bookmark, count($this->a_formatting));
+ $this->a_formatting = array_merge($af_part1, array($clone), $af_part2);
+
+ /* 13. Remove the formatting element from the stack
+ of open elements, and insert the clone into the stack
+ of open elements immediately after (i.e. in a more
+ deeply nested position than) the position of the
+ furthest block in that stack. */
+ $fe_s_pos = array_search($formatting_element, $this->stack, true);
+ $fb_s_pos = array_search($furthest_block, $this->stack, true);
+ unset($this->stack[$fe_s_pos]);
+
+ $s_part1 = array_slice($this->stack, 0, $fb_s_pos);
+ $s_part2 = array_slice($this->stack, $fb_s_pos + 1, count($this->stack));
+ $this->stack = array_merge($s_part1, array($clone), $s_part2);
+
+ /* 14. Jump back to step 1 in this series of steps. */
+ unset($formatting_element, $fe_af_pos, $fe_s_pos, $furthest_block);
+ }
+ break;
+
+ /* An end tag token whose tag name is one of: "button",
+ "marquee", "object" */
+ case 'button': case 'marquee': case 'object':
+ /* If the stack of open elements has an element in scope whose
+ tag name matches the tag name of the token, then generate implied
+ tags. */
+ if($this->elementInScope($token['name'])) {
+ $this->generateImpliedEndTags();
+
+ /* Now, if the current node is not an element with the same
+ tag name as the token, then this is a parse error. */
+ // k
+
+ /* Now, if the stack of open elements has an element in scope
+ whose tag name matches the tag name of the token, then pop
+ elements from the stack until that element has been popped from
+ the stack, and clear the list of active formatting elements up
+ to the last marker. */
+ for($n = count($this->stack) - 1; $n >= 0; $n--) {
+ if($this->stack[$n]->nodeName === $token['name']) {
+ $n = -1;
+ }
+
+ array_pop($this->stack);
+ }
+
+ $marker = end(array_keys($this->a_formatting, self::MARKER, true));
+
+ for($n = count($this->a_formatting) - 1; $n > $marker; $n--) {
+ array_pop($this->a_formatting);
+ }
+ }
+ break;
+
+ /* Or an end tag whose tag name is one of: "area", "basefont",
+ "bgsound", "br", "embed", "hr", "iframe", "image", "img",
+ "input", "isindex", "noembed", "noframes", "param", "select",
+ "spacer", "table", "textarea", "wbr" */
+ case 'area': case 'basefont': case 'bgsound': case 'br':
+ case 'embed': case 'hr': case 'iframe': case 'image':
+ case 'img': case 'input': case 'isindex': case 'noembed':
+ case 'noframes': case 'param': case 'select': case 'spacer':
+ case 'table': case 'textarea': case 'wbr':
+ // Parse error. Ignore the token.
+ break;
+
+ /* An end tag token not covered by the previous entries */
+ default:
+ for($n = count($this->stack) - 1; $n >= 0; $n--) {
+ /* Initialise node to be the current node (the bottommost
+ node of the stack). */
+ $node = end($this->stack);
+
+ /* If node has the same tag name as the end tag token,
+ then: */
+ if($token['name'] === $node->nodeName) {
+ /* Generate implied end tags. */
+ $this->generateImpliedEndTags();
+
+ /* If the tag name of the end tag token does not
+ match the tag name of the current node, this is a
+ parse error. */
+ // k
+
+ /* Pop all the nodes from the current node up to
+ node, including node, then stop this algorithm. */
+ for($x = count($this->stack) - $n; $x >= $n; $x--) {
+ array_pop($this->stack);
+ }
+
+ } else {
+ $category = $this->getElementCategory($node);
+
+ if($category !== self::SPECIAL && $category !== self::SCOPING) {
+ /* Otherwise, if node is in neither the formatting
+ category nor the phrasing category, then this is a
+ parse error. Stop this algorithm. The end tag token
+ is ignored. */
+ return false;
+ }
+ }
+ }
+ break;
+ }
+ break;
+ }
+ }
+
+ private function inTable($token)
+ {
+ $clear = array('html', 'table');
+
+ /* A character token that is one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE */
+ if($token['type'] === HTML5::CHARACTR &&
+ preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])) {
+ /* Append the character to the current node. */
+ $text = $this->dom->createTextNode($token['data']);
+ end($this->stack)->appendChild($text);
+
+ /* A comment token */
+ } elseif($token['type'] === HTML5::COMMENT) {
+ /* Append a Comment node to the current node with the data
+ attribute set to the data given in the comment token. */
+ $comment = $this->dom->createComment($token['data']);
+ end($this->stack)->appendChild($comment);
+
+ /* A start tag whose tag name is "caption" */
+ } elseif($token['type'] === HTML5::STARTTAG &&
+ $token['name'] === 'caption') {
+ /* Clear the stack back to a table context. */
+ $this->clearStackToTableContext($clear);
+
+ /* Insert a marker at the end of the list of active
+ formatting elements. */
+ $this->a_formatting[] = self::MARKER;
+
+ /* Insert an HTML element for the token, then switch the
+ insertion mode to "in caption". */
+ $this->insertElement($token);
+ $this->mode = self::IN_CAPTION;
+
+ /* A start tag whose tag name is "colgroup" */
+ } elseif($token['type'] === HTML5::STARTTAG &&
+ $token['name'] === 'colgroup') {
+ /* Clear the stack back to a table context. */
+ $this->clearStackToTableContext($clear);
+
+ /* Insert an HTML element for the token, then switch the
+ insertion mode to "in column group". */
+ $this->insertElement($token);
+ $this->mode = self::IN_CGROUP;
+
+ /* A start tag whose tag name is "col" */
+ } elseif($token['type'] === HTML5::STARTTAG &&
+ $token['name'] === 'col') {
+ $this->inTable(array(
+ 'name' => 'colgroup',
+ 'type' => HTML5::STARTTAG,
+ 'attr' => array()
+ ));
+
+ $this->inColumnGroup($token);
+
+ /* A start tag whose tag name is one of: "tbody", "tfoot", "thead" */
+ } elseif($token['type'] === HTML5::STARTTAG && in_array($token['name'],
+ array('tbody', 'tfoot', 'thead'))) {
+ /* Clear the stack back to a table context. */
+ $this->clearStackToTableContext($clear);
+
+ /* Insert an HTML element for the token, then switch the insertion
+ mode to "in table body". */
+ $this->insertElement($token);
+ $this->mode = self::IN_TBODY;
+
+ /* A start tag whose tag name is one of: "td", "th", "tr" */
+ } elseif($token['type'] === HTML5::STARTTAG &&
+ in_array($token['name'], array('td', 'th', 'tr'))) {
+ /* Act as if a start tag token with the tag name "tbody" had been
+ seen, then reprocess the current token. */
+ $this->inTable(array(
+ 'name' => 'tbody',
+ 'type' => HTML5::STARTTAG,
+ 'attr' => array()
+ ));
+
+ return $this->inTableBody($token);
+
+ /* A start tag whose tag name is "table" */
+ } elseif($token['type'] === HTML5::STARTTAG &&
+ $token['name'] === 'table') {
+ /* Parse error. Act as if an end tag token with the tag name "table"
+ had been seen, then, if that token wasn't ignored, reprocess the
+ current token. */
+ $this->inTable(array(
+ 'name' => 'table',
+ 'type' => HTML5::ENDTAG
+ ));
+
+ return $this->mainPhase($token);
+
+ /* An end tag whose tag name is "table" */
+ } elseif($token['type'] === HTML5::ENDTAG &&
+ $token['name'] === 'table') {
+ /* If the stack of open elements does not have an element in table
+ scope with the same tag name as the token, this is a parse error.
+ Ignore the token. (innerHTML case) */
+ if(!$this->elementInScope($token['name'], true)) {
+ return false;
+
+ /* Otherwise: */
+ } else {
+ /* Generate implied end tags. */
+ $this->generateImpliedEndTags();
+
+ /* Now, if the current node is not a table element, then this
+ is a parse error. */
+ // w/e
+
+ /* Pop elements from this stack until a table element has been
+ popped from the stack. */
+ while(true) {
+ $current = end($this->stack)->nodeName;
+ array_pop($this->stack);
+
+ if($current === 'table') {
+ break;
+ }
+ }
+
+ /* Reset the insertion mode appropriately. */
+ $this->resetInsertionMode();
+ }
+
+ /* An end tag whose tag name is one of: "body", "caption", "col",
+ "colgroup", "html", "tbody", "td", "tfoot", "th", "thead", "tr" */
+ } elseif($token['type'] === HTML5::ENDTAG && in_array($token['name'],
+ array('body', 'caption', 'col', 'colgroup', 'html', 'tbody', 'td',
+ 'tfoot', 'th', 'thead', 'tr'))) {
+ // Parse error. Ignore the token.
+
+ /* Anything else */
+ } else {
+ /* Parse error. Process the token as if the insertion mode was "in
+ body", with the following exception: */
+
+ /* If the current node is a table, tbody, tfoot, thead, or tr
+ element, then, whenever a node would be inserted into the current
+ node, it must instead be inserted into the foster parent element. */
+ if(in_array(end($this->stack)->nodeName,
+ array('table', 'tbody', 'tfoot', 'thead', 'tr'))) {
+ /* The foster parent element is the parent element of the last
+ table element in the stack of open elements, if there is a
+ table element and it has such a parent element. If there is no
+ table element in the stack of open elements (innerHTML case),
+ then the foster parent element is the first element in the
+ stack of open elements (the html element). Otherwise, if there
+ is a table element in the stack of open elements, but the last
+ table element in the stack of open elements has no parent, or
+ its parent node is not an element, then the foster parent
+ element is the element before the last table element in the
+ stack of open elements. */
+ for($n = count($this->stack) - 1; $n >= 0; $n--) {
+ if($this->stack[$n]->nodeName === 'table') {
+ $table = $this->stack[$n];
+ break;
+ }
+ }
+
+ if(isset($table) && $table->parentNode !== null) {
+ $this->foster_parent = $table->parentNode;
+
+ } elseif(!isset($table)) {
+ $this->foster_parent = $this->stack[0];
+
+ } elseif(isset($table) && ($table->parentNode === null ||
+ $table->parentNode->nodeType !== XML_ELEMENT_NODE)) {
+ $this->foster_parent = $this->stack[$n - 1];
+ }
+ }
+
+ $this->inBody($token);
+ }
+ }
+
+ private function inCaption($token)
+ {
+ /* An end tag whose tag name is "caption" */
+ if($token['type'] === HTML5::ENDTAG && $token['name'] === 'caption') {
+ /* If the stack of open elements does not have an element in table
+ scope with the same tag name as the token, this is a parse error.
+ Ignore the token. (innerHTML case) */
+ if(!$this->elementInScope($token['name'], true)) {
+ // Ignore
+
+ /* Otherwise: */
+ } else {
+ /* Generate implied end tags. */
+ $this->generateImpliedEndTags();
+
+ /* Now, if the current node is not a caption element, then this
+ is a parse error. */
+ // w/e
+
+ /* Pop elements from this stack until a caption element has
+ been popped from the stack. */
+ while(true) {
+ $node = end($this->stack)->nodeName;
+ array_pop($this->stack);
+
+ if($node === 'caption') {
+ break;
+ }
+ }
+
+ /* Clear the list of active formatting elements up to the last
+ marker. */
+ $this->clearTheActiveFormattingElementsUpToTheLastMarker();
+
+ /* Switch the insertion mode to "in table". */
+ $this->mode = self::IN_TABLE;
+ }
+
+ /* A start tag whose tag name is one of: "caption", "col", "colgroup",
+ "tbody", "td", "tfoot", "th", "thead", "tr", or an end tag whose tag
+ name is "table" */
+ } elseif(($token['type'] === HTML5::STARTTAG && in_array($token['name'],
+ array('caption', 'col', 'colgroup', 'tbody', 'td', 'tfoot', 'th',
+ 'thead', 'tr'))) || ($token['type'] === HTML5::ENDTAG &&
+ $token['name'] === 'table')) {
+ /* Parse error. Act as if an end tag with the tag name "caption"
+ had been seen, then, if that token wasn't ignored, reprocess the
+ current token. */
+ $this->inCaption(array(
+ 'name' => 'caption',
+ 'type' => HTML5::ENDTAG
+ ));
+
+ return $this->inTable($token);
+
+ /* An end tag whose tag name is one of: "body", "col", "colgroup",
+ "html", "tbody", "td", "tfoot", "th", "thead", "tr" */
+ } elseif($token['type'] === HTML5::ENDTAG && in_array($token['name'],
+ array('body', 'col', 'colgroup', 'html', 'tbody', 'tfoot', 'th',
+ 'thead', 'tr'))) {
+ // Parse error. Ignore the token.
+
+ /* Anything else */
+ } else {
+ /* Process the token as if the insertion mode was "in body". */
+ $this->inBody($token);
+ }
+ }
+
+ private function inColumnGroup($token)
+ {
+ /* A character token that is one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE */
+ if($token['type'] === HTML5::CHARACTR &&
+ preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])) {
+ /* Append the character to the current node. */
+ $text = $this->dom->createTextNode($token['data']);
+ end($this->stack)->appendChild($text);
+
+ /* A comment token */
+ } elseif($token['type'] === HTML5::COMMENT) {
+ /* Append a Comment node to the current node with the data
+ attribute set to the data given in the comment token. */
+ $comment = $this->dom->createComment($token['data']);
+ end($this->stack)->appendChild($comment);
+
+ /* A start tag whose tag name is "col" */
+ } elseif($token['type'] === HTML5::STARTTAG && $token['name'] === 'col') {
+ /* Insert a col element for the token. Immediately pop the current
+ node off the stack of open elements. */
+ $this->insertElement($token);
+ array_pop($this->stack);
+
+ /* An end tag whose tag name is "colgroup" */
+ } elseif($token['type'] === HTML5::ENDTAG &&
+ $token['name'] === 'colgroup') {
+ /* If the current node is the root html element, then this is a
+ parse error, ignore the token. (innerHTML case) */
+ if(end($this->stack)->nodeName === 'html') {
+ // Ignore
+
+ /* Otherwise, pop the current node (which will be a colgroup
+ element) from the stack of open elements. Switch the insertion
+ mode to "in table". */
+ } else {
+ array_pop($this->stack);
+ $this->mode = self::IN_TABLE;
+ }
+
+ /* An end tag whose tag name is "col" */
+ } elseif($token['type'] === HTML5::ENDTAG && $token['name'] === 'col') {
+ /* Parse error. Ignore the token. */
+
+ /* Anything else */
+ } else {
+ /* Act as if an end tag with the tag name "colgroup" had been seen,
+ and then, if that token wasn't ignored, reprocess the current token. */
+ $this->inColumnGroup(array(
+ 'name' => 'colgroup',
+ 'type' => HTML5::ENDTAG
+ ));
+
+ return $this->inTable($token);
+ }
+ }
+
+ private function inTableBody($token)
+ {
+ $clear = array('tbody', 'tfoot', 'thead', 'html');
+
+ /* A start tag whose tag name is "tr" */
+ if($token['type'] === HTML5::STARTTAG && $token['name'] === 'tr') {
+ /* Clear the stack back to a table body context. */
+ $this->clearStackToTableContext($clear);
+
+ /* Insert a tr element for the token, then switch the insertion
+ mode to "in row". */
+ $this->insertElement($token);
+ $this->mode = self::IN_ROW;
+
+ /* A start tag whose tag name is one of: "th", "td" */
+ } elseif($token['type'] === HTML5::STARTTAG &&
+ ($token['name'] === 'th' || $token['name'] === 'td')) {
+ /* Parse error. Act as if a start tag with the tag name "tr" had
+ been seen, then reprocess the current token. */
+ $this->inTableBody(array(
+ 'name' => 'tr',
+ 'type' => HTML5::STARTTAG,
+ 'attr' => array()
+ ));
+
+ return $this->inRow($token);
+
+ /* An end tag whose tag name is one of: "tbody", "tfoot", "thead" */
+ } elseif($token['type'] === HTML5::ENDTAG &&
+ in_array($token['name'], array('tbody', 'tfoot', 'thead'))) {
+ /* If the stack of open elements does not have an element in table
+ scope with the same tag name as the token, this is a parse error.
+ Ignore the token. */
+ if(!$this->elementInScope($token['name'], true)) {
+ // Ignore
+
+ /* Otherwise: */
+ } else {
+ /* Clear the stack back to a table body context. */
+ $this->clearStackToTableContext($clear);
+
+ /* Pop the current node from the stack of open elements. Switch
+ the insertion mode to "in table". */
+ array_pop($this->stack);
+ $this->mode = self::IN_TABLE;
+ }
+
+ /* A start tag whose tag name is one of: "caption", "col", "colgroup",
+ "tbody", "tfoot", "thead", or an end tag whose tag name is "table" */
+ } elseif(($token['type'] === HTML5::STARTTAG && in_array($token['name'],
+ array('caption', 'col', 'colgroup', 'tbody', 'tfoor', 'thead'))) ||
+ ($token['type'] === HTML5::STARTTAG && $token['name'] === 'table')) {
+ /* If the stack of open elements does not have a tbody, thead, or
+ tfoot element in table scope, this is a parse error. Ignore the
+ token. (innerHTML case) */
+ if(!$this->elementInScope(array('tbody', 'thead', 'tfoot'), true)) {
+ // Ignore.
+
+ /* Otherwise: */
+ } else {
+ /* Clear the stack back to a table body context. */
+ $this->clearStackToTableContext($clear);
+
+ /* Act as if an end tag with the same tag name as the current
+ node ("tbody", "tfoot", or "thead") had been seen, then
+ reprocess the current token. */
+ $this->inTableBody(array(
+ 'name' => end($this->stack)->nodeName,
+ 'type' => HTML5::ENDTAG
+ ));
+
+ return $this->mainPhase($token);
+ }
+
+ /* An end tag whose tag name is one of: "body", "caption", "col",
+ "colgroup", "html", "td", "th", "tr" */
+ } elseif($token['type'] === HTML5::ENDTAG && in_array($token['name'],
+ array('body', 'caption', 'col', 'colgroup', 'html', 'td', 'th', 'tr'))) {
+ /* Parse error. Ignore the token. */
+
+ /* Anything else */
+ } else {
+ /* Process the token as if the insertion mode was "in table". */
+ $this->inTable($token);
+ }
+ }
+
+ private function inRow($token)
+ {
+ $clear = array('tr', 'html');
+
+ /* A start tag whose tag name is one of: "th", "td" */
+ if($token['type'] === HTML5::STARTTAG &&
+ ($token['name'] === 'th' || $token['name'] === 'td')) {
+ /* Clear the stack back to a table row context. */
+ $this->clearStackToTableContext($clear);
+
+ /* Insert an HTML element for the token, then switch the insertion
+ mode to "in cell". */
+ $this->insertElement($token);
+ $this->mode = self::IN_CELL;
+
+ /* Insert a marker at the end of the list of active formatting
+ elements. */
+ $this->a_formatting[] = self::MARKER;
+
+ /* An end tag whose tag name is "tr" */
+ } elseif($token['type'] === HTML5::ENDTAG && $token['name'] === 'tr') {
+ /* If the stack of open elements does not have an element in table
+ scope with the same tag name as the token, this is a parse error.
+ Ignore the token. (innerHTML case) */
+ if(!$this->elementInScope($token['name'], true)) {
+ // Ignore.
+
+ /* Otherwise: */
+ } else {
+ /* Clear the stack back to a table row context. */
+ $this->clearStackToTableContext($clear);
+
+ /* Pop the current node (which will be a tr element) from the
+ stack of open elements. Switch the insertion mode to "in table
+ body". */
+ array_pop($this->stack);
+ $this->mode = self::IN_TBODY;
+ }
+
+ /* A start tag whose tag name is one of: "caption", "col", "colgroup",
+ "tbody", "tfoot", "thead", "tr" or an end tag whose tag name is "table" */
+ } elseif($token['type'] === HTML5::STARTTAG && in_array($token['name'],
+ array('caption', 'col', 'colgroup', 'tbody', 'tfoot', 'thead', 'tr'))) {
+ /* Act as if an end tag with the tag name "tr" had been seen, then,
+ if that token wasn't ignored, reprocess the current token. */
+ $this->inRow(array(
+ 'name' => 'tr',
+ 'type' => HTML5::ENDTAG
+ ));
+
+ return $this->inCell($token);
+
+ /* An end tag whose tag name is one of: "tbody", "tfoot", "thead" */
+ } elseif($token['type'] === HTML5::ENDTAG &&
+ in_array($token['name'], array('tbody', 'tfoot', 'thead'))) {
+ /* If the stack of open elements does not have an element in table
+ scope with the same tag name as the token, this is a parse error.
+ Ignore the token. */
+ if(!$this->elementInScope($token['name'], true)) {
+ // Ignore.
+
+ /* Otherwise: */
+ } else {
+ /* Otherwise, act as if an end tag with the tag name "tr" had
+ been seen, then reprocess the current token. */
+ $this->inRow(array(
+ 'name' => 'tr',
+ 'type' => HTML5::ENDTAG
+ ));
+
+ return $this->inCell($token);
+ }
+
+ /* An end tag whose tag name is one of: "body", "caption", "col",
+ "colgroup", "html", "td", "th" */
+ } elseif($token['type'] === HTML5::ENDTAG && in_array($token['name'],
+ array('body', 'caption', 'col', 'colgroup', 'html', 'td', 'th', 'tr'))) {
+ /* Parse error. Ignore the token. */
+
+ /* Anything else */
+ } else {
+ /* Process the token as if the insertion mode was "in table". */
+ $this->inTable($token);
+ }
+ }
+
+ private function inCell($token)
+ {
+ /* An end tag whose tag name is one of: "td", "th" */
+ if($token['type'] === HTML5::ENDTAG &&
+ ($token['name'] === 'td' || $token['name'] === 'th')) {
+ /* If the stack of open elements does not have an element in table
+ scope with the same tag name as that of the token, then this is a
+ parse error and the token must be ignored. */
+ if(!$this->elementInScope($token['name'], true)) {
+ // Ignore.
+
+ /* Otherwise: */
+ } else {
+ /* Generate implied end tags, except for elements with the same
+ tag name as the token. */
+ $this->generateImpliedEndTags(array($token['name']));
+
+ /* Now, if the current node is not an element with the same tag
+ name as the token, then this is a parse error. */
+ // k
+
+ /* Pop elements from this stack until an element with the same
+ tag name as the token has been popped from the stack. */
+ while(true) {
+ $node = end($this->stack)->nodeName;
+ array_pop($this->stack);
+
+ if($node === $token['name']) {
+ break;
+ }
+ }
+
+ /* Clear the list of active formatting elements up to the last
+ marker. */
+ $this->clearTheActiveFormattingElementsUpToTheLastMarker();
+
+ /* Switch the insertion mode to "in row". (The current node
+ will be a tr element at this point.) */
+ $this->mode = self::IN_ROW;
+ }
+
+ /* A start tag whose tag name is one of: "caption", "col", "colgroup",
+ "tbody", "td", "tfoot", "th", "thead", "tr" */
+ } elseif($token['type'] === HTML5::STARTTAG && in_array($token['name'],
+ array('caption', 'col', 'colgroup', 'tbody', 'td', 'tfoot', 'th',
+ 'thead', 'tr'))) {
+ /* If the stack of open elements does not have a td or th element
+ in table scope, then this is a parse error; ignore the token.
+ (innerHTML case) */
+ if(!$this->elementInScope(array('td', 'th'), true)) {
+ // Ignore.
+
+ /* Otherwise, close the cell (see below) and reprocess the current
+ token. */
+ } else {
+ $this->closeCell();
+ return $this->inRow($token);
+ }
+
+ /* A start tag whose tag name is one of: "caption", "col", "colgroup",
+ "tbody", "td", "tfoot", "th", "thead", "tr" */
+ } elseif($token['type'] === HTML5::STARTTAG && in_array($token['name'],
+ array('caption', 'col', 'colgroup', 'tbody', 'td', 'tfoot', 'th',
+ 'thead', 'tr'))) {
+ /* If the stack of open elements does not have a td or th element
+ in table scope, then this is a parse error; ignore the token.
+ (innerHTML case) */
+ if(!$this->elementInScope(array('td', 'th'), true)) {
+ // Ignore.
+
+ /* Otherwise, close the cell (see below) and reprocess the current
+ token. */
+ } else {
+ $this->closeCell();
+ return $this->inRow($token);
+ }
+
+ /* An end tag whose tag name is one of: "body", "caption", "col",
+ "colgroup", "html" */
+ } elseif($token['type'] === HTML5::ENDTAG && in_array($token['name'],
+ array('body', 'caption', 'col', 'colgroup', 'html'))) {
+ /* Parse error. Ignore the token. */
+
+ /* An end tag whose tag name is one of: "table", "tbody", "tfoot",
+ "thead", "tr" */
+ } elseif($token['type'] === HTML5::ENDTAG && in_array($token['name'],
+ array('table', 'tbody', 'tfoot', 'thead', 'tr'))) {
+ /* If the stack of open elements does not have an element in table
+ scope with the same tag name as that of the token (which can only
+ happen for "tbody", "tfoot" and "thead", or, in the innerHTML case),
+ then this is a parse error and the token must be ignored. */
+ if(!$this->elementInScope($token['name'], true)) {
+ // Ignore.
+
+ /* Otherwise, close the cell (see below) and reprocess the current
+ token. */
+ } else {
+ $this->closeCell();
+ return $this->inRow($token);
+ }
+
+ /* Anything else */
+ } else {
+ /* Process the token as if the insertion mode was "in body". */
+ $this->inBody($token);
+ }
+ }
+
+ private function inSelect($token)
+ {
+ /* Handle the token as follows: */
+
+ /* A character token */
+ if($token['type'] === HTML5::CHARACTR) {
+ /* Append the token's character to the current node. */
+ $this->insertText($token['data']);
+
+ /* A comment token */
+ } elseif($token['type'] === HTML5::COMMENT) {
+ /* Append a Comment node to the current node with the data
+ attribute set to the data given in the comment token. */
+ $this->insertComment($token['data']);
+
+ /* A start tag token whose tag name is "option" */
+ } elseif($token['type'] === HTML5::STARTTAG &&
+ $token['name'] === 'option') {
+ /* If the current node is an option element, act as if an end tag
+ with the tag name "option" had been seen. */
+ if(end($this->stack)->nodeName === 'option') {
+ $this->inSelect(array(
+ 'name' => 'option',
+ 'type' => HTML5::ENDTAG
+ ));
+ }
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+
+ /* A start tag token whose tag name is "optgroup" */
+ } elseif($token['type'] === HTML5::STARTTAG &&
+ $token['name'] === 'optgroup') {
+ /* If the current node is an option element, act as if an end tag
+ with the tag name "option" had been seen. */
+ if(end($this->stack)->nodeName === 'option') {
+ $this->inSelect(array(
+ 'name' => 'option',
+ 'type' => HTML5::ENDTAG
+ ));
+ }
+
+ /* If the current node is an optgroup element, act as if an end tag
+ with the tag name "optgroup" had been seen. */
+ if(end($this->stack)->nodeName === 'optgroup') {
+ $this->inSelect(array(
+ 'name' => 'optgroup',
+ 'type' => HTML5::ENDTAG
+ ));
+ }
+
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+
+ /* An end tag token whose tag name is "optgroup" */
+ } elseif($token['type'] === HTML5::ENDTAG &&
+ $token['name'] === 'optgroup') {
+ /* First, if the current node is an option element, and the node
+ immediately before it in the stack of open elements is an optgroup
+ element, then act as if an end tag with the tag name "option" had
+ been seen. */
+ $elements_in_stack = count($this->stack);
+
+ if($this->stack[$elements_in_stack - 1]->nodeName === 'option' &&
+ $this->stack[$elements_in_stack - 2]->nodeName === 'optgroup') {
+ $this->inSelect(array(
+ 'name' => 'option',
+ 'type' => HTML5::ENDTAG
+ ));
+ }
+
+ /* If the current node is an optgroup element, then pop that node
+ from the stack of open elements. Otherwise, this is a parse error,
+ ignore the token. */
+ if($this->stack[$elements_in_stack - 1] === 'optgroup') {
+ array_pop($this->stack);
+ }
+
+ /* An end tag token whose tag name is "option" */
+ } elseif($token['type'] === HTML5::ENDTAG &&
+ $token['name'] === 'option') {
+ /* If the current node is an option element, then pop that node
+ from the stack of open elements. Otherwise, this is a parse error,
+ ignore the token. */
+ if(end($this->stack)->nodeName === 'option') {
+ array_pop($this->stack);
+ }
+
+ /* An end tag whose tag name is "select" */
+ } elseif($token['type'] === HTML5::ENDTAG &&
+ $token['name'] === 'select') {
+ /* If the stack of open elements does not have an element in table
+ scope with the same tag name as the token, this is a parse error.
+ Ignore the token. (innerHTML case) */
+ if(!$this->elementInScope($token['name'], true)) {
+ // w/e
+
+ /* Otherwise: */
+ } else {
+ /* Pop elements from the stack of open elements until a select
+ element has been popped from the stack. */
+ while(true) {
+ $current = end($this->stack)->nodeName;
+ array_pop($this->stack);
+
+ if($current === 'select') {
+ break;
+ }
+ }
+
+ /* Reset the insertion mode appropriately. */
+ $this->resetInsertionMode();
+ }
+
+ /* A start tag whose tag name is "select" */
+ } elseif($token['name'] === 'select' &&
+ $token['type'] === HTML5::STARTTAG) {
+ /* Parse error. Act as if the token had been an end tag with the
+ tag name "select" instead. */
+ $this->inSelect(array(
+ 'name' => 'select',
+ 'type' => HTML5::ENDTAG
+ ));
+
+ /* An end tag whose tag name is one of: "caption", "table", "tbody",
+ "tfoot", "thead", "tr", "td", "th" */
+ } elseif(in_array($token['name'], array('caption', 'table', 'tbody',
+ 'tfoot', 'thead', 'tr', 'td', 'th')) && $token['type'] === HTML5::ENDTAG) {
+ /* Parse error. */
+ // w/e
+
+ /* If the stack of open elements has an element in table scope with
+ the same tag name as that of the token, then act as if an end tag
+ with the tag name "select" had been seen, and reprocess the token.
+ Otherwise, ignore the token. */
+ if($this->elementInScope($token['name'], true)) {
+ $this->inSelect(array(
+ 'name' => 'select',
+ 'type' => HTML5::ENDTAG
+ ));
+
+ $this->mainPhase($token);
+ }
+
+ /* Anything else */
+ } else {
+ /* Parse error. Ignore the token. */
+ }
+ }
+
+ private function afterBody($token)
+ {
+ /* Handle the token as follows: */
+
+ /* A character token that is one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE */
+ if($token['type'] === HTML5::CHARACTR &&
+ preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])) {
+ /* Process the token as it would be processed if the insertion mode
+ was "in body". */
+ $this->inBody($token);
+
+ /* A comment token */
+ } elseif($token['type'] === HTML5::COMMENT) {
+ /* Append a Comment node to the first element in the stack of open
+ elements (the html element), with the data attribute set to the
+ data given in the comment token. */
+ $comment = $this->dom->createComment($token['data']);
+ $this->stack[0]->appendChild($comment);
+
+ /* An end tag with the tag name "html" */
+ } elseif($token['type'] === HTML5::ENDTAG && $token['name'] === 'html') {
+ /* If the parser was originally created in order to handle the
+ setting of an element's innerHTML attribute, this is a parse error;
+ ignore the token. (The element will be an html element in this
+ case.) (innerHTML case) */
+
+ /* Otherwise, switch to the trailing end phase. */
+ $this->phase = self::END_PHASE;
+
+ /* Anything else */
+ } else {
+ /* Parse error. Set the insertion mode to "in body" and reprocess
+ the token. */
+ $this->mode = self::IN_BODY;
+ return $this->inBody($token);
+ }
+ }
+
+ private function inFrameset($token)
+ {
+ /* Handle the token as follows: */
+
+ /* A character token that is one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ U+000D CARRIAGE RETURN (CR), or U+0020 SPACE */
+ if($token['type'] === HTML5::CHARACTR &&
+ preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])) {
+ /* Append the character to the current node. */
+ $this->insertText($token['data']);
+
+ /* A comment token */
+ } elseif($token['type'] === HTML5::COMMENT) {
+ /* Append a Comment node to the current node with the data
+ attribute set to the data given in the comment token. */
+ $this->insertComment($token['data']);
+
+ /* A start tag with the tag name "frameset" */
+ } elseif($token['name'] === 'frameset' &&
+ $token['type'] === HTML5::STARTTAG) {
+ $this->insertElement($token);
+
+ /* An end tag with the tag name "frameset" */
+ } elseif($token['name'] === 'frameset' &&
+ $token['type'] === HTML5::ENDTAG) {
+ /* If the current node is the root html element, then this is a
+ parse error; ignore the token. (innerHTML case) */
+ if(end($this->stack)->nodeName === 'html') {
+ // Ignore
+
+ } else {
+ /* Otherwise, pop the current node from the stack of open
+ elements. */
+ array_pop($this->stack);
+
+ /* If the parser was not originally created in order to handle
+ the setting of an element's innerHTML attribute (innerHTML case),
+ and the current node is no longer a frameset element, then change
+ the insertion mode to "after frameset". */
+ $this->mode = self::AFTR_FRAME;
+ }
+
+ /* A start tag with the tag name "frame" */
+ } elseif($token['name'] === 'frame' &&
+ $token['type'] === HTML5::STARTTAG) {
+ /* Insert an HTML element for the token. */
+ $this->insertElement($token);
+
+ /* Immediately pop the current node off the stack of open elements. */
+ array_pop($this->stack);
+
+ /* A start tag with the tag name "noframes" */
+ } elseif($token['name'] === 'noframes' &&
+ $token['type'] === HTML5::STARTTAG) {
+ /* Process the token as if the insertion mode had been "in body". */
+ $this->inBody($token);
+
+ /* Anything else */
+ } else {
+ /* Parse error. Ignore the token. */
+ }
+ }
+
+ private function afterFrameset($token)
+ {
+ /* Handle the token as follows: */
+
+ /* A character token that is one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ U+000D CARRIAGE RETURN (CR), or U+0020 SPACE */
+ if($token['type'] === HTML5::CHARACTR &&
+ preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])) {
+ /* Append the character to the current node. */
+ $this->insertText($token['data']);
+
+ /* A comment token */
+ } elseif($token['type'] === HTML5::COMMENT) {
+ /* Append a Comment node to the current node with the data
+ attribute set to the data given in the comment token. */
+ $this->insertComment($token['data']);
+
+ /* An end tag with the tag name "html" */
+ } elseif($token['name'] === 'html' &&
+ $token['type'] === HTML5::ENDTAG) {
+ /* Switch to the trailing end phase. */
+ $this->phase = self::END_PHASE;
+
+ /* A start tag with the tag name "noframes" */
+ } elseif($token['name'] === 'noframes' &&
+ $token['type'] === HTML5::STARTTAG) {
+ /* Process the token as if the insertion mode had been "in body". */
+ $this->inBody($token);
+
+ /* Anything else */
+ } else {
+ /* Parse error. Ignore the token. */
+ }
+ }
+
+ private function trailingEndPhase($token)
+ {
+ /* After the main phase, as each token is emitted from the tokenisation
+ stage, it must be processed as described in this section. */
+
+ /* A DOCTYPE token */
+ if($token['type'] === HTML5::DOCTYPE) {
+ // Parse error. Ignore the token.
+
+ /* A comment token */
+ } elseif($token['type'] === HTML5::COMMENT) {
+ /* Append a Comment node to the Document object with the data
+ attribute set to the data given in the comment token. */
+ $comment = $this->dom->createComment($token['data']);
+ $this->dom->appendChild($comment);
+
+ /* A character token that is one of one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE */
+ } elseif($token['type'] === HTML5::CHARACTR &&
+ preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])) {
+ /* Process the token as it would be processed in the main phase. */
+ $this->mainPhase($token);
+
+ /* A character token that is not one of U+0009 CHARACTER TABULATION,
+ U+000A LINE FEED (LF), U+000B LINE TABULATION, U+000C FORM FEED (FF),
+ or U+0020 SPACE. Or a start tag token. Or an end tag token. */
+ } elseif(($token['type'] === HTML5::CHARACTR &&
+ preg_match('/^[\t\n\x0b\x0c ]+$/', $token['data'])) ||
+ $token['type'] === HTML5::STARTTAG || $token['type'] === HTML5::ENDTAG) {
+ /* Parse error. Switch back to the main phase and reprocess the
+ token. */
+ $this->phase = self::MAIN_PHASE;
+ return $this->mainPhase($token);
+
+ /* An end-of-file token */
+ } elseif($token['type'] === HTML5::EOF) {
+ /* OMG DONE!! */
+ }
+ }
+
+ private function insertElement($token, $append = true)
+ {
+ $el = $this->dom->createElement($token['name']);
+
+ foreach($token['attr'] as $attr) {
+ if(!$el->hasAttribute($attr['name'])) {
+ $el->setAttribute($attr['name'], $attr['value']);
+ }
+ }
+
+ $this->appendToRealParent($el);
+ $this->stack[] = $el;
+
+ return $el;
+ }
+
+ private function insertText($data)
+ {
+ $text = $this->dom->createTextNode($data);
+ $this->appendToRealParent($text);
+ }
+
+ private function insertComment($data)
+ {
+ $comment = $this->dom->createComment($data);
+ $this->appendToRealParent($comment);
+ }
+
+ private function appendToRealParent($node)
+ {
+ if($this->foster_parent === null) {
+ end($this->stack)->appendChild($node);
+
+ } elseif($this->foster_parent !== null) {
+ /* If the foster parent element is the parent element of the
+ last table element in the stack of open elements, then the new
+ node must be inserted immediately before the last table element
+ in the stack of open elements in the foster parent element;
+ otherwise, the new node must be appended to the foster parent
+ element. */
+ for($n = count($this->stack) - 1; $n >= 0; $n--) {
+ if($this->stack[$n]->nodeName === 'table' &&
+ $this->stack[$n]->parentNode !== null) {
+ $table = $this->stack[$n];
+ break;
+ }
+ }
+
+ if(isset($table) && $this->foster_parent->isSameNode($table->parentNode))
+ $this->foster_parent->insertBefore($node, $table);
+ else
+ $this->foster_parent->appendChild($node);
+
+ $this->foster_parent = null;
+ }
+ }
+
+ private function elementInScope($el, $table = false)
+ {
+ if(is_array($el)) {
+ foreach($el as $element) {
+ if($this->elementInScope($element, $table)) {
+ return true;
+ }
+ }
+
+ return false;
+ }
+
+ $leng = count($this->stack);
+
+ for($n = 0; $n < $leng; $n++) {
+ /* 1. Initialise node to be the current node (the bottommost node of
+ the stack). */
+ $node = $this->stack[$leng - 1 - $n];
+
+ if($node->tagName === $el) {
+ /* 2. If node is the target node, terminate in a match state. */
+ return true;
+
+ } elseif($node->tagName === 'table') {
+ /* 3. Otherwise, if node is a table element, terminate in a failure
+ state. */
+ return false;
+
+ } elseif($table === true && in_array($node->tagName, array('caption', 'td',
+ 'th', 'button', 'marquee', 'object'))) {
+ /* 4. Otherwise, if the algorithm is the "has an element in scope"
+ variant (rather than the "has an element in table scope" variant),
+ and node is one of the following, terminate in a failure state. */
+ return false;
+
+ } elseif($node === $node->ownerDocument->documentElement) {
+ /* 5. Otherwise, if node is an html element (root element), terminate
+ in a failure state. (This can only happen if the node is the topmost
+ node of the stack of open elements, and prevents the next step from
+ being invoked if there are no more elements in the stack.) */
+ return false;
+ }
+
+ /* Otherwise, set node to the previous entry in the stack of open
+ elements and return to step 2. (This will never fail, since the loop
+ will always terminate in the previous step if the top of the stack
+ is reached.) */
+ }
+ }
+
+ private function reconstructActiveFormattingElements()
+ {
+ /* 1. If there are no entries in the list of active formatting elements,
+ then there is nothing to reconstruct; stop this algorithm. */
+ $formatting_elements = count($this->a_formatting);
+
+ if($formatting_elements === 0) {
+ return false;
+ }
+
+ /* 3. Let entry be the last (most recently added) element in the list
+ of active formatting elements. */
+ $entry = end($this->a_formatting);
+
+ /* 2. If the last (most recently added) entry in the list of active
+ formatting elements is a marker, or if it is an element that is in the
+ stack of open elements, then there is nothing to reconstruct; stop this
+ algorithm. */
+ if($entry === self::MARKER || in_array($entry, $this->stack, true)) {
+ return false;
+ }
+
+ for($a = $formatting_elements - 1; $a >= 0; true) {
+ /* 4. If there are no entries before entry in the list of active
+ formatting elements, then jump to step 8. */
+ if($a === 0) {
+ $step_seven = false;
+ break;
+ }
+
+ /* 5. Let entry be the entry one earlier than entry in the list of
+ active formatting elements. */
+ $a--;
+ $entry = $this->a_formatting[$a];
+
+ /* 6. If entry is neither a marker nor an element that is also in
+ thetack of open elements, go to step 4. */
+ if($entry === self::MARKER || in_array($entry, $this->stack, true)) {
+ break;
+ }
+ }
+
+ while(true) {
+ /* 7. Let entry be the element one later than entry in the list of
+ active formatting elements. */
+ if(isset($step_seven) && $step_seven === true) {
+ $a++;
+ $entry = $this->a_formatting[$a];
+ }
+
+ /* 8. Perform a shallow clone of the element entry to obtain clone. */
+ $clone = $entry->cloneNode();
+
+ /* 9. Append clone to the current node and push it onto the stack
+ of open elements so that it is the new current node. */
+ end($this->stack)->appendChild($clone);
+ $this->stack[] = $clone;
+
+ /* 10. Replace the entry for entry in the list with an entry for
+ clone. */
+ $this->a_formatting[$a] = $clone;
+
+ /* 11. If the entry for clone in the list of active formatting
+ elements is not the last entry in the list, return to step 7. */
+ if(end($this->a_formatting) !== $clone) {
+ $step_seven = true;
+ } else {
+ break;
+ }
+ }
+ }
+
+ private function clearTheActiveFormattingElementsUpToTheLastMarker()
+ {
+ /* When the steps below require the UA to clear the list of active
+ formatting elements up to the last marker, the UA must perform the
+ following steps: */
+
+ while(true) {
+ /* 1. Let entry be the last (most recently added) entry in the list
+ of active formatting elements. */
+ $entry = end($this->a_formatting);
+
+ /* 2. Remove entry from the list of active formatting elements. */
+ array_pop($this->a_formatting);
+
+ /* 3. If entry was a marker, then stop the algorithm at this point.
+ The list has been cleared up to the last marker. */
+ if($entry === self::MARKER) {
+ break;
+ }
+ }
+ }
+
+ private function generateImpliedEndTags(array $exclude = array())
+ {
+ /* When the steps below require the UA to generate implied end tags,
+ then, if the current node is a dd element, a dt element, an li element,
+ a p element, a td element, a th element, or a tr element, the UA must
+ act as if an end tag with the respective tag name had been seen and
+ then generate implied end tags again. */
+ $node = end($this->stack);
+ $elements = array_diff(array('dd', 'dt', 'li', 'p', 'td', 'th', 'tr'), $exclude);
+
+ while(in_array(end($this->stack)->nodeName, $elements)) {
+ array_pop($this->stack);
+ }
+ }
+
+ private function getElementCategory($name)
+ {
+ if(in_array($name, $this->special))
+ return self::SPECIAL;
+
+ elseif(in_array($name, $this->scoping))
+ return self::SCOPING;
+
+ elseif(in_array($name, $this->formatting))
+ return self::FORMATTING;
+
+ else
+ return self::PHRASING;
+ }
+
+ private function clearStackToTableContext($elements)
+ {
+ /* When the steps above require the UA to clear the stack back to a
+ table context, it means that the UA must, while the current node is not
+ a table element or an html element, pop elements from the stack of open
+ elements. If this causes any elements to be popped from the stack, then
+ this is a parse error. */
+ while(true) {
+ $node = end($this->stack)->nodeName;
+
+ if(in_array($node, $elements)) {
+ break;
+ } else {
+ array_pop($this->stack);
+ }
+ }
+ }
+
+ private function resetInsertionMode()
+ {
+ /* 1. Let last be false. */
+ $last = false;
+ $leng = count($this->stack);
+
+ for($n = $leng - 1; $n >= 0; $n--) {
+ /* 2. Let node be the last node in the stack of open elements. */
+ $node = $this->stack[$n];
+
+ /* 3. If node is the first node in the stack of open elements, then
+ set last to true. If the element whose innerHTML attribute is being
+ set is neither a td element nor a th element, then set node to the
+ element whose innerHTML attribute is being set. (innerHTML case) */
+ if($this->stack[0]->isSameNode($node)) {
+ $last = true;
+ }
+
+ /* 4. If node is a select element, then switch the insertion mode to
+ "in select" and abort these steps. (innerHTML case) */
+ if($node->nodeName === 'select') {
+ $this->mode = self::IN_SELECT;
+ break;
+
+ /* 5. If node is a td or th element, then switch the insertion mode
+ to "in cell" and abort these steps. */
+ } elseif($node->nodeName === 'td' || $node->nodeName === 'th') {
+ $this->mode = self::IN_CELL;
+ break;
+
+ /* 6. If node is a tr element, then switch the insertion mode to
+ "in row" and abort these steps. */
+ } elseif($node->nodeName === 'tr') {
+ $this->mode = self::IN_ROW;
+ break;
+
+ /* 7. If node is a tbody, thead, or tfoot element, then switch the
+ insertion mode to "in table body" and abort these steps. */
+ } elseif(in_array($node->nodeName, array('tbody', 'thead', 'tfoot'))) {
+ $this->mode = self::IN_TBODY;
+ break;
+
+ /* 8. If node is a caption element, then switch the insertion mode
+ to "in caption" and abort these steps. */
+ } elseif($node->nodeName === 'caption') {
+ $this->mode = self::IN_CAPTION;
+ break;
+
+ /* 9. If node is a colgroup element, then switch the insertion mode
+ to "in column group" and abort these steps. (innerHTML case) */
+ } elseif($node->nodeName === 'colgroup') {
+ $this->mode = self::IN_CGROUP;
+ break;
+
+ /* 10. If node is a table element, then switch the insertion mode
+ to "in table" and abort these steps. */
+ } elseif($node->nodeName === 'table') {
+ $this->mode = self::IN_TABLE;
+ break;
+
+ /* 11. If node is a head element, then switch the insertion mode
+ to "in body" ("in body"! not "in head"!) and abort these steps.
+ (innerHTML case) */
+ } elseif($node->nodeName === 'head') {
+ $this->mode = self::IN_BODY;
+ break;
+
+ /* 12. If node is a body element, then switch the insertion mode to
+ "in body" and abort these steps. */
+ } elseif($node->nodeName === 'body') {
+ $this->mode = self::IN_BODY;
+ break;
+
+ /* 13. If node is a frameset element, then switch the insertion
+ mode to "in frameset" and abort these steps. (innerHTML case) */
+ } elseif($node->nodeName === 'frameset') {
+ $this->mode = self::IN_FRAME;
+ break;
+
+ /* 14. If node is an html element, then: if the head element
+ pointer is null, switch the insertion mode to "before head",
+ otherwise, switch the insertion mode to "after head". In either
+ case, abort these steps. (innerHTML case) */
+ } elseif($node->nodeName === 'html') {
+ $this->mode = ($this->head_pointer === null)
+ ? self::BEFOR_HEAD
+ : self::AFTER_HEAD;
+
+ break;
+
+ /* 15. If last is true, then set the insertion mode to "in body"
+ and abort these steps. (innerHTML case) */
+ } elseif($last) {
+ $this->mode = self::IN_BODY;
+ break;
+ }
+ }
+ }
+
+ private function closeCell()
+ {
+ /* If the stack of open elements has a td or th element in table scope,
+ then act as if an end tag token with that tag name had been seen. */
+ foreach(array('td', 'th') as $cell) {
+ if($this->elementInScope($cell, true)) {
+ $this->inCell(array(
+ 'name' => $cell,
+ 'type' => HTML5::ENDTAG
+ ));
+
+ break;
+ }
+ }
+ }
+
+ public function save()
+ {
+ return $this->dom;
+ }
+}
diff --git a/vendor/ezyang/htmlpurifier/maintenance/add-vimline.php b/vendor/ezyang/htmlpurifier/maintenance/add-vimline.php
new file mode 100644
index 000000000..d6a8eb202
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/maintenance/add-vimline.php
@@ -0,0 +1,130 @@
+#!/usr/bin/php
+<?php
+
+chdir(dirname(__FILE__));
+require_once 'common.php';
+assertCli();
+
+/**
+ * @file
+ * Adds vimline to files
+ */
+
+chdir(dirname(__FILE__) . '/..');
+$FS = new FSTools();
+
+$vimline = 'vim: et sw=4 sts=4';
+
+$files = $FS->globr('.', '*');
+foreach ($files as $file) {
+ if (
+ !is_file($file) ||
+ prefix_is('./docs/doxygen', $file) ||
+ prefix_is('./library/standalone', $file) ||
+ prefix_is('./docs/specimens', $file) ||
+ postfix_is('.ser', $file) ||
+ postfix_is('.tgz', $file) ||
+ postfix_is('.patch', $file) ||
+ postfix_is('.dtd', $file) ||
+ postfix_is('.ent', $file) ||
+ postfix_is('.png', $file) ||
+ postfix_is('.ico', $file) ||
+ // wontfix
+ postfix_is('.vtest', $file) ||
+ postfix_is('.svg', $file) ||
+ postfix_is('.phpt', $file) ||
+ postfix_is('VERSION', $file) ||
+ postfix_is('WHATSNEW', $file) ||
+ postfix_is('configdoc/usage.xml', $file) ||
+ postfix_is('library/HTMLPurifier.includes.php', $file) ||
+ postfix_is('library/HTMLPurifier.safe-includes.php', $file) ||
+ postfix_is('smoketests/xssAttacks.xml', $file) ||
+ // phpt files
+ postfix_is('.diff', $file) ||
+ postfix_is('.exp', $file) ||
+ postfix_is('.log', $file) ||
+ postfix_is('.out', $file) ||
+
+ $file == './library/HTMLPurifier/Lexer/PH5P.php' ||
+ $file == './maintenance/PH5P.php'
+ ) continue;
+ $ext = strrchr($file, '.');
+ if (
+ postfix_is('README', $file) ||
+ postfix_is('LICENSE', $file) ||
+ postfix_is('CREDITS', $file) ||
+ postfix_is('INSTALL', $file) ||
+ postfix_is('NEWS', $file) ||
+ postfix_is('TODO', $file) ||
+ postfix_is('WYSIWYG', $file) ||
+ postfix_is('Changelog', $file)
+ ) $ext = '.txt';
+ if (postfix_is('Doxyfile', $file)) $ext = 'Doxyfile';
+ if (postfix_is('.php.in', $file)) $ext = '.php';
+ $no_nl = false;
+ switch ($ext) {
+ case '.php':
+ case '.inc':
+ case '.js':
+ $line = '// %s';
+ break;
+ case '.html':
+ case '.xsl':
+ case '.xml':
+ case '.htc':
+ $line = "<!-- %s\n-->";
+ break;
+ case '.htmlt':
+ $no_nl = true;
+ $line = '--# %s';
+ break;
+ case '.ini':
+ $line = '; %s';
+ break;
+ case '.css':
+ $line = '/* %s */';
+ break;
+ case '.bat':
+ $line = 'rem %s';
+ break;
+ case '.txt':
+ case '.utf8':
+ if (
+ prefix_is('./library/HTMLPurifier/ConfigSchema', $file) ||
+ prefix_is('./smoketests/test-schema', $file) ||
+ prefix_is('./tests/HTMLPurifier/StringHashParser', $file)
+ ) {
+ $no_nl = true;
+ $line = '--# %s';
+ } else {
+ $line = ' %s';
+ }
+ break;
+ case 'Doxyfile':
+ $line = '# %s';
+ break;
+ default:
+ throw new Exception('Unknown file: ' . $file);
+ }
+
+ echo "$file\n";
+ $contents = file_get_contents($file);
+
+ $regex = '~' . str_replace('%s', 'vim: .+', preg_quote($line, '~')) . '~m';
+ $contents = preg_replace($regex, '', $contents);
+
+ $contents = rtrim($contents);
+
+ if (strpos($contents, "\r\n") !== false) $nl = "\r\n";
+ elseif (strpos($contents, "\n") !== false) $nl = "\n";
+ elseif (strpos($contents, "\r") !== false) $nl = "\r";
+ else $nl = PHP_EOL;
+
+ if (!$no_nl) $contents .= $nl;
+ $contents .= $nl . str_replace('%s', $vimline, $line) . $nl;
+
+ file_put_contents($file, $contents);
+
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/maintenance/common.php b/vendor/ezyang/htmlpurifier/maintenance/common.php
new file mode 100644
index 000000000..342bc205a
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/maintenance/common.php
@@ -0,0 +1,25 @@
+<?php
+
+function assertCli()
+{
+ if (php_sapi_name() != 'cli' && !getenv('PHP_IS_CLI')) {
+ echo 'Script cannot be called from web-browser (if you are indeed calling via cli,
+set environment variable PHP_IS_CLI to work around this).';
+ exit(1);
+ }
+}
+
+function prefix_is($comp, $subject)
+{
+ return strncmp($comp, $subject, strlen($comp)) === 0;
+}
+
+function postfix_is($comp, $subject)
+{
+ return strlen($subject) < $comp ? false : substr($subject, -strlen($comp)) === $comp;
+}
+
+// Load useful stuff like FSTools
+require_once dirname(__FILE__) . '/../extras/HTMLPurifierExtras.auto.php';
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/maintenance/compile-doxygen.sh b/vendor/ezyang/htmlpurifier/maintenance/compile-doxygen.sh
new file mode 100755
index 000000000..ecd1127fd
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/maintenance/compile-doxygen.sh
@@ -0,0 +1,11 @@
+#!/bin/bash
+cd ..
+mkdir docs/doxygen
+rm -Rf docs/doxygen/*
+doxygen 1>docs/doxygen/info.log 2>docs/doxygen/errors.log
+if [ "$?" != 0 ]; then
+ cat docs/doxygen/errors.log
+ exit
+fi
+cd docs
+tar czf doxygen.tgz doxygen
diff --git a/vendor/ezyang/htmlpurifier/maintenance/config-scanner.php b/vendor/ezyang/htmlpurifier/maintenance/config-scanner.php
new file mode 100644
index 000000000..c614d1fbc
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/maintenance/config-scanner.php
@@ -0,0 +1,155 @@
+#!/usr/bin/php
+<?php
+
+chdir(dirname(__FILE__));
+require_once 'common.php';
+require_once '../library/HTMLPurifier.auto.php';
+assertCli();
+
+if (version_compare(PHP_VERSION, '5.2.2', '<')) {
+ echo "This script requires PHP 5.2.2 or later, for tokenizer line numbers.";
+ exit(1);
+}
+
+/**
+ * @file
+ * Scans HTML Purifier source code for $config tokens and records the
+ * directive being used; configdoc can use this info later.
+ *
+ * Currently, this just dumps all the info onto the console. Eventually, it
+ * will create an XML file that our XSLT transform can use.
+ */
+
+$FS = new FSTools();
+chdir(dirname(__FILE__) . '/../library/');
+$raw_files = $FS->globr('.', '*.php');
+$files = array();
+foreach ($raw_files as $file) {
+ $file = substr($file, 2); // rm leading './'
+ if (strncmp('standalone/', $file, 11) === 0) continue; // rm generated files
+ if (substr_count($file, '.') > 1) continue; // rm meta files
+ $files[] = $file;
+}
+
+/**
+ * Moves the $i cursor to the next non-whitespace token
+ */
+function consumeWhitespace($tokens, &$i)
+{
+ do {$i++;} while (is_array($tokens[$i]) && $tokens[$i][0] === T_WHITESPACE);
+}
+
+/**
+ * Tests whether or not a token is a particular type. There are three run-cases:
+ * - ($token, $expect_token): tests if the token is $expect_token type;
+ * - ($token, $expect_value): tests if the token is the string $expect_value;
+ * - ($token, $expect_token, $expect_value): tests if token is $expect_token type, and
+ * its string representation is $expect_value
+ */
+function testToken($token, $value_or_token, $value = null)
+{
+ if (is_null($value)) {
+ if (is_int($value_or_token)) return is_array($token) && $token[0] === $value_or_token;
+ else return $token === $value_or_token;
+ } else {
+ return is_array($token) && $token[0] === $value_or_token && $token[1] === $value;
+ }
+}
+
+$counter = 0;
+$full_counter = 0;
+$tracker = array();
+
+foreach ($files as $file) {
+ $tokens = token_get_all(file_get_contents($file));
+ $file = str_replace('\\', '/', $file);
+ for ($i = 0, $c = count($tokens); $i < $c; $i++) {
+ $ok = false;
+ // Match $config
+ if (!$ok && testToken($tokens[$i], T_VARIABLE, '$config')) $ok = true;
+ // Match $this->config
+ while (!$ok && testToken($tokens[$i], T_VARIABLE, '$this')) {
+ consumeWhitespace($tokens, $i);
+ if (!testToken($tokens[$i], T_OBJECT_OPERATOR)) break;
+ consumeWhitespace($tokens, $i);
+ if (testToken($tokens[$i], T_STRING, 'config')) $ok = true;
+ break;
+ }
+ if (!$ok) continue;
+
+ $ok = false;
+ for($i++; $i < $c; $i++) {
+ if ($tokens[$i] === ',' || $tokens[$i] === ')' || $tokens[$i] === ';') {
+ break;
+ }
+ if (is_string($tokens[$i])) continue;
+ if ($tokens[$i][0] === T_OBJECT_OPERATOR) {
+ $ok = true;
+ break;
+ }
+ }
+ if (!$ok) continue;
+
+ $line = $tokens[$i][2];
+
+ consumeWhitespace($tokens, $i);
+ if (!testToken($tokens[$i], T_STRING, 'get')) continue;
+
+ consumeWhitespace($tokens, $i);
+ if (!testToken($tokens[$i], '(')) continue;
+
+ $full_counter++;
+
+ $matched = false;
+ do {
+
+ // What we currently don't match are batch retrievals, and
+ // wildcard retrievals. This data might be useful in the future,
+ // which is why we have a do {} while loop that doesn't actually
+ // do anything.
+
+ consumeWhitespace($tokens, $i);
+ if (!testToken($tokens[$i], T_CONSTANT_ENCAPSED_STRING)) continue;
+ $id = substr($tokens[$i][1], 1, -1);
+
+ $counter++;
+ $matched = true;
+
+ if (!isset($tracker[$id])) $tracker[$id] = array();
+ if (!isset($tracker[$id][$file])) $tracker[$id][$file] = array();
+ $tracker[$id][$file][] = $line;
+
+ } while (0);
+
+ //echo "$file:$line uses $namespace.$directive\n";
+ }
+}
+
+echo "\n$counter/$full_counter instances of \$config or \$this->config found in source code.\n";
+
+echo "Generating XML... ";
+
+$xw = new XMLWriter();
+$xw->openURI('../configdoc/usage.xml');
+$xw->setIndent(true);
+$xw->startDocument('1.0', 'UTF-8');
+$xw->startElement('usage');
+foreach ($tracker as $id => $files) {
+ $xw->startElement('directive');
+ $xw->writeAttribute('id', $id);
+ foreach ($files as $file => $lines) {
+ $xw->startElement('file');
+ $xw->writeAttribute('name', $file);
+ foreach ($lines as $line) {
+ $xw->writeElement('line', $line);
+ }
+ $xw->endElement();
+ }
+ $xw->endElement();
+}
+$xw->endElement();
+$xw->flush();
+
+echo "done!\n";
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/maintenance/flush-definition-cache.php b/vendor/ezyang/htmlpurifier/maintenance/flush-definition-cache.php
new file mode 100755
index 000000000..138badb65
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/maintenance/flush-definition-cache.php
@@ -0,0 +1,42 @@
+#!/usr/bin/php
+<?php
+
+chdir(dirname(__FILE__));
+require_once 'common.php';
+assertCli();
+
+/**
+ * @file
+ * Flushes the definition serial cache. This file should be
+ * called if changes to any subclasses of HTMLPurifier_Definition
+ * or related classes (such as HTMLPurifier_HTMLModule) are made. This
+ * may also be necessary if you've modified a customized version.
+ *
+ * @param Accepts one argument, cache type to flush; otherwise flushes all
+ * the caches.
+ */
+
+echo "Flushing cache... \n";
+
+require_once(dirname(__FILE__) . '/../library/HTMLPurifier.auto.php');
+
+$config = HTMLPurifier_Config::createDefault();
+
+$names = array('HTML', 'CSS', 'URI', 'Test');
+if (isset($argv[1])) {
+ if (in_array($argv[1], $names)) {
+ $names = array($argv[1]);
+ } else {
+ throw new Exception("Cache parameter {$argv[1]} is not a valid cache");
+ }
+}
+
+foreach ($names as $name) {
+ echo " - Flushing $name\n";
+ $cache = new HTMLPurifier_DefinitionCache_Serializer($name);
+ $cache->flush($config);
+}
+
+echo "Cache flushed successfully.\n";
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/maintenance/flush.php b/vendor/ezyang/htmlpurifier/maintenance/flush.php
new file mode 100644
index 000000000..c0853d230
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/maintenance/flush.php
@@ -0,0 +1,30 @@
+#!/usr/bin/php
+<?php
+
+chdir(dirname(__FILE__));
+require_once 'common.php';
+assertCli();
+
+/**
+ * @file
+ * Runs all generation/flush cache scripts to ensure that somewhat volatile
+ * generated files are up-to-date.
+ */
+
+function e($cmd)
+{
+ echo "\$ $cmd\n";
+ passthru($cmd, $status);
+ echo "\n";
+ if ($status) exit($status);
+}
+
+$php = empty($_SERVER['argv'][1]) ? 'php' : $_SERVER['argv'][1];
+
+e($php . ' generate-includes.php');
+e($php . ' generate-schema-cache.php');
+e($php . ' flush-definition-cache.php');
+e($php . ' generate-standalone.php');
+e($php . ' config-scanner.php');
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/maintenance/generate-entity-file.php b/vendor/ezyang/htmlpurifier/maintenance/generate-entity-file.php
new file mode 100755
index 000000000..ff1713e39
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/maintenance/generate-entity-file.php
@@ -0,0 +1,75 @@
+#!/usr/bin/php
+<?php
+
+chdir(dirname(__FILE__));
+require_once 'common.php';
+assertCli();
+
+/**
+ * @file
+ * Parses *.ent files into an entity lookup table, and then serializes and
+ * writes the whole kaboodle to a file. The resulting file is cached so
+ * that this script does not need to be run. This script should rarely,
+ * if ever, be run, since HTML's entities are fairly immutable.
+ */
+
+// here's where the entity files are located, assuming working directory
+// is the same as the location of this PHP file. Needs trailing slash.
+$entity_dir = '../docs/entities/';
+
+// defines the output file for the serialized content.
+$output_file = '../library/HTMLPurifier/EntityLookup/entities.ser';
+
+// courtesy of a PHP manual comment
+function unichr($dec)
+{
+ if ($dec < 128) {
+ $utf = chr($dec);
+ } elseif ($dec < 2048) {
+ $utf = chr(192 + (($dec - ($dec % 64)) / 64));
+ $utf .= chr(128 + ($dec % 64));
+ } else {
+ $utf = chr(224 + (($dec - ($dec % 4096)) / 4096));
+ $utf .= chr(128 + ((($dec % 4096) - ($dec % 64)) / 64));
+ $utf .= chr(128 + ($dec % 64));
+ }
+ return $utf;
+}
+
+if ( !is_dir($entity_dir) ) exit("Fatal Error: Can't find entity directory.\n");
+if ( file_exists($output_file) ) exit("Fatal Error: output file already exists.\n");
+
+$dh = @opendir($entity_dir);
+if ( !$dh ) exit("Fatal Error: Cannot read entity directory.\n");
+
+$entity_files = array();
+while (($file = readdir($dh)) !== false) {
+ if (@$file[0] === '.') continue;
+ if (substr(strrchr($file, "."), 1) !== 'ent') continue;
+ $entity_files[] = $file;
+}
+closedir($dh);
+
+if ( !$entity_files ) exit("Fatal Error: No entity files to parse.\n");
+
+$entity_table = array();
+$regexp = '/<!ENTITY\s+([A-Za-z0-9]+)\s+"&#(?:38;#)?([0-9]+);">/';
+
+foreach ( $entity_files as $file ) {
+ $contents = file_get_contents($entity_dir . $file);
+ $matches = array();
+ preg_match_all($regexp, $contents, $matches, PREG_SET_ORDER);
+ foreach ($matches as $match) {
+ $entity_table[$match[1]] = unichr($match[2]);
+ }
+}
+
+$output = serialize($entity_table);
+
+$fh = fopen($output_file, 'w');
+fwrite($fh, $output);
+fclose($fh);
+
+echo "Completed successfully.";
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/maintenance/generate-includes.php b/vendor/ezyang/htmlpurifier/maintenance/generate-includes.php
new file mode 100644
index 000000000..01e1c2aba
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/maintenance/generate-includes.php
@@ -0,0 +1,192 @@
+#!/usr/bin/php
+<?php
+
+chdir(dirname(__FILE__));
+require_once 'common.php';
+require_once '../tests/path2class.func.php';
+require_once '../library/HTMLPurifier/Bootstrap.php';
+assertCli();
+
+/**
+ * @file
+ * Generates an include stub for users who do not want to use the autoloader.
+ * When new files are added to HTML Purifier's main codebase, this file should
+ * be called.
+ */
+
+chdir(dirname(__FILE__) . '/../library/');
+$FS = new FSTools();
+
+$exclude_dirs = array(
+ 'HTMLPurifier/Language/',
+ 'HTMLPurifier/ConfigSchema/',
+ 'HTMLPurifier/Filter/',
+ 'HTMLPurifier/Printer/',
+ /* These should be excluded, but need to have ConfigSchema support first
+
+ */
+);
+$exclude_files = array(
+ 'HTMLPurifier/Lexer/PEARSax3.php',
+ 'HTMLPurifier/Lexer/PH5P.php',
+ 'HTMLPurifier/Printer.php',
+);
+
+// Determine what files need to be included:
+echo 'Scanning for files... ';
+$raw_files = $FS->globr('.', '*.php');
+if (!$raw_files) throw new Exception('Did not find any PHP source files');
+$files = array();
+foreach ($raw_files as $file) {
+ $file = substr($file, 2); // rm leading './'
+ if (strncmp('standalone/', $file, 11) === 0) continue; // rm generated files
+ if (substr_count($file, '.') > 1) continue; // rm meta files
+ $ok = true;
+ foreach ($exclude_dirs as $dir) {
+ if (strncmp($dir, $file, strlen($dir)) === 0) {
+ $ok = false;
+ break;
+ }
+ }
+ if (!$ok) continue; // rm excluded directories
+ if (in_array($file, $exclude_files)) continue; // rm excluded files
+ $files[] = $file;
+}
+echo "done!\n";
+
+// Reorder list so that dependencies are included first:
+
+/**
+ * Returns a lookup array of dependencies for a file.
+ *
+ * @note This function expects that format $name extends $parent on one line
+ *
+ * @param string $file
+ * File to check dependencies of.
+ * @return array
+ * Lookup array of files the file is dependent on, sorted accordingly.
+ */
+function get_dependency_lookup($file)
+{
+ static $cache = array();
+ if (isset($cache[$file])) return $cache[$file];
+ if (!file_exists($file)) {
+ echo "File doesn't exist: $file\n";
+ return array();
+ }
+ $fh = fopen($file, 'r');
+ $deps = array();
+ while (!feof($fh)) {
+ $line = fgets($fh);
+ if (strncmp('class', $line, 5) === 0) {
+ // The implementation here is fragile and will break if we attempt
+ // to use interfaces. Beware!
+ $arr = explode(' extends ', trim($line, ' {'."\n\r"), 2);
+ if (count($arr) < 2) break;
+ $parent = $arr[1];
+ $dep_file = HTMLPurifier_Bootstrap::getPath($parent);
+ if (!$dep_file) break;
+ $deps[$dep_file] = true;
+ break;
+ }
+ }
+ fclose($fh);
+ foreach (array_keys($deps) as $file) {
+ // Extra dependencies must come *before* base dependencies
+ $deps = get_dependency_lookup($file) + $deps;
+ }
+ $cache[$file] = $deps;
+ return $deps;
+}
+
+/**
+ * Sorts files based on dependencies. This function is lazy and will not
+ * group files with dependencies together; it will merely ensure that a file
+ * is never included before its dependencies are.
+ *
+ * @param $files
+ * Files array to sort.
+ * @return
+ * Sorted array ($files is not modified by reference!)
+ */
+function dep_sort($files)
+{
+ $ret = array();
+ $cache = array();
+ foreach ($files as $file) {
+ if (isset($cache[$file])) continue;
+ $deps = get_dependency_lookup($file);
+ foreach (array_keys($deps) as $dep) {
+ if (!isset($cache[$dep])) {
+ $ret[] = $dep;
+ $cache[$dep] = true;
+ }
+ }
+ $cache[$file] = true;
+ $ret[] = $file;
+ }
+ return $ret;
+}
+
+$files = dep_sort($files);
+
+// Build the actual include stub:
+
+$version = trim(file_get_contents('../VERSION'));
+
+// stub
+$php = "<?php
+
+/**
+ * @file
+ * This file was auto-generated by generate-includes.php and includes all of
+ * the core files required by HTML Purifier. Use this if performance is a
+ * primary concern and you are using an opcode cache. PLEASE DO NOT EDIT THIS
+ * FILE, changes will be overwritten the next time the script is run.
+ *
+ * @version $version
+ *
+ * @warning
+ * You must *not* include any other HTML Purifier files before this file,
+ * because 'require' not 'require_once' is used.
+ *
+ * @warning
+ * This file requires that the include path contains the HTML Purifier
+ * library directory; this is not auto-set.
+ */
+
+";
+
+foreach ($files as $file) {
+ $php .= "require '$file';" . PHP_EOL;
+}
+
+echo "Writing HTMLPurifier.includes.php... ";
+file_put_contents('HTMLPurifier.includes.php', $php);
+echo "done!\n";
+
+$php = "<?php
+
+/**
+ * @file
+ * This file was auto-generated by generate-includes.php and includes all of
+ * the core files required by HTML Purifier. This is a convenience stub that
+ * includes all files using dirname(__FILE__) and require_once. PLEASE DO NOT
+ * EDIT THIS FILE, changes will be overwritten the next time the script is run.
+ *
+ * Changes to include_path are not necessary.
+ */
+
+\$__dir = dirname(__FILE__);
+
+";
+
+foreach ($files as $file) {
+ $php .= "require_once \$__dir . '/$file';" . PHP_EOL;
+}
+
+echo "Writing HTMLPurifier.safe-includes.php... ";
+file_put_contents('HTMLPurifier.safe-includes.php', $php);
+echo "done!\n";
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/maintenance/generate-ph5p-patch.php b/vendor/ezyang/htmlpurifier/maintenance/generate-ph5p-patch.php
new file mode 100644
index 000000000..c92a7d211
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/maintenance/generate-ph5p-patch.php
@@ -0,0 +1,22 @@
+<?php
+
+/**
+ * @file
+ * This file compares our version of PH5P with Jero's original version, and
+ * generates a patch of the differences. This script should be run whenever
+ * library/HTMLPurifier/Lexer/PH5P.php is modified.
+ */
+
+$orig = realpath(dirname(__FILE__) . '/PH5P.php');
+$new = realpath(dirname(__FILE__) . '/../library/HTMLPurifier/Lexer/PH5P.php');
+$newt = dirname(__FILE__) . '/PH5P.new.php'; // temporary file
+
+// minor text-processing of new file to get into same format as original
+$new_src = file_get_contents($new);
+$new_src = '<?php' . PHP_EOL . substr($new_src, strpos($new_src, 'class HTML5 {'));
+
+file_put_contents($newt, $new_src);
+shell_exec("diff -u \"$orig\" \"$newt\" > PH5P.patch");
+unlink($newt);
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/maintenance/generate-schema-cache.php b/vendor/ezyang/htmlpurifier/maintenance/generate-schema-cache.php
new file mode 100644
index 000000000..339ff12da
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/maintenance/generate-schema-cache.php
@@ -0,0 +1,45 @@
+#!/usr/bin/php
+<?php
+
+require_once dirname(__FILE__) . '/common.php';
+require_once dirname(__FILE__) . '/../library/HTMLPurifier.auto.php';
+assertCli();
+
+/**
+ * @file
+ * Generates a schema cache file, saving it to
+ * library/HTMLPurifier/ConfigSchema/schema.ser.
+ *
+ * This should be run when new configuration options are added to
+ * HTML Purifier. A cached version is available via the repository
+ * so this does not normally have to be regenerated.
+ *
+ * If you have a directory containing custom configuration schema files,
+ * you can simple add a path to that directory as a parameter to
+ * this, and they will get included.
+ */
+
+$target = dirname(__FILE__) . '/../library/HTMLPurifier/ConfigSchema/schema.ser';
+
+$builder = new HTMLPurifier_ConfigSchema_InterchangeBuilder();
+$interchange = new HTMLPurifier_ConfigSchema_Interchange();
+
+$builder->buildDir($interchange);
+
+$loader = dirname(__FILE__) . '/../config-schema.php';
+if (file_exists($loader)) include $loader;
+foreach ($_SERVER['argv'] as $i => $dir) {
+ if ($i === 0) continue;
+ $builder->buildDir($interchange, realpath($dir));
+}
+
+$interchange->validate();
+
+$schema_builder = new HTMLPurifier_ConfigSchema_Builder_ConfigSchema();
+$schema = $schema_builder->build($interchange);
+
+echo "Saving schema... ";
+file_put_contents($target, serialize($schema));
+echo "done!\n";
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/maintenance/generate-standalone.php b/vendor/ezyang/htmlpurifier/maintenance/generate-standalone.php
new file mode 100755
index 000000000..254d4d83b
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/maintenance/generate-standalone.php
@@ -0,0 +1,159 @@
+#!/usr/bin/php
+<?php
+
+chdir(dirname(__FILE__));
+require_once 'common.php';
+assertCli();
+
+/**
+ * @file
+ * Compiles all of HTML Purifier's library files into one big file
+ * named HTMLPurifier.standalone.php. This is usually called during the
+ * release process.
+ */
+
+/**
+ * Global hash that tracks already loaded includes
+ */
+$GLOBALS['loaded'] = array();
+
+/**
+ * Custom FSTools for this script that overloads some behavior
+ * @warning The overloading of copy() is not necessarily global for
+ * this script. Watch out!
+ */
+class MergeLibraryFSTools extends FSTools
+{
+ public function copyable($entry)
+ {
+ // Skip hidden files
+ if ($entry[0] == '.') {
+ return false;
+ }
+ return true;
+ }
+ public function copy($source, $dest)
+ {
+ copy_and_remove_includes($source, $dest);
+ }
+}
+$FS = new MergeLibraryFSTools();
+
+/**
+ * Replaces the includes inside PHP source code with the corresponding
+ * source.
+ * @param string $text PHP source code to replace includes from
+ */
+function replace_includes($text)
+{
+ // also remove vim modelines
+ return preg_replace_callback(
+ "/require(?:_once)? ['\"]([^'\"]+)['\"];/",
+ 'replace_includes_callback',
+ $text
+ );
+}
+
+/**
+ * Removes leading PHP tags from included files. Assumes that there is
+ * no trailing tag. Also removes vim modelines.
+ * @note This is safe for files that have internal <?php
+ * @param string $text Text to have leading PHP tag from
+ */
+function remove_php_tags($text)
+{
+ $text = preg_replace('#// vim:.+#', '', $text);
+ return substr($text, 5);
+}
+
+/**
+ * Copies the contents of a directory to the standalone directory
+ * @param string $dir Directory to copy
+ */
+function make_dir_standalone($dir)
+{
+ global $FS;
+ return $FS->copyr($dir, 'standalone/' . $dir);
+}
+
+/**
+ * Copies the contents of a file to the standalone directory
+ * @param string $file File to copy
+ */
+function make_file_standalone($file)
+{
+ global $FS;
+ $FS->mkdirr('standalone/' . dirname($file));
+ copy_and_remove_includes($file, 'standalone/' . $file);
+ return true;
+}
+
+/**
+ * Copies a file to another location recursively, if it is a PHP file
+ * remove includes
+ * @param string $file Original file
+ * @param string $sfile New location of file
+ */
+function copy_and_remove_includes($file, $sfile)
+{
+ $contents = file_get_contents($file);
+ if (strrchr($file, '.') === '.php') $contents = replace_includes($contents);
+ return file_put_contents($sfile, $contents);
+}
+
+/**
+ * @param $matches preg_replace_callback matches array, where index 1
+ * is the filename to include
+ */
+function replace_includes_callback($matches)
+{
+ $file = $matches[1];
+ $preserve = array(
+ // PEAR (external)
+ 'XML/HTMLSax3.php' => 1
+ );
+ if (isset($preserve[$file])) {
+ return $matches[0];
+ }
+ if (isset($GLOBALS['loaded'][$file])) return '';
+ $GLOBALS['loaded'][$file] = true;
+ return replace_includes(remove_php_tags(file_get_contents($file)));
+}
+
+echo 'Generating includes file... ';
+shell_exec('php generate-includes.php');
+echo "done!\n";
+
+chdir(dirname(__FILE__) . '/../library/');
+
+echo 'Creating full file...';
+$contents = replace_includes(file_get_contents('HTMLPurifier.includes.php'));
+$contents = str_replace(
+ // Note that bootstrap is now inside the standalone file
+ "define('HTMLPURIFIER_PREFIX', realpath(dirname(__FILE__) . '/..'));",
+ "define('HTMLPURIFIER_PREFIX', dirname(__FILE__) . '/standalone');
+ set_include_path(HTMLPURIFIER_PREFIX . PATH_SEPARATOR . get_include_path());",
+ $contents
+);
+file_put_contents('HTMLPurifier.standalone.php', $contents);
+echo ' done!' . PHP_EOL;
+
+echo 'Creating standalone directory...';
+$FS->rmdirr('standalone'); // ensure a clean copy
+
+// data files
+$FS->mkdirr('standalone/HTMLPurifier/DefinitionCache/Serializer');
+make_file_standalone('HTMLPurifier/EntityLookup/entities.ser');
+make_file_standalone('HTMLPurifier/ConfigSchema/schema.ser');
+
+// non-standard inclusion setup
+make_dir_standalone('HTMLPurifier/ConfigSchema');
+make_dir_standalone('HTMLPurifier/Language');
+make_dir_standalone('HTMLPurifier/Filter');
+make_dir_standalone('HTMLPurifier/Printer');
+make_file_standalone('HTMLPurifier/Printer.php');
+make_file_standalone('HTMLPurifier/Lexer/PH5P.php');
+
+echo ' done!' . PHP_EOL;
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/maintenance/merge-library.php b/vendor/ezyang/htmlpurifier/maintenance/merge-library.php
new file mode 100755
index 000000000..de2eecdc0
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/maintenance/merge-library.php
@@ -0,0 +1,11 @@
+#!/usr/bin/php
+<?php
+
+/**
+ * @file
+ * Deprecated in favor of generate-standalone.php.
+ */
+
+require dirname(__FILE__) . '/generate-standalone.php';
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/maintenance/old-extract-schema.php b/vendor/ezyang/htmlpurifier/maintenance/old-extract-schema.php
new file mode 100644
index 000000000..514a08dd9
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/maintenance/old-extract-schema.php
@@ -0,0 +1,71 @@
+#!/usr/bin/php
+<?php
+
+chdir(dirname(__FILE__));
+require_once 'common.php';
+assertCli();
+
+echo "Please do not run this script. It is here for historical purposes only.";
+exit;
+
+/**
+ * @file
+ * Extracts all definitions inside a configuration schema
+ * (HTMLPurifier_ConfigSchema) and exports them as plain text files.
+ *
+ * @todo Extract version numbers.
+ */
+
+define('HTMLPURIFIER_SCHEMA_STRICT', true); // description data needs to be collected
+require_once dirname(__FILE__) . '/../library/HTMLPurifier.auto.php';
+
+// We need includes to ensure all HTMLPurifier_ConfigSchema calls are
+// performed.
+require_once 'HTMLPurifier.includes.php';
+
+// Also, these extra files will be necessary.
+require_once 'HTMLPurifier/Filter/ExtractStyleBlocks.php';
+
+/**
+ * Takes a hash and saves its contents to library/HTMLPurifier/ConfigSchema/
+ */
+function saveHash($hash)
+{
+ if ($hash === false) return;
+ $dir = realpath(dirname(__FILE__) . '/../library/HTMLPurifier/ConfigSchema');
+ $name = $hash['ID'] . '.txt';
+ $file = $dir . '/' . $name;
+ if (file_exists($file)) {
+ trigger_error("File already exists; skipped $name");
+ return;
+ }
+ $file = new FSTools_File($file);
+ $file->open('w');
+ $multiline = false;
+ foreach ($hash as $key => $value) {
+ $multiline = $multiline || (strpos($value, "\n") !== false);
+ if ($multiline) {
+ $file->put("--$key--" . PHP_EOL);
+ $file->put(str_replace("\n", PHP_EOL, $value) . PHP_EOL);
+ } else {
+ if ($key == 'ID') {
+ $file->put("$value" . PHP_EOL);
+ } else {
+ $file->put("$key: $value" . PHP_EOL);
+ }
+ }
+ }
+ $file->close();
+}
+
+$schema = HTMLPurifier_ConfigSchema::instance();
+$adapter = new HTMLPurifier_ConfigSchema_StringHashReverseAdapter($schema);
+
+foreach ($schema->info as $ns => $ns_array) {
+ saveHash($adapter->get($ns));
+ foreach ($ns_array as $dir => $x) {
+ saveHash($adapter->get($ns, $dir));
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/maintenance/old-remove-require-once.php b/vendor/ezyang/htmlpurifier/maintenance/old-remove-require-once.php
new file mode 100644
index 000000000..f47c7d0f1
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/maintenance/old-remove-require-once.php
@@ -0,0 +1,32 @@
+#!/usr/bin/php
+<?php
+
+chdir(dirname(__FILE__));
+require_once 'common.php';
+assertCli();
+
+echo "Please do not run this script. It is here for historical purposes only.";
+exit;
+
+/**
+ * @file
+ * Removes leading includes from files.
+ *
+ * @note
+ * This does not remove inline includes; those must be handled manually.
+ */
+
+chdir(dirname(__FILE__) . '/../tests/HTMLPurifier');
+$FS = new FSTools();
+
+$files = $FS->globr('.', '*.php');
+foreach ($files as $file) {
+ if (substr_count(basename($file), '.') > 1) continue;
+ $old_code = file_get_contents($file);
+ $new_code = preg_replace("#^require_once .+[\n\r]*#m", '', $old_code);
+ if ($old_code !== $new_code) {
+ file_put_contents($file, $new_code);
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/maintenance/old-remove-schema-def.php b/vendor/ezyang/htmlpurifier/maintenance/old-remove-schema-def.php
new file mode 100644
index 000000000..5ae031973
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/maintenance/old-remove-schema-def.php
@@ -0,0 +1,32 @@
+#!/usr/bin/php
+<?php
+
+chdir(dirname(__FILE__));
+require_once 'common.php';
+assertCli();
+
+echo "Please do not run this script. It is here for historical purposes only.";
+exit;
+
+/**
+ * @file
+ * Removes ConfigSchema function calls from source files.
+ */
+
+chdir(dirname(__FILE__) . '/../library/');
+$FS = new FSTools();
+
+$files = $FS->globr('.', '*.php');
+foreach ($files as $file) {
+ if (substr_count(basename($file), '.') > 1) continue;
+ $old_code = file_get_contents($file);
+ $new_code = preg_replace("#^HTMLPurifier_ConfigSchema::.+?\);[\n\r]*#ms", '', $old_code);
+ if ($old_code !== $new_code) {
+ file_put_contents($file, $new_code);
+ }
+ if (preg_match('#^\s+HTMLPurifier_ConfigSchema::#m', $new_code)) {
+ echo "Indented ConfigSchema call in $file\n";
+ }
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/maintenance/regenerate-docs.sh b/vendor/ezyang/htmlpurifier/maintenance/regenerate-docs.sh
new file mode 100755
index 000000000..6f4d720ff
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/maintenance/regenerate-docs.sh
@@ -0,0 +1,5 @@
+#!/bin/bash -e
+./compile-doxygen.sh
+cd ../docs
+scp doxygen.tgz htmlpurifier.org:/home/ezyang/htmlpurifier.org
+ssh htmlpurifier.org "cd /home/ezyang/htmlpurifier.org && ./reload-docs.sh"
diff --git a/vendor/ezyang/htmlpurifier/maintenance/remove-trailing-whitespace.php b/vendor/ezyang/htmlpurifier/maintenance/remove-trailing-whitespace.php
new file mode 100644
index 000000000..857870546
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/maintenance/remove-trailing-whitespace.php
@@ -0,0 +1,37 @@
+#!/usr/bin/php
+<?php
+
+chdir(dirname(__FILE__));
+require_once 'common.php';
+assertCli();
+
+/**
+ * @file
+ * Removes trailing whitespace from files.
+ */
+
+chdir(dirname(__FILE__) . '/..');
+$FS = new FSTools();
+
+$files = $FS->globr('.', '{,.}*', GLOB_BRACE);
+foreach ($files as $file) {
+ if (
+ !is_file($file) ||
+ prefix_is('./.git', $file) ||
+ prefix_is('./docs/doxygen', $file) ||
+ postfix_is('.ser', $file) ||
+ postfix_is('.tgz', $file) ||
+ postfix_is('.patch', $file) ||
+ postfix_is('.dtd', $file) ||
+ postfix_is('.ent', $file) ||
+ $file == './library/HTMLPurifier/Lexer/PH5P.php' ||
+ $file == './maintenance/PH5P.php'
+ ) continue;
+ $contents = file_get_contents($file);
+ $result = preg_replace('/^(.*?)[ \t]+(\r?)$/m', '\1\2', $contents, -1, $count);
+ if (!$count) continue;
+ echo "$file\n";
+ file_put_contents($file, $result);
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/maintenance/rename-config.php b/vendor/ezyang/htmlpurifier/maintenance/rename-config.php
new file mode 100644
index 000000000..6e59e2a79
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/maintenance/rename-config.php
@@ -0,0 +1,84 @@
+#!/usr/bin/php
+<?php
+
+chdir(dirname(__FILE__));
+require_once 'common.php';
+require_once '../library/HTMLPurifier.auto.php';
+assertCli();
+
+/**
+ * @file
+ * Renames a configuration directive. This involves renaming the file,
+ * adding an alias, and then regenerating the cache. You still have to
+ * manually go through and fix any calls to the directive.
+ * @warning This script doesn't handle multi-stringhash files.
+ */
+
+$argv = $_SERVER['argv'];
+if (count($argv) < 3) {
+ echo "Usage: {$argv[0]} OldName NewName\n";
+ exit(1);
+}
+
+chdir('../library/HTMLPurifier/ConfigSchema/schema');
+
+$old = $argv[1];
+$new = $argv[2];
+
+if (!file_exists("$old.txt")) {
+ echo "Cannot move undefined configuration directive $old\n";
+ exit(1);
+}
+
+if ($old === $new) {
+ echo "Attempting to move to self, aborting\n";
+ exit(1);
+}
+
+if (file_exists("$new.txt")) {
+ echo "Cannot move to already defined directive $new\n";
+ exit(1);
+}
+
+$file = "$old.txt";
+$builder = new HTMLPurifier_ConfigSchema_InterchangeBuilder();
+$interchange = new HTMLPurifier_ConfigSchema_Interchange();
+$builder->buildFile($interchange, $file);
+$contents = file_get_contents($file);
+
+if (strpos($contents, "\r\n") !== false) {
+ $nl = "\r\n";
+} elseif (strpos($contents, "\r") !== false) {
+ $nl = "\r";
+} else {
+ $nl = "\n";
+}
+
+// replace name with new name
+$contents = str_replace($old, $new, $contents);
+
+if ($interchange->directives[$old]->aliases) {
+ $pos_alias = strpos($contents, 'ALIASES:');
+ $pos_ins = strpos($contents, $nl, $pos_alias);
+ if ($pos_ins === false) $pos_ins = strlen($contents);
+ $contents =
+ substr($contents, 0, $pos_ins) . ", $old" . substr($contents, $pos_ins);
+ file_put_contents($file, $contents);
+} else {
+ $lines = explode($nl, $contents);
+ $insert = false;
+ foreach ($lines as $n => $line) {
+ if (strncmp($line, '--', 2) === 0) {
+ $insert = $n;
+ break;
+ }
+ }
+ if (!$insert) {
+ $lines[] = "ALIASES: $old";
+ } else {
+ array_splice($lines, $insert, 0, "ALIASES: $old");
+ }
+ file_put_contents($file, implode($nl, $lines));
+}
+
+rename("$old.txt", "$new.txt") || exit(1);
diff --git a/vendor/ezyang/htmlpurifier/maintenance/update-config.php b/vendor/ezyang/htmlpurifier/maintenance/update-config.php
new file mode 100644
index 000000000..2d8a7a9c1
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/maintenance/update-config.php
@@ -0,0 +1,34 @@
+#!/usr/bin/php
+<?php
+
+chdir(dirname(__FILE__));
+require_once 'common.php';
+assertCli();
+
+/**
+ * @file
+ * Converts all instances of $config->set and $config->get to the new
+ * format, as described by docs/dev-config-bcbreaks.txt
+ */
+
+$FS = new FSTools();
+chdir(dirname(__FILE__) . '/..');
+$raw_files = $FS->globr('.', '*.php');
+foreach ($raw_files as $file) {
+ $file = substr($file, 2); // rm leading './'
+ if (strpos($file, 'library/standalone/') === 0) continue;
+ if (strpos($file, 'maintenance/update-config.php') === 0) continue;
+ if (strpos($file, 'test-settings.php') === 0) continue;
+ if (substr_count($file, '.') > 1) continue; // rm meta files
+ // process the file
+ $contents = file_get_contents($file);
+ $contents = preg_replace(
+ "#config->(set|get)\('(.+?)', '(.+?)'#",
+ "config->\\1('\\2.\\3'",
+ $contents
+ );
+ if ($contents === '') continue;
+ file_put_contents($file, $contents);
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/package.php b/vendor/ezyang/htmlpurifier/package.php
new file mode 100644
index 000000000..bfef93622
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/package.php
@@ -0,0 +1,61 @@
+<?php
+
+set_time_limit(0);
+
+require_once 'PEAR/PackageFileManager2.php';
+require_once 'PEAR/PackageFileManager/File.php';
+PEAR::setErrorHandling(PEAR_ERROR_PRINT);
+$pkg = new PEAR_PackageFileManager2;
+
+$pkg->setOptions(
+ array(
+ 'baseinstalldir' => '/',
+ 'packagefile' => 'package.xml',
+ 'packagedirectory' => realpath(dirname(__FILE__) . '/library'),
+ 'filelistgenerator' => 'file',
+ 'include' => array('*'),
+ 'dir_roles' => array('/' => 'php'), // hack to put *.ser files in the right place
+ 'ignore' => array(
+ 'HTMLPurifier.standalone.php',
+ 'HTMLPurifier.path.php',
+ '*.tar.gz',
+ '*.tgz',
+ 'standalone/'
+ ),
+ )
+);
+
+$pkg->setPackage('HTMLPurifier');
+$pkg->setLicense('LGPL', 'http://www.gnu.org/licenses/lgpl.html');
+$pkg->setSummary('Standards-compliant HTML filter');
+$pkg->setDescription(
+ 'HTML Purifier is an HTML filter that will remove all malicious code
+ (better known as XSS) with a thoroughly audited, secure yet permissive
+ whitelist and will also make sure your documents are standards
+ compliant.'
+);
+
+$pkg->addMaintainer('lead', 'ezyang', 'Edward Z. Yang', 'admin@htmlpurifier.org', 'yes');
+
+$version = trim(file_get_contents('VERSION'));
+$api_version = substr($version, 0, strrpos($version, '.'));
+
+$pkg->setChannel('htmlpurifier.org');
+$pkg->setAPIVersion($api_version);
+$pkg->setAPIStability('stable');
+$pkg->setReleaseVersion($version);
+$pkg->setReleaseStability('stable');
+
+$pkg->addRelease();
+
+$pkg->setNotes(file_get_contents('WHATSNEW'));
+$pkg->setPackageType('php');
+
+$pkg->setPhpDep('5.0.0');
+$pkg->setPearinstallerDep('1.4.3');
+
+$pkg->generateContents();
+
+$pkg->writePackageFile();
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/phpdoc.ini b/vendor/ezyang/htmlpurifier/phpdoc.ini
new file mode 100644
index 000000000..c4c372353
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/phpdoc.ini
@@ -0,0 +1,102 @@
+;; phpDocumentor parse configuration file
+;;
+;; This file is designed to cut down on repetitive typing on the command-line or web interface
+;; You can copy this file to create a number of configuration files that can be used with the
+;; command-line switch -c, as in phpdoc -c default.ini or phpdoc -c myini.ini. The web
+;; interface will automatically generate a list of .ini files that can be used.
+;;
+;; default.ini is used to generate the online manual at http://www.phpdoc.org/docs
+;;
+;; ALL .ini files must be in the user subdirectory of phpDocumentor with an extension of .ini
+;;
+;; Copyright 2002, Greg Beaver <cellog@users.sourceforge.net>
+;;
+;; WARNING: do not change the name of any command-line parameters, phpDocumentor will ignore them
+
+[Parse Data]
+;; title of all the documentation
+;; legal values: any string
+title = HTML Purifier API Documentation
+
+;; parse files that start with a . like .bash_profile
+;; legal values: true, false
+hidden = false
+
+;; show elements marked @access private in documentation by setting this to on
+;; legal values: on, off
+parseprivate = off
+
+;; parse with javadoc-like description (first sentence is always the short description)
+;; legal values: on, off
+javadocdesc = on
+
+;; add any custom @tags separated by commas here
+;; legal values: any legal tagname separated by commas.
+;customtags = mytag1,mytag2
+
+;; This is only used by the XML:DocBook/peardoc2 converter
+defaultcategoryname = Documentation
+
+;; what is the main package?
+;; legal values: alphanumeric string plus - and _
+defaultpackagename = HTMLPurifier
+
+;; output any parsing information? set to on for cron jobs
+;; legal values: on
+;quiet = on
+
+;; parse a PEAR-style repository. Do not turn this on if your project does
+;; not have a parent directory named "pear"
+;; legal values: on/off
+;pear = on
+
+;; where should the documentation be written?
+;; legal values: a legal path
+target = docs/phpdoc
+
+;; Which files should be parsed out as special documentation files, such as README,
+;; INSTALL and CHANGELOG? This overrides the default files found in
+;; phpDocumentor.ini (this file is not a user .ini file, but the global file)
+readmeinstallchangelog = README, INSTALL, NEWS, WYSIWYG, SLOW, LICENSE, CREDITS
+
+;; limit output to the specified packages, even if others are parsed
+;; legal values: package names separated by commas
+;packageoutput = package1,package2
+
+;; comma-separated list of files to parse
+;; legal values: paths separated by commas
+;filename = /path/to/file1,/path/to/file2,fileincurrentdirectory
+
+;; comma-separated list of directories to parse
+;; legal values: directory paths separated by commas
+;directory = /path1,/path2,.,..,subdirectory
+;directory = /home/jeichorn/cvs/pear
+directory = .
+
+;; template base directory (the equivalent directory of <installdir>/phpDocumentor)
+;templatebase = /path/to/my/templates
+
+;; directory to find any example files in through @example and {@example} tags
+;examplesdir = /path/to/my/templates
+
+;; comma-separated list of files, directories or wildcards ? and * (any wildcard) to ignore
+;; legal values: any wildcard strings separated by commas
+;ignore = /path/to/ignore*,*list.php,myfile.php,subdirectory/
+ignore = *tests*,*benchmarks*,*docs*,*test-settings.php,*configdoc*,*maintenance*,*smoketests*,*standalone*,*.svn*,*conf*
+
+sourcecode = on
+
+;; comma-separated list of Converters to use in outputformat:Convertername:templatedirectory format
+;; legal values: HTML:frames:default,HTML:frames:l0l33t,HTML:frames:phpdoc.de,HTML:frames:phphtmllib,
+;; HTML:frames:earthli,
+;; HTML:frames:DOM/default,HTML:frames:DOM/l0l33t,HTML:frames:DOM/phpdoc.de,
+;; HTML:frames:DOM/phphtmllib,HTML:frames:DOM/earthli
+;; HTML:Smarty:default,HTML:Smarty:PHP,HTML:Smarty:HandS
+;; PDF:default:default,CHM:default:default,XML:DocBook/peardoc2:default
+output=HTML:frames:default
+
+;; turn this option on if you want highlighted source code for every file
+;; legal values: on/off
+sourcecode = on
+
+; vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/plugins/modx.txt b/vendor/ezyang/htmlpurifier/plugins/modx.txt
new file mode 100644
index 000000000..0763821b5
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/plugins/modx.txt
@@ -0,0 +1,112 @@
+
+MODx Plugin
+
+MODx <http://www.modxcms.com/> is an open source PHP application framework.
+I first came across them in my referrer logs when tillda asked if anyone
+could implement an HTML Purifier plugin. This forum thread
+<http://modxcms.com/forums/index.php/topic,6604.0.html> eventually resulted
+in the fruition of this plugin that davidm says, "is on top of my favorite
+list." HTML Purifier goes great with WYSIWYG editors!
+
+
+
+1. Credits
+
+PaulGregory wrote the overall structure of the code. I added the
+slashes hack.
+
+
+
+2. Install
+
+First, you need to place HTML Purifier library somewhere. The code here
+assumes that you've placed in MODx's assets/plugins/htmlpurifier (no version
+number).
+
+Log into the manager, and navigate:
+
+Resources > Manage Resources > Plugins tab > New Plugin
+
+Type in a name (probably HTML Purifier), and copy paste this code into the
+textarea:
+
+--------------------------------------------------------------------------------
+$e = &$modx->Event;
+if ($e->name == 'OnBeforeDocFormSave') {
+ global $content;
+
+ include_once '../assets/plugins/htmlpurifier/library/HTMLPurifier.auto.php';
+ $purifier = new HTMLPurifier();
+
+ static $magic_quotes = null;
+ if ($magic_quotes === null) {
+ // this is an ugly hack because this hook hasn't
+ // had the backslashes removed yet when magic_quotes_gpc is on,
+ // but HTMLPurifier must not have the quotes slashed.
+ $magic_quotes = get_magic_quotes_gpc();
+ }
+
+ if ($magic_quotes) $content = stripslashes($content);
+ $content = $purifier->purify($content);
+ if ($magic_quotes) $content = addslashes($content);
+}
+--------------------------------------------------------------------------------
+
+Then navigate to the System Events tab and check "OnBeforeDocFormSave".
+Save the plugin. HTML Purifier now is integrated!
+
+
+
+3. Making sure it works
+
+You can test HTML Purifier by deliberately putting in crappy HTML and seeing
+whether or not it gets fixed. A better way is to put in something like this:
+
+<p lang="fr">Il est bon</p>
+
+...and seeing whether or not the content comes out as:
+
+<p lang="fr" xml:lang="fr">Il est bon</p>
+
+(lang to xml:lang synchronization is one of the many features HTML Purifier
+has).
+
+
+
+4. Caveat Emptor
+
+This code does not intercept save requests from the QuickEdit plugin, this may
+be added in a later version. It also modifies things on save, so there's a
+slight chance that HTML Purifier may make a boo-boo and accidently mess things
+up (the original version is not saved).
+
+Finally, make sure that MODx is using UTF-8. If you are using, say, a French
+localisation, you may be using Latin-1, if that's the case, configure
+HTML Purifier properly like this:
+
+$config = HTMLPurifier_Config::createDefault();
+$config->set('Core', 'Encoding', 'ISO-8859-1'); // or whatever encoding
+$purifier = new HTMLPurifier($config);
+
+
+
+5. Known Bugs
+
+'rn' characters sometimes mysteriously appear after purification. We are
+currently investigating this issue. See: <http://htmlpurifier.org/phorum/read.php?3,1866>
+
+
+
+6. See Also
+
+A modified version of Jot 1.1.3 is available, which integrates with HTML
+Purifier. You can check it out here: <http://modxcms.com/forums/index.php/topic,25621.msg161970.html>
+
+
+X. Changelog
+
+2008-06-16
+- Updated code to work with 3.1.0 and later
+- Add Known Bugs and See Also section
+
+ vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/plugins/phorum/.gitignore b/vendor/ezyang/htmlpurifier/plugins/phorum/.gitignore
new file mode 100644
index 000000000..8325e0902
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/plugins/phorum/.gitignore
@@ -0,0 +1,2 @@
+migrate.php
+htmlpurifier/*
diff --git a/vendor/ezyang/htmlpurifier/plugins/phorum/Changelog b/vendor/ezyang/htmlpurifier/plugins/phorum/Changelog
new file mode 100644
index 000000000..9f939e54a
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/plugins/phorum/Changelog
@@ -0,0 +1,27 @@
+Changelog HTMLPurifier : Phorum Mod
+|||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
+
+= KEY ====================
+ # Breaks back-compat
+ ! Feature
+ - Bugfix
+ + Sub-comment
+ . Internal change
+==========================
+
+Version 4.0.0 for Phorum 5.2, released July 9, 2009
+# Works only with HTML Purifier 4.0.0
+! Better installation documentation
+- Fixed double encoded quotes
+- Fixed fatal error when migrate.php is blank
+
+Version 3.0.0 for Phorum 5.2, released January 12, 2008
+# WYSIWYG and suppress_message options are now configurable via web
+ interface.
+- Module now compatible with Phorum 5.2, primary bugs were in migration
+ code as well as signature and edit message handling. This module is NOT
+ compatible with Phorum 5.1.
+- Buggy WYSIWYG mode refined
+. AutoFormatParam added to list of default configuration namespaces
+
+ vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/plugins/phorum/INSTALL b/vendor/ezyang/htmlpurifier/plugins/phorum/INSTALL
new file mode 100644
index 000000000..23c76fc5c
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/plugins/phorum/INSTALL
@@ -0,0 +1,84 @@
+
+Install
+ How to install the Phorum HTML Purifier plugin
+
+0. PREREQUISITES
+----------------
+This Phorum module only works on PHP5 and with HTML Purifier 4.0.0
+or later.
+
+1. UNZIP
+--------
+Unzip phorum-htmlpurifier-x.y.z, producing an htmlpurifier folder.
+You've already done this step if you're reading this!
+
+2. MOVE
+-------
+Move the htmlpurifier folder to the mods/ folder of your Phorum
+installation, so the directory structure looks like:
+
+phorum/
+ mods/
+ htmlpurifier/
+ INSTALL - this install file
+ info.txt, ... - the module files
+ htmlpurifier/
+
+3. INSTALL HTML PURIFIER
+------------------------
+Download and unzip HTML Purifier <htmlpurifier.org>. Place the contents of
+the library/ folder in the htmlpurifier/htmlpurifier folder. Your directory
+structure will look like:
+
+phorum/
+ mods/
+ htmlpurifier/
+ htmlpurifier/
+ HTMLPurifier.auto.php
+ ... - other files
+ HTMLPurifier/
+
+Advanced users:
+ If you have HTML Purifier installed elsewhere on your server,
+ all you need is an HTMLPurifier.auto.php file in the library folder which
+ includes the HTMLPurifier.auto.php file in your install.
+
+4. MIGRATE
+----------
+If you're setting up a new Phorum installation, all you need to do is create
+a blank migrate.php file in the htmlpurifier module folder (NOT the library
+folder.
+
+If you have an old Phorum installation and was using BBCode,
+copy migrate.bbcode.php to migrate.php. If you were using a different input
+format, follow the instructions in migrate.bbcode.php to create your own custom
+migrate.php file.
+
+Your directory structure should now look like this:
+
+phorum/
+ mods/
+ htmlpurifier/
+ migrate.php
+
+5. ENABLE
+---------
+Navigate to your Phorum admin panel at http://example.com/phorum/admin.php,
+click on Global Settings > Modules, scroll to "HTML Purifier Phorum Mod" and
+turn it On.
+
+6. MIGRATE SIGNATURES
+---------------------
+If you're setting up a new Phorum installation, skip this step.
+
+If you allowed your users to make signatures, navigate to the module settings
+page of HTML Purifier (Global Settings > Modules > HTML Purifier Phorum Mod >
+Configure), type in "yes" in the "Confirm" box, and press "Migrate."
+
+ONLY DO THIS ONCE! BE SURE TO BACK UP YOUR DATABASE!
+
+7. CONFIGURE
+------------
+Configure using Edit settings. See that page for more information.
+
+ vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/plugins/phorum/README b/vendor/ezyang/htmlpurifier/plugins/phorum/README
new file mode 100644
index 000000000..0524ed39d
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/plugins/phorum/README
@@ -0,0 +1,45 @@
+
+HTML Purifier Phorum Mod - Filter your HTML the Standards-Compliant Way!
+
+This Phorum mod enables HTML posting on Phorum. Under normal circumstances,
+this would cause a huge security risk, but because we are running
+HTML through HTML Purifier, output is guaranteed to be XSS free and
+standards-compliant.
+
+This mod requires HTML input, and previous markup languages need to be
+converted accordingly. Thus, it is vital that you create a 'migrate.php'
+file that works with your installation. If you're using the built-in
+BBCode formatting, simply move migrate.bbcode.php to that place; for
+other markup languages, consult said file for instructions on how
+to adapt it to your needs.
+
+ -- NOTE -------------------------------------------------
+ You can also run this module in parallel with another
+ formatting module; this module attempts to place itself
+ at the end of the filtering chain. However, if any
+ previous modules produce insecure HTML (for instance,
+ a JavaScript email obfuscator) they will get cleaned.
+
+This module will not work if 'migrate.php' is not created, and an improperly
+made migration file may *CORRUPT* Phorum, so please take your time to
+do this correctly. It should go without saying to *BACKUP YOUR DATABASE*
+before attempting anything here. If no migration is necessary, you can
+simply create a blank migrate.php file. HTML Purifier is smart and will
+not re-migrate already processed messages. However, the original code
+is irretrievably lost (we may change this in the future.)
+
+This module will not automatically migrate user signatures, because this
+process may take a long time. After installing the HTML Purifier module and
+then configuring 'migrate.php', navigate to Settings and click 'Migrate
+Signatures' to migrate all user signatures to HTML.
+
+All of HTML Purifier's usual functions are configurable via the mod settings
+page. If you require custom configuration, create config.php file in
+the mod directory that edits a $config variable. Be sure, also, to
+set $PHORUM['mod_htmlpurifier']['wysiwyg'] to TRUE if you are using a
+WYSIWYG editor (you can do this through a common hook or the web
+configuration form).
+
+Visit HTML Purifier at <http://htmlpurifier.org/>.
+
+ vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/plugins/phorum/config.default.php b/vendor/ezyang/htmlpurifier/plugins/phorum/config.default.php
new file mode 100644
index 000000000..e047c0b42
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/plugins/phorum/config.default.php
@@ -0,0 +1,57 @@
+<?php
+
+if(!defined("PHORUM")) exit;
+
+// default HTML Purifier configuration settings
+$config->set('HTML.Allowed',
+ // alphabetically sorted
+'a[href|title]
+abbr[title]
+acronym[title]
+b
+blockquote[cite]
+br
+caption
+cite
+code
+dd
+del
+dfn
+div
+dl
+dt
+em
+i
+img[src|alt|title|class]
+ins
+kbd
+li
+ol
+p
+pre
+s
+strike
+strong
+sub
+sup
+table
+tbody
+td
+tfoot
+th
+thead
+tr
+tt
+u
+ul
+var');
+$config->set('AutoFormat.AutoParagraph', true);
+$config->set('AutoFormat.Linkify', true);
+$config->set('HTML.Doctype', 'XHTML 1.0 Transitional');
+$config->set('Core.AggressivelyFixLt', true);
+$config->set('Core.Encoding', $GLOBALS['PHORUM']['DATA']['CHARSET']); // we'll change this eventually
+if (strtolower($GLOBALS['PHORUM']['DATA']['CHARSET']) !== 'utf-8') {
+ $config->set('Core.EscapeNonASCIICharacters', true);
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/plugins/phorum/htmlpurifier.php b/vendor/ezyang/htmlpurifier/plugins/phorum/htmlpurifier.php
new file mode 100644
index 000000000..f66d8c36c
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/plugins/phorum/htmlpurifier.php
@@ -0,0 +1,316 @@
+<?php
+
+/**
+ * HTML Purifier Phorum Mod. Filter your HTML the Standards-Compliant Way!
+ *
+ * This Phorum mod enables users to post raw HTML into Phorum. But never
+ * fear: with the help of HTML Purifier, this HTML will be beat into
+ * de-XSSed and standards-compliant form, safe for general consumption.
+ * It is not recommended, but possible to run this mod in parallel
+ * with other formatters (in short, please DISABLE the BBcode mod).
+ *
+ * For help migrating from your previous markup language to pure HTML
+ * please check the migrate.bbcode.php file.
+ *
+ * If you'd like to use this with a WYSIWYG editor, make sure that
+ * editor sets $PHORUM['mod_htmlpurifier']['wysiwyg'] to true. Otherwise,
+ * administrators who need to edit other people's comments may be at
+ * risk for some nasty attacks.
+ *
+ * Tested with Phorum 5.2.11.
+ */
+
+// Note: Cache data is base64 encoded because Phorum insists on flinging
+// to the user and expecting it to come back unharmed, newlines and
+// all, which ain't happening. It's slower, it takes up more space, but
+// at least it won't get mutilated
+
+/**
+ * Purifies a data array
+ */
+function phorum_htmlpurifier_format($data)
+{
+ $PHORUM = $GLOBALS["PHORUM"];
+
+ $purifier =& HTMLPurifier::getInstance();
+ $cache_serial = $PHORUM['mod_htmlpurifier']['body_cache_serial'];
+
+ foreach($data as $message_id => $message){
+ if(isset($message['body'])) {
+
+ if ($message_id) {
+ // we're dealing with a real message, not a fake, so
+ // there a number of shortcuts that can be taken
+
+ if (isset($message['meta']['htmlpurifier_light'])) {
+ // format hook was called outside of Phorum's normal
+ // functions, do the abridged purification
+ $data[$message_id]['body'] = $purifier->purify($message['body']);
+ continue;
+ }
+
+ if (!empty($PHORUM['args']['purge'])) {
+ // purge the cache, must be below the following if
+ unset($message['meta']['body_cache']);
+ }
+
+ if (
+ isset($message['meta']['body_cache']) &&
+ isset($message['meta']['body_cache_serial']) &&
+ $message['meta']['body_cache_serial'] == $cache_serial
+ ) {
+ // cached version is present, bail out early
+ $data[$message_id]['body'] = base64_decode($message['meta']['body_cache']);
+ continue;
+ }
+ }
+
+ // migration might edit this array, that's why it's defined
+ // so early
+ $updated_message = array();
+
+ // create the $body variable
+ if (
+ $message_id && // message must be real to migrate
+ !isset($message['meta']['body_cache_serial'])
+ ) {
+ // perform migration
+ $fake_data = array();
+ list($signature, $edit_message) = phorum_htmlpurifier_remove_sig_and_editmessage($message);
+ $fake_data[$message_id] = $message;
+ $fake_data = phorum_htmlpurifier_migrate($fake_data);
+ $body = $fake_data[$message_id]['body'];
+ $body = str_replace("<phorum break>\n", "\n", $body);
+ $updated_message['body'] = $body; // save it in
+ $body .= $signature . $edit_message; // add it back in
+ } else {
+ // reverse Phorum's pre-processing
+ $body = $message['body'];
+ // order is important
+ $body = str_replace("<phorum break>\n", "\n", $body);
+ $body = str_replace(array('&lt;','&gt;','&amp;', '&quot;'), array('<','>','&','"'), $body);
+ if (!$message_id && defined('PHORUM_CONTROL_CENTER')) {
+ // we're in control.php, so it was double-escaped
+ $body = str_replace(array('&lt;','&gt;','&amp;', '&quot;'), array('<','>','&','"'), $body);
+ }
+ }
+
+ $body = $purifier->purify($body);
+
+ // dynamically update the cache (MUST BE DONE HERE!)
+ // this is inefficient because it's one db call per
+ // cache miss, but once the cache is in place things are
+ // a lot zippier.
+
+ if ($message_id) { // make sure it's not a fake id
+ $updated_message['meta'] = $message['meta'];
+ $updated_message['meta']['body_cache'] = base64_encode($body);
+ $updated_message['meta']['body_cache_serial'] = $cache_serial;
+ phorum_db_update_message($message_id, $updated_message);
+ }
+
+ // must not get overloaded until after we cache it, otherwise
+ // we'll inadvertently change the original text
+ $data[$message_id]['body'] = $body;
+
+ }
+ }
+
+ return $data;
+}
+
+// -----------------------------------------------------------------------
+// This is fragile code, copied from read.php:596 (Phorum 5.2.6). Please
+// keep this code in-sync with Phorum
+
+/**
+ * Generates a signature based on a message array
+ */
+function phorum_htmlpurifier_generate_sig($row)
+{
+ $phorum_sig = '';
+ if(isset($row["user"]["signature"])
+ && isset($row['meta']['show_signature']) && $row['meta']['show_signature']==1){
+ $phorum_sig=trim($row["user"]["signature"]);
+ if(!empty($phorum_sig)){
+ $phorum_sig="\n\n$phorum_sig";
+ }
+ }
+ return $phorum_sig;
+}
+
+/**
+ * Generates an edit message based on a message array
+ */
+function phorum_htmlpurifier_generate_editmessage($row)
+{
+ $PHORUM = $GLOBALS['PHORUM'];
+ $editmessage = '';
+ if(isset($row['meta']['edit_count']) && $row['meta']['edit_count'] > 0) {
+ $editmessage = str_replace ("%count%", $row['meta']['edit_count'], $PHORUM["DATA"]["LANG"]["EditedMessage"]);
+ $editmessage = str_replace ("%lastedit%", phorum_date($PHORUM["short_date_time"],$row['meta']['edit_date']), $editmessage);
+ $editmessage = str_replace ("%lastuser%", $row['meta']['edit_username'], $editmessage);
+ $editmessage = "\n\n\n\n$editmessage";
+ }
+ return $editmessage;
+}
+
+// End fragile code
+// -----------------------------------------------------------------------
+
+/**
+ * Removes the signature and edit message from a message
+ * @param $row Message passed by reference
+ */
+function phorum_htmlpurifier_remove_sig_and_editmessage(&$row)
+{
+ $signature = phorum_htmlpurifier_generate_sig($row);
+ $editmessage = phorum_htmlpurifier_generate_editmessage($row);
+ $replacements = array();
+ // we need to remove add <phorum break> as that is the form these
+ // extra bits are in.
+ if ($signature) $replacements[str_replace("\n", "<phorum break>\n", $signature)] = '';
+ if ($editmessage) $replacements[str_replace("\n", "<phorum break>\n", $editmessage)] = '';
+ $row['body'] = strtr($row['body'], $replacements);
+ return array($signature, $editmessage);
+}
+
+/**
+ * Indicate that data is fully HTML and not from migration, invalidate
+ * previous caches
+ * @note This function could generate the actual cache entries, but
+ * since there's data missing that must be deferred to the first read
+ */
+function phorum_htmlpurifier_posting($message)
+{
+ $PHORUM = $GLOBALS["PHORUM"];
+ unset($message['meta']['body_cache']); // invalidate the cache
+ $message['meta']['body_cache_serial'] = $PHORUM['mod_htmlpurifier']['body_cache_serial'];
+ return $message;
+}
+
+/**
+ * Overload quoting mechanism to prevent default, mail-style quote from happening
+ */
+function phorum_htmlpurifier_quote($array)
+{
+ $PHORUM = $GLOBALS["PHORUM"];
+ $purifier =& HTMLPurifier::getInstance();
+ $text = $purifier->purify($array[1]);
+ $source = htmlspecialchars($array[0]);
+ return "<blockquote cite=\"$source\">\n$text\n</blockquote>";
+}
+
+/**
+ * Ensure that our format hook is processed last. Also, loads the library.
+ * @credits <http://secretsauce.phorum.org/snippets/make_bbcode_last_formatter.php.txt>
+ */
+function phorum_htmlpurifier_common()
+{
+ require_once(dirname(__FILE__).'/htmlpurifier/HTMLPurifier.auto.php');
+ require(dirname(__FILE__).'/init-config.php');
+
+ $config = phorum_htmlpurifier_get_config();
+ HTMLPurifier::getInstance($config);
+
+ // increment revision.txt if you want to invalidate the cache
+ $GLOBALS['PHORUM']['mod_htmlpurifier']['body_cache_serial'] = $config->getSerial();
+
+ // load migration
+ if (file_exists(dirname(__FILE__) . '/migrate.php')) {
+ include(dirname(__FILE__) . '/migrate.php');
+ } else {
+ echo '<strong>Error:</strong> No migration path specified for HTML Purifier, please check
+ <tt>modes/htmlpurifier/migrate.bbcode.php</tt> for instructions on
+ how to migrate from your previous markup language.';
+ exit;
+ }
+
+ if (!function_exists('phorum_htmlpurifier_migrate')) {
+ // Dummy function
+ function phorum_htmlpurifier_migrate($data) {return $data;}
+ }
+
+}
+
+/**
+ * Pre-emptively performs purification if it looks like a WYSIWYG editor
+ * is being used
+ */
+function phorum_htmlpurifier_before_editor($message)
+{
+ if (!empty($GLOBALS['PHORUM']['mod_htmlpurifier']['wysiwyg'])) {
+ if (!empty($message['body'])) {
+ $body = $message['body'];
+ // de-entity-ize contents
+ $body = str_replace(array('&lt;','&gt;','&amp;'), array('<','>','&'), $body);
+ $purifier =& HTMLPurifier::getInstance();
+ $body = $purifier->purify($body);
+ // re-entity-ize contents
+ $body = htmlspecialchars($body, ENT_QUOTES, $GLOBALS['PHORUM']['DATA']['CHARSET']);
+ $message['body'] = $body;
+ }
+ }
+ return $message;
+}
+
+function phorum_htmlpurifier_editor_after_subject()
+{
+ // don't show this message if it's a WYSIWYG editor, since it will
+ // then be handled automatically
+ if (!empty($GLOBALS['PHORUM']['mod_htmlpurifier']['wysiwyg'])) {
+ $i = $GLOBALS['PHORUM']['DATA']['MODE'];
+ if ($i == 'quote' || $i == 'edit' || $i == 'moderation') {
+ ?>
+ <div>
+ <p>
+ <strong>Notice:</strong> HTML has been scrubbed for your safety.
+ If you would like to see the original, turn off WYSIWYG mode
+ (consult your administrator for details.)
+ </p>
+ </div>
+ <?php
+ }
+ return;
+ }
+ if (!empty($GLOBALS['PHORUM']['mod_htmlpurifier']['suppress_message'])) return;
+ ?><div class="htmlpurifier-help">
+ <p>
+ <strong>HTML input</strong> is enabled. Make sure you escape all HTML and
+ angled brackets with <code>&amp;lt;</code> and <code>&amp;gt;</code>.
+ </p><?php
+ $purifier =& HTMLPurifier::getInstance();
+ $config = $purifier->config;
+ if ($config->get('AutoFormat.AutoParagraph')) {
+ ?><p>
+ <strong>Auto-paragraphing</strong> is enabled. Double
+ newlines will be converted to paragraphs; for single
+ newlines, use the <code>pre</code> tag.
+ </p><?php
+ }
+ $html_definition = $config->getDefinition('HTML');
+ $allowed = array();
+ foreach ($html_definition->info as $name => $x) $allowed[] = "<code>$name</code>";
+ sort($allowed);
+ $allowed_text = implode(', ', $allowed);
+ ?><p><strong>Allowed tags:</strong> <?php
+ echo $allowed_text;
+ ?>.</p><?php
+ ?>
+ </p>
+ <p>
+ For inputting literal code such as HTML and PHP for display, use
+ CDATA tags to auto-escape your angled brackets, and <code>pre</code>
+ to preserve newlines:
+ </p>
+ <pre>&lt;pre&gt;&lt;![CDATA[
+<em>Place code here</em>
+]]&gt;&lt;/pre&gt;</pre>
+ <p>
+ Power users, you can hide this notice with:
+ <pre>.htmlpurifier-help {display:none;}</pre>
+ </p>
+ </div><?php
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/plugins/phorum/info.txt b/vendor/ezyang/htmlpurifier/plugins/phorum/info.txt
new file mode 100644
index 000000000..723465490
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/plugins/phorum/info.txt
@@ -0,0 +1,18 @@
+title: HTML Purifier Phorum Mod
+desc: This module enables standards-compliant HTML filtering on Phorum. Please check migrate.bbcode.php before enabling this mod.
+author: Edward Z. Yang
+url: http://htmlpurifier.org/
+version: 4.0.0
+
+hook: format|phorum_htmlpurifier_format
+hook: quote|phorum_htmlpurifier_quote
+hook: posting_custom_action|phorum_htmlpurifier_posting
+hook: common|phorum_htmlpurifier_common
+hook: before_editor|phorum_htmlpurifier_before_editor
+hook: tpl_editor_after_subject|phorum_htmlpurifier_editor_after_subject
+
+# This module is meant to be a drop-in for bbcode, so make it run last.
+priority: run module after *
+priority: run hook format after *
+
+ vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/plugins/phorum/init-config.php b/vendor/ezyang/htmlpurifier/plugins/phorum/init-config.php
new file mode 100644
index 000000000..e19787b4b
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/plugins/phorum/init-config.php
@@ -0,0 +1,30 @@
+<?php
+
+/**
+ * Initializes the appropriate configuration from either a PHP file
+ * or a module configuration value
+ * @return Instance of HTMLPurifier_Config
+ */
+function phorum_htmlpurifier_get_config($default = false)
+{
+ global $PHORUM;
+ $config_exists = phorum_htmlpurifier_config_file_exists();
+ if ($default || $config_exists || !isset($PHORUM['mod_htmlpurifier']['config'])) {
+ $config = HTMLPurifier_Config::createDefault();
+ include(dirname(__FILE__) . '/config.default.php');
+ if ($config_exists) {
+ include(dirname(__FILE__) . '/config.php');
+ }
+ unset($PHORUM['mod_htmlpurifier']['config']); // unnecessary
+ } else {
+ $config = HTMLPurifier_Config::create($PHORUM['mod_htmlpurifier']['config']);
+ }
+ return $config;
+}
+
+function phorum_htmlpurifier_config_file_exists()
+{
+ return file_exists(dirname(__FILE__) . '/config.php');
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/plugins/phorum/migrate.bbcode.php b/vendor/ezyang/htmlpurifier/plugins/phorum/migrate.bbcode.php
new file mode 100644
index 000000000..0d0919455
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/plugins/phorum/migrate.bbcode.php
@@ -0,0 +1,31 @@
+<?php
+
+/**
+ * This file is responsible for migrating from a specific markup language
+ * like BBCode or Markdown to HTML. WARNING: THIS PROCESS IS NOT REVERSIBLE
+ *
+ * Copy this file to 'migrate.php' and it will automatically work for
+ * BBCode; you may need to tweak this a little to get it to work for other
+ * languages (usually, just replace the include name and the function name).
+ *
+ * If you do NOT want to have any migration performed (for instance, you
+ * are installing the module on a new forum with no posts), simply remove
+ * phorum_htmlpurifier_migrate() function. You still need migrate.php
+ * present, otherwise the module won't work. This ensures that the user
+ * explicitly says, "No, I do not need to migrate."
+ */
+
+if(!defined("PHORUM")) exit;
+
+require_once(dirname(__FILE__) . "/../bbcode/bbcode.php");
+
+/**
+ * 'format' hook style function that will be called to convert
+ * legacy markup into HTML.
+ */
+function phorum_htmlpurifier_migrate($data)
+{
+ return phorum_mod_bbcode_format($data); // bbcode's 'format' hook
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/plugins/phorum/settings.php b/vendor/ezyang/htmlpurifier/plugins/phorum/settings.php
new file mode 100644
index 000000000..8158f0282
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/plugins/phorum/settings.php
@@ -0,0 +1,64 @@
+<?php
+
+// based off of BBCode's settings file
+
+/**
+ * HTML Purifier Phorum mod settings configuration. This provides
+ * a convenient web-interface for editing the most common HTML Purifier
+ * configuration directives. You can also specify custom configuration
+ * by creating a 'config.php' file.
+ */
+
+if(!defined("PHORUM_ADMIN")) exit;
+
+// error reporting is good!
+error_reporting(E_ALL ^ E_NOTICE);
+
+// load library and other paraphenalia
+require_once './include/admin/PhorumInputForm.php';
+require_once (dirname(__FILE__) . '/htmlpurifier/HTMLPurifier.auto.php');
+require_once (dirname(__FILE__) . '/init-config.php');
+require_once (dirname(__FILE__) . '/settings/migrate-sigs-form.php');
+require_once (dirname(__FILE__) . '/settings/migrate-sigs.php');
+require_once (dirname(__FILE__) . '/settings/form.php');
+require_once (dirname(__FILE__) . '/settings/save.php');
+
+// define friendly configuration directives. you can expand this array
+// to get more web-definable directives
+$PHORUM['mod_htmlpurifier']['directives'] = array(
+ 'URI.Host', // auto-detectable
+ 'URI.DisableExternal',
+ 'URI.DisableExternalResources',
+ 'URI.DisableResources',
+ 'URI.Munge',
+ 'URI.HostBlacklist',
+ 'URI.Disable',
+ 'HTML.TidyLevel',
+ 'HTML.Doctype', // auto-detectable
+ 'HTML.Allowed',
+ 'AutoFormat',
+ '-AutoFormat.Custom',
+ 'AutoFormatParam',
+ 'Output.TidyFormat',
+);
+
+// lower this setting if you're getting time outs/out of memory
+$PHORUM['mod_htmlpurifier']['migrate-sigs-increment'] = 100;
+
+if (isset($_POST['reset'])) {
+ unset($PHORUM['mod_htmlpurifier']['config']);
+}
+
+if ($offset = phorum_htmlpurifier_migrate_sigs_check()) {
+ // migrate signatures
+ phorum_htmlpurifier_migrate_sigs($offset);
+} elseif(!empty($_POST)){
+ // save settings
+ phorum_htmlpurifier_save_settings();
+}
+
+phorum_htmlpurifier_show_migrate_sigs_form();
+echo '<br />';
+phorum_htmlpurifier_show_form();
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/plugins/phorum/settings/form.php b/vendor/ezyang/htmlpurifier/plugins/phorum/settings/form.php
new file mode 100644
index 000000000..9b6ad5f39
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/plugins/phorum/settings/form.php
@@ -0,0 +1,95 @@
+<?php
+
+function phorum_htmlpurifier_show_form()
+{
+ if (phorum_htmlpurifier_config_file_exists()) {
+ phorum_htmlpurifier_show_config_info();
+ return;
+ }
+
+ global $PHORUM;
+
+ $config = phorum_htmlpurifier_get_config();
+
+ $frm = new PhorumInputForm ("", "post", "Save");
+ $frm->hidden("module", "modsettings");
+ $frm->hidden("mod", "htmlpurifier"); // this is the directory name that the Settings file lives in
+
+ if (!empty($error)){
+ echo "$error<br />";
+ }
+
+ $frm->addbreak("Edit settings for the HTML Purifier module");
+
+ $frm->addMessage('<p>The box below sets <code>$PHORUM[\'mod_htmlpurifier\'][\'wysiwyg\']</code>.
+ When checked, contents sent for edit are now purified and the
+ informative message is disabled. If your WYSIWYG editor is disabled for
+ admin edits, you can safely keep this unchecked.</p>');
+ $frm->addRow('Use WYSIWYG?', $frm->checkbox('wysiwyg', '1', '', $PHORUM['mod_htmlpurifier']['wysiwyg']));
+
+ $frm->addMessage('<p>The box below sets <code>$PHORUM[\'mod_htmlpurifier\'][\'suppress_message\']</code>,
+ which removes the big how-to use
+ HTML Purifier message.</p>');
+ $frm->addRow('Suppress information?', $frm->checkbox('suppress_message', '1', '', $PHORUM['mod_htmlpurifier']['suppress_message']));
+
+ $frm->addMessage('<p>Click on directive links to read what each option does
+ (links do not open in new windows).</p>
+ <p>For more flexibility (for instance, you want to edit the full
+ range of configuration directives), you can create a <tt>config.php</tt>
+ file in your <tt>mods/htmlpurifier/</tt> directory. Doing so will,
+ however, make the web configuration interface unavailable.</p>');
+
+ require_once 'HTMLPurifier/Printer/ConfigForm.php';
+ $htmlpurifier_form = new HTMLPurifier_Printer_ConfigForm('config', 'http://htmlpurifier.org/live/configdoc/plain.html#%s');
+ $htmlpurifier_form->setTextareaDimensions(23, 7); // widen a little, since we have space
+
+ $frm->addMessage($htmlpurifier_form->render(
+ $config, $PHORUM['mod_htmlpurifier']['directives'], false));
+
+ $frm->addMessage("<strong>Warning: Changing HTML Purifier's configuration will invalidate
+ the cache. Expect to see a flurry of database activity after you change
+ any of these settings.</strong>");
+
+ $frm->addrow('Reset to defaults:', $frm->checkbox("reset", "1", "", false));
+
+ // hack to include extra styling
+ echo '<style type="text/css">' . $htmlpurifier_form->getCSS() . '
+ .hp-config {margin-left:auto;margin-right:auto;}
+ </style>';
+ $js = $htmlpurifier_form->getJavaScript();
+ echo '<script type="text/javascript">'."<!--\n$js\n//-->".'</script>';
+
+ $frm->show();
+}
+
+function phorum_htmlpurifier_show_config_info()
+{
+ global $PHORUM;
+
+ // update mod_htmlpurifier for housekeeping
+ phorum_htmlpurifier_commit_settings();
+
+ // politely tell user how to edit settings manually
+?>
+ <div class="input-form-td-break">How to edit settings for HTML Purifier module</div>
+ <p>
+ A <tt>config.php</tt> file exists in your <tt>mods/htmlpurifier/</tt>
+ directory. This file contains your custom configuration: in order to
+ change it, please navigate to that file and edit it accordingly.
+ You can also set <code>$GLOBALS['PHORUM']['mod_htmlpurifier']['wysiwyg']</code>
+ or <code>$GLOBALS['PHORUM']['mod_htmlpurifier']['suppress_message']</code>
+ </p>
+ <p>
+ To use the web interface, delete <tt>config.php</tt> (or rename it to
+ <tt>config.php.bak</tt>).
+ </p>
+ <p>
+ <strong>Warning: Changing HTML Purifier's configuration will invalidate
+ the cache. Expect to see a flurry of database activity after you change
+ any of these settings.</strong>
+ </p>
+<?php
+
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/plugins/phorum/settings/migrate-sigs-form.php b/vendor/ezyang/htmlpurifier/plugins/phorum/settings/migrate-sigs-form.php
new file mode 100644
index 000000000..abea3b51d
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/plugins/phorum/settings/migrate-sigs-form.php
@@ -0,0 +1,22 @@
+<?php
+
+function phorum_htmlpurifier_show_migrate_sigs_form()
+{
+ $frm = new PhorumInputForm ('', "post", "Migrate");
+ $frm->hidden("module", "modsettings");
+ $frm->hidden("mod", "htmlpurifier");
+ $frm->hidden("migrate-sigs", "1");
+ $frm->addbreak("Migrate user signatures to HTML");
+ $frm->addMessage('This operation will migrate your users signatures
+ to HTML. <strong>This process is irreversible and must only be performed once.</strong>
+ Type in yes in the confirmation field to migrate.');
+ if (!file_exists(dirname(__FILE__) . '/../migrate.php')) {
+ $frm->addMessage('Migration file does not exist, cannot migrate signatures.
+ Please check <tt>migrate.bbcode.php</tt> on how to create an appropriate file.');
+ } else {
+ $frm->addrow('Confirm:', $frm->text_box("confirmation", ""));
+ }
+ $frm->show();
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/plugins/phorum/settings/migrate-sigs.php b/vendor/ezyang/htmlpurifier/plugins/phorum/settings/migrate-sigs.php
new file mode 100644
index 000000000..5ea9cd0b8
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/plugins/phorum/settings/migrate-sigs.php
@@ -0,0 +1,79 @@
+<?php
+
+function phorum_htmlpurifier_migrate_sigs_check()
+{
+ global $PHORUM;
+ $offset = 0;
+ if (!empty($_POST['migrate-sigs'])) {
+ if (!isset($_POST['confirmation']) || strtolower($_POST['confirmation']) !== 'yes') {
+ echo 'Invalid confirmation code.';
+ exit;
+ }
+ $PHORUM['mod_htmlpurifier']['migrate-sigs'] = true;
+ phorum_db_update_settings(array("mod_htmlpurifier"=>$PHORUM["mod_htmlpurifier"]));
+ $offset = 1;
+ } elseif (!empty($_GET['migrate-sigs']) && $PHORUM['mod_htmlpurifier']['migrate-sigs']) {
+ $offset = (int) $_GET['migrate-sigs'];
+ }
+ return $offset;
+}
+
+function phorum_htmlpurifier_migrate_sigs($offset)
+{
+ global $PHORUM;
+
+ if(!$offset) return; // bail out quick if $offset == 0
+
+ // theoretically, we could get rid of this multi-request
+ // doo-hickery if safe mode is off
+ @set_time_limit(0); // attempt to let this run
+ $increment = $PHORUM['mod_htmlpurifier']['migrate-sigs-increment'];
+
+ require_once(dirname(__FILE__) . '/../migrate.php');
+ // migrate signatures
+ // do this in batches so we don't run out of time/space
+ $end = $offset + $increment;
+ $user_ids = array();
+ for ($i = $offset; $i < $end; $i++) {
+ $user_ids[] = $i;
+ }
+ $userinfos = phorum_db_user_get_fields($user_ids, 'signature');
+ foreach ($userinfos as $i => $user) {
+ if (empty($user['signature'])) continue;
+ $sig = $user['signature'];
+ // perform standard Phorum processing on the sig
+ $sig = str_replace(array("&","<",">"), array("&amp;","&lt;","&gt;"), $sig);
+ $sig = preg_replace("/<((http|https|ftp):\/\/[a-z0-9;\/\?:@=\&\$\-_\.\+!*'\(\),~%]+?)>/i", "$1", $sig);
+ // prepare fake data to pass to migration function
+ $fake_data = array(array("author"=>"", "email"=>"", "subject"=>"", 'body' => $sig));
+ list($fake_message) = phorum_htmlpurifier_migrate($fake_data);
+ $user['signature'] = $fake_message['body'];
+ if (!phorum_api_user_save($user)) {
+ exit('Error while saving user data');
+ }
+ }
+ unset($userinfos); // free up memory
+
+ // query for highest ID in database
+ $type = $PHORUM['DBCONFIG']['type'];
+ $sql = "select MAX(user_id) from {$PHORUM['user_table']}";
+ $row = phorum_db_interact(DB_RETURN_ROW, $sql);
+ $top_id = (int) $row[0];
+
+ $offset += $increment;
+ if ($offset > $top_id) { // test for end condition
+ echo 'Migration finished';
+ $PHORUM['mod_htmlpurifier']['migrate-sigs'] = false;
+ phorum_htmlpurifier_commit_settings();
+ return true;
+ }
+ $host = $_SERVER['HTTP_HOST'];
+ $uri = rtrim(dirname($_SERVER['PHP_SELF']), '/\\');
+ $extra = 'admin.php?module=modsettings&mod=htmlpurifier&migrate-sigs=' . $offset;
+ // relies on output buffering to work
+ header("Location: http://$host$uri/$extra");
+ exit;
+
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/plugins/phorum/settings/save.php b/vendor/ezyang/htmlpurifier/plugins/phorum/settings/save.php
new file mode 100644
index 000000000..2aefaf83a
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/plugins/phorum/settings/save.php
@@ -0,0 +1,29 @@
+<?php
+
+function phorum_htmlpurifier_save_settings()
+{
+ global $PHORUM;
+ if (phorum_htmlpurifier_config_file_exists()) {
+ echo "Cannot update settings, <code>mods/htmlpurifier/config.php</code> already exists. To change
+ settings, edit that file. To use the web form, delete that file.<br />";
+ } else {
+ $config = phorum_htmlpurifier_get_config(true);
+ if (!isset($_POST['reset'])) $config->mergeArrayFromForm($_POST, 'config', $PHORUM['mod_htmlpurifier']['directives']);
+ $PHORUM['mod_htmlpurifier']['config'] = $config->getAll();
+ }
+ $PHORUM['mod_htmlpurifier']['wysiwyg'] = !empty($_POST['wysiwyg']);
+ $PHORUM['mod_htmlpurifier']['suppress_message'] = !empty($_POST['suppress_message']);
+ if(!phorum_htmlpurifier_commit_settings()){
+ $error="Database error while updating settings.";
+ } else {
+ echo "Settings Updated<br />";
+ }
+}
+
+function phorum_htmlpurifier_commit_settings()
+{
+ global $PHORUM;
+ return phorum_db_update_settings(array("mod_htmlpurifier"=>$PHORUM["mod_htmlpurifier"]));
+}
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/release1-update.php b/vendor/ezyang/htmlpurifier/release1-update.php
new file mode 100644
index 000000000..834d38567
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/release1-update.php
@@ -0,0 +1,110 @@
+<?php
+
+// release script
+// PHP 5.0 only
+
+if (php_sapi_name() != 'cli') {
+ echo 'Release script cannot be called from web-browser.';
+ exit;
+}
+
+if (!isset($argv[1])) {
+ echo
+'php release.php [version]
+ HTML Purifier release script
+';
+ exit;
+}
+
+$version = trim($argv[1]);
+
+// Bump version numbers:
+
+// ...in VERSION
+file_put_contents('VERSION', $version);
+
+// ...in NEWS
+if ($is_dev = (strpos($version, 'dev') === false)) {
+ $date = date('Y-m-d');
+ $news_c = str_replace(
+ $l = "$version, unknown release date",
+ "$version, released $date",
+ file_get_contents('NEWS'),
+ $c
+ );
+ if (!$c) {
+ echo 'Could not update NEWS, missing ' . $l . PHP_EOL;
+ exit;
+ } elseif ($c > 1) {
+ echo 'More than one release declaration in NEWS replaced' . PHP_EOL;
+ exit;
+ }
+ file_put_contents('NEWS', $news_c);
+}
+
+// ...in Doxyfile
+$doxyfile_c = preg_replace(
+ '/(?<=PROJECT_NUMBER {9}= )[^\s]+/m', // brittle
+ $version,
+ file_get_contents('Doxyfile'),
+ 1, $c
+);
+if (!$c) {
+ echo 'Could not update Doxyfile, missing PROJECT_NUMBER.' . PHP_EOL;
+ exit;
+}
+file_put_contents('Doxyfile', $doxyfile_c);
+
+// ...in HTMLPurifier.php
+$htmlpurifier_c = file_get_contents('library/HTMLPurifier.php');
+$htmlpurifier_c = preg_replace(
+ '/HTML Purifier .+? - /',
+ "HTML Purifier $version - ",
+ $htmlpurifier_c,
+ 1, $c
+);
+if (!$c) {
+ echo 'Could not update HTMLPurifier.php, missing HTML Purifier [version] header.' . PHP_EOL;
+ exit;
+}
+$htmlpurifier_c = preg_replace(
+ '/public \$version = \'.+?\';/',
+ "public \$version = '$version';",
+ $htmlpurifier_c,
+ 1, $c
+);
+if (!$c) {
+ echo 'Could not update HTMLPurifier.php, missing public $version.' . PHP_EOL;
+ exit;
+}
+$htmlpurifier_c = preg_replace(
+ '/const VERSION = \'.+?\';/',
+ "const VERSION = '$version';",
+ $htmlpurifier_c,
+ 1, $c
+);
+if (!$c) {
+ echo 'Could not update HTMLPurifier.php, missing const $version.' . PHP_EOL;
+ exit;
+}
+file_put_contents('library/HTMLPurifier.php', $htmlpurifier_c);
+
+$config_c = file_get_contents('library/HTMLPurifier/Config.php');
+$config_c = preg_replace(
+ '/public \$version = \'.+?\';/',
+ "public \$version = '$version';",
+ $config_c,
+ 1, $c
+);
+if (!$c) {
+ echo 'Could not update Config.php, missing public $version.' . PHP_EOL;
+ exit;
+}
+file_put_contents('library/HTMLPurifier/Config.php', $config_c);
+
+passthru('php maintenance/flush.php');
+
+if ($is_dev) echo "Review changes, write something in WHATSNEW and FOCUS, and then commit with log 'Release $version.'" . PHP_EOL;
+else echo "Numbers updated to dev, no other modifications necessary!";
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/release2-tag.php b/vendor/ezyang/htmlpurifier/release2-tag.php
new file mode 100644
index 000000000..25e5300d8
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/release2-tag.php
@@ -0,0 +1,22 @@
+<?php
+
+// Tags releases
+
+if (php_sapi_name() != 'cli') {
+ echo 'Release script cannot be called from web-browser.';
+ exit;
+}
+
+require 'svn.php';
+
+$svn_info = my_svn_info('.');
+
+$version = trim(file_get_contents('VERSION'));
+
+$trunk_url = $svn_info['Repository Root'] . '/htmlpurifier/trunk';
+$trunk_tag_url = $svn_info['Repository Root'] . '/htmlpurifier/tags/' . $version;
+
+echo "Tagging trunk to tags/$version...";
+passthru("svn copy --message \"Tag $version release.\" $trunk_url $trunk_tag_url");
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/test-settings.sample.php b/vendor/ezyang/htmlpurifier/test-settings.sample.php
new file mode 100644
index 000000000..480b66279
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/test-settings.sample.php
@@ -0,0 +1,74 @@
+<?php
+
+// ATTENTION! DO NOT EDIT THIS FILE!
+// This file is necessary to run the unit tests and profiling scripts.
+// Please copy it to 'test-settings.php' and make the necessary edits.
+
+// Note: The only external library you *need* is SimpleTest; everything else
+// is optional.
+
+// We've got a lot of tests, so we recommend turning the limit off.
+set_time_limit(0);
+
+// Turning off output buffering will prevent mysterious errors from core dumps.
+$data = @ob_get_clean();
+if ($data !== false && $data !== '') {
+ echo "Output buffer contains data [".urlencode($data)."]\n";
+ exit;
+}
+
+// -----------------------------------------------------------------------------
+// REQUIRED SETTINGS
+
+// Note on running SimpleTest:
+// You want the Git copy of SimpleTest, found here:
+// https://github.com/simpletest/simpletest/
+//
+// If SimpleTest is borked with HTML Purifier, please contact me or
+// the SimpleTest devs; I am a developer for SimpleTest so I should be
+// able to quickly assess a fix. SimpleTest's problem is my problem!
+
+// Where is SimpleTest located? Remember to include a trailing slash!
+$simpletest_location = '/path/to/simpletest/';
+
+// -----------------------------------------------------------------------------
+// OPTIONAL SETTINGS
+
+// Note on running PHPT:
+// Vanilla PHPT from https://github.com/tswicegood/PHPT_Core should
+// work fine on Linux w/o multitest.
+//
+// To do multitest or Windows testing, you'll need some more
+// patches at https://github.com/ezyang/PHPT_Core
+//
+// I haven't tested the Windows setup in a while so I don't know if
+// it still works.
+
+// Should PHPT tests be enabled?
+$GLOBALS['HTMLPurifierTest']['PHPT'] = false;
+
+// If PHPT isn't in your Path via PEAR, set that here:
+// set_include_path('/path/to/phpt/Core/src' . PATH_SEPARATOR . get_include_path());
+
+// Where is CSSTidy located? (Include trailing slash. Leave false to disable.)
+$csstidy_location = false;
+
+// For tests/multitest.php, which versions to test?
+$versions_to_test = array();
+
+// Stable PHP binary to use when invoking maintenance scripts.
+$php = 'php';
+
+// For tests/multitest.php, what is the multi-version executable? It must
+// accept an extra parameter (version number) before all other arguments
+$phpv = false;
+
+// Should PEAR tests be run? If you've got a valid PEAR installation, set this
+// to true (or, if it's not in the include path, to its install directory).
+$GLOBALS['HTMLPurifierTest']['PEAR'] = false;
+
+// If PEAR is enabled, what PEAR tests should be run? (Note: you will
+// need to ensure these libraries are installed)
+$GLOBALS['HTMLPurifierTest']['Net_IDNA2'] = true;
+
+// vim: et sw=4 sts=4
diff --git a/vendor/ezyang/htmlpurifier/test-settings.travis.php b/vendor/ezyang/htmlpurifier/test-settings.travis.php
new file mode 100644
index 000000000..b1edce4aa
--- /dev/null
+++ b/vendor/ezyang/htmlpurifier/test-settings.travis.php
@@ -0,0 +1,72 @@
+<?php
+
+// This file is the configuration for Travis testing.
+
+// Note: The only external library you *need* is SimpleTest; everything else
+// is optional.
+
+// We've got a lot of tests, so we recommend turning the limit off.
+set_time_limit(0);
+
+// Turning off output buffering will prevent mysterious errors from core dumps.
+$data = @ob_get_clean();
+if ($data !== false && $data !== '') {
+ echo "Output buffer contains data [".urlencode($data)."]\n";
+ exit;
+}
+
+// -----------------------------------------------------------------------------
+// REQUIRED SETTINGS
+
+// Note on running SimpleTest:
+// You want the Git copy of SimpleTest, found here:
+// https://github.com/simpletest/simpletest/
+//
+// If SimpleTest is borked with HTML Purifier, please contact me or
+// the SimpleTest devs; I am a developer for SimpleTest so I should be
+// able to quickly assess a fix. SimpleTest's problem is my problem!
+
+// Where is SimpleTest located? Remember to include a trailing slash!
+$simpletest_location = dirname(__FILE__) . '/simpletest/';
+
+// -----------------------------------------------------------------------------
+// OPTIONAL SETTINGS
+
+// Note on running PHPT:
+// Vanilla PHPT from https://github.com/tswicegood/PHPT_Core should
+// work fine on Linux w/o multitest.
+//
+// To do multitest or Windows testing, you'll need some more
+// patches at https://github.com/ezyang/PHPT_Core
+//
+// I haven't tested the Windows setup in a while so I don't know if
+// it still works.
+
+// Should PHPT tests be enabled?
+$GLOBALS['HTMLPurifierTest']['PHPT'] = false;
+
+// If PHPT isn't in your Path via PEAR, set that here:
+// set_include_path('/path/to/phpt/Core/src' . PATH_SEPARATOR . get_include_path());
+
+// Where is CSSTidy located? (Include trailing slash. Leave false to disable.)
+$csstidy_location = false;
+
+// For tests/multitest.php, which versions to test?
+$versions_to_test = array();
+
+// Stable PHP binary to use when invoking maintenance scripts.
+$php = 'php';
+
+// For tests/multitest.php, what is the multi-version executable? It must
+// accept an extra parameter (version number) before all other arguments
+$phpv = false;
+
+// Should PEAR tests be run? If you've got a valid PEAR installation, set this
+// to true (or, if it's not in the include path, to its install directory).
+$GLOBALS['HTMLPurifierTest']['PEAR'] = false;
+
+// If PEAR is enabled, what PEAR tests should be run? (Note: you will
+// need to ensure these libraries are installed)
+$GLOBALS['HTMLPurifierTest']['Net_IDNA2'] = true;
+
+// vim: et sw=4 sts=4
diff --git a/vendor/league/html-to-markdown/CHANGELOG.md b/vendor/league/html-to-markdown/CHANGELOG.md
new file mode 100644
index 000000000..067864412
--- /dev/null
+++ b/vendor/league/html-to-markdown/CHANGELOG.md
@@ -0,0 +1,214 @@
+# Change Log
+All notable changes to this project will be documented in this file.
+Updates should follow the [Keep a CHANGELOG](http://keepachangelog.com/) principles.
+
+## [Unreleased][unreleased]
+
+## [4.4.1]
+
+### Fixed
+ - Fixed autolinking of invalid URLs (#129)
+
+## [4.4.0]
+
+### Added
+ - Added `hard_break` configuration option (#112, #115)
+ - The `HtmlConverter` can now be instantiated with an `Environment` (#118)
+
+### Fixed
+ - Fixed handling of paragraphs in list item elements (#47, #110)
+ - Fixed phantom spaces when newlines follow `br` elements (#116, #117)
+ - Fixed link converter not sanitizing inner spaces properly (#119, #120)
+
+## [4.3.1]
+### Changed
+ - Revised the sanitization implementation (#109)
+
+### Fixed
+ - Fixed tag-like content not being escaped (#67, #109)
+ - Fixed thematic break-like content not being escaped (#65, #109)
+ - Fixed codefence-like content not being escaped (#64, #109)
+
+## [4.3.0]
+### Added
+ - Added full support for PHP 7.0 and 7.1
+
+### Changed
+ - Changed `<pre>` and `<pre><code>` conversions to use backticks instead of indendation (#102)
+
+### Fixed
+ - Fixed issue where specified code language was not preserved (#70, #102)
+ - Fixed issue where `<code>` tags nested in `<pre>` was not converted properly (#70, #102)
+ - Fixed header-like content not being escaped (#76, #105)
+ - Fixed blockquote-like content not being escaped (#77, #103)
+ - Fixed ordered list-like content not being escaped (#73, #106)
+ - Fixed unordered list-like content not being escaped (#71, #107)
+
+## [4.2.2]
+### Fixed
+ - Fixed sanitization bug which sometimes removes desired content (#63, #101)
+
+## [4.2.1]
+### Fixed
+ - Fixed path to autoload.php when used as a library (#98)
+ - Fixed edge case for tags containing only whitespace (#99)
+
+### Removed
+ - Removed double HTML entity decoding, as this is not desireable (#60)
+
+## [4.2.0]
+
+### Added
+ - Added the ability to invoke HtmlConverter objects as functions (#85)
+
+### Fixed
+ - Fixed improper handling of nested list items (#19 and #84)
+ - Fixed preceeding or trailing spaces within emphasis tags (#83)
+
+## [4.1.1]
+
+### Fixed
+ - Fixed conversion of empty paragraphs (#78)
+ - Fixed `preg_replace` so it wouldn't break UTF-8 characters (#79)
+
+## [4.1.0]
+
+### Added
+ - Added `bin/html-to-markdown` script
+
+### Changed
+ - Changed default italic character to `_` (#58)
+
+## [4.0.1]
+
+### Fixed
+ - Added escaping to avoid * and _ in a text being rendered as emphasis (#48)
+
+### Removed
+ - Removed the demo (#51)
+ - `.styleci.yml` and `CONTRIBUTING.md` are no longer included in distributions (#50)
+
+## [4.0.0]
+
+This release changes the visibility of several methods/properties. #42 and #43 brought to light that some visiblities were
+not ideally set, so this releases fixes that. Moving forwards this should reduce the chance of introducing BC-breaking changes.
+
+### Added
+ - Added new `HtmlConverter::getEnvironment()` method to expose the `Environment` (#42, #43)
+
+### Changed
+ - Changed `Environment::addConverter()` from `protected` to `public`, enabling custom converters to be added (#42, #43)
+ - Changed `HtmlConverter::createDOMDocument()` from `protected` to `private`
+ - Changed `Element::nextCached` from `protected` to `private`
+ - Made the `Environment` class `final`
+
+## [3.1.1]
+### Fixed
+ - Empty HTML strings now result in empty Markdown documents (#40, #41)
+
+## [3.1.0]
+### Added
+ - Added new `equals` method to `Element` to check for equality
+
+### Changes
+ - Use Linux line endings consistently instead of plaform-specific line endings (#36)
+
+### Fixed
+ - Cleaned up code style
+
+## [3.0.0]
+### Changed
+ - Changed namespace to `League\HTMLToMarkdown`
+ - Changed packagist name to `league/html-to-markdown`
+ - Re-organized code into several separate classes
+ - `<a>` tags with identical href and inner text are now rendered using angular bracket syntax (#31)
+ - `<div>` elements are now treated as block-level elements (#33)
+
+## [2.2.2]
+### Added
+ - Added support for PHP 5.6 and HHVM
+ - Enabled testing against PHP 7 nightlies
+ - Added this CHANGELOG.md
+
+### Fixed
+ - Fixed whitespace preservation between inline elements (#9 and #10)
+
+## [2.2.1]
+### Fixed
+ - Preserve placeholder links (#22)
+
+## [2.2.0]
+### Added
+ - Added CircleCI config
+
+### Changed
+ - `<pre>` blocks are now treated as code elements
+
+### Removed
+ - Dropped support for PHP 5.2
+ - Removed incorrect README comment regarding `#text` nodes (#17)
+
+## [2.1.2]
+### Added
+ - Added the ability to blacklist/remove specific node types (#11)
+
+### Changed
+ - Line breaks are now placed after divs instead of before them
+ - Newlines inside of link texts are now removed
+ - Updated the minimum PHPUnit version to 4.*
+
+## [2.1.1]
+### Added
+ - Added options to customize emphasis characters
+
+## [2.1.0]
+### Added
+ - Added option to strip HTML tags without Markdown equivalents
+ - Added `convert()` method for converter reuse
+ - Added ability to set options after instance construction
+ - Documented the required PHP extensions (#4)
+
+### Changed
+ - ATX style now used for h1 and h2 tags inside blockquotes
+
+### Fixed
+ - Newlines inside blockquotes are now started with a bracket
+ - Fixed some incorrect docblocks
+ - `__toString()` now returns an empty string if input is empty
+ - Convert head tag if body tag is empty (#7)
+ - Preserve special characters inside tags without md equivalents (#6)
+
+
+## [2.0.1]
+### Fixed
+ - Fixed first line indentation for multi-line code blocks
+ - Fixed consecutive anchors get separating spaces stripped (#3)
+
+## [2.0.0]
+### Added
+ - Initial release
+
+[unreleased]: https://github.com/thephpleague/html-to-markdown/compare/4.4.1...master
+[4.4.1]: https://github.com/thephpleague/html-to-markdown/compare/4.4.0...4.4.1
+[4.4.0]: https://github.com/thephpleague/html-to-markdown/compare/4.3.1...4.4.0
+[4.3.1]: https://github.com/thephpleague/html-to-markdown/compare/4.3.0...4.3.1
+[4.3.0]: https://github.com/thephpleague/html-to-markdown/compare/4.2.2...4.3.0
+[4.2.2]: https://github.com/thephpleague/html-to-markdown/compare/4.2.1...4.2.2
+[4.2.1]: https://github.com/thephpleague/html-to-markdown/compare/4.2.0...4.2.1
+[4.2.0]: https://github.com/thephpleague/html-to-markdown/compare/4.1.1...4.2.0
+[4.1.1]: https://github.com/thephpleague/html-to-markdown/compare/4.1.0...4.1.1
+[4.1.0]: https://github.com/thephpleague/html-to-markdown/compare/4.0.1...4.1.0
+[4.0.1]: https://github.com/thephpleague/html-to-markdown/compare/4.0.0...4.0.1
+[4.0.0]: https://github.com/thephpleague/html-to-markdown/compare/3.1.1...4.0.0
+[3.1.1]: https://github.com/thephpleague/html-to-markdown/compare/3.1.0...3.1.1
+[3.1.0]: https://github.com/thephpleague/html-to-markdown/compare/3.0.0...3.1.0
+[3.0.0]: https://github.com/thephpleague/html-to-markdown/compare/2.2.2...3.0.0
+[2.2.2]: https://github.com/thephpleague/html-to-markdown/compare/2.2.1...2.2.2
+[2.2.1]: https://github.com/thephpleague/html-to-markdown/compare/2.2.0...2.2.1
+[2.2.0]: https://github.com/thephpleague/html-to-markdown/compare/2.1.2...2.2.0
+[2.1.2]: https://github.com/thephpleague/html-to-markdown/compare/2.1.1...2.1.2
+[2.1.1]: https://github.com/thephpleague/html-to-markdown/compare/2.1.0...2.1.1
+[2.1.0]: https://github.com/thephpleague/html-to-markdown/compare/2.0.1...2.1.0
+[2.0.1]: https://github.com/thephpleague/html-to-markdown/compare/2.0.0...2.0.1
+[2.0.0]: https://github.com/thephpleague/html-to-markdown/compare/775f91e...2.0.0
+
diff --git a/vendor/league/html-to-markdown/CONDUCT.md b/vendor/league/html-to-markdown/CONDUCT.md
new file mode 100644
index 000000000..01b8644f1
--- /dev/null
+++ b/vendor/league/html-to-markdown/CONDUCT.md
@@ -0,0 +1,22 @@
+# Contributor Code of Conduct
+
+As contributors and maintainers of this project, and in the interest of fostering an open and welcoming community, we pledge to respect all people who contribute through reporting issues, posting feature requests, updating documentation, submitting pull requests or patches, and other activities.
+
+We are committed to making participation in this project a harassment-free experience for everyone, regardless of level of experience, gender, gender identity and expression, sexual orientation, disability, personal appearance, body size, race, ethnicity, age, religion, or nationality.
+
+Examples of unacceptable behavior by participants include:
+
+* The use of sexualized language or imagery
+* Personal attacks
+* Trolling or insulting/derogatory comments
+* Public or private harassment
+* Publishing other's private information, such as physical or electronic addresses, without explicit permission
+* Other unethical or unprofessional conduct.
+
+Project maintainers have the right and responsibility to remove, edit, or reject comments, commits, code, wiki edits, issues, and other contributions that are not aligned to this Code of Conduct. By adopting this Code of Conduct, project maintainers commit themselves to fairly and consistently applying these principles to every aspect of managing this project. Project maintainers who do not follow or enforce the Code of Conduct may be permanently removed from the project team.
+
+This code of conduct applies both within project spaces and in public spaces when an individual is representing the project or its community.
+
+Instances of abusive, harassing, or otherwise unacceptable behavior may be reported by opening an issue or contacting one or more of the project maintainers.
+
+This Code of Conduct is adapted from the [Contributor Covenant](http://contributor-covenant.org), version 1.2.0, available at [http://contributor-covenant.org/version/1/2/0/](http://contributor-covenant.org/version/1/2/0/)
diff --git a/vendor/league/html-to-markdown/LICENSE b/vendor/league/html-to-markdown/LICENSE
new file mode 100644
index 000000000..6c04a59dd
--- /dev/null
+++ b/vendor/league/html-to-markdown/LICENSE
@@ -0,0 +1,22 @@
+The MIT License (MIT)
+
+Copyright (c) 2015 Colin O'Dell
+
+Originally created by Nick Cernis
+
+Permission is hereby granted, free of charge, to any person obtaining a copy of
+this software and associated documentation files (the "Software"), to deal in
+the Software without restriction, including without limitation the rights to
+use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
+the Software, and to permit persons to whom the Software is furnished to do so,
+subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in all
+copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
+FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. \ No newline at end of file
diff --git a/vendor/league/html-to-markdown/README.md b/vendor/league/html-to-markdown/README.md
new file mode 100644
index 000000000..8d75649d6
--- /dev/null
+++ b/vendor/league/html-to-markdown/README.md
@@ -0,0 +1,196 @@
+HTML To Markdown for PHP
+========================
+
+[![Join the chat at https://gitter.im/thephpleague/html-to-markdown](https://badges.gitter.im/Join%20Chat.svg)](https://gitter.im/thephpleague/html-to-markdown?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
+
+[![Latest Version](https://img.shields.io/packagist/v/league/html-to-markdown.svg?style=flat-square)](https://packagist.org/packages/league/html-to-markdown)
+[![Software License](http://img.shields.io/badge/license-MIT-brightgreen.svg?style=flat-square)](LICENSE)
+[![Build Status](https://img.shields.io/travis/thephpleague/html-to-markdown/master.svg?style=flat-square)](https://travis-ci.org/thephpleague/html-to-markdown)
+[![Coverage Status](https://img.shields.io/scrutinizer/coverage/g/thephpleague/html-to-markdown.svg?style=flat-square)](https://scrutinizer-ci.com/g/thephpleague/html-to-markdown/code-structure)
+[![Quality Score](https://img.shields.io/scrutinizer/g/thephpleague/html-to-markdown.svg?style=flat-square)](https://scrutinizer-ci.com/g/thephpleague/html-to-markdown)
+[![Total Downloads](https://img.shields.io/packagist/dt/league/html-to-markdown.svg?style=flat-square)](https://packagist.org/packages/league/html-to-markdown)
+
+Library which converts HTML to [Markdown](http://daringfireball.net/projects/markdown/) for your sanity and convenience.
+
+
+**Requires**: PHP 5.3+
+
+**Lead Developer**: [@colinodell](http://twitter.com/colinodell)
+
+**Original Author**: [@nickcernis](http://twitter.com/nickcernis)
+
+
+### Why convert HTML to Markdown?
+
+*"What alchemy is this?"* you mutter. *"I can see why you'd convert [Markdown to HTML](https://github.com/thephpleague/commonmark),"* you continue, already labouring the question somewhat, *"but why go the other way?"*
+
+Typically you would convert HTML to Markdown if:
+
+1. You have an existing HTML document that needs to be edited by people with good taste.
+2. You want to store new content in HTML format but edit it as Markdown.
+3. You want to convert HTML email to plain text email.
+4. You know a guy who's been converting HTML to Markdown for years, and now he can speak Elvish. You'd quite like to be able to speak Elvish.
+5. You just really like Markdown.
+
+### How to use it
+
+Require the library by issuing this command:
+
+```bash
+composer require league/html-to-markdown
+```
+
+Add `require 'vendor/autoload.php';` to the top of your script.
+
+Next, create a new HtmlConverter instance, passing in your valid HTML code to its `convert()` function:
+
+```php
+use League\HTMLToMarkdown\HtmlConverter;
+
+$converter = new HtmlConverter();
+
+$html = "<h3>Quick, to the Batpoles!</h3>";
+$markdown = $converter->convert($html);
+```
+
+The `$markdown` variable now contains the Markdown version of your HTML as a string:
+
+```php
+echo $markdown; // ==> ### Quick, to the Batpoles!
+```
+
+The included `demo` directory contains an HTML->Markdown conversion form to try out.
+
+### Conversion options
+
+By default, HTML To Markdown preserves HTML tags without Markdown equivalents, like `<span>` and `<div>`.
+
+To strip HTML tags that don't have a Markdown equivalent while preserving the content inside them, set `strip_tags` to true, like this:
+
+```php
+$converter = new HtmlConverter(array('strip_tags' => true));
+
+$html = '<span>Turnips!</span>';
+$markdown = $converter->convert($html); // $markdown now contains "Turnips!"
+```
+
+Or more explicitly, like this:
+
+```php
+$converter = new HtmlConverter();
+$converter->getConfig()->setOption('strip_tags', true);
+
+$html = '<span>Turnips!</span>';
+$markdown = $converter->convert($html); // $markdown now contains "Turnips!"
+```
+
+Note that only the tags themselves are stripped, not the content they hold.
+
+To strip tags and their content, pass a space-separated list of tags in `remove_nodes`, like this:
+
+```php
+$converter = new HtmlConverter(array('remove_nodes' => 'span div'));
+
+$html = '<span>Turnips!</span><div>Monkeys!</div>';
+$markdown = $converter->convert($html); // $markdown now contains ""
+```
+
+### Style options
+
+Bold and italic tags are converted using the asterisk syntax by default. Change this to the underlined syntax using the `bold_style` and `italic_style` options.
+
+```php
+$converter = new HtmlConverter();
+$converter->getConfig()->setOption('italic_style', '_');
+$converter->getConfig()->setOption('bold_style', '__');
+
+$html = '<em>Italic</em> and a <strong>bold</strong>';
+$markdown = $converter->convert($html); // $markdown now contains "_Italic_ and a __bold__"
+```
+
+### Line break options
+
+By default, `br` tags are converted to two spaces followed by a newline character as per [traditional Markdown](https://daringfireball.net/projects/markdown/syntax#p). Set `hard_break` to `true` to omit the two spaces, as per GitHub Flavored Markdown (GFM).
+
+```php
+$converter = new HtmlConverter();
+$html = '<p>test<br>line break</p>';
+
+$converter->getConfig()->setOption('hard_break', true);
+$markdown = $converter->convert($html); // $markdown now contains "test\nline break"
+
+$converter->getConfig()->setOption('hard_break', false); // default
+$markdown = $converter->convert($html); // $markdown now contains "test \nline break"
+```
+
+### Passing custom Environment object
+
+You can pass current `Environment` object to customize i.e. which converters should be used.
+
+```php
+$environment = new Environment(array(
+ // your configuration here
+));
+$environment->addConverter(new HeaderConverter()); // optionally - add converter manually
+
+$converter = new HtmlConverter($environment);
+
+$html = '<h3>Header</h3>
+<img src="" />
+';
+$markdown = $converter->convert($html); // $markdown now contains "### Header" and "<img src="" />"
+```
+
+### Limitations
+
+- Markdown Extra, MultiMarkdown and other variants aren't supported – just Markdown.
+
+### Known issues
+
+- Nested lists and lists containing multiple paragraphs aren't converted correctly.
+- Lists inside blockquotes aren't converted correctly.
+- Any reported [open issues here](https://github.com/thephpleague/html-to-markdown/issues?state=open).
+
+[Report your issue or request a feature here.](https://github.com/thephpleague/html-to-markdown/issues/new) Issues with patches or failing tests are especially welcome.
+
+### Style notes
+
+- Setext (underlined) headers are the default for H1 and H2. If you prefer the ATX style for H1 and H2 (# Header 1 and ## Header 2), set `header_style` to 'atx' in the options array when you instantiate the object:
+
+ `$converter = new HtmlConverter(array('header_style'=>'atx'));`
+
+ Headers of H3 priority and lower always use atx style.
+
+- Links and images are referenced inline. Footnote references (where image src and anchor href attributes are listed in the footnotes) are not used.
+- Blockquotes aren't line wrapped – it makes the converted Markdown easier to edit.
+
+### Dependencies
+
+HTML To Markdown requires PHP's [xml](http://www.php.net/manual/en/xml.installation.php), [lib-xml](http://www.php.net/manual/en/libxml.installation.php), and [dom](http://www.php.net/manual/en/dom.installation.php) extensions, all of which are enabled by default on most distributions.
+
+Errors such as "Fatal error: Class 'DOMDocument' not found" on distributions such as CentOS that disable PHP's xml extension can be resolved by installing php-xml.
+
+### Contributors
+
+Many thanks to all [contributors](https://github.com/thephpleague/html-to-markdown/graphs/contributors) so far. Further improvements and feature suggestions are very welcome.
+
+### How it works
+
+HTML To Markdown creates a DOMDocument from the supplied HTML, walks through the tree, and converts each node to a text node containing the equivalent markdown, starting from the most deeply nested node and working inwards towards the root node.
+
+### To-do
+
+- Support for nested lists and lists inside blockquotes.
+- Offer an option to preserve tags as HTML if they contain attributes that can't be represented with Markdown (e.g. `style`).
+
+### Trying to convert Markdown to HTML?
+
+Use one of these great libraries:
+
+ - [league/commonmark](https://github.com/thephpleague/commonmark) (recommended)
+ - [cebe/markdown](https://github.com/cebe/markdown)
+ - [PHP Markdown](https://michelf.ca/projects/php-markdown/)
+ - [Parsedown](https://github.com/erusev/parsedown)
+
+No guarantees about the Elvish, though.
+
diff --git a/vendor/league/html-to-markdown/bin/html-to-markdown b/vendor/league/html-to-markdown/bin/html-to-markdown
new file mode 100755
index 000000000..2815a7cef
--- /dev/null
+++ b/vendor/league/html-to-markdown/bin/html-to-markdown
@@ -0,0 +1,108 @@
+#!/usr/bin/env php
+<?php
+
+requireAutoloader();
+
+ini_set('display_errors', 'stderr');
+
+foreach ($argv as $i => $arg) {
+ if ($i === 0) {
+ continue;
+ }
+
+ if (substr($arg, 0, 1) === '-') {
+ switch ($arg) {
+ case '-h':
+ case '--help':
+ echo getHelpText();
+ exit(0);
+ default:
+ fail('Unknown option: ' . $arg);
+ }
+ } else {
+ $src = $argv[1];
+ }
+}
+
+if (isset($src)) {
+ if (!file_exists($src)) {
+ fail('File not found: ' . $src);
+ }
+
+ $html = file_get_contents($src);
+} else {
+ $stdin = fopen('php://stdin', 'r');
+ stream_set_blocking($stdin, false);
+ $html = stream_get_contents($stdin);
+ fclose($stdin);
+
+ if (empty($html)) {
+ fail(getHelpText());
+ }
+}
+
+
+$converter = new League\HTMLToMarkdown\HtmlConverter();
+echo $converter->convert($html);
+
+/**
+ * Get help and usage info
+ *
+ * @return string
+ */
+function getHelpText()
+{
+ return <<<HELP
+HTML To Markdown
+
+Usage: html-to-markdown [OPTIONS] [FILE]
+
+ -h, --help Shows help and usage information
+
+ If no file is given, input will be read from STDIN
+
+Examples:
+
+ Converting a file named document.html:
+
+ html-to-markdown document.html
+
+ Converting a file and saving its output:
+
+ html-to-markdown document.html > output.md
+
+ Converting from STDIN:
+
+ echo -e '<h1>Hello World!</h1>' | html-to-markdown
+
+ Converting from STDIN and saving the output:
+
+ echo -e '<h1>Hello World!</h1>' | html-to-markdown > output.md
+
+HELP;
+}
+
+/**
+ * @param string $message Error message
+ */
+function fail($message)
+{
+ fwrite(STDERR, $message . "\n");
+ exit(1);
+}
+
+function requireAutoloader()
+{
+ $autoloadPaths = array(
+ // Local package usage
+ __DIR__ . '/../vendor/autoload.php',
+ // Package was included as a library
+ __DIR__ . '/../../../autoload.php',
+ );
+ foreach ($autoloadPaths as $path) {
+ if (file_exists($path)) {
+ require_once $path;
+ break;
+ }
+ }
+}
diff --git a/vendor/league/html-to-markdown/composer.json b/vendor/league/html-to-markdown/composer.json
new file mode 100644
index 000000000..58764bcb5
--- /dev/null
+++ b/vendor/league/html-to-markdown/composer.json
@@ -0,0 +1,48 @@
+{
+ "name": "league/html-to-markdown",
+ "type": "library",
+ "description": "An HTML-to-markdown conversion helper for PHP",
+ "keywords": ["markdown", "html"],
+ "homepage": "https://github.com/thephpleague/html-to-markdown",
+ "license": "MIT",
+ "authors": [
+ {
+ "name": "Colin O'Dell",
+ "email": "colinodell@gmail.com",
+ "homepage": "http://www.colinodell.com",
+ "role": "Lead Developer"
+ },
+ {
+ "name": "Nick Cernis",
+ "email": "nick@cern.is",
+ "homepage": "http://modernnerd.net",
+ "role": "Original Author"
+ }
+ ],
+ "autoload": {
+ "psr-4": {
+ "League\\HTMLToMarkdown\\": "src/"
+ }
+ },
+ "autoload-dev": {
+ "psr-4": {
+ "League\\HTMLToMarkdown\\Test\\": "tests"
+ }
+ },
+ "require": {
+ "php": ">=5.3.3",
+ "ext-dom": "*",
+ "ext-xml": "*"
+ },
+ "require-dev": {
+ "mikehaertl/php-shellcommand": "~1.1.0",
+ "phpunit/phpunit": "4.*",
+ "scrutinizer/ocular": "~1.1"
+ },
+ "bin": ["bin/html-to-markdown"],
+ "extra": {
+ "branch-alias": {
+ "dev-master": "4.5-dev"
+ }
+ }
+}
diff --git a/vendor/league/html-to-markdown/src/Configuration.php b/vendor/league/html-to-markdown/src/Configuration.php
new file mode 100644
index 000000000..2943383aa
--- /dev/null
+++ b/vendor/league/html-to-markdown/src/Configuration.php
@@ -0,0 +1,60 @@
+<?php
+
+namespace League\HTMLToMarkdown;
+
+class Configuration
+{
+ protected $config;
+
+ /**
+ * @param array $config
+ */
+ public function __construct(array $config = array())
+ {
+ $this->config = $config;
+ }
+
+ /**
+ * @param array $config
+ */
+ public function merge(array $config = array())
+ {
+ $this->config = array_replace_recursive($this->config, $config);
+ }
+
+ /**
+ * @param array $config
+ */
+ public function replace(array $config = array())
+ {
+ $this->config = $config;
+ }
+
+ /**
+ * @param string $key
+ * @param mixed $value
+ */
+ public function setOption($key, $value)
+ {
+ $this->config[$key] = $value;
+ }
+
+ /**
+ * @param string|null $key
+ * @param mixed|null $default
+ *
+ * @return mixed|null
+ */
+ public function getOption($key = null, $default = null)
+ {
+ if ($key === null) {
+ return $this->config;
+ }
+
+ if (!isset($this->config[$key])) {
+ return $default;
+ }
+
+ return $this->config[$key];
+ }
+}
diff --git a/vendor/league/html-to-markdown/src/ConfigurationAwareInterface.php b/vendor/league/html-to-markdown/src/ConfigurationAwareInterface.php
new file mode 100644
index 000000000..8aca530be
--- /dev/null
+++ b/vendor/league/html-to-markdown/src/ConfigurationAwareInterface.php
@@ -0,0 +1,11 @@
+<?php
+
+namespace League\HTMLToMarkdown;
+
+interface ConfigurationAwareInterface
+{
+ /**
+ * @param Configuration $config
+ */
+ public function setConfig(Configuration $config);
+}
diff --git a/vendor/league/html-to-markdown/src/Converter/BlockquoteConverter.php b/vendor/league/html-to-markdown/src/Converter/BlockquoteConverter.php
new file mode 100644
index 000000000..eb2d09d17
--- /dev/null
+++ b/vendor/league/html-to-markdown/src/Converter/BlockquoteConverter.php
@@ -0,0 +1,44 @@
+<?php
+
+namespace League\HTMLToMarkdown\Converter;
+
+use League\HTMLToMarkdown\ElementInterface;
+
+class BlockquoteConverter implements ConverterInterface
+{
+ /**
+ * @param ElementInterface $element
+ *
+ * @return string
+ */
+ public function convert(ElementInterface $element)
+ {
+ // Contents should have already been converted to Markdown by this point,
+ // so we just need to add '>' symbols to each line.
+
+ $markdown = '';
+
+ $quote_content = trim($element->getValue());
+
+ $lines = preg_split('/\r\n|\r|\n/', $quote_content);
+
+ $total_lines = count($lines);
+
+ foreach ($lines as $i => $line) {
+ $markdown .= '> ' . $line . "\n";
+ if ($i + 1 === $total_lines) {
+ $markdown .= "\n";
+ }
+ }
+
+ return $markdown;
+ }
+
+ /**
+ * @return string[]
+ */
+ public function getSupportedTags()
+ {
+ return array('blockquote');
+ }
+}
diff --git a/vendor/league/html-to-markdown/src/Converter/CodeConverter.php b/vendor/league/html-to-markdown/src/Converter/CodeConverter.php
new file mode 100644
index 000000000..c8ec2c005
--- /dev/null
+++ b/vendor/league/html-to-markdown/src/Converter/CodeConverter.php
@@ -0,0 +1,62 @@
+<?php
+
+namespace League\HTMLToMarkdown\Converter;
+
+use League\HTMLToMarkdown\ElementInterface;
+
+class CodeConverter implements ConverterInterface
+{
+ /**
+ * @param ElementInterface $element
+ *
+ * @return string
+ */
+ public function convert(ElementInterface $element)
+ {
+ $language = null;
+
+ // Checking for language class on the code block
+ $classes = $element->getAttribute('class');
+
+ if ($classes) {
+ // Since tags can have more than one class, we need to find the one that starts with 'language-'
+ $classes = explode(' ', $classes);
+ foreach ($classes as $class) {
+ if (strpos($class, 'language-') !== false) {
+ // Found one, save it as the selected language and stop looping over the classes.
+ // The space after the language avoids gluing the actual code with the language tag
+ $language = str_replace('language-', '', $class) . ' ';
+ break;
+ }
+ }
+ }
+
+ $markdown = '';
+ $code = html_entity_decode($element->getChildrenAsString());
+
+ // In order to remove the code tags we need to search for them and, in the case of the opening tag
+ // use a regular expression to find the tag and the other attributes it might have
+ $code = preg_replace('/<code\b[^>]*>/', '', $code);
+ $code = str_replace('</code>', '', $code);
+
+ // Checking if the code has multiple lines
+ $lines = preg_split('/\r\n|\r|\n/', $code);
+ if (count($lines) > 1) {
+ // Multiple lines detected, adding three backticks and newlines
+ $markdown .= '```' . $language . "\n" . $code . "\n" . '```';
+ } else {
+ // One line of code, wrapping it on one backtick.
+ $markdown .= '`' . $language . $code . '`';
+ }
+
+ return $markdown;
+ }
+
+ /**
+ * @return string[]
+ */
+ public function getSupportedTags()
+ {
+ return array('code');
+ }
+}
diff --git a/vendor/league/html-to-markdown/src/Converter/CommentConverter.php b/vendor/league/html-to-markdown/src/Converter/CommentConverter.php
new file mode 100644
index 000000000..55038b254
--- /dev/null
+++ b/vendor/league/html-to-markdown/src/Converter/CommentConverter.php
@@ -0,0 +1,26 @@
+<?php
+
+namespace League\HTMLToMarkdown\Converter;
+
+use League\HTMLToMarkdown\ElementInterface;
+
+class CommentConverter implements ConverterInterface
+{
+ /**
+ * @param ElementInterface $element
+ *
+ * @return string
+ */
+ public function convert(ElementInterface $element)
+ {
+ return '';
+ }
+
+ /**
+ * @return string[]
+ */
+ public function getSupportedTags()
+ {
+ return array('#comment');
+ }
+}
diff --git a/vendor/league/html-to-markdown/src/Converter/ConverterInterface.php b/vendor/league/html-to-markdown/src/Converter/ConverterInterface.php
new file mode 100644
index 000000000..8530559a0
--- /dev/null
+++ b/vendor/league/html-to-markdown/src/Converter/ConverterInterface.php
@@ -0,0 +1,20 @@
+<?php
+
+namespace League\HTMLToMarkdown\Converter;
+
+use League\HTMLToMarkdown\ElementInterface;
+
+interface ConverterInterface
+{
+ /**
+ * @param ElementInterface $element
+ *
+ * @return string
+ */
+ public function convert(ElementInterface $element);
+
+ /**
+ * @return string[]
+ */
+ public function getSupportedTags();
+}
diff --git a/vendor/league/html-to-markdown/src/Converter/DefaultConverter.php b/vendor/league/html-to-markdown/src/Converter/DefaultConverter.php
new file mode 100644
index 000000000..964a71093
--- /dev/null
+++ b/vendor/league/html-to-markdown/src/Converter/DefaultConverter.php
@@ -0,0 +1,50 @@
+<?php
+
+namespace League\HTMLToMarkdown\Converter;
+
+use League\HTMLToMarkdown\Configuration;
+use League\HTMLToMarkdown\ConfigurationAwareInterface;
+use League\HTMLToMarkdown\ElementInterface;
+
+class DefaultConverter implements ConverterInterface, ConfigurationAwareInterface
+{
+ const DEFAULT_CONVERTER = '_default';
+
+ /**
+ * @var Configuration
+ */
+ protected $config;
+
+ /**
+ * @param Configuration $config
+ */
+ public function setConfig(Configuration $config)
+ {
+ $this->config = $config;
+ }
+
+ /**
+ * @param ElementInterface $element
+ *
+ * @return string
+ */
+ public function convert(ElementInterface $element)
+ {
+ // If strip_tags is false (the default), preserve tags that don't have Markdown equivalents,
+ // such as <span> nodes on their own. C14N() canonicalizes the node to a string.
+ // See: http://www.php.net/manual/en/domnode.c14n.php
+ if ($this->config->getOption('strip_tags', false)) {
+ return $element->getValue();
+ }
+
+ return html_entity_decode($element->getChildrenAsString());
+ }
+
+ /**
+ * @return string[]
+ */
+ public function getSupportedTags()
+ {
+ return array(self::DEFAULT_CONVERTER);
+ }
+}
diff --git a/vendor/league/html-to-markdown/src/Converter/DivConverter.php b/vendor/league/html-to-markdown/src/Converter/DivConverter.php
new file mode 100644
index 000000000..656a0ba4d
--- /dev/null
+++ b/vendor/league/html-to-markdown/src/Converter/DivConverter.php
@@ -0,0 +1,45 @@
+<?php
+
+namespace League\HTMLToMarkdown\Converter;
+
+use League\HTMLToMarkdown\Configuration;
+use League\HTMLToMarkdown\ConfigurationAwareInterface;
+use League\HTMLToMarkdown\ElementInterface;
+
+class DivConverter implements ConverterInterface, ConfigurationAwareInterface
+{
+ /**
+ * @var Configuration
+ */
+ protected $config;
+
+ /**
+ * @param Configuration $config
+ */
+ public function setConfig(Configuration $config)
+ {
+ $this->config = $config;
+ }
+
+ /**
+ * @param ElementInterface $element
+ *
+ * @return string
+ */
+ public function convert(ElementInterface $element)
+ {
+ if ($this->config->getOption('strip_tags', false)) {
+ return $element->getValue() . "\n\n";
+ }
+
+ return html_entity_decode($element->getChildrenAsString());
+ }
+
+ /**
+ * @return string[]
+ */
+ public function getSupportedTags()
+ {
+ return array('div');
+ }
+}
diff --git a/vendor/league/html-to-markdown/src/Converter/EmphasisConverter.php b/vendor/league/html-to-markdown/src/Converter/EmphasisConverter.php
new file mode 100644
index 000000000..67250769b
--- /dev/null
+++ b/vendor/league/html-to-markdown/src/Converter/EmphasisConverter.php
@@ -0,0 +1,57 @@
+<?php
+
+namespace League\HTMLToMarkdown\Converter;
+
+use League\HTMLToMarkdown\Configuration;
+use League\HTMLToMarkdown\ConfigurationAwareInterface;
+use League\HTMLToMarkdown\ElementInterface;
+
+class EmphasisConverter implements ConverterInterface, ConfigurationAwareInterface
+{
+ /**
+ * @var Configuration
+ */
+ protected $config;
+
+ /**
+ * @param Configuration $config
+ */
+ public function setConfig(Configuration $config)
+ {
+ $this->config = $config;
+ }
+
+ /**
+ * @param ElementInterface $element
+ *
+ * @return string
+ */
+ public function convert(ElementInterface $element)
+ {
+ $tag = $element->getTagName();
+ $value = $element->getValue();
+
+ if (!trim($value)) {
+ return '';
+ }
+
+ if ($tag === 'i' || $tag === 'em') {
+ $style = $this->config->getOption('italic_style');
+ } else {
+ $style = $this->config->getOption('bold_style');
+ }
+
+ $prefix = ltrim($value) !== $value ? ' ' : '';
+ $suffix = rtrim($value) !== $value ? ' ' : '';
+
+ return $prefix . $style . trim($value) . $style . $suffix;
+ }
+
+ /**
+ * @return string[]
+ */
+ public function getSupportedTags()
+ {
+ return array('em', 'i', 'strong', 'b');
+ }
+}
diff --git a/vendor/league/html-to-markdown/src/Converter/HardBreakConverter.php b/vendor/league/html-to-markdown/src/Converter/HardBreakConverter.php
new file mode 100644
index 000000000..37cd44e73
--- /dev/null
+++ b/vendor/league/html-to-markdown/src/Converter/HardBreakConverter.php
@@ -0,0 +1,41 @@
+<?php
+
+namespace League\HTMLToMarkdown\Converter;
+
+use League\HTMLToMarkdown\Configuration;
+use League\HTMLToMarkdown\ConfigurationAwareInterface;
+use League\HTMLToMarkdown\ElementInterface;
+
+class HardBreakConverter implements ConverterInterface, ConfigurationAwareInterface
+{
+ /**
+ * @var Configuration
+ */
+ protected $config;
+
+ /**
+ * @param Configuration $config
+ */
+ public function setConfig(Configuration $config)
+ {
+ $this->config = $config;
+ }
+
+ /**
+ * @param ElementInterface $element
+ *
+ * @return string
+ */
+ public function convert(ElementInterface $element)
+ {
+ return $this->config->getOption('hard_break') ? "\n" : " \n";
+ }
+
+ /**
+ * @return string[]
+ */
+ public function getSupportedTags()
+ {
+ return array('br');
+ }
+}
diff --git a/vendor/league/html-to-markdown/src/Converter/HeaderConverter.php b/vendor/league/html-to-markdown/src/Converter/HeaderConverter.php
new file mode 100644
index 000000000..d117e7d36
--- /dev/null
+++ b/vendor/league/html-to-markdown/src/Converter/HeaderConverter.php
@@ -0,0 +1,78 @@
+<?php
+
+namespace League\HTMLToMarkdown\Converter;
+
+use League\HTMLToMarkdown\Configuration;
+use League\HTMLToMarkdown\ConfigurationAwareInterface;
+use League\HTMLToMarkdown\ElementInterface;
+
+class HeaderConverter implements ConverterInterface, ConfigurationAwareInterface
+{
+ const STYLE_ATX = 'atx';
+ const STYLE_SETEXT = 'setext';
+
+ /**
+ * @var Configuration
+ */
+ protected $config;
+
+ /**
+ * @param Configuration $config
+ */
+ public function setConfig(Configuration $config)
+ {
+ $this->config = $config;
+ }
+
+ /**
+ * @param ElementInterface $element
+ *
+ * @return string
+ */
+ public function convert(ElementInterface $element)
+ {
+ $level = (int) substr($element->getTagName(), 1, 1);
+ $style = $this->config->getOption('header_style', self::STYLE_SETEXT);
+
+ if (($level === 1 || $level === 2) && !$element->isDescendantOf('blockquote') && $style === self::STYLE_SETEXT) {
+ return $this->createSetextHeader($level, $element->getValue());
+ }
+
+ return $this->createAtxHeader($level, $element->getValue());
+ }
+
+ /**
+ * @return string[]
+ */
+ public function getSupportedTags()
+ {
+ return array('h1', 'h2', 'h3', 'h4', 'h5', 'h6');
+ }
+
+ /**
+ * @param int $level
+ * @param string $content
+ *
+ * @return string
+ */
+ private function createSetextHeader($level, $content)
+ {
+ $length = function_exists('mb_strlen') ? mb_strlen($content, 'utf-8') : strlen($content);
+ $underline = ($level === 1) ? '=' : '-';
+
+ return $content . "\n" . str_repeat($underline, $length) . "\n\n";
+ }
+
+ /**
+ * @param int $level
+ * @param string $content
+ *
+ * @return string
+ */
+ private function createAtxHeader($level, $content)
+ {
+ $prefix = str_repeat('#', $level) . ' ';
+
+ return $prefix . $content . "\n\n";
+ }
+}
diff --git a/vendor/league/html-to-markdown/src/Converter/HorizontalRuleConverter.php b/vendor/league/html-to-markdown/src/Converter/HorizontalRuleConverter.php
new file mode 100644
index 000000000..8f54f9397
--- /dev/null
+++ b/vendor/league/html-to-markdown/src/Converter/HorizontalRuleConverter.php
@@ -0,0 +1,26 @@
+<?php
+
+namespace League\HTMLToMarkdown\Converter;
+
+use League\HTMLToMarkdown\ElementInterface;
+
+class HorizontalRuleConverter implements ConverterInterface
+{
+ /**
+ * @param ElementInterface $element
+ *
+ * @return string
+ */
+ public function convert(ElementInterface $element)
+ {
+ return "- - - - - -\n\n";
+ }
+
+ /**
+ * @return string[]
+ */
+ public function getSupportedTags()
+ {
+ return array('hr');
+ }
+}
diff --git a/vendor/league/html-to-markdown/src/Converter/ImageConverter.php b/vendor/league/html-to-markdown/src/Converter/ImageConverter.php
new file mode 100644
index 000000000..657c769c2
--- /dev/null
+++ b/vendor/league/html-to-markdown/src/Converter/ImageConverter.php
@@ -0,0 +1,35 @@
+<?php
+
+namespace League\HTMLToMarkdown\Converter;
+
+use League\HTMLToMarkdown\ElementInterface;
+
+class ImageConverter implements ConverterInterface
+{
+ /**
+ * @param ElementInterface $element
+ *
+ * @return string
+ */
+ public function convert(ElementInterface $element)
+ {
+ $src = $element->getAttribute('src');
+ $alt = $element->getAttribute('alt');
+ $title = $element->getAttribute('title');
+
+ if ($title !== '') {
+ // No newlines added. <img> should be in a block-level element.
+ return '![' . $alt . '](' . $src . ' "' . $title . '")';
+ }
+
+ return '![' . $alt . '](' . $src . ')';
+ }
+
+ /**
+ * @return string[]
+ */
+ public function getSupportedTags()
+ {
+ return array('img');
+ }
+}
diff --git a/vendor/league/html-to-markdown/src/Converter/LinkConverter.php b/vendor/league/html-to-markdown/src/Converter/LinkConverter.php
new file mode 100644
index 000000000..f0765f38b
--- /dev/null
+++ b/vendor/league/html-to-markdown/src/Converter/LinkConverter.php
@@ -0,0 +1,52 @@
+<?php
+
+namespace League\HTMLToMarkdown\Converter;
+
+use League\HTMLToMarkdown\ElementInterface;
+
+class LinkConverter implements ConverterInterface
+{
+ /**
+ * @param ElementInterface $element
+ *
+ * @return string
+ */
+ public function convert(ElementInterface $element)
+ {
+ $href = $element->getAttribute('href');
+ $title = $element->getAttribute('title');
+ $text = trim($element->getValue());
+
+ if ($title !== '') {
+ $markdown = '[' . $text . '](' . $href . ' "' . $title . '")';
+ } elseif ($href === $text && $this->isValidAutolink($href)) {
+ $markdown = '<' . $href . '>';
+ } else {
+ $markdown = '[' . $text . '](' . $href . ')';
+ }
+
+ if (!$href) {
+ $markdown = html_entity_decode($element->getChildrenAsString());
+ }
+
+ return $markdown;
+ }
+
+ /**
+ * @return string[]
+ */
+ public function getSupportedTags()
+ {
+ return array('a');
+ }
+
+ /**
+ * @param string $href
+ *
+ * @return bool
+ */
+ private function isValidAutolink($href)
+ {
+ return preg_match('/^[A-Za-z][A-Za-z0-9.+-]{1,31}:[^<>\x00-\x20]*/i', $href) === 1;
+ }
+}
diff --git a/vendor/league/html-to-markdown/src/Converter/ListBlockConverter.php b/vendor/league/html-to-markdown/src/Converter/ListBlockConverter.php
new file mode 100644
index 000000000..07a4c85a9
--- /dev/null
+++ b/vendor/league/html-to-markdown/src/Converter/ListBlockConverter.php
@@ -0,0 +1,26 @@
+<?php
+
+namespace League\HTMLToMarkdown\Converter;
+
+use League\HTMLToMarkdown\ElementInterface;
+
+class ListBlockConverter implements ConverterInterface
+{
+ /**
+ * @param ElementInterface $element
+ *
+ * @return string
+ */
+ public function convert(ElementInterface $element)
+ {
+ return $element->getValue() . "\n";
+ }
+
+ /**
+ * @return string[]
+ */
+ public function getSupportedTags()
+ {
+ return array('ol', 'ul');
+ }
+}
diff --git a/vendor/league/html-to-markdown/src/Converter/ListItemConverter.php b/vendor/league/html-to-markdown/src/Converter/ListItemConverter.php
new file mode 100644
index 000000000..dafec077c
--- /dev/null
+++ b/vendor/league/html-to-markdown/src/Converter/ListItemConverter.php
@@ -0,0 +1,47 @@
+<?php
+
+namespace League\HTMLToMarkdown\Converter;
+
+use League\HTMLToMarkdown\ElementInterface;
+
+class ListItemConverter implements ConverterInterface
+{
+ /**
+ * @param ElementInterface $element
+ *
+ * @return string
+ */
+ public function convert(ElementInterface $element)
+ {
+ // If parent is an ol, use numbers, otherwise, use dashes
+ $list_type = $element->getParent()->getTagName();
+
+ // Add spaces to start for nested list items
+ $level = $element->getListItemLevel($element);
+
+ $prefixForParagraph = str_repeat(' ', $level + 1);
+ $value = trim(implode("\n" . $prefixForParagraph, explode("\n", trim($element->getValue()))));
+
+ // If list item is the first in a nested list, add a newline before it
+ $prefix = '';
+ if ($level > 0 && $element->getSiblingPosition() === 1) {
+ $prefix = "\n";
+ }
+
+ if ($list_type === 'ul') {
+ return $prefix . '- ' . $value . "\n";
+ }
+
+ $number = $element->getSiblingPosition();
+
+ return $prefix . $number . '. ' . $value . "\n";
+ }
+
+ /**
+ * @return string[]
+ */
+ public function getSupportedTags()
+ {
+ return array('li');
+ }
+}
diff --git a/vendor/league/html-to-markdown/src/Converter/ParagraphConverter.php b/vendor/league/html-to-markdown/src/Converter/ParagraphConverter.php
new file mode 100644
index 000000000..cf852bfcf
--- /dev/null
+++ b/vendor/league/html-to-markdown/src/Converter/ParagraphConverter.php
@@ -0,0 +1,124 @@
+<?php
+
+namespace League\HTMLToMarkdown\Converter;
+
+use League\HTMLToMarkdown\ElementInterface;
+
+class ParagraphConverter implements ConverterInterface
+{
+ /**
+ * @param ElementInterface $element
+ *
+ * @return string
+ */
+ public function convert(ElementInterface $element)
+ {
+ $value = $element->getValue();
+
+ $markdown = '';
+
+ $lines = preg_split('/\r\n|\r|\n/', $value);
+ foreach ($lines as $line) {
+ /*
+ * Some special characters need to be escaped based on the position that they appear
+ * The following function will deal with those special cases.
+ */
+ $markdown .= $this->escapeSpecialCharacters($line);
+ $markdown .= "\n";
+ }
+
+ return trim($markdown) !== '' ? rtrim($markdown) . "\n\n" : '';
+ }
+
+ /**
+ * @return string[]
+ */
+ public function getSupportedTags()
+ {
+ return array('p');
+ }
+
+ /**
+ * @param string $line
+ *
+ * @return string
+ */
+ private function escapeSpecialCharacters($line)
+ {
+ $line = $this->escapeFirstCharacters($line);
+ $line = $this->escapeOtherCharacters($line);
+ $line = $this->escapeOtherCharactersRegex($line);
+
+ return $line;
+ }
+
+ /**
+ * @param string $line
+ *
+ * @return string
+ */
+ private function escapeFirstCharacters($line)
+ {
+ $escapable = array(
+ '>',
+ '- ',
+ '+ ',
+ '--',
+ '~~~',
+ '---',
+ '- - -'
+ );
+
+ foreach ($escapable as $i) {
+ if (strpos(ltrim($line), $i) === 0) {
+ // Found a character that must be escaped, adding a backslash before
+ return '\\' . ltrim($line);
+ }
+ }
+
+ return $line;
+ }
+
+ /**
+ * @param string $line
+ *
+ * @return string
+ */
+ private function escapeOtherCharacters($line)
+ {
+ $escapable = array(
+ '<!--'
+ );
+
+ foreach ($escapable as $i) {
+ if (strpos($line, $i) !== false) {
+ // Found an escapable character, escaping it
+ $line = substr_replace($line, '\\', strpos($line, $i), 0);
+ }
+ }
+
+ return $line;
+ }
+
+ /**
+ * @param string $line
+ *
+ * @return string
+ */
+ private function escapeOtherCharactersRegex($line)
+ {
+ $regExs = array(
+ // Match numbers ending on ')' or '.' that are at the beginning of the line.
+ '/^[0-9]+(?=\)|\.)/'
+ );
+
+ foreach ($regExs as $i) {
+ if (preg_match($i, $line, $match)) {
+ // Matched an escapable character, adding a backslash on the string before the offending character
+ $line = substr_replace($line, '\\', strlen($match[0]), 0);
+ }
+ }
+
+ return $line;
+ }
+}
diff --git a/vendor/league/html-to-markdown/src/Converter/PreformattedConverter.php b/vendor/league/html-to-markdown/src/Converter/PreformattedConverter.php
new file mode 100644
index 000000000..7a4ec3357
--- /dev/null
+++ b/vendor/league/html-to-markdown/src/Converter/PreformattedConverter.php
@@ -0,0 +1,59 @@
+<?php
+
+namespace League\HTMLToMarkdown\Converter;
+
+use League\HTMLToMarkdown\ElementInterface;
+
+class PreformattedConverter implements ConverterInterface
+{
+ /**
+ * @param ElementInterface $element
+ *
+ * @return string
+ */
+ public function convert(ElementInterface $element)
+ {
+ $markdown = '';
+
+ $pre_content = html_entity_decode($element->getChildrenAsString());
+ $pre_content = str_replace(array('<pre>', '</pre>'), '', $pre_content);
+
+ /*
+ * Checking for the code tag.
+ * Usually pre tags are used along with code tags. This conditional will check for already converted code tags,
+ * which use backticks, and if those backticks are at the beginning and at the end of the string it means
+ * there's no more information to convert.
+ */
+
+ $firstBacktick = strpos(trim($pre_content), '`');
+ $lastBacktick = strrpos(trim($pre_content), '`');
+ if ($firstBacktick === 0 && $lastBacktick === strlen(trim($pre_content)) - 1) {
+ return $pre_content;
+ }
+
+ // If the execution reaches this point it means it's just a pre tag, with no code tag nested
+
+ // Normalizing new lines
+ $pre_content = preg_replace('/\r\n|\r|\n/', PHP_EOL, $pre_content);
+
+ // Checking if the string has multiple lines
+ $lines = preg_split('/\r\n|\r|\n/', $pre_content);
+ if (count($lines) > 1) {
+ // Multiple lines detected, adding three backticks and newlines
+ $markdown .= '```' . "\n" . $pre_content . "\n" . '```';
+ } else {
+ // One line of code, wrapping it on one backtick.
+ $markdown .= '`' . $pre_content . '`';
+ }
+
+ return $markdown;
+ }
+
+ /**
+ * @return string[]
+ */
+ public function getSupportedTags()
+ {
+ return array('pre');
+ }
+}
diff --git a/vendor/league/html-to-markdown/src/Converter/TextConverter.php b/vendor/league/html-to-markdown/src/Converter/TextConverter.php
new file mode 100644
index 000000000..d6d91e16f
--- /dev/null
+++ b/vendor/league/html-to-markdown/src/Converter/TextConverter.php
@@ -0,0 +1,46 @@
+<?php
+
+namespace League\HTMLToMarkdown\Converter;
+
+use League\HTMLToMarkdown\ElementInterface;
+
+class TextConverter implements ConverterInterface
+{
+ /**
+ * @param ElementInterface $element
+ *
+ * @return string
+ */
+ public function convert(ElementInterface $element)
+ {
+ $markdown = $element->getValue();
+
+ // Remove leftover \n at the beginning of the line
+ $markdown = ltrim($markdown, "\n");
+
+ // Replace sequences of invisible characters with spaces
+ $markdown = preg_replace('~\s+~u', ' ', $markdown);
+
+ // Escape the following characters: '*', '_', '[', ']' and '\'
+ $markdown = preg_replace('~([*_\\[\\]\\\\])~u', '\\\\$1', $markdown);
+
+ $markdown = preg_replace('~^#~u', '\\\\#', $markdown);
+
+ if ($markdown === ' ') {
+ $next = $element->getNext();
+ if (!$next || $next->isBlock()) {
+ $markdown = '';
+ }
+ }
+
+ return $markdown;
+ }
+
+ /**
+ * @return string[]
+ */
+ public function getSupportedTags()
+ {
+ return array('#text');
+ }
+}
diff --git a/vendor/league/html-to-markdown/src/Element.php b/vendor/league/html-to-markdown/src/Element.php
new file mode 100644
index 000000000..e1e9d1a09
--- /dev/null
+++ b/vendor/league/html-to-markdown/src/Element.php
@@ -0,0 +1,257 @@
+<?php
+
+namespace League\HTMLToMarkdown;
+
+class Element implements ElementInterface
+{
+ /**
+ * @var \DOMNode
+ */
+ protected $node;
+
+ /**
+ * @var ElementInterface|null
+ */
+ private $nextCached;
+
+ public function __construct(\DOMNode $node)
+ {
+ $this->node = $node;
+ }
+
+ /**
+ * @return bool
+ */
+ public function isBlock()
+ {
+ switch ($this->getTagName()) {
+ case 'blockquote':
+ case 'body':
+ case 'code':
+ case 'div':
+ case 'h1':
+ case 'h2':
+ case 'h3':
+ case 'h4':
+ case 'h5':
+ case 'h6':
+ case 'hr':
+ case 'html':
+ case 'li':
+ case 'p':
+ case 'ol':
+ case 'ul':
+ return true;
+ default:
+ return false;
+ }
+ }
+
+ /**
+ * @return bool
+ */
+ public function isText()
+ {
+ return $this->getTagName() === '#text';
+ }
+
+ /**
+ * @return bool
+ */
+ public function isWhitespace()
+ {
+ return $this->getTagName() === '#text' && trim($this->getValue()) === '';
+ }
+
+ /**
+ * @return string
+ */
+ public function getTagName()
+ {
+ return $this->node->nodeName;
+ }
+
+ /**
+ * @return string
+ */
+ public function getValue()
+ {
+ return $this->node->nodeValue;
+ }
+
+ /**
+ * @return ElementInterface|null
+ */
+ public function getParent()
+ {
+ return new static($this->node->parentNode) ?: null;
+ }
+
+ /**
+ * @return bool
+ */
+ public function hasChildren()
+ {
+ return $this->node->hasChildNodes();
+ }
+
+ /**
+ * @return ElementInterface[]
+ */
+ public function getChildren()
+ {
+ $ret = array();
+ /** @var \DOMNode $node */
+ foreach ($this->node->childNodes as $node) {
+ $ret[] = new static($node);
+ }
+
+ return $ret;
+ }
+
+ /**
+ * @return ElementInterface|null
+ */
+ public function getNext()
+ {
+ if ($this->nextCached === null) {
+ $nextNode = $this->getNextNode($this->node);
+ if ($nextNode !== null) {
+ $this->nextCached = new static($nextNode);
+ }
+ }
+
+ return $this->nextCached;
+ }
+
+ /**
+ * @param \DomNode $node
+ * @param bool $checkChildren
+ *
+ * @return \DomNode|null
+ */
+ private function getNextNode($node, $checkChildren = true)
+ {
+ if ($checkChildren && $node->firstChild) {
+ return $node->firstChild;
+ }
+
+ if ($node->nextSibling) {
+ return $node->nextSibling;
+ }
+
+ if ($node->parentNode) {
+ return $this->getNextNode($node->parentNode, false);
+ }
+ }
+
+ /**
+ * @param string[]|string $tagNames
+ *
+ * @return bool
+ */
+ public function isDescendantOf($tagNames)
+ {
+ if (!is_array($tagNames)) {
+ $tagNames = array($tagNames);
+ }
+
+ for ($p = $this->node->parentNode; $p !== false; $p = $p->parentNode) {
+ if (is_null($p)) {
+ return false;
+ }
+
+ if (in_array($p->nodeName, $tagNames)) {
+ return true;
+ }
+ }
+
+ return false;
+ }
+
+ /**
+ * @param string $markdown
+ */
+ public function setFinalMarkdown($markdown)
+ {
+ $markdown_node = $this->node->ownerDocument->createTextNode($markdown);
+ $this->node->parentNode->replaceChild($markdown_node, $this->node);
+ }
+
+ /**
+ * @return string
+ */
+ public function getChildrenAsString()
+ {
+ return $this->node->C14N();
+ }
+
+ /**
+ * @return int
+ */
+ public function getSiblingPosition()
+ {
+ $position = 0;
+
+ // Loop through all nodes and find the given $node
+ foreach ($this->getParent()->getChildren() as $current_node) {
+ if (!$current_node->isWhitespace()) {
+ $position++;
+ }
+
+ // TODO: Need a less-buggy way of comparing these
+ // Perhaps we can somehow ensure that we always have the exact same object and use === instead?
+ if ($this->equals($current_node)) {
+ break;
+ }
+ }
+
+ return $position;
+ }
+
+ /**
+ * @return int
+ */
+ public function getListItemLevel()
+ {
+ $level = 0;
+ $parent = $this->getParent();
+
+ while ($parent !== null && $parent->node->parentNode) {
+ if ($parent->getTagName() === 'li') {
+ $level++;
+ }
+ $parent = $parent->getParent();
+ }
+
+ return $level;
+ }
+
+ /**
+ * @param string $name
+ *
+ * @return string
+ */
+ public function getAttribute($name)
+ {
+ if ($this->node instanceof \DOMElement) {
+ return $this->node->getAttribute($name);
+ }
+
+ return '';
+ }
+
+ /**
+ * @param ElementInterface $element
+ *
+ * @return bool
+ */
+ public function equals(ElementInterface $element)
+ {
+ if ($element instanceof self) {
+ return $element->node === $this->node;
+ }
+
+ return $element === $this;
+ }
+}
diff --git a/vendor/league/html-to-markdown/src/ElementInterface.php b/vendor/league/html-to-markdown/src/ElementInterface.php
new file mode 100644
index 000000000..138ddf286
--- /dev/null
+++ b/vendor/league/html-to-markdown/src/ElementInterface.php
@@ -0,0 +1,80 @@
+<?php
+
+namespace League\HTMLToMarkdown;
+
+interface ElementInterface
+{
+ /**
+ * @return bool
+ */
+ public function isBlock();
+
+ /**
+ * @return bool
+ */
+ public function isText();
+
+ /**
+ * @return bool
+ */
+ public function isWhitespace();
+
+ /**
+ * @return string
+ */
+ public function getTagName();
+
+ /**
+ * @return string
+ */
+ public function getValue();
+
+ /**
+ * @return ElementInterface|null
+ */
+ public function getParent();
+
+ /**
+ * @param string|string[] $tagNames
+ *
+ * @return bool
+ */
+ public function isDescendantOf($tagNames);
+
+ /**
+ * @return bool
+ */
+ public function hasChildren();
+
+ /**
+ * @return ElementInterface[]
+ */
+ public function getChildren();
+
+ /**
+ * @return ElementInterface|null
+ */
+ public function getNext();
+
+ /**
+ * @return int
+ */
+ public function getSiblingPosition();
+
+ /**
+ * @return string
+ */
+ public function getChildrenAsString();
+
+ /**
+ * @param string $markdown
+ */
+ public function setFinalMarkdown($markdown);
+
+ /**
+ * @param string $name
+ *
+ * @return string
+ */
+ public function getAttribute($name);
+}
diff --git a/vendor/league/html-to-markdown/src/Environment.php b/vendor/league/html-to-markdown/src/Environment.php
new file mode 100644
index 000000000..560cfe613
--- /dev/null
+++ b/vendor/league/html-to-markdown/src/Environment.php
@@ -0,0 +1,104 @@
+<?php
+
+namespace League\HTMLToMarkdown;
+
+use League\HTMLToMarkdown\Converter\BlockquoteConverter;
+use League\HTMLToMarkdown\Converter\CodeConverter;
+use League\HTMLToMarkdown\Converter\CommentConverter;
+use League\HTMLToMarkdown\Converter\ConverterInterface;
+use League\HTMLToMarkdown\Converter\DefaultConverter;
+use League\HTMLToMarkdown\Converter\DivConverter;
+use League\HTMLToMarkdown\Converter\EmphasisConverter;
+use League\HTMLToMarkdown\Converter\HardBreakConverter;
+use League\HTMLToMarkdown\Converter\HeaderConverter;
+use League\HTMLToMarkdown\Converter\HorizontalRuleConverter;
+use League\HTMLToMarkdown\Converter\ImageConverter;
+use League\HTMLToMarkdown\Converter\LinkConverter;
+use League\HTMLToMarkdown\Converter\ListBlockConverter;
+use League\HTMLToMarkdown\Converter\ListItemConverter;
+use League\HTMLToMarkdown\Converter\ParagraphConverter;
+use League\HTMLToMarkdown\Converter\PreformattedConverter;
+use League\HTMLToMarkdown\Converter\TextConverter;
+
+final class Environment
+{
+ /**
+ * @var Configuration
+ */
+ protected $config;
+
+ /**
+ * @var ConverterInterface[]
+ */
+ protected $converters = array();
+
+ public function __construct(array $config = array())
+ {
+ $this->config = new Configuration($config);
+ $this->addConverter(new DefaultConverter());
+ }
+
+ /**
+ * @return Configuration
+ */
+ public function getConfig()
+ {
+ return $this->config;
+ }
+
+ /**
+ * @param ConverterInterface $converter
+ */
+ public function addConverter(ConverterInterface $converter)
+ {
+ if ($converter instanceof ConfigurationAwareInterface) {
+ $converter->setConfig($this->config);
+ }
+
+ foreach ($converter->getSupportedTags() as $tag) {
+ $this->converters[$tag] = $converter;
+ }
+ }
+
+ /**
+ * @param string $tag
+ *
+ * @return ConverterInterface
+ */
+ public function getConverterByTag($tag)
+ {
+ if (isset($this->converters[$tag])) {
+ return $this->converters[$tag];
+ }
+
+ return $this->converters[DefaultConverter::DEFAULT_CONVERTER];
+ }
+
+ /**
+ * @param array $config
+ *
+ * @return Environment
+ */
+ public static function createDefaultEnvironment(array $config = array())
+ {
+ $environment = new static($config);
+
+ $environment->addConverter(new BlockquoteConverter());
+ $environment->addConverter(new CodeConverter());
+ $environment->addConverter(new CommentConverter());
+ $environment->addConverter(new DivConverter());
+ $environment->addConverter(new EmphasisConverter());
+ $environment->addConverter(new HardBreakConverter());
+ $environment->addConverter(new HeaderConverter());
+ $environment->addConverter(new HorizontalRuleConverter());
+ $environment->addConverter(new ImageConverter());
+ $environment->addConverter(new LinkConverter());
+ $environment->addConverter(new ListBlockConverter());
+ $environment->addConverter(new ListItemConverter());
+ $environment->addConverter(new ParagraphConverter());
+ $environment->addConverter(new PreformattedConverter());
+ $environment->addConverter(new TextConverter());
+
+ return $environment;
+ }
+}
diff --git a/vendor/league/html-to-markdown/src/HtmlConverter.php b/vendor/league/html-to-markdown/src/HtmlConverter.php
new file mode 100644
index 000000000..db3c29e1c
--- /dev/null
+++ b/vendor/league/html-to-markdown/src/HtmlConverter.php
@@ -0,0 +1,231 @@
+<?php
+
+namespace League\HTMLToMarkdown;
+
+/**
+ * Class HtmlConverter
+ *
+ * A helper class to convert HTML to Markdown.
+ *
+ * @author Colin O'Dell <colinodell@gmail.com>
+ * @author Nick Cernis <nick@cern.is>
+ *
+ * @link https://github.com/thephpleague/html-to-markdown/ Latest version on GitHub.
+ *
+ * @license http://www.opensource.org/licenses/mit-license.php MIT
+ */
+class HtmlConverter
+{
+ /**
+ * @var Environment
+ */
+ protected $environment;
+
+ /**
+ * Constructor
+ *
+ * @param Environment|array $options Environment object or configuration options
+ */
+ public function __construct($options = array())
+ {
+ if ($options instanceof Environment) {
+ $this->environment = $options;
+ } elseif (is_array($options)) {
+ $defaults = array(
+ 'header_style' => 'setext', // Set to 'atx' to output H1 and H2 headers as # Header1 and ## Header2
+ 'suppress_errors' => true, // Set to false to show warnings when loading malformed HTML
+ 'strip_tags' => false, // Set to true to strip tags that don't have markdown equivalents. N.B. Strips tags, not their content. Useful to clean MS Word HTML output.
+ 'bold_style' => '**', // Set to '__' if you prefer the underlined style
+ 'italic_style' => '_', // Set to '*' if you prefer the asterisk style
+ 'remove_nodes' => '', // space-separated list of dom nodes that should be removed. example: 'meta style script'
+ 'hard_break' => false,// Set to true to turn <br> into `\n` instead of ` \n`
+ );
+
+ $this->environment = Environment::createDefaultEnvironment($defaults);
+
+ $this->environment->getConfig()->merge($options);
+ }
+ }
+
+ /**
+ * @return Environment
+ */
+ public function getEnvironment()
+ {
+ return $this->environment;
+ }
+
+ /**
+ * @return Configuration
+ */
+ public function getConfig()
+ {
+ return $this->environment->getConfig();
+ }
+
+ /**
+ * Convert
+ *
+ * @see HtmlConverter::convert
+ *
+ * @param string $html
+ *
+ * @return string The Markdown version of the html
+ */
+ public function __invoke($html)
+ {
+ return $this->convert($html);
+ }
+
+ /**
+ * Convert
+ *
+ * Loads HTML and passes to getMarkdown()
+ *
+ * @param string $html
+ *
+ * @throws \InvalidArgumentException
+ *
+ * @return string The Markdown version of the html
+ */
+ public function convert($html)
+ {
+ if (trim($html) === '') {
+ return '';
+ }
+
+ $document = $this->createDOMDocument($html);
+
+ // Work on the entire DOM tree (including head and body)
+ if (!($root = $document->getElementsByTagName('html')->item(0))) {
+ throw new \InvalidArgumentException('Invalid HTML was provided');
+ }
+
+ $rootElement = new Element($root);
+ $this->convertChildren($rootElement);
+
+ // Store the now-modified DOMDocument as a string
+ $markdown = $document->saveHTML();
+
+ return $this->sanitize($markdown);
+ }
+
+ /**
+ * @param string $html
+ *
+ * @return \DOMDocument
+ */
+ private function createDOMDocument($html)
+ {
+ $document = new \DOMDocument();
+
+ if ($this->getConfig()->getOption('suppress_errors')) {
+ // Suppress conversion errors (from http://bit.ly/pCCRSX)
+ libxml_use_internal_errors(true);
+ }
+
+ // Hack to load utf-8 HTML (from http://bit.ly/pVDyCt)
+ $document->loadHTML('<?xml encoding="UTF-8">' . $html);
+ $document->encoding = 'UTF-8';
+
+ if ($this->getConfig()->getOption('suppress_errors')) {
+ libxml_clear_errors();
+ }
+
+ return $document;
+ }
+
+ /**
+ * Convert Children
+ *
+ * Recursive function to drill into the DOM and convert each node into Markdown from the inside out.
+ *
+ * Finds children of each node and convert those to #text nodes containing their Markdown equivalent,
+ * starting with the innermost element and working up to the outermost element.
+ *
+ * @param ElementInterface $element
+ */
+ private function convertChildren(ElementInterface $element)
+ {
+ // Don't convert HTML code inside <code> and <pre> blocks to Markdown - that should stay as HTML
+ // except if the current node is a code tag, which needs to be converted by the CodeConverter.
+ if ($element->isDescendantOf(array('pre', 'code')) && $element->getTagName() !== 'code') {
+ return;
+ }
+
+ // If the node has children, convert those to Markdown first
+ if ($element->hasChildren()) {
+ foreach ($element->getChildren() as $child) {
+ $this->convertChildren($child);
+ }
+ }
+
+ // Now that child nodes have been converted, convert the original node
+ $markdown = $this->convertToMarkdown($element);
+
+ // Create a DOM text node containing the Markdown equivalent of the original node
+
+ // Replace the old $node e.g. '<h3>Title</h3>' with the new $markdown_node e.g. '### Title'
+ $element->setFinalMarkdown($markdown);
+ }
+
+ /**
+ * Convert to Markdown
+ *
+ * Converts an individual node into a #text node containing a string of its Markdown equivalent.
+ *
+ * Example: An <h3> node with text content of 'Title' becomes a text node with content of '### Title'
+ *
+ * @param ElementInterface $element
+ *
+ * @return string The converted HTML as Markdown
+ */
+ protected function convertToMarkdown(ElementInterface $element)
+ {
+ $tag = $element->getTagName();
+
+ // Strip nodes named in remove_nodes
+ $tags_to_remove = explode(' ', $this->getConfig()->getOption('remove_nodes'));
+ if (in_array($tag, $tags_to_remove)) {
+ return false;
+ }
+
+ $converter = $this->environment->getConverterByTag($tag);
+
+ return $converter->convert($element);
+ }
+
+ /**
+ * @param string $markdown
+ *
+ * @return string
+ */
+ protected function sanitize($markdown)
+ {
+ $markdown = html_entity_decode($markdown, ENT_QUOTES, 'UTF-8');
+ $markdown = preg_replace('/<!DOCTYPE [^>]+>/', '', $markdown); // Strip doctype declaration
+ $markdown = trim($markdown); // Remove blank spaces at the beggining of the html
+
+ /*
+ * Removing unwanted tags. Tags should be added to the array in the order they are expected.
+ * XML, html and body opening tags should be in that order. Same case with closing tags
+ */
+ $unwanted = array('<?xml encoding="UTF-8">', '<html>', '</html>', '<body>', '</body>', '<head>', '</head>', '&#xD;');
+
+ foreach ($unwanted as $tag) {
+ if (strpos($tag, '/') === false) {
+ // Opening tags
+ if (strpos($markdown, $tag) === 0) {
+ $markdown = substr($markdown, strlen($tag));
+ }
+ } else {
+ // Closing tags
+ if (strpos($markdown, $tag) === strlen($markdown) - strlen($tag)) {
+ $markdown = substr($markdown, 0, -strlen($tag));
+ }
+ }
+ }
+
+ return trim($markdown, "\n\r\0\x0B");
+ }
+}
diff --git a/vendor/michelf/php-markdown/License.md b/vendor/michelf/php-markdown/License.md
new file mode 100644
index 000000000..c16197b69
--- /dev/null
+++ b/vendor/michelf/php-markdown/License.md
@@ -0,0 +1,36 @@
+PHP Markdown Lib
+Copyright (c) 2004-2016 Michel Fortin
+<https://michelf.ca/>
+All rights reserved.
+
+Based on Markdown
+Copyright (c) 2003-2006 John Gruber
+<https://daringfireball.net/>
+All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+* Redistributions of source code must retain the above copyright notice,
+ this list of conditions and the following disclaimer.
+
+* Redistributions in binary form must reproduce the above copyright
+ notice, this list of conditions and the following disclaimer in the
+ documentation and/or other materials provided with the distribution.
+
+* Neither the name "Markdown" nor the names of its contributors may
+ be used to endorse or promote products derived from this software
+ without specific prior written permission.
+
+This software is provided by the copyright holders and contributors "as
+is" and any express or implied warranties, including, but not limited
+to, the implied warranties of merchantability and fitness for a
+particular purpose are disclaimed. In no event shall the copyright owner
+or contributors be liable for any direct, indirect, incidental, special,
+exemplary, or consequential damages (including, but not limited to,
+procurement of substitute goods or services; loss of use, data, or
+profits; or business interruption) however caused and on any theory of
+liability, whether in contract, strict liability, or tort (including
+negligence or otherwise) arising in any way out of the use of this
+software, even if advised of the possibility of such damage.
diff --git a/vendor/michelf/php-markdown/Michelf/Markdown.inc.php b/vendor/michelf/php-markdown/Michelf/Markdown.inc.php
new file mode 100644
index 000000000..e2bd3808e
--- /dev/null
+++ b/vendor/michelf/php-markdown/Michelf/Markdown.inc.php
@@ -0,0 +1,10 @@
+<?php
+
+// Use this file if you cannot use class autoloading. It will include all the
+// files needed for the Markdown parser.
+//
+// Take a look at the PSR-0-compatible class autoloading implementation
+// in the Readme.php file if you want a simple autoloader setup.
+
+require_once dirname(__FILE__) . '/MarkdownInterface.php';
+require_once dirname(__FILE__) . '/Markdown.php';
diff --git a/vendor/michelf/php-markdown/Michelf/Markdown.php b/vendor/michelf/php-markdown/Michelf/Markdown.php
new file mode 100644
index 000000000..c3eaf4464
--- /dev/null
+++ b/vendor/michelf/php-markdown/Michelf/Markdown.php
@@ -0,0 +1,1896 @@
+<?php
+/**
+ * Markdown - A text-to-HTML conversion tool for web writers
+ *
+ * @package php-markdown
+ * @author Michel Fortin <michel.fortin@michelf.com>
+ * @copyright 2004-2016 Michel Fortin <https://michelf.com/projects/php-markdown/>
+ * @copyright (Original Markdown) 2004-2006 John Gruber <https://daringfireball.net/projects/markdown/>
+ */
+
+namespace Michelf;
+
+/**
+ * Markdown Parser Class
+ */
+class Markdown implements MarkdownInterface {
+ /**
+ * Define the package version
+ * @var string
+ */
+ const MARKDOWNLIB_VERSION = "1.7.0";
+
+ /**
+ * Simple function interface - Initialize the parser and return the result
+ * of its transform method. This will work fine for derived classes too.
+ *
+ * @api
+ *
+ * @param string $text
+ * @return string
+ */
+ public static function defaultTransform($text) {
+ // Take parser class on which this function was called.
+ $parser_class = \get_called_class();
+
+ // Try to take parser from the static parser list
+ static $parser_list;
+ $parser =& $parser_list[$parser_class];
+
+ // Create the parser it not already set
+ if (!$parser) {
+ $parser = new $parser_class;
+ }
+
+ // Transform text using parser.
+ return $parser->transform($text);
+ }
+
+ /**
+ * Configuration variables
+ */
+
+ /**
+ * Change to ">" for HTML output.
+ * @var string
+ */
+ public $empty_element_suffix = " />";
+
+ /**
+ * The width of indentation of the output markup
+ * @var int
+ */
+ public $tab_width = 4;
+
+ /**
+ * Change to `true` to disallow markup or entities.
+ * @var boolean
+ */
+ public $no_markup = false;
+ public $no_entities = false;
+
+
+ /**
+ * Change to `true` to enable line breaks on \n without two trailling spaces
+ * @var boolean
+ */
+ public $hard_wrap = false;
+
+ /**
+ * Predefined URLs and titles for reference links and images.
+ * @var array
+ */
+ public $predef_urls = array();
+ public $predef_titles = array();
+
+ /**
+ * Optional filter function for URLs
+ * @var callable
+ */
+ public $url_filter_func = null;
+
+ /**
+ * Optional header id="" generation callback function.
+ * @var callable
+ */
+ public $header_id_func = null;
+
+ /**
+ * Optional function for converting code block content to HTML
+ * @var callable
+ */
+ public $code_block_content_func = null;
+
+ /**
+ * Optional function for converting code span content to HTML.
+ * @var callable
+ */
+ public $code_span_content_func = null;
+
+ /**
+ * Class attribute to toggle "enhanced ordered list" behaviour
+ * setting this to true will allow ordered lists to start from the index
+ * number that is defined first.
+ *
+ * For example:
+ * 2. List item two
+ * 3. List item three
+ *
+ * Becomes:
+ * <ol start="2">
+ * <li>List item two</li>
+ * <li>List item three</li>
+ * </ol>
+ *
+ * @var bool
+ */
+ public $enhanced_ordered_list = false;
+
+ /**
+ * Parser implementation
+ */
+
+ /**
+ * Regex to match balanced [brackets].
+ * Needed to insert a maximum bracked depth while converting to PHP.
+ * @var int
+ */
+ protected $nested_brackets_depth = 6;
+ protected $nested_brackets_re;
+
+ protected $nested_url_parenthesis_depth = 4;
+ protected $nested_url_parenthesis_re;
+
+ /**
+ * Table of hash values for escaped characters:
+ * @var string
+ */
+ protected $escape_chars = '\`*_{}[]()>#+-.!';
+ protected $escape_chars_re;
+
+ /**
+ * Constructor function. Initialize appropriate member variables.
+ * @return void
+ */
+ public function __construct() {
+ $this->_initDetab();
+ $this->prepareItalicsAndBold();
+
+ $this->nested_brackets_re =
+ str_repeat('(?>[^\[\]]+|\[', $this->nested_brackets_depth).
+ str_repeat('\])*', $this->nested_brackets_depth);
+
+ $this->nested_url_parenthesis_re =
+ str_repeat('(?>[^()\s]+|\(', $this->nested_url_parenthesis_depth).
+ str_repeat('(?>\)))*', $this->nested_url_parenthesis_depth);
+
+ $this->escape_chars_re = '['.preg_quote($this->escape_chars).']';
+
+ // Sort document, block, and span gamut in ascendent priority order.
+ asort($this->document_gamut);
+ asort($this->block_gamut);
+ asort($this->span_gamut);
+ }
+
+
+ /**
+ * Internal hashes used during transformation.
+ * @var array
+ */
+ protected $urls = array();
+ protected $titles = array();
+ protected $html_hashes = array();
+
+ /**
+ * Status flag to avoid invalid nesting.
+ * @var boolean
+ */
+ protected $in_anchor = false;
+
+ /**
+ * Called before the transformation process starts to setup parser states.
+ * @return void
+ */
+ protected function setup() {
+ // Clear global hashes.
+ $this->urls = $this->predef_urls;
+ $this->titles = $this->predef_titles;
+ $this->html_hashes = array();
+ $this->in_anchor = false;
+ }
+
+ /**
+ * Called after the transformation process to clear any variable which may
+ * be taking up memory unnecessarly.
+ * @return void
+ */
+ protected function teardown() {
+ $this->urls = array();
+ $this->titles = array();
+ $this->html_hashes = array();
+ }
+
+ /**
+ * Main function. Performs some preprocessing on the input text and pass
+ * it through the document gamut.
+ *
+ * @api
+ *
+ * @param string $text
+ * @return string
+ */
+ public function transform($text) {
+ $this->setup();
+
+ # Remove UTF-8 BOM and marker character in input, if present.
+ $text = preg_replace('{^\xEF\xBB\xBF|\x1A}', '', $text);
+
+ # Standardize line endings:
+ # DOS to Unix and Mac to Unix
+ $text = preg_replace('{\r\n?}', "\n", $text);
+
+ # Make sure $text ends with a couple of newlines:
+ $text .= "\n\n";
+
+ # Convert all tabs to spaces.
+ $text = $this->detab($text);
+
+ # Turn block-level HTML blocks into hash entries
+ $text = $this->hashHTMLBlocks($text);
+
+ # Strip any lines consisting only of spaces and tabs.
+ # This makes subsequent regexen easier to write, because we can
+ # match consecutive blank lines with /\n+/ instead of something
+ # contorted like /[ ]*\n+/ .
+ $text = preg_replace('/^[ ]+$/m', '', $text);
+
+ # Run document gamut methods.
+ foreach ($this->document_gamut as $method => $priority) {
+ $text = $this->$method($text);
+ }
+
+ $this->teardown();
+
+ return $text . "\n";
+ }
+
+ /**
+ * Define the document gamut
+ * @var array
+ */
+ protected $document_gamut = array(
+ // Strip link definitions, store in hashes.
+ "stripLinkDefinitions" => 20,
+ "runBasicBlockGamut" => 30,
+ );
+
+ /**
+ * Strips link definitions from text, stores the URLs and titles in
+ * hash references
+ * @param string $text
+ * @return string
+ */
+ protected function stripLinkDefinitions($text) {
+
+ $less_than_tab = $this->tab_width - 1;
+
+ // Link defs are in the form: ^[id]: url "optional title"
+ $text = preg_replace_callback('{
+ ^[ ]{0,'.$less_than_tab.'}\[(.+)\][ ]?: # id = $1
+ [ ]*
+ \n? # maybe *one* newline
+ [ ]*
+ (?:
+ <(.+?)> # url = $2
+ |
+ (\S+?) # url = $3
+ )
+ [ ]*
+ \n? # maybe one newline
+ [ ]*
+ (?:
+ (?<=\s) # lookbehind for whitespace
+ ["(]
+ (.*?) # title = $4
+ [")]
+ [ ]*
+ )? # title is optional
+ (?:\n+|\Z)
+ }xm',
+ array($this, '_stripLinkDefinitions_callback'),
+ $text
+ );
+ return $text;
+ }
+
+ /**
+ * The callback to strip link definitions
+ * @param array $matches
+ * @return string
+ */
+ protected function _stripLinkDefinitions_callback($matches) {
+ $link_id = strtolower($matches[1]);
+ $url = $matches[2] == '' ? $matches[3] : $matches[2];
+ $this->urls[$link_id] = $url;
+ $this->titles[$link_id] =& $matches[4];
+ return ''; // String that will replace the block
+ }
+
+ /**
+ * Hashify HTML blocks
+ * @param string $text
+ * @return string
+ */
+ protected function hashHTMLBlocks($text) {
+ if ($this->no_markup) {
+ return $text;
+ }
+
+ $less_than_tab = $this->tab_width - 1;
+
+ /**
+ * Hashify HTML blocks:
+ *
+ * We only want to do this for block-level HTML tags, such as headers,
+ * lists, and tables. That's because we still want to wrap <p>s around
+ * "paragraphs" that are wrapped in non-block-level tags, such as
+ * anchors, phrase emphasis, and spans. The list of tags we're looking
+ * for is hard-coded:
+ *
+ * * List "a" is made of tags which can be both inline or block-level.
+ * These will be treated block-level when the start tag is alone on
+ * its line, otherwise they're not matched here and will be taken as
+ * inline later.
+ * * List "b" is made of tags which are always block-level;
+ */
+ $block_tags_a_re = 'ins|del';
+ $block_tags_b_re = 'p|div|h[1-6]|blockquote|pre|table|dl|ol|ul|address|'.
+ 'script|noscript|style|form|fieldset|iframe|math|svg|'.
+ 'article|section|nav|aside|hgroup|header|footer|'.
+ 'figure';
+
+ // Regular expression for the content of a block tag.
+ $nested_tags_level = 4;
+ $attr = '
+ (?> # optional tag attributes
+ \s # starts with whitespace
+ (?>
+ [^>"/]+ # text outside quotes
+ |
+ /+(?!>) # slash not followed by ">"
+ |
+ "[^"]*" # text inside double quotes (tolerate ">")
+ |
+ \'[^\']*\' # text inside single quotes (tolerate ">")
+ )*
+ )?
+ ';
+ $content =
+ str_repeat('
+ (?>
+ [^<]+ # content without tag
+ |
+ <\2 # nested opening tag
+ '.$attr.' # attributes
+ (?>
+ />
+ |
+ >', $nested_tags_level). // end of opening tag
+ '.*?'. // last level nested tag content
+ str_repeat('
+ </\2\s*> # closing nested tag
+ )
+ |
+ <(?!/\2\s*> # other tags with a different name
+ )
+ )*',
+ $nested_tags_level);
+ $content2 = str_replace('\2', '\3', $content);
+
+ /**
+ * First, look for nested blocks, e.g.:
+ * <div>
+ * <div>
+ * tags for inner block must be indented.
+ * </div>
+ * </div>
+ *
+ * The outermost tags must start at the left margin for this to match,
+ * and the inner nested divs must be indented.
+ * We need to do this before the next, more liberal match, because the
+ * next match will start at the first `<div>` and stop at the
+ * first `</div>`.
+ */
+ $text = preg_replace_callback('{(?>
+ (?>
+ (?<=\n) # Starting on its own line
+ | # or
+ \A\n? # the at beginning of the doc
+ )
+ ( # save in $1
+
+ # Match from `\n<tag>` to `</tag>\n`, handling nested tags
+ # in between.
+
+ [ ]{0,'.$less_than_tab.'}
+ <('.$block_tags_b_re.')# start tag = $2
+ '.$attr.'> # attributes followed by > and \n
+ '.$content.' # content, support nesting
+ </\2> # the matching end tag
+ [ ]* # trailing spaces/tabs
+ (?=\n+|\Z) # followed by a newline or end of document
+
+ | # Special version for tags of group a.
+
+ [ ]{0,'.$less_than_tab.'}
+ <('.$block_tags_a_re.')# start tag = $3
+ '.$attr.'>[ ]*\n # attributes followed by >
+ '.$content2.' # content, support nesting
+ </\3> # the matching end tag
+ [ ]* # trailing spaces/tabs
+ (?=\n+|\Z) # followed by a newline or end of document
+
+ | # Special case just for <hr />. It was easier to make a special
+ # case than to make the other regex more complicated.
+
+ [ ]{0,'.$less_than_tab.'}
+ <(hr) # start tag = $2
+ '.$attr.' # attributes
+ /?> # the matching end tag
+ [ ]*
+ (?=\n{2,}|\Z) # followed by a blank line or end of document
+
+ | # Special case for standalone HTML comments:
+
+ [ ]{0,'.$less_than_tab.'}
+ (?s:
+ <!-- .*? -->
+ )
+ [ ]*
+ (?=\n{2,}|\Z) # followed by a blank line or end of document
+
+ | # PHP and ASP-style processor instructions (<? and <%)
+
+ [ ]{0,'.$less_than_tab.'}
+ (?s:
+ <([?%]) # $2
+ .*?
+ \2>
+ )
+ [ ]*
+ (?=\n{2,}|\Z) # followed by a blank line or end of document
+
+ )
+ )}Sxmi',
+ array($this, '_hashHTMLBlocks_callback'),
+ $text
+ );
+
+ return $text;
+ }
+
+ /**
+ * The callback for hashing HTML blocks
+ * @param string $matches
+ * @return string
+ */
+ protected function _hashHTMLBlocks_callback($matches) {
+ $text = $matches[1];
+ $key = $this->hashBlock($text);
+ return "\n\n$key\n\n";
+ }
+
+ /**
+ * Called whenever a tag must be hashed when a function insert an atomic
+ * element in the text stream. Passing $text to through this function gives
+ * a unique text-token which will be reverted back when calling unhash.
+ *
+ * The $boundary argument specify what character should be used to surround
+ * the token. By convension, "B" is used for block elements that needs not
+ * to be wrapped into paragraph tags at the end, ":" is used for elements
+ * that are word separators and "X" is used in the general case.
+ *
+ * @param string $text
+ * @param string $boundary
+ * @return string
+ */
+ protected function hashPart($text, $boundary = 'X') {
+ // Swap back any tag hash found in $text so we do not have to `unhash`
+ // multiple times at the end.
+ $text = $this->unhash($text);
+
+ // Then hash the block.
+ static $i = 0;
+ $key = "$boundary\x1A" . ++$i . $boundary;
+ $this->html_hashes[$key] = $text;
+ return $key; // String that will replace the tag.
+ }
+
+ /**
+ * Shortcut function for hashPart with block-level boundaries.
+ * @param string $text
+ * @return string
+ */
+ protected function hashBlock($text) {
+ return $this->hashPart($text, 'B');
+ }
+
+ /**
+ * Define the block gamut - these are all the transformations that form
+ * block-level tags like paragraphs, headers, and list items.
+ * @var array
+ */
+ protected $block_gamut = array(
+ "doHeaders" => 10,
+ "doHorizontalRules" => 20,
+ "doLists" => 40,
+ "doCodeBlocks" => 50,
+ "doBlockQuotes" => 60,
+ );
+
+ /**
+ * Run block gamut tranformations.
+ *
+ * We need to escape raw HTML in Markdown source before doing anything
+ * else. This need to be done for each block, and not only at the
+ * begining in the Markdown function since hashed blocks can be part of
+ * list items and could have been indented. Indented blocks would have
+ * been seen as a code block in a previous pass of hashHTMLBlocks.
+ *
+ * @param string $text
+ * @return string
+ */
+ protected function runBlockGamut($text) {
+ $text = $this->hashHTMLBlocks($text);
+ return $this->runBasicBlockGamut($text);
+ }
+
+ /**
+ * Run block gamut tranformations, without hashing HTML blocks. This is
+ * useful when HTML blocks are known to be already hashed, like in the first
+ * whole-document pass.
+ *
+ * @param string $text
+ * @return string
+ */
+ protected function runBasicBlockGamut($text) {
+
+ foreach ($this->block_gamut as $method => $priority) {
+ $text = $this->$method($text);
+ }
+
+ // Finally form paragraph and restore hashed blocks.
+ $text = $this->formParagraphs($text);
+
+ return $text;
+ }
+
+ /**
+ * Convert horizontal rules
+ * @param string $text
+ * @return string
+ */
+ protected function doHorizontalRules($text) {
+ return preg_replace(
+ '{
+ ^[ ]{0,3} # Leading space
+ ([-*_]) # $1: First marker
+ (?> # Repeated marker group
+ [ ]{0,2} # Zero, one, or two spaces.
+ \1 # Marker character
+ ){2,} # Group repeated at least twice
+ [ ]* # Tailing spaces
+ $ # End of line.
+ }mx',
+ "\n".$this->hashBlock("<hr$this->empty_element_suffix")."\n",
+ $text
+ );
+ }
+
+ /**
+ * These are all the transformations that occur *within* block-level
+ * tags like paragraphs, headers, and list items.
+ * @var array
+ */
+ protected $span_gamut = array(
+ // Process character escapes, code spans, and inline HTML
+ // in one shot.
+ "parseSpan" => -30,
+ // Process anchor and image tags. Images must come first,
+ // because ![foo][f] looks like an anchor.
+ "doImages" => 10,
+ "doAnchors" => 20,
+ // Make links out of things like `<https://example.com/>`
+ // Must come after doAnchors, because you can use < and >
+ // delimiters in inline links like [this](<url>).
+ "doAutoLinks" => 30,
+ "encodeAmpsAndAngles" => 40,
+ "doItalicsAndBold" => 50,
+ "doHardBreaks" => 60,
+ );
+
+ /**
+ * Run span gamut transformations
+ * @param string $text
+ * @return string
+ */
+ protected function runSpanGamut($text) {
+ foreach ($this->span_gamut as $method => $priority) {
+ $text = $this->$method($text);
+ }
+
+ return $text;
+ }
+
+ /**
+ * Do hard breaks
+ * @param string $text
+ * @return string
+ */
+ protected function doHardBreaks($text) {
+ if ($this->hard_wrap) {
+ return preg_replace_callback('/ *\n/',
+ array($this, '_doHardBreaks_callback'), $text);
+ } else {
+ return preg_replace_callback('/ {2,}\n/',
+ array($this, '_doHardBreaks_callback'), $text);
+ }
+ }
+
+ /**
+ * Trigger part hashing for the hard break (callback method)
+ * @param array $matches
+ * @return string
+ */
+ protected function _doHardBreaks_callback($matches) {
+ return $this->hashPart("<br$this->empty_element_suffix\n");
+ }
+
+ /**
+ * Turn Markdown link shortcuts into XHTML <a> tags.
+ * @param string $text
+ * @return string
+ */
+ protected function doAnchors($text) {
+ if ($this->in_anchor) {
+ return $text;
+ }
+ $this->in_anchor = true;
+
+ // First, handle reference-style links: [link text] [id]
+ $text = preg_replace_callback('{
+ ( # wrap whole match in $1
+ \[
+ ('.$this->nested_brackets_re.') # link text = $2
+ \]
+
+ [ ]? # one optional space
+ (?:\n[ ]*)? # one optional newline followed by spaces
+
+ \[
+ (.*?) # id = $3
+ \]
+ )
+ }xs',
+ array($this, '_doAnchors_reference_callback'), $text);
+
+ // Next, inline-style links: [link text](url "optional title")
+ $text = preg_replace_callback('{
+ ( # wrap whole match in $1
+ \[
+ ('.$this->nested_brackets_re.') # link text = $2
+ \]
+ \( # literal paren
+ [ \n]*
+ (?:
+ <(.+?)> # href = $3
+ |
+ ('.$this->nested_url_parenthesis_re.') # href = $4
+ )
+ [ \n]*
+ ( # $5
+ ([\'"]) # quote char = $6
+ (.*?) # Title = $7
+ \6 # matching quote
+ [ \n]* # ignore any spaces/tabs between closing quote and )
+ )? # title is optional
+ \)
+ )
+ }xs',
+ array($this, '_doAnchors_inline_callback'), $text);
+
+ // Last, handle reference-style shortcuts: [link text]
+ // These must come last in case you've also got [link text][1]
+ // or [link text](/foo)
+ $text = preg_replace_callback('{
+ ( # wrap whole match in $1
+ \[
+ ([^\[\]]+) # link text = $2; can\'t contain [ or ]
+ \]
+ )
+ }xs',
+ array($this, '_doAnchors_reference_callback'), $text);
+
+ $this->in_anchor = false;
+ return $text;
+ }
+
+ /**
+ * Callback method to parse referenced anchors
+ * @param string $matches
+ * @return string
+ */
+ protected function _doAnchors_reference_callback($matches) {
+ $whole_match = $matches[1];
+ $link_text = $matches[2];
+ $link_id =& $matches[3];
+
+ if ($link_id == "") {
+ // for shortcut links like [this][] or [this].
+ $link_id = $link_text;
+ }
+
+ // lower-case and turn embedded newlines into spaces
+ $link_id = strtolower($link_id);
+ $link_id = preg_replace('{[ ]?\n}', ' ', $link_id);
+
+ if (isset($this->urls[$link_id])) {
+ $url = $this->urls[$link_id];
+ $url = $this->encodeURLAttribute($url);
+
+ $result = "<a href=\"$url\"";
+ if ( isset( $this->titles[$link_id] ) ) {
+ $title = $this->titles[$link_id];
+ $title = $this->encodeAttribute($title);
+ $result .= " title=\"$title\"";
+ }
+
+ $link_text = $this->runSpanGamut($link_text);
+ $result .= ">$link_text</a>";
+ $result = $this->hashPart($result);
+ } else {
+ $result = $whole_match;
+ }
+ return $result;
+ }
+
+ /**
+ * Callback method to parse inline anchors
+ * @param string $matches
+ * @return string
+ */
+ protected function _doAnchors_inline_callback($matches) {
+ $whole_match = $matches[1];
+ $link_text = $this->runSpanGamut($matches[2]);
+ $url = $matches[3] == '' ? $matches[4] : $matches[3];
+ $title =& $matches[7];
+
+ // If the URL was of the form <s p a c e s> it got caught by the HTML
+ // tag parser and hashed. Need to reverse the process before using
+ // the URL.
+ $unhashed = $this->unhash($url);
+ if ($unhashed != $url)
+ $url = preg_replace('/^<(.*)>$/', '\1', $unhashed);
+
+ $url = $this->encodeURLAttribute($url);
+
+ $result = "<a href=\"$url\"";
+ if (isset($title)) {
+ $title = $this->encodeAttribute($title);
+ $result .= " title=\"$title\"";
+ }
+
+ $link_text = $this->runSpanGamut($link_text);
+ $result .= ">$link_text</a>";
+
+ return $this->hashPart($result);
+ }
+
+ /**
+ * Turn Markdown image shortcuts into <img> tags.
+ * @param string $text
+ * @return string
+ */
+ protected function doImages($text) {
+ // First, handle reference-style labeled images: ![alt text][id]
+ $text = preg_replace_callback('{
+ ( # wrap whole match in $1
+ !\[
+ ('.$this->nested_brackets_re.') # alt text = $2
+ \]
+
+ [ ]? # one optional space
+ (?:\n[ ]*)? # one optional newline followed by spaces
+
+ \[
+ (.*?) # id = $3
+ \]
+
+ )
+ }xs',
+ array($this, '_doImages_reference_callback'), $text);
+
+ // Next, handle inline images: ![alt text](url "optional title")
+ // Don't forget: encode * and _
+ $text = preg_replace_callback('{
+ ( # wrap whole match in $1
+ !\[
+ ('.$this->nested_brackets_re.') # alt text = $2
+ \]
+ \s? # One optional whitespace character
+ \( # literal paren
+ [ \n]*
+ (?:
+ <(\S*)> # src url = $3
+ |
+ ('.$this->nested_url_parenthesis_re.') # src url = $4
+ )
+ [ \n]*
+ ( # $5
+ ([\'"]) # quote char = $6
+ (.*?) # title = $7
+ \6 # matching quote
+ [ \n]*
+ )? # title is optional
+ \)
+ )
+ }xs',
+ array($this, '_doImages_inline_callback'), $text);
+
+ return $text;
+ }
+
+ /**
+ * Callback to parse references image tags
+ * @param array $matches
+ * @return string
+ */
+ protected function _doImages_reference_callback($matches) {
+ $whole_match = $matches[1];
+ $alt_text = $matches[2];
+ $link_id = strtolower($matches[3]);
+
+ if ($link_id == "") {
+ $link_id = strtolower($alt_text); // for shortcut links like ![this][].
+ }
+
+ $alt_text = $this->encodeAttribute($alt_text);
+ if (isset($this->urls[$link_id])) {
+ $url = $this->encodeURLAttribute($this->urls[$link_id]);
+ $result = "<img src=\"$url\" alt=\"$alt_text\"";
+ if (isset($this->titles[$link_id])) {
+ $title = $this->titles[$link_id];
+ $title = $this->encodeAttribute($title);
+ $result .= " title=\"$title\"";
+ }
+ $result .= $this->empty_element_suffix;
+ $result = $this->hashPart($result);
+ } else {
+ // If there's no such link ID, leave intact:
+ $result = $whole_match;
+ }
+
+ return $result;
+ }
+
+ /**
+ * Callback to parse inline image tags
+ * @param array $matches
+ * @return string
+ */
+ protected function _doImages_inline_callback($matches) {
+ $whole_match = $matches[1];
+ $alt_text = $matches[2];
+ $url = $matches[3] == '' ? $matches[4] : $matches[3];
+ $title =& $matches[7];
+
+ $alt_text = $this->encodeAttribute($alt_text);
+ $url = $this->encodeURLAttribute($url);
+ $result = "<img src=\"$url\" alt=\"$alt_text\"";
+ if (isset($title)) {
+ $title = $this->encodeAttribute($title);
+ $result .= " title=\"$title\""; // $title already quoted
+ }
+ $result .= $this->empty_element_suffix;
+
+ return $this->hashPart($result);
+ }
+
+ /**
+ * Parse Markdown heading elements to HTML
+ * @param string $text
+ * @return string
+ */
+ protected function doHeaders($text) {
+ /**
+ * Setext-style headers:
+ * Header 1
+ * ========
+ *
+ * Header 2
+ * --------
+ */
+ $text = preg_replace_callback('{ ^(.+?)[ ]*\n(=+|-+)[ ]*\n+ }mx',
+ array($this, '_doHeaders_callback_setext'), $text);
+
+ /**
+ * atx-style headers:
+ * # Header 1
+ * ## Header 2
+ * ## Header 2 with closing hashes ##
+ * ...
+ * ###### Header 6
+ */
+ $text = preg_replace_callback('{
+ ^(\#{1,6}) # $1 = string of #\'s
+ [ ]*
+ (.+?) # $2 = Header text
+ [ ]*
+ \#* # optional closing #\'s (not counted)
+ \n+
+ }xm',
+ array($this, '_doHeaders_callback_atx'), $text);
+
+ return $text;
+ }
+
+ /**
+ * Setext header parsing callback
+ * @param array $matches
+ * @return string
+ */
+ protected function _doHeaders_callback_setext($matches) {
+ // Terrible hack to check we haven't found an empty list item.
+ if ($matches[2] == '-' && preg_match('{^-(?: |$)}', $matches[1])) {
+ return $matches[0];
+ }
+
+ $level = $matches[2]{0} == '=' ? 1 : 2;
+
+ // ID attribute generation
+ $idAtt = $this->_generateIdFromHeaderValue($matches[1]);
+
+ $block = "<h$level$idAtt>".$this->runSpanGamut($matches[1])."</h$level>";
+ return "\n" . $this->hashBlock($block) . "\n\n";
+ }
+
+ /**
+ * ATX header parsing callback
+ * @param array $matches
+ * @return string
+ */
+ protected function _doHeaders_callback_atx($matches) {
+ // ID attribute generation
+ $idAtt = $this->_generateIdFromHeaderValue($matches[2]);
+
+ $level = strlen($matches[1]);
+ $block = "<h$level$idAtt>".$this->runSpanGamut($matches[2])."</h$level>";
+ return "\n" . $this->hashBlock($block) . "\n\n";
+ }
+
+ /**
+ * If a header_id_func property is set, we can use it to automatically
+ * generate an id attribute.
+ *
+ * This method returns a string in the form id="foo", or an empty string
+ * otherwise.
+ * @param string $headerValue
+ * @return string
+ */
+ protected function _generateIdFromHeaderValue($headerValue) {
+ if (!is_callable($this->header_id_func)) {
+ return "";
+ }
+
+ $idValue = call_user_func($this->header_id_func, $headerValue);
+ if (!$idValue) {
+ return "";
+ }
+
+ return ' id="' . $this->encodeAttribute($idValue) . '"';
+ }
+
+ /**
+ * Form HTML ordered (numbered) and unordered (bulleted) lists.
+ * @param string $text
+ * @return string
+ */
+ protected function doLists($text) {
+ $less_than_tab = $this->tab_width - 1;
+
+ // Re-usable patterns to match list item bullets and number markers:
+ $marker_ul_re = '[*+-]';
+ $marker_ol_re = '\d+[\.]';
+
+ $markers_relist = array(
+ $marker_ul_re => $marker_ol_re,
+ $marker_ol_re => $marker_ul_re,
+ );
+
+ foreach ($markers_relist as $marker_re => $other_marker_re) {
+ // Re-usable pattern to match any entirel ul or ol list:
+ $whole_list_re = '
+ ( # $1 = whole list
+ ( # $2
+ ([ ]{0,'.$less_than_tab.'}) # $3 = number of spaces
+ ('.$marker_re.') # $4 = first list item marker
+ [ ]+
+ )
+ (?s:.+?)
+ ( # $5
+ \z
+ |
+ \n{2,}
+ (?=\S)
+ (?! # Negative lookahead for another list item marker
+ [ ]*
+ '.$marker_re.'[ ]+
+ )
+ |
+ (?= # Lookahead for another kind of list
+ \n
+ \3 # Must have the same indentation
+ '.$other_marker_re.'[ ]+
+ )
+ )
+ )
+ '; // mx
+
+ // We use a different prefix before nested lists than top-level lists.
+ //See extended comment in _ProcessListItems().
+
+ if ($this->list_level) {
+ $text = preg_replace_callback('{
+ ^
+ '.$whole_list_re.'
+ }mx',
+ array($this, '_doLists_callback'), $text);
+ } else {
+ $text = preg_replace_callback('{
+ (?:(?<=\n)\n|\A\n?) # Must eat the newline
+ '.$whole_list_re.'
+ }mx',
+ array($this, '_doLists_callback'), $text);
+ }
+ }
+
+ return $text;
+ }
+
+ /**
+ * List parsing callback
+ * @param array $matches
+ * @return string
+ */
+ protected function _doLists_callback($matches) {
+ // Re-usable patterns to match list item bullets and number markers:
+ $marker_ul_re = '[*+-]';
+ $marker_ol_re = '\d+[\.]';
+ $marker_any_re = "(?:$marker_ul_re|$marker_ol_re)";
+ $marker_ol_start_re = '[0-9]+';
+
+ $list = $matches[1];
+ $list_type = preg_match("/$marker_ul_re/", $matches[4]) ? "ul" : "ol";
+
+ $marker_any_re = ( $list_type == "ul" ? $marker_ul_re : $marker_ol_re );
+
+ $list .= "\n";
+ $result = $this->processListItems($list, $marker_any_re);
+
+ $ol_start = 1;
+ if ($this->enhanced_ordered_list) {
+ // Get the start number for ordered list.
+ if ($list_type == 'ol') {
+ $ol_start_array = array();
+ $ol_start_check = preg_match("/$marker_ol_start_re/", $matches[4], $ol_start_array);
+ if ($ol_start_check){
+ $ol_start = $ol_start_array[0];
+ }
+ }
+ }
+
+ if ($ol_start > 1 && $list_type == 'ol'){
+ $result = $this->hashBlock("<$list_type start=\"$ol_start\">\n" . $result . "</$list_type>");
+ } else {
+ $result = $this->hashBlock("<$list_type>\n" . $result . "</$list_type>");
+ }
+ return "\n". $result ."\n\n";
+ }
+
+ /**
+ * Nesting tracker for list levels
+ * @var integer
+ */
+ protected $list_level = 0;
+
+ /**
+ * Process the contents of a single ordered or unordered list, splitting it
+ * into individual list items.
+ * @param string $list_str
+ * @param string $marker_any_re
+ * @return string
+ */
+ protected function processListItems($list_str, $marker_any_re) {
+ /**
+ * The $this->list_level global keeps track of when we're inside a list.
+ * Each time we enter a list, we increment it; when we leave a list,
+ * we decrement. If it's zero, we're not in a list anymore.
+ *
+ * We do this because when we're not inside a list, we want to treat
+ * something like this:
+ *
+ * I recommend upgrading to version
+ * 8. Oops, now this line is treated
+ * as a sub-list.
+ *
+ * As a single paragraph, despite the fact that the second line starts
+ * with a digit-period-space sequence.
+ *
+ * Whereas when we're inside a list (or sub-list), that line will be
+ * treated as the start of a sub-list. What a kludge, huh? This is
+ * an aspect of Markdown's syntax that's hard to parse perfectly
+ * without resorting to mind-reading. Perhaps the solution is to
+ * change the syntax rules such that sub-lists must start with a
+ * starting cardinal number; e.g. "1." or "a.".
+ */
+ $this->list_level++;
+
+ // Trim trailing blank lines:
+ $list_str = preg_replace("/\n{2,}\\z/", "\n", $list_str);
+
+ $list_str = preg_replace_callback('{
+ (\n)? # leading line = $1
+ (^[ ]*) # leading whitespace = $2
+ ('.$marker_any_re.' # list marker and space = $3
+ (?:[ ]+|(?=\n)) # space only required if item is not empty
+ )
+ ((?s:.*?)) # list item text = $4
+ (?:(\n+(?=\n))|\n) # tailing blank line = $5
+ (?= \n* (\z | \2 ('.$marker_any_re.') (?:[ ]+|(?=\n))))
+ }xm',
+ array($this, '_processListItems_callback'), $list_str);
+
+ $this->list_level--;
+ return $list_str;
+ }
+
+ /**
+ * List item parsing callback
+ * @param array $matches
+ * @return string
+ */
+ protected function _processListItems_callback($matches) {
+ $item = $matches[4];
+ $leading_line =& $matches[1];
+ $leading_space =& $matches[2];
+ $marker_space = $matches[3];
+ $tailing_blank_line =& $matches[5];
+
+ if ($leading_line || $tailing_blank_line ||
+ preg_match('/\n{2,}/', $item))
+ {
+ // Replace marker with the appropriate whitespace indentation
+ $item = $leading_space . str_repeat(' ', strlen($marker_space)) . $item;
+ $item = $this->runBlockGamut($this->outdent($item)."\n");
+ } else {
+ // Recursion for sub-lists:
+ $item = $this->doLists($this->outdent($item));
+ $item = $this->formParagraphs($item, false);
+ }
+
+ return "<li>" . $item . "</li>\n";
+ }
+
+ /**
+ * Process Markdown `<pre><code>` blocks.
+ * @param string $text
+ * @return string
+ */
+ protected function doCodeBlocks($text) {
+ $text = preg_replace_callback('{
+ (?:\n\n|\A\n?)
+ ( # $1 = the code block -- one or more lines, starting with a space/tab
+ (?>
+ [ ]{'.$this->tab_width.'} # Lines must start with a tab or a tab-width of spaces
+ .*\n+
+ )+
+ )
+ ((?=^[ ]{0,'.$this->tab_width.'}\S)|\Z) # Lookahead for non-space at line-start, or end of doc
+ }xm',
+ array($this, '_doCodeBlocks_callback'), $text);
+
+ return $text;
+ }
+
+ /**
+ * Code block parsing callback
+ * @param array $matches
+ * @return string
+ */
+ protected function _doCodeBlocks_callback($matches) {
+ $codeblock = $matches[1];
+
+ $codeblock = $this->outdent($codeblock);
+ if ($this->code_block_content_func) {
+ $codeblock = call_user_func($this->code_block_content_func, $codeblock, "");
+ } else {
+ $codeblock = htmlspecialchars($codeblock, ENT_NOQUOTES);
+ }
+
+ # trim leading newlines and trailing newlines
+ $codeblock = preg_replace('/\A\n+|\n+\z/', '', $codeblock);
+
+ $codeblock = "<pre><code>$codeblock\n</code></pre>";
+ return "\n\n" . $this->hashBlock($codeblock) . "\n\n";
+ }
+
+ /**
+ * Create a code span markup for $code. Called from handleSpanToken.
+ * @param string $code
+ * @return string
+ */
+ protected function makeCodeSpan($code) {
+ if ($this->code_span_content_func) {
+ $code = call_user_func($this->code_span_content_func, $code);
+ } else {
+ $code = htmlspecialchars(trim($code), ENT_NOQUOTES);
+ }
+ return $this->hashPart("<code>$code</code>");
+ }
+
+ /**
+ * Define the emphasis operators with their regex matches
+ * @var array
+ */
+ protected $em_relist = array(
+ '' => '(?:(?<!\*)\*(?!\*)|(?<!_)_(?!_))(?![\.,:;]?\s)',
+ '*' => '(?<![\s*])\*(?!\*)',
+ '_' => '(?<![\s_])_(?!_)',
+ );
+
+ /**
+ * Define the strong operators with their regex matches
+ * @var array
+ */
+ protected $strong_relist = array(
+ '' => '(?:(?<!\*)\*\*(?!\*)|(?<!_)__(?!_))(?![\.,:;]?\s)',
+ '**' => '(?<![\s*])\*\*(?!\*)',
+ '__' => '(?<![\s_])__(?!_)',
+ );
+
+ /**
+ * Define the emphasis + strong operators with their regex matches
+ * @var array
+ */
+ protected $em_strong_relist = array(
+ '' => '(?:(?<!\*)\*\*\*(?!\*)|(?<!_)___(?!_))(?![\.,:;]?\s)',
+ '***' => '(?<![\s*])\*\*\*(?!\*)',
+ '___' => '(?<![\s_])___(?!_)',
+ );
+
+ /**
+ * Container for prepared regular expressions
+ * @var array
+ */
+ protected $em_strong_prepared_relist;
+
+ /**
+ * Prepare regular expressions for searching emphasis tokens in any
+ * context.
+ * @return void
+ */
+ protected function prepareItalicsAndBold() {
+ foreach ($this->em_relist as $em => $em_re) {
+ foreach ($this->strong_relist as $strong => $strong_re) {
+ // Construct list of allowed token expressions.
+ $token_relist = array();
+ if (isset($this->em_strong_relist["$em$strong"])) {
+ $token_relist[] = $this->em_strong_relist["$em$strong"];
+ }
+ $token_relist[] = $em_re;
+ $token_relist[] = $strong_re;
+
+ // Construct master expression from list.
+ $token_re = '{(' . implode('|', $token_relist) . ')}';
+ $this->em_strong_prepared_relist["$em$strong"] = $token_re;
+ }
+ }
+ }
+
+ /**
+ * Convert Markdown italics (emphasis) and bold (strong) to HTML
+ * @param string $text
+ * @return string
+ */
+ protected function doItalicsAndBold($text) {
+ $token_stack = array('');
+ $text_stack = array('');
+ $em = '';
+ $strong = '';
+ $tree_char_em = false;
+
+ while (1) {
+ // Get prepared regular expression for seraching emphasis tokens
+ // in current context.
+ $token_re = $this->em_strong_prepared_relist["$em$strong"];
+
+ // Each loop iteration search for the next emphasis token.
+ // Each token is then passed to handleSpanToken.
+ $parts = preg_split($token_re, $text, 2, PREG_SPLIT_DELIM_CAPTURE);
+ $text_stack[0] .= $parts[0];
+ $token =& $parts[1];
+ $text =& $parts[2];
+
+ if (empty($token)) {
+ // Reached end of text span: empty stack without emitting.
+ // any more emphasis.
+ while ($token_stack[0]) {
+ $text_stack[1] .= array_shift($token_stack);
+ $text_stack[0] .= array_shift($text_stack);
+ }
+ break;
+ }
+
+ $token_len = strlen($token);
+ if ($tree_char_em) {
+ // Reached closing marker while inside a three-char emphasis.
+ if ($token_len == 3) {
+ // Three-char closing marker, close em and strong.
+ array_shift($token_stack);
+ $span = array_shift($text_stack);
+ $span = $this->runSpanGamut($span);
+ $span = "<strong><em>$span</em></strong>";
+ $text_stack[0] .= $this->hashPart($span);
+ $em = '';
+ $strong = '';
+ } else {
+ // Other closing marker: close one em or strong and
+ // change current token state to match the other
+ $token_stack[0] = str_repeat($token{0}, 3-$token_len);
+ $tag = $token_len == 2 ? "strong" : "em";
+ $span = $text_stack[0];
+ $span = $this->runSpanGamut($span);
+ $span = "<$tag>$span</$tag>";
+ $text_stack[0] = $this->hashPart($span);
+ $$tag = ''; // $$tag stands for $em or $strong
+ }
+ $tree_char_em = false;
+ } else if ($token_len == 3) {
+ if ($em) {
+ // Reached closing marker for both em and strong.
+ // Closing strong marker:
+ for ($i = 0; $i < 2; ++$i) {
+ $shifted_token = array_shift($token_stack);
+ $tag = strlen($shifted_token) == 2 ? "strong" : "em";
+ $span = array_shift($text_stack);
+ $span = $this->runSpanGamut($span);
+ $span = "<$tag>$span</$tag>";
+ $text_stack[0] .= $this->hashPart($span);
+ $$tag = ''; // $$tag stands for $em or $strong
+ }
+ } else {
+ // Reached opening three-char emphasis marker. Push on token
+ // stack; will be handled by the special condition above.
+ $em = $token{0};
+ $strong = "$em$em";
+ array_unshift($token_stack, $token);
+ array_unshift($text_stack, '');
+ $tree_char_em = true;
+ }
+ } else if ($token_len == 2) {
+ if ($strong) {
+ // Unwind any dangling emphasis marker:
+ if (strlen($token_stack[0]) == 1) {
+ $text_stack[1] .= array_shift($token_stack);
+ $text_stack[0] .= array_shift($text_stack);
+ }
+ // Closing strong marker:
+ array_shift($token_stack);
+ $span = array_shift($text_stack);
+ $span = $this->runSpanGamut($span);
+ $span = "<strong>$span</strong>";
+ $text_stack[0] .= $this->hashPart($span);
+ $strong = '';
+ } else {
+ array_unshift($token_stack, $token);
+ array_unshift($text_stack, '');
+ $strong = $token;
+ }
+ } else {
+ // Here $token_len == 1
+ if ($em) {
+ if (strlen($token_stack[0]) == 1) {
+ // Closing emphasis marker:
+ array_shift($token_stack);
+ $span = array_shift($text_stack);
+ $span = $this->runSpanGamut($span);
+ $span = "<em>$span</em>";
+ $text_stack[0] .= $this->hashPart($span);
+ $em = '';
+ } else {
+ $text_stack[0] .= $token;
+ }
+ } else {
+ array_unshift($token_stack, $token);
+ array_unshift($text_stack, '');
+ $em = $token;
+ }
+ }
+ }
+ return $text_stack[0];
+ }
+
+ /**
+ * Parse Markdown blockquotes to HTML
+ * @param string $text
+ * @return string
+ */
+ protected function doBlockQuotes($text) {
+ $text = preg_replace_callback('/
+ ( # Wrap whole match in $1
+ (?>
+ ^[ ]*>[ ]? # ">" at the start of a line
+ .+\n # rest of the first line
+ (.+\n)* # subsequent consecutive lines
+ \n* # blanks
+ )+
+ )
+ /xm',
+ array($this, '_doBlockQuotes_callback'), $text);
+
+ return $text;
+ }
+
+ /**
+ * Blockquote parsing callback
+ * @param array $matches
+ * @return string
+ */
+ protected function _doBlockQuotes_callback($matches) {
+ $bq = $matches[1];
+ // trim one level of quoting - trim whitespace-only lines
+ $bq = preg_replace('/^[ ]*>[ ]?|^[ ]+$/m', '', $bq);
+ $bq = $this->runBlockGamut($bq); // recurse
+
+ $bq = preg_replace('/^/m', " ", $bq);
+ // These leading spaces cause problem with <pre> content,
+ // so we need to fix that:
+ $bq = preg_replace_callback('{(\s*<pre>.+?</pre>)}sx',
+ array($this, '_doBlockQuotes_callback2'), $bq);
+
+ return "\n" . $this->hashBlock("<blockquote>\n$bq\n</blockquote>") . "\n\n";
+ }
+
+ /**
+ * Blockquote parsing callback
+ * @param array $matches
+ * @return string
+ */
+ protected function _doBlockQuotes_callback2($matches) {
+ $pre = $matches[1];
+ $pre = preg_replace('/^ /m', '', $pre);
+ return $pre;
+ }
+
+ /**
+ * Parse paragraphs
+ *
+ * @param string $text String to process in paragraphs
+ * @param boolean $wrap_in_p Whether paragraphs should be wrapped in <p> tags
+ * @return string
+ */
+ protected function formParagraphs($text, $wrap_in_p = true) {
+ // Strip leading and trailing lines:
+ $text = preg_replace('/\A\n+|\n+\z/', '', $text);
+
+ $grafs = preg_split('/\n{2,}/', $text, -1, PREG_SPLIT_NO_EMPTY);
+
+ // Wrap <p> tags and unhashify HTML blocks
+ foreach ($grafs as $key => $value) {
+ if (!preg_match('/^B\x1A[0-9]+B$/', $value)) {
+ // Is a paragraph.
+ $value = $this->runSpanGamut($value);
+ if ($wrap_in_p) {
+ $value = preg_replace('/^([ ]*)/', "<p>", $value);
+ $value .= "</p>";
+ }
+ $grafs[$key] = $this->unhash($value);
+ } else {
+ // Is a block.
+ // Modify elements of @grafs in-place...
+ $graf = $value;
+ $block = $this->html_hashes[$graf];
+ $graf = $block;
+// if (preg_match('{
+// \A
+// ( # $1 = <div> tag
+// <div \s+
+// [^>]*
+// \b
+// markdown\s*=\s* ([\'"]) # $2 = attr quote char
+// 1
+// \2
+// [^>]*
+// >
+// )
+// ( # $3 = contents
+// .*
+// )
+// (</div>) # $4 = closing tag
+// \z
+// }xs', $block, $matches))
+// {
+// list(, $div_open, , $div_content, $div_close) = $matches;
+//
+// // We can't call Markdown(), because that resets the hash;
+// // that initialization code should be pulled into its own sub, though.
+// $div_content = $this->hashHTMLBlocks($div_content);
+//
+// // Run document gamut methods on the content.
+// foreach ($this->document_gamut as $method => $priority) {
+// $div_content = $this->$method($div_content);
+// }
+//
+// $div_open = preg_replace(
+// '{\smarkdown\s*=\s*([\'"]).+?\1}', '', $div_open);
+//
+// $graf = $div_open . "\n" . $div_content . "\n" . $div_close;
+// }
+ $grafs[$key] = $graf;
+ }
+ }
+
+ return implode("\n\n", $grafs);
+ }
+
+ /**
+ * Encode text for a double-quoted HTML attribute. This function
+ * is *not* suitable for attributes enclosed in single quotes.
+ * @param string $text
+ * @return string
+ */
+ protected function encodeAttribute($text) {
+ $text = $this->encodeAmpsAndAngles($text);
+ $text = str_replace('"', '&quot;', $text);
+ return $text;
+ }
+
+ /**
+ * Encode text for a double-quoted HTML attribute containing a URL,
+ * applying the URL filter if set. Also generates the textual
+ * representation for the URL (removing mailto: or tel:) storing it in $text.
+ * This function is *not* suitable for attributes enclosed in single quotes.
+ *
+ * @param string $url
+ * @param string &$text Passed by reference
+ * @return string URL
+ */
+ protected function encodeURLAttribute($url, &$text = null) {
+ if ($this->url_filter_func) {
+ $url = call_user_func($this->url_filter_func, $url);
+ }
+
+ if (preg_match('{^mailto:}i', $url)) {
+ $url = $this->encodeEntityObfuscatedAttribute($url, $text, 7);
+ } else if (preg_match('{^tel:}i', $url)) {
+ $url = $this->encodeAttribute($url);
+ $text = substr($url, 4);
+ } else {
+ $url = $this->encodeAttribute($url);
+ $text = $url;
+ }
+
+ return $url;
+ }
+
+ /**
+ * Smart processing for ampersands and angle brackets that need to
+ * be encoded. Valid character entities are left alone unless the
+ * no-entities mode is set.
+ * @param string $text
+ * @return string
+ */
+ protected function encodeAmpsAndAngles($text) {
+ if ($this->no_entities) {
+ $text = str_replace('&', '&amp;', $text);
+ } else {
+ // Ampersand-encoding based entirely on Nat Irons's Amputator
+ // MT plugin: <http://bumppo.net/projects/amputator/>
+ $text = preg_replace('/&(?!#?[xX]?(?:[0-9a-fA-F]+|\w+);)/',
+ '&amp;', $text);
+ }
+ // Encode remaining <'s
+ $text = str_replace('<', '&lt;', $text);
+
+ return $text;
+ }
+
+ /**
+ * Parse Markdown automatic links to anchor HTML tags
+ * @param string $text
+ * @return string
+ */
+ protected function doAutoLinks($text) {
+ $text = preg_replace_callback('{<((https?|ftp|dict|tel):[^\'">\s]+)>}i',
+ array($this, '_doAutoLinks_url_callback'), $text);
+
+ // Email addresses: <address@domain.foo>
+ $text = preg_replace_callback('{
+ <
+ (?:mailto:)?
+ (
+ (?:
+ [-!#$%&\'*+/=?^_`.{|}~\w\x80-\xFF]+
+ |
+ ".*?"
+ )
+ \@
+ (?:
+ [-a-z0-9\x80-\xFF]+(\.[-a-z0-9\x80-\xFF]+)*\.[a-z]+
+ |
+ \[[\d.a-fA-F:]+\] # IPv4 & IPv6
+ )
+ )
+ >
+ }xi',
+ array($this, '_doAutoLinks_email_callback'), $text);
+
+ return $text;
+ }
+
+ /**
+ * Parse URL callback
+ * @param array $matches
+ * @return string
+ */
+ protected function _doAutoLinks_url_callback($matches) {
+ $url = $this->encodeURLAttribute($matches[1], $text);
+ $link = "<a href=\"$url\">$text</a>";
+ return $this->hashPart($link);
+ }
+
+ /**
+ * Parse email address callback
+ * @param array $matches
+ * @return string
+ */
+ protected function _doAutoLinks_email_callback($matches) {
+ $addr = $matches[1];
+ $url = $this->encodeURLAttribute("mailto:$addr", $text);
+ $link = "<a href=\"$url\">$text</a>";
+ return $this->hashPart($link);
+ }
+
+ /**
+ * Input: some text to obfuscate, e.g. "mailto:foo@example.com"
+ *
+ * Output: the same text but with most characters encoded as either a
+ * decimal or hex entity, in the hopes of foiling most address
+ * harvesting spam bots. E.g.:
+ *
+ * &#109;&#x61;&#105;&#x6c;&#116;&#x6f;&#58;&#x66;o&#111;
+ * &#x40;&#101;&#x78;&#97;&#x6d;&#112;&#x6c;&#101;&#46;&#x63;&#111;
+ * &#x6d;
+ *
+ * Note: the additional output $tail is assigned the same value as the
+ * ouput, minus the number of characters specified by $head_length.
+ *
+ * Based by a filter by Matthew Wickline, posted to BBEdit-Talk.
+ * With some optimizations by Milian Wolff. Forced encoding of HTML
+ * attribute special characters by Allan Odgaard.
+ *
+ * @param string $text
+ * @param string &$tail
+ * @param integer $head_length
+ * @return string
+ */
+ protected function encodeEntityObfuscatedAttribute($text, &$tail = null, $head_length = 0) {
+ if ($text == "") {
+ return $tail = "";
+ }
+
+ $chars = preg_split('/(?<!^)(?!$)/', $text);
+ $seed = (int)abs(crc32($text) / strlen($text)); // Deterministic seed.
+
+ foreach ($chars as $key => $char) {
+ $ord = ord($char);
+ // Ignore non-ascii chars.
+ if ($ord < 128) {
+ $r = ($seed * (1 + $key)) % 100; // Pseudo-random function.
+ // roughly 10% raw, 45% hex, 45% dec
+ // '@' *must* be encoded. I insist.
+ // '"' and '>' have to be encoded inside the attribute
+ if ($r > 90 && strpos('@"&>', $char) === false) {
+ /* do nothing */
+ } else if ($r < 45) {
+ $chars[$key] = '&#x'.dechex($ord).';';
+ } else {
+ $chars[$key] = '&#'.$ord.';';
+ }
+ }
+ }
+
+ $text = implode('', $chars);
+ $tail = $head_length ? implode('', array_slice($chars, $head_length)) : $text;
+
+ return $text;
+ }
+
+ /**
+ * Take the string $str and parse it into tokens, hashing embeded HTML,
+ * escaped characters and handling code spans.
+ * @param string $str
+ * @return string
+ */
+ protected function parseSpan($str) {
+ $output = '';
+
+ $span_re = '{
+ (
+ \\\\'.$this->escape_chars_re.'
+ |
+ (?<![`\\\\])
+ `+ # code span marker
+ '.( $this->no_markup ? '' : '
+ |
+ <!-- .*? --> # comment
+ |
+ <\?.*?\?> | <%.*?%> # processing instruction
+ |
+ <[!$]?[-a-zA-Z0-9:_]+ # regular tags
+ (?>
+ \s
+ (?>[^"\'>]+|"[^"]*"|\'[^\']*\')*
+ )?
+ >
+ |
+ <[-a-zA-Z0-9:_]+\s*/> # xml-style empty tag
+ |
+ </[-a-zA-Z0-9:_]+\s*> # closing tag
+ ').'
+ )
+ }xs';
+
+ while (1) {
+ // Each loop iteration seach for either the next tag, the next
+ // openning code span marker, or the next escaped character.
+ // Each token is then passed to handleSpanToken.
+ $parts = preg_split($span_re, $str, 2, PREG_SPLIT_DELIM_CAPTURE);
+
+ // Create token from text preceding tag.
+ if ($parts[0] != "") {
+ $output .= $parts[0];
+ }
+
+ // Check if we reach the end.
+ if (isset($parts[1])) {
+ $output .= $this->handleSpanToken($parts[1], $parts[2]);
+ $str = $parts[2];
+ } else {
+ break;
+ }
+ }
+
+ return $output;
+ }
+
+ /**
+ * Handle $token provided by parseSpan by determining its nature and
+ * returning the corresponding value that should replace it.
+ * @param string $token
+ * @param string &$str
+ * @return string
+ */
+ protected function handleSpanToken($token, &$str) {
+ switch ($token{0}) {
+ case "\\":
+ return $this->hashPart("&#". ord($token{1}). ";");
+ case "`":
+ // Search for end marker in remaining text.
+ if (preg_match('/^(.*?[^`])'.preg_quote($token).'(?!`)(.*)$/sm',
+ $str, $matches))
+ {
+ $str = $matches[2];
+ $codespan = $this->makeCodeSpan($matches[1]);
+ return $this->hashPart($codespan);
+ }
+ return $token; // Return as text since no ending marker found.
+ default:
+ return $this->hashPart($token);
+ }
+ }
+
+ /**
+ * Remove one level of line-leading tabs or spaces
+ * @param string $text
+ * @return string
+ */
+ protected function outdent($text) {
+ return preg_replace('/^(\t|[ ]{1,' . $this->tab_width . '})/m', '', $text);
+ }
+
+
+ /**
+ * String length function for detab. `_initDetab` will create a function to
+ * handle UTF-8 if the default function does not exist.
+ * @var string
+ */
+ protected $utf8_strlen = 'mb_strlen';
+
+ /**
+ * Replace tabs with the appropriate amount of spaces.
+ *
+ * For each line we separate the line in blocks delemited by tab characters.
+ * Then we reconstruct every line by adding the appropriate number of space
+ * between each blocks.
+ *
+ * @param string $text
+ * @return string
+ */
+ protected function detab($text) {
+ $text = preg_replace_callback('/^.*\t.*$/m',
+ array($this, '_detab_callback'), $text);
+
+ return $text;
+ }
+
+ /**
+ * Replace tabs callback
+ * @param string $matches
+ * @return string
+ */
+ protected function _detab_callback($matches) {
+ $line = $matches[0];
+ $strlen = $this->utf8_strlen; // strlen function for UTF-8.
+
+ // Split in blocks.
+ $blocks = explode("\t", $line);
+ // Add each blocks to the line.
+ $line = $blocks[0];
+ unset($blocks[0]); // Do not add first block twice.
+ foreach ($blocks as $block) {
+ // Calculate amount of space, insert spaces, insert block.
+ $amount = $this->tab_width -
+ $strlen($line, 'UTF-8') % $this->tab_width;
+ $line .= str_repeat(" ", $amount) . $block;
+ }
+ return $line;
+ }
+
+ /**
+ * Check for the availability of the function in the `utf8_strlen` property
+ * (initially `mb_strlen`). If the function is not available, create a
+ * function that will loosely count the number of UTF-8 characters with a
+ * regular expression.
+ * @return void
+ */
+ protected function _initDetab() {
+
+ if (function_exists($this->utf8_strlen)) {
+ return;
+ }
+
+ $this->utf8_strlen = create_function('$text', 'return preg_match_all(
+ "/[\\\\x00-\\\\xBF]|[\\\\xC0-\\\\xFF][\\\\x80-\\\\xBF]*/",
+ $text, $m);');
+ }
+
+ /**
+ * Swap back in all the tags hashed by _HashHTMLBlocks.
+ * @param string $text
+ * @return string
+ */
+ protected function unhash($text) {
+ return preg_replace_callback('/(.)\x1A[0-9]+\1/',
+ array($this, '_unhash_callback'), $text);
+ }
+
+ /**
+ * Unhashing callback
+ * @param array $matches
+ * @return string
+ */
+ protected function _unhash_callback($matches) {
+ return $this->html_hashes[$matches[0]];
+ }
+}
diff --git a/vendor/michelf/php-markdown/Michelf/MarkdownExtra.inc.php b/vendor/michelf/php-markdown/Michelf/MarkdownExtra.inc.php
new file mode 100644
index 000000000..d09bd7a48
--- /dev/null
+++ b/vendor/michelf/php-markdown/Michelf/MarkdownExtra.inc.php
@@ -0,0 +1,11 @@
+<?php
+
+// Use this file if you cannot use class autoloading. It will include all the
+// files needed for the MarkdownExtra parser.
+//
+// Take a look at the PSR-0-compatible class autoloading implementation
+// in the Readme.php file if you want a simple autoloader setup.
+
+require_once dirname(__FILE__) . '/MarkdownInterface.php';
+require_once dirname(__FILE__) . '/Markdown.php';
+require_once dirname(__FILE__) . '/MarkdownExtra.php';
diff --git a/vendor/michelf/php-markdown/Michelf/MarkdownExtra.php b/vendor/michelf/php-markdown/Michelf/MarkdownExtra.php
new file mode 100644
index 000000000..ac6b1b4f2
--- /dev/null
+++ b/vendor/michelf/php-markdown/Michelf/MarkdownExtra.php
@@ -0,0 +1,1785 @@
+<?php
+/**
+ * Markdown Extra - A text-to-HTML conversion tool for web writers
+ *
+ * @package php-markdown
+ * @author Michel Fortin <michel.fortin@michelf.com>
+ * @copyright 2004-2016 Michel Fortin <https://michelf.com/projects/php-markdown/>
+ * @copyright (Original Markdown) 2004-2006 John Gruber <https://daringfireball.net/projects/markdown/>
+ */
+
+namespace Michelf;
+
+/**
+ * Markdown Extra Parser Class
+ */
+class MarkdownExtra extends \Michelf\Markdown {
+ /**
+ * Configuration variables
+ */
+
+ /**
+ * Prefix for footnote ids.
+ * @var string
+ */
+ public $fn_id_prefix = "";
+
+ /**
+ * Optional title attribute for footnote links and backlinks.
+ * @var string
+ */
+ public $fn_link_title = "";
+ public $fn_backlink_title = "";
+
+ /**
+ * Optional class attribute for footnote links and backlinks.
+ * @var string
+ */
+ public $fn_link_class = "footnote-ref";
+ public $fn_backlink_class = "footnote-backref";
+
+ /**
+ * Content to be displayed within footnote backlinks. The default is '↩';
+ * the U+FE0E on the end is a Unicode variant selector used to prevent iOS
+ * from displaying the arrow character as an emoji.
+ * @var string
+ */
+ public $fn_backlink_html = '&#8617;&#xFE0E;';
+
+ /**
+ * Class name for table cell alignment (%% replaced left/center/right)
+ * For instance: 'go-%%' becomes 'go-left' or 'go-right' or 'go-center'
+ * If empty, the align attribute is used instead of a class name.
+ * @var string
+ */
+ public $table_align_class_tmpl = '';
+
+ /**
+ * Optional class prefix for fenced code block.
+ * @var string
+ */
+ public $code_class_prefix = "";
+
+ /**
+ * Class attribute for code blocks goes on the `code` tag;
+ * setting this to true will put attributes on the `pre` tag instead.
+ * @var boolean
+ */
+ public $code_attr_on_pre = false;
+
+ /**
+ * Predefined abbreviations.
+ * @var array
+ */
+ public $predef_abbr = array();
+
+ /**
+ * Parser implementation
+ */
+
+ /**
+ * Constructor function. Initialize the parser object.
+ * @return void
+ */
+ public function __construct() {
+ // Add extra escapable characters before parent constructor
+ // initialize the table.
+ $this->escape_chars .= ':|';
+
+ // Insert extra document, block, and span transformations.
+ // Parent constructor will do the sorting.
+ $this->document_gamut += array(
+ "doFencedCodeBlocks" => 5,
+ "stripFootnotes" => 15,
+ "stripAbbreviations" => 25,
+ "appendFootnotes" => 50,
+ );
+ $this->block_gamut += array(
+ "doFencedCodeBlocks" => 5,
+ "doTables" => 15,
+ "doDefLists" => 45,
+ );
+ $this->span_gamut += array(
+ "doFootnotes" => 5,
+ "doAbbreviations" => 70,
+ );
+
+ $this->enhanced_ordered_list = true;
+ parent::__construct();
+ }
+
+
+ /**
+ * Extra variables used during extra transformations.
+ * @var array
+ */
+ protected $footnotes = array();
+ protected $footnotes_ordered = array();
+ protected $footnotes_ref_count = array();
+ protected $footnotes_numbers = array();
+ protected $abbr_desciptions = array();
+ /** @var @string */
+ protected $abbr_word_re = '';
+
+ /**
+ * Give the current footnote number.
+ * @var integer
+ */
+ protected $footnote_counter = 1;
+
+ /**
+ * Setting up Extra-specific variables.
+ */
+ protected function setup() {
+ parent::setup();
+
+ $this->footnotes = array();
+ $this->footnotes_ordered = array();
+ $this->footnotes_ref_count = array();
+ $this->footnotes_numbers = array();
+ $this->abbr_desciptions = array();
+ $this->abbr_word_re = '';
+ $this->footnote_counter = 1;
+
+ foreach ($this->predef_abbr as $abbr_word => $abbr_desc) {
+ if ($this->abbr_word_re)
+ $this->abbr_word_re .= '|';
+ $this->abbr_word_re .= preg_quote($abbr_word);
+ $this->abbr_desciptions[$abbr_word] = trim($abbr_desc);
+ }
+ }
+
+ /**
+ * Clearing Extra-specific variables.
+ */
+ protected function teardown() {
+ $this->footnotes = array();
+ $this->footnotes_ordered = array();
+ $this->footnotes_ref_count = array();
+ $this->footnotes_numbers = array();
+ $this->abbr_desciptions = array();
+ $this->abbr_word_re = '';
+
+ parent::teardown();
+ }
+
+
+ /**
+ * Extra attribute parser
+ */
+
+ /**
+ * Expression to use to catch attributes (includes the braces)
+ * @var string
+ */
+ protected $id_class_attr_catch_re = '\{((?>[ ]*[#.a-z][-_:a-zA-Z0-9=]+){1,})[ ]*\}';
+
+ /**
+ * Expression to use when parsing in a context when no capture is desired
+ * @var string
+ */
+ protected $id_class_attr_nocatch_re = '\{(?>[ ]*[#.a-z][-_:a-zA-Z0-9=]+){1,}[ ]*\}';
+
+ /**
+ * Parse attributes caught by the $this->id_class_attr_catch_re expression
+ * and return the HTML-formatted list of attributes.
+ *
+ * Currently supported attributes are .class and #id.
+ *
+ * In addition, this method also supports supplying a default Id value,
+ * which will be used to populate the id attribute in case it was not
+ * overridden.
+ * @param string $tag_name
+ * @param string $attr
+ * @param mixed $defaultIdValue
+ * @param array $classes
+ * @return string
+ */
+ protected function doExtraAttributes($tag_name, $attr, $defaultIdValue = null, $classes = array()) {
+ if (empty($attr) && !$defaultIdValue && empty($classes)) return "";
+
+ // Split on components
+ preg_match_all('/[#.a-z][-_:a-zA-Z0-9=]+/', $attr, $matches);
+ $elements = $matches[0];
+
+ // Handle classes and IDs (only first ID taken into account)
+ $attributes = array();
+ $id = false;
+ foreach ($elements as $element) {
+ if ($element{0} == '.') {
+ $classes[] = substr($element, 1);
+ } else if ($element{0} == '#') {
+ if ($id === false) $id = substr($element, 1);
+ } else if (strpos($element, '=') > 0) {
+ $parts = explode('=', $element, 2);
+ $attributes[] = $parts[0] . '="' . $parts[1] . '"';
+ }
+ }
+
+ if (!$id) $id = $defaultIdValue;
+
+ // Compose attributes as string
+ $attr_str = "";
+ if (!empty($id)) {
+ $attr_str .= ' id="'.$this->encodeAttribute($id) .'"';
+ }
+ if (!empty($classes)) {
+ $attr_str .= ' class="'. implode(" ", $classes) . '"';
+ }
+ if (!$this->no_markup && !empty($attributes)) {
+ $attr_str .= ' '.implode(" ", $attributes);
+ }
+ return $attr_str;
+ }
+
+ /**
+ * Strips link definitions from text, stores the URLs and titles in
+ * hash references.
+ * @param string $text
+ * @return string
+ */
+ protected function stripLinkDefinitions($text) {
+ $less_than_tab = $this->tab_width - 1;
+
+ // Link defs are in the form: ^[id]: url "optional title"
+ $text = preg_replace_callback('{
+ ^[ ]{0,'.$less_than_tab.'}\[(.+)\][ ]?: # id = $1
+ [ ]*
+ \n? # maybe *one* newline
+ [ ]*
+ (?:
+ <(.+?)> # url = $2
+ |
+ (\S+?) # url = $3
+ )
+ [ ]*
+ \n? # maybe one newline
+ [ ]*
+ (?:
+ (?<=\s) # lookbehind for whitespace
+ ["(]
+ (.*?) # title = $4
+ [")]
+ [ ]*
+ )? # title is optional
+ (?:[ ]* '.$this->id_class_attr_catch_re.' )? # $5 = extra id & class attr
+ (?:\n+|\Z)
+ }xm',
+ array($this, '_stripLinkDefinitions_callback'),
+ $text);
+ return $text;
+ }
+
+ /**
+ * Strip link definition callback
+ * @param array $matches
+ * @return string
+ */
+ protected function _stripLinkDefinitions_callback($matches) {
+ $link_id = strtolower($matches[1]);
+ $url = $matches[2] == '' ? $matches[3] : $matches[2];
+ $this->urls[$link_id] = $url;
+ $this->titles[$link_id] =& $matches[4];
+ $this->ref_attr[$link_id] = $this->doExtraAttributes("", $dummy =& $matches[5]);
+ return ''; // String that will replace the block
+ }
+
+
+ /**
+ * HTML block parser
+ */
+
+ /**
+ * Tags that are always treated as block tags
+ * @var string
+ */
+ protected $block_tags_re = 'p|div|h[1-6]|blockquote|pre|table|dl|ol|ul|address|form|fieldset|iframe|hr|legend|article|section|nav|aside|hgroup|header|footer|figcaption|figure';
+
+ /**
+ * Tags treated as block tags only if the opening tag is alone on its line
+ * @var string
+ */
+ protected $context_block_tags_re = 'script|noscript|style|ins|del|iframe|object|source|track|param|math|svg|canvas|audio|video';
+
+ /**
+ * Tags where markdown="1" default to span mode:
+ * @var string
+ */
+ protected $contain_span_tags_re = 'p|h[1-6]|li|dd|dt|td|th|legend|address';
+
+ /**
+ * Tags which must not have their contents modified, no matter where
+ * they appear
+ * @var string
+ */
+ protected $clean_tags_re = 'script|style|math|svg';
+
+ /**
+ * Tags that do not need to be closed.
+ * @var string
+ */
+ protected $auto_close_tags_re = 'hr|img|param|source|track';
+
+ /**
+ * Hashify HTML Blocks and "clean tags".
+ *
+ * We only want to do this for block-level HTML tags, such as headers,
+ * lists, and tables. That's because we still want to wrap <p>s around
+ * "paragraphs" that are wrapped in non-block-level tags, such as anchors,
+ * phrase emphasis, and spans. The list of tags we're looking for is
+ * hard-coded.
+ *
+ * This works by calling _HashHTMLBlocks_InMarkdown, which then calls
+ * _HashHTMLBlocks_InHTML when it encounter block tags. When the markdown="1"
+ * attribute is found within a tag, _HashHTMLBlocks_InHTML calls back
+ * _HashHTMLBlocks_InMarkdown to handle the Markdown syntax within the tag.
+ * These two functions are calling each other. It's recursive!
+ * @param string $text
+ * @return string
+ */
+ protected function hashHTMLBlocks($text) {
+ if ($this->no_markup) {
+ return $text;
+ }
+
+ // Call the HTML-in-Markdown hasher.
+ list($text, ) = $this->_hashHTMLBlocks_inMarkdown($text);
+
+ return $text;
+ }
+
+ /**
+ * Parse markdown text, calling _HashHTMLBlocks_InHTML for block tags.
+ *
+ * * $indent is the number of space to be ignored when checking for code
+ * blocks. This is important because if we don't take the indent into
+ * account, something like this (which looks right) won't work as expected:
+ *
+ * <div>
+ * <div markdown="1">
+ * Hello World. <-- Is this a Markdown code block or text?
+ * </div> <-- Is this a Markdown code block or a real tag?
+ * <div>
+ *
+ * If you don't like this, just don't indent the tag on which
+ * you apply the markdown="1" attribute.
+ *
+ * * If $enclosing_tag_re is not empty, stops at the first unmatched closing
+ * tag with that name. Nested tags supported.
+ *
+ * * If $span is true, text inside must treated as span. So any double
+ * newline will be replaced by a single newline so that it does not create
+ * paragraphs.
+ *
+ * Returns an array of that form: ( processed text , remaining text )
+ *
+ * @param string $text
+ * @param integer $indent
+ * @param string $enclosing_tag_re
+ * @param boolean $span
+ * @return array
+ */
+ protected function _hashHTMLBlocks_inMarkdown($text, $indent = 0,
+ $enclosing_tag_re = '', $span = false)
+ {
+
+ if ($text === '') return array('', '');
+
+ // Regex to check for the presense of newlines around a block tag.
+ $newline_before_re = '/(?:^\n?|\n\n)*$/';
+ $newline_after_re =
+ '{
+ ^ # Start of text following the tag.
+ (?>[ ]*<!--.*?-->)? # Optional comment.
+ [ ]*\n # Must be followed by newline.
+ }xs';
+
+ // Regex to match any tag.
+ $block_tag_re =
+ '{
+ ( # $2: Capture whole tag.
+ </? # Any opening or closing tag.
+ (?> # Tag name.
+ ' . $this->block_tags_re . ' |
+ ' . $this->context_block_tags_re . ' |
+ ' . $this->clean_tags_re . ' |
+ (?!\s)'.$enclosing_tag_re . '
+ )
+ (?:
+ (?=[\s"\'/a-zA-Z0-9]) # Allowed characters after tag name.
+ (?>
+ ".*?" | # Double quotes (can contain `>`)
+ \'.*?\' | # Single quotes (can contain `>`)
+ .+? # Anything but quotes and `>`.
+ )*?
+ )?
+ > # End of tag.
+ |
+ <!-- .*? --> # HTML Comment
+ |
+ <\?.*?\?> | <%.*?%> # Processing instruction
+ |
+ <!\[CDATA\[.*?\]\]> # CData Block
+ ' . ( !$span ? ' # If not in span.
+ |
+ # Indented code block
+ (?: ^[ ]*\n | ^ | \n[ ]*\n )
+ [ ]{' . ($indent + 4) . '}[^\n]* \n
+ (?>
+ (?: [ ]{' . ($indent + 4) . '}[^\n]* | [ ]* ) \n
+ )*
+ |
+ # Fenced code block marker
+ (?<= ^ | \n )
+ [ ]{0,' . ($indent + 3) . '}(?:~{3,}|`{3,})
+ [ ]*
+ (?: \.?[-_:a-zA-Z0-9]+ )? # standalone class name
+ [ ]*
+ (?: ' . $this->id_class_attr_nocatch_re . ' )? # extra attributes
+ [ ]*
+ (?= \n )
+ ' : '' ) . ' # End (if not is span).
+ |
+ # Code span marker
+ # Note, this regex needs to go after backtick fenced
+ # code blocks but it should also be kept outside of the
+ # "if not in span" condition adding backticks to the parser
+ `+
+ )
+ }xs';
+
+
+ $depth = 0; // Current depth inside the tag tree.
+ $parsed = ""; // Parsed text that will be returned.
+
+ // Loop through every tag until we find the closing tag of the parent
+ // or loop until reaching the end of text if no parent tag specified.
+ do {
+ // Split the text using the first $tag_match pattern found.
+ // Text before pattern will be first in the array, text after
+ // pattern will be at the end, and between will be any catches made
+ // by the pattern.
+ $parts = preg_split($block_tag_re, $text, 2,
+ PREG_SPLIT_DELIM_CAPTURE);
+
+ // If in Markdown span mode, add a empty-string span-level hash
+ // after each newline to prevent triggering any block element.
+ if ($span) {
+ $void = $this->hashPart("", ':');
+ $newline = "\n$void";
+ $parts[0] = $void . str_replace("\n", $newline, $parts[0]) . $void;
+ }
+
+ $parsed .= $parts[0]; // Text before current tag.
+
+ // If end of $text has been reached. Stop loop.
+ if (count($parts) < 3) {
+ $text = "";
+ break;
+ }
+
+ $tag = $parts[1]; // Tag to handle.
+ $text = $parts[2]; // Remaining text after current tag.
+ $tag_re = preg_quote($tag); // For use in a regular expression.
+
+ // Check for: Fenced code block marker.
+ // Note: need to recheck the whole tag to disambiguate backtick
+ // fences from code spans
+ if (preg_match('{^\n?([ ]{0,' . ($indent + 3) . '})(~{3,}|`{3,})[ ]*(?:\.?[-_:a-zA-Z0-9]+)?[ ]*(?:' . $this->id_class_attr_nocatch_re . ')?[ ]*\n?$}', $tag, $capture)) {
+ // Fenced code block marker: find matching end marker.
+ $fence_indent = strlen($capture[1]); // use captured indent in re
+ $fence_re = $capture[2]; // use captured fence in re
+ if (preg_match('{^(?>.*\n)*?[ ]{' . ($fence_indent) . '}' . $fence_re . '[ ]*(?:\n|$)}', $text,
+ $matches))
+ {
+ // End marker found: pass text unchanged until marker.
+ $parsed .= $tag . $matches[0];
+ $text = substr($text, strlen($matches[0]));
+ }
+ else {
+ // No end marker: just skip it.
+ $parsed .= $tag;
+ }
+ }
+ // Check for: Indented code block.
+ else if ($tag{0} == "\n" || $tag{0} == " ") {
+ // Indented code block: pass it unchanged, will be handled
+ // later.
+ $parsed .= $tag;
+ }
+ // Check for: Code span marker
+ // Note: need to check this after backtick fenced code blocks
+ else if ($tag{0} == "`") {
+ // Find corresponding end marker.
+ $tag_re = preg_quote($tag);
+ if (preg_match('{^(?>.+?|\n(?!\n))*?(?<!`)' . $tag_re . '(?!`)}',
+ $text, $matches))
+ {
+ // End marker found: pass text unchanged until marker.
+ $parsed .= $tag . $matches[0];
+ $text = substr($text, strlen($matches[0]));
+ }
+ else {
+ // Unmatched marker: just skip it.
+ $parsed .= $tag;
+ }
+ }
+ // Check for: Opening Block level tag or
+ // Opening Context Block tag (like ins and del)
+ // used as a block tag (tag is alone on it's line).
+ else if (preg_match('{^<(?:' . $this->block_tags_re . ')\b}', $tag) ||
+ ( preg_match('{^<(?:' . $this->context_block_tags_re . ')\b}', $tag) &&
+ preg_match($newline_before_re, $parsed) &&
+ preg_match($newline_after_re, $text) )
+ )
+ {
+ // Need to parse tag and following text using the HTML parser.
+ list($block_text, $text) =
+ $this->_hashHTMLBlocks_inHTML($tag . $text, "hashBlock", true);
+
+ // Make sure it stays outside of any paragraph by adding newlines.
+ $parsed .= "\n\n$block_text\n\n";
+ }
+ // Check for: Clean tag (like script, math)
+ // HTML Comments, processing instructions.
+ else if (preg_match('{^<(?:' . $this->clean_tags_re . ')\b}', $tag) ||
+ $tag{1} == '!' || $tag{1} == '?')
+ {
+ // Need to parse tag and following text using the HTML parser.
+ // (don't check for markdown attribute)
+ list($block_text, $text) =
+ $this->_hashHTMLBlocks_inHTML($tag . $text, "hashClean", false);
+
+ $parsed .= $block_text;
+ }
+ // Check for: Tag with same name as enclosing tag.
+ else if ($enclosing_tag_re !== '' &&
+ // Same name as enclosing tag.
+ preg_match('{^</?(?:' . $enclosing_tag_re . ')\b}', $tag))
+ {
+ // Increase/decrease nested tag count.
+ if ($tag{1} == '/') $depth--;
+ else if ($tag{strlen($tag)-2} != '/') $depth++;
+
+ if ($depth < 0) {
+ // Going out of parent element. Clean up and break so we
+ // return to the calling function.
+ $text = $tag . $text;
+ break;
+ }
+
+ $parsed .= $tag;
+ }
+ else {
+ $parsed .= $tag;
+ }
+ } while ($depth >= 0);
+
+ return array($parsed, $text);
+ }
+
+ /**
+ * Parse HTML, calling _HashHTMLBlocks_InMarkdown for block tags.
+ *
+ * * Calls $hash_method to convert any blocks.
+ * * Stops when the first opening tag closes.
+ * * $md_attr indicate if the use of the `markdown="1"` attribute is allowed.
+ * (it is not inside clean tags)
+ *
+ * Returns an array of that form: ( processed text , remaining text )
+ * @param string $text
+ * @param string $hash_method
+ * @param string $md_attr
+ * @return array
+ */
+ protected function _hashHTMLBlocks_inHTML($text, $hash_method, $md_attr) {
+ if ($text === '') return array('', '');
+
+ // Regex to match `markdown` attribute inside of a tag.
+ $markdown_attr_re = '
+ {
+ \s* # Eat whitespace before the `markdown` attribute
+ markdown
+ \s*=\s*
+ (?>
+ (["\']) # $1: quote delimiter
+ (.*?) # $2: attribute value
+ \1 # matching delimiter
+ |
+ ([^\s>]*) # $3: unquoted attribute value
+ )
+ () # $4: make $3 always defined (avoid warnings)
+ }xs';
+
+ // Regex to match any tag.
+ $tag_re = '{
+ ( # $2: Capture whole tag.
+ </? # Any opening or closing tag.
+ [\w:$]+ # Tag name.
+ (?:
+ (?=[\s"\'/a-zA-Z0-9]) # Allowed characters after tag name.
+ (?>
+ ".*?" | # Double quotes (can contain `>`)
+ \'.*?\' | # Single quotes (can contain `>`)
+ .+? # Anything but quotes and `>`.
+ )*?
+ )?
+ > # End of tag.
+ |
+ <!-- .*? --> # HTML Comment
+ |
+ <\?.*?\?> | <%.*?%> # Processing instruction
+ |
+ <!\[CDATA\[.*?\]\]> # CData Block
+ )
+ }xs';
+
+ $original_text = $text; // Save original text in case of faliure.
+
+ $depth = 0; // Current depth inside the tag tree.
+ $block_text = ""; // Temporary text holder for current text.
+ $parsed = ""; // Parsed text that will be returned.
+
+ // Get the name of the starting tag.
+ // (This pattern makes $base_tag_name_re safe without quoting.)
+ if (preg_match('/^<([\w:$]*)\b/', $text, $matches))
+ $base_tag_name_re = $matches[1];
+
+ // Loop through every tag until we find the corresponding closing tag.
+ do {
+ // Split the text using the first $tag_match pattern found.
+ // Text before pattern will be first in the array, text after
+ // pattern will be at the end, and between will be any catches made
+ // by the pattern.
+ $parts = preg_split($tag_re, $text, 2, PREG_SPLIT_DELIM_CAPTURE);
+
+ if (count($parts) < 3) {
+ // End of $text reached with unbalenced tag(s).
+ // In that case, we return original text unchanged and pass the
+ // first character as filtered to prevent an infinite loop in the
+ // parent function.
+ return array($original_text{0}, substr($original_text, 1));
+ }
+
+ $block_text .= $parts[0]; // Text before current tag.
+ $tag = $parts[1]; // Tag to handle.
+ $text = $parts[2]; // Remaining text after current tag.
+
+ // Check for: Auto-close tag (like <hr/>)
+ // Comments and Processing Instructions.
+ if (preg_match('{^</?(?:' . $this->auto_close_tags_re . ')\b}', $tag) ||
+ $tag{1} == '!' || $tag{1} == '?')
+ {
+ // Just add the tag to the block as if it was text.
+ $block_text .= $tag;
+ }
+ else {
+ // Increase/decrease nested tag count. Only do so if
+ // the tag's name match base tag's.
+ if (preg_match('{^</?' . $base_tag_name_re . '\b}', $tag)) {
+ if ($tag{1} == '/') $depth--;
+ else if ($tag{strlen($tag)-2} != '/') $depth++;
+ }
+
+ // Check for `markdown="1"` attribute and handle it.
+ if ($md_attr &&
+ preg_match($markdown_attr_re, $tag, $attr_m) &&
+ preg_match('/^1|block|span$/', $attr_m[2] . $attr_m[3]))
+ {
+ // Remove `markdown` attribute from opening tag.
+ $tag = preg_replace($markdown_attr_re, '', $tag);
+
+ // Check if text inside this tag must be parsed in span mode.
+ $this->mode = $attr_m[2] . $attr_m[3];
+ $span_mode = $this->mode == 'span' || $this->mode != 'block' &&
+ preg_match('{^<(?:' . $this->contain_span_tags_re . ')\b}', $tag);
+
+ // Calculate indent before tag.
+ if (preg_match('/(?:^|\n)( *?)(?! ).*?$/', $block_text, $matches)) {
+ $strlen = $this->utf8_strlen;
+ $indent = $strlen($matches[1], 'UTF-8');
+ } else {
+ $indent = 0;
+ }
+
+ // End preceding block with this tag.
+ $block_text .= $tag;
+ $parsed .= $this->$hash_method($block_text);
+
+ // Get enclosing tag name for the ParseMarkdown function.
+ // (This pattern makes $tag_name_re safe without quoting.)
+ preg_match('/^<([\w:$]*)\b/', $tag, $matches);
+ $tag_name_re = $matches[1];
+
+ // Parse the content using the HTML-in-Markdown parser.
+ list ($block_text, $text)
+ = $this->_hashHTMLBlocks_inMarkdown($text, $indent,
+ $tag_name_re, $span_mode);
+
+ // Outdent markdown text.
+ if ($indent > 0) {
+ $block_text = preg_replace("/^[ ]{1,$indent}/m", "",
+ $block_text);
+ }
+
+ // Append tag content to parsed text.
+ if (!$span_mode) $parsed .= "\n\n$block_text\n\n";
+ else $parsed .= "$block_text";
+
+ // Start over with a new block.
+ $block_text = "";
+ }
+ else $block_text .= $tag;
+ }
+
+ } while ($depth > 0);
+
+ // Hash last block text that wasn't processed inside the loop.
+ $parsed .= $this->$hash_method($block_text);
+
+ return array($parsed, $text);
+ }
+
+ /**
+ * Called whenever a tag must be hashed when a function inserts a "clean" tag
+ * in $text, it passes through this function and is automaticaly escaped,
+ * blocking invalid nested overlap.
+ * @param string $text
+ * @return string
+ */
+ protected function hashClean($text) {
+ return $this->hashPart($text, 'C');
+ }
+
+ /**
+ * Turn Markdown link shortcuts into XHTML <a> tags.
+ * @param string $text
+ * @return string
+ */
+ protected function doAnchors($text) {
+ if ($this->in_anchor) {
+ return $text;
+ }
+ $this->in_anchor = true;
+
+ // First, handle reference-style links: [link text] [id]
+ $text = preg_replace_callback('{
+ ( # wrap whole match in $1
+ \[
+ (' . $this->nested_brackets_re . ') # link text = $2
+ \]
+
+ [ ]? # one optional space
+ (?:\n[ ]*)? # one optional newline followed by spaces
+
+ \[
+ (.*?) # id = $3
+ \]
+ )
+ }xs',
+ array($this, '_doAnchors_reference_callback'), $text);
+
+ // Next, inline-style links: [link text](url "optional title")
+ $text = preg_replace_callback('{
+ ( # wrap whole match in $1
+ \[
+ (' . $this->nested_brackets_re . ') # link text = $2
+ \]
+ \( # literal paren
+ [ \n]*
+ (?:
+ <(.+?)> # href = $3
+ |
+ (' . $this->nested_url_parenthesis_re . ') # href = $4
+ )
+ [ \n]*
+ ( # $5
+ ([\'"]) # quote char = $6
+ (.*?) # Title = $7
+ \6 # matching quote
+ [ \n]* # ignore any spaces/tabs between closing quote and )
+ )? # title is optional
+ \)
+ (?:[ ]? ' . $this->id_class_attr_catch_re . ' )? # $8 = id/class attributes
+ )
+ }xs',
+ array($this, '_doAnchors_inline_callback'), $text);
+
+ // Last, handle reference-style shortcuts: [link text]
+ // These must come last in case you've also got [link text][1]
+ // or [link text](/foo)
+ $text = preg_replace_callback('{
+ ( # wrap whole match in $1
+ \[
+ ([^\[\]]+) # link text = $2; can\'t contain [ or ]
+ \]
+ )
+ }xs',
+ array($this, '_doAnchors_reference_callback'), $text);
+
+ $this->in_anchor = false;
+ return $text;
+ }
+
+ /**
+ * Callback for reference anchors
+ * @param array $matches
+ * @return string
+ */
+ protected function _doAnchors_reference_callback($matches) {
+ $whole_match = $matches[1];
+ $link_text = $matches[2];
+ $link_id =& $matches[3];
+
+ if ($link_id == "") {
+ // for shortcut links like [this][] or [this].
+ $link_id = $link_text;
+ }
+
+ // lower-case and turn embedded newlines into spaces
+ $link_id = strtolower($link_id);
+ $link_id = preg_replace('{[ ]?\n}', ' ', $link_id);
+
+ if (isset($this->urls[$link_id])) {
+ $url = $this->urls[$link_id];
+ $url = $this->encodeURLAttribute($url);
+
+ $result = "<a href=\"$url\"";
+ if ( isset( $this->titles[$link_id] ) ) {
+ $title = $this->titles[$link_id];
+ $title = $this->encodeAttribute($title);
+ $result .= " title=\"$title\"";
+ }
+ if (isset($this->ref_attr[$link_id]))
+ $result .= $this->ref_attr[$link_id];
+
+ $link_text = $this->runSpanGamut($link_text);
+ $result .= ">$link_text</a>";
+ $result = $this->hashPart($result);
+ }
+ else {
+ $result = $whole_match;
+ }
+ return $result;
+ }
+
+ /**
+ * Callback for inline anchors
+ * @param array $matches
+ * @return string
+ */
+ protected function _doAnchors_inline_callback($matches) {
+ $whole_match = $matches[1];
+ $link_text = $this->runSpanGamut($matches[2]);
+ $url = $matches[3] == '' ? $matches[4] : $matches[3];
+ $title =& $matches[7];
+ $attr = $this->doExtraAttributes("a", $dummy =& $matches[8]);
+
+ // if the URL was of the form <s p a c e s> it got caught by the HTML
+ // tag parser and hashed. Need to reverse the process before using the URL.
+ $unhashed = $this->unhash($url);
+ if ($unhashed != $url)
+ $url = preg_replace('/^<(.*)>$/', '\1', $unhashed);
+
+ $url = $this->encodeURLAttribute($url);
+
+ $result = "<a href=\"$url\"";
+ if (isset($title)) {
+ $title = $this->encodeAttribute($title);
+ $result .= " title=\"$title\"";
+ }
+ $result .= $attr;
+
+ $link_text = $this->runSpanGamut($link_text);
+ $result .= ">$link_text</a>";
+
+ return $this->hashPart($result);
+ }
+
+ /**
+ * Turn Markdown image shortcuts into <img> tags.
+ * @param string $text
+ * @return string
+ */
+ protected function doImages($text) {
+ // First, handle reference-style labeled images: ![alt text][id]
+ $text = preg_replace_callback('{
+ ( # wrap whole match in $1
+ !\[
+ (' . $this->nested_brackets_re . ') # alt text = $2
+ \]
+
+ [ ]? # one optional space
+ (?:\n[ ]*)? # one optional newline followed by spaces
+
+ \[
+ (.*?) # id = $3
+ \]
+
+ )
+ }xs',
+ array($this, '_doImages_reference_callback'), $text);
+
+ // Next, handle inline images: ![alt text](url "optional title")
+ // Don't forget: encode * and _
+ $text = preg_replace_callback('{
+ ( # wrap whole match in $1
+ !\[
+ (' . $this->nested_brackets_re . ') # alt text = $2
+ \]
+ \s? # One optional whitespace character
+ \( # literal paren
+ [ \n]*
+ (?:
+ <(\S*)> # src url = $3
+ |
+ (' . $this->nested_url_parenthesis_re . ') # src url = $4
+ )
+ [ \n]*
+ ( # $5
+ ([\'"]) # quote char = $6
+ (.*?) # title = $7
+ \6 # matching quote
+ [ \n]*
+ )? # title is optional
+ \)
+ (?:[ ]? ' . $this->id_class_attr_catch_re . ' )? # $8 = id/class attributes
+ )
+ }xs',
+ array($this, '_doImages_inline_callback'), $text);
+
+ return $text;
+ }
+
+ /**
+ * Callback for referenced images
+ * @param array $matches
+ * @return string
+ */
+ protected function _doImages_reference_callback($matches) {
+ $whole_match = $matches[1];
+ $alt_text = $matches[2];
+ $link_id = strtolower($matches[3]);
+
+ if ($link_id == "") {
+ $link_id = strtolower($alt_text); // for shortcut links like ![this][].
+ }
+
+ $alt_text = $this->encodeAttribute($alt_text);
+ if (isset($this->urls[$link_id])) {
+ $url = $this->encodeURLAttribute($this->urls[$link_id]);
+ $result = "<img src=\"$url\" alt=\"$alt_text\"";
+ if (isset($this->titles[$link_id])) {
+ $title = $this->titles[$link_id];
+ $title = $this->encodeAttribute($title);
+ $result .= " title=\"$title\"";
+ }
+ if (isset($this->ref_attr[$link_id]))
+ $result .= $this->ref_attr[$link_id];
+ $result .= $this->empty_element_suffix;
+ $result = $this->hashPart($result);
+ }
+ else {
+ // If there's no such link ID, leave intact:
+ $result = $whole_match;
+ }
+
+ return $result;
+ }
+
+ /**
+ * Callback for inline images
+ * @param array $matches
+ * @return string
+ */
+ protected function _doImages_inline_callback($matches) {
+ $whole_match = $matches[1];
+ $alt_text = $matches[2];
+ $url = $matches[3] == '' ? $matches[4] : $matches[3];
+ $title =& $matches[7];
+ $attr = $this->doExtraAttributes("img", $dummy =& $matches[8]);
+
+ $alt_text = $this->encodeAttribute($alt_text);
+ $url = $this->encodeURLAttribute($url);
+ $result = "<img src=\"$url\" alt=\"$alt_text\"";
+ if (isset($title)) {
+ $title = $this->encodeAttribute($title);
+ $result .= " title=\"$title\""; // $title already quoted
+ }
+ $result .= $attr;
+ $result .= $this->empty_element_suffix;
+
+ return $this->hashPart($result);
+ }
+
+ /**
+ * Process markdown headers. Redefined to add ID and class attribute support.
+ * @param string $text
+ * @return string
+ */
+ protected function doHeaders($text) {
+ // Setext-style headers:
+ // Header 1 {#header1}
+ // ========
+ //
+ // Header 2 {#header2 .class1 .class2}
+ // --------
+ //
+ $text = preg_replace_callback(
+ '{
+ (^.+?) # $1: Header text
+ (?:[ ]+ ' . $this->id_class_attr_catch_re . ' )? # $3 = id/class attributes
+ [ ]*\n(=+|-+)[ ]*\n+ # $3: Header footer
+ }mx',
+ array($this, '_doHeaders_callback_setext'), $text);
+
+ // atx-style headers:
+ // # Header 1 {#header1}
+ // ## Header 2 {#header2}
+ // ## Header 2 with closing hashes ## {#header3.class1.class2}
+ // ...
+ // ###### Header 6 {.class2}
+ //
+ $text = preg_replace_callback('{
+ ^(\#{1,6}) # $1 = string of #\'s
+ [ ]*
+ (.+?) # $2 = Header text
+ [ ]*
+ \#* # optional closing #\'s (not counted)
+ (?:[ ]+ ' . $this->id_class_attr_catch_re . ' )? # $3 = id/class attributes
+ [ ]*
+ \n+
+ }xm',
+ array($this, '_doHeaders_callback_atx'), $text);
+
+ return $text;
+ }
+
+ /**
+ * Callback for setext headers
+ * @param array $matches
+ * @return string
+ */
+ protected function _doHeaders_callback_setext($matches) {
+ if ($matches[3] == '-' && preg_match('{^- }', $matches[1])) {
+ return $matches[0];
+ }
+
+ $level = $matches[3]{0} == '=' ? 1 : 2;
+
+ $defaultId = is_callable($this->header_id_func) ? call_user_func($this->header_id_func, $matches[1]) : null;
+
+ $attr = $this->doExtraAttributes("h$level", $dummy =& $matches[2], $defaultId);
+ $block = "<h$level$attr>" . $this->runSpanGamut($matches[1]) . "</h$level>";
+ return "\n" . $this->hashBlock($block) . "\n\n";
+ }
+
+ /**
+ * Callback for atx headers
+ * @param array $matches
+ * @return string
+ */
+ protected function _doHeaders_callback_atx($matches) {
+ $level = strlen($matches[1]);
+
+ $defaultId = is_callable($this->header_id_func) ? call_user_func($this->header_id_func, $matches[2]) : null;
+ $attr = $this->doExtraAttributes("h$level", $dummy =& $matches[3], $defaultId);
+ $block = "<h$level$attr>" . $this->runSpanGamut($matches[2]) . "</h$level>";
+ return "\n" . $this->hashBlock($block) . "\n\n";
+ }
+
+ /**
+ * Form HTML tables.
+ * @param string $text
+ * @return string
+ */
+ protected function doTables($text) {
+ $less_than_tab = $this->tab_width - 1;
+ // Find tables with leading pipe.
+ //
+ // | Header 1 | Header 2
+ // | -------- | --------
+ // | Cell 1 | Cell 2
+ // | Cell 3 | Cell 4
+ $text = preg_replace_callback('
+ {
+ ^ # Start of a line
+ [ ]{0,' . $less_than_tab . '} # Allowed whitespace.
+ [|] # Optional leading pipe (present)
+ (.+) \n # $1: Header row (at least one pipe)
+
+ [ ]{0,' . $less_than_tab . '} # Allowed whitespace.
+ [|] ([ ]*[-:]+[-| :]*) \n # $2: Header underline
+
+ ( # $3: Cells
+ (?>
+ [ ]* # Allowed whitespace.
+ [|] .* \n # Row content.
+ )*
+ )
+ (?=\n|\Z) # Stop at final double newline.
+ }xm',
+ array($this, '_doTable_leadingPipe_callback'), $text);
+
+ // Find tables without leading pipe.
+ //
+ // Header 1 | Header 2
+ // -------- | --------
+ // Cell 1 | Cell 2
+ // Cell 3 | Cell 4
+ $text = preg_replace_callback('
+ {
+ ^ # Start of a line
+ [ ]{0,' . $less_than_tab . '} # Allowed whitespace.
+ (\S.*[|].*) \n # $1: Header row (at least one pipe)
+
+ [ ]{0,' . $less_than_tab . '} # Allowed whitespace.
+ ([-:]+[ ]*[|][-| :]*) \n # $2: Header underline
+
+ ( # $3: Cells
+ (?>
+ .* [|] .* \n # Row content
+ )*
+ )
+ (?=\n|\Z) # Stop at final double newline.
+ }xm',
+ array($this, '_DoTable_callback'), $text);
+
+ return $text;
+ }
+
+ /**
+ * Callback for removing the leading pipe for each row
+ * @param array $matches
+ * @return string
+ */
+ protected function _doTable_leadingPipe_callback($matches) {
+ $head = $matches[1];
+ $underline = $matches[2];
+ $content = $matches[3];
+
+ $content = preg_replace('/^ *[|]/m', '', $content);
+
+ return $this->_doTable_callback(array($matches[0], $head, $underline, $content));
+ }
+
+ /**
+ * Make the align attribute in a table
+ * @param string $alignname
+ * @return string
+ */
+ protected function _doTable_makeAlignAttr($alignname)
+ {
+ if (empty($this->table_align_class_tmpl)) {
+ return " align=\"$alignname\"";
+ }
+
+ $classname = str_replace('%%', $alignname, $this->table_align_class_tmpl);
+ return " class=\"$classname\"";
+ }
+
+ /**
+ * Calback for processing tables
+ * @param array $matches
+ * @return string
+ */
+ protected function _doTable_callback($matches) {
+ $head = $matches[1];
+ $underline = $matches[2];
+ $content = $matches[3];
+
+ // Remove any tailing pipes for each line.
+ $head = preg_replace('/[|] *$/m', '', $head);
+ $underline = preg_replace('/[|] *$/m', '', $underline);
+ $content = preg_replace('/[|] *$/m', '', $content);
+
+ // Reading alignement from header underline.
+ $separators = preg_split('/ *[|] */', $underline);
+ foreach ($separators as $n => $s) {
+ if (preg_match('/^ *-+: *$/', $s))
+ $attr[$n] = $this->_doTable_makeAlignAttr('right');
+ else if (preg_match('/^ *:-+: *$/', $s))
+ $attr[$n] = $this->_doTable_makeAlignAttr('center');
+ else if (preg_match('/^ *:-+ *$/', $s))
+ $attr[$n] = $this->_doTable_makeAlignAttr('left');
+ else
+ $attr[$n] = '';
+ }
+
+ // Parsing span elements, including code spans, character escapes,
+ // and inline HTML tags, so that pipes inside those gets ignored.
+ $head = $this->parseSpan($head);
+ $headers = preg_split('/ *[|] */', $head);
+ $col_count = count($headers);
+ $attr = array_pad($attr, $col_count, '');
+
+ // Write column headers.
+ $text = "<table>\n";
+ $text .= "<thead>\n";
+ $text .= "<tr>\n";
+ foreach ($headers as $n => $header)
+ $text .= " <th$attr[$n]>" . $this->runSpanGamut(trim($header)) . "</th>\n";
+ $text .= "</tr>\n";
+ $text .= "</thead>\n";
+
+ // Split content by row.
+ $rows = explode("\n", trim($content, "\n"));
+
+ $text .= "<tbody>\n";
+ foreach ($rows as $row) {
+ // Parsing span elements, including code spans, character escapes,
+ // and inline HTML tags, so that pipes inside those gets ignored.
+ $row = $this->parseSpan($row);
+
+ // Split row by cell.
+ $row_cells = preg_split('/ *[|] */', $row, $col_count);
+ $row_cells = array_pad($row_cells, $col_count, '');
+
+ $text .= "<tr>\n";
+ foreach ($row_cells as $n => $cell)
+ $text .= " <td$attr[$n]>" . $this->runSpanGamut(trim($cell)) . "</td>\n";
+ $text .= "</tr>\n";
+ }
+ $text .= "</tbody>\n";
+ $text .= "</table>";
+
+ return $this->hashBlock($text) . "\n";
+ }
+
+ /**
+ * Form HTML definition lists.
+ * @param string $text
+ * @return string
+ */
+ protected function doDefLists($text) {
+ $less_than_tab = $this->tab_width - 1;
+
+ // Re-usable pattern to match any entire dl list:
+ $whole_list_re = '(?>
+ ( # $1 = whole list
+ ( # $2
+ [ ]{0,' . $less_than_tab . '}
+ ((?>.*\S.*\n)+) # $3 = defined term
+ \n?
+ [ ]{0,' . $less_than_tab . '}:[ ]+ # colon starting definition
+ )
+ (?s:.+?)
+ ( # $4
+ \z
+ |
+ \n{2,}
+ (?=\S)
+ (?! # Negative lookahead for another term
+ [ ]{0,' . $less_than_tab . '}
+ (?: \S.*\n )+? # defined term
+ \n?
+ [ ]{0,' . $less_than_tab . '}:[ ]+ # colon starting definition
+ )
+ (?! # Negative lookahead for another definition
+ [ ]{0,' . $less_than_tab . '}:[ ]+ # colon starting definition
+ )
+ )
+ )
+ )'; // mx
+
+ $text = preg_replace_callback('{
+ (?>\A\n?|(?<=\n\n))
+ ' . $whole_list_re . '
+ }mx',
+ array($this, '_doDefLists_callback'), $text);
+
+ return $text;
+ }
+
+ /**
+ * Callback for processing definition lists
+ * @param array $matches
+ * @return string
+ */
+ protected function _doDefLists_callback($matches) {
+ // Re-usable patterns to match list item bullets and number markers:
+ $list = $matches[1];
+
+ // Turn double returns into triple returns, so that we can make a
+ // paragraph for the last item in a list, if necessary:
+ $result = trim($this->processDefListItems($list));
+ $result = "<dl>\n" . $result . "\n</dl>";
+ return $this->hashBlock($result) . "\n\n";
+ }
+
+ /**
+ * Process the contents of a single definition list, splitting it
+ * into individual term and definition list items.
+ * @param string $list_str
+ * @return string
+ */
+ protected function processDefListItems($list_str) {
+
+ $less_than_tab = $this->tab_width - 1;
+
+ // Trim trailing blank lines:
+ $list_str = preg_replace("/\n{2,}\\z/", "\n", $list_str);
+
+ // Process definition terms.
+ $list_str = preg_replace_callback('{
+ (?>\A\n?|\n\n+) # leading line
+ ( # definition terms = $1
+ [ ]{0,' . $less_than_tab . '} # leading whitespace
+ (?!\:[ ]|[ ]) # negative lookahead for a definition
+ # mark (colon) or more whitespace.
+ (?> \S.* \n)+? # actual term (not whitespace).
+ )
+ (?=\n?[ ]{0,3}:[ ]) # lookahead for following line feed
+ # with a definition mark.
+ }xm',
+ array($this, '_processDefListItems_callback_dt'), $list_str);
+
+ // Process actual definitions.
+ $list_str = preg_replace_callback('{
+ \n(\n+)? # leading line = $1
+ ( # marker space = $2
+ [ ]{0,' . $less_than_tab . '} # whitespace before colon
+ \:[ ]+ # definition mark (colon)
+ )
+ ((?s:.+?)) # definition text = $3
+ (?= \n+ # stop at next definition mark,
+ (?: # next term or end of text
+ [ ]{0,' . $less_than_tab . '} \:[ ] |
+ <dt> | \z
+ )
+ )
+ }xm',
+ array($this, '_processDefListItems_callback_dd'), $list_str);
+
+ return $list_str;
+ }
+
+ /**
+ * Callback for <dt> elements in definition lists
+ * @param array $matches
+ * @return string
+ */
+ protected function _processDefListItems_callback_dt($matches) {
+ $terms = explode("\n", trim($matches[1]));
+ $text = '';
+ foreach ($terms as $term) {
+ $term = $this->runSpanGamut(trim($term));
+ $text .= "\n<dt>" . $term . "</dt>";
+ }
+ return $text . "\n";
+ }
+
+ /**
+ * Callback for <dd> elements in definition lists
+ * @param array $matches
+ * @return string
+ */
+ protected function _processDefListItems_callback_dd($matches) {
+ $leading_line = $matches[1];
+ $marker_space = $matches[2];
+ $def = $matches[3];
+
+ if ($leading_line || preg_match('/\n{2,}/', $def)) {
+ // Replace marker with the appropriate whitespace indentation
+ $def = str_repeat(' ', strlen($marker_space)) . $def;
+ $def = $this->runBlockGamut($this->outdent($def . "\n\n"));
+ $def = "\n". $def ."\n";
+ }
+ else {
+ $def = rtrim($def);
+ $def = $this->runSpanGamut($this->outdent($def));
+ }
+
+ return "\n<dd>" . $def . "</dd>\n";
+ }
+
+ /**
+ * Adding the fenced code block syntax to regular Markdown:
+ *
+ * ~~~
+ * Code block
+ * ~~~
+ *
+ * @param string $text
+ * @return string
+ */
+ protected function doFencedCodeBlocks($text) {
+
+ $less_than_tab = $this->tab_width;
+
+ $text = preg_replace_callback('{
+ (?:\n|\A)
+ # 1: Opening marker
+ (
+ (?:~{3,}|`{3,}) # 3 or more tildes/backticks.
+ )
+ [ ]*
+ (?:
+ \.?([-_:a-zA-Z0-9]+) # 2: standalone class name
+ )?
+ [ ]*
+ (?:
+ ' . $this->id_class_attr_catch_re . ' # 3: Extra attributes
+ )?
+ [ ]* \n # Whitespace and newline following marker.
+
+ # 4: Content
+ (
+ (?>
+ (?!\1 [ ]* \n) # Not a closing marker.
+ .*\n+
+ )+
+ )
+
+ # Closing marker.
+ \1 [ ]* (?= \n )
+ }xm',
+ array($this, '_doFencedCodeBlocks_callback'), $text);
+
+ return $text;
+ }
+
+ /**
+ * Callback to process fenced code blocks
+ * @param array $matches
+ * @return string
+ */
+ protected function _doFencedCodeBlocks_callback($matches) {
+ $classname =& $matches[2];
+ $attrs =& $matches[3];
+ $codeblock = $matches[4];
+
+ if ($this->code_block_content_func) {
+ $codeblock = call_user_func($this->code_block_content_func, $codeblock, $classname);
+ } else {
+ $codeblock = htmlspecialchars($codeblock, ENT_NOQUOTES);
+ }
+
+ $codeblock = preg_replace_callback('/^\n+/',
+ array($this, '_doFencedCodeBlocks_newlines'), $codeblock);
+
+ $classes = array();
+ if ($classname != "") {
+ if ($classname{0} == '.')
+ $classname = substr($classname, 1);
+ $classes[] = $this->code_class_prefix . $classname;
+ }
+ $attr_str = $this->doExtraAttributes($this->code_attr_on_pre ? "pre" : "code", $attrs, null, $classes);
+ $pre_attr_str = $this->code_attr_on_pre ? $attr_str : '';
+ $code_attr_str = $this->code_attr_on_pre ? '' : $attr_str;
+ $codeblock = "<pre$pre_attr_str><code$code_attr_str>$codeblock</code></pre>";
+
+ return "\n\n".$this->hashBlock($codeblock)."\n\n";
+ }
+
+ /**
+ * Replace new lines in fenced code blocks
+ * @param array $matches
+ * @return string
+ */
+ protected function _doFencedCodeBlocks_newlines($matches) {
+ return str_repeat("<br$this->empty_element_suffix",
+ strlen($matches[0]));
+ }
+
+ /**
+ * Redefining emphasis markers so that emphasis by underscore does not
+ * work in the middle of a word.
+ * @var array
+ */
+ protected $em_relist = array(
+ '' => '(?:(?<!\*)\*(?!\*)|(?<![a-zA-Z0-9_])_(?!_))(?![\.,:;]?\s)',
+ '*' => '(?<![\s*])\*(?!\*)',
+ '_' => '(?<![\s_])_(?![a-zA-Z0-9_])',
+ );
+ protected $strong_relist = array(
+ '' => '(?:(?<!\*)\*\*(?!\*)|(?<![a-zA-Z0-9_])__(?!_))(?![\.,:;]?\s)',
+ '**' => '(?<![\s*])\*\*(?!\*)',
+ '__' => '(?<![\s_])__(?![a-zA-Z0-9_])',
+ );
+ protected $em_strong_relist = array(
+ '' => '(?:(?<!\*)\*\*\*(?!\*)|(?<![a-zA-Z0-9_])___(?!_))(?![\.,:;]?\s)',
+ '***' => '(?<![\s*])\*\*\*(?!\*)',
+ '___' => '(?<![\s_])___(?![a-zA-Z0-9_])',
+ );
+
+ /**
+ * Parse text into paragraphs
+ * @param string $text String to process in paragraphs
+ * @param boolean $wrap_in_p Whether paragraphs should be wrapped in <p> tags
+ * @return string HTML output
+ */
+ protected function formParagraphs($text, $wrap_in_p = true) {
+ // Strip leading and trailing lines:
+ $text = preg_replace('/\A\n+|\n+\z/', '', $text);
+
+ $grafs = preg_split('/\n{2,}/', $text, -1, PREG_SPLIT_NO_EMPTY);
+
+ // Wrap <p> tags and unhashify HTML blocks
+ foreach ($grafs as $key => $value) {
+ $value = trim($this->runSpanGamut($value));
+
+ // Check if this should be enclosed in a paragraph.
+ // Clean tag hashes & block tag hashes are left alone.
+ $is_p = $wrap_in_p && !preg_match('/^B\x1A[0-9]+B|^C\x1A[0-9]+C$/', $value);
+
+ if ($is_p) {
+ $value = "<p>$value</p>";
+ }
+ $grafs[$key] = $value;
+ }
+
+ // Join grafs in one text, then unhash HTML tags.
+ $text = implode("\n\n", $grafs);
+
+ // Finish by removing any tag hashes still present in $text.
+ $text = $this->unhash($text);
+
+ return $text;
+ }
+
+
+ /**
+ * Footnotes - Strips link definitions from text, stores the URLs and
+ * titles in hash references.
+ * @param string $text
+ * @return string
+ */
+ protected function stripFootnotes($text) {
+ $less_than_tab = $this->tab_width - 1;
+
+ // Link defs are in the form: [^id]: url "optional title"
+ $text = preg_replace_callback('{
+ ^[ ]{0,' . $less_than_tab . '}\[\^(.+?)\][ ]?: # note_id = $1
+ [ ]*
+ \n? # maybe *one* newline
+ ( # text = $2 (no blank lines allowed)
+ (?:
+ .+ # actual text
+ |
+ \n # newlines but
+ (?!\[.+?\][ ]?:\s)# negative lookahead for footnote or link definition marker.
+ (?!\n+[ ]{0,3}\S)# ensure line is not blank and followed
+ # by non-indented content
+ )*
+ )
+ }xm',
+ array($this, '_stripFootnotes_callback'),
+ $text);
+ return $text;
+ }
+
+ /**
+ * Callback for stripping footnotes
+ * @param array $matches
+ * @return string
+ */
+ protected function _stripFootnotes_callback($matches) {
+ $note_id = $this->fn_id_prefix . $matches[1];
+ $this->footnotes[$note_id] = $this->outdent($matches[2]);
+ return ''; // String that will replace the block
+ }
+
+ /**
+ * Replace footnote references in $text [^id] with a special text-token
+ * which will be replaced by the actual footnote marker in appendFootnotes.
+ * @param string $text
+ * @return string
+ */
+ protected function doFootnotes($text) {
+ if (!$this->in_anchor) {
+ $text = preg_replace('{\[\^(.+?)\]}', "F\x1Afn:\\1\x1A:", $text);
+ }
+ return $text;
+ }
+
+ /**
+ * Append footnote list to text
+ * @param string $text
+ * @return string
+ */
+ protected function appendFootnotes($text) {
+ $text = preg_replace_callback('{F\x1Afn:(.*?)\x1A:}',
+ array($this, '_appendFootnotes_callback'), $text);
+
+ if (!empty($this->footnotes_ordered)) {
+ $text .= "\n\n";
+ $text .= "<div class=\"footnotes\">\n";
+ $text .= "<hr" . $this->empty_element_suffix . "\n";
+ $text .= "<ol>\n\n";
+
+ $attr = "";
+ if ($this->fn_backlink_class != "") {
+ $class = $this->fn_backlink_class;
+ $class = $this->encodeAttribute($class);
+ $attr .= " class=\"$class\"";
+ }
+ if ($this->fn_backlink_title != "") {
+ $title = $this->fn_backlink_title;
+ $title = $this->encodeAttribute($title);
+ $attr .= " title=\"$title\"";
+ }
+ $backlink_text = $this->fn_backlink_html;
+ $num = 0;
+
+ while (!empty($this->footnotes_ordered)) {
+ $footnote = reset($this->footnotes_ordered);
+ $note_id = key($this->footnotes_ordered);
+ unset($this->footnotes_ordered[$note_id]);
+ $ref_count = $this->footnotes_ref_count[$note_id];
+ unset($this->footnotes_ref_count[$note_id]);
+ unset($this->footnotes[$note_id]);
+
+ $footnote .= "\n"; // Need to append newline before parsing.
+ $footnote = $this->runBlockGamut("$footnote\n");
+ $footnote = preg_replace_callback('{F\x1Afn:(.*?)\x1A:}',
+ array($this, '_appendFootnotes_callback'), $footnote);
+
+ $attr = str_replace("%%", ++$num, $attr);
+ $note_id = $this->encodeAttribute($note_id);
+
+ // Prepare backlink, multiple backlinks if multiple references
+ $backlink = "<a href=\"#fnref:$note_id\"$attr>$backlink_text</a>";
+ for ($ref_num = 2; $ref_num <= $ref_count; ++$ref_num) {
+ $backlink .= " <a href=\"#fnref$ref_num:$note_id\"$attr>$backlink_text</a>";
+ }
+ // Add backlink to last paragraph; create new paragraph if needed.
+ if (preg_match('{</p>$}', $footnote)) {
+ $footnote = substr($footnote, 0, -4) . "&#160;$backlink</p>";
+ } else {
+ $footnote .= "\n\n<p>$backlink</p>";
+ }
+
+ $text .= "<li id=\"fn:$note_id\">\n";
+ $text .= $footnote . "\n";
+ $text .= "</li>\n\n";
+ }
+
+ $text .= "</ol>\n";
+ $text .= "</div>";
+ }
+ return $text;
+ }
+
+ /**
+ * Callback for appending footnotes
+ * @param array $matches
+ * @return string
+ */
+ protected function _appendFootnotes_callback($matches) {
+ $node_id = $this->fn_id_prefix . $matches[1];
+
+ // Create footnote marker only if it has a corresponding footnote *and*
+ // the footnote hasn't been used by another marker.
+ if (isset($this->footnotes[$node_id])) {
+ $num =& $this->footnotes_numbers[$node_id];
+ if (!isset($num)) {
+ // Transfer footnote content to the ordered list and give it its
+ // number
+ $this->footnotes_ordered[$node_id] = $this->footnotes[$node_id];
+ $this->footnotes_ref_count[$node_id] = 1;
+ $num = $this->footnote_counter++;
+ $ref_count_mark = '';
+ } else {
+ $ref_count_mark = $this->footnotes_ref_count[$node_id] += 1;
+ }
+
+ $attr = "";
+ if ($this->fn_link_class != "") {
+ $class = $this->fn_link_class;
+ $class = $this->encodeAttribute($class);
+ $attr .= " class=\"$class\"";
+ }
+ if ($this->fn_link_title != "") {
+ $title = $this->fn_link_title;
+ $title = $this->encodeAttribute($title);
+ $attr .= " title=\"$title\"";
+ }
+
+ $attr = str_replace("%%", $num, $attr);
+ $node_id = $this->encodeAttribute($node_id);
+
+ return
+ "<sup id=\"fnref$ref_count_mark:$node_id\">".
+ "<a href=\"#fn:$node_id\"$attr>$num</a>".
+ "</sup>";
+ }
+
+ return "[^" . $matches[1] . "]";
+ }
+
+
+ /**
+ * Abbreviations - strips abbreviations from text, stores titles in hash
+ * references.
+ * @param string $text
+ * @return string
+ */
+ protected function stripAbbreviations($text) {
+ $less_than_tab = $this->tab_width - 1;
+
+ // Link defs are in the form: [id]*: url "optional title"
+ $text = preg_replace_callback('{
+ ^[ ]{0,' . $less_than_tab . '}\*\[(.+?)\][ ]?: # abbr_id = $1
+ (.*) # text = $2 (no blank lines allowed)
+ }xm',
+ array($this, '_stripAbbreviations_callback'),
+ $text);
+ return $text;
+ }
+
+ /**
+ * Callback for stripping abbreviations
+ * @param array $matches
+ * @return string
+ */
+ protected function _stripAbbreviations_callback($matches) {
+ $abbr_word = $matches[1];
+ $abbr_desc = $matches[2];
+ if ($this->abbr_word_re) {
+ $this->abbr_word_re .= '|';
+ }
+ $this->abbr_word_re .= preg_quote($abbr_word);
+ $this->abbr_desciptions[$abbr_word] = trim($abbr_desc);
+ return ''; // String that will replace the block
+ }
+
+ /**
+ * Find defined abbreviations in text and wrap them in <abbr> elements.
+ * @param string $text
+ * @return string
+ */
+ protected function doAbbreviations($text) {
+ if ($this->abbr_word_re) {
+ // cannot use the /x modifier because abbr_word_re may
+ // contain significant spaces:
+ $text = preg_replace_callback('{' .
+ '(?<![\w\x1A])' .
+ '(?:' . $this->abbr_word_re . ')' .
+ '(?![\w\x1A])' .
+ '}',
+ array($this, '_doAbbreviations_callback'), $text);
+ }
+ return $text;
+ }
+
+ /**
+ * Callback for processing abbreviations
+ * @param array $matches
+ * @return string
+ */
+ protected function _doAbbreviations_callback($matches) {
+ $abbr = $matches[0];
+ if (isset($this->abbr_desciptions[$abbr])) {
+ $desc = $this->abbr_desciptions[$abbr];
+ if (empty($desc)) {
+ return $this->hashPart("<abbr>$abbr</abbr>");
+ } else {
+ $desc = $this->encodeAttribute($desc);
+ return $this->hashPart("<abbr title=\"$desc\">$abbr</abbr>");
+ }
+ } else {
+ return $matches[0];
+ }
+ }
+}
diff --git a/vendor/michelf/php-markdown/Michelf/MarkdownInterface.inc.php b/vendor/michelf/php-markdown/Michelf/MarkdownInterface.inc.php
new file mode 100644
index 000000000..c4e9ac7f6
--- /dev/null
+++ b/vendor/michelf/php-markdown/Michelf/MarkdownInterface.inc.php
@@ -0,0 +1,9 @@
+<?php
+
+// Use this file if you cannot use class autoloading. It will include all the
+// files needed for the MarkdownInterface interface.
+//
+// Take a look at the PSR-0-compatible class autoloading implementation
+// in the Readme.php file if you want a simple autoloader setup.
+
+require_once dirname(__FILE__) . '/MarkdownInterface.php';
diff --git a/vendor/michelf/php-markdown/Michelf/MarkdownInterface.php b/vendor/michelf/php-markdown/Michelf/MarkdownInterface.php
new file mode 100644
index 000000000..8512e3753
--- /dev/null
+++ b/vendor/michelf/php-markdown/Michelf/MarkdownInterface.php
@@ -0,0 +1,38 @@
+<?php
+/**
+ * Markdown - A text-to-HTML conversion tool for web writers
+ *
+ * @package php-markdown
+ * @author Michel Fortin <michel.fortin@michelf.com>
+ * @copyright 2004-2016 Michel Fortin <https://michelf.com/projects/php-markdown/>
+ * @copyright (Original Markdown) 2004-2006 John Gruber <https://daringfireball.net/projects/markdown/>
+ */
+
+namespace Michelf;
+
+/**
+ * Markdown Parser Interface
+ */
+interface MarkdownInterface {
+ /**
+ * Initialize the parser and return the result of its transform method.
+ * This will work fine for derived classes too.
+ *
+ * @api
+ *
+ * @param string $text
+ * @return string
+ */
+ public static function defaultTransform($text);
+
+ /**
+ * Main function. Performs some preprocessing on the input text
+ * and pass it through the document gamut.
+ *
+ * @api
+ *
+ * @param string $text
+ * @return string
+ */
+ public function transform($text);
+}
diff --git a/vendor/michelf/php-markdown/Readme.md b/vendor/michelf/php-markdown/Readme.md
new file mode 100644
index 000000000..044407106
--- /dev/null
+++ b/vendor/michelf/php-markdown/Readme.md
@@ -0,0 +1,384 @@
+PHP Markdown
+============
+
+PHP Markdown Lib 1.7.0 - 29 Oct 2016
+
+by Michel Fortin
+<https://michelf.ca/>
+
+based on Markdown by John Gruber
+<https://daringfireball.net/>
+
+
+Introduction
+------------
+
+This is a library package that includes the PHP Markdown parser and its
+sibling PHP Markdown Extra with additional features.
+
+Markdown is a text-to-HTML conversion tool for web writers. Markdown
+allows you to write using an easy-to-read, easy-to-write plain text
+format, then convert it to structurally valid XHTML (or HTML).
+
+"Markdown" is actually two things: a plain text markup syntax, and a
+software tool, originally written in Perl, that converts the plain text
+markup to HTML. PHP Markdown is a port to PHP of the original Markdown
+program by John Gruber.
+
+* [Full documentation of the Markdown syntax](<https://daringfireball.net/projects/markdown/>)
+ — Daring Fireball (John Gruber)
+* [Markdown Extra syntax additions](<https://michelf.ca/projects/php-markdown/extra/>)
+ — Michel Fortin
+
+
+Requirement
+-----------
+
+This library package requires PHP 5.3 or later.
+
+Note: The older plugin/library hybrid package for PHP Markdown and
+PHP Markdown Extra is still maintained and will work with PHP 4.0.5 and later.
+
+Before PHP 5.3.7, pcre.backtrack_limit defaults to 100 000, which is too small
+in many situations. You might need to set it to higher values. Later PHP
+releases defaults to 1 000 000, which is usually fine.
+
+
+Usage
+-----
+
+This library package is meant to be used with class autoloading. For autoloading
+to work, your project needs have setup a PSR-0-compatible autoloader. See the
+included Readme.php file for a minimal autoloader setup. (If you cannot use
+autoloading, see below.)
+
+With class autoloading in place, putting the 'Michelf' folder in your
+include path should be enough for this to work:
+
+ use \Michelf\Markdown;
+ $my_html = Markdown::defaultTransform($my_text);
+
+Markdown Extra syntax is also available the same way:
+
+ use \Michelf\MarkdownExtra;
+ $my_html = MarkdownExtra::defaultTransform($my_text);
+
+If you wish to use PHP Markdown with another text filter function
+built to parse HTML, you should filter the text *after* the `transform`
+function call. This is an example with [PHP SmartyPants][psp]:
+
+ use \Michelf\Markdown, \Michelf\SmartyPants;
+ $my_html = Markdown::defaultTransform($my_text);
+ $my_html = SmartyPants::defaultTransform($my_html);
+
+All these examples are using the static `defaultTransform` static function
+found inside the parser class. If you want to customize the parser
+configuration, you can also instantiate it directly and change some
+configuration variables:
+
+ use \Michelf\MarkdownExtra;
+ $parser = new MarkdownExtra;
+ $parser->fn_id_prefix = "post22-";
+ $my_html = $parser->transform($my_text);
+
+To learn more, see the full list of [configuration variables].
+
+ [configuration variables]: https://michelf.ca/projects/php-markdown/configuration/
+
+
+### Usage without an autoloader
+
+If you cannot use class autoloading, you can still use `include` or `require`
+to access the parser. To load the `\Michelf\Markdown` parser, do it this way:
+
+ require_once 'Michelf/Markdown.inc.php';
+
+Or, if you need the `\Michelf\MarkdownExtra` parser:
+
+ require_once 'Michelf/MarkdownExtra.inc.php';
+
+While the plain `.php` files depend on autoloading to work correctly, using the
+`.inc.php` files instead will eagerly load the dependencies that would be
+loaded on demand if you were using autoloading.
+
+
+Public API and Versioning Policy
+---------------------------------
+
+Version numbers are of the form *major*.*minor*.*patch*.
+
+The public API of PHP Markdown consist of the two parser classes `Markdown`
+and `MarkdownExtra`, their constructors, the `transform` and `defaultTransform`
+functions and their configuration variables. The public API is stable for
+a given major version number. It might get additions when the minor version
+number increments.
+
+**Protected members are not considered public API.** This is unconventional
+and deserves an explanation. Incrementing the major version number every time
+the underlying implementation of something changes is going to give
+nonessential version numbers for the vast majority of people who just use the
+parser. Protected members are meant to create parser subclasses that behave in
+different ways. Very few people create parser subclasses. I don't want to
+discourage it by making everything private, but at the same time I can't
+guarantee any stable hook between versions if you use protected members.
+
+**Syntax changes** will increment the minor number for new features, and the
+patch number for small corrections. A *new feature* is something that needs a
+change in the syntax documentation. Note that since PHP Markdown Lib includes
+two parsers, a syntax change for either of them will increment the minor
+number. Also note that there is nothing perfectly backward-compatible with the
+Markdown syntax: all inputs are always valid, so new features always replace
+something that was previously legal, although generally nonsensical to do.
+
+
+Bugs
+----
+
+To file bug reports please send email to:
+<michel.fortin@michelf.ca>
+
+Please include with your report: (1) the example input; (2) the output you
+expected; (3) the output PHP Markdown actually produced.
+
+If you have a problem where Markdown gives you an empty result, first check
+that the backtrack limit is not too low by running `php --info | grep pcre`.
+See Installation and Requirement above for details.
+
+
+Development and Testing
+-----------------------
+
+Pull requests for fixing bugs are welcome. Proposed new features are
+going to be meticulously reviewed -- taking into account backward compatibility,
+potential side effects, and future extensibility -- before deciding on
+acceptance or rejection.
+
+If you make a pull request that includes changes to the parser please add
+tests for what is being changed to [MDTest][] and make a pull request there
+too.
+
+ [MDTest]: https://github.com/michelf/mdtest/
+
+
+Donations
+---------
+
+If you wish to make a donation that will help me devote more time to
+PHP Markdown, please visit [michelf.ca/donate] or send Bitcoin to
+[1HiuX34czvVPPdhXbUAsAu7pZcesniDCGH].
+
+ [michelf.ca/donate]: https://michelf.ca/donate/#!Thanks%20for%20PHP%20Markdown
+ [1HiuX34czvVPPdhXbUAsAu7pZcesniDCGH]: bitcoin:1HiuX34czvVPPdhXbUAsAu7pZcesniDCGH
+
+
+Version History
+---------------
+
+PHP Markdown Lib 1.7.0 (29 Oct 2016)
+
+* Added a `hard_wrap` configuration variable to make all newline characters
+ in the text become `<br>` tags in the HTML output. By default, according
+ to the standard Markdown syntax these newlines are ignored unless they a
+ preceded by two spaces. Thanks to Jonathan Cohlmeyer for the implementation.
+
+* Improved the parsing of list items to fix problematic cases that came to
+ light with the addition of `hard_wrap`. This should have no effect on the
+ output except span-level list items that ended with two spaces (and thus
+ ended with a line break).
+
+* Added a `code_span_content_func` configuration variable which takes a
+ function that will convert the content of the code span to HTML. This can
+ be useful to implement syntax highlighting. Although contrary to its
+ code block equivalent, there is no syntax for specifying a language.
+ Credits to styxit for the implementation.
+
+* Fixed a Markdwon Extra issue where two-space-at-end-of-line hard breaks
+ wouldn't work inside of HTML block elements such as `<p markdown="1">`
+ where the element expects only span-level content.
+
+* In the parser code, switched to PHPDoc comment format. Thanks to
+ Robbie Averill for the help.
+
+
+PHP Markdown Lib 1.6.0 (23 Dec 2015)
+
+Note: this version was incorrectly released as 1.5.1 on Dec 22, a number
+that contradicted the versioning policy.
+
+* For fenced code blocks in Markdown Extra, can now set a class name for the
+ code block's language before the special attribute block. Previously, this
+ class name was only allowed in the absence of the special attribute block.
+
+* Added a `code_block_content_func` configuration variable which takes a
+ function that will convert the content of the code block to HTML. This is
+ most useful for syntax highlighting. For fenced code blocks in Markdown
+ Extra, the function has access to the language class name (the one outside
+ of the special attribute block). Credits to Mario Konrad for providing the
+ implementation.
+
+* The curled arrow character for the backlink in footnotes is now followed
+ by a Unicode variant selector to prevent it from being displayed in emoji
+ form on iOS.
+
+ Note that in older browsers the variant selector is often interpreted as a
+ separate character, making it visible after the arrow. So there is now a
+ also a `fn_backlink_html` configuration variable that can be used to set
+ the link text to something else. Credits to Dana for providing the
+ implementation.
+
+* Fixed an issue in MarkdownExtra where long header lines followed by a
+ special attribute block would hit the backtrack limit an cause an empty
+ string to be returned.
+
+
+PHP Markdown Lib 1.5.0 (1 Mar 2015)
+
+* Added the ability start ordered lists with a number different from 1 and
+ and have that reflected in the HTML output. This can be enabled with
+ the `enhanced_ordered_lists` configuration variable for the Markdown
+ parser; it is enabled by default for Markdown Extra.
+ Credits to Matt Gorle for providing the implementation.
+
+* Added the ability to insert custom HTML attributes with simple values
+ everywhere an extra attribute block is allowed (links, images, headers).
+ The value must be unquoted, cannot contains spaces and is limited to
+ alphanumeric ASCII characters.
+ Credits to Peter Droogmans for providing the implementation.
+
+* Added a `header_id_func` configuration variable which takes a function
+ that can generate an `id` attribute value from the header text.
+ Credits to Evert Pot for providing the implementation.
+
+* Added a `url_filter_func` configuration variable which takes a function
+ that can rewrite any link or image URL to something different.
+
+
+PHP Markdown Lib 1.4.1 (4 May 2014)
+
+* The HTML block parser will now treat `<figure>` as a block-level element
+ (as it should) and no longer wrap it in `<p>` or parse it's content with
+ the as Markdown syntax (although with Extra you can use `markdown="1"`
+ if you wish to use the Markdown syntax inside it).
+
+* The content of `<style>` elements will now be left alone, its content
+ won't be interpreted as Markdown.
+
+* Corrected an bug where some inline links with spaces in them would not
+ work even when surounded with angle brackets:
+
+ [link](<s p a c e s>)
+
+* Fixed an issue where email addresses with quotes in them would not always
+ have the quotes escaped in the link attribute, causing broken links (and
+ invalid HTML).
+
+* Fixed the case were a link definition following a footnote definition would
+ be swallowed by the footnote unless it was separated by a blank line.
+
+
+PHP Markdown Lib 1.4.0 (29 Nov 2013)
+
+* Added support for the `tel:` URL scheme in automatic links.
+
+ <tel:+1-111-111-1111>
+
+ It gets converted to this (note the `tel:` prefix becomes invisible):
+
+ <a href="tel:+1-111-111-1111">+1-111-111-1111</a>
+
+* Added backtick fenced code blocks to MarkdownExtra, originally from
+ Github-Flavored Markdown.
+
+* Added an interface called MarkdownInterface implemented by both
+ the Markdown and MarkdownExtra parsers. You can use the interface if
+ you want to create a mockup parser object for unit testing.
+
+* For those of you who cannot use class autoloading, you can now
+ include `Michelf/Markdown.inc.php` or `Michelf/MarkdownExtra.inc.php` (note
+ the `.inc.php` extension) to automatically include other files required
+ by the parser.
+
+
+PHP Markdown Lib 1.3 (11 Apr 2013)
+
+This is the first release of PHP Markdown Lib. This package requires PHP
+version 5.3 or later and is designed to work with PSR-0 autoloading and,
+optionally with Composer. Here is a list of the changes since
+PHP Markdown Extra 1.2.6:
+
+* Plugin interface for WordPress and other systems is no longer present in
+ the Lib package. The classic package is still available if you need it:
+ <https://michelf.ca/projects/php-markdown/classic/>
+
+* Added `public` and `protected` protection attributes, plus a section about
+ what is "public API" and what isn't in the Readme file.
+
+* Changed HTML output for footnotes: now instead of adding `rel` and `rev`
+ attributes, footnotes links have the class name `footnote-ref` and
+ backlinks `footnote-backref`.
+
+* Fixed some regular expressions to make PCRE not shout warnings about POSIX
+ collation classes (dependent on your version of PCRE).
+
+* Added optional class and id attributes to images and links using the same
+ syntax as for headers:
+
+ [link](url){#id .class}
+ ![img](url){#id .class}
+
+ It work too for reference-style links and images. In this case you need
+ to put those attributes at the reference definition:
+
+ [link][linkref] or [linkref]
+ ![img][linkref]
+
+ [linkref]: url "optional title" {#id .class}
+
+* Fixed a PHP notice message triggered when some table column separator
+ markers are missing on the separator line below column headers.
+
+* Fixed a small mistake that could cause the parser to retain an invalid
+ state related to parsing links across multiple runs. This was never
+ observed (that I know of), but it's still worth fixing.
+
+
+Copyright and License
+---------------------
+
+PHP Markdown Lib
+Copyright (c) 2004-2016 Michel Fortin
+<https://michelf.ca/>
+All rights reserved.
+
+Based on Markdown
+Copyright (c) 2003-2005 John Gruber
+<https://daringfireball.net/>
+All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+* Redistributions of source code must retain the above copyright
+ notice, this list of conditions and the following disclaimer.
+
+* Redistributions in binary form must reproduce the above copyright
+ notice, this list of conditions and the following disclaimer in the
+ documentation and/or other materials provided with the
+ distribution.
+
+* Neither the name "Markdown" nor the names of its contributors may
+ be used to endorse or promote products derived from this software
+ without specific prior written permission.
+
+This software is provided by the copyright holders and contributors "as
+is" and any express or implied warranties, including, but not limited
+to, the implied warranties of merchantability and fitness for a
+particular purpose are disclaimed. In no event shall the copyright owner
+or contributors be liable for any direct, indirect, incidental, special,
+exemplary, or consequential damages (including, but not limited to,
+procurement of substitute goods or services; loss of use, data, or
+profits; or business interruption) however caused and on any theory of
+liability, whether in contract, strict liability, or tort (including
+negligence or otherwise) arising in any way out of the use of this
+software, even if advised of the possibility of such damage.
diff --git a/vendor/michelf/php-markdown/Readme.php b/vendor/michelf/php-markdown/Readme.php
new file mode 100644
index 000000000..89449dea4
--- /dev/null
+++ b/vendor/michelf/php-markdown/Readme.php
@@ -0,0 +1,31 @@
+<?php
+
+// This file passes the content of the Readme.md file in the same directory
+// through the Markdown filter. You can adapt this sample code in any way
+// you like.
+
+// Install PSR-0-compatible class autoloader
+spl_autoload_register(function($class){
+ require preg_replace('{\\\\|_(?!.*\\\\)}', DIRECTORY_SEPARATOR, ltrim($class, '\\')).'.php';
+});
+
+// Get Markdown class
+use \Michelf\Markdown;
+
+// Read file and pass content through the Markdown parser
+$text = file_get_contents('Readme.md');
+$html = Markdown::defaultTransform($text);
+
+?>
+<!DOCTYPE html>
+<html>
+ <head>
+ <title>PHP Markdown Lib - Readme</title>
+ </head>
+ <body>
+ <?php
+ // Put HTML content in the document
+ echo $html;
+ ?>
+ </body>
+</html>
diff --git a/vendor/michelf/php-markdown/composer.json b/vendor/michelf/php-markdown/composer.json
new file mode 100644
index 000000000..36a4f744a
--- /dev/null
+++ b/vendor/michelf/php-markdown/composer.json
@@ -0,0 +1,31 @@
+{
+ "name": "michelf/php-markdown",
+ "type": "library",
+ "description": "PHP Markdown",
+ "homepage": "https://michelf.ca/projects/php-markdown/",
+ "keywords": ["markdown"],
+ "license": "BSD-3-Clause",
+ "authors": [
+ {
+ "name": "Michel Fortin",
+ "email": "michel.fortin@michelf.ca",
+ "homepage": "https://michelf.ca/",
+ "role": "Developer"
+ },
+ {
+ "name": "John Gruber",
+ "homepage": "https://daringfireball.net/"
+ }
+ ],
+ "require": {
+ "php": ">=5.3.0"
+ },
+ "autoload": {
+ "psr-0": { "Michelf": "" }
+ },
+ "extra": {
+ "branch-alias": {
+ "dev-lib": "1.4.x-dev"
+ }
+ }
+}
diff --git a/vendor/sabre/dav/.travis.yml b/vendor/sabre/dav/.travis.yml
index a9189c981..85637048a 100644
--- a/vendor/sabre/dav/.travis.yml
+++ b/vendor/sabre/dav/.travis.yml
@@ -2,7 +2,9 @@ language: php
php:
- 5.5
- 5.6
- - 7
+ - 7.0
+ - 7.1
+
env:
matrix:
@@ -19,7 +21,6 @@ before_script:
- mysql -e 'create database sabredav_test'
- psql -c "create database sabredav_test" -U postgres
- psql -c "create user sabredav with PASSWORD 'sabredav';GRANT ALL PRIVILEGES ON DATABASE sabredav_test TO sabredav" -U postgres
- - phpenv config-rm xdebug.ini; true
# - composer self-update
- composer update --prefer-dist $LOWEST_DEPS
@@ -28,7 +29,7 @@ before_script:
script:
- ./bin/phpunit --configuration tests/phpunit.xml.dist $TEST_DEPS
- - ./bin/sabre-cs-fixer fix lib/ --dry-run --diff
+ - ./bin/sabre-cs-fixer fix . --dry-run --diff
cache:
directories:
diff --git a/vendor/sabre/dav/CHANGELOG.md b/vendor/sabre/dav/CHANGELOG.md
index d8a3898c3..0bccc995c 100644
--- a/vendor/sabre/dav/CHANGELOG.md
+++ b/vendor/sabre/dav/CHANGELOG.md
@@ -1,6 +1,28 @@
ChangeLog
=========
+3.2.2 (2017-02-14)
+------------------
+
+* #943: Fix CardDAV XML reporting bug, which was affecting several CardDAV
+ clients. Bug was introduced in 3.2.1.
+* The zip release ships with [sabre/vobject 4.1.2][vobj],
+ [sabre/http 4.2.2][http], [sabre/event 3.0.0][evnt],
+ [sabre/uri 1.2.0][uri] and [sabre/xml 1.5.0][xml].
+
+
+3.2.1 (2017-01-28)
+------------------
+
+* #877: Fix for syncing large calendars when using the Sqlite PDO backend.
+ (@theseer).
+* #889 Added support for filtering vCard properties in the addressbook-query
+ REPORT (@DeepDiver1975).
+* The zip release ships with [sabre/vobject 4.1.2][vobj],
+ [sabre/http 4.2.2][http], [sabre/event 3.0.0][evnt],
+ [sabre/uri 1.2.0][uri] and [sabre/xml 1.5.0][xml].
+
+
3.2.0 (2016-06-27)
------------------
@@ -88,6 +110,9 @@ ChangeLog
------------------
* Fixed: Creating a new calendar on some MySQL configurations caused an error.
+* #889 Added support for filtering vCard properties in the addressbook-query
+ REPORT (@DeepDiver1975).
+
3.1.4 (2016-05-28)
@@ -200,6 +225,13 @@ ChangeLog
[sabre/uri 1.0.1][uri] and [sabre/xml 1.1.0][xml].
+3.0.10 (2016-??-??)
+------------------
+
+* #889 Added support for filtering vCard properties in the addressbook-query
+ REPORT (@DeepDiver1975).
+
+
3.0.9 (2016-04-06)
------------------
@@ -463,11 +495,13 @@ ChangeLog
* #193: Fix `Sabre\DAV\FSExt\Directory::getQuotaInfo()` on windows.
-2.1.11 (2016-??-??)
+2.1.11 (2016-10-06)
-------------------
* #805: It wasn't possible to create calendars that hold events, journals and
todos using MySQL, because the `components` column was 1 byte too small.
+* The zip release ships with [sabre/vobject 3.5.3][vobj],
+ [sabre/http 3.0.5][http], and [sabre/event 2.0.2][evnt].
2.1.10 (2016-03-10)
@@ -475,6 +509,8 @@ ChangeLog
* #784: Sync logs for address books were not correctly cleaned up after
deleting them.
+* The zip release ships with [sabre/vobject 3.5.0][vobj],
+ [sabre/http 3.0.5][http], and [sabre/event 2.0.2][evnt].
2.1.9 (2016-01-25)
@@ -627,7 +663,7 @@ ChangeLog
* Added: Automatically converting between vCard 3, 4 and jCard using the
`Accept:` header, in CardDAV reports, and automatically converting from
jCard to vCard upon `PUT`. It's important to note that your backends _may_
- now recieve both vCard 3.0 and 4.0.
+ now receive both vCard 3.0 and 4.0.
* Added: #444. Collections can now opt-in to support high-speed `MOVE`.
* Changed: PropertyStorage backends now have a `move` method.
* Added: `beforeMove`, and `afterMove` events.
@@ -812,7 +848,7 @@ ChangeLog
* Added: Support for the `{DAV:}supported-method-set` property server-wide.
* Making it easier for implementors to override how the CardDAV addressbook
home is located.
-* Fixed: Issue #422 Preconditions were not being set on PUT on non-existant
+* Fixed: Issue #422 Preconditions were not being set on PUT on non-existent
files. Not really a chance for data-loss, but incorrect nevertheless.
* Fixed: Issue #428: Etag check with `If:` fails if the target is a collection.
* Fixed: Issues #430, #431, #433: Locks plugin didn't not properly release
@@ -1024,7 +1060,7 @@ ChangeLog
* Added: Sharee's can now also read out the list of invites for a shared
calendar.
* Added: The Proxy principal classes now both implement an interface, for
- greater flexiblity.
+ greater flexibility.
1.7.13 (2014-07-28)
@@ -1042,7 +1078,7 @@ ChangeLog
Sabre_DAV_PartialUpdate_IFile interface is now deprecated and will be removed
in a future version.
* Fixed: Restoring old setting after changing libxml_disable_entity_loader.
-* Fixed: Issue #422: Preconditions were not being set on PUT on non-existant
+* Fixed: Issue #422: Preconditions were not being set on PUT on non-existent
files. Not really a chance for data-loss, but incorrect nevertheless.
* Fixed: Issue #427: Now checking preconditions on DELETE requests.
* Fixed: Issue #428: Etag check with If: fails if the target is a collection.
@@ -1121,7 +1157,7 @@ ChangeLog
------------------
* The zip release ships with sabre/vobject 2.0.5.
-* Changed: To be compatibile with MS Office 2011 for Mac, a workaround was
+* Changed: To be compatible with MS Office 2011 for Mac, a workaround was
removed that was added to support old versions of Windows XP (pre-SP3).
Indeed! We needed a crazy workaround to work with one MS product in the past,
and we can't keep that workaround to be compatible with another MS product.
@@ -1129,7 +1165,7 @@ ChangeLog
* Fixed: Range requests now work for non-seekable streams. (Thanks Alfred
Klomp).
* Fixed: Changed serialization of {DAV:}getlastmodified and {DAV:}supportedlock
- to improve compatiblity with MS Office 2011 for Mac.
+ to improve compatibility with MS Office 2011 for Mac.
* Changed: reverted the automatic translation of 'DAV:' xml namespaces to
'urn:DAV' when parsing files. Issues were reported with libxml 2.6.32, on a
relatively recent debian release, so we'll wait till 2015 to take this one out
@@ -2006,7 +2042,7 @@ ChangeLog
-------------------
* Fixed: Issue 34: Invalid Lock-Token header response.
-* Added: Issue 35: Addign SabreDAV version to HTTP OPTIONS responses.
+* Added: Issue 35: Adding SabreDAV version to HTTP OPTIONS responses.
1.0.9 (2010-03-19)
@@ -2220,7 +2256,7 @@ ChangeLog
* Added: Simple HTML directory plugin, for browser access.
* Added: Server class now sends back standard pre-condition error xml bodies.
This was new since RFC4918.
-* Added: Sabre_DAV_Tree_Aggregrate, which can 'host' multiple Tree objects into
+* Added: Sabre_DAV_Tree_Aggregate, which can 'host' multiple Tree objects into
one.
* Added: simple basis for HTTP REPORT method. This method is not used yet, but
can be used by plugins to add reports.
@@ -2237,7 +2273,7 @@ ChangeLog
8.2.
* Fixed: TemporaryFileFilter now lets through GET's if they actually exist on
the backend. (r274)
-* FIxed: Some methods didn't get passed through in the FilterTree (r283).
+* Fixed: Some methods didn't get passed through in the FilterTree (r283).
* Fixed: LockManager is now slightly more complex, Tree classes slightly less.
(r287)
diff --git a/vendor/sabre/dav/README.md b/vendor/sabre/dav/README.md
index 8edcd4073..86a0fe9a6 100644
--- a/vendor/sabre/dav/README.md
+++ b/vendor/sabre/dav/README.md
@@ -10,6 +10,7 @@ Full documentation can be found on the website:
http://sabre.io/
+
Build status
------------
@@ -30,6 +31,7 @@ Documentation
* [Introduction](http://sabre.io/dav/).
* [Installation](http://sabre.io/dav/install/).
+
Made at fruux
-------------
diff --git a/vendor/sabre/dav/bin/build.php b/vendor/sabre/dav/bin/build.php
index c4ba20941..c4ba20941 100644..100755
--- a/vendor/sabre/dav/bin/build.php
+++ b/vendor/sabre/dav/bin/build.php
diff --git a/vendor/sabre/dav/bin/googlecode_upload.py b/vendor/sabre/dav/bin/googlecode_upload.py
index caafd5ded..caafd5ded 100644..100755
--- a/vendor/sabre/dav/bin/googlecode_upload.py
+++ b/vendor/sabre/dav/bin/googlecode_upload.py
diff --git a/vendor/sabre/dav/bin/migrateto20.php b/vendor/sabre/dav/bin/migrateto20.php
index 77236804f..77236804f 100644..100755
--- a/vendor/sabre/dav/bin/migrateto20.php
+++ b/vendor/sabre/dav/bin/migrateto20.php
diff --git a/vendor/sabre/dav/bin/migrateto21.php b/vendor/sabre/dav/bin/migrateto21.php
index c81ee5cca..c81ee5cca 100644..100755
--- a/vendor/sabre/dav/bin/migrateto21.php
+++ b/vendor/sabre/dav/bin/migrateto21.php
diff --git a/vendor/sabre/dav/bin/migrateto30.php b/vendor/sabre/dav/bin/migrateto30.php
index 9ca77c13c..9ca77c13c 100644..100755
--- a/vendor/sabre/dav/bin/migrateto30.php
+++ b/vendor/sabre/dav/bin/migrateto30.php
diff --git a/vendor/sabre/dav/bin/migrateto32.php b/vendor/sabre/dav/bin/migrateto32.php
index 7567aeb60..7567aeb60 100644..100755
--- a/vendor/sabre/dav/bin/migrateto32.php
+++ b/vendor/sabre/dav/bin/migrateto32.php
diff --git a/vendor/sabre/dav/bin/sabredav.php b/vendor/sabre/dav/bin/sabredav.php
index 950075d1a..950075d1a 100644..100755
--- a/vendor/sabre/dav/bin/sabredav.php
+++ b/vendor/sabre/dav/bin/sabredav.php
diff --git a/vendor/sabre/dav/composer.json b/vendor/sabre/dav/composer.json
index f85d9655e..fca0e07fb 100644
--- a/vendor/sabre/dav/composer.json
+++ b/vendor/sabre/dav/composer.json
@@ -32,9 +32,9 @@
"psr/log": "^1.0"
},
"require-dev" : {
- "phpunit/phpunit" : "> 4.8, <=6.0.0",
+ "phpunit/phpunit" : "> 4.8, <6.0.0",
"evert/phpdoc-md" : "~0.1.0",
- "sabre/cs" : "~0.0.5",
+ "sabre/cs" : "^1.0.0",
"monolog/monolog": "^1.18"
},
"suggest" : {
diff --git a/vendor/sabre/dav/lib/CalDAV/Backend/AbstractBackend.php b/vendor/sabre/dav/lib/CalDAV/Backend/AbstractBackend.php
index d58b4a46e..311b1c415 100644
--- a/vendor/sabre/dav/lib/CalDAV/Backend/AbstractBackend.php
+++ b/vendor/sabre/dav/lib/CalDAV/Backend/AbstractBackend.php
@@ -2,8 +2,8 @@
namespace Sabre\CalDAV\Backend;
-use Sabre\VObject;
use Sabre\CalDAV;
+use Sabre\VObject;
/**
* Abstract Calendaring backend. Extend this class to create your own backends.
@@ -26,9 +26,9 @@ abstract class AbstractBackend implements BackendInterface {
* Calling the handle method is like telling the PropPatch object "I
* promise I can handle updating this property".
*
- * Read the PropPatch documenation for more info and examples.
+ * Read the PropPatch documentation for more info and examples.
*
- * @param string $path
+ * @param mixed $calendarId
* @param \Sabre\DAV\PropPatch $propPatch
* @return void
*/
diff --git a/vendor/sabre/dav/lib/CalDAV/Backend/NotificationSupport.php b/vendor/sabre/dav/lib/CalDAV/Backend/NotificationSupport.php
index 9c00a89ef..bf2ef27a0 100644
--- a/vendor/sabre/dav/lib/CalDAV/Backend/NotificationSupport.php
+++ b/vendor/sabre/dav/lib/CalDAV/Backend/NotificationSupport.php
@@ -49,8 +49,8 @@ interface NotificationSupport extends BackendInterface {
* If the user chose to accept the share, this method should return the
* newly created calendar url.
*
- * @param string href The sharee who is replying (often a mailto: address)
- * @param int status One of the SharingPlugin::STATUS_* constants
+ * @param string $href The sharee who is replying (often a mailto: address)
+ * @param int $status One of the SharingPlugin::STATUS_* constants
* @param string $calendarUri The url to the calendar thats being shared
* @param string $inReplyTo The unique id this message is a response to
* @param string $summary A description of the reply
diff --git a/vendor/sabre/dav/lib/CalDAV/Backend/PDO.php b/vendor/sabre/dav/lib/CalDAV/Backend/PDO.php
index 95f1d49a6..458440588 100644
--- a/vendor/sabre/dav/lib/CalDAV/Backend/PDO.php
+++ b/vendor/sabre/dav/lib/CalDAV/Backend/PDO.php
@@ -5,8 +5,8 @@ namespace Sabre\CalDAV\Backend;
use Sabre\CalDAV;
use Sabre\DAV;
use Sabre\DAV\Exception\Forbidden;
-use Sabre\VObject;
use Sabre\DAV\Xml\Element\Sharee;
+use Sabre\VObject;
/**
* PDO CalDAV backend
@@ -296,7 +296,7 @@ SQL
* Calling the handle method is like telling the PropPatch object "I
* promise I can handle updating this property".
*
- * Read the PropPatch documenation for more info and examples.
+ * Read the PropPatch documentation for more info and examples.
*
* @param mixed $calendarId
* @param \Sabre\DAV\PropPatch $propPatch
@@ -481,13 +481,13 @@ SQL
if (!$row) return null;
return [
- 'id' => $row['id'],
- 'uri' => $row['uri'],
- 'lastmodified' => (int)$row['lastmodified'],
- 'etag' => '"' . $row['etag'] . '"',
- 'size' => (int)$row['size'],
- 'calendardata' => $row['calendardata'],
- 'component' => strtolower($row['componenttype']),
+ 'id' => $row['id'],
+ 'uri' => $row['uri'],
+ 'lastmodified' => (int)$row['lastmodified'],
+ 'etag' => '"' . $row['etag'] . '"',
+ 'size' => (int)$row['size'],
+ 'calendardata' => $row['calendardata'],
+ 'component' => strtolower($row['componenttype']),
];
}
@@ -511,27 +511,29 @@ SQL
}
list($calendarId, $instanceId) = $calendarId;
- $query = 'SELECT id, uri, lastmodified, etag, calendarid, size, calendardata, componenttype FROM ' . $this->calendarObjectTableName . ' WHERE calendarid = ? AND uri IN (';
- // Inserting a whole bunch of question marks
- $query .= implode(',', array_fill(0, count($uris), '?'));
- $query .= ')';
+ $result = [];
+ foreach (array_chunk($uris, 900) as $chunk) {
+ $query = 'SELECT id, uri, lastmodified, etag, calendarid, size, calendardata, componenttype FROM ' . $this->calendarObjectTableName . ' WHERE calendarid = ? AND uri IN (';
+ // Inserting a whole bunch of question marks
+ $query .= implode(',', array_fill(0, count($chunk), '?'));
+ $query .= ')';
- $stmt = $this->pdo->prepare($query);
- $stmt->execute(array_merge([$calendarId], $uris));
+ $stmt = $this->pdo->prepare($query);
+ $stmt->execute(array_merge([$calendarId], $chunk));
- $result = [];
- while ($row = $stmt->fetch(\PDO::FETCH_ASSOC)) {
+ while ($row = $stmt->fetch(\PDO::FETCH_ASSOC)) {
- $result[] = [
- 'id' => $row['id'],
- 'uri' => $row['uri'],
- 'lastmodified' => (int)$row['lastmodified'],
- 'etag' => '"' . $row['etag'] . '"',
- 'size' => (int)$row['size'],
- 'calendardata' => $row['calendardata'],
- 'component' => strtolower($row['componenttype']),
- ];
+ $result[] = [
+ 'id' => $row['id'],
+ 'uri' => $row['uri'],
+ 'lastmodified' => (int)$row['lastmodified'],
+ 'etag' => '"' . $row['etag'] . '"',
+ 'size' => (int)$row['size'],
+ 'calendardata' => $row['calendardata'],
+ 'component' => strtolower($row['componenttype']),
+ ];
+ }
}
return $result;
@@ -686,7 +688,7 @@ SQL
}
}
-
+
// Ensure Occurence values are positive
if ($firstOccurence < 0) $firstOccurence = 0;
if ($lastOccurence < 0) $lastOccurence = 0;
@@ -769,7 +771,7 @@ SQL
* Note that especially time-range-filters may be difficult to parse. A
* time-range filter specified on a VEVENT must for instance also handle
* recurrence rules correctly.
- * A good example of how to interprete all these filters can also simply
+ * A good example of how to interpret all these filters can also simply
* be found in \Sabre\CalDAV\CalendarQueryFilter. This class is as correct
* as possible, so it gives you a good idea on what type of stuff you need
* to think of.
@@ -969,7 +971,7 @@ SQL;
// Current synctoken
$stmt = $this->pdo->prepare('SELECT synctoken FROM ' . $this->calendarTableName . ' WHERE id = ?');
- $stmt->execute([ $calendarId ]);
+ $stmt->execute([$calendarId]);
$currentToken = $stmt->fetchColumn(0);
if (is_null($currentToken)) return null;
@@ -1181,7 +1183,7 @@ SQL;
* Calling the handle method is like telling the PropPatch object "I
* promise I can handle updating this property".
*
- * Read the PropPatch documenation for more info and examples.
+ * Read the PropPatch documentation for more info and examples.
*
* @param mixed $subscriptionId
* @param \Sabre\DAV\PropPatch $propPatch
@@ -1327,7 +1329,7 @@ SQL;
function createSchedulingObject($principalUri, $objectUri, $objectData) {
$stmt = $this->pdo->prepare('INSERT INTO ' . $this->schedulingObjectTableName . ' (principaluri, calendardata, uri, lastmodified, etag, size) VALUES (?, ?, ?, ?, ?, ?)');
- $stmt->execute([$principalUri, $objectData, $objectUri, time(), md5($objectData), strlen($objectData) ]);
+ $stmt->execute([$principalUri, $objectData, $objectUri, time(), md5($objectData), strlen($objectData)]);
}
@@ -1483,7 +1485,7 @@ SQL;
'inviteStatus' => (int)$row['share_invitestatus'],
'properties' =>
!empty($row['share_displayname'])
- ? [ '{DAV:}displayname' => $row['share_displayname'] ]
+ ? ['{DAV:}displayname' => $row['share_displayname']]
: [],
'principal' => $row['principaluri'],
]);
@@ -1502,7 +1504,7 @@ SQL;
*/
function setPublishStatus($calendarId, $value) {
- throw new \Sabre\DAV\Exception\NotImplemented('Not implemented');
+ throw new DAV\Exception\NotImplemented('Not implemented');
}
diff --git a/vendor/sabre/dav/lib/CalDAV/Backend/SharingSupport.php b/vendor/sabre/dav/lib/CalDAV/Backend/SharingSupport.php
index 8b6e074e0..278ec2564 100644
--- a/vendor/sabre/dav/lib/CalDAV/Backend/SharingSupport.php
+++ b/vendor/sabre/dav/lib/CalDAV/Backend/SharingSupport.php
@@ -11,9 +11,9 @@ namespace Sabre\CalDAV\Backend;
* 1. Return shared calendars for users.
* 2. For every calendar, return calendar-resource-uri. This strings is a URI or
* relative URI reference that must be unique for every calendar, but
- * identical for every instance of the same shared calenar.
- * 3. For every calenar, you must return a share-access element. This element
- * should contain one of the Sabre\DAV\Sharing\Plugin:ACCESS_* contants and
+ * identical for every instance of the same shared calendar.
+ * 3. For every calendar, you must return a share-access element. This element
+ * should contain one of the Sabre\DAV\Sharing\Plugin:ACCESS_* constants and
* indicates the access level the user has.
*
* @copyright Copyright (C) fruux GmbH (https://fruux.com/)
diff --git a/vendor/sabre/dav/lib/CalDAV/Backend/SimplePDO.php b/vendor/sabre/dav/lib/CalDAV/Backend/SimplePDO.php
index f8238ea9a..d21f7f916 100644
--- a/vendor/sabre/dav/lib/CalDAV/Backend/SimplePDO.php
+++ b/vendor/sabre/dav/lib/CalDAV/Backend/SimplePDO.php
@@ -8,7 +8,7 @@ use Sabre\DAV;
/**
* Simple PDO CalDAV backend.
*
- * This class is basically the most minmum example to get a caldav backend up
+ * This class is basically the most minimum example to get a caldav backend up
* and running. This class uses the following schema (MySQL example):
*
* CREATE TABLE simple_calendars (
@@ -209,12 +209,12 @@ class SimplePDO extends AbstractBackend {
if (!$row) return null;
return [
- 'id' => $row['id'],
- 'uri' => $row['uri'],
- 'etag' => '"' . md5($row['calendardata']) . '"',
- 'calendarid' => $calendarId,
- 'size' => strlen($row['calendardata']),
- 'calendardata' => $row['calendardata'],
+ 'id' => $row['id'],
+ 'uri' => $row['uri'],
+ 'etag' => '"' . md5($row['calendardata']) . '"',
+ 'calendarid' => $calendarId,
+ 'size' => strlen($row['calendardata']),
+ 'calendardata' => $row['calendardata'],
];
}
diff --git a/vendor/sabre/dav/lib/CalDAV/Backend/SubscriptionSupport.php b/vendor/sabre/dav/lib/CalDAV/Backend/SubscriptionSupport.php
index a39289f5e..d77a2fe0f 100644
--- a/vendor/sabre/dav/lib/CalDAV/Backend/SubscriptionSupport.php
+++ b/vendor/sabre/dav/lib/CalDAV/Backend/SubscriptionSupport.php
@@ -70,7 +70,7 @@ interface SubscriptionSupport extends BackendInterface {
* Calling the handle method is like telling the PropPatch object "I
* promise I can handle updating this property".
*
- * Read the PropPatch documenation for more info and examples.
+ * Read the PropPatch documentation for more info and examples.
*
* @param mixed $subscriptionId
* @param \Sabre\DAV\PropPatch $propPatch
diff --git a/vendor/sabre/dav/lib/CalDAV/Calendar.php b/vendor/sabre/dav/lib/CalDAV/Calendar.php
index 90ace0d21..7467900cc 100644
--- a/vendor/sabre/dav/lib/CalDAV/Calendar.php
+++ b/vendor/sabre/dav/lib/CalDAV/Calendar.php
@@ -3,8 +3,8 @@
namespace Sabre\CalDAV;
use Sabre\DAV;
-use Sabre\DAVACL;
use Sabre\DAV\PropPatch;
+use Sabre\DAVACL;
/**
* This object represents a CalDAV calendar.
diff --git a/vendor/sabre/dav/lib/CalDAV/CalendarHome.php b/vendor/sabre/dav/lib/CalDAV/CalendarHome.php
index 0a4bfb68f..ffd7f72fb 100644
--- a/vendor/sabre/dav/lib/CalDAV/CalendarHome.php
+++ b/vendor/sabre/dav/lib/CalDAV/CalendarHome.php
@@ -27,7 +27,7 @@ class CalendarHome implements DAV\IExtendedCollection, DAVACL\IACL {
/**
* CalDAV backend
*
- * @var Sabre\CalDAV\Backend\BackendInterface
+ * @var Backend\BackendInterface
*/
protected $caldavBackend;
@@ -42,7 +42,7 @@ class CalendarHome implements DAV\IExtendedCollection, DAVACL\IACL {
* Constructor
*
* @param Backend\BackendInterface $caldavBackend
- * @param mixed $userUri
+ * @param array $principalInfo
*/
function __construct(Backend\BackendInterface $caldavBackend, $principalInfo) {
@@ -334,8 +334,8 @@ class CalendarHome implements DAV\IExtendedCollection, DAVACL\IACL {
* This method should return the url of the newly created calendar if the
* share was accepted.
*
- * @param string href The sharee who is replying (often a mailto: address)
- * @param int status One of the SharingPlugin::STATUS_* constants
+ * @param string $href The sharee who is replying (often a mailto: address)
+ * @param int $status One of the SharingPlugin::STATUS_* constants
* @param string $calendarUri The url to the calendar thats being shared
* @param string $inReplyTo The unique id this message is a response to
* @param string $summary A description of the reply
diff --git a/vendor/sabre/dav/lib/CalDAV/CalendarObject.php b/vendor/sabre/dav/lib/CalDAV/CalendarObject.php
index 001b35112..9d6532a35 100644
--- a/vendor/sabre/dav/lib/CalDAV/CalendarObject.php
+++ b/vendor/sabre/dav/lib/CalDAV/CalendarObject.php
@@ -16,7 +16,7 @@ class CalendarObject extends \Sabre\DAV\File implements ICalendarObject, \Sabre\
/**
* Sabre\CalDAV\Backend\BackendInterface
*
- * @var Sabre\CalDAV\Backend\AbstractBackend
+ * @var Backend\AbstractBackend
*/
protected $caldavBackend;
diff --git a/vendor/sabre/dav/lib/CalDAV/CalendarQueryValidator.php b/vendor/sabre/dav/lib/CalDAV/CalendarQueryValidator.php
index f3c7524d2..df8008fe2 100644
--- a/vendor/sabre/dav/lib/CalDAV/CalendarQueryValidator.php
+++ b/vendor/sabre/dav/lib/CalDAV/CalendarQueryValidator.php
@@ -2,8 +2,8 @@
namespace Sabre\CalDAV;
-use Sabre\VObject;
use DateTime;
+use Sabre\VObject;
/**
* CalendarQuery Validator
@@ -25,7 +25,7 @@ class CalendarQueryValidator {
*
* The list of filters must be formatted as parsed by \Sabre\CalDAV\CalendarQueryParser
*
- * @param VObject\Component $vObject
+ * @param VObject\Component\VCalendar $vObject
* @param array $filters
* @return bool
*/
diff --git a/vendor/sabre/dav/lib/CalDAV/CalendarRoot.php b/vendor/sabre/dav/lib/CalDAV/CalendarRoot.php
index 0ac50e41d..1d6b2ac9f 100644
--- a/vendor/sabre/dav/lib/CalDAV/CalendarRoot.php
+++ b/vendor/sabre/dav/lib/CalDAV/CalendarRoot.php
@@ -22,7 +22,7 @@ class CalendarRoot extends \Sabre\DAVACL\AbstractPrincipalCollection {
/**
* CalDAV backend
*
- * @var Sabre\CalDAV\Backend\BackendInterface
+ * @var Backend\BackendInterface
*/
protected $caldavBackend;
diff --git a/vendor/sabre/dav/lib/CalDAV/Exception/InvalidComponentType.php b/vendor/sabre/dav/lib/CalDAV/Exception/InvalidComponentType.php
index 5ce8a93f5..7aff2edab 100644
--- a/vendor/sabre/dav/lib/CalDAV/Exception/InvalidComponentType.php
+++ b/vendor/sabre/dav/lib/CalDAV/Exception/InvalidComponentType.php
@@ -2,8 +2,8 @@
namespace Sabre\CalDAV\Exception;
-use Sabre\DAV;
use Sabre\CalDAV;
+use Sabre\DAV;
/**
* InvalidComponentType
diff --git a/vendor/sabre/dav/lib/CalDAV/ICSExportPlugin.php b/vendor/sabre/dav/lib/CalDAV/ICSExportPlugin.php
index a3a824c71..fc8b971f3 100644
--- a/vendor/sabre/dav/lib/CalDAV/ICSExportPlugin.php
+++ b/vendor/sabre/dav/lib/CalDAV/ICSExportPlugin.php
@@ -2,13 +2,13 @@
namespace Sabre\CalDAV;
+use DateTime;
use DateTimeZone;
use Sabre\DAV;
-use Sabre\VObject;
+use Sabre\DAV\Exception\BadRequest;
use Sabre\HTTP\RequestInterface;
use Sabre\HTTP\ResponseInterface;
-use Sabre\DAV\Exception\BadRequest;
-use DateTime;
+use Sabre\VObject;
/**
* ICS Exporter
diff --git a/vendor/sabre/dav/lib/CalDAV/Notifications/Collection.php b/vendor/sabre/dav/lib/CalDAV/Notifications/Collection.php
index 5fda61dfa..557832a5a 100644
--- a/vendor/sabre/dav/lib/CalDAV/Notifications/Collection.php
+++ b/vendor/sabre/dav/lib/CalDAV/Notifications/Collection.php
@@ -2,8 +2,8 @@
namespace Sabre\CalDAV\Notifications;
-use Sabre\DAV;
use Sabre\CalDAV;
+use Sabre\DAV;
use Sabre\DAVACL;
/**
@@ -27,7 +27,7 @@ class Collection extends DAV\Collection implements ICollection, DAVACL\IACL {
/**
* The notification backend
*
- * @var Sabre\CalDAV\Backend\NotificationSupport
+ * @var CalDAV\Backend\NotificationSupport
*/
protected $caldavBackend;
diff --git a/vendor/sabre/dav/lib/CalDAV/Notifications/INode.php b/vendor/sabre/dav/lib/CalDAV/Notifications/INode.php
index f9986b714..783b92be9 100644
--- a/vendor/sabre/dav/lib/CalDAV/Notifications/INode.php
+++ b/vendor/sabre/dav/lib/CalDAV/Notifications/INode.php
@@ -2,6 +2,8 @@
namespace Sabre\CalDAV\Notifications;
+use Sabre\CalDAV\Xml\Notification\NotificationInterface;
+
/**
* This node represents a single notification.
*
@@ -20,16 +22,16 @@ interface INode {
/**
* This method must return an xml element, using the
- * Sabre\CalDAV\Notifications\INotificationType classes.
+ * Sabre\CalDAV\Xml\Notification\NotificationInterface classes.
*
- * @return INotificationType
+ * @return NotificationInterface
*/
function getNotificationType();
/**
* Returns the etag for the notification.
*
- * The etag must be surrounded by litteral double-quotes.
+ * The etag must be surrounded by literal double-quotes.
*
* @return string
*/
diff --git a/vendor/sabre/dav/lib/CalDAV/Notifications/Node.php b/vendor/sabre/dav/lib/CalDAV/Notifications/Node.php
index 11df0c94b..ad7ddf8f5 100644
--- a/vendor/sabre/dav/lib/CalDAV/Notifications/Node.php
+++ b/vendor/sabre/dav/lib/CalDAV/Notifications/Node.php
@@ -2,9 +2,9 @@
namespace Sabre\CalDAV\Notifications;
-use Sabre\DAV;
use Sabre\CalDAV;
use Sabre\CalDAV\Xml\Notification\NotificationInterface;
+use Sabre\DAV;
use Sabre\DAVACL;
/**
@@ -25,14 +25,14 @@ class Node extends DAV\File implements INode, DAVACL\IACL {
/**
* The notification backend
*
- * @var Sabre\CalDAV\Backend\NotificationSupport
+ * @var CalDAV\Backend\NotificationSupport
*/
protected $caldavBackend;
/**
* The actual notification
*
- * @var Sabre\CalDAV\Notifications\INotificationType
+ * @var NotificationInterface
*/
protected $notification;
@@ -61,7 +61,7 @@ class Node extends DAV\File implements INode, DAVACL\IACL {
/**
* Returns the path name for this notification
*
- * @return id
+ * @return string
*/
function getName() {
@@ -84,9 +84,9 @@ class Node extends DAV\File implements INode, DAVACL\IACL {
/**
* This method must return an xml element, using the
- * Sabre\CalDAV\Notifications\INotificationType classes.
+ * Sabre\CalDAV\Xml\Notification\NotificationInterface classes.
*
- * @return INotificationType
+ * @return NotificationInterface
*/
function getNotificationType() {
diff --git a/vendor/sabre/dav/lib/CalDAV/Notifications/Plugin.php b/vendor/sabre/dav/lib/CalDAV/Notifications/Plugin.php
index 546bf927f..e742351f5 100644
--- a/vendor/sabre/dav/lib/CalDAV/Notifications/Plugin.php
+++ b/vendor/sabre/dav/lib/CalDAV/Notifications/Plugin.php
@@ -3,10 +3,10 @@
namespace Sabre\CalDAV\Notifications;
use Sabre\DAV;
-use Sabre\DAV\PropFind;
use Sabre\DAV\INode as BaseINode;
-use Sabre\DAV\ServerPlugin;
+use Sabre\DAV\PropFind;
use Sabre\DAV\Server;
+use Sabre\DAV\ServerPlugin;
use Sabre\DAVACL;
use Sabre\HTTP\RequestInterface;
use Sabre\HTTP\ResponseInterface;
diff --git a/vendor/sabre/dav/lib/CalDAV/Plugin.php b/vendor/sabre/dav/lib/CalDAV/Plugin.php
index 71ba75206..def11d52d 100644
--- a/vendor/sabre/dav/lib/CalDAV/Plugin.php
+++ b/vendor/sabre/dav/lib/CalDAV/Plugin.php
@@ -9,11 +9,11 @@ use Sabre\DAV\INode;
use Sabre\DAV\MkCol;
use Sabre\DAV\Xml\Property\LocalHref;
use Sabre\DAVACL;
-use Sabre\VObject;
use Sabre\HTTP;
-use Sabre\Uri;
use Sabre\HTTP\RequestInterface;
use Sabre\HTTP\ResponseInterface;
+use Sabre\Uri;
+use Sabre\VObject;
/**
* CalDAV plugin
@@ -302,8 +302,8 @@ class Plugin extends DAV\ServerPlugin {
$this->server->createCollection($path, new MkCol($resourceType, $properties));
- $this->server->httpResponse->setStatus(201);
- $this->server->httpResponse->setHeader('Content-Length', 0);
+ $response->setStatus(201);
+ $response->setHeader('Content-Length', 0);
// This breaks the method chain.
return false;
@@ -926,7 +926,7 @@ class Plugin extends DAV\ServerPlugin {
);
}
- // We use an extra variable to allow event handles to tell us wether
+ // We use an extra variable to allow event handles to tell us whether
// the object was modified or not.
//
// This helps us determine if we need to re-serialize the object.
diff --git a/vendor/sabre/dav/lib/CalDAV/Principal/ProxyRead.php b/vendor/sabre/dav/lib/CalDAV/Principal/ProxyRead.php
index 93f0fe095..e3881831e 100644
--- a/vendor/sabre/dav/lib/CalDAV/Principal/ProxyRead.php
+++ b/vendor/sabre/dav/lib/CalDAV/Principal/ProxyRead.php
@@ -2,8 +2,8 @@
namespace Sabre\CalDAV\Principal;
-use Sabre\DAVACL;
use Sabre\DAV;
+use Sabre\DAVACL;
/**
* ProxyRead principal
@@ -84,8 +84,8 @@ class ProxyRead implements IProxyRead {
/**
* Renames the node
*
- * @throws DAV\Exception\Forbidden
* @param string $name The new name
+ * @throws DAV\Exception\Forbidden
* @return void
*/
function setName($name) {
diff --git a/vendor/sabre/dav/lib/CalDAV/Principal/ProxyWrite.php b/vendor/sabre/dav/lib/CalDAV/Principal/ProxyWrite.php
index 8124c05e0..43dd9bf07 100644
--- a/vendor/sabre/dav/lib/CalDAV/Principal/ProxyWrite.php
+++ b/vendor/sabre/dav/lib/CalDAV/Principal/ProxyWrite.php
@@ -2,8 +2,8 @@
namespace Sabre\CalDAV\Principal;
-use Sabre\DAVACL;
use Sabre\DAV;
+use Sabre\DAVACL;
/**
* ProxyWrite principal
@@ -84,8 +84,8 @@ class ProxyWrite implements IProxyWrite {
/**
* Renames the node
*
- * @throws DAV\Exception\Forbidden
* @param string $name The new name
+ * @throws DAV\Exception\Forbidden
* @return void
*/
function setName($name) {
diff --git a/vendor/sabre/dav/lib/CalDAV/Schedule/IMipPlugin.php b/vendor/sabre/dav/lib/CalDAV/Schedule/IMipPlugin.php
index ffb1fe45b..6f5acb29a 100644
--- a/vendor/sabre/dav/lib/CalDAV/Schedule/IMipPlugin.php
+++ b/vendor/sabre/dav/lib/CalDAV/Schedule/IMipPlugin.php
@@ -181,7 +181,7 @@ class IMipPlugin extends DAV\ServerPlugin {
return [
'name' => $this->getPluginName(),
- 'description' => 'Email delivery (rfc6037) for CalDAV scheduling',
+ 'description' => 'Email delivery (rfc6047) for CalDAV scheduling',
'link' => 'http://sabre.io/dav/scheduling/',
];
diff --git a/vendor/sabre/dav/lib/CalDAV/Schedule/Inbox.php b/vendor/sabre/dav/lib/CalDAV/Schedule/Inbox.php
index 6b374ea3f..81b017307 100644
--- a/vendor/sabre/dav/lib/CalDAV/Schedule/Inbox.php
+++ b/vendor/sabre/dav/lib/CalDAV/Schedule/Inbox.php
@@ -2,10 +2,10 @@
namespace Sabre\CalDAV\Schedule;
-use Sabre\DAV;
use Sabre\CalDAV;
-use Sabre\DAVACL;
use Sabre\CalDAV\Backend;
+use Sabre\DAV;
+use Sabre\DAVACL;
use Sabre\VObject;
/**
@@ -83,7 +83,7 @@ class Inbox extends DAV\Collection implements IInbox {
* Data will either be supplied as a stream resource, or in certain cases
* as a string. Keep in mind that you may have to support either.
*
- * After succesful creation of the file, you may choose to return the ETag
+ * After successful creation of the file, you may choose to return the ETag
* of the new file here.
*
* The returned ETag must be surrounded by double-quotes (The quotes should
diff --git a/vendor/sabre/dav/lib/CalDAV/Schedule/Outbox.php b/vendor/sabre/dav/lib/CalDAV/Schedule/Outbox.php
index 29eefa744..888ea3086 100644
--- a/vendor/sabre/dav/lib/CalDAV/Schedule/Outbox.php
+++ b/vendor/sabre/dav/lib/CalDAV/Schedule/Outbox.php
@@ -2,8 +2,8 @@
namespace Sabre\CalDAV\Schedule;
-use Sabre\DAV;
use Sabre\CalDAV;
+use Sabre\DAV;
use Sabre\DAVACL;
/**
diff --git a/vendor/sabre/dav/lib/CalDAV/Schedule/Plugin.php b/vendor/sabre/dav/lib/CalDAV/Schedule/Plugin.php
index 47511140f..0b991e619 100644
--- a/vendor/sabre/dav/lib/CalDAV/Schedule/Plugin.php
+++ b/vendor/sabre/dav/lib/CalDAV/Schedule/Plugin.php
@@ -3,29 +3,28 @@
namespace Sabre\CalDAV\Schedule;
use DateTimeZone;
+use Sabre\CalDAV\ICalendar;
+use Sabre\CalDAV\ICalendarObject;
+use Sabre\CalDAV\Xml\Property\ScheduleCalendarTransp;
+use Sabre\DAV\Exception\BadRequest;
+use Sabre\DAV\Exception\Forbidden;
+use Sabre\DAV\Exception\NotFound;
+use Sabre\DAV\Exception\NotImplemented;
+use Sabre\DAV\INode;
+use Sabre\DAV\PropFind;
+use Sabre\DAV\PropPatch;
use Sabre\DAV\Server;
use Sabre\DAV\ServerPlugin;
use Sabre\DAV\Sharing;
-use Sabre\DAV\PropFind;
-use Sabre\DAV\PropPatch;
-use Sabre\DAV\INode;
-use Sabre\DAV\Xml\Property\Href;
use Sabre\DAV\Xml\Property\LocalHref;
+use Sabre\DAVACL;
use Sabre\HTTP\RequestInterface;
use Sabre\HTTP\ResponseInterface;
use Sabre\VObject;
-use Sabre\VObject\Reader;
use Sabre\VObject\Component\VCalendar;
use Sabre\VObject\ITip;
use Sabre\VObject\ITip\Message;
-use Sabre\DAVACL;
-use Sabre\CalDAV\ICalendar;
-use Sabre\CalDAV\ICalendarObject;
-use Sabre\CalDAV\Xml\Property\ScheduleCalendarTransp;
-use Sabre\DAV\Exception\NotFound;
-use Sabre\DAV\Exception\Forbidden;
-use Sabre\DAV\Exception\BadRequest;
-use Sabre\DAV\Exception\NotImplemented;
+use Sabre\VObject\Reader;
/**
* CalDAV scheduling plugin.
@@ -377,7 +376,7 @@ class Plugin extends ServerPlugin {
/**
* This method is responsible for delivering the ITip message.
*
- * @param ITip\Message $itipMessage
+ * @param ITip\Message $iTipMessage
* @return void
*/
function deliver(ITip\Message $iTipMessage) {
@@ -890,8 +889,8 @@ class Plugin extends ServerPlugin {
* * 3.7;description
*
* @param string $email address
- * @param DateTimeInterface $start
- * @param DateTimeInterface $end
+ * @param \DateTimeInterface $start
+ * @param \DateTimeInterface $end
* @param VObject\Component $request
* @return array
*/
@@ -1059,7 +1058,7 @@ class Plugin extends ServerPlugin {
return [
'name' => $this->getPluginName(),
- 'description' => 'Adds calendar-auto-schedule, as defined in rf6868',
+ 'description' => 'Adds calendar-auto-schedule, as defined in rfc6638',
'link' => 'http://sabre.io/dav/scheduling/',
];
diff --git a/vendor/sabre/dav/lib/CalDAV/Schedule/SchedulingObject.php b/vendor/sabre/dav/lib/CalDAV/Schedule/SchedulingObject.php
index 6d9d3d5ec..0cd05a965 100644
--- a/vendor/sabre/dav/lib/CalDAV/Schedule/SchedulingObject.php
+++ b/vendor/sabre/dav/lib/CalDAV/Schedule/SchedulingObject.php
@@ -42,7 +42,7 @@ class SchedulingObject extends \Sabre\CalDAV\CalendarObject implements IScheduli
* * lastmodified - (optional) format as a unix timestamp.
* * acl - (optional) Use this to override the default ACL for the node.
*
- * @param Backend\BackendInterface $caldavBackend
+ * @param Backend\SchedulingSupport $caldavBackend
* @param array $objectData
*/
function __construct(Backend\SchedulingSupport $caldavBackend, array $objectData) {
diff --git a/vendor/sabre/dav/lib/CalDAV/SharingPlugin.php b/vendor/sabre/dav/lib/CalDAV/SharingPlugin.php
index 6f7df02bc..5cce79678 100644
--- a/vendor/sabre/dav/lib/CalDAV/SharingPlugin.php
+++ b/vendor/sabre/dav/lib/CalDAV/SharingPlugin.php
@@ -3,7 +3,6 @@
namespace Sabre\CalDAV;
use Sabre\DAV;
-use Sabre\DAV\Xml\Property\Href;
use Sabre\DAV\Xml\Property\LocalHref;
use Sabre\HTTP\RequestInterface;
use Sabre\HTTP\ResponseInterface;
@@ -29,7 +28,7 @@ class SharingPlugin extends DAV\ServerPlugin {
/**
* Reference to SabreDAV server object.
*
- * @var Sabre\DAV\Server
+ * @var DAV\Server
*/
protected $server;
diff --git a/vendor/sabre/dav/lib/CalDAV/Subscriptions/Plugin.php b/vendor/sabre/dav/lib/CalDAV/Subscriptions/Plugin.php
index 7abbfb1f9..877d96c6c 100644
--- a/vendor/sabre/dav/lib/CalDAV/Subscriptions/Plugin.php
+++ b/vendor/sabre/dav/lib/CalDAV/Subscriptions/Plugin.php
@@ -4,8 +4,8 @@ namespace Sabre\CalDAV\Subscriptions;
use Sabre\DAV\INode;
use Sabre\DAV\PropFind;
-use Sabre\DAV\ServerPlugin;
use Sabre\DAV\Server;
+use Sabre\DAV\ServerPlugin;
/**
* This plugin adds calendar-subscription support to your CalDAV server.
diff --git a/vendor/sabre/dav/lib/CalDAV/Subscriptions/Subscription.php b/vendor/sabre/dav/lib/CalDAV/Subscriptions/Subscription.php
index 3bb3451f3..6a1851ed8 100644
--- a/vendor/sabre/dav/lib/CalDAV/Subscriptions/Subscription.php
+++ b/vendor/sabre/dav/lib/CalDAV/Subscriptions/Subscription.php
@@ -2,12 +2,12 @@
namespace Sabre\CalDAV\Subscriptions;
+use Sabre\CalDAV\Backend\SubscriptionSupport;
use Sabre\DAV\Collection;
-use Sabre\DAV\Xml\Property\Href;
use Sabre\DAV\PropPatch;
-use Sabre\DAVACL\IACL;
+use Sabre\DAV\Xml\Property\Href;
use Sabre\DAVACL\ACLTrait;
-use Sabre\CalDAV\Backend\SubscriptionSupport;
+use Sabre\DAVACL\IACL;
/**
* Subscription Node
@@ -25,7 +25,7 @@ class Subscription extends Collection implements ISubscription, IACL {
/**
* caldavBackend
*
- * @var SupportsSubscriptions
+ * @var SubscriptionSupport
*/
protected $caldavBackend;
@@ -40,7 +40,7 @@ class Subscription extends Collection implements ISubscription, IACL {
* Constructor
*
* @param SubscriptionSupport $caldavBackend
- * @param array $calendarInfo
+ * @param array $subscriptionInfo
*/
function __construct(SubscriptionSupport $caldavBackend, array $subscriptionInfo) {
@@ -104,7 +104,7 @@ class Subscription extends Collection implements ISubscription, IACL {
/**
* Returns an array with all the child nodes
*
- * @return DAV\INode[]
+ * @return \Sabre\DAV\INode[]
*/
function getChildren() {
diff --git a/vendor/sabre/dav/lib/CalDAV/Xml/Filter/CalendarData.php b/vendor/sabre/dav/lib/CalDAV/Xml/Filter/CalendarData.php
index 9babcf15c..9669be304 100644
--- a/vendor/sabre/dav/lib/CalDAV/Xml/Filter/CalendarData.php
+++ b/vendor/sabre/dav/lib/CalDAV/Xml/Filter/CalendarData.php
@@ -2,11 +2,11 @@
namespace Sabre\CalDAV\Xml\Filter;
-use Sabre\Xml\Reader;
-use Sabre\Xml\XmlDeserializable;
-use Sabre\DAV\Exception\BadRequest;
use Sabre\CalDAV\Plugin;
+use Sabre\DAV\Exception\BadRequest;
use Sabre\VObject\DateTimeParser;
+use Sabre\Xml\Reader;
+use Sabre\Xml\XmlDeserializable;
/**
* CalendarData parser.
@@ -30,7 +30,7 @@ class CalendarData implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/CalDAV/Xml/Filter/CompFilter.php b/vendor/sabre/dav/lib/CalDAV/Xml/Filter/CompFilter.php
index c9b27dbfd..c21ede66b 100644
--- a/vendor/sabre/dav/lib/CalDAV/Xml/Filter/CompFilter.php
+++ b/vendor/sabre/dav/lib/CalDAV/Xml/Filter/CompFilter.php
@@ -2,11 +2,11 @@
namespace Sabre\CalDAV\Xml\Filter;
-use Sabre\Xml\Reader;
-use Sabre\Xml\XmlDeserializable;
-use Sabre\DAV\Exception\BadRequest;
use Sabre\CalDAV\Plugin;
+use Sabre\DAV\Exception\BadRequest;
use Sabre\VObject\DateTimeParser;
+use Sabre\Xml\Reader;
+use Sabre\Xml\XmlDeserializable;
/**
* CompFilter parser.
@@ -27,7 +27,7 @@ class CompFilter implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/CalDAV/Xml/Filter/ParamFilter.php b/vendor/sabre/dav/lib/CalDAV/Xml/Filter/ParamFilter.php
index eb7f564df..bf422cf05 100644
--- a/vendor/sabre/dav/lib/CalDAV/Xml/Filter/ParamFilter.php
+++ b/vendor/sabre/dav/lib/CalDAV/Xml/Filter/ParamFilter.php
@@ -2,9 +2,9 @@
namespace Sabre\CalDAV\Xml\Filter;
+use Sabre\CalDAV\Plugin;
use Sabre\Xml\Reader;
use Sabre\Xml\XmlDeserializable;
-use Sabre\CalDAV\Plugin;
/**
* PropFilter parser.
@@ -25,7 +25,7 @@ class ParamFilter implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/CalDAV/Xml/Filter/PropFilter.php b/vendor/sabre/dav/lib/CalDAV/Xml/Filter/PropFilter.php
index 4c2e1b172..db9207295 100644
--- a/vendor/sabre/dav/lib/CalDAV/Xml/Filter/PropFilter.php
+++ b/vendor/sabre/dav/lib/CalDAV/Xml/Filter/PropFilter.php
@@ -2,11 +2,11 @@
namespace Sabre\CalDAV\Xml\Filter;
-use Sabre\Xml\Reader;
-use Sabre\Xml\XmlDeserializable;
-use Sabre\DAV\Exception\BadRequest;
use Sabre\CalDAV\Plugin;
+use Sabre\DAV\Exception\BadRequest;
use Sabre\VObject\DateTimeParser;
+use Sabre\Xml\Reader;
+use Sabre\Xml\XmlDeserializable;
/**
* PropFilter parser.
@@ -27,7 +27,7 @@ class PropFilter implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/CalDAV/Xml/Notification/Invite.php b/vendor/sabre/dav/lib/CalDAV/Xml/Notification/Invite.php
index 1ca64f3e8..92a9ac7b7 100644
--- a/vendor/sabre/dav/lib/CalDAV/Xml/Notification/Invite.php
+++ b/vendor/sabre/dav/lib/CalDAV/Xml/Notification/Invite.php
@@ -2,10 +2,10 @@
namespace Sabre\CalDAV\Xml\Notification;
-use Sabre\Xml\Writer;
-use Sabre\CalDAV\SharingPlugin as SharingPlugin;
use Sabre\CalDAV;
+use Sabre\CalDAV\SharingPlugin as SharingPlugin;
use Sabre\DAV;
+use Sabre\Xml\Writer;
/**
* This class represents the cs:invite-notification notification element.
@@ -107,7 +107,7 @@ class Invite implements NotificationInterface {
/**
* The list of supported components
*
- * @var Sabre\CalDAV\Property\SupportedCalendarComponentSet
+ * @var CalDAV\Xml\Property\SupportedCalendarComponentSet
*/
protected $supportedComponents;
@@ -166,12 +166,12 @@ class Invite implements NotificationInterface {
}
/**
- * The xmlSerialize metod is called during xml writing.
+ * The xmlSerialize method is called during xml writing.
*
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
diff --git a/vendor/sabre/dav/lib/CalDAV/Xml/Notification/InviteReply.php b/vendor/sabre/dav/lib/CalDAV/Xml/Notification/InviteReply.php
index 51bfc178a..f4b10a396 100644
--- a/vendor/sabre/dav/lib/CalDAV/Xml/Notification/InviteReply.php
+++ b/vendor/sabre/dav/lib/CalDAV/Xml/Notification/InviteReply.php
@@ -2,10 +2,10 @@
namespace Sabre\CalDAV\Xml\Notification;
-use Sabre\Xml\Writer;
use Sabre\CalDAV;
use Sabre\CalDAV\SharingPlugin;
use Sabre\DAV;
+use Sabre\Xml\Writer;
/**
* This class represents the cs:invite-reply notification element.
@@ -117,12 +117,12 @@ class InviteReply implements NotificationInterface {
}
/**
- * The xmlSerialize metod is called during xml writing.
+ * The xmlSerialize method is called during xml writing.
*
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
diff --git a/vendor/sabre/dav/lib/CalDAV/Xml/Notification/NotificationInterface.php b/vendor/sabre/dav/lib/CalDAV/Xml/Notification/NotificationInterface.php
index 1c08f12fd..b98f9c888 100644
--- a/vendor/sabre/dav/lib/CalDAV/Xml/Notification/NotificationInterface.php
+++ b/vendor/sabre/dav/lib/CalDAV/Xml/Notification/NotificationInterface.php
@@ -2,8 +2,8 @@
namespace Sabre\CalDAV\Xml\Notification;
-use Sabre\Xml\XmlSerializable;
use Sabre\Xml\Writer;
+use Sabre\Xml\XmlSerializable;
/**
* This interface reflects a single notification type.
diff --git a/vendor/sabre/dav/lib/CalDAV/Xml/Notification/SystemStatus.php b/vendor/sabre/dav/lib/CalDAV/Xml/Notification/SystemStatus.php
index d41702e07..8c945dd68 100644
--- a/vendor/sabre/dav/lib/CalDAV/Xml/Notification/SystemStatus.php
+++ b/vendor/sabre/dav/lib/CalDAV/Xml/Notification/SystemStatus.php
@@ -2,8 +2,8 @@
namespace Sabre\CalDAV\Xml\Notification;
-use Sabre\Xml\Writer;
use Sabre\CalDAV\Plugin;
+use Sabre\Xml\Writer;
/**
* SystemStatus notification
diff --git a/vendor/sabre/dav/lib/CalDAV/Xml/Property/AllowedSharingModes.php b/vendor/sabre/dav/lib/CalDAV/Xml/Property/AllowedSharingModes.php
index c2a2d565e..54e5a116a 100644
--- a/vendor/sabre/dav/lib/CalDAV/Xml/Property/AllowedSharingModes.php
+++ b/vendor/sabre/dav/lib/CalDAV/Xml/Property/AllowedSharingModes.php
@@ -2,9 +2,9 @@
namespace Sabre\CalDAV\Xml\Property;
-use Sabre\Xml\XmlSerializable;
-use Sabre\Xml\Writer;
use Sabre\CalDAV\Plugin;
+use Sabre\Xml\Writer;
+use Sabre\Xml\XmlSerializable;
/**
* AllowedSharingModes
@@ -53,12 +53,12 @@ class AllowedSharingModes implements XmlSerializable {
}
/**
- * The xmlSerialize metod is called during xml writing.
+ * The xmlSerialize method is called during xml writing.
*
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
diff --git a/vendor/sabre/dav/lib/CalDAV/Xml/Property/EmailAddressSet.php b/vendor/sabre/dav/lib/CalDAV/Xml/Property/EmailAddressSet.php
index f577a9919..fc6f1d505 100644
--- a/vendor/sabre/dav/lib/CalDAV/Xml/Property/EmailAddressSet.php
+++ b/vendor/sabre/dav/lib/CalDAV/Xml/Property/EmailAddressSet.php
@@ -49,12 +49,12 @@ class EmailAddressSet implements XmlSerializable {
}
/**
- * The xmlSerialize metod is called during xml writing.
+ * The xmlSerialize method is called during xml writing.
*
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
diff --git a/vendor/sabre/dav/lib/CalDAV/Xml/Property/Invite.php b/vendor/sabre/dav/lib/CalDAV/Xml/Property/Invite.php
index 40ff6b936..4f33c464c 100644
--- a/vendor/sabre/dav/lib/CalDAV/Xml/Property/Invite.php
+++ b/vendor/sabre/dav/lib/CalDAV/Xml/Property/Invite.php
@@ -2,10 +2,11 @@
namespace Sabre\CalDAV\Xml\Property;
-use Sabre\Xml\XmlSerializable;
-use Sabre\Xml\Writer;
use Sabre\CalDAV\Plugin;
use Sabre\DAV;
+use Sabre\DAV\Xml\Element\Sharee;
+use Sabre\Xml\Writer;
+use Sabre\Xml\XmlSerializable;
/**
* Invite property
@@ -51,12 +52,12 @@ class Invite implements XmlSerializable {
}
/**
- * The xmlSerialize metod is called during xml writing.
+ * The xmlSerialize method is called during xml writing.
*
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
@@ -75,7 +76,7 @@ class Invite implements XmlSerializable {
foreach ($this->sharees as $sharee) {
- if ($sharee->access === \Sabre\DAV\Sharing\Plugin::ACCESS_SHAREDOWNER) {
+ if ($sharee->access === DAV\Sharing\Plugin::ACCESS_SHAREDOWNER) {
$writer->startElement($cs . 'organizer');
} else {
$writer->startElement($cs . 'user');
@@ -109,7 +110,7 @@ class Invite implements XmlSerializable {
}
- $href = new \Sabre\DAV\Xml\Property\Href($sharee->href);
+ $href = new DAV\Xml\Property\Href($sharee->href);
$href->xmlSerialize($writer);
if (isset($sharee->properties['{DAV:}displayname'])) {
diff --git a/vendor/sabre/dav/lib/CalDAV/Xml/Property/ScheduleCalendarTransp.php b/vendor/sabre/dav/lib/CalDAV/Xml/Property/ScheduleCalendarTransp.php
index a82b8eff7..10c20be55 100644
--- a/vendor/sabre/dav/lib/CalDAV/Xml/Property/ScheduleCalendarTransp.php
+++ b/vendor/sabre/dav/lib/CalDAV/Xml/Property/ScheduleCalendarTransp.php
@@ -2,11 +2,11 @@
namespace Sabre\CalDAV\Xml\Property;
+use Sabre\CalDAV\Plugin;
+use Sabre\Xml\Deserializer;
use Sabre\Xml\Element;
use Sabre\Xml\Reader;
-use Sabre\Xml\Deserializer;
use Sabre\Xml\Writer;
-use Sabre\CalDAV\Plugin;
/**
* schedule-calendar-transp property.
@@ -62,12 +62,12 @@ class ScheduleCalendarTransp implements Element {
}
/**
- * The xmlSerialize metod is called during xml writing.
+ * The xmlSerialize method is called during xml writing.
*
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
@@ -96,7 +96,7 @@ class ScheduleCalendarTransp implements Element {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/CalDAV/Xml/Property/SupportedCalendarComponentSet.php b/vendor/sabre/dav/lib/CalDAV/Xml/Property/SupportedCalendarComponentSet.php
index 7a26e767e..7fc25c5f0 100644
--- a/vendor/sabre/dav/lib/CalDAV/Xml/Property/SupportedCalendarComponentSet.php
+++ b/vendor/sabre/dav/lib/CalDAV/Xml/Property/SupportedCalendarComponentSet.php
@@ -2,11 +2,11 @@
namespace Sabre\CalDAV\Xml\Property;
+use Sabre\CalDAV\Plugin;
use Sabre\Xml\Element;
use Sabre\Xml\ParseException;
use Sabre\Xml\Reader;
use Sabre\Xml\Writer;
-use Sabre\CalDAV\Plugin;
/**
* SupportedCalendarComponentSet property.
@@ -55,12 +55,12 @@ class SupportedCalendarComponentSet implements Element {
}
/**
- * The xmlSerialize metod is called during xml writing.
+ * The xmlSerialize method is called during xml writing.
*
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
@@ -88,7 +88,7 @@ class SupportedCalendarComponentSet implements Element {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/CalDAV/Xml/Property/SupportedCalendarData.php b/vendor/sabre/dav/lib/CalDAV/Xml/Property/SupportedCalendarData.php
index b0c407fd6..d123ba4c0 100644
--- a/vendor/sabre/dav/lib/CalDAV/Xml/Property/SupportedCalendarData.php
+++ b/vendor/sabre/dav/lib/CalDAV/Xml/Property/SupportedCalendarData.php
@@ -2,9 +2,9 @@
namespace Sabre\CalDAV\Xml\Property;
-use Sabre\Xml\XmlSerializable;
-use Sabre\Xml\Writer;
use Sabre\CalDAV\Plugin;
+use Sabre\Xml\Writer;
+use Sabre\Xml\XmlSerializable;
/**
* Supported-calendar-data property
@@ -23,12 +23,12 @@ use Sabre\CalDAV\Plugin;
class SupportedCalendarData implements XmlSerializable {
/**
- * The xmlSerialize metod is called during xml writing.
+ * The xmlSerialize method is called during xml writing.
*
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
diff --git a/vendor/sabre/dav/lib/CalDAV/Xml/Property/SupportedCollationSet.php b/vendor/sabre/dav/lib/CalDAV/Xml/Property/SupportedCollationSet.php
index 71de25a62..af10860d0 100644
--- a/vendor/sabre/dav/lib/CalDAV/Xml/Property/SupportedCollationSet.php
+++ b/vendor/sabre/dav/lib/CalDAV/Xml/Property/SupportedCollationSet.php
@@ -2,9 +2,9 @@
namespace Sabre\CalDAV\Xml\Property;
+use Sabre\CalDAV\Plugin;
use Sabre\Xml\Writer;
use Sabre\Xml\XmlSerializable;
-use Sabre\CalDAV\Plugin;
/**
* supported-collation-set property
@@ -22,12 +22,12 @@ use Sabre\CalDAV\Plugin;
class SupportedCollationSet implements XmlSerializable {
/**
- * The xmlSerialize metod is called during xml writing.
+ * The xmlSerialize method is called during xml writing.
*
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
diff --git a/vendor/sabre/dav/lib/CalDAV/Xml/Request/CalendarMultiGetReport.php b/vendor/sabre/dav/lib/CalDAV/Xml/Request/CalendarMultiGetReport.php
index 79b3bb3ac..6d3c5d508 100644
--- a/vendor/sabre/dav/lib/CalDAV/Xml/Request/CalendarMultiGetReport.php
+++ b/vendor/sabre/dav/lib/CalDAV/Xml/Request/CalendarMultiGetReport.php
@@ -2,10 +2,10 @@
namespace Sabre\CalDAV\Xml\Request;
-use Sabre\Xml\XmlDeserializable;
-use Sabre\Xml\Reader;
use Sabre\CalDAV\Plugin;
use Sabre\Uri;
+use Sabre\Xml\Reader;
+use Sabre\Xml\XmlDeserializable;
/**
* CalendarMultiGetReport request parser.
@@ -64,7 +64,7 @@ class CalendarMultiGetReport implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/CalDAV/Xml/Request/CalendarQueryReport.php b/vendor/sabre/dav/lib/CalDAV/Xml/Request/CalendarQueryReport.php
index 848a4dc46..e0b1c7950 100644
--- a/vendor/sabre/dav/lib/CalDAV/Xml/Request/CalendarQueryReport.php
+++ b/vendor/sabre/dav/lib/CalDAV/Xml/Request/CalendarQueryReport.php
@@ -2,10 +2,10 @@
namespace Sabre\CalDAV\Xml\Request;
-use Sabre\Xml\XmlDeserializable;
-use Sabre\Xml\Reader;
-use Sabre\DAV\Exception\BadRequest;
use Sabre\CalDAV\Plugin;
+use Sabre\DAV\Exception\BadRequest;
+use Sabre\Xml\Reader;
+use Sabre\Xml\XmlDeserializable;
/**
* CalendarQueryReport request parser.
@@ -64,7 +64,7 @@ class CalendarQueryReport implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/CalDAV/Xml/Request/FreeBusyQueryReport.php b/vendor/sabre/dav/lib/CalDAV/Xml/Request/FreeBusyQueryReport.php
index e3b27d08e..0f6c1e074 100644
--- a/vendor/sabre/dav/lib/CalDAV/Xml/Request/FreeBusyQueryReport.php
+++ b/vendor/sabre/dav/lib/CalDAV/Xml/Request/FreeBusyQueryReport.php
@@ -38,7 +38,7 @@ class FreeBusyQueryReport implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/CalDAV/Xml/Request/InviteReply.php b/vendor/sabre/dav/lib/CalDAV/Xml/Request/InviteReply.php
index 2ecf6c2bb..db32cc6a5 100644
--- a/vendor/sabre/dav/lib/CalDAV/Xml/Request/InviteReply.php
+++ b/vendor/sabre/dav/lib/CalDAV/Xml/Request/InviteReply.php
@@ -6,9 +6,9 @@ use Sabre\CalDAV\Plugin;
use Sabre\CalDAV\SharingPlugin;
use Sabre\DAV;
use Sabre\DAV\Exception\BadRequest;
+use Sabre\Xml\Element\KeyValue;
use Sabre\Xml\Reader;
use Sabre\Xml\XmlDeserializable;
-use Sabre\Xml\Element\KeyValue;
/**
* Invite-reply POST request parser
@@ -82,7 +82,7 @@ class InviteReply implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/CalDAV/Xml/Request/MkCalendar.php b/vendor/sabre/dav/lib/CalDAV/Xml/Request/MkCalendar.php
index 7b745db55..ce7fafde9 100644
--- a/vendor/sabre/dav/lib/CalDAV/Xml/Request/MkCalendar.php
+++ b/vendor/sabre/dav/lib/CalDAV/Xml/Request/MkCalendar.php
@@ -39,7 +39,7 @@ class MkCalendar implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
@@ -62,8 +62,8 @@ class MkCalendar implements XmlDeserializable {
$self = new self();
$elementMap = $reader->elementMap;
- $elementMap['{DAV:}prop'] = 'Sabre\DAV\Xml\Element\Prop';
- $elementMap['{DAV:}set'] = 'Sabre\Xml\Element\KeyValue';
+ $elementMap['{DAV:}prop'] = 'Sabre\DAV\Xml\Element\Prop';
+ $elementMap['{DAV:}set'] = 'Sabre\Xml\Element\KeyValue';
$elems = $reader->parseInnerTree($elementMap);
foreach ($elems as $elem) {
diff --git a/vendor/sabre/dav/lib/CalDAV/Xml/Request/Share.php b/vendor/sabre/dav/lib/CalDAV/Xml/Request/Share.php
index b5d9a133c..e0bd8e0af 100644
--- a/vendor/sabre/dav/lib/CalDAV/Xml/Request/Share.php
+++ b/vendor/sabre/dav/lib/CalDAV/Xml/Request/Share.php
@@ -41,7 +41,7 @@ class Share implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/CardDAV/AddressBook.php b/vendor/sabre/dav/lib/CardDAV/AddressBook.php
index 6dd098618..c9d28a091 100644
--- a/vendor/sabre/dav/lib/CardDAV/AddressBook.php
+++ b/vendor/sabre/dav/lib/CardDAV/AddressBook.php
@@ -60,7 +60,7 @@ class AddressBook extends DAV\Collection implements IAddressBook, DAV\IPropertie
* Returns a card
*
* @param string $name
- * @return \ICard
+ * @return Card
*/
function getChild($name) {
diff --git a/vendor/sabre/dav/lib/CardDAV/AddressBookHome.php b/vendor/sabre/dav/lib/CardDAV/AddressBookHome.php
index 888a44a40..d770c0ffe 100644
--- a/vendor/sabre/dav/lib/CardDAV/AddressBookHome.php
+++ b/vendor/sabre/dav/lib/CardDAV/AddressBookHome.php
@@ -127,7 +127,7 @@ class AddressBookHome extends DAV\Collection implements DAV\IExtendedCollection,
*
* @param string $name
* @todo needs optimizing
- * @return \AddressBook
+ * @return AddressBook
*/
function getChild($name) {
diff --git a/vendor/sabre/dav/lib/CardDAV/AddressBookRoot.php b/vendor/sabre/dav/lib/CardDAV/AddressBookRoot.php
index 4a33df4ec..a9f1183da 100644
--- a/vendor/sabre/dav/lib/CardDAV/AddressBookRoot.php
+++ b/vendor/sabre/dav/lib/CardDAV/AddressBookRoot.php
@@ -18,7 +18,7 @@ class AddressBookRoot extends DAVACL\AbstractPrincipalCollection {
/**
* Principal Backend
*
- * @var Sabre\DAVACL\PrincipalBackend\BackendInteface
+ * @var DAVACL\PrincipalBackend\BackendInterface
*/
protected $principalBackend;
diff --git a/vendor/sabre/dav/lib/CardDAV/Backend/BackendInterface.php b/vendor/sabre/dav/lib/CardDAV/Backend/BackendInterface.php
index 54e42b899..18c0c0a99 100644
--- a/vendor/sabre/dav/lib/CardDAV/Backend/BackendInterface.php
+++ b/vendor/sabre/dav/lib/CardDAV/Backend/BackendInterface.php
@@ -46,7 +46,7 @@ interface BackendInterface {
* Calling the handle method is like telling the PropPatch object "I
* promise I can handle updating this property".
*
- * Read the PropPatch documenation for more info and examples.
+ * Read the PropPatch documentation for more info and examples.
*
* @param string $addressBookId
* @param \Sabre\DAV\PropPatch $propPatch
diff --git a/vendor/sabre/dav/lib/CardDAV/Backend/PDO.php b/vendor/sabre/dav/lib/CardDAV/Backend/PDO.php
index 7c3feff93..13487e9da 100644
--- a/vendor/sabre/dav/lib/CardDAV/Backend/PDO.php
+++ b/vendor/sabre/dav/lib/CardDAV/Backend/PDO.php
@@ -93,7 +93,7 @@ class PDO extends AbstractBackend implements SyncSupport {
* Calling the handle method is like telling the PropPatch object "I
* promise I can handle updating this property".
*
- * Read the PropPatch documenation for more info and examples.
+ * Read the PropPatch documentation for more info and examples.
*
* @param string $addressBookId
* @param \Sabre\DAV\PropPatch $propPatch
@@ -240,7 +240,7 @@ class PDO extends AbstractBackend implements SyncSupport {
}
/**
- * Returns a specfic card.
+ * Returns a specific card.
*
* The same set of properties must be returned as with getCards. The only
* exception is that 'carddata' is absolutely required.
@@ -466,7 +466,7 @@ class PDO extends AbstractBackend implements SyncSupport {
// Current synctoken
$stmt = $this->pdo->prepare('SELECT synctoken FROM ' . $this->addressBooksTableName . ' WHERE id = ?');
- $stmt->execute([ $addressBookId ]);
+ $stmt->execute([$addressBookId]);
$currentToken = $stmt->fetchColumn(0);
if (is_null($currentToken)) return null;
diff --git a/vendor/sabre/dav/lib/CardDAV/Card.php b/vendor/sabre/dav/lib/CardDAV/Card.php
index 0a040be6b..42a2d7b6a 100644
--- a/vendor/sabre/dav/lib/CardDAV/Card.php
+++ b/vendor/sabre/dav/lib/CardDAV/Card.php
@@ -2,8 +2,8 @@
namespace Sabre\CardDAV;
-use Sabre\DAVACL;
use Sabre\DAV;
+use Sabre\DAVACL;
/**
* The Card object represents a single Card from an addressbook
diff --git a/vendor/sabre/dav/lib/CardDAV/Plugin.php b/vendor/sabre/dav/lib/CardDAV/Plugin.php
index 0507df100..272ae71fa 100644
--- a/vendor/sabre/dav/lib/CardDAV/Plugin.php
+++ b/vendor/sabre/dav/lib/CardDAV/Plugin.php
@@ -43,7 +43,7 @@ class Plugin extends DAV\ServerPlugin {
/**
* Server class
*
- * @var Sabre\DAV\Server
+ * @var DAV\Server
*/
protected $server;
@@ -490,7 +490,8 @@ class Plugin extends DAV\ServerPlugin {
$props[200]['{' . self::NS_CARDDAV . '}address-data'] = $this->convertVCard(
$props[200]['{' . self::NS_CARDDAV . '}address-data'],
- $vcardType
+ $vcardType,
+ $report->addressDataProperties
);
}
@@ -845,14 +846,26 @@ class Plugin extends DAV\ServerPlugin {
*
* @param string|resource $data
* @param string $target
+ * @param array $propertiesFilter
* @return string
*/
- protected function convertVCard($data, $target) {
+ protected function convertVCard($data, $target, array $propertiesFilter = null) {
if (is_resource($data)) {
$data = stream_get_contents($data);
}
$input = VObject\Reader::read($data);
+ if (!empty($propertiesFilter)) {
+ $propertiesFilter = array_merge(['UID', 'VERSION', 'FN'], $propertiesFilter);
+ $keys = array_unique(array_map(function($child) {
+ return $child->name;
+ }, $input->children()));
+ $keys = array_diff($keys, $propertiesFilter);
+ foreach ($keys as $key) {
+ unset($input->$key);
+ }
+ $data = $input->serialize();
+ }
$output = null;
try {
diff --git a/vendor/sabre/dav/lib/CardDAV/VCFExportPlugin.php b/vendor/sabre/dav/lib/CardDAV/VCFExportPlugin.php
index d015589ad..2d61db6ac 100644
--- a/vendor/sabre/dav/lib/CardDAV/VCFExportPlugin.php
+++ b/vendor/sabre/dav/lib/CardDAV/VCFExportPlugin.php
@@ -3,9 +3,9 @@
namespace Sabre\CardDAV;
use Sabre\DAV;
-use Sabre\VObject;
use Sabre\HTTP\RequestInterface;
use Sabre\HTTP\ResponseInterface;
+use Sabre\VObject;
/**
* VCF Exporter
@@ -24,7 +24,7 @@ class VCFExportPlugin extends DAV\ServerPlugin {
/**
* Reference to Server class
*
- * @var Sabre\DAV\Server
+ * @var DAV\Server
*/
protected $server;
diff --git a/vendor/sabre/dav/lib/CardDAV/Xml/Filter/AddressData.php b/vendor/sabre/dav/lib/CardDAV/Xml/Filter/AddressData.php
index 34028db85..a130cd61d 100644
--- a/vendor/sabre/dav/lib/CardDAV/Xml/Filter/AddressData.php
+++ b/vendor/sabre/dav/lib/CardDAV/Xml/Filter/AddressData.php
@@ -26,7 +26,7 @@ class AddressData implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
@@ -51,7 +51,11 @@ class AddressData implements XmlDeserializable {
'version' => $reader->getAttribute('version') ?: '3.0',
];
- $reader->next();
+ $elems = (array)$reader->parseInnerTree();
+ $result['addressDataProperties'] = array_map(function($element) {
+ return $element['attributes']['name'];
+ }, $elems);
+
return $result;
}
diff --git a/vendor/sabre/dav/lib/CardDAV/Xml/Filter/ParamFilter.php b/vendor/sabre/dav/lib/CardDAV/Xml/Filter/ParamFilter.php
index 9646ae3e6..936e26917 100644
--- a/vendor/sabre/dav/lib/CardDAV/Xml/Filter/ParamFilter.php
+++ b/vendor/sabre/dav/lib/CardDAV/Xml/Filter/ParamFilter.php
@@ -2,10 +2,10 @@
namespace Sabre\CardDAV\Xml\Filter;
+use Sabre\CardDAV\Plugin;
+use Sabre\DAV\Exception\BadRequest;
use Sabre\Xml\Element;
use Sabre\Xml\Reader;
-use Sabre\DAV\Exception\BadRequest;
-use Sabre\CardDAV\Plugin;
/**
* ParamFilter parser.
@@ -26,7 +26,7 @@ abstract class ParamFilter implements Element {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/CardDAV/Xml/Filter/PropFilter.php b/vendor/sabre/dav/lib/CardDAV/Xml/Filter/PropFilter.php
index c162da160..d7799429d 100644
--- a/vendor/sabre/dav/lib/CardDAV/Xml/Filter/PropFilter.php
+++ b/vendor/sabre/dav/lib/CardDAV/Xml/Filter/PropFilter.php
@@ -2,10 +2,10 @@
namespace Sabre\CardDAV\Xml\Filter;
+use Sabre\CardDAV\Plugin;
+use Sabre\DAV\Exception\BadRequest;
use Sabre\Xml\Reader;
use Sabre\Xml\XmlDeserializable;
-use Sabre\DAV\Exception\BadRequest;
-use Sabre\CardDAV\Plugin;
/**
* PropFilter parser.
@@ -26,7 +26,7 @@ class PropFilter implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/CardDAV/Xml/Property/SupportedAddressData.php b/vendor/sabre/dav/lib/CardDAV/Xml/Property/SupportedAddressData.php
index 6ff57b6e3..aecd8a09f 100644
--- a/vendor/sabre/dav/lib/CardDAV/Xml/Property/SupportedAddressData.php
+++ b/vendor/sabre/dav/lib/CardDAV/Xml/Property/SupportedAddressData.php
@@ -2,9 +2,9 @@
namespace Sabre\CardDAV\Xml\Property;
+use Sabre\CardDAV\Plugin;
use Sabre\Xml\Writer;
use Sabre\Xml\XmlSerializable;
-use Sabre\CardDAV\Plugin;
/**
* Supported-address-data property
@@ -49,12 +49,12 @@ class SupportedAddressData implements XmlSerializable {
}
/**
- * The xmlSerialize metod is called during xml writing.
+ * The xmlSerialize method is called during xml writing.
*
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
diff --git a/vendor/sabre/dav/lib/CardDAV/Xml/Property/SupportedCollationSet.php b/vendor/sabre/dav/lib/CardDAV/Xml/Property/SupportedCollationSet.php
index 1fc064900..778aa2b64 100644
--- a/vendor/sabre/dav/lib/CardDAV/Xml/Property/SupportedCollationSet.php
+++ b/vendor/sabre/dav/lib/CardDAV/Xml/Property/SupportedCollationSet.php
@@ -18,12 +18,12 @@ use Sabre\Xml\XmlSerializable;
class SupportedCollationSet implements XmlSerializable {
/**
- * The xmlSerialize metod is called during xml writing.
+ * The xmlSerialize method is called during xml writing.
*
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
diff --git a/vendor/sabre/dav/lib/CardDAV/Xml/Request/AddressBookMultiGetReport.php b/vendor/sabre/dav/lib/CardDAV/Xml/Request/AddressBookMultiGetReport.php
index c97c5eb4f..0115a0107 100644
--- a/vendor/sabre/dav/lib/CardDAV/Xml/Request/AddressBookMultiGetReport.php
+++ b/vendor/sabre/dav/lib/CardDAV/Xml/Request/AddressBookMultiGetReport.php
@@ -54,7 +54,7 @@ class AddressBookMultiGetReport implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/CardDAV/Xml/Request/AddressBookQueryReport.php b/vendor/sabre/dav/lib/CardDAV/Xml/Request/AddressBookQueryReport.php
index a68ac5800..09fad008a 100644
--- a/vendor/sabre/dav/lib/CardDAV/Xml/Request/AddressBookQueryReport.php
+++ b/vendor/sabre/dav/lib/CardDAV/Xml/Request/AddressBookQueryReport.php
@@ -2,10 +2,10 @@
namespace Sabre\CardDAV\Xml\Request;
+use Sabre\CardDAV\Plugin;
+use Sabre\DAV\Exception\BadRequest;
use Sabre\Xml\Reader;
use Sabre\Xml\XmlDeserializable;
-use Sabre\DAV\Exception\BadRequest;
-use Sabre\CardDAV\Plugin;
/**
* AddressBookQueryReport request parser.
@@ -29,6 +29,13 @@ class AddressBookQueryReport implements XmlDeserializable {
public $properties;
/**
+ * An array with requested vcard properties.
+ *
+ * @var array
+ */
+ public $addressDataProperties = [];
+
+ /**
* List of property/component filters.
*
* This is an array with filters. Every item is a property filter. Every
@@ -92,7 +99,7 @@ class AddressBookQueryReport implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/DAV/Auth/Backend/AbstractDigest.php b/vendor/sabre/dav/lib/DAV/Auth/Backend/AbstractDigest.php
index 85c5f30d5..4b47f56c9 100644
--- a/vendor/sabre/dav/lib/DAV/Auth/Backend/AbstractDigest.php
+++ b/vendor/sabre/dav/lib/DAV/Auth/Backend/AbstractDigest.php
@@ -2,8 +2,8 @@
namespace Sabre\DAV\Auth\Backend;
-use Sabre\HTTP;
use Sabre\DAV;
+use Sabre\HTTP;
use Sabre\HTTP\RequestInterface;
use Sabre\HTTP\ResponseInterface;
diff --git a/vendor/sabre/dav/lib/DAV/Auth/Backend/PDO.php b/vendor/sabre/dav/lib/DAV/Auth/Backend/PDO.php
index 76ad89391..c2f6de974 100644
--- a/vendor/sabre/dav/lib/DAV/Auth/Backend/PDO.php
+++ b/vendor/sabre/dav/lib/DAV/Auth/Backend/PDO.php
@@ -31,7 +31,7 @@ class PDO extends AbstractDigest {
*
* If the filename argument is passed in, it will parse out the specified file fist.
*
- * @param PDO $pdo
+ * @param \PDO $pdo
*/
function __construct(\PDO $pdo) {
diff --git a/vendor/sabre/dav/lib/DAV/Auth/Plugin.php b/vendor/sabre/dav/lib/DAV/Auth/Plugin.php
index 4b5f35ac3..bbb5d180d 100644
--- a/vendor/sabre/dav/lib/DAV/Auth/Plugin.php
+++ b/vendor/sabre/dav/lib/DAV/Auth/Plugin.php
@@ -2,11 +2,11 @@
namespace Sabre\DAV\Auth;
-use Sabre\HTTP\RequestInterface;
-use Sabre\HTTP\ResponseInterface;
use Sabre\DAV\Exception\NotAuthenticated;
use Sabre\DAV\Server;
use Sabre\DAV\ServerPlugin;
+use Sabre\HTTP\RequestInterface;
+use Sabre\HTTP\ResponseInterface;
/**
* This plugin provides Authentication for a WebDAV server.
@@ -181,7 +181,7 @@ class Plugin extends ServerPlugin {
*
* If login was not successful, the second item in the array will contain a
* an array with strings. The strings are a list of reasons why login was
- * unsuccesful. For every auth backend there will be one reason, so usually
+ * unsuccessful. For every auth backend there will be one reason, so usually
* there's just one.
*
* @param RequestInterface $request
diff --git a/vendor/sabre/dav/lib/DAV/Browser/GuessContentType.php b/vendor/sabre/dav/lib/DAV/Browser/GuessContentType.php
index 01cddc230..3ba2aee25 100644
--- a/vendor/sabre/dav/lib/DAV/Browser/GuessContentType.php
+++ b/vendor/sabre/dav/lib/DAV/Browser/GuessContentType.php
@@ -2,10 +2,10 @@
namespace Sabre\DAV\Browser;
-use Sabre\HTTP\URLUtil;
use Sabre\DAV;
-use Sabre\DAV\PropFind;
use Sabre\DAV\Inode;
+use Sabre\DAV\PropFind;
+use Sabre\HTTP\URLUtil;
/**
* GuessContentType plugin
diff --git a/vendor/sabre/dav/lib/DAV/Browser/MapGetToPropFind.php b/vendor/sabre/dav/lib/DAV/Browser/MapGetToPropFind.php
index 38ee63bcd..61327c49a 100644
--- a/vendor/sabre/dav/lib/DAV/Browser/MapGetToPropFind.php
+++ b/vendor/sabre/dav/lib/DAV/Browser/MapGetToPropFind.php
@@ -21,7 +21,7 @@ class MapGetToPropFind extends DAV\ServerPlugin {
/**
* reference to server class
*
- * @var Sabre\DAV\Server
+ * @var DAV\Server
*/
protected $server;
diff --git a/vendor/sabre/dav/lib/DAV/Browser/Plugin.php b/vendor/sabre/dav/lib/DAV/Browser/Plugin.php
index 49359a045..545ad5633 100644
--- a/vendor/sabre/dav/lib/DAV/Browser/Plugin.php
+++ b/vendor/sabre/dav/lib/DAV/Browser/Plugin.php
@@ -4,9 +4,9 @@ namespace Sabre\DAV\Browser;
use Sabre\DAV;
use Sabre\DAV\MkCol;
-use Sabre\HTTP\URLUtil;
use Sabre\HTTP\RequestInterface;
use Sabre\HTTP\ResponseInterface;
+use Sabre\HTTP\URLUtil;
/**
* Browser Plugin
@@ -26,7 +26,7 @@ class Plugin extends DAV\ServerPlugin {
/**
* reference to server class
*
- * @var Sabre\DAV\Server
+ * @var DAV\Server
*/
protected $server;
@@ -112,7 +112,7 @@ class Plugin extends DAV\ServerPlugin {
$getVars = $request->getQueryParameters();
// CSP headers
- $this->server->httpResponse->setHeader('Content-Security-Policy', "default-src 'none'; img-src 'self'; style-src 'self'; font-src 'self';");
+ $response->setHeader('Content-Security-Policy', "default-src 'none'; img-src 'self'; style-src 'self'; font-src 'self';");
$sabreAction = isset($getVars['sabreAction']) ? $getVars['sabreAction'] : null;
@@ -317,7 +317,7 @@ class Plugin extends DAV\ServerPlugin {
$buttonActions = '';
if ($subProps['subNode'] instanceof DAV\IFile) {
- $buttonActions = '<a href="' . $this->escapeHTML($subProps['fullPath']) . '?sabreAction=info"><span class="oi" data-glyph="info"></span></a>';
+ $buttonActions = '<a href="' . $this->escapeHTML($subProps['fullPath']) . '?sabreAction=info"><span class="oi" data-glyph="info"></span></a>';
}
$this->server->emit('browserButtonActions', [$subProps['fullPath'], $subProps['subNode'], &$buttonActions]);
@@ -414,11 +414,14 @@ class Plugin extends DAV\ServerPlugin {
*
* @param string $title
* @param string $path
- * @return void
+ * @return string
*/
function generateHeader($title, $path = null) {
- $version = DAV\Version::VERSION;
+ $version = '';
+ if (DAV\Server::$exposeVersion) {
+ $version = DAV\Version::VERSION;
+ }
$vars = [
'title' => $this->escapeHTML($title),
@@ -475,7 +478,10 @@ HTML;
*/
function generateFooter() {
- $version = DAV\Version::VERSION;
+ $version = '';
+ if (DAV\Server::$exposeVersion) {
+ $version = DAV\Version::VERSION;
+ }
return <<<HTML
<footer>Generated by SabreDAV $version (c)2007-2016 <a href="http://sabre.io/">http://sabre.io/</a></footer>
</body>
@@ -506,23 +512,21 @@ HTML;
if (get_class($node) === 'Sabre\\DAV\\SimpleCollection')
return;
- ob_start();
- echo '<form method="post" action="">
- <h3>Create new folder</h3>
- <input type="hidden" name="sabreAction" value="mkcol" />
- <label>Name:</label> <input type="text" name="name" /><br />
- <input type="submit" value="create" />
- </form>
- <form method="post" action="" enctype="multipart/form-data">
- <h3>Upload file</h3>
- <input type="hidden" name="sabreAction" value="put" />
- <label>Name (optional):</label> <input type="text" name="name" /><br />
- <label>File:</label> <input type="file" name="file" /><br />
- <input type="submit" value="upload" />
- </form>
- ';
-
- $output .= ob_get_clean();
+ $output .= <<<HTML
+<form method="post" action="">
+<h3>Create new folder</h3>
+<input type="hidden" name="sabreAction" value="mkcol" />
+<label>Name:</label> <input type="text" name="name" /><br />
+<input type="submit" value="create" />
+</form>
+<form method="post" action="" enctype="multipart/form-data">
+<h3>Upload file</h3>
+<input type="hidden" name="sabreAction" value="put" />
+<label>Name (optional):</label> <input type="text" name="name" /><br />
+<label>File:</label> <input type="file" name="file" /><br />
+<input type="submit" value="upload" />
+</form>
+HTML;
}
@@ -543,8 +547,8 @@ HTML;
* This method returns a local pathname to an asset.
*
* @param string $assetName
- * @return string
* @throws DAV\Exception\NotFound
+ * @return string
*/
protected function getLocalAssetPath($assetName) {
@@ -575,9 +579,9 @@ HTML;
// Rudimentary mime type detection
$mime = 'application/octet-stream';
$map = [
- 'ico' => 'image/vnd.microsoft.icon',
- 'png' => 'image/png',
- 'css' => 'text/css',
+ 'ico' => 'image/vnd.microsoft.icon',
+ 'png' => 'image/png',
+ 'css' => 'text/css',
];
$ext = substr($assetName, strrpos($assetName, '.') + 1);
@@ -623,7 +627,7 @@ HTML;
* Maps a resource type to a human-readable string and icon.
*
* @param array $resourceTypes
- * @param INode $node
+ * @param DAV\INode $node
* @return array
*/
private function mapResourceType(array $resourceTypes, $node) {
diff --git a/vendor/sabre/dav/lib/DAV/Browser/PropFindAll.php b/vendor/sabre/dav/lib/DAV/Browser/PropFindAll.php
index 1ac439672..c14b7f2f9 100644
--- a/vendor/sabre/dav/lib/DAV/Browser/PropFindAll.php
+++ b/vendor/sabre/dav/lib/DAV/Browser/PropFindAll.php
@@ -28,7 +28,7 @@ class PropFindAll extends PropFind {
/**
* Handles a specific property.
*
- * This method checks wether the specified property was requested in this
+ * This method checks whether the specified property was requested in this
* PROPFIND request, and if so, it will call the callback and use the
* return value for it's value.
*
diff --git a/vendor/sabre/dav/lib/DAV/Client.php b/vendor/sabre/dav/lib/DAV/Client.php
index 08d5d4702..175ad1bc4 100644
--- a/vendor/sabre/dav/lib/DAV/Client.php
+++ b/vendor/sabre/dav/lib/DAV/Client.php
@@ -231,7 +231,7 @@ class Client extends HTTP\Client {
$response = $this->send($request);
if ((int)$response->getStatus() >= 400) {
- throw new \Sabre\HTTP\ClientHttpException($response);
+ throw new HTTP\ClientHttpException($response);
}
$result = $this->parseMultiStatus($response->getBodyAsString());
@@ -281,7 +281,7 @@ class Client extends HTTP\Client {
$response = $this->send($request);
if ($response->getStatus() >= 400) {
- throw new \Sabre\HTTP\ClientHttpException($response);
+ throw new HTTP\ClientHttpException($response);
}
if ($response->getStatus() === 207) {
@@ -303,7 +303,7 @@ class Client extends HTTP\Client {
}
if ($errorProperties) {
- throw new \Sabre\HTTP\ClientException('PROPPATCH failed. The following properties errored: ' . implode(', ', $errorProperties));
+ throw new HTTP\ClientException('PROPPATCH failed. The following properties errored: ' . implode(', ', $errorProperties));
}
}
return true;
diff --git a/vendor/sabre/dav/lib/DAV/Collection.php b/vendor/sabre/dav/lib/DAV/Collection.php
index a46bcc342..35c90b5af 100644
--- a/vendor/sabre/dav/lib/DAV/Collection.php
+++ b/vendor/sabre/dav/lib/DAV/Collection.php
@@ -68,7 +68,7 @@ abstract class Collection extends Node implements ICollection {
* Data will either be supplied as a stream resource, or in certain cases
* as a string. Keep in mind that you may have to support either.
*
- * After succesful creation of the file, you may choose to return the ETag
+ * After successful creation of the file, you may choose to return the ETag
* of the new file here.
*
* The returned ETag must be surrounded by double-quotes (The quotes should
diff --git a/vendor/sabre/dav/lib/DAV/CorePlugin.php b/vendor/sabre/dav/lib/DAV/CorePlugin.php
index a1b052915..676cdd04a 100644
--- a/vendor/sabre/dav/lib/DAV/CorePlugin.php
+++ b/vendor/sabre/dav/lib/DAV/CorePlugin.php
@@ -165,7 +165,7 @@ class CorePlugin extends ServerPlugin {
} else {
$start = $nodeSize - $range[1];
- $end = $nodeSize - 1;
+ $end = $nodeSize - 1;
if ($start < 0) $start = 0;
@@ -194,7 +194,7 @@ class CorePlugin extends ServerPlugin {
$response->setBody($body);
}
- // Sending back false will interupt the event chain and tell the server
+ // Sending back false will interrupt the event chain and tell the server
// we've handled this method.
return false;
@@ -224,7 +224,7 @@ class CorePlugin extends ServerPlugin {
$response->setHeader('Content-Length', '0');
$response->setStatus(200);
- // Sending back false will interupt the event chain and tell the server
+ // Sending back false will interrupt the event chain and tell the server
// we've handled this method.
return false;
@@ -264,7 +264,7 @@ class CorePlugin extends ServerPlugin {
$response->setHeader('X-Sabre-Real-Status', $e->getHTTPCode());
}
- // Sending back false will interupt the event chain and tell the server
+ // Sending back false will interrupt the event chain and tell the server
// we've handled this method.
return false;
@@ -290,7 +290,7 @@ class CorePlugin extends ServerPlugin {
$response->setStatus(204);
$response->setHeader('Content-Length', '0');
- // Sending back false will interupt the event chain and tell the server
+ // Sending back false will interrupt the event chain and tell the server
// we've handled this method.
return false;
@@ -333,7 +333,7 @@ class CorePlugin extends ServerPlugin {
// The only two options for the depth of a propfind is 0 or 1 - as long as depth infinity is not enabled
if (!$this->server->enablePropfindDepthInfinity && $depth != 0) $depth = 1;
- $newProperties = $this->server->getPropertiesForPath($path, $propFindXml->properties, $depth);
+ $newProperties = $this->server->getPropertiesIteratorForPath($path, $propFindXml->properties, $depth);
// This is a multi-status response
$response->setStatus(207);
@@ -355,7 +355,7 @@ class CorePlugin extends ServerPlugin {
$data = $this->server->generateMultiStatus($newProperties, $minimal);
$response->setBody($data);
- // Sending back false will interupt the event chain and tell the server
+ // Sending back false will interrupt the event chain and tell the server
// we've handled this method.
return false;
@@ -390,7 +390,7 @@ class CorePlugin extends ServerPlugin {
if ($prefer['return'] === 'minimal') {
// If return-minimal is specified, we only have to check if the
- // request was succesful, and don't need to return the
+ // request was successful, and don't need to return the
// multi-status.
$ok = true;
foreach ($result as $prop => $code) {
@@ -427,7 +427,7 @@ class CorePlugin extends ServerPlugin {
$this->server->generateMultiStatus([$multiStatus])
);
- // Sending back false will interupt the event chain and tell the server
+ // Sending back false will interrupt the event chain and tell the server
// we've handled this method.
return false;
@@ -533,7 +533,7 @@ class CorePlugin extends ServerPlugin {
}
- // Sending back false will interupt the event chain and tell the server
+ // Sending back false will interrupt the event chain and tell the server
// we've handled this method.
return false;
@@ -602,7 +602,7 @@ class CorePlugin extends ServerPlugin {
$response->setStatus(201);
}
- // Sending back false will interupt the event chain and tell the server
+ // Sending back false will interrupt the event chain and tell the server
// we've handled this method.
return false;
@@ -653,7 +653,7 @@ class CorePlugin extends ServerPlugin {
$response->setHeader('Content-Length', '0');
$response->setStatus($moveInfo['destinationExists'] ? 204 : 201);
- // Sending back false will interupt the event chain and tell the server
+ // Sending back false will interrupt the event chain and tell the server
// we've handled this method.
return false;
@@ -688,7 +688,7 @@ class CorePlugin extends ServerPlugin {
$response->setHeader('Content-Length', '0');
$response->setStatus($copyInfo['destinationExists'] ? 204 : 201);
- // Sending back false will interupt the event chain and tell the server
+ // Sending back false will interrupt the event chain and tell the server
// we've handled this method.
return false;
@@ -722,7 +722,7 @@ class CorePlugin extends ServerPlugin {
}
- // Sending back false will interupt the event chain and tell the server
+ // Sending back false will interrupt the event chain and tell the server
// we've handled this method.
return false;
@@ -740,7 +740,7 @@ class CorePlugin extends ServerPlugin {
*/
function propPatchProtectedPropertyCheck($path, PropPatch $propPatch) {
- // Comparing the mutation list to the list of propetected properties.
+ // Comparing the mutation list to the list of protected properties.
$mutations = $propPatch->getMutations();
$protected = array_intersect(
diff --git a/vendor/sabre/dav/lib/DAV/Exception/InvalidResourceType.php b/vendor/sabre/dav/lib/DAV/Exception/InvalidResourceType.php
index 505fe5c10..6324d9f3a 100644
--- a/vendor/sabre/dav/lib/DAV/Exception/InvalidResourceType.php
+++ b/vendor/sabre/dav/lib/DAV/Exception/InvalidResourceType.php
@@ -19,7 +19,7 @@ class InvalidResourceType extends Forbidden {
/**
* This method allows the exception to include additional information into the WebDAV error response
*
- * @param DAV\Server $server
+ * @param \Sabre\DAV\Server $server
* @param \DOMElement $errorNode
* @return void
*/
diff --git a/vendor/sabre/dav/lib/DAV/FS/Node.php b/vendor/sabre/dav/lib/DAV/FS/Node.php
index 831c11911..424718f96 100644
--- a/vendor/sabre/dav/lib/DAV/FS/Node.php
+++ b/vendor/sabre/dav/lib/DAV/FS/Node.php
@@ -43,7 +43,7 @@ abstract class Node implements DAV\INode {
*/
function getName() {
- list(, $name) = URLUtil::splitPath($this->path);
+ list(, $name) = URLUtil::splitPath($this->path);
return $name;
}
diff --git a/vendor/sabre/dav/lib/DAV/File.php b/vendor/sabre/dav/lib/DAV/File.php
index 675956b22..5161fbd51 100644
--- a/vendor/sabre/dav/lib/DAV/File.php
+++ b/vendor/sabre/dav/lib/DAV/File.php
@@ -19,7 +19,7 @@ abstract class File extends Node implements IFile {
*
* The data argument is a readable stream resource.
*
- * After a succesful put operation, you may choose to return an ETag. The
+ * After a successful put operation, you may choose to return an ETag. The
* etag must always be surrounded by double-quotes. These quotes must
* appear in the actual string you're returning.
*
diff --git a/vendor/sabre/dav/lib/DAV/IFile.php b/vendor/sabre/dav/lib/DAV/IFile.php
index 37e7cd33c..19d8d8637 100644
--- a/vendor/sabre/dav/lib/DAV/IFile.php
+++ b/vendor/sabre/dav/lib/DAV/IFile.php
@@ -20,7 +20,7 @@ interface IFile extends INode {
*
* The data argument is a readable stream resource.
*
- * After a succesful put operation, you may choose to return an ETag. The
+ * After a successful put operation, you may choose to return an ETag. The
* etag must always be surrounded by double-quotes. These quotes must
* appear in the actual string you're returning.
*
@@ -32,7 +32,7 @@ interface IFile extends INode {
* different object on a subsequent GET you are strongly recommended to not
* return an ETag, and just return null.
*
- * @param resource|data $data
+ * @param resource|string $data
* @return string|null
*/
function put($data);
diff --git a/vendor/sabre/dav/lib/DAV/IMoveTarget.php b/vendor/sabre/dav/lib/DAV/IMoveTarget.php
index f0f67bc26..92fde1d5c 100644
--- a/vendor/sabre/dav/lib/DAV/IMoveTarget.php
+++ b/vendor/sabre/dav/lib/DAV/IMoveTarget.php
@@ -7,7 +7,7 @@ namespace Sabre\DAV;
* nodes may be moved into this collection".
*
* The benefit of this, is that sabre/dav will by default perform a move, by
- * tranfersing an entire directory tree, copying every collection, and deleting
+ * transferring an entire directory tree, copying every collection, and deleting
* every item.
*
* If a backend supports a better optimized move operation, this can trigger
diff --git a/vendor/sabre/dav/lib/DAV/Locks/Backend/PDO.php b/vendor/sabre/dav/lib/DAV/Locks/Backend/PDO.php
index a01d9bae4..510f266f7 100644
--- a/vendor/sabre/dav/lib/DAV/Locks/Backend/PDO.php
+++ b/vendor/sabre/dav/lib/DAV/Locks/Backend/PDO.php
@@ -33,7 +33,7 @@ class PDO extends AbstractBackend {
/**
* Constructor
*
- * @param PDO $pdo
+ * @param \PDO $pdo
*/
function __construct(\PDO $pdo) {
@@ -102,7 +102,7 @@ class PDO extends AbstractBackend {
$lockInfo->created = $row['created'];
$lockInfo->scope = $row['scope'];
$lockInfo->depth = $row['depth'];
- $lockInfo->uri = $row['uri'];
+ $lockInfo->uri = $row['uri'];
$lockList[] = $lockInfo;
}
diff --git a/vendor/sabre/dav/lib/DAV/Locks/Plugin.php b/vendor/sabre/dav/lib/DAV/Locks/Plugin.php
index 4855b7076..41a3bf3fa 100644
--- a/vendor/sabre/dav/lib/DAV/Locks/Plugin.php
+++ b/vendor/sabre/dav/lib/DAV/Locks/Plugin.php
@@ -25,14 +25,14 @@ class Plugin extends DAV\ServerPlugin {
/**
* locksBackend
*
- * @var Backend\Backend\Interface
+ * @var Backend\BackendInterface
*/
protected $locksBackend;
/**
* server
*
- * @var Sabre\DAV\Server
+ * @var DAV\Server
*/
protected $server;
@@ -256,7 +256,7 @@ class Plugin extends DAV\ServerPlugin {
$response->setStatus($newFile ? 201 : 200);
$response->setBody($this->generateLockResponse($lockInfo));
- // Returning false will interupt the event chain and mark this method
+ // Returning false will interrupt the event chain and mark this method
// as 'handled'.
return false;
diff --git a/vendor/sabre/dav/lib/DAV/MkCol.php b/vendor/sabre/dav/lib/DAV/MkCol.php
index c79055418..042e14bca 100644
--- a/vendor/sabre/dav/lib/DAV/MkCol.php
+++ b/vendor/sabre/dav/lib/DAV/MkCol.php
@@ -61,6 +61,7 @@ class MkCol extends PropPatch {
* checked.
*
* @param string|string[] $resourceType
+ * @return bool
*/
function hasResourceType($resourceType) {
diff --git a/vendor/sabre/dav/lib/DAV/Mount/Plugin.php b/vendor/sabre/dav/lib/DAV/Mount/Plugin.php
index 8e06acb9f..dc923ad85 100644
--- a/vendor/sabre/dav/lib/DAV/Mount/Plugin.php
+++ b/vendor/sabre/dav/lib/DAV/Mount/Plugin.php
@@ -20,7 +20,7 @@ class Plugin extends DAV\ServerPlugin {
/**
* Reference to Server class
*
- * @var Sabre\DAV\Server
+ * @var DAV\Server
*/
protected $server;
diff --git a/vendor/sabre/dav/lib/DAV/Node.php b/vendor/sabre/dav/lib/DAV/Node.php
index ba270e8f9..ef6eea18e 100644
--- a/vendor/sabre/dav/lib/DAV/Node.php
+++ b/vendor/sabre/dav/lib/DAV/Node.php
@@ -29,7 +29,7 @@ abstract class Node implements INode {
/**
* Deletes the current node
*
- * @throws Sabre\DAV\Exception\Forbidden
+ * @throws Exception\Forbidden
* @return void
*/
function delete() {
@@ -41,8 +41,8 @@ abstract class Node implements INode {
/**
* Renames the node
*
- * @throws Sabre\DAV\Exception\Forbidden
* @param string $name The new name
+ * @throws Exception\Forbidden
* @return void
*/
function setName($name) {
diff --git a/vendor/sabre/dav/lib/DAV/PartialUpdate/Plugin.php b/vendor/sabre/dav/lib/DAV/PartialUpdate/Plugin.php
index 24ba970b1..9c129d705 100644
--- a/vendor/sabre/dav/lib/DAV/PartialUpdate/Plugin.php
+++ b/vendor/sabre/dav/lib/DAV/PartialUpdate/Plugin.php
@@ -29,7 +29,7 @@ class Plugin extends DAV\ServerPlugin {
/**
* Reference to server
*
- * @var Sabre\DAV\Server
+ * @var DAV\Server
*/
protected $server;
diff --git a/vendor/sabre/dav/lib/DAV/PropFind.php b/vendor/sabre/dav/lib/DAV/PropFind.php
index 8ae6b6cfd..0940a1ce2 100644
--- a/vendor/sabre/dav/lib/DAV/PropFind.php
+++ b/vendor/sabre/dav/lib/DAV/PropFind.php
@@ -72,7 +72,7 @@ class PropFind {
/**
* Handles a specific property.
*
- * This method checks wether the specified property was requested in this
+ * This method checks whether the specified property was requested in this
* PROPFIND request, and if so, it will call the callback and use the
* return value for it's value.
*
diff --git a/vendor/sabre/dav/lib/DAV/PropertyStorage/Backend/BackendInterface.php b/vendor/sabre/dav/lib/DAV/PropertyStorage/Backend/BackendInterface.php
index 31ecafdb2..b15d7fef9 100644
--- a/vendor/sabre/dav/lib/DAV/PropertyStorage/Backend/BackendInterface.php
+++ b/vendor/sabre/dav/lib/DAV/PropertyStorage/Backend/BackendInterface.php
@@ -23,7 +23,7 @@ interface BackendInterface {
* This method received a PropFind object, which contains all the
* information about the properties that need to be fetched.
*
- * Ususually you would just want to call 'get404Properties' on this object,
+ * Usually you would just want to call 'get404Properties' on this object,
* as this will give you the _exact_ list of properties that need to be
* fetched, and haven't yet.
*
diff --git a/vendor/sabre/dav/lib/DAV/PropertyStorage/Backend/PDO.php b/vendor/sabre/dav/lib/DAV/PropertyStorage/Backend/PDO.php
index 2fe843884..6f3f1feaf 100644
--- a/vendor/sabre/dav/lib/DAV/PropertyStorage/Backend/PDO.php
+++ b/vendor/sabre/dav/lib/DAV/PropertyStorage/Backend/PDO.php
@@ -66,7 +66,7 @@ class PDO implements BackendInterface {
* This method received a PropFind object, which contains all the
* information about the properties that need to be fetched.
*
- * Ususually you would just want to call 'get404Properties' on this object,
+ * Usually you would just want to call 'get404Properties' on this object,
* as this will give you the _exact_ list of properties that need to be
* fetched, and haven't yet.
*
diff --git a/vendor/sabre/dav/lib/DAV/PropertyStorage/Plugin.php b/vendor/sabre/dav/lib/DAV/PropertyStorage/Plugin.php
index 0c28b7882..a66a14113 100644
--- a/vendor/sabre/dav/lib/DAV/PropertyStorage/Plugin.php
+++ b/vendor/sabre/dav/lib/DAV/PropertyStorage/Plugin.php
@@ -2,11 +2,11 @@
namespace Sabre\DAV\PropertyStorage;
+use Sabre\DAV\INode;
+use Sabre\DAV\PropFind;
+use Sabre\DAV\PropPatch;
use Sabre\DAV\Server;
use Sabre\DAV\ServerPlugin;
-use Sabre\DAV\PropPatch;
-use Sabre\DAV\PropFind;
-use Sabre\DAV\INode;
/**
* PropertyStorage Plugin.
@@ -30,7 +30,7 @@ class Plugin extends ServerPlugin {
* paths, you can use a pathFilter to do this.
*
* The pathFilter should be a callable. The callable retrieves a path as
- * its argument, and should return true or false wether it allows
+ * its argument, and should return true or false whether it allows
* properties to be stored.
*
* @var callable
@@ -38,6 +38,11 @@ class Plugin extends ServerPlugin {
public $pathFilter;
/**
+ * @var Backend\BackendInterface
+ */
+ public $backend;
+
+ /**
* Creates the plugin
*
* @param Backend\BackendInterface $backend
diff --git a/vendor/sabre/dav/lib/DAV/Server.php b/vendor/sabre/dav/lib/DAV/Server.php
index 024b7a557..6805ec0b0 100644
--- a/vendor/sabre/dav/lib/DAV/Server.php
+++ b/vendor/sabre/dav/lib/DAV/Server.php
@@ -2,16 +2,16 @@
namespace Sabre\DAV;
+use Psr\Log\LoggerAwareInterface;
+use Psr\Log\LoggerAwareTrait;
+use Psr\Log\LoggerInterface;
+use Psr\Log\NullLogger;
use Sabre\Event\EventEmitter;
use Sabre\HTTP;
use Sabre\HTTP\RequestInterface;
use Sabre\HTTP\ResponseInterface;
use Sabre\HTTP\URLUtil;
use Sabre\Uri;
-use Psr\Log\LoggerAwareInterface;
-use Psr\Log\LoggerAwareTrait;
-use Psr\Log\LoggerInterface;
-use Psr\Log\NullLogger;
/**
* Main DAV server class
@@ -37,7 +37,7 @@ class Server extends EventEmitter implements LoggerAwareInterface {
/**
* The tree object
*
- * @var Sabre\DAV\Tree
+ * @var Tree
*/
public $tree;
@@ -51,21 +51,21 @@ class Server extends EventEmitter implements LoggerAwareInterface {
/**
* httpResponse
*
- * @var Sabre\HTTP\Response
+ * @var HTTP\Response
*/
public $httpResponse;
/**
* httpRequest
*
- * @var Sabre\HTTP\Request
+ * @var HTTP\Request
*/
public $httpRequest;
/**
* PHP HTTP Sapi
*
- * @var Sabre\HTTP\Sapi
+ * @var HTTP\Sapi
*/
public $sapi;
@@ -437,7 +437,7 @@ class Server extends EventEmitter implements LoggerAwareInterface {
}
/**
- * Returns the PSR-3 logger objcet.
+ * Returns the PSR-3 logger object.
*
* @return LoggerInterface
*/
@@ -455,7 +455,7 @@ class Server extends EventEmitter implements LoggerAwareInterface {
*
* @param RequestInterface $request
* @param ResponseInterface $response
- * @param $sendResponse Whether to send the HTTP response to the DAV client.
+ * @param bool $sendResponse Whether to send the HTTP response to the DAV client.
* @return void
*/
function invokeMethod(RequestInterface $request, ResponseInterface $response, $sendResponse = true) {
@@ -681,18 +681,18 @@ class Server extends EventEmitter implements LoggerAwareInterface {
// can be true or false
'respond-async' => false,
// Could be set to 'representation' or 'minimal'.
- 'return' => null,
+ 'return' => null,
// Used as a timeout, is usually a number.
- 'wait' => null,
+ 'wait' => null,
// can be 'strict' or 'lenient'.
- 'handling' => false,
+ 'handling' => false,
];
if ($prefer = $this->httpRequest->getHeader('Prefer')) {
$result = array_merge(
$result,
- \Sabre\HTTP\parsePrefer($prefer)
+ HTTP\parsePrefer($prefer)
);
} elseif ($this->httpRequest->getHeader('Brief') == 't') {
@@ -794,6 +794,7 @@ class Server extends EventEmitter implements LoggerAwareInterface {
*
* @param string $path
* @param array $propertyNames
+ * @return array
*/
function getProperties($path, $propertyNames) {
@@ -877,12 +878,14 @@ class Server extends EventEmitter implements LoggerAwareInterface {
/**
* Small helper to support PROPFIND with DEPTH_INFINITY.
*
- * @param array[] $propFindRequests
* @param PropFind $propFind
- * @return void
+ * @param array $yieldFirst
+ * @return \Iterator
*/
- private function addPathNodesRecursively(&$propFindRequests, PropFind $propFind) {
-
+ private function generatePathNodes(PropFind $propFind, array $yieldFirst = null) {
+ if ($yieldFirst !== null) {
+ yield $yieldFirst;
+ }
$newDepth = $propFind->getDepth();
$path = $propFind->getPath();
@@ -900,13 +903,15 @@ class Server extends EventEmitter implements LoggerAwareInterface {
}
$subPropFind->setPath($subPath);
- $propFindRequests[] = [
+ yield [
$subPropFind,
$childNode
];
if (($newDepth === self::DEPTH_INFINITY || $newDepth >= 1) && $childNode instanceof ICollection) {
- $this->addPathNodesRecursively($propFindRequests, $subPropFind);
+ foreach ($this->generatePathNodes($subPropFind) as $subItem) {
+ yield $subItem;
+ }
}
}
@@ -925,9 +930,31 @@ class Server extends EventEmitter implements LoggerAwareInterface {
* @param array $propertyNames
* @param int $depth
* @return array
+ *
+ * @deprecated Use getPropertiesIteratorForPath() instead (as it's more memory efficient)
+ * @see getPropertiesIteratorForPath()
*/
function getPropertiesForPath($path, $propertyNames = [], $depth = 0) {
+ return iterator_to_array($this->getPropertiesIteratorForPath($path, $propertyNames, $depth));
+
+ }
+ /**
+ * Returns a list of properties for a given path
+ *
+ * The path that should be supplied should have the baseUrl stripped out
+ * The list of properties should be supplied in Clark notation. If the list is empty
+ * 'allprops' is assumed.
+ *
+ * If a depth of 1 is requested child elements will also be returned.
+ *
+ * @param string $path
+ * @param array $propertyNames
+ * @param int $depth
+ * @return \Iterator
+ */
+ function getPropertiesIteratorForPath($path, $propertyNames = [], $depth = 0) {
+
// The only two options for the depth of a propfind is 0 or 1 - as long as depth infinity is not enabled
if (!$this->enablePropfindDepthInfinity && $depth != 0) $depth = 1;
@@ -944,11 +971,9 @@ class Server extends EventEmitter implements LoggerAwareInterface {
]];
if (($depth > 0 || $depth === self::DEPTH_INFINITY) && $parentNode instanceof ICollection) {
- $this->addPathNodesRecursively($propFindRequests, $propFind);
+ $propFindRequests = $this->generatePathNodes(clone $propFind, current($propFindRequests));
}
- $returnPropertyList = [];
-
foreach ($propFindRequests as $propFindRequest) {
list($propFind, $node) = $propFindRequest;
@@ -965,13 +990,11 @@ class Server extends EventEmitter implements LoggerAwareInterface {
if (in_array('{DAV:}collection', $resourceType) || in_array('{DAV:}principal', $resourceType)) {
$result['href'] .= '/';
}
- $returnPropertyList[] = $result;
+ yield $result;
}
}
- return $returnPropertyList;
-
}
/**
@@ -1430,7 +1453,7 @@ class Server extends EventEmitter implements LoggerAwareInterface {
// Plugins are responsible for validating all the tokens.
// If a plugin deemed a token 'valid', it will set 'validToken' to
// true.
- $this->emit('validateTokens', [ $request, &$ifConditions ]);
+ $this->emit('validateTokens', [$request, &$ifConditions]);
// Now we're going to analyze the result.
@@ -1450,7 +1473,7 @@ class Server extends EventEmitter implements LoggerAwareInterface {
if (!$token['etag']) {
$etagValid = true;
}
- // Checking the ETag, only if the token was already deamed
+ // Checking the ETag, only if the token was already deemed
// valid and there is one.
if ($token['etag'] && $tokenValid) {
@@ -1626,13 +1649,18 @@ class Server extends EventEmitter implements LoggerAwareInterface {
*
* If 'strip404s' is set to true, all 404 responses will be removed.
*
- * @param array $fileProperties The list with nodes
- * @param bool strip404s
+ * @param array|\Traversable $fileProperties The list with nodes
+ * @param bool $strip404s
* @return string
*/
- function generateMultiStatus(array $fileProperties, $strip404s = false) {
+ function generateMultiStatus($fileProperties, $strip404s = false) {
- $xml = [];
+ $w = $this->xml->getWriter();
+ $w->openMemory();
+ $w->contextUri = $this->baseUri;
+ $w->startDocument();
+
+ $w->startElement('{DAV:}multistatus');
foreach ($fileProperties as $entry) {
@@ -1645,13 +1673,14 @@ class Server extends EventEmitter implements LoggerAwareInterface {
ltrim($href, '/'),
$entry
);
- $xml[] = [
+ $w->write([
'name' => '{DAV:}response',
'value' => $response
- ];
-
+ ]);
}
- return $this->xml->write('{DAV:}multistatus', $xml, $this->baseUri);
+ $w->endElement();
+
+ return $w->outputMemory();
}
diff --git a/vendor/sabre/dav/lib/DAV/Sharing/Plugin.php b/vendor/sabre/dav/lib/DAV/Sharing/Plugin.php
index 354d06a56..ef5702c57 100644
--- a/vendor/sabre/dav/lib/DAV/Sharing/Plugin.php
+++ b/vendor/sabre/dav/lib/DAV/Sharing/Plugin.php
@@ -8,8 +8,8 @@ use Sabre\DAV\INode;
use Sabre\DAV\PropFind;
use Sabre\DAV\Server;
use Sabre\DAV\ServerPlugin;
-use Sabre\DAV\Xml\Property;
use Sabre\DAV\Xml\Element\Sharee;
+use Sabre\DAV\Xml\Property;
use Sabre\HTTP\RequestInterface;
use Sabre\HTTP\ResponseInterface;
@@ -40,7 +40,7 @@ class Plugin extends ServerPlugin {
/**
* Reference to SabreDAV server object.
*
- * @var Sabre\DAV\Server
+ * @var Server
*/
protected $server;
diff --git a/vendor/sabre/dav/lib/DAV/Sync/Plugin.php b/vendor/sabre/dav/lib/DAV/Sync/Plugin.php
index 4a141c72b..8e4b1aa64 100644
--- a/vendor/sabre/dav/lib/DAV/Sync/Plugin.php
+++ b/vendor/sabre/dav/lib/DAV/Sync/Plugin.php
@@ -3,8 +3,8 @@
namespace Sabre\DAV\Sync;
use Sabre\DAV;
-use Sabre\HTTP\RequestInterface;
use Sabre\DAV\Xml\Request\SyncCollectionReport;
+use Sabre\HTTP\RequestInterface;
/**
* This plugin all WebDAV-sync capabilities to the Server.
diff --git a/vendor/sabre/dav/lib/DAV/TemporaryFileFilterPlugin.php b/vendor/sabre/dav/lib/DAV/TemporaryFileFilterPlugin.php
index c5b8aa1ca..7b453d105 100644
--- a/vendor/sabre/dav/lib/DAV/TemporaryFileFilterPlugin.php
+++ b/vendor/sabre/dav/lib/DAV/TemporaryFileFilterPlugin.php
@@ -14,7 +14,7 @@ use Sabre\HTTP\URLUtil;
* a WebDAV share as a disk.
*
* It will intercept these files and place them in a separate directory.
- * these files are not deleted automatically, so it is adviceable to
+ * these files are not deleted automatically, so it is advisable to
* delete these after they are not accessed for 24 hours.
*
* Currently it supports:
@@ -51,7 +51,7 @@ class TemporaryFileFilterPlugin extends ServerPlugin {
/**
* A reference to the main Server class
*
- * @var Sabre\DAV\Server
+ * @var \Sabre\DAV\Server
*/
protected $server;
@@ -134,12 +134,12 @@ class TemporaryFileFilterPlugin extends ServerPlugin {
*
* @param string $uri
* @param resource $data
- * @param DAV\ICollection $parentNode
+ * @param ICollection $parent
* @param bool $modified Should be set to true, if this event handler
* changed &$data.
* @return bool
*/
- function beforeCreateFile($uri, $data, $parent, $modified) {
+ function beforeCreateFile($uri, $data, ICollection $parent, $modified) {
if ($tempPath = $this->isTempFile($uri)) {
diff --git a/vendor/sabre/dav/lib/DAV/Version.php b/vendor/sabre/dav/lib/DAV/Version.php
index 2fda85db8..89918e5bc 100644
--- a/vendor/sabre/dav/lib/DAV/Version.php
+++ b/vendor/sabre/dav/lib/DAV/Version.php
@@ -14,6 +14,6 @@ class Version {
/**
* Full version number
*/
- const VERSION = '3.2.0';
+ const VERSION = '3.2.2';
}
diff --git a/vendor/sabre/dav/lib/DAV/Xml/Element/Prop.php b/vendor/sabre/dav/lib/DAV/Xml/Element/Prop.php
index db5332c50..71ef03e3f 100644
--- a/vendor/sabre/dav/lib/DAV/Xml/Element/Prop.php
+++ b/vendor/sabre/dav/lib/DAV/Xml/Element/Prop.php
@@ -3,8 +3,8 @@
namespace Sabre\DAV\Xml\Element;
use Sabre\DAV\Xml\Property\Complex;
-use Sabre\Xml\XmlDeserializable;
use Sabre\Xml\Reader;
+use Sabre\Xml\XmlDeserializable;
/**
* This class is responsible for decoding the {DAV:}prop element as it appears
@@ -22,7 +22,7 @@ class Prop implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
@@ -90,7 +90,7 @@ class Prop implements XmlDeserializable {
if (array_key_exists($name, $reader->elementMap)) {
$deserializer = $reader->elementMap[$name];
if (is_subclass_of($deserializer, 'Sabre\\Xml\\XmlDeserializable')) {
- $value = call_user_func([ $deserializer, 'xmlDeserialize' ], $reader);
+ $value = call_user_func([$deserializer, 'xmlDeserialize'], $reader);
} elseif (is_callable($deserializer)) {
$value = call_user_func($deserializer, $reader);
} else {
diff --git a/vendor/sabre/dav/lib/DAV/Xml/Element/Response.php b/vendor/sabre/dav/lib/DAV/Xml/Element/Response.php
index 97a2bb59f..ce97ae943 100644
--- a/vendor/sabre/dav/lib/DAV/Xml/Element/Response.php
+++ b/vendor/sabre/dav/lib/DAV/Xml/Element/Response.php
@@ -160,7 +160,7 @@ class Response implements Element {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/DAV/Xml/Element/Sharee.php b/vendor/sabre/dav/lib/DAV/Xml/Element/Sharee.php
index dcfd7bd2e..e187bf11c 100644
--- a/vendor/sabre/dav/lib/DAV/Xml/Element/Sharee.php
+++ b/vendor/sabre/dav/lib/DAV/Xml/Element/Sharee.php
@@ -105,7 +105,7 @@ class Sharee implements Element {
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
@@ -146,7 +146,7 @@ class Sharee implements Element {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/DAV/Xml/Property/Complex.php b/vendor/sabre/dav/lib/DAV/Xml/Property/Complex.php
index 1d9202082..258806e4a 100644
--- a/vendor/sabre/dav/lib/DAV/Xml/Property/Complex.php
+++ b/vendor/sabre/dav/lib/DAV/Xml/Property/Complex.php
@@ -20,7 +20,7 @@ class Complex extends XmlFragment {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/DAV/Xml/Property/GetLastModified.php b/vendor/sabre/dav/lib/DAV/Xml/Property/GetLastModified.php
index 2db47269f..101a0f0c9 100644
--- a/vendor/sabre/dav/lib/DAV/Xml/Property/GetLastModified.php
+++ b/vendor/sabre/dav/lib/DAV/Xml/Property/GetLastModified.php
@@ -2,12 +2,12 @@
namespace Sabre\DAV\Xml\Property;
+use DateTime;
+use DateTimeZone;
+use Sabre\HTTP;
use Sabre\Xml\Element;
use Sabre\Xml\Reader;
use Sabre\Xml\Writer;
-use Sabre\HTTP;
-use DateTime;
-use DateTimeZone;
/**
* This property represents the {DAV:}getlastmodified property.
@@ -83,7 +83,7 @@ class GetLastModified implements Element {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/DAV/Xml/Property/Href.php b/vendor/sabre/dav/lib/DAV/Xml/Property/Href.php
index 0027f72e1..6c4f11b87 100644
--- a/vendor/sabre/dav/lib/DAV/Xml/Property/Href.php
+++ b/vendor/sabre/dav/lib/DAV/Xml/Property/Href.php
@@ -4,10 +4,10 @@ namespace Sabre\DAV\Xml\Property;
use Sabre\DAV\Browser\HtmlOutput;
use Sabre\DAV\Browser\HtmlOutputHelper;
+use Sabre\Uri;
use Sabre\Xml\Element;
use Sabre\Xml\Reader;
use Sabre\Xml\Writer;
-use Sabre\Uri;
/**
* Href property
@@ -40,7 +40,7 @@ class Href implements Element, HtmlOutput {
* If auto-prefix is set to false, the hrefs will be treated as absolute
* and not relative to the servers base uri.
*
- * @param string|string[] $href
+ * @param string|string[] $hrefs
*/
function __construct($hrefs) {
@@ -74,12 +74,12 @@ class Href implements Element, HtmlOutput {
}
/**
- * The xmlSerialize metod is called during xml writing.
+ * The xmlSerialize method is called during xml writing.
*
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
@@ -128,7 +128,7 @@ class Href implements Element, HtmlOutput {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/DAV/Xml/Property/Invite.php b/vendor/sabre/dav/lib/DAV/Xml/Property/Invite.php
index 0616ff113..6adad3650 100644
--- a/vendor/sabre/dav/lib/DAV/Xml/Property/Invite.php
+++ b/vendor/sabre/dav/lib/DAV/Xml/Property/Invite.php
@@ -2,9 +2,9 @@
namespace Sabre\DAV\Xml\Property;
-use Sabre\DAV\Sharing\Sharee;
-use Sabre\Xml\XmlSerializable;
+use Sabre\DAV\Xml\Element\Sharee;
use Sabre\Xml\Writer;
+use Sabre\Xml\XmlSerializable;
/**
* This class represents the {DAV:}invite property.
@@ -46,7 +46,7 @@ class Invite implements XmlSerializable {
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
diff --git a/vendor/sabre/dav/lib/DAV/Xml/Property/LocalHref.php b/vendor/sabre/dav/lib/DAV/Xml/Property/LocalHref.php
index 76a27b95d..00d2fa708 100644
--- a/vendor/sabre/dav/lib/DAV/Xml/Property/LocalHref.php
+++ b/vendor/sabre/dav/lib/DAV/Xml/Property/LocalHref.php
@@ -8,7 +8,7 @@ use Sabre\HTTP;
* LocalHref property
*
* Like the Href property, this element represents {DAV:}href. The difference
- * is that this is used stricly for paths on the server. The LocalHref property
+ * is that this is used strictly for paths on the server. The LocalHref property
* will prepare the path so it's a valid URI.
*
* These two objects behave identically:
@@ -32,7 +32,7 @@ class LocalHref extends Href {
* If auto-prefix is set to false, the hrefs will be treated as absolute
* and not relative to the servers base uri.
*
- * @param string|string[] $href
+ * @param string|string[] $hrefs
*/
function __construct($hrefs) {
diff --git a/vendor/sabre/dav/lib/DAV/Xml/Property/ResourceType.php b/vendor/sabre/dav/lib/DAV/Xml/Property/ResourceType.php
index 302888321..ce640ff32 100644
--- a/vendor/sabre/dav/lib/DAV/Xml/Property/ResourceType.php
+++ b/vendor/sabre/dav/lib/DAV/Xml/Property/ResourceType.php
@@ -28,7 +28,7 @@ class ResourceType extends Element\Elements implements HtmlOutput {
*
* The resourcetype must be specified in clark-notation
*
- * @param array|string|null $resourceType
+ * @param array|string|null $resourceTypes
*/
function __construct($resourceTypes = null) {
@@ -77,7 +77,7 @@ class ResourceType extends Element\Elements implements HtmlOutput {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/DAV/Xml/Property/ShareAccess.php b/vendor/sabre/dav/lib/DAV/Xml/Property/ShareAccess.php
index a3fc6b0e1..939062f76 100644
--- a/vendor/sabre/dav/lib/DAV/Xml/Property/ShareAccess.php
+++ b/vendor/sabre/dav/lib/DAV/Xml/Property/ShareAccess.php
@@ -2,8 +2,8 @@
namespace Sabre\DAV\Xml\Property;
-use Sabre\DAV\Sharing\Plugin as SharingPlugin;
use Sabre\DAV\Exception\BadRequest;
+use Sabre\DAV\Sharing\Plugin as SharingPlugin;
use Sabre\Xml\Element;
use Sabre\Xml\Reader;
use Sabre\Xml\Writer;
@@ -62,7 +62,7 @@ class ShareAccess implements Element {
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
@@ -102,7 +102,7 @@ class ShareAccess implements Element {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/DAV/Xml/Property/SupportedLock.php b/vendor/sabre/dav/lib/DAV/Xml/Property/SupportedLock.php
index f6d01aa37..677fdde4b 100644
--- a/vendor/sabre/dav/lib/DAV/Xml/Property/SupportedLock.php
+++ b/vendor/sabre/dav/lib/DAV/Xml/Property/SupportedLock.php
@@ -21,12 +21,12 @@ use Sabre\Xml\XmlSerializable;
class SupportedLock implements XmlSerializable {
/**
- * The xmlSerialize metod is called during xml writing.
+ * The xmlSerialize method is called during xml writing.
*
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
@@ -43,11 +43,11 @@ class SupportedLock implements XmlSerializable {
$writer->writeElement('{DAV:}lockentry', [
'{DAV:}lockscope' => ['{DAV:}exclusive' => null],
- '{DAV:}locktype' => ['{DAV:}write' => null],
+ '{DAV:}locktype' => ['{DAV:}write' => null],
]);
$writer->writeElement('{DAV:}lockentry', [
'{DAV:}lockscope' => ['{DAV:}shared' => null],
- '{DAV:}locktype' => ['{DAV:}write' => null],
+ '{DAV:}locktype' => ['{DAV:}write' => null],
]);
}
diff --git a/vendor/sabre/dav/lib/DAV/Xml/Property/SupportedMethodSet.php b/vendor/sabre/dav/lib/DAV/Xml/Property/SupportedMethodSet.php
index 7641f3739..1a3878ef7 100644
--- a/vendor/sabre/dav/lib/DAV/Xml/Property/SupportedMethodSet.php
+++ b/vendor/sabre/dav/lib/DAV/Xml/Property/SupportedMethodSet.php
@@ -67,12 +67,12 @@ class SupportedMethodSet implements XmlSerializable, HtmlOutput {
}
/**
- * The xmlSerialize metod is called during xml writing.
+ * The xmlSerialize method is called during xml writing.
*
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
diff --git a/vendor/sabre/dav/lib/DAV/Xml/Property/SupportedReportSet.php b/vendor/sabre/dav/lib/DAV/Xml/Property/SupportedReportSet.php
index ebf27300d..96383ec96 100644
--- a/vendor/sabre/dav/lib/DAV/Xml/Property/SupportedReportSet.php
+++ b/vendor/sabre/dav/lib/DAV/Xml/Property/SupportedReportSet.php
@@ -98,12 +98,12 @@ class SupportedReportSet implements XmlSerializable, HtmlOutput {
}
/**
- * The xmlSerialize metod is called during xml writing.
+ * The xmlSerialize method is called during xml writing.
*
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
diff --git a/vendor/sabre/dav/lib/DAV/Xml/Request/Lock.php b/vendor/sabre/dav/lib/DAV/Xml/Request/Lock.php
index 76df98d13..c315a9a45 100644
--- a/vendor/sabre/dav/lib/DAV/Xml/Request/Lock.php
+++ b/vendor/sabre/dav/lib/DAV/Xml/Request/Lock.php
@@ -38,7 +38,7 @@ class Lock implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/DAV/Xml/Request/MkCol.php b/vendor/sabre/dav/lib/DAV/Xml/Request/MkCol.php
index 5db239061..9490bf58c 100644
--- a/vendor/sabre/dav/lib/DAV/Xml/Request/MkCol.php
+++ b/vendor/sabre/dav/lib/DAV/Xml/Request/MkCol.php
@@ -40,7 +40,7 @@ class MkCol implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
@@ -63,8 +63,8 @@ class MkCol implements XmlDeserializable {
$self = new self();
$elementMap = $reader->elementMap;
- $elementMap['{DAV:}prop'] = 'Sabre\DAV\Xml\Element\Prop';
- $elementMap['{DAV:}set'] = 'Sabre\Xml\Element\KeyValue';
+ $elementMap['{DAV:}prop'] = 'Sabre\DAV\Xml\Element\Prop';
+ $elementMap['{DAV:}set'] = 'Sabre\Xml\Element\KeyValue';
$elementMap['{DAV:}remove'] = 'Sabre\Xml\Element\KeyValue';
$elems = $reader->parseInnerTree($elementMap);
diff --git a/vendor/sabre/dav/lib/DAV/Xml/Request/PropFind.php b/vendor/sabre/dav/lib/DAV/Xml/Request/PropFind.php
index ad3ad7c43..f1b5b6fdc 100644
--- a/vendor/sabre/dav/lib/DAV/Xml/Request/PropFind.php
+++ b/vendor/sabre/dav/lib/DAV/Xml/Request/PropFind.php
@@ -36,7 +36,7 @@ class PropFind implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/DAV/Xml/Request/PropPatch.php b/vendor/sabre/dav/lib/DAV/Xml/Request/PropPatch.php
index 07a05f887..821b9e047 100644
--- a/vendor/sabre/dav/lib/DAV/Xml/Request/PropPatch.php
+++ b/vendor/sabre/dav/lib/DAV/Xml/Request/PropPatch.php
@@ -29,12 +29,12 @@ class PropPatch implements Element {
public $properties = [];
/**
- * The xmlSerialize metod is called during xml writing.
+ * The xmlSerialize method is called during xml writing.
*
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
@@ -68,7 +68,7 @@ class PropPatch implements Element {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
@@ -91,8 +91,8 @@ class PropPatch implements Element {
$self = new self();
$elementMap = $reader->elementMap;
- $elementMap['{DAV:}prop'] = 'Sabre\DAV\Xml\Element\Prop';
- $elementMap['{DAV:}set'] = 'Sabre\Xml\Element\KeyValue';
+ $elementMap['{DAV:}prop'] = 'Sabre\DAV\Xml\Element\Prop';
+ $elementMap['{DAV:}set'] = 'Sabre\Xml\Element\KeyValue';
$elementMap['{DAV:}remove'] = 'Sabre\Xml\Element\KeyValue';
$elems = $reader->parseInnerTree($elementMap);
diff --git a/vendor/sabre/dav/lib/DAV/Xml/Request/ShareResource.php b/vendor/sabre/dav/lib/DAV/Xml/Request/ShareResource.php
index 965e5857c..526a4eb6f 100644
--- a/vendor/sabre/dav/lib/DAV/Xml/Request/ShareResource.php
+++ b/vendor/sabre/dav/lib/DAV/Xml/Request/ShareResource.php
@@ -2,9 +2,9 @@
namespace Sabre\DAV\Xml\Request;
+use Sabre\DAV\Xml\Element\Sharee;
use Sabre\Xml\Reader;
use Sabre\Xml\XmlDeserializable;
-use Sabre\DAV\Xml\Element\Sharee;
/**
* ShareResource request parser.
@@ -40,7 +40,7 @@ class ShareResource implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/DAV/Xml/Request/SyncCollectionReport.php b/vendor/sabre/dav/lib/DAV/Xml/Request/SyncCollectionReport.php
index 3092ada47..830293a01 100644
--- a/vendor/sabre/dav/lib/DAV/Xml/Request/SyncCollectionReport.php
+++ b/vendor/sabre/dav/lib/DAV/Xml/Request/SyncCollectionReport.php
@@ -2,10 +2,10 @@
namespace Sabre\DAV\Xml\Request;
+use Sabre\DAV\Exception\BadRequest;
+use Sabre\Xml\Element\KeyValue;
use Sabre\Xml\Reader;
use Sabre\Xml\XmlDeserializable;
-use Sabre\Xml\Element\KeyValue;
-use Sabre\DAV\Exception\BadRequest;
/**
* SyncCollection request parser.
@@ -51,7 +51,7 @@ class SyncCollectionReport implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
@@ -75,7 +75,7 @@ class SyncCollectionReport implements XmlDeserializable {
$reader->pushContext();
- $reader->elementMap['{DAV:}prop'] = 'Sabre\Xml\Element\Elements';
+ $reader->elementMap['{DAV:}prop'] = 'Sabre\Xml\Element\Elements';
$elems = KeyValue::xmlDeserialize($reader);
$reader->popContext();
diff --git a/vendor/sabre/dav/lib/DAV/Xml/Response/MultiStatus.php b/vendor/sabre/dav/lib/DAV/Xml/Response/MultiStatus.php
index 16a3d4a68..cf5a0453b 100644
--- a/vendor/sabre/dav/lib/DAV/Xml/Response/MultiStatus.php
+++ b/vendor/sabre/dav/lib/DAV/Xml/Response/MultiStatus.php
@@ -99,7 +99,7 @@ class MultiStatus implements Element {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/DAVACL/Exception/NotRecognizedPrincipal.php b/vendor/sabre/dav/lib/DAVACL/Exception/NotRecognizedPrincipal.php
index 4349bf101..d7ae188ae 100644
--- a/vendor/sabre/dav/lib/DAVACL/Exception/NotRecognizedPrincipal.php
+++ b/vendor/sabre/dav/lib/DAVACL/Exception/NotRecognizedPrincipal.php
@@ -5,7 +5,7 @@ namespace Sabre\DAVACL\Exception;
use Sabre\DAV;
/**
- * If a client tried to set a privilege assigned to a non-existant principal,
+ * If a client tried to set a privilege assigned to a non-existent principal,
* this exception will be thrown.
*
* @copyright Copyright (C) fruux GmbH (https://fruux.com/)
diff --git a/vendor/sabre/dav/lib/DAVACL/FS/Collection.php b/vendor/sabre/dav/lib/DAVACL/FS/Collection.php
index 1c08b43b1..b4fe7a1b0 100644
--- a/vendor/sabre/dav/lib/DAVACL/FS/Collection.php
+++ b/vendor/sabre/dav/lib/DAVACL/FS/Collection.php
@@ -2,11 +2,11 @@
namespace Sabre\DAVACL\FS;
+use Sabre\DAV\Exception\Forbidden;
+use Sabre\DAV\Exception\NotFound;
use Sabre\DAV\FSExt\Directory as BaseCollection;
use Sabre\DAVACL\ACLTrait;
use Sabre\DAVACL\IACL;
-use Sabre\DAV\Exception\Forbidden;
-use Sabre\DAV\Exception\NotFound;
/**
* This is an ACL-enabled collection.
diff --git a/vendor/sabre/dav/lib/DAVACL/FS/File.php b/vendor/sabre/dav/lib/DAVACL/FS/File.php
index 387597bf7..aaf2ae148 100644
--- a/vendor/sabre/dav/lib/DAVACL/FS/File.php
+++ b/vendor/sabre/dav/lib/DAVACL/FS/File.php
@@ -3,8 +3,8 @@
namespace Sabre\DAVACL\FS;
use Sabre\DAV\FSExt\File as BaseFile;
-use Sabre\DAVACL\IACL;
use Sabre\DAVACL\ACLTrait;
+use Sabre\DAVACL\IACL;
/**
* This is an ACL-enabled file node.
diff --git a/vendor/sabre/dav/lib/DAVACL/FS/HomeCollection.php b/vendor/sabre/dav/lib/DAVACL/FS/HomeCollection.php
index 9e21353ea..201235e5a 100644
--- a/vendor/sabre/dav/lib/DAVACL/FS/HomeCollection.php
+++ b/vendor/sabre/dav/lib/DAVACL/FS/HomeCollection.php
@@ -72,7 +72,7 @@ class HomeCollection extends AbstractPrincipalCollection implements IACL {
* supplied by the authentication backend.
*
* @param array $principalInfo
- * @return \Sabre\DAVACL\INode
+ * @return \Sabre\DAV\INode
*/
function getChildForPrincipal(array $principalInfo) {
diff --git a/vendor/sabre/dav/lib/DAVACL/Plugin.php b/vendor/sabre/dav/lib/DAVACL/Plugin.php
index 8e912309e..a2aa118d7 100644
--- a/vendor/sabre/dav/lib/DAVACL/Plugin.php
+++ b/vendor/sabre/dav/lib/DAVACL/Plugin.php
@@ -3,11 +3,12 @@
namespace Sabre\DAVACL;
use Sabre\DAV;
-use Sabre\DAV\INode;
-use Sabre\DAV\Xml\Property\Href;
use Sabre\DAV\Exception\BadRequest;
-use Sabre\DAV\Exception\NotFound;
+use Sabre\DAV\Exception\Forbidden;
use Sabre\DAV\Exception\NotAuthenticated;
+use Sabre\DAV\Exception\NotFound;
+use Sabre\DAV\INode;
+use Sabre\DAV\Xml\Property\Href;
use Sabre\DAVACL\Exception\NeedPrivileges;
use Sabre\HTTP\RequestInterface;
use Sabre\HTTP\ResponseInterface;
@@ -53,7 +54,7 @@ class Plugin extends DAV\ServerPlugin {
/**
* Reference to server object.
*
- * @var Sabre\DAV\Server
+ * @var DAV\Server
*/
protected $server;
@@ -228,14 +229,14 @@ class Plugin extends DAV\ServerPlugin {
/**
* Returns the standard users' principal.
*
- * This is one authorative principal url for the current user.
+ * This is one authoritative principal url for the current user.
* This method will return null if the user wasn't logged in.
*
* @return string|null
*/
function getCurrentUserPrincipal() {
- /** @var $authPlugin Sabre\DAV\Auth\Plugin */
+ /** @var $authPlugin \Sabre\DAV\Auth\Plugin */
$authPlugin = $this->server->getPlugin('auth');
if (!$authPlugin) {
return null;
@@ -283,8 +284,7 @@ class Plugin extends DAV\ServerPlugin {
*
* These rules are used for all nodes that don't implement the IACL interface.
*
- * @param array $acl
- * @return void
+ * @return array
*/
function getDefaultAcl() {
@@ -299,7 +299,7 @@ class Plugin extends DAV\ServerPlugin {
* set of rules allow anyone to do anything, as long as they are
* authenticated.
*
- * var array
+ * @var array
*/
protected $defaultAcl = [
[
@@ -321,7 +321,7 @@ class Plugin extends DAV\ServerPlugin {
/**
* Returns all the principal groups the specified principal is a member of.
*
- * @param string $principal
+ * @param string $mainPrincipal
* @return array
*/
function getPrincipalMembership($mainPrincipal) {
@@ -365,7 +365,7 @@ class Plugin extends DAV\ServerPlugin {
/**
* Find out of a principal equals another principal.
*
- * This is a quick way to find out wether a principal URI is part of a
+ * This is a quick way to find out whether a principal URI is part of a
* group, or any subgroups.
*
* The first argument is the principal URI you want to check against. For
@@ -373,10 +373,10 @@ class Plugin extends DAV\ServerPlugin {
* which you want to find out of it is the same as the first principal, or
* in a member of the first principal's group or subgroups.
*
- * So the arguments are not interchangable. If principal A is in group B,
+ * So the arguments are not interchangeable. If principal A is in group B,
* passing 'B', 'A' will yield true, but 'A', 'B' is false.
*
- * If the sceond argument is not passed, we will use the current user
+ * If the second argument is not passed, we will use the current user
* principal.
*
* @param string $checkPrincipal
@@ -412,8 +412,8 @@ class Plugin extends DAV\ServerPlugin {
* ]
* ]
*
- * Privileges can be nested using "aggregrates". Doing so means that
- * if you assign someone the aggregrating privilege, all the
+ * Privileges can be nested using "aggregates". Doing so means that
+ * if you assign someone the aggregating privilege, all the
* sub-privileges will automatically be granted.
*
* Marking a privilege as abstract means that the privilege cannot be
@@ -484,7 +484,7 @@ class Plugin extends DAV\ServerPlugin {
],
],
];
- if ($node instanceof \Sabre\DAV\ICollection) {
+ if ($node instanceof DAV\ICollection) {
$supportedPrivileges['{DAV:}write']['aggregates']['{DAV:}bind'] = [
'abstract' => false,
'aggregates' => [],
@@ -494,7 +494,7 @@ class Plugin extends DAV\ServerPlugin {
'aggregates' => [],
];
}
- if ($node instanceof \Sabre\DAVACL\IACL) {
+ if ($node instanceof IACL) {
$supportedPrivileges['{DAV:}write']['aggregates']['{DAV:}write-acl'] = [
'abstract' => false,
'aggregates' => [],
@@ -980,8 +980,6 @@ class Plugin extends DAV\ServerPlugin {
*
* @param DAV\PropFind $propFind
* @param DAV\INode $node
- * @param array $requestedProperties
- * @param array $returnedProperties
* @TODO really should be broken into multiple methods, or even a class.
* @return bool
*/
@@ -1423,7 +1421,7 @@ class Plugin extends DAV\ServerPlugin {
];
}
- // Replacing the property with its expannded form.
+ // Replacing the property with its expanded form.
$node[200][$propertyName] = $childProps;
}
diff --git a/vendor/sabre/dav/lib/DAVACL/Principal.php b/vendor/sabre/dav/lib/DAVACL/Principal.php
index 6ebb30907..d7db94999 100644
--- a/vendor/sabre/dav/lib/DAVACL/Principal.php
+++ b/vendor/sabre/dav/lib/DAVACL/Principal.php
@@ -41,7 +41,7 @@ class Principal extends DAV\Node implements IPrincipal, DAV\IProperties, IACL {
/**
* Creates the principal object
*
- * @param IPrincipalBackend $principalBackend
+ * @param PrincipalBackend\BackendInterface $principalBackend
* @param array $principalProperties
*/
function __construct(PrincipalBackend\BackendInterface $principalBackend, array $principalProperties = []) {
diff --git a/vendor/sabre/dav/lib/DAVACL/PrincipalBackend/BackendInterface.php b/vendor/sabre/dav/lib/DAVACL/PrincipalBackend/BackendInterface.php
index 2cb83071a..40b6e33ea 100644
--- a/vendor/sabre/dav/lib/DAVACL/PrincipalBackend/BackendInterface.php
+++ b/vendor/sabre/dav/lib/DAVACL/PrincipalBackend/BackendInterface.php
@@ -53,7 +53,7 @@ interface BackendInterface {
* Calling the handle method is like telling the PropPatch object "I
* promise I can handle updating this property".
*
- * Read the PropPatch documenation for more info and examples.
+ * Read the PropPatch documentation for more info and examples.
*
* @param string $path
* @param \Sabre\DAV\PropPatch $propPatch
diff --git a/vendor/sabre/dav/lib/DAVACL/PrincipalBackend/PDO.php b/vendor/sabre/dav/lib/DAVACL/PrincipalBackend/PDO.php
index a491dc88f..eb0df888b 100644
--- a/vendor/sabre/dav/lib/DAVACL/PrincipalBackend/PDO.php
+++ b/vendor/sabre/dav/lib/DAVACL/PrincipalBackend/PDO.php
@@ -11,7 +11,7 @@ use Sabre\HTTP\URLUtil;
*
*
* This backend assumes all principals are in a single collection. The default collection
- * is 'principals/', but this can be overriden.
+ * is 'principals/', but this can be overridden.
*
* @copyright Copyright (C) fruux GmbH (https://fruux.com/)
* @author Evert Pot (http://evertpot.com/)
@@ -65,7 +65,7 @@ class PDO extends AbstractBackend implements CreatePrincipalSupport {
/**
* Sets up the backend.
*
- * @param PDO $pdo
+ * @param \PDO $pdo
*/
function __construct(\PDO $pdo) {
@@ -171,7 +171,7 @@ class PDO extends AbstractBackend implements CreatePrincipalSupport {
* Calling the handle method is like telling the PropPatch object "I
* promise I can handle updating this property".
*
- * Read the PropPatch documenation for more info and examples.
+ * Read the PropPatch documentation for more info and examples.
*
* @param string $path
* @param DAV\PropPatch $propPatch
@@ -307,7 +307,7 @@ class PDO extends AbstractBackend implements CreatePrincipalSupport {
case "mailto":
$query = 'SELECT uri FROM ' . $this->tableName . ' WHERE lower(email)=lower(?)';
$stmt = $this->pdo->prepare($query);
- $stmt->execute([ $value ]);
+ $stmt->execute([$value]);
while ($row = $stmt->fetch(\PDO::FETCH_ASSOC)) {
// Checking if the principal is in the prefix
diff --git a/vendor/sabre/dav/lib/DAVACL/PrincipalCollection.php b/vendor/sabre/dav/lib/DAVACL/PrincipalCollection.php
index d8a90153a..ee5b88a90 100644
--- a/vendor/sabre/dav/lib/DAVACL/PrincipalCollection.php
+++ b/vendor/sabre/dav/lib/DAVACL/PrincipalCollection.php
@@ -57,7 +57,7 @@ class PrincipalCollection extends AbstractPrincipalCollection implements IExtend
*
* @param string $name
* @param MkCol $mkCol
- * @throws Exception\InvalidResourceType
+ * @throws InvalidResourceType
* @return void
*/
function createExtendedCollection($name, MkCol $mkCol) {
diff --git a/vendor/sabre/dav/lib/DAVACL/Xml/Property/Acl.php b/vendor/sabre/dav/lib/DAVACL/Xml/Property/Acl.php
index 9f5e40df1..0e1c30ccf 100644
--- a/vendor/sabre/dav/lib/DAVACL/Xml/Property/Acl.php
+++ b/vendor/sabre/dav/lib/DAVACL/Xml/Property/Acl.php
@@ -78,12 +78,12 @@ class Acl implements Element, HtmlOutput {
}
/**
- * The xmlSerialize metod is called during xml writing.
+ * The xmlSerialize method is called during xml writing.
*
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
@@ -149,7 +149,7 @@ class Acl implements Element, HtmlOutput {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/DAVACL/Xml/Property/AclRestrictions.php b/vendor/sabre/dav/lib/DAVACL/Xml/Property/AclRestrictions.php
index f669cc5e1..8d5854c23 100644
--- a/vendor/sabre/dav/lib/DAVACL/Xml/Property/AclRestrictions.php
+++ b/vendor/sabre/dav/lib/DAVACL/Xml/Property/AclRestrictions.php
@@ -2,8 +2,8 @@
namespace Sabre\DAVACL\Xml\Property;
-use Sabre\Xml\XmlSerializable;
use Sabre\Xml\Writer;
+use Sabre\Xml\XmlSerializable;
/**
* AclRestrictions property
@@ -17,12 +17,12 @@ use Sabre\Xml\Writer;
class AclRestrictions implements XmlSerializable {
/**
- * The xmlSerialize metod is called during xml writing.
+ * The xmlSerialize method is called during xml writing.
*
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
diff --git a/vendor/sabre/dav/lib/DAVACL/Xml/Property/CurrentUserPrivilegeSet.php b/vendor/sabre/dav/lib/DAVACL/Xml/Property/CurrentUserPrivilegeSet.php
index 0a95eb2b7..74c09cee1 100644
--- a/vendor/sabre/dav/lib/DAVACL/Xml/Property/CurrentUserPrivilegeSet.php
+++ b/vendor/sabre/dav/lib/DAVACL/Xml/Property/CurrentUserPrivilegeSet.php
@@ -41,12 +41,12 @@ class CurrentUserPrivilegeSet implements Element, HtmlOutput {
}
/**
- * The xmlSerialize metod is called during xml writing.
+ * The xmlSerialize method is called during xml writing.
*
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
@@ -99,7 +99,7 @@ class CurrentUserPrivilegeSet implements Element, HtmlOutput {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/DAVACL/Xml/Property/Principal.php b/vendor/sabre/dav/lib/DAVACL/Xml/Property/Principal.php
index d32249d8b..04d22165d 100644
--- a/vendor/sabre/dav/lib/DAVACL/Xml/Property/Principal.php
+++ b/vendor/sabre/dav/lib/DAVACL/Xml/Property/Principal.php
@@ -85,12 +85,12 @@ class Principal extends DAV\Xml\Property\Href {
/**
- * The xmlSerialize metod is called during xml writing.
+ * The xmlSerialize method is called during xml writing.
*
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
diff --git a/vendor/sabre/dav/lib/DAVACL/Xml/Property/SupportedPrivilegeSet.php b/vendor/sabre/dav/lib/DAVACL/Xml/Property/SupportedPrivilegeSet.php
index 55e7783ae..b963cc8c3 100644
--- a/vendor/sabre/dav/lib/DAVACL/Xml/Property/SupportedPrivilegeSet.php
+++ b/vendor/sabre/dav/lib/DAVACL/Xml/Property/SupportedPrivilegeSet.php
@@ -4,8 +4,8 @@ namespace Sabre\DAVACL\Xml\Property;
use Sabre\DAV\Browser\HtmlOutput;
use Sabre\DAV\Browser\HtmlOutputHelper;
-use Sabre\Xml\XmlSerializable;
use Sabre\Xml\Writer;
+use Sabre\Xml\XmlSerializable;
/**
* SupportedPrivilegeSet property
@@ -53,12 +53,12 @@ class SupportedPrivilegeSet implements XmlSerializable, HtmlOutput {
}
/**
- * The xmlSerialize metod is called during xml writing.
+ * The xmlSerialize method is called during xml writing.
*
* Use the $writer argument to write its own xml serialization.
*
* An important note: do _not_ create a parent element. Any element
- * implementing XmlSerializble should only ever write what's considered
+ * implementing XmlSerializable should only ever write what's considered
* its 'inner xml'.
*
* The parent of the current element is responsible for writing a
@@ -73,7 +73,7 @@ class SupportedPrivilegeSet implements XmlSerializable, HtmlOutput {
*/
function xmlSerialize(Writer $writer) {
- $this->serializePriv($writer, '{DAV:}all', [ 'aggregates' => $this->privileges]);
+ $this->serializePriv($writer, '{DAV:}all', ['aggregates' => $this->privileges]);
}
@@ -114,7 +114,7 @@ class SupportedPrivilegeSet implements XmlSerializable, HtmlOutput {
ob_start();
echo "<ul class=\"tree\">";
- $traverse('{DAV:}all', [ 'aggregates' => $this->getValue() ]);
+ $traverse('{DAV:}all', ['aggregates' => $this->getValue()]);
echo "</ul>\n";
return ob_get_clean();
@@ -129,6 +129,7 @@ class SupportedPrivilegeSet implements XmlSerializable, HtmlOutput {
* This is a recursive function.
*
* @param Writer $writer
+ * @param string $privName
* @param array $privilege
* @return void
*/
diff --git a/vendor/sabre/dav/lib/DAVACL/Xml/Request/AclPrincipalPropSetReport.php b/vendor/sabre/dav/lib/DAVACL/Xml/Request/AclPrincipalPropSetReport.php
index f01c1e6ab..0aa2f29a5 100644
--- a/vendor/sabre/dav/lib/DAVACL/Xml/Request/AclPrincipalPropSetReport.php
+++ b/vendor/sabre/dav/lib/DAVACL/Xml/Request/AclPrincipalPropSetReport.php
@@ -2,9 +2,9 @@
namespace Sabre\DAVACL\Xml\Request;
-use Sabre\Xml\XmlDeserializable;
-use Sabre\Xml\Reader;
use Sabre\Xml\Deserializer;
+use Sabre\Xml\Reader;
+use Sabre\Xml\XmlDeserializable;
/**
* AclPrincipalPropSet request parser.
@@ -24,7 +24,7 @@ class AclPrincipalPropSetReport implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/DAVACL/Xml/Request/ExpandPropertyReport.php b/vendor/sabre/dav/lib/DAVACL/Xml/Request/ExpandPropertyReport.php
index 3f535e301..a9938ba5b 100644
--- a/vendor/sabre/dav/lib/DAVACL/Xml/Request/ExpandPropertyReport.php
+++ b/vendor/sabre/dav/lib/DAVACL/Xml/Request/ExpandPropertyReport.php
@@ -35,7 +35,7 @@ class ExpandPropertyReport implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/DAVACL/Xml/Request/PrincipalMatchReport.php b/vendor/sabre/dav/lib/DAVACL/Xml/Request/PrincipalMatchReport.php
index 5c4e88189..1be15ab2d 100644
--- a/vendor/sabre/dav/lib/DAVACL/Xml/Request/PrincipalMatchReport.php
+++ b/vendor/sabre/dav/lib/DAVACL/Xml/Request/PrincipalMatchReport.php
@@ -2,9 +2,9 @@
namespace Sabre\DAVACL\Xml\Request;
-use Sabre\Xml\XmlDeserializable;
-use Sabre\Xml\Reader;
use Sabre\Xml\Deserializer;
+use Sabre\Xml\Reader;
+use Sabre\Xml\XmlDeserializable;
/**
* PrincipalMatchReport request parser.
@@ -55,7 +55,7 @@ class PrincipalMatchReport implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/DAVACL/Xml/Request/PrincipalPropertySearchReport.php b/vendor/sabre/dav/lib/DAVACL/Xml/Request/PrincipalPropertySearchReport.php
index 1e7aa4481..b0cf0e408 100644
--- a/vendor/sabre/dav/lib/DAVACL/Xml/Request/PrincipalPropertySearchReport.php
+++ b/vendor/sabre/dav/lib/DAVACL/Xml/Request/PrincipalPropertySearchReport.php
@@ -2,9 +2,9 @@
namespace Sabre\DAVACL\Xml\Request;
+use Sabre\DAV\Exception\BadRequest;
use Sabre\Xml\Reader;
use Sabre\Xml\XmlDeserializable;
-use Sabre\DAV\Exception\BadRequest;
/**
* PrincipalSearchPropertySetReport request parser.
@@ -56,7 +56,7 @@ class PrincipalPropertySearchReport implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/lib/DAVACL/Xml/Request/PrincipalSearchPropertySetReport.php b/vendor/sabre/dav/lib/DAVACL/Xml/Request/PrincipalSearchPropertySetReport.php
index ade157b19..64d1f7f86 100644
--- a/vendor/sabre/dav/lib/DAVACL/Xml/Request/PrincipalSearchPropertySetReport.php
+++ b/vendor/sabre/dav/lib/DAVACL/Xml/Request/PrincipalSearchPropertySetReport.php
@@ -2,9 +2,9 @@
namespace Sabre\DAVACL\Xml\Request;
+use Sabre\DAV\Exception\BadRequest;
use Sabre\Xml\Reader;
use Sabre\Xml\XmlDeserializable;
-use Sabre\DAV\Exception\BadRequest;
/**
* PrincipalSearchPropertySetReport request parser.
@@ -23,7 +23,7 @@ class PrincipalSearchPropertySetReport implements XmlDeserializable {
/**
* The deserialize method is called during xml parsing.
*
- * This method is called statictly, this is because in theory this method
+ * This method is called statically, this is because in theory this method
* may be used as a type of constructor, or factory method.
*
* Often you want to return an instance of the current class, but you are
diff --git a/vendor/sabre/dav/tests/Sabre/CalDAV/Backend/AbstractPDOTest.php b/vendor/sabre/dav/tests/Sabre/CalDAV/Backend/AbstractPDOTest.php
index 2a00f7925..406dbe0e8 100644
--- a/vendor/sabre/dav/tests/Sabre/CalDAV/Backend/AbstractPDOTest.php
+++ b/vendor/sabre/dav/tests/Sabre/CalDAV/Backend/AbstractPDOTest.php
@@ -280,7 +280,7 @@ abstract class AbstractPDOTest extends \PHPUnit_Framework_TestCase {
],
];
- $result = $backend->getMultipleCalendarObjects($returnedId, [ 'id-1', 'id-2' ]);
+ $result = $backend->getMultipleCalendarObjects($returnedId, ['id-1', 'id-2']);
foreach ($check as $index => $props) {
@@ -441,7 +441,7 @@ abstract class AbstractPDOTest extends \PHPUnit_Framework_TestCase {
/**
* @depends testCreateCalendarObject
*/
- function testCreateCalendarObjectInfiniteReccurence() {
+ function testCreateCalendarObjectInfiniteRecurrence() {
$backend = new PDO($this->pdo);
$returnedId = $backend->createCalendar('principals/user2', 'somerandomid', []);
@@ -470,7 +470,7 @@ abstract class AbstractPDOTest extends \PHPUnit_Framework_TestCase {
/**
* @depends testCreateCalendarObject
*/
- function testCreateCalendarObjectEndingReccurence() {
+ function testCreateCalendarObjectEndingRecurrence() {
$backend = new PDO($this->pdo);
$returnedId = $backend->createCalendar('principals/user2', 'somerandomid', []);
@@ -1246,8 +1246,8 @@ abstract class AbstractPDOTest extends \PHPUnit_Framework_TestCase {
$calendar['id'],
[
new Sharee([
- 'href' => 'mailto:user@example.org',
- 'access' => \Sabre\DAV\Sharing\Plugin::ACCESS_NOACCESS,
+ 'href' => 'mailto:user@example.org',
+ 'access' => \Sabre\DAV\Sharing\Plugin::ACCESS_NOACCESS,
])
]
);
@@ -1263,8 +1263,8 @@ abstract class AbstractPDOTest extends \PHPUnit_Framework_TestCase {
$calendar['id'],
[
new Sharee([
- 'href' => 'principals/user2',
- 'access' => \Sabre\DAV\Sharing\Plugin::ACCESS_NOACCESS,
+ 'href' => 'principals/user2',
+ 'access' => \Sabre\DAV\Sharing\Plugin::ACCESS_NOACCESS,
])
]
);
diff --git a/vendor/sabre/dav/tests/Sabre/CalDAV/Backend/Mock.php b/vendor/sabre/dav/tests/Sabre/CalDAV/Backend/Mock.php
index d4dcc07dc..cc665cd8f 100644
--- a/vendor/sabre/dav/tests/Sabre/CalDAV/Backend/Mock.php
+++ b/vendor/sabre/dav/tests/Sabre/CalDAV/Backend/Mock.php
@@ -2,8 +2,8 @@
namespace Sabre\CalDAV\Backend;
-use Sabre\DAV;
use Sabre\CalDAV;
+use Sabre\DAV;
class Mock extends AbstractBackend {
diff --git a/vendor/sabre/dav/tests/Sabre/CalDAV/CalendarObjectTest.php b/vendor/sabre/dav/tests/Sabre/CalDAV/CalendarObjectTest.php
index 0d98922ff..c92cde661 100644
--- a/vendor/sabre/dav/tests/Sabre/CalDAV/CalendarObjectTest.php
+++ b/vendor/sabre/dav/tests/Sabre/CalDAV/CalendarObjectTest.php
@@ -114,7 +114,7 @@ class CalendarObjectTest extends \PHPUnit_Framework_TestCase {
$obj = $children[0];
$obj->delete();
- $children2 = $this->calendar->getChildren();
+ $children2 = $this->calendar->getChildren();
$this->assertEquals(count($children) - 1, count($children2));
}
diff --git a/vendor/sabre/dav/tests/Sabre/CalDAV/CalendarQueryValidatorTest.php b/vendor/sabre/dav/tests/Sabre/CalDAV/CalendarQueryValidatorTest.php
index 4c2558a9b..f3305163b 100644
--- a/vendor/sabre/dav/tests/Sabre/CalDAV/CalendarQueryValidatorTest.php
+++ b/vendor/sabre/dav/tests/Sabre/CalDAV/CalendarQueryValidatorTest.php
@@ -21,6 +21,9 @@ ICS;
}
/**
+ * @param string $icalObject
+ * @param array $filters
+ * @param int $outcome
* @dataProvider provider
*/
function testValid($icalObject, $filters, $outcome) {
diff --git a/vendor/sabre/dav/tests/Sabre/CalDAV/FreeBusyReportTest.php b/vendor/sabre/dav/tests/Sabre/CalDAV/FreeBusyReportTest.php
index 7a756774f..7604c7f4c 100644
--- a/vendor/sabre/dav/tests/Sabre/CalDAV/FreeBusyReportTest.php
+++ b/vendor/sabre/dav/tests/Sabre/CalDAV/FreeBusyReportTest.php
@@ -11,11 +11,11 @@ require_once 'Sabre/HTTP/ResponseMock.php';
class FreeBusyReportTest extends \PHPUnit_Framework_TestCase {
/**
- * @var Sabre\CalDAV\Plugin
+ * @var Plugin
*/
protected $plugin;
/**
- * @var Sabre\DAV\Server
+ * @var DAV\Server
*/
protected $server;
diff --git a/vendor/sabre/dav/tests/Sabre/CalDAV/ICSExportPluginTest.php b/vendor/sabre/dav/tests/Sabre/CalDAV/ICSExportPluginTest.php
index 9719529fb..75412577e 100644
--- a/vendor/sabre/dav/tests/Sabre/CalDAV/ICSExportPluginTest.php
+++ b/vendor/sabre/dav/tests/Sabre/CalDAV/ICSExportPluginTest.php
@@ -3,9 +3,9 @@
namespace Sabre\CalDAV;
use Sabre\DAV;
+use Sabre\DAVACL;
use Sabre\HTTP;
use Sabre\VObject;
-use Sabre\DAVACL;
class ICSExportPluginTest extends \Sabre\DAVServerTest {
diff --git a/vendor/sabre/dav/tests/Sabre/CalDAV/PluginTest.php b/vendor/sabre/dav/tests/Sabre/CalDAV/PluginTest.php
index 8d538dee5..859f6aa0c 100644
--- a/vendor/sabre/dav/tests/Sabre/CalDAV/PluginTest.php
+++ b/vendor/sabre/dav/tests/Sabre/CalDAV/PluginTest.php
@@ -2,11 +2,11 @@
namespace Sabre\CalDAV;
-use Sabre\DAVACL;
-use Sabre\DAV;
-use Sabre\HTTP;
use DateTime;
use DateTimeZone;
+use Sabre\DAV;
+use Sabre\DAVACL;
+use Sabre\HTTP;
class PluginTest extends \PHPUnit_Framework_TestCase {
diff --git a/vendor/sabre/dav/tests/Sabre/CalDAV/SharingPluginTest.php b/vendor/sabre/dav/tests/Sabre/CalDAV/SharingPluginTest.php
index 6e9e88419..9589176a3 100644
--- a/vendor/sabre/dav/tests/Sabre/CalDAV/SharingPluginTest.php
+++ b/vendor/sabre/dav/tests/Sabre/CalDAV/SharingPluginTest.php
@@ -194,8 +194,8 @@ RRR;
$this->assertEquals(
[
new Sharee([
- 'href' => 'mailto:joe@example.org',
- 'properties' => [
+ 'href' => 'mailto:joe@example.org',
+ 'properties' => [
'{DAV:}displayname' => 'Joe Shmoe',
],
'access' => \Sabre\DAV\Sharing\Plugin::ACCESS_READWRITE,
diff --git a/vendor/sabre/dav/tests/Sabre/CardDAV/AddressBookQueryTest.php b/vendor/sabre/dav/tests/Sabre/CardDAV/AddressBookQueryTest.php
index 2c3171bf3..f8da38a16 100644
--- a/vendor/sabre/dav/tests/Sabre/CardDAV/AddressBookQueryTest.php
+++ b/vendor/sabre/dav/tests/Sabre/CardDAV/AddressBookQueryTest.php
@@ -2,8 +2,8 @@
namespace Sabre\CardDAV;
-use Sabre\HTTP;
use Sabre\DAV;
+use Sabre\HTTP;
require_once 'Sabre/CardDAV/AbstractPluginTest.php';
require_once 'Sabre/HTTP/ResponseMock.php';
@@ -288,14 +288,14 @@ class AddressBookQueryTest extends AbstractPluginTest {
);
$request->setBody(
-'<?xml version="1.0"?>
+ '<?xml version="1.0"?>
<c:addressbook-query xmlns:d="DAV:" xmlns:c="urn:ietf:params:xml:ns:carddav">
<d:prop>
<c:address-data content-type="application/vcard+json" />
<d:getetag />
</d:prop>
</c:addressbook-query>'
- );
+ );
$response = new HTTP\ResponseMock();
@@ -305,6 +305,51 @@ class AddressBookQueryTest extends AbstractPluginTest {
$this->server->exec();
$this->assertEquals(415, $response->status, 'Incorrect status code. Full response body:' . $response->body);
+ }
+
+ function testAddressBookProperties() {
+
+ $request = new HTTP\Request(
+ 'REPORT',
+ '/addressbooks/user1/book3',
+ ['Depth' => '1']
+ );
+
+ $request->setBody(
+ '<?xml version="1.0"?>
+<c:addressbook-query xmlns:d="DAV:" xmlns:c="urn:ietf:params:xml:ns:carddav">
+ <d:prop>
+ <c:address-data>
+ <c:prop name="FN"/>
+ <c:prop name="BDAY"/>
+ </c:address-data>
+ <d:getetag />
+ </d:prop>
+</c:addressbook-query>'
+ );
+
+ $response = new HTTP\ResponseMock();
+
+ $this->server->httpRequest = $request;
+ $this->server->httpResponse = $response;
+
+ $this->server->exec();
+
+ $this->assertEquals(207, $response->status, 'Incorrect status code. Full response body:' . $response->body);
+
+ // using the client for parsing
+ $client = new DAV\Client(['baseUri' => '/']);
+
+ $result = $client->parseMultiStatus($response->body);
+
+ $this->assertEquals([
+ '/addressbooks/user1/book3/card3' => [
+ 200 => [
+ '{DAV:}getetag' => '"' . md5("BEGIN:VCARD\nVERSION:3.0\nUID:12345\nFN:Test-Card\nEMAIL;TYPE=home:bar@example.org\nEND:VCARD") . '"',
+ '{urn:ietf:params:xml:ns:carddav}address-data' => "BEGIN:VCARD\r\nVERSION:3.0\r\nUID:12345\r\nFN:Test-Card\r\nEND:VCARD\r\n",
+ ],
+ ],
+ ], $result);
}
}
diff --git a/vendor/sabre/dav/tests/Sabre/CardDAV/AddressBookTest.php b/vendor/sabre/dav/tests/Sabre/CardDAV/AddressBookTest.php
index 1a36fd10c..1f0064dd3 100644
--- a/vendor/sabre/dav/tests/Sabre/CardDAV/AddressBookTest.php
+++ b/vendor/sabre/dav/tests/Sabre/CardDAV/AddressBookTest.php
@@ -85,7 +85,7 @@ class AddressBookTest extends \PHPUnit_Framework_TestCase {
function testDelete() {
$this->ab->delete();
- $this->assertEquals([], $this->backend->addressBooks);
+ $this->assertEquals(1, count($this->backend->addressBooks));
}
@@ -175,7 +175,7 @@ class AddressBookTest extends \PHPUnit_Framework_TestCase {
$backend = new Backend\PDO(
$this->getPDO()
);
- $ab = new AddressBook($backend, [ 'id' => 1, '{DAV:}sync-token' => 2]);
+ $ab = new AddressBook($backend, ['id' => 1, '{DAV:}sync-token' => 2]);
$this->assertEquals(2, $ab->getSyncToken());
}
@@ -187,7 +187,7 @@ class AddressBookTest extends \PHPUnit_Framework_TestCase {
$backend = new Backend\PDO(
$this->getPDO()
);
- $ab = new AddressBook($backend, [ 'id' => 1, '{http://sabredav.org/ns}sync-token' => 2]);
+ $ab = new AddressBook($backend, ['id' => 1, '{http://sabredav.org/ns}sync-token' => 2]);
$this->assertEquals(2, $ab->getSyncToken());
}
diff --git a/vendor/sabre/dav/tests/Sabre/CardDAV/Backend/Mock.php b/vendor/sabre/dav/tests/Sabre/CardDAV/Backend/Mock.php
index 840b898e8..8638dc74a 100644
--- a/vendor/sabre/dav/tests/Sabre/CardDAV/Backend/Mock.php
+++ b/vendor/sabre/dav/tests/Sabre/CardDAV/Backend/Mock.php
@@ -20,6 +20,12 @@ class Mock extends AbstractBackend {
'principaluri' => 'principals/user1',
'{DAV:}displayname' => 'd-name',
],
+ [
+ 'id' => 'bar',
+ 'uri' => 'book3',
+ 'principaluri' => 'principals/user1',
+ '{DAV:}displayname' => 'd-name',
+ ],
];
$card2 = fopen('php://memory', 'r+');
@@ -30,6 +36,9 @@ class Mock extends AbstractBackend {
'card1' => "BEGIN:VCARD\nVERSION:3.0\nUID:12345\nEND:VCARD",
'card2' => $card2,
],
+ 'bar' => [
+ 'card3' => "BEGIN:VCARD\nVERSION:3.0\nUID:12345\nFN:Test-Card\nEMAIL;TYPE=home:bar@example.org\nEND:VCARD",
+ ],
];
}
@@ -58,7 +67,7 @@ class Mock extends AbstractBackend {
* Calling the handle method is like telling the PropPatch object "I
* promise I can handle updating this property".
*
- * Read the PropPatch documenation for more info and examples.
+ * Read the PropPatch documentation for more info and examples.
*
* @param string $addressBookId
* @param \Sabre\DAV\PropPatch $propPatch
@@ -117,7 +126,7 @@ class Mock extends AbstractBackend {
* calculating them. If they are specified, you can also ommit carddata.
* This may speed up certain requests, especially with large cards.
*
- * @param mixed $addressbookId
+ * @param mixed $addressBookId
* @return array
*/
function getCards($addressBookId) {
diff --git a/vendor/sabre/dav/tests/Sabre/CardDAV/MultiGetTest.php b/vendor/sabre/dav/tests/Sabre/CardDAV/MultiGetTest.php
index d79239d0f..2d57c6ae7 100644
--- a/vendor/sabre/dav/tests/Sabre/CardDAV/MultiGetTest.php
+++ b/vendor/sabre/dav/tests/Sabre/CardDAV/MultiGetTest.php
@@ -2,8 +2,8 @@
namespace Sabre\CardDAV;
-use Sabre\HTTP;
use Sabre\DAV;
+use Sabre\HTTP;
require_once 'Sabre/HTTP/ResponseMock.php';
diff --git a/vendor/sabre/dav/tests/Sabre/CardDAV/SogoStripContentTypeTest.php b/vendor/sabre/dav/tests/Sabre/CardDAV/SogoStripContentTypeTest.php
index 0ba4fd669..d4bc48098 100644
--- a/vendor/sabre/dav/tests/Sabre/CardDAV/SogoStripContentTypeTest.php
+++ b/vendor/sabre/dav/tests/Sabre/CardDAV/SogoStripContentTypeTest.php
@@ -2,8 +2,8 @@
namespace Sabre\CardDAV;
-use Sabre\HTTP;
use Sabre\DAV\PropFind;
+use Sabre\HTTP;
class SogoStripContentTypeTest extends \Sabre\DAVServerTest {
diff --git a/vendor/sabre/dav/tests/Sabre/CardDAV/ValidateFilterTest.php b/vendor/sabre/dav/tests/Sabre/CardDAV/ValidateFilterTest.php
index 57ac21b4a..03c468f86 100644
--- a/vendor/sabre/dav/tests/Sabre/CardDAV/ValidateFilterTest.php
+++ b/vendor/sabre/dav/tests/Sabre/CardDAV/ValidateFilterTest.php
@@ -7,6 +7,11 @@ require_once 'Sabre/CardDAV/AbstractPluginTest.php';
class ValidateFilterTest extends AbstractPluginTest {
/**
+ * @param string $input
+ * @param array $filters
+ * @param string $test
+ * @param bool $result
+ * @param string|null $message
* @dataProvider data
*/
function testFilter($input, $filters, $test, $result, $message = null) {
diff --git a/vendor/sabre/dav/tests/Sabre/CardDAV/ValidateVCardTest.php b/vendor/sabre/dav/tests/Sabre/CardDAV/ValidateVCardTest.php
index dda8a0c37..acba2cfc8 100644
--- a/vendor/sabre/dav/tests/Sabre/CardDAV/ValidateVCardTest.php
+++ b/vendor/sabre/dav/tests/Sabre/CardDAV/ValidateVCardTest.php
@@ -3,8 +3,8 @@
namespace Sabre\CardDAV;
use Sabre\DAV;
-use Sabre\HTTP;
use Sabre\DAVACL;
+use Sabre\HTTP;
require_once 'Sabre/HTTP/ResponseMock.php';
@@ -293,10 +293,10 @@ VCF;
$response = $this->request($request, 204);
$expected = [
- 'uri' => 'blabla.vcf',
- 'carddata' => $body,
- 'size' => strlen($body),
- 'etag' => '"' . md5($body) . '"',
+ 'uri' => 'blabla.vcf',
+ 'carddata' => $body,
+ 'size' => strlen($body),
+ 'etag' => '"' . md5($body) . '"',
];
$this->assertEquals($expected, $this->cardBackend->getCard('addressbook1', 'blabla.vcf'));
diff --git a/vendor/sabre/dav/tests/Sabre/DAV/Auth/Backend/Mock.php b/vendor/sabre/dav/tests/Sabre/DAV/Auth/Backend/Mock.php
index b30b3f143..369bc249e 100644
--- a/vendor/sabre/dav/tests/Sabre/DAV/Auth/Backend/Mock.php
+++ b/vendor/sabre/dav/tests/Sabre/DAV/Auth/Backend/Mock.php
@@ -76,6 +76,8 @@ class Mock implements BackendInterface {
* append your own WWW-Authenticate header instead of overwriting the
* existing one.
*
+ * @param RequestInterface $request
+ * @param ResponseInterface $response
* @return void
*/
function challenge(RequestInterface $request, ResponseInterface $response) {
diff --git a/vendor/sabre/dav/tests/Sabre/DAV/Auth/PluginTest.php b/vendor/sabre/dav/tests/Sabre/DAV/Auth/PluginTest.php
index b566dd757..743446127 100644
--- a/vendor/sabre/dav/tests/Sabre/DAV/Auth/PluginTest.php
+++ b/vendor/sabre/dav/tests/Sabre/DAV/Auth/PluginTest.php
@@ -2,8 +2,8 @@
namespace Sabre\DAV\Auth;
-use Sabre\HTTP;
use Sabre\DAV;
+use Sabre\HTTP;
class PluginTest extends \PHPUnit_Framework_TestCase {
diff --git a/vendor/sabre/dav/tests/Sabre/DAV/ClientTest.php b/vendor/sabre/dav/tests/Sabre/DAV/ClientTest.php
index 4cf27dfaa..687f61e2f 100644
--- a/vendor/sabre/dav/tests/Sabre/DAV/ClientTest.php
+++ b/vendor/sabre/dav/tests/Sabre/DAV/ClientTest.php
@@ -224,7 +224,7 @@ XML;
XML;
$client->response = new Response(207, [], $responseBody);
- $result = $client->propPatch('foo', ['{DAV:}displayname' => 'hi', '{urn:zim}gir' => null], 1);
+ $result = $client->propPatch('foo', ['{DAV:}displayname' => 'hi', '{urn:zim}gir' => null]);
$this->assertTrue($result);
$request = $client->request;
$this->assertEquals('PROPPATCH', $request->getMethod());
@@ -246,7 +246,7 @@ XML;
]);
$client->response = new Response(403, [], '');
- $client->propPatch('foo', ['{DAV:}displayname' => 'hi', '{urn:zim}gir' => null], 1);
+ $client->propPatch('foo', ['{DAV:}displayname' => 'hi', '{urn:zim}gir' => null]);
}
@@ -276,7 +276,7 @@ XML;
XML;
$client->response = new Response(207, [], $responseBody);
- $client->propPatch('foo', ['{DAV:}displayname' => 'hi', '{urn:zim}gir' => null], 1);
+ $client->propPatch('foo', ['{DAV:}displayname' => 'hi', '{urn:zim}gir' => null]);
}
diff --git a/vendor/sabre/dav/tests/Sabre/DAV/Exception/LockedTest.php b/vendor/sabre/dav/tests/Sabre/DAV/Exception/LockedTest.php
index 8788475cb..174a561b5 100644
--- a/vendor/sabre/dav/tests/Sabre/DAV/Exception/LockedTest.php
+++ b/vendor/sabre/dav/tests/Sabre/DAV/Exception/LockedTest.php
@@ -2,8 +2,8 @@
namespace Sabre\DAV\Exception;
-use Sabre\DAV;
use DOMDocument;
+use Sabre\DAV;
class LockedTest extends \PHPUnit_Framework_TestCase {
diff --git a/vendor/sabre/dav/tests/Sabre/DAV/Issue33Test.php b/vendor/sabre/dav/tests/Sabre/DAV/Issue33Test.php
index edd09e634..ba2cf3dc1 100644
--- a/vendor/sabre/dav/tests/Sabre/DAV/Issue33Test.php
+++ b/vendor/sabre/dav/tests/Sabre/DAV/Issue33Test.php
@@ -99,7 +99,7 @@ class Issue33Test extends \PHPUnit_Framework_TestCase {
$server->sapi = new HTTP\SapiMock();
$server->exec();
- $this->assertTrue(file_exists(SABRE_TEMPDIR . '/issue33/' . urldecode('%C3%A0fo%C3%B3')));
+ $this->assertTrue(file_exists(SABRE_TEMPDIR . '/issue33/' . urldecode('%C3%A0fo%C3%B3')));
}
diff --git a/vendor/sabre/dav/tests/Sabre/DAV/Locks/MSWordTest.php b/vendor/sabre/dav/tests/Sabre/DAV/Locks/MSWordTest.php
index f08f19da5..1111db5b5 100644
--- a/vendor/sabre/dav/tests/Sabre/DAV/Locks/MSWordTest.php
+++ b/vendor/sabre/dav/tests/Sabre/DAV/Locks/MSWordTest.php
@@ -2,8 +2,8 @@
namespace Sabre\DAV\Locks;
-use Sabre\HTTP;
use Sabre\DAV;
+use Sabre\HTTP;
require_once 'Sabre/HTTP/ResponseMock.php';
require_once 'Sabre/TestUtil.php';
@@ -112,9 +112,9 @@ class MSWordTest extends \PHPUnit_Framework_TestCase {
function getPutRequest($lockToken) {
$request = HTTP\Sapi::createFromServerArray([
- 'REQUEST_METHOD' => 'PUT',
- 'REQUEST_URI' => '/Nouveau%20Microsoft%20Office%20Excel%20Worksheet.xlsx',
- 'HTTP_IF' => 'If: (' . $lockToken . ')',
+ 'REQUEST_METHOD' => 'PUT',
+ 'REQUEST_URI' => '/Nouveau%20Microsoft%20Office%20Excel%20Worksheet.xlsx',
+ 'HTTP_IF' => 'If: (' . $lockToken . ')',
]);
$request->setBody('FAKE BODY');
return $request;
diff --git a/vendor/sabre/dav/tests/Sabre/DAV/Locks/PluginTest.php b/vendor/sabre/dav/tests/Sabre/DAV/Locks/PluginTest.php
index 6511d4e7d..dbbf6757a 100644
--- a/vendor/sabre/dav/tests/Sabre/DAV/Locks/PluginTest.php
+++ b/vendor/sabre/dav/tests/Sabre/DAV/Locks/PluginTest.php
@@ -2,8 +2,8 @@
namespace Sabre\DAV\Locks;
-use Sabre\HTTP;
use Sabre\DAV;
+use Sabre\HTTP;
require_once 'Sabre/DAV/AbstractServer.php';
@@ -168,7 +168,7 @@ class PluginTest extends DAV\AbstractServer {
$this->response = new HTTP\ResponseMock();
$this->server->httpResponse = $this->response;
- $request = new HTTP\Request('LOCK', '/test.txt', ['If' => '(' . $lockToken . ')' ]);
+ $request = new HTTP\Request('LOCK', '/test.txt', ['If' => '(' . $lockToken . ')']);
$request->setBody('');
$this->server->httpRequest = $request;
@@ -203,7 +203,7 @@ class PluginTest extends DAV\AbstractServer {
$this->response = new HTTP\ResponseMock();
$this->server->httpResponse = $this->response;
- $request = new HTTP\Request('LOCK', '/test.txt', ['If' => '(' . $lockToken . 'foobar) (<opaquelocktoken:anotherbadtoken>)' ]);
+ $request = new HTTP\Request('LOCK', '/test.txt', ['If' => '(' . $lockToken . 'foobar) (<opaquelocktoken:anotherbadtoken>)']);
$request->setBody('');
$this->server->httpRequest = $request;
diff --git a/vendor/sabre/dav/tests/Sabre/DAV/Mock/Collection.php b/vendor/sabre/dav/tests/Sabre/DAV/Mock/Collection.php
index 6ccab4f66..fded5e474 100644
--- a/vendor/sabre/dav/tests/Sabre/DAV/Mock/Collection.php
+++ b/vendor/sabre/dav/tests/Sabre/DAV/Mock/Collection.php
@@ -30,6 +30,7 @@ class Collection extends DAV\Collection {
*
* @param string $name
* @param array $children
+ * @param Collection $parent
* @return void
*/
function __construct($name, array $children = [], Collection $parent = null) {
@@ -122,6 +123,8 @@ class Collection extends DAV\Collection {
/**
* Adds an already existing node to this collection.
+ *
+ * @param \Sabre\DAV\INode $node
*/
function addNode(\Sabre\DAV\INode $node) {
diff --git a/vendor/sabre/dav/tests/Sabre/DAV/Mock/File.php b/vendor/sabre/dav/tests/Sabre/DAV/Mock/File.php
index 23855e3c5..a624b6b6b 100644
--- a/vendor/sabre/dav/tests/Sabre/DAV/Mock/File.php
+++ b/vendor/sabre/dav/tests/Sabre/DAV/Mock/File.php
@@ -24,7 +24,9 @@ class File extends DAV\File {
* Creates the object
*
* @param string $name
- * @param array $children
+ * @param resource $contents
+ * @param Collection $parent
+ * @param int $lastModified
* @return void
*/
function __construct($name, $contents, Collection $parent = null, $lastModified = -1) {
@@ -57,6 +59,7 @@ class File extends DAV\File {
/**
* Changes the name of the node.
*
+ * @param string $name
* @return void
*/
function setName($name) {
@@ -70,7 +73,7 @@ class File extends DAV\File {
*
* The data argument is a readable stream resource.
*
- * After a succesful put operation, you may choose to return an ETag. The
+ * After a successful put operation, you may choose to return an ETag. The
* etag must always be surrounded by double-quotes. These quotes must
* appear in the actual string you're returning.
*
diff --git a/vendor/sabre/dav/tests/Sabre/DAV/PartialUpdate/SpecificationTest.php b/vendor/sabre/dav/tests/Sabre/DAV/PartialUpdate/SpecificationTest.php
index ca8ca3f6e..2c6274173 100644
--- a/vendor/sabre/dav/tests/Sabre/DAV/PartialUpdate/SpecificationTest.php
+++ b/vendor/sabre/dav/tests/Sabre/DAV/PartialUpdate/SpecificationTest.php
@@ -38,6 +38,11 @@ class SpecificationTest extends \PHPUnit_Framework_TestCase {
}
/**
+ * @param string $headerValue
+ * @param string $httpStatus
+ * @param string $endResult
+ * @param int $contentLength
+ *
* @dataProvider data
*/
function testUpdateRange($headerValue, $httpStatus, $endResult, $contentLength = 4) {
diff --git a/vendor/sabre/dav/tests/Sabre/DAV/ServerEventsTest.php b/vendor/sabre/dav/tests/Sabre/DAV/ServerEventsTest.php
index 4c576f108..42759647a 100644
--- a/vendor/sabre/dav/tests/Sabre/DAV/ServerEventsTest.php
+++ b/vendor/sabre/dav/tests/Sabre/DAV/ServerEventsTest.php
@@ -39,8 +39,8 @@ class ServerEventsTest extends AbstractServer {
$this->server->on('afterResponse', [$mock, 'afterResponseCallback']);
$this->server->httpRequest = HTTP\Sapi::createFromServerArray([
- 'REQUEST_METHOD' => 'GET',
- 'REQUEST_URI' => '/test.txt',
+ 'REQUEST_METHOD' => 'GET',
+ 'REQUEST_URI' => '/test.txt',
]);
$this->server->exec();
@@ -118,8 +118,8 @@ class ServerEventsTest extends AbstractServer {
);
} catch (Exception $e) {}
- $this->assertEquals(2, $k);
-
+ // Fun fact, PHP 7.1 changes the order when sorting-by-callback.
+ $this->assertTrue($k >= 2 && $k <= 3);
}
diff --git a/vendor/sabre/dav/tests/Sabre/DAV/ServerRangeTest.php b/vendor/sabre/dav/tests/Sabre/DAV/ServerRangeTest.php
index bafbef6e4..81224d687 100644
--- a/vendor/sabre/dav/tests/Sabre/DAV/ServerRangeTest.php
+++ b/vendor/sabre/dav/tests/Sabre/DAV/ServerRangeTest.php
@@ -144,7 +144,7 @@ class ServerRangeTest extends \Sabre\DAVServerTest {
'Content-Length' => [4],
'Content-Range' => ['bytes 2-5/12'],
// 'ETag' => ['"' . md5('Test contents') . '"'],
- 'Last-Modified' => [$this->lastModified],
+ 'Last-Modified' => [$this->lastModified],
],
$response->getHeaders()
);
diff --git a/vendor/sabre/dav/tests/Sabre/DAV/StringUtilTest.php b/vendor/sabre/dav/tests/Sabre/DAV/StringUtilTest.php
index 8888f0276..e98fe9048 100644
--- a/vendor/sabre/dav/tests/Sabre/DAV/StringUtilTest.php
+++ b/vendor/sabre/dav/tests/Sabre/DAV/StringUtilTest.php
@@ -5,6 +5,13 @@ namespace Sabre\DAV;
class StringUtilTest extends \PHPUnit_Framework_TestCase {
/**
+ * @param string $haystack
+ * @param string $needle
+ * @param string $collation
+ * @param string $matchType
+ * @param string $result
+ * @throws Exception\BadRequest
+ *
* @dataProvider dataset
*/
function testTextMatch($haystack, $needle, $collation, $matchType, $result) {
diff --git a/vendor/sabre/dav/tests/Sabre/DAV/TreeTest.php b/vendor/sabre/dav/tests/Sabre/DAV/TreeTest.php
index ad33200c8..e719e38d5 100644
--- a/vendor/sabre/dav/tests/Sabre/DAV/TreeTest.php
+++ b/vendor/sabre/dav/tests/Sabre/DAV/TreeTest.php
@@ -200,8 +200,8 @@ class TreeFileTester extends File implements IProperties {
* To update specific properties, call the 'handle' method on this object.
* Read the PropPatch documentation for more information.
*
- * @param array $mutations
- * @return bool|array
+ * @param PropPatch $propPatch
+ * @return void
*/
function propPatch(PropPatch $propPatch) {
@@ -220,6 +220,7 @@ class TreeMultiGetTester extends TreeDirectoryTester implements IMultiGet {
*
* If any children are not found, you do not have to return them.
*
+ * @param array $paths
* @return array
*/
function getMultipleChildren(array $paths) {
diff --git a/vendor/sabre/dav/tests/Sabre/DAVACL/PrincipalBackend/Mock.php b/vendor/sabre/dav/tests/Sabre/DAVACL/PrincipalBackend/Mock.php
index afb094a39..1464f4c26 100644
--- a/vendor/sabre/dav/tests/Sabre/DAVACL/PrincipalBackend/Mock.php
+++ b/vendor/sabre/dav/tests/Sabre/DAVACL/PrincipalBackend/Mock.php
@@ -128,7 +128,7 @@ class Mock extends AbstractBackend {
* Calling the handle method is like telling the PropPatch object "I
* promise I can handle updating this property".
*
- * Read the PropPatch documenation for more info and examples.
+ * Read the PropPatch documentation for more info and examples.
*
* @param string $path
* @param \Sabre\DAV\PropPatch $propPatch
diff --git a/vendor/sabre/http/.travis.yml b/vendor/sabre/http/.travis.yml
index 490e42e1e..8ae84d90f 100644
--- a/vendor/sabre/http/.travis.yml
+++ b/vendor/sabre/http/.travis.yml
@@ -4,6 +4,7 @@ php:
- 5.5
- 5.6
- 7
+ - 7.1
- hhvm
matrix:
@@ -16,7 +17,8 @@ env:
before_script:
- - composer self-update
+ - rm -f ~/.phpenv/versions/$(phpenv version-name)/etc/conf.d/xdebug.ini
+# - composer self-update
- composer update --prefer-source $PREFER_LOWEST
script:
diff --git a/vendor/sabre/http/CHANGELOG.md b/vendor/sabre/http/CHANGELOG.md
index 9a751d8fb..00be2d887 100644
--- a/vendor/sabre/http/CHANGELOG.md
+++ b/vendor/sabre/http/CHANGELOG.md
@@ -1,19 +1,31 @@
ChangeLog
=========
+4.2.3 (2017-06-12)
+------------------
+
+* #74, #77: Work around 4GB file size limit at 32 Bit systems
+
+
+4.2.2 (2017-01-02)
+------------------
+
+* #72: Handling clients that send invalid `Content-Length` headers.
+
+
4.2.1 (2016-01-06)
------------------
* #56: `getBodyAsString` now returns at most as many bytes as the contents of
the `Content-Length` header. This allows users to pass much larger strings
without having to copy and truncate them.
+* The client now sets a default `User-Agent` header identifying this library.
4.2.0 (2016-01-04)
------------------
* This package now supports sabre/event 3.0.
-* The client now sets a default `User-Agent` header identifying this library.
4.1.0 (2015-09-04)
diff --git a/vendor/sabre/http/LICENSE b/vendor/sabre/http/LICENSE
index 19812ad7a..864041b22 100644
--- a/vendor/sabre/http/LICENSE
+++ b/vendor/sabre/http/LICENSE
@@ -1,4 +1,4 @@
-Copyright (C) 2009-2016 fruux GmbH (https://fruux.com/)
+Copyright (C) 2009-2017 fruux GmbH (https://fruux.com/)
All rights reserved.
diff --git a/vendor/sabre/http/composer.json b/vendor/sabre/http/composer.json
index b061194cf..507d5d28d 100644
--- a/vendor/sabre/http/composer.json
+++ b/vendor/sabre/http/composer.json
@@ -7,6 +7,7 @@
"require" : {
"php" : ">=5.4",
"ext-mbstring" : "*",
+ "ext-ctype" : "*",
"sabre/event" : ">=1.0.0,<4.0.0",
"sabre/uri" : "~1.0"
},
diff --git a/vendor/sabre/http/lib/Message.php b/vendor/sabre/http/lib/Message.php
index 5c6887d8a..45bd18398 100644
--- a/vendor/sabre/http/lib/Message.php
+++ b/vendor/sabre/http/lib/Message.php
@@ -75,12 +75,11 @@ abstract class Message implements MessageInterface {
return '';
}
$contentLength = $this->getHeader('Content-Length');
- if (null === $contentLength) {
- return stream_get_contents($body);
- } else {
+ if (is_int($contentLength) || ctype_digit($contentLength)) {
return stream_get_contents($body, $contentLength);
+ } else {
+ return stream_get_contents($body);
}
-
}
/**
@@ -189,7 +188,7 @@ abstract class Message implements MessageInterface {
/**
* Updates a HTTP header.
*
- * The case-sensitity of the name value must be retained as-is.
+ * The case-sensitivity of the name value must be retained as-is.
*
* If the header already existed, it will be overwritten.
*
@@ -270,10 +269,11 @@ abstract class Message implements MessageInterface {
/**
* Removes a HTTP header.
*
- * The specified header name must be treated as case-insenstive.
+ * The specified header name must be treated as case-insensitive.
* This method should return true if the header was successfully deleted,
* and false if the header did not exist.
*
+ * @param string $name
* @return bool
*/
function removeHeader($name) {
diff --git a/vendor/sabre/http/lib/MessageDecoratorTrait.php b/vendor/sabre/http/lib/MessageDecoratorTrait.php
index f104af38d..1cb32da22 100644
--- a/vendor/sabre/http/lib/MessageDecoratorTrait.php
+++ b/vendor/sabre/http/lib/MessageDecoratorTrait.php
@@ -144,7 +144,7 @@ trait MessageDecoratorTrait {
/**
* Updates a HTTP header.
*
- * The case-sensitity of the name value must be retained as-is.
+ * The case-sensitivity of the name value must be retained as-is.
*
* If the header already existed, it will be overwritten.
*
@@ -210,15 +210,16 @@ trait MessageDecoratorTrait {
/**
* Removes a HTTP header.
*
- * The specified header name must be treated as case-insenstive.
+ * The specified header name must be treated as case-insensitive.
* This method should return true if the header was successfully deleted,
* and false if the header did not exist.
*
+ * @param string $name
* @return bool
*/
function removeHeader($name) {
- $this->inner->removeHeader($name);
+ return $this->inner->removeHeader($name);
}
diff --git a/vendor/sabre/http/lib/MessageInterface.php b/vendor/sabre/http/lib/MessageInterface.php
index 55d8485c1..df55beb2f 100644
--- a/vendor/sabre/http/lib/MessageInterface.php
+++ b/vendor/sabre/http/lib/MessageInterface.php
@@ -44,7 +44,7 @@ interface MessageInterface {
/**
* Updates the body resource with a new stream.
*
- * @param resource $body
+ * @param resource|string $body
* @return void
*/
function setBody($body);
@@ -153,6 +153,7 @@ interface MessageInterface {
* This method should return true if the header was successfully deleted,
* and false if the header did not exist.
*
+ * @param string $name
* @return bool
*/
function removeHeader($name);
diff --git a/vendor/sabre/http/lib/Request.php b/vendor/sabre/http/lib/Request.php
index 8bcaf32a6..dfa3d5b48 100644
--- a/vendor/sabre/http/lib/Request.php
+++ b/vendor/sabre/http/lib/Request.php
@@ -301,7 +301,7 @@ class Request extends Message implements RequestInterface {
foreach ($value as $v) {
if ($key === 'Authorization') {
list($v) = explode(' ', $v, 2);
- $v .= ' REDACTED';
+ $v .= ' REDACTED';
}
$out .= $key . ": " . $v . "\r\n";
}
diff --git a/vendor/sabre/http/lib/Response.php b/vendor/sabre/http/lib/Response.php
index d2ba6d40d..01920d8d9 100644
--- a/vendor/sabre/http/lib/Response.php
+++ b/vendor/sabre/http/lib/Response.php
@@ -100,7 +100,6 @@ class Response extends Message implements ResponseInterface {
* @param string|int $status
* @param array $headers
* @param resource $body
- * @return void
*/
function __construct($status = null, array $headers = null, $body = null) {
@@ -145,7 +144,7 @@ class Response extends Message implements ResponseInterface {
* added.
*
* @param string|int $status
- * @throws \InvalidArgumentExeption
+ * @throws \InvalidArgumentException
* @return void
*/
function setStatus($status) {
diff --git a/vendor/sabre/http/lib/ResponseInterface.php b/vendor/sabre/http/lib/ResponseInterface.php
index c0ecc35ae..411cdc06c 100644
--- a/vendor/sabre/http/lib/ResponseInterface.php
+++ b/vendor/sabre/http/lib/ResponseInterface.php
@@ -37,7 +37,7 @@ interface ResponseInterface extends MessageInterface {
* added.
*
* @param string|int $status
- * @throws \InvalidArgumentExeption
+ * @throws \InvalidArgumentException
* @return void
*/
function setStatus($status);
diff --git a/vendor/sabre/http/lib/Sapi.php b/vendor/sabre/http/lib/Sapi.php
index 6c83c8719..6fc6452e4 100644
--- a/vendor/sabre/http/lib/Sapi.php
+++ b/vendor/sabre/http/lib/Sapi.php
@@ -75,7 +75,15 @@ class Sapi {
if ($contentLength !== null) {
$output = fopen('php://output', 'wb');
if (is_resource($body) && get_resource_type($body) == 'stream') {
- stream_copy_to_stream($body, $output, $contentLength);
+ if (PHP_INT_SIZE !== 4){
+ // use the dedicated function on 64 Bit systems
+ stream_copy_to_stream($body, $output, $contentLength);
+ } else {
+ // workaround for 32 Bit systems to avoid stream_copy_to_stream
+ while (!feof($body)) {
+ fwrite($output, fread($body, 8192));
+ }
+ }
} else {
fwrite($output, $body, $contentLength);
}
diff --git a/vendor/sabre/http/lib/URLUtil.php b/vendor/sabre/http/lib/URLUtil.php
index 474856348..85c0e1150 100644
--- a/vendor/sabre/http/lib/URLUtil.php
+++ b/vendor/sabre/http/lib/URLUtil.php
@@ -10,7 +10,7 @@ use Sabre\URI;
* Note: this class is deprecated. All its functionality moved to functions.php
* or sabre\uri.
*
- * @deprectated
+ * @deprecated
* @copyright Copyright (C) fruux GmbH (https://fruux.com/)
* @author Evert Pot (http://evertpot.com/)
* @license http://sabre.io/license/ Modified BSD License
diff --git a/vendor/sabre/http/lib/Util.php b/vendor/sabre/http/lib/Util.php
index 83bde50a4..e3f13a645 100644
--- a/vendor/sabre/http/lib/Util.php
+++ b/vendor/sabre/http/lib/Util.php
@@ -31,7 +31,7 @@ class Util {
* Deprecated! Use negotiateContentType.
*
* @deprecated Use \Sabre\HTTP\NegotiateContentType
- * @param string|null $acceptHeader
+ * @param string|null $acceptHeaderValue
* @param array $availableOptions
* @return string|null
*/
diff --git a/vendor/sabre/http/lib/Version.php b/vendor/sabre/http/lib/Version.php
index 789ee4543..aeb080e93 100644
--- a/vendor/sabre/http/lib/Version.php
+++ b/vendor/sabre/http/lib/Version.php
@@ -14,6 +14,6 @@ class Version {
/**
* Full version number
*/
- const VERSION = '4.2.1';
+ const VERSION = '4.2.3';
}
diff --git a/vendor/sabre/http/lib/functions.php b/vendor/sabre/http/lib/functions.php
index 1ec123f2e..d94119623 100644
--- a/vendor/sabre/http/lib/functions.php
+++ b/vendor/sabre/http/lib/functions.php
@@ -79,7 +79,7 @@ function toDate(DateTime $dateTime) {
// We need to clone it, as we don't want to affect the existing
// DateTime.
$dateTime = clone $dateTime;
- $dateTime->setTimeZone(new \DateTimeZone('GMT'));
+ $dateTime->setTimezone(new \DateTimeZone('GMT'));
return $dateTime->format('D, d M Y H:i:s \G\M\T');
}
@@ -216,7 +216,7 @@ function negotiateContentType($acceptHeaderValue, array $availableOptions) {
* Parameters are currently discarded. There's no known prefer value that
* uses them.
*
- * @param string|string[] $header
+ * @param string|string[] $input
* @return array
*/
function parsePrefer($input) {
diff --git a/vendor/sabre/uri/.travis.yml b/vendor/sabre/uri/.travis.yml
index f7d1a0657..75c8270df 100644
--- a/vendor/sabre/uri/.travis.yml
+++ b/vendor/sabre/uri/.travis.yml
@@ -3,8 +3,8 @@ php:
- 5.4
- 5.5
- 5.6
- - hhvm
- 7
+ - 7.1
script:
- ./bin/phpunit --configuration tests/phpunit.xml.dist
diff --git a/vendor/sabre/uri/CHANGELOG.md b/vendor/sabre/uri/CHANGELOG.md
index 9fa510dc2..92aaa7507 100644
--- a/vendor/sabre/uri/CHANGELOG.md
+++ b/vendor/sabre/uri/CHANGELOG.md
@@ -1,6 +1,29 @@
ChangeLog
=========
+1.2.1 (2017-02-20)
+------------------
+
+* #16: Correctly parse urls that are only a fragment `#`.
+
+
+1.2.0 (2016-12-06)
+------------------
+
+* Now throwing `InvalidUriException` if a uri passed to the `parse` function
+ is invalid or could not be parsed.
+* #11: Fix support for URIs that start with a triple slash. PHP's `parse_uri()`
+ doesn't support them, so we now have a pure-php fallback in case it fails.
+* #9: Fix support for relative URI's that have a non-uri encoded colon `:` in
+ them.
+
+
+1.1.1 (2016-10-27)
+------------------
+
+* #10: Correctly support file:// URIs in the build() method. (@yuloh)
+
+
1.1.0 (2016-03-07)
------------------
diff --git a/vendor/sabre/uri/LICENSE b/vendor/sabre/uri/LICENSE
index 9a3a91946..087996be7 100644
--- a/vendor/sabre/uri/LICENSE
+++ b/vendor/sabre/uri/LICENSE
@@ -1,4 +1,4 @@
-Copyright (C) 2014-2016 fruux GmbH (https://fruux.com/)
+Copyright (C) 2014-2017 fruux GmbH (https://fruux.com/)
All rights reserved.
diff --git a/vendor/sabre/uri/README.md b/vendor/sabre/uri/README.md
index 76f55d8e4..aa21bfe06 100644
--- a/vendor/sabre/uri/README.md
+++ b/vendor/sabre/uri/README.md
@@ -25,14 +25,6 @@ Further reading
* [Usage][8]
-Build status
-------------
-
-| branch | status |
-| ------ | ------ |
-| master | [![Build Status](https://travis-ci.org/fruux/sabre-uri.svg?branch=master)](https://travis-ci.org/fruux/sabre-uri) |
-
-
Questions?
----------
diff --git a/vendor/sabre/uri/composer.json b/vendor/sabre/uri/composer.json
index 7b48acb71..49d69e723 100644
--- a/vendor/sabre/uri/composer.json
+++ b/vendor/sabre/uri/composer.json
@@ -32,8 +32,8 @@
}
},
"require-dev": {
- "sabre/cs": "~0.0.1",
- "phpunit/phpunit" : "*"
+ "sabre/cs": "~1.0.0",
+ "phpunit/phpunit" : ">=4.0,<6.0"
},
"config" : {
"bin-dir" : "bin/"
diff --git a/vendor/sabre/uri/lib/InvalidUriException.php b/vendor/sabre/uri/lib/InvalidUriException.php
new file mode 100644
index 000000000..0385fd462
--- /dev/null
+++ b/vendor/sabre/uri/lib/InvalidUriException.php
@@ -0,0 +1,17 @@
+<?php
+
+namespace Sabre\Uri;
+
+/**
+ * Invalid Uri
+ *
+ * This is thrown when an attempt was made to use Sabre\Uri parse a uri that
+ * it could not.
+ *
+ * @copyright Copyright (C) fruux GmbH (https://fruux.com/)
+ * @author Evert Pot (https://evertpot.com/)
+ * @license http://sabre.io/license/
+ */
+class InvalidUriException extends \Exception {
+
+}
diff --git a/vendor/sabre/uri/lib/Version.php b/vendor/sabre/uri/lib/Version.php
index 88678d4d5..fa544538b 100644
--- a/vendor/sabre/uri/lib/Version.php
+++ b/vendor/sabre/uri/lib/Version.php
@@ -14,6 +14,6 @@ class Version {
/**
* Full version number
*/
- const VERSION = '1.1.0';
+ const VERSION = '1.2.1';
}
diff --git a/vendor/sabre/uri/lib/functions.php b/vendor/sabre/uri/lib/functions.php
index 06181aef0..39b4a6f08 100644
--- a/vendor/sabre/uri/lib/functions.php
+++ b/vendor/sabre/uri/lib/functions.php
@@ -45,8 +45,8 @@ function resolve($basePath, $newPath) {
$newParts = [];
$newParts['scheme'] = $pick('scheme');
- $newParts['host'] = $pick('host');
- $newParts['port'] = $pick('port');
+ $newParts['host'] = $pick('host');
+ $newParts['port'] = $pick('port');
$path = '';
if ($delta['path']) {
@@ -193,8 +193,13 @@ function parse($uri) {
$uri
);
+ $result = parse_url($uri);
+ if (!$result) {
+ $result = _parse_fallback($uri);
+ }
+
return
- parse_url($uri) + [
+ $result + [
'scheme' => null,
'host' => null,
'path' => null,
@@ -233,7 +238,7 @@ function build(array $parts) {
$uri = $parts['scheme'] . ':';
}
- if ($authority) {
+ if ($authority || (!empty($parts['scheme']) && $parts['scheme'] === 'file')) {
// No scheme, but there is a host.
$uri .= '//' . $authority;
@@ -280,3 +285,89 @@ function split($path) {
return [null,null];
}
+
+/**
+ * This function is another implementation of parse_url, except this one is
+ * fully written in PHP.
+ *
+ * The reason is that the PHP bug team is not willing to admit that there are
+ * bugs in the parse_url implementation.
+ *
+ * This function is only called if the main parse method fails. It's pretty
+ * crude and probably slow, so the original parse_url is usually preferred.
+ *
+ * @param string $uri
+ * @return array
+ */
+function _parse_fallback($uri) {
+
+ // Normally a URI must be ASCII, however. However, often it's not and
+ // parse_url might corrupt these strings.
+ //
+ // For that reason we take any non-ascii characters from the uri and
+ // uriencode them first.
+ $uri = preg_replace_callback(
+ '/[^[:ascii:]]/u',
+ function($matches) {
+ return rawurlencode($matches[0]);
+ },
+ $uri
+ );
+
+ $result = [
+ 'scheme' => null,
+ 'host' => null,
+ 'port' => null,
+ 'user' => null,
+ 'path' => null,
+ 'fragment' => null,
+ 'query' => null,
+ ];
+
+ if (preg_match('% ^([A-Za-z][A-Za-z0-9+-\.]+): %x', $uri, $matches)) {
+
+ $result['scheme'] = $matches[1];
+ // Take what's left.
+ $uri = substr($uri, strlen($result['scheme']) + 1);
+
+ }
+
+ // Taking off a fragment part
+ if (strpos($uri, '#') !== false) {
+ list($uri, $result['fragment']) = explode('#', $uri, 2);
+ }
+ // Taking off the query part
+ if (strpos($uri, '?') !== false) {
+ list($uri, $result['query']) = explode('?', $uri, 2);
+ }
+
+ if (substr($uri, 0, 3) === '///') {
+ // The triple slash uris are a bit unusual, but we have special handling
+ // for them.
+ $result['path'] = substr($uri, 2);
+ $result['host'] = '';
+ } elseif (substr($uri, 0, 2) === '//') {
+ // Uris that have an authority part.
+ $regex = '
+ %^
+ //
+ (?: (?<user> [^:@]+) (: (?<pass> [^@]+)) @)?
+ (?<host> ( [^:/]* | \[ [^\]]+ \] ))
+ (?: : (?<port> [0-9]+))?
+ (?<path> / .*)?
+ $%x
+ ';
+ if (!preg_match($regex, $uri, $matches)) {
+ throw new InvalidUriException('Invalid, or could not parse URI');
+ }
+ if ($matches['host']) $result['host'] = $matches['host'];
+ if ($matches['port']) $result['port'] = (int)$matches['port'];
+ if (isset($matches['path'])) $result['path'] = $matches['path'];
+ if ($matches['user']) $result['user'] = $matches['user'];
+ if ($matches['pass']) $result['pass'] = $matches['pass'];
+ } else {
+ $result['path'] = $uri;
+ }
+
+ return $result;
+}
diff --git a/vendor/sabre/vobject/.travis.yml b/vendor/sabre/vobject/.travis.yml
index b7266a878..3c5b32157 100644
--- a/vendor/sabre/vobject/.travis.yml
+++ b/vendor/sabre/vobject/.travis.yml
@@ -2,7 +2,8 @@ language: php
php:
- 5.5
- 5.6
- - 7
+ - 7.0
+ - 7.1
sudo: false
diff --git a/vendor/sabre/vobject/CHANGELOG.md b/vendor/sabre/vobject/CHANGELOG.md
index 4c72680f8..c8f4cb4be 100644
--- a/vendor/sabre/vobject/CHANGELOG.md
+++ b/vendor/sabre/vobject/CHANGELOG.md
@@ -1,6 +1,22 @@
ChangeLog
=========
+4.1.2 (2016-12-15)
+------------------
+
+* #340: Support for `BYYEARDAY` recurrence when `FREQ=YEARLY`. (@PHPGangsta)
+* #341: Support for `BYWEEKNO` recurrence when `FREQ=YEARLY`. (@PHPGangsta)
+* Updated to the latest windows timezone data mappings.
+* #344: Auto-detecting more Outlook 365-generated timezone identifiers.
+ (@jpirkey)
+* #348: `FreeBusyGenerator` can now accept streams.
+* Support sabre/xml 1.5 and 2.0.
+* #355: Support `DateTimeInterface` in more places where only `DateTime` was
+ supported. (@gharlan).
+* #351: Fixing an inclusive/exclusive problem with `isInTimeRange` and
+ `fastForward` with all-day events. (@strokyl, thanks you are brilliant).
+
+
4.1.1 (2016-07-15)
------------------
@@ -143,7 +159,7 @@ ChangeLog
and `IntegerValue` to allow PHP 7 compatibility.
-3.5.3 (????-??-??)
+3.5.3 (2016-10-06)
------------------
* #331: Fix dealing with multiple overridden instances falling on the same
diff --git a/vendor/sabre/vobject/bin/fetch_windows_zones.php b/vendor/sabre/vobject/bin/fetch_windows_zones.php
index 1b1fdc37c..3f2a00f7a 100755
--- a/vendor/sabre/vobject/bin/fetch_windows_zones.php
+++ b/vendor/sabre/vobject/bin/fetch_windows_zones.php
@@ -36,7 +36,7 @@ fwrite($f, " *\n");
fwrite($f, " * Last update: " . date(DATE_W3C) . "\n");
fwrite($f, " * Source: " . $windowsZonesUrl . "\n");
fwrite($f, " *\n");
-fwrite($f, " * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/).\n");
+fwrite($f, " * @copyright Copyright (C) fruux GmbH (https://fruux.com/).\n");
fwrite($f, " * @license http://sabre.io/license/ Modified BSD License\n");
fwrite($f, " */\n");
fwrite($f, "\n");
diff --git a/vendor/sabre/vobject/composer.json b/vendor/sabre/vobject/composer.json
index bd6348a82..cfa4a712d 100644
--- a/vendor/sabre/vobject/composer.json
+++ b/vendor/sabre/vobject/composer.json
@@ -34,11 +34,11 @@
"require" : {
"php" : ">=5.5",
"ext-mbstring" : "*",
- "sabre/xml" : "~1.1"
+ "sabre/xml" : ">=1.5 <3.0"
},
"require-dev" : {
"phpunit/phpunit" : "*",
- "sabre/cs" : "~0.0.3"
+ "sabre/cs" : "^1.0.0"
},
"suggest" : {
diff --git a/vendor/sabre/vobject/lib/BirthdayCalendarGenerator.php b/vendor/sabre/vobject/lib/BirthdayCalendarGenerator.php
index afa41ab1c..553912249 100644
--- a/vendor/sabre/vobject/lib/BirthdayCalendarGenerator.php
+++ b/vendor/sabre/vobject/lib/BirthdayCalendarGenerator.php
@@ -159,10 +159,10 @@ class BirthdayCalendarGenerator {
// Create event.
$event = $calendar->add('VEVENT', [
- 'SUMMARY' => sprintf($this->format, $object->FN->getValue()),
- 'DTSTART' => new \DateTime($object->BDAY->getValue()),
- 'RRULE' => 'FREQ=YEARLY',
- 'TRANSP' => 'TRANSPARENT',
+ 'SUMMARY' => sprintf($this->format, $object->FN->getValue()),
+ 'DTSTART' => new \DateTime($object->BDAY->getValue()),
+ 'RRULE' => 'FREQ=YEARLY',
+ 'TRANSP' => 'TRANSPARENT',
]);
// add VALUE=date
diff --git a/vendor/sabre/vobject/lib/Component/VAlarm.php b/vendor/sabre/vobject/lib/Component/VAlarm.php
index 8cbd572e6..faa8a5e74 100644
--- a/vendor/sabre/vobject/lib/Component/VAlarm.php
+++ b/vendor/sabre/vobject/lib/Component/VAlarm.php
@@ -2,10 +2,10 @@
namespace Sabre\VObject\Component;
+use DateTimeImmutable;
+use DateTimeInterface;
use Sabre\VObject;
use Sabre\VObject\InvalidDataException;
-use DateTimeInterface;
-use DateTimeImmutable;
/**
* VAlarm component.
diff --git a/vendor/sabre/vobject/lib/Component/VCalendar.php b/vendor/sabre/vobject/lib/Component/VCalendar.php
index 988db9dc2..1b3137d38 100644
--- a/vendor/sabre/vobject/lib/Component/VCalendar.php
+++ b/vendor/sabre/vobject/lib/Component/VCalendar.php
@@ -6,10 +6,10 @@ use DateTimeInterface;
use DateTimeZone;
use Sabre\VObject;
use Sabre\VObject\Component;
+use Sabre\VObject\InvalidDataException;
use Sabre\VObject\Property;
use Sabre\VObject\Recur\EventIterator;
use Sabre\VObject\Recur\NoInstancesException;
-use Sabre\VObject\InvalidDataException;
/**
* The VCalendar component.
@@ -54,21 +54,21 @@ class VCalendar extends VObject\Document {
* @var array
*/
static $valueMap = [
- 'BINARY' => 'Sabre\\VObject\\Property\\Binary',
- 'BOOLEAN' => 'Sabre\\VObject\\Property\\Boolean',
- 'CAL-ADDRESS' => 'Sabre\\VObject\\Property\\ICalendar\\CalAddress',
- 'DATE' => 'Sabre\\VObject\\Property\\ICalendar\\Date',
- 'DATE-TIME' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime',
- 'DURATION' => 'Sabre\\VObject\\Property\\ICalendar\\Duration',
- 'FLOAT' => 'Sabre\\VObject\\Property\\FloatValue',
- 'INTEGER' => 'Sabre\\VObject\\Property\\IntegerValue',
- 'PERIOD' => 'Sabre\\VObject\\Property\\ICalendar\\Period',
- 'RECUR' => 'Sabre\\VObject\\Property\\ICalendar\\Recur',
- 'TEXT' => 'Sabre\\VObject\\Property\\Text',
- 'TIME' => 'Sabre\\VObject\\Property\\Time',
- 'UNKNOWN' => 'Sabre\\VObject\\Property\\Unknown', // jCard / jCal-only.
- 'URI' => 'Sabre\\VObject\\Property\\Uri',
- 'UTC-OFFSET' => 'Sabre\\VObject\\Property\\UtcOffset',
+ 'BINARY' => 'Sabre\\VObject\\Property\\Binary',
+ 'BOOLEAN' => 'Sabre\\VObject\\Property\\Boolean',
+ 'CAL-ADDRESS' => 'Sabre\\VObject\\Property\\ICalendar\\CalAddress',
+ 'DATE' => 'Sabre\\VObject\\Property\\ICalendar\\Date',
+ 'DATE-TIME' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime',
+ 'DURATION' => 'Sabre\\VObject\\Property\\ICalendar\\Duration',
+ 'FLOAT' => 'Sabre\\VObject\\Property\\FloatValue',
+ 'INTEGER' => 'Sabre\\VObject\\Property\\IntegerValue',
+ 'PERIOD' => 'Sabre\\VObject\\Property\\ICalendar\\Period',
+ 'RECUR' => 'Sabre\\VObject\\Property\\ICalendar\\Recur',
+ 'TEXT' => 'Sabre\\VObject\\Property\\Text',
+ 'TIME' => 'Sabre\\VObject\\Property\\Time',
+ 'UNKNOWN' => 'Sabre\\VObject\\Property\\Unknown', // jCard / jCal-only.
+ 'URI' => 'Sabre\\VObject\\Property\\Uri',
+ 'UTC-OFFSET' => 'Sabre\\VObject\\Property\\UtcOffset',
];
/**
@@ -78,40 +78,40 @@ class VCalendar extends VObject\Document {
*/
static $propertyMap = [
// Calendar properties
- 'CALSCALE' => 'Sabre\\VObject\\Property\\FlatText',
- 'METHOD' => 'Sabre\\VObject\\Property\\FlatText',
- 'PRODID' => 'Sabre\\VObject\\Property\\FlatText',
- 'VERSION' => 'Sabre\\VObject\\Property\\FlatText',
+ 'CALSCALE' => 'Sabre\\VObject\\Property\\FlatText',
+ 'METHOD' => 'Sabre\\VObject\\Property\\FlatText',
+ 'PRODID' => 'Sabre\\VObject\\Property\\FlatText',
+ 'VERSION' => 'Sabre\\VObject\\Property\\FlatText',
// Component properties
- 'ATTACH' => 'Sabre\\VObject\\Property\\Uri',
- 'CATEGORIES' => 'Sabre\\VObject\\Property\\Text',
- 'CLASS' => 'Sabre\\VObject\\Property\\FlatText',
- 'COMMENT' => 'Sabre\\VObject\\Property\\FlatText',
- 'DESCRIPTION' => 'Sabre\\VObject\\Property\\FlatText',
- 'GEO' => 'Sabre\\VObject\\Property\\FloatValue',
- 'LOCATION' => 'Sabre\\VObject\\Property\\FlatText',
- 'PERCENT-COMPLETE' => 'Sabre\\VObject\\Property\\IntegerValue',
- 'PRIORITY' => 'Sabre\\VObject\\Property\\IntegerValue',
- 'RESOURCES' => 'Sabre\\VObject\\Property\\Text',
- 'STATUS' => 'Sabre\\VObject\\Property\\FlatText',
- 'SUMMARY' => 'Sabre\\VObject\\Property\\FlatText',
+ 'ATTACH' => 'Sabre\\VObject\\Property\\Uri',
+ 'CATEGORIES' => 'Sabre\\VObject\\Property\\Text',
+ 'CLASS' => 'Sabre\\VObject\\Property\\FlatText',
+ 'COMMENT' => 'Sabre\\VObject\\Property\\FlatText',
+ 'DESCRIPTION' => 'Sabre\\VObject\\Property\\FlatText',
+ 'GEO' => 'Sabre\\VObject\\Property\\FloatValue',
+ 'LOCATION' => 'Sabre\\VObject\\Property\\FlatText',
+ 'PERCENT-COMPLETE' => 'Sabre\\VObject\\Property\\IntegerValue',
+ 'PRIORITY' => 'Sabre\\VObject\\Property\\IntegerValue',
+ 'RESOURCES' => 'Sabre\\VObject\\Property\\Text',
+ 'STATUS' => 'Sabre\\VObject\\Property\\FlatText',
+ 'SUMMARY' => 'Sabre\\VObject\\Property\\FlatText',
// Date and Time Component Properties
- 'COMPLETED' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime',
- 'DTEND' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime',
- 'DUE' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime',
- 'DTSTART' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime',
- 'DURATION' => 'Sabre\\VObject\\Property\\ICalendar\\Duration',
- 'FREEBUSY' => 'Sabre\\VObject\\Property\\ICalendar\\Period',
- 'TRANSP' => 'Sabre\\VObject\\Property\\FlatText',
+ 'COMPLETED' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime',
+ 'DTEND' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime',
+ 'DUE' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime',
+ 'DTSTART' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime',
+ 'DURATION' => 'Sabre\\VObject\\Property\\ICalendar\\Duration',
+ 'FREEBUSY' => 'Sabre\\VObject\\Property\\ICalendar\\Period',
+ 'TRANSP' => 'Sabre\\VObject\\Property\\FlatText',
// Time Zone Component Properties
- 'TZID' => 'Sabre\\VObject\\Property\\FlatText',
- 'TZNAME' => 'Sabre\\VObject\\Property\\FlatText',
- 'TZOFFSETFROM' => 'Sabre\\VObject\\Property\\UtcOffset',
- 'TZOFFSETTO' => 'Sabre\\VObject\\Property\\UtcOffset',
- 'TZURL' => 'Sabre\\VObject\\Property\\Uri',
+ 'TZID' => 'Sabre\\VObject\\Property\\FlatText',
+ 'TZNAME' => 'Sabre\\VObject\\Property\\FlatText',
+ 'TZOFFSETFROM' => 'Sabre\\VObject\\Property\\UtcOffset',
+ 'TZOFFSETTO' => 'Sabre\\VObject\\Property\\UtcOffset',
+ 'TZURL' => 'Sabre\\VObject\\Property\\Uri',
// Relationship Component Properties
'ATTENDEE' => 'Sabre\\VObject\\Property\\ICalendar\\CalAddress',
@@ -123,15 +123,15 @@ class VCalendar extends VObject\Document {
'UID' => 'Sabre\\VObject\\Property\\FlatText',
// Recurrence Component Properties
- 'EXDATE' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime',
- 'RDATE' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime',
- 'RRULE' => 'Sabre\\VObject\\Property\\ICalendar\\Recur',
- 'EXRULE' => 'Sabre\\VObject\\Property\\ICalendar\\Recur', // Deprecated since rfc5545
+ 'EXDATE' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime',
+ 'RDATE' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime',
+ 'RRULE' => 'Sabre\\VObject\\Property\\ICalendar\\Recur',
+ 'EXRULE' => 'Sabre\\VObject\\Property\\ICalendar\\Recur', // Deprecated since rfc5545
// Alarm Component Properties
- 'ACTION' => 'Sabre\\VObject\\Property\\FlatText',
- 'REPEAT' => 'Sabre\\VObject\\Property\\IntegerValue',
- 'TRIGGER' => 'Sabre\\VObject\\Property\\ICalendar\\Duration',
+ 'ACTION' => 'Sabre\\VObject\\Property\\FlatText',
+ 'REPEAT' => 'Sabre\\VObject\\Property\\IntegerValue',
+ 'TRIGGER' => 'Sabre\\VObject\\Property\\ICalendar\\Duration',
// Change Management Component Properties
'CREATED' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime',
@@ -143,13 +143,13 @@ class VCalendar extends VObject\Document {
'REQUEST-STATUS' => 'Sabre\\VObject\\Property\\Text',
// Additions from draft-daboo-valarm-extensions-04
- 'ALARM-AGENT' => 'Sabre\\VObject\\Property\\Text',
- 'ACKNOWLEDGED' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime',
- 'PROXIMITY' => 'Sabre\\VObject\\Property\\Text',
- 'DEFAULT-ALARM' => 'Sabre\\VObject\\Property\\Boolean',
+ 'ALARM-AGENT' => 'Sabre\\VObject\\Property\\Text',
+ 'ACKNOWLEDGED' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime',
+ 'PROXIMITY' => 'Sabre\\VObject\\Property\\Text',
+ 'DEFAULT-ALARM' => 'Sabre\\VObject\\Property\\Boolean',
// Additions from draft-daboo-calendar-availability-05
- 'BUSYTYPE' => 'Sabre\\VObject\\Property\\Text',
+ 'BUSYTYPE' => 'Sabre\\VObject\\Property\\Text',
];
diff --git a/vendor/sabre/vobject/lib/Component/VCard.php b/vendor/sabre/vobject/lib/Component/VCard.php
index 3c05191a9..4f620de10 100644
--- a/vendor/sabre/vobject/lib/Component/VCard.php
+++ b/vendor/sabre/vobject/lib/Component/VCard.php
@@ -74,19 +74,19 @@ class VCard extends VObject\Document {
static $propertyMap = [
// vCard 2.1 properties and up
- 'N' => 'Sabre\\VObject\\Property\\Text',
- 'FN' => 'Sabre\\VObject\\Property\\FlatText',
- 'PHOTO' => 'Sabre\\VObject\\Property\\Binary',
- 'BDAY' => 'Sabre\\VObject\\Property\\VCard\\DateAndOrTime',
- 'ADR' => 'Sabre\\VObject\\Property\\Text',
- 'LABEL' => 'Sabre\\VObject\\Property\\FlatText', // Removed in vCard 4.0
- 'TEL' => 'Sabre\\VObject\\Property\\FlatText',
- 'EMAIL' => 'Sabre\\VObject\\Property\\FlatText',
- 'MAILER' => 'Sabre\\VObject\\Property\\FlatText', // Removed in vCard 4.0
- 'GEO' => 'Sabre\\VObject\\Property\\FlatText',
- 'TITLE' => 'Sabre\\VObject\\Property\\FlatText',
- 'ROLE' => 'Sabre\\VObject\\Property\\FlatText',
- 'LOGO' => 'Sabre\\VObject\\Property\\Binary',
+ 'N' => 'Sabre\\VObject\\Property\\Text',
+ 'FN' => 'Sabre\\VObject\\Property\\FlatText',
+ 'PHOTO' => 'Sabre\\VObject\\Property\\Binary',
+ 'BDAY' => 'Sabre\\VObject\\Property\\VCard\\DateAndOrTime',
+ 'ADR' => 'Sabre\\VObject\\Property\\Text',
+ 'LABEL' => 'Sabre\\VObject\\Property\\FlatText', // Removed in vCard 4.0
+ 'TEL' => 'Sabre\\VObject\\Property\\FlatText',
+ 'EMAIL' => 'Sabre\\VObject\\Property\\FlatText',
+ 'MAILER' => 'Sabre\\VObject\\Property\\FlatText', // Removed in vCard 4.0
+ 'GEO' => 'Sabre\\VObject\\Property\\FlatText',
+ 'TITLE' => 'Sabre\\VObject\\Property\\FlatText',
+ 'ROLE' => 'Sabre\\VObject\\Property\\FlatText',
+ 'LOGO' => 'Sabre\\VObject\\Property\\Binary',
// 'AGENT' => 'Sabre\\VObject\\Property\\', // Todo: is an embedded vCard. Probably rare, so
// not supported at the moment
'ORG' => 'Sabre\\VObject\\Property\\Text',
@@ -107,13 +107,13 @@ class VCard extends VObject\Document {
'CLASS' => 'Sabre\\VObject\\Property\\FlatText', // Removed in vCard 4.0
// rfc2739 properties
- 'FBURL' => 'Sabre\\VObject\\Property\\Uri',
- 'CAPURI' => 'Sabre\\VObject\\Property\\Uri',
- 'CALURI' => 'Sabre\\VObject\\Property\\Uri',
- 'CALADRURI' => 'Sabre\\VObject\\Property\\Uri',
+ 'FBURL' => 'Sabre\\VObject\\Property\\Uri',
+ 'CAPURI' => 'Sabre\\VObject\\Property\\Uri',
+ 'CALURI' => 'Sabre\\VObject\\Property\\Uri',
+ 'CALADRURI' => 'Sabre\\VObject\\Property\\Uri',
// rfc4770 properties
- 'IMPP' => 'Sabre\\VObject\\Property\\Uri',
+ 'IMPP' => 'Sabre\\VObject\\Property\\Uri',
// vCard 4.0 properties
'SOURCE' => 'Sabre\\VObject\\Property\\Uri',
@@ -127,9 +127,9 @@ class VCard extends VObject\Document {
'RELATED' => 'Sabre\\VObject\\Property\\Uri',
// rfc6474 properties
- 'BIRTHPLACE' => 'Sabre\\VObject\\Property\\FlatText',
- 'DEATHPLACE' => 'Sabre\\VObject\\Property\\FlatText',
- 'DEATHDATE' => 'Sabre\\VObject\\Property\\VCard\\DateAndOrTime',
+ 'BIRTHPLACE' => 'Sabre\\VObject\\Property\\FlatText',
+ 'DEATHPLACE' => 'Sabre\\VObject\\Property\\FlatText',
+ 'DEATHDATE' => 'Sabre\\VObject\\Property\\VCard\\DateAndOrTime',
// rfc6715 properties
'EXPERTISE' => 'Sabre\\VObject\\Property\\FlatText',
@@ -368,7 +368,7 @@ class VCard extends VObject\Document {
// FN is commented out, because it's already handled by the
// validate function, which may also try to repair it.
// 'FN' => '+',
- 'UID' => '?',
+ 'UID' => '?',
];
}
diff --git a/vendor/sabre/vobject/lib/DateTimeParser.php b/vendor/sabre/vobject/lib/DateTimeParser.php
index 443bbb660..f9a802d25 100644
--- a/vendor/sabre/vobject/lib/DateTimeParser.php
+++ b/vendor/sabre/vobject/lib/DateTimeParser.php
@@ -2,9 +2,9 @@
namespace Sabre\VObject;
+use DateInterval;
use DateTimeImmutable;
use DateTimeZone;
-use DateInterval;
/**
* DateTimeParser.
@@ -509,7 +509,7 @@ class DateTimeParser {
static function parseVCardDateAndOrTime($date) {
// \d{8}|\d{4}-\d\d|--\d\d(\d\d)?|---\d\d
- $valueDate = '/^(?J)(?:' .
+ $valueDate = '/^(?J)(?:' .
'(?<year>\d{4})(?<month>\d\d)(?<date>\d\d)' .
'|(?<year>\d{4})-(?<month>\d\d)' .
'|--(?<month>\d\d)(?<date>\d\d)?' .
@@ -517,7 +517,7 @@ class DateTimeParser {
')$/';
// (\d\d(\d\d(\d\d)?)?|-\d\d(\d\d)?|--\d\d)(Z|[+\-]\d\d(\d\d)?)?
- $valueTime = '/^(?J)(?:' .
+ $valueTime = '/^(?J)(?:' .
'((?<hour>\d\d)((?<minute>\d\d)(?<second>\d\d)?)?' .
'|-(?<minute>\d\d)(?<second>\d\d)?' .
'|--(?<second>\d\d))' .
@@ -554,12 +554,12 @@ class DateTimeParser {
];
// The $valueDateTime expression has a bug with (?J) so we simulate it.
- $parts['date0'] = &$parts['date'];
- $parts['date1'] = &$parts['date'];
- $parts['date2'] = &$parts['date'];
+ $parts['date0'] = &$parts['date'];
+ $parts['date1'] = &$parts['date'];
+ $parts['date2'] = &$parts['date'];
$parts['month0'] = &$parts['month'];
$parts['month1'] = &$parts['month'];
- $parts['year0'] = &$parts['year'];
+ $parts['year0'] = &$parts['year'];
foreach ($parts as $part => &$value) {
if (!empty($matches[$part])) {
diff --git a/vendor/sabre/vobject/lib/FreeBusyGenerator.php b/vendor/sabre/vobject/lib/FreeBusyGenerator.php
index e33621090..e30b136c4 100644
--- a/vendor/sabre/vobject/lib/FreeBusyGenerator.php
+++ b/vendor/sabre/vobject/lib/FreeBusyGenerator.php
@@ -2,8 +2,8 @@
namespace Sabre\VObject;
-use DateTimeInterface;
use DateTimeImmutable;
+use DateTimeInterface;
use DateTimeZone;
use Sabre\VObject\Component\VCalendar;
use Sabre\VObject\Recur\EventIterator;
@@ -152,7 +152,7 @@ class FreeBusyGenerator {
$this->objects = [];
foreach ($objects as $object) {
- if (is_string($object)) {
+ if (is_string($object) || is_resource($object)) {
$this->objects[] = Reader::read($object);
} elseif ($object instanceof Component) {
$this->objects[] = $object;
@@ -292,7 +292,7 @@ class FreeBusyGenerator {
list($higherStart, $higherEnd) = $higherVavail->getEffectiveStartEnd();
if (
(is_null($higherStart) || $higherStart < $compStart) &&
- (is_null($higherEnd) || $higherEnd > $compEnd)
+ (is_null($higherEnd) || $higherEnd > $compEnd)
) {
// Component is fully covered by a higher priority
diff --git a/vendor/sabre/vobject/lib/Parameter.php b/vendor/sabre/vobject/lib/Parameter.php
index 270643eab..a99a33eec 100644
--- a/vendor/sabre/vobject/lib/Parameter.php
+++ b/vendor/sabre/vobject/lib/Parameter.php
@@ -2,8 +2,8 @@
namespace Sabre\VObject;
-use Sabre\Xml;
use ArrayIterator;
+use Sabre\Xml;
/**
* VObject Parameter.
diff --git a/vendor/sabre/vobject/lib/Parser/Json.php b/vendor/sabre/vobject/lib/Parser/Json.php
index 370c981a8..a77258a2e 100644
--- a/vendor/sabre/vobject/lib/Parser/Json.php
+++ b/vendor/sabre/vobject/lib/Parser/Json.php
@@ -4,8 +4,8 @@ namespace Sabre\VObject\Parser;
use Sabre\VObject\Component\VCalendar;
use Sabre\VObject\Component\VCard;
-use Sabre\VObject\ParseException;
use Sabre\VObject\EofException;
+use Sabre\VObject\ParseException;
/**
* Json Parser.
diff --git a/vendor/sabre/vobject/lib/Parser/MimeDir.php b/vendor/sabre/vobject/lib/Parser/MimeDir.php
index 6a7f9317b..fa75a1a3b 100644
--- a/vendor/sabre/vobject/lib/Parser/MimeDir.php
+++ b/vendor/sabre/vobject/lib/Parser/MimeDir.php
@@ -2,12 +2,12 @@
namespace Sabre\VObject\Parser;
-use Sabre\VObject\ParseException;
-use Sabre\VObject\EofException;
use Sabre\VObject\Component;
use Sabre\VObject\Component\VCalendar;
use Sabre\VObject\Component\VCard;
use Sabre\VObject\Document;
+use Sabre\VObject\EofException;
+use Sabre\VObject\ParseException;
/**
* MimeDir parser.
diff --git a/vendor/sabre/vobject/lib/Parser/XML.php b/vendor/sabre/vobject/lib/Parser/XML.php
index 060a7fe2e..5ac423984 100644
--- a/vendor/sabre/vobject/lib/Parser/XML.php
+++ b/vendor/sabre/vobject/lib/Parser/XML.php
@@ -20,7 +20,7 @@ use Sabre\Xml as SabreXml;
*/
class XML extends Parser {
- const XCAL_NAMESPACE = 'urn:ietf:params:xml:ns:icalendar-2.0';
+ const XCAL_NAMESPACE = 'urn:ietf:params:xml:ns:icalendar-2.0';
const XCARD_NAMESPACE = 'urn:ietf:params:xml:ns:vcard-4.0';
/**
@@ -100,7 +100,7 @@ class XML extends Parser {
foreach ($this->input['value'] as &$vCard) {
$this->root = new VCard(['version' => '4.0'], false);
- $this->pointer = &$vCard;
+ $this->pointer = &$vCard;
$this->parseVCardComponents($this->root);
// We just parse the first <vcard /> element.
@@ -172,10 +172,10 @@ class XML extends Parser {
list($namespace, $tagName) = SabreXml\Service::parseClarkNotation($xmlProperty['name']);
- $propertyName = $tagName;
- $propertyValue = [];
+ $propertyName = $tagName;
+ $propertyValue = [];
$propertyParameters = [];
- $propertyType = 'text';
+ $propertyType = 'text';
// A property which is not part of the standard.
if ($namespace !== self::XCAL_NAMESPACE
@@ -253,8 +253,8 @@ class XML extends Parser {
switch ($propertyNameExtended) {
case 'xcal:geo':
- $propertyType = 'float';
- $propertyValue['latitude'] = 0;
+ $propertyType = 'float';
+ $propertyValue['latitude'] = 0;
$propertyValue['longitude'] = 0;
foreach ($xmlProperty['value'] as $xmlRequestChild) {
@@ -296,7 +296,7 @@ class XML extends Parser {
if ('period' === $tagName) {
$propertyParameters['value'] = 'PERIOD';
- $propertyValue[] = implode('/', $specialChild['value']);
+ $propertyValue[] = implode('/', $specialChild['value']);
}
else {
@@ -306,7 +306,7 @@ class XML extends Parser {
break;
default:
- $propertyType = static::getTagName($xmlProperty['value'][0]['name']);
+ $propertyType = static::getTagName($xmlProperty['value'][0]['name']);
foreach ($xmlProperty['value'] as $value) {
$propertyValue[] = $value['value'];
@@ -343,7 +343,7 @@ class XML extends Parser {
foreach ($components as $component) {
- $componentName = static::getTagName($component['name']);
+ $componentName = static::getTagName($component['name']);
$currentComponent = $this->root->createComponent(
$componentName,
null,
@@ -404,7 +404,7 @@ class XML extends Parser {
$reader->elementMap['{' . self::XCAL_NAMESPACE . '}recur']
= 'Sabre\VObject\Parser\XML\Element\KeyValue';
$reader->xml($input);
- $input = $reader->parse();
+ $input = $reader->parse();
}
diff --git a/vendor/sabre/vobject/lib/Property/ICalendar/Duration.php b/vendor/sabre/vobject/lib/Property/ICalendar/Duration.php
index 66d366960..7b7e1ce8e 100644
--- a/vendor/sabre/vobject/lib/Property/ICalendar/Duration.php
+++ b/vendor/sabre/vobject/lib/Property/ICalendar/Duration.php
@@ -2,8 +2,8 @@
namespace Sabre\VObject\Property\ICalendar;
-use Sabre\VObject\Property;
use Sabre\VObject\DateTimeParser;
+use Sabre\VObject\Property;
/**
* Duration property.
diff --git a/vendor/sabre/vobject/lib/Property/ICalendar/Period.php b/vendor/sabre/vobject/lib/Property/ICalendar/Period.php
index a4561d929..d35b425aa 100644
--- a/vendor/sabre/vobject/lib/Property/ICalendar/Period.php
+++ b/vendor/sabre/vobject/lib/Property/ICalendar/Period.php
@@ -2,8 +2,8 @@
namespace Sabre\VObject\Property\ICalendar;
-use Sabre\VObject\Property;
use Sabre\VObject\DateTimeParser;
+use Sabre\VObject\Property;
use Sabre\Xml;
/**
diff --git a/vendor/sabre/vobject/lib/Property/ICalendar/Recur.php b/vendor/sabre/vobject/lib/Property/ICalendar/Recur.php
index 8392a5cc1..434b77088 100644
--- a/vendor/sabre/vobject/lib/Property/ICalendar/Recur.php
+++ b/vendor/sabre/vobject/lib/Property/ICalendar/Recur.php
@@ -287,6 +287,54 @@ class Recur extends Property {
}
}
}
+ // if there is no valid entry left, remove the whole value
+ if (is_array($value) && empty($values[$key])) {
+ unset($values[$key]);
+ }
+ } elseif ($key == 'BYWEEKNO') {
+ $byWeekNo = (array)$value;
+ foreach ($byWeekNo as $i => $v) {
+ if (!is_numeric($v) || (int)$v < -53 || (int)$v == 0 || (int)$v > 53) {
+ $warnings[] = [
+ 'level' => $repair ? 1 : 3,
+ 'message' => 'BYWEEKNO in RRULE must have value(s) from -53 to -1, or 1 to 53!',
+ 'node' => $this
+ ];
+ if ($repair) {
+ if (is_array($value)) {
+ unset($values[$key][$i]);
+ } else {
+ unset($values[$key]);
+ }
+ }
+ }
+ }
+ // if there is no valid entry left, remove the whole value
+ if (is_array($value) && empty($values[$key])) {
+ unset($values[$key]);
+ }
+ } elseif ($key == 'BYYEARDAY') {
+ $byYearDay = (array)$value;
+ foreach ($byYearDay as $i => $v) {
+ if (!is_numeric($v) || (int)$v < -366 || (int)$v == 0 || (int)$v > 366) {
+ $warnings[] = [
+ 'level' => $repair ? 1 : 3,
+ 'message' => 'BYYEARDAY in RRULE must have value(s) from -366 to -1, or 1 to 366!',
+ 'node' => $this
+ ];
+ if ($repair) {
+ if (is_array($value)) {
+ unset($values[$key][$i]);
+ } else {
+ unset($values[$key]);
+ }
+ }
+ }
+ }
+ // if there is no valid entry left, remove the whole value
+ if (is_array($value) && empty($values[$key])) {
+ unset($values[$key]);
+ }
}
}
diff --git a/vendor/sabre/vobject/lib/Property/Text.php b/vendor/sabre/vobject/lib/Property/Text.php
index abc17563f..476dcde4d 100644
--- a/vendor/sabre/vobject/lib/Property/Text.php
+++ b/vendor/sabre/vobject/lib/Property/Text.php
@@ -2,10 +2,10 @@
namespace Sabre\VObject\Property;
-use Sabre\VObject\Property;
use Sabre\VObject\Component;
-use Sabre\VObject\Parser\MimeDir;
use Sabre\VObject\Document;
+use Sabre\VObject\Parser\MimeDir;
+use Sabre\VObject\Property;
use Sabre\Xml;
/**
diff --git a/vendor/sabre/vobject/lib/Property/Uri.php b/vendor/sabre/vobject/lib/Property/Uri.php
index 58e676e60..88fcfaab8 100644
--- a/vendor/sabre/vobject/lib/Property/Uri.php
+++ b/vendor/sabre/vobject/lib/Property/Uri.php
@@ -2,8 +2,8 @@
namespace Sabre\VObject\Property;
-use Sabre\VObject\Property;
use Sabre\VObject\Parameter;
+use Sabre\VObject\Property;
/**
* URI property.
diff --git a/vendor/sabre/vobject/lib/Property/VCard/DateAndOrTime.php b/vendor/sabre/vobject/lib/Property/VCard/DateAndOrTime.php
index 650e19cbf..3b4ae3bb5 100644
--- a/vendor/sabre/vobject/lib/Property/VCard/DateAndOrTime.php
+++ b/vendor/sabre/vobject/lib/Property/VCard/DateAndOrTime.php
@@ -2,9 +2,9 @@
namespace Sabre\VObject\Property\VCard;
-use DateTimeInterface;
-use DateTimeImmutable;
use DateTime;
+use DateTimeImmutable;
+use DateTimeInterface;
use Sabre\VObject\DateTimeParser;
use Sabre\VObject\InvalidDataException;
use Sabre\VObject\Property;
@@ -45,7 +45,7 @@ class DateAndOrTime extends Property {
/**
* Sets a multi-valued property.
*
- * You may also specify DateTime objects here.
+ * You may also specify DateTimeInterface objects here.
*
* @param array $parts
*
@@ -56,7 +56,7 @@ class DateAndOrTime extends Property {
if (count($parts) > 1) {
throw new \InvalidArgumentException('Only one value allowed');
}
- if (isset($parts[0]) && $parts[0] instanceof \DateTime) {
+ if (isset($parts[0]) && $parts[0] instanceof DateTimeInterface) {
$this->setDateTime($parts[0]);
} else {
parent::setParts($parts);
@@ -69,15 +69,15 @@ class DateAndOrTime extends Property {
*
* This may be either a single, or multiple strings in an array.
*
- * Instead of strings, you may also use DateTime here.
+ * Instead of strings, you may also use DateTimeInterface here.
*
- * @param string|array|\DateTime $value
+ * @param string|array|DateTimeInterface $value
*
* @return void
*/
function setValue($value) {
- if ($value instanceof \DateTime) {
+ if ($value instanceof DateTimeInterface) {
$this->setDateTime($value);
} else {
parent::setValue($value);
@@ -261,8 +261,8 @@ class DateAndOrTime extends Property {
protected function xmlSerializeValue(Xml\Writer $writer) {
$valueType = strtolower($this->getValueType());
- $parts = DateTimeParser::parseVCardDateAndOrTime($this->getValue());
- $value = '';
+ $parts = DateTimeParser::parseVCardDateAndOrTime($this->getValue());
+ $value = '';
// $d = defined
$d = function($part) use ($parts) {
@@ -280,7 +280,7 @@ class DateAndOrTime extends Property {
// value-date = element date {
// xsd:string { pattern = "\d{8}|\d{4}-\d\d|--\d\d(\d\d)?|---\d\d" }
// }
- if (($d('year') || $d('month') || $d('date'))
+ if (($d('year') || $d('month') || $d('date'))
&& (!$d('hour') && !$d('minute') && !$d('second') && !$d('timezone'))) {
if ($d('year') && $d('month') && $d('date')) {
@@ -298,8 +298,8 @@ class DateAndOrTime extends Property {
// xsd:string { pattern = "(\d\d(\d\d(\d\d)?)?|-\d\d(\d\d?)|--\d\d)"
// ~ "(Z|[+\-]\d\d(\d\d)?)?" }
// }
- } elseif ((!$d('year') && !$d('month') && !$d('date'))
- && ($d('hour') || $d('minute') || $d('second'))) {
+ } elseif ((!$d('year') && !$d('month') && !$d('date'))
+ && ($d('hour') || $d('minute') || $d('second'))) {
if ($d('hour')) {
$value .= $r('hour') . $r('minute') . $r('second');
diff --git a/vendor/sabre/vobject/lib/Recur/EventIterator.php b/vendor/sabre/vobject/lib/Recur/EventIterator.php
index f91c336bc..d313305a0 100644
--- a/vendor/sabre/vobject/lib/Recur/EventIterator.php
+++ b/vendor/sabre/vobject/lib/Recur/EventIterator.php
@@ -2,9 +2,9 @@
namespace Sabre\VObject\Recur;
-use DateTimeZone;
use DateTimeImmutable;
use DateTimeInterface;
+use DateTimeZone;
use InvalidArgumentException;
use Sabre\VObject\Component;
use Sabre\VObject\Component\VEvent;
@@ -43,6 +43,8 @@ use Sabre\VObject\Settings;
* * BYSETPOS
* * FREQ=YEARLY
* * BYMONTH
+ * * BYYEARDAY
+ * * BYWEEKNO
* * BYMONTHDAY (only if BYMONTH is also set)
* * BYDAY (only if BYMONTH is also set)
*
@@ -407,7 +409,7 @@ class EventIterator implements \Iterator {
*/
function fastForward(DateTimeInterface $dateTime) {
- while ($this->valid() && $this->getDtEnd() < $dateTime) {
+ while ($this->valid() && $this->getDtEnd() <= $dateTime) {
$this->next();
}
diff --git a/vendor/sabre/vobject/lib/Recur/RRuleIterator.php b/vendor/sabre/vobject/lib/Recur/RRuleIterator.php
index 4c89f3ce4..20f34ef42 100644
--- a/vendor/sabre/vobject/lib/Recur/RRuleIterator.php
+++ b/vendor/sabre/vobject/lib/Recur/RRuleIterator.php
@@ -2,8 +2,8 @@
namespace Sabre\VObject\Recur;
-use DateTimeInterface;
use DateTimeImmutable;
+use DateTimeInterface;
use Iterator;
use Sabre\VObject\DateTimeParser;
use Sabre\VObject\InvalidDataException;
@@ -374,8 +374,8 @@ class RRuleIterator implements Iterator {
$currentHour = $this->currentDate->format('G');
} while (
- ($this->byDay && !in_array($currentDay, $recurrenceDays)) ||
- ($this->byHour && !in_array($currentHour, $recurrenceHours)) ||
+ ($this->byDay && !in_array($currentDay, $recurrenceDays)) ||
+ ($this->byHour && !in_array($currentHour, $recurrenceHours)) ||
($this->byMonth && !in_array($currentMonth, $recurrenceMonths))
);
@@ -537,6 +537,83 @@ class RRuleIterator implements Iterator {
}
+ if ($this->byWeekNo !== null) { // byWeekNo is an array with values from -53 to -1, or 1 to 53
+ $dayOffsets = [];
+ if ($this->byDay) {
+ foreach ($this->byDay as $byDay) {
+ $dayOffsets[] = $this->dayMap[$byDay];
+ }
+ } else { // default is Monday
+ $dayOffsets[] = 1;
+ }
+
+ $currentYear = $this->currentDate->format('Y');
+
+ while (true) {
+ $checkDates = [];
+
+ // loop through all WeekNo and Days to check all the combinations
+ foreach ($this->byWeekNo as $byWeekNo) {
+ foreach ($dayOffsets as $dayOffset) {
+ $date = clone $this->currentDate;
+ $date->setISODate($currentYear, $byWeekNo, $dayOffset);
+
+ if ($date > $this->currentDate) {
+ $checkDates[] = $date;
+ }
+ }
+ }
+
+ if (count($checkDates) > 0) {
+ $this->currentDate = min($checkDates);
+ return;
+ }
+
+ // if there is no date found, check the next year
+ $currentYear += $this->interval;
+ }
+ }
+
+ if ($this->byYearDay !== null) { // byYearDay is an array with values from -366 to -1, or 1 to 366
+ $dayOffsets = [];
+ if ($this->byDay) {
+ foreach ($this->byDay as $byDay) {
+ $dayOffsets[] = $this->dayMap[$byDay];
+ }
+ } else { // default is Monday-Sunday
+ $dayOffsets = [1,2,3,4,5,6,7];
+ }
+
+ $currentYear = $this->currentDate->format('Y');
+
+ while (true) {
+ $checkDates = [];
+
+ // loop through all YearDay and Days to check all the combinations
+ foreach ($this->byYearDay as $byYearDay) {
+ $date = clone $this->currentDate;
+ $date->setDate($currentYear, 1, 1);
+ if ($byYearDay > 0) {
+ $date->add(new \DateInterval('P' . $byYearDay . 'D'));
+ } else {
+ $date->sub(new \DateInterval('P' . abs($byYearDay) . 'D'));
+ }
+
+ if ($date > $this->currentDate && in_array($date->format('N'), $dayOffsets)) {
+ $checkDates[] = $date;
+ }
+ }
+
+ if (count($checkDates) > 0) {
+ $this->currentDate = min($checkDates);
+ return;
+ }
+
+ // if there is no date found, check the next year
+ $currentYear += $this->interval;
+ }
+ }
+
// The easiest form
$this->currentDate = $this->currentDate->modify('+' . $this->interval . ' years');
return;
@@ -710,10 +787,20 @@ class RRuleIterator implements Iterator {
case 'BYYEARDAY' :
$this->byYearDay = (array)$value;
+ foreach ($this->byYearDay as $byYearDay) {
+ if (!is_numeric($byYearDay) || (int)$byYearDay < -366 || (int)$byYearDay == 0 || (int)$byYearDay > 366) {
+ throw new InvalidDataException('BYYEARDAY in RRULE must have value(s) from 1 to 366, or -366 to -1!');
+ }
+ }
break;
case 'BYWEEKNO' :
$this->byWeekNo = (array)$value;
+ foreach ($this->byWeekNo as $byWeekNo) {
+ if (!is_numeric($byWeekNo) || (int)$byWeekNo < -53 || (int)$byWeekNo == 0 || (int)$byWeekNo > 53) {
+ throw new InvalidDataException('BYWEEKNO in RRULE must have value(s) from 1 to 53, or -53 to -1!');
+ }
+ }
break;
case 'BYMONTH' :
diff --git a/vendor/sabre/vobject/lib/TimeZoneUtil.php b/vendor/sabre/vobject/lib/TimeZoneUtil.php
index 2a95ae898..925183e8d 100644
--- a/vendor/sabre/vobject/lib/TimeZoneUtil.php
+++ b/vendor/sabre/vobject/lib/TimeZoneUtil.php
@@ -165,6 +165,16 @@ class TimeZoneUtil {
return new \DateTimeZone(self::$map[$tzid]);
}
+ // Some Microsoft products prefix the offset first, so let's strip that off
+ // and see if it is our tzid map. We don't want to check for this first just
+ // in case there are overrides in our tzid map.
+ if (preg_match('/^\((UTC|GMT)(\+|\-)[\d]{2}\:[\d]{2}\) (.*)/', $tzid, $matches)) {
+ $tzidAlternate = $matches[3];
+ if (isset(self::$map[$tzidAlternate])) {
+ return new \DateTimeZone(self::$map[$tzidAlternate]);
+ }
+ }
+
// Maybe the author was hyper-lazy and just included an offset. We
// support it, but we aren't happy about it.
if (preg_match('/^GMT(\+|-)([0-9]{4})$/', $tzid, $matches)) {
diff --git a/vendor/sabre/vobject/lib/Version.php b/vendor/sabre/vobject/lib/Version.php
index ca9f21960..346e2044d 100644
--- a/vendor/sabre/vobject/lib/Version.php
+++ b/vendor/sabre/vobject/lib/Version.php
@@ -14,6 +14,6 @@ class Version {
/**
* Full version number.
*/
- const VERSION = '4.1.1';
+ const VERSION = '4.1.2';
}
diff --git a/vendor/sabre/vobject/lib/timezonedata/lotuszones.php b/vendor/sabre/vobject/lib/timezonedata/lotuszones.php
index 7d0785f04..79d555a92 100644
--- a/vendor/sabre/vobject/lib/timezonedata/lotuszones.php
+++ b/vendor/sabre/vobject/lib/timezonedata/lotuszones.php
@@ -17,85 +17,85 @@ return [
'Mexico Standard Time 2' => 'America/Chihuahua',
'Mountain' => 'America/Denver',
// 'Mountain Standard Time' => 'America/Chihuahua', // conflict with windows timezones.
- 'US Mountain' => 'America/Phoenix',
- 'Canada Central' => 'America/Edmonton',
- 'Central America' => 'America/Guatemala',
- 'Central' => 'America/Chicago',
+ 'US Mountain' => 'America/Phoenix',
+ 'Canada Central' => 'America/Edmonton',
+ 'Central America' => 'America/Guatemala',
+ 'Central' => 'America/Chicago',
// 'Central Standard Time' => 'America/Mexico_City', // conflict with windows timezones.
- 'Mexico' => 'America/Mexico_City',
- 'Eastern' => 'America/New_York',
- 'SA Pacific' => 'America/Bogota',
- 'US Eastern' => 'America/Indiana/Indianapolis',
- 'Venezuela' => 'America/Caracas',
- 'Atlantic' => 'America/Halifax',
- 'Central Brazilian' => 'America/Manaus',
- 'Pacific SA' => 'America/Santiago',
- 'SA Western' => 'America/La_Paz',
- 'Newfoundland' => 'America/St_Johns',
- 'Argentina' => 'America/Argentina/Buenos_Aires',
- 'E. South America' => 'America/Belem',
- 'Greenland' => 'America/Godthab',
- 'Montevideo' => 'America/Montevideo',
- 'SA Eastern' => 'America/Belem',
+ 'Mexico' => 'America/Mexico_City',
+ 'Eastern' => 'America/New_York',
+ 'SA Pacific' => 'America/Bogota',
+ 'US Eastern' => 'America/Indiana/Indianapolis',
+ 'Venezuela' => 'America/Caracas',
+ 'Atlantic' => 'America/Halifax',
+ 'Central Brazilian' => 'America/Manaus',
+ 'Pacific SA' => 'America/Santiago',
+ 'SA Western' => 'America/La_Paz',
+ 'Newfoundland' => 'America/St_Johns',
+ 'Argentina' => 'America/Argentina/Buenos_Aires',
+ 'E. South America' => 'America/Belem',
+ 'Greenland' => 'America/Godthab',
+ 'Montevideo' => 'America/Montevideo',
+ 'SA Eastern' => 'America/Belem',
// 'Mid-Atlantic' => 'Etc/GMT-2', // conflict with windows timezones.
- 'Azores' => 'Atlantic/Azores',
- 'Cape Verde' => 'Atlantic/Cape_Verde',
- 'Greenwich' => 'Atlantic/Reykjavik', // No I'm serious.. Greenwich is not GMT.
- 'Morocco' => 'Africa/Casablanca',
- 'Central Europe' => 'Europe/Prague',
- 'Central European' => 'Europe/Sarajevo',
- 'Romance' => 'Europe/Paris',
- 'W. Central Africa' => 'Africa/Lagos', // Best guess
- 'W. Europe' => 'Europe/Amsterdam',
- 'E. Europe' => 'Europe/Minsk',
- 'Egypt' => 'Africa/Cairo',
- 'FLE' => 'Europe/Helsinki',
- 'GTB' => 'Europe/Athens',
- 'Israel' => 'Asia/Jerusalem',
- 'Jordan' => 'Asia/Amman',
- 'Middle East' => 'Asia/Beirut',
- 'Namibia' => 'Africa/Windhoek',
- 'South Africa' => 'Africa/Harare',
- 'Arab' => 'Asia/Kuwait',
- 'Arabic' => 'Asia/Baghdad',
- 'E. Africa' => 'Africa/Nairobi',
- 'Georgian' => 'Asia/Tbilisi',
- 'Russian' => 'Europe/Moscow',
- 'Iran' => 'Asia/Tehran',
- 'Arabian' => 'Asia/Muscat',
- 'Armenian' => 'Asia/Yerevan',
- 'Azerbijan' => 'Asia/Baku',
- 'Caucasus' => 'Asia/Yerevan',
- 'Mauritius' => 'Indian/Mauritius',
- 'Afghanistan' => 'Asia/Kabul',
- 'Ekaterinburg' => 'Asia/Yekaterinburg',
- 'Pakistan' => 'Asia/Karachi',
- 'West Asia' => 'Asia/Tashkent',
- 'India' => 'Asia/Calcutta',
- 'Sri Lanka' => 'Asia/Colombo',
- 'Nepal' => 'Asia/Kathmandu',
- 'Central Asia' => 'Asia/Dhaka',
- 'N. Central Asia' => 'Asia/Almaty',
- 'Myanmar' => 'Asia/Rangoon',
- 'North Asia' => 'Asia/Krasnoyarsk',
- 'SE Asia' => 'Asia/Bangkok',
- 'China' => 'Asia/Shanghai',
- 'North Asia East' => 'Asia/Irkutsk',
- 'Singapore' => 'Asia/Singapore',
- 'Taipei' => 'Asia/Taipei',
- 'W. Australia' => 'Australia/Perth',
- 'Korea' => 'Asia/Seoul',
- 'Tokyo' => 'Asia/Tokyo',
- 'Yakutsk' => 'Asia/Yakutsk',
- 'AUS Central' => 'Australia/Darwin',
- 'Cen. Australia' => 'Australia/Adelaide',
- 'AUS Eastern' => 'Australia/Sydney',
- 'E. Australia' => 'Australia/Brisbane',
- 'Tasmania' => 'Australia/Hobart',
- 'Vladivostok' => 'Asia/Vladivostok',
- 'West Pacific' => 'Pacific/Guam',
- 'Central Pacific' => 'Asia/Magadan',
- 'Fiji' => 'Pacific/Fiji',
- 'New Zealand' => 'Pacific/Auckland',
- 'Tonga' => 'Pacific/Tongatapu',
+ 'Azores' => 'Atlantic/Azores',
+ 'Cape Verde' => 'Atlantic/Cape_Verde',
+ 'Greenwich' => 'Atlantic/Reykjavik', // No I'm serious.. Greenwich is not GMT.
+ 'Morocco' => 'Africa/Casablanca',
+ 'Central Europe' => 'Europe/Prague',
+ 'Central European' => 'Europe/Sarajevo',
+ 'Romance' => 'Europe/Paris',
+ 'W. Central Africa' => 'Africa/Lagos', // Best guess
+ 'W. Europe' => 'Europe/Amsterdam',
+ 'E. Europe' => 'Europe/Minsk',
+ 'Egypt' => 'Africa/Cairo',
+ 'FLE' => 'Europe/Helsinki',
+ 'GTB' => 'Europe/Athens',
+ 'Israel' => 'Asia/Jerusalem',
+ 'Jordan' => 'Asia/Amman',
+ 'Middle East' => 'Asia/Beirut',
+ 'Namibia' => 'Africa/Windhoek',
+ 'South Africa' => 'Africa/Harare',
+ 'Arab' => 'Asia/Kuwait',
+ 'Arabic' => 'Asia/Baghdad',
+ 'E. Africa' => 'Africa/Nairobi',
+ 'Georgian' => 'Asia/Tbilisi',
+ 'Russian' => 'Europe/Moscow',
+ 'Iran' => 'Asia/Tehran',
+ 'Arabian' => 'Asia/Muscat',
+ 'Armenian' => 'Asia/Yerevan',
+ 'Azerbijan' => 'Asia/Baku',
+ 'Caucasus' => 'Asia/Yerevan',
+ 'Mauritius' => 'Indian/Mauritius',
+ 'Afghanistan' => 'Asia/Kabul',
+ 'Ekaterinburg' => 'Asia/Yekaterinburg',
+ 'Pakistan' => 'Asia/Karachi',
+ 'West Asia' => 'Asia/Tashkent',
+ 'India' => 'Asia/Calcutta',
+ 'Sri Lanka' => 'Asia/Colombo',
+ 'Nepal' => 'Asia/Kathmandu',
+ 'Central Asia' => 'Asia/Dhaka',
+ 'N. Central Asia' => 'Asia/Almaty',
+ 'Myanmar' => 'Asia/Rangoon',
+ 'North Asia' => 'Asia/Krasnoyarsk',
+ 'SE Asia' => 'Asia/Bangkok',
+ 'China' => 'Asia/Shanghai',
+ 'North Asia East' => 'Asia/Irkutsk',
+ 'Singapore' => 'Asia/Singapore',
+ 'Taipei' => 'Asia/Taipei',
+ 'W. Australia' => 'Australia/Perth',
+ 'Korea' => 'Asia/Seoul',
+ 'Tokyo' => 'Asia/Tokyo',
+ 'Yakutsk' => 'Asia/Yakutsk',
+ 'AUS Central' => 'Australia/Darwin',
+ 'Cen. Australia' => 'Australia/Adelaide',
+ 'AUS Eastern' => 'Australia/Sydney',
+ 'E. Australia' => 'Australia/Brisbane',
+ 'Tasmania' => 'Australia/Hobart',
+ 'Vladivostok' => 'Asia/Vladivostok',
+ 'West Pacific' => 'Pacific/Guam',
+ 'Central Pacific' => 'Asia/Magadan',
+ 'Fiji' => 'Pacific/Fiji',
+ 'New Zealand' => 'Pacific/Auckland',
+ 'Tonga' => 'Pacific/Tongatapu',
];
diff --git a/vendor/sabre/vobject/lib/timezonedata/windowszones.php b/vendor/sabre/vobject/lib/timezonedata/windowszones.php
index ac69847cc..29f3a6cb8 100644
--- a/vendor/sabre/vobject/lib/timezonedata/windowszones.php
+++ b/vendor/sabre/vobject/lib/timezonedata/windowszones.php
@@ -3,28 +3,33 @@
/**
* Automatically generated timezone file
*
- * Last update: 2015-07-27T16:56:36-04:00
+ * Last update: 2016-08-24T17:35:38-04:00
* Source: http://unicode.org/repos/cldr/trunk/common/supplemental/windowsZones.xml
*
- * @copyright Copyright (C) fruux GmbH (https://fruux.com/)
+ * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/).
* @license http://sabre.io/license/ Modified BSD License
*/
-return [
+return [
'AUS Central Standard Time' => 'Australia/Darwin',
'AUS Eastern Standard Time' => 'Australia/Sydney',
'Afghanistan Standard Time' => 'Asia/Kabul',
'Alaskan Standard Time' => 'America/Anchorage',
+ 'Aleutian Standard Time' => 'America/Adak',
+ 'Altai Standard Time' => 'Asia/Barnaul',
'Arab Standard Time' => 'Asia/Riyadh',
'Arabian Standard Time' => 'Asia/Dubai',
'Arabic Standard Time' => 'Asia/Baghdad',
'Argentina Standard Time' => 'America/Buenos_Aires',
+ 'Astrakhan Standard Time' => 'Europe/Astrakhan',
'Atlantic Standard Time' => 'America/Halifax',
+ 'Aus Central W. Standard Time' => 'Australia/Eucla',
'Azerbaijan Standard Time' => 'Asia/Baku',
'Azores Standard Time' => 'Atlantic/Azores',
'Bahia Standard Time' => 'America/Bahia',
'Bangladesh Standard Time' => 'Asia/Dhaka',
'Belarus Standard Time' => 'Europe/Minsk',
+ 'Bougainville Standard Time' => 'Pacific/Bougainville',
'Canada Central Standard Time' => 'America/Regina',
'Cape Verde Standard Time' => 'Atlantic/Cape_Verde',
'Caucasus Standard Time' => 'Asia/Yerevan',
@@ -37,11 +42,15 @@ return [
'Central Pacific Standard Time' => 'Pacific/Guadalcanal',
'Central Standard Time' => 'America/Chicago',
'Central Standard Time (Mexico)' => 'America/Mexico_City',
+ 'Chatham Islands Standard Time' => 'Pacific/Chatham',
'China Standard Time' => 'Asia/Shanghai',
+ 'Cuba Standard Time' => 'America/Havana',
'Dateline Standard Time' => 'Etc/GMT+12',
'E. Africa Standard Time' => 'Africa/Nairobi',
'E. Australia Standard Time' => 'Australia/Brisbane',
+ 'E. Europe Standard Time' => 'Europe/Chisinau',
'E. South America Standard Time' => 'America/Sao_Paulo',
+ 'Easter Island Standard Time' => 'Pacific/Easter',
'Eastern Standard Time' => 'America/New_York',
'Eastern Standard Time (Mexico)' => 'America/Cancun',
'Egypt Standard Time' => 'Africa/Cairo',
@@ -53,6 +62,7 @@ return [
'Georgian Standard Time' => 'Asia/Tbilisi',
'Greenland Standard Time' => 'America/Godthab',
'Greenwich Standard Time' => 'Atlantic/Reykjavik',
+ 'Haiti Standard Time' => 'America/Port-au-Prince',
'Hawaiian Standard Time' => 'Pacific/Honolulu',
'India Standard Time' => 'Asia/Calcutta',
'Iran Standard Time' => 'Asia/Tehran',
@@ -62,7 +72,9 @@ return [
'Korea Standard Time' => 'Asia/Seoul',
'Libya Standard Time' => 'Africa/Tripoli',
'Line Islands Standard Time' => 'Pacific/Kiritimati',
+ 'Lord Howe Standard Time' => 'Australia/Lord_Howe',
'Magadan Standard Time' => 'Asia/Magadan',
+ 'Marquesas Standard Time' => 'Pacific/Marquesas',
'Mauritius Standard Time' => 'Indian/Mauritius',
'Middle East Standard Time' => 'Asia/Beirut',
'Montevideo Standard Time' => 'America/Montevideo',
@@ -75,11 +87,13 @@ return [
'Nepal Standard Time' => 'Asia/Katmandu',
'New Zealand Standard Time' => 'Pacific/Auckland',
'Newfoundland Standard Time' => 'America/St_Johns',
+ 'Norfolk Standard Time' => 'Pacific/Norfolk',
'North Asia East Standard Time' => 'Asia/Irkutsk',
'North Asia Standard Time' => 'Asia/Krasnoyarsk',
+ 'North Korea Standard Time' => 'Asia/Pyongyang',
'Pacific SA Standard Time' => 'America/Santiago',
'Pacific Standard Time' => 'America/Los_Angeles',
- 'Pacific Standard Time (Mexico)' => 'America/Santa_Isabel',
+ 'Pacific Standard Time (Mexico)' => 'America/Tijuana',
'Pakistan Standard Time' => 'Asia/Karachi',
'Paraguay Standard Time' => 'America/Asuncion',
'Romance Standard Time' => 'Europe/Paris',
@@ -91,6 +105,8 @@ return [
'SA Pacific Standard Time' => 'America/Bogota',
'SA Western Standard Time' => 'America/La_Paz',
'SE Asia Standard Time' => 'Asia/Bangkok',
+ 'Saint Pierre Standard Time' => 'America/Miquelon',
+ 'Sakhalin Standard Time' => 'Asia/Sakhalin',
'Samoa Standard Time' => 'Pacific/Apia',
'Singapore Standard Time' => 'Asia/Singapore',
'South Africa Standard Time' => 'Africa/Johannesburg',
@@ -98,14 +114,20 @@ return [
'Syria Standard Time' => 'Asia/Damascus',
'Taipei Standard Time' => 'Asia/Taipei',
'Tasmania Standard Time' => 'Australia/Hobart',
+ 'Tocantins Standard Time' => 'America/Araguaina',
'Tokyo Standard Time' => 'Asia/Tokyo',
+ 'Tomsk Standard Time' => 'Asia/Tomsk',
'Tonga Standard Time' => 'Pacific/Tongatapu',
+ 'Transbaikal Standard Time' => 'Asia/Chita',
'Turkey Standard Time' => 'Europe/Istanbul',
+ 'Turks And Caicos Standard Time' => 'America/Grand_Turk',
'US Eastern Standard Time' => 'America/Indianapolis',
'US Mountain Standard Time' => 'America/Phoenix',
'UTC' => 'Etc/GMT',
'UTC+12' => 'Etc/GMT-12',
'UTC-02' => 'Etc/GMT+2',
+ 'UTC-08' => 'Etc/GMT+8',
+ 'UTC-09' => 'Etc/GMT+9',
'UTC-11' => 'Etc/GMT+11',
'Ulaanbaatar Standard Time' => 'Asia/Ulaanbaatar',
'Venezuela Standard Time' => 'America/Caracas',
@@ -113,7 +135,9 @@ return [
'W. Australia Standard Time' => 'Australia/Perth',
'W. Central Africa Standard Time' => 'Africa/Lagos',
'W. Europe Standard Time' => 'Europe/Berlin',
+ 'W. Mongolia Standard Time' => 'Asia/Hovd',
'West Asia Standard Time' => 'Asia/Tashkent',
+ 'West Bank Standard Time' => 'Asia/Hebron',
'West Pacific Standard Time' => 'Pacific/Port_Moresby',
'Yakutsk Standard Time' => 'Asia/Yakutsk',
];
diff --git a/library/simplepie/LICENSE.txt b/vendor/simplepie/simplepie/LICENSE.txt
index a822a4bd9..a822a4bd9 100644
--- a/library/simplepie/LICENSE.txt
+++ b/vendor/simplepie/simplepie/LICENSE.txt
diff --git a/vendor/simplepie/simplepie/README.markdown b/vendor/simplepie/simplepie/README.markdown
new file mode 100644
index 000000000..c346204d0
--- /dev/null
+++ b/vendor/simplepie/simplepie/README.markdown
@@ -0,0 +1,113 @@
+SimplePie
+=========
+
+SimplePie is a very fast and easy-to-use class, written in PHP, that puts the
+'simple' back into 'really simple syndication'. Flexible enough to suit
+beginners and veterans alike, SimplePie is focused on [speed, ease of use,
+compatibility and standards compliance][what_is].
+
+[what_is]: http://simplepie.org/wiki/faq/what_is_simplepie
+
+
+Requirements
+------------
+* PHP 5.3.0+ (5.3.6+ recommended since SimplePie 1.4.2)
+ * Support for PHP 5.2 stopped in branch `one-dot-three`
+ * Support for PHP 4 stopped in branch `one-dot-two`
+* libxml2 (certain 2.7.x releases are too buggy for words, and will crash)
+* One of iconv, mbstring or intl extensions
+* cURL or fsockopen()
+* PCRE support
+
+
+What comes in the package?
+--------------------------
+1. `library/` - SimplePie classes for use with the autoloader
+2. `autoloader.php` - The SimplePie Autoloader if you want to use the separate
+ file version.
+3. `README.markdown` - This document.
+4. `LICENSE.txt` - A copy of the BSD license.
+5. `compatibility_test/` - The SimplePie compatibility test that checks your
+ server for required settings.
+6. `demo/` - A basic feed reader demo that shows off some of SimplePie's more
+ noticeable features.
+7. `idn/` - A third-party library that SimplePie can optionally use to
+ understand Internationalized Domain Names (IDNs).
+8. `build/` - Scripts related to generating pieces of SimplePie
+9. `test/` - SimplePie's unit test suite.
+
+### Where's `simplepie.inc`?
+Since SimplePie 1.3, we've split the classes into separate files to make it easier
+to maintain and use.
+
+If you'd like a single monolithic file, you can run `php build/compile.php` to
+generate `SimplePie.compiled.php`.
+
+To start the demo
+-----------------
+1. Upload this package to your webserver.
+2. Make sure that the cache folder inside of the demo folder is server-writable.
+3. Navigate your browser to the demo folder.
+
+
+Need support?
+-------------
+For further setup and install documentation, function references, etc., visit
+[the wiki][wiki]. If you're using the latest version off GitHub, you can also
+check out the [API documentation][].
+
+If you can't find an answer to your question in the documentation, head on over
+to one of our [support channels][]. For bug reports and feature requests, visit
+the [issue tracker][].
+
+[API documentation]: http://dev.simplepie.org/api/
+[wiki]: http://simplepie.org/wiki/
+[support channels]: http://simplepie.org/support/
+[issue tracker]: http://github.com/simplepie/simplepie/issues
+
+
+Project status
+--------------
+SimplePie is currently maintained by Malcolm Blaney.
+
+As an open source project, SimplePie is maintained on a somewhat sporadic basis.
+This means that feature requests may not be fulfilled straight away, as time has
+to be prioritized.
+
+If you'd like to contribute to SimplePie, the best way to get started is to fork
+the project on GitHub and send pull requests for patches. When doing so, please
+be aware of our [coding standards][].
+
+[coding standards]: http://simplepie.org/wiki/misc/coding_standards
+
+
+Authors and contributors
+------------------------
+### Current
+* [Malcolm Blaney][] (Maintainer, support)
+
+### Alumni
+* [Ryan McCue][] (developer, support)
+* [Ryan Parman][] (Creator, developer, evangelism, support)
+* [Geoffrey Sneddon][] (Lead developer)
+* [Michael Shipley][] (Submitter of patches, support)
+* [Steve Minutillo][] (Submitter of patches)
+
+[Malcolm Blaney]: https://unicyclic.com/mal
+[Ryan McCue]: http://ryanmccue.info
+[Ryan Parman]: http://ryanparman.com
+[Geoffrey Sneddon]: http://gsnedders.com
+[Michael Shipley]: http://michaelpshipley.com
+[Steve Minutillo]: http://minutillo.com/steve/
+
+
+### Contributors
+For a complete list of contributors:
+
+1. Pull down the latest SimplePie code
+2. In the `simplepie` directory, run `git shortlog -ns`
+
+
+License
+-------
+[New BSD license](http://www.opensource.org/licenses/BSD-3-Clause)
diff --git a/vendor/simplepie/simplepie/autoloader.php b/vendor/simplepie/simplepie/autoloader.php
new file mode 100644
index 000000000..fd7690da2
--- /dev/null
+++ b/vendor/simplepie/simplepie/autoloader.php
@@ -0,0 +1,85 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+
+// autoloader
+spl_autoload_register(array(new SimplePie_Autoloader(), 'autoload'));
+
+if (!class_exists('SimplePie'))
+{
+ trigger_error('Autoloader not registered properly', E_USER_ERROR);
+}
+
+/**
+ * Autoloader class
+ *
+ * @package SimplePie
+ * @subpackage API
+ */
+class SimplePie_Autoloader
+{
+ /**
+ * Constructor
+ */
+ public function __construct()
+ {
+ $this->path = dirname(__FILE__) . DIRECTORY_SEPARATOR . 'library';
+ }
+
+ /**
+ * Autoloader
+ *
+ * @param string $class The name of the class to attempt to load.
+ */
+ public function autoload($class)
+ {
+ // Only load the class if it starts with "SimplePie"
+ if (strpos($class, 'SimplePie') !== 0)
+ {
+ return;
+ }
+
+ $filename = $this->path . DIRECTORY_SEPARATOR . str_replace('_', DIRECTORY_SEPARATOR, $class) . '.php';
+ include $filename;
+ }
+} \ No newline at end of file
diff --git a/vendor/simplepie/simplepie/composer.json b/vendor/simplepie/simplepie/composer.json
new file mode 100644
index 000000000..b5965b26f
--- /dev/null
+++ b/vendor/simplepie/simplepie/composer.json
@@ -0,0 +1,40 @@
+{
+ "name": "simplepie/simplepie",
+ "description": "A simple Atom/RSS parsing library for PHP",
+ "type": "library",
+ "keywords": ["rss", "atom", "feeds"],
+ "homepage": "http://simplepie.org/",
+ "license": "BSD-3-Clause",
+ "authors": [
+ {
+ "name": "Ryan Parman",
+ "homepage": "http://ryanparman.com/",
+ "role": "Creator, alumnus developer"
+ },
+ {
+ "name": "Geoffrey Sneddon",
+ "homepage": "http://gsnedders.com/",
+ "role": "Alumnus developer"
+ },
+ {
+ "name": "Ryan McCue",
+ "email": "me@ryanmccue.info",
+ "homepage": "http://ryanmccue.info/",
+ "role": "Developer"
+ }
+ ],
+ "require": {
+ "php": ">=5.3.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "~4 || ~5"
+ },
+ "suggest": {
+ "mf2/mf2": "Microformat module that allows for parsing HTML for microformats"
+ },
+ "autoload": {
+ "psr-0": {
+ "SimplePie": "library"
+ }
+ }
+}
diff --git a/vendor/simplepie/simplepie/db.sql b/vendor/simplepie/simplepie/db.sql
new file mode 100644
index 000000000..879382940
--- /dev/null
+++ b/vendor/simplepie/simplepie/db.sql
@@ -0,0 +1,40 @@
+/* SQLite */
+CREATE TABLE cache_data (
+ id TEXT NOT NULL,
+ items SMALLINT NOT NULL DEFAULT 0,
+ data BLOB NOT NULL,
+ mtime INTEGER UNSIGNED NOT NULL
+);
+CREATE UNIQUE INDEX id ON cache_data(id);
+
+CREATE TABLE items (
+ feed_id TEXT NOT NULL,
+ id TEXT NOT NULL,
+ data TEXT NOT NULL,
+ posted INTEGER UNSIGNED NOT NULL
+);
+CREATE INDEX feed_id ON items(feed_id);
+
+
+/* MySQL */
+--- Don't paste this to create tables, since SimplePie will create
+--- tables by its own.
+CREATE TABLE `cache_data` (
+ `id` TEXT CHARACTER SET utf8 NOT NULL,
+ `items` SMALLINT NOT NULL DEFAULT 0,
+ `data` BLOB NOT NULL,
+ `mtime` INT UNSIGNED NOT NULL,
+ UNIQUE (
+ `id`(125)
+ )
+);
+
+CREATE TABLE `items` (
+ `feed_id` TEXT CHARACTER SET utf8 NOT NULL,
+ `id` TEXT CHARACTER SET utf8 NOT NULL,
+ `data` MEDIUMBLOB NOT NULL,
+ `posted` INT UNSIGNED NOT NULL,
+ INDEX `feed_id` (
+ `feed_id`(125)
+ )
+); \ No newline at end of file
diff --git a/library/simplepie/idn/LICENCE b/vendor/simplepie/simplepie/idn/LICENCE
index 25a1d22df..25a1d22df 100644
--- a/library/simplepie/idn/LICENCE
+++ b/vendor/simplepie/simplepie/idn/LICENCE
diff --git a/library/simplepie/idn/ReadMe.txt b/vendor/simplepie/simplepie/idn/ReadMe.txt
index 7ca8c7e6d..7ca8c7e6d 100644
--- a/library/simplepie/idn/ReadMe.txt
+++ b/vendor/simplepie/simplepie/idn/ReadMe.txt
diff --git a/vendor/simplepie/simplepie/idn/idna_convert.class.php b/vendor/simplepie/simplepie/idn/idna_convert.class.php
new file mode 100644
index 000000000..eb9d5f516
--- /dev/null
+++ b/vendor/simplepie/simplepie/idn/idna_convert.class.php
@@ -0,0 +1,969 @@
+<?php
+// {{{ license
+
+/* vim: set expandtab tabstop=4 shiftwidth=4 softtabstop=4 foldmethod=marker: */
+//
+// +----------------------------------------------------------------------+
+// | This library is free software; you can redistribute it and/or modify |
+// | it under the terms of the GNU Lesser General Public License as |
+// | published by the Free Software Foundation; either version 2.1 of the |
+// | License, or (at your option) any later version. |
+// | |
+// | This library 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 |
+// | Lesser General Public License for more details. |
+// | |
+// | You should have received a copy of the GNU Lesser General Public |
+// | License along with this library; if not, write to the Free Software |
+// | Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 |
+// | USA. |
+// +----------------------------------------------------------------------+
+//
+
+// }}}
+
+/**
+ * Encode/decode Internationalized Domain Names.
+ *
+ * The class allows to convert internationalized domain names
+ * (see RFC 3490 for details) as they can be used with various registries worldwide
+ * to be translated between their original (localized) form and their encoded form
+ * as it will be used in the DNS (Domain Name System).
+ *
+ * The class provides two public methods, encode() and decode(), which do exactly
+ * what you would expect them to do. You are allowed to use complete domain names,
+ * simple strings and complete email addresses as well. That means, that you might
+ * use any of the following notations:
+ *
+ * - www.nörgler.com
+ * - xn--nrgler-wxa
+ * - xn--brse-5qa.xn--knrz-1ra.info
+ *
+ * Unicode input might be given as either UTF-8 string, UCS-4 string or UCS-4
+ * array. Unicode output is available in the same formats.
+ * You can select your preferred format via {@link set_paramter()}.
+ *
+ * ACE input and output is always expected to be ASCII.
+ *
+ * @author Matthias Sommerfeld <mso@phlylabs.de>
+ * @copyright 2004-2007 phlyLabs Berlin, http://phlylabs.de
+ * @version 0.5.1
+ *
+ */
+class idna_convert
+{
+ /**
+ * Holds all relevant mapping tables, loaded from a seperate file on construct
+ * See RFC3454 for details
+ *
+ * @var array
+ * @access private
+ */
+ var $NP = array();
+
+ // Internal settings, do not mess with them
+ var $_punycode_prefix = 'xn--';
+ var $_invalid_ucs = 0x80000000;
+ var $_max_ucs = 0x10FFFF;
+ var $_base = 36;
+ var $_tmin = 1;
+ var $_tmax = 26;
+ var $_skew = 38;
+ var $_damp = 700;
+ var $_initial_bias = 72;
+ var $_initial_n = 0x80;
+ var $_sbase = 0xAC00;
+ var $_lbase = 0x1100;
+ var $_vbase = 0x1161;
+ var $_tbase = 0x11A7;
+ var $_lcount = 19;
+ var $_vcount = 21;
+ var $_tcount = 28;
+ var $_ncount = 588; // _vcount * _tcount
+ var $_scount = 11172; // _lcount * _tcount * _vcount
+ var $_error = false;
+
+ // See {@link set_paramter()} for details of how to change the following
+ // settings from within your script / application
+ var $_api_encoding = 'utf8'; // Default input charset is UTF-8
+ var $_allow_overlong = false; // Overlong UTF-8 encodings are forbidden
+ var $_strict_mode = false; // Behave strict or not
+
+ // The constructor
+ function __construct($options = false)
+ {
+ $this->slast = $this->_sbase + $this->_lcount * $this->_vcount * $this->_tcount;
+ if (function_exists('file_get_contents')) {
+ $this->NP = unserialize(file_get_contents(dirname(__FILE__).'/npdata.ser'));
+ } else {
+ $this->NP = unserialize(join('', file(dirname(__FILE__).'/npdata.ser')));
+ }
+ // If parameters are given, pass these to the respective method
+ if (is_array($options)) {
+ return $this->set_parameter($options);
+ }
+ return true;
+ }
+
+ /**
+ * Sets a new option value. Available options and values:
+ * [encoding - Use either UTF-8, UCS4 as array or UCS4 as string as input ('utf8' for UTF-8,
+ * 'ucs4_string' and 'ucs4_array' respectively for UCS4); The output is always UTF-8]
+ * [overlong - Unicode does not allow unnecessarily long encodings of chars,
+ * to allow this, set this parameter to true, else to false;
+ * default is false.]
+ * [strict - true: strict mode, good for registration purposes - Causes errors
+ * on failures; false: loose mode, ideal for "wildlife" applications
+ * by silently ignoring errors and returning the original input instead
+ *
+ * @param mixed Parameter to set (string: single parameter; array of Parameter => Value pairs)
+ * @param string Value to use (if parameter 1 is a string)
+ * @return boolean true on success, false otherwise
+ * @access public
+ */
+ function set_parameter($option, $value = false)
+ {
+ if (!is_array($option)) {
+ $option = array($option => $value);
+ }
+ foreach ($option as $k => $v) {
+ switch ($k) {
+ case 'encoding':
+ switch ($v) {
+ case 'utf8':
+ case 'ucs4_string':
+ case 'ucs4_array':
+ $this->_api_encoding = $v;
+ break;
+ default:
+ $this->_error('Set Parameter: Unknown parameter '.$v.' for option '.$k);
+ return false;
+ }
+ break;
+ case 'overlong':
+ $this->_allow_overlong = ($v) ? true : false;
+ break;
+ case 'strict':
+ $this->_strict_mode = ($v) ? true : false;
+ break;
+ default:
+ $this->_error('Set Parameter: Unknown option '.$k);
+ return false;
+ }
+ }
+ return true;
+ }
+
+ /**
+ * Decode a given ACE domain name
+ * @param string Domain name (ACE string)
+ * [@param string Desired output encoding, see {@link set_parameter}]
+ * @return string Decoded Domain name (UTF-8 or UCS-4)
+ * @access public
+ */
+ function decode($input, $one_time_encoding = false)
+ {
+ // Optionally set
+ if ($one_time_encoding) {
+ switch ($one_time_encoding) {
+ case 'utf8':
+ case 'ucs4_string':
+ case 'ucs4_array':
+ break;
+ default:
+ $this->_error('Unknown encoding '.$one_time_encoding);
+ return false;
+ }
+ }
+ // Make sure to drop any newline characters around
+ $input = trim($input);
+
+ // Negotiate input and try to determine, whether it is a plain string,
+ // an email address or something like a complete URL
+ if (strpos($input, '@')) { // Maybe it is an email address
+ // No no in strict mode
+ if ($this->_strict_mode) {
+ $this->_error('Only simple domain name parts can be handled in strict mode');
+ return false;
+ }
+ list ($email_pref, $input) = explode('@', $input, 2);
+ $arr = explode('.', $input);
+ foreach ($arr as $k => $v) {
+ if (preg_match('!^'.preg_quote($this->_punycode_prefix, '!').'!', $v)) {
+ $conv = $this->_decode($v);
+ if ($conv) $arr[$k] = $conv;
+ }
+ }
+ $input = join('.', $arr);
+ $arr = explode('.', $email_pref);
+ foreach ($arr as $k => $v) {
+ if (preg_match('!^'.preg_quote($this->_punycode_prefix, '!').'!', $v)) {
+ $conv = $this->_decode($v);
+ if ($conv) $arr[$k] = $conv;
+ }
+ }
+ $email_pref = join('.', $arr);
+ $return = $email_pref . '@' . $input;
+ } elseif (preg_match('![:\./]!', $input)) { // Or a complete domain name (with or without paths / parameters)
+ // No no in strict mode
+ if ($this->_strict_mode) {
+ $this->_error('Only simple domain name parts can be handled in strict mode');
+ return false;
+ }
+ $parsed = parse_url($input);
+ if (isset($parsed['host'])) {
+ $arr = explode('.', $parsed['host']);
+ foreach ($arr as $k => $v) {
+ $conv = $this->_decode($v);
+ if ($conv) $arr[$k] = $conv;
+ }
+ $parsed['host'] = join('.', $arr);
+ $return =
+ (empty($parsed['scheme']) ? '' : $parsed['scheme'].(strtolower($parsed['scheme']) == 'mailto' ? ':' : '://'))
+ .(empty($parsed['user']) ? '' : $parsed['user'].(empty($parsed['pass']) ? '' : ':'.$parsed['pass']).'@')
+ .$parsed['host']
+ .(empty($parsed['port']) ? '' : ':'.$parsed['port'])
+ .(empty($parsed['path']) ? '' : $parsed['path'])
+ .(empty($parsed['query']) ? '' : '?'.$parsed['query'])
+ .(empty($parsed['fragment']) ? '' : '#'.$parsed['fragment']);
+ } else { // parse_url seems to have failed, try without it
+ $arr = explode('.', $input);
+ foreach ($arr as $k => $v) {
+ $conv = $this->_decode($v);
+ $arr[$k] = ($conv) ? $conv : $v;
+ }
+ $return = join('.', $arr);
+ }
+ } else { // Otherwise we consider it being a pure domain name string
+ $return = $this->_decode($input);
+ if (!$return) $return = $input;
+ }
+ // The output is UTF-8 by default, other output formats need conversion here
+ // If one time encoding is given, use this, else the objects property
+ switch (($one_time_encoding) ? $one_time_encoding : $this->_api_encoding) {
+ case 'utf8':
+ return $return;
+ break;
+ case 'ucs4_string':
+ return $this->_ucs4_to_ucs4_string($this->_utf8_to_ucs4($return));
+ break;
+ case 'ucs4_array':
+ return $this->_utf8_to_ucs4($return);
+ break;
+ default:
+ $this->_error('Unsupported output format');
+ return false;
+ }
+ }
+
+ /**
+ * Encode a given UTF-8 domain name
+ * @param string Domain name (UTF-8 or UCS-4)
+ * [@param string Desired input encoding, see {@link set_parameter}]
+ * @return string Encoded Domain name (ACE string)
+ * @access public
+ */
+ function encode($decoded, $one_time_encoding = false)
+ {
+ // Forcing conversion of input to UCS4 array
+ // If one time encoding is given, use this, else the objects property
+ switch ($one_time_encoding ? $one_time_encoding : $this->_api_encoding) {
+ case 'utf8':
+ $decoded = $this->_utf8_to_ucs4($decoded);
+ break;
+ case 'ucs4_string':
+ $decoded = $this->_ucs4_string_to_ucs4($decoded);
+ case 'ucs4_array':
+ break;
+ default:
+ $this->_error('Unsupported input format: '.($one_time_encoding ? $one_time_encoding : $this->_api_encoding));
+ return false;
+ }
+
+ // No input, no output, what else did you expect?
+ if (empty($decoded)) return '';
+
+ // Anchors for iteration
+ $last_begin = 0;
+ // Output string
+ $output = '';
+ foreach ($decoded as $k => $v) {
+ // Make sure to use just the plain dot
+ switch($v) {
+ case 0x3002:
+ case 0xFF0E:
+ case 0xFF61:
+ $decoded[$k] = 0x2E;
+ // Right, no break here, the above are converted to dots anyway
+ // Stumbling across an anchoring character
+ case 0x2E:
+ case 0x2F:
+ case 0x3A:
+ case 0x3F:
+ case 0x40:
+ // Neither email addresses nor URLs allowed in strict mode
+ if ($this->_strict_mode) {
+ $this->_error('Neither email addresses nor URLs are allowed in strict mode.');
+ return false;
+ } else {
+ // Skip first char
+ if ($k) {
+ $encoded = '';
+ $encoded = $this->_encode(array_slice($decoded, $last_begin, (($k)-$last_begin)));
+ if ($encoded) {
+ $output .= $encoded;
+ } else {
+ $output .= $this->_ucs4_to_utf8(array_slice($decoded, $last_begin, (($k)-$last_begin)));
+ }
+ $output .= chr($decoded[$k]);
+ }
+ $last_begin = $k + 1;
+ }
+ }
+ }
+ // Catch the rest of the string
+ if ($last_begin) {
+ $inp_len = sizeof($decoded);
+ $encoded = '';
+ $encoded = $this->_encode(array_slice($decoded, $last_begin, (($inp_len)-$last_begin)));
+ if ($encoded) {
+ $output .= $encoded;
+ } else {
+ $output .= $this->_ucs4_to_utf8(array_slice($decoded, $last_begin, (($inp_len)-$last_begin)));
+ }
+ return $output;
+ } else {
+ if ($output = $this->_encode($decoded)) {
+ return $output;
+ } else {
+ return $this->_ucs4_to_utf8($decoded);
+ }
+ }
+ }
+
+ /**
+ * Use this method to get the last error ocurred
+ * @param void
+ * @return string The last error, that occured
+ * @access public
+ */
+ function get_last_error()
+ {
+ return $this->_error;
+ }
+
+ /**
+ * The actual decoding algorithm
+ * @access private
+ */
+ function _decode($encoded)
+ {
+ // We do need to find the Punycode prefix
+ if (!preg_match('!^'.preg_quote($this->_punycode_prefix, '!').'!', $encoded)) {
+ $this->_error('This is not a punycode string');
+ return false;
+ }
+ $encode_test = preg_replace('!^'.preg_quote($this->_punycode_prefix, '!').'!', '', $encoded);
+ // If nothing left after removing the prefix, it is hopeless
+ if (!$encode_test) {
+ $this->_error('The given encoded string was empty');
+ return false;
+ }
+ // Find last occurence of the delimiter
+ $delim_pos = strrpos($encoded, '-');
+ if ($delim_pos > strlen($this->_punycode_prefix)) {
+ for ($k = strlen($this->_punycode_prefix); $k < $delim_pos; ++$k) {
+ $decoded[] = ord($encoded{$k});
+ }
+ } else {
+ $decoded = array();
+ }
+ $deco_len = count($decoded);
+ $enco_len = strlen($encoded);
+
+ // Wandering through the strings; init
+ $is_first = true;
+ $bias = $this->_initial_bias;
+ $idx = 0;
+ $char = $this->_initial_n;
+
+ for ($enco_idx = ($delim_pos) ? ($delim_pos + 1) : 0; $enco_idx < $enco_len; ++$deco_len) {
+ for ($old_idx = $idx, $w = 1, $k = $this->_base; 1 ; $k += $this->_base) {
+ $digit = $this->_decode_digit($encoded{$enco_idx++});
+ $idx += $digit * $w;
+ $t = ($k <= $bias) ? $this->_tmin :
+ (($k >= $bias + $this->_tmax) ? $this->_tmax : ($k - $bias));
+ if ($digit < $t) break;
+ $w = (int) ($w * ($this->_base - $t));
+ }
+ $bias = $this->_adapt($idx - $old_idx, $deco_len + 1, $is_first);
+ $is_first = false;
+ $char += (int) ($idx / ($deco_len + 1));
+ $idx %= ($deco_len + 1);
+ if ($deco_len > 0) {
+ // Make room for the decoded char
+ for ($i = $deco_len; $i > $idx; $i--) {
+ $decoded[$i] = $decoded[($i - 1)];
+ }
+ }
+ $decoded[$idx++] = $char;
+ }
+ return $this->_ucs4_to_utf8($decoded);
+ }
+
+ /**
+ * The actual encoding algorithm
+ * @access private
+ */
+ function _encode($decoded)
+ {
+ // We cannot encode a domain name containing the Punycode prefix
+ $extract = strlen($this->_punycode_prefix);
+ $check_pref = $this->_utf8_to_ucs4($this->_punycode_prefix);
+ $check_deco = array_slice($decoded, 0, $extract);
+
+ if ($check_pref == $check_deco) {
+ $this->_error('This is already a punycode string');
+ return false;
+ }
+ // We will not try to encode strings consisting of basic code points only
+ $encodable = false;
+ foreach ($decoded as $k => $v) {
+ if ($v > 0x7a) {
+ $encodable = true;
+ break;
+ }
+ }
+ if (!$encodable) {
+ $this->_error('The given string does not contain encodable chars');
+ return false;
+ }
+
+ // Do NAMEPREP
+ $decoded = $this->_nameprep($decoded);
+ if (!$decoded || !is_array($decoded)) return false; // NAMEPREP failed
+
+ $deco_len = count($decoded);
+ if (!$deco_len) return false; // Empty array
+
+ $codecount = 0; // How many chars have been consumed
+
+ $encoded = '';
+ // Copy all basic code points to output
+ for ($i = 0; $i < $deco_len; ++$i) {
+ $test = $decoded[$i];
+ // Will match [-0-9a-zA-Z]
+ if ((0x2F < $test && $test < 0x40) || (0x40 < $test && $test < 0x5B)
+ || (0x60 < $test && $test <= 0x7B) || (0x2D == $test)) {
+ $encoded .= chr($decoded[$i]);
+ $codecount++;
+ }
+ }
+ if ($codecount == $deco_len) return $encoded; // All codepoints were basic ones
+
+ // Start with the prefix; copy it to output
+ $encoded = $this->_punycode_prefix.$encoded;
+
+ // If we have basic code points in output, add an hyphen to the end
+ if ($codecount) $encoded .= '-';
+
+ // Now find and encode all non-basic code points
+ $is_first = true;
+ $cur_code = $this->_initial_n;
+ $bias = $this->_initial_bias;
+ $delta = 0;
+ while ($codecount < $deco_len) {
+ // Find the smallest code point >= the current code point and
+ // remember the last ouccrence of it in the input
+ for ($i = 0, $next_code = $this->_max_ucs; $i < $deco_len; $i++) {
+ if ($decoded[$i] >= $cur_code && $decoded[$i] <= $next_code) {
+ $next_code = $decoded[$i];
+ }
+ }
+
+ $delta += ($next_code - $cur_code) * ($codecount + 1);
+ $cur_code = $next_code;
+
+ // Scan input again and encode all characters whose code point is $cur_code
+ for ($i = 0; $i < $deco_len; $i++) {
+ if ($decoded[$i] < $cur_code) {
+ $delta++;
+ } elseif ($decoded[$i] == $cur_code) {
+ for ($q = $delta, $k = $this->_base; 1; $k += $this->_base) {
+ $t = ($k <= $bias) ? $this->_tmin :
+ (($k >= $bias + $this->_tmax) ? $this->_tmax : $k - $bias);
+ if ($q < $t) break;
+ $encoded .= $this->_encode_digit(intval($t + (($q - $t) % ($this->_base - $t)))); //v0.4.5 Changed from ceil() to intval()
+ $q = (int) (($q - $t) / ($this->_base - $t));
+ }
+ $encoded .= $this->_encode_digit($q);
+ $bias = $this->_adapt($delta, $codecount+1, $is_first);
+ $codecount++;
+ $delta = 0;
+ $is_first = false;
+ }
+ }
+ $delta++;
+ $cur_code++;
+ }
+ return $encoded;
+ }
+
+ /**
+ * Adapt the bias according to the current code point and position
+ * @access private
+ */
+ function _adapt($delta, $npoints, $is_first)
+ {
+ $delta = intval($is_first ? ($delta / $this->_damp) : ($delta / 2));
+ $delta += intval($delta / $npoints);
+ for ($k = 0; $delta > (($this->_base - $this->_tmin) * $this->_tmax) / 2; $k += $this->_base) {
+ $delta = intval($delta / ($this->_base - $this->_tmin));
+ }
+ return intval($k + ($this->_base - $this->_tmin + 1) * $delta / ($delta + $this->_skew));
+ }
+
+ /**
+ * Encoding a certain digit
+ * @access private
+ */
+ function _encode_digit($d)
+ {
+ return chr($d + 22 + 75 * ($d < 26));
+ }
+
+ /**
+ * Decode a certain digit
+ * @access private
+ */
+ function _decode_digit($cp)
+ {
+ $cp = ord($cp);
+ return ($cp - 48 < 10) ? $cp - 22 : (($cp - 65 < 26) ? $cp - 65 : (($cp - 97 < 26) ? $cp - 97 : $this->_base));
+ }
+
+ /**
+ * Internal error handling method
+ * @access private
+ */
+ function _error($error = '')
+ {
+ $this->_error = $error;
+ }
+
+ /**
+ * Do Nameprep according to RFC3491 and RFC3454
+ * @param array Unicode Characters
+ * @return string Unicode Characters, Nameprep'd
+ * @access private
+ */
+ function _nameprep($input)
+ {
+ $output = array();
+ $error = false;
+ //
+ // Mapping
+ // Walking through the input array, performing the required steps on each of
+ // the input chars and putting the result into the output array
+ // While mapping required chars we apply the cannonical ordering
+ foreach ($input as $v) {
+ // Map to nothing == skip that code point
+ if (in_array($v, $this->NP['map_nothing'])) continue;
+
+ // Try to find prohibited input
+ if (in_array($v, $this->NP['prohibit']) || in_array($v, $this->NP['general_prohibited'])) {
+ $this->_error('NAMEPREP: Prohibited input U+'.sprintf('%08X', $v));
+ return false;
+ }
+ foreach ($this->NP['prohibit_ranges'] as $range) {
+ if ($range[0] <= $v && $v <= $range[1]) {
+ $this->_error('NAMEPREP: Prohibited input U+'.sprintf('%08X', $v));
+ return false;
+ }
+ }
+ //
+ // Hangul syllable decomposition
+ if (0xAC00 <= $v && $v <= 0xD7AF) {
+ foreach ($this->_hangul_decompose($v) as $out) {
+ $output[] = (int) $out;
+ }
+ // There's a decomposition mapping for that code point
+ } elseif (isset($this->NP['replacemaps'][$v])) {
+ foreach ($this->_apply_cannonical_ordering($this->NP['replacemaps'][$v]) as $out) {
+ $output[] = (int) $out;
+ }
+ } else {
+ $output[] = (int) $v;
+ }
+ }
+ // Before applying any Combining, try to rearrange any Hangul syllables
+ $output = $this->_hangul_compose($output);
+ //
+ // Combine code points
+ //
+ $last_class = 0;
+ $last_starter = 0;
+ $out_len = count($output);
+ for ($i = 0; $i < $out_len; ++$i) {
+ $class = $this->_get_combining_class($output[$i]);
+ if ((!$last_class || $last_class > $class) && $class) {
+ // Try to match
+ $seq_len = $i - $last_starter;
+ $out = $this->_combine(array_slice($output, $last_starter, $seq_len));
+ // On match: Replace the last starter with the composed character and remove
+ // the now redundant non-starter(s)
+ if ($out) {
+ $output[$last_starter] = $out;
+ if (count($out) != $seq_len) {
+ for ($j = $i+1; $j < $out_len; ++$j) {
+ $output[$j-1] = $output[$j];
+ }
+ unset($output[$out_len]);
+ }
+ // Rewind the for loop by one, since there can be more possible compositions
+ $i--;
+ $out_len--;
+ $last_class = ($i == $last_starter) ? 0 : $this->_get_combining_class($output[$i-1]);
+ continue;
+ }
+ }
+ // The current class is 0
+ if (!$class) $last_starter = $i;
+ $last_class = $class;
+ }
+ return $output;
+ }
+
+ /**
+ * Decomposes a Hangul syllable
+ * (see http://www.unicode.org/unicode/reports/tr15/#Hangul
+ * @param integer 32bit UCS4 code point
+ * @return array Either Hangul Syllable decomposed or original 32bit value as one value array
+ * @access private
+ */
+ function _hangul_decompose($char)
+ {
+ $sindex = (int) $char - $this->_sbase;
+ if ($sindex < 0 || $sindex >= $this->_scount) {
+ return array($char);
+ }
+ $result = array();
+ $result[] = (int) $this->_lbase + $sindex / $this->_ncount;
+ $result[] = (int) $this->_vbase + ($sindex % $this->_ncount) / $this->_tcount;
+ $T = intval($this->_tbase + $sindex % $this->_tcount);
+ if ($T != $this->_tbase) $result[] = $T;
+ return $result;
+ }
+ /**
+ * Ccomposes a Hangul syllable
+ * (see http://www.unicode.org/unicode/reports/tr15/#Hangul
+ * @param array Decomposed UCS4 sequence
+ * @return array UCS4 sequence with syllables composed
+ * @access private
+ */
+ function _hangul_compose($input)
+ {
+ $inp_len = count($input);
+ if (!$inp_len) return array();
+ $result = array();
+ $last = (int) $input[0];
+ $result[] = $last; // copy first char from input to output
+
+ for ($i = 1; $i < $inp_len; ++$i) {
+ $char = (int) $input[$i];
+ $sindex = $last - $this->_sbase;
+ $lindex = $last - $this->_lbase;
+ $vindex = $char - $this->_vbase;
+ $tindex = $char - $this->_tbase;
+ // Find out, whether two current characters are LV and T
+ if (0 <= $sindex && $sindex < $this->_scount && ($sindex % $this->_tcount == 0)
+ && 0 <= $tindex && $tindex <= $this->_tcount) {
+ // create syllable of form LVT
+ $last += $tindex;
+ $result[(count($result) - 1)] = $last; // reset last
+ continue; // discard char
+ }
+ // Find out, whether two current characters form L and V
+ if (0 <= $lindex && $lindex < $this->_lcount && 0 <= $vindex && $vindex < $this->_vcount) {
+ // create syllable of form LV
+ $last = (int) $this->_sbase + ($lindex * $this->_vcount + $vindex) * $this->_tcount;
+ $result[(count($result) - 1)] = $last; // reset last
+ continue; // discard char
+ }
+ // if neither case was true, just add the character
+ $last = $char;
+ $result[] = $char;
+ }
+ return $result;
+ }
+
+ /**
+ * Returns the combining class of a certain wide char
+ * @param integer Wide char to check (32bit integer)
+ * @return integer Combining class if found, else 0
+ * @access private
+ */
+ function _get_combining_class($char)
+ {
+ return isset($this->NP['norm_combcls'][$char]) ? $this->NP['norm_combcls'][$char] : 0;
+ }
+
+ /**
+ * Apllies the cannonical ordering of a decomposed UCS4 sequence
+ * @param array Decomposed UCS4 sequence
+ * @return array Ordered USC4 sequence
+ * @access private
+ */
+ function _apply_cannonical_ordering($input)
+ {
+ $swap = true;
+ $size = count($input);
+ while ($swap) {
+ $swap = false;
+ $last = $this->_get_combining_class(intval($input[0]));
+ for ($i = 0; $i < $size-1; ++$i) {
+ $next = $this->_get_combining_class(intval($input[$i+1]));
+ if ($next != 0 && $last > $next) {
+ // Move item leftward until it fits
+ for ($j = $i + 1; $j > 0; --$j) {
+ if ($this->_get_combining_class(intval($input[$j-1])) <= $next) break;
+ $t = intval($input[$j]);
+ $input[$j] = intval($input[$j-1]);
+ $input[$j-1] = $t;
+ $swap = true;
+ }
+ // Reentering the loop looking at the old character again
+ $next = $last;
+ }
+ $last = $next;
+ }
+ }
+ return $input;
+ }
+
+ /**
+ * Do composition of a sequence of starter and non-starter
+ * @param array UCS4 Decomposed sequence
+ * @return array Ordered USC4 sequence
+ * @access private
+ */
+ function _combine($input)
+ {
+ $inp_len = count($input);
+ foreach ($this->NP['replacemaps'] as $np_src => $np_target) {
+ if ($np_target[0] != $input[0]) continue;
+ if (count($np_target) != $inp_len) continue;
+ $hit = false;
+ foreach ($input as $k2 => $v2) {
+ if ($v2 == $np_target[$k2]) {
+ $hit = true;
+ } else {
+ $hit = false;
+ break;
+ }
+ }
+ if ($hit) return $np_src;
+ }
+ return false;
+ }
+
+ /**
+ * This converts an UTF-8 encoded string to its UCS-4 representation
+ * By talking about UCS-4 "strings" we mean arrays of 32bit integers representing
+ * each of the "chars". This is due to PHP not being able to handle strings with
+ * bit depth different from 8. This apllies to the reverse method _ucs4_to_utf8(), too.
+ * The following UTF-8 encodings are supported:
+ * bytes bits representation
+ * 1 7 0xxxxxxx
+ * 2 11 110xxxxx 10xxxxxx
+ * 3 16 1110xxxx 10xxxxxx 10xxxxxx
+ * 4 21 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx
+ * 5 26 111110xx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
+ * 6 31 1111110x 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
+ * Each x represents a bit that can be used to store character data.
+ * The five and six byte sequences are part of Annex D of ISO/IEC 10646-1:2000
+ * @access private
+ */
+ function _utf8_to_ucs4($input)
+ {
+ $output = array();
+ $out_len = 0;
+ $inp_len = strlen($input);
+ $mode = 'next';
+ $test = 'none';
+ for ($k = 0; $k < $inp_len; ++$k) {
+ $v = ord($input{$k}); // Extract byte from input string
+
+ if ($v < 128) { // We found an ASCII char - put into stirng as is
+ $output[$out_len] = $v;
+ ++$out_len;
+ if ('add' == $mode) {
+ $this->_error('Conversion from UTF-8 to UCS-4 failed: malformed input at byte '.$k);
+ return false;
+ }
+ continue;
+ }
+ if ('next' == $mode) { // Try to find the next start byte; determine the width of the Unicode char
+ $start_byte = $v;
+ $mode = 'add';
+ $test = 'range';
+ if ($v >> 5 == 6) { // &110xxxxx 10xxxxx
+ $next_byte = 0; // Tells, how many times subsequent bitmasks must rotate 6bits to the left
+ $v = ($v - 192) << 6;
+ } elseif ($v >> 4 == 14) { // &1110xxxx 10xxxxxx 10xxxxxx
+ $next_byte = 1;
+ $v = ($v - 224) << 12;
+ } elseif ($v >> 3 == 30) { // &11110xxx 10xxxxxx 10xxxxxx 10xxxxxx
+ $next_byte = 2;
+ $v = ($v - 240) << 18;
+ } elseif ($v >> 2 == 62) { // &111110xx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
+ $next_byte = 3;
+ $v = ($v - 248) << 24;
+ } elseif ($v >> 1 == 126) { // &1111110x 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
+ $next_byte = 4;
+ $v = ($v - 252) << 30;
+ } else {
+ $this->_error('This might be UTF-8, but I don\'t understand it at byte '.$k);
+ return false;
+ }
+ if ('add' == $mode) {
+ $output[$out_len] = (int) $v;
+ ++$out_len;
+ continue;
+ }
+ }
+ if ('add' == $mode) {
+ if (!$this->_allow_overlong && $test == 'range') {
+ $test = 'none';
+ if (($v < 0xA0 && $start_byte == 0xE0) || ($v < 0x90 && $start_byte == 0xF0) || ($v > 0x8F && $start_byte == 0xF4)) {
+ $this->_error('Bogus UTF-8 character detected (out of legal range) at byte '.$k);
+ return false;
+ }
+ }
+ if ($v >> 6 == 2) { // Bit mask must be 10xxxxxx
+ $v = ($v - 128) << ($next_byte * 6);
+ $output[($out_len - 1)] += $v;
+ --$next_byte;
+ } else {
+ $this->_error('Conversion from UTF-8 to UCS-4 failed: malformed input at byte '.$k);
+ return false;
+ }
+ if ($next_byte < 0) {
+ $mode = 'next';
+ }
+ }
+ } // for
+ return $output;
+ }
+
+ /**
+ * Convert UCS-4 string into UTF-8 string
+ * See _utf8_to_ucs4() for details
+ * @access private
+ */
+ function _ucs4_to_utf8($input)
+ {
+ $output = '';
+ $k = 0;
+ foreach ($input as $v) {
+ ++$k;
+ // $v = ord($v);
+ if ($v < 128) { // 7bit are transferred literally
+ $output .= chr($v);
+ } elseif ($v < (1 << 11)) { // 2 bytes
+ $output .= chr(192 + ($v >> 6)) . chr(128 + ($v & 63));
+ } elseif ($v < (1 << 16)) { // 3 bytes
+ $output .= chr(224 + ($v >> 12)) . chr(128 + (($v >> 6) & 63)) . chr(128 + ($v & 63));
+ } elseif ($v < (1 << 21)) { // 4 bytes
+ $output .= chr(240 + ($v >> 18)) . chr(128 + (($v >> 12) & 63))
+ . chr(128 + (($v >> 6) & 63)) . chr(128 + ($v & 63));
+ } elseif ($v < (1 << 26)) { // 5 bytes
+ $output .= chr(248 + ($v >> 24)) . chr(128 + (($v >> 18) & 63))
+ . chr(128 + (($v >> 12) & 63)) . chr(128 + (($v >> 6) & 63))
+ . chr(128 + ($v & 63));
+ } elseif ($v < (1 << 31)) { // 6 bytes
+ $output .= chr(252 + ($v >> 30)) . chr(128 + (($v >> 24) & 63))
+ . chr(128 + (($v >> 18) & 63)) . chr(128 + (($v >> 12) & 63))
+ . chr(128 + (($v >> 6) & 63)) . chr(128 + ($v & 63));
+ } else {
+ $this->_error('Conversion from UCS-4 to UTF-8 failed: malformed input at byte '.$k);
+ return false;
+ }
+ }
+ return $output;
+ }
+
+ /**
+ * Convert UCS-4 array into UCS-4 string
+ *
+ * @access private
+ */
+ function _ucs4_to_ucs4_string($input)
+ {
+ $output = '';
+ // Take array values and split output to 4 bytes per value
+ // The bit mask is 255, which reads &11111111
+ foreach ($input as $v) {
+ $output .= chr(($v >> 24) & 255).chr(($v >> 16) & 255).chr(($v >> 8) & 255).chr($v & 255);
+ }
+ return $output;
+ }
+
+ /**
+ * Convert UCS-4 strin into UCS-4 garray
+ *
+ * @access private
+ */
+ function _ucs4_string_to_ucs4($input)
+ {
+ $output = array();
+ $inp_len = strlen($input);
+ // Input length must be dividable by 4
+ if ($inp_len % 4) {
+ $this->_error('Input UCS4 string is broken');
+ return false;
+ }
+ // Empty input - return empty output
+ if (!$inp_len) return $output;
+ for ($i = 0, $out_len = -1; $i < $inp_len; ++$i) {
+ // Increment output position every 4 input bytes
+ if (!($i % 4)) {
+ $out_len++;
+ $output[$out_len] = 0;
+ }
+ $output[$out_len] += ord($input{$i}) << (8 * (3 - ($i % 4) ) );
+ }
+ return $output;
+ }
+}
+
+/**
+* Adapter class for aligning the API of idna_convert with that of Net_IDNA
+* @author Matthias Sommerfeld <mso@phlylabs.de>
+*/
+class Net_IDNA_php4 extends idna_convert
+{
+ /**
+ * Sets a new option value. Available options and values:
+ * [encoding - Use either UTF-8, UCS4 as array or UCS4 as string as input ('utf8' for UTF-8,
+ * 'ucs4_string' and 'ucs4_array' respectively for UCS4); The output is always UTF-8]
+ * [overlong - Unicode does not allow unnecessarily long encodings of chars,
+ * to allow this, set this parameter to true, else to false;
+ * default is false.]
+ * [strict - true: strict mode, good for registration purposes - Causes errors
+ * on failures; false: loose mode, ideal for "wildlife" applications
+ * by silently ignoring errors and returning the original input instead
+ *
+ * @param mixed Parameter to set (string: single parameter; array of Parameter => Value pairs)
+ * @param string Value to use (if parameter 1 is a string)
+ * @return boolean true on success, false otherwise
+ * @access public
+ */
+ function setParams($option, $param = false)
+ {
+ return $this->IC->set_parameters($option, $param);
+ }
+}
+
+?>
diff --git a/library/simplepie/idn/npdata.ser b/vendor/simplepie/simplepie/idn/npdata.ser
index d7ce6d03f..d7ce6d03f 100644
--- a/library/simplepie/idn/npdata.ser
+++ b/vendor/simplepie/simplepie/idn/npdata.ser
diff --git a/vendor/simplepie/simplepie/library/SimplePie.php b/vendor/simplepie/simplepie/library/SimplePie.php
new file mode 100755
index 000000000..428bfc068
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie.php
@@ -0,0 +1,3303 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2017, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @version 1.5
+ * @copyright 2004-2017 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * SimplePie Name
+ */
+define('SIMPLEPIE_NAME', 'SimplePie');
+
+/**
+ * SimplePie Version
+ */
+define('SIMPLEPIE_VERSION', '1.5');
+
+/**
+ * SimplePie Build
+ * @todo Hardcode for release (there's no need to have to call SimplePie_Misc::get_build() only every load of simplepie.inc)
+ */
+define('SIMPLEPIE_BUILD', gmdate('YmdHis', SimplePie_Misc::get_build()));
+
+/**
+ * SimplePie Website URL
+ */
+define('SIMPLEPIE_URL', 'http://simplepie.org');
+
+/**
+ * SimplePie Useragent
+ * @see SimplePie::set_useragent()
+ */
+define('SIMPLEPIE_USERAGENT', SIMPLEPIE_NAME . '/' . SIMPLEPIE_VERSION . ' (Feed Parser; ' . SIMPLEPIE_URL . '; Allow like Gecko) Build/' . SIMPLEPIE_BUILD);
+
+/**
+ * SimplePie Linkback
+ */
+define('SIMPLEPIE_LINKBACK', '<a href="' . SIMPLEPIE_URL . '" title="' . SIMPLEPIE_NAME . ' ' . SIMPLEPIE_VERSION . '">' . SIMPLEPIE_NAME . '</a>');
+
+/**
+ * No Autodiscovery
+ * @see SimplePie::set_autodiscovery_level()
+ */
+define('SIMPLEPIE_LOCATOR_NONE', 0);
+
+/**
+ * Feed Link Element Autodiscovery
+ * @see SimplePie::set_autodiscovery_level()
+ */
+define('SIMPLEPIE_LOCATOR_AUTODISCOVERY', 1);
+
+/**
+ * Local Feed Extension Autodiscovery
+ * @see SimplePie::set_autodiscovery_level()
+ */
+define('SIMPLEPIE_LOCATOR_LOCAL_EXTENSION', 2);
+
+/**
+ * Local Feed Body Autodiscovery
+ * @see SimplePie::set_autodiscovery_level()
+ */
+define('SIMPLEPIE_LOCATOR_LOCAL_BODY', 4);
+
+/**
+ * Remote Feed Extension Autodiscovery
+ * @see SimplePie::set_autodiscovery_level()
+ */
+define('SIMPLEPIE_LOCATOR_REMOTE_EXTENSION', 8);
+
+/**
+ * Remote Feed Body Autodiscovery
+ * @see SimplePie::set_autodiscovery_level()
+ */
+define('SIMPLEPIE_LOCATOR_REMOTE_BODY', 16);
+
+/**
+ * All Feed Autodiscovery
+ * @see SimplePie::set_autodiscovery_level()
+ */
+define('SIMPLEPIE_LOCATOR_ALL', 31);
+
+/**
+ * No known feed type
+ */
+define('SIMPLEPIE_TYPE_NONE', 0);
+
+/**
+ * RSS 0.90
+ */
+define('SIMPLEPIE_TYPE_RSS_090', 1);
+
+/**
+ * RSS 0.91 (Netscape)
+ */
+define('SIMPLEPIE_TYPE_RSS_091_NETSCAPE', 2);
+
+/**
+ * RSS 0.91 (Userland)
+ */
+define('SIMPLEPIE_TYPE_RSS_091_USERLAND', 4);
+
+/**
+ * RSS 0.91 (both Netscape and Userland)
+ */
+define('SIMPLEPIE_TYPE_RSS_091', 6);
+
+/**
+ * RSS 0.92
+ */
+define('SIMPLEPIE_TYPE_RSS_092', 8);
+
+/**
+ * RSS 0.93
+ */
+define('SIMPLEPIE_TYPE_RSS_093', 16);
+
+/**
+ * RSS 0.94
+ */
+define('SIMPLEPIE_TYPE_RSS_094', 32);
+
+/**
+ * RSS 1.0
+ */
+define('SIMPLEPIE_TYPE_RSS_10', 64);
+
+/**
+ * RSS 2.0
+ */
+define('SIMPLEPIE_TYPE_RSS_20', 128);
+
+/**
+ * RDF-based RSS
+ */
+define('SIMPLEPIE_TYPE_RSS_RDF', 65);
+
+/**
+ * Non-RDF-based RSS (truly intended as syndication format)
+ */
+define('SIMPLEPIE_TYPE_RSS_SYNDICATION', 190);
+
+/**
+ * All RSS
+ */
+define('SIMPLEPIE_TYPE_RSS_ALL', 255);
+
+/**
+ * Atom 0.3
+ */
+define('SIMPLEPIE_TYPE_ATOM_03', 256);
+
+/**
+ * Atom 1.0
+ */
+define('SIMPLEPIE_TYPE_ATOM_10', 512);
+
+/**
+ * All Atom
+ */
+define('SIMPLEPIE_TYPE_ATOM_ALL', 768);
+
+/**
+ * All feed types
+ */
+define('SIMPLEPIE_TYPE_ALL', 1023);
+
+/**
+ * No construct
+ */
+define('SIMPLEPIE_CONSTRUCT_NONE', 0);
+
+/**
+ * Text construct
+ */
+define('SIMPLEPIE_CONSTRUCT_TEXT', 1);
+
+/**
+ * HTML construct
+ */
+define('SIMPLEPIE_CONSTRUCT_HTML', 2);
+
+/**
+ * XHTML construct
+ */
+define('SIMPLEPIE_CONSTRUCT_XHTML', 4);
+
+/**
+ * base64-encoded construct
+ */
+define('SIMPLEPIE_CONSTRUCT_BASE64', 8);
+
+/**
+ * IRI construct
+ */
+define('SIMPLEPIE_CONSTRUCT_IRI', 16);
+
+/**
+ * A construct that might be HTML
+ */
+define('SIMPLEPIE_CONSTRUCT_MAYBE_HTML', 32);
+
+/**
+ * All constructs
+ */
+define('SIMPLEPIE_CONSTRUCT_ALL', 63);
+
+/**
+ * Don't change case
+ */
+define('SIMPLEPIE_SAME_CASE', 1);
+
+/**
+ * Change to lowercase
+ */
+define('SIMPLEPIE_LOWERCASE', 2);
+
+/**
+ * Change to uppercase
+ */
+define('SIMPLEPIE_UPPERCASE', 4);
+
+/**
+ * PCRE for HTML attributes
+ */
+define('SIMPLEPIE_PCRE_HTML_ATTRIBUTE', '((?:[\x09\x0A\x0B\x0C\x0D\x20]+[^\x09\x0A\x0B\x0C\x0D\x20\x2F\x3E][^\x09\x0A\x0B\x0C\x0D\x20\x2F\x3D\x3E]*(?:[\x09\x0A\x0B\x0C\x0D\x20]*=[\x09\x0A\x0B\x0C\x0D\x20]*(?:"(?:[^"]*)"|\'(?:[^\']*)\'|(?:[^\x09\x0A\x0B\x0C\x0D\x20\x22\x27\x3E][^\x09\x0A\x0B\x0C\x0D\x20\x3E]*)?))?)*)[\x09\x0A\x0B\x0C\x0D\x20]*');
+
+/**
+ * PCRE for XML attributes
+ */
+define('SIMPLEPIE_PCRE_XML_ATTRIBUTE', '((?:\s+(?:(?:[^\s:]+:)?[^\s:]+)\s*=\s*(?:"(?:[^"]*)"|\'(?:[^\']*)\'))*)\s*');
+
+/**
+ * XML Namespace
+ */
+define('SIMPLEPIE_NAMESPACE_XML', 'http://www.w3.org/XML/1998/namespace');
+
+/**
+ * Atom 1.0 Namespace
+ */
+define('SIMPLEPIE_NAMESPACE_ATOM_10', 'http://www.w3.org/2005/Atom');
+
+/**
+ * Atom 0.3 Namespace
+ */
+define('SIMPLEPIE_NAMESPACE_ATOM_03', 'http://purl.org/atom/ns#');
+
+/**
+ * RDF Namespace
+ */
+define('SIMPLEPIE_NAMESPACE_RDF', 'http://www.w3.org/1999/02/22-rdf-syntax-ns#');
+
+/**
+ * RSS 0.90 Namespace
+ */
+define('SIMPLEPIE_NAMESPACE_RSS_090', 'http://my.netscape.com/rdf/simple/0.9/');
+
+/**
+ * RSS 1.0 Namespace
+ */
+define('SIMPLEPIE_NAMESPACE_RSS_10', 'http://purl.org/rss/1.0/');
+
+/**
+ * RSS 1.0 Content Module Namespace
+ */
+define('SIMPLEPIE_NAMESPACE_RSS_10_MODULES_CONTENT', 'http://purl.org/rss/1.0/modules/content/');
+
+/**
+ * RSS 2.0 Namespace
+ * (Stupid, I know, but I'm certain it will confuse people less with support.)
+ */
+define('SIMPLEPIE_NAMESPACE_RSS_20', '');
+
+/**
+ * DC 1.0 Namespace
+ */
+define('SIMPLEPIE_NAMESPACE_DC_10', 'http://purl.org/dc/elements/1.0/');
+
+/**
+ * DC 1.1 Namespace
+ */
+define('SIMPLEPIE_NAMESPACE_DC_11', 'http://purl.org/dc/elements/1.1/');
+
+/**
+ * W3C Basic Geo (WGS84 lat/long) Vocabulary Namespace
+ */
+define('SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO', 'http://www.w3.org/2003/01/geo/wgs84_pos#');
+
+/**
+ * GeoRSS Namespace
+ */
+define('SIMPLEPIE_NAMESPACE_GEORSS', 'http://www.georss.org/georss');
+
+/**
+ * Media RSS Namespace
+ */
+define('SIMPLEPIE_NAMESPACE_MEDIARSS', 'http://search.yahoo.com/mrss/');
+
+/**
+ * Wrong Media RSS Namespace. Caused by a long-standing typo in the spec.
+ */
+define('SIMPLEPIE_NAMESPACE_MEDIARSS_WRONG', 'http://search.yahoo.com/mrss');
+
+/**
+ * Wrong Media RSS Namespace #2. New namespace introduced in Media RSS 1.5.
+ */
+define('SIMPLEPIE_NAMESPACE_MEDIARSS_WRONG2', 'http://video.search.yahoo.com/mrss');
+
+/**
+ * Wrong Media RSS Namespace #3. A possible typo of the Media RSS 1.5 namespace.
+ */
+define('SIMPLEPIE_NAMESPACE_MEDIARSS_WRONG3', 'http://video.search.yahoo.com/mrss/');
+
+/**
+ * Wrong Media RSS Namespace #4. New spec location after the RSS Advisory Board takes it over, but not a valid namespace.
+ */
+define('SIMPLEPIE_NAMESPACE_MEDIARSS_WRONG4', 'http://www.rssboard.org/media-rss');
+
+/**
+ * Wrong Media RSS Namespace #5. A possible typo of the RSS Advisory Board URL.
+ */
+define('SIMPLEPIE_NAMESPACE_MEDIARSS_WRONG5', 'http://www.rssboard.org/media-rss/');
+
+/**
+ * iTunes RSS Namespace
+ */
+define('SIMPLEPIE_NAMESPACE_ITUNES', 'http://www.itunes.com/dtds/podcast-1.0.dtd');
+
+/**
+ * XHTML Namespace
+ */
+define('SIMPLEPIE_NAMESPACE_XHTML', 'http://www.w3.org/1999/xhtml');
+
+/**
+ * IANA Link Relations Registry
+ */
+define('SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY', 'http://www.iana.org/assignments/relation/');
+
+/**
+ * No file source
+ */
+define('SIMPLEPIE_FILE_SOURCE_NONE', 0);
+
+/**
+ * Remote file source
+ */
+define('SIMPLEPIE_FILE_SOURCE_REMOTE', 1);
+
+/**
+ * Local file source
+ */
+define('SIMPLEPIE_FILE_SOURCE_LOCAL', 2);
+
+/**
+ * fsockopen() file source
+ */
+define('SIMPLEPIE_FILE_SOURCE_FSOCKOPEN', 4);
+
+/**
+ * cURL file source
+ */
+define('SIMPLEPIE_FILE_SOURCE_CURL', 8);
+
+/**
+ * file_get_contents() file source
+ */
+define('SIMPLEPIE_FILE_SOURCE_FILE_GET_CONTENTS', 16);
+
+
+
+/**
+ * SimplePie
+ *
+ * @package SimplePie
+ * @subpackage API
+ */
+class SimplePie
+{
+ /**
+ * @var array Raw data
+ * @access private
+ */
+ public $data = array();
+
+ /**
+ * @var mixed Error string
+ * @access private
+ */
+ public $error;
+
+ /**
+ * @var object Instance of SimplePie_Sanitize (or other class)
+ * @see SimplePie::set_sanitize_class()
+ * @access private
+ */
+ public $sanitize;
+
+ /**
+ * @var string SimplePie Useragent
+ * @see SimplePie::set_useragent()
+ * @access private
+ */
+ public $useragent = SIMPLEPIE_USERAGENT;
+
+ /**
+ * @var string Feed URL
+ * @see SimplePie::set_feed_url()
+ * @access private
+ */
+ public $feed_url;
+
+ /**
+ * @var string Original feed URL, or new feed URL iff HTTP 301 Moved Permanently
+ * @see SimplePie::subscribe_url()
+ * @access private
+ */
+ public $permanent_url = null;
+
+ /**
+ * @var object Instance of SimplePie_File to use as a feed
+ * @see SimplePie::set_file()
+ * @access private
+ */
+ public $file;
+
+ /**
+ * @var string Raw feed data
+ * @see SimplePie::set_raw_data()
+ * @access private
+ */
+ public $raw_data;
+
+ /**
+ * @var int Timeout for fetching remote files
+ * @see SimplePie::set_timeout()
+ * @access private
+ */
+ public $timeout = 10;
+
+ /**
+ * @var array Custom curl options
+ * @see SimplePie::set_curl_options()
+ * @access private
+ */
+ public $curl_options = array();
+
+ /**
+ * @var bool Forces fsockopen() to be used for remote files instead
+ * of cURL, even if a new enough version is installed
+ * @see SimplePie::force_fsockopen()
+ * @access private
+ */
+ public $force_fsockopen = false;
+
+ /**
+ * @var bool Force the given data/URL to be treated as a feed no matter what
+ * it appears like
+ * @see SimplePie::force_feed()
+ * @access private
+ */
+ public $force_feed = false;
+
+ /**
+ * @var bool Enable/Disable Caching
+ * @see SimplePie::enable_cache()
+ * @access private
+ */
+ public $cache = true;
+
+ /**
+ * @var bool Force SimplePie to fallback to expired cache, if enabled,
+ * when feed is unavailable.
+ * @see SimplePie::force_cache_fallback()
+ * @access private
+ */
+ public $force_cache_fallback = false;
+
+ /**
+ * @var int Cache duration (in seconds)
+ * @see SimplePie::set_cache_duration()
+ * @access private
+ */
+ public $cache_duration = 3600;
+
+ /**
+ * @var int Auto-discovery cache duration (in seconds)
+ * @see SimplePie::set_autodiscovery_cache_duration()
+ * @access private
+ */
+ public $autodiscovery_cache_duration = 604800; // 7 Days.
+
+ /**
+ * @var string Cache location (relative to executing script)
+ * @see SimplePie::set_cache_location()
+ * @access private
+ */
+ public $cache_location = './cache';
+
+ /**
+ * @var string Function that creates the cache filename
+ * @see SimplePie::set_cache_name_function()
+ * @access private
+ */
+ public $cache_name_function = 'md5';
+
+ /**
+ * @var bool Reorder feed by date descending
+ * @see SimplePie::enable_order_by_date()
+ * @access private
+ */
+ public $order_by_date = true;
+
+ /**
+ * @var mixed Force input encoding to be set to the follow value
+ * (false, or anything type-cast to false, disables this feature)
+ * @see SimplePie::set_input_encoding()
+ * @access private
+ */
+ public $input_encoding = false;
+
+ /**
+ * @var int Feed Autodiscovery Level
+ * @see SimplePie::set_autodiscovery_level()
+ * @access private
+ */
+ public $autodiscovery = SIMPLEPIE_LOCATOR_ALL;
+
+ /**
+ * Class registry object
+ *
+ * @var SimplePie_Registry
+ */
+ public $registry;
+
+ /**
+ * @var int Maximum number of feeds to check with autodiscovery
+ * @see SimplePie::set_max_checked_feeds()
+ * @access private
+ */
+ public $max_checked_feeds = 10;
+
+ /**
+ * @var array All the feeds found during the autodiscovery process
+ * @see SimplePie::get_all_discovered_feeds()
+ * @access private
+ */
+ public $all_discovered_feeds = array();
+
+ /**
+ * @var string Web-accessible path to the handler_image.php file.
+ * @see SimplePie::set_image_handler()
+ * @access private
+ */
+ public $image_handler = '';
+
+ /**
+ * @var array Stores the URLs when multiple feeds are being initialized.
+ * @see SimplePie::set_feed_url()
+ * @access private
+ */
+ public $multifeed_url = array();
+
+ /**
+ * @var array Stores SimplePie objects when multiple feeds initialized.
+ * @access private
+ */
+ public $multifeed_objects = array();
+
+ /**
+ * @var array Stores the get_object_vars() array for use with multifeeds.
+ * @see SimplePie::set_feed_url()
+ * @access private
+ */
+ public $config_settings = null;
+
+ /**
+ * @var integer Stores the number of items to return per-feed with multifeeds.
+ * @see SimplePie::set_item_limit()
+ * @access private
+ */
+ public $item_limit = 0;
+
+ /**
+ * @var bool Stores if last-modified and/or etag headers were sent with the
+ * request when checking a feed.
+ */
+ public $check_modified = false;
+
+ /**
+ * @var array Stores the default attributes to be stripped by strip_attributes().
+ * @see SimplePie::strip_attributes()
+ * @access private
+ */
+ public $strip_attributes = array('bgsound', 'class', 'expr', 'id', 'style', 'onclick', 'onerror', 'onfinish', 'onmouseover', 'onmouseout', 'onfocus', 'onblur', 'lowsrc', 'dynsrc');
+
+ /**
+ * @var array Stores the default attributes to add to different tags by add_attributes().
+ * @see SimplePie::add_attributes()
+ * @access private
+ */
+ public $add_attributes = array('audio' => array('preload' => 'none'), 'iframe' => array('sandbox' => 'allow-scripts allow-same-origin'), 'video' => array('preload' => 'none'));
+
+ /**
+ * @var array Stores the default tags to be stripped by strip_htmltags().
+ * @see SimplePie::strip_htmltags()
+ * @access private
+ */
+ public $strip_htmltags = array('base', 'blink', 'body', 'doctype', 'embed', 'font', 'form', 'frame', 'frameset', 'html', 'iframe', 'input', 'marquee', 'meta', 'noscript', 'object', 'param', 'script', 'style');
+
+ /**
+ * @var bool Should we throw exceptions, or use the old-style error property?
+ * @access private
+ */
+ public $enable_exceptions = false;
+
+ /**
+ * The SimplePie class contains feed level data and options
+ *
+ * To use SimplePie, create the SimplePie object with no parameters. You can
+ * then set configuration options using the provided methods. After setting
+ * them, you must initialise the feed using $feed->init(). At that point the
+ * object's methods and properties will be available to you.
+ *
+ * Previously, it was possible to pass in the feed URL along with cache
+ * options directly into the constructor. This has been removed as of 1.3 as
+ * it caused a lot of confusion.
+ *
+ * @since 1.0 Preview Release
+ */
+ public function __construct()
+ {
+ if (version_compare(PHP_VERSION, '5.3', '<'))
+ {
+ trigger_error('Please upgrade to PHP 5.3 or newer.');
+ die();
+ }
+
+ // Other objects, instances created here so we can set options on them
+ $this->sanitize = new SimplePie_Sanitize();
+ $this->registry = new SimplePie_Registry();
+
+ if (func_num_args() > 0)
+ {
+ $level = defined('E_USER_DEPRECATED') ? E_USER_DEPRECATED : E_USER_WARNING;
+ trigger_error('Passing parameters to the constructor is no longer supported. Please use set_feed_url(), set_cache_location(), and set_cache_duration() directly.', $level);
+
+ $args = func_get_args();
+ switch (count($args)) {
+ case 3:
+ $this->set_cache_duration($args[2]);
+ case 2:
+ $this->set_cache_location($args[1]);
+ case 1:
+ $this->set_feed_url($args[0]);
+ $this->init();
+ }
+ }
+ }
+
+ /**
+ * Used for converting object to a string
+ */
+ public function __toString()
+ {
+ return md5(serialize($this->data));
+ }
+
+ /**
+ * Remove items that link back to this before destroying this object
+ */
+ public function __destruct()
+ {
+ if ((version_compare(PHP_VERSION, '5.3', '<') || !gc_enabled()) && !ini_get('zend.ze1_compatibility_mode'))
+ {
+ if (!empty($this->data['items']))
+ {
+ foreach ($this->data['items'] as $item)
+ {
+ $item->__destruct();
+ }
+ unset($item, $this->data['items']);
+ }
+ if (!empty($this->data['ordered_items']))
+ {
+ foreach ($this->data['ordered_items'] as $item)
+ {
+ $item->__destruct();
+ }
+ unset($item, $this->data['ordered_items']);
+ }
+ }
+ }
+
+ /**
+ * Force the given data/URL to be treated as a feed
+ *
+ * This tells SimplePie to ignore the content-type provided by the server.
+ * Be careful when using this option, as it will also disable autodiscovery.
+ *
+ * @since 1.1
+ * @param bool $enable Force the given data/URL to be treated as a feed
+ */
+ public function force_feed($enable = false)
+ {
+ $this->force_feed = (bool) $enable;
+ }
+
+ /**
+ * Set the URL of the feed you want to parse
+ *
+ * This allows you to enter the URL of the feed you want to parse, or the
+ * website you want to try to use auto-discovery on. This takes priority
+ * over any set raw data.
+ *
+ * You can set multiple feeds to mash together by passing an array instead
+ * of a string for the $url. Remember that with each additional feed comes
+ * additional processing and resources.
+ *
+ * @since 1.0 Preview Release
+ * @see set_raw_data()
+ * @param string|array $url This is the URL (or array of URLs) that you want to parse.
+ */
+ public function set_feed_url($url)
+ {
+ $this->multifeed_url = array();
+ if (is_array($url))
+ {
+ foreach ($url as $value)
+ {
+ $this->multifeed_url[] = $this->registry->call('Misc', 'fix_protocol', array($value, 1));
+ }
+ }
+ else
+ {
+ $this->feed_url = $this->registry->call('Misc', 'fix_protocol', array($url, 1));
+ $this->permanent_url = $this->feed_url;
+ }
+ }
+
+ /**
+ * Set an instance of {@see SimplePie_File} to use as a feed
+ *
+ * @param SimplePie_File &$file
+ * @return bool True on success, false on failure
+ */
+ public function set_file(&$file)
+ {
+ if ($file instanceof SimplePie_File)
+ {
+ $this->feed_url = $file->url;
+ $this->permanent_url = $this->feed_url;
+ $this->file =& $file;
+ return true;
+ }
+ return false;
+ }
+
+ /**
+ * Set the raw XML data to parse
+ *
+ * Allows you to use a string of RSS/Atom data instead of a remote feed.
+ *
+ * If you have a feed available as a string in PHP, you can tell SimplePie
+ * to parse that data string instead of a remote feed. Any set feed URL
+ * takes precedence.
+ *
+ * @since 1.0 Beta 3
+ * @param string $data RSS or Atom data as a string.
+ * @see set_feed_url()
+ */
+ public function set_raw_data($data)
+ {
+ $this->raw_data = $data;
+ }
+
+ /**
+ * Set the the default timeout for fetching remote feeds
+ *
+ * This allows you to change the maximum time the feed's server to respond
+ * and send the feed back.
+ *
+ * @since 1.0 Beta 3
+ * @param int $timeout The maximum number of seconds to spend waiting to retrieve a feed.
+ */
+ public function set_timeout($timeout = 10)
+ {
+ $this->timeout = (int) $timeout;
+ }
+
+ /**
+ * Set custom curl options
+ *
+ * This allows you to change default curl options
+ *
+ * @since 1.0 Beta 3
+ * @param array $curl_options Curl options to add to default settings
+ */
+ public function set_curl_options(array $curl_options = array())
+ {
+ $this->curl_options = $curl_options;
+ }
+
+ /**
+ * Force SimplePie to use fsockopen() instead of cURL
+ *
+ * @since 1.0 Beta 3
+ * @param bool $enable Force fsockopen() to be used
+ */
+ public function force_fsockopen($enable = false)
+ {
+ $this->force_fsockopen = (bool) $enable;
+ }
+
+ /**
+ * Enable/disable caching in SimplePie.
+ *
+ * This option allows you to disable caching all-together in SimplePie.
+ * However, disabling the cache can lead to longer load times.
+ *
+ * @since 1.0 Preview Release
+ * @param bool $enable Enable caching
+ */
+ public function enable_cache($enable = true)
+ {
+ $this->cache = (bool) $enable;
+ }
+
+ /**
+ * SimplePie to continue to fall back to expired cache, if enabled, when
+ * feed is unavailable.
+ *
+ * This tells SimplePie to ignore any file errors and fall back to cache
+ * instead. This only works if caching is enabled and cached content
+ * still exists.
+
+ * @param bool $enable Force use of cache on fail.
+ */
+ public function force_cache_fallback($enable = false)
+ {
+ $this->force_cache_fallback= (bool) $enable;
+ }
+
+ /**
+ * Set the length of time (in seconds) that the contents of a feed will be
+ * cached
+ *
+ * @param int $seconds The feed content cache duration
+ */
+ public function set_cache_duration($seconds = 3600)
+ {
+ $this->cache_duration = (int) $seconds;
+ }
+
+ /**
+ * Set the length of time (in seconds) that the autodiscovered feed URL will
+ * be cached
+ *
+ * @param int $seconds The autodiscovered feed URL cache duration.
+ */
+ public function set_autodiscovery_cache_duration($seconds = 604800)
+ {
+ $this->autodiscovery_cache_duration = (int) $seconds;
+ }
+
+ /**
+ * Set the file system location where the cached files should be stored
+ *
+ * @param string $location The file system location.
+ */
+ public function set_cache_location($location = './cache')
+ {
+ $this->cache_location = (string) $location;
+ }
+
+ /**
+ * Set whether feed items should be sorted into reverse chronological order
+ *
+ * @param bool $enable Sort as reverse chronological order.
+ */
+ public function enable_order_by_date($enable = true)
+ {
+ $this->order_by_date = (bool) $enable;
+ }
+
+ /**
+ * Set the character encoding used to parse the feed
+ *
+ * This overrides the encoding reported by the feed, however it will fall
+ * back to the normal encoding detection if the override fails
+ *
+ * @param string $encoding Character encoding
+ */
+ public function set_input_encoding($encoding = false)
+ {
+ if ($encoding)
+ {
+ $this->input_encoding = (string) $encoding;
+ }
+ else
+ {
+ $this->input_encoding = false;
+ }
+ }
+
+ /**
+ * Set how much feed autodiscovery to do
+ *
+ * @see SIMPLEPIE_LOCATOR_NONE
+ * @see SIMPLEPIE_LOCATOR_AUTODISCOVERY
+ * @see SIMPLEPIE_LOCATOR_LOCAL_EXTENSION
+ * @see SIMPLEPIE_LOCATOR_LOCAL_BODY
+ * @see SIMPLEPIE_LOCATOR_REMOTE_EXTENSION
+ * @see SIMPLEPIE_LOCATOR_REMOTE_BODY
+ * @see SIMPLEPIE_LOCATOR_ALL
+ * @param int $level Feed Autodiscovery Level (level can be a combination of the above constants, see bitwise OR operator)
+ */
+ public function set_autodiscovery_level($level = SIMPLEPIE_LOCATOR_ALL)
+ {
+ $this->autodiscovery = (int) $level;
+ }
+
+ /**
+ * Get the class registry
+ *
+ * Use this to override SimplePie's default classes
+ * @see SimplePie_Registry
+ * @return SimplePie_Registry
+ */
+ public function &get_registry()
+ {
+ return $this->registry;
+ }
+
+ /**#@+
+ * Useful when you are overloading or extending SimplePie's default classes.
+ *
+ * @deprecated Use {@see get_registry()} instead
+ * @link http://php.net/manual/en/language.oop5.basic.php#language.oop5.basic.extends PHP5 extends documentation
+ * @param string $class Name of custom class
+ * @return boolean True on success, false otherwise
+ */
+ /**
+ * Set which class SimplePie uses for caching
+ */
+ public function set_cache_class($class = 'SimplePie_Cache')
+ {
+ return $this->registry->register('Cache', $class, true);
+ }
+
+ /**
+ * Set which class SimplePie uses for auto-discovery
+ */
+ public function set_locator_class($class = 'SimplePie_Locator')
+ {
+ return $this->registry->register('Locator', $class, true);
+ }
+
+ /**
+ * Set which class SimplePie uses for XML parsing
+ */
+ public function set_parser_class($class = 'SimplePie_Parser')
+ {
+ return $this->registry->register('Parser', $class, true);
+ }
+
+ /**
+ * Set which class SimplePie uses for remote file fetching
+ */
+ public function set_file_class($class = 'SimplePie_File')
+ {
+ return $this->registry->register('File', $class, true);
+ }
+
+ /**
+ * Set which class SimplePie uses for data sanitization
+ */
+ public function set_sanitize_class($class = 'SimplePie_Sanitize')
+ {
+ return $this->registry->register('Sanitize', $class, true);
+ }
+
+ /**
+ * Set which class SimplePie uses for handling feed items
+ */
+ public function set_item_class($class = 'SimplePie_Item')
+ {
+ return $this->registry->register('Item', $class, true);
+ }
+
+ /**
+ * Set which class SimplePie uses for handling author data
+ */
+ public function set_author_class($class = 'SimplePie_Author')
+ {
+ return $this->registry->register('Author', $class, true);
+ }
+
+ /**
+ * Set which class SimplePie uses for handling category data
+ */
+ public function set_category_class($class = 'SimplePie_Category')
+ {
+ return $this->registry->register('Category', $class, true);
+ }
+
+ /**
+ * Set which class SimplePie uses for feed enclosures
+ */
+ public function set_enclosure_class($class = 'SimplePie_Enclosure')
+ {
+ return $this->registry->register('Enclosure', $class, true);
+ }
+
+ /**
+ * Set which class SimplePie uses for `<media:text>` captions
+ */
+ public function set_caption_class($class = 'SimplePie_Caption')
+ {
+ return $this->registry->register('Caption', $class, true);
+ }
+
+ /**
+ * Set which class SimplePie uses for `<media:copyright>`
+ */
+ public function set_copyright_class($class = 'SimplePie_Copyright')
+ {
+ return $this->registry->register('Copyright', $class, true);
+ }
+
+ /**
+ * Set which class SimplePie uses for `<media:credit>`
+ */
+ public function set_credit_class($class = 'SimplePie_Credit')
+ {
+ return $this->registry->register('Credit', $class, true);
+ }
+
+ /**
+ * Set which class SimplePie uses for `<media:rating>`
+ */
+ public function set_rating_class($class = 'SimplePie_Rating')
+ {
+ return $this->registry->register('Rating', $class, true);
+ }
+
+ /**
+ * Set which class SimplePie uses for `<media:restriction>`
+ */
+ public function set_restriction_class($class = 'SimplePie_Restriction')
+ {
+ return $this->registry->register('Restriction', $class, true);
+ }
+
+ /**
+ * Set which class SimplePie uses for content-type sniffing
+ */
+ public function set_content_type_sniffer_class($class = 'SimplePie_Content_Type_Sniffer')
+ {
+ return $this->registry->register('Content_Type_Sniffer', $class, true);
+ }
+
+ /**
+ * Set which class SimplePie uses item sources
+ */
+ public function set_source_class($class = 'SimplePie_Source')
+ {
+ return $this->registry->register('Source', $class, true);
+ }
+ /**#@-*/
+
+ /**
+ * Set the user agent string
+ *
+ * @param string $ua New user agent string.
+ */
+ public function set_useragent($ua = SIMPLEPIE_USERAGENT)
+ {
+ $this->useragent = (string) $ua;
+ }
+
+ /**
+ * Set callback function to create cache filename with
+ *
+ * @param mixed $function Callback function
+ */
+ public function set_cache_name_function($function = 'md5')
+ {
+ if (is_callable($function))
+ {
+ $this->cache_name_function = $function;
+ }
+ }
+
+ /**
+ * Set options to make SP as fast as possible
+ *
+ * Forgoes a substantial amount of data sanitization in favor of speed. This
+ * turns SimplePie into a dumb parser of feeds.
+ *
+ * @param bool $set Whether to set them or not
+ */
+ public function set_stupidly_fast($set = false)
+ {
+ if ($set)
+ {
+ $this->enable_order_by_date(false);
+ $this->remove_div(false);
+ $this->strip_comments(false);
+ $this->strip_htmltags(false);
+ $this->strip_attributes(false);
+ $this->add_attributes(false);
+ $this->set_image_handler(false);
+ }
+ }
+
+ /**
+ * Set maximum number of feeds to check with autodiscovery
+ *
+ * @param int $max Maximum number of feeds to check
+ */
+ public function set_max_checked_feeds($max = 10)
+ {
+ $this->max_checked_feeds = (int) $max;
+ }
+
+ public function remove_div($enable = true)
+ {
+ $this->sanitize->remove_div($enable);
+ }
+
+ public function strip_htmltags($tags = '', $encode = null)
+ {
+ if ($tags === '')
+ {
+ $tags = $this->strip_htmltags;
+ }
+ $this->sanitize->strip_htmltags($tags);
+ if ($encode !== null)
+ {
+ $this->sanitize->encode_instead_of_strip($tags);
+ }
+ }
+
+ public function encode_instead_of_strip($enable = true)
+ {
+ $this->sanitize->encode_instead_of_strip($enable);
+ }
+
+ public function strip_attributes($attribs = '')
+ {
+ if ($attribs === '')
+ {
+ $attribs = $this->strip_attributes;
+ }
+ $this->sanitize->strip_attributes($attribs);
+ }
+
+ public function add_attributes($attribs = '')
+ {
+ if ($attribs === '')
+ {
+ $attribs = $this->add_attributes;
+ }
+ $this->sanitize->add_attributes($attribs);
+ }
+
+ /**
+ * Set the output encoding
+ *
+ * Allows you to override SimplePie's output to match that of your webpage.
+ * This is useful for times when your webpages are not being served as
+ * UTF-8. This setting will be obeyed by {@see handle_content_type()}, and
+ * is similar to {@see set_input_encoding()}.
+ *
+ * It should be noted, however, that not all character encodings can support
+ * all characters. If your page is being served as ISO-8859-1 and you try
+ * to display a Japanese feed, you'll likely see garbled characters.
+ * Because of this, it is highly recommended to ensure that your webpages
+ * are served as UTF-8.
+ *
+ * The number of supported character encodings depends on whether your web
+ * host supports {@link http://php.net/mbstring mbstring},
+ * {@link http://php.net/iconv iconv}, or both. See
+ * {@link http://simplepie.org/wiki/faq/Supported_Character_Encodings} for
+ * more information.
+ *
+ * @param string $encoding
+ */
+ public function set_output_encoding($encoding = 'UTF-8')
+ {
+ $this->sanitize->set_output_encoding($encoding);
+ }
+
+ public function strip_comments($strip = false)
+ {
+ $this->sanitize->strip_comments($strip);
+ }
+
+ /**
+ * Set element/attribute key/value pairs of HTML attributes
+ * containing URLs that need to be resolved relative to the feed
+ *
+ * Defaults to |a|@href, |area|@href, |blockquote|@cite, |del|@cite,
+ * |form|@action, |img|@longdesc, |img|@src, |input|@src, |ins|@cite,
+ * |q|@cite
+ *
+ * @since 1.0
+ * @param array|null $element_attribute Element/attribute key/value pairs, null for default
+ */
+ public function set_url_replacements($element_attribute = null)
+ {
+ $this->sanitize->set_url_replacements($element_attribute);
+ }
+
+ /**
+ * Set the handler to enable the display of cached images.
+ *
+ * @param str $page Web-accessible path to the handler_image.php file.
+ * @param str $qs The query string that the value should be passed to.
+ */
+ public function set_image_handler($page = false, $qs = 'i')
+ {
+ if ($page !== false)
+ {
+ $this->sanitize->set_image_handler($page . '?' . $qs . '=');
+ }
+ else
+ {
+ $this->image_handler = '';
+ }
+ }
+
+ /**
+ * Set the limit for items returned per-feed with multifeeds
+ *
+ * @param integer $limit The maximum number of items to return.
+ */
+ public function set_item_limit($limit = 0)
+ {
+ $this->item_limit = (int) $limit;
+ }
+
+ /**
+ * Enable throwing exceptions
+ *
+ * @param boolean $enable Should we throw exceptions, or use the old-style error property?
+ */
+ public function enable_exceptions($enable = true)
+ {
+ $this->enable_exceptions = $enable;
+ }
+
+ /**
+ * Initialize the feed object
+ *
+ * This is what makes everything happen. Period. This is where all of the
+ * configuration options get processed, feeds are fetched, cached, and
+ * parsed, and all of that other good stuff.
+ *
+ * @return boolean True if successful, false otherwise
+ */
+ public function init()
+ {
+ // Check absolute bare minimum requirements.
+ if (!extension_loaded('xml') || !extension_loaded('pcre'))
+ {
+ $this->error = 'XML or PCRE extensions not loaded!';
+ return false;
+ }
+ // Then check the xml extension is sane (i.e., libxml 2.7.x issue on PHP < 5.2.9 and libxml 2.7.0 to 2.7.2 on any version) if we don't have xmlreader.
+ elseif (!extension_loaded('xmlreader'))
+ {
+ static $xml_is_sane = null;
+ if ($xml_is_sane === null)
+ {
+ $parser_check = xml_parser_create();
+ xml_parse_into_struct($parser_check, '<foo>&amp;</foo>', $values);
+ xml_parser_free($parser_check);
+ $xml_is_sane = isset($values[0]['value']);
+ }
+ if (!$xml_is_sane)
+ {
+ return false;
+ }
+ }
+
+ if (method_exists($this->sanitize, 'set_registry'))
+ {
+ $this->sanitize->set_registry($this->registry);
+ }
+
+ // Pass whatever was set with config options over to the sanitizer.
+ // Pass the classes in for legacy support; new classes should use the registry instead
+ $this->sanitize->pass_cache_data($this->cache, $this->cache_location, $this->cache_name_function, $this->registry->get_class('Cache'));
+ $this->sanitize->pass_file_data($this->registry->get_class('File'), $this->timeout, $this->useragent, $this->force_fsockopen, $this->curl_options);
+
+ if (!empty($this->multifeed_url))
+ {
+ $i = 0;
+ $success = 0;
+ $this->multifeed_objects = array();
+ $this->error = array();
+ foreach ($this->multifeed_url as $url)
+ {
+ $this->multifeed_objects[$i] = clone $this;
+ $this->multifeed_objects[$i]->set_feed_url($url);
+ $single_success = $this->multifeed_objects[$i]->init();
+ $success |= $single_success;
+ if (!$single_success)
+ {
+ $this->error[$i] = $this->multifeed_objects[$i]->error();
+ }
+ $i++;
+ }
+ return (bool) $success;
+ }
+ elseif ($this->feed_url === null && $this->raw_data === null)
+ {
+ return false;
+ }
+
+ $this->error = null;
+ $this->data = array();
+ $this->check_modified = false;
+ $this->multifeed_objects = array();
+ $cache = false;
+
+ if ($this->feed_url !== null)
+ {
+ $parsed_feed_url = $this->registry->call('Misc', 'parse_url', array($this->feed_url));
+
+ // Decide whether to enable caching
+ if ($this->cache && $parsed_feed_url['scheme'] !== '')
+ {
+ $cache = $this->registry->call('Cache', 'get_handler', array($this->cache_location, call_user_func($this->cache_name_function, $this->feed_url), 'spc'));
+ }
+
+ // Fetch the data via SimplePie_File into $this->raw_data
+ if (($fetched = $this->fetch_data($cache)) === true)
+ {
+ return true;
+ }
+ elseif ($fetched === false) {
+ return false;
+ }
+
+ list($headers, $sniffed) = $fetched;
+ }
+
+ // Empty response check
+ if(empty($this->raw_data)){
+ $this->error = "A feed could not be found at `$this->feed_url`. Empty body.";
+ $this->registry->call('Misc', 'error', array($this->error, E_USER_NOTICE, __FILE__, __LINE__));
+ return false;
+ }
+
+ // Set up array of possible encodings
+ $encodings = array();
+
+ // First check to see if input has been overridden.
+ if ($this->input_encoding !== false)
+ {
+ $encodings[] = strtoupper($this->input_encoding);
+ }
+
+ $application_types = array('application/xml', 'application/xml-dtd', 'application/xml-external-parsed-entity');
+ $text_types = array('text/xml', 'text/xml-external-parsed-entity');
+
+ // RFC 3023 (only applies to sniffed content)
+ if (isset($sniffed))
+ {
+ if (in_array($sniffed, $application_types) || substr($sniffed, 0, 12) === 'application/' && substr($sniffed, -4) === '+xml')
+ {
+ if (isset($headers['content-type']) && preg_match('/;\x20?charset=([^;]*)/i', $headers['content-type'], $charset))
+ {
+ $encodings[] = strtoupper($charset[1]);
+ }
+ $encodings = array_merge($encodings, $this->registry->call('Misc', 'xml_encoding', array($this->raw_data, &$this->registry)));
+ $encodings[] = 'UTF-8';
+ }
+ elseif (in_array($sniffed, $text_types) || substr($sniffed, 0, 5) === 'text/' && substr($sniffed, -4) === '+xml')
+ {
+ if (isset($headers['content-type']) && preg_match('/;\x20?charset=([^;]*)/i', $headers['content-type'], $charset))
+ {
+ $encodings[] = strtoupper($charset[1]);
+ }
+ $encodings[] = 'US-ASCII';
+ }
+ // Text MIME-type default
+ elseif (substr($sniffed, 0, 5) === 'text/')
+ {
+ $encodings[] = 'UTF-8';
+ }
+ }
+
+ // Fallback to XML 1.0 Appendix F.1/UTF-8/ISO-8859-1
+ $encodings = array_merge($encodings, $this->registry->call('Misc', 'xml_encoding', array($this->raw_data, &$this->registry)));
+ $encodings[] = 'UTF-8';
+ $encodings[] = 'ISO-8859-1';
+
+ // There's no point in trying an encoding twice
+ $encodings = array_unique($encodings);
+
+ // Loop through each possible encoding, till we return something, or run out of possibilities
+ foreach ($encodings as $encoding)
+ {
+ // Change the encoding to UTF-8 (as we always use UTF-8 internally)
+ if ($utf8_data = $this->registry->call('Misc', 'change_encoding', array($this->raw_data, $encoding, 'UTF-8')))
+ {
+ // Create new parser
+ $parser = $this->registry->create('Parser');
+
+ // If it's parsed fine
+ if ($parser->parse($utf8_data, 'UTF-8', $this->permanent_url))
+ {
+ $this->data = $parser->get_data();
+ if (!($this->get_type() & ~SIMPLEPIE_TYPE_NONE))
+ {
+ $this->error = "A feed could not be found at `$this->feed_url`. This does not appear to be a valid RSS or Atom feed.";
+ $this->registry->call('Misc', 'error', array($this->error, E_USER_NOTICE, __FILE__, __LINE__));
+ return false;
+ }
+
+ if (isset($headers))
+ {
+ $this->data['headers'] = $headers;
+ }
+ $this->data['build'] = SIMPLEPIE_BUILD;
+
+ // Cache the file if caching is enabled
+ if ($cache && !$cache->save($this))
+ {
+ trigger_error("$this->cache_location is not writeable. Make sure you've set the correct relative or absolute path, and that the location is server-writable.", E_USER_WARNING);
+ }
+ return true;
+ }
+ }
+ }
+
+ if (isset($parser))
+ {
+ // We have an error, just set SimplePie_Misc::error to it and quit
+ $this->error = $this->feed_url;
+ $this->error .= sprintf(' is invalid XML, likely due to invalid characters. XML error: %s at line %d, column %d', $parser->get_error_string(), $parser->get_current_line(), $parser->get_current_column());
+ }
+ else
+ {
+ $this->error = 'The data could not be converted to UTF-8.';
+ if (!extension_loaded('mbstring') && !extension_loaded('iconv') && !class_exists('\UConverter')) {
+ $this->error .= ' You MUST have either the iconv, mbstring or intl (PHP 5.5+) extension installed and enabled.';
+ } else {
+ $missingExtensions = array();
+ if (!extension_loaded('iconv')) {
+ $missingExtensions[] = 'iconv';
+ }
+ if (!extension_loaded('mbstring')) {
+ $missingExtensions[] = 'mbstring';
+ }
+ if (!class_exists('\UConverter')) {
+ $missingExtensions[] = 'intl (PHP 5.5+)';
+ }
+ $this->error .= ' Try installing/enabling the ' . implode(' or ', $missingExtensions) . ' extension.';
+ }
+ }
+
+ $this->registry->call('Misc', 'error', array($this->error, E_USER_NOTICE, __FILE__, __LINE__));
+
+ return false;
+ }
+
+ /**
+ * Fetch the data via SimplePie_File
+ *
+ * If the data is already cached, attempt to fetch it from there instead
+ * @param SimplePie_Cache|false $cache Cache handler, or false to not load from the cache
+ * @return array|true Returns true if the data was loaded from the cache, or an array of HTTP headers and sniffed type
+ */
+ protected function fetch_data(&$cache)
+ {
+ // If it's enabled, use the cache
+ if ($cache)
+ {
+ // Load the Cache
+ $this->data = $cache->load();
+ if (!empty($this->data))
+ {
+ // If the cache is for an outdated build of SimplePie
+ if (!isset($this->data['build']) || $this->data['build'] !== SIMPLEPIE_BUILD)
+ {
+ $cache->unlink();
+ $this->data = array();
+ }
+ // If we've hit a collision just rerun it with caching disabled
+ elseif (isset($this->data['url']) && $this->data['url'] !== $this->feed_url)
+ {
+ $cache = false;
+ $this->data = array();
+ }
+ // If we've got a non feed_url stored (if the page isn't actually a feed, or is a redirect) use that URL.
+ elseif (isset($this->data['feed_url']))
+ {
+ // If the autodiscovery cache is still valid use it.
+ if ($cache->mtime() + $this->autodiscovery_cache_duration > time())
+ {
+ // Do not need to do feed autodiscovery yet.
+ if ($this->data['feed_url'] !== $this->data['url'])
+ {
+ $this->set_feed_url($this->data['feed_url']);
+ return $this->init();
+ }
+
+ $cache->unlink();
+ $this->data = array();
+ }
+ }
+ // Check if the cache has been updated
+ elseif ($cache->mtime() + $this->cache_duration < time())
+ {
+ // Want to know if we tried to send last-modified and/or etag headers
+ // when requesting this file. (Note that it's up to the file to
+ // support this, but we don't always send the headers either.)
+ $this->check_modified = true;
+ if (isset($this->data['headers']['last-modified']) || isset($this->data['headers']['etag']))
+ {
+ $headers = array(
+ 'Accept' => 'application/atom+xml, application/rss+xml, application/rdf+xml;q=0.9, application/xml;q=0.8, text/xml;q=0.8, text/html;q=0.7, unknown/unknown;q=0.1, application/unknown;q=0.1, */*;q=0.1',
+ );
+ if (isset($this->data['headers']['last-modified']))
+ {
+ $headers['if-modified-since'] = $this->data['headers']['last-modified'];
+ }
+ if (isset($this->data['headers']['etag']))
+ {
+ $headers['if-none-match'] = $this->data['headers']['etag'];
+ }
+
+ $file = $this->registry->create('File', array($this->feed_url, $this->timeout/10, 5, $headers, $this->useragent, $this->force_fsockopen, $this->curl_options));
+
+ if ($file->success)
+ {
+ if ($file->status_code === 304)
+ {
+ // Set raw_data to false here too, to signify that the cache
+ // is still valid.
+ $this->raw_data = false;
+ $cache->touch();
+ return true;
+ }
+ }
+ else
+ {
+ $this->check_modified = false;
+ if($this->force_cache_fallback)
+ {
+ $cache->touch();
+ return true;
+ }
+
+ unset($file);
+ }
+ }
+ }
+ // If the cache is still valid, just return true
+ else
+ {
+ $this->raw_data = false;
+ return true;
+ }
+ }
+ // If the cache is empty, delete it
+ else
+ {
+ $cache->unlink();
+ $this->data = array();
+ }
+ }
+ // If we don't already have the file (it'll only exist if we've opened it to check if the cache has been modified), open it.
+ if (!isset($file))
+ {
+ if ($this->file instanceof SimplePie_File && $this->file->url === $this->feed_url)
+ {
+ $file =& $this->file;
+ }
+ else
+ {
+ $headers = array(
+ 'Accept' => 'application/atom+xml, application/rss+xml, application/rdf+xml;q=0.9, application/xml;q=0.8, text/xml;q=0.8, text/html;q=0.7, unknown/unknown;q=0.1, application/unknown;q=0.1, */*;q=0.1',
+ );
+ $file = $this->registry->create('File', array($this->feed_url, $this->timeout, 5, $headers, $this->useragent, $this->force_fsockopen, $this->curl_options));
+ }
+ }
+ // If the file connection has an error, set SimplePie::error to that and quit
+ if (!$file->success && !($file->method & SIMPLEPIE_FILE_SOURCE_REMOTE === 0 || ($file->status_code === 200 || $file->status_code > 206 && $file->status_code < 300)))
+ {
+ $this->error = $file->error;
+ return !empty($this->data);
+ }
+
+ if (!$this->force_feed)
+ {
+ // Check if the supplied URL is a feed, if it isn't, look for it.
+ $locate = $this->registry->create('Locator', array(&$file, $this->timeout, $this->useragent, $this->max_checked_feeds));
+
+ if (!$locate->is_feed($file))
+ {
+ $copyStatusCode = $file->status_code;
+ $copyContentType = $file->headers['content-type'];
+ try
+ {
+ $microformats = false;
+ if (function_exists('Mf2\parse')) {
+ // Check for both h-feed and h-entry, as both a feed with no entries
+ // and a list of entries without an h-feed wrapper are both valid.
+ $position = 0;
+ while ($position = strpos($file->body, 'h-feed', $position))
+ {
+ $start = $position < 200 ? 0 : $position - 200;
+ $check = substr($file->body, $start, 400);
+ if ($microformats = preg_match('/class="[^"]*h-feed/', $check))
+ {
+ break;
+ }
+ $position += 7;
+ }
+ $position = 0;
+ while ($position = strpos($file->body, 'h-entry', $position))
+ {
+ $start = $position < 200 ? 0 : $position - 200;
+ $check = substr($file->body, $start, 400);
+ if ($microformats = preg_match('/class="[^"]*h-entry/', $check))
+ {
+ break;
+ }
+ $position += 7;
+ }
+ }
+ // Now also do feed discovery, but if an h-entry was found don't
+ // overwrite the current value of file.
+ $discovered = $locate->find($this->autodiscovery,
+ $this->all_discovered_feeds);
+ if ($microformats)
+ {
+ if ($hub = $locate->get_rel_link('hub'))
+ {
+ $self = $locate->get_rel_link('self');
+ $this->store_links($file, $hub, $self);
+ }
+ // Push the current file onto all_discovered feeds so the user can
+ // be shown this as one of the options.
+ if (isset($this->all_discovered_feeds)) {
+ $this->all_discovered_feeds[] = $file;
+ }
+ }
+ else
+ {
+ if ($discovered)
+ {
+ $file = $discovered;
+ }
+ else
+ {
+ // We need to unset this so that if SimplePie::set_file() has
+ // been called that object is untouched
+ unset($file);
+ $this->error = "A feed could not be found at `$this->feed_url`; the status code is `$copyStatusCode` and content-type is `$copyContentType`";
+ $this->registry->call('Misc', 'error', array($this->error, E_USER_NOTICE, __FILE__, __LINE__));
+ return false;
+ }
+ }
+ }
+ catch (SimplePie_Exception $e)
+ {
+ // We need to unset this so that if SimplePie::set_file() has been called that object is untouched
+ unset($file);
+ // This is usually because DOMDocument doesn't exist
+ $this->error = $e->getMessage();
+ $this->registry->call('Misc', 'error', array($this->error, E_USER_NOTICE, $e->getFile(), $e->getLine()));
+ return false;
+ }
+ if ($cache)
+ {
+ $this->data = array('url' => $this->feed_url, 'feed_url' => $file->url, 'build' => SIMPLEPIE_BUILD);
+ if (!$cache->save($this))
+ {
+ trigger_error("$this->cache_location is not writeable. Make sure you've set the correct relative or absolute path, and that the location is server-writable.", E_USER_WARNING);
+ }
+ $cache = $this->registry->call('Cache', 'get_handler', array($this->cache_location, call_user_func($this->cache_name_function, $file->url), 'spc'));
+ }
+ $this->feed_url = $file->url;
+ }
+ $locate = null;
+ }
+
+ $this->raw_data = $file->body;
+ $this->permanent_url = $file->permanent_url;
+ $headers = $file->headers;
+ $sniffer = $this->registry->create('Content_Type_Sniffer', array(&$file));
+ $sniffed = $sniffer->get_type();
+
+ return array($headers, $sniffed);
+ }
+
+ /**
+ * Get the error message for the occured error
+ *
+ * @return string|array Error message, or array of messages for multifeeds
+ */
+ public function error()
+ {
+ return $this->error;
+ }
+
+ /**
+ * Get the raw XML
+ *
+ * This is the same as the old `$feed->enable_xml_dump(true)`, but returns
+ * the data instead of printing it.
+ *
+ * @return string|boolean Raw XML data, false if the cache is used
+ */
+ public function get_raw_data()
+ {
+ return $this->raw_data;
+ }
+
+ /**
+ * Get the character encoding used for output
+ *
+ * @since Preview Release
+ * @return string
+ */
+ public function get_encoding()
+ {
+ return $this->sanitize->output_encoding;
+ }
+
+ /**
+ * Send the content-type header with correct encoding
+ *
+ * This method ensures that the SimplePie-enabled page is being served with
+ * the correct {@link http://www.iana.org/assignments/media-types/ mime-type}
+ * and character encoding HTTP headers (character encoding determined by the
+ * {@see set_output_encoding} config option).
+ *
+ * This won't work properly if any content or whitespace has already been
+ * sent to the browser, because it relies on PHP's
+ * {@link http://php.net/header header()} function, and these are the
+ * circumstances under which the function works.
+ *
+ * Because it's setting these settings for the entire page (as is the nature
+ * of HTTP headers), this should only be used once per page (again, at the
+ * top).
+ *
+ * @param string $mime MIME type to serve the page as
+ */
+ public function handle_content_type($mime = 'text/html')
+ {
+ if (!headers_sent())
+ {
+ $header = "Content-type: $mime;";
+ if ($this->get_encoding())
+ {
+ $header .= ' charset=' . $this->get_encoding();
+ }
+ else
+ {
+ $header .= ' charset=UTF-8';
+ }
+ header($header);
+ }
+ }
+
+ /**
+ * Get the type of the feed
+ *
+ * This returns a SIMPLEPIE_TYPE_* constant, which can be tested against
+ * using {@link http://php.net/language.operators.bitwise bitwise operators}
+ *
+ * @since 0.8 (usage changed to using constants in 1.0)
+ * @see SIMPLEPIE_TYPE_NONE Unknown.
+ * @see SIMPLEPIE_TYPE_RSS_090 RSS 0.90.
+ * @see SIMPLEPIE_TYPE_RSS_091_NETSCAPE RSS 0.91 (Netscape).
+ * @see SIMPLEPIE_TYPE_RSS_091_USERLAND RSS 0.91 (Userland).
+ * @see SIMPLEPIE_TYPE_RSS_091 RSS 0.91.
+ * @see SIMPLEPIE_TYPE_RSS_092 RSS 0.92.
+ * @see SIMPLEPIE_TYPE_RSS_093 RSS 0.93.
+ * @see SIMPLEPIE_TYPE_RSS_094 RSS 0.94.
+ * @see SIMPLEPIE_TYPE_RSS_10 RSS 1.0.
+ * @see SIMPLEPIE_TYPE_RSS_20 RSS 2.0.x.
+ * @see SIMPLEPIE_TYPE_RSS_RDF RDF-based RSS.
+ * @see SIMPLEPIE_TYPE_RSS_SYNDICATION Non-RDF-based RSS (truly intended as syndication format).
+ * @see SIMPLEPIE_TYPE_RSS_ALL Any version of RSS.
+ * @see SIMPLEPIE_TYPE_ATOM_03 Atom 0.3.
+ * @see SIMPLEPIE_TYPE_ATOM_10 Atom 1.0.
+ * @see SIMPLEPIE_TYPE_ATOM_ALL Any version of Atom.
+ * @see SIMPLEPIE_TYPE_ALL Any known/supported feed type.
+ * @return int SIMPLEPIE_TYPE_* constant
+ */
+ public function get_type()
+ {
+ if (!isset($this->data['type']))
+ {
+ $this->data['type'] = SIMPLEPIE_TYPE_ALL;
+ if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed']))
+ {
+ $this->data['type'] &= SIMPLEPIE_TYPE_ATOM_10;
+ }
+ elseif (isset($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed']))
+ {
+ $this->data['type'] &= SIMPLEPIE_TYPE_ATOM_03;
+ }
+ elseif (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF']))
+ {
+ if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_10]['channel'])
+ || isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_10]['image'])
+ || isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_10]['item'])
+ || isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_10]['textinput']))
+ {
+ $this->data['type'] &= SIMPLEPIE_TYPE_RSS_10;
+ }
+ if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_090]['channel'])
+ || isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_090]['image'])
+ || isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_090]['item'])
+ || isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_090]['textinput']))
+ {
+ $this->data['type'] &= SIMPLEPIE_TYPE_RSS_090;
+ }
+ }
+ elseif (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss']))
+ {
+ $this->data['type'] &= SIMPLEPIE_TYPE_RSS_ALL;
+ if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['attribs']['']['version']))
+ {
+ switch (trim($this->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['attribs']['']['version']))
+ {
+ case '0.91':
+ $this->data['type'] &= SIMPLEPIE_TYPE_RSS_091;
+ if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_20]['skiphours']['hour'][0]['data']))
+ {
+ switch (trim($this->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_20]['skiphours']['hour'][0]['data']))
+ {
+ case '0':
+ $this->data['type'] &= SIMPLEPIE_TYPE_RSS_091_NETSCAPE;
+ break;
+
+ case '24':
+ $this->data['type'] &= SIMPLEPIE_TYPE_RSS_091_USERLAND;
+ break;
+ }
+ }
+ break;
+
+ case '0.92':
+ $this->data['type'] &= SIMPLEPIE_TYPE_RSS_092;
+ break;
+
+ case '0.93':
+ $this->data['type'] &= SIMPLEPIE_TYPE_RSS_093;
+ break;
+
+ case '0.94':
+ $this->data['type'] &= SIMPLEPIE_TYPE_RSS_094;
+ break;
+
+ case '2.0':
+ $this->data['type'] &= SIMPLEPIE_TYPE_RSS_20;
+ break;
+ }
+ }
+ }
+ else
+ {
+ $this->data['type'] = SIMPLEPIE_TYPE_NONE;
+ }
+ }
+ return $this->data['type'];
+ }
+
+ /**
+ * Get the URL for the feed
+ *
+ * When the 'permanent' mode is enabled, returns the original feed URL,
+ * except in the case of an `HTTP 301 Moved Permanently` status response,
+ * in which case the location of the first redirection is returned.
+ *
+ * When the 'permanent' mode is disabled (default),
+ * may or may not be different from the URL passed to {@see set_feed_url()},
+ * depending on whether auto-discovery was used.
+ *
+ * @since Preview Release (previously called `get_feed_url()` since SimplePie 0.8.)
+ * @todo Support <itunes:new-feed-url>
+ * @todo Also, |atom:link|@rel=self
+ * @param bool $permanent Permanent mode to return only the original URL or the first redirection
+ * iff it is a 301 redirection
+ * @return string|null
+ */
+ public function subscribe_url($permanent = false)
+ {
+ if ($permanent)
+ {
+ if ($this->permanent_url !== null)
+ {
+ // sanitize encodes ampersands which are required when used in a url.
+ return str_replace('&amp;', '&',
+ $this->sanitize($this->permanent_url,
+ SIMPLEPIE_CONSTRUCT_IRI));
+ }
+ }
+ else
+ {
+ if ($this->feed_url !== null)
+ {
+ return str_replace('&amp;', '&',
+ $this->sanitize($this->feed_url,
+ SIMPLEPIE_CONSTRUCT_IRI));
+ }
+ }
+ return null;
+ }
+
+ /**
+ * Get data for an feed-level element
+ *
+ * This method allows you to get access to ANY element/attribute that is a
+ * sub-element of the opening feed tag.
+ *
+ * The return value is an indexed array of elements matching the given
+ * namespace and tag name. Each element has `attribs`, `data` and `child`
+ * subkeys. For `attribs` and `child`, these contain namespace subkeys.
+ * `attribs` then has one level of associative name => value data (where
+ * `value` is a string) after the namespace. `child` has tag-indexed keys
+ * after the namespace, each member of which is an indexed array matching
+ * this same format.
+ *
+ * For example:
+ * <pre>
+ * // This is probably a bad example because we already support
+ * // <media:content> natively, but it shows you how to parse through
+ * // the nodes.
+ * $group = $item->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'group');
+ * $content = $group[0]['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['content'];
+ * $file = $content[0]['attribs']['']['url'];
+ * echo $file;
+ * </pre>
+ *
+ * @since 1.0
+ * @see http://simplepie.org/wiki/faq/supported_xml_namespaces
+ * @param string $namespace The URL of the XML namespace of the elements you're trying to access
+ * @param string $tag Tag name
+ * @return array
+ */
+ public function get_feed_tags($namespace, $tag)
+ {
+ $type = $this->get_type();
+ if ($type & SIMPLEPIE_TYPE_ATOM_10)
+ {
+ if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0]['child'][$namespace][$tag]))
+ {
+ return $this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0]['child'][$namespace][$tag];
+ }
+ }
+ if ($type & SIMPLEPIE_TYPE_ATOM_03)
+ {
+ if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0]['child'][$namespace][$tag]))
+ {
+ return $this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0]['child'][$namespace][$tag];
+ }
+ }
+ if ($type & SIMPLEPIE_TYPE_RSS_RDF)
+ {
+ if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][$namespace][$tag]))
+ {
+ return $this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['child'][$namespace][$tag];
+ }
+ }
+ if ($type & SIMPLEPIE_TYPE_RSS_SYNDICATION)
+ {
+ if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['child'][$namespace][$tag]))
+ {
+ return $this->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['child'][$namespace][$tag];
+ }
+ }
+ return null;
+ }
+
+ /**
+ * Get data for an channel-level element
+ *
+ * This method allows you to get access to ANY element/attribute in the
+ * channel/header section of the feed.
+ *
+ * See {@see SimplePie::get_feed_tags()} for a description of the return value
+ *
+ * @since 1.0
+ * @see http://simplepie.org/wiki/faq/supported_xml_namespaces
+ * @param string $namespace The URL of the XML namespace of the elements you're trying to access
+ * @param string $tag Tag name
+ * @return array
+ */
+ public function get_channel_tags($namespace, $tag)
+ {
+ $type = $this->get_type();
+ if ($type & SIMPLEPIE_TYPE_ATOM_ALL)
+ {
+ if ($return = $this->get_feed_tags($namespace, $tag))
+ {
+ return $return;
+ }
+ }
+ if ($type & SIMPLEPIE_TYPE_RSS_10)
+ {
+ if ($channel = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'channel'))
+ {
+ if (isset($channel[0]['child'][$namespace][$tag]))
+ {
+ return $channel[0]['child'][$namespace][$tag];
+ }
+ }
+ }
+ if ($type & SIMPLEPIE_TYPE_RSS_090)
+ {
+ if ($channel = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'channel'))
+ {
+ if (isset($channel[0]['child'][$namespace][$tag]))
+ {
+ return $channel[0]['child'][$namespace][$tag];
+ }
+ }
+ }
+ if ($type & SIMPLEPIE_TYPE_RSS_SYNDICATION)
+ {
+ if ($channel = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'channel'))
+ {
+ if (isset($channel[0]['child'][$namespace][$tag]))
+ {
+ return $channel[0]['child'][$namespace][$tag];
+ }
+ }
+ }
+ return null;
+ }
+
+ /**
+ * Get data for an channel-level element
+ *
+ * This method allows you to get access to ANY element/attribute in the
+ * image/logo section of the feed.
+ *
+ * See {@see SimplePie::get_feed_tags()} for a description of the return value
+ *
+ * @since 1.0
+ * @see http://simplepie.org/wiki/faq/supported_xml_namespaces
+ * @param string $namespace The URL of the XML namespace of the elements you're trying to access
+ * @param string $tag Tag name
+ * @return array
+ */
+ public function get_image_tags($namespace, $tag)
+ {
+ $type = $this->get_type();
+ if ($type & SIMPLEPIE_TYPE_RSS_10)
+ {
+ if ($image = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'image'))
+ {
+ if (isset($image[0]['child'][$namespace][$tag]))
+ {
+ return $image[0]['child'][$namespace][$tag];
+ }
+ }
+ }
+ if ($type & SIMPLEPIE_TYPE_RSS_090)
+ {
+ if ($image = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'image'))
+ {
+ if (isset($image[0]['child'][$namespace][$tag]))
+ {
+ return $image[0]['child'][$namespace][$tag];
+ }
+ }
+ }
+ if ($type & SIMPLEPIE_TYPE_RSS_SYNDICATION)
+ {
+ if ($image = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'image'))
+ {
+ if (isset($image[0]['child'][$namespace][$tag]))
+ {
+ return $image[0]['child'][$namespace][$tag];
+ }
+ }
+ }
+ return null;
+ }
+
+ /**
+ * Get the base URL value from the feed
+ *
+ * Uses `<xml:base>` if available, otherwise uses the first link in the
+ * feed, or failing that, the URL of the feed itself.
+ *
+ * @see get_link
+ * @see subscribe_url
+ *
+ * @param array $element
+ * @return string
+ */
+ public function get_base($element = array())
+ {
+ if (!($this->get_type() & SIMPLEPIE_TYPE_RSS_SYNDICATION) && !empty($element['xml_base_explicit']) && isset($element['xml_base']))
+ {
+ return $element['xml_base'];
+ }
+ elseif ($this->get_link() !== null)
+ {
+ return $this->get_link();
+ }
+ else
+ {
+ return $this->subscribe_url();
+ }
+ }
+
+ /**
+ * Sanitize feed data
+ *
+ * @access private
+ * @see SimplePie_Sanitize::sanitize()
+ * @param string $data Data to sanitize
+ * @param int $type One of the SIMPLEPIE_CONSTRUCT_* constants
+ * @param string $base Base URL to resolve URLs against
+ * @return string Sanitized data
+ */
+ public function sanitize($data, $type, $base = '')
+ {
+ try
+ {
+ return $this->sanitize->sanitize($data, $type, $base);
+ }
+ catch (SimplePie_Exception $e)
+ {
+ if (!$this->enable_exceptions)
+ {
+ $this->error = $e->getMessage();
+ $this->registry->call('Misc', 'error', array($this->error, E_USER_WARNING, $e->getFile(), $e->getLine()));
+ return '';
+ }
+
+ throw $e;
+ }
+ }
+
+ /**
+ * Get the title of the feed
+ *
+ * Uses `<atom:title>`, `<title>` or `<dc:title>`
+ *
+ * @since 1.0 (previously called `get_feed_title` since 0.8)
+ * @return string|null
+ */
+ public function get_title()
+ {
+ if ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'title'))
+ {
+ return $this->sanitize($return[0]['data'], $this->registry->call('Misc', 'atom_10_construct_type', array($return[0]['attribs'])), $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'title'))
+ {
+ return $this->sanitize($return[0]['data'], $this->registry->call('Misc', 'atom_03_construct_type', array($return[0]['attribs'])), $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'title'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'title'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'title'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_11, 'title'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_10, 'title'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get a category for the feed
+ *
+ * @since Unknown
+ * @param int $key The category that you want to return. Remember that arrays begin with 0, not 1
+ * @return SimplePie_Category|null
+ */
+ public function get_category($key = 0)
+ {
+ $categories = $this->get_categories();
+ if (isset($categories[$key]))
+ {
+ return $categories[$key];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get all categories for the feed
+ *
+ * Uses `<atom:category>`, `<category>` or `<dc:subject>`
+ *
+ * @since Unknown
+ * @return array|null List of {@see SimplePie_Category} objects
+ */
+ public function get_categories()
+ {
+ $categories = array();
+
+ foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'category') as $category)
+ {
+ $term = null;
+ $scheme = null;
+ $label = null;
+ if (isset($category['attribs']['']['term']))
+ {
+ $term = $this->sanitize($category['attribs']['']['term'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($category['attribs']['']['scheme']))
+ {
+ $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($category['attribs']['']['label']))
+ {
+ $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $categories[] = $this->registry->create('Category', array($term, $scheme, $label));
+ }
+ foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'category') as $category)
+ {
+ // This is really the label, but keep this as the term also for BC.
+ // Label will also work on retrieving because that falls back to term.
+ $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ if (isset($category['attribs']['']['domain']))
+ {
+ $scheme = $this->sanitize($category['attribs']['']['domain'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $scheme = null;
+ }
+ $categories[] = $this->registry->create('Category', array($term, $scheme, null));
+ }
+ foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_11, 'subject') as $category)
+ {
+ $categories[] = $this->registry->create('Category', array($this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null));
+ }
+ foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_10, 'subject') as $category)
+ {
+ $categories[] = $this->registry->create('Category', array($this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null));
+ }
+
+ if (!empty($categories))
+ {
+ return array_unique($categories);
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get an author for the feed
+ *
+ * @since 1.1
+ * @param int $key The author that you want to return. Remember that arrays begin with 0, not 1
+ * @return SimplePie_Author|null
+ */
+ public function get_author($key = 0)
+ {
+ $authors = $this->get_authors();
+ if (isset($authors[$key]))
+ {
+ return $authors[$key];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get all authors for the feed
+ *
+ * Uses `<atom:author>`, `<author>`, `<dc:creator>` or `<itunes:author>`
+ *
+ * @since 1.1
+ * @return array|null List of {@see SimplePie_Author} objects
+ */
+ public function get_authors()
+ {
+ $authors = array();
+ foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'author') as $author)
+ {
+ $name = null;
+ $uri = null;
+ $email = null;
+ if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data']))
+ {
+ $name = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data']))
+ {
+ $uri = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]));
+ }
+ if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data']))
+ {
+ $email = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if ($name !== null || $email !== null || $uri !== null)
+ {
+ $authors[] = $this->registry->create('Author', array($name, $uri, $email));
+ }
+ }
+ if ($author = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'author'))
+ {
+ $name = null;
+ $url = null;
+ $email = null;
+ if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data']))
+ {
+ $name = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data']))
+ {
+ $url = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]));
+ }
+ if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data']))
+ {
+ $email = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if ($name !== null || $email !== null || $url !== null)
+ {
+ $authors[] = $this->registry->create('Author', array($name, $url, $email));
+ }
+ }
+ foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_11, 'creator') as $author)
+ {
+ $authors[] = $this->registry->create('Author', array($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null));
+ }
+ foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_10, 'creator') as $author)
+ {
+ $authors[] = $this->registry->create('Author', array($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null));
+ }
+ foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'author') as $author)
+ {
+ $authors[] = $this->registry->create('Author', array($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null));
+ }
+
+ if (!empty($authors))
+ {
+ return array_unique($authors);
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get a contributor for the feed
+ *
+ * @since 1.1
+ * @param int $key The contrbutor that you want to return. Remember that arrays begin with 0, not 1
+ * @return SimplePie_Author|null
+ */
+ public function get_contributor($key = 0)
+ {
+ $contributors = $this->get_contributors();
+ if (isset($contributors[$key]))
+ {
+ return $contributors[$key];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get all contributors for the feed
+ *
+ * Uses `<atom:contributor>`
+ *
+ * @since 1.1
+ * @return array|null List of {@see SimplePie_Author} objects
+ */
+ public function get_contributors()
+ {
+ $contributors = array();
+ foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'contributor') as $contributor)
+ {
+ $name = null;
+ $uri = null;
+ $email = null;
+ if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data']))
+ {
+ $name = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data']))
+ {
+ $uri = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]));
+ }
+ if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data']))
+ {
+ $email = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if ($name !== null || $email !== null || $uri !== null)
+ {
+ $contributors[] = $this->registry->create('Author', array($name, $uri, $email));
+ }
+ }
+ foreach ((array) $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'contributor') as $contributor)
+ {
+ $name = null;
+ $url = null;
+ $email = null;
+ if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data']))
+ {
+ $name = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data']))
+ {
+ $url = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]));
+ }
+ if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data']))
+ {
+ $email = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if ($name !== null || $email !== null || $url !== null)
+ {
+ $contributors[] = $this->registry->create('Author', array($name, $url, $email));
+ }
+ }
+
+ if (!empty($contributors))
+ {
+ return array_unique($contributors);
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get a single link for the feed
+ *
+ * @since 1.0 (previously called `get_feed_link` since Preview Release, `get_feed_permalink()` since 0.8)
+ * @param int $key The link that you want to return. Remember that arrays begin with 0, not 1
+ * @param string $rel The relationship of the link to return
+ * @return string|null Link URL
+ */
+ public function get_link($key = 0, $rel = 'alternate')
+ {
+ $links = $this->get_links($rel);
+ if (isset($links[$key]))
+ {
+ return $links[$key];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the permalink for the item
+ *
+ * Returns the first link available with a relationship of "alternate".
+ * Identical to {@see get_link()} with key 0
+ *
+ * @see get_link
+ * @since 1.0 (previously called `get_feed_link` since Preview Release, `get_feed_permalink()` since 0.8)
+ * @internal Added for parity between the parent-level and the item/entry-level.
+ * @return string|null Link URL
+ */
+ public function get_permalink()
+ {
+ return $this->get_link(0);
+ }
+
+ /**
+ * Get all links for the feed
+ *
+ * Uses `<atom:link>` or `<link>`
+ *
+ * @since Beta 2
+ * @param string $rel The relationship of links to return
+ * @return array|null Links found for the feed (strings)
+ */
+ public function get_links($rel = 'alternate')
+ {
+ if (!isset($this->data['links']))
+ {
+ $this->data['links'] = array();
+ if ($links = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'link'))
+ {
+ foreach ($links as $link)
+ {
+ if (isset($link['attribs']['']['href']))
+ {
+ $link_rel = (isset($link['attribs']['']['rel'])) ? $link['attribs']['']['rel'] : 'alternate';
+ $this->data['links'][$link_rel][] = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link));
+ }
+ }
+ }
+ if ($links = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'link'))
+ {
+ foreach ($links as $link)
+ {
+ if (isset($link['attribs']['']['href']))
+ {
+ $link_rel = (isset($link['attribs']['']['rel'])) ? $link['attribs']['']['rel'] : 'alternate';
+ $this->data['links'][$link_rel][] = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link));
+
+ }
+ }
+ }
+ if ($links = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'link'))
+ {
+ $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0]));
+ }
+ if ($links = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'link'))
+ {
+ $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0]));
+ }
+ if ($links = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'link'))
+ {
+ $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0]));
+ }
+
+ $keys = array_keys($this->data['links']);
+ foreach ($keys as $key)
+ {
+ if ($this->registry->call('Misc', 'is_isegment_nz_nc', array($key)))
+ {
+ if (isset($this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key]))
+ {
+ $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key] = array_merge($this->data['links'][$key], $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key]);
+ $this->data['links'][$key] =& $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key];
+ }
+ else
+ {
+ $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key] =& $this->data['links'][$key];
+ }
+ }
+ elseif (substr($key, 0, 41) === SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY)
+ {
+ $this->data['links'][substr($key, 41)] =& $this->data['links'][$key];
+ }
+ $this->data['links'][$key] = array_unique($this->data['links'][$key]);
+ }
+ }
+
+ if (isset($this->data['links'][$rel]))
+ {
+ return $this->data['links'][$rel];
+ }
+ else if (isset($this->data['headers']['link']) &&
+ preg_match('/<([^>]+)>; rel='.preg_quote($rel).'/',
+ $this->data['headers']['link'], $match))
+ {
+ return array($match[1]);
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ public function get_all_discovered_feeds()
+ {
+ return $this->all_discovered_feeds;
+ }
+
+ /**
+ * Get the content for the item
+ *
+ * Uses `<atom:subtitle>`, `<atom:tagline>`, `<description>`,
+ * `<dc:description>`, `<itunes:summary>` or `<itunes:subtitle>`
+ *
+ * @since 1.0 (previously called `get_feed_description()` since 0.8)
+ * @return string|null
+ */
+ public function get_description()
+ {
+ if ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'subtitle'))
+ {
+ return $this->sanitize($return[0]['data'], $this->registry->call('Misc', 'atom_10_construct_type', array($return[0]['attribs'])), $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'tagline'))
+ {
+ return $this->sanitize($return[0]['data'], $this->registry->call('Misc', 'atom_03_construct_type', array($return[0]['attribs'])), $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'description'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'description'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'description'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_11, 'description'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_10, 'description'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'summary'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'subtitle'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($return[0]));
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the copyright info for the feed
+ *
+ * Uses `<atom:rights>`, `<atom:copyright>` or `<dc:rights>`
+ *
+ * @since 1.0 (previously called `get_feed_copyright()` since 0.8)
+ * @return string|null
+ */
+ public function get_copyright()
+ {
+ if ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'rights'))
+ {
+ return $this->sanitize($return[0]['data'], $this->registry->call('Misc', 'atom_10_construct_type', array($return[0]['attribs'])), $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'copyright'))
+ {
+ return $this->sanitize($return[0]['data'], $this->registry->call('Misc', 'atom_03_construct_type', array($return[0]['attribs'])), $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'copyright'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_11, 'rights'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_10, 'rights'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the language for the feed
+ *
+ * Uses `<language>`, `<dc:language>`, or @xml_lang
+ *
+ * @since 1.0 (previously called `get_feed_language()` since 0.8)
+ * @return string|null
+ */
+ public function get_language()
+ {
+ if ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'language'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_11, 'language'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_DC_10, 'language'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif (isset($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0]['xml_lang']))
+ {
+ return $this->sanitize($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0]['xml_lang'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif (isset($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0]['xml_lang']))
+ {
+ return $this->sanitize($this->data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0]['xml_lang'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif (isset($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['xml_lang']))
+ {
+ return $this->sanitize($this->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]['xml_lang'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif (isset($this->data['headers']['content-language']))
+ {
+ return $this->sanitize($this->data['headers']['content-language'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the latitude coordinates for the item
+ *
+ * Compatible with the W3C WGS84 Basic Geo and GeoRSS specifications
+ *
+ * Uses `<geo:lat>` or `<georss:point>`
+ *
+ * @since 1.0
+ * @link http://www.w3.org/2003/01/geo/ W3C WGS84 Basic Geo
+ * @link http://www.georss.org/ GeoRSS
+ * @return string|null
+ */
+ public function get_latitude()
+ {
+
+ if ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'lat'))
+ {
+ return (float) $return[0]['data'];
+ }
+ elseif (($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_GEORSS, 'point')) && preg_match('/^((?:-)?[0-9]+(?:\.[0-9]+)) ((?:-)?[0-9]+(?:\.[0-9]+))$/', trim($return[0]['data']), $match))
+ {
+ return (float) $match[1];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the longitude coordinates for the feed
+ *
+ * Compatible with the W3C WGS84 Basic Geo and GeoRSS specifications
+ *
+ * Uses `<geo:long>`, `<geo:lon>` or `<georss:point>`
+ *
+ * @since 1.0
+ * @link http://www.w3.org/2003/01/geo/ W3C WGS84 Basic Geo
+ * @link http://www.georss.org/ GeoRSS
+ * @return string|null
+ */
+ public function get_longitude()
+ {
+ if ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'long'))
+ {
+ return (float) $return[0]['data'];
+ }
+ elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'lon'))
+ {
+ return (float) $return[0]['data'];
+ }
+ elseif (($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_GEORSS, 'point')) && preg_match('/^((?:-)?[0-9]+(?:\.[0-9]+)) ((?:-)?[0-9]+(?:\.[0-9]+))$/', trim($return[0]['data']), $match))
+ {
+ return (float) $match[2];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the feed logo's title
+ *
+ * RSS 0.9.0, 1.0 and 2.0 feeds are allowed to have a "feed logo" title.
+ *
+ * Uses `<image><title>` or `<image><dc:title>`
+ *
+ * @return string|null
+ */
+ public function get_image_title()
+ {
+ if ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'title'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'title'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'title'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_DC_11, 'title'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_DC_10, 'title'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the feed logo's URL
+ *
+ * RSS 0.9.0, 2.0, Atom 1.0, and feeds with iTunes RSS tags are allowed to
+ * have a "feed logo" URL. This points directly to the image itself.
+ *
+ * Uses `<itunes:image>`, `<atom:logo>`, `<atom:icon>`,
+ * `<image><title>` or `<image><dc:title>`
+ *
+ * @return string|null
+ */
+ public function get_image_url()
+ {
+ if ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'image'))
+ {
+ return $this->sanitize($return[0]['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI);
+ }
+ elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'logo'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'icon'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'url'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'url'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'url'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0]));
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+
+ /**
+ * Get the feed logo's link
+ *
+ * RSS 0.9.0, 1.0 and 2.0 feeds are allowed to have a "feed logo" link. This
+ * points to a human-readable page that the image should link to.
+ *
+ * Uses `<itunes:image>`, `<atom:logo>`, `<atom:icon>`,
+ * `<image><title>` or `<image><dc:title>`
+ *
+ * @return string|null
+ */
+ public function get_image_link()
+ {
+ if ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'link'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'link'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'link'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0]));
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the feed logo's link
+ *
+ * RSS 2.0 feeds are allowed to have a "feed logo" width.
+ *
+ * Uses `<image><width>` or defaults to 88.0 if no width is specified and
+ * the feed is an RSS 2.0 feed.
+ *
+ * @return int|float|null
+ */
+ public function get_image_width()
+ {
+ if ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'width'))
+ {
+ return round($return[0]['data']);
+ }
+ elseif ($this->get_type() & SIMPLEPIE_TYPE_RSS_SYNDICATION && $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'url'))
+ {
+ return 88.0;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the feed logo's height
+ *
+ * RSS 2.0 feeds are allowed to have a "feed logo" height.
+ *
+ * Uses `<image><height>` or defaults to 31.0 if no height is specified and
+ * the feed is an RSS 2.0 feed.
+ *
+ * @return int|float|null
+ */
+ public function get_image_height()
+ {
+ if ($return = $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'height'))
+ {
+ return round($return[0]['data']);
+ }
+ elseif ($this->get_type() & SIMPLEPIE_TYPE_RSS_SYNDICATION && $this->get_image_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'url'))
+ {
+ return 31.0;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the number of items in the feed
+ *
+ * This is well-suited for {@link http://php.net/for for()} loops with
+ * {@see get_item()}
+ *
+ * @param int $max Maximum value to return. 0 for no limit
+ * @return int Number of items in the feed
+ */
+ public function get_item_quantity($max = 0)
+ {
+ $max = (int) $max;
+ $qty = count($this->get_items());
+ if ($max === 0)
+ {
+ return $qty;
+ }
+ else
+ {
+ return ($qty > $max) ? $max : $qty;
+ }
+ }
+
+ /**
+ * Get a single item from the feed
+ *
+ * This is better suited for {@link http://php.net/for for()} loops, whereas
+ * {@see get_items()} is better suited for
+ * {@link http://php.net/foreach foreach()} loops.
+ *
+ * @see get_item_quantity()
+ * @since Beta 2
+ * @param int $key The item that you want to return. Remember that arrays begin with 0, not 1
+ * @return SimplePie_Item|null
+ */
+ public function get_item($key = 0)
+ {
+ $items = $this->get_items();
+ if (isset($items[$key]))
+ {
+ return $items[$key];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get all items from the feed
+ *
+ * This is better suited for {@link http://php.net/for for()} loops, whereas
+ * {@see get_items()} is better suited for
+ * {@link http://php.net/foreach foreach()} loops.
+ *
+ * @see get_item_quantity
+ * @since Beta 2
+ * @param int $start Index to start at
+ * @param int $end Number of items to return. 0 for all items after `$start`
+ * @return SimplePie_Item[]|null List of {@see SimplePie_Item} objects
+ */
+ public function get_items($start = 0, $end = 0)
+ {
+ if (!isset($this->data['items']))
+ {
+ if (!empty($this->multifeed_objects))
+ {
+ $this->data['items'] = SimplePie::merge_items($this->multifeed_objects, $start, $end, $this->item_limit);
+ if (empty($this->data['items']))
+ {
+ return array();
+ }
+ return $this->data['items'];
+ }
+ $this->data['items'] = array();
+ if ($items = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'entry'))
+ {
+ $keys = array_keys($items);
+ foreach ($keys as $key)
+ {
+ $this->data['items'][] = $this->registry->create('Item', array($this, $items[$key]));
+ }
+ }
+ if ($items = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'entry'))
+ {
+ $keys = array_keys($items);
+ foreach ($keys as $key)
+ {
+ $this->data['items'][] = $this->registry->create('Item', array($this, $items[$key]));
+ }
+ }
+ if ($items = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'item'))
+ {
+ $keys = array_keys($items);
+ foreach ($keys as $key)
+ {
+ $this->data['items'][] = $this->registry->create('Item', array($this, $items[$key]));
+ }
+ }
+ if ($items = $this->get_feed_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'item'))
+ {
+ $keys = array_keys($items);
+ foreach ($keys as $key)
+ {
+ $this->data['items'][] = $this->registry->create('Item', array($this, $items[$key]));
+ }
+ }
+ if ($items = $this->get_channel_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'item'))
+ {
+ $keys = array_keys($items);
+ foreach ($keys as $key)
+ {
+ $this->data['items'][] = $this->registry->create('Item', array($this, $items[$key]));
+ }
+ }
+ }
+
+ if (empty($this->data['items']))
+ {
+ return array();
+ }
+
+ if ($this->order_by_date)
+ {
+ if (!isset($this->data['ordered_items']))
+ {
+ $this->data['ordered_items'] = $this->data['items'];
+ usort($this->data['ordered_items'], array(get_class($this), 'sort_items'));
+ }
+ $items = $this->data['ordered_items'];
+ }
+ else
+ {
+ $items = $this->data['items'];
+ }
+ // Slice the data as desired
+ if ($end === 0)
+ {
+ return array_slice($items, $start);
+ }
+ else
+ {
+ return array_slice($items, $start, $end);
+ }
+ }
+
+ /**
+ * Set the favicon handler
+ *
+ * @deprecated Use your own favicon handling instead
+ */
+ public function set_favicon_handler($page = false, $qs = 'i')
+ {
+ $level = defined('E_USER_DEPRECATED') ? E_USER_DEPRECATED : E_USER_WARNING;
+ trigger_error('Favicon handling has been removed, please use your own handling', $level);
+ return false;
+ }
+
+ /**
+ * Get the favicon for the current feed
+ *
+ * @deprecated Use your own favicon handling instead
+ */
+ public function get_favicon()
+ {
+ $level = defined('E_USER_DEPRECATED') ? E_USER_DEPRECATED : E_USER_WARNING;
+ trigger_error('Favicon handling has been removed, please use your own handling', $level);
+
+ if (($url = $this->get_link()) !== null)
+ {
+ return 'http://g.etfv.co/' . urlencode($url);
+ }
+
+ return false;
+ }
+
+ /**
+ * Magic method handler
+ *
+ * @param string $method Method name
+ * @param array $args Arguments to the method
+ * @return mixed
+ */
+ public function __call($method, $args)
+ {
+ if (strpos($method, 'subscribe_') === 0)
+ {
+ $level = defined('E_USER_DEPRECATED') ? E_USER_DEPRECATED : E_USER_WARNING;
+ trigger_error('subscribe_*() has been deprecated, implement the callback yourself', $level);
+ return '';
+ }
+ if ($method === 'enable_xml_dump')
+ {
+ $level = defined('E_USER_DEPRECATED') ? E_USER_DEPRECATED : E_USER_WARNING;
+ trigger_error('enable_xml_dump() has been deprecated, use get_raw_data() instead', $level);
+ return false;
+ }
+
+ $class = get_class($this);
+ $trace = debug_backtrace();
+ $file = $trace[0]['file'];
+ $line = $trace[0]['line'];
+ trigger_error("Call to undefined method $class::$method() in $file on line $line", E_USER_ERROR);
+ }
+
+ /**
+ * Sorting callback for items
+ *
+ * @access private
+ * @param SimplePie $a
+ * @param SimplePie $b
+ * @return boolean
+ */
+ public static function sort_items($a, $b)
+ {
+ $a_date = $a->get_date('U');
+ $b_date = $b->get_date('U');
+ if ($a_date && $b_date) {
+ return $a_date > $b_date ? -1 : 1;
+ }
+ // Sort items without dates to the top.
+ if ($a_date) {
+ return 1;
+ }
+ if ($b_date) {
+ return -1;
+ }
+ return 0;
+ }
+
+ /**
+ * Merge items from several feeds into one
+ *
+ * If you're merging multiple feeds together, they need to all have dates
+ * for the items or else SimplePie will refuse to sort them.
+ *
+ * @link http://simplepie.org/wiki/tutorial/sort_multiple_feeds_by_time_and_date#if_feeds_require_separate_per-feed_settings
+ * @param array $urls List of SimplePie feed objects to merge
+ * @param int $start Starting item
+ * @param int $end Number of items to return
+ * @param int $limit Maximum number of items per feed
+ * @return array
+ */
+ public static function merge_items($urls, $start = 0, $end = 0, $limit = 0)
+ {
+ if (is_array($urls) && sizeof($urls) > 0)
+ {
+ $items = array();
+ foreach ($urls as $arg)
+ {
+ if ($arg instanceof SimplePie)
+ {
+ $items = array_merge($items, $arg->get_items(0, $limit));
+ }
+ else
+ {
+ trigger_error('Arguments must be SimplePie objects', E_USER_WARNING);
+ }
+ }
+
+ usort($items, array(get_class($urls[0]), 'sort_items'));
+
+ if ($end === 0)
+ {
+ return array_slice($items, $start);
+ }
+ else
+ {
+ return array_slice($items, $start, $end);
+ }
+ }
+ else
+ {
+ trigger_error('Cannot merge zero SimplePie objects', E_USER_WARNING);
+ return array();
+ }
+ }
+
+ /**
+ * Store PubSubHubbub links as headers
+ *
+ * There is no way to find PuSH links in the body of a microformats feed,
+ * so they are added to the headers when found, to be used later by get_links.
+ * @param SimplePie_File $file
+ * @param string $hub
+ * @param string $self
+ */
+ private function store_links(&$file, $hub, $self) {
+ if (isset($file->headers['link']['hub']) ||
+ (isset($file->headers['link']) &&
+ preg_match('/rel=hub/', $file->headers['link'])))
+ {
+ return;
+ }
+
+ if ($hub)
+ {
+ if (isset($file->headers['link']))
+ {
+ if ($file->headers['link'] !== '')
+ {
+ $file->headers['link'] = ', ';
+ }
+ }
+ else
+ {
+ $file->headers['link'] = '';
+ }
+ $file->headers['link'] .= '<'.$hub.'>; rel=hub';
+ if ($self)
+ {
+ $file->headers['link'] .= ', <'.$self.'>; rel=self';
+ }
+ }
+ }
+}
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Author.php b/vendor/simplepie/simplepie/library/SimplePie/Author.php
new file mode 100644
index 000000000..e6768ff29
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Author.php
@@ -0,0 +1,156 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * Manages all author-related data
+ *
+ * Used by {@see SimplePie_Item::get_author()} and {@see SimplePie::get_authors()}
+ *
+ * This class can be overloaded with {@see SimplePie::set_author_class()}
+ *
+ * @package SimplePie
+ * @subpackage API
+ */
+class SimplePie_Author
+{
+ /**
+ * Author's name
+ *
+ * @var string
+ * @see get_name()
+ */
+ var $name;
+
+ /**
+ * Author's link
+ *
+ * @var string
+ * @see get_link()
+ */
+ var $link;
+
+ /**
+ * Author's email address
+ *
+ * @var string
+ * @see get_email()
+ */
+ var $email;
+
+ /**
+ * Constructor, used to input the data
+ *
+ * @param string $name
+ * @param string $link
+ * @param string $email
+ */
+ public function __construct($name = null, $link = null, $email = null)
+ {
+ $this->name = $name;
+ $this->link = $link;
+ $this->email = $email;
+ }
+
+ /**
+ * String-ified version
+ *
+ * @return string
+ */
+ public function __toString()
+ {
+ // There is no $this->data here
+ return md5(serialize($this));
+ }
+
+ /**
+ * Author's name
+ *
+ * @return string|null
+ */
+ public function get_name()
+ {
+ if ($this->name !== null)
+ {
+ return $this->name;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Author's link
+ *
+ * @return string|null
+ */
+ public function get_link()
+ {
+ if ($this->link !== null)
+ {
+ return $this->link;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Author's email address
+ *
+ * @return string|null
+ */
+ public function get_email()
+ {
+ if ($this->email !== null)
+ {
+ return $this->email;
+ }
+ else
+ {
+ return null;
+ }
+ }
+}
+
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Cache.php b/vendor/simplepie/simplepie/library/SimplePie/Cache.php
new file mode 100644
index 000000000..d98cc6511
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Cache.php
@@ -0,0 +1,134 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * Used to create cache objects
+ *
+ * This class can be overloaded with {@see SimplePie::set_cache_class()},
+ * although the preferred way is to create your own handler
+ * via {@see register()}
+ *
+ * @package SimplePie
+ * @subpackage Caching
+ */
+class SimplePie_Cache
+{
+ /**
+ * Cache handler classes
+ *
+ * These receive 3 parameters to their constructor, as documented in
+ * {@see register()}
+ * @var array
+ */
+ protected static $handlers = array(
+ 'mysql' => 'SimplePie_Cache_MySQL',
+ 'memcache' => 'SimplePie_Cache_Memcache',
+ 'memcached' => 'SimplePie_Cache_Memcached',
+ 'redis' => 'SimplePie_Cache_Redis'
+ );
+
+ /**
+ * Don't call the constructor. Please.
+ */
+ private function __construct() { }
+
+ /**
+ * Create a new SimplePie_Cache object
+ *
+ * @param string $location URL location (scheme is used to determine handler)
+ * @param string $filename Unique identifier for cache object
+ * @param string $extension 'spi' or 'spc'
+ * @return SimplePie_Cache_Base Type of object depends on scheme of `$location`
+ */
+ public static function get_handler($location, $filename, $extension)
+ {
+ $type = explode(':', $location, 2);
+ $type = $type[0];
+ if (!empty(self::$handlers[$type]))
+ {
+ $class = self::$handlers[$type];
+ return new $class($location, $filename, $extension);
+ }
+
+ return new SimplePie_Cache_File($location, $filename, $extension);
+ }
+
+ /**
+ * Create a new SimplePie_Cache object
+ *
+ * @deprecated Use {@see get_handler} instead
+ */
+ public function create($location, $filename, $extension)
+ {
+ trigger_error('Cache::create() has been replaced with Cache::get_handler(). Switch to the registry system to use this.', E_USER_DEPRECATED);
+ return self::get_handler($location, $filename, $extension);
+ }
+
+ /**
+ * Register a handler
+ *
+ * @param string $type DSN type to register for
+ * @param string $class Name of handler class. Must implement SimplePie_Cache_Base
+ */
+ public static function register($type, $class)
+ {
+ self::$handlers[$type] = $class;
+ }
+
+ /**
+ * Parse a URL into an array
+ *
+ * @param string $url
+ * @return array
+ */
+ public static function parse_URL($url)
+ {
+ $params = parse_url($url);
+ $params['extras'] = array();
+ if (isset($params['query']))
+ {
+ parse_str($params['query'], $params['extras']);
+ }
+ return $params;
+ }
+}
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Cache/Base.php b/vendor/simplepie/simplepie/library/SimplePie/Cache/Base.php
new file mode 100644
index 000000000..333fb05cf
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Cache/Base.php
@@ -0,0 +1,113 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * Base for cache objects
+ *
+ * Classes to be used with {@see SimplePie_Cache::register()} are expected
+ * to implement this interface.
+ *
+ * @package SimplePie
+ * @subpackage Caching
+ */
+interface SimplePie_Cache_Base
+{
+ /**
+ * Feed cache type
+ *
+ * @var string
+ */
+ const TYPE_FEED = 'spc';
+
+ /**
+ * Image cache type
+ *
+ * @var string
+ */
+ const TYPE_IMAGE = 'spi';
+
+ /**
+ * Create a new cache object
+ *
+ * @param string $location Location string (from SimplePie::$cache_location)
+ * @param string $name Unique ID for the cache
+ * @param string $type Either TYPE_FEED for SimplePie data, or TYPE_IMAGE for image data
+ */
+ public function __construct($location, $name, $type);
+
+ /**
+ * Save data to the cache
+ *
+ * @param array|SimplePie $data Data to store in the cache. If passed a SimplePie object, only cache the $data property
+ * @return bool Successfulness
+ */
+ public function save($data);
+
+ /**
+ * Retrieve the data saved to the cache
+ *
+ * @return array Data for SimplePie::$data
+ */
+ public function load();
+
+ /**
+ * Retrieve the last modified time for the cache
+ *
+ * @return int Timestamp
+ */
+ public function mtime();
+
+ /**
+ * Set the last modified time to the current time
+ *
+ * @return bool Success status
+ */
+ public function touch();
+
+ /**
+ * Remove the cache
+ *
+ * @return bool Success status
+ */
+ public function unlink();
+}
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Cache/DB.php b/vendor/simplepie/simplepie/library/SimplePie/Cache/DB.php
new file mode 100644
index 000000000..7e8f77532
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Cache/DB.php
@@ -0,0 +1,136 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * Base class for database-based caches
+ *
+ * @package SimplePie
+ * @subpackage Caching
+ */
+abstract class SimplePie_Cache_DB implements SimplePie_Cache_Base
+{
+ /**
+ * Helper for database conversion
+ *
+ * Converts a given {@see SimplePie} object into data to be stored
+ *
+ * @param SimplePie $data
+ * @return array First item is the serialized data for storage, second item is the unique ID for this item
+ */
+ protected static function prepare_simplepie_object_for_cache($data)
+ {
+ $items = $data->get_items();
+ $items_by_id = array();
+
+ if (!empty($items))
+ {
+ foreach ($items as $item)
+ {
+ $items_by_id[$item->get_id()] = $item;
+ }
+
+ if (count($items_by_id) !== count($items))
+ {
+ $items_by_id = array();
+ foreach ($items as $item)
+ {
+ $items_by_id[$item->get_id(true)] = $item;
+ }
+ }
+
+ if (isset($data->data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0]))
+ {
+ $channel =& $data->data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0];
+ }
+ elseif (isset($data->data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0]))
+ {
+ $channel =& $data->data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0];
+ }
+ elseif (isset($data->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]))
+ {
+ $channel =& $data->data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0];
+ }
+ elseif (isset($data->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_20]['channel'][0]))
+ {
+ $channel =& $data->data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]['child'][SIMPLEPIE_NAMESPACE_RSS_20]['channel'][0];
+ }
+ else
+ {
+ $channel = null;
+ }
+
+ if ($channel !== null)
+ {
+ if (isset($channel['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['entry']))
+ {
+ unset($channel['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['entry']);
+ }
+ if (isset($channel['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['entry']))
+ {
+ unset($channel['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['entry']);
+ }
+ if (isset($channel['child'][SIMPLEPIE_NAMESPACE_RSS_10]['item']))
+ {
+ unset($channel['child'][SIMPLEPIE_NAMESPACE_RSS_10]['item']);
+ }
+ if (isset($channel['child'][SIMPLEPIE_NAMESPACE_RSS_090]['item']))
+ {
+ unset($channel['child'][SIMPLEPIE_NAMESPACE_RSS_090]['item']);
+ }
+ if (isset($channel['child'][SIMPLEPIE_NAMESPACE_RSS_20]['item']))
+ {
+ unset($channel['child'][SIMPLEPIE_NAMESPACE_RSS_20]['item']);
+ }
+ }
+ if (isset($data->data['items']))
+ {
+ unset($data->data['items']);
+ }
+ if (isset($data->data['ordered_items']))
+ {
+ unset($data->data['ordered_items']);
+ }
+ }
+ return array(serialize($data->data), $items_by_id);
+ }
+}
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Cache/File.php b/vendor/simplepie/simplepie/library/SimplePie/Cache/File.php
new file mode 100644
index 000000000..6ba6c5f6e
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Cache/File.php
@@ -0,0 +1,164 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * Caches data to the filesystem
+ *
+ * @package SimplePie
+ * @subpackage Caching
+ */
+class SimplePie_Cache_File implements SimplePie_Cache_Base
+{
+ /**
+ * Location string
+ *
+ * @see SimplePie::$cache_location
+ * @var string
+ */
+ protected $location;
+
+ /**
+ * Filename
+ *
+ * @var string
+ */
+ protected $filename;
+
+ /**
+ * File extension
+ *
+ * @var string
+ */
+ protected $extension;
+
+ /**
+ * File path
+ *
+ * @var string
+ */
+ protected $name;
+
+ /**
+ * Create a new cache object
+ *
+ * @param string $location Location string (from SimplePie::$cache_location)
+ * @param string $name Unique ID for the cache
+ * @param string $type Either TYPE_FEED for SimplePie data, or TYPE_IMAGE for image data
+ */
+ public function __construct($location, $name, $type)
+ {
+ $this->location = $location;
+ $this->filename = $name;
+ $this->extension = $type;
+ $this->name = "$this->location/$this->filename.$this->extension";
+ }
+
+ /**
+ * Save data to the cache
+ *
+ * @param array|SimplePie $data Data to store in the cache. If passed a SimplePie object, only cache the $data property
+ * @return bool Successfulness
+ */
+ public function save($data)
+ {
+ if (file_exists($this->name) && is_writeable($this->name) || file_exists($this->location) && is_writeable($this->location))
+ {
+ if ($data instanceof SimplePie)
+ {
+ $data = $data->data;
+ }
+
+ $data = serialize($data);
+ return (bool) file_put_contents($this->name, $data);
+ }
+ return false;
+ }
+
+ /**
+ * Retrieve the data saved to the cache
+ *
+ * @return array Data for SimplePie::$data
+ */
+ public function load()
+ {
+ if (file_exists($this->name) && is_readable($this->name))
+ {
+ return unserialize(file_get_contents($this->name));
+ }
+ return false;
+ }
+
+ /**
+ * Retrieve the last modified time for the cache
+ *
+ * @return int Timestamp
+ */
+ public function mtime()
+ {
+ return @filemtime($this->name);
+ }
+
+ /**
+ * Set the last modified time to the current time
+ *
+ * @return bool Success status
+ */
+ public function touch()
+ {
+ return @touch($this->name);
+ }
+
+ /**
+ * Remove the cache
+ *
+ * @return bool Success status
+ */
+ public function unlink()
+ {
+ if (file_exists($this->name))
+ {
+ return unlink($this->name);
+ }
+ return false;
+ }
+}
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Cache/Memcache.php b/vendor/simplepie/simplepie/library/SimplePie/Cache/Memcache.php
new file mode 100644
index 000000000..5190eef93
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Cache/Memcache.php
@@ -0,0 +1,180 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * Caches data to memcache
+ *
+ * Registered for URLs with the "memcache" protocol
+ *
+ * For example, `memcache://localhost:11211/?timeout=3600&prefix=sp_` will
+ * connect to memcache on `localhost` on port 11211. All tables will be
+ * prefixed with `sp_` and data will expire after 3600 seconds
+ *
+ * @package SimplePie
+ * @subpackage Caching
+ * @uses Memcache
+ */
+class SimplePie_Cache_Memcache implements SimplePie_Cache_Base
+{
+ /**
+ * Memcache instance
+ *
+ * @var Memcache
+ */
+ protected $cache;
+
+ /**
+ * Options
+ *
+ * @var array
+ */
+ protected $options;
+
+ /**
+ * Cache name
+ *
+ * @var string
+ */
+ protected $name;
+
+ /**
+ * Create a new cache object
+ *
+ * @param string $location Location string (from SimplePie::$cache_location)
+ * @param string $name Unique ID for the cache
+ * @param string $type Either TYPE_FEED for SimplePie data, or TYPE_IMAGE for image data
+ */
+ public function __construct($location, $name, $type)
+ {
+ $this->options = array(
+ 'host' => '127.0.0.1',
+ 'port' => 11211,
+ 'extras' => array(
+ 'timeout' => 3600, // one hour
+ 'prefix' => 'simplepie_',
+ ),
+ );
+ $this->options = SimplePie_Misc::array_merge_recursive($this->options, SimplePie_Cache::parse_URL($location));
+
+ $this->name = $this->options['extras']['prefix'] . md5("$name:$type");
+
+ $this->cache = new Memcache();
+ $this->cache->addServer($this->options['host'], (int) $this->options['port']);
+ }
+
+ /**
+ * Save data to the cache
+ *
+ * @param array|SimplePie $data Data to store in the cache. If passed a SimplePie object, only cache the $data property
+ * @return bool Successfulness
+ */
+ public function save($data)
+ {
+ if ($data instanceof SimplePie)
+ {
+ $data = $data->data;
+ }
+ return $this->cache->set($this->name, serialize($data), MEMCACHE_COMPRESSED, (int) $this->options['extras']['timeout']);
+ }
+
+ /**
+ * Retrieve the data saved to the cache
+ *
+ * @return array Data for SimplePie::$data
+ */
+ public function load()
+ {
+ $data = $this->cache->get($this->name);
+
+ if ($data !== false)
+ {
+ return unserialize($data);
+ }
+ return false;
+ }
+
+ /**
+ * Retrieve the last modified time for the cache
+ *
+ * @return int Timestamp
+ */
+ public function mtime()
+ {
+ $data = $this->cache->get($this->name);
+
+ if ($data !== false)
+ {
+ // essentially ignore the mtime because Memcache expires on its own
+ return time();
+ }
+
+ return false;
+ }
+
+ /**
+ * Set the last modified time to the current time
+ *
+ * @return bool Success status
+ */
+ public function touch()
+ {
+ $data = $this->cache->get($this->name);
+
+ if ($data !== false)
+ {
+ return $this->cache->set($this->name, $data, MEMCACHE_COMPRESSED, (int) $this->options['extras']['timeout']);
+ }
+
+ return false;
+ }
+
+ /**
+ * Remove the cache
+ *
+ * @return bool Success status
+ */
+ public function unlink()
+ {
+ return $this->cache->delete($this->name, 0);
+ }
+}
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Cache/Memcached.php b/vendor/simplepie/simplepie/library/SimplePie/Cache/Memcached.php
new file mode 100755
index 000000000..1f73b3890
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Cache/Memcached.php
@@ -0,0 +1,166 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * Caches data to memcached
+ *
+ * Registered for URLs with the "memcached" protocol
+ *
+ * For example, `memcached://localhost:11211/?timeout=3600&prefix=sp_` will
+ * connect to memcached on `localhost` on port 11211. All tables will be
+ * prefixed with `sp_` and data will expire after 3600 seconds
+ *
+ * @package SimplePie
+ * @subpackage Caching
+ * @author Paul L. McNeely
+ * @uses Memcached
+ */
+class SimplePie_Cache_Memcached implements SimplePie_Cache_Base
+{
+ /**
+ * Memcached instance
+ * @var Memcached
+ */
+ protected $cache;
+
+ /**
+ * Options
+ * @var array
+ */
+ protected $options;
+
+ /**
+ * Cache name
+ * @var string
+ */
+ protected $name;
+
+ /**
+ * Create a new cache object
+ * @param string $location Location string (from SimplePie::$cache_location)
+ * @param string $name Unique ID for the cache
+ * @param string $type Either TYPE_FEED for SimplePie data, or TYPE_IMAGE for image data
+ */
+ public function __construct($location, $name, $type) {
+ $this->options = array(
+ 'host' => '127.0.0.1',
+ 'port' => 11211,
+ 'extras' => array(
+ 'timeout' => 3600, // one hour
+ 'prefix' => 'simplepie_',
+ ),
+ );
+ $this->options = SimplePie_Misc::array_merge_recursive($this->options, SimplePie_Cache::parse_URL($location));
+
+ $this->name = $this->options['extras']['prefix'] . md5("$name:$type");
+
+ $this->cache = new Memcached();
+ $this->cache->addServer($this->options['host'], (int)$this->options['port']);
+ }
+
+ /**
+ * Save data to the cache
+ * @param array|SimplePie $data Data to store in the cache. If passed a SimplePie object, only cache the $data property
+ * @return bool Successfulness
+ */
+ public function save($data) {
+ if ($data instanceof SimplePie) {
+ $data = $data->data;
+ }
+
+ return $this->setData(serialize($data));
+ }
+
+ /**
+ * Retrieve the data saved to the cache
+ * @return array Data for SimplePie::$data
+ */
+ public function load() {
+ $data = $this->cache->get($this->name);
+
+ if ($data !== false) {
+ return unserialize($data);
+ }
+ return false;
+ }
+
+ /**
+ * Retrieve the last modified time for the cache
+ * @return int Timestamp
+ */
+ public function mtime() {
+ $data = $this->cache->get($this->name . '_mtime');
+ return (int) $data;
+ }
+
+ /**
+ * Set the last modified time to the current time
+ * @return bool Success status
+ */
+ public function touch() {
+ $data = $this->cache->get($this->name);
+ return $this->setData($data);
+ }
+
+ /**
+ * Remove the cache
+ * @return bool Success status
+ */
+ public function unlink() {
+ return $this->cache->delete($this->name, 0);
+ }
+
+ /**
+ * Set the last modified time and data to Memcached
+ * @return bool Success status
+ */
+ private function setData($data) {
+
+ if ($data !== false) {
+ $this->cache->set($this->name . '_mtime', time(), (int)$this->options['extras']['timeout']);
+ return $this->cache->set($this->name, $data, (int)$this->options['extras']['timeout']);
+ }
+
+ return false;
+ }
+}
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Cache/MySQL.php b/vendor/simplepie/simplepie/library/SimplePie/Cache/MySQL.php
new file mode 100644
index 000000000..8686b6c67
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Cache/MySQL.php
@@ -0,0 +1,454 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * Caches data to a MySQL database
+ *
+ * Registered for URLs with the "mysql" protocol
+ *
+ * For example, `mysql://root:password@localhost:3306/mydb?prefix=sp_` will
+ * connect to the `mydb` database on `localhost` on port 3306, with the user
+ * `root` and the password `password`. All tables will be prefixed with `sp_`
+ *
+ * @package SimplePie
+ * @subpackage Caching
+ */
+class SimplePie_Cache_MySQL extends SimplePie_Cache_DB
+{
+ /**
+ * PDO instance
+ *
+ * @var PDO
+ */
+ protected $mysql;
+
+ /**
+ * Options
+ *
+ * @var array
+ */
+ protected $options;
+
+ /**
+ * Cache ID
+ *
+ * @var string
+ */
+ protected $id;
+
+ /**
+ * Create a new cache object
+ *
+ * @param string $location Location string (from SimplePie::$cache_location)
+ * @param string $name Unique ID for the cache
+ * @param string $type Either TYPE_FEED for SimplePie data, or TYPE_IMAGE for image data
+ */
+ public function __construct($location, $name, $type)
+ {
+ $this->options = array(
+ 'user' => null,
+ 'pass' => null,
+ 'host' => '127.0.0.1',
+ 'port' => '3306',
+ 'path' => '',
+ 'extras' => array(
+ 'prefix' => '',
+ 'cache_purge_time' => 2592000
+ ),
+ );
+
+ $this->options = SimplePie_Misc::array_merge_recursive($this->options, SimplePie_Cache::parse_URL($location));
+
+ // Path is prefixed with a "/"
+ $this->options['dbname'] = substr($this->options['path'], 1);
+
+ try
+ {
+ $this->mysql = new PDO("mysql:dbname={$this->options['dbname']};host={$this->options['host']};port={$this->options['port']}", $this->options['user'], $this->options['pass'], array(PDO::MYSQL_ATTR_INIT_COMMAND => 'SET NAMES utf8'));
+ }
+ catch (PDOException $e)
+ {
+ $this->mysql = null;
+ return;
+ }
+
+ $this->id = $name . $type;
+
+ if (!$query = $this->mysql->query('SHOW TABLES'))
+ {
+ $this->mysql = null;
+ return;
+ }
+
+ $db = array();
+ while ($row = $query->fetchColumn())
+ {
+ $db[] = $row;
+ }
+
+ if (!in_array($this->options['extras']['prefix'] . 'cache_data', $db))
+ {
+ $query = $this->mysql->exec('CREATE TABLE `' . $this->options['extras']['prefix'] . 'cache_data` (`id` TEXT CHARACTER SET utf8 NOT NULL, `items` SMALLINT NOT NULL DEFAULT 0, `data` BLOB NOT NULL, `mtime` INT UNSIGNED NOT NULL, UNIQUE (`id`(125)))');
+ if ($query === false)
+ {
+ trigger_error("Can't create " . $this->options['extras']['prefix'] . "cache_data table, check permissions", E_USER_WARNING);
+ $this->mysql = null;
+ return;
+ }
+ }
+
+ if (!in_array($this->options['extras']['prefix'] . 'items', $db))
+ {
+ $query = $this->mysql->exec('CREATE TABLE `' . $this->options['extras']['prefix'] . 'items` (`feed_id` TEXT CHARACTER SET utf8 NOT NULL, `id` TEXT CHARACTER SET utf8 NOT NULL, `data` MEDIUMBLOB NOT NULL, `posted` INT UNSIGNED NOT NULL, INDEX `feed_id` (`feed_id`(125)))');
+ if ($query === false)
+ {
+ trigger_error("Can't create " . $this->options['extras']['prefix'] . "items table, check permissions", E_USER_WARNING);
+ $this->mysql = null;
+ return;
+ }
+ }
+ }
+
+ /**
+ * Save data to the cache
+ *
+ * @param array|SimplePie $data Data to store in the cache. If passed a SimplePie object, only cache the $data property
+ * @return bool Successfulness
+ */
+ public function save($data)
+ {
+ if ($this->mysql === null)
+ {
+ return false;
+ }
+
+ $query = $this->mysql->prepare('DELETE i, cd FROM `' . $this->options['extras']['prefix'] . 'cache_data` cd, ' .
+ '`' . $this->options['extras']['prefix'] . 'items` i ' .
+ 'WHERE cd.id = i.feed_id ' .
+ 'AND cd.mtime < (unix_timestamp() - :purge_time)');
+ $query->bindValue(':purge_time', $this->options['extras']['cache_purge_time']);
+
+ if (!$query->execute())
+ {
+ return false;
+ }
+
+ if ($data instanceof SimplePie)
+ {
+ $data = clone $data;
+
+ $prepared = self::prepare_simplepie_object_for_cache($data);
+
+ $query = $this->mysql->prepare('SELECT COUNT(*) FROM `' . $this->options['extras']['prefix'] . 'cache_data` WHERE `id` = :feed');
+ $query->bindValue(':feed', $this->id);
+ if ($query->execute())
+ {
+ if ($query->fetchColumn() > 0)
+ {
+ $items = count($prepared[1]);
+ if ($items)
+ {
+ $sql = 'UPDATE `' . $this->options['extras']['prefix'] . 'cache_data` SET `items` = :items, `data` = :data, `mtime` = :time WHERE `id` = :feed';
+ $query = $this->mysql->prepare($sql);
+ $query->bindValue(':items', $items);
+ }
+ else
+ {
+ $sql = 'UPDATE `' . $this->options['extras']['prefix'] . 'cache_data` SET `data` = :data, `mtime` = :time WHERE `id` = :feed';
+ $query = $this->mysql->prepare($sql);
+ }
+
+ $query->bindValue(':data', $prepared[0]);
+ $query->bindValue(':time', time());
+ $query->bindValue(':feed', $this->id);
+ if (!$query->execute())
+ {
+ return false;
+ }
+ }
+ else
+ {
+ $query = $this->mysql->prepare('INSERT INTO `' . $this->options['extras']['prefix'] . 'cache_data` (`id`, `items`, `data`, `mtime`) VALUES(:feed, :count, :data, :time)');
+ $query->bindValue(':feed', $this->id);
+ $query->bindValue(':count', count($prepared[1]));
+ $query->bindValue(':data', $prepared[0]);
+ $query->bindValue(':time', time());
+ if (!$query->execute())
+ {
+ return false;
+ }
+ }
+
+ $ids = array_keys($prepared[1]);
+ if (!empty($ids))
+ {
+ foreach ($ids as $id)
+ {
+ $database_ids[] = $this->mysql->quote($id);
+ }
+
+ $query = $this->mysql->prepare('SELECT `id` FROM `' . $this->options['extras']['prefix'] . 'items` WHERE `id` = ' . implode(' OR `id` = ', $database_ids) . ' AND `feed_id` = :feed');
+ $query->bindValue(':feed', $this->id);
+
+ if ($query->execute())
+ {
+ $existing_ids = array();
+ while ($row = $query->fetchColumn())
+ {
+ $existing_ids[] = $row;
+ }
+
+ $new_ids = array_diff($ids, $existing_ids);
+
+ foreach ($new_ids as $new_id)
+ {
+ if (!($date = $prepared[1][$new_id]->get_date('U')))
+ {
+ $date = time();
+ }
+
+ $query = $this->mysql->prepare('INSERT INTO `' . $this->options['extras']['prefix'] . 'items` (`feed_id`, `id`, `data`, `posted`) VALUES(:feed, :id, :data, :date)');
+ $query->bindValue(':feed', $this->id);
+ $query->bindValue(':id', $new_id);
+ $query->bindValue(':data', serialize($prepared[1][$new_id]->data));
+ $query->bindValue(':date', $date);
+ if (!$query->execute())
+ {
+ return false;
+ }
+ }
+ return true;
+ }
+ }
+ else
+ {
+ return true;
+ }
+ }
+ }
+ else
+ {
+ $query = $this->mysql->prepare('SELECT `id` FROM `' . $this->options['extras']['prefix'] . 'cache_data` WHERE `id` = :feed');
+ $query->bindValue(':feed', $this->id);
+ if ($query->execute())
+ {
+ if ($query->rowCount() > 0)
+ {
+ $query = $this->mysql->prepare('UPDATE `' . $this->options['extras']['prefix'] . 'cache_data` SET `items` = 0, `data` = :data, `mtime` = :time WHERE `id` = :feed');
+ $query->bindValue(':data', serialize($data));
+ $query->bindValue(':time', time());
+ $query->bindValue(':feed', $this->id);
+ if ($this->execute())
+ {
+ return true;
+ }
+ }
+ else
+ {
+ $query = $this->mysql->prepare('INSERT INTO `' . $this->options['extras']['prefix'] . 'cache_data` (`id`, `items`, `data`, `mtime`) VALUES(:id, 0, :data, :time)');
+ $query->bindValue(':id', $this->id);
+ $query->bindValue(':data', serialize($data));
+ $query->bindValue(':time', time());
+ if ($query->execute())
+ {
+ return true;
+ }
+ }
+ }
+ }
+ return false;
+ }
+
+ /**
+ * Retrieve the data saved to the cache
+ *
+ * @return array Data for SimplePie::$data
+ */
+ public function load()
+ {
+ if ($this->mysql === null)
+ {
+ return false;
+ }
+
+ $query = $this->mysql->prepare('SELECT `items`, `data` FROM `' . $this->options['extras']['prefix'] . 'cache_data` WHERE `id` = :id');
+ $query->bindValue(':id', $this->id);
+ if ($query->execute() && ($row = $query->fetch()))
+ {
+ $data = unserialize($row[1]);
+
+ if (isset($this->options['items'][0]))
+ {
+ $items = (int) $this->options['items'][0];
+ }
+ else
+ {
+ $items = (int) $row[0];
+ }
+
+ if ($items !== 0)
+ {
+ if (isset($data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0]))
+ {
+ $feed =& $data['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['feed'][0];
+ }
+ elseif (isset($data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0]))
+ {
+ $feed =& $data['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['feed'][0];
+ }
+ elseif (isset($data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0]))
+ {
+ $feed =& $data['child'][SIMPLEPIE_NAMESPACE_RDF]['RDF'][0];
+ }
+ elseif (isset($data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0]))
+ {
+ $feed =& $data['child'][SIMPLEPIE_NAMESPACE_RSS_20]['rss'][0];
+ }
+ else
+ {
+ $feed = null;
+ }
+
+ if ($feed !== null)
+ {
+ $sql = 'SELECT `data` FROM `' . $this->options['extras']['prefix'] . 'items` WHERE `feed_id` = :feed ORDER BY `posted` DESC';
+ if ($items > 0)
+ {
+ $sql .= ' LIMIT ' . $items;
+ }
+
+ $query = $this->mysql->prepare($sql);
+ $query->bindValue(':feed', $this->id);
+ if ($query->execute())
+ {
+ while ($row = $query->fetchColumn())
+ {
+ $feed['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['entry'][] = unserialize($row);
+ }
+ }
+ else
+ {
+ return false;
+ }
+ }
+ }
+ return $data;
+ }
+ return false;
+ }
+
+ /**
+ * Retrieve the last modified time for the cache
+ *
+ * @return int Timestamp
+ */
+ public function mtime()
+ {
+ if ($this->mysql === null)
+ {
+ return false;
+ }
+
+ $query = $this->mysql->prepare('SELECT `mtime` FROM `' . $this->options['extras']['prefix'] . 'cache_data` WHERE `id` = :id');
+ $query->bindValue(':id', $this->id);
+ if ($query->execute() && ($time = $query->fetchColumn()))
+ {
+ return $time;
+ }
+ else
+ {
+ return false;
+ }
+ }
+
+ /**
+ * Set the last modified time to the current time
+ *
+ * @return bool Success status
+ */
+ public function touch()
+ {
+ if ($this->mysql === null)
+ {
+ return false;
+ }
+
+ $query = $this->mysql->prepare('UPDATE `' . $this->options['extras']['prefix'] . 'cache_data` SET `mtime` = :time WHERE `id` = :id');
+ $query->bindValue(':time', time());
+ $query->bindValue(':id', $this->id);
+ if ($query->execute() && $query->rowCount() > 0)
+ {
+ return true;
+ }
+ else
+ {
+ return false;
+ }
+ }
+
+ /**
+ * Remove the cache
+ *
+ * @return bool Success status
+ */
+ public function unlink()
+ {
+ if ($this->mysql === null)
+ {
+ return false;
+ }
+
+ $query = $this->mysql->prepare('DELETE FROM `' . $this->options['extras']['prefix'] . 'cache_data` WHERE `id` = :id');
+ $query->bindValue(':id', $this->id);
+ $query2 = $this->mysql->prepare('DELETE FROM `' . $this->options['extras']['prefix'] . 'items` WHERE `feed_id` = :id');
+ $query2->bindValue(':id', $this->id);
+ if ($query->execute() && $query2->execute())
+ {
+ return true;
+ }
+ else
+ {
+ return false;
+ }
+ }
+}
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Cache/Redis.php b/vendor/simplepie/simplepie/library/SimplePie/Cache/Redis.php
new file mode 100644
index 000000000..04d72c79a
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Cache/Redis.php
@@ -0,0 +1,166 @@
+<?php
+
+/**
+ * SimplePie Redis Cache Extension
+ *
+ * @package SimplePie
+ * @author Jan Kozak <galvani78@gmail.com>
+ * @link http://galvani.cz/
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ * @version 0.2.9
+ */
+
+
+/**
+ * Caches data to redis
+ *
+ * Registered for URLs with the "redis" protocol
+ *
+ * For example, `redis://localhost:6379/?timeout=3600&prefix=sp_&dbIndex=0` will
+ * connect to redis on `localhost` on port 6379. All tables will be
+ * prefixed with `simple_primary-` and data will expire after 3600 seconds
+ *
+ * @package SimplePie
+ * @subpackage Caching
+ * @uses Redis
+ */
+class SimplePie_Cache_Redis implements SimplePie_Cache_Base {
+ /**
+ * Redis instance
+ *
+ * @var \Redis
+ */
+ protected $cache;
+
+ /**
+ * Options
+ *
+ * @var array
+ */
+ protected $options;
+
+ /**
+ * Cache name
+ *
+ * @var string
+ */
+ protected $name;
+
+ /**
+ * Cache Data
+ *
+ * @var type
+ */
+ protected $data;
+
+ /**
+ * Create a new cache object
+ *
+ * @param string $location Location string (from SimplePie::$cache_location)
+ * @param string $name Unique ID for the cache
+ * @param string $type Either TYPE_FEED for SimplePie data, or TYPE_IMAGE for image data
+ */
+ public function __construct($location, $name, $options = null) {
+ //$this->cache = \flow\simple\cache\Redis::getRedisClientInstance();
+ $parsed = SimplePie_Cache::parse_URL($location);
+ $redis = new Redis();
+ $redis->connect($parsed['host'], $parsed['port']);
+ $this->cache = $redis;
+
+ if (!is_null($options) && is_array($options)) {
+ $this->options = $options;
+ } else {
+ $this->options = array (
+ 'prefix' => 'rss:simple_primary:',
+ 'expire' => 0,
+ );
+ }
+
+ $this->name = $this->options['prefix'] . $name;
+ }
+
+ /**
+ * @param \Redis $cache
+ */
+ public function setRedisClient(\Redis $cache) {
+ $this->cache = $cache;
+ }
+
+ /**
+ * Save data to the cache
+ *
+ * @param array|SimplePie $data Data to store in the cache. If passed a SimplePie object, only cache the $data property
+ * @return bool Successfulness
+ */
+ public function save($data) {
+ if ($data instanceof SimplePie) {
+ $data = $data->data;
+ }
+ $response = $this->cache->set($this->name, serialize($data));
+ if ($this->options['expire']) {
+ $this->cache->expire($this->name, $this->options['expire']);
+ }
+
+ return $response;
+ }
+
+ /**
+ * Retrieve the data saved to the cache
+ *
+ * @return array Data for SimplePie::$data
+ */
+ public function load() {
+ $data = $this->cache->get($this->name);
+
+ if ($data !== false) {
+ return unserialize($data);
+ }
+ return false;
+ }
+
+ /**
+ * Retrieve the last modified time for the cache
+ *
+ * @return int Timestamp
+ */
+ public function mtime() {
+
+ $data = $this->cache->get($this->name);
+
+ if ($data !== false) {
+ return time();
+ }
+
+ return false;
+ }
+
+ /**
+ * Set the last modified time to the current time
+ *
+ * @return bool Success status
+ */
+ public function touch() {
+
+ $data = $this->cache->get($this->name);
+
+ if ($data !== false) {
+ $return = $this->cache->set($this->name, $data);
+ if ($this->options['expire']) {
+ return $this->cache->expire($this->name, $this->ttl);
+ }
+ return $return;
+ }
+
+ return false;
+ }
+
+ /**
+ * Remove the cache
+ *
+ * @return bool Success status
+ */
+ public function unlink() {
+ return $this->cache->set($this->name, null);
+ }
+
+}
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Caption.php b/vendor/simplepie/simplepie/library/SimplePie/Caption.php
new file mode 100644
index 000000000..abf07de1b
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Caption.php
@@ -0,0 +1,209 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+
+/**
+ * Handles `<media:text>` captions as defined in Media RSS.
+ *
+ * Used by {@see SimplePie_Enclosure::get_caption()} and {@see SimplePie_Enclosure::get_captions()}
+ *
+ * This class can be overloaded with {@see SimplePie::set_caption_class()}
+ *
+ * @package SimplePie
+ * @subpackage API
+ */
+class SimplePie_Caption
+{
+ /**
+ * Content type
+ *
+ * @var string
+ * @see get_type()
+ */
+ var $type;
+
+ /**
+ * Language
+ *
+ * @var string
+ * @see get_language()
+ */
+ var $lang;
+
+ /**
+ * Start time
+ *
+ * @var string
+ * @see get_starttime()
+ */
+ var $startTime;
+
+ /**
+ * End time
+ *
+ * @var string
+ * @see get_endtime()
+ */
+ var $endTime;
+
+ /**
+ * Caption text
+ *
+ * @var string
+ * @see get_text()
+ */
+ var $text;
+
+ /**
+ * Constructor, used to input the data
+ *
+ * For documentation on all the parameters, see the corresponding
+ * properties and their accessors
+ */
+ public function __construct($type = null, $lang = null, $startTime = null, $endTime = null, $text = null)
+ {
+ $this->type = $type;
+ $this->lang = $lang;
+ $this->startTime = $startTime;
+ $this->endTime = $endTime;
+ $this->text = $text;
+ }
+
+ /**
+ * String-ified version
+ *
+ * @return string
+ */
+ public function __toString()
+ {
+ // There is no $this->data here
+ return md5(serialize($this));
+ }
+
+ /**
+ * Get the end time
+ *
+ * @return string|null Time in the format 'hh:mm:ss.SSS'
+ */
+ public function get_endtime()
+ {
+ if ($this->endTime !== null)
+ {
+ return $this->endTime;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the language
+ *
+ * @link http://tools.ietf.org/html/rfc3066
+ * @return string|null Language code as per RFC 3066
+ */
+ public function get_language()
+ {
+ if ($this->lang !== null)
+ {
+ return $this->lang;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the start time
+ *
+ * @return string|null Time in the format 'hh:mm:ss.SSS'
+ */
+ public function get_starttime()
+ {
+ if ($this->startTime !== null)
+ {
+ return $this->startTime;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the text of the caption
+ *
+ * @return string|null
+ */
+ public function get_text()
+ {
+ if ($this->text !== null)
+ {
+ return $this->text;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the content type (not MIME type)
+ *
+ * @return string|null Either 'text' or 'html'
+ */
+ public function get_type()
+ {
+ if ($this->type !== null)
+ {
+ return $this->type;
+ }
+ else
+ {
+ return null;
+ }
+ }
+}
+
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Category.php b/vendor/simplepie/simplepie/library/SimplePie/Category.php
new file mode 100644
index 000000000..df0f13f9a
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Category.php
@@ -0,0 +1,163 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * Manages all category-related data
+ *
+ * Used by {@see SimplePie_Item::get_category()} and {@see SimplePie_Item::get_categories()}
+ *
+ * This class can be overloaded with {@see SimplePie::set_category_class()}
+ *
+ * @package SimplePie
+ * @subpackage API
+ */
+class SimplePie_Category
+{
+ /**
+ * Category identifier
+ *
+ * @var string|null
+ * @see get_term
+ */
+ var $term;
+
+ /**
+ * Categorization scheme identifier
+ *
+ * @var string|null
+ * @see get_scheme()
+ */
+ var $scheme;
+
+ /**
+ * Human readable label
+ *
+ * @var string|null
+ * @see get_label()
+ */
+ var $label;
+
+ /**
+ * Category type
+ *
+ * category for <category>
+ * subject for <dc:subject>
+ *
+ * @var string|null
+ * @see get_type()
+ */
+ var $type;
+
+ /**
+ * Constructor, used to input the data
+ *
+ * @param string|null $term
+ * @param string|null $scheme
+ * @param string|null $label
+ * @param string|null $type
+ */
+ public function __construct($term = null, $scheme = null, $label = null, $type = null)
+ {
+ $this->term = $term;
+ $this->scheme = $scheme;
+ $this->label = $label;
+ $this->type = $type;
+ }
+
+ /**
+ * String-ified version
+ *
+ * @return string
+ */
+ public function __toString()
+ {
+ // There is no $this->data here
+ return md5(serialize($this));
+ }
+
+ /**
+ * Get the category identifier
+ *
+ * @return string|null
+ */
+ public function get_term()
+ {
+ return $this->term;
+ }
+
+ /**
+ * Get the categorization scheme identifier
+ *
+ * @return string|null
+ */
+ public function get_scheme()
+ {
+ return $this->scheme;
+ }
+
+ /**
+ * Get the human readable label
+ *
+ * @param bool $strict
+ * @return string|null
+ */
+ public function get_label($strict = false)
+ {
+ if ($this->label === null && $strict !== true)
+ {
+ return $this->get_term();
+ }
+ return $this->label;
+ }
+
+ /**
+ * Get the category type
+ *
+ * @return string|null
+ */
+ public function get_type()
+ {
+ return $this->type;
+ }
+}
+
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Content/Type/Sniffer.php b/vendor/simplepie/simplepie/library/SimplePie/Content/Type/Sniffer.php
new file mode 100644
index 000000000..ff35de614
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Content/Type/Sniffer.php
@@ -0,0 +1,331 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+
+/**
+ * Content-type sniffing
+ *
+ * Based on the rules in http://tools.ietf.org/html/draft-abarth-mime-sniff-06
+ *
+ * This is used since we can't always trust Content-Type headers, and is based
+ * upon the HTML5 parsing rules.
+ *
+ *
+ * This class can be overloaded with {@see SimplePie::set_content_type_sniffer_class()}
+ *
+ * @package SimplePie
+ * @subpackage HTTP
+ */
+class SimplePie_Content_Type_Sniffer
+{
+ /**
+ * File object
+ *
+ * @var SimplePie_File
+ */
+ var $file;
+
+ /**
+ * Create an instance of the class with the input file
+ *
+ * @param SimplePie_Content_Type_Sniffer $file Input file
+ */
+ public function __construct($file)
+ {
+ $this->file = $file;
+ }
+
+ /**
+ * Get the Content-Type of the specified file
+ *
+ * @return string Actual Content-Type
+ */
+ public function get_type()
+ {
+ if (isset($this->file->headers['content-type']))
+ {
+ if (!isset($this->file->headers['content-encoding'])
+ && ($this->file->headers['content-type'] === 'text/plain'
+ || $this->file->headers['content-type'] === 'text/plain; charset=ISO-8859-1'
+ || $this->file->headers['content-type'] === 'text/plain; charset=iso-8859-1'
+ || $this->file->headers['content-type'] === 'text/plain; charset=UTF-8'))
+ {
+ return $this->text_or_binary();
+ }
+
+ if (($pos = strpos($this->file->headers['content-type'], ';')) !== false)
+ {
+ $official = substr($this->file->headers['content-type'], 0, $pos);
+ }
+ else
+ {
+ $official = $this->file->headers['content-type'];
+ }
+ $official = trim(strtolower($official));
+
+ if ($official === 'unknown/unknown'
+ || $official === 'application/unknown')
+ {
+ return $this->unknown();
+ }
+ elseif (substr($official, -4) === '+xml'
+ || $official === 'text/xml'
+ || $official === 'application/xml')
+ {
+ return $official;
+ }
+ elseif (substr($official, 0, 6) === 'image/')
+ {
+ if ($return = $this->image())
+ {
+ return $return;
+ }
+ else
+ {
+ return $official;
+ }
+ }
+ elseif ($official === 'text/html')
+ {
+ return $this->feed_or_html();
+ }
+ else
+ {
+ return $official;
+ }
+ }
+ else
+ {
+ return $this->unknown();
+ }
+ }
+
+ /**
+ * Sniff text or binary
+ *
+ * @return string Actual Content-Type
+ */
+ public function text_or_binary()
+ {
+ if (substr($this->file->body, 0, 2) === "\xFE\xFF"
+ || substr($this->file->body, 0, 2) === "\xFF\xFE"
+ || substr($this->file->body, 0, 4) === "\x00\x00\xFE\xFF"
+ || substr($this->file->body, 0, 3) === "\xEF\xBB\xBF")
+ {
+ return 'text/plain';
+ }
+ elseif (preg_match('/[\x00-\x08\x0E-\x1A\x1C-\x1F]/', $this->file->body))
+ {
+ return 'application/octect-stream';
+ }
+ else
+ {
+ return 'text/plain';
+ }
+ }
+
+ /**
+ * Sniff unknown
+ *
+ * @return string Actual Content-Type
+ */
+ public function unknown()
+ {
+ $ws = strspn($this->file->body, "\x09\x0A\x0B\x0C\x0D\x20");
+ if (strtolower(substr($this->file->body, $ws, 14)) === '<!doctype html'
+ || strtolower(substr($this->file->body, $ws, 5)) === '<html'
+ || strtolower(substr($this->file->body, $ws, 7)) === '<script')
+ {
+ return 'text/html';
+ }
+ elseif (substr($this->file->body, 0, 5) === '%PDF-')
+ {
+ return 'application/pdf';
+ }
+ elseif (substr($this->file->body, 0, 11) === '%!PS-Adobe-')
+ {
+ return 'application/postscript';
+ }
+ elseif (substr($this->file->body, 0, 6) === 'GIF87a'
+ || substr($this->file->body, 0, 6) === 'GIF89a')
+ {
+ return 'image/gif';
+ }
+ elseif (substr($this->file->body, 0, 8) === "\x89\x50\x4E\x47\x0D\x0A\x1A\x0A")
+ {
+ return 'image/png';
+ }
+ elseif (substr($this->file->body, 0, 3) === "\xFF\xD8\xFF")
+ {
+ return 'image/jpeg';
+ }
+ elseif (substr($this->file->body, 0, 2) === "\x42\x4D")
+ {
+ return 'image/bmp';
+ }
+ elseif (substr($this->file->body, 0, 4) === "\x00\x00\x01\x00")
+ {
+ return 'image/vnd.microsoft.icon';
+ }
+ else
+ {
+ return $this->text_or_binary();
+ }
+ }
+
+ /**
+ * Sniff images
+ *
+ * @return string Actual Content-Type
+ */
+ public function image()
+ {
+ if (substr($this->file->body, 0, 6) === 'GIF87a'
+ || substr($this->file->body, 0, 6) === 'GIF89a')
+ {
+ return 'image/gif';
+ }
+ elseif (substr($this->file->body, 0, 8) === "\x89\x50\x4E\x47\x0D\x0A\x1A\x0A")
+ {
+ return 'image/png';
+ }
+ elseif (substr($this->file->body, 0, 3) === "\xFF\xD8\xFF")
+ {
+ return 'image/jpeg';
+ }
+ elseif (substr($this->file->body, 0, 2) === "\x42\x4D")
+ {
+ return 'image/bmp';
+ }
+ elseif (substr($this->file->body, 0, 4) === "\x00\x00\x01\x00")
+ {
+ return 'image/vnd.microsoft.icon';
+ }
+ else
+ {
+ return false;
+ }
+ }
+
+ /**
+ * Sniff HTML
+ *
+ * @return string Actual Content-Type
+ */
+ public function feed_or_html()
+ {
+ $len = strlen($this->file->body);
+ $pos = strspn($this->file->body, "\x09\x0A\x0D\x20\xEF\xBB\xBF");
+
+ while ($pos < $len)
+ {
+ switch ($this->file->body[$pos])
+ {
+ case "\x09":
+ case "\x0A":
+ case "\x0D":
+ case "\x20":
+ $pos += strspn($this->file->body, "\x09\x0A\x0D\x20", $pos);
+ continue 2;
+
+ case '<':
+ $pos++;
+ break;
+
+ default:
+ return 'text/html';
+ }
+
+ if (substr($this->file->body, $pos, 3) === '!--')
+ {
+ $pos += 3;
+ if ($pos < $len && ($pos = strpos($this->file->body, '-->', $pos)) !== false)
+ {
+ $pos += 3;
+ }
+ else
+ {
+ return 'text/html';
+ }
+ }
+ elseif (substr($this->file->body, $pos, 1) === '!')
+ {
+ if ($pos < $len && ($pos = strpos($this->file->body, '>', $pos)) !== false)
+ {
+ $pos++;
+ }
+ else
+ {
+ return 'text/html';
+ }
+ }
+ elseif (substr($this->file->body, $pos, 1) === '?')
+ {
+ if ($pos < $len && ($pos = strpos($this->file->body, '?>', $pos)) !== false)
+ {
+ $pos += 2;
+ }
+ else
+ {
+ return 'text/html';
+ }
+ }
+ elseif (substr($this->file->body, $pos, 3) === 'rss'
+ || substr($this->file->body, $pos, 7) === 'rdf:RDF')
+ {
+ return 'application/rss+xml';
+ }
+ elseif (substr($this->file->body, $pos, 4) === 'feed')
+ {
+ return 'application/atom+xml';
+ }
+ else
+ {
+ return 'text/html';
+ }
+ }
+
+ return 'text/html';
+ }
+}
+
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Copyright.php b/vendor/simplepie/simplepie/library/SimplePie/Copyright.php
new file mode 100644
index 000000000..3f3d07d3b
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Copyright.php
@@ -0,0 +1,129 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * Manages `<media:copyright>` copyright tags as defined in Media RSS
+ *
+ * Used by {@see SimplePie_Enclosure::get_copyright()}
+ *
+ * This class can be overloaded with {@see SimplePie::set_copyright_class()}
+ *
+ * @package SimplePie
+ * @subpackage API
+ */
+class SimplePie_Copyright
+{
+ /**
+ * Copyright URL
+ *
+ * @var string
+ * @see get_url()
+ */
+ var $url;
+
+ /**
+ * Attribution
+ *
+ * @var string
+ * @see get_attribution()
+ */
+ var $label;
+
+ /**
+ * Constructor, used to input the data
+ *
+ * For documentation on all the parameters, see the corresponding
+ * properties and their accessors
+ */
+ public function __construct($url = null, $label = null)
+ {
+ $this->url = $url;
+ $this->label = $label;
+ }
+
+ /**
+ * String-ified version
+ *
+ * @return string
+ */
+ public function __toString()
+ {
+ // There is no $this->data here
+ return md5(serialize($this));
+ }
+
+ /**
+ * Get the copyright URL
+ *
+ * @return string|null URL to copyright information
+ */
+ public function get_url()
+ {
+ if ($this->url !== null)
+ {
+ return $this->url;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the attribution text
+ *
+ * @return string|null
+ */
+ public function get_attribution()
+ {
+ if ($this->label !== null)
+ {
+ return $this->label;
+ }
+ else
+ {
+ return null;
+ }
+ }
+}
+
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Core.php b/vendor/simplepie/simplepie/library/SimplePie/Core.php
new file mode 100644
index 000000000..c856ba361
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Core.php
@@ -0,0 +1,56 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * SimplePie class.
+ *
+ * Class for backward compatibility.
+ *
+ * @deprecated Use {@see SimplePie} directly
+ * @package SimplePie
+ * @subpackage API
+ */
+class SimplePie_Core extends SimplePie
+{
+
+} \ No newline at end of file
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Credit.php b/vendor/simplepie/simplepie/library/SimplePie/Credit.php
new file mode 100644
index 000000000..9bad9ef34
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Credit.php
@@ -0,0 +1,155 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * Handles `<media:credit>` as defined in Media RSS
+ *
+ * Used by {@see SimplePie_Enclosure::get_credit()} and {@see SimplePie_Enclosure::get_credits()}
+ *
+ * This class can be overloaded with {@see SimplePie::set_credit_class()}
+ *
+ * @package SimplePie
+ * @subpackage API
+ */
+class SimplePie_Credit
+{
+ /**
+ * Credited role
+ *
+ * @var string
+ * @see get_role()
+ */
+ var $role;
+
+ /**
+ * Organizational scheme
+ *
+ * @var string
+ * @see get_scheme()
+ */
+ var $scheme;
+
+ /**
+ * Credited name
+ *
+ * @var string
+ * @see get_name()
+ */
+ var $name;
+
+ /**
+ * Constructor, used to input the data
+ *
+ * For documentation on all the parameters, see the corresponding
+ * properties and their accessors
+ */
+ public function __construct($role = null, $scheme = null, $name = null)
+ {
+ $this->role = $role;
+ $this->scheme = $scheme;
+ $this->name = $name;
+ }
+
+ /**
+ * String-ified version
+ *
+ * @return string
+ */
+ public function __toString()
+ {
+ // There is no $this->data here
+ return md5(serialize($this));
+ }
+
+ /**
+ * Get the role of the person receiving credit
+ *
+ * @return string|null
+ */
+ public function get_role()
+ {
+ if ($this->role !== null)
+ {
+ return $this->role;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the organizational scheme
+ *
+ * @return string|null
+ */
+ public function get_scheme()
+ {
+ if ($this->scheme !== null)
+ {
+ return $this->scheme;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the credited person/entity's name
+ *
+ * @return string|null
+ */
+ public function get_name()
+ {
+ if ($this->name !== null)
+ {
+ return $this->name;
+ }
+ else
+ {
+ return null;
+ }
+ }
+}
+
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Decode/HTML/Entities.php b/vendor/simplepie/simplepie/library/SimplePie/Decode/HTML/Entities.php
new file mode 100644
index 000000000..de3f2cb53
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Decode/HTML/Entities.php
@@ -0,0 +1,615 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+
+/**
+ * Decode HTML Entities
+ *
+ * This implements HTML5 as of revision 967 (2007-06-28)
+ *
+ * @deprecated Use DOMDocument instead!
+ * @package SimplePie
+ */
+class SimplePie_Decode_HTML_Entities
+{
+ /**
+ * Data to be parsed
+ *
+ * @access private
+ * @var string
+ */
+ var $data = '';
+
+ /**
+ * Currently consumed bytes
+ *
+ * @access private
+ * @var string
+ */
+ var $consumed = '';
+
+ /**
+ * Position of the current byte being parsed
+ *
+ * @access private
+ * @var int
+ */
+ var $position = 0;
+
+ /**
+ * Create an instance of the class with the input data
+ *
+ * @access public
+ * @param string $data Input data
+ */
+ public function __construct($data)
+ {
+ $this->data = $data;
+ }
+
+ /**
+ * Parse the input data
+ *
+ * @access public
+ * @return string Output data
+ */
+ public function parse()
+ {
+ while (($this->position = strpos($this->data, '&', $this->position)) !== false)
+ {
+ $this->consume();
+ $this->entity();
+ $this->consumed = '';
+ }
+ return $this->data;
+ }
+
+ /**
+ * Consume the next byte
+ *
+ * @access private
+ * @return mixed The next byte, or false, if there is no more data
+ */
+ public function consume()
+ {
+ if (isset($this->data[$this->position]))
+ {
+ $this->consumed .= $this->data[$this->position];
+ return $this->data[$this->position++];
+ }
+ else
+ {
+ return false;
+ }
+ }
+
+ /**
+ * Consume a range of characters
+ *
+ * @access private
+ * @param string $chars Characters to consume
+ * @return mixed A series of characters that match the range, or false
+ */
+ public function consume_range($chars)
+ {
+ if ($len = strspn($this->data, $chars, $this->position))
+ {
+ $data = substr($this->data, $this->position, $len);
+ $this->consumed .= $data;
+ $this->position += $len;
+ return $data;
+ }
+ else
+ {
+ return false;
+ }
+ }
+
+ /**
+ * Unconsume one byte
+ *
+ * @access private
+ */
+ public function unconsume()
+ {
+ $this->consumed = substr($this->consumed, 0, -1);
+ $this->position--;
+ }
+
+ /**
+ * Decode an entity
+ *
+ * @access private
+ */
+ public function entity()
+ {
+ switch ($this->consume())
+ {
+ case "\x09":
+ case "\x0A":
+ case "\x0B":
+ case "\x0C":
+ case "\x20":
+ case "\x3C":
+ case "\x26":
+ case false:
+ break;
+
+ case "\x23":
+ switch ($this->consume())
+ {
+ case "\x78":
+ case "\x58":
+ $range = '0123456789ABCDEFabcdef';
+ $hex = true;
+ break;
+
+ default:
+ $range = '0123456789';
+ $hex = false;
+ $this->unconsume();
+ break;
+ }
+
+ if ($codepoint = $this->consume_range($range))
+ {
+ static $windows_1252_specials = array(0x0D => "\x0A", 0x80 => "\xE2\x82\xAC", 0x81 => "\xEF\xBF\xBD", 0x82 => "\xE2\x80\x9A", 0x83 => "\xC6\x92", 0x84 => "\xE2\x80\x9E", 0x85 => "\xE2\x80\xA6", 0x86 => "\xE2\x80\xA0", 0x87 => "\xE2\x80\xA1", 0x88 => "\xCB\x86", 0x89 => "\xE2\x80\xB0", 0x8A => "\xC5\xA0", 0x8B => "\xE2\x80\xB9", 0x8C => "\xC5\x92", 0x8D => "\xEF\xBF\xBD", 0x8E => "\xC5\xBD", 0x8F => "\xEF\xBF\xBD", 0x90 => "\xEF\xBF\xBD", 0x91 => "\xE2\x80\x98", 0x92 => "\xE2\x80\x99", 0x93 => "\xE2\x80\x9C", 0x94 => "\xE2\x80\x9D", 0x95 => "\xE2\x80\xA2", 0x96 => "\xE2\x80\x93", 0x97 => "\xE2\x80\x94", 0x98 => "\xCB\x9C", 0x99 => "\xE2\x84\xA2", 0x9A => "\xC5\xA1", 0x9B => "\xE2\x80\xBA", 0x9C => "\xC5\x93", 0x9D => "\xEF\xBF\xBD", 0x9E => "\xC5\xBE", 0x9F => "\xC5\xB8");
+
+ if ($hex)
+ {
+ $codepoint = hexdec($codepoint);
+ }
+ else
+ {
+ $codepoint = intval($codepoint);
+ }
+
+ if (isset($windows_1252_specials[$codepoint]))
+ {
+ $replacement = $windows_1252_specials[$codepoint];
+ }
+ else
+ {
+ $replacement = SimplePie_Misc::codepoint_to_utf8($codepoint);
+ }
+
+ if (!in_array($this->consume(), array(';', false), true))
+ {
+ $this->unconsume();
+ }
+
+ $consumed_length = strlen($this->consumed);
+ $this->data = substr_replace($this->data, $replacement, $this->position - $consumed_length, $consumed_length);
+ $this->position += strlen($replacement) - $consumed_length;
+ }
+ break;
+
+ default:
+ static $entities = array(
+ 'Aacute' => "\xC3\x81",
+ 'aacute' => "\xC3\xA1",
+ 'Aacute;' => "\xC3\x81",
+ 'aacute;' => "\xC3\xA1",
+ 'Acirc' => "\xC3\x82",
+ 'acirc' => "\xC3\xA2",
+ 'Acirc;' => "\xC3\x82",
+ 'acirc;' => "\xC3\xA2",
+ 'acute' => "\xC2\xB4",
+ 'acute;' => "\xC2\xB4",
+ 'AElig' => "\xC3\x86",
+ 'aelig' => "\xC3\xA6",
+ 'AElig;' => "\xC3\x86",
+ 'aelig;' => "\xC3\xA6",
+ 'Agrave' => "\xC3\x80",
+ 'agrave' => "\xC3\xA0",
+ 'Agrave;' => "\xC3\x80",
+ 'agrave;' => "\xC3\xA0",
+ 'alefsym;' => "\xE2\x84\xB5",
+ 'Alpha;' => "\xCE\x91",
+ 'alpha;' => "\xCE\xB1",
+ 'AMP' => "\x26",
+ 'amp' => "\x26",
+ 'AMP;' => "\x26",
+ 'amp;' => "\x26",
+ 'and;' => "\xE2\x88\xA7",
+ 'ang;' => "\xE2\x88\xA0",
+ 'apos;' => "\x27",
+ 'Aring' => "\xC3\x85",
+ 'aring' => "\xC3\xA5",
+ 'Aring;' => "\xC3\x85",
+ 'aring;' => "\xC3\xA5",
+ 'asymp;' => "\xE2\x89\x88",
+ 'Atilde' => "\xC3\x83",
+ 'atilde' => "\xC3\xA3",
+ 'Atilde;' => "\xC3\x83",
+ 'atilde;' => "\xC3\xA3",
+ 'Auml' => "\xC3\x84",
+ 'auml' => "\xC3\xA4",
+ 'Auml;' => "\xC3\x84",
+ 'auml;' => "\xC3\xA4",
+ 'bdquo;' => "\xE2\x80\x9E",
+ 'Beta;' => "\xCE\x92",
+ 'beta;' => "\xCE\xB2",
+ 'brvbar' => "\xC2\xA6",
+ 'brvbar;' => "\xC2\xA6",
+ 'bull;' => "\xE2\x80\xA2",
+ 'cap;' => "\xE2\x88\xA9",
+ 'Ccedil' => "\xC3\x87",
+ 'ccedil' => "\xC3\xA7",
+ 'Ccedil;' => "\xC3\x87",
+ 'ccedil;' => "\xC3\xA7",
+ 'cedil' => "\xC2\xB8",
+ 'cedil;' => "\xC2\xB8",
+ 'cent' => "\xC2\xA2",
+ 'cent;' => "\xC2\xA2",
+ 'Chi;' => "\xCE\xA7",
+ 'chi;' => "\xCF\x87",
+ 'circ;' => "\xCB\x86",
+ 'clubs;' => "\xE2\x99\xA3",
+ 'cong;' => "\xE2\x89\x85",
+ 'COPY' => "\xC2\xA9",
+ 'copy' => "\xC2\xA9",
+ 'COPY;' => "\xC2\xA9",
+ 'copy;' => "\xC2\xA9",
+ 'crarr;' => "\xE2\x86\xB5",
+ 'cup;' => "\xE2\x88\xAA",
+ 'curren' => "\xC2\xA4",
+ 'curren;' => "\xC2\xA4",
+ 'Dagger;' => "\xE2\x80\xA1",
+ 'dagger;' => "\xE2\x80\xA0",
+ 'dArr;' => "\xE2\x87\x93",
+ 'darr;' => "\xE2\x86\x93",
+ 'deg' => "\xC2\xB0",
+ 'deg;' => "\xC2\xB0",
+ 'Delta;' => "\xCE\x94",
+ 'delta;' => "\xCE\xB4",
+ 'diams;' => "\xE2\x99\xA6",
+ 'divide' => "\xC3\xB7",
+ 'divide;' => "\xC3\xB7",
+ 'Eacute' => "\xC3\x89",
+ 'eacute' => "\xC3\xA9",
+ 'Eacute;' => "\xC3\x89",
+ 'eacute;' => "\xC3\xA9",
+ 'Ecirc' => "\xC3\x8A",
+ 'ecirc' => "\xC3\xAA",
+ 'Ecirc;' => "\xC3\x8A",
+ 'ecirc;' => "\xC3\xAA",
+ 'Egrave' => "\xC3\x88",
+ 'egrave' => "\xC3\xA8",
+ 'Egrave;' => "\xC3\x88",
+ 'egrave;' => "\xC3\xA8",
+ 'empty;' => "\xE2\x88\x85",
+ 'emsp;' => "\xE2\x80\x83",
+ 'ensp;' => "\xE2\x80\x82",
+ 'Epsilon;' => "\xCE\x95",
+ 'epsilon;' => "\xCE\xB5",
+ 'equiv;' => "\xE2\x89\xA1",
+ 'Eta;' => "\xCE\x97",
+ 'eta;' => "\xCE\xB7",
+ 'ETH' => "\xC3\x90",
+ 'eth' => "\xC3\xB0",
+ 'ETH;' => "\xC3\x90",
+ 'eth;' => "\xC3\xB0",
+ 'Euml' => "\xC3\x8B",
+ 'euml' => "\xC3\xAB",
+ 'Euml;' => "\xC3\x8B",
+ 'euml;' => "\xC3\xAB",
+ 'euro;' => "\xE2\x82\xAC",
+ 'exist;' => "\xE2\x88\x83",
+ 'fnof;' => "\xC6\x92",
+ 'forall;' => "\xE2\x88\x80",
+ 'frac12' => "\xC2\xBD",
+ 'frac12;' => "\xC2\xBD",
+ 'frac14' => "\xC2\xBC",
+ 'frac14;' => "\xC2\xBC",
+ 'frac34' => "\xC2\xBE",
+ 'frac34;' => "\xC2\xBE",
+ 'frasl;' => "\xE2\x81\x84",
+ 'Gamma;' => "\xCE\x93",
+ 'gamma;' => "\xCE\xB3",
+ 'ge;' => "\xE2\x89\xA5",
+ 'GT' => "\x3E",
+ 'gt' => "\x3E",
+ 'GT;' => "\x3E",
+ 'gt;' => "\x3E",
+ 'hArr;' => "\xE2\x87\x94",
+ 'harr;' => "\xE2\x86\x94",
+ 'hearts;' => "\xE2\x99\xA5",
+ 'hellip;' => "\xE2\x80\xA6",
+ 'Iacute' => "\xC3\x8D",
+ 'iacute' => "\xC3\xAD",
+ 'Iacute;' => "\xC3\x8D",
+ 'iacute;' => "\xC3\xAD",
+ 'Icirc' => "\xC3\x8E",
+ 'icirc' => "\xC3\xAE",
+ 'Icirc;' => "\xC3\x8E",
+ 'icirc;' => "\xC3\xAE",
+ 'iexcl' => "\xC2\xA1",
+ 'iexcl;' => "\xC2\xA1",
+ 'Igrave' => "\xC3\x8C",
+ 'igrave' => "\xC3\xAC",
+ 'Igrave;' => "\xC3\x8C",
+ 'igrave;' => "\xC3\xAC",
+ 'image;' => "\xE2\x84\x91",
+ 'infin;' => "\xE2\x88\x9E",
+ 'int;' => "\xE2\x88\xAB",
+ 'Iota;' => "\xCE\x99",
+ 'iota;' => "\xCE\xB9",
+ 'iquest' => "\xC2\xBF",
+ 'iquest;' => "\xC2\xBF",
+ 'isin;' => "\xE2\x88\x88",
+ 'Iuml' => "\xC3\x8F",
+ 'iuml' => "\xC3\xAF",
+ 'Iuml;' => "\xC3\x8F",
+ 'iuml;' => "\xC3\xAF",
+ 'Kappa;' => "\xCE\x9A",
+ 'kappa;' => "\xCE\xBA",
+ 'Lambda;' => "\xCE\x9B",
+ 'lambda;' => "\xCE\xBB",
+ 'lang;' => "\xE3\x80\x88",
+ 'laquo' => "\xC2\xAB",
+ 'laquo;' => "\xC2\xAB",
+ 'lArr;' => "\xE2\x87\x90",
+ 'larr;' => "\xE2\x86\x90",
+ 'lceil;' => "\xE2\x8C\x88",
+ 'ldquo;' => "\xE2\x80\x9C",
+ 'le;' => "\xE2\x89\xA4",
+ 'lfloor;' => "\xE2\x8C\x8A",
+ 'lowast;' => "\xE2\x88\x97",
+ 'loz;' => "\xE2\x97\x8A",
+ 'lrm;' => "\xE2\x80\x8E",
+ 'lsaquo;' => "\xE2\x80\xB9",
+ 'lsquo;' => "\xE2\x80\x98",
+ 'LT' => "\x3C",
+ 'lt' => "\x3C",
+ 'LT;' => "\x3C",
+ 'lt;' => "\x3C",
+ 'macr' => "\xC2\xAF",
+ 'macr;' => "\xC2\xAF",
+ 'mdash;' => "\xE2\x80\x94",
+ 'micro' => "\xC2\xB5",
+ 'micro;' => "\xC2\xB5",
+ 'middot' => "\xC2\xB7",
+ 'middot;' => "\xC2\xB7",
+ 'minus;' => "\xE2\x88\x92",
+ 'Mu;' => "\xCE\x9C",
+ 'mu;' => "\xCE\xBC",
+ 'nabla;' => "\xE2\x88\x87",
+ 'nbsp' => "\xC2\xA0",
+ 'nbsp;' => "\xC2\xA0",
+ 'ndash;' => "\xE2\x80\x93",
+ 'ne;' => "\xE2\x89\xA0",
+ 'ni;' => "\xE2\x88\x8B",
+ 'not' => "\xC2\xAC",
+ 'not;' => "\xC2\xAC",
+ 'notin;' => "\xE2\x88\x89",
+ 'nsub;' => "\xE2\x8A\x84",
+ 'Ntilde' => "\xC3\x91",
+ 'ntilde' => "\xC3\xB1",
+ 'Ntilde;' => "\xC3\x91",
+ 'ntilde;' => "\xC3\xB1",
+ 'Nu;' => "\xCE\x9D",
+ 'nu;' => "\xCE\xBD",
+ 'Oacute' => "\xC3\x93",
+ 'oacute' => "\xC3\xB3",
+ 'Oacute;' => "\xC3\x93",
+ 'oacute;' => "\xC3\xB3",
+ 'Ocirc' => "\xC3\x94",
+ 'ocirc' => "\xC3\xB4",
+ 'Ocirc;' => "\xC3\x94",
+ 'ocirc;' => "\xC3\xB4",
+ 'OElig;' => "\xC5\x92",
+ 'oelig;' => "\xC5\x93",
+ 'Ograve' => "\xC3\x92",
+ 'ograve' => "\xC3\xB2",
+ 'Ograve;' => "\xC3\x92",
+ 'ograve;' => "\xC3\xB2",
+ 'oline;' => "\xE2\x80\xBE",
+ 'Omega;' => "\xCE\xA9",
+ 'omega;' => "\xCF\x89",
+ 'Omicron;' => "\xCE\x9F",
+ 'omicron;' => "\xCE\xBF",
+ 'oplus;' => "\xE2\x8A\x95",
+ 'or;' => "\xE2\x88\xA8",
+ 'ordf' => "\xC2\xAA",
+ 'ordf;' => "\xC2\xAA",
+ 'ordm' => "\xC2\xBA",
+ 'ordm;' => "\xC2\xBA",
+ 'Oslash' => "\xC3\x98",
+ 'oslash' => "\xC3\xB8",
+ 'Oslash;' => "\xC3\x98",
+ 'oslash;' => "\xC3\xB8",
+ 'Otilde' => "\xC3\x95",
+ 'otilde' => "\xC3\xB5",
+ 'Otilde;' => "\xC3\x95",
+ 'otilde;' => "\xC3\xB5",
+ 'otimes;' => "\xE2\x8A\x97",
+ 'Ouml' => "\xC3\x96",
+ 'ouml' => "\xC3\xB6",
+ 'Ouml;' => "\xC3\x96",
+ 'ouml;' => "\xC3\xB6",
+ 'para' => "\xC2\xB6",
+ 'para;' => "\xC2\xB6",
+ 'part;' => "\xE2\x88\x82",
+ 'permil;' => "\xE2\x80\xB0",
+ 'perp;' => "\xE2\x8A\xA5",
+ 'Phi;' => "\xCE\xA6",
+ 'phi;' => "\xCF\x86",
+ 'Pi;' => "\xCE\xA0",
+ 'pi;' => "\xCF\x80",
+ 'piv;' => "\xCF\x96",
+ 'plusmn' => "\xC2\xB1",
+ 'plusmn;' => "\xC2\xB1",
+ 'pound' => "\xC2\xA3",
+ 'pound;' => "\xC2\xA3",
+ 'Prime;' => "\xE2\x80\xB3",
+ 'prime;' => "\xE2\x80\xB2",
+ 'prod;' => "\xE2\x88\x8F",
+ 'prop;' => "\xE2\x88\x9D",
+ 'Psi;' => "\xCE\xA8",
+ 'psi;' => "\xCF\x88",
+ 'QUOT' => "\x22",
+ 'quot' => "\x22",
+ 'QUOT;' => "\x22",
+ 'quot;' => "\x22",
+ 'radic;' => "\xE2\x88\x9A",
+ 'rang;' => "\xE3\x80\x89",
+ 'raquo' => "\xC2\xBB",
+ 'raquo;' => "\xC2\xBB",
+ 'rArr;' => "\xE2\x87\x92",
+ 'rarr;' => "\xE2\x86\x92",
+ 'rceil;' => "\xE2\x8C\x89",
+ 'rdquo;' => "\xE2\x80\x9D",
+ 'real;' => "\xE2\x84\x9C",
+ 'REG' => "\xC2\xAE",
+ 'reg' => "\xC2\xAE",
+ 'REG;' => "\xC2\xAE",
+ 'reg;' => "\xC2\xAE",
+ 'rfloor;' => "\xE2\x8C\x8B",
+ 'Rho;' => "\xCE\xA1",
+ 'rho;' => "\xCF\x81",
+ 'rlm;' => "\xE2\x80\x8F",
+ 'rsaquo;' => "\xE2\x80\xBA",
+ 'rsquo;' => "\xE2\x80\x99",
+ 'sbquo;' => "\xE2\x80\x9A",
+ 'Scaron;' => "\xC5\xA0",
+ 'scaron;' => "\xC5\xA1",
+ 'sdot;' => "\xE2\x8B\x85",
+ 'sect' => "\xC2\xA7",
+ 'sect;' => "\xC2\xA7",
+ 'shy' => "\xC2\xAD",
+ 'shy;' => "\xC2\xAD",
+ 'Sigma;' => "\xCE\xA3",
+ 'sigma;' => "\xCF\x83",
+ 'sigmaf;' => "\xCF\x82",
+ 'sim;' => "\xE2\x88\xBC",
+ 'spades;' => "\xE2\x99\xA0",
+ 'sub;' => "\xE2\x8A\x82",
+ 'sube;' => "\xE2\x8A\x86",
+ 'sum;' => "\xE2\x88\x91",
+ 'sup;' => "\xE2\x8A\x83",
+ 'sup1' => "\xC2\xB9",
+ 'sup1;' => "\xC2\xB9",
+ 'sup2' => "\xC2\xB2",
+ 'sup2;' => "\xC2\xB2",
+ 'sup3' => "\xC2\xB3",
+ 'sup3;' => "\xC2\xB3",
+ 'supe;' => "\xE2\x8A\x87",
+ 'szlig' => "\xC3\x9F",
+ 'szlig;' => "\xC3\x9F",
+ 'Tau;' => "\xCE\xA4",
+ 'tau;' => "\xCF\x84",
+ 'there4;' => "\xE2\x88\xB4",
+ 'Theta;' => "\xCE\x98",
+ 'theta;' => "\xCE\xB8",
+ 'thetasym;' => "\xCF\x91",
+ 'thinsp;' => "\xE2\x80\x89",
+ 'THORN' => "\xC3\x9E",
+ 'thorn' => "\xC3\xBE",
+ 'THORN;' => "\xC3\x9E",
+ 'thorn;' => "\xC3\xBE",
+ 'tilde;' => "\xCB\x9C",
+ 'times' => "\xC3\x97",
+ 'times;' => "\xC3\x97",
+ 'TRADE;' => "\xE2\x84\xA2",
+ 'trade;' => "\xE2\x84\xA2",
+ 'Uacute' => "\xC3\x9A",
+ 'uacute' => "\xC3\xBA",
+ 'Uacute;' => "\xC3\x9A",
+ 'uacute;' => "\xC3\xBA",
+ 'uArr;' => "\xE2\x87\x91",
+ 'uarr;' => "\xE2\x86\x91",
+ 'Ucirc' => "\xC3\x9B",
+ 'ucirc' => "\xC3\xBB",
+ 'Ucirc;' => "\xC3\x9B",
+ 'ucirc;' => "\xC3\xBB",
+ 'Ugrave' => "\xC3\x99",
+ 'ugrave' => "\xC3\xB9",
+ 'Ugrave;' => "\xC3\x99",
+ 'ugrave;' => "\xC3\xB9",
+ 'uml' => "\xC2\xA8",
+ 'uml;' => "\xC2\xA8",
+ 'upsih;' => "\xCF\x92",
+ 'Upsilon;' => "\xCE\xA5",
+ 'upsilon;' => "\xCF\x85",
+ 'Uuml' => "\xC3\x9C",
+ 'uuml' => "\xC3\xBC",
+ 'Uuml;' => "\xC3\x9C",
+ 'uuml;' => "\xC3\xBC",
+ 'weierp;' => "\xE2\x84\x98",
+ 'Xi;' => "\xCE\x9E",
+ 'xi;' => "\xCE\xBE",
+ 'Yacute' => "\xC3\x9D",
+ 'yacute' => "\xC3\xBD",
+ 'Yacute;' => "\xC3\x9D",
+ 'yacute;' => "\xC3\xBD",
+ 'yen' => "\xC2\xA5",
+ 'yen;' => "\xC2\xA5",
+ 'yuml' => "\xC3\xBF",
+ 'Yuml;' => "\xC5\xB8",
+ 'yuml;' => "\xC3\xBF",
+ 'Zeta;' => "\xCE\x96",
+ 'zeta;' => "\xCE\xB6",
+ 'zwj;' => "\xE2\x80\x8D",
+ 'zwnj;' => "\xE2\x80\x8C"
+ );
+
+ for ($i = 0, $match = null; $i < 9 && $this->consume() !== false; $i++)
+ {
+ $consumed = substr($this->consumed, 1);
+ if (isset($entities[$consumed]))
+ {
+ $match = $consumed;
+ }
+ }
+
+ if ($match !== null)
+ {
+ $this->data = substr_replace($this->data, $entities[$match], $this->position - strlen($consumed) - 1, strlen($match) + 1);
+ $this->position += strlen($entities[$match]) - strlen($consumed) - 1;
+ }
+ break;
+ }
+ }
+}
+
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Enclosure.php b/vendor/simplepie/simplepie/library/SimplePie/Enclosure.php
new file mode 100644
index 000000000..15060e193
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Enclosure.php
@@ -0,0 +1,1379 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * Handles everything related to enclosures (including Media RSS and iTunes RSS)
+ *
+ * Used by {@see SimplePie_Item::get_enclosure()} and {@see SimplePie_Item::get_enclosures()}
+ *
+ * This class can be overloaded with {@see SimplePie::set_enclosure_class()}
+ *
+ * @package SimplePie
+ * @subpackage API
+ */
+class SimplePie_Enclosure
+{
+ /**
+ * @var string
+ * @see get_bitrate()
+ */
+ var $bitrate;
+
+ /**
+ * @var array
+ * @see get_captions()
+ */
+ var $captions;
+
+ /**
+ * @var array
+ * @see get_categories()
+ */
+ var $categories;
+
+ /**
+ * @var int
+ * @see get_channels()
+ */
+ var $channels;
+
+ /**
+ * @var SimplePie_Copyright
+ * @see get_copyright()
+ */
+ var $copyright;
+
+ /**
+ * @var array
+ * @see get_credits()
+ */
+ var $credits;
+
+ /**
+ * @var string
+ * @see get_description()
+ */
+ var $description;
+
+ /**
+ * @var int
+ * @see get_duration()
+ */
+ var $duration;
+
+ /**
+ * @var string
+ * @see get_expression()
+ */
+ var $expression;
+
+ /**
+ * @var string
+ * @see get_framerate()
+ */
+ var $framerate;
+
+ /**
+ * @var string
+ * @see get_handler()
+ */
+ var $handler;
+
+ /**
+ * @var array
+ * @see get_hashes()
+ */
+ var $hashes;
+
+ /**
+ * @var string
+ * @see get_height()
+ */
+ var $height;
+
+ /**
+ * @deprecated
+ * @var null
+ */
+ var $javascript;
+
+ /**
+ * @var array
+ * @see get_keywords()
+ */
+ var $keywords;
+
+ /**
+ * @var string
+ * @see get_language()
+ */
+ var $lang;
+
+ /**
+ * @var string
+ * @see get_length()
+ */
+ var $length;
+
+ /**
+ * @var string
+ * @see get_link()
+ */
+ var $link;
+
+ /**
+ * @var string
+ * @see get_medium()
+ */
+ var $medium;
+
+ /**
+ * @var string
+ * @see get_player()
+ */
+ var $player;
+
+ /**
+ * @var array
+ * @see get_ratings()
+ */
+ var $ratings;
+
+ /**
+ * @var array
+ * @see get_restrictions()
+ */
+ var $restrictions;
+
+ /**
+ * @var string
+ * @see get_sampling_rate()
+ */
+ var $samplingrate;
+
+ /**
+ * @var array
+ * @see get_thumbnails()
+ */
+ var $thumbnails;
+
+ /**
+ * @var string
+ * @see get_title()
+ */
+ var $title;
+
+ /**
+ * @var string
+ * @see get_type()
+ */
+ var $type;
+
+ /**
+ * @var string
+ * @see get_width()
+ */
+ var $width;
+
+ /**
+ * Constructor, used to input the data
+ *
+ * For documentation on all the parameters, see the corresponding
+ * properties and their accessors
+ *
+ * @uses idna_convert If available, this will convert an IDN
+ */
+ public function __construct($link = null, $type = null, $length = null, $javascript = null, $bitrate = null, $captions = null, $categories = null, $channels = null, $copyright = null, $credits = null, $description = null, $duration = null, $expression = null, $framerate = null, $hashes = null, $height = null, $keywords = null, $lang = null, $medium = null, $player = null, $ratings = null, $restrictions = null, $samplingrate = null, $thumbnails = null, $title = null, $width = null)
+ {
+ $this->bitrate = $bitrate;
+ $this->captions = $captions;
+ $this->categories = $categories;
+ $this->channels = $channels;
+ $this->copyright = $copyright;
+ $this->credits = $credits;
+ $this->description = $description;
+ $this->duration = $duration;
+ $this->expression = $expression;
+ $this->framerate = $framerate;
+ $this->hashes = $hashes;
+ $this->height = $height;
+ $this->keywords = $keywords;
+ $this->lang = $lang;
+ $this->length = $length;
+ $this->link = $link;
+ $this->medium = $medium;
+ $this->player = $player;
+ $this->ratings = $ratings;
+ $this->restrictions = $restrictions;
+ $this->samplingrate = $samplingrate;
+ $this->thumbnails = $thumbnails;
+ $this->title = $title;
+ $this->type = $type;
+ $this->width = $width;
+
+ if (class_exists('idna_convert'))
+ {
+ $idn = new idna_convert();
+ $parsed = SimplePie_Misc::parse_url($link);
+ $this->link = SimplePie_Misc::compress_parse_url($parsed['scheme'], $idn->encode($parsed['authority']), $parsed['path'], $parsed['query'], $parsed['fragment']);
+ }
+ $this->handler = $this->get_handler(); // Needs to load last
+ }
+
+ /**
+ * String-ified version
+ *
+ * @return string
+ */
+ public function __toString()
+ {
+ // There is no $this->data here
+ return md5(serialize($this));
+ }
+
+ /**
+ * Get the bitrate
+ *
+ * @return string|null
+ */
+ public function get_bitrate()
+ {
+ if ($this->bitrate !== null)
+ {
+ return $this->bitrate;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get a single caption
+ *
+ * @param int $key
+ * @return SimplePie_Caption|null
+ */
+ public function get_caption($key = 0)
+ {
+ $captions = $this->get_captions();
+ if (isset($captions[$key]))
+ {
+ return $captions[$key];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get all captions
+ *
+ * @return array|null Array of {@see SimplePie_Caption} objects
+ */
+ public function get_captions()
+ {
+ if ($this->captions !== null)
+ {
+ return $this->captions;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get a single category
+ *
+ * @param int $key
+ * @return SimplePie_Category|null
+ */
+ public function get_category($key = 0)
+ {
+ $categories = $this->get_categories();
+ if (isset($categories[$key]))
+ {
+ return $categories[$key];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get all categories
+ *
+ * @return array|null Array of {@see SimplePie_Category} objects
+ */
+ public function get_categories()
+ {
+ if ($this->categories !== null)
+ {
+ return $this->categories;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the number of audio channels
+ *
+ * @return int|null
+ */
+ public function get_channels()
+ {
+ if ($this->channels !== null)
+ {
+ return $this->channels;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the copyright information
+ *
+ * @return SimplePie_Copyright|null
+ */
+ public function get_copyright()
+ {
+ if ($this->copyright !== null)
+ {
+ return $this->copyright;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get a single credit
+ *
+ * @param int $key
+ * @return SimplePie_Credit|null
+ */
+ public function get_credit($key = 0)
+ {
+ $credits = $this->get_credits();
+ if (isset($credits[$key]))
+ {
+ return $credits[$key];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get all credits
+ *
+ * @return array|null Array of {@see SimplePie_Credit} objects
+ */
+ public function get_credits()
+ {
+ if ($this->credits !== null)
+ {
+ return $this->credits;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the description of the enclosure
+ *
+ * @return string|null
+ */
+ public function get_description()
+ {
+ if ($this->description !== null)
+ {
+ return $this->description;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the duration of the enclosure
+ *
+ * @param bool $convert Convert seconds into hh:mm:ss
+ * @return string|int|null 'hh:mm:ss' string if `$convert` was specified, otherwise integer (or null if none found)
+ */
+ public function get_duration($convert = false)
+ {
+ if ($this->duration !== null)
+ {
+ if ($convert)
+ {
+ $time = SimplePie_Misc::time_hms($this->duration);
+ return $time;
+ }
+ else
+ {
+ return $this->duration;
+ }
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the expression
+ *
+ * @return string Probably one of 'sample', 'full', 'nonstop', 'clip'. Defaults to 'full'
+ */
+ public function get_expression()
+ {
+ if ($this->expression !== null)
+ {
+ return $this->expression;
+ }
+ else
+ {
+ return 'full';
+ }
+ }
+
+ /**
+ * Get the file extension
+ *
+ * @return string|null
+ */
+ public function get_extension()
+ {
+ if ($this->link !== null)
+ {
+ $url = SimplePie_Misc::parse_url($this->link);
+ if ($url['path'] !== '')
+ {
+ return pathinfo($url['path'], PATHINFO_EXTENSION);
+ }
+ }
+ return null;
+ }
+
+ /**
+ * Get the framerate (in frames-per-second)
+ *
+ * @return string|null
+ */
+ public function get_framerate()
+ {
+ if ($this->framerate !== null)
+ {
+ return $this->framerate;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the preferred handler
+ *
+ * @return string|null One of 'flash', 'fmedia', 'quicktime', 'wmedia', 'mp3'
+ */
+ public function get_handler()
+ {
+ return $this->get_real_type(true);
+ }
+
+ /**
+ * Get a single hash
+ *
+ * @link http://www.rssboard.org/media-rss#media-hash
+ * @param int $key
+ * @return string|null Hash as per `media:hash`, prefixed with "$algo:"
+ */
+ public function get_hash($key = 0)
+ {
+ $hashes = $this->get_hashes();
+ if (isset($hashes[$key]))
+ {
+ return $hashes[$key];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get all credits
+ *
+ * @return array|null Array of strings, see {@see get_hash()}
+ */
+ public function get_hashes()
+ {
+ if ($this->hashes !== null)
+ {
+ return $this->hashes;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the height
+ *
+ * @return string|null
+ */
+ public function get_height()
+ {
+ if ($this->height !== null)
+ {
+ return $this->height;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the language
+ *
+ * @link http://tools.ietf.org/html/rfc3066
+ * @return string|null Language code as per RFC 3066
+ */
+ public function get_language()
+ {
+ if ($this->lang !== null)
+ {
+ return $this->lang;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get a single keyword
+ *
+ * @param int $key
+ * @return string|null
+ */
+ public function get_keyword($key = 0)
+ {
+ $keywords = $this->get_keywords();
+ if (isset($keywords[$key]))
+ {
+ return $keywords[$key];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get all keywords
+ *
+ * @return array|null Array of strings
+ */
+ public function get_keywords()
+ {
+ if ($this->keywords !== null)
+ {
+ return $this->keywords;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get length
+ *
+ * @return float Length in bytes
+ */
+ public function get_length()
+ {
+ if ($this->length !== null)
+ {
+ return $this->length;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the URL
+ *
+ * @return string|null
+ */
+ public function get_link()
+ {
+ if ($this->link !== null)
+ {
+ return urldecode($this->link);
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the medium
+ *
+ * @link http://www.rssboard.org/media-rss#media-content
+ * @return string|null Should be one of 'image', 'audio', 'video', 'document', 'executable'
+ */
+ public function get_medium()
+ {
+ if ($this->medium !== null)
+ {
+ return $this->medium;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the player URL
+ *
+ * Typically the same as {@see get_permalink()}
+ * @return string|null Player URL
+ */
+ public function get_player()
+ {
+ if ($this->player !== null)
+ {
+ return $this->player;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get a single rating
+ *
+ * @param int $key
+ * @return SimplePie_Rating|null
+ */
+ public function get_rating($key = 0)
+ {
+ $ratings = $this->get_ratings();
+ if (isset($ratings[$key]))
+ {
+ return $ratings[$key];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get all ratings
+ *
+ * @return array|null Array of {@see SimplePie_Rating} objects
+ */
+ public function get_ratings()
+ {
+ if ($this->ratings !== null)
+ {
+ return $this->ratings;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get a single restriction
+ *
+ * @param int $key
+ * @return SimplePie_Restriction|null
+ */
+ public function get_restriction($key = 0)
+ {
+ $restrictions = $this->get_restrictions();
+ if (isset($restrictions[$key]))
+ {
+ return $restrictions[$key];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get all restrictions
+ *
+ * @return array|null Array of {@see SimplePie_Restriction} objects
+ */
+ public function get_restrictions()
+ {
+ if ($this->restrictions !== null)
+ {
+ return $this->restrictions;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the sampling rate (in kHz)
+ *
+ * @return string|null
+ */
+ public function get_sampling_rate()
+ {
+ if ($this->samplingrate !== null)
+ {
+ return $this->samplingrate;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the file size (in MiB)
+ *
+ * @return float|null File size in mebibytes (1048 bytes)
+ */
+ public function get_size()
+ {
+ $length = $this->get_length();
+ if ($length !== null)
+ {
+ return round($length/1048576, 2);
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get a single thumbnail
+ *
+ * @param int $key
+ * @return string|null Thumbnail URL
+ */
+ public function get_thumbnail($key = 0)
+ {
+ $thumbnails = $this->get_thumbnails();
+ if (isset($thumbnails[$key]))
+ {
+ return $thumbnails[$key];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get all thumbnails
+ *
+ * @return array|null Array of thumbnail URLs
+ */
+ public function get_thumbnails()
+ {
+ if ($this->thumbnails !== null)
+ {
+ return $this->thumbnails;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the title
+ *
+ * @return string|null
+ */
+ public function get_title()
+ {
+ if ($this->title !== null)
+ {
+ return $this->title;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get mimetype of the enclosure
+ *
+ * @see get_real_type()
+ * @return string|null MIME type
+ */
+ public function get_type()
+ {
+ if ($this->type !== null)
+ {
+ return $this->type;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the width
+ *
+ * @return string|null
+ */
+ public function get_width()
+ {
+ if ($this->width !== null)
+ {
+ return $this->width;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Embed the enclosure using `<embed>`
+ *
+ * @deprecated Use the second parameter to {@see embed} instead
+ *
+ * @param array|string $options See first paramter to {@see embed}
+ * @return string HTML string to output
+ */
+ public function native_embed($options='')
+ {
+ return $this->embed($options, true);
+ }
+
+ /**
+ * Embed the enclosure using Javascript
+ *
+ * `$options` is an array or comma-separated key:value string, with the
+ * following properties:
+ *
+ * - `alt` (string): Alternate content for when an end-user does not have
+ * the appropriate handler installed or when a file type is
+ * unsupported. Can be any text or HTML. Defaults to blank.
+ * - `altclass` (string): If a file type is unsupported, the end-user will
+ * see the alt text (above) linked directly to the content. That link
+ * will have this value as its class name. Defaults to blank.
+ * - `audio` (string): This is an image that should be used as a
+ * placeholder for audio files before they're loaded (QuickTime-only).
+ * Can be any relative or absolute URL. Defaults to blank.
+ * - `bgcolor` (string): The background color for the media, if not
+ * already transparent. Defaults to `#ffffff`.
+ * - `height` (integer): The height of the embedded media. Accepts any
+ * numeric pixel value (such as `360`) or `auto`. Defaults to `auto`,
+ * and it is recommended that you use this default.
+ * - `loop` (boolean): Do you want the media to loop when it's done?
+ * Defaults to `false`.
+ * - `mediaplayer` (string): The location of the included
+ * `mediaplayer.swf` file. This allows for the playback of Flash Video
+ * (`.flv`) files, and is the default handler for non-Odeo MP3's.
+ * Defaults to blank.
+ * - `video` (string): This is an image that should be used as a
+ * placeholder for video files before they're loaded (QuickTime-only).
+ * Can be any relative or absolute URL. Defaults to blank.
+ * - `width` (integer): The width of the embedded media. Accepts any
+ * numeric pixel value (such as `480`) or `auto`. Defaults to `auto`,
+ * and it is recommended that you use this default.
+ * - `widescreen` (boolean): Is the enclosure widescreen or standard?
+ * This applies only to video enclosures, and will automatically resize
+ * the content appropriately. Defaults to `false`, implying 4:3 mode.
+ *
+ * Note: Non-widescreen (4:3) mode with `width` and `height` set to `auto`
+ * will default to 480x360 video resolution. Widescreen (16:9) mode with
+ * `width` and `height` set to `auto` will default to 480x270 video resolution.
+ *
+ * @todo If the dimensions for media:content are defined, use them when width/height are set to 'auto'.
+ * @param array|string $options Comma-separated key:value list, or array
+ * @param bool $native Use `<embed>`
+ * @return string HTML string to output
+ */
+ public function embed($options = '', $native = false)
+ {
+ // Set up defaults
+ $audio = '';
+ $video = '';
+ $alt = '';
+ $altclass = '';
+ $loop = 'false';
+ $width = 'auto';
+ $height = 'auto';
+ $bgcolor = '#ffffff';
+ $mediaplayer = '';
+ $widescreen = false;
+ $handler = $this->get_handler();
+ $type = $this->get_real_type();
+
+ // Process options and reassign values as necessary
+ if (is_array($options))
+ {
+ extract($options);
+ }
+ else
+ {
+ $options = explode(',', $options);
+ foreach($options as $option)
+ {
+ $opt = explode(':', $option, 2);
+ if (isset($opt[0], $opt[1]))
+ {
+ $opt[0] = trim($opt[0]);
+ $opt[1] = trim($opt[1]);
+ switch ($opt[0])
+ {
+ case 'audio':
+ $audio = $opt[1];
+ break;
+
+ case 'video':
+ $video = $opt[1];
+ break;
+
+ case 'alt':
+ $alt = $opt[1];
+ break;
+
+ case 'altclass':
+ $altclass = $opt[1];
+ break;
+
+ case 'loop':
+ $loop = $opt[1];
+ break;
+
+ case 'width':
+ $width = $opt[1];
+ break;
+
+ case 'height':
+ $height = $opt[1];
+ break;
+
+ case 'bgcolor':
+ $bgcolor = $opt[1];
+ break;
+
+ case 'mediaplayer':
+ $mediaplayer = $opt[1];
+ break;
+
+ case 'widescreen':
+ $widescreen = $opt[1];
+ break;
+ }
+ }
+ }
+ }
+
+ $mime = explode('/', $type, 2);
+ $mime = $mime[0];
+
+ // Process values for 'auto'
+ if ($width === 'auto')
+ {
+ if ($mime === 'video')
+ {
+ if ($height === 'auto')
+ {
+ $width = 480;
+ }
+ elseif ($widescreen)
+ {
+ $width = round((intval($height)/9)*16);
+ }
+ else
+ {
+ $width = round((intval($height)/3)*4);
+ }
+ }
+ else
+ {
+ $width = '100%';
+ }
+ }
+
+ if ($height === 'auto')
+ {
+ if ($mime === 'audio')
+ {
+ $height = 0;
+ }
+ elseif ($mime === 'video')
+ {
+ if ($width === 'auto')
+ {
+ if ($widescreen)
+ {
+ $height = 270;
+ }
+ else
+ {
+ $height = 360;
+ }
+ }
+ elseif ($widescreen)
+ {
+ $height = round((intval($width)/16)*9);
+ }
+ else
+ {
+ $height = round((intval($width)/4)*3);
+ }
+ }
+ else
+ {
+ $height = 376;
+ }
+ }
+ elseif ($mime === 'audio')
+ {
+ $height = 0;
+ }
+
+ // Set proper placeholder value
+ if ($mime === 'audio')
+ {
+ $placeholder = $audio;
+ }
+ elseif ($mime === 'video')
+ {
+ $placeholder = $video;
+ }
+
+ $embed = '';
+
+ // Flash
+ if ($handler === 'flash')
+ {
+ if ($native)
+ {
+ $embed .= "<embed src=\"" . $this->get_link() . "\" pluginspage=\"http://adobe.com/go/getflashplayer\" type=\"$type\" quality=\"high\" width=\"$width\" height=\"$height\" bgcolor=\"$bgcolor\" loop=\"$loop\"></embed>";
+ }
+ else
+ {
+ $embed .= "<script type='text/javascript'>embed_flash('$bgcolor', '$width', '$height', '" . $this->get_link() . "', '$loop', '$type');</script>";
+ }
+ }
+
+ // Flash Media Player file types.
+ // Preferred handler for MP3 file types.
+ elseif ($handler === 'fmedia' || ($handler === 'mp3' && $mediaplayer !== ''))
+ {
+ $height += 20;
+ if ($native)
+ {
+ $embed .= "<embed src=\"$mediaplayer\" pluginspage=\"http://adobe.com/go/getflashplayer\" type=\"application/x-shockwave-flash\" quality=\"high\" width=\"$width\" height=\"$height\" wmode=\"transparent\" flashvars=\"file=" . rawurlencode($this->get_link().'?file_extension=.'.$this->get_extension()) . "&autostart=false&repeat=$loop&showdigits=true&showfsbutton=false\"></embed>";
+ }
+ else
+ {
+ $embed .= "<script type='text/javascript'>embed_flv('$width', '$height', '" . rawurlencode($this->get_link().'?file_extension=.'.$this->get_extension()) . "', '$placeholder', '$loop', '$mediaplayer');</script>";
+ }
+ }
+
+ // QuickTime 7 file types. Need to test with QuickTime 6.
+ // Only handle MP3's if the Flash Media Player is not present.
+ elseif ($handler === 'quicktime' || ($handler === 'mp3' && $mediaplayer === ''))
+ {
+ $height += 16;
+ if ($native)
+ {
+ if ($placeholder !== '')
+ {
+ $embed .= "<embed type=\"$type\" style=\"cursor:hand; cursor:pointer;\" href=\"" . $this->get_link() . "\" src=\"$placeholder\" width=\"$width\" height=\"$height\" autoplay=\"false\" target=\"myself\" controller=\"false\" loop=\"$loop\" scale=\"aspect\" bgcolor=\"$bgcolor\" pluginspage=\"http://apple.com/quicktime/download/\"></embed>";
+ }
+ else
+ {
+ $embed .= "<embed type=\"$type\" style=\"cursor:hand; cursor:pointer;\" src=\"" . $this->get_link() . "\" width=\"$width\" height=\"$height\" autoplay=\"false\" target=\"myself\" controller=\"true\" loop=\"$loop\" scale=\"aspect\" bgcolor=\"$bgcolor\" pluginspage=\"http://apple.com/quicktime/download/\"></embed>";
+ }
+ }
+ else
+ {
+ $embed .= "<script type='text/javascript'>embed_quicktime('$type', '$bgcolor', '$width', '$height', '" . $this->get_link() . "', '$placeholder', '$loop');</script>";
+ }
+ }
+
+ // Windows Media
+ elseif ($handler === 'wmedia')
+ {
+ $height += 45;
+ if ($native)
+ {
+ $embed .= "<embed type=\"application/x-mplayer2\" src=\"" . $this->get_link() . "\" autosize=\"1\" width=\"$width\" height=\"$height\" showcontrols=\"1\" showstatusbar=\"0\" showdisplay=\"0\" autostart=\"0\"></embed>";
+ }
+ else
+ {
+ $embed .= "<script type='text/javascript'>embed_wmedia('$width', '$height', '" . $this->get_link() . "');</script>";
+ }
+ }
+
+ // Everything else
+ else $embed .= '<a href="' . $this->get_link() . '" class="' . $altclass . '">' . $alt . '</a>';
+
+ return $embed;
+ }
+
+ /**
+ * Get the real media type
+ *
+ * Often, feeds lie to us, necessitating a bit of deeper inspection. This
+ * converts types to their canonical representations based on the file
+ * extension
+ *
+ * @see get_type()
+ * @param bool $find_handler Internal use only, use {@see get_handler()} instead
+ * @return string MIME type
+ */
+ public function get_real_type($find_handler = false)
+ {
+ // Mime-types by handler.
+ $types_flash = array('application/x-shockwave-flash', 'application/futuresplash'); // Flash
+ $types_fmedia = array('video/flv', 'video/x-flv','flv-application/octet-stream'); // Flash Media Player
+ $types_quicktime = array('audio/3gpp', 'audio/3gpp2', 'audio/aac', 'audio/x-aac', 'audio/aiff', 'audio/x-aiff', 'audio/mid', 'audio/midi', 'audio/x-midi', 'audio/mp4', 'audio/m4a', 'audio/x-m4a', 'audio/wav', 'audio/x-wav', 'video/3gpp', 'video/3gpp2', 'video/m4v', 'video/x-m4v', 'video/mp4', 'video/mpeg', 'video/x-mpeg', 'video/quicktime', 'video/sd-video'); // QuickTime
+ $types_wmedia = array('application/asx', 'application/x-mplayer2', 'audio/x-ms-wma', 'audio/x-ms-wax', 'video/x-ms-asf-plugin', 'video/x-ms-asf', 'video/x-ms-wm', 'video/x-ms-wmv', 'video/x-ms-wvx'); // Windows Media
+ $types_mp3 = array('audio/mp3', 'audio/x-mp3', 'audio/mpeg', 'audio/x-mpeg'); // MP3
+
+ if ($this->get_type() !== null)
+ {
+ $type = strtolower($this->type);
+ }
+ else
+ {
+ $type = null;
+ }
+
+ // If we encounter an unsupported mime-type, check the file extension and guess intelligently.
+ if (!in_array($type, array_merge($types_flash, $types_fmedia, $types_quicktime, $types_wmedia, $types_mp3)))
+ {
+ switch (strtolower($this->get_extension()))
+ {
+ // Audio mime-types
+ case 'aac':
+ case 'adts':
+ $type = 'audio/acc';
+ break;
+
+ case 'aif':
+ case 'aifc':
+ case 'aiff':
+ case 'cdda':
+ $type = 'audio/aiff';
+ break;
+
+ case 'bwf':
+ $type = 'audio/wav';
+ break;
+
+ case 'kar':
+ case 'mid':
+ case 'midi':
+ case 'smf':
+ $type = 'audio/midi';
+ break;
+
+ case 'm4a':
+ $type = 'audio/x-m4a';
+ break;
+
+ case 'mp3':
+ case 'swa':
+ $type = 'audio/mp3';
+ break;
+
+ case 'wav':
+ $type = 'audio/wav';
+ break;
+
+ case 'wax':
+ $type = 'audio/x-ms-wax';
+ break;
+
+ case 'wma':
+ $type = 'audio/x-ms-wma';
+ break;
+
+ // Video mime-types
+ case '3gp':
+ case '3gpp':
+ $type = 'video/3gpp';
+ break;
+
+ case '3g2':
+ case '3gp2':
+ $type = 'video/3gpp2';
+ break;
+
+ case 'asf':
+ $type = 'video/x-ms-asf';
+ break;
+
+ case 'flv':
+ $type = 'video/x-flv';
+ break;
+
+ case 'm1a':
+ case 'm1s':
+ case 'm1v':
+ case 'm15':
+ case 'm75':
+ case 'mp2':
+ case 'mpa':
+ case 'mpeg':
+ case 'mpg':
+ case 'mpm':
+ case 'mpv':
+ $type = 'video/mpeg';
+ break;
+
+ case 'm4v':
+ $type = 'video/x-m4v';
+ break;
+
+ case 'mov':
+ case 'qt':
+ $type = 'video/quicktime';
+ break;
+
+ case 'mp4':
+ case 'mpg4':
+ $type = 'video/mp4';
+ break;
+
+ case 'sdv':
+ $type = 'video/sd-video';
+ break;
+
+ case 'wm':
+ $type = 'video/x-ms-wm';
+ break;
+
+ case 'wmv':
+ $type = 'video/x-ms-wmv';
+ break;
+
+ case 'wvx':
+ $type = 'video/x-ms-wvx';
+ break;
+
+ // Flash mime-types
+ case 'spl':
+ $type = 'application/futuresplash';
+ break;
+
+ case 'swf':
+ $type = 'application/x-shockwave-flash';
+ break;
+ }
+ }
+
+ if ($find_handler)
+ {
+ if (in_array($type, $types_flash))
+ {
+ return 'flash';
+ }
+ elseif (in_array($type, $types_fmedia))
+ {
+ return 'fmedia';
+ }
+ elseif (in_array($type, $types_quicktime))
+ {
+ return 'quicktime';
+ }
+ elseif (in_array($type, $types_wmedia))
+ {
+ return 'wmedia';
+ }
+ elseif (in_array($type, $types_mp3))
+ {
+ return 'mp3';
+ }
+ else
+ {
+ return null;
+ }
+ }
+ else
+ {
+ return $type;
+ }
+ }
+}
+
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Exception.php b/vendor/simplepie/simplepie/library/SimplePie/Exception.php
new file mode 100644
index 000000000..53c015e77
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Exception.php
@@ -0,0 +1,51 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * General SimplePie exception class
+ *
+ * @package SimplePie
+ */
+class SimplePie_Exception extends Exception
+{
+} \ No newline at end of file
diff --git a/vendor/simplepie/simplepie/library/SimplePie/File.php b/vendor/simplepie/simplepie/library/SimplePie/File.php
new file mode 100644
index 000000000..e670e05a0
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/File.php
@@ -0,0 +1,306 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * Used for fetching remote files and reading local files
+ *
+ * Supports HTTP 1.0 via cURL or fsockopen, with spotty HTTP 1.1 support
+ *
+ * This class can be overloaded with {@see SimplePie::set_file_class()}
+ *
+ * @package SimplePie
+ * @subpackage HTTP
+ * @todo Move to properly supporting RFC2616 (HTTP/1.1)
+ */
+class SimplePie_File
+{
+ var $url;
+ var $useragent;
+ var $success = true;
+ var $headers = array();
+ var $body;
+ var $status_code;
+ var $redirects = 0;
+ var $error;
+ var $method = SIMPLEPIE_FILE_SOURCE_NONE;
+ var $permanent_url;
+
+ public function __construct($url, $timeout = 10, $redirects = 5, $headers = null, $useragent = null, $force_fsockopen = false, $curl_options = array())
+ {
+ if (class_exists('idna_convert'))
+ {
+ $idn = new idna_convert();
+ $parsed = SimplePie_Misc::parse_url($url);
+ $url = SimplePie_Misc::compress_parse_url($parsed['scheme'], $idn->encode($parsed['authority']), $parsed['path'], $parsed['query'], $parsed['fragment']);
+ }
+ $this->url = $url;
+ $this->permanent_url = $url;
+ $this->useragent = $useragent;
+ if (preg_match('/^http(s)?:\/\//i', $url))
+ {
+ if ($useragent === null)
+ {
+ $useragent = ini_get('user_agent');
+ $this->useragent = $useragent;
+ }
+ if (!is_array($headers))
+ {
+ $headers = array();
+ }
+ if (!$force_fsockopen && function_exists('curl_exec'))
+ {
+ $this->method = SIMPLEPIE_FILE_SOURCE_REMOTE | SIMPLEPIE_FILE_SOURCE_CURL;
+ $fp = curl_init();
+ $headers2 = array();
+ foreach ($headers as $key => $value)
+ {
+ $headers2[] = "$key: $value";
+ }
+ if (version_compare(SimplePie_Misc::get_curl_version(), '7.10.5', '>='))
+ {
+ curl_setopt($fp, CURLOPT_ENCODING, '');
+ }
+ curl_setopt($fp, CURLOPT_URL, $url);
+ curl_setopt($fp, CURLOPT_HEADER, 1);
+ curl_setopt($fp, CURLOPT_RETURNTRANSFER, 1);
+ curl_setopt($fp, CURLOPT_FAILONERROR, 1);
+ curl_setopt($fp, CURLOPT_TIMEOUT, $timeout);
+ curl_setopt($fp, CURLOPT_CONNECTTIMEOUT, $timeout);
+ curl_setopt($fp, CURLOPT_REFERER, $url);
+ curl_setopt($fp, CURLOPT_USERAGENT, $useragent);
+ curl_setopt($fp, CURLOPT_HTTPHEADER, $headers2);
+ if (!ini_get('open_basedir') && !ini_get('safe_mode') && version_compare(SimplePie_Misc::get_curl_version(), '7.15.2', '>='))
+ {
+ curl_setopt($fp, CURLOPT_FOLLOWLOCATION, 1);
+ curl_setopt($fp, CURLOPT_MAXREDIRS, $redirects);
+ }
+ foreach ($curl_options as $curl_param => $curl_value) {
+ curl_setopt($fp, $curl_param, $curl_value);
+ }
+
+ $this->headers = curl_exec($fp);
+ if (curl_errno($fp) === 23 || curl_errno($fp) === 61)
+ {
+ curl_setopt($fp, CURLOPT_ENCODING, 'none');
+ $this->headers = curl_exec($fp);
+ }
+ if (curl_errno($fp))
+ {
+ $this->error = 'cURL error ' . curl_errno($fp) . ': ' . curl_error($fp);
+ $this->success = false;
+ }
+ else
+ {
+ // Use the updated url provided by curl_getinfo after any redirects.
+ if ($info = curl_getinfo($fp)) {
+ $this->url = $info['url'];
+ }
+ curl_close($fp);
+ $this->headers = explode("\r\n\r\n", $this->headers, $info['redirect_count'] + 1);
+ $this->headers = array_pop($this->headers);
+ $parser = new SimplePie_HTTP_Parser($this->headers);
+ if ($parser->parse())
+ {
+ $this->headers = $parser->headers;
+ $this->body = trim($parser->body);
+ $this->status_code = $parser->status_code;
+ if ((in_array($this->status_code, array(300, 301, 302, 303, 307)) || $this->status_code > 307 && $this->status_code < 400) && isset($this->headers['location']) && $this->redirects < $redirects)
+ {
+ $this->redirects++;
+ $location = SimplePie_Misc::absolutize_url($this->headers['location'], $url);
+ $previousStatusCode = $this->status_code;
+ $this->__construct($location, $timeout, $redirects, $headers, $useragent, $force_fsockopen);
+ $this->permanent_url = ($previousStatusCode == 301) ? $location : $url;
+ return;
+ }
+ }
+ }
+ }
+ else
+ {
+ $this->method = SIMPLEPIE_FILE_SOURCE_REMOTE | SIMPLEPIE_FILE_SOURCE_FSOCKOPEN;
+ $url_parts = parse_url($url);
+ $socket_host = $url_parts['host'];
+ if (isset($url_parts['scheme']) && strtolower($url_parts['scheme']) === 'https')
+ {
+ $socket_host = "ssl://$url_parts[host]";
+ $url_parts['port'] = 443;
+ }
+ if (!isset($url_parts['port']))
+ {
+ $url_parts['port'] = 80;
+ }
+ $fp = @fsockopen($socket_host, $url_parts['port'], $errno, $errstr, $timeout);
+ if (!$fp)
+ {
+ $this->error = 'fsockopen error: ' . $errstr;
+ $this->success = false;
+ }
+ else
+ {
+ stream_set_timeout($fp, $timeout);
+ if (isset($url_parts['path']))
+ {
+ if (isset($url_parts['query']))
+ {
+ $get = "$url_parts[path]?$url_parts[query]";
+ }
+ else
+ {
+ $get = $url_parts['path'];
+ }
+ }
+ else
+ {
+ $get = '/';
+ }
+ $out = "GET $get HTTP/1.1\r\n";
+ $out .= "Host: $url_parts[host]\r\n";
+ $out .= "User-Agent: $useragent\r\n";
+ if (extension_loaded('zlib'))
+ {
+ $out .= "Accept-Encoding: x-gzip,gzip,deflate\r\n";
+ }
+
+ if (isset($url_parts['user']) && isset($url_parts['pass']))
+ {
+ $out .= "Authorization: Basic " . base64_encode("$url_parts[user]:$url_parts[pass]") . "\r\n";
+ }
+ foreach ($headers as $key => $value)
+ {
+ $out .= "$key: $value\r\n";
+ }
+ $out .= "Connection: Close\r\n\r\n";
+ fwrite($fp, $out);
+
+ $info = stream_get_meta_data($fp);
+
+ $this->headers = '';
+ while (!$info['eof'] && !$info['timed_out'])
+ {
+ $this->headers .= fread($fp, 1160);
+ $info = stream_get_meta_data($fp);
+ }
+ if (!$info['timed_out'])
+ {
+ $parser = new SimplePie_HTTP_Parser($this->headers);
+ if ($parser->parse())
+ {
+ $this->headers = $parser->headers;
+ $this->body = $parser->body;
+ $this->status_code = $parser->status_code;
+ if ((in_array($this->status_code, array(300, 301, 302, 303, 307)) || $this->status_code > 307 && $this->status_code < 400) && isset($this->headers['location']) && $this->redirects < $redirects)
+ {
+ $this->redirects++;
+ $location = SimplePie_Misc::absolutize_url($this->headers['location'], $url);
+ $previousStatusCode = $this->status_code;
+ $this->__construct($location, $timeout, $redirects, $headers, $useragent, $force_fsockopen);
+ $this->permanent_url = ($previousStatusCode == 301) ? $location : $url;
+ return;
+ }
+ if (isset($this->headers['content-encoding']))
+ {
+ // Hey, we act dumb elsewhere, so let's do that here too
+ switch (strtolower(trim($this->headers['content-encoding'], "\x09\x0A\x0D\x20")))
+ {
+ case 'gzip':
+ case 'x-gzip':
+ $decoder = new SimplePie_gzdecode($this->body);
+ if (!$decoder->parse())
+ {
+ $this->error = 'Unable to decode HTTP "gzip" stream';
+ $this->success = false;
+ }
+ else
+ {
+ $this->body = trim($decoder->data);
+ }
+ break;
+
+ case 'deflate':
+ if (($decompressed = gzinflate($this->body)) !== false)
+ {
+ $this->body = $decompressed;
+ }
+ else if (($decompressed = gzuncompress($this->body)) !== false)
+ {
+ $this->body = $decompressed;
+ }
+ else if (function_exists('gzdecode') && ($decompressed = gzdecode($this->body)) !== false)
+ {
+ $this->body = $decompressed;
+ }
+ else
+ {
+ $this->error = 'Unable to decode HTTP "deflate" stream';
+ $this->success = false;
+ }
+ break;
+
+ default:
+ $this->error = 'Unknown content coding';
+ $this->success = false;
+ }
+ }
+ }
+ }
+ else
+ {
+ $this->error = 'fsocket timed out';
+ $this->success = false;
+ }
+ fclose($fp);
+ }
+ }
+ }
+ else
+ {
+ $this->method = SIMPLEPIE_FILE_SOURCE_LOCAL | SIMPLEPIE_FILE_SOURCE_FILE_GET_CONTENTS;
+ if (empty($url) || !($this->body = trim(file_get_contents($url))))
+ {
+ $this->error = 'file_get_contents could not read the file';
+ $this->success = false;
+ }
+ }
+ }
+}
diff --git a/vendor/simplepie/simplepie/library/SimplePie/HTTP/Parser.php b/vendor/simplepie/simplepie/library/SimplePie/HTTP/Parser.php
new file mode 100644
index 000000000..63ae1e03d
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/HTTP/Parser.php
@@ -0,0 +1,499 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+
+/**
+ * HTTP Response Parser
+ *
+ * @package SimplePie
+ * @subpackage HTTP
+ */
+class SimplePie_HTTP_Parser
+{
+ /**
+ * HTTP Version
+ *
+ * @var float
+ */
+ public $http_version = 0.0;
+
+ /**
+ * Status code
+ *
+ * @var int
+ */
+ public $status_code = 0;
+
+ /**
+ * Reason phrase
+ *
+ * @var string
+ */
+ public $reason = '';
+
+ /**
+ * Key/value pairs of the headers
+ *
+ * @var array
+ */
+ public $headers = array();
+
+ /**
+ * Body of the response
+ *
+ * @var string
+ */
+ public $body = '';
+
+ /**
+ * Current state of the state machine
+ *
+ * @var string
+ */
+ protected $state = 'http_version';
+
+ /**
+ * Input data
+ *
+ * @var string
+ */
+ protected $data = '';
+
+ /**
+ * Input data length (to avoid calling strlen() everytime this is needed)
+ *
+ * @var int
+ */
+ protected $data_length = 0;
+
+ /**
+ * Current position of the pointer
+ *
+ * @var int
+ */
+ protected $position = 0;
+
+ /**
+ * Name of the hedaer currently being parsed
+ *
+ * @var string
+ */
+ protected $name = '';
+
+ /**
+ * Value of the hedaer currently being parsed
+ *
+ * @var string
+ */
+ protected $value = '';
+
+ /**
+ * Create an instance of the class with the input data
+ *
+ * @param string $data Input data
+ */
+ public function __construct($data)
+ {
+ $this->data = $data;
+ $this->data_length = strlen($this->data);
+ }
+
+ /**
+ * Parse the input data
+ *
+ * @return bool true on success, false on failure
+ */
+ public function parse()
+ {
+ while ($this->state && $this->state !== 'emit' && $this->has_data())
+ {
+ $state = $this->state;
+ $this->$state();
+ }
+ $this->data = '';
+ if ($this->state === 'emit' || $this->state === 'body')
+ {
+ return true;
+ }
+ else
+ {
+ $this->http_version = '';
+ $this->status_code = '';
+ $this->reason = '';
+ $this->headers = array();
+ $this->body = '';
+ return false;
+ }
+ }
+
+ /**
+ * Check whether there is data beyond the pointer
+ *
+ * @return bool true if there is further data, false if not
+ */
+ protected function has_data()
+ {
+ return (bool) ($this->position < $this->data_length);
+ }
+
+ /**
+ * See if the next character is LWS
+ *
+ * @return bool true if the next character is LWS, false if not
+ */
+ protected function is_linear_whitespace()
+ {
+ return (bool) ($this->data[$this->position] === "\x09"
+ || $this->data[$this->position] === "\x20"
+ || ($this->data[$this->position] === "\x0A"
+ && isset($this->data[$this->position + 1])
+ && ($this->data[$this->position + 1] === "\x09" || $this->data[$this->position + 1] === "\x20")));
+ }
+
+ /**
+ * Parse the HTTP version
+ */
+ protected function http_version()
+ {
+ if (strpos($this->data, "\x0A") !== false && strtoupper(substr($this->data, 0, 5)) === 'HTTP/')
+ {
+ $len = strspn($this->data, '0123456789.', 5);
+ $this->http_version = substr($this->data, 5, $len);
+ $this->position += 5 + $len;
+ if (substr_count($this->http_version, '.') <= 1)
+ {
+ $this->http_version = (float) $this->http_version;
+ $this->position += strspn($this->data, "\x09\x20", $this->position);
+ $this->state = 'status';
+ }
+ else
+ {
+ $this->state = false;
+ }
+ }
+ else
+ {
+ $this->state = false;
+ }
+ }
+
+ /**
+ * Parse the status code
+ */
+ protected function status()
+ {
+ if ($len = strspn($this->data, '0123456789', $this->position))
+ {
+ $this->status_code = (int) substr($this->data, $this->position, $len);
+ $this->position += $len;
+ $this->state = 'reason';
+ }
+ else
+ {
+ $this->state = false;
+ }
+ }
+
+ /**
+ * Parse the reason phrase
+ */
+ protected function reason()
+ {
+ $len = strcspn($this->data, "\x0A", $this->position);
+ $this->reason = trim(substr($this->data, $this->position, $len), "\x09\x0D\x20");
+ $this->position += $len + 1;
+ $this->state = 'new_line';
+ }
+
+ /**
+ * Deal with a new line, shifting data around as needed
+ */
+ protected function new_line()
+ {
+ $this->value = trim($this->value, "\x0D\x20");
+ if ($this->name !== '' && $this->value !== '')
+ {
+ $this->name = strtolower($this->name);
+ // We should only use the last Content-Type header. c.f. issue #1
+ if (isset($this->headers[$this->name]) && $this->name !== 'content-type')
+ {
+ $this->headers[$this->name] .= ', ' . $this->value;
+ }
+ else
+ {
+ $this->headers[$this->name] = $this->value;
+ }
+ }
+ $this->name = '';
+ $this->value = '';
+ if (substr($this->data[$this->position], 0, 2) === "\x0D\x0A")
+ {
+ $this->position += 2;
+ $this->state = 'body';
+ }
+ elseif ($this->data[$this->position] === "\x0A")
+ {
+ $this->position++;
+ $this->state = 'body';
+ }
+ else
+ {
+ $this->state = 'name';
+ }
+ }
+
+ /**
+ * Parse a header name
+ */
+ protected function name()
+ {
+ $len = strcspn($this->data, "\x0A:", $this->position);
+ if (isset($this->data[$this->position + $len]))
+ {
+ if ($this->data[$this->position + $len] === "\x0A")
+ {
+ $this->position += $len;
+ $this->state = 'new_line';
+ }
+ else
+ {
+ $this->name = substr($this->data, $this->position, $len);
+ $this->position += $len + 1;
+ $this->state = 'value';
+ }
+ }
+ else
+ {
+ $this->state = false;
+ }
+ }
+
+ /**
+ * Parse LWS, replacing consecutive LWS characters with a single space
+ */
+ protected function linear_whitespace()
+ {
+ do
+ {
+ if (substr($this->data, $this->position, 2) === "\x0D\x0A")
+ {
+ $this->position += 2;
+ }
+ elseif ($this->data[$this->position] === "\x0A")
+ {
+ $this->position++;
+ }
+ $this->position += strspn($this->data, "\x09\x20", $this->position);
+ } while ($this->has_data() && $this->is_linear_whitespace());
+ $this->value .= "\x20";
+ }
+
+ /**
+ * See what state to move to while within non-quoted header values
+ */
+ protected function value()
+ {
+ if ($this->is_linear_whitespace())
+ {
+ $this->linear_whitespace();
+ }
+ else
+ {
+ switch ($this->data[$this->position])
+ {
+ case '"':
+ // Workaround for ETags: we have to include the quotes as
+ // part of the tag.
+ if (strtolower($this->name) === 'etag')
+ {
+ $this->value .= '"';
+ $this->position++;
+ $this->state = 'value_char';
+ break;
+ }
+ $this->position++;
+ $this->state = 'quote';
+ break;
+
+ case "\x0A":
+ $this->position++;
+ $this->state = 'new_line';
+ break;
+
+ default:
+ $this->state = 'value_char';
+ break;
+ }
+ }
+ }
+
+ /**
+ * Parse a header value while outside quotes
+ */
+ protected function value_char()
+ {
+ $len = strcspn($this->data, "\x09\x20\x0A\"", $this->position);
+ $this->value .= substr($this->data, $this->position, $len);
+ $this->position += $len;
+ $this->state = 'value';
+ }
+
+ /**
+ * See what state to move to while within quoted header values
+ */
+ protected function quote()
+ {
+ if ($this->is_linear_whitespace())
+ {
+ $this->linear_whitespace();
+ }
+ else
+ {
+ switch ($this->data[$this->position])
+ {
+ case '"':
+ $this->position++;
+ $this->state = 'value';
+ break;
+
+ case "\x0A":
+ $this->position++;
+ $this->state = 'new_line';
+ break;
+
+ case '\\':
+ $this->position++;
+ $this->state = 'quote_escaped';
+ break;
+
+ default:
+ $this->state = 'quote_char';
+ break;
+ }
+ }
+ }
+
+ /**
+ * Parse a header value while within quotes
+ */
+ protected function quote_char()
+ {
+ $len = strcspn($this->data, "\x09\x20\x0A\"\\", $this->position);
+ $this->value .= substr($this->data, $this->position, $len);
+ $this->position += $len;
+ $this->state = 'value';
+ }
+
+ /**
+ * Parse an escaped character within quotes
+ */
+ protected function quote_escaped()
+ {
+ $this->value .= $this->data[$this->position];
+ $this->position++;
+ $this->state = 'quote';
+ }
+
+ /**
+ * Parse the body
+ */
+ protected function body()
+ {
+ $this->body = substr($this->data, $this->position);
+ if (!empty($this->headers['transfer-encoding']))
+ {
+ unset($this->headers['transfer-encoding']);
+ $this->state = 'chunked';
+ }
+ else
+ {
+ $this->state = 'emit';
+ }
+ }
+
+ /**
+ * Parsed a "Transfer-Encoding: chunked" body
+ */
+ protected function chunked()
+ {
+ if (!preg_match('/^([0-9a-f]+)[^\r\n]*\r\n/i', trim($this->body)))
+ {
+ $this->state = 'emit';
+ return;
+ }
+
+ $decoded = '';
+ $encoded = $this->body;
+
+ while (true)
+ {
+ $is_chunked = (bool) preg_match( '/^([0-9a-f]+)[^\r\n]*\r\n/i', $encoded, $matches );
+ if (!$is_chunked)
+ {
+ // Looks like it's not chunked after all
+ $this->state = 'emit';
+ return;
+ }
+
+ $length = hexdec(trim($matches[1]));
+ if ($length === 0)
+ {
+ // Ignore trailer headers
+ $this->state = 'emit';
+ $this->body = $decoded;
+ return;
+ }
+
+ $chunk_length = strlen($matches[0]);
+ $decoded .= $part = substr($encoded, $chunk_length, $length);
+ $encoded = substr($encoded, $chunk_length + $length + 2);
+
+ if (trim($encoded) === '0' || empty($encoded))
+ {
+ $this->state = 'emit';
+ $this->body = $decoded;
+ return;
+ }
+ }
+ }
+}
diff --git a/vendor/simplepie/simplepie/library/SimplePie/IRI.php b/vendor/simplepie/simplepie/library/SimplePie/IRI.php
new file mode 100644
index 000000000..2b3fbaf07
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/IRI.php
@@ -0,0 +1,1257 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * IRI parser/serialiser/normaliser
+ *
+ * @package SimplePie
+ * @subpackage HTTP
+ * @author Geoffrey Sneddon
+ * @author Steve Minutillo
+ * @author Ryan McCue
+ * @copyright 2007-2012 Geoffrey Sneddon, Steve Minutillo, Ryan McCue
+ * @license http://www.opensource.org/licenses/bsd-license.php
+ */
+class SimplePie_IRI
+{
+ /**
+ * Scheme
+ *
+ * @var string
+ */
+ protected $scheme = null;
+
+ /**
+ * User Information
+ *
+ * @var string
+ */
+ protected $iuserinfo = null;
+
+ /**
+ * ihost
+ *
+ * @var string
+ */
+ protected $ihost = null;
+
+ /**
+ * Port
+ *
+ * @var string
+ */
+ protected $port = null;
+
+ /**
+ * ipath
+ *
+ * @var string
+ */
+ protected $ipath = '';
+
+ /**
+ * iquery
+ *
+ * @var string
+ */
+ protected $iquery = null;
+
+ /**
+ * ifragment
+ *
+ * @var string
+ */
+ protected $ifragment = null;
+
+ /**
+ * Normalization database
+ *
+ * Each key is the scheme, each value is an array with each key as the IRI
+ * part and value as the default value for that part.
+ */
+ protected $normalization = array(
+ 'acap' => array(
+ 'port' => 674
+ ),
+ 'dict' => array(
+ 'port' => 2628
+ ),
+ 'file' => array(
+ 'ihost' => 'localhost'
+ ),
+ 'http' => array(
+ 'port' => 80,
+ 'ipath' => '/'
+ ),
+ 'https' => array(
+ 'port' => 443,
+ 'ipath' => '/'
+ ),
+ );
+
+ /**
+ * Return the entire IRI when you try and read the object as a string
+ *
+ * @return string
+ */
+ public function __toString()
+ {
+ return $this->get_iri();
+ }
+
+ /**
+ * Overload __set() to provide access via properties
+ *
+ * @param string $name Property name
+ * @param mixed $value Property value
+ */
+ public function __set($name, $value)
+ {
+ if (method_exists($this, 'set_' . $name))
+ {
+ call_user_func(array($this, 'set_' . $name), $value);
+ }
+ elseif (
+ $name === 'iauthority'
+ || $name === 'iuserinfo'
+ || $name === 'ihost'
+ || $name === 'ipath'
+ || $name === 'iquery'
+ || $name === 'ifragment'
+ )
+ {
+ call_user_func(array($this, 'set_' . substr($name, 1)), $value);
+ }
+ }
+
+ /**
+ * Overload __get() to provide access via properties
+ *
+ * @param string $name Property name
+ * @return mixed
+ */
+ public function __get($name)
+ {
+ // isset() returns false for null, we don't want to do that
+ // Also why we use array_key_exists below instead of isset()
+ $props = get_object_vars($this);
+
+ if (
+ $name === 'iri' ||
+ $name === 'uri' ||
+ $name === 'iauthority' ||
+ $name === 'authority'
+ )
+ {
+ $return = $this->{"get_$name"}();
+ }
+ elseif (array_key_exists($name, $props))
+ {
+ $return = $this->$name;
+ }
+ // host -> ihost
+ elseif (($prop = 'i' . $name) && array_key_exists($prop, $props))
+ {
+ $name = $prop;
+ $return = $this->$prop;
+ }
+ // ischeme -> scheme
+ elseif (($prop = substr($name, 1)) && array_key_exists($prop, $props))
+ {
+ $name = $prop;
+ $return = $this->$prop;
+ }
+ else
+ {
+ trigger_error('Undefined property: ' . get_class($this) . '::' . $name, E_USER_NOTICE);
+ $return = null;
+ }
+
+ if ($return === null && isset($this->normalization[$this->scheme][$name]))
+ {
+ return $this->normalization[$this->scheme][$name];
+ }
+ else
+ {
+ return $return;
+ }
+ }
+
+ /**
+ * Overload __isset() to provide access via properties
+ *
+ * @param string $name Property name
+ * @return bool
+ */
+ public function __isset($name)
+ {
+ if (method_exists($this, 'get_' . $name) || isset($this->$name))
+ {
+ return true;
+ }
+ else
+ {
+ return false;
+ }
+ }
+
+ /**
+ * Overload __unset() to provide access via properties
+ *
+ * @param string $name Property name
+ */
+ public function __unset($name)
+ {
+ if (method_exists($this, 'set_' . $name))
+ {
+ call_user_func(array($this, 'set_' . $name), '');
+ }
+ }
+
+ /**
+ * Create a new IRI object, from a specified string
+ *
+ * @param string $iri
+ */
+ public function __construct($iri = null)
+ {
+ $this->set_iri($iri);
+ }
+
+ /**
+ * Clean up
+ */
+ public function __destruct() {
+ $this->set_iri(null, true);
+ $this->set_path(null, true);
+ $this->set_authority(null, true);
+ }
+
+ /**
+ * Create a new IRI object by resolving a relative IRI
+ *
+ * Returns false if $base is not absolute, otherwise an IRI.
+ *
+ * @param IRI|string $base (Absolute) Base IRI
+ * @param IRI|string $relative Relative IRI
+ * @return IRI|false
+ */
+ public static function absolutize($base, $relative)
+ {
+ if (!($relative instanceof SimplePie_IRI))
+ {
+ $relative = new SimplePie_IRI($relative);
+ }
+ if (!$relative->is_valid())
+ {
+ return false;
+ }
+ elseif ($relative->scheme !== null)
+ {
+ return clone $relative;
+ }
+ else
+ {
+ if (!($base instanceof SimplePie_IRI))
+ {
+ $base = new SimplePie_IRI($base);
+ }
+ if ($base->scheme !== null && $base->is_valid())
+ {
+ if ($relative->get_iri() !== '')
+ {
+ if ($relative->iuserinfo !== null || $relative->ihost !== null || $relative->port !== null)
+ {
+ $target = clone $relative;
+ $target->scheme = $base->scheme;
+ }
+ else
+ {
+ $target = new SimplePie_IRI;
+ $target->scheme = $base->scheme;
+ $target->iuserinfo = $base->iuserinfo;
+ $target->ihost = $base->ihost;
+ $target->port = $base->port;
+ if ($relative->ipath !== '')
+ {
+ if ($relative->ipath[0] === '/')
+ {
+ $target->ipath = $relative->ipath;
+ }
+ elseif (($base->iuserinfo !== null || $base->ihost !== null || $base->port !== null) && $base->ipath === '')
+ {
+ $target->ipath = '/' . $relative->ipath;
+ }
+ elseif (($last_segment = strrpos($base->ipath, '/')) !== false)
+ {
+ $target->ipath = substr($base->ipath, 0, $last_segment + 1) . $relative->ipath;
+ }
+ else
+ {
+ $target->ipath = $relative->ipath;
+ }
+ $target->ipath = $target->remove_dot_segments($target->ipath);
+ $target->iquery = $relative->iquery;
+ }
+ else
+ {
+ $target->ipath = $base->ipath;
+ if ($relative->iquery !== null)
+ {
+ $target->iquery = $relative->iquery;
+ }
+ elseif ($base->iquery !== null)
+ {
+ $target->iquery = $base->iquery;
+ }
+ }
+ $target->ifragment = $relative->ifragment;
+ }
+ }
+ else
+ {
+ $target = clone $base;
+ $target->ifragment = null;
+ }
+ $target->scheme_normalization();
+ return $target;
+ }
+ else
+ {
+ return false;
+ }
+ }
+ }
+
+ /**
+ * Parse an IRI into scheme/authority/path/query/fragment segments
+ *
+ * @param string $iri
+ * @return array
+ */
+ protected function parse_iri($iri)
+ {
+ $iri = trim($iri, "\x20\x09\x0A\x0C\x0D");
+ if (preg_match('/^((?P<scheme>[^:\/?#]+):)?(\/\/(?P<authority>[^\/?#]*))?(?P<path>[^?#]*)(\?(?P<query>[^#]*))?(#(?P<fragment>.*))?$/', $iri, $match))
+ {
+ if ($match[1] === '')
+ {
+ $match['scheme'] = null;
+ }
+ if (!isset($match[3]) || $match[3] === '')
+ {
+ $match['authority'] = null;
+ }
+ if (!isset($match[5]))
+ {
+ $match['path'] = '';
+ }
+ if (!isset($match[6]) || $match[6] === '')
+ {
+ $match['query'] = null;
+ }
+ if (!isset($match[8]) || $match[8] === '')
+ {
+ $match['fragment'] = null;
+ }
+ return $match;
+ }
+ else
+ {
+ // This can occur when a paragraph is accidentally parsed as a URI
+ return false;
+ }
+ }
+
+ /**
+ * Remove dot segments from a path
+ *
+ * @param string $input
+ * @return string
+ */
+ protected function remove_dot_segments($input)
+ {
+ $output = '';
+ while (strpos($input, './') !== false || strpos($input, '/.') !== false || $input === '.' || $input === '..')
+ {
+ // A: If the input buffer begins with a prefix of "../" or "./", then remove that prefix from the input buffer; otherwise,
+ if (strpos($input, '../') === 0)
+ {
+ $input = substr($input, 3);
+ }
+ elseif (strpos($input, './') === 0)
+ {
+ $input = substr($input, 2);
+ }
+ // B: if the input buffer begins with a prefix of "/./" or "/.", where "." is a complete path segment, then replace that prefix with "/" in the input buffer; otherwise,
+ elseif (strpos($input, '/./') === 0)
+ {
+ $input = substr($input, 2);
+ }
+ elseif ($input === '/.')
+ {
+ $input = '/';
+ }
+ // C: if the input buffer begins with a prefix of "/../" or "/..", where ".." is a complete path segment, then replace that prefix with "/" in the input buffer and remove the last segment and its preceding "/" (if any) from the output buffer; otherwise,
+ elseif (strpos($input, '/../') === 0)
+ {
+ $input = substr($input, 3);
+ $output = substr_replace($output, '', strrpos($output, '/'));
+ }
+ elseif ($input === '/..')
+ {
+ $input = '/';
+ $output = substr_replace($output, '', strrpos($output, '/'));
+ }
+ // D: if the input buffer consists only of "." or "..", then remove that from the input buffer; otherwise,
+ elseif ($input === '.' || $input === '..')
+ {
+ $input = '';
+ }
+ // E: move the first path segment in the input buffer to the end of the output buffer, including the initial "/" character (if any) and any subsequent characters up to, but not including, the next "/" character or the end of the input buffer
+ elseif (($pos = strpos($input, '/', 1)) !== false)
+ {
+ $output .= substr($input, 0, $pos);
+ $input = substr_replace($input, '', 0, $pos);
+ }
+ else
+ {
+ $output .= $input;
+ $input = '';
+ }
+ }
+ return $output . $input;
+ }
+
+ /**
+ * Replace invalid character with percent encoding
+ *
+ * @param string $string Input string
+ * @param string $extra_chars Valid characters not in iunreserved or
+ * iprivate (this is ASCII-only)
+ * @param bool $iprivate Allow iprivate
+ * @return string
+ */
+ protected function replace_invalid_with_pct_encoding($string, $extra_chars, $iprivate = false)
+ {
+ // Normalize as many pct-encoded sections as possible
+ $string = preg_replace_callback('/(?:%[A-Fa-f0-9]{2})+/', array($this, 'remove_iunreserved_percent_encoded'), $string);
+
+ // Replace invalid percent characters
+ $string = preg_replace('/%(?![A-Fa-f0-9]{2})/', '%25', $string);
+
+ // Add unreserved and % to $extra_chars (the latter is safe because all
+ // pct-encoded sections are now valid).
+ $extra_chars .= 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-._~%';
+
+ // Now replace any bytes that aren't allowed with their pct-encoded versions
+ $position = 0;
+ $strlen = strlen($string);
+ while (($position += strspn($string, $extra_chars, $position)) < $strlen)
+ {
+ $value = ord($string[$position]);
+
+ // Start position
+ $start = $position;
+
+ // By default we are valid
+ $valid = true;
+
+ // No one byte sequences are valid due to the while.
+ // Two byte sequence:
+ if (($value & 0xE0) === 0xC0)
+ {
+ $character = ($value & 0x1F) << 6;
+ $length = 2;
+ $remaining = 1;
+ }
+ // Three byte sequence:
+ elseif (($value & 0xF0) === 0xE0)
+ {
+ $character = ($value & 0x0F) << 12;
+ $length = 3;
+ $remaining = 2;
+ }
+ // Four byte sequence:
+ elseif (($value & 0xF8) === 0xF0)
+ {
+ $character = ($value & 0x07) << 18;
+ $length = 4;
+ $remaining = 3;
+ }
+ // Invalid byte:
+ else
+ {
+ $valid = false;
+ $length = 1;
+ $remaining = 0;
+ }
+
+ if ($remaining)
+ {
+ if ($position + $length <= $strlen)
+ {
+ for ($position++; $remaining; $position++)
+ {
+ $value = ord($string[$position]);
+
+ // Check that the byte is valid, then add it to the character:
+ if (($value & 0xC0) === 0x80)
+ {
+ $character |= ($value & 0x3F) << (--$remaining * 6);
+ }
+ // If it is invalid, count the sequence as invalid and reprocess the current byte:
+ else
+ {
+ $valid = false;
+ $position--;
+ break;
+ }
+ }
+ }
+ else
+ {
+ $position = $strlen - 1;
+ $valid = false;
+ }
+ }
+
+ // Percent encode anything invalid or not in ucschar
+ if (
+ // Invalid sequences
+ !$valid
+ // Non-shortest form sequences are invalid
+ || $length > 1 && $character <= 0x7F
+ || $length > 2 && $character <= 0x7FF
+ || $length > 3 && $character <= 0xFFFF
+ // Outside of range of ucschar codepoints
+ // Noncharacters
+ || ($character & 0xFFFE) === 0xFFFE
+ || $character >= 0xFDD0 && $character <= 0xFDEF
+ || (
+ // Everything else not in ucschar
+ $character > 0xD7FF && $character < 0xF900
+ || $character < 0xA0
+ || $character > 0xEFFFD
+ )
+ && (
+ // Everything not in iprivate, if it applies
+ !$iprivate
+ || $character < 0xE000
+ || $character > 0x10FFFD
+ )
+ )
+ {
+ // If we were a character, pretend we weren't, but rather an error.
+ if ($valid)
+ $position--;
+
+ for ($j = $start; $j <= $position; $j++)
+ {
+ $string = substr_replace($string, sprintf('%%%02X', ord($string[$j])), $j, 1);
+ $j += 2;
+ $position += 2;
+ $strlen += 2;
+ }
+ }
+ }
+
+ return $string;
+ }
+
+ /**
+ * Callback function for preg_replace_callback.
+ *
+ * Removes sequences of percent encoded bytes that represent UTF-8
+ * encoded characters in iunreserved
+ *
+ * @param array $match PCRE match
+ * @return string Replacement
+ */
+ protected function remove_iunreserved_percent_encoded($match)
+ {
+ // As we just have valid percent encoded sequences we can just explode
+ // and ignore the first member of the returned array (an empty string).
+ $bytes = explode('%', $match[0]);
+
+ // Initialize the new string (this is what will be returned) and that
+ // there are no bytes remaining in the current sequence (unsurprising
+ // at the first byte!).
+ $string = '';
+ $remaining = 0;
+
+ // Loop over each and every byte, and set $value to its value
+ for ($i = 1, $len = count($bytes); $i < $len; $i++)
+ {
+ $value = hexdec($bytes[$i]);
+
+ // If we're the first byte of sequence:
+ if (!$remaining)
+ {
+ // Start position
+ $start = $i;
+
+ // By default we are valid
+ $valid = true;
+
+ // One byte sequence:
+ if ($value <= 0x7F)
+ {
+ $character = $value;
+ $length = 1;
+ }
+ // Two byte sequence:
+ elseif (($value & 0xE0) === 0xC0)
+ {
+ $character = ($value & 0x1F) << 6;
+ $length = 2;
+ $remaining = 1;
+ }
+ // Three byte sequence:
+ elseif (($value & 0xF0) === 0xE0)
+ {
+ $character = ($value & 0x0F) << 12;
+ $length = 3;
+ $remaining = 2;
+ }
+ // Four byte sequence:
+ elseif (($value & 0xF8) === 0xF0)
+ {
+ $character = ($value & 0x07) << 18;
+ $length = 4;
+ $remaining = 3;
+ }
+ // Invalid byte:
+ else
+ {
+ $valid = false;
+ $remaining = 0;
+ }
+ }
+ // Continuation byte:
+ else
+ {
+ // Check that the byte is valid, then add it to the character:
+ if (($value & 0xC0) === 0x80)
+ {
+ $remaining--;
+ $character |= ($value & 0x3F) << ($remaining * 6);
+ }
+ // If it is invalid, count the sequence as invalid and reprocess the current byte as the start of a sequence:
+ else
+ {
+ $valid = false;
+ $remaining = 0;
+ $i--;
+ }
+ }
+
+ // If we've reached the end of the current byte sequence, append it to Unicode::$data
+ if (!$remaining)
+ {
+ // Percent encode anything invalid or not in iunreserved
+ if (
+ // Invalid sequences
+ !$valid
+ // Non-shortest form sequences are invalid
+ || $length > 1 && $character <= 0x7F
+ || $length > 2 && $character <= 0x7FF
+ || $length > 3 && $character <= 0xFFFF
+ // Outside of range of iunreserved codepoints
+ || $character < 0x2D
+ || $character > 0xEFFFD
+ // Noncharacters
+ || ($character & 0xFFFE) === 0xFFFE
+ || $character >= 0xFDD0 && $character <= 0xFDEF
+ // Everything else not in iunreserved (this is all BMP)
+ || $character === 0x2F
+ || $character > 0x39 && $character < 0x41
+ || $character > 0x5A && $character < 0x61
+ || $character > 0x7A && $character < 0x7E
+ || $character > 0x7E && $character < 0xA0
+ || $character > 0xD7FF && $character < 0xF900
+ )
+ {
+ for ($j = $start; $j <= $i; $j++)
+ {
+ $string .= '%' . strtoupper($bytes[$j]);
+ }
+ }
+ else
+ {
+ for ($j = $start; $j <= $i; $j++)
+ {
+ $string .= chr(hexdec($bytes[$j]));
+ }
+ }
+ }
+ }
+
+ // If we have any bytes left over they are invalid (i.e., we are
+ // mid-way through a multi-byte sequence)
+ if ($remaining)
+ {
+ for ($j = $start; $j < $len; $j++)
+ {
+ $string .= '%' . strtoupper($bytes[$j]);
+ }
+ }
+
+ return $string;
+ }
+
+ protected function scheme_normalization()
+ {
+ if (isset($this->normalization[$this->scheme]['iuserinfo']) && $this->iuserinfo === $this->normalization[$this->scheme]['iuserinfo'])
+ {
+ $this->iuserinfo = null;
+ }
+ if (isset($this->normalization[$this->scheme]['ihost']) && $this->ihost === $this->normalization[$this->scheme]['ihost'])
+ {
+ $this->ihost = null;
+ }
+ if (isset($this->normalization[$this->scheme]['port']) && $this->port === $this->normalization[$this->scheme]['port'])
+ {
+ $this->port = null;
+ }
+ if (isset($this->normalization[$this->scheme]['ipath']) && $this->ipath === $this->normalization[$this->scheme]['ipath'])
+ {
+ $this->ipath = '';
+ }
+ if (isset($this->normalization[$this->scheme]['iquery']) && $this->iquery === $this->normalization[$this->scheme]['iquery'])
+ {
+ $this->iquery = null;
+ }
+ if (isset($this->normalization[$this->scheme]['ifragment']) && $this->ifragment === $this->normalization[$this->scheme]['ifragment'])
+ {
+ $this->ifragment = null;
+ }
+ }
+
+ /**
+ * Check if the object represents a valid IRI. This needs to be done on each
+ * call as some things change depending on another part of the IRI.
+ *
+ * @return bool
+ */
+ public function is_valid()
+ {
+ if ($this->ipath === '') return true;
+
+ $isauthority = $this->iuserinfo !== null || $this->ihost !== null ||
+ $this->port !== null;
+ if ($isauthority && $this->ipath[0] === '/') return true;
+
+ if (!$isauthority && (substr($this->ipath, 0, 2) === '//')) return false;
+
+ // Relative urls cannot have a colon in the first path segment (and the
+ // slashes themselves are not included so skip the first character).
+ if (!$this->scheme && !$isauthority &&
+ strpos($this->ipath, ':') !== false &&
+ strpos($this->ipath, '/', 1) !== false &&
+ strpos($this->ipath, ':') < strpos($this->ipath, '/', 1)) return false;
+
+ return true;
+ }
+
+ /**
+ * Set the entire IRI. Returns true on success, false on failure (if there
+ * are any invalid characters).
+ *
+ * @param string $iri
+ * @return bool
+ */
+ public function set_iri($iri, $clear_cache = false)
+ {
+ static $cache;
+ if ($clear_cache)
+ {
+ $cache = null;
+ return;
+ }
+ if (!$cache)
+ {
+ $cache = array();
+ }
+
+ if ($iri === null)
+ {
+ return true;
+ }
+ elseif (isset($cache[$iri]))
+ {
+ list($this->scheme,
+ $this->iuserinfo,
+ $this->ihost,
+ $this->port,
+ $this->ipath,
+ $this->iquery,
+ $this->ifragment,
+ $return) = $cache[$iri];
+ return $return;
+ }
+ else
+ {
+ $parsed = $this->parse_iri((string) $iri);
+ if (!$parsed)
+ {
+ return false;
+ }
+
+ $return = $this->set_scheme($parsed['scheme'])
+ && $this->set_authority($parsed['authority'])
+ && $this->set_path($parsed['path'])
+ && $this->set_query($parsed['query'])
+ && $this->set_fragment($parsed['fragment']);
+
+ $cache[$iri] = array($this->scheme,
+ $this->iuserinfo,
+ $this->ihost,
+ $this->port,
+ $this->ipath,
+ $this->iquery,
+ $this->ifragment,
+ $return);
+ return $return;
+ }
+ }
+
+ /**
+ * Set the scheme. Returns true on success, false on failure (if there are
+ * any invalid characters).
+ *
+ * @param string $scheme
+ * @return bool
+ */
+ public function set_scheme($scheme)
+ {
+ if ($scheme === null)
+ {
+ $this->scheme = null;
+ }
+ elseif (!preg_match('/^[A-Za-z][0-9A-Za-z+\-.]*$/', $scheme))
+ {
+ $this->scheme = null;
+ return false;
+ }
+ else
+ {
+ $this->scheme = strtolower($scheme);
+ }
+ return true;
+ }
+
+ /**
+ * Set the authority. Returns true on success, false on failure (if there are
+ * any invalid characters).
+ *
+ * @param string $authority
+ * @return bool
+ */
+ public function set_authority($authority, $clear_cache = false)
+ {
+ static $cache;
+ if ($clear_cache)
+ {
+ $cache = null;
+ return;
+ }
+ if (!$cache)
+ $cache = array();
+
+ if ($authority === null)
+ {
+ $this->iuserinfo = null;
+ $this->ihost = null;
+ $this->port = null;
+ return true;
+ }
+ elseif (isset($cache[$authority]))
+ {
+ list($this->iuserinfo,
+ $this->ihost,
+ $this->port,
+ $return) = $cache[$authority];
+
+ return $return;
+ }
+ else
+ {
+ $remaining = $authority;
+ if (($iuserinfo_end = strrpos($remaining, '@')) !== false)
+ {
+ $iuserinfo = substr($remaining, 0, $iuserinfo_end);
+ $remaining = substr($remaining, $iuserinfo_end + 1);
+ }
+ else
+ {
+ $iuserinfo = null;
+ }
+ if (($port_start = strpos($remaining, ':', strpos($remaining, ']'))) !== false)
+ {
+ if (($port = substr($remaining, $port_start + 1)) === false)
+ {
+ $port = null;
+ }
+ $remaining = substr($remaining, 0, $port_start);
+ }
+ else
+ {
+ $port = null;
+ }
+
+ $return = $this->set_userinfo($iuserinfo) &&
+ $this->set_host($remaining) &&
+ $this->set_port($port);
+
+ $cache[$authority] = array($this->iuserinfo,
+ $this->ihost,
+ $this->port,
+ $return);
+
+ return $return;
+ }
+ }
+
+ /**
+ * Set the iuserinfo.
+ *
+ * @param string $iuserinfo
+ * @return bool
+ */
+ public function set_userinfo($iuserinfo)
+ {
+ if ($iuserinfo === null)
+ {
+ $this->iuserinfo = null;
+ }
+ else
+ {
+ $this->iuserinfo = $this->replace_invalid_with_pct_encoding($iuserinfo, '!$&\'()*+,;=:');
+ $this->scheme_normalization();
+ }
+
+ return true;
+ }
+
+ /**
+ * Set the ihost. Returns true on success, false on failure (if there are
+ * any invalid characters).
+ *
+ * @param string $ihost
+ * @return bool
+ */
+ public function set_host($ihost)
+ {
+ if ($ihost === null)
+ {
+ $this->ihost = null;
+ return true;
+ }
+ elseif (substr($ihost, 0, 1) === '[' && substr($ihost, -1) === ']')
+ {
+ if (SimplePie_Net_IPv6::check_ipv6(substr($ihost, 1, -1)))
+ {
+ $this->ihost = '[' . SimplePie_Net_IPv6::compress(substr($ihost, 1, -1)) . ']';
+ }
+ else
+ {
+ $this->ihost = null;
+ return false;
+ }
+ }
+ else
+ {
+ $ihost = $this->replace_invalid_with_pct_encoding($ihost, '!$&\'()*+,;=');
+
+ // Lowercase, but ignore pct-encoded sections (as they should
+ // remain uppercase). This must be done after the previous step
+ // as that can add unescaped characters.
+ $position = 0;
+ $strlen = strlen($ihost);
+ while (($position += strcspn($ihost, 'ABCDEFGHIJKLMNOPQRSTUVWXYZ%', $position)) < $strlen)
+ {
+ if ($ihost[$position] === '%')
+ {
+ $position += 3;
+ }
+ else
+ {
+ $ihost[$position] = strtolower($ihost[$position]);
+ $position++;
+ }
+ }
+
+ $this->ihost = $ihost;
+ }
+
+ $this->scheme_normalization();
+
+ return true;
+ }
+
+ /**
+ * Set the port. Returns true on success, false on failure (if there are
+ * any invalid characters).
+ *
+ * @param string $port
+ * @return bool
+ */
+ public function set_port($port)
+ {
+ if ($port === null)
+ {
+ $this->port = null;
+ return true;
+ }
+ elseif (strspn($port, '0123456789') === strlen($port))
+ {
+ $this->port = (int) $port;
+ $this->scheme_normalization();
+ return true;
+ }
+ else
+ {
+ $this->port = null;
+ return false;
+ }
+ }
+
+ /**
+ * Set the ipath.
+ *
+ * @param string $ipath
+ * @return bool
+ */
+ public function set_path($ipath, $clear_cache = false)
+ {
+ static $cache;
+ if ($clear_cache)
+ {
+ $cache = null;
+ return;
+ }
+ if (!$cache)
+ {
+ $cache = array();
+ }
+
+ $ipath = (string) $ipath;
+
+ if (isset($cache[$ipath]))
+ {
+ $this->ipath = $cache[$ipath][(int) ($this->scheme !== null)];
+ }
+ else
+ {
+ $valid = $this->replace_invalid_with_pct_encoding($ipath, '!$&\'()*+,;=@:/');
+ $removed = $this->remove_dot_segments($valid);
+
+ $cache[$ipath] = array($valid, $removed);
+ $this->ipath = ($this->scheme !== null) ? $removed : $valid;
+ }
+
+ $this->scheme_normalization();
+ return true;
+ }
+
+ /**
+ * Set the iquery.
+ *
+ * @param string $iquery
+ * @return bool
+ */
+ public function set_query($iquery)
+ {
+ if ($iquery === null)
+ {
+ $this->iquery = null;
+ }
+ else
+ {
+ $this->iquery = $this->replace_invalid_with_pct_encoding($iquery, '!$&\'()*+,;=:@/?', true);
+ $this->scheme_normalization();
+ }
+ return true;
+ }
+
+ /**
+ * Set the ifragment.
+ *
+ * @param string $ifragment
+ * @return bool
+ */
+ public function set_fragment($ifragment)
+ {
+ if ($ifragment === null)
+ {
+ $this->ifragment = null;
+ }
+ else
+ {
+ $this->ifragment = $this->replace_invalid_with_pct_encoding($ifragment, '!$&\'()*+,;=:@/?');
+ $this->scheme_normalization();
+ }
+ return true;
+ }
+
+ /**
+ * Convert an IRI to a URI (or parts thereof)
+ *
+ * @return string
+ */
+ public function to_uri($string)
+ {
+ static $non_ascii;
+ if (!$non_ascii)
+ {
+ $non_ascii = implode('', range("\x80", "\xFF"));
+ }
+
+ $position = 0;
+ $strlen = strlen($string);
+ while (($position += strcspn($string, $non_ascii, $position)) < $strlen)
+ {
+ $string = substr_replace($string, sprintf('%%%02X', ord($string[$position])), $position, 1);
+ $position += 3;
+ $strlen += 2;
+ }
+
+ return $string;
+ }
+
+ /**
+ * Get the complete IRI
+ *
+ * @return string
+ */
+ public function get_iri()
+ {
+ if (!$this->is_valid())
+ {
+ return false;
+ }
+
+ $iri = '';
+ if ($this->scheme !== null)
+ {
+ $iri .= $this->scheme . ':';
+ }
+ if (($iauthority = $this->get_iauthority()) !== null)
+ {
+ $iri .= '//' . $iauthority;
+ }
+ if ($this->ipath !== '')
+ {
+ $iri .= $this->ipath;
+ }
+ elseif (!empty($this->normalization[$this->scheme]['ipath']) && $iauthority !== null && $iauthority !== '')
+ {
+ $iri .= $this->normalization[$this->scheme]['ipath'];
+ }
+ if ($this->iquery !== null)
+ {
+ $iri .= '?' . $this->iquery;
+ }
+ if ($this->ifragment !== null)
+ {
+ $iri .= '#' . $this->ifragment;
+ }
+
+ return $iri;
+ }
+
+ /**
+ * Get the complete URI
+ *
+ * @return string
+ */
+ public function get_uri()
+ {
+ return $this->to_uri($this->get_iri());
+ }
+
+ /**
+ * Get the complete iauthority
+ *
+ * @return string
+ */
+ protected function get_iauthority()
+ {
+ if ($this->iuserinfo !== null || $this->ihost !== null || $this->port !== null)
+ {
+ $iauthority = '';
+ if ($this->iuserinfo !== null)
+ {
+ $iauthority .= $this->iuserinfo . '@';
+ }
+ if ($this->ihost !== null)
+ {
+ $iauthority .= $this->ihost;
+ }
+ if ($this->port !== null)
+ {
+ $iauthority .= ':' . $this->port;
+ }
+ return $iauthority;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the complete authority
+ *
+ * @return string
+ */
+ protected function get_authority()
+ {
+ $iauthority = $this->get_iauthority();
+ if (is_string($iauthority))
+ return $this->to_uri($iauthority);
+ else
+ return $iauthority;
+ }
+}
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Item.php b/vendor/simplepie/simplepie/library/SimplePie/Item.php
new file mode 100644
index 000000000..00f4179bf
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Item.php
@@ -0,0 +1,3009 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+
+/**
+ * Manages all item-related data
+ *
+ * Used by {@see SimplePie::get_item()} and {@see SimplePie::get_items()}
+ *
+ * This class can be overloaded with {@see SimplePie::set_item_class()}
+ *
+ * @package SimplePie
+ * @subpackage API
+ */
+class SimplePie_Item
+{
+ /**
+ * Parent feed
+ *
+ * @access private
+ * @var SimplePie
+ */
+ var $feed;
+
+ /**
+ * Raw data
+ *
+ * @access private
+ * @var array
+ */
+ var $data = array();
+
+ /**
+ * Registry object
+ *
+ * @see set_registry
+ * @var SimplePie_Registry
+ */
+ protected $registry;
+
+ /**
+ * Create a new item object
+ *
+ * This is usually used by {@see SimplePie::get_items} and
+ * {@see SimplePie::get_item}. Avoid creating this manually.
+ *
+ * @param SimplePie $feed Parent feed
+ * @param array $data Raw data
+ */
+ public function __construct($feed, $data)
+ {
+ $this->feed = $feed;
+ $this->data = $data;
+ }
+
+ /**
+ * Set the registry handler
+ *
+ * This is usually used by {@see SimplePie_Registry::create}
+ *
+ * @since 1.3
+ * @param SimplePie_Registry $registry
+ */
+ public function set_registry(SimplePie_Registry $registry)
+ {
+ $this->registry = $registry;
+ }
+
+ /**
+ * Get a string representation of the item
+ *
+ * @return string
+ */
+ public function __toString()
+ {
+ return md5(serialize($this->data));
+ }
+
+ /**
+ * Remove items that link back to this before destroying this object
+ */
+ public function __destruct()
+ {
+ if ((version_compare(PHP_VERSION, '5.3', '<') || !gc_enabled()) && !ini_get('zend.ze1_compatibility_mode'))
+ {
+ unset($this->feed);
+ }
+ }
+
+ /**
+ * Get data for an item-level element
+ *
+ * This method allows you to get access to ANY element/attribute that is a
+ * sub-element of the item/entry tag.
+ *
+ * See {@see SimplePie::get_feed_tags()} for a description of the return value
+ *
+ * @since 1.0
+ * @see http://simplepie.org/wiki/faq/supported_xml_namespaces
+ * @param string $namespace The URL of the XML namespace of the elements you're trying to access
+ * @param string $tag Tag name
+ * @return array
+ */
+ public function get_item_tags($namespace, $tag)
+ {
+ if (isset($this->data['child'][$namespace][$tag]))
+ {
+ return $this->data['child'][$namespace][$tag];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the base URL value from the parent feed
+ *
+ * Uses `<xml:base>`
+ *
+ * @param array $element
+ * @return string
+ */
+ public function get_base($element = array())
+ {
+ return $this->feed->get_base($element);
+ }
+
+ /**
+ * Sanitize feed data
+ *
+ * @access private
+ * @see SimplePie::sanitize()
+ * @param string $data Data to sanitize
+ * @param int $type One of the SIMPLEPIE_CONSTRUCT_* constants
+ * @param string $base Base URL to resolve URLs against
+ * @return string Sanitized data
+ */
+ public function sanitize($data, $type, $base = '')
+ {
+ return $this->feed->sanitize($data, $type, $base);
+ }
+
+ /**
+ * Get the parent feed
+ *
+ * Note: this may not work as you think for multifeeds!
+ *
+ * @link http://simplepie.org/faq/typical_multifeed_gotchas#missing_data_from_feed
+ * @since 1.0
+ * @return SimplePie
+ */
+ public function get_feed()
+ {
+ return $this->feed;
+ }
+
+ /**
+ * Get the unique identifier for the item
+ *
+ * This is usually used when writing code to check for new items in a feed.
+ *
+ * Uses `<atom:id>`, `<guid>`, `<dc:identifier>` or the `about` attribute
+ * for RDF. If none of these are supplied (or `$hash` is true), creates an
+ * MD5 hash based on the permalink, title and content.
+ *
+ * @since Beta 2
+ * @param boolean $hash Should we force using a hash instead of the supplied ID?
+ * @param string|false $fn User-supplied function to generate an hash
+ * @return string|null
+ */
+ public function get_id($hash = false, $fn = 'md5')
+ {
+ if (!$hash)
+ {
+ if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'id'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'id'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'guid'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_11, 'identifier'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_10, 'identifier'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif (isset($this->data['attribs'][SIMPLEPIE_NAMESPACE_RDF]['about']))
+ {
+ return $this->sanitize($this->data['attribs'][SIMPLEPIE_NAMESPACE_RDF]['about'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ }
+ if ($fn === false)
+ {
+ return null;
+ }
+ elseif (!is_callable($fn))
+ {
+ trigger_error('User-supplied function $fn must be callable', E_USER_WARNING);
+ $fn = 'md5';
+ }
+ return call_user_func($fn,
+ $this->get_permalink().$this->get_title().$this->get_content());
+ }
+
+ /**
+ * Get the title of the item
+ *
+ * Uses `<atom:title>`, `<title>` or `<dc:title>`
+ *
+ * @since Beta 2 (previously called `get_item_title` since 0.8)
+ * @return string|null
+ */
+ public function get_title()
+ {
+ if (!isset($this->data['title']))
+ {
+ if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'title'))
+ {
+ $this->data['title'] = $this->sanitize($return[0]['data'], $this->registry->call('Misc', 'atom_10_construct_type', array($return[0]['attribs'])), $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'title'))
+ {
+ $this->data['title'] = $this->sanitize($return[0]['data'], $this->registry->call('Misc', 'atom_03_construct_type', array($return[0]['attribs'])), $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'title'))
+ {
+ $this->data['title'] = $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'title'))
+ {
+ $this->data['title'] = $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'title'))
+ {
+ $this->data['title'] = $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_11, 'title'))
+ {
+ $this->data['title'] = $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_10, 'title'))
+ {
+ $this->data['title'] = $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $this->data['title'] = null;
+ }
+ }
+ return $this->data['title'];
+ }
+
+ /**
+ * Get the content for the item
+ *
+ * Prefers summaries over full content , but will return full content if a
+ * summary does not exist.
+ *
+ * To prefer full content instead, use {@see get_content}
+ *
+ * Uses `<atom:summary>`, `<description>`, `<dc:description>` or
+ * `<itunes:subtitle>`
+ *
+ * @since 0.8
+ * @param boolean $description_only Should we avoid falling back to the content?
+ * @return string|null
+ */
+ public function get_description($description_only = false)
+ {
+ if (($tags = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'summary')) &&
+ ($return = $this->sanitize($tags[0]['data'], $this->registry->call('Misc', 'atom_10_construct_type', array($tags[0]['attribs'])), $this->get_base($tags[0]))))
+ {
+ return $return;
+ }
+ elseif (($tags = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'summary')) &&
+ ($return = $this->sanitize($tags[0]['data'], $this->registry->call('Misc', 'atom_03_construct_type', array($tags[0]['attribs'])), $this->get_base($tags[0]))))
+ {
+ return $return;
+ }
+ elseif (($tags = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'description')) &&
+ ($return = $this->sanitize($tags[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($tags[0]))))
+ {
+ return $return;
+ }
+ elseif (($tags = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'description')) &&
+ ($return = $this->sanitize($tags[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($tags[0]))))
+ {
+ return $return;
+ }
+ elseif (($tags = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_11, 'description')) &&
+ ($return = $this->sanitize($tags[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT)))
+ {
+ return $return;
+ }
+ elseif (($tags = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_10, 'description')) &&
+ ($return = $this->sanitize($tags[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT)))
+ {
+ return $return;
+ }
+ elseif (($tags = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'summary')) &&
+ ($return = $this->sanitize($tags[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($tags[0]))))
+ {
+ return $return;
+ }
+ elseif (($tags = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'subtitle')) &&
+ ($return = $this->sanitize($tags[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT)))
+ {
+ return $return;
+ }
+ elseif (($tags = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'description')) &&
+ ($return = $this->sanitize($tags[0]['data'], SIMPLEPIE_CONSTRUCT_HTML)))
+ {
+ return $return;
+ }
+
+ elseif (!$description_only)
+ {
+ return $this->get_content(true);
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the content for the item
+ *
+ * Prefers full content over summaries, but will return a summary if full
+ * content does not exist.
+ *
+ * To prefer summaries instead, use {@see get_description}
+ *
+ * Uses `<atom:content>` or `<content:encoded>` (RSS 1.0 Content Module)
+ *
+ * @since 1.0
+ * @param boolean $content_only Should we avoid falling back to the description?
+ * @return string|null
+ */
+ public function get_content($content_only = false)
+ {
+ if (($tags = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'content')) &&
+ ($return = $this->sanitize($tags[0]['data'], $this->registry->call('Misc', 'atom_10_content_construct_type', array($tags[0]['attribs'])), $this->get_base($tags[0]))))
+ {
+ return $return;
+ }
+ elseif (($tags = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'content')) &&
+ ($return = $this->sanitize($tags[0]['data'], $this->registry->call('Misc', 'atom_03_construct_type', array($tags[0]['attribs'])), $this->get_base($tags[0]))))
+ {
+ return $return;
+ }
+ elseif (($tags = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_10_MODULES_CONTENT, 'encoded')) &&
+ ($return = $this->sanitize($tags[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($tags[0]))))
+ {
+ return $return;
+ }
+ elseif (!$content_only)
+ {
+ return $this->get_description(true);
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the media:thumbnail of the item
+ *
+ * Uses `<media:thumbnail>`
+ *
+ *
+ * @return array|null
+ */
+ public function get_thumbnail()
+ {
+ if (!isset($this->data['thumbnail']))
+ {
+ if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'thumbnail'))
+ {
+ $this->data['thumbnail'] = $return[0]['attribs'][''];
+ }
+ else
+ {
+ $this->data['thumbnail'] = null;
+ }
+ }
+ return $this->data['thumbnail'];
+ }
+
+ /**
+ * Get a category for the item
+ *
+ * @since Beta 3 (previously called `get_categories()` since Beta 2)
+ * @param int $key The category that you want to return. Remember that arrays begin with 0, not 1
+ * @return SimplePie_Category|null
+ */
+ public function get_category($key = 0)
+ {
+ $categories = $this->get_categories();
+ if (isset($categories[$key]))
+ {
+ return $categories[$key];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get all categories for the item
+ *
+ * Uses `<atom:category>`, `<category>` or `<dc:subject>`
+ *
+ * @since Beta 3
+ * @return SimplePie_Category[]|null List of {@see SimplePie_Category} objects
+ */
+ public function get_categories()
+ {
+ $categories = array();
+
+ $type = 'category';
+ foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, $type) as $category)
+ {
+ $term = null;
+ $scheme = null;
+ $label = null;
+ if (isset($category['attribs']['']['term']))
+ {
+ $term = $this->sanitize($category['attribs']['']['term'], SIMPLEPIE_CONSTRUCT_HTML);
+ }
+ if (isset($category['attribs']['']['scheme']))
+ {
+ $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_HTML);
+ }
+ if (isset($category['attribs']['']['label']))
+ {
+ $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_HTML);
+ }
+ $categories[] = $this->registry->create('Category', array($term, $scheme, $label, $type));
+ }
+ foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, $type) as $category)
+ {
+ // This is really the label, but keep this as the term also for BC.
+ // Label will also work on retrieving because that falls back to term.
+ $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_HTML);
+ if (isset($category['attribs']['']['domain']))
+ {
+ $scheme = $this->sanitize($category['attribs']['']['domain'], SIMPLEPIE_CONSTRUCT_HTML);
+ }
+ else
+ {
+ $scheme = null;
+ }
+ $categories[] = $this->registry->create('Category', array($term, $scheme, null, $type));
+ }
+
+ $type = 'subject';
+ foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_11, $type) as $category)
+ {
+ $categories[] = $this->registry->create('Category', array($this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_HTML), null, null, $type));
+ }
+ foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_10, $type) as $category)
+ {
+ $categories[] = $this->registry->create('Category', array($this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_HTML), null, null, $type));
+ }
+
+ if (!empty($categories))
+ {
+ return array_unique($categories);
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get an author for the item
+ *
+ * @since Beta 2
+ * @param int $key The author that you want to return. Remember that arrays begin with 0, not 1
+ * @return SimplePie_Author|null
+ */
+ public function get_author($key = 0)
+ {
+ $authors = $this->get_authors();
+ if (isset($authors[$key]))
+ {
+ return $authors[$key];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get a contributor for the item
+ *
+ * @since 1.1
+ * @param int $key The contrbutor that you want to return. Remember that arrays begin with 0, not 1
+ * @return SimplePie_Author|null
+ */
+ public function get_contributor($key = 0)
+ {
+ $contributors = $this->get_contributors();
+ if (isset($contributors[$key]))
+ {
+ return $contributors[$key];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get all contributors for the item
+ *
+ * Uses `<atom:contributor>`
+ *
+ * @since 1.1
+ * @return array|null List of {@see SimplePie_Author} objects
+ */
+ public function get_contributors()
+ {
+ $contributors = array();
+ foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'contributor') as $contributor)
+ {
+ $name = null;
+ $uri = null;
+ $email = null;
+ if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data']))
+ {
+ $name = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data']))
+ {
+ $uri = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]));
+ }
+ if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data']))
+ {
+ $email = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if ($name !== null || $email !== null || $uri !== null)
+ {
+ $contributors[] = $this->registry->create('Author', array($name, $uri, $email));
+ }
+ }
+ foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'contributor') as $contributor)
+ {
+ $name = null;
+ $url = null;
+ $email = null;
+ if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data']))
+ {
+ $name = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data']))
+ {
+ $url = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]));
+ }
+ if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data']))
+ {
+ $email = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if ($name !== null || $email !== null || $url !== null)
+ {
+ $contributors[] = $this->registry->create('Author', array($name, $url, $email));
+ }
+ }
+
+ if (!empty($contributors))
+ {
+ return array_unique($contributors);
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get all authors for the item
+ *
+ * Uses `<atom:author>`, `<author>`, `<dc:creator>` or `<itunes:author>`
+ *
+ * @since Beta 2
+ * @return array|null List of {@see SimplePie_Author} objects
+ */
+ public function get_authors()
+ {
+ $authors = array();
+ foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'author') as $author)
+ {
+ $name = null;
+ $uri = null;
+ $email = null;
+ if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data']))
+ {
+ $name = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_HTML);
+ }
+ if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data']))
+ {
+ $uri = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]));
+ }
+ if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data']))
+ {
+ $email = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_HTML);
+ }
+ if ($name !== null || $email !== null || $uri !== null)
+ {
+ $authors[] = $this->registry->create('Author', array($name, $uri, $email));
+ }
+ }
+ if ($author = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'author'))
+ {
+ $name = null;
+ $url = null;
+ $email = null;
+ if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data']))
+ {
+ $name = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_HTML);
+ }
+ if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data']))
+ {
+ $url = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]));
+ }
+ if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data']))
+ {
+ $email = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_HTML);
+ }
+ if ($name !== null || $email !== null || $url !== null)
+ {
+ $authors[] = $this->registry->create('Author', array($name, $url, $email));
+ }
+ }
+ if ($author = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'author'))
+ {
+ $authors[] = $this->registry->create('Author', array(null, null, $this->sanitize($author[0]['data'], SIMPLEPIE_CONSTRUCT_HTML)));
+ }
+ foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_11, 'creator') as $author)
+ {
+ $authors[] = $this->registry->create('Author', array($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_HTML), null, null));
+ }
+ foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_10, 'creator') as $author)
+ {
+ $authors[] = $this->registry->create('Author', array($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_HTML), null, null));
+ }
+ foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'author') as $author)
+ {
+ $authors[] = $this->registry->create('Author', array($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_HTML), null, null));
+ }
+
+ if (!empty($authors))
+ {
+ return array_unique($authors);
+ }
+ elseif (($source = $this->get_source()) && ($authors = $source->get_authors()))
+ {
+ return $authors;
+ }
+ elseif ($authors = $this->feed->get_authors())
+ {
+ return $authors;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the copyright info for the item
+ *
+ * Uses `<atom:rights>` or `<dc:rights>`
+ *
+ * @since 1.1
+ * @return string
+ */
+ public function get_copyright()
+ {
+ if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'rights'))
+ {
+ return $this->sanitize($return[0]['data'], $this->registry->call('Misc', 'atom_10_construct_type', array($return[0]['attribs'])), $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_11, 'rights'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_10, 'rights'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the posting date/time for the item
+ *
+ * Uses `<atom:published>`, `<atom:updated>`, `<atom:issued>`,
+ * `<atom:modified>`, `<pubDate>` or `<dc:date>`
+ *
+ * Note: obeys PHP's timezone setting. To get a UTC date/time, use
+ * {@see get_gmdate}
+ *
+ * @since Beta 2 (previously called `get_item_date` since 0.8)
+ *
+ * @param string $date_format Supports any PHP date format from {@see http://php.net/date} (empty for the raw data)
+ * @return int|string|null
+ */
+ public function get_date($date_format = 'j F Y, g:i a')
+ {
+ if (!isset($this->data['date']))
+ {
+ if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'published'))
+ {
+ $this->data['date']['raw'] = $return[0]['data'];
+ }
+ elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'pubDate'))
+ {
+ $this->data['date']['raw'] = $return[0]['data'];
+ }
+ elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_11, 'date'))
+ {
+ $this->data['date']['raw'] = $return[0]['data'];
+ }
+ elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_DC_10, 'date'))
+ {
+ $this->data['date']['raw'] = $return[0]['data'];
+ }
+ elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'updated'))
+ {
+ $this->data['date']['raw'] = $return[0]['data'];
+ }
+ elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'issued'))
+ {
+ $this->data['date']['raw'] = $return[0]['data'];
+ }
+ elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'created'))
+ {
+ $this->data['date']['raw'] = $return[0]['data'];
+ }
+ elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'modified'))
+ {
+ $this->data['date']['raw'] = $return[0]['data'];
+ }
+
+ if (!empty($this->data['date']['raw']))
+ {
+ $parser = $this->registry->call('Parse_Date', 'get');
+ $this->data['date']['parsed'] = $parser->parse($this->data['date']['raw']);
+ }
+ else
+ {
+ $this->data['date'] = null;
+ }
+ }
+ if ($this->data['date'])
+ {
+ $date_format = (string) $date_format;
+ switch ($date_format)
+ {
+ case '':
+ return $this->sanitize($this->data['date']['raw'], SIMPLEPIE_CONSTRUCT_TEXT);
+
+ case 'U':
+ return $this->data['date']['parsed'];
+
+ default:
+ return date($date_format, $this->data['date']['parsed']);
+ }
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the update date/time for the item
+ *
+ * Uses `<atom:updated>`
+ *
+ * Note: obeys PHP's timezone setting. To get a UTC date/time, use
+ * {@see get_gmdate}
+ *
+ * @param string $date_format Supports any PHP date format from {@see http://php.net/date} (empty for the raw data)
+ * @return int|string|null
+ */
+ public function get_updated_date($date_format = 'j F Y, g:i a')
+ {
+ if (!isset($this->data['updated']))
+ {
+ if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'updated'))
+ {
+ $this->data['updated']['raw'] = $return[0]['data'];
+ }
+
+ if (!empty($this->data['updated']['raw']))
+ {
+ $parser = $this->registry->call('Parse_Date', 'get');
+ $this->data['updated']['parsed'] = $parser->parse($this->data['updated']['raw']);
+ }
+ else
+ {
+ $this->data['updated'] = null;
+ }
+ }
+ if ($this->data['updated'])
+ {
+ $date_format = (string) $date_format;
+ switch ($date_format)
+ {
+ case '':
+ return $this->sanitize($this->data['updated']['raw'], SIMPLEPIE_CONSTRUCT_TEXT);
+
+ case 'U':
+ return $this->data['updated']['parsed'];
+
+ default:
+ return date($date_format, $this->data['updated']['parsed']);
+ }
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the localized posting date/time for the item
+ *
+ * Returns the date formatted in the localized language. To display in
+ * languages other than the server's default, you need to change the locale
+ * with {@link http://php.net/setlocale setlocale()}. The available
+ * localizations depend on which ones are installed on your web server.
+ *
+ * @since 1.0
+ *
+ * @param string $date_format Supports any PHP date format from {@see http://php.net/strftime} (empty for the raw data)
+ * @return int|string|null
+ */
+ public function get_local_date($date_format = '%c')
+ {
+ if (!$date_format)
+ {
+ return $this->sanitize($this->get_date(''), SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif (($date = $this->get_date('U')) !== null && $date !== false)
+ {
+ return strftime($date_format, $date);
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the posting date/time for the item (UTC time)
+ *
+ * @see get_date
+ * @param string $date_format Supports any PHP date format from {@see http://php.net/date}
+ * @return int|string|null
+ */
+ public function get_gmdate($date_format = 'j F Y, g:i a')
+ {
+ $date = $this->get_date('U');
+ if ($date === null)
+ {
+ return null;
+ }
+
+ return gmdate($date_format, $date);
+ }
+
+ /**
+ * Get the update date/time for the item (UTC time)
+ *
+ * @see get_updated_date
+ * @param string $date_format Supports any PHP date format from {@see http://php.net/date}
+ * @return int|string|null
+ */
+ public function get_updated_gmdate($date_format = 'j F Y, g:i a')
+ {
+ $date = $this->get_updated_date('U');
+ if ($date === null)
+ {
+ return null;
+ }
+
+ return gmdate($date_format, $date);
+ }
+
+ /**
+ * Get the permalink for the item
+ *
+ * Returns the first link available with a relationship of "alternate".
+ * Identical to {@see get_link()} with key 0
+ *
+ * @see get_link
+ * @since 0.8
+ * @return string|null Permalink URL
+ */
+ public function get_permalink()
+ {
+ $link = $this->get_link();
+ $enclosure = $this->get_enclosure(0);
+ if ($link !== null)
+ {
+ return $link;
+ }
+ elseif ($enclosure !== null)
+ {
+ return $enclosure->get_link();
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get a single link for the item
+ *
+ * @since Beta 3
+ * @param int $key The link that you want to return. Remember that arrays begin with 0, not 1
+ * @param string $rel The relationship of the link to return
+ * @return string|null Link URL
+ */
+ public function get_link($key = 0, $rel = 'alternate')
+ {
+ $links = $this->get_links($rel);
+ if ($links[$key] !== null)
+ {
+ return $links[$key];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get all links for the item
+ *
+ * Uses `<atom:link>`, `<link>` or `<guid>`
+ *
+ * @since Beta 2
+ * @param string $rel The relationship of links to return
+ * @return array|null Links found for the item (strings)
+ */
+ public function get_links($rel = 'alternate')
+ {
+ if (!isset($this->data['links']))
+ {
+ $this->data['links'] = array();
+ foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'link') as $link)
+ {
+ if (isset($link['attribs']['']['href']))
+ {
+ $link_rel = (isset($link['attribs']['']['rel'])) ? $link['attribs']['']['rel'] : 'alternate';
+ $this->data['links'][$link_rel][] = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link));
+
+ }
+ }
+ foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'link') as $link)
+ {
+ if (isset($link['attribs']['']['href']))
+ {
+ $link_rel = (isset($link['attribs']['']['rel'])) ? $link['attribs']['']['rel'] : 'alternate';
+ $this->data['links'][$link_rel][] = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link));
+ }
+ }
+ if ($links = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'link'))
+ {
+ $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0]));
+ }
+ if ($links = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'link'))
+ {
+ $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0]));
+ }
+ if ($links = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'link'))
+ {
+ $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0]));
+ }
+ if ($links = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'guid'))
+ {
+ if (!isset($links[0]['attribs']['']['isPermaLink']) || strtolower(trim($links[0]['attribs']['']['isPermaLink'])) === 'true')
+ {
+ $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0]));
+ }
+ }
+
+ $keys = array_keys($this->data['links']);
+ foreach ($keys as $key)
+ {
+ if ($this->registry->call('Misc', 'is_isegment_nz_nc', array($key)))
+ {
+ if (isset($this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key]))
+ {
+ $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key] = array_merge($this->data['links'][$key], $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key]);
+ $this->data['links'][$key] =& $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key];
+ }
+ else
+ {
+ $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key] =& $this->data['links'][$key];
+ }
+ }
+ elseif (substr($key, 0, 41) === SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY)
+ {
+ $this->data['links'][substr($key, 41)] =& $this->data['links'][$key];
+ }
+ $this->data['links'][$key] = array_unique($this->data['links'][$key]);
+ }
+ }
+ if (isset($this->data['links'][$rel]))
+ {
+ return $this->data['links'][$rel];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get an enclosure from the item
+ *
+ * Supports the <enclosure> RSS tag, as well as Media RSS and iTunes RSS.
+ *
+ * @since Beta 2
+ * @todo Add ability to prefer one type of content over another (in a media group).
+ * @param int $key The enclosure that you want to return. Remember that arrays begin with 0, not 1
+ * @return SimplePie_Enclosure|null
+ */
+ public function get_enclosure($key = 0, $prefer = null)
+ {
+ $enclosures = $this->get_enclosures();
+ if (isset($enclosures[$key]))
+ {
+ return $enclosures[$key];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get all available enclosures (podcasts, etc.)
+ *
+ * Supports the <enclosure> RSS tag, as well as Media RSS and iTunes RSS.
+ *
+ * At this point, we're pretty much assuming that all enclosures for an item
+ * are the same content. Anything else is too complicated to
+ * properly support.
+ *
+ * @since Beta 2
+ * @todo Add support for end-user defined sorting of enclosures by type/handler (so we can prefer the faster-loading FLV over MP4).
+ * @todo If an element exists at a level, but its value is empty, we should fall back to the value from the parent (if it exists).
+ * @return SimplePie_Enclosure[]|null List of SimplePie_Enclosure items
+ */
+ public function get_enclosures()
+ {
+ if (!isset($this->data['enclosures']))
+ {
+ $this->data['enclosures'] = array();
+
+ // Elements
+ $captions_parent = null;
+ $categories_parent = null;
+ $copyrights_parent = null;
+ $credits_parent = null;
+ $description_parent = null;
+ $duration_parent = null;
+ $hashes_parent = null;
+ $keywords_parent = null;
+ $player_parent = null;
+ $ratings_parent = null;
+ $restrictions_parent = null;
+ $thumbnails_parent = null;
+ $title_parent = null;
+
+ // Let's do the channel and item-level ones first, and just re-use them if we need to.
+ $parent = $this->get_feed();
+
+ // CAPTIONS
+ if ($captions = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'text'))
+ {
+ foreach ($captions as $caption)
+ {
+ $caption_type = null;
+ $caption_lang = null;
+ $caption_startTime = null;
+ $caption_endTime = null;
+ $caption_text = null;
+ if (isset($caption['attribs']['']['type']))
+ {
+ $caption_type = $this->sanitize($caption['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($caption['attribs']['']['lang']))
+ {
+ $caption_lang = $this->sanitize($caption['attribs']['']['lang'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($caption['attribs']['']['start']))
+ {
+ $caption_startTime = $this->sanitize($caption['attribs']['']['start'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($caption['attribs']['']['end']))
+ {
+ $caption_endTime = $this->sanitize($caption['attribs']['']['end'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($caption['data']))
+ {
+ $caption_text = $this->sanitize($caption['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $captions_parent[] = $this->registry->create('Caption', array($caption_type, $caption_lang, $caption_startTime, $caption_endTime, $caption_text));
+ }
+ }
+ elseif ($captions = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'text'))
+ {
+ foreach ($captions as $caption)
+ {
+ $caption_type = null;
+ $caption_lang = null;
+ $caption_startTime = null;
+ $caption_endTime = null;
+ $caption_text = null;
+ if (isset($caption['attribs']['']['type']))
+ {
+ $caption_type = $this->sanitize($caption['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($caption['attribs']['']['lang']))
+ {
+ $caption_lang = $this->sanitize($caption['attribs']['']['lang'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($caption['attribs']['']['start']))
+ {
+ $caption_startTime = $this->sanitize($caption['attribs']['']['start'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($caption['attribs']['']['end']))
+ {
+ $caption_endTime = $this->sanitize($caption['attribs']['']['end'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($caption['data']))
+ {
+ $caption_text = $this->sanitize($caption['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $captions_parent[] = $this->registry->create('Caption', array($caption_type, $caption_lang, $caption_startTime, $caption_endTime, $caption_text));
+ }
+ }
+ if (is_array($captions_parent))
+ {
+ $captions_parent = array_values(array_unique($captions_parent));
+ }
+
+ // CATEGORIES
+ foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'category') as $category)
+ {
+ $term = null;
+ $scheme = null;
+ $label = null;
+ if (isset($category['data']))
+ {
+ $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($category['attribs']['']['scheme']))
+ {
+ $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $scheme = 'http://search.yahoo.com/mrss/category_schema';
+ }
+ if (isset($category['attribs']['']['label']))
+ {
+ $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $categories_parent[] = $this->registry->create('Category', array($term, $scheme, $label));
+ }
+ foreach ((array) $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'category') as $category)
+ {
+ $term = null;
+ $scheme = null;
+ $label = null;
+ if (isset($category['data']))
+ {
+ $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($category['attribs']['']['scheme']))
+ {
+ $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $scheme = 'http://search.yahoo.com/mrss/category_schema';
+ }
+ if (isset($category['attribs']['']['label']))
+ {
+ $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $categories_parent[] = $this->registry->create('Category', array($term, $scheme, $label));
+ }
+ foreach ((array) $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'category') as $category)
+ {
+ $term = null;
+ $scheme = 'http://www.itunes.com/dtds/podcast-1.0.dtd';
+ $label = null;
+ if (isset($category['attribs']['']['text']))
+ {
+ $label = $this->sanitize($category['attribs']['']['text'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $categories_parent[] = $this->registry->create('Category', array($term, $scheme, $label));
+
+ if (isset($category['child'][SIMPLEPIE_NAMESPACE_ITUNES]['category']))
+ {
+ foreach ((array) $category['child'][SIMPLEPIE_NAMESPACE_ITUNES]['category'] as $subcategory)
+ {
+ if (isset($subcategory['attribs']['']['text']))
+ {
+ $label = $this->sanitize($subcategory['attribs']['']['text'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $categories_parent[] = $this->registry->create('Category', array($term, $scheme, $label));
+ }
+ }
+ }
+ if (is_array($categories_parent))
+ {
+ $categories_parent = array_values(array_unique($categories_parent));
+ }
+
+ // COPYRIGHT
+ if ($copyright = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'copyright'))
+ {
+ $copyright_url = null;
+ $copyright_label = null;
+ if (isset($copyright[0]['attribs']['']['url']))
+ {
+ $copyright_url = $this->sanitize($copyright[0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($copyright[0]['data']))
+ {
+ $copyright_label = $this->sanitize($copyright[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $copyrights_parent = $this->registry->create('Copyright', array($copyright_url, $copyright_label));
+ }
+ elseif ($copyright = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'copyright'))
+ {
+ $copyright_url = null;
+ $copyright_label = null;
+ if (isset($copyright[0]['attribs']['']['url']))
+ {
+ $copyright_url = $this->sanitize($copyright[0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($copyright[0]['data']))
+ {
+ $copyright_label = $this->sanitize($copyright[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $copyrights_parent = $this->registry->create('Copyright', array($copyright_url, $copyright_label));
+ }
+
+ // CREDITS
+ if ($credits = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'credit'))
+ {
+ foreach ($credits as $credit)
+ {
+ $credit_role = null;
+ $credit_scheme = null;
+ $credit_name = null;
+ if (isset($credit['attribs']['']['role']))
+ {
+ $credit_role = $this->sanitize($credit['attribs']['']['role'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($credit['attribs']['']['scheme']))
+ {
+ $credit_scheme = $this->sanitize($credit['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $credit_scheme = 'urn:ebu';
+ }
+ if (isset($credit['data']))
+ {
+ $credit_name = $this->sanitize($credit['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $credits_parent[] = $this->registry->create('Credit', array($credit_role, $credit_scheme, $credit_name));
+ }
+ }
+ elseif ($credits = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'credit'))
+ {
+ foreach ($credits as $credit)
+ {
+ $credit_role = null;
+ $credit_scheme = null;
+ $credit_name = null;
+ if (isset($credit['attribs']['']['role']))
+ {
+ $credit_role = $this->sanitize($credit['attribs']['']['role'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($credit['attribs']['']['scheme']))
+ {
+ $credit_scheme = $this->sanitize($credit['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $credit_scheme = 'urn:ebu';
+ }
+ if (isset($credit['data']))
+ {
+ $credit_name = $this->sanitize($credit['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $credits_parent[] = $this->registry->create('Credit', array($credit_role, $credit_scheme, $credit_name));
+ }
+ }
+ if (is_array($credits_parent))
+ {
+ $credits_parent = array_values(array_unique($credits_parent));
+ }
+
+ // DESCRIPTION
+ if ($description_parent = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'description'))
+ {
+ if (isset($description_parent[0]['data']))
+ {
+ $description_parent = $this->sanitize($description_parent[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ }
+ elseif ($description_parent = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'description'))
+ {
+ if (isset($description_parent[0]['data']))
+ {
+ $description_parent = $this->sanitize($description_parent[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ }
+
+ // DURATION
+ if ($duration_parent = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'duration'))
+ {
+ $seconds = null;
+ $minutes = null;
+ $hours = null;
+ if (isset($duration_parent[0]['data']))
+ {
+ $temp = explode(':', $this->sanitize($duration_parent[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT));
+ if (sizeof($temp) > 0)
+ {
+ $seconds = (int) array_pop($temp);
+ }
+ if (sizeof($temp) > 0)
+ {
+ $minutes = (int) array_pop($temp);
+ $seconds += $minutes * 60;
+ }
+ if (sizeof($temp) > 0)
+ {
+ $hours = (int) array_pop($temp);
+ $seconds += $hours * 3600;
+ }
+ unset($temp);
+ $duration_parent = $seconds;
+ }
+ }
+
+ // HASHES
+ if ($hashes_iterator = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'hash'))
+ {
+ foreach ($hashes_iterator as $hash)
+ {
+ $value = null;
+ $algo = null;
+ if (isset($hash['data']))
+ {
+ $value = $this->sanitize($hash['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($hash['attribs']['']['algo']))
+ {
+ $algo = $this->sanitize($hash['attribs']['']['algo'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $algo = 'md5';
+ }
+ $hashes_parent[] = $algo.':'.$value;
+ }
+ }
+ elseif ($hashes_iterator = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'hash'))
+ {
+ foreach ($hashes_iterator as $hash)
+ {
+ $value = null;
+ $algo = null;
+ if (isset($hash['data']))
+ {
+ $value = $this->sanitize($hash['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($hash['attribs']['']['algo']))
+ {
+ $algo = $this->sanitize($hash['attribs']['']['algo'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $algo = 'md5';
+ }
+ $hashes_parent[] = $algo.':'.$value;
+ }
+ }
+ if (is_array($hashes_parent))
+ {
+ $hashes_parent = array_values(array_unique($hashes_parent));
+ }
+
+ // KEYWORDS
+ if ($keywords = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'keywords'))
+ {
+ if (isset($keywords[0]['data']))
+ {
+ $temp = explode(',', $this->sanitize($keywords[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT));
+ foreach ($temp as $word)
+ {
+ $keywords_parent[] = trim($word);
+ }
+ }
+ unset($temp);
+ }
+ elseif ($keywords = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'keywords'))
+ {
+ if (isset($keywords[0]['data']))
+ {
+ $temp = explode(',', $this->sanitize($keywords[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT));
+ foreach ($temp as $word)
+ {
+ $keywords_parent[] = trim($word);
+ }
+ }
+ unset($temp);
+ }
+ elseif ($keywords = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'keywords'))
+ {
+ if (isset($keywords[0]['data']))
+ {
+ $temp = explode(',', $this->sanitize($keywords[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT));
+ foreach ($temp as $word)
+ {
+ $keywords_parent[] = trim($word);
+ }
+ }
+ unset($temp);
+ }
+ elseif ($keywords = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'keywords'))
+ {
+ if (isset($keywords[0]['data']))
+ {
+ $temp = explode(',', $this->sanitize($keywords[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT));
+ foreach ($temp as $word)
+ {
+ $keywords_parent[] = trim($word);
+ }
+ }
+ unset($temp);
+ }
+ if (is_array($keywords_parent))
+ {
+ $keywords_parent = array_values(array_unique($keywords_parent));
+ }
+
+ // PLAYER
+ if ($player_parent = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'player'))
+ {
+ if (isset($player_parent[0]['attribs']['']['url']))
+ {
+ $player_parent = $this->sanitize($player_parent[0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
+ }
+ }
+ elseif ($player_parent = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'player'))
+ {
+ if (isset($player_parent[0]['attribs']['']['url']))
+ {
+ $player_parent = $this->sanitize($player_parent[0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
+ }
+ }
+
+ // RATINGS
+ if ($ratings = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'rating'))
+ {
+ foreach ($ratings as $rating)
+ {
+ $rating_scheme = null;
+ $rating_value = null;
+ if (isset($rating['attribs']['']['scheme']))
+ {
+ $rating_scheme = $this->sanitize($rating['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $rating_scheme = 'urn:simple';
+ }
+ if (isset($rating['data']))
+ {
+ $rating_value = $this->sanitize($rating['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $ratings_parent[] = $this->registry->create('Rating', array($rating_scheme, $rating_value));
+ }
+ }
+ elseif ($ratings = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'explicit'))
+ {
+ foreach ($ratings as $rating)
+ {
+ $rating_scheme = 'urn:itunes';
+ $rating_value = null;
+ if (isset($rating['data']))
+ {
+ $rating_value = $this->sanitize($rating['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $ratings_parent[] = $this->registry->create('Rating', array($rating_scheme, $rating_value));
+ }
+ }
+ elseif ($ratings = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'rating'))
+ {
+ foreach ($ratings as $rating)
+ {
+ $rating_scheme = null;
+ $rating_value = null;
+ if (isset($rating['attribs']['']['scheme']))
+ {
+ $rating_scheme = $this->sanitize($rating['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $rating_scheme = 'urn:simple';
+ }
+ if (isset($rating['data']))
+ {
+ $rating_value = $this->sanitize($rating['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $ratings_parent[] = $this->registry->create('Rating', array($rating_scheme, $rating_value));
+ }
+ }
+ elseif ($ratings = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'explicit'))
+ {
+ foreach ($ratings as $rating)
+ {
+ $rating_scheme = 'urn:itunes';
+ $rating_value = null;
+ if (isset($rating['data']))
+ {
+ $rating_value = $this->sanitize($rating['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $ratings_parent[] = $this->registry->create('Rating', array($rating_scheme, $rating_value));
+ }
+ }
+ if (is_array($ratings_parent))
+ {
+ $ratings_parent = array_values(array_unique($ratings_parent));
+ }
+
+ // RESTRICTIONS
+ if ($restrictions = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'restriction'))
+ {
+ foreach ($restrictions as $restriction)
+ {
+ $restriction_relationship = null;
+ $restriction_type = null;
+ $restriction_value = null;
+ if (isset($restriction['attribs']['']['relationship']))
+ {
+ $restriction_relationship = $this->sanitize($restriction['attribs']['']['relationship'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($restriction['attribs']['']['type']))
+ {
+ $restriction_type = $this->sanitize($restriction['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($restriction['data']))
+ {
+ $restriction_value = $this->sanitize($restriction['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $restrictions_parent[] = $this->registry->create('Restriction', array($restriction_relationship, $restriction_type, $restriction_value));
+ }
+ }
+ elseif ($restrictions = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'block'))
+ {
+ foreach ($restrictions as $restriction)
+ {
+ $restriction_relationship = 'allow';
+ $restriction_type = null;
+ $restriction_value = 'itunes';
+ if (isset($restriction['data']) && strtolower($restriction['data']) === 'yes')
+ {
+ $restriction_relationship = 'deny';
+ }
+ $restrictions_parent[] = $this->registry->create('Restriction', array($restriction_relationship, $restriction_type, $restriction_value));
+ }
+ }
+ elseif ($restrictions = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'restriction'))
+ {
+ foreach ($restrictions as $restriction)
+ {
+ $restriction_relationship = null;
+ $restriction_type = null;
+ $restriction_value = null;
+ if (isset($restriction['attribs']['']['relationship']))
+ {
+ $restriction_relationship = $this->sanitize($restriction['attribs']['']['relationship'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($restriction['attribs']['']['type']))
+ {
+ $restriction_type = $this->sanitize($restriction['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($restriction['data']))
+ {
+ $restriction_value = $this->sanitize($restriction['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $restrictions_parent[] = $this->registry->create('Restriction', array($restriction_relationship, $restriction_type, $restriction_value));
+ }
+ }
+ elseif ($restrictions = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'block'))
+ {
+ foreach ($restrictions as $restriction)
+ {
+ $restriction_relationship = 'allow';
+ $restriction_type = null;
+ $restriction_value = 'itunes';
+ if (isset($restriction['data']) && strtolower($restriction['data']) === 'yes')
+ {
+ $restriction_relationship = 'deny';
+ }
+ $restrictions_parent[] = $this->registry->create('Restriction', array($restriction_relationship, $restriction_type, $restriction_value));
+ }
+ }
+ if (is_array($restrictions_parent))
+ {
+ $restrictions_parent = array_values(array_unique($restrictions_parent));
+ }
+ else
+ {
+ $restrictions_parent = array(new SimplePie_Restriction('allow', null, 'default'));
+ }
+
+ // THUMBNAILS
+ if ($thumbnails = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'thumbnail'))
+ {
+ foreach ($thumbnails as $thumbnail)
+ {
+ if (isset($thumbnail['attribs']['']['url']))
+ {
+ $thumbnails_parent[] = $this->sanitize($thumbnail['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
+ }
+ }
+ }
+ elseif ($thumbnails = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'thumbnail'))
+ {
+ foreach ($thumbnails as $thumbnail)
+ {
+ if (isset($thumbnail['attribs']['']['url']))
+ {
+ $thumbnails_parent[] = $this->sanitize($thumbnail['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
+ }
+ }
+ }
+
+ // TITLES
+ if ($title_parent = $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'title'))
+ {
+ if (isset($title_parent[0]['data']))
+ {
+ $title_parent = $this->sanitize($title_parent[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ }
+ elseif ($title_parent = $parent->get_channel_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'title'))
+ {
+ if (isset($title_parent[0]['data']))
+ {
+ $title_parent = $this->sanitize($title_parent[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ }
+
+ // Clear the memory
+ unset($parent);
+
+ // Attributes
+ $bitrate = null;
+ $channels = null;
+ $duration = null;
+ $expression = null;
+ $framerate = null;
+ $height = null;
+ $javascript = null;
+ $lang = null;
+ $length = null;
+ $medium = null;
+ $samplingrate = null;
+ $type = null;
+ $url = null;
+ $width = null;
+
+ // Elements
+ $captions = null;
+ $categories = null;
+ $copyrights = null;
+ $credits = null;
+ $description = null;
+ $hashes = null;
+ $keywords = null;
+ $player = null;
+ $ratings = null;
+ $restrictions = null;
+ $thumbnails = null;
+ $title = null;
+
+ // If we have media:group tags, loop through them.
+ foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_MEDIARSS, 'group') as $group)
+ {
+ if(isset($group['child']) && isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['content']))
+ {
+ // If we have media:content tags, loop through them.
+ foreach ((array) $group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['content'] as $content)
+ {
+ if (isset($content['attribs']['']['url']))
+ {
+ // Attributes
+ $bitrate = null;
+ $channels = null;
+ $duration = null;
+ $expression = null;
+ $framerate = null;
+ $height = null;
+ $javascript = null;
+ $lang = null;
+ $length = null;
+ $medium = null;
+ $samplingrate = null;
+ $type = null;
+ $url = null;
+ $width = null;
+
+ // Elements
+ $captions = null;
+ $categories = null;
+ $copyrights = null;
+ $credits = null;
+ $description = null;
+ $hashes = null;
+ $keywords = null;
+ $player = null;
+ $ratings = null;
+ $restrictions = null;
+ $thumbnails = null;
+ $title = null;
+
+ // Start checking the attributes of media:content
+ if (isset($content['attribs']['']['bitrate']))
+ {
+ $bitrate = $this->sanitize($content['attribs']['']['bitrate'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($content['attribs']['']['channels']))
+ {
+ $channels = $this->sanitize($content['attribs']['']['channels'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($content['attribs']['']['duration']))
+ {
+ $duration = $this->sanitize($content['attribs']['']['duration'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $duration = $duration_parent;
+ }
+ if (isset($content['attribs']['']['expression']))
+ {
+ $expression = $this->sanitize($content['attribs']['']['expression'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($content['attribs']['']['framerate']))
+ {
+ $framerate = $this->sanitize($content['attribs']['']['framerate'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($content['attribs']['']['height']))
+ {
+ $height = $this->sanitize($content['attribs']['']['height'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($content['attribs']['']['lang']))
+ {
+ $lang = $this->sanitize($content['attribs']['']['lang'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($content['attribs']['']['fileSize']))
+ {
+ $length = ceil($content['attribs']['']['fileSize']);
+ }
+ if (isset($content['attribs']['']['medium']))
+ {
+ $medium = $this->sanitize($content['attribs']['']['medium'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($content['attribs']['']['samplingrate']))
+ {
+ $samplingrate = $this->sanitize($content['attribs']['']['samplingrate'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($content['attribs']['']['type']))
+ {
+ $type = $this->sanitize($content['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($content['attribs']['']['width']))
+ {
+ $width = $this->sanitize($content['attribs']['']['width'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $url = $this->sanitize($content['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
+
+ // Checking the other optional media: elements. Priority: media:content, media:group, item, channel
+
+ // CAPTIONS
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['text']))
+ {
+ foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['text'] as $caption)
+ {
+ $caption_type = null;
+ $caption_lang = null;
+ $caption_startTime = null;
+ $caption_endTime = null;
+ $caption_text = null;
+ if (isset($caption['attribs']['']['type']))
+ {
+ $caption_type = $this->sanitize($caption['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($caption['attribs']['']['lang']))
+ {
+ $caption_lang = $this->sanitize($caption['attribs']['']['lang'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($caption['attribs']['']['start']))
+ {
+ $caption_startTime = $this->sanitize($caption['attribs']['']['start'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($caption['attribs']['']['end']))
+ {
+ $caption_endTime = $this->sanitize($caption['attribs']['']['end'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($caption['data']))
+ {
+ $caption_text = $this->sanitize($caption['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $captions[] = $this->registry->create('Caption', array($caption_type, $caption_lang, $caption_startTime, $caption_endTime, $caption_text));
+ }
+ if (is_array($captions))
+ {
+ $captions = array_values(array_unique($captions));
+ }
+ }
+ elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['text']))
+ {
+ foreach ($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['text'] as $caption)
+ {
+ $caption_type = null;
+ $caption_lang = null;
+ $caption_startTime = null;
+ $caption_endTime = null;
+ $caption_text = null;
+ if (isset($caption['attribs']['']['type']))
+ {
+ $caption_type = $this->sanitize($caption['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($caption['attribs']['']['lang']))
+ {
+ $caption_lang = $this->sanitize($caption['attribs']['']['lang'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($caption['attribs']['']['start']))
+ {
+ $caption_startTime = $this->sanitize($caption['attribs']['']['start'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($caption['attribs']['']['end']))
+ {
+ $caption_endTime = $this->sanitize($caption['attribs']['']['end'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($caption['data']))
+ {
+ $caption_text = $this->sanitize($caption['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $captions[] = $this->registry->create('Caption', array($caption_type, $caption_lang, $caption_startTime, $caption_endTime, $caption_text));
+ }
+ if (is_array($captions))
+ {
+ $captions = array_values(array_unique($captions));
+ }
+ }
+ else
+ {
+ $captions = $captions_parent;
+ }
+
+ // CATEGORIES
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['category']))
+ {
+ foreach ((array) $content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['category'] as $category)
+ {
+ $term = null;
+ $scheme = null;
+ $label = null;
+ if (isset($category['data']))
+ {
+ $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($category['attribs']['']['scheme']))
+ {
+ $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $scheme = 'http://search.yahoo.com/mrss/category_schema';
+ }
+ if (isset($category['attribs']['']['label']))
+ {
+ $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $categories[] = $this->registry->create('Category', array($term, $scheme, $label));
+ }
+ }
+ if (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['category']))
+ {
+ foreach ((array) $group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['category'] as $category)
+ {
+ $term = null;
+ $scheme = null;
+ $label = null;
+ if (isset($category['data']))
+ {
+ $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($category['attribs']['']['scheme']))
+ {
+ $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $scheme = 'http://search.yahoo.com/mrss/category_schema';
+ }
+ if (isset($category['attribs']['']['label']))
+ {
+ $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $categories[] = $this->registry->create('Category', array($term, $scheme, $label));
+ }
+ }
+ if (is_array($categories) && is_array($categories_parent))
+ {
+ $categories = array_values(array_unique(array_merge($categories, $categories_parent)));
+ }
+ elseif (is_array($categories))
+ {
+ $categories = array_values(array_unique($categories));
+ }
+ elseif (is_array($categories_parent))
+ {
+ $categories = array_values(array_unique($categories_parent));
+ }
+
+ // COPYRIGHTS
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright']))
+ {
+ $copyright_url = null;
+ $copyright_label = null;
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['attribs']['']['url']))
+ {
+ $copyright_url = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['data']))
+ {
+ $copyright_label = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $copyrights = $this->registry->create('Copyright', array($copyright_url, $copyright_label));
+ }
+ elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright']))
+ {
+ $copyright_url = null;
+ $copyright_label = null;
+ if (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['attribs']['']['url']))
+ {
+ $copyright_url = $this->sanitize($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['data']))
+ {
+ $copyright_label = $this->sanitize($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $copyrights = $this->registry->create('Copyright', array($copyright_url, $copyright_label));
+ }
+ else
+ {
+ $copyrights = $copyrights_parent;
+ }
+
+ // CREDITS
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['credit']))
+ {
+ foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['credit'] as $credit)
+ {
+ $credit_role = null;
+ $credit_scheme = null;
+ $credit_name = null;
+ if (isset($credit['attribs']['']['role']))
+ {
+ $credit_role = $this->sanitize($credit['attribs']['']['role'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($credit['attribs']['']['scheme']))
+ {
+ $credit_scheme = $this->sanitize($credit['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $credit_scheme = 'urn:ebu';
+ }
+ if (isset($credit['data']))
+ {
+ $credit_name = $this->sanitize($credit['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $credits[] = $this->registry->create('Credit', array($credit_role, $credit_scheme, $credit_name));
+ }
+ if (is_array($credits))
+ {
+ $credits = array_values(array_unique($credits));
+ }
+ }
+ elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['credit']))
+ {
+ foreach ($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['credit'] as $credit)
+ {
+ $credit_role = null;
+ $credit_scheme = null;
+ $credit_name = null;
+ if (isset($credit['attribs']['']['role']))
+ {
+ $credit_role = $this->sanitize($credit['attribs']['']['role'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($credit['attribs']['']['scheme']))
+ {
+ $credit_scheme = $this->sanitize($credit['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $credit_scheme = 'urn:ebu';
+ }
+ if (isset($credit['data']))
+ {
+ $credit_name = $this->sanitize($credit['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $credits[] = $this->registry->create('Credit', array($credit_role, $credit_scheme, $credit_name));
+ }
+ if (is_array($credits))
+ {
+ $credits = array_values(array_unique($credits));
+ }
+ }
+ else
+ {
+ $credits = $credits_parent;
+ }
+
+ // DESCRIPTION
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['description']))
+ {
+ $description = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['description'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['description']))
+ {
+ $description = $this->sanitize($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['description'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $description = $description_parent;
+ }
+
+ // HASHES
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['hash']))
+ {
+ foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['hash'] as $hash)
+ {
+ $value = null;
+ $algo = null;
+ if (isset($hash['data']))
+ {
+ $value = $this->sanitize($hash['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($hash['attribs']['']['algo']))
+ {
+ $algo = $this->sanitize($hash['attribs']['']['algo'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $algo = 'md5';
+ }
+ $hashes[] = $algo.':'.$value;
+ }
+ if (is_array($hashes))
+ {
+ $hashes = array_values(array_unique($hashes));
+ }
+ }
+ elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['hash']))
+ {
+ foreach ($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['hash'] as $hash)
+ {
+ $value = null;
+ $algo = null;
+ if (isset($hash['data']))
+ {
+ $value = $this->sanitize($hash['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($hash['attribs']['']['algo']))
+ {
+ $algo = $this->sanitize($hash['attribs']['']['algo'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $algo = 'md5';
+ }
+ $hashes[] = $algo.':'.$value;
+ }
+ if (is_array($hashes))
+ {
+ $hashes = array_values(array_unique($hashes));
+ }
+ }
+ else
+ {
+ $hashes = $hashes_parent;
+ }
+
+ // KEYWORDS
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords']))
+ {
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords'][0]['data']))
+ {
+ $temp = explode(',', $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT));
+ foreach ($temp as $word)
+ {
+ $keywords[] = trim($word);
+ }
+ unset($temp);
+ }
+ if (is_array($keywords))
+ {
+ $keywords = array_values(array_unique($keywords));
+ }
+ }
+ elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords']))
+ {
+ if (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords'][0]['data']))
+ {
+ $temp = explode(',', $this->sanitize($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT));
+ foreach ($temp as $word)
+ {
+ $keywords[] = trim($word);
+ }
+ unset($temp);
+ }
+ if (is_array($keywords))
+ {
+ $keywords = array_values(array_unique($keywords));
+ }
+ }
+ else
+ {
+ $keywords = $keywords_parent;
+ }
+
+ // PLAYER
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['player']))
+ {
+ $player = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['player'][0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
+ }
+ elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['player']))
+ {
+ $player = $this->sanitize($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['player'][0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
+ }
+ else
+ {
+ $player = $player_parent;
+ }
+
+ // RATINGS
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['rating']))
+ {
+ foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['rating'] as $rating)
+ {
+ $rating_scheme = null;
+ $rating_value = null;
+ if (isset($rating['attribs']['']['scheme']))
+ {
+ $rating_scheme = $this->sanitize($rating['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $rating_scheme = 'urn:simple';
+ }
+ if (isset($rating['data']))
+ {
+ $rating_value = $this->sanitize($rating['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $ratings[] = $this->registry->create('Rating', array($rating_scheme, $rating_value));
+ }
+ if (is_array($ratings))
+ {
+ $ratings = array_values(array_unique($ratings));
+ }
+ }
+ elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['rating']))
+ {
+ foreach ($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['rating'] as $rating)
+ {
+ $rating_scheme = null;
+ $rating_value = null;
+ if (isset($rating['attribs']['']['scheme']))
+ {
+ $rating_scheme = $this->sanitize($rating['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $rating_scheme = 'urn:simple';
+ }
+ if (isset($rating['data']))
+ {
+ $rating_value = $this->sanitize($rating['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $ratings[] = $this->registry->create('Rating', array($rating_scheme, $rating_value));
+ }
+ if (is_array($ratings))
+ {
+ $ratings = array_values(array_unique($ratings));
+ }
+ }
+ else
+ {
+ $ratings = $ratings_parent;
+ }
+
+ // RESTRICTIONS
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['restriction']))
+ {
+ foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['restriction'] as $restriction)
+ {
+ $restriction_relationship = null;
+ $restriction_type = null;
+ $restriction_value = null;
+ if (isset($restriction['attribs']['']['relationship']))
+ {
+ $restriction_relationship = $this->sanitize($restriction['attribs']['']['relationship'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($restriction['attribs']['']['type']))
+ {
+ $restriction_type = $this->sanitize($restriction['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($restriction['data']))
+ {
+ $restriction_value = $this->sanitize($restriction['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $restrictions[] = $this->registry->create('Restriction', array($restriction_relationship, $restriction_type, $restriction_value));
+ }
+ if (is_array($restrictions))
+ {
+ $restrictions = array_values(array_unique($restrictions));
+ }
+ }
+ elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['restriction']))
+ {
+ foreach ($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['restriction'] as $restriction)
+ {
+ $restriction_relationship = null;
+ $restriction_type = null;
+ $restriction_value = null;
+ if (isset($restriction['attribs']['']['relationship']))
+ {
+ $restriction_relationship = $this->sanitize($restriction['attribs']['']['relationship'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($restriction['attribs']['']['type']))
+ {
+ $restriction_type = $this->sanitize($restriction['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($restriction['data']))
+ {
+ $restriction_value = $this->sanitize($restriction['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $restrictions[] = $this->registry->create('Restriction', array($restriction_relationship, $restriction_type, $restriction_value));
+ }
+ if (is_array($restrictions))
+ {
+ $restrictions = array_values(array_unique($restrictions));
+ }
+ }
+ else
+ {
+ $restrictions = $restrictions_parent;
+ }
+
+ // THUMBNAILS
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['thumbnail']))
+ {
+ foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['thumbnail'] as $thumbnail)
+ {
+ $thumbnails[] = $this->sanitize($thumbnail['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
+ }
+ if (is_array($thumbnails))
+ {
+ $thumbnails = array_values(array_unique($thumbnails));
+ }
+ }
+ elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['thumbnail']))
+ {
+ foreach ($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['thumbnail'] as $thumbnail)
+ {
+ $thumbnails[] = $this->sanitize($thumbnail['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
+ }
+ if (is_array($thumbnails))
+ {
+ $thumbnails = array_values(array_unique($thumbnails));
+ }
+ }
+ else
+ {
+ $thumbnails = $thumbnails_parent;
+ }
+
+ // TITLES
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['title']))
+ {
+ $title = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['title'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif (isset($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['title']))
+ {
+ $title = $this->sanitize($group['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['title'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $title = $title_parent;
+ }
+
+ $this->data['enclosures'][] = $this->registry->create('Enclosure', array($url, $type, $length, null, $bitrate, $captions, $categories, $channels, $copyrights, $credits, $description, $duration, $expression, $framerate, $hashes, $height, $keywords, $lang, $medium, $player, $ratings, $restrictions, $samplingrate, $thumbnails, $title, $width));
+ }
+ }
+ }
+ }
+
+ // If we have standalone media:content tags, loop through them.
+ if (isset($this->data['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['content']))
+ {
+ foreach ((array) $this->data['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['content'] as $content)
+ {
+ if (isset($content['attribs']['']['url']) || isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['player']))
+ {
+ // Attributes
+ $bitrate = null;
+ $channels = null;
+ $duration = null;
+ $expression = null;
+ $framerate = null;
+ $height = null;
+ $javascript = null;
+ $lang = null;
+ $length = null;
+ $medium = null;
+ $samplingrate = null;
+ $type = null;
+ $url = null;
+ $width = null;
+
+ // Elements
+ $captions = null;
+ $categories = null;
+ $copyrights = null;
+ $credits = null;
+ $description = null;
+ $hashes = null;
+ $keywords = null;
+ $player = null;
+ $ratings = null;
+ $restrictions = null;
+ $thumbnails = null;
+ $title = null;
+
+ // Start checking the attributes of media:content
+ if (isset($content['attribs']['']['bitrate']))
+ {
+ $bitrate = $this->sanitize($content['attribs']['']['bitrate'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($content['attribs']['']['channels']))
+ {
+ $channels = $this->sanitize($content['attribs']['']['channels'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($content['attribs']['']['duration']))
+ {
+ $duration = $this->sanitize($content['attribs']['']['duration'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $duration = $duration_parent;
+ }
+ if (isset($content['attribs']['']['expression']))
+ {
+ $expression = $this->sanitize($content['attribs']['']['expression'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($content['attribs']['']['framerate']))
+ {
+ $framerate = $this->sanitize($content['attribs']['']['framerate'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($content['attribs']['']['height']))
+ {
+ $height = $this->sanitize($content['attribs']['']['height'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($content['attribs']['']['lang']))
+ {
+ $lang = $this->sanitize($content['attribs']['']['lang'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($content['attribs']['']['fileSize']))
+ {
+ $length = ceil($content['attribs']['']['fileSize']);
+ }
+ if (isset($content['attribs']['']['medium']))
+ {
+ $medium = $this->sanitize($content['attribs']['']['medium'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($content['attribs']['']['samplingrate']))
+ {
+ $samplingrate = $this->sanitize($content['attribs']['']['samplingrate'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($content['attribs']['']['type']))
+ {
+ $type = $this->sanitize($content['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($content['attribs']['']['width']))
+ {
+ $width = $this->sanitize($content['attribs']['']['width'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($content['attribs']['']['url']))
+ {
+ $url = $this->sanitize($content['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
+ }
+ // Checking the other optional media: elements. Priority: media:content, media:group, item, channel
+
+ // CAPTIONS
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['text']))
+ {
+ foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['text'] as $caption)
+ {
+ $caption_type = null;
+ $caption_lang = null;
+ $caption_startTime = null;
+ $caption_endTime = null;
+ $caption_text = null;
+ if (isset($caption['attribs']['']['type']))
+ {
+ $caption_type = $this->sanitize($caption['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($caption['attribs']['']['lang']))
+ {
+ $caption_lang = $this->sanitize($caption['attribs']['']['lang'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($caption['attribs']['']['start']))
+ {
+ $caption_startTime = $this->sanitize($caption['attribs']['']['start'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($caption['attribs']['']['end']))
+ {
+ $caption_endTime = $this->sanitize($caption['attribs']['']['end'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($caption['data']))
+ {
+ $caption_text = $this->sanitize($caption['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $captions[] = $this->registry->create('Caption', array($caption_type, $caption_lang, $caption_startTime, $caption_endTime, $caption_text));
+ }
+ if (is_array($captions))
+ {
+ $captions = array_values(array_unique($captions));
+ }
+ }
+ else
+ {
+ $captions = $captions_parent;
+ }
+
+ // CATEGORIES
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['category']))
+ {
+ foreach ((array) $content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['category'] as $category)
+ {
+ $term = null;
+ $scheme = null;
+ $label = null;
+ if (isset($category['data']))
+ {
+ $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($category['attribs']['']['scheme']))
+ {
+ $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $scheme = 'http://search.yahoo.com/mrss/category_schema';
+ }
+ if (isset($category['attribs']['']['label']))
+ {
+ $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $categories[] = $this->registry->create('Category', array($term, $scheme, $label));
+ }
+ }
+ if (is_array($categories) && is_array($categories_parent))
+ {
+ $categories = array_values(array_unique(array_merge($categories, $categories_parent)));
+ }
+ elseif (is_array($categories))
+ {
+ $categories = array_values(array_unique($categories));
+ }
+ elseif (is_array($categories_parent))
+ {
+ $categories = array_values(array_unique($categories_parent));
+ }
+ else
+ {
+ $categories = null;
+ }
+
+ // COPYRIGHTS
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright']))
+ {
+ $copyright_url = null;
+ $copyright_label = null;
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['attribs']['']['url']))
+ {
+ $copyright_url = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['data']))
+ {
+ $copyright_label = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['copyright'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $copyrights = $this->registry->create('Copyright', array($copyright_url, $copyright_label));
+ }
+ else
+ {
+ $copyrights = $copyrights_parent;
+ }
+
+ // CREDITS
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['credit']))
+ {
+ foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['credit'] as $credit)
+ {
+ $credit_role = null;
+ $credit_scheme = null;
+ $credit_name = null;
+ if (isset($credit['attribs']['']['role']))
+ {
+ $credit_role = $this->sanitize($credit['attribs']['']['role'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($credit['attribs']['']['scheme']))
+ {
+ $credit_scheme = $this->sanitize($credit['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $credit_scheme = 'urn:ebu';
+ }
+ if (isset($credit['data']))
+ {
+ $credit_name = $this->sanitize($credit['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $credits[] = $this->registry->create('Credit', array($credit_role, $credit_scheme, $credit_name));
+ }
+ if (is_array($credits))
+ {
+ $credits = array_values(array_unique($credits));
+ }
+ }
+ else
+ {
+ $credits = $credits_parent;
+ }
+
+ // DESCRIPTION
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['description']))
+ {
+ $description = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['description'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $description = $description_parent;
+ }
+
+ // HASHES
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['hash']))
+ {
+ foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['hash'] as $hash)
+ {
+ $value = null;
+ $algo = null;
+ if (isset($hash['data']))
+ {
+ $value = $this->sanitize($hash['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($hash['attribs']['']['algo']))
+ {
+ $algo = $this->sanitize($hash['attribs']['']['algo'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $algo = 'md5';
+ }
+ $hashes[] = $algo.':'.$value;
+ }
+ if (is_array($hashes))
+ {
+ $hashes = array_values(array_unique($hashes));
+ }
+ }
+ else
+ {
+ $hashes = $hashes_parent;
+ }
+
+ // KEYWORDS
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords']))
+ {
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords'][0]['data']))
+ {
+ $temp = explode(',', $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['keywords'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT));
+ foreach ($temp as $word)
+ {
+ $keywords[] = trim($word);
+ }
+ unset($temp);
+ }
+ if (is_array($keywords))
+ {
+ $keywords = array_values(array_unique($keywords));
+ }
+ }
+ else
+ {
+ $keywords = $keywords_parent;
+ }
+
+ // PLAYER
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['player']))
+ {
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['player'][0]['attribs']['']['url'])) {
+ $player = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['player'][0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
+ }
+ }
+ else
+ {
+ $player = $player_parent;
+ }
+
+ // RATINGS
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['rating']))
+ {
+ foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['rating'] as $rating)
+ {
+ $rating_scheme = null;
+ $rating_value = null;
+ if (isset($rating['attribs']['']['scheme']))
+ {
+ $rating_scheme = $this->sanitize($rating['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $rating_scheme = 'urn:simple';
+ }
+ if (isset($rating['data']))
+ {
+ $rating_value = $this->sanitize($rating['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $ratings[] = $this->registry->create('Rating', array($rating_scheme, $rating_value));
+ }
+ if (is_array($ratings))
+ {
+ $ratings = array_values(array_unique($ratings));
+ }
+ }
+ else
+ {
+ $ratings = $ratings_parent;
+ }
+
+ // RESTRICTIONS
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['restriction']))
+ {
+ foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['restriction'] as $restriction)
+ {
+ $restriction_relationship = null;
+ $restriction_type = null;
+ $restriction_value = null;
+ if (isset($restriction['attribs']['']['relationship']))
+ {
+ $restriction_relationship = $this->sanitize($restriction['attribs']['']['relationship'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($restriction['attribs']['']['type']))
+ {
+ $restriction_type = $this->sanitize($restriction['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($restriction['data']))
+ {
+ $restriction_value = $this->sanitize($restriction['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $restrictions[] = $this->registry->create('Restriction', array($restriction_relationship, $restriction_type, $restriction_value));
+ }
+ if (is_array($restrictions))
+ {
+ $restrictions = array_values(array_unique($restrictions));
+ }
+ }
+ else
+ {
+ $restrictions = $restrictions_parent;
+ }
+
+ // THUMBNAILS
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['thumbnail']))
+ {
+ foreach ($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['thumbnail'] as $thumbnail)
+ {
+ if (isset($thumbnail['attribs']['']['url'])) {
+ $thumbnails[] = $this->sanitize($thumbnail['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI);
+ }
+ }
+ if (is_array($thumbnails))
+ {
+ $thumbnails = array_values(array_unique($thumbnails));
+ }
+ }
+ else
+ {
+ $thumbnails = $thumbnails_parent;
+ }
+
+ // TITLES
+ if (isset($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['title']))
+ {
+ $title = $this->sanitize($content['child'][SIMPLEPIE_NAMESPACE_MEDIARSS]['title'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $title = $title_parent;
+ }
+
+ $this->data['enclosures'][] = $this->registry->create('Enclosure', array($url, $type, $length, null, $bitrate, $captions, $categories, $channels, $copyrights, $credits, $description, $duration, $expression, $framerate, $hashes, $height, $keywords, $lang, $medium, $player, $ratings, $restrictions, $samplingrate, $thumbnails, $title, $width));
+ }
+ }
+ }
+
+ foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'link') as $link)
+ {
+ if (isset($link['attribs']['']['href']) && !empty($link['attribs']['']['rel']) && $link['attribs']['']['rel'] === 'enclosure')
+ {
+ // Attributes
+ $bitrate = null;
+ $channels = null;
+ $duration = null;
+ $expression = null;
+ $framerate = null;
+ $height = null;
+ $javascript = null;
+ $lang = null;
+ $length = null;
+ $medium = null;
+ $samplingrate = null;
+ $type = null;
+ $url = null;
+ $width = null;
+
+ $url = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link));
+ if (isset($link['attribs']['']['type']))
+ {
+ $type = $this->sanitize($link['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($link['attribs']['']['length']))
+ {
+ $length = ceil($link['attribs']['']['length']);
+ }
+ if (isset($link['attribs']['']['title']))
+ {
+ $title = $this->sanitize($link['attribs']['']['title'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $title = $title_parent;
+ }
+
+ // Since we don't have group or content for these, we'll just pass the '*_parent' variables directly to the constructor
+ $this->data['enclosures'][] = $this->registry->create('Enclosure', array($url, $type, $length, null, $bitrate, $captions_parent, $categories_parent, $channels, $copyrights_parent, $credits_parent, $description_parent, $duration_parent, $expression, $framerate, $hashes_parent, $height, $keywords_parent, $lang, $medium, $player_parent, $ratings_parent, $restrictions_parent, $samplingrate, $thumbnails_parent, $title, $width));
+ }
+ }
+
+ foreach ((array) $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'link') as $link)
+ {
+ if (isset($link['attribs']['']['href']) && !empty($link['attribs']['']['rel']) && $link['attribs']['']['rel'] === 'enclosure')
+ {
+ // Attributes
+ $bitrate = null;
+ $channels = null;
+ $duration = null;
+ $expression = null;
+ $framerate = null;
+ $height = null;
+ $javascript = null;
+ $lang = null;
+ $length = null;
+ $medium = null;
+ $samplingrate = null;
+ $type = null;
+ $url = null;
+ $width = null;
+
+ $url = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link));
+ if (isset($link['attribs']['']['type']))
+ {
+ $type = $this->sanitize($link['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($link['attribs']['']['length']))
+ {
+ $length = ceil($link['attribs']['']['length']);
+ }
+
+ // Since we don't have group or content for these, we'll just pass the '*_parent' variables directly to the constructor
+ $this->data['enclosures'][] = $this->registry->create('Enclosure', array($url, $type, $length, null, $bitrate, $captions_parent, $categories_parent, $channels, $copyrights_parent, $credits_parent, $description_parent, $duration_parent, $expression, $framerate, $hashes_parent, $height, $keywords_parent, $lang, $medium, $player_parent, $ratings_parent, $restrictions_parent, $samplingrate, $thumbnails_parent, $title_parent, $width));
+ }
+ }
+
+ if ($enclosure = $this->get_item_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'enclosure'))
+ {
+ if (isset($enclosure[0]['attribs']['']['url']))
+ {
+ // Attributes
+ $bitrate = null;
+ $channels = null;
+ $duration = null;
+ $expression = null;
+ $framerate = null;
+ $height = null;
+ $javascript = null;
+ $lang = null;
+ $length = null;
+ $medium = null;
+ $samplingrate = null;
+ $type = null;
+ $url = null;
+ $width = null;
+
+ $url = $this->sanitize($enclosure[0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($enclosure[0]));
+ if (isset($enclosure[0]['attribs']['']['type']))
+ {
+ $type = $this->sanitize($enclosure[0]['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($enclosure[0]['attribs']['']['length']))
+ {
+ $length = ceil($enclosure[0]['attribs']['']['length']);
+ }
+
+ // Since we don't have group or content for these, we'll just pass the '*_parent' variables directly to the constructor
+ $this->data['enclosures'][] = $this->registry->create('Enclosure', array($url, $type, $length, null, $bitrate, $captions_parent, $categories_parent, $channels, $copyrights_parent, $credits_parent, $description_parent, $duration_parent, $expression, $framerate, $hashes_parent, $height, $keywords_parent, $lang, $medium, $player_parent, $ratings_parent, $restrictions_parent, $samplingrate, $thumbnails_parent, $title_parent, $width));
+ }
+ }
+
+ if (sizeof($this->data['enclosures']) === 0 && ($url || $type || $length || $bitrate || $captions_parent || $categories_parent || $channels || $copyrights_parent || $credits_parent || $description_parent || $duration_parent || $expression || $framerate || $hashes_parent || $height || $keywords_parent || $lang || $medium || $player_parent || $ratings_parent || $restrictions_parent || $samplingrate || $thumbnails_parent || $title_parent || $width))
+ {
+ // Since we don't have group or content for these, we'll just pass the '*_parent' variables directly to the constructor
+ $this->data['enclosures'][] = $this->registry->create('Enclosure', array($url, $type, $length, null, $bitrate, $captions_parent, $categories_parent, $channels, $copyrights_parent, $credits_parent, $description_parent, $duration_parent, $expression, $framerate, $hashes_parent, $height, $keywords_parent, $lang, $medium, $player_parent, $ratings_parent, $restrictions_parent, $samplingrate, $thumbnails_parent, $title_parent, $width));
+ }
+
+ $this->data['enclosures'] = array_values(array_unique($this->data['enclosures']));
+ }
+ if (!empty($this->data['enclosures']))
+ {
+ return $this->data['enclosures'];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the latitude coordinates for the item
+ *
+ * Compatible with the W3C WGS84 Basic Geo and GeoRSS specifications
+ *
+ * Uses `<geo:lat>` or `<georss:point>`
+ *
+ * @since 1.0
+ * @link http://www.w3.org/2003/01/geo/ W3C WGS84 Basic Geo
+ * @link http://www.georss.org/ GeoRSS
+ * @return string|null
+ */
+ public function get_latitude()
+ {
+ if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'lat'))
+ {
+ return (float) $return[0]['data'];
+ }
+ elseif (($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_GEORSS, 'point')) && preg_match('/^((?:-)?[0-9]+(?:\.[0-9]+)) ((?:-)?[0-9]+(?:\.[0-9]+))$/', trim($return[0]['data']), $match))
+ {
+ return (float) $match[1];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the longitude coordinates for the item
+ *
+ * Compatible with the W3C WGS84 Basic Geo and GeoRSS specifications
+ *
+ * Uses `<geo:long>`, `<geo:lon>` or `<georss:point>`
+ *
+ * @since 1.0
+ * @link http://www.w3.org/2003/01/geo/ W3C WGS84 Basic Geo
+ * @link http://www.georss.org/ GeoRSS
+ * @return string|null
+ */
+ public function get_longitude()
+ {
+ if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'long'))
+ {
+ return (float) $return[0]['data'];
+ }
+ elseif ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'lon'))
+ {
+ return (float) $return[0]['data'];
+ }
+ elseif (($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_GEORSS, 'point')) && preg_match('/^((?:-)?[0-9]+(?:\.[0-9]+)) ((?:-)?[0-9]+(?:\.[0-9]+))$/', trim($return[0]['data']), $match))
+ {
+ return (float) $match[2];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the `<atom:source>` for the item
+ *
+ * @since 1.1
+ * @return SimplePie_Source|null
+ */
+ public function get_source()
+ {
+ if ($return = $this->get_item_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'source'))
+ {
+ return $this->registry->create('Source', array($this, $return[0]));
+ }
+ else
+ {
+ return null;
+ }
+ }
+}
+
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Locator.php b/vendor/simplepie/simplepie/library/SimplePie/Locator.php
new file mode 100644
index 000000000..bc314c2cd
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Locator.php
@@ -0,0 +1,429 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * Used for feed auto-discovery
+ *
+ *
+ * This class can be overloaded with {@see SimplePie::set_locator_class()}
+ *
+ * @package SimplePie
+ */
+class SimplePie_Locator
+{
+ var $useragent;
+ var $timeout;
+ var $file;
+ var $local = array();
+ var $elsewhere = array();
+ var $cached_entities = array();
+ var $http_base;
+ var $base;
+ var $base_location = 0;
+ var $checked_feeds = 0;
+ var $max_checked_feeds = 10;
+ protected $registry;
+
+ public function __construct(SimplePie_File $file, $timeout = 10, $useragent = null, $max_checked_feeds = 10)
+ {
+ $this->file = $file;
+ $this->useragent = $useragent;
+ $this->timeout = $timeout;
+ $this->max_checked_feeds = $max_checked_feeds;
+
+ if (class_exists('DOMDocument'))
+ {
+ $this->dom = new DOMDocument();
+
+ set_error_handler(array('SimplePie_Misc', 'silence_errors'));
+ $this->dom->loadHTML($this->file->body);
+ restore_error_handler();
+ }
+ else
+ {
+ $this->dom = null;
+ }
+ }
+
+ public function set_registry(SimplePie_Registry $registry)
+ {
+ $this->registry = $registry;
+ }
+
+ public function find($type = SIMPLEPIE_LOCATOR_ALL, &$working)
+ {
+ if ($this->is_feed($this->file))
+ {
+ return $this->file;
+ }
+
+ if ($this->file->method & SIMPLEPIE_FILE_SOURCE_REMOTE)
+ {
+ $sniffer = $this->registry->create('Content_Type_Sniffer', array($this->file));
+ if ($sniffer->get_type() !== 'text/html')
+ {
+ return null;
+ }
+ }
+
+ if ($type & ~SIMPLEPIE_LOCATOR_NONE)
+ {
+ $this->get_base();
+ }
+
+ if ($type & SIMPLEPIE_LOCATOR_AUTODISCOVERY && $working = $this->autodiscovery())
+ {
+ return $working[0];
+ }
+
+ if ($type & (SIMPLEPIE_LOCATOR_LOCAL_EXTENSION | SIMPLEPIE_LOCATOR_LOCAL_BODY | SIMPLEPIE_LOCATOR_REMOTE_EXTENSION | SIMPLEPIE_LOCATOR_REMOTE_BODY) && $this->get_links())
+ {
+ if ($type & SIMPLEPIE_LOCATOR_LOCAL_EXTENSION && $working = $this->extension($this->local))
+ {
+ return $working[0];
+ }
+
+ if ($type & SIMPLEPIE_LOCATOR_LOCAL_BODY && $working = $this->body($this->local))
+ {
+ return $working[0];
+ }
+
+ if ($type & SIMPLEPIE_LOCATOR_REMOTE_EXTENSION && $working = $this->extension($this->elsewhere))
+ {
+ return $working[0];
+ }
+
+ if ($type & SIMPLEPIE_LOCATOR_REMOTE_BODY && $working = $this->body($this->elsewhere))
+ {
+ return $working[0];
+ }
+ }
+ return null;
+ }
+
+ public function is_feed($file, $check_html = false)
+ {
+ if ($file->method & SIMPLEPIE_FILE_SOURCE_REMOTE)
+ {
+ $sniffer = $this->registry->create('Content_Type_Sniffer', array($file));
+ $sniffed = $sniffer->get_type();
+ $mime_types = array('application/rss+xml', 'application/rdf+xml',
+ 'text/rdf', 'application/atom+xml', 'text/xml',
+ 'application/xml', 'application/x-rss+xml');
+ if ($check_html)
+ {
+ $mime_types[] = 'text/html';
+ }
+ if (in_array($sniffed, $mime_types))
+ {
+ return true;
+ }
+ else
+ {
+ return false;
+ }
+ }
+ elseif ($file->method & SIMPLEPIE_FILE_SOURCE_LOCAL)
+ {
+ return true;
+ }
+ else
+ {
+ return false;
+ }
+ }
+
+ public function get_base()
+ {
+ if ($this->dom === null)
+ {
+ throw new SimplePie_Exception('DOMDocument not found, unable to use locator');
+ }
+ $this->http_base = $this->file->url;
+ $this->base = $this->http_base;
+ $elements = $this->dom->getElementsByTagName('base');
+ foreach ($elements as $element)
+ {
+ if ($element->hasAttribute('href'))
+ {
+ $base = $this->registry->call('Misc', 'absolutize_url', array(trim($element->getAttribute('href')), $this->http_base));
+ if ($base === false)
+ {
+ continue;
+ }
+ $this->base = $base;
+ $this->base_location = method_exists($element, 'getLineNo') ? $element->getLineNo() : 0;
+ break;
+ }
+ }
+ }
+
+ public function autodiscovery()
+ {
+ $done = array();
+ $feeds = array();
+ $feeds = array_merge($feeds, $this->search_elements_by_tag('link', $done, $feeds));
+ $feeds = array_merge($feeds, $this->search_elements_by_tag('a', $done, $feeds));
+ $feeds = array_merge($feeds, $this->search_elements_by_tag('area', $done, $feeds));
+
+ if (!empty($feeds))
+ {
+ return array_values($feeds);
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ protected function search_elements_by_tag($name, &$done, $feeds)
+ {
+ if ($this->dom === null)
+ {
+ throw new SimplePie_Exception('DOMDocument not found, unable to use locator');
+ }
+
+ $links = $this->dom->getElementsByTagName($name);
+ foreach ($links as $link)
+ {
+ if ($this->checked_feeds === $this->max_checked_feeds)
+ {
+ break;
+ }
+ if ($link->hasAttribute('href') && $link->hasAttribute('rel'))
+ {
+ $rel = array_unique($this->registry->call('Misc', 'space_separated_tokens', array(strtolower($link->getAttribute('rel')))));
+ $line = method_exists($link, 'getLineNo') ? $link->getLineNo() : 1;
+
+ if ($this->base_location < $line)
+ {
+ $href = $this->registry->call('Misc', 'absolutize_url', array(trim($link->getAttribute('href')), $this->base));
+ }
+ else
+ {
+ $href = $this->registry->call('Misc', 'absolutize_url', array(trim($link->getAttribute('href')), $this->http_base));
+ }
+ if ($href === false)
+ {
+ continue;
+ }
+
+ if (!in_array($href, $done) && in_array('feed', $rel) || (in_array('alternate', $rel) && !in_array('stylesheet', $rel) && $link->hasAttribute('type') && in_array(strtolower($this->registry->call('Misc', 'parse_mime', array($link->getAttribute('type')))), array('text/html', 'application/rss+xml', 'application/atom+xml'))) && !isset($feeds[$href]))
+ {
+ $this->checked_feeds++;
+ $headers = array(
+ 'Accept' => 'application/atom+xml, application/rss+xml, application/rdf+xml;q=0.9, application/xml;q=0.8, text/xml;q=0.8, text/html;q=0.7, unknown/unknown;q=0.1, application/unknown;q=0.1, */*;q=0.1',
+ );
+ $feed = $this->registry->create('File', array($href, $this->timeout, 5, $headers, $this->useragent));
+ if ($feed->success && ($feed->method & SIMPLEPIE_FILE_SOURCE_REMOTE === 0 || ($feed->status_code === 200 || $feed->status_code > 206 && $feed->status_code < 300)) && $this->is_feed($feed, true))
+ {
+ $feeds[$href] = $feed;
+ }
+ }
+ $done[] = $href;
+ }
+ }
+
+ return $feeds;
+ }
+
+ public function get_links()
+ {
+ if ($this->dom === null)
+ {
+ throw new SimplePie_Exception('DOMDocument not found, unable to use locator');
+ }
+
+ $links = $this->dom->getElementsByTagName('a');
+ foreach ($links as $link)
+ {
+ if ($link->hasAttribute('href'))
+ {
+ $href = trim($link->getAttribute('href'));
+ $parsed = $this->registry->call('Misc', 'parse_url', array($href));
+ if ($parsed['scheme'] === '' || preg_match('/^(https?|feed)?$/i', $parsed['scheme']))
+ {
+ if (method_exists($link, 'getLineNo') && $this->base_location < $link->getLineNo())
+ {
+ $href = $this->registry->call('Misc', 'absolutize_url', array(trim($link->getAttribute('href')), $this->base));
+ }
+ else
+ {
+ $href = $this->registry->call('Misc', 'absolutize_url', array(trim($link->getAttribute('href')), $this->http_base));
+ }
+ if ($href === false)
+ {
+ continue;
+ }
+
+ $current = $this->registry->call('Misc', 'parse_url', array($this->file->url));
+
+ if ($parsed['authority'] === '' || $parsed['authority'] === $current['authority'])
+ {
+ $this->local[] = $href;
+ }
+ else
+ {
+ $this->elsewhere[] = $href;
+ }
+ }
+ }
+ }
+ $this->local = array_unique($this->local);
+ $this->elsewhere = array_unique($this->elsewhere);
+ if (!empty($this->local) || !empty($this->elsewhere))
+ {
+ return true;
+ }
+ return null;
+ }
+
+ public function get_rel_link($rel)
+ {
+ if ($this->dom === null)
+ {
+ throw new SimplePie_Exception('DOMDocument not found, unable to use '.
+ 'locator');
+ }
+ if (!class_exists('DOMXpath'))
+ {
+ throw new SimplePie_Exception('DOMXpath not found, unable to use '.
+ 'get_rel_link');
+ }
+
+ $xpath = new DOMXpath($this->dom);
+ $query = '//a[@rel and @href] | //link[@rel and @href]';
+ foreach ($xpath->query($query) as $link)
+ {
+ $href = trim($link->getAttribute('href'));
+ $parsed = $this->registry->call('Misc', 'parse_url', array($href));
+ if ($parsed['scheme'] === '' ||
+ preg_match('/^https?$/i', $parsed['scheme']))
+ {
+ if (method_exists($link, 'getLineNo') &&
+ $this->base_location < $link->getLineNo())
+ {
+ $href =
+ $this->registry->call('Misc', 'absolutize_url',
+ array(trim($link->getAttribute('href')),
+ $this->base));
+ }
+ else
+ {
+ $href =
+ $this->registry->call('Misc', 'absolutize_url',
+ array(trim($link->getAttribute('href')),
+ $this->http_base));
+ }
+ if ($href === false)
+ {
+ return null;
+ }
+ $rel_values = explode(' ', strtolower($link->getAttribute('rel')));
+ if (in_array($rel, $rel_values))
+ {
+ return $href;
+ }
+ }
+ }
+ return null;
+ }
+
+ public function extension(&$array)
+ {
+ foreach ($array as $key => $value)
+ {
+ if ($this->checked_feeds === $this->max_checked_feeds)
+ {
+ break;
+ }
+ if (in_array(strtolower(strrchr($value, '.')), array('.rss', '.rdf', '.atom', '.xml')))
+ {
+ $this->checked_feeds++;
+
+ $headers = array(
+ 'Accept' => 'application/atom+xml, application/rss+xml, application/rdf+xml;q=0.9, application/xml;q=0.8, text/xml;q=0.8, text/html;q=0.7, unknown/unknown;q=0.1, application/unknown;q=0.1, */*;q=0.1',
+ );
+ $feed = $this->registry->create('File', array($value, $this->timeout, 5, $headers, $this->useragent));
+ if ($feed->success && ($feed->method & SIMPLEPIE_FILE_SOURCE_REMOTE === 0 || ($feed->status_code === 200 || $feed->status_code > 206 && $feed->status_code < 300)) && $this->is_feed($feed))
+ {
+ return array($feed);
+ }
+ else
+ {
+ unset($array[$key]);
+ }
+ }
+ }
+ return null;
+ }
+
+ public function body(&$array)
+ {
+ foreach ($array as $key => $value)
+ {
+ if ($this->checked_feeds === $this->max_checked_feeds)
+ {
+ break;
+ }
+ if (preg_match('/(rss|rdf|atom|xml)/i', $value))
+ {
+ $this->checked_feeds++;
+ $headers = array(
+ 'Accept' => 'application/atom+xml, application/rss+xml, application/rdf+xml;q=0.9, application/xml;q=0.8, text/xml;q=0.8, text/html;q=0.7, unknown/unknown;q=0.1, application/unknown;q=0.1, */*;q=0.1',
+ );
+ $feed = $this->registry->create('File', array($value, $this->timeout, 5, null, $this->useragent));
+ if ($feed->success && ($feed->method & SIMPLEPIE_FILE_SOURCE_REMOTE === 0 || ($feed->status_code === 200 || $feed->status_code > 206 && $feed->status_code < 300)) && $this->is_feed($feed))
+ {
+ return array($feed);
+ }
+ else
+ {
+ unset($array[$key]);
+ }
+ }
+ }
+ return null;
+ }
+}
+
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Misc.php b/vendor/simplepie/simplepie/library/SimplePie/Misc.php
new file mode 100644
index 000000000..2e3107eb4
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Misc.php
@@ -0,0 +1,2279 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * Miscellanous utilities
+ *
+ * @package SimplePie
+ */
+class SimplePie_Misc
+{
+ public static function time_hms($seconds)
+ {
+ $time = '';
+
+ $hours = floor($seconds / 3600);
+ $remainder = $seconds % 3600;
+ if ($hours > 0)
+ {
+ $time .= $hours.':';
+ }
+
+ $minutes = floor($remainder / 60);
+ $seconds = $remainder % 60;
+ if ($minutes < 10 && $hours > 0)
+ {
+ $minutes = '0' . $minutes;
+ }
+ if ($seconds < 10)
+ {
+ $seconds = '0' . $seconds;
+ }
+
+ $time .= $minutes.':';
+ $time .= $seconds;
+
+ return $time;
+ }
+
+ public static function absolutize_url($relative, $base)
+ {
+ $iri = SimplePie_IRI::absolutize(new SimplePie_IRI($base), $relative);
+ if ($iri === false)
+ {
+ return false;
+ }
+ return $iri->get_uri();
+ }
+
+ /**
+ * Get a HTML/XML element from a HTML string
+ *
+ * @deprecated Use DOMDocument instead (parsing HTML with regex is bad!)
+ * @param string $realname Element name (including namespace prefix if applicable)
+ * @param string $string HTML document
+ * @return array
+ */
+ public static function get_element($realname, $string)
+ {
+ $return = array();
+ $name = preg_quote($realname, '/');
+ if (preg_match_all("/<($name)" . SIMPLEPIE_PCRE_HTML_ATTRIBUTE . "(>(.*)<\/$name>|(\/)?>)/siU", $string, $matches, PREG_SET_ORDER | PREG_OFFSET_CAPTURE))
+ {
+ for ($i = 0, $total_matches = count($matches); $i < $total_matches; $i++)
+ {
+ $return[$i]['tag'] = $realname;
+ $return[$i]['full'] = $matches[$i][0][0];
+ $return[$i]['offset'] = $matches[$i][0][1];
+ if (strlen($matches[$i][3][0]) <= 2)
+ {
+ $return[$i]['self_closing'] = true;
+ }
+ else
+ {
+ $return[$i]['self_closing'] = false;
+ $return[$i]['content'] = $matches[$i][4][0];
+ }
+ $return[$i]['attribs'] = array();
+ if (isset($matches[$i][2][0]) && preg_match_all('/[\x09\x0A\x0B\x0C\x0D\x20]+([^\x09\x0A\x0B\x0C\x0D\x20\x2F\x3E][^\x09\x0A\x0B\x0C\x0D\x20\x2F\x3D\x3E]*)(?:[\x09\x0A\x0B\x0C\x0D\x20]*=[\x09\x0A\x0B\x0C\x0D\x20]*(?:"([^"]*)"|\'([^\']*)\'|([^\x09\x0A\x0B\x0C\x0D\x20\x22\x27\x3E][^\x09\x0A\x0B\x0C\x0D\x20\x3E]*)?))?/', ' ' . $matches[$i][2][0] . ' ', $attribs, PREG_SET_ORDER))
+ {
+ for ($j = 0, $total_attribs = count($attribs); $j < $total_attribs; $j++)
+ {
+ if (count($attribs[$j]) === 2)
+ {
+ $attribs[$j][2] = $attribs[$j][1];
+ }
+ $return[$i]['attribs'][strtolower($attribs[$j][1])]['data'] = SimplePie_Misc::entities_decode(end($attribs[$j]));
+ }
+ }
+ }
+ }
+ return $return;
+ }
+
+ public static function element_implode($element)
+ {
+ $full = "<$element[tag]";
+ foreach ($element['attribs'] as $key => $value)
+ {
+ $key = strtolower($key);
+ $full .= " $key=\"" . htmlspecialchars($value['data'], ENT_COMPAT, 'UTF-8') . '"';
+ }
+ if ($element['self_closing'])
+ {
+ $full .= ' />';
+ }
+ else
+ {
+ $full .= ">$element[content]</$element[tag]>";
+ }
+ return $full;
+ }
+
+ public static function error($message, $level, $file, $line)
+ {
+ if ((ini_get('error_reporting') & $level) > 0)
+ {
+ switch ($level)
+ {
+ case E_USER_ERROR:
+ $note = 'PHP Error';
+ break;
+ case E_USER_WARNING:
+ $note = 'PHP Warning';
+ break;
+ case E_USER_NOTICE:
+ $note = 'PHP Notice';
+ break;
+ default:
+ $note = 'Unknown Error';
+ break;
+ }
+
+ $log_error = true;
+ if (!function_exists('error_log'))
+ {
+ $log_error = false;
+ }
+
+ $log_file = @ini_get('error_log');
+ if (!empty($log_file) && ('syslog' !== $log_file) && !@is_writable($log_file))
+ {
+ $log_error = false;
+ }
+
+ if ($log_error)
+ {
+ @error_log("$note: $message in $file on line $line", 0);
+ }
+ }
+
+ return $message;
+ }
+
+ public static function fix_protocol($url, $http = 1)
+ {
+ $url = SimplePie_Misc::normalize_url($url);
+ $parsed = SimplePie_Misc::parse_url($url);
+ if ($parsed['scheme'] !== '' && $parsed['scheme'] !== 'http' && $parsed['scheme'] !== 'https')
+ {
+ return SimplePie_Misc::fix_protocol(SimplePie_Misc::compress_parse_url('http', $parsed['authority'], $parsed['path'], $parsed['query'], $parsed['fragment']), $http);
+ }
+
+ if ($parsed['scheme'] === '' && $parsed['authority'] === '' && !file_exists($url))
+ {
+ return SimplePie_Misc::fix_protocol(SimplePie_Misc::compress_parse_url('http', $parsed['path'], '', $parsed['query'], $parsed['fragment']), $http);
+ }
+
+ if ($http === 2 && $parsed['scheme'] !== '')
+ {
+ return "feed:$url";
+ }
+ elseif ($http === 3 && strtolower($parsed['scheme']) === 'http')
+ {
+ return substr_replace($url, 'podcast', 0, 4);
+ }
+ elseif ($http === 4 && strtolower($parsed['scheme']) === 'http')
+ {
+ return substr_replace($url, 'itpc', 0, 4);
+ }
+ else
+ {
+ return $url;
+ }
+ }
+
+ public static function array_merge_recursive($array1, $array2)
+ {
+ foreach ($array2 as $key => $value)
+ {
+ if (is_array($value))
+ {
+ $array1[$key] = SimplePie_Misc::array_merge_recursive($array1[$key], $value);
+ }
+ else
+ {
+ $array1[$key] = $value;
+ }
+ }
+
+ return $array1;
+ }
+
+ public static function parse_url($url)
+ {
+ $iri = new SimplePie_IRI($url);
+ return array(
+ 'scheme' => (string) $iri->scheme,
+ 'authority' => (string) $iri->authority,
+ 'path' => (string) $iri->path,
+ 'query' => (string) $iri->query,
+ 'fragment' => (string) $iri->fragment
+ );
+ }
+
+ public static function compress_parse_url($scheme = '', $authority = '', $path = '', $query = '', $fragment = '')
+ {
+ $iri = new SimplePie_IRI('');
+ $iri->scheme = $scheme;
+ $iri->authority = $authority;
+ $iri->path = $path;
+ $iri->query = $query;
+ $iri->fragment = $fragment;
+ return $iri->get_uri();
+ }
+
+ public static function normalize_url($url)
+ {
+ $iri = new SimplePie_IRI($url);
+ return $iri->get_uri();
+ }
+
+ public static function percent_encoding_normalization($match)
+ {
+ $integer = hexdec($match[1]);
+ if ($integer >= 0x41 && $integer <= 0x5A || $integer >= 0x61 && $integer <= 0x7A || $integer >= 0x30 && $integer <= 0x39 || $integer === 0x2D || $integer === 0x2E || $integer === 0x5F || $integer === 0x7E)
+ {
+ return chr($integer);
+ }
+ else
+ {
+ return strtoupper($match[0]);
+ }
+ }
+
+ /**
+ * Converts a Windows-1252 encoded string to a UTF-8 encoded string
+ *
+ * @static
+ * @param string $string Windows-1252 encoded string
+ * @return string UTF-8 encoded string
+ */
+ public static function windows_1252_to_utf8($string)
+ {
+ static $convert_table = array("\x80" => "\xE2\x82\xAC", "\x81" => "\xEF\xBF\xBD", "\x82" => "\xE2\x80\x9A", "\x83" => "\xC6\x92", "\x84" => "\xE2\x80\x9E", "\x85" => "\xE2\x80\xA6", "\x86" => "\xE2\x80\xA0", "\x87" => "\xE2\x80\xA1", "\x88" => "\xCB\x86", "\x89" => "\xE2\x80\xB0", "\x8A" => "\xC5\xA0", "\x8B" => "\xE2\x80\xB9", "\x8C" => "\xC5\x92", "\x8D" => "\xEF\xBF\xBD", "\x8E" => "\xC5\xBD", "\x8F" => "\xEF\xBF\xBD", "\x90" => "\xEF\xBF\xBD", "\x91" => "\xE2\x80\x98", "\x92" => "\xE2\x80\x99", "\x93" => "\xE2\x80\x9C", "\x94" => "\xE2\x80\x9D", "\x95" => "\xE2\x80\xA2", "\x96" => "\xE2\x80\x93", "\x97" => "\xE2\x80\x94", "\x98" => "\xCB\x9C", "\x99" => "\xE2\x84\xA2", "\x9A" => "\xC5\xA1", "\x9B" => "\xE2\x80\xBA", "\x9C" => "\xC5\x93", "\x9D" => "\xEF\xBF\xBD", "\x9E" => "\xC5\xBE", "\x9F" => "\xC5\xB8", "\xA0" => "\xC2\xA0", "\xA1" => "\xC2\xA1", "\xA2" => "\xC2\xA2", "\xA3" => "\xC2\xA3", "\xA4" => "\xC2\xA4", "\xA5" => "\xC2\xA5", "\xA6" => "\xC2\xA6", "\xA7" => "\xC2\xA7", "\xA8" => "\xC2\xA8", "\xA9" => "\xC2\xA9", "\xAA" => "\xC2\xAA", "\xAB" => "\xC2\xAB", "\xAC" => "\xC2\xAC", "\xAD" => "\xC2\xAD", "\xAE" => "\xC2\xAE", "\xAF" => "\xC2\xAF", "\xB0" => "\xC2\xB0", "\xB1" => "\xC2\xB1", "\xB2" => "\xC2\xB2", "\xB3" => "\xC2\xB3", "\xB4" => "\xC2\xB4", "\xB5" => "\xC2\xB5", "\xB6" => "\xC2\xB6", "\xB7" => "\xC2\xB7", "\xB8" => "\xC2\xB8", "\xB9" => "\xC2\xB9", "\xBA" => "\xC2\xBA", "\xBB" => "\xC2\xBB", "\xBC" => "\xC2\xBC", "\xBD" => "\xC2\xBD", "\xBE" => "\xC2\xBE", "\xBF" => "\xC2\xBF", "\xC0" => "\xC3\x80", "\xC1" => "\xC3\x81", "\xC2" => "\xC3\x82", "\xC3" => "\xC3\x83", "\xC4" => "\xC3\x84", "\xC5" => "\xC3\x85", "\xC6" => "\xC3\x86", "\xC7" => "\xC3\x87", "\xC8" => "\xC3\x88", "\xC9" => "\xC3\x89", "\xCA" => "\xC3\x8A", "\xCB" => "\xC3\x8B", "\xCC" => "\xC3\x8C", "\xCD" => "\xC3\x8D", "\xCE" => "\xC3\x8E", "\xCF" => "\xC3\x8F", "\xD0" => "\xC3\x90", "\xD1" => "\xC3\x91", "\xD2" => "\xC3\x92", "\xD3" => "\xC3\x93", "\xD4" => "\xC3\x94", "\xD5" => "\xC3\x95", "\xD6" => "\xC3\x96", "\xD7" => "\xC3\x97", "\xD8" => "\xC3\x98", "\xD9" => "\xC3\x99", "\xDA" => "\xC3\x9A", "\xDB" => "\xC3\x9B", "\xDC" => "\xC3\x9C", "\xDD" => "\xC3\x9D", "\xDE" => "\xC3\x9E", "\xDF" => "\xC3\x9F", "\xE0" => "\xC3\xA0", "\xE1" => "\xC3\xA1", "\xE2" => "\xC3\xA2", "\xE3" => "\xC3\xA3", "\xE4" => "\xC3\xA4", "\xE5" => "\xC3\xA5", "\xE6" => "\xC3\xA6", "\xE7" => "\xC3\xA7", "\xE8" => "\xC3\xA8", "\xE9" => "\xC3\xA9", "\xEA" => "\xC3\xAA", "\xEB" => "\xC3\xAB", "\xEC" => "\xC3\xAC", "\xED" => "\xC3\xAD", "\xEE" => "\xC3\xAE", "\xEF" => "\xC3\xAF", "\xF0" => "\xC3\xB0", "\xF1" => "\xC3\xB1", "\xF2" => "\xC3\xB2", "\xF3" => "\xC3\xB3", "\xF4" => "\xC3\xB4", "\xF5" => "\xC3\xB5", "\xF6" => "\xC3\xB6", "\xF7" => "\xC3\xB7", "\xF8" => "\xC3\xB8", "\xF9" => "\xC3\xB9", "\xFA" => "\xC3\xBA", "\xFB" => "\xC3\xBB", "\xFC" => "\xC3\xBC", "\xFD" => "\xC3\xBD", "\xFE" => "\xC3\xBE", "\xFF" => "\xC3\xBF");
+
+ return strtr($string, $convert_table);
+ }
+
+ /**
+ * Change a string from one encoding to another
+ *
+ * @param string $data Raw data in $input encoding
+ * @param string $input Encoding of $data
+ * @param string $output Encoding you want
+ * @return string|boolean False if we can't convert it
+ */
+ public static function change_encoding($data, $input, $output)
+ {
+ $input = SimplePie_Misc::encoding($input);
+ $output = SimplePie_Misc::encoding($output);
+
+ // We fail to fail on non US-ASCII bytes
+ if ($input === 'US-ASCII')
+ {
+ static $non_ascii_octects = '';
+ if (!$non_ascii_octects)
+ {
+ for ($i = 0x80; $i <= 0xFF; $i++)
+ {
+ $non_ascii_octects .= chr($i);
+ }
+ }
+ $data = substr($data, 0, strcspn($data, $non_ascii_octects));
+ }
+
+ // This is first, as behaviour of this is completely predictable
+ if ($input === 'windows-1252' && $output === 'UTF-8')
+ {
+ return SimplePie_Misc::windows_1252_to_utf8($data);
+ }
+ // This is second, as behaviour of this varies only with PHP version (the middle part of this expression checks the encoding is supported).
+ elseif (function_exists('mb_convert_encoding') && ($return = SimplePie_Misc::change_encoding_mbstring($data, $input, $output)))
+ {
+ return $return;
+ }
+ // This is third, as behaviour of this varies with OS userland and PHP version
+ elseif (function_exists('iconv') && ($return = SimplePie_Misc::change_encoding_iconv($data, $input, $output)))
+ {
+ return $return;
+ }
+ // This is last, as behaviour of this varies with OS userland and PHP version
+ elseif (class_exists('\UConverter') && ($return = SimplePie_Misc::change_encoding_uconverter($data, $input, $output)))
+ {
+ return $return;
+ }
+ // If we can't do anything, just fail
+ else
+ {
+ return false;
+ }
+ }
+
+ protected static function change_encoding_mbstring($data, $input, $output)
+ {
+ if ($input === 'windows-949')
+ {
+ $input = 'EUC-KR';
+ }
+ if ($output === 'windows-949')
+ {
+ $output = 'EUC-KR';
+ }
+ if ($input === 'Windows-31J')
+ {
+ $input = 'SJIS';
+ }
+ if ($output === 'Windows-31J')
+ {
+ $output = 'SJIS';
+ }
+
+ // Check that the encoding is supported
+ if (@mb_convert_encoding("\x80", 'UTF-16BE', $input) === "\x00\x80")
+ {
+ return false;
+ }
+ if (!in_array($input, mb_list_encodings()))
+ {
+ return false;
+ }
+
+ // Let's do some conversion
+ if ($return = @mb_convert_encoding($data, $output, $input))
+ {
+ return $return;
+ }
+
+ return false;
+ }
+
+ protected static function change_encoding_iconv($data, $input, $output)
+ {
+ return @iconv($input, $output, $data);
+ }
+
+ /**
+ * @param string $data
+ * @param string $input
+ * @param string $output
+ * @return string|false
+ */
+ protected static function change_encoding_uconverter($data, $input, $output)
+ {
+ return @\UConverter::transcode($data, $output, $input);
+ }
+
+ /**
+ * Normalize an encoding name
+ *
+ * This is automatically generated by create.php
+ *
+ * To generate it, run `php create.php` on the command line, and copy the
+ * output to replace this function.
+ *
+ * @param string $charset Character set to standardise
+ * @return string Standardised name
+ */
+ public static function encoding($charset)
+ {
+ // Normalization from UTS #22
+ switch (strtolower(preg_replace('/(?:[^a-zA-Z0-9]+|([^0-9])0+)/', '\1', $charset)))
+ {
+ case 'adobestandardencoding':
+ case 'csadobestandardencoding':
+ return 'Adobe-Standard-Encoding';
+
+ case 'adobesymbolencoding':
+ case 'cshppsmath':
+ return 'Adobe-Symbol-Encoding';
+
+ case 'ami1251':
+ case 'amiga1251':
+ return 'Amiga-1251';
+
+ case 'ansix31101983':
+ case 'csat5001983':
+ case 'csiso99naplps':
+ case 'isoir99':
+ case 'naplps':
+ return 'ANSI_X3.110-1983';
+
+ case 'arabic7':
+ case 'asmo449':
+ case 'csiso89asmo449':
+ case 'iso9036':
+ case 'isoir89':
+ return 'ASMO_449';
+
+ case 'big5':
+ case 'csbig5':
+ return 'Big5';
+
+ case 'big5hkscs':
+ return 'Big5-HKSCS';
+
+ case 'bocu1':
+ case 'csbocu1':
+ return 'BOCU-1';
+
+ case 'brf':
+ case 'csbrf':
+ return 'BRF';
+
+ case 'bs4730':
+ case 'csiso4unitedkingdom':
+ case 'gb':
+ case 'iso646gb':
+ case 'isoir4':
+ case 'uk':
+ return 'BS_4730';
+
+ case 'bsviewdata':
+ case 'csiso47bsviewdata':
+ case 'isoir47':
+ return 'BS_viewdata';
+
+ case 'cesu8':
+ case 'cscesu8':
+ return 'CESU-8';
+
+ case 'ca':
+ case 'csa71':
+ case 'csaz243419851':
+ case 'csiso121canadian1':
+ case 'iso646ca':
+ case 'isoir121':
+ return 'CSA_Z243.4-1985-1';
+
+ case 'csa72':
+ case 'csaz243419852':
+ case 'csiso122canadian2':
+ case 'iso646ca2':
+ case 'isoir122':
+ return 'CSA_Z243.4-1985-2';
+
+ case 'csaz24341985gr':
+ case 'csiso123csaz24341985gr':
+ case 'isoir123':
+ return 'CSA_Z243.4-1985-gr';
+
+ case 'csiso139csn369103':
+ case 'csn369103':
+ case 'isoir139':
+ return 'CSN_369103';
+
+ case 'csdecmcs':
+ case 'dec':
+ case 'decmcs':
+ return 'DEC-MCS';
+
+ case 'csiso21german':
+ case 'de':
+ case 'din66003':
+ case 'iso646de':
+ case 'isoir21':
+ return 'DIN_66003';
+
+ case 'csdkus':
+ case 'dkus':
+ return 'dk-us';
+
+ case 'csiso646danish':
+ case 'dk':
+ case 'ds2089':
+ case 'iso646dk':
+ return 'DS_2089';
+
+ case 'csibmebcdicatde':
+ case 'ebcdicatde':
+ return 'EBCDIC-AT-DE';
+
+ case 'csebcdicatdea':
+ case 'ebcdicatdea':
+ return 'EBCDIC-AT-DE-A';
+
+ case 'csebcdiccafr':
+ case 'ebcdiccafr':
+ return 'EBCDIC-CA-FR';
+
+ case 'csebcdicdkno':
+ case 'ebcdicdkno':
+ return 'EBCDIC-DK-NO';
+
+ case 'csebcdicdknoa':
+ case 'ebcdicdknoa':
+ return 'EBCDIC-DK-NO-A';
+
+ case 'csebcdices':
+ case 'ebcdices':
+ return 'EBCDIC-ES';
+
+ case 'csebcdicesa':
+ case 'ebcdicesa':
+ return 'EBCDIC-ES-A';
+
+ case 'csebcdicess':
+ case 'ebcdicess':
+ return 'EBCDIC-ES-S';
+
+ case 'csebcdicfise':
+ case 'ebcdicfise':
+ return 'EBCDIC-FI-SE';
+
+ case 'csebcdicfisea':
+ case 'ebcdicfisea':
+ return 'EBCDIC-FI-SE-A';
+
+ case 'csebcdicfr':
+ case 'ebcdicfr':
+ return 'EBCDIC-FR';
+
+ case 'csebcdicit':
+ case 'ebcdicit':
+ return 'EBCDIC-IT';
+
+ case 'csebcdicpt':
+ case 'ebcdicpt':
+ return 'EBCDIC-PT';
+
+ case 'csebcdicuk':
+ case 'ebcdicuk':
+ return 'EBCDIC-UK';
+
+ case 'csebcdicus':
+ case 'ebcdicus':
+ return 'EBCDIC-US';
+
+ case 'csiso111ecmacyrillic':
+ case 'ecmacyrillic':
+ case 'isoir111':
+ case 'koi8e':
+ return 'ECMA-cyrillic';
+
+ case 'csiso17spanish':
+ case 'es':
+ case 'iso646es':
+ case 'isoir17':
+ return 'ES';
+
+ case 'csiso85spanish2':
+ case 'es2':
+ case 'iso646es2':
+ case 'isoir85':
+ return 'ES2';
+
+ case 'cseucpkdfmtjapanese':
+ case 'eucjp':
+ case 'extendedunixcodepackedformatforjapanese':
+ return 'EUC-JP';
+
+ case 'cseucfixwidjapanese':
+ case 'extendedunixcodefixedwidthforjapanese':
+ return 'Extended_UNIX_Code_Fixed_Width_for_Japanese';
+
+ case 'gb18030':
+ return 'GB18030';
+
+ case 'chinese':
+ case 'cp936':
+ case 'csgb2312':
+ case 'csiso58gb231280':
+ case 'gb2312':
+ case 'gb231280':
+ case 'gbk':
+ case 'isoir58':
+ case 'ms936':
+ case 'windows936':
+ return 'GBK';
+
+ case 'cn':
+ case 'csiso57gb1988':
+ case 'gb198880':
+ case 'iso646cn':
+ case 'isoir57':
+ return 'GB_1988-80';
+
+ case 'csiso153gost1976874':
+ case 'gost1976874':
+ case 'isoir153':
+ case 'stsev35888':
+ return 'GOST_19768-74';
+
+ case 'csiso150':
+ case 'csiso150greekccitt':
+ case 'greekccitt':
+ case 'isoir150':
+ return 'greek-ccitt';
+
+ case 'csiso88greek7':
+ case 'greek7':
+ case 'isoir88':
+ return 'greek7';
+
+ case 'csiso18greek7old':
+ case 'greek7old':
+ case 'isoir18':
+ return 'greek7-old';
+
+ case 'cshpdesktop':
+ case 'hpdesktop':
+ return 'HP-DeskTop';
+
+ case 'cshplegal':
+ case 'hplegal':
+ return 'HP-Legal';
+
+ case 'cshpmath8':
+ case 'hpmath8':
+ return 'HP-Math8';
+
+ case 'cshppifont':
+ case 'hppifont':
+ return 'HP-Pi-font';
+
+ case 'cshproman8':
+ case 'hproman8':
+ case 'r8':
+ case 'roman8':
+ return 'hp-roman8';
+
+ case 'hzgb2312':
+ return 'HZ-GB-2312';
+
+ case 'csibmsymbols':
+ case 'ibmsymbols':
+ return 'IBM-Symbols';
+
+ case 'csibmthai':
+ case 'ibmthai':
+ return 'IBM-Thai';
+
+ case 'cp37':
+ case 'csibm37':
+ case 'ebcdiccpca':
+ case 'ebcdiccpnl':
+ case 'ebcdiccpus':
+ case 'ebcdiccpwt':
+ case 'ibm37':
+ return 'IBM037';
+
+ case 'cp38':
+ case 'csibm38':
+ case 'ebcdicint':
+ case 'ibm38':
+ return 'IBM038';
+
+ case 'cp273':
+ case 'csibm273':
+ case 'ibm273':
+ return 'IBM273';
+
+ case 'cp274':
+ case 'csibm274':
+ case 'ebcdicbe':
+ case 'ibm274':
+ return 'IBM274';
+
+ case 'cp275':
+ case 'csibm275':
+ case 'ebcdicbr':
+ case 'ibm275':
+ return 'IBM275';
+
+ case 'csibm277':
+ case 'ebcdiccpdk':
+ case 'ebcdiccpno':
+ case 'ibm277':
+ return 'IBM277';
+
+ case 'cp278':
+ case 'csibm278':
+ case 'ebcdiccpfi':
+ case 'ebcdiccpse':
+ case 'ibm278':
+ return 'IBM278';
+
+ case 'cp280':
+ case 'csibm280':
+ case 'ebcdiccpit':
+ case 'ibm280':
+ return 'IBM280';
+
+ case 'cp281':
+ case 'csibm281':
+ case 'ebcdicjpe':
+ case 'ibm281':
+ return 'IBM281';
+
+ case 'cp284':
+ case 'csibm284':
+ case 'ebcdiccpes':
+ case 'ibm284':
+ return 'IBM284';
+
+ case 'cp285':
+ case 'csibm285':
+ case 'ebcdiccpgb':
+ case 'ibm285':
+ return 'IBM285';
+
+ case 'cp290':
+ case 'csibm290':
+ case 'ebcdicjpkana':
+ case 'ibm290':
+ return 'IBM290';
+
+ case 'cp297':
+ case 'csibm297':
+ case 'ebcdiccpfr':
+ case 'ibm297':
+ return 'IBM297';
+
+ case 'cp420':
+ case 'csibm420':
+ case 'ebcdiccpar1':
+ case 'ibm420':
+ return 'IBM420';
+
+ case 'cp423':
+ case 'csibm423':
+ case 'ebcdiccpgr':
+ case 'ibm423':
+ return 'IBM423';
+
+ case 'cp424':
+ case 'csibm424':
+ case 'ebcdiccphe':
+ case 'ibm424':
+ return 'IBM424';
+
+ case '437':
+ case 'cp437':
+ case 'cspc8codepage437':
+ case 'ibm437':
+ return 'IBM437';
+
+ case 'cp500':
+ case 'csibm500':
+ case 'ebcdiccpbe':
+ case 'ebcdiccpch':
+ case 'ibm500':
+ return 'IBM500';
+
+ case 'cp775':
+ case 'cspc775baltic':
+ case 'ibm775':
+ return 'IBM775';
+
+ case '850':
+ case 'cp850':
+ case 'cspc850multilingual':
+ case 'ibm850':
+ return 'IBM850';
+
+ case '851':
+ case 'cp851':
+ case 'csibm851':
+ case 'ibm851':
+ return 'IBM851';
+
+ case '852':
+ case 'cp852':
+ case 'cspcp852':
+ case 'ibm852':
+ return 'IBM852';
+
+ case '855':
+ case 'cp855':
+ case 'csibm855':
+ case 'ibm855':
+ return 'IBM855';
+
+ case '857':
+ case 'cp857':
+ case 'csibm857':
+ case 'ibm857':
+ return 'IBM857';
+
+ case 'ccsid858':
+ case 'cp858':
+ case 'ibm858':
+ case 'pcmultilingual850euro':
+ return 'IBM00858';
+
+ case '860':
+ case 'cp860':
+ case 'csibm860':
+ case 'ibm860':
+ return 'IBM860';
+
+ case '861':
+ case 'cp861':
+ case 'cpis':
+ case 'csibm861':
+ case 'ibm861':
+ return 'IBM861';
+
+ case '862':
+ case 'cp862':
+ case 'cspc862latinhebrew':
+ case 'ibm862':
+ return 'IBM862';
+
+ case '863':
+ case 'cp863':
+ case 'csibm863':
+ case 'ibm863':
+ return 'IBM863';
+
+ case 'cp864':
+ case 'csibm864':
+ case 'ibm864':
+ return 'IBM864';
+
+ case '865':
+ case 'cp865':
+ case 'csibm865':
+ case 'ibm865':
+ return 'IBM865';
+
+ case '866':
+ case 'cp866':
+ case 'csibm866':
+ case 'ibm866':
+ return 'IBM866';
+
+ case 'cp868':
+ case 'cpar':
+ case 'csibm868':
+ case 'ibm868':
+ return 'IBM868';
+
+ case '869':
+ case 'cp869':
+ case 'cpgr':
+ case 'csibm869':
+ case 'ibm869':
+ return 'IBM869';
+
+ case 'cp870':
+ case 'csibm870':
+ case 'ebcdiccproece':
+ case 'ebcdiccpyu':
+ case 'ibm870':
+ return 'IBM870';
+
+ case 'cp871':
+ case 'csibm871':
+ case 'ebcdiccpis':
+ case 'ibm871':
+ return 'IBM871';
+
+ case 'cp880':
+ case 'csibm880':
+ case 'ebcdiccyrillic':
+ case 'ibm880':
+ return 'IBM880';
+
+ case 'cp891':
+ case 'csibm891':
+ case 'ibm891':
+ return 'IBM891';
+
+ case 'cp903':
+ case 'csibm903':
+ case 'ibm903':
+ return 'IBM903';
+
+ case '904':
+ case 'cp904':
+ case 'csibbm904':
+ case 'ibm904':
+ return 'IBM904';
+
+ case 'cp905':
+ case 'csibm905':
+ case 'ebcdiccptr':
+ case 'ibm905':
+ return 'IBM905';
+
+ case 'cp918':
+ case 'csibm918':
+ case 'ebcdiccpar2':
+ case 'ibm918':
+ return 'IBM918';
+
+ case 'ccsid924':
+ case 'cp924':
+ case 'ebcdiclatin9euro':
+ case 'ibm924':
+ return 'IBM00924';
+
+ case 'cp1026':
+ case 'csibm1026':
+ case 'ibm1026':
+ return 'IBM1026';
+
+ case 'ibm1047':
+ return 'IBM1047';
+
+ case 'ccsid1140':
+ case 'cp1140':
+ case 'ebcdicus37euro':
+ case 'ibm1140':
+ return 'IBM01140';
+
+ case 'ccsid1141':
+ case 'cp1141':
+ case 'ebcdicde273euro':
+ case 'ibm1141':
+ return 'IBM01141';
+
+ case 'ccsid1142':
+ case 'cp1142':
+ case 'ebcdicdk277euro':
+ case 'ebcdicno277euro':
+ case 'ibm1142':
+ return 'IBM01142';
+
+ case 'ccsid1143':
+ case 'cp1143':
+ case 'ebcdicfi278euro':
+ case 'ebcdicse278euro':
+ case 'ibm1143':
+ return 'IBM01143';
+
+ case 'ccsid1144':
+ case 'cp1144':
+ case 'ebcdicit280euro':
+ case 'ibm1144':
+ return 'IBM01144';
+
+ case 'ccsid1145':
+ case 'cp1145':
+ case 'ebcdices284euro':
+ case 'ibm1145':
+ return 'IBM01145';
+
+ case 'ccsid1146':
+ case 'cp1146':
+ case 'ebcdicgb285euro':
+ case 'ibm1146':
+ return 'IBM01146';
+
+ case 'ccsid1147':
+ case 'cp1147':
+ case 'ebcdicfr297euro':
+ case 'ibm1147':
+ return 'IBM01147';
+
+ case 'ccsid1148':
+ case 'cp1148':
+ case 'ebcdicinternational500euro':
+ case 'ibm1148':
+ return 'IBM01148';
+
+ case 'ccsid1149':
+ case 'cp1149':
+ case 'ebcdicis871euro':
+ case 'ibm1149':
+ return 'IBM01149';
+
+ case 'csiso143iecp271':
+ case 'iecp271':
+ case 'isoir143':
+ return 'IEC_P27-1';
+
+ case 'csiso49inis':
+ case 'inis':
+ case 'isoir49':
+ return 'INIS';
+
+ case 'csiso50inis8':
+ case 'inis8':
+ case 'isoir50':
+ return 'INIS-8';
+
+ case 'csiso51iniscyrillic':
+ case 'iniscyrillic':
+ case 'isoir51':
+ return 'INIS-cyrillic';
+
+ case 'csinvariant':
+ case 'invariant':
+ return 'INVARIANT';
+
+ case 'iso2022cn':
+ return 'ISO-2022-CN';
+
+ case 'iso2022cnext':
+ return 'ISO-2022-CN-EXT';
+
+ case 'csiso2022jp':
+ case 'iso2022jp':
+ return 'ISO-2022-JP';
+
+ case 'csiso2022jp2':
+ case 'iso2022jp2':
+ return 'ISO-2022-JP-2';
+
+ case 'csiso2022kr':
+ case 'iso2022kr':
+ return 'ISO-2022-KR';
+
+ case 'cswindows30latin1':
+ case 'iso88591windows30latin1':
+ return 'ISO-8859-1-Windows-3.0-Latin-1';
+
+ case 'cswindows31latin1':
+ case 'iso88591windows31latin1':
+ return 'ISO-8859-1-Windows-3.1-Latin-1';
+
+ case 'csisolatin2':
+ case 'iso88592':
+ case 'iso885921987':
+ case 'isoir101':
+ case 'l2':
+ case 'latin2':
+ return 'ISO-8859-2';
+
+ case 'cswindows31latin2':
+ case 'iso88592windowslatin2':
+ return 'ISO-8859-2-Windows-Latin-2';
+
+ case 'csisolatin3':
+ case 'iso88593':
+ case 'iso885931988':
+ case 'isoir109':
+ case 'l3':
+ case 'latin3':
+ return 'ISO-8859-3';
+
+ case 'csisolatin4':
+ case 'iso88594':
+ case 'iso885941988':
+ case 'isoir110':
+ case 'l4':
+ case 'latin4':
+ return 'ISO-8859-4';
+
+ case 'csisolatincyrillic':
+ case 'cyrillic':
+ case 'iso88595':
+ case 'iso885951988':
+ case 'isoir144':
+ return 'ISO-8859-5';
+
+ case 'arabic':
+ case 'asmo708':
+ case 'csisolatinarabic':
+ case 'ecma114':
+ case 'iso88596':
+ case 'iso885961987':
+ case 'isoir127':
+ return 'ISO-8859-6';
+
+ case 'csiso88596e':
+ case 'iso88596e':
+ return 'ISO-8859-6-E';
+
+ case 'csiso88596i':
+ case 'iso88596i':
+ return 'ISO-8859-6-I';
+
+ case 'csisolatingreek':
+ case 'ecma118':
+ case 'elot928':
+ case 'greek':
+ case 'greek8':
+ case 'iso88597':
+ case 'iso885971987':
+ case 'isoir126':
+ return 'ISO-8859-7';
+
+ case 'csisolatinhebrew':
+ case 'hebrew':
+ case 'iso88598':
+ case 'iso885981988':
+ case 'isoir138':
+ return 'ISO-8859-8';
+
+ case 'csiso88598e':
+ case 'iso88598e':
+ return 'ISO-8859-8-E';
+
+ case 'csiso88598i':
+ case 'iso88598i':
+ return 'ISO-8859-8-I';
+
+ case 'cswindows31latin5':
+ case 'iso88599windowslatin5':
+ return 'ISO-8859-9-Windows-Latin-5';
+
+ case 'csisolatin6':
+ case 'iso885910':
+ case 'iso8859101992':
+ case 'isoir157':
+ case 'l6':
+ case 'latin6':
+ return 'ISO-8859-10';
+
+ case 'iso885913':
+ return 'ISO-8859-13';
+
+ case 'iso885914':
+ case 'iso8859141998':
+ case 'isoceltic':
+ case 'isoir199':
+ case 'l8':
+ case 'latin8':
+ return 'ISO-8859-14';
+
+ case 'iso885915':
+ case 'latin9':
+ return 'ISO-8859-15';
+
+ case 'iso885916':
+ case 'iso8859162001':
+ case 'isoir226':
+ case 'l10':
+ case 'latin10':
+ return 'ISO-8859-16';
+
+ case 'iso10646j1':
+ return 'ISO-10646-J-1';
+
+ case 'csunicode':
+ case 'iso10646ucs2':
+ return 'ISO-10646-UCS-2';
+
+ case 'csucs4':
+ case 'iso10646ucs4':
+ return 'ISO-10646-UCS-4';
+
+ case 'csunicodeascii':
+ case 'iso10646ucsbasic':
+ return 'ISO-10646-UCS-Basic';
+
+ case 'csunicodelatin1':
+ case 'iso10646':
+ case 'iso10646unicodelatin1':
+ return 'ISO-10646-Unicode-Latin1';
+
+ case 'csiso10646utf1':
+ case 'iso10646utf1':
+ return 'ISO-10646-UTF-1';
+
+ case 'csiso115481':
+ case 'iso115481':
+ case 'isotr115481':
+ return 'ISO-11548-1';
+
+ case 'csiso90':
+ case 'isoir90':
+ return 'iso-ir-90';
+
+ case 'csunicodeibm1261':
+ case 'isounicodeibm1261':
+ return 'ISO-Unicode-IBM-1261';
+
+ case 'csunicodeibm1264':
+ case 'isounicodeibm1264':
+ return 'ISO-Unicode-IBM-1264';
+
+ case 'csunicodeibm1265':
+ case 'isounicodeibm1265':
+ return 'ISO-Unicode-IBM-1265';
+
+ case 'csunicodeibm1268':
+ case 'isounicodeibm1268':
+ return 'ISO-Unicode-IBM-1268';
+
+ case 'csunicodeibm1276':
+ case 'isounicodeibm1276':
+ return 'ISO-Unicode-IBM-1276';
+
+ case 'csiso646basic1983':
+ case 'iso646basic1983':
+ case 'ref':
+ return 'ISO_646.basic:1983';
+
+ case 'csiso2intlrefversion':
+ case 'irv':
+ case 'iso646irv1983':
+ case 'isoir2':
+ return 'ISO_646.irv:1983';
+
+ case 'csiso2033':
+ case 'e13b':
+ case 'iso20331983':
+ case 'isoir98':
+ return 'ISO_2033-1983';
+
+ case 'csiso5427cyrillic':
+ case 'iso5427':
+ case 'isoir37':
+ return 'ISO_5427';
+
+ case 'iso5427cyrillic1981':
+ case 'iso54271981':
+ case 'isoir54':
+ return 'ISO_5427:1981';
+
+ case 'csiso5428greek':
+ case 'iso54281980':
+ case 'isoir55':
+ return 'ISO_5428:1980';
+
+ case 'csiso6937add':
+ case 'iso6937225':
+ case 'isoir152':
+ return 'ISO_6937-2-25';
+
+ case 'csisotextcomm':
+ case 'iso69372add':
+ case 'isoir142':
+ return 'ISO_6937-2-add';
+
+ case 'csiso8859supp':
+ case 'iso8859supp':
+ case 'isoir154':
+ case 'latin125':
+ return 'ISO_8859-supp';
+
+ case 'csiso10367box':
+ case 'iso10367box':
+ case 'isoir155':
+ return 'ISO_10367-box';
+
+ case 'csiso15italian':
+ case 'iso646it':
+ case 'isoir15':
+ case 'it':
+ return 'IT';
+
+ case 'csiso13jisc6220jp':
+ case 'isoir13':
+ case 'jisc62201969':
+ case 'jisc62201969jp':
+ case 'katakana':
+ case 'x2017':
+ return 'JIS_C6220-1969-jp';
+
+ case 'csiso14jisc6220ro':
+ case 'iso646jp':
+ case 'isoir14':
+ case 'jisc62201969ro':
+ case 'jp':
+ return 'JIS_C6220-1969-ro';
+
+ case 'csiso42jisc62261978':
+ case 'isoir42':
+ case 'jisc62261978':
+ return 'JIS_C6226-1978';
+
+ case 'csiso87jisx208':
+ case 'isoir87':
+ case 'jisc62261983':
+ case 'jisx2081983':
+ case 'x208':
+ return 'JIS_C6226-1983';
+
+ case 'csiso91jisc62291984a':
+ case 'isoir91':
+ case 'jisc62291984a':
+ case 'jpocra':
+ return 'JIS_C6229-1984-a';
+
+ case 'csiso92jisc62991984b':
+ case 'iso646jpocrb':
+ case 'isoir92':
+ case 'jisc62291984b':
+ case 'jpocrb':
+ return 'JIS_C6229-1984-b';
+
+ case 'csiso93jis62291984badd':
+ case 'isoir93':
+ case 'jisc62291984badd':
+ case 'jpocrbadd':
+ return 'JIS_C6229-1984-b-add';
+
+ case 'csiso94jis62291984hand':
+ case 'isoir94':
+ case 'jisc62291984hand':
+ case 'jpocrhand':
+ return 'JIS_C6229-1984-hand';
+
+ case 'csiso95jis62291984handadd':
+ case 'isoir95':
+ case 'jisc62291984handadd':
+ case 'jpocrhandadd':
+ return 'JIS_C6229-1984-hand-add';
+
+ case 'csiso96jisc62291984kana':
+ case 'isoir96':
+ case 'jisc62291984kana':
+ return 'JIS_C6229-1984-kana';
+
+ case 'csjisencoding':
+ case 'jisencoding':
+ return 'JIS_Encoding';
+
+ case 'cshalfwidthkatakana':
+ case 'jisx201':
+ case 'x201':
+ return 'JIS_X0201';
+
+ case 'csiso159jisx2121990':
+ case 'isoir159':
+ case 'jisx2121990':
+ case 'x212':
+ return 'JIS_X0212-1990';
+
+ case 'csiso141jusib1002':
+ case 'iso646yu':
+ case 'isoir141':
+ case 'js':
+ case 'jusib1002':
+ case 'yu':
+ return 'JUS_I.B1.002';
+
+ case 'csiso147macedonian':
+ case 'isoir147':
+ case 'jusib1003mac':
+ case 'macedonian':
+ return 'JUS_I.B1.003-mac';
+
+ case 'csiso146serbian':
+ case 'isoir146':
+ case 'jusib1003serb':
+ case 'serbian':
+ return 'JUS_I.B1.003-serb';
+
+ case 'koi7switched':
+ return 'KOI7-switched';
+
+ case 'cskoi8r':
+ case 'koi8r':
+ return 'KOI8-R';
+
+ case 'koi8u':
+ return 'KOI8-U';
+
+ case 'csksc5636':
+ case 'iso646kr':
+ case 'ksc5636':
+ return 'KSC5636';
+
+ case 'cskz1048':
+ case 'kz1048':
+ case 'rk1048':
+ case 'strk10482002':
+ return 'KZ-1048';
+
+ case 'csiso19latingreek':
+ case 'isoir19':
+ case 'latingreek':
+ return 'latin-greek';
+
+ case 'csiso27latingreek1':
+ case 'isoir27':
+ case 'latingreek1':
+ return 'Latin-greek-1';
+
+ case 'csiso158lap':
+ case 'isoir158':
+ case 'lap':
+ case 'latinlap':
+ return 'latin-lap';
+
+ case 'csmacintosh':
+ case 'mac':
+ case 'macintosh':
+ return 'macintosh';
+
+ case 'csmicrosoftpublishing':
+ case 'microsoftpublishing':
+ return 'Microsoft-Publishing';
+
+ case 'csmnem':
+ case 'mnem':
+ return 'MNEM';
+
+ case 'csmnemonic':
+ case 'mnemonic':
+ return 'MNEMONIC';
+
+ case 'csiso86hungarian':
+ case 'hu':
+ case 'iso646hu':
+ case 'isoir86':
+ case 'msz77953':
+ return 'MSZ_7795.3';
+
+ case 'csnatsdano':
+ case 'isoir91':
+ case 'natsdano':
+ return 'NATS-DANO';
+
+ case 'csnatsdanoadd':
+ case 'isoir92':
+ case 'natsdanoadd':
+ return 'NATS-DANO-ADD';
+
+ case 'csnatssefi':
+ case 'isoir81':
+ case 'natssefi':
+ return 'NATS-SEFI';
+
+ case 'csnatssefiadd':
+ case 'isoir82':
+ case 'natssefiadd':
+ return 'NATS-SEFI-ADD';
+
+ case 'csiso151cuba':
+ case 'cuba':
+ case 'iso646cu':
+ case 'isoir151':
+ case 'ncnc1081':
+ return 'NC_NC00-10:81';
+
+ case 'csiso69french':
+ case 'fr':
+ case 'iso646fr':
+ case 'isoir69':
+ case 'nfz62010':
+ return 'NF_Z_62-010';
+
+ case 'csiso25french':
+ case 'iso646fr1':
+ case 'isoir25':
+ case 'nfz620101973':
+ return 'NF_Z_62-010_(1973)';
+
+ case 'csiso60danishnorwegian':
+ case 'csiso60norwegian1':
+ case 'iso646no':
+ case 'isoir60':
+ case 'no':
+ case 'ns45511':
+ return 'NS_4551-1';
+
+ case 'csiso61norwegian2':
+ case 'iso646no2':
+ case 'isoir61':
+ case 'no2':
+ case 'ns45512':
+ return 'NS_4551-2';
+
+ case 'osdebcdicdf3irv':
+ return 'OSD_EBCDIC_DF03_IRV';
+
+ case 'osdebcdicdf41':
+ return 'OSD_EBCDIC_DF04_1';
+
+ case 'osdebcdicdf415':
+ return 'OSD_EBCDIC_DF04_15';
+
+ case 'cspc8danishnorwegian':
+ case 'pc8danishnorwegian':
+ return 'PC8-Danish-Norwegian';
+
+ case 'cspc8turkish':
+ case 'pc8turkish':
+ return 'PC8-Turkish';
+
+ case 'csiso16portuguese':
+ case 'iso646pt':
+ case 'isoir16':
+ case 'pt':
+ return 'PT';
+
+ case 'csiso84portuguese2':
+ case 'iso646pt2':
+ case 'isoir84':
+ case 'pt2':
+ return 'PT2';
+
+ case 'cp154':
+ case 'csptcp154':
+ case 'cyrillicasian':
+ case 'pt154':
+ case 'ptcp154':
+ return 'PTCP154';
+
+ case 'scsu':
+ return 'SCSU';
+
+ case 'csiso10swedish':
+ case 'fi':
+ case 'iso646fi':
+ case 'iso646se':
+ case 'isoir10':
+ case 'se':
+ case 'sen850200b':
+ return 'SEN_850200_B';
+
+ case 'csiso11swedishfornames':
+ case 'iso646se2':
+ case 'isoir11':
+ case 'se2':
+ case 'sen850200c':
+ return 'SEN_850200_C';
+
+ case 'csiso102t617bit':
+ case 'isoir102':
+ case 't617bit':
+ return 'T.61-7bit';
+
+ case 'csiso103t618bit':
+ case 'isoir103':
+ case 't61':
+ case 't618bit':
+ return 'T.61-8bit';
+
+ case 'csiso128t101g2':
+ case 'isoir128':
+ case 't101g2':
+ return 'T.101-G2';
+
+ case 'cstscii':
+ case 'tscii':
+ return 'TSCII';
+
+ case 'csunicode11':
+ case 'unicode11':
+ return 'UNICODE-1-1';
+
+ case 'csunicode11utf7':
+ case 'unicode11utf7':
+ return 'UNICODE-1-1-UTF-7';
+
+ case 'csunknown8bit':
+ case 'unknown8bit':
+ return 'UNKNOWN-8BIT';
+
+ case 'ansix341968':
+ case 'ansix341986':
+ case 'ascii':
+ case 'cp367':
+ case 'csascii':
+ case 'ibm367':
+ case 'iso646irv1991':
+ case 'iso646us':
+ case 'isoir6':
+ case 'us':
+ case 'usascii':
+ return 'US-ASCII';
+
+ case 'csusdk':
+ case 'usdk':
+ return 'us-dk';
+
+ case 'utf7':
+ return 'UTF-7';
+
+ case 'utf8':
+ return 'UTF-8';
+
+ case 'utf16':
+ return 'UTF-16';
+
+ case 'utf16be':
+ return 'UTF-16BE';
+
+ case 'utf16le':
+ return 'UTF-16LE';
+
+ case 'utf32':
+ return 'UTF-32';
+
+ case 'utf32be':
+ return 'UTF-32BE';
+
+ case 'utf32le':
+ return 'UTF-32LE';
+
+ case 'csventurainternational':
+ case 'venturainternational':
+ return 'Ventura-International';
+
+ case 'csventuramath':
+ case 'venturamath':
+ return 'Ventura-Math';
+
+ case 'csventuraus':
+ case 'venturaus':
+ return 'Ventura-US';
+
+ case 'csiso70videotexsupp1':
+ case 'isoir70':
+ case 'videotexsuppl':
+ return 'videotex-suppl';
+
+ case 'csviqr':
+ case 'viqr':
+ return 'VIQR';
+
+ case 'csviscii':
+ case 'viscii':
+ return 'VISCII';
+
+ case 'csshiftjis':
+ case 'cswindows31j':
+ case 'mskanji':
+ case 'shiftjis':
+ case 'windows31j':
+ return 'Windows-31J';
+
+ case 'iso885911':
+ case 'tis620':
+ return 'windows-874';
+
+ case 'cseuckr':
+ case 'csksc56011987':
+ case 'euckr':
+ case 'isoir149':
+ case 'korean':
+ case 'ksc5601':
+ case 'ksc56011987':
+ case 'ksc56011989':
+ case 'windows949':
+ return 'windows-949';
+
+ case 'windows1250':
+ return 'windows-1250';
+
+ case 'windows1251':
+ return 'windows-1251';
+
+ case 'cp819':
+ case 'csisolatin1':
+ case 'ibm819':
+ case 'iso88591':
+ case 'iso885911987':
+ case 'isoir100':
+ case 'l1':
+ case 'latin1':
+ case 'windows1252':
+ return 'windows-1252';
+
+ case 'windows1253':
+ return 'windows-1253';
+
+ case 'csisolatin5':
+ case 'iso88599':
+ case 'iso885991989':
+ case 'isoir148':
+ case 'l5':
+ case 'latin5':
+ case 'windows1254':
+ return 'windows-1254';
+
+ case 'windows1255':
+ return 'windows-1255';
+
+ case 'windows1256':
+ return 'windows-1256';
+
+ case 'windows1257':
+ return 'windows-1257';
+
+ case 'windows1258':
+ return 'windows-1258';
+
+ default:
+ return $charset;
+ }
+ }
+
+ public static function get_curl_version()
+ {
+ if (is_array($curl = curl_version()))
+ {
+ $curl = $curl['version'];
+ }
+ elseif (substr($curl, 0, 5) === 'curl/')
+ {
+ $curl = substr($curl, 5, strcspn($curl, "\x09\x0A\x0B\x0C\x0D", 5));
+ }
+ elseif (substr($curl, 0, 8) === 'libcurl/')
+ {
+ $curl = substr($curl, 8, strcspn($curl, "\x09\x0A\x0B\x0C\x0D", 8));
+ }
+ else
+ {
+ $curl = 0;
+ }
+ return $curl;
+ }
+
+ /**
+ * Strip HTML comments
+ *
+ * @param string $data Data to strip comments from
+ * @return string Comment stripped string
+ */
+ public static function strip_comments($data)
+ {
+ $output = '';
+ while (($start = strpos($data, '<!--')) !== false)
+ {
+ $output .= substr($data, 0, $start);
+ if (($end = strpos($data, '-->', $start)) !== false)
+ {
+ $data = substr_replace($data, '', 0, $end + 3);
+ }
+ else
+ {
+ $data = '';
+ }
+ }
+ return $output . $data;
+ }
+
+ public static function parse_date($dt)
+ {
+ $parser = SimplePie_Parse_Date::get();
+ return $parser->parse($dt);
+ }
+
+ /**
+ * Decode HTML entities
+ *
+ * @deprecated Use DOMDocument instead
+ * @param string $data Input data
+ * @return string Output data
+ */
+ public static function entities_decode($data)
+ {
+ $decoder = new SimplePie_Decode_HTML_Entities($data);
+ return $decoder->parse();
+ }
+
+ /**
+ * Remove RFC822 comments
+ *
+ * @param string $data Data to strip comments from
+ * @return string Comment stripped string
+ */
+ public static function uncomment_rfc822($string)
+ {
+ $string = (string) $string;
+ $position = 0;
+ $length = strlen($string);
+ $depth = 0;
+
+ $output = '';
+
+ while ($position < $length && ($pos = strpos($string, '(', $position)) !== false)
+ {
+ $output .= substr($string, $position, $pos - $position);
+ $position = $pos + 1;
+ if ($string[$pos - 1] !== '\\')
+ {
+ $depth++;
+ while ($depth && $position < $length)
+ {
+ $position += strcspn($string, '()', $position);
+ if ($string[$position - 1] === '\\')
+ {
+ $position++;
+ continue;
+ }
+ elseif (isset($string[$position]))
+ {
+ switch ($string[$position])
+ {
+ case '(':
+ $depth++;
+ break;
+
+ case ')':
+ $depth--;
+ break;
+ }
+ $position++;
+ }
+ else
+ {
+ break;
+ }
+ }
+ }
+ else
+ {
+ $output .= '(';
+ }
+ }
+ $output .= substr($string, $position);
+
+ return $output;
+ }
+
+ public static function parse_mime($mime)
+ {
+ if (($pos = strpos($mime, ';')) === false)
+ {
+ return trim($mime);
+ }
+ else
+ {
+ return trim(substr($mime, 0, $pos));
+ }
+ }
+
+ public static function atom_03_construct_type($attribs)
+ {
+ if (isset($attribs['']['mode']) && strtolower(trim($attribs['']['mode']) === 'base64'))
+ {
+ $mode = SIMPLEPIE_CONSTRUCT_BASE64;
+ }
+ else
+ {
+ $mode = SIMPLEPIE_CONSTRUCT_NONE;
+ }
+ if (isset($attribs['']['type']))
+ {
+ switch (strtolower(trim($attribs['']['type'])))
+ {
+ case 'text':
+ case 'text/plain':
+ return SIMPLEPIE_CONSTRUCT_TEXT | $mode;
+
+ case 'html':
+ case 'text/html':
+ return SIMPLEPIE_CONSTRUCT_HTML | $mode;
+
+ case 'xhtml':
+ case 'application/xhtml+xml':
+ return SIMPLEPIE_CONSTRUCT_XHTML | $mode;
+
+ default:
+ return SIMPLEPIE_CONSTRUCT_NONE | $mode;
+ }
+ }
+ else
+ {
+ return SIMPLEPIE_CONSTRUCT_TEXT | $mode;
+ }
+ }
+
+ public static function atom_10_construct_type($attribs)
+ {
+ if (isset($attribs['']['type']))
+ {
+ switch (strtolower(trim($attribs['']['type'])))
+ {
+ case 'text':
+ return SIMPLEPIE_CONSTRUCT_TEXT;
+
+ case 'html':
+ return SIMPLEPIE_CONSTRUCT_HTML;
+
+ case 'xhtml':
+ return SIMPLEPIE_CONSTRUCT_XHTML;
+
+ default:
+ return SIMPLEPIE_CONSTRUCT_NONE;
+ }
+ }
+ return SIMPLEPIE_CONSTRUCT_TEXT;
+ }
+
+ public static function atom_10_content_construct_type($attribs)
+ {
+ if (isset($attribs['']['type']))
+ {
+ $type = strtolower(trim($attribs['']['type']));
+ switch ($type)
+ {
+ case 'text':
+ return SIMPLEPIE_CONSTRUCT_TEXT;
+
+ case 'html':
+ return SIMPLEPIE_CONSTRUCT_HTML;
+
+ case 'xhtml':
+ return SIMPLEPIE_CONSTRUCT_XHTML;
+ }
+ if (in_array(substr($type, -4), array('+xml', '/xml')) || substr($type, 0, 5) === 'text/')
+ {
+ return SIMPLEPIE_CONSTRUCT_NONE;
+ }
+ else
+ {
+ return SIMPLEPIE_CONSTRUCT_BASE64;
+ }
+ }
+ else
+ {
+ return SIMPLEPIE_CONSTRUCT_TEXT;
+ }
+ }
+
+ public static function is_isegment_nz_nc($string)
+ {
+ return (bool) preg_match('/^([A-Za-z0-9\-._~\x{A0}-\x{D7FF}\x{F900}-\x{FDCF}\x{FDF0}-\x{FFEF}\x{10000}-\x{1FFFD}\x{20000}-\x{2FFFD}\x{30000}-\x{3FFFD}\x{40000}-\x{4FFFD}\x{50000}-\x{5FFFD}\x{60000}-\x{6FFFD}\x{70000}-\x{7FFFD}\x{80000}-\x{8FFFD}\x{90000}-\x{9FFFD}\x{A0000}-\x{AFFFD}\x{B0000}-\x{BFFFD}\x{C0000}-\x{CFFFD}\x{D0000}-\x{DFFFD}\x{E1000}-\x{EFFFD}!$&\'()*+,;=@]|(%[0-9ABCDEF]{2}))+$/u', $string);
+ }
+
+ public static function space_separated_tokens($string)
+ {
+ $space_characters = "\x20\x09\x0A\x0B\x0C\x0D";
+ $string_length = strlen($string);
+
+ $position = strspn($string, $space_characters);
+ $tokens = array();
+
+ while ($position < $string_length)
+ {
+ $len = strcspn($string, $space_characters, $position);
+ $tokens[] = substr($string, $position, $len);
+ $position += $len;
+ $position += strspn($string, $space_characters, $position);
+ }
+
+ return $tokens;
+ }
+
+ /**
+ * Converts a unicode codepoint to a UTF-8 character
+ *
+ * @static
+ * @param int $codepoint Unicode codepoint
+ * @return string UTF-8 character
+ */
+ public static function codepoint_to_utf8($codepoint)
+ {
+ $codepoint = (int) $codepoint;
+ if ($codepoint < 0)
+ {
+ return false;
+ }
+ else if ($codepoint <= 0x7f)
+ {
+ return chr($codepoint);
+ }
+ else if ($codepoint <= 0x7ff)
+ {
+ return chr(0xc0 | ($codepoint >> 6)) . chr(0x80 | ($codepoint & 0x3f));
+ }
+ else if ($codepoint <= 0xffff)
+ {
+ return chr(0xe0 | ($codepoint >> 12)) . chr(0x80 | (($codepoint >> 6) & 0x3f)) . chr(0x80 | ($codepoint & 0x3f));
+ }
+ else if ($codepoint <= 0x10ffff)
+ {
+ return chr(0xf0 | ($codepoint >> 18)) . chr(0x80 | (($codepoint >> 12) & 0x3f)) . chr(0x80 | (($codepoint >> 6) & 0x3f)) . chr(0x80 | ($codepoint & 0x3f));
+ }
+ else
+ {
+ // U+FFFD REPLACEMENT CHARACTER
+ return "\xEF\xBF\xBD";
+ }
+ }
+
+ /**
+ * Similar to parse_str()
+ *
+ * Returns an associative array of name/value pairs, where the value is an
+ * array of values that have used the same name
+ *
+ * @static
+ * @param string $str The input string.
+ * @return array
+ */
+ public static function parse_str($str)
+ {
+ $return = array();
+ $str = explode('&', $str);
+
+ foreach ($str as $section)
+ {
+ if (strpos($section, '=') !== false)
+ {
+ list($name, $value) = explode('=', $section, 2);
+ $return[urldecode($name)][] = urldecode($value);
+ }
+ else
+ {
+ $return[urldecode($section)][] = null;
+ }
+ }
+
+ return $return;
+ }
+
+ /**
+ * Detect XML encoding, as per XML 1.0 Appendix F.1
+ *
+ * @todo Add support for EBCDIC
+ * @param string $data XML data
+ * @param SimplePie_Registry $registry Class registry
+ * @return array Possible encodings
+ */
+ public static function xml_encoding($data, $registry)
+ {
+ // UTF-32 Big Endian BOM
+ if (substr($data, 0, 4) === "\x00\x00\xFE\xFF")
+ {
+ $encoding[] = 'UTF-32BE';
+ }
+ // UTF-32 Little Endian BOM
+ elseif (substr($data, 0, 4) === "\xFF\xFE\x00\x00")
+ {
+ $encoding[] = 'UTF-32LE';
+ }
+ // UTF-16 Big Endian BOM
+ elseif (substr($data, 0, 2) === "\xFE\xFF")
+ {
+ $encoding[] = 'UTF-16BE';
+ }
+ // UTF-16 Little Endian BOM
+ elseif (substr($data, 0, 2) === "\xFF\xFE")
+ {
+ $encoding[] = 'UTF-16LE';
+ }
+ // UTF-8 BOM
+ elseif (substr($data, 0, 3) === "\xEF\xBB\xBF")
+ {
+ $encoding[] = 'UTF-8';
+ }
+ // UTF-32 Big Endian Without BOM
+ elseif (substr($data, 0, 20) === "\x00\x00\x00\x3C\x00\x00\x00\x3F\x00\x00\x00\x78\x00\x00\x00\x6D\x00\x00\x00\x6C")
+ {
+ if ($pos = strpos($data, "\x00\x00\x00\x3F\x00\x00\x00\x3E"))
+ {
+ $parser = $registry->create('XML_Declaration_Parser', array(SimplePie_Misc::change_encoding(substr($data, 20, $pos - 20), 'UTF-32BE', 'UTF-8')));
+ if ($parser->parse())
+ {
+ $encoding[] = $parser->encoding;
+ }
+ }
+ $encoding[] = 'UTF-32BE';
+ }
+ // UTF-32 Little Endian Without BOM
+ elseif (substr($data, 0, 20) === "\x3C\x00\x00\x00\x3F\x00\x00\x00\x78\x00\x00\x00\x6D\x00\x00\x00\x6C\x00\x00\x00")
+ {
+ if ($pos = strpos($data, "\x3F\x00\x00\x00\x3E\x00\x00\x00"))
+ {
+ $parser = $registry->create('XML_Declaration_Parser', array(SimplePie_Misc::change_encoding(substr($data, 20, $pos - 20), 'UTF-32LE', 'UTF-8')));
+ if ($parser->parse())
+ {
+ $encoding[] = $parser->encoding;
+ }
+ }
+ $encoding[] = 'UTF-32LE';
+ }
+ // UTF-16 Big Endian Without BOM
+ elseif (substr($data, 0, 10) === "\x00\x3C\x00\x3F\x00\x78\x00\x6D\x00\x6C")
+ {
+ if ($pos = strpos($data, "\x00\x3F\x00\x3E"))
+ {
+ $parser = $registry->create('XML_Declaration_Parser', array(SimplePie_Misc::change_encoding(substr($data, 20, $pos - 10), 'UTF-16BE', 'UTF-8')));
+ if ($parser->parse())
+ {
+ $encoding[] = $parser->encoding;
+ }
+ }
+ $encoding[] = 'UTF-16BE';
+ }
+ // UTF-16 Little Endian Without BOM
+ elseif (substr($data, 0, 10) === "\x3C\x00\x3F\x00\x78\x00\x6D\x00\x6C\x00")
+ {
+ if ($pos = strpos($data, "\x3F\x00\x3E\x00"))
+ {
+ $parser = $registry->create('XML_Declaration_Parser', array(SimplePie_Misc::change_encoding(substr($data, 20, $pos - 10), 'UTF-16LE', 'UTF-8')));
+ if ($parser->parse())
+ {
+ $encoding[] = $parser->encoding;
+ }
+ }
+ $encoding[] = 'UTF-16LE';
+ }
+ // US-ASCII (or superset)
+ elseif (substr($data, 0, 5) === "\x3C\x3F\x78\x6D\x6C")
+ {
+ if ($pos = strpos($data, "\x3F\x3E"))
+ {
+ $parser = $registry->create('XML_Declaration_Parser', array(substr($data, 5, $pos - 5)));
+ if ($parser->parse())
+ {
+ $encoding[] = $parser->encoding;
+ }
+ }
+ $encoding[] = 'UTF-8';
+ }
+ // Fallback to UTF-8
+ else
+ {
+ $encoding[] = 'UTF-8';
+ }
+ return $encoding;
+ }
+
+ public static function output_javascript()
+ {
+ if (function_exists('ob_gzhandler'))
+ {
+ ob_start('ob_gzhandler');
+ }
+ header('Content-type: text/javascript; charset: UTF-8');
+ header('Cache-Control: must-revalidate');
+ header('Expires: ' . gmdate('D, d M Y H:i:s', time() + 604800) . ' GMT'); // 7 days
+ ?>
+function embed_quicktime(type, bgcolor, width, height, link, placeholder, loop) {
+ if (placeholder != '') {
+ document.writeln('<embed type="'+type+'" style="cursor:hand; cursor:pointer;" href="'+link+'" src="'+placeholder+'" width="'+width+'" height="'+height+'" autoplay="false" target="myself" controller="false" loop="'+loop+'" scale="aspect" bgcolor="'+bgcolor+'" pluginspage="http://www.apple.com/quicktime/download/"></embed>');
+ }
+ else {
+ document.writeln('<embed type="'+type+'" style="cursor:hand; cursor:pointer;" src="'+link+'" width="'+width+'" height="'+height+'" autoplay="false" target="myself" controller="true" loop="'+loop+'" scale="aspect" bgcolor="'+bgcolor+'" pluginspage="http://www.apple.com/quicktime/download/"></embed>');
+ }
+}
+
+function embed_flash(bgcolor, width, height, link, loop, type) {
+ document.writeln('<embed src="'+link+'" pluginspage="http://www.macromedia.com/go/getflashplayer" type="'+type+'" quality="high" width="'+width+'" height="'+height+'" bgcolor="'+bgcolor+'" loop="'+loop+'"></embed>');
+}
+
+function embed_flv(width, height, link, placeholder, loop, player) {
+ document.writeln('<embed src="'+player+'" pluginspage="http://www.macromedia.com/go/getflashplayer" type="application/x-shockwave-flash" quality="high" width="'+width+'" height="'+height+'" wmode="transparent" flashvars="file='+link+'&autostart=false&repeat='+loop+'&showdigits=true&showfsbutton=false"></embed>');
+}
+
+function embed_wmedia(width, height, link) {
+ document.writeln('<embed type="application/x-mplayer2" src="'+link+'" autosize="1" width="'+width+'" height="'+height+'" showcontrols="1" showstatusbar="0" showdisplay="0" autostart="0"></embed>');
+}
+ <?php
+ }
+
+ /**
+ * Get the SimplePie build timestamp
+ *
+ * Uses the git index if it exists, otherwise uses the modification time
+ * of the newest file.
+ */
+ public static function get_build()
+ {
+ $root = dirname(dirname(__FILE__));
+ if (file_exists($root . '/.git/index'))
+ {
+ return filemtime($root . '/.git/index');
+ }
+ elseif (file_exists($root . '/SimplePie'))
+ {
+ $time = 0;
+ foreach (glob($root . '/SimplePie/*.php') as $file)
+ {
+ if (($mtime = filemtime($file)) > $time)
+ {
+ $time = $mtime;
+ }
+ }
+ return $time;
+ }
+ elseif (file_exists(dirname(__FILE__) . '/Core.php'))
+ {
+ return filemtime(dirname(__FILE__) . '/Core.php');
+ }
+ else
+ {
+ return filemtime(__FILE__);
+ }
+ }
+
+ /**
+ * Format debugging information
+ */
+ public static function debug(&$sp)
+ {
+ $info = 'SimplePie ' . SIMPLEPIE_VERSION . ' Build ' . SIMPLEPIE_BUILD . "\n";
+ $info .= 'PHP ' . PHP_VERSION . "\n";
+ if ($sp->error() !== null)
+ {
+ $info .= 'Error occurred: ' . $sp->error() . "\n";
+ }
+ else
+ {
+ $info .= "No error found.\n";
+ }
+ $info .= "Extensions:\n";
+ $extensions = array('pcre', 'curl', 'zlib', 'mbstring', 'iconv', 'xmlreader', 'xml');
+ foreach ($extensions as $ext)
+ {
+ if (extension_loaded($ext))
+ {
+ $info .= " $ext loaded\n";
+ switch ($ext)
+ {
+ case 'pcre':
+ $info .= ' Version ' . PCRE_VERSION . "\n";
+ break;
+ case 'curl':
+ $version = curl_version();
+ $info .= ' Version ' . $version['version'] . "\n";
+ break;
+ case 'mbstring':
+ $info .= ' Overloading: ' . mb_get_info('func_overload') . "\n";
+ break;
+ case 'iconv':
+ $info .= ' Version ' . ICONV_VERSION . "\n";
+ break;
+ case 'xml':
+ $info .= ' Version ' . LIBXML_DOTTED_VERSION . "\n";
+ break;
+ }
+ }
+ else
+ {
+ $info .= " $ext not loaded\n";
+ }
+ }
+ return $info;
+ }
+
+ public static function silence_errors($num, $str)
+ {
+ // No-op
+ }
+}
+
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Net/IPv6.php b/vendor/simplepie/simplepie/library/SimplePie/Net/IPv6.php
new file mode 100644
index 000000000..47658aff2
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Net/IPv6.php
@@ -0,0 +1,275 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+
+/**
+ * Class to validate and to work with IPv6 addresses.
+ *
+ * @package SimplePie
+ * @subpackage HTTP
+ * @copyright 2003-2005 The PHP Group
+ * @license http://www.opensource.org/licenses/bsd-license.php
+ * @link http://pear.php.net/package/Net_IPv6
+ * @author Alexander Merz <alexander.merz@web.de>
+ * @author elfrink at introweb dot nl
+ * @author Josh Peck <jmp at joshpeck dot org>
+ * @author Geoffrey Sneddon <geoffers@gmail.com>
+ */
+class SimplePie_Net_IPv6
+{
+ /**
+ * Uncompresses an IPv6 address
+ *
+ * RFC 4291 allows you to compress concecutive zero pieces in an address to
+ * '::'. This method expects a valid IPv6 address and expands the '::' to
+ * the required number of zero pieces.
+ *
+ * Example: FF01::101 -> FF01:0:0:0:0:0:0:101
+ * ::1 -> 0:0:0:0:0:0:0:1
+ *
+ * @author Alexander Merz <alexander.merz@web.de>
+ * @author elfrink at introweb dot nl
+ * @author Josh Peck <jmp at joshpeck dot org>
+ * @copyright 2003-2005 The PHP Group
+ * @license http://www.opensource.org/licenses/bsd-license.php
+ * @param string $ip An IPv6 address
+ * @return string The uncompressed IPv6 address
+ */
+ public static function uncompress($ip)
+ {
+ $c1 = -1;
+ $c2 = -1;
+ if (substr_count($ip, '::') === 1)
+ {
+ list($ip1, $ip2) = explode('::', $ip);
+ if ($ip1 === '')
+ {
+ $c1 = -1;
+ }
+ else
+ {
+ $c1 = substr_count($ip1, ':');
+ }
+ if ($ip2 === '')
+ {
+ $c2 = -1;
+ }
+ else
+ {
+ $c2 = substr_count($ip2, ':');
+ }
+ if (strpos($ip2, '.') !== false)
+ {
+ $c2++;
+ }
+ // ::
+ if ($c1 === -1 && $c2 === -1)
+ {
+ $ip = '0:0:0:0:0:0:0:0';
+ }
+ // ::xxx
+ else if ($c1 === -1)
+ {
+ $fill = str_repeat('0:', 7 - $c2);
+ $ip = str_replace('::', $fill, $ip);
+ }
+ // xxx::
+ else if ($c2 === -1)
+ {
+ $fill = str_repeat(':0', 7 - $c1);
+ $ip = str_replace('::', $fill, $ip);
+ }
+ // xxx::xxx
+ else
+ {
+ $fill = ':' . str_repeat('0:', 6 - $c2 - $c1);
+ $ip = str_replace('::', $fill, $ip);
+ }
+ }
+ return $ip;
+ }
+
+ /**
+ * Compresses an IPv6 address
+ *
+ * RFC 4291 allows you to compress concecutive zero pieces in an address to
+ * '::'. This method expects a valid IPv6 address and compresses consecutive
+ * zero pieces to '::'.
+ *
+ * Example: FF01:0:0:0:0:0:0:101 -> FF01::101
+ * 0:0:0:0:0:0:0:1 -> ::1
+ *
+ * @see uncompress()
+ * @param string $ip An IPv6 address
+ * @return string The compressed IPv6 address
+ */
+ public static function compress($ip)
+ {
+ // Prepare the IP to be compressed
+ $ip = self::uncompress($ip);
+ $ip_parts = self::split_v6_v4($ip);
+
+ // Replace all leading zeros
+ $ip_parts[0] = preg_replace('/(^|:)0+([0-9])/', '\1\2', $ip_parts[0]);
+
+ // Find bunches of zeros
+ if (preg_match_all('/(?:^|:)(?:0(?::|$))+/', $ip_parts[0], $matches, PREG_OFFSET_CAPTURE))
+ {
+ $max = 0;
+ $pos = null;
+ foreach ($matches[0] as $match)
+ {
+ if (strlen($match[0]) > $max)
+ {
+ $max = strlen($match[0]);
+ $pos = $match[1];
+ }
+ }
+
+ $ip_parts[0] = substr_replace($ip_parts[0], '::', $pos, $max);
+ }
+
+ if ($ip_parts[1] !== '')
+ {
+ return implode(':', $ip_parts);
+ }
+ else
+ {
+ return $ip_parts[0];
+ }
+ }
+
+ /**
+ * Splits an IPv6 address into the IPv6 and IPv4 representation parts
+ *
+ * RFC 4291 allows you to represent the last two parts of an IPv6 address
+ * using the standard IPv4 representation
+ *
+ * Example: 0:0:0:0:0:0:13.1.68.3
+ * 0:0:0:0:0:FFFF:129.144.52.38
+ *
+ * @param string $ip An IPv6 address
+ * @return array [0] contains the IPv6 represented part, and [1] the IPv4 represented part
+ */
+ private static function split_v6_v4($ip)
+ {
+ if (strpos($ip, '.') !== false)
+ {
+ $pos = strrpos($ip, ':');
+ $ipv6_part = substr($ip, 0, $pos);
+ $ipv4_part = substr($ip, $pos + 1);
+ return array($ipv6_part, $ipv4_part);
+ }
+ else
+ {
+ return array($ip, '');
+ }
+ }
+
+ /**
+ * Checks an IPv6 address
+ *
+ * Checks if the given IP is a valid IPv6 address
+ *
+ * @param string $ip An IPv6 address
+ * @return bool true if $ip is a valid IPv6 address
+ */
+ public static function check_ipv6($ip)
+ {
+ $ip = self::uncompress($ip);
+ list($ipv6, $ipv4) = self::split_v6_v4($ip);
+ $ipv6 = explode(':', $ipv6);
+ $ipv4 = explode('.', $ipv4);
+ if (count($ipv6) === 8 && count($ipv4) === 1 || count($ipv6) === 6 && count($ipv4) === 4)
+ {
+ foreach ($ipv6 as $ipv6_part)
+ {
+ // The section can't be empty
+ if ($ipv6_part === '')
+ return false;
+
+ // Nor can it be over four characters
+ if (strlen($ipv6_part) > 4)
+ return false;
+
+ // Remove leading zeros (this is safe because of the above)
+ $ipv6_part = ltrim($ipv6_part, '0');
+ if ($ipv6_part === '')
+ $ipv6_part = '0';
+
+ // Check the value is valid
+ $value = hexdec($ipv6_part);
+ if (dechex($value) !== strtolower($ipv6_part) || $value < 0 || $value > 0xFFFF)
+ return false;
+ }
+ if (count($ipv4) === 4)
+ {
+ foreach ($ipv4 as $ipv4_part)
+ {
+ $value = (int) $ipv4_part;
+ if ((string) $value !== $ipv4_part || $value < 0 || $value > 0xFF)
+ return false;
+ }
+ }
+ return true;
+ }
+ else
+ {
+ return false;
+ }
+ }
+
+ /**
+ * Checks if the given IP is a valid IPv6 address
+ *
+ * @codeCoverageIgnore
+ * @deprecated Use {@see SimplePie_Net_IPv6::check_ipv6()} instead
+ * @see check_ipv6
+ * @param string $ip An IPv6 address
+ * @return bool true if $ip is a valid IPv6 address
+ */
+ public static function checkIPv6($ip)
+ {
+ return self::check_ipv6($ip);
+ }
+}
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Parse/Date.php b/vendor/simplepie/simplepie/library/SimplePie/Parse/Date.php
new file mode 100644
index 000000000..1f2156655
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Parse/Date.php
@@ -0,0 +1,983 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+
+/**
+ * Date Parser
+ *
+ * @package SimplePie
+ * @subpackage Parsing
+ */
+class SimplePie_Parse_Date
+{
+ /**
+ * Input data
+ *
+ * @access protected
+ * @var string
+ */
+ var $date;
+
+ /**
+ * List of days, calendar day name => ordinal day number in the week
+ *
+ * @access protected
+ * @var array
+ */
+ var $day = array(
+ // English
+ 'mon' => 1,
+ 'monday' => 1,
+ 'tue' => 2,
+ 'tuesday' => 2,
+ 'wed' => 3,
+ 'wednesday' => 3,
+ 'thu' => 4,
+ 'thursday' => 4,
+ 'fri' => 5,
+ 'friday' => 5,
+ 'sat' => 6,
+ 'saturday' => 6,
+ 'sun' => 7,
+ 'sunday' => 7,
+ // Dutch
+ 'maandag' => 1,
+ 'dinsdag' => 2,
+ 'woensdag' => 3,
+ 'donderdag' => 4,
+ 'vrijdag' => 5,
+ 'zaterdag' => 6,
+ 'zondag' => 7,
+ // French
+ 'lundi' => 1,
+ 'mardi' => 2,
+ 'mercredi' => 3,
+ 'jeudi' => 4,
+ 'vendredi' => 5,
+ 'samedi' => 6,
+ 'dimanche' => 7,
+ // German
+ 'montag' => 1,
+ 'dienstag' => 2,
+ 'mittwoch' => 3,
+ 'donnerstag' => 4,
+ 'freitag' => 5,
+ 'samstag' => 6,
+ 'sonnabend' => 6,
+ 'sonntag' => 7,
+ // Italian
+ 'lunedì' => 1,
+ 'martedì' => 2,
+ 'mercoledì' => 3,
+ 'giovedì' => 4,
+ 'venerdì' => 5,
+ 'sabato' => 6,
+ 'domenica' => 7,
+ // Spanish
+ 'lunes' => 1,
+ 'martes' => 2,
+ 'miércoles' => 3,
+ 'jueves' => 4,
+ 'viernes' => 5,
+ 'sábado' => 6,
+ 'domingo' => 7,
+ // Finnish
+ 'maanantai' => 1,
+ 'tiistai' => 2,
+ 'keskiviikko' => 3,
+ 'torstai' => 4,
+ 'perjantai' => 5,
+ 'lauantai' => 6,
+ 'sunnuntai' => 7,
+ // Hungarian
+ 'hétfő' => 1,
+ 'kedd' => 2,
+ 'szerda' => 3,
+ 'csütörtok' => 4,
+ 'péntek' => 5,
+ 'szombat' => 6,
+ 'vasárnap' => 7,
+ // Greek
+ 'Δευ' => 1,
+ 'Τρι' => 2,
+ 'Τετ' => 3,
+ 'Πεμ' => 4,
+ 'Παρ' => 5,
+ 'Σαβ' => 6,
+ 'Κυρ' => 7,
+ );
+
+ /**
+ * List of months, calendar month name => calendar month number
+ *
+ * @access protected
+ * @var array
+ */
+ var $month = array(
+ // English
+ 'jan' => 1,
+ 'january' => 1,
+ 'feb' => 2,
+ 'february' => 2,
+ 'mar' => 3,
+ 'march' => 3,
+ 'apr' => 4,
+ 'april' => 4,
+ 'may' => 5,
+ // No long form of May
+ 'jun' => 6,
+ 'june' => 6,
+ 'jul' => 7,
+ 'july' => 7,
+ 'aug' => 8,
+ 'august' => 8,
+ 'sep' => 9,
+ 'september' => 9,
+ 'oct' => 10,
+ 'october' => 10,
+ 'nov' => 11,
+ 'november' => 11,
+ 'dec' => 12,
+ 'december' => 12,
+ // Dutch
+ 'januari' => 1,
+ 'februari' => 2,
+ 'maart' => 3,
+ 'april' => 4,
+ 'mei' => 5,
+ 'juni' => 6,
+ 'juli' => 7,
+ 'augustus' => 8,
+ 'september' => 9,
+ 'oktober' => 10,
+ 'november' => 11,
+ 'december' => 12,
+ // French
+ 'janvier' => 1,
+ 'février' => 2,
+ 'mars' => 3,
+ 'avril' => 4,
+ 'mai' => 5,
+ 'juin' => 6,
+ 'juillet' => 7,
+ 'août' => 8,
+ 'septembre' => 9,
+ 'octobre' => 10,
+ 'novembre' => 11,
+ 'décembre' => 12,
+ // German
+ 'januar' => 1,
+ 'februar' => 2,
+ 'märz' => 3,
+ 'april' => 4,
+ 'mai' => 5,
+ 'juni' => 6,
+ 'juli' => 7,
+ 'august' => 8,
+ 'september' => 9,
+ 'oktober' => 10,
+ 'november' => 11,
+ 'dezember' => 12,
+ // Italian
+ 'gennaio' => 1,
+ 'febbraio' => 2,
+ 'marzo' => 3,
+ 'aprile' => 4,
+ 'maggio' => 5,
+ 'giugno' => 6,
+ 'luglio' => 7,
+ 'agosto' => 8,
+ 'settembre' => 9,
+ 'ottobre' => 10,
+ 'novembre' => 11,
+ 'dicembre' => 12,
+ // Spanish
+ 'enero' => 1,
+ 'febrero' => 2,
+ 'marzo' => 3,
+ 'abril' => 4,
+ 'mayo' => 5,
+ 'junio' => 6,
+ 'julio' => 7,
+ 'agosto' => 8,
+ 'septiembre' => 9,
+ 'setiembre' => 9,
+ 'octubre' => 10,
+ 'noviembre' => 11,
+ 'diciembre' => 12,
+ // Finnish
+ 'tammikuu' => 1,
+ 'helmikuu' => 2,
+ 'maaliskuu' => 3,
+ 'huhtikuu' => 4,
+ 'toukokuu' => 5,
+ 'kesäkuu' => 6,
+ 'heinäkuu' => 7,
+ 'elokuu' => 8,
+ 'suuskuu' => 9,
+ 'lokakuu' => 10,
+ 'marras' => 11,
+ 'joulukuu' => 12,
+ // Hungarian
+ 'január' => 1,
+ 'február' => 2,
+ 'március' => 3,
+ 'április' => 4,
+ 'május' => 5,
+ 'június' => 6,
+ 'július' => 7,
+ 'augusztus' => 8,
+ 'szeptember' => 9,
+ 'október' => 10,
+ 'november' => 11,
+ 'december' => 12,
+ // Greek
+ 'Ιαν' => 1,
+ 'Φεβ' => 2,
+ 'Μάώ' => 3,
+ 'Μαώ' => 3,
+ 'Απρ' => 4,
+ 'Μάι' => 5,
+ 'Μαϊ' => 5,
+ 'Μαι' => 5,
+ 'Ιούν' => 6,
+ 'Ιον' => 6,
+ 'Ιούλ' => 7,
+ 'Ιολ' => 7,
+ 'Αύγ' => 8,
+ 'Αυγ' => 8,
+ 'Σεπ' => 9,
+ 'Οκτ' => 10,
+ 'Νοέ' => 11,
+ 'Δεκ' => 12,
+ );
+
+ /**
+ * List of timezones, abbreviation => offset from UTC
+ *
+ * @access protected
+ * @var array
+ */
+ var $timezone = array(
+ 'ACDT' => 37800,
+ 'ACIT' => 28800,
+ 'ACST' => 34200,
+ 'ACT' => -18000,
+ 'ACWDT' => 35100,
+ 'ACWST' => 31500,
+ 'AEDT' => 39600,
+ 'AEST' => 36000,
+ 'AFT' => 16200,
+ 'AKDT' => -28800,
+ 'AKST' => -32400,
+ 'AMDT' => 18000,
+ 'AMT' => -14400,
+ 'ANAST' => 46800,
+ 'ANAT' => 43200,
+ 'ART' => -10800,
+ 'AZOST' => -3600,
+ 'AZST' => 18000,
+ 'AZT' => 14400,
+ 'BIOT' => 21600,
+ 'BIT' => -43200,
+ 'BOT' => -14400,
+ 'BRST' => -7200,
+ 'BRT' => -10800,
+ 'BST' => 3600,
+ 'BTT' => 21600,
+ 'CAST' => 18000,
+ 'CAT' => 7200,
+ 'CCT' => 23400,
+ 'CDT' => -18000,
+ 'CEDT' => 7200,
+ 'CEST' => 7200,
+ 'CET' => 3600,
+ 'CGST' => -7200,
+ 'CGT' => -10800,
+ 'CHADT' => 49500,
+ 'CHAST' => 45900,
+ 'CIST' => -28800,
+ 'CKT' => -36000,
+ 'CLDT' => -10800,
+ 'CLST' => -14400,
+ 'COT' => -18000,
+ 'CST' => -21600,
+ 'CVT' => -3600,
+ 'CXT' => 25200,
+ 'DAVT' => 25200,
+ 'DTAT' => 36000,
+ 'EADT' => -18000,
+ 'EAST' => -21600,
+ 'EAT' => 10800,
+ 'ECT' => -18000,
+ 'EDT' => -14400,
+ 'EEST' => 10800,
+ 'EET' => 7200,
+ 'EGT' => -3600,
+ 'EKST' => 21600,
+ 'EST' => -18000,
+ 'FJT' => 43200,
+ 'FKDT' => -10800,
+ 'FKST' => -14400,
+ 'FNT' => -7200,
+ 'GALT' => -21600,
+ 'GEDT' => 14400,
+ 'GEST' => 10800,
+ 'GFT' => -10800,
+ 'GILT' => 43200,
+ 'GIT' => -32400,
+ 'GST' => 14400,
+ 'GST' => -7200,
+ 'GYT' => -14400,
+ 'HAA' => -10800,
+ 'HAC' => -18000,
+ 'HADT' => -32400,
+ 'HAE' => -14400,
+ 'HAP' => -25200,
+ 'HAR' => -21600,
+ 'HAST' => -36000,
+ 'HAT' => -9000,
+ 'HAY' => -28800,
+ 'HKST' => 28800,
+ 'HMT' => 18000,
+ 'HNA' => -14400,
+ 'HNC' => -21600,
+ 'HNE' => -18000,
+ 'HNP' => -28800,
+ 'HNR' => -25200,
+ 'HNT' => -12600,
+ 'HNY' => -32400,
+ 'IRDT' => 16200,
+ 'IRKST' => 32400,
+ 'IRKT' => 28800,
+ 'IRST' => 12600,
+ 'JFDT' => -10800,
+ 'JFST' => -14400,
+ 'JST' => 32400,
+ 'KGST' => 21600,
+ 'KGT' => 18000,
+ 'KOST' => 39600,
+ 'KOVST' => 28800,
+ 'KOVT' => 25200,
+ 'KRAST' => 28800,
+ 'KRAT' => 25200,
+ 'KST' => 32400,
+ 'LHDT' => 39600,
+ 'LHST' => 37800,
+ 'LINT' => 50400,
+ 'LKT' => 21600,
+ 'MAGST' => 43200,
+ 'MAGT' => 39600,
+ 'MAWT' => 21600,
+ 'MDT' => -21600,
+ 'MESZ' => 7200,
+ 'MEZ' => 3600,
+ 'MHT' => 43200,
+ 'MIT' => -34200,
+ 'MNST' => 32400,
+ 'MSDT' => 14400,
+ 'MSST' => 10800,
+ 'MST' => -25200,
+ 'MUT' => 14400,
+ 'MVT' => 18000,
+ 'MYT' => 28800,
+ 'NCT' => 39600,
+ 'NDT' => -9000,
+ 'NFT' => 41400,
+ 'NMIT' => 36000,
+ 'NOVST' => 25200,
+ 'NOVT' => 21600,
+ 'NPT' => 20700,
+ 'NRT' => 43200,
+ 'NST' => -12600,
+ 'NUT' => -39600,
+ 'NZDT' => 46800,
+ 'NZST' => 43200,
+ 'OMSST' => 25200,
+ 'OMST' => 21600,
+ 'PDT' => -25200,
+ 'PET' => -18000,
+ 'PETST' => 46800,
+ 'PETT' => 43200,
+ 'PGT' => 36000,
+ 'PHOT' => 46800,
+ 'PHT' => 28800,
+ 'PKT' => 18000,
+ 'PMDT' => -7200,
+ 'PMST' => -10800,
+ 'PONT' => 39600,
+ 'PST' => -28800,
+ 'PWT' => 32400,
+ 'PYST' => -10800,
+ 'PYT' => -14400,
+ 'RET' => 14400,
+ 'ROTT' => -10800,
+ 'SAMST' => 18000,
+ 'SAMT' => 14400,
+ 'SAST' => 7200,
+ 'SBT' => 39600,
+ 'SCDT' => 46800,
+ 'SCST' => 43200,
+ 'SCT' => 14400,
+ 'SEST' => 3600,
+ 'SGT' => 28800,
+ 'SIT' => 28800,
+ 'SRT' => -10800,
+ 'SST' => -39600,
+ 'SYST' => 10800,
+ 'SYT' => 7200,
+ 'TFT' => 18000,
+ 'THAT' => -36000,
+ 'TJT' => 18000,
+ 'TKT' => -36000,
+ 'TMT' => 18000,
+ 'TOT' => 46800,
+ 'TPT' => 32400,
+ 'TRUT' => 36000,
+ 'TVT' => 43200,
+ 'TWT' => 28800,
+ 'UYST' => -7200,
+ 'UYT' => -10800,
+ 'UZT' => 18000,
+ 'VET' => -14400,
+ 'VLAST' => 39600,
+ 'VLAT' => 36000,
+ 'VOST' => 21600,
+ 'VUT' => 39600,
+ 'WAST' => 7200,
+ 'WAT' => 3600,
+ 'WDT' => 32400,
+ 'WEST' => 3600,
+ 'WFT' => 43200,
+ 'WIB' => 25200,
+ 'WIT' => 32400,
+ 'WITA' => 28800,
+ 'WKST' => 18000,
+ 'WST' => 28800,
+ 'YAKST' => 36000,
+ 'YAKT' => 32400,
+ 'YAPT' => 36000,
+ 'YEKST' => 21600,
+ 'YEKT' => 18000,
+ );
+
+ /**
+ * Cached PCRE for SimplePie_Parse_Date::$day
+ *
+ * @access protected
+ * @var string
+ */
+ var $day_pcre;
+
+ /**
+ * Cached PCRE for SimplePie_Parse_Date::$month
+ *
+ * @access protected
+ * @var string
+ */
+ var $month_pcre;
+
+ /**
+ * Array of user-added callback methods
+ *
+ * @access private
+ * @var array
+ */
+ var $built_in = array();
+
+ /**
+ * Array of user-added callback methods
+ *
+ * @access private
+ * @var array
+ */
+ var $user = array();
+
+ /**
+ * Create new SimplePie_Parse_Date object, and set self::day_pcre,
+ * self::month_pcre, and self::built_in
+ *
+ * @access private
+ */
+ public function __construct()
+ {
+ $this->day_pcre = '(' . implode(array_keys($this->day), '|') . ')';
+ $this->month_pcre = '(' . implode(array_keys($this->month), '|') . ')';
+
+ static $cache;
+ if (!isset($cache[get_class($this)]))
+ {
+ $all_methods = get_class_methods($this);
+
+ foreach ($all_methods as $method)
+ {
+ if (strtolower(substr($method, 0, 5)) === 'date_')
+ {
+ $cache[get_class($this)][] = $method;
+ }
+ }
+ }
+
+ foreach ($cache[get_class($this)] as $method)
+ {
+ $this->built_in[] = $method;
+ }
+ }
+
+ /**
+ * Get the object
+ *
+ * @access public
+ */
+ public static function get()
+ {
+ static $object;
+ if (!$object)
+ {
+ $object = new SimplePie_Parse_Date;
+ }
+ return $object;
+ }
+
+ /**
+ * Parse a date
+ *
+ * @final
+ * @access public
+ * @param string $date Date to parse
+ * @return int Timestamp corresponding to date string, or false on failure
+ */
+ public function parse($date)
+ {
+ foreach ($this->user as $method)
+ {
+ if (($returned = call_user_func($method, $date)) !== false)
+ {
+ return $returned;
+ }
+ }
+
+ foreach ($this->built_in as $method)
+ {
+ if (($returned = call_user_func(array($this, $method), $date)) !== false)
+ {
+ return $returned;
+ }
+ }
+
+ return false;
+ }
+
+ /**
+ * Add a callback method to parse a date
+ *
+ * @final
+ * @access public
+ * @param callback $callback
+ */
+ public function add_callback($callback)
+ {
+ if (is_callable($callback))
+ {
+ $this->user[] = $callback;
+ }
+ else
+ {
+ trigger_error('User-supplied function must be a valid callback', E_USER_WARNING);
+ }
+ }
+
+ /**
+ * Parse a superset of W3C-DTF (allows hyphens and colons to be omitted, as
+ * well as allowing any of upper or lower case "T", horizontal tabs, or
+ * spaces to be used as the time separator (including more than one))
+ *
+ * @access protected
+ * @return int Timestamp
+ */
+ public function date_w3cdtf($date)
+ {
+ static $pcre;
+ if (!$pcre)
+ {
+ $year = '([0-9]{4})';
+ $month = $day = $hour = $minute = $second = '([0-9]{2})';
+ $decimal = '([0-9]*)';
+ $zone = '(?:(Z)|([+\-])([0-9]{1,2}):?([0-9]{1,2}))';
+ $pcre = '/^' . $year . '(?:-?' . $month . '(?:-?' . $day . '(?:[Tt\x09\x20]+' . $hour . '(?::?' . $minute . '(?::?' . $second . '(?:.' . $decimal . ')?)?)?' . $zone . ')?)?)?$/';
+ }
+ if (preg_match($pcre, $date, $match))
+ {
+ /*
+ Capturing subpatterns:
+ 1: Year
+ 2: Month
+ 3: Day
+ 4: Hour
+ 5: Minute
+ 6: Second
+ 7: Decimal fraction of a second
+ 8: Zulu
+ 9: Timezone ±
+ 10: Timezone hours
+ 11: Timezone minutes
+ */
+
+ // Fill in empty matches
+ for ($i = count($match); $i <= 3; $i++)
+ {
+ $match[$i] = '1';
+ }
+
+ for ($i = count($match); $i <= 7; $i++)
+ {
+ $match[$i] = '0';
+ }
+
+ // Numeric timezone
+ if (isset($match[9]) && $match[9] !== '')
+ {
+ $timezone = $match[10] * 3600;
+ $timezone += $match[11] * 60;
+ if ($match[9] === '-')
+ {
+ $timezone = 0 - $timezone;
+ }
+ }
+ else
+ {
+ $timezone = 0;
+ }
+
+ // Convert the number of seconds to an integer, taking decimals into account
+ $second = round((int)$match[6] + (int)$match[7] / pow(10, strlen($match[7])));
+
+ return gmmktime($match[4], $match[5], $second, $match[2], $match[3], $match[1]) - $timezone;
+ }
+ else
+ {
+ return false;
+ }
+ }
+
+ /**
+ * Remove RFC822 comments
+ *
+ * @access protected
+ * @param string $data Data to strip comments from
+ * @return string Comment stripped string
+ */
+ public function remove_rfc2822_comments($string)
+ {
+ $string = (string) $string;
+ $position = 0;
+ $length = strlen($string);
+ $depth = 0;
+
+ $output = '';
+
+ while ($position < $length && ($pos = strpos($string, '(', $position)) !== false)
+ {
+ $output .= substr($string, $position, $pos - $position);
+ $position = $pos + 1;
+ if ($pos === 0 || $string[$pos - 1] !== '\\')
+ {
+ $depth++;
+ while ($depth && $position < $length)
+ {
+ $position += strcspn($string, '()', $position);
+ if ($string[$position - 1] === '\\')
+ {
+ $position++;
+ continue;
+ }
+ elseif (isset($string[$position]))
+ {
+ switch ($string[$position])
+ {
+ case '(':
+ $depth++;
+ break;
+
+ case ')':
+ $depth--;
+ break;
+ }
+ $position++;
+ }
+ else
+ {
+ break;
+ }
+ }
+ }
+ else
+ {
+ $output .= '(';
+ }
+ }
+ $output .= substr($string, $position);
+
+ return $output;
+ }
+
+ /**
+ * Parse RFC2822's date format
+ *
+ * @access protected
+ * @return int Timestamp
+ */
+ public function date_rfc2822($date)
+ {
+ static $pcre;
+ if (!$pcre)
+ {
+ $wsp = '[\x09\x20]';
+ $fws = '(?:' . $wsp . '+|' . $wsp . '*(?:\x0D\x0A' . $wsp . '+)+)';
+ $optional_fws = $fws . '?';
+ $day_name = $this->day_pcre;
+ $month = $this->month_pcre;
+ $day = '([0-9]{1,2})';
+ $hour = $minute = $second = '([0-9]{2})';
+ $year = '([0-9]{2,4})';
+ $num_zone = '([+\-])([0-9]{2})([0-9]{2})';
+ $character_zone = '([A-Z]{1,5})';
+ $zone = '(?:' . $num_zone . '|' . $character_zone . ')';
+ $pcre = '/(?:' . $optional_fws . $day_name . $optional_fws . ',)?' . $optional_fws . $day . $fws . $month . $fws . $year . $fws . $hour . $optional_fws . ':' . $optional_fws . $minute . '(?:' . $optional_fws . ':' . $optional_fws . $second . ')?' . $fws . $zone . '/i';
+ }
+ if (preg_match($pcre, $this->remove_rfc2822_comments($date), $match))
+ {
+ /*
+ Capturing subpatterns:
+ 1: Day name
+ 2: Day
+ 3: Month
+ 4: Year
+ 5: Hour
+ 6: Minute
+ 7: Second
+ 8: Timezone ±
+ 9: Timezone hours
+ 10: Timezone minutes
+ 11: Alphabetic timezone
+ */
+
+ // Find the month number
+ $month = $this->month[strtolower($match[3])];
+
+ // Numeric timezone
+ if ($match[8] !== '')
+ {
+ $timezone = $match[9] * 3600;
+ $timezone += $match[10] * 60;
+ if ($match[8] === '-')
+ {
+ $timezone = 0 - $timezone;
+ }
+ }
+ // Character timezone
+ elseif (isset($this->timezone[strtoupper($match[11])]))
+ {
+ $timezone = $this->timezone[strtoupper($match[11])];
+ }
+ // Assume everything else to be -0000
+ else
+ {
+ $timezone = 0;
+ }
+
+ // Deal with 2/3 digit years
+ if ($match[4] < 50)
+ {
+ $match[4] += 2000;
+ }
+ elseif ($match[4] < 1000)
+ {
+ $match[4] += 1900;
+ }
+
+ // Second is optional, if it is empty set it to zero
+ if ($match[7] !== '')
+ {
+ $second = $match[7];
+ }
+ else
+ {
+ $second = 0;
+ }
+
+ return gmmktime($match[5], $match[6], $second, $month, $match[2], $match[4]) - $timezone;
+ }
+ else
+ {
+ return false;
+ }
+ }
+
+ /**
+ * Parse RFC850's date format
+ *
+ * @access protected
+ * @return int Timestamp
+ */
+ public function date_rfc850($date)
+ {
+ static $pcre;
+ if (!$pcre)
+ {
+ $space = '[\x09\x20]+';
+ $day_name = $this->day_pcre;
+ $month = $this->month_pcre;
+ $day = '([0-9]{1,2})';
+ $year = $hour = $minute = $second = '([0-9]{2})';
+ $zone = '([A-Z]{1,5})';
+ $pcre = '/^' . $day_name . ',' . $space . $day . '-' . $month . '-' . $year . $space . $hour . ':' . $minute . ':' . $second . $space . $zone . '$/i';
+ }
+ if (preg_match($pcre, $date, $match))
+ {
+ /*
+ Capturing subpatterns:
+ 1: Day name
+ 2: Day
+ 3: Month
+ 4: Year
+ 5: Hour
+ 6: Minute
+ 7: Second
+ 8: Timezone
+ */
+
+ // Month
+ $month = $this->month[strtolower($match[3])];
+
+ // Character timezone
+ if (isset($this->timezone[strtoupper($match[8])]))
+ {
+ $timezone = $this->timezone[strtoupper($match[8])];
+ }
+ // Assume everything else to be -0000
+ else
+ {
+ $timezone = 0;
+ }
+
+ // Deal with 2 digit year
+ if ($match[4] < 50)
+ {
+ $match[4] += 2000;
+ }
+ else
+ {
+ $match[4] += 1900;
+ }
+
+ return gmmktime($match[5], $match[6], $match[7], $month, $match[2], $match[4]) - $timezone;
+ }
+ else
+ {
+ return false;
+ }
+ }
+
+ /**
+ * Parse C99's asctime()'s date format
+ *
+ * @access protected
+ * @return int Timestamp
+ */
+ public function date_asctime($date)
+ {
+ static $pcre;
+ if (!$pcre)
+ {
+ $space = '[\x09\x20]+';
+ $wday_name = $this->day_pcre;
+ $mon_name = $this->month_pcre;
+ $day = '([0-9]{1,2})';
+ $hour = $sec = $min = '([0-9]{2})';
+ $year = '([0-9]{4})';
+ $terminator = '\x0A?\x00?';
+ $pcre = '/^' . $wday_name . $space . $mon_name . $space . $day . $space . $hour . ':' . $min . ':' . $sec . $space . $year . $terminator . '$/i';
+ }
+ if (preg_match($pcre, $date, $match))
+ {
+ /*
+ Capturing subpatterns:
+ 1: Day name
+ 2: Month
+ 3: Day
+ 4: Hour
+ 5: Minute
+ 6: Second
+ 7: Year
+ */
+
+ $month = $this->month[strtolower($match[2])];
+ return gmmktime($match[4], $match[5], $match[6], $month, $match[3], $match[7]);
+ }
+ else
+ {
+ return false;
+ }
+ }
+
+ /**
+ * Parse dates using strtotime()
+ *
+ * @access protected
+ * @return int Timestamp
+ */
+ public function date_strtotime($date)
+ {
+ $strtotime = strtotime($date);
+ if ($strtotime === -1 || $strtotime === false)
+ {
+ return false;
+ }
+ else
+ {
+ return $strtotime;
+ }
+ }
+}
+
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Parser.php b/vendor/simplepie/simplepie/library/SimplePie/Parser.php
new file mode 100644
index 000000000..17139abe9
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Parser.php
@@ -0,0 +1,656 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * Parses XML into something sane
+ *
+ *
+ * This class can be overloaded with {@see SimplePie::set_parser_class()}
+ *
+ * @package SimplePie
+ * @subpackage Parsing
+ */
+class SimplePie_Parser
+{
+ var $error_code;
+ var $error_string;
+ var $current_line;
+ var $current_column;
+ var $current_byte;
+ var $separator = ' ';
+ var $namespace = array('');
+ var $element = array('');
+ var $xml_base = array('');
+ var $xml_base_explicit = array(false);
+ var $xml_lang = array('');
+ var $data = array();
+ var $datas = array(array());
+ var $current_xhtml_construct = -1;
+ var $encoding;
+ protected $registry;
+
+ public function set_registry(SimplePie_Registry $registry)
+ {
+ $this->registry = $registry;
+ }
+
+ public function parse(&$data, $encoding, $url = '')
+ {
+ if (function_exists('Mf2\parse')) {
+ // Check for both h-feed and h-entry, as both a feed with no entries
+ // and a list of entries without an h-feed wrapper are both valid.
+ $position = 0;
+ while ($position = strpos($data, 'h-feed', $position)) {
+ $start = $position < 200 ? 0 : $position - 200;
+ $check = substr($data, $start, 400);
+ if (preg_match('/class="[^"]*h-feed/', $check)) {
+ return $this->parse_microformats($data, $url);
+ }
+ $position += 7;
+ }
+ $position = 0;
+ while ($position = strpos($data, 'h-entry', $position)) {
+ $start = $position < 200 ? 0 : $position - 200;
+ $check = substr($data, $start, 400);
+ if (preg_match('/class="[^"]*h-entry/', $check)) {
+ return $this->parse_microformats($data, $url);
+ }
+ $position += 7;
+ }
+ }
+
+ // Use UTF-8 if we get passed US-ASCII, as every US-ASCII character is a UTF-8 character
+ if (strtoupper($encoding) === 'US-ASCII')
+ {
+ $this->encoding = 'UTF-8';
+ }
+ else
+ {
+ $this->encoding = $encoding;
+ }
+
+ // Strip BOM:
+ // UTF-32 Big Endian BOM
+ if (substr($data, 0, 4) === "\x00\x00\xFE\xFF")
+ {
+ $data = substr($data, 4);
+ }
+ // UTF-32 Little Endian BOM
+ elseif (substr($data, 0, 4) === "\xFF\xFE\x00\x00")
+ {
+ $data = substr($data, 4);
+ }
+ // UTF-16 Big Endian BOM
+ elseif (substr($data, 0, 2) === "\xFE\xFF")
+ {
+ $data = substr($data, 2);
+ }
+ // UTF-16 Little Endian BOM
+ elseif (substr($data, 0, 2) === "\xFF\xFE")
+ {
+ $data = substr($data, 2);
+ }
+ // UTF-8 BOM
+ elseif (substr($data, 0, 3) === "\xEF\xBB\xBF")
+ {
+ $data = substr($data, 3);
+ }
+
+ if (substr($data, 0, 5) === '<?xml' && strspn(substr($data, 5, 1), "\x09\x0A\x0D\x20") && ($pos = strpos($data, '?>')) !== false)
+ {
+ $declaration = $this->registry->create('XML_Declaration_Parser', array(substr($data, 5, $pos - 5)));
+ if ($declaration->parse())
+ {
+ $data = substr($data, $pos + 2);
+ $data = '<?xml version="' . $declaration->version . '" encoding="' . $encoding . '" standalone="' . (($declaration->standalone) ? 'yes' : 'no') . '"?>' ."\n". $this->declare_html_entities() . $data;
+ }
+ else
+ {
+ $this->error_string = 'SimplePie bug! Please report this!';
+ return false;
+ }
+ }
+
+ $return = true;
+
+ static $xml_is_sane = null;
+ if ($xml_is_sane === null)
+ {
+ $parser_check = xml_parser_create();
+ xml_parse_into_struct($parser_check, '<foo>&amp;</foo>', $values);
+ xml_parser_free($parser_check);
+ $xml_is_sane = isset($values[0]['value']);
+ }
+
+ // Create the parser
+ if ($xml_is_sane)
+ {
+ $xml = xml_parser_create_ns($this->encoding, $this->separator);
+ xml_parser_set_option($xml, XML_OPTION_SKIP_WHITE, 1);
+ xml_parser_set_option($xml, XML_OPTION_CASE_FOLDING, 0);
+ xml_set_object($xml, $this);
+ xml_set_character_data_handler($xml, 'cdata');
+ xml_set_element_handler($xml, 'tag_open', 'tag_close');
+
+ // Parse!
+ if (!xml_parse($xml, $data, true))
+ {
+ $this->error_code = xml_get_error_code($xml);
+ $this->error_string = xml_error_string($this->error_code);
+ $return = false;
+ }
+ $this->current_line = xml_get_current_line_number($xml);
+ $this->current_column = xml_get_current_column_number($xml);
+ $this->current_byte = xml_get_current_byte_index($xml);
+ xml_parser_free($xml);
+ return $return;
+ }
+ else
+ {
+ libxml_clear_errors();
+ $xml = new XMLReader();
+ $xml->xml($data);
+ while (@$xml->read())
+ {
+ switch ($xml->nodeType)
+ {
+
+ case constant('XMLReader::END_ELEMENT'):
+ if ($xml->namespaceURI !== '')
+ {
+ $tagName = $xml->namespaceURI . $this->separator . $xml->localName;
+ }
+ else
+ {
+ $tagName = $xml->localName;
+ }
+ $this->tag_close(null, $tagName);
+ break;
+ case constant('XMLReader::ELEMENT'):
+ $empty = $xml->isEmptyElement;
+ if ($xml->namespaceURI !== '')
+ {
+ $tagName = $xml->namespaceURI . $this->separator . $xml->localName;
+ }
+ else
+ {
+ $tagName = $xml->localName;
+ }
+ $attributes = array();
+ while ($xml->moveToNextAttribute())
+ {
+ if ($xml->namespaceURI !== '')
+ {
+ $attrName = $xml->namespaceURI . $this->separator . $xml->localName;
+ }
+ else
+ {
+ $attrName = $xml->localName;
+ }
+ $attributes[$attrName] = $xml->value;
+ }
+ $this->tag_open(null, $tagName, $attributes);
+ if ($empty)
+ {
+ $this->tag_close(null, $tagName);
+ }
+ break;
+ case constant('XMLReader::TEXT'):
+
+ case constant('XMLReader::CDATA'):
+ $this->cdata(null, $xml->value);
+ break;
+ }
+ }
+ if ($error = libxml_get_last_error())
+ {
+ $this->error_code = $error->code;
+ $this->error_string = $error->message;
+ $this->current_line = $error->line;
+ $this->current_column = $error->column;
+ return false;
+ }
+ else
+ {
+ return true;
+ }
+ }
+ }
+
+ public function get_error_code()
+ {
+ return $this->error_code;
+ }
+
+ public function get_error_string()
+ {
+ return $this->error_string;
+ }
+
+ public function get_current_line()
+ {
+ return $this->current_line;
+ }
+
+ public function get_current_column()
+ {
+ return $this->current_column;
+ }
+
+ public function get_current_byte()
+ {
+ return $this->current_byte;
+ }
+
+ public function get_data()
+ {
+ return $this->data;
+ }
+
+ public function tag_open($parser, $tag, $attributes)
+ {
+ list($this->namespace[], $this->element[]) = $this->split_ns($tag);
+
+ $attribs = array();
+ foreach ($attributes as $name => $value)
+ {
+ list($attrib_namespace, $attribute) = $this->split_ns($name);
+ $attribs[$attrib_namespace][$attribute] = $value;
+ }
+
+ if (isset($attribs[SIMPLEPIE_NAMESPACE_XML]['base']))
+ {
+ $base = $this->registry->call('Misc', 'absolutize_url', array($attribs[SIMPLEPIE_NAMESPACE_XML]['base'], end($this->xml_base)));
+ if ($base !== false)
+ {
+ $this->xml_base[] = $base;
+ $this->xml_base_explicit[] = true;
+ }
+ }
+ else
+ {
+ $this->xml_base[] = end($this->xml_base);
+ $this->xml_base_explicit[] = end($this->xml_base_explicit);
+ }
+
+ if (isset($attribs[SIMPLEPIE_NAMESPACE_XML]['lang']))
+ {
+ $this->xml_lang[] = $attribs[SIMPLEPIE_NAMESPACE_XML]['lang'];
+ }
+ else
+ {
+ $this->xml_lang[] = end($this->xml_lang);
+ }
+
+ if ($this->current_xhtml_construct >= 0)
+ {
+ $this->current_xhtml_construct++;
+ if (end($this->namespace) === SIMPLEPIE_NAMESPACE_XHTML)
+ {
+ $this->data['data'] .= '<' . end($this->element);
+ if (isset($attribs['']))
+ {
+ foreach ($attribs[''] as $name => $value)
+ {
+ $this->data['data'] .= ' ' . $name . '="' . htmlspecialchars($value, ENT_COMPAT, $this->encoding) . '"';
+ }
+ }
+ $this->data['data'] .= '>';
+ }
+ }
+ else
+ {
+ $this->datas[] =& $this->data;
+ $this->data =& $this->data['child'][end($this->namespace)][end($this->element)][];
+ $this->data = array('data' => '', 'attribs' => $attribs, 'xml_base' => end($this->xml_base), 'xml_base_explicit' => end($this->xml_base_explicit), 'xml_lang' => end($this->xml_lang));
+ if ((end($this->namespace) === SIMPLEPIE_NAMESPACE_ATOM_03 && in_array(end($this->element), array('title', 'tagline', 'copyright', 'info', 'summary', 'content')) && isset($attribs['']['mode']) && $attribs['']['mode'] === 'xml')
+ || (end($this->namespace) === SIMPLEPIE_NAMESPACE_ATOM_10 && in_array(end($this->element), array('rights', 'subtitle', 'summary', 'info', 'title', 'content')) && isset($attribs['']['type']) && $attribs['']['type'] === 'xhtml')
+ || (end($this->namespace) === SIMPLEPIE_NAMESPACE_RSS_20 && in_array(end($this->element), array('title')))
+ || (end($this->namespace) === SIMPLEPIE_NAMESPACE_RSS_090 && in_array(end($this->element), array('title')))
+ || (end($this->namespace) === SIMPLEPIE_NAMESPACE_RSS_10 && in_array(end($this->element), array('title'))))
+ {
+ $this->current_xhtml_construct = 0;
+ }
+ }
+ }
+
+ public function cdata($parser, $cdata)
+ {
+ if ($this->current_xhtml_construct >= 0)
+ {
+ $this->data['data'] .= htmlspecialchars($cdata, ENT_QUOTES, $this->encoding);
+ }
+ else
+ {
+ $this->data['data'] .= $cdata;
+ }
+ }
+
+ public function tag_close($parser, $tag)
+ {
+ if ($this->current_xhtml_construct >= 0)
+ {
+ $this->current_xhtml_construct--;
+ if (end($this->namespace) === SIMPLEPIE_NAMESPACE_XHTML && !in_array(end($this->element), array('area', 'base', 'basefont', 'br', 'col', 'frame', 'hr', 'img', 'input', 'isindex', 'link', 'meta', 'param')))
+ {
+ $this->data['data'] .= '</' . end($this->element) . '>';
+ }
+ }
+ if ($this->current_xhtml_construct === -1)
+ {
+ $this->data =& $this->datas[count($this->datas) - 1];
+ array_pop($this->datas);
+ }
+
+ array_pop($this->element);
+ array_pop($this->namespace);
+ array_pop($this->xml_base);
+ array_pop($this->xml_base_explicit);
+ array_pop($this->xml_lang);
+ }
+
+ public function split_ns($string)
+ {
+ static $cache = array();
+ if (!isset($cache[$string]))
+ {
+ if ($pos = strpos($string, $this->separator))
+ {
+ static $separator_length;
+ if (!$separator_length)
+ {
+ $separator_length = strlen($this->separator);
+ }
+ $namespace = substr($string, 0, $pos);
+ $local_name = substr($string, $pos + $separator_length);
+ if (strtolower($namespace) === SIMPLEPIE_NAMESPACE_ITUNES)
+ {
+ $namespace = SIMPLEPIE_NAMESPACE_ITUNES;
+ }
+
+ // Normalize the Media RSS namespaces
+ if ($namespace === SIMPLEPIE_NAMESPACE_MEDIARSS_WRONG ||
+ $namespace === SIMPLEPIE_NAMESPACE_MEDIARSS_WRONG2 ||
+ $namespace === SIMPLEPIE_NAMESPACE_MEDIARSS_WRONG3 ||
+ $namespace === SIMPLEPIE_NAMESPACE_MEDIARSS_WRONG4 ||
+ $namespace === SIMPLEPIE_NAMESPACE_MEDIARSS_WRONG5 )
+ {
+ $namespace = SIMPLEPIE_NAMESPACE_MEDIARSS;
+ }
+ $cache[$string] = array($namespace, $local_name);
+ }
+ else
+ {
+ $cache[$string] = array('', $string);
+ }
+ }
+ return $cache[$string];
+ }
+
+ private function parse_hcard($data, $category = false) {
+ $name = '';
+ $link = '';
+ // Check if h-card is set and pass that information on in the link.
+ if (isset($data['type']) && in_array('h-card', $data['type'])) {
+ if (isset($data['properties']['name'][0])) {
+ $name = $data['properties']['name'][0];
+ }
+ if (isset($data['properties']['url'][0])) {
+ $link = $data['properties']['url'][0];
+ if ($name === '') {
+ $name = $link;
+ }
+ else {
+ // can't have commas in categories.
+ $name = str_replace(',', '', $name);
+ }
+ $person_tag = $category ? '<span class="person-tag"></span>' : '';
+ return '<a class="h-card" href="'.$link.'">'.$person_tag.$name.'</a>';
+ }
+ }
+ return isset($data['value']) ? $data['value'] : '';
+ }
+
+ private function parse_microformats(&$data, $url) {
+ $feed_title = '';
+ $feed_author = NULL;
+ $author_cache = array();
+ $items = array();
+ $entries = array();
+ $mf = Mf2\parse($data, $url);
+ // First look for an h-feed.
+ $h_feed = array();
+ foreach ($mf['items'] as $mf_item) {
+ if (in_array('h-feed', $mf_item['type'])) {
+ $h_feed = $mf_item;
+ break;
+ }
+ // Also look for an h-feed in the children of each top level item.
+ if (!isset($mf_item['children'][0]['type'])) continue;
+ if (in_array('h-feed', $mf_item['children'][0]['type'])) {
+ $h_feed = $mf_item['children'][0];
+ // In this case the parent of the h-feed may be an h-card, so use it as
+ // the feed_author.
+ if (in_array('h-card', $mf_item['type'])) $feed_author = $mf_item;
+ break;
+ }
+ }
+ if (isset($h_feed['children'])) {
+ $entries = $h_feed['children'];
+ // Also set the feed title and store author from the h-feed if available.
+ if (isset($mf['items'][0]['properties']['name'][0])) {
+ $feed_title = $mf['items'][0]['properties']['name'][0];
+ }
+ if (isset($mf['items'][0]['properties']['author'][0])) {
+ $feed_author = $mf['items'][0]['properties']['author'][0];
+ }
+ }
+ else {
+ $entries = $mf['items'];
+ }
+ for ($i = 0; $i < count($entries); $i++) {
+ $entry = $entries[$i];
+ if (in_array('h-entry', $entry['type'])) {
+ $item = array();
+ $title = '';
+ $description = '';
+ if (isset($entry['properties']['url'][0])) {
+ $link = $entry['properties']['url'][0];
+ if (isset($link['value'])) $link = $link['value'];
+ $item['link'] = array(array('data' => $link));
+ }
+ if (isset($entry['properties']['uid'][0])) {
+ $guid = $entry['properties']['uid'][0];
+ if (isset($guid['value'])) $guid = $guid['value'];
+ $item['guid'] = array(array('data' => $guid));
+ }
+ if (isset($entry['properties']['name'][0])) {
+ $title = $entry['properties']['name'][0];
+ if (isset($title['value'])) $title = $title['value'];
+ $item['title'] = array(array('data' => $title));
+ }
+ if (isset($entry['properties']['author'][0]) || isset($feed_author)) {
+ // author is a special case, it can be plain text or an h-card array.
+ // If it's plain text it can also be a url that should be followed to
+ // get the actual h-card.
+ $author = isset($entry['properties']['author'][0]) ?
+ $entry['properties']['author'][0] : $feed_author;
+ if (!is_string($author)) {
+ $author = $this->parse_hcard($author);
+ }
+ else if (strpos($author, 'http') === 0) {
+ if (isset($author_cache[$author])) {
+ $author = $author_cache[$author];
+ }
+ else {
+ $mf = Mf2\fetch($author);
+ foreach ($mf['items'] as $hcard) {
+ // Only interested in an h-card by itself in this case.
+ if (!in_array('h-card', $hcard['type'])) {
+ continue;
+ }
+ // It must have a url property matching what we fetched.
+ if (!isset($hcard['properties']['url']) ||
+ !(in_array($author, $hcard['properties']['url']))) {
+ continue;
+ }
+ // Save parse_hcard the trouble of finding the correct url.
+ $hcard['properties']['url'][0] = $author;
+ // Cache this h-card for the next h-entry to check.
+ $author_cache[$author] = $this->parse_hcard($hcard);
+ $author = $author_cache[$author];
+ break;
+ }
+ }
+ }
+ $item['author'] = array(array('data' => $author));
+ }
+ if (isset($entry['properties']['photo'][0])) {
+ // If a photo is also in content, don't need to add it again here.
+ $content = '';
+ if (isset($entry['properties']['content'][0]['html'])) {
+ $content = $entry['properties']['content'][0]['html'];
+ }
+ $photo_list = array();
+ for ($j = 0; $j < count($entry['properties']['photo']); $j++) {
+ $photo = $entry['properties']['photo'][$j];
+ if (strpos($content, $photo) === false) {
+ $photo_list[] = $photo;
+ }
+ }
+ // When there's more than one photo show the first and use a lightbox.
+ $count = count($photo_list);
+ if ($count > 1) {
+ $description = '<p>';
+ for ($j = 0; $j < $count; $j++) {
+ $hidden = $j === 0 ? '' : 'class="hidden" ';
+ $description .= '<a href="'.$photo_list[$j].'" '.$hidden.
+ 'data-lightbox="image-set-'.$i.'">'.
+ '<img src="'.$photo_list[$j].'"></a>';
+ }
+ $description .= '<br><b>'.$count.' photos</b></p>';
+ }
+ else if ($count == 1) {
+ $description = '<p><img src="'.$photo_list[0].'"></p>';
+ }
+ }
+ if (isset($entry['properties']['content'][0]['html'])) {
+ // e-content['value'] is the same as p-name when they are on the same
+ // element. Use this to replace title with a strip_tags version so
+ // that alt text from images is not included in the title.
+ if ($entry['properties']['content'][0]['value'] === $title) {
+ $title = strip_tags($entry['properties']['content'][0]['html']);
+ $item['title'] = array(array('data' => $title));
+ }
+ $description .= $entry['properties']['content'][0]['html'];
+ if (isset($entry['properties']['in-reply-to'][0]['value'])) {
+ $in_reply_to = $entry['properties']['in-reply-to'][0]['value'];
+ $description .= '<p><span class="in-reply-to"></span> '.
+ '<a href="'.$in_reply_to.'">'.$in_reply_to.'</a><p>';
+ }
+ $item['description'] = array(array('data' => $description));
+ }
+ if (isset($entry['properties']['category'])) {
+ $category_csv = '';
+ // Categories can also contain h-cards.
+ foreach ($entry['properties']['category'] as $category) {
+ if ($category_csv !== '') $category_csv .= ', ';
+ if (is_string($category)) {
+ // Can't have commas in categories.
+ $category_csv .= str_replace(',', '', $category);
+ }
+ else {
+ $category_csv .= $this->parse_hcard($category, true);
+ }
+ }
+ $item['category'] = array(array('data' => $category_csv));
+ }
+ if (isset($entry['properties']['published'][0])) {
+ $timestamp = strtotime($entry['properties']['published'][0]);
+ $pub_date = date('F j Y g:ia', $timestamp).' GMT';
+ $item['pubDate'] = array(array('data' => $pub_date));
+ }
+ // The title and description are set to the empty string to represent
+ // a deleted item (which also makes it an invalid rss item).
+ if (isset($entry['properties']['deleted'][0])) {
+ $item['title'] = array(array('data' => ''));
+ $item['description'] = array(array('data' => ''));
+ }
+ $items[] = array('child' => array('' => $item));
+ }
+ }
+ // Mimic RSS data format when storing microformats.
+ $link = array(array('data' => $url));
+ $image = '';
+ if (!is_string($feed_author) &&
+ isset($feed_author['properties']['photo'][0])) {
+ $image = array(array('child' => array('' => array('url' =>
+ array(array('data' => $feed_author['properties']['photo'][0]))))));
+ }
+ // Use the a name given for the h-feed, or get the title from the html.
+ if ($feed_title !== '') {
+ $feed_title = array(array('data' => htmlspecialchars($feed_title)));
+ }
+ else if ($position = strpos($data, '<title>')) {
+ $start = $position < 200 ? 0 : $position - 200;
+ $check = substr($data, $start, 400);
+ $matches = array();
+ if (preg_match('/<title>(.+)<\/title>/', $check, $matches)) {
+ $feed_title = array(array('data' => htmlspecialchars($matches[1])));
+ }
+ }
+ $channel = array('channel' => array(array('child' => array('' =>
+ array('link' => $link, 'image' => $image, 'title' => $feed_title,
+ 'item' => $items)))));
+ $rss = array(array('attribs' => array('' => array('version' => '2.0')),
+ 'child' => array('' => $channel)));
+ $this->data = array('child' => array('' => array('rss' => $rss)));
+ return true;
+ }
+
+ private function declare_html_entities() {
+ // This is required because the RSS specification says that entity-encoded
+ // html is allowed, but the xml specification says they must be declared.
+ return '<!DOCTYPE html [ <!ENTITY nbsp "&#x00A0;"> <!ENTITY iexcl "&#x00A1;"> <!ENTITY cent "&#x00A2;"> <!ENTITY pound "&#x00A3;"> <!ENTITY curren "&#x00A4;"> <!ENTITY yen "&#x00A5;"> <!ENTITY brvbar "&#x00A6;"> <!ENTITY sect "&#x00A7;"> <!ENTITY uml "&#x00A8;"> <!ENTITY copy "&#x00A9;"> <!ENTITY ordf "&#x00AA;"> <!ENTITY laquo "&#x00AB;"> <!ENTITY not "&#x00AC;"> <!ENTITY shy "&#x00AD;"> <!ENTITY reg "&#x00AE;"> <!ENTITY macr "&#x00AF;"> <!ENTITY deg "&#x00B0;"> <!ENTITY plusmn "&#x00B1;"> <!ENTITY sup2 "&#x00B2;"> <!ENTITY sup3 "&#x00B3;"> <!ENTITY acute "&#x00B4;"> <!ENTITY micro "&#x00B5;"> <!ENTITY para "&#x00B6;"> <!ENTITY middot "&#x00B7;"> <!ENTITY cedil "&#x00B8;"> <!ENTITY sup1 "&#x00B9;"> <!ENTITY ordm "&#x00BA;"> <!ENTITY raquo "&#x00BB;"> <!ENTITY frac14 "&#x00BC;"> <!ENTITY frac12 "&#x00BD;"> <!ENTITY frac34 "&#x00BE;"> <!ENTITY iquest "&#x00BF;"> <!ENTITY Agrave "&#x00C0;"> <!ENTITY Aacute "&#x00C1;"> <!ENTITY Acirc "&#x00C2;"> <!ENTITY Atilde "&#x00C3;"> <!ENTITY Auml "&#x00C4;"> <!ENTITY Aring "&#x00C5;"> <!ENTITY AElig "&#x00C6;"> <!ENTITY Ccedil "&#x00C7;"> <!ENTITY Egrave "&#x00C8;"> <!ENTITY Eacute "&#x00C9;"> <!ENTITY Ecirc "&#x00CA;"> <!ENTITY Euml "&#x00CB;"> <!ENTITY Igrave "&#x00CC;"> <!ENTITY Iacute "&#x00CD;"> <!ENTITY Icirc "&#x00CE;"> <!ENTITY Iuml "&#x00CF;"> <!ENTITY ETH "&#x00D0;"> <!ENTITY Ntilde "&#x00D1;"> <!ENTITY Ograve "&#x00D2;"> <!ENTITY Oacute "&#x00D3;"> <!ENTITY Ocirc "&#x00D4;"> <!ENTITY Otilde "&#x00D5;"> <!ENTITY Ouml "&#x00D6;"> <!ENTITY times "&#x00D7;"> <!ENTITY Oslash "&#x00D8;"> <!ENTITY Ugrave "&#x00D9;"> <!ENTITY Uacute "&#x00DA;"> <!ENTITY Ucirc "&#x00DB;"> <!ENTITY Uuml "&#x00DC;"> <!ENTITY Yacute "&#x00DD;"> <!ENTITY THORN "&#x00DE;"> <!ENTITY szlig "&#x00DF;"> <!ENTITY agrave "&#x00E0;"> <!ENTITY aacute "&#x00E1;"> <!ENTITY acirc "&#x00E2;"> <!ENTITY atilde "&#x00E3;"> <!ENTITY auml "&#x00E4;"> <!ENTITY aring "&#x00E5;"> <!ENTITY aelig "&#x00E6;"> <!ENTITY ccedil "&#x00E7;"> <!ENTITY egrave "&#x00E8;"> <!ENTITY eacute "&#x00E9;"> <!ENTITY ecirc "&#x00EA;"> <!ENTITY euml "&#x00EB;"> <!ENTITY igrave "&#x00EC;"> <!ENTITY iacute "&#x00ED;"> <!ENTITY icirc "&#x00EE;"> <!ENTITY iuml "&#x00EF;"> <!ENTITY eth "&#x00F0;"> <!ENTITY ntilde "&#x00F1;"> <!ENTITY ograve "&#x00F2;"> <!ENTITY oacute "&#x00F3;"> <!ENTITY ocirc "&#x00F4;"> <!ENTITY otilde "&#x00F5;"> <!ENTITY ouml "&#x00F6;"> <!ENTITY divide "&#x00F7;"> <!ENTITY oslash "&#x00F8;"> <!ENTITY ugrave "&#x00F9;"> <!ENTITY uacute "&#x00FA;"> <!ENTITY ucirc "&#x00FB;"> <!ENTITY uuml "&#x00FC;"> <!ENTITY yacute "&#x00FD;"> <!ENTITY thorn "&#x00FE;"> <!ENTITY yuml "&#x00FF;"> <!ENTITY OElig "&#x0152;"> <!ENTITY oelig "&#x0153;"> <!ENTITY Scaron "&#x0160;"> <!ENTITY scaron "&#x0161;"> <!ENTITY Yuml "&#x0178;"> <!ENTITY fnof "&#x0192;"> <!ENTITY circ "&#x02C6;"> <!ENTITY tilde "&#x02DC;"> <!ENTITY Alpha "&#x0391;"> <!ENTITY Beta "&#x0392;"> <!ENTITY Gamma "&#x0393;"> <!ENTITY Epsilon "&#x0395;"> <!ENTITY Zeta "&#x0396;"> <!ENTITY Eta "&#x0397;"> <!ENTITY Theta "&#x0398;"> <!ENTITY Iota "&#x0399;"> <!ENTITY Kappa "&#x039A;"> <!ENTITY Lambda "&#x039B;"> <!ENTITY Mu "&#x039C;"> <!ENTITY Nu "&#x039D;"> <!ENTITY Xi "&#x039E;"> <!ENTITY Omicron "&#x039F;"> <!ENTITY Pi "&#x03A0;"> <!ENTITY Rho "&#x03A1;"> <!ENTITY Sigma "&#x03A3;"> <!ENTITY Tau "&#x03A4;"> <!ENTITY Upsilon "&#x03A5;"> <!ENTITY Phi "&#x03A6;"> <!ENTITY Chi "&#x03A7;"> <!ENTITY Psi "&#x03A8;"> <!ENTITY Omega "&#x03A9;"> <!ENTITY alpha "&#x03B1;"> <!ENTITY beta "&#x03B2;"> <!ENTITY gamma "&#x03B3;"> <!ENTITY delta "&#x03B4;"> <!ENTITY epsilon "&#x03B5;"> <!ENTITY zeta "&#x03B6;"> <!ENTITY eta "&#x03B7;"> <!ENTITY theta "&#x03B8;"> <!ENTITY iota "&#x03B9;"> <!ENTITY kappa "&#x03BA;"> <!ENTITY lambda "&#x03BB;"> <!ENTITY mu "&#x03BC;"> <!ENTITY nu "&#x03BD;"> <!ENTITY xi "&#x03BE;"> <!ENTITY omicron "&#x03BF;"> <!ENTITY pi "&#x03C0;"> <!ENTITY rho "&#x03C1;"> <!ENTITY sigmaf "&#x03C2;"> <!ENTITY sigma "&#x03C3;"> <!ENTITY tau "&#x03C4;"> <!ENTITY upsilon "&#x03C5;"> <!ENTITY phi "&#x03C6;"> <!ENTITY chi "&#x03C7;"> <!ENTITY psi "&#x03C8;"> <!ENTITY omega "&#x03C9;"> <!ENTITY thetasym "&#x03D1;"> <!ENTITY upsih "&#x03D2;"> <!ENTITY piv "&#x03D6;"> <!ENTITY ensp "&#x2002;"> <!ENTITY emsp "&#x2003;"> <!ENTITY thinsp "&#x2009;"> <!ENTITY zwnj "&#x200C;"> <!ENTITY zwj "&#x200D;"> <!ENTITY lrm "&#x200E;"> <!ENTITY rlm "&#x200F;"> <!ENTITY ndash "&#x2013;"> <!ENTITY mdash "&#x2014;"> <!ENTITY lsquo "&#x2018;"> <!ENTITY rsquo "&#x2019;"> <!ENTITY sbquo "&#x201A;"> <!ENTITY ldquo "&#x201C;"> <!ENTITY rdquo "&#x201D;"> <!ENTITY bdquo "&#x201E;"> <!ENTITY dagger "&#x2020;"> <!ENTITY Dagger "&#x2021;"> <!ENTITY bull "&#x2022;"> <!ENTITY hellip "&#x2026;"> <!ENTITY permil "&#x2030;"> <!ENTITY prime "&#x2032;"> <!ENTITY Prime "&#x2033;"> <!ENTITY lsaquo "&#x2039;"> <!ENTITY rsaquo "&#x203A;"> <!ENTITY oline "&#x203E;"> <!ENTITY frasl "&#x2044;"> <!ENTITY euro "&#x20AC;"> <!ENTITY image "&#x2111;"> <!ENTITY weierp "&#x2118;"> <!ENTITY real "&#x211C;"> <!ENTITY trade "&#x2122;"> <!ENTITY alefsym "&#x2135;"> <!ENTITY larr "&#x2190;"> <!ENTITY uarr "&#x2191;"> <!ENTITY rarr "&#x2192;"> <!ENTITY darr "&#x2193;"> <!ENTITY harr "&#x2194;"> <!ENTITY crarr "&#x21B5;"> <!ENTITY lArr "&#x21D0;"> <!ENTITY uArr "&#x21D1;"> <!ENTITY rArr "&#x21D2;"> <!ENTITY dArr "&#x21D3;"> <!ENTITY hArr "&#x21D4;"> <!ENTITY forall "&#x2200;"> <!ENTITY part "&#x2202;"> <!ENTITY exist "&#x2203;"> <!ENTITY empty "&#x2205;"> <!ENTITY nabla "&#x2207;"> <!ENTITY isin "&#x2208;"> <!ENTITY notin "&#x2209;"> <!ENTITY ni "&#x220B;"> <!ENTITY prod "&#x220F;"> <!ENTITY sum "&#x2211;"> <!ENTITY minus "&#x2212;"> <!ENTITY lowast "&#x2217;"> <!ENTITY radic "&#x221A;"> <!ENTITY prop "&#x221D;"> <!ENTITY infin "&#x221E;"> <!ENTITY ang "&#x2220;"> <!ENTITY and "&#x2227;"> <!ENTITY or "&#x2228;"> <!ENTITY cap "&#x2229;"> <!ENTITY cup "&#x222A;"> <!ENTITY int "&#x222B;"> <!ENTITY there4 "&#x2234;"> <!ENTITY sim "&#x223C;"> <!ENTITY cong "&#x2245;"> <!ENTITY asymp "&#x2248;"> <!ENTITY ne "&#x2260;"> <!ENTITY equiv "&#x2261;"> <!ENTITY le "&#x2264;"> <!ENTITY ge "&#x2265;"> <!ENTITY sub "&#x2282;"> <!ENTITY sup "&#x2283;"> <!ENTITY nsub "&#x2284;"> <!ENTITY sube "&#x2286;"> <!ENTITY supe "&#x2287;"> <!ENTITY oplus "&#x2295;"> <!ENTITY otimes "&#x2297;"> <!ENTITY perp "&#x22A5;"> <!ENTITY sdot "&#x22C5;"> <!ENTITY lceil "&#x2308;"> <!ENTITY rceil "&#x2309;"> <!ENTITY lfloor "&#x230A;"> <!ENTITY rfloor "&#x230B;"> <!ENTITY lang "&#x2329;"> <!ENTITY rang "&#x232A;"> <!ENTITY loz "&#x25CA;"> <!ENTITY spades "&#x2660;"> <!ENTITY clubs "&#x2663;"> <!ENTITY hearts "&#x2665;"> <!ENTITY diams "&#x2666;"> ]>';
+ }
+} \ No newline at end of file
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Rating.php b/vendor/simplepie/simplepie/library/SimplePie/Rating.php
new file mode 100644
index 000000000..eaf57080c
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Rating.php
@@ -0,0 +1,128 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * Handles `<media:rating>` or `<itunes:explicit>` tags as defined in Media RSS and iTunes RSS respectively
+ *
+ * Used by {@see SimplePie_Enclosure::get_rating()} and {@see SimplePie_Enclosure::get_ratings()}
+ *
+ * This class can be overloaded with {@see SimplePie::set_rating_class()}
+ *
+ * @package SimplePie
+ * @subpackage API
+ */
+class SimplePie_Rating
+{
+ /**
+ * Rating scheme
+ *
+ * @var string
+ * @see get_scheme()
+ */
+ var $scheme;
+
+ /**
+ * Rating value
+ *
+ * @var string
+ * @see get_value()
+ */
+ var $value;
+
+ /**
+ * Constructor, used to input the data
+ *
+ * For documentation on all the parameters, see the corresponding
+ * properties and their accessors
+ */
+ public function __construct($scheme = null, $value = null)
+ {
+ $this->scheme = $scheme;
+ $this->value = $value;
+ }
+
+ /**
+ * String-ified version
+ *
+ * @return string
+ */
+ public function __toString()
+ {
+ // There is no $this->data here
+ return md5(serialize($this));
+ }
+
+ /**
+ * Get the organizational scheme for the rating
+ *
+ * @return string|null
+ */
+ public function get_scheme()
+ {
+ if ($this->scheme !== null)
+ {
+ return $this->scheme;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the value of the rating
+ *
+ * @return string|null
+ */
+ public function get_value()
+ {
+ if ($this->value !== null)
+ {
+ return $this->value;
+ }
+ else
+ {
+ return null;
+ }
+ }
+}
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Registry.php b/vendor/simplepie/simplepie/library/SimplePie/Registry.php
new file mode 100755
index 000000000..e0909bb74
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Registry.php
@@ -0,0 +1,224 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * Handles creating objects and calling methods
+ *
+ * Access this via {@see SimplePie::get_registry()}
+ *
+ * @package SimplePie
+ */
+class SimplePie_Registry
+{
+ /**
+ * Default class mapping
+ *
+ * Overriding classes *must* subclass these.
+ *
+ * @var array
+ */
+ protected $default = array(
+ 'Cache' => 'SimplePie_Cache',
+ 'Locator' => 'SimplePie_Locator',
+ 'Parser' => 'SimplePie_Parser',
+ 'File' => 'SimplePie_File',
+ 'Sanitize' => 'SimplePie_Sanitize',
+ 'Item' => 'SimplePie_Item',
+ 'Author' => 'SimplePie_Author',
+ 'Category' => 'SimplePie_Category',
+ 'Enclosure' => 'SimplePie_Enclosure',
+ 'Caption' => 'SimplePie_Caption',
+ 'Copyright' => 'SimplePie_Copyright',
+ 'Credit' => 'SimplePie_Credit',
+ 'Rating' => 'SimplePie_Rating',
+ 'Restriction' => 'SimplePie_Restriction',
+ 'Content_Type_Sniffer' => 'SimplePie_Content_Type_Sniffer',
+ 'Source' => 'SimplePie_Source',
+ 'Misc' => 'SimplePie_Misc',
+ 'XML_Declaration_Parser' => 'SimplePie_XML_Declaration_Parser',
+ 'Parse_Date' => 'SimplePie_Parse_Date',
+ );
+
+ /**
+ * Class mapping
+ *
+ * @see register()
+ * @var array
+ */
+ protected $classes = array();
+
+ /**
+ * Legacy classes
+ *
+ * @see register()
+ * @var array
+ */
+ protected $legacy = array();
+
+ /**
+ * Constructor
+ *
+ * No-op
+ */
+ public function __construct() { }
+
+ /**
+ * Register a class
+ *
+ * @param string $type See {@see $default} for names
+ * @param string $class Class name, must subclass the corresponding default
+ * @param bool $legacy Whether to enable legacy support for this class
+ * @return bool Successfulness
+ */
+ public function register($type, $class, $legacy = false)
+ {
+ if (!@is_subclass_of($class, $this->default[$type]))
+ {
+ return false;
+ }
+
+ $this->classes[$type] = $class;
+
+ if ($legacy)
+ {
+ $this->legacy[] = $class;
+ }
+
+ return true;
+ }
+
+ /**
+ * Get the class registered for a type
+ *
+ * Where possible, use {@see create()} or {@see call()} instead
+ *
+ * @param string $type
+ * @return string|null
+ */
+ public function get_class($type)
+ {
+ if (!empty($this->classes[$type]))
+ {
+ return $this->classes[$type];
+ }
+ if (!empty($this->default[$type]))
+ {
+ return $this->default[$type];
+ }
+
+ return null;
+ }
+
+ /**
+ * Create a new instance of a given type
+ *
+ * @param string $type
+ * @param array $parameters Parameters to pass to the constructor
+ * @return object Instance of class
+ */
+ public function &create($type, $parameters = array())
+ {
+ $class = $this->get_class($type);
+
+ if (in_array($class, $this->legacy))
+ {
+ switch ($type)
+ {
+ case 'locator':
+ // Legacy: file, timeout, useragent, file_class, max_checked_feeds, content_type_sniffer_class
+ // Specified: file, timeout, useragent, max_checked_feeds
+ $replacement = array($this->get_class('file'), $parameters[3], $this->get_class('content_type_sniffer'));
+ array_splice($parameters, 3, 1, $replacement);
+ break;
+ }
+ }
+
+ if (!method_exists($class, '__construct'))
+ {
+ $instance = new $class;
+ }
+ else
+ {
+ $reflector = new ReflectionClass($class);
+ $instance = $reflector->newInstanceArgs($parameters);
+ }
+
+ if (method_exists($instance, 'set_registry'))
+ {
+ $instance->set_registry($this);
+ }
+ return $instance;
+ }
+
+ /**
+ * Call a static method for a type
+ *
+ * @param string $type
+ * @param string $method
+ * @param array $parameters
+ * @return mixed
+ */
+ public function &call($type, $method, $parameters = array())
+ {
+ $class = $this->get_class($type);
+
+ if (in_array($class, $this->legacy))
+ {
+ switch ($type)
+ {
+ case 'Cache':
+ // For backwards compatibility with old non-static
+ // Cache::create() methods
+ if ($method === 'get_handler')
+ {
+ $result = @call_user_func_array(array($class, 'create'), $parameters);
+ return $result;
+ }
+ break;
+ }
+ }
+
+ $result = call_user_func_array(array($class, $method), $parameters);
+ return $result;
+ }
+}
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Restriction.php b/vendor/simplepie/simplepie/library/SimplePie/Restriction.php
new file mode 100644
index 000000000..001a5cd28
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Restriction.php
@@ -0,0 +1,154 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * Handles `<media:restriction>` as defined in Media RSS
+ *
+ * Used by {@see SimplePie_Enclosure::get_restriction()} and {@see SimplePie_Enclosure::get_restrictions()}
+ *
+ * This class can be overloaded with {@see SimplePie::set_restriction_class()}
+ *
+ * @package SimplePie
+ * @subpackage API
+ */
+class SimplePie_Restriction
+{
+ /**
+ * Relationship ('allow'/'deny')
+ *
+ * @var string
+ * @see get_relationship()
+ */
+ var $relationship;
+
+ /**
+ * Type of restriction
+ *
+ * @var string
+ * @see get_type()
+ */
+ var $type;
+
+ /**
+ * Restricted values
+ *
+ * @var string
+ * @see get_value()
+ */
+ var $value;
+
+ /**
+ * Constructor, used to input the data
+ *
+ * For documentation on all the parameters, see the corresponding
+ * properties and their accessors
+ */
+ public function __construct($relationship = null, $type = null, $value = null)
+ {
+ $this->relationship = $relationship;
+ $this->type = $type;
+ $this->value = $value;
+ }
+
+ /**
+ * String-ified version
+ *
+ * @return string
+ */
+ public function __toString()
+ {
+ // There is no $this->data here
+ return md5(serialize($this));
+ }
+
+ /**
+ * Get the relationship
+ *
+ * @return string|null Either 'allow' or 'deny'
+ */
+ public function get_relationship()
+ {
+ if ($this->relationship !== null)
+ {
+ return $this->relationship;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the type
+ *
+ * @return string|null
+ */
+ public function get_type()
+ {
+ if ($this->type !== null)
+ {
+ return $this->type;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Get the list of restricted things
+ *
+ * @return string|null
+ */
+ public function get_value()
+ {
+ if ($this->value !== null)
+ {
+ return $this->value;
+ }
+ else
+ {
+ return null;
+ }
+ }
+}
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Sanitize.php b/vendor/simplepie/simplepie/library/SimplePie/Sanitize.php
new file mode 100644
index 000000000..5a11721df
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Sanitize.php
@@ -0,0 +1,591 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * Used for data cleanup and post-processing
+ *
+ *
+ * This class can be overloaded with {@see SimplePie::set_sanitize_class()}
+ *
+ * @package SimplePie
+ * @todo Move to using an actual HTML parser (this will allow tags to be properly stripped, and to switch between HTML and XHTML), this will also make it easier to shorten a string while preserving HTML tags
+ */
+class SimplePie_Sanitize
+{
+ // Private vars
+ var $base;
+
+ // Options
+ var $remove_div = true;
+ var $image_handler = '';
+ var $strip_htmltags = array('base', 'blink', 'body', 'doctype', 'embed', 'font', 'form', 'frame', 'frameset', 'html', 'iframe', 'input', 'marquee', 'meta', 'noscript', 'object', 'param', 'script', 'style');
+ var $encode_instead_of_strip = false;
+ var $strip_attributes = array('bgsound', 'expr', 'id', 'style', 'onclick', 'onerror', 'onfinish', 'onmouseover', 'onmouseout', 'onfocus', 'onblur', 'lowsrc', 'dynsrc');
+ var $add_attributes = array('audio' => array('preload' => 'none'), 'iframe' => array('sandbox' => 'allow-scripts allow-same-origin'), 'video' => array('preload' => 'none'));
+ var $strip_comments = false;
+ var $output_encoding = 'UTF-8';
+ var $enable_cache = true;
+ var $cache_location = './cache';
+ var $cache_name_function = 'md5';
+ var $timeout = 10;
+ var $useragent = '';
+ var $force_fsockopen = false;
+ var $replace_url_attributes = null;
+
+ public function __construct()
+ {
+ // Set defaults
+ $this->set_url_replacements(null);
+ }
+
+ public function remove_div($enable = true)
+ {
+ $this->remove_div = (bool) $enable;
+ }
+
+ public function set_image_handler($page = false)
+ {
+ if ($page)
+ {
+ $this->image_handler = (string) $page;
+ }
+ else
+ {
+ $this->image_handler = false;
+ }
+ }
+
+ public function set_registry(SimplePie_Registry $registry)
+ {
+ $this->registry = $registry;
+ }
+
+ public function pass_cache_data($enable_cache = true, $cache_location = './cache', $cache_name_function = 'md5', $cache_class = 'SimplePie_Cache')
+ {
+ if (isset($enable_cache))
+ {
+ $this->enable_cache = (bool) $enable_cache;
+ }
+
+ if ($cache_location)
+ {
+ $this->cache_location = (string) $cache_location;
+ }
+
+ if ($cache_name_function)
+ {
+ $this->cache_name_function = (string) $cache_name_function;
+ }
+ }
+
+ public function pass_file_data($file_class = 'SimplePie_File', $timeout = 10, $useragent = '', $force_fsockopen = false)
+ {
+ if ($timeout)
+ {
+ $this->timeout = (string) $timeout;
+ }
+
+ if ($useragent)
+ {
+ $this->useragent = (string) $useragent;
+ }
+
+ if ($force_fsockopen)
+ {
+ $this->force_fsockopen = (string) $force_fsockopen;
+ }
+ }
+
+ public function strip_htmltags($tags = array('base', 'blink', 'body', 'doctype', 'embed', 'font', 'form', 'frame', 'frameset', 'html', 'iframe', 'input', 'marquee', 'meta', 'noscript', 'object', 'param', 'script', 'style'))
+ {
+ if ($tags)
+ {
+ if (is_array($tags))
+ {
+ $this->strip_htmltags = $tags;
+ }
+ else
+ {
+ $this->strip_htmltags = explode(',', $tags);
+ }
+ }
+ else
+ {
+ $this->strip_htmltags = false;
+ }
+ }
+
+ public function encode_instead_of_strip($encode = false)
+ {
+ $this->encode_instead_of_strip = (bool) $encode;
+ }
+
+ public function strip_attributes($attribs = array('bgsound', 'expr', 'id', 'style', 'onclick', 'onerror', 'onfinish', 'onmouseover', 'onmouseout', 'onfocus', 'onblur', 'lowsrc', 'dynsrc'))
+ {
+ if ($attribs)
+ {
+ if (is_array($attribs))
+ {
+ $this->strip_attributes = $attribs;
+ }
+ else
+ {
+ $this->strip_attributes = explode(',', $attribs);
+ }
+ }
+ else
+ {
+ $this->strip_attributes = false;
+ }
+ }
+
+ public function add_attributes($attribs = array('audio' => array('preload' => 'none'), 'iframe' => array('sandbox' => 'allow-scripts allow-same-origin'), 'video' => array('preload' => 'none')))
+ {
+ if ($attribs)
+ {
+ if (is_array($attribs))
+ {
+ $this->add_attributes = $attribs;
+ }
+ else
+ {
+ $this->add_attributes = explode(',', $attribs);
+ }
+ }
+ else
+ {
+ $this->add_attributes = false;
+ }
+ }
+
+ public function strip_comments($strip = false)
+ {
+ $this->strip_comments = (bool) $strip;
+ }
+
+ public function set_output_encoding($encoding = 'UTF-8')
+ {
+ $this->output_encoding = (string) $encoding;
+ }
+
+ /**
+ * Set element/attribute key/value pairs of HTML attributes
+ * containing URLs that need to be resolved relative to the feed
+ *
+ * Defaults to |a|@href, |area|@href, |blockquote|@cite, |del|@cite,
+ * |form|@action, |img|@longdesc, |img|@src, |input|@src, |ins|@cite,
+ * |q|@cite
+ *
+ * @since 1.0
+ * @param array|null $element_attribute Element/attribute key/value pairs, null for default
+ */
+ public function set_url_replacements($element_attribute = null)
+ {
+ if ($element_attribute === null)
+ {
+ $element_attribute = array(
+ 'a' => 'href',
+ 'area' => 'href',
+ 'blockquote' => 'cite',
+ 'del' => 'cite',
+ 'form' => 'action',
+ 'img' => array(
+ 'longdesc',
+ 'src'
+ ),
+ 'input' => 'src',
+ 'ins' => 'cite',
+ 'q' => 'cite'
+ );
+ }
+ $this->replace_url_attributes = (array) $element_attribute;
+ }
+
+ public function sanitize($data, $type, $base = '')
+ {
+ $data = trim($data);
+ if ($data !== '' || $type & SIMPLEPIE_CONSTRUCT_IRI)
+ {
+ if ($type & SIMPLEPIE_CONSTRUCT_MAYBE_HTML)
+ {
+ if (preg_match('/(&(#(x[0-9a-fA-F]+|[0-9]+)|[a-zA-Z0-9]+)|<\/[A-Za-z][^\x09\x0A\x0B\x0C\x0D\x20\x2F\x3E]*' . SIMPLEPIE_PCRE_HTML_ATTRIBUTE . '>)/', $data))
+ {
+ $type |= SIMPLEPIE_CONSTRUCT_HTML;
+ }
+ else
+ {
+ $type |= SIMPLEPIE_CONSTRUCT_TEXT;
+ }
+ }
+
+ if ($type & SIMPLEPIE_CONSTRUCT_BASE64)
+ {
+ $data = base64_decode($data);
+ }
+
+ if ($type & (SIMPLEPIE_CONSTRUCT_HTML | SIMPLEPIE_CONSTRUCT_XHTML))
+ {
+
+ if (!class_exists('DOMDocument'))
+ {
+ throw new SimplePie_Exception('DOMDocument not found, unable to use sanitizer');
+ }
+ $document = new DOMDocument();
+ $document->encoding = 'UTF-8';
+
+ $data = $this->preprocess($data, $type);
+
+ set_error_handler(array('SimplePie_Misc', 'silence_errors'));
+ $document->loadHTML($data);
+ restore_error_handler();
+
+ $xpath = new DOMXPath($document);
+
+ // Strip comments
+ if ($this->strip_comments)
+ {
+ $comments = $xpath->query('//comment()');
+
+ foreach ($comments as $comment)
+ {
+ $comment->parentNode->removeChild($comment);
+ }
+ }
+
+ // Strip out HTML tags and attributes that might cause various security problems.
+ // Based on recommendations by Mark Pilgrim at:
+ // http://diveintomark.org/archives/2003/06/12/how_to_consume_rss_safely
+ if ($this->strip_htmltags)
+ {
+ foreach ($this->strip_htmltags as $tag)
+ {
+ $this->strip_tag($tag, $document, $xpath, $type);
+ }
+ }
+
+ if ($this->strip_attributes)
+ {
+ foreach ($this->strip_attributes as $attrib)
+ {
+ $this->strip_attr($attrib, $xpath);
+ }
+ }
+
+ if ($this->add_attributes)
+ {
+ foreach ($this->add_attributes as $tag => $valuePairs)
+ {
+ $this->add_attr($tag, $valuePairs, $document);
+ }
+ }
+
+ // Replace relative URLs
+ $this->base = $base;
+ foreach ($this->replace_url_attributes as $element => $attributes)
+ {
+ $this->replace_urls($document, $element, $attributes);
+ }
+
+ // If image handling (caching, etc.) is enabled, cache and rewrite all the image tags.
+ if (isset($this->image_handler) && ((string) $this->image_handler) !== '' && $this->enable_cache)
+ {
+ $images = $document->getElementsByTagName('img');
+ foreach ($images as $img)
+ {
+ if ($img->hasAttribute('src'))
+ {
+ $image_url = call_user_func($this->cache_name_function, $img->getAttribute('src'));
+ $cache = $this->registry->call('Cache', 'get_handler', array($this->cache_location, $image_url, 'spi'));
+
+ if ($cache->load())
+ {
+ $img->setAttribute('src', $this->image_handler . $image_url);
+ }
+ else
+ {
+ $file = $this->registry->create('File', array($img->getAttribute('src'), $this->timeout, 5, array('X-FORWARDED-FOR' => $_SERVER['REMOTE_ADDR']), $this->useragent, $this->force_fsockopen));
+ $headers = $file->headers;
+
+ if ($file->success && ($file->method & SIMPLEPIE_FILE_SOURCE_REMOTE === 0 || ($file->status_code === 200 || $file->status_code > 206 && $file->status_code < 300)))
+ {
+ if ($cache->save(array('headers' => $file->headers, 'body' => $file->body)))
+ {
+ $img->setAttribute('src', $this->image_handler . $image_url);
+ }
+ else
+ {
+ trigger_error("$this->cache_location is not writeable. Make sure you've set the correct relative or absolute path, and that the location is server-writable.", E_USER_WARNING);
+ }
+ }
+ }
+ }
+ }
+ }
+
+ // Get content node
+ $div = $document->getElementsByTagName('body')->item(0)->firstChild;
+ // Finally, convert to a HTML string
+ if (version_compare(PHP_VERSION, '5.3.6', '>='))
+ {
+ $data = trim($document->saveHTML($div));
+ }
+ else
+ {
+ $data = trim($document->saveXML($div));
+ }
+
+ if ($this->remove_div)
+ {
+ $data = preg_replace('/^<div' . SIMPLEPIE_PCRE_XML_ATTRIBUTE . '>/', '', $data);
+ $data = preg_replace('/<\/div>$/', '', $data);
+ }
+ else
+ {
+ $data = preg_replace('/^<div' . SIMPLEPIE_PCRE_XML_ATTRIBUTE . '>/', '<div>', $data);
+ }
+ }
+
+ if ($type & SIMPLEPIE_CONSTRUCT_IRI)
+ {
+ $absolute = $this->registry->call('Misc', 'absolutize_url', array($data, $base));
+ if ($absolute !== false)
+ {
+ $data = $absolute;
+ }
+ }
+
+ if ($type & (SIMPLEPIE_CONSTRUCT_TEXT | SIMPLEPIE_CONSTRUCT_IRI))
+ {
+ $data = htmlspecialchars($data, ENT_COMPAT, 'UTF-8');
+ }
+
+ if ($this->output_encoding !== 'UTF-8')
+ {
+ $data = $this->registry->call('Misc', 'change_encoding', array($data, 'UTF-8', $this->output_encoding));
+ }
+ }
+ return $data;
+ }
+
+ protected function preprocess($html, $type)
+ {
+ $ret = '';
+ $html = preg_replace('%</?(?:html|body)[^>]*?'.'>%is', '', $html);
+ if ($type & ~SIMPLEPIE_CONSTRUCT_XHTML)
+ {
+ // Atom XHTML constructs are wrapped with a div by default
+ // Note: No protection if $html contains a stray </div>!
+ $html = '<div>' . $html . '</div>';
+ $ret .= '<!DOCTYPE html>';
+ $content_type = 'text/html';
+ }
+ else
+ {
+ $ret .= '<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">';
+ $content_type = 'application/xhtml+xml';
+ }
+
+ $ret .= '<html><head>';
+ $ret .= '<meta http-equiv="Content-Type" content="' . $content_type . '; charset=utf-8" />';
+ $ret .= '</head><body>' . $html . '</body></html>';
+ return $ret;
+ }
+
+ public function replace_urls($document, $tag, $attributes)
+ {
+ if (!is_array($attributes))
+ {
+ $attributes = array($attributes);
+ }
+
+ if (!is_array($this->strip_htmltags) || !in_array($tag, $this->strip_htmltags))
+ {
+ $elements = $document->getElementsByTagName($tag);
+ foreach ($elements as $element)
+ {
+ foreach ($attributes as $attribute)
+ {
+ if ($element->hasAttribute($attribute))
+ {
+ $value = $this->registry->call('Misc', 'absolutize_url', array($element->getAttribute($attribute), $this->base));
+ if ($value !== false)
+ {
+ $element->setAttribute($attribute, $value);
+ }
+ }
+ }
+ }
+ }
+ }
+
+ public function do_strip_htmltags($match)
+ {
+ if ($this->encode_instead_of_strip)
+ {
+ if (isset($match[4]) && !in_array(strtolower($match[1]), array('script', 'style')))
+ {
+ $match[1] = htmlspecialchars($match[1], ENT_COMPAT, 'UTF-8');
+ $match[2] = htmlspecialchars($match[2], ENT_COMPAT, 'UTF-8');
+ return "&lt;$match[1]$match[2]&gt;$match[3]&lt;/$match[1]&gt;";
+ }
+ else
+ {
+ return htmlspecialchars($match[0], ENT_COMPAT, 'UTF-8');
+ }
+ }
+ elseif (isset($match[4]) && !in_array(strtolower($match[1]), array('script', 'style')))
+ {
+ return $match[4];
+ }
+ else
+ {
+ return '';
+ }
+ }
+
+ protected function strip_tag($tag, $document, $xpath, $type)
+ {
+ $elements = $xpath->query('body//' . $tag);
+ if ($this->encode_instead_of_strip)
+ {
+ foreach ($elements as $element)
+ {
+ $fragment = $document->createDocumentFragment();
+
+ // For elements which aren't script or style, include the tag itself
+ if (!in_array($tag, array('script', 'style')))
+ {
+ $text = '<' . $tag;
+ if ($element->hasAttributes())
+ {
+ $attrs = array();
+ foreach ($element->attributes as $name => $attr)
+ {
+ $value = $attr->value;
+
+ // In XHTML, empty values should never exist, so we repeat the value
+ if (empty($value) && ($type & SIMPLEPIE_CONSTRUCT_XHTML))
+ {
+ $value = $name;
+ }
+ // For HTML, empty is fine
+ elseif (empty($value) && ($type & SIMPLEPIE_CONSTRUCT_HTML))
+ {
+ $attrs[] = $name;
+ continue;
+ }
+
+ // Standard attribute text
+ $attrs[] = $name . '="' . $attr->value . '"';
+ }
+ $text .= ' ' . implode(' ', $attrs);
+ }
+ $text .= '>';
+ $fragment->appendChild(new DOMText($text));
+ }
+
+ $number = $element->childNodes->length;
+ for ($i = $number; $i > 0; $i--)
+ {
+ $child = $element->childNodes->item(0);
+ $fragment->appendChild($child);
+ }
+
+ if (!in_array($tag, array('script', 'style')))
+ {
+ $fragment->appendChild(new DOMText('</' . $tag . '>'));
+ }
+
+ $element->parentNode->replaceChild($fragment, $element);
+ }
+
+ return;
+ }
+ elseif (in_array($tag, array('script', 'style')))
+ {
+ foreach ($elements as $element)
+ {
+ $element->parentNode->removeChild($element);
+ }
+
+ return;
+ }
+ else
+ {
+ foreach ($elements as $element)
+ {
+ $fragment = $document->createDocumentFragment();
+ $number = $element->childNodes->length;
+ for ($i = $number; $i > 0; $i--)
+ {
+ $child = $element->childNodes->item(0);
+ $fragment->appendChild($child);
+ }
+
+ $element->parentNode->replaceChild($fragment, $element);
+ }
+ }
+ }
+
+ protected function strip_attr($attrib, $xpath)
+ {
+ $elements = $xpath->query('//*[@' . $attrib . ']');
+
+ foreach ($elements as $element)
+ {
+ $element->removeAttribute($attrib);
+ }
+ }
+
+ protected function add_attr($tag, $valuePairs, $document)
+ {
+ $elements = $document->getElementsByTagName($tag);
+ foreach ($elements as $element)
+ {
+ foreach ($valuePairs as $attrib => $value)
+ {
+ $element->setAttribute($attrib, $value);
+ }
+ }
+ }
+}
diff --git a/vendor/simplepie/simplepie/library/SimplePie/Source.php b/vendor/simplepie/simplepie/library/SimplePie/Source.php
new file mode 100644
index 000000000..1a66a392d
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/Source.php
@@ -0,0 +1,610 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+/**
+ * Handles `<atom:source>`
+ *
+ * Used by {@see SimplePie_Item::get_source()}
+ *
+ * This class can be overloaded with {@see SimplePie::set_source_class()}
+ *
+ * @package SimplePie
+ * @subpackage API
+ */
+class SimplePie_Source
+{
+ var $item;
+ var $data = array();
+ protected $registry;
+
+ public function __construct($item, $data)
+ {
+ $this->item = $item;
+ $this->data = $data;
+ }
+
+ public function set_registry(SimplePie_Registry $registry)
+ {
+ $this->registry = $registry;
+ }
+
+ public function __toString()
+ {
+ return md5(serialize($this->data));
+ }
+
+ public function get_source_tags($namespace, $tag)
+ {
+ if (isset($this->data['child'][$namespace][$tag]))
+ {
+ return $this->data['child'][$namespace][$tag];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ public function get_base($element = array())
+ {
+ return $this->item->get_base($element);
+ }
+
+ public function sanitize($data, $type, $base = '')
+ {
+ return $this->item->sanitize($data, $type, $base);
+ }
+
+ public function get_item()
+ {
+ return $this->item;
+ }
+
+ public function get_title()
+ {
+ if ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'title'))
+ {
+ return $this->sanitize($return[0]['data'], $this->registry->call('Misc', 'atom_10_construct_type', array($return[0]['attribs'])), $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'title'))
+ {
+ return $this->sanitize($return[0]['data'], $this->registry->call('Misc', 'atom_03_construct_type', array($return[0]['attribs'])), $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'title'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'title'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'title'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_11, 'title'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_10, 'title'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ public function get_category($key = 0)
+ {
+ $categories = $this->get_categories();
+ if (isset($categories[$key]))
+ {
+ return $categories[$key];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ public function get_categories()
+ {
+ $categories = array();
+
+ foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'category') as $category)
+ {
+ $term = null;
+ $scheme = null;
+ $label = null;
+ if (isset($category['attribs']['']['term']))
+ {
+ $term = $this->sanitize($category['attribs']['']['term'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($category['attribs']['']['scheme']))
+ {
+ $scheme = $this->sanitize($category['attribs']['']['scheme'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($category['attribs']['']['label']))
+ {
+ $label = $this->sanitize($category['attribs']['']['label'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ $categories[] = $this->registry->create('Category', array($term, $scheme, $label));
+ }
+ foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'category') as $category)
+ {
+ // This is really the label, but keep this as the term also for BC.
+ // Label will also work on retrieving because that falls back to term.
+ $term = $this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ if (isset($category['attribs']['']['domain']))
+ {
+ $scheme = $this->sanitize($category['attribs']['']['domain'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ $scheme = null;
+ }
+ $categories[] = $this->registry->create('Category', array($term, $scheme, null));
+ }
+ foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_11, 'subject') as $category)
+ {
+ $categories[] = $this->registry->create('Category', array($this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null));
+ }
+ foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_10, 'subject') as $category)
+ {
+ $categories[] = $this->registry->create('Category', array($this->sanitize($category['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null));
+ }
+
+ if (!empty($categories))
+ {
+ return array_unique($categories);
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ public function get_author($key = 0)
+ {
+ $authors = $this->get_authors();
+ if (isset($authors[$key]))
+ {
+ return $authors[$key];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ public function get_authors()
+ {
+ $authors = array();
+ foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'author') as $author)
+ {
+ $name = null;
+ $uri = null;
+ $email = null;
+ if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data']))
+ {
+ $name = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data']))
+ {
+ $uri = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]));
+ }
+ if (isset($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data']))
+ {
+ $email = $this->sanitize($author['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if ($name !== null || $email !== null || $uri !== null)
+ {
+ $authors[] = $this->registry->create('Author', array($name, $uri, $email));
+ }
+ }
+ if ($author = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'author'))
+ {
+ $name = null;
+ $url = null;
+ $email = null;
+ if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data']))
+ {
+ $name = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data']))
+ {
+ $url = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]));
+ }
+ if (isset($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data']))
+ {
+ $email = $this->sanitize($author[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if ($name !== null || $email !== null || $url !== null)
+ {
+ $authors[] = $this->registry->create('Author', array($name, $url, $email));
+ }
+ }
+ foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_11, 'creator') as $author)
+ {
+ $authors[] = $this->registry->create('Author', array($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null));
+ }
+ foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_10, 'creator') as $author)
+ {
+ $authors[] = $this->registry->create('Author', array($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null));
+ }
+ foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'author') as $author)
+ {
+ $authors[] = $this->registry->create('Author', array($this->sanitize($author['data'], SIMPLEPIE_CONSTRUCT_TEXT), null, null));
+ }
+
+ if (!empty($authors))
+ {
+ return array_unique($authors);
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ public function get_contributor($key = 0)
+ {
+ $contributors = $this->get_contributors();
+ if (isset($contributors[$key]))
+ {
+ return $contributors[$key];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ public function get_contributors()
+ {
+ $contributors = array();
+ foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'contributor') as $contributor)
+ {
+ $name = null;
+ $uri = null;
+ $email = null;
+ if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data']))
+ {
+ $name = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data']))
+ {
+ $uri = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]));
+ }
+ if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data']))
+ {
+ $email = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if ($name !== null || $email !== null || $uri !== null)
+ {
+ $contributors[] = $this->registry->create('Author', array($name, $uri, $email));
+ }
+ }
+ foreach ((array) $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'contributor') as $contributor)
+ {
+ $name = null;
+ $url = null;
+ $email = null;
+ if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data']))
+ {
+ $name = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['name'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data']))
+ {
+ $url = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['url'][0]));
+ }
+ if (isset($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data']))
+ {
+ $email = $this->sanitize($contributor['child'][SIMPLEPIE_NAMESPACE_ATOM_03]['email'][0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ if ($name !== null || $email !== null || $url !== null)
+ {
+ $contributors[] = $this->registry->create('Author', array($name, $url, $email));
+ }
+ }
+
+ if (!empty($contributors))
+ {
+ return array_unique($contributors);
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ public function get_link($key = 0, $rel = 'alternate')
+ {
+ $links = $this->get_links($rel);
+ if (isset($links[$key]))
+ {
+ return $links[$key];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Added for parity between the parent-level and the item/entry-level.
+ */
+ public function get_permalink()
+ {
+ return $this->get_link(0);
+ }
+
+ public function get_links($rel = 'alternate')
+ {
+ if (!isset($this->data['links']))
+ {
+ $this->data['links'] = array();
+ if ($links = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'link'))
+ {
+ foreach ($links as $link)
+ {
+ if (isset($link['attribs']['']['href']))
+ {
+ $link_rel = (isset($link['attribs']['']['rel'])) ? $link['attribs']['']['rel'] : 'alternate';
+ $this->data['links'][$link_rel][] = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link));
+ }
+ }
+ }
+ if ($links = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'link'))
+ {
+ foreach ($links as $link)
+ {
+ if (isset($link['attribs']['']['href']))
+ {
+ $link_rel = (isset($link['attribs']['']['rel'])) ? $link['attribs']['']['rel'] : 'alternate';
+ $this->data['links'][$link_rel][] = $this->sanitize($link['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($link));
+
+ }
+ }
+ }
+ if ($links = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'link'))
+ {
+ $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0]));
+ }
+ if ($links = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'link'))
+ {
+ $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0]));
+ }
+ if ($links = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'link'))
+ {
+ $this->data['links']['alternate'][] = $this->sanitize($links[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($links[0]));
+ }
+
+ $keys = array_keys($this->data['links']);
+ foreach ($keys as $key)
+ {
+ if ($this->registry->call('Misc', 'is_isegment_nz_nc', array($key)))
+ {
+ if (isset($this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key]))
+ {
+ $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key] = array_merge($this->data['links'][$key], $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key]);
+ $this->data['links'][$key] =& $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key];
+ }
+ else
+ {
+ $this->data['links'][SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY . $key] =& $this->data['links'][$key];
+ }
+ }
+ elseif (substr($key, 0, 41) === SIMPLEPIE_IANA_LINK_RELATIONS_REGISTRY)
+ {
+ $this->data['links'][substr($key, 41)] =& $this->data['links'][$key];
+ }
+ $this->data['links'][$key] = array_unique($this->data['links'][$key]);
+ }
+ }
+
+ if (isset($this->data['links'][$rel]))
+ {
+ return $this->data['links'][$rel];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ public function get_description()
+ {
+ if ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'subtitle'))
+ {
+ return $this->sanitize($return[0]['data'], $this->registry->call('Misc', 'atom_10_construct_type', array($return[0]['attribs'])), $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'tagline'))
+ {
+ return $this->sanitize($return[0]['data'], $this->registry->call('Misc', 'atom_03_construct_type', array($return[0]['attribs'])), $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_10, 'description'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_090, 'description'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'description'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_MAYBE_HTML, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_11, 'description'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_10, 'description'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'summary'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'subtitle'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_HTML, $this->get_base($return[0]));
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ public function get_copyright()
+ {
+ if ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'rights'))
+ {
+ return $this->sanitize($return[0]['data'], $this->registry->call('Misc', 'atom_10_construct_type', array($return[0]['attribs'])), $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_03, 'copyright'))
+ {
+ return $this->sanitize($return[0]['data'], $this->registry->call('Misc', 'atom_03_construct_type', array($return[0]['attribs'])), $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'copyright'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_11, 'rights'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_10, 'rights'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ public function get_language()
+ {
+ if ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_RSS_20, 'language'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_11, 'language'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_DC_10, 'language'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ elseif (isset($this->data['xml_lang']))
+ {
+ return $this->sanitize($this->data['xml_lang'], SIMPLEPIE_CONSTRUCT_TEXT);
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ public function get_latitude()
+ {
+ if ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'lat'))
+ {
+ return (float) $return[0]['data'];
+ }
+ elseif (($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_GEORSS, 'point')) && preg_match('/^((?:-)?[0-9]+(?:\.[0-9]+)) ((?:-)?[0-9]+(?:\.[0-9]+))$/', trim($return[0]['data']), $match))
+ {
+ return (float) $match[1];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ public function get_longitude()
+ {
+ if ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'long'))
+ {
+ return (float) $return[0]['data'];
+ }
+ elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_W3C_BASIC_GEO, 'lon'))
+ {
+ return (float) $return[0]['data'];
+ }
+ elseif (($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_GEORSS, 'point')) && preg_match('/^((?:-)?[0-9]+(?:\.[0-9]+)) ((?:-)?[0-9]+(?:\.[0-9]+))$/', trim($return[0]['data']), $match))
+ {
+ return (float) $match[2];
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ public function get_image_url()
+ {
+ if ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ITUNES, 'image'))
+ {
+ return $this->sanitize($return[0]['attribs']['']['href'], SIMPLEPIE_CONSTRUCT_IRI);
+ }
+ elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'logo'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0]));
+ }
+ elseif ($return = $this->get_source_tags(SIMPLEPIE_NAMESPACE_ATOM_10, 'icon'))
+ {
+ return $this->sanitize($return[0]['data'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($return[0]));
+ }
+ else
+ {
+ return null;
+ }
+ }
+}
+
diff --git a/vendor/simplepie/simplepie/library/SimplePie/XML/Declaration/Parser.php b/vendor/simplepie/simplepie/library/SimplePie/XML/Declaration/Parser.php
new file mode 100644
index 000000000..99e751672
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/XML/Declaration/Parser.php
@@ -0,0 +1,361 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+
+/**
+ * Parses the XML Declaration
+ *
+ * @package SimplePie
+ * @subpackage Parsing
+ */
+class SimplePie_XML_Declaration_Parser
+{
+ /**
+ * XML Version
+ *
+ * @access public
+ * @var string
+ */
+ var $version = '1.0';
+
+ /**
+ * Encoding
+ *
+ * @access public
+ * @var string
+ */
+ var $encoding = 'UTF-8';
+
+ /**
+ * Standalone
+ *
+ * @access public
+ * @var bool
+ */
+ var $standalone = false;
+
+ /**
+ * Current state of the state machine
+ *
+ * @access private
+ * @var string
+ */
+ var $state = 'before_version_name';
+
+ /**
+ * Input data
+ *
+ * @access private
+ * @var string
+ */
+ var $data = '';
+
+ /**
+ * Input data length (to avoid calling strlen() everytime this is needed)
+ *
+ * @access private
+ * @var int
+ */
+ var $data_length = 0;
+
+ /**
+ * Current position of the pointer
+ *
+ * @var int
+ * @access private
+ */
+ var $position = 0;
+
+ /**
+ * Create an instance of the class with the input data
+ *
+ * @access public
+ * @param string $data Input data
+ */
+ public function __construct($data)
+ {
+ $this->data = $data;
+ $this->data_length = strlen($this->data);
+ }
+
+ /**
+ * Parse the input data
+ *
+ * @access public
+ * @return bool true on success, false on failure
+ */
+ public function parse()
+ {
+ while ($this->state && $this->state !== 'emit' && $this->has_data())
+ {
+ $state = $this->state;
+ $this->$state();
+ }
+ $this->data = '';
+ if ($this->state === 'emit')
+ {
+ return true;
+ }
+ else
+ {
+ $this->version = '';
+ $this->encoding = '';
+ $this->standalone = '';
+ return false;
+ }
+ }
+
+ /**
+ * Check whether there is data beyond the pointer
+ *
+ * @access private
+ * @return bool true if there is further data, false if not
+ */
+ public function has_data()
+ {
+ return (bool) ($this->position < $this->data_length);
+ }
+
+ /**
+ * Advance past any whitespace
+ *
+ * @return int Number of whitespace characters passed
+ */
+ public function skip_whitespace()
+ {
+ $whitespace = strspn($this->data, "\x09\x0A\x0D\x20", $this->position);
+ $this->position += $whitespace;
+ return $whitespace;
+ }
+
+ /**
+ * Read value
+ */
+ public function get_value()
+ {
+ $quote = substr($this->data, $this->position, 1);
+ if ($quote === '"' || $quote === "'")
+ {
+ $this->position++;
+ $len = strcspn($this->data, $quote, $this->position);
+ if ($this->has_data())
+ {
+ $value = substr($this->data, $this->position, $len);
+ $this->position += $len + 1;
+ return $value;
+ }
+ }
+ return false;
+ }
+
+ public function before_version_name()
+ {
+ if ($this->skip_whitespace())
+ {
+ $this->state = 'version_name';
+ }
+ else
+ {
+ $this->state = false;
+ }
+ }
+
+ public function version_name()
+ {
+ if (substr($this->data, $this->position, 7) === 'version')
+ {
+ $this->position += 7;
+ $this->skip_whitespace();
+ $this->state = 'version_equals';
+ }
+ else
+ {
+ $this->state = false;
+ }
+ }
+
+ public function version_equals()
+ {
+ if (substr($this->data, $this->position, 1) === '=')
+ {
+ $this->position++;
+ $this->skip_whitespace();
+ $this->state = 'version_value';
+ }
+ else
+ {
+ $this->state = false;
+ }
+ }
+
+ public function version_value()
+ {
+ if ($this->version = $this->get_value())
+ {
+ $this->skip_whitespace();
+ if ($this->has_data())
+ {
+ $this->state = 'encoding_name';
+ }
+ else
+ {
+ $this->state = 'emit';
+ }
+ }
+ else
+ {
+ $this->state = false;
+ }
+ }
+
+ public function encoding_name()
+ {
+ if (substr($this->data, $this->position, 8) === 'encoding')
+ {
+ $this->position += 8;
+ $this->skip_whitespace();
+ $this->state = 'encoding_equals';
+ }
+ else
+ {
+ $this->state = 'standalone_name';
+ }
+ }
+
+ public function encoding_equals()
+ {
+ if (substr($this->data, $this->position, 1) === '=')
+ {
+ $this->position++;
+ $this->skip_whitespace();
+ $this->state = 'encoding_value';
+ }
+ else
+ {
+ $this->state = false;
+ }
+ }
+
+ public function encoding_value()
+ {
+ if ($this->encoding = $this->get_value())
+ {
+ $this->skip_whitespace();
+ if ($this->has_data())
+ {
+ $this->state = 'standalone_name';
+ }
+ else
+ {
+ $this->state = 'emit';
+ }
+ }
+ else
+ {
+ $this->state = false;
+ }
+ }
+
+ public function standalone_name()
+ {
+ if (substr($this->data, $this->position, 10) === 'standalone')
+ {
+ $this->position += 10;
+ $this->skip_whitespace();
+ $this->state = 'standalone_equals';
+ }
+ else
+ {
+ $this->state = false;
+ }
+ }
+
+ public function standalone_equals()
+ {
+ if (substr($this->data, $this->position, 1) === '=')
+ {
+ $this->position++;
+ $this->skip_whitespace();
+ $this->state = 'standalone_value';
+ }
+ else
+ {
+ $this->state = false;
+ }
+ }
+
+ public function standalone_value()
+ {
+ if ($standalone = $this->get_value())
+ {
+ switch ($standalone)
+ {
+ case 'yes':
+ $this->standalone = true;
+ break;
+
+ case 'no':
+ $this->standalone = false;
+ break;
+
+ default:
+ $this->state = false;
+ return;
+ }
+
+ $this->skip_whitespace();
+ if ($this->has_data())
+ {
+ $this->state = false;
+ }
+ else
+ {
+ $this->state = 'emit';
+ }
+ }
+ else
+ {
+ $this->state = false;
+ }
+ }
+}
diff --git a/vendor/simplepie/simplepie/library/SimplePie/gzdecode.php b/vendor/simplepie/simplepie/library/SimplePie/gzdecode.php
new file mode 100644
index 000000000..0e8bc8fc6
--- /dev/null
+++ b/vendor/simplepie/simplepie/library/SimplePie/gzdecode.php
@@ -0,0 +1,370 @@
+<?php
+/**
+ * SimplePie
+ *
+ * A PHP-Based RSS and Atom Feed Framework.
+ * Takes the hard work out of managing a complete RSS/Atom solution.
+ *
+ * Copyright (c) 2004-2016, Ryan Parman, Geoffrey Sneddon, Ryan McCue, and contributors
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * * Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * * Neither the name of the SimplePie Team nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS
+ * AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ * @package SimplePie
+ * @copyright 2004-2016 Ryan Parman, Geoffrey Sneddon, Ryan McCue
+ * @author Ryan Parman
+ * @author Geoffrey Sneddon
+ * @author Ryan McCue
+ * @link http://simplepie.org/ SimplePie
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ */
+
+
+/**
+ * Decode 'gzip' encoded HTTP data
+ *
+ * @package SimplePie
+ * @subpackage HTTP
+ * @link http://www.gzip.org/format.txt
+ */
+class SimplePie_gzdecode
+{
+ /**
+ * Compressed data
+ *
+ * @access private
+ * @var string
+ * @see gzdecode::$data
+ */
+ var $compressed_data;
+
+ /**
+ * Size of compressed data
+ *
+ * @access private
+ * @var int
+ */
+ var $compressed_size;
+
+ /**
+ * Minimum size of a valid gzip string
+ *
+ * @access private
+ * @var int
+ */
+ var $min_compressed_size = 18;
+
+ /**
+ * Current position of pointer
+ *
+ * @access private
+ * @var int
+ */
+ var $position = 0;
+
+ /**
+ * Flags (FLG)
+ *
+ * @access private
+ * @var int
+ */
+ var $flags;
+
+ /**
+ * Uncompressed data
+ *
+ * @access public
+ * @see gzdecode::$compressed_data
+ * @var string
+ */
+ var $data;
+
+ /**
+ * Modified time
+ *
+ * @access public
+ * @var int
+ */
+ var $MTIME;
+
+ /**
+ * Extra Flags
+ *
+ * @access public
+ * @var int
+ */
+ var $XFL;
+
+ /**
+ * Operating System
+ *
+ * @access public
+ * @var int
+ */
+ var $OS;
+
+ /**
+ * Subfield ID 1
+ *
+ * @access public
+ * @see gzdecode::$extra_field
+ * @see gzdecode::$SI2
+ * @var string
+ */
+ var $SI1;
+
+ /**
+ * Subfield ID 2
+ *
+ * @access public
+ * @see gzdecode::$extra_field
+ * @see gzdecode::$SI1
+ * @var string
+ */
+ var $SI2;
+
+ /**
+ * Extra field content
+ *
+ * @access public
+ * @see gzdecode::$SI1
+ * @see gzdecode::$SI2
+ * @var string
+ */
+ var $extra_field;
+
+ /**
+ * Original filename
+ *
+ * @access public
+ * @var string
+ */
+ var $filename;
+
+ /**
+ * Human readable comment
+ *
+ * @access public
+ * @var string
+ */
+ var $comment;
+
+ /**
+ * Don't allow anything to be set
+ *
+ * @param string $name
+ * @param mixed $value
+ */
+ public function __set($name, $value)
+ {
+ trigger_error("Cannot write property $name", E_USER_ERROR);
+ }
+
+ /**
+ * Set the compressed string and related properties
+ *
+ * @param string $data
+ */
+ public function __construct($data)
+ {
+ $this->compressed_data = $data;
+ $this->compressed_size = strlen($data);
+ }
+
+ /**
+ * Decode the GZIP stream
+ *
+ * @return bool Successfulness
+ */
+ public function parse()
+ {
+ if ($this->compressed_size >= $this->min_compressed_size)
+ {
+ // Check ID1, ID2, and CM
+ if (substr($this->compressed_data, 0, 3) !== "\x1F\x8B\x08")
+ {
+ return false;
+ }
+
+ // Get the FLG (FLaGs)
+ $this->flags = ord($this->compressed_data[3]);
+
+ // FLG bits above (1 << 4) are reserved
+ if ($this->flags > 0x1F)
+ {
+ return false;
+ }
+
+ // Advance the pointer after the above
+ $this->position += 4;
+
+ // MTIME
+ $mtime = substr($this->compressed_data, $this->position, 4);
+ // Reverse the string if we're on a big-endian arch because l is the only signed long and is machine endianness
+ if (current(unpack('S', "\x00\x01")) === 1)
+ {
+ $mtime = strrev($mtime);
+ }
+ $this->MTIME = current(unpack('l', $mtime));
+ $this->position += 4;
+
+ // Get the XFL (eXtra FLags)
+ $this->XFL = ord($this->compressed_data[$this->position++]);
+
+ // Get the OS (Operating System)
+ $this->OS = ord($this->compressed_data[$this->position++]);
+
+ // Parse the FEXTRA
+ if ($this->flags & 4)
+ {
+ // Read subfield IDs
+ $this->SI1 = $this->compressed_data[$this->position++];
+ $this->SI2 = $this->compressed_data[$this->position++];
+
+ // SI2 set to zero is reserved for future use
+ if ($this->SI2 === "\x00")
+ {
+ return false;
+ }
+
+ // Get the length of the extra field
+ $len = current(unpack('v', substr($this->compressed_data, $this->position, 2)));
+ $this->position += 2;
+
+ // Check the length of the string is still valid
+ $this->min_compressed_size += $len + 4;
+ if ($this->compressed_size >= $this->min_compressed_size)
+ {
+ // Set the extra field to the given data
+ $this->extra_field = substr($this->compressed_data, $this->position, $len);
+ $this->position += $len;
+ }
+ else
+ {
+ return false;
+ }
+ }
+
+ // Parse the FNAME
+ if ($this->flags & 8)
+ {
+ // Get the length of the filename
+ $len = strcspn($this->compressed_data, "\x00", $this->position);
+
+ // Check the length of the string is still valid
+ $this->min_compressed_size += $len + 1;
+ if ($this->compressed_size >= $this->min_compressed_size)
+ {
+ // Set the original filename to the given string
+ $this->filename = substr($this->compressed_data, $this->position, $len);
+ $this->position += $len + 1;
+ }
+ else
+ {
+ return false;
+ }
+ }
+
+ // Parse the FCOMMENT
+ if ($this->flags & 16)
+ {
+ // Get the length of the comment
+ $len = strcspn($this->compressed_data, "\x00", $this->position);
+
+ // Check the length of the string is still valid
+ $this->min_compressed_size += $len + 1;
+ if ($this->compressed_size >= $this->min_compressed_size)
+ {
+ // Set the original comment to the given string
+ $this->comment = substr($this->compressed_data, $this->position, $len);
+ $this->position += $len + 1;
+ }
+ else
+ {
+ return false;
+ }
+ }
+
+ // Parse the FHCRC
+ if ($this->flags & 2)
+ {
+ // Check the length of the string is still valid
+ $this->min_compressed_size += $len + 2;
+ if ($this->compressed_size >= $this->min_compressed_size)
+ {
+ // Read the CRC
+ $crc = current(unpack('v', substr($this->compressed_data, $this->position, 2)));
+
+ // Check the CRC matches
+ if ((crc32(substr($this->compressed_data, 0, $this->position)) & 0xFFFF) === $crc)
+ {
+ $this->position += 2;
+ }
+ else
+ {
+ return false;
+ }
+ }
+ else
+ {
+ return false;
+ }
+ }
+
+ // Decompress the actual data
+ if (($this->data = gzinflate(substr($this->compressed_data, $this->position, -8))) === false)
+ {
+ return false;
+ }
+ else
+ {
+ $this->position = $this->compressed_size - 8;
+ }
+
+ // Check CRC of data
+ $crc = current(unpack('V', substr($this->compressed_data, $this->position, 4)));
+ $this->position += 4;
+ /*if (extension_loaded('hash') && sprintf('%u', current(unpack('V', hash('crc32b', $this->data)))) !== sprintf('%u', $crc))
+ {
+ return false;
+ }*/
+
+ // Check ISIZE of data
+ $isize = current(unpack('V', substr($this->compressed_data, $this->position, 4)));
+ $this->position += 4;
+ if (sprintf('%u', strlen($this->data) & 0xFFFFFFFF) !== sprintf('%u', $isize))
+ {
+ return false;
+ }
+
+ // Wow, against all odds, we've actually got a valid gzip string
+ return true;
+ }
+ else
+ {
+ return false;
+ }
+ }
+}
diff --git a/view/css/bootstrap-red.css b/view/css/bootstrap-red.css
index f1ebb204e..2dfc9e07b 100644
--- a/view/css/bootstrap-red.css
+++ b/view/css/bootstrap-red.css
@@ -4,66 +4,83 @@
nav .badge {
position: absolute;
- top: 1px;
- left: 1px;
- font-size: 10px;
- line-height: 20px;
- padding: 0px 5px;
- height: 20px;
- min-width: 20px;
- border-radius: 10px;
+ font-size: 0.75rem;
}
-#navbar-collapse-1 i,
-.navbar-header i {
- font-size: 14px;
+nav .dropdown-menu {
+ min-width: 16rem;
}
-nav .navbar-header img {
- height: 49px;
- width: 49px;
- margin-top: 1px;
+@media screen and (min-width: 767px) {
+ nav .badge {
+ top: 0px;
+ left: 0px;
+ line-height: 0.75;
+ }
}
-/* nav overrides end */
+@media screen and (max-width: 767px) {
+ .navbar {
+ padding: .5rem 7px;
+ }
+
+ nav .badge {
+ top: 0.5rem;
+ left: 1.5rem;
+ }
+}
+
+.widget .badge {
+ font-size: 100%;
+}
+
+.nav-item.nav-item-hack {
+ height: 2.3rem;
+}
+
+.navbar-toggler-right {
+ padding: 0.2rem 0;
+}
-aside .nav-pills > li > a,
-.response-list .nav-pills > li > a {
- padding: 6px 10px;
+#navbar-collapse-1 i {
+ font-size: 1.0rem;
}
nav .dropdown-menu {
- margin-top: 0px;
max-height: 70vh;
overflow: auto;
}
-nav .navbar-collapse.in .dropdown-menu {
- max-height: none;
- overflow: none;
+#navbar-collapse-2 {
+ flex-basis: 100%;
+ max-height: 70vh;
}
-.wall-item-tools .dropdown-menu {
- min-width: auto;
+#navbar-collapse-2.show {
+ overflow: auto;
}
-.nav-tabs.nav-justified > li {
- white-space: nowrap;
+
+#navbar-collapse-2.collapsing .dropdown-header,
+#navbar-collapse-2.show .dropdown-header {
+ padding: 0.5rem 0.1rem;
}
-code {
- white-space: normal;
+.navbar-dark .navbar-toggler {
+ color: rgba(255,255,255,1);
}
+/* nav overrides end */
-.form-control {
- font-size: unset;
+.wall-item-tools .dropdown-menu {
+ min-width: auto;
}
-.panel-group {
- margin-bottom: 0px;
+label {
+ font-weight: bold;
}
-/* Bootstrap assumes that checkboxes are on the left of labels, while it's usually the opposite in Red */
-.field.checkbox input[type="checkbox"] { margin-left: 0px; }
-.field.checkbox label { padding-left: 0px; font-weight: 700}
+small,
+.small {
+ font-size: 0.75rem;
+}
diff --git a/view/css/cdav_addressbook.css b/view/css/cdav_addressbook.css
new file mode 100644
index 000000000..038358e43
--- /dev/null
+++ b/view/css/cdav_addressbook.css
@@ -0,0 +1,103 @@
+.vcard-header {
+ cursor: pointer;
+ padding: 7px 10px;
+ margin-bottom: 3px;
+}
+
+.vcard-header:hover,
+.vcard-header.active {
+ background-color: rgb(238,238,238);
+ cursor: pointer;
+}
+
+.vcard-header.active:hover {
+ cursor: initial;
+}
+
+.vcard-add-field {
+ margin-top: 8px;
+ display: none;
+}
+
+.vcard-cancel {
+ margin: 6px 10px;
+ height: 32px;
+ line-height: 32px;
+ color: #777;
+ font-size: 16px;
+
+ cursor: pointer;
+ display: none;
+ float: right;
+}
+
+.vcard-info {
+ display: none;
+}
+
+.vcard-nophoto {
+ display: inline-block;
+ width: 32px;
+ height: 32px;
+ border-radius: 4px;
+ border: 1px solid #ccc;
+ text-align: center;
+ font-size: 20px;
+ color: #fff;
+ background-color: #ddd;
+}
+
+.vcard-photo {
+ width: 32px;
+ height: 32px;
+ border-radius: 4px;
+ border: 1px solid #ccc;
+ text-align: center;
+}
+
+.vcard-fn-preview,
+input.vcard-fn {
+ font-size: 16px !important;
+ margin-left: 5px;
+}
+
+.vcard-email-preview,
+.vcard-tel-preview {
+ color: #999;
+}
+
+
+.vcard-fn,
+#create_form,
+#more_block {
+ display: none;
+}
+
+input.vcard-fn,
+.vcard-fn-create input,
+.vcard-org input,
+.vcard-title input,
+.vcard-tel input,
+.vcard-email input,
+.vcard-impp input,
+.vcard-url input,
+.vcard-adr input,
+.vcard-note input {
+ padding: 0px;
+ margin-left: 5px;
+ border-width: 0px 0px 1px 0px;
+ border-radius: 0px;
+ background-color: transparent;
+ min-width: 160px;
+}
+
+#template-form-vcard-org,
+#template-form-vcard-title,
+#template-form-vcard-tel,
+#template-form-vcard-email,
+#template-form-vcard-impp,
+#template-form-vcard-url,
+#template-form-vcard-adr,
+#template-form-vcard-note {
+ display: none;
+}
diff --git a/view/css/cdav_calendar.css b/view/css/cdav_calendar.css
new file mode 100644
index 000000000..d68278a63
--- /dev/null
+++ b/view/css/cdav_calendar.css
@@ -0,0 +1,22 @@
+/* fix borders */
+
+.fc th:first-child,
+.fc td:first-child {
+ border-left-width: 0px;
+}
+
+.fc th:last-child,
+.fc td:last-child {
+ border-right-width: 0px;
+ border-bottom-width: 0px;
+}
+
+.fc-unthemed th,
+.fc-unthemed td,
+.fc-unthemed thead,
+.fc-unthemed tbody,
+.fc-unthemed .fc-divider,
+.fc-unthemed .fc-row,
+.fc-unthemed .fc-popover {
+ border-color: #ccc !important;
+}
diff --git a/view/css/conversation.css b/view/css/conversation.css
index aec457302..d2736acaa 100644
--- a/view/css/conversation.css
+++ b/view/css/conversation.css
@@ -1,9 +1,10 @@
+
/* jot */
.jothidden input[type="text"] {
border: 0px;
margin: 0px;
- height: 39px;
+ height: 2.5rem;
width: 100%;
}
@@ -23,15 +24,15 @@
#jot-title-wrap input,
#jot-pagetitle-wrap input {
- padding: 10px;
+ padding: 0.5rem;
}
#profile-jot-text {
resize: none;
border-width: 0px;
- height: 39px;
- line-height: 19px;
- padding: 10px;
+ height: 2.5rem;
+ line-height: 1.5rem;
+ padding: 0.5rem;
width: 100%;
display: inherit;
}
@@ -60,53 +61,20 @@
}
#profile-jot-text-loading {
- float: left;
padding: 30px 0px 0px 12px;
}
#profile-jot-submit-wrapper {
border-top: 1px solid #ccc;
- padding: 10px;
-}
-
-#profile-jot-perms-end {
- height: 30px;
-}
-
-#profile-jot-wrapper {
- margin-bottom: 30px;
-}
-
-#profile-jot-plugin-wrapper {
- margin-top: 10px;
-}
-
-#profile-rotator-wrapper {
- float: left;
-}
-
-#profile-rotator {
- padding: 15px 0px 0px 15px;
}
/* conversation */
-.thread-wrapper.toplevel_item {
- margin-bottom: 20px;
-}
/* conv_item */
-.wall-item-head {
- padding: 10px 10px 0.5em 10px;
-}
-
-.wall-item-content {
- padding: 0.5em 10px;
-}
-
-.wall-item-tools {
- padding: 0.5em 10px 10px 10px;
+.wall-item-head-new {
+ border-top: 0.2rem solid #007bff;
}
.wall-item-info {
@@ -119,10 +87,6 @@
margin-left:10px;
}
-.lockview-panel {
- padding: 3px 20px;
-}
-
.wall-item-lock {
float: left;
}
@@ -137,6 +101,12 @@ a.wall-item-name-link {
text-overflow: ellipsis;
}
+.wall-item-ago,
+.wall-item-ago i {
+ font-size: 0.75rem;
+ line-height: 1;
+}
+
.wall-item-ago .fa-check {
cursor: pointer;
}
@@ -145,50 +115,28 @@ a.wall-item-name-link {
overflow: hidden;
}
-.wall-item-content h1,
-.wall-item-content h2 {
- font-size: 1.319em;
-}
-
-.wall-item-title h3,
-.wall-item-content h3,
-.wall-item-content h4 {
- font-size: 1.112em;
-}
-
.wall-item-content img {
max-width: 100%;
}
-.wall-item-title h3 {
+.wall-item-title.h3 {
font-weight: bold;
margin: 0px;
- white-space: nowrap;
- overflow: hidden;
- text-overflow: ellipsis;
+ word-wrap: break-word;
}
-.wall-item-title-end {
- clear: both;
+.wall-item-title.bg-primary a {
+ color: #fff;
}
.wall-item-body {
word-wrap: break-word;
}
-.body-tags {
- margin-top: 5px;
-}
-
.item-tool {
cursor: pointer;
}
-.like-rotator {
- float: right;
- margin: 16px;
-}
-
.item-select {
opacity: 0.1;
filter:alpha(opacity=10);
@@ -212,91 +160,54 @@ a.wall-item-name-link {
}
.ivoted {
- color: #337AB7;
+ color: #007bff;
}
.item-highlight {
- border-left: 3px solid #337AB7;
+ border-left: 0.2rem solid #007bff;
}
.item-highlight .wall-item-head,
.item-highlight .wall-item-content,
.item-highlight .wall-item-tools {
- padding-left: 7px;
+ padding-left: 0.3rem;
}
/* comment_item */
-.comment-edit-text-empty,
-.comment-edit-text-full {
+
+.comment-edit-text {
+ padding: 0.5rem;
width: 100%;
display: inherit;
-}
-
-.comment-edit-text-empty {
- padding: 0px 8px;
- line-height: 28px;
- height: 30px;
- overflow: hidden;
+ line-height: 1;
+ height: 2rem;
resize: none;
-
}
-.comment-edit-text-full {
- padding: 8px;
- height: 150px;
- overflow: auto;
+.comment-edit-text.expanded {
+ line-height: 1.25;
+ height: 7rem;
resize: vertical;
}
-.qcomment {
- border: 1px solid #EEE;
- padding: 3px;
- margin-top: 15px;
- margin-left: 25px;
- width: 125px;
- overflow-y: auto;
-}
-
-.qcomment option {
- width: 125px;
- overflow-x: hidden;
-}
-
-.qcomment {
- opacity: 0.3;
- filter:alpha(opacity=30);
-}
-
-.qcomment:hover {
- opacity: 1.0;
- filter:alpha(opacity=100);
-}
-
-.comment-tools {
- display: none;
- margin-top: 7px;
-}
-
+.comment-tools,
.comment-edit-preview {
display: none;
- margin-top: 7px;
}
/* disable link handling for unknown entries */
-.dropdown-menu > li > a.disabled {
+.dropdown-menu a.disabled {
pointer-events: none;
cursor: default;
}
.item-verified {
color: darkgreen;
- font-size: 1em !important;
}
.item-forged {
color: #FF0000;
- font-size: 1em !important;
}
/* event item */
@@ -354,6 +265,7 @@ code {
font-size: 1em;
padding: 1em 1.5em;
display: block;
+ white-space: pre-wrap;
}
code.inline-code {
diff --git a/view/css/default.css b/view/css/default.css
index a51461201..fc6da54f9 100644
--- a/view/css/default.css
+++ b/view/css/default.css
@@ -18,7 +18,7 @@ aside {
position: relative;
display: table-cell;
vertical-align: top;
- padding: 71px 7px 0px 7px;
+ padding: 4.5rem 7px 0px 7px;
}
section {
@@ -26,5 +26,5 @@ section {
width: 100%;
display: table-cell;
vertical-align: top;
- padding: 71px 7px 200px 7px;
+ padding: 4.5rem 7px 200px 7px;
}
diff --git a/view/css/mod_apps.css b/view/css/mod_apps.css
index 0a231bc84..5e6000fb4 100644
--- a/view/css/mod_apps.css
+++ b/view/css/mod_apps.css
@@ -1,8 +1,7 @@
.app-container {
float: left;
- width: 150px;
- height: 180px;
- padding: 20px;
+ width: 148px;
+ margin: 20px;
}
.app-name {
diff --git a/view/css/mod_chat.css b/view/css/mod_chat.css
index 57aecd557..c56091102 100644
--- a/view/css/mod_chat.css
+++ b/view/css/mod_chat.css
@@ -16,6 +16,10 @@
text-align: right;
}
+#chatrooms-index td:nth-child(3){
+ white-space: nowrap;
+}
+
#chatrooms-index th:nth-child(4),
#chatrooms-index td:nth-child(4){
padding: 7px 10px 7px 7px;
diff --git a/view/css/mod_events.css b/view/css/mod_events.css
index f0b5c0166..6fccf3f44 100644
--- a/view/css/mod_events.css
+++ b/view/css/mod_events.css
@@ -21,11 +21,6 @@
border-color: #ccc !important;
}
-#events-spinner .spinner {
- margin-top: 9px;
- margin-bottom: -9px;
-}
-
.bootstrap-tagsinput {
width: 100%;
padding: 6px 12px;
diff --git a/view/css/mod_help.css b/view/css/mod_help.css
index f59a40894..643885c99 100644
--- a/view/css/mod_help.css
+++ b/view/css/mod_help.css
@@ -11,14 +11,6 @@
padding-bottom: 0.3em;
}
-#doco-content h4 {
- text-decoration: underline;
-}
-
-#doco-content h5 {
- text-decoration: underline;
-}
-
#region_1 .widget ul ul {
list-style-type: none;
}
@@ -27,3 +19,11 @@
#doco-top-toc li {
padding: 3px 0px;
}
+
+#doco-side-toc li {
+ padding-left: 10px;
+}
+
+#doco-side-toc {
+ padding-top: 10px;
+} \ No newline at end of file
diff --git a/view/css/mod_mail.css b/view/css/mod_mail.css
index c1874edac..bcc7a8f94 100644
--- a/view/css/mod_mail.css
+++ b/view/css/mod_mail.css
@@ -1,34 +1,7 @@
-.mail-conv-sender {
- float: left;
- margin-right: 10px;
- margin-bottom: 10px;
-}
-
-.mail-conv-sender img{
- width: 32px;
- height: 32px;
-}
-
-.mail-conv-sender-name {
- font-weight: bold;
-}
-
-.mail-conv-body {
- margin-bottom: 10px;
-}
-
.mail-conv-body img {
max-width: 100%;
}
-#prvmail-rotator {
- margin: 15px;
-}
-
-#prvmail-text {
- height: 15.0em;
-}
-
-.mail-conv-outside-wrapper {
- margin-bottom: 20px;
+.prvmail-rotator-wrapper {
+ margin: 1rem;
}
diff --git a/view/css/mod_manage.css b/view/css/mod_manage.css
index 077b6b838..b08c90b62 100644
--- a/view/css/mod_manage.css
+++ b/view/css/mod_manage.css
@@ -4,10 +4,6 @@
text-decoration: none;
}
-.new-notification {
- color: #c60032;
-}
-
.channel-photo-wrapper {
display: table-cell;
table-layout: fixed;
@@ -24,11 +20,3 @@
vertical-align: top;
padding-left: 10px;
}
-
-.selected-channel {
- color: green;
-}
-
-#all-channels-end {
- margin-bottom: 20px;
-}
diff --git a/view/css/mod_setup.css b/view/css/mod_setup.css
deleted file mode 100644
index ee725d055..000000000
--- a/view/css/mod_setup.css
+++ /dev/null
@@ -1,34 +0,0 @@
-#install-dbhost-label,
-#install-dbuser-label,
-#install-dbpass-label,
-#install-dbdata-label,
-#install-tz-desc {
- float: left;
- width: 250px;
- margin-top: 10px;
- margin-bottom: 10px;
-
-}
-
-#install-dbhost,
-#install-dbuser,
-#install-dbpass,
-#install-dbdata {
- float: left;
- width: 200px;
- margin-left: 20px;
-}
-
-#install-dbhost-end,
-#install-dbuser-end,
-#install-dbpass-end,
-#install-dbdata-end,
-#install-tz-end {
- clear: both;
-}
-
-#install-form select#timezone_select {
- float: left;
- margin-top: 18px;
- margin-left: 20px;
-}
diff --git a/view/css/mod_webpages.css b/view/css/mod_webpages.css
index 805d95dc2..f665800f1 100644
--- a/view/css/mod_webpages.css
+++ b/view/css/mod_webpages.css
@@ -6,27 +6,31 @@
width: 100%;
}
-#webpage-list-table th:nth-child(1){
+#webpage-list-table th:nth-child(1) {
padding: 7px 3px 7px 10px;
white-space: nowrap;
}
-#webpage-list-table td:nth-child(1){
+#webpage-list-table td:nth-child(1) {
padding: 7px 3px 7px 10px;
}
-#webpage-list-table th:nth-child(2){
+#webpage-list-table th:nth-child(2) {
+ white-space: nowrap;
+}
+
+#webpage-list-table td:nth-child(3) {
white-space: nowrap;
}
#webpage-list-table th:nth-child(7),
-#webpage-list-table td:nth-child(7){
+#webpage-list-table td:nth-child(7) {
padding: 7px 3px;
white-space: nowrap;
}
#webpage-list-table th:nth-child(8),
-#webpage-list-table td:nth-child(8){
+#webpage-list-table td:nth-child(8) {
padding: 7px 10px 7px 7px;
white-space: nowrap;
}
@@ -192,4 +196,4 @@
-ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)";
filter: alpha(opacity=100);
opacity: 1;
-} \ No newline at end of file
+}
diff --git a/view/css/mod_wiki.css b/view/css/mod_wiki.css
index 83f17c820..4e4c71e1d 100644
--- a/view/css/mod_wiki.css
+++ b/view/css/mod_wiki.css
@@ -33,22 +33,18 @@
width: 100%;
}
+td i {
+ padding: 7px 5px;
+ cursor: pointer;
+}
+
#wikis-index th:nth-child(1),
#wikis-index td:nth-child(1){
padding: 7px 3px 7px 10px;
}
-#wikis-index th:nth-child(3),
-#wikis-index td:nth-child(3){
- padding: 7px 10px 7px 7px;
-}
-
-#wikis-index th:nth-child(4),
-#wikis-index td:nth-child(4){
- padding: 7px 10px 7px 7px;
-}
-
-.wikis-index-tool {
- padding: 7px 10px;
+#wikis-index th:nth-last-child(1),
+#wikis-index td:nth-last-child(1){
+ padding-right: 10px;
}
diff --git a/view/css/navbar_tucson.css b/view/css/navbar_tucson.css
new file mode 100644
index 000000000..79f95fe63
--- /dev/null
+++ b/view/css/navbar_tucson.css
@@ -0,0 +1,3 @@
+#notifications {
+ display: none;
+}
diff --git a/view/css/widgets.css b/view/css/widgets.css
index 9b97d8bf7..cea3a3820 100644
--- a/view/css/widgets.css
+++ b/view/css/widgets.css
@@ -1,17 +1,15 @@
.widget {
- margin-bottom: 10px;
- padding: 10px;
+ margin-bottom: 1rem;
+ padding: 0.5rem;
}
.widget h3 {
margin-top: 0px;
}
-.widget-input {
- width: 100%;
- border-top-right-radius: 0px;
- border-bottom-right-radius: 0px;
- border-right: 0px;
+.widget .active .wall-item-ago,
+.widget .active .dropdown-sub-text {
+ color: #fff;
}
.tags {
@@ -20,34 +18,15 @@
.widget-nav-pills-icons {
opacity: 0;
- padding: 6px 10px;
float: right;
- position: relative;
- z-index:1;
}
-
.widget-nav-pills-checkbox {
- padding: 6px 10px;
+ padding: 0.6rem 1.4rem;
float: right;
- position: relative;
- z-index:1;
cursor: pointer;
}
-i.widget-nav-pills-icons,
-i.widget-nav-pills-checkbox {
- margin-top: 2px;
-}
-
-.widget-nav-pills-icons:hover + a {
- background-color: #eee;
-}
-
-.widget-nav-pills-checkbox:hover + a {
- background-color: #eee;
-}
-
li:hover .widget-nav-pills-icons {
opacity: 1;
}
@@ -78,7 +57,13 @@ li:hover .widget-nav-pills-icons {
/* affinity slider */
#main-slider {
- margin: 10px 7px 45px 7px;
+ margin: 10px 7px 4rem 7px;
+}
+
+@media screen and (max-width: 767px) {
+ #main-slider {
+ margin: 4rem 7px 4rem 7px;
+ }
}
/* posted date */
@@ -150,16 +135,6 @@ li:hover .group-edit-icon {
width: 250px;
}
-/* events tools */
-
-#event-upload-form {
- margin-top: 10px;
-}
-
-#event-upload-choose {
- width: 100%;
-}
-
/* cover photo */
#cover-photo {
@@ -174,20 +149,22 @@ li:hover .group-edit-icon {
bottom: 0px;
left: 0px;
width: 100%;
- padding: 15px;
+ padding: 1rem;
+}
+
+#cover-photo-caption h1,
+#cover-photo-caption h3 {
color: #fff;
font-weight: bold;
- text-shadow: 1px 1px 3px rgba(0,0,0,.7);
+ text-shadow: 1px 1px 3px rgba(0,0,0,0.5);
}
-.cover-photo-title {
- font-size: 30px;
+a.wikilist {
+ z-index: 1;
}
-.cover-photo-subtitle {
- font-size: 20px;
-}
+/* mail list */
-a.wikilist {
- z-index: 1;
+.active .conv-participants {
+ color: #fff;
}
diff --git a/view/de/hmessages.po b/view/de/hmessages.po
index fbdb33166..85fb8ca4e 100644
--- a/view/de/hmessages.po
+++ b/view/de/hmessages.po
@@ -8,25 +8,25 @@
# Tobias Diekershoff <tobias.diekershoff@gmx.net>, 2013
# do.t <tobias@tonstrom.de>, 2014
# Einer von Vielen <tom@jfellow.net>, 2013
-# Ettore Atalan <atalanttore@googlemail.com>, 2015-2016
+# Ettore Atalan <atalanttore@googlemail.com>, 2015-2017
# Frank Dieckmann <frank@lumina-verte.org>, 2013
# Harald Klimach <harald@klimachs.de>, 2016
# JooBee <d13@raclan.de>, 2014
# Kai <kai@proppower.de>, 2015
-# Oliver <post@toktan.org>, 2015-2016
-# Phellmes <forum@suschka.de>, 2014,2016
+# Oliver <post@toktan.org>, 2015-2017
+# Phellmes <forum@suschka.de>, 2014,2016-2017
# sasiflo <transiflex@sasiflo.de>, 2014
# Steff <steff@digitalesecho.de>, 2015-2016
# Tobias Diekershoff <tobias.diekershoff@gmx.net>, 2016
-# Tobias Diekershoff <tobias.diekershoff@gmx.net>, 2016
+# Tobias Diekershoff <tobias.diekershoff@gmx.net>, 2016-2017
# zottel <transifex@zottel.net>, 2015
# sasiflo <transiflex@sasiflo.de>, 2015
msgid ""
msgstr ""
"Project-Id-Version: Redmatrix\n"
"Report-Msgid-Bugs-To: \n"
-"POT-Creation-Date: 2016-12-09 00:05-0800\n"
-"PO-Revision-Date: 2016-12-10 12:27+0000\n"
+"POT-Creation-Date: 2017-10-19 12:01+0200\n"
+"PO-Revision-Date: 2017-10-21 11:21+0000\n"
"Last-Translator: Phellmes <forum@suschka.de>\n"
"Language-Team: German (http://www.transifex.com/Friendica/red-matrix/language/de/)\n"
"MIME-Version: 1.0\n"
@@ -35,1672 +35,2100 @@ msgstr ""
"Language: de\n"
"Plural-Forms: nplurals=2; plural=(n != 1);\n"
-#: ../../Zotlabs/Access/PermissionRoles.php:227
-#: ../../include/permissions.php:945
+#: ../../Zotlabs/Access/Permissions.php:53
+msgid "Can view my channel stream and posts"
+msgstr "Kann meinen Kanal-Stream und meine Beiträge sehen"
+
+#: ../../Zotlabs/Access/Permissions.php:54
+msgid "Can send me their channel stream and posts"
+msgstr "Kann mir die Beiträge aus seinem/ihrem Kanal schicken"
+
+#: ../../Zotlabs/Access/Permissions.php:55
+msgid "Can view my default channel profile"
+msgstr "Kann mein Standardprofil sehen"
+
+#: ../../Zotlabs/Access/Permissions.php:56
+msgid "Can view my connections"
+msgstr "Kann meine Verbindungen sehen"
+
+#: ../../Zotlabs/Access/Permissions.php:57
+msgid "Can view my file storage and photos"
+msgstr "Kann meine Datei- und Bilderordner sehen"
+
+#: ../../Zotlabs/Access/Permissions.php:58
+msgid "Can upload/modify my file storage and photos"
+msgstr "Kann in meine Datei- und Bilderordner hochladen/ändern"
+
+#: ../../Zotlabs/Access/Permissions.php:59
+msgid "Can view my channel webpages"
+msgstr "Kann die Webseiten meines Kanals sehen"
+
+#: ../../Zotlabs/Access/Permissions.php:60
+msgid "Can view my wiki pages"
+msgstr "Kann meine Wiki-Seiten sehen"
+
+#: ../../Zotlabs/Access/Permissions.php:61
+msgid "Can create/edit my channel webpages"
+msgstr "Kann Webseiten in meinem Kanal erstellen/ändern"
+
+#: ../../Zotlabs/Access/Permissions.php:62
+msgid "Can write to my wiki pages"
+msgstr "Kann meine Wiki-Seiten bearbeiten"
+
+#: ../../Zotlabs/Access/Permissions.php:63
+msgid "Can post on my channel (wall) page"
+msgstr "Kann auf meiner Kanal-Seite (\"wall\") Beiträge veröffentlichen"
+
+#: ../../Zotlabs/Access/Permissions.php:64
+msgid "Can comment on or like my posts"
+msgstr "Darf meine Beiträge kommentieren und mögen/nicht mögen"
+
+#: ../../Zotlabs/Access/Permissions.php:65
+msgid "Can send me private mail messages"
+msgstr "Kann mir private Nachrichten schicken"
+
+#: ../../Zotlabs/Access/Permissions.php:66
+msgid "Can like/dislike profiles and profile things"
+msgstr "Kann Profile und Profilsachen mögen/nicht mögen"
+
+#: ../../Zotlabs/Access/Permissions.php:67
+msgid "Can forward to all my channel connections via @+ mentions in posts"
+msgstr "Kann an alle meine Verbindungen via @-Erwähnungen Nachrichten weiterleiten"
+
+#: ../../Zotlabs/Access/Permissions.php:68
+msgid "Can chat with me"
+msgstr "Kann mit mir chatten"
+
+#: ../../Zotlabs/Access/Permissions.php:69
+msgid "Can source my public posts in derived channels"
+msgstr "Kann meine öffentlichen Beiträge als Quellen für Kanäle verwenden"
+
+#: ../../Zotlabs/Access/Permissions.php:70
+msgid "Can administer my channel"
+msgstr "Kann meinen Kanal administrieren"
+
+#: ../../Zotlabs/Access/PermissionRoles.php:248
msgid "Social Networking"
msgstr "Soziales Netzwerk"
-#: ../../Zotlabs/Access/PermissionRoles.php:228
-#: ../../include/permissions.php:945
+#: ../../Zotlabs/Access/PermissionRoles.php:249
msgid "Social - Mostly Public"
msgstr "Soziales Netzwerk - Weitgehend öffentlich"
-#: ../../Zotlabs/Access/PermissionRoles.php:229
-#: ../../include/permissions.php:945
+#: ../../Zotlabs/Access/PermissionRoles.php:250
msgid "Social - Restricted"
msgstr "Soziales Netzwerk - Beschränkt"
-#: ../../Zotlabs/Access/PermissionRoles.php:230
-#: ../../include/permissions.php:945
+#: ../../Zotlabs/Access/PermissionRoles.php:251
msgid "Social - Private"
msgstr "Soziales Netzwerk - Privat"
-#: ../../Zotlabs/Access/PermissionRoles.php:233
-#: ../../include/permissions.php:946
+#: ../../Zotlabs/Access/PermissionRoles.php:254
msgid "Community Forum"
msgstr "Forum"
-#: ../../Zotlabs/Access/PermissionRoles.php:234
-#: ../../include/permissions.php:946
+#: ../../Zotlabs/Access/PermissionRoles.php:255
msgid "Forum - Mostly Public"
msgstr "Forum - Weitgehend öffentlich"
-#: ../../Zotlabs/Access/PermissionRoles.php:235
-#: ../../include/permissions.php:946
+#: ../../Zotlabs/Access/PermissionRoles.php:256
msgid "Forum - Restricted"
msgstr "Forum - Beschränkt"
-#: ../../Zotlabs/Access/PermissionRoles.php:236
-#: ../../include/permissions.php:946
+#: ../../Zotlabs/Access/PermissionRoles.php:257
msgid "Forum - Private"
msgstr "Forum - Privat"
-#: ../../Zotlabs/Access/PermissionRoles.php:239
-#: ../../include/permissions.php:947
+#: ../../Zotlabs/Access/PermissionRoles.php:260
msgid "Feed Republish"
msgstr "Teilen von Feeds"
-#: ../../Zotlabs/Access/PermissionRoles.php:240
-#: ../../include/permissions.php:947
+#: ../../Zotlabs/Access/PermissionRoles.php:261
msgid "Feed - Mostly Public"
msgstr "Feeds - Weitgehend öffentlich"
-#: ../../Zotlabs/Access/PermissionRoles.php:241
-#: ../../include/permissions.php:947
+#: ../../Zotlabs/Access/PermissionRoles.php:262
msgid "Feed - Restricted"
msgstr "Feeds - Beschränkt"
-#: ../../Zotlabs/Access/PermissionRoles.php:244
-#: ../../include/permissions.php:948
+#: ../../Zotlabs/Access/PermissionRoles.php:265
msgid "Special Purpose"
msgstr "Für besondere Zwecke"
-#: ../../Zotlabs/Access/PermissionRoles.php:245
-#: ../../include/permissions.php:948
+#: ../../Zotlabs/Access/PermissionRoles.php:266
msgid "Special - Celebrity/Soapbox"
msgstr "Speziell - Mitteilungs-Kanal (keine Kommentare)"
-#: ../../Zotlabs/Access/PermissionRoles.php:246
-#: ../../include/permissions.php:948
+#: ../../Zotlabs/Access/PermissionRoles.php:267
msgid "Special - Group Repository"
msgstr "Speziell - Gruppenarchiv"
-#: ../../Zotlabs/Access/PermissionRoles.php:249
-#: ../../Zotlabs/Module/Register.php:213
-#: ../../Zotlabs/Module/New_channel.php:132
-#: ../../Zotlabs/Module/Settings/Channel.php:445
-#: ../../extend/addon/addon/cdav/cdav.php:277
-#: ../../extend/addon/addon/cdav/cdav.php:284
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1148
-#: ../../include/selectors.php:49 ../../include/selectors.php:66
-#: ../../include/selectors.php:104 ../../include/selectors.php:140
-#: ../../include/permissions.php:949
+#: ../../Zotlabs/Access/PermissionRoles.php:270
+#: ../../Zotlabs/Module/Cdav.php:1182 ../../Zotlabs/Module/New_channel.php:132
+#: ../../Zotlabs/Module/Settings/Channel.php:467
+#: ../../Zotlabs/Module/Connedit.php:936 ../../Zotlabs/Module/Profiles.php:798
+#: ../../Zotlabs/Module/Register.php:213 ../../include/selectors.php:49
+#: ../../include/selectors.php:66 ../../include/selectors.php:104
+#: ../../include/selectors.php:140 ../../include/event.php:1297
+#: ../../include/event.php:1304 ../../include/connections.php:689
+#: ../../include/connections.php:696
msgid "Other"
msgstr "Andere"
-#: ../../Zotlabs/Access/PermissionRoles.php:250
-#: ../../include/permissions.php:949
+#: ../../Zotlabs/Access/PermissionRoles.php:271
msgid "Custom/Expert Mode"
msgstr "Benutzerdefiniert/Expertenmodus"
-#: ../../Zotlabs/Access/Permissions.php:46
-msgid "Can view my channel stream and posts"
-msgstr "Kann meinen Kanal-Stream und meine Beiträge sehen"
+#: ../../Zotlabs/Module/Blocks.php:33 ../../Zotlabs/Module/Editlayout.php:31
+#: ../../Zotlabs/Module/Connect.php:17
+#: ../../Zotlabs/Module/Achievements.php:15 ../../Zotlabs/Module/Hcard.php:12
+#: ../../Zotlabs/Module/Editblock.php:31 ../../Zotlabs/Module/Profile.php:20
+#: ../../Zotlabs/Module/Layouts.php:31 ../../Zotlabs/Module/Editwebpage.php:32
+#: ../../Zotlabs/Module/Cards.php:29 ../../Zotlabs/Module/Webpages.php:33
+#: ../../Zotlabs/Module/Filestorage.php:51 ../../include/channel.php:1163
+msgid "Requested profile is not available."
+msgstr "Das angefragte Profil ist nicht verfügbar."
-#: ../../Zotlabs/Access/Permissions.php:47 ../../include/permissions.php:42
-msgid "Can send me their channel stream and posts"
-msgstr "Kann mir die Beiträge aus seinem/ihrem Kanal schicken"
+#: ../../Zotlabs/Module/Blocks.php:73 ../../Zotlabs/Module/Blocks.php:80
+#: ../../Zotlabs/Module/Invite.php:17 ../../Zotlabs/Module/Invite.php:94
+#: ../../Zotlabs/Module/Editlayout.php:67
+#: ../../Zotlabs/Module/Editlayout.php:90 ../../Zotlabs/Module/Channel.php:110
+#: ../../Zotlabs/Module/Channel.php:248 ../../Zotlabs/Module/Channel.php:288
+#: ../../Zotlabs/Module/Settings.php:59 ../../Zotlabs/Module/Locs.php:87
+#: ../../Zotlabs/Module/Mitem.php:115 ../../Zotlabs/Module/Events.php:271
+#: ../../Zotlabs/Module/Appman.php:82 ../../Zotlabs/Module/Regmod.php:21
+#: ../../Zotlabs/Module/New_channel.php:77
+#: ../../Zotlabs/Module/New_channel.php:104
+#: ../../Zotlabs/Module/Sharedwithme.php:16 ../../Zotlabs/Module/Setup.php:209
+#: ../../Zotlabs/Module/Moderate.php:13
+#: ../../Zotlabs/Module/Achievements.php:34 ../../Zotlabs/Module/Thing.php:275
+#: ../../Zotlabs/Module/Thing.php:295 ../../Zotlabs/Module/Thing.php:336
+#: ../../Zotlabs/Module/Api.php:24 ../../Zotlabs/Module/Editblock.php:67
+#: ../../Zotlabs/Module/Profile.php:85 ../../Zotlabs/Module/Profile.php:101
+#: ../../Zotlabs/Module/Mood.php:116 ../../Zotlabs/Module/Connections.php:29
+#: ../../Zotlabs/Module/Viewsrc.php:19 ../../Zotlabs/Module/Bookmarks.php:64
+#: ../../Zotlabs/Module/Photos.php:69 ../../Zotlabs/Module/Wiki.php:50
+#: ../../Zotlabs/Module/Wiki.php:273 ../../Zotlabs/Module/Wiki.php:388
+#: ../../Zotlabs/Module/Pdledit.php:29 ../../Zotlabs/Module/Poke.php:149
+#: ../../Zotlabs/Module/Profile_photo.php:288
+#: ../../Zotlabs/Module/Profile_photo.php:301
+#: ../../Zotlabs/Module/Authtest.php:16 ../../Zotlabs/Module/Item.php:223
+#: ../../Zotlabs/Module/Item.php:240 ../../Zotlabs/Module/Item.php:250
+#: ../../Zotlabs/Module/Item.php:1102 ../../Zotlabs/Module/Page.php:34
+#: ../../Zotlabs/Module/Page.php:125 ../../Zotlabs/Module/Connedit.php:389
+#: ../../Zotlabs/Module/Chat.php:100 ../../Zotlabs/Module/Chat.php:105
+#: ../../Zotlabs/Module/Menu.php:78 ../../Zotlabs/Module/Layouts.php:71
+#: ../../Zotlabs/Module/Layouts.php:78 ../../Zotlabs/Module/Layouts.php:89
+#: ../../Zotlabs/Module/Group.php:13 ../../Zotlabs/Module/Profiles.php:198
+#: ../../Zotlabs/Module/Profiles.php:635
+#: ../../Zotlabs/Module/Editwebpage.php:68
+#: ../../Zotlabs/Module/Editwebpage.php:89
+#: ../../Zotlabs/Module/Editwebpage.php:107
+#: ../../Zotlabs/Module/Editwebpage.php:121 ../../Zotlabs/Module/Manage.php:10
+#: ../../Zotlabs/Module/Cards.php:68 ../../Zotlabs/Module/Webpages.php:118
+#: ../../Zotlabs/Module/Block.php:24 ../../Zotlabs/Module/Block.php:74
+#: ../../Zotlabs/Module/Editpost.php:17 ../../Zotlabs/Module/Sources.php:74
+#: ../../Zotlabs/Module/Like.php:181 ../../Zotlabs/Module/Suggest.php:28
+#: ../../Zotlabs/Module/Message.php:18 ../../Zotlabs/Module/Mail.php:146
+#: ../../Zotlabs/Module/Register.php:77
+#: ../../Zotlabs/Module/Cover_photo.php:281
+#: ../../Zotlabs/Module/Cover_photo.php:294
+#: ../../Zotlabs/Module/Display.php:343 ../../Zotlabs/Module/Network.php:15
+#: ../../Zotlabs/Module/Filestorage.php:15
+#: ../../Zotlabs/Module/Filestorage.php:70
+#: ../../Zotlabs/Module/Filestorage.php:85
+#: ../../Zotlabs/Module/Filestorage.php:112 ../../Zotlabs/Module/Common.php:38
+#: ../../Zotlabs/Module/Viewconnections.php:28
+#: ../../Zotlabs/Module/Viewconnections.php:33
+#: ../../Zotlabs/Module/Service_limits.php:11
+#: ../../Zotlabs/Module/Rate.php:113 ../../Zotlabs/Module/Card_edit.php:51
+#: ../../Zotlabs/Module/Notifications.php:11
+#: ../../Zotlabs/Lib/Chatroom.php:137 ../../Zotlabs/Web/WebServer.php:169
+#: ../../addon/keepout/keepout.php:36 ../../addon/openid/Mod_Id.php:53
+#: ../../addon/gitwiki/Mod_Gitwiki.php:196
+#: ../../addon/gitwiki/Mod_Gitwiki.php:292 ../../addon/pumpio/pumpio.php:40
+#: ../../include/attach.php:144 ../../include/attach.php:191
+#: ../../include/attach.php:255 ../../include/attach.php:269
+#: ../../include/attach.php:276 ../../include/attach.php:344
+#: ../../include/attach.php:358 ../../include/attach.php:365
+#: ../../include/attach.php:443 ../../include/attach.php:924
+#: ../../include/attach.php:998 ../../include/attach.php:1163
+#: ../../include/items.php:3489 ../../include/photos.php:28
+msgid "Permission denied."
+msgstr "Berechtigung verweigert."
-#: ../../Zotlabs/Access/Permissions.php:48 ../../include/permissions.php:36
-msgid "Can view my default channel profile"
-msgstr "Kann mein Standardprofil sehen"
+#: ../../Zotlabs/Module/Blocks.php:97 ../../Zotlabs/Module/Blocks.php:155
+#: ../../Zotlabs/Module/Editblock.php:113
+msgid "Block Name"
+msgstr "Block-Name"
-#: ../../Zotlabs/Access/Permissions.php:49 ../../include/permissions.php:37
-msgid "Can view my connections"
-msgstr "Kann meine Verbindungen sehen"
+#: ../../Zotlabs/Module/Blocks.php:154 ../../include/text.php:2288
+msgid "Blocks"
+msgstr "Blöcke"
-#: ../../Zotlabs/Access/Permissions.php:50 ../../include/permissions.php:38
-msgid "Can view my file storage and photos"
-msgstr "Kann meine Datei- und Bilderordner sehen"
+#: ../../Zotlabs/Module/Blocks.php:156
+msgid "Block Title"
+msgstr "Titel des Blocks"
-#: ../../Zotlabs/Access/Permissions.php:51
-msgid "Can upload/modify my file storage and photos"
-msgstr "Kann in meine Datei- und Bilderordner hochladen/ändern"
+#: ../../Zotlabs/Module/Blocks.php:157 ../../Zotlabs/Module/Menu.php:114
+#: ../../Zotlabs/Module/Layouts.php:191 ../../Zotlabs/Module/Webpages.php:251
+msgid "Created"
+msgstr "Erstellt"
-#: ../../Zotlabs/Access/Permissions.php:52
-msgid "Can view my channel webpages"
-msgstr "Kann die Webseiten meines Kanals sehen"
+#: ../../Zotlabs/Module/Blocks.php:158 ../../Zotlabs/Module/Menu.php:115
+#: ../../Zotlabs/Module/Layouts.php:192 ../../Zotlabs/Module/Webpages.php:252
+msgid "Edited"
+msgstr "Geändert"
-#: ../../Zotlabs/Access/Permissions.php:53
-msgid "Can create/edit my channel webpages"
-msgstr "Kann Webseiten in meinem Kanal erstellen/ändern"
+#: ../../Zotlabs/Module/Blocks.php:159 ../../Zotlabs/Module/Cdav.php:1185
+#: ../../Zotlabs/Module/New_channel.php:147
+#: ../../Zotlabs/Module/Connedit.php:939 ../../Zotlabs/Module/Menu.php:118
+#: ../../Zotlabs/Module/Layouts.php:185 ../../Zotlabs/Module/Profiles.php:801
+#: ../../Zotlabs/Module/Cards.php:96 ../../Zotlabs/Module/Webpages.php:239
+#: ../../Zotlabs/Storage/Browser.php:229 ../../Zotlabs/Storage/Browser.php:335
+#: ../../Zotlabs/Widget/Cdav.php:127 ../../Zotlabs/Widget/Cdav.php:164
+msgid "Create"
+msgstr "Erstelle"
-#: ../../Zotlabs/Access/Permissions.php:54
-msgid "Can post on my channel (wall) page"
-msgstr "Kann auf meiner Kanal-Seite (\"wall\") Beiträge veröffentlichen"
+#: ../../Zotlabs/Module/Blocks.php:160 ../../Zotlabs/Module/Editlayout.php:114
+#: ../../Zotlabs/Module/Admin/Profs.php:154
+#: ../../Zotlabs/Module/Settings/Oauth.php:149
+#: ../../Zotlabs/Module/Thing.php:261 ../../Zotlabs/Module/Editblock.php:114
+#: ../../Zotlabs/Module/Connections.php:260
+#: ../../Zotlabs/Module/Connections.php:297
+#: ../../Zotlabs/Module/Connections.php:317 ../../Zotlabs/Module/Wiki.php:202
+#: ../../Zotlabs/Module/Wiki.php:346 ../../Zotlabs/Module/Menu.php:112
+#: ../../Zotlabs/Module/Layouts.php:193
+#: ../../Zotlabs/Module/Editwebpage.php:142
+#: ../../Zotlabs/Module/Webpages.php:240 ../../Zotlabs/Module/Editpost.php:85
+#: ../../Zotlabs/Module/Card_edit.php:99 ../../Zotlabs/Lib/Apps.php:399
+#: ../../Zotlabs/Lib/ThreadItem.php:111 ../../Zotlabs/Storage/Browser.php:239
+#: ../../Zotlabs/Widget/Cdav.php:125 ../../Zotlabs/Widget/Cdav.php:161
+#: ../../addon/gitwiki/Mod_Gitwiki.php:151
+#: ../../addon/gitwiki/Mod_Gitwiki.php:252 ../../include/channel.php:1262
+#: ../../include/channel.php:1266 ../../include/menu.php:113
+msgid "Edit"
+msgstr "Bearbeiten"
-#: ../../Zotlabs/Access/Permissions.php:55 ../../include/permissions.php:44
-msgid "Can comment on or like my posts"
-msgstr "Darf meine Beiträge kommentieren und mögen/nicht mögen"
+#: ../../Zotlabs/Module/Blocks.php:161 ../../Zotlabs/Module/Photos.php:1049
+#: ../../Zotlabs/Module/Layouts.php:194 ../../Zotlabs/Module/Webpages.php:241
+#: ../../Zotlabs/Widget/Cdav.php:123 ../../include/conversation.php:1346
+msgid "Share"
+msgstr "Teilen"
-#: ../../Zotlabs/Access/Permissions.php:56 ../../include/permissions.php:45
-msgid "Can send me private mail messages"
-msgstr "Kann mir private Nachrichten schicken"
+#: ../../Zotlabs/Module/Blocks.php:162 ../../Zotlabs/Module/Editlayout.php:138
+#: ../../Zotlabs/Module/Cdav.php:897 ../../Zotlabs/Module/Cdav.php:1187
+#: ../../Zotlabs/Module/Admin/Accounts.php:173
+#: ../../Zotlabs/Module/Admin/Channels.php:149
+#: ../../Zotlabs/Module/Admin/Profs.php:155
+#: ../../Zotlabs/Module/Settings/Oauth.php:150
+#: ../../Zotlabs/Module/Thing.php:262 ../../Zotlabs/Module/Editblock.php:139
+#: ../../Zotlabs/Module/Connections.php:268
+#: ../../Zotlabs/Module/Photos.php:1150 ../../Zotlabs/Module/Connedit.php:654
+#: ../../Zotlabs/Module/Connedit.php:941 ../../Zotlabs/Module/Group.php:179
+#: ../../Zotlabs/Module/Profiles.php:803
+#: ../../Zotlabs/Module/Editwebpage.php:167
+#: ../../Zotlabs/Module/Webpages.php:242
+#: ../../Zotlabs/Module/Card_edit.php:129 ../../Zotlabs/Lib/Apps.php:400
+#: ../../Zotlabs/Lib/ThreadItem.php:131 ../../Zotlabs/Storage/Browser.php:240
+#: ../../include/conversation.php:674 ../../include/conversation.php:717
+msgid "Delete"
+msgstr "Löschen"
-#: ../../Zotlabs/Access/Permissions.php:57
-msgid "Can like/dislike profiles and profile things"
-msgstr "Kann Profile und Profilsachen mögen/nicht mögen"
+#: ../../Zotlabs/Module/Blocks.php:166 ../../Zotlabs/Module/Events.php:694
+#: ../../Zotlabs/Module/Wiki.php:204 ../../Zotlabs/Module/Layouts.php:198
+#: ../../Zotlabs/Module/Webpages.php:246 ../../Zotlabs/Module/Pubsites.php:60
+#: ../../addon/gitwiki/Mod_Gitwiki.php:153
+msgid "View"
+msgstr "Ansicht"
-#: ../../Zotlabs/Access/Permissions.php:58
-msgid "Can forward to all my channel connections via @+ mentions in posts"
-msgstr "Kann an alle meine Verbindungen via @-Erwähnungen Nachrichten weiterleiten"
+#: ../../Zotlabs/Module/Invite.php:29
+msgid "Total invitation limit exceeded."
+msgstr "Einladungslimit überschritten."
-#: ../../Zotlabs/Access/Permissions.php:59
-msgid "Can chat with me"
-msgstr "Kann mit mir chatten"
+#: ../../Zotlabs/Module/Invite.php:53
+#, php-format
+msgid "%s : Not a valid email address."
+msgstr "%s : Keine gültige Email Adresse."
-#: ../../Zotlabs/Access/Permissions.php:60 ../../include/permissions.php:53
-msgid "Can source my public posts in derived channels"
-msgstr "Kann meine öffentlichen Beiträge als Quellen für Kanäle verwenden"
+#: ../../Zotlabs/Module/Invite.php:67
+msgid "Please join us on $Projectname"
+msgstr "Schließe Dich uns auf $Projectname an!"
-#: ../../Zotlabs/Access/Permissions.php:61
-msgid "Can administer my channel"
-msgstr "Kann meinen Kanal administrieren"
+#: ../../Zotlabs/Module/Invite.php:77
+msgid "Invitation limit exceeded. Please contact your site administrator."
+msgstr "Einladungslimit überschritten. Bitte kontaktiere den Administrator Deines $Projectname-Servers."
-#: ../../Zotlabs/Storage/Browser.php:106 ../../Zotlabs/Storage/Browser.php:237
-msgid "parent"
-msgstr "Übergeordnetes Verzeichnis"
+#: ../../Zotlabs/Module/Invite.php:82
+#, php-format
+msgid "%s : Message delivery failed."
+msgstr "%s : Nachricht konnte nicht zugestellt werden."
-#: ../../Zotlabs/Storage/Browser.php:130 ../../include/text.php:2682
-msgid "Collection"
-msgstr "Sammlung"
+#: ../../Zotlabs/Module/Invite.php:86
+#, php-format
+msgid "%d message sent."
+msgid_plural "%d messages sent."
+msgstr[0] "%d Nachricht gesendet."
+msgstr[1] "%d Nachrichten gesendet."
-#: ../../Zotlabs/Storage/Browser.php:133
-msgid "Principal"
-msgstr "Prinzipal"
+#: ../../Zotlabs/Module/Invite.php:107
+msgid "You have no more invitations available"
+msgstr "Du hast keine weiteren verfügbare Einladungen"
-#: ../../Zotlabs/Storage/Browser.php:136
-msgid "Addressbook"
-msgstr "Adressbuch"
+#: ../../Zotlabs/Module/Invite.php:138
+msgid "Send invitations"
+msgstr "Einladungen senden"
-#: ../../Zotlabs/Storage/Browser.php:139
-msgid "Calendar"
-msgstr "Kalender"
+#: ../../Zotlabs/Module/Invite.php:139
+msgid "Enter email addresses, one per line:"
+msgstr "Email-Adressen eintragen, eine pro Zeile:"
-#: ../../Zotlabs/Storage/Browser.php:142
-msgid "Schedule Inbox"
-msgstr "Posteingang für überwachte Kalender"
+#: ../../Zotlabs/Module/Invite.php:140 ../../Zotlabs/Module/Mail.php:285
+msgid "Your message:"
+msgstr "Deine Nachricht:"
-#: ../../Zotlabs/Storage/Browser.php:145
-msgid "Schedule Outbox"
-msgstr "Postausgang für überwachte Kalender"
+#: ../../Zotlabs/Module/Invite.php:141
+msgid "Please join my community on $Projectname."
+msgstr "Schließe Dich uns auf $Projectname an!"
+
+#: ../../Zotlabs/Module/Invite.php:143
+msgid "You will need to supply this invitation code:"
+msgstr "Bitte verwende bei der Registrierung den folgenden Einladungscode:"
+
+#: ../../Zotlabs/Module/Invite.php:144
+msgid ""
+"1. Register at any $Projectname location (they are all inter-connected)"
+msgstr "1. Registriere Dich auf einem beliebigen $Projectname-Hub (sie sind alle miteinander verbunden)"
+
+#: ../../Zotlabs/Module/Invite.php:146
+msgid "2. Enter my $Projectname network address into the site searchbar."
+msgstr "2. Gib meine $Projectname-Adresse im Suchfeld ein."
+
+#: ../../Zotlabs/Module/Invite.php:147
+msgid "or visit"
+msgstr "oder besuche"
+
+#: ../../Zotlabs/Module/Invite.php:149
+msgid "3. Click [Connect]"
+msgstr "3. Klicke auf [Verbinden]"
+
+#: ../../Zotlabs/Module/Invite.php:151 ../../Zotlabs/Module/Locs.php:121
+#: ../../Zotlabs/Module/Mitem.php:243 ../../Zotlabs/Module/Events.php:493
+#: ../../Zotlabs/Module/Appman.php:148
+#: ../../Zotlabs/Module/Import_items.php:129
+#: ../../Zotlabs/Module/Setup.php:308 ../../Zotlabs/Module/Setup.php:349
+#: ../../Zotlabs/Module/Connect.php:98
+#: ../../Zotlabs/Module/Admin/Features.php:66
+#: ../../Zotlabs/Module/Admin/Plugins.php:438
+#: ../../Zotlabs/Module/Admin/Accounts.php:166
+#: ../../Zotlabs/Module/Admin/Logs.php:84
+#: ../../Zotlabs/Module/Admin/Channels.php:147
+#: ../../Zotlabs/Module/Admin/Themes.php:158
+#: ../../Zotlabs/Module/Admin/Site.php:273
+#: ../../Zotlabs/Module/Admin/Profs.php:157
+#: ../../Zotlabs/Module/Admin/Account_edit.php:74
+#: ../../Zotlabs/Module/Admin/Security.php:104
+#: ../../Zotlabs/Module/Settings/Permcats.php:110
+#: ../../Zotlabs/Module/Settings/Channel.php:480
+#: ../../Zotlabs/Module/Settings/Features.php:47
+#: ../../Zotlabs/Module/Settings/Tokens.php:168
+#: ../../Zotlabs/Module/Settings/Account.php:118
+#: ../../Zotlabs/Module/Settings/Featured.php:52
+#: ../../Zotlabs/Module/Settings/Display.php:207
+#: ../../Zotlabs/Module/Settings/Oauth.php:87
+#: ../../Zotlabs/Module/Thing.php:321 ../../Zotlabs/Module/Thing.php:374
+#: ../../Zotlabs/Module/Import.php:529 ../../Zotlabs/Module/Cal.php:343
+#: ../../Zotlabs/Module/Mood.php:139 ../../Zotlabs/Module/Photos.php:659
+#: ../../Zotlabs/Module/Photos.php:1029 ../../Zotlabs/Module/Photos.php:1069
+#: ../../Zotlabs/Module/Photos.php:1187 ../../Zotlabs/Module/Wiki.php:206
+#: ../../Zotlabs/Module/Pdledit.php:94 ../../Zotlabs/Module/Poke.php:200
+#: ../../Zotlabs/Module/Connedit.php:904 ../../Zotlabs/Module/Chat.php:196
+#: ../../Zotlabs/Module/Chat.php:242 ../../Zotlabs/Module/Pconfig.php:107
+#: ../../Zotlabs/Module/Group.php:87 ../../Zotlabs/Module/Profiles.php:726
+#: ../../Zotlabs/Module/Sources.php:114 ../../Zotlabs/Module/Sources.php:149
+#: ../../Zotlabs/Module/Xchan.php:15 ../../Zotlabs/Module/Mail.php:431
+#: ../../Zotlabs/Module/Filestorage.php:155 ../../Zotlabs/Module/Rate.php:166
+#: ../../Zotlabs/Lib/ThreadItem.php:743
+#: ../../Zotlabs/Widget/Eventstools.php:16
+#: ../../Zotlabs/Widget/Wiki_pages.php:61
+#: ../../view/theme/redbasic_c/php/config.php:95
+#: ../../view/theme/redbasic/php/config.php:93
+#: ../../addon/skeleton/skeleton.php:65 ../../addon/gnusoc/gnusoc.php:269
+#: ../../addon/planets/planets.php:153
+#: ../../addon/openclipatar/openclipatar.php:53
+#: ../../addon/wppost/wppost.php:113 ../../addon/nsfw/nsfw.php:92
+#: ../../addon/ijpost/ijpost.php:89 ../../addon/dwpost/dwpost.php:89
+#: ../../addon/mailhost/mailhost.php:40
+#: ../../addon/likebanner/likebanner.php:57
+#: ../../addon/redphotos/redphotos.php:136 ../../addon/irc/irc.php:53
+#: ../../addon/ljpost/ljpost.php:86 ../../addon/startpage/startpage.php:113
+#: ../../addon/diaspora/diaspora.php:807
+#: ../../addon/gitwiki/Mod_Gitwiki.php:155
+#: ../../addon/rainbowtag/rainbowtag.php:85 ../../addon/visage/visage.php:170
+#: ../../addon/nsabait/nsabait.php:161 ../../addon/mailtest/mailtest.php:100
+#: ../../addon/openstreetmap/openstreetmap.php:168
+#: ../../addon/rtof/rtof.php:101 ../../addon/jappixmini/jappixmini.php:371
+#: ../../addon/superblock/superblock.php:120 ../../addon/nofed/nofed.php:80
+#: ../../addon/redred/redred.php:119 ../../addon/logrot/logrot.php:35
+#: ../../addon/frphotos/frphotos.php:96 ../../addon/pubcrawl/pubcrawl.php:1049
+#: ../../addon/chords/Mod_Chords.php:60 ../../addon/libertree/libertree.php:85
+#: ../../addon/flattrwidget/flattrwidget.php:124
+#: ../../addon/statusnet/statusnet.php:322
+#: ../../addon/statusnet/statusnet.php:380
+#: ../../addon/statusnet/statusnet.php:432
+#: ../../addon/statusnet/statusnet.php:899 ../../addon/twitter/twitter.php:217
+#: ../../addon/twitter/twitter.php:259
+#: ../../addon/smileybutton/smileybutton.php:219
+#: ../../addon/piwik/piwik.php:95 ../../addon/pageheader/pageheader.php:48
+#: ../../addon/authchoose/authchoose.php:71 ../../addon/xmpp/xmpp.php:69
+#: ../../addon/pumpio/pumpio.php:237 ../../addon/redfiles/redfiles.php:124
+#: ../../addon/hubwall/hubwall.php:95 ../../include/js_strings.php:22
+msgid "Submit"
+msgstr "Absenden"
+
+#: ../../Zotlabs/Module/Editlayout.php:79
+#: ../../Zotlabs/Module/Editblock.php:79 ../../Zotlabs/Module/Editblock.php:95
+#: ../../Zotlabs/Module/Editwebpage.php:80
+#: ../../Zotlabs/Module/Editpost.php:24 ../../Zotlabs/Module/Card_edit.php:17
+#: ../../Zotlabs/Module/Card_edit.php:33
+msgid "Item not found"
+msgstr "Element nicht gefunden"
+
+#: ../../Zotlabs/Module/Editlayout.php:128
+#: ../../Zotlabs/Module/Layouts.php:129 ../../Zotlabs/Module/Layouts.php:189
+msgid "Layout Name"
+msgstr "Layout-Name"
+
+#: ../../Zotlabs/Module/Editlayout.php:129
+#: ../../Zotlabs/Module/Layouts.php:132
+msgid "Layout Description (Optional)"
+msgstr "Layout-Beschreibung (optional)"
+
+#: ../../Zotlabs/Module/Editlayout.php:137
+msgid "Edit Layout"
+msgstr "Layout bearbeiten"
+
+#: ../../Zotlabs/Module/Profperm.php:28 ../../Zotlabs/Module/Subthread.php:62
+#: ../../Zotlabs/Module/Import_items.php:120 ../../Zotlabs/Module/Group.php:74
+#: ../../Zotlabs/Module/Dreport.php:10 ../../Zotlabs/Module/Dreport.php:68
+#: ../../Zotlabs/Module/Like.php:283 ../../Zotlabs/Web/WebServer.php:168
+#: ../../addon/redphotos/redphotos.php:119
+#: ../../addon/frphotos/frphotos.php:81 ../../addon/redfiles/redfiles.php:109
+#: ../../include/items.php:346
+msgid "Permission denied"
+msgstr "Keine Berechtigung"
+
+#: ../../Zotlabs/Module/Profperm.php:34 ../../Zotlabs/Module/Profperm.php:63
+msgid "Invalid profile identifier."
+msgstr "Ungültiger Profil-Identifikator"
+
+#: ../../Zotlabs/Module/Profperm.php:111
+msgid "Profile Visibility Editor"
+msgstr "Profil-Sichtbarkeits-Editor"
+
+#: ../../Zotlabs/Module/Profperm.php:113 ../../include/channel.php:1585
+msgid "Profile"
+msgstr "Profil"
+
+#: ../../Zotlabs/Module/Profperm.php:115
+msgid "Click on a contact to add or remove."
+msgstr "Klicke auf einen Kontakt, um ihn hinzuzufügen oder zu entfernen."
+
+#: ../../Zotlabs/Module/Profperm.php:124
+msgid "Visible To"
+msgstr "Sichtbar für"
+
+#: ../../Zotlabs/Module/Profperm.php:140
+#: ../../Zotlabs/Module/Connections.php:140
+msgid "All Connections"
+msgstr "Alle Verbindungen"
+
+#: ../../Zotlabs/Module/Cdav.php:785
+msgid "INVALID EVENT DISMISSED!"
+msgstr "UNGÜLTIGEN TERMIN ABGELEHNT!"
+
+#: ../../Zotlabs/Module/Cdav.php:786
+msgid "Summary: "
+msgstr "Zusammenfassung:"
-#: ../../Zotlabs/Storage/Browser.php:163 ../../Zotlabs/Module/Photos.php:789
-#: ../../Zotlabs/Module/Photos.php:1249
-#: ../../Zotlabs/Module/Embedphotos.php:145 ../../Zotlabs/Lib/Apps.php:490
-#: ../../Zotlabs/Lib/Apps.php:565
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:745
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:746
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:753
-#: ../../include/widgets.php:1754 ../../include/conversation.php:1047
+#: ../../Zotlabs/Module/Cdav.php:786 ../../Zotlabs/Module/Cdav.php:787
+#: ../../Zotlabs/Module/Cdav.php:794 ../../Zotlabs/Module/Embedphotos.php:146
+#: ../../Zotlabs/Module/Photos.php:764 ../../Zotlabs/Module/Photos.php:1220
+#: ../../Zotlabs/Lib/Apps.php:727 ../../Zotlabs/Lib/Apps.php:805
+#: ../../Zotlabs/Storage/Browser.php:164 ../../Zotlabs/Widget/Portfolio.php:86
+#: ../../Zotlabs/Widget/Album.php:84 ../../addon/pubcrawl/as.php:841
+#: ../../include/conversation.php:1143
msgid "Unknown"
msgstr "Unbekannt"
-#: ../../Zotlabs/Storage/Browser.php:224 ../../Zotlabs/Module/Fbrowser.php:85
-#: ../../Zotlabs/Lib/Apps.php:217 ../../include/nav.php:96
-#: ../../include/conversation.php:1699
-msgid "Files"
-msgstr "Dateien"
+#: ../../Zotlabs/Module/Cdav.php:787
+msgid "Date: "
+msgstr "Datum:"
-#: ../../Zotlabs/Storage/Browser.php:225
-msgid "Total"
-msgstr "Summe"
+#: ../../Zotlabs/Module/Cdav.php:788 ../../Zotlabs/Module/Cdav.php:795
+msgid "Reason: "
+msgstr "Grund:"
-#: ../../Zotlabs/Storage/Browser.php:227
-msgid "Shared"
-msgstr "Geteilt"
+#: ../../Zotlabs/Module/Cdav.php:793
+msgid "INVALID CARD DISMISSED!"
+msgstr "UNGÜLTIGE KARTE ABGELEHNT!"
-#: ../../Zotlabs/Storage/Browser.php:228 ../../Zotlabs/Storage/Browser.php:321
-#: ../../Zotlabs/Module/Menu.php:118 ../../Zotlabs/Module/New_channel.php:147
-#: ../../Zotlabs/Module/Blocks.php:159 ../../Zotlabs/Module/Layouts.php:184
-#: ../../Zotlabs/Module/Webpages.php:239
-#: ../../extend/addon/addon/cdav/include/widgets.php:127
-#: ../../extend/addon/addon/cdav/include/widgets.php:164
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1151
-#: ../../include/widgets.php:969
-msgid "Create"
-msgstr "Erstelle"
+#: ../../Zotlabs/Module/Cdav.php:794
+msgid "Name: "
+msgstr "Name: "
-#: ../../Zotlabs/Storage/Browser.php:229 ../../Zotlabs/Storage/Browser.php:323
-#: ../../Zotlabs/Module/Cover_photo.php:357
-#: ../../Zotlabs/Module/Photos.php:816 ../../Zotlabs/Module/Photos.php:1370
-#: ../../Zotlabs/Module/Profile_photo.php:410
-#: ../../Zotlabs/Module/Embedphotos.php:157
-#: ../../extend/addon/addon/cdav/include/widgets.php:132
-#: ../../extend/addon/addon/cdav/include/widgets.php:168
-#: ../../include/widgets.php:1767
-msgid "Upload"
-msgstr "Hochladen"
+#: ../../Zotlabs/Module/Cdav.php:868 ../../Zotlabs/Module/Events.php:460
+msgid "Event title"
+msgstr "Termintitel"
+
+#: ../../Zotlabs/Module/Cdav.php:869 ../../Zotlabs/Module/Events.php:466
+msgid "Start date and time"
+msgstr "Startdatum und -zeit"
+
+#: ../../Zotlabs/Module/Cdav.php:869 ../../Zotlabs/Module/Cdav.php:870
+msgid "Example: YYYY-MM-DD HH:mm"
+msgstr "Beispiel: JJJJ-MM-TT HH:mm"
+
+#: ../../Zotlabs/Module/Cdav.php:870
+msgid "End date and time"
+msgstr "Enddatum und -zeit"
+
+#: ../../Zotlabs/Module/Cdav.php:871 ../../Zotlabs/Module/Events.php:473
+#: ../../Zotlabs/Module/Appman.php:138 ../../Zotlabs/Module/Rbmark.php:101
+#: ../../addon/rendezvous/rendezvous.php:173
+msgid "Description"
+msgstr "Beschreibung"
+
+#: ../../Zotlabs/Module/Cdav.php:872 ../../Zotlabs/Module/Locs.php:117
+#: ../../Zotlabs/Module/Events.php:475 ../../Zotlabs/Module/Profiles.php:509
+#: ../../Zotlabs/Module/Profiles.php:737 ../../Zotlabs/Module/Pubsites.php:52
+#: ../../include/js_strings.php:25
+msgid "Location"
+msgstr "Ort"
+
+#: ../../Zotlabs/Module/Cdav.php:879 ../../Zotlabs/Module/Events.php:689
+#: ../../Zotlabs/Module/Events.php:698 ../../Zotlabs/Module/Cal.php:337
+#: ../../Zotlabs/Module/Cal.php:344 ../../Zotlabs/Module/Photos.php:918
+msgid "Previous"
+msgstr "Voriges"
+
+#: ../../Zotlabs/Module/Cdav.php:880 ../../Zotlabs/Module/Events.php:690
+#: ../../Zotlabs/Module/Events.php:699 ../../Zotlabs/Module/Setup.php:263
+#: ../../Zotlabs/Module/Cal.php:338 ../../Zotlabs/Module/Cal.php:345
+#: ../../Zotlabs/Module/Photos.php:927
+msgid "Next"
+msgstr "Nächste"
+
+#: ../../Zotlabs/Module/Cdav.php:881 ../../Zotlabs/Module/Events.php:700
+#: ../../Zotlabs/Module/Cal.php:346
+msgid "Today"
+msgstr "Heute"
+
+#: ../../Zotlabs/Module/Cdav.php:882 ../../Zotlabs/Module/Events.php:695
+msgid "Month"
+msgstr "Monat"
+
+#: ../../Zotlabs/Module/Cdav.php:883 ../../Zotlabs/Module/Events.php:696
+msgid "Week"
+msgstr "Woche"
+
+#: ../../Zotlabs/Module/Cdav.php:884 ../../Zotlabs/Module/Events.php:697
+msgid "Day"
+msgstr "Tag"
+
+#: ../../Zotlabs/Module/Cdav.php:885
+msgid "List month"
+msgstr "Liste Monat"
+
+#: ../../Zotlabs/Module/Cdav.php:886
+msgid "List week"
+msgstr "Liste Woche"
+
+#: ../../Zotlabs/Module/Cdav.php:887
+msgid "List day"
+msgstr "Liste Tag"
+
+#: ../../Zotlabs/Module/Cdav.php:894
+msgid "More"
+msgstr "Mehr"
+
+#: ../../Zotlabs/Module/Cdav.php:895
+msgid "Less"
+msgstr "Weniger"
-#: ../../Zotlabs/Storage/Browser.php:233
+#: ../../Zotlabs/Module/Cdav.php:896
+msgid "Select calendar"
+msgstr "Kalender auswählen"
+
+#: ../../Zotlabs/Module/Cdav.php:898
+msgid "Delete all"
+msgstr "Alles löschen"
+
+#: ../../Zotlabs/Module/Cdav.php:899 ../../Zotlabs/Module/Cdav.php:1188
+#: ../../Zotlabs/Module/Admin/Plugins.php:423
+#: ../../Zotlabs/Module/Settings/Oauth.php:88
+#: ../../Zotlabs/Module/Settings/Oauth.php:114
+#: ../../Zotlabs/Module/Wiki.php:333 ../../Zotlabs/Module/Wiki.php:363
+#: ../../Zotlabs/Module/Connedit.php:942 ../../Zotlabs/Module/Fbrowser.php:66
+#: ../../Zotlabs/Module/Fbrowser.php:88 ../../Zotlabs/Module/Profiles.php:804
+#: ../../Zotlabs/Module/Filer.php:55 ../../Zotlabs/Module/Tagrm.php:15
+#: ../../Zotlabs/Module/Tagrm.php:138 ../../addon/js_upload/js_upload.php:46
+#: ../../addon/gitwiki/Mod_Gitwiki.php:244
+#: ../../addon/gitwiki/Mod_Gitwiki.php:267 ../../include/conversation.php:1369
+#: ../../include/conversation.php:1418
+msgid "Cancel"
+msgstr "Abbrechen"
+
+#: ../../Zotlabs/Module/Cdav.php:900
+msgid "Sorry! Editing of recurrent events is not yet implemented."
+msgstr "Entschuldigung, aber das Bearbeiten von wiederkehrenden Veranstaltungen ist leider noch nicht implementiert."
+
+#: ../../Zotlabs/Module/Cdav.php:1170
+#: ../../Zotlabs/Module/Sharedwithme.php:105
#: ../../Zotlabs/Module/Admin/Channels.php:159
-#: ../../Zotlabs/Module/Sharedwithme.php:99 ../../Zotlabs/Module/Wiki.php:151
#: ../../Zotlabs/Module/Settings/Oauth.php:89
#: ../../Zotlabs/Module/Settings/Oauth.php:115
-#: ../../Zotlabs/Module/Chat.php:250
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1136
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:132
+#: ../../Zotlabs/Module/Wiki.php:209 ../../Zotlabs/Module/Connedit.php:924
+#: ../../Zotlabs/Module/Chat.php:251 ../../Zotlabs/Lib/NativeWikiPage.php:554
+#: ../../Zotlabs/Storage/Browser.php:234
+#: ../../Zotlabs/Widget/Wiki_page_history.php:22
+#: ../../addon/rendezvous/rendezvous.php:172
+#: ../../addon/gitwiki/Mod_Gitwiki.php:158
msgid "Name"
msgstr "Name"
-#: ../../Zotlabs/Storage/Browser.php:234 ../../Zotlabs/Module/Wiki.php:152
-msgid "Type"
-msgstr "Typ"
+#: ../../Zotlabs/Module/Cdav.php:1171 ../../Zotlabs/Module/Connedit.php:925
+msgid "Organisation"
+msgstr "Organisation"
-#: ../../Zotlabs/Storage/Browser.php:235
-#: ../../Zotlabs/Module/Sharedwithme.php:101 ../../include/text.php:1390
-msgid "Size"
-msgstr "Größe"
+#: ../../Zotlabs/Module/Cdav.php:1172 ../../Zotlabs/Module/Connedit.php:926
+msgid "Title"
+msgstr "Titel"
-#: ../../Zotlabs/Storage/Browser.php:236
-#: ../../Zotlabs/Module/Sharedwithme.php:102
-msgid "Last Modified"
-msgstr "Zuletzt geändert"
+#: ../../Zotlabs/Module/Cdav.php:1173 ../../Zotlabs/Module/Connedit.php:927
+#: ../../Zotlabs/Module/Profiles.php:789
+msgid "Phone"
+msgstr "Telefon"
-#: ../../Zotlabs/Storage/Browser.php:238
-#: ../../Zotlabs/Module/Connections.php:290
-#: ../../Zotlabs/Module/Connections.php:310
-#: ../../Zotlabs/Module/Admin/Profs.php:154
-#: ../../Zotlabs/Module/Editlayout.php:114
-#: ../../Zotlabs/Module/Editwebpage.php:145 ../../Zotlabs/Module/Menu.php:112
-#: ../../Zotlabs/Module/Editblock.php:109 ../../Zotlabs/Module/Editpost.php:84
-#: ../../Zotlabs/Module/Blocks.php:160 ../../Zotlabs/Module/Layouts.php:192
-#: ../../Zotlabs/Module/Webpages.php:240 ../../Zotlabs/Module/Wiki.php:144
-#: ../../Zotlabs/Module/Wiki.php:252
-#: ../../Zotlabs/Module/Settings/Oauth.php:149
-#: ../../Zotlabs/Module/Thing.php:260 ../../Zotlabs/Lib/Apps.php:341
-#: ../../Zotlabs/Lib/ThreadItem.php:106
-#: ../../extend/addon/addon/cdav/include/widgets.php:125
-#: ../../extend/addon/addon/cdav/include/widgets.php:161
-#: ../../include/channel.php:961 ../../include/channel.php:965
-#: ../../include/page_widgets.php:9 ../../include/page_widgets.php:39
-#: ../../include/menu.php:113 ../../include/widgets.php:965
-msgid "Edit"
-msgstr "Bearbeiten"
+#: ../../Zotlabs/Module/Cdav.php:1174
+#: ../../Zotlabs/Module/Admin/Accounts.php:169
+#: ../../Zotlabs/Module/Admin/Accounts.php:181
+#: ../../Zotlabs/Module/Connedit.php:928 ../../Zotlabs/Module/Profiles.php:790
+#: ../../addon/openid/MysqlProvider.php:56
+#: ../../addon/openid/MysqlProvider.php:57 ../../addon/rtof/rtof.php:93
+#: ../../addon/redred/redred.php:107 ../../include/network.php:1706
+msgid "Email"
+msgstr "E-Mail"
-#: ../../Zotlabs/Storage/Browser.php:239 ../../Zotlabs/Module/Connedit.php:635
-#: ../../Zotlabs/Module/Connections.php:263
-#: ../../Zotlabs/Module/Admin/Profs.php:155
-#: ../../Zotlabs/Module/Admin/Accounts.php:173
-#: ../../Zotlabs/Module/Admin/Channels.php:149
-#: ../../Zotlabs/Module/Editlayout.php:137
-#: ../../Zotlabs/Module/Editwebpage.php:170
-#: ../../Zotlabs/Module/Editblock.php:134 ../../Zotlabs/Module/Group.php:177
-#: ../../Zotlabs/Module/Photos.php:1179 ../../Zotlabs/Module/Blocks.php:162
-#: ../../Zotlabs/Module/Webpages.php:242
-#: ../../Zotlabs/Module/Settings/Oauth.php:150
-#: ../../Zotlabs/Module/Thing.php:261 ../../Zotlabs/Lib/Apps.php:342
-#: ../../Zotlabs/Lib/ThreadItem.php:126
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:864
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1153
-#: ../../include/conversation.php:676
-msgid "Delete"
-msgstr "Löschen"
+#: ../../Zotlabs/Module/Cdav.php:1175 ../../Zotlabs/Module/Connedit.php:929
+#: ../../Zotlabs/Module/Profiles.php:791
+msgid "Instant messenger"
+msgstr "Sofortnachrichtendienst"
-#: ../../Zotlabs/Storage/Browser.php:299
-#, php-format
-msgid "You are using %1$s of your available file storage."
-msgstr "Sie verwenden %1$s von Ihrem verfügbaren Dateispeicher."
+#: ../../Zotlabs/Module/Cdav.php:1176 ../../Zotlabs/Module/Connedit.php:930
+#: ../../Zotlabs/Module/Profiles.php:792
+msgid "Website"
+msgstr "Webseite"
-#: ../../Zotlabs/Storage/Browser.php:304
-#, php-format
-msgid "You are using %1$s of %2$s available file storage. (%3$s&#37;)"
-msgstr "Sie verwenden %1$s von %2$s verfügbarem Dateispeicher. (%3$s&#37;)"
+#: ../../Zotlabs/Module/Cdav.php:1177 ../../Zotlabs/Module/Locs.php:118
+#: ../../Zotlabs/Module/Admin/Channels.php:160
+#: ../../Zotlabs/Module/Connedit.php:931 ../../Zotlabs/Module/Profiles.php:502
+#: ../../Zotlabs/Module/Profiles.php:793
+msgid "Address"
+msgstr "Adresse"
-#: ../../Zotlabs/Storage/Browser.php:315
-msgid "WARNING:"
-msgstr "WARNUNG:"
+#: ../../Zotlabs/Module/Cdav.php:1178 ../../Zotlabs/Module/Connedit.php:932
+#: ../../Zotlabs/Module/Profiles.php:794
+msgid "Note"
+msgstr "Hinweis"
-#: ../../Zotlabs/Storage/Browser.php:320
-msgid "Create new folder"
-msgstr "Neuen Ordner anlegen"
+#: ../../Zotlabs/Module/Cdav.php:1179 ../../Zotlabs/Module/Connedit.php:933
+#: ../../Zotlabs/Module/Profiles.php:795 ../../include/event.php:1290
+#: ../../include/connections.php:682
+msgid "Mobile"
+msgstr "Mobil"
-#: ../../Zotlabs/Storage/Browser.php:322
-msgid "Upload file"
-msgstr "Datei hochladen"
+#: ../../Zotlabs/Module/Cdav.php:1180 ../../Zotlabs/Module/Connedit.php:934
+#: ../../Zotlabs/Module/Profiles.php:796 ../../include/event.php:1291
+#: ../../include/connections.php:683
+msgid "Home"
+msgstr "Home"
-#: ../../Zotlabs/Storage/Browser.php:335
-msgid "Drop files here to immediately upload"
-msgstr "Dateien zum sofortigen Hochladen hier fallen lassen"
+#: ../../Zotlabs/Module/Cdav.php:1181 ../../Zotlabs/Module/Connedit.php:935
+#: ../../Zotlabs/Module/Profiles.php:797 ../../include/event.php:1294
+#: ../../include/connections.php:686
+msgid "Work"
+msgstr "Arbeit"
-#: ../../Zotlabs/Web/Router.php:67 ../../Zotlabs/Web/WebServer.php:128
-#: ../../Zotlabs/Module/Achievements.php:34
-#: ../../Zotlabs/Module/Register.php:77 ../../Zotlabs/Module/Connedit.php:397
-#: ../../Zotlabs/Module/Authtest.php:16 ../../Zotlabs/Module/Bookmarks.php:61
-#: ../../Zotlabs/Module/Locs.php:87 ../../Zotlabs/Module/Page.php:35
-#: ../../Zotlabs/Module/Page.php:91 ../../Zotlabs/Module/Manage.php:10
-#: ../../Zotlabs/Module/Connections.php:33
-#: ../../Zotlabs/Module/Cover_photo.php:277
-#: ../../Zotlabs/Module/Cover_photo.php:290
-#: ../../Zotlabs/Module/Editlayout.php:67
-#: ../../Zotlabs/Module/Editlayout.php:90
-#: ../../Zotlabs/Module/Editwebpage.php:68
-#: ../../Zotlabs/Module/Editwebpage.php:89
-#: ../../Zotlabs/Module/Editwebpage.php:104
-#: ../../Zotlabs/Module/Editwebpage.php:126
-#: ../../Zotlabs/Module/Channel.php:107 ../../Zotlabs/Module/Channel.php:237
-#: ../../Zotlabs/Module/Channel.php:277 ../../Zotlabs/Module/Network.php:15
-#: ../../Zotlabs/Module/Menu.php:78 ../../Zotlabs/Module/Appman.php:75
-#: ../../Zotlabs/Module/Filestorage.php:23
-#: ../../Zotlabs/Module/Filestorage.php:78
-#: ../../Zotlabs/Module/Filestorage.php:93
-#: ../../Zotlabs/Module/Filestorage.php:120 ../../Zotlabs/Module/Item.php:220
-#: ../../Zotlabs/Module/Item.php:230 ../../Zotlabs/Module/Item.php:1098
-#: ../../Zotlabs/Module/Settings.php:59 ../../Zotlabs/Module/Mail.php:135
-#: ../../Zotlabs/Module/Block.php:26 ../../Zotlabs/Module/Block.php:76
-#: ../../Zotlabs/Module/Invite.php:17 ../../Zotlabs/Module/Invite.php:94
-#: ../../Zotlabs/Module/Editblock.php:67 ../../Zotlabs/Module/Group.php:13
-#: ../../Zotlabs/Module/Mitem.php:115 ../../Zotlabs/Module/Message.php:18
-#: ../../Zotlabs/Module/Mood.php:116 ../../Zotlabs/Module/Photos.php:73
-#: ../../Zotlabs/Module/Setup.php:212 ../../Zotlabs/Module/Editpost.php:17
-#: ../../Zotlabs/Module/New_channel.php:77
-#: ../../Zotlabs/Module/New_channel.php:104
-#: ../../Zotlabs/Module/Notifications.php:11 ../../Zotlabs/Module/Poke.php:137
-#: ../../Zotlabs/Module/Profiles.php:197 ../../Zotlabs/Module/Profiles.php:595
-#: ../../Zotlabs/Module/Profile.php:68 ../../Zotlabs/Module/Profile.php:76
-#: ../../Zotlabs/Module/Blocks.php:73 ../../Zotlabs/Module/Blocks.php:80
-#: ../../Zotlabs/Module/Layouts.php:71 ../../Zotlabs/Module/Layouts.php:78
-#: ../../Zotlabs/Module/Layouts.php:89 ../../Zotlabs/Module/Rate.php:113
-#: ../../Zotlabs/Module/Like.php:181
-#: ../../Zotlabs/Module/Profile_photo.php:273
-#: ../../Zotlabs/Module/Profile_photo.php:286
-#: ../../Zotlabs/Module/Common.php:39 ../../Zotlabs/Module/Api.php:24
-#: ../../Zotlabs/Module/Regmod.php:21 ../../Zotlabs/Module/Pdledit.php:29
-#: ../../Zotlabs/Module/Service_limits.php:11
-#: ../../Zotlabs/Module/Webpages.php:116
-#: ../../Zotlabs/Module/Sharedwithme.php:11 ../../Zotlabs/Module/Wiki.php:189
-#: ../../Zotlabs/Module/Wiki.php:302 ../../Zotlabs/Module/Sources.php:74
-#: ../../Zotlabs/Module/Suggest.php:30 ../../Zotlabs/Module/Thing.php:274
-#: ../../Zotlabs/Module/Thing.php:294 ../../Zotlabs/Module/Thing.php:335
-#: ../../Zotlabs/Module/Viewconnections.php:28
-#: ../../Zotlabs/Module/Viewconnections.php:33
-#: ../../Zotlabs/Module/Viewsrc.php:18 ../../Zotlabs/Module/Chat.php:100
-#: ../../Zotlabs/Module/Chat.php:105 ../../Zotlabs/Module/Events.php:267
-#: ../../Zotlabs/Lib/Chatroom.php:137
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:55
-#: ../../extend/addon/addon/keepout/keepout.php:36
-#: ../../extend/addon/addon/pumpio/pumpio.php:40
-#: ../../extend/addon/addon/openid/Mod_Id.php:53
-#: ../../extend/addon/addon/diaspora_reconnect/diaspora_reconnect.php:58
-#: ../../include/items.php:3422 ../../include/attach.php:142
-#: ../../include/attach.php:189 ../../include/attach.php:253
-#: ../../include/attach.php:267 ../../include/attach.php:274
-#: ../../include/attach.php:341 ../../include/attach.php:355
-#: ../../include/attach.php:362 ../../include/attach.php:439
-#: ../../include/attach.php:906 ../../include/attach.php:977
-#: ../../include/attach.php:1135 ../../include/photos.php:27
-msgid "Permission denied."
-msgstr "Berechtigung verweigert."
+#: ../../Zotlabs/Module/Cdav.php:1183 ../../Zotlabs/Module/Connedit.php:937
+#: ../../Zotlabs/Module/Profiles.php:799
+#: ../../addon/jappixmini/jappixmini.php:368
+msgid "Add Contact"
+msgstr "Kontakt hinzufügen"
-#: ../../Zotlabs/Web/Router.php:148 ../../include/help.php:63
-msgid "Not Found"
-msgstr "Nicht gefunden"
+#: ../../Zotlabs/Module/Cdav.php:1184 ../../Zotlabs/Module/Connedit.php:938
+#: ../../Zotlabs/Module/Profiles.php:800
+msgid "Add Field"
+msgstr "Feld hinzufügen"
-#: ../../Zotlabs/Web/Router.php:151 ../../Zotlabs/Module/Page.php:94
-#: ../../Zotlabs/Module/Display.php:120 ../../Zotlabs/Module/Block.php:79
-#: ../../include/help.php:66
-msgid "Page not found."
-msgstr "Seite nicht gefunden."
+#: ../../Zotlabs/Module/Cdav.php:1186
+#: ../../Zotlabs/Module/Admin/Plugins.php:453
+#: ../../Zotlabs/Module/Settings/Oauth.php:42
+#: ../../Zotlabs/Module/Settings/Oauth.php:113
+#: ../../Zotlabs/Module/Connedit.php:940 ../../Zotlabs/Module/Profiles.php:802
+#: ../../Zotlabs/Lib/Apps.php:383
+msgid "Update"
+msgstr "Aktualisieren"
-#: ../../Zotlabs/Web/WebServer.php:127 ../../Zotlabs/Module/Dreport.php:10
-#: ../../Zotlabs/Module/Dreport.php:68
-#: ../../Zotlabs/Module/Import_items.php:114 ../../Zotlabs/Module/Group.php:72
-#: ../../Zotlabs/Module/Profperm.php:28 ../../Zotlabs/Module/Like.php:283
-#: ../../Zotlabs/Module/Subthread.php:62
-#: ../../extend/addon/addon/frphotos/frphotos.php:81
-#: ../../extend/addon/addon/redfiles/redfiles.php:109
-#: ../../extend/addon/addon/redphotos/redphotos.php:119
-#: ../../include/items.php:327
-msgid "Permission denied"
-msgstr "Keine Berechtigung"
+#: ../../Zotlabs/Module/Cdav.php:1189 ../../Zotlabs/Module/Connedit.php:943
+msgid "P.O. Box"
+msgstr "Postfach"
-#: ../../Zotlabs/Zot/Auth.php:138
-msgid ""
-"Remote authentication blocked. You are logged into this site locally. Please"
-" logout and retry."
-msgstr "Fern-Authentifizierung blockiert. Du bist lokal auf diesem Server angemeldet. Bitte melde Dich ab und versuche es erneut."
+#: ../../Zotlabs/Module/Cdav.php:1190 ../../Zotlabs/Module/Connedit.php:944
+msgid "Additional"
+msgstr "Zusätzlich"
-#: ../../Zotlabs/Zot/Auth.php:250
-#: ../../extend/addon/addon/openid/Mod_Openid.php:76
-#: ../../extend/addon/addon/openid/Mod_Openid.php:183
-#, php-format
-msgid "Welcome %s. Remote authentication successful."
-msgstr "Willkommen %s. Entfernte Authentifizierung erfolgreich."
+#: ../../Zotlabs/Module/Cdav.php:1191 ../../Zotlabs/Module/Connedit.php:945
+msgid "Street"
+msgstr "Straße"
-#: ../../Zotlabs/Module/Achievements.php:15
-#: ../../Zotlabs/Module/Connect.php:17 ../../Zotlabs/Module/Editlayout.php:31
-#: ../../Zotlabs/Module/Editwebpage.php:32
-#: ../../Zotlabs/Module/Filestorage.php:59
-#: ../../Zotlabs/Module/Editblock.php:31 ../../Zotlabs/Module/Hcard.php:12
-#: ../../Zotlabs/Module/Profile.php:20 ../../Zotlabs/Module/Blocks.php:33
-#: ../../Zotlabs/Module/Layouts.php:31 ../../Zotlabs/Module/Webpages.php:33
-#: ../../include/channel.php:862
-msgid "Requested profile is not available."
-msgstr "Das angefragte Profil ist nicht verfügbar."
+#: ../../Zotlabs/Module/Cdav.php:1192 ../../Zotlabs/Module/Connedit.php:946
+msgid "Locality"
+msgstr "Ortschaft"
-#: ../../Zotlabs/Module/Achievements.php:38
-msgid "Some blurb about what to do when you're new here"
-msgstr "Ein Hinweis, was man tun kann, wenn man neu hier ist"
+#: ../../Zotlabs/Module/Cdav.php:1193 ../../Zotlabs/Module/Connedit.php:947
+msgid "Region"
+msgstr "Region"
-#: ../../Zotlabs/Module/Chatsvc.php:117
-msgid "Away"
-msgstr "Abwesend"
+#: ../../Zotlabs/Module/Cdav.php:1194 ../../Zotlabs/Module/Connedit.php:948
+msgid "ZIP Code"
+msgstr "Postleitzahl"
-#: ../../Zotlabs/Module/Chatsvc.php:122
-msgid "Online"
-msgstr "Online"
+#: ../../Zotlabs/Module/Cdav.php:1195 ../../Zotlabs/Module/Connedit.php:949
+#: ../../Zotlabs/Module/Profiles.php:760
+msgid "Country"
+msgstr "Land"
-#: ../../Zotlabs/Module/Register.php:49
-msgid "Maximum daily site registrations exceeded. Please try again tomorrow."
-msgstr "Maximale Anzahl täglicher Neuanmeldungen erreicht. Bitte versuche es morgen noch einmal."
+#: ../../Zotlabs/Module/Cdav.php:1242
+msgid "Default Calendar"
+msgstr "Standardkalender"
-#: ../../Zotlabs/Module/Register.php:55
-msgid ""
-"Please indicate acceptance of the Terms of Service. Registration failed."
-msgstr "Bitte stimme den Nutzungsbedingungen zu. Registrierung fehlgeschlagen."
+#: ../../Zotlabs/Module/Cdav.php:1252
+msgid "Default Addressbook"
+msgstr "Standardadressbuch"
-#: ../../Zotlabs/Module/Register.php:89
-msgid "Passwords do not match."
-msgstr "Passwörter stimmen nicht überein."
+#: ../../Zotlabs/Module/Regdir.php:49 ../../Zotlabs/Module/Dirsearch.php:25
+msgid "This site is not a directory server"
+msgstr "Diese Webseite ist kein Verzeichnisserver"
-#: ../../Zotlabs/Module/Register.php:131
-msgid ""
-"Registration successful. Please check your email for validation "
-"instructions."
-msgstr "Registrierung erfolgreich. Eine E-Mail mit weiteren Anweisungen wurde an Dich gesendet."
+#: ../../Zotlabs/Module/Channel.php:32 ../../Zotlabs/Module/Chat.php:25
+#: ../../addon/gitwiki/Mod_Gitwiki.php:28 ../../addon/chess/chess.php:431
+msgid "You must be logged in to see this page."
+msgstr "Du musst angemeldet sein, um diese Seite betrachten zu können."
-#: ../../Zotlabs/Module/Register.php:137
-msgid "Your registration is pending approval by the site owner."
-msgstr "Deine Registrierung muss noch vom Betreiber der Seite freigegeben werden."
+#: ../../Zotlabs/Module/Channel.php:47 ../../Zotlabs/Module/Hcard.php:37
+#: ../../Zotlabs/Module/Profile.php:45
+msgid "Posts and comments"
+msgstr "Beiträge und Kommentare"
-#: ../../Zotlabs/Module/Register.php:140
-msgid "Your registration can not be processed."
-msgstr "Deine Registrierung konnte nicht verarbeitet werden."
+#: ../../Zotlabs/Module/Channel.php:54 ../../Zotlabs/Module/Hcard.php:44
+#: ../../Zotlabs/Module/Profile.php:52
+msgid "Only posts"
+msgstr "Nur Beiträge"
-#: ../../Zotlabs/Module/Register.php:184
-msgid "Registration on this hub is disabled."
-msgstr "Die Registrierung auf diesem Hub ist nicht möglich."
+#: ../../Zotlabs/Module/Channel.php:107
+msgid "Insufficient permissions. Request redirected to profile page."
+msgstr "Unzureichende Zugriffsrechte. Die Anfrage wurde zur Profil-Seite umgeleitet."
-#: ../../Zotlabs/Module/Register.php:193
-msgid "Registration on this hub is by approval only."
-msgstr "Eine Registrierung auf diesem Hub erfordert die Zustimmung durch den Administrator."
+#: ../../Zotlabs/Module/Uexport.php:57 ../../Zotlabs/Module/Uexport.php:58
+msgid "Export Channel"
+msgstr "Kanal exportieren"
-#: ../../Zotlabs/Module/Register.php:194
-msgid "<a href=\"pubsites\">Register at another affiliated hub.</a>"
-msgstr "<a href=\"pubsites\">Registriere Dich auf einem der anderen verbundenen Hubs.</a>"
+#: ../../Zotlabs/Module/Uexport.php:59
+msgid ""
+"Export your basic channel information to a file. This acts as a backup of "
+"your connections, permissions, profile and basic data, which can be used to "
+"import your data to a new server hub, but does not contain your content."
+msgstr "Exportiert die grundlegenden Kanal-Informationen in eine kleine Datei. Diese stellt eine Sicherung Deiner Verbindungen, Berechtigungen, Profile und Basisdaten bereit, die für den Import auf einem anderen Hub verwendet werden kann, aber nicht die Beiträge Deines Kanals enthält."
-#: ../../Zotlabs/Module/Register.php:204
+#: ../../Zotlabs/Module/Uexport.php:60
+msgid "Export Content"
+msgstr "Kanal und Inhalte exportieren"
+
+#: ../../Zotlabs/Module/Uexport.php:61
msgid ""
-"This site has exceeded the number of allowed daily account registrations. "
-"Please try again tomorrow."
-msgstr "Die maximale Anzahl täglicher Registrierungen auf diesem Server wurde überschritten. Bitte versuche es morgen noch einmal."
+"Export your channel information and recent content to a JSON backup that can"
+" be restored or imported to another server hub. This backs up all of your "
+"connections, permissions, profile data and several months of posts. This "
+"file may be VERY large. Please be patient - it may take several minutes for"
+" this download to begin."
+msgstr "Exportiert Deine Kanal-Informationen sowie alle zugehörigen Inhalte in eine JSON-Sicherungsdatei. Die sichert alle Verbindungen, Berechtigungen, Profildaten und Deine Beiträge aus mehreren Monaten. Diese Datei kann SEHR groß werden! Bitte habe ein wenig Geduld – es kann mehrere Minuten dauern, bis der Download startet."
-#: ../../Zotlabs/Module/Register.php:221 ../../Zotlabs/Module/Siteinfo.php:27
-msgid "Terms of Service"
-msgstr "Nutzungsbedingungen"
+#: ../../Zotlabs/Module/Uexport.php:63
+msgid "Export your posts from a given year."
+msgstr "Exportiert die Beiträge des angegebenen Jahres."
-#: ../../Zotlabs/Module/Register.php:227
+#: ../../Zotlabs/Module/Uexport.php:65
+msgid ""
+"You may also export your posts and conversations for a particular year or "
+"month. Adjust the date in your browser location bar to select other dates. "
+"If the export fails (possibly due to memory exhaustion on your server hub), "
+"please try again selecting a more limited date range."
+msgstr "Du kannst auch die Beiträge und Konversationen eines bestimmten Jahres oder Monats exportieren. Ändere das Datum in der Adresszeile Deines Browsers, um andere Zeiträume zu wählen. Falls der Export fehlschlägt (vermutlich, weil auf diesem Hub nicht genügend Speicher zur Verfügung steht), versuche es noch einmal mit einer kleineren Zeitspanne."
+
+#: ../../Zotlabs/Module/Uexport.php:66
#, php-format
-msgid "I accept the %s for this website"
-msgstr "Ich akzeptiere die %s für diese Webseite"
+msgid ""
+"To select all posts for a given year, such as this year, visit <a "
+"href=\"%1$s\">%2$s</a>"
+msgstr "Um alle Beiträge eines bestimmten Jahres, zum Beispiel dieses Jahres, auszuwählen, klicke <a href=\"%1$s\">%2$s</a>."
-#: ../../Zotlabs/Module/Register.php:229
+#: ../../Zotlabs/Module/Uexport.php:67
#, php-format
-msgid "I am over 13 years of age and accept the %s for this website"
-msgstr "Ich bin älter als 13 Jahre und akzeptiere die %s dieser Webseite"
+msgid ""
+"To select all posts for a given month, such as January of this year, visit "
+"<a href=\"%1$s\">%2$s</a>"
+msgstr "Um alle Beiträge eines bestimmten Monats auszuwählen, zum Beispiel vom Januar diesen Jahres, klicke <a href=\"%1$s\">%2$s</a>."
-#: ../../Zotlabs/Module/Register.php:233
-msgid "Your email address"
-msgstr "Ihre E-Mail Adresse"
+#: ../../Zotlabs/Module/Uexport.php:68
+#, php-format
+msgid ""
+"These content files may be imported or restored by visiting <a "
+"href=\"%1$s\">%2$s</a> on any site containing your channel. For best results"
+" please import or restore these in date order (oldest first)."
+msgstr "Diese Inhalts-Sicherungen können wiederhergestellt werden, indem Du <a href=\"%1$s\">%2$s</a> auf jeglichem Hub besuchst, der diesen Kanal enthält. Das funktioniert am besten, wenn Du dabei die zeitliche Reihenfolge einhältst, also die Sicherungen für den ältesten Zeitraum zuerst importierst."
-#: ../../Zotlabs/Module/Register.php:234
-msgid "Choose a password"
-msgstr "Passwort"
+#: ../../Zotlabs/Module/Search.php:17 ../../Zotlabs/Module/Photos.php:490
+#: ../../Zotlabs/Module/Ratings.php:83 ../../Zotlabs/Module/Directory.php:63
+#: ../../Zotlabs/Module/Display.php:21
+#: ../../Zotlabs/Module/Viewconnections.php:23
+msgid "Public access denied."
+msgstr "Öffentlichen Zugriff verweigert."
-#: ../../Zotlabs/Module/Register.php:235
-msgid "Please re-enter your password"
-msgstr "Bitte gib Dein Passwort noch einmal ein"
+#: ../../Zotlabs/Module/Search.php:44 ../../Zotlabs/Module/Connections.php:313
+#: ../../Zotlabs/Lib/Apps.php:250 ../../Zotlabs/Widget/Sitesearch.php:31
+#: ../../include/text.php:1029 ../../include/text.php:1041
+#: ../../include/acl_selectors.php:213 ../../include/nav.php:204
+msgid "Search"
+msgstr "Suche"
-#: ../../Zotlabs/Module/Register.php:236
-msgid "Please enter your invitation code"
-msgstr "Bitte trage Deinen Einladungs-Code ein"
+#: ../../Zotlabs/Module/Search.php:225
+#, php-format
+msgid "Items tagged with: %s"
+msgstr "Beiträge mit Schlagwort: %s"
-#: ../../Zotlabs/Module/Register.php:237
-#: ../../Zotlabs/Module/New_channel.php:134
-msgid "Name or caption"
-msgstr "Name oder Titel"
+#: ../../Zotlabs/Module/Search.php:227
+#, php-format
+msgid "Search results for: %s"
+msgstr "Suchergebnisse für: %s"
-#: ../../Zotlabs/Module/Register.php:237
-#: ../../Zotlabs/Module/New_channel.php:134
-msgid "Examples: \"Bob Jameson\", \"Lisa and her Horses\", \"Soccer\", \"Aviation Group\""
-msgstr "Beispiele: „Horst Weidinger“, „Lisa und ihr Meerschweinchen“, „Fußball“, „Segelflieger-Forum“ "
+#: ../../Zotlabs/Module/Pubstream.php:38
+#: ../../Zotlabs/Widget/Notifications.php:128
+msgid "Public Stream"
+msgstr "Öffentlicher Beitrags-Stream"
-#: ../../Zotlabs/Module/Register.php:239
-#: ../../Zotlabs/Module/New_channel.php:136
-msgid "Choose a short nickname"
-msgstr "Wähle einen kurzen Spitznamen"
+#: ../../Zotlabs/Module/Locs.php:25 ../../Zotlabs/Module/Locs.php:54
+msgid "Location not found."
+msgstr "Klon nicht gefunden."
-#: ../../Zotlabs/Module/Register.php:239
-#: ../../Zotlabs/Module/New_channel.php:136
-#, php-format
+#: ../../Zotlabs/Module/Locs.php:62
+msgid "Location lookup failed."
+msgstr "Nachschlagen des Kanal-Ortes fehlgeschlagen"
+
+#: ../../Zotlabs/Module/Locs.php:66
msgid ""
-"Your nickname will be used to create an easy to remember channel address "
-"e.g. nickname%s"
-msgstr "Dein Spitzname wird verwendet, um eine leicht zu merkende Kanal-Adresse (ähnlich einer E-Mail-Adresse) zu erzeugen, die Du mit anderen austauschen kannst, z.B. nickname%s"
+"Please select another location to become primary before removing the primary"
+" location."
+msgstr "Bitte mache einen anderen Kanal-Ort zum primären Ort, bevor Du den primären Ort löschst."
-#: ../../Zotlabs/Module/Register.php:240
-#: ../../Zotlabs/Module/New_channel.php:137
-msgid "Channel role and privacy"
-msgstr "Kanaltyp und Privatspäre-Einstellungen"
+#: ../../Zotlabs/Module/Locs.php:95
+msgid "Syncing locations"
+msgstr "Synchronisiere Klone"
-#: ../../Zotlabs/Module/Register.php:240
-#: ../../Zotlabs/Module/New_channel.php:137
-msgid "Select a channel role with your privacy requirements."
-msgstr "Wähle einen passenden Kanaltyp mit den zugehörigen Voreinstellungen zur Privatsphäre."
+#: ../../Zotlabs/Module/Locs.php:105
+msgid "No locations found."
+msgstr "Keine Klon-Adressen gefunden."
-#: ../../Zotlabs/Module/Register.php:240
-#: ../../Zotlabs/Module/New_channel.php:137
-msgid "Read more about roles"
-msgstr "Mehr Informationen über Rollen"
+#: ../../Zotlabs/Module/Locs.php:116
+msgid "Manage Channel Locations"
+msgstr "Klon-Adressen verwalten"
-#: ../../Zotlabs/Module/Register.php:241
-msgid "no"
-msgstr "nein"
+#: ../../Zotlabs/Module/Locs.php:119 ../../Zotlabs/Module/Admin.php:111
+msgid "Primary"
+msgstr "Primär"
-#: ../../Zotlabs/Module/Register.php:241
-msgid "yes"
-msgstr "ja"
+#: ../../Zotlabs/Module/Locs.php:120 ../../Zotlabs/Module/Menu.php:113
+msgid "Drop"
+msgstr "Löschen"
-#: ../../Zotlabs/Module/Register.php:253
-#: ../../Zotlabs/Module/Admin/Site.php:261
-msgid "Registration"
-msgstr "Registrierung"
+#: ../../Zotlabs/Module/Locs.php:122
+msgid "Sync Now"
+msgstr "Jetzt synchronisieren"
-#: ../../Zotlabs/Module/Register.php:258
-msgid "Membership on this site is by invitation only."
-msgstr "Mitgliedschaft auf dieser Seite ist nur nach vorheriger Einladung möglich."
+#: ../../Zotlabs/Module/Locs.php:123
+msgid "Please wait several minutes between consecutive operations."
+msgstr "Bitte warte mehrere Minuten zwischen dem Ausführen zweier Operationen!"
-#: ../../Zotlabs/Module/Register.php:270 ../../include/nav.php:150
-#: ../../boot.php:1701
-msgid "Register"
-msgstr "Registrieren"
+#: ../../Zotlabs/Module/Locs.php:124
+msgid ""
+"When possible, drop a location by logging into that website/hub and removing"
+" your channel."
+msgstr "Wenn möglich, lösche einen Klon, indem Du Dich auf dem jeweiligen Hub einloggst und den Kanal dort löschst."
-#: ../../Zotlabs/Module/Register.php:271
+#: ../../Zotlabs/Module/Locs.php:125
+msgid "Use this form to drop the location if the hub is no longer operating."
+msgstr "Benutze dieses Formular zum Löschen eines Klons, wenn es den Hub nicht mehr gibt."
+
+#: ../../Zotlabs/Module/Apporder.php:39
+msgid "Change Order of Navigation Apps"
+msgstr "App-Reihenfolge in der Navigation ändern"
+
+#: ../../Zotlabs/Module/Apporder.php:40
msgid ""
-"This site may require email verification after submitting this form. If you "
-"are returned to a login page, please check your email for instructions."
-msgstr "Diese Seite verlangt möglicherweise eine Emailbestätigung nach dem Absenden des Formulars. Wenn Du auf eine Login-Seite zurückgeleitet wirst, prüfe bitte Deinen Posteingang auf neue Mails mit entsprechenden Hinweisen."
+"Use arrows to move the corresponding app up or down in the display list"
+msgstr "Benutze die Pfeiltasten, um die jeweilige App in der Anzeigeliste auf- oder abwärts zu bewegen."
-#: ../../Zotlabs/Module/Probe.php:28 ../../Zotlabs/Module/Probe.php:32
-#, php-format
-msgid "Fetching URL returns error: %1$s"
-msgstr "Abrufen der URL gab einen Fehler zurück: %1$s"
+#: ../../Zotlabs/Module/Mitem.php:28 ../../Zotlabs/Module/Menu.php:144
+msgid "Menu not found."
+msgstr "Menü nicht gefunden"
-#: ../../Zotlabs/Module/Match.php:26
-msgid "Profile Match"
-msgstr "Profil-Übereinstimmungen"
+#: ../../Zotlabs/Module/Mitem.php:52
+msgid "Unable to create element."
+msgstr "Element konnte nicht erstellt werden."
-#: ../../Zotlabs/Module/Match.php:35
-msgid "No keywords to match. Please add keywords to your default profile."
-msgstr "Keine Schlüsselwörter für den Abgleich gefunden. Bitte füge Schlüsselwörter zu Deinem Standardprofil hinzu."
+#: ../../Zotlabs/Module/Mitem.php:76
+msgid "Unable to update menu element."
+msgstr "Kann Menü-Element nicht aktualisieren."
-#: ../../Zotlabs/Module/Match.php:67
-msgid "is interested in:"
-msgstr "interessiert sich für:"
+#: ../../Zotlabs/Module/Mitem.php:92
+msgid "Unable to add menu element."
+msgstr "Kann Menü-Bestandteil nicht hinzufügen."
-#: ../../Zotlabs/Module/Match.php:68 ../../Zotlabs/Module/Directory.php:328
-#: ../../Zotlabs/Module/Suggest.php:56 ../../include/channel.php:1036
-#: ../../include/connections.php:78 ../../include/widgets.php:147
-#: ../../include/widgets.php:184 ../../include/conversation.php:971
-msgid "Connect"
-msgstr "Verbinden"
+#: ../../Zotlabs/Module/Mitem.php:120 ../../Zotlabs/Module/Menu.php:166
+#: ../../Zotlabs/Module/Xchan.php:41
+msgid "Not found."
+msgstr "Nicht gefunden."
-#: ../../Zotlabs/Module/Match.php:74
-msgid "No matches"
-msgstr "Keine Übereinstimmungen"
+#: ../../Zotlabs/Module/Mitem.php:153 ../../Zotlabs/Module/Mitem.php:230
+msgid "Menu Item Permissions"
+msgstr "Zugriffsrechte des Menü-Elements"
-#: ../../Zotlabs/Module/Connedit.php:82
-msgid "Could not access contact record."
-msgstr "Konnte nicht auf den Kontakteintrag zugreifen."
+#: ../../Zotlabs/Module/Mitem.php:154 ../../Zotlabs/Module/Mitem.php:231
+#: ../../Zotlabs/Module/Settings/Channel.php:513
+msgid "(click to open/close)"
+msgstr "(zum öffnen/schließen anklicken)"
-#: ../../Zotlabs/Module/Connedit.php:106
-msgid "Could not locate selected profile."
-msgstr "Gewähltes Profil nicht gefunden."
+#: ../../Zotlabs/Module/Mitem.php:160 ../../Zotlabs/Module/Mitem.php:176
+msgid "Link Name"
+msgstr "Name des Links"
-#: ../../Zotlabs/Module/Connedit.php:258
-msgid "Connection updated."
-msgstr "Verbindung aktualisiert."
+#: ../../Zotlabs/Module/Mitem.php:161 ../../Zotlabs/Module/Mitem.php:239
+msgid "Link or Submenu Target"
+msgstr "Ziel des Links oder Untermenüs"
-#: ../../Zotlabs/Module/Connedit.php:260
-msgid "Failed to update connection record."
-msgstr "Konnte den Verbindungseintrag nicht aktualisieren."
+#: ../../Zotlabs/Module/Mitem.php:161
+msgid "Enter URL of the link or select a menu name to create a submenu"
+msgstr "URL des Links eingeben oder Menünamen wählen, um ein Untermenü anzulegen."
-#: ../../Zotlabs/Module/Connedit.php:310
-msgid "is now connected to"
-msgstr "ist jetzt verbunden mit"
+#: ../../Zotlabs/Module/Mitem.php:162 ../../Zotlabs/Module/Mitem.php:240
+msgid "Use magic-auth if available"
+msgstr "Magic-Auth verwenden, falls verfügbar"
-#: ../../Zotlabs/Module/Connedit.php:411 ../../Zotlabs/Module/Connedit.php:716
-#: ../../Zotlabs/Module/Admin/Site.php:218 ../../Zotlabs/Module/Menu.php:100
-#: ../../Zotlabs/Module/Menu.php:157 ../../Zotlabs/Module/Filestorage.php:160
-#: ../../Zotlabs/Module/Filestorage.php:168 ../../Zotlabs/Module/Mitem.php:162
-#: ../../Zotlabs/Module/Mitem.php:163 ../../Zotlabs/Module/Mitem.php:240
-#: ../../Zotlabs/Module/Mitem.php:241 ../../Zotlabs/Module/Photos.php:653
-#: ../../Zotlabs/Module/Profiles.php:641 ../../Zotlabs/Module/Api.php:97
-#: ../../Zotlabs/Module/Removeme.php:63 ../../Zotlabs/Module/Wiki.php:159
-#: ../../Zotlabs/Module/Settings/Channel.php:289
+#: ../../Zotlabs/Module/Mitem.php:162 ../../Zotlabs/Module/Mitem.php:163
+#: ../../Zotlabs/Module/Mitem.php:240 ../../Zotlabs/Module/Mitem.php:241
+#: ../../Zotlabs/Module/Events.php:470 ../../Zotlabs/Module/Events.php:471
+#: ../../Zotlabs/Module/Removeme.php:63
+#: ../../Zotlabs/Module/Admin/Site.php:237
+#: ../../Zotlabs/Module/Settings/Channel.php:298
#: ../../Zotlabs/Module/Settings/Display.php:103
-#: ../../Zotlabs/Module/Events.php:463 ../../Zotlabs/Module/Events.php:464
-#: ../../extend/addon/addon/dwpost/dwpost.php:73
-#: ../../extend/addon/addon/dwpost/dwpost.php:85
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:120
-#: ../../extend/addon/addon/friendica/dfrn_request.php:865
-#: ../../extend/addon/addon/ijpost/ijpost.php:73
-#: ../../extend/addon/addon/ijpost/ijpost.php:85
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:309
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:313
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:343
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:351
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:355
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:359
-#: ../../extend/addon/addon/libertree/libertree.php:69
-#: ../../extend/addon/addon/libertree/libertree.php:81
-#: ../../extend/addon/addon/ljpost/ljpost.php:70
-#: ../../extend/addon/addon/ljpost/ljpost.php:82
-#: ../../extend/addon/addon/nofed/nofed.php:72
-#: ../../extend/addon/addon/nofed/nofed.php:76
-#: ../../extend/addon/addon/nsabait/nsabait.php:157
-#: ../../extend/addon/addon/nsfw/nsfw.php:84
-#: ../../extend/addon/addon/planets/planets.php:153
-#: ../../extend/addon/addon/pumpio/pumpio.php:219
-#: ../../extend/addon/addon/pumpio/pumpio.php:223
-#: ../../extend/addon/addon/pumpio/pumpio.php:227
-#: ../../extend/addon/addon/pumpio/pumpio.php:231
-#: ../../extend/addon/addon/rainbowtag/rainbowtag.php:81
-#: ../../extend/addon/addon/redred/redred.php:95
-#: ../../extend/addon/addon/redred/redred.php:99
-#: ../../extend/addon/addon/rtof/rtof.php:81
-#: ../../extend/addon/addon/rtof/rtof.php:85
-#: ../../extend/addon/addon/smileybutton/smileybutton.php:273
-#: ../../extend/addon/addon/smileybutton/smileybutton.php:277
-#: ../../extend/addon/addon/statusnet/statusnet.php:389
-#: ../../extend/addon/addon/statusnet/statusnet.php:411
-#: ../../extend/addon/addon/statusnet/statusnet.php:415
-#: ../../extend/addon/addon/statusnet/statusnet.php:424
-#: ../../extend/addon/addon/twitter/twitter.php:242
-#: ../../extend/addon/addon/twitter/twitter.php:246
-#: ../../extend/addon/addon/twitter/twitter.php:255
-#: ../../extend/addon/addon/visage/visage.php:166
-#: ../../extend/addon/addon/wppost/wppost.php:82
-#: ../../extend/addon/addon/wppost/wppost.php:105
-#: ../../extend/addon/addon/wppost/wppost.php:109
-#: ../../extend/addon/addon/xmpp/xmpp.php:53
-#: ../../extend/addon/addon/cdav/cdav.php:234 ../../include/dir_fns.php:143
-#: ../../include/dir_fns.php:144 ../../include/dir_fns.php:145
-#: ../../include/widgets.php:978 ../../view/theme/redbasic/php/config.php:111
-#: ../../view/theme/redbasic/php/config.php:136 ../../boot.php:1723
+#: ../../Zotlabs/Module/Api.php:97 ../../Zotlabs/Module/Photos.php:644
+#: ../../Zotlabs/Module/Wiki.php:218 ../../Zotlabs/Module/Wiki.php:219
+#: ../../Zotlabs/Module/Connedit.php:396 ../../Zotlabs/Module/Connedit.php:779
+#: ../../Zotlabs/Module/Menu.php:100 ../../Zotlabs/Module/Menu.php:157
+#: ../../Zotlabs/Module/Profiles.php:681
+#: ../../Zotlabs/Module/Filestorage.php:150
+#: ../../Zotlabs/Module/Filestorage.php:158
+#: ../../Zotlabs/Storage/Browser.php:351 ../../boot.php:1644
+#: ../../view/theme/redbasic_c/php/config.php:100
+#: ../../view/theme/redbasic_c/php/config.php:115
+#: ../../view/theme/redbasic/php/config.php:98
+#: ../../addon/planets/planets.php:149 ../../addon/wppost/wppost.php:82
+#: ../../addon/wppost/wppost.php:105 ../../addon/wppost/wppost.php:109
+#: ../../addon/nsfw/nsfw.php:84 ../../addon/ijpost/ijpost.php:73
+#: ../../addon/ijpost/ijpost.php:85 ../../addon/dwpost/dwpost.php:73
+#: ../../addon/dwpost/dwpost.php:85 ../../addon/ljpost/ljpost.php:70
+#: ../../addon/ljpost/ljpost.php:82 ../../addon/gitwiki/Mod_Gitwiki.php:166
+#: ../../addon/rainbowtag/rainbowtag.php:81 ../../addon/visage/visage.php:166
+#: ../../addon/nsabait/nsabait.php:157 ../../addon/rtof/rtof.php:81
+#: ../../addon/rtof/rtof.php:85 ../../addon/jappixmini/jappixmini.php:309
+#: ../../addon/jappixmini/jappixmini.php:313
+#: ../../addon/jappixmini/jappixmini.php:343
+#: ../../addon/jappixmini/jappixmini.php:351
+#: ../../addon/jappixmini/jappixmini.php:355
+#: ../../addon/jappixmini/jappixmini.php:359 ../../addon/nofed/nofed.php:72
+#: ../../addon/nofed/nofed.php:76 ../../addon/redred/redred.php:95
+#: ../../addon/redred/redred.php:99 ../../addon/libertree/libertree.php:69
+#: ../../addon/libertree/libertree.php:81
+#: ../../addon/flattrwidget/flattrwidget.php:120
+#: ../../addon/statusnet/statusnet.php:389
+#: ../../addon/statusnet/statusnet.php:411
+#: ../../addon/statusnet/statusnet.php:415
+#: ../../addon/statusnet/statusnet.php:424 ../../addon/twitter/twitter.php:242
+#: ../../addon/twitter/twitter.php:246 ../../addon/twitter/twitter.php:255
+#: ../../addon/smileybutton/smileybutton.php:211
+#: ../../addon/smileybutton/smileybutton.php:215
+#: ../../addon/authchoose/authchoose.php:67 ../../addon/xmpp/xmpp.php:53
+#: ../../addon/pumpio/pumpio.php:219 ../../addon/pumpio/pumpio.php:223
+#: ../../addon/pumpio/pumpio.php:227 ../../addon/pumpio/pumpio.php:231
+#: ../../include/dir_fns.php:143 ../../include/dir_fns.php:144
+#: ../../include/dir_fns.php:145
msgid "No"
msgstr "Nein"
-#: ../../Zotlabs/Module/Connedit.php:411
-#: ../../Zotlabs/Module/Admin/Site.php:220 ../../Zotlabs/Module/Menu.php:100
-#: ../../Zotlabs/Module/Menu.php:157 ../../Zotlabs/Module/Filestorage.php:160
-#: ../../Zotlabs/Module/Filestorage.php:168 ../../Zotlabs/Module/Mitem.php:162
-#: ../../Zotlabs/Module/Mitem.php:163 ../../Zotlabs/Module/Mitem.php:240
-#: ../../Zotlabs/Module/Mitem.php:241 ../../Zotlabs/Module/Photos.php:653
-#: ../../Zotlabs/Module/Profiles.php:641 ../../Zotlabs/Module/Api.php:96
-#: ../../Zotlabs/Module/Removeme.php:63 ../../Zotlabs/Module/Wiki.php:159
-#: ../../Zotlabs/Module/Settings/Channel.php:289
+#: ../../Zotlabs/Module/Mitem.php:162 ../../Zotlabs/Module/Mitem.php:163
+#: ../../Zotlabs/Module/Mitem.php:240 ../../Zotlabs/Module/Mitem.php:241
+#: ../../Zotlabs/Module/Events.php:470 ../../Zotlabs/Module/Events.php:471
+#: ../../Zotlabs/Module/Removeme.php:63
+#: ../../Zotlabs/Module/Admin/Site.php:239
+#: ../../Zotlabs/Module/Settings/Channel.php:298
#: ../../Zotlabs/Module/Settings/Display.php:103
-#: ../../Zotlabs/Module/Events.php:463 ../../Zotlabs/Module/Events.php:464
-#: ../../extend/addon/addon/dwpost/dwpost.php:73
-#: ../../extend/addon/addon/dwpost/dwpost.php:85
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:120
-#: ../../extend/addon/addon/friendica/dfrn_request.php:865
-#: ../../extend/addon/addon/ijpost/ijpost.php:73
-#: ../../extend/addon/addon/ijpost/ijpost.php:85
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:309
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:313
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:343
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:351
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:355
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:359
-#: ../../extend/addon/addon/libertree/libertree.php:69
-#: ../../extend/addon/addon/libertree/libertree.php:81
-#: ../../extend/addon/addon/ljpost/ljpost.php:70
-#: ../../extend/addon/addon/ljpost/ljpost.php:82
-#: ../../extend/addon/addon/nofed/nofed.php:72
-#: ../../extend/addon/addon/nofed/nofed.php:76
-#: ../../extend/addon/addon/nsabait/nsabait.php:157
-#: ../../extend/addon/addon/nsfw/nsfw.php:84
-#: ../../extend/addon/addon/planets/planets.php:153
-#: ../../extend/addon/addon/pumpio/pumpio.php:219
-#: ../../extend/addon/addon/pumpio/pumpio.php:223
-#: ../../extend/addon/addon/pumpio/pumpio.php:227
-#: ../../extend/addon/addon/pumpio/pumpio.php:231
-#: ../../extend/addon/addon/rainbowtag/rainbowtag.php:81
-#: ../../extend/addon/addon/redred/redred.php:95
-#: ../../extend/addon/addon/redred/redred.php:99
-#: ../../extend/addon/addon/rtof/rtof.php:81
-#: ../../extend/addon/addon/rtof/rtof.php:85
-#: ../../extend/addon/addon/smileybutton/smileybutton.php:273
-#: ../../extend/addon/addon/smileybutton/smileybutton.php:277
-#: ../../extend/addon/addon/statusnet/statusnet.php:389
-#: ../../extend/addon/addon/statusnet/statusnet.php:411
-#: ../../extend/addon/addon/statusnet/statusnet.php:415
-#: ../../extend/addon/addon/statusnet/statusnet.php:424
-#: ../../extend/addon/addon/twitter/twitter.php:242
-#: ../../extend/addon/addon/twitter/twitter.php:246
-#: ../../extend/addon/addon/twitter/twitter.php:255
-#: ../../extend/addon/addon/visage/visage.php:166
-#: ../../extend/addon/addon/wppost/wppost.php:82
-#: ../../extend/addon/addon/wppost/wppost.php:105
-#: ../../extend/addon/addon/wppost/wppost.php:109
-#: ../../extend/addon/addon/xmpp/xmpp.php:53
-#: ../../extend/addon/addon/cdav/cdav.php:234 ../../include/dir_fns.php:143
-#: ../../include/dir_fns.php:144 ../../include/dir_fns.php:145
-#: ../../include/widgets.php:978 ../../view/theme/redbasic/php/config.php:111
-#: ../../view/theme/redbasic/php/config.php:136 ../../boot.php:1723
+#: ../../Zotlabs/Module/Api.php:96 ../../Zotlabs/Module/Photos.php:644
+#: ../../Zotlabs/Module/Wiki.php:218 ../../Zotlabs/Module/Wiki.php:219
+#: ../../Zotlabs/Module/Connedit.php:396 ../../Zotlabs/Module/Menu.php:100
+#: ../../Zotlabs/Module/Menu.php:157 ../../Zotlabs/Module/Profiles.php:681
+#: ../../Zotlabs/Module/Filestorage.php:150
+#: ../../Zotlabs/Module/Filestorage.php:158
+#: ../../Zotlabs/Storage/Browser.php:351 ../../boot.php:1644
+#: ../../view/theme/redbasic_c/php/config.php:100
+#: ../../view/theme/redbasic_c/php/config.php:115
+#: ../../view/theme/redbasic/php/config.php:98
+#: ../../addon/planets/planets.php:149 ../../addon/wppost/wppost.php:82
+#: ../../addon/wppost/wppost.php:105 ../../addon/wppost/wppost.php:109
+#: ../../addon/nsfw/nsfw.php:84 ../../addon/ijpost/ijpost.php:73
+#: ../../addon/ijpost/ijpost.php:85 ../../addon/dwpost/dwpost.php:73
+#: ../../addon/dwpost/dwpost.php:85 ../../addon/ljpost/ljpost.php:70
+#: ../../addon/ljpost/ljpost.php:82 ../../addon/gitwiki/Mod_Gitwiki.php:166
+#: ../../addon/rainbowtag/rainbowtag.php:81 ../../addon/visage/visage.php:166
+#: ../../addon/nsabait/nsabait.php:157 ../../addon/rtof/rtof.php:81
+#: ../../addon/rtof/rtof.php:85 ../../addon/jappixmini/jappixmini.php:309
+#: ../../addon/jappixmini/jappixmini.php:313
+#: ../../addon/jappixmini/jappixmini.php:343
+#: ../../addon/jappixmini/jappixmini.php:351
+#: ../../addon/jappixmini/jappixmini.php:355
+#: ../../addon/jappixmini/jappixmini.php:359 ../../addon/nofed/nofed.php:72
+#: ../../addon/nofed/nofed.php:76 ../../addon/redred/redred.php:95
+#: ../../addon/redred/redred.php:99 ../../addon/libertree/libertree.php:69
+#: ../../addon/libertree/libertree.php:81
+#: ../../addon/flattrwidget/flattrwidget.php:120
+#: ../../addon/statusnet/statusnet.php:389
+#: ../../addon/statusnet/statusnet.php:411
+#: ../../addon/statusnet/statusnet.php:415
+#: ../../addon/statusnet/statusnet.php:424 ../../addon/twitter/twitter.php:242
+#: ../../addon/twitter/twitter.php:246 ../../addon/twitter/twitter.php:255
+#: ../../addon/smileybutton/smileybutton.php:211
+#: ../../addon/smileybutton/smileybutton.php:215
+#: ../../addon/authchoose/authchoose.php:67 ../../addon/xmpp/xmpp.php:53
+#: ../../addon/pumpio/pumpio.php:219 ../../addon/pumpio/pumpio.php:223
+#: ../../addon/pumpio/pumpio.php:227 ../../addon/pumpio/pumpio.php:231
+#: ../../include/dir_fns.php:143 ../../include/dir_fns.php:144
+#: ../../include/dir_fns.php:145
msgid "Yes"
msgstr "Ja"
-#: ../../Zotlabs/Module/Connedit.php:443
-msgid "Could not access address book record."
-msgstr "Konnte nicht auf den Adressbuch-Eintrag zugreifen."
+#: ../../Zotlabs/Module/Mitem.php:163 ../../Zotlabs/Module/Mitem.php:241
+msgid "Open link in new window"
+msgstr "Öffne Link in neuem Fenster"
-#: ../../Zotlabs/Module/Connedit.php:463
-msgid "Refresh failed - channel is currently unavailable."
-msgstr "Aktualisierung fehlgeschlagen – der Kanal ist im Moment nicht erreichbar."
+#: ../../Zotlabs/Module/Mitem.php:164 ../../Zotlabs/Module/Mitem.php:242
+msgid "Order in list"
+msgstr "Reihenfolge in der Liste"
-#: ../../Zotlabs/Module/Connedit.php:478 ../../Zotlabs/Module/Connedit.php:487
-#: ../../Zotlabs/Module/Connedit.php:496 ../../Zotlabs/Module/Connedit.php:505
-#: ../../Zotlabs/Module/Connedit.php:518
-msgid "Unable to set address book parameters."
-msgstr "Konnte die Adressbuch-Parameter nicht setzen."
+#: ../../Zotlabs/Module/Mitem.php:164 ../../Zotlabs/Module/Mitem.php:242
+msgid "Higher numbers will sink to bottom of listing"
+msgstr "Größere Nummern werden weiter unten in der Auflistung einsortiert"
-#: ../../Zotlabs/Module/Connedit.php:542
-msgid "Connection has been removed."
-msgstr "Verbindung wurde gelöscht."
+#: ../../Zotlabs/Module/Mitem.php:165
+msgid "Submit and finish"
+msgstr "Absenden und fertigstellen"
-#: ../../Zotlabs/Module/Connedit.php:582 ../../Zotlabs/Lib/Apps.php:221
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:56
-#: ../../include/nav.php:89 ../../include/conversation.php:969
-msgid "View Profile"
-msgstr "Profil ansehen"
+#: ../../Zotlabs/Module/Mitem.php:166
+msgid "Submit and continue"
+msgstr "Absenden und fortfahren"
-#: ../../Zotlabs/Module/Connedit.php:585
-#, php-format
-msgid "View %s's profile"
-msgstr "%ss Profil ansehen"
+#: ../../Zotlabs/Module/Mitem.php:174
+msgid "Menu:"
+msgstr "Menü:"
-#: ../../Zotlabs/Module/Connedit.php:589
-msgid "Refresh Permissions"
-msgstr "Zugriffsrechte neu laden"
+#: ../../Zotlabs/Module/Mitem.php:177
+msgid "Link Target"
+msgstr "Ziel des Links"
-#: ../../Zotlabs/Module/Connedit.php:592
-msgid "Fetch updated permissions"
-msgstr "Aktualisierte Zugriffsrechte abfragen"
+#: ../../Zotlabs/Module/Mitem.php:180
+msgid "Edit menu"
+msgstr "Menü bearbeiten"
-#: ../../Zotlabs/Module/Connedit.php:596
-msgid "Recent Activity"
-msgstr "Kürzliche Aktivitäten"
+#: ../../Zotlabs/Module/Mitem.php:183
+msgid "Edit element"
+msgstr "Bestandteil bearbeiten"
-#: ../../Zotlabs/Module/Connedit.php:599
-msgid "View recent posts and comments"
-msgstr "Betrachte die neuesten Beiträge und Kommentare"
+#: ../../Zotlabs/Module/Mitem.php:184
+msgid "Drop element"
+msgstr "Bestandteil löschen"
-#: ../../Zotlabs/Module/Connedit.php:603
-#: ../../Zotlabs/Module/Admin/Accounts.php:175
-msgid "Unblock"
-msgstr "Freigeben"
+#: ../../Zotlabs/Module/Mitem.php:185
+msgid "New element"
+msgstr "Neues Bestandteil"
-#: ../../Zotlabs/Module/Connedit.php:603
-#: ../../Zotlabs/Module/Admin/Accounts.php:174
-msgid "Block"
-msgstr "Blockieren"
+#: ../../Zotlabs/Module/Mitem.php:186
+msgid "Edit this menu container"
+msgstr "Diesen Menü-Container bearbeiten"
-#: ../../Zotlabs/Module/Connedit.php:606
-msgid "Block (or Unblock) all communications with this connection"
-msgstr "Jegliche Kommunikation mit dieser Verbindung blockieren/zulassen"
+#: ../../Zotlabs/Module/Mitem.php:187
+msgid "Add menu element"
+msgstr "Menüelement hinzufügen"
-#: ../../Zotlabs/Module/Connedit.php:607
-msgid "This connection is blocked!"
-msgstr "Die Verbindung ist geblockt!"
+#: ../../Zotlabs/Module/Mitem.php:188
+msgid "Delete this menu item"
+msgstr "Lösche dieses Menü-Bestandteil"
-#: ../../Zotlabs/Module/Connedit.php:611
-msgid "Unignore"
-msgstr "Nicht ignorieren"
+#: ../../Zotlabs/Module/Mitem.php:189
+msgid "Edit this menu item"
+msgstr "Bearbeite dieses Menü-Bestandteil"
-#: ../../Zotlabs/Module/Connedit.php:611
-#: ../../Zotlabs/Module/Connections.php:277
-msgid "Ignore"
-msgstr "Ignorieren"
+#: ../../Zotlabs/Module/Mitem.php:206
+msgid "Menu item not found."
+msgstr "Menü-Bestandteil nicht gefunden."
-#: ../../Zotlabs/Module/Connedit.php:614
-msgid "Ignore (or Unignore) all inbound communications from this connection"
-msgstr "Jegliche eingehende Kommunikation von dieser Verbindung ignorieren/zulassen"
+#: ../../Zotlabs/Module/Mitem.php:219
+msgid "Menu item deleted."
+msgstr "Menü-Bestandteil gelöscht."
-#: ../../Zotlabs/Module/Connedit.php:615
-msgid "This connection is ignored!"
-msgstr "Die Verbindung wird ignoriert!"
+#: ../../Zotlabs/Module/Mitem.php:221
+msgid "Menu item could not be deleted."
+msgstr "Menü-Bestandteil kann nicht gelöscht werden."
-#: ../../Zotlabs/Module/Connedit.php:619
-msgid "Unarchive"
-msgstr "Aus Archiv zurückholen"
+#: ../../Zotlabs/Module/Mitem.php:228
+msgid "Edit Menu Element"
+msgstr "Bearbeite Menü-Bestandteil"
-#: ../../Zotlabs/Module/Connedit.php:619
-msgid "Archive"
-msgstr "Archivieren"
+#: ../../Zotlabs/Module/Mitem.php:238
+msgid "Link text"
+msgstr "Link Text"
-#: ../../Zotlabs/Module/Connedit.php:622
+#: ../../Zotlabs/Module/Events.php:25
+msgid "Calendar entries imported."
+msgstr "Kalendereinträge wurden importiert."
+
+#: ../../Zotlabs/Module/Events.php:27
+msgid "No calendar entries found."
+msgstr "Keine Kalendereinträge gefunden."
+
+#: ../../Zotlabs/Module/Events.php:110
+msgid "Event can not end before it has started."
+msgstr "Termin-Ende liegt vor dem Beginn."
+
+#: ../../Zotlabs/Module/Events.php:112 ../../Zotlabs/Module/Events.php:121
+#: ../../Zotlabs/Module/Events.php:143
+msgid "Unable to generate preview."
+msgstr "Vorschau konnte nicht erzeugt werden."
+
+#: ../../Zotlabs/Module/Events.php:119
+msgid "Event title and start time are required."
+msgstr "Titel und Startzeit des Termins sind erforderlich."
+
+#: ../../Zotlabs/Module/Events.php:141 ../../Zotlabs/Module/Events.php:265
+msgid "Event not found."
+msgstr "Termin nicht gefunden."
+
+#: ../../Zotlabs/Module/Events.php:260 ../../Zotlabs/Module/Tagger.php:51
+#: ../../Zotlabs/Module/Like.php:372 ../../include/conversation.php:119
+#: ../../include/text.php:1941 ../../include/event.php:1145
+msgid "event"
+msgstr "Termin"
+
+#: ../../Zotlabs/Module/Events.php:460
+msgid "Edit event title"
+msgstr "Termintitel bearbeiten"
+
+#: ../../Zotlabs/Module/Events.php:460 ../../Zotlabs/Module/Events.php:465
+#: ../../Zotlabs/Module/Appman.php:136 ../../Zotlabs/Module/Appman.php:137
+#: ../../Zotlabs/Module/Profiles.php:748 ../../Zotlabs/Module/Profiles.php:752
+#: ../../include/datetime.php:259
+msgid "Required"
+msgstr "Benötigt"
+
+#: ../../Zotlabs/Module/Events.php:462
+msgid "Categories (comma-separated list)"
+msgstr "Kategorien (Kommagetrennte Liste)"
+
+#: ../../Zotlabs/Module/Events.php:463
+msgid "Edit Category"
+msgstr "Kategorie bearbeiten"
+
+#: ../../Zotlabs/Module/Events.php:463
+msgid "Category"
+msgstr "Kategorie"
+
+#: ../../Zotlabs/Module/Events.php:466
+msgid "Edit start date and time"
+msgstr "Startdatum und -zeit bearbeiten"
+
+#: ../../Zotlabs/Module/Events.php:467 ../../Zotlabs/Module/Events.php:470
+msgid "Finish date and time are not known or not relevant"
+msgstr "Enddatum und -zeit sind unbekannt oder irrelevant"
+
+#: ../../Zotlabs/Module/Events.php:469
+msgid "Edit finish date and time"
+msgstr "Enddatum und -zeit bearbeiten"
+
+#: ../../Zotlabs/Module/Events.php:469
+msgid "Finish date and time"
+msgstr "Enddatum und -zeit"
+
+#: ../../Zotlabs/Module/Events.php:471 ../../Zotlabs/Module/Events.php:472
+msgid "Adjust for viewer timezone"
+msgstr "An die Zeitzone des Betrachters anpassen"
+
+#: ../../Zotlabs/Module/Events.php:471
msgid ""
-"Archive (or Unarchive) this connection - mark channel dead but keep content"
-msgstr "Verbindung archivieren/aus dem Archiv zurückholen (Archiv = Kanal als erloschen markieren, aber die Beiträge behalten)"
+"Important for events that happen in a particular place. Not practical for "
+"global holidays."
+msgstr "Wichtig für Veranstaltungen die an bestimmten Orten stattfinden. Nicht sinnvoll für globale Feiertage / Ferien."
-#: ../../Zotlabs/Module/Connedit.php:623
-msgid "This connection is archived!"
-msgstr "Die Verbindung ist archiviert!"
+#: ../../Zotlabs/Module/Events.php:473
+msgid "Edit Description"
+msgstr "Beschreibung bearbeiten"
-#: ../../Zotlabs/Module/Connedit.php:627
-msgid "Unhide"
-msgstr "Wieder sichtbar machen"
+#: ../../Zotlabs/Module/Events.php:475
+msgid "Edit Location"
+msgstr "Ort bearbeiten"
-#: ../../Zotlabs/Module/Connedit.php:627
-msgid "Hide"
-msgstr "Verstecken"
+#: ../../Zotlabs/Module/Events.php:478 ../../Zotlabs/Module/Photos.php:1070
+#: ../../Zotlabs/Module/Webpages.php:247 ../../Zotlabs/Lib/ThreadItem.php:753
+#: ../../include/conversation.php:1313
+msgid "Preview"
+msgstr "Vorschau"
-#: ../../Zotlabs/Module/Connedit.php:630
-msgid "Hide or Unhide this connection from your other connections"
-msgstr "Diese Verbindung vor anderen Verbindungen verstecken/zeigen"
+#: ../../Zotlabs/Module/Events.php:479 ../../include/conversation.php:1385
+msgid "Permission settings"
+msgstr "Berechtigungs-Einstellungen"
-#: ../../Zotlabs/Module/Connedit.php:631
-msgid "This connection is hidden!"
-msgstr "Die Verbindung ist versteckt!"
+#: ../../Zotlabs/Module/Events.php:489
+msgid "Timezone:"
+msgstr "Zeitzone:"
-#: ../../Zotlabs/Module/Connedit.php:638
-msgid "Delete this connection"
-msgstr "Verbindung löschen"
+#: ../../Zotlabs/Module/Events.php:494
+msgid "Advanced Options"
+msgstr "Weitere Optionen"
-#: ../../Zotlabs/Module/Connedit.php:655 ../../include/widgets.php:529
-msgid "Me"
-msgstr "Ich"
+#: ../../Zotlabs/Module/Events.php:605 ../../Zotlabs/Module/Cal.php:264
+msgid "l, F j"
+msgstr "l, j. F"
-#: ../../Zotlabs/Module/Connedit.php:656 ../../include/widgets.php:530
-msgid "Family"
-msgstr "Familie"
+#: ../../Zotlabs/Module/Events.php:633
+msgid "Edit event"
+msgstr "Termin bearbeiten"
-#: ../../Zotlabs/Module/Connedit.php:657
-#: ../../Zotlabs/Module/Settings/Channel.php:61
-#: ../../Zotlabs/Module/Settings/Channel.php:65
-#: ../../Zotlabs/Module/Settings/Channel.php:66
-#: ../../Zotlabs/Module/Settings/Channel.php:69
-#: ../../Zotlabs/Module/Settings/Channel.php:80
-#: ../../include/selectors.php:123 ../../include/channel.php:402
-#: ../../include/channel.php:403 ../../include/channel.php:410
-#: ../../include/widgets.php:531
-msgid "Friends"
-msgstr "Freunde"
+#: ../../Zotlabs/Module/Events.php:635
+msgid "Delete event"
+msgstr "Termin löschen"
-#: ../../Zotlabs/Module/Connedit.php:658 ../../include/widgets.php:532
-msgid "Acquaintances"
-msgstr "Bekannte"
+#: ../../Zotlabs/Module/Events.php:660 ../../Zotlabs/Module/Cal.php:313
+#: ../../include/text.php:1760
+msgid "Link to Source"
+msgstr "Link zur Quelle"
-#: ../../Zotlabs/Module/Connedit.php:659
-#: ../../Zotlabs/Module/Connections.php:92
-#: ../../Zotlabs/Module/Connections.php:107 ../../include/widgets.php:533
-msgid "All"
-msgstr "Alle"
+#: ../../Zotlabs/Module/Events.php:669
+msgid "calendar"
+msgstr "Kalender"
-#: ../../Zotlabs/Module/Connedit.php:716
-msgid "Approve this connection"
-msgstr "Verbindung genehmigen"
+#: ../../Zotlabs/Module/Events.php:688 ../../Zotlabs/Module/Cal.php:336
+msgid "Edit Event"
+msgstr "Termin bearbeiten"
-#: ../../Zotlabs/Module/Connedit.php:716
-msgid "Accept connection to allow communication"
-msgstr "Akzeptiere die Verbindung, um Kommunikation zu ermöglichen"
+#: ../../Zotlabs/Module/Events.php:688 ../../Zotlabs/Module/Cal.php:336
+msgid "Create Event"
+msgstr "Termin anlegen"
-#: ../../Zotlabs/Module/Connedit.php:721
-msgid "Set Affinity"
-msgstr "Beziehung festlegen"
+#: ../../Zotlabs/Module/Events.php:691 ../../Zotlabs/Module/Cal.php:339
+#: ../../include/channel.php:1588
+msgid "Export"
+msgstr "Exportieren"
-#: ../../Zotlabs/Module/Connedit.php:724
-msgid "Set Profile"
-msgstr "Profil festlegen"
+#: ../../Zotlabs/Module/Events.php:731
+msgid "Event removed"
+msgstr "Termin gelöscht"
-#: ../../Zotlabs/Module/Connedit.php:727
-msgid "Set Affinity & Profile"
-msgstr "Beziehung und Profile festlegen"
+#: ../../Zotlabs/Module/Events.php:734
+msgid "Failed to remove event"
+msgstr "Termin konnte nicht gelöscht werden"
-#: ../../Zotlabs/Module/Connedit.php:776
-msgid "none"
-msgstr "Keine"
+#: ../../Zotlabs/Module/Appman.php:38 ../../Zotlabs/Module/Appman.php:55
+msgid "App installed."
+msgstr "App installiert."
-#: ../../Zotlabs/Module/Connedit.php:780 ../../include/widgets.php:656
-msgid "Connection Default Permissions"
-msgstr "Standardzugriffsrechte für neue Verbindungen:"
+#: ../../Zotlabs/Module/Appman.php:48
+msgid "Malformed app."
+msgstr "Fehlerhafte App."
-#: ../../Zotlabs/Module/Connedit.php:780 ../../include/items.php:3909
-#, php-format
-msgid "Connection: %s"
-msgstr "Verbindung: %s"
+#: ../../Zotlabs/Module/Appman.php:125
+msgid "Embed code"
+msgstr "Code einbetten"
-#: ../../Zotlabs/Module/Connedit.php:781
-msgid "Apply these permissions automatically"
-msgstr "Diese Berechtigungen automatisch anwenden"
+#: ../../Zotlabs/Module/Appman.php:131
+msgid "Edit App"
+msgstr "App bearbeiten"
-#: ../../Zotlabs/Module/Connedit.php:781
-msgid "Connection requests will be approved without your interaction"
-msgstr "Verbindungsanfragen werden sofort bestätigt, ohne dass Deine aktive Zustimmung erforderlich ist."
+#: ../../Zotlabs/Module/Appman.php:131
+msgid "Create App"
+msgstr "App erstellen"
-#: ../../Zotlabs/Module/Connedit.php:784
-msgid "This connection's primary address is"
-msgstr "Die Hauptadresse der Verbindung ist"
+#: ../../Zotlabs/Module/Appman.php:136
+msgid "Name of app"
+msgstr "Name der App"
-#: ../../Zotlabs/Module/Connedit.php:785
-msgid "Available locations:"
-msgstr "Verfügbare Klone:"
+#: ../../Zotlabs/Module/Appman.php:137
+msgid "Location (URL) of app"
+msgstr "Ort (URL) der App"
-#: ../../Zotlabs/Module/Connedit.php:789
-msgid ""
-"The permissions indicated on this page will be applied to all new "
-"connections."
-msgstr "Die auf dieser Seite angegebenen Berechtigungen werden auf alle neuen Verbindungen angewendet."
+#: ../../Zotlabs/Module/Appman.php:139
+msgid "Photo icon URL"
+msgstr "URL zum Icon"
-#: ../../Zotlabs/Module/Connedit.php:790
-msgid "Connection Tools"
-msgstr "Verbindungswerkzeuge"
+#: ../../Zotlabs/Module/Appman.php:139
+msgid "80 x 80 pixels - optional"
+msgstr "80 x 80 Pixel – optional"
-#: ../../Zotlabs/Module/Connedit.php:792
-msgid "Slide to adjust your degree of friendship"
-msgstr "Verschieben, um den Grad der Freundschaft zu einzustellen"
+#: ../../Zotlabs/Module/Appman.php:140
+msgid "Categories (optional, comma separated list)"
+msgstr "Kategorien (optional, kommagetrennte Liste)"
-#: ../../Zotlabs/Module/Connedit.php:793 ../../Zotlabs/Module/Rate.php:155
-#: ../../include/js_strings.php:20
-msgid "Rating"
-msgstr "Bewertung"
+#: ../../Zotlabs/Module/Appman.php:141
+msgid "Version ID"
+msgstr "Versions-ID"
-#: ../../Zotlabs/Module/Connedit.php:794
-msgid "Slide to adjust your rating"
-msgstr "Verschieben, um Deine Bewertung einzustellen"
+#: ../../Zotlabs/Module/Appman.php:142
+msgid "Price of app"
+msgstr "Preis der App"
-#: ../../Zotlabs/Module/Connedit.php:795 ../../Zotlabs/Module/Connedit.php:800
-msgid "Optionally explain your rating"
-msgstr "Optional kannst Du Deine Bewertung begründen"
+#: ../../Zotlabs/Module/Appman.php:143
+msgid "Location (URL) to purchase app"
+msgstr "Ort (URL), um die App zu kaufen"
-#: ../../Zotlabs/Module/Connedit.php:797
-msgid "Custom Filter"
-msgstr "Benutzerdefinierter Filter"
+#: ../../Zotlabs/Module/Regmod.php:15
+msgid "Please login."
+msgstr "Bitte melde dich an."
-#: ../../Zotlabs/Module/Connedit.php:798
-msgid "Only import posts with this text"
-msgstr "Nur Beiträge mit diesem Text importieren"
+#: ../../Zotlabs/Module/Magic.php:72
+msgid "Hub not found."
+msgstr "Server nicht gefunden."
+
+#: ../../Zotlabs/Module/Subthread.php:87 ../../Zotlabs/Module/Tagger.php:47
+#: ../../Zotlabs/Module/Like.php:370
+#: ../../addon/redphotos/redphotohelper.php:71
+#: ../../addon/diaspora/Receiver.php:1424 ../../addon/pubcrawl/as.php:1288
+#: ../../include/conversation.php:116 ../../include/text.php:1938
+msgid "photo"
+msgstr "Foto"
+
+#: ../../Zotlabs/Module/Subthread.php:87 ../../Zotlabs/Module/Like.php:370
+#: ../../addon/diaspora/Receiver.php:1424 ../../addon/pubcrawl/as.php:1288
+#: ../../include/conversation.php:144 ../../include/text.php:1944
+msgid "status"
+msgstr "Status"
-#: ../../Zotlabs/Module/Connedit.php:798 ../../Zotlabs/Module/Connedit.php:799
+#: ../../Zotlabs/Module/Subthread.php:118
+#, php-format
+msgid "%1$s is following %2$s's %3$s"
+msgstr "%1$s folgt nun %2$ss %3$s"
+
+#: ../../Zotlabs/Module/Subthread.php:120
+#, php-format
+msgid "%1$s stopped following %2$s's %3$s"
+msgstr "%1$s folgt %2$ss %3$s nicht mehr"
+
+#: ../../Zotlabs/Module/Import_items.php:48 ../../Zotlabs/Module/Import.php:64
+msgid "Nothing to import."
+msgstr "Nichts zu importieren."
+
+#: ../../Zotlabs/Module/Import_items.php:72 ../../Zotlabs/Module/Import.php:79
+#: ../../Zotlabs/Module/Import.php:95
+msgid "Unable to download data from old server"
+msgstr "Daten können vom alten Server nicht heruntergeladen werden"
+
+#: ../../Zotlabs/Module/Import_items.php:77
+#: ../../Zotlabs/Module/Import.php:102
+msgid "Imported file is empty."
+msgstr "Die importierte Datei ist leer."
+
+#: ../../Zotlabs/Module/Import_items.php:93
+#: ../../Zotlabs/Module/Import.php:121
+#, php-format
+msgid "Warning: Database versions differ by %1$d updates."
+msgstr "Achtung: Datenbankversionen unterscheiden sich um %1$d Aktualisierungen."
+
+#: ../../Zotlabs/Module/Import_items.php:108
+msgid "Import completed"
+msgstr "Import abgeschlossen"
+
+#: ../../Zotlabs/Module/Import_items.php:125
+msgid "Import Items"
+msgstr "Beiträge importieren"
+
+#: ../../Zotlabs/Module/Import_items.php:126
msgid ""
-"words one per line or #tags or /patterns/ or lang=xx, leave blank to import "
-"all posts"
-msgstr "Einzelne Wörter pro Zeile, #Tags oder /Reguläre Ausdrücke/. lang=xx (z.B. lang=de) ermöglicht Filterung nach Sprache. Leer lassen, um alle Beiträge zu importieren."
+"Use this form to import existing posts and content from an export file."
+msgstr "Mit diesem Formular kannst Du existierende Beiträge und Inhalte aus einer Sicherungsdatei importieren."
-#: ../../Zotlabs/Module/Connedit.php:799
-msgid "Do not import posts with this text"
-msgstr "Beiträge mit diesem Text nicht importieren"
+#: ../../Zotlabs/Module/Import_items.php:127
+#: ../../Zotlabs/Module/Import.php:516
+msgid "File to Upload"
+msgstr "Hochzuladende Datei:"
-#: ../../Zotlabs/Module/Connedit.php:801
-msgid "This information is public!"
-msgstr "Diese Information ist öffentlich!"
+#: ../../Zotlabs/Module/New_channel.php:121
+#: ../../Zotlabs/Module/Manage.php:138
+#, php-format
+msgid "You have created %1$.0f of %2$.0f allowed channels."
+msgstr "Du hast %1$.0f von maximal %2$.0f erlaubten Kanälen eingerichtet."
-#: ../../Zotlabs/Module/Connedit.php:806
-msgid "Connection Pending Approval"
-msgstr "Verbindung wartet auf Bestätigung"
+#: ../../Zotlabs/Module/New_channel.php:134
+#: ../../Zotlabs/Module/Register.php:237
+msgid "Name or caption"
+msgstr "Name oder Titel"
-#: ../../Zotlabs/Module/Connedit.php:809
-#: ../../Zotlabs/Module/Settings/Tokens.php:163
-msgid "inherited"
-msgstr "geerbt"
+#: ../../Zotlabs/Module/New_channel.php:134
+#: ../../Zotlabs/Module/Register.php:237
+msgid "Examples: \"Bob Jameson\", \"Lisa and her Horses\", \"Soccer\", \"Aviation Group\""
+msgstr "Beispiele: „Horst Weidinger“, „Lisa und ihr Meerschweinchen“, „Fußball“, „Segelflieger-Forum“ "
-#: ../../Zotlabs/Module/Connedit.php:810 ../../Zotlabs/Module/Locs.php:121
-#: ../../Zotlabs/Module/Connect.php:98
-#: ../../Zotlabs/Module/Admin/Features.php:66
-#: ../../Zotlabs/Module/Admin/Logs.php:84
-#: ../../Zotlabs/Module/Admin/Plugins.php:429
-#: ../../Zotlabs/Module/Admin/Profs.php:157
-#: ../../Zotlabs/Module/Admin/Security.php:104
-#: ../../Zotlabs/Module/Admin/Themes.php:156
-#: ../../Zotlabs/Module/Admin/Account_edit.php:74
-#: ../../Zotlabs/Module/Admin/Accounts.php:166
-#: ../../Zotlabs/Module/Admin/Channels.php:147
-#: ../../Zotlabs/Module/Admin/Site.php:260 ../../Zotlabs/Module/Appman.php:126
-#: ../../Zotlabs/Module/Filestorage.php:165 ../../Zotlabs/Module/Mail.php:384
-#: ../../Zotlabs/Module/Import_items.php:122
-#: ../../Zotlabs/Module/Invite.php:149 ../../Zotlabs/Module/Group.php:85
-#: ../../Zotlabs/Module/Mitem.php:243 ../../Zotlabs/Module/Mood.php:139
-#: ../../Zotlabs/Module/Photos.php:668 ../../Zotlabs/Module/Photos.php:1058
-#: ../../Zotlabs/Module/Photos.php:1098 ../../Zotlabs/Module/Photos.php:1216
-#: ../../Zotlabs/Module/Setup.php:309 ../../Zotlabs/Module/Setup.php:357
-#: ../../Zotlabs/Module/Poke.php:186 ../../Zotlabs/Module/Profiles.php:681
-#: ../../Zotlabs/Module/Pconfig.php:107 ../../Zotlabs/Module/Rate.php:166
-#: ../../Zotlabs/Module/Pdledit.php:74 ../../Zotlabs/Module/Cal.php:342
-#: ../../Zotlabs/Module/Wiki.php:148 ../../Zotlabs/Module/Sources.php:114
-#: ../../Zotlabs/Module/Sources.php:149
-#: ../../Zotlabs/Module/Settings/Features.php:47
-#: ../../Zotlabs/Module/Settings/Oauth.php:87
-#: ../../Zotlabs/Module/Settings/Tokens.php:167
-#: ../../Zotlabs/Module/Settings/Account.php:118
-#: ../../Zotlabs/Module/Settings/Channel.php:455
-#: ../../Zotlabs/Module/Settings/Display.php:196
-#: ../../Zotlabs/Module/Thing.php:320 ../../Zotlabs/Module/Thing.php:370
-#: ../../Zotlabs/Module/Import.php:543 ../../Zotlabs/Module/Chat.php:196
-#: ../../Zotlabs/Module/Chat.php:241 ../../Zotlabs/Module/Xchan.php:15
-#: ../../Zotlabs/Module/Events.php:484 ../../Zotlabs/Lib/ThreadItem.php:729
-#: ../../extend/addon/addon/chords/Mod_Chords.php:60
-#: ../../extend/addon/addon/diaspora/diaspora.php:710
-#: ../../extend/addon/addon/dwpost/dwpost.php:89
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:124
-#: ../../extend/addon/addon/friendica/friendica.php:128
-#: ../../extend/addon/addon/frphotos/frphotos.php:96
-#: ../../extend/addon/addon/gnusoc/gnusoc.php:129
-#: ../../extend/addon/addon/hubwall/hubwall.php:95
-#: ../../extend/addon/addon/ijpost/ijpost.php:89
-#: ../../extend/addon/addon/irc/irc.php:53
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:371
-#: ../../extend/addon/addon/libertree/libertree.php:85
-#: ../../extend/addon/addon/ljpost/ljpost.php:86
-#: ../../extend/addon/addon/logrot/logrot.php:35
-#: ../../extend/addon/addon/mailhost/mailhost.php:40
-#: ../../extend/addon/addon/nofed/nofed.php:80
-#: ../../extend/addon/addon/nsabait/nsabait.php:161
-#: ../../extend/addon/addon/nsfw/nsfw.php:92
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:52
-#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:168
-#: ../../extend/addon/addon/pageheader/pageheader.php:48
-#: ../../extend/addon/addon/piwik/piwik.php:95
-#: ../../extend/addon/addon/planets/planets.php:157
-#: ../../extend/addon/addon/pumpio/pumpio.php:237
-#: ../../extend/addon/addon/rainbowtag/rainbowtag.php:85
-#: ../../extend/addon/addon/redfiles/redfiles.php:124
-#: ../../extend/addon/addon/redphotos/redphotos.php:136
-#: ../../extend/addon/addon/redred/redred.php:119
-#: ../../extend/addon/addon/rtof/rtof.php:101
-#: ../../extend/addon/addon/skeleton/skeleton.php:65
-#: ../../extend/addon/addon/smileybutton/smileybutton.php:281
-#: ../../extend/addon/addon/startpage/startpage.php:113
-#: ../../extend/addon/addon/statusnet/statusnet.php:322
-#: ../../extend/addon/addon/statusnet/statusnet.php:380
-#: ../../extend/addon/addon/statusnet/statusnet.php:432
-#: ../../extend/addon/addon/statusnet/statusnet.php:899
-#: ../../extend/addon/addon/superblock/superblock.php:114
-#: ../../extend/addon/addon/twitter/twitter.php:217
-#: ../../extend/addon/addon/twitter/twitter.php:259
-#: ../../extend/addon/addon/visage/visage.php:170
-#: ../../extend/addon/addon/wppost/wppost.php:113
-#: ../../extend/addon/addon/xmpp/xmpp.php:69
-#: ../../extend/addon/addon/cdav/cdav.php:246
-#: ../../extend/addon/addon/likebanner/likebanner.php:57
-#: ../../extend/addon/addon/mailtest/mailtest.php:100
-#: ../../include/js_strings.php:22 ../../include/widgets.php:796
-#: ../../view/theme/redbasic/php/config.php:106
-msgid "Submit"
-msgstr "Absenden"
+#: ../../Zotlabs/Module/New_channel.php:136
+#: ../../Zotlabs/Module/Register.php:239
+msgid "Choose a short nickname"
+msgstr "Wähle einen kurzen Spitznamen"
-#: ../../Zotlabs/Module/Connedit.php:811
+#: ../../Zotlabs/Module/New_channel.php:136
+#: ../../Zotlabs/Module/Register.php:239
#, php-format
msgid ""
-"Please choose the profile you would like to display to %s when viewing your "
-"profile securely."
-msgstr "Bitte wähle ein Profil, das wir %s zeigen sollen, wenn Deine Profilseite über eine verifizierte Verbindung aufgerufen wird."
+"Your nickname will be used to create an easy to remember channel address "
+"e.g. nickname%s"
+msgstr "Dein Spitzname wird verwendet, um eine leicht zu merkende Kanal-Adresse (ähnlich einer E-Mail-Adresse) zu erzeugen, die Du mit anderen austauschen kannst, z.B. nickname%s"
-#: ../../Zotlabs/Module/Connedit.php:813
-#: ../../Zotlabs/Module/Settings/Tokens.php:160
-msgid "Their Settings"
-msgstr "Deren Einstellungen"
+#: ../../Zotlabs/Module/New_channel.php:137
+#: ../../Zotlabs/Module/Register.php:240
+msgid "Channel role and privacy"
+msgstr "Kanaltyp und Privatspäre-Einstellungen"
-#: ../../Zotlabs/Module/Connedit.php:814
-#: ../../Zotlabs/Module/Settings/Tokens.php:161
-msgid "My Settings"
-msgstr "Meine Einstellungen"
+#: ../../Zotlabs/Module/New_channel.php:137
+#: ../../Zotlabs/Module/Register.php:240
+msgid "Select a channel role with your privacy requirements."
+msgstr "Wähle einen passenden Kanaltyp mit den zugehörigen Voreinstellungen zur Privatsphäre."
-#: ../../Zotlabs/Module/Connedit.php:816
-#: ../../Zotlabs/Module/Settings/Tokens.php:165
-msgid "Individual Permissions"
-msgstr "Individuelle Zugriffsrechte"
+#: ../../Zotlabs/Module/New_channel.php:137
+#: ../../Zotlabs/Module/Register.php:240
+msgid "Read more about roles"
+msgstr "Mehr Informationen über Rollen"
-#: ../../Zotlabs/Module/Connedit.php:817
-#: ../../Zotlabs/Module/Settings/Tokens.php:166
+#: ../../Zotlabs/Module/New_channel.php:140
+msgid "Create Channel"
+msgstr "Einen neuen Kanal anlegen"
+
+#: ../../Zotlabs/Module/New_channel.php:141
msgid ""
-"Some permissions may be inherited from your channel's <a "
-"href=\"settings\"><strong>privacy settings</strong></a>, which have higher "
-"priority than individual settings. You can <strong>not</strong> change those"
-" settings here."
-msgstr "Einige Berechtigungen werden möglicherweise von den globalen <a href=\"settings\">Sicherheits- und Privatsphäre-Einstellungen</a> dieses Kanals vererbt. Diese haben eine höhere Priorität als die Einstellungen an der Verbindung und können hier nicht verändert werden."
+"A channel is your identity on this network. It can represent a person, a "
+"blog, or a forum to name a few. Channels can make connections with other "
+"channels to share information with highly detailed permissions."
+msgstr "Ein Kanal ist Deine Identität in diesem Netzwerk. Er kann eine Person, ein Blog oder ein Forum repräsentieren, nur um ein paar Beispiele zu nennen. Kanäle können Verbindungen miteinander eingehen, um Informationen zu teilen, jeweils basierend auf sehr detaillierten Berechtigungseinstellungen."
-#: ../../Zotlabs/Module/Connedit.php:818
+#: ../../Zotlabs/Module/New_channel.php:142
msgid ""
-"Some permissions may be inherited from your channel's <a "
-"href=\"settings\"><strong>privacy settings</strong></a>, which have higher "
-"priority than individual settings. You can change those settings here but "
-"they wont have any impact unless the inherited setting changes."
-msgstr "Einige Berechtigungen werden möglicherweise von den globalen <a href=\"settings\">Sicherheits- und Privatsphäre-Einstellungen</a> dieses Kanals geerbt. Diese haben eine höhere Priorität als die Einstellungen an der Verbindung. Werden geerbte Einstellungen hier geändert, hat dies keine Auswirkungen."
+"or <a href=\"import\">import an existing channel</a> from another location."
+msgstr "oder <a href=\"import\">importiere einen bestehenden Kanal</a> von einem anderen Server."
-#: ../../Zotlabs/Module/Connedit.php:819
-msgid "Last update:"
-msgstr "Letzte Aktualisierung:"
+#: ../../Zotlabs/Module/Removeme.php:35
+msgid ""
+"Channel removals are not allowed within 48 hours of changing the account "
+"password."
+msgstr "Innerhalb von 48 Stunden nach einer Änderung des Passworts können keine Kanäle gelöscht werden."
-#: ../../Zotlabs/Module/Dreport.php:45
-msgid "Invalid message"
-msgstr "Ungültige Beitrags-ID (mid)"
+#: ../../Zotlabs/Module/Removeme.php:60
+msgid "Remove This Channel"
+msgstr "Diesen Kanal löschen"
-#: ../../Zotlabs/Module/Dreport.php:78
-msgid "no results"
-msgstr "keine Ergebnisse"
+#: ../../Zotlabs/Module/Removeme.php:61
+#: ../../Zotlabs/Module/Removeaccount.php:58
+#: ../../Zotlabs/Module/Changeaddr.php:78
+msgid "WARNING: "
+msgstr "WARNUNG: "
-#: ../../Zotlabs/Module/Dreport.php:93
-msgid "channel sync processed"
-msgstr "Kanal-Sync verarbeitet"
+#: ../../Zotlabs/Module/Removeme.php:61
+msgid "This channel will be completely removed from the network. "
+msgstr "Dieser Kanal wird vollständig aus dem Netzwerk gelöscht."
-#: ../../Zotlabs/Module/Dreport.php:97
-msgid "queued"
-msgstr "zur Warteschlange hinzugefügt"
+#: ../../Zotlabs/Module/Removeme.php:61
+#: ../../Zotlabs/Module/Removeaccount.php:58
+msgid "This action is permanent and can not be undone!"
+msgstr "Dieser Schritt ist endgültig und kann nicht rückgängig gemacht werden!"
-#: ../../Zotlabs/Module/Dreport.php:101
-msgid "posted"
-msgstr "zugestellt"
+#: ../../Zotlabs/Module/Removeme.php:62
+#: ../../Zotlabs/Module/Removeaccount.php:59
+#: ../../Zotlabs/Module/Changeaddr.php:79
+msgid "Please enter your password for verification:"
+msgstr "Bitte gib zur Bestätigung Dein Passwort ein:"
-#: ../../Zotlabs/Module/Dreport.php:105
-msgid "accepted for delivery"
-msgstr "für Zustellung akzeptiert"
+#: ../../Zotlabs/Module/Removeme.php:63
+msgid "Remove this channel and all its clones from the network"
+msgstr "Lösche diesen Kanal und all seine Klone aus dem Netzwerk"
-#: ../../Zotlabs/Module/Dreport.php:109
-msgid "updated"
-msgstr "aktualisiert"
+#: ../../Zotlabs/Module/Removeme.php:63
+msgid ""
+"By default only the instance of the channel located on this hub will be "
+"removed from the network"
+msgstr "Standardmäßig wird der Kanal nur auf diesem Server gelöscht, seine Klone verbleiben im Netzwerk"
-#: ../../Zotlabs/Module/Dreport.php:112
-msgid "update ignored"
-msgstr "Aktualisierung ignoriert"
+#: ../../Zotlabs/Module/Removeme.php:64
+#: ../../Zotlabs/Module/Settings/Channel.php:580
+msgid "Remove Channel"
+msgstr "Kanal löschen"
-#: ../../Zotlabs/Module/Dreport.php:115
-msgid "permission denied"
-msgstr "Zugriff verweigert"
+#: ../../Zotlabs/Module/Sharedwithme.php:104
+msgid "Files: shared with me"
+msgstr "Dateien, die mit mir geteilt wurden"
-#: ../../Zotlabs/Module/Dreport.php:119
-msgid "recipient not found"
-msgstr "Empfänger nicht gefunden."
+#: ../../Zotlabs/Module/Sharedwithme.php:106
+msgid "NEW"
+msgstr "NEU"
-#: ../../Zotlabs/Module/Dreport.php:122
-msgid "mail recalled"
-msgstr "Mail widerrufen"
+#: ../../Zotlabs/Module/Sharedwithme.php:107
+#: ../../Zotlabs/Storage/Browser.php:236 ../../include/text.php:1394
+msgid "Size"
+msgstr "Größe"
-#: ../../Zotlabs/Module/Dreport.php:125
-msgid "duplicate mail received"
-msgstr "Doppelte Mail erhalten"
+#: ../../Zotlabs/Module/Sharedwithme.php:108
+#: ../../Zotlabs/Storage/Browser.php:237
+msgid "Last Modified"
+msgstr "Zuletzt geändert"
-#: ../../Zotlabs/Module/Dreport.php:128
-msgid "mail delivered"
-msgstr "Mail zugestellt"
+#: ../../Zotlabs/Module/Sharedwithme.php:109
+msgid "Remove all files"
+msgstr "Alle Dateien löschen"
-#: ../../Zotlabs/Module/Dreport.php:148
-#, php-format
-msgid "Delivery report for %1$s"
-msgstr "Zustellungsbericht für %1$s"
+#: ../../Zotlabs/Module/Sharedwithme.php:110
+msgid "Remove this file"
+msgstr "Diese Datei löschen"
-#: ../../Zotlabs/Module/Dreport.php:151
-msgid "Options"
-msgstr "Optionen"
+#: ../../Zotlabs/Module/Setup.php:170
+msgid "$Projectname Server - Setup"
+msgstr "$Projectname Server-Einrichtung"
-#: ../../Zotlabs/Module/Dreport.php:152
-msgid "Redeliver"
-msgstr "Erneut zustellen"
+#: ../../Zotlabs/Module/Setup.php:174
+msgid "Could not connect to database."
+msgstr "Kann nicht mit der Datenbank verbinden."
-#: ../../Zotlabs/Module/Bookmarks.php:53
-msgid "Bookmark added"
-msgstr "Lesezeichen hinzugefügt"
+#: ../../Zotlabs/Module/Setup.php:178
+msgid ""
+"Could not connect to specified site URL. Possible SSL certificate or DNS "
+"issue."
+msgstr "Konnte die angegebene Webseiten-URL nicht erreichen. Möglicherweise ein Problem mit dem SSL-Zertifikat oder dem DNS."
-#: ../../Zotlabs/Module/Bookmarks.php:75
-msgid "My Bookmarks"
-msgstr "Meine Lesezeichen"
+#: ../../Zotlabs/Module/Setup.php:185
+msgid "Could not create table."
+msgstr "Konnte Tabelle nicht erstellen."
-#: ../../Zotlabs/Module/Bookmarks.php:86
-msgid "My Connections Bookmarks"
-msgstr "Lesezeichen meiner Kontakte"
+#: ../../Zotlabs/Module/Setup.php:191
+msgid "Your site database has been installed."
+msgstr "Die Datenbank Deines Hubs wurde installiert."
-#: ../../Zotlabs/Module/Acl.php:313
-msgid "network"
-msgstr "Netzwerk"
+#: ../../Zotlabs/Module/Setup.php:197
+msgid ""
+"You may need to import the file \"install/schema_xxx.sql\" manually using a "
+"database client."
+msgstr "Möglicherweise musst Du die Datei install/schema_xxx.sql manuell mit Hilfe eines Datenkbank-Clients importieren."
-#: ../../Zotlabs/Module/Acl.php:323
-msgid "RSS"
-msgstr "RSS"
+#: ../../Zotlabs/Module/Setup.php:198 ../../Zotlabs/Module/Setup.php:262
+#: ../../Zotlabs/Module/Setup.php:745
+msgid "Please see the file \"install/INSTALL.txt\"."
+msgstr "Lies die Datei \"install/INSTALL.txt\"."
-#: ../../Zotlabs/Module/Locs.php:25 ../../Zotlabs/Module/Locs.php:54
-msgid "Location not found."
-msgstr "Klon nicht gefunden."
+#: ../../Zotlabs/Module/Setup.php:259
+msgid "System check"
+msgstr "Systemprüfung"
-#: ../../Zotlabs/Module/Locs.php:62
-msgid "Location lookup failed."
-msgstr "Nachschlagen des Kanal-Ortes fehlgeschlagen"
+#: ../../Zotlabs/Module/Setup.php:264
+msgid "Check again"
+msgstr "Nochmal prüfen"
-#: ../../Zotlabs/Module/Locs.php:66
+#: ../../Zotlabs/Module/Setup.php:286
+msgid "Database connection"
+msgstr "Datenbankverbindung"
+
+#: ../../Zotlabs/Module/Setup.php:287
msgid ""
-"Please select another location to become primary before removing the primary"
-" location."
-msgstr "Bitte mache einen anderen Kanal-Ort zum primären Ort, bevor Du den primären Ort löschst."
+"In order to install $Projectname we need to know how to connect to your "
+"database."
+msgstr "Um $Projectname zu installieren, müssen wir wissen, wie wir eine Verbindung zu Deiner Datenbank aufbauen können."
-#: ../../Zotlabs/Module/Locs.php:95
-msgid "Syncing locations"
-msgstr "Synchronisiere Klone"
+#: ../../Zotlabs/Module/Setup.php:288
+msgid ""
+"Please contact your hosting provider or site administrator if you have "
+"questions about these settings."
+msgstr "Bitte kontaktiere Deinen Hosting-Provider oder Administrator, falls Du Fragen zu diesen Einstellungen hast."
-#: ../../Zotlabs/Module/Locs.php:105
-msgid "No locations found."
-msgstr "Keine Klon-Adressen gefunden."
+#: ../../Zotlabs/Module/Setup.php:289
+msgid ""
+"The database you specify below should already exist. If it does not, please "
+"create it before continuing."
+msgstr "Die Datenbank, die Du weiter unten angibst, sollte bereits existieren. Sollte das noch nicht der Fall sein, erzeuge sie bitte bevor Du fortfährst."
-#: ../../Zotlabs/Module/Locs.php:116
-msgid "Manage Channel Locations"
-msgstr "Klon-Adressen verwalten"
+#: ../../Zotlabs/Module/Setup.php:293
+msgid "Database Server Name"
+msgstr "Datenbankservername"
-#: ../../Zotlabs/Module/Locs.php:117 ../../Zotlabs/Module/Pubsites.php:51
-#: ../../Zotlabs/Module/Profiles.php:471 ../../Zotlabs/Module/Profiles.php:692
-#: ../../Zotlabs/Module/Events.php:468
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:839
-#: ../../include/js_strings.php:25
-msgid "Location"
-msgstr "Ort"
+#: ../../Zotlabs/Module/Setup.php:293
+msgid "Default is 127.0.0.1"
+msgstr "Standard ist 127.0.0.1"
-#: ../../Zotlabs/Module/Locs.php:118
-#: ../../Zotlabs/Module/Admin/Channels.php:160
-#: ../../Zotlabs/Module/Profiles.php:464
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1143
-msgid "Address"
-msgstr "Adresse"
+#: ../../Zotlabs/Module/Setup.php:294
+msgid "Database Port"
+msgstr "Datenbankport"
-#: ../../Zotlabs/Module/Locs.php:119
-msgid "Primary"
-msgstr "Primär"
+#: ../../Zotlabs/Module/Setup.php:294
+msgid "Communication port number - use 0 for default"
+msgstr "Port-Nummer für die Kommunikation – verwende 0 für die Standardeinstellung"
-#: ../../Zotlabs/Module/Locs.php:120 ../../Zotlabs/Module/Menu.php:113
-msgid "Drop"
-msgstr "Löschen"
+#: ../../Zotlabs/Module/Setup.php:295
+msgid "Database Login Name"
+msgstr "Datenbank-Benutzername"
-#: ../../Zotlabs/Module/Locs.php:122
-msgid "Sync Now"
-msgstr "Jetzt synchronisieren"
+#: ../../Zotlabs/Module/Setup.php:296
+msgid "Database Login Password"
+msgstr "Datenbank-Passwort"
-#: ../../Zotlabs/Module/Locs.php:123
-msgid "Please wait several minutes between consecutive operations."
-msgstr "Bitte warte mehrere Minuten zwischen dem Ausführen zweier Operationen!"
+#: ../../Zotlabs/Module/Setup.php:297
+msgid "Database Name"
+msgstr "Datenbankname"
-#: ../../Zotlabs/Module/Locs.php:124
+#: ../../Zotlabs/Module/Setup.php:298
+msgid "Database Type"
+msgstr "Datenbanktyp"
+
+#: ../../Zotlabs/Module/Setup.php:300 ../../Zotlabs/Module/Setup.php:341
+msgid "Site administrator email address"
+msgstr "E-Mail Adresse des Seiten-Administrators"
+
+#: ../../Zotlabs/Module/Setup.php:300 ../../Zotlabs/Module/Setup.php:341
msgid ""
-"When possible, drop a location by logging into that website/hub and removing"
-" your channel."
-msgstr "Wenn möglich, lösche einen Klon, indem Du Dich auf dem jeweiligen Hub einloggst und den Kanal dort löschst."
+"Your account email address must match this in order to use the web admin "
+"panel."
+msgstr "Die E-Mail-Adresse Deines Accounts muss dieser Adresse entsprechen, damit Du Zugriff zur Administrations-Seite erhältst."
-#: ../../Zotlabs/Module/Locs.php:125
-msgid "Use this form to drop the location if the hub is no longer operating."
-msgstr "Benutze dieses Formular zum Löschen eines Klons, wenn es den Hub nicht mehr gibt."
+#: ../../Zotlabs/Module/Setup.php:301 ../../Zotlabs/Module/Setup.php:343
+msgid "Website URL"
+msgstr "Webseiten-URL"
-#: ../../Zotlabs/Module/Connect.php:61 ../../Zotlabs/Module/Connect.php:109
-msgid "Continue"
-msgstr "Fortfahren"
+#: ../../Zotlabs/Module/Setup.php:301 ../../Zotlabs/Module/Setup.php:343
+msgid "Please use SSL (https) URL if available."
+msgstr "Nutze wenn möglich eine SSL-URL (https)."
-#: ../../Zotlabs/Module/Connect.php:90
-msgid "Premium Channel Setup"
-msgstr "Premium-Kanal-Einrichtung"
+#: ../../Zotlabs/Module/Setup.php:302 ../../Zotlabs/Module/Setup.php:345
+msgid "Please select a default timezone for your website"
+msgstr "Standard-Zeitzone für Deinen Server"
-#: ../../Zotlabs/Module/Connect.php:92
-msgid "Enable premium channel connection restrictions"
-msgstr "Einschränkungen für einen Premium-Kanal aktivieren"
+#: ../../Zotlabs/Module/Setup.php:330
+msgid "Site settings"
+msgstr "Seiteneinstellungen"
-#: ../../Zotlabs/Module/Connect.php:93
+#: ../../Zotlabs/Module/Setup.php:384
+msgid "PHP version 5.5 or greater is required."
+msgstr "PHP-Version 5.5 oder höher ist erforderlich."
+
+#: ../../Zotlabs/Module/Setup.php:385
+msgid "PHP version"
+msgstr "PHP-Version"
+
+#: ../../Zotlabs/Module/Setup.php:401
+msgid "Could not find a command line version of PHP in the web server PATH."
+msgstr "Konnte die Kommandozeilen-Version von PHP nicht im PATH des Web-Servers finden."
+
+#: ../../Zotlabs/Module/Setup.php:402
msgid ""
-"Please enter your restrictions or conditions, such as paypal receipt, usage "
-"guidelines, etc."
-msgstr "Bitte gib Deine Nutzungsbedingungen ein, z.B. Paypal-Quittung, Richtlinien etc."
+"If you don't have a command line version of PHP installed on server, you "
+"will not be able to run background polling via cron."
+msgstr "Ohne Kommandozeilen-Version von PHP auf dem Server wirst Du nicht in der Lage sein, Hintergrundprozesse via cron auszuführen."
-#: ../../Zotlabs/Module/Connect.php:95 ../../Zotlabs/Module/Connect.php:115
+#: ../../Zotlabs/Module/Setup.php:406
+msgid "PHP executable path"
+msgstr "PHP-Pfad zu ausführbarer Datei"
+
+#: ../../Zotlabs/Module/Setup.php:406
msgid ""
-"This channel may require additional steps or acknowledgement of the "
-"following conditions prior to connecting:"
-msgstr "Unter Umständen sind weitere Schritte oder die Bestätigung der folgenden Bedingungen vor dem Verbinden mit diesem Kanal nötig."
+"Enter full path to php executable. You can leave this blank to continue the "
+"installation."
+msgstr "Gib den vollen Pfad zum PHP-Interpreter an. Du kannst dieses Feld frei lassen und mit der Installation fortfahren."
-#: ../../Zotlabs/Module/Connect.php:96
+#: ../../Zotlabs/Module/Setup.php:411
+msgid "Command line PHP"
+msgstr "PHP-Befehlszeile"
+
+#: ../../Zotlabs/Module/Setup.php:421
msgid ""
-"Potential connections will then see the following text before proceeding:"
-msgstr "Potentielle Kontakte werden den folgenden Text sehen, bevor fortgefahren wird:"
+"Unable to check command line PHP, as shell_exec() is disabled. This is "
+"required."
+msgstr "Prüfung auf Kommandozeilen-PHP fehlgeschlagen, da shell_exec() deaktiviert ist. Dies wird aber benötigt."
-#: ../../Zotlabs/Module/Connect.php:97 ../../Zotlabs/Module/Connect.php:118
+#: ../../Zotlabs/Module/Setup.php:424
msgid ""
-"By continuing, I certify that I have complied with any instructions provided"
-" on this page."
-msgstr "Indem ich fortfahre, bestätige ich die Erfüllung aller Anweisungen auf dieser Seite."
+"The command line version of PHP on your system does not have "
+"\"register_argc_argv\" enabled."
+msgstr "Bei der Kommandozeilen-Version von PHP auf Deinem System ist \"register_argc_argv\" nicht aktiviert."
-#: ../../Zotlabs/Module/Connect.php:106
-msgid "(No specific instructions have been provided by the channel owner.)"
-msgstr "(Der Kanal-Besitzer hat keine speziellen Anweisungen hinterlegt.)"
+#: ../../Zotlabs/Module/Setup.php:425
+msgid "This is required for message delivery to work."
+msgstr "Das wird benötigt, damit die Auslieferung von Nachrichten funktioniert."
-#: ../../Zotlabs/Module/Connect.php:114
-msgid "Restricted or Premium Channel"
-msgstr "Eingeschränkter oder Premium-Kanal"
+#: ../../Zotlabs/Module/Setup.php:428
+msgid "PHP register_argc_argv"
+msgstr "PHP register_argc_argv"
-#: ../../Zotlabs/Module/Page.php:40 ../../Zotlabs/Module/Block.php:31
-msgid "Invalid item."
-msgstr "Ungültiges Element."
+#: ../../Zotlabs/Module/Setup.php:446
+#, php-format
+msgid ""
+"Your max allowed total upload size is set to %s. Maximum size of one file to"
+" upload is set to %s. You are allowed to upload up to %d files at once."
+msgstr "Die Maximalgröße für Uploads insgesamt liegt bei %s. Die Maximalgröße für eine Datei liegt bei %s. Es können maximal %d Dateien gleichzeitig hochgeladen werden."
-#: ../../Zotlabs/Module/Page.php:56 ../../Zotlabs/Module/Chanview.php:96
-#: ../../Zotlabs/Module/Block.php:43 ../../Zotlabs/Module/Cal.php:62
-#: ../../Zotlabs/Module/Wall_upload.php:31
-msgid "Channel not found."
-msgstr "Kanal nicht gefunden."
+#: ../../Zotlabs/Module/Setup.php:451
+msgid "You can adjust these settings in the server php.ini file."
+msgstr "Du kannst diese Einstellungen in der php.ini - Datei des Servers anpassen."
-#: ../../Zotlabs/Module/Page.php:131
+#: ../../Zotlabs/Module/Setup.php:453
+msgid "PHP upload limits"
+msgstr "PHP-Hochladebeschränkungen"
+
+#: ../../Zotlabs/Module/Setup.php:476
msgid ""
-"Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod "
-"tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam,"
-" quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo "
-"consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse "
-"cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat "
-"non proident, sunt in culpa qui officia deserunt mollit anim id est laborum."
-msgstr "Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum."
+"Error: the \"openssl_pkey_new\" function on this system is not able to "
+"generate encryption keys"
+msgstr "Fehler: Die „openssl_pkey_new“-Funktion auf diesem System ist nicht in der Lage, Schlüssel für die Verschlüsselung zu erzeugen."
-#: ../../Zotlabs/Module/Filer.php:52
-msgid "Save to Folder:"
-msgstr "Speichern in Ordner:"
+#: ../../Zotlabs/Module/Setup.php:477
+msgid ""
+"If running under Windows, please see "
+"\"http://www.php.net/manual/en/openssl.installation.php\"."
+msgstr "Wenn Du Windows verwendest, findest Du unter http://www.php.net/manual/en/openssl.installation.php eine Installationsanleitung."
-#: ../../Zotlabs/Module/Filer.php:52
-msgid "- select -"
-msgstr "– auswählen –"
+#: ../../Zotlabs/Module/Setup.php:480
+msgid "Generate encryption keys"
+msgstr "Verschlüsselungsschlüssel erzeugen"
-#: ../../Zotlabs/Module/Filer.php:53 ../../Zotlabs/Module/Admin/Profs.php:74
-#: ../../Zotlabs/Module/Admin/Profs.php:94 ../../Zotlabs/Module/Rbmark.php:32
-#: ../../Zotlabs/Module/Rbmark.php:104 ../../include/text.php:987
-#: ../../include/text.php:999 ../../include/widgets.php:201
-msgid "Save"
-msgstr "Speichern"
+#: ../../Zotlabs/Module/Setup.php:497
+msgid "libCurl PHP module"
+msgstr "libCurl-PHP-Modul"
-#: ../../Zotlabs/Module/Manage.php:136
-#: ../../Zotlabs/Module/New_channel.php:121
-#, php-format
-msgid "You have created %1$.0f of %2$.0f allowed channels."
-msgstr "Du hast %1$.0f von maximal %2$.0f erlaubten Kanälen eingerichtet."
+#: ../../Zotlabs/Module/Setup.php:498
+msgid "GD graphics PHP module"
+msgstr "GD-Grafik-PHP-Modul"
-#: ../../Zotlabs/Module/Manage.php:143
-msgid "Create a new channel"
-msgstr "Neuen Kanal anlegen"
+#: ../../Zotlabs/Module/Setup.php:499
+msgid "OpenSSL PHP module"
+msgstr "OpenSSL-PHP-Modul"
-#: ../../Zotlabs/Module/Manage.php:143 ../../Zotlabs/Module/Profiles.php:772
-#: ../../Zotlabs/Module/Wiki.php:147 ../../Zotlabs/Module/Chat.php:255
-msgid "Create New"
-msgstr "Neu anlegen"
+#: ../../Zotlabs/Module/Setup.php:500
+msgid "PDO database PHP module"
+msgstr "PDO-Datenbank-PHP-Modul"
-#: ../../Zotlabs/Module/Manage.php:164 ../../Zotlabs/Lib/Apps.php:214
-#: ../../include/nav.php:209
-msgid "Channel Manager"
-msgstr "Kanal-Manager"
+#: ../../Zotlabs/Module/Setup.php:501
+msgid "mb_string PHP module"
+msgstr "mb_string-PHP-Modul"
-#: ../../Zotlabs/Module/Manage.php:165
-msgid "Current Channel"
-msgstr "Aktueller Kanal"
+#: ../../Zotlabs/Module/Setup.php:502
+msgid "xml PHP module"
+msgstr "xml-PHP-Modul"
-#: ../../Zotlabs/Module/Manage.php:167
-msgid "Switch to one of your channels by selecting it."
-msgstr "Wechsle zu einem Deiner Kanäle, indem Du auf ihn klickst."
+#: ../../Zotlabs/Module/Setup.php:503
+msgid "zip PHP module"
+msgstr "zip PHP Modul"
-#: ../../Zotlabs/Module/Manage.php:168
-msgid "Default Channel"
-msgstr "Standard Kanal"
+#: ../../Zotlabs/Module/Setup.php:507 ../../Zotlabs/Module/Setup.php:509
+msgid "Apache mod_rewrite module"
+msgstr "Apache-mod_rewrite-Modul"
-#: ../../Zotlabs/Module/Manage.php:169
-msgid "Make Default"
-msgstr "Zum Standard machen"
+#: ../../Zotlabs/Module/Setup.php:507
+msgid ""
+"Error: Apache webserver mod-rewrite module is required but not installed."
+msgstr "Fehler: Das Apache-Modul mod-rewrite wird benötigt, ist aber nicht installiert."
-#: ../../Zotlabs/Module/Manage.php:172
-#, php-format
-msgid "%d new messages"
-msgstr "%d neue Nachrichten"
+#: ../../Zotlabs/Module/Setup.php:513 ../../Zotlabs/Module/Setup.php:516
+msgid "exec"
+msgstr "exec"
-#: ../../Zotlabs/Module/Manage.php:173
-#, php-format
-msgid "%d new introductions"
-msgstr "%d neue Vorstellungen"
+#: ../../Zotlabs/Module/Setup.php:513
+msgid ""
+"Error: exec is required but is either not installed or has been disabled in "
+"php.ini"
+msgstr "Fehler: exec ist erforderlich, aber entweder nicht installiert oder wurde in der php.ini deaktiviert"
-#: ../../Zotlabs/Module/Manage.php:175
-msgid "Delegated Channel"
-msgstr "Delegierte Kanäle"
+#: ../../Zotlabs/Module/Setup.php:519 ../../Zotlabs/Module/Setup.php:522
+msgid "shell_exec"
+msgstr "shell_exec"
-#: ../../Zotlabs/Module/Connections.php:56
-#: ../../Zotlabs/Module/Connections.php:161
-#: ../../Zotlabs/Module/Connections.php:242
-msgid "Blocked"
-msgstr "Blockiert"
+#: ../../Zotlabs/Module/Setup.php:519
+msgid ""
+"Error: shell_exec is required but is either not installed or has been "
+"disabled in php.ini"
+msgstr "Fehler: shell_exec ist erforderlich, aber entweder nicht installiert oder wurde in der php.ini deaktiviert"
-#: ../../Zotlabs/Module/Connections.php:61
-#: ../../Zotlabs/Module/Connections.php:168
-#: ../../Zotlabs/Module/Connections.php:241
-msgid "Ignored"
-msgstr "Ignoriert"
+#: ../../Zotlabs/Module/Setup.php:527
+msgid "Error: libCURL PHP module required but not installed."
+msgstr "Fehler: Das PHP-Modul libCURL wird benötigt, ist aber nicht installiert."
-#: ../../Zotlabs/Module/Connections.php:66
-#: ../../Zotlabs/Module/Connections.php:182
-#: ../../Zotlabs/Module/Connections.php:240
-msgid "Hidden"
-msgstr "Versteckt"
+#: ../../Zotlabs/Module/Setup.php:531
+msgid ""
+"Error: GD graphics PHP module with JPEG support required but not installed."
+msgstr "Fehler: Das PHP-Modul GD-Grafik mit JPEG-Unterstützung wird benötigt, ist aber nicht installiert."
-#: ../../Zotlabs/Module/Connections.php:71
-#: ../../Zotlabs/Module/Connections.php:175
-#: ../../Zotlabs/Module/Connections.php:239
-msgid "Archived"
-msgstr "Archiviert"
+#: ../../Zotlabs/Module/Setup.php:535
+msgid "Error: openssl PHP module required but not installed."
+msgstr "Fehler: Das PHP-Modul openssl wird benötigt, ist aber nicht installiert."
-#: ../../Zotlabs/Module/Connections.php:76
-#: ../../Zotlabs/Module/Connections.php:86 ../../Zotlabs/Module/Menu.php:116
-#: ../../include/conversation.php:1594
-msgid "New"
-msgstr "Neu"
+#: ../../Zotlabs/Module/Setup.php:539
+msgid "Error: PDO database PHP module required but not installed."
+msgstr "Fehler: PDO-Datenbank-PHP-Modul ist erforderlich, aber nicht installiert."
-#: ../../Zotlabs/Module/Connections.php:138
-msgid "New Connections"
-msgstr "Neue Verbindungen"
+#: ../../Zotlabs/Module/Setup.php:543
+msgid "Error: mb_string PHP module required but not installed."
+msgstr "Fehler: Das PHP-Modul mb_string wird benötigt, ist aber nicht installiert."
-#: ../../Zotlabs/Module/Connections.php:141
-msgid "Show pending (new) connections"
-msgstr "Ausstehende (neue) Verbindungsanfragen anzeigen"
+#: ../../Zotlabs/Module/Setup.php:547
+msgid "Error: xml PHP module required for DAV but not installed."
+msgstr "Fehler: Das xml-PHP-Modul wird für DAV benötigt, ist aber nicht installiert."
-#: ../../Zotlabs/Module/Connections.php:145
-#: ../../Zotlabs/Module/Profperm.php:144
-msgid "All Connections"
-msgstr "Alle Verbindungen"
+#: ../../Zotlabs/Module/Setup.php:551
+msgid "Error: zip PHP module required but not installed."
+msgstr "Fehler: Das zip PHP Modul ist erforderlich, ist aber nicht installiert."
-#: ../../Zotlabs/Module/Connections.php:148
-msgid "Show all connections"
-msgstr "Alle Verbindungen anzeigen"
+#: ../../Zotlabs/Module/Setup.php:569
+msgid ""
+"The web installer needs to be able to create a file called \".htconfig.php\""
+" in the top folder of your web server and it is unable to do so."
+msgstr "Der Installations-Assistent muss in der Lage sein, die Datei \".htconfig.php\" im Stammverzeichnis des Web-Servers anzulegen, ist er aber nicht."
-#: ../../Zotlabs/Module/Connections.php:164
-msgid "Only show blocked connections"
-msgstr "Nur blockierte Verbindungen anzeigen"
+#: ../../Zotlabs/Module/Setup.php:570
+msgid ""
+"This is most often a permission setting, as the web server may not be able "
+"to write files in your folder - even if you can."
+msgstr "Meist liegt das daran, dass der Nutzer, unter dem der Web-Server läuft, keine Schreibrechte in dem Verzeichnis hat – selbst wenn Du selbst das darfst."
-#: ../../Zotlabs/Module/Connections.php:171
-msgid "Only show ignored connections"
-msgstr "Nur ignorierte Verbindungen anzeigen"
+#: ../../Zotlabs/Module/Setup.php:571
+msgid ""
+"At the end of this procedure, we will give you a text to save in a file "
+"named .htconfig.php in your Red top folder."
+msgstr "Am Schluss dieses Vorgangs wird ein Text generiert, den Du unter dem Dateinamen .htconfig.php im Stammverzeichnis Deiner Hubzilla-Installation speichern musst."
-#: ../../Zotlabs/Module/Connections.php:178
-msgid "Only show archived connections"
-msgstr "Nur archivierte Verbindungen anzeigen"
+#: ../../Zotlabs/Module/Setup.php:572
+msgid ""
+"You can alternatively skip this procedure and perform a manual installation."
+" Please see the file \"install/INSTALL.txt\" for instructions."
+msgstr "Alternativ kannst Du diesen Schritt überspringen und die Installation manuell vornehmen. Lies dazu die Datei install/INSTALL.txt."
-#: ../../Zotlabs/Module/Connections.php:185
-msgid "Only show hidden connections"
-msgstr "Nur versteckte Verbindungen anzeigen"
+#: ../../Zotlabs/Module/Setup.php:575
+msgid ".htconfig.php is writable"
+msgstr ".htconfig.php ist beschreibbar"
-#: ../../Zotlabs/Module/Connections.php:238
-msgid "Pending approval"
-msgstr "Wartet auf Genehmigung"
+#: ../../Zotlabs/Module/Setup.php:589
+msgid ""
+"This software uses the Smarty3 template engine to render its web views. "
+"Smarty3 compiles templates to PHP to speed up rendering."
+msgstr "Diese Software verwendet die Smarty3 Template Engine, um Vorlagen für die Webdarstellung zu verarbeiten. Smarty3 übersetzt diese Vorlagen nach PHP, um die Darstellung zu beschleunigen."
-#: ../../Zotlabs/Module/Connections.php:254
+#: ../../Zotlabs/Module/Setup.php:590
#, php-format
-msgid "%1$s [%2$s]"
-msgstr "%1$s [%2$s]"
-
-#: ../../Zotlabs/Module/Connections.php:255
-msgid "Edit connection"
-msgstr "Verbindung bearbeiten"
-
-#: ../../Zotlabs/Module/Connections.php:256
-msgid "Delete connection"
-msgstr "Verbindung löschen"
+msgid ""
+"In order to store these compiled templates, the web server needs to have "
+"write access to the directory %s under the top level web folder."
+msgstr "Um diese kompilierten Vorlagen speichern zu können, braucht der Web-Server Schreibzugriff auf das Verzeichnis %s unterhalb des Hubzilla-Stammverzeichnisses."
-#: ../../Zotlabs/Module/Connections.php:265
-msgid "Channel address"
-msgstr "Kanaladresse"
+#: ../../Zotlabs/Module/Setup.php:591 ../../Zotlabs/Module/Setup.php:612
+msgid ""
+"Please ensure that the user that your web server runs as (e.g. www-data) has"
+" write access to this folder."
+msgstr "Bitte stelle sicher, dass der Nutzer, unter dem der Web-Server läuft (z.B. www-data), Schreibzugriff auf dieses Verzeichnis hat."
-#: ../../Zotlabs/Module/Connections.php:267
-msgid "Network"
-msgstr "Netzwerk"
+#: ../../Zotlabs/Module/Setup.php:592
+#, php-format
+msgid ""
+"Note: as a security measure, you should give the web server write access to "
+"%s only--not the template files (.tpl) that it contains."
+msgstr "Hinweis: Aus Sicherheitsgründen sollte der Web-Server nur auf %s Schreibrechte haben, nicht auf die Template-Dateien (.tpl), die das Verzeichnis enthält."
-#: ../../Zotlabs/Module/Connections.php:270
-msgid "Status"
-msgstr "Status"
+#: ../../Zotlabs/Module/Setup.php:595
+#, php-format
+msgid "%s is writable"
+msgstr "%s ist beschreibbar"
-#: ../../Zotlabs/Module/Connections.php:272
-msgid "Connected"
-msgstr "Verbunden"
+#: ../../Zotlabs/Module/Setup.php:611
+msgid ""
+"This software uses the store directory to save uploaded files. The web "
+"server needs to have write access to the store directory under the top level"
+" web folder"
+msgstr "Diese Software benutzt das Verzeichnis store, um hochgeladene Dateien zu speichern. Der Webserver benötigt Schreibrechte für dieses Verzeichnis direkt unterhalb des Web-Stammverzeichnisses."
-#: ../../Zotlabs/Module/Connections.php:274
-msgid "Approve connection"
-msgstr "Verbindung genehmigen"
+#: ../../Zotlabs/Module/Setup.php:615
+msgid "store is writable"
+msgstr "store ist schreibbar"
-#: ../../Zotlabs/Module/Connections.php:275
-#: ../../Zotlabs/Module/Admin/Accounts.php:171
-msgid "Approve"
-msgstr "Genehmigen"
+#: ../../Zotlabs/Module/Setup.php:647
+msgid ""
+"SSL certificate cannot be validated. Fix certificate or disable https access"
+" to this site."
+msgstr "Das SSL-Zertifikat konnte nicht validiert werden. Korrigiere das Zertifikat oder deaktiviere den HTTPS-Zugriff auf diesen Server."
-#: ../../Zotlabs/Module/Connections.php:276
-msgid "Ignore connection"
-msgstr "Verbindung ignorieren"
+#: ../../Zotlabs/Module/Setup.php:648
+msgid ""
+"If you have https access to your website or allow connections to TCP port "
+"443 (the https: port), you MUST use a browser-valid certificate. You MUST "
+"NOT use self-signed certificates!"
+msgstr "Wenn Du via HTTPS auf Deinen Server zugreifen möchtest, also Verbindungen über den Port 443 möglich sein sollen, ist ein SSL-Zertifikat einer Zertifizierungsstelle (CA) notwendig, das von den Browsern ohne Sicherheitsabfrage akzeptiert wird. Die Verwendung eines selbst signierten Zertifikates ist nicht möglich."
-#: ../../Zotlabs/Module/Connections.php:278
-msgid "Recent activity"
-msgstr "Kürzliche Aktivitäten"
+#: ../../Zotlabs/Module/Setup.php:649
+msgid ""
+"This restriction is incorporated because public posts from you may for "
+"example contain references to images on your own hub."
+msgstr "Diese Einschränkung wurde eingebaut, weil Deine öffentlichen Beiträge zum Beispiel Verweise auf Bilder auf Deinem eigenen Hub enthalten können."
-#: ../../Zotlabs/Module/Connections.php:302 ../../Zotlabs/Lib/Apps.php:209
-#: ../../include/nav.php:189 ../../include/text.php:916
-msgid "Connections"
-msgstr "Verbindungen"
+#: ../../Zotlabs/Module/Setup.php:650
+msgid ""
+"If your certificate is not recognized, members of other sites (who may "
+"themselves have valid certificates) will get a warning message on their own "
+"site complaining about security issues."
+msgstr "Wenn Dein Zertifikat nicht von jedem Browser akzeptiert wird, erhalten die Mitglieder anderer $Projectname-Hubs (die mit korrekten Zertifikaten ausgestattet sind) Sicherheits-Warnmeldungen, obwohl sie gar nicht direkt auf Deinem Server unterwegs sind (zum Beispiel, wenn ein Bild aus einem Deiner Beiträge angezeigt wird)."
-#: ../../Zotlabs/Module/Connections.php:306 ../../Zotlabs/Module/Search.php:44
-#: ../../Zotlabs/Lib/Apps.php:230 ../../include/nav.php:168
-#: ../../include/text.php:986 ../../include/text.php:998
-#: ../../include/widgets.php:315 ../../include/acl_selectors.php:203
-msgid "Search"
-msgstr "Suche"
+#: ../../Zotlabs/Module/Setup.php:651
+msgid ""
+"This can cause usability issues elsewhere (not just on your own site) so we "
+"must insist on this requirement."
+msgstr "Dies kann Probleme für andere Nutzer (nicht nur auf Deinem eigenen Server) verursachen, so dass wir auf dieser Forderung bestehen müssen."
-#: ../../Zotlabs/Module/Connections.php:307
-msgid "Search your connections"
-msgstr "Verbindungen durchsuchen"
+#: ../../Zotlabs/Module/Setup.php:652
+msgid ""
+"Providers are available that issue free certificates which are browser-"
+"valid."
+msgstr "Es gibt einige Zertifizierungsstellen (CAs), bei denen solche Zertifikate kostenlos zu haben sind."
-#: ../../Zotlabs/Module/Connections.php:308
-msgid "Connections search"
-msgstr "Verbindung suchen"
+#: ../../Zotlabs/Module/Setup.php:654
+msgid ""
+"If you are confident that the certificate is valid and signed by a trusted "
+"authority, check to see if you have failed to install an intermediate cert. "
+"These are not normally required by browsers, but are required for server-to-"
+"server communications."
+msgstr "Wenn Du sicher bist, dass das Zertifikat gültig und von einer vertrauenswürdigen Zertifizierungsstelle signiert ist, prüfe auf ggf. noch zu installierende Zwischenzertifikate (intermediate). Diese werden nicht unbedingt von Browsern benötigt, aber sehr wohl für die Kommunikation zwischen Servern."
-#: ../../Zotlabs/Module/Connections.php:309
-#: ../../Zotlabs/Module/Directory.php:391
-#: ../../Zotlabs/Module/Directory.php:396 ../../include/contact_widgets.php:23
-msgid "Find"
-msgstr "Finde"
+#: ../../Zotlabs/Module/Setup.php:656
+msgid "SSL certificate validation"
+msgstr "SSL Zertifikatverifizierung"
-#: ../../Zotlabs/Module/Cover_photo.php:58
-#: ../../Zotlabs/Module/Profile_photo.php:61
-msgid "Image uploaded but image cropping failed."
-msgstr "Bild hochgeladen, aber das Zurechtschneiden schlug fehl."
+#: ../../Zotlabs/Module/Setup.php:662
+msgid ""
+"Url rewrite in .htaccess is not working. Check your server "
+"configuration.Test: "
+msgstr "Das Umschreiben von URLs (rewrite) per .htaccess funktioniert nicht. Bitte prüfe die Server-Konfiguration. Test:"
-#: ../../Zotlabs/Module/Cover_photo.php:134
-#: ../../Zotlabs/Module/Cover_photo.php:181
-msgid "Cover Photos"
-msgstr "Cover Foto"
+#: ../../Zotlabs/Module/Setup.php:665
+msgid "Url rewrite is working"
+msgstr "Url rewrite funktioniert"
-#: ../../Zotlabs/Module/Cover_photo.php:154
-#: ../../Zotlabs/Module/Profile_photo.php:135
-msgid "Image resize failed."
-msgstr "Bild-Anpassung fehlgeschlagen."
+#: ../../Zotlabs/Module/Setup.php:679
+msgid ""
+"The database configuration file \".htconfig.php\" could not be written. "
+"Please use the enclosed text to create a configuration file in your web "
+"server root."
+msgstr "Die Datenbank-Konfigurationsdatei „.htconfig.php“ konnte nicht geschrieben werden. Bitte verwende den unten angegebenen Text, um die Konfigurationsdatei im Stammverzeichnis des Webservers anzulegen."
-#: ../../Zotlabs/Module/Cover_photo.php:168
-#: ../../Zotlabs/Module/Profile_photo.php:196 ../../include/photos.php:149
-msgid "Unable to process image"
-msgstr "Kann Bild nicht verarbeiten"
+#: ../../Zotlabs/Module/Setup.php:703
+#: ../../addon/rendezvous/rendezvous.php:401
+msgid "Errors encountered creating database tables."
+msgstr "Fehler beim Anlegen der Datenbank-Tabellen aufgetreten."
-#: ../../Zotlabs/Module/Cover_photo.php:192
-#: ../../Zotlabs/Module/Profile_photo.php:231
-msgid "Image upload failed."
-msgstr "Hochladen des Bilds fehlgeschlagen."
+#: ../../Zotlabs/Module/Setup.php:743
+msgid "<h1>What next?</h1>"
+msgstr "<h1>Wie geht es jetzt weiter?</h1>"
-#: ../../Zotlabs/Module/Cover_photo.php:210
-#: ../../Zotlabs/Module/Profile_photo.php:250
-msgid "Unable to process image."
-msgstr "Kann Bild nicht verarbeiten."
+#: ../../Zotlabs/Module/Setup.php:744
+msgid ""
+"IMPORTANT: You will need to [manually] setup a scheduled task for the "
+"poller."
+msgstr "WICHTIG: Du musst [manuell] einen Cronjob für den Poller einrichten."
-#: ../../Zotlabs/Module/Cover_photo.php:233 ../../include/items.php:4253
-msgid "female"
-msgstr "weiblich"
+#: ../../Zotlabs/Module/Connect.php:61 ../../Zotlabs/Module/Connect.php:109
+msgid "Continue"
+msgstr "Fortfahren"
-#: ../../Zotlabs/Module/Cover_photo.php:234 ../../include/items.php:4254
-#, php-format
-msgid "%1$s updated her %2$s"
-msgstr "%1$s hat ihr %2$s aktualisiert"
+#: ../../Zotlabs/Module/Connect.php:90
+msgid "Premium Channel Setup"
+msgstr "Premium-Kanal-Einrichtung"
-#: ../../Zotlabs/Module/Cover_photo.php:235 ../../include/items.php:4255
-msgid "male"
-msgstr "männlich"
+#: ../../Zotlabs/Module/Connect.php:92
+msgid "Enable premium channel connection restrictions"
+msgstr "Einschränkungen für einen Premium-Kanal aktivieren"
-#: ../../Zotlabs/Module/Cover_photo.php:236 ../../include/items.php:4256
-#, php-format
-msgid "%1$s updated his %2$s"
-msgstr "%1$s hat sein %2$s aktualisiert"
+#: ../../Zotlabs/Module/Connect.php:93
+msgid ""
+"Please enter your restrictions or conditions, such as paypal receipt, usage "
+"guidelines, etc."
+msgstr "Bitte gib Deine Nutzungsbedingungen ein, z.B. Paypal-Quittung, Richtlinien etc."
-#: ../../Zotlabs/Module/Cover_photo.php:238 ../../include/items.php:4258
-#, php-format
-msgid "%1$s updated their %2$s"
-msgstr "%1$s hat sein/ihr %2$s aktualisiert"
+#: ../../Zotlabs/Module/Connect.php:95 ../../Zotlabs/Module/Connect.php:115
+msgid ""
+"This channel may require additional steps or acknowledgement of the "
+"following conditions prior to connecting:"
+msgstr "Unter Umständen sind weitere Schritte oder die Bestätigung der folgenden Bedingungen vor dem Verbinden mit diesem Kanal nötig."
-#: ../../Zotlabs/Module/Cover_photo.php:240 ../../include/channel.php:1677
-msgid "cover photo"
-msgstr "Cover Foto"
+#: ../../Zotlabs/Module/Connect.php:96
+msgid ""
+"Potential connections will then see the following text before proceeding:"
+msgstr "Potentielle Kontakte werden den folgenden Text sehen, bevor fortgefahren wird:"
-#: ../../Zotlabs/Module/Cover_photo.php:303
-#: ../../Zotlabs/Module/Cover_photo.php:318
-#: ../../Zotlabs/Module/Profile_photo.php:311
-#: ../../Zotlabs/Module/Profile_photo.php:352
-msgid "Photo not available."
-msgstr "Foto nicht verfügbar."
+#: ../../Zotlabs/Module/Connect.php:97 ../../Zotlabs/Module/Connect.php:118
+msgid ""
+"By continuing, I certify that I have complied with any instructions provided"
+" on this page."
+msgstr "Indem ich fortfahre, bestätige ich die Erfüllung aller Anweisungen auf dieser Seite."
-#: ../../Zotlabs/Module/Cover_photo.php:354
-#: ../../Zotlabs/Module/Profile_photo.php:407
-msgid "Upload File:"
-msgstr "Datei hochladen:"
+#: ../../Zotlabs/Module/Connect.php:106
+msgid "(No specific instructions have been provided by the channel owner.)"
+msgstr "(Der Kanal-Besitzer hat keine speziellen Anweisungen hinterlegt.)"
-#: ../../Zotlabs/Module/Cover_photo.php:355
-#: ../../Zotlabs/Module/Profile_photo.php:408
-msgid "Select a profile:"
-msgstr "Wähle ein Profil:"
+#: ../../Zotlabs/Module/Connect.php:114
+msgid "Restricted or Premium Channel"
+msgstr "Eingeschränkter oder Premium-Kanal"
-#: ../../Zotlabs/Module/Cover_photo.php:356
-msgid "Upload Cover Photo"
-msgstr "Cover Foto hochladen"
+#: ../../Zotlabs/Module/Admin/Queue.php:35
+msgid "Queue Statistics"
+msgstr "Warteschlangenstatistiken"
-#: ../../Zotlabs/Module/Cover_photo.php:361
-#: ../../Zotlabs/Module/Profile_photo.php:416
-#: ../../Zotlabs/Module/Settings/Channel.php:399
-msgid "or"
-msgstr "oder"
+#: ../../Zotlabs/Module/Admin/Queue.php:36
+msgid "Total Entries"
+msgstr "Einträge insgesamt"
-#: ../../Zotlabs/Module/Cover_photo.php:361
-#: ../../Zotlabs/Module/Profile_photo.php:416
-msgid "skip this step"
-msgstr "diesen Schritt überspringen"
+#: ../../Zotlabs/Module/Admin/Queue.php:37
+msgid "Priority"
+msgstr "Priorität"
-#: ../../Zotlabs/Module/Cover_photo.php:361
-#: ../../Zotlabs/Module/Profile_photo.php:416
-msgid "select a photo from your photo albums"
-msgstr "ein Foto aus meinen Fotoalben"
+#: ../../Zotlabs/Module/Admin/Queue.php:38
+msgid "Destination URL"
+msgstr "Ziel-URL"
-#: ../../Zotlabs/Module/Cover_photo.php:377
-#: ../../Zotlabs/Module/Profile_photo.php:435
-msgid "Crop Image"
-msgstr "Bild zuschneiden"
+#: ../../Zotlabs/Module/Admin/Queue.php:39
+msgid "Mark hub permanently offline"
+msgstr "Hub als permanent offline markieren"
-#: ../../Zotlabs/Module/Cover_photo.php:378
-#: ../../Zotlabs/Module/Profile_photo.php:436
-msgid "Please adjust the image cropping for optimum viewing."
-msgstr "Bitte schneide das Bild für eine optimale Anzeige passend zu."
+#: ../../Zotlabs/Module/Admin/Queue.php:40
+msgid "Empty queue for this hub"
+msgstr "Warteschlange für diesen Hub leeren"
-#: ../../Zotlabs/Module/Cover_photo.php:380
-#: ../../Zotlabs/Module/Profile_photo.php:438
-msgid "Done Editing"
-msgstr "Bearbeitung fertigstellen"
+#: ../../Zotlabs/Module/Admin/Queue.php:41
+msgid "Last known contact"
+msgstr "Letzter Kontakt"
#: ../../Zotlabs/Module/Admin/Features.php:55
#: ../../Zotlabs/Module/Admin/Features.php:56
@@ -1723,476 +2151,191 @@ msgstr "Blockiere die Funktion %s"
msgid "Manage Additional Features"
msgstr "Zusätzliche Funktionen verwalten"
-#: ../../Zotlabs/Module/Admin/Logs.php:28
-msgid "Log settings updated."
-msgstr "Protokoll-Einstellungen aktualisiert."
+#: ../../Zotlabs/Module/Admin/Dbsync.php:19
+msgid "Update has been marked successful"
+msgstr "Update wurde als erfolgreich markiert"
-#: ../../Zotlabs/Module/Admin/Logs.php:82
-#: ../../Zotlabs/Module/Admin/Plugins.php:336
-#: ../../Zotlabs/Module/Admin/Plugins.php:427
-#: ../../Zotlabs/Module/Admin/Security.php:86
-#: ../../Zotlabs/Module/Admin/Themes.php:120
-#: ../../Zotlabs/Module/Admin/Themes.php:154
-#: ../../Zotlabs/Module/Admin/Accounts.php:164
-#: ../../Zotlabs/Module/Admin/Channels.php:145
-#: ../../Zotlabs/Module/Admin/Site.php:258 ../../Zotlabs/Module/Admin.php:137
-msgid "Administration"
-msgstr "Administration"
+#: ../../Zotlabs/Module/Admin/Dbsync.php:29
+#, php-format
+msgid "Executing %s failed. Check system logs."
+msgstr "Ausführen von %s fehlgeschlagen. Überprüfe die Systemprotokolle."
-#: ../../Zotlabs/Module/Admin/Logs.php:83 ../../include/widgets.php:1658
-#: ../../include/widgets.php:1668
-msgid "Logs"
-msgstr "Protokolle"
+#: ../../Zotlabs/Module/Admin/Dbsync.php:32
+#, php-format
+msgid "Update %s was successfully applied."
+msgstr "Update %s wurde erfolgreich ausgeführt."
-#: ../../Zotlabs/Module/Admin/Logs.php:85
-msgid "Clear"
-msgstr "Leeren"
+#: ../../Zotlabs/Module/Admin/Dbsync.php:36
+#, php-format
+msgid "Update %s did not return a status. Unknown if it succeeded."
+msgstr "Update %s lieferte keinen Rückgabewert. Erfolg unbekannt."
-#: ../../Zotlabs/Module/Admin/Logs.php:91
-msgid "Debugging"
-msgstr "Debugging"
+#: ../../Zotlabs/Module/Admin/Dbsync.php:39
+#, php-format
+msgid "Update function %s could not be found."
+msgstr "Update-Funktion %s konnte nicht gefunden werden."
-#: ../../Zotlabs/Module/Admin/Logs.php:92
-msgid "Log file"
-msgstr "Protokolldatei"
+#: ../../Zotlabs/Module/Admin/Dbsync.php:55
+msgid "No failed updates."
+msgstr "Keine fehlgeschlagenen Aktualisierungen."
-#: ../../Zotlabs/Module/Admin/Logs.php:92
-msgid ""
-"Must be writable by web server. Relative to your top-level webserver "
-"directory."
-msgstr "Muss für den Web-Server schreibbar sein. Relativ zum Hubzilla-Stammverzeichnis."
+#: ../../Zotlabs/Module/Admin/Dbsync.php:59
+msgid "Failed Updates"
+msgstr "Fehlgeschlagene Aktualisierungen"
-#: ../../Zotlabs/Module/Admin/Logs.php:93
-msgid "Log level"
-msgstr "Protokollstufe"
+#: ../../Zotlabs/Module/Admin/Dbsync.php:61
+msgid "Mark success (if update was manually applied)"
+msgstr "Als erfolgreich markieren (wenn das Update manuell ausgeführt wurde)"
-#: ../../Zotlabs/Module/Admin/Plugins.php:254
-#: ../../Zotlabs/Module/Admin/Themes.php:69
-#: ../../Zotlabs/Module/Filestorage.php:32 ../../Zotlabs/Module/Display.php:40
-#: ../../Zotlabs/Module/Admin.php:60 ../../Zotlabs/Module/Thing.php:89
-#: ../../Zotlabs/Module/Viewsrc.php:24 ../../include/items.php:3343
+#: ../../Zotlabs/Module/Admin/Dbsync.php:62
+msgid "Attempt to execute this update step automatically"
+msgstr "Versuche, diesen Updateschritt automatisch auszuführen"
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:259
+#: ../../Zotlabs/Module/Admin/Themes.php:72 ../../Zotlabs/Module/Thing.php:89
+#: ../../Zotlabs/Module/Viewsrc.php:25 ../../Zotlabs/Module/Display.php:33
+#: ../../Zotlabs/Module/Display.php:347
+#: ../../Zotlabs/Module/Filestorage.php:24 ../../Zotlabs/Module/Admin.php:62
+#: ../../include/items.php:3410
msgid "Item not found."
msgstr "Element nicht gefunden."
-#: ../../Zotlabs/Module/Admin/Plugins.php:284
+#: ../../Zotlabs/Module/Admin/Plugins.php:289
#, php-format
msgid "Plugin %s disabled."
msgstr "Plug-In %s deaktiviert."
-#: ../../Zotlabs/Module/Admin/Plugins.php:289
+#: ../../Zotlabs/Module/Admin/Plugins.php:294
#, php-format
msgid "Plugin %s enabled."
msgstr "Plug-In %s aktiviert."
-#: ../../Zotlabs/Module/Admin/Plugins.php:305
-#: ../../Zotlabs/Module/Admin/Themes.php:93
+#: ../../Zotlabs/Module/Admin/Plugins.php:310
+#: ../../Zotlabs/Module/Admin/Themes.php:95
msgid "Disable"
msgstr "Deaktivieren"
-#: ../../Zotlabs/Module/Admin/Plugins.php:308
-#: ../../Zotlabs/Module/Admin/Themes.php:95
+#: ../../Zotlabs/Module/Admin/Plugins.php:313
+#: ../../Zotlabs/Module/Admin/Themes.php:97
msgid "Enable"
msgstr "Aktivieren"
-#: ../../Zotlabs/Module/Admin/Plugins.php:337
-#: ../../Zotlabs/Module/Admin/Plugins.php:428 ../../include/widgets.php:1636
+#: ../../Zotlabs/Module/Admin/Plugins.php:341
+#: ../../Zotlabs/Module/Admin/Plugins.php:436
+#: ../../Zotlabs/Module/Admin/Accounts.php:164
+#: ../../Zotlabs/Module/Admin/Logs.php:82
+#: ../../Zotlabs/Module/Admin/Channels.php:145
+#: ../../Zotlabs/Module/Admin/Themes.php:122
+#: ../../Zotlabs/Module/Admin/Themes.php:156
+#: ../../Zotlabs/Module/Admin/Site.php:271
+#: ../../Zotlabs/Module/Admin/Security.php:86
+#: ../../Zotlabs/Module/Admin.php:136
+msgid "Administration"
+msgstr "Administration"
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:342
+#: ../../Zotlabs/Module/Admin/Plugins.php:437
+#: ../../Zotlabs/Widget/Admin.php:27
msgid "Plugins"
msgstr "Plug-Ins"
-#: ../../Zotlabs/Module/Admin/Plugins.php:338
-#: ../../Zotlabs/Module/Admin/Themes.php:122
+#: ../../Zotlabs/Module/Admin/Plugins.php:343
+#: ../../Zotlabs/Module/Admin/Themes.php:124
msgid "Toggle"
msgstr "Umschalten"
-#: ../../Zotlabs/Module/Admin/Plugins.php:339
-#: ../../Zotlabs/Module/Admin/Themes.php:123 ../../Zotlabs/Lib/Apps.php:216
-#: ../../include/nav.php:211 ../../include/widgets.php:680
+#: ../../Zotlabs/Module/Admin/Plugins.php:344
+#: ../../Zotlabs/Module/Admin/Themes.php:125 ../../Zotlabs/Lib/Apps.php:236
+#: ../../Zotlabs/Widget/Settings_menu.php:133 ../../include/nav.php:132
+#: ../../include/nav.php:217
msgid "Settings"
msgstr "Einstellungen"
-#: ../../Zotlabs/Module/Admin/Plugins.php:346
-#: ../../Zotlabs/Module/Admin/Themes.php:132
+#: ../../Zotlabs/Module/Admin/Plugins.php:351
+#: ../../Zotlabs/Module/Admin/Themes.php:134
msgid "Author: "
msgstr "Autor: "
-#: ../../Zotlabs/Module/Admin/Plugins.php:347
-#: ../../Zotlabs/Module/Admin/Themes.php:133
+#: ../../Zotlabs/Module/Admin/Plugins.php:352
+#: ../../Zotlabs/Module/Admin/Themes.php:135
msgid "Maintainer: "
msgstr "Betreuer:"
-#: ../../Zotlabs/Module/Admin/Plugins.php:348
+#: ../../Zotlabs/Module/Admin/Plugins.php:353
msgid "Minimum project version: "
msgstr "Minimale Version des Projekts:"
-#: ../../Zotlabs/Module/Admin/Plugins.php:349
+#: ../../Zotlabs/Module/Admin/Plugins.php:354
msgid "Maximum project version: "
msgstr "Maximale Version des Projekts:"
-#: ../../Zotlabs/Module/Admin/Plugins.php:350
+#: ../../Zotlabs/Module/Admin/Plugins.php:355
msgid "Minimum PHP version: "
msgstr "Minimale PHP Version:"
-#: ../../Zotlabs/Module/Admin/Plugins.php:351
+#: ../../Zotlabs/Module/Admin/Plugins.php:356
msgid "Compatible Server Roles: "
msgstr "Kompatible Serverrollen: "
-#: ../../Zotlabs/Module/Admin/Plugins.php:352
+#: ../../Zotlabs/Module/Admin/Plugins.php:357
msgid "Requires: "
msgstr "Benötigt:"
-#: ../../Zotlabs/Module/Admin/Plugins.php:353
-#: ../../Zotlabs/Module/Admin/Plugins.php:433
+#: ../../Zotlabs/Module/Admin/Plugins.php:358
+#: ../../Zotlabs/Module/Admin/Plugins.php:442
msgid "Disabled - version incompatibility"
msgstr "Abgeschaltet - Versionsinkompatibilität"
-#: ../../Zotlabs/Module/Admin/Plugins.php:402
+#: ../../Zotlabs/Module/Admin/Plugins.php:411
msgid "Enter the public git repository URL of the plugin repo."
msgstr "Gib die öffentliche Git-Repository-URL des Plugin-Repository an."
-#: ../../Zotlabs/Module/Admin/Plugins.php:403
+#: ../../Zotlabs/Module/Admin/Plugins.php:412
msgid "Plugin repo git URL"
msgstr "Plugin-Repository Git URL"
-#: ../../Zotlabs/Module/Admin/Plugins.php:404
+#: ../../Zotlabs/Module/Admin/Plugins.php:413
msgid "Custom repo name"
msgstr "Benutzerdefinierter Repository-Name"
-#: ../../Zotlabs/Module/Admin/Plugins.php:404
+#: ../../Zotlabs/Module/Admin/Plugins.php:413
msgid "(optional)"
msgstr "(optional)"
-#: ../../Zotlabs/Module/Admin/Plugins.php:405
+#: ../../Zotlabs/Module/Admin/Plugins.php:414
msgid "Download Plugin Repo"
msgstr "Plugin-Repository herunterladen"
-#: ../../Zotlabs/Module/Admin/Plugins.php:412
+#: ../../Zotlabs/Module/Admin/Plugins.php:421
msgid "Install new repo"
msgstr "Neues Repository installieren"
-#: ../../Zotlabs/Module/Admin/Plugins.php:413 ../../Zotlabs/Lib/Apps.php:334
+#: ../../Zotlabs/Module/Admin/Plugins.php:422 ../../Zotlabs/Lib/Apps.php:383
msgid "Install"
msgstr "Installieren"
-#: ../../Zotlabs/Module/Admin/Plugins.php:414
-#: ../../Zotlabs/Module/Fbrowser.php:66 ../../Zotlabs/Module/Fbrowser.php:88
-#: ../../Zotlabs/Module/Wiki.php:242 ../../Zotlabs/Module/Wiki.php:277
-#: ../../Zotlabs/Module/Settings/Oauth.php:88
-#: ../../Zotlabs/Module/Settings/Oauth.php:114
-#: ../../Zotlabs/Module/Tagrm.php:15 ../../Zotlabs/Module/Tagrm.php:138
-#: ../../extend/addon/addon/friendica/dfrn_request.php:879
-#: ../../extend/addon/addon/js_upload/js_upload.php:46
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:866
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1154
-#: ../../include/conversation.php:1264 ../../include/conversation.php:1313
-msgid "Cancel"
-msgstr "Abbrechen"
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:435
+#: ../../Zotlabs/Module/Admin/Plugins.php:445
msgid "Manage Repos"
msgstr "Repositorien verwalten"
-#: ../../Zotlabs/Module/Admin/Plugins.php:436
+#: ../../Zotlabs/Module/Admin/Plugins.php:446
msgid "Installed Plugin Repositories"
msgstr "Installierte Plugin-Repositorien"
-#: ../../Zotlabs/Module/Admin/Plugins.php:437
+#: ../../Zotlabs/Module/Admin/Plugins.php:447
msgid "Install a New Plugin Repository"
msgstr "Ein neues Plugin-Repository installieren"
-#: ../../Zotlabs/Module/Admin/Plugins.php:443
-#: ../../Zotlabs/Module/Settings/Oauth.php:42
-#: ../../Zotlabs/Module/Settings/Oauth.php:113 ../../Zotlabs/Lib/Apps.php:334
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1152
-msgid "Update"
-msgstr "Aktualisieren"
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:444
+#: ../../Zotlabs/Module/Admin/Plugins.php:454
msgid "Switch branch"
msgstr "Zweig/Branch wechseln"
-#: ../../Zotlabs/Module/Admin/Plugins.php:445
-#: ../../Zotlabs/Module/Photos.php:989 ../../Zotlabs/Module/Tagrm.php:137
-#: ../../extend/addon/addon/superblock/superblock.php:110
+#: ../../Zotlabs/Module/Admin/Plugins.php:455
+#: ../../Zotlabs/Module/Photos.php:967 ../../Zotlabs/Module/Tagrm.php:137
+#: ../../addon/superblock/superblock.php:116
msgid "Remove"
msgstr "Entfernen"
-#: ../../Zotlabs/Module/Admin/Profs.php:69
-msgid "New Profile Field"
-msgstr "Neues Profilfeld"
-
-#: ../../Zotlabs/Module/Admin/Profs.php:70
-#: ../../Zotlabs/Module/Admin/Profs.php:90
-msgid "Field nickname"
-msgstr "Kurzname für das Feld"
-
-#: ../../Zotlabs/Module/Admin/Profs.php:70
-#: ../../Zotlabs/Module/Admin/Profs.php:90
-msgid "System name of field"
-msgstr "Systemname des Feldes"
-
-#: ../../Zotlabs/Module/Admin/Profs.php:71
-#: ../../Zotlabs/Module/Admin/Profs.php:91
-msgid "Input type"
-msgstr "Art des Inhalts"
-
-#: ../../Zotlabs/Module/Admin/Profs.php:72
-#: ../../Zotlabs/Module/Admin/Profs.php:92
-msgid "Field Name"
-msgstr "Feldname"
-
-#: ../../Zotlabs/Module/Admin/Profs.php:72
-#: ../../Zotlabs/Module/Admin/Profs.php:92
-msgid "Label on profile pages"
-msgstr "Bezeichnung auf Profilseiten"
-
-#: ../../Zotlabs/Module/Admin/Profs.php:73
-#: ../../Zotlabs/Module/Admin/Profs.php:93
-msgid "Help text"
-msgstr "Hilfetext"
-
-#: ../../Zotlabs/Module/Admin/Profs.php:73
-#: ../../Zotlabs/Module/Admin/Profs.php:93
-msgid "Additional info (optional)"
-msgstr "Zusätzliche Informationen (optional)"
-
-#: ../../Zotlabs/Module/Admin/Profs.php:83
-msgid "Field definition not found"
-msgstr "Feld-Definition nicht gefunden"
-
-#: ../../Zotlabs/Module/Admin/Profs.php:89
-msgid "Edit Profile Field"
-msgstr "Profilfeld bearbeiten"
-
-#: ../../Zotlabs/Module/Admin/Profs.php:147 ../../include/widgets.php:1639
-msgid "Profile Fields"
-msgstr "Profil Felder"
-
-#: ../../Zotlabs/Module/Admin/Profs.php:148
-msgid "Basic Profile Fields"
-msgstr "Notwendige Profil Felder"
-
-#: ../../Zotlabs/Module/Admin/Profs.php:149
-msgid "Advanced Profile Fields"
-msgstr "Erweiterte Profil Felder"
-
-#: ../../Zotlabs/Module/Admin/Profs.php:149
-msgid "(In addition to basic fields)"
-msgstr "(zusätzlich zu notwendige Felder)"
-
-#: ../../Zotlabs/Module/Admin/Profs.php:151
-msgid "All available fields"
-msgstr "Alle verfügbaren Felder"
-
-#: ../../Zotlabs/Module/Admin/Profs.php:152
-msgid "Custom Fields"
-msgstr "Benutzerdefinierte Felder"
-
-#: ../../Zotlabs/Module/Admin/Profs.php:156
-msgid "Create Custom Field"
-msgstr "Erstelle benutzerdefiniertes Feld"
-
-#: ../../Zotlabs/Module/Admin/Queue.php:36
-msgid "Queue Statistics"
-msgstr "Warteschlangenstatistiken"
-
-#: ../../Zotlabs/Module/Admin/Queue.php:37
-msgid "Total Entries"
-msgstr "Einträge insgesamt"
-
-#: ../../Zotlabs/Module/Admin/Queue.php:38
-msgid "Priority"
-msgstr "Priorität"
-
-#: ../../Zotlabs/Module/Admin/Queue.php:39
-msgid "Destination URL"
-msgstr "Ziel-URL"
-
-#: ../../Zotlabs/Module/Admin/Queue.php:40
-msgid "Mark hub permanently offline"
-msgstr "Hub als permanent offline markieren"
-
-#: ../../Zotlabs/Module/Admin/Queue.php:41
-msgid "Empty queue for this hub"
-msgstr "Warteschlange für diesen Hub leeren"
-
-#: ../../Zotlabs/Module/Admin/Queue.php:42
-msgid "Last known contact"
-msgstr "Letzter Kontakt"
-
-#: ../../Zotlabs/Module/Admin/Security.php:77
-msgid ""
-"By default, unfiltered HTML is allowed in embedded media. This is inherently"
-" insecure."
-msgstr "Standardmäßig wird ungefiltertes HTML in eingebetteten Inhalten zugelassen. Das ist prinzipiell unsicher."
-
-#: ../../Zotlabs/Module/Admin/Security.php:80
-msgid ""
-"The recommended setting is to only allow unfiltered HTML from the following "
-"sites:"
-msgstr "Die empfohlene Einstellung ist, ungefiltertes HTML nur von den nachfolgenden Webseiten zu erlauben:"
-
-#: ../../Zotlabs/Module/Admin/Security.php:81
-msgid ""
-"https://youtube.com/<br />https://www.youtube.com/<br />https://youtu.be/<br"
-" />https://vimeo.com/<br />https://soundcloud.com/<br />"
-msgstr "https://youtube.com/<br />https://www.youtube.com/<br />https://youtu.be/<br />https://vimeo.com/<br />https://soundcloud.com/<br />"
-
-#: ../../Zotlabs/Module/Admin/Security.php:82
-msgid ""
-"All other embedded content will be filtered, <strong>unless</strong> "
-"embedded content from that site is explicitly blocked."
-msgstr "Alle anderen eingebetteten Inhalte werden gefiltert, <strong>es sei denn</strong>, eingebettete Inhalte von einer bestimmten Seite sind explizit blockiert."
-
-#: ../../Zotlabs/Module/Admin/Security.php:87 ../../include/widgets.php:1634
-msgid "Security"
-msgstr "Sicherheit"
-
-#: ../../Zotlabs/Module/Admin/Security.php:89
-msgid "Block public"
-msgstr "Öffentlichen Zugriff blockieren"
-
-#: ../../Zotlabs/Module/Admin/Security.php:89
-msgid ""
-"Check to block public access to all otherwise public personal pages on this "
-"site unless you are currently authenticated."
-msgstr "Blockiere den öffentlichen Zugriff auf alle ansonsten öffentlichen persönlichen Seiten dieser Website, sofern ein Besucher nicht angemeldet ist."
-
-#: ../../Zotlabs/Module/Admin/Security.php:90
-msgid "Set \"Transport Security\" HTTP header"
-msgstr "Setze den \"Transport Security\" HTTP Header"
-
-#: ../../Zotlabs/Module/Admin/Security.php:91
-msgid "Set \"Content Security Policy\" HTTP header"
-msgstr "Setze den \"Content Security Policy\" HTTP Header"
-
-#: ../../Zotlabs/Module/Admin/Security.php:92
-msgid "Allowed email domains"
-msgstr "Erlaubte Domains für E-Mails"
-
-#: ../../Zotlabs/Module/Admin/Security.php:92
-msgid ""
-"Comma separated list of domains which are allowed in email addresses for "
-"registrations to this site. Wildcards are accepted. Empty to allow any "
-"domains"
-msgstr "Liste der Domains, die für E-Mail-Adressen bei der Registrierung erlaubt sind, durch Kommas getrennt. Platzhalter werden akzeptiert. Leer lassen, um alle Domains zu erlauben."
-
-#: ../../Zotlabs/Module/Admin/Security.php:93
-msgid "Not allowed email domains"
-msgstr "Nicht erlaubte Domains für E-Mails"
-
-#: ../../Zotlabs/Module/Admin/Security.php:93
-msgid ""
-"Comma separated list of domains which are not allowed in email addresses for"
-" registrations to this site. Wildcards are accepted. Empty to allow any "
-"domains, unless allowed domains have been defined."
-msgstr "Domains in E-Mail-Adressen, die keine Erlaubnis erhalten, sich auf Deinem Hub zu registrieren. Mehrere Domains können durch Kommas getrennt werden. Platzhalter (*/?) sind möglich. Keine Eingabe bedeutet keine Einschränkung, unabhängig davon, ob unter erlaubte Domains etwas eingegeben wurde."
-
-#: ../../Zotlabs/Module/Admin/Security.php:94
-msgid "Allow communications only from these sites"
-msgstr "Kommunikation nur von diesen Seiten erlauben"
-
-#: ../../Zotlabs/Module/Admin/Security.php:94
-msgid ""
-"One site per line. Leave empty to allow communication from anywhere by "
-"default"
-msgstr "Ein Eintrag pro Zeile. Lasse das Feld leer, um Kommunikation grundlegend von überall her zu erlauben."
-
-#: ../../Zotlabs/Module/Admin/Security.php:95
-msgid "Block communications from these sites"
-msgstr "Kommunikation von diesen Seiten blockieren"
-
-#: ../../Zotlabs/Module/Admin/Security.php:96
-msgid "Allow communications only from these channels"
-msgstr "Kommunikation nur von diesen Kanälen erlauben"
-
-#: ../../Zotlabs/Module/Admin/Security.php:96
-msgid ""
-"One channel (hash) per line. Leave empty to allow from any channel by "
-"default"
-msgstr "Ein Kanal (hash) pro Zeile. Leerlassen um jeden Kanal zuzulassen. "
-
-#: ../../Zotlabs/Module/Admin/Security.php:97
-msgid "Block communications from these channels"
-msgstr "Kommunikation von folgenden Kanälen blockieren"
-
-#: ../../Zotlabs/Module/Admin/Security.php:98
-msgid "Only allow embeds from secure (SSL) websites and links."
-msgstr "Erlaube Einbettungen nur von sicheren (SSL) Webseiten und Links."
-
-#: ../../Zotlabs/Module/Admin/Security.php:99
-msgid "Allow unfiltered embedded HTML content only from these domains"
-msgstr "Erlaube Einbettung von Inhalten mit ungefiltertem HTML nur von diesen Domains"
-
-#: ../../Zotlabs/Module/Admin/Security.php:99
-msgid "One site per line. By default embedded content is filtered."
-msgstr "Eine Website/Domain pro Zeile. Standardmäßig wird eingebetteter Inhalt gefiltert."
-
-#: ../../Zotlabs/Module/Admin/Security.php:100
-msgid "Block embedded HTML from these domains"
-msgstr "Eingebettete HTML Inhalte von diesen Seiten blockieren"
-
-#: ../../Zotlabs/Module/Admin/Themes.php:18
-msgid "Theme settings updated."
-msgstr "Theme-Einstellungen aktualisiert."
-
-#: ../../Zotlabs/Module/Admin/Themes.php:58
-msgid "No themes found."
-msgstr "Keine Theme gefunden."
-
-#: ../../Zotlabs/Module/Admin/Themes.php:114
-msgid "Screenshot"
-msgstr "Bildschirmfoto"
-
-#: ../../Zotlabs/Module/Admin/Themes.php:121
-#: ../../Zotlabs/Module/Admin/Themes.php:155 ../../include/widgets.php:1637
-msgid "Themes"
-msgstr "Themes"
-
-#: ../../Zotlabs/Module/Admin/Themes.php:160
-msgid "[Experimental]"
-msgstr "[Experimentell]"
-
-#: ../../Zotlabs/Module/Admin/Themes.php:161
-msgid "[Unsupported]"
-msgstr "[Nicht unterstützt]"
-
-#: ../../Zotlabs/Module/Admin/Account_edit.php:29
-#, php-format
-msgid "Password changed for account %d."
-msgstr "Passwort für Konto %d geändert."
-
-#: ../../Zotlabs/Module/Admin/Account_edit.php:46
-msgid "Account settings updated."
-msgstr "Kontoeinstellungen aktualisiert."
-
-#: ../../Zotlabs/Module/Admin/Account_edit.php:61
-msgid "Account not found."
-msgstr "Konto nicht gefunden."
-
-#: ../../Zotlabs/Module/Admin/Account_edit.php:68
-msgid "Account Edit"
-msgstr "Kontobearbeitung"
-
-#: ../../Zotlabs/Module/Admin/Account_edit.php:69
-msgid "New Password"
-msgstr "Neues Passwort"
-
-#: ../../Zotlabs/Module/Admin/Account_edit.php:70
-msgid "New Password again"
-msgstr "Neues Passwort wiederholen"
-
-#: ../../Zotlabs/Module/Admin/Account_edit.php:71
-msgid "Technical skill level"
-msgstr "Technische Qualifikationsstufe"
-
-#: ../../Zotlabs/Module/Admin/Account_edit.php:72
-msgid "Account language (for emails)"
-msgstr "Kontosprache (für E-Mails)"
-
-#: ../../Zotlabs/Module/Admin/Account_edit.php:73
-msgid "Service class"
-msgstr "Dienstklasse"
-
#: ../../Zotlabs/Module/Admin/Accounts.php:36
#, php-format
msgid "%s account blocked/unblocked"
@@ -2211,7 +2354,7 @@ msgstr[1] "%s Konten gelöscht"
msgid "Account not found"
msgstr "Konto nicht gefunden"
-#: ../../Zotlabs/Module/Admin/Accounts.php:90
+#: ../../Zotlabs/Module/Admin/Accounts.php:90 ../../include/channel.php:2357
#, php-format
msgid "Account '%s' deleted"
msgstr "Konto '%s' gelöscht"
@@ -2227,7 +2370,8 @@ msgid "Account '%s' unblocked"
msgstr "Konto '%s' freigegeben"
#: ../../Zotlabs/Module/Admin/Accounts.php:165
-#: ../../Zotlabs/Module/Admin/Accounts.php:178 ../../include/widgets.php:1632
+#: ../../Zotlabs/Module/Admin/Accounts.php:178
+#: ../../Zotlabs/Module/Admin.php:96 ../../Zotlabs/Widget/Admin.php:23
msgid "Accounts"
msgstr "Konten"
@@ -2244,30 +2388,34 @@ msgstr "Registrierungen warten auf Bestätigung"
msgid "Request date"
msgstr "Antragsdatum"
-#: ../../Zotlabs/Module/Admin/Accounts.php:169
-#: ../../Zotlabs/Module/Admin/Accounts.php:181
-#: ../../extend/addon/addon/redred/redred.php:107
-#: ../../extend/addon/addon/rtof/rtof.php:93
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1140
-#: ../../extend/addon/addon/openid/MysqlProvider.php:56
-#: ../../extend/addon/addon/openid/MysqlProvider.php:57
-#: ../../include/network.php:2237
-msgid "Email"
-msgstr "E-Mail"
-
#: ../../Zotlabs/Module/Admin/Accounts.php:170
msgid "No registrations."
msgstr "Keine Registrierungen."
+#: ../../Zotlabs/Module/Admin/Accounts.php:171
+#: ../../Zotlabs/Module/Connections.php:282 ../../include/conversation.php:716
+msgid "Approve"
+msgstr "Genehmigen"
+
#: ../../Zotlabs/Module/Admin/Accounts.php:172
msgid "Deny"
msgstr "Verweigern"
+#: ../../Zotlabs/Module/Admin/Accounts.php:174
+#: ../../Zotlabs/Module/Connedit.php:622
+msgid "Block"
+msgstr "Blockieren"
+
+#: ../../Zotlabs/Module/Admin/Accounts.php:175
+#: ../../Zotlabs/Module/Connedit.php:622
+msgid "Unblock"
+msgstr "Freigeben"
+
#: ../../Zotlabs/Module/Admin/Accounts.php:180
msgid "ID"
msgstr "ID"
-#: ../../Zotlabs/Module/Admin/Accounts.php:182 ../../include/group.php:267
+#: ../../Zotlabs/Module/Admin/Accounts.php:182 ../../include/group.php:288
msgid "All Channels"
msgstr "Alle Kanäle"
@@ -2299,6 +2447,37 @@ msgid ""
"this site will be permanently deleted!\\n\\nAre you sure?"
msgstr "Das Konto {0} wird gelöscht!\\n\\nAlles, was dieses Konto auf diesem Hub veröffentlicht hat, wird endgültig gelöscht werden!\\n\\nBist Du sicher?"
+#: ../../Zotlabs/Module/Admin/Logs.php:28
+msgid "Log settings updated."
+msgstr "Protokoll-Einstellungen aktualisiert."
+
+#: ../../Zotlabs/Module/Admin/Logs.php:83 ../../Zotlabs/Widget/Admin.php:48
+#: ../../Zotlabs/Widget/Admin.php:58
+msgid "Logs"
+msgstr "Protokolle"
+
+#: ../../Zotlabs/Module/Admin/Logs.php:85
+msgid "Clear"
+msgstr "Leeren"
+
+#: ../../Zotlabs/Module/Admin/Logs.php:91
+msgid "Debugging"
+msgstr "Debugging"
+
+#: ../../Zotlabs/Module/Admin/Logs.php:92
+msgid "Log file"
+msgstr "Protokolldatei"
+
+#: ../../Zotlabs/Module/Admin/Logs.php:92
+msgid ""
+"Must be writable by web server. Relative to your top-level webserver "
+"directory."
+msgstr "Muss für den Web-Server schreibbar sein. Relativ zum Hubzilla-Stammverzeichnis."
+
+#: ../../Zotlabs/Module/Admin/Logs.php:93
+msgid "Log level"
+msgstr "Protokollstufe"
+
#: ../../Zotlabs/Module/Admin/Channels.php:31
#, php-format
msgid "%s channel censored/uncensored"
@@ -2349,7 +2528,8 @@ msgstr "Code für Kanal '%s' freigegeben"
msgid "Channel '%s' code disallowed"
msgstr "Code für Kanal '%s' gesperrt"
-#: ../../Zotlabs/Module/Admin/Channels.php:146 ../../include/widgets.php:1633
+#: ../../Zotlabs/Module/Admin/Channels.php:146
+#: ../../Zotlabs/Module/Admin.php:110 ../../Zotlabs/Widget/Admin.php:24
msgid "Channels"
msgstr "Kanäle"
@@ -2370,7 +2550,7 @@ msgid "Disallow Code"
msgstr "Code sperren"
#: ../../Zotlabs/Module/Admin/Channels.php:154
-#: ../../include/conversation.php:1671
+#: ../../include/conversation.php:1791 ../../include/nav.php:399
msgid "Channel"
msgstr "Kanal"
@@ -2390,1444 +2570,1735 @@ msgid ""
"channel on this site will be permanently deleted!\\n\\nAre you sure?"
msgstr "Der Kanal {0} wird gelöscht!\\n\\nAlles was von diesem Kanal auf diesem Server geschrieben wurde, wird gelöscht!\\n\\nBist Du sicher?"
-#: ../../Zotlabs/Module/Admin/Dbsync.php:19
-msgid "Update has been marked successful"
-msgstr "Update wurde als erfolgreich markiert"
-
-#: ../../Zotlabs/Module/Admin/Dbsync.php:29
-#, php-format
-msgid "Executing %s failed. Check system logs."
-msgstr "Ausführen von %s fehlgeschlagen. Überprüfe die Systemprotokolle."
-
-#: ../../Zotlabs/Module/Admin/Dbsync.php:32
-#, php-format
-msgid "Update %s was successfully applied."
-msgstr "Update %s wurde erfolgreich ausgeführt."
-
-#: ../../Zotlabs/Module/Admin/Dbsync.php:36
-#, php-format
-msgid "Update %s did not return a status. Unknown if it succeeded."
-msgstr "Update %s lieferte keinen Rückgabewert. Erfolg unbekannt."
+#: ../../Zotlabs/Module/Admin/Themes.php:26
+msgid "Theme settings updated."
+msgstr "Design-Einstellungen aktualisiert."
-#: ../../Zotlabs/Module/Admin/Dbsync.php:39
-#, php-format
-msgid "Update function %s could not be found."
-msgstr "Update-Funktion %s konnte nicht gefunden werden."
+#: ../../Zotlabs/Module/Admin/Themes.php:61
+msgid "No themes found."
+msgstr "Keine Designs gefunden."
-#: ../../Zotlabs/Module/Admin/Dbsync.php:55
-msgid "No failed updates."
-msgstr "Keine fehlgeschlagenen Aktualisierungen."
+#: ../../Zotlabs/Module/Admin/Themes.php:116
+msgid "Screenshot"
+msgstr "Bildschirmfoto"
-#: ../../Zotlabs/Module/Admin/Dbsync.php:59
-msgid "Failed Updates"
-msgstr "Fehlgeschlagene Aktualisierungen"
+#: ../../Zotlabs/Module/Admin/Themes.php:123
+#: ../../Zotlabs/Module/Admin/Themes.php:157 ../../Zotlabs/Widget/Admin.php:28
+msgid "Themes"
+msgstr "Designs"
-#: ../../Zotlabs/Module/Admin/Dbsync.php:61
-msgid "Mark success (if update was manually applied)"
-msgstr "Als erfolgreich markieren (wenn das Update manuell ausgeführt wurde)"
+#: ../../Zotlabs/Module/Admin/Themes.php:162
+msgid "[Experimental]"
+msgstr "[Experimentell]"
-#: ../../Zotlabs/Module/Admin/Dbsync.php:62
-msgid "Attempt to execute this update step automatically"
-msgstr "Versuche, diesen Updateschritt automatisch auszuführen"
+#: ../../Zotlabs/Module/Admin/Themes.php:163
+msgid "[Unsupported]"
+msgstr "[Nicht unterstützt]"
-#: ../../Zotlabs/Module/Admin/Site.php:133
+#: ../../Zotlabs/Module/Admin/Site.php:144
msgid "Site settings updated."
msgstr "Site-Einstellungen aktualisiert."
-#: ../../Zotlabs/Module/Admin/Site.php:159 ../../include/text.php:2918
+#: ../../Zotlabs/Module/Admin/Site.php:170
+#: ../../view/theme/redbasic_c/php/config.php:15
+#: ../../view/theme/redbasic/php/config.php:15 ../../include/text.php:2943
msgid "Default"
msgstr "Standard"
-#: ../../Zotlabs/Module/Admin/Site.php:169
-#: ../../Zotlabs/Module/Settings/Display.php:143
+#: ../../Zotlabs/Module/Admin/Site.php:181
+#: ../../Zotlabs/Module/Settings/Display.php:137
+#, php-format
+msgid "%s - (Incompatible)"
+msgstr "%s - (Inkompatibel)"
+
+#: ../../Zotlabs/Module/Admin/Site.php:188
+#: ../../Zotlabs/Module/Settings/Display.php:151
msgid "mobile"
msgstr "mobil"
-#: ../../Zotlabs/Module/Admin/Site.php:171
+#: ../../Zotlabs/Module/Admin/Site.php:190
msgid "experimental"
msgstr "experimentell"
-#: ../../Zotlabs/Module/Admin/Site.php:173
+#: ../../Zotlabs/Module/Admin/Site.php:192
msgid "unsupported"
msgstr "nicht unterstützt"
-#: ../../Zotlabs/Module/Admin/Site.php:219
+#: ../../Zotlabs/Module/Admin/Site.php:238
msgid "Yes - with approval"
msgstr "Ja - mit Zustimmung"
-#: ../../Zotlabs/Module/Admin/Site.php:225
+#: ../../Zotlabs/Module/Admin/Site.php:244
msgid "My site is not a public server"
msgstr "Mein Server ist kein öffentlicher Server"
-#: ../../Zotlabs/Module/Admin/Site.php:226
+#: ../../Zotlabs/Module/Admin/Site.php:245
msgid "My site has paid access only"
msgstr "Meine Seite hat nur bezahlten Zugriff"
-#: ../../Zotlabs/Module/Admin/Site.php:227
+#: ../../Zotlabs/Module/Admin/Site.php:246
msgid "My site has free access only"
msgstr "Meine Seite hat nur freien Zugriff"
-#: ../../Zotlabs/Module/Admin/Site.php:228
+#: ../../Zotlabs/Module/Admin/Site.php:247
msgid "My site offers free accounts with optional paid upgrades"
msgstr "Mein Server bietet kostenlose Konten mit der Möglichkeit zu bezahlten Upgrades"
-#: ../../Zotlabs/Module/Admin/Site.php:239 ../../Zotlabs/Module/Setup.php:328
-msgid "Basic/Minimal Social Networking"
-msgstr "Einfaches/minimales soziales Netzwerken"
-
-#: ../../Zotlabs/Module/Admin/Site.php:240 ../../Zotlabs/Module/Setup.php:329
-msgid "Standard Configuration (default)"
-msgstr "Standardkonfiguration (Standard)"
-
-#: ../../Zotlabs/Module/Admin/Site.php:241 ../../Zotlabs/Module/Setup.php:330
-msgid "Professional"
-msgstr "Professionell"
-
-#: ../../Zotlabs/Module/Admin/Site.php:245 ../../Zotlabs/Lib/Techlevels.php:10
+#: ../../Zotlabs/Module/Admin/Site.php:258
msgid "Beginner/Basic"
msgstr "Anfänger/Basis"
-#: ../../Zotlabs/Module/Admin/Site.php:246 ../../Zotlabs/Lib/Techlevels.php:11
+#: ../../Zotlabs/Module/Admin/Site.php:259
msgid "Novice - not skilled but willing to learn"
msgstr "Anfänger - unerfahren, aber bereit zu lernen"
-#: ../../Zotlabs/Module/Admin/Site.php:247 ../../Zotlabs/Lib/Techlevels.php:12
+#: ../../Zotlabs/Module/Admin/Site.php:260
msgid "Intermediate - somewhat comfortable"
msgstr "Fortgeschritten - relativ komfortabel"
-#: ../../Zotlabs/Module/Admin/Site.php:248 ../../Zotlabs/Lib/Techlevels.php:13
+#: ../../Zotlabs/Module/Admin/Site.php:261
msgid "Advanced - very comfortable"
msgstr "Fortgeschritten - sehr komfortabel"
-#: ../../Zotlabs/Module/Admin/Site.php:249 ../../Zotlabs/Lib/Techlevels.php:14
+#: ../../Zotlabs/Module/Admin/Site.php:262
msgid "Expert - I can write computer code"
msgstr "Experte - Ich kann Computercode schreiben"
-#: ../../Zotlabs/Module/Admin/Site.php:250 ../../Zotlabs/Lib/Techlevels.php:15
+#: ../../Zotlabs/Module/Admin/Site.php:263
msgid "Wizard - I probably know more than you do"
msgstr "Zauberer - ich kann wahrscheinlich mehr als Du"
-#: ../../Zotlabs/Module/Admin/Site.php:259 ../../include/widgets.php:1631
+#: ../../Zotlabs/Module/Admin/Site.php:272 ../../Zotlabs/Widget/Admin.php:22
msgid "Site"
msgstr "Seite"
-#: ../../Zotlabs/Module/Admin/Site.php:262
+#: ../../Zotlabs/Module/Admin/Site.php:274
+#: ../../Zotlabs/Module/Register.php:251
+msgid "Registration"
+msgstr "Registrierung"
+
+#: ../../Zotlabs/Module/Admin/Site.php:275
msgid "File upload"
msgstr "Dateiupload"
-#: ../../Zotlabs/Module/Admin/Site.php:263
+#: ../../Zotlabs/Module/Admin/Site.php:276
msgid "Policies"
msgstr "Richtlinien"
-#: ../../Zotlabs/Module/Admin/Site.php:264
+#: ../../Zotlabs/Module/Admin/Site.php:277
#: ../../include/contact_widgets.php:16
msgid "Advanced"
msgstr "Fortgeschritten"
-#: ../../Zotlabs/Module/Admin/Site.php:268
-#: ../../extend/addon/addon/statusnet/statusnet.php:890
+#: ../../Zotlabs/Module/Admin/Site.php:281
+#: ../../addon/statusnet/statusnet.php:890
msgid "Site name"
msgstr "Seitenname"
-#: ../../Zotlabs/Module/Admin/Site.php:270 ../../Zotlabs/Module/Setup.php:351
-msgid "Server Configuration/Role"
-msgstr "Serverkonfiguration/Rolle"
-
-#: ../../Zotlabs/Module/Admin/Site.php:272
+#: ../../Zotlabs/Module/Admin/Site.php:283
msgid "Site default technical skill level"
msgstr "Standard-Qualifikationsstufe der Website"
-#: ../../Zotlabs/Module/Admin/Site.php:272
+#: ../../Zotlabs/Module/Admin/Site.php:283
msgid "Used to provide a member experience matched to technical comfort level"
msgstr "Dies wird verwendet, um eine Benutzererfahrung passend zur technischen Qualifikationsstufe zu bieten."
-#: ../../Zotlabs/Module/Admin/Site.php:274
+#: ../../Zotlabs/Module/Admin/Site.php:285
msgid "Lock the technical skill level setting"
msgstr "Sperre die technische Qualifikationsstufe"
-#: ../../Zotlabs/Module/Admin/Site.php:274
+#: ../../Zotlabs/Module/Admin/Site.php:285
msgid "Members can set their own technical comfort level by default"
msgstr "Benutzer können standardmäßig ihre eigene technische Qualifikationsstufe einstellen"
-#: ../../Zotlabs/Module/Admin/Site.php:276
+#: ../../Zotlabs/Module/Admin/Site.php:287
msgid "Banner/Logo"
msgstr "Banner/Logo"
-#: ../../Zotlabs/Module/Admin/Site.php:277
+#: ../../Zotlabs/Module/Admin/Site.php:288
msgid "Administrator Information"
msgstr "Administrator-Informationen"
-#: ../../Zotlabs/Module/Admin/Site.php:277
+#: ../../Zotlabs/Module/Admin/Site.php:288
msgid ""
"Contact information for site administrators. Displayed on siteinfo page. "
"BBCode can be used here"
msgstr "Kontaktinformationen für Administratoren des Servers. Wird auf der siteinfo-Seite angezeigt. BBCode kann verwendet werden."
-#: ../../Zotlabs/Module/Admin/Site.php:278
-#: ../../Zotlabs/Module/Siteinfo.php:23
+#: ../../Zotlabs/Module/Admin/Site.php:289
+#: ../../Zotlabs/Module/Siteinfo.php:22
msgid "Site Information"
msgstr "Seiteninformationen"
-#: ../../Zotlabs/Module/Admin/Site.php:278
+#: ../../Zotlabs/Module/Admin/Site.php:289
msgid ""
"Publicly visible description of this site. Displayed on siteinfo page. "
"BBCode can be used here"
msgstr "Öffentlich sichtbare Beschreibung dieses Servers. Wird auf der siteinfo-Seite angezeigt. BBCode kann hier verwendet werden."
-#: ../../Zotlabs/Module/Admin/Site.php:279
+#: ../../Zotlabs/Module/Admin/Site.php:290
msgid "System language"
msgstr "System-Sprache"
-#: ../../Zotlabs/Module/Admin/Site.php:280
+#: ../../Zotlabs/Module/Admin/Site.php:291
msgid "System theme"
-msgstr "System-Theme"
+msgstr "System-Design"
-#: ../../Zotlabs/Module/Admin/Site.php:280
+#: ../../Zotlabs/Module/Admin/Site.php:291
msgid ""
"Default system theme - may be over-ridden by user profiles - <a href='#' "
"id='cnftheme'>change theme settings</a>"
-msgstr "Standard-System-Theme – kann durch Nutzerprofile überschieben werden – <a href='#' id='cnftheme'>Theme-Einstellungen ändern</a>"
+msgstr "Standard-System-Design – kann durch Nutzerprofile überschieben werden – <a href='#' id='cnftheme'>Design-Einstellungen ändern</a>"
-#: ../../Zotlabs/Module/Admin/Site.php:281
+#: ../../Zotlabs/Module/Admin/Site.php:292
msgid "Mobile system theme"
-msgstr "Mobile System-Theme:"
+msgstr "System-Design für mobile Geräte:"
-#: ../../Zotlabs/Module/Admin/Site.php:281
+#: ../../Zotlabs/Module/Admin/Site.php:292
msgid "Theme for mobile devices"
msgstr "Theme für mobile Geräte"
-#: ../../Zotlabs/Module/Admin/Site.php:283
+#: ../../Zotlabs/Module/Admin/Site.php:294
msgid "Allow Feeds as Connections"
msgstr "Feeds als Verbindungen erlauben"
-#: ../../Zotlabs/Module/Admin/Site.php:283
+#: ../../Zotlabs/Module/Admin/Site.php:294
msgid "(Heavy system resource usage)"
msgstr "(führt zu hoher Systemlast)"
-#: ../../Zotlabs/Module/Admin/Site.php:284
+#: ../../Zotlabs/Module/Admin/Site.php:295
msgid "Maximum image size"
msgstr "Maximale Bildgröße"
-#: ../../Zotlabs/Module/Admin/Site.php:284
+#: ../../Zotlabs/Module/Admin/Site.php:295
msgid ""
"Maximum size in bytes of uploaded images. Default is 0, which means no "
"limits."
msgstr "Maximale Größe hochgeladener Bilder in Bytes. Standard ist 0 (keine Einschränkung)."
-#: ../../Zotlabs/Module/Admin/Site.php:285
+#: ../../Zotlabs/Module/Admin/Site.php:296
msgid "Does this site allow new member registration?"
msgstr "Erlaubt dieser Server die Registrierung neuer Nutzer?"
-#: ../../Zotlabs/Module/Admin/Site.php:286
+#: ../../Zotlabs/Module/Admin/Site.php:297
msgid "Invitation only"
msgstr "Nur mit Einladung"
-#: ../../Zotlabs/Module/Admin/Site.php:286
+#: ../../Zotlabs/Module/Admin/Site.php:297
msgid ""
"Only allow new member registrations with an invitation code. Above register "
"policy must be set to Yes."
msgstr "Erlaube die Neuregistrierung von Mitglieder nur mit einem Einladungscode. Die Registrierungs-Politik muss oben auf Ja gesetzt werden."
-#: ../../Zotlabs/Module/Admin/Site.php:287
+#: ../../Zotlabs/Module/Admin/Site.php:298
msgid "Which best describes the types of account offered by this hub?"
msgstr "Was ist die passendste Beschreibung der Konten auf diesem Hub?"
-#: ../../Zotlabs/Module/Admin/Site.php:288
+#: ../../Zotlabs/Module/Admin/Site.php:299
msgid "Register text"
msgstr "Registrierungstext"
-#: ../../Zotlabs/Module/Admin/Site.php:288
+#: ../../Zotlabs/Module/Admin/Site.php:299
msgid "Will be displayed prominently on the registration page."
msgstr "Wird gut sichtbar auf der Registrierungs-Seite angezeigt."
-#: ../../Zotlabs/Module/Admin/Site.php:289
+#: ../../Zotlabs/Module/Admin/Site.php:300
msgid "Site homepage to show visitors (default: login box)"
msgstr "Homepage des Hubs, die Besuchern angezeigt wird (Voreinstellung: Anmeldemaske)"
-#: ../../Zotlabs/Module/Admin/Site.php:289
+#: ../../Zotlabs/Module/Admin/Site.php:300
msgid ""
"example: 'public' to show public stream, 'page/sys/home' to show a system "
"webpage called 'home' or 'include:home.html' to include a file."
msgstr "Beispiele: 'public', um den Stream aller öffentlichen Beiträge anzuzeigen, 'page/sys/home', um eine System-Webseite namens 'home' anzuzeigen, 'include:home.html', um eine Datei einzufügen."
-#: ../../Zotlabs/Module/Admin/Site.php:290
+#: ../../Zotlabs/Module/Admin/Site.php:301
msgid "Preserve site homepage URL"
msgstr "Homepage-URL schützen"
-#: ../../Zotlabs/Module/Admin/Site.php:290
+#: ../../Zotlabs/Module/Admin/Site.php:301
msgid ""
"Present the site homepage in a frame at the original location instead of "
"redirecting"
msgstr "Zeigt die Homepage an der Original-URL in einem Frame an, statt auf die eigentliche Adresse der Seite umzuleiten."
-#: ../../Zotlabs/Module/Admin/Site.php:291
+#: ../../Zotlabs/Module/Admin/Site.php:302
msgid "Accounts abandoned after x days"
msgstr "Konten gelten nach X Tagen als unbenutzt"
-#: ../../Zotlabs/Module/Admin/Site.php:291
+#: ../../Zotlabs/Module/Admin/Site.php:302
msgid ""
"Will not waste system resources polling external sites for abandonded "
"accounts. Enter 0 for no time limit."
msgstr "Verschwende keine Systemressourcen auf das Pollen von externen Seiten, wenn das Konto nicht mehr benutzt wird. Trage hier 0 für kein zeitliches Limit."
-#: ../../Zotlabs/Module/Admin/Site.php:292
+#: ../../Zotlabs/Module/Admin/Site.php:303
msgid "Allowed friend domains"
msgstr "Erlaubte Domains für Kontakte"
-#: ../../Zotlabs/Module/Admin/Site.php:292
+#: ../../Zotlabs/Module/Admin/Site.php:303
msgid ""
"Comma separated list of domains which are allowed to establish friendships "
"with this site. Wildcards are accepted. Empty to allow any domains"
msgstr "Liste der Domains, die für Freundschaften erlaubt sind, durch Kommas getrennt. Platzhalter werden akzeptiert. Leer lassen, um alle Domains zu erlauben."
-#: ../../Zotlabs/Module/Admin/Site.php:293
+#: ../../Zotlabs/Module/Admin/Site.php:304
msgid "Verify Email Addresses"
msgstr "E-Mail-Adressen überprüfen"
-#: ../../Zotlabs/Module/Admin/Site.php:293
+#: ../../Zotlabs/Module/Admin/Site.php:304
msgid ""
"Check to verify email addresses used in account registration (recommended)."
msgstr "Aktivieren, um die Überprüfung von E-Mail-Adressen bei der Registrierung von Benutzerkonten zu aktivieren (empfohlen)."
-#: ../../Zotlabs/Module/Admin/Site.php:294
+#: ../../Zotlabs/Module/Admin/Site.php:305
msgid "Force publish"
msgstr "Veröffentlichung erzwingen"
-#: ../../Zotlabs/Module/Admin/Site.php:294
+#: ../../Zotlabs/Module/Admin/Site.php:305
msgid ""
"Check to force all profiles on this site to be listed in the site directory."
msgstr "Die Veröffentlichung aller Profile dieses Servers im Verzeichnis erzwingen."
-#: ../../Zotlabs/Module/Admin/Site.php:295
+#: ../../Zotlabs/Module/Admin/Site.php:306
msgid "Import Public Streams"
msgstr "Öffentliche Beiträge importieren"
-#: ../../Zotlabs/Module/Admin/Site.php:295
+#: ../../Zotlabs/Module/Admin/Site.php:306
msgid ""
"Import and allow access to public content pulled from other sites. Warning: "
"this content is unmoderated."
msgstr "Öffentliche Beiträge von anderen Servern importieren und zur Verfügung stellen. Warnung: Diese Inhalte sind nicht moderiert."
-#: ../../Zotlabs/Module/Admin/Site.php:296
+#: ../../Zotlabs/Module/Admin/Site.php:307
msgid "Login on Homepage"
msgstr "Log-in auf der Startseite"
-#: ../../Zotlabs/Module/Admin/Site.php:296
+#: ../../Zotlabs/Module/Admin/Site.php:307
msgid ""
"Present a login box to visitors on the home page if no other content has "
"been configured."
msgstr "Zeigt Besuchern der Homepage eine Anmeldemaske, falls keine anderen Inhalte konfiguriert wurden."
-#: ../../Zotlabs/Module/Admin/Site.php:297
+#: ../../Zotlabs/Module/Admin/Site.php:308
msgid "Enable context help"
msgstr "Kontext-Hilfe aktivieren"
-#: ../../Zotlabs/Module/Admin/Site.php:297
+#: ../../Zotlabs/Module/Admin/Site.php:308
msgid ""
"Display contextual help for the current page when the help button is "
"pressed."
msgstr "Zeigt Kontext-sensitive Hilfe für die aktuelle Seite an, wenn der Hilfe-Knopf geklickt wird."
-#: ../../Zotlabs/Module/Admin/Site.php:299
+#: ../../Zotlabs/Module/Admin/Site.php:310
+msgid "Reply-to email address for system generated email."
+msgstr "Antwortadresse (reply-to) für Emails, die vom System generiert wurden."
+
+#: ../../Zotlabs/Module/Admin/Site.php:311
+msgid "Sender (From) email address for system generated email."
+msgstr "Absenderadresse (from) für Emails, die vom System generiert wurden."
+
+#: ../../Zotlabs/Module/Admin/Site.php:312
+msgid "Name of email sender for system generated email."
+msgstr "Name des Versenders von Emails, die vom System generiert wurden."
+
+#: ../../Zotlabs/Module/Admin/Site.php:314
msgid "Directory Server URL"
msgstr "Verzeichnisserver-URL"
-#: ../../Zotlabs/Module/Admin/Site.php:299
+#: ../../Zotlabs/Module/Admin/Site.php:314
msgid "Default directory server"
msgstr "Standard-Verzeichnisserver"
-#: ../../Zotlabs/Module/Admin/Site.php:301
+#: ../../Zotlabs/Module/Admin/Site.php:316
msgid "Proxy user"
msgstr "Proxy Benutzer"
-#: ../../Zotlabs/Module/Admin/Site.php:302
+#: ../../Zotlabs/Module/Admin/Site.php:317
msgid "Proxy URL"
msgstr "Proxy URL"
-#: ../../Zotlabs/Module/Admin/Site.php:303
+#: ../../Zotlabs/Module/Admin/Site.php:318
msgid "Network timeout"
msgstr "Netzwerk-Timeout"
-#: ../../Zotlabs/Module/Admin/Site.php:303
+#: ../../Zotlabs/Module/Admin/Site.php:318
msgid "Value is in seconds. Set to 0 for unlimited (not recommended)."
msgstr "Wert in Sekunden. 0 für unbegrenzt (nicht empfohlen)."
-#: ../../Zotlabs/Module/Admin/Site.php:304
+#: ../../Zotlabs/Module/Admin/Site.php:319
msgid "Delivery interval"
msgstr "Auslieferung Intervall"
-#: ../../Zotlabs/Module/Admin/Site.php:304
+#: ../../Zotlabs/Module/Admin/Site.php:319
msgid ""
"Delay background delivery processes by this many seconds to reduce system "
"load. Recommend: 4-5 for shared hosts, 2-3 for virtual private servers. 0-1 "
"for large dedicated servers."
msgstr "Verzögere im Hintergrund laufende Auslieferungsprozesse um die angegebene Anzahl Sekunden, um die Systemlast zu verringern. Empfehlungen: 4-5 für Shared Hosts, 2-3 für VPS, 0-1 für große dedizierte Server."
-#: ../../Zotlabs/Module/Admin/Site.php:305
+#: ../../Zotlabs/Module/Admin/Site.php:320
msgid "Deliveries per process"
msgstr "Zustellungen pro Prozess"
-#: ../../Zotlabs/Module/Admin/Site.php:305
+#: ../../Zotlabs/Module/Admin/Site.php:320
msgid ""
"Number of deliveries to attempt in a single operating system process. Adjust"
" if necessary to tune system performance. Recommend: 1-5."
msgstr "Anzahl der Zustellungen, die innerhalb eines einzelnen Betriebssystemprozesses versucht werden. Anpassen, falls nötig, um die System-Performance zu verbessern. Empfehlung: 1-5."
-#: ../../Zotlabs/Module/Admin/Site.php:306
+#: ../../Zotlabs/Module/Admin/Site.php:321
msgid "Poll interval"
msgstr "Abfrageintervall"
-#: ../../Zotlabs/Module/Admin/Site.php:306
+#: ../../Zotlabs/Module/Admin/Site.php:321
msgid ""
"Delay background polling processes by this many seconds to reduce system "
"load. If 0, use delivery interval."
msgstr "Verzögere Hintergrundprozesse um diese Anzahl Sekunden, um die Systemlast zu reduzieren. Bei 0 wird das Auslieferungsintervall verwendet."
-#: ../../Zotlabs/Module/Admin/Site.php:307
+#: ../../Zotlabs/Module/Admin/Site.php:322
+msgid "Path to ImageMagick convert program"
+msgstr "Pfad zum ImageMagick-Programm convert"
+
+#: ../../Zotlabs/Module/Admin/Site.php:322
+msgid ""
+"If set, use this program to generate photo thumbnails for huge images ( > "
+"4000 pixels in either dimension), otherwise memory exhaustion may occur. "
+"Example: /usr/bin/convert"
+msgstr "Wenn gesetzt, dann verwende dieses Programm zum Erzeugen von Vorschaubildern großer Fotos (>4000 Pixel in beiden Richtungen), anderenfalls kann Speicherüberlauf auftreten. Beispiel: /usr/bin/convert"
+
+#: ../../Zotlabs/Module/Admin/Site.php:323
msgid "Maximum Load Average"
msgstr "Maximales Load Average"
-#: ../../Zotlabs/Module/Admin/Site.php:307
+#: ../../Zotlabs/Module/Admin/Site.php:323
msgid ""
"Maximum system load before delivery and poll processes are deferred - "
"default 50."
msgstr "Maximale Systemlast, bevor Verteil- und Empfangsprozesse verschoben werden – Standard 50"
-#: ../../Zotlabs/Module/Admin/Site.php:308
+#: ../../Zotlabs/Module/Admin/Site.php:324
msgid "Expiration period in days for imported (grid/network) content"
msgstr "Setze den Zeitraum (in Tagen), ab wann importierte (aus dem Netzwerk) Inhalte ablaufen sollen"
-#: ../../Zotlabs/Module/Admin/Site.php:308
+#: ../../Zotlabs/Module/Admin/Site.php:324
msgid "0 for no expiration of imported content"
msgstr "0 = keine Löschung importierter Inhalte"
-#: ../../Zotlabs/Module/Pubsites.php:24 ../../include/widgets.php:1454
-msgid "Public Hubs"
-msgstr "Öffentliche Hubs"
+#: ../../Zotlabs/Module/Admin/Profs.php:69
+msgid "New Profile Field"
+msgstr "Neues Profilfeld"
-#: ../../Zotlabs/Module/Pubsites.php:27
-msgid ""
-"The listed hubs allow public registration for the $Projectname network. All "
-"hubs in the network are interlinked so membership on any of them conveys "
-"membership in the network as a whole. Some hubs may require subscription or "
-"provide tiered service plans. The hub itself <strong>may</strong> provide "
-"additional details."
-msgstr "Die hier aufgeführten Hubs sind öffentlich und erlauben die Registrierung im $Projectname Netzwerk. Alle Hubs dieses Netzwerks sind miteinander verbunden, so dass die Mitgliedschaft auf einem Hub die Verbindung zu beliebigen Seiten und Kanälen auf anderen Hubs ermöglicht. Es könnte sein, dass einige dieser Hubs kostenpflichtig sind oder abgestufte, je nach Umfang kostenpflichtige Mitgliedschaften anbieten. Auf den Seiten der einzelnen Hubs <strong>könnten</strong> jeweils nähere Informationen dazu stehen."
+#: ../../Zotlabs/Module/Admin/Profs.php:70
+#: ../../Zotlabs/Module/Admin/Profs.php:90
+msgid "Field nickname"
+msgstr "Kurzname für das Feld"
-#: ../../Zotlabs/Module/Pubsites.php:33
-msgid "Hub URL"
-msgstr "Hub-URL"
+#: ../../Zotlabs/Module/Admin/Profs.php:70
+#: ../../Zotlabs/Module/Admin/Profs.php:90
+msgid "System name of field"
+msgstr "Systemname des Feldes"
-#: ../../Zotlabs/Module/Pubsites.php:33
-msgid "Access Type"
-msgstr "Zugriffstyp"
+#: ../../Zotlabs/Module/Admin/Profs.php:71
+#: ../../Zotlabs/Module/Admin/Profs.php:91
+msgid "Input type"
+msgstr "Art des Inhalts"
-#: ../../Zotlabs/Module/Pubsites.php:33
-msgid "Registration Policy"
-msgstr "Registrierungsrichtlinien"
+#: ../../Zotlabs/Module/Admin/Profs.php:72
+#: ../../Zotlabs/Module/Admin/Profs.php:92
+msgid "Field Name"
+msgstr "Feldname"
-#: ../../Zotlabs/Module/Pubsites.php:33
-msgid "Stats"
-msgstr "Statistiken"
+#: ../../Zotlabs/Module/Admin/Profs.php:72
+#: ../../Zotlabs/Module/Admin/Profs.php:92
+msgid "Label on profile pages"
+msgstr "Bezeichnung auf Profilseiten"
-#: ../../Zotlabs/Module/Pubsites.php:33
-msgid "Software"
-msgstr "Software"
+#: ../../Zotlabs/Module/Admin/Profs.php:73
+#: ../../Zotlabs/Module/Admin/Profs.php:93
+msgid "Help text"
+msgstr "Hilfetext"
-#: ../../Zotlabs/Module/Pubsites.php:35 ../../Zotlabs/Module/Ratings.php:97
-#: ../../include/conversation.php:974
-msgid "Ratings"
-msgstr "Bewertungen"
+#: ../../Zotlabs/Module/Admin/Profs.php:73
+#: ../../Zotlabs/Module/Admin/Profs.php:93
+msgid "Additional info (optional)"
+msgstr "Zusätzliche Informationen (optional)"
-#: ../../Zotlabs/Module/Pubsites.php:48
-msgid "Rate"
-msgstr "Bewerten"
+#: ../../Zotlabs/Module/Admin/Profs.php:74
+#: ../../Zotlabs/Module/Admin/Profs.php:94 ../../Zotlabs/Module/Rbmark.php:32
+#: ../../Zotlabs/Module/Rbmark.php:104 ../../Zotlabs/Module/Filer.php:53
+#: ../../Zotlabs/Widget/Notes.php:18 ../../include/text.php:1030
+#: ../../include/text.php:1042
+msgid "Save"
+msgstr "Speichern"
-#: ../../Zotlabs/Module/Pubsites.php:59 ../../Zotlabs/Module/Blocks.php:166
-#: ../../Zotlabs/Module/Layouts.php:197 ../../Zotlabs/Module/Webpages.php:246
-#: ../../Zotlabs/Module/Wiki.php:146 ../../Zotlabs/Module/Events.php:685
-#: ../../include/page_widgets.php:42 ../../include/widgets.php:967
-msgid "View"
-msgstr "Ansicht"
+#: ../../Zotlabs/Module/Admin/Profs.php:83
+msgid "Field definition not found"
+msgstr "Feld-Definition nicht gefunden"
-#: ../../Zotlabs/Module/Editlayout.php:79
-#: ../../Zotlabs/Module/Editwebpage.php:80
-#: ../../Zotlabs/Module/Editblock.php:79 ../../Zotlabs/Module/Editblock.php:95
-#: ../../Zotlabs/Module/Editpost.php:24
-msgid "Item not found"
-msgstr "Element nicht gefunden"
+#: ../../Zotlabs/Module/Admin/Profs.php:89
+msgid "Edit Profile Field"
+msgstr "Profilfeld bearbeiten"
-#: ../../Zotlabs/Module/Editlayout.php:127
-#: ../../Zotlabs/Module/Layouts.php:128 ../../Zotlabs/Module/Layouts.php:188
-msgid "Layout Name"
-msgstr "Layout-Name"
+#: ../../Zotlabs/Module/Admin/Profs.php:147 ../../Zotlabs/Widget/Admin.php:30
+msgid "Profile Fields"
+msgstr "Profil Felder"
-#: ../../Zotlabs/Module/Editlayout.php:128
-#: ../../Zotlabs/Module/Layouts.php:131
-msgid "Layout Description (Optional)"
-msgstr "Layout-Beschreibung (optional)"
+#: ../../Zotlabs/Module/Admin/Profs.php:148
+msgid "Basic Profile Fields"
+msgstr "Notwendige Profil Felder"
-#: ../../Zotlabs/Module/Editlayout.php:136
-msgid "Edit Layout"
-msgstr "Layout bearbeiten"
+#: ../../Zotlabs/Module/Admin/Profs.php:149
+msgid "Advanced Profile Fields"
+msgstr "Erweiterte Profil Felder"
-#: ../../Zotlabs/Module/Editwebpage.php:142
-msgid "Page link"
-msgstr "Seiten-Link"
+#: ../../Zotlabs/Module/Admin/Profs.php:149
+msgid "(In addition to basic fields)"
+msgstr "(zusätzlich zu notwendige Felder)"
-#: ../../Zotlabs/Module/Editwebpage.php:146 ../../Zotlabs/Module/Mail.php:258
-#: ../../Zotlabs/Module/Mail.php:383 ../../Zotlabs/Module/Editblock.php:111
-#: ../../Zotlabs/Module/Chat.php:207 ../../include/conversation.php:1165
-msgid "Insert web link"
-msgstr "Link einfügen"
+#: ../../Zotlabs/Module/Admin/Profs.php:151
+msgid "All available fields"
+msgstr "Alle verfügbaren Felder"
-#: ../../Zotlabs/Module/Editwebpage.php:169
-msgid "Edit Webpage"
-msgstr "Webseite bearbeiten"
+#: ../../Zotlabs/Module/Admin/Profs.php:152
+msgid "Custom Fields"
+msgstr "Benutzerdefinierte Felder"
-#: ../../Zotlabs/Module/Fbrowser.php:29 ../../Zotlabs/Lib/Apps.php:222
-#: ../../include/nav.php:95 ../../include/conversation.php:1692
-msgid "Photos"
-msgstr "Fotos"
+#: ../../Zotlabs/Module/Admin/Profs.php:156
+msgid "Create Custom Field"
+msgstr "Erstelle benutzerdefiniertes Feld"
-#: ../../Zotlabs/Module/Channel.php:32 ../../Zotlabs/Module/Wiki.php:20
-#: ../../Zotlabs/Module/Chat.php:25
-#: ../../extend/addon/addon/chess/chess.php:400
-msgid "You must be logged in to see this page."
-msgstr "Du musst angemeldet sein, um diese Seite betrachten zu können."
+#: ../../Zotlabs/Module/Admin/Account_edit.php:29
+#, php-format
+msgid "Password changed for account %d."
+msgstr "Passwort für Konto %d geändert."
-#: ../../Zotlabs/Module/Channel.php:44
-msgid "Posts and comments"
-msgstr "Beiträge und Kommentare"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:46
+msgid "Account settings updated."
+msgstr "Kontoeinstellungen aktualisiert."
-#: ../../Zotlabs/Module/Channel.php:45
-msgid "Only posts"
-msgstr "Nur Beiträge"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:61
+msgid "Account not found."
+msgstr "Konto nicht gefunden."
-#: ../../Zotlabs/Module/Channel.php:104
-msgid "Insufficient permissions. Request redirected to profile page."
-msgstr "Unzureichende Zugriffsrechte. Die Anfrage wurde zur Profil-Seite umgeleitet."
+#: ../../Zotlabs/Module/Admin/Account_edit.php:68
+msgid "Account Edit"
+msgstr "Kontobearbeitung"
-#: ../../Zotlabs/Module/Network.php:96
-msgid "No such group"
-msgstr "Gruppe nicht gefunden"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:69
+msgid "New Password"
+msgstr "Neues Passwort"
-#: ../../Zotlabs/Module/Network.php:136
-msgid "No such channel"
-msgstr "Kanal nicht gefunden"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:70
+msgid "New Password again"
+msgstr "Neues Passwort wiederholen"
-#: ../../Zotlabs/Module/Network.php:141
-msgid "forum"
-msgstr "Forum"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:71
+msgid "Technical skill level"
+msgstr "Technische Qualifikationsstufe"
-#: ../../Zotlabs/Module/Network.php:153
-msgid "Search Results For:"
-msgstr "Suchergebnisse für:"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:72
+msgid "Account language (for emails)"
+msgstr "Kontosprache (für E-Mails)"
-#: ../../Zotlabs/Module/Network.php:221
-msgid "Privacy group is empty"
-msgstr "Gruppe ist leer"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:73
+msgid "Service class"
+msgstr "Dienstklasse"
-#: ../../Zotlabs/Module/Network.php:230
-msgid "Privacy group: "
-msgstr "Gruppe:"
+#: ../../Zotlabs/Module/Admin/Security.php:77
+msgid ""
+"By default, unfiltered HTML is allowed in embedded media. This is inherently"
+" insecure."
+msgstr "Standardmäßig wird ungefiltertes HTML in eingebetteten Inhalten zugelassen. Das ist prinzipiell unsicher."
-#: ../../Zotlabs/Module/Network.php:256
-msgid "Invalid connection."
-msgstr "Ungültige Verbindung."
+#: ../../Zotlabs/Module/Admin/Security.php:80
+msgid ""
+"The recommended setting is to only allow unfiltered HTML from the following "
+"sites:"
+msgstr "Die empfohlene Einstellung ist, ungefiltertes HTML nur von den nachfolgenden Webseiten zu erlauben:"
-#: ../../Zotlabs/Module/Menu.php:49
-msgid "Unable to update menu."
-msgstr "Kann Menü nicht aktualisieren."
+#: ../../Zotlabs/Module/Admin/Security.php:81
+msgid ""
+"https://youtube.com/<br />https://www.youtube.com/<br />https://youtu.be/<br"
+" />https://vimeo.com/<br />https://soundcloud.com/<br />"
+msgstr "https://youtube.com/<br />https://www.youtube.com/<br />https://youtu.be/<br />https://vimeo.com/<br />https://soundcloud.com/<br />"
-#: ../../Zotlabs/Module/Menu.php:60
-msgid "Unable to create menu."
-msgstr "Kann Menü nicht erstellen."
+#: ../../Zotlabs/Module/Admin/Security.php:82
+msgid ""
+"All other embedded content will be filtered, <strong>unless</strong> "
+"embedded content from that site is explicitly blocked."
+msgstr "Alle anderen eingebetteten Inhalte werden gefiltert, <strong>es sei denn</strong>, eingebettete Inhalte von einer bestimmten Seite sind explizit blockiert."
-#: ../../Zotlabs/Module/Menu.php:98 ../../Zotlabs/Module/Menu.php:110
-msgid "Menu Name"
-msgstr "Name des Menüs"
+#: ../../Zotlabs/Module/Admin/Security.php:87
+#: ../../Zotlabs/Widget/Admin.php:25
+msgid "Security"
+msgstr "Sicherheit"
-#: ../../Zotlabs/Module/Menu.php:98
-msgid "Unique name (not visible on webpage) - required"
-msgstr "Eindeutiger Name (nicht sichtbar auf der Webseite) – erforderlich"
+#: ../../Zotlabs/Module/Admin/Security.php:89
+msgid "Block public"
+msgstr "Öffentlichen Zugriff blockieren"
-#: ../../Zotlabs/Module/Menu.php:99 ../../Zotlabs/Module/Menu.php:111
-msgid "Menu Title"
-msgstr "Menütitel"
+#: ../../Zotlabs/Module/Admin/Security.php:89
+msgid ""
+"Check to block public access to all otherwise public personal pages on this "
+"site unless you are currently authenticated."
+msgstr "Blockiere den öffentlichen Zugriff auf alle ansonsten öffentlichen persönlichen Seiten dieser Website, sofern ein Besucher nicht angemeldet ist."
-#: ../../Zotlabs/Module/Menu.php:99
-msgid "Visible on webpage - leave empty for no title"
-msgstr "Sichtbar auf der Webseite – für keinen Titel leer lassen"
+#: ../../Zotlabs/Module/Admin/Security.php:90
+msgid "Set \"Transport Security\" HTTP header"
+msgstr "Setze den \"Transport Security\" HTTP Header"
-#: ../../Zotlabs/Module/Menu.php:100
-msgid "Allow Bookmarks"
-msgstr "Lesezeichen erlauben"
+#: ../../Zotlabs/Module/Admin/Security.php:91
+msgid "Set \"Content Security Policy\" HTTP header"
+msgstr "Setze den \"Content Security Policy\" HTTP Header"
-#: ../../Zotlabs/Module/Menu.php:100 ../../Zotlabs/Module/Menu.php:157
-msgid "Menu may be used to store saved bookmarks"
-msgstr "Im Menü können gespeicherte Lesezeichen abgelegt werden"
+#: ../../Zotlabs/Module/Admin/Security.php:92
+msgid "Allowed email domains"
+msgstr "Erlaubte Domains für E-Mails"
-#: ../../Zotlabs/Module/Menu.php:101 ../../Zotlabs/Module/Menu.php:159
-msgid "Submit and proceed"
-msgstr "Absenden und fortfahren"
+#: ../../Zotlabs/Module/Admin/Security.php:92
+msgid ""
+"Comma separated list of domains which are allowed in email addresses for "
+"registrations to this site. Wildcards are accepted. Empty to allow any "
+"domains"
+msgstr "Liste der Domains, die für E-Mail-Adressen bei der Registrierung erlaubt sind, durch Kommas getrennt. Platzhalter werden akzeptiert. Leer lassen, um alle Domains zu erlauben."
-#: ../../Zotlabs/Module/Menu.php:107 ../../include/text.php:2271
-msgid "Menus"
-msgstr "Menüs"
+#: ../../Zotlabs/Module/Admin/Security.php:93
+msgid "Not allowed email domains"
+msgstr "Nicht erlaubte Domains für E-Mails"
-#: ../../Zotlabs/Module/Menu.php:114 ../../Zotlabs/Module/Blocks.php:157
-#: ../../Zotlabs/Module/Layouts.php:190 ../../Zotlabs/Module/Webpages.php:251
-#: ../../include/page_widgets.php:47
-msgid "Created"
-msgstr "Erstellt"
+#: ../../Zotlabs/Module/Admin/Security.php:93
+msgid ""
+"Comma separated list of domains which are not allowed in email addresses for"
+" registrations to this site. Wildcards are accepted. Empty to allow any "
+"domains, unless allowed domains have been defined."
+msgstr "Domains in E-Mail-Adressen, die keine Erlaubnis erhalten, sich auf Deinem Hub zu registrieren. Mehrere Domains können durch Kommas getrennt werden. Platzhalter (*/?) sind möglich. Keine Eingabe bedeutet keine Einschränkung, unabhängig davon, ob unter erlaubte Domains etwas eingegeben wurde."
-#: ../../Zotlabs/Module/Menu.php:115 ../../Zotlabs/Module/Blocks.php:158
-#: ../../Zotlabs/Module/Layouts.php:191 ../../Zotlabs/Module/Webpages.php:252
-#: ../../include/page_widgets.php:48
-msgid "Edited"
-msgstr "Geändert"
+#: ../../Zotlabs/Module/Admin/Security.php:94
+msgid "Allow communications only from these sites"
+msgstr "Kommunikation nur von diesen Servern/Domains erlauben"
-#: ../../Zotlabs/Module/Menu.php:117
-msgid "Bookmarks allowed"
-msgstr "Lesezeichen erlaubt"
+#: ../../Zotlabs/Module/Admin/Security.php:94
+msgid ""
+"One site per line. Leave empty to allow communication from anywhere by "
+"default"
+msgstr "Ein Eintrag pro Zeile. Lasse das Feld leer, um Kommunikation grundlegend von überall her zu erlauben."
-#: ../../Zotlabs/Module/Menu.php:119
-msgid "Delete this menu"
-msgstr "Lösche dieses Menü"
+#: ../../Zotlabs/Module/Admin/Security.php:95
+msgid "Block communications from these sites"
+msgstr "Kommunikation von diesen Servern/Domains blockieren"
-#: ../../Zotlabs/Module/Menu.php:120 ../../Zotlabs/Module/Menu.php:154
-msgid "Edit menu contents"
-msgstr "Bearbeite Menü Inhalte"
+#: ../../Zotlabs/Module/Admin/Security.php:96
+msgid "Allow communications only from these channels"
+msgstr "Kommunikation nur von diesen Kanälen erlauben"
-#: ../../Zotlabs/Module/Menu.php:121
-msgid "Edit this menu"
-msgstr "Dieses Menü bearbeiten"
+#: ../../Zotlabs/Module/Admin/Security.php:96
+msgid ""
+"One channel (hash) per line. Leave empty to allow from any channel by "
+"default"
+msgstr "Ein Kanal (hash) pro Zeile. Leerlassen um jeden Kanal zuzulassen. "
-#: ../../Zotlabs/Module/Menu.php:136
-msgid "Menu could not be deleted."
-msgstr "Menü konnte nicht gelöscht werden."
+#: ../../Zotlabs/Module/Admin/Security.php:97
+msgid "Block communications from these channels"
+msgstr "Kommunikation von folgenden Kanälen blockieren"
-#: ../../Zotlabs/Module/Menu.php:144 ../../Zotlabs/Module/Mitem.php:28
-msgid "Menu not found."
-msgstr "Menü nicht gefunden"
+#: ../../Zotlabs/Module/Admin/Security.php:98
+msgid "Only allow embeds from secure (SSL) websites and links."
+msgstr "Erlaube Einbettungen nur von sicheren (SSL) Webseiten und Links."
-#: ../../Zotlabs/Module/Menu.php:149
-msgid "Edit Menu"
-msgstr "Menü bearbeiten"
+#: ../../Zotlabs/Module/Admin/Security.php:99
+msgid "Allow unfiltered embedded HTML content only from these domains"
+msgstr "Erlaube Einbettung von Inhalten mit ungefiltertem HTML nur von diesen Domains"
-#: ../../Zotlabs/Module/Menu.php:153
-msgid "Add or remove entries to this menu"
-msgstr "Einträge zu diesem Menü hinzufügen oder entfernen"
+#: ../../Zotlabs/Module/Admin/Security.php:99
+msgid "One site per line. By default embedded content is filtered."
+msgstr "Eine Website/Domain pro Zeile. Standardmäßig wird eingebetteter Inhalt gefiltert."
-#: ../../Zotlabs/Module/Menu.php:155
-msgid "Menu name"
-msgstr "Menü Name"
+#: ../../Zotlabs/Module/Admin/Security.php:100
+msgid "Block embedded HTML from these domains"
+msgstr "Eingebettete HTML Inhalte von diesen Servern/Domains blockieren"
-#: ../../Zotlabs/Module/Menu.php:155
-msgid "Must be unique, only seen by you"
-msgstr "Muss eindeutig sein, ist aber nur für Dich sichtbar"
+#: ../../Zotlabs/Module/Lockview.php:75
+msgid "Remote privacy information not available."
+msgstr "Privatsphäre-Einstellungen anderer Nutzer sind nicht verfügbar."
-#: ../../Zotlabs/Module/Menu.php:156
-msgid "Menu title"
-msgstr "Menü Titel"
+#: ../../Zotlabs/Module/Lockview.php:96
+msgid "Visible to:"
+msgstr "Sichtbar für:"
-#: ../../Zotlabs/Module/Menu.php:156
-msgid "Menu title as seen by others"
-msgstr "Menü Titel wie er von anderen gesehen wird"
+#: ../../Zotlabs/Module/Lockview.php:117 ../../Zotlabs/Module/Lockview.php:153
+#: ../../Zotlabs/Module/Acl.php:118 ../../include/acl_selectors.php:183
+msgctxt "acl"
+msgid "Profile"
+msgstr "Profil"
-#: ../../Zotlabs/Module/Menu.php:157
-msgid "Allow bookmarks"
-msgstr "Erlaube Lesezeichen"
+#: ../../Zotlabs/Module/Moderate.php:55
+msgid "Comment approved"
+msgstr "Kommentar bestätigt"
-#: ../../Zotlabs/Module/Menu.php:166 ../../Zotlabs/Module/Mitem.php:120
-#: ../../Zotlabs/Module/Xchan.php:41
-msgid "Not found."
-msgstr "Nicht gefunden."
+#: ../../Zotlabs/Module/Moderate.php:59
+msgid "Comment deleted"
+msgstr "Kommentar gelöscht"
-#: ../../Zotlabs/Module/Appman.php:37 ../../Zotlabs/Module/Appman.php:53
-msgid "App installed."
-msgstr "App installiert."
+#: ../../Zotlabs/Module/Settings/Permcats.php:37
+msgid "Permission category saved."
+msgstr "Berechtigungsrolle gespeichert."
-#: ../../Zotlabs/Module/Appman.php:46
-msgid "Malformed app."
-msgstr "Fehlerhafte App."
+#: ../../Zotlabs/Module/Settings/Permcats.php:61
+msgid ""
+"Use this form to create permission rules for various classes of people or "
+"connections."
+msgstr "Verwende dieses Formular, um Berechtigungsrollen für verschiedene Gruppen von Personen oder Verbindungen zu erstellen."
-#: ../../Zotlabs/Module/Appman.php:104
-msgid "Embed code"
-msgstr "Code einbetten"
+#: ../../Zotlabs/Module/Settings/Permcats.php:94
+msgid "Permission Categories"
+msgstr "Berechtigungsrollen"
-#: ../../Zotlabs/Module/Appman.php:110 ../../include/widgets.php:107
-msgid "Edit App"
-msgstr "App bearbeiten"
+#: ../../Zotlabs/Module/Settings/Permcats.php:102
+msgid "Permission Name"
+msgstr "Name der Berechtigungsrolle"
-#: ../../Zotlabs/Module/Appman.php:110
-msgid "Create App"
-msgstr "App erstellen"
+#: ../../Zotlabs/Module/Settings/Permcats.php:103
+#: ../../Zotlabs/Module/Settings/Tokens.php:161
+#: ../../Zotlabs/Module/Connedit.php:908
+msgid "My Settings"
+msgstr "Meine Einstellungen"
-#: ../../Zotlabs/Module/Appman.php:115
-msgid "Name of app"
-msgstr "Name der App"
+#: ../../Zotlabs/Module/Settings/Permcats.php:105
+#: ../../Zotlabs/Module/Settings/Tokens.php:163
+#: ../../Zotlabs/Module/Connedit.php:903
+msgid "inherited"
+msgstr "geerbt"
-#: ../../Zotlabs/Module/Appman.php:115 ../../Zotlabs/Module/Appman.php:116
-#: ../../Zotlabs/Module/Profiles.php:703 ../../Zotlabs/Module/Profiles.php:707
-#: ../../Zotlabs/Module/Events.php:453 ../../Zotlabs/Module/Events.php:458
-#: ../../include/datetime.php:259
-msgid "Required"
-msgstr "Benötigt"
+#: ../../Zotlabs/Module/Settings/Permcats.php:108
+#: ../../Zotlabs/Module/Settings/Tokens.php:166
+#: ../../Zotlabs/Module/Connedit.php:910
+msgid "Individual Permissions"
+msgstr "Individuelle Zugriffsrechte"
-#: ../../Zotlabs/Module/Appman.php:116
-msgid "Location (URL) of app"
-msgstr "Ort (URL) der App"
+#: ../../Zotlabs/Module/Settings/Permcats.php:109
+#: ../../Zotlabs/Module/Settings/Tokens.php:167
+#: ../../Zotlabs/Module/Connedit.php:911
+msgid ""
+"Some permissions may be inherited from your channel's <a "
+"href=\"settings\"><strong>privacy settings</strong></a>, which have higher "
+"priority than individual settings. You can <strong>not</strong> change those"
+" settings here."
+msgstr "Einige Berechtigungen werden möglicherweise von den globalen <a href=\"settings\">Sicherheits- und Privatsphäre-Einstellungen</a> dieses Kanals vererbt. Diese haben eine höhere Priorität als die Einstellungen an der Verbindung und können hier nicht verändert werden."
-#: ../../Zotlabs/Module/Appman.php:117 ../../Zotlabs/Module/Rbmark.php:101
-#: ../../Zotlabs/Module/Events.php:466
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:838
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:133
-msgid "Description"
-msgstr "Beschreibung"
+#: ../../Zotlabs/Module/Settings/Channel.php:62
+#: ../../Zotlabs/Module/Settings/Channel.php:66
+#: ../../Zotlabs/Module/Settings/Channel.php:67
+#: ../../Zotlabs/Module/Settings/Channel.php:70
+#: ../../Zotlabs/Module/Settings/Channel.php:81
+#: ../../Zotlabs/Module/Connedit.php:711 ../../Zotlabs/Widget/Affinity.php:28
+#: ../../include/selectors.php:123 ../../include/channel.php:423
+#: ../../include/channel.php:424 ../../include/channel.php:431
+msgid "Friends"
+msgstr "Freunde"
-#: ../../Zotlabs/Module/Appman.php:118
-msgid "Photo icon URL"
-msgstr "URL zum Icon"
+#: ../../Zotlabs/Module/Settings/Channel.php:255
+#: ../../addon/rendezvous/rendezvous.php:82
+#: ../../addon/openstreetmap/openstreetmap.php:184
+#: ../../addon/msgfooter/msgfooter.php:54 ../../addon/logrot/logrot.php:54
+#: ../../addon/twitter/twitter.php:766 ../../addon/piwik/piwik.php:116
+#: ../../addon/xmpp/xmpp.php:102
+msgid "Settings updated."
+msgstr "Einstellungen aktualisiert."
-#: ../../Zotlabs/Module/Appman.php:118
-msgid "80 x 80 pixels - optional"
-msgstr "80 x 80 Pixel – optional"
+#: ../../Zotlabs/Module/Settings/Channel.php:316
+msgid "Nobody except yourself"
+msgstr "Niemand außer Dir selbst"
-#: ../../Zotlabs/Module/Appman.php:119
-msgid "Categories (optional, comma separated list)"
-msgstr "Kategorien (optional, kommagetrennte Liste)"
+#: ../../Zotlabs/Module/Settings/Channel.php:317
+msgid "Only those you specifically allow"
+msgstr "Nur die, denen Du es explizit erlaubst"
-#: ../../Zotlabs/Module/Appman.php:120
-msgid "Version ID"
-msgstr "Versions-ID"
+#: ../../Zotlabs/Module/Settings/Channel.php:318
+msgid "Approved connections"
+msgstr "Angenommene Verbindungen"
-#: ../../Zotlabs/Module/Appman.php:121
-msgid "Price of app"
-msgstr "Preis der App"
+#: ../../Zotlabs/Module/Settings/Channel.php:319
+msgid "Any connections"
+msgstr "Beliebige Verbindungen"
-#: ../../Zotlabs/Module/Appman.php:122
-msgid "Location (URL) to purchase app"
-msgstr "Ort (URL), um die App zu kaufen"
+#: ../../Zotlabs/Module/Settings/Channel.php:320
+msgid "Anybody on this website"
+msgstr "Jeder auf dieser Website"
-#: ../../Zotlabs/Module/Rpost.php:138 ../../Zotlabs/Module/Editpost.php:107
-msgid "Edit post"
-msgstr "Bearbeite Beitrag"
+#: ../../Zotlabs/Module/Settings/Channel.php:321
+msgid "Anybody in this network"
+msgstr "Alle $Projectname-Mitglieder"
-#: ../../Zotlabs/Module/Help.php:23
-msgid "Documentation Search"
-msgstr "Suche in der Dokumentation"
+#: ../../Zotlabs/Module/Settings/Channel.php:322
+msgid "Anybody authenticated"
+msgstr "Jeder authentifizierte"
-#: ../../Zotlabs/Module/Help.php:82
-msgid "$Projectname Documentation"
-msgstr "$Projectname-Dokumentation"
+#: ../../Zotlabs/Module/Settings/Channel.php:323
+msgid "Anybody on the internet"
+msgstr "Jeder im Internet"
-#: ../../Zotlabs/Module/Ffsapi.php:12
-msgid "Share content from Firefox to $Projectname"
-msgstr "Inhalte von Firefox nach $Projectname teilen"
+#: ../../Zotlabs/Module/Settings/Channel.php:399
+msgid "Publish your default profile in the network directory"
+msgstr "Standard-Profil im Netzwerk-Verzeichnis veröffentlichen"
-#: ../../Zotlabs/Module/Ffsapi.php:15
-msgid "Activate the Firefox $Projectname provider"
-msgstr "Aktiviert den $Projectname-Provider für firefox"
+#: ../../Zotlabs/Module/Settings/Channel.php:404
+msgid "Allow us to suggest you as a potential friend to new members?"
+msgstr "Dürfen wir Dich neuen Mitgliedern als potentiellen Kontakt vorschlagen?"
-#: ../../Zotlabs/Module/Apps.php:46 ../../include/nav.php:166
-#: ../../include/widgets.php:102
-msgid "Apps"
-msgstr "Apps"
+#: ../../Zotlabs/Module/Settings/Channel.php:408
+#: ../../Zotlabs/Module/Profile_photo.php:437
+#: ../../Zotlabs/Module/Cover_photo.php:365
+msgid "or"
+msgstr "oder"
-#: ../../Zotlabs/Module/Home.php:74 ../../Zotlabs/Module/Home.php:82
-msgid "$Projectname"
-msgstr "$Projectname"
+#: ../../Zotlabs/Module/Settings/Channel.php:413
+msgid "Your channel address is"
+msgstr "Deine Kanal-Adresse lautet"
-#: ../../Zotlabs/Module/Home.php:92
-#, php-format
-msgid "Welcome to %s"
-msgstr "Willkommen auf %s"
+#: ../../Zotlabs/Module/Settings/Channel.php:416
+msgid "Your files/photos are accessible via WebDAV at"
+msgstr "Deine Dateien/Fotos sind via WebDAV verfügbar auf"
-#: ../../Zotlabs/Module/Filestorage.php:87
-msgid "Permission Denied."
-msgstr "Zugriff verweigert."
+#: ../../Zotlabs/Module/Settings/Channel.php:478
+msgid "Channel Settings"
+msgstr "Kanal-Einstellungen"
-#: ../../Zotlabs/Module/Filestorage.php:103
-msgid "File not found."
-msgstr "Datei nicht gefunden."
+#: ../../Zotlabs/Module/Settings/Channel.php:485
+msgid "Basic Settings"
+msgstr "Grundeinstellungen"
-#: ../../Zotlabs/Module/Filestorage.php:146
-msgid "Edit file permissions"
-msgstr "Dateiberechtigungen bearbeiten"
+#: ../../Zotlabs/Module/Settings/Channel.php:486
+#: ../../include/channel.php:1473
+msgid "Full Name:"
+msgstr "Voller Name:"
-#: ../../Zotlabs/Module/Filestorage.php:152
-#: ../../Zotlabs/Module/Photos.php:658 ../../Zotlabs/Module/Photos.php:1047
-#: ../../Zotlabs/Module/Thing.php:313 ../../Zotlabs/Module/Thing.php:363
-#: ../../Zotlabs/Module/Chat.php:234 ../../include/acl_selectors.php:208
-msgid "Permissions"
-msgstr "Berechtigungen"
+#: ../../Zotlabs/Module/Settings/Channel.php:487
+#: ../../Zotlabs/Module/Settings/Account.php:119
+msgid "Email Address:"
+msgstr "Email Adresse:"
-#: ../../Zotlabs/Module/Filestorage.php:159
-msgid "Set/edit permissions"
-msgstr "Berechtigungen setzen/ändern"
+#: ../../Zotlabs/Module/Settings/Channel.php:488
+msgid "Your Timezone:"
+msgstr "Ihre Zeitzone:"
-#: ../../Zotlabs/Module/Filestorage.php:160
-msgid "Include all files and sub folders"
-msgstr "Alle Dateien und Unterverzeichnisse einbinden"
+#: ../../Zotlabs/Module/Settings/Channel.php:489
+msgid "Default Post Location:"
+msgstr "Standardstandort:"
-#: ../../Zotlabs/Module/Filestorage.php:161
-msgid "Return to file list"
-msgstr "Zurück zur Dateiliste"
+#: ../../Zotlabs/Module/Settings/Channel.php:489
+msgid "Geographical location to display on your posts"
+msgstr "Geografischer Ort, der bei Deinen Beiträgen angezeigt werden soll"
-#: ../../Zotlabs/Module/Filestorage.php:163
-msgid "Copy/paste this code to attach file to a post"
-msgstr "Diesen Code kopieren und einfügen, um die Datei an einen Beitrag anzuhängen"
+#: ../../Zotlabs/Module/Settings/Channel.php:490
+msgid "Use Browser Location:"
+msgstr "Standort des Browsers verwenden:"
-#: ../../Zotlabs/Module/Filestorage.php:164
-msgid "Copy/paste this URL to link file from a web page"
-msgstr "Diese URL verwenden, um von einer Webseite aus auf die Datei zu verlinken"
+#: ../../Zotlabs/Module/Settings/Channel.php:492
+msgid "Adult Content"
+msgstr "Nicht jugendfreie Inhalte"
-#: ../../Zotlabs/Module/Filestorage.php:166
-msgid "Share this file"
-msgstr "Diese Datei freigeben"
+#: ../../Zotlabs/Module/Settings/Channel.php:492
+msgid ""
+"This channel frequently or regularly publishes adult content. (Please tag "
+"any adult material and/or nudity with #NSFW)"
+msgstr "Dieser Kanal veröffentlicht regelmäßig Inhalte, die für Minderjährige ungeeignet sind. (Bitte markiere solche Inhalte mit dem Schlagwort #NSFW)"
-#: ../../Zotlabs/Module/Filestorage.php:167
-msgid "Show URL to this file"
-msgstr "URL zu dieser Datei anzeigen"
+#: ../../Zotlabs/Module/Settings/Channel.php:494
+msgid "Security and Privacy Settings"
+msgstr "Sicherheits- und Datenschutz-Einstellungen"
-#: ../../Zotlabs/Module/Filestorage.php:168
-msgid "Notify your contacts about this file"
-msgstr "Meine Kontakte über diese Datei benachrichtigen"
+#: ../../Zotlabs/Module/Settings/Channel.php:496
+msgid "Your permissions are already configured. Click to view/adjust"
+msgstr "Deine Zugriffsrechte sind schon konfiguriert. Klicke hier, um sie zu betrachten oder zu ändern"
-#: ../../Zotlabs/Module/Directory.php:64 ../../Zotlabs/Module/Display.php:17
-#: ../../Zotlabs/Module/Ratings.php:83 ../../Zotlabs/Module/Photos.php:509
-#: ../../Zotlabs/Module/Search.php:17
-#: ../../Zotlabs/Module/Viewconnections.php:23
-#: ../../extend/addon/addon/friendica/dfrn_request.php:794
-msgid "Public access denied."
-msgstr "Öffentlichen Zugriff verweigert."
+#: ../../Zotlabs/Module/Settings/Channel.php:498
+msgid "Hide my online presence"
+msgstr "Meine Online-Präsenz verbergen"
-#: ../../Zotlabs/Module/Directory.php:245
+#: ../../Zotlabs/Module/Settings/Channel.php:498
+msgid "Prevents displaying in your profile that you are online"
+msgstr "Verhindert die Anzeige Deines Online-Status in deinem Profil"
+
+#: ../../Zotlabs/Module/Settings/Channel.php:500
+msgid "Simple Privacy Settings:"
+msgstr "Einfache Privatsphäre-Einstellungen"
+
+#: ../../Zotlabs/Module/Settings/Channel.php:501
+msgid ""
+"Very Public - <em>extremely permissive (should be used with caution)</em>"
+msgstr "Komplett offen – <em>extrem ungeschützt (mit großer Vorsicht verwenden!)</em>"
+
+#: ../../Zotlabs/Module/Settings/Channel.php:502
+msgid ""
+"Typical - <em>default public, privacy when desired (similar to social "
+"network permissions but with improved privacy)</em>"
+msgstr "Typisch – <em>Standard öffentlich, Privatsphäre, wo sie erwünscht ist (ähnlich den Einstellungen in sozialen Netzwerken, aber mit besser geschützter Privatsphäre)</em>"
+
+#: ../../Zotlabs/Module/Settings/Channel.php:503
+msgid "Private - <em>default private, never open or public</em>"
+msgstr "Privat – <em>Standard privat, nie offen oder öffentlich</em>"
+
+#: ../../Zotlabs/Module/Settings/Channel.php:504
+msgid "Blocked - <em>default blocked to/from everybody</em>"
+msgstr "Blockiert – <em>Alle standardmäßig blockiert</em>"
+
+#: ../../Zotlabs/Module/Settings/Channel.php:506
+msgid "Allow others to tag your posts"
+msgstr "Erlaube anderen, Deine Beiträge zu verschlagworten"
+
+#: ../../Zotlabs/Module/Settings/Channel.php:506
+msgid ""
+"Often used by the community to retro-actively flag inappropriate content"
+msgstr "Wird oft von der Community genutzt um rückwirkend anstößigen Inhalt zu markieren"
+
+#: ../../Zotlabs/Module/Settings/Channel.php:508
+msgid "Channel Permission Limits"
+msgstr "Kanal-Berechtigungslimits"
+
+#: ../../Zotlabs/Module/Settings/Channel.php:510
+msgid "Expire other channel content after this many days"
+msgstr "Den Inhalt anderer Kanäle nach dieser Anzahl Tage verfallen lassen"
+
+#: ../../Zotlabs/Module/Settings/Channel.php:510
+msgid "0 or blank to use the website limit."
+msgstr "0 oder leer lassen, um den voreingestellten Wert der Webseite zu verwenden."
+
+#: ../../Zotlabs/Module/Settings/Channel.php:510
#, php-format
-msgid "%d rating"
-msgid_plural "%d ratings"
-msgstr[0] "%d Bewertung"
-msgstr[1] "%d Bewertungen"
+msgid "This website expires after %d days."
+msgstr "Diese Webseite läuft nach %d Tagen ab."
-#: ../../Zotlabs/Module/Directory.php:256
-msgid "Gender: "
-msgstr "Geschlecht:"
+#: ../../Zotlabs/Module/Settings/Channel.php:510
+msgid "This website does not expire imported content."
+msgstr "Diese Webseite lässt importierte Inhalte nicht verfallen."
-#: ../../Zotlabs/Module/Directory.php:258
-msgid "Status: "
-msgstr "Status:"
+#: ../../Zotlabs/Module/Settings/Channel.php:510
+msgid "The website limit takes precedence if lower than your limit."
+msgstr "Das Verfallslimit der Webseite hat Vorrang, wenn es niedriger als Deines hier ist."
-#: ../../Zotlabs/Module/Directory.php:260
-msgid "Homepage: "
-msgstr "Webseite:"
+#: ../../Zotlabs/Module/Settings/Channel.php:511
+msgid "Maximum Friend Requests/Day:"
+msgstr "Maximale Kontaktanfragen pro Tag:"
-#: ../../Zotlabs/Module/Directory.php:309 ../../include/channel.php:1215
-msgid "Age:"
-msgstr "Alter:"
+#: ../../Zotlabs/Module/Settings/Channel.php:511
+msgid "May reduce spam activity"
+msgstr "Kann die Spam-Aktivität verringern"
-#: ../../Zotlabs/Module/Directory.php:314 ../../include/channel.php:1051
-#: ../../include/event.php:52 ../../include/event.php:84
-#: ../../include/bb2diaspora.php:520
-msgid "Location:"
-msgstr "Ort:"
+#: ../../Zotlabs/Module/Settings/Channel.php:512
+msgid "Default Privacy Group"
+msgstr "Standard-Gruppe"
-#: ../../Zotlabs/Module/Directory.php:320
-msgid "Description:"
-msgstr "Beschreibung:"
+#: ../../Zotlabs/Module/Settings/Channel.php:514
+msgid "Use my default audience setting for the type of object published"
+msgstr "Verwende Deine eingestellte Standard-Zielgruppe des jeweiligen Inhaltstyps"
-#: ../../Zotlabs/Module/Directory.php:325 ../../include/channel.php:1231
-msgid "Hometown:"
-msgstr "Heimatstadt:"
+#: ../../Zotlabs/Module/Settings/Channel.php:521
+msgid "Channel permissions category:"
+msgstr "Zugriffsrechte-Kategorie des Kanals:"
-#: ../../Zotlabs/Module/Directory.php:327 ../../include/channel.php:1239
-msgid "About:"
-msgstr "Über:"
+#: ../../Zotlabs/Module/Settings/Channel.php:522
+msgid "Default Permissions Group"
+msgstr "Standard-Berechtigungsgruppe"
-#: ../../Zotlabs/Module/Directory.php:329
-msgid "Public Forum:"
-msgstr "Öffentliches Forum:"
+#: ../../Zotlabs/Module/Settings/Channel.php:528
+msgid "Maximum private messages per day from unknown people:"
+msgstr "Maximale Anzahl privater Nachrichten pro Tag von unbekannten Leuten:"
-#: ../../Zotlabs/Module/Directory.php:332
-msgid "Keywords: "
-msgstr "Schlüsselwörter:"
+#: ../../Zotlabs/Module/Settings/Channel.php:528
+msgid "Useful to reduce spamming"
+msgstr "Nützlich, um Spam zu verringern"
-#: ../../Zotlabs/Module/Directory.php:335
-msgid "Don't suggest"
-msgstr "Nicht vorschlagen"
+#: ../../Zotlabs/Module/Settings/Channel.php:531
+msgid "Notification Settings"
+msgstr "Benachrichtigungs-Einstellungen"
-#: ../../Zotlabs/Module/Directory.php:337
-msgid "Common connections:"
-msgstr "Gemeinsame Verbindungen:"
+#: ../../Zotlabs/Module/Settings/Channel.php:532
+msgid "By default post a status message when:"
+msgstr "Sende standardmäßig Status-Nachrichten, wenn:"
-#: ../../Zotlabs/Module/Directory.php:386
-msgid "Global Directory"
-msgstr "Globales Verzeichnis"
+#: ../../Zotlabs/Module/Settings/Channel.php:533
+msgid "accepting a friend request"
+msgstr "Du eine Verbindungsanfrage annimmst"
-#: ../../Zotlabs/Module/Directory.php:386
-msgid "Local Directory"
-msgstr "Lokales Verzeichnis"
+#: ../../Zotlabs/Module/Settings/Channel.php:534
+msgid "joining a forum/community"
+msgstr "Du einem Forum beitrittst"
-#: ../../Zotlabs/Module/Directory.php:392
-msgid "Finding:"
-msgstr "Ergebnisse:"
+#: ../../Zotlabs/Module/Settings/Channel.php:535
+msgid "making an <em>interesting</em> profile change"
+msgstr "Du eine <em>interessante</em> Änderung an Deinem Profil vornimmst"
-#: ../../Zotlabs/Module/Directory.php:395 ../../Zotlabs/Module/Suggest.php:64
-#: ../../include/contact_widgets.php:24
-msgid "Channel Suggestions"
-msgstr "Kanal-Vorschläge"
+#: ../../Zotlabs/Module/Settings/Channel.php:536
+msgid "Send a notification email when:"
+msgstr "Eine E-Mail-Benachrichtigung senden, wenn:"
-#: ../../Zotlabs/Module/Directory.php:397
-msgid "next page"
-msgstr "nächste Seite"
+#: ../../Zotlabs/Module/Settings/Channel.php:537
+msgid "You receive a connection request"
+msgstr "Du eine Verbindungsanfrage erhältst"
-#: ../../Zotlabs/Module/Directory.php:397
-msgid "previous page"
-msgstr "vorherige Seite"
+#: ../../Zotlabs/Module/Settings/Channel.php:538
+msgid "Your connections are confirmed"
+msgstr "Eine Verbindung bestätigt wurde"
-#: ../../Zotlabs/Module/Directory.php:398
-msgid "Sort options"
-msgstr "Sortieroptionen"
+#: ../../Zotlabs/Module/Settings/Channel.php:539
+msgid "Someone writes on your profile wall"
+msgstr "Jemand auf Deine Pinnwand schreibt"
-#: ../../Zotlabs/Module/Directory.php:399
-msgid "Alphabetic"
-msgstr "alphabetisch"
+#: ../../Zotlabs/Module/Settings/Channel.php:540
+msgid "Someone writes a followup comment"
+msgstr "Jemand einen Beitrag kommentiert"
-#: ../../Zotlabs/Module/Directory.php:400
-msgid "Reverse Alphabetic"
-msgstr "Entgegengesetzt alphabetisch"
+#: ../../Zotlabs/Module/Settings/Channel.php:541
+msgid "You receive a private message"
+msgstr "Du eine private Nachricht erhältst"
-#: ../../Zotlabs/Module/Directory.php:401
-msgid "Newest to Oldest"
-msgstr "Neueste zuerst"
+#: ../../Zotlabs/Module/Settings/Channel.php:542
+msgid "You receive a friend suggestion"
+msgstr "Du einen Kontaktvorschlag erhältst"
-#: ../../Zotlabs/Module/Directory.php:402
-msgid "Oldest to Newest"
-msgstr "Älteste zuerst"
+#: ../../Zotlabs/Module/Settings/Channel.php:543
+msgid "You are tagged in a post"
+msgstr "Du in einem Beitrag erwähnt wurdest"
-#: ../../Zotlabs/Module/Directory.php:419
-msgid "No entries (some entries may be hidden)."
-msgstr "Keine Einträge gefunden (einige könnten versteckt sein)."
+#: ../../Zotlabs/Module/Settings/Channel.php:544
+msgid "You are poked/prodded/etc. in a post"
+msgstr "Du in einem Beitrag angestupst/geknufft/o.ä. wurdest"
-#: ../../Zotlabs/Module/Item.php:184
-msgid "Unable to locate original post."
-msgstr "Originalbeitrag nicht gefunden."
+#: ../../Zotlabs/Module/Settings/Channel.php:546
+msgid "Someone likes your post/comment"
+msgstr "Jemand mag Ihren Beitrag/Kommentar"
-#: ../../Zotlabs/Module/Item.php:447
-msgid "Empty post discarded."
-msgstr "Leeren Beitrag verworfen."
+#: ../../Zotlabs/Module/Settings/Channel.php:549
+msgid "Show visual notifications including:"
+msgstr "Visuelle Benachrichtigungen anzeigen für:"
-#: ../../Zotlabs/Module/Item.php:489
-msgid "Executable content type not permitted to this channel."
-msgstr "Ausführbarer Content-Typ ist für diesen Kanal nicht freigegeben."
+#: ../../Zotlabs/Module/Settings/Channel.php:551
+msgid "Unseen grid activity"
+msgstr "Ungesehene Netzwerk-Aktivität"
-#: ../../Zotlabs/Module/Item.php:871
-msgid "Duplicate post suppressed."
-msgstr "Doppelter Beitrag unterdrückt."
+#: ../../Zotlabs/Module/Settings/Channel.php:552
+msgid "Unseen channel activity"
+msgstr "Ungesehene Kanal-Aktivität"
-#: ../../Zotlabs/Module/Item.php:1013
-msgid "System error. Post not saved."
-msgstr "Systemfehler. Beitrag nicht gespeichert."
+#: ../../Zotlabs/Module/Settings/Channel.php:553
+msgid "Unseen private messages"
+msgstr "Ungelesene persönliche Nachrichten"
-#: ../../Zotlabs/Module/Item.php:1137
-msgid "Unable to obtain post information from database."
-msgstr "Beitragsinformationen können nicht aus der Datenbank abgerufen werden."
+#: ../../Zotlabs/Module/Settings/Channel.php:553
+#: ../../Zotlabs/Module/Settings/Channel.php:558
+#: ../../Zotlabs/Module/Settings/Channel.php:559
+#: ../../Zotlabs/Module/Settings/Channel.php:560
+#: ../../addon/jappixmini/jappixmini.php:343
+msgid "Recommended"
+msgstr "Empfohlen"
-#: ../../Zotlabs/Module/Item.php:1144
-#, php-format
-msgid "You have reached your limit of %1$.0f top level posts."
-msgstr "Du hast die maximale Anzahl von %1$.0f Beiträgen erreicht."
+#: ../../Zotlabs/Module/Settings/Channel.php:554
+msgid "Upcoming events"
+msgstr "Baldige Termine"
-#: ../../Zotlabs/Module/Item.php:1151
-#, php-format
-msgid "You have reached your limit of %1$.0f webpages."
-msgstr "Du hast die maximale Anzahl von %1$.0f Webseiten erreicht."
+#: ../../Zotlabs/Module/Settings/Channel.php:555
+msgid "Events today"
+msgstr "Heutige Termine"
-#: ../../Zotlabs/Module/Chanview.php:134
-msgid "toggle full screen mode"
-msgstr "auf Vollbildmodus umschalten"
+#: ../../Zotlabs/Module/Settings/Channel.php:556
+msgid "Upcoming birthdays"
+msgstr "Baldige Geburtstage"
-#: ../../Zotlabs/Module/Follow.php:31
-msgid "Channel added."
-msgstr "Kanal hinzugefügt."
+#: ../../Zotlabs/Module/Settings/Channel.php:556
+msgid "Not available in all themes"
+msgstr "Nicht in allen Designs verfügbar"
-#: ../../Zotlabs/Module/Mail.php:38
-msgid "Unable to lookup recipient."
-msgstr "Konnte den Empfänger nicht finden."
+#: ../../Zotlabs/Module/Settings/Channel.php:557
+msgid "System (personal) notifications"
+msgstr "System – (persönliche) Benachrichtigungen"
-#: ../../Zotlabs/Module/Mail.php:45
-msgid "Unable to communicate with requested channel."
-msgstr "Die Kommunikation mit dem ausgewählten Kanal ist fehlgeschlagen."
+#: ../../Zotlabs/Module/Settings/Channel.php:558
+msgid "System info messages"
+msgstr "System – Info-Nachrichten"
-#: ../../Zotlabs/Module/Mail.php:52
-msgid "Cannot verify requested channel."
-msgstr "Verifizierung des angeforderten Kanals fehlgeschlagen."
+#: ../../Zotlabs/Module/Settings/Channel.php:559
+msgid "System critical alerts"
+msgstr "System – kritische Warnungen"
-#: ../../Zotlabs/Module/Mail.php:70
-msgid "Selected channel has private message restrictions. Send failed."
-msgstr "Der ausgewählte Kanal hat Einschränkungen bzgl. privater Nachrichten. Senden fehlgeschlagen."
+#: ../../Zotlabs/Module/Settings/Channel.php:560
+msgid "New connections"
+msgstr "Neue Verbindungen"
-#: ../../Zotlabs/Module/Mail.php:149
-msgid "Messages"
-msgstr "Nachrichten"
+#: ../../Zotlabs/Module/Settings/Channel.php:561
+msgid "System Registrations"
+msgstr "System – Registrierungen"
-#: ../../Zotlabs/Module/Mail.php:184
-msgid "Message recalled."
-msgstr "Nachricht widerrufen."
+#: ../../Zotlabs/Module/Settings/Channel.php:562
+msgid "Unseen shared files"
+msgstr "Ungesehene geteilte Dateien"
-#: ../../Zotlabs/Module/Mail.php:197
-msgid "Conversation removed."
-msgstr "Unterhaltung gelöscht."
+#: ../../Zotlabs/Module/Settings/Channel.php:563
+msgid "Unseen public activity"
+msgstr "Ungesehene öffentliche Aktivität"
-#: ../../Zotlabs/Module/Mail.php:211 ../../Zotlabs/Module/Mail.php:320
-#: ../../Zotlabs/Module/Chat.php:205 ../../include/conversation.php:1200
-msgid "Please enter a link URL:"
-msgstr "Gib eine URL ein:"
+#: ../../Zotlabs/Module/Settings/Channel.php:564
+msgid ""
+"Also show new wall posts, private messages and connections under Notices"
+msgstr "Neue Pinnwand-Nachrichten, private Nachrichten und Verbindungen unter Benachrichtigungen anzeigen"
-#: ../../Zotlabs/Module/Mail.php:212 ../../Zotlabs/Module/Mail.php:321
-msgid "Expires YYYY-MM-DD HH:MM"
-msgstr "Verfällt YYYY-MM-DD HH;MM"
+#: ../../Zotlabs/Module/Settings/Channel.php:566
+msgid "Notify me of events this many days in advance"
+msgstr "Benachrichtige mich zu Terminen so viele Tage im Voraus"
-#: ../../Zotlabs/Module/Mail.php:240
-msgid "Requested channel is not in this network"
-msgstr "Angeforderter Kanal ist nicht in diesem Netzwerk."
+#: ../../Zotlabs/Module/Settings/Channel.php:566
+msgid "Must be greater than 0"
+msgstr "Muss größer als 0 sein"
-#: ../../Zotlabs/Module/Mail.php:248
-msgid "Send Private Message"
-msgstr "Private Nachricht senden"
+#: ../../Zotlabs/Module/Settings/Channel.php:572
+msgid "Advanced Account/Page Type Settings"
+msgstr "Erweiterte Account- und Seitenart-Einstellungen"
-#: ../../Zotlabs/Module/Mail.php:249 ../../Zotlabs/Module/Mail.php:374
-msgid "To:"
-msgstr "An:"
+#: ../../Zotlabs/Module/Settings/Channel.php:573
+msgid "Change the behaviour of this account for special situations"
+msgstr "Ändere das Verhalten dieses Accounts unter speziellen Umständen"
-#: ../../Zotlabs/Module/Mail.php:252 ../../Zotlabs/Module/Mail.php:376
-msgid "Subject:"
-msgstr "Betreff:"
+#: ../../Zotlabs/Module/Settings/Channel.php:575
+msgid "Miscellaneous Settings"
+msgstr "Sonstige Einstellungen"
-#: ../../Zotlabs/Module/Mail.php:255 ../../Zotlabs/Module/Invite.php:138
-msgid "Your message:"
-msgstr "Deine Nachricht:"
+#: ../../Zotlabs/Module/Settings/Channel.php:576
+msgid "Default photo upload folder"
+msgstr "Voreingestellter Ordner für hochgeladene Fotos"
-#: ../../Zotlabs/Module/Mail.php:257 ../../Zotlabs/Module/Mail.php:382
-#: ../../include/conversation.php:1260
-msgid "Attach file"
-msgstr "Datei anhängen"
+#: ../../Zotlabs/Module/Settings/Channel.php:576
+#: ../../Zotlabs/Module/Settings/Channel.php:577
+msgid "%Y - current year, %m - current month"
+msgstr "%Y - aktuelles Jahr, %m - aktueller Monat"
-#: ../../Zotlabs/Module/Mail.php:259
-msgid "Send"
-msgstr "Absenden"
+#: ../../Zotlabs/Module/Settings/Channel.php:577
+msgid "Default file upload folder"
+msgstr "Voreingestellter Ordner für hochgeladene Dateien"
-#: ../../Zotlabs/Module/Mail.php:262 ../../Zotlabs/Module/Mail.php:387
-#: ../../include/conversation.php:1305
-msgid "Set expiration date"
-msgstr "Verfallsdatum"
+#: ../../Zotlabs/Module/Settings/Channel.php:579
+msgid "Personal menu to display in your channel pages"
+msgstr "Eigenes Menü zur Anzeige auf den Seiten deines Kanals"
-#: ../../Zotlabs/Module/Mail.php:264 ../../Zotlabs/Module/Mail.php:389
-#: ../../Zotlabs/Module/Chat.php:206 ../../Zotlabs/Lib/ThreadItem.php:741
-#: ../../include/conversation.php:1310
-msgid "Encrypt text"
-msgstr "Text verschlüsseln"
+#: ../../Zotlabs/Module/Settings/Channel.php:581
+msgid "Remove this channel."
+msgstr "Diesen Kanal löschen"
-#: ../../Zotlabs/Module/Mail.php:346
-msgid "Delete message"
-msgstr "Nachricht löschen"
+#: ../../Zotlabs/Module/Settings/Channel.php:582
+msgid "Firefox Share $Projectname provider"
+msgstr "$Projectname-Provider für Firefox Share"
-#: ../../Zotlabs/Module/Mail.php:347
-msgid "Delivery report"
-msgstr "Zustellungsbericht"
+#: ../../Zotlabs/Module/Settings/Channel.php:583
+msgid "Start calendar week on Monday"
+msgstr "Beginne die kalendarische Woche am Montag"
-#: ../../Zotlabs/Module/Mail.php:348
-msgid "Recall message"
-msgstr "Nachricht widerrufen"
+#: ../../Zotlabs/Module/Settings/Features.php:45
+msgid "Additional Features"
+msgstr "Zusätzliche Funktionen"
-#: ../../Zotlabs/Module/Mail.php:350
-msgid "Message has been recalled."
-msgstr "Die Nachricht wurde widerrufen."
+#: ../../Zotlabs/Module/Settings/Tokens.php:31
+#, php-format
+msgid "This channel is limited to %d tokens"
+msgstr "Dieser Kanal ist auf %d Token begrenzt"
-#: ../../Zotlabs/Module/Mail.php:367
-msgid "Delete Conversation"
-msgstr "Unterhaltung löschen"
+#: ../../Zotlabs/Module/Settings/Tokens.php:37
+msgid "Name and Password are required."
+msgstr "Name und Passwort sind erforderlich."
-#: ../../Zotlabs/Module/Mail.php:369
+#: ../../Zotlabs/Module/Settings/Tokens.php:77
+msgid "Token saved."
+msgstr "Token gespeichert."
+
+#: ../../Zotlabs/Module/Settings/Tokens.php:113
msgid ""
-"No secure communications available. You <strong>may</strong> be able to "
-"respond from the sender's profile page."
-msgstr "Keine sichere Kommunikation verfügbar. <strong>Eventuell</strong> kannst Du auf der Profilseite des Absenders antworten."
+"Use this form to create temporary access identifiers to share things with "
+"non-members. These identities may be used in Access Control Lists and "
+"visitors may login using these credentials to access private content."
+msgstr "Mit diesem Formular kannst Du temporäre Zugangs-IDs anlegen, um Inhalte mit Nicht-Mitgliedern zu teilen. Die IDs können in Berechtigungslisten (ACLs) verwendet werden, und Besucher können sich damit einloggen, um auf private Inhalte zuzugreifen."
-#: ../../Zotlabs/Module/Mail.php:373
-msgid "Send Reply"
-msgstr "Antwort senden"
+#: ../../Zotlabs/Module/Settings/Tokens.php:115
+msgid ""
+"You may also provide <em>dropbox</em> style access links to friends and "
+"associates by adding the Login Password to any specific site URL as shown. "
+"Examples:"
+msgstr "Du kannst auch <em>Dropbox</em>-ähnliche Zugriffslinks an Andere weitergeben, indem du das Login-Passwort an eine entsprechende URL anhängst wie nachfolgend gezeigt. Beispiele:"
-#: ../../Zotlabs/Module/Mail.php:378
-#, php-format
-msgid "Your message for %s (%s):"
-msgstr "Deine Nachricht für %s (%s):"
+#: ../../Zotlabs/Module/Settings/Tokens.php:150
+#: ../../Zotlabs/Widget/Settings_menu.php:92
+msgid "Guest Access Tokens"
+msgstr "Gastzugangstoken"
-#: ../../Zotlabs/Module/Impel.php:41 ../../include/bbcode.php:203
-msgid "webpage"
-msgstr "Webseite"
+#: ../../Zotlabs/Module/Settings/Tokens.php:157
+msgid "Login Name"
+msgstr "Anmeldename"
-#: ../../Zotlabs/Module/Impel.php:46 ../../include/bbcode.php:209
-msgid "block"
-msgstr "Block"
+#: ../../Zotlabs/Module/Settings/Tokens.php:158
+msgid "Login Password"
+msgstr "Anmeldepasswort"
-#: ../../Zotlabs/Module/Impel.php:51 ../../include/bbcode.php:206
-msgid "layout"
-msgstr "Layout"
+#: ../../Zotlabs/Module/Settings/Tokens.php:159
+msgid "Expires (yyyy-mm-dd)"
+msgstr "Läuft ab (jjjj-mm-tt)"
-#: ../../Zotlabs/Module/Impel.php:58 ../../include/bbcode.php:212
-msgid "menu"
-msgstr "Menü"
+#: ../../Zotlabs/Module/Settings/Tokens.php:160
+#: ../../Zotlabs/Module/Connedit.php:907
+msgid "Their Settings"
+msgstr "Deren Einstellungen"
-#: ../../Zotlabs/Module/Impel.php:191
-#, php-format
-msgid "%s element installed"
-msgstr "Element für %s installiert"
+#: ../../Zotlabs/Module/Settings/Account.php:20
+msgid "Not valid email."
+msgstr "Keine gültige E-Mail Adresse."
-#: ../../Zotlabs/Module/Impel.php:194
-#, php-format
-msgid "%s element installation failed"
-msgstr "Installation des Elements %s fehlgeschlagen"
+#: ../../Zotlabs/Module/Settings/Account.php:23
+msgid "Protected email address. Cannot change to that email."
+msgstr "Geschützte E-Mail Adresse. Diese kann nicht verändert werden."
-#: ../../Zotlabs/Module/Import_items.php:42 ../../Zotlabs/Module/Import.php:71
-msgid "Nothing to import."
-msgstr "Nichts zu importieren."
+#: ../../Zotlabs/Module/Settings/Account.php:32
+msgid "System failure storing new email. Please try again."
+msgstr "Systemfehler während des Speicherns der neuen Mail. Bitte versuche es noch einmal."
-#: ../../Zotlabs/Module/Import_items.php:66 ../../Zotlabs/Module/Import.php:83
-#: ../../Zotlabs/Module/Import.php:98
-msgid "Unable to download data from old server"
-msgstr "Daten können vom alten Server nicht heruntergeladen werden"
+#: ../../Zotlabs/Module/Settings/Account.php:40
+msgid "Technical skill level updated"
+msgstr "Technische Qualifikationsstufe aktualisiert"
-#: ../../Zotlabs/Module/Import_items.php:72
-#: ../../Zotlabs/Module/Import.php:105
-msgid "Imported file is empty."
-msgstr "Die importierte Datei ist leer."
+#: ../../Zotlabs/Module/Settings/Account.php:56
+msgid "Password verification failed."
+msgstr "Passwortüberprüfung fehlgeschlagen."
-#: ../../Zotlabs/Module/Import_items.php:88
-#: ../../Zotlabs/Module/Import.php:127
-#, php-format
-msgid "Warning: Database versions differ by %1$d updates."
-msgstr "Achtung: Datenbankversionen unterscheiden sich um %1$d Aktualisierungen."
+#: ../../Zotlabs/Module/Settings/Account.php:63
+msgid "Passwords do not match. Password unchanged."
+msgstr "Kennwörter stimmen nicht überein. Kennwort nicht verändert."
-#: ../../Zotlabs/Module/Import_items.php:104
-msgid "Import completed"
-msgstr "Import abgeschlossen"
+#: ../../Zotlabs/Module/Settings/Account.php:67
+msgid "Empty passwords are not allowed. Password unchanged."
+msgstr "Leere Kennwörter sind nicht erlaubt. Kennwort nicht verändert."
-#: ../../Zotlabs/Module/Import_items.php:119
-msgid "Import Items"
-msgstr "Beiträge importieren"
+#: ../../Zotlabs/Module/Settings/Account.php:81
+msgid "Password changed."
+msgstr "Kennwort geändert."
-#: ../../Zotlabs/Module/Import_items.php:120
-msgid ""
-"Use this form to import existing posts and content from an export file."
-msgstr "Mit diesem Formular kannst Du existierende Beiträge und Inhalte aus einer Sicherungsdatei importieren."
+#: ../../Zotlabs/Module/Settings/Account.php:83
+msgid "Password update failed. Please try again."
+msgstr "Kennwortänderung fehlgeschlagen. Bitte versuche es noch einmal."
-#: ../../Zotlabs/Module/Import_items.php:121
-#: ../../Zotlabs/Module/Import.php:532
-msgid "File to Upload"
-msgstr "Hochzuladende Datei:"
+#: ../../Zotlabs/Module/Settings/Account.php:112
+msgid "Account Settings"
+msgstr "Konto-Einstellungen"
-#: ../../Zotlabs/Module/Invite.php:29
-msgid "Total invitation limit exceeded."
-msgstr "Einladungslimit überschritten."
+#: ../../Zotlabs/Module/Settings/Account.php:113
+msgid "Current Password"
+msgstr "Aktuelles Passwort"
-#: ../../Zotlabs/Module/Invite.php:53
-#, php-format
-msgid "%s : Not a valid email address."
-msgstr "%s : Keine gültige Email Adresse."
+#: ../../Zotlabs/Module/Settings/Account.php:114
+msgid "Enter New Password"
+msgstr "Gib ein neues Passwort ein"
-#: ../../Zotlabs/Module/Invite.php:67
-msgid "Please join us on $Projectname"
-msgstr "Schließe Dich uns auf $Projectname an!"
+#: ../../Zotlabs/Module/Settings/Account.php:115
+msgid "Confirm New Password"
+msgstr "Bestätige das neue Passwort"
-#: ../../Zotlabs/Module/Invite.php:77
-msgid "Invitation limit exceeded. Please contact your site administrator."
-msgstr "Einladungslimit überschritten. Bitte kontaktiere den Administrator Deines $Projectname-Servers."
+#: ../../Zotlabs/Module/Settings/Account.php:115
+msgid "Leave password fields blank unless changing"
+msgstr "Lasse die Passwort-Felder leer, außer Du möchtest das Passwort ändern"
-#: ../../Zotlabs/Module/Invite.php:82
-#, php-format
-msgid "%s : Message delivery failed."
-msgstr "%s : Nachricht konnte nicht zugestellt werden."
+#: ../../Zotlabs/Module/Settings/Account.php:116
+msgid "Your technical skill level"
+msgstr "Deine technische Qualifikationsstufe"
-#: ../../Zotlabs/Module/Invite.php:86
+#: ../../Zotlabs/Module/Settings/Account.php:116
+msgid "Used to provide a member experience matched to your comfort level"
+msgstr "Dies wird verwendet, um Dir eine Benutzererfahrung passend zu Deiner technischen Qualifikationsstufe zu bieten."
+
+#: ../../Zotlabs/Module/Settings/Account.php:120
+#: ../../Zotlabs/Module/Removeaccount.php:61
+msgid "Remove Account"
+msgstr "Konto entfernen"
+
+#: ../../Zotlabs/Module/Settings/Account.php:121
+msgid "Remove this account including all its channels"
+msgstr "Dieses Konto inklusive all seiner Kanäle löschen"
+
+#: ../../Zotlabs/Module/Settings/Featured.php:21
+msgid "Affinity Slider settings updated."
+msgstr "Die Beziehungsgrad-Schieberegler-Einstellungen wurden aktualisiert."
+
+#: ../../Zotlabs/Module/Settings/Featured.php:36
+msgid "No feature settings configured"
+msgstr "Keine Funktions-Einstellungen konfiguriert"
+
+#: ../../Zotlabs/Module/Settings/Featured.php:43
+msgid "Default maximum affinity level"
+msgstr "Voreinstellung für maximalen Beziehungsgrad"
+
+#: ../../Zotlabs/Module/Settings/Featured.php:48
+msgid "Default minimum affinity level"
+msgstr "Voreinstellung für minimalen Beziehungsgrad"
+
+#: ../../Zotlabs/Module/Settings/Featured.php:52
+msgid "Affinity Slider Settings"
+msgstr "Beziehungsgrad-Schieberegler-Einstellungen"
+
+#: ../../Zotlabs/Module/Settings/Featured.php:62
+msgid "Feature/Addon Settings"
+msgstr "Funktions-/Addon-Einstellungen"
+
+#: ../../Zotlabs/Module/Settings/Display.php:145
+msgid "No special theme for mobile devices"
+msgstr "Kein spezielles Design für mobile Geräte"
+
+#: ../../Zotlabs/Module/Settings/Display.php:148
#, php-format
-msgid "%d message sent."
-msgid_plural "%d messages sent."
-msgstr[0] "%d Nachricht gesendet."
-msgstr[1] "%d Nachrichten gesendet."
+msgid "%s - (Experimental)"
+msgstr "%s – (experimentell)"
-#: ../../Zotlabs/Module/Invite.php:105
-msgid "You have no more invitations available"
-msgstr "Du hast keine weiteren verfügbare Einladungen"
+#: ../../Zotlabs/Module/Settings/Display.php:202
+msgid "Display Settings"
+msgstr "Anzeige-Einstellungen"
-#: ../../Zotlabs/Module/Invite.php:136
-msgid "Send invitations"
-msgstr "Einladungen senden"
+#: ../../Zotlabs/Module/Settings/Display.php:203
+msgid "Theme Settings"
+msgstr "Design-Einstellungen"
-#: ../../Zotlabs/Module/Invite.php:137
-msgid "Enter email addresses, one per line:"
-msgstr "Email-Adressen eintragen, eine pro Zeile:"
+#: ../../Zotlabs/Module/Settings/Display.php:204
+msgid "Custom Theme Settings"
+msgstr "Benutzerdefinierte Design-Einstellungen"
-#: ../../Zotlabs/Module/Invite.php:139
-msgid "Please join my community on $Projectname."
-msgstr "Schließe Dich uns auf $Projectname an!"
+#: ../../Zotlabs/Module/Settings/Display.php:205
+msgid "Content Settings"
+msgstr "Inhaltseinstellungen"
-#: ../../Zotlabs/Module/Invite.php:141
-msgid "You will need to supply this invitation code:"
-msgstr "Bitte verwende bei der Registrierung den folgenden Einladungscode:"
+#: ../../Zotlabs/Module/Settings/Display.php:211
+msgid "Display Theme:"
+msgstr "Anzeige-Design:"
+
+#: ../../Zotlabs/Module/Settings/Display.php:212
+msgid "Select scheme"
+msgstr "Schema wählen"
+
+#: ../../Zotlabs/Module/Settings/Display.php:214
+msgid "Mobile Theme:"
+msgstr "Design für mobile Geräte:"
-#: ../../Zotlabs/Module/Invite.php:142
+#: ../../Zotlabs/Module/Settings/Display.php:215
+msgid "Preload images before rendering the page"
+msgstr "Bilder im voraus laden, bevor die Seite angezeigt wird"
+
+#: ../../Zotlabs/Module/Settings/Display.php:215
msgid ""
-"1. Register at any $Projectname location (they are all inter-connected)"
-msgstr "1. Registriere Dich auf einem beliebigen $Projectname-Hub (sie sind alle miteinander verbunden)"
+"The subjective page load time will be longer but the page will be ready when"
+" displayed"
+msgstr "Die empfundene Ladezeit wird sich erhöhen, aber dafür ist das Layout stabil, sobald eine Seite angezeigt wird"
-#: ../../Zotlabs/Module/Invite.php:144
-msgid "2. Enter my $Projectname network address into the site searchbar."
-msgstr "2. Gib meine $Projectname-Adresse im Suchfeld ein."
+#: ../../Zotlabs/Module/Settings/Display.php:216
+msgid "Enable user zoom on mobile devices"
+msgstr "Zoom auf Mobilgeräten aktivieren"
-#: ../../Zotlabs/Module/Invite.php:145
-msgid "or visit"
-msgstr "oder besuche"
+#: ../../Zotlabs/Module/Settings/Display.php:217
+msgid "Update browser every xx seconds"
+msgstr "Browser alle xx Sekunden aktualisieren"
-#: ../../Zotlabs/Module/Invite.php:147
-msgid "3. Click [Connect]"
-msgstr "3. Klicke auf [Verbinden]"
+#: ../../Zotlabs/Module/Settings/Display.php:217
+msgid "Minimum of 10 seconds, no maximum"
+msgstr "Minimum 10 Sekunden, kein Maximum"
-#: ../../Zotlabs/Module/Editblock.php:108 ../../Zotlabs/Module/Blocks.php:97
-#: ../../Zotlabs/Module/Blocks.php:155
-msgid "Block Name"
-msgstr "Block-Name"
+#: ../../Zotlabs/Module/Settings/Display.php:218
+msgid "Maximum number of conversations to load at any time:"
+msgstr "Maximale Anzahl von Unterhaltungen, die auf einmal geladen werden sollen:"
-#: ../../Zotlabs/Module/Editblock.php:124 ../../include/conversation.php:1276
-msgid "Title (optional)"
-msgstr "Titel (optional)"
+#: ../../Zotlabs/Module/Settings/Display.php:218
+msgid "Maximum of 100 items"
+msgstr "Maximum: 100 Beiträge"
-#: ../../Zotlabs/Module/Editblock.php:133
-msgid "Edit Block"
-msgstr "Block bearbeiten"
+#: ../../Zotlabs/Module/Settings/Display.php:219
+msgid "Show emoticons (smilies) as images"
+msgstr "Emoticons (Smilies) als Bilder anzeigen"
-#: ../../Zotlabs/Module/Group.php:24
-msgid "Privacy group created."
-msgstr "Gruppe wurde erstellt."
+#: ../../Zotlabs/Module/Settings/Display.php:220
+msgid "Manual conversation updates"
+msgstr "Manuelle Konversationsaktualisierung"
-#: ../../Zotlabs/Module/Group.php:30
-msgid "Could not create privacy group."
-msgstr "Gruppe konnte nicht erstellt werden."
+#: ../../Zotlabs/Module/Settings/Display.php:220
+msgid "Default is on, turning this off may increase screen jumping"
+msgstr "Voreinstellung ist An, dies abzuschalten kann das unerwartete Springen der Seitenanzeige erhöhen."
-#: ../../Zotlabs/Module/Group.php:42 ../../Zotlabs/Module/Group.php:141
-#: ../../include/items.php:3876
-msgid "Privacy group not found."
-msgstr "Gruppe nicht gefunden."
+#: ../../Zotlabs/Module/Settings/Display.php:221
+msgid "Link post titles to source"
+msgstr "Beitragstitel zum Originalbeitrag verlinken"
-#: ../../Zotlabs/Module/Group.php:58
-msgid "Privacy group updated."
-msgstr "Gruppe wurde aktualisiert."
+#: ../../Zotlabs/Module/Settings/Display.php:222
+msgid "System Page Layout Editor - (advanced)"
+msgstr "System-Seitenlayout-Editor (für Experten)"
-#: ../../Zotlabs/Module/Group.php:90
-msgid "Create a group of channels."
-msgstr "Erstelle eine Gruppe für Kanäle."
+#: ../../Zotlabs/Module/Settings/Display.php:225
+msgid "Use blog/list mode on channel page"
+msgstr "Blog-/Listenmodus auf der Kanalseite verwenden"
-#: ../../Zotlabs/Module/Group.php:91 ../../Zotlabs/Module/Group.php:184
-msgid "Privacy group name: "
-msgstr "Gruppenname:"
+#: ../../Zotlabs/Module/Settings/Display.php:225
+#: ../../Zotlabs/Module/Settings/Display.php:226
+msgid "(comments displayed separately)"
+msgstr "(Kommentare werden separat angezeigt)"
-#: ../../Zotlabs/Module/Group.php:93 ../../Zotlabs/Module/Group.php:187
-msgid "Members are visible to other channels"
-msgstr "Mitglieder sind sichtbar für andere Kanäle"
+#: ../../Zotlabs/Module/Settings/Display.php:226
+msgid "Use blog/list mode on grid page"
+msgstr "Blog-/Listenmodus auf der Netzwerkseite verwenden"
-#: ../../Zotlabs/Module/Group.php:111
-msgid "Privacy group removed."
-msgstr "Gruppe wurde entfernt."
+#: ../../Zotlabs/Module/Settings/Display.php:227
+msgid "Channel page max height of content (in pixels)"
+msgstr "Maximale Höhe von Beitragsblöcken auf der Kanalseite (in Pixeln)"
-#: ../../Zotlabs/Module/Group.php:113
-msgid "Unable to remove privacy group."
-msgstr "Gruppe konnte nicht entfernt werden."
+#: ../../Zotlabs/Module/Settings/Display.php:227
+#: ../../Zotlabs/Module/Settings/Display.php:228
+msgid "click to expand content exceeding this height"
+msgstr "Blöcke, deren Inhalt diese Höhe überschreitet, können per Klick vergrößert werden."
-#: ../../Zotlabs/Module/Group.php:183
-msgid "Privacy group editor"
-msgstr "Gruppeneditor"
+#: ../../Zotlabs/Module/Settings/Display.php:228
+msgid "Grid page max height of content (in pixels)"
+msgstr "Maximale Höhe (in Pixel) des Inhalts der Netzwerkseite"
-#: ../../Zotlabs/Module/Group.php:197
-msgid "Members"
-msgstr "Mitglieder"
+#: ../../Zotlabs/Module/Settings/Oauth.php:34
+msgid "Name is required"
+msgstr "Name ist erforderlich"
-#: ../../Zotlabs/Module/Group.php:199
-msgid "All Connected Channels"
-msgstr "Alle verbundenen Kanäle"
+#: ../../Zotlabs/Module/Settings/Oauth.php:38
+msgid "Key and Secret are required"
+msgstr "Schlüssel und Geheimnis werden benötigt"
-#: ../../Zotlabs/Module/Group.php:231
-msgid "Click on a channel to add or remove."
-msgstr "Wähle einen Kanal zum hinzufügen oder entfernen aus."
+#: ../../Zotlabs/Module/Settings/Oauth.php:86
+#: ../../Zotlabs/Module/Settings/Oauth.php:112
+#: ../../Zotlabs/Module/Settings/Oauth.php:148
+msgid "Add application"
+msgstr "Anwendung hinzufügen"
-#: ../../Zotlabs/Module/Profperm.php:34 ../../Zotlabs/Module/Profperm.php:63
-msgid "Invalid profile identifier."
-msgstr "Ungültiger Profil-Identifikator"
+#: ../../Zotlabs/Module/Settings/Oauth.php:89
+msgid "Name of application"
+msgstr "Name der Anwendung"
-#: ../../Zotlabs/Module/Profperm.php:115
-msgid "Profile Visibility Editor"
-msgstr "Profil-Sichtbarkeits-Editor"
+#: ../../Zotlabs/Module/Settings/Oauth.php:90
+#: ../../Zotlabs/Module/Settings/Oauth.php:116
+#: ../../addon/statusnet/statusnet.php:893 ../../addon/twitter/twitter.php:775
+msgid "Consumer Key"
+msgstr "Consumer Key"
-#: ../../Zotlabs/Module/Profperm.php:117 ../../include/channel.php:1282
-msgid "Profile"
-msgstr "Profil"
+#: ../../Zotlabs/Module/Settings/Oauth.php:90
+#: ../../Zotlabs/Module/Settings/Oauth.php:91
+msgid "Automatically generated - change if desired. Max length 20"
+msgstr "Automatisch erzeugt – ändern, falls erwünscht. Maximale Länge 20"
-#: ../../Zotlabs/Module/Profperm.php:119
-msgid "Click on a contact to add or remove."
-msgstr "Klicke auf einen Kontakt, um ihn hinzuzufügen oder zu entfernen."
+#: ../../Zotlabs/Module/Settings/Oauth.php:91
+#: ../../Zotlabs/Module/Settings/Oauth.php:117
+#: ../../addon/statusnet/statusnet.php:892 ../../addon/twitter/twitter.php:776
+msgid "Consumer Secret"
+msgstr "Consumer Secret"
-#: ../../Zotlabs/Module/Profperm.php:128
-msgid "Visible To"
-msgstr "Sichtbar für"
+#: ../../Zotlabs/Module/Settings/Oauth.php:92
+#: ../../Zotlabs/Module/Settings/Oauth.php:118
+msgid "Redirect"
+msgstr "Umleitung"
-#: ../../Zotlabs/Module/Magic.php:71
-msgid "Hub not found."
-msgstr "Server nicht gefunden."
+#: ../../Zotlabs/Module/Settings/Oauth.php:92
+msgid ""
+"Redirect URI - leave blank unless your application specifically requires "
+"this"
+msgstr "Umleitungs-URl – lasse das leer, solange Deine Anwendung es nicht explizit erfordert"
-#: ../../Zotlabs/Module/Mitem.php:52
-msgid "Unable to create element."
-msgstr "Element konnte nicht erstellt werden."
+#: ../../Zotlabs/Module/Settings/Oauth.php:93
+#: ../../Zotlabs/Module/Settings/Oauth.php:119
+msgid "Icon url"
+msgstr "Symbol-URL"
-#: ../../Zotlabs/Module/Mitem.php:76
-msgid "Unable to update menu element."
-msgstr "Kann Menü-Element nicht aktualisieren."
+#: ../../Zotlabs/Module/Settings/Oauth.php:93
+#: ../../Zotlabs/Module/Sources.php:112 ../../Zotlabs/Module/Sources.php:147
+msgid "Optional"
+msgstr "Optional"
-#: ../../Zotlabs/Module/Mitem.php:92
-msgid "Unable to add menu element."
-msgstr "Kann Menü-Bestandteil nicht hinzufügen."
+#: ../../Zotlabs/Module/Settings/Oauth.php:104
+msgid "Application not found."
+msgstr "Die Anwendung wurde nicht gefunden."
-#: ../../Zotlabs/Module/Mitem.php:153 ../../Zotlabs/Module/Mitem.php:230
-msgid "Menu Item Permissions"
-msgstr "Zugriffsrechte des Menü-Elements"
+#: ../../Zotlabs/Module/Settings/Oauth.php:147
+msgid "Connected Apps"
+msgstr "Verbundene Apps"
-#: ../../Zotlabs/Module/Mitem.php:154 ../../Zotlabs/Module/Mitem.php:231
-#: ../../Zotlabs/Module/Settings/Channel.php:489
-msgid "(click to open/close)"
-msgstr "(zum öffnen/schließen anklicken)"
+#: ../../Zotlabs/Module/Settings/Oauth.php:151
+msgid "Client key starts with"
+msgstr "Client Key beginnt mit"
-#: ../../Zotlabs/Module/Mitem.php:160 ../../Zotlabs/Module/Mitem.php:176
-msgid "Link Name"
-msgstr "Name des Links"
+#: ../../Zotlabs/Module/Settings/Oauth.php:152
+msgid "No name"
+msgstr "Kein Name"
-#: ../../Zotlabs/Module/Mitem.php:161 ../../Zotlabs/Module/Mitem.php:239
-msgid "Link or Submenu Target"
-msgstr "Ziel des Links oder Untermenüs"
+#: ../../Zotlabs/Module/Settings/Oauth.php:153
+msgid "Remove authorization"
+msgstr "Authorisierung aufheben"
-#: ../../Zotlabs/Module/Mitem.php:161
-msgid "Enter URL of the link or select a menu name to create a submenu"
-msgstr "URL des Links eingeben oder Menünamen wählen, um ein Untermenü anzulegen."
+#: ../../Zotlabs/Module/Embedphotos.php:140
+#: ../../Zotlabs/Module/Photos.php:758 ../../Zotlabs/Module/Photos.php:1297
+#: ../../Zotlabs/Widget/Portfolio.php:78 ../../Zotlabs/Widget/Album.php:78
+msgid "View Photo"
+msgstr "Foto ansehen"
-#: ../../Zotlabs/Module/Mitem.php:162 ../../Zotlabs/Module/Mitem.php:240
-msgid "Use magic-auth if available"
-msgstr "Magic-Auth verwenden, falls verfügbar"
+#: ../../Zotlabs/Module/Embedphotos.php:156
+#: ../../Zotlabs/Module/Photos.php:789 ../../Zotlabs/Widget/Portfolio.php:97
+#: ../../Zotlabs/Widget/Album.php:95
+msgid "Edit Album"
+msgstr "Album bearbeiten"
-#: ../../Zotlabs/Module/Mitem.php:163 ../../Zotlabs/Module/Mitem.php:241
-msgid "Open link in new window"
-msgstr "Öffne Link in neuem Fenster"
+#: ../../Zotlabs/Module/Embedphotos.php:158
+#: ../../Zotlabs/Module/Photos.php:791 ../../Zotlabs/Module/Photos.php:1328
+#: ../../Zotlabs/Module/Profile_photo.php:431
+#: ../../Zotlabs/Module/Cover_photo.php:361
+#: ../../Zotlabs/Storage/Browser.php:230 ../../Zotlabs/Storage/Browser.php:337
+#: ../../Zotlabs/Widget/Cdav.php:132 ../../Zotlabs/Widget/Cdav.php:168
+#: ../../Zotlabs/Widget/Portfolio.php:99 ../../Zotlabs/Widget/Album.php:97
+msgid "Upload"
+msgstr "Hochladen"
-#: ../../Zotlabs/Module/Mitem.php:164 ../../Zotlabs/Module/Mitem.php:242
-msgid "Order in list"
-msgstr "Reihenfolge in der Liste"
+#: ../../Zotlabs/Module/Achievements.php:38
+msgid "Some blurb about what to do when you're new here"
+msgstr "Ein Hinweis, was man tun kann, wenn man neu hier ist"
-#: ../../Zotlabs/Module/Mitem.php:164 ../../Zotlabs/Module/Mitem.php:242
-msgid "Higher numbers will sink to bottom of listing"
-msgstr "Größere Nummern werden weiter unten in der Auflistung einsortiert"
+#: ../../Zotlabs/Module/Thing.php:115
+msgid "Thing updated"
+msgstr "Sache aktualisiert"
-#: ../../Zotlabs/Module/Mitem.php:165
-msgid "Submit and finish"
-msgstr "Absenden und fertigstellen"
+#: ../../Zotlabs/Module/Thing.php:167
+msgid "Object store: failed"
+msgstr "Speichern des Objekts fehlgeschlagen"
-#: ../../Zotlabs/Module/Mitem.php:166
-msgid "Submit and continue"
-msgstr "Absenden und fortfahren"
+#: ../../Zotlabs/Module/Thing.php:171
+msgid "Thing added"
+msgstr "Sache hinzugefügt"
-#: ../../Zotlabs/Module/Mitem.php:174
-msgid "Menu:"
-msgstr "Menü:"
+#: ../../Zotlabs/Module/Thing.php:197
+#, php-format
+msgid "OBJ: %1$s %2$s %3$s"
+msgstr "OBJ: %1$s %2$s %3$s"
-#: ../../Zotlabs/Module/Mitem.php:177
-msgid "Link Target"
-msgstr "Ziel des Links"
+#: ../../Zotlabs/Module/Thing.php:260
+msgid "Show Thing"
+msgstr "Sache anzeigen"
-#: ../../Zotlabs/Module/Mitem.php:180
-msgid "Edit menu"
-msgstr "Menü bearbeiten"
+#: ../../Zotlabs/Module/Thing.php:267
+msgid "item not found."
+msgstr "Eintrag nicht gefunden"
-#: ../../Zotlabs/Module/Mitem.php:183
-msgid "Edit element"
-msgstr "Bestandteil bearbeiten"
+#: ../../Zotlabs/Module/Thing.php:300
+msgid "Edit Thing"
+msgstr "Sache bearbeiten"
-#: ../../Zotlabs/Module/Mitem.php:184
-msgid "Drop element"
-msgstr "Bestandteil löschen"
+#: ../../Zotlabs/Module/Thing.php:302 ../../Zotlabs/Module/Thing.php:359
+msgid "Select a profile"
+msgstr "Wähle ein Profil"
-#: ../../Zotlabs/Module/Mitem.php:185
-msgid "New element"
-msgstr "Neues Bestandteil"
+#: ../../Zotlabs/Module/Thing.php:306 ../../Zotlabs/Module/Thing.php:362
+msgid "Post an activity"
+msgstr "Aktivitätsnachricht senden"
-#: ../../Zotlabs/Module/Mitem.php:186
-msgid "Edit this menu container"
-msgstr "Diesen Menü-Container bearbeiten"
+#: ../../Zotlabs/Module/Thing.php:306 ../../Zotlabs/Module/Thing.php:362
+msgid "Only sends to viewers of the applicable profile"
+msgstr "Nur an Betrachter des ausgewählten Profils senden"
-#: ../../Zotlabs/Module/Mitem.php:187
-msgid "Add menu element"
-msgstr "Menüelement hinzufügen"
+#: ../../Zotlabs/Module/Thing.php:308 ../../Zotlabs/Module/Thing.php:364
+msgid "Name of thing e.g. something"
+msgstr "Name der Sache, z. B. irgendwas"
-#: ../../Zotlabs/Module/Mitem.php:188
-msgid "Delete this menu item"
-msgstr "Lösche dieses Menü-Bestandteil"
+#: ../../Zotlabs/Module/Thing.php:310 ../../Zotlabs/Module/Thing.php:365
+msgid "URL of thing (optional)"
+msgstr "URL der Sache (optional)"
-#: ../../Zotlabs/Module/Mitem.php:189
-msgid "Edit this menu item"
-msgstr "Bearbeite dieses Menü-Bestandteil"
+#: ../../Zotlabs/Module/Thing.php:312 ../../Zotlabs/Module/Thing.php:366
+msgid "URL for photo of thing (optional)"
+msgstr "URL eines Fotos der Sache (optional)"
-#: ../../Zotlabs/Module/Mitem.php:206
-msgid "Menu item not found."
-msgstr "Menü-Bestandteil nicht gefunden."
+#: ../../Zotlabs/Module/Thing.php:314 ../../Zotlabs/Module/Thing.php:367
+#: ../../Zotlabs/Module/Photos.php:649 ../../Zotlabs/Module/Photos.php:1018
+#: ../../Zotlabs/Module/Connedit.php:676 ../../Zotlabs/Module/Chat.php:235
+#: ../../Zotlabs/Module/Filestorage.php:142
+#: ../../include/acl_selectors.php:218
+msgid "Permissions"
+msgstr "Berechtigungen"
-#: ../../Zotlabs/Module/Mitem.php:219
-msgid "Menu item deleted."
-msgstr "Menü-Bestandteil gelöscht."
+#: ../../Zotlabs/Module/Thing.php:357
+msgid "Add Thing to your Profile"
+msgstr "Die Sache Deinem Profil hinzufügen"
-#: ../../Zotlabs/Module/Mitem.php:221
-msgid "Menu item could not be deleted."
-msgstr "Menü-Bestandteil kann nicht gelöscht werden."
+#: ../../Zotlabs/Module/Notify.php:61
+#: ../../Zotlabs/Module/Notifications.php:38
+msgid "No more system notifications."
+msgstr "Keine System-Benachrichtigungen mehr."
-#: ../../Zotlabs/Module/Mitem.php:228
-msgid "Edit Menu Element"
-msgstr "Bearbeite Menü-Bestandteil"
+#: ../../Zotlabs/Module/Notify.php:65
+#: ../../Zotlabs/Module/Notifications.php:42
+msgid "System Notifications"
+msgstr "System-Benachrichtigungen"
-#: ../../Zotlabs/Module/Mitem.php:238
-msgid "Link text"
-msgstr "Link Text"
+#: ../../Zotlabs/Module/Follow.php:31
+msgid "Channel added."
+msgstr "Kanal hinzugefügt."
-#: ../../Zotlabs/Module/Ratings.php:70
-msgid "No ratings"
-msgstr "Keine Bewertungen"
+#: ../../Zotlabs/Module/Import.php:143
+#, php-format
+msgid "Your service plan only allows %d channels."
+msgstr "Dein Vertrag erlaubt nur %d Kanäle."
-#: ../../Zotlabs/Module/Ratings.php:98
-msgid "Rating: "
-msgstr "Bewertung: "
+#: ../../Zotlabs/Module/Import.php:157
+msgid "No channel. Import failed."
+msgstr "Kein Kanal. Import fehlgeschlagen."
-#: ../../Zotlabs/Module/Ratings.php:99
-msgid "Website: "
-msgstr "Webseite: "
+#: ../../Zotlabs/Module/Import.php:481
+#: ../../addon/diaspora/import_diaspora.php:142
+msgid "Import completed."
+msgstr "Import abgeschlossen."
-#: ../../Zotlabs/Module/Ratings.php:101
-msgid "Description: "
-msgstr "Beschreibung: "
+#: ../../Zotlabs/Module/Import.php:509
+msgid "You must be logged in to use this feature."
+msgstr "Du musst angemeldet sein um diese Funktion zu nutzen."
+
+#: ../../Zotlabs/Module/Import.php:514
+msgid "Import Channel"
+msgstr "Kanal importieren"
+
+#: ../../Zotlabs/Module/Import.php:515
+msgid ""
+"Use this form to import an existing channel from a different server/hub. You"
+" may retrieve the channel identity from the old server/hub via the network "
+"or provide an export file."
+msgstr "Verwende dieses Formular, um einen existierenden Kanal von einem anderen Hub zu importieren. Du kannst den Kanal direkt vom bisherigen Hub über das Netzwerk oder aus einer exportierten Sicherheitskopie importieren."
+
+#: ../../Zotlabs/Module/Import.php:517
+msgid "Or provide the old server/hub details"
+msgstr "Oder gib die Details Deines bisherigen $Projectname-Hubs ein"
+
+#: ../../Zotlabs/Module/Import.php:518
+msgid "Your old identity address (xyz@example.com)"
+msgstr "Bisherige Kanal-Adresse (xyz@example.com)"
+
+#: ../../Zotlabs/Module/Import.php:519
+msgid "Your old login email address"
+msgstr "Deine alte Login-E-Mail-Adresse"
+
+#: ../../Zotlabs/Module/Import.php:520
+msgid "Your old login password"
+msgstr "Dein altes Passwort"
+
+#: ../../Zotlabs/Module/Import.php:521
+msgid ""
+"For either option, please choose whether to make this hub your new primary "
+"address, or whether your old location should continue this role. You will be"
+" able to post from either location, but only one can be marked as the "
+"primary location for files, photos, and media."
+msgstr "Egal, welche Option Du wählst – bitte lege fest, ob dieser Server die neue primäre Adresse dieses Kanals sein soll, oder ob der bisherige $Projectname-Hub diese Rolle weiterhin wahrnimmt. Du kannst von beiden Servern aus posten, aber nur einer kann der primäre Ort Deiner Dateien, Fotos und Medien sein."
+
+#: ../../Zotlabs/Module/Import.php:522
+msgid "Make this hub my primary location"
+msgstr "Dieser $Pojectname-Hub ist mein primärer Hub."
+
+#: ../../Zotlabs/Module/Import.php:523
+msgid "Move this channel (disable all previous locations)"
+msgstr "Verschiebe diesen Kanal (deaktiviere alle vorherigen Adressen/Klone)"
+
+#: ../../Zotlabs/Module/Import.php:524
+msgid "Import a few months of posts if possible (limited by available memory"
+msgstr "Importiere die Beiträge einiger Monate, sofern möglich (beschränkt durch verfügbaren Speicher)"
+
+#: ../../Zotlabs/Module/Import.php:525
+msgid ""
+"This process may take several minutes to complete. Please submit the form "
+"only once and leave this page open until finished."
+msgstr "Dieser Vorgang kann einige Minuten dauern. Bitte sende das Formular nur einmal ab und lasse diese Seite bis zur Fertigstellung offen."
+
+#: ../../Zotlabs/Module/Rmagic.php:35
+msgid "Authentication failed."
+msgstr "Authentifizierung fehlgeschlagen."
+
+#: ../../Zotlabs/Module/Rmagic.php:75 ../../boot.php:1640
+#: ../../include/channel.php:2204
+msgid "Remote Authentication"
+msgstr "Entfernte Authentifizierung"
+
+#: ../../Zotlabs/Module/Rmagic.php:76 ../../include/channel.php:2205
+msgid "Enter your channel address (e.g. channel@example.com)"
+msgstr "Deine Kanal-Adresse (z. B. channel@example.com)"
+
+#: ../../Zotlabs/Module/Rmagic.php:77 ../../include/channel.php:2206
+msgid "Authenticate"
+msgstr "Authentifizieren"
+
+#: ../../Zotlabs/Module/Cal.php:62 ../../Zotlabs/Module/Chanview.php:96
+#: ../../Zotlabs/Module/Page.php:75 ../../Zotlabs/Module/Wall_upload.php:31
+#: ../../Zotlabs/Module/Block.php:41 ../../Zotlabs/Module/Card_edit.php:44
+msgid "Channel not found."
+msgstr "Kanal nicht gefunden."
+
+#: ../../Zotlabs/Module/Cal.php:69
+msgid "Permissions denied."
+msgstr "Berechtigung verweigert."
+
+#: ../../Zotlabs/Module/Cal.php:342 ../../include/text.php:2312
+msgid "Import"
+msgstr "Import"
+
+#: ../../Zotlabs/Module/Api.php:72 ../../Zotlabs/Module/Api.php:93
+msgid "Authorize application connection"
+msgstr "Zugriff für die Anwendung autorisieren"
+
+#: ../../Zotlabs/Module/Api.php:73
+msgid "Return to your app and insert this Security Code:"
+msgstr "Gehen Sie zu Ihrer App zurück und tragen Sie diesen Sicherheitscode ein:"
+
+#: ../../Zotlabs/Module/Api.php:83
+msgid "Please login to continue."
+msgstr "Zum Weitermachen, bitte einloggen."
+
+#: ../../Zotlabs/Module/Api.php:95
+msgid ""
+"Do you want to authorize this application to access your posts and contacts,"
+" and/or create new posts for you?"
+msgstr "Möchtest Du dieser Anwendung erlauben, Deine Nachrichten und Kontakte abzurufen und/oder neue Nachrichten für Dich zu erstellen?"
#: ../../Zotlabs/Module/Attach.php:13
msgid "Item not available."
msgstr "Element nicht verfügbar."
-#: ../../Zotlabs/Module/Mood.php:67 ../../include/conversation.php:260
+#: ../../Zotlabs/Module/Editblock.php:116 ../../Zotlabs/Module/Chat.php:207
+#: ../../Zotlabs/Module/Editwebpage.php:143 ../../Zotlabs/Module/Mail.php:288
+#: ../../Zotlabs/Module/Mail.php:430 ../../Zotlabs/Module/Card_edit.php:101
+#: ../../include/conversation.php:1261
+msgid "Insert web link"
+msgstr "Link einfügen"
+
+#: ../../Zotlabs/Module/Editblock.php:129
+#: ../../Zotlabs/Module/Card_edit.php:117 ../../include/conversation.php:1381
+msgid "Title (optional)"
+msgstr "Titel (optional)"
+
+#: ../../Zotlabs/Module/Editblock.php:138
+msgid "Edit Block"
+msgstr "Block bearbeiten"
+
+#: ../../Zotlabs/Module/Profile.php:93
+msgid "vcard"
+msgstr "VCard"
+
+#: ../../Zotlabs/Module/Apps.php:47 ../../Zotlabs/Lib/Apps.php:223
+msgid "Apps"
+msgstr "Apps"
+
+#: ../../Zotlabs/Module/Apps.php:50
+msgid "Manage apps"
+msgstr "Apps verwalten"
+
+#: ../../Zotlabs/Module/Apps.php:51
+msgid "Create new app"
+msgstr "Neue App erstellen"
+
+#: ../../Zotlabs/Module/Mood.php:67 ../../include/conversation.php:256
#, php-format
msgctxt "mood"
msgid "%1$s is %2$s"
msgstr "%1$s ist %2$s"
-#: ../../Zotlabs/Module/Mood.php:135 ../../Zotlabs/Lib/Apps.php:227
+#: ../../Zotlabs/Module/Mood.php:135 ../../Zotlabs/Lib/Apps.php:247
msgid "Mood"
msgstr "Laune"
@@ -3835,823 +4306,1503 @@ msgstr "Laune"
msgid "Set your current mood and tell your friends"
msgstr "Wähle Deine aktuelle Stimmung und teile sie mit Deinen Freunden"
-#: ../../Zotlabs/Module/Notify.php:57
-#: ../../Zotlabs/Module/Notifications.php:35
-msgid "No more system notifications."
-msgstr "Keine System-Benachrichtigungen mehr."
+#: ../../Zotlabs/Module/Connections.php:54
+#: ../../Zotlabs/Module/Connections.php:156
+#: ../../Zotlabs/Module/Connections.php:245
+msgid "Blocked"
+msgstr "Blockiert"
-#: ../../Zotlabs/Module/Notify.php:61
-#: ../../Zotlabs/Module/Notifications.php:39
-msgid "System Notifications"
-msgstr "System-Benachrichtigungen"
+#: ../../Zotlabs/Module/Connections.php:59
+#: ../../Zotlabs/Module/Connections.php:163
+#: ../../Zotlabs/Module/Connections.php:244
+msgid "Ignored"
+msgstr "Ignoriert"
+
+#: ../../Zotlabs/Module/Connections.php:64
+#: ../../Zotlabs/Module/Connections.php:177
+#: ../../Zotlabs/Module/Connections.php:243
+msgid "Hidden"
+msgstr "Versteckt"
+
+#: ../../Zotlabs/Module/Connections.php:69
+#: ../../Zotlabs/Module/Connections.php:170
+msgid "Archived/Unreachable"
+msgstr "Archiviert/Unerreichbar"
+
+#: ../../Zotlabs/Module/Connections.php:74
+#: ../../Zotlabs/Module/Connections.php:83 ../../Zotlabs/Module/Menu.php:116
+#: ../../include/conversation.php:1697
+msgid "New"
+msgstr "Neu"
+
+#: ../../Zotlabs/Module/Connections.php:88
+#: ../../Zotlabs/Module/Connections.php:102
+#: ../../Zotlabs/Module/Connedit.php:713 ../../Zotlabs/Widget/Affinity.php:30
+msgid "All"
+msgstr "Alle"
+
+#: ../../Zotlabs/Module/Connections.php:133
+#: ../../Zotlabs/Widget/Notifications.php:80
+msgid "New Connections"
+msgstr "Neue Verbindungen"
+
+#: ../../Zotlabs/Module/Connections.php:136
+msgid "Show pending (new) connections"
+msgstr "Ausstehende (neue) Verbindungsanfragen anzeigen"
+
+#: ../../Zotlabs/Module/Connections.php:143
+msgid "Show all connections"
+msgstr "Alle Verbindungen anzeigen"
+
+#: ../../Zotlabs/Module/Connections.php:159
+msgid "Only show blocked connections"
+msgstr "Nur blockierte Verbindungen anzeigen"
+
+#: ../../Zotlabs/Module/Connections.php:166
+msgid "Only show ignored connections"
+msgstr "Nur ignorierte Verbindungen anzeigen"
+
+#: ../../Zotlabs/Module/Connections.php:173
+msgid "Only show archived/unreachable connections"
+msgstr "Nur archivierte/unerreichbare Verbindungen anzeigen"
+
+#: ../../Zotlabs/Module/Connections.php:180
+msgid "Only show hidden connections"
+msgstr "Nur versteckte Verbindungen anzeigen"
+
+#: ../../Zotlabs/Module/Connections.php:241
+msgid "Pending approval"
+msgstr "Wartet auf Genehmigung"
+
+#: ../../Zotlabs/Module/Connections.php:242
+msgid "Archived"
+msgstr "Archiviert"
+
+#: ../../Zotlabs/Module/Connections.php:246
+msgid "Not connected at this location"
+msgstr "An diesem Ort nicht verbunden"
+
+#: ../../Zotlabs/Module/Connections.php:258
+#, php-format
+msgid "%1$s [%2$s]"
+msgstr "%1$s [%2$s]"
+
+#: ../../Zotlabs/Module/Connections.php:259
+msgid "Edit connection"
+msgstr "Verbindung bearbeiten"
+
+#: ../../Zotlabs/Module/Connections.php:261
+msgid "Delete connection"
+msgstr "Verbindung löschen"
+
+#: ../../Zotlabs/Module/Connections.php:270
+msgid "Channel address"
+msgstr "Kanaladresse"
+
+#: ../../Zotlabs/Module/Connections.php:272
+msgid "Network"
+msgstr "Netzwerk"
+
+#: ../../Zotlabs/Module/Connections.php:275
+msgid "Call"
+msgstr "Anruf"
+
+#: ../../Zotlabs/Module/Connections.php:277
+msgid "Status"
+msgstr "Status"
+
+#: ../../Zotlabs/Module/Connections.php:279
+msgid "Connected"
+msgstr "Verbunden"
+
+#: ../../Zotlabs/Module/Connections.php:281
+msgid "Approve connection"
+msgstr "Verbindung genehmigen"
+
+#: ../../Zotlabs/Module/Connections.php:283
+msgid "Ignore connection"
+msgstr "Verbindung ignorieren"
+
+#: ../../Zotlabs/Module/Connections.php:284
+#: ../../Zotlabs/Module/Connedit.php:630
+msgid "Ignore"
+msgstr "Ignorieren"
+
+#: ../../Zotlabs/Module/Connections.php:285
+msgid "Recent activity"
+msgstr "Kürzliche Aktivitäten"
+
+#: ../../Zotlabs/Module/Connections.php:309 ../../Zotlabs/Lib/Apps.php:229
+#: ../../include/text.php:959 ../../include/nav.php:107
+msgid "Connections"
+msgstr "Verbindungen"
+
+#: ../../Zotlabs/Module/Connections.php:314
+msgid "Search your connections"
+msgstr "Verbindungen durchsuchen"
-#: ../../Zotlabs/Module/Photos.php:82
+#: ../../Zotlabs/Module/Connections.php:315
+msgid "Connections search"
+msgstr "Verbindung suchen"
+
+#: ../../Zotlabs/Module/Connections.php:316
+#: ../../Zotlabs/Module/Directory.php:391
+#: ../../Zotlabs/Module/Directory.php:396 ../../include/contact_widgets.php:23
+msgid "Find"
+msgstr "Finde"
+
+#: ../../Zotlabs/Module/Viewsrc.php:43
+msgid "item"
+msgstr "Beitrag"
+
+#: ../../Zotlabs/Module/Viewsrc.php:55
+msgid "Source of Item"
+msgstr "Quelle des Elements"
+
+#: ../../Zotlabs/Module/Bookmarks.php:56
+msgid "Bookmark added"
+msgstr "Lesezeichen hinzugefügt"
+
+#: ../../Zotlabs/Module/Bookmarks.php:79
+msgid "My Bookmarks"
+msgstr "Meine Lesezeichen"
+
+#: ../../Zotlabs/Module/Bookmarks.php:90
+msgid "My Connections Bookmarks"
+msgstr "Lesezeichen meiner Kontakte"
+
+#: ../../Zotlabs/Module/Removeaccount.php:35
+msgid ""
+"Account removals are not allowed within 48 hours of changing the account "
+"password."
+msgstr "Das Löschen von Konten innerhalb 48 Stunden nachdem deren Passwort geändert wurde ist nicht erlaubt."
+
+#: ../../Zotlabs/Module/Removeaccount.php:57
+msgid "Remove This Account"
+msgstr "Dieses Konto löschen"
+
+#: ../../Zotlabs/Module/Removeaccount.php:58
+msgid ""
+"This account and all its channels will be completely removed from the "
+"network. "
+msgstr "Dieses Konto mit all seinen Kanälen wird vollständig aus dem Netzwerk gelöscht."
+
+#: ../../Zotlabs/Module/Removeaccount.php:60
+msgid ""
+"Remove this account, all its channels and all its channel clones from the "
+"network"
+msgstr "Dieses Konto, all seine Kanäle sowie alle Kanal-Klone aus dem Netzwerk löschen"
+
+#: ../../Zotlabs/Module/Removeaccount.php:60
+msgid ""
+"By default only the instances of the channels located on this hub will be "
+"removed from the network"
+msgstr "Standardmäßig werden nur die Kanalklone auf diesem $Projectname-Hub aus dem Netzwerk entfernt"
+
+#: ../../Zotlabs/Module/Photos.php:78
msgid "Page owner information could not be retrieved."
msgstr "Informationen über den Besitzer der Seite konnten nicht gefunden werden."
-#: ../../Zotlabs/Module/Photos.php:97 ../../Zotlabs/Module/Photos.php:734
-#: ../../Zotlabs/Module/Profile_photo.php:115
-#: ../../Zotlabs/Module/Profile_photo.php:219
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:225
-#: ../../include/photo/photo_driver.php:728
-msgid "Profile Photos"
-msgstr "Profilfotos"
-
-#: ../../Zotlabs/Module/Photos.php:103 ../../Zotlabs/Module/Photos.php:129
+#: ../../Zotlabs/Module/Photos.php:94 ../../Zotlabs/Module/Photos.php:120
msgid "Album not found."
msgstr "Album nicht gefunden."
-#: ../../Zotlabs/Module/Photos.php:112
+#: ../../Zotlabs/Module/Photos.php:103
msgid "Delete Album"
msgstr "Album löschen"
-#: ../../Zotlabs/Module/Photos.php:133
-msgid ""
-"Multiple storage folders exist with this album name, but within different "
-"directories. Please remove the desired folder or folders using the Files "
-"manager"
-msgstr "Mehrere Speicherordner mit diesem Albumnamen sind bereits vorhanden, aber in verschiedenen Verzeichnissen. Bitte entfernen Sie den oder die gewünschten Ordner mit dem Dateimanager"
-
-#: ../../Zotlabs/Module/Photos.php:190 ../../Zotlabs/Module/Photos.php:1059
+#: ../../Zotlabs/Module/Photos.php:174 ../../Zotlabs/Module/Photos.php:1030
msgid "Delete Photo"
msgstr "Foto löschen"
-#: ../../Zotlabs/Module/Photos.php:520
+#: ../../Zotlabs/Module/Photos.php:501
msgid "No photos selected"
msgstr "Keine Fotos ausgewählt"
-#: ../../Zotlabs/Module/Photos.php:569
+#: ../../Zotlabs/Module/Photos.php:550
msgid "Access to this item is restricted."
msgstr "Der Zugriff auf dieses Foto ist eingeschränkt."
-#: ../../Zotlabs/Module/Photos.php:608
+#: ../../Zotlabs/Module/Photos.php:593
#, php-format
msgid "%1$.2f MB of %2$.2f MB photo storage used."
msgstr "%1$.2f MB von %2$.2f MB Foto-Speicher belegt."
-#: ../../Zotlabs/Module/Photos.php:611
+#: ../../Zotlabs/Module/Photos.php:596
#, php-format
msgid "%1$.2f MB photo storage used."
msgstr "%1$.2f MB Foto-Speicher belegt."
-#: ../../Zotlabs/Module/Photos.php:647
+#: ../../Zotlabs/Module/Photos.php:638
msgid "Upload Photos"
msgstr "Fotos hochladen"
-#: ../../Zotlabs/Module/Photos.php:651
+#: ../../Zotlabs/Module/Photos.php:642
msgid "Enter an album name"
msgstr "Namen für ein neues Album eingeben"
-#: ../../Zotlabs/Module/Photos.php:652
+#: ../../Zotlabs/Module/Photos.php:643
msgid "or select an existing album (doubleclick)"
msgstr "oder ein bereits vorhandenes auswählen (Doppelklick)"
-#: ../../Zotlabs/Module/Photos.php:653
+#: ../../Zotlabs/Module/Photos.php:644
msgid "Create a status post for this upload"
msgstr "Einen Statusbeitrag für diesen Upload erzeugen"
-#: ../../Zotlabs/Module/Photos.php:654
+#: ../../Zotlabs/Module/Photos.php:645
msgid "Caption (optional):"
msgstr "Beschriftung (optional):"
-#: ../../Zotlabs/Module/Photos.php:655
+#: ../../Zotlabs/Module/Photos.php:646
msgid "Description (optional):"
msgstr "Beschreibung (optional):"
-#: ../../Zotlabs/Module/Photos.php:686
-msgid "Album name could not be decoded"
-msgstr "Albumname konnte nicht dekodiert werden"
-
-#: ../../Zotlabs/Module/Photos.php:734
-msgid "Contact Photos"
-msgstr "Kontakt-Bilder"
-
-#: ../../Zotlabs/Module/Photos.php:757
+#: ../../Zotlabs/Module/Photos.php:732
msgid "Show Newest First"
msgstr "Neueste zuerst anzeigen"
-#: ../../Zotlabs/Module/Photos.php:759
+#: ../../Zotlabs/Module/Photos.php:734
msgid "Show Oldest First"
msgstr "Älteste zuerst anzeigen"
-#: ../../Zotlabs/Module/Photos.php:783 ../../Zotlabs/Module/Photos.php:1337
-#: ../../Zotlabs/Module/Embedphotos.php:139 ../../include/widgets.php:1748
-msgid "View Photo"
-msgstr "Foto ansehen"
-
-#: ../../Zotlabs/Module/Photos.php:814
-#: ../../Zotlabs/Module/Embedphotos.php:155 ../../include/widgets.php:1765
-msgid "Edit Album"
-msgstr "Album bearbeiten"
-
-#: ../../Zotlabs/Module/Photos.php:861
+#: ../../Zotlabs/Module/Photos.php:839
msgid "Permission denied. Access to this item may be restricted."
msgstr "Berechtigung verweigert. Der Zugriff ist wahrscheinlich eingeschränkt worden."
-#: ../../Zotlabs/Module/Photos.php:863
+#: ../../Zotlabs/Module/Photos.php:841
msgid "Photo not available"
msgstr "Foto nicht verfügbar"
-#: ../../Zotlabs/Module/Photos.php:921
+#: ../../Zotlabs/Module/Photos.php:899
msgid "Use as profile photo"
msgstr "Als Profilfoto verwenden"
-#: ../../Zotlabs/Module/Photos.php:922
+#: ../../Zotlabs/Module/Photos.php:900
msgid "Use as cover photo"
msgstr "Als Titelbild verwenden"
-#: ../../Zotlabs/Module/Photos.php:929
+#: ../../Zotlabs/Module/Photos.php:907
msgid "Private Photo"
msgstr "Privates Foto"
-#: ../../Zotlabs/Module/Photos.php:940 ../../Zotlabs/Module/Cal.php:336
-#: ../../Zotlabs/Module/Cal.php:343 ../../Zotlabs/Module/Events.php:680
-#: ../../Zotlabs/Module/Events.php:689
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:846
-msgid "Previous"
-msgstr "Voriges"
-
-#: ../../Zotlabs/Module/Photos.php:944
+#: ../../Zotlabs/Module/Photos.php:922
msgid "View Full Size"
msgstr "In voller Größe anzeigen"
-#: ../../Zotlabs/Module/Photos.php:949 ../../Zotlabs/Module/Setup.php:264
-#: ../../Zotlabs/Module/Cal.php:337 ../../Zotlabs/Module/Cal.php:344
-#: ../../Zotlabs/Module/Events.php:681 ../../Zotlabs/Module/Events.php:690
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:847
-msgid "Next"
-msgstr "Nächste"
-
-#: ../../Zotlabs/Module/Photos.php:1033
+#: ../../Zotlabs/Module/Photos.php:1004
msgid "Edit photo"
msgstr "Foto bearbeiten"
-#: ../../Zotlabs/Module/Photos.php:1035
+#: ../../Zotlabs/Module/Photos.php:1006
msgid "Rotate CW (right)"
msgstr "Drehen im UZS (rechts)"
-#: ../../Zotlabs/Module/Photos.php:1036
+#: ../../Zotlabs/Module/Photos.php:1007
msgid "Rotate CCW (left)"
msgstr "Drehen gegen UZS (links)"
-#: ../../Zotlabs/Module/Photos.php:1039
+#: ../../Zotlabs/Module/Photos.php:1010
msgid "Move photo to album"
msgstr "Foto in Album verschieben"
-#: ../../Zotlabs/Module/Photos.php:1040
+#: ../../Zotlabs/Module/Photos.php:1011
msgid "Enter a new album name"
msgstr "Gib einen Namen für ein neues Album ein"
-#: ../../Zotlabs/Module/Photos.php:1041
+#: ../../Zotlabs/Module/Photos.php:1012
msgid "or select an existing one (doubleclick)"
msgstr "oder wähle ein bereits vorhandenes aus (Doppelklick)"
-#: ../../Zotlabs/Module/Photos.php:1044
+#: ../../Zotlabs/Module/Photos.php:1015
msgid "Caption"
msgstr "Bildunterschrift"
-#: ../../Zotlabs/Module/Photos.php:1046
+#: ../../Zotlabs/Module/Photos.php:1017
msgid "Add a Tag"
msgstr "Schlagwort hinzufügen"
-#: ../../Zotlabs/Module/Photos.php:1054
+#: ../../Zotlabs/Module/Photos.php:1025
msgid "Example: @bob, @Barbara_Jensen, @jim@example.com"
msgstr "Beispiele: @ben, @Karl_Prester, @lieschen@example.com"
-#: ../../Zotlabs/Module/Photos.php:1057
+#: ../../Zotlabs/Module/Photos.php:1028
msgid "Flag as adult in album view"
msgstr "In der Albumansicht als nicht jugendfrei markieren"
-#: ../../Zotlabs/Module/Photos.php:1076 ../../Zotlabs/Lib/ThreadItem.php:268
+#: ../../Zotlabs/Module/Photos.php:1047 ../../Zotlabs/Lib/ThreadItem.php:271
msgid "I like this (toggle)"
msgstr "Mir gefällt das (Umschalter)"
-#: ../../Zotlabs/Module/Photos.php:1077 ../../Zotlabs/Lib/ThreadItem.php:269
+#: ../../Zotlabs/Module/Photos.php:1048 ../../Zotlabs/Lib/ThreadItem.php:272
msgid "I don't like this (toggle)"
msgstr "Mir gefällt das nicht (Umschalter)"
-#: ../../Zotlabs/Module/Photos.php:1078 ../../Zotlabs/Module/Blocks.php:161
-#: ../../Zotlabs/Module/Layouts.php:193 ../../Zotlabs/Module/Webpages.php:241
-#: ../../extend/addon/addon/cdav/include/widgets.php:123
-#: ../../include/conversation.php:1248
-msgid "Share"
-msgstr "Teilen"
-
-#: ../../Zotlabs/Module/Photos.php:1079 ../../Zotlabs/Lib/ThreadItem.php:409
-#: ../../include/conversation.php:757
+#: ../../Zotlabs/Module/Photos.php:1050 ../../Zotlabs/Lib/ThreadItem.php:416
+#: ../../include/conversation.php:768
msgid "Please wait"
msgstr "Bitte warten"
-#: ../../Zotlabs/Module/Photos.php:1095 ../../Zotlabs/Module/Photos.php:1213
-#: ../../Zotlabs/Lib/ThreadItem.php:726
+#: ../../Zotlabs/Module/Photos.php:1066 ../../Zotlabs/Module/Photos.php:1184
+#: ../../Zotlabs/Lib/ThreadItem.php:740
msgid "This is you"
msgstr "Das bist Du"
-#: ../../Zotlabs/Module/Photos.php:1097 ../../Zotlabs/Module/Photos.php:1215
-#: ../../Zotlabs/Lib/ThreadItem.php:728 ../../include/js_strings.php:6
+#: ../../Zotlabs/Module/Photos.php:1068 ../../Zotlabs/Module/Photos.php:1186
+#: ../../Zotlabs/Lib/ThreadItem.php:742 ../../include/js_strings.php:6
msgid "Comment"
msgstr "Kommentar"
-#: ../../Zotlabs/Module/Photos.php:1099 ../../Zotlabs/Module/Webpages.php:247
-#: ../../Zotlabs/Module/Events.php:471 ../../Zotlabs/Lib/ThreadItem.php:738
-#: ../../include/page_widgets.php:43 ../../include/conversation.php:1217
-msgid "Preview"
-msgstr "Vorschau"
-
-#: ../../Zotlabs/Module/Photos.php:1113 ../../include/conversation.php:593
+#: ../../Zotlabs/Module/Photos.php:1084 ../../include/conversation.php:594
msgctxt "title"
msgid "Likes"
msgstr "Gefällt mir"
-#: ../../Zotlabs/Module/Photos.php:1113 ../../include/conversation.php:593
+#: ../../Zotlabs/Module/Photos.php:1084 ../../include/conversation.php:594
msgctxt "title"
msgid "Dislikes"
msgstr "Gefällt mir nicht"
-#: ../../Zotlabs/Module/Photos.php:1114 ../../include/conversation.php:594
+#: ../../Zotlabs/Module/Photos.php:1085 ../../include/conversation.php:595
msgctxt "title"
msgid "Agree"
msgstr "Zustimmungen"
-#: ../../Zotlabs/Module/Photos.php:1114 ../../include/conversation.php:594
+#: ../../Zotlabs/Module/Photos.php:1085 ../../include/conversation.php:595
msgctxt "title"
msgid "Disagree"
msgstr "Ablehnungen"
-#: ../../Zotlabs/Module/Photos.php:1114 ../../include/conversation.php:594
+#: ../../Zotlabs/Module/Photos.php:1085 ../../include/conversation.php:595
msgctxt "title"
msgid "Abstain"
msgstr "Enthaltungen"
-#: ../../Zotlabs/Module/Photos.php:1115 ../../include/conversation.php:595
+#: ../../Zotlabs/Module/Photos.php:1086 ../../include/conversation.php:596
msgctxt "title"
msgid "Attending"
msgstr "Zusagen"
-#: ../../Zotlabs/Module/Photos.php:1115 ../../include/conversation.php:595
+#: ../../Zotlabs/Module/Photos.php:1086 ../../include/conversation.php:596
msgctxt "title"
msgid "Not attending"
msgstr "Absagen"
-#: ../../Zotlabs/Module/Photos.php:1115 ../../include/conversation.php:595
+#: ../../Zotlabs/Module/Photos.php:1086 ../../include/conversation.php:596
msgctxt "title"
msgid "Might attend"
msgstr "Vielleicht"
-#: ../../Zotlabs/Module/Photos.php:1132 ../../Zotlabs/Module/Photos.php:1144
-#: ../../Zotlabs/Lib/ThreadItem.php:186 ../../Zotlabs/Lib/ThreadItem.php:198
-#: ../../include/conversation.php:1783
+#: ../../Zotlabs/Module/Photos.php:1103 ../../Zotlabs/Module/Photos.php:1115
+#: ../../Zotlabs/Lib/ThreadItem.php:191 ../../Zotlabs/Lib/ThreadItem.php:203
msgid "View all"
msgstr "Alles anzeigen"
-#: ../../Zotlabs/Module/Photos.php:1136 ../../Zotlabs/Lib/ThreadItem.php:190
-#: ../../include/channel.php:1190 ../../include/taxonomy.php:403
-#: ../../include/conversation.php:1807
+#: ../../Zotlabs/Module/Photos.php:1107 ../../Zotlabs/Lib/ThreadItem.php:195
+#: ../../include/conversation.php:1950 ../../include/channel.php:1491
+#: ../../include/taxonomy.php:520
msgctxt "noun"
msgid "Like"
msgid_plural "Likes"
msgstr[0] "Gefällt mir"
msgstr[1] "Gefällt mir"
-#: ../../Zotlabs/Module/Photos.php:1141 ../../Zotlabs/Lib/ThreadItem.php:195
-#: ../../include/conversation.php:1810
+#: ../../Zotlabs/Module/Photos.php:1112 ../../Zotlabs/Lib/ThreadItem.php:200
+#: ../../include/conversation.php:1953
msgctxt "noun"
msgid "Dislike"
msgid_plural "Dislikes"
msgstr[0] "Gefällt nicht"
msgstr[1] "Gefällt nicht"
-#: ../../Zotlabs/Module/Photos.php:1241
+#: ../../Zotlabs/Module/Photos.php:1212
msgid "Photo Tools"
msgstr "Fotowerkzeuge"
-#: ../../Zotlabs/Module/Photos.php:1250
+#: ../../Zotlabs/Module/Photos.php:1221
msgid "In This Photo:"
msgstr "Auf diesem Foto:"
-#: ../../Zotlabs/Module/Photos.php:1255
+#: ../../Zotlabs/Module/Photos.php:1226
msgid "Map"
msgstr "Karte"
-#: ../../Zotlabs/Module/Photos.php:1263 ../../Zotlabs/Lib/ThreadItem.php:398
+#: ../../Zotlabs/Module/Photos.php:1234 ../../Zotlabs/Lib/ThreadItem.php:404
msgctxt "noun"
msgid "Likes"
msgstr "Gefällt mir"
-#: ../../Zotlabs/Module/Photos.php:1264 ../../Zotlabs/Lib/ThreadItem.php:399
+#: ../../Zotlabs/Module/Photos.php:1235 ../../Zotlabs/Lib/ThreadItem.php:405
msgctxt "noun"
msgid "Dislikes"
msgstr "Gefällt nicht"
-#: ../../Zotlabs/Module/Photos.php:1269 ../../Zotlabs/Lib/ThreadItem.php:404
-#: ../../include/acl_selectors.php:210
+#: ../../Zotlabs/Module/Photos.php:1240 ../../Zotlabs/Lib/ThreadItem.php:410
+#: ../../include/acl_selectors.php:220
msgid "Close"
msgstr "Schließen"
-#: ../../Zotlabs/Module/Photos.php:1343
-msgid "View Album"
-msgstr "Album ansehen"
-
-#: ../../Zotlabs/Module/Photos.php:1354 ../../Zotlabs/Module/Photos.php:1367
-#: ../../Zotlabs/Module/Photos.php:1368
+#: ../../Zotlabs/Module/Photos.php:1312 ../../Zotlabs/Module/Photos.php:1325
+#: ../../Zotlabs/Module/Photos.php:1326 ../../include/photos.php:601
msgid "Recent Photos"
msgstr "Neueste Fotos"
-#: ../../Zotlabs/Module/Setup.php:176
-msgid "$Projectname Server - Setup"
-msgstr "$Projectname Server-Einrichtung"
+#: ../../Zotlabs/Module/Wiki.php:30
+msgid "Profile Unavailable."
+msgstr "Profil nicht verfügbar."
-#: ../../Zotlabs/Module/Setup.php:180
-msgid "Could not connect to database."
-msgstr "Kann nicht mit der Datenbank verbinden."
+#: ../../Zotlabs/Module/Wiki.php:44 ../../addon/gitwiki/Mod_Gitwiki.php:42
+msgid "Not found"
+msgstr "Nicht gefunden"
-#: ../../Zotlabs/Module/Setup.php:184
-msgid ""
-"Could not connect to specified site URL. Possible SSL certificate or DNS "
-"issue."
-msgstr "Konnte die angegebene Webseiten-URL nicht erreichen. Möglicherweise ein Problem mit dem SSL-Zertifikat oder dem DNS."
+#: ../../Zotlabs/Module/Wiki.php:68 ../../addon/gitwiki/Mod_Gitwiki.php:62
+msgid "Invalid channel"
+msgstr "Ungültiger Kanal"
-#: ../../Zotlabs/Module/Setup.php:191
-msgid "Could not create table."
-msgstr "Konnte Tabelle nicht erstellen."
+#: ../../Zotlabs/Module/Wiki.php:124 ../../addon/gitwiki/Mod_Gitwiki.php:107
+msgid "Error retrieving wiki"
+msgstr "Fehler beim Abrufen des Wiki"
-#: ../../Zotlabs/Module/Setup.php:196
-msgid "Your site database has been installed."
-msgstr "Die Datenbank Deines Hubs wurde installiert."
+#: ../../Zotlabs/Module/Wiki.php:131 ../../addon/gitwiki/Mod_Gitwiki.php:114
+msgid "Error creating zip file export folder"
+msgstr "Fehler bei der Erzeugung des Zip-Datei Export-Verzeichnisses "
-#: ../../Zotlabs/Module/Setup.php:200
-msgid ""
-"You may need to import the file \"install/schema_xxx.sql\" manually using a "
-"database client."
-msgstr "Möglicherweise musst Du die Datei install/schema_xxx.sql manuell mit Hilfe eines Datenkbank-Clients importieren."
+#: ../../Zotlabs/Module/Wiki.php:182 ../../addon/gitwiki/Mod_Gitwiki.php:132
+msgid "Error downloading wiki: "
+msgstr "Fehler beim Herunterladen des Wiki:"
-#: ../../Zotlabs/Module/Setup.php:201 ../../Zotlabs/Module/Setup.php:263
-#: ../../Zotlabs/Module/Setup.php:745
-msgid "Please see the file \"install/INSTALL.txt\"."
-msgstr "Lies die Datei \"install/INSTALL.txt\"."
+#: ../../Zotlabs/Module/Wiki.php:197 ../../addon/gitwiki/Mod_Gitwiki.php:146
+#: ../../include/conversation.php:1897 ../../include/nav.php:504
+msgid "Wikis"
+msgstr "Wikis"
-#: ../../Zotlabs/Module/Setup.php:260
-msgid "System check"
-msgstr "Systemprüfung"
+#: ../../Zotlabs/Module/Wiki.php:203 ../../addon/gitwiki/Mod_Gitwiki.php:152
+msgid "Download"
+msgstr "Herunterladen"
-#: ../../Zotlabs/Module/Setup.php:265
-msgid "Check again"
-msgstr "Nochmal prüfen"
+#: ../../Zotlabs/Module/Wiki.php:205 ../../Zotlabs/Module/Chat.php:256
+#: ../../Zotlabs/Module/Profiles.php:834 ../../Zotlabs/Module/Manage.php:145
+#: ../../addon/gitwiki/Mod_Gitwiki.php:154
+msgid "Create New"
+msgstr "Neu anlegen"
-#: ../../Zotlabs/Module/Setup.php:287
-msgid "Database connection"
-msgstr "Datenbankverbindung"
+#: ../../Zotlabs/Module/Wiki.php:207 ../../addon/gitwiki/Mod_Gitwiki.php:156
+msgid "Wiki name"
+msgstr "Name des Wiki"
-#: ../../Zotlabs/Module/Setup.php:288
-msgid ""
-"In order to install $Projectname we need to know how to connect to your "
-"database."
-msgstr "Um $Projectname zu installieren, müssen wir wissen, wie wir eine Verbindung zu Deiner Datenbank aufbauen können."
+#: ../../Zotlabs/Module/Wiki.php:208 ../../addon/gitwiki/Mod_Gitwiki.php:157
+msgid "Content type"
+msgstr "Inhaltstyp"
-#: ../../Zotlabs/Module/Setup.php:289
-msgid ""
-"Please contact your hosting provider or site administrator if you have "
-"questions about these settings."
-msgstr "Bitte kontaktiere Deinen Hosting-Provider oder Administrator, falls Du Fragen zu diesen Einstellungen hast."
+#: ../../Zotlabs/Module/Wiki.php:208 ../../Zotlabs/Module/Wiki.php:336
+#: ../../Zotlabs/Widget/Wiki_pages.php:57 ../../include/text.php:1802
+msgid "Markdown"
+msgstr "Markdown"
-#: ../../Zotlabs/Module/Setup.php:290
-msgid ""
-"The database you specify below should already exist. If it does not, please "
-"create it before continuing."
-msgstr "Die Datenbank, die Du weiter unten angibst, sollte bereits existieren. Sollte das noch nicht der Fall sein, erzeuge sie bitte bevor Du fortfährst."
+#: ../../Zotlabs/Module/Wiki.php:208 ../../Zotlabs/Module/Wiki.php:336
+#: ../../Zotlabs/Widget/Wiki_pages.php:57 ../../include/text.php:1800
+msgid "BBcode"
+msgstr "BBcode"
-#: ../../Zotlabs/Module/Setup.php:294
-msgid "Database Server Name"
-msgstr "Datenbankservername"
+#: ../../Zotlabs/Module/Wiki.php:208 ../../Zotlabs/Widget/Wiki_pages.php:57
+#: ../../include/text.php:1803
+msgid "Text"
+msgstr "Text"
-#: ../../Zotlabs/Module/Setup.php:294
-msgid "Default is 127.0.0.1"
-msgstr "Standard ist 127.0.0.1"
+#: ../../Zotlabs/Module/Wiki.php:210 ../../Zotlabs/Storage/Browser.php:235
+#: ../../addon/gitwiki/Mod_Gitwiki.php:159
+msgid "Type"
+msgstr "Typ"
-#: ../../Zotlabs/Module/Setup.php:295
-msgid "Database Port"
-msgstr "Datenbankport"
+#: ../../Zotlabs/Module/Wiki.php:211
+msgid "Any&nbsp;type"
+msgstr "Alle&nbsp;Arten"
-#: ../../Zotlabs/Module/Setup.php:295
-msgid "Communication port number - use 0 for default"
-msgstr "Port-Nummer für die Kommunikation – verwende 0 für die Standardeinstellung"
+#: ../../Zotlabs/Module/Wiki.php:218
+msgid "Lock content type"
+msgstr "Inhaltstyp sperren"
-#: ../../Zotlabs/Module/Setup.php:296
-msgid "Database Login Name"
-msgstr "Datenbank-Benutzername"
+#: ../../Zotlabs/Module/Wiki.php:219 ../../addon/gitwiki/Mod_Gitwiki.php:166
+msgid "Create a status post for this wiki"
+msgstr "Erzeuge einen Statusbeitrag für dieses Wiki"
-#: ../../Zotlabs/Module/Setup.php:297
-msgid "Database Login Password"
-msgstr "Datenbank-Passwort"
+#: ../../Zotlabs/Module/Wiki.php:220
+msgid "Edit Wiki Name"
+msgstr "Wiki-Namen bearbeiten"
-#: ../../Zotlabs/Module/Setup.php:298
-msgid "Database Name"
-msgstr "Datenbankname"
+#: ../../Zotlabs/Module/Wiki.php:262 ../../addon/gitwiki/Mod_Gitwiki.php:185
+msgid "Wiki not found"
+msgstr "Wiki nicht gefunden"
-#: ../../Zotlabs/Module/Setup.php:299
-msgid "Database Type"
-msgstr "Datenbanktyp"
+#: ../../Zotlabs/Module/Wiki.php:286 ../../addon/gitwiki/Mod_Gitwiki.php:210
+msgid "Rename page"
+msgstr "Seite umbenennen"
-#: ../../Zotlabs/Module/Setup.php:301 ../../Zotlabs/Module/Setup.php:347
-msgid "Site administrator email address"
-msgstr "E-Mail Adresse des Seiten-Administrators"
+#: ../../Zotlabs/Module/Wiki.php:296 ../../addon/gitwiki/Mod_Gitwiki.php:214
+msgid "Error retrieving page content"
+msgstr "Fehler beim Abrufen des Seiteninhalts"
-#: ../../Zotlabs/Module/Setup.php:301 ../../Zotlabs/Module/Setup.php:347
-msgid ""
-"Your account email address must match this in order to use the web admin "
-"panel."
-msgstr "Die E-Mail-Adresse Deines Accounts muss dieser Adresse entsprechen, damit Du Zugriff zur Administrations-Seite erhältst."
+#: ../../Zotlabs/Module/Wiki.php:302 ../../Zotlabs/Module/Wiki.php:304
+msgid "New page"
+msgstr "Neue Seite"
-#: ../../Zotlabs/Module/Setup.php:302 ../../Zotlabs/Module/Setup.php:349
-msgid "Website URL"
-msgstr "Webseiten-URL"
+#: ../../Zotlabs/Module/Wiki.php:331 ../../addon/gitwiki/Mod_Gitwiki.php:242
+msgid "Revision Comparison"
+msgstr "Revisionsvergleich"
-#: ../../Zotlabs/Module/Setup.php:302 ../../Zotlabs/Module/Setup.php:349
-msgid "Please use SSL (https) URL if available."
-msgstr "Nutze wenn möglich eine SSL-URL (https)."
+#: ../../Zotlabs/Module/Wiki.php:332 ../../addon/gitwiki/Mod_Gitwiki.php:243
+msgid "Revert"
+msgstr "Rückgängig machen"
-#: ../../Zotlabs/Module/Setup.php:303 ../../Zotlabs/Module/Setup.php:353
-msgid "Please select a default timezone for your website"
-msgstr "Standard-Zeitzone für Deinen Server"
+#: ../../Zotlabs/Module/Wiki.php:339
+msgid "Short description of your changes (optional)"
+msgstr "Kurze Beschreibung Ihrer Änderungen (optional)"
-#: ../../Zotlabs/Module/Setup.php:336
-msgid "Site settings"
-msgstr "Seiteneinstellungen"
+#: ../../Zotlabs/Module/Wiki.php:346 ../../addon/gitwiki/Mod_Gitwiki.php:252
+msgid "Source"
+msgstr "Quelle"
-#: ../../Zotlabs/Module/Setup.php:392
-msgid "PHP version 5.5 or greater is required."
-msgstr "PHP-Version 5.5 oder höher ist erforderlich."
+#: ../../Zotlabs/Module/Wiki.php:356 ../../addon/gitwiki/Mod_Gitwiki.php:260
+msgid "New page name"
+msgstr "Neuer Seitenname"
-#: ../../Zotlabs/Module/Setup.php:393
-msgid "PHP version"
-msgstr "PHP-Version"
+#: ../../Zotlabs/Module/Wiki.php:361 ../../addon/gitwiki/Mod_Gitwiki.php:265
+#: ../../include/conversation.php:1265
+msgid "Embed image from photo albums"
+msgstr "Bild aus Fotoalben einbetten"
-#: ../../Zotlabs/Module/Setup.php:409
-msgid "Could not find a command line version of PHP in the web server PATH."
-msgstr "Konnte die Kommandozeilen-Version von PHP nicht im PATH des Web-Servers finden."
+#: ../../Zotlabs/Module/Wiki.php:362 ../../addon/gitwiki/Mod_Gitwiki.php:266
+#: ../../include/conversation.php:1368
+msgid "Embed an image from your albums"
+msgstr "Betten Sie ein Bild aus Ihren Alben ein"
-#: ../../Zotlabs/Module/Setup.php:410
-msgid ""
-"If you don't have a command line version of PHP installed on server, you "
-"will not be able to run background polling via cron."
-msgstr "Ohne Kommandozeilen-Version von PHP auf dem Server wirst Du nicht in der Lage sein, Hintergrundprozesse via cron auszuführen."
+#: ../../Zotlabs/Module/Wiki.php:364 ../../addon/gitwiki/Mod_Gitwiki.php:268
+#: ../../include/conversation.php:1370 ../../include/conversation.php:1417
+msgid "OK"
+msgstr "Ok"
-#: ../../Zotlabs/Module/Setup.php:414
-msgid "PHP executable path"
-msgstr "PHP-Pfad zu ausführbarer Datei"
+#: ../../Zotlabs/Module/Wiki.php:365 ../../addon/gitwiki/Mod_Gitwiki.php:269
+#: ../../include/conversation.php:1301
+msgid "Choose images to embed"
+msgstr "Wählen Sie Bilder zum Einbetten aus"
-#: ../../Zotlabs/Module/Setup.php:414
-msgid ""
-"Enter full path to php executable. You can leave this blank to continue the "
-"installation."
-msgstr "Gib den vollen Pfad zum PHP-Interpreter an. Du kannst dieses Feld frei lassen und mit der Installation fortfahren."
+#: ../../Zotlabs/Module/Wiki.php:366 ../../addon/gitwiki/Mod_Gitwiki.php:270
+#: ../../include/conversation.php:1302
+msgid "Choose an album"
+msgstr "Wählen Sie ein Album aus"
-#: ../../Zotlabs/Module/Setup.php:419
-msgid "Command line PHP"
-msgstr "PHP-Befehlszeile"
+#: ../../Zotlabs/Module/Wiki.php:367 ../../addon/gitwiki/Mod_Gitwiki.php:271
+msgid "Choose a different album"
+msgstr "Wählen Sie ein anderes Album aus"
-#: ../../Zotlabs/Module/Setup.php:429
-msgid ""
-"Unable to check command line PHP, as shell_exec() is disabled. This is "
-"required."
-msgstr "Prüfung auf Kommandozeilen-PHP fehlgeschlagen, da shell_exec() deaktiviert ist. Dies wird aber benötigt."
+#: ../../Zotlabs/Module/Wiki.php:368 ../../addon/gitwiki/Mod_Gitwiki.php:272
+#: ../../include/conversation.php:1304
+msgid "Error getting album list"
+msgstr "Fehler beim Holen der Albenliste"
+
+#: ../../Zotlabs/Module/Wiki.php:369 ../../addon/gitwiki/Mod_Gitwiki.php:273
+#: ../../include/conversation.php:1305
+msgid "Error getting photo link"
+msgstr "Fehler beim Holen des Fotolinks"
+
+#: ../../Zotlabs/Module/Wiki.php:370 ../../addon/gitwiki/Mod_Gitwiki.php:274
+#: ../../include/conversation.php:1306
+msgid "Error getting album"
+msgstr "Fehler beim Holen des Albums"
+
+#: ../../Zotlabs/Module/Wiki.php:442 ../../addon/gitwiki/Mod_Gitwiki.php:337
+msgid "Error creating wiki. Invalid name."
+msgstr "Fehler beim Erstellen des Wiki. Ungültiger Name."
+
+#: ../../Zotlabs/Module/Wiki.php:449
+msgid "A wiki with this name already exists."
+msgstr "Es existiert bereits ein Wiki mit diesem Namen."
+
+#: ../../Zotlabs/Module/Wiki.php:462 ../../addon/gitwiki/Mod_Gitwiki.php:348
+msgid "Wiki created, but error creating Home page."
+msgstr "Das Wiki wurde erzeugt, aber es gab einen Fehler bei der Erstellung der Startseite"
+
+#: ../../Zotlabs/Module/Wiki.php:469 ../../addon/gitwiki/Mod_Gitwiki.php:353
+msgid "Error creating wiki"
+msgstr "Fehler beim Erstellen des Wiki"
+
+#: ../../Zotlabs/Module/Wiki.php:492
+msgid "Error updating wiki. Invalid name."
+msgstr "Fehler beim Aktualisieren des Wikis. Ungültiger Name."
+
+#: ../../Zotlabs/Module/Wiki.php:512
+msgid "Error updating wiki"
+msgstr "Fehler beim Aktualisieren des Wikis"
+
+#: ../../Zotlabs/Module/Wiki.php:527
+msgid "Wiki delete permission denied."
+msgstr "Wiki-Löschberechtigung verweigert."
+
+#: ../../Zotlabs/Module/Wiki.php:537
+msgid "Error deleting wiki"
+msgstr "Fehler beim Löschen des Wiki"
+
+#: ../../Zotlabs/Module/Wiki.php:565 ../../addon/gitwiki/Mod_Gitwiki.php:400
+msgid "New page created"
+msgstr "Neue Seite erstellt"
+
+#: ../../Zotlabs/Module/Wiki.php:686
+msgid "Cannot delete Home"
+msgstr "Kann die Startseite nicht löschen"
+
+#: ../../Zotlabs/Module/Wiki.php:750
+msgid "Current Revision"
+msgstr "Aktuelle Revision"
+
+#: ../../Zotlabs/Module/Wiki.php:750
+msgid "Selected Revision"
+msgstr "Ausgewählte Revision"
+
+#: ../../Zotlabs/Module/Wiki.php:800
+msgid "You must be authenticated."
+msgstr "Sie müssen authenzifiziert sein."
+
+#: ../../Zotlabs/Module/Chanview.php:139
+msgid "toggle full screen mode"
+msgstr "auf Vollbildmodus umschalten"
+
+#: ../../Zotlabs/Module/Pdledit.php:21
+msgid "Layout updated."
+msgstr "Layout aktualisiert."
+
+#: ../../Zotlabs/Module/Pdledit.php:34 ../../Zotlabs/Module/Chat.php:219
+msgid "Feature disabled."
+msgstr "Funktion deaktiviert."
+
+#: ../../Zotlabs/Module/Pdledit.php:47 ../../Zotlabs/Module/Pdledit.php:88
+msgid "Edit System Page Description"
+msgstr "Systemseitenbeschreibung bearbeiten"
+
+#: ../../Zotlabs/Module/Pdledit.php:68
+msgid "(modified)"
+msgstr "(geändert)"
+
+#: ../../Zotlabs/Module/Pdledit.php:68 ../../Zotlabs/Module/Lostpass.php:133
+msgid "Reset"
+msgstr "Zurücksetzen"
-#: ../../Zotlabs/Module/Setup.php:432
+#: ../../Zotlabs/Module/Pdledit.php:83
+msgid "Layout not found."
+msgstr "Layout nicht gefunden."
+
+#: ../../Zotlabs/Module/Pdledit.php:89
+msgid "Module Name:"
+msgstr "Modulname:"
+
+#: ../../Zotlabs/Module/Pdledit.php:90
+msgid "Layout Help"
+msgstr "Layout-Hilfe"
+
+#: ../../Zotlabs/Module/Pdledit.php:91
+msgid "Edit another layout"
+msgstr "Ein weiteres Layout bearbeiten"
+
+#: ../../Zotlabs/Module/Poke.php:182 ../../Zotlabs/Lib/Apps.php:248
+#: ../../include/conversation.php:1075
+msgid "Poke"
+msgstr "Anstupsen"
+
+#: ../../Zotlabs/Module/Poke.php:183
+msgid "Poke somebody"
+msgstr "Jemanden anstupsen"
+
+#: ../../Zotlabs/Module/Poke.php:186
+msgid "Poke/Prod"
+msgstr "Anstupsen/Knuffen"
+
+#: ../../Zotlabs/Module/Poke.php:187
+msgid "Poke, prod or do other things to somebody"
+msgstr "Jemanden anstupsen, knuffen oder sonstiges"
+
+#: ../../Zotlabs/Module/Poke.php:194
+msgid "Recipient"
+msgstr "Empfänger"
+
+#: ../../Zotlabs/Module/Poke.php:195
+msgid "Choose what you wish to do to recipient"
+msgstr "Wähle, was Du mit dem/r Empfänger/in tun willst"
+
+#: ../../Zotlabs/Module/Poke.php:198 ../../Zotlabs/Module/Poke.php:199
+msgid "Make this post private"
+msgstr "Diesen Beitrag privat machen"
+
+#: ../../Zotlabs/Module/Profile_photo.php:61
+#: ../../Zotlabs/Module/Cover_photo.php:56
+msgid "Image uploaded but image cropping failed."
+msgstr "Bild hochgeladen, aber das Zurechtschneiden schlug fehl."
+
+#: ../../Zotlabs/Module/Profile_photo.php:115
+#: ../../Zotlabs/Module/Profile_photo.php:234
+#: ../../include/photo/photo_driver.php:710
+msgid "Profile Photos"
+msgstr "Profilfotos"
+
+#: ../../Zotlabs/Module/Profile_photo.php:137
+#: ../../Zotlabs/Module/Cover_photo.php:159
+msgid "Image resize failed."
+msgstr "Bild-Anpassung fehlgeschlagen."
+
+#: ../../Zotlabs/Module/Profile_photo.php:204
+#: ../../addon/openclipatar/openclipatar.php:298
msgid ""
-"The command line version of PHP on your system does not have "
-"\"register_argc_argv\" enabled."
-msgstr "Bei der Kommandozeilen-Version von PHP auf Deinem System ist \"register_argc_argv\" nicht aktiviert."
+"Shift-reload the page or clear browser cache if the new photo does not "
+"display immediately."
+msgstr "Leere den Browser Cache oder nutze Umschalten-Neu Laden, falls das neue Foto nicht sofort angezeigt wird."
-#: ../../Zotlabs/Module/Setup.php:433
-msgid "This is required for message delivery to work."
-msgstr "Das wird benötigt, damit die Auslieferung von Nachrichten funktioniert."
+#: ../../Zotlabs/Module/Profile_photo.php:211
+#: ../../Zotlabs/Module/Cover_photo.php:173 ../../include/photos.php:156
+msgid "Unable to process image"
+msgstr "Kann Bild nicht verarbeiten"
-#: ../../Zotlabs/Module/Setup.php:436
-msgid "PHP register_argc_argv"
-msgstr "PHP register_argc_argv"
+#: ../../Zotlabs/Module/Profile_photo.php:246
+#: ../../Zotlabs/Module/Cover_photo.php:197
+msgid "Image upload failed."
+msgstr "Hochladen des Bilds fehlgeschlagen."
-#: ../../Zotlabs/Module/Setup.php:454
+#: ../../Zotlabs/Module/Profile_photo.php:265
+#: ../../Zotlabs/Module/Cover_photo.php:214
+msgid "Unable to process image."
+msgstr "Kann Bild nicht verarbeiten."
+
+#: ../../Zotlabs/Module/Profile_photo.php:326
+#: ../../Zotlabs/Module/Profile_photo.php:373
+#: ../../Zotlabs/Module/Cover_photo.php:307
+#: ../../Zotlabs/Module/Cover_photo.php:322
+msgid "Photo not available."
+msgstr "Foto nicht verfügbar."
+
+#: ../../Zotlabs/Module/Profile_photo.php:428
+#: ../../Zotlabs/Module/Cover_photo.php:358
+msgid "Upload File:"
+msgstr "Datei hochladen:"
+
+#: ../../Zotlabs/Module/Profile_photo.php:429
+#: ../../Zotlabs/Module/Cover_photo.php:359
+msgid "Select a profile:"
+msgstr "Wähle ein Profil:"
+
+#: ../../Zotlabs/Module/Profile_photo.php:430
+msgid "Use Photo for Profile"
+msgstr "Foto für Profil verwenden"
+
+#: ../../Zotlabs/Module/Profile_photo.php:430
+msgid "Upload Profile Photo"
+msgstr "Lade neues Profilfoto hoch"
+
+#: ../../Zotlabs/Module/Profile_photo.php:431
+#: ../../addon/openclipatar/openclipatar.php:182
+#: ../../addon/openclipatar/openclipatar.php:194
+msgid "Use"
+msgstr "Verwenden"
+
+#: ../../Zotlabs/Module/Profile_photo.php:437
+#: ../../Zotlabs/Module/Cover_photo.php:365
+msgid "skip this step"
+msgstr "diesen Schritt überspringen"
+
+#: ../../Zotlabs/Module/Profile_photo.php:437
+#: ../../Zotlabs/Module/Cover_photo.php:365
+msgid "select a photo from your photo albums"
+msgstr "ein Foto aus meinen Fotoalben"
+
+#: ../../Zotlabs/Module/Profile_photo.php:456
+#: ../../Zotlabs/Module/Cover_photo.php:381
+msgid "Crop Image"
+msgstr "Bild zuschneiden"
+
+#: ../../Zotlabs/Module/Profile_photo.php:457
+#: ../../Zotlabs/Module/Cover_photo.php:382
+msgid "Please adjust the image cropping for optimum viewing."
+msgstr "Bitte schneide das Bild für eine optimale Anzeige passend zu."
+
+#: ../../Zotlabs/Module/Profile_photo.php:459
+#: ../../Zotlabs/Module/Cover_photo.php:384
+msgid "Done Editing"
+msgstr "Bearbeitung fertigstellen"
+
+#: ../../Zotlabs/Module/Chatsvc.php:131
+msgid "Away"
+msgstr "Abwesend"
+
+#: ../../Zotlabs/Module/Chatsvc.php:136
+msgid "Online"
+msgstr "Online"
+
+#: ../../Zotlabs/Module/Item.php:185
+msgid "Unable to locate original post."
+msgstr "Originalbeitrag nicht gefunden."
+
+#: ../../Zotlabs/Module/Item.php:470
+msgid "Empty post discarded."
+msgstr "Leeren Beitrag verworfen."
+
+#: ../../Zotlabs/Module/Item.php:870
+msgid "Duplicate post suppressed."
+msgstr "Doppelter Beitrag unterdrückt."
+
+#: ../../Zotlabs/Module/Item.php:1015
+msgid "System error. Post not saved."
+msgstr "Systemfehler. Beitrag nicht gespeichert."
+
+#: ../../Zotlabs/Module/Item.php:1051
+msgid "Your comment is awaiting approval."
+msgstr "Dein Kommentar muss noch bestätigt werden."
+
+#: ../../Zotlabs/Module/Item.php:1156
+msgid "Unable to obtain post information from database."
+msgstr "Beitragsinformationen können nicht aus der Datenbank abgerufen werden."
+
+#: ../../Zotlabs/Module/Item.php:1163
#, php-format
-msgid ""
-"Your max allowed total upload size is set to %s. Maximum size of one file to"
-" upload is set to %s. You are allowed to upload up to %d files at once."
-msgstr "Die Maximalgröße für Uploads insgesamt liegt bei %s. Die Maximalgröße für eine Datei liegt bei %s. Es können maximal %d Dateien gleichzeitig hochgeladen werden."
+msgid "You have reached your limit of %1$.0f top level posts."
+msgstr "Du hast die maximale Anzahl von %1$.0f Beiträgen erreicht."
-#: ../../Zotlabs/Module/Setup.php:459
-msgid "You can adjust these settings in the server php.ini file."
-msgstr "Du kannst diese Einstellungen in der php.ini - Datei des Servers anpassen."
+#: ../../Zotlabs/Module/Item.php:1170
+#, php-format
+msgid "You have reached your limit of %1$.0f webpages."
+msgstr "Du hast die maximale Anzahl von %1$.0f Webseiten erreicht."
-#: ../../Zotlabs/Module/Setup.php:461
-msgid "PHP upload limits"
-msgstr "PHP-Hochladebeschränkungen"
+#: ../../Zotlabs/Module/Ping.php:318
+msgid "sent you a private message"
+msgstr "hat Dir eine private Nachricht geschickt"
-#: ../../Zotlabs/Module/Setup.php:484
-msgid ""
-"Error: the \"openssl_pkey_new\" function on this system is not able to "
-"generate encryption keys"
-msgstr "Fehler: Die „openssl_pkey_new“-Funktion auf diesem System ist nicht in der Lage, Schlüssel für die Verschlüsselung zu erzeugen."
+#: ../../Zotlabs/Module/Ping.php:369
+msgid "added your channel"
+msgstr "hat deinen Kanal hinzugefügt"
+
+#: ../../Zotlabs/Module/Ping.php:393
+msgid "requires approval"
+msgstr "Zustimmung erforderlich"
+
+#: ../../Zotlabs/Module/Ping.php:403
+msgid "g A l F d"
+msgstr "l, d. F, G:i \\U\\h\\r"
+
+#: ../../Zotlabs/Module/Ping.php:421
+msgid "[today]"
+msgstr "[Heute]"
+
+#: ../../Zotlabs/Module/Ping.php:430
+msgid "posted an event"
+msgstr "hat einen Termin veröffentlicht"
+
+#: ../../Zotlabs/Module/Ping.php:463
+msgid "shared a file with you"
+msgstr "hat eine Datei mit Dir geteilt"
-#: ../../Zotlabs/Module/Setup.php:485
+#: ../../Zotlabs/Module/Page.php:39 ../../Zotlabs/Module/Block.php:29
+msgid "Invalid item."
+msgstr "Ungültiges Element."
+
+#: ../../Zotlabs/Module/Page.php:128 ../../Zotlabs/Module/Block.php:77
+#: ../../Zotlabs/Module/Display.php:120
+#: ../../Zotlabs/Lib/NativeWikiPage.php:515 ../../Zotlabs/Web/Router.php:158
+#: ../../include/help.php:81
+msgid "Page not found."
+msgstr "Seite nicht gefunden."
+
+#: ../../Zotlabs/Module/Page.php:165
msgid ""
-"If running under Windows, please see "
-"\"http://www.php.net/manual/en/openssl.installation.php\"."
-msgstr "Wenn Du Windows verwendest, findest Du unter http://www.php.net/manual/en/openssl.installation.php eine Installationsanleitung."
+"Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod "
+"tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam,"
+" quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo "
+"consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse "
+"cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat "
+"non proident, sunt in culpa qui officia deserunt mollit anim id est laborum."
+msgstr "Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum."
-#: ../../Zotlabs/Module/Setup.php:488
-msgid "Generate encryption keys"
-msgstr "Verschlüsselungsschlüssel erzeugen"
+#: ../../Zotlabs/Module/Connedit.php:79
+msgid "Could not access contact record."
+msgstr "Konnte nicht auf den Kontakteintrag zugreifen."
-#: ../../Zotlabs/Module/Setup.php:500
-msgid "libCurl PHP module"
-msgstr "libCurl-PHP-Modul"
+#: ../../Zotlabs/Module/Connedit.php:109
+msgid "Could not locate selected profile."
+msgstr "Gewähltes Profil nicht gefunden."
-#: ../../Zotlabs/Module/Setup.php:501
-msgid "GD graphics PHP module"
-msgstr "GD-Grafik-PHP-Modul"
+#: ../../Zotlabs/Module/Connedit.php:246
+msgid "Connection updated."
+msgstr "Verbindung aktualisiert."
-#: ../../Zotlabs/Module/Setup.php:502
-msgid "OpenSSL PHP module"
-msgstr "OpenSSL-PHP-Modul"
+#: ../../Zotlabs/Module/Connedit.php:248
+msgid "Failed to update connection record."
+msgstr "Konnte den Verbindungseintrag nicht aktualisieren."
-#: ../../Zotlabs/Module/Setup.php:503
-msgid "PDO database PHP module"
-msgstr "PDO-Datenbank-PHP-Modul"
+#: ../../Zotlabs/Module/Connedit.php:302
+msgid "is now connected to"
+msgstr "ist jetzt verbunden mit"
-#: ../../Zotlabs/Module/Setup.php:504
-msgid "mb_string PHP module"
-msgstr "mb_string-PHP-Modul"
+#: ../../Zotlabs/Module/Connedit.php:427
+msgid "Could not access address book record."
+msgstr "Konnte nicht auf den Adressbuch-Eintrag zugreifen."
-#: ../../Zotlabs/Module/Setup.php:505
-msgid "xml PHP module"
-msgstr "xml-PHP-Modul"
+#: ../../Zotlabs/Module/Connedit.php:475
+msgid "Refresh failed - channel is currently unavailable."
+msgstr "Aktualisierung fehlgeschlagen – der Kanal ist im Moment nicht erreichbar."
-#: ../../Zotlabs/Module/Setup.php:509 ../../Zotlabs/Module/Setup.php:511
-msgid "Apache mod_rewrite module"
-msgstr "Apache-mod_rewrite-Modul"
+#: ../../Zotlabs/Module/Connedit.php:490 ../../Zotlabs/Module/Connedit.php:499
+#: ../../Zotlabs/Module/Connedit.php:508 ../../Zotlabs/Module/Connedit.php:517
+#: ../../Zotlabs/Module/Connedit.php:530
+msgid "Unable to set address book parameters."
+msgstr "Konnte die Adressbuch-Parameter nicht setzen."
-#: ../../Zotlabs/Module/Setup.php:509
-msgid ""
-"Error: Apache webserver mod-rewrite module is required but not installed."
-msgstr "Fehler: Das Apache-Modul mod-rewrite wird benötigt, ist aber nicht installiert."
+#: ../../Zotlabs/Module/Connedit.php:554
+msgid "Connection has been removed."
+msgstr "Verbindung wurde gelöscht."
-#: ../../Zotlabs/Module/Setup.php:515 ../../Zotlabs/Module/Setup.php:518
-msgid "exec"
-msgstr "exec"
+#: ../../Zotlabs/Module/Connedit.php:594 ../../Zotlabs/Lib/Apps.php:241
+#: ../../addon/openclipatar/openclipatar.php:57
+#: ../../include/conversation.php:1015 ../../include/nav.php:141
+msgid "View Profile"
+msgstr "Profil ansehen"
-#: ../../Zotlabs/Module/Setup.php:515
-msgid ""
-"Error: exec is required but is either not installed or has been disabled in "
-"php.ini"
-msgstr "Fehler: exec ist erforderlich, aber entweder nicht installiert oder wurde in der php.ini deaktiviert"
+#: ../../Zotlabs/Module/Connedit.php:597
+#, php-format
+msgid "View %s's profile"
+msgstr "%ss Profil ansehen"
-#: ../../Zotlabs/Module/Setup.php:521 ../../Zotlabs/Module/Setup.php:524
-msgid "shell_exec"
-msgstr "shell_exec"
+#: ../../Zotlabs/Module/Connedit.php:601
+msgid "Refresh Permissions"
+msgstr "Zugriffsrechte neu laden"
-#: ../../Zotlabs/Module/Setup.php:521
-msgid ""
-"Error: shell_exec is required but is either not installed or has been "
-"disabled in php.ini"
-msgstr "Fehler: shell_exec ist erforderlich, aber entweder nicht installiert oder wurde in der php.ini deaktiviert"
+#: ../../Zotlabs/Module/Connedit.php:604
+msgid "Fetch updated permissions"
+msgstr "Aktualisierte Zugriffsrechte abrufen"
-#: ../../Zotlabs/Module/Setup.php:529
-msgid "Error: libCURL PHP module required but not installed."
-msgstr "Fehler: Das PHP-Modul libCURL wird benötigt, ist aber nicht installiert."
+#: ../../Zotlabs/Module/Connedit.php:608
+msgid "Refresh Photo"
+msgstr "Foto aktualisieren"
-#: ../../Zotlabs/Module/Setup.php:533
-msgid ""
-"Error: GD graphics PHP module with JPEG support required but not installed."
-msgstr "Fehler: Das PHP-Modul GD-Grafik mit JPEG-Unterstützung wird benötigt, ist aber nicht installiert."
+#: ../../Zotlabs/Module/Connedit.php:611
+msgid "Fetch updated photo"
+msgstr "Aktualisiertes Profilfoto abrufen"
-#: ../../Zotlabs/Module/Setup.php:537
-msgid "Error: openssl PHP module required but not installed."
-msgstr "Fehler: Das PHP-Modul openssl wird benötigt, ist aber nicht installiert."
+#: ../../Zotlabs/Module/Connedit.php:615
+msgid "Recent Activity"
+msgstr "Kürzliche Aktivitäten"
-#: ../../Zotlabs/Module/Setup.php:541
-msgid "Error: PDO database PHP module required but not installed."
-msgstr "Fehler: PDO-Datenbank-PHP-Modul ist erforderlich, aber nicht installiert."
+#: ../../Zotlabs/Module/Connedit.php:618
+msgid "View recent posts and comments"
+msgstr "Betrachte die neuesten Beiträge und Kommentare"
-#: ../../Zotlabs/Module/Setup.php:545
-msgid "Error: mb_string PHP module required but not installed."
-msgstr "Fehler: Das PHP-Modul mb_string wird benötigt, ist aber nicht installiert."
+#: ../../Zotlabs/Module/Connedit.php:625
+msgid "Block (or Unblock) all communications with this connection"
+msgstr "Jegliche Kommunikation mit dieser Verbindung blockieren/zulassen"
-#: ../../Zotlabs/Module/Setup.php:549
-msgid "Error: xml PHP module required for DAV but not installed."
-msgstr "Fehler: Das xml-PHP-Modul wird für DAV benötigt, ist aber nicht installiert."
+#: ../../Zotlabs/Module/Connedit.php:626
+msgid "This connection is blocked!"
+msgstr "Die Verbindung ist geblockt!"
-#: ../../Zotlabs/Module/Setup.php:567
-msgid ""
-"The web installer needs to be able to create a file called \".htconfig.php\""
-" in the top folder of your web server and it is unable to do so."
-msgstr "Der Installations-Assistent muss in der Lage sein, die Datei \".htconfig.php\" im Stammverzeichnis des Web-Servers anzulegen, ist er aber nicht."
+#: ../../Zotlabs/Module/Connedit.php:630
+msgid "Unignore"
+msgstr "Nicht ignorieren"
-#: ../../Zotlabs/Module/Setup.php:568
-msgid ""
-"This is most often a permission setting, as the web server may not be able "
-"to write files in your folder - even if you can."
-msgstr "Meist liegt das daran, dass der Nutzer, unter dem der Web-Server läuft, keine Schreibrechte in dem Verzeichnis hat – selbst wenn Du selbst das darfst."
+#: ../../Zotlabs/Module/Connedit.php:633
+msgid "Ignore (or Unignore) all inbound communications from this connection"
+msgstr "Jegliche eingehende Kommunikation von dieser Verbindung ignorieren/zulassen"
-#: ../../Zotlabs/Module/Setup.php:569
-msgid ""
-"At the end of this procedure, we will give you a text to save in a file "
-"named .htconfig.php in your Red top folder."
-msgstr "Am Schluss dieses Vorgangs wird ein Text generiert, den Du unter dem Dateinamen .htconfig.php im Stammverzeichnis Deiner Hubzilla-Installation speichern musst."
+#: ../../Zotlabs/Module/Connedit.php:634
+msgid "This connection is ignored!"
+msgstr "Die Verbindung wird ignoriert!"
-#: ../../Zotlabs/Module/Setup.php:570
+#: ../../Zotlabs/Module/Connedit.php:638
+msgid "Unarchive"
+msgstr "Aus Archiv zurückholen"
+
+#: ../../Zotlabs/Module/Connedit.php:638
+msgid "Archive"
+msgstr "Archivieren"
+
+#: ../../Zotlabs/Module/Connedit.php:641
msgid ""
-"You can alternatively skip this procedure and perform a manual installation."
-" Please see the file \"install/INSTALL.txt\" for instructions."
-msgstr "Alternativ kannst Du diesen Schritt überspringen und die Installation manuell vornehmen. Lies dazu die Datei install/INSTALL.txt."
+"Archive (or Unarchive) this connection - mark channel dead but keep content"
+msgstr "Verbindung archivieren/aus dem Archiv zurückholen (Archiv = Kanal als erloschen markieren, aber die Beiträge behalten)"
-#: ../../Zotlabs/Module/Setup.php:573
-msgid ".htconfig.php is writable"
-msgstr ".htconfig.php ist beschreibbar"
+#: ../../Zotlabs/Module/Connedit.php:642
+msgid "This connection is archived!"
+msgstr "Die Verbindung ist archiviert!"
+
+#: ../../Zotlabs/Module/Connedit.php:646
+msgid "Unhide"
+msgstr "Wieder sichtbar machen"
+
+#: ../../Zotlabs/Module/Connedit.php:646
+msgid "Hide"
+msgstr "Verstecken"
+
+#: ../../Zotlabs/Module/Connedit.php:649
+msgid "Hide or Unhide this connection from your other connections"
+msgstr "Diese Verbindung vor anderen Verbindungen verstecken/zeigen"
+
+#: ../../Zotlabs/Module/Connedit.php:650
+msgid "This connection is hidden!"
+msgstr "Die Verbindung ist versteckt!"
+
+#: ../../Zotlabs/Module/Connedit.php:657
+msgid "Delete this connection"
+msgstr "Verbindung löschen"
+
+#: ../../Zotlabs/Module/Connedit.php:665
+msgid "Fetch Vcard"
+msgstr "Vcard abrufen"
+
+#: ../../Zotlabs/Module/Connedit.php:668
+msgid "Fetch electronic calling card for this connection"
+msgstr "Rufe eine digitale Visitenkarte für diese Verbindung ab"
+
+#: ../../Zotlabs/Module/Connedit.php:679
+msgid "Open Individual Permissions section by default"
+msgstr "Öffne standardmäßig den Bereich für individuelle Berechtigungen"
-#: ../../Zotlabs/Module/Setup.php:587
+#: ../../Zotlabs/Module/Connedit.php:702
+msgid "Affinity"
+msgstr "Beziehung"
+
+#: ../../Zotlabs/Module/Connedit.php:705
+msgid "Open Set Affinity section by default"
+msgstr "Öffne standardmäßig den Bereich für Beziehungsgrad-Einstellungen"
+
+#: ../../Zotlabs/Module/Connedit.php:709 ../../Zotlabs/Widget/Affinity.php:26
+msgid "Me"
+msgstr "Ich"
+
+#: ../../Zotlabs/Module/Connedit.php:710 ../../Zotlabs/Widget/Affinity.php:27
+msgid "Family"
+msgstr "Familie"
+
+#: ../../Zotlabs/Module/Connedit.php:712 ../../Zotlabs/Widget/Affinity.php:29
+msgid "Acquaintances"
+msgstr "Bekannte"
+
+#: ../../Zotlabs/Module/Connedit.php:739
+msgid "Filter"
+msgstr "Filter"
+
+#: ../../Zotlabs/Module/Connedit.php:742
+msgid "Open Custom Filter section by default"
+msgstr "Öffne standardmäßig den Bereich für benutzerdefinierte Filter"
+
+#: ../../Zotlabs/Module/Connedit.php:779
+msgid "Approve this connection"
+msgstr "Verbindung genehmigen"
+
+#: ../../Zotlabs/Module/Connedit.php:779
+msgid "Accept connection to allow communication"
+msgstr "Akzeptiere die Verbindung, um Kommunikation zu ermöglichen"
+
+#: ../../Zotlabs/Module/Connedit.php:784
+msgid "Set Affinity"
+msgstr "Beziehung festlegen"
+
+#: ../../Zotlabs/Module/Connedit.php:787
+msgid "Set Profile"
+msgstr "Profil festlegen"
+
+#: ../../Zotlabs/Module/Connedit.php:790
+msgid "Set Affinity & Profile"
+msgstr "Beziehung und Profile festlegen"
+
+#: ../../Zotlabs/Module/Connedit.php:855
+msgid "This connection is unreachable from this location."
+msgstr "Diese Verbindung ist von diesem Ort unerreichbar."
+
+#: ../../Zotlabs/Module/Connedit.php:856
+msgid "This connection may be unreachable from other channel locations."
+msgstr "Diese Verbindung könnte von anderen Standpunkten des Kanals nicht erreichbar sein."
+
+#: ../../Zotlabs/Module/Connedit.php:858
+msgid "Location independence is not supported by their network."
+msgstr "Standort Unabhängigkeit wird vom anderen Netzwerk nicht unterstützt."
+
+#: ../../Zotlabs/Module/Connedit.php:864
msgid ""
-"This software uses the Smarty3 template engine to render its web views. "
-"Smarty3 compiles templates to PHP to speed up rendering."
-msgstr "Diese Software verwendet die Smarty3 Template Engine, um Vorlagen für die Webdarstellung zu verarbeiten. Smarty3 übersetzt diese Vorlagen nach PHP, um die Darstellung zu beschleunigen."
+"This connection is unreachable from this location. Location independence is "
+"not supported by their network."
+msgstr "Diese Verbindung ist von diesem Standort aus unerreichbar. Standort Unabhängigkeit wird vom anderen Netzwerk nicht unterstützt."
+
+#: ../../Zotlabs/Module/Connedit.php:867
+#: ../../Zotlabs/Widget/Settings_menu.php:109
+msgid "Connection Default Permissions"
+msgstr "Standardzugriffsrechte für neue Verbindungen:"
-#: ../../Zotlabs/Module/Setup.php:588
+#: ../../Zotlabs/Module/Connedit.php:867 ../../include/items.php:3974
#, php-format
+msgid "Connection: %s"
+msgstr "Verbindung: %s"
+
+#: ../../Zotlabs/Module/Connedit.php:868
+msgid "Apply these permissions automatically"
+msgstr "Diese Berechtigungen automatisch anwenden"
+
+#: ../../Zotlabs/Module/Connedit.php:868
+msgid "Connection requests will be approved without your interaction"
+msgstr "Verbindungsanfragen werden sofort bestätigt, ohne dass Deine aktive Zustimmung erforderlich ist."
+
+#: ../../Zotlabs/Module/Connedit.php:869
+msgid "Permission role"
+msgstr "Berechtigungsrolle"
+
+#: ../../Zotlabs/Module/Connedit.php:870
+msgid "Add permission role"
+msgstr "Berechtigungsrolle hinzufügen"
+
+#: ../../Zotlabs/Module/Connedit.php:877
+msgid "This connection's primary address is"
+msgstr "Die Hauptadresse der Verbindung ist"
+
+#: ../../Zotlabs/Module/Connedit.php:878
+msgid "Available locations:"
+msgstr "Verfügbare Klone:"
+
+#: ../../Zotlabs/Module/Connedit.php:883
msgid ""
-"In order to store these compiled templates, the web server needs to have "
-"write access to the directory %s under the top level web folder."
-msgstr "Um diese kompilierten Vorlagen speichern zu können, braucht der Web-Server Schreibzugriff auf das Verzeichnis %s unterhalb des Hubzilla-Stammverzeichnisses."
+"The permissions indicated on this page will be applied to all new "
+"connections."
+msgstr "Die auf dieser Seite angegebenen Berechtigungen werden auf alle neuen Verbindungen angewendet."
-#: ../../Zotlabs/Module/Setup.php:589 ../../Zotlabs/Module/Setup.php:610
+#: ../../Zotlabs/Module/Connedit.php:884
+msgid "Connection Tools"
+msgstr "Verbindungswerkzeuge"
+
+#: ../../Zotlabs/Module/Connedit.php:886
+msgid "Slide to adjust your degree of friendship"
+msgstr "Verschieben, um den Grad der Freundschaft zu einzustellen"
+
+#: ../../Zotlabs/Module/Connedit.php:887 ../../Zotlabs/Module/Rate.php:155
+#: ../../include/js_strings.php:20
+msgid "Rating"
+msgstr "Bewertung"
+
+#: ../../Zotlabs/Module/Connedit.php:888
+msgid "Slide to adjust your rating"
+msgstr "Verschieben, um Deine Bewertung einzustellen"
+
+#: ../../Zotlabs/Module/Connedit.php:889 ../../Zotlabs/Module/Connedit.php:894
+msgid "Optionally explain your rating"
+msgstr "Optional kannst Du Deine Bewertung begründen"
+
+#: ../../Zotlabs/Module/Connedit.php:891
+msgid "Custom Filter"
+msgstr "Benutzerdefinierter Filter"
+
+#: ../../Zotlabs/Module/Connedit.php:892
+msgid "Only import posts with this text"
+msgstr "Nur Beiträge mit diesem Text importieren"
+
+#: ../../Zotlabs/Module/Connedit.php:892 ../../Zotlabs/Module/Connedit.php:893
msgid ""
-"Please ensure that the user that your web server runs as (e.g. www-data) has"
-" write access to this folder."
-msgstr "Bitte stelle sicher, dass der Nutzer, unter dem der Web-Server läuft (z.B. www-data), Schreibzugriff auf dieses Verzeichnis hat."
+"words one per line or #tags or /patterns/ or lang=xx, leave blank to import "
+"all posts"
+msgstr "Einzelne Wörter pro Zeile, #Tags oder /Reguläre Ausdrücke/. lang=xx (z.B. lang=de) ermöglicht Filterung nach Sprache. Leer lassen, um alle Beiträge zu importieren."
-#: ../../Zotlabs/Module/Setup.php:590
+#: ../../Zotlabs/Module/Connedit.php:893
+msgid "Do not import posts with this text"
+msgstr "Beiträge mit diesem Text nicht importieren"
+
+#: ../../Zotlabs/Module/Connedit.php:895
+msgid "This information is public!"
+msgstr "Diese Information ist öffentlich!"
+
+#: ../../Zotlabs/Module/Connedit.php:900
+msgid "Connection Pending Approval"
+msgstr "Verbindung wartet auf Bestätigung"
+
+#: ../../Zotlabs/Module/Connedit.php:905
#, php-format
msgid ""
-"Note: as a security measure, you should give the web server write access to "
-"%s only--not the template files (.tpl) that it contains."
-msgstr "Hinweis: Aus Sicherheitsgründen sollte der Web-Server nur auf %s Schreibrechte haben, nicht auf die Template-Dateien (.tpl), die das Verzeichnis enthält."
+"Please choose the profile you would like to display to %s when viewing your "
+"profile securely."
+msgstr "Bitte wähle ein Profil, das wir %s zeigen sollen, wenn Deine Profilseite über eine verifizierte Verbindung aufgerufen wird."
+
+#: ../../Zotlabs/Module/Connedit.php:912
+msgid ""
+"Some permissions may be inherited from your channel's <a "
+"href=\"settings\"><strong>privacy settings</strong></a>, which have higher "
+"priority than individual settings. You can change those settings here but "
+"they wont have any impact unless the inherited setting changes."
+msgstr "Einige Berechtigungen werden möglicherweise von den globalen <a href=\"settings\">Sicherheits- und Privatsphäre-Einstellungen</a> dieses Kanals geerbt. Diese haben eine höhere Priorität als die Einstellungen an der Verbindung. Werden geerbte Einstellungen hier geändert, hat dies keine Auswirkungen."
+
+#: ../../Zotlabs/Module/Connedit.php:913
+msgid "Last update:"
+msgstr "Letzte Aktualisierung:"
+
+#: ../../Zotlabs/Module/Connedit.php:922
+msgid "Details"
+msgstr "Details"
+
+#: ../../Zotlabs/Module/Chat.php:181
+msgid "Room not found"
+msgstr "Chatraum nicht gefunden"
+
+#: ../../Zotlabs/Module/Chat.php:197
+msgid "Leave Room"
+msgstr "Raum verlassen"
+
+#: ../../Zotlabs/Module/Chat.php:198
+msgid "Delete Room"
+msgstr "Raum löschen"
+
+#: ../../Zotlabs/Module/Chat.php:199
+msgid "I am away right now"
+msgstr "Ich bin gerade nicht da"
+
+#: ../../Zotlabs/Module/Chat.php:200
+msgid "I am online"
+msgstr "Ich bin online"
+
+#: ../../Zotlabs/Module/Chat.php:202
+msgid "Bookmark this room"
+msgstr "Lesezeichen für diesen Raum setzen"
+
+#: ../../Zotlabs/Module/Chat.php:205 ../../Zotlabs/Module/Mail.php:241
+#: ../../Zotlabs/Module/Mail.php:362 ../../include/conversation.php:1296
+msgid "Please enter a link URL:"
+msgstr "Gib eine URL ein:"
-#: ../../Zotlabs/Module/Setup.php:593
+#: ../../Zotlabs/Module/Chat.php:206 ../../Zotlabs/Module/Mail.php:294
+#: ../../Zotlabs/Module/Mail.php:436 ../../Zotlabs/Lib/ThreadItem.php:757
+#: ../../include/conversation.php:1415
+msgid "Encrypt text"
+msgstr "Text verschlüsseln"
+
+#: ../../Zotlabs/Module/Chat.php:232
+msgid "New Chatroom"
+msgstr "Neuer Chatraum"
+
+#: ../../Zotlabs/Module/Chat.php:233
+msgid "Chatroom name"
+msgstr "Chatraumname"
+
+#: ../../Zotlabs/Module/Chat.php:234
+msgid "Expiration of chats (minutes)"
+msgstr "Verfall von Chats (Minuten)"
+
+#: ../../Zotlabs/Module/Chat.php:250
#, php-format
-msgid "%s is writable"
-msgstr "%s ist beschreibbar"
+msgid "%1$s's Chatrooms"
+msgstr "%1$ss Chaträume"
-#: ../../Zotlabs/Module/Setup.php:609
-msgid ""
-"This software uses the store directory to save uploaded files. The web "
-"server needs to have write access to the store directory under the top level"
-" web folder"
-msgstr "Diese Software benutzt das Verzeichnis store, um hochgeladene Dateien zu speichern. Der Webserver benötigt Schreibrechte für dieses Verzeichnis direkt unterhalb des Web-Stammverzeichnisses."
+#: ../../Zotlabs/Module/Chat.php:255
+msgid "No chatrooms available"
+msgstr "Keine Chaträume verfügbar"
-#: ../../Zotlabs/Module/Setup.php:613
-msgid "store is writable"
-msgstr "store ist schreibbar"
+#: ../../Zotlabs/Module/Chat.php:259
+msgid "Expiration"
+msgstr "Verfall"
-#: ../../Zotlabs/Module/Setup.php:646
-msgid ""
-"SSL certificate cannot be validated. Fix certificate or disable https access"
-" to this site."
-msgstr "Das SSL-Zertifikat konnte nicht validiert werden. Korrigiere das Zertifikat oder deaktiviere den HTTPS-Zugriff auf diesen Server."
+#: ../../Zotlabs/Module/Chat.php:260
+msgid "min"
+msgstr "min"
-#: ../../Zotlabs/Module/Setup.php:647
-msgid ""
-"If you have https access to your website or allow connections to TCP port "
-"443 (the https: port), you MUST use a browser-valid certificate. You MUST "
-"NOT use self-signed certificates!"
-msgstr "Wenn Du via HTTPS auf Deinen Server zugreifen möchtest, also Verbindungen über den Port 443 möglich sein sollen, ist ein SSL-Zertifikat einer Zertifizierungsstelle (CA) notwendig, das von den Browsern ohne Sicherheitsabfrage akzeptiert wird. Die Verwendung eines selbst signierten Zertifikates ist nicht möglich."
+#: ../../Zotlabs/Module/Fbrowser.php:29 ../../Zotlabs/Lib/Apps.php:242
+#: ../../include/conversation.php:1814 ../../include/nav.php:422
+msgid "Photos"
+msgstr "Fotos"
-#: ../../Zotlabs/Module/Setup.php:648
-msgid ""
-"This restriction is incorporated because public posts from you may for "
-"example contain references to images on your own hub."
-msgstr "Diese Einschränkung wurde eingebaut, weil Deine öffentlichen Beiträge zum Beispiel Verweise auf Bilder auf Deinem eigenen Hub enthalten können."
+#: ../../Zotlabs/Module/Fbrowser.php:85 ../../Zotlabs/Lib/Apps.php:237
+#: ../../Zotlabs/Storage/Browser.php:225 ../../include/conversation.php:1822
+#: ../../include/nav.php:430
+msgid "Files"
+msgstr "Dateien"
-#: ../../Zotlabs/Module/Setup.php:649
-msgid ""
-"If your certificate is not recognized, members of other sites (who may "
-"themselves have valid certificates) will get a warning message on their own "
-"site complaining about security issues."
-msgstr "Wenn Dein Zertifikat nicht von jedem Browser akzeptiert wird, erhalten die Mitglieder anderer $Projectname-Hubs (die mit korrekten Zertifikaten ausgestattet sind) Sicherheits-Warnmeldungen, obwohl sie gar nicht direkt auf Deinem Server unterwegs sind (zum Beispiel, wenn ein Bild aus einem Deiner Beiträge angezeigt wird)."
+#: ../../Zotlabs/Module/Menu.php:49
+msgid "Unable to update menu."
+msgstr "Kann Menü nicht aktualisieren."
-#: ../../Zotlabs/Module/Setup.php:650
-msgid ""
-"This can cause usability issues elsewhere (not just on your own site) so we "
-"must insist on this requirement."
-msgstr "Dies kann Probleme für andere Nutzer (nicht nur auf Deinem eigenen Server) verursachen, so dass wir auf dieser Forderung bestehen müssen."
+#: ../../Zotlabs/Module/Menu.php:60
+msgid "Unable to create menu."
+msgstr "Kann Menü nicht erstellen."
-#: ../../Zotlabs/Module/Setup.php:651
-msgid ""
-"Providers are available that issue free certificates which are browser-"
-"valid."
-msgstr "Es gibt einige Zertifizierungsstellen (CAs), bei denen solche Zertifikate kostenlos zu haben sind."
+#: ../../Zotlabs/Module/Menu.php:98 ../../Zotlabs/Module/Menu.php:110
+msgid "Menu Name"
+msgstr "Name des Menüs"
-#: ../../Zotlabs/Module/Setup.php:653
-msgid ""
-"If you are confident that the certificate is valid and signed by a trusted "
-"authority, check to see if you have failed to install an intermediate cert. "
-"These are not normally required by browsers, but are required for server-to-"
-"server communications."
-msgstr "Wenn Du sicher bist, dass das Zertifikat gültig und von einer vertrauenswürdigen Zertifizierungsstelle signiert ist, prüfe auf ggf. noch zu installierende Zwischenzertifikate (intermediate). Diese werden nicht unbedingt von Browsern benötigt, aber sehr wohl für die Kommunikation zwischen Servern."
+#: ../../Zotlabs/Module/Menu.php:98
+msgid "Unique name (not visible on webpage) - required"
+msgstr "Eindeutiger Name (nicht sichtbar auf der Webseite) – erforderlich"
-#: ../../Zotlabs/Module/Setup.php:655
-msgid "SSL certificate validation"
-msgstr "SSL Zertifikatverifizierung"
+#: ../../Zotlabs/Module/Menu.php:99 ../../Zotlabs/Module/Menu.php:111
+msgid "Menu Title"
+msgstr "Menütitel"
-#: ../../Zotlabs/Module/Setup.php:661
-msgid ""
-"Url rewrite in .htaccess is not working. Check your server "
-"configuration.Test: "
-msgstr "Das Umschreiben von URLs (rewrite) per .htaccess funktioniert nicht. Bitte prüfe die Server-Konfiguration. Test:"
+#: ../../Zotlabs/Module/Menu.php:99
+msgid "Visible on webpage - leave empty for no title"
+msgstr "Sichtbar auf der Webseite – für keinen Titel leer lassen"
-#: ../../Zotlabs/Module/Setup.php:664
-msgid "Url rewrite is working"
-msgstr "Url rewrite funktioniert"
+#: ../../Zotlabs/Module/Menu.php:100
+msgid "Allow Bookmarks"
+msgstr "Lesezeichen erlauben"
-#: ../../Zotlabs/Module/Setup.php:678
-msgid ""
-"The database configuration file \".htconfig.php\" could not be written. "
-"Please use the enclosed text to create a configuration file in your web "
-"server root."
-msgstr "Die Datenbank-Konfigurationsdatei „.htconfig.php“ konnte nicht geschrieben werden. Bitte verwende den unten angegebenen Text, um die Konfigurationsdatei im Stammverzeichnis des Webservers anzulegen."
+#: ../../Zotlabs/Module/Menu.php:100 ../../Zotlabs/Module/Menu.php:157
+msgid "Menu may be used to store saved bookmarks"
+msgstr "Im Menü können gespeicherte Lesezeichen abgelegt werden"
-#: ../../Zotlabs/Module/Setup.php:702
-#: ../../extend/addon/addon/cdav/cdav.php:41
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:352
-msgid "Errors encountered creating database tables."
-msgstr "Fehler beim Anlegen der Datenbank-Tabellen aufgetreten."
+#: ../../Zotlabs/Module/Menu.php:101 ../../Zotlabs/Module/Menu.php:159
+msgid "Submit and proceed"
+msgstr "Absenden und fortfahren"
-#: ../../Zotlabs/Module/Setup.php:743
-msgid "<h1>What next</h1>"
-msgstr "<h1>Was als Nächstes</h1>"
+#: ../../Zotlabs/Module/Menu.php:107 ../../include/text.php:2289
+msgid "Menus"
+msgstr "Menüs"
-#: ../../Zotlabs/Module/Setup.php:744
-msgid ""
-"IMPORTANT: You will need to [manually] setup a scheduled task for the "
-"poller."
-msgstr "WICHTIG: Du musst [manuell] einen Cronjob für den Poller einrichten."
+#: ../../Zotlabs/Module/Menu.php:117
+msgid "Bookmarks allowed"
+msgstr "Lesezeichen erlaubt"
-#: ../../Zotlabs/Module/Editpost.php:35
-msgid "Item is not editable"
-msgstr "Element kann nicht bearbeitet werden."
+#: ../../Zotlabs/Module/Menu.php:119
+msgid "Delete this menu"
+msgstr "Lösche dieses Menü"
-#: ../../Zotlabs/Module/Regdir.php:49 ../../Zotlabs/Module/Dirsearch.php:25
-msgid "This site is not a directory server"
-msgstr "Diese Webseite ist kein Verzeichnisserver"
+#: ../../Zotlabs/Module/Menu.php:120 ../../Zotlabs/Module/Menu.php:154
+msgid "Edit menu contents"
+msgstr "Bearbeite Menü Inhalte"
-#: ../../Zotlabs/Module/New_channel.php:140
-msgid "Create Channel"
-msgstr "Einen neuen Kanal anlegen"
+#: ../../Zotlabs/Module/Menu.php:121
+msgid "Edit this menu"
+msgstr "Dieses Menü bearbeiten"
-#: ../../Zotlabs/Module/New_channel.php:141
-msgid ""
-"A channel is your identity on this network. It can represent a person, a "
-"blog, or a forum to name a few. Channels can make connections with other "
-"channels to share information with highly detailed permissions."
-msgstr "Ein Kanal ist Deine Identität in diesem Netzwerk. Er kann eine Person, ein Blog oder ein Forum repräsentieren, nur um ein paar Beispiele zu nennen. Kanäle können Verbindungen miteinander eingehen, um Informationen zu teilen, jeweils basierend auf sehr detaillierten Berechtigungseinstellungen."
+#: ../../Zotlabs/Module/Menu.php:136
+msgid "Menu could not be deleted."
+msgstr "Menü konnte nicht gelöscht werden."
-#: ../../Zotlabs/Module/New_channel.php:142
+#: ../../Zotlabs/Module/Menu.php:149
+msgid "Edit Menu"
+msgstr "Menü bearbeiten"
+
+#: ../../Zotlabs/Module/Menu.php:153
+msgid "Add or remove entries to this menu"
+msgstr "Einträge zu diesem Menü hinzufügen oder entfernen"
+
+#: ../../Zotlabs/Module/Menu.php:155
+msgid "Menu name"
+msgstr "Menü Name"
+
+#: ../../Zotlabs/Module/Menu.php:155
+msgid "Must be unique, only seen by you"
+msgstr "Muss eindeutig sein, ist aber nur für Dich sichtbar"
+
+#: ../../Zotlabs/Module/Menu.php:156
+msgid "Menu title"
+msgstr "Menü Titel"
+
+#: ../../Zotlabs/Module/Menu.php:156
+msgid "Menu title as seen by others"
+msgstr "Menü Titel wie er von anderen gesehen wird"
+
+#: ../../Zotlabs/Module/Menu.php:157
+msgid "Allow bookmarks"
+msgstr "Erlaube Lesezeichen"
+
+#: ../../Zotlabs/Module/Layouts.php:184 ../../include/text.php:2290
+msgid "Layouts"
+msgstr "Layouts"
+
+#: ../../Zotlabs/Module/Layouts.php:186 ../../Zotlabs/Lib/Apps.php:245
+#: ../../include/nav.php:201 ../../include/nav.php:301
+#: ../../include/help.php:68 ../../include/help.php:74
+msgid "Help"
+msgstr "Hilfe"
+
+#: ../../Zotlabs/Module/Layouts.php:186
+msgid "Comanche page description language help"
+msgstr "Hilfe zur Comanche-Seitenbeschreibungssprache"
+
+#: ../../Zotlabs/Module/Layouts.php:190
+msgid "Layout Description"
+msgstr "Layout-Beschreibung"
+
+#: ../../Zotlabs/Module/Layouts.php:195
+msgid "Download PDL file"
+msgstr "PDL-Datei herunterladen"
+
+#: ../../Zotlabs/Module/Tagger.php:55 ../../include/markdown.php:141
+#: ../../include/bbcode.php:333
+msgid "post"
+msgstr "Beitrag"
+
+#: ../../Zotlabs/Module/Tagger.php:57 ../../include/conversation.php:146
+#: ../../include/text.php:1946
+msgid "comment"
+msgstr "Kommentar"
+
+#: ../../Zotlabs/Module/Tagger.php:95
+#, php-format
+msgid "%1$s tagged %2$s's %3$s with %4$s"
+msgstr "%1$s hat %2$ss %3$s mit %4$s verschlagwortet"
+
+#: ../../Zotlabs/Module/Pconfig.php:26 ../../Zotlabs/Module/Pconfig.php:59
+msgid "This setting requires special processing and editing has been blocked."
+msgstr "Diese Einstellung erfordert eine besondere Verarbeitung und ist blockiert."
+
+#: ../../Zotlabs/Module/Pconfig.php:48
+msgid "Configuration Editor"
+msgstr "Konfigurationseditor"
+
+#: ../../Zotlabs/Module/Pconfig.php:49
msgid ""
-"or <a href=\"import\">import an existing channel</a> from another location."
-msgstr "oder <a href=\"import\">importiere einen bestehenden Kanal</a> von einem anderen Server."
+"Warning: Changing some settings could render your channel inoperable. Please"
+" leave this page unless you are comfortable with and knowledgeable about how"
+" to correctly use this feature."
+msgstr "Warnung: Einige Einstellungen können Deinen Kanal funktionsunfähig machen. Bitte verlasse diese Seite, es sei denn Du bist vertraut damit, wie dieses Feature korrekt verwendet wird."
-#: ../../Zotlabs/Module/Notifications.php:40 ../../include/nav.php:194
-msgid "Mark all system notifications seen"
-msgstr "Markiere alle System-Benachrichtigungen als gesehen"
+#: ../../Zotlabs/Module/Group.php:24
+msgid "Privacy group created."
+msgstr "Gruppe wurde erstellt."
-#: ../../Zotlabs/Module/Poke.php:168 ../../Zotlabs/Lib/Apps.php:228
-#: ../../include/conversation.php:975
-msgid "Poke"
-msgstr "Anstupsen"
+#: ../../Zotlabs/Module/Group.php:30
+msgid "Could not create privacy group."
+msgstr "Gruppe konnte nicht erstellt werden."
-#: ../../Zotlabs/Module/Poke.php:169
-msgid "Poke somebody"
-msgstr "Jemanden anstupsen"
+#: ../../Zotlabs/Module/Group.php:42 ../../Zotlabs/Module/Group.php:143
+#: ../../include/items.php:3941
+msgid "Privacy group not found."
+msgstr "Gruppe nicht gefunden."
-#: ../../Zotlabs/Module/Poke.php:172
-msgid "Poke/Prod"
-msgstr "Anstupsen/Knuffen"
+#: ../../Zotlabs/Module/Group.php:58
+msgid "Privacy group updated."
+msgstr "Gruppe wurde aktualisiert."
-#: ../../Zotlabs/Module/Poke.php:173
-msgid "Poke, prod or do other things to somebody"
-msgstr "Jemanden anstupsen, knuffen oder sonstiges"
+#: ../../Zotlabs/Module/Group.php:92
+msgid "Create a group of channels."
+msgstr "Erstelle eine Gruppe für Kanäle."
-#: ../../Zotlabs/Module/Poke.php:180
-msgid "Recipient"
-msgstr "Empfänger"
+#: ../../Zotlabs/Module/Group.php:93 ../../Zotlabs/Module/Group.php:186
+msgid "Privacy group name: "
+msgstr "Gruppenname:"
-#: ../../Zotlabs/Module/Poke.php:181
-msgid "Choose what you wish to do to recipient"
-msgstr "Wähle, was Du mit dem/r Empfänger/in tun willst"
+#: ../../Zotlabs/Module/Group.php:95 ../../Zotlabs/Module/Group.php:189
+msgid "Members are visible to other channels"
+msgstr "Mitglieder sind sichtbar für andere Kanäle"
-#: ../../Zotlabs/Module/Poke.php:184 ../../Zotlabs/Module/Poke.php:185
-msgid "Make this post private"
-msgstr "Diesen Beitrag privat machen"
+#: ../../Zotlabs/Module/Group.php:113
+msgid "Privacy group removed."
+msgstr "Gruppe wurde entfernt."
+
+#: ../../Zotlabs/Module/Group.php:115
+msgid "Unable to remove privacy group."
+msgstr "Gruppe konnte nicht entfernt werden."
+
+#: ../../Zotlabs/Module/Group.php:185
+msgid "Privacy group editor"
+msgstr "Gruppeneditor"
+
+#: ../../Zotlabs/Module/Group.php:199 ../../Zotlabs/Module/Help.php:81
+msgid "Members"
+msgstr "Mitglieder"
+
+#: ../../Zotlabs/Module/Group.php:201
+msgid "All Connected Channels"
+msgstr "Alle verbundenen Kanäle"
-#: ../../Zotlabs/Module/Profiles.php:24 ../../Zotlabs/Module/Profiles.php:183
-#: ../../Zotlabs/Module/Profiles.php:240 ../../Zotlabs/Module/Profiles.php:619
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:62
+#: ../../Zotlabs/Module/Group.php:233
+msgid "Click on a channel to add or remove."
+msgstr "Wähle einen Kanal zum hinzufügen oder entfernen aus."
+
+#: ../../Zotlabs/Module/Profiles.php:24 ../../Zotlabs/Module/Profiles.php:184
+#: ../../Zotlabs/Module/Profiles.php:241 ../../Zotlabs/Module/Profiles.php:659
msgid "Profile not found."
msgstr "Profil nicht gefunden."
@@ -4659,953 +5810,424 @@ msgstr "Profil nicht gefunden."
msgid "Profile deleted."
msgstr "Profil gelöscht."
-#: ../../Zotlabs/Module/Profiles.php:68 ../../Zotlabs/Module/Profiles.php:104
+#: ../../Zotlabs/Module/Profiles.php:68 ../../Zotlabs/Module/Profiles.php:105
msgid "Profile-"
msgstr "Profil-"
-#: ../../Zotlabs/Module/Profiles.php:89 ../../Zotlabs/Module/Profiles.php:126
+#: ../../Zotlabs/Module/Profiles.php:90 ../../Zotlabs/Module/Profiles.php:127
msgid "New profile created."
msgstr "Neues Profil erstellt."
-#: ../../Zotlabs/Module/Profiles.php:110
+#: ../../Zotlabs/Module/Profiles.php:111
msgid "Profile unavailable to clone."
msgstr "Profil kann nicht geklont werden."
-#: ../../Zotlabs/Module/Profiles.php:145
+#: ../../Zotlabs/Module/Profiles.php:146
msgid "Profile unavailable to export."
msgstr "Dieses Profil kann nicht exportiert werden."
-#: ../../Zotlabs/Module/Profiles.php:250
+#: ../../Zotlabs/Module/Profiles.php:252
msgid "Profile Name is required."
msgstr "Profil-Name erforderlich."
-#: ../../Zotlabs/Module/Profiles.php:421
+#: ../../Zotlabs/Module/Profiles.php:459
msgid "Marital Status"
msgstr "Familienstand"
-#: ../../Zotlabs/Module/Profiles.php:425
+#: ../../Zotlabs/Module/Profiles.php:463
msgid "Romantic Partner"
msgstr "Romantische Partner"
-#: ../../Zotlabs/Module/Profiles.php:429 ../../Zotlabs/Module/Profiles.php:730
+#: ../../Zotlabs/Module/Profiles.php:467 ../../Zotlabs/Module/Profiles.php:775
msgid "Likes"
msgstr "Gefällt"
-#: ../../Zotlabs/Module/Profiles.php:433 ../../Zotlabs/Module/Profiles.php:731
+#: ../../Zotlabs/Module/Profiles.php:471 ../../Zotlabs/Module/Profiles.php:776
msgid "Dislikes"
msgstr "Gefällt nicht"
-#: ../../Zotlabs/Module/Profiles.php:437 ../../Zotlabs/Module/Profiles.php:738
+#: ../../Zotlabs/Module/Profiles.php:475 ../../Zotlabs/Module/Profiles.php:783
msgid "Work/Employment"
msgstr "Arbeit/Anstellung"
-#: ../../Zotlabs/Module/Profiles.php:440
+#: ../../Zotlabs/Module/Profiles.php:478
msgid "Religion"
msgstr "Religion"
-#: ../../Zotlabs/Module/Profiles.php:444
+#: ../../Zotlabs/Module/Profiles.php:482
msgid "Political Views"
msgstr "Politische Ansichten"
-#: ../../Zotlabs/Module/Profiles.php:448
-#: ../../extend/addon/addon/openid/MysqlProvider.php:74
+#: ../../Zotlabs/Module/Profiles.php:486
+#: ../../addon/openid/MysqlProvider.php:74
msgid "Gender"
msgstr "Geschlecht"
-#: ../../Zotlabs/Module/Profiles.php:452
+#: ../../Zotlabs/Module/Profiles.php:490
msgid "Sexual Preference"
msgstr "Sexuelle Orientierung"
-#: ../../Zotlabs/Module/Profiles.php:456
+#: ../../Zotlabs/Module/Profiles.php:494
msgid "Homepage"
msgstr "Webseite"
-#: ../../Zotlabs/Module/Profiles.php:460
+#: ../../Zotlabs/Module/Profiles.php:498
msgid "Interests"
msgstr "Hobbys/Interessen"
-#: ../../Zotlabs/Module/Profiles.php:554
+#: ../../Zotlabs/Module/Profiles.php:594
msgid "Profile updated."
msgstr "Profil aktualisiert."
-#: ../../Zotlabs/Module/Profiles.php:638
+#: ../../Zotlabs/Module/Profiles.php:678
msgid "Hide your connections list from viewers of this profile"
msgstr "Deine Verbindungen vor Betrachtern dieses Profils verbergen"
-#: ../../Zotlabs/Module/Profiles.php:680
+#: ../../Zotlabs/Module/Profiles.php:725
msgid "Edit Profile Details"
msgstr "Bearbeite Profil-Details"
-#: ../../Zotlabs/Module/Profiles.php:682
+#: ../../Zotlabs/Module/Profiles.php:727
msgid "View this profile"
msgstr "Dieses Profil ansehen"
-#: ../../Zotlabs/Module/Profiles.php:683 ../../Zotlabs/Module/Profiles.php:765
-#: ../../include/channel.php:983
+#: ../../Zotlabs/Module/Profiles.php:728 ../../Zotlabs/Module/Profiles.php:827
+#: ../../include/channel.php:1284
msgid "Edit visibility"
msgstr "Sichtbarkeit bearbeiten"
-#: ../../Zotlabs/Module/Profiles.php:684
+#: ../../Zotlabs/Module/Profiles.php:729
msgid "Profile Tools"
msgstr "Profilwerkzeuge"
-#: ../../Zotlabs/Module/Profiles.php:685
+#: ../../Zotlabs/Module/Profiles.php:730
msgid "Change cover photo"
msgstr "Titelbild ändern"
-#: ../../Zotlabs/Module/Profiles.php:686 ../../include/channel.php:954
+#: ../../Zotlabs/Module/Profiles.php:731 ../../include/channel.php:1255
msgid "Change profile photo"
msgstr "Profilfoto ändern"
-#: ../../Zotlabs/Module/Profiles.php:687
+#: ../../Zotlabs/Module/Profiles.php:732
msgid "Create a new profile using these settings"
msgstr "Neues Profil anlegen und diese Einstellungen übernehmen"
-#: ../../Zotlabs/Module/Profiles.php:688
+#: ../../Zotlabs/Module/Profiles.php:733
msgid "Clone this profile"
msgstr "Dieses Profil klonen"
-#: ../../Zotlabs/Module/Profiles.php:689
+#: ../../Zotlabs/Module/Profiles.php:734
msgid "Delete this profile"
msgstr "Dieses Profil löschen"
-#: ../../Zotlabs/Module/Profiles.php:690
+#: ../../Zotlabs/Module/Profiles.php:735
msgid "Add profile things"
msgstr "Sachen zum Profil hinzufügen"
-#: ../../Zotlabs/Module/Profiles.php:691 ../../include/widgets.php:105
-#: ../../include/conversation.php:1585
+#: ../../Zotlabs/Module/Profiles.php:736 ../../include/conversation.php:1688
msgid "Personal"
msgstr "Persönlich"
-#: ../../Zotlabs/Module/Profiles.php:693
+#: ../../Zotlabs/Module/Profiles.php:738
msgid "Relation"
msgstr "Beziehung"
-#: ../../Zotlabs/Module/Profiles.php:694 ../../include/datetime.php:55
+#: ../../Zotlabs/Module/Profiles.php:739 ../../include/datetime.php:55
msgid "Miscellaneous"
msgstr "Verschiedenes"
-#: ../../Zotlabs/Module/Profiles.php:696
+#: ../../Zotlabs/Module/Profiles.php:741
msgid "Import profile from file"
msgstr "Profil aus einer Datei importieren"
-#: ../../Zotlabs/Module/Profiles.php:697
+#: ../../Zotlabs/Module/Profiles.php:742
msgid "Export profile to file"
msgstr "Profil in eine Datei exportieren"
-#: ../../Zotlabs/Module/Profiles.php:698
+#: ../../Zotlabs/Module/Profiles.php:743
msgid "Your gender"
msgstr "Dein Geschlecht"
-#: ../../Zotlabs/Module/Profiles.php:699
+#: ../../Zotlabs/Module/Profiles.php:744
msgid "Marital status"
msgstr "Familienstand"
-#: ../../Zotlabs/Module/Profiles.php:700
+#: ../../Zotlabs/Module/Profiles.php:745
msgid "Sexual preference"
msgstr "Sexuelle Orientierung"
-#: ../../Zotlabs/Module/Profiles.php:703
+#: ../../Zotlabs/Module/Profiles.php:748
msgid "Profile name"
msgstr "Profilname"
-#: ../../Zotlabs/Module/Profiles.php:705
+#: ../../Zotlabs/Module/Profiles.php:750
msgid "This is your default profile."
msgstr "Das ist Dein Standardprofil."
-#: ../../Zotlabs/Module/Profiles.php:707
+#: ../../Zotlabs/Module/Profiles.php:752
msgid "Your full name"
msgstr "Dein voller Name"
-#: ../../Zotlabs/Module/Profiles.php:708
+#: ../../Zotlabs/Module/Profiles.php:753
msgid "Title/Description"
msgstr "Titel/Beschreibung"
-#: ../../Zotlabs/Module/Profiles.php:711
+#: ../../Zotlabs/Module/Profiles.php:756
msgid "Street address"
msgstr "Straße und Hausnummer"
-#: ../../Zotlabs/Module/Profiles.php:712
+#: ../../Zotlabs/Module/Profiles.php:757
msgid "Locality/City"
msgstr "Wohnort"
-#: ../../Zotlabs/Module/Profiles.php:713
+#: ../../Zotlabs/Module/Profiles.php:758
msgid "Region/State"
msgstr "Region/Bundesstaat"
-#: ../../Zotlabs/Module/Profiles.php:714
+#: ../../Zotlabs/Module/Profiles.php:759
msgid "Postal/Zip code"
msgstr "Postleitzahl"
-#: ../../Zotlabs/Module/Profiles.php:715
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1161
-msgid "Country"
-msgstr "Land"
-
-#: ../../Zotlabs/Module/Profiles.php:720
+#: ../../Zotlabs/Module/Profiles.php:765
msgid "Who (if applicable)"
msgstr "Wer (falls anwendbar)"
-#: ../../Zotlabs/Module/Profiles.php:720
+#: ../../Zotlabs/Module/Profiles.php:765
msgid "Examples: cathy123, Cathy Williams, cathy@example.com"
msgstr "Beispiele: cathy123, Cathy Williams, cathy@example.com"
-#: ../../Zotlabs/Module/Profiles.php:721
+#: ../../Zotlabs/Module/Profiles.php:766
msgid "Since (date)"
msgstr "Seit (Datum)"
-#: ../../Zotlabs/Module/Profiles.php:724
+#: ../../Zotlabs/Module/Profiles.php:769
msgid "Tell us about yourself"
msgstr "Erzähle uns ein wenig von Dir"
-#: ../../Zotlabs/Module/Profiles.php:725
-#: ../../extend/addon/addon/openid/MysqlProvider.php:68
+#: ../../Zotlabs/Module/Profiles.php:770
+#: ../../addon/openid/MysqlProvider.php:68
msgid "Homepage URL"
msgstr "Homepage-URL"
-#: ../../Zotlabs/Module/Profiles.php:726
+#: ../../Zotlabs/Module/Profiles.php:771
msgid "Hometown"
msgstr "Heimatort"
-#: ../../Zotlabs/Module/Profiles.php:727
+#: ../../Zotlabs/Module/Profiles.php:772
msgid "Political views"
msgstr "Politische Ansichten"
-#: ../../Zotlabs/Module/Profiles.php:728
+#: ../../Zotlabs/Module/Profiles.php:773
msgid "Religious views"
msgstr "Religiöse Ansichten"
-#: ../../Zotlabs/Module/Profiles.php:729
+#: ../../Zotlabs/Module/Profiles.php:774
msgid "Keywords used in directory listings"
msgstr "Schlüsselwörter, die in Verzeichnis-Auflistungen verwendet werden"
-#: ../../Zotlabs/Module/Profiles.php:729
+#: ../../Zotlabs/Module/Profiles.php:774
msgid "Example: fishing photography software"
msgstr "Beispiel: Angeln Fotografie Software"
-#: ../../Zotlabs/Module/Profiles.php:732
+#: ../../Zotlabs/Module/Profiles.php:777
msgid "Musical interests"
msgstr "Musikalische Interessen"
-#: ../../Zotlabs/Module/Profiles.php:733
+#: ../../Zotlabs/Module/Profiles.php:778
msgid "Books, literature"
msgstr "Bücher, Literatur"
-#: ../../Zotlabs/Module/Profiles.php:734
+#: ../../Zotlabs/Module/Profiles.php:779
msgid "Television"
msgstr "Fernsehen"
-#: ../../Zotlabs/Module/Profiles.php:735
+#: ../../Zotlabs/Module/Profiles.php:780
msgid "Film/Dance/Culture/Entertainment"
msgstr "Film/Tanz/Kultur/Unterhaltung"
-#: ../../Zotlabs/Module/Profiles.php:736
+#: ../../Zotlabs/Module/Profiles.php:781
msgid "Hobbies/Interests"
msgstr "Hobbys/Interessen"
-#: ../../Zotlabs/Module/Profiles.php:737
+#: ../../Zotlabs/Module/Profiles.php:782
msgid "Love/Romance"
msgstr "Liebe/Romantik"
-#: ../../Zotlabs/Module/Profiles.php:739
+#: ../../Zotlabs/Module/Profiles.php:784
msgid "School/Education"
msgstr "Schule/Ausbildung"
-#: ../../Zotlabs/Module/Profiles.php:740
+#: ../../Zotlabs/Module/Profiles.php:785
msgid "Contact information and social networks"
msgstr "Kontaktinformation und soziale Netzwerke"
-#: ../../Zotlabs/Module/Profiles.php:741
+#: ../../Zotlabs/Module/Profiles.php:786
msgid "My other channels"
msgstr "Meine anderen Kanäle"
-#: ../../Zotlabs/Module/Profiles.php:761 ../../include/channel.php:979
+#: ../../Zotlabs/Module/Profiles.php:788
+msgid "Communications"
+msgstr "Kommunikation"
+
+#: ../../Zotlabs/Module/Profiles.php:823 ../../include/channel.php:1280
msgid "Profile Image"
msgstr "Profilfoto:"
-#: ../../Zotlabs/Module/Profiles.php:771 ../../include/channel.php:961
-#: ../../include/nav.php:91
+#: ../../Zotlabs/Module/Profiles.php:833 ../../include/channel.php:1262
+#: ../../include/nav.php:144
msgid "Edit Profiles"
msgstr "Profile bearbeiten"
-#: ../../Zotlabs/Module/Oexchange.php:27
-msgid "Unable to find your hub."
-msgstr "Konnte Deinen Server nicht finden."
-
-#: ../../Zotlabs/Module/Oexchange.php:41
-msgid "Post successful."
-msgstr "Veröffentlichung erfolgreich."
-
-#: ../../Zotlabs/Module/Pconfig.php:26 ../../Zotlabs/Module/Pconfig.php:59
-msgid "This setting requires special processing and editing has been blocked."
-msgstr "Diese Einstellung erfordert eine besondere Verarbeitung und ist blockiert."
-
-#: ../../Zotlabs/Module/Pconfig.php:48
-msgid "Configuration Editor"
-msgstr "Konfigurationseditor"
-
-#: ../../Zotlabs/Module/Pconfig.php:49
-msgid ""
-"Warning: Changing some settings could render your channel inoperable. Please"
-" leave this page unless you are comfortable with and knowledgeable about how"
-" to correctly use this feature."
-msgstr "Warnung: Einige Einstellungen können Deinen Kanal funktionsunfähig machen. Bitte verlasse diese Seite, es sei denn Du bist vertraut damit, wie dieses Feature korrekt verwendet wird."
-
-#: ../../Zotlabs/Module/Blocks.php:154 ../../include/text.php:2270
-msgid "Blocks"
-msgstr "Blöcke"
-
-#: ../../Zotlabs/Module/Blocks.php:156
-msgid "Block Title"
-msgstr "Titel des Blocks"
-
-#: ../../Zotlabs/Module/Layouts.php:183 ../../include/text.php:2272
-msgid "Layouts"
-msgstr "Layouts"
-
-#: ../../Zotlabs/Module/Layouts.php:185 ../../Zotlabs/Lib/Apps.php:225
-#: ../../include/nav.php:162 ../../include/help.php:53
-#: ../../include/help.php:59
-msgid "Help"
-msgstr "Hilfe"
-
-#: ../../Zotlabs/Module/Layouts.php:185
-msgid "Comanche page description language help"
-msgstr "Hilfe zur Comanche-Seitenbeschreibungssprache"
-
-#: ../../Zotlabs/Module/Layouts.php:189
-msgid "Layout Description"
-msgstr "Layout-Beschreibung"
-
-#: ../../Zotlabs/Module/Layouts.php:194
-msgid "Download PDL file"
-msgstr "PDL-Datei herunterladen"
-
-#: ../../Zotlabs/Module/Rate.php:156
-msgid "Website:"
-msgstr "Webseite:"
-
-#: ../../Zotlabs/Module/Rate.php:159
-#, php-format
-msgid "Remote Channel [%s] (not yet known on this site)"
-msgstr "Kanal [%s] (auf diesem Server noch unbekannt)"
-
-#: ../../Zotlabs/Module/Rate.php:160
-msgid "Rating (this information is public)"
-msgstr "Bewertung (öffentlich sichtbar)"
-
-#: ../../Zotlabs/Module/Rate.php:161
-msgid "Optionally explain your rating (this information is public)"
-msgstr "Optional kannst du deine Bewertung erklären (öffentlich sichtbar)"
-
-#: ../../Zotlabs/Module/Like.php:19
-msgid "Like/Dislike"
-msgstr "Mögen/Nicht mögen"
-
-#: ../../Zotlabs/Module/Like.php:24
-msgid "This action is restricted to members."
-msgstr "Diese Aktion kann nur von Mitgliedern ausgeführt werden."
-
-#: ../../Zotlabs/Module/Like.php:25
-msgid ""
-"Please <a href=\"rmagic\">login with your $Projectname ID</a> or <a "
-"href=\"register\">register as a new $Projectname member</a> to continue."
-msgstr "Um fortzufahren <a href=\"rmagic\">melde Dich bitte mit Deiner $Projectname-ID an</a> oder <a href=\"register\">registriere Dich als neues $Projectname-Mitglied</a>."
-
-#: ../../Zotlabs/Module/Like.php:105 ../../Zotlabs/Module/Like.php:131
-#: ../../Zotlabs/Module/Like.php:169
-msgid "Invalid request."
-msgstr "Ungültige Anfrage."
-
-#: ../../Zotlabs/Module/Like.php:117 ../../include/conversation.php:126
-msgid "channel"
-msgstr "Kanal"
-
-#: ../../Zotlabs/Module/Like.php:146
-msgid "thing"
-msgstr "Sache"
-
-#: ../../Zotlabs/Module/Like.php:192
-msgid "Channel unavailable."
-msgstr "Kanal nicht vorhanden."
-
-#: ../../Zotlabs/Module/Like.php:240
-msgid "Previous action reversed."
-msgstr "Die vorherige Aktion wurde rückgängig gemacht."
-
-#: ../../Zotlabs/Module/Like.php:370 ../../Zotlabs/Module/Subthread.php:87
-#: ../../Zotlabs/Module/Tagger.php:47
-#: ../../extend/addon/addon/diaspora/inbound.php:1792
-#: ../../extend/addon/addon/redphotos/redphotohelper.php:74
-#: ../../include/text.php:1940 ../../include/conversation.php:120
-msgid "photo"
-msgstr "Foto"
-
-#: ../../Zotlabs/Module/Like.php:370 ../../Zotlabs/Module/Subthread.php:87
-#: ../../extend/addon/addon/diaspora/inbound.php:1792
-#: ../../include/text.php:1946 ../../include/conversation.php:148
-msgid "status"
-msgstr "Status"
-
-#: ../../Zotlabs/Module/Like.php:372 ../../Zotlabs/Module/Tagger.php:51
-#: ../../Zotlabs/Module/Events.php:256 ../../include/text.php:1943
-#: ../../include/event.php:961 ../../include/conversation.php:123
-msgid "event"
-msgstr "Termin"
-
-#: ../../Zotlabs/Module/Like.php:419
-#: ../../extend/addon/addon/diaspora/inbound.php:1821
-#: ../../include/conversation.php:164
-#, php-format
-msgid "%1$s likes %2$s's %3$s"
-msgstr "%1$s gefällt %2$ss %3$s"
-
-#: ../../Zotlabs/Module/Like.php:421 ../../include/conversation.php:167
-#, php-format
-msgid "%1$s doesn't like %2$s's %3$s"
-msgstr "%1$s gefällt %2$ss %3$s nicht"
-
-#: ../../Zotlabs/Module/Like.php:423
-#, php-format
-msgid "%1$s agrees with %2$s's %3$s"
-msgstr "%1$s stimmt %2$ss %3$s zu"
-
-#: ../../Zotlabs/Module/Like.php:425
-#, php-format
-msgid "%1$s doesn't agree with %2$s's %3$s"
-msgstr "%1$s lehnt %2$ss %3$s ab"
-
-#: ../../Zotlabs/Module/Like.php:427
-#, php-format
-msgid "%1$s abstains from a decision on %2$s's %3$s"
-msgstr "%1$s enthält sich zu %2$ss %3$s"
-
-#: ../../Zotlabs/Module/Like.php:429
-#, php-format
-msgid "%1$s is attending %2$s's %3$s"
-msgstr "%1$s nimmt an %2$ss %3$s teil"
-
-#: ../../Zotlabs/Module/Like.php:431
-#, php-format
-msgid "%1$s is not attending %2$s's %3$s"
-msgstr "%1$s nimmt an %2$ss %3$s nicht teil"
+#: ../../Zotlabs/Module/Editwebpage.php:139
+msgid "Page link"
+msgstr "Seiten-Link"
-#: ../../Zotlabs/Module/Like.php:433
-#, php-format
-msgid "%1$s may attend %2$s's %3$s"
-msgstr "%1$s nimmt vielleicht an %2$ss %3$s teil"
+#: ../../Zotlabs/Module/Editwebpage.php:166
+msgid "Edit Webpage"
+msgstr "Webseite bearbeiten"
-#: ../../Zotlabs/Module/Like.php:538
-msgid "Action completed."
-msgstr "Aktion durchgeführt."
+#: ../../Zotlabs/Module/Manage.php:145
+msgid "Create a new channel"
+msgstr "Neuen Kanal anlegen"
-#: ../../Zotlabs/Module/Like.php:539
-msgid "Thank you."
-msgstr "Vielen Dank."
+#: ../../Zotlabs/Module/Manage.php:170 ../../Zotlabs/Lib/Apps.php:234
+#: ../../include/nav.php:129 ../../include/nav.php:215
+msgid "Channel Manager"
+msgstr "Kanal-Manager"
-#: ../../Zotlabs/Module/Profile_photo.php:186
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:293
-msgid ""
-"Shift-reload the page or clear browser cache if the new photo does not "
-"display immediately."
-msgstr "Leere den Browser Cache oder nutze Umschalten-Neu Laden, falls das neue Foto nicht sofort angezeigt wird."
+#: ../../Zotlabs/Module/Manage.php:171
+msgid "Current Channel"
+msgstr "Aktueller Kanal"
-#: ../../Zotlabs/Module/Profile_photo.php:409
-msgid "Use Photo for Profile"
-msgstr "Foto für Profil verwenden"
+#: ../../Zotlabs/Module/Manage.php:173
+msgid "Switch to one of your channels by selecting it."
+msgstr "Wechsle zu einem Deiner Kanäle, indem Du auf ihn klickst."
-#: ../../Zotlabs/Module/Profile_photo.php:409
-msgid "Upload Profile Photo"
-msgstr "Lade neues Profilfoto hoch"
+#: ../../Zotlabs/Module/Manage.php:174
+msgid "Default Channel"
+msgstr "Standard Kanal"
-#: ../../Zotlabs/Module/Profile_photo.php:410
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:181
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:193
-msgid "Use"
-msgstr "Verwenden"
+#: ../../Zotlabs/Module/Manage.php:175
+msgid "Make Default"
+msgstr "Zum Standard machen"
-#: ../../Zotlabs/Module/Search.php:223
+#: ../../Zotlabs/Module/Manage.php:178
#, php-format
-msgid "Items tagged with: %s"
-msgstr "Beiträge mit Schlagwort: %s"
+msgid "%d new messages"
+msgstr "%d neue Nachrichten"
-#: ../../Zotlabs/Module/Search.php:225
+#: ../../Zotlabs/Module/Manage.php:179
#, php-format
-msgid "Search results for: %s"
-msgstr "Suchergebnisse für: %s"
-
-#: ../../Zotlabs/Module/Common.php:14
-msgid "No channel."
-msgstr "Kein Kanal."
-
-#: ../../Zotlabs/Module/Common.php:43
-msgid "Common connections"
-msgstr "Gemeinsame Verbindungen"
-
-#: ../../Zotlabs/Module/Common.php:48
-msgid "No connections in common."
-msgstr "Keine gemeinsamen Verbindungen."
-
-#: ../../Zotlabs/Module/Api.php:72 ../../Zotlabs/Module/Api.php:93
-msgid "Authorize application connection"
-msgstr "Zugriff für die Anwendung autorisieren"
-
-#: ../../Zotlabs/Module/Api.php:73
-msgid "Return to your app and insert this Security Code:"
-msgstr "Gehen Sie zu Ihrer App zurück und tragen Sie diesen Sicherheitscode ein:"
-
-#: ../../Zotlabs/Module/Api.php:83
-msgid "Please login to continue."
-msgstr "Zum Weitermachen, bitte einloggen."
-
-#: ../../Zotlabs/Module/Api.php:95
-msgid ""
-"Do you want to authorize this application to access your posts and contacts,"
-" and/or create new posts for you?"
-msgstr "Möchtest Du dieser Anwendung erlauben, Deine Nachrichten und Kontakte abzurufen und/oder neue Nachrichten für Dich zu erstellen?"
-
-#: ../../Zotlabs/Module/Ping.php:254
-msgid "sent you a private message"
-msgstr "hat Dir eine private Nachricht geschickt"
+msgid "%d new introductions"
+msgstr "%d neue Vorstellungen"
-#: ../../Zotlabs/Module/Ping.php:302
-msgid "added your channel"
-msgstr "hat deinen Kanal hinzugefügt"
+#: ../../Zotlabs/Module/Manage.php:181
+msgid "Delegated Channel"
+msgstr "Delegierte Kanäle"
-#: ../../Zotlabs/Module/Ping.php:312
-msgid "g A l F d"
-msgstr "l, d. F, G:i \\U\\h\\r"
+#: ../../Zotlabs/Module/Cards.php:38 ../../Zotlabs/Module/Cards.php:178
+#: ../../Zotlabs/Lib/Apps.php:224 ../../include/conversation.php:1873
+#: ../../include/features.php:122 ../../include/nav.php:479
+msgid "Cards"
+msgstr "Karten"
-#: ../../Zotlabs/Module/Ping.php:330
-msgid "[today]"
-msgstr "[Heute]"
+#: ../../Zotlabs/Module/Cards.php:95
+msgid "Add Card"
+msgstr "Karte hinzufügen"
-#: ../../Zotlabs/Module/Ping.php:339
-msgid "posted an event"
-msgstr "hat einen Termin veröffentlicht"
+#: ../../Zotlabs/Module/Dirsearch.php:33
+msgid "This directory server requires an access token"
+msgstr "Dieser Verzeichnisserver benötigt einen Zugriffstoken"
-#: ../../Zotlabs/Module/Siteinfo.php:20
+#: ../../Zotlabs/Module/Siteinfo.php:19
msgid "About this site"
msgstr "Über diese Seite"
-#: ../../Zotlabs/Module/Siteinfo.php:21
+#: ../../Zotlabs/Module/Siteinfo.php:20
msgid "Site Name"
msgstr "Seitenname"
-#: ../../Zotlabs/Module/Siteinfo.php:25 ../../include/network.php:1962
+#: ../../Zotlabs/Module/Siteinfo.php:24
msgid "Administrator"
msgstr "Administrator"
-#: ../../Zotlabs/Module/Siteinfo.php:28
+#: ../../Zotlabs/Module/Siteinfo.php:26 ../../Zotlabs/Module/Register.php:221
+msgid "Terms of Service"
+msgstr "Nutzungsbedingungen"
+
+#: ../../Zotlabs/Module/Siteinfo.php:27
msgid "Software and Project information"
msgstr "Software und Projektinformationen"
-#: ../../Zotlabs/Module/Siteinfo.php:29
+#: ../../Zotlabs/Module/Siteinfo.php:28
msgid "This site is powered by $Projectname"
msgstr "Diese Website wird bereitgestellt durch $Projectname"
-#: ../../Zotlabs/Module/Siteinfo.php:30
+#: ../../Zotlabs/Module/Siteinfo.php:29
msgid ""
"Federated and decentralised networking and identity services provided by Zot"
msgstr "Verbundene, dezentrale Netzwerk- und Identitätsdienste, ermöglicht mittels Zot"
-#: ../../Zotlabs/Module/Siteinfo.php:32
+#: ../../Zotlabs/Module/Siteinfo.php:31
#, php-format
msgid "Version %s"
msgstr "Version %s"
-#: ../../Zotlabs/Module/Siteinfo.php:33
+#: ../../Zotlabs/Module/Siteinfo.php:32
msgid "Project homepage"
msgstr "Projekt-Website"
-#: ../../Zotlabs/Module/Siteinfo.php:34
+#: ../../Zotlabs/Module/Siteinfo.php:33
msgid "Developer homepage"
msgstr "Entwickler-Website"
-#: ../../Zotlabs/Module/Lostpass.php:19
-msgid "No valid account found."
-msgstr "Kein gültiges Konto gefunden."
-
-#: ../../Zotlabs/Module/Lostpass.php:33
-msgid "Password reset request issued. Check your email."
-msgstr "Zurücksetzen des Passworts eingeleitet. Schau in Deine E-Mails."
-
-#: ../../Zotlabs/Module/Lostpass.php:39 ../../Zotlabs/Module/Lostpass.php:108
-#, php-format
-msgid "Site Member (%s)"
-msgstr "Nutzer (%s)"
-
-#: ../../Zotlabs/Module/Lostpass.php:44 ../../Zotlabs/Module/Lostpass.php:49
-#, php-format
-msgid "Password reset requested at %s"
-msgstr "Passwort-Rücksetzung auf %s angefordert"
-
-#: ../../Zotlabs/Module/Lostpass.php:68
-msgid ""
-"Request could not be verified. (You may have previously submitted it.) "
-"Password reset failed."
-msgstr "Die Anfrage konnte nicht verifiziert werden. (Vielleicht hast Du schon einmal auf den Link in der E-Mail geklickt?) Passwort-Rücksetzung fehlgeschlagen."
-
-#: ../../Zotlabs/Module/Lostpass.php:91 ../../boot.php:1727
-msgid "Password Reset"
-msgstr "Zurücksetzen des Kennworts"
-
-#: ../../Zotlabs/Module/Lostpass.php:92
-msgid "Your password has been reset as requested."
-msgstr "Dein Passwort wurde wie angefordert neu erstellt."
-
-#: ../../Zotlabs/Module/Lostpass.php:93
-msgid "Your new password is"
-msgstr "Dein neues Passwort lautet"
-
-#: ../../Zotlabs/Module/Lostpass.php:94
-msgid "Save or copy your new password - and then"
-msgstr "Speichere oder kopiere Dein neues Passwort – und dann"
-
-#: ../../Zotlabs/Module/Lostpass.php:95
-msgid "click here to login"
-msgstr "Klicke hier, um dich anzumelden"
-
-#: ../../Zotlabs/Module/Lostpass.php:96
-msgid ""
-"Your password may be changed from the <em>Settings</em> page after "
-"successful login."
-msgstr "Dein Passwort kann unter <em>Einstellungen</em> nach einer erfolgreichen Anmeldung geändert werden."
-
-#: ../../Zotlabs/Module/Lostpass.php:117
-#, php-format
-msgid "Your password has changed at %s"
-msgstr "Auf %s wurde Dein Passwort geändert"
-
-#: ../../Zotlabs/Module/Lostpass.php:130
-msgid "Forgot your Password?"
-msgstr "Kennwort vergessen?"
-
-#: ../../Zotlabs/Module/Lostpass.php:131
-msgid ""
-"Enter your email address and submit to have your password reset. Then check "
-"your email for further instructions."
-msgstr "Gib Deine E-Mail-Adresse ein, um Dein Passwort zurücksetzen zu lassen. Du erhältst dann weitere Anweisungen per E-Mail."
-
-#: ../../Zotlabs/Module/Lostpass.php:132
-msgid "Email Address"
-msgstr "E-Mail Adresse"
-
-#: ../../Zotlabs/Module/Lostpass.php:133
-msgid "Reset"
-msgstr "Zurücksetzen"
-
-#: ../../Zotlabs/Module/Rbmark.php:94
-msgid "Select a bookmark folder"
-msgstr "Lesezeichenordner wählen"
-
-#: ../../Zotlabs/Module/Rbmark.php:99
-msgid "Save Bookmark"
-msgstr "Lesezeichen speichern"
-
-#: ../../Zotlabs/Module/Rbmark.php:100
-msgid "URL of bookmark"
-msgstr "URL des Lesezeichens"
-
-#: ../../Zotlabs/Module/Rbmark.php:105
-msgid "Or enter new bookmark folder name"
-msgstr "Oder gib einen neuen Namen für den Lesezeichenordner ein"
-
-#: ../../Zotlabs/Module/Dirsearch.php:33
-msgid "This directory server requires an access token"
-msgstr "Dieser Verzeichnisserver benötigt einen Zugriffstoken"
-
-#: ../../Zotlabs/Module/Rmagic.php:35
-msgid "Authentication failed."
-msgstr "Authentifizierung fehlgeschlagen."
-
-#: ../../Zotlabs/Module/Rmagic.php:75
-msgid "Remote Authentication"
-msgstr "Entfernte Authentifizierung"
-
-#: ../../Zotlabs/Module/Rmagic.php:76
-msgid "Enter your channel address (e.g. channel@example.com)"
-msgstr "Deine Kanal-Adresse (z. B. channel@example.com)"
-
-#: ../../Zotlabs/Module/Rmagic.php:77
-msgid "Authenticate"
-msgstr "Authentifizieren"
-
-#: ../../Zotlabs/Module/Regmod.php:15
-msgid "Please login."
-msgstr "Bitte melde dich an."
-
-#: ../../Zotlabs/Module/Removeaccount.php:35
-msgid ""
-"Account removals are not allowed within 48 hours of changing the account "
-"password."
-msgstr "Das Löschen von Konten innerhalb 48 Stunden nachdem deren Passwort geändert wurde ist nicht erlaubt."
-
-#: ../../Zotlabs/Module/Removeaccount.php:57
-msgid "Remove This Account"
-msgstr "Dieses Konto löschen"
-
-#: ../../Zotlabs/Module/Removeaccount.php:58
-#: ../../Zotlabs/Module/Removeme.php:61
-msgid "WARNING: "
-msgstr "WARNUNG: "
-
-#: ../../Zotlabs/Module/Removeaccount.php:58
-msgid ""
-"This account and all its channels will be completely removed from the "
-"network. "
-msgstr "Dieses Konto mit all seinen Kanälen wird vollständig aus dem Netzwerk gelöscht."
-
-#: ../../Zotlabs/Module/Removeaccount.php:58
-#: ../../Zotlabs/Module/Removeme.php:61
-msgid "This action is permanent and can not be undone!"
-msgstr "Dieser Schritt ist endgültig und kann nicht rückgängig gemacht werden!"
-
-#: ../../Zotlabs/Module/Removeaccount.php:59
-#: ../../Zotlabs/Module/Removeme.php:62
-msgid "Please enter your password for verification:"
-msgstr "Bitte gib zur Bestätigung Dein Passwort ein:"
-
-#: ../../Zotlabs/Module/Removeaccount.php:60
-msgid ""
-"Remove this account, all its channels and all its channel clones from the "
-"network"
-msgstr "Dieses Konto, all seine Kanäle sowie alle Kanal-Klone aus dem Netzwerk löschen"
-
-#: ../../Zotlabs/Module/Removeaccount.php:60
-msgid ""
-"By default only the instances of the channels located on this hub will be "
-"removed from the network"
-msgstr "Standardmäßig werden nur die Kanalklone auf diesem $Projectname-Hub aus dem Netzwerk entfernt"
-
-#: ../../Zotlabs/Module/Removeaccount.php:61
-#: ../../Zotlabs/Module/Settings/Account.php:120
-msgid "Remove Account"
-msgstr "Konto entfernen"
-
-#: ../../Zotlabs/Module/Pdledit.php:21
-msgid "Layout updated."
-msgstr "Layout aktualisiert."
-
-#: ../../Zotlabs/Module/Pdledit.php:34 ../../Zotlabs/Module/Chat.php:218
-msgid "Feature disabled."
-msgstr "Funktion deaktiviert."
-
-#: ../../Zotlabs/Module/Pdledit.php:42 ../../Zotlabs/Module/Pdledit.php:69
-msgid "Edit System Page Description"
-msgstr "Systemseitenbeschreibung bearbeiten"
-
-#: ../../Zotlabs/Module/Pdledit.php:64
-msgid "Layout not found."
-msgstr "Layout nicht gefunden."
-
-#: ../../Zotlabs/Module/Pdledit.php:70
-msgid "Module Name:"
-msgstr "Modulname:"
-
-#: ../../Zotlabs/Module/Pdledit.php:71
-msgid "Layout Help"
-msgstr "Layout-Hilfe"
-
-#: ../../Zotlabs/Module/Uexport.php:55 ../../Zotlabs/Module/Uexport.php:56
-msgid "Export Channel"
-msgstr "Kanal exportieren"
-
-#: ../../Zotlabs/Module/Uexport.php:57
-msgid ""
-"Export your basic channel information to a file. This acts as a backup of "
-"your connections, permissions, profile and basic data, which can be used to "
-"import your data to a new server hub, but does not contain your content."
-msgstr "Exportiert die grundlegenden Kanal-Informationen in eine kleine Datei. Diese stellt eine Sicherung Deiner Verbindungen, Berechtigungen, Profile und Basisdaten bereit, die für den Import auf einem anderen Hub verwendet werden kann, aber nicht die Beiträge Deines Kanals enthält."
-
-#: ../../Zotlabs/Module/Uexport.php:58
-msgid "Export Content"
-msgstr "Kanal und Inhalte exportieren"
-
-#: ../../Zotlabs/Module/Uexport.php:59
-msgid ""
-"Export your channel information and recent content to a JSON backup that can"
-" be restored or imported to another server hub. This backs up all of your "
-"connections, permissions, profile data and several months of posts. This "
-"file may be VERY large. Please be patient - it may take several minutes for"
-" this download to begin."
-msgstr "Exportiert Deine Kanal-Informationen sowie alle zugehörigen Inhalte in eine JSON-Sicherungsdatei. Die sichert alle Verbindungen, Berechtigungen, Profildaten und Deine Beiträge aus mehreren Monaten. Diese Datei kann SEHR groß werden! Bitte habe ein wenig Geduld – es kann mehrere Minuten dauern, bis der Download startet."
-
-#: ../../Zotlabs/Module/Uexport.php:60
-msgid "Export your posts from a given year."
-msgstr "Exportiert die Beiträge des angegebenen Jahres."
-
-#: ../../Zotlabs/Module/Uexport.php:62
-msgid ""
-"You may also export your posts and conversations for a particular year or "
-"month. Adjust the date in your browser location bar to select other dates. "
-"If the export fails (possibly due to memory exhaustion on your server hub), "
-"please try again selecting a more limited date range."
-msgstr "Du kannst auch die Beiträge und Konversationen eines bestimmten Jahres oder Monats exportieren. Ändere das Datum in der Adresszeile Deines Browsers, um andere Zeiträume zu wählen. Falls der Export fehlschlägt (vermutlich, weil auf diesem Hub nicht genügend Speicher zur Verfügung steht), versuche es noch einmal mit einer kleineren Zeitspanne."
-
-#: ../../Zotlabs/Module/Uexport.php:63
-#, php-format
-msgid ""
-"To select all posts for a given year, such as this year, visit <a "
-"href=\"%1$s\">%2$s</a>"
-msgstr "Um alle Beiträge eines bestimmten Jahres, zum Beispiel dieses Jahres, auszuwählen, klicke <a href=\"%1$s\">%2$s</a>."
-
-#: ../../Zotlabs/Module/Uexport.php:64
-#, php-format
-msgid ""
-"To select all posts for a given month, such as January of this year, visit "
-"<a href=\"%1$s\">%2$s</a>"
-msgstr "Um alle Beiträge eines bestimmten Monats auszuwählen, zum Beispiel vom Januar diesen Jahres, klicke <a href=\"%1$s\">%2$s</a>."
-
-#: ../../Zotlabs/Module/Uexport.php:65
-#, php-format
-msgid ""
-"These content files may be imported or restored by visiting <a "
-"href=\"%1$s\">%2$s</a> on any site containing your channel. For best results"
-" please import or restore these in date order (oldest first)."
-msgstr "Diese Inhalts-Sicherungen können wiederhergestellt werden, indem Du <a href=\"%1$s\">%2$s</a> auf jeglichem Hub besuchst, der diesen Kanal enthält. Das funktioniert am besten, wenn Du dabei die zeitliche Reihenfolge einhältst, also die Sicherungen für den ältesten Zeitraum zuerst importierst."
-
-#: ../../Zotlabs/Module/Cal.php:69
-msgid "Permissions denied."
-msgstr "Berechtigung verweigert."
-
-#: ../../Zotlabs/Module/Cal.php:263 ../../Zotlabs/Module/Events.php:596
-msgid "l, F j"
-msgstr "l, j. F"
-
-#: ../../Zotlabs/Module/Cal.php:312 ../../Zotlabs/Module/Events.php:651
-#: ../../include/text.php:1748
-msgid "Link to Source"
-msgstr "Link zur Quelle"
-
-#: ../../Zotlabs/Module/Cal.php:335 ../../Zotlabs/Module/Events.php:679
-msgid "Edit Event"
-msgstr "Termin bearbeiten"
-
-#: ../../Zotlabs/Module/Cal.php:335 ../../Zotlabs/Module/Events.php:679
-msgid "Create Event"
-msgstr "Termin anlegen"
-
-#: ../../Zotlabs/Module/Cal.php:338 ../../Zotlabs/Module/Events.php:682
-msgid "Export"
-msgstr "Exportieren"
-
-#: ../../Zotlabs/Module/Cal.php:341 ../../include/text.php:2294
-msgid "Import"
-msgstr "Import"
-
-#: ../../Zotlabs/Module/Cal.php:345 ../../Zotlabs/Module/Events.php:691
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:848
-msgid "Today"
-msgstr "Heute"
-
-#: ../../Zotlabs/Module/Admin.php:94
-msgid "# Accounts"
-msgstr "Anzahl der Konten"
-
-#: ../../Zotlabs/Module/Admin.php:95
-msgid "# blocked accounts"
-msgstr "Anzahl der blockierten Konten"
-
-#: ../../Zotlabs/Module/Admin.php:96
-msgid "# expired accounts"
-msgstr "Anzahl der abgelaufenen Konten"
-
-#: ../../Zotlabs/Module/Admin.php:97
-msgid "# expiring accounts"
-msgstr "Anzahl der ablaufenden Konten"
-
-#: ../../Zotlabs/Module/Admin.php:108
-msgid "# Channels"
-msgstr "Anzahl der Kanäle"
-
-#: ../../Zotlabs/Module/Admin.php:109
-msgid "# primary"
-msgstr "Anzahl der primären Kanäle"
-
-#: ../../Zotlabs/Module/Admin.php:110
-msgid "# clones"
-msgstr "Anzahl der Klone"
-
-#: ../../Zotlabs/Module/Admin.php:116
-msgid "Message queues"
-msgstr "Nachrichten-Warteschlangen"
-
-#: ../../Zotlabs/Module/Admin.php:133
-msgid "Your software should be updated"
-msgstr "Die installierte Software sollte aktualisiert werden"
-
-#: ../../Zotlabs/Module/Admin.php:138
-msgid "Summary"
-msgstr "Zusammenfassung"
-
-#: ../../Zotlabs/Module/Admin.php:141
-msgid "Registered accounts"
-msgstr "Registrierte Konten"
-
-#: ../../Zotlabs/Module/Admin.php:142
-msgid "Pending registrations"
-msgstr "Ausstehende Registrierungen"
-
-#: ../../Zotlabs/Module/Admin.php:143
-msgid "Registered channels"
-msgstr "Registrierte Kanäle"
-
-#: ../../Zotlabs/Module/Admin.php:144
-msgid "Active plugins"
-msgstr "Aktive Plug-Ins"
-
-#: ../../Zotlabs/Module/Admin.php:145
-msgid "Version"
-msgstr "Version"
-
-#: ../../Zotlabs/Module/Admin.php:146
-msgid "Repository version (master)"
-msgstr "Repository-Version (master)"
+#: ../../Zotlabs/Module/Ratings.php:70
+msgid "No ratings"
+msgstr "Keine Bewertungen"
-#: ../../Zotlabs/Module/Admin.php:147
-msgid "Repository version (dev)"
-msgstr "Repository-Version (dev)"
+#: ../../Zotlabs/Module/Ratings.php:97 ../../Zotlabs/Module/Pubsites.php:35
+#: ../../include/conversation.php:1065
+msgid "Ratings"
+msgstr "Bewertungen"
-#: ../../Zotlabs/Module/Lockview.php:75
-msgid "Remote privacy information not available."
-msgstr "Privatsphäre-Einstellungen anderer Nutzer sind nicht verfügbar."
+#: ../../Zotlabs/Module/Ratings.php:98
+msgid "Rating: "
+msgstr "Bewertung: "
-#: ../../Zotlabs/Module/Lockview.php:96
-msgid "Visible to:"
-msgstr "Sichtbar für:"
+#: ../../Zotlabs/Module/Ratings.php:99
+msgid "Website: "
+msgstr "Webseite: "
-#: ../../Zotlabs/Module/Service_limits.php:23
-msgid "No service class restrictions found."
-msgstr "Keine Dienstklassenbeschränkungen gefunden."
+#: ../../Zotlabs/Module/Ratings.php:101
+msgid "Description: "
+msgstr "Beschreibung: "
-#: ../../Zotlabs/Module/Webpages.php:52
+#: ../../Zotlabs/Module/Webpages.php:54
msgid "Import Webpage Elements"
msgstr "Webseitenelemente importieren"
-#: ../../Zotlabs/Module/Webpages.php:53
+#: ../../Zotlabs/Module/Webpages.php:55
msgid "Import selected"
msgstr "Import ausgewählt"
-#: ../../Zotlabs/Module/Webpages.php:76
+#: ../../Zotlabs/Module/Webpages.php:78
msgid "Export Webpage Elements"
msgstr "Webseitenelemente exportieren"
-#: ../../Zotlabs/Module/Webpages.php:77
+#: ../../Zotlabs/Module/Webpages.php:79
msgid "Export selected"
msgstr "Exportieren ausgewählt"
-#: ../../Zotlabs/Module/Webpages.php:237 ../../Zotlabs/Lib/Apps.php:218
-#: ../../include/nav.php:109 ../../include/conversation.php:1745
+#: ../../Zotlabs/Module/Webpages.php:237 ../../Zotlabs/Lib/Apps.php:238
+#: ../../include/conversation.php:1884 ../../include/nav.php:491
msgid "Webpages"
msgstr "Webseiten"
-#: ../../Zotlabs/Module/Webpages.php:248 ../../include/page_widgets.php:44
+#: ../../Zotlabs/Module/Webpages.php:248
msgid "Actions"
msgstr "Aktionen"
-#: ../../Zotlabs/Module/Webpages.php:249 ../../include/page_widgets.php:45
+#: ../../Zotlabs/Module/Webpages.php:249
msgid "Page Link"
msgstr "Seiten-Link"
@@ -5633,176 +6255,111 @@ msgstr "Keine Webseitenelemente erkannt."
msgid "Import complete."
msgstr "Import abgeschlossen."
-#: ../../Zotlabs/Module/Removeme.php:35
+#: ../../Zotlabs/Module/Changeaddr.php:35
msgid ""
-"Channel removals are not allowed within 48 hours of changing the account "
-"password."
-msgstr "Innerhalb von 48 Stunden nach einer Änderung des Passworts können keine Kanäle gelöscht werden."
+"Channel name changes are not allowed within 48 hours of changing the account"
+" password."
+msgstr "Innerhalb von 48 Stunden nach einer Änderung des Konto-Passworts können Kanäle nicht umbenannt werden."
-#: ../../Zotlabs/Module/Removeme.php:60
-msgid "Remove This Channel"
-msgstr "Diesen Kanal löschen"
-
-#: ../../Zotlabs/Module/Removeme.php:61
-msgid "This channel will be completely removed from the network. "
-msgstr "Dieser Kanal wird vollständig aus dem Netzwerk gelöscht."
-
-#: ../../Zotlabs/Module/Removeme.php:63
-msgid "Remove this channel and all its clones from the network"
-msgstr "Lösche diesen Kanal und all seine Klone aus dem Netzwerk"
+#: ../../Zotlabs/Module/Changeaddr.php:46 ../../include/channel.php:209
+#: ../../include/channel.php:579
+msgid "Reserved nickname. Please choose another."
+msgstr "Reservierter Kurzname. Bitte wähle einen anderen."
-#: ../../Zotlabs/Module/Removeme.php:63
+#: ../../Zotlabs/Module/Changeaddr.php:51 ../../include/channel.php:214
+#: ../../include/channel.php:584
msgid ""
-"By default only the instance of the channel located on this hub will be "
-"removed from the network"
-msgstr "Standardmäßig wird der Kanal nur auf diesem Server gelöscht, seine Klone verbleiben im Netzwerk"
-
-#: ../../Zotlabs/Module/Removeme.php:64
-#: ../../Zotlabs/Module/Settings/Channel.php:547
-msgid "Remove Channel"
-msgstr "Kanal löschen"
-
-#: ../../Zotlabs/Module/Sharedwithme.php:98
-msgid "Files: shared with me"
-msgstr "Dateien, die mit mir geteilt wurden"
-
-#: ../../Zotlabs/Module/Sharedwithme.php:100
-msgid "NEW"
-msgstr "NEU"
-
-#: ../../Zotlabs/Module/Sharedwithme.php:103
-msgid "Remove all files"
-msgstr "Alle Dateien löschen"
-
-#: ../../Zotlabs/Module/Sharedwithme.php:104
-msgid "Remove this file"
-msgstr "Diese Datei löschen"
-
-#: ../../Zotlabs/Module/Wiki.php:34
-msgid "Not found"
-msgstr "Nicht gefunden"
-
-#: ../../Zotlabs/Module/Wiki.php:55
-msgid "Invalid channel"
-msgstr "Ungültiger Kanal"
-
-#: ../../Zotlabs/Module/Wiki.php:100
-msgid "Error retrieving wiki"
-msgstr "Fehler beim Abrufen des Wiki"
-
-#: ../../Zotlabs/Module/Wiki.php:107
-msgid "Error creating zip file export folder"
-msgstr "Fehler bei der Erzeugung des Zip-Datei Export-Verzeichnisses "
-
-#: ../../Zotlabs/Module/Wiki.php:125
-msgid "Error downloading wiki: "
-msgstr "Fehler beim Herunterladen des Wiki:"
-
-#: ../../Zotlabs/Module/Wiki.php:139 ../../include/nav.php:111
-#: ../../include/conversation.php:1755
-msgid "Wikis"
-msgstr "Wikis"
-
-#: ../../Zotlabs/Module/Wiki.php:145 ../../include/widgets.php:966
-msgid "Download"
-msgstr "Herunterladen"
-
-#: ../../Zotlabs/Module/Wiki.php:149 ../../include/widgets.php:970
-msgid "Wiki name"
-msgstr "Name des Wiki"
+"Nickname has unsupported characters or is already being used on this site."
+msgstr "Der Spitzname enthält nicht-unterstütze Zeichen oder wird bereits auf dieser Seite genutzt."
-#: ../../Zotlabs/Module/Wiki.php:150
-msgid "Content type"
-msgstr "Inhaltstyp"
+#: ../../Zotlabs/Module/Changeaddr.php:77
+msgid "Change channel nickname/address"
+msgstr "Kanalname/-adresse ändern"
-#: ../../Zotlabs/Module/Wiki.php:159
-msgid "Create a status post for this wiki"
-msgstr "Erzeuge einen Statusbeitrag für dieses Wiki"
+#: ../../Zotlabs/Module/Changeaddr.php:78
+msgid "Any/all connections on other networks will be lost!"
+msgstr "Jegliche/alle Verbindungen zu anderen Netzwerken gehen verloren!"
-#: ../../Zotlabs/Module/Wiki.php:178
-msgid "Wiki not found"
-msgstr "Wiki nicht gefunden"
-
-#: ../../Zotlabs/Module/Wiki.php:203
-msgid "Rename page"
-msgstr "Seite umbenennen"
+#: ../../Zotlabs/Module/Changeaddr.php:80
+msgid "New channel address"
+msgstr "Neue Kanaladresse"
-#: ../../Zotlabs/Module/Wiki.php:207
-msgid "Error retrieving page content"
-msgstr "Fehler beim Abrufen des Seiteninhalts"
+#: ../../Zotlabs/Module/Changeaddr.php:81
+msgid "Rename Channel"
+msgstr "Kanal umbenennen"
-#: ../../Zotlabs/Module/Wiki.php:240
-msgid "Revision Comparison"
-msgstr "Revisionsvergleich"
+#: ../../Zotlabs/Module/Editpost.php:38 ../../Zotlabs/Module/Editpost.php:43
+msgid "Item is not editable"
+msgstr "Element kann nicht bearbeitet werden."
-#: ../../Zotlabs/Module/Wiki.php:241
-msgid "Revert"
-msgstr "Rückgängig machen"
+#: ../../Zotlabs/Module/Editpost.php:108 ../../Zotlabs/Module/Rpost.php:178
+msgid "Edit post"
+msgstr "Bearbeite Beitrag"
-#: ../../Zotlabs/Module/Wiki.php:250
-msgid "Choose an available wiki from the list on the left."
-msgstr "Wähle ein vorhandenes Wiki aus der Liste auf der linken Seite aus."
+#: ../../Zotlabs/Module/Dreport.php:45
+msgid "Invalid message"
+msgstr "Ungültige Beitrags-ID (mid)"
-#: ../../Zotlabs/Module/Wiki.php:252
-msgid "Source"
-msgstr "Quelle"
+#: ../../Zotlabs/Module/Dreport.php:78
+msgid "no results"
+msgstr "keine Ergebnisse"
-#: ../../Zotlabs/Module/Wiki.php:269
-msgid "New page name"
-msgstr "Neuer Seitenname"
+#: ../../Zotlabs/Module/Dreport.php:93
+msgid "channel sync processed"
+msgstr "Kanal-Sync verarbeitet"
-#: ../../Zotlabs/Module/Wiki.php:275 ../../include/conversation.php:1169
-msgid "Embed image from photo albums"
-msgstr "Bild aus Fotoalben einbetten"
+#: ../../Zotlabs/Module/Dreport.php:97
+msgid "queued"
+msgstr "zur Warteschlange hinzugefügt"
-#: ../../Zotlabs/Module/Wiki.php:276 ../../include/conversation.php:1263
-msgid "Embed an image from your albums"
-msgstr "Betten Sie ein Bild aus Ihren Alben ein"
+#: ../../Zotlabs/Module/Dreport.php:101
+msgid "posted"
+msgstr "zugestellt"
-#: ../../Zotlabs/Module/Wiki.php:278 ../../include/conversation.php:1265
-#: ../../include/conversation.php:1312
-msgid "OK"
-msgstr "Ok"
+#: ../../Zotlabs/Module/Dreport.php:105
+msgid "accepted for delivery"
+msgstr "für Zustellung akzeptiert"
-#: ../../Zotlabs/Module/Wiki.php:279 ../../include/conversation.php:1205
-msgid "Choose images to embed"
-msgstr "Wählen Sie Bilder zum Einbetten aus"
+#: ../../Zotlabs/Module/Dreport.php:109
+msgid "updated"
+msgstr "aktualisiert"
-#: ../../Zotlabs/Module/Wiki.php:280 ../../include/conversation.php:1206
-msgid "Choose an album"
-msgstr "Wählen Sie ein Album aus"
+#: ../../Zotlabs/Module/Dreport.php:112
+msgid "update ignored"
+msgstr "Aktualisierung ignoriert"
-#: ../../Zotlabs/Module/Wiki.php:281 ../../include/conversation.php:1207
-msgid "Choose a different album..."
-msgstr "Wählen Sie ein anderes Album aus..."
+#: ../../Zotlabs/Module/Dreport.php:115
+msgid "permission denied"
+msgstr "Zugriff verweigert"
-#: ../../Zotlabs/Module/Wiki.php:282 ../../include/conversation.php:1208
-msgid "Error getting album list"
-msgstr "Fehler beim Holen der Albenliste"
+#: ../../Zotlabs/Module/Dreport.php:119
+msgid "recipient not found"
+msgstr "Empfänger nicht gefunden."
-#: ../../Zotlabs/Module/Wiki.php:283 ../../include/conversation.php:1209
-msgid "Error getting photo link"
-msgstr "Fehler beim Holen des Fotolinks"
+#: ../../Zotlabs/Module/Dreport.php:122
+msgid "mail recalled"
+msgstr "Mail widerrufen"
-#: ../../Zotlabs/Module/Wiki.php:284 ../../include/conversation.php:1210
-msgid "Error getting album"
-msgstr "Fehler beim Holen des Albums"
+#: ../../Zotlabs/Module/Dreport.php:125
+msgid "duplicate mail received"
+msgstr "Doppelte Mail erhalten"
-#: ../../Zotlabs/Module/Wiki.php:348
-msgid "Error creating wiki. Invalid name."
-msgstr "Fehler beim Erstellen des Wiki. Ungültiger Name."
+#: ../../Zotlabs/Module/Dreport.php:128
+msgid "mail delivered"
+msgstr "Mail zugestellt"
-#: ../../Zotlabs/Module/Wiki.php:359
-msgid "Wiki created, but error creating Home page."
-msgstr "Das Wiki wurde erzeugt, aber es gab einen Fehler bei der Erstellung der Startseite"
+#: ../../Zotlabs/Module/Dreport.php:148
+#, php-format
+msgid "Delivery report for %1$s"
+msgstr "Zustellungsbericht für %1$s"
-#: ../../Zotlabs/Module/Wiki.php:364
-msgid "Error creating wiki"
-msgstr "Fehler beim Erstellen des Wiki"
+#: ../../Zotlabs/Module/Dreport.php:151 ../../Zotlabs/Widget/Wiki_pages.php:60
+msgid "Options"
+msgstr "Optionen"
-#: ../../Zotlabs/Module/Wiki.php:410
-msgid "New page created"
-msgstr "Neue Seite erstellt"
+#: ../../Zotlabs/Module/Dreport.php:152
+msgid "Redeliver"
+msgstr "Erneut zustellen"
#: ../../Zotlabs/Module/Sources.php:37
msgid "Failed to create source. No channel selected."
@@ -5820,8 +6377,8 @@ msgstr "Quelle aktualisiert."
msgid "*"
msgstr "*"
-#: ../../Zotlabs/Module/Sources.php:96 ../../include/features.php:195
-#: ../../include/widgets.php:672
+#: ../../Zotlabs/Module/Sources.php:96
+#: ../../Zotlabs/Widget/Settings_menu.php:125 ../../include/features.php:218
msgid "Channel Sources"
msgstr "Kanal-Quellen"
@@ -5857,11 +6414,6 @@ msgid ""
"separated)"
msgstr "Füge die folgenden Kategorien zu Beiträgen, die aus dieser Quelle importiert werden, hinzu (kommagetrennt)"
-#: ../../Zotlabs/Module/Sources.php:112 ../../Zotlabs/Module/Sources.php:147
-#: ../../Zotlabs/Module/Settings/Oauth.php:93
-msgid "Optional"
-msgstr "Optional"
-
#: ../../Zotlabs/Module/Sources.php:133 ../../Zotlabs/Module/Sources.php:161
msgid "Source not found."
msgstr "Quelle nicht gefunden."
@@ -5882,722 +6434,588 @@ msgstr "Quelle gelöscht"
msgid "Unable to remove source."
msgstr "Konnte die Quelle nicht löschen."
-#: ../../Zotlabs/Module/Subthread.php:118
-#, php-format
-msgid "%1$s is following %2$s's %3$s"
-msgstr "%1$s folgt nun %2$ss %3$s"
+#: ../../Zotlabs/Module/Like.php:19
+msgid "Like/Dislike"
+msgstr "Mögen/Nicht mögen"
-#: ../../Zotlabs/Module/Subthread.php:120
-#, php-format
-msgid "%1$s stopped following %2$s's %3$s"
-msgstr "%1$s folgt %2$ss %3$s nicht mehr"
+#: ../../Zotlabs/Module/Like.php:24
+msgid "This action is restricted to members."
+msgstr "Diese Aktion kann nur von Mitgliedern ausgeführt werden."
-#: ../../Zotlabs/Module/Suggest.php:39
+#: ../../Zotlabs/Module/Like.php:25
msgid ""
-"No suggestions available. If this is a new site, please try again in 24 "
-"hours."
-msgstr "Keine Vorschläge vorhanden. Wenn das ein neuer Server ist, versuche es in 24 Stunden noch einmal."
-
-#: ../../Zotlabs/Module/Suggest.php:58 ../../include/widgets.php:149
-msgid "Ignore/Hide"
-msgstr "Ignorieren/Verstecken"
-
-#: ../../Zotlabs/Module/Tagger.php:55 ../../include/bbcode.php:274
-msgid "post"
-msgstr "Beitrag"
-
-#: ../../Zotlabs/Module/Tagger.php:57 ../../include/text.php:1948
-#: ../../include/conversation.php:150
-msgid "comment"
-msgstr "Kommentar"
-
-#: ../../Zotlabs/Module/Tagger.php:100
-#, php-format
-msgid "%1$s tagged %2$s's %3$s with %4$s"
-msgstr "%1$s hat %2$ss %3$s mit %4$s verschlagwortet"
-
-#: ../../Zotlabs/Module/Settings/Features.php:45
-msgid "Additional Features"
-msgstr "Zusätzliche Funktionen"
-
-#: ../../Zotlabs/Module/Settings/Oauth.php:34
-msgid "Name is required"
-msgstr "Name ist erforderlich"
-
-#: ../../Zotlabs/Module/Settings/Oauth.php:38
-msgid "Key and Secret are required"
-msgstr "Schlüssel und Geheimnis werden benötigt"
-
-#: ../../Zotlabs/Module/Settings/Oauth.php:86
-#: ../../Zotlabs/Module/Settings/Oauth.php:112
-#: ../../Zotlabs/Module/Settings/Oauth.php:148
-msgid "Add application"
-msgstr "Anwendung hinzufügen"
-
-#: ../../Zotlabs/Module/Settings/Oauth.php:89
-msgid "Name of application"
-msgstr "Name der Anwendung"
-
-#: ../../Zotlabs/Module/Settings/Oauth.php:90
-#: ../../Zotlabs/Module/Settings/Oauth.php:116
-#: ../../extend/addon/addon/statusnet/statusnet.php:893
-#: ../../extend/addon/addon/twitter/twitter.php:775
-msgid "Consumer Key"
-msgstr "Consumer Key"
-
-#: ../../Zotlabs/Module/Settings/Oauth.php:90
-#: ../../Zotlabs/Module/Settings/Oauth.php:91
-msgid "Automatically generated - change if desired. Max length 20"
-msgstr "Automatisch erzeugt – ändern, falls erwünscht. Maximale Länge 20"
+"Please <a href=\"rmagic\">login with your $Projectname ID</a> or <a "
+"href=\"register\">register as a new $Projectname member</a> to continue."
+msgstr "Um fortzufahren <a href=\"rmagic\">melde Dich bitte mit Deiner $Projectname-ID an</a> oder <a href=\"register\">registriere Dich als neues $Projectname-Mitglied</a>."
-#: ../../Zotlabs/Module/Settings/Oauth.php:91
-#: ../../Zotlabs/Module/Settings/Oauth.php:117
-#: ../../extend/addon/addon/statusnet/statusnet.php:892
-#: ../../extend/addon/addon/twitter/twitter.php:776
-msgid "Consumer Secret"
-msgstr "Consumer Secret"
+#: ../../Zotlabs/Module/Like.php:105 ../../Zotlabs/Module/Like.php:131
+#: ../../Zotlabs/Module/Like.php:169
+msgid "Invalid request."
+msgstr "Ungültige Anfrage."
-#: ../../Zotlabs/Module/Settings/Oauth.php:92
-#: ../../Zotlabs/Module/Settings/Oauth.php:118
-msgid "Redirect"
-msgstr "Umleitung"
+#: ../../Zotlabs/Module/Like.php:117 ../../include/conversation.php:122
+msgid "channel"
+msgstr "Kanal"
-#: ../../Zotlabs/Module/Settings/Oauth.php:92
-msgid ""
-"Redirect URI - leave blank unless your application specifically requires "
-"this"
-msgstr "Umleitungs-URl – lasse das leer, solange Deine Anwendung es nicht explizit erfordert"
+#: ../../Zotlabs/Module/Like.php:146
+msgid "thing"
+msgstr "Sache"
-#: ../../Zotlabs/Module/Settings/Oauth.php:93
-#: ../../Zotlabs/Module/Settings/Oauth.php:119
-msgid "Icon url"
-msgstr "Symbol-URL"
+#: ../../Zotlabs/Module/Like.php:192
+msgid "Channel unavailable."
+msgstr "Kanal nicht vorhanden."
-#: ../../Zotlabs/Module/Settings/Oauth.php:104
-msgid "Application not found."
-msgstr "Die Anwendung wurde nicht gefunden."
+#: ../../Zotlabs/Module/Like.php:240
+msgid "Previous action reversed."
+msgstr "Die vorherige Aktion wurde rückgängig gemacht."
-#: ../../Zotlabs/Module/Settings/Oauth.php:147
-msgid "Connected Apps"
-msgstr "Verbundene Apps"
+#: ../../Zotlabs/Module/Like.php:423 ../../addon/diaspora/Receiver.php:1453
+#: ../../addon/pubcrawl/as.php:1323 ../../include/conversation.php:160
+#, php-format
+msgid "%1$s likes %2$s's %3$s"
+msgstr "%1$s gefällt %2$ss %3$s"
-#: ../../Zotlabs/Module/Settings/Oauth.php:151
-msgid "Client key starts with"
-msgstr "Client Key beginnt mit"
+#: ../../Zotlabs/Module/Like.php:425 ../../addon/pubcrawl/as.php:1325
+#: ../../include/conversation.php:163
+#, php-format
+msgid "%1$s doesn't like %2$s's %3$s"
+msgstr "%1$s gefällt %2$ss %3$s nicht"
-#: ../../Zotlabs/Module/Settings/Oauth.php:152
-msgid "No name"
-msgstr "Kein Name"
+#: ../../Zotlabs/Module/Like.php:427
+#, php-format
+msgid "%1$s agrees with %2$s's %3$s"
+msgstr "%1$s stimmt %2$ss %3$s zu"
-#: ../../Zotlabs/Module/Settings/Oauth.php:153
-msgid "Remove authorization"
-msgstr "Authorisierung aufheben"
+#: ../../Zotlabs/Module/Like.php:429
+#, php-format
+msgid "%1$s doesn't agree with %2$s's %3$s"
+msgstr "%1$s lehnt %2$ss %3$s ab"
-#: ../../Zotlabs/Module/Settings/Tokens.php:31
+#: ../../Zotlabs/Module/Like.php:431
#, php-format
-msgid "This channel is limited to %d tokens"
-msgstr "Dieser Kanal ist auf %d Token begrenzt"
+msgid "%1$s abstains from a decision on %2$s's %3$s"
+msgstr "%1$s enthält sich zu %2$ss %3$s"
-#: ../../Zotlabs/Module/Settings/Tokens.php:37
-msgid "Name and Password are required."
-msgstr "Name und Passwort sind erforderlich."
+#: ../../Zotlabs/Module/Like.php:433
+#, php-format
+msgid "%1$s is attending %2$s's %3$s"
+msgstr "%1$s nimmt an %2$ss %3$s teil"
-#: ../../Zotlabs/Module/Settings/Tokens.php:77
-msgid "Token saved."
-msgstr "Token gespeichert."
+#: ../../Zotlabs/Module/Like.php:435
+#, php-format
+msgid "%1$s is not attending %2$s's %3$s"
+msgstr "%1$s nimmt an %2$ss %3$s nicht teil"
-#: ../../Zotlabs/Module/Settings/Tokens.php:113
-msgid ""
-"Use this form to create temporary access identifiers to share things with "
-"non-members. These identities may be used in Access Control Lists and "
-"visitors may login using these credentials to access private content."
-msgstr "Mit diesem Formular kannst Du temporäre Zugangs-IDs anlegen, um Inhalte mit Nicht-Mitgliedern zu teilen. Die IDs können in Berechtigungslisten (ACLs) verwendet werden, und Besucher können sich damit einloggen, um auf private Inhalte zuzugreifen."
+#: ../../Zotlabs/Module/Like.php:437
+#, php-format
+msgid "%1$s may attend %2$s's %3$s"
+msgstr "%1$s nimmt vielleicht an %2$ss %3$s teil"
-#: ../../Zotlabs/Module/Settings/Tokens.php:115
-msgid ""
-"You may also provide <em>dropbox</em> style access links to friends and "
-"associates by adding the Login Password to any specific site URL as shown. "
-"Examples:"
-msgstr "Du kannst auch <em>Dropbox</em>-ähnliche Zugriffslinks an Andere weitergeben, indem du das Login-Passwort an eine entsprechende URL anhängst wie nachfolgend gezeigt. Beispiele:"
+#: ../../Zotlabs/Module/Like.php:547
+msgid "Action completed."
+msgstr "Aktion durchgeführt."
-#: ../../Zotlabs/Module/Settings/Tokens.php:150 ../../include/widgets.php:647
-msgid "Guest Access Tokens"
-msgstr "Gastzugangstoken"
+#: ../../Zotlabs/Module/Like.php:548
+msgid "Thank you."
+msgstr "Vielen Dank."
-#: ../../Zotlabs/Module/Settings/Tokens.php:157
-msgid "Login Name"
-msgstr "Anmeldename"
+#: ../../Zotlabs/Module/Directory.php:245
+#, php-format
+msgid "%d rating"
+msgid_plural "%d ratings"
+msgstr[0] "%d Bewertung"
+msgstr[1] "%d Bewertungen"
-#: ../../Zotlabs/Module/Settings/Tokens.php:158
-msgid "Login Password"
-msgstr "Anmeldepasswort"
+#: ../../Zotlabs/Module/Directory.php:256
+msgid "Gender: "
+msgstr "Geschlecht:"
-#: ../../Zotlabs/Module/Settings/Tokens.php:159
-msgid "Expires (yyyy-mm-dd)"
-msgstr "Läuft ab (jjjj-mm-tt)"
+#: ../../Zotlabs/Module/Directory.php:258
+msgid "Status: "
+msgstr "Status:"
-#: ../../Zotlabs/Module/Settings/Account.php:20
-msgid "Not valid email."
-msgstr "Keine gültige E-Mail Adresse."
+#: ../../Zotlabs/Module/Directory.php:260
+msgid "Homepage: "
+msgstr "Webseite:"
-#: ../../Zotlabs/Module/Settings/Account.php:23
-msgid "Protected email address. Cannot change to that email."
-msgstr "Geschützte E-Mail Adresse. Diese kann nicht verändert werden."
+#: ../../Zotlabs/Module/Directory.php:309 ../../include/channel.php:1516
+msgid "Age:"
+msgstr "Alter:"
-#: ../../Zotlabs/Module/Settings/Account.php:32
-msgid "System failure storing new email. Please try again."
-msgstr "Systemfehler während des Speicherns der neuen Mail. Bitte versuche es noch einmal."
+#: ../../Zotlabs/Module/Directory.php:314 ../../include/channel.php:1352
+#: ../../include/event.php:52 ../../include/event.php:84
+msgid "Location:"
+msgstr "Ort:"
-#: ../../Zotlabs/Module/Settings/Account.php:40
-msgid "Technical skill level updated"
-msgstr "Technische Qualifikationsstufe aktualisiert"
+#: ../../Zotlabs/Module/Directory.php:320
+msgid "Description:"
+msgstr "Beschreibung:"
-#: ../../Zotlabs/Module/Settings/Account.php:56
-msgid "Password verification failed."
-msgstr "Passwortüberprüfung fehlgeschlagen."
+#: ../../Zotlabs/Module/Directory.php:325 ../../include/channel.php:1532
+msgid "Hometown:"
+msgstr "Heimatstadt:"
-#: ../../Zotlabs/Module/Settings/Account.php:63
-msgid "Passwords do not match. Password unchanged."
-msgstr "Kennwörter stimmen nicht überein. Kennwort nicht verändert."
+#: ../../Zotlabs/Module/Directory.php:327 ../../include/channel.php:1540
+msgid "About:"
+msgstr "Über:"
-#: ../../Zotlabs/Module/Settings/Account.php:67
-msgid "Empty passwords are not allowed. Password unchanged."
-msgstr "Leere Kennwörter sind nicht erlaubt. Kennwort nicht verändert."
+#: ../../Zotlabs/Module/Directory.php:328 ../../Zotlabs/Module/Suggest.php:56
+#: ../../Zotlabs/Widget/Follow.php:32 ../../Zotlabs/Widget/Suggestions.php:44
+#: ../../include/conversation.php:1035 ../../include/channel.php:1337
+#: ../../include/connections.php:111
+msgid "Connect"
+msgstr "Verbinden"
-#: ../../Zotlabs/Module/Settings/Account.php:81
-msgid "Password changed."
-msgstr "Kennwort geändert."
+#: ../../Zotlabs/Module/Directory.php:329
+msgid "Public Forum:"
+msgstr "Öffentliches Forum:"
-#: ../../Zotlabs/Module/Settings/Account.php:83
-msgid "Password update failed. Please try again."
-msgstr "Kennwortänderung fehlgeschlagen. Bitte versuche es noch einmal."
+#: ../../Zotlabs/Module/Directory.php:332
+msgid "Keywords: "
+msgstr "Schlüsselwörter:"
-#: ../../Zotlabs/Module/Settings/Account.php:112
-msgid "Account Settings"
-msgstr "Konto-Einstellungen"
+#: ../../Zotlabs/Module/Directory.php:335
+msgid "Don't suggest"
+msgstr "Nicht vorschlagen"
-#: ../../Zotlabs/Module/Settings/Account.php:113
-msgid "Current Password"
-msgstr "Aktuelles Passwort"
+#: ../../Zotlabs/Module/Directory.php:337
+msgid "Common connections:"
+msgstr "Gemeinsame Verbindungen:"
-#: ../../Zotlabs/Module/Settings/Account.php:114
-msgid "Enter New Password"
-msgstr "Gib ein neues Passwort ein"
+#: ../../Zotlabs/Module/Directory.php:386
+msgid "Global Directory"
+msgstr "Globales Verzeichnis"
-#: ../../Zotlabs/Module/Settings/Account.php:115
-msgid "Confirm New Password"
-msgstr "Bestätige das neue Passwort"
+#: ../../Zotlabs/Module/Directory.php:386
+msgid "Local Directory"
+msgstr "Lokales Verzeichnis"
-#: ../../Zotlabs/Module/Settings/Account.php:115
-msgid "Leave password fields blank unless changing"
-msgstr "Lasse die Passwort-Felder leer, außer Du möchtest das Passwort ändern"
+#: ../../Zotlabs/Module/Directory.php:392
+msgid "Finding:"
+msgstr "Ergebnisse:"
-#: ../../Zotlabs/Module/Settings/Account.php:116
-msgid "Your technical skill level"
-msgstr "Deine technische Qualifikationsstufe"
+#: ../../Zotlabs/Module/Directory.php:395 ../../Zotlabs/Module/Suggest.php:64
+#: ../../include/contact_widgets.php:24
+msgid "Channel Suggestions"
+msgstr "Kanal-Vorschläge"
-#: ../../Zotlabs/Module/Settings/Account.php:116
-msgid "Used to provide a member experience matched to your comfort level"
-msgstr "Dies wird verwendet, um Dir eine Benutzererfahrung passend zu Deiner technischen Qualifikationsstufe zu bieten."
+#: ../../Zotlabs/Module/Directory.php:397
+msgid "next page"
+msgstr "nächste Seite"
-#: ../../Zotlabs/Module/Settings/Account.php:119
-#: ../../Zotlabs/Module/Settings/Channel.php:462
-msgid "Email Address:"
-msgstr "Email Adresse:"
+#: ../../Zotlabs/Module/Directory.php:397
+msgid "previous page"
+msgstr "vorherige Seite"
-#: ../../Zotlabs/Module/Settings/Account.php:121
-msgid "Remove this account including all its channels"
-msgstr "Dieses Konto inklusive all seiner Kanäle löschen"
+#: ../../Zotlabs/Module/Directory.php:398
+msgid "Sort options"
+msgstr "Sortieroptionen"
-#: ../../Zotlabs/Module/Settings/Channel.php:246
-#: ../../extend/addon/addon/logrot/logrot.php:54
-#: ../../extend/addon/addon/msgfooter/msgfooter.php:54
-#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:184
-#: ../../extend/addon/addon/piwik/piwik.php:116
-#: ../../extend/addon/addon/twitter/twitter.php:766
-#: ../../extend/addon/addon/xmpp/xmpp.php:102
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:82
-msgid "Settings updated."
-msgstr "Einstellungen aktualisiert."
+#: ../../Zotlabs/Module/Directory.php:399
+msgid "Alphabetic"
+msgstr "alphabetisch"
-#: ../../Zotlabs/Module/Settings/Channel.php:307
-msgid "Nobody except yourself"
-msgstr "Niemand außer Dir selbst"
+#: ../../Zotlabs/Module/Directory.php:400
+msgid "Reverse Alphabetic"
+msgstr "Entgegengesetzt alphabetisch"
-#: ../../Zotlabs/Module/Settings/Channel.php:308
-msgid "Only those you specifically allow"
-msgstr "Nur die, denen Du es explizit erlaubst"
+#: ../../Zotlabs/Module/Directory.php:401
+msgid "Newest to Oldest"
+msgstr "Neueste zuerst"
-#: ../../Zotlabs/Module/Settings/Channel.php:309
-msgid "Approved connections"
-msgstr "Angenommene Verbindungen"
+#: ../../Zotlabs/Module/Directory.php:402
+msgid "Oldest to Newest"
+msgstr "Älteste zuerst"
-#: ../../Zotlabs/Module/Settings/Channel.php:310
-msgid "Any connections"
-msgstr "Beliebige Verbindungen"
+#: ../../Zotlabs/Module/Directory.php:419
+msgid "No entries (some entries may be hidden)."
+msgstr "Keine Einträge gefunden (einige könnten versteckt sein)."
-#: ../../Zotlabs/Module/Settings/Channel.php:311
-msgid "Anybody on this website"
-msgstr "Jeder auf dieser Website"
+#: ../../Zotlabs/Module/Xchan.php:10
+msgid "Xchan Lookup"
+msgstr "Xchan-Suche"
-#: ../../Zotlabs/Module/Settings/Channel.php:312
-msgid "Anybody in this network"
-msgstr "Alle $Projectname-Mitglieder"
+#: ../../Zotlabs/Module/Xchan.php:13
+msgid "Lookup xchan beginning with (or webbie): "
+msgstr "Nach xchans oder Webbies (Kanal-Adressen) suchen, die wie folgt beginnen:"
-#: ../../Zotlabs/Module/Settings/Channel.php:313
-msgid "Anybody authenticated"
-msgstr "Jeder authentifizierte"
+#: ../../Zotlabs/Module/Suggest.php:39
+msgid ""
+"No suggestions available. If this is a new site, please try again in 24 "
+"hours."
+msgstr "Keine Vorschläge vorhanden. Wenn das ein neuer Server ist, versuche es in 24 Stunden noch einmal."
-#: ../../Zotlabs/Module/Settings/Channel.php:314
-msgid "Anybody on the internet"
-msgstr "Jeder im Internet"
+#: ../../Zotlabs/Module/Suggest.php:58 ../../Zotlabs/Widget/Suggestions.php:46
+msgid "Ignore/Hide"
+msgstr "Ignorieren/Verstecken"
-#: ../../Zotlabs/Module/Settings/Channel.php:390
-msgid "Publish your default profile in the network directory"
-msgstr "Standard-Profil im Netzwerk-Verzeichnis veröffentlichen"
+#: ../../Zotlabs/Module/Oexchange.php:27
+msgid "Unable to find your hub."
+msgstr "Konnte Deinen Server nicht finden."
-#: ../../Zotlabs/Module/Settings/Channel.php:395
-msgid "Allow us to suggest you as a potential friend to new members?"
-msgstr "Dürfen wir Dich neuen Mitgliedern als potentiellen Kontakt vorschlagen?"
+#: ../../Zotlabs/Module/Oexchange.php:41
+msgid "Post successful."
+msgstr "Veröffentlichung erfolgreich."
-#: ../../Zotlabs/Module/Settings/Channel.php:404
-msgid "Your channel address is"
-msgstr "Deine Kanal-Adresse lautet"
+#: ../../Zotlabs/Module/Mail.php:73
+msgid "Unable to lookup recipient."
+msgstr "Konnte den Empfänger nicht finden."
-#: ../../Zotlabs/Module/Settings/Channel.php:407
-msgid "Your files/photos are accessible via WebDAV at"
-msgstr "Deine Dateien/Fotos sind via WebDAV verfügbar auf"
+#: ../../Zotlabs/Module/Mail.php:80
+msgid "Unable to communicate with requested channel."
+msgstr "Die Kommunikation mit dem ausgewählten Kanal ist fehlgeschlagen."
-#: ../../Zotlabs/Module/Settings/Channel.php:453
-msgid "Channel Settings"
-msgstr "Kanal-Einstellungen"
+#: ../../Zotlabs/Module/Mail.php:87
+msgid "Cannot verify requested channel."
+msgstr "Verifizierung des angeforderten Kanals fehlgeschlagen."
-#: ../../Zotlabs/Module/Settings/Channel.php:460
-msgid "Basic Settings"
-msgstr "Grundeinstellungen"
+#: ../../Zotlabs/Module/Mail.php:105
+msgid "Selected channel has private message restrictions. Send failed."
+msgstr "Der ausgewählte Kanal hat Einschränkungen bzgl. privater Nachrichten. Senden fehlgeschlagen."
-#: ../../Zotlabs/Module/Settings/Channel.php:461
-#: ../../include/channel.php:1172
-msgid "Full Name:"
-msgstr "Voller Name:"
+#: ../../Zotlabs/Module/Mail.php:160
+msgid "Messages"
+msgstr "Nachrichten"
-#: ../../Zotlabs/Module/Settings/Channel.php:463
-msgid "Your Timezone:"
-msgstr "Ihre Zeitzone:"
+#: ../../Zotlabs/Module/Mail.php:173
+msgid "message"
+msgstr "Nachricht"
-#: ../../Zotlabs/Module/Settings/Channel.php:464
-msgid "Default Post Location:"
-msgstr "Standardstandort:"
+#: ../../Zotlabs/Module/Mail.php:214
+msgid "Message recalled."
+msgstr "Nachricht widerrufen."
-#: ../../Zotlabs/Module/Settings/Channel.php:464
-msgid "Geographical location to display on your posts"
-msgstr "Geografischer Ort, der bei Deinen Beiträgen angezeigt werden soll"
+#: ../../Zotlabs/Module/Mail.php:227
+msgid "Conversation removed."
+msgstr "Unterhaltung gelöscht."
-#: ../../Zotlabs/Module/Settings/Channel.php:465
-msgid "Use Browser Location:"
-msgstr "Standort des Browsers verwenden:"
+#: ../../Zotlabs/Module/Mail.php:242 ../../Zotlabs/Module/Mail.php:363
+msgid "Expires YYYY-MM-DD HH:MM"
+msgstr "Verfällt YYYY-MM-DD HH;MM"
-#: ../../Zotlabs/Module/Settings/Channel.php:467
-msgid "Adult Content"
-msgstr "Nicht jugendfreie Inhalte"
+#: ../../Zotlabs/Module/Mail.php:270
+msgid "Requested channel is not in this network"
+msgstr "Angeforderter Kanal ist nicht in diesem Netzwerk."
-#: ../../Zotlabs/Module/Settings/Channel.php:467
-msgid ""
-"This channel frequently or regularly publishes adult content. (Please tag "
-"any adult material and/or nudity with #NSFW)"
-msgstr "Dieser Kanal veröffentlicht regelmäßig Inhalte, die für Minderjährige ungeeignet sind. (Bitte markiere solche Inhalte mit dem Schlagwort #NSFW)"
+#: ../../Zotlabs/Module/Mail.php:278
+msgid "Send Private Message"
+msgstr "Private Nachricht senden"
-#: ../../Zotlabs/Module/Settings/Channel.php:469
-msgid "Security and Privacy Settings"
-msgstr "Sicherheits- und Datenschutz-Einstellungen"
+#: ../../Zotlabs/Module/Mail.php:279 ../../Zotlabs/Module/Mail.php:421
+msgid "To:"
+msgstr "An:"
-#: ../../Zotlabs/Module/Settings/Channel.php:472
-msgid "Your permissions are already configured. Click to view/adjust"
-msgstr "Deine Zugriffsrechte sind schon konfiguriert. Klicke hier, um sie zu betrachten oder zu ändern"
+#: ../../Zotlabs/Module/Mail.php:282 ../../Zotlabs/Module/Mail.php:423
+msgid "Subject:"
+msgstr "Betreff:"
-#: ../../Zotlabs/Module/Settings/Channel.php:474
-msgid "Hide my online presence"
-msgstr "Meine Online-Präsenz verbergen"
+#: ../../Zotlabs/Module/Mail.php:287 ../../Zotlabs/Module/Mail.php:429
+#: ../../include/conversation.php:1365
+msgid "Attach file"
+msgstr "Datei anhängen"
-#: ../../Zotlabs/Module/Settings/Channel.php:474
-msgid "Prevents displaying in your profile that you are online"
-msgstr "Verhindert die Anzeige Deines Online-Status in deinem Profil"
+#: ../../Zotlabs/Module/Mail.php:289
+msgid "Send"
+msgstr "Absenden"
-#: ../../Zotlabs/Module/Settings/Channel.php:476
-msgid "Simple Privacy Settings:"
-msgstr "Einfache Privatsphäre-Einstellungen"
+#: ../../Zotlabs/Module/Mail.php:292 ../../Zotlabs/Module/Mail.php:434
+#: ../../include/conversation.php:1410
+msgid "Set expiration date"
+msgstr "Verfallsdatum"
-#: ../../Zotlabs/Module/Settings/Channel.php:477
-msgid ""
-"Very Public - <em>extremely permissive (should be used with caution)</em>"
-msgstr "Komplett offen – <em>extrem ungeschützt (mit großer Vorsicht verwenden!)</em>"
+#: ../../Zotlabs/Module/Mail.php:393
+msgid "Delete message"
+msgstr "Nachricht löschen"
-#: ../../Zotlabs/Module/Settings/Channel.php:478
-msgid ""
-"Typical - <em>default public, privacy when desired (similar to social "
-"network permissions but with improved privacy)</em>"
-msgstr "Typisch – <em>Standard öffentlich, Privatsphäre, wo sie erwünscht ist (ähnlich den Einstellungen in sozialen Netzwerken, aber mit besser geschützter Privatsphäre)</em>"
+#: ../../Zotlabs/Module/Mail.php:394
+msgid "Delivery report"
+msgstr "Zustellungsbericht"
-#: ../../Zotlabs/Module/Settings/Channel.php:479
-msgid "Private - <em>default private, never open or public</em>"
-msgstr "Privat – <em>Standard privat, nie offen oder öffentlich</em>"
+#: ../../Zotlabs/Module/Mail.php:395
+msgid "Recall message"
+msgstr "Nachricht widerrufen"
-#: ../../Zotlabs/Module/Settings/Channel.php:480
-msgid "Blocked - <em>default blocked to/from everybody</em>"
-msgstr "Blockiert – <em>Alle standardmäßig blockiert</em>"
+#: ../../Zotlabs/Module/Mail.php:397
+msgid "Message has been recalled."
+msgstr "Die Nachricht wurde widerrufen."
-#: ../../Zotlabs/Module/Settings/Channel.php:482
-msgid "Allow others to tag your posts"
-msgstr "Erlaube anderen, Deine Beiträge zu verschlagworten"
+#: ../../Zotlabs/Module/Mail.php:414
+msgid "Delete Conversation"
+msgstr "Unterhaltung löschen"
-#: ../../Zotlabs/Module/Settings/Channel.php:482
+#: ../../Zotlabs/Module/Mail.php:416
msgid ""
-"Often used by the community to retro-actively flag inappropriate content"
-msgstr "Wird oft von der Community genutzt um rückwirkend anstößigen Inhalt zu markieren"
-
-#: ../../Zotlabs/Module/Settings/Channel.php:484
-msgid "Channel Permission Limits"
-msgstr "Kanal-Berechtigungslimits"
-
-#: ../../Zotlabs/Module/Settings/Channel.php:486
-msgid "Expire other channel content after this many days"
-msgstr "Den Inhalt anderer Kanäle nach dieser Anzahl Tage verfallen lassen"
+"No secure communications available. You <strong>may</strong> be able to "
+"respond from the sender's profile page."
+msgstr "Keine sichere Kommunikation verfügbar. <strong>Eventuell</strong> kannst Du auf der Profilseite des Absenders antworten."
-#: ../../Zotlabs/Module/Settings/Channel.php:486
-msgid "0 or blank to use the website limit."
-msgstr "0 oder leer lassen, um den voreingestellten Wert der Webseite zu verwenden."
+#: ../../Zotlabs/Module/Mail.php:420
+msgid "Send Reply"
+msgstr "Antwort senden"
-#: ../../Zotlabs/Module/Settings/Channel.php:486
+#: ../../Zotlabs/Module/Mail.php:425
#, php-format
-msgid "This website expires after %d days."
-msgstr "Diese Webseite läuft nach %d Tagen ab."
-
-#: ../../Zotlabs/Module/Settings/Channel.php:486
-msgid "This website does not expire imported content."
-msgstr "Diese Webseite lässt importierte Inhalte nicht verfallen."
-
-#: ../../Zotlabs/Module/Settings/Channel.php:486
-msgid "The website limit takes precedence if lower than your limit."
-msgstr "Das Verfallslimit der Webseite hat Vorrang, wenn es niedriger als Deines hier ist."
-
-#: ../../Zotlabs/Module/Settings/Channel.php:487
-msgid "Maximum Friend Requests/Day:"
-msgstr "Maximale Kontaktanfragen pro Tag:"
-
-#: ../../Zotlabs/Module/Settings/Channel.php:487
-msgid "May reduce spam activity"
-msgstr "Kann die Spam-Aktivität verringern"
-
-#: ../../Zotlabs/Module/Settings/Channel.php:488
-msgid "Default Access Control List (ACL)"
-msgstr "Standard-Zugriffsberechtigungsliste (ACL)"
-
-#: ../../Zotlabs/Module/Settings/Channel.php:490
-msgid "Use my default audience setting for the type of object published"
-msgstr "Verwende Deine eingestellte Standard-Zielgruppe des jeweiligen Inhaltstyps"
-
-#: ../../Zotlabs/Module/Settings/Channel.php:497
-msgid "Channel permissions category:"
-msgstr "Zugriffsrechte-Kategorie des Kanals:"
-
-#: ../../Zotlabs/Module/Settings/Channel.php:503
-msgid "Maximum private messages per day from unknown people:"
-msgstr "Maximale Anzahl privater Nachrichten pro Tag von unbekannten Leuten:"
-
-#: ../../Zotlabs/Module/Settings/Channel.php:503
-msgid "Useful to reduce spamming"
-msgstr "Nützlich, um Spam zu verringern"
-
-#: ../../Zotlabs/Module/Settings/Channel.php:506
-msgid "Notification Settings"
-msgstr "Benachrichtigungs-Einstellungen"
-
-#: ../../Zotlabs/Module/Settings/Channel.php:507
-msgid "By default post a status message when:"
-msgstr "Sende standardmäßig Status-Nachrichten, wenn:"
-
-#: ../../Zotlabs/Module/Settings/Channel.php:508
-msgid "accepting a friend request"
-msgstr "Du eine Verbindungsanfrage annimmst"
-
-#: ../../Zotlabs/Module/Settings/Channel.php:509
-msgid "joining a forum/community"
-msgstr "Du einem Forum beitrittst"
-
-#: ../../Zotlabs/Module/Settings/Channel.php:510
-msgid "making an <em>interesting</em> profile change"
-msgstr "Du eine <em>interessante</em> Änderung an Deinem Profil vornimmst"
+msgid "Your message for %s (%s):"
+msgstr "Deine Nachricht für %s (%s):"
-#: ../../Zotlabs/Module/Settings/Channel.php:511
-msgid "Send a notification email when:"
-msgstr "Eine E-Mail-Benachrichtigung senden, wenn:"
+#: ../../Zotlabs/Module/Pubsites.php:24 ../../Zotlabs/Widget/Pubsites.php:12
+msgid "Public Hubs"
+msgstr "Öffentliche Hubs"
-#: ../../Zotlabs/Module/Settings/Channel.php:512
-msgid "You receive a connection request"
-msgstr "Du eine Verbindungsanfrage erhältst"
+#: ../../Zotlabs/Module/Pubsites.php:27
+msgid ""
+"The listed hubs allow public registration for the $Projectname network. All "
+"hubs in the network are interlinked so membership on any of them conveys "
+"membership in the network as a whole. Some hubs may require subscription or "
+"provide tiered service plans. The hub itself <strong>may</strong> provide "
+"additional details."
+msgstr "Die hier aufgeführten Hubs sind öffentlich und erlauben die Registrierung im $Projectname Netzwerk. Alle Hubs dieses Netzwerks sind miteinander verbunden, so dass die Mitgliedschaft auf einem Hub die Verbindung zu beliebigen Seiten und Kanälen auf anderen Hubs ermöglicht. Es könnte sein, dass einige dieser Hubs kostenpflichtig sind oder abgestufte, je nach Umfang kostenpflichtige Mitgliedschaften anbieten. Auf den Seiten der einzelnen Hubs <strong>könnten</strong> jeweils nähere Informationen dazu stehen."
-#: ../../Zotlabs/Module/Settings/Channel.php:513
-msgid "Your connections are confirmed"
-msgstr "Eine Verbindung bestätigt wurde"
+#: ../../Zotlabs/Module/Pubsites.php:33
+msgid "Hub URL"
+msgstr "Hub-URL"
-#: ../../Zotlabs/Module/Settings/Channel.php:514
-msgid "Someone writes on your profile wall"
-msgstr "Jemand auf Deine Pinnwand schreibt"
+#: ../../Zotlabs/Module/Pubsites.php:33
+msgid "Access Type"
+msgstr "Zugriffstyp"
-#: ../../Zotlabs/Module/Settings/Channel.php:515
-msgid "Someone writes a followup comment"
-msgstr "Jemand einen Beitrag kommentiert"
+#: ../../Zotlabs/Module/Pubsites.php:33
+msgid "Registration Policy"
+msgstr "Registrierungsrichtlinien"
-#: ../../Zotlabs/Module/Settings/Channel.php:516
-msgid "You receive a private message"
-msgstr "Du eine private Nachricht erhältst"
+#: ../../Zotlabs/Module/Pubsites.php:33
+msgid "Stats"
+msgstr "Statistiken"
-#: ../../Zotlabs/Module/Settings/Channel.php:517
-msgid "You receive a friend suggestion"
-msgstr "Du einen Kontaktvorschlag erhältst"
+#: ../../Zotlabs/Module/Pubsites.php:33
+msgid "Software"
+msgstr "Software"
-#: ../../Zotlabs/Module/Settings/Channel.php:518
-msgid "You are tagged in a post"
-msgstr "Du in einem Beitrag erwähnt wurdest"
+#: ../../Zotlabs/Module/Pubsites.php:49
+msgid "Rate"
+msgstr "Bewerten"
-#: ../../Zotlabs/Module/Settings/Channel.php:519
-msgid "You are poked/prodded/etc. in a post"
-msgstr "Du in einem Beitrag angestupst/geknufft/o.ä. wurdest"
+#: ../../Zotlabs/Module/Impel.php:41 ../../include/bbcode.php:263
+msgid "webpage"
+msgstr "Webseite"
-#: ../../Zotlabs/Module/Settings/Channel.php:522
-msgid "Show visual notifications including:"
-msgstr "Visuelle Benachrichtigungen anzeigen für:"
+#: ../../Zotlabs/Module/Impel.php:46 ../../include/bbcode.php:269
+msgid "block"
+msgstr "Block"
-#: ../../Zotlabs/Module/Settings/Channel.php:524
-msgid "Unseen grid activity"
-msgstr "Ungesehene Netzwerk-Aktivität"
+#: ../../Zotlabs/Module/Impel.php:51 ../../include/bbcode.php:266
+msgid "layout"
+msgstr "Layout"
-#: ../../Zotlabs/Module/Settings/Channel.php:525
-msgid "Unseen channel activity"
-msgstr "Ungesehene Kanal-Aktivität"
+#: ../../Zotlabs/Module/Impel.php:58 ../../include/bbcode.php:272
+msgid "menu"
+msgstr "Menü"
-#: ../../Zotlabs/Module/Settings/Channel.php:526
-msgid "Unseen private messages"
-msgstr "Ungelesene persönliche Nachrichten"
+#: ../../Zotlabs/Module/Impel.php:181
+#, php-format
+msgid "%s element installed"
+msgstr "Element für %s installiert"
-#: ../../Zotlabs/Module/Settings/Channel.php:526
-#: ../../Zotlabs/Module/Settings/Channel.php:531
-#: ../../Zotlabs/Module/Settings/Channel.php:532
-#: ../../Zotlabs/Module/Settings/Channel.php:533
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:343
-msgid "Recommended"
-msgstr "Empfohlen"
+#: ../../Zotlabs/Module/Impel.php:184
+#, php-format
+msgid "%s element installation failed"
+msgstr "Installation des Elements %s fehlgeschlagen"
-#: ../../Zotlabs/Module/Settings/Channel.php:527
-msgid "Upcoming events"
-msgstr "Baldige Termine"
+#: ../../Zotlabs/Module/Rbmark.php:94
+msgid "Select a bookmark folder"
+msgstr "Lesezeichenordner wählen"
-#: ../../Zotlabs/Module/Settings/Channel.php:528
-msgid "Events today"
-msgstr "Heutige Termine"
+#: ../../Zotlabs/Module/Rbmark.php:99
+msgid "Save Bookmark"
+msgstr "Lesezeichen speichern"
-#: ../../Zotlabs/Module/Settings/Channel.php:529
-msgid "Upcoming birthdays"
-msgstr "Baldige Geburtstage"
+#: ../../Zotlabs/Module/Rbmark.php:100
+msgid "URL of bookmark"
+msgstr "URL des Lesezeichens"
-#: ../../Zotlabs/Module/Settings/Channel.php:529
-msgid "Not available in all themes"
-msgstr "Nicht in allen Themes verfügbar"
+#: ../../Zotlabs/Module/Rbmark.php:105
+msgid "Or enter new bookmark folder name"
+msgstr "Oder gib einen neuen Namen für den Lesezeichenordner ein"
-#: ../../Zotlabs/Module/Settings/Channel.php:530
-msgid "System (personal) notifications"
-msgstr "System – (persönliche) Benachrichtigungen"
+#: ../../Zotlabs/Module/Filer.php:52
+msgid "Enter a folder name"
+msgstr "Gib einen Ordnernamen ein"
-#: ../../Zotlabs/Module/Settings/Channel.php:531
-msgid "System info messages"
-msgstr "System – Info-Nachrichten"
+#: ../../Zotlabs/Module/Filer.php:52
+msgid "or select an existing folder (doubleclick)"
+msgstr "oder wähle einen vorhanden Ordner aus (Doppelklick)"
-#: ../../Zotlabs/Module/Settings/Channel.php:532
-msgid "System critical alerts"
-msgstr "System – kritische Warnungen"
+#: ../../Zotlabs/Module/Filer.php:54 ../../Zotlabs/Lib/ThreadItem.php:141
+msgid "Save to Folder"
+msgstr "In Ordner speichern"
-#: ../../Zotlabs/Module/Settings/Channel.php:533
-msgid "New connections"
-msgstr "Neue Verbindungen"
+#: ../../Zotlabs/Module/Probe.php:30 ../../Zotlabs/Module/Probe.php:34
+#, php-format
+msgid "Fetching URL returns error: %1$s"
+msgstr "Abrufen der URL gab einen Fehler zurück: %1$s"
-#: ../../Zotlabs/Module/Settings/Channel.php:534
-msgid "System Registrations"
-msgstr "System – Registrierungen"
+#: ../../Zotlabs/Module/Register.php:49
+msgid "Maximum daily site registrations exceeded. Please try again tomorrow."
+msgstr "Maximale Anzahl täglicher Neuanmeldungen erreicht. Bitte versuche es morgen noch einmal."
-#: ../../Zotlabs/Module/Settings/Channel.php:535
+#: ../../Zotlabs/Module/Register.php:55
msgid ""
-"Also show new wall posts, private messages and connections under Notices"
-msgstr "Neue Pinnwand-Nachrichten, private Nachrichten und Verbindungen unter Benachrichtigungen anzeigen"
-
-#: ../../Zotlabs/Module/Settings/Channel.php:537
-msgid "Notify me of events this many days in advance"
-msgstr "Benachrichtige mich zu Terminen so viele Tage im Voraus"
-
-#: ../../Zotlabs/Module/Settings/Channel.php:537
-msgid "Must be greater than 0"
-msgstr "Muss größer als 0 sein"
-
-#: ../../Zotlabs/Module/Settings/Channel.php:539
-msgid "Advanced Account/Page Type Settings"
-msgstr "Erweiterte Account- und Seitenart-Einstellungen"
-
-#: ../../Zotlabs/Module/Settings/Channel.php:540
-msgid "Change the behaviour of this account for special situations"
-msgstr "Ändere das Verhalten dieses Accounts unter speziellen Umständen"
+"Please indicate acceptance of the Terms of Service. Registration failed."
+msgstr "Bitte stimme den Nutzungsbedingungen zu. Registrierung fehlgeschlagen."
-#: ../../Zotlabs/Module/Settings/Channel.php:542
-msgid "Miscellaneous Settings"
-msgstr "Sonstige Einstellungen"
+#: ../../Zotlabs/Module/Register.php:89
+msgid "Passwords do not match."
+msgstr "Passwörter stimmen nicht überein."
-#: ../../Zotlabs/Module/Settings/Channel.php:543
-msgid "Default photo upload folder"
-msgstr "Voreingestellter Ordner für hochgeladene Fotos"
+#: ../../Zotlabs/Module/Register.php:131
+msgid ""
+"Registration successful. Please check your email for validation "
+"instructions."
+msgstr "Registrierung erfolgreich. Eine E-Mail mit weiteren Anweisungen wurde an Dich gesendet."
-#: ../../Zotlabs/Module/Settings/Channel.php:543
-#: ../../Zotlabs/Module/Settings/Channel.php:544
-msgid "%Y - current year, %m - current month"
-msgstr "%Y - aktuelles Jahr, %m - aktueller Monat"
+#: ../../Zotlabs/Module/Register.php:137
+msgid "Your registration is pending approval by the site owner."
+msgstr "Deine Registrierung muss noch vom Betreiber der Seite freigegeben werden."
-#: ../../Zotlabs/Module/Settings/Channel.php:544
-msgid "Default file upload folder"
-msgstr "Voreingestellter Ordner für hochgeladene Dateien"
+#: ../../Zotlabs/Module/Register.php:140
+msgid "Your registration can not be processed."
+msgstr "Deine Registrierung konnte nicht verarbeitet werden."
-#: ../../Zotlabs/Module/Settings/Channel.php:546
-msgid "Personal menu to display in your channel pages"
-msgstr "Eigenes Menü zur Anzeige auf den Seiten deines Kanals"
+#: ../../Zotlabs/Module/Register.php:184
+msgid "Registration on this hub is disabled."
+msgstr "Die Registrierung auf diesem Hub ist nicht möglich."
-#: ../../Zotlabs/Module/Settings/Channel.php:548
-msgid "Remove this channel."
-msgstr "Diesen Kanal löschen"
+#: ../../Zotlabs/Module/Register.php:193
+msgid "Registration on this hub is by approval only."
+msgstr "Eine Registrierung auf diesem Hub erfordert die Zustimmung durch den Administrator."
-#: ../../Zotlabs/Module/Settings/Channel.php:549
-msgid "Firefox Share $Projectname provider"
-msgstr "$Projectname-Provider für Firefox Share"
+#: ../../Zotlabs/Module/Register.php:194
+msgid "<a href=\"pubsites\">Register at another affiliated hub.</a>"
+msgstr "<a href=\"pubsites\">Registriere Dich auf einem der anderen verbundenen Hubs.</a>"
-#: ../../Zotlabs/Module/Settings/Channel.php:550
-msgid "Start calendar week on monday"
-msgstr "Montag als erster Tag der Kalenderwoche"
+#: ../../Zotlabs/Module/Register.php:204
+msgid ""
+"This site has exceeded the number of allowed daily account registrations. "
+"Please try again tomorrow."
+msgstr "Die maximale Anzahl täglicher Registrierungen auf diesem Server wurde überschritten. Bitte versuche es morgen noch einmal."
-#: ../../Zotlabs/Module/Settings/Display.php:137
-msgid "No special theme for mobile devices"
-msgstr "Keine spezielle Theme für mobile Geräte"
+#: ../../Zotlabs/Module/Register.php:227
+#, php-format
+msgid "I accept the %s for this website"
+msgstr "Ich akzeptiere die %s für diese Webseite"
-#: ../../Zotlabs/Module/Settings/Display.php:140
+#: ../../Zotlabs/Module/Register.php:229
#, php-format
-msgid "%s - (Experimental)"
-msgstr "%s – (experimentell)"
+msgid "I am over 13 years of age and accept the %s for this website"
+msgstr "Ich bin älter als 13 Jahre und akzeptiere die %s dieser Webseite"
-#: ../../Zotlabs/Module/Settings/Display.php:191
-msgid "Display Settings"
-msgstr "Anzeige-Einstellungen"
+#: ../../Zotlabs/Module/Register.php:233
+msgid "Your email address"
+msgstr "Ihre E-Mail Adresse"
-#: ../../Zotlabs/Module/Settings/Display.php:192
-msgid "Theme Settings"
-msgstr "Theme-Einstellungen"
+#: ../../Zotlabs/Module/Register.php:234
+msgid "Choose a password"
+msgstr "Passwort"
-#: ../../Zotlabs/Module/Settings/Display.php:193
-msgid "Custom Theme Settings"
-msgstr "Benutzerdefinierte Theme-Einstellungen"
+#: ../../Zotlabs/Module/Register.php:235
+msgid "Please re-enter your password"
+msgstr "Bitte gib Dein Passwort noch einmal ein"
-#: ../../Zotlabs/Module/Settings/Display.php:194
-msgid "Content Settings"
-msgstr "Inhaltseinstellungen"
+#: ../../Zotlabs/Module/Register.php:236
+msgid "Please enter your invitation code"
+msgstr "Bitte trage Deinen Einladungs-Code ein"
-#: ../../Zotlabs/Module/Settings/Display.php:200
-msgid "Display Theme:"
-msgstr "Anzeige-Theme:"
+#: ../../Zotlabs/Module/Register.php:241
+msgid "no"
+msgstr "nein"
-#: ../../Zotlabs/Module/Settings/Display.php:201
-msgid "Select scheme"
-msgstr "Schema wählen"
+#: ../../Zotlabs/Module/Register.php:241
+msgid "yes"
+msgstr "ja"
-#: ../../Zotlabs/Module/Settings/Display.php:203
-msgid "Mobile Theme:"
-msgstr "Mobile Theme:"
+#: ../../Zotlabs/Module/Register.php:256
+msgid "Membership on this site is by invitation only."
+msgstr "Mitgliedschaft auf dieser Seite ist nur nach vorheriger Einladung möglich."
-#: ../../Zotlabs/Module/Settings/Display.php:204
-msgid "Preload images before rendering the page"
-msgstr "Bilder im voraus laden, bevor die Seite angezeigt wird"
+#: ../../Zotlabs/Module/Register.php:268 ../../boot.php:1620
+#: ../../include/nav.php:189
+msgid "Register"
+msgstr "Registrieren"
-#: ../../Zotlabs/Module/Settings/Display.php:204
+#: ../../Zotlabs/Module/Register.php:269
msgid ""
-"The subjective page load time will be longer but the page will be ready when"
-" displayed"
-msgstr "Die empfundene Ladezeit wird sich erhöhen, aber dafür ist das Layout stabil, sobald eine Seite angezeigt wird"
-
-#: ../../Zotlabs/Module/Settings/Display.php:205
-msgid "Enable user zoom on mobile devices"
-msgstr "Zoom auf Mobilgeräten aktivieren"
-
-#: ../../Zotlabs/Module/Settings/Display.php:206
-msgid "Update browser every xx seconds"
-msgstr "Browser alle xx Sekunden aktualisieren"
+"This site may require email verification after submitting this form. If you "
+"are returned to a login page, please check your email for instructions."
+msgstr "Diese Seite verlangt möglicherweise eine Emailbestätigung nach dem Absenden des Formulars. Wenn Du auf eine Login-Seite zurückgeleitet wirst, prüfe bitte Deinen Posteingang auf neue Mails mit entsprechenden Hinweisen."
-#: ../../Zotlabs/Module/Settings/Display.php:206
-msgid "Minimum of 10 seconds, no maximum"
-msgstr "Minimum 10 Sekunden, kein Maximum"
+#: ../../Zotlabs/Module/Cover_photo.php:136
+#: ../../Zotlabs/Module/Cover_photo.php:186
+msgid "Cover Photos"
+msgstr "Cover Foto"
-#: ../../Zotlabs/Module/Settings/Display.php:207
-msgid "Maximum number of conversations to load at any time:"
-msgstr "Maximale Anzahl von Unterhaltungen, die auf einmal geladen werden sollen:"
+#: ../../Zotlabs/Module/Cover_photo.php:237 ../../include/items.php:4320
+msgid "female"
+msgstr "weiblich"
-#: ../../Zotlabs/Module/Settings/Display.php:207
-msgid "Maximum of 100 items"
-msgstr "Maximum: 100 Beiträge"
+#: ../../Zotlabs/Module/Cover_photo.php:238 ../../include/items.php:4321
+#, php-format
+msgid "%1$s updated her %2$s"
+msgstr "%1$s hat ihr %2$s aktualisiert"
-#: ../../Zotlabs/Module/Settings/Display.php:208
-msgid "Show emoticons (smilies) as images"
-msgstr "Emoticons (Smilies) als Bilder anzeigen"
+#: ../../Zotlabs/Module/Cover_photo.php:239 ../../include/items.php:4322
+msgid "male"
+msgstr "männlich"
-#: ../../Zotlabs/Module/Settings/Display.php:209
-msgid "Manual conversation updates"
-msgstr "Manuelle Konversationsaktualisierung"
+#: ../../Zotlabs/Module/Cover_photo.php:240 ../../include/items.php:4323
+#, php-format
+msgid "%1$s updated his %2$s"
+msgstr "%1$s hat sein %2$s aktualisiert"
-#: ../../Zotlabs/Module/Settings/Display.php:209
-msgid "Default is automatic, which may increase screen jumping"
-msgstr "Voreinstellung ist Automatisch, was aber das Springen der Seitenanzeige erhöhen kann."
+#: ../../Zotlabs/Module/Cover_photo.php:242 ../../include/items.php:4325
+#, php-format
+msgid "%1$s updated their %2$s"
+msgstr "%1$s hat sein/ihr %2$s aktualisiert"
-#: ../../Zotlabs/Module/Settings/Display.php:210
-msgid "Link post titles to source"
-msgstr "Beitragstitel zum Originalbeitrag verlinken"
+#: ../../Zotlabs/Module/Cover_photo.php:244 ../../include/channel.php:1980
+msgid "cover photo"
+msgstr "Cover Foto"
-#: ../../Zotlabs/Module/Settings/Display.php:211
-msgid "System Page Layout Editor - (advanced)"
-msgstr "System-Seitenlayout-Editor (für Experten)"
+#: ../../Zotlabs/Module/Cover_photo.php:360
+msgid "Upload Cover Photo"
+msgstr "Cover Foto hochladen"
-#: ../../Zotlabs/Module/Settings/Display.php:214
-msgid "Use blog/list mode on channel page"
-msgstr "Blog-/Listenmodus auf der Kanalseite verwenden"
+#: ../../Zotlabs/Module/Help.php:23
+msgid "Documentation Search"
+msgstr "Suche in der Dokumentation"
-#: ../../Zotlabs/Module/Settings/Display.php:214
-#: ../../Zotlabs/Module/Settings/Display.php:215
-msgid "(comments displayed separately)"
-msgstr "(Kommentare werden separat angezeigt)"
+#: ../../Zotlabs/Module/Help.php:80 ../../include/conversation.php:1804
+#: ../../include/nav.php:412
+msgid "About"
+msgstr "Über"
-#: ../../Zotlabs/Module/Settings/Display.php:215
-msgid "Use blog/list mode on grid page"
-msgstr "Blog-/Listenmodus auf der Netzwerkseite verwenden"
+#: ../../Zotlabs/Module/Help.php:82
+msgid "Administrators"
+msgstr "Administratoren"
-#: ../../Zotlabs/Module/Settings/Display.php:216
-msgid "Channel page max height of content (in pixels)"
-msgstr "Maximale Höhe von Beitragsblöcken auf der Kanalseite (in Pixeln)"
+#: ../../Zotlabs/Module/Help.php:83
+msgid "Developers"
+msgstr "Entwickler"
-#: ../../Zotlabs/Module/Settings/Display.php:216
-#: ../../Zotlabs/Module/Settings/Display.php:217
-msgid "click to expand content exceeding this height"
-msgstr "Blöcke, deren Inhalt diese Höhe überschreitet, können per Klick vergrößert werden."
+#: ../../Zotlabs/Module/Help.php:84
+msgid "Tutorials"
+msgstr "Tutorials"
-#: ../../Zotlabs/Module/Settings/Display.php:217
-msgid "Grid page max height of content (in pixels)"
-msgstr "Maximale Höhe (in Pixel) des Inhalts der Netzwerkseite"
+#: ../../Zotlabs/Module/Help.php:95
+msgid "$Projectname Documentation"
+msgstr "$Projectname-Dokumentation"
-#: ../../Zotlabs/Module/Settings/Featured.php:24
-msgid "No feature settings configured"
-msgstr "Keine Funktions-Einstellungen konfiguriert"
+#: ../../Zotlabs/Module/Help.php:96
+msgid "Contents"
+msgstr "Inhalt"
-#: ../../Zotlabs/Module/Settings/Featured.php:31
-msgid "Feature/Addon Settings"
-msgstr "Funktions-/Addon-Einstellungen"
+#: ../../Zotlabs/Module/Display.php:340
+msgid "Item has been removed."
+msgstr "Der Beitrag wurde entfernt."
#: ../../Zotlabs/Module/Tagrm.php:48 ../../Zotlabs/Module/Tagrm.php:98
msgid "Tag removed"
@@ -6611,135 +7029,108 @@ msgstr "Schlagwort entfernen"
msgid "Select a tag to remove: "
msgstr "Schlagwort zum Entfernen auswählen:"
-#: ../../Zotlabs/Module/Thing.php:114
-msgid "Thing updated"
-msgstr "Sache aktualisiert"
-
-#: ../../Zotlabs/Module/Thing.php:166
-msgid "Object store: failed"
-msgstr "Speichern des Objekts fehlgeschlagen"
-
-#: ../../Zotlabs/Module/Thing.php:170
-msgid "Thing added"
-msgstr "Sache hinzugefügt"
-
-#: ../../Zotlabs/Module/Thing.php:196
-#, php-format
-msgid "OBJ: %1$s %2$s %3$s"
-msgstr "OBJ: %1$s %2$s %3$s"
-
-#: ../../Zotlabs/Module/Thing.php:259
-msgid "Show Thing"
-msgstr "Sache anzeigen"
+#: ../../Zotlabs/Module/Network.php:97
+msgid "No such group"
+msgstr "Gruppe nicht gefunden"
-#: ../../Zotlabs/Module/Thing.php:266
-msgid "item not found."
-msgstr "Eintrag nicht gefunden"
+#: ../../Zotlabs/Module/Network.php:136
+msgid "No such channel"
+msgstr "Kanal nicht gefunden"
-#: ../../Zotlabs/Module/Thing.php:299
-msgid "Edit Thing"
-msgstr "Sache bearbeiten"
+#: ../../Zotlabs/Module/Network.php:141
+msgid "forum"
+msgstr "Forum"
-#: ../../Zotlabs/Module/Thing.php:301 ../../Zotlabs/Module/Thing.php:355
-msgid "Select a profile"
-msgstr "Wähle ein Profil"
+#: ../../Zotlabs/Module/Network.php:153
+msgid "Search Results For:"
+msgstr "Suchergebnisse für:"
-#: ../../Zotlabs/Module/Thing.php:305 ../../Zotlabs/Module/Thing.php:358
-msgid "Post an activity"
-msgstr "Aktivitätsnachricht senden"
+#: ../../Zotlabs/Module/Network.php:221
+msgid "Privacy group is empty"
+msgstr "Gruppe ist leer"
-#: ../../Zotlabs/Module/Thing.php:305 ../../Zotlabs/Module/Thing.php:358
-msgid "Only sends to viewers of the applicable profile"
-msgstr "Nur an Betrachter des ausgewählten Profils senden"
+#: ../../Zotlabs/Module/Network.php:230
+msgid "Privacy group: "
+msgstr "Gruppe:"
-#: ../../Zotlabs/Module/Thing.php:307 ../../Zotlabs/Module/Thing.php:360
-msgid "Name of thing e.g. something"
-msgstr "Name der Sache, z. B. irgendwas"
+#: ../../Zotlabs/Module/Network.php:256
+msgid "Invalid connection."
+msgstr "Ungültige Verbindung."
-#: ../../Zotlabs/Module/Thing.php:309 ../../Zotlabs/Module/Thing.php:361
-msgid "URL of thing (optional)"
-msgstr "URL der Sache (optional)"
+#: ../../Zotlabs/Module/Network.php:275 ../../addon/redred/redred.php:65
+msgid "Invalid channel."
+msgstr "Ungültiger Kanal."
-#: ../../Zotlabs/Module/Thing.php:311 ../../Zotlabs/Module/Thing.php:362
-msgid "URL for photo of thing (optional)"
-msgstr "URL eines Fotos der Sache (optional)"
+#: ../../Zotlabs/Module/Acl.php:351
+msgid "network"
+msgstr "Netzwerk"
-#: ../../Zotlabs/Module/Thing.php:353
-msgid "Add Thing to your Profile"
-msgstr "Die Sache Deinem Profil hinzufügen"
+#: ../../Zotlabs/Module/Home.php:74 ../../Zotlabs/Module/Home.php:82
+#: ../../addon/opensearch/opensearch.php:42
+msgid "$Projectname"
+msgstr "$Projectname"
-#: ../../Zotlabs/Module/Import.php:33
+#: ../../Zotlabs/Module/Home.php:92
#, php-format
-msgid "Your service plan only allows %d channels."
-msgstr "Dein Vertrag erlaubt nur %d Kanäle."
+msgid "Welcome to %s"
+msgstr "Willkommen auf %s"
-#: ../../Zotlabs/Module/Import.php:157 ../../include/import.php:100
-msgid "Cloned channel not found. Import failed."
-msgstr "Geklonter Kanal nicht gefunden. Import fehlgeschlagen."
+#: ../../Zotlabs/Module/Filestorage.php:79
+msgid "Permission Denied."
+msgstr "Zugriff verweigert."
-#: ../../Zotlabs/Module/Import.php:167
-msgid "No channel. Import failed."
-msgstr "Kein Kanal. Import fehlgeschlagen."
+#: ../../Zotlabs/Module/Filestorage.php:95
+msgid "File not found."
+msgstr "Datei nicht gefunden."
-#: ../../Zotlabs/Module/Import.php:503
-#: ../../include/Import/import_diaspora.php:142
-msgid "Import completed."
-msgstr "Import abgeschlossen."
+#: ../../Zotlabs/Module/Filestorage.php:137
+msgid "Edit file permissions"
+msgstr "Dateiberechtigungen bearbeiten"
-#: ../../Zotlabs/Module/Import.php:525
-msgid "You must be logged in to use this feature."
-msgstr "Du musst angemeldet sein um diese Funktion zu nutzen."
+#: ../../Zotlabs/Module/Filestorage.php:149
+msgid "Set/edit permissions"
+msgstr "Berechtigungen setzen/ändern"
-#: ../../Zotlabs/Module/Import.php:530
-msgid "Import Channel"
-msgstr "Kanal importieren"
+#: ../../Zotlabs/Module/Filestorage.php:150
+msgid "Include all files and sub folders"
+msgstr "Alle Dateien und Unterverzeichnisse einbinden"
-#: ../../Zotlabs/Module/Import.php:531
-msgid ""
-"Use this form to import an existing channel from a different server/hub. You"
-" may retrieve the channel identity from the old server/hub via the network "
-"or provide an export file."
-msgstr "Verwende dieses Formular, um einen existierenden Kanal von einem anderen Hub zu importieren. Du kannst den Kanal direkt vom bisherigen Hub über das Netzwerk oder aus einer exportierten Sicherheitskopie importieren."
+#: ../../Zotlabs/Module/Filestorage.php:151
+msgid "Return to file list"
+msgstr "Zurück zur Dateiliste"
-#: ../../Zotlabs/Module/Import.php:533
-msgid "Or provide the old server/hub details"
-msgstr "Oder gib die Details Deines bisherigen $Projectname-Hubs ein"
+#: ../../Zotlabs/Module/Filestorage.php:153
+msgid "Copy/paste this code to attach file to a post"
+msgstr "Diesen Code kopieren und einfügen, um die Datei an einen Beitrag anzuhängen"
-#: ../../Zotlabs/Module/Import.php:534
-msgid "Your old identity address (xyz@example.com)"
-msgstr "Bisherige Kanal-Adresse (xyz@example.com)"
+#: ../../Zotlabs/Module/Filestorage.php:154
+msgid "Copy/paste this URL to link file from a web page"
+msgstr "Diese URL verwenden, um von einer Webseite aus auf die Datei zu verlinken"
-#: ../../Zotlabs/Module/Import.php:535
-msgid "Your old login email address"
-msgstr "Deine alte Login-E-Mail-Adresse"
+#: ../../Zotlabs/Module/Filestorage.php:156
+msgid "Share this file"
+msgstr "Diese Datei freigeben"
-#: ../../Zotlabs/Module/Import.php:536
-msgid "Your old login password"
-msgstr "Dein altes Passwort"
+#: ../../Zotlabs/Module/Filestorage.php:157
+msgid "Show URL to this file"
+msgstr "URL zu dieser Datei anzeigen"
-#: ../../Zotlabs/Module/Import.php:537
-msgid ""
-"For either option, please choose whether to make this hub your new primary "
-"address, or whether your old location should continue this role. You will be"
-" able to post from either location, but only one can be marked as the "
-"primary location for files, photos, and media."
-msgstr "Egal, welche Option Du wählst – bitte lege fest, ob dieser Server die neue primäre Adresse dieses Kanals sein soll, oder ob der bisherige $Projectname-Hub diese Rolle weiterhin wahrnimmt. Du kannst von beiden Servern aus posten, aber nur einer kann der primäre Ort Deiner Dateien, Fotos und Medien sein."
+#: ../../Zotlabs/Module/Filestorage.php:158
+#: ../../Zotlabs/Storage/Browser.php:351
+msgid "Show in your contacts shared folder"
+msgstr "Im geteilten Ordner Deiner Kontakte anzeigen"
-#: ../../Zotlabs/Module/Import.php:538
-msgid "Make this hub my primary location"
-msgstr "Dieser $Pojectname-Hub ist mein primärer Hub."
+#: ../../Zotlabs/Module/Common.php:14
+msgid "No channel."
+msgstr "Kein Kanal."
-#: ../../Zotlabs/Module/Import.php:539
-msgid ""
-"Import existing posts if possible (experimental - limited by available "
-"memory"
-msgstr "Importiere bestehende Beiträge falls möglich (experimentell - begrenzt durch zur Verfügung stehenden Speicher"
+#: ../../Zotlabs/Module/Common.php:45
+msgid "No connections in common."
+msgstr "Keine gemeinsamen Verbindungen."
-#: ../../Zotlabs/Module/Import.php:540
-msgid ""
-"This process may take several minutes to complete. Please submit the form "
-"only once and leave this page open until finished."
-msgstr "Dieser Vorgang kann einige Minuten dauern. Bitte sende das Formular nur einmal ab und lasse diese Seite bis zur Fertigstellung offen."
+#: ../../Zotlabs/Module/Common.php:65
+msgid "View Common Connections"
+msgstr "Zeige gemeinsame Verbindungen"
#: ../../Zotlabs/Module/Viewconnections.php:65
msgid "No connections."
@@ -6754,330 +7145,395 @@ msgstr "%ss Profil [%s] besuchen"
msgid "View Connections"
msgstr "Verbindungen anzeigen"
-#: ../../Zotlabs/Module/Viewsrc.php:44
-msgid "Source of Item"
-msgstr "Quelle des Elements"
-
-#: ../../Zotlabs/Module/Chat.php:181
-msgid "Room not found"
-msgstr "Chatraum nicht gefunden"
-
-#: ../../Zotlabs/Module/Chat.php:197
-msgid "Leave Room"
-msgstr "Raum verlassen"
-
-#: ../../Zotlabs/Module/Chat.php:198
-msgid "Delete Room"
-msgstr "Raum löschen"
-
-#: ../../Zotlabs/Module/Chat.php:199
-msgid "I am away right now"
-msgstr "Ich bin gerade nicht da"
-
-#: ../../Zotlabs/Module/Chat.php:200
-msgid "I am online"
-msgstr "Ich bin online"
-
-#: ../../Zotlabs/Module/Chat.php:202
-msgid "Bookmark this room"
-msgstr "Lesezeichen für diesen Raum setzen"
-
-#: ../../Zotlabs/Module/Chat.php:231
-msgid "New Chatroom"
-msgstr "Neuer Chatraum"
-
-#: ../../Zotlabs/Module/Chat.php:232
-msgid "Chatroom name"
-msgstr "Chatraumname"
-
-#: ../../Zotlabs/Module/Chat.php:233
-msgid "Expiration of chats (minutes)"
-msgstr "Verfall von Chats (Minuten)"
+#: ../../Zotlabs/Module/Admin.php:97
+msgid "Blocked accounts"
+msgstr "Blockierte Benutzerkonten"
-#: ../../Zotlabs/Module/Chat.php:249
-#, php-format
-msgid "%1$s's Chatrooms"
-msgstr "%1$ss Chaträume"
+#: ../../Zotlabs/Module/Admin.php:98
+msgid "Expired accounts"
+msgstr "Abgelaufene Benutzerkonten"
-#: ../../Zotlabs/Module/Chat.php:254
-msgid "No chatrooms available"
-msgstr "Keine Chaträume verfügbar"
+#: ../../Zotlabs/Module/Admin.php:99
+msgid "Expiring accounts"
+msgstr "Ablaufende Benutzerkonten"
-#: ../../Zotlabs/Module/Chat.php:258
-msgid "Expiration"
-msgstr "Verfall"
+#: ../../Zotlabs/Module/Admin.php:112
+msgid "Clones"
+msgstr "Klone"
-#: ../../Zotlabs/Module/Chat.php:259
-msgid "min"
-msgstr "min"
+#: ../../Zotlabs/Module/Admin.php:118
+msgid "Message queues"
+msgstr "Nachrichten-Warteschlangen"
-#: ../../Zotlabs/Module/Xchan.php:10
-msgid "Xchan Lookup"
-msgstr "Xchan-Suche"
+#: ../../Zotlabs/Module/Admin.php:132
+msgid "Your software should be updated"
+msgstr "Die installierte Software sollte aktualisiert werden"
-#: ../../Zotlabs/Module/Xchan.php:13
-msgid "Lookup xchan beginning with (or webbie): "
-msgstr "Nach xchans oder Webbies (Kanal-Adressen) suchen, die wie folgt beginnen:"
+#: ../../Zotlabs/Module/Admin.php:137
+msgid "Summary"
+msgstr "Zusammenfassung"
-#: ../../Zotlabs/Module/Events.php:25
-msgid "Calendar entries imported."
-msgstr "Kalendereinträge wurden importiert."
+#: ../../Zotlabs/Module/Admin.php:140
+msgid "Registered accounts"
+msgstr "Registrierte Konten"
-#: ../../Zotlabs/Module/Events.php:27
-msgid "No calendar entries found."
-msgstr "Keine Kalendereinträge gefunden."
+#: ../../Zotlabs/Module/Admin.php:141
+msgid "Pending registrations"
+msgstr "Ausstehende Registrierungen"
-#: ../../Zotlabs/Module/Events.php:106
-msgid "Event can not end before it has started."
-msgstr "Termin-Ende liegt vor dem Beginn."
+#: ../../Zotlabs/Module/Admin.php:142
+msgid "Registered channels"
+msgstr "Registrierte Kanäle"
-#: ../../Zotlabs/Module/Events.php:108 ../../Zotlabs/Module/Events.php:117
-#: ../../Zotlabs/Module/Events.php:139
-msgid "Unable to generate preview."
-msgstr "Vorschau konnte nicht erzeugt werden."
+#: ../../Zotlabs/Module/Admin.php:143
+msgid "Active plugins"
+msgstr "Aktive Plug-Ins"
-#: ../../Zotlabs/Module/Events.php:115
-msgid "Event title and start time are required."
-msgstr "Titel und Startzeit des Termins sind erforderlich."
+#: ../../Zotlabs/Module/Admin.php:144
+msgid "Version"
+msgstr "Version"
-#: ../../Zotlabs/Module/Events.php:137 ../../Zotlabs/Module/Events.php:261
-msgid "Event not found."
-msgstr "Termin nicht gefunden."
+#: ../../Zotlabs/Module/Admin.php:145
+msgid "Repository version (master)"
+msgstr "Repository-Version (master)"
-#: ../../Zotlabs/Module/Events.php:453
-msgid "Edit event title"
-msgstr "Termintitel bearbeiten"
+#: ../../Zotlabs/Module/Admin.php:146
+msgid "Repository version (dev)"
+msgstr "Repository-Version (dev)"
-#: ../../Zotlabs/Module/Events.php:453
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:835
-msgid "Event title"
-msgstr "Termintitel"
+#: ../../Zotlabs/Module/Service_limits.php:23
+msgid "No service class restrictions found."
+msgstr "Keine Dienstklassenbeschränkungen gefunden."
-#: ../../Zotlabs/Module/Events.php:455
-msgid "Categories (comma-separated list)"
-msgstr "Kategorien (Kommagetrennte Liste)"
+#: ../../Zotlabs/Module/Rate.php:156
+msgid "Website:"
+msgstr "Webseite:"
-#: ../../Zotlabs/Module/Events.php:456
-msgid "Edit Category"
-msgstr "Kategorie bearbeiten"
+#: ../../Zotlabs/Module/Rate.php:159
+#, php-format
+msgid "Remote Channel [%s] (not yet known on this site)"
+msgstr "Kanal [%s] (auf diesem Server noch unbekannt)"
-#: ../../Zotlabs/Module/Events.php:456
-msgid "Category"
-msgstr "Kategorie"
+#: ../../Zotlabs/Module/Rate.php:160
+msgid "Rating (this information is public)"
+msgstr "Bewertung (öffentlich sichtbar)"
-#: ../../Zotlabs/Module/Events.php:459
-msgid "Edit start date and time"
-msgstr "Startdatum und -zeit bearbeiten"
+#: ../../Zotlabs/Module/Rate.php:161
+msgid "Optionally explain your rating (this information is public)"
+msgstr "Optional kannst du deine Bewertung erklären (öffentlich sichtbar)"
-#: ../../Zotlabs/Module/Events.php:459
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:836
-msgid "Start date and time"
-msgstr "Startdatum und -zeit"
+#: ../../Zotlabs/Module/Card_edit.php:128
+msgid "Edit Card"
+msgstr "Karte bearbeiten"
-#: ../../Zotlabs/Module/Events.php:460 ../../Zotlabs/Module/Events.php:463
-msgid "Finish date and time are not known or not relevant"
-msgstr "Enddatum und -zeit sind unbekannt oder irrelevant"
+#: ../../Zotlabs/Module/Lostpass.php:19
+msgid "No valid account found."
+msgstr "Kein gültiges Konto gefunden."
-#: ../../Zotlabs/Module/Events.php:462
-msgid "Edit finish date and time"
-msgstr "Enddatum und -zeit bearbeiten"
+#: ../../Zotlabs/Module/Lostpass.php:33
+msgid "Password reset request issued. Check your email."
+msgstr "Zurücksetzen des Passworts eingeleitet. Schau in Deine E-Mails."
-#: ../../Zotlabs/Module/Events.php:462
-msgid "Finish date and time"
-msgstr "Enddatum und -zeit"
+#: ../../Zotlabs/Module/Lostpass.php:39 ../../Zotlabs/Module/Lostpass.php:108
+#, php-format
+msgid "Site Member (%s)"
+msgstr "Nutzer (%s)"
-#: ../../Zotlabs/Module/Events.php:464 ../../Zotlabs/Module/Events.php:465
-msgid "Adjust for viewer timezone"
-msgstr "An die Zeitzone des Betrachters anpassen"
+#: ../../Zotlabs/Module/Lostpass.php:44 ../../Zotlabs/Module/Lostpass.php:49
+#, php-format
+msgid "Password reset requested at %s"
+msgstr "Passwort-Rücksetzung auf %s angefordert"
-#: ../../Zotlabs/Module/Events.php:464
+#: ../../Zotlabs/Module/Lostpass.php:68
msgid ""
-"Important for events that happen in a particular place. Not practical for "
-"global holidays."
-msgstr "Wichtig für Veranstaltungen die an bestimmten Orten stattfinden. Nicht sinnvoll für globale Feiertage / Ferien."
+"Request could not be verified. (You may have previously submitted it.) "
+"Password reset failed."
+msgstr "Die Anfrage konnte nicht verifiziert werden. (Vielleicht hast Du schon einmal auf den Link in der E-Mail geklickt?) Passwort-Rücksetzung fehlgeschlagen."
-#: ../../Zotlabs/Module/Events.php:466
-msgid "Edit Description"
-msgstr "Beschreibung bearbeiten"
+#: ../../Zotlabs/Module/Lostpass.php:91 ../../boot.php:1648
+msgid "Password Reset"
+msgstr "Zurücksetzen des Kennworts"
-#: ../../Zotlabs/Module/Events.php:468
-msgid "Edit Location"
-msgstr "Ort bearbeiten"
+#: ../../Zotlabs/Module/Lostpass.php:92
+msgid "Your password has been reset as requested."
+msgstr "Dein Passwort wurde wie angefordert neu erstellt."
-#: ../../Zotlabs/Module/Events.php:472 ../../include/conversation.php:1280
-msgid "Permission settings"
-msgstr "Berechtigungs-Einstellungen"
+#: ../../Zotlabs/Module/Lostpass.php:93
+msgid "Your new password is"
+msgstr "Dein neues Passwort lautet"
-#: ../../Zotlabs/Module/Events.php:485
-msgid "Advanced Options"
-msgstr "Weitere Optionen"
+#: ../../Zotlabs/Module/Lostpass.php:94
+msgid "Save or copy your new password - and then"
+msgstr "Speichere oder kopiere Dein neues Passwort – und dann"
-#: ../../Zotlabs/Module/Events.php:624
-msgid "Edit event"
-msgstr "Termin bearbeiten"
+#: ../../Zotlabs/Module/Lostpass.php:95
+msgid "click here to login"
+msgstr "Klicke hier, um dich anzumelden"
-#: ../../Zotlabs/Module/Events.php:626
-msgid "Delete event"
-msgstr "Termin löschen"
+#: ../../Zotlabs/Module/Lostpass.php:96
+msgid ""
+"Your password may be changed from the <em>Settings</em> page after "
+"successful login."
+msgstr "Dein Passwort kann unter <em>Einstellungen</em> nach einer erfolgreichen Anmeldung geändert werden."
-#: ../../Zotlabs/Module/Events.php:660
-msgid "calendar"
-msgstr "Kalender"
+#: ../../Zotlabs/Module/Lostpass.php:117
+#, php-format
+msgid "Your password has changed at %s"
+msgstr "Auf %s wurde Dein Passwort geändert"
-#: ../../Zotlabs/Module/Events.php:686
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:849
-msgid "Month"
-msgstr "Monat"
+#: ../../Zotlabs/Module/Lostpass.php:130
+msgid "Forgot your Password?"
+msgstr "Kennwort vergessen?"
-#: ../../Zotlabs/Module/Events.php:687
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:850
-msgid "Week"
-msgstr "Woche"
+#: ../../Zotlabs/Module/Lostpass.php:131
+msgid ""
+"Enter your email address and submit to have your password reset. Then check "
+"your email for further instructions."
+msgstr "Gib Deine E-Mail-Adresse ein, um Dein Passwort zurücksetzen zu lassen. Du erhältst dann weitere Anweisungen per E-Mail."
-#: ../../Zotlabs/Module/Events.php:688
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:851
-msgid "Day"
-msgstr "Tag"
+#: ../../Zotlabs/Module/Lostpass.php:132
+msgid "Email Address"
+msgstr "E-Mail Adresse"
-#: ../../Zotlabs/Module/Events.php:722
-msgid "Event removed"
-msgstr "Termin gelöscht"
+#: ../../Zotlabs/Module/Notifications.php:43
+#: ../../Zotlabs/Lib/ThreadItem.php:397
+msgid "Mark all seen"
+msgstr "Alle als gelesen markieren"
-#: ../../Zotlabs/Module/Events.php:725
-msgid "Failed to remove event"
-msgstr "Termin konnte nicht gelöscht werden"
+#: ../../Zotlabs/Lib/Techlevels.php:10
+msgid "0. Beginner/Basic"
+msgstr "0. Einsteiger/Basis"
-#: ../../Zotlabs/Lib/Chatroom.php:27
-msgid "Missing room name"
-msgstr "Der Chatraum hat keinen Namen"
+#: ../../Zotlabs/Lib/Techlevels.php:11
+msgid "1. Novice - not skilled but willing to learn"
+msgstr "1. Anfänger - unerfahren, aber bereit zu lernen"
-#: ../../Zotlabs/Lib/Chatroom.php:36
-msgid "Duplicate room name"
-msgstr "Name des Chatraums bereits vergeben"
+#: ../../Zotlabs/Lib/Techlevels.php:12
+msgid "2. Intermediate - somewhat comfortable"
+msgstr "2. Fortgeschritten - relativ komfortabel"
-#: ../../Zotlabs/Lib/Chatroom.php:86 ../../Zotlabs/Lib/Chatroom.php:94
-msgid "Invalid room specifier."
-msgstr "Ungültiger Raumbezeichner."
+#: ../../Zotlabs/Lib/Techlevels.php:13
+msgid "3. Advanced - very comfortable"
+msgstr "3. Fortgeschritten - sehr komfortabel"
-#: ../../Zotlabs/Lib/Chatroom.php:126
-msgid "Room not found."
-msgstr "Chatraum konnte nicht gefunden werden."
+#: ../../Zotlabs/Lib/Techlevels.php:14
+msgid "4. Expert - I can write computer code"
+msgstr "4. Experte - Ich kann Computercode schreiben"
-#: ../../Zotlabs/Lib/Chatroom.php:147
-msgid "Room is full"
-msgstr "Der Chatraum ist voll"
+#: ../../Zotlabs/Lib/Techlevels.php:15
+msgid "5. Wizard - I probably know more than you do"
+msgstr "5. Zauberer - ich kann wahrscheinlich mehr als Du"
-#: ../../Zotlabs/Lib/Apps.php:205
+#: ../../Zotlabs/Lib/Apps.php:225
msgid "Site Admin"
msgstr "Hub-Administration"
-#: ../../Zotlabs/Lib/Apps.php:206
-#: ../../extend/addon/addon/buglink/buglink.php:16
+#: ../../Zotlabs/Lib/Apps.php:226 ../../addon/buglink/buglink.php:16
msgid "Report Bug"
msgstr "Fehler melden"
-#: ../../Zotlabs/Lib/Apps.php:207
+#: ../../Zotlabs/Lib/Apps.php:227
msgid "View Bookmarks"
msgstr "Lesezeichen ansehen"
-#: ../../Zotlabs/Lib/Apps.php:208
+#: ../../Zotlabs/Lib/Apps.php:228
msgid "My Chatrooms"
msgstr "Meine Chaträume"
-#: ../../Zotlabs/Lib/Apps.php:210
+#: ../../Zotlabs/Lib/Apps.php:230
msgid "Firefox Share"
msgstr "Teilen-Knopf für Firefox"
-#: ../../Zotlabs/Lib/Apps.php:211
+#: ../../Zotlabs/Lib/Apps.php:231
msgid "Remote Diagnostics"
msgstr "Ferndiagnose"
-#: ../../Zotlabs/Lib/Apps.php:212 ../../include/features.php:319
+#: ../../Zotlabs/Lib/Apps.php:232 ../../include/features.php:342
msgid "Suggest Channels"
msgstr "Kanäle vorschlagen"
-#: ../../Zotlabs/Lib/Apps.php:213 ../../include/nav.php:115
-#: ../../boot.php:1719
+#: ../../Zotlabs/Lib/Apps.php:233 ../../boot.php:1639
+#: ../../include/nav.php:153 ../../include/nav.php:157
msgid "Login"
msgstr "Anmelden"
-#: ../../Zotlabs/Lib/Apps.php:215 ../../include/nav.php:182
-msgid "Grid"
-msgstr "Grid"
+#: ../../Zotlabs/Lib/Apps.php:235 ../../include/nav.php:98
+msgid "Activity"
+msgstr "Aktivität"
-#: ../../Zotlabs/Lib/Apps.php:219 ../../include/features.php:99
-#: ../../include/conversation.php:1758
+#: ../../Zotlabs/Lib/Apps.php:239 ../../include/conversation.php:1900
+#: ../../include/features.php:95 ../../include/nav.php:507
msgid "Wiki"
msgstr "Wiki"
-#: ../../Zotlabs/Lib/Apps.php:220 ../../include/nav.php:185
+#: ../../Zotlabs/Lib/Apps.php:240 ../../include/nav.php:102
msgid "Channel Home"
msgstr "Mein Kanal"
-#: ../../Zotlabs/Lib/Apps.php:223 ../../include/nav.php:204
-#: ../../include/conversation.php:1709 ../../include/conversation.php:1712
+#: ../../Zotlabs/Lib/Apps.php:243 ../../include/conversation.php:1833
+#: ../../include/conversation.php:1836 ../../include/nav.php:124
+#: ../../include/nav.php:441 ../../include/nav.php:444
msgid "Events"
msgstr "Termine"
-#: ../../Zotlabs/Lib/Apps.php:224 ../../include/nav.php:170
+#: ../../Zotlabs/Lib/Apps.php:244
msgid "Directory"
msgstr "Verzeichnis"
-#: ../../Zotlabs/Lib/Apps.php:226 ../../include/nav.php:196
+#: ../../Zotlabs/Lib/Apps.php:246 ../../include/nav.php:116
msgid "Mail"
msgstr "Mail"
-#: ../../Zotlabs/Lib/Apps.php:229 ../../include/nav.php:99
+#: ../../Zotlabs/Lib/Apps.php:249
msgid "Chat"
msgstr "Chat"
-#: ../../Zotlabs/Lib/Apps.php:231
+#: ../../Zotlabs/Lib/Apps.php:251
msgid "Probe"
msgstr "Testen"
-#: ../../Zotlabs/Lib/Apps.php:232
+#: ../../Zotlabs/Lib/Apps.php:252
msgid "Suggest"
msgstr "Empfehlen"
-#: ../../Zotlabs/Lib/Apps.php:233
+#: ../../Zotlabs/Lib/Apps.php:253
msgid "Random Channel"
msgstr "Zufälliger Kanal"
-#: ../../Zotlabs/Lib/Apps.php:234
+#: ../../Zotlabs/Lib/Apps.php:254
msgid "Invite"
msgstr "Einladen"
-#: ../../Zotlabs/Lib/Apps.php:235 ../../include/widgets.php:1635
+#: ../../Zotlabs/Lib/Apps.php:255 ../../Zotlabs/Widget/Admin.php:26
msgid "Features"
msgstr "Funktionen"
-#: ../../Zotlabs/Lib/Apps.php:236
-#: ../../extend/addon/addon/openid/MysqlProvider.php:69
+#: ../../Zotlabs/Lib/Apps.php:256 ../../addon/openid/MysqlProvider.php:69
msgid "Language"
msgstr "Sprache"
-#: ../../Zotlabs/Lib/Apps.php:237
+#: ../../Zotlabs/Lib/Apps.php:257
msgid "Post"
msgstr "Beitrag schreiben"
-#: ../../Zotlabs/Lib/Apps.php:238
-#: ../../extend/addon/addon/openid/MysqlProvider.php:58
-#: ../../extend/addon/addon/openid/MysqlProvider.php:59
-#: ../../extend/addon/addon/openid/MysqlProvider.php:60
+#: ../../Zotlabs/Lib/Apps.php:258 ../../addon/openid/MysqlProvider.php:58
+#: ../../addon/openid/MysqlProvider.php:59
+#: ../../addon/openid/MysqlProvider.php:60
msgid "Profile Photo"
msgstr "Profilfoto"
-#: ../../Zotlabs/Lib/Apps.php:339
+#: ../../Zotlabs/Lib/Apps.php:397
msgid "Purchase"
msgstr "Kaufen"
+#: ../../Zotlabs/Lib/Apps.php:401
+msgid "Undelete"
+msgstr "Wieder hergestellt"
+
+#: ../../Zotlabs/Lib/Apps.php:407
+msgid "Add to app-tray"
+msgstr "Zum App-Menü hinzufügen"
+
+#: ../../Zotlabs/Lib/Apps.php:408
+msgid "Remove from app-tray"
+msgstr "Aus dem App-Menü entfernen"
+
+#: ../../Zotlabs/Lib/Permcat.php:58
+msgctxt "permcat"
+msgid "default"
+msgstr "Standard"
+
+#: ../../Zotlabs/Lib/Permcat.php:96
+msgctxt "permcat"
+msgid "follower"
+msgstr "Abonnent"
+
+#: ../../Zotlabs/Lib/Permcat.php:100
+msgctxt "permcat"
+msgid "contributor"
+msgstr "Beitragender"
+
+#: ../../Zotlabs/Lib/Permcat.php:104
+msgctxt "permcat"
+msgid "publisher"
+msgstr "Autor"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:42
+#: ../../Zotlabs/Lib/NativeWikiPage.php:90
+msgid "(No Title)"
+msgstr "(Kein Titel)"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:104
+msgid "Wiki page create failed."
+msgstr "Anlegen der Wiki-Seite fehlgeschlagen."
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:117
+msgid "Wiki not found."
+msgstr "Wiki nicht gefunden."
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:128
+msgid "Destination name already exists"
+msgstr "Zielname bereits vorhanden"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:160
+#: ../../Zotlabs/Lib/NativeWikiPage.php:355
+msgid "Page not found"
+msgstr "Seite nicht gefunden"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:191
+msgid "Error reading page content"
+msgstr "Fehler beim Lesen des Seiteninhalts"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:347
+#: ../../Zotlabs/Lib/NativeWikiPage.php:396
+#: ../../Zotlabs/Lib/NativeWikiPage.php:463
+#: ../../Zotlabs/Lib/NativeWikiPage.php:504
+msgid "Error reading wiki"
+msgstr "Fehler beim Lesen des Wiki"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:384
+msgid "Page update failed."
+msgstr "Seitenaktualisierung fehlgeschlagen."
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:418
+msgid "Nothing deleted"
+msgstr "Nichts gelöscht"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:484
+msgid "Compare: object not found."
+msgstr "Vergleichen: Objekt nicht gefunden."
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:490
+msgid "Page updated"
+msgstr "Seite aktualisiert"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:493
+msgid "Untitled"
+msgstr "Ohne Titel"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:499
+msgid "Wiki resource_id required for git commit"
+msgstr "Die resource_id des Wiki wird benötigt für den git commit."
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:555
+#: ../../Zotlabs/Widget/Wiki_page_history.php:23
+msgctxt "wiki_history"
+msgid "Message"
+msgstr "Nachricht"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:593
+#: ../../addon/gitwiki/gitwiki_backend.php:579 ../../include/bbcode.php:672
+#: ../../include/bbcode.php:818
+msgid "Different viewers will see this text differently"
+msgstr "Verschiedene Betrachter werden diesen Text unterschiedlich sehen"
+
#: ../../Zotlabs/Lib/PermissionDescription.php:34
#: ../../include/acl_selectors.php:128
msgid "Visible to your default audience"
msgstr "Standard-Sichtbarkeit gemäß Kanaleinstellungen"
#: ../../Zotlabs/Lib/PermissionDescription.php:107
-#: ../../include/acl_selectors.php:191
+#: ../../include/acl_selectors.php:201
msgid "Only me"
msgstr "Nur ich"
@@ -7134,2177 +7590,2839 @@ msgstr "Dies ist Deine Voreinstellung für die Sichtbarkeit Deiner Dateien und F
msgid "This is your default setting for the audience of your webpages"
msgstr "Dies ist Deine Voreinstellung für die Sichtbarkeit Deiner Webseiten."
-#: ../../Zotlabs/Lib/ThreadItem.php:95 ../../include/conversation.php:683
+#: ../../Zotlabs/Lib/Chatroom.php:27
+msgid "Missing room name"
+msgstr "Der Chatraum hat keinen Namen"
+
+#: ../../Zotlabs/Lib/Chatroom.php:36
+msgid "Duplicate room name"
+msgstr "Name des Chatraums bereits vergeben"
+
+#: ../../Zotlabs/Lib/Chatroom.php:86 ../../Zotlabs/Lib/Chatroom.php:94
+msgid "Invalid room specifier."
+msgstr "Ungültiger Raumbezeichner."
+
+#: ../../Zotlabs/Lib/Chatroom.php:126
+msgid "Room not found."
+msgstr "Chatraum konnte nicht gefunden werden."
+
+#: ../../Zotlabs/Lib/Chatroom.php:147
+msgid "Room is full"
+msgstr "Der Chatraum ist voll"
+
+#: ../../Zotlabs/Lib/Enotify.php:60
+msgid "$Projectname Notification"
+msgstr "$Projectname-Benachrichtigung"
+
+#: ../../Zotlabs/Lib/Enotify.php:61 ../../addon/diaspora/util.php:283
+#: ../../addon/diaspora/util.php:296 ../../addon/diaspora/p.php:48
+msgid "$projectname"
+msgstr "$projectname"
+
+#: ../../Zotlabs/Lib/Enotify.php:63
+msgid "Thank You,"
+msgstr "Danke."
+
+#: ../../Zotlabs/Lib/Enotify.php:65 ../../addon/hubwall/hubwall.php:33
+#, php-format
+msgid "%s Administrator"
+msgstr "der Administrator von %s"
+
+#: ../../Zotlabs/Lib/Enotify.php:116
+#, php-format
+msgid "%s <!item_type!>"
+msgstr "%s <!item_type!>"
+
+#: ../../Zotlabs/Lib/Enotify.php:120
+#, php-format
+msgid "[$Projectname:Notify] New mail received at %s"
+msgstr "[$Projectname:Benachrichtigung] Neue Mail empfangen auf %s"
+
+#: ../../Zotlabs/Lib/Enotify.php:122
+#, php-format
+msgid "%1$s, %2$s sent you a new private message at %3$s."
+msgstr "%1$s, %2$s hat Dir eine private Nachricht auf %3$s gesendet."
+
+#: ../../Zotlabs/Lib/Enotify.php:123
+#, php-format
+msgid "%1$s sent you %2$s."
+msgstr "%1$s hat Dir %2$s geschickt."
+
+#: ../../Zotlabs/Lib/Enotify.php:123
+msgid "a private message"
+msgstr "eine private Nachricht"
+
+#: ../../Zotlabs/Lib/Enotify.php:124
+#, php-format
+msgid "Please visit %s to view and/or reply to your private messages."
+msgstr "Bitte besuche %s, um die private Nachricht anzusehen und/oder darauf zu antworten."
+
+#: ../../Zotlabs/Lib/Enotify.php:184
+#, php-format
+msgid "%1$s, %2$s commented on [zrl=%3$s]a %4$s[/zrl]"
+msgstr "%1$s, %2$s hat [zrl=%3$s]einen %4$s[/zrl] kommentiert"
+
+#: ../../Zotlabs/Lib/Enotify.php:192
+#, php-format
+msgid "%1$s, %2$s commented on [zrl=%3$s]%4$s's %5$s[/zrl]"
+msgstr "%1$s, %2$s hat [zrl=%3$s]%4$ss %5$s[/zrl] kommentiert"
+
+#: ../../Zotlabs/Lib/Enotify.php:201
+#, php-format
+msgid "%1$s, %2$s commented on [zrl=%3$s]your %4$s[/zrl]"
+msgstr "%1$s, %2$s hat [zrl=%3$s]Deinen %4$s[/zrl] kommentiert"
+
+#: ../../Zotlabs/Lib/Enotify.php:213
+#, php-format
+msgid "[$Projectname:Notify] Moderated Comment to conversation #%1$d by %2$s"
+msgstr "[$Projectname:Benachrichtigung] Moderierter Kommantar in Unterhaltung #%1$d von %2$s"
+
+#: ../../Zotlabs/Lib/Enotify.php:215
+#, php-format
+msgid "[$Projectname:Notify] Comment to conversation #%1$d by %2$s"
+msgstr "[$Projectname:Benachrichtigung] Kommentar in Unterhaltung #%1$d von %2$s"
+
+#: ../../Zotlabs/Lib/Enotify.php:216
+#, php-format
+msgid "%1$s, %2$s commented on an item/conversation you have been following."
+msgstr "%1$s, %2$s hat eine Unterhaltung kommentiert, der Du folgst."
+
+#: ../../Zotlabs/Lib/Enotify.php:219 ../../Zotlabs/Lib/Enotify.php:301
+#: ../../Zotlabs/Lib/Enotify.php:318 ../../Zotlabs/Lib/Enotify.php:344
+#: ../../Zotlabs/Lib/Enotify.php:362 ../../Zotlabs/Lib/Enotify.php:376
+#, php-format
+msgid "Please visit %s to view and/or reply to the conversation."
+msgstr "Bitte besuche %s, um die Unterhaltung anzusehen und/oder zu kommentieren."
+
+#: ../../Zotlabs/Lib/Enotify.php:223 ../../Zotlabs/Lib/Enotify.php:224
+#, php-format
+msgid "Please visit %s to approve or reject this comment."
+msgstr "Bitte besuche %s, um diesen Kommentar anzunehmen oder abzulehnen."
+
+#: ../../Zotlabs/Lib/Enotify.php:282
+#, php-format
+msgid "%1$s, %2$s liked [zrl=%3$s]your %4$s[/zrl]"
+msgstr "%1$s, %2$s gefällt [zrl=%3$s]dein %4$s[/zrl]"
+
+#: ../../Zotlabs/Lib/Enotify.php:297
+#, php-format
+msgid "[$Projectname:Notify] Like received to conversation #%1$d by %2$s"
+msgstr "[$Projectname:Benachrichtigung] Gefällt mir in Unterhaltung #%1$d von %2$s erhalten"
+
+#: ../../Zotlabs/Lib/Enotify.php:298
+#, php-format
+msgid "%1$s, %2$s liked an item/conversation you created."
+msgstr "%1$s, %2$s gefällt ein Beitrag oder eine Unterhaltung von Dir"
+
+#: ../../Zotlabs/Lib/Enotify.php:309
+#, php-format
+msgid "[$Projectname:Notify] %s posted to your profile wall"
+msgstr "[$Projectname:Benachrichtigung] %s schrieb auf Deine Pinnwand"
+
+#: ../../Zotlabs/Lib/Enotify.php:311
+#, php-format
+msgid "%1$s, %2$s posted to your profile wall at %3$s"
+msgstr "%1$s, %2$s hat auf Deine Pinnwand auf %3$s geschrieben"
+
+#: ../../Zotlabs/Lib/Enotify.php:313
+#, php-format
+msgid "%1$s, %2$s posted to [zrl=%3$s]your wall[/zrl]"
+msgstr "%1$s, %2$s hat auf [zrl=%3$s]Deine Pinnwand[/zrl] geschrieben"
+
+#: ../../Zotlabs/Lib/Enotify.php:337
+#, php-format
+msgid "[$Projectname:Notify] %s tagged you"
+msgstr "[$Projectname:Benachrichtigung] %s hat Dich erwähnt"
+
+#: ../../Zotlabs/Lib/Enotify.php:338
+#, php-format
+msgid "%1$s, %2$s tagged you at %3$s"
+msgstr "%1$s, %2$s hat Dich auf %3$s erwähnt"
+
+#: ../../Zotlabs/Lib/Enotify.php:339
+#, php-format
+msgid "%1$s, %2$s [zrl=%3$s]tagged you[/zrl]."
+msgstr "%1$s, %2$s [zrl=%3$s]hat Dich erwähnt[/zrl]."
+
+#: ../../Zotlabs/Lib/Enotify.php:351
+#, php-format
+msgid "[$Projectname:Notify] %1$s poked you"
+msgstr "[$Projectname:Benachrichtigung] %1$s hat Dich angestupst"
+
+#: ../../Zotlabs/Lib/Enotify.php:352
+#, php-format
+msgid "%1$s, %2$s poked you at %3$s"
+msgstr "%1$s, %2$s hat Dich auf %3$s angestupst"
+
+#: ../../Zotlabs/Lib/Enotify.php:353
+#, php-format
+msgid "%1$s, %2$s [zrl=%2$s]poked you[/zrl]."
+msgstr "%1$s, %2$s [zrl=%2$s]hat Dich angestupst[/zrl]."
+
+#: ../../Zotlabs/Lib/Enotify.php:369
+#, php-format
+msgid "[$Projectname:Notify] %s tagged your post"
+msgstr "[$Projectname:Benachrichtigung] %s hat Deinen Beitrag verschlagwortet"
+
+#: ../../Zotlabs/Lib/Enotify.php:370
+#, php-format
+msgid "%1$s, %2$s tagged your post at %3$s"
+msgstr "%1$s, %2$s hat Deinen Beitrag auf %3$s verschlagwortet"
+
+#: ../../Zotlabs/Lib/Enotify.php:371
+#, php-format
+msgid "%1$s, %2$s tagged [zrl=%3$s]your post[/zrl]"
+msgstr "%1$s, %2$s hat [zrl=%3$s]Deinen Beitrag[/zrl] verschlagwortet"
+
+#: ../../Zotlabs/Lib/Enotify.php:383
+msgid "[$Projectname:Notify] Introduction received"
+msgstr "[$Projectname:Benachrichtigung] Verbindungsanfrage erhalten"
+
+#: ../../Zotlabs/Lib/Enotify.php:384
+#, php-format
+msgid "%1$s, you've received an new connection request from '%2$s' at %3$s"
+msgstr "%1$s, Du hast eine neue Verbindungsanfrage von '%2$s' auf %3$s erhalten"
+
+#: ../../Zotlabs/Lib/Enotify.php:385
+#, php-format
+msgid ""
+"%1$s, you've received [zrl=%2$s]a new connection request[/zrl] from %3$s."
+msgstr "%1$s, Du hast [zrl=%2$s]eine neue Verbindungsanfrage[/zrl] von %3$s erhalten."
+
+#: ../../Zotlabs/Lib/Enotify.php:389 ../../Zotlabs/Lib/Enotify.php:408
+#, php-format
+msgid "You may visit their profile at %s"
+msgstr "Du kannst Dir das Profil unter %s ansehen"
+
+#: ../../Zotlabs/Lib/Enotify.php:391
+#, php-format
+msgid "Please visit %s to approve or reject the connection request."
+msgstr "Bitte besuche %s , um die Verbindungsanfrage anzunehmen oder abzulehnen."
+
+#: ../../Zotlabs/Lib/Enotify.php:398
+msgid "[$Projectname:Notify] Friend suggestion received"
+msgstr "[$Projectname:Benachrichtigung] Freundschaftsvorschlag erhalten"
+
+#: ../../Zotlabs/Lib/Enotify.php:399
+#, php-format
+msgid "%1$s, you've received a friend suggestion from '%2$s' at %3$s"
+msgstr "%1$s, Du hast einen Kontaktvorschlag von „%2$s“ auf %3$s erhalten"
+
+#: ../../Zotlabs/Lib/Enotify.php:400
+#, php-format
+msgid ""
+"%1$s, you've received [zrl=%2$s]a friend suggestion[/zrl] for %3$s from "
+"%4$s."
+msgstr "%1$s, Du hast [zrl=%2$s]einen Kontaktvorschlag[/zrl] für %3$s von %4$s erhalten."
+
+#: ../../Zotlabs/Lib/Enotify.php:406
+msgid "Name:"
+msgstr "Name:"
+
+#: ../../Zotlabs/Lib/Enotify.php:407
+msgid "Photo:"
+msgstr "Foto:"
+
+#: ../../Zotlabs/Lib/Enotify.php:410
+#, php-format
+msgid "Please visit %s to approve or reject the suggestion."
+msgstr "Bitte besuche %s um den Vorschlag zu akzeptieren oder abzulehnen."
+
+#: ../../Zotlabs/Lib/Enotify.php:629
+msgid "[$Projectname:Notify]"
+msgstr "[$Projectname:Benachrichtigung]"
+
+#: ../../Zotlabs/Lib/Enotify.php:789
+msgid "created a new post"
+msgstr "Neuer Beitrag wurde erzeugt"
+
+#: ../../Zotlabs/Lib/Enotify.php:790
+#, php-format
+msgid "commented on %s's post"
+msgstr "hat %s's Beitrag kommentiert"
+
+#: ../../Zotlabs/Lib/NativeWiki.php:151
+msgid "Wiki updated successfully"
+msgstr "Wiki erfolgreich aktualisiert"
+
+#: ../../Zotlabs/Lib/NativeWiki.php:198
+msgid "Wiki files deleted successfully"
+msgstr "Wiki-Dateien erfolgreich gelöscht"
+
+#: ../../Zotlabs/Lib/DB_Upgrade.php:95
+#, php-format
+msgid "Update Error at %s"
+msgstr "Aktualisierungsfehler auf %s"
+
+#: ../../Zotlabs/Lib/DB_Upgrade.php:101
+#, php-format
+msgid "Update %s failed. See error logs."
+msgstr "Aktualisierung %s fehlgeschlagen. Details in den Fehlerprotokollen."
+
+#: ../../Zotlabs/Lib/ThreadItem.php:97 ../../include/conversation.php:681
msgid "Private Message"
msgstr "Private Nachricht"
-#: ../../Zotlabs/Lib/ThreadItem.php:132 ../../include/conversation.php:675
+#: ../../Zotlabs/Lib/ThreadItem.php:137 ../../include/conversation.php:673
msgid "Select"
msgstr "Auswählen"
-#: ../../Zotlabs/Lib/ThreadItem.php:136
-msgid "Save to Folder"
-msgstr "In Ordner speichern"
-
-#: ../../Zotlabs/Lib/ThreadItem.php:157
+#: ../../Zotlabs/Lib/ThreadItem.php:162
msgid "I will attend"
msgstr "Ich werde teilnehmen"
-#: ../../Zotlabs/Lib/ThreadItem.php:157
+#: ../../Zotlabs/Lib/ThreadItem.php:162
msgid "I will not attend"
msgstr "Ich werde nicht teilnehmen"
-#: ../../Zotlabs/Lib/ThreadItem.php:157
+#: ../../Zotlabs/Lib/ThreadItem.php:162
msgid "I might attend"
msgstr "Ich werde vielleicht teilnehmen"
-#: ../../Zotlabs/Lib/ThreadItem.php:167
+#: ../../Zotlabs/Lib/ThreadItem.php:172
msgid "I agree"
msgstr "Ich stimme zu"
-#: ../../Zotlabs/Lib/ThreadItem.php:167
+#: ../../Zotlabs/Lib/ThreadItem.php:172
msgid "I disagree"
msgstr "Ich lehne ab"
-#: ../../Zotlabs/Lib/ThreadItem.php:167
+#: ../../Zotlabs/Lib/ThreadItem.php:172
msgid "I abstain"
msgstr "Ich enthalte mich"
-#: ../../Zotlabs/Lib/ThreadItem.php:223
+#: ../../Zotlabs/Lib/ThreadItem.php:228
msgid "Add Star"
msgstr "Stern hinzufügen"
-#: ../../Zotlabs/Lib/ThreadItem.php:224
+#: ../../Zotlabs/Lib/ThreadItem.php:229
msgid "Remove Star"
msgstr "Stern entfernen"
-#: ../../Zotlabs/Lib/ThreadItem.php:225
+#: ../../Zotlabs/Lib/ThreadItem.php:230
msgid "Toggle Star Status"
msgstr "Markierungsstatus (Stern) umschalten"
-#: ../../Zotlabs/Lib/ThreadItem.php:229
+#: ../../Zotlabs/Lib/ThreadItem.php:234
msgid "starred"
msgstr "markiert"
-#: ../../Zotlabs/Lib/ThreadItem.php:239 ../../include/conversation.php:690
+#: ../../Zotlabs/Lib/ThreadItem.php:244 ../../include/conversation.php:688
msgid "Message signature validated"
msgstr "Signatur überprüft"
-#: ../../Zotlabs/Lib/ThreadItem.php:240 ../../include/conversation.php:691
+#: ../../Zotlabs/Lib/ThreadItem.php:245 ../../include/conversation.php:689
msgid "Message signature incorrect"
msgstr "Signatur nicht korrekt"
-#: ../../Zotlabs/Lib/ThreadItem.php:248
+#: ../../Zotlabs/Lib/ThreadItem.php:253
msgid "Add Tag"
msgstr "Tag hinzufügen"
-#: ../../Zotlabs/Lib/ThreadItem.php:268 ../../include/taxonomy.php:316
+#: ../../Zotlabs/Lib/ThreadItem.php:271 ../../include/taxonomy.php:433
msgid "like"
msgstr "mag"
-#: ../../Zotlabs/Lib/ThreadItem.php:269 ../../include/taxonomy.php:317
+#: ../../Zotlabs/Lib/ThreadItem.php:272 ../../include/taxonomy.php:434
msgid "dislike"
msgstr "verurteile"
-#: ../../Zotlabs/Lib/ThreadItem.php:273
+#: ../../Zotlabs/Lib/ThreadItem.php:276
msgid "Share This"
msgstr "Teilen"
-#: ../../Zotlabs/Lib/ThreadItem.php:273
+#: ../../Zotlabs/Lib/ThreadItem.php:276
msgid "share"
msgstr "Teilen"
-#: ../../Zotlabs/Lib/ThreadItem.php:282
+#: ../../Zotlabs/Lib/ThreadItem.php:285
msgid "Delivery Report"
msgstr "Zustellungsbericht"
-#: ../../Zotlabs/Lib/ThreadItem.php:300
+#: ../../Zotlabs/Lib/ThreadItem.php:303
#, php-format
msgid "%d comment"
msgid_plural "%d comments"
msgstr[0] "%d Kommentar"
msgstr[1] "%d Kommentare"
-#: ../../Zotlabs/Lib/ThreadItem.php:329 ../../Zotlabs/Lib/ThreadItem.php:330
+#: ../../Zotlabs/Lib/ThreadItem.php:333 ../../Zotlabs/Lib/ThreadItem.php:334
#, php-format
msgid "View %s's profile - %s"
msgstr "Schaue Dir %ss Profil an – %s"
-#: ../../Zotlabs/Lib/ThreadItem.php:333
+#: ../../Zotlabs/Lib/ThreadItem.php:337
msgid "to"
msgstr "an"
-#: ../../Zotlabs/Lib/ThreadItem.php:334
+#: ../../Zotlabs/Lib/ThreadItem.php:338
msgid "via"
msgstr "via"
-#: ../../Zotlabs/Lib/ThreadItem.php:335
+#: ../../Zotlabs/Lib/ThreadItem.php:339
msgid "Wall-to-Wall"
msgstr "Wall-to-Wall"
-#: ../../Zotlabs/Lib/ThreadItem.php:336
+#: ../../Zotlabs/Lib/ThreadItem.php:340
msgid "via Wall-To-Wall:"
msgstr "via Wall-To-Wall:"
-#: ../../Zotlabs/Lib/ThreadItem.php:348 ../../include/conversation.php:736
+#: ../../Zotlabs/Lib/ThreadItem.php:353 ../../include/conversation.php:747
#, php-format
msgid "from %s"
msgstr "via %s"
-#: ../../Zotlabs/Lib/ThreadItem.php:351 ../../include/conversation.php:739
+#: ../../Zotlabs/Lib/ThreadItem.php:356 ../../include/conversation.php:750
#, php-format
msgid "last edited: %s"
msgstr "zuletzt bearbeitet: %s"
-#: ../../Zotlabs/Lib/ThreadItem.php:352 ../../include/conversation.php:740
+#: ../../Zotlabs/Lib/ThreadItem.php:357 ../../include/conversation.php:751
#, php-format
msgid "Expires: %s"
msgstr "Verfällt: %s"
-#: ../../Zotlabs/Lib/ThreadItem.php:358
+#: ../../Zotlabs/Lib/ThreadItem.php:363
msgid "Attend"
msgstr "Zusagen"
-#: ../../Zotlabs/Lib/ThreadItem.php:359
+#: ../../Zotlabs/Lib/ThreadItem.php:364
msgid "Attendance Options"
msgstr "Zusageoptionen"
-#: ../../Zotlabs/Lib/ThreadItem.php:360
+#: ../../Zotlabs/Lib/ThreadItem.php:365
msgid "Vote"
msgstr "Abstimmen"
-#: ../../Zotlabs/Lib/ThreadItem.php:361
+#: ../../Zotlabs/Lib/ThreadItem.php:366
msgid "Voting Options"
msgstr "Abstimmungsoptionen"
-#: ../../Zotlabs/Lib/ThreadItem.php:381
-#: ../../extend/addon/addon/bookmarker/bookmarker.php:38
+#: ../../Zotlabs/Lib/ThreadItem.php:387
+#: ../../addon/bookmarker/bookmarker.php:38
msgid "Save Bookmarks"
msgstr "Favoriten speichern"
-#: ../../Zotlabs/Lib/ThreadItem.php:382
+#: ../../Zotlabs/Lib/ThreadItem.php:388
msgid "Add to Calendar"
msgstr "Zum Kalender hinzufügen"
-#: ../../Zotlabs/Lib/ThreadItem.php:391
-msgid "Mark all seen"
-msgstr "Alle als gelesen markieren"
+#: ../../Zotlabs/Lib/ThreadItem.php:415 ../../include/conversation.php:471
+msgid "This is an unsaved preview"
+msgstr "Dies ist eine nicht gespeicherte Vorschau"
-#: ../../Zotlabs/Lib/ThreadItem.php:440 ../../include/js_strings.php:7
+#: ../../Zotlabs/Lib/ThreadItem.php:447 ../../include/js_strings.php:7
#, php-format
msgid "%s show all"
msgstr "%s mehr anzeigen"
-#: ../../Zotlabs/Lib/ThreadItem.php:730 ../../include/conversation.php:1255
+#: ../../Zotlabs/Lib/ThreadItem.php:744 ../../include/conversation.php:1360
msgid "Bold"
msgstr "Fett"
-#: ../../Zotlabs/Lib/ThreadItem.php:731 ../../include/conversation.php:1256
+#: ../../Zotlabs/Lib/ThreadItem.php:745 ../../include/conversation.php:1361
msgid "Italic"
msgstr "Kursiv"
-#: ../../Zotlabs/Lib/ThreadItem.php:732 ../../include/conversation.php:1257
+#: ../../Zotlabs/Lib/ThreadItem.php:746 ../../include/conversation.php:1362
msgid "Underline"
msgstr "Unterstrichen"
-#: ../../Zotlabs/Lib/ThreadItem.php:733 ../../include/conversation.php:1258
+#: ../../Zotlabs/Lib/ThreadItem.php:747 ../../include/conversation.php:1363
msgid "Quote"
msgstr "Zitat"
-#: ../../Zotlabs/Lib/ThreadItem.php:734 ../../include/conversation.php:1259
+#: ../../Zotlabs/Lib/ThreadItem.php:748 ../../include/conversation.php:1364
msgid "Code"
msgstr "Code"
-#: ../../Zotlabs/Lib/ThreadItem.php:735
+#: ../../Zotlabs/Lib/ThreadItem.php:749
msgid "Image"
msgstr "Bild"
-#: ../../Zotlabs/Lib/ThreadItem.php:736
+#: ../../Zotlabs/Lib/ThreadItem.php:750
+msgid "Attach File"
+msgstr "Datei anhängen"
+
+#: ../../Zotlabs/Lib/ThreadItem.php:751
msgid "Insert Link"
msgstr "Link einfügen"
-#: ../../Zotlabs/Lib/ThreadItem.php:737
+#: ../../Zotlabs/Lib/ThreadItem.php:752
msgid "Video"
msgstr "Video"
-#: ../../Zotlabs/Lib/Enotify.php:60 ../../include/network.php:1914
-msgid "$Projectname Notification"
-msgstr "$Projectname-Benachrichtigung"
+#: ../../Zotlabs/Lib/ThreadItem.php:762
+msgid "Your full name (required)"
+msgstr "Ihr vollständiger Name (erforderlich)"
-#: ../../Zotlabs/Lib/Enotify.php:61 ../../extend/addon/addon/diaspora/p.php:46
-#: ../../extend/addon/addon/diaspora/util.php:218
-#: ../../extend/addon/addon/diaspora/util.php:231
-#: ../../include/network.php:1915
-msgid "$projectname"
-msgstr "$projectname"
+#: ../../Zotlabs/Lib/ThreadItem.php:763
+msgid "Your email address (required)"
+msgstr "Ihre E-Mail-Adresse (erforderlich)"
-#: ../../Zotlabs/Lib/Enotify.php:63 ../../include/network.php:1917
-msgid "Thank You,"
-msgstr "Danke."
+#: ../../Zotlabs/Lib/ThreadItem.php:764
+msgid "Your website URL (optional)"
+msgstr "Ihre Webseiten-URL (optional)"
-#: ../../Zotlabs/Lib/Enotify.php:65 ../../include/network.php:1919
-#, php-format
-msgid "%s Administrator"
-msgstr "der Administrator von %s"
+#: ../../Zotlabs/Zot/Auth.php:152
+msgid ""
+"Remote authentication blocked. You are logged into this site locally. Please"
+" logout and retry."
+msgstr "Fern-Authentifizierung blockiert. Du bist lokal auf diesem Server angemeldet. Bitte melde Dich ab und versuche es erneut."
-#: ../../Zotlabs/Lib/Enotify.php:116
+#: ../../Zotlabs/Zot/Auth.php:264 ../../addon/openid/Mod_Openid.php:76
+#: ../../addon/openid/Mod_Openid.php:178
#, php-format
-msgid "%s <!item_type!>"
-msgstr "%s <!item_type!>"
+msgid "Welcome %s. Remote authentication successful."
+msgstr "Willkommen %s. Entfernte Authentifizierung erfolgreich."
-#: ../../Zotlabs/Lib/Enotify.php:120
-#, php-format
-msgid "[$Projectname:Notify] New mail received at %s"
-msgstr "[$Projectname:Benachrichtigung] Neue Mail empfangen auf %s"
+#: ../../Zotlabs/Storage/Browser.php:107 ../../Zotlabs/Storage/Browser.php:238
+msgid "parent"
+msgstr "Übergeordnetes Verzeichnis"
-#: ../../Zotlabs/Lib/Enotify.php:122
-#, php-format
-msgid "%1$s, %2$s sent you a new private message at %3$s."
-msgstr "%1$s, %2$s hat Dir eine private Nachricht auf %3$s gesendet."
+#: ../../Zotlabs/Storage/Browser.php:131 ../../include/text.php:2707
+msgid "Collection"
+msgstr "Sammlung"
-#: ../../Zotlabs/Lib/Enotify.php:123
-#, php-format
-msgid "%1$s sent you %2$s."
-msgstr "%1$s hat Dir %2$s geschickt."
+#: ../../Zotlabs/Storage/Browser.php:134
+msgid "Principal"
+msgstr "Prinzipal"
-#: ../../Zotlabs/Lib/Enotify.php:123
-msgid "a private message"
-msgstr "eine private Nachricht"
+#: ../../Zotlabs/Storage/Browser.php:137
+msgid "Addressbook"
+msgstr "Adressbuch"
-#: ../../Zotlabs/Lib/Enotify.php:124
-#, php-format
-msgid "Please visit %s to view and/or reply to your private messages."
-msgstr "Bitte besuche %s, um die private Nachricht anzusehen und/oder darauf zu antworten."
+#: ../../Zotlabs/Storage/Browser.php:140
+msgid "Calendar"
+msgstr "Kalender"
-#: ../../Zotlabs/Lib/Enotify.php:183
-#, php-format
-msgid "%1$s, %2$s commented on [zrl=%3$s]a %4$s[/zrl]"
-msgstr "%1$s, %2$s hat [zrl=%3$s]einen %4$s[/zrl] kommentiert"
+#: ../../Zotlabs/Storage/Browser.php:143
+msgid "Schedule Inbox"
+msgstr "Posteingang für überwachte Kalender"
-#: ../../Zotlabs/Lib/Enotify.php:191
-#, php-format
-msgid "%1$s, %2$s commented on [zrl=%3$s]%4$s's %5$s[/zrl]"
-msgstr "%1$s, %2$s hat [zrl=%3$s]%4$ss %5$s[/zrl] kommentiert"
+#: ../../Zotlabs/Storage/Browser.php:146
+msgid "Schedule Outbox"
+msgstr "Postausgang für überwachte Kalender"
-#: ../../Zotlabs/Lib/Enotify.php:200
-#, php-format
-msgid "%1$s, %2$s commented on [zrl=%3$s]your %4$s[/zrl]"
-msgstr "%1$s, %2$s hat [zrl=%3$s]Deinen %4$s[/zrl] kommentiert"
+#: ../../Zotlabs/Storage/Browser.php:226
+msgid "Total"
+msgstr "Summe"
-#: ../../Zotlabs/Lib/Enotify.php:211
-#, php-format
-msgid "[$Projectname:Notify] Comment to conversation #%1$d by %2$s"
-msgstr "[$Projectname:Benachrichtigung] Kommentar in Unterhaltung #%1$d von %2$s"
+#: ../../Zotlabs/Storage/Browser.php:228
+msgid "Shared"
+msgstr "Geteilt"
-#: ../../Zotlabs/Lib/Enotify.php:212
+#: ../../Zotlabs/Storage/Browser.php:304
#, php-format
-msgid "%1$s, %2$s commented on an item/conversation you have been following."
-msgstr "%1$s, %2$s hat eine Unterhaltung kommentiert, der Du folgst."
+msgid "You are using %1$s of your available file storage."
+msgstr "Sie verwenden %1$s von Ihrem verfügbaren Dateispeicher."
-#: ../../Zotlabs/Lib/Enotify.php:215 ../../Zotlabs/Lib/Enotify.php:230
-#: ../../Zotlabs/Lib/Enotify.php:256 ../../Zotlabs/Lib/Enotify.php:274
-#: ../../Zotlabs/Lib/Enotify.php:288
+#: ../../Zotlabs/Storage/Browser.php:309
#, php-format
-msgid "Please visit %s to view and/or reply to the conversation."
-msgstr "Bitte besuche %s, um die Unterhaltung anzusehen und/oder zu kommentieren."
+msgid "You are using %1$s of %2$s available file storage. (%3$s&#37;)"
+msgstr "Sie verwenden %1$s von %2$s verfügbarem Dateispeicher. (%3$s&#37;)"
-#: ../../Zotlabs/Lib/Enotify.php:221
-#, php-format
-msgid "[$Projectname:Notify] %s posted to your profile wall"
-msgstr "[$Projectname:Benachrichtigung] %s schrieb auf Deine Pinnwand"
+#: ../../Zotlabs/Storage/Browser.php:320
+msgid "WARNING:"
+msgstr "WARNUNG:"
-#: ../../Zotlabs/Lib/Enotify.php:223
-#, php-format
-msgid "%1$s, %2$s posted to your profile wall at %3$s"
-msgstr "%1$s, %2$s hat auf Deine Pinnwand auf %3$s geschrieben"
+#: ../../Zotlabs/Storage/Browser.php:330
+msgid ""
+"Please use DAV to upload large (video, audio) files.<br>See <a class=\"zrl\""
+" href=\"help/member/member_guide#Cloud_Desktop_Clients\">Cloud Desktop "
+"Clients</a>"
+msgstr "Bitte verwende DAV, um große Dateien (Audio, Video) hochzuladen.<br>Für weitere Informationen siehe <a class=\"zrl\" href=\"help/member/member_guide#Cloud_Desktop_Clients\">Cloud Desktop Clients</a>"
-#: ../../Zotlabs/Lib/Enotify.php:225
-#, php-format
-msgid "%1$s, %2$s posted to [zrl=%3$s]your wall[/zrl]"
-msgstr "%1$s, %2$s hat auf [zrl=%3$s]Deine Pinnwand[/zrl] geschrieben"
+#: ../../Zotlabs/Storage/Browser.php:334
+msgid "Create new folder"
+msgstr "Neuen Ordner anlegen"
-#: ../../Zotlabs/Lib/Enotify.php:249
-#, php-format
-msgid "[$Projectname:Notify] %s tagged you"
-msgstr "[$Projectname:Benachrichtigung] %s hat Dich erwähnt"
+#: ../../Zotlabs/Storage/Browser.php:336
+msgid "Upload file"
+msgstr "Datei hochladen"
-#: ../../Zotlabs/Lib/Enotify.php:250
-#, php-format
-msgid "%1$s, %2$s tagged you at %3$s"
-msgstr "%1$s, %2$s hat Dich auf %3$s erwähnt"
+#: ../../Zotlabs/Storage/Browser.php:350
+msgid "Drop files here to immediately upload"
+msgstr "Dateien zum sofortigen Hochladen hier fallen lassen"
-#: ../../Zotlabs/Lib/Enotify.php:251
-#, php-format
-msgid "%1$s, %2$s [zrl=%3$s]tagged you[/zrl]."
-msgstr "%1$s, %2$s [zrl=%3$s]hat Dich erwähnt[/zrl]."
+#: ../../Zotlabs/Widget/Forums.php:85
+msgid "Forums"
+msgstr "Foren"
-#: ../../Zotlabs/Lib/Enotify.php:263
-#, php-format
-msgid "[$Projectname:Notify] %1$s poked you"
-msgstr "[$Projectname:Benachrichtigung] %1$s hat Dich angestupst"
+#: ../../Zotlabs/Widget/Cdav.php:37
+msgid "Select Channel"
+msgstr "Kanal auswählen"
-#: ../../Zotlabs/Lib/Enotify.php:264
-#, php-format
-msgid "%1$s, %2$s poked you at %3$s"
-msgstr "%1$s, %2$s hat Dich auf %3$s angestupst"
+#: ../../Zotlabs/Widget/Cdav.php:42
+msgid "Read-write"
+msgstr "Lesen-schreiben"
-#: ../../Zotlabs/Lib/Enotify.php:265
-#, php-format
-msgid "%1$s, %2$s [zrl=%2$s]poked you[/zrl]."
-msgstr "%1$s, %2$s [zrl=%2$s]hat Dich angestupst[/zrl]."
+#: ../../Zotlabs/Widget/Cdav.php:43
+msgid "Read-only"
+msgstr "Nur Lesen"
-#: ../../Zotlabs/Lib/Enotify.php:281
-#, php-format
-msgid "[$Projectname:Notify] %s tagged your post"
-msgstr "[$Projectname:Benachrichtigung] %s hat Deinen Beitrag verschlagwortet"
+#: ../../Zotlabs/Widget/Cdav.php:116
+msgid "My Calendars"
+msgstr "Meine Kalender"
-#: ../../Zotlabs/Lib/Enotify.php:282
-#, php-format
-msgid "%1$s, %2$s tagged your post at %3$s"
-msgstr "%1$s, %2$s hat Deinen Beitrag auf %3$s verschlagwortet"
+#: ../../Zotlabs/Widget/Cdav.php:118
+msgid "Shared Calendars"
+msgstr "Geteilte Kalender"
-#: ../../Zotlabs/Lib/Enotify.php:283
-#, php-format
-msgid "%1$s, %2$s tagged [zrl=%3$s]your post[/zrl]"
-msgstr "%1$s, %2$s hat [zrl=%3$s]Deinen Beitrag[/zrl] verschlagwortet"
+#: ../../Zotlabs/Widget/Cdav.php:122
+msgid "Share this calendar"
+msgstr "Diesen Kalender teilen"
-#: ../../Zotlabs/Lib/Enotify.php:295
-msgid "[$Projectname:Notify] Introduction received"
-msgstr "[$Projectname:Benachrichtigung] Verbindungsanfrage erhalten"
+#: ../../Zotlabs/Widget/Cdav.php:124
+msgid "Calendar name and color"
+msgstr "Kalendername und -farbe"
-#: ../../Zotlabs/Lib/Enotify.php:296
-#, php-format
-msgid "%1$s, you've received an new connection request from '%2$s' at %3$s"
-msgstr "%1$s, Du hast eine neue Verbindungsanfrage von '%2$s' auf %3$s erhalten"
+#: ../../Zotlabs/Widget/Cdav.php:126
+msgid "Create new calendar"
+msgstr "Neuen Kalender erstellen"
-#: ../../Zotlabs/Lib/Enotify.php:297
-#, php-format
-msgid ""
-"%1$s, you've received [zrl=%2$s]a new connection request[/zrl] from %3$s."
-msgstr "%1$s, Du hast [zrl=%2$s]eine neue Verbindungsanfrage[/zrl] von %3$s erhalten."
+#: ../../Zotlabs/Widget/Cdav.php:128
+msgid "Calendar Name"
+msgstr "Kalendername"
-#: ../../Zotlabs/Lib/Enotify.php:301 ../../Zotlabs/Lib/Enotify.php:320
-#, php-format
-msgid "You may visit their profile at %s"
-msgstr "Du kannst Dir das Profil unter %s ansehen"
+#: ../../Zotlabs/Widget/Cdav.php:129
+msgid "Calendar Tools"
+msgstr "Kalenderwerkzeuge"
-#: ../../Zotlabs/Lib/Enotify.php:303
-#, php-format
-msgid "Please visit %s to approve or reject the connection request."
-msgstr "Bitte besuche %s , um die Verbindungsanfrage anzunehmen oder abzulehnen."
+#: ../../Zotlabs/Widget/Cdav.php:130
+msgid "Import calendar"
+msgstr "Kalender importieren"
-#: ../../Zotlabs/Lib/Enotify.php:310
-msgid "[$Projectname:Notify] Friend suggestion received"
-msgstr "[$Projectname:Benachrichtigung] Freundschaftsvorschlag erhalten"
+#: ../../Zotlabs/Widget/Cdav.php:131
+msgid "Select a calendar to import to"
+msgstr "Kalender zum Hineinimportieren auswählen"
-#: ../../Zotlabs/Lib/Enotify.php:311
-#, php-format
-msgid "%1$s, you've received a friend suggestion from '%2$s' at %3$s"
-msgstr "%1$s, Du hast einen Kontaktvorschlag von „%2$s“ auf %3$s erhalten"
+#: ../../Zotlabs/Widget/Cdav.php:158
+msgid "Addressbooks"
+msgstr "Adressbücher"
-#: ../../Zotlabs/Lib/Enotify.php:312
-#, php-format
-msgid ""
-"%1$s, you've received [zrl=%2$s]a friend suggestion[/zrl] for %3$s from "
-"%4$s."
-msgstr "%1$s, Du hast [zrl=%2$s]einen Kontaktvorschlag[/zrl] für %3$s von %4$s erhalten."
+#: ../../Zotlabs/Widget/Cdav.php:160
+msgid "Addressbook name"
+msgstr "Adressbuchname"
-#: ../../Zotlabs/Lib/Enotify.php:318
-msgid "Name:"
-msgstr "Name:"
+#: ../../Zotlabs/Widget/Cdav.php:162
+msgid "Create new addressbook"
+msgstr "Neues Adressbuch erstellen"
-#: ../../Zotlabs/Lib/Enotify.php:319
-msgid "Photo:"
-msgstr "Foto:"
+#: ../../Zotlabs/Widget/Cdav.php:163
+msgid "Addressbook Name"
+msgstr "Adressbuchname"
-#: ../../Zotlabs/Lib/Enotify.php:322
-#, php-format
-msgid "Please visit %s to approve or reject the suggestion."
-msgstr "Bitte besuche %s um den Vorschlag zu akzeptieren oder abzulehnen."
+#: ../../Zotlabs/Widget/Cdav.php:165
+msgid "Addressbook Tools"
+msgstr "Adressbuchwerkzeuge"
-#: ../../Zotlabs/Lib/Enotify.php:540
-msgid "[$Projectname:Notify]"
-msgstr "[$Projectname:Benachrichtigung]"
+#: ../../Zotlabs/Widget/Cdav.php:166
+msgid "Import addressbook"
+msgstr "Adressbuch importieren"
-#: ../../Zotlabs/Lib/Enotify.php:700
-msgid "created a new post"
-msgstr "Neuer Beitrag wurde erzeugt"
+#: ../../Zotlabs/Widget/Cdav.php:167
+msgid "Select an addressbook to import to"
+msgstr "Adressbuch zum Hineinimportieren auswählen"
-#: ../../Zotlabs/Lib/Enotify.php:701
-#, php-format
-msgid "commented on %s's post"
-msgstr "hat %s's Beitrag kommentiert"
+#: ../../Zotlabs/Widget/Appcategories.php:39
+#: ../../Zotlabs/Widget/Tagcloud.php:25 ../../include/contact_widgets.php:91
+#: ../../include/contact_widgets.php:132 ../../include/taxonomy.php:285
+#: ../../include/taxonomy.php:367 ../../include/taxonomy.php:387
+msgid "Categories"
+msgstr "Kategorien"
-#: ../../extend/addon/addon/adultphotoflag/adultphotoflag.php:24
-msgid "Flag Adult Photos"
-msgstr "Nicht jugendfreie Fotos markieren"
+#: ../../Zotlabs/Widget/Appcategories.php:42 ../../Zotlabs/Widget/Filer.php:31
+#: ../../include/contact_widgets.php:56 ../../include/contact_widgets.php:94
+#: ../../include/contact_widgets.php:135
+msgid "Everything"
+msgstr "Alles"
-#: ../../extend/addon/addon/adultphotoflag/adultphotoflag.php:25
-msgid ""
-"Provide photo edit option to hide inappropriate photos from default album "
-"view"
-msgstr "Stellt eine Option zum Verstecken von Fotos mit unangemessenen Inhalten in der Standard-Albumansicht bereit"
+#: ../../Zotlabs/Widget/Eventstools.php:13
+msgid "Events Tools"
+msgstr "Kalenderwerkzeuge"
-#: ../../extend/addon/addon/chords/Mod_Chords.php:44
-msgid ""
-"This is a fairly comprehensive and complete guitar chord dictionary which "
-"will list most of the available ways to play a certain chord, starting from "
-"the base of the fingerboard up to a few frets beyond the twelfth fret "
-"(beyond which everything repeats). A couple of non-standard tunings are "
-"provided for the benefit of slide players, etc."
-msgstr ""
+#: ../../Zotlabs/Widget/Eventstools.php:14
+msgid "Export Calendar"
+msgstr "Kalender exportieren"
-#: ../../extend/addon/addon/chords/Mod_Chords.php:46
-msgid ""
-"Chord names start with a root note (A-G) and may include sharps (#) and "
-"flats (b). This software will parse most of the standard naming conventions "
-"such as maj, min, dim, sus(2 or 4), aug, with optional repeating elements."
-msgstr ""
+#: ../../Zotlabs/Widget/Eventstools.php:15
+msgid "Import Calendar"
+msgstr "Kalender importieren"
-#: ../../extend/addon/addon/chords/Mod_Chords.php:48
-msgid ""
-"Valid examples include A, A7, Am7, Amaj7, Amaj9, Ammaj7, Aadd4, Asus2Add4, "
-"E7b13b11 ..."
-msgstr "Einige gültige Beispiele: A, A7, Am7, Amaj7, Amaj9, Ammaj7, Aadd4, Asus2Add4, E7b13b11 ..."
+#: ../../Zotlabs/Widget/Suggestedchats.php:32
+msgid "Suggested Chatrooms"
+msgstr "Chatraum-Vorschläge"
-#: ../../extend/addon/addon/chords/Mod_Chords.php:51
-msgid "Guitar Chords"
-msgstr "Gitarrenakkorde"
+#: ../../Zotlabs/Widget/Mailmenu.php:13
+msgid "Private Mail Menu"
+msgstr "Private Nachrichten"
-#: ../../extend/addon/addon/chords/Mod_Chords.php:52
-msgid "The complete online chord dictionary"
-msgstr "Das komplette online Akkord-Verzeichnis"
+#: ../../Zotlabs/Widget/Mailmenu.php:15
+msgid "Combined View"
+msgstr "Kombinierte Anzeige"
-#: ../../extend/addon/addon/chords/Mod_Chords.php:57
-msgid "Tuning"
-msgstr "Stimmen"
+#: ../../Zotlabs/Widget/Mailmenu.php:20 ../../include/nav.php:119
+msgid "Inbox"
+msgstr "Eingang"
-#: ../../extend/addon/addon/chords/Mod_Chords.php:58
-msgid "Chord name: example: Em7"
-msgstr "Beispiel Akkord Name: Em7"
+#: ../../Zotlabs/Widget/Mailmenu.php:25 ../../include/nav.php:120
+msgid "Outbox"
+msgstr "Ausgang"
-#: ../../extend/addon/addon/chords/Mod_Chords.php:59
-msgid "Show for left handed stringing"
-msgstr "Linkshänder-Besaitung anzeigen"
+#: ../../Zotlabs/Widget/Mailmenu.php:30 ../../include/nav.php:121
+msgid "New Message"
+msgstr "Neue Nachricht"
-#: ../../extend/addon/addon/chords/chords.php:33
-msgid "Quick Reference"
-msgstr "Schnellreferenz"
+#: ../../Zotlabs/Widget/Chatroom_list.php:16
+#: ../../include/conversation.php:1847 ../../include/conversation.php:1850
+#: ../../include/nav.php:455 ../../include/nav.php:458
+msgid "Chatrooms"
+msgstr "Chaträume"
-#: ../../extend/addon/addon/diaspora/diaspora.php:671
-msgid "Diaspora Protocol Settings updated."
-msgstr "Diaspora-Protokolleinstellungen aktualisiert."
+#: ../../Zotlabs/Widget/Chatroom_list.php:20
+msgid "Overview"
+msgstr "Übersicht"
-#: ../../extend/addon/addon/diaspora/diaspora.php:692
-msgid "Enable the Diaspora protocol for this channel"
-msgstr "Diaspora-Protokoll für diesen Kanal aktivieren"
+#: ../../Zotlabs/Widget/Rating.php:51
+msgid "Rating Tools"
+msgstr "Bewertungswerkzeuge"
-#: ../../extend/addon/addon/diaspora/diaspora.php:696
-msgid "Allow any Diaspora member to comment on your public posts"
-msgstr "Jedem Diaspora-Mitglied erlauben, Deine öffentlichen Beiträge zu kommentieren"
+#: ../../Zotlabs/Widget/Rating.php:55 ../../Zotlabs/Widget/Rating.php:57
+msgid "Rate Me"
+msgstr "Bewerte mich"
-#: ../../extend/addon/addon/diaspora/diaspora.php:700
-msgid "Prevent your hashtags from being redirected to other sites"
-msgstr "Verhindern, dass Deine hashtags zu anderen Seiten umgeleitet werden"
+#: ../../Zotlabs/Widget/Rating.php:60
+msgid "View Ratings"
+msgstr "Bewertungen ansehen"
-#: ../../extend/addon/addon/diaspora/diaspora.php:705
-msgid "Followed hashtags (comma separated, do not include the #)"
-msgstr "Verfolgte Hashtags (Komma separierte Liste, ohne die #)"
+#: ../../Zotlabs/Widget/Activity.php:50
+msgctxt "widget"
+msgid "Activity"
+msgstr "Aktivität"
-#: ../../extend/addon/addon/diaspora/diaspora.php:710
-msgid "Diaspora Protocol Settings"
-msgstr "Diaspora-Protokolleinstellungen"
+#: ../../Zotlabs/Widget/Follow.php:22
+#, php-format
+msgid "You have %1$.0f of %2$.0f allowed connections."
+msgstr "Du bist %1$.0f von maximal %2$.0f erlaubten Verbindungen eingegangen."
-#: ../../extend/addon/addon/dirstats/dirstats.php:94
-msgid "Hubzilla Directory Stats"
-msgstr "Hubzilla-Verzeichnisstatistiken"
+#: ../../Zotlabs/Widget/Follow.php:29
+msgid "Add New Connection"
+msgstr "Neue Verbindung hinzufügen"
-#: ../../extend/addon/addon/dirstats/dirstats.php:95
-msgid "Total Hubs"
-msgstr "Hubs insgesamt"
+#: ../../Zotlabs/Widget/Follow.php:30
+msgid "Enter channel address"
+msgstr "Adresse des Kanals eingeben"
-#: ../../extend/addon/addon/dirstats/dirstats.php:97
-msgid "Hubzilla Hubs"
-msgstr "Hubzilla Hubs"
+#: ../../Zotlabs/Widget/Follow.php:31
+msgid "Examples: bob@example.com, https://example.com/barbara"
+msgstr "Beispiele: bob@beispiel.com, http://beispiel.com/barbara"
-#: ../../extend/addon/addon/dirstats/dirstats.php:99
-msgid "Friendica Hubs"
-msgstr "Friendica Hubs"
+#: ../../Zotlabs/Widget/Wiki_list.php:15 ../../addon/gitwiki/gitwiki.php:95
+msgid "Wiki List"
+msgstr "Wikiliste"
-#: ../../extend/addon/addon/dirstats/dirstats.php:101
-msgid "Diaspora Pods"
-msgstr "Diaspora Pods"
+#: ../../Zotlabs/Widget/Archive.php:43
+msgid "Archives"
+msgstr "Archive"
-#: ../../extend/addon/addon/dirstats/dirstats.php:103
-msgid "Hubzilla Channels"
-msgstr "Hubzilla-Kanäle"
+#: ../../Zotlabs/Widget/Conversations.php:17
+msgid "Received Messages"
+msgstr "Erhaltene Nachrichten"
-#: ../../extend/addon/addon/dirstats/dirstats.php:105
-msgid "Friendica Channels"
-msgstr "Friendica-Kanäle"
+#: ../../Zotlabs/Widget/Conversations.php:21
+msgid "Sent Messages"
+msgstr "Gesendete Nachrichten"
-#: ../../extend/addon/addon/dirstats/dirstats.php:107
-msgid "Diaspora Channels"
-msgstr "Diaspora-Kanäle"
+#: ../../Zotlabs/Widget/Conversations.php:25
+msgid "Conversations"
+msgstr "Konversationen"
-#: ../../extend/addon/addon/dirstats/dirstats.php:109
-msgid "Aged 35 and above"
-msgstr "35 und älter"
+#: ../../Zotlabs/Widget/Conversations.php:35
+msgid "No messages."
+msgstr "Keine Nachrichten."
-#: ../../extend/addon/addon/dirstats/dirstats.php:111
-msgid "Aged 34 and under"
-msgstr "34 und jünger"
+#: ../../Zotlabs/Widget/Conversations.php:55
+msgid "Delete conversation"
+msgstr "Unterhaltung löschen"
-#: ../../extend/addon/addon/dirstats/dirstats.php:113
-msgid "Average Age"
-msgstr "Durchschnittsalter"
+#: ../../Zotlabs/Widget/Chatroom_members.php:11
+msgid "Chat Members"
+msgstr "Chatmitglieder"
-#: ../../extend/addon/addon/dirstats/dirstats.php:115
-msgid "Known Chatrooms"
-msgstr "Bekannte Chaträume"
+#: ../../Zotlabs/Widget/Photo.php:48 ../../Zotlabs/Widget/Photo_rand.php:58
+msgid "photo/image"
+msgstr "Foto/Bild"
-#: ../../extend/addon/addon/dirstats/dirstats.php:117
-msgid "Known Tags"
-msgstr "Bekannte Schlagwörter"
+#: ../../Zotlabs/Widget/Savedsearch.php:75
+msgid "Remove term"
+msgstr "Eintrag löschen"
-#: ../../extend/addon/addon/dirstats/dirstats.php:119
-msgid ""
-"Please note Diaspora and Friendica statistics are merely those **this "
-"directory** is aware of, and not all those known in the network. This also "
-"applies to chatrooms,"
-msgstr "Bitte berücksichtige, dass Diaspora und Friendica Statistiken nur solche einschließen, die **diesem Verzeichnis** bekannt sind, nicht alle im Netzwerk bekannten. Das gilt auch für Chaträume."
+#: ../../Zotlabs/Widget/Savedsearch.php:83 ../../include/features.php:306
+msgid "Saved Searches"
+msgstr "Gespeicherte Suchanfragen"
-#: ../../extend/addon/addon/donate/donate.php:21
-msgid "Project Servers and Resources"
-msgstr "Projektserver und -ressourcen"
+#: ../../Zotlabs/Widget/Savedsearch.php:84 ../../include/group.php:337
+msgid "add"
+msgstr "hinzufügen"
-#: ../../extend/addon/addon/donate/donate.php:22
-msgid "Project Creator and Tech Lead"
-msgstr "Projektersteller und Technischer Leiter"
+#: ../../Zotlabs/Widget/Notes.php:16
+msgid "Notes"
+msgstr "Notizen"
-#: ../../extend/addon/addon/donate/donate.php:23
-msgid "Admin, developer, directorymin, support bloke"
-msgstr "Administrator, Entwickler, Verzeichnis Betreibender, Supportleistende"
+#: ../../Zotlabs/Widget/Wiki_pages.php:47 ../../addon/gitwiki/gitwiki.php:76
+msgid "Wiki Pages"
+msgstr "Wikiseiten"
-#: ../../extend/addon/addon/donate/donate.php:50
-msgid ""
-"And the hundreds of other people and organisations who helped make the "
-"Hubzilla possible."
-msgstr "Und die hunderte anderen Menschen und Organisationen, die geholfen haben Hubzilla möglich zu machen."
+#: ../../Zotlabs/Widget/Wiki_pages.php:53 ../../addon/gitwiki/gitwiki.php:81
+msgid "Add new page"
+msgstr "Neue Seite hinzufügen"
-#: ../../extend/addon/addon/donate/donate.php:53
-msgid ""
-"The Redmatrix/Hubzilla projects are provided primarily by volunteers giving "
-"their time and expertise - and often paying out of pocket for services they "
-"share with others."
-msgstr "Die Redmatrix/Hubzilla Projekte werden hauptsächlich von Freiwilligen bereitgestellt, die ihre Zeit und Expertise zur Verfügung stellen - und oft aus eigener Tasche für die Dienste zahlen, die sie mit anderen teilen."
+#: ../../Zotlabs/Widget/Wiki_pages.php:58 ../../addon/gitwiki/gitwiki.php:82
+msgid "Page name"
+msgstr "Seitenname"
-#: ../../extend/addon/addon/donate/donate.php:54
-msgid ""
-"There is no corporate funding and no ads, and we do not collect and sell "
-"your personal information. (We don't control your personal information - "
-"<strong>you do</strong>.)"
-msgstr "Es gibt keine Finanzierung durch Firmen, keine Werbung und wir verkaufen Deine persönlichen Daten nicht. (Wir kontrollieren Deine persönlichen Daten nicht - <strong>das machst Du</strong>.)"
+#: ../../Zotlabs/Widget/Affinity.php:49
+msgid "Refresh"
+msgstr "Aktualisieren"
-#: ../../extend/addon/addon/donate/donate.php:55
-msgid ""
-"Help support our ground-breaking work in decentralisation, web identity, and"
-" privacy."
-msgstr "Hilf uns bei unserer wegweisenden Arbeit im Bereich der Dezantralisation, von Web-Identitäten und Privatsphäre."
+#: ../../Zotlabs/Widget/Tasklist.php:23
+msgid "Tasks"
+msgstr "Aufgaben"
-#: ../../extend/addon/addon/donate/donate.php:57
-msgid ""
-"Your donations keep servers and services running and also helps us to "
-"provide innovative new features and continued development."
-msgstr "Die Spenden werden dafür verwendet Server und Dienste am laufen zu halten und helfen desweiteren innovative Neuerungen zu schaffen und die Entwicklung voran zu treiben."
+#: ../../Zotlabs/Widget/Suggestions.php:51
+msgid "Suggestions"
+msgstr "Vorschläge"
-#: ../../extend/addon/addon/donate/donate.php:60
-msgid "Donate"
-msgstr "Spenden"
+#: ../../Zotlabs/Widget/Suggestions.php:52
+msgid "See more..."
+msgstr "Mehr anzeigen …"
-#: ../../extend/addon/addon/donate/donate.php:62
-msgid ""
-"Choose a project, developer, or public hub to support with a one-time "
-"donation"
-msgstr "Wähle ein Projekt, einen Entwickler oder einen öffentlichen Hub den du mit einer einmaligen Spende unterstützen willst."
+#: ../../Zotlabs/Widget/Filer.php:28 ../../include/contact_widgets.php:53
+#: ../../include/features.php:395
+msgid "Saved Folders"
+msgstr "Gespeicherte Ordner"
-#: ../../extend/addon/addon/donate/donate.php:63
-msgid "Donate Now"
-msgstr "Jetzt spenden"
+#: ../../Zotlabs/Widget/Cover_photo.php:54
+msgid "Click to show more"
+msgstr "Klick, um mehr anzuzeigen"
-#: ../../extend/addon/addon/donate/donate.php:64
-msgid ""
-"<strong><em>Or</em></strong> become a project sponsor (Hubzilla Project "
-"only)"
-msgstr "<strong><em>Oder</em></strong> werde ein Unterstützer des Projekts (ausschließlich Hubzilla)"
+#: ../../Zotlabs/Widget/Admin.php:23 ../../Zotlabs/Widget/Admin.php:60
+msgid "Member registrations waiting for confirmation"
+msgstr "Nutzer-Anmeldungen, die auf Bestätigung warten"
-#: ../../extend/addon/addon/donate/donate.php:65
-msgid ""
-"Please indicate if you would like your first name or full name (or nothing) "
-"to appear in our sponsor listing"
-msgstr "Bitte teile uns mit ob dein kompletter Name oder dein Vorname (oder gar nichts) auf unserer Sponsoren-Seite veröffentlicht werden soll."
+#: ../../Zotlabs/Widget/Admin.php:29
+msgid "Inspect queue"
+msgstr "Warteschlange kontrollieren"
-#: ../../extend/addon/addon/donate/donate.php:66
-msgid "Sponsor"
-msgstr "Sponsor"
+#: ../../Zotlabs/Widget/Admin.php:31
+msgid "DB updates"
+msgstr "DB-Aktualisierungen"
-#: ../../extend/addon/addon/donate/donate.php:69
-msgid "Special thanks to: "
-msgstr "Besonderer Dank an: "
+#: ../../Zotlabs/Widget/Admin.php:55 ../../include/nav.php:224
+msgid "Admin"
+msgstr "Administration"
-#: ../../extend/addon/addon/dwpost/dwpost.php:42
-msgid "Post to Dreamwidth"
-msgstr "Bei Dreamwidth veröffentlichen"
+#: ../../Zotlabs/Widget/Admin.php:56
+msgid "Plugin Features"
+msgstr "Plug-In Funktionen"
-#: ../../extend/addon/addon/dwpost/dwpost.php:73
-msgid "Enable Dreamwidth Post Plugin"
-msgstr "Aktiviere das Dreamwidth-Plugin"
+#: ../../Zotlabs/Widget/Settings_menu.php:35
+msgid "Account settings"
+msgstr "Konto-Einstellungen"
-#: ../../extend/addon/addon/dwpost/dwpost.php:77
-msgid "Dreamwidth username"
-msgstr "Dreamwidth-Benutzername"
+#: ../../Zotlabs/Widget/Settings_menu.php:41
+msgid "Channel settings"
+msgstr "Kanal-Einstellungen"
-#: ../../extend/addon/addon/dwpost/dwpost.php:81
-msgid "Dreamwidth password"
-msgstr "Dreamwidth-Passwort"
+#: ../../Zotlabs/Widget/Settings_menu.php:50
+msgid "Additional features"
+msgstr "Zusätzliche Funktionen"
-#: ../../extend/addon/addon/dwpost/dwpost.php:85
-msgid "Post to Dreamwidth by default"
-msgstr "Standardmäßig auf auf Dreamwidth posten"
+#: ../../Zotlabs/Widget/Settings_menu.php:57
+msgid "Feature/Addon settings"
+msgstr "Plugin-Einstellungen"
-#: ../../extend/addon/addon/dwpost/dwpost.php:89
-msgid "Dreamwidth Post Settings"
-msgstr "Dreamwidth-Beitragseinstellungen"
+#: ../../Zotlabs/Widget/Settings_menu.php:63
+msgid "Display settings"
+msgstr "Anzeige-Einstellungen"
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:45
-msgid "Flattr this!"
-msgstr "Flattr this!"
+#: ../../Zotlabs/Widget/Settings_menu.php:70
+msgid "Manage locations"
+msgstr "Klon-Adressen verwalten"
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:83
-msgid "Flattr widget settings updated."
-msgstr "Flattr Widget Einstellungen aktualisiert"
+#: ../../Zotlabs/Widget/Settings_menu.php:77
+msgid "Export channel"
+msgstr "Kanal exportieren"
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:100
-msgid "Flattr user"
-msgstr "Flattr Nutzer"
+#: ../../Zotlabs/Widget/Settings_menu.php:84
+msgid "Connected apps"
+msgstr "Verbundene Apps"
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:104
-msgid "URL of the Thing to flattr"
-msgstr "URL des Dings zum flattrn"
+#: ../../Zotlabs/Widget/Settings_menu.php:100 ../../include/features.php:158
+msgid "Permission Groups"
+msgstr "Berechtigungsrollen"
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:104
-msgid "If empty channel URL is used"
-msgstr "Falls leer wird die Channel URL verwendet"
+#: ../../Zotlabs/Widget/Settings_menu.php:117
+msgid "Premium Channel Settings"
+msgstr "Premium-Kanal-Einstellungen"
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:108
-msgid "Title of the Thing to flattr"
-msgstr "Titel des Dings zum flattrn"
+#: ../../Zotlabs/Widget/Bookmarkedchats.php:24
+msgid "Bookmarked Chatrooms"
+msgstr "Gespeicherte Chatrooms"
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:108
-msgid "If empty \"channel name on The Hubzilla\" will be used"
-msgstr "Falls leer wird \"Kanalname auf The Hubzilla\" verwendet"
+#: ../../Zotlabs/Widget/Notifications.php:16
+msgid "New Network Activity"
+msgstr "Neue Netzwerk-Aktivitäten"
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:112
-msgid "Static or dynamic flattr button"
-msgstr "Statischer oder dynamischer Flattr Button"
+#: ../../Zotlabs/Widget/Notifications.php:17
+msgid "New Network Activity Notifications"
+msgstr "Benachrichtigungen für neue Netzwerk-Aktivitäten"
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:112
-msgid "static"
-msgstr "statisch"
+#: ../../Zotlabs/Widget/Notifications.php:20 ../../include/nav.php:99
+msgid "View your network activity"
+msgstr "Zeige Deine Netzwerk-Aktivitäten"
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:112
-msgid "dynamic"
-msgstr "dynamisch"
+#: ../../Zotlabs/Widget/Notifications.php:24
+msgid "Mark all notifications read"
+msgstr "Alle Benachrichtigungen als gesehen markieren"
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:116
-msgid "Alignment of the widget"
-msgstr "Ausrichtung des Widgets"
+#: ../../Zotlabs/Widget/Notifications.php:32
+msgid "New Home Activity"
+msgstr "Neue Kanal-Aktivitäten"
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:116
-msgid "left"
-msgstr "links"
+#: ../../Zotlabs/Widget/Notifications.php:33
+msgid "New Home Activity Notifications"
+msgstr "Benachrichtigungen für neue Kanal-Aktivitäten"
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:116
-msgid "right"
-msgstr "rechts"
+#: ../../Zotlabs/Widget/Notifications.php:36
+msgid "View your home activity"
+msgstr "Zeige Deine Kanal-Aktivitäten"
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:120
-msgid "Enable Flattr widget"
-msgstr "Flattr Widget verwenden"
+#: ../../Zotlabs/Widget/Notifications.php:40
+#: ../../Zotlabs/Widget/Notifications.php:136
+msgid "Mark all notifications seen"
+msgstr "Alle Benachrichtigungen als gesehen markieren"
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:124
-msgid "Flattr Widget Settings"
-msgstr "Flattr Widget Einstellungen"
+#: ../../Zotlabs/Widget/Notifications.php:48
+msgid "New Mails"
+msgstr "Neue Mails"
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:118
-msgid "Contact not found."
-msgstr "Kontakt nicht gefunden."
+#: ../../Zotlabs/Widget/Notifications.php:49
+msgid "New Mails Notifications"
+msgstr "Benachrichtigungen für neue Mails"
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:119
-msgid ""
-"This may occasionally happen if contact was requested by both persons and it"
-" has already been approved."
-msgstr "Dies kann unter Umständen passieren, wenn der Kontakt von beiden Seiten aus angefragt wurde und er bereits akzeptiert wurde.."
+#: ../../Zotlabs/Widget/Notifications.php:52
+msgid "View your private mails"
+msgstr "Zeige Deine persönlichen Mails"
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:238
-msgid "Response from remote site was not understood."
-msgstr "Antwort des entfernten Seite war unverständlich."
+#: ../../Zotlabs/Widget/Notifications.php:56
+msgid "Mark all messages seen"
+msgstr "Alle Mails als gelesen markieren"
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:247
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:252
-msgid "Unexpected response from remote site: "
-msgstr "Unerwartete Antwort der entfernten Seite"
+#: ../../Zotlabs/Widget/Notifications.php:64
+msgid "New Events"
+msgstr "Neue Termine"
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:261
-msgid "Confirmation completed successfully."
-msgstr "Bestätigung erfolgreich abgeschlossen."
+#: ../../Zotlabs/Widget/Notifications.php:65
+msgid "New Events Notifications"
+msgstr "Benachrichtigungen für neue Termine"
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:263
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:277
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:284
-msgid "Remote site reported: "
-msgstr "Meldung der entfernten Seite"
+#: ../../Zotlabs/Widget/Notifications.php:68 ../../include/nav.php:125
+msgid "View events"
+msgstr "Termine ansehen"
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:275
-msgid "Temporary failure. Please wait and try again."
-msgstr "Vorübergehende Störung. Bitte warte einen Moment und versuche es später erneut."
+#: ../../Zotlabs/Widget/Notifications.php:72 ../../include/nav.php:126
+msgid "Mark all events seen"
+msgstr "Markiere alle Termine als gesehen"
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:282
-msgid "Introduction failed or was revoked."
-msgstr "Vorstellung fehlgeschlagen oder wurde zurück gezogen."
+#: ../../Zotlabs/Widget/Notifications.php:81
+msgid "New Connections Notifications"
+msgstr "Benachrichtigungen für neue Verbindungen"
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:428
-msgid "Unable to set contact photo."
-msgstr "Konnte das Kontakt-Photo nicht setzen."
+#: ../../Zotlabs/Widget/Notifications.php:84
+msgid "View all connections"
+msgstr "Zeige alle Verbindungen"
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:485
-#, php-format
-msgid "%1$s is now friends with %2$s"
-msgstr "%1$s ist nun mit %2$s befreundet"
+#: ../../Zotlabs/Widget/Notifications.php:92
+msgid "New Files"
+msgstr "Neue Dateien"
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:570
-#, php-format
-msgid "No user record found for '%s' "
-msgstr "Kein Benutzereintrag für '%s' gefunden"
+#: ../../Zotlabs/Widget/Notifications.php:93
+msgid "New Files Notifications"
+msgstr "Benachrichtigungen für neue Dateien"
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:580
-msgid "Our site encryption key is apparently messed up."
-msgstr "Der Verschlüsselungsschlüssel unserer Seite ist anscheinend kaputt."
+#: ../../Zotlabs/Widget/Notifications.php:100
+#: ../../Zotlabs/Widget/Notifications.php:101 ../../include/nav.php:112
+msgid "Notices"
+msgstr "Benachrichtigungen"
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:591
-msgid "Empty site URL was provided or URL could not be decrypted by us."
-msgstr "Eine leere Seiten URL wurde angegeben, oder die URL konnte von uns nicht entziffert werden."
+#: ../../Zotlabs/Widget/Notifications.php:104
+msgid "View all notices"
+msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:612
-msgid "Contact record was not found for you on our site."
-msgstr "Für dich wurden keinerlei Kontaktdaten auf unserer Seite gefunden."
+#: ../../Zotlabs/Widget/Notifications.php:108
+msgid "Mark all notices seen"
+msgstr ""
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:626
-#, php-format
-msgid "Site public key not available in contact record for URL %s."
-msgstr "Der öffentliche Schlüssel dieser Seite ist für die Kontaktdaten mit der URL %s nocht verfügbar."
+#: ../../Zotlabs/Widget/Notifications.php:118
+msgid "New Registrations"
+msgstr "Neue Registrierungen"
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:646
-msgid ""
-"The ID provided by your system is a duplicate on our system. It should work "
-"if you try again."
-msgstr "Die ID, die Durch Dein System angegeben wurde ist ein Duplikat auf unserem. Es sollte funktionieren, wenn Du es noch einmal versuchst."
+#: ../../Zotlabs/Widget/Notifications.php:119
+msgid "New Registrations Notifications"
+msgstr "Benachrichtigungen für neue Registrierungen"
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:657
-msgid "Unable to set your contact credentials on our system."
-msgstr ""
+#: ../../Zotlabs/Widget/Notifications.php:129
+msgid "Public Stream Notifications"
+msgstr "Benachrichtigungen für öffentlichen Beitrags-Stream"
+
+#: ../../Zotlabs/Widget/Notifications.php:132
+msgid "View the public stream"
+msgstr "Zeige öffentlichen Beitrags-Stream"
+
+#: ../../Zotlabs/Widget/Notifications.php:143
+#: ../../include/conversation.php:871 ../../include/nav.php:305
+msgid "Loading..."
+msgstr "Lädt ..."
+
+#: ../../util/nconfig.php:34
+msgid "Source channel not found."
+msgstr "Quellkanal nicht gefunden."
+
+#: ../../boot.php:1619
+msgid "Create an account to access services and applications"
+msgstr "Erstelle ein Konto, um auf Dienste und Anwendungen zugreifen zu können."
+
+#: ../../boot.php:1638 ../../include/nav.php:138 ../../include/nav.php:167
+#: ../../include/nav.php:184
+msgid "Logout"
+msgstr "Abmelden"
+
+#: ../../boot.php:1642
+msgid "Login/Email"
+msgstr "Anmelden/E-Mail"
+
+#: ../../boot.php:1643
+msgid "Password"
+msgstr "Kennwort"
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:724
-msgid "Unable to update your contact profile details on our system"
-msgstr "Konnte die Details deines Profils auf unserem System nicht aktualisieren."
+#: ../../boot.php:1644
+msgid "Remember me"
+msgstr "Angaben speichern"
+
+#: ../../boot.php:1647
+msgid "Forgot your password?"
+msgstr "Passwort vergessen?"
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:751
-#: ../../extend/addon/addon/friendica/dfrn_request.php:749
-msgid "[Name Withheld]"
-msgstr "[Name zurück gehalten]"
+#: ../../boot.php:2191
+msgid "toggle mobile"
+msgstr "auf/von mobile Ansicht wechseln"
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:796
+#: ../../boot.php:2344
#, php-format
-msgid "%1$s has joined %2$s"
-msgstr "%1$s ist %2$s beigetreten"
+msgid "[$Projectname] Website SSL error for %s"
+msgstr "[$Projectname] Webseiten-SSL-Fehler für %s"
+
+#: ../../boot.php:2349
+msgid "Website SSL certificate is not valid. Please correct."
+msgstr "Das SSL-Zertifikat der Website ist nicht gültig. Bitte beheben."
-#: ../../extend/addon/addon/friendica/dfrn_poll.php:103
-#: ../../extend/addon/addon/friendica/dfrn_poll.php:536
+#: ../../boot.php:2468
#, php-format
-msgid "%1$s welcomes %2$s"
-msgstr "%1$s heißt %2$s willkommen"
+msgid "[$Projectname] Cron tasks not running on %s"
+msgstr "[$Projectname] Cron-Jobs laufen nicht auf %s"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:102
-msgid "This introduction has already been accepted."
-msgstr "Die Vorstellung wurde bereits akzeptiert."
+#: ../../boot.php:2473
+msgid "Cron/Scheduled tasks not running."
+msgstr "Cron-Aufgaben laufen nicht."
-#: ../../extend/addon/addon/friendica/dfrn_request.php:123
-#: ../../extend/addon/addon/friendica/dfrn_request.php:528
-msgid "Profile location is not valid or does not contain profile information."
-msgstr ""
+#: ../../boot.php:2474 ../../include/datetime.php:286
+msgid "never"
+msgstr "Nie"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:128
-#: ../../extend/addon/addon/friendica/dfrn_request.php:533
-msgid "Warning: profile location has no identifiable owner name."
-msgstr ""
+#: ../../view/theme/redbasic_c/php/config.php:16
+#: ../../view/theme/redbasic_c/php/config.php:19
+#: ../../view/theme/redbasic/php/config.php:16
+#: ../../view/theme/redbasic/php/config.php:19
+msgid "Focus (Hubzilla default)"
+msgstr "Focus (Voreinstellung für Hubzilla)"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:130
-#: ../../extend/addon/addon/friendica/dfrn_request.php:535
-msgid "Warning: profile location has no profile photo."
-msgstr ""
+#: ../../view/theme/redbasic_c/php/config.php:99
+#: ../../view/theme/redbasic/php/config.php:97
+msgid "Theme settings"
+msgstr "Design-Einstellungen"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:133
-#: ../../extend/addon/addon/friendica/dfrn_request.php:538
-#, php-format
-msgid "%d required parameter was not found at the given location"
-msgid_plural "%d required parameters were not found at the given location"
-msgstr[0] ""
-msgstr[1] ""
+#: ../../view/theme/redbasic_c/php/config.php:100
+#: ../../view/theme/redbasic/php/config.php:98
+msgid "Narrow navbar"
+msgstr "Schmale Navigationsleiste"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:180
-msgid "Introduction complete."
-msgstr "Einführung abgeschlossen."
+#: ../../view/theme/redbasic_c/php/config.php:101
+#: ../../view/theme/redbasic/php/config.php:99
+msgid "Navigation bar background color"
+msgstr "Hintergrundfarbe der Navigationsleiste"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:224
-msgid "Unrecoverable protocol error."
-msgstr "Nicht behebbarer Protokollfehler."
+#: ../../view/theme/redbasic_c/php/config.php:102
+#: ../../view/theme/redbasic/php/config.php:100
+msgid "Navigation bar icon color "
+msgstr "Farbe für die Icons der Navigationsleiste"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:252
-msgid "Profile unavailable."
-msgstr "Profil nicht verfügbar."
+#: ../../view/theme/redbasic_c/php/config.php:103
+#: ../../view/theme/redbasic/php/config.php:101
+msgid "Navigation bar active icon color "
+msgstr "Farbe für aktive Icons der Navigationsleiste"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:277
-#, php-format
-msgid "%s has received too many connection requests today."
-msgstr "%s hat heute bereits zu viele Kontaktanfragen erhalten."
+#: ../../view/theme/redbasic_c/php/config.php:104
+#: ../../view/theme/redbasic/php/config.php:102
+msgid "Link color"
+msgstr "Linkfarbe"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:278
-msgid "Spam protection measures have been invoked."
-msgstr "Maßnahmen zum Spam-Schutz wurden aktiviert."
+#: ../../view/theme/redbasic_c/php/config.php:105
+#: ../../view/theme/redbasic/php/config.php:103
+msgid "Set font-color for banner"
+msgstr "Farbe der Schrift des Banners"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:279
-msgid "Friends are advised to please try again in 24 hours."
-msgstr "Freunde sollten es bitte in 24 Stunden erneut versuchen."
+#: ../../view/theme/redbasic_c/php/config.php:106
+#: ../../view/theme/redbasic/php/config.php:104
+msgid "Set the background color"
+msgstr "Hintergrundfarbe"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:341
-msgid "Invalid locator"
-msgstr ""
+#: ../../view/theme/redbasic_c/php/config.php:107
+#: ../../view/theme/redbasic/php/config.php:105
+msgid "Set the background image"
+msgstr "Hintergrundbild"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:350
-msgid "Invalid email address."
-msgstr "Ungültige E-Mail-Adresse."
+#: ../../view/theme/redbasic_c/php/config.php:108
+#: ../../view/theme/redbasic/php/config.php:106
+msgid "Set the background color of items"
+msgstr "Hintergrundfarbe für Beiträge"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:377
-msgid "This account has not been configured for email. Request failed."
-msgstr "Dieser Account wurde nicht für E-Mail konfiguriert. Anfrage gescheitert."
+#: ../../view/theme/redbasic_c/php/config.php:109
+#: ../../view/theme/redbasic/php/config.php:107
+msgid "Set the background color of comments"
+msgstr "Hintergrundfarbe für Kommentare"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:473
-msgid "Unable to resolve your name at the provided location."
-msgstr ""
+#: ../../view/theme/redbasic_c/php/config.php:110
+#: ../../view/theme/redbasic/php/config.php:108
+msgid "Set font-size for the entire application"
+msgstr "Schriftgröße für die gesamte Anwendung"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:486
-msgid "You have already introduced yourself here."
-msgstr "Du hast dich hier bereits vorgestellt."
+#: ../../view/theme/redbasic_c/php/config.php:110
+#: ../../view/theme/redbasic/php/config.php:108
+msgid "Examples: 1rem, 100%, 16px"
+msgstr "Beispiele: 1rem, 100%, 16px"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:490
-#, php-format
-msgid "Apparently you are already friends with %s."
-msgstr "Anscheinend bist du bereits mit %s in Kontakt."
+#: ../../view/theme/redbasic_c/php/config.php:111
+#: ../../view/theme/redbasic/php/config.php:109
+msgid "Set font-color for posts and comments"
+msgstr "Schriftfarbe für Beiträge und Kommentare"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:511
-msgid "Invalid profile URL."
-msgstr "Ungültige Profil-URL."
+#: ../../view/theme/redbasic_c/php/config.php:112
+#: ../../view/theme/redbasic/php/config.php:110
+msgid "Set radius of corners"
+msgstr "Ecken-Radius"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:517
-msgid "Disallowed profile URL."
-msgstr "Nicht erlaubte Profil-URL."
+#: ../../view/theme/redbasic_c/php/config.php:112
+#: ../../view/theme/redbasic/php/config.php:110
+msgid "Example: 4px"
+msgstr "Beispiel: 4px"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:587
-msgid "Failed to update contact record."
-msgstr "Konnte den Verbindungseintrag nicht aktualisieren."
+#: ../../view/theme/redbasic_c/php/config.php:113
+#: ../../view/theme/redbasic/php/config.php:111
+msgid "Set shadow depth of photos"
+msgstr "Schattentiefe von Fotos"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:608
-msgid "Your introduction has been sent."
-msgstr "Deine Vorstellung wurde gesendet."
+#: ../../view/theme/redbasic_c/php/config.php:114
+#: ../../view/theme/redbasic/php/config.php:112
+msgid "Set maximum width of content region in pixel"
+msgstr "Maximalbreite des Inhaltsbereichs in Pixel festlegen"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:662
-msgid "Please login to confirm introduction."
-msgstr "Bitte melde dich an um die Vorstellung zu bestätigen."
+#: ../../view/theme/redbasic_c/php/config.php:114
+#: ../../view/theme/redbasic/php/config.php:112
+msgid "Leave empty for default width"
+msgstr "Leer lassen für Standardbreite"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:676
-msgid ""
-"Incorrect identity currently logged in. Please login to "
-"<strong>this</strong> profile."
-msgstr ""
+#: ../../view/theme/redbasic_c/php/config.php:115
+msgid "Left align page content"
+msgstr "Seiteninhalt linksbündig anzeigen"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:690
-#: ../../extend/addon/addon/friendica/dfrn_request.php:707
-msgid "Confirm"
-msgstr "Bestätigen"
+#: ../../view/theme/redbasic_c/php/config.php:116
+#: ../../view/theme/redbasic/php/config.php:113
+msgid "Set size of conversation author photo"
+msgstr "Größe der Avatare von Themenstartern"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:702
-msgid "Hide this contact"
-msgstr "Diesen Kontakt verbergen"
+#: ../../view/theme/redbasic_c/php/config.php:117
+#: ../../view/theme/redbasic/php/config.php:114
+msgid "Set size of followup author photos"
+msgstr "Größe der Avatare von Kommentatoren"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:705
-#, php-format
-msgid "Welcome home %s."
-msgstr "Willkommen daheim %s"
+#: ../../addon/rendezvous/rendezvous.php:57
+msgid "Errors encountered deleting database table "
+msgstr "Beim Löschen der Datenbanktabelle sind Fehler aufgetreten."
-#: ../../extend/addon/addon/friendica/dfrn_request.php:706
-#, php-format
-msgid "Please confirm your introduction/connection request to %s."
-msgstr "Bitte bestätige deine Vorstellung/Kontaktanfrage bei %s."
+#: ../../addon/rendezvous/rendezvous.php:95
+#: ../../addon/twitter/twitter.php:773
+msgid "Submit Settings"
+msgstr "Einstellungen absenden"
+
+#: ../../addon/rendezvous/rendezvous.php:96
+msgid "Drop tables when uninstalling?"
+msgstr "Lösche Tabellen beim Deinstallieren?"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:836
+#: ../../addon/rendezvous/rendezvous.php:96
msgid ""
-"Please enter your 'Identity Address' from one of the following supported "
-"communications networks:"
-msgstr "Bitte gib deine \"Identitäts Adresse\" von einem der folgenden unterstützten Kommunikations Netzwerke an."
+"If checked, the Rendezvous database tables will be deleted when the plugin "
+"is uninstalled."
+msgstr "Wenn ausgewählt, werden die Rendezvous-Tabellen in der Datenbank gelöscht, sobald das Plugin deinstalliert wird."
-#: ../../extend/addon/addon/friendica/dfrn_request.php:857
-#, php-format
+#: ../../addon/rendezvous/rendezvous.php:97
+msgid "Mapbox Access Token"
+msgstr "Mapbox Zugangs-Token"
+
+#: ../../addon/rendezvous/rendezvous.php:97
msgid ""
-"If you are not yet a member of the free social web, <a "
-"href=\"%s/siteinfo\">follow this link to find a public Friendica site and "
-"join us today</a>."
-msgstr ""
+"If you enter a Mapbox access token, it will be used to retrieve map tiles "
+"from Mapbox instead of the default OpenStreetMap tile server."
+msgstr "Wenn Du ein Mapbox Zugangs-Token eingibst, werden die Kartendaten (Kacheln) damit von Mapbox geladen, anstatt von OpenStreetMap, welches die Voreinstellung ist."
-#: ../../extend/addon/addon/friendica/dfrn_request.php:862
-msgid "Friend/Connection Request"
-msgstr "Freundschafts-/Verbindungsanfrage"
+#: ../../addon/rendezvous/rendezvous.php:162
+msgid "Rendezvous"
+msgstr "Rendezvous"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:863
+#: ../../addon/rendezvous/rendezvous.php:167
msgid ""
-"Examples: jojo@demo.friendica.com, http://demo.friendica.com/profile/jojo, "
-"testuser@identi.ca"
-msgstr "Beispiele: jojo@demo.friendica.com, http://demo.friendica.com/profile/jojo, testuser@identi.ca"
+"This identity has been deleted by another member due to inactivity. Please "
+"press the \"New identity\" button or refresh the page to register a new "
+"identity. You may use the same name."
+msgstr "Diese Identität wurde von einem anderen Mitglied aufgrund von Inaktivität gelöscht. Bitte klicke auf \"Neue Identität\" oder aktualisiere die Website im Browser, um eine neue Identität zu registrieren. Du kannst dabei den selben Namen verwenden."
-#: ../../extend/addon/addon/friendica/dfrn_request.php:864
-msgid "Please answer the following:"
-msgstr "Bitte beantworten Sie folgendes:"
+#: ../../addon/rendezvous/rendezvous.php:168
+msgid "Welcome to Rendezvous!"
+msgstr "Willkommen bei Rendezvous!"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:865
-#, php-format
-msgid "Does %s know you?"
-msgstr "Kennt %s Sie?"
+#: ../../addon/rendezvous/rendezvous.php:169
+msgid ""
+"Enter your name to join this rendezvous. To begin sharing your location with"
+" the other members, tap the GPS control. When your location is discovered, a"
+" red dot will appear and others will be able to see you on the map."
+msgstr "Gib Deinen Namen ein, um diesem Rendezvous beizutreten. Um Deinen Standort mit anderen Mitgliedern zu teilen, klicke auf das GPS Symbol. Sobald Dein Standort ermittelt ist, erscheint ein roter Punkt, und die Anderen werden Dich auf der Karte sehen können."
-#: ../../extend/addon/addon/friendica/dfrn_request.php:869
-msgid "Add a personal note:"
-msgstr "Eine persönliche Nachricht hinterlassen:"
+#: ../../addon/rendezvous/rendezvous.php:171
+msgid "Let's meet here"
+msgstr "Lasst uns hier treffen"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:871
-#: ../../include/network.php:2232 ../../include/network.php:2233
-msgid "Friendica"
-msgstr "Friendica"
+#: ../../addon/rendezvous/rendezvous.php:174
+msgid "New marker"
+msgstr "Neue Markierung"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:872
-msgid "StatusNet/Federated Social Web"
-msgstr "StatusNet/Föderierte Soziale Netzwerke"
+#: ../../addon/rendezvous/rendezvous.php:175
+msgid "Edit marker"
+msgstr "Markierung bearbeiten"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:873
-#: ../../include/network.php:2238
-msgid "Diaspora"
-msgstr "Diaspora"
+#: ../../addon/rendezvous/rendezvous.php:176
+msgid "New identity"
+msgstr "Neue Identität"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:874
-#, php-format
+#: ../../addon/rendezvous/rendezvous.php:177
+msgid "Delete marker"
+msgstr "Markierung löschen"
+
+#: ../../addon/rendezvous/rendezvous.php:178
+msgid "Delete member"
+msgstr "Mitglied löschen"
+
+#: ../../addon/rendezvous/rendezvous.php:179
+msgid "Edit proximity alert"
+msgstr "Annäherungsalarm bearbeiten"
+
+#: ../../addon/rendezvous/rendezvous.php:180
msgid ""
-" - please do not use this form. Instead, enter %s into your Diaspora search"
-" bar."
-msgstr "- bitte verwende nicht dieses Formular sondern gib %s in die Suchleiste deiner Diaspora Seite ein."
+"A proximity alert will be issued when this member is within a certain radius"
+" of you.<br><br>Enter a radius in meters (0 to disable):"
+msgstr "Ein Annäherungsalarm wird ausgelöst werden, sobald sich dieses Mitglied innerhalb eines bestimmten Radius von Dir aufhält.<br><br>Gib einen Radius in Metern ein (0 zum Abschalten der Funktion):"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:875
-msgid "Your Identity Address:"
-msgstr "Ihre Identitätsadresse:"
+#: ../../addon/rendezvous/rendezvous.php:180
+#: ../../addon/rendezvous/rendezvous.php:185
+msgid "distance"
+msgstr "Entfernung"
-#: ../../extend/addon/addon/friendica/dfrn_request.php:878
-msgid "Submit Request"
-msgstr "Anfrage absenden"
+#: ../../addon/rendezvous/rendezvous.php:181
+msgid "Proximity alert distance (meters)"
+msgstr "Entfernung für Annäherungsalarm (in Metern)"
-#: ../../extend/addon/addon/friendica/friendica.php:113
-#: ../../extend/addon/addon/gnusoc/gnusoc.php:114
+#: ../../addon/rendezvous/rendezvous.php:182
+#: ../../addon/rendezvous/rendezvous.php:184
+msgid ""
+"A proximity alert will be issued when you are within a certain radius of the"
+" marker location.<br><br>Enter a radius in meters (0 to disable):"
+msgstr "Ein Annäherungsalarm wird ausgelöst werden, sobald Du Dich innerhalb eines bestimmten Radius der Markierung aufhält.<br><br>Gib einen Radius in Metern ein (0 zum Abschalten der Funktion):"
+
+#: ../../addon/rendezvous/rendezvous.php:183
+msgid "Marker proximity alert"
+msgstr "Annäherungsalarm für Markierung"
+
+#: ../../addon/rendezvous/rendezvous.php:186
+msgid "Reminder note"
+msgstr "Erinnerungshinweis"
+
+#: ../../addon/rendezvous/rendezvous.php:187
+msgid ""
+"Enter a note to be displayed when you are within the specified proximity..."
+msgstr "Gib eine Nachricht ein, die angezeigt werden soll, wenn Du Dich in der festgelegten Nähe befindest..."
+
+#: ../../addon/rendezvous/rendezvous.php:199
+msgid "Add new rendezvous"
+msgstr "Neues Rendezvous hinzufügen"
+
+#: ../../addon/rendezvous/rendezvous.php:200
+msgid ""
+"Create a new rendezvous and share the access link with those you wish to "
+"invite to the group. Those who open the link become members of the "
+"rendezvous. They can view other member locations, add markers to the map, or"
+" share their own locations with the group."
+msgstr "Erstelle ein neues Rendezvous und teile den Zugriffslink mit allen, die Du in die Gruppe einladen möchtest. Die, die den Link öffnen, werden Mitglieder des Rendezvous. Sie können die Standorte der anderen Mitglieder sehen, Marker zur Karte hinzufügen oder ihre eigenen Standorte mit der Gruppe teilen."
+
+#: ../../addon/skeleton/skeleton.php:59
+msgid "Some setting"
+msgstr "Einige Einstellungen"
+
+#: ../../addon/skeleton/skeleton.php:61
+msgid "A setting"
+msgstr "Eine Einstellung"
+
+#: ../../addon/skeleton/skeleton.php:64
+msgid "Skeleton Settings"
+msgstr "Skeleton Einstellungen"
+
+#: ../../addon/gnusoc/gnusoc.php:243
msgid "GNU-Social Protocol Settings updated."
-msgstr "GNU Social Protokoll Einstellungen aktualisiert"
+msgstr "GNU social Protokoll Einstellungen aktualisiert"
-#: ../../extend/addon/addon/friendica/friendica.php:124
-msgid "Enable the (experimental) GNU-Social protocol for this channel"
-msgstr "GNU Social Protokoll (experimentell) für diesen Kanal aktualisieren"
+#: ../../addon/gnusoc/gnusoc.php:262
+msgid ""
+"The GNU-Social protocol does not support location independence. Connections "
+"you make within that network may be unreachable from alternate channel "
+"locations."
+msgstr "Das GNU-Social-Protokoll unterstützt keine Server-unabhängigen Identitäten. Verbindungen, die Du mit diesem Netzwerk eingehst, können von anderen Orten (Klonen) dieses Kanals aus unerreichbar sein."
+
+#: ../../addon/gnusoc/gnusoc.php:265
+msgid "Enable the GNU-Social protocol for this channel"
+msgstr "Aktiviere das GNU social Protokoll für diesen Kanal"
-#: ../../extend/addon/addon/friendica/friendica.php:128
-#: ../../extend/addon/addon/gnusoc/gnusoc.php:129
+#: ../../addon/gnusoc/gnusoc.php:269
msgid "GNU-Social Protocol Settings"
-msgstr "GNU Social Protokoll Einstellungen"
+msgstr "GNU social Protokoll Einstellungen"
-#: ../../extend/addon/addon/friendica/friendica.php:185
-#: ../../extend/addon/addon/gnusoc/gnusoc.php:319
+#: ../../addon/gnusoc/gnusoc.php:460
msgid "Follow"
msgstr "Folgen"
-#: ../../extend/addon/addon/friendica/friendica.php:188
-#: ../../extend/addon/addon/gnusoc/gnusoc.php:322
+#: ../../addon/gnusoc/gnusoc.php:463
#, php-format
msgid "%1$s is now following %2$s"
msgstr "%1$s folgt nun %2$s"
-#: ../../extend/addon/addon/frphotos/frphotos.php:91
-msgid "Friendica Photo Album Import"
-msgstr "Friendica-Fotoalbumimport"
+#: ../../addon/planets/planets.php:121
+msgid "Planets Settings updated."
+msgstr "Planeten Einstellungen aktualisiert"
-#: ../../extend/addon/addon/frphotos/frphotos.php:92
-msgid "This will import all your Friendica photo albums to this Red channel."
-msgstr "Hiermit werden all deine Fotoalben von Friendica in diesen Hubzilla Kanal importiert."
+#: ../../addon/planets/planets.php:149
+msgid "Enable Planets Plugin"
+msgstr "Aktiviere Planeten Plugin"
-#: ../../extend/addon/addon/frphotos/frphotos.php:93
-msgid "Friendica Server base URL"
-msgstr "BasisURL des Friendica Servers"
+#: ../../addon/planets/planets.php:153
+msgid "Planets Settings"
+msgstr "Planeten Einstellungen"
-#: ../../extend/addon/addon/frphotos/frphotos.php:94
-msgid "Friendica Login Username"
-msgstr "Friendica-Anmeldebenutzername"
+#: ../../addon/openclipatar/openclipatar.php:50
+#: ../../addon/openclipatar/openclipatar.php:128
+msgid "System defaults:"
+msgstr "Systemstandardeinstellungen:"
-#: ../../extend/addon/addon/frphotos/frphotos.php:95
-msgid "Friendica Login Password"
-msgstr "Friendica-Anmeldepasswort"
+#: ../../addon/openclipatar/openclipatar.php:54
+msgid "Preferred Clipart IDs"
+msgstr "Bevorzugte Clipart-IDs"
-#: ../../extend/addon/addon/gnusoc/gnusoc.php:125
-msgid "Enable the GNU-Social protocol for this channel"
-msgstr "GNU Social Protokoll für diesen Kanal aktualisieren"
+#: ../../addon/openclipatar/openclipatar.php:54
+msgid "List of preferred clipart ids. These will be shown first."
+msgstr "Liste bevorzugter Clipart-IDs. Diese werden zuerst angezeigt."
-#: ../../extend/addon/addon/hubwall/hubwall.php:19
-msgid "Send email to all members"
-msgstr "E-Mail an alle Mitglieder senden"
+#: ../../addon/openclipatar/openclipatar.php:55
+msgid "Default Search Term"
+msgstr "Standard-Suchbegriff"
-#: ../../extend/addon/addon/hubwall/hubwall.php:33
-#, php-format
-msgid "$1%s Administrator"
-msgstr "$1%s Administrator"
+#: ../../addon/openclipatar/openclipatar.php:55
+msgid "The default search term. These will be shown second."
+msgstr "Der Standard-Suchbegriff. Dieser wird an zweiter Stelle angezeigt."
-#: ../../extend/addon/addon/hubwall/hubwall.php:50
-#: ../../extend/addon/addon/mailtest/mailtest.php:50
-msgid "No recipients found."
-msgstr "Keine Empfänger gefunden."
+#: ../../addon/openclipatar/openclipatar.php:56
+msgid "Return After"
+msgstr "Zurückkehren nach"
-#: ../../extend/addon/addon/hubwall/hubwall.php:73
-#, php-format
-msgid "%1$d of %2$d messages sent."
-msgstr "%1$d von %2$d Nachrichten gesendet."
+#: ../../addon/openclipatar/openclipatar.php:56
+msgid "Page to load after image selection."
+msgstr "Die Seite, die nach Auswahl eines Bildes geladen werden soll."
-#: ../../extend/addon/addon/hubwall/hubwall.php:81
-msgid "Send email to all hub members."
-msgstr "Eine E-Mail an alle Mitglieder dieses Hubs senden."
+#: ../../addon/openclipatar/openclipatar.php:58 ../../include/channel.php:1266
+#: ../../include/nav.php:146
+msgid "Edit Profile"
+msgstr "Profil bearbeiten"
-#: ../../extend/addon/addon/hubwall/hubwall.php:92
-#: ../../extend/addon/addon/mailtest/mailtest.php:96
-msgid "Message subject"
-msgstr "Betreff der Nachricht"
+#: ../../addon/openclipatar/openclipatar.php:59
+msgid "Profile List"
+msgstr "Profilliste"
-#: ../../extend/addon/addon/hubwall/hubwall.php:93
-msgid "Sender Email address"
-msgstr "E-Mail Adresse des Absenders"
+#: ../../addon/openclipatar/openclipatar.php:61
+msgid "Order of Preferred"
+msgstr "Reihenfolge der Bevorzugten"
-#: ../../extend/addon/addon/hubwall/hubwall.php:94
-msgid "Test mode (only send to hub administrator)"
-msgstr "Test Modus (nur an Hub Administratoren senden)"
+#: ../../addon/openclipatar/openclipatar.php:61
+msgid "Sort order of preferred clipart ids."
+msgstr "Sortierreihenfolge der bevorzugten Clipart-IDs."
-#: ../../extend/addon/addon/ijpost/ijpost.php:42
-msgid "Post to Insanejournal"
-msgstr "Bei InsaneJournal veröffentlichen"
+#: ../../addon/openclipatar/openclipatar.php:62
+#: ../../addon/openclipatar/openclipatar.php:68
+msgid "Newest first"
+msgstr "Neueste zuerst"
-#: ../../extend/addon/addon/ijpost/ijpost.php:73
-msgid "Enable InsaneJournal Post Plugin"
-msgstr "Aktiviere das InsaneJournal Plugin"
+#: ../../addon/openclipatar/openclipatar.php:65
+msgid "As entered"
+msgstr "Wie eingegeben"
-#: ../../extend/addon/addon/ijpost/ijpost.php:77
-msgid "InsaneJournal username"
-msgstr "InsaneJournal-Benutzername"
+#: ../../addon/openclipatar/openclipatar.php:67
+msgid "Order of other"
+msgstr "Sortierung aller anderen"
-#: ../../extend/addon/addon/ijpost/ijpost.php:81
-msgid "InsaneJournal password"
-msgstr "InsaneJournal-Passwort"
+#: ../../addon/openclipatar/openclipatar.php:67
+msgid "Sort order of other clipart ids."
+msgstr "Sortierreihenfolge der übrigen Clipart-IDs."
-#: ../../extend/addon/addon/ijpost/ijpost.php:85
-msgid "Post to InsaneJournal by default"
-msgstr "Standardmäßig bei InsaneJournal veröffentlichen"
+#: ../../addon/openclipatar/openclipatar.php:69
+msgid "Most downloaded first"
+msgstr "Meist heruntergeladene zuerst"
-#: ../../extend/addon/addon/ijpost/ijpost.php:89
-msgid "InsaneJournal Post Settings"
-msgstr "InsaneJournal-Beitragseinstellungen"
+#: ../../addon/openclipatar/openclipatar.php:70
+msgid "Most liked first"
+msgstr "Beliebteste zuerst"
-#: ../../extend/addon/addon/ijpost/ijpost.php:104
-msgid "Insane Journal Settings saved."
-msgstr "InsaneJournal-Einstellungen gespeichert."
+#: ../../addon/openclipatar/openclipatar.php:72
+msgid "Preferred IDs Message"
+msgstr "Nachricht für bevorzugte IDs"
-#: ../../extend/addon/addon/irc/irc.php:45
-msgid "Channels to auto connect"
-msgstr ""
+#: ../../addon/openclipatar/openclipatar.php:72
+msgid "Message to display above preferred results."
+msgstr "Nachricht, die über den Ergebnissen mit den bevorzugten IDs angezeigt werden soll."
-#: ../../extend/addon/addon/irc/irc.php:45
-#: ../../extend/addon/addon/irc/irc.php:49
-msgid "Comma separated list"
-msgstr "Kommagetrennte Liste"
+#: ../../addon/openclipatar/openclipatar.php:78
+msgid "Uploaded by: "
+msgstr "Hochgeladen von: "
-#: ../../extend/addon/addon/irc/irc.php:49
-#: ../../extend/addon/addon/irc/irc.php:96
-msgid "Popular Channels"
-msgstr "Beliebte Kanäle"
+#: ../../addon/openclipatar/openclipatar.php:78
+msgid "Drawn by: "
+msgstr "Gezeichnet von: "
-#: ../../extend/addon/addon/irc/irc.php:53
-msgid "IRC Settings"
-msgstr "IRC-Einstellungen"
+#: ../../addon/openclipatar/openclipatar.php:192
+msgid "Or select from a free OpenClipart.org image:"
+msgstr "Oder wähle ein freies Bild von OpenClipart.org:"
-#: ../../extend/addon/addon/irc/irc.php:69
-msgid "IRC settings saved."
-msgstr "IRC-Einstellungen gespeichert."
+#: ../../addon/openclipatar/openclipatar.php:195
+msgid "Search Term"
+msgstr "Suchbegriff"
-#: ../../extend/addon/addon/irc/irc.php:74
-msgid "IRC Chatroom"
-msgstr "IRC-Chatraum"
+#: ../../addon/openclipatar/openclipatar.php:232
+msgid "Unknown error. Please try again later."
+msgstr "Unbekannter Fehler. Bitte versuchen Sie es später erneut."
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:305
-#: ../../include/channel.php:1056 ../../include/channel.php:1218
-msgid "Status:"
-msgstr "Status:"
+#: ../../addon/openclipatar/openclipatar.php:308
+msgid "Profile photo updated successfully."
+msgstr "Profilfoto erfolgreich aktualisiert."
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:309
-msgid "Activate addon"
-msgstr "Addon aktiviren"
+#: ../../addon/zotvi/zot6.php:25 ../../include/zot.php:3983
+msgid "invalid target signature"
+msgstr "Ungültige Signatur des Ziels"
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:313
-msgid "Hide Jappixmini Chat-Widget from the webinterface"
-msgstr "Jappix Mini Chat-Widget von der Weboberfläche verbergen"
+#: ../../addon/adultphotoflag/adultphotoflag.php:24
+msgid "Flag Adult Photos"
+msgstr "Nicht jugendfreie Fotos markieren"
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:318
-msgid "Jabber username"
-msgstr "Jabber-Benutzername"
+#: ../../addon/adultphotoflag/adultphotoflag.php:25
+msgid ""
+"Provide photo edit option to hide inappropriate photos from default album "
+"view"
+msgstr "Stellt eine Option zum Verstecken von Fotos mit unangemessenen Inhalten in der Standard-Albumansicht bereit"
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:324
-msgid "Jabber server"
-msgstr "Jabber-Server"
+#: ../../addon/wppost/wppost.php:45
+msgid "Post to WordPress"
+msgstr "Auf WordPress posten"
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:330
-msgid "Jabber BOSH host URL"
-msgstr "Jabber BOSH Host URL"
+#: ../../addon/wppost/wppost.php:82
+msgid "Enable WordPress Post Plugin"
+msgstr "Aktiviere das WordPress-Plugin"
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:337
-msgid "Jabber password"
-msgstr "Jabber-Passwort"
+#: ../../addon/wppost/wppost.php:86
+msgid "WordPress username"
+msgstr "WordPress-Benutzername"
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:343
-msgid "Encrypt Jabber password with Hubzilla password"
-msgstr "Jabber-Passwort mit Hubzilla-Passwort verschlüsseln"
+#: ../../addon/wppost/wppost.php:90
+msgid "WordPress password"
+msgstr "WordPress-Passwort"
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:347
-#: ../../extend/addon/addon/redred/redred.php:115
-msgid "Hubzilla password"
-msgstr "Hubzilla-Passwort"
+#: ../../addon/wppost/wppost.php:94
+msgid "WordPress API URL"
+msgstr "WordPress-API-URL"
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:351
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:355
-msgid "Approve subscription requests from Hubzilla contacts automatically"
-msgstr ""
+#: ../../addon/wppost/wppost.php:95
+msgid "Typically https://your-blog.tld/xmlrpc.php"
+msgstr "Normalerweise https://your-blog.tld/xmlrpc.php"
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:359
-msgid "Purge internal list of jabber addresses of contacts"
-msgstr "Interne Liste der Jabber Adressen von Kontakten löschen"
+#: ../../addon/wppost/wppost.php:98
+msgid "WordPress blogid"
+msgstr "WordPress blogid"
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:364
-msgid "Configuration Help"
-msgstr "Konfigurationshilfe"
+#: ../../addon/wppost/wppost.php:99
+msgid "For multi-user sites such as wordpress.com, otherwise leave blank"
+msgstr "Nötig für Mehrbenutzer Seiten wie wordpress.com, andernfalls frei lassen"
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:368
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1149
-msgid "Add Contact"
-msgstr "Kontakt hinzufügen"
+#: ../../addon/wppost/wppost.php:105
+msgid "Post to WordPress by default"
+msgstr "Standardmäßig auf auf WordPress posten"
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:371
-msgid "Jappix Mini Settings"
-msgstr "Jappix Mini Einstellungen"
+#: ../../addon/wppost/wppost.php:109
+msgid "Forward comments (requires hubzilla_wp plugin)"
+msgstr "Kommentare weiterleiten (benötigt hubzilla_wp Plugin)"
-#: ../../extend/addon/addon/js_upload/js_upload.php:44
+#: ../../addon/wppost/wppost.php:113
+msgid "WordPress Post Settings"
+msgstr "WordPress-Beitragseinstellungen"
+
+#: ../../addon/wppost/wppost.php:129
+msgid "Wordpress Settings saved."
+msgstr "Wordpress-Einstellungen gespeichert."
+
+#: ../../addon/nsfw/nsfw.php:80
+msgid ""
+"This plugin looks in posts for the words/text you specify below, and "
+"collapses any content containing those keywords so it is not displayed at "
+"inappropriate times, such as sexual innuendo that may be improper in a work "
+"setting. It is polite and recommended to tag any content containing nudity "
+"with #NSFW. This filter can also match any other word/text you specify, and"
+" can thereby be used as a general purpose content filter."
+msgstr "Dieses Plugin sucht in Beiträgen nach Wörtern oder Textbausteinen, die Du hier unterhalb einträgst, und faltet alle Beiträge zusammen, in denen es diese Bausteine findet. Auf diese Weise wird verhindert, dass Inhalte, wie z.B. sexuelle Anspielungen, in unpassenden Momenten angezeigt werden. Es gilt als höflich und empfohlen, den #NSFW Tag für Beiträge zu verwenden, bei denen Du davon ausgehen kannst, dass andere sie anstößig finden könnten. Du kannst aber auch beliebige andere Wörter in der Liste angeben und das Plugin so als allgemeinen Inhaltsfilter verwenden."
+
+#: ../../addon/nsfw/nsfw.php:84
+msgid "Enable Content filter"
+msgstr "Inhaltsfilter aktivieren"
+
+#: ../../addon/nsfw/nsfw.php:88
+msgid "Comma separated list of keywords to hide"
+msgstr "Kommaseparierte Liste von Schlüsselworten die verborgen werden sollen."
+
+#: ../../addon/nsfw/nsfw.php:88
+msgid "Word, /regular-expression/, lang=xx, lang!=xx"
+msgstr "Wort, /regular-expression/, lang=xx, lang!=xx"
+
+#: ../../addon/nsfw/nsfw.php:92
+msgid "Not Safe For Work Settings"
+msgstr "Not Safe For Work Einstellungen"
+
+#: ../../addon/nsfw/nsfw.php:92
+msgid "General Purpose Content Filter"
+msgstr "Allzweck-Inhaltsfilter"
+
+#: ../../addon/nsfw/nsfw.php:110
+msgid "NSFW Settings saved."
+msgstr "NSFW-Einstellungen gespeichert."
+
+#: ../../addon/nsfw/nsfw.php:207
+msgid "Possible adult content"
+msgstr "Möglicherweise nicht jugendfreie Inhalte"
+
+#: ../../addon/nsfw/nsfw.php:211
+#, php-format
+msgid "%s - view"
+msgstr "%s - ansehen"
+
+#: ../../addon/ijpost/ijpost.php:42
+msgid "Post to Insanejournal"
+msgstr "Bei InsaneJournal veröffentlichen"
+
+#: ../../addon/ijpost/ijpost.php:73
+msgid "Enable InsaneJournal Post Plugin"
+msgstr "Aktiviere das InsaneJournal Plugin"
+
+#: ../../addon/ijpost/ijpost.php:77
+msgid "InsaneJournal username"
+msgstr "InsaneJournal-Benutzername"
+
+#: ../../addon/ijpost/ijpost.php:81
+msgid "InsaneJournal password"
+msgstr "InsaneJournal-Passwort"
+
+#: ../../addon/ijpost/ijpost.php:85
+msgid "Post to InsaneJournal by default"
+msgstr "Standardmäßig bei InsaneJournal veröffentlichen"
+
+#: ../../addon/ijpost/ijpost.php:89
+msgid "InsaneJournal Post Settings"
+msgstr "InsaneJournal-Beitragseinstellungen"
+
+#: ../../addon/ijpost/ijpost.php:104
+msgid "Insane Journal Settings saved."
+msgstr "InsaneJournal-Einstellungen gespeichert."
+
+#: ../../addon/js_upload/js_upload.php:44
msgid "Upload a file"
msgstr "Datei hochladen"
-#: ../../extend/addon/addon/js_upload/js_upload.php:45
+#: ../../addon/js_upload/js_upload.php:45
msgid "Drop files here to upload"
msgstr "Dateien zum Hochladen hier fallen lassen"
-#: ../../extend/addon/addon/js_upload/js_upload.php:47
+#: ../../addon/js_upload/js_upload.php:47
msgid "Failed"
msgstr "Fehlgeschlagen"
-#: ../../extend/addon/addon/js_upload/js_upload.php:315
+#: ../../addon/js_upload/js_upload.php:315
msgid "No files were uploaded."
msgstr "Es wurden keine Dateien hochgeladen."
-#: ../../extend/addon/addon/js_upload/js_upload.php:322
+#: ../../addon/js_upload/js_upload.php:322
msgid "Uploaded file is empty"
msgstr "Hochgeladene Datei ist leer"
-#: ../../extend/addon/addon/js_upload/js_upload.php:335
+#: ../../addon/js_upload/js_upload.php:335
msgid "Image exceeds size limit of "
msgstr "Bild überschreitet Größenbeschränkung von "
-#: ../../extend/addon/addon/js_upload/js_upload.php:347
+#: ../../addon/js_upload/js_upload.php:347
msgid "File has an invalid extension, it should be one of "
msgstr "Die Datei hat eine ungültige Endung. Erlaubt sind folgende:"
-#: ../../extend/addon/addon/js_upload/js_upload.php:359
+#: ../../addon/js_upload/js_upload.php:359
msgid "Upload was cancelled, or server error encountered"
msgstr "Das Hochladen wurde abgebrochen oder es ist ein Serverfehler aufgetreten."
-#: ../../extend/addon/addon/ldapauth/ldapauth.php:61
-msgid "An account has been created for you."
-msgstr "Ein Konto wurde für Sie erstellt."
+#: ../../addon/dwpost/dwpost.php:42
+msgid "Post to Dreamwidth"
+msgstr "Bei Dreamwidth veröffentlichen"
-#: ../../extend/addon/addon/ldapauth/ldapauth.php:68
-msgid "Authentication successful but rejected: account creation is disabled."
-msgstr "Authentifizierung war erfolgreich wurde aber abgewiesen! Das Anlegen von Accounts wurde deaktiviert."
+#: ../../addon/dwpost/dwpost.php:73
+msgid "Enable Dreamwidth Post Plugin"
+msgstr "Aktiviere das Dreamwidth-Plugin"
-#: ../../extend/addon/addon/libertree/libertree.php:38
-msgid "Post to Libertree"
-msgstr "Bei Libertree veröffentlichen"
+#: ../../addon/dwpost/dwpost.php:77
+msgid "Dreamwidth username"
+msgstr "Dreamwidth-Benutzername"
-#: ../../extend/addon/addon/libertree/libertree.php:69
-msgid "Enable Libertree Post Plugin"
-msgstr "Aktivire das Libertree-Plugin"
+#: ../../addon/dwpost/dwpost.php:81
+msgid "Dreamwidth password"
+msgstr "Dreamwidth-Passwort"
-#: ../../extend/addon/addon/libertree/libertree.php:73
-msgid "Libertree API token"
-msgstr "Libertree API Token"
+#: ../../addon/dwpost/dwpost.php:85
+msgid "Post to Dreamwidth by default"
+msgstr "Standardmäßig auf auf Dreamwidth posten"
-#: ../../extend/addon/addon/libertree/libertree.php:77
-msgid "Libertree site URL"
-msgstr "URL der Libertree Seite"
+#: ../../addon/dwpost/dwpost.php:89
+msgid "Dreamwidth Post Settings"
+msgstr "Dreamwidth-Beitragseinstellungen"
-#: ../../extend/addon/addon/libertree/libertree.php:81
-msgid "Post to Libertree by default"
-msgstr "Standardmäßig bei Libertree veröffentlichen"
+#: ../../addon/firefox/firefox.php:23
+msgid "Install Firefox Sharing Tools"
+msgstr "Installiere das Firefox Sharing Werkzeug"
-#: ../../extend/addon/addon/libertree/libertree.php:85
-msgid "Libertree Post Settings"
-msgstr "Libertree-Beitragseinstellungen"
+#: ../../addon/firefox/firefox.php:34
+msgid "Share content from Firefox to $Projectname"
+msgstr "Inhalte von Firefox nach $Projectname teilen"
-#: ../../extend/addon/addon/libertree/libertree.php:99
-msgid "Libertree Settings saved."
-msgstr "Libertree-Einstellungen gespeichert."
+#: ../../addon/firefox/firefox.php:37
+msgid "Install Firefox Sharing Tools to this web browser"
+msgstr "Installiere das Firefox Sharing Werkzeug in diesen Webbrowser"
+
+#: ../../addon/dirstats/dirstats.php:94
+msgid "Hubzilla Directory Stats"
+msgstr "Hubzilla-Verzeichnisstatistiken"
+
+#: ../../addon/dirstats/dirstats.php:95
+msgid "Total Hubs"
+msgstr "Hubs insgesamt"
+
+#: ../../addon/dirstats/dirstats.php:97
+msgid "Hubzilla Hubs"
+msgstr "Hubzilla Hubs"
+
+#: ../../addon/dirstats/dirstats.php:99
+msgid "Friendica Hubs"
+msgstr "Friendica Hubs"
+
+#: ../../addon/dirstats/dirstats.php:101
+msgid "Diaspora Pods"
+msgstr "Diaspora Pods"
+
+#: ../../addon/dirstats/dirstats.php:103
+msgid "Hubzilla Channels"
+msgstr "Hubzilla-Kanäle"
+
+#: ../../addon/dirstats/dirstats.php:105
+msgid "Friendica Channels"
+msgstr "Friendica-Kanäle"
+
+#: ../../addon/dirstats/dirstats.php:107
+msgid "Diaspora Channels"
+msgstr "Diaspora-Kanäle"
+
+#: ../../addon/dirstats/dirstats.php:109
+msgid "Aged 35 and above"
+msgstr "35 und älter"
+
+#: ../../addon/dirstats/dirstats.php:111
+msgid "Aged 34 and under"
+msgstr "34 und jünger"
+
+#: ../../addon/dirstats/dirstats.php:113
+msgid "Average Age"
+msgstr "Durchschnittsalter"
+
+#: ../../addon/dirstats/dirstats.php:115
+msgid "Known Chatrooms"
+msgstr "Bekannte Chaträume"
+
+#: ../../addon/dirstats/dirstats.php:117
+msgid "Known Tags"
+msgstr "Bekannte Schlagwörter"
+
+#: ../../addon/dirstats/dirstats.php:119
+msgid ""
+"Please note Diaspora and Friendica statistics are merely those **this "
+"directory** is aware of, and not all those known in the network. This also "
+"applies to chatrooms,"
+msgstr "Bitte berücksichtige, dass Diaspora und Friendica Statistiken nur solche einschließen, die **diesem Verzeichnis** bekannt sind, nicht alle im Netzwerk bekannten. Das gilt auch für Chaträume."
+
+#: ../../addon/mailhost/mailhost.php:36
+msgid "Email notification hub"
+msgstr "Hub für E-Mail-Benachrichtigungen"
+
+#: ../../addon/mailhost/mailhost.php:36
+msgid "Hostname"
+msgstr "Servername"
+
+#: ../../addon/mailhost/mailhost.php:40
+msgid "Mailhost Settings"
+msgstr "Mailhost-Einstellungen"
+
+#: ../../addon/mailhost/mailhost.php:54
+msgid "MAILHOST Settings saved."
+msgstr "MAILHOST-Einstellungen gespeichert."
+
+#: ../../addon/likebanner/likebanner.php:51
+msgid "Your Webbie:"
+msgstr "Dein Webbie"
+
+#: ../../addon/likebanner/likebanner.php:54
+msgid "Fontsize (px):"
+msgstr "Schriftgröße (px):"
+
+#: ../../addon/likebanner/likebanner.php:68
+msgid "Link:"
+msgstr "Link:"
+
+#: ../../addon/likebanner/likebanner.php:70
+msgid "Like us on Hubzilla"
+msgstr "Like us on Hubzilla"
+
+#: ../../addon/likebanner/likebanner.php:72
+msgid "Embed:"
+msgstr "Einbetten"
-#: ../../extend/addon/addon/ljpost/ljpost.php:42
+#: ../../addon/redphotos/redphotos.php:106
+msgid "Photos imported"
+msgstr "Fotos importiert"
+
+#: ../../addon/redphotos/redphotos.php:129
+msgid "Redmatrix Photo Album Import"
+msgstr "Redmatrix-Fotoalbumimport"
+
+#: ../../addon/redphotos/redphotos.php:130
+msgid "This will import all your Redmatrix photo albums to this channel."
+msgstr "Hiermit werden all deine Fotoalben von Redmatrix in diesen Kanal importiert."
+
+#: ../../addon/redphotos/redphotos.php:131
+#: ../../addon/redfiles/redfiles.php:121
+msgid "Redmatrix Server base URL"
+msgstr "Basis-URL des Redmatrix Servers"
+
+#: ../../addon/redphotos/redphotos.php:132
+#: ../../addon/redfiles/redfiles.php:122
+msgid "Redmatrix Login Username"
+msgstr "Redmatrix-Anmeldebenutzername"
+
+#: ../../addon/redphotos/redphotos.php:133
+#: ../../addon/redfiles/redfiles.php:123
+msgid "Redmatrix Login Password"
+msgstr "Redmatrix-Anmeldepasswort"
+
+#: ../../addon/redphotos/redphotos.php:134
+msgid "Import just this album"
+msgstr "Nur dieses Album importieren"
+
+#: ../../addon/redphotos/redphotos.php:134
+msgid "Leave blank to import all albums"
+msgstr "Leer lassen um alle Alben zu importieren"
+
+#: ../../addon/redphotos/redphotos.php:135
+msgid "Maximum count to import"
+msgstr "Maximal zu importierende Anzahl"
+
+#: ../../addon/redphotos/redphotos.php:135
+msgid "0 or blank to import all available"
+msgstr "0 oder leer lassen um alles zu importieren"
+
+#: ../../addon/irc/irc.php:45
+msgid "Channels to auto connect"
+msgstr "Kanäle zur automatischen Verbindung"
+
+#: ../../addon/irc/irc.php:45 ../../addon/irc/irc.php:49
+msgid "Comma separated list"
+msgstr "Kommagetrennte Liste"
+
+#: ../../addon/irc/irc.php:49 ../../addon/irc/irc.php:96
+msgid "Popular Channels"
+msgstr "Beliebte Kanäle"
+
+#: ../../addon/irc/irc.php:53
+msgid "IRC Settings"
+msgstr "IRC-Einstellungen"
+
+#: ../../addon/irc/irc.php:69
+msgid "IRC settings saved."
+msgstr "IRC-Einstellungen gespeichert."
+
+#: ../../addon/irc/irc.php:74
+msgid "IRC Chatroom"
+msgstr "IRC-Chatraum"
+
+#: ../../addon/ljpost/ljpost.php:42
msgid "Post to LiveJournal"
msgstr "Bei LiveJurnal veröffentlichen"
-#: ../../extend/addon/addon/ljpost/ljpost.php:70
+#: ../../addon/ljpost/ljpost.php:70
msgid "Enable LiveJournal Post Plugin"
msgstr "Aktiviere das LiveJurnal Plugin"
-#: ../../extend/addon/addon/ljpost/ljpost.php:74
+#: ../../addon/ljpost/ljpost.php:74
msgid "LiveJournal username"
msgstr "LiveJournal-Benutzername"
-#: ../../extend/addon/addon/ljpost/ljpost.php:78
+#: ../../addon/ljpost/ljpost.php:78
msgid "LiveJournal password"
msgstr "LiveJournal-Passwort"
-#: ../../extend/addon/addon/ljpost/ljpost.php:82
+#: ../../addon/ljpost/ljpost.php:82
msgid "Post to LiveJournal by default"
msgstr "Standardmäßig bei LiveJurnal veröffentlichen"
-#: ../../extend/addon/addon/ljpost/ljpost.php:86
+#: ../../addon/ljpost/ljpost.php:86
msgid "LiveJournal Post Settings"
msgstr "LiveJournal-Beitragseinstellungen"
-#: ../../extend/addon/addon/ljpost/ljpost.php:101
+#: ../../addon/ljpost/ljpost.php:101
msgid "LiveJournal Settings saved."
msgstr "LiveJournal-Einstellungen gespeichert."
-#: ../../extend/addon/addon/logrot/logrot.php:36
-msgid "Logfile archive directory"
-msgstr "Verzeichnis der Logdatei"
-
-#: ../../extend/addon/addon/logrot/logrot.php:36
-msgid "Directory to store rotated logs"
-msgstr "Verzeichnis, in dem rotierte Logs gespeichert werden sollen"
-
-#: ../../extend/addon/addon/logrot/logrot.php:37
-msgid "Logfile size in bytes before rotating"
-msgstr "zu erreichende Logdateigröße in Bytes, bevor rotiert wird"
+#: ../../addon/openid/openid.php:49
+msgid ""
+"We encountered a problem while logging in with the OpenID you provided. "
+"Please check the correct spelling of the ID."
+msgstr "Wir haben ein Problem mit der OpenID festgestellt, mit der Du Dich anmelden wolltest. Bitte überprüfe sie noch einmal."
-#: ../../extend/addon/addon/logrot/logrot.php:38
-msgid "Number of logfiles to retain"
-msgstr "Anzahl aufzubewahrender rotierter Logdateien"
+#: ../../addon/openid/openid.php:49
+msgid "The error message was:"
+msgstr "Die Fehlermeldung war:"
-#: ../../extend/addon/addon/mailhost/mailhost.php:36
-msgid "Email notification hub"
-msgstr "Hub für E-Mail-Benachrichtigungen"
+#: ../../addon/openid/MysqlProvider.php:52
+msgid "First Name"
+msgstr "Vorname"
-#: ../../extend/addon/addon/mailhost/mailhost.php:36
-msgid "Hostname"
-msgstr "Servername"
+#: ../../addon/openid/MysqlProvider.php:53
+msgid "Last Name"
+msgstr "Nachname"
-#: ../../extend/addon/addon/mailhost/mailhost.php:40
-msgid "Mailhost Settings"
-msgstr "Mailhost-Einstellungen"
+#: ../../addon/openid/MysqlProvider.php:54 ../../addon/redred/redred.php:111
+msgid "Nickname"
+msgstr "Spitzname"
-#: ../../extend/addon/addon/mailhost/mailhost.php:54
-msgid "MAILHOST Settings saved."
-msgstr "MAILHOST-Einstellungen gespeichert."
+#: ../../addon/openid/MysqlProvider.php:55
+msgid "Full Name"
+msgstr "Voller Name"
-#: ../../extend/addon/addon/moremoods/moremoods.php:19
-msgid "lonely"
-msgstr "einsam"
+#: ../../addon/openid/MysqlProvider.php:61
+msgid "Profile Photo 16px"
+msgstr "Profilfoto 16 px"
-#: ../../extend/addon/addon/moremoods/moremoods.php:20
-msgid "drunk"
-msgstr "betrunken"
+#: ../../addon/openid/MysqlProvider.php:62
+msgid "Profile Photo 32px"
+msgstr "Profilfoto 32 px"
-#: ../../extend/addon/addon/moremoods/moremoods.php:21
-msgid "horny"
-msgstr "geil"
+#: ../../addon/openid/MysqlProvider.php:63
+msgid "Profile Photo 48px"
+msgstr "Profilfoto 48 px"
-#: ../../extend/addon/addon/moremoods/moremoods.php:22
-msgid "stoned"
-msgstr "bekifft"
+#: ../../addon/openid/MysqlProvider.php:64
+msgid "Profile Photo 64px"
+msgstr "Profilfoto 64 px"
-#: ../../extend/addon/addon/moremoods/moremoods.php:23
-msgid "fucked up"
-msgstr "beschissen"
+#: ../../addon/openid/MysqlProvider.php:65
+msgid "Profile Photo 80px"
+msgstr "Profilfoto 80 px"
-#: ../../extend/addon/addon/moremoods/moremoods.php:24
-msgid "clusterfucked"
-msgstr "clusterfucked"
+#: ../../addon/openid/MysqlProvider.php:66
+msgid "Profile Photo 128px"
+msgstr "Profilfoto 128 px"
-#: ../../extend/addon/addon/moremoods/moremoods.php:25
-msgid "crazy"
-msgstr "verrückt"
+#: ../../addon/openid/MysqlProvider.php:67
+msgid "Timezone"
+msgstr "Zeitzone"
-#: ../../extend/addon/addon/moremoods/moremoods.php:26
-msgid "hurt"
-msgstr "verletzt"
+#: ../../addon/openid/MysqlProvider.php:70
+msgid "Birth Year"
+msgstr "Geburtsjahr"
-#: ../../extend/addon/addon/moremoods/moremoods.php:27
-msgid "sleepy"
-msgstr "müde"
+#: ../../addon/openid/MysqlProvider.php:71
+msgid "Birth Month"
+msgstr "Geburtsmonat"
-#: ../../extend/addon/addon/moremoods/moremoods.php:28
-msgid "grumpy"
-msgstr "mürrisch"
+#: ../../addon/openid/MysqlProvider.php:72
+msgid "Birth Day"
+msgstr "Geburtstag"
-#: ../../extend/addon/addon/moremoods/moremoods.php:29
-msgid "high"
-msgstr "hoch"
+#: ../../addon/openid/MysqlProvider.php:73
+msgid "Birthdate"
+msgstr "Geburtsdatum"
-#: ../../extend/addon/addon/moremoods/moremoods.php:30
-msgid "semi-conscious"
-msgstr "halb bewusstlos"
+#: ../../addon/openid/Mod_Openid.php:30
+msgid "OpenID protocol error. No ID returned."
+msgstr "OpenID-Protokollfehler. Keine Kennung zurückgegeben."
-#: ../../extend/addon/addon/moremoods/moremoods.php:31
-msgid "in love"
-msgstr "verliebt"
+#: ../../addon/openid/Mod_Openid.php:188 ../../include/auth.php:289
+msgid "Login failed."
+msgstr "Login fehlgeschlagen."
-#: ../../extend/addon/addon/moremoods/moremoods.php:32
-msgid "in lust"
-msgstr ""
+#: ../../addon/openid/Mod_Id.php:85 ../../include/selectors.php:49
+#: ../../include/selectors.php:66 ../../include/channel.php:1432
+msgid "Male"
+msgstr "Männlich"
-#: ../../extend/addon/addon/moremoods/moremoods.php:33
-msgid "naked"
-msgstr "nackt"
+#: ../../addon/openid/Mod_Id.php:87 ../../include/selectors.php:49
+#: ../../include/selectors.php:66 ../../include/channel.php:1430
+msgid "Female"
+msgstr "Weiblich"
-#: ../../extend/addon/addon/moremoods/moremoods.php:34
-msgid "stinky"
-msgstr "stinkend"
+#: ../../addon/randpost/randpost.php:97
+msgid "You're welcome."
+msgstr "Gern geschehen."
-#: ../../extend/addon/addon/moremoods/moremoods.php:35
-msgid "sweaty"
-msgstr "verschwitzt"
+#: ../../addon/randpost/randpost.php:98
+msgid "Ah shucks..."
+msgstr "Ach Mist..."
-#: ../../extend/addon/addon/moremoods/moremoods.php:36
-msgid "bleeding out"
-msgstr "blutend"
+#: ../../addon/randpost/randpost.php:99
+msgid "Don't mention it."
+msgstr "Keine Ursache."
-#: ../../extend/addon/addon/moremoods/moremoods.php:37
-msgid "victorious"
-msgstr "siegreich"
+#: ../../addon/randpost/randpost.php:100
+msgid "&lt;blush&gt;"
+msgstr ""
-#: ../../extend/addon/addon/moremoods/moremoods.php:38
-msgid "defeated"
-msgstr "besiegt"
+#: ../../addon/startpage/startpage.php:109
+msgid "Page to load after login"
+msgstr "Seite, die nach dem Login geladen werden soll"
-#: ../../extend/addon/addon/moremoods/moremoods.php:39
-msgid "envious"
-msgstr "neidisch"
+#: ../../addon/startpage/startpage.php:109
+msgid ""
+"Examples: &quot;apps&quot;, &quot;network?f=&gid=37&quot; (privacy "
+"collection), &quot;channel&quot; or &quot;notifications/system&quot; (leave "
+"blank for default network page (grid)."
+msgstr "Beispiele: &quot;apps&quot;, &quot;network?f=&gid=37&quot; (Gruppen-gefilterte Beiträge), &quot;channel&quot; oder &quot;notifications/system&quot; (freilassen für die Standard-Netzwerkseite (grid)."
-#: ../../extend/addon/addon/moremoods/moremoods.php:40
-msgid "jealous"
-msgstr "eifersüchtig"
+#: ../../addon/startpage/startpage.php:113
+msgid "Startpage Settings"
+msgstr "Startseiteneinstellungen"
-#: ../../extend/addon/addon/morepokes/morepokes.php:19
+#: ../../addon/morepokes/morepokes.php:19
msgid "bitchslap"
msgstr "Ohrfeige"
-#: ../../extend/addon/addon/morepokes/morepokes.php:19
+#: ../../addon/morepokes/morepokes.php:19
msgid "bitchslapped"
msgstr "geohrfeigt"
-#: ../../extend/addon/addon/morepokes/morepokes.php:20
+#: ../../addon/morepokes/morepokes.php:20
msgid "shag"
msgstr "bumsen"
-#: ../../extend/addon/addon/morepokes/morepokes.php:20
+#: ../../addon/morepokes/morepokes.php:20
msgid "shagged"
msgstr "gebumst"
-#: ../../extend/addon/addon/morepokes/morepokes.php:21
+#: ../../addon/morepokes/morepokes.php:21
msgid "patent"
msgstr "Patent"
-#: ../../extend/addon/addon/morepokes/morepokes.php:21
+#: ../../addon/morepokes/morepokes.php:21
msgid "patented"
msgstr "patentiert"
-#: ../../extend/addon/addon/morepokes/morepokes.php:22
+#: ../../addon/morepokes/morepokes.php:22
msgid "hug"
msgstr "umarmen"
-#: ../../extend/addon/addon/morepokes/morepokes.php:22
+#: ../../addon/morepokes/morepokes.php:22
msgid "hugged"
msgstr "umarmt"
-#: ../../extend/addon/addon/morepokes/morepokes.php:23
+#: ../../addon/morepokes/morepokes.php:23
msgid "murder"
msgstr "ermorden"
-#: ../../extend/addon/addon/morepokes/morepokes.php:23
+#: ../../addon/morepokes/morepokes.php:23
msgid "murdered"
msgstr "ermordet"
-#: ../../extend/addon/addon/morepokes/morepokes.php:24
+#: ../../addon/morepokes/morepokes.php:24
msgid "worship"
-msgstr ""
+msgstr "Anbetung"
-#: ../../extend/addon/addon/morepokes/morepokes.php:24
+#: ../../addon/morepokes/morepokes.php:24
msgid "worshipped"
-msgstr ""
+msgstr "angebetet"
-#: ../../extend/addon/addon/morepokes/morepokes.php:25
+#: ../../addon/morepokes/morepokes.php:25
msgid "kiss"
msgstr "küssen"
-#: ../../extend/addon/addon/morepokes/morepokes.php:25
+#: ../../addon/morepokes/morepokes.php:25
msgid "kissed"
msgstr "geküsst"
-#: ../../extend/addon/addon/morepokes/morepokes.php:26
+#: ../../addon/morepokes/morepokes.php:26
msgid "tempt"
msgstr "verlocken"
-#: ../../extend/addon/addon/morepokes/morepokes.php:26
+#: ../../addon/morepokes/morepokes.php:26
msgid "tempted"
msgstr "verlockt"
-#: ../../extend/addon/addon/morepokes/morepokes.php:27
+#: ../../addon/morepokes/morepokes.php:27
msgid "raise eyebrows at"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:27
+#: ../../addon/morepokes/morepokes.php:27
msgid "raised their eyebrows at"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:28
+#: ../../addon/morepokes/morepokes.php:28
msgid "insult"
msgstr "beleidigen"
-#: ../../extend/addon/addon/morepokes/morepokes.php:28
+#: ../../addon/morepokes/morepokes.php:28
msgid "insulted"
msgstr "beleidigt"
-#: ../../extend/addon/addon/morepokes/morepokes.php:29
+#: ../../addon/morepokes/morepokes.php:29
msgid "praise"
msgstr "loben"
-#: ../../extend/addon/addon/morepokes/morepokes.php:29
+#: ../../addon/morepokes/morepokes.php:29
msgid "praised"
msgstr "gelobt"
-#: ../../extend/addon/addon/morepokes/morepokes.php:30
+#: ../../addon/morepokes/morepokes.php:30
msgid "be dubious of"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:30
+#: ../../addon/morepokes/morepokes.php:30
msgid "was dubious of"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:31
+#: ../../addon/morepokes/morepokes.php:31
msgid "eat"
msgstr "essen"
-#: ../../extend/addon/addon/morepokes/morepokes.php:31
+#: ../../addon/morepokes/morepokes.php:31
msgid "ate"
msgstr "aß"
-#: ../../extend/addon/addon/morepokes/morepokes.php:32
+#: ../../addon/morepokes/morepokes.php:32
msgid "giggle and fawn at"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:32
+#: ../../addon/morepokes/morepokes.php:32
msgid "giggled and fawned at"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:33
+#: ../../addon/morepokes/morepokes.php:33
msgid "doubt"
msgstr "anzweifeln"
-#: ../../extend/addon/addon/morepokes/morepokes.php:33
+#: ../../addon/morepokes/morepokes.php:33
msgid "doubted"
msgstr "angezweifelt"
-#: ../../extend/addon/addon/morepokes/morepokes.php:34
+#: ../../addon/morepokes/morepokes.php:34
msgid "glare"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:34
+#: ../../addon/morepokes/morepokes.php:34
msgid "glared at"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:35
+#: ../../addon/morepokes/morepokes.php:35
msgid "fuck"
msgstr "ficken"
-#: ../../extend/addon/addon/morepokes/morepokes.php:35
+#: ../../addon/morepokes/morepokes.php:35
msgid "fucked"
msgstr "gefickt"
-#: ../../extend/addon/addon/morepokes/morepokes.php:36
+#: ../../addon/morepokes/morepokes.php:36
msgid "bonk"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:36
+#: ../../addon/morepokes/morepokes.php:36
msgid "bonked"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:37
+#: ../../addon/morepokes/morepokes.php:37
msgid "declare undying love for"
msgstr ""
-#: ../../extend/addon/addon/morepokes/morepokes.php:37
+#: ../../addon/morepokes/morepokes.php:37
msgid "declared undying love for"
msgstr ""
-#: ../../extend/addon/addon/msgfooter/msgfooter.php:46
-#: ../../extend/addon/addon/xmpp/xmpp.php:91
-msgid "Save Settings"
-msgstr "Einstellungen speichern"
-
-#: ../../extend/addon/addon/msgfooter/msgfooter.php:47
-msgid "text to include in all outgoing posts from this site"
-msgstr "Test der in alle Beiträge angefügt werden soll, die von dieser Seite ausgehen"
+#: ../../addon/diaspora/diaspora.php:763
+msgid "Diaspora Protocol Settings updated."
+msgstr "Diaspora Protokoll Einstellungen aktualisiert"
-#: ../../extend/addon/addon/nofed/nofed.php:42
-msgid "Federate"
-msgstr ""
+#: ../../addon/diaspora/diaspora.php:782
+msgid ""
+"The Diaspora protocol does not support location independence. Connections "
+"you make within that network may be unreachable from alternate channel "
+"locations."
+msgstr "Das Diaspora-Protokoll unterstützt keine Server-unabhängigen Identitäten. Verbindungen, die Du mit diesem Netzwerk eingehst, können von anderen Orten (Klonen) dieses Kanals aus unerreichbar sein."
-#: ../../extend/addon/addon/nofed/nofed.php:56
-msgid "nofed Settings saved."
-msgstr "nofed Einstellungen gespeichert"
+#: ../../addon/diaspora/diaspora.php:785
+msgid "Enable the Diaspora protocol for this channel"
+msgstr "Das Diaspora Protokoll für diesen Kanal aktivieren"
-#: ../../extend/addon/addon/nofed/nofed.php:72
-msgid "Allow Federation Toggle"
-msgstr ""
+#: ../../addon/diaspora/diaspora.php:789
+msgid "Allow any Diaspora member to comment on your public posts"
+msgstr "Erlaube jedem Diaspora Nutzer deine öffentlichen Beiträge zu kommentieren"
-#: ../../extend/addon/addon/nofed/nofed.php:76
-msgid "Federate posts by default"
-msgstr ""
+#: ../../addon/diaspora/diaspora.php:793
+msgid "Prevent your hashtags from being redirected to other sites"
+msgstr "Verhindern, dass Deine Hashtags zu anderen Seiten umgeleitet werden"
-#: ../../extend/addon/addon/nofed/nofed.php:80
-msgid "NoFed Settings"
-msgstr "NoFed-Einstellungen"
+#: ../../addon/diaspora/diaspora.php:797
+msgid ""
+"Sign and forward posts and comments with no existing Diaspora signature"
+msgstr "Signieren und Weiterleiten von Beiträgen und Kommentaren ohne vorhandene Diaspora-Signatur"
-#: ../../extend/addon/addon/nsabait/nsabait.php:125
-msgid "Nsabait Settings updated."
-msgstr "Nsabait-Einstellungen aktualisiert."
+#: ../../addon/diaspora/diaspora.php:802
+msgid "Followed hashtags (comma separated, do not include the #)"
+msgstr "Verfolgte Hashtags (Komma separierte Liste, ohne die #)"
-#: ../../extend/addon/addon/nsabait/nsabait.php:157
-msgid "Enable NSAbait Plugin"
-msgstr ""
+#: ../../addon/diaspora/diaspora.php:807
+msgid "Diaspora Protocol Settings"
+msgstr "Diaspora Protokoll Einstellungen"
-#: ../../extend/addon/addon/nsabait/nsabait.php:161
-msgid "NSAbait Settings"
-msgstr "NSAbait-Einstellungen"
+#: ../../addon/diaspora/import_diaspora.php:16
+msgid "No username found in import file."
+msgstr "Es wurde kein Nutzername in der importierten Datei gefunden."
-#: ../../extend/addon/addon/nsfw/nsfw.php:80
-msgid ""
-"This plugin looks in posts for the words/text you specify below, and "
-"collapses any content containing those keywords so it is not displayed at "
-"inappropriate times, such as sexual innuendo that may be improper in a work "
-"setting. It is polite and recommended to tag any content containing nudity "
-"with #NSFW. This filter can also match any other word/text you specify, and"
-" can thereby be used as a general purpose content filter."
-msgstr ""
+#: ../../addon/diaspora/import_diaspora.php:41 ../../include/import.php:62
+msgid "Unable to create a unique channel address. Import failed."
+msgstr "Es war nicht möglich, eine eindeutige Kanal-Adresse zu erzeugen. Der Import ist fehlgeschlagen."
-#: ../../extend/addon/addon/nsfw/nsfw.php:84
-msgid "Enable Content filter"
-msgstr "Inhaltsfilter aktivieren"
+#: ../../addon/testdrive/testdrive.php:104
+#, php-format
+msgid "Your account on %s will expire in a few days."
+msgstr "Dein Account auf %s wird in ein paar Tagen ablaufen."
-#: ../../extend/addon/addon/nsfw/nsfw.php:88
-msgid "Comma separated list of keywords to hide"
-msgstr ""
+#: ../../addon/testdrive/testdrive.php:105
+msgid "Your $Productname test account is about to expire."
+msgstr "Dein $Productname Test-Account wird bald auslaufen."
-#: ../../extend/addon/addon/nsfw/nsfw.php:88
-msgid "Use /expression/ to provide regular expressions"
-msgstr ""
+#: ../../addon/rainbowtag/rainbowtag.php:81
+msgid "Enable Rainbowtag"
+msgstr "Rainbowtag aktivieren"
-#: ../../extend/addon/addon/nsfw/nsfw.php:92
-msgid "Not Safe For Work Settings"
-msgstr "Not Safe For Work Einstellungen"
+#: ../../addon/rainbowtag/rainbowtag.php:85
+msgid "Rainbowtag Settings"
+msgstr "Rainbowtag-Einstellungen"
-#: ../../extend/addon/addon/nsfw/nsfw.php:92
-msgid "General Purpose Content Filter"
-msgstr "Allzweck-Inhaltsfilter"
+#: ../../addon/rainbowtag/rainbowtag.php:101
+msgid "Rainbowtag Settings saved."
+msgstr "Rainbowtag-Einstellungen gespeichert."
-#: ../../extend/addon/addon/nsfw/nsfw.php:110
-msgid "NSFW Settings saved."
-msgstr "NSFW-Einstellungen gespeichert."
+#: ../../addon/upload_limits/upload_limits.php:25
+msgid "Show Upload Limits"
+msgstr "Hochladebeschränkungen anzeigen"
-#: ../../extend/addon/addon/nsfw/nsfw.php:207
-msgid "Possible adult content"
-msgstr "Möglicherweise nicht jugendfreie Inhalte"
+#: ../../addon/upload_limits/upload_limits.php:27
+msgid "Hubzilla configured maximum size: "
+msgstr "Die in Hubzilla eingestellte maximale Größe:"
-#: ../../extend/addon/addon/nsfw/nsfw.php:211
-#, php-format
-msgid "%s - click to open/close"
-msgstr "%s - zum öffnen/schließen anklicken"
+#: ../../addon/upload_limits/upload_limits.php:28
+msgid "PHP upload_max_filesize: "
+msgstr "PHP upload_max_filesize:"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:49
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:127
-msgid "System defaults:"
-msgstr "Systemstandardeinstellungen:"
+#: ../../addon/upload_limits/upload_limits.php:29
+msgid "PHP post_max_size (must be larger than upload_max_filesize): "
+msgstr "PHP post_max_size (muss größer sein als upload_max_filesize):"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:53
-msgid "Preferred Clipart IDs"
+#: ../../addon/gravatar/gravatar.php:123
+msgid "generic profile image"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:53
-msgid "List of preferred clipart ids. These will be shown first."
+#: ../../addon/gravatar/gravatar.php:124
+msgid "random geometric pattern"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:54
-msgid "Default Search Term"
+#: ../../addon/gravatar/gravatar.php:125
+msgid "monster face"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:54
-msgid "The default search term. These will be shown second."
+#: ../../addon/gravatar/gravatar.php:126
+msgid "computer generated face"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:55
-msgid "Return After"
+#: ../../addon/gravatar/gravatar.php:127
+msgid "retro arcade style face"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:55
-msgid "Page to load after image selection."
-msgstr ""
+#: ../../addon/gravatar/gravatar.php:128
+msgid "Hub default profile photo"
+msgstr "Standard-Profilfoto für diesen Hub"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:57
-#: ../../include/channel.php:965 ../../include/nav.php:93
-msgid "Edit Profile"
-msgstr "Profile bearbeiten"
+#: ../../addon/gravatar/gravatar.php:143
+msgid "Information"
+msgstr "Information"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:58
-msgid "Profile List"
-msgstr "Profilliste"
+#: ../../addon/gravatar/gravatar.php:143
+msgid ""
+"Libravatar addon is installed, too. Please disable Libravatar addon or this "
+"Gravatar addon.<br>The Libravatar addon will fall back to Gravatar if "
+"nothing was found at Libravatar."
+msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:60
-msgid "Order of Preferred"
-msgstr "Bevorzugte Reihenfolge"
+#: ../../addon/gravatar/gravatar.php:150
+#: ../../addon/msgfooter/msgfooter.php:46 ../../addon/xmpp/xmpp.php:91
+msgid "Save Settings"
+msgstr "Einstellungen speichern"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:60
-msgid "Sort order of preferred clipart ids."
+#: ../../addon/gravatar/gravatar.php:151
+msgid "Default avatar image"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:61
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:67
-msgid "Newest first"
-msgstr "Neueste zuerst"
+#: ../../addon/gravatar/gravatar.php:151
+msgid "Select default avatar image if none was found at Gravatar. See README"
+msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:64
-msgid "As entered"
-msgstr "Wie eingegeben"
+#: ../../addon/gravatar/gravatar.php:152
+msgid "Rating of images"
+msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:66
-msgid "Order of other"
+#: ../../addon/gravatar/gravatar.php:152
+msgid "Select the appropriate avatar rating for your site. See README"
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:66
-msgid "Sort order of other clipart ids."
+#: ../../addon/gravatar/gravatar.php:165
+msgid "Gravatar settings updated."
msgstr ""
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:68
-msgid "Most downloaded first"
-msgstr "Meist heruntergeladene zuerst"
+#: ../../addon/visage/visage.php:93
+msgid "Recent Channel/Profile Viewers"
+msgstr "Kürzliche Kanal/Profil Besucher"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:69
-msgid "Most liked first"
-msgstr "Beliebteste zuerst"
+#: ../../addon/visage/visage.php:98
+msgid "This plugin/addon has not been configured."
+msgstr "Dieses Plugin/Addon wurde noch nicht konfiguriert."
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:71
-msgid "Preferred IDs Message"
-msgstr ""
+#: ../../addon/visage/visage.php:99
+#, php-format
+msgid "Please visit the Visage settings on %s"
+msgstr "Bitte rufe die Visage Einstellungen auf %s auf"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:71
-msgid "Message to display above preferred results."
-msgstr ""
+#: ../../addon/visage/visage.php:99
+msgid "your feature settings page"
+msgstr "Die Funktions-Einstellungsseite"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:77
-msgid "Uploaded by: "
-msgstr "Hochgeladen von: "
+#: ../../addon/visage/visage.php:112
+msgid "No entries."
+msgstr "Keine Einträge."
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:77
-msgid "Drawn by: "
-msgstr "Gezeichnet von: "
+#: ../../addon/visage/visage.php:166
+msgid "Enable Visage Visitor Logging"
+msgstr "Aktiviere das Visage-Besucher Logging"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:191
-msgid "Or select from a free OpenClipart.org image:"
-msgstr ""
+#: ../../addon/visage/visage.php:170
+msgid "Visage Settings"
+msgstr "Visage-Einstellungen"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:194
-msgid "Search Term"
-msgstr "Suchbegriff"
+#: ../../addon/nsabait/nsabait.php:125
+msgid "Nsabait Settings updated."
+msgstr "Nsabait-Einstellungen aktualisiert."
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:216
-msgid "Unknown error. Please try again later."
-msgstr "Unbekannter Fehler. Bitte versuchen Sie es später erneut."
+#: ../../addon/nsabait/nsabait.php:157
+msgid "Enable NSAbait Plugin"
+msgstr "Aktiviere das NSAbait Plugin"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:303
-msgid "Profile photo updated successfully."
-msgstr "Profilfoto erfolgreich aktualisiert."
+#: ../../addon/nsabait/nsabait.php:161
+msgid "NSAbait Settings"
+msgstr "NSAbait-Einstellungen"
+
+#: ../../addon/mailtest/mailtest.php:19
+msgid "Send test email"
+msgstr "Test-E-Mail senden"
-#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:146
+#: ../../addon/mailtest/mailtest.php:50 ../../addon/hubwall/hubwall.php:50
+msgid "No recipients found."
+msgstr "Keine Empfänger gefunden."
+
+#: ../../addon/mailtest/mailtest.php:66
+msgid "Mail sent."
+msgstr "Mail gesendet."
+
+#: ../../addon/mailtest/mailtest.php:68
+msgid "Sending of mail failed."
+msgstr "Senden der E-Mail fehlgeschlagen."
+
+#: ../../addon/mailtest/mailtest.php:77
+msgid "Mail Test"
+msgstr "Mail Test"
+
+#: ../../addon/mailtest/mailtest.php:96 ../../addon/hubwall/hubwall.php:92
+msgid "Message subject"
+msgstr "Betreff der Nachricht"
+
+#: ../../addon/openstreetmap/openstreetmap.php:146
msgid "View Larger"
msgstr "Größer anzeigen"
-#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:169
+#: ../../addon/openstreetmap/openstreetmap.php:169
msgid "Tile Server URL"
msgstr "Kachelserver-URL"
-#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:169
+#: ../../addon/openstreetmap/openstreetmap.php:169
msgid ""
"A list of <a href=\"http://wiki.openstreetmap.org/wiki/TMS\" "
"target=\"_blank\">public tile servers</a>"
msgstr "Eine Liste <a href=\"http://wiki.openstreetmap.org/wiki/TMS\" target=\"_blank\">öffentlicher Kachelserver</a>"
-#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:170
+#: ../../addon/openstreetmap/openstreetmap.php:170
msgid "Nominatim (reverse geocoding) Server URL"
msgstr "Nominatim (reverse Geokodierung) Server URL"
-#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:170
+#: ../../addon/openstreetmap/openstreetmap.php:170
msgid ""
"A list of <a href=\"http://wiki.openstreetmap.org/wiki/Nominatim\" "
"target=\"_blank\">Nominatim servers</a>"
msgstr "Eine Liste der <a href=\"http://wiki.openstreetmap.org/wiki/Nominatim\" target=\"_blank\">Nominatim Server</a>"
-#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:171
+#: ../../addon/openstreetmap/openstreetmap.php:171
msgid "Default zoom"
msgstr "Standardzoom"
-#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:171
+#: ../../addon/openstreetmap/openstreetmap.php:171
msgid ""
"The default zoom level. (1:world, 18:highest, also depends on tile server)"
msgstr "Die Standard-Vergrößerungsstufe (1:Welt, 18:höchste, hängt außerdem vom Kachelserver ab)."
-#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:172
+#: ../../addon/openstreetmap/openstreetmap.php:172
msgid "Include marker on map"
msgstr "Markierung auf der Karte einschließen"
-#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:172
+#: ../../addon/openstreetmap/openstreetmap.php:172
msgid "Include a marker on the map."
msgstr "Binde eine Markierung auf der Karte ein."
-#: ../../extend/addon/addon/pageheader/pageheader.php:43
-msgid "Message to display on every page on this server"
-msgstr "Nachricht, die auf jeder Seite dieses Servers angezeigt werden soll"
+#: ../../addon/msgfooter/msgfooter.php:47
+msgid "text to include in all outgoing posts from this site"
+msgstr "Test der in alle Beiträge angefügt werden soll, die von dieser Seite ausgehen"
-#: ../../extend/addon/addon/pageheader/pageheader.php:48
-msgid "Pageheader Settings"
-msgstr "Nachrichtenkopf-Einstellungen"
+#: ../../addon/rtof/rtof.php:45
+msgid "Post to Friendica"
+msgstr "Bei Friendica veröffentlichen"
-#: ../../extend/addon/addon/pageheader/pageheader.php:64
-msgid "pageheader Settings saved."
-msgstr "Nachrichtenkopf-Einstellungen gespeichert."
+#: ../../addon/rtof/rtof.php:62
+msgid "rtof Settings saved."
+msgstr "rtof-Einstellungen gespeichert."
-#: ../../extend/addon/addon/piwik/piwik.php:85
-msgid ""
-"This website is tracked using the <a href='http://www.piwik.org'>Piwik</a> "
-"analytics tool."
-msgstr "Diese Website verwendet <a href='http://www.piwik.org'>Piwik</a>, um die Besucherzugriffe auszuwerten."
+#: ../../addon/rtof/rtof.php:81
+msgid "Allow posting to Friendica"
+msgstr "Erlaube die Veröffentlichung bei Friendica"
-#: ../../extend/addon/addon/piwik/piwik.php:88
-#, php-format
-msgid ""
-"If you do not want that your visits are logged this way you <a href='%s'>can"
-" set a cookie to prevent Piwik from tracking further visits of the site</a> "
-"(opt-out)."
-msgstr "Wenn Du nicht möchtest, dass Deine Besuche zu diesem Zweck gespeichert werden, kannst Du <a href='%s'>ein Cookie setzen, welches Piwik davon abhält, Deine weiteren Besuche auf dieser Website zu verfolgen</a> (Opt-out)."
+#: ../../addon/rtof/rtof.php:85
+msgid "Send public postings to Friendica by default"
+msgstr "Standardmäßig öffentliche Beiträge bei Friendica veröffentlichen"
-#: ../../extend/addon/addon/piwik/piwik.php:96
-msgid "Piwik Base URL"
-msgstr "Piwik Basis-URL"
+#: ../../addon/rtof/rtof.php:89
+msgid "Friendica API Path"
+msgstr "Friendica-API-Pfad"
-#: ../../extend/addon/addon/piwik/piwik.php:96
-msgid ""
-"Absolute path to your Piwik installation. (without protocol (http/s), with "
-"trailing slash)"
-msgstr "Der absolute Pfad zu Deiner Piwik-Installation (ohne Protokoll (http/s), aber mit abschließendem Schrägstrich / )."
+#: ../../addon/rtof/rtof.php:89 ../../addon/redred/redred.php:103
+msgid "https://{sitename}/api"
+msgstr "https://{sitename}/api"
-#: ../../extend/addon/addon/piwik/piwik.php:97
-msgid "Site ID"
-msgstr "Seitenkennung"
+#: ../../addon/rtof/rtof.php:93
+msgid "Friendica login name"
+msgstr "Friendica-Anmeldename"
-#: ../../extend/addon/addon/piwik/piwik.php:98
-msgid "Show opt-out cookie link?"
-msgstr "Den Opt-out Cookie-Link anzeigen?"
+#: ../../addon/rtof/rtof.php:97
+msgid "Friendica password"
+msgstr "Friendica-Passwort"
-#: ../../extend/addon/addon/piwik/piwik.php:99
-msgid "Asynchronous tracking"
-msgstr "Asynchrones Tracking"
+#: ../../addon/rtof/rtof.php:101
+msgid "Hubzilla to Friendica Post Settings"
+msgstr "Hubzilla-zu-Friendica Beitragseinstellungen"
-#: ../../extend/addon/addon/piwik/piwik.php:100
-msgid "Enable frontend JavaScript error tracking"
-msgstr "Ermögliche Frontend-JavaScript-Fehlertracking"
+#: ../../addon/jappixmini/jappixmini.php:305 ../../include/channel.php:1357
+#: ../../include/channel.php:1519
+msgid "Status:"
+msgstr "Status:"
-#: ../../extend/addon/addon/piwik/piwik.php:100
-msgid "This feature requires Piwik >= 2.2.0"
-msgstr "Diese Funktion erfordert Piwik >= 2.2.0"
+#: ../../addon/jappixmini/jappixmini.php:309
+msgid "Activate addon"
+msgstr "Addon aktiviren"
-#: ../../extend/addon/addon/planets/planets.php:121
-msgid "Planets Settings updated."
-msgstr "Planeten Einstellungen aktualisiert"
+#: ../../addon/jappixmini/jappixmini.php:313
+msgid "Hide Jappixmini Chat-Widget from the webinterface"
+msgstr "Jappix Mini Chat-Widget von der Weboberfläche verbergen"
-#: ../../extend/addon/addon/planets/planets.php:153
-msgid "Enable Planets Plugin"
-msgstr "Aktiviere Planeten Plugin"
+#: ../../addon/jappixmini/jappixmini.php:318
+msgid "Jabber username"
+msgstr "Jabber-Benutzername"
-#: ../../extend/addon/addon/planets/planets.php:157
-msgid "Planets Settings"
-msgstr "Planeten Einstellungen"
+#: ../../addon/jappixmini/jappixmini.php:324
+msgid "Jabber server"
+msgstr "Jabber-Server"
-#: ../../extend/addon/addon/pumpio/pumpio.php:148
-msgid "You are now authenticated to pumpio."
-msgstr "Du bist nun bei pumpio authenzifiziert."
+#: ../../addon/jappixmini/jappixmini.php:330
+msgid "Jabber BOSH host URL"
+msgstr "Jabber BOSH Host URL"
-#: ../../extend/addon/addon/pumpio/pumpio.php:149
-msgid "return to the featured settings page"
-msgstr ""
+#: ../../addon/jappixmini/jappixmini.php:337
+msgid "Jabber password"
+msgstr "Jabber-Passwort"
-#: ../../extend/addon/addon/pumpio/pumpio.php:163
-msgid "Post to Pump.io"
-msgstr "Bei pumpio veröffentlichen"
+#: ../../addon/jappixmini/jappixmini.php:343
+msgid "Encrypt Jabber password with Hubzilla password"
+msgstr "Jabber-Passwort mit Hubzilla-Passwort verschlüsseln"
-#: ../../extend/addon/addon/pumpio/pumpio.php:198
-msgid "Pump.io servername"
-msgstr "Pump.io-Servername"
+#: ../../addon/jappixmini/jappixmini.php:347 ../../addon/redred/redred.php:115
+msgid "Hubzilla password"
+msgstr "Hubzilla-Passwort"
-#: ../../extend/addon/addon/pumpio/pumpio.php:198
-msgid "Without \"http://\" or \"https://\""
-msgstr "Ohne \"http://\" oder \"https://\""
+#: ../../addon/jappixmini/jappixmini.php:351
+#: ../../addon/jappixmini/jappixmini.php:355
+msgid "Approve subscription requests from Hubzilla contacts automatically"
+msgstr "Verbindungsanfragen von Hubzilla-Kontakten automatisch annehmen"
-#: ../../extend/addon/addon/pumpio/pumpio.php:202
-msgid "Pump.io username"
-msgstr "Pump.io-Benutzername"
+#: ../../addon/jappixmini/jappixmini.php:359
+msgid "Purge internal list of jabber addresses of contacts"
+msgstr "Interne Liste der Jabber Adressen von Kontakten löschen"
-#: ../../extend/addon/addon/pumpio/pumpio.php:202
-msgid "Without the servername"
-msgstr "Ohne dem Servernamen"
+#: ../../addon/jappixmini/jappixmini.php:364
+msgid "Configuration Help"
+msgstr "Konfigurationshilfe"
-#: ../../extend/addon/addon/pumpio/pumpio.php:213
-msgid "You are not authenticated to pumpio"
-msgstr "Du bist nicht bei pumpio authentifiziert."
+#: ../../addon/jappixmini/jappixmini.php:371
+msgid "Jappix Mini Settings"
+msgstr "Jappix Mini Einstellungen"
-#: ../../extend/addon/addon/pumpio/pumpio.php:215
-msgid "(Re-)Authenticate your pump.io connection"
-msgstr "Deine pumpio Verbindung (erneut) authentifizieren"
+#: ../../addon/superblock/superblock.php:112
+msgid "Currently blocked"
+msgstr "Derzeit blockiert"
-#: ../../extend/addon/addon/pumpio/pumpio.php:219
-msgid "Enable pump.io Post Plugin"
-msgstr "Aktiviere das pumpio-Plugin"
+#: ../../addon/superblock/superblock.php:114
+msgid "No channels currently blocked"
+msgstr "Momentan sind keine Kanäle blockiert"
-#: ../../extend/addon/addon/pumpio/pumpio.php:223
-msgid "Post to pump.io by default"
-msgstr "Standardmäßig bei pumpio veröffentlichen"
+#: ../../addon/superblock/superblock.php:120
+msgid "\"Superblock\" Settings"
+msgstr "\"Superblock\"-Einstellungen"
-#: ../../extend/addon/addon/pumpio/pumpio.php:227
-msgid "Should posts be public"
-msgstr "Sollen die Beiträge öffentlich sein"
+#: ../../addon/superblock/superblock.php:345
+msgid "Block Completely"
+msgstr "Vollständig blockieren"
-#: ../../extend/addon/addon/pumpio/pumpio.php:231
-msgid "Mirror all public posts"
-msgstr "Öffentliche Beiträge spiegeln"
+#: ../../addon/superblock/superblock.php:394
+msgid "superblock settings updated"
+msgstr "Superblock Einstellungen aktualisiert"
-#: ../../extend/addon/addon/pumpio/pumpio.php:237
-msgid "Pump.io Post Settings"
-msgstr "Pump.io-Beitragseinstellungen"
+#: ../../addon/nofed/nofed.php:42
+msgid "Federate"
+msgstr "Beitrag verteilen"
-#: ../../extend/addon/addon/pumpio/pumpio.php:266
-msgid "PumpIO Settings saved."
-msgstr "PumpIO-Einstellungen gespeichert."
+#: ../../addon/nofed/nofed.php:56
+msgid "nofed Settings saved."
+msgstr "nofed Einstellungen gespeichert"
-#: ../../extend/addon/addon/qrator/qrator.php:48
-msgid "QR code"
-msgstr "QR-Code"
+#: ../../addon/nofed/nofed.php:72
+msgid "Allow Federation Toggle"
+msgstr "Umschalter zur Beitragsverteilung bereitstellen"
-#: ../../extend/addon/addon/qrator/qrator.php:63
-msgid "QR Generator"
-msgstr "QR-Generator"
+#: ../../addon/nofed/nofed.php:76
+msgid "Federate posts by default"
+msgstr "Beiträge standardmäßig verteilen"
-#: ../../extend/addon/addon/qrator/qrator.php:64
-msgid "Enter some text"
+#: ../../addon/nofed/nofed.php:80
+msgid "NoFed Settings"
+msgstr "NoFed-Einstellungen"
+
+#: ../../addon/redred/redred.php:45
+msgid "Post to Red"
msgstr ""
-#: ../../extend/addon/addon/rainbowtag/rainbowtag.php:81
-msgid "Enable Rainbowtag"
-msgstr "Rainbowtag aktivieren"
+#: ../../addon/redred/redred.php:60
+msgid "Channel is required."
+msgstr "Kanal ist erforderlich."
-#: ../../extend/addon/addon/rainbowtag/rainbowtag.php:85
-msgid "Rainbowtag Settings"
-msgstr "Rainbowtag-Einstellungen"
+#: ../../addon/redred/redred.php:76
+msgid "redred Settings saved."
+msgstr "redred-Einstellungen gespeichert."
-#: ../../extend/addon/addon/rainbowtag/rainbowtag.php:101
-msgid "Rainbowtag Settings saved."
-msgstr "Rainbowtag-Einstellungen gespeichert."
+#: ../../addon/redred/redred.php:95
+msgid "Allow posting to another Hubzilla Channel"
+msgstr "Erlaube die Veröffentlichung in anderen Hubzilla Kanälen"
-#: ../../extend/addon/addon/randpost/randpost.php:97
-msgid "You're welcome."
-msgstr "Gern geschehen."
+#: ../../addon/redred/redred.php:99
+msgid "Send public postings to Hubzilla channel by default"
+msgstr ""
-#: ../../extend/addon/addon/randpost/randpost.php:98
-msgid "Ah shucks..."
+#: ../../addon/redred/redred.php:103
+msgid "Hubzilla API Path"
+msgstr "Hubzilla-API-Pfad"
+
+#: ../../addon/redred/redred.php:107
+msgid "Hubzilla login name"
+msgstr "Hubzilla-Anmeldename"
+
+#: ../../addon/redred/redred.php:111
+msgid "Hubzilla channel name"
+msgstr "Hubzilla-Kanalname"
+
+#: ../../addon/redred/redred.php:119
+msgid "Hubzilla Crosspost Settings"
msgstr ""
-#: ../../extend/addon/addon/randpost/randpost.php:99
-msgid "Don't mention it."
-msgstr "Keine Ursache."
+#: ../../addon/logrot/logrot.php:36
+msgid "Logfile archive directory"
+msgstr "Verzeichnis der Logdatei"
-#: ../../extend/addon/addon/randpost/randpost.php:100
-msgid "&lt;blush&gt;"
+#: ../../addon/logrot/logrot.php:36
+msgid "Directory to store rotated logs"
+msgstr "Verzeichnis, in dem rotierte Logs gespeichert werden sollen"
+
+#: ../../addon/logrot/logrot.php:37
+msgid "Logfile size in bytes before rotating"
+msgstr "zu erreichende Logdateigröße in Bytes, bevor rotiert wird"
+
+#: ../../addon/logrot/logrot.php:38
+msgid "Number of logfiles to retain"
+msgstr "Anzahl aufzubewahrender rotierter Logdateien"
+
+#: ../../addon/frphotos/frphotos.php:91
+msgid "Friendica Photo Album Import"
+msgstr "Friendica-Fotoalbumimport"
+
+#: ../../addon/frphotos/frphotos.php:92
+msgid "This will import all your Friendica photo albums to this Red channel."
+msgstr "Hiermit werden all deine Fotoalben von Friendica in diesen Hubzilla Kanal importiert."
+
+#: ../../addon/frphotos/frphotos.php:93
+msgid "Friendica Server base URL"
+msgstr "BasisURL des Friendica Servers"
+
+#: ../../addon/frphotos/frphotos.php:94
+msgid "Friendica Login Username"
+msgstr "Friendica-Anmeldebenutzername"
+
+#: ../../addon/frphotos/frphotos.php:95
+msgid "Friendica Login Password"
+msgstr "Friendica-Anmeldepasswort"
+
+#: ../../addon/pubcrawl/as.php:1076 ../../addon/pubcrawl/as.php:1160
+#: ../../addon/pubcrawl/as.php:1332 ../../include/network.php:1705
+msgid "ActivityPub"
+msgstr "ActivityPub"
+
+#: ../../addon/pubcrawl/pubcrawl.php:1032
+msgid "ActivityPub Protocol Settings updated."
msgstr ""
-#: ../../extend/addon/addon/redfiles/redfiles.php:119
-msgid "Redmatrix File Storage Import"
+#: ../../addon/pubcrawl/pubcrawl.php:1041
+msgid ""
+"The ActivityPub protocol does not support location independence. Connections"
+" you make within that network may be unreachable from alternate channel "
+"locations."
msgstr ""
-#: ../../extend/addon/addon/redfiles/redfiles.php:120
-msgid "This will import all your Redmatrix cloud files to this channel."
-msgstr "Hiermit werden alle deine Daten aus der Redmatrix Cloud in diesen Kanal importiert."
+#: ../../addon/pubcrawl/pubcrawl.php:1044
+msgid "Enable the ActivityPub protocol for this channel"
+msgstr ""
-#: ../../extend/addon/addon/redfiles/redfiles.php:121
-#: ../../extend/addon/addon/redphotos/redphotos.php:131
-msgid "Redmatrix Server base URL"
-msgstr "Basis-URL des Redmatrix Servers"
+#: ../../addon/pubcrawl/pubcrawl.php:1049
+msgid "ActivityPub Protocol Settings"
+msgstr ""
-#: ../../extend/addon/addon/redfiles/redfiles.php:122
-#: ../../extend/addon/addon/redphotos/redphotos.php:132
-msgid "Redmatrix Login Username"
-msgstr "Redmatrix-Anmeldebenutzername"
+#: ../../addon/donate/donate.php:21
+msgid "Project Servers and Resources"
+msgstr "Projektserver und -ressourcen"
-#: ../../extend/addon/addon/redfiles/redfiles.php:123
-#: ../../extend/addon/addon/redphotos/redphotos.php:133
-msgid "Redmatrix Login Password"
-msgstr "Redmatrix-Anmeldepasswort"
+#: ../../addon/donate/donate.php:22
+msgid "Project Creator and Tech Lead"
+msgstr "Projektersteller und Technischer Leiter"
-#: ../../extend/addon/addon/redfiles/redfilehelper.php:67
-msgid "file"
-msgstr "Datei"
+#: ../../addon/donate/donate.php:23
+msgid "Admin, developer, directorymin, support bloke"
+msgstr "Administrator, Entwickler, Verzeichnis Betreibender, Supportleistende"
-#: ../../extend/addon/addon/redphotos/redphotos.php:106
-msgid "Photos imported"
-msgstr "Fotos importiert"
+#: ../../addon/donate/donate.php:50
+msgid ""
+"And the hundreds of other people and organisations who helped make the "
+"Hubzilla possible."
+msgstr "Und die hunderte anderen Menschen und Organisationen, die geholfen haben Hubzilla möglich zu machen."
-#: ../../extend/addon/addon/redphotos/redphotos.php:129
-msgid "Redmatrix Photo Album Import"
-msgstr "Redmatrix-Fotoalbumimport"
+#: ../../addon/donate/donate.php:53
+msgid ""
+"The Redmatrix/Hubzilla projects are provided primarily by volunteers giving "
+"their time and expertise - and often paying out of pocket for services they "
+"share with others."
+msgstr "Die Redmatrix/Hubzilla Projekte werden hauptsächlich von Freiwilligen bereitgestellt, die ihre Zeit und Expertise zur Verfügung stellen - und oft aus eigener Tasche für die Dienste zahlen, die sie mit anderen teilen."
-#: ../../extend/addon/addon/redphotos/redphotos.php:130
-msgid "This will import all your Redmatrix photo albums to this channel."
-msgstr "Hiermit werden all deine Fotoalben von Redmatrix in diesen Kanal importiert."
+#: ../../addon/donate/donate.php:54
+msgid ""
+"There is no corporate funding and no ads, and we do not collect and sell "
+"your personal information. (We don't control your personal information - "
+"<strong>you do</strong>.)"
+msgstr "Es gibt keine Finanzierung durch Firmen, keine Werbung und wir verkaufen Deine persönlichen Daten nicht. (Wir kontrollieren Deine persönlichen Daten nicht - <strong>das machst Du</strong>.)"
-#: ../../extend/addon/addon/redphotos/redphotos.php:134
-msgid "Import just this album"
-msgstr "Nur dieses Album importieren"
+#: ../../addon/donate/donate.php:55
+msgid ""
+"Help support our ground-breaking work in decentralisation, web identity, and"
+" privacy."
+msgstr "Hilf uns bei unserer wegweisenden Arbeit im Bereich der Dezantralisation, von Web-Identitäten und Privatsphäre."
-#: ../../extend/addon/addon/redphotos/redphotos.php:134
-msgid "Leave blank to import all albums"
-msgstr "Leer lassen um alle Alben zu importieren"
+#: ../../addon/donate/donate.php:57
+msgid ""
+"Your donations keep servers and services running and also helps us to "
+"provide innovative new features and continued development."
+msgstr "Die Spenden werden dafür verwendet Server und Dienste am laufen zu halten und helfen desweiteren innovative Neuerungen zu schaffen und die Entwicklung voran zu treiben."
-#: ../../extend/addon/addon/redphotos/redphotos.php:135
-msgid "Maximum count to import"
-msgstr "Maximal zu importierende Anzahl"
+#: ../../addon/donate/donate.php:60
+msgid "Donate"
+msgstr "Spenden"
-#: ../../extend/addon/addon/redphotos/redphotos.php:135
-msgid "0 or blank to import all available"
-msgstr "0 oder leer lassen um alles zu importieren"
+#: ../../addon/donate/donate.php:62
+msgid ""
+"Choose a project, developer, or public hub to support with a one-time "
+"donation"
+msgstr "Wähle ein Projekt, einen Entwickler oder einen öffentlichen Hub den du mit einer einmaligen Spende unterstützen willst."
-#: ../../extend/addon/addon/redred/redred.php:45
-msgid "Post to Red"
-msgstr ""
+#: ../../addon/donate/donate.php:63
+msgid "Donate Now"
+msgstr "Jetzt spenden"
-#: ../../extend/addon/addon/redred/redred.php:60
-msgid "Channel is required."
-msgstr "Kanal ist erforderlich."
+#: ../../addon/donate/donate.php:64
+msgid ""
+"<strong><em>Or</em></strong> become a project sponsor (Hubzilla Project "
+"only)"
+msgstr "<strong><em>Oder</em></strong> werde ein Unterstützer des Projekts (ausschließlich Hubzilla)"
-#: ../../extend/addon/addon/redred/redred.php:65
-msgid "Invalid channel."
-msgstr "Ungültiger Kanal."
+#: ../../addon/donate/donate.php:65
+msgid ""
+"Please indicate if you would like your first name or full name (or nothing) "
+"to appear in our sponsor listing"
+msgstr "Bitte teile uns mit ob dein kompletter Name oder dein Vorname (oder gar nichts) auf unserer Sponsoren-Seite veröffentlicht werden soll."
-#: ../../extend/addon/addon/redred/redred.php:76
-msgid "redred Settings saved."
-msgstr "redred-Einstellungen gespeichert."
+#: ../../addon/donate/donate.php:66
+msgid "Sponsor"
+msgstr "Sponsor"
-#: ../../extend/addon/addon/redred/redred.php:95
-msgid "Allow posting to another Hubzilla Channel"
-msgstr "Erlaube die Veröffentlichung in anderen Hubzilla Kanälen"
+#: ../../addon/donate/donate.php:69
+msgid "Special thanks to: "
+msgstr "Besonderer Dank an: "
-#: ../../extend/addon/addon/redred/redred.php:99
-msgid "Send public postings to Hubzilla channel by default"
+#: ../../addon/chords/Mod_Chords.php:44
+msgid ""
+"This is a fairly comprehensive and complete guitar chord dictionary which "
+"will list most of the available ways to play a certain chord, starting from "
+"the base of the fingerboard up to a few frets beyond the twelfth fret "
+"(beyond which everything repeats). A couple of non-standard tunings are "
+"provided for the benefit of slide players, etc."
msgstr ""
-#: ../../extend/addon/addon/redred/redred.php:103
-msgid "Hubzilla API Path"
-msgstr "Hubzilla-API-Pfad"
+#: ../../addon/chords/Mod_Chords.php:46
+msgid ""
+"Chord names start with a root note (A-G) and may include sharps (#) and "
+"flats (b). This software will parse most of the standard naming conventions "
+"such as maj, min, dim, sus(2 or 4), aug, with optional repeating elements."
+msgstr ""
-#: ../../extend/addon/addon/redred/redred.php:103
-#: ../../extend/addon/addon/rtof/rtof.php:89
-msgid "https://{sitename}/api"
-msgstr "https://{sitename}/api"
+#: ../../addon/chords/Mod_Chords.php:48
+msgid ""
+"Valid examples include A, A7, Am7, Amaj7, Amaj9, Ammaj7, Aadd4, Asus2Add4, "
+"E7b13b11 ..."
+msgstr "Einige gültige Beispiele: A, A7, Am7, Amaj7, Amaj9, Ammaj7, Aadd4, Asus2Add4, E7b13b11 ..."
-#: ../../extend/addon/addon/redred/redred.php:107
-msgid "Hubzilla login name"
-msgstr "Hubzilla-Anmeldename"
+#: ../../addon/chords/Mod_Chords.php:51
+msgid "Guitar Chords"
+msgstr "Gitarrenakkorde"
-#: ../../extend/addon/addon/redred/redred.php:111
-msgid "Hubzilla channel name"
-msgstr "Hubzilla-Kanalname"
+#: ../../addon/chords/Mod_Chords.php:52
+msgid "The complete online chord dictionary"
+msgstr "Das komplette online Akkord-Verzeichnis"
-#: ../../extend/addon/addon/redred/redred.php:111
-#: ../../extend/addon/addon/openid/MysqlProvider.php:54
-msgid "Nickname"
-msgstr "Spitzname"
+#: ../../addon/chords/Mod_Chords.php:57
+msgid "Tuning"
+msgstr "Stimmen"
-#: ../../extend/addon/addon/redred/redred.php:119
-msgid "Hubzilla Crosspost Settings"
-msgstr ""
+#: ../../addon/chords/Mod_Chords.php:58
+msgid "Chord name: example: Em7"
+msgstr "Beispiel Akkord Name: Em7"
-#: ../../extend/addon/addon/rtof/rtof.php:45
-msgid "Post to Friendica"
-msgstr "Bei Friendica veröffentlichen"
+#: ../../addon/chords/Mod_Chords.php:59
+msgid "Show for left handed stringing"
+msgstr "Linkshänder-Besaitung anzeigen"
-#: ../../extend/addon/addon/rtof/rtof.php:62
-msgid "rtof Settings saved."
-msgstr "rtof-Einstellungen gespeichert."
+#: ../../addon/chords/chords.php:33
+msgid "Quick Reference"
+msgstr "Schnellreferenz"
-#: ../../extend/addon/addon/rtof/rtof.php:81
-msgid "Allow posting to Friendica"
-msgstr "Erlaube die Veröffentlichung bei Friendica"
+#: ../../addon/libertree/libertree.php:38
+msgid "Post to Libertree"
+msgstr "Bei Libertree veröffentlichen"
-#: ../../extend/addon/addon/rtof/rtof.php:85
-msgid "Send public postings to Friendica by default"
-msgstr "Standardmäßig öffentliche Beiträge bei Friendica veröffentlichen"
+#: ../../addon/libertree/libertree.php:69
+msgid "Enable Libertree Post Plugin"
+msgstr "Aktivire das Libertree-Plugin"
-#: ../../extend/addon/addon/rtof/rtof.php:89
-msgid "Friendica API Path"
-msgstr "Friendica-API-Pfad"
+#: ../../addon/libertree/libertree.php:73
+msgid "Libertree API token"
+msgstr "Libertree API Token"
-#: ../../extend/addon/addon/rtof/rtof.php:93
-msgid "Friendica login name"
-msgstr "Friendica-Anmeldename"
+#: ../../addon/libertree/libertree.php:77
+msgid "Libertree site URL"
+msgstr "URL der Libertree Seite"
-#: ../../extend/addon/addon/rtof/rtof.php:97
-msgid "Friendica password"
-msgstr "Friendica-Passwort"
+#: ../../addon/libertree/libertree.php:81
+msgid "Post to Libertree by default"
+msgstr "Standardmäßig bei Libertree veröffentlichen"
-#: ../../extend/addon/addon/rtof/rtof.php:101
-msgid "Hubzilla to Friendica Post Settings"
-msgstr ""
+#: ../../addon/libertree/libertree.php:85
+msgid "Libertree Post Settings"
+msgstr "Libertree-Beitragseinstellungen"
-#: ../../extend/addon/addon/sendzid/sendzid.php:25
-msgid "Extended Identity Sharing"
-msgstr "Erweitertes Teilen von Identitäten"
+#: ../../addon/libertree/libertree.php:99
+msgid "Libertree Settings saved."
+msgstr "Libertree-Einstellungen gespeichert."
-#: ../../extend/addon/addon/sendzid/sendzid.php:26
-msgid ""
-"Share your identity with all websites on the internet. When disabled, "
-"identity is only shared with sites in the matrix."
-msgstr ""
+#: ../../addon/flattrwidget/flattrwidget.php:45
+msgid "Flattr this!"
+msgstr "Flattr this!"
-#: ../../extend/addon/addon/skeleton/skeleton.php:59
-msgid "Some setting"
-msgstr ""
+#: ../../addon/flattrwidget/flattrwidget.php:83
+msgid "Flattr widget settings updated."
+msgstr "Flattr Widget Einstellungen aktualisiert"
-#: ../../extend/addon/addon/skeleton/skeleton.php:61
-msgid "A setting"
-msgstr "Eine Einstellung"
+#: ../../addon/flattrwidget/flattrwidget.php:100
+msgid "Flattr user"
+msgstr "Flattr Nutzer"
-#: ../../extend/addon/addon/skeleton/skeleton.php:64
-msgid "Skeleton Settings"
-msgstr ""
+#: ../../addon/flattrwidget/flattrwidget.php:104
+msgid "URL of the Thing to flattr"
+msgstr "URL des Dings zum flattrn"
-#: ../../extend/addon/addon/smileybutton/smileybutton.php:273
-msgid "Deactivate the feature"
-msgstr "Diese Funktion abschalten"
+#: ../../addon/flattrwidget/flattrwidget.php:104
+msgid "If empty channel URL is used"
+msgstr "Falls leer wird die Channel URL verwendet"
-#: ../../extend/addon/addon/smileybutton/smileybutton.php:277
-msgid "Hide the button and show the smilies directly."
-msgstr "Verstecke die Schaltfläche und zeige die Smilies direkt an."
+#: ../../addon/flattrwidget/flattrwidget.php:108
+msgid "Title of the Thing to flattr"
+msgstr "Titel des Dings zum flattrn"
-#: ../../extend/addon/addon/smileybutton/smileybutton.php:281
-msgid "Smileybutton Settings"
-msgstr "Smileyknopf-Einstellungen"
+#: ../../addon/flattrwidget/flattrwidget.php:108
+msgid "If empty \"channel name on The Hubzilla\" will be used"
+msgstr "Falls leer wird \"Kanalname auf The Hubzilla\" verwendet"
-#: ../../extend/addon/addon/startpage/startpage.php:109
-msgid "Page to load after login"
-msgstr "Seite, die nach dem Login geladen werden soll"
+#: ../../addon/flattrwidget/flattrwidget.php:112
+msgid "Static or dynamic flattr button"
+msgstr "Statischer oder dynamischer Flattr Button"
-#: ../../extend/addon/addon/startpage/startpage.php:109
-msgid ""
-"Examples: &quot;apps&quot;, &quot;network?f=&gid=37&quot; (privacy "
-"collection), &quot;channel&quot; or &quot;notifications/system&quot; (leave "
-"blank for default network page (grid)."
-msgstr "Beispiele: &quot;apps&quot;, &quot;network?f=&gid=37&quot; (Gruppen-gefilterte Beiträge), &quot;channel&quot; oder &quot;notifications/system&quot; (freilassen für die Standard-Netzwerkseite (grid)."
+#: ../../addon/flattrwidget/flattrwidget.php:112
+msgid "static"
+msgstr "statisch"
-#: ../../extend/addon/addon/startpage/startpage.php:113
-msgid "Startpage Settings"
-msgstr "Startseiteneinstellungen"
+#: ../../addon/flattrwidget/flattrwidget.php:112
+msgid "dynamic"
+msgstr "dynamisch"
+
+#: ../../addon/flattrwidget/flattrwidget.php:116
+msgid "Alignment of the widget"
+msgstr "Ausrichtung des Widgets"
+
+#: ../../addon/flattrwidget/flattrwidget.php:116
+msgid "left"
+msgstr "links"
+
+#: ../../addon/flattrwidget/flattrwidget.php:116
+msgid "right"
+msgstr "rechts"
+
+#: ../../addon/flattrwidget/flattrwidget.php:120
+msgid "Enable Flattr widget"
+msgstr "Flattr Widget verwenden"
+
+#: ../../addon/flattrwidget/flattrwidget.php:124
+msgid "Flattr Widget Settings"
+msgstr "Flattr Widget Einstellungen"
-#: ../../extend/addon/addon/statusnet/statusnet.php:143
+#: ../../addon/statusnet/statusnet.php:143
msgid "Post to GNU social"
msgstr "Bei GNU social veröffentlichen"
-#: ../../extend/addon/addon/statusnet/statusnet.php:195
+#: ../../addon/statusnet/statusnet.php:195
msgid ""
"Please contact your site administrator.<br />The provided API URL is not "
"valid."
msgstr "Bitte kontaktiere den Administrator deines Hubs.<br />Die angegebene API URL ist nicht korrekt."
-#: ../../extend/addon/addon/statusnet/statusnet.php:232
+#: ../../addon/statusnet/statusnet.php:232
msgid "We could not contact the GNU social API with the Path you entered."
msgstr "Mit dem angegebenen Pfad war es uns nicht möglich, die GNU social API zu erreichen."
-#: ../../extend/addon/addon/statusnet/statusnet.php:266
+#: ../../addon/statusnet/statusnet.php:266
msgid "GNU social settings updated."
msgstr "GNU social Einstellungen aktualisiert."
-#: ../../extend/addon/addon/statusnet/statusnet.php:310
+#: ../../addon/statusnet/statusnet.php:310
msgid "Globally Available GNU social OAuthKeys"
msgstr "Global verfügbare GNU social OAuthKeys"
-#: ../../extend/addon/addon/statusnet/statusnet.php:312
+#: ../../addon/statusnet/statusnet.php:312
msgid ""
"There are preconfigured OAuth key pairs for some GNU social servers "
"available. If you are using one of them, please use these credentials.<br "
"/>If not feel free to connect to any other GNU social instance (see below)."
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:327
+#: ../../addon/statusnet/statusnet.php:327
msgid "Provide your own OAuth Credentials"
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:329
+#: ../../addon/statusnet/statusnet.php:329
msgid ""
"No consumer key pair for GNU social found. Register your Hubzilla Account as"
" an desktop client on your GNU social account, copy the consumer key pair "
@@ -9313,27 +10431,27 @@ msgid ""
"Hubzilla installation at your favourite GNU social installation."
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:333
+#: ../../addon/statusnet/statusnet.php:333
msgid "OAuth Consumer Key"
msgstr "OAuth Consumer Key"
-#: ../../extend/addon/addon/statusnet/statusnet.php:337
+#: ../../addon/statusnet/statusnet.php:337
msgid "OAuth Consumer Secret"
msgstr "OAuth Consumer Secret"
-#: ../../extend/addon/addon/statusnet/statusnet.php:341
+#: ../../addon/statusnet/statusnet.php:341
msgid "Base API Path"
msgstr "Basis Pfad der API"
-#: ../../extend/addon/addon/statusnet/statusnet.php:341
+#: ../../addon/statusnet/statusnet.php:341
msgid "Remember the trailing /"
msgstr "Denke an das abschließende /"
-#: ../../extend/addon/addon/statusnet/statusnet.php:345
+#: ../../addon/statusnet/statusnet.php:345
msgid "GNU social application name"
msgstr "GNU social Anwendungsname"
-#: ../../extend/addon/addon/statusnet/statusnet.php:368
+#: ../../addon/statusnet/statusnet.php:368
msgid ""
"To connect to your GNU social account click the button below to get a "
"security code from GNU social which you have to copy into the input box "
@@ -9341,32 +10459,31 @@ msgid ""
"posted to GNU social."
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:370
+#: ../../addon/statusnet/statusnet.php:370
msgid "Log in with GNU social"
msgstr "Mit GNU social anmelden"
-#: ../../extend/addon/addon/statusnet/statusnet.php:373
+#: ../../addon/statusnet/statusnet.php:373
msgid "Copy the security code from GNU social here"
msgstr "Kopiere den Sicherheitscode von GNU social hier her"
-#: ../../extend/addon/addon/statusnet/statusnet.php:383
+#: ../../addon/statusnet/statusnet.php:383
msgid "Cancel Connection Process"
msgstr "Verbindungsprozes abbrechen"
-#: ../../extend/addon/addon/statusnet/statusnet.php:385
+#: ../../addon/statusnet/statusnet.php:385
msgid "Current GNU social API is"
msgstr "Aktuelle GNU social API ist"
-#: ../../extend/addon/addon/statusnet/statusnet.php:389
+#: ../../addon/statusnet/statusnet.php:389
msgid "Cancel GNU social Connection"
msgstr "GNU social Verbindung trennen"
-#: ../../extend/addon/addon/statusnet/statusnet.php:401
-#: ../../extend/addon/addon/twitter/twitter.php:232
+#: ../../addon/statusnet/statusnet.php:401 ../../addon/twitter/twitter.php:232
msgid "Currently connected to: "
msgstr "Momentan verbunden mit:"
-#: ../../extend/addon/addon/statusnet/statusnet.php:406
+#: ../../addon/statusnet/statusnet.php:406
msgid ""
"<strong>Note</strong>: Due your privacy settings (<em>Hide your profile "
"details from unknown viewers?</em>) the link potentially included in public "
@@ -9374,277 +10491,359 @@ msgid ""
"informing the visitor that the access to your profile has been restricted."
msgstr ""
-#: ../../extend/addon/addon/statusnet/statusnet.php:411
+#: ../../addon/statusnet/statusnet.php:411
msgid "Allow posting to GNU social"
msgstr "Erlaube die Veröffentlichung bei GNU social"
-#: ../../extend/addon/addon/statusnet/statusnet.php:411
+#: ../../addon/statusnet/statusnet.php:411
msgid ""
"If enabled your public postings can be posted to the associated GNU-social "
"account"
msgstr "Wenn aktiv können deine öffentlichen Beiträge bei dem verbundenen GNU social Account veröffentlicht werden."
-#: ../../extend/addon/addon/statusnet/statusnet.php:415
+#: ../../addon/statusnet/statusnet.php:415
msgid "Post to GNU social by default"
msgstr "Standardmäßig bei GNU social veröffentlichen"
-#: ../../extend/addon/addon/statusnet/statusnet.php:415
+#: ../../addon/statusnet/statusnet.php:415
msgid ""
"If enabled your public postings will be posted to the associated GNU-social "
"account by default"
msgstr "Wenn aktiv werden all deine öffentlichen Beiträge standardmäßig bei dem verbundenen GNU social Account veröffentlicht."
-#: ../../extend/addon/addon/statusnet/statusnet.php:424
-#: ../../extend/addon/addon/twitter/twitter.php:255
+#: ../../addon/statusnet/statusnet.php:424 ../../addon/twitter/twitter.php:255
msgid "Clear OAuth configuration"
msgstr "OAuth Konfiguration löschen"
-#: ../../extend/addon/addon/statusnet/statusnet.php:432
+#: ../../addon/statusnet/statusnet.php:432
msgid "GNU social Post Settings"
msgstr "GNU social Einstellungen"
-#: ../../extend/addon/addon/statusnet/statusnet.php:891
+#: ../../addon/statusnet/statusnet.php:891
msgid "API URL"
msgstr "API-URL"
-#: ../../extend/addon/addon/statusnet/statusnet.php:894
+#: ../../addon/statusnet/statusnet.php:894
msgid "Application name"
msgstr "Anwendungsname"
-#: ../../extend/addon/addon/superblock/superblock.php:106
-msgid "Currently blocked"
-msgstr "Derzeit blockiert"
+#: ../../addon/qrator/qrator.php:48
+msgid "QR code"
+msgstr "QR-Code"
-#: ../../extend/addon/addon/superblock/superblock.php:108
-msgid "No channels currently blocked"
-msgstr "Momentan sind keine Kanäle blockiert"
+#: ../../addon/qrator/qrator.php:63
+msgid "QR Generator"
+msgstr "QR-Generator"
-#: ../../extend/addon/addon/superblock/superblock.php:114
-msgid "\"Superblock\" Settings"
-msgstr "\"Superblock\"-Einstellungen"
+#: ../../addon/qrator/qrator.php:64
+msgid "Enter some text"
+msgstr "Etwas Text eingeben"
-#: ../../extend/addon/addon/superblock/superblock.php:279
-msgid "Block Completely"
-msgstr "Vollständig blockieren"
+#: ../../addon/chess/chess.php:278 ../../addon/chess/chess.php:465
+msgid "Invalid game."
+msgstr "Ungültiges Spiel."
-#: ../../extend/addon/addon/superblock/superblock.php:326
-msgid "superblock settings updated"
-msgstr "Superblock Einstellungen aktualisiert"
+#: ../../addon/chess/chess.php:284 ../../addon/chess/chess.php:471
+msgid "You are not a player in this game."
+msgstr "Sie sind kein Spieler in diesem Spiel."
-#: ../../extend/addon/addon/testdrive/testdrive.php:104
-#, php-format
-msgid "Your account on %s will expire in a few days."
-msgstr "Dein Account auf %s wird in ein paar Tagen ablaufen."
+#: ../../addon/chess/chess.php:340
+msgid "You must be a local channel to create a game."
+msgstr "Um ein Spiel zu eröffnen, musst du ein lokaler Kanal sein"
-#: ../../extend/addon/addon/testdrive/testdrive.php:105
-msgid "Your $Productname test account is about to expire."
-msgstr "Dein $Productname Test-Account wird bald auslaufen."
+#: ../../addon/chess/chess.php:358
+msgid "You must select one opponent that is not yourself."
+msgstr "Du musst einen Gegner wählen, der nicht du selbst ist"
-#: ../../extend/addon/addon/tictac/tictac.php:21
-msgid "Three Dimensional Tic-Tac-Toe"
-msgstr "Dreidimensionales Tic-Tac-Toe"
+#: ../../addon/chess/chess.php:367
+msgid "You must select white or black."
+msgstr "Sie müssen weiß oder schwarz auswählen."
-#: ../../extend/addon/addon/tictac/tictac.php:54
-msgid "3D Tic-Tac-Toe"
-msgstr "3D Tic-Tac-Toe"
+#: ../../addon/chess/chess.php:375
+msgid "Error creating new game."
+msgstr "Fehler beim Erstellen eines neuen Spiels."
-#: ../../extend/addon/addon/tictac/tictac.php:59
-msgid "New game"
-msgstr "Neues Spiel"
+#: ../../addon/chess/chess.php:409 ../../include/channel.php:1117
+msgid "Requested channel is not available."
+msgstr "Angeforderte Kanal nicht verfügbar."
-#: ../../extend/addon/addon/tictac/tictac.php:60
-msgid "New game with handicap"
-msgstr "Neues Handicaü-Spiel"
+#: ../../addon/chess/chess.php:423
+msgid "You must select a local channel /chess/channelname"
+msgstr "Du musst einen lokalen Kanal/Schach(Kanalnamen aufwählen"
+
+#: ../../addon/chess/chess.php:969
+msgid "Enable notifications"
+msgstr "Benachrichtigungen aktivieren"
+
+#: ../../addon/twitter/twitter.php:99
+msgid "Post to Twitter"
+msgstr "Bei Twitter veröffentlichen"
+
+#: ../../addon/twitter/twitter.php:154
+msgid "Twitter settings updated."
+msgstr "Twitter-Einstellungen aktualisiert."
-#: ../../extend/addon/addon/tictac/tictac.php:61
+#: ../../addon/twitter/twitter.php:183
msgid ""
-"Three dimensional tic-tac-toe is just like the traditional game except that "
-"it is played on multiple levels simultaneously. "
-msgstr "3D Tic-Tac-Toe funktioniert wie das ursprüngliche Spiel, nur dass es auf mehreren Ebenen gleichzeitig gespielt wird."
+"No consumer key pair for Twitter found. Please contact your site "
+"administrator."
+msgstr "Es wurde kein Consumer-Schlüsselpaar für Twitter gefunden. Bitte kontaktiere deinen Seiten-Administrator."
-#: ../../extend/addon/addon/tictac/tictac.php:62
+#: ../../addon/twitter/twitter.php:205
msgid ""
-"In this case there are three levels. You win by getting three in a row on "
-"any level, as well as up, down, and diagonally across the different levels."
-msgstr "In diesem Fall sind es drei Ebenen. Du gewinnst, wenn es dir gelingt drei in einer Reihe auf einer beliebigen Ebene oder diagonal über die verschiedenen Ebenen hinweg zu erreichen."
+"At this Hubzilla instance the Twitter plugin was enabled but you have not "
+"yet connected your account to your Twitter account. To do so click the "
+"button below to get a PIN from Twitter which you have to copy into the input"
+" box below and submit the form. Only your <strong>public</strong> posts will"
+" be posted to Twitter."
+msgstr "Auf diesem Hubzilla-Server ist das Twitter-Plugin aktiviert, aber Du hast Dich hier noch nicht mit Deinem Twitter-Konto verbunden. Um dies zu tun, klicke die Schaltfläche unten, um eine PIN von Twitter zu erhalten, die Du dann in das Eingabefeld darunter einfügen und das Formular bestätigen musst. Nur Deine <strong>öffentlichen</strong> Beiträge werden auf Twitter geteilt."
-#: ../../extend/addon/addon/tictac/tictac.php:64
+#: ../../addon/twitter/twitter.php:207
+msgid "Log in with Twitter"
+msgstr "Mit Twitter anmelden"
+
+#: ../../addon/twitter/twitter.php:210
+msgid "Copy the PIN from Twitter here"
+msgstr "PIN von Twitter hier her kopieren"
+
+#: ../../addon/twitter/twitter.php:237
msgid ""
-"The handicap game disables the center position on the middle level because "
-"the player claiming this square often has an unfair advantage."
-msgstr "Bei einem Handicap-Spiel wird die Position im Zentrum der mittleren Ebene gesperrt, da der Spieler der dieses Feld für sich beansprucht meist einen unfairen Vorteil hat."
+"<strong>Note:</strong> Due your privacy settings (<em>Hide your profile "
+"details from unknown viewers?</em>) the link potentially included in public "
+"postings relayed to Twitter will lead the visitor to a blank page informing "
+"the visitor that the access to your profile has been restricted."
+msgstr "<strong>Hinweis:</strong> Entsprechend Deiner Privatsphären-Einstellungen (<em>Profil-Details vor nicht angemeldeten Besuchern verbergen?</em>) kann ein ggf. zu Twitter geteilter Link Besucher auf eine leere Seite führen, die darüber informiert, dass der Zugriff zu Deinem Profil eingeschränkt ist."
-#: ../../extend/addon/addon/tictac/tictac.php:183
-msgid "You go first..."
-msgstr "Du darfst anfangen..."
+#: ../../addon/twitter/twitter.php:242
+msgid "Allow posting to Twitter"
+msgstr "Erlaube die Veröffentlichung bei Twitter"
-#: ../../extend/addon/addon/tictac/tictac.php:188
-msgid "I'm going first this time..."
-msgstr "Diesmal werde ich anfangen..."
+#: ../../addon/twitter/twitter.php:242
+msgid ""
+"If enabled your public postings can be posted to the associated Twitter "
+"account"
+msgstr "Wenn aktiv können deine öffentlichen Beiträge bei dem verbundenen Twitter Account veröffentlicht werden."
-#: ../../extend/addon/addon/tictac/tictac.php:194
-msgid "You won!"
-msgstr "Sie haben gewonnen!"
+#: ../../addon/twitter/twitter.php:246
+msgid "Send public postings to Twitter by default"
+msgstr "Standardmäßig öffentliche Beiträge bei Twitter veröffentlichen"
-#: ../../extend/addon/addon/tictac/tictac.php:200
-#: ../../extend/addon/addon/tictac/tictac.php:225
-msgid "\"Cat\" game!"
-msgstr ""
+#: ../../addon/twitter/twitter.php:246
+msgid ""
+"If enabled your public postings will be posted to the associated Twitter "
+"account by default"
+msgstr "Wenn aktiv können deine öffentlichen Beiträge bei dem verbundenen Twitter Account veröffentlicht werden."
-#: ../../extend/addon/addon/tictac/tictac.php:223
-msgid "I won!"
-msgstr "Ich habe gewonnen!"
+#: ../../addon/twitter/twitter.php:264
+msgid "Twitter Post Settings"
+msgstr "Twitter-Beitragseinstellungen"
+
+#: ../../addon/smileybutton/smileybutton.php:211
+msgid "Deactivate the feature"
+msgstr "Diese Funktion abschalten"
+
+#: ../../addon/smileybutton/smileybutton.php:215
+msgid "Hide the button and show the smilies directly."
+msgstr "Verstecke die Schaltfläche und zeige die Smilies direkt an."
+
+#: ../../addon/smileybutton/smileybutton.php:219
+msgid "Smileybutton Settings"
+msgstr "Smileyknopf-Einstellungen"
+
+#: ../../addon/piwik/piwik.php:85
+msgid ""
+"This website is tracked using the <a href='http://www.piwik.org'>Piwik</a> "
+"analytics tool."
+msgstr "Diese Website verwendet <a href='http://www.piwik.org'>Piwik</a>, um die Besucherzugriffe auszuwerten."
+
+#: ../../addon/piwik/piwik.php:88
+#, php-format
+msgid ""
+"If you do not want that your visits are logged this way you <a href='%s'>can"
+" set a cookie to prevent Piwik from tracking further visits of the site</a> "
+"(opt-out)."
+msgstr "Wenn Du nicht möchtest, dass Deine Besuche zu diesem Zweck gespeichert werden, kannst Du <a href='%s'>ein Cookie setzen, welches Piwik davon abhält, Deine weiteren Besuche auf dieser Website zu verfolgen</a> (Opt-out)."
+
+#: ../../addon/piwik/piwik.php:96
+msgid "Piwik Base URL"
+msgstr "Piwik Basis-URL"
+
+#: ../../addon/piwik/piwik.php:96
+msgid ""
+"Absolute path to your Piwik installation. (without protocol (http/s), with "
+"trailing slash)"
+msgstr "Der absolute Pfad zu Deiner Piwik-Installation (ohne Protokoll (http/s), aber mit abschließendem Schrägstrich / )."
+
+#: ../../addon/piwik/piwik.php:97
+msgid "Site ID"
+msgstr "Seitenkennung"
-#: ../../extend/addon/addon/tour/tour.php:75
+#: ../../addon/piwik/piwik.php:98
+msgid "Show opt-out cookie link?"
+msgstr "Den Opt-out Cookie-Link anzeigen?"
+
+#: ../../addon/piwik/piwik.php:99
+msgid "Asynchronous tracking"
+msgstr "Asynchrones Tracking"
+
+#: ../../addon/piwik/piwik.php:100
+msgid "Enable frontend JavaScript error tracking"
+msgstr "Ermögliche Frontend-JavaScript-Fehlertracking"
+
+#: ../../addon/piwik/piwik.php:100
+msgid "This feature requires Piwik >= 2.2.0"
+msgstr "Diese Funktion erfordert Piwik >= 2.2.0"
+
+#: ../../addon/tour/tour.php:75
msgid "Edit your profile and change settings."
msgstr "Bearbeite dein Profil und ändere die Einstellungen."
-#: ../../extend/addon/addon/tour/tour.php:76
+#: ../../addon/tour/tour.php:76
msgid "Click here to see activity from your connections."
msgstr "Klicke hier, um die Aktivitäten Deiner Verbindungen zu sehen."
-#: ../../extend/addon/addon/tour/tour.php:77
+#: ../../addon/tour/tour.php:77
msgid "Click here to see your channel home."
msgstr "Klicke hier, um Deine Kanal-Hauptseite zu sehen."
-#: ../../extend/addon/addon/tour/tour.php:78
+#: ../../addon/tour/tour.php:78
msgid "You can access your private messages from here."
msgstr "Hierüber kannst Du auf Deine privaten Nachrichten zugreifen."
-#: ../../extend/addon/addon/tour/tour.php:79
+#: ../../addon/tour/tour.php:79
msgid "Create new events here."
msgstr "Neue Termine hier erstellen"
-#: ../../extend/addon/addon/tour/tour.php:80
+#: ../../addon/tour/tour.php:80
msgid ""
"You can accept new connections and change permissions for existing ones "
"here. You can also e.g. create groups of contacts."
msgstr "Du kannst hier neue Verbindungen akzeptieren sowie die Einstellungen bereits vorhandener Vebindungen bearbeiten. Außerdem kannst Du Verbindungen in Gruppen zusammenfassen."
-#: ../../extend/addon/addon/tour/tour.php:81
+#: ../../addon/tour/tour.php:81
msgid "System notifications will arrive here"
msgstr "Systembenachrichtigungen werden hier eintreffen"
-#: ../../extend/addon/addon/tour/tour.php:82
+#: ../../addon/tour/tour.php:82
msgid "Search for content and users"
msgstr "Nach Inhalt von Benutzern suchen"
-#: ../../extend/addon/addon/tour/tour.php:83
+#: ../../addon/tour/tour.php:83
msgid "Browse for new contacts"
msgstr "Schaue nach möglichen neuen Verbindungen."
-#: ../../extend/addon/addon/tour/tour.php:84
+#: ../../addon/tour/tour.php:84
msgid "Launch installed apps"
msgstr "Installierte Apps starten"
-#: ../../extend/addon/addon/tour/tour.php:85
+#: ../../addon/tour/tour.php:85
msgid "Looking for help? Click here."
msgstr "Du benötigst Hilfe? Klicke hier."
-#: ../../extend/addon/addon/tour/tour.php:86
+#: ../../addon/tour/tour.php:86
msgid ""
"New events have occurred in your network. Click here to see what has "
"happened!"
msgstr "In Deinem Netzwerk gibt es neue Ereignisse. Klicke hier, um zu sehen, was passiert ist!"
-#: ../../extend/addon/addon/tour/tour.php:87
+#: ../../addon/tour/tour.php:87
msgid "You have received a new private message. Click here to see from who!"
msgstr "Du hast eine neue private Nachricht erhalten. Klicke hier, um zu sehen, von wem!"
-#: ../../extend/addon/addon/tour/tour.php:88
+#: ../../addon/tour/tour.php:88
msgid "There are events this week. Click here too see which!"
msgstr "Es gibt neue Termine diese Woche. Klicke hier, um zu sehen, welche!"
-#: ../../extend/addon/addon/tour/tour.php:89
+#: ../../addon/tour/tour.php:89
msgid "You have received a new introduction. Click here to see who!"
msgstr "Du hast eine neue Verbindungsanfrage erhalten. Klicke hier, um zu sehen, wer es ist!"
-#: ../../extend/addon/addon/tour/tour.php:90
+#: ../../addon/tour/tour.php:90
msgid ""
"There is a new system notification. Click here to see what has happened!"
msgstr "Es gibt eine neue Systembenachrichtigung. Klicke hier, um zu sehen, was passiert ist!"
-#: ../../extend/addon/addon/tour/tour.php:93
+#: ../../addon/tour/tour.php:93
msgid "Click here to share text, images, videos and sound."
msgstr "Klicke hier, um Texte, Bilder, Videos und Klänge zu teilen."
-#: ../../extend/addon/addon/tour/tour.php:94
+#: ../../addon/tour/tour.php:94
msgid "You can write an optional title for your update (good for long posts)."
msgstr "Du kannst Deinem Beitrag einen optionalen Titel geben (gut für lange Beiträge)."
-#: ../../extend/addon/addon/tour/tour.php:95
+#: ../../addon/tour/tour.php:95
msgid "Entering some categories here makes it easier to find your post later."
msgstr "Ein paar Kategorien hier einzugeben, macht es leichter, Deinen Beitrag später wiederzufinden."
-#: ../../extend/addon/addon/tour/tour.php:96
+#: ../../addon/tour/tour.php:96
msgid "Share photos, links, location, etc."
msgstr "Teile Photos, Links, Standort, usw."
-#: ../../extend/addon/addon/tour/tour.php:97
+#: ../../addon/tour/tour.php:97
msgid ""
"Only want to share content for a while? Make it expire at a certain date."
msgstr "Du möchtest diesen Inhalt nur für eine Weile teilen? Dann lass ihn zu einem bestimmten Datum ablaufen."
-#: ../../extend/addon/addon/tour/tour.php:98
+#: ../../addon/tour/tour.php:98
msgid "You can password protect content."
msgstr "Du kannst Inhalte mit einem Passwort schützen."
-#: ../../extend/addon/addon/tour/tour.php:99
+#: ../../addon/tour/tour.php:99
msgid "Choose who you share with."
msgstr "Wähle aus, mit wem Du teilen möchtest."
-#: ../../extend/addon/addon/tour/tour.php:101
+#: ../../addon/tour/tour.php:101
msgid "Click here when you are done."
msgstr "Klicke hier, wenn Du fertig bist."
-#: ../../extend/addon/addon/tour/tour.php:104
+#: ../../addon/tour/tour.php:104
msgid "Adjust from which channels posts should be displayed."
msgstr "Lege fest, von welchen Kanälen Beiträge angezeigt werden sollen."
-#: ../../extend/addon/addon/tour/tour.php:105
+#: ../../addon/tour/tour.php:105
msgid "Only show posts from channels in the specified privacy group."
msgstr "Zeige nur Beträge von Kanälen, die in einer bestimmten Gruppe sind."
-#: ../../extend/addon/addon/tour/tour.php:109
+#: ../../addon/tour/tour.php:109
msgid "Easily find posts containing tags (keywords preceded by the \"#\" symbol)."
msgstr "Finde Beiträge, die bestimmte Tags enthalten (Stichworte, die mit dem \"#\"-Symbol beginnen)."
-#: ../../extend/addon/addon/tour/tour.php:110
+#: ../../addon/tour/tour.php:110
msgid "Easily find posts in given category."
msgstr "Finde Beiträge in bestimmten Kategorien."
-#: ../../extend/addon/addon/tour/tour.php:111
+#: ../../addon/tour/tour.php:111
msgid "Easily find posts by date."
msgstr "Finde Beiträge anhand des Datums."
-#: ../../extend/addon/addon/tour/tour.php:112
+#: ../../addon/tour/tour.php:112
msgid ""
"Suggested users who have volounteered to be shown as suggestions, and who we"
" think you might find interesting."
msgstr "Vorgeschlagene Kanäle, die in ihren Einstellungen zugestimmt haben, als Vorschläge angezeigt zu werden, und die Du eventuell interessant finden könntest."
-#: ../../extend/addon/addon/tour/tour.php:113
+#: ../../addon/tour/tour.php:113
msgid "Here you see channels you have connected to."
msgstr "Hier siehst du die Kanäle, mit denen Du verbunden bist."
-#: ../../extend/addon/addon/tour/tour.php:114
+#: ../../addon/tour/tour.php:114
msgid "Save your search so you can repeat it at a later date."
msgstr "Speichere Deine Suche, so dass Du sie später leicht erneut durchführen kannst."
-#: ../../extend/addon/addon/tour/tour.php:117
+#: ../../addon/tour/tour.php:117
msgid ""
"If you see this icon you can be sure that the sender is who it say it is. It"
" is normal that it is not always possible to verify the sender, so the icon "
"will be missing sometimes. There is usually no need to worry about that."
msgstr "Wenn Du dieses Symbol siehst, kannst Du weitgehend sicher sein, dass der Ansender dem angegebenen entspricht. Nicht immer ist es möglich, den Absender zu verifizieren, daher fehlt das Symbol mitunter. Das ist aber in der Regel kein Grund zur Sorge."
-#: ../../extend/addon/addon/tour/tour.php:118
+#: ../../addon/tour/tour.php:118
msgid ""
"Danger! It seems someone tried to forge a message! This message is not "
"necessarily from who it says it is from!"
msgstr "Vorsicht! Es kann sein, dass jemand versucht, eine Nachricht zu fälschen! Diese Nachricht muss nicht unbedingt vom angegebenen Absender stammen!"
-#: ../../extend/addon/addon/tour/tour.php:125
+#: ../../addon/tour/tour.php:125
msgid ""
"Welcome to Hubzilla! Would you like to see a tour of the UI?</p> <p>You can "
"pause it at any time and continue where you left off by reloading the page, "
@@ -9652,931 +10851,340 @@ msgid ""
"return key"
msgstr "Willkommen zu Hubzilla! Möchtest Du eine Tour der Benutzeroberfläche angezeigt bekommen?</p><p>Du kannst zu jeder Zeit pausieren und fortsetzen, wo Du aufgehört hast, indem Du die Seite neu lädtst, oder zu einer anderen Seite springst.</p><p>Du kannst auc durch das Drücken der Enter-Taste weitergehen."
-#: ../../extend/addon/addon/twitter/twitter.php:99
-msgid "Post to Twitter"
-msgstr "Bei Twitter veröffentlichen"
-
-#: ../../extend/addon/addon/twitter/twitter.php:154
-msgid "Twitter settings updated."
-msgstr "Twitter-Einstellungen aktualisiert."
+#: ../../addon/sendzid/sendzid.php:25
+msgid "Extended Identity Sharing"
+msgstr "Erweitertes Teilen von Identitäten"
-#: ../../extend/addon/addon/twitter/twitter.php:183
+#: ../../addon/sendzid/sendzid.php:26
msgid ""
-"No consumer key pair for Twitter found. Please contact your site "
-"administrator."
-msgstr ""
+"Share your identity with all websites on the internet. When disabled, "
+"identity is only shared with sites in the matrix."
+msgstr "Teile Deine Identität mit allen Webseiten im Internet. Ist dies deaktiviert, wird Deine Identität nur mit Hubzilla-Servern geteilt."
-#: ../../extend/addon/addon/twitter/twitter.php:205
-msgid ""
-"At this Hubzilla instance the Twitter plugin was enabled but you have not "
-"yet connected your account to your Twitter account. To do so click the "
-"button below to get a PIN from Twitter which you have to copy into the input"
-" box below and submit the form. Only your <strong>public</strong> posts will"
-" be posted to Twitter."
-msgstr ""
+#: ../../addon/tictac/tictac.php:21
+msgid "Three Dimensional Tic-Tac-Toe"
+msgstr "Dreidimensionales Tic-Tac-Toe"
-#: ../../extend/addon/addon/twitter/twitter.php:207
-msgid "Log in with Twitter"
-msgstr "Mit Twitter anmelden"
+#: ../../addon/tictac/tictac.php:54
+msgid "3D Tic-Tac-Toe"
+msgstr "3D Tic-Tac-Toe"
-#: ../../extend/addon/addon/twitter/twitter.php:210
-msgid "Copy the PIN from Twitter here"
-msgstr "PIN von Twitter hier her kopieren"
+#: ../../addon/tictac/tictac.php:59
+msgid "New game"
+msgstr "Neues Spiel"
-#: ../../extend/addon/addon/twitter/twitter.php:237
+#: ../../addon/tictac/tictac.php:60
+msgid "New game with handicap"
+msgstr "Neues Handicaü-Spiel"
+
+#: ../../addon/tictac/tictac.php:61
msgid ""
-"<strong>Note:</strong> Due your privacy settings (<em>Hide your profile "
-"details from unknown viewers?</em>) the link potentially included in public "
-"postings relayed to Twitter will lead the visitor to a blank page informing "
-"the visitor that the access to your profile has been restricted."
-msgstr ""
+"Three dimensional tic-tac-toe is just like the traditional game except that "
+"it is played on multiple levels simultaneously. "
+msgstr "3D Tic-Tac-Toe funktioniert wie das ursprüngliche Spiel, nur dass es auf mehreren Ebenen gleichzeitig gespielt wird."
-#: ../../extend/addon/addon/twitter/twitter.php:242
-msgid "Allow posting to Twitter"
-msgstr "Erlaube die Veröffentlichung bei Twitter"
+#: ../../addon/tictac/tictac.php:62
+msgid ""
+"In this case there are three levels. You win by getting three in a row on "
+"any level, as well as up, down, and diagonally across the different levels."
+msgstr "In diesem Fall sind es drei Ebenen. Du gewinnst, wenn es dir gelingt drei in einer Reihe auf einer beliebigen Ebene oder diagonal über die verschiedenen Ebenen hinweg zu erreichen."
-#: ../../extend/addon/addon/twitter/twitter.php:242
+#: ../../addon/tictac/tictac.php:64
msgid ""
-"If enabled your public postings can be posted to the associated Twitter "
-"account"
-msgstr "Wenn aktiv können deine öffentlichen Beiträge bei dem verbundenen Twitter Account veröffentlicht werden."
+"The handicap game disables the center position on the middle level because "
+"the player claiming this square often has an unfair advantage."
+msgstr "Bei einem Handicap-Spiel wird die Position im Zentrum der mittleren Ebene gesperrt, da der Spieler der dieses Feld für sich beansprucht meist einen unfairen Vorteil hat."
-#: ../../extend/addon/addon/twitter/twitter.php:246
-msgid "Send public postings to Twitter by default"
-msgstr "Standardmäßig öffentliche Beiträge bei Twitter veröffentlichen"
+#: ../../addon/tictac/tictac.php:183
+msgid "You go first..."
+msgstr "Du darfst anfangen..."
-#: ../../extend/addon/addon/twitter/twitter.php:246
-msgid ""
-"If enabled your public postings will be posted to the associated Twitter "
-"account by default"
-msgstr "Wenn aktiv können deine öffentlichen Beiträge bei dem verbundenen Twitter Account veröffentlicht werden."
+#: ../../addon/tictac/tictac.php:188
+msgid "I'm going first this time..."
+msgstr "Diesmal werde ich anfangen..."
-#: ../../extend/addon/addon/twitter/twitter.php:264
-msgid "Twitter Post Settings"
-msgstr "Twitter-Beitragseinstellungen"
+#: ../../addon/tictac/tictac.php:194
+msgid "You won!"
+msgstr "Sie haben gewonnen!"
-#: ../../extend/addon/addon/twitter/twitter.php:773
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:95
-msgid "Submit Settings"
-msgstr "Einstellungen absenden"
+#: ../../addon/tictac/tictac.php:200 ../../addon/tictac/tictac.php:225
+msgid "\"Cat\" game!"
+msgstr "\"Katzen\"-Spiel!"
-#: ../../extend/addon/addon/upload_limits/upload_limits.php:25
-msgid "Show Upload Limits"
-msgstr "Hochladebeschränkungen anzeigen"
+#: ../../addon/tictac/tictac.php:223
+msgid "I won!"
+msgstr "Ich habe gewonnen!"
-#: ../../extend/addon/addon/upload_limits/upload_limits.php:27
-msgid "Hubzilla configured maximum size: "
-msgstr "Die in Hubzilla eingestellte maximale Größe:"
+#: ../../addon/pageheader/pageheader.php:43
+msgid "Message to display on every page on this server"
+msgstr "Nachricht, die auf jeder Seite dieses Servers angezeigt werden soll"
-#: ../../extend/addon/addon/upload_limits/upload_limits.php:28
-msgid "PHP upload_max_filesize: "
-msgstr "PHP upload_max_filesize:"
+#: ../../addon/pageheader/pageheader.php:48
+msgid "Pageheader Settings"
+msgstr "Nachrichtenkopf-Einstellungen"
-#: ../../extend/addon/addon/upload_limits/upload_limits.php:29
-msgid "PHP post_max_size (must be larger than upload_max_filesize): "
-msgstr "PHP post_max_size (muss größer sein als upload_max_filesize):"
+#: ../../addon/pageheader/pageheader.php:64
+msgid "pageheader Settings saved."
+msgstr "Nachrichtenkopf-Einstellungen gespeichert."
-#: ../../extend/addon/addon/visage/visage.php:93
-msgid "Recent Channel/Profile Viewers"
-msgstr "Kürzliche Kanal/Profil Besucher"
+#: ../../addon/authchoose/authchoose.php:67
+msgid "Only authenticate automatically to sites of your friends"
+msgstr "Authentifiziere Dich nur auf Seiten deiner Freunde automatisch"
-#: ../../extend/addon/addon/visage/visage.php:98
-msgid "This plugin/addon has not been configured."
-msgstr "Dieses Plugin/Addon wurde noch nicht konfiguriert."
+#: ../../addon/authchoose/authchoose.php:67
+msgid "By default you are automatically authenticated anywhere in the network"
+msgstr "Authentifiziere Dich standardmäßig bei allen Seiten im Netzwerk automatisch"
-#: ../../extend/addon/addon/visage/visage.php:99
-#, php-format
-msgid "Please visit the Visage settings on %s"
-msgstr "Bitte rufe die Visage Einstellungen auf %s auf"
+#: ../../addon/authchoose/authchoose.php:71
+msgid "Authchoose Settings"
+msgstr "Einstellungen für automatische Authentifizierung"
-#: ../../extend/addon/addon/visage/visage.php:99
-msgid "your feature settings page"
-msgstr ""
+#: ../../addon/authchoose/authchoose.php:85
+msgid "Atuhchoose Settings updated."
+msgstr "Einstellungen für automatische Authentifizierung aktualisiert."
-#: ../../extend/addon/addon/visage/visage.php:112
-msgid "No entries."
-msgstr "Keine Einträge."
+#: ../../addon/moremoods/moremoods.php:19
+msgid "lonely"
+msgstr "einsam"
-#: ../../extend/addon/addon/visage/visage.php:166
-msgid "Enable Visage Visitor Logging"
-msgstr "Aktiviere das Visage-Besucher Logging"
+#: ../../addon/moremoods/moremoods.php:20
+msgid "drunk"
+msgstr "betrunken"
-#: ../../extend/addon/addon/visage/visage.php:170
-msgid "Visage Settings"
-msgstr "Visage-Einstellungen"
+#: ../../addon/moremoods/moremoods.php:21
+msgid "horny"
+msgstr "geil"
-#: ../../extend/addon/addon/wholikesme/wholikesme.php:29
-msgid "Who likes me?"
-msgstr "Wer mag mich?"
+#: ../../addon/moremoods/moremoods.php:22
+msgid "stoned"
+msgstr "bekifft"
-#: ../../extend/addon/addon/wppost/wppost.php:45
-msgid "Post to WordPress"
-msgstr "Auf WordPress posten"
+#: ../../addon/moremoods/moremoods.php:23
+msgid "fucked up"
+msgstr "beschissen"
-#: ../../extend/addon/addon/wppost/wppost.php:82
-msgid "Enable WordPress Post Plugin"
-msgstr "Aktiviere das WordPress-Plugin"
+#: ../../addon/moremoods/moremoods.php:24
+msgid "clusterfucked"
+msgstr "clusterfucked"
-#: ../../extend/addon/addon/wppost/wppost.php:86
-msgid "WordPress username"
-msgstr "WordPress-Benutzername"
+#: ../../addon/moremoods/moremoods.php:25
+msgid "crazy"
+msgstr "verrückt"
-#: ../../extend/addon/addon/wppost/wppost.php:90
-msgid "WordPress password"
-msgstr "WordPress-Passwort"
+#: ../../addon/moremoods/moremoods.php:26
+msgid "hurt"
+msgstr "verletzt"
-#: ../../extend/addon/addon/wppost/wppost.php:94
-msgid "WordPress API URL"
-msgstr "WordPress-API-URL"
+#: ../../addon/moremoods/moremoods.php:27
+msgid "sleepy"
+msgstr "müde"
-#: ../../extend/addon/addon/wppost/wppost.php:95
-msgid "Typically https://your-blog.tld/xmlrpc.php"
-msgstr "Normalerweise https://your-blog.tld/xmlrpc.php"
+#: ../../addon/moremoods/moremoods.php:28
+msgid "grumpy"
+msgstr "mürrisch"
-#: ../../extend/addon/addon/wppost/wppost.php:98
-msgid "WordPress blogid"
-msgstr "WordPress blogid"
+#: ../../addon/moremoods/moremoods.php:29
+msgid "high"
+msgstr "hoch"
-#: ../../extend/addon/addon/wppost/wppost.php:99
-msgid "For multi-user sites such as wordpress.com, otherwise leave blank"
-msgstr "Nötig für Mehrbenutzer Seiten wie wordpress.com, andernfalls frei lassen"
+#: ../../addon/moremoods/moremoods.php:30
+msgid "semi-conscious"
+msgstr "halb bewusstlos"
-#: ../../extend/addon/addon/wppost/wppost.php:105
-msgid "Post to WordPress by default"
-msgstr "Standardmäßig auf auf WordPress posten"
+#: ../../addon/moremoods/moremoods.php:31
+msgid "in love"
+msgstr "verliebt"
-#: ../../extend/addon/addon/wppost/wppost.php:109
-msgid "Forward comments (requires hubzilla_wp plugin)"
-msgstr "Kommentare weiterleiten (benötigt hubzilla_wp Plugin)"
+#: ../../addon/moremoods/moremoods.php:32
+msgid "in lust"
+msgstr ""
-#: ../../extend/addon/addon/wppost/wppost.php:113
-msgid "WordPress Post Settings"
-msgstr "WordPress-Beitragseinstellungen"
+#: ../../addon/moremoods/moremoods.php:33
+msgid "naked"
+msgstr "nackt"
-#: ../../extend/addon/addon/wppost/wppost.php:129
-msgid "Wordpress Settings saved."
-msgstr "Wordpress-Einstellungen gespeichert."
+#: ../../addon/moremoods/moremoods.php:34
+msgid "stinky"
+msgstr "stinkend"
+
+#: ../../addon/moremoods/moremoods.php:35
+msgid "sweaty"
+msgstr "verschwitzt"
+
+#: ../../addon/moremoods/moremoods.php:36
+msgid "bleeding out"
+msgstr "blutend"
+
+#: ../../addon/moremoods/moremoods.php:37
+msgid "victorious"
+msgstr "siegreich"
+
+#: ../../addon/moremoods/moremoods.php:38
+msgid "defeated"
+msgstr "besiegt"
+
+#: ../../addon/moremoods/moremoods.php:39
+msgid "envious"
+msgstr "neidisch"
+
+#: ../../addon/moremoods/moremoods.php:40
+msgid "jealous"
+msgstr "eifersüchtig"
-#: ../../extend/addon/addon/xmpp/xmpp.php:31
+#: ../../addon/xmpp/xmpp.php:31
msgid "XMPP settings updated."
msgstr "XMPP-Einstellungen aktualisiert."
-#: ../../extend/addon/addon/xmpp/xmpp.php:53
+#: ../../addon/xmpp/xmpp.php:53
msgid "Enable Chat"
msgstr "Chat aktivieren"
-#: ../../extend/addon/addon/xmpp/xmpp.php:58
+#: ../../addon/xmpp/xmpp.php:58
msgid "Individual credentials"
msgstr "Individuelle Anmeldedaten"
-#: ../../extend/addon/addon/xmpp/xmpp.php:64
+#: ../../addon/xmpp/xmpp.php:64
msgid "Jabber BOSH server"
msgstr "Jabber BOSH Server"
-#: ../../extend/addon/addon/xmpp/xmpp.php:69
+#: ../../addon/xmpp/xmpp.php:69
msgid "XMPP Settings"
msgstr "XMPP-Einstellungen"
-#: ../../extend/addon/addon/xmpp/xmpp.php:92
+#: ../../addon/xmpp/xmpp.php:92
msgid "Jabber BOSH host"
msgstr "Jabber BOSH Host"
-#: ../../extend/addon/addon/xmpp/xmpp.php:93
+#: ../../addon/xmpp/xmpp.php:93
msgid "Use central userbase"
msgstr "Zentrale Benutzerbasis verwenden"
-#: ../../extend/addon/addon/xmpp/xmpp.php:93
+#: ../../addon/xmpp/xmpp.php:93
msgid ""
"If enabled, members will automatically login to an ejabberd server that has "
"to be installed on this machine with synchronized credentials via the "
"\"auth_ejabberd.php\" script."
msgstr ""
-#: ../../extend/addon/addon/cdav/include/widgets.php:37
-msgid "Select Channel"
-msgstr "Kanal auswählen"
-
-#: ../../extend/addon/addon/cdav/include/widgets.php:42
-msgid "Read-write"
-msgstr "Lesen-schreiben"
-
-#: ../../extend/addon/addon/cdav/include/widgets.php:43
-msgid "Read-only"
-msgstr "Nur Lesen"
-
-#: ../../extend/addon/addon/cdav/include/widgets.php:116
-msgid "My Calendars"
-msgstr "Meine Kalender"
-
-#: ../../extend/addon/addon/cdav/include/widgets.php:118
-msgid "Shared Calendars"
-msgstr "Geteilte Kalender"
-
-#: ../../extend/addon/addon/cdav/include/widgets.php:122
-msgid "Share this calendar"
-msgstr "Diesen Kalender teilen"
-
-#: ../../extend/addon/addon/cdav/include/widgets.php:124
-msgid "Calendar name and color"
-msgstr "Kalendername und -farbe"
-
-#: ../../extend/addon/addon/cdav/include/widgets.php:126
-msgid "Create new calendar"
-msgstr "Neuen Kalender erstellen"
-
-#: ../../extend/addon/addon/cdav/include/widgets.php:128
-msgid "Calendar Name"
-msgstr "Kalendername"
-
-#: ../../extend/addon/addon/cdav/include/widgets.php:129
-msgid "Calendar Tools"
-msgstr "Kalenderwerkzeuge"
-
-#: ../../extend/addon/addon/cdav/include/widgets.php:130
-msgid "Import calendar"
-msgstr "Kalender importieren"
-
-#: ../../extend/addon/addon/cdav/include/widgets.php:131
-msgid "Select a calendar to import to"
-msgstr "Kalender zum Hineinimportieren auswählen"
-
-#: ../../extend/addon/addon/cdav/include/widgets.php:158
-msgid "Addressbooks"
-msgstr "Adressbücher"
-
-#: ../../extend/addon/addon/cdav/include/widgets.php:160
-msgid "Addressbook name"
-msgstr "Adressbuchname"
-
-#: ../../extend/addon/addon/cdav/include/widgets.php:162
-msgid "Create new addressbook"
-msgstr "Neues Adressbuch erstellen"
-
-#: ../../extend/addon/addon/cdav/include/widgets.php:163
-msgid "Addressbook Name"
-msgstr "Adressbuchname"
-
-#: ../../extend/addon/addon/cdav/include/widgets.php:165
-msgid "Addressbook Tools"
-msgstr "Adressbuchwerkzeuge"
-
-#: ../../extend/addon/addon/cdav/include/widgets.php:166
-msgid "Import addressbook"
-msgstr "Adressbuch importieren"
-
-#: ../../extend/addon/addon/cdav/include/widgets.php:167
-msgid "Select an addressbook to import to"
-msgstr "Adressbuch zum Hineinimportieren auswählen"
-
-#: ../../extend/addon/addon/cdav/cdav.php:36
-msgid "Errors encountered creating database table: "
-msgstr ""
-
-#: ../../extend/addon/addon/cdav/cdav.php:197
-msgid "Default Calendar"
-msgstr "Standardkalender"
-
-#: ../../extend/addon/addon/cdav/cdav.php:206
-msgid "Default Addressbook"
-msgstr "Standardadressbuch"
-
-#: ../../extend/addon/addon/cdav/cdav.php:215
-msgid "CalDAV/CardDAV Settings saved."
-msgstr "CalDAV/CardDAV-Einstellungen gespeichert."
-
-#: ../../extend/addon/addon/cdav/cdav.php:234
-msgid "Enable CalDAV/CardDAV Server for this channel"
-msgstr "Aktiviere den CalDAV/CardDAV Server für diesen Kanal"
-
-#: ../../extend/addon/addon/cdav/cdav.php:237
-#, php-format
-msgid "Your CalDAV resources are located at %s "
-msgstr "Deine CalDAV Resourcen sind unter %s verfügbar"
-
-#: ../../extend/addon/addon/cdav/cdav.php:240
-#, php-format
-msgid "Your CardDAV resources are located at %s "
-msgstr "Deine CardDAV Ressourcen sind unter %s verfügbar"
-
-#: ../../extend/addon/addon/cdav/cdav.php:246
-msgid "CalDAV/CardDAV Settings"
-msgstr "CalDAV/CardDAV-Einstellungen"
-
-#: ../../extend/addon/addon/cdav/cdav.php:270
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1145
-msgid "Mobile"
-msgstr "Mobil"
-
-#: ../../extend/addon/addon/cdav/cdav.php:271
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1146 ../../include/nav.php:88
-msgid "Home"
-msgstr "Home"
-
-#: ../../extend/addon/addon/cdav/cdav.php:272
-msgid "Home, Voice"
-msgstr "Zuhause, Sprache"
-
-#: ../../extend/addon/addon/cdav/cdav.php:273
-msgid "Home, Fax"
-msgstr "Zuhause, Fax"
-
-#: ../../extend/addon/addon/cdav/cdav.php:274
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1147
-msgid "Work"
-msgstr "Arbeit"
-
-#: ../../extend/addon/addon/cdav/cdav.php:275
-msgid "Work, Voice"
-msgstr "Arbeit, Sprache"
-
-#: ../../extend/addon/addon/cdav/cdav.php:276
-msgid "Work, Fax"
-msgstr "Arbeit, Fax"
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:744
-msgid "INVALID EVENT DISMISSED!"
-msgstr "UNGÜLTIGEN TERMIN ABGELEHNT!"
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:745
-msgid "Summary: "
-msgstr "Zusammenfassung:"
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:746
-msgid "Date: "
-msgstr "Datum:"
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:747
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:754
-msgid "Reason: "
-msgstr "Grund:"
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:752
-msgid "INVALID CARD DISMISSED!"
-msgstr "UNGÜLTIGE KARTE ABGELEHNT!"
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:753
-msgid "Name: "
-msgstr "Name: "
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:770
-msgid ""
-"You have to enable this plugin in Feature/Addon Settings > CalDAV/CardDAV "
-"Settings before you can use it."
-msgstr ""
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:836
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:837
-msgid "Example: YYYY-MM-DD HH:mm"
-msgstr "Beispiel: JJJJ-MM-TT HH:mm"
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:837
-msgid "End date and time"
-msgstr "Enddatum und -zeit"
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:852
-msgid "List month"
-msgstr ""
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:853
-msgid "List week"
-msgstr ""
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:854
-msgid "List day"
-msgstr ""
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:861
-msgid "More"
-msgstr "Mehr"
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:862
-msgid "Less"
-msgstr "Weniger"
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:863
-msgid "Select calendar"
-msgstr "Kalender auswählen"
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:865
-msgid "Delete all"
-msgstr "Alles löschen"
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:867
-msgid "Sorry! Editing of recurrent events is not yet implemented."
-msgstr "Entschuldigung, aber das Bearbeiten von wiederkehrenden Veranstaltungen ist leider noch nicht implementiert."
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1137
-msgid "Organisation"
-msgstr "Organisation"
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1138
-#: ../../include/page_widgets.php:46
-msgid "Title"
-msgstr "Titel"
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1139
-msgid "Phone"
-msgstr "Telefon"
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1141
-msgid "Instant messenger"
-msgstr ""
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1142
-msgid "Website"
-msgstr "Webseite"
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1144
-msgid "Note"
-msgstr "Hinweis"
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1150
-msgid "Add Field"
-msgstr "Feld hinzufügen"
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1155
-msgid "P.O. Box"
-msgstr ""
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1156
-msgid "Additional"
-msgstr "Zusätzlich"
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1157
-msgid "Street"
-msgstr "Straße"
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1158
-msgid "Locality"
-msgstr "Ortschaft"
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1159
-msgid "Region"
-msgstr "Region"
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1160
-msgid "ZIP Code"
-msgstr "Postleitzahl"
-
-#: ../../extend/addon/addon/chess/chess.php:276
-#: ../../extend/addon/addon/chess/chess.php:430
-msgid "Invalid game."
-msgstr "Ungültiges Spiel."
-
-#: ../../extend/addon/addon/chess/chess.php:282
-#: ../../extend/addon/addon/chess/chess.php:436
-msgid "You are not a player in this game."
-msgstr "Sie sind kein Spieler in diesem Spiel."
-
-#: ../../extend/addon/addon/chess/chess.php:315
-msgid "You must be a local channel to create a game."
-msgstr "Um ein Spiel zu eröffnen, musst du ein lokaler Kanal sein"
-
-#: ../../extend/addon/addon/chess/chess.php:333
-msgid "You must select one opponent that is not yourself."
-msgstr "Du musst einen Gegner wählen, der nicht du selbst ist"
-
-#: ../../extend/addon/addon/chess/chess.php:336
-msgid "Creating new game..."
-msgstr "Neues Spiel wird erstellt..."
-
-#: ../../extend/addon/addon/chess/chess.php:342
-msgid "You must select white or black."
-msgstr "Sie müssen weiß oder schwarz auswählen."
-
-#: ../../extend/addon/addon/chess/chess.php:349
-msgid "Error creating new game."
-msgstr "Fehler beim Erstellen eines neuen Spiels."
-
-#: ../../extend/addon/addon/chess/chess.php:379 ../../include/channel.php:816
-msgid "Requested channel is not available."
-msgstr "Angeforderte Kanal nicht verfügbar."
-
-#: ../../extend/addon/addon/chess/chess.php:392
-msgid "You must select a local channel /chess/channelname"
-msgstr "Du musst einen lokalen Kanal/Schach(Kanalnamen aufwählen"
-
-#: ../../extend/addon/addon/chess/chess.php:920
-msgid "Enable notifications"
-msgstr "Benachrichtigungen aktivieren"
-
-#: ../../extend/addon/addon/likebanner/likebanner.php:51
-msgid "Your Webbie:"
-msgstr "Dein Webbie"
-
-#: ../../extend/addon/addon/likebanner/likebanner.php:54
-msgid "Fontsize (px):"
-msgstr "Schriftgröße (px):"
-
-#: ../../extend/addon/addon/likebanner/likebanner.php:68
-msgid "Link:"
-msgstr "Link:"
-
-#: ../../extend/addon/addon/likebanner/likebanner.php:70
-msgid "Like us on Hubzilla"
-msgstr "Like us on Hubzilla"
-
-#: ../../extend/addon/addon/likebanner/likebanner.php:72
-msgid "Embed:"
-msgstr "Einbetten"
-
-#: ../../extend/addon/addon/openid/Mod_Id.php:85
-#: ../../include/selectors.php:49 ../../include/selectors.php:66
-msgid "Male"
-msgstr "Männlich"
-
-#: ../../extend/addon/addon/openid/Mod_Id.php:87
-#: ../../include/selectors.php:49 ../../include/selectors.php:66
-msgid "Female"
-msgstr "Weiblich"
-
-#: ../../extend/addon/addon/openid/Mod_Openid.php:30
-msgid "OpenID protocol error. No ID returned."
-msgstr "OpenID-Protokollfehler. Keine Kennung zurückgegeben."
-
-#: ../../extend/addon/addon/openid/Mod_Openid.php:193
-#: ../../include/auth.php:286
-msgid "Login failed."
-msgstr "Login fehlgeschlagen."
-
-#: ../../extend/addon/addon/openid/MysqlProvider.php:52
-msgid "First Name"
-msgstr "Vorname"
-
-#: ../../extend/addon/addon/openid/MysqlProvider.php:53
-msgid "Last Name"
-msgstr "Nachname"
-
-#: ../../extend/addon/addon/openid/MysqlProvider.php:55
-msgid "Full Name"
-msgstr "Voller Name"
-
-#: ../../extend/addon/addon/openid/MysqlProvider.php:61
-msgid "Profile Photo 16px"
-msgstr "Profilfoto 16 px"
-
-#: ../../extend/addon/addon/openid/MysqlProvider.php:62
-msgid "Profile Photo 32px"
-msgstr "Profilfoto 32 px"
-
-#: ../../extend/addon/addon/openid/MysqlProvider.php:63
-msgid "Profile Photo 48px"
-msgstr "Profilfoto 48 px"
-
-#: ../../extend/addon/addon/openid/MysqlProvider.php:64
-msgid "Profile Photo 64px"
-msgstr "Profilfoto 64 px"
-
-#: ../../extend/addon/addon/openid/MysqlProvider.php:65
-msgid "Profile Photo 80px"
-msgstr "Profilfoto 80 px"
-
-#: ../../extend/addon/addon/openid/MysqlProvider.php:66
-msgid "Profile Photo 128px"
-msgstr "Profilfoto 128 px"
-
-#: ../../extend/addon/addon/openid/MysqlProvider.php:67
-msgid "Timezone"
-msgstr "Zeitzone"
-
-#: ../../extend/addon/addon/openid/MysqlProvider.php:70
-msgid "Birth Year"
-msgstr "Geburtsjahr"
-
-#: ../../extend/addon/addon/openid/MysqlProvider.php:71
-msgid "Birth Month"
-msgstr "Geburtsmonat"
-
-#: ../../extend/addon/addon/openid/MysqlProvider.php:72
-msgid "Birth Day"
-msgstr "Geburtstag"
-
-#: ../../extend/addon/addon/openid/MysqlProvider.php:73
-msgid "Birthdate"
-msgstr "Geburtsdatum"
-
-#: ../../extend/addon/addon/openid/openid.php:49
-msgid ""
-"We encountered a problem while logging in with the OpenID you provided. "
-"Please check the correct spelling of the ID."
-msgstr "Wir haben ein Problem mit der OpenID festgestellt, mit der Du Dich anmelden wolltest. Bitte überprüfe sie noch einmal."
-
-#: ../../extend/addon/addon/openid/openid.php:49
-msgid "The error message was:"
-msgstr "Die Fehlermeldung war:"
-
-#: ../../extend/addon/addon/diaspora_reconnect/diaspora_reconnect.php:44
-#, php-format
-msgid "Reconnecting %d connections"
-msgstr "Erneuere %d Verbindungen"
+#: ../../addon/wholikesme/wholikesme.php:29
+msgid "Who likes me?"
+msgstr "Wer mag mich?"
-#: ../../extend/addon/addon/diaspora_reconnect/diaspora_reconnect.php:63
-msgid "Diaspora Reconnect"
-msgstr ""
+#: ../../addon/pumpio/pumpio.php:148
+msgid "You are now authenticated to pumpio."
+msgstr "Du bist nun bei pumpio authenzifiziert."
-#: ../../extend/addon/addon/diaspora_reconnect/diaspora_reconnect.php:65
-msgid ""
-"Use this form to re-establish Diaspora connections which were initially made"
-" from a different hub."
+#: ../../addon/pumpio/pumpio.php:149
+msgid "return to the featured settings page"
msgstr ""
-#: ../../extend/addon/addon/diaspora_reconnect/diaspora_reconnect.php:70
-msgid "Reconnect"
-msgstr "Erneut verbinden"
-
-#: ../../extend/addon/addon/mailtest/mailtest.php:19
-msgid "Send test email"
-msgstr "Test-E-Mail senden"
-
-#: ../../extend/addon/addon/mailtest/mailtest.php:66
-msgid "Mail sent."
-msgstr "Mail gesendet."
-
-#: ../../extend/addon/addon/mailtest/mailtest.php:68
-msgid "Sending of mail failed."
-msgstr "Senden der E-Mail fehlgeschlagen."
-
-#: ../../extend/addon/addon/mailtest/mailtest.php:77
-msgid "Mail Test"
-msgstr "Mail Test"
-
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:57
-msgid "Errors encountered deleting database table "
-msgstr "Beim Löschen der Datenbanktabelle sind Fehler aufgetreten."
-
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:96
-msgid "Drop tables when uninstalling?"
-msgstr "Lösche Tabellen beim Deinstallieren?"
-
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:96
-msgid ""
-"If checked, the Rendezvous database tables will be deleted when the plugin "
-"is uninstalled."
-msgstr "Wenn ausgewählt, werden die Rendezvous-Tabellen in der Datenbank gelöscht, sobald das Plugin deinstalliert wird."
-
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:97
-msgid "Mapbox Access Token"
-msgstr "Mapbox Zugangs-Token"
-
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:97
-msgid ""
-"If you enter a Mapbox access token, it will be used to retrieve map tiles "
-"from Mapbox instead of the default OpenStreetMap tile server."
-msgstr "Wenn Du ein Mapbox Zugangs-Token eingibst, werden die Kartendaten (Kacheln) damit von Mapbox geladen, anstatt von OpenStreetMap, welches die Voreinstellung ist."
-
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:122
-msgid "Rendezvous"
-msgstr "Rendezvous"
-
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:127
-msgid ""
-"This identity has been deleted by another member due to inactivity. Please "
-"press the \"New identity\" button or refresh the page to register a new "
-"identity. You may use the same name."
-msgstr "Diese Identität wurde von einem anderen Mitglied aufgrund von Inaktivität gelöscht. Bitte klicke auf \"Neue Identität\" oder aktualisiere die Website im Browser, um eine neue Identität zu registrieren. Du kannst dabei den selben Namen verwenden."
-
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:128
-msgid "Welcome to Rendezvous!"
-msgstr "Willkommen bei Rendezvous!"
-
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:129
-msgid ""
-"Enter your name to join this rendezvous. To begin sharing your location with"
-" the other members, tap the GPS control. When your location is discovered, a"
-" red dot will appear and others will be able to see you on the map."
-msgstr "Gib Deinen Namen ein, um diesem Rendezvous beizutreten. Um Deinen Standort mit anderen Mitgliedern zu teilen, klicke auf das GPS Symbol. Sobald Dein Standort ermittelt ist, erscheint ein roter Punkt, und die Anderen werden Dich auf der Karte sehen können."
-
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:131
-msgid "Let's meet here"
-msgstr "Lasst uns hier treffen"
-
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:134
-msgid "New marker"
-msgstr "Neue Markierung"
-
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:135
-msgid "Edit marker"
-msgstr "Markierung bearbeiten"
-
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:136
-msgid "New identity"
-msgstr "Neue Identität"
-
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:137
-msgid "Delete marker"
-msgstr "Markierung löschen"
-
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:138
-msgid "Delete member"
-msgstr "Mitglied löschen"
-
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:139
-msgid "Edit proximity alert"
-msgstr "Annäherungsalarm bearbeiten"
-
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:140
-msgid ""
-"A proximity alert will be issued when this member is within a certain radius"
-" of you.<br><br>Enter a radius in meters (0 to disable):"
-msgstr "Ein Annäherungsalarm wird ausgelöst werden, sobald sich dieses Mitglied innerhalb eines bestimmten Radius von Dir aufhält.<br><br>Gib einen Radius in Metern ein (0 zum Abschalten der Funktion):"
-
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:140
-msgid "distance"
-msgstr "Entfernung"
-
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:150
-msgid "Add new rendezvous"
-msgstr "Neues Rendezvous hinzufügen"
-
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:151
-msgid ""
-"Create a new rendezvous and share the access link with those you wish to "
-"invite to the group. Those who open the link become members of the "
-"rendezvous. They can view other member locations, add markers to the map, or"
-" share their own locations with the group."
-msgstr "Erstelle ein neues Rendezvous und teile den Zugriffslink mit allen, die Du in die Gruppe einladen möchtest. Die, die den Link öffnen, werden Mitglieder des Rendezvous. Sie können die Standorte der anderen Mitglieder sehen, Marker zur Karte hinzufügen oder ihre eigenen Standorte mit der Gruppe teilen."
-
-#: ../../include/Import/import_diaspora.php:16
-msgid "No username found in import file."
-msgstr "Kein Benutzername in der Importdatei gefunden."
-
-#: ../../include/Import/import_diaspora.php:41 ../../include/import.php:51
-msgid "Unable to create a unique channel address. Import failed."
-msgstr "Es war nicht möglich, eine eindeutige Kanal-Adresse zu erzeugen. Der Import ist fehlgeschlagen."
-
-#: ../../include/dba/dba_driver.php:187
-#, php-format
-msgid "Cannot locate DNS info for database server '%s'"
-msgstr "Kann die DNS-Informationen für den Datenbank-Server '%s' nicht finden"
+#: ../../addon/pumpio/pumpio.php:163
+msgid "Post to Pump.io"
+msgstr "Bei pumpio veröffentlichen"
-#: ../../include/datetime.php:147
-msgid "Birthday"
-msgstr "Geburtstag"
+#: ../../addon/pumpio/pumpio.php:198
+msgid "Pump.io servername"
+msgstr "Pump.io-Servername"
-#: ../../include/datetime.php:149
-msgid "Age: "
-msgstr "Alter:"
+#: ../../addon/pumpio/pumpio.php:198
+msgid "Without \"http://\" or \"https://\""
+msgstr "Ohne \"http://\" oder \"https://\""
-#: ../../include/datetime.php:151
-msgid "YYYY-MM-DD or MM-DD"
-msgstr "JJJJ-MM-TT oder MM-TT"
+#: ../../addon/pumpio/pumpio.php:202
+msgid "Pump.io username"
+msgstr "Pump.io-Benutzername"
-#: ../../include/datetime.php:286 ../../boot.php:2563
-msgid "never"
-msgstr "Nie"
+#: ../../addon/pumpio/pumpio.php:202
+msgid "Without the servername"
+msgstr "Ohne dem Servernamen"
-#: ../../include/datetime.php:292
-msgid "less than a second ago"
-msgstr "Vor weniger als einer Sekunde"
+#: ../../addon/pumpio/pumpio.php:213
+msgid "You are not authenticated to pumpio"
+msgstr "Du bist nicht bei pumpio authentifiziert."
-#: ../../include/datetime.php:310
-#, php-format
-msgctxt "e.g. 22 hours ago, 1 minute ago"
-msgid "%1$d %2$s ago"
-msgstr "vor %1$d %2$s"
+#: ../../addon/pumpio/pumpio.php:215
+msgid "(Re-)Authenticate your pump.io connection"
+msgstr "Deine pumpio Verbindung (erneut) authentifizieren"
-#: ../../include/datetime.php:321
-msgctxt "relative_date"
-msgid "year"
-msgid_plural "years"
-msgstr[0] "Jahr"
-msgstr[1] "Jahre"
+#: ../../addon/pumpio/pumpio.php:219
+msgid "Enable pump.io Post Plugin"
+msgstr "Aktiviere das pumpio-Plugin"
-#: ../../include/datetime.php:324
-msgctxt "relative_date"
-msgid "month"
-msgid_plural "months"
-msgstr[0] "Monat"
-msgstr[1] "Monate"
+#: ../../addon/pumpio/pumpio.php:223
+msgid "Post to pump.io by default"
+msgstr "Standardmäßig bei pumpio veröffentlichen"
-#: ../../include/datetime.php:327
-msgctxt "relative_date"
-msgid "week"
-msgid_plural "weeks"
-msgstr[0] "Woche"
-msgstr[1] "Wochen"
+#: ../../addon/pumpio/pumpio.php:227
+msgid "Should posts be public"
+msgstr "Sollen die Beiträge öffentlich sein"
-#: ../../include/datetime.php:330
-msgctxt "relative_date"
-msgid "day"
-msgid_plural "days"
-msgstr[0] "Tag"
-msgstr[1] "Tage"
+#: ../../addon/pumpio/pumpio.php:231
+msgid "Mirror all public posts"
+msgstr "Öffentliche Beiträge spiegeln"
-#: ../../include/datetime.php:333
-msgctxt "relative_date"
-msgid "hour"
-msgid_plural "hours"
-msgstr[0] "Stunde"
-msgstr[1] "Stunden"
+#: ../../addon/pumpio/pumpio.php:237
+msgid "Pump.io Post Settings"
+msgstr "Pump.io-Beitragseinstellungen"
-#: ../../include/datetime.php:336
-msgctxt "relative_date"
-msgid "minute"
-msgid_plural "minutes"
-msgstr[0] "Minute"
-msgstr[1] "Minuten"
+#: ../../addon/pumpio/pumpio.php:266
+msgid "PumpIO Settings saved."
+msgstr "PumpIO-Einstellungen gespeichert."
-#: ../../include/datetime.php:339
-msgctxt "relative_date"
-msgid "second"
-msgid_plural "seconds"
-msgstr[0] "Sekunde"
-msgstr[1] "Sekunden"
+#: ../../addon/ldapauth/ldapauth.php:61
+msgid "An account has been created for you."
+msgstr "Ein Konto wurde für Sie erstellt."
-#: ../../include/datetime.php:576
-#, php-format
-msgid "%1$s's birthday"
-msgstr "%1$ss Geburtstag"
+#: ../../addon/ldapauth/ldapauth.php:68
+msgid "Authentication successful but rejected: account creation is disabled."
+msgstr "Authentifizierung war erfolgreich wurde aber abgewiesen! Das Anlegen von Accounts wurde deaktiviert."
-#: ../../include/datetime.php:577
+#: ../../addon/opensearch/opensearch.php:26
#, php-format
-msgid "Happy Birthday %1$s"
-msgstr "Alles Gute zum Geburtstag, %1$s"
-
-#: ../../include/account.php:35
-msgid "Not a valid email address"
-msgstr "Ungültige E-Mail-Adresse"
-
-#: ../../include/account.php:37
-msgid "Your email domain is not among those allowed on this site"
-msgstr "Deine E-Mail-Adresse ist auf dieser Seite nicht erlaubt"
-
-#: ../../include/account.php:43
-msgid "Your email address is already registered at this site."
-msgstr "Deine E-Mail-Adresse ist auf dieser Seite bereits registriert."
-
-#: ../../include/account.php:75
-msgid "An invitation is required."
-msgstr "Eine Einladung wird benötigt."
-
-#: ../../include/account.php:79
-msgid "Invitation could not be verified."
-msgstr "Die Einladung konnte nicht bestätigt werden."
-
-#: ../../include/account.php:130
-msgid "Please enter the required information."
-msgstr "Bitte gib die benötigten Informationen ein."
+msgctxt "opensearch"
+msgid "Search %1$s (%2$s)"
+msgstr "Suche %1$s (%2$s)"
-#: ../../include/account.php:198
-msgid "Failed to store account information."
-msgstr "Speichern der Nutzerkontodaten fehlgeschlagen."
+#: ../../addon/opensearch/opensearch.php:28
+msgctxt "opensearch"
+msgid "$Projectname"
+msgstr "$Projectname"
-#: ../../include/account.php:263
-#, php-format
-msgid "Registration confirmation for %s"
-msgstr "Registrierungsbestätigung für %s"
+#: ../../addon/opensearch/opensearch.php:43
+msgid "Search $Projectname"
+msgstr "$Projectname suchen"
-#: ../../include/account.php:330
-#, php-format
-msgid "Registration request at %s"
-msgstr "Registrierungsanfrage auf %s"
+#: ../../addon/redfiles/redfiles.php:119
+msgid "Redmatrix File Storage Import"
+msgstr ""
-#: ../../include/account.php:352
-msgid "your registration password"
-msgstr "Dein Registrierungspasswort"
+#: ../../addon/redfiles/redfiles.php:120
+msgid "This will import all your Redmatrix cloud files to this channel."
+msgstr "Hiermit werden alle deine Daten aus der Redmatrix Cloud in diesen Kanal importiert."
-#: ../../include/account.php:358 ../../include/account.php:420
-#, php-format
-msgid "Registration details for %s"
-msgstr "Registrierungsdetails für %s"
+#: ../../addon/redfiles/redfilehelper.php:64
+msgid "file"
+msgstr "Datei"
-#: ../../include/account.php:431
-msgid "Account approved."
-msgstr "Nutzerkonto bestätigt."
+#: ../../addon/hubwall/hubwall.php:19
+msgid "Send email to all members"
+msgstr "E-Mail an alle Mitglieder senden"
-#: ../../include/account.php:471
+#: ../../addon/hubwall/hubwall.php:73
#, php-format
-msgid "Registration revoked for %s"
-msgstr "Registrierung für %s wurde widerrufen"
-
-#: ../../include/account.php:756 ../../include/account.php:758
-msgid "Click here to upgrade."
-msgstr "Klicke hier, um das Upgrade durchzuführen."
-
-#: ../../include/account.php:764
-msgid "This action exceeds the limits set by your subscription plan."
-msgstr "Diese Aktion überschreitet die Grenzen Ihres Abonnements."
-
-#: ../../include/account.php:769
-msgid "This action is not available under your subscription plan."
-msgstr "Diese Aktion ist in Ihrem Abonnement nicht verfügbar."
-
-#: ../../include/message.php:20
-msgid "No recipient provided."
-msgstr "Kein Empfänger angegeben"
+msgid "%1$d of %2$d messages sent."
+msgstr "%1$d von %2$d Nachrichten gesendet."
-#: ../../include/message.php:25
-msgid "[no subject]"
-msgstr "[no subject]"
+#: ../../addon/hubwall/hubwall.php:81
+msgid "Send email to all hub members."
+msgstr "Eine E-Mail an alle Mitglieder dieses Hubs senden."
-#: ../../include/message.php:45
-msgid "Unable to determine sender."
-msgstr "Kann Absender nicht bestimmen."
+#: ../../addon/hubwall/hubwall.php:93
+msgid "Sender Email address"
+msgstr "E-Mail Adresse des Absenders"
-#: ../../include/message.php:223
-msgid "Stored post could not be verified."
-msgstr "Gespeicherter Beitrag konnten nicht überprüft werden."
+#: ../../addon/hubwall/hubwall.php:94
+msgid "Test mode (only send to hub administrator)"
+msgstr "Test Modus (nur an Hub Administratoren senden)"
#: ../../include/selectors.php:30
msgid "Frequently"
@@ -10634,11 +11242,11 @@ msgstr "Transsexuell"
msgid "Hermaphrodite"
msgstr "Zwitter"
-#: ../../include/selectors.php:49
+#: ../../include/selectors.php:49 ../../include/channel.php:1436
msgid "Neuter"
msgstr "Geschlechtslos"
-#: ../../include/selectors.php:49
+#: ../../include/selectors.php:49 ../../include/channel.php:1438
msgid "Non-specific"
msgstr "unklar"
@@ -10818,1031 +11426,681 @@ msgstr "Interessiert mich nicht"
msgid "Ask me"
msgstr "Frag mich mal"
-#: ../../include/channel.php:33
-msgid "Unable to obtain identity information from database"
-msgstr "Kann keine Identitäts-Informationen aus Datenbank beziehen"
+#: ../../include/conversation.php:200
+#, php-format
+msgid "%1$s is now connected with %2$s"
+msgstr "%1$s ist jetzt mit %2$s verbunden"
-#: ../../include/channel.php:67
-msgid "Empty name"
-msgstr "Namensfeld leer"
+#: ../../include/conversation.php:235
+#, php-format
+msgid "%1$s poked %2$s"
+msgstr "%1$s stupste %2$s an"
-#: ../../include/channel.php:70
-msgid "Name too long"
-msgstr "Name ist zu lang"
+#: ../../include/conversation.php:239 ../../include/text.php:1104
+#: ../../include/text.php:1109
+msgid "poked"
+msgstr "stupste"
-#: ../../include/channel.php:181
-msgid "No account identifier"
-msgstr "Keine Account-Kennung"
+#: ../../include/conversation.php:720
+#, php-format
+msgid "View %s's profile @ %s"
+msgstr "%ss Profil auf %s ansehen"
-#: ../../include/channel.php:193
-msgid "Nickname is required."
-msgstr "Spitzname ist erforderlich."
+#: ../../include/conversation.php:740
+msgid "Categories:"
+msgstr "Kategorien:"
-#: ../../include/channel.php:207
-msgid "Reserved nickname. Please choose another."
-msgstr "Reservierter Kurzname. Bitte wähle einen anderen."
+#: ../../include/conversation.php:741
+msgid "Filed under:"
+msgstr "Gespeichert unter:"
-#: ../../include/channel.php:212
-msgid ""
-"Nickname has unsupported characters or is already being used on this site."
-msgstr "Der Spitzname enthält nicht-unterstütze Zeichen oder wird bereits auf dieser Seite genutzt."
+#: ../../include/conversation.php:766
+msgid "View in context"
+msgstr "Im Zusammenhang anschauen"
-#: ../../include/channel.php:272
-msgid "Unable to retrieve created identity"
-msgstr "Kann die erstellte Identität nicht empfangen"
+#: ../../include/conversation.php:867
+msgid "remove"
+msgstr "lösche"
-#: ../../include/channel.php:341
-msgid "Default Profile"
-msgstr "Standard-Profil"
+#: ../../include/conversation.php:872
+msgid "Delete Selected Items"
+msgstr "Lösche die ausgewählten Elemente"
-#: ../../include/channel.php:962
-msgid "Create New Profile"
-msgstr "Neues Profil erstellen"
+#: ../../include/conversation.php:915
+msgid "View Source"
+msgstr "Quelle anzeigen"
-#: ../../include/channel.php:982
-msgid "Visible to everybody"
-msgstr "Für jeden sichtbar"
+#: ../../include/conversation.php:925
+msgid "Follow Thread"
+msgstr "Unterhaltung folgen"
-#: ../../include/channel.php:1055 ../../include/channel.php:1174
-msgid "Gender:"
-msgstr "Geschlecht:"
+#: ../../include/conversation.php:934
+msgid "Unfollow Thread"
+msgstr "Unterhaltung nicht mehr folgen"
-#: ../../include/channel.php:1057 ../../include/channel.php:1229
-msgid "Homepage:"
-msgstr "Homepage:"
+#: ../../include/conversation.php:1025
+msgid "Activity/Posts"
+msgstr "Aktivitäten/Beiträge"
-#: ../../include/channel.php:1058
-msgid "Online Now"
-msgstr "gerade online"
+#: ../../include/conversation.php:1045
+msgid "Edit Connection"
+msgstr "Verbindung bearbeiten"
-#: ../../include/channel.php:1179
-msgid "Like this channel"
-msgstr "Dieser Kanal gefällt mir"
+#: ../../include/conversation.php:1055
+msgid "Message"
+msgstr "Nachricht"
-#: ../../include/channel.php:1203
-msgid "j F, Y"
-msgstr "j. F Y"
+#: ../../include/conversation.php:1189
+#, php-format
+msgid "%s likes this."
+msgstr "%s gefällt das."
-#: ../../include/channel.php:1204
-msgid "j F"
-msgstr "j. F"
+#: ../../include/conversation.php:1189
+#, php-format
+msgid "%s doesn't like this."
+msgstr "%s gefällt das nicht."
-#: ../../include/channel.php:1211
-msgid "Birthday:"
-msgstr "Geburtstag:"
+#: ../../include/conversation.php:1193
+#, php-format
+msgid "<span %1$s>%2$d people</span> like this."
+msgid_plural "<span %1$s>%2$d people</span> like this."
+msgstr[0] "<span %1$s>%2$d Person</span> gefällt das."
+msgstr[1] "<span %1$s>%2$d Leuten</span> gefällt das."
-#: ../../include/channel.php:1224
+#: ../../include/conversation.php:1195
#, php-format
-msgid "for %1$d %2$s"
-msgstr "seit %1$d %2$s"
+msgid "<span %1$s>%2$d people</span> don't like this."
+msgid_plural "<span %1$s>%2$d people</span> don't like this."
+msgstr[0] "<span %1$s>%2$d Person</span> gefällt das nicht."
+msgstr[1] "<span %1$s>%2$d Leuten</span> gefällt das nicht."
-#: ../../include/channel.php:1227
-msgid "Sexual Preference:"
-msgstr "Sexuelle Orientierung:"
+#: ../../include/conversation.php:1201
+msgid "and"
+msgstr "und"
-#: ../../include/channel.php:1233
-msgid "Tags:"
-msgstr "Schlagworte:"
+#: ../../include/conversation.php:1204
+#, php-format
+msgid ", and %d other people"
+msgid_plural ", and %d other people"
+msgstr[0] ""
+msgstr[1] ", und %d andere"
-#: ../../include/channel.php:1235
-msgid "Political Views:"
-msgstr "Politische Ansichten:"
+#: ../../include/conversation.php:1205
+#, php-format
+msgid "%s like this."
+msgstr "%s gefällt das."
-#: ../../include/channel.php:1237
-msgid "Religion:"
-msgstr "Religion:"
+#: ../../include/conversation.php:1205
+#, php-format
+msgid "%s don't like this."
+msgstr "%s gefällt das nicht."
-#: ../../include/channel.php:1241
-msgid "Hobbies/Interests:"
-msgstr "Hobbys/Interessen:"
+#: ../../include/conversation.php:1248
+msgid "Set your location"
+msgstr "Standort"
-#: ../../include/channel.php:1243
-msgid "Likes:"
-msgstr "Gefällt:"
+#: ../../include/conversation.php:1249
+msgid "Clear browser location"
+msgstr "Browser-Standort löschen"
-#: ../../include/channel.php:1245
-msgid "Dislikes:"
-msgstr "Gefällt nicht:"
+#: ../../include/conversation.php:1297
+msgid "Tag term:"
+msgstr "Schlagwort:"
-#: ../../include/channel.php:1247
-msgid "Contact information and Social Networks:"
-msgstr "Kontaktinformation und soziale Netzwerke:"
+#: ../../include/conversation.php:1298
+msgid "Where are you right now?"
+msgstr "Wo bist Du jetzt grade?"
-#: ../../include/channel.php:1249
-msgid "My other channels:"
-msgstr "Meine anderen Kanäle:"
+#: ../../include/conversation.php:1303
+msgid "Choose a different album..."
+msgstr "Wählen Sie ein anderes Album aus..."
-#: ../../include/channel.php:1251
-msgid "Musical interests:"
-msgstr "Musikalische Interessen:"
+#: ../../include/conversation.php:1307
+msgid "Comments enabled"
+msgstr "Kommentare aktiviert"
-#: ../../include/channel.php:1253
-msgid "Books, literature:"
-msgstr "Bücher, Literatur:"
+#: ../../include/conversation.php:1308
+msgid "Comments disabled"
+msgstr "Kommentare deaktiviert"
-#: ../../include/channel.php:1255
-msgid "Television:"
-msgstr "Fernsehen:"
+#: ../../include/conversation.php:1355
+msgid "Page link name"
+msgstr "Link zur Seite"
-#: ../../include/channel.php:1257
-msgid "Film/dance/culture/entertainment:"
-msgstr "Film/Tanz/Kultur/Unterhaltung:"
+#: ../../include/conversation.php:1358
+msgid "Post as"
+msgstr "Veröffentlichen als"
-#: ../../include/channel.php:1259
-msgid "Love/Romance:"
-msgstr "Liebe/Romantik:"
+#: ../../include/conversation.php:1372
+msgid "Toggle voting"
+msgstr "Umfragewerkzeug aktivieren"
-#: ../../include/channel.php:1261
-msgid "Work/employment:"
-msgstr "Arbeit/Anstellung:"
+#: ../../include/conversation.php:1375
+msgid "Disable comments"
+msgstr "Kommentare deaktivieren"
-#: ../../include/channel.php:1263
-msgid "School/education:"
-msgstr "Schule/Ausbildung:"
+#: ../../include/conversation.php:1376
+msgid "Toggle comments"
+msgstr "Kommentare umschalten"
-#: ../../include/channel.php:1284
-msgid "Like this thing"
-msgstr "Gefällt mir"
+#: ../../include/conversation.php:1384
+msgid "Categories (optional, comma-separated list)"
+msgstr "Kategorien (optional, kommagetrennte Liste)"
-#: ../../include/connections.php:95
-msgid "New window"
-msgstr "Neues Fenster"
+#: ../../include/conversation.php:1407
+msgid "Other networks and post services"
+msgstr "Andere Netzwerke und Platformen"
-#: ../../include/connections.php:96
-msgid "Open the selected location in a different window or browser tab"
-msgstr "Öffne die markierte Adresse in einem neuen Browserfenster oder Tab"
+#: ../../include/conversation.php:1413
+msgid "Set publish date"
+msgstr "Veröffentlichungsdatum festlegen"
-#: ../../include/connections.php:214
-#, php-format
-msgid "User '%s' deleted"
-msgstr "Benutzer '%s' gelöscht"
+#: ../../include/conversation.php:1673
+msgid "Commented Order"
+msgstr "Neueste Kommentare"
-#: ../../include/dir_fns.php:141
-msgid "Directory Options"
-msgstr "Verzeichnisoptionen"
+#: ../../include/conversation.php:1676
+msgid "Sort by Comment Date"
+msgstr "Nach Kommentardatum sortiert"
-#: ../../include/dir_fns.php:143
-msgid "Safe Mode"
-msgstr "Sicherer Modus"
+#: ../../include/conversation.php:1680
+msgid "Posted Order"
+msgstr "Neueste Beiträge"
-#: ../../include/dir_fns.php:144
-msgid "Public Forums Only"
-msgstr "Nur öffentliche Foren"
+#: ../../include/conversation.php:1683
+msgid "Sort by Post Date"
+msgstr "Nach Beitragsdatum sortiert"
-#: ../../include/dir_fns.php:145
-msgid "This Website Only"
-msgstr "Nur dieser Hub"
+#: ../../include/conversation.php:1691
+msgid "Posts that mention or involve you"
+msgstr "Beiträge mit Beteiligung Deinerseits"
-#: ../../include/nav.php:85 ../../include/nav.php:118 ../../boot.php:1718
-msgid "Logout"
-msgstr "Abmelden"
+#: ../../include/conversation.php:1700
+msgid "Activity Stream - by date"
+msgstr "Activity Stream – nach Datum sortiert"
-#: ../../include/nav.php:85 ../../include/nav.php:118
-msgid "End this session"
-msgstr "Beende diese Sitzung"
+#: ../../include/conversation.php:1706
+msgid "Starred"
+msgstr "Markiert"
-#: ../../include/nav.php:88
-msgid "Your posts and conversations"
-msgstr "Deine Beiträge und Unterhaltungen"
+#: ../../include/conversation.php:1709
+msgid "Favourite Posts"
+msgstr "Markierte Beiträge"
-#: ../../include/nav.php:89
-msgid "Your profile page"
-msgstr "Deine Profilseite"
+#: ../../include/conversation.php:1716
+msgid "Spam"
+msgstr "Spam"
-#: ../../include/nav.php:91
-msgid "Manage/Edit profiles"
-msgstr "Profile verwalten"
+#: ../../include/conversation.php:1719
+msgid "Posts flagged as SPAM"
+msgstr "Nachrichten, die als SPAM markiert wurden"
-#: ../../include/nav.php:93
-msgid "Edit your profile"
-msgstr "Profil bearbeiten"
+#: ../../include/conversation.php:1794 ../../include/nav.php:402
+msgid "Status Messages and Posts"
+msgstr "Statusnachrichten und Beiträge"
-#: ../../include/nav.php:95
-msgid "Your photos"
-msgstr "Deine Bilder"
+#: ../../include/conversation.php:1807 ../../include/nav.php:415
+msgid "Profile Details"
+msgstr "Profil-Details"
-#: ../../include/nav.php:96
-msgid "Your files"
-msgstr "Deine Dateien"
+#: ../../include/conversation.php:1817 ../../include/nav.php:425
+#: ../../include/photos.php:600
+msgid "Photo Albums"
+msgstr "Fotoalben"
-#: ../../include/nav.php:99
-msgid "Your chatrooms"
-msgstr "Deine Chaträume"
+#: ../../include/conversation.php:1825 ../../include/nav.php:433
+msgid "Files and Storage"
+msgstr "Dateien und Speicher"
-#: ../../include/nav.php:105 ../../include/conversation.php:1735
+#: ../../include/conversation.php:1862 ../../include/nav.php:468
msgid "Bookmarks"
msgstr "Lesezeichen"
-#: ../../include/nav.php:105
-msgid "Your bookmarks"
-msgstr "Deine Lesezeichen"
-
-#: ../../include/nav.php:109
-msgid "Your webpages"
-msgstr "Deine Webseiten"
-
-#: ../../include/nav.php:111
-msgid "Your wikis"
-msgstr "Ihre Wikis"
-
-#: ../../include/nav.php:115
-msgid "Sign in"
-msgstr "Anmelden"
-
-#: ../../include/nav.php:131
-msgid "Remote authentication"
-msgstr "Über Konto auf anderem Server einloggen"
-
-#: ../../include/nav.php:131
-msgid "Click to authenticate to your home hub"
-msgstr "Klicke, um Dich über Deinen Heimat-Server zu authentifizieren"
-
-#: ../../include/nav.php:143
-msgid "Get me home"
-msgstr "Bringe mich nach Hause (eigener Kanal)"
-
-#: ../../include/nav.php:145
-msgid "Log me out of this site"
-msgstr "Logge mich von dieser Seite aus"
-
-#: ../../include/nav.php:150
-msgid "Create an account"
-msgstr "Erzeuge ein Konto"
-
-#: ../../include/nav.php:162
-msgid "Help and documentation"
-msgstr "Hilfe und Dokumentation"
-
-#: ../../include/nav.php:166
-msgid "Applications, utilities, links, games"
-msgstr "Anwendungen (Apps), Zubehör, Links, Spiele"
-
-#: ../../include/nav.php:168
-msgid "Search site @name, #tag, ?docs, content"
-msgstr "Hub durchsuchen: @Name. #Schlagwort, ?Dokumentation, Inhalt"
-
-#: ../../include/nav.php:170
-msgid "Channel Directory"
-msgstr "Kanal-Verzeichnis"
-
-#: ../../include/nav.php:182
-msgid "Your grid"
-msgstr "Dein Grid"
-
-#: ../../include/nav.php:183
-msgid "Mark all grid notifications seen"
-msgstr "Alle Grid-Benachrichtigungen als angesehen markieren"
-
-#: ../../include/nav.php:185
-msgid "Channel home"
-msgstr "Mein Kanal"
-
-#: ../../include/nav.php:186
-msgid "Mark all channel notifications seen"
-msgstr "Markiere alle Kanal-Benachrichtigungen als angesehen"
-
-#: ../../include/nav.php:192
-msgid "Notices"
-msgstr "Benachrichtigungen"
-
-#: ../../include/nav.php:192
-msgid "Notifications"
-msgstr "Benachrichtigungen"
-
-#: ../../include/nav.php:193
-msgid "See all notifications"
-msgstr "Alle Benachrichtigungen ansehen"
-
-#: ../../include/nav.php:196
-msgid "Private mail"
-msgstr "Persönliche Mail"
-
-#: ../../include/nav.php:197
-msgid "See all private messages"
-msgstr "Alle persönlichen Nachrichten ansehen"
-
-#: ../../include/nav.php:198
-msgid "Mark all private messages seen"
-msgstr "Markiere alle persönlichen Nachrichten als gesehen"
-
-#: ../../include/nav.php:199 ../../include/widgets.php:700
-msgid "Inbox"
-msgstr "Eingang"
-
-#: ../../include/nav.php:200 ../../include/widgets.php:705
-msgid "Outbox"
-msgstr "Ausgang"
-
-#: ../../include/nav.php:201 ../../include/widgets.php:710
-msgid "New Message"
-msgstr "Neue Nachricht"
-
-#: ../../include/nav.php:204
-msgid "Event Calendar"
-msgstr "Terminkalender"
-
-#: ../../include/nav.php:205
-msgid "See all events"
-msgstr "Alle Termine ansehen"
-
-#: ../../include/nav.php:206
-msgid "Mark all events seen"
-msgstr "Markiere alle Termine als gesehen"
-
-#: ../../include/nav.php:209
-msgid "Manage Your Channels"
-msgstr "Verwalte Deine Kanäle"
-
-#: ../../include/nav.php:211
-msgid "Account/Channel Settings"
-msgstr "Konto-/Kanal-Einstellungen"
-
-#: ../../include/nav.php:219 ../../include/widgets.php:1665
-msgid "Admin"
-msgstr "Administration"
-
-#: ../../include/nav.php:219
-msgid "Site Setup and Configuration"
-msgstr "Seiten-Einrichtung und -Konfiguration"
-
-#: ../../include/nav.php:250 ../../include/conversation.php:869
-msgid "Loading..."
-msgstr "Lädt ..."
-
-#: ../../include/nav.php:255
-msgid "@name, #tag, ?doc, content"
-msgstr "@Name, #Schlagwort, ?Dokumentation, Inhalt"
-
-#: ../../include/nav.php:256
-msgid "Please wait..."
-msgstr "Bitte warten..."
-
-#: ../../include/features.php:58
-msgid "General Features"
-msgstr "Allgemeine Funktionen"
-
-#: ../../include/features.php:63
-msgid "Multiple Profiles"
-msgstr "Mehrfachprofile"
-
-#: ../../include/features.php:64
-msgid "Ability to create multiple profiles"
-msgstr "Ermöglicht das Anlegen mehrerer Profile pro Kanal"
-
-#: ../../include/features.php:72
-msgid "Advanced Profiles"
-msgstr "Erweiterte Profile"
-
-#: ../../include/features.php:73
-msgid "Additional profile sections and selections"
-msgstr "Stellt zusätzliche Bereiche und Felder im Profil zur Verfügung"
-
-#: ../../include/features.php:81
-msgid "Profile Import/Export"
-msgstr "Profil-Import/Export"
-
-#: ../../include/features.php:82
-msgid "Save and load profile details across sites/channels"
-msgstr "Ermöglicht das Speichern von Profilen, um sie in einen anderen Kanal zu importieren"
-
-#: ../../include/features.php:90
-msgid "Web Pages"
-msgstr "Webseiten"
-
-#: ../../include/features.php:91
-msgid "Provide managed web pages on your channel"
-msgstr "Ermöglicht das Erstellen von Webseiten in Deinem Kanal"
-
-#: ../../include/features.php:100
-msgid "Provide a wiki for your channel"
-msgstr "Stelle ein Wiki in Deinem Kanal zur Verfügung"
-
-#: ../../include/features.php:117
-msgid "Private Notes"
-msgstr "Private Notizen"
-
-#: ../../include/features.php:118
-msgid "Enables a tool to store notes and reminders (note: not encrypted)"
-msgstr "Aktiviert ein Werkzeug mit dem Notizen und Erinnerungen gespeichert werden können (Hinweis: nicht verschlüsselt)"
-
-#: ../../include/features.php:126
-msgid "Navigation Channel Select"
-msgstr "Kanal-Auswahl in der Navigationsleiste"
-
-#: ../../include/features.php:127
-msgid "Change channels directly from within the navigation dropdown menu"
-msgstr "Ermöglicht den direkten Wechsel zu anderen Kanälen über das Navigationsmenü"
-
-#: ../../include/features.php:135
-msgid "Photo Location"
-msgstr "Aufnahmeort"
-
-#: ../../include/features.php:136
-msgid "If location data is available on uploaded photos, link this to a map."
-msgstr "Verlinkt den Aufnahmeort von Fotos (falls verfügbar) auf einer Karte"
-
-#: ../../include/features.php:144
-msgid "Access Controlled Chatrooms"
-msgstr "Zugriffskontrollierte Chaträume"
-
-#: ../../include/features.php:145
-msgid "Provide chatrooms and chat services with access control."
-msgstr "Bieten Sie Chaträume und Chatdienste mit Zugriffskontrolle an."
-
-#: ../../include/features.php:153
-msgid "Smart Birthdays"
-msgstr "Smarte Geburtstage"
-
-#: ../../include/features.php:154
-msgid ""
-"Make birthday events timezone aware in case your friends are scattered "
-"across the planet."
-msgstr "Stellt für Geburtstage einen Zeitzonenbezug her, falls deine Freunde über den ganzen Planeten verstreut sind."
-
-#: ../../include/features.php:162
-msgid "Advanced Directory Search"
-msgstr "Erweiterte Verzeichnissuche"
-
-#: ../../include/features.php:163
-msgid "Allows creation of complex directory search queries"
-msgstr "Ermöglicht die Erstellung komplexer Verzeichnis-Suchabfragen"
-
-#: ../../include/features.php:171
-msgid "Advanced Theme and Layout Settings"
-msgstr "Erweiterte Design- und Layout-Einstellungen"
-
-#: ../../include/features.php:172
-msgid "Allows fine tuning of themes and page layouts"
-msgstr "Erlaubt die Feineinstellung von Designs und Seitenlayouts"
-
-#: ../../include/features.php:182
-msgid "Post Composition Features"
-msgstr "Nachbearbeitungsfunktionen"
-
-#: ../../include/features.php:186
-msgid "Large Photos"
-msgstr "Große Fotos"
+#: ../../include/conversation.php:1865 ../../include/nav.php:471
+msgid "Saved Bookmarks"
+msgstr "Gespeicherte Lesezeichen"
-#: ../../include/features.php:187
-msgid ""
-"Include large (1024px) photo thumbnails in posts. If not enabled, use small "
-"(640px) photo thumbnails"
-msgstr "Große Vorschaubilder (1024px) in Beiträgen anzeigen. Falls nicht aktiviert, werden kleine Vorschaubilder (640px) verwendet."
+#: ../../include/conversation.php:1876 ../../include/nav.php:482
+msgid "View Cards"
+msgstr ""
-#: ../../include/features.php:196
-msgid "Automatically import channel content from other channels or feeds"
-msgstr "Ermöglicht den automatischen Import von Inhalten für diesen Kanal von anderen Kanälen oder Feeds"
+#: ../../include/conversation.php:1887 ../../include/nav.php:494
+msgid "View Webpages"
+msgstr "Webseiten anzeigen"
-#: ../../include/features.php:204
-msgid "Even More Encryption"
-msgstr "Noch mehr Verschlüsselung"
+#: ../../include/conversation.php:1956
+msgctxt "noun"
+msgid "Attending"
+msgid_plural "Attending"
+msgstr[0] "Zusage"
+msgstr[1] "Zusagen"
-#: ../../include/features.php:205
-msgid ""
-"Allow optional encryption of content end-to-end with a shared secret key"
-msgstr "Ermöglicht optional die zusätzliche Verschlüsselung von Inhalten (Ende-zu-Ende mit geteiltem Schlüssel)"
+#: ../../include/conversation.php:1959
+msgctxt "noun"
+msgid "Not Attending"
+msgid_plural "Not Attending"
+msgstr[0] "Absage"
+msgstr[1] "Absagen"
-#: ../../include/features.php:213
-msgid "Enable Voting Tools"
-msgstr "Umfragewerkzeuge aktivieren"
+#: ../../include/conversation.php:1962
+msgctxt "noun"
+msgid "Undecided"
+msgid_plural "Undecided"
+msgstr[0] " Unentschlossen"
+msgstr[1] "Unentschlossene"
-#: ../../include/features.php:214
-msgid "Provide a class of post which others can vote on"
-msgstr "Aktiviert die Umfragewerkzeuge, um anderen die Möglichkeit zu geben, einem Beitrag zuzustimmen, ihn abzulehnen oder sich zu enthalten. (Muss im Beitrag selbst noch aktiviert werden.)"
+#: ../../include/conversation.php:1965
+msgctxt "noun"
+msgid "Agree"
+msgid_plural "Agrees"
+msgstr[0] "Zustimmung"
+msgstr[1] "Zustimmungen"
-#: ../../include/features.php:222
-msgid "Disable Comments"
-msgstr "Kommentare deaktivieren"
+#: ../../include/conversation.php:1968
+msgctxt "noun"
+msgid "Disagree"
+msgid_plural "Disagrees"
+msgstr[0] "Ablehnung"
+msgstr[1] "Ablehnungen"
-#: ../../include/features.php:223
-msgid "Provide the option to disable comments for a post"
-msgstr "Ermöglicht, die Kommentarfunktion für einzelne Beiträge abzuschalten"
+#: ../../include/conversation.php:1971
+msgctxt "noun"
+msgid "Abstain"
+msgid_plural "Abstains"
+msgstr[0] "Enthaltung"
+msgstr[1] "Enthaltungen"
-#: ../../include/features.php:231
-msgid "Delayed Posting"
-msgstr "Verzögertes Senden"
+#: ../../include/dir_fns.php:141
+msgid "Directory Options"
+msgstr "Verzeichnisoptionen"
-#: ../../include/features.php:232
-msgid "Allow posts to be published at a later date"
-msgstr "Ermöglicht es, Beiträge zu einem späteren Zeitpunkt zu veröffentlichen"
+#: ../../include/dir_fns.php:143
+msgid "Safe Mode"
+msgstr "Sicherer Modus"
-#: ../../include/features.php:240
-msgid "Content Expiration"
-msgstr "Verfall von Inhalten"
+#: ../../include/dir_fns.php:144
+msgid "Public Forums Only"
+msgstr "Nur öffentliche Foren"
-#: ../../include/features.php:241
-msgid "Remove posts/comments and/or private messages at a future time"
-msgstr "Ermöglicht das automatische Löschen von Beiträgen, Kommentaren und/oder privaten Nachrichten zu einem zukünftigen Datum."
+#: ../../include/dir_fns.php:145
+msgid "This Website Only"
+msgstr "Nur dieser Hub"
-#: ../../include/features.php:249
-msgid "Suppress Duplicate Posts/Comments"
-msgstr "Doppelte Beiträge unterdrücken"
+#: ../../include/bookmarks.php:34
+#, php-format
+msgid "%1$s's bookmarks"
+msgstr "%1$ss Lesezeichen"
-#: ../../include/features.php:250
+#: ../../include/import.php:41
msgid ""
-"Prevent posts with identical content to be published with less than two "
-"minutes in between submissions."
-msgstr "Verhindert, dass innerhalb von zwei Minuten Beiträge mit identischem Inhalt veröffentlicht werden."
-
-#: ../../include/features.php:261
-msgid "Network and Stream Filtering"
-msgstr "Netzwerk- und Stream-Filter"
-
-#: ../../include/features.php:265
-msgid "Search by Date"
-msgstr "Suche nach Datum"
-
-#: ../../include/features.php:266
-msgid "Ability to select posts by date ranges"
-msgstr "Möglichkeit, Beiträge nach Zeiträumen auszuwählen"
-
-#: ../../include/features.php:274 ../../include/group.php:311
-msgid "Privacy Groups"
-msgstr "Gruppen"
-
-#: ../../include/features.php:275
-msgid "Enable management and selection of privacy groups"
-msgstr "Auswahl und Verwaltung von Gruppen für Kanäle aktivieren"
-
-#: ../../include/features.php:283 ../../include/widgets.php:283
-msgid "Saved Searches"
-msgstr "Gespeicherte Suchanfragen"
-
-#: ../../include/features.php:284
-msgid "Save search terms for re-use"
-msgstr "Ermöglicht das Abspeichern von Suchbegriffen zur Wiederverwendung"
-
-#: ../../include/features.php:292
-msgid "Network Personal Tab"
-msgstr "Persönlicher Netzwerkreiter"
-
-#: ../../include/features.php:293
-msgid "Enable tab to display only Network posts that you've interacted on"
-msgstr "Aktiviert einen Reiter in der Grid-Ansicht, der nur Netzwerk-Beiträge anzeigt, mit denen Du interagiert hast"
-
-#: ../../include/features.php:301
-msgid "Network New Tab"
-msgstr "Netzwerkreiter Neu"
-
-#: ../../include/features.php:302
-msgid "Enable tab to display all new Network activity"
-msgstr "Aktiviert einen Reiter in der Grid-Ansicht, der alle neuen Netzwerkaktivitäten anzeigt"
-
-#: ../../include/features.php:310
-msgid "Affinity Tool"
-msgstr "Beziehungs-Tool"
-
-#: ../../include/features.php:311
-msgid "Filter stream activity by depth of relationships"
-msgstr "Aktiviert ein Werkzeug in der Grid-Ansicht, das den Stream nach Grad der Beziehung filtern kann"
-
-#: ../../include/features.php:320
-msgid "Show friend and connection suggestions"
-msgstr "Freund- und Verbindungsvorschläge anzeigen"
-
-#: ../../include/features.php:328
-msgid "Connection Filtering"
-msgstr "Filter für Verbindungen"
-
-#: ../../include/features.php:329
-msgid "Filter incoming posts from connections based on keywords/content"
-msgstr "Ermöglicht die Filterung eingehender Beiträge anhand von Schlüsselwörtern (muss an der Verbindung konfiguriert werden)"
-
-#: ../../include/features.php:341
-msgid "Post/Comment Tools"
-msgstr "Beitrag-/Kommentar-Tools"
-
-#: ../../include/features.php:345
-msgid "Community Tagging"
-msgstr "Gemeinschaftliches Verschlagworten"
-
-#: ../../include/features.php:346
-msgid "Ability to tag existing posts"
-msgstr "Ermöglicht das Verschlagworten existierender Beiträge"
-
-#: ../../include/features.php:354
-msgid "Post Categories"
-msgstr "Beitrags-Kategorien"
-
-#: ../../include/features.php:355
-msgid "Add categories to your posts"
-msgstr "Aktiviert Kategorien für Beiträge"
-
-#: ../../include/features.php:363
-msgid "Emoji Reactions"
-msgstr "Emoji Reaktionen"
-
-#: ../../include/features.php:364
-msgid "Add emoji reaction ability to posts"
-msgstr "Aktiviert Emoji-Reaktionen für Beiträge"
-
-#: ../../include/features.php:372 ../../include/contact_widgets.php:53
-#: ../../include/widgets.php:346
-msgid "Saved Folders"
-msgstr "Gespeicherte Ordner"
-
-#: ../../include/features.php:373
-msgid "Ability to file posts under folders"
-msgstr "Möglichkeit, Beiträge in Verzeichnissen zu sammeln"
-
-#: ../../include/features.php:381
-msgid "Dislike Posts"
-msgstr "Gefällt-mir-nicht-Beiträge"
-
-#: ../../include/features.php:382
-msgid "Ability to dislike posts/comments"
-msgstr "Aktiviert die „Gefällt mir nicht“-Schaltfläche"
-
-#: ../../include/features.php:390
-msgid "Star Posts"
-msgstr "Beiträge mit Sternchen versehen"
-
-#: ../../include/features.php:391
-msgid "Ability to mark special posts with a star indicator"
-msgstr "Ermöglicht die lokale Markierung spezieller Beiträge mit einem Sternchen-Symbol"
-
-#: ../../include/features.php:399
-msgid "Tag Cloud"
-msgstr "Schlagwort-Wolke"
-
-#: ../../include/features.php:400
-msgid "Provide a personal tag cloud on your channel page"
-msgstr "Aktiviert die Anzeige einer Schlagwort-Wolke (Tag Cloud) auf Deiner Kanal-Seite"
-
-#: ../../include/features.php:412
-msgid "Premium Channel"
-msgstr "Premium-Kanal"
+"Cannot create a duplicate channel identifier on this system. Import failed."
+msgstr "Kann keinen doppelten Kanal-Identifikator auf diesem System erzeugen (Spitzname oder Hash schon belegt). Import fehlgeschlagen."
-#: ../../include/features.php:413
-msgid ""
-"Allows you to set restrictions and terms on those that connect with your "
-"channel"
-msgstr "Ermöglicht es, Einschränkungen und Bedingungen für Verbindungen dieses Kanals festzulegen"
+#: ../../include/import.php:105
+msgid "Cloned channel not found. Import failed."
+msgstr "Geklonter Kanal nicht gefunden. Import fehlgeschlagen."
-#: ../../include/text.php:460
+#: ../../include/text.php:478
msgid "prev"
msgstr "vorherige"
-#: ../../include/text.php:462
+#: ../../include/text.php:480
msgid "first"
msgstr "erste"
-#: ../../include/text.php:491
+#: ../../include/text.php:509
msgid "last"
msgstr "letzte"
-#: ../../include/text.php:494
+#: ../../include/text.php:512
msgid "next"
msgstr "nächste"
-#: ../../include/text.php:505
+#: ../../include/text.php:523
msgid "older"
msgstr "älter"
-#: ../../include/text.php:507
+#: ../../include/text.php:525
msgid "newer"
msgstr "neuer"
-#: ../../include/text.php:904
+#: ../../include/text.php:947
msgid "No connections"
msgstr "Keine Verbindungen"
-#: ../../include/text.php:929
+#: ../../include/text.php:972
#, php-format
msgid "View all %s connections"
msgstr "Alle Verbindungen von %s anzeigen"
-#: ../../include/text.php:1074 ../../include/text.php:1079
+#: ../../include/text.php:1104 ../../include/text.php:1109
msgid "poke"
msgstr "anstupsen"
-#: ../../include/text.php:1074 ../../include/text.php:1079
-#: ../../include/conversation.php:243
-msgid "poked"
-msgstr "stupste"
-
-#: ../../include/text.php:1080
+#: ../../include/text.php:1110
msgid "ping"
msgstr "anpingen"
-#: ../../include/text.php:1080
+#: ../../include/text.php:1110
msgid "pinged"
msgstr "pingte"
-#: ../../include/text.php:1081
+#: ../../include/text.php:1111
msgid "prod"
msgstr "knuffen"
-#: ../../include/text.php:1081
+#: ../../include/text.php:1111
msgid "prodded"
msgstr "knuffte"
-#: ../../include/text.php:1082
+#: ../../include/text.php:1112
msgid "slap"
msgstr "ohrfeigen"
-#: ../../include/text.php:1082
+#: ../../include/text.php:1112
msgid "slapped"
msgstr "ohrfeigte"
-#: ../../include/text.php:1083
+#: ../../include/text.php:1113
msgid "finger"
msgstr "befummeln"
-#: ../../include/text.php:1083
+#: ../../include/text.php:1113
msgid "fingered"
msgstr "befummelte"
-#: ../../include/text.php:1084
+#: ../../include/text.php:1114
msgid "rebuff"
msgstr "eine Abfuhr erteilen"
-#: ../../include/text.php:1084
+#: ../../include/text.php:1114
msgid "rebuffed"
msgstr "zurückgewiesen"
-#: ../../include/text.php:1096
+#: ../../include/text.php:1126
msgid "happy"
msgstr "glücklich"
-#: ../../include/text.php:1097
+#: ../../include/text.php:1127
msgid "sad"
msgstr "traurig"
-#: ../../include/text.php:1098
+#: ../../include/text.php:1128
msgid "mellow"
msgstr "sanft"
-#: ../../include/text.php:1099
+#: ../../include/text.php:1129
msgid "tired"
msgstr "müde"
-#: ../../include/text.php:1100
+#: ../../include/text.php:1130
msgid "perky"
msgstr "frech"
-#: ../../include/text.php:1101
+#: ../../include/text.php:1131
msgid "angry"
msgstr "sauer"
-#: ../../include/text.php:1102
+#: ../../include/text.php:1132
msgid "stupefied"
msgstr "verblüfft"
-#: ../../include/text.php:1103
+#: ../../include/text.php:1133
msgid "puzzled"
msgstr "verwirrt"
-#: ../../include/text.php:1104
+#: ../../include/text.php:1134
msgid "interested"
msgstr "interessiert"
-#: ../../include/text.php:1105
+#: ../../include/text.php:1135
msgid "bitter"
msgstr "verbittert"
-#: ../../include/text.php:1106
+#: ../../include/text.php:1136
msgid "cheerful"
msgstr "fröhlich"
-#: ../../include/text.php:1107
+#: ../../include/text.php:1137
msgid "alive"
msgstr "lebendig"
-#: ../../include/text.php:1108
+#: ../../include/text.php:1138
msgid "annoyed"
msgstr "verärgert"
-#: ../../include/text.php:1109
+#: ../../include/text.php:1139
msgid "anxious"
msgstr "unruhig"
-#: ../../include/text.php:1110
+#: ../../include/text.php:1140
msgid "cranky"
msgstr "schrullig"
-#: ../../include/text.php:1111
+#: ../../include/text.php:1141
msgid "disturbed"
msgstr "verstört"
-#: ../../include/text.php:1112
+#: ../../include/text.php:1142
msgid "frustrated"
msgstr "frustriert"
-#: ../../include/text.php:1113
+#: ../../include/text.php:1143
msgid "depressed"
msgstr "deprimiert"
-#: ../../include/text.php:1114
+#: ../../include/text.php:1144
msgid "motivated"
msgstr "motiviert"
-#: ../../include/text.php:1115
+#: ../../include/text.php:1145
msgid "relaxed"
msgstr "entspannt"
-#: ../../include/text.php:1116
+#: ../../include/text.php:1146
msgid "surprised"
msgstr "überrascht"
-#: ../../include/text.php:1303 ../../include/js_strings.php:70
+#: ../../include/text.php:1320 ../../include/js_strings.php:70
msgid "Monday"
msgstr "Montag"
-#: ../../include/text.php:1303 ../../include/js_strings.php:71
+#: ../../include/text.php:1320 ../../include/js_strings.php:71
msgid "Tuesday"
msgstr "Dienstag"
-#: ../../include/text.php:1303 ../../include/js_strings.php:72
+#: ../../include/text.php:1320 ../../include/js_strings.php:72
msgid "Wednesday"
msgstr "Mittwoch"
-#: ../../include/text.php:1303 ../../include/js_strings.php:73
+#: ../../include/text.php:1320 ../../include/js_strings.php:73
msgid "Thursday"
msgstr "Donnerstag"
-#: ../../include/text.php:1303 ../../include/js_strings.php:74
+#: ../../include/text.php:1320 ../../include/js_strings.php:74
msgid "Friday"
msgstr "Freitag"
-#: ../../include/text.php:1303 ../../include/js_strings.php:75
+#: ../../include/text.php:1320 ../../include/js_strings.php:75
msgid "Saturday"
msgstr "Samstag"
-#: ../../include/text.php:1303 ../../include/js_strings.php:69
+#: ../../include/text.php:1320 ../../include/js_strings.php:69
msgid "Sunday"
msgstr "Sonntag"
-#: ../../include/text.php:1307 ../../include/js_strings.php:45
+#: ../../include/text.php:1324 ../../include/js_strings.php:45
msgid "January"
msgstr "Januar"
-#: ../../include/text.php:1307 ../../include/js_strings.php:46
+#: ../../include/text.php:1324 ../../include/js_strings.php:46
msgid "February"
msgstr "Februar"
-#: ../../include/text.php:1307 ../../include/js_strings.php:47
+#: ../../include/text.php:1324 ../../include/js_strings.php:47
msgid "March"
msgstr "März"
-#: ../../include/text.php:1307 ../../include/js_strings.php:48
+#: ../../include/text.php:1324 ../../include/js_strings.php:48
msgid "April"
msgstr "April"
-#: ../../include/text.php:1307
+#: ../../include/text.php:1324
msgid "May"
msgstr "Mai"
-#: ../../include/text.php:1307 ../../include/js_strings.php:50
+#: ../../include/text.php:1324 ../../include/js_strings.php:50
msgid "June"
msgstr "Juni"
-#: ../../include/text.php:1307 ../../include/js_strings.php:51
+#: ../../include/text.php:1324 ../../include/js_strings.php:51
msgid "July"
msgstr "Juli"
-#: ../../include/text.php:1307 ../../include/js_strings.php:52
+#: ../../include/text.php:1324 ../../include/js_strings.php:52
msgid "August"
msgstr "August"
-#: ../../include/text.php:1307 ../../include/js_strings.php:53
+#: ../../include/text.php:1324 ../../include/js_strings.php:53
msgid "September"
msgstr "September"
-#: ../../include/text.php:1307 ../../include/js_strings.php:54
+#: ../../include/text.php:1324 ../../include/js_strings.php:54
msgid "October"
msgstr "Oktober"
-#: ../../include/text.php:1307 ../../include/js_strings.php:55
+#: ../../include/text.php:1324 ../../include/js_strings.php:55
msgid "November"
msgstr "November"
-#: ../../include/text.php:1307 ../../include/js_strings.php:56
+#: ../../include/text.php:1324 ../../include/js_strings.php:56
msgid "December"
msgstr "Dezember"
-#: ../../include/text.php:1384 ../../include/text.php:1388
+#: ../../include/text.php:1388 ../../include/text.php:1392
msgid "Unknown Attachment"
msgstr "Unbekannter Anhang"
-#: ../../include/text.php:1390
+#: ../../include/text.php:1394 ../../include/feedutils.php:780
msgid "unknown"
msgstr "unbekannt"
-#: ../../include/text.php:1426
+#: ../../include/text.php:1430
msgid "remove category"
msgstr "Kategorie entfernen"
-#: ../../include/text.php:1503
+#: ../../include/text.php:1504
msgid "remove from file"
msgstr "aus der Datei entfernen"
-#: ../../include/text.php:1770 ../../include/language.php:367
+#: ../../include/text.php:1623 ../../include/message.php:12
+msgid "Download binary/encrypted content"
+msgstr "Binären/verschlüsselten Inhalt herunterladen"
+
+#: ../../include/text.php:1782 ../../include/language.php:367
msgid "default"
msgstr "Standard"
-#: ../../include/text.php:1778
+#: ../../include/text.php:1790
msgid "Page layout"
msgstr "Seiten-Layout"
-#: ../../include/text.php:1778
+#: ../../include/text.php:1790
msgid "You can create your own with the layouts tool"
msgstr "Mit dem Gestaltungswerkzeug kannst Du Deine eigenen Layouts erstellen"
-#: ../../include/text.php:1820
+#: ../../include/text.php:1801
+msgid "HTML"
+msgstr ""
+
+#: ../../include/text.php:1804
+msgid "Comanche Layout"
+msgstr ""
+
+#: ../../include/text.php:1809
+msgid "PHP"
+msgstr ""
+
+#: ../../include/text.php:1818
msgid "Page content type"
msgstr "Art des Seiteninhalts"
-#: ../../include/text.php:1953
+#: ../../include/text.php:1951
msgid "activity"
msgstr "Aktivität"
-#: ../../include/text.php:2267
+#: ../../include/text.php:2014
+msgid "a-z, 0-9, -, and _ only"
+msgstr ""
+
+#: ../../include/text.php:2285
msgid "Design Tools"
msgstr "Gestaltungswerkzeuge"
-#: ../../include/text.php:2273
+#: ../../include/text.php:2291
msgid "Pages"
msgstr "Seiten"
-#: ../../include/text.php:2295
+#: ../../include/text.php:2313
msgid "Import website..."
msgstr "Webseite importieren..."
-#: ../../include/text.php:2296
+#: ../../include/text.php:2314
msgid "Select folder to import"
msgstr "Ordner zum Importieren auswählen"
-#: ../../include/text.php:2297
+#: ../../include/text.php:2315
msgid "Import from a zipped folder:"
msgstr "Aus einem gezippten Ordner importieren:"
-#: ../../include/text.php:2298
+#: ../../include/text.php:2316
msgid "Import from cloud files:"
msgstr "Aus Cloud-Dateien importieren:"
-#: ../../include/text.php:2299
+#: ../../include/text.php:2317
msgid "/cloud/channel/path/to/folder"
msgstr "/Cloud/Kanal/Pfad/zum/Ordner"
-#: ../../include/text.php:2300
+#: ../../include/text.php:2318
msgid "Enter path to website files"
msgstr "Pfad zu Webseitendateien eingeben"
-#: ../../include/text.php:2301
+#: ../../include/text.php:2319
msgid "Select folder"
msgstr "Ordner auswählen"
-#: ../../include/text.php:2302
+#: ../../include/text.php:2320
msgid "Export website..."
msgstr "Webseite exportieren..."
-#: ../../include/text.php:2303
+#: ../../include/text.php:2321
msgid "Export to a zip file"
msgstr "In eine ZIP-Datei exportieren"
-#: ../../include/text.php:2304
+#: ../../include/text.php:2322
msgid "website.zip"
msgstr "website.zip"
-#: ../../include/text.php:2305
+#: ../../include/text.php:2323
msgid "Enter a name for the zip file."
msgstr "Geben Sie einen für die ZIP-Datei ein."
-#: ../../include/text.php:2306
+#: ../../include/text.php:2324
msgid "Export to cloud files"
msgstr "In Cloud-Dateien exportieren"
-#: ../../include/text.php:2307
+#: ../../include/text.php:2325
msgid "/path/to/export/folder"
msgstr "/Pfad/zum/exportierenden/Ordner"
-#: ../../include/text.php:2308
+#: ../../include/text.php:2326
msgid "Enter a path to a cloud files destination."
msgstr "Gib den Pfad zu einem Datei-Speicherort in der Cloud ein."
-#: ../../include/text.php:2309
+#: ../../include/text.php:2327
msgid "Specify folder"
msgstr "Ordner angeben"
-#: ../../include/bookmarks.php:35
-#, php-format
-msgid "%1$s's bookmarks"
-msgstr "%1$ss Lesezeichen"
-
-#: ../../include/wiki.php:545 ../../include/bbcode.php:552
-#: ../../include/bbcode.php:683
-msgid "Different viewers will see this text differently"
-msgstr "Verschiedene Betrachter werden diesen Text unterschiedlich sehen"
-
-#: ../../include/help.php:31
-msgid "Help:"
-msgstr "Hilfe:"
-
-#: ../../include/page_widgets.php:7
-msgid "New Page"
-msgstr "Neue Seite"
-
#: ../../include/contact_widgets.php:11
#, php-format
msgid "%d invitation available"
@@ -11878,27 +12136,51 @@ msgstr "Lade Freunde ein"
msgid "Advanced example: name=fred and country=iceland"
msgstr "Fortgeschrittenes Beispiel: name=fred and country=iceland"
-#: ../../include/contact_widgets.php:56 ../../include/contact_widgets.php:94
-#: ../../include/widgets.php:349 ../../include/widgets.php:468
-msgid "Everything"
-msgstr "Alles"
+#: ../../include/contact_widgets.php:166
+msgid "Common Connections"
+msgstr ""
-#: ../../include/contact_widgets.php:91 ../../include/taxonomy.php:188
-#: ../../include/taxonomy.php:270 ../../include/widgets.php:46
-#: ../../include/widgets.php:465
-msgid "Categories"
-msgstr "Kategorien"
+#: ../../include/contact_widgets.php:171
+#, php-format
+msgid "View all %d common connections"
+msgstr ""
-#: ../../include/contact_widgets.php:122
+#: ../../include/markdown.php:139 ../../include/bbcode.php:337
#, php-format
-msgid "%d connection in common"
-msgid_plural "%d connections in common"
-msgstr[0] "%d gemeinsame Verbindung"
-msgstr[1] "%d gemeinsame Verbindungen"
+msgid "%1$s wrote the following %2$s %3$s"
+msgstr "%1$s schrieb den folgenden %2$s %3$s"
+
+#: ../../include/follow.php:37
+msgid "Channel is blocked on this site."
+msgstr "Der Kanal ist auf dieser Seite blockiert "
+
+#: ../../include/follow.php:42
+msgid "Channel location missing."
+msgstr "Adresse des Kanals fehlt."
-#: ../../include/contact_widgets.php:127
-msgid "show more"
-msgstr "mehr zeigen"
+#: ../../include/follow.php:84
+msgid "Response from remote channel was incomplete."
+msgstr "Antwort des entfernten Kanals war unvollständig."
+
+#: ../../include/follow.php:101
+msgid "Channel was deleted and no longer exists."
+msgstr "Kanal wurde gelöscht und existiert nicht mehr."
+
+#: ../../include/follow.php:156
+msgid "Remote channel or protocol unavailable."
+msgstr ""
+
+#: ../../include/follow.php:179
+msgid "Channel discovery failed."
+msgstr "Kanalsuche fehlgeschlagen"
+
+#: ../../include/follow.php:191
+msgid "Protocol disabled."
+msgstr "Protokoll deaktiviert."
+
+#: ../../include/follow.php:202
+msgid "Cannot connect to yourself."
+msgstr "Du kannst Dich nicht mit Dir selbst verbinden."
#: ../../include/js_strings.php:5
msgid "Delete this item?"
@@ -12016,7 +12298,7 @@ msgstr "%d Tage"
#: ../../include/js_strings.php:38
msgid "about a month"
-msgstr "ungefähr ein Monat"
+msgstr "ungefähr einen Monat"
#: ../../include/js_strings.php:39
#, php-format
@@ -12147,1246 +12429,1237 @@ msgctxt "calendar"
msgid "All day"
msgstr "Ganztägig"
-#: ../../include/network.php:729
-msgid "view full size"
-msgstr "In Vollbildansicht anschauen"
+#: ../../include/message.php:40
+msgid "Unable to determine sender."
+msgstr "Kann Absender nicht bestimmen."
-#: ../../include/network.php:1978
-msgid "No Subject"
-msgstr "Kein Betreff"
+#: ../../include/message.php:79
+msgid "No recipient provided."
+msgstr "Kein Empfänger angegeben"
-#: ../../include/network.php:2234
-msgid "OStatus"
-msgstr "OStatus"
+#: ../../include/message.php:84
+msgid "[no subject]"
+msgstr "[no subject]"
-#: ../../include/network.php:2235
-msgid "GNU-Social"
-msgstr "GNU-Social"
+#: ../../include/message.php:214
+msgid "Stored post could not be verified."
+msgstr "Gespeicherter Beitrag konnten nicht überprüft werden."
-#: ../../include/network.php:2236
-msgid "RSS/Atom"
-msgstr "RSS/Atom"
+#: ../../include/activities.php:41
+msgid " and "
+msgstr "und"
-#: ../../include/network.php:2239
-msgid "Facebook"
-msgstr "Facebook"
+#: ../../include/activities.php:49
+msgid "public profile"
+msgstr "öffentliches Profil"
-#: ../../include/network.php:2240
-msgid "Zot"
-msgstr "Zot!"
+#: ../../include/activities.php:58
+#, php-format
+msgid "%1$s changed %2$s to &ldquo;%3$s&rdquo;"
+msgstr "%1$s hat %2$s auf &ldquo;%3$s&rdquo; geändert"
-#: ../../include/network.php:2241
-msgid "LinkedIn"
-msgstr "LinkedIn"
+#: ../../include/activities.php:59
+#, php-format
+msgid "Visit %1$s's %2$s"
+msgstr "Besuche %1$s's %2$s"
-#: ../../include/network.php:2242
-msgid "XMPP/IM"
-msgstr "XMPP/IM"
+#: ../../include/activities.php:62
+#, php-format
+msgid "%1$s has an updated %2$s, changing %3$s."
+msgstr "%1$s hat ein aktualisiertes %2$s, %3$s wurde verändert."
-#: ../../include/network.php:2243
-msgid "MySpace"
-msgstr "MySpace"
+#: ../../include/attach.php:250 ../../include/attach.php:339
+msgid "Item was not found."
+msgstr "Beitrag wurde nicht gefunden."
-#: ../../include/taxonomy.php:228 ../../include/taxonomy.php:249
-msgid "Tags"
-msgstr "Schlagwörter"
+#: ../../include/attach.php:505
+msgid "No source file."
+msgstr "Keine Quelldatei."
-#: ../../include/taxonomy.php:293
-msgid "Keywords"
-msgstr "Schlüsselwörter"
+#: ../../include/attach.php:527
+msgid "Cannot locate file to replace"
+msgstr "Kann Datei zum Ersetzen nicht finden"
-#: ../../include/taxonomy.php:314
-msgid "have"
-msgstr "habe"
+#: ../../include/attach.php:545
+msgid "Cannot locate file to revise/update"
+msgstr "Kann Datei zum Prüfen/Aktualisieren nicht finden"
-#: ../../include/taxonomy.php:314
-msgid "has"
-msgstr "hat"
+#: ../../include/attach.php:680
+#, php-format
+msgid "File exceeds size limit of %d"
+msgstr "Datei überschreitet das Größen-Limit von %d"
-#: ../../include/taxonomy.php:315
-msgid "want"
-msgstr "will"
+#: ../../include/attach.php:694
+#, php-format
+msgid "You have reached your limit of %1$.0f Mbytes attachment storage."
+msgstr "Die Größe Deiner Datei-Anhänge hat das Maximum von %1$.0f MByte erreicht."
-#: ../../include/taxonomy.php:315
-msgid "wants"
-msgstr "will"
+#: ../../include/attach.php:864
+msgid "File upload failed. Possible system limit or action terminated."
+msgstr "Datei-Upload fehlgeschlagen. Mögliche Systembegrenzung oder abgebrochener Prozess."
-#: ../../include/taxonomy.php:316
-msgid "likes"
-msgstr "gefällt"
+#: ../../include/attach.php:877
+msgid "Stored file could not be verified. Upload failed."
+msgstr "Gespeichert Datei konnte nicht verifiziert werden. Upload abgebrochen."
-#: ../../include/taxonomy.php:317
-msgid "dislikes"
-msgstr "missfällt"
+#: ../../include/attach.php:938 ../../include/attach.php:954
+msgid "Path not available."
+msgstr "Pfad nicht verfügbar."
-#: ../../include/import.php:30
-msgid ""
-"Cannot create a duplicate channel identifier on this system. Import failed."
-msgstr "Kann keinen doppelten Kanal-Identifikator auf diesem System erzeugen (Spitzname oder Hash schon belegt). Import fehlgeschlagen."
+#: ../../include/attach.php:1003 ../../include/attach.php:1168
+msgid "Empty pathname"
+msgstr "Leere Pfadangabe"
-#: ../../include/import.php:90
-msgid "Channel clone failed. Import failed."
-msgstr "Klonen des Kanals fehlgeschlagen. Import fehlgeschlagen."
+#: ../../include/attach.php:1029
+msgid "duplicate filename or path"
+msgstr "doppelter Dateiname oder Pfad"
-#: ../../include/import.php:1354
-msgid "Unable to import element \""
-msgstr "Element konnte nicht importiert werden."
+#: ../../include/attach.php:1054
+msgid "Path not found."
+msgstr "Pfad nicht gefunden."
-#: ../../include/security.php:117
-msgid "guest:"
-msgstr "Gast:"
+#: ../../include/attach.php:1122
+msgid "mkdir failed."
+msgstr "mkdir fehlgeschlagen."
-#: ../../include/security.php:535
+#: ../../include/attach.php:1126
+msgid "database storage failed."
+msgstr "Speichern in der Datenbank fehlgeschlagen."
+
+#: ../../include/attach.php:1174
+msgid "Empty path"
+msgstr "Leere Pfadangabe"
+
+#: ../../include/security.php:531
msgid ""
"The form security token was not correct. This probably happened because the "
"form has been opened for too long (>3 hours) before submitting it."
msgstr "Das Security-Token des Formulars war nicht korrekt. Das ist wahrscheinlich passiert, weil das Formular zu lange (>3 Stunden) offen war, bevor es abgeschickt wurde."
-#: ../../include/zot.php:662
-msgid "Invalid data packet"
-msgstr "Ungültiges Datenpaket"
-
-#: ../../include/zot.php:678
-msgid "Unable to verify channel signature"
-msgstr "Konnte die Signatur des Kanals nicht verifizieren"
-
-#: ../../include/zot.php:2320
-#, php-format
-msgid "Unable to verify site signature for %s"
-msgstr "Kann die Signatur der Seite von %s nicht verifizieren"
-
-#: ../../include/zot.php:3718
-msgid "invalid target signature"
-msgstr "Ungültige Signatur des Ziels"
-
-#: ../../include/items.php:837 ../../include/items.php:882
+#: ../../include/items.php:857 ../../include/items.php:909
msgid "(Unknown)"
msgstr "(Unbekannt)"
-#: ../../include/items.php:1080
+#: ../../include/items.php:1093
msgid "Visible to anybody on the internet."
msgstr "Für jeden im Internet sichtbar."
-#: ../../include/items.php:1082
+#: ../../include/items.php:1095
msgid "Visible to you only."
msgstr "Nur für Dich sichtbar."
-#: ../../include/items.php:1084
+#: ../../include/items.php:1097
msgid "Visible to anybody in this network."
msgstr "Für jedes $Projectname-Mitglied sichtbar."
-#: ../../include/items.php:1086
+#: ../../include/items.php:1099
msgid "Visible to anybody authenticated."
msgstr "Für jeden sichtbar, der angemeldet ist."
-#: ../../include/items.php:1088
+#: ../../include/items.php:1101
#, php-format
msgid "Visible to anybody on %s."
msgstr "Für jeden auf %s sichtbar."
-#: ../../include/items.php:1090
+#: ../../include/items.php:1103
msgid "Visible to all connections."
msgstr "Für alle Verbindungen sichtbar."
-#: ../../include/items.php:1092
+#: ../../include/items.php:1105
msgid "Visible to approved connections."
msgstr "Nur für akzeptierte Verbindungen sichtbar."
-#: ../../include/items.php:1094
+#: ../../include/items.php:1107
msgid "Visible to specific connections."
msgstr "Sichtbar für bestimmte Verbindungen."
-#: ../../include/items.php:3892
+#: ../../include/items.php:3957
msgid "Privacy group is empty."
msgstr "Gruppe ist leer."
-#: ../../include/items.php:3899
+#: ../../include/items.php:3964
#, php-format
msgid "Privacy group: %s"
msgstr "Gruppe: %s"
-#: ../../include/items.php:3911
+#: ../../include/items.php:3976
msgid "Connection not found."
msgstr "Die Verbindung wurde nicht gefunden."
-#: ../../include/items.php:4260
+#: ../../include/items.php:4327
msgid "profile photo"
msgstr "Profilfoto"
-#: ../../include/items.php:4456
+#: ../../include/items.php:4520
#, php-format
msgid "[Edited %s]"
msgstr "[%s wurde bearbeitet]"
-#: ../../include/items.php:4456
+#: ../../include/items.php:4520
msgctxt "edit_activity"
msgid "Post"
msgstr "Beitrag"
-#: ../../include/items.php:4456
+#: ../../include/items.php:4520
msgctxt "edit_activity"
msgid "Comment"
msgstr "Kommentar"
-#: ../../include/auth.php:148
-msgid "Logged out."
-msgstr "Ausgeloggt."
+#: ../../include/channel.php:34
+msgid "Unable to obtain identity information from database"
+msgstr "Kann keine Identitäts-Informationen aus Datenbank beziehen"
-#: ../../include/auth.php:275
-msgid "Failed authentication"
-msgstr "Authentifizierung fehlgeschlagen"
+#: ../../include/channel.php:69
+msgid "Empty name"
+msgstr "Namensfeld leer"
-#: ../../include/activities.php:41
-msgid " and "
-msgstr "und"
+#: ../../include/channel.php:72
+msgid "Name too long"
+msgstr "Name ist zu lang"
-#: ../../include/activities.php:49
-msgid "public profile"
-msgstr "öffentliches Profil"
+#: ../../include/channel.php:183
+msgid "No account identifier"
+msgstr "Keine Account-Kennung"
-#: ../../include/activities.php:58
-#, php-format
-msgid "%1$s changed %2$s to &ldquo;%3$s&rdquo;"
-msgstr "%1$s hat %2$s auf &ldquo;%3$s&rdquo; geändert"
+#: ../../include/channel.php:195
+msgid "Nickname is required."
+msgstr "Spitzname ist erforderlich."
-#: ../../include/activities.php:59
-#, php-format
-msgid "Visit %1$s's %2$s"
-msgstr "Besuche %1$s's %2$s"
+#: ../../include/channel.php:273
+msgid "Unable to retrieve created identity"
+msgstr "Kann die erstellte Identität nicht empfangen"
-#: ../../include/activities.php:62
-#, php-format
-msgid "%1$s has an updated %2$s, changing %3$s."
-msgstr "%1$s hat ein aktualisiertes %2$s, %3$s wurde verändert."
+#: ../../include/channel.php:359
+msgid "Default Profile"
+msgstr "Standard-Profil"
-#: ../../include/attach.php:248 ../../include/attach.php:336
-msgid "Item was not found."
-msgstr "Beitrag wurde nicht gefunden."
+#: ../../include/channel.php:512 ../../include/channel.php:601
+msgid "Unable to retrieve modified identity"
+msgstr "Geänderte Identität kann nicht empfangen werden"
-#: ../../include/attach.php:497
-msgid "No source file."
-msgstr "Keine Quelldatei."
+#: ../../include/channel.php:1263
+msgid "Create New Profile"
+msgstr "Neues Profil erstellen"
-#: ../../include/attach.php:519
-msgid "Cannot locate file to replace"
-msgstr "Kann Datei zum Ersetzen nicht finden"
+#: ../../include/channel.php:1283
+msgid "Visible to everybody"
+msgstr "Für jeden sichtbar"
-#: ../../include/attach.php:537
-msgid "Cannot locate file to revise/update"
-msgstr "Kann Datei zum Prüfen/Aktualisieren nicht finden"
+#: ../../include/channel.php:1356 ../../include/channel.php:1475
+msgid "Gender:"
+msgstr "Geschlecht:"
-#: ../../include/attach.php:668
-#, php-format
-msgid "File exceeds size limit of %d"
-msgstr "Datei überschreitet das Größen-Limit von %d"
+#: ../../include/channel.php:1358 ../../include/channel.php:1530
+msgid "Homepage:"
+msgstr "Homepage:"
+
+#: ../../include/channel.php:1359
+msgid "Online Now"
+msgstr "gerade online"
+
+#: ../../include/channel.php:1434
+msgid "Trans"
+msgstr ""
-#: ../../include/attach.php:682
+#: ../../include/channel.php:1480
+msgid "Like this channel"
+msgstr "Dieser Kanal gefällt mir"
+
+#: ../../include/channel.php:1504
+msgid "j F, Y"
+msgstr "j. F Y"
+
+#: ../../include/channel.php:1505
+msgid "j F"
+msgstr "j. F"
+
+#: ../../include/channel.php:1512
+msgid "Birthday:"
+msgstr "Geburtstag:"
+
+#: ../../include/channel.php:1525
#, php-format
-msgid "You have reached your limit of %1$.0f Mbytes attachment storage."
-msgstr "Die Größe Deiner Datei-Anhänge hat das Maximum von %1$.0f MByte erreicht."
+msgid "for %1$d %2$s"
+msgstr "seit %1$d %2$s"
-#: ../../include/attach.php:852
-msgid "File upload failed. Possible system limit or action terminated."
-msgstr "Datei-Upload fehlgeschlagen. Mögliche Systembegrenzung oder abgebrochener Prozess."
+#: ../../include/channel.php:1528
+msgid "Sexual Preference:"
+msgstr "Sexuelle Orientierung:"
-#: ../../include/attach.php:865
-msgid "Stored file could not be verified. Upload failed."
-msgstr "Gespeichert Datei konnte nicht verifiziert werden. Upload abgebrochen."
+#: ../../include/channel.php:1534
+msgid "Tags:"
+msgstr "Schlagworte:"
-#: ../../include/attach.php:920 ../../include/attach.php:936
-msgid "Path not available."
-msgstr "Pfad nicht verfügbar."
+#: ../../include/channel.php:1536
+msgid "Political Views:"
+msgstr "Politische Ansichten:"
-#: ../../include/attach.php:982 ../../include/attach.php:1140
-msgid "Empty pathname"
-msgstr "Leere Pfadangabe"
+#: ../../include/channel.php:1538
+msgid "Religion:"
+msgstr "Religion:"
-#: ../../include/attach.php:1008
-msgid "duplicate filename or path"
-msgstr "doppelter Dateiname oder Pfad"
+#: ../../include/channel.php:1542
+msgid "Hobbies/Interests:"
+msgstr "Hobbys/Interessen:"
-#: ../../include/attach.php:1030
-msgid "Path not found."
-msgstr "Pfad nicht gefunden."
+#: ../../include/channel.php:1544
+msgid "Likes:"
+msgstr "Gefällt:"
-#: ../../include/attach.php:1094
-msgid "mkdir failed."
-msgstr "mkdir fehlgeschlagen."
+#: ../../include/channel.php:1546
+msgid "Dislikes:"
+msgstr "Gefällt nicht:"
-#: ../../include/attach.php:1098
-msgid "database storage failed."
-msgstr "Speichern in der Datenbank fehlgeschlagen."
+#: ../../include/channel.php:1548
+msgid "Contact information and Social Networks:"
+msgstr "Kontaktinformation und soziale Netzwerke:"
-#: ../../include/attach.php:1146
-msgid "Empty path"
-msgstr "Leere Pfadangabe"
+#: ../../include/channel.php:1550
+msgid "My other channels:"
+msgstr "Meine anderen Kanäle:"
+
+#: ../../include/channel.php:1552
+msgid "Musical interests:"
+msgstr "Musikalische Interessen:"
+
+#: ../../include/channel.php:1554
+msgid "Books, literature:"
+msgstr "Bücher, Literatur:"
+
+#: ../../include/channel.php:1556
+msgid "Television:"
+msgstr "Fernsehen:"
+
+#: ../../include/channel.php:1558
+msgid "Film/dance/culture/entertainment:"
+msgstr "Film/Tanz/Kultur/Unterhaltung:"
+
+#: ../../include/channel.php:1560
+msgid "Love/Romance:"
+msgstr "Liebe/Romantik:"
+
+#: ../../include/channel.php:1562
+msgid "Work/employment:"
+msgstr "Arbeit/Anstellung:"
+
+#: ../../include/channel.php:1564
+msgid "School/education:"
+msgstr "Schule/Ausbildung:"
+
+#: ../../include/channel.php:1587
+msgid "Like this thing"
+msgstr "Gefällt mir"
#: ../../include/event.php:22 ../../include/event.php:69
-#: ../../include/bb2diaspora.php:498
msgid "l F d, Y \\@ g:i A"
msgstr "l, d. F Y, H:i"
#: ../../include/event.php:30 ../../include/event.php:73
-#: ../../include/bb2diaspora.php:504
msgid "Starts:"
msgstr "Beginnt:"
#: ../../include/event.php:40 ../../include/event.php:77
-#: ../../include/bb2diaspora.php:512
msgid "Finishes:"
msgstr "Endet:"
-#: ../../include/event.php:824
+#: ../../include/event.php:1008
msgid "This event has been added to your calendar."
msgstr "Dieser Termin wurde zu Deinem Kalender hinzugefügt"
-#: ../../include/event.php:1024
+#: ../../include/event.php:1208
msgid "Not specified"
msgstr "Keine Angabe"
-#: ../../include/event.php:1025
+#: ../../include/event.php:1209
msgid "Needs Action"
msgstr "Aktion erforderlich"
-#: ../../include/event.php:1026
+#: ../../include/event.php:1210
msgid "Completed"
msgstr "Abgeschlossen"
-#: ../../include/event.php:1027
+#: ../../include/event.php:1211
msgid "In Process"
msgstr "In Bearbeitung"
-#: ../../include/event.php:1028
+#: ../../include/event.php:1212
msgid "Cancelled"
msgstr "gestrichen"
-#: ../../include/follow.php:27
-msgid "Channel is blocked on this site."
-msgstr "Der Kanal ist auf dieser Seite blockiert "
+#: ../../include/event.php:1292 ../../include/connections.php:684
+msgid "Home, Voice"
+msgstr "Zuhause, Sprache"
-#: ../../include/follow.php:32
-msgid "Channel location missing."
-msgstr "Adresse des Kanals fehlt."
+#: ../../include/event.php:1293 ../../include/connections.php:685
+msgid "Home, Fax"
+msgstr "Zuhause, Fax"
-#: ../../include/follow.php:80
-msgid "Response from remote channel was incomplete."
-msgstr "Antwort des entfernten Kanals war unvollständig."
+#: ../../include/event.php:1295 ../../include/connections.php:687
+msgid "Work, Voice"
+msgstr "Arbeit, Sprache"
-#: ../../include/follow.php:97
-msgid "Channel was deleted and no longer exists."
-msgstr "Kanal wurde gelöscht und existiert nicht mehr."
+#: ../../include/event.php:1296 ../../include/connections.php:688
+msgid "Work, Fax"
+msgstr "Arbeit, Fax"
-#: ../../include/follow.php:147 ../../include/follow.php:183
-msgid "Protocol disabled."
-msgstr "Protokoll deaktiviert."
+#: ../../include/network.php:752
+msgid "view full size"
+msgstr "In Vollbildansicht anschauen"
-#: ../../include/follow.php:171
-msgid "Channel discovery failed."
-msgstr "Kanalsuche fehlgeschlagen"
+#: ../../include/network.php:1700 ../../include/network.php:1701
+msgid "Friendica"
+msgstr "Friendica"
-#: ../../include/follow.php:210
-msgid "Cannot connect to yourself."
-msgstr "Du kannst Dich nicht mit Dir selbst verbinden."
+#: ../../include/network.php:1702
+msgid "OStatus"
+msgstr "OStatus"
-#: ../../include/group.php:26
-msgid ""
-"A deleted group with this name was revived. Existing item permissions "
-"<strong>may</strong> apply to this group and any future members. If this is "
-"not what you intended, please create another group with a different name."
-msgstr "Es hat früher schon einmal eine Gruppe mit diesem Namen existiert, die gelöscht wurde. Es <strong>könnten</strong> von damals noch Elemente (Beiträge, Dateien etc.) vorhanden sein, die allen jetzigen und zukünftigen Mitgliedern dieser Gruppe den Zugriff erlauben. Wenn das nicht Deine Absicht ist, erstelle bitte eine neue Gruppe mit einem anderen Namen."
+#: ../../include/network.php:1703
+msgid "GNU-Social"
+msgstr "GNU-Social"
-#: ../../include/group.php:248
-msgid "Add new connections to this privacy group"
-msgstr "Neue Verbindung zu dieser Gruppe hinzufügen"
+#: ../../include/network.php:1704
+msgid "RSS/Atom"
+msgstr "RSS/Atom"
-#: ../../include/group.php:289
-msgid "edit"
-msgstr "Bearbeiten"
+#: ../../include/network.php:1707
+msgid "Diaspora"
+msgstr "Diaspora"
-#: ../../include/group.php:312
-msgid "Edit group"
-msgstr "Gruppe ändern"
+#: ../../include/network.php:1708
+msgid "Facebook"
+msgstr "Facebook"
-#: ../../include/group.php:313
-msgid "Add privacy group"
-msgstr "Gruppe hinzufügen"
+#: ../../include/network.php:1709
+msgid "Zot"
+msgstr "Zot!"
-#: ../../include/group.php:314
-msgid "Channels not in any privacy group"
-msgstr "Kanäle, die in keiner Gruppe sind"
+#: ../../include/network.php:1710
+msgid "LinkedIn"
+msgstr "LinkedIn"
-#: ../../include/group.php:316 ../../include/widgets.php:284
-msgid "add"
-msgstr "hinzufügen"
+#: ../../include/network.php:1711
+msgid "XMPP/IM"
+msgstr "XMPP/IM"
+
+#: ../../include/network.php:1712
+msgid "MySpace"
+msgstr "MySpace"
#: ../../include/language.php:380
msgid "Select an alternate language"
msgstr "Wähle eine alternative Sprache"
-#: ../../include/photos.php:115
-#, php-format
-msgid "Image exceeds website size limit of %lu bytes"
-msgstr "Bild überschreitet das Webseitenlimit von %lu Bytes"
-
-#: ../../include/photos.php:122
-msgid "Image file is empty."
-msgstr "Bilddatei ist leer."
-
-#: ../../include/photos.php:260
-msgid "Photo storage failed."
-msgstr "Fotospeicherung fehlgeschlagen."
-
-#: ../../include/photos.php:300
-msgid "a new photo"
-msgstr "ein neues Foto"
-
-#: ../../include/photos.php:304
-#, php-format
-msgctxt "photo_upload"
-msgid "%1$s posted %2$s to %3$s"
-msgstr "%1$s hat %2$s auf %3$s veröffentlicht"
-
-#: ../../include/photos.php:507 ../../include/conversation.php:1695
-msgid "Photo Albums"
-msgstr "Fotoalben"
-
-#: ../../include/photos.php:511
-msgid "Upload New Photos"
-msgstr "Neue Fotos hochladen"
+#: ../../include/acl_selectors.php:208
+msgid "Who can see this?"
+msgstr "Wer kann das sehen?"
-#: ../../include/widgets.php:103
-msgid "System"
-msgstr "System"
+#: ../../include/acl_selectors.php:209
+msgid "Custom selection"
+msgstr "Benutzerdefinierte Auswahl"
-#: ../../include/widgets.php:106
-msgid "New App"
-msgstr "Neue App"
+#: ../../include/acl_selectors.php:210
+msgid ""
+"Select \"Show\" to allow viewing. \"Don't show\" lets you override and limit"
+" the scope of \"Show\"."
+msgstr "Wähle \"Anzeigen\", um Betrachtung zuzulassen. \"Nicht anzeigen\" überstimmt und limitiert den Aktionsradius von \"Anzeigen\" für Ausnahmen."
-#: ../../include/widgets.php:154
-msgid "Suggestions"
-msgstr "Vorschläge"
+#: ../../include/acl_selectors.php:211
+msgid "Show"
+msgstr "Anzeigen"
-#: ../../include/widgets.php:155
-msgid "See more..."
-msgstr "Mehr anzeigen …"
+#: ../../include/acl_selectors.php:212
+msgid "Don't show"
+msgstr "Nicht anzeigen"
-#: ../../include/widgets.php:175
+#: ../../include/acl_selectors.php:245
#, php-format
-msgid "You have %1$.0f of %2$.0f allowed connections."
-msgstr "Du bist %1$.0f von maximal %2$.0f erlaubten Verbindungen eingegangen."
-
-#: ../../include/widgets.php:181
-msgid "Add New Connection"
-msgstr "Neue Verbindung hinzufügen"
-
-#: ../../include/widgets.php:182
-msgid "Enter channel address"
-msgstr "Adresse des Kanals eingeben"
-
-#: ../../include/widgets.php:183
-msgid "Examples: bob@example.com, https://example.com/barbara"
-msgstr "Beispiele: bob@beispiel.com, http://beispiel.com/barbara"
-
-#: ../../include/widgets.php:199
-msgid "Notes"
-msgstr "Notizen"
-
-#: ../../include/widgets.php:275
-msgid "Remove term"
-msgstr "Eintrag löschen"
-
-#: ../../include/widgets.php:390
-msgid "Archives"
-msgstr "Archive"
-
-#: ../../include/widgets.php:552
-msgid "Refresh"
-msgstr "Aktualisieren"
+msgid ""
+"Post permissions %s cannot be changed %s after a post is shared.</br />These"
+" permissions set who is allowed to view the post."
+msgstr "Beitragsberechtigungen %s können nicht geändert werden %s, nachdem der Beitrag gesendet wurde.<br />Diese Berechtigungen bestimmen, wer den Beitrag sehen kann."
-#: ../../include/widgets.php:592
-msgid "Account settings"
-msgstr "Konto-Einstellungen"
+#: ../../include/dba/dba_driver.php:190
+#, php-format
+msgid "Cannot locate DNS info for database server '%s'"
+msgstr "Kann die DNS-Informationen für den Datenbank-Server '%s' nicht finden"
-#: ../../include/widgets.php:598
-msgid "Channel settings"
-msgstr "Kanal-Einstellungen"
+#: ../../include/bbcode.php:194 ../../include/bbcode.php:1102
+#: ../../include/bbcode.php:1105 ../../include/bbcode.php:1110
+#: ../../include/bbcode.php:1113 ../../include/bbcode.php:1116
+#: ../../include/bbcode.php:1119 ../../include/bbcode.php:1124
+#: ../../include/bbcode.php:1127 ../../include/bbcode.php:1132
+#: ../../include/bbcode.php:1135 ../../include/bbcode.php:1138
+#: ../../include/bbcode.php:1141
+msgid "Image/photo"
+msgstr "Bild/Foto"
-#: ../../include/widgets.php:607
-msgid "Additional features"
-msgstr "Zusätzliche Funktionen"
+#: ../../include/bbcode.php:233 ../../include/bbcode.php:1152
+msgid "Encrypted content"
+msgstr "Verschlüsselter Inhalt"
-#: ../../include/widgets.php:614
-msgid "Feature/Addon settings"
-msgstr "Plugin-Einstellungen"
+#: ../../include/bbcode.php:249
+#, php-format
+msgid "Install %s element: "
+msgstr "Element %s installieren: "
-#: ../../include/widgets.php:620
-msgid "Display settings"
-msgstr "Anzeige-Einstellungen"
+#: ../../include/bbcode.php:253
+#, php-format
+msgid ""
+"This post contains an installable %s element, however you lack permissions "
+"to install it on this site."
+msgstr "Dieser Beitrag beinhaltet ein installierbares %s Element, aber Du hast nicht die nötigen Rechte, um es auf diesem Hub zu installieren."
-#: ../../include/widgets.php:627
-msgid "Manage locations"
-msgstr "Klon-Adressen verwalten"
+#: ../../include/bbcode.php:331
+msgid "card"
+msgstr "Karte"
-#: ../../include/widgets.php:634
-msgid "Export channel"
-msgstr "Kanal exportieren"
+#: ../../include/bbcode.php:414 ../../include/bbcode.php:422
+msgid "Click to open/close"
+msgstr "Klicke zum Öffnen/Schließen"
-#: ../../include/widgets.php:640
-msgid "Connected apps"
-msgstr "Verbundene Apps"
+#: ../../include/bbcode.php:422
+msgid "spoiler"
+msgstr "Spoiler"
-#: ../../include/widgets.php:664
-msgid "Premium Channel Settings"
-msgstr "Premium-Kanal-Einstellungen"
+#: ../../include/bbcode.php:1090
+msgid "$1 wrote:"
+msgstr "$1 schrieb:"
-#: ../../include/widgets.php:693
-msgid "Private Mail Menu"
-msgstr "Private Nachrichten"
+#: ../../include/oembed.php:328
+msgid " by "
+msgstr "von"
-#: ../../include/widgets.php:695
-msgid "Combined View"
-msgstr "Kombinierte Anzeige"
+#: ../../include/oembed.php:329
+msgid " on "
+msgstr "am"
-#: ../../include/widgets.php:727 ../../include/widgets.php:739
-msgid "Conversations"
-msgstr "Konversationen"
+#: ../../include/oembed.php:358
+msgid "Embedded content"
+msgstr "Eingebetteter Inhalt"
-#: ../../include/widgets.php:731
-msgid "Received Messages"
-msgstr "Erhaltene Nachrichten"
+#: ../../include/oembed.php:367
+msgid "Embedding disabled"
+msgstr "Einbetten deaktiviert"
-#: ../../include/widgets.php:735
-msgid "Sent Messages"
-msgstr "Gesendete Nachrichten"
+#: ../../include/zid.php:305
+#, php-format
+msgid "OpenWebAuth: %1$s welcomes %2$s"
+msgstr ""
-#: ../../include/widgets.php:749
-msgid "No messages."
-msgstr "Keine Nachrichten."
+#: ../../include/features.php:54
+msgid "General Features"
+msgstr "Allgemeine Funktionen"
-#: ../../include/widgets.php:767
-msgid "Delete conversation"
-msgstr "Unterhaltung löschen"
+#: ../../include/features.php:59
+msgid "Multiple Profiles"
+msgstr "Mehrfachprofile"
-#: ../../include/widgets.php:793
-msgid "Events Tools"
-msgstr "Kalenderwerkzeuge"
+#: ../../include/features.php:60
+msgid "Ability to create multiple profiles"
+msgstr "Ermöglicht das Anlegen mehrerer Profile pro Kanal"
-#: ../../include/widgets.php:794
-msgid "Export Calendar"
-msgstr "Kalender exportieren"
+#: ../../include/features.php:68
+msgid "Advanced Profiles"
+msgstr "Erweiterte Profile"
-#: ../../include/widgets.php:795
-msgid "Import Calendar"
-msgstr "Kalender importieren"
+#: ../../include/features.php:69
+msgid "Additional profile sections and selections"
+msgstr "Stellt zusätzliche Bereiche und Felder im Profil zur Verfügung"
-#: ../../include/widgets.php:883 ../../include/conversation.php:1722
-#: ../../include/conversation.php:1725
-msgid "Chatrooms"
-msgstr "Chaträume"
+#: ../../include/features.php:77
+msgid "Profile Import/Export"
+msgstr "Profil-Import/Export"
-#: ../../include/widgets.php:887
-msgid "Overview"
-msgstr "Übersicht"
+#: ../../include/features.php:78
+msgid "Save and load profile details across sites/channels"
+msgstr "Ermöglicht das Speichern von Profilen, um sie in einen anderen Kanal zu importieren"
-#: ../../include/widgets.php:894
-msgid "Chat Members"
-msgstr "Chatmitglieder"
+#: ../../include/features.php:86
+msgid "Web Pages"
+msgstr "Webseiten"
-#: ../../include/widgets.php:960
-msgid "Wiki List"
-msgstr "Wikiliste"
+#: ../../include/features.php:87
+msgid "Provide managed web pages on your channel"
+msgstr "Ermöglicht das Erstellen von Webseiten in Deinem Kanal"
-#: ../../include/widgets.php:968
-msgid "Create new wiki"
-msgstr "Neues Wiki erstellen"
+#: ../../include/features.php:96
+msgid "Provide a wiki for your channel"
+msgstr "Stelle ein Wiki in Deinem Kanal zur Verfügung"
-#: ../../include/widgets.php:978
-msgid "Send notification"
-msgstr "Benachrichtigung senden"
+#: ../../include/features.php:113
+msgid "Private Notes"
+msgstr "Private Notizen"
-#: ../../include/widgets.php:1014
-msgid "Wiki Pages"
-msgstr "Wikiseiten"
+#: ../../include/features.php:114
+msgid "Enables a tool to store notes and reminders (note: not encrypted)"
+msgstr "Aktiviert ein Werkzeug mit dem Notizen und Erinnerungen gespeichert werden können (Hinweis: nicht verschlüsselt)"
-#: ../../include/widgets.php:1019
-msgid "Add new page"
-msgstr "Neue Seite hinzufügen"
+#: ../../include/features.php:123
+msgid "Create personal planning cards"
+msgstr "Erstelle persönliche (Notiz-)Karten zur Planung/Koordination oder ähnlichen Zwecken"
-#: ../../include/widgets.php:1020
-msgid "Page name"
-msgstr "Seitenname"
+#: ../../include/features.php:131
+msgid "Navigation Channel Select"
+msgstr "Kanal-Auswahl in der Navigationsleiste"
-#: ../../include/widgets.php:1052
-msgid "Bookmarked Chatrooms"
-msgstr "Gespeicherte Chatrooms"
+#: ../../include/features.php:132
+msgid "Change channels directly from within the navigation dropdown menu"
+msgstr "Ermöglicht den direkten Wechsel zu anderen Kanälen über das Navigationsmenü"
-#: ../../include/widgets.php:1083
-msgid "Suggested Chatrooms"
-msgstr "Chatraum-Vorschläge"
+#: ../../include/features.php:140
+msgid "Photo Location"
+msgstr "Aufnahmeort"
-#: ../../include/widgets.php:1228 ../../include/widgets.php:1340
-msgid "photo/image"
-msgstr "Foto/Bild"
+#: ../../include/features.php:141
+msgid "If location data is available on uploaded photos, link this to a map."
+msgstr "Verlinkt den Aufnahmeort von Fotos (falls verfügbar) auf einer Karte"
-#: ../../include/widgets.php:1283
-msgid "Click to show more"
-msgstr "Klick, um mehr anzuzeigen"
+#: ../../include/features.php:149
+msgid "Access Controlled Chatrooms"
+msgstr "Zugriffskontrollierte Chaträume"
-#: ../../include/widgets.php:1434
-msgid "Rating Tools"
-msgstr "Bewertungswerkzeuge"
+#: ../../include/features.php:150
+msgid "Provide chatrooms and chat services with access control."
+msgstr "Bieten Sie Chaträume und Chatdienste mit Zugriffskontrolle an."
-#: ../../include/widgets.php:1438 ../../include/widgets.php:1440
-msgid "Rate Me"
-msgstr "Bewerte mich"
+#: ../../include/features.php:159
+msgid "Provide alternate connection permission roles."
+msgstr "Stelle benutzerdefinierte Berechtigungsrollen für Verbindungen zur Verfügung."
-#: ../../include/widgets.php:1443
-msgid "View Ratings"
-msgstr "Bewertungen ansehen"
+#: ../../include/features.php:167
+msgid "Smart Birthdays"
+msgstr "Smarte Geburtstage"
-#: ../../include/widgets.php:1536
-msgid "Forums"
-msgstr "Foren"
+#: ../../include/features.php:168
+msgid ""
+"Make birthday events timezone aware in case your friends are scattered "
+"across the planet."
+msgstr "Stellt für Geburtstage einen Zeitzonenbezug her, falls deine Freunde über den ganzen Planeten verstreut sind."
-#: ../../include/widgets.php:1565
-msgid "Tasks"
-msgstr "Aufgaben"
+#: ../../include/features.php:176
+msgid "Event Timezone Selection"
+msgstr "Termin-Zeitzonenauswahl"
-#: ../../include/widgets.php:1576
-msgid "Documentation"
-msgstr "Dokumentation"
+#: ../../include/features.php:177
+msgid "Allow event creation in timezones other than your own."
+msgstr "Ermögliche das Erstellen von Terminen in anderen Zeitzonen als Deiner eigenen."
-#: ../../include/widgets.php:1632 ../../include/widgets.php:1670
-msgid "Member registrations waiting for confirmation"
-msgstr "Nutzer-Anmeldungen, die auf Bestätigung warten"
+#: ../../include/features.php:185
+msgid "Advanced Directory Search"
+msgstr "Erweiterte Verzeichnissuche"
-#: ../../include/widgets.php:1638
-msgid "Inspect queue"
-msgstr "Warteschlange kontrollieren"
+#: ../../include/features.php:186
+msgid "Allows creation of complex directory search queries"
+msgstr "Ermöglicht die Erstellung komplexer Verzeichnis-Suchabfragen"
-#: ../../include/widgets.php:1640
-msgid "DB updates"
-msgstr "DB-Aktualisierungen"
+#: ../../include/features.php:194
+msgid "Advanced Theme and Layout Settings"
+msgstr "Erweiterte Design- und Layout-Einstellungen"
-#: ../../include/widgets.php:1666
-msgid "Plugin Features"
-msgstr "Plug-In Funktionen"
+#: ../../include/features.php:195
+msgid "Allows fine tuning of themes and page layouts"
+msgstr "Erlaubt die Feineinstellung von Designs und Seitenlayouts"
-#: ../../include/acl_selectors.php:198
-msgid "Who can see this?"
-msgstr "Wer kann das sehen?"
+#: ../../include/features.php:205
+msgid "Post Composition Features"
+msgstr "Nachbearbeitungsfunktionen"
-#: ../../include/acl_selectors.php:199
-msgid "Custom selection"
-msgstr "Benutzerdefinierte Auswahl"
+#: ../../include/features.php:209
+msgid "Large Photos"
+msgstr "Große Fotos"
-#: ../../include/acl_selectors.php:200
+#: ../../include/features.php:210
msgid ""
-"Select \"Show\" to allow viewing. \"Don't show\" lets you override and limit"
-" the scope of \"Show\"."
-msgstr "Wähle \"Anzeigen\", um Betrachtung zuzulassen. \"Nicht anzeigen\" überstimmt und limitiert den Aktionsradius von \"Anzeigen\" für Ausnahmen."
+"Include large (1024px) photo thumbnails in posts. If not enabled, use small "
+"(640px) photo thumbnails"
+msgstr "Große Vorschaubilder (1024px) in Beiträgen anzeigen. Falls nicht aktiviert, werden kleine Vorschaubilder (640px) verwendet."
-#: ../../include/acl_selectors.php:201
-msgid "Show"
-msgstr "Anzeigen"
+#: ../../include/features.php:219
+msgid "Automatically import channel content from other channels or feeds"
+msgstr "Ermöglicht den automatischen Import von Inhalten für diesen Kanal von anderen Kanälen oder Feeds"
-#: ../../include/acl_selectors.php:202
-msgid "Don't show"
-msgstr "Nicht anzeigen"
+#: ../../include/features.php:227
+msgid "Even More Encryption"
+msgstr "Noch mehr Verschlüsselung"
-#: ../../include/acl_selectors.php:235
-#, php-format
+#: ../../include/features.php:228
msgid ""
-"Post permissions %s cannot be changed %s after a post is shared.</br />These"
-" permissions set who is allowed to view the post."
-msgstr "Beitragsberechtigungen %s können nicht geändert werden %s, nachdem der Beitrag gesendet wurde.<br />Diese Berechtigungen bestimmen, wer den Beitrag sehen kann."
-
-#: ../../include/oembed.php:312
-msgid " by "
-msgstr "von"
-
-#: ../../include/oembed.php:313
-msgid " on "
-msgstr "am"
-
-#: ../../include/oembed.php:342
-msgid "Embedded content"
-msgstr "Eingebetteter Inhalt"
-
-#: ../../include/oembed.php:351
-msgid "Embedding disabled"
-msgstr "Einbetten deaktiviert"
+"Allow optional encryption of content end-to-end with a shared secret key"
+msgstr "Ermöglicht optional die zusätzliche Verschlüsselung von Inhalten (Ende-zu-Ende mit geteiltem Schlüssel)"
-#: ../../include/bb2diaspora.php:403
-msgid "Attachments:"
-msgstr "Anhänge:"
+#: ../../include/features.php:236
+msgid "Enable Voting Tools"
+msgstr "Umfragewerkzeuge aktivieren"
-#: ../../include/bb2diaspora.php:500
-msgid "$Projectname event notification:"
-msgstr "$Projectname-Terminbenachrichtigung:"
+#: ../../include/features.php:237
+msgid "Provide a class of post which others can vote on"
+msgstr "Aktiviert die Umfragewerkzeuge, um anderen die Möglichkeit zu geben, einem Beitrag zuzustimmen, ihn abzulehnen oder sich zu enthalten. (Muss im Beitrag selbst noch aktiviert werden.)"
-#: ../../include/permissions.php:35
-msgid "Can view my normal stream and posts"
-msgstr "Kann meine normalen Beiträge sehen"
+#: ../../include/features.php:245
+msgid "Disable Comments"
+msgstr "Kommentare deaktivieren"
-#: ../../include/permissions.php:39
-msgid "Can view my webpages"
-msgstr "Kann meine Webseiten sehen"
+#: ../../include/features.php:246
+msgid "Provide the option to disable comments for a post"
+msgstr "Ermöglicht, die Kommentarfunktion für einzelne Beiträge abzuschalten"
-#: ../../include/permissions.php:43
-msgid "Can post on my channel page (\"wall\")"
-msgstr "Kann auf meiner Kanal-Seite (\"wall\") Beiträge veröffentlichen"
+#: ../../include/features.php:254
+msgid "Delayed Posting"
+msgstr "Verzögertes Senden"
-#: ../../include/permissions.php:46
-msgid "Can like/dislike stuff"
-msgstr "Kann andere Elemente mögen/nicht mögen"
+#: ../../include/features.php:255
+msgid "Allow posts to be published at a later date"
+msgstr "Ermöglicht es, Beiträge zu einem späteren Zeitpunkt zu veröffentlichen"
-#: ../../include/permissions.php:46
-msgid "Profiles and things other than posts/comments"
-msgstr "Profile und alles außer Beiträge und Kommentare"
+#: ../../include/features.php:263
+msgid "Content Expiration"
+msgstr "Verfall von Inhalten"
-#: ../../include/permissions.php:48
-msgid "Can forward to all my channel contacts via post @mentions"
-msgstr "Kann an alle meine Kontakte via @-Erwähnung Nachrichten weiterleiten"
+#: ../../include/features.php:264
+msgid "Remove posts/comments and/or private messages at a future time"
+msgstr "Ermöglicht das automatische Löschen von Beiträgen, Kommentaren und/oder privaten Nachrichten zu einem zukünftigen Datum."
-#: ../../include/permissions.php:48
-msgid "Advanced - useful for creating group forum channels"
-msgstr "Fortgeschritten - sinnvoll, um Gruppen-Kanäle/-Foren zu erstellen"
+#: ../../include/features.php:272
+msgid "Suppress Duplicate Posts/Comments"
+msgstr "Doppelte Beiträge unterdrücken"
-#: ../../include/permissions.php:49
-msgid "Can chat with me (when available)"
-msgstr "Kann mit mir chatten (wenn verfügbar)"
+#: ../../include/features.php:273
+msgid ""
+"Prevent posts with identical content to be published with less than two "
+"minutes in between submissions."
+msgstr "Verhindert, dass innerhalb von zwei Minuten Beiträge mit identischem Inhalt veröffentlicht werden."
-#: ../../include/permissions.php:50
-msgid "Can write to my file storage and photos"
-msgstr "Kann in meine Datei- und Bilderordner schreiben"
+#: ../../include/features.php:284
+msgid "Network and Stream Filtering"
+msgstr "Netzwerk- und Stream-Filter"
-#: ../../include/permissions.php:51
-msgid "Can edit my webpages"
-msgstr "Kann meine Webseiten bearbeiten"
+#: ../../include/features.php:288
+msgid "Search by Date"
+msgstr "Suche nach Datum"
-#: ../../include/permissions.php:53
-msgid "Somewhat advanced - very useful in open communities"
-msgstr "Etwas fortgeschritten – sehr nützlich in offenen Gemeinschaften"
+#: ../../include/features.php:289
+msgid "Ability to select posts by date ranges"
+msgstr "Möglichkeit, Beiträge nach Zeiträumen auszuwählen"
-#: ../../include/permissions.php:55
-msgid "Can administer my channel resources"
-msgstr "Kann meine Kanäle administrieren"
+#: ../../include/features.php:297 ../../include/group.php:332
+msgid "Privacy Groups"
+msgstr "Gruppen"
-#: ../../include/permissions.php:55
-msgid ""
-"Extremely advanced. Leave this alone unless you know what you are doing"
-msgstr "Sehr fortgeschritten. Bearbeite das nur, wenn Du genau weißt, was Du tust"
+#: ../../include/features.php:298
+msgid "Enable management and selection of privacy groups"
+msgstr "Auswahl und Verwaltung von Gruppen für Kanäle aktivieren"
-#: ../../include/conversation.php:204
-#, php-format
-msgid "%1$s is now connected with %2$s"
-msgstr "%1$s ist jetzt mit %2$s verbunden"
+#: ../../include/features.php:307
+msgid "Save search terms for re-use"
+msgstr "Ermöglicht das Abspeichern von Suchbegriffen zur Wiederverwendung"
-#: ../../include/conversation.php:239
-#, php-format
-msgid "%1$s poked %2$s"
-msgstr "%1$s stupste %2$s an"
+#: ../../include/features.php:315
+msgid "Network Personal Tab"
+msgstr "Persönlicher Netzwerkreiter"
-#: ../../include/conversation.php:710
-#, php-format
-msgid "View %s's profile @ %s"
-msgstr "%ss Profil auf %s ansehen"
+#: ../../include/features.php:316
+msgid "Enable tab to display only Network posts that you've interacted on"
+msgstr "Aktiviert einen Reiter in der Grid-Ansicht, der nur Netzwerk-Beiträge anzeigt, mit denen Du interagiert hast"
-#: ../../include/conversation.php:729
-msgid "Categories:"
-msgstr "Kategorien:"
+#: ../../include/features.php:324
+msgid "Network New Tab"
+msgstr "Netzwerkreiter Neu"
-#: ../../include/conversation.php:730
-msgid "Filed under:"
-msgstr "Gespeichert unter:"
+#: ../../include/features.php:325
+msgid "Enable tab to display all new Network activity"
+msgstr "Aktiviert einen Reiter in der Grid-Ansicht, der alle neuen Netzwerkaktivitäten anzeigt"
-#: ../../include/conversation.php:755
-msgid "View in context"
-msgstr "Im Zusammenhang anschauen"
+#: ../../include/features.php:333
+msgid "Affinity Tool"
+msgstr "Beziehungs-Tool"
-#: ../../include/conversation.php:865
-msgid "remove"
-msgstr "lösche"
+#: ../../include/features.php:334
+msgid "Filter stream activity by depth of relationships"
+msgstr "Aktiviert ein Werkzeug in der Grid-Ansicht, das den Stream nach Grad der Beziehung filtern kann"
-#: ../../include/conversation.php:870
-msgid "Delete Selected Items"
-msgstr "Lösche die ausgewählten Elemente"
+#: ../../include/features.php:343
+msgid "Show friend and connection suggestions"
+msgstr "Freund- und Verbindungsvorschläge anzeigen"
-#: ../../include/conversation.php:963
-msgid "View Source"
-msgstr "Quelle anzeigen"
+#: ../../include/features.php:351
+msgid "Connection Filtering"
+msgstr "Filter für Verbindungen"
-#: ../../include/conversation.php:964
-msgid "Follow Thread"
-msgstr "Unterhaltung folgen"
+#: ../../include/features.php:352
+msgid "Filter incoming posts from connections based on keywords/content"
+msgstr "Ermöglicht die Filterung eingehender Beiträge anhand von Schlüsselwörtern (muss an der Verbindung konfiguriert werden)"
-#: ../../include/conversation.php:965
-msgid "Unfollow Thread"
-msgstr "Unterhaltung nicht mehr folgen"
+#: ../../include/features.php:364
+msgid "Post/Comment Tools"
+msgstr "Beitrag-/Kommentar-Tools"
-#: ../../include/conversation.php:970
-msgid "Activity/Posts"
-msgstr "Aktivitäten/Beiträge"
+#: ../../include/features.php:368
+msgid "Community Tagging"
+msgstr "Gemeinschaftliches Verschlagworten"
-#: ../../include/conversation.php:972
-msgid "Edit Connection"
-msgstr "Verbindung bearbeiten"
+#: ../../include/features.php:369
+msgid "Ability to tag existing posts"
+msgstr "Ermöglicht das Verschlagworten existierender Beiträge"
-#: ../../include/conversation.php:973
-msgid "Message"
-msgstr "Nachricht"
+#: ../../include/features.php:377
+msgid "Post Categories"
+msgstr "Beitrags-Kategorien"
-#: ../../include/conversation.php:1093
-#, php-format
-msgid "%s likes this."
-msgstr "%s gefällt das."
+#: ../../include/features.php:378
+msgid "Add categories to your posts"
+msgstr "Aktiviert Kategorien für Beiträge"
-#: ../../include/conversation.php:1093
-#, php-format
-msgid "%s doesn't like this."
-msgstr "%s gefällt das nicht."
+#: ../../include/features.php:386
+msgid "Emoji Reactions"
+msgstr "Emoji Reaktionen"
-#: ../../include/conversation.php:1097
-#, php-format
-msgid "<span %1$s>%2$d people</span> like this."
-msgid_plural "<span %1$s>%2$d people</span> like this."
-msgstr[0] "<span %1$s>%2$d Person</span> gefällt das."
-msgstr[1] "<span %1$s>%2$d Leuten</span> gefällt das."
+#: ../../include/features.php:387
+msgid "Add emoji reaction ability to posts"
+msgstr "Aktiviert Emoji-Reaktionen für Beiträge"
-#: ../../include/conversation.php:1099
-#, php-format
-msgid "<span %1$s>%2$d people</span> don't like this."
-msgid_plural "<span %1$s>%2$d people</span> don't like this."
-msgstr[0] "<span %1$s>%2$d Person</span> gefällt das nicht."
-msgstr[1] "<span %1$s>%2$d Leuten</span> gefällt das nicht."
+#: ../../include/features.php:396
+msgid "Ability to file posts under folders"
+msgstr "Möglichkeit, Beiträge in Verzeichnissen zu sammeln"
-#: ../../include/conversation.php:1105
-msgid "and"
-msgstr "und"
+#: ../../include/features.php:404
+msgid "Dislike Posts"
+msgstr "Gefällt-mir-nicht-Beiträge"
-#: ../../include/conversation.php:1108
-#, php-format
-msgid ", and %d other people"
-msgid_plural ", and %d other people"
-msgstr[0] ""
-msgstr[1] ", und %d andere"
+#: ../../include/features.php:405
+msgid "Ability to dislike posts/comments"
+msgstr "Aktiviert die „Gefällt mir nicht“-Schaltfläche"
-#: ../../include/conversation.php:1109
-#, php-format
-msgid "%s like this."
-msgstr "%s gefällt das."
+#: ../../include/features.php:413
+msgid "Star Posts"
+msgstr "Beiträge mit Sternchen versehen"
-#: ../../include/conversation.php:1109
-#, php-format
-msgid "%s don't like this."
-msgstr "%s gefällt das nicht."
+#: ../../include/features.php:414
+msgid "Ability to mark special posts with a star indicator"
+msgstr "Ermöglicht die lokale Markierung spezieller Beiträge mit einem Sternchen-Symbol"
-#: ../../include/conversation.php:1152
-msgid "Set your location"
-msgstr "Standort"
+#: ../../include/features.php:422
+msgid "Tag Cloud"
+msgstr "Schlagwort-Wolke"
-#: ../../include/conversation.php:1153
-msgid "Clear browser location"
-msgstr "Browser-Standort löschen"
+#: ../../include/features.php:423
+msgid "Provide a personal tag cloud on your channel page"
+msgstr "Aktiviert die Anzeige einer Schlagwort-Wolke (Tag Cloud) auf Deiner Kanal-Seite"
-#: ../../include/conversation.php:1201
-msgid "Tag term:"
-msgstr "Schlagwort:"
+#: ../../include/features.php:434
+msgid "Premium Channel"
+msgstr "Premium-Kanal"
-#: ../../include/conversation.php:1202
-msgid "Where are you right now?"
-msgstr "Wo bist Du jetzt grade?"
+#: ../../include/features.php:435
+msgid ""
+"Allows you to set restrictions and terms on those that connect with your "
+"channel"
+msgstr "Ermöglicht es, Einschränkungen und Bedingungen für Verbindungen dieses Kanals festzulegen"
-#: ../../include/conversation.php:1211
-msgid "Comments enabled"
-msgstr "Kommentare aktiviert"
+#: ../../include/taxonomy.php:325 ../../include/taxonomy.php:346
+msgid "Tags"
+msgstr "Schlagwörter"
-#: ../../include/conversation.php:1212
-msgid "Comments disabled"
-msgstr "Kommentare deaktiviert"
+#: ../../include/taxonomy.php:410
+msgid "Keywords"
+msgstr "Schlüsselwörter"
-#: ../../include/conversation.php:1250
-msgid "Page link name"
-msgstr "Link zur Seite"
+#: ../../include/taxonomy.php:431
+msgid "have"
+msgstr "habe"
-#: ../../include/conversation.php:1253
-msgid "Post as"
-msgstr "Veröffentlichen als"
+#: ../../include/taxonomy.php:431
+msgid "has"
+msgstr "hat"
-#: ../../include/conversation.php:1267
-msgid "Toggle voting"
-msgstr "Umfragewerkzeug aktivieren"
+#: ../../include/taxonomy.php:432
+msgid "want"
+msgstr "will"
-#: ../../include/conversation.php:1270
-msgid "Disable comments"
-msgstr "Kommentare deaktivieren"
+#: ../../include/taxonomy.php:432
+msgid "wants"
+msgstr "will"
-#: ../../include/conversation.php:1271
-msgid "Toggle comments"
-msgstr "Kommentare umschalten"
+#: ../../include/taxonomy.php:433
+msgid "likes"
+msgstr "gefällt"
-#: ../../include/conversation.php:1279
-msgid "Categories (optional, comma-separated list)"
-msgstr "Kategorien (optional, kommagetrennte Liste)"
+#: ../../include/taxonomy.php:434
+msgid "dislikes"
+msgstr "missfällt"
-#: ../../include/conversation.php:1302
-msgid "Other networks and post services"
-msgstr "Andere Netzwerke und Platformen"
+#: ../../include/account.php:35
+msgid "Not a valid email address"
+msgstr "Ungültige E-Mail-Adresse"
-#: ../../include/conversation.php:1308
-msgid "Set publish date"
-msgstr "Veröffentlichungsdatum festlegen"
+#: ../../include/account.php:37
+msgid "Your email domain is not among those allowed on this site"
+msgstr "Deine E-Mail-Adresse ist auf dieser Seite nicht erlaubt"
-#: ../../include/conversation.php:1562
-msgid "Discover"
-msgstr "Entdecken"
+#: ../../include/account.php:43
+msgid "Your email address is already registered at this site."
+msgstr "Deine E-Mail-Adresse ist auf dieser Seite bereits registriert."
-#: ../../include/conversation.php:1565
-msgid "Imported public streams"
-msgstr "Importierte öffentliche Beiträge"
+#: ../../include/account.php:75
+msgid "An invitation is required."
+msgstr "Eine Einladung wird benötigt."
-#: ../../include/conversation.php:1570
-msgid "Commented Order"
-msgstr "Neueste Kommentare"
+#: ../../include/account.php:79
+msgid "Invitation could not be verified."
+msgstr "Die Einladung konnte nicht bestätigt werden."
-#: ../../include/conversation.php:1573
-msgid "Sort by Comment Date"
-msgstr "Nach Kommentardatum sortiert"
+#: ../../include/account.php:157
+msgid "Please enter the required information."
+msgstr "Bitte gib die benötigten Informationen ein."
-#: ../../include/conversation.php:1577
-msgid "Posted Order"
-msgstr "Neueste Beiträge"
+#: ../../include/account.php:224
+msgid "Failed to store account information."
+msgstr "Speichern der Nutzerkontodaten fehlgeschlagen."
-#: ../../include/conversation.php:1580
-msgid "Sort by Post Date"
-msgstr "Nach Beitragsdatum sortiert"
+#: ../../include/account.php:291
+#, php-format
+msgid "Registration confirmation for %s"
+msgstr "Registrierungsbestätigung für %s"
-#: ../../include/conversation.php:1588
-msgid "Posts that mention or involve you"
-msgstr "Beiträge mit Beteiligung Deinerseits"
+#: ../../include/account.php:360
+#, php-format
+msgid "Registration request at %s"
+msgstr "Registrierungsanfrage auf %s"
-#: ../../include/conversation.php:1597
-msgid "Activity Stream - by date"
-msgstr "Activity Stream – nach Datum sortiert"
+#: ../../include/account.php:382
+msgid "your registration password"
+msgstr "Dein Registrierungspasswort"
-#: ../../include/conversation.php:1603
-msgid "Starred"
-msgstr "Markiert"
+#: ../../include/account.php:388 ../../include/account.php:450
+#, php-format
+msgid "Registration details for %s"
+msgstr "Registrierungsdetails für %s"
-#: ../../include/conversation.php:1606
-msgid "Favourite Posts"
-msgstr "Markierte Beiträge"
+#: ../../include/account.php:461
+msgid "Account approved."
+msgstr "Nutzerkonto bestätigt."
-#: ../../include/conversation.php:1613
-msgid "Spam"
-msgstr "Spam"
+#: ../../include/account.php:501
+#, php-format
+msgid "Registration revoked for %s"
+msgstr "Registrierung für %s wurde widerrufen"
-#: ../../include/conversation.php:1616
-msgid "Posts flagged as SPAM"
-msgstr "Nachrichten, die als SPAM markiert wurden"
+#: ../../include/account.php:780 ../../include/account.php:782
+msgid "Click here to upgrade."
+msgstr "Klicke hier, um das Upgrade durchzuführen."
-#: ../../include/conversation.php:1674
-msgid "Status Messages and Posts"
-msgstr "Statusnachrichten und Beiträge"
+#: ../../include/account.php:788
+msgid "This action exceeds the limits set by your subscription plan."
+msgstr "Diese Aktion überschreitet die Grenzen Ihres Abonnements."
-#: ../../include/conversation.php:1683
-msgid "About"
-msgstr "Über"
+#: ../../include/account.php:793
+msgid "This action is not available under your subscription plan."
+msgstr "Diese Aktion ist in Ihrem Abonnement nicht verfügbar."
-#: ../../include/conversation.php:1686
-msgid "Profile Details"
-msgstr "Profil-Details"
+#: ../../include/datetime.php:147
+msgid "Birthday"
+msgstr "Geburtstag"
-#: ../../include/conversation.php:1702
-msgid "Files and Storage"
-msgstr "Dateien und Speicher"
+#: ../../include/datetime.php:149
+msgid "Age: "
+msgstr "Alter:"
-#: ../../include/conversation.php:1738
-msgid "Saved Bookmarks"
-msgstr "Gespeicherte Lesezeichen"
+#: ../../include/datetime.php:151
+msgid "YYYY-MM-DD or MM-DD"
+msgstr "JJJJ-MM-TT oder MM-TT"
-#: ../../include/conversation.php:1748
-msgid "Manage Webpages"
-msgstr "Webseiten verwalten"
+#: ../../include/datetime.php:292
+msgid "less than a second ago"
+msgstr "Vor weniger als einer Sekunde"
-#: ../../include/conversation.php:1813
-msgctxt "noun"
-msgid "Attending"
-msgid_plural "Attending"
-msgstr[0] "Zusage"
-msgstr[1] "Zusagen"
+#: ../../include/datetime.php:310
+#, php-format
+msgctxt "e.g. 22 hours ago, 1 minute ago"
+msgid "%1$d %2$s ago"
+msgstr "vor %1$d %2$s"
-#: ../../include/conversation.php:1816
-msgctxt "noun"
-msgid "Not Attending"
-msgid_plural "Not Attending"
-msgstr[0] "Absage"
-msgstr[1] "Absagen"
+#: ../../include/datetime.php:321
+msgctxt "relative_date"
+msgid "year"
+msgid_plural "years"
+msgstr[0] "Jahr"
+msgstr[1] "Jahre"
-#: ../../include/conversation.php:1819
-msgctxt "noun"
-msgid "Undecided"
-msgid_plural "Undecided"
-msgstr[0] " Unentschlossen"
-msgstr[1] "Unentschlossene"
+#: ../../include/datetime.php:324
+msgctxt "relative_date"
+msgid "month"
+msgid_plural "months"
+msgstr[0] "Monat"
+msgstr[1] "Monate"
-#: ../../include/conversation.php:1822
-msgctxt "noun"
-msgid "Agree"
-msgid_plural "Agrees"
-msgstr[0] "Zustimmung"
-msgstr[1] "Zustimmungen"
+#: ../../include/datetime.php:327
+msgctxt "relative_date"
+msgid "week"
+msgid_plural "weeks"
+msgstr[0] "Woche"
+msgstr[1] "Wochen"
-#: ../../include/conversation.php:1825
-msgctxt "noun"
-msgid "Disagree"
-msgid_plural "Disagrees"
-msgstr[0] "Ablehnung"
-msgstr[1] "Ablehnungen"
+#: ../../include/datetime.php:330
+msgctxt "relative_date"
+msgid "day"
+msgid_plural "days"
+msgstr[0] "Tag"
+msgstr[1] "Tage"
-#: ../../include/conversation.php:1828
-msgctxt "noun"
-msgid "Abstain"
-msgid_plural "Abstains"
-msgstr[0] "Enthaltung"
-msgstr[1] "Enthaltungen"
+#: ../../include/datetime.php:333
+msgctxt "relative_date"
+msgid "hour"
+msgid_plural "hours"
+msgstr[0] "Stunde"
+msgstr[1] "Stunden"
-#: ../../include/bbcode.php:134 ../../include/bbcode.php:962
-#: ../../include/bbcode.php:965 ../../include/bbcode.php:970
-#: ../../include/bbcode.php:973 ../../include/bbcode.php:976
-#: ../../include/bbcode.php:979 ../../include/bbcode.php:984
-#: ../../include/bbcode.php:987 ../../include/bbcode.php:992
-#: ../../include/bbcode.php:995 ../../include/bbcode.php:998
-#: ../../include/bbcode.php:1001
-msgid "Image/photo"
-msgstr "Bild/Foto"
+#: ../../include/datetime.php:336
+msgctxt "relative_date"
+msgid "minute"
+msgid_plural "minutes"
+msgstr[0] "Minute"
+msgstr[1] "Minuten"
-#: ../../include/bbcode.php:173 ../../include/bbcode.php:1012
-msgid "Encrypted content"
-msgstr "Verschlüsselter Inhalt"
+#: ../../include/datetime.php:339
+msgctxt "relative_date"
+msgid "second"
+msgid_plural "seconds"
+msgstr[0] "Sekunde"
+msgstr[1] "Sekunden"
-#: ../../include/bbcode.php:189
+#: ../../include/datetime.php:576
#, php-format
-msgid "Install %s element: "
-msgstr "Element %s installieren: "
+msgid "%1$s's birthday"
+msgstr "%1$ss Geburtstag"
-#: ../../include/bbcode.php:193
+#: ../../include/datetime.php:577
#, php-format
-msgid ""
-"This post contains an installable %s element, however you lack permissions "
-"to install it on this site."
-msgstr "Dieser Beitrag beinhaltet ein installierbares %s Element, aber Du hast nicht die nötigen Rechte, um es auf diesem Hub zu installieren."
+msgid "Happy Birthday %1$s"
+msgstr "Alles Gute zum Geburtstag, %1$s"
-#: ../../include/bbcode.php:272
-#, php-format
-msgid "%1$s wrote the following %2$s %3$s"
-msgstr "%1$s schrieb den folgenden %2$s %3$s"
+#: ../../include/nav.php:91
+msgid "Remote authentication"
+msgstr "Über Konto auf anderem Server einloggen"
-#: ../../include/bbcode.php:349 ../../include/bbcode.php:357
-msgid "Click to open/close"
-msgstr "Klicke zum Öffnen/Schließen"
+#: ../../include/nav.php:91
+msgid "Click to authenticate to your home hub"
+msgstr "Klicke, um Dich über Deinen Heimat-Server zu authentifizieren"
-#: ../../include/bbcode.php:357
-msgid "spoiler"
-msgstr "Spoiler"
+#: ../../include/nav.php:98
+msgid "Network Activity"
+msgstr "Netzwerk-Aktivitäten"
-#: ../../include/bbcode.php:950
-msgid "$1 wrote:"
-msgstr "$1 schrieb:"
+#: ../../include/nav.php:100
+msgid "Mark all activity notifications seen"
+msgstr "Alle Benachrichtigungen als gesehen markieren"
-#: ../../view/theme/redbasic/php/config.php:9
-msgid "Focus (Hubzilla default)"
-msgstr "Focus (Voreinstellung für Hubzilla)"
+#: ../../include/nav.php:102
+msgid "Channel home"
+msgstr "Mein Kanal"
-#: ../../view/theme/redbasic/php/config.php:110
-msgid "Theme settings"
-msgstr "Theme-Einstellungen"
+#: ../../include/nav.php:103
+msgid "View your channel home"
+msgstr "Zeige Deine Kanalseite an"
-#: ../../view/theme/redbasic/php/config.php:111
-msgid "Narrow navbar"
-msgstr "Schmale Navigationsleiste"
+#: ../../include/nav.php:104
+msgid "Mark all channel notifications seen"
+msgstr "Markiere alle Kanal-Benachrichtigungen als angesehen"
-#: ../../view/theme/redbasic/php/config.php:112
-msgid "Navigation bar background color"
-msgstr "Hintergrundfarbe der Navigationsleiste"
+#: ../../include/nav.php:109
+msgid "Registrations"
+msgstr "Registrierungen"
-#: ../../view/theme/redbasic/php/config.php:113
-msgid "Navigation bar gradient top color"
-msgstr "Farbverlauf der Navigationsleiste: Farbe oben"
+#: ../../include/nav.php:112
+msgid "Notifications"
+msgstr "Benachrichtigungen"
-#: ../../view/theme/redbasic/php/config.php:114
-msgid "Navigation bar gradient bottom color"
-msgstr "Farbverlauf der Navigationsleiste: Farbe unten"
+#: ../../include/nav.php:113
+msgid "View all notifications"
+msgstr "Alle Benachrichtigungen ansehen"
-#: ../../view/theme/redbasic/php/config.php:115
-msgid "Navigation active button gradient top color"
-msgstr "Navigations-Button aktiv: Farbe für Farbverlauf oben"
+#: ../../include/nav.php:114
+msgid "Mark all system notifications seen"
+msgstr "Markiere alle System-Benachrichtigungen als gesehen"
-#: ../../view/theme/redbasic/php/config.php:116
-msgid "Navigation active button gradient bottom color"
-msgstr "Navigations-Button aktiv: Farbe für Farbverlauf unten"
+#: ../../include/nav.php:116
+msgid "Private mail"
+msgstr "Persönliche Mail"
-#: ../../view/theme/redbasic/php/config.php:117
-msgid "Navigation bar border color "
-msgstr "Farbe für den Rand der Navigationsleiste"
+#: ../../include/nav.php:117
+msgid "View your private messages"
+msgstr "Zeige Deine persönlichen Nachrichten an"
-#: ../../view/theme/redbasic/php/config.php:118
-msgid "Navigation bar icon color "
-msgstr "Farbe für die Icons der Navigationsleiste"
+#: ../../include/nav.php:118
+msgid "Mark all private messages seen"
+msgstr "Markiere alle persönlichen Nachrichten als gesehen"
-#: ../../view/theme/redbasic/php/config.php:119
-msgid "Navigation bar active icon color "
-msgstr "Farbe für aktive Icons der Navigationsleiste"
+#: ../../include/nav.php:124
+msgid "Event Calendar"
+msgstr "Terminkalender"
-#: ../../view/theme/redbasic/php/config.php:120
-msgid "link color"
-msgstr "Farbe für Links"
+#: ../../include/nav.php:129 ../../include/nav.php:215
+msgid "Manage Your Channels"
+msgstr "Verwalte Deine Kanäle"
-#: ../../view/theme/redbasic/php/config.php:121
-msgid "Set font-color for banner"
-msgstr "Farbe der Schrift des Banners"
+#: ../../include/nav.php:132 ../../include/nav.php:217
+msgid "Account/Channel Settings"
+msgstr "Konto-/Kanal-Einstellungen"
-#: ../../view/theme/redbasic/php/config.php:122
-msgid "Set the background color"
-msgstr "Hintergrundfarbe"
+#: ../../include/nav.php:138 ../../include/nav.php:167
+msgid "End this session"
+msgstr "Beende diese Sitzung"
-#: ../../view/theme/redbasic/php/config.php:123
-msgid "Set the background image"
-msgstr "Hintergrundbild"
+#: ../../include/nav.php:141
+msgid "Your profile page"
+msgstr "Deine Profilseite"
-#: ../../view/theme/redbasic/php/config.php:124
-msgid "Set the background color of items"
-msgstr "Hintergrundfarbe für Beiträge"
+#: ../../include/nav.php:144
+msgid "Manage/Edit profiles"
+msgstr "Profile verwalten"
-#: ../../view/theme/redbasic/php/config.php:125
-msgid "Set the background color of comments"
-msgstr "Hintergrundfarbe für Kommentare"
+#: ../../include/nav.php:146
+msgid "Edit your profile"
+msgstr "Profil bearbeiten"
-#: ../../view/theme/redbasic/php/config.php:126
-msgid "Set the border color of comments"
-msgstr "Farbe des Randes von Kommentaren"
+#: ../../include/nav.php:153 ../../include/nav.php:157
+msgid "Sign in"
+msgstr "Anmelden"
-#: ../../view/theme/redbasic/php/config.php:127
-msgid "Set the indent for comments"
-msgstr "Einzugsbreite für Kommentare"
+#: ../../include/nav.php:182
+msgid "Take me home"
+msgstr "Bringe mich nach Hause (eigener Kanal)"
-#: ../../view/theme/redbasic/php/config.php:128
-msgid "Set the basic color for item icons"
-msgstr "Grundfarbe für Beitrags-Icons"
+#: ../../include/nav.php:184
+msgid "Log me out of this site"
+msgstr "Logge mich von dieser Seite aus"
-#: ../../view/theme/redbasic/php/config.php:129
-msgid "Set the hover color for item icons"
-msgstr "Farbe für Beitrags-Icons unter dem Mauszeiger"
+#: ../../include/nav.php:189
+msgid "Create an account"
+msgstr "Erzeuge ein Konto"
-#: ../../view/theme/redbasic/php/config.php:130
-msgid "Set font-size for the entire application"
-msgstr "Schriftgröße für die gesamte Anwendung"
+#: ../../include/nav.php:201
+msgid "Help and documentation"
+msgstr "Hilfe und Dokumentation"
-#: ../../view/theme/redbasic/php/config.php:130
-msgid "Example: 14px"
-msgstr "Beispiel: 14px"
+#: ../../include/nav.php:204
+msgid "Search site @name, #tag, ?docs, content"
+msgstr "Hub durchsuchen: @Name. #Schlagwort, ?Dokumentation, Inhalt"
-#: ../../view/theme/redbasic/php/config.php:131
-msgid "Set font-size for posts and comments"
-msgstr "Schriftgröße für Beiträge und Kommentare"
+#: ../../include/nav.php:224
+msgid "Site Setup and Configuration"
+msgstr "Seiten-Einrichtung und -Konfiguration"
-#: ../../view/theme/redbasic/php/config.php:132
-msgid "Set font-color for posts and comments"
-msgstr "Schriftfarbe für Beiträge und Kommentare"
+#: ../../include/nav.php:311
+msgid "@name, #tag, ?doc, content"
+msgstr "@Name, #Schlagwort, ?Dokumentation, Inhalt"
-#: ../../view/theme/redbasic/php/config.php:133
-msgid "Set radius of corners"
-msgstr "Ecken-Radius"
+#: ../../include/nav.php:312
+msgid "Please wait..."
+msgstr "Bitte warten..."
-#: ../../view/theme/redbasic/php/config.php:134
-msgid "Set shadow depth of photos"
-msgstr "Schattentiefe von Fotos"
+#: ../../include/nav.php:318
+msgid "Add Apps"
+msgstr "Apps hinzufügen"
-#: ../../view/theme/redbasic/php/config.php:135
-msgid "Set maximum width of content region in pixel"
-msgstr "Maximalbreite des Inhaltsbereichs in Pixel festlegen"
+#: ../../include/nav.php:319
+msgid "Arrange Apps"
+msgstr "Apps anordnen"
-#: ../../view/theme/redbasic/php/config.php:135
-msgid "Leave empty for default width"
-msgstr "Leer lassen für Standardbreite"
+#: ../../include/nav.php:320
+msgid "Toggle System Apps"
+msgstr "System-Apps umschalten"
-#: ../../view/theme/redbasic/php/config.php:136
-msgid "Left align page content"
-msgstr "Seiteninhalt linksbündig anzeigen"
+#: ../../include/photos.php:123
+#, php-format
+msgid "Image exceeds website size limit of %lu bytes"
+msgstr "Bild überschreitet das Webseitenlimit von %lu Bytes"
-#: ../../view/theme/redbasic/php/config.php:137
-msgid "Set minimum opacity of nav bar - to hide it"
-msgstr "Mindest-Deckkraft der Navigationsleiste ( - versteckt sie)"
+#: ../../include/photos.php:130
+msgid "Image file is empty."
+msgstr "Bilddatei ist leer."
-#: ../../view/theme/redbasic/php/config.php:138
-msgid "Set size of conversation author photo"
-msgstr "Größe der Avatare von Themenstartern"
+#: ../../include/photos.php:268
+msgid "Photo storage failed."
+msgstr "Fotospeicherung fehlgeschlagen."
-#: ../../view/theme/redbasic/php/config.php:139
-msgid "Set size of followup author photos"
-msgstr "Größe der Avatare von Kommentatoren"
+#: ../../include/photos.php:308
+msgid "a new photo"
+msgstr "ein neues Foto"
-#: ../../boot.php:1175
+#: ../../include/photos.php:312
#, php-format
-msgctxt "opensearch"
-msgid "Search %1$s (%2$s)"
-msgstr "Suche %1$s (%2$s)"
+msgctxt "photo_upload"
+msgid "%1$s posted %2$s to %3$s"
+msgstr "%1$s hat %2$s auf %3$s veröffentlicht"
-#: ../../boot.php:1175
-msgctxt "opensearch"
-msgid "$Projectname"
-msgstr "$Projectname"
+#: ../../include/photos.php:605
+msgid "Upload New Photos"
+msgstr "Neue Fotos hochladen"
-#: ../../boot.php:1493
-#, php-format
-msgid "Update %s failed. See error logs."
-msgstr "Aktualisierung %s fehlgeschlagen. Details in den Fehlerprotokollen."
+#: ../../include/zot.php:654
+msgid "Invalid data packet"
+msgstr "Ungültiges Datenpaket"
+
+#: ../../include/zot.php:681
+msgid "Unable to verify channel signature"
+msgstr "Konnte die Signatur des Kanals nicht verifizieren"
-#: ../../boot.php:1496
+#: ../../include/zot.php:2368
#, php-format
-msgid "Update Error at %s"
-msgstr "Aktualisierungsfehler auf %s"
+msgid "Unable to verify site signature for %s"
+msgstr "Kann die Signatur der Seite von %s nicht verifizieren"
-#: ../../boot.php:1700
+#: ../../include/group.php:26
msgid ""
-"Create an account to access services and applications within the Hubzilla"
-msgstr "Erstelle ein Konto, um Anwendungen und Dienste innerhalb von Hubzilla nutzen zu können."
+"A deleted group with this name was revived. Existing item permissions "
+"<strong>may</strong> apply to this group and any future members. If this is "
+"not what you intended, please create another group with a different name."
+msgstr "Es hat früher schon einmal eine Gruppe mit diesem Namen existiert, die gelöscht wurde. Es <strong>könnten</strong> von damals noch Elemente (Beiträge, Dateien etc.) vorhanden sein, die allen jetzigen und zukünftigen Mitgliedern dieser Gruppe den Zugriff erlauben. Wenn das nicht Deine Absicht ist, erstelle bitte eine neue Gruppe mit einem anderen Namen."
-#: ../../boot.php:1721
-msgid "Login/Email"
-msgstr "Anmelden/E-Mail"
+#: ../../include/group.php:268
+msgid "Add new connections to this privacy group"
+msgstr "Neue Verbindung zu dieser Gruppe hinzufügen"
-#: ../../boot.php:1722
-msgid "Password"
-msgstr "Kennwort"
+#: ../../include/group.php:310
+msgid "edit"
+msgstr "Bearbeiten"
-#: ../../boot.php:1723
-msgid "Remember me"
-msgstr "Angaben speichern"
+#: ../../include/group.php:333
+msgid "Edit group"
+msgstr "Gruppe ändern"
-#: ../../boot.php:1726
-msgid "Forgot your password?"
-msgstr "Passwort vergessen?"
+#: ../../include/group.php:334
+msgid "Add privacy group"
+msgstr "Gruppe hinzufügen"
-#: ../../boot.php:2287
-msgid "toggle mobile"
-msgstr "auf/von mobile Ansicht wechseln"
+#: ../../include/group.php:335
+msgid "Channels not in any privacy group"
+msgstr "Kanäle, die in keiner Gruppe sind"
-#: ../../boot.php:2442
-msgid "Website SSL certificate is not valid. Please correct."
-msgstr "Das SSL-Zertifikat der Website ist nicht gültig. Bitte beheben."
+#: ../../include/connections.php:128
+msgid "New window"
+msgstr "Neues Fenster"
-#: ../../boot.php:2445
-#, php-format
-msgid "[hubzilla] Website SSL error for %s"
-msgstr "[hubzilla] Website-SSL-Fehler für %s"
+#: ../../include/connections.php:129
+msgid "Open the selected location in a different window or browser tab"
+msgstr "Öffne die markierte Adresse in einem neuen Browserfenster oder Tab"
-#: ../../boot.php:2562
-msgid "Cron/Scheduled tasks not running."
-msgstr "Cron-Aufgaben laufen nicht."
+#: ../../include/auth.php:148
+msgid "Logged out."
+msgstr "Ausgeloggt."
-#: ../../boot.php:2566
-#, php-format
-msgid "[hubzilla] Cron tasks not running on %s"
-msgstr "[hubzilla] Cron-Aufgaben für %s laufen nicht"
+#: ../../include/auth.php:263
+msgid "Email validation is incomplete. Please check your email."
+msgstr "E-Mail-Bestätigung nicht abgeschlossen. Bitte prüfe Deine E-Mails (ggf. Spam-Filterung mit berücksichtigen)."
+
+#: ../../include/auth.php:278
+msgid "Failed authentication"
+msgstr "Authentifizierung fehlgeschlagen"
+
+#: ../../include/help.php:34
+msgid "Help:"
+msgstr "Hilfe:"
+
+#: ../../include/help.php:78
+msgid "Not Found"
+msgstr "Nicht gefunden"
diff --git a/view/de/hstrings.php b/view/de/hstrings.php
index 5d2a987ae..25011af40 100644
--- a/view/de/hstrings.php
+++ b/view/de/hstrings.php
@@ -5,22 +5,6 @@ function string_plural_select_de($n){
return ($n != 1);;
}}
App::$rtl = 0;
-App::$strings["Social Networking"] = "Soziales Netzwerk";
-App::$strings["Social - Mostly Public"] = "Soziales Netzwerk - Weitgehend öffentlich";
-App::$strings["Social - Restricted"] = "Soziales Netzwerk - Beschränkt";
-App::$strings["Social - Private"] = "Soziales Netzwerk - Privat";
-App::$strings["Community Forum"] = "Forum";
-App::$strings["Forum - Mostly Public"] = "Forum - Weitgehend öffentlich";
-App::$strings["Forum - Restricted"] = "Forum - Beschränkt";
-App::$strings["Forum - Private"] = "Forum - Privat";
-App::$strings["Feed Republish"] = "Teilen von Feeds";
-App::$strings["Feed - Mostly Public"] = "Feeds - Weitgehend öffentlich";
-App::$strings["Feed - Restricted"] = "Feeds - Beschränkt";
-App::$strings["Special Purpose"] = "Für besondere Zwecke";
-App::$strings["Special - Celebrity/Soapbox"] = "Speziell - Mitteilungs-Kanal (keine Kommentare)";
-App::$strings["Special - Group Repository"] = "Speziell - Gruppenarchiv";
-App::$strings["Other"] = "Andere";
-App::$strings["Custom/Expert Mode"] = "Benutzerdefiniert/Expertenmodus";
App::$strings["Can view my channel stream and posts"] = "Kann meinen Kanal-Stream und meine Beiträge sehen";
App::$strings["Can send me their channel stream and posts"] = "Kann mir die Beiträge aus seinem/ihrem Kanal schicken";
App::$strings["Can view my default channel profile"] = "Kann mein Standardprofil sehen";
@@ -28,7 +12,9 @@ App::$strings["Can view my connections"] = "Kann meine Verbindungen sehen";
App::$strings["Can view my file storage and photos"] = "Kann meine Datei- und Bilderordner sehen";
App::$strings["Can upload/modify my file storage and photos"] = "Kann in meine Datei- und Bilderordner hochladen/ändern";
App::$strings["Can view my channel webpages"] = "Kann die Webseiten meines Kanals sehen";
+App::$strings["Can view my wiki pages"] = "Kann meine Wiki-Seiten sehen";
App::$strings["Can create/edit my channel webpages"] = "Kann Webseiten in meinem Kanal erstellen/ändern";
+App::$strings["Can write to my wiki pages"] = "Kann meine Wiki-Seiten bearbeiten";
App::$strings["Can post on my channel (wall) page"] = "Kann auf meiner Kanal-Seite (\"wall\") Beiträge veröffentlichen";
App::$strings["Can comment on or like my posts"] = "Darf meine Beiträge kommentieren und mögen/nicht mögen";
App::$strings["Can send me private mail messages"] = "Kann mir private Nachrichten schicken";
@@ -37,184 +23,360 @@ App::$strings["Can forward to all my channel connections via @+ mentions in post
App::$strings["Can chat with me"] = "Kann mit mir chatten";
App::$strings["Can source my public posts in derived channels"] = "Kann meine öffentlichen Beiträge als Quellen für Kanäle verwenden";
App::$strings["Can administer my channel"] = "Kann meinen Kanal administrieren";
-App::$strings["parent"] = "Übergeordnetes Verzeichnis";
-App::$strings["Collection"] = "Sammlung";
-App::$strings["Principal"] = "Prinzipal";
-App::$strings["Addressbook"] = "Adressbuch";
-App::$strings["Calendar"] = "Kalender";
-App::$strings["Schedule Inbox"] = "Posteingang für überwachte Kalender";
-App::$strings["Schedule Outbox"] = "Postausgang für überwachte Kalender";
-App::$strings["Unknown"] = "Unbekannt";
-App::$strings["Files"] = "Dateien";
-App::$strings["Total"] = "Summe";
-App::$strings["Shared"] = "Geteilt";
+App::$strings["Social Networking"] = "Soziales Netzwerk";
+App::$strings["Social - Mostly Public"] = "Soziales Netzwerk - Weitgehend öffentlich";
+App::$strings["Social - Restricted"] = "Soziales Netzwerk - Beschränkt";
+App::$strings["Social - Private"] = "Soziales Netzwerk - Privat";
+App::$strings["Community Forum"] = "Forum";
+App::$strings["Forum - Mostly Public"] = "Forum - Weitgehend öffentlich";
+App::$strings["Forum - Restricted"] = "Forum - Beschränkt";
+App::$strings["Forum - Private"] = "Forum - Privat";
+App::$strings["Feed Republish"] = "Teilen von Feeds";
+App::$strings["Feed - Mostly Public"] = "Feeds - Weitgehend öffentlich";
+App::$strings["Feed - Restricted"] = "Feeds - Beschränkt";
+App::$strings["Special Purpose"] = "Für besondere Zwecke";
+App::$strings["Special - Celebrity/Soapbox"] = "Speziell - Mitteilungs-Kanal (keine Kommentare)";
+App::$strings["Special - Group Repository"] = "Speziell - Gruppenarchiv";
+App::$strings["Other"] = "Andere";
+App::$strings["Custom/Expert Mode"] = "Benutzerdefiniert/Expertenmodus";
+App::$strings["Requested profile is not available."] = "Das angefragte Profil ist nicht verfügbar.";
+App::$strings["Permission denied."] = "Berechtigung verweigert.";
+App::$strings["Block Name"] = "Block-Name";
+App::$strings["Blocks"] = "Blöcke";
+App::$strings["Block Title"] = "Titel des Blocks";
+App::$strings["Created"] = "Erstellt";
+App::$strings["Edited"] = "Geändert";
App::$strings["Create"] = "Erstelle";
-App::$strings["Upload"] = "Hochladen";
-App::$strings["Name"] = "Name";
-App::$strings["Type"] = "Typ";
-App::$strings["Size"] = "Größe";
-App::$strings["Last Modified"] = "Zuletzt geändert";
App::$strings["Edit"] = "Bearbeiten";
+App::$strings["Share"] = "Teilen";
App::$strings["Delete"] = "Löschen";
-App::$strings["You are using %1\$s of your available file storage."] = "Sie verwenden %1\$s von Ihrem verfügbaren Dateispeicher.";
-App::$strings["You are using %1\$s of %2\$s available file storage. (%3\$s&#37;)"] = "Sie verwenden %1\$s von %2\$s verfügbarem Dateispeicher. (%3\$s&#37;)";
-App::$strings["WARNING:"] = "WARNUNG:";
-App::$strings["Create new folder"] = "Neuen Ordner anlegen";
-App::$strings["Upload file"] = "Datei hochladen";
-App::$strings["Drop files here to immediately upload"] = "Dateien zum sofortigen Hochladen hier fallen lassen";
-App::$strings["Permission denied."] = "Berechtigung verweigert.";
-App::$strings["Not Found"] = "Nicht gefunden";
-App::$strings["Page not found."] = "Seite nicht gefunden.";
-App::$strings["Permission denied"] = "Keine Berechtigung";
-App::$strings["Remote authentication blocked. You are logged into this site locally. Please logout and retry."] = "Fern-Authentifizierung blockiert. Du bist lokal auf diesem Server angemeldet. Bitte melde Dich ab und versuche es erneut.";
-App::$strings["Welcome %s. Remote authentication successful."] = "Willkommen %s. Entfernte Authentifizierung erfolgreich.";
-App::$strings["Requested profile is not available."] = "Das angefragte Profil ist nicht verfügbar.";
-App::$strings["Some blurb about what to do when you're new here"] = "Ein Hinweis, was man tun kann, wenn man neu hier ist";
-App::$strings["Away"] = "Abwesend";
-App::$strings["Online"] = "Online";
-App::$strings["Maximum daily site registrations exceeded. Please try again tomorrow."] = "Maximale Anzahl täglicher Neuanmeldungen erreicht. Bitte versuche es morgen noch einmal.";
-App::$strings["Please indicate acceptance of the Terms of Service. Registration failed."] = "Bitte stimme den Nutzungsbedingungen zu. Registrierung fehlgeschlagen.";
-App::$strings["Passwords do not match."] = "Passwörter stimmen nicht überein.";
-App::$strings["Registration successful. Please check your email for validation instructions."] = "Registrierung erfolgreich. Eine E-Mail mit weiteren Anweisungen wurde an Dich gesendet.";
-App::$strings["Your registration is pending approval by the site owner."] = "Deine Registrierung muss noch vom Betreiber der Seite freigegeben werden.";
-App::$strings["Your registration can not be processed."] = "Deine Registrierung konnte nicht verarbeitet werden.";
-App::$strings["Registration on this hub is disabled."] = "Die Registrierung auf diesem Hub ist nicht möglich.";
-App::$strings["Registration on this hub is by approval only."] = "Eine Registrierung auf diesem Hub erfordert die Zustimmung durch den Administrator.";
-App::$strings["<a href=\"pubsites\">Register at another affiliated hub.</a>"] = "<a href=\"pubsites\">Registriere Dich auf einem der anderen verbundenen Hubs.</a>";
-App::$strings["This site has exceeded the number of allowed daily account registrations. Please try again tomorrow."] = "Die maximale Anzahl täglicher Registrierungen auf diesem Server wurde überschritten. Bitte versuche es morgen noch einmal.";
-App::$strings["Terms of Service"] = "Nutzungsbedingungen";
-App::$strings["I accept the %s for this website"] = "Ich akzeptiere die %s für diese Webseite";
-App::$strings["I am over 13 years of age and accept the %s for this website"] = "Ich bin älter als 13 Jahre und akzeptiere die %s dieser Webseite";
-App::$strings["Your email address"] = "Ihre E-Mail Adresse";
-App::$strings["Choose a password"] = "Passwort";
-App::$strings["Please re-enter your password"] = "Bitte gib Dein Passwort noch einmal ein";
-App::$strings["Please enter your invitation code"] = "Bitte trage Deinen Einladungs-Code ein";
-App::$strings["Name or caption"] = "Name oder Titel";
-App::$strings["Examples: \"Bob Jameson\", \"Lisa and her Horses\", \"Soccer\", \"Aviation Group\""] = "Beispiele: „Horst Weidinger“, „Lisa und ihr Meerschweinchen“, „Fußball“, „Segelflieger-Forum“ ";
-App::$strings["Choose a short nickname"] = "Wähle einen kurzen Spitznamen";
-App::$strings["Your nickname will be used to create an easy to remember channel address e.g. nickname%s"] = "Dein Spitzname wird verwendet, um eine leicht zu merkende Kanal-Adresse (ähnlich einer E-Mail-Adresse) zu erzeugen, die Du mit anderen austauschen kannst, z.B. nickname%s";
-App::$strings["Channel role and privacy"] = "Kanaltyp und Privatspäre-Einstellungen";
-App::$strings["Select a channel role with your privacy requirements."] = "Wähle einen passenden Kanaltyp mit den zugehörigen Voreinstellungen zur Privatsphäre.";
-App::$strings["Read more about roles"] = "Mehr Informationen über Rollen";
-App::$strings["no"] = "nein";
-App::$strings["yes"] = "ja";
-App::$strings["Registration"] = "Registrierung";
-App::$strings["Membership on this site is by invitation only."] = "Mitgliedschaft auf dieser Seite ist nur nach vorheriger Einladung möglich.";
-App::$strings["Register"] = "Registrieren";
-App::$strings["This site may require email verification after submitting this form. If you are returned to a login page, please check your email for instructions."] = "Diese Seite verlangt möglicherweise eine Emailbestätigung nach dem Absenden des Formulars. Wenn Du auf eine Login-Seite zurückgeleitet wirst, prüfe bitte Deinen Posteingang auf neue Mails mit entsprechenden Hinweisen.";
-App::$strings["Fetching URL returns error: %1\$s"] = "Abrufen der URL gab einen Fehler zurück: %1\$s";
-App::$strings["Profile Match"] = "Profil-Übereinstimmungen";
-App::$strings["No keywords to match. Please add keywords to your default profile."] = "Keine Schlüsselwörter für den Abgleich gefunden. Bitte füge Schlüsselwörter zu Deinem Standardprofil hinzu.";
-App::$strings["is interested in:"] = "interessiert sich für:";
-App::$strings["Connect"] = "Verbinden";
-App::$strings["No matches"] = "Keine Übereinstimmungen";
-App::$strings["Could not access contact record."] = "Konnte nicht auf den Kontakteintrag zugreifen.";
-App::$strings["Could not locate selected profile."] = "Gewähltes Profil nicht gefunden.";
-App::$strings["Connection updated."] = "Verbindung aktualisiert.";
-App::$strings["Failed to update connection record."] = "Konnte den Verbindungseintrag nicht aktualisieren.";
-App::$strings["is now connected to"] = "ist jetzt verbunden mit";
-App::$strings["No"] = "Nein";
-App::$strings["Yes"] = "Ja";
-App::$strings["Could not access address book record."] = "Konnte nicht auf den Adressbuch-Eintrag zugreifen.";
-App::$strings["Refresh failed - channel is currently unavailable."] = "Aktualisierung fehlgeschlagen – der Kanal ist im Moment nicht erreichbar.";
-App::$strings["Unable to set address book parameters."] = "Konnte die Adressbuch-Parameter nicht setzen.";
-App::$strings["Connection has been removed."] = "Verbindung wurde gelöscht.";
-App::$strings["View Profile"] = "Profil ansehen";
-App::$strings["View %s's profile"] = "%ss Profil ansehen";
-App::$strings["Refresh Permissions"] = "Zugriffsrechte neu laden";
-App::$strings["Fetch updated permissions"] = "Aktualisierte Zugriffsrechte abfragen";
-App::$strings["Recent Activity"] = "Kürzliche Aktivitäten";
-App::$strings["View recent posts and comments"] = "Betrachte die neuesten Beiträge und Kommentare";
-App::$strings["Unblock"] = "Freigeben";
-App::$strings["Block"] = "Blockieren";
-App::$strings["Block (or Unblock) all communications with this connection"] = "Jegliche Kommunikation mit dieser Verbindung blockieren/zulassen";
-App::$strings["This connection is blocked!"] = "Die Verbindung ist geblockt!";
-App::$strings["Unignore"] = "Nicht ignorieren";
-App::$strings["Ignore"] = "Ignorieren";
-App::$strings["Ignore (or Unignore) all inbound communications from this connection"] = "Jegliche eingehende Kommunikation von dieser Verbindung ignorieren/zulassen";
-App::$strings["This connection is ignored!"] = "Die Verbindung wird ignoriert!";
-App::$strings["Unarchive"] = "Aus Archiv zurückholen";
-App::$strings["Archive"] = "Archivieren";
-App::$strings["Archive (or Unarchive) this connection - mark channel dead but keep content"] = "Verbindung archivieren/aus dem Archiv zurückholen (Archiv = Kanal als erloschen markieren, aber die Beiträge behalten)";
-App::$strings["This connection is archived!"] = "Die Verbindung ist archiviert!";
-App::$strings["Unhide"] = "Wieder sichtbar machen";
-App::$strings["Hide"] = "Verstecken";
-App::$strings["Hide or Unhide this connection from your other connections"] = "Diese Verbindung vor anderen Verbindungen verstecken/zeigen";
-App::$strings["This connection is hidden!"] = "Die Verbindung ist versteckt!";
-App::$strings["Delete this connection"] = "Verbindung löschen";
-App::$strings["Me"] = "Ich";
-App::$strings["Family"] = "Familie";
-App::$strings["Friends"] = "Freunde";
-App::$strings["Acquaintances"] = "Bekannte";
-App::$strings["All"] = "Alle";
-App::$strings["Approve this connection"] = "Verbindung genehmigen";
-App::$strings["Accept connection to allow communication"] = "Akzeptiere die Verbindung, um Kommunikation zu ermöglichen";
-App::$strings["Set Affinity"] = "Beziehung festlegen";
-App::$strings["Set Profile"] = "Profil festlegen";
-App::$strings["Set Affinity & Profile"] = "Beziehung und Profile festlegen";
-App::$strings["none"] = "Keine";
-App::$strings["Connection Default Permissions"] = "Standardzugriffsrechte für neue Verbindungen:";
-App::$strings["Connection: %s"] = "Verbindung: %s";
-App::$strings["Apply these permissions automatically"] = "Diese Berechtigungen automatisch anwenden";
-App::$strings["Connection requests will be approved without your interaction"] = "Verbindungsanfragen werden sofort bestätigt, ohne dass Deine aktive Zustimmung erforderlich ist.";
-App::$strings["This connection's primary address is"] = "Die Hauptadresse der Verbindung ist";
-App::$strings["Available locations:"] = "Verfügbare Klone:";
-App::$strings["The permissions indicated on this page will be applied to all new connections."] = "Die auf dieser Seite angegebenen Berechtigungen werden auf alle neuen Verbindungen angewendet.";
-App::$strings["Connection Tools"] = "Verbindungswerkzeuge";
-App::$strings["Slide to adjust your degree of friendship"] = "Verschieben, um den Grad der Freundschaft zu einzustellen";
-App::$strings["Rating"] = "Bewertung";
-App::$strings["Slide to adjust your rating"] = "Verschieben, um Deine Bewertung einzustellen";
-App::$strings["Optionally explain your rating"] = "Optional kannst Du Deine Bewertung begründen";
-App::$strings["Custom Filter"] = "Benutzerdefinierter Filter";
-App::$strings["Only import posts with this text"] = "Nur Beiträge mit diesem Text importieren";
-App::$strings["words one per line or #tags or /patterns/ or lang=xx, leave blank to import all posts"] = "Einzelne Wörter pro Zeile, #Tags oder /Reguläre Ausdrücke/. lang=xx (z.B. lang=de) ermöglicht Filterung nach Sprache. Leer lassen, um alle Beiträge zu importieren.";
-App::$strings["Do not import posts with this text"] = "Beiträge mit diesem Text nicht importieren";
-App::$strings["This information is public!"] = "Diese Information ist öffentlich!";
-App::$strings["Connection Pending Approval"] = "Verbindung wartet auf Bestätigung";
-App::$strings["inherited"] = "geerbt";
+App::$strings["View"] = "Ansicht";
+App::$strings["Total invitation limit exceeded."] = "Einladungslimit überschritten.";
+App::$strings["%s : Not a valid email address."] = "%s : Keine gültige Email Adresse.";
+App::$strings["Please join us on \$Projectname"] = "Schließe Dich uns auf \$Projectname an!";
+App::$strings["Invitation limit exceeded. Please contact your site administrator."] = "Einladungslimit überschritten. Bitte kontaktiere den Administrator Deines \$Projectname-Servers.";
+App::$strings["%s : Message delivery failed."] = "%s : Nachricht konnte nicht zugestellt werden.";
+App::$strings["%d message sent."] = array(
+ 0 => "%d Nachricht gesendet.",
+ 1 => "%d Nachrichten gesendet.",
+);
+App::$strings["You have no more invitations available"] = "Du hast keine weiteren verfügbare Einladungen";
+App::$strings["Send invitations"] = "Einladungen senden";
+App::$strings["Enter email addresses, one per line:"] = "Email-Adressen eintragen, eine pro Zeile:";
+App::$strings["Your message:"] = "Deine Nachricht:";
+App::$strings["Please join my community on \$Projectname."] = "Schließe Dich uns auf \$Projectname an!";
+App::$strings["You will need to supply this invitation code:"] = "Bitte verwende bei der Registrierung den folgenden Einladungscode:";
+App::$strings["1. Register at any \$Projectname location (they are all inter-connected)"] = "1. Registriere Dich auf einem beliebigen \$Projectname-Hub (sie sind alle miteinander verbunden)";
+App::$strings["2. Enter my \$Projectname network address into the site searchbar."] = "2. Gib meine \$Projectname-Adresse im Suchfeld ein.";
+App::$strings["or visit"] = "oder besuche";
+App::$strings["3. Click [Connect]"] = "3. Klicke auf [Verbinden]";
App::$strings["Submit"] = "Absenden";
-App::$strings["Please choose the profile you would like to display to %s when viewing your profile securely."] = "Bitte wähle ein Profil, das wir %s zeigen sollen, wenn Deine Profilseite über eine verifizierte Verbindung aufgerufen wird.";
-App::$strings["Their Settings"] = "Deren Einstellungen";
-App::$strings["My Settings"] = "Meine Einstellungen";
-App::$strings["Individual Permissions"] = "Individuelle Zugriffsrechte";
-App::$strings["Some permissions may be inherited from your channel's <a href=\"settings\"><strong>privacy settings</strong></a>, which have higher priority than individual settings. You can <strong>not</strong> change those settings here."] = "Einige Berechtigungen werden möglicherweise von den globalen <a href=\"settings\">Sicherheits- und Privatsphäre-Einstellungen</a> dieses Kanals vererbt. Diese haben eine höhere Priorität als die Einstellungen an der Verbindung und können hier nicht verändert werden.";
-App::$strings["Some permissions may be inherited from your channel's <a href=\"settings\"><strong>privacy settings</strong></a>, which have higher priority than individual settings. You can change those settings here but they wont have any impact unless the inherited setting changes."] = "Einige Berechtigungen werden möglicherweise von den globalen <a href=\"settings\">Sicherheits- und Privatsphäre-Einstellungen</a> dieses Kanals geerbt. Diese haben eine höhere Priorität als die Einstellungen an der Verbindung. Werden geerbte Einstellungen hier geändert, hat dies keine Auswirkungen.";
-App::$strings["Last update:"] = "Letzte Aktualisierung:";
-App::$strings["Invalid message"] = "Ungültige Beitrags-ID (mid)";
-App::$strings["no results"] = "keine Ergebnisse";
-App::$strings["channel sync processed"] = "Kanal-Sync verarbeitet";
-App::$strings["queued"] = "zur Warteschlange hinzugefügt";
-App::$strings["posted"] = "zugestellt";
-App::$strings["accepted for delivery"] = "für Zustellung akzeptiert";
-App::$strings["updated"] = "aktualisiert";
-App::$strings["update ignored"] = "Aktualisierung ignoriert";
-App::$strings["permission denied"] = "Zugriff verweigert";
-App::$strings["recipient not found"] = "Empfänger nicht gefunden.";
-App::$strings["mail recalled"] = "Mail widerrufen";
-App::$strings["duplicate mail received"] = "Doppelte Mail erhalten";
-App::$strings["mail delivered"] = "Mail zugestellt";
-App::$strings["Delivery report for %1\$s"] = "Zustellungsbericht für %1\$s";
-App::$strings["Options"] = "Optionen";
-App::$strings["Redeliver"] = "Erneut zustellen";
-App::$strings["Bookmark added"] = "Lesezeichen hinzugefügt";
-App::$strings["My Bookmarks"] = "Meine Lesezeichen";
-App::$strings["My Connections Bookmarks"] = "Lesezeichen meiner Kontakte";
-App::$strings["network"] = "Netzwerk";
-App::$strings["RSS"] = "RSS";
+App::$strings["Item not found"] = "Element nicht gefunden";
+App::$strings["Layout Name"] = "Layout-Name";
+App::$strings["Layout Description (Optional)"] = "Layout-Beschreibung (optional)";
+App::$strings["Edit Layout"] = "Layout bearbeiten";
+App::$strings["Permission denied"] = "Keine Berechtigung";
+App::$strings["Invalid profile identifier."] = "Ungültiger Profil-Identifikator";
+App::$strings["Profile Visibility Editor"] = "Profil-Sichtbarkeits-Editor";
+App::$strings["Profile"] = "Profil";
+App::$strings["Click on a contact to add or remove."] = "Klicke auf einen Kontakt, um ihn hinzuzufügen oder zu entfernen.";
+App::$strings["Visible To"] = "Sichtbar für";
+App::$strings["All Connections"] = "Alle Verbindungen";
+App::$strings["INVALID EVENT DISMISSED!"] = "UNGÜLTIGEN TERMIN ABGELEHNT!";
+App::$strings["Summary: "] = "Zusammenfassung:";
+App::$strings["Unknown"] = "Unbekannt";
+App::$strings["Date: "] = "Datum:";
+App::$strings["Reason: "] = "Grund:";
+App::$strings["INVALID CARD DISMISSED!"] = "UNGÜLTIGE KARTE ABGELEHNT!";
+App::$strings["Name: "] = "Name: ";
+App::$strings["Event title"] = "Termintitel";
+App::$strings["Start date and time"] = "Startdatum und -zeit";
+App::$strings["Example: YYYY-MM-DD HH:mm"] = "Beispiel: JJJJ-MM-TT HH:mm";
+App::$strings["End date and time"] = "Enddatum und -zeit";
+App::$strings["Description"] = "Beschreibung";
+App::$strings["Location"] = "Ort";
+App::$strings["Previous"] = "Voriges";
+App::$strings["Next"] = "Nächste";
+App::$strings["Today"] = "Heute";
+App::$strings["Month"] = "Monat";
+App::$strings["Week"] = "Woche";
+App::$strings["Day"] = "Tag";
+App::$strings["List month"] = "Liste Monat";
+App::$strings["List week"] = "Liste Woche";
+App::$strings["List day"] = "Liste Tag";
+App::$strings["More"] = "Mehr";
+App::$strings["Less"] = "Weniger";
+App::$strings["Select calendar"] = "Kalender auswählen";
+App::$strings["Delete all"] = "Alles löschen";
+App::$strings["Cancel"] = "Abbrechen";
+App::$strings["Sorry! Editing of recurrent events is not yet implemented."] = "Entschuldigung, aber das Bearbeiten von wiederkehrenden Veranstaltungen ist leider noch nicht implementiert.";
+App::$strings["Name"] = "Name";
+App::$strings["Organisation"] = "Organisation";
+App::$strings["Title"] = "Titel";
+App::$strings["Phone"] = "Telefon";
+App::$strings["Email"] = "E-Mail";
+App::$strings["Instant messenger"] = "Sofortnachrichtendienst";
+App::$strings["Website"] = "Webseite";
+App::$strings["Address"] = "Adresse";
+App::$strings["Note"] = "Hinweis";
+App::$strings["Mobile"] = "Mobil";
+App::$strings["Home"] = "Home";
+App::$strings["Work"] = "Arbeit";
+App::$strings["Add Contact"] = "Kontakt hinzufügen";
+App::$strings["Add Field"] = "Feld hinzufügen";
+App::$strings["Update"] = "Aktualisieren";
+App::$strings["P.O. Box"] = "Postfach";
+App::$strings["Additional"] = "Zusätzlich";
+App::$strings["Street"] = "Straße";
+App::$strings["Locality"] = "Ortschaft";
+App::$strings["Region"] = "Region";
+App::$strings["ZIP Code"] = "Postleitzahl";
+App::$strings["Country"] = "Land";
+App::$strings["Default Calendar"] = "Standardkalender";
+App::$strings["Default Addressbook"] = "Standardadressbuch";
+App::$strings["This site is not a directory server"] = "Diese Webseite ist kein Verzeichnisserver";
+App::$strings["You must be logged in to see this page."] = "Du musst angemeldet sein, um diese Seite betrachten zu können.";
+App::$strings["Posts and comments"] = "Beiträge und Kommentare";
+App::$strings["Only posts"] = "Nur Beiträge";
+App::$strings["Insufficient permissions. Request redirected to profile page."] = "Unzureichende Zugriffsrechte. Die Anfrage wurde zur Profil-Seite umgeleitet.";
+App::$strings["Export Channel"] = "Kanal exportieren";
+App::$strings["Export your basic channel information to a file. This acts as a backup of your connections, permissions, profile and basic data, which can be used to import your data to a new server hub, but does not contain your content."] = "Exportiert die grundlegenden Kanal-Informationen in eine kleine Datei. Diese stellt eine Sicherung Deiner Verbindungen, Berechtigungen, Profile und Basisdaten bereit, die für den Import auf einem anderen Hub verwendet werden kann, aber nicht die Beiträge Deines Kanals enthält.";
+App::$strings["Export Content"] = "Kanal und Inhalte exportieren";
+App::$strings["Export your channel information and recent content to a JSON backup that can be restored or imported to another server hub. This backs up all of your connections, permissions, profile data and several months of posts. This file may be VERY large. Please be patient - it may take several minutes for this download to begin."] = "Exportiert Deine Kanal-Informationen sowie alle zugehörigen Inhalte in eine JSON-Sicherungsdatei. Die sichert alle Verbindungen, Berechtigungen, Profildaten und Deine Beiträge aus mehreren Monaten. Diese Datei kann SEHR groß werden! Bitte habe ein wenig Geduld – es kann mehrere Minuten dauern, bis der Download startet.";
+App::$strings["Export your posts from a given year."] = "Exportiert die Beiträge des angegebenen Jahres.";
+App::$strings["You may also export your posts and conversations for a particular year or month. Adjust the date in your browser location bar to select other dates. If the export fails (possibly due to memory exhaustion on your server hub), please try again selecting a more limited date range."] = "Du kannst auch die Beiträge und Konversationen eines bestimmten Jahres oder Monats exportieren. Ändere das Datum in der Adresszeile Deines Browsers, um andere Zeiträume zu wählen. Falls der Export fehlschlägt (vermutlich, weil auf diesem Hub nicht genügend Speicher zur Verfügung steht), versuche es noch einmal mit einer kleineren Zeitspanne.";
+App::$strings["To select all posts for a given year, such as this year, visit <a href=\"%1\$s\">%2\$s</a>"] = "Um alle Beiträge eines bestimmten Jahres, zum Beispiel dieses Jahres, auszuwählen, klicke <a href=\"%1\$s\">%2\$s</a>.";
+App::$strings["To select all posts for a given month, such as January of this year, visit <a href=\"%1\$s\">%2\$s</a>"] = "Um alle Beiträge eines bestimmten Monats auszuwählen, zum Beispiel vom Januar diesen Jahres, klicke <a href=\"%1\$s\">%2\$s</a>.";
+App::$strings["These content files may be imported or restored by visiting <a href=\"%1\$s\">%2\$s</a> on any site containing your channel. For best results please import or restore these in date order (oldest first)."] = "Diese Inhalts-Sicherungen können wiederhergestellt werden, indem Du <a href=\"%1\$s\">%2\$s</a> auf jeglichem Hub besuchst, der diesen Kanal enthält. Das funktioniert am besten, wenn Du dabei die zeitliche Reihenfolge einhältst, also die Sicherungen für den ältesten Zeitraum zuerst importierst.";
+App::$strings["Public access denied."] = "Öffentlichen Zugriff verweigert.";
+App::$strings["Search"] = "Suche";
+App::$strings["Items tagged with: %s"] = "Beiträge mit Schlagwort: %s";
+App::$strings["Search results for: %s"] = "Suchergebnisse für: %s";
+App::$strings["Public Stream"] = "Öffentlicher Beitrags-Stream";
App::$strings["Location not found."] = "Klon nicht gefunden.";
App::$strings["Location lookup failed."] = "Nachschlagen des Kanal-Ortes fehlgeschlagen";
App::$strings["Please select another location to become primary before removing the primary location."] = "Bitte mache einen anderen Kanal-Ort zum primären Ort, bevor Du den primären Ort löschst.";
App::$strings["Syncing locations"] = "Synchronisiere Klone";
App::$strings["No locations found."] = "Keine Klon-Adressen gefunden.";
App::$strings["Manage Channel Locations"] = "Klon-Adressen verwalten";
-App::$strings["Location"] = "Ort";
-App::$strings["Address"] = "Adresse";
App::$strings["Primary"] = "Primär";
App::$strings["Drop"] = "Löschen";
App::$strings["Sync Now"] = "Jetzt synchronisieren";
App::$strings["Please wait several minutes between consecutive operations."] = "Bitte warte mehrere Minuten zwischen dem Ausführen zweier Operationen!";
App::$strings["When possible, drop a location by logging into that website/hub and removing your channel."] = "Wenn möglich, lösche einen Klon, indem Du Dich auf dem jeweiligen Hub einloggst und den Kanal dort löschst.";
App::$strings["Use this form to drop the location if the hub is no longer operating."] = "Benutze dieses Formular zum Löschen eines Klons, wenn es den Hub nicht mehr gibt.";
+App::$strings["Change Order of Navigation Apps"] = "App-Reihenfolge in der Navigation ändern";
+App::$strings["Use arrows to move the corresponding app up or down in the display list"] = "Benutze die Pfeiltasten, um die jeweilige App in der Anzeigeliste auf- oder abwärts zu bewegen.";
+App::$strings["Menu not found."] = "Menü nicht gefunden";
+App::$strings["Unable to create element."] = "Element konnte nicht erstellt werden.";
+App::$strings["Unable to update menu element."] = "Kann Menü-Element nicht aktualisieren.";
+App::$strings["Unable to add menu element."] = "Kann Menü-Bestandteil nicht hinzufügen.";
+App::$strings["Not found."] = "Nicht gefunden.";
+App::$strings["Menu Item Permissions"] = "Zugriffsrechte des Menü-Elements";
+App::$strings["(click to open/close)"] = "(zum öffnen/schließen anklicken)";
+App::$strings["Link Name"] = "Name des Links";
+App::$strings["Link or Submenu Target"] = "Ziel des Links oder Untermenüs";
+App::$strings["Enter URL of the link or select a menu name to create a submenu"] = "URL des Links eingeben oder Menünamen wählen, um ein Untermenü anzulegen.";
+App::$strings["Use magic-auth if available"] = "Magic-Auth verwenden, falls verfügbar";
+App::$strings["No"] = "Nein";
+App::$strings["Yes"] = "Ja";
+App::$strings["Open link in new window"] = "Öffne Link in neuem Fenster";
+App::$strings["Order in list"] = "Reihenfolge in der Liste";
+App::$strings["Higher numbers will sink to bottom of listing"] = "Größere Nummern werden weiter unten in der Auflistung einsortiert";
+App::$strings["Submit and finish"] = "Absenden und fertigstellen";
+App::$strings["Submit and continue"] = "Absenden und fortfahren";
+App::$strings["Menu:"] = "Menü:";
+App::$strings["Link Target"] = "Ziel des Links";
+App::$strings["Edit menu"] = "Menü bearbeiten";
+App::$strings["Edit element"] = "Bestandteil bearbeiten";
+App::$strings["Drop element"] = "Bestandteil löschen";
+App::$strings["New element"] = "Neues Bestandteil";
+App::$strings["Edit this menu container"] = "Diesen Menü-Container bearbeiten";
+App::$strings["Add menu element"] = "Menüelement hinzufügen";
+App::$strings["Delete this menu item"] = "Lösche dieses Menü-Bestandteil";
+App::$strings["Edit this menu item"] = "Bearbeite dieses Menü-Bestandteil";
+App::$strings["Menu item not found."] = "Menü-Bestandteil nicht gefunden.";
+App::$strings["Menu item deleted."] = "Menü-Bestandteil gelöscht.";
+App::$strings["Menu item could not be deleted."] = "Menü-Bestandteil kann nicht gelöscht werden.";
+App::$strings["Edit Menu Element"] = "Bearbeite Menü-Bestandteil";
+App::$strings["Link text"] = "Link Text";
+App::$strings["Calendar entries imported."] = "Kalendereinträge wurden importiert.";
+App::$strings["No calendar entries found."] = "Keine Kalendereinträge gefunden.";
+App::$strings["Event can not end before it has started."] = "Termin-Ende liegt vor dem Beginn.";
+App::$strings["Unable to generate preview."] = "Vorschau konnte nicht erzeugt werden.";
+App::$strings["Event title and start time are required."] = "Titel und Startzeit des Termins sind erforderlich.";
+App::$strings["Event not found."] = "Termin nicht gefunden.";
+App::$strings["event"] = "Termin";
+App::$strings["Edit event title"] = "Termintitel bearbeiten";
+App::$strings["Required"] = "Benötigt";
+App::$strings["Categories (comma-separated list)"] = "Kategorien (Kommagetrennte Liste)";
+App::$strings["Edit Category"] = "Kategorie bearbeiten";
+App::$strings["Category"] = "Kategorie";
+App::$strings["Edit start date and time"] = "Startdatum und -zeit bearbeiten";
+App::$strings["Finish date and time are not known or not relevant"] = "Enddatum und -zeit sind unbekannt oder irrelevant";
+App::$strings["Edit finish date and time"] = "Enddatum und -zeit bearbeiten";
+App::$strings["Finish date and time"] = "Enddatum und -zeit";
+App::$strings["Adjust for viewer timezone"] = "An die Zeitzone des Betrachters anpassen";
+App::$strings["Important for events that happen in a particular place. Not practical for global holidays."] = "Wichtig für Veranstaltungen die an bestimmten Orten stattfinden. Nicht sinnvoll für globale Feiertage / Ferien.";
+App::$strings["Edit Description"] = "Beschreibung bearbeiten";
+App::$strings["Edit Location"] = "Ort bearbeiten";
+App::$strings["Preview"] = "Vorschau";
+App::$strings["Permission settings"] = "Berechtigungs-Einstellungen";
+App::$strings["Timezone:"] = "Zeitzone:";
+App::$strings["Advanced Options"] = "Weitere Optionen";
+App::$strings["l, F j"] = "l, j. F";
+App::$strings["Edit event"] = "Termin bearbeiten";
+App::$strings["Delete event"] = "Termin löschen";
+App::$strings["Link to Source"] = "Link zur Quelle";
+App::$strings["calendar"] = "Kalender";
+App::$strings["Edit Event"] = "Termin bearbeiten";
+App::$strings["Create Event"] = "Termin anlegen";
+App::$strings["Export"] = "Exportieren";
+App::$strings["Event removed"] = "Termin gelöscht";
+App::$strings["Failed to remove event"] = "Termin konnte nicht gelöscht werden";
+App::$strings["App installed."] = "App installiert.";
+App::$strings["Malformed app."] = "Fehlerhafte App.";
+App::$strings["Embed code"] = "Code einbetten";
+App::$strings["Edit App"] = "App bearbeiten";
+App::$strings["Create App"] = "App erstellen";
+App::$strings["Name of app"] = "Name der App";
+App::$strings["Location (URL) of app"] = "Ort (URL) der App";
+App::$strings["Photo icon URL"] = "URL zum Icon";
+App::$strings["80 x 80 pixels - optional"] = "80 x 80 Pixel – optional";
+App::$strings["Categories (optional, comma separated list)"] = "Kategorien (optional, kommagetrennte Liste)";
+App::$strings["Version ID"] = "Versions-ID";
+App::$strings["Price of app"] = "Preis der App";
+App::$strings["Location (URL) to purchase app"] = "Ort (URL), um die App zu kaufen";
+App::$strings["Please login."] = "Bitte melde dich an.";
+App::$strings["Hub not found."] = "Server nicht gefunden.";
+App::$strings["photo"] = "Foto";
+App::$strings["status"] = "Status";
+App::$strings["%1\$s is following %2\$s's %3\$s"] = "%1\$s folgt nun %2\$ss %3\$s";
+App::$strings["%1\$s stopped following %2\$s's %3\$s"] = "%1\$s folgt %2\$ss %3\$s nicht mehr";
+App::$strings["Nothing to import."] = "Nichts zu importieren.";
+App::$strings["Unable to download data from old server"] = "Daten können vom alten Server nicht heruntergeladen werden";
+App::$strings["Imported file is empty."] = "Die importierte Datei ist leer.";
+App::$strings["Warning: Database versions differ by %1\$d updates."] = "Achtung: Datenbankversionen unterscheiden sich um %1\$d Aktualisierungen.";
+App::$strings["Import completed"] = "Import abgeschlossen";
+App::$strings["Import Items"] = "Beiträge importieren";
+App::$strings["Use this form to import existing posts and content from an export file."] = "Mit diesem Formular kannst Du existierende Beiträge und Inhalte aus einer Sicherungsdatei importieren.";
+App::$strings["File to Upload"] = "Hochzuladende Datei:";
+App::$strings["You have created %1$.0f of %2$.0f allowed channels."] = "Du hast %1$.0f von maximal %2$.0f erlaubten Kanälen eingerichtet.";
+App::$strings["Name or caption"] = "Name oder Titel";
+App::$strings["Examples: \"Bob Jameson\", \"Lisa and her Horses\", \"Soccer\", \"Aviation Group\""] = "Beispiele: „Horst Weidinger“, „Lisa und ihr Meerschweinchen“, „Fußball“, „Segelflieger-Forum“ ";
+App::$strings["Choose a short nickname"] = "Wähle einen kurzen Spitznamen";
+App::$strings["Your nickname will be used to create an easy to remember channel address e.g. nickname%s"] = "Dein Spitzname wird verwendet, um eine leicht zu merkende Kanal-Adresse (ähnlich einer E-Mail-Adresse) zu erzeugen, die Du mit anderen austauschen kannst, z.B. nickname%s";
+App::$strings["Channel role and privacy"] = "Kanaltyp und Privatspäre-Einstellungen";
+App::$strings["Select a channel role with your privacy requirements."] = "Wähle einen passenden Kanaltyp mit den zugehörigen Voreinstellungen zur Privatsphäre.";
+App::$strings["Read more about roles"] = "Mehr Informationen über Rollen";
+App::$strings["Create Channel"] = "Einen neuen Kanal anlegen";
+App::$strings["A channel is your identity on this network. It can represent a person, a blog, or a forum to name a few. Channels can make connections with other channels to share information with highly detailed permissions."] = "Ein Kanal ist Deine Identität in diesem Netzwerk. Er kann eine Person, ein Blog oder ein Forum repräsentieren, nur um ein paar Beispiele zu nennen. Kanäle können Verbindungen miteinander eingehen, um Informationen zu teilen, jeweils basierend auf sehr detaillierten Berechtigungseinstellungen.";
+App::$strings["or <a href=\"import\">import an existing channel</a> from another location."] = "oder <a href=\"import\">importiere einen bestehenden Kanal</a> von einem anderen Server.";
+App::$strings["Channel removals are not allowed within 48 hours of changing the account password."] = "Innerhalb von 48 Stunden nach einer Änderung des Passworts können keine Kanäle gelöscht werden.";
+App::$strings["Remove This Channel"] = "Diesen Kanal löschen";
+App::$strings["WARNING: "] = "WARNUNG: ";
+App::$strings["This channel will be completely removed from the network. "] = "Dieser Kanal wird vollständig aus dem Netzwerk gelöscht.";
+App::$strings["This action is permanent and can not be undone!"] = "Dieser Schritt ist endgültig und kann nicht rückgängig gemacht werden!";
+App::$strings["Please enter your password for verification:"] = "Bitte gib zur Bestätigung Dein Passwort ein:";
+App::$strings["Remove this channel and all its clones from the network"] = "Lösche diesen Kanal und all seine Klone aus dem Netzwerk";
+App::$strings["By default only the instance of the channel located on this hub will be removed from the network"] = "Standardmäßig wird der Kanal nur auf diesem Server gelöscht, seine Klone verbleiben im Netzwerk";
+App::$strings["Remove Channel"] = "Kanal löschen";
+App::$strings["Files: shared with me"] = "Dateien, die mit mir geteilt wurden";
+App::$strings["NEW"] = "NEU";
+App::$strings["Size"] = "Größe";
+App::$strings["Last Modified"] = "Zuletzt geändert";
+App::$strings["Remove all files"] = "Alle Dateien löschen";
+App::$strings["Remove this file"] = "Diese Datei löschen";
+App::$strings["\$Projectname Server - Setup"] = "\$Projectname Server-Einrichtung";
+App::$strings["Could not connect to database."] = "Kann nicht mit der Datenbank verbinden.";
+App::$strings["Could not connect to specified site URL. Possible SSL certificate or DNS issue."] = "Konnte die angegebene Webseiten-URL nicht erreichen. Möglicherweise ein Problem mit dem SSL-Zertifikat oder dem DNS.";
+App::$strings["Could not create table."] = "Konnte Tabelle nicht erstellen.";
+App::$strings["Your site database has been installed."] = "Die Datenbank Deines Hubs wurde installiert.";
+App::$strings["You may need to import the file \"install/schema_xxx.sql\" manually using a database client."] = "Möglicherweise musst Du die Datei install/schema_xxx.sql manuell mit Hilfe eines Datenkbank-Clients importieren.";
+App::$strings["Please see the file \"install/INSTALL.txt\"."] = "Lies die Datei \"install/INSTALL.txt\".";
+App::$strings["System check"] = "Systemprüfung";
+App::$strings["Check again"] = "Nochmal prüfen";
+App::$strings["Database connection"] = "Datenbankverbindung";
+App::$strings["In order to install \$Projectname we need to know how to connect to your database."] = "Um \$Projectname zu installieren, müssen wir wissen, wie wir eine Verbindung zu Deiner Datenbank aufbauen können.";
+App::$strings["Please contact your hosting provider or site administrator if you have questions about these settings."] = "Bitte kontaktiere Deinen Hosting-Provider oder Administrator, falls Du Fragen zu diesen Einstellungen hast.";
+App::$strings["The database you specify below should already exist. If it does not, please create it before continuing."] = "Die Datenbank, die Du weiter unten angibst, sollte bereits existieren. Sollte das noch nicht der Fall sein, erzeuge sie bitte bevor Du fortfährst.";
+App::$strings["Database Server Name"] = "Datenbankservername";
+App::$strings["Default is 127.0.0.1"] = "Standard ist 127.0.0.1";
+App::$strings["Database Port"] = "Datenbankport";
+App::$strings["Communication port number - use 0 for default"] = "Port-Nummer für die Kommunikation – verwende 0 für die Standardeinstellung";
+App::$strings["Database Login Name"] = "Datenbank-Benutzername";
+App::$strings["Database Login Password"] = "Datenbank-Passwort";
+App::$strings["Database Name"] = "Datenbankname";
+App::$strings["Database Type"] = "Datenbanktyp";
+App::$strings["Site administrator email address"] = "E-Mail Adresse des Seiten-Administrators";
+App::$strings["Your account email address must match this in order to use the web admin panel."] = "Die E-Mail-Adresse Deines Accounts muss dieser Adresse entsprechen, damit Du Zugriff zur Administrations-Seite erhältst.";
+App::$strings["Website URL"] = "Webseiten-URL";
+App::$strings["Please use SSL (https) URL if available."] = "Nutze wenn möglich eine SSL-URL (https).";
+App::$strings["Please select a default timezone for your website"] = "Standard-Zeitzone für Deinen Server";
+App::$strings["Site settings"] = "Seiteneinstellungen";
+App::$strings["PHP version 5.5 or greater is required."] = "PHP-Version 5.5 oder höher ist erforderlich.";
+App::$strings["PHP version"] = "PHP-Version";
+App::$strings["Could not find a command line version of PHP in the web server PATH."] = "Konnte die Kommandozeilen-Version von PHP nicht im PATH des Web-Servers finden.";
+App::$strings["If you don't have a command line version of PHP installed on server, you will not be able to run background polling via cron."] = "Ohne Kommandozeilen-Version von PHP auf dem Server wirst Du nicht in der Lage sein, Hintergrundprozesse via cron auszuführen.";
+App::$strings["PHP executable path"] = "PHP-Pfad zu ausführbarer Datei";
+App::$strings["Enter full path to php executable. You can leave this blank to continue the installation."] = "Gib den vollen Pfad zum PHP-Interpreter an. Du kannst dieses Feld frei lassen und mit der Installation fortfahren.";
+App::$strings["Command line PHP"] = "PHP-Befehlszeile";
+App::$strings["Unable to check command line PHP, as shell_exec() is disabled. This is required."] = "Prüfung auf Kommandozeilen-PHP fehlgeschlagen, da shell_exec() deaktiviert ist. Dies wird aber benötigt.";
+App::$strings["The command line version of PHP on your system does not have \"register_argc_argv\" enabled."] = "Bei der Kommandozeilen-Version von PHP auf Deinem System ist \"register_argc_argv\" nicht aktiviert.";
+App::$strings["This is required for message delivery to work."] = "Das wird benötigt, damit die Auslieferung von Nachrichten funktioniert.";
+App::$strings["PHP register_argc_argv"] = "PHP register_argc_argv";
+App::$strings["Your max allowed total upload size is set to %s. Maximum size of one file to upload is set to %s. You are allowed to upload up to %d files at once."] = "Die Maximalgröße für Uploads insgesamt liegt bei %s. Die Maximalgröße für eine Datei liegt bei %s. Es können maximal %d Dateien gleichzeitig hochgeladen werden.";
+App::$strings["You can adjust these settings in the server php.ini file."] = "Du kannst diese Einstellungen in der php.ini - Datei des Servers anpassen.";
+App::$strings["PHP upload limits"] = "PHP-Hochladebeschränkungen";
+App::$strings["Error: the \"openssl_pkey_new\" function on this system is not able to generate encryption keys"] = "Fehler: Die „openssl_pkey_new“-Funktion auf diesem System ist nicht in der Lage, Schlüssel für die Verschlüsselung zu erzeugen.";
+App::$strings["If running under Windows, please see \"http://www.php.net/manual/en/openssl.installation.php\"."] = "Wenn Du Windows verwendest, findest Du unter http://www.php.net/manual/en/openssl.installation.php eine Installationsanleitung.";
+App::$strings["Generate encryption keys"] = "Verschlüsselungsschlüssel erzeugen";
+App::$strings["libCurl PHP module"] = "libCurl-PHP-Modul";
+App::$strings["GD graphics PHP module"] = "GD-Grafik-PHP-Modul";
+App::$strings["OpenSSL PHP module"] = "OpenSSL-PHP-Modul";
+App::$strings["PDO database PHP module"] = "PDO-Datenbank-PHP-Modul";
+App::$strings["mb_string PHP module"] = "mb_string-PHP-Modul";
+App::$strings["xml PHP module"] = "xml-PHP-Modul";
+App::$strings["zip PHP module"] = "zip PHP Modul";
+App::$strings["Apache mod_rewrite module"] = "Apache-mod_rewrite-Modul";
+App::$strings["Error: Apache webserver mod-rewrite module is required but not installed."] = "Fehler: Das Apache-Modul mod-rewrite wird benötigt, ist aber nicht installiert.";
+App::$strings["exec"] = "exec";
+App::$strings["Error: exec is required but is either not installed or has been disabled in php.ini"] = "Fehler: exec ist erforderlich, aber entweder nicht installiert oder wurde in der php.ini deaktiviert";
+App::$strings["shell_exec"] = "shell_exec";
+App::$strings["Error: shell_exec is required but is either not installed or has been disabled in php.ini"] = "Fehler: shell_exec ist erforderlich, aber entweder nicht installiert oder wurde in der php.ini deaktiviert";
+App::$strings["Error: libCURL PHP module required but not installed."] = "Fehler: Das PHP-Modul libCURL wird benötigt, ist aber nicht installiert.";
+App::$strings["Error: GD graphics PHP module with JPEG support required but not installed."] = "Fehler: Das PHP-Modul GD-Grafik mit JPEG-Unterstützung wird benötigt, ist aber nicht installiert.";
+App::$strings["Error: openssl PHP module required but not installed."] = "Fehler: Das PHP-Modul openssl wird benötigt, ist aber nicht installiert.";
+App::$strings["Error: PDO database PHP module required but not installed."] = "Fehler: PDO-Datenbank-PHP-Modul ist erforderlich, aber nicht installiert.";
+App::$strings["Error: mb_string PHP module required but not installed."] = "Fehler: Das PHP-Modul mb_string wird benötigt, ist aber nicht installiert.";
+App::$strings["Error: xml PHP module required for DAV but not installed."] = "Fehler: Das xml-PHP-Modul wird für DAV benötigt, ist aber nicht installiert.";
+App::$strings["Error: zip PHP module required but not installed."] = "Fehler: Das zip PHP Modul ist erforderlich, ist aber nicht installiert.";
+App::$strings["The web installer needs to be able to create a file called \".htconfig.php\" in the top folder of your web server and it is unable to do so."] = "Der Installations-Assistent muss in der Lage sein, die Datei \".htconfig.php\" im Stammverzeichnis des Web-Servers anzulegen, ist er aber nicht.";
+App::$strings["This is most often a permission setting, as the web server may not be able to write files in your folder - even if you can."] = "Meist liegt das daran, dass der Nutzer, unter dem der Web-Server läuft, keine Schreibrechte in dem Verzeichnis hat – selbst wenn Du selbst das darfst.";
+App::$strings["At the end of this procedure, we will give you a text to save in a file named .htconfig.php in your Red top folder."] = "Am Schluss dieses Vorgangs wird ein Text generiert, den Du unter dem Dateinamen .htconfig.php im Stammverzeichnis Deiner Hubzilla-Installation speichern musst.";
+App::$strings["You can alternatively skip this procedure and perform a manual installation. Please see the file \"install/INSTALL.txt\" for instructions."] = "Alternativ kannst Du diesen Schritt überspringen und die Installation manuell vornehmen. Lies dazu die Datei install/INSTALL.txt.";
+App::$strings[".htconfig.php is writable"] = ".htconfig.php ist beschreibbar";
+App::$strings["This software uses the Smarty3 template engine to render its web views. Smarty3 compiles templates to PHP to speed up rendering."] = "Diese Software verwendet die Smarty3 Template Engine, um Vorlagen für die Webdarstellung zu verarbeiten. Smarty3 übersetzt diese Vorlagen nach PHP, um die Darstellung zu beschleunigen.";
+App::$strings["In order to store these compiled templates, the web server needs to have write access to the directory %s under the top level web folder."] = "Um diese kompilierten Vorlagen speichern zu können, braucht der Web-Server Schreibzugriff auf das Verzeichnis %s unterhalb des Hubzilla-Stammverzeichnisses.";
+App::$strings["Please ensure that the user that your web server runs as (e.g. www-data) has write access to this folder."] = "Bitte stelle sicher, dass der Nutzer, unter dem der Web-Server läuft (z.B. www-data), Schreibzugriff auf dieses Verzeichnis hat.";
+App::$strings["Note: as a security measure, you should give the web server write access to %s only--not the template files (.tpl) that it contains."] = "Hinweis: Aus Sicherheitsgründen sollte der Web-Server nur auf %s Schreibrechte haben, nicht auf die Template-Dateien (.tpl), die das Verzeichnis enthält.";
+App::$strings["%s is writable"] = "%s ist beschreibbar";
+App::$strings["This software uses the store directory to save uploaded files. The web server needs to have write access to the store directory under the top level web folder"] = "Diese Software benutzt das Verzeichnis store, um hochgeladene Dateien zu speichern. Der Webserver benötigt Schreibrechte für dieses Verzeichnis direkt unterhalb des Web-Stammverzeichnisses.";
+App::$strings["store is writable"] = "store ist schreibbar";
+App::$strings["SSL certificate cannot be validated. Fix certificate or disable https access to this site."] = "Das SSL-Zertifikat konnte nicht validiert werden. Korrigiere das Zertifikat oder deaktiviere den HTTPS-Zugriff auf diesen Server.";
+App::$strings["If you have https access to your website or allow connections to TCP port 443 (the https: port), you MUST use a browser-valid certificate. You MUST NOT use self-signed certificates!"] = "Wenn Du via HTTPS auf Deinen Server zugreifen möchtest, also Verbindungen über den Port 443 möglich sein sollen, ist ein SSL-Zertifikat einer Zertifizierungsstelle (CA) notwendig, das von den Browsern ohne Sicherheitsabfrage akzeptiert wird. Die Verwendung eines selbst signierten Zertifikates ist nicht möglich.";
+App::$strings["This restriction is incorporated because public posts from you may for example contain references to images on your own hub."] = "Diese Einschränkung wurde eingebaut, weil Deine öffentlichen Beiträge zum Beispiel Verweise auf Bilder auf Deinem eigenen Hub enthalten können.";
+App::$strings["If your certificate is not recognized, members of other sites (who may themselves have valid certificates) will get a warning message on their own site complaining about security issues."] = "Wenn Dein Zertifikat nicht von jedem Browser akzeptiert wird, erhalten die Mitglieder anderer \$Projectname-Hubs (die mit korrekten Zertifikaten ausgestattet sind) Sicherheits-Warnmeldungen, obwohl sie gar nicht direkt auf Deinem Server unterwegs sind (zum Beispiel, wenn ein Bild aus einem Deiner Beiträge angezeigt wird).";
+App::$strings["This can cause usability issues elsewhere (not just on your own site) so we must insist on this requirement."] = "Dies kann Probleme für andere Nutzer (nicht nur auf Deinem eigenen Server) verursachen, so dass wir auf dieser Forderung bestehen müssen.";
+App::$strings["Providers are available that issue free certificates which are browser-valid."] = "Es gibt einige Zertifizierungsstellen (CAs), bei denen solche Zertifikate kostenlos zu haben sind.";
+App::$strings["If you are confident that the certificate is valid and signed by a trusted authority, check to see if you have failed to install an intermediate cert. These are not normally required by browsers, but are required for server-to-server communications."] = "Wenn Du sicher bist, dass das Zertifikat gültig und von einer vertrauenswürdigen Zertifizierungsstelle signiert ist, prüfe auf ggf. noch zu installierende Zwischenzertifikate (intermediate). Diese werden nicht unbedingt von Browsern benötigt, aber sehr wohl für die Kommunikation zwischen Servern.";
+App::$strings["SSL certificate validation"] = "SSL Zertifikatverifizierung";
+App::$strings["Url rewrite in .htaccess is not working. Check your server configuration.Test: "] = "Das Umschreiben von URLs (rewrite) per .htaccess funktioniert nicht. Bitte prüfe die Server-Konfiguration. Test:";
+App::$strings["Url rewrite is working"] = "Url rewrite funktioniert";
+App::$strings["The database configuration file \".htconfig.php\" could not be written. Please use the enclosed text to create a configuration file in your web server root."] = "Die Datenbank-Konfigurationsdatei „.htconfig.php“ konnte nicht geschrieben werden. Bitte verwende den unten angegebenen Text, um die Konfigurationsdatei im Stammverzeichnis des Webservers anzulegen.";
+App::$strings["Errors encountered creating database tables."] = "Fehler beim Anlegen der Datenbank-Tabellen aufgetreten.";
+App::$strings["<h1>What next?</h1>"] = "<h1>Wie geht es jetzt weiter?</h1>";
+App::$strings["IMPORTANT: You will need to [manually] setup a scheduled task for the poller."] = "WICHTIG: Du musst [manuell] einen Cronjob für den Poller einrichten.";
App::$strings["Continue"] = "Fortfahren";
App::$strings["Premium Channel Setup"] = "Premium-Kanal-Einrichtung";
App::$strings["Enable premium channel connection restrictions"] = "Einschränkungen für einen Premium-Kanal aktivieren";
@@ -224,92 +386,32 @@ App::$strings["Potential connections will then see the following text before pro
App::$strings["By continuing, I certify that I have complied with any instructions provided on this page."] = "Indem ich fortfahre, bestätige ich die Erfüllung aller Anweisungen auf dieser Seite.";
App::$strings["(No specific instructions have been provided by the channel owner.)"] = "(Der Kanal-Besitzer hat keine speziellen Anweisungen hinterlegt.)";
App::$strings["Restricted or Premium Channel"] = "Eingeschränkter oder Premium-Kanal";
-App::$strings["Invalid item."] = "Ungültiges Element.";
-App::$strings["Channel not found."] = "Kanal nicht gefunden.";
-App::$strings["Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum."] = "Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.";
-App::$strings["Save to Folder:"] = "Speichern in Ordner:";
-App::$strings["- select -"] = "– auswählen –";
-App::$strings["Save"] = "Speichern";
-App::$strings["You have created %1$.0f of %2$.0f allowed channels."] = "Du hast %1$.0f von maximal %2$.0f erlaubten Kanälen eingerichtet.";
-App::$strings["Create a new channel"] = "Neuen Kanal anlegen";
-App::$strings["Create New"] = "Neu anlegen";
-App::$strings["Channel Manager"] = "Kanal-Manager";
-App::$strings["Current Channel"] = "Aktueller Kanal";
-App::$strings["Switch to one of your channels by selecting it."] = "Wechsle zu einem Deiner Kanäle, indem Du auf ihn klickst.";
-App::$strings["Default Channel"] = "Standard Kanal";
-App::$strings["Make Default"] = "Zum Standard machen";
-App::$strings["%d new messages"] = "%d neue Nachrichten";
-App::$strings["%d new introductions"] = "%d neue Vorstellungen";
-App::$strings["Delegated Channel"] = "Delegierte Kanäle";
-App::$strings["Blocked"] = "Blockiert";
-App::$strings["Ignored"] = "Ignoriert";
-App::$strings["Hidden"] = "Versteckt";
-App::$strings["Archived"] = "Archiviert";
-App::$strings["New"] = "Neu";
-App::$strings["New Connections"] = "Neue Verbindungen";
-App::$strings["Show pending (new) connections"] = "Ausstehende (neue) Verbindungsanfragen anzeigen";
-App::$strings["All Connections"] = "Alle Verbindungen";
-App::$strings["Show all connections"] = "Alle Verbindungen anzeigen";
-App::$strings["Only show blocked connections"] = "Nur blockierte Verbindungen anzeigen";
-App::$strings["Only show ignored connections"] = "Nur ignorierte Verbindungen anzeigen";
-App::$strings["Only show archived connections"] = "Nur archivierte Verbindungen anzeigen";
-App::$strings["Only show hidden connections"] = "Nur versteckte Verbindungen anzeigen";
-App::$strings["Pending approval"] = "Wartet auf Genehmigung";
-App::$strings["%1\$s [%2\$s]"] = "%1\$s [%2\$s]";
-App::$strings["Edit connection"] = "Verbindung bearbeiten";
-App::$strings["Delete connection"] = "Verbindung löschen";
-App::$strings["Channel address"] = "Kanaladresse";
-App::$strings["Network"] = "Netzwerk";
-App::$strings["Status"] = "Status";
-App::$strings["Connected"] = "Verbunden";
-App::$strings["Approve connection"] = "Verbindung genehmigen";
-App::$strings["Approve"] = "Genehmigen";
-App::$strings["Ignore connection"] = "Verbindung ignorieren";
-App::$strings["Recent activity"] = "Kürzliche Aktivitäten";
-App::$strings["Connections"] = "Verbindungen";
-App::$strings["Search"] = "Suche";
-App::$strings["Search your connections"] = "Verbindungen durchsuchen";
-App::$strings["Connections search"] = "Verbindung suchen";
-App::$strings["Find"] = "Finde";
-App::$strings["Image uploaded but image cropping failed."] = "Bild hochgeladen, aber das Zurechtschneiden schlug fehl.";
-App::$strings["Cover Photos"] = "Cover Foto";
-App::$strings["Image resize failed."] = "Bild-Anpassung fehlgeschlagen.";
-App::$strings["Unable to process image"] = "Kann Bild nicht verarbeiten";
-App::$strings["Image upload failed."] = "Hochladen des Bilds fehlgeschlagen.";
-App::$strings["Unable to process image."] = "Kann Bild nicht verarbeiten.";
-App::$strings["female"] = "weiblich";
-App::$strings["%1\$s updated her %2\$s"] = "%1\$s hat ihr %2\$s aktualisiert";
-App::$strings["male"] = "männlich";
-App::$strings["%1\$s updated his %2\$s"] = "%1\$s hat sein %2\$s aktualisiert";
-App::$strings["%1\$s updated their %2\$s"] = "%1\$s hat sein/ihr %2\$s aktualisiert";
-App::$strings["cover photo"] = "Cover Foto";
-App::$strings["Photo not available."] = "Foto nicht verfügbar.";
-App::$strings["Upload File:"] = "Datei hochladen:";
-App::$strings["Select a profile:"] = "Wähle ein Profil:";
-App::$strings["Upload Cover Photo"] = "Cover Foto hochladen";
-App::$strings["or"] = "oder";
-App::$strings["skip this step"] = "diesen Schritt überspringen";
-App::$strings["select a photo from your photo albums"] = "ein Foto aus meinen Fotoalben";
-App::$strings["Crop Image"] = "Bild zuschneiden";
-App::$strings["Please adjust the image cropping for optimum viewing."] = "Bitte schneide das Bild für eine optimale Anzeige passend zu.";
-App::$strings["Done Editing"] = "Bearbeitung fertigstellen";
+App::$strings["Queue Statistics"] = "Warteschlangenstatistiken";
+App::$strings["Total Entries"] = "Einträge insgesamt";
+App::$strings["Priority"] = "Priorität";
+App::$strings["Destination URL"] = "Ziel-URL";
+App::$strings["Mark hub permanently offline"] = "Hub als permanent offline markieren";
+App::$strings["Empty queue for this hub"] = "Warteschlange für diesen Hub leeren";
+App::$strings["Last known contact"] = "Letzter Kontakt";
App::$strings["Off"] = "Aus";
App::$strings["On"] = "An";
App::$strings["Lock feature %s"] = "Blockiere die Funktion %s";
App::$strings["Manage Additional Features"] = "Zusätzliche Funktionen verwalten";
-App::$strings["Log settings updated."] = "Protokoll-Einstellungen aktualisiert.";
-App::$strings["Administration"] = "Administration";
-App::$strings["Logs"] = "Protokolle";
-App::$strings["Clear"] = "Leeren";
-App::$strings["Debugging"] = "Debugging";
-App::$strings["Log file"] = "Protokolldatei";
-App::$strings["Must be writable by web server. Relative to your top-level webserver directory."] = "Muss für den Web-Server schreibbar sein. Relativ zum Hubzilla-Stammverzeichnis.";
-App::$strings["Log level"] = "Protokollstufe";
+App::$strings["Update has been marked successful"] = "Update wurde als erfolgreich markiert";
+App::$strings["Executing %s failed. Check system logs."] = "Ausführen von %s fehlgeschlagen. Überprüfe die Systemprotokolle.";
+App::$strings["Update %s was successfully applied."] = "Update %s wurde erfolgreich ausgeführt.";
+App::$strings["Update %s did not return a status. Unknown if it succeeded."] = "Update %s lieferte keinen Rückgabewert. Erfolg unbekannt.";
+App::$strings["Update function %s could not be found."] = "Update-Funktion %s konnte nicht gefunden werden.";
+App::$strings["No failed updates."] = "Keine fehlgeschlagenen Aktualisierungen.";
+App::$strings["Failed Updates"] = "Fehlgeschlagene Aktualisierungen";
+App::$strings["Mark success (if update was manually applied)"] = "Als erfolgreich markieren (wenn das Update manuell ausgeführt wurde)";
+App::$strings["Attempt to execute this update step automatically"] = "Versuche, diesen Updateschritt automatisch auszuführen";
App::$strings["Item not found."] = "Element nicht gefunden.";
App::$strings["Plugin %s disabled."] = "Plug-In %s deaktiviert.";
App::$strings["Plugin %s enabled."] = "Plug-In %s aktiviert.";
App::$strings["Disable"] = "Deaktivieren";
App::$strings["Enable"] = "Aktivieren";
+App::$strings["Administration"] = "Administration";
App::$strings["Plugins"] = "Plug-Ins";
App::$strings["Toggle"] = "Umschalten";
App::$strings["Settings"] = "Einstellungen";
@@ -328,75 +430,11 @@ App::$strings["(optional)"] = "(optional)";
App::$strings["Download Plugin Repo"] = "Plugin-Repository herunterladen";
App::$strings["Install new repo"] = "Neues Repository installieren";
App::$strings["Install"] = "Installieren";
-App::$strings["Cancel"] = "Abbrechen";
App::$strings["Manage Repos"] = "Repositorien verwalten";
App::$strings["Installed Plugin Repositories"] = "Installierte Plugin-Repositorien";
App::$strings["Install a New Plugin Repository"] = "Ein neues Plugin-Repository installieren";
-App::$strings["Update"] = "Aktualisieren";
App::$strings["Switch branch"] = "Zweig/Branch wechseln";
App::$strings["Remove"] = "Entfernen";
-App::$strings["New Profile Field"] = "Neues Profilfeld";
-App::$strings["Field nickname"] = "Kurzname für das Feld";
-App::$strings["System name of field"] = "Systemname des Feldes";
-App::$strings["Input type"] = "Art des Inhalts";
-App::$strings["Field Name"] = "Feldname";
-App::$strings["Label on profile pages"] = "Bezeichnung auf Profilseiten";
-App::$strings["Help text"] = "Hilfetext";
-App::$strings["Additional info (optional)"] = "Zusätzliche Informationen (optional)";
-App::$strings["Field definition not found"] = "Feld-Definition nicht gefunden";
-App::$strings["Edit Profile Field"] = "Profilfeld bearbeiten";
-App::$strings["Profile Fields"] = "Profil Felder";
-App::$strings["Basic Profile Fields"] = "Notwendige Profil Felder";
-App::$strings["Advanced Profile Fields"] = "Erweiterte Profil Felder";
-App::$strings["(In addition to basic fields)"] = "(zusätzlich zu notwendige Felder)";
-App::$strings["All available fields"] = "Alle verfügbaren Felder";
-App::$strings["Custom Fields"] = "Benutzerdefinierte Felder";
-App::$strings["Create Custom Field"] = "Erstelle benutzerdefiniertes Feld";
-App::$strings["Queue Statistics"] = "Warteschlangenstatistiken";
-App::$strings["Total Entries"] = "Einträge insgesamt";
-App::$strings["Priority"] = "Priorität";
-App::$strings["Destination URL"] = "Ziel-URL";
-App::$strings["Mark hub permanently offline"] = "Hub als permanent offline markieren";
-App::$strings["Empty queue for this hub"] = "Warteschlange für diesen Hub leeren";
-App::$strings["Last known contact"] = "Letzter Kontakt";
-App::$strings["By default, unfiltered HTML is allowed in embedded media. This is inherently insecure."] = "Standardmäßig wird ungefiltertes HTML in eingebetteten Inhalten zugelassen. Das ist prinzipiell unsicher.";
-App::$strings["The recommended setting is to only allow unfiltered HTML from the following sites:"] = "Die empfohlene Einstellung ist, ungefiltertes HTML nur von den nachfolgenden Webseiten zu erlauben:";
-App::$strings["https://youtube.com/<br />https://www.youtube.com/<br />https://youtu.be/<br />https://vimeo.com/<br />https://soundcloud.com/<br />"] = "https://youtube.com/<br />https://www.youtube.com/<br />https://youtu.be/<br />https://vimeo.com/<br />https://soundcloud.com/<br />";
-App::$strings["All other embedded content will be filtered, <strong>unless</strong> embedded content from that site is explicitly blocked."] = "Alle anderen eingebetteten Inhalte werden gefiltert, <strong>es sei denn</strong>, eingebettete Inhalte von einer bestimmten Seite sind explizit blockiert.";
-App::$strings["Security"] = "Sicherheit";
-App::$strings["Block public"] = "Öffentlichen Zugriff blockieren";
-App::$strings["Check to block public access to all otherwise public personal pages on this site unless you are currently authenticated."] = "Blockiere den öffentlichen Zugriff auf alle ansonsten öffentlichen persönlichen Seiten dieser Website, sofern ein Besucher nicht angemeldet ist.";
-App::$strings["Set \"Transport Security\" HTTP header"] = "Setze den \"Transport Security\" HTTP Header";
-App::$strings["Set \"Content Security Policy\" HTTP header"] = "Setze den \"Content Security Policy\" HTTP Header";
-App::$strings["Allowed email domains"] = "Erlaubte Domains für E-Mails";
-App::$strings["Comma separated list of domains which are allowed in email addresses for registrations to this site. Wildcards are accepted. Empty to allow any domains"] = "Liste der Domains, die für E-Mail-Adressen bei der Registrierung erlaubt sind, durch Kommas getrennt. Platzhalter werden akzeptiert. Leer lassen, um alle Domains zu erlauben.";
-App::$strings["Not allowed email domains"] = "Nicht erlaubte Domains für E-Mails";
-App::$strings["Comma separated list of domains which are not allowed in email addresses for registrations to this site. Wildcards are accepted. Empty to allow any domains, unless allowed domains have been defined."] = "Domains in E-Mail-Adressen, die keine Erlaubnis erhalten, sich auf Deinem Hub zu registrieren. Mehrere Domains können durch Kommas getrennt werden. Platzhalter (*/?) sind möglich. Keine Eingabe bedeutet keine Einschränkung, unabhängig davon, ob unter erlaubte Domains etwas eingegeben wurde.";
-App::$strings["Allow communications only from these sites"] = "Kommunikation nur von diesen Seiten erlauben";
-App::$strings["One site per line. Leave empty to allow communication from anywhere by default"] = "Ein Eintrag pro Zeile. Lasse das Feld leer, um Kommunikation grundlegend von überall her zu erlauben.";
-App::$strings["Block communications from these sites"] = "Kommunikation von diesen Seiten blockieren";
-App::$strings["Allow communications only from these channels"] = "Kommunikation nur von diesen Kanälen erlauben";
-App::$strings["One channel (hash) per line. Leave empty to allow from any channel by default"] = "Ein Kanal (hash) pro Zeile. Leerlassen um jeden Kanal zuzulassen. ";
-App::$strings["Block communications from these channels"] = "Kommunikation von folgenden Kanälen blockieren";
-App::$strings["Only allow embeds from secure (SSL) websites and links."] = "Erlaube Einbettungen nur von sicheren (SSL) Webseiten und Links.";
-App::$strings["Allow unfiltered embedded HTML content only from these domains"] = "Erlaube Einbettung von Inhalten mit ungefiltertem HTML nur von diesen Domains";
-App::$strings["One site per line. By default embedded content is filtered."] = "Eine Website/Domain pro Zeile. Standardmäßig wird eingebetteter Inhalt gefiltert.";
-App::$strings["Block embedded HTML from these domains"] = "Eingebettete HTML Inhalte von diesen Seiten blockieren";
-App::$strings["Theme settings updated."] = "Theme-Einstellungen aktualisiert.";
-App::$strings["No themes found."] = "Keine Theme gefunden.";
-App::$strings["Screenshot"] = "Bildschirmfoto";
-App::$strings["Themes"] = "Themes";
-App::$strings["[Experimental]"] = "[Experimentell]";
-App::$strings["[Unsupported]"] = "[Nicht unterstützt]";
-App::$strings["Password changed for account %d."] = "Passwort für Konto %d geändert.";
-App::$strings["Account settings updated."] = "Kontoeinstellungen aktualisiert.";
-App::$strings["Account not found."] = "Konto nicht gefunden.";
-App::$strings["Account Edit"] = "Kontobearbeitung";
-App::$strings["New Password"] = "Neues Passwort";
-App::$strings["New Password again"] = "Neues Passwort wiederholen";
-App::$strings["Technical skill level"] = "Technische Qualifikationsstufe";
-App::$strings["Account language (for emails)"] = "Kontosprache (für E-Mails)";
-App::$strings["Service class"] = "Dienstklasse";
App::$strings["%s account blocked/unblocked"] = array(
0 => "%s Konto blockiert/freigegeben",
1 => "%s Konten blockiert/freigegeben",
@@ -413,9 +451,11 @@ App::$strings["Accounts"] = "Konten";
App::$strings["select all"] = "Alle auswählen";
App::$strings["Registrations waiting for confirm"] = "Registrierungen warten auf Bestätigung";
App::$strings["Request date"] = "Antragsdatum";
-App::$strings["Email"] = "E-Mail";
App::$strings["No registrations."] = "Keine Registrierungen.";
+App::$strings["Approve"] = "Genehmigen";
App::$strings["Deny"] = "Verweigern";
+App::$strings["Block"] = "Blockieren";
+App::$strings["Unblock"] = "Freigeben";
App::$strings["ID"] = "ID";
App::$strings["All Channels"] = "Alle Kanäle";
App::$strings["Register date"] = "Registrierungs-Datum";
@@ -424,6 +464,13 @@ App::$strings["Expires"] = "Verfällt";
App::$strings["Service Class"] = "Service-Klasse";
App::$strings["Selected accounts will be deleted!\\n\\nEverything these accounts had posted on this site will be permanently deleted!\\n\\nAre you sure?"] = "Die ausgewählten Konten werden gelöscht!\\n\\nAlles, was diese Konten auf diesem Hub veröffentlicht haben, wird endgültig gelöscht werden!\\n\\nBist du dir sicher?";
App::$strings["The account {0} will be deleted!\\n\\nEverything this account has posted on this site will be permanently deleted!\\n\\nAre you sure?"] = "Das Konto {0} wird gelöscht!\\n\\nAlles, was dieses Konto auf diesem Hub veröffentlicht hat, wird endgültig gelöscht werden!\\n\\nBist Du sicher?";
+App::$strings["Log settings updated."] = "Protokoll-Einstellungen aktualisiert.";
+App::$strings["Logs"] = "Protokolle";
+App::$strings["Clear"] = "Leeren";
+App::$strings["Debugging"] = "Debugging";
+App::$strings["Log file"] = "Protokolldatei";
+App::$strings["Must be writable by web server. Relative to your top-level webserver directory."] = "Muss für den Web-Server schreibbar sein. Relativ zum Hubzilla-Stammverzeichnis.";
+App::$strings["Log level"] = "Protokollstufe";
App::$strings["%s channel censored/uncensored"] = array(
0 => "%s Kanal gesperrt/freigegeben",
1 => "%s Kanäle gesperrt/freigegeben",
@@ -451,17 +498,15 @@ App::$strings["Channel"] = "Kanal";
App::$strings["UID"] = "UID";
App::$strings["Selected channels will be deleted!\\n\\nEverything that was posted in these channels on this site will be permanently deleted!\\n\\nAre you sure?"] = "Alle ausgewählten Kanäle werden gelöscht!\\n\\nAlles was von diesen Kanälen auf diesem Server geschrieben wurde, wird dauerhaft gelöscht!\\n\\nBist Du sicher?";
App::$strings["The channel {0} will be deleted!\\n\\nEverything that was posted in this channel on this site will be permanently deleted!\\n\\nAre you sure?"] = "Der Kanal {0} wird gelöscht!\\n\\nAlles was von diesem Kanal auf diesem Server geschrieben wurde, wird gelöscht!\\n\\nBist Du sicher?";
-App::$strings["Update has been marked successful"] = "Update wurde als erfolgreich markiert";
-App::$strings["Executing %s failed. Check system logs."] = "Ausführen von %s fehlgeschlagen. Überprüfe die Systemprotokolle.";
-App::$strings["Update %s was successfully applied."] = "Update %s wurde erfolgreich ausgeführt.";
-App::$strings["Update %s did not return a status. Unknown if it succeeded."] = "Update %s lieferte keinen Rückgabewert. Erfolg unbekannt.";
-App::$strings["Update function %s could not be found."] = "Update-Funktion %s konnte nicht gefunden werden.";
-App::$strings["No failed updates."] = "Keine fehlgeschlagenen Aktualisierungen.";
-App::$strings["Failed Updates"] = "Fehlgeschlagene Aktualisierungen";
-App::$strings["Mark success (if update was manually applied)"] = "Als erfolgreich markieren (wenn das Update manuell ausgeführt wurde)";
-App::$strings["Attempt to execute this update step automatically"] = "Versuche, diesen Updateschritt automatisch auszuführen";
+App::$strings["Theme settings updated."] = "Design-Einstellungen aktualisiert.";
+App::$strings["No themes found."] = "Keine Designs gefunden.";
+App::$strings["Screenshot"] = "Bildschirmfoto";
+App::$strings["Themes"] = "Designs";
+App::$strings["[Experimental]"] = "[Experimentell]";
+App::$strings["[Unsupported]"] = "[Nicht unterstützt]";
App::$strings["Site settings updated."] = "Site-Einstellungen aktualisiert.";
App::$strings["Default"] = "Standard";
+App::$strings["%s - (Incompatible)"] = "%s - (Inkompatibel)";
App::$strings["mobile"] = "mobil";
App::$strings["experimental"] = "experimentell";
App::$strings["unsupported"] = "nicht unterstützt";
@@ -470,9 +515,6 @@ App::$strings["My site is not a public server"] = "Mein Server ist kein öffentl
App::$strings["My site has paid access only"] = "Meine Seite hat nur bezahlten Zugriff";
App::$strings["My site has free access only"] = "Meine Seite hat nur freien Zugriff";
App::$strings["My site offers free accounts with optional paid upgrades"] = "Mein Server bietet kostenlose Konten mit der Möglichkeit zu bezahlten Upgrades";
-App::$strings["Basic/Minimal Social Networking"] = "Einfaches/minimales soziales Netzwerken";
-App::$strings["Standard Configuration (default)"] = "Standardkonfiguration (Standard)";
-App::$strings["Professional"] = "Professionell";
App::$strings["Beginner/Basic"] = "Anfänger/Basis";
App::$strings["Novice - not skilled but willing to learn"] = "Anfänger - unerfahren, aber bereit zu lernen";
App::$strings["Intermediate - somewhat comfortable"] = "Fortgeschritten - relativ komfortabel";
@@ -480,11 +522,11 @@ App::$strings["Advanced - very comfortable"] = "Fortgeschritten - sehr komfortab
App::$strings["Expert - I can write computer code"] = "Experte - Ich kann Computercode schreiben";
App::$strings["Wizard - I probably know more than you do"] = "Zauberer - ich kann wahrscheinlich mehr als Du";
App::$strings["Site"] = "Seite";
+App::$strings["Registration"] = "Registrierung";
App::$strings["File upload"] = "Dateiupload";
App::$strings["Policies"] = "Richtlinien";
App::$strings["Advanced"] = "Fortgeschritten";
App::$strings["Site name"] = "Seitenname";
-App::$strings["Server Configuration/Role"] = "Serverkonfiguration/Rolle";
App::$strings["Site default technical skill level"] = "Standard-Qualifikationsstufe der Website";
App::$strings["Used to provide a member experience matched to technical comfort level"] = "Dies wird verwendet, um eine Benutzererfahrung passend zur technischen Qualifikationsstufe zu bieten.";
App::$strings["Lock the technical skill level setting"] = "Sperre die technische Qualifikationsstufe";
@@ -495,9 +537,9 @@ App::$strings["Contact information for site administrators. Displayed on sitein
App::$strings["Site Information"] = "Seiteninformationen";
App::$strings["Publicly visible description of this site. Displayed on siteinfo page. BBCode can be used here"] = "Öffentlich sichtbare Beschreibung dieses Servers. Wird auf der siteinfo-Seite angezeigt. BBCode kann hier verwendet werden.";
App::$strings["System language"] = "System-Sprache";
-App::$strings["System theme"] = "System-Theme";
-App::$strings["Default system theme - may be over-ridden by user profiles - <a href='#' id='cnftheme'>change theme settings</a>"] = "Standard-System-Theme – kann durch Nutzerprofile überschieben werden – <a href='#' id='cnftheme'>Theme-Einstellungen ändern</a>";
-App::$strings["Mobile system theme"] = "Mobile System-Theme:";
+App::$strings["System theme"] = "System-Design";
+App::$strings["Default system theme - may be over-ridden by user profiles - <a href='#' id='cnftheme'>change theme settings</a>"] = "Standard-System-Design – kann durch Nutzerprofile überschieben werden – <a href='#' id='cnftheme'>Design-Einstellungen ändern</a>";
+App::$strings["Mobile system theme"] = "System-Design für mobile Geräte:";
App::$strings["Theme for mobile devices"] = "Theme für mobile Geräte";
App::$strings["Allow Feeds as Connections"] = "Feeds als Verbindungen erlauben";
App::$strings["(Heavy system resource usage)"] = "(führt zu hoher Systemlast)";
@@ -527,6 +569,9 @@ App::$strings["Login on Homepage"] = "Log-in auf der Startseite";
App::$strings["Present a login box to visitors on the home page if no other content has been configured."] = "Zeigt Besuchern der Homepage eine Anmeldemaske, falls keine anderen Inhalte konfiguriert wurden.";
App::$strings["Enable context help"] = "Kontext-Hilfe aktivieren";
App::$strings["Display contextual help for the current page when the help button is pressed."] = "Zeigt Kontext-sensitive Hilfe für die aktuelle Seite an, wenn der Hilfe-Knopf geklickt wird.";
+App::$strings["Reply-to email address for system generated email."] = "Antwortadresse (reply-to) für Emails, die vom System generiert wurden.";
+App::$strings["Sender (From) email address for system generated email."] = "Absenderadresse (from) für Emails, die vom System generiert wurden.";
+App::$strings["Name of email sender for system generated email."] = "Name des Versenders von Emails, die vom System generiert wurden.";
App::$strings["Directory Server URL"] = "Verzeichnisserver-URL";
App::$strings["Default directory server"] = "Standard-Verzeichnisserver";
App::$strings["Proxy user"] = "Proxy Benutzer";
@@ -539,263 +584,351 @@ App::$strings["Deliveries per process"] = "Zustellungen pro Prozess";
App::$strings["Number of deliveries to attempt in a single operating system process. Adjust if necessary to tune system performance. Recommend: 1-5."] = "Anzahl der Zustellungen, die innerhalb eines einzelnen Betriebssystemprozesses versucht werden. Anpassen, falls nötig, um die System-Performance zu verbessern. Empfehlung: 1-5.";
App::$strings["Poll interval"] = "Abfrageintervall";
App::$strings["Delay background polling processes by this many seconds to reduce system load. If 0, use delivery interval."] = "Verzögere Hintergrundprozesse um diese Anzahl Sekunden, um die Systemlast zu reduzieren. Bei 0 wird das Auslieferungsintervall verwendet.";
+App::$strings["Path to ImageMagick convert program"] = "Pfad zum ImageMagick-Programm convert";
+App::$strings["If set, use this program to generate photo thumbnails for huge images ( > 4000 pixels in either dimension), otherwise memory exhaustion may occur. Example: /usr/bin/convert"] = "Wenn gesetzt, dann verwende dieses Programm zum Erzeugen von Vorschaubildern großer Fotos (>4000 Pixel in beiden Richtungen), anderenfalls kann Speicherüberlauf auftreten. Beispiel: /usr/bin/convert";
App::$strings["Maximum Load Average"] = "Maximales Load Average";
App::$strings["Maximum system load before delivery and poll processes are deferred - default 50."] = "Maximale Systemlast, bevor Verteil- und Empfangsprozesse verschoben werden – Standard 50";
App::$strings["Expiration period in days for imported (grid/network) content"] = "Setze den Zeitraum (in Tagen), ab wann importierte (aus dem Netzwerk) Inhalte ablaufen sollen";
App::$strings["0 for no expiration of imported content"] = "0 = keine Löschung importierter Inhalte";
-App::$strings["Public Hubs"] = "Öffentliche Hubs";
-App::$strings["The listed hubs allow public registration for the \$Projectname network. All hubs in the network are interlinked so membership on any of them conveys membership in the network as a whole. Some hubs may require subscription or provide tiered service plans. The hub itself <strong>may</strong> provide additional details."] = "Die hier aufgeführten Hubs sind öffentlich und erlauben die Registrierung im \$Projectname Netzwerk. Alle Hubs dieses Netzwerks sind miteinander verbunden, so dass die Mitgliedschaft auf einem Hub die Verbindung zu beliebigen Seiten und Kanälen auf anderen Hubs ermöglicht. Es könnte sein, dass einige dieser Hubs kostenpflichtig sind oder abgestufte, je nach Umfang kostenpflichtige Mitgliedschaften anbieten. Auf den Seiten der einzelnen Hubs <strong>könnten</strong> jeweils nähere Informationen dazu stehen.";
-App::$strings["Hub URL"] = "Hub-URL";
-App::$strings["Access Type"] = "Zugriffstyp";
-App::$strings["Registration Policy"] = "Registrierungsrichtlinien";
-App::$strings["Stats"] = "Statistiken";
-App::$strings["Software"] = "Software";
-App::$strings["Ratings"] = "Bewertungen";
-App::$strings["Rate"] = "Bewerten";
-App::$strings["View"] = "Ansicht";
-App::$strings["Item not found"] = "Element nicht gefunden";
-App::$strings["Layout Name"] = "Layout-Name";
-App::$strings["Layout Description (Optional)"] = "Layout-Beschreibung (optional)";
-App::$strings["Edit Layout"] = "Layout bearbeiten";
-App::$strings["Page link"] = "Seiten-Link";
-App::$strings["Insert web link"] = "Link einfügen";
-App::$strings["Edit Webpage"] = "Webseite bearbeiten";
-App::$strings["Photos"] = "Fotos";
-App::$strings["You must be logged in to see this page."] = "Du musst angemeldet sein, um diese Seite betrachten zu können.";
-App::$strings["Posts and comments"] = "Beiträge und Kommentare";
-App::$strings["Only posts"] = "Nur Beiträge";
-App::$strings["Insufficient permissions. Request redirected to profile page."] = "Unzureichende Zugriffsrechte. Die Anfrage wurde zur Profil-Seite umgeleitet.";
-App::$strings["No such group"] = "Gruppe nicht gefunden";
-App::$strings["No such channel"] = "Kanal nicht gefunden";
-App::$strings["forum"] = "Forum";
-App::$strings["Search Results For:"] = "Suchergebnisse für:";
-App::$strings["Privacy group is empty"] = "Gruppe ist leer";
-App::$strings["Privacy group: "] = "Gruppe:";
-App::$strings["Invalid connection."] = "Ungültige Verbindung.";
-App::$strings["Unable to update menu."] = "Kann Menü nicht aktualisieren.";
-App::$strings["Unable to create menu."] = "Kann Menü nicht erstellen.";
-App::$strings["Menu Name"] = "Name des Menüs";
-App::$strings["Unique name (not visible on webpage) - required"] = "Eindeutiger Name (nicht sichtbar auf der Webseite) – erforderlich";
-App::$strings["Menu Title"] = "Menütitel";
-App::$strings["Visible on webpage - leave empty for no title"] = "Sichtbar auf der Webseite – für keinen Titel leer lassen";
-App::$strings["Allow Bookmarks"] = "Lesezeichen erlauben";
-App::$strings["Menu may be used to store saved bookmarks"] = "Im Menü können gespeicherte Lesezeichen abgelegt werden";
-App::$strings["Submit and proceed"] = "Absenden und fortfahren";
-App::$strings["Menus"] = "Menüs";
-App::$strings["Created"] = "Erstellt";
-App::$strings["Edited"] = "Geändert";
-App::$strings["Bookmarks allowed"] = "Lesezeichen erlaubt";
-App::$strings["Delete this menu"] = "Lösche dieses Menü";
-App::$strings["Edit menu contents"] = "Bearbeite Menü Inhalte";
-App::$strings["Edit this menu"] = "Dieses Menü bearbeiten";
-App::$strings["Menu could not be deleted."] = "Menü konnte nicht gelöscht werden.";
-App::$strings["Menu not found."] = "Menü nicht gefunden";
-App::$strings["Edit Menu"] = "Menü bearbeiten";
-App::$strings["Add or remove entries to this menu"] = "Einträge zu diesem Menü hinzufügen oder entfernen";
-App::$strings["Menu name"] = "Menü Name";
-App::$strings["Must be unique, only seen by you"] = "Muss eindeutig sein, ist aber nur für Dich sichtbar";
-App::$strings["Menu title"] = "Menü Titel";
-App::$strings["Menu title as seen by others"] = "Menü Titel wie er von anderen gesehen wird";
-App::$strings["Allow bookmarks"] = "Erlaube Lesezeichen";
-App::$strings["Not found."] = "Nicht gefunden.";
-App::$strings["App installed."] = "App installiert.";
-App::$strings["Malformed app."] = "Fehlerhafte App.";
-App::$strings["Embed code"] = "Code einbetten";
-App::$strings["Edit App"] = "App bearbeiten";
-App::$strings["Create App"] = "App erstellen";
-App::$strings["Name of app"] = "Name der App";
-App::$strings["Required"] = "Benötigt";
-App::$strings["Location (URL) of app"] = "Ort (URL) der App";
-App::$strings["Description"] = "Beschreibung";
-App::$strings["Photo icon URL"] = "URL zum Icon";
-App::$strings["80 x 80 pixels - optional"] = "80 x 80 Pixel – optional";
-App::$strings["Categories (optional, comma separated list)"] = "Kategorien (optional, kommagetrennte Liste)";
-App::$strings["Version ID"] = "Versions-ID";
-App::$strings["Price of app"] = "Preis der App";
-App::$strings["Location (URL) to purchase app"] = "Ort (URL), um die App zu kaufen";
-App::$strings["Edit post"] = "Bearbeite Beitrag";
-App::$strings["Documentation Search"] = "Suche in der Dokumentation";
-App::$strings["\$Projectname Documentation"] = "\$Projectname-Dokumentation";
-App::$strings["Share content from Firefox to \$Projectname"] = "Inhalte von Firefox nach \$Projectname teilen";
-App::$strings["Activate the Firefox \$Projectname provider"] = "Aktiviert den \$Projectname-Provider für firefox";
-App::$strings["Apps"] = "Apps";
-App::$strings["\$Projectname"] = "\$Projectname";
-App::$strings["Welcome to %s"] = "Willkommen auf %s";
-App::$strings["Permission Denied."] = "Zugriff verweigert.";
-App::$strings["File not found."] = "Datei nicht gefunden.";
-App::$strings["Edit file permissions"] = "Dateiberechtigungen bearbeiten";
+App::$strings["New Profile Field"] = "Neues Profilfeld";
+App::$strings["Field nickname"] = "Kurzname für das Feld";
+App::$strings["System name of field"] = "Systemname des Feldes";
+App::$strings["Input type"] = "Art des Inhalts";
+App::$strings["Field Name"] = "Feldname";
+App::$strings["Label on profile pages"] = "Bezeichnung auf Profilseiten";
+App::$strings["Help text"] = "Hilfetext";
+App::$strings["Additional info (optional)"] = "Zusätzliche Informationen (optional)";
+App::$strings["Save"] = "Speichern";
+App::$strings["Field definition not found"] = "Feld-Definition nicht gefunden";
+App::$strings["Edit Profile Field"] = "Profilfeld bearbeiten";
+App::$strings["Profile Fields"] = "Profil Felder";
+App::$strings["Basic Profile Fields"] = "Notwendige Profil Felder";
+App::$strings["Advanced Profile Fields"] = "Erweiterte Profil Felder";
+App::$strings["(In addition to basic fields)"] = "(zusätzlich zu notwendige Felder)";
+App::$strings["All available fields"] = "Alle verfügbaren Felder";
+App::$strings["Custom Fields"] = "Benutzerdefinierte Felder";
+App::$strings["Create Custom Field"] = "Erstelle benutzerdefiniertes Feld";
+App::$strings["Password changed for account %d."] = "Passwort für Konto %d geändert.";
+App::$strings["Account settings updated."] = "Kontoeinstellungen aktualisiert.";
+App::$strings["Account not found."] = "Konto nicht gefunden.";
+App::$strings["Account Edit"] = "Kontobearbeitung";
+App::$strings["New Password"] = "Neues Passwort";
+App::$strings["New Password again"] = "Neues Passwort wiederholen";
+App::$strings["Technical skill level"] = "Technische Qualifikationsstufe";
+App::$strings["Account language (for emails)"] = "Kontosprache (für E-Mails)";
+App::$strings["Service class"] = "Dienstklasse";
+App::$strings["By default, unfiltered HTML is allowed in embedded media. This is inherently insecure."] = "Standardmäßig wird ungefiltertes HTML in eingebetteten Inhalten zugelassen. Das ist prinzipiell unsicher.";
+App::$strings["The recommended setting is to only allow unfiltered HTML from the following sites:"] = "Die empfohlene Einstellung ist, ungefiltertes HTML nur von den nachfolgenden Webseiten zu erlauben:";
+App::$strings["https://youtube.com/<br />https://www.youtube.com/<br />https://youtu.be/<br />https://vimeo.com/<br />https://soundcloud.com/<br />"] = "https://youtube.com/<br />https://www.youtube.com/<br />https://youtu.be/<br />https://vimeo.com/<br />https://soundcloud.com/<br />";
+App::$strings["All other embedded content will be filtered, <strong>unless</strong> embedded content from that site is explicitly blocked."] = "Alle anderen eingebetteten Inhalte werden gefiltert, <strong>es sei denn</strong>, eingebettete Inhalte von einer bestimmten Seite sind explizit blockiert.";
+App::$strings["Security"] = "Sicherheit";
+App::$strings["Block public"] = "Öffentlichen Zugriff blockieren";
+App::$strings["Check to block public access to all otherwise public personal pages on this site unless you are currently authenticated."] = "Blockiere den öffentlichen Zugriff auf alle ansonsten öffentlichen persönlichen Seiten dieser Website, sofern ein Besucher nicht angemeldet ist.";
+App::$strings["Set \"Transport Security\" HTTP header"] = "Setze den \"Transport Security\" HTTP Header";
+App::$strings["Set \"Content Security Policy\" HTTP header"] = "Setze den \"Content Security Policy\" HTTP Header";
+App::$strings["Allowed email domains"] = "Erlaubte Domains für E-Mails";
+App::$strings["Comma separated list of domains which are allowed in email addresses for registrations to this site. Wildcards are accepted. Empty to allow any domains"] = "Liste der Domains, die für E-Mail-Adressen bei der Registrierung erlaubt sind, durch Kommas getrennt. Platzhalter werden akzeptiert. Leer lassen, um alle Domains zu erlauben.";
+App::$strings["Not allowed email domains"] = "Nicht erlaubte Domains für E-Mails";
+App::$strings["Comma separated list of domains which are not allowed in email addresses for registrations to this site. Wildcards are accepted. Empty to allow any domains, unless allowed domains have been defined."] = "Domains in E-Mail-Adressen, die keine Erlaubnis erhalten, sich auf Deinem Hub zu registrieren. Mehrere Domains können durch Kommas getrennt werden. Platzhalter (*/?) sind möglich. Keine Eingabe bedeutet keine Einschränkung, unabhängig davon, ob unter erlaubte Domains etwas eingegeben wurde.";
+App::$strings["Allow communications only from these sites"] = "Kommunikation nur von diesen Servern/Domains erlauben";
+App::$strings["One site per line. Leave empty to allow communication from anywhere by default"] = "Ein Eintrag pro Zeile. Lasse das Feld leer, um Kommunikation grundlegend von überall her zu erlauben.";
+App::$strings["Block communications from these sites"] = "Kommunikation von diesen Servern/Domains blockieren";
+App::$strings["Allow communications only from these channels"] = "Kommunikation nur von diesen Kanälen erlauben";
+App::$strings["One channel (hash) per line. Leave empty to allow from any channel by default"] = "Ein Kanal (hash) pro Zeile. Leerlassen um jeden Kanal zuzulassen. ";
+App::$strings["Block communications from these channels"] = "Kommunikation von folgenden Kanälen blockieren";
+App::$strings["Only allow embeds from secure (SSL) websites and links."] = "Erlaube Einbettungen nur von sicheren (SSL) Webseiten und Links.";
+App::$strings["Allow unfiltered embedded HTML content only from these domains"] = "Erlaube Einbettung von Inhalten mit ungefiltertem HTML nur von diesen Domains";
+App::$strings["One site per line. By default embedded content is filtered."] = "Eine Website/Domain pro Zeile. Standardmäßig wird eingebetteter Inhalt gefiltert.";
+App::$strings["Block embedded HTML from these domains"] = "Eingebettete HTML Inhalte von diesen Servern/Domains blockieren";
+App::$strings["Remote privacy information not available."] = "Privatsphäre-Einstellungen anderer Nutzer sind nicht verfügbar.";
+App::$strings["Visible to:"] = "Sichtbar für:";
+App::$strings["__ctx:acl__ Profile"] = "Profil";
+App::$strings["Comment approved"] = "Kommentar bestätigt";
+App::$strings["Comment deleted"] = "Kommentar gelöscht";
+App::$strings["Permission category saved."] = "Berechtigungsrolle gespeichert.";
+App::$strings["Use this form to create permission rules for various classes of people or connections."] = "Verwende dieses Formular, um Berechtigungsrollen für verschiedene Gruppen von Personen oder Verbindungen zu erstellen.";
+App::$strings["Permission Categories"] = "Berechtigungsrollen";
+App::$strings["Permission Name"] = "Name der Berechtigungsrolle";
+App::$strings["My Settings"] = "Meine Einstellungen";
+App::$strings["inherited"] = "geerbt";
+App::$strings["Individual Permissions"] = "Individuelle Zugriffsrechte";
+App::$strings["Some permissions may be inherited from your channel's <a href=\"settings\"><strong>privacy settings</strong></a>, which have higher priority than individual settings. You can <strong>not</strong> change those settings here."] = "Einige Berechtigungen werden möglicherweise von den globalen <a href=\"settings\">Sicherheits- und Privatsphäre-Einstellungen</a> dieses Kanals vererbt. Diese haben eine höhere Priorität als die Einstellungen an der Verbindung und können hier nicht verändert werden.";
+App::$strings["Friends"] = "Freunde";
+App::$strings["Settings updated."] = "Einstellungen aktualisiert.";
+App::$strings["Nobody except yourself"] = "Niemand außer Dir selbst";
+App::$strings["Only those you specifically allow"] = "Nur die, denen Du es explizit erlaubst";
+App::$strings["Approved connections"] = "Angenommene Verbindungen";
+App::$strings["Any connections"] = "Beliebige Verbindungen";
+App::$strings["Anybody on this website"] = "Jeder auf dieser Website";
+App::$strings["Anybody in this network"] = "Alle \$Projectname-Mitglieder";
+App::$strings["Anybody authenticated"] = "Jeder authentifizierte";
+App::$strings["Anybody on the internet"] = "Jeder im Internet";
+App::$strings["Publish your default profile in the network directory"] = "Standard-Profil im Netzwerk-Verzeichnis veröffentlichen";
+App::$strings["Allow us to suggest you as a potential friend to new members?"] = "Dürfen wir Dich neuen Mitgliedern als potentiellen Kontakt vorschlagen?";
+App::$strings["or"] = "oder";
+App::$strings["Your channel address is"] = "Deine Kanal-Adresse lautet";
+App::$strings["Your files/photos are accessible via WebDAV at"] = "Deine Dateien/Fotos sind via WebDAV verfügbar auf";
+App::$strings["Channel Settings"] = "Kanal-Einstellungen";
+App::$strings["Basic Settings"] = "Grundeinstellungen";
+App::$strings["Full Name:"] = "Voller Name:";
+App::$strings["Email Address:"] = "Email Adresse:";
+App::$strings["Your Timezone:"] = "Ihre Zeitzone:";
+App::$strings["Default Post Location:"] = "Standardstandort:";
+App::$strings["Geographical location to display on your posts"] = "Geografischer Ort, der bei Deinen Beiträgen angezeigt werden soll";
+App::$strings["Use Browser Location:"] = "Standort des Browsers verwenden:";
+App::$strings["Adult Content"] = "Nicht jugendfreie Inhalte";
+App::$strings["This channel frequently or regularly publishes adult content. (Please tag any adult material and/or nudity with #NSFW)"] = "Dieser Kanal veröffentlicht regelmäßig Inhalte, die für Minderjährige ungeeignet sind. (Bitte markiere solche Inhalte mit dem Schlagwort #NSFW)";
+App::$strings["Security and Privacy Settings"] = "Sicherheits- und Datenschutz-Einstellungen";
+App::$strings["Your permissions are already configured. Click to view/adjust"] = "Deine Zugriffsrechte sind schon konfiguriert. Klicke hier, um sie zu betrachten oder zu ändern";
+App::$strings["Hide my online presence"] = "Meine Online-Präsenz verbergen";
+App::$strings["Prevents displaying in your profile that you are online"] = "Verhindert die Anzeige Deines Online-Status in deinem Profil";
+App::$strings["Simple Privacy Settings:"] = "Einfache Privatsphäre-Einstellungen";
+App::$strings["Very Public - <em>extremely permissive (should be used with caution)</em>"] = "Komplett offen – <em>extrem ungeschützt (mit großer Vorsicht verwenden!)</em>";
+App::$strings["Typical - <em>default public, privacy when desired (similar to social network permissions but with improved privacy)</em>"] = "Typisch – <em>Standard öffentlich, Privatsphäre, wo sie erwünscht ist (ähnlich den Einstellungen in sozialen Netzwerken, aber mit besser geschützter Privatsphäre)</em>";
+App::$strings["Private - <em>default private, never open or public</em>"] = "Privat – <em>Standard privat, nie offen oder öffentlich</em>";
+App::$strings["Blocked - <em>default blocked to/from everybody</em>"] = "Blockiert – <em>Alle standardmäßig blockiert</em>";
+App::$strings["Allow others to tag your posts"] = "Erlaube anderen, Deine Beiträge zu verschlagworten";
+App::$strings["Often used by the community to retro-actively flag inappropriate content"] = "Wird oft von der Community genutzt um rückwirkend anstößigen Inhalt zu markieren";
+App::$strings["Channel Permission Limits"] = "Kanal-Berechtigungslimits";
+App::$strings["Expire other channel content after this many days"] = "Den Inhalt anderer Kanäle nach dieser Anzahl Tage verfallen lassen";
+App::$strings["0 or blank to use the website limit."] = "0 oder leer lassen, um den voreingestellten Wert der Webseite zu verwenden.";
+App::$strings["This website expires after %d days."] = "Diese Webseite läuft nach %d Tagen ab.";
+App::$strings["This website does not expire imported content."] = "Diese Webseite lässt importierte Inhalte nicht verfallen.";
+App::$strings["The website limit takes precedence if lower than your limit."] = "Das Verfallslimit der Webseite hat Vorrang, wenn es niedriger als Deines hier ist.";
+App::$strings["Maximum Friend Requests/Day:"] = "Maximale Kontaktanfragen pro Tag:";
+App::$strings["May reduce spam activity"] = "Kann die Spam-Aktivität verringern";
+App::$strings["Default Privacy Group"] = "Standard-Gruppe";
+App::$strings["Use my default audience setting for the type of object published"] = "Verwende Deine eingestellte Standard-Zielgruppe des jeweiligen Inhaltstyps";
+App::$strings["Channel permissions category:"] = "Zugriffsrechte-Kategorie des Kanals:";
+App::$strings["Default Permissions Group"] = "Standard-Berechtigungsgruppe";
+App::$strings["Maximum private messages per day from unknown people:"] = "Maximale Anzahl privater Nachrichten pro Tag von unbekannten Leuten:";
+App::$strings["Useful to reduce spamming"] = "Nützlich, um Spam zu verringern";
+App::$strings["Notification Settings"] = "Benachrichtigungs-Einstellungen";
+App::$strings["By default post a status message when:"] = "Sende standardmäßig Status-Nachrichten, wenn:";
+App::$strings["accepting a friend request"] = "Du eine Verbindungsanfrage annimmst";
+App::$strings["joining a forum/community"] = "Du einem Forum beitrittst";
+App::$strings["making an <em>interesting</em> profile change"] = "Du eine <em>interessante</em> Änderung an Deinem Profil vornimmst";
+App::$strings["Send a notification email when:"] = "Eine E-Mail-Benachrichtigung senden, wenn:";
+App::$strings["You receive a connection request"] = "Du eine Verbindungsanfrage erhältst";
+App::$strings["Your connections are confirmed"] = "Eine Verbindung bestätigt wurde";
+App::$strings["Someone writes on your profile wall"] = "Jemand auf Deine Pinnwand schreibt";
+App::$strings["Someone writes a followup comment"] = "Jemand einen Beitrag kommentiert";
+App::$strings["You receive a private message"] = "Du eine private Nachricht erhältst";
+App::$strings["You receive a friend suggestion"] = "Du einen Kontaktvorschlag erhältst";
+App::$strings["You are tagged in a post"] = "Du in einem Beitrag erwähnt wurdest";
+App::$strings["You are poked/prodded/etc. in a post"] = "Du in einem Beitrag angestupst/geknufft/o.ä. wurdest";
+App::$strings["Someone likes your post/comment"] = "Jemand mag Ihren Beitrag/Kommentar";
+App::$strings["Show visual notifications including:"] = "Visuelle Benachrichtigungen anzeigen für:";
+App::$strings["Unseen grid activity"] = "Ungesehene Netzwerk-Aktivität";
+App::$strings["Unseen channel activity"] = "Ungesehene Kanal-Aktivität";
+App::$strings["Unseen private messages"] = "Ungelesene persönliche Nachrichten";
+App::$strings["Recommended"] = "Empfohlen";
+App::$strings["Upcoming events"] = "Baldige Termine";
+App::$strings["Events today"] = "Heutige Termine";
+App::$strings["Upcoming birthdays"] = "Baldige Geburtstage";
+App::$strings["Not available in all themes"] = "Nicht in allen Designs verfügbar";
+App::$strings["System (personal) notifications"] = "System – (persönliche) Benachrichtigungen";
+App::$strings["System info messages"] = "System – Info-Nachrichten";
+App::$strings["System critical alerts"] = "System – kritische Warnungen";
+App::$strings["New connections"] = "Neue Verbindungen";
+App::$strings["System Registrations"] = "System – Registrierungen";
+App::$strings["Unseen shared files"] = "Ungesehene geteilte Dateien";
+App::$strings["Unseen public activity"] = "Ungesehene öffentliche Aktivität";
+App::$strings["Also show new wall posts, private messages and connections under Notices"] = "Neue Pinnwand-Nachrichten, private Nachrichten und Verbindungen unter Benachrichtigungen anzeigen";
+App::$strings["Notify me of events this many days in advance"] = "Benachrichtige mich zu Terminen so viele Tage im Voraus";
+App::$strings["Must be greater than 0"] = "Muss größer als 0 sein";
+App::$strings["Advanced Account/Page Type Settings"] = "Erweiterte Account- und Seitenart-Einstellungen";
+App::$strings["Change the behaviour of this account for special situations"] = "Ändere das Verhalten dieses Accounts unter speziellen Umständen";
+App::$strings["Miscellaneous Settings"] = "Sonstige Einstellungen";
+App::$strings["Default photo upload folder"] = "Voreingestellter Ordner für hochgeladene Fotos";
+App::$strings["%Y - current year, %m - current month"] = "%Y - aktuelles Jahr, %m - aktueller Monat";
+App::$strings["Default file upload folder"] = "Voreingestellter Ordner für hochgeladene Dateien";
+App::$strings["Personal menu to display in your channel pages"] = "Eigenes Menü zur Anzeige auf den Seiten deines Kanals";
+App::$strings["Remove this channel."] = "Diesen Kanal löschen";
+App::$strings["Firefox Share \$Projectname provider"] = "\$Projectname-Provider für Firefox Share";
+App::$strings["Start calendar week on Monday"] = "Beginne die kalendarische Woche am Montag";
+App::$strings["Additional Features"] = "Zusätzliche Funktionen";
+App::$strings["This channel is limited to %d tokens"] = "Dieser Kanal ist auf %d Token begrenzt";
+App::$strings["Name and Password are required."] = "Name und Passwort sind erforderlich.";
+App::$strings["Token saved."] = "Token gespeichert.";
+App::$strings["Use this form to create temporary access identifiers to share things with non-members. These identities may be used in Access Control Lists and visitors may login using these credentials to access private content."] = "Mit diesem Formular kannst Du temporäre Zugangs-IDs anlegen, um Inhalte mit Nicht-Mitgliedern zu teilen. Die IDs können in Berechtigungslisten (ACLs) verwendet werden, und Besucher können sich damit einloggen, um auf private Inhalte zuzugreifen.";
+App::$strings["You may also provide <em>dropbox</em> style access links to friends and associates by adding the Login Password to any specific site URL as shown. Examples:"] = "Du kannst auch <em>Dropbox</em>-ähnliche Zugriffslinks an Andere weitergeben, indem du das Login-Passwort an eine entsprechende URL anhängst wie nachfolgend gezeigt. Beispiele:";
+App::$strings["Guest Access Tokens"] = "Gastzugangstoken";
+App::$strings["Login Name"] = "Anmeldename";
+App::$strings["Login Password"] = "Anmeldepasswort";
+App::$strings["Expires (yyyy-mm-dd)"] = "Läuft ab (jjjj-mm-tt)";
+App::$strings["Their Settings"] = "Deren Einstellungen";
+App::$strings["Not valid email."] = "Keine gültige E-Mail Adresse.";
+App::$strings["Protected email address. Cannot change to that email."] = "Geschützte E-Mail Adresse. Diese kann nicht verändert werden.";
+App::$strings["System failure storing new email. Please try again."] = "Systemfehler während des Speicherns der neuen Mail. Bitte versuche es noch einmal.";
+App::$strings["Technical skill level updated"] = "Technische Qualifikationsstufe aktualisiert";
+App::$strings["Password verification failed."] = "Passwortüberprüfung fehlgeschlagen.";
+App::$strings["Passwords do not match. Password unchanged."] = "Kennwörter stimmen nicht überein. Kennwort nicht verändert.";
+App::$strings["Empty passwords are not allowed. Password unchanged."] = "Leere Kennwörter sind nicht erlaubt. Kennwort nicht verändert.";
+App::$strings["Password changed."] = "Kennwort geändert.";
+App::$strings["Password update failed. Please try again."] = "Kennwortänderung fehlgeschlagen. Bitte versuche es noch einmal.";
+App::$strings["Account Settings"] = "Konto-Einstellungen";
+App::$strings["Current Password"] = "Aktuelles Passwort";
+App::$strings["Enter New Password"] = "Gib ein neues Passwort ein";
+App::$strings["Confirm New Password"] = "Bestätige das neue Passwort";
+App::$strings["Leave password fields blank unless changing"] = "Lasse die Passwort-Felder leer, außer Du möchtest das Passwort ändern";
+App::$strings["Your technical skill level"] = "Deine technische Qualifikationsstufe";
+App::$strings["Used to provide a member experience matched to your comfort level"] = "Dies wird verwendet, um Dir eine Benutzererfahrung passend zu Deiner technischen Qualifikationsstufe zu bieten.";
+App::$strings["Remove Account"] = "Konto entfernen";
+App::$strings["Remove this account including all its channels"] = "Dieses Konto inklusive all seiner Kanäle löschen";
+App::$strings["Affinity Slider settings updated."] = "Die Beziehungsgrad-Schieberegler-Einstellungen wurden aktualisiert.";
+App::$strings["No feature settings configured"] = "Keine Funktions-Einstellungen konfiguriert";
+App::$strings["Default maximum affinity level"] = "Voreinstellung für maximalen Beziehungsgrad";
+App::$strings["Default minimum affinity level"] = "Voreinstellung für minimalen Beziehungsgrad";
+App::$strings["Affinity Slider Settings"] = "Beziehungsgrad-Schieberegler-Einstellungen";
+App::$strings["Feature/Addon Settings"] = "Funktions-/Addon-Einstellungen";
+App::$strings["No special theme for mobile devices"] = "Kein spezielles Design für mobile Geräte";
+App::$strings["%s - (Experimental)"] = "%s – (experimentell)";
+App::$strings["Display Settings"] = "Anzeige-Einstellungen";
+App::$strings["Theme Settings"] = "Design-Einstellungen";
+App::$strings["Custom Theme Settings"] = "Benutzerdefinierte Design-Einstellungen";
+App::$strings["Content Settings"] = "Inhaltseinstellungen";
+App::$strings["Display Theme:"] = "Anzeige-Design:";
+App::$strings["Select scheme"] = "Schema wählen";
+App::$strings["Mobile Theme:"] = "Design für mobile Geräte:";
+App::$strings["Preload images before rendering the page"] = "Bilder im voraus laden, bevor die Seite angezeigt wird";
+App::$strings["The subjective page load time will be longer but the page will be ready when displayed"] = "Die empfundene Ladezeit wird sich erhöhen, aber dafür ist das Layout stabil, sobald eine Seite angezeigt wird";
+App::$strings["Enable user zoom on mobile devices"] = "Zoom auf Mobilgeräten aktivieren";
+App::$strings["Update browser every xx seconds"] = "Browser alle xx Sekunden aktualisieren";
+App::$strings["Minimum of 10 seconds, no maximum"] = "Minimum 10 Sekunden, kein Maximum";
+App::$strings["Maximum number of conversations to load at any time:"] = "Maximale Anzahl von Unterhaltungen, die auf einmal geladen werden sollen:";
+App::$strings["Maximum of 100 items"] = "Maximum: 100 Beiträge";
+App::$strings["Show emoticons (smilies) as images"] = "Emoticons (Smilies) als Bilder anzeigen";
+App::$strings["Manual conversation updates"] = "Manuelle Konversationsaktualisierung";
+App::$strings["Default is on, turning this off may increase screen jumping"] = "Voreinstellung ist An, dies abzuschalten kann das unerwartete Springen der Seitenanzeige erhöhen.";
+App::$strings["Link post titles to source"] = "Beitragstitel zum Originalbeitrag verlinken";
+App::$strings["System Page Layout Editor - (advanced)"] = "System-Seitenlayout-Editor (für Experten)";
+App::$strings["Use blog/list mode on channel page"] = "Blog-/Listenmodus auf der Kanalseite verwenden";
+App::$strings["(comments displayed separately)"] = "(Kommentare werden separat angezeigt)";
+App::$strings["Use blog/list mode on grid page"] = "Blog-/Listenmodus auf der Netzwerkseite verwenden";
+App::$strings["Channel page max height of content (in pixels)"] = "Maximale Höhe von Beitragsblöcken auf der Kanalseite (in Pixeln)";
+App::$strings["click to expand content exceeding this height"] = "Blöcke, deren Inhalt diese Höhe überschreitet, können per Klick vergrößert werden.";
+App::$strings["Grid page max height of content (in pixels)"] = "Maximale Höhe (in Pixel) des Inhalts der Netzwerkseite";
+App::$strings["Name is required"] = "Name ist erforderlich";
+App::$strings["Key and Secret are required"] = "Schlüssel und Geheimnis werden benötigt";
+App::$strings["Add application"] = "Anwendung hinzufügen";
+App::$strings["Name of application"] = "Name der Anwendung";
+App::$strings["Consumer Key"] = "Consumer Key";
+App::$strings["Automatically generated - change if desired. Max length 20"] = "Automatisch erzeugt – ändern, falls erwünscht. Maximale Länge 20";
+App::$strings["Consumer Secret"] = "Consumer Secret";
+App::$strings["Redirect"] = "Umleitung";
+App::$strings["Redirect URI - leave blank unless your application specifically requires this"] = "Umleitungs-URl – lasse das leer, solange Deine Anwendung es nicht explizit erfordert";
+App::$strings["Icon url"] = "Symbol-URL";
+App::$strings["Optional"] = "Optional";
+App::$strings["Application not found."] = "Die Anwendung wurde nicht gefunden.";
+App::$strings["Connected Apps"] = "Verbundene Apps";
+App::$strings["Client key starts with"] = "Client Key beginnt mit";
+App::$strings["No name"] = "Kein Name";
+App::$strings["Remove authorization"] = "Authorisierung aufheben";
+App::$strings["View Photo"] = "Foto ansehen";
+App::$strings["Edit Album"] = "Album bearbeiten";
+App::$strings["Upload"] = "Hochladen";
+App::$strings["Some blurb about what to do when you're new here"] = "Ein Hinweis, was man tun kann, wenn man neu hier ist";
+App::$strings["Thing updated"] = "Sache aktualisiert";
+App::$strings["Object store: failed"] = "Speichern des Objekts fehlgeschlagen";
+App::$strings["Thing added"] = "Sache hinzugefügt";
+App::$strings["OBJ: %1\$s %2\$s %3\$s"] = "OBJ: %1\$s %2\$s %3\$s";
+App::$strings["Show Thing"] = "Sache anzeigen";
+App::$strings["item not found."] = "Eintrag nicht gefunden";
+App::$strings["Edit Thing"] = "Sache bearbeiten";
+App::$strings["Select a profile"] = "Wähle ein Profil";
+App::$strings["Post an activity"] = "Aktivitätsnachricht senden";
+App::$strings["Only sends to viewers of the applicable profile"] = "Nur an Betrachter des ausgewählten Profils senden";
+App::$strings["Name of thing e.g. something"] = "Name der Sache, z. B. irgendwas";
+App::$strings["URL of thing (optional)"] = "URL der Sache (optional)";
+App::$strings["URL for photo of thing (optional)"] = "URL eines Fotos der Sache (optional)";
App::$strings["Permissions"] = "Berechtigungen";
-App::$strings["Set/edit permissions"] = "Berechtigungen setzen/ändern";
-App::$strings["Include all files and sub folders"] = "Alle Dateien und Unterverzeichnisse einbinden";
-App::$strings["Return to file list"] = "Zurück zur Dateiliste";
-App::$strings["Copy/paste this code to attach file to a post"] = "Diesen Code kopieren und einfügen, um die Datei an einen Beitrag anzuhängen";
-App::$strings["Copy/paste this URL to link file from a web page"] = "Diese URL verwenden, um von einer Webseite aus auf die Datei zu verlinken";
-App::$strings["Share this file"] = "Diese Datei freigeben";
-App::$strings["Show URL to this file"] = "URL zu dieser Datei anzeigen";
-App::$strings["Notify your contacts about this file"] = "Meine Kontakte über diese Datei benachrichtigen";
-App::$strings["Public access denied."] = "Öffentlichen Zugriff verweigert.";
-App::$strings["%d rating"] = array(
- 0 => "%d Bewertung",
- 1 => "%d Bewertungen",
-);
-App::$strings["Gender: "] = "Geschlecht:";
-App::$strings["Status: "] = "Status:";
-App::$strings["Homepage: "] = "Webseite:";
-App::$strings["Age:"] = "Alter:";
-App::$strings["Location:"] = "Ort:";
-App::$strings["Description:"] = "Beschreibung:";
-App::$strings["Hometown:"] = "Heimatstadt:";
-App::$strings["About:"] = "Über:";
-App::$strings["Public Forum:"] = "Öffentliches Forum:";
-App::$strings["Keywords: "] = "Schlüsselwörter:";
-App::$strings["Don't suggest"] = "Nicht vorschlagen";
-App::$strings["Common connections:"] = "Gemeinsame Verbindungen:";
-App::$strings["Global Directory"] = "Globales Verzeichnis";
-App::$strings["Local Directory"] = "Lokales Verzeichnis";
-App::$strings["Finding:"] = "Ergebnisse:";
-App::$strings["Channel Suggestions"] = "Kanal-Vorschläge";
-App::$strings["next page"] = "nächste Seite";
-App::$strings["previous page"] = "vorherige Seite";
-App::$strings["Sort options"] = "Sortieroptionen";
-App::$strings["Alphabetic"] = "alphabetisch";
-App::$strings["Reverse Alphabetic"] = "Entgegengesetzt alphabetisch";
-App::$strings["Newest to Oldest"] = "Neueste zuerst";
-App::$strings["Oldest to Newest"] = "Älteste zuerst";
-App::$strings["No entries (some entries may be hidden)."] = "Keine Einträge gefunden (einige könnten versteckt sein).";
-App::$strings["Unable to locate original post."] = "Originalbeitrag nicht gefunden.";
-App::$strings["Empty post discarded."] = "Leeren Beitrag verworfen.";
-App::$strings["Executable content type not permitted to this channel."] = "Ausführbarer Content-Typ ist für diesen Kanal nicht freigegeben.";
-App::$strings["Duplicate post suppressed."] = "Doppelter Beitrag unterdrückt.";
-App::$strings["System error. Post not saved."] = "Systemfehler. Beitrag nicht gespeichert.";
-App::$strings["Unable to obtain post information from database."] = "Beitragsinformationen können nicht aus der Datenbank abgerufen werden.";
-App::$strings["You have reached your limit of %1$.0f top level posts."] = "Du hast die maximale Anzahl von %1$.0f Beiträgen erreicht.";
-App::$strings["You have reached your limit of %1$.0f webpages."] = "Du hast die maximale Anzahl von %1$.0f Webseiten erreicht.";
-App::$strings["toggle full screen mode"] = "auf Vollbildmodus umschalten";
+App::$strings["Add Thing to your Profile"] = "Die Sache Deinem Profil hinzufügen";
+App::$strings["No more system notifications."] = "Keine System-Benachrichtigungen mehr.";
+App::$strings["System Notifications"] = "System-Benachrichtigungen";
App::$strings["Channel added."] = "Kanal hinzugefügt.";
-App::$strings["Unable to lookup recipient."] = "Konnte den Empfänger nicht finden.";
-App::$strings["Unable to communicate with requested channel."] = "Die Kommunikation mit dem ausgewählten Kanal ist fehlgeschlagen.";
-App::$strings["Cannot verify requested channel."] = "Verifizierung des angeforderten Kanals fehlgeschlagen.";
-App::$strings["Selected channel has private message restrictions. Send failed."] = "Der ausgewählte Kanal hat Einschränkungen bzgl. privater Nachrichten. Senden fehlgeschlagen.";
-App::$strings["Messages"] = "Nachrichten";
-App::$strings["Message recalled."] = "Nachricht widerrufen.";
-App::$strings["Conversation removed."] = "Unterhaltung gelöscht.";
-App::$strings["Please enter a link URL:"] = "Gib eine URL ein:";
-App::$strings["Expires YYYY-MM-DD HH:MM"] = "Verfällt YYYY-MM-DD HH;MM";
-App::$strings["Requested channel is not in this network"] = "Angeforderter Kanal ist nicht in diesem Netzwerk.";
-App::$strings["Send Private Message"] = "Private Nachricht senden";
-App::$strings["To:"] = "An:";
-App::$strings["Subject:"] = "Betreff:";
-App::$strings["Your message:"] = "Deine Nachricht:";
-App::$strings["Attach file"] = "Datei anhängen";
-App::$strings["Send"] = "Absenden";
-App::$strings["Set expiration date"] = "Verfallsdatum";
-App::$strings["Encrypt text"] = "Text verschlüsseln";
-App::$strings["Delete message"] = "Nachricht löschen";
-App::$strings["Delivery report"] = "Zustellungsbericht";
-App::$strings["Recall message"] = "Nachricht widerrufen";
-App::$strings["Message has been recalled."] = "Die Nachricht wurde widerrufen.";
-App::$strings["Delete Conversation"] = "Unterhaltung löschen";
-App::$strings["No secure communications available. You <strong>may</strong> be able to respond from the sender's profile page."] = "Keine sichere Kommunikation verfügbar. <strong>Eventuell</strong> kannst Du auf der Profilseite des Absenders antworten.";
-App::$strings["Send Reply"] = "Antwort senden";
-App::$strings["Your message for %s (%s):"] = "Deine Nachricht für %s (%s):";
-App::$strings["webpage"] = "Webseite";
-App::$strings["block"] = "Block";
-App::$strings["layout"] = "Layout";
-App::$strings["menu"] = "Menü";
-App::$strings["%s element installed"] = "Element für %s installiert";
-App::$strings["%s element installation failed"] = "Installation des Elements %s fehlgeschlagen";
-App::$strings["Nothing to import."] = "Nichts zu importieren.";
-App::$strings["Unable to download data from old server"] = "Daten können vom alten Server nicht heruntergeladen werden";
-App::$strings["Imported file is empty."] = "Die importierte Datei ist leer.";
-App::$strings["Warning: Database versions differ by %1\$d updates."] = "Achtung: Datenbankversionen unterscheiden sich um %1\$d Aktualisierungen.";
-App::$strings["Import completed"] = "Import abgeschlossen";
-App::$strings["Import Items"] = "Beiträge importieren";
-App::$strings["Use this form to import existing posts and content from an export file."] = "Mit diesem Formular kannst Du existierende Beiträge und Inhalte aus einer Sicherungsdatei importieren.";
-App::$strings["File to Upload"] = "Hochzuladende Datei:";
-App::$strings["Total invitation limit exceeded."] = "Einladungslimit überschritten.";
-App::$strings["%s : Not a valid email address."] = "%s : Keine gültige Email Adresse.";
-App::$strings["Please join us on \$Projectname"] = "Schließe Dich uns auf \$Projectname an!";
-App::$strings["Invitation limit exceeded. Please contact your site administrator."] = "Einladungslimit überschritten. Bitte kontaktiere den Administrator Deines \$Projectname-Servers.";
-App::$strings["%s : Message delivery failed."] = "%s : Nachricht konnte nicht zugestellt werden.";
-App::$strings["%d message sent."] = array(
- 0 => "%d Nachricht gesendet.",
- 1 => "%d Nachrichten gesendet.",
-);
-App::$strings["You have no more invitations available"] = "Du hast keine weiteren verfügbare Einladungen";
-App::$strings["Send invitations"] = "Einladungen senden";
-App::$strings["Enter email addresses, one per line:"] = "Email-Adressen eintragen, eine pro Zeile:";
-App::$strings["Please join my community on \$Projectname."] = "Schließe Dich uns auf \$Projectname an!";
-App::$strings["You will need to supply this invitation code:"] = "Bitte verwende bei der Registrierung den folgenden Einladungscode:";
-App::$strings["1. Register at any \$Projectname location (they are all inter-connected)"] = "1. Registriere Dich auf einem beliebigen \$Projectname-Hub (sie sind alle miteinander verbunden)";
-App::$strings["2. Enter my \$Projectname network address into the site searchbar."] = "2. Gib meine \$Projectname-Adresse im Suchfeld ein.";
-App::$strings["or visit"] = "oder besuche";
-App::$strings["3. Click [Connect]"] = "3. Klicke auf [Verbinden]";
-App::$strings["Block Name"] = "Block-Name";
+App::$strings["Your service plan only allows %d channels."] = "Dein Vertrag erlaubt nur %d Kanäle.";
+App::$strings["No channel. Import failed."] = "Kein Kanal. Import fehlgeschlagen.";
+App::$strings["Import completed."] = "Import abgeschlossen.";
+App::$strings["You must be logged in to use this feature."] = "Du musst angemeldet sein um diese Funktion zu nutzen.";
+App::$strings["Import Channel"] = "Kanal importieren";
+App::$strings["Use this form to import an existing channel from a different server/hub. You may retrieve the channel identity from the old server/hub via the network or provide an export file."] = "Verwende dieses Formular, um einen existierenden Kanal von einem anderen Hub zu importieren. Du kannst den Kanal direkt vom bisherigen Hub über das Netzwerk oder aus einer exportierten Sicherheitskopie importieren.";
+App::$strings["Or provide the old server/hub details"] = "Oder gib die Details Deines bisherigen \$Projectname-Hubs ein";
+App::$strings["Your old identity address (xyz@example.com)"] = "Bisherige Kanal-Adresse (xyz@example.com)";
+App::$strings["Your old login email address"] = "Deine alte Login-E-Mail-Adresse";
+App::$strings["Your old login password"] = "Dein altes Passwort";
+App::$strings["For either option, please choose whether to make this hub your new primary address, or whether your old location should continue this role. You will be able to post from either location, but only one can be marked as the primary location for files, photos, and media."] = "Egal, welche Option Du wählst – bitte lege fest, ob dieser Server die neue primäre Adresse dieses Kanals sein soll, oder ob der bisherige \$Projectname-Hub diese Rolle weiterhin wahrnimmt. Du kannst von beiden Servern aus posten, aber nur einer kann der primäre Ort Deiner Dateien, Fotos und Medien sein.";
+App::$strings["Make this hub my primary location"] = "Dieser $Pojectname-Hub ist mein primärer Hub.";
+App::$strings["Move this channel (disable all previous locations)"] = "Verschiebe diesen Kanal (deaktiviere alle vorherigen Adressen/Klone)";
+App::$strings["Import a few months of posts if possible (limited by available memory"] = "Importiere die Beiträge einiger Monate, sofern möglich (beschränkt durch verfügbaren Speicher)";
+App::$strings["This process may take several minutes to complete. Please submit the form only once and leave this page open until finished."] = "Dieser Vorgang kann einige Minuten dauern. Bitte sende das Formular nur einmal ab und lasse diese Seite bis zur Fertigstellung offen.";
+App::$strings["Authentication failed."] = "Authentifizierung fehlgeschlagen.";
+App::$strings["Remote Authentication"] = "Entfernte Authentifizierung";
+App::$strings["Enter your channel address (e.g. channel@example.com)"] = "Deine Kanal-Adresse (z. B. channel@example.com)";
+App::$strings["Authenticate"] = "Authentifizieren";
+App::$strings["Channel not found."] = "Kanal nicht gefunden.";
+App::$strings["Permissions denied."] = "Berechtigung verweigert.";
+App::$strings["Import"] = "Import";
+App::$strings["Authorize application connection"] = "Zugriff für die Anwendung autorisieren";
+App::$strings["Return to your app and insert this Security Code:"] = "Gehen Sie zu Ihrer App zurück und tragen Sie diesen Sicherheitscode ein:";
+App::$strings["Please login to continue."] = "Zum Weitermachen, bitte einloggen.";
+App::$strings["Do you want to authorize this application to access your posts and contacts, and/or create new posts for you?"] = "Möchtest Du dieser Anwendung erlauben, Deine Nachrichten und Kontakte abzurufen und/oder neue Nachrichten für Dich zu erstellen?";
+App::$strings["Item not available."] = "Element nicht verfügbar.";
+App::$strings["Insert web link"] = "Link einfügen";
App::$strings["Title (optional)"] = "Titel (optional)";
App::$strings["Edit Block"] = "Block bearbeiten";
-App::$strings["Privacy group created."] = "Gruppe wurde erstellt.";
-App::$strings["Could not create privacy group."] = "Gruppe konnte nicht erstellt werden.";
-App::$strings["Privacy group not found."] = "Gruppe nicht gefunden.";
-App::$strings["Privacy group updated."] = "Gruppe wurde aktualisiert.";
-App::$strings["Create a group of channels."] = "Erstelle eine Gruppe für Kanäle.";
-App::$strings["Privacy group name: "] = "Gruppenname:";
-App::$strings["Members are visible to other channels"] = "Mitglieder sind sichtbar für andere Kanäle";
-App::$strings["Privacy group removed."] = "Gruppe wurde entfernt.";
-App::$strings["Unable to remove privacy group."] = "Gruppe konnte nicht entfernt werden.";
-App::$strings["Privacy group editor"] = "Gruppeneditor";
-App::$strings["Members"] = "Mitglieder";
-App::$strings["All Connected Channels"] = "Alle verbundenen Kanäle";
-App::$strings["Click on a channel to add or remove."] = "Wähle einen Kanal zum hinzufügen oder entfernen aus.";
-App::$strings["Invalid profile identifier."] = "Ungültiger Profil-Identifikator";
-App::$strings["Profile Visibility Editor"] = "Profil-Sichtbarkeits-Editor";
-App::$strings["Profile"] = "Profil";
-App::$strings["Click on a contact to add or remove."] = "Klicke auf einen Kontakt, um ihn hinzuzufügen oder zu entfernen.";
-App::$strings["Visible To"] = "Sichtbar für";
-App::$strings["Hub not found."] = "Server nicht gefunden.";
-App::$strings["Unable to create element."] = "Element konnte nicht erstellt werden.";
-App::$strings["Unable to update menu element."] = "Kann Menü-Element nicht aktualisieren.";
-App::$strings["Unable to add menu element."] = "Kann Menü-Bestandteil nicht hinzufügen.";
-App::$strings["Menu Item Permissions"] = "Zugriffsrechte des Menü-Elements";
-App::$strings["(click to open/close)"] = "(zum öffnen/schließen anklicken)";
-App::$strings["Link Name"] = "Name des Links";
-App::$strings["Link or Submenu Target"] = "Ziel des Links oder Untermenüs";
-App::$strings["Enter URL of the link or select a menu name to create a submenu"] = "URL des Links eingeben oder Menünamen wählen, um ein Untermenü anzulegen.";
-App::$strings["Use magic-auth if available"] = "Magic-Auth verwenden, falls verfügbar";
-App::$strings["Open link in new window"] = "Öffne Link in neuem Fenster";
-App::$strings["Order in list"] = "Reihenfolge in der Liste";
-App::$strings["Higher numbers will sink to bottom of listing"] = "Größere Nummern werden weiter unten in der Auflistung einsortiert";
-App::$strings["Submit and finish"] = "Absenden und fertigstellen";
-App::$strings["Submit and continue"] = "Absenden und fortfahren";
-App::$strings["Menu:"] = "Menü:";
-App::$strings["Link Target"] = "Ziel des Links";
-App::$strings["Edit menu"] = "Menü bearbeiten";
-App::$strings["Edit element"] = "Bestandteil bearbeiten";
-App::$strings["Drop element"] = "Bestandteil löschen";
-App::$strings["New element"] = "Neues Bestandteil";
-App::$strings["Edit this menu container"] = "Diesen Menü-Container bearbeiten";
-App::$strings["Add menu element"] = "Menüelement hinzufügen";
-App::$strings["Delete this menu item"] = "Lösche dieses Menü-Bestandteil";
-App::$strings["Edit this menu item"] = "Bearbeite dieses Menü-Bestandteil";
-App::$strings["Menu item not found."] = "Menü-Bestandteil nicht gefunden.";
-App::$strings["Menu item deleted."] = "Menü-Bestandteil gelöscht.";
-App::$strings["Menu item could not be deleted."] = "Menü-Bestandteil kann nicht gelöscht werden.";
-App::$strings["Edit Menu Element"] = "Bearbeite Menü-Bestandteil";
-App::$strings["Link text"] = "Link Text";
-App::$strings["No ratings"] = "Keine Bewertungen";
-App::$strings["Rating: "] = "Bewertung: ";
-App::$strings["Website: "] = "Webseite: ";
-App::$strings["Description: "] = "Beschreibung: ";
-App::$strings["Item not available."] = "Element nicht verfügbar.";
+App::$strings["vcard"] = "VCard";
+App::$strings["Apps"] = "Apps";
+App::$strings["Manage apps"] = "Apps verwalten";
+App::$strings["Create new app"] = "Neue App erstellen";
App::$strings["__ctx:mood__ %1\$s is %2\$s"] = "%1\$s ist %2\$s";
App::$strings["Mood"] = "Laune";
App::$strings["Set your current mood and tell your friends"] = "Wähle Deine aktuelle Stimmung und teile sie mit Deinen Freunden";
-App::$strings["No more system notifications."] = "Keine System-Benachrichtigungen mehr.";
-App::$strings["System Notifications"] = "System-Benachrichtigungen";
+App::$strings["Blocked"] = "Blockiert";
+App::$strings["Ignored"] = "Ignoriert";
+App::$strings["Hidden"] = "Versteckt";
+App::$strings["Archived/Unreachable"] = "Archiviert/Unerreichbar";
+App::$strings["New"] = "Neu";
+App::$strings["All"] = "Alle";
+App::$strings["New Connections"] = "Neue Verbindungen";
+App::$strings["Show pending (new) connections"] = "Ausstehende (neue) Verbindungsanfragen anzeigen";
+App::$strings["Show all connections"] = "Alle Verbindungen anzeigen";
+App::$strings["Only show blocked connections"] = "Nur blockierte Verbindungen anzeigen";
+App::$strings["Only show ignored connections"] = "Nur ignorierte Verbindungen anzeigen";
+App::$strings["Only show archived/unreachable connections"] = "Nur archivierte/unerreichbare Verbindungen anzeigen";
+App::$strings["Only show hidden connections"] = "Nur versteckte Verbindungen anzeigen";
+App::$strings["Pending approval"] = "Wartet auf Genehmigung";
+App::$strings["Archived"] = "Archiviert";
+App::$strings["Not connected at this location"] = "An diesem Ort nicht verbunden";
+App::$strings["%1\$s [%2\$s]"] = "%1\$s [%2\$s]";
+App::$strings["Edit connection"] = "Verbindung bearbeiten";
+App::$strings["Delete connection"] = "Verbindung löschen";
+App::$strings["Channel address"] = "Kanaladresse";
+App::$strings["Network"] = "Netzwerk";
+App::$strings["Call"] = "Anruf";
+App::$strings["Status"] = "Status";
+App::$strings["Connected"] = "Verbunden";
+App::$strings["Approve connection"] = "Verbindung genehmigen";
+App::$strings["Ignore connection"] = "Verbindung ignorieren";
+App::$strings["Ignore"] = "Ignorieren";
+App::$strings["Recent activity"] = "Kürzliche Aktivitäten";
+App::$strings["Connections"] = "Verbindungen";
+App::$strings["Search your connections"] = "Verbindungen durchsuchen";
+App::$strings["Connections search"] = "Verbindung suchen";
+App::$strings["Find"] = "Finde";
+App::$strings["item"] = "Beitrag";
+App::$strings["Source of Item"] = "Quelle des Elements";
+App::$strings["Bookmark added"] = "Lesezeichen hinzugefügt";
+App::$strings["My Bookmarks"] = "Meine Lesezeichen";
+App::$strings["My Connections Bookmarks"] = "Lesezeichen meiner Kontakte";
+App::$strings["Account removals are not allowed within 48 hours of changing the account password."] = "Das Löschen von Konten innerhalb 48 Stunden nachdem deren Passwort geändert wurde ist nicht erlaubt.";
+App::$strings["Remove This Account"] = "Dieses Konto löschen";
+App::$strings["This account and all its channels will be completely removed from the network. "] = "Dieses Konto mit all seinen Kanälen wird vollständig aus dem Netzwerk gelöscht.";
+App::$strings["Remove this account, all its channels and all its channel clones from the network"] = "Dieses Konto, all seine Kanäle sowie alle Kanal-Klone aus dem Netzwerk löschen";
+App::$strings["By default only the instances of the channels located on this hub will be removed from the network"] = "Standardmäßig werden nur die Kanalklone auf diesem \$Projectname-Hub aus dem Netzwerk entfernt";
App::$strings["Page owner information could not be retrieved."] = "Informationen über den Besitzer der Seite konnten nicht gefunden werden.";
-App::$strings["Profile Photos"] = "Profilfotos";
App::$strings["Album not found."] = "Album nicht gefunden.";
App::$strings["Delete Album"] = "Album löschen";
-App::$strings["Multiple storage folders exist with this album name, but within different directories. Please remove the desired folder or folders using the Files manager"] = "Mehrere Speicherordner mit diesem Albumnamen sind bereits vorhanden, aber in verschiedenen Verzeichnissen. Bitte entfernen Sie den oder die gewünschten Ordner mit dem Dateimanager";
App::$strings["Delete Photo"] = "Foto löschen";
App::$strings["No photos selected"] = "Keine Fotos ausgewählt";
App::$strings["Access to this item is restricted."] = "Der Zugriff auf dieses Foto ist eingeschränkt.";
@@ -807,20 +940,14 @@ App::$strings["or select an existing album (doubleclick)"] = "oder ein bereits v
App::$strings["Create a status post for this upload"] = "Einen Statusbeitrag für diesen Upload erzeugen";
App::$strings["Caption (optional):"] = "Beschriftung (optional):";
App::$strings["Description (optional):"] = "Beschreibung (optional):";
-App::$strings["Album name could not be decoded"] = "Albumname konnte nicht dekodiert werden";
-App::$strings["Contact Photos"] = "Kontakt-Bilder";
App::$strings["Show Newest First"] = "Neueste zuerst anzeigen";
App::$strings["Show Oldest First"] = "Älteste zuerst anzeigen";
-App::$strings["View Photo"] = "Foto ansehen";
-App::$strings["Edit Album"] = "Album bearbeiten";
App::$strings["Permission denied. Access to this item may be restricted."] = "Berechtigung verweigert. Der Zugriff ist wahrscheinlich eingeschränkt worden.";
App::$strings["Photo not available"] = "Foto nicht verfügbar";
App::$strings["Use as profile photo"] = "Als Profilfoto verwenden";
App::$strings["Use as cover photo"] = "Als Titelbild verwenden";
App::$strings["Private Photo"] = "Privates Foto";
-App::$strings["Previous"] = "Voriges";
App::$strings["View Full Size"] = "In voller Größe anzeigen";
-App::$strings["Next"] = "Nächste";
App::$strings["Edit photo"] = "Foto bearbeiten";
App::$strings["Rotate CW (right)"] = "Drehen im UZS (rechts)";
App::$strings["Rotate CCW (left)"] = "Drehen gegen UZS (links)";
@@ -833,11 +960,9 @@ App::$strings["Example: @bob, @Barbara_Jensen, @jim@example.com"] = "Beispiele:
App::$strings["Flag as adult in album view"] = "In der Albumansicht als nicht jugendfrei markieren";
App::$strings["I like this (toggle)"] = "Mir gefällt das (Umschalter)";
App::$strings["I don't like this (toggle)"] = "Mir gefällt das nicht (Umschalter)";
-App::$strings["Share"] = "Teilen";
App::$strings["Please wait"] = "Bitte warten";
App::$strings["This is you"] = "Das bist Du";
App::$strings["Comment"] = "Kommentar";
-App::$strings["Preview"] = "Vorschau";
App::$strings["__ctx:title__ Likes"] = "Gefällt mir";
App::$strings["__ctx:title__ Dislikes"] = "Gefällt mir nicht";
App::$strings["__ctx:title__ Agree"] = "Zustimmungen";
@@ -861,102 +986,67 @@ App::$strings["Map"] = "Karte";
App::$strings["__ctx:noun__ Likes"] = "Gefällt mir";
App::$strings["__ctx:noun__ Dislikes"] = "Gefällt nicht";
App::$strings["Close"] = "Schließen";
-App::$strings["View Album"] = "Album ansehen";
App::$strings["Recent Photos"] = "Neueste Fotos";
-App::$strings["\$Projectname Server - Setup"] = "\$Projectname Server-Einrichtung";
-App::$strings["Could not connect to database."] = "Kann nicht mit der Datenbank verbinden.";
-App::$strings["Could not connect to specified site URL. Possible SSL certificate or DNS issue."] = "Konnte die angegebene Webseiten-URL nicht erreichen. Möglicherweise ein Problem mit dem SSL-Zertifikat oder dem DNS.";
-App::$strings["Could not create table."] = "Konnte Tabelle nicht erstellen.";
-App::$strings["Your site database has been installed."] = "Die Datenbank Deines Hubs wurde installiert.";
-App::$strings["You may need to import the file \"install/schema_xxx.sql\" manually using a database client."] = "Möglicherweise musst Du die Datei install/schema_xxx.sql manuell mit Hilfe eines Datenkbank-Clients importieren.";
-App::$strings["Please see the file \"install/INSTALL.txt\"."] = "Lies die Datei \"install/INSTALL.txt\".";
-App::$strings["System check"] = "Systemprüfung";
-App::$strings["Check again"] = "Nochmal prüfen";
-App::$strings["Database connection"] = "Datenbankverbindung";
-App::$strings["In order to install \$Projectname we need to know how to connect to your database."] = "Um \$Projectname zu installieren, müssen wir wissen, wie wir eine Verbindung zu Deiner Datenbank aufbauen können.";
-App::$strings["Please contact your hosting provider or site administrator if you have questions about these settings."] = "Bitte kontaktiere Deinen Hosting-Provider oder Administrator, falls Du Fragen zu diesen Einstellungen hast.";
-App::$strings["The database you specify below should already exist. If it does not, please create it before continuing."] = "Die Datenbank, die Du weiter unten angibst, sollte bereits existieren. Sollte das noch nicht der Fall sein, erzeuge sie bitte bevor Du fortfährst.";
-App::$strings["Database Server Name"] = "Datenbankservername";
-App::$strings["Default is 127.0.0.1"] = "Standard ist 127.0.0.1";
-App::$strings["Database Port"] = "Datenbankport";
-App::$strings["Communication port number - use 0 for default"] = "Port-Nummer für die Kommunikation – verwende 0 für die Standardeinstellung";
-App::$strings["Database Login Name"] = "Datenbank-Benutzername";
-App::$strings["Database Login Password"] = "Datenbank-Passwort";
-App::$strings["Database Name"] = "Datenbankname";
-App::$strings["Database Type"] = "Datenbanktyp";
-App::$strings["Site administrator email address"] = "E-Mail Adresse des Seiten-Administrators";
-App::$strings["Your account email address must match this in order to use the web admin panel."] = "Die E-Mail-Adresse Deines Accounts muss dieser Adresse entsprechen, damit Du Zugriff zur Administrations-Seite erhältst.";
-App::$strings["Website URL"] = "Webseiten-URL";
-App::$strings["Please use SSL (https) URL if available."] = "Nutze wenn möglich eine SSL-URL (https).";
-App::$strings["Please select a default timezone for your website"] = "Standard-Zeitzone für Deinen Server";
-App::$strings["Site settings"] = "Seiteneinstellungen";
-App::$strings["PHP version 5.5 or greater is required."] = "PHP-Version 5.5 oder höher ist erforderlich.";
-App::$strings["PHP version"] = "PHP-Version";
-App::$strings["Could not find a command line version of PHP in the web server PATH."] = "Konnte die Kommandozeilen-Version von PHP nicht im PATH des Web-Servers finden.";
-App::$strings["If you don't have a command line version of PHP installed on server, you will not be able to run background polling via cron."] = "Ohne Kommandozeilen-Version von PHP auf dem Server wirst Du nicht in der Lage sein, Hintergrundprozesse via cron auszuführen.";
-App::$strings["PHP executable path"] = "PHP-Pfad zu ausführbarer Datei";
-App::$strings["Enter full path to php executable. You can leave this blank to continue the installation."] = "Gib den vollen Pfad zum PHP-Interpreter an. Du kannst dieses Feld frei lassen und mit der Installation fortfahren.";
-App::$strings["Command line PHP"] = "PHP-Befehlszeile";
-App::$strings["Unable to check command line PHP, as shell_exec() is disabled. This is required."] = "Prüfung auf Kommandozeilen-PHP fehlgeschlagen, da shell_exec() deaktiviert ist. Dies wird aber benötigt.";
-App::$strings["The command line version of PHP on your system does not have \"register_argc_argv\" enabled."] = "Bei der Kommandozeilen-Version von PHP auf Deinem System ist \"register_argc_argv\" nicht aktiviert.";
-App::$strings["This is required for message delivery to work."] = "Das wird benötigt, damit die Auslieferung von Nachrichten funktioniert.";
-App::$strings["PHP register_argc_argv"] = "PHP register_argc_argv";
-App::$strings["Your max allowed total upload size is set to %s. Maximum size of one file to upload is set to %s. You are allowed to upload up to %d files at once."] = "Die Maximalgröße für Uploads insgesamt liegt bei %s. Die Maximalgröße für eine Datei liegt bei %s. Es können maximal %d Dateien gleichzeitig hochgeladen werden.";
-App::$strings["You can adjust these settings in the server php.ini file."] = "Du kannst diese Einstellungen in der php.ini - Datei des Servers anpassen.";
-App::$strings["PHP upload limits"] = "PHP-Hochladebeschränkungen";
-App::$strings["Error: the \"openssl_pkey_new\" function on this system is not able to generate encryption keys"] = "Fehler: Die „openssl_pkey_new“-Funktion auf diesem System ist nicht in der Lage, Schlüssel für die Verschlüsselung zu erzeugen.";
-App::$strings["If running under Windows, please see \"http://www.php.net/manual/en/openssl.installation.php\"."] = "Wenn Du Windows verwendest, findest Du unter http://www.php.net/manual/en/openssl.installation.php eine Installationsanleitung.";
-App::$strings["Generate encryption keys"] = "Verschlüsselungsschlüssel erzeugen";
-App::$strings["libCurl PHP module"] = "libCurl-PHP-Modul";
-App::$strings["GD graphics PHP module"] = "GD-Grafik-PHP-Modul";
-App::$strings["OpenSSL PHP module"] = "OpenSSL-PHP-Modul";
-App::$strings["PDO database PHP module"] = "PDO-Datenbank-PHP-Modul";
-App::$strings["mb_string PHP module"] = "mb_string-PHP-Modul";
-App::$strings["xml PHP module"] = "xml-PHP-Modul";
-App::$strings["Apache mod_rewrite module"] = "Apache-mod_rewrite-Modul";
-App::$strings["Error: Apache webserver mod-rewrite module is required but not installed."] = "Fehler: Das Apache-Modul mod-rewrite wird benötigt, ist aber nicht installiert.";
-App::$strings["exec"] = "exec";
-App::$strings["Error: exec is required but is either not installed or has been disabled in php.ini"] = "Fehler: exec ist erforderlich, aber entweder nicht installiert oder wurde in der php.ini deaktiviert";
-App::$strings["shell_exec"] = "shell_exec";
-App::$strings["Error: shell_exec is required but is either not installed or has been disabled in php.ini"] = "Fehler: shell_exec ist erforderlich, aber entweder nicht installiert oder wurde in der php.ini deaktiviert";
-App::$strings["Error: libCURL PHP module required but not installed."] = "Fehler: Das PHP-Modul libCURL wird benötigt, ist aber nicht installiert.";
-App::$strings["Error: GD graphics PHP module with JPEG support required but not installed."] = "Fehler: Das PHP-Modul GD-Grafik mit JPEG-Unterstützung wird benötigt, ist aber nicht installiert.";
-App::$strings["Error: openssl PHP module required but not installed."] = "Fehler: Das PHP-Modul openssl wird benötigt, ist aber nicht installiert.";
-App::$strings["Error: PDO database PHP module required but not installed."] = "Fehler: PDO-Datenbank-PHP-Modul ist erforderlich, aber nicht installiert.";
-App::$strings["Error: mb_string PHP module required but not installed."] = "Fehler: Das PHP-Modul mb_string wird benötigt, ist aber nicht installiert.";
-App::$strings["Error: xml PHP module required for DAV but not installed."] = "Fehler: Das xml-PHP-Modul wird für DAV benötigt, ist aber nicht installiert.";
-App::$strings["The web installer needs to be able to create a file called \".htconfig.php\" in the top folder of your web server and it is unable to do so."] = "Der Installations-Assistent muss in der Lage sein, die Datei \".htconfig.php\" im Stammverzeichnis des Web-Servers anzulegen, ist er aber nicht.";
-App::$strings["This is most often a permission setting, as the web server may not be able to write files in your folder - even if you can."] = "Meist liegt das daran, dass der Nutzer, unter dem der Web-Server läuft, keine Schreibrechte in dem Verzeichnis hat – selbst wenn Du selbst das darfst.";
-App::$strings["At the end of this procedure, we will give you a text to save in a file named .htconfig.php in your Red top folder."] = "Am Schluss dieses Vorgangs wird ein Text generiert, den Du unter dem Dateinamen .htconfig.php im Stammverzeichnis Deiner Hubzilla-Installation speichern musst.";
-App::$strings["You can alternatively skip this procedure and perform a manual installation. Please see the file \"install/INSTALL.txt\" for instructions."] = "Alternativ kannst Du diesen Schritt überspringen und die Installation manuell vornehmen. Lies dazu die Datei install/INSTALL.txt.";
-App::$strings[".htconfig.php is writable"] = ".htconfig.php ist beschreibbar";
-App::$strings["This software uses the Smarty3 template engine to render its web views. Smarty3 compiles templates to PHP to speed up rendering."] = "Diese Software verwendet die Smarty3 Template Engine, um Vorlagen für die Webdarstellung zu verarbeiten. Smarty3 übersetzt diese Vorlagen nach PHP, um die Darstellung zu beschleunigen.";
-App::$strings["In order to store these compiled templates, the web server needs to have write access to the directory %s under the top level web folder."] = "Um diese kompilierten Vorlagen speichern zu können, braucht der Web-Server Schreibzugriff auf das Verzeichnis %s unterhalb des Hubzilla-Stammverzeichnisses.";
-App::$strings["Please ensure that the user that your web server runs as (e.g. www-data) has write access to this folder."] = "Bitte stelle sicher, dass der Nutzer, unter dem der Web-Server läuft (z.B. www-data), Schreibzugriff auf dieses Verzeichnis hat.";
-App::$strings["Note: as a security measure, you should give the web server write access to %s only--not the template files (.tpl) that it contains."] = "Hinweis: Aus Sicherheitsgründen sollte der Web-Server nur auf %s Schreibrechte haben, nicht auf die Template-Dateien (.tpl), die das Verzeichnis enthält.";
-App::$strings["%s is writable"] = "%s ist beschreibbar";
-App::$strings["This software uses the store directory to save uploaded files. The web server needs to have write access to the store directory under the top level web folder"] = "Diese Software benutzt das Verzeichnis store, um hochgeladene Dateien zu speichern. Der Webserver benötigt Schreibrechte für dieses Verzeichnis direkt unterhalb des Web-Stammverzeichnisses.";
-App::$strings["store is writable"] = "store ist schreibbar";
-App::$strings["SSL certificate cannot be validated. Fix certificate or disable https access to this site."] = "Das SSL-Zertifikat konnte nicht validiert werden. Korrigiere das Zertifikat oder deaktiviere den HTTPS-Zugriff auf diesen Server.";
-App::$strings["If you have https access to your website or allow connections to TCP port 443 (the https: port), you MUST use a browser-valid certificate. You MUST NOT use self-signed certificates!"] = "Wenn Du via HTTPS auf Deinen Server zugreifen möchtest, also Verbindungen über den Port 443 möglich sein sollen, ist ein SSL-Zertifikat einer Zertifizierungsstelle (CA) notwendig, das von den Browsern ohne Sicherheitsabfrage akzeptiert wird. Die Verwendung eines selbst signierten Zertifikates ist nicht möglich.";
-App::$strings["This restriction is incorporated because public posts from you may for example contain references to images on your own hub."] = "Diese Einschränkung wurde eingebaut, weil Deine öffentlichen Beiträge zum Beispiel Verweise auf Bilder auf Deinem eigenen Hub enthalten können.";
-App::$strings["If your certificate is not recognized, members of other sites (who may themselves have valid certificates) will get a warning message on their own site complaining about security issues."] = "Wenn Dein Zertifikat nicht von jedem Browser akzeptiert wird, erhalten die Mitglieder anderer \$Projectname-Hubs (die mit korrekten Zertifikaten ausgestattet sind) Sicherheits-Warnmeldungen, obwohl sie gar nicht direkt auf Deinem Server unterwegs sind (zum Beispiel, wenn ein Bild aus einem Deiner Beiträge angezeigt wird).";
-App::$strings["This can cause usability issues elsewhere (not just on your own site) so we must insist on this requirement."] = "Dies kann Probleme für andere Nutzer (nicht nur auf Deinem eigenen Server) verursachen, so dass wir auf dieser Forderung bestehen müssen.";
-App::$strings["Providers are available that issue free certificates which are browser-valid."] = "Es gibt einige Zertifizierungsstellen (CAs), bei denen solche Zertifikate kostenlos zu haben sind.";
-App::$strings["If you are confident that the certificate is valid and signed by a trusted authority, check to see if you have failed to install an intermediate cert. These are not normally required by browsers, but are required for server-to-server communications."] = "Wenn Du sicher bist, dass das Zertifikat gültig und von einer vertrauenswürdigen Zertifizierungsstelle signiert ist, prüfe auf ggf. noch zu installierende Zwischenzertifikate (intermediate). Diese werden nicht unbedingt von Browsern benötigt, aber sehr wohl für die Kommunikation zwischen Servern.";
-App::$strings["SSL certificate validation"] = "SSL Zertifikatverifizierung";
-App::$strings["Url rewrite in .htaccess is not working. Check your server configuration.Test: "] = "Das Umschreiben von URLs (rewrite) per .htaccess funktioniert nicht. Bitte prüfe die Server-Konfiguration. Test:";
-App::$strings["Url rewrite is working"] = "Url rewrite funktioniert";
-App::$strings["The database configuration file \".htconfig.php\" could not be written. Please use the enclosed text to create a configuration file in your web server root."] = "Die Datenbank-Konfigurationsdatei „.htconfig.php“ konnte nicht geschrieben werden. Bitte verwende den unten angegebenen Text, um die Konfigurationsdatei im Stammverzeichnis des Webservers anzulegen.";
-App::$strings["Errors encountered creating database tables."] = "Fehler beim Anlegen der Datenbank-Tabellen aufgetreten.";
-App::$strings["<h1>What next</h1>"] = "<h1>Was als Nächstes</h1>";
-App::$strings["IMPORTANT: You will need to [manually] setup a scheduled task for the poller."] = "WICHTIG: Du musst [manuell] einen Cronjob für den Poller einrichten.";
-App::$strings["Item is not editable"] = "Element kann nicht bearbeitet werden.";
-App::$strings["This site is not a directory server"] = "Diese Webseite ist kein Verzeichnisserver";
-App::$strings["Create Channel"] = "Einen neuen Kanal anlegen";
-App::$strings["A channel is your identity on this network. It can represent a person, a blog, or a forum to name a few. Channels can make connections with other channels to share information with highly detailed permissions."] = "Ein Kanal ist Deine Identität in diesem Netzwerk. Er kann eine Person, ein Blog oder ein Forum repräsentieren, nur um ein paar Beispiele zu nennen. Kanäle können Verbindungen miteinander eingehen, um Informationen zu teilen, jeweils basierend auf sehr detaillierten Berechtigungseinstellungen.";
-App::$strings["or <a href=\"import\">import an existing channel</a> from another location."] = "oder <a href=\"import\">importiere einen bestehenden Kanal</a> von einem anderen Server.";
-App::$strings["Mark all system notifications seen"] = "Markiere alle System-Benachrichtigungen als gesehen";
+App::$strings["Profile Unavailable."] = "Profil nicht verfügbar.";
+App::$strings["Not found"] = "Nicht gefunden";
+App::$strings["Invalid channel"] = "Ungültiger Kanal";
+App::$strings["Error retrieving wiki"] = "Fehler beim Abrufen des Wiki";
+App::$strings["Error creating zip file export folder"] = "Fehler bei der Erzeugung des Zip-Datei Export-Verzeichnisses ";
+App::$strings["Error downloading wiki: "] = "Fehler beim Herunterladen des Wiki:";
+App::$strings["Wikis"] = "Wikis";
+App::$strings["Download"] = "Herunterladen";
+App::$strings["Create New"] = "Neu anlegen";
+App::$strings["Wiki name"] = "Name des Wiki";
+App::$strings["Content type"] = "Inhaltstyp";
+App::$strings["Markdown"] = "Markdown";
+App::$strings["BBcode"] = "BBcode";
+App::$strings["Text"] = "Text";
+App::$strings["Type"] = "Typ";
+App::$strings["Any&nbsp;type"] = "Alle&nbsp;Arten";
+App::$strings["Lock content type"] = "Inhaltstyp sperren";
+App::$strings["Create a status post for this wiki"] = "Erzeuge einen Statusbeitrag für dieses Wiki";
+App::$strings["Edit Wiki Name"] = "Wiki-Namen bearbeiten";
+App::$strings["Wiki not found"] = "Wiki nicht gefunden";
+App::$strings["Rename page"] = "Seite umbenennen";
+App::$strings["Error retrieving page content"] = "Fehler beim Abrufen des Seiteninhalts";
+App::$strings["New page"] = "Neue Seite";
+App::$strings["Revision Comparison"] = "Revisionsvergleich";
+App::$strings["Revert"] = "Rückgängig machen";
+App::$strings["Short description of your changes (optional)"] = "Kurze Beschreibung Ihrer Änderungen (optional)";
+App::$strings["Source"] = "Quelle";
+App::$strings["New page name"] = "Neuer Seitenname";
+App::$strings["Embed image from photo albums"] = "Bild aus Fotoalben einbetten";
+App::$strings["Embed an image from your albums"] = "Betten Sie ein Bild aus Ihren Alben ein";
+App::$strings["OK"] = "Ok";
+App::$strings["Choose images to embed"] = "Wählen Sie Bilder zum Einbetten aus";
+App::$strings["Choose an album"] = "Wählen Sie ein Album aus";
+App::$strings["Choose a different album"] = "Wählen Sie ein anderes Album aus";
+App::$strings["Error getting album list"] = "Fehler beim Holen der Albenliste";
+App::$strings["Error getting photo link"] = "Fehler beim Holen des Fotolinks";
+App::$strings["Error getting album"] = "Fehler beim Holen des Albums";
+App::$strings["Error creating wiki. Invalid name."] = "Fehler beim Erstellen des Wiki. Ungültiger Name.";
+App::$strings["A wiki with this name already exists."] = "Es existiert bereits ein Wiki mit diesem Namen.";
+App::$strings["Wiki created, but error creating Home page."] = "Das Wiki wurde erzeugt, aber es gab einen Fehler bei der Erstellung der Startseite";
+App::$strings["Error creating wiki"] = "Fehler beim Erstellen des Wiki";
+App::$strings["Error updating wiki. Invalid name."] = "Fehler beim Aktualisieren des Wikis. Ungültiger Name.";
+App::$strings["Error updating wiki"] = "Fehler beim Aktualisieren des Wikis";
+App::$strings["Wiki delete permission denied."] = "Wiki-Löschberechtigung verweigert.";
+App::$strings["Error deleting wiki"] = "Fehler beim Löschen des Wiki";
+App::$strings["New page created"] = "Neue Seite erstellt";
+App::$strings["Cannot delete Home"] = "Kann die Startseite nicht löschen";
+App::$strings["Current Revision"] = "Aktuelle Revision";
+App::$strings["Selected Revision"] = "Ausgewählte Revision";
+App::$strings["You must be authenticated."] = "Sie müssen authenzifiziert sein.";
+App::$strings["toggle full screen mode"] = "auf Vollbildmodus umschalten";
+App::$strings["Layout updated."] = "Layout aktualisiert.";
+App::$strings["Feature disabled."] = "Funktion deaktiviert.";
+App::$strings["Edit System Page Description"] = "Systemseitenbeschreibung bearbeiten";
+App::$strings["(modified)"] = "(geändert)";
+App::$strings["Reset"] = "Zurücksetzen";
+App::$strings["Layout not found."] = "Layout nicht gefunden.";
+App::$strings["Module Name:"] = "Modulname:";
+App::$strings["Layout Help"] = "Layout-Hilfe";
+App::$strings["Edit another layout"] = "Ein weiteres Layout bearbeiten";
App::$strings["Poke"] = "Anstupsen";
App::$strings["Poke somebody"] = "Jemanden anstupsen";
App::$strings["Poke/Prod"] = "Anstupsen/Knuffen";
@@ -964,6 +1054,181 @@ App::$strings["Poke, prod or do other things to somebody"] = "Jemanden anstupsen
App::$strings["Recipient"] = "Empfänger";
App::$strings["Choose what you wish to do to recipient"] = "Wähle, was Du mit dem/r Empfänger/in tun willst";
App::$strings["Make this post private"] = "Diesen Beitrag privat machen";
+App::$strings["Image uploaded but image cropping failed."] = "Bild hochgeladen, aber das Zurechtschneiden schlug fehl.";
+App::$strings["Profile Photos"] = "Profilfotos";
+App::$strings["Image resize failed."] = "Bild-Anpassung fehlgeschlagen.";
+App::$strings["Shift-reload the page or clear browser cache if the new photo does not display immediately."] = "Leere den Browser Cache oder nutze Umschalten-Neu Laden, falls das neue Foto nicht sofort angezeigt wird.";
+App::$strings["Unable to process image"] = "Kann Bild nicht verarbeiten";
+App::$strings["Image upload failed."] = "Hochladen des Bilds fehlgeschlagen.";
+App::$strings["Unable to process image."] = "Kann Bild nicht verarbeiten.";
+App::$strings["Photo not available."] = "Foto nicht verfügbar.";
+App::$strings["Upload File:"] = "Datei hochladen:";
+App::$strings["Select a profile:"] = "Wähle ein Profil:";
+App::$strings["Use Photo for Profile"] = "Foto für Profil verwenden";
+App::$strings["Upload Profile Photo"] = "Lade neues Profilfoto hoch";
+App::$strings["Use"] = "Verwenden";
+App::$strings["skip this step"] = "diesen Schritt überspringen";
+App::$strings["select a photo from your photo albums"] = "ein Foto aus meinen Fotoalben";
+App::$strings["Crop Image"] = "Bild zuschneiden";
+App::$strings["Please adjust the image cropping for optimum viewing."] = "Bitte schneide das Bild für eine optimale Anzeige passend zu.";
+App::$strings["Done Editing"] = "Bearbeitung fertigstellen";
+App::$strings["Away"] = "Abwesend";
+App::$strings["Online"] = "Online";
+App::$strings["Unable to locate original post."] = "Originalbeitrag nicht gefunden.";
+App::$strings["Empty post discarded."] = "Leeren Beitrag verworfen.";
+App::$strings["Duplicate post suppressed."] = "Doppelter Beitrag unterdrückt.";
+App::$strings["System error. Post not saved."] = "Systemfehler. Beitrag nicht gespeichert.";
+App::$strings["Your comment is awaiting approval."] = "Dein Kommentar muss noch bestätigt werden.";
+App::$strings["Unable to obtain post information from database."] = "Beitragsinformationen können nicht aus der Datenbank abgerufen werden.";
+App::$strings["You have reached your limit of %1$.0f top level posts."] = "Du hast die maximale Anzahl von %1$.0f Beiträgen erreicht.";
+App::$strings["You have reached your limit of %1$.0f webpages."] = "Du hast die maximale Anzahl von %1$.0f Webseiten erreicht.";
+App::$strings["sent you a private message"] = "hat Dir eine private Nachricht geschickt";
+App::$strings["added your channel"] = "hat deinen Kanal hinzugefügt";
+App::$strings["requires approval"] = "Zustimmung erforderlich";
+App::$strings["g A l F d"] = "l, d. F, G:i \\U\\h\\r";
+App::$strings["[today]"] = "[Heute]";
+App::$strings["posted an event"] = "hat einen Termin veröffentlicht";
+App::$strings["shared a file with you"] = "hat eine Datei mit Dir geteilt";
+App::$strings["Invalid item."] = "Ungültiges Element.";
+App::$strings["Page not found."] = "Seite nicht gefunden.";
+App::$strings["Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum."] = "Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.";
+App::$strings["Could not access contact record."] = "Konnte nicht auf den Kontakteintrag zugreifen.";
+App::$strings["Could not locate selected profile."] = "Gewähltes Profil nicht gefunden.";
+App::$strings["Connection updated."] = "Verbindung aktualisiert.";
+App::$strings["Failed to update connection record."] = "Konnte den Verbindungseintrag nicht aktualisieren.";
+App::$strings["is now connected to"] = "ist jetzt verbunden mit";
+App::$strings["Could not access address book record."] = "Konnte nicht auf den Adressbuch-Eintrag zugreifen.";
+App::$strings["Refresh failed - channel is currently unavailable."] = "Aktualisierung fehlgeschlagen – der Kanal ist im Moment nicht erreichbar.";
+App::$strings["Unable to set address book parameters."] = "Konnte die Adressbuch-Parameter nicht setzen.";
+App::$strings["Connection has been removed."] = "Verbindung wurde gelöscht.";
+App::$strings["View Profile"] = "Profil ansehen";
+App::$strings["View %s's profile"] = "%ss Profil ansehen";
+App::$strings["Refresh Permissions"] = "Zugriffsrechte neu laden";
+App::$strings["Fetch updated permissions"] = "Aktualisierte Zugriffsrechte abrufen";
+App::$strings["Refresh Photo"] = "Foto aktualisieren";
+App::$strings["Fetch updated photo"] = "Aktualisiertes Profilfoto abrufen";
+App::$strings["Recent Activity"] = "Kürzliche Aktivitäten";
+App::$strings["View recent posts and comments"] = "Betrachte die neuesten Beiträge und Kommentare";
+App::$strings["Block (or Unblock) all communications with this connection"] = "Jegliche Kommunikation mit dieser Verbindung blockieren/zulassen";
+App::$strings["This connection is blocked!"] = "Die Verbindung ist geblockt!";
+App::$strings["Unignore"] = "Nicht ignorieren";
+App::$strings["Ignore (or Unignore) all inbound communications from this connection"] = "Jegliche eingehende Kommunikation von dieser Verbindung ignorieren/zulassen";
+App::$strings["This connection is ignored!"] = "Die Verbindung wird ignoriert!";
+App::$strings["Unarchive"] = "Aus Archiv zurückholen";
+App::$strings["Archive"] = "Archivieren";
+App::$strings["Archive (or Unarchive) this connection - mark channel dead but keep content"] = "Verbindung archivieren/aus dem Archiv zurückholen (Archiv = Kanal als erloschen markieren, aber die Beiträge behalten)";
+App::$strings["This connection is archived!"] = "Die Verbindung ist archiviert!";
+App::$strings["Unhide"] = "Wieder sichtbar machen";
+App::$strings["Hide"] = "Verstecken";
+App::$strings["Hide or Unhide this connection from your other connections"] = "Diese Verbindung vor anderen Verbindungen verstecken/zeigen";
+App::$strings["This connection is hidden!"] = "Die Verbindung ist versteckt!";
+App::$strings["Delete this connection"] = "Verbindung löschen";
+App::$strings["Fetch Vcard"] = "Vcard abrufen";
+App::$strings["Fetch electronic calling card for this connection"] = "Rufe eine digitale Visitenkarte für diese Verbindung ab";
+App::$strings["Open Individual Permissions section by default"] = "Öffne standardmäßig den Bereich für individuelle Berechtigungen";
+App::$strings["Affinity"] = "Beziehung";
+App::$strings["Open Set Affinity section by default"] = "Öffne standardmäßig den Bereich für Beziehungsgrad-Einstellungen";
+App::$strings["Me"] = "Ich";
+App::$strings["Family"] = "Familie";
+App::$strings["Acquaintances"] = "Bekannte";
+App::$strings["Filter"] = "Filter";
+App::$strings["Open Custom Filter section by default"] = "Öffne standardmäßig den Bereich für benutzerdefinierte Filter";
+App::$strings["Approve this connection"] = "Verbindung genehmigen";
+App::$strings["Accept connection to allow communication"] = "Akzeptiere die Verbindung, um Kommunikation zu ermöglichen";
+App::$strings["Set Affinity"] = "Beziehung festlegen";
+App::$strings["Set Profile"] = "Profil festlegen";
+App::$strings["Set Affinity & Profile"] = "Beziehung und Profile festlegen";
+App::$strings["This connection is unreachable from this location."] = "Diese Verbindung ist von diesem Ort unerreichbar.";
+App::$strings["This connection may be unreachable from other channel locations."] = "Diese Verbindung könnte von anderen Standpunkten des Kanals nicht erreichbar sein.";
+App::$strings["Location independence is not supported by their network."] = "Standort Unabhängigkeit wird vom anderen Netzwerk nicht unterstützt.";
+App::$strings["This connection is unreachable from this location. Location independence is not supported by their network."] = "Diese Verbindung ist von diesem Standort aus unerreichbar. Standort Unabhängigkeit wird vom anderen Netzwerk nicht unterstützt.";
+App::$strings["Connection Default Permissions"] = "Standardzugriffsrechte für neue Verbindungen:";
+App::$strings["Connection: %s"] = "Verbindung: %s";
+App::$strings["Apply these permissions automatically"] = "Diese Berechtigungen automatisch anwenden";
+App::$strings["Connection requests will be approved without your interaction"] = "Verbindungsanfragen werden sofort bestätigt, ohne dass Deine aktive Zustimmung erforderlich ist.";
+App::$strings["Permission role"] = "Berechtigungsrolle";
+App::$strings["Add permission role"] = "Berechtigungsrolle hinzufügen";
+App::$strings["This connection's primary address is"] = "Die Hauptadresse der Verbindung ist";
+App::$strings["Available locations:"] = "Verfügbare Klone:";
+App::$strings["The permissions indicated on this page will be applied to all new connections."] = "Die auf dieser Seite angegebenen Berechtigungen werden auf alle neuen Verbindungen angewendet.";
+App::$strings["Connection Tools"] = "Verbindungswerkzeuge";
+App::$strings["Slide to adjust your degree of friendship"] = "Verschieben, um den Grad der Freundschaft zu einzustellen";
+App::$strings["Rating"] = "Bewertung";
+App::$strings["Slide to adjust your rating"] = "Verschieben, um Deine Bewertung einzustellen";
+App::$strings["Optionally explain your rating"] = "Optional kannst Du Deine Bewertung begründen";
+App::$strings["Custom Filter"] = "Benutzerdefinierter Filter";
+App::$strings["Only import posts with this text"] = "Nur Beiträge mit diesem Text importieren";
+App::$strings["words one per line or #tags or /patterns/ or lang=xx, leave blank to import all posts"] = "Einzelne Wörter pro Zeile, #Tags oder /Reguläre Ausdrücke/. lang=xx (z.B. lang=de) ermöglicht Filterung nach Sprache. Leer lassen, um alle Beiträge zu importieren.";
+App::$strings["Do not import posts with this text"] = "Beiträge mit diesem Text nicht importieren";
+App::$strings["This information is public!"] = "Diese Information ist öffentlich!";
+App::$strings["Connection Pending Approval"] = "Verbindung wartet auf Bestätigung";
+App::$strings["Please choose the profile you would like to display to %s when viewing your profile securely."] = "Bitte wähle ein Profil, das wir %s zeigen sollen, wenn Deine Profilseite über eine verifizierte Verbindung aufgerufen wird.";
+App::$strings["Some permissions may be inherited from your channel's <a href=\"settings\"><strong>privacy settings</strong></a>, which have higher priority than individual settings. You can change those settings here but they wont have any impact unless the inherited setting changes."] = "Einige Berechtigungen werden möglicherweise von den globalen <a href=\"settings\">Sicherheits- und Privatsphäre-Einstellungen</a> dieses Kanals geerbt. Diese haben eine höhere Priorität als die Einstellungen an der Verbindung. Werden geerbte Einstellungen hier geändert, hat dies keine Auswirkungen.";
+App::$strings["Last update:"] = "Letzte Aktualisierung:";
+App::$strings["Details"] = "Details";
+App::$strings["Room not found"] = "Chatraum nicht gefunden";
+App::$strings["Leave Room"] = "Raum verlassen";
+App::$strings["Delete Room"] = "Raum löschen";
+App::$strings["I am away right now"] = "Ich bin gerade nicht da";
+App::$strings["I am online"] = "Ich bin online";
+App::$strings["Bookmark this room"] = "Lesezeichen für diesen Raum setzen";
+App::$strings["Please enter a link URL:"] = "Gib eine URL ein:";
+App::$strings["Encrypt text"] = "Text verschlüsseln";
+App::$strings["New Chatroom"] = "Neuer Chatraum";
+App::$strings["Chatroom name"] = "Chatraumname";
+App::$strings["Expiration of chats (minutes)"] = "Verfall von Chats (Minuten)";
+App::$strings["%1\$s's Chatrooms"] = "%1\$ss Chaträume";
+App::$strings["No chatrooms available"] = "Keine Chaträume verfügbar";
+App::$strings["Expiration"] = "Verfall";
+App::$strings["min"] = "min";
+App::$strings["Photos"] = "Fotos";
+App::$strings["Files"] = "Dateien";
+App::$strings["Unable to update menu."] = "Kann Menü nicht aktualisieren.";
+App::$strings["Unable to create menu."] = "Kann Menü nicht erstellen.";
+App::$strings["Menu Name"] = "Name des Menüs";
+App::$strings["Unique name (not visible on webpage) - required"] = "Eindeutiger Name (nicht sichtbar auf der Webseite) – erforderlich";
+App::$strings["Menu Title"] = "Menütitel";
+App::$strings["Visible on webpage - leave empty for no title"] = "Sichtbar auf der Webseite – für keinen Titel leer lassen";
+App::$strings["Allow Bookmarks"] = "Lesezeichen erlauben";
+App::$strings["Menu may be used to store saved bookmarks"] = "Im Menü können gespeicherte Lesezeichen abgelegt werden";
+App::$strings["Submit and proceed"] = "Absenden und fortfahren";
+App::$strings["Menus"] = "Menüs";
+App::$strings["Bookmarks allowed"] = "Lesezeichen erlaubt";
+App::$strings["Delete this menu"] = "Lösche dieses Menü";
+App::$strings["Edit menu contents"] = "Bearbeite Menü Inhalte";
+App::$strings["Edit this menu"] = "Dieses Menü bearbeiten";
+App::$strings["Menu could not be deleted."] = "Menü konnte nicht gelöscht werden.";
+App::$strings["Edit Menu"] = "Menü bearbeiten";
+App::$strings["Add or remove entries to this menu"] = "Einträge zu diesem Menü hinzufügen oder entfernen";
+App::$strings["Menu name"] = "Menü Name";
+App::$strings["Must be unique, only seen by you"] = "Muss eindeutig sein, ist aber nur für Dich sichtbar";
+App::$strings["Menu title"] = "Menü Titel";
+App::$strings["Menu title as seen by others"] = "Menü Titel wie er von anderen gesehen wird";
+App::$strings["Allow bookmarks"] = "Erlaube Lesezeichen";
+App::$strings["Layouts"] = "Layouts";
+App::$strings["Help"] = "Hilfe";
+App::$strings["Comanche page description language help"] = "Hilfe zur Comanche-Seitenbeschreibungssprache";
+App::$strings["Layout Description"] = "Layout-Beschreibung";
+App::$strings["Download PDL file"] = "PDL-Datei herunterladen";
+App::$strings["post"] = "Beitrag";
+App::$strings["comment"] = "Kommentar";
+App::$strings["%1\$s tagged %2\$s's %3\$s with %4\$s"] = "%1\$s hat %2\$ss %3\$s mit %4\$s verschlagwortet";
+App::$strings["This setting requires special processing and editing has been blocked."] = "Diese Einstellung erfordert eine besondere Verarbeitung und ist blockiert.";
+App::$strings["Configuration Editor"] = "Konfigurationseditor";
+App::$strings["Warning: Changing some settings could render your channel inoperable. Please leave this page unless you are comfortable with and knowledgeable about how to correctly use this feature."] = "Warnung: Einige Einstellungen können Deinen Kanal funktionsunfähig machen. Bitte verlasse diese Seite, es sei denn Du bist vertraut damit, wie dieses Feature korrekt verwendet wird.";
+App::$strings["Privacy group created."] = "Gruppe wurde erstellt.";
+App::$strings["Could not create privacy group."] = "Gruppe konnte nicht erstellt werden.";
+App::$strings["Privacy group not found."] = "Gruppe nicht gefunden.";
+App::$strings["Privacy group updated."] = "Gruppe wurde aktualisiert.";
+App::$strings["Create a group of channels."] = "Erstelle eine Gruppe für Kanäle.";
+App::$strings["Privacy group name: "] = "Gruppenname:";
+App::$strings["Members are visible to other channels"] = "Mitglieder sind sichtbar für andere Kanäle";
+App::$strings["Privacy group removed."] = "Gruppe wurde entfernt.";
+App::$strings["Unable to remove privacy group."] = "Gruppe konnte nicht entfernt werden.";
+App::$strings["Privacy group editor"] = "Gruppeneditor";
+App::$strings["Members"] = "Mitglieder";
+App::$strings["All Connected Channels"] = "Alle verbundenen Kanäle";
+App::$strings["Click on a channel to add or remove."] = "Wähle einen Kanal zum hinzufügen oder entfernen aus.";
App::$strings["Profile not found."] = "Profil nicht gefunden.";
App::$strings["Profile deleted."] = "Profil gelöscht.";
App::$strings["Profile-"] = "Profil-";
@@ -1010,7 +1275,6 @@ App::$strings["Street address"] = "Straße und Hausnummer";
App::$strings["Locality/City"] = "Wohnort";
App::$strings["Region/State"] = "Region/Bundesstaat";
App::$strings["Postal/Zip code"] = "Postleitzahl";
-App::$strings["Country"] = "Land";
App::$strings["Who (if applicable)"] = "Wer (falls anwendbar)";
App::$strings["Examples: cathy123, Cathy Williams, cathy@example.com"] = "Beispiele: cathy123, Cathy Williams, cathy@example.com";
App::$strings["Since (date)"] = "Seit (Datum)";
@@ -1030,150 +1294,38 @@ App::$strings["Love/Romance"] = "Liebe/Romantik";
App::$strings["School/Education"] = "Schule/Ausbildung";
App::$strings["Contact information and social networks"] = "Kontaktinformation und soziale Netzwerke";
App::$strings["My other channels"] = "Meine anderen Kanäle";
+App::$strings["Communications"] = "Kommunikation";
App::$strings["Profile Image"] = "Profilfoto:";
App::$strings["Edit Profiles"] = "Profile bearbeiten";
-App::$strings["Unable to find your hub."] = "Konnte Deinen Server nicht finden.";
-App::$strings["Post successful."] = "Veröffentlichung erfolgreich.";
-App::$strings["This setting requires special processing and editing has been blocked."] = "Diese Einstellung erfordert eine besondere Verarbeitung und ist blockiert.";
-App::$strings["Configuration Editor"] = "Konfigurationseditor";
-App::$strings["Warning: Changing some settings could render your channel inoperable. Please leave this page unless you are comfortable with and knowledgeable about how to correctly use this feature."] = "Warnung: Einige Einstellungen können Deinen Kanal funktionsunfähig machen. Bitte verlasse diese Seite, es sei denn Du bist vertraut damit, wie dieses Feature korrekt verwendet wird.";
-App::$strings["Blocks"] = "Blöcke";
-App::$strings["Block Title"] = "Titel des Blocks";
-App::$strings["Layouts"] = "Layouts";
-App::$strings["Help"] = "Hilfe";
-App::$strings["Comanche page description language help"] = "Hilfe zur Comanche-Seitenbeschreibungssprache";
-App::$strings["Layout Description"] = "Layout-Beschreibung";
-App::$strings["Download PDL file"] = "PDL-Datei herunterladen";
-App::$strings["Website:"] = "Webseite:";
-App::$strings["Remote Channel [%s] (not yet known on this site)"] = "Kanal [%s] (auf diesem Server noch unbekannt)";
-App::$strings["Rating (this information is public)"] = "Bewertung (öffentlich sichtbar)";
-App::$strings["Optionally explain your rating (this information is public)"] = "Optional kannst du deine Bewertung erklären (öffentlich sichtbar)";
-App::$strings["Like/Dislike"] = "Mögen/Nicht mögen";
-App::$strings["This action is restricted to members."] = "Diese Aktion kann nur von Mitgliedern ausgeführt werden.";
-App::$strings["Please <a href=\"rmagic\">login with your \$Projectname ID</a> or <a href=\"register\">register as a new \$Projectname member</a> to continue."] = "Um fortzufahren <a href=\"rmagic\">melde Dich bitte mit Deiner \$Projectname-ID an</a> oder <a href=\"register\">registriere Dich als neues \$Projectname-Mitglied</a>.";
-App::$strings["Invalid request."] = "Ungültige Anfrage.";
-App::$strings["channel"] = "Kanal";
-App::$strings["thing"] = "Sache";
-App::$strings["Channel unavailable."] = "Kanal nicht vorhanden.";
-App::$strings["Previous action reversed."] = "Die vorherige Aktion wurde rückgängig gemacht.";
-App::$strings["photo"] = "Foto";
-App::$strings["status"] = "Status";
-App::$strings["event"] = "Termin";
-App::$strings["%1\$s likes %2\$s's %3\$s"] = "%1\$s gefällt %2\$ss %3\$s";
-App::$strings["%1\$s doesn't like %2\$s's %3\$s"] = "%1\$s gefällt %2\$ss %3\$s nicht";
-App::$strings["%1\$s agrees with %2\$s's %3\$s"] = "%1\$s stimmt %2\$ss %3\$s zu";
-App::$strings["%1\$s doesn't agree with %2\$s's %3\$s"] = "%1\$s lehnt %2\$ss %3\$s ab";
-App::$strings["%1\$s abstains from a decision on %2\$s's %3\$s"] = "%1\$s enthält sich zu %2\$ss %3\$s";
-App::$strings["%1\$s is attending %2\$s's %3\$s"] = "%1\$s nimmt an %2\$ss %3\$s teil";
-App::$strings["%1\$s is not attending %2\$s's %3\$s"] = "%1\$s nimmt an %2\$ss %3\$s nicht teil";
-App::$strings["%1\$s may attend %2\$s's %3\$s"] = "%1\$s nimmt vielleicht an %2\$ss %3\$s teil";
-App::$strings["Action completed."] = "Aktion durchgeführt.";
-App::$strings["Thank you."] = "Vielen Dank.";
-App::$strings["Shift-reload the page or clear browser cache if the new photo does not display immediately."] = "Leere den Browser Cache oder nutze Umschalten-Neu Laden, falls das neue Foto nicht sofort angezeigt wird.";
-App::$strings["Use Photo for Profile"] = "Foto für Profil verwenden";
-App::$strings["Upload Profile Photo"] = "Lade neues Profilfoto hoch";
-App::$strings["Use"] = "Verwenden";
-App::$strings["Items tagged with: %s"] = "Beiträge mit Schlagwort: %s";
-App::$strings["Search results for: %s"] = "Suchergebnisse für: %s";
-App::$strings["No channel."] = "Kein Kanal.";
-App::$strings["Common connections"] = "Gemeinsame Verbindungen";
-App::$strings["No connections in common."] = "Keine gemeinsamen Verbindungen.";
-App::$strings["Authorize application connection"] = "Zugriff für die Anwendung autorisieren";
-App::$strings["Return to your app and insert this Security Code:"] = "Gehen Sie zu Ihrer App zurück und tragen Sie diesen Sicherheitscode ein:";
-App::$strings["Please login to continue."] = "Zum Weitermachen, bitte einloggen.";
-App::$strings["Do you want to authorize this application to access your posts and contacts, and/or create new posts for you?"] = "Möchtest Du dieser Anwendung erlauben, Deine Nachrichten und Kontakte abzurufen und/oder neue Nachrichten für Dich zu erstellen?";
-App::$strings["sent you a private message"] = "hat Dir eine private Nachricht geschickt";
-App::$strings["added your channel"] = "hat deinen Kanal hinzugefügt";
-App::$strings["g A l F d"] = "l, d. F, G:i \\U\\h\\r";
-App::$strings["[today]"] = "[Heute]";
-App::$strings["posted an event"] = "hat einen Termin veröffentlicht";
+App::$strings["Page link"] = "Seiten-Link";
+App::$strings["Edit Webpage"] = "Webseite bearbeiten";
+App::$strings["Create a new channel"] = "Neuen Kanal anlegen";
+App::$strings["Channel Manager"] = "Kanal-Manager";
+App::$strings["Current Channel"] = "Aktueller Kanal";
+App::$strings["Switch to one of your channels by selecting it."] = "Wechsle zu einem Deiner Kanäle, indem Du auf ihn klickst.";
+App::$strings["Default Channel"] = "Standard Kanal";
+App::$strings["Make Default"] = "Zum Standard machen";
+App::$strings["%d new messages"] = "%d neue Nachrichten";
+App::$strings["%d new introductions"] = "%d neue Vorstellungen";
+App::$strings["Delegated Channel"] = "Delegierte Kanäle";
+App::$strings["Cards"] = "Karten";
+App::$strings["Add Card"] = "Karte hinzufügen";
+App::$strings["This directory server requires an access token"] = "Dieser Verzeichnisserver benötigt einen Zugriffstoken";
App::$strings["About this site"] = "Über diese Seite";
App::$strings["Site Name"] = "Seitenname";
App::$strings["Administrator"] = "Administrator";
+App::$strings["Terms of Service"] = "Nutzungsbedingungen";
App::$strings["Software and Project information"] = "Software und Projektinformationen";
App::$strings["This site is powered by \$Projectname"] = "Diese Website wird bereitgestellt durch \$Projectname";
App::$strings["Federated and decentralised networking and identity services provided by Zot"] = "Verbundene, dezentrale Netzwerk- und Identitätsdienste, ermöglicht mittels Zot";
App::$strings["Version %s"] = "Version %s";
App::$strings["Project homepage"] = "Projekt-Website";
App::$strings["Developer homepage"] = "Entwickler-Website";
-App::$strings["No valid account found."] = "Kein gültiges Konto gefunden.";
-App::$strings["Password reset request issued. Check your email."] = "Zurücksetzen des Passworts eingeleitet. Schau in Deine E-Mails.";
-App::$strings["Site Member (%s)"] = "Nutzer (%s)";
-App::$strings["Password reset requested at %s"] = "Passwort-Rücksetzung auf %s angefordert";
-App::$strings["Request could not be verified. (You may have previously submitted it.) Password reset failed."] = "Die Anfrage konnte nicht verifiziert werden. (Vielleicht hast Du schon einmal auf den Link in der E-Mail geklickt?) Passwort-Rücksetzung fehlgeschlagen.";
-App::$strings["Password Reset"] = "Zurücksetzen des Kennworts";
-App::$strings["Your password has been reset as requested."] = "Dein Passwort wurde wie angefordert neu erstellt.";
-App::$strings["Your new password is"] = "Dein neues Passwort lautet";
-App::$strings["Save or copy your new password - and then"] = "Speichere oder kopiere Dein neues Passwort – und dann";
-App::$strings["click here to login"] = "Klicke hier, um dich anzumelden";
-App::$strings["Your password may be changed from the <em>Settings</em> page after successful login."] = "Dein Passwort kann unter <em>Einstellungen</em> nach einer erfolgreichen Anmeldung geändert werden.";
-App::$strings["Your password has changed at %s"] = "Auf %s wurde Dein Passwort geändert";
-App::$strings["Forgot your Password?"] = "Kennwort vergessen?";
-App::$strings["Enter your email address and submit to have your password reset. Then check your email for further instructions."] = "Gib Deine E-Mail-Adresse ein, um Dein Passwort zurücksetzen zu lassen. Du erhältst dann weitere Anweisungen per E-Mail.";
-App::$strings["Email Address"] = "E-Mail Adresse";
-App::$strings["Reset"] = "Zurücksetzen";
-App::$strings["Select a bookmark folder"] = "Lesezeichenordner wählen";
-App::$strings["Save Bookmark"] = "Lesezeichen speichern";
-App::$strings["URL of bookmark"] = "URL des Lesezeichens";
-App::$strings["Or enter new bookmark folder name"] = "Oder gib einen neuen Namen für den Lesezeichenordner ein";
-App::$strings["This directory server requires an access token"] = "Dieser Verzeichnisserver benötigt einen Zugriffstoken";
-App::$strings["Authentication failed."] = "Authentifizierung fehlgeschlagen.";
-App::$strings["Remote Authentication"] = "Entfernte Authentifizierung";
-App::$strings["Enter your channel address (e.g. channel@example.com)"] = "Deine Kanal-Adresse (z. B. channel@example.com)";
-App::$strings["Authenticate"] = "Authentifizieren";
-App::$strings["Please login."] = "Bitte melde dich an.";
-App::$strings["Account removals are not allowed within 48 hours of changing the account password."] = "Das Löschen von Konten innerhalb 48 Stunden nachdem deren Passwort geändert wurde ist nicht erlaubt.";
-App::$strings["Remove This Account"] = "Dieses Konto löschen";
-App::$strings["WARNING: "] = "WARNUNG: ";
-App::$strings["This account and all its channels will be completely removed from the network. "] = "Dieses Konto mit all seinen Kanälen wird vollständig aus dem Netzwerk gelöscht.";
-App::$strings["This action is permanent and can not be undone!"] = "Dieser Schritt ist endgültig und kann nicht rückgängig gemacht werden!";
-App::$strings["Please enter your password for verification:"] = "Bitte gib zur Bestätigung Dein Passwort ein:";
-App::$strings["Remove this account, all its channels and all its channel clones from the network"] = "Dieses Konto, all seine Kanäle sowie alle Kanal-Klone aus dem Netzwerk löschen";
-App::$strings["By default only the instances of the channels located on this hub will be removed from the network"] = "Standardmäßig werden nur die Kanalklone auf diesem \$Projectname-Hub aus dem Netzwerk entfernt";
-App::$strings["Remove Account"] = "Konto entfernen";
-App::$strings["Layout updated."] = "Layout aktualisiert.";
-App::$strings["Feature disabled."] = "Funktion deaktiviert.";
-App::$strings["Edit System Page Description"] = "Systemseitenbeschreibung bearbeiten";
-App::$strings["Layout not found."] = "Layout nicht gefunden.";
-App::$strings["Module Name:"] = "Modulname:";
-App::$strings["Layout Help"] = "Layout-Hilfe";
-App::$strings["Export Channel"] = "Kanal exportieren";
-App::$strings["Export your basic channel information to a file. This acts as a backup of your connections, permissions, profile and basic data, which can be used to import your data to a new server hub, but does not contain your content."] = "Exportiert die grundlegenden Kanal-Informationen in eine kleine Datei. Diese stellt eine Sicherung Deiner Verbindungen, Berechtigungen, Profile und Basisdaten bereit, die für den Import auf einem anderen Hub verwendet werden kann, aber nicht die Beiträge Deines Kanals enthält.";
-App::$strings["Export Content"] = "Kanal und Inhalte exportieren";
-App::$strings["Export your channel information and recent content to a JSON backup that can be restored or imported to another server hub. This backs up all of your connections, permissions, profile data and several months of posts. This file may be VERY large. Please be patient - it may take several minutes for this download to begin."] = "Exportiert Deine Kanal-Informationen sowie alle zugehörigen Inhalte in eine JSON-Sicherungsdatei. Die sichert alle Verbindungen, Berechtigungen, Profildaten und Deine Beiträge aus mehreren Monaten. Diese Datei kann SEHR groß werden! Bitte habe ein wenig Geduld – es kann mehrere Minuten dauern, bis der Download startet.";
-App::$strings["Export your posts from a given year."] = "Exportiert die Beiträge des angegebenen Jahres.";
-App::$strings["You may also export your posts and conversations for a particular year or month. Adjust the date in your browser location bar to select other dates. If the export fails (possibly due to memory exhaustion on your server hub), please try again selecting a more limited date range."] = "Du kannst auch die Beiträge und Konversationen eines bestimmten Jahres oder Monats exportieren. Ändere das Datum in der Adresszeile Deines Browsers, um andere Zeiträume zu wählen. Falls der Export fehlschlägt (vermutlich, weil auf diesem Hub nicht genügend Speicher zur Verfügung steht), versuche es noch einmal mit einer kleineren Zeitspanne.";
-App::$strings["To select all posts for a given year, such as this year, visit <a href=\"%1\$s\">%2\$s</a>"] = "Um alle Beiträge eines bestimmten Jahres, zum Beispiel dieses Jahres, auszuwählen, klicke <a href=\"%1\$s\">%2\$s</a>.";
-App::$strings["To select all posts for a given month, such as January of this year, visit <a href=\"%1\$s\">%2\$s</a>"] = "Um alle Beiträge eines bestimmten Monats auszuwählen, zum Beispiel vom Januar diesen Jahres, klicke <a href=\"%1\$s\">%2\$s</a>.";
-App::$strings["These content files may be imported or restored by visiting <a href=\"%1\$s\">%2\$s</a> on any site containing your channel. For best results please import or restore these in date order (oldest first)."] = "Diese Inhalts-Sicherungen können wiederhergestellt werden, indem Du <a href=\"%1\$s\">%2\$s</a> auf jeglichem Hub besuchst, der diesen Kanal enthält. Das funktioniert am besten, wenn Du dabei die zeitliche Reihenfolge einhältst, also die Sicherungen für den ältesten Zeitraum zuerst importierst.";
-App::$strings["Permissions denied."] = "Berechtigung verweigert.";
-App::$strings["l, F j"] = "l, j. F";
-App::$strings["Link to Source"] = "Link zur Quelle";
-App::$strings["Edit Event"] = "Termin bearbeiten";
-App::$strings["Create Event"] = "Termin anlegen";
-App::$strings["Export"] = "Exportieren";
-App::$strings["Import"] = "Import";
-App::$strings["Today"] = "Heute";
-App::$strings["# Accounts"] = "Anzahl der Konten";
-App::$strings["# blocked accounts"] = "Anzahl der blockierten Konten";
-App::$strings["# expired accounts"] = "Anzahl der abgelaufenen Konten";
-App::$strings["# expiring accounts"] = "Anzahl der ablaufenden Konten";
-App::$strings["# Channels"] = "Anzahl der Kanäle";
-App::$strings["# primary"] = "Anzahl der primären Kanäle";
-App::$strings["# clones"] = "Anzahl der Klone";
-App::$strings["Message queues"] = "Nachrichten-Warteschlangen";
-App::$strings["Your software should be updated"] = "Die installierte Software sollte aktualisiert werden";
-App::$strings["Summary"] = "Zusammenfassung";
-App::$strings["Registered accounts"] = "Registrierte Konten";
-App::$strings["Pending registrations"] = "Ausstehende Registrierungen";
-App::$strings["Registered channels"] = "Registrierte Kanäle";
-App::$strings["Active plugins"] = "Aktive Plug-Ins";
-App::$strings["Version"] = "Version";
-App::$strings["Repository version (master)"] = "Repository-Version (master)";
-App::$strings["Repository version (dev)"] = "Repository-Version (dev)";
-App::$strings["Remote privacy information not available."] = "Privatsphäre-Einstellungen anderer Nutzer sind nicht verfügbar.";
-App::$strings["Visible to:"] = "Sichtbar für:";
-App::$strings["No service class restrictions found."] = "Keine Dienstklassenbeschränkungen gefunden.";
+App::$strings["No ratings"] = "Keine Bewertungen";
+App::$strings["Ratings"] = "Bewertungen";
+App::$strings["Rating: "] = "Bewertung: ";
+App::$strings["Website: "] = "Webseite: ";
+App::$strings["Description: "] = "Beschreibung: ";
App::$strings["Import Webpage Elements"] = "Webseitenelemente importieren";
App::$strings["Import selected"] = "Import ausgewählt";
App::$strings["Export Webpage Elements"] = "Webseitenelemente exportieren";
@@ -1187,47 +1339,31 @@ App::$strings["Error opening zip file"] = "Fehler beim Öffnen der ZIP-Datei";
App::$strings["Invalid folder path."] = "Ungültiger Ordnerpfad.";
App::$strings["No webpage elements detected."] = "Keine Webseitenelemente erkannt.";
App::$strings["Import complete."] = "Import abgeschlossen.";
-App::$strings["Channel removals are not allowed within 48 hours of changing the account password."] = "Innerhalb von 48 Stunden nach einer Änderung des Passworts können keine Kanäle gelöscht werden.";
-App::$strings["Remove This Channel"] = "Diesen Kanal löschen";
-App::$strings["This channel will be completely removed from the network. "] = "Dieser Kanal wird vollständig aus dem Netzwerk gelöscht.";
-App::$strings["Remove this channel and all its clones from the network"] = "Lösche diesen Kanal und all seine Klone aus dem Netzwerk";
-App::$strings["By default only the instance of the channel located on this hub will be removed from the network"] = "Standardmäßig wird der Kanal nur auf diesem Server gelöscht, seine Klone verbleiben im Netzwerk";
-App::$strings["Remove Channel"] = "Kanal löschen";
-App::$strings["Files: shared with me"] = "Dateien, die mit mir geteilt wurden";
-App::$strings["NEW"] = "NEU";
-App::$strings["Remove all files"] = "Alle Dateien löschen";
-App::$strings["Remove this file"] = "Diese Datei löschen";
-App::$strings["Not found"] = "Nicht gefunden";
-App::$strings["Invalid channel"] = "Ungültiger Kanal";
-App::$strings["Error retrieving wiki"] = "Fehler beim Abrufen des Wiki";
-App::$strings["Error creating zip file export folder"] = "Fehler bei der Erzeugung des Zip-Datei Export-Verzeichnisses ";
-App::$strings["Error downloading wiki: "] = "Fehler beim Herunterladen des Wiki:";
-App::$strings["Wikis"] = "Wikis";
-App::$strings["Download"] = "Herunterladen";
-App::$strings["Wiki name"] = "Name des Wiki";
-App::$strings["Content type"] = "Inhaltstyp";
-App::$strings["Create a status post for this wiki"] = "Erzeuge einen Statusbeitrag für dieses Wiki";
-App::$strings["Wiki not found"] = "Wiki nicht gefunden";
-App::$strings["Rename page"] = "Seite umbenennen";
-App::$strings["Error retrieving page content"] = "Fehler beim Abrufen des Seiteninhalts";
-App::$strings["Revision Comparison"] = "Revisionsvergleich";
-App::$strings["Revert"] = "Rückgängig machen";
-App::$strings["Choose an available wiki from the list on the left."] = "Wähle ein vorhandenes Wiki aus der Liste auf der linken Seite aus.";
-App::$strings["Source"] = "Quelle";
-App::$strings["New page name"] = "Neuer Seitenname";
-App::$strings["Embed image from photo albums"] = "Bild aus Fotoalben einbetten";
-App::$strings["Embed an image from your albums"] = "Betten Sie ein Bild aus Ihren Alben ein";
-App::$strings["OK"] = "Ok";
-App::$strings["Choose images to embed"] = "Wählen Sie Bilder zum Einbetten aus";
-App::$strings["Choose an album"] = "Wählen Sie ein Album aus";
-App::$strings["Choose a different album..."] = "Wählen Sie ein anderes Album aus...";
-App::$strings["Error getting album list"] = "Fehler beim Holen der Albenliste";
-App::$strings["Error getting photo link"] = "Fehler beim Holen des Fotolinks";
-App::$strings["Error getting album"] = "Fehler beim Holen des Albums";
-App::$strings["Error creating wiki. Invalid name."] = "Fehler beim Erstellen des Wiki. Ungültiger Name.";
-App::$strings["Wiki created, but error creating Home page."] = "Das Wiki wurde erzeugt, aber es gab einen Fehler bei der Erstellung der Startseite";
-App::$strings["Error creating wiki"] = "Fehler beim Erstellen des Wiki";
-App::$strings["New page created"] = "Neue Seite erstellt";
+App::$strings["Channel name changes are not allowed within 48 hours of changing the account password."] = "Innerhalb von 48 Stunden nach einer Änderung des Konto-Passworts können Kanäle nicht umbenannt werden.";
+App::$strings["Reserved nickname. Please choose another."] = "Reservierter Kurzname. Bitte wähle einen anderen.";
+App::$strings["Nickname has unsupported characters or is already being used on this site."] = "Der Spitzname enthält nicht-unterstütze Zeichen oder wird bereits auf dieser Seite genutzt.";
+App::$strings["Change channel nickname/address"] = "Kanalname/-adresse ändern";
+App::$strings["Any/all connections on other networks will be lost!"] = "Jegliche/alle Verbindungen zu anderen Netzwerken gehen verloren!";
+App::$strings["New channel address"] = "Neue Kanaladresse";
+App::$strings["Rename Channel"] = "Kanal umbenennen";
+App::$strings["Item is not editable"] = "Element kann nicht bearbeitet werden.";
+App::$strings["Edit post"] = "Bearbeite Beitrag";
+App::$strings["Invalid message"] = "Ungültige Beitrags-ID (mid)";
+App::$strings["no results"] = "keine Ergebnisse";
+App::$strings["channel sync processed"] = "Kanal-Sync verarbeitet";
+App::$strings["queued"] = "zur Warteschlange hinzugefügt";
+App::$strings["posted"] = "zugestellt";
+App::$strings["accepted for delivery"] = "für Zustellung akzeptiert";
+App::$strings["updated"] = "aktualisiert";
+App::$strings["update ignored"] = "Aktualisierung ignoriert";
+App::$strings["permission denied"] = "Zugriff verweigert";
+App::$strings["recipient not found"] = "Empfänger nicht gefunden.";
+App::$strings["mail recalled"] = "Mail widerrufen";
+App::$strings["duplicate mail received"] = "Doppelte Mail erhalten";
+App::$strings["mail delivered"] = "Mail zugestellt";
+App::$strings["Delivery report for %1\$s"] = "Zustellungsbericht für %1\$s";
+App::$strings["Options"] = "Optionen";
+App::$strings["Redeliver"] = "Erneut zustellen";
App::$strings["Failed to create source. No channel selected."] = "Konnte die Quelle nicht anlegen. Kein Kanal ausgewählt.";
App::$strings["Source created."] = "Quelle erstellt.";
App::$strings["Source updated."] = "Quelle aktualisiert.";
@@ -1240,264 +1376,220 @@ App::$strings["Only import content with these words (one per line)"] = "Importie
App::$strings["Leave blank to import all public content"] = "Leer lassen, um alle öffentlichen Beiträge zu importieren";
App::$strings["Channel Name"] = "Name des Kanals";
App::$strings["Add the following categories to posts imported from this source (comma separated)"] = "Füge die folgenden Kategorien zu Beiträgen, die aus dieser Quelle importiert werden, hinzu (kommagetrennt)";
-App::$strings["Optional"] = "Optional";
App::$strings["Source not found."] = "Quelle nicht gefunden.";
App::$strings["Edit Source"] = "Quelle bearbeiten";
App::$strings["Delete Source"] = "Quelle löschen";
App::$strings["Source removed"] = "Quelle gelöscht";
App::$strings["Unable to remove source."] = "Konnte die Quelle nicht löschen.";
-App::$strings["%1\$s is following %2\$s's %3\$s"] = "%1\$s folgt nun %2\$ss %3\$s";
-App::$strings["%1\$s stopped following %2\$s's %3\$s"] = "%1\$s folgt %2\$ss %3\$s nicht mehr";
+App::$strings["Like/Dislike"] = "Mögen/Nicht mögen";
+App::$strings["This action is restricted to members."] = "Diese Aktion kann nur von Mitgliedern ausgeführt werden.";
+App::$strings["Please <a href=\"rmagic\">login with your \$Projectname ID</a> or <a href=\"register\">register as a new \$Projectname member</a> to continue."] = "Um fortzufahren <a href=\"rmagic\">melde Dich bitte mit Deiner \$Projectname-ID an</a> oder <a href=\"register\">registriere Dich als neues \$Projectname-Mitglied</a>.";
+App::$strings["Invalid request."] = "Ungültige Anfrage.";
+App::$strings["channel"] = "Kanal";
+App::$strings["thing"] = "Sache";
+App::$strings["Channel unavailable."] = "Kanal nicht vorhanden.";
+App::$strings["Previous action reversed."] = "Die vorherige Aktion wurde rückgängig gemacht.";
+App::$strings["%1\$s likes %2\$s's %3\$s"] = "%1\$s gefällt %2\$ss %3\$s";
+App::$strings["%1\$s doesn't like %2\$s's %3\$s"] = "%1\$s gefällt %2\$ss %3\$s nicht";
+App::$strings["%1\$s agrees with %2\$s's %3\$s"] = "%1\$s stimmt %2\$ss %3\$s zu";
+App::$strings["%1\$s doesn't agree with %2\$s's %3\$s"] = "%1\$s lehnt %2\$ss %3\$s ab";
+App::$strings["%1\$s abstains from a decision on %2\$s's %3\$s"] = "%1\$s enthält sich zu %2\$ss %3\$s";
+App::$strings["%1\$s is attending %2\$s's %3\$s"] = "%1\$s nimmt an %2\$ss %3\$s teil";
+App::$strings["%1\$s is not attending %2\$s's %3\$s"] = "%1\$s nimmt an %2\$ss %3\$s nicht teil";
+App::$strings["%1\$s may attend %2\$s's %3\$s"] = "%1\$s nimmt vielleicht an %2\$ss %3\$s teil";
+App::$strings["Action completed."] = "Aktion durchgeführt.";
+App::$strings["Thank you."] = "Vielen Dank.";
+App::$strings["%d rating"] = array(
+ 0 => "%d Bewertung",
+ 1 => "%d Bewertungen",
+);
+App::$strings["Gender: "] = "Geschlecht:";
+App::$strings["Status: "] = "Status:";
+App::$strings["Homepage: "] = "Webseite:";
+App::$strings["Age:"] = "Alter:";
+App::$strings["Location:"] = "Ort:";
+App::$strings["Description:"] = "Beschreibung:";
+App::$strings["Hometown:"] = "Heimatstadt:";
+App::$strings["About:"] = "Über:";
+App::$strings["Connect"] = "Verbinden";
+App::$strings["Public Forum:"] = "Öffentliches Forum:";
+App::$strings["Keywords: "] = "Schlüsselwörter:";
+App::$strings["Don't suggest"] = "Nicht vorschlagen";
+App::$strings["Common connections:"] = "Gemeinsame Verbindungen:";
+App::$strings["Global Directory"] = "Globales Verzeichnis";
+App::$strings["Local Directory"] = "Lokales Verzeichnis";
+App::$strings["Finding:"] = "Ergebnisse:";
+App::$strings["Channel Suggestions"] = "Kanal-Vorschläge";
+App::$strings["next page"] = "nächste Seite";
+App::$strings["previous page"] = "vorherige Seite";
+App::$strings["Sort options"] = "Sortieroptionen";
+App::$strings["Alphabetic"] = "alphabetisch";
+App::$strings["Reverse Alphabetic"] = "Entgegengesetzt alphabetisch";
+App::$strings["Newest to Oldest"] = "Neueste zuerst";
+App::$strings["Oldest to Newest"] = "Älteste zuerst";
+App::$strings["No entries (some entries may be hidden)."] = "Keine Einträge gefunden (einige könnten versteckt sein).";
+App::$strings["Xchan Lookup"] = "Xchan-Suche";
+App::$strings["Lookup xchan beginning with (or webbie): "] = "Nach xchans oder Webbies (Kanal-Adressen) suchen, die wie folgt beginnen:";
App::$strings["No suggestions available. If this is a new site, please try again in 24 hours."] = "Keine Vorschläge vorhanden. Wenn das ein neuer Server ist, versuche es in 24 Stunden noch einmal.";
App::$strings["Ignore/Hide"] = "Ignorieren/Verstecken";
-App::$strings["post"] = "Beitrag";
-App::$strings["comment"] = "Kommentar";
-App::$strings["%1\$s tagged %2\$s's %3\$s with %4\$s"] = "%1\$s hat %2\$ss %3\$s mit %4\$s verschlagwortet";
-App::$strings["Additional Features"] = "Zusätzliche Funktionen";
-App::$strings["Name is required"] = "Name ist erforderlich";
-App::$strings["Key and Secret are required"] = "Schlüssel und Geheimnis werden benötigt";
-App::$strings["Add application"] = "Anwendung hinzufügen";
-App::$strings["Name of application"] = "Name der Anwendung";
-App::$strings["Consumer Key"] = "Consumer Key";
-App::$strings["Automatically generated - change if desired. Max length 20"] = "Automatisch erzeugt – ändern, falls erwünscht. Maximale Länge 20";
-App::$strings["Consumer Secret"] = "Consumer Secret";
-App::$strings["Redirect"] = "Umleitung";
-App::$strings["Redirect URI - leave blank unless your application specifically requires this"] = "Umleitungs-URl – lasse das leer, solange Deine Anwendung es nicht explizit erfordert";
-App::$strings["Icon url"] = "Symbol-URL";
-App::$strings["Application not found."] = "Die Anwendung wurde nicht gefunden.";
-App::$strings["Connected Apps"] = "Verbundene Apps";
-App::$strings["Client key starts with"] = "Client Key beginnt mit";
-App::$strings["No name"] = "Kein Name";
-App::$strings["Remove authorization"] = "Authorisierung aufheben";
-App::$strings["This channel is limited to %d tokens"] = "Dieser Kanal ist auf %d Token begrenzt";
-App::$strings["Name and Password are required."] = "Name und Passwort sind erforderlich.";
-App::$strings["Token saved."] = "Token gespeichert.";
-App::$strings["Use this form to create temporary access identifiers to share things with non-members. These identities may be used in Access Control Lists and visitors may login using these credentials to access private content."] = "Mit diesem Formular kannst Du temporäre Zugangs-IDs anlegen, um Inhalte mit Nicht-Mitgliedern zu teilen. Die IDs können in Berechtigungslisten (ACLs) verwendet werden, und Besucher können sich damit einloggen, um auf private Inhalte zuzugreifen.";
-App::$strings["You may also provide <em>dropbox</em> style access links to friends and associates by adding the Login Password to any specific site URL as shown. Examples:"] = "Du kannst auch <em>Dropbox</em>-ähnliche Zugriffslinks an Andere weitergeben, indem du das Login-Passwort an eine entsprechende URL anhängst wie nachfolgend gezeigt. Beispiele:";
-App::$strings["Guest Access Tokens"] = "Gastzugangstoken";
-App::$strings["Login Name"] = "Anmeldename";
-App::$strings["Login Password"] = "Anmeldepasswort";
-App::$strings["Expires (yyyy-mm-dd)"] = "Läuft ab (jjjj-mm-tt)";
-App::$strings["Not valid email."] = "Keine gültige E-Mail Adresse.";
-App::$strings["Protected email address. Cannot change to that email."] = "Geschützte E-Mail Adresse. Diese kann nicht verändert werden.";
-App::$strings["System failure storing new email. Please try again."] = "Systemfehler während des Speicherns der neuen Mail. Bitte versuche es noch einmal.";
-App::$strings["Technical skill level updated"] = "Technische Qualifikationsstufe aktualisiert";
-App::$strings["Password verification failed."] = "Passwortüberprüfung fehlgeschlagen.";
-App::$strings["Passwords do not match. Password unchanged."] = "Kennwörter stimmen nicht überein. Kennwort nicht verändert.";
-App::$strings["Empty passwords are not allowed. Password unchanged."] = "Leere Kennwörter sind nicht erlaubt. Kennwort nicht verändert.";
-App::$strings["Password changed."] = "Kennwort geändert.";
-App::$strings["Password update failed. Please try again."] = "Kennwortänderung fehlgeschlagen. Bitte versuche es noch einmal.";
-App::$strings["Account Settings"] = "Konto-Einstellungen";
-App::$strings["Current Password"] = "Aktuelles Passwort";
-App::$strings["Enter New Password"] = "Gib ein neues Passwort ein";
-App::$strings["Confirm New Password"] = "Bestätige das neue Passwort";
-App::$strings["Leave password fields blank unless changing"] = "Lasse die Passwort-Felder leer, außer Du möchtest das Passwort ändern";
-App::$strings["Your technical skill level"] = "Deine technische Qualifikationsstufe";
-App::$strings["Used to provide a member experience matched to your comfort level"] = "Dies wird verwendet, um Dir eine Benutzererfahrung passend zu Deiner technischen Qualifikationsstufe zu bieten.";
-App::$strings["Email Address:"] = "Email Adresse:";
-App::$strings["Remove this account including all its channels"] = "Dieses Konto inklusive all seiner Kanäle löschen";
-App::$strings["Settings updated."] = "Einstellungen aktualisiert.";
-App::$strings["Nobody except yourself"] = "Niemand außer Dir selbst";
-App::$strings["Only those you specifically allow"] = "Nur die, denen Du es explizit erlaubst";
-App::$strings["Approved connections"] = "Angenommene Verbindungen";
-App::$strings["Any connections"] = "Beliebige Verbindungen";
-App::$strings["Anybody on this website"] = "Jeder auf dieser Website";
-App::$strings["Anybody in this network"] = "Alle \$Projectname-Mitglieder";
-App::$strings["Anybody authenticated"] = "Jeder authentifizierte";
-App::$strings["Anybody on the internet"] = "Jeder im Internet";
-App::$strings["Publish your default profile in the network directory"] = "Standard-Profil im Netzwerk-Verzeichnis veröffentlichen";
-App::$strings["Allow us to suggest you as a potential friend to new members?"] = "Dürfen wir Dich neuen Mitgliedern als potentiellen Kontakt vorschlagen?";
-App::$strings["Your channel address is"] = "Deine Kanal-Adresse lautet";
-App::$strings["Your files/photos are accessible via WebDAV at"] = "Deine Dateien/Fotos sind via WebDAV verfügbar auf";
-App::$strings["Channel Settings"] = "Kanal-Einstellungen";
-App::$strings["Basic Settings"] = "Grundeinstellungen";
-App::$strings["Full Name:"] = "Voller Name:";
-App::$strings["Your Timezone:"] = "Ihre Zeitzone:";
-App::$strings["Default Post Location:"] = "Standardstandort:";
-App::$strings["Geographical location to display on your posts"] = "Geografischer Ort, der bei Deinen Beiträgen angezeigt werden soll";
-App::$strings["Use Browser Location:"] = "Standort des Browsers verwenden:";
-App::$strings["Adult Content"] = "Nicht jugendfreie Inhalte";
-App::$strings["This channel frequently or regularly publishes adult content. (Please tag any adult material and/or nudity with #NSFW)"] = "Dieser Kanal veröffentlicht regelmäßig Inhalte, die für Minderjährige ungeeignet sind. (Bitte markiere solche Inhalte mit dem Schlagwort #NSFW)";
-App::$strings["Security and Privacy Settings"] = "Sicherheits- und Datenschutz-Einstellungen";
-App::$strings["Your permissions are already configured. Click to view/adjust"] = "Deine Zugriffsrechte sind schon konfiguriert. Klicke hier, um sie zu betrachten oder zu ändern";
-App::$strings["Hide my online presence"] = "Meine Online-Präsenz verbergen";
-App::$strings["Prevents displaying in your profile that you are online"] = "Verhindert die Anzeige Deines Online-Status in deinem Profil";
-App::$strings["Simple Privacy Settings:"] = "Einfache Privatsphäre-Einstellungen";
-App::$strings["Very Public - <em>extremely permissive (should be used with caution)</em>"] = "Komplett offen – <em>extrem ungeschützt (mit großer Vorsicht verwenden!)</em>";
-App::$strings["Typical - <em>default public, privacy when desired (similar to social network permissions but with improved privacy)</em>"] = "Typisch – <em>Standard öffentlich, Privatsphäre, wo sie erwünscht ist (ähnlich den Einstellungen in sozialen Netzwerken, aber mit besser geschützter Privatsphäre)</em>";
-App::$strings["Private - <em>default private, never open or public</em>"] = "Privat – <em>Standard privat, nie offen oder öffentlich</em>";
-App::$strings["Blocked - <em>default blocked to/from everybody</em>"] = "Blockiert – <em>Alle standardmäßig blockiert</em>";
-App::$strings["Allow others to tag your posts"] = "Erlaube anderen, Deine Beiträge zu verschlagworten";
-App::$strings["Often used by the community to retro-actively flag inappropriate content"] = "Wird oft von der Community genutzt um rückwirkend anstößigen Inhalt zu markieren";
-App::$strings["Channel Permission Limits"] = "Kanal-Berechtigungslimits";
-App::$strings["Expire other channel content after this many days"] = "Den Inhalt anderer Kanäle nach dieser Anzahl Tage verfallen lassen";
-App::$strings["0 or blank to use the website limit."] = "0 oder leer lassen, um den voreingestellten Wert der Webseite zu verwenden.";
-App::$strings["This website expires after %d days."] = "Diese Webseite läuft nach %d Tagen ab.";
-App::$strings["This website does not expire imported content."] = "Diese Webseite lässt importierte Inhalte nicht verfallen.";
-App::$strings["The website limit takes precedence if lower than your limit."] = "Das Verfallslimit der Webseite hat Vorrang, wenn es niedriger als Deines hier ist.";
-App::$strings["Maximum Friend Requests/Day:"] = "Maximale Kontaktanfragen pro Tag:";
-App::$strings["May reduce spam activity"] = "Kann die Spam-Aktivität verringern";
-App::$strings["Default Access Control List (ACL)"] = "Standard-Zugriffsberechtigungsliste (ACL)";
-App::$strings["Use my default audience setting for the type of object published"] = "Verwende Deine eingestellte Standard-Zielgruppe des jeweiligen Inhaltstyps";
-App::$strings["Channel permissions category:"] = "Zugriffsrechte-Kategorie des Kanals:";
-App::$strings["Maximum private messages per day from unknown people:"] = "Maximale Anzahl privater Nachrichten pro Tag von unbekannten Leuten:";
-App::$strings["Useful to reduce spamming"] = "Nützlich, um Spam zu verringern";
-App::$strings["Notification Settings"] = "Benachrichtigungs-Einstellungen";
-App::$strings["By default post a status message when:"] = "Sende standardmäßig Status-Nachrichten, wenn:";
-App::$strings["accepting a friend request"] = "Du eine Verbindungsanfrage annimmst";
-App::$strings["joining a forum/community"] = "Du einem Forum beitrittst";
-App::$strings["making an <em>interesting</em> profile change"] = "Du eine <em>interessante</em> Änderung an Deinem Profil vornimmst";
-App::$strings["Send a notification email when:"] = "Eine E-Mail-Benachrichtigung senden, wenn:";
-App::$strings["You receive a connection request"] = "Du eine Verbindungsanfrage erhältst";
-App::$strings["Your connections are confirmed"] = "Eine Verbindung bestätigt wurde";
-App::$strings["Someone writes on your profile wall"] = "Jemand auf Deine Pinnwand schreibt";
-App::$strings["Someone writes a followup comment"] = "Jemand einen Beitrag kommentiert";
-App::$strings["You receive a private message"] = "Du eine private Nachricht erhältst";
-App::$strings["You receive a friend suggestion"] = "Du einen Kontaktvorschlag erhältst";
-App::$strings["You are tagged in a post"] = "Du in einem Beitrag erwähnt wurdest";
-App::$strings["You are poked/prodded/etc. in a post"] = "Du in einem Beitrag angestupst/geknufft/o.ä. wurdest";
-App::$strings["Show visual notifications including:"] = "Visuelle Benachrichtigungen anzeigen für:";
-App::$strings["Unseen grid activity"] = "Ungesehene Netzwerk-Aktivität";
-App::$strings["Unseen channel activity"] = "Ungesehene Kanal-Aktivität";
-App::$strings["Unseen private messages"] = "Ungelesene persönliche Nachrichten";
-App::$strings["Recommended"] = "Empfohlen";
-App::$strings["Upcoming events"] = "Baldige Termine";
-App::$strings["Events today"] = "Heutige Termine";
-App::$strings["Upcoming birthdays"] = "Baldige Geburtstage";
-App::$strings["Not available in all themes"] = "Nicht in allen Themes verfügbar";
-App::$strings["System (personal) notifications"] = "System – (persönliche) Benachrichtigungen";
-App::$strings["System info messages"] = "System – Info-Nachrichten";
-App::$strings["System critical alerts"] = "System – kritische Warnungen";
-App::$strings["New connections"] = "Neue Verbindungen";
-App::$strings["System Registrations"] = "System – Registrierungen";
-App::$strings["Also show new wall posts, private messages and connections under Notices"] = "Neue Pinnwand-Nachrichten, private Nachrichten und Verbindungen unter Benachrichtigungen anzeigen";
-App::$strings["Notify me of events this many days in advance"] = "Benachrichtige mich zu Terminen so viele Tage im Voraus";
-App::$strings["Must be greater than 0"] = "Muss größer als 0 sein";
-App::$strings["Advanced Account/Page Type Settings"] = "Erweiterte Account- und Seitenart-Einstellungen";
-App::$strings["Change the behaviour of this account for special situations"] = "Ändere das Verhalten dieses Accounts unter speziellen Umständen";
-App::$strings["Miscellaneous Settings"] = "Sonstige Einstellungen";
-App::$strings["Default photo upload folder"] = "Voreingestellter Ordner für hochgeladene Fotos";
-App::$strings["%Y - current year, %m - current month"] = "%Y - aktuelles Jahr, %m - aktueller Monat";
-App::$strings["Default file upload folder"] = "Voreingestellter Ordner für hochgeladene Dateien";
-App::$strings["Personal menu to display in your channel pages"] = "Eigenes Menü zur Anzeige auf den Seiten deines Kanals";
-App::$strings["Remove this channel."] = "Diesen Kanal löschen";
-App::$strings["Firefox Share \$Projectname provider"] = "\$Projectname-Provider für Firefox Share";
-App::$strings["Start calendar week on monday"] = "Montag als erster Tag der Kalenderwoche";
-App::$strings["No special theme for mobile devices"] = "Keine spezielle Theme für mobile Geräte";
-App::$strings["%s - (Experimental)"] = "%s – (experimentell)";
-App::$strings["Display Settings"] = "Anzeige-Einstellungen";
-App::$strings["Theme Settings"] = "Theme-Einstellungen";
-App::$strings["Custom Theme Settings"] = "Benutzerdefinierte Theme-Einstellungen";
-App::$strings["Content Settings"] = "Inhaltseinstellungen";
-App::$strings["Display Theme:"] = "Anzeige-Theme:";
-App::$strings["Select scheme"] = "Schema wählen";
-App::$strings["Mobile Theme:"] = "Mobile Theme:";
-App::$strings["Preload images before rendering the page"] = "Bilder im voraus laden, bevor die Seite angezeigt wird";
-App::$strings["The subjective page load time will be longer but the page will be ready when displayed"] = "Die empfundene Ladezeit wird sich erhöhen, aber dafür ist das Layout stabil, sobald eine Seite angezeigt wird";
-App::$strings["Enable user zoom on mobile devices"] = "Zoom auf Mobilgeräten aktivieren";
-App::$strings["Update browser every xx seconds"] = "Browser alle xx Sekunden aktualisieren";
-App::$strings["Minimum of 10 seconds, no maximum"] = "Minimum 10 Sekunden, kein Maximum";
-App::$strings["Maximum number of conversations to load at any time:"] = "Maximale Anzahl von Unterhaltungen, die auf einmal geladen werden sollen:";
-App::$strings["Maximum of 100 items"] = "Maximum: 100 Beiträge";
-App::$strings["Show emoticons (smilies) as images"] = "Emoticons (Smilies) als Bilder anzeigen";
-App::$strings["Manual conversation updates"] = "Manuelle Konversationsaktualisierung";
-App::$strings["Default is automatic, which may increase screen jumping"] = "Voreinstellung ist Automatisch, was aber das Springen der Seitenanzeige erhöhen kann.";
-App::$strings["Link post titles to source"] = "Beitragstitel zum Originalbeitrag verlinken";
-App::$strings["System Page Layout Editor - (advanced)"] = "System-Seitenlayout-Editor (für Experten)";
-App::$strings["Use blog/list mode on channel page"] = "Blog-/Listenmodus auf der Kanalseite verwenden";
-App::$strings["(comments displayed separately)"] = "(Kommentare werden separat angezeigt)";
-App::$strings["Use blog/list mode on grid page"] = "Blog-/Listenmodus auf der Netzwerkseite verwenden";
-App::$strings["Channel page max height of content (in pixels)"] = "Maximale Höhe von Beitragsblöcken auf der Kanalseite (in Pixeln)";
-App::$strings["click to expand content exceeding this height"] = "Blöcke, deren Inhalt diese Höhe überschreitet, können per Klick vergrößert werden.";
-App::$strings["Grid page max height of content (in pixels)"] = "Maximale Höhe (in Pixel) des Inhalts der Netzwerkseite";
-App::$strings["No feature settings configured"] = "Keine Funktions-Einstellungen konfiguriert";
-App::$strings["Feature/Addon Settings"] = "Funktions-/Addon-Einstellungen";
+App::$strings["Unable to find your hub."] = "Konnte Deinen Server nicht finden.";
+App::$strings["Post successful."] = "Veröffentlichung erfolgreich.";
+App::$strings["Unable to lookup recipient."] = "Konnte den Empfänger nicht finden.";
+App::$strings["Unable to communicate with requested channel."] = "Die Kommunikation mit dem ausgewählten Kanal ist fehlgeschlagen.";
+App::$strings["Cannot verify requested channel."] = "Verifizierung des angeforderten Kanals fehlgeschlagen.";
+App::$strings["Selected channel has private message restrictions. Send failed."] = "Der ausgewählte Kanal hat Einschränkungen bzgl. privater Nachrichten. Senden fehlgeschlagen.";
+App::$strings["Messages"] = "Nachrichten";
+App::$strings["message"] = "Nachricht";
+App::$strings["Message recalled."] = "Nachricht widerrufen.";
+App::$strings["Conversation removed."] = "Unterhaltung gelöscht.";
+App::$strings["Expires YYYY-MM-DD HH:MM"] = "Verfällt YYYY-MM-DD HH;MM";
+App::$strings["Requested channel is not in this network"] = "Angeforderter Kanal ist nicht in diesem Netzwerk.";
+App::$strings["Send Private Message"] = "Private Nachricht senden";
+App::$strings["To:"] = "An:";
+App::$strings["Subject:"] = "Betreff:";
+App::$strings["Attach file"] = "Datei anhängen";
+App::$strings["Send"] = "Absenden";
+App::$strings["Set expiration date"] = "Verfallsdatum";
+App::$strings["Delete message"] = "Nachricht löschen";
+App::$strings["Delivery report"] = "Zustellungsbericht";
+App::$strings["Recall message"] = "Nachricht widerrufen";
+App::$strings["Message has been recalled."] = "Die Nachricht wurde widerrufen.";
+App::$strings["Delete Conversation"] = "Unterhaltung löschen";
+App::$strings["No secure communications available. You <strong>may</strong> be able to respond from the sender's profile page."] = "Keine sichere Kommunikation verfügbar. <strong>Eventuell</strong> kannst Du auf der Profilseite des Absenders antworten.";
+App::$strings["Send Reply"] = "Antwort senden";
+App::$strings["Your message for %s (%s):"] = "Deine Nachricht für %s (%s):";
+App::$strings["Public Hubs"] = "Öffentliche Hubs";
+App::$strings["The listed hubs allow public registration for the \$Projectname network. All hubs in the network are interlinked so membership on any of them conveys membership in the network as a whole. Some hubs may require subscription or provide tiered service plans. The hub itself <strong>may</strong> provide additional details."] = "Die hier aufgeführten Hubs sind öffentlich und erlauben die Registrierung im \$Projectname Netzwerk. Alle Hubs dieses Netzwerks sind miteinander verbunden, so dass die Mitgliedschaft auf einem Hub die Verbindung zu beliebigen Seiten und Kanälen auf anderen Hubs ermöglicht. Es könnte sein, dass einige dieser Hubs kostenpflichtig sind oder abgestufte, je nach Umfang kostenpflichtige Mitgliedschaften anbieten. Auf den Seiten der einzelnen Hubs <strong>könnten</strong> jeweils nähere Informationen dazu stehen.";
+App::$strings["Hub URL"] = "Hub-URL";
+App::$strings["Access Type"] = "Zugriffstyp";
+App::$strings["Registration Policy"] = "Registrierungsrichtlinien";
+App::$strings["Stats"] = "Statistiken";
+App::$strings["Software"] = "Software";
+App::$strings["Rate"] = "Bewerten";
+App::$strings["webpage"] = "Webseite";
+App::$strings["block"] = "Block";
+App::$strings["layout"] = "Layout";
+App::$strings["menu"] = "Menü";
+App::$strings["%s element installed"] = "Element für %s installiert";
+App::$strings["%s element installation failed"] = "Installation des Elements %s fehlgeschlagen";
+App::$strings["Select a bookmark folder"] = "Lesezeichenordner wählen";
+App::$strings["Save Bookmark"] = "Lesezeichen speichern";
+App::$strings["URL of bookmark"] = "URL des Lesezeichens";
+App::$strings["Or enter new bookmark folder name"] = "Oder gib einen neuen Namen für den Lesezeichenordner ein";
+App::$strings["Enter a folder name"] = "Gib einen Ordnernamen ein";
+App::$strings["or select an existing folder (doubleclick)"] = "oder wähle einen vorhanden Ordner aus (Doppelklick)";
+App::$strings["Save to Folder"] = "In Ordner speichern";
+App::$strings["Fetching URL returns error: %1\$s"] = "Abrufen der URL gab einen Fehler zurück: %1\$s";
+App::$strings["Maximum daily site registrations exceeded. Please try again tomorrow."] = "Maximale Anzahl täglicher Neuanmeldungen erreicht. Bitte versuche es morgen noch einmal.";
+App::$strings["Please indicate acceptance of the Terms of Service. Registration failed."] = "Bitte stimme den Nutzungsbedingungen zu. Registrierung fehlgeschlagen.";
+App::$strings["Passwords do not match."] = "Passwörter stimmen nicht überein.";
+App::$strings["Registration successful. Please check your email for validation instructions."] = "Registrierung erfolgreich. Eine E-Mail mit weiteren Anweisungen wurde an Dich gesendet.";
+App::$strings["Your registration is pending approval by the site owner."] = "Deine Registrierung muss noch vom Betreiber der Seite freigegeben werden.";
+App::$strings["Your registration can not be processed."] = "Deine Registrierung konnte nicht verarbeitet werden.";
+App::$strings["Registration on this hub is disabled."] = "Die Registrierung auf diesem Hub ist nicht möglich.";
+App::$strings["Registration on this hub is by approval only."] = "Eine Registrierung auf diesem Hub erfordert die Zustimmung durch den Administrator.";
+App::$strings["<a href=\"pubsites\">Register at another affiliated hub.</a>"] = "<a href=\"pubsites\">Registriere Dich auf einem der anderen verbundenen Hubs.</a>";
+App::$strings["This site has exceeded the number of allowed daily account registrations. Please try again tomorrow."] = "Die maximale Anzahl täglicher Registrierungen auf diesem Server wurde überschritten. Bitte versuche es morgen noch einmal.";
+App::$strings["I accept the %s for this website"] = "Ich akzeptiere die %s für diese Webseite";
+App::$strings["I am over 13 years of age and accept the %s for this website"] = "Ich bin älter als 13 Jahre und akzeptiere die %s dieser Webseite";
+App::$strings["Your email address"] = "Ihre E-Mail Adresse";
+App::$strings["Choose a password"] = "Passwort";
+App::$strings["Please re-enter your password"] = "Bitte gib Dein Passwort noch einmal ein";
+App::$strings["Please enter your invitation code"] = "Bitte trage Deinen Einladungs-Code ein";
+App::$strings["no"] = "nein";
+App::$strings["yes"] = "ja";
+App::$strings["Membership on this site is by invitation only."] = "Mitgliedschaft auf dieser Seite ist nur nach vorheriger Einladung möglich.";
+App::$strings["Register"] = "Registrieren";
+App::$strings["This site may require email verification after submitting this form. If you are returned to a login page, please check your email for instructions."] = "Diese Seite verlangt möglicherweise eine Emailbestätigung nach dem Absenden des Formulars. Wenn Du auf eine Login-Seite zurückgeleitet wirst, prüfe bitte Deinen Posteingang auf neue Mails mit entsprechenden Hinweisen.";
+App::$strings["Cover Photos"] = "Cover Foto";
+App::$strings["female"] = "weiblich";
+App::$strings["%1\$s updated her %2\$s"] = "%1\$s hat ihr %2\$s aktualisiert";
+App::$strings["male"] = "männlich";
+App::$strings["%1\$s updated his %2\$s"] = "%1\$s hat sein %2\$s aktualisiert";
+App::$strings["%1\$s updated their %2\$s"] = "%1\$s hat sein/ihr %2\$s aktualisiert";
+App::$strings["cover photo"] = "Cover Foto";
+App::$strings["Upload Cover Photo"] = "Cover Foto hochladen";
+App::$strings["Documentation Search"] = "Suche in der Dokumentation";
+App::$strings["About"] = "Über";
+App::$strings["Administrators"] = "Administratoren";
+App::$strings["Developers"] = "Entwickler";
+App::$strings["Tutorials"] = "Tutorials";
+App::$strings["\$Projectname Documentation"] = "\$Projectname-Dokumentation";
+App::$strings["Contents"] = "Inhalt";
+App::$strings["Item has been removed."] = "Der Beitrag wurde entfernt.";
App::$strings["Tag removed"] = "Schlagwort entfernt";
App::$strings["Remove Item Tag"] = "Schlagwort entfernen";
App::$strings["Select a tag to remove: "] = "Schlagwort zum Entfernen auswählen:";
-App::$strings["Thing updated"] = "Sache aktualisiert";
-App::$strings["Object store: failed"] = "Speichern des Objekts fehlgeschlagen";
-App::$strings["Thing added"] = "Sache hinzugefügt";
-App::$strings["OBJ: %1\$s %2\$s %3\$s"] = "OBJ: %1\$s %2\$s %3\$s";
-App::$strings["Show Thing"] = "Sache anzeigen";
-App::$strings["item not found."] = "Eintrag nicht gefunden";
-App::$strings["Edit Thing"] = "Sache bearbeiten";
-App::$strings["Select a profile"] = "Wähle ein Profil";
-App::$strings["Post an activity"] = "Aktivitätsnachricht senden";
-App::$strings["Only sends to viewers of the applicable profile"] = "Nur an Betrachter des ausgewählten Profils senden";
-App::$strings["Name of thing e.g. something"] = "Name der Sache, z. B. irgendwas";
-App::$strings["URL of thing (optional)"] = "URL der Sache (optional)";
-App::$strings["URL for photo of thing (optional)"] = "URL eines Fotos der Sache (optional)";
-App::$strings["Add Thing to your Profile"] = "Die Sache Deinem Profil hinzufügen";
-App::$strings["Your service plan only allows %d channels."] = "Dein Vertrag erlaubt nur %d Kanäle.";
-App::$strings["Cloned channel not found. Import failed."] = "Geklonter Kanal nicht gefunden. Import fehlgeschlagen.";
-App::$strings["No channel. Import failed."] = "Kein Kanal. Import fehlgeschlagen.";
-App::$strings["Import completed."] = "Import abgeschlossen.";
-App::$strings["You must be logged in to use this feature."] = "Du musst angemeldet sein um diese Funktion zu nutzen.";
-App::$strings["Import Channel"] = "Kanal importieren";
-App::$strings["Use this form to import an existing channel from a different server/hub. You may retrieve the channel identity from the old server/hub via the network or provide an export file."] = "Verwende dieses Formular, um einen existierenden Kanal von einem anderen Hub zu importieren. Du kannst den Kanal direkt vom bisherigen Hub über das Netzwerk oder aus einer exportierten Sicherheitskopie importieren.";
-App::$strings["Or provide the old server/hub details"] = "Oder gib die Details Deines bisherigen \$Projectname-Hubs ein";
-App::$strings["Your old identity address (xyz@example.com)"] = "Bisherige Kanal-Adresse (xyz@example.com)";
-App::$strings["Your old login email address"] = "Deine alte Login-E-Mail-Adresse";
-App::$strings["Your old login password"] = "Dein altes Passwort";
-App::$strings["For either option, please choose whether to make this hub your new primary address, or whether your old location should continue this role. You will be able to post from either location, but only one can be marked as the primary location for files, photos, and media."] = "Egal, welche Option Du wählst – bitte lege fest, ob dieser Server die neue primäre Adresse dieses Kanals sein soll, oder ob der bisherige \$Projectname-Hub diese Rolle weiterhin wahrnimmt. Du kannst von beiden Servern aus posten, aber nur einer kann der primäre Ort Deiner Dateien, Fotos und Medien sein.";
-App::$strings["Make this hub my primary location"] = "Dieser $Pojectname-Hub ist mein primärer Hub.";
-App::$strings["Import existing posts if possible (experimental - limited by available memory"] = "Importiere bestehende Beiträge falls möglich (experimentell - begrenzt durch zur Verfügung stehenden Speicher";
-App::$strings["This process may take several minutes to complete. Please submit the form only once and leave this page open until finished."] = "Dieser Vorgang kann einige Minuten dauern. Bitte sende das Formular nur einmal ab und lasse diese Seite bis zur Fertigstellung offen.";
+App::$strings["No such group"] = "Gruppe nicht gefunden";
+App::$strings["No such channel"] = "Kanal nicht gefunden";
+App::$strings["forum"] = "Forum";
+App::$strings["Search Results For:"] = "Suchergebnisse für:";
+App::$strings["Privacy group is empty"] = "Gruppe ist leer";
+App::$strings["Privacy group: "] = "Gruppe:";
+App::$strings["Invalid connection."] = "Ungültige Verbindung.";
+App::$strings["Invalid channel."] = "Ungültiger Kanal.";
+App::$strings["network"] = "Netzwerk";
+App::$strings["\$Projectname"] = "\$Projectname";
+App::$strings["Welcome to %s"] = "Willkommen auf %s";
+App::$strings["Permission Denied."] = "Zugriff verweigert.";
+App::$strings["File not found."] = "Datei nicht gefunden.";
+App::$strings["Edit file permissions"] = "Dateiberechtigungen bearbeiten";
+App::$strings["Set/edit permissions"] = "Berechtigungen setzen/ändern";
+App::$strings["Include all files and sub folders"] = "Alle Dateien und Unterverzeichnisse einbinden";
+App::$strings["Return to file list"] = "Zurück zur Dateiliste";
+App::$strings["Copy/paste this code to attach file to a post"] = "Diesen Code kopieren und einfügen, um die Datei an einen Beitrag anzuhängen";
+App::$strings["Copy/paste this URL to link file from a web page"] = "Diese URL verwenden, um von einer Webseite aus auf die Datei zu verlinken";
+App::$strings["Share this file"] = "Diese Datei freigeben";
+App::$strings["Show URL to this file"] = "URL zu dieser Datei anzeigen";
+App::$strings["Show in your contacts shared folder"] = "Im geteilten Ordner Deiner Kontakte anzeigen";
+App::$strings["No channel."] = "Kein Kanal.";
+App::$strings["No connections in common."] = "Keine gemeinsamen Verbindungen.";
+App::$strings["View Common Connections"] = "Zeige gemeinsame Verbindungen";
App::$strings["No connections."] = "Keine Verbindungen.";
App::$strings["Visit %s's profile [%s]"] = "%ss Profil [%s] besuchen";
App::$strings["View Connections"] = "Verbindungen anzeigen";
-App::$strings["Source of Item"] = "Quelle des Elements";
-App::$strings["Room not found"] = "Chatraum nicht gefunden";
-App::$strings["Leave Room"] = "Raum verlassen";
-App::$strings["Delete Room"] = "Raum löschen";
-App::$strings["I am away right now"] = "Ich bin gerade nicht da";
-App::$strings["I am online"] = "Ich bin online";
-App::$strings["Bookmark this room"] = "Lesezeichen für diesen Raum setzen";
-App::$strings["New Chatroom"] = "Neuer Chatraum";
-App::$strings["Chatroom name"] = "Chatraumname";
-App::$strings["Expiration of chats (minutes)"] = "Verfall von Chats (Minuten)";
-App::$strings["%1\$s's Chatrooms"] = "%1\$ss Chaträume";
-App::$strings["No chatrooms available"] = "Keine Chaträume verfügbar";
-App::$strings["Expiration"] = "Verfall";
-App::$strings["min"] = "min";
-App::$strings["Xchan Lookup"] = "Xchan-Suche";
-App::$strings["Lookup xchan beginning with (or webbie): "] = "Nach xchans oder Webbies (Kanal-Adressen) suchen, die wie folgt beginnen:";
-App::$strings["Calendar entries imported."] = "Kalendereinträge wurden importiert.";
-App::$strings["No calendar entries found."] = "Keine Kalendereinträge gefunden.";
-App::$strings["Event can not end before it has started."] = "Termin-Ende liegt vor dem Beginn.";
-App::$strings["Unable to generate preview."] = "Vorschau konnte nicht erzeugt werden.";
-App::$strings["Event title and start time are required."] = "Titel und Startzeit des Termins sind erforderlich.";
-App::$strings["Event not found."] = "Termin nicht gefunden.";
-App::$strings["Edit event title"] = "Termintitel bearbeiten";
-App::$strings["Event title"] = "Termintitel";
-App::$strings["Categories (comma-separated list)"] = "Kategorien (Kommagetrennte Liste)";
-App::$strings["Edit Category"] = "Kategorie bearbeiten";
-App::$strings["Category"] = "Kategorie";
-App::$strings["Edit start date and time"] = "Startdatum und -zeit bearbeiten";
-App::$strings["Start date and time"] = "Startdatum und -zeit";
-App::$strings["Finish date and time are not known or not relevant"] = "Enddatum und -zeit sind unbekannt oder irrelevant";
-App::$strings["Edit finish date and time"] = "Enddatum und -zeit bearbeiten";
-App::$strings["Finish date and time"] = "Enddatum und -zeit";
-App::$strings["Adjust for viewer timezone"] = "An die Zeitzone des Betrachters anpassen";
-App::$strings["Important for events that happen in a particular place. Not practical for global holidays."] = "Wichtig für Veranstaltungen die an bestimmten Orten stattfinden. Nicht sinnvoll für globale Feiertage / Ferien.";
-App::$strings["Edit Description"] = "Beschreibung bearbeiten";
-App::$strings["Edit Location"] = "Ort bearbeiten";
-App::$strings["Permission settings"] = "Berechtigungs-Einstellungen";
-App::$strings["Advanced Options"] = "Weitere Optionen";
-App::$strings["Edit event"] = "Termin bearbeiten";
-App::$strings["Delete event"] = "Termin löschen";
-App::$strings["calendar"] = "Kalender";
-App::$strings["Month"] = "Monat";
-App::$strings["Week"] = "Woche";
-App::$strings["Day"] = "Tag";
-App::$strings["Event removed"] = "Termin gelöscht";
-App::$strings["Failed to remove event"] = "Termin konnte nicht gelöscht werden";
-App::$strings["Missing room name"] = "Der Chatraum hat keinen Namen";
-App::$strings["Duplicate room name"] = "Name des Chatraums bereits vergeben";
-App::$strings["Invalid room specifier."] = "Ungültiger Raumbezeichner.";
-App::$strings["Room not found."] = "Chatraum konnte nicht gefunden werden.";
-App::$strings["Room is full"] = "Der Chatraum ist voll";
+App::$strings["Blocked accounts"] = "Blockierte Benutzerkonten";
+App::$strings["Expired accounts"] = "Abgelaufene Benutzerkonten";
+App::$strings["Expiring accounts"] = "Ablaufende Benutzerkonten";
+App::$strings["Clones"] = "Klone";
+App::$strings["Message queues"] = "Nachrichten-Warteschlangen";
+App::$strings["Your software should be updated"] = "Die installierte Software sollte aktualisiert werden";
+App::$strings["Summary"] = "Zusammenfassung";
+App::$strings["Registered accounts"] = "Registrierte Konten";
+App::$strings["Pending registrations"] = "Ausstehende Registrierungen";
+App::$strings["Registered channels"] = "Registrierte Kanäle";
+App::$strings["Active plugins"] = "Aktive Plug-Ins";
+App::$strings["Version"] = "Version";
+App::$strings["Repository version (master)"] = "Repository-Version (master)";
+App::$strings["Repository version (dev)"] = "Repository-Version (dev)";
+App::$strings["No service class restrictions found."] = "Keine Dienstklassenbeschränkungen gefunden.";
+App::$strings["Website:"] = "Webseite:";
+App::$strings["Remote Channel [%s] (not yet known on this site)"] = "Kanal [%s] (auf diesem Server noch unbekannt)";
+App::$strings["Rating (this information is public)"] = "Bewertung (öffentlich sichtbar)";
+App::$strings["Optionally explain your rating (this information is public)"] = "Optional kannst du deine Bewertung erklären (öffentlich sichtbar)";
+App::$strings["Edit Card"] = "Karte bearbeiten";
+App::$strings["No valid account found."] = "Kein gültiges Konto gefunden.";
+App::$strings["Password reset request issued. Check your email."] = "Zurücksetzen des Passworts eingeleitet. Schau in Deine E-Mails.";
+App::$strings["Site Member (%s)"] = "Nutzer (%s)";
+App::$strings["Password reset requested at %s"] = "Passwort-Rücksetzung auf %s angefordert";
+App::$strings["Request could not be verified. (You may have previously submitted it.) Password reset failed."] = "Die Anfrage konnte nicht verifiziert werden. (Vielleicht hast Du schon einmal auf den Link in der E-Mail geklickt?) Passwort-Rücksetzung fehlgeschlagen.";
+App::$strings["Password Reset"] = "Zurücksetzen des Kennworts";
+App::$strings["Your password has been reset as requested."] = "Dein Passwort wurde wie angefordert neu erstellt.";
+App::$strings["Your new password is"] = "Dein neues Passwort lautet";
+App::$strings["Save or copy your new password - and then"] = "Speichere oder kopiere Dein neues Passwort – und dann";
+App::$strings["click here to login"] = "Klicke hier, um dich anzumelden";
+App::$strings["Your password may be changed from the <em>Settings</em> page after successful login."] = "Dein Passwort kann unter <em>Einstellungen</em> nach einer erfolgreichen Anmeldung geändert werden.";
+App::$strings["Your password has changed at %s"] = "Auf %s wurde Dein Passwort geändert";
+App::$strings["Forgot your Password?"] = "Kennwort vergessen?";
+App::$strings["Enter your email address and submit to have your password reset. Then check your email for further instructions."] = "Gib Deine E-Mail-Adresse ein, um Dein Passwort zurücksetzen zu lassen. Du erhältst dann weitere Anweisungen per E-Mail.";
+App::$strings["Email Address"] = "E-Mail Adresse";
+App::$strings["Mark all seen"] = "Alle als gelesen markieren";
+App::$strings["0. Beginner/Basic"] = "0. Einsteiger/Basis";
+App::$strings["1. Novice - not skilled but willing to learn"] = "1. Anfänger - unerfahren, aber bereit zu lernen";
+App::$strings["2. Intermediate - somewhat comfortable"] = "2. Fortgeschritten - relativ komfortabel";
+App::$strings["3. Advanced - very comfortable"] = "3. Fortgeschritten - sehr komfortabel";
+App::$strings["4. Expert - I can write computer code"] = "4. Experte - Ich kann Computercode schreiben";
+App::$strings["5. Wizard - I probably know more than you do"] = "5. Zauberer - ich kann wahrscheinlich mehr als Du";
App::$strings["Site Admin"] = "Hub-Administration";
App::$strings["Report Bug"] = "Fehler melden";
App::$strings["View Bookmarks"] = "Lesezeichen ansehen";
@@ -1506,7 +1598,7 @@ App::$strings["Firefox Share"] = "Teilen-Knopf für Firefox";
App::$strings["Remote Diagnostics"] = "Ferndiagnose";
App::$strings["Suggest Channels"] = "Kanäle vorschlagen";
App::$strings["Login"] = "Anmelden";
-App::$strings["Grid"] = "Grid";
+App::$strings["Activity"] = "Aktivität";
App::$strings["Wiki"] = "Wiki";
App::$strings["Channel Home"] = "Mein Kanal";
App::$strings["Events"] = "Termine";
@@ -1522,6 +1614,28 @@ App::$strings["Language"] = "Sprache";
App::$strings["Post"] = "Beitrag schreiben";
App::$strings["Profile Photo"] = "Profilfoto";
App::$strings["Purchase"] = "Kaufen";
+App::$strings["Undelete"] = "Wieder hergestellt";
+App::$strings["Add to app-tray"] = "Zum App-Menü hinzufügen";
+App::$strings["Remove from app-tray"] = "Aus dem App-Menü entfernen";
+App::$strings["__ctx:permcat__ default"] = "Standard";
+App::$strings["__ctx:permcat__ follower"] = "Abonnent";
+App::$strings["__ctx:permcat__ contributor"] = "Beitragender";
+App::$strings["__ctx:permcat__ publisher"] = "Autor";
+App::$strings["(No Title)"] = "(Kein Titel)";
+App::$strings["Wiki page create failed."] = "Anlegen der Wiki-Seite fehlgeschlagen.";
+App::$strings["Wiki not found."] = "Wiki nicht gefunden.";
+App::$strings["Destination name already exists"] = "Zielname bereits vorhanden";
+App::$strings["Page not found"] = "Seite nicht gefunden";
+App::$strings["Error reading page content"] = "Fehler beim Lesen des Seiteninhalts";
+App::$strings["Error reading wiki"] = "Fehler beim Lesen des Wiki";
+App::$strings["Page update failed."] = "Seitenaktualisierung fehlgeschlagen.";
+App::$strings["Nothing deleted"] = "Nichts gelöscht";
+App::$strings["Compare: object not found."] = "Vergleichen: Objekt nicht gefunden.";
+App::$strings["Page updated"] = "Seite aktualisiert";
+App::$strings["Untitled"] = "Ohne Titel";
+App::$strings["Wiki resource_id required for git commit"] = "Die resource_id des Wiki wird benötigt für den git commit.";
+App::$strings["__ctx:wiki_history__ Message"] = "Nachricht";
+App::$strings["Different viewers will see this text differently"] = "Verschiedene Betrachter werden diesen Text unterschiedlich sehen";
App::$strings["Visible to your default audience"] = "Standard-Sichtbarkeit gemäß Kanaleinstellungen";
App::$strings["Only me"] = "Nur ich";
App::$strings["Public"] = "Öffentlich";
@@ -1536,9 +1650,64 @@ App::$strings["This is your default setting for who can view your default channe
App::$strings["This is your default setting for who can view your connections"] = "Dies ist Deine Voreinstellung für die Sichtbarkeit Deiner Verbindungen.";
App::$strings["This is your default setting for who can view your file storage and photos"] = "Dies ist Deine Voreinstellung für die Sichtbarkeit Deiner Dateien und Fotos.";
App::$strings["This is your default setting for the audience of your webpages"] = "Dies ist Deine Voreinstellung für die Sichtbarkeit Deiner Webseiten.";
+App::$strings["Missing room name"] = "Der Chatraum hat keinen Namen";
+App::$strings["Duplicate room name"] = "Name des Chatraums bereits vergeben";
+App::$strings["Invalid room specifier."] = "Ungültiger Raumbezeichner.";
+App::$strings["Room not found."] = "Chatraum konnte nicht gefunden werden.";
+App::$strings["Room is full"] = "Der Chatraum ist voll";
+App::$strings["\$Projectname Notification"] = "\$Projectname-Benachrichtigung";
+App::$strings["\$projectname"] = "\$projectname";
+App::$strings["Thank You,"] = "Danke.";
+App::$strings["%s Administrator"] = "der Administrator von %s";
+App::$strings["%s <!item_type!>"] = "%s <!item_type!>";
+App::$strings["[\$Projectname:Notify] New mail received at %s"] = "[\$Projectname:Benachrichtigung] Neue Mail empfangen auf %s";
+App::$strings["%1\$s, %2\$s sent you a new private message at %3\$s."] = "%1\$s, %2\$s hat Dir eine private Nachricht auf %3\$s gesendet.";
+App::$strings["%1\$s sent you %2\$s."] = "%1\$s hat Dir %2\$s geschickt.";
+App::$strings["a private message"] = "eine private Nachricht";
+App::$strings["Please visit %s to view and/or reply to your private messages."] = "Bitte besuche %s, um die private Nachricht anzusehen und/oder darauf zu antworten.";
+App::$strings["%1\$s, %2\$s commented on [zrl=%3\$s]a %4\$s[/zrl]"] = "%1\$s, %2\$s hat [zrl=%3\$s]einen %4\$s[/zrl] kommentiert";
+App::$strings["%1\$s, %2\$s commented on [zrl=%3\$s]%4\$s's %5\$s[/zrl]"] = "%1\$s, %2\$s hat [zrl=%3\$s]%4\$ss %5\$s[/zrl] kommentiert";
+App::$strings["%1\$s, %2\$s commented on [zrl=%3\$s]your %4\$s[/zrl]"] = "%1\$s, %2\$s hat [zrl=%3\$s]Deinen %4\$s[/zrl] kommentiert";
+App::$strings["[\$Projectname:Notify] Moderated Comment to conversation #%1\$d by %2\$s"] = "[\$Projectname:Benachrichtigung] Moderierter Kommantar in Unterhaltung #%1\$d von %2\$s";
+App::$strings["[\$Projectname:Notify] Comment to conversation #%1\$d by %2\$s"] = "[\$Projectname:Benachrichtigung] Kommentar in Unterhaltung #%1\$d von %2\$s";
+App::$strings["%1\$s, %2\$s commented on an item/conversation you have been following."] = "%1\$s, %2\$s hat eine Unterhaltung kommentiert, der Du folgst.";
+App::$strings["Please visit %s to view and/or reply to the conversation."] = "Bitte besuche %s, um die Unterhaltung anzusehen und/oder zu kommentieren.";
+App::$strings["Please visit %s to approve or reject this comment."] = "Bitte besuche %s, um diesen Kommentar anzunehmen oder abzulehnen.";
+App::$strings["%1\$s, %2\$s liked [zrl=%3\$s]your %4\$s[/zrl]"] = "%1\$s, %2\$s gefällt [zrl=%3\$s]dein %4\$s[/zrl]";
+App::$strings["[\$Projectname:Notify] Like received to conversation #%1\$d by %2\$s"] = "[\$Projectname:Benachrichtigung] Gefällt mir in Unterhaltung #%1\$d von %2\$s erhalten";
+App::$strings["%1\$s, %2\$s liked an item/conversation you created."] = "%1\$s, %2\$s gefällt ein Beitrag oder eine Unterhaltung von Dir";
+App::$strings["[\$Projectname:Notify] %s posted to your profile wall"] = "[\$Projectname:Benachrichtigung] %s schrieb auf Deine Pinnwand";
+App::$strings["%1\$s, %2\$s posted to your profile wall at %3\$s"] = "%1\$s, %2\$s hat auf Deine Pinnwand auf %3\$s geschrieben";
+App::$strings["%1\$s, %2\$s posted to [zrl=%3\$s]your wall[/zrl]"] = "%1\$s, %2\$s hat auf [zrl=%3\$s]Deine Pinnwand[/zrl] geschrieben";
+App::$strings["[\$Projectname:Notify] %s tagged you"] = "[\$Projectname:Benachrichtigung] %s hat Dich erwähnt";
+App::$strings["%1\$s, %2\$s tagged you at %3\$s"] = "%1\$s, %2\$s hat Dich auf %3\$s erwähnt";
+App::$strings["%1\$s, %2\$s [zrl=%3\$s]tagged you[/zrl]."] = "%1\$s, %2\$s [zrl=%3\$s]hat Dich erwähnt[/zrl].";
+App::$strings["[\$Projectname:Notify] %1\$s poked you"] = "[\$Projectname:Benachrichtigung] %1\$s hat Dich angestupst";
+App::$strings["%1\$s, %2\$s poked you at %3\$s"] = "%1\$s, %2\$s hat Dich auf %3\$s angestupst";
+App::$strings["%1\$s, %2\$s [zrl=%2\$s]poked you[/zrl]."] = "%1\$s, %2\$s [zrl=%2\$s]hat Dich angestupst[/zrl].";
+App::$strings["[\$Projectname:Notify] %s tagged your post"] = "[\$Projectname:Benachrichtigung] %s hat Deinen Beitrag verschlagwortet";
+App::$strings["%1\$s, %2\$s tagged your post at %3\$s"] = "%1\$s, %2\$s hat Deinen Beitrag auf %3\$s verschlagwortet";
+App::$strings["%1\$s, %2\$s tagged [zrl=%3\$s]your post[/zrl]"] = "%1\$s, %2\$s hat [zrl=%3\$s]Deinen Beitrag[/zrl] verschlagwortet";
+App::$strings["[\$Projectname:Notify] Introduction received"] = "[\$Projectname:Benachrichtigung] Verbindungsanfrage erhalten";
+App::$strings["%1\$s, you've received an new connection request from '%2\$s' at %3\$s"] = "%1\$s, Du hast eine neue Verbindungsanfrage von '%2\$s' auf %3\$s erhalten";
+App::$strings["%1\$s, you've received [zrl=%2\$s]a new connection request[/zrl] from %3\$s."] = "%1\$s, Du hast [zrl=%2\$s]eine neue Verbindungsanfrage[/zrl] von %3\$s erhalten.";
+App::$strings["You may visit their profile at %s"] = "Du kannst Dir das Profil unter %s ansehen";
+App::$strings["Please visit %s to approve or reject the connection request."] = "Bitte besuche %s , um die Verbindungsanfrage anzunehmen oder abzulehnen.";
+App::$strings["[\$Projectname:Notify] Friend suggestion received"] = "[\$Projectname:Benachrichtigung] Freundschaftsvorschlag erhalten";
+App::$strings["%1\$s, you've received a friend suggestion from '%2\$s' at %3\$s"] = "%1\$s, Du hast einen Kontaktvorschlag von „%2\$s“ auf %3\$s erhalten";
+App::$strings["%1\$s, you've received [zrl=%2\$s]a friend suggestion[/zrl] for %3\$s from %4\$s."] = "%1\$s, Du hast [zrl=%2\$s]einen Kontaktvorschlag[/zrl] für %3\$s von %4\$s erhalten.";
+App::$strings["Name:"] = "Name:";
+App::$strings["Photo:"] = "Foto:";
+App::$strings["Please visit %s to approve or reject the suggestion."] = "Bitte besuche %s um den Vorschlag zu akzeptieren oder abzulehnen.";
+App::$strings["[\$Projectname:Notify]"] = "[\$Projectname:Benachrichtigung]";
+App::$strings["created a new post"] = "Neuer Beitrag wurde erzeugt";
+App::$strings["commented on %s's post"] = "hat %s's Beitrag kommentiert";
+App::$strings["Wiki updated successfully"] = "Wiki erfolgreich aktualisiert";
+App::$strings["Wiki files deleted successfully"] = "Wiki-Dateien erfolgreich gelöscht";
+App::$strings["Update Error at %s"] = "Aktualisierungsfehler auf %s";
+App::$strings["Update %s failed. See error logs."] = "Aktualisierung %s fehlgeschlagen. Details in den Fehlerprotokollen.";
App::$strings["Private Message"] = "Private Nachricht";
App::$strings["Select"] = "Auswählen";
-App::$strings["Save to Folder"] = "In Ordner speichern";
App::$strings["I will attend"] = "Ich werde teilnehmen";
App::$strings["I will not attend"] = "Ich werde nicht teilnehmen";
App::$strings["I might attend"] = "Ich werde vielleicht teilnehmen";
@@ -1575,7 +1744,7 @@ App::$strings["Vote"] = "Abstimmen";
App::$strings["Voting Options"] = "Abstimmungsoptionen";
App::$strings["Save Bookmarks"] = "Favoriten speichern";
App::$strings["Add to Calendar"] = "Zum Kalender hinzufügen";
-App::$strings["Mark all seen"] = "Alle als gelesen markieren";
+App::$strings["This is an unsaved preview"] = "Dies ist eine nicht gespeicherte Vorschau";
App::$strings["%s show all"] = "%s mehr anzeigen";
App::$strings["Bold"] = "Fett";
App::$strings["Italic"] = "Kursiv";
@@ -1583,67 +1752,284 @@ App::$strings["Underline"] = "Unterstrichen";
App::$strings["Quote"] = "Zitat";
App::$strings["Code"] = "Code";
App::$strings["Image"] = "Bild";
+App::$strings["Attach File"] = "Datei anhängen";
App::$strings["Insert Link"] = "Link einfügen";
App::$strings["Video"] = "Video";
-App::$strings["\$Projectname Notification"] = "\$Projectname-Benachrichtigung";
-App::$strings["\$projectname"] = "\$projectname";
-App::$strings["Thank You,"] = "Danke.";
-App::$strings["%s Administrator"] = "der Administrator von %s";
-App::$strings["%s <!item_type!>"] = "%s <!item_type!>";
-App::$strings["[\$Projectname:Notify] New mail received at %s"] = "[\$Projectname:Benachrichtigung] Neue Mail empfangen auf %s";
-App::$strings["%1\$s, %2\$s sent you a new private message at %3\$s."] = "%1\$s, %2\$s hat Dir eine private Nachricht auf %3\$s gesendet.";
-App::$strings["%1\$s sent you %2\$s."] = "%1\$s hat Dir %2\$s geschickt.";
-App::$strings["a private message"] = "eine private Nachricht";
-App::$strings["Please visit %s to view and/or reply to your private messages."] = "Bitte besuche %s, um die private Nachricht anzusehen und/oder darauf zu antworten.";
-App::$strings["%1\$s, %2\$s commented on [zrl=%3\$s]a %4\$s[/zrl]"] = "%1\$s, %2\$s hat [zrl=%3\$s]einen %4\$s[/zrl] kommentiert";
-App::$strings["%1\$s, %2\$s commented on [zrl=%3\$s]%4\$s's %5\$s[/zrl]"] = "%1\$s, %2\$s hat [zrl=%3\$s]%4\$ss %5\$s[/zrl] kommentiert";
-App::$strings["%1\$s, %2\$s commented on [zrl=%3\$s]your %4\$s[/zrl]"] = "%1\$s, %2\$s hat [zrl=%3\$s]Deinen %4\$s[/zrl] kommentiert";
-App::$strings["[\$Projectname:Notify] Comment to conversation #%1\$d by %2\$s"] = "[\$Projectname:Benachrichtigung] Kommentar in Unterhaltung #%1\$d von %2\$s";
-App::$strings["%1\$s, %2\$s commented on an item/conversation you have been following."] = "%1\$s, %2\$s hat eine Unterhaltung kommentiert, der Du folgst.";
-App::$strings["Please visit %s to view and/or reply to the conversation."] = "Bitte besuche %s, um die Unterhaltung anzusehen und/oder zu kommentieren.";
-App::$strings["[\$Projectname:Notify] %s posted to your profile wall"] = "[\$Projectname:Benachrichtigung] %s schrieb auf Deine Pinnwand";
-App::$strings["%1\$s, %2\$s posted to your profile wall at %3\$s"] = "%1\$s, %2\$s hat auf Deine Pinnwand auf %3\$s geschrieben";
-App::$strings["%1\$s, %2\$s posted to [zrl=%3\$s]your wall[/zrl]"] = "%1\$s, %2\$s hat auf [zrl=%3\$s]Deine Pinnwand[/zrl] geschrieben";
-App::$strings["[\$Projectname:Notify] %s tagged you"] = "[\$Projectname:Benachrichtigung] %s hat Dich erwähnt";
-App::$strings["%1\$s, %2\$s tagged you at %3\$s"] = "%1\$s, %2\$s hat Dich auf %3\$s erwähnt";
-App::$strings["%1\$s, %2\$s [zrl=%3\$s]tagged you[/zrl]."] = "%1\$s, %2\$s [zrl=%3\$s]hat Dich erwähnt[/zrl].";
-App::$strings["[\$Projectname:Notify] %1\$s poked you"] = "[\$Projectname:Benachrichtigung] %1\$s hat Dich angestupst";
-App::$strings["%1\$s, %2\$s poked you at %3\$s"] = "%1\$s, %2\$s hat Dich auf %3\$s angestupst";
-App::$strings["%1\$s, %2\$s [zrl=%2\$s]poked you[/zrl]."] = "%1\$s, %2\$s [zrl=%2\$s]hat Dich angestupst[/zrl].";
-App::$strings["[\$Projectname:Notify] %s tagged your post"] = "[\$Projectname:Benachrichtigung] %s hat Deinen Beitrag verschlagwortet";
-App::$strings["%1\$s, %2\$s tagged your post at %3\$s"] = "%1\$s, %2\$s hat Deinen Beitrag auf %3\$s verschlagwortet";
-App::$strings["%1\$s, %2\$s tagged [zrl=%3\$s]your post[/zrl]"] = "%1\$s, %2\$s hat [zrl=%3\$s]Deinen Beitrag[/zrl] verschlagwortet";
-App::$strings["[\$Projectname:Notify] Introduction received"] = "[\$Projectname:Benachrichtigung] Verbindungsanfrage erhalten";
-App::$strings["%1\$s, you've received an new connection request from '%2\$s' at %3\$s"] = "%1\$s, Du hast eine neue Verbindungsanfrage von '%2\$s' auf %3\$s erhalten";
-App::$strings["%1\$s, you've received [zrl=%2\$s]a new connection request[/zrl] from %3\$s."] = "%1\$s, Du hast [zrl=%2\$s]eine neue Verbindungsanfrage[/zrl] von %3\$s erhalten.";
-App::$strings["You may visit their profile at %s"] = "Du kannst Dir das Profil unter %s ansehen";
-App::$strings["Please visit %s to approve or reject the connection request."] = "Bitte besuche %s , um die Verbindungsanfrage anzunehmen oder abzulehnen.";
-App::$strings["[\$Projectname:Notify] Friend suggestion received"] = "[\$Projectname:Benachrichtigung] Freundschaftsvorschlag erhalten";
-App::$strings["%1\$s, you've received a friend suggestion from '%2\$s' at %3\$s"] = "%1\$s, Du hast einen Kontaktvorschlag von „%2\$s“ auf %3\$s erhalten";
-App::$strings["%1\$s, you've received [zrl=%2\$s]a friend suggestion[/zrl] for %3\$s from %4\$s."] = "%1\$s, Du hast [zrl=%2\$s]einen Kontaktvorschlag[/zrl] für %3\$s von %4\$s erhalten.";
-App::$strings["Name:"] = "Name:";
-App::$strings["Photo:"] = "Foto:";
-App::$strings["Please visit %s to approve or reject the suggestion."] = "Bitte besuche %s um den Vorschlag zu akzeptieren oder abzulehnen.";
-App::$strings["[\$Projectname:Notify]"] = "[\$Projectname:Benachrichtigung]";
-App::$strings["created a new post"] = "Neuer Beitrag wurde erzeugt";
-App::$strings["commented on %s's post"] = "hat %s's Beitrag kommentiert";
+App::$strings["Your full name (required)"] = "Ihr vollständiger Name (erforderlich)";
+App::$strings["Your email address (required)"] = "Ihre E-Mail-Adresse (erforderlich)";
+App::$strings["Your website URL (optional)"] = "Ihre Webseiten-URL (optional)";
+App::$strings["Remote authentication blocked. You are logged into this site locally. Please logout and retry."] = "Fern-Authentifizierung blockiert. Du bist lokal auf diesem Server angemeldet. Bitte melde Dich ab und versuche es erneut.";
+App::$strings["Welcome %s. Remote authentication successful."] = "Willkommen %s. Entfernte Authentifizierung erfolgreich.";
+App::$strings["parent"] = "Übergeordnetes Verzeichnis";
+App::$strings["Collection"] = "Sammlung";
+App::$strings["Principal"] = "Prinzipal";
+App::$strings["Addressbook"] = "Adressbuch";
+App::$strings["Calendar"] = "Kalender";
+App::$strings["Schedule Inbox"] = "Posteingang für überwachte Kalender";
+App::$strings["Schedule Outbox"] = "Postausgang für überwachte Kalender";
+App::$strings["Total"] = "Summe";
+App::$strings["Shared"] = "Geteilt";
+App::$strings["You are using %1\$s of your available file storage."] = "Sie verwenden %1\$s von Ihrem verfügbaren Dateispeicher.";
+App::$strings["You are using %1\$s of %2\$s available file storage. (%3\$s&#37;)"] = "Sie verwenden %1\$s von %2\$s verfügbarem Dateispeicher. (%3\$s&#37;)";
+App::$strings["WARNING:"] = "WARNUNG:";
+App::$strings["Please use DAV to upload large (video, audio) files.<br>See <a class=\"zrl\" href=\"help/member/member_guide#Cloud_Desktop_Clients\">Cloud Desktop Clients</a>"] = "Bitte verwende DAV, um große Dateien (Audio, Video) hochzuladen.<br>Für weitere Informationen siehe <a class=\"zrl\" href=\"help/member/member_guide#Cloud_Desktop_Clients\">Cloud Desktop Clients</a>";
+App::$strings["Create new folder"] = "Neuen Ordner anlegen";
+App::$strings["Upload file"] = "Datei hochladen";
+App::$strings["Drop files here to immediately upload"] = "Dateien zum sofortigen Hochladen hier fallen lassen";
+App::$strings["Forums"] = "Foren";
+App::$strings["Select Channel"] = "Kanal auswählen";
+App::$strings["Read-write"] = "Lesen-schreiben";
+App::$strings["Read-only"] = "Nur Lesen";
+App::$strings["My Calendars"] = "Meine Kalender";
+App::$strings["Shared Calendars"] = "Geteilte Kalender";
+App::$strings["Share this calendar"] = "Diesen Kalender teilen";
+App::$strings["Calendar name and color"] = "Kalendername und -farbe";
+App::$strings["Create new calendar"] = "Neuen Kalender erstellen";
+App::$strings["Calendar Name"] = "Kalendername";
+App::$strings["Calendar Tools"] = "Kalenderwerkzeuge";
+App::$strings["Import calendar"] = "Kalender importieren";
+App::$strings["Select a calendar to import to"] = "Kalender zum Hineinimportieren auswählen";
+App::$strings["Addressbooks"] = "Adressbücher";
+App::$strings["Addressbook name"] = "Adressbuchname";
+App::$strings["Create new addressbook"] = "Neues Adressbuch erstellen";
+App::$strings["Addressbook Name"] = "Adressbuchname";
+App::$strings["Addressbook Tools"] = "Adressbuchwerkzeuge";
+App::$strings["Import addressbook"] = "Adressbuch importieren";
+App::$strings["Select an addressbook to import to"] = "Adressbuch zum Hineinimportieren auswählen";
+App::$strings["Categories"] = "Kategorien";
+App::$strings["Everything"] = "Alles";
+App::$strings["Events Tools"] = "Kalenderwerkzeuge";
+App::$strings["Export Calendar"] = "Kalender exportieren";
+App::$strings["Import Calendar"] = "Kalender importieren";
+App::$strings["Suggested Chatrooms"] = "Chatraum-Vorschläge";
+App::$strings["Private Mail Menu"] = "Private Nachrichten";
+App::$strings["Combined View"] = "Kombinierte Anzeige";
+App::$strings["Inbox"] = "Eingang";
+App::$strings["Outbox"] = "Ausgang";
+App::$strings["New Message"] = "Neue Nachricht";
+App::$strings["Chatrooms"] = "Chaträume";
+App::$strings["Overview"] = "Übersicht";
+App::$strings["Rating Tools"] = "Bewertungswerkzeuge";
+App::$strings["Rate Me"] = "Bewerte mich";
+App::$strings["View Ratings"] = "Bewertungen ansehen";
+App::$strings["__ctx:widget__ Activity"] = "Aktivität";
+App::$strings["You have %1$.0f of %2$.0f allowed connections."] = "Du bist %1$.0f von maximal %2$.0f erlaubten Verbindungen eingegangen.";
+App::$strings["Add New Connection"] = "Neue Verbindung hinzufügen";
+App::$strings["Enter channel address"] = "Adresse des Kanals eingeben";
+App::$strings["Examples: bob@example.com, https://example.com/barbara"] = "Beispiele: bob@beispiel.com, http://beispiel.com/barbara";
+App::$strings["Wiki List"] = "Wikiliste";
+App::$strings["Archives"] = "Archive";
+App::$strings["Received Messages"] = "Erhaltene Nachrichten";
+App::$strings["Sent Messages"] = "Gesendete Nachrichten";
+App::$strings["Conversations"] = "Konversationen";
+App::$strings["No messages."] = "Keine Nachrichten.";
+App::$strings["Delete conversation"] = "Unterhaltung löschen";
+App::$strings["Chat Members"] = "Chatmitglieder";
+App::$strings["photo/image"] = "Foto/Bild";
+App::$strings["Remove term"] = "Eintrag löschen";
+App::$strings["Saved Searches"] = "Gespeicherte Suchanfragen";
+App::$strings["add"] = "hinzufügen";
+App::$strings["Notes"] = "Notizen";
+App::$strings["Wiki Pages"] = "Wikiseiten";
+App::$strings["Add new page"] = "Neue Seite hinzufügen";
+App::$strings["Page name"] = "Seitenname";
+App::$strings["Refresh"] = "Aktualisieren";
+App::$strings["Tasks"] = "Aufgaben";
+App::$strings["Suggestions"] = "Vorschläge";
+App::$strings["See more..."] = "Mehr anzeigen …";
+App::$strings["Saved Folders"] = "Gespeicherte Ordner";
+App::$strings["Click to show more"] = "Klick, um mehr anzuzeigen";
+App::$strings["Member registrations waiting for confirmation"] = "Nutzer-Anmeldungen, die auf Bestätigung warten";
+App::$strings["Inspect queue"] = "Warteschlange kontrollieren";
+App::$strings["DB updates"] = "DB-Aktualisierungen";
+App::$strings["Admin"] = "Administration";
+App::$strings["Plugin Features"] = "Plug-In Funktionen";
+App::$strings["Account settings"] = "Konto-Einstellungen";
+App::$strings["Channel settings"] = "Kanal-Einstellungen";
+App::$strings["Additional features"] = "Zusätzliche Funktionen";
+App::$strings["Feature/Addon settings"] = "Plugin-Einstellungen";
+App::$strings["Display settings"] = "Anzeige-Einstellungen";
+App::$strings["Manage locations"] = "Klon-Adressen verwalten";
+App::$strings["Export channel"] = "Kanal exportieren";
+App::$strings["Connected apps"] = "Verbundene Apps";
+App::$strings["Permission Groups"] = "Berechtigungsrollen";
+App::$strings["Premium Channel Settings"] = "Premium-Kanal-Einstellungen";
+App::$strings["Bookmarked Chatrooms"] = "Gespeicherte Chatrooms";
+App::$strings["New Network Activity"] = "Neue Netzwerk-Aktivitäten";
+App::$strings["New Network Activity Notifications"] = "Benachrichtigungen für neue Netzwerk-Aktivitäten";
+App::$strings["View your network activity"] = "Zeige Deine Netzwerk-Aktivitäten";
+App::$strings["Mark all notifications read"] = "Alle Benachrichtigungen als gesehen markieren";
+App::$strings["New Home Activity"] = "Neue Kanal-Aktivitäten";
+App::$strings["New Home Activity Notifications"] = "Benachrichtigungen für neue Kanal-Aktivitäten";
+App::$strings["View your home activity"] = "Zeige Deine Kanal-Aktivitäten";
+App::$strings["Mark all notifications seen"] = "Alle Benachrichtigungen als gesehen markieren";
+App::$strings["New Mails"] = "Neue Mails";
+App::$strings["New Mails Notifications"] = "Benachrichtigungen für neue Mails";
+App::$strings["View your private mails"] = "Zeige Deine persönlichen Mails";
+App::$strings["Mark all messages seen"] = "Alle Mails als gelesen markieren";
+App::$strings["New Events"] = "Neue Termine";
+App::$strings["New Events Notifications"] = "Benachrichtigungen für neue Termine";
+App::$strings["View events"] = "Termine ansehen";
+App::$strings["Mark all events seen"] = "Markiere alle Termine als gesehen";
+App::$strings["New Connections Notifications"] = "Benachrichtigungen für neue Verbindungen";
+App::$strings["View all connections"] = "Zeige alle Verbindungen";
+App::$strings["New Files"] = "Neue Dateien";
+App::$strings["New Files Notifications"] = "Benachrichtigungen für neue Dateien";
+App::$strings["Notices"] = "Benachrichtigungen";
+App::$strings["View all notices"] = "";
+App::$strings["Mark all notices seen"] = "";
+App::$strings["New Registrations"] = "Neue Registrierungen";
+App::$strings["New Registrations Notifications"] = "Benachrichtigungen für neue Registrierungen";
+App::$strings["Public Stream Notifications"] = "Benachrichtigungen für öffentlichen Beitrags-Stream";
+App::$strings["View the public stream"] = "Zeige öffentlichen Beitrags-Stream";
+App::$strings["Loading..."] = "Lädt ...";
+App::$strings["Source channel not found."] = "Quellkanal nicht gefunden.";
+App::$strings["Create an account to access services and applications"] = "Erstelle ein Konto, um auf Dienste und Anwendungen zugreifen zu können.";
+App::$strings["Logout"] = "Abmelden";
+App::$strings["Login/Email"] = "Anmelden/E-Mail";
+App::$strings["Password"] = "Kennwort";
+App::$strings["Remember me"] = "Angaben speichern";
+App::$strings["Forgot your password?"] = "Passwort vergessen?";
+App::$strings["toggle mobile"] = "auf/von mobile Ansicht wechseln";
+App::$strings["[\$Projectname] Website SSL error for %s"] = "[\$Projectname] Webseiten-SSL-Fehler für %s";
+App::$strings["Website SSL certificate is not valid. Please correct."] = "Das SSL-Zertifikat der Website ist nicht gültig. Bitte beheben.";
+App::$strings["[\$Projectname] Cron tasks not running on %s"] = "[\$Projectname] Cron-Jobs laufen nicht auf %s";
+App::$strings["Cron/Scheduled tasks not running."] = "Cron-Aufgaben laufen nicht.";
+App::$strings["never"] = "Nie";
+App::$strings["Focus (Hubzilla default)"] = "Focus (Voreinstellung für Hubzilla)";
+App::$strings["Theme settings"] = "Design-Einstellungen";
+App::$strings["Narrow navbar"] = "Schmale Navigationsleiste";
+App::$strings["Navigation bar background color"] = "Hintergrundfarbe der Navigationsleiste";
+App::$strings["Navigation bar icon color "] = "Farbe für die Icons der Navigationsleiste";
+App::$strings["Navigation bar active icon color "] = "Farbe für aktive Icons der Navigationsleiste";
+App::$strings["Link color"] = "Linkfarbe";
+App::$strings["Set font-color for banner"] = "Farbe der Schrift des Banners";
+App::$strings["Set the background color"] = "Hintergrundfarbe";
+App::$strings["Set the background image"] = "Hintergrundbild";
+App::$strings["Set the background color of items"] = "Hintergrundfarbe für Beiträge";
+App::$strings["Set the background color of comments"] = "Hintergrundfarbe für Kommentare";
+App::$strings["Set font-size for the entire application"] = "Schriftgröße für die gesamte Anwendung";
+App::$strings["Examples: 1rem, 100%, 16px"] = "Beispiele: 1rem, 100%, 16px";
+App::$strings["Set font-color for posts and comments"] = "Schriftfarbe für Beiträge und Kommentare";
+App::$strings["Set radius of corners"] = "Ecken-Radius";
+App::$strings["Example: 4px"] = "Beispiel: 4px";
+App::$strings["Set shadow depth of photos"] = "Schattentiefe von Fotos";
+App::$strings["Set maximum width of content region in pixel"] = "Maximalbreite des Inhaltsbereichs in Pixel festlegen";
+App::$strings["Leave empty for default width"] = "Leer lassen für Standardbreite";
+App::$strings["Left align page content"] = "Seiteninhalt linksbündig anzeigen";
+App::$strings["Set size of conversation author photo"] = "Größe der Avatare von Themenstartern";
+App::$strings["Set size of followup author photos"] = "Größe der Avatare von Kommentatoren";
+App::$strings["Errors encountered deleting database table "] = "Beim Löschen der Datenbanktabelle sind Fehler aufgetreten.";
+App::$strings["Submit Settings"] = "Einstellungen absenden";
+App::$strings["Drop tables when uninstalling?"] = "Lösche Tabellen beim Deinstallieren?";
+App::$strings["If checked, the Rendezvous database tables will be deleted when the plugin is uninstalled."] = "Wenn ausgewählt, werden die Rendezvous-Tabellen in der Datenbank gelöscht, sobald das Plugin deinstalliert wird.";
+App::$strings["Mapbox Access Token"] = "Mapbox Zugangs-Token";
+App::$strings["If you enter a Mapbox access token, it will be used to retrieve map tiles from Mapbox instead of the default OpenStreetMap tile server."] = "Wenn Du ein Mapbox Zugangs-Token eingibst, werden die Kartendaten (Kacheln) damit von Mapbox geladen, anstatt von OpenStreetMap, welches die Voreinstellung ist.";
+App::$strings["Rendezvous"] = "Rendezvous";
+App::$strings["This identity has been deleted by another member due to inactivity. Please press the \"New identity\" button or refresh the page to register a new identity. You may use the same name."] = "Diese Identität wurde von einem anderen Mitglied aufgrund von Inaktivität gelöscht. Bitte klicke auf \"Neue Identität\" oder aktualisiere die Website im Browser, um eine neue Identität zu registrieren. Du kannst dabei den selben Namen verwenden.";
+App::$strings["Welcome to Rendezvous!"] = "Willkommen bei Rendezvous!";
+App::$strings["Enter your name to join this rendezvous. To begin sharing your location with the other members, tap the GPS control. When your location is discovered, a red dot will appear and others will be able to see you on the map."] = "Gib Deinen Namen ein, um diesem Rendezvous beizutreten. Um Deinen Standort mit anderen Mitgliedern zu teilen, klicke auf das GPS Symbol. Sobald Dein Standort ermittelt ist, erscheint ein roter Punkt, und die Anderen werden Dich auf der Karte sehen können.";
+App::$strings["Let's meet here"] = "Lasst uns hier treffen";
+App::$strings["New marker"] = "Neue Markierung";
+App::$strings["Edit marker"] = "Markierung bearbeiten";
+App::$strings["New identity"] = "Neue Identität";
+App::$strings["Delete marker"] = "Markierung löschen";
+App::$strings["Delete member"] = "Mitglied löschen";
+App::$strings["Edit proximity alert"] = "Annäherungsalarm bearbeiten";
+App::$strings["A proximity alert will be issued when this member is within a certain radius of you.<br><br>Enter a radius in meters (0 to disable):"] = "Ein Annäherungsalarm wird ausgelöst werden, sobald sich dieses Mitglied innerhalb eines bestimmten Radius von Dir aufhält.<br><br>Gib einen Radius in Metern ein (0 zum Abschalten der Funktion):";
+App::$strings["distance"] = "Entfernung";
+App::$strings["Proximity alert distance (meters)"] = "Entfernung für Annäherungsalarm (in Metern)";
+App::$strings["A proximity alert will be issued when you are within a certain radius of the marker location.<br><br>Enter a radius in meters (0 to disable):"] = "Ein Annäherungsalarm wird ausgelöst werden, sobald Du Dich innerhalb eines bestimmten Radius der Markierung aufhält.<br><br>Gib einen Radius in Metern ein (0 zum Abschalten der Funktion):";
+App::$strings["Marker proximity alert"] = "Annäherungsalarm für Markierung";
+App::$strings["Reminder note"] = "Erinnerungshinweis";
+App::$strings["Enter a note to be displayed when you are within the specified proximity..."] = "Gib eine Nachricht ein, die angezeigt werden soll, wenn Du Dich in der festgelegten Nähe befindest...";
+App::$strings["Add new rendezvous"] = "Neues Rendezvous hinzufügen";
+App::$strings["Create a new rendezvous and share the access link with those you wish to invite to the group. Those who open the link become members of the rendezvous. They can view other member locations, add markers to the map, or share their own locations with the group."] = "Erstelle ein neues Rendezvous und teile den Zugriffslink mit allen, die Du in die Gruppe einladen möchtest. Die, die den Link öffnen, werden Mitglieder des Rendezvous. Sie können die Standorte der anderen Mitglieder sehen, Marker zur Karte hinzufügen oder ihre eigenen Standorte mit der Gruppe teilen.";
+App::$strings["Some setting"] = "Einige Einstellungen";
+App::$strings["A setting"] = "Eine Einstellung";
+App::$strings["Skeleton Settings"] = "Skeleton Einstellungen";
+App::$strings["GNU-Social Protocol Settings updated."] = "GNU social Protokoll Einstellungen aktualisiert";
+App::$strings["The GNU-Social protocol does not support location independence. Connections you make within that network may be unreachable from alternate channel locations."] = "Das GNU-Social-Protokoll unterstützt keine Server-unabhängigen Identitäten. Verbindungen, die Du mit diesem Netzwerk eingehst, können von anderen Orten (Klonen) dieses Kanals aus unerreichbar sein.";
+App::$strings["Enable the GNU-Social protocol for this channel"] = "Aktiviere das GNU social Protokoll für diesen Kanal";
+App::$strings["GNU-Social Protocol Settings"] = "GNU social Protokoll Einstellungen";
+App::$strings["Follow"] = "Folgen";
+App::$strings["%1\$s is now following %2\$s"] = "%1\$s folgt nun %2\$s";
+App::$strings["Planets Settings updated."] = "Planeten Einstellungen aktualisiert";
+App::$strings["Enable Planets Plugin"] = "Aktiviere Planeten Plugin";
+App::$strings["Planets Settings"] = "Planeten Einstellungen";
+App::$strings["System defaults:"] = "Systemstandardeinstellungen:";
+App::$strings["Preferred Clipart IDs"] = "Bevorzugte Clipart-IDs";
+App::$strings["List of preferred clipart ids. These will be shown first."] = "Liste bevorzugter Clipart-IDs. Diese werden zuerst angezeigt.";
+App::$strings["Default Search Term"] = "Standard-Suchbegriff";
+App::$strings["The default search term. These will be shown second."] = "Der Standard-Suchbegriff. Dieser wird an zweiter Stelle angezeigt.";
+App::$strings["Return After"] = "Zurückkehren nach";
+App::$strings["Page to load after image selection."] = "Die Seite, die nach Auswahl eines Bildes geladen werden soll.";
+App::$strings["Edit Profile"] = "Profil bearbeiten";
+App::$strings["Profile List"] = "Profilliste";
+App::$strings["Order of Preferred"] = "Reihenfolge der Bevorzugten";
+App::$strings["Sort order of preferred clipart ids."] = "Sortierreihenfolge der bevorzugten Clipart-IDs.";
+App::$strings["Newest first"] = "Neueste zuerst";
+App::$strings["As entered"] = "Wie eingegeben";
+App::$strings["Order of other"] = "Sortierung aller anderen";
+App::$strings["Sort order of other clipart ids."] = "Sortierreihenfolge der übrigen Clipart-IDs.";
+App::$strings["Most downloaded first"] = "Meist heruntergeladene zuerst";
+App::$strings["Most liked first"] = "Beliebteste zuerst";
+App::$strings["Preferred IDs Message"] = "Nachricht für bevorzugte IDs";
+App::$strings["Message to display above preferred results."] = "Nachricht, die über den Ergebnissen mit den bevorzugten IDs angezeigt werden soll.";
+App::$strings["Uploaded by: "] = "Hochgeladen von: ";
+App::$strings["Drawn by: "] = "Gezeichnet von: ";
+App::$strings["Or select from a free OpenClipart.org image:"] = "Oder wähle ein freies Bild von OpenClipart.org:";
+App::$strings["Search Term"] = "Suchbegriff";
+App::$strings["Unknown error. Please try again later."] = "Unbekannter Fehler. Bitte versuchen Sie es später erneut.";
+App::$strings["Profile photo updated successfully."] = "Profilfoto erfolgreich aktualisiert.";
+App::$strings["invalid target signature"] = "Ungültige Signatur des Ziels";
App::$strings["Flag Adult Photos"] = "Nicht jugendfreie Fotos markieren";
App::$strings["Provide photo edit option to hide inappropriate photos from default album view"] = "Stellt eine Option zum Verstecken von Fotos mit unangemessenen Inhalten in der Standard-Albumansicht bereit";
-App::$strings["This is a fairly comprehensive and complete guitar chord dictionary which will list most of the available ways to play a certain chord, starting from the base of the fingerboard up to a few frets beyond the twelfth fret (beyond which everything repeats). A couple of non-standard tunings are provided for the benefit of slide players, etc."] = "";
-App::$strings["Chord names start with a root note (A-G) and may include sharps (#) and flats (b). This software will parse most of the standard naming conventions such as maj, min, dim, sus(2 or 4), aug, with optional repeating elements."] = "";
-App::$strings["Valid examples include A, A7, Am7, Amaj7, Amaj9, Ammaj7, Aadd4, Asus2Add4, E7b13b11 ..."] = "Einige gültige Beispiele: A, A7, Am7, Amaj7, Amaj9, Ammaj7, Aadd4, Asus2Add4, E7b13b11 ...";
-App::$strings["Guitar Chords"] = "Gitarrenakkorde";
-App::$strings["The complete online chord dictionary"] = "Das komplette online Akkord-Verzeichnis";
-App::$strings["Tuning"] = "Stimmen";
-App::$strings["Chord name: example: Em7"] = "Beispiel Akkord Name: Em7";
-App::$strings["Show for left handed stringing"] = "Linkshänder-Besaitung anzeigen";
-App::$strings["Quick Reference"] = "Schnellreferenz";
-App::$strings["Diaspora Protocol Settings updated."] = "Diaspora-Protokolleinstellungen aktualisiert.";
-App::$strings["Enable the Diaspora protocol for this channel"] = "Diaspora-Protokoll für diesen Kanal aktivieren";
-App::$strings["Allow any Diaspora member to comment on your public posts"] = "Jedem Diaspora-Mitglied erlauben, Deine öffentlichen Beiträge zu kommentieren";
-App::$strings["Prevent your hashtags from being redirected to other sites"] = "Verhindern, dass Deine hashtags zu anderen Seiten umgeleitet werden";
-App::$strings["Followed hashtags (comma separated, do not include the #)"] = "Verfolgte Hashtags (Komma separierte Liste, ohne die #)";
-App::$strings["Diaspora Protocol Settings"] = "Diaspora-Protokolleinstellungen";
+App::$strings["Post to WordPress"] = "Auf WordPress posten";
+App::$strings["Enable WordPress Post Plugin"] = "Aktiviere das WordPress-Plugin";
+App::$strings["WordPress username"] = "WordPress-Benutzername";
+App::$strings["WordPress password"] = "WordPress-Passwort";
+App::$strings["WordPress API URL"] = "WordPress-API-URL";
+App::$strings["Typically https://your-blog.tld/xmlrpc.php"] = "Normalerweise https://your-blog.tld/xmlrpc.php";
+App::$strings["WordPress blogid"] = "WordPress blogid";
+App::$strings["For multi-user sites such as wordpress.com, otherwise leave blank"] = "Nötig für Mehrbenutzer Seiten wie wordpress.com, andernfalls frei lassen";
+App::$strings["Post to WordPress by default"] = "Standardmäßig auf auf WordPress posten";
+App::$strings["Forward comments (requires hubzilla_wp plugin)"] = "Kommentare weiterleiten (benötigt hubzilla_wp Plugin)";
+App::$strings["WordPress Post Settings"] = "WordPress-Beitragseinstellungen";
+App::$strings["Wordpress Settings saved."] = "Wordpress-Einstellungen gespeichert.";
+App::$strings["This plugin looks in posts for the words/text you specify below, and collapses any content containing those keywords so it is not displayed at inappropriate times, such as sexual innuendo that may be improper in a work setting. It is polite and recommended to tag any content containing nudity with #NSFW. This filter can also match any other word/text you specify, and can thereby be used as a general purpose content filter."] = "Dieses Plugin sucht in Beiträgen nach Wörtern oder Textbausteinen, die Du hier unterhalb einträgst, und faltet alle Beiträge zusammen, in denen es diese Bausteine findet. Auf diese Weise wird verhindert, dass Inhalte, wie z.B. sexuelle Anspielungen, in unpassenden Momenten angezeigt werden. Es gilt als höflich und empfohlen, den #NSFW Tag für Beiträge zu verwenden, bei denen Du davon ausgehen kannst, dass andere sie anstößig finden könnten. Du kannst aber auch beliebige andere Wörter in der Liste angeben und das Plugin so als allgemeinen Inhaltsfilter verwenden.";
+App::$strings["Enable Content filter"] = "Inhaltsfilter aktivieren";
+App::$strings["Comma separated list of keywords to hide"] = "Kommaseparierte Liste von Schlüsselworten die verborgen werden sollen.";
+App::$strings["Word, /regular-expression/, lang=xx, lang!=xx"] = "Wort, /regular-expression/, lang=xx, lang!=xx";
+App::$strings["Not Safe For Work Settings"] = "Not Safe For Work Einstellungen";
+App::$strings["General Purpose Content Filter"] = "Allzweck-Inhaltsfilter";
+App::$strings["NSFW Settings saved."] = "NSFW-Einstellungen gespeichert.";
+App::$strings["Possible adult content"] = "Möglicherweise nicht jugendfreie Inhalte";
+App::$strings["%s - view"] = "%s - ansehen";
+App::$strings["Post to Insanejournal"] = "Bei InsaneJournal veröffentlichen";
+App::$strings["Enable InsaneJournal Post Plugin"] = "Aktiviere das InsaneJournal Plugin";
+App::$strings["InsaneJournal username"] = "InsaneJournal-Benutzername";
+App::$strings["InsaneJournal password"] = "InsaneJournal-Passwort";
+App::$strings["Post to InsaneJournal by default"] = "Standardmäßig bei InsaneJournal veröffentlichen";
+App::$strings["InsaneJournal Post Settings"] = "InsaneJournal-Beitragseinstellungen";
+App::$strings["Insane Journal Settings saved."] = "InsaneJournal-Einstellungen gespeichert.";
+App::$strings["Upload a file"] = "Datei hochladen";
+App::$strings["Drop files here to upload"] = "Dateien zum Hochladen hier fallen lassen";
+App::$strings["Failed"] = "Fehlgeschlagen";
+App::$strings["No files were uploaded."] = "Es wurden keine Dateien hochgeladen.";
+App::$strings["Uploaded file is empty"] = "Hochgeladene Datei ist leer";
+App::$strings["Image exceeds size limit of "] = "Bild überschreitet Größenbeschränkung von ";
+App::$strings["File has an invalid extension, it should be one of "] = "Die Datei hat eine ungültige Endung. Erlaubt sind folgende:";
+App::$strings["Upload was cancelled, or server error encountered"] = "Das Hochladen wurde abgebrochen oder es ist ein Serverfehler aufgetreten.";
+App::$strings["Post to Dreamwidth"] = "Bei Dreamwidth veröffentlichen";
+App::$strings["Enable Dreamwidth Post Plugin"] = "Aktiviere das Dreamwidth-Plugin";
+App::$strings["Dreamwidth username"] = "Dreamwidth-Benutzername";
+App::$strings["Dreamwidth password"] = "Dreamwidth-Passwort";
+App::$strings["Post to Dreamwidth by default"] = "Standardmäßig auf auf Dreamwidth posten";
+App::$strings["Dreamwidth Post Settings"] = "Dreamwidth-Beitragseinstellungen";
+App::$strings["Install Firefox Sharing Tools"] = "Installiere das Firefox Sharing Werkzeug";
+App::$strings["Share content from Firefox to \$Projectname"] = "Inhalte von Firefox nach \$Projectname teilen";
+App::$strings["Install Firefox Sharing Tools to this web browser"] = "Installiere das Firefox Sharing Werkzeug in diesen Webbrowser";
App::$strings["Hubzilla Directory Stats"] = "Hubzilla-Verzeichnisstatistiken";
App::$strings["Total Hubs"] = "Hubs insgesamt";
App::$strings["Hubzilla Hubs"] = "Hubzilla Hubs";
@@ -1658,169 +2044,31 @@ App::$strings["Average Age"] = "Durchschnittsalter";
App::$strings["Known Chatrooms"] = "Bekannte Chaträume";
App::$strings["Known Tags"] = "Bekannte Schlagwörter";
App::$strings["Please note Diaspora and Friendica statistics are merely those **this directory** is aware of, and not all those known in the network. This also applies to chatrooms,"] = "Bitte berücksichtige, dass Diaspora und Friendica Statistiken nur solche einschließen, die **diesem Verzeichnis** bekannt sind, nicht alle im Netzwerk bekannten. Das gilt auch für Chaträume.";
-App::$strings["Project Servers and Resources"] = "Projektserver und -ressourcen";
-App::$strings["Project Creator and Tech Lead"] = "Projektersteller und Technischer Leiter";
-App::$strings["Admin, developer, directorymin, support bloke"] = "Administrator, Entwickler, Verzeichnis Betreibender, Supportleistende";
-App::$strings["And the hundreds of other people and organisations who helped make the Hubzilla possible."] = "Und die hunderte anderen Menschen und Organisationen, die geholfen haben Hubzilla möglich zu machen.";
-App::$strings["The Redmatrix/Hubzilla projects are provided primarily by volunteers giving their time and expertise - and often paying out of pocket for services they share with others."] = "Die Redmatrix/Hubzilla Projekte werden hauptsächlich von Freiwilligen bereitgestellt, die ihre Zeit und Expertise zur Verfügung stellen - und oft aus eigener Tasche für die Dienste zahlen, die sie mit anderen teilen.";
-App::$strings["There is no corporate funding and no ads, and we do not collect and sell your personal information. (We don't control your personal information - <strong>you do</strong>.)"] = "Es gibt keine Finanzierung durch Firmen, keine Werbung und wir verkaufen Deine persönlichen Daten nicht. (Wir kontrollieren Deine persönlichen Daten nicht - <strong>das machst Du</strong>.)";
-App::$strings["Help support our ground-breaking work in decentralisation, web identity, and privacy."] = "Hilf uns bei unserer wegweisenden Arbeit im Bereich der Dezantralisation, von Web-Identitäten und Privatsphäre.";
-App::$strings["Your donations keep servers and services running and also helps us to provide innovative new features and continued development."] = "Die Spenden werden dafür verwendet Server und Dienste am laufen zu halten und helfen desweiteren innovative Neuerungen zu schaffen und die Entwicklung voran zu treiben.";
-App::$strings["Donate"] = "Spenden";
-App::$strings["Choose a project, developer, or public hub to support with a one-time donation"] = "Wähle ein Projekt, einen Entwickler oder einen öffentlichen Hub den du mit einer einmaligen Spende unterstützen willst.";
-App::$strings["Donate Now"] = "Jetzt spenden";
-App::$strings["<strong><em>Or</em></strong> become a project sponsor (Hubzilla Project only)"] = "<strong><em>Oder</em></strong> werde ein Unterstützer des Projekts (ausschließlich Hubzilla)";
-App::$strings["Please indicate if you would like your first name or full name (or nothing) to appear in our sponsor listing"] = "Bitte teile uns mit ob dein kompletter Name oder dein Vorname (oder gar nichts) auf unserer Sponsoren-Seite veröffentlicht werden soll.";
-App::$strings["Sponsor"] = "Sponsor";
-App::$strings["Special thanks to: "] = "Besonderer Dank an: ";
-App::$strings["Post to Dreamwidth"] = "Bei Dreamwidth veröffentlichen";
-App::$strings["Enable Dreamwidth Post Plugin"] = "Aktiviere das Dreamwidth-Plugin";
-App::$strings["Dreamwidth username"] = "Dreamwidth-Benutzername";
-App::$strings["Dreamwidth password"] = "Dreamwidth-Passwort";
-App::$strings["Post to Dreamwidth by default"] = "Standardmäßig auf auf Dreamwidth posten";
-App::$strings["Dreamwidth Post Settings"] = "Dreamwidth-Beitragseinstellungen";
-App::$strings["Flattr this!"] = "Flattr this!";
-App::$strings["Flattr widget settings updated."] = "Flattr Widget Einstellungen aktualisiert";
-App::$strings["Flattr user"] = "Flattr Nutzer";
-App::$strings["URL of the Thing to flattr"] = "URL des Dings zum flattrn";
-App::$strings["If empty channel URL is used"] = "Falls leer wird die Channel URL verwendet";
-App::$strings["Title of the Thing to flattr"] = "Titel des Dings zum flattrn";
-App::$strings["If empty \"channel name on The Hubzilla\" will be used"] = "Falls leer wird \"Kanalname auf The Hubzilla\" verwendet";
-App::$strings["Static or dynamic flattr button"] = "Statischer oder dynamischer Flattr Button";
-App::$strings["static"] = "statisch";
-App::$strings["dynamic"] = "dynamisch";
-App::$strings["Alignment of the widget"] = "Ausrichtung des Widgets";
-App::$strings["left"] = "links";
-App::$strings["right"] = "rechts";
-App::$strings["Enable Flattr widget"] = "Flattr Widget verwenden";
-App::$strings["Flattr Widget Settings"] = "Flattr Widget Einstellungen";
-App::$strings["Contact not found."] = "Kontakt nicht gefunden.";
-App::$strings["This may occasionally happen if contact was requested by both persons and it has already been approved."] = "Dies kann unter Umständen passieren, wenn der Kontakt von beiden Seiten aus angefragt wurde und er bereits akzeptiert wurde..";
-App::$strings["Response from remote site was not understood."] = "Antwort des entfernten Seite war unverständlich.";
-App::$strings["Unexpected response from remote site: "] = "Unerwartete Antwort der entfernten Seite";
-App::$strings["Confirmation completed successfully."] = "Bestätigung erfolgreich abgeschlossen.";
-App::$strings["Remote site reported: "] = "Meldung der entfernten Seite";
-App::$strings["Temporary failure. Please wait and try again."] = "Vorübergehende Störung. Bitte warte einen Moment und versuche es später erneut.";
-App::$strings["Introduction failed or was revoked."] = "Vorstellung fehlgeschlagen oder wurde zurück gezogen.";
-App::$strings["Unable to set contact photo."] = "Konnte das Kontakt-Photo nicht setzen.";
-App::$strings["%1\$s is now friends with %2\$s"] = "%1\$s ist nun mit %2\$s befreundet";
-App::$strings["No user record found for '%s' "] = "Kein Benutzereintrag für '%s' gefunden";
-App::$strings["Our site encryption key is apparently messed up."] = "Der Verschlüsselungsschlüssel unserer Seite ist anscheinend kaputt.";
-App::$strings["Empty site URL was provided or URL could not be decrypted by us."] = "Eine leere Seiten URL wurde angegeben, oder die URL konnte von uns nicht entziffert werden.";
-App::$strings["Contact record was not found for you on our site."] = "Für dich wurden keinerlei Kontaktdaten auf unserer Seite gefunden.";
-App::$strings["Site public key not available in contact record for URL %s."] = "Der öffentliche Schlüssel dieser Seite ist für die Kontaktdaten mit der URL %s nocht verfügbar.";
-App::$strings["The ID provided by your system is a duplicate on our system. It should work if you try again."] = "Die ID, die Durch Dein System angegeben wurde ist ein Duplikat auf unserem. Es sollte funktionieren, wenn Du es noch einmal versuchst.";
-App::$strings["Unable to set your contact credentials on our system."] = "";
-App::$strings["Unable to update your contact profile details on our system"] = "Konnte die Details deines Profils auf unserem System nicht aktualisieren.";
-App::$strings["[Name Withheld]"] = "[Name zurück gehalten]";
-App::$strings["%1\$s has joined %2\$s"] = "%1\$s ist %2\$s beigetreten";
-App::$strings["%1\$s welcomes %2\$s"] = "%1\$s heißt %2\$s willkommen";
-App::$strings["This introduction has already been accepted."] = "Die Vorstellung wurde bereits akzeptiert.";
-App::$strings["Profile location is not valid or does not contain profile information."] = "";
-App::$strings["Warning: profile location has no identifiable owner name."] = "";
-App::$strings["Warning: profile location has no profile photo."] = "";
-App::$strings["%d required parameter was not found at the given location"] = array(
- 0 => "",
- 1 => "",
-);
-App::$strings["Introduction complete."] = "Einführung abgeschlossen.";
-App::$strings["Unrecoverable protocol error."] = "Nicht behebbarer Protokollfehler.";
-App::$strings["Profile unavailable."] = "Profil nicht verfügbar.";
-App::$strings["%s has received too many connection requests today."] = "%s hat heute bereits zu viele Kontaktanfragen erhalten.";
-App::$strings["Spam protection measures have been invoked."] = "Maßnahmen zum Spam-Schutz wurden aktiviert.";
-App::$strings["Friends are advised to please try again in 24 hours."] = "Freunde sollten es bitte in 24 Stunden erneut versuchen.";
-App::$strings["Invalid locator"] = "";
-App::$strings["Invalid email address."] = "Ungültige E-Mail-Adresse.";
-App::$strings["This account has not been configured for email. Request failed."] = "Dieser Account wurde nicht für E-Mail konfiguriert. Anfrage gescheitert.";
-App::$strings["Unable to resolve your name at the provided location."] = "";
-App::$strings["You have already introduced yourself here."] = "Du hast dich hier bereits vorgestellt.";
-App::$strings["Apparently you are already friends with %s."] = "Anscheinend bist du bereits mit %s in Kontakt.";
-App::$strings["Invalid profile URL."] = "Ungültige Profil-URL.";
-App::$strings["Disallowed profile URL."] = "Nicht erlaubte Profil-URL.";
-App::$strings["Failed to update contact record."] = "Konnte den Verbindungseintrag nicht aktualisieren.";
-App::$strings["Your introduction has been sent."] = "Deine Vorstellung wurde gesendet.";
-App::$strings["Please login to confirm introduction."] = "Bitte melde dich an um die Vorstellung zu bestätigen.";
-App::$strings["Incorrect identity currently logged in. Please login to <strong>this</strong> profile."] = "";
-App::$strings["Confirm"] = "Bestätigen";
-App::$strings["Hide this contact"] = "Diesen Kontakt verbergen";
-App::$strings["Welcome home %s."] = "Willkommen daheim %s";
-App::$strings["Please confirm your introduction/connection request to %s."] = "Bitte bestätige deine Vorstellung/Kontaktanfrage bei %s.";
-App::$strings["Please enter your 'Identity Address' from one of the following supported communications networks:"] = "Bitte gib deine \"Identitäts Adresse\" von einem der folgenden unterstützten Kommunikations Netzwerke an.";
-App::$strings["If you are not yet a member of the free social web, <a href=\"%s/siteinfo\">follow this link to find a public Friendica site and join us today</a>."] = "";
-App::$strings["Friend/Connection Request"] = "Freundschafts-/Verbindungsanfrage";
-App::$strings["Examples: jojo@demo.friendica.com, http://demo.friendica.com/profile/jojo, testuser@identi.ca"] = "Beispiele: jojo@demo.friendica.com, http://demo.friendica.com/profile/jojo, testuser@identi.ca";
-App::$strings["Please answer the following:"] = "Bitte beantworten Sie folgendes:";
-App::$strings["Does %s know you?"] = "Kennt %s Sie?";
-App::$strings["Add a personal note:"] = "Eine persönliche Nachricht hinterlassen:";
-App::$strings["Friendica"] = "Friendica";
-App::$strings["StatusNet/Federated Social Web"] = "StatusNet/Föderierte Soziale Netzwerke";
-App::$strings["Diaspora"] = "Diaspora";
-App::$strings[" - please do not use this form. Instead, enter %s into your Diaspora search bar."] = "- bitte verwende nicht dieses Formular sondern gib %s in die Suchleiste deiner Diaspora Seite ein.";
-App::$strings["Your Identity Address:"] = "Ihre Identitätsadresse:";
-App::$strings["Submit Request"] = "Anfrage absenden";
-App::$strings["GNU-Social Protocol Settings updated."] = "GNU Social Protokoll Einstellungen aktualisiert";
-App::$strings["Enable the (experimental) GNU-Social protocol for this channel"] = "GNU Social Protokoll (experimentell) für diesen Kanal aktualisieren";
-App::$strings["GNU-Social Protocol Settings"] = "GNU Social Protokoll Einstellungen";
-App::$strings["Follow"] = "Folgen";
-App::$strings["%1\$s is now following %2\$s"] = "%1\$s folgt nun %2\$s";
-App::$strings["Friendica Photo Album Import"] = "Friendica-Fotoalbumimport";
-App::$strings["This will import all your Friendica photo albums to this Red channel."] = "Hiermit werden all deine Fotoalben von Friendica in diesen Hubzilla Kanal importiert.";
-App::$strings["Friendica Server base URL"] = "BasisURL des Friendica Servers";
-App::$strings["Friendica Login Username"] = "Friendica-Anmeldebenutzername";
-App::$strings["Friendica Login Password"] = "Friendica-Anmeldepasswort";
-App::$strings["Enable the GNU-Social protocol for this channel"] = "GNU Social Protokoll für diesen Kanal aktualisieren";
-App::$strings["Send email to all members"] = "E-Mail an alle Mitglieder senden";
-App::$strings["$1%s Administrator"] = "$1%s Administrator";
-App::$strings["No recipients found."] = "Keine Empfänger gefunden.";
-App::$strings["%1\$d of %2\$d messages sent."] = "%1\$d von %2\$d Nachrichten gesendet.";
-App::$strings["Send email to all hub members."] = "Eine E-Mail an alle Mitglieder dieses Hubs senden.";
-App::$strings["Message subject"] = "Betreff der Nachricht";
-App::$strings["Sender Email address"] = "E-Mail Adresse des Absenders";
-App::$strings["Test mode (only send to hub administrator)"] = "Test Modus (nur an Hub Administratoren senden)";
-App::$strings["Post to Insanejournal"] = "Bei InsaneJournal veröffentlichen";
-App::$strings["Enable InsaneJournal Post Plugin"] = "Aktiviere das InsaneJournal Plugin";
-App::$strings["InsaneJournal username"] = "InsaneJournal-Benutzername";
-App::$strings["InsaneJournal password"] = "InsaneJournal-Passwort";
-App::$strings["Post to InsaneJournal by default"] = "Standardmäßig bei InsaneJournal veröffentlichen";
-App::$strings["InsaneJournal Post Settings"] = "InsaneJournal-Beitragseinstellungen";
-App::$strings["Insane Journal Settings saved."] = "InsaneJournal-Einstellungen gespeichert.";
-App::$strings["Channels to auto connect"] = "";
+App::$strings["Email notification hub"] = "Hub für E-Mail-Benachrichtigungen";
+App::$strings["Hostname"] = "Servername";
+App::$strings["Mailhost Settings"] = "Mailhost-Einstellungen";
+App::$strings["MAILHOST Settings saved."] = "MAILHOST-Einstellungen gespeichert.";
+App::$strings["Your Webbie:"] = "Dein Webbie";
+App::$strings["Fontsize (px):"] = "Schriftgröße (px):";
+App::$strings["Link:"] = "Link:";
+App::$strings["Like us on Hubzilla"] = "Like us on Hubzilla";
+App::$strings["Embed:"] = "Einbetten";
+App::$strings["Photos imported"] = "Fotos importiert";
+App::$strings["Redmatrix Photo Album Import"] = "Redmatrix-Fotoalbumimport";
+App::$strings["This will import all your Redmatrix photo albums to this channel."] = "Hiermit werden all deine Fotoalben von Redmatrix in diesen Kanal importiert.";
+App::$strings["Redmatrix Server base URL"] = "Basis-URL des Redmatrix Servers";
+App::$strings["Redmatrix Login Username"] = "Redmatrix-Anmeldebenutzername";
+App::$strings["Redmatrix Login Password"] = "Redmatrix-Anmeldepasswort";
+App::$strings["Import just this album"] = "Nur dieses Album importieren";
+App::$strings["Leave blank to import all albums"] = "Leer lassen um alle Alben zu importieren";
+App::$strings["Maximum count to import"] = "Maximal zu importierende Anzahl";
+App::$strings["0 or blank to import all available"] = "0 oder leer lassen um alles zu importieren";
+App::$strings["Channels to auto connect"] = "Kanäle zur automatischen Verbindung";
App::$strings["Comma separated list"] = "Kommagetrennte Liste";
App::$strings["Popular Channels"] = "Beliebte Kanäle";
App::$strings["IRC Settings"] = "IRC-Einstellungen";
App::$strings["IRC settings saved."] = "IRC-Einstellungen gespeichert.";
App::$strings["IRC Chatroom"] = "IRC-Chatraum";
-App::$strings["Status:"] = "Status:";
-App::$strings["Activate addon"] = "Addon aktiviren";
-App::$strings["Hide Jappixmini Chat-Widget from the webinterface"] = "Jappix Mini Chat-Widget von der Weboberfläche verbergen";
-App::$strings["Jabber username"] = "Jabber-Benutzername";
-App::$strings["Jabber server"] = "Jabber-Server";
-App::$strings["Jabber BOSH host URL"] = "Jabber BOSH Host URL";
-App::$strings["Jabber password"] = "Jabber-Passwort";
-App::$strings["Encrypt Jabber password with Hubzilla password"] = "Jabber-Passwort mit Hubzilla-Passwort verschlüsseln";
-App::$strings["Hubzilla password"] = "Hubzilla-Passwort";
-App::$strings["Approve subscription requests from Hubzilla contacts automatically"] = "";
-App::$strings["Purge internal list of jabber addresses of contacts"] = "Interne Liste der Jabber Adressen von Kontakten löschen";
-App::$strings["Configuration Help"] = "Konfigurationshilfe";
-App::$strings["Add Contact"] = "Kontakt hinzufügen";
-App::$strings["Jappix Mini Settings"] = "Jappix Mini Einstellungen";
-App::$strings["Upload a file"] = "Datei hochladen";
-App::$strings["Drop files here to upload"] = "Dateien zum Hochladen hier fallen lassen";
-App::$strings["Failed"] = "Fehlgeschlagen";
-App::$strings["No files were uploaded."] = "Es wurden keine Dateien hochgeladen.";
-App::$strings["Uploaded file is empty"] = "Hochgeladene Datei ist leer";
-App::$strings["Image exceeds size limit of "] = "Bild überschreitet Größenbeschränkung von ";
-App::$strings["File has an invalid extension, it should be one of "] = "Die Datei hat eine ungültige Endung. Erlaubt sind folgende:";
-App::$strings["Upload was cancelled, or server error encountered"] = "Das Hochladen wurde abgebrochen oder es ist ein Serverfehler aufgetreten.";
-App::$strings["An account has been created for you."] = "Ein Konto wurde für Sie erstellt.";
-App::$strings["Authentication successful but rejected: account creation is disabled."] = "Authentifizierung war erfolgreich wurde aber abgewiesen! Das Anlegen von Accounts wurde deaktiviert.";
-App::$strings["Post to Libertree"] = "Bei Libertree veröffentlichen";
-App::$strings["Enable Libertree Post Plugin"] = "Aktivire das Libertree-Plugin";
-App::$strings["Libertree API token"] = "Libertree API Token";
-App::$strings["Libertree site URL"] = "URL der Libertree Seite";
-App::$strings["Post to Libertree by default"] = "Standardmäßig bei Libertree veröffentlichen";
-App::$strings["Libertree Post Settings"] = "Libertree-Beitragseinstellungen";
-App::$strings["Libertree Settings saved."] = "Libertree-Einstellungen gespeichert.";
App::$strings["Post to LiveJournal"] = "Bei LiveJurnal veröffentlichen";
App::$strings["Enable LiveJournal Post Plugin"] = "Aktiviere das LiveJurnal Plugin";
App::$strings["LiveJournal username"] = "LiveJournal-Benutzername";
@@ -1828,36 +2076,34 @@ App::$strings["LiveJournal password"] = "LiveJournal-Passwort";
App::$strings["Post to LiveJournal by default"] = "Standardmäßig bei LiveJurnal veröffentlichen";
App::$strings["LiveJournal Post Settings"] = "LiveJournal-Beitragseinstellungen";
App::$strings["LiveJournal Settings saved."] = "LiveJournal-Einstellungen gespeichert.";
-App::$strings["Logfile archive directory"] = "Verzeichnis der Logdatei";
-App::$strings["Directory to store rotated logs"] = "Verzeichnis, in dem rotierte Logs gespeichert werden sollen";
-App::$strings["Logfile size in bytes before rotating"] = "zu erreichende Logdateigröße in Bytes, bevor rotiert wird";
-App::$strings["Number of logfiles to retain"] = "Anzahl aufzubewahrender rotierter Logdateien";
-App::$strings["Email notification hub"] = "Hub für E-Mail-Benachrichtigungen";
-App::$strings["Hostname"] = "Servername";
-App::$strings["Mailhost Settings"] = "Mailhost-Einstellungen";
-App::$strings["MAILHOST Settings saved."] = "MAILHOST-Einstellungen gespeichert.";
-App::$strings["lonely"] = "einsam";
-App::$strings["drunk"] = "betrunken";
-App::$strings["horny"] = "geil";
-App::$strings["stoned"] = "bekifft";
-App::$strings["fucked up"] = "beschissen";
-App::$strings["clusterfucked"] = "clusterfucked";
-App::$strings["crazy"] = "verrückt";
-App::$strings["hurt"] = "verletzt";
-App::$strings["sleepy"] = "müde";
-App::$strings["grumpy"] = "mürrisch";
-App::$strings["high"] = "hoch";
-App::$strings["semi-conscious"] = "halb bewusstlos";
-App::$strings["in love"] = "verliebt";
-App::$strings["in lust"] = "";
-App::$strings["naked"] = "nackt";
-App::$strings["stinky"] = "stinkend";
-App::$strings["sweaty"] = "verschwitzt";
-App::$strings["bleeding out"] = "blutend";
-App::$strings["victorious"] = "siegreich";
-App::$strings["defeated"] = "besiegt";
-App::$strings["envious"] = "neidisch";
-App::$strings["jealous"] = "eifersüchtig";
+App::$strings["We encountered a problem while logging in with the OpenID you provided. Please check the correct spelling of the ID."] = "Wir haben ein Problem mit der OpenID festgestellt, mit der Du Dich anmelden wolltest. Bitte überprüfe sie noch einmal.";
+App::$strings["The error message was:"] = "Die Fehlermeldung war:";
+App::$strings["First Name"] = "Vorname";
+App::$strings["Last Name"] = "Nachname";
+App::$strings["Nickname"] = "Spitzname";
+App::$strings["Full Name"] = "Voller Name";
+App::$strings["Profile Photo 16px"] = "Profilfoto 16 px";
+App::$strings["Profile Photo 32px"] = "Profilfoto 32 px";
+App::$strings["Profile Photo 48px"] = "Profilfoto 48 px";
+App::$strings["Profile Photo 64px"] = "Profilfoto 64 px";
+App::$strings["Profile Photo 80px"] = "Profilfoto 80 px";
+App::$strings["Profile Photo 128px"] = "Profilfoto 128 px";
+App::$strings["Timezone"] = "Zeitzone";
+App::$strings["Birth Year"] = "Geburtsjahr";
+App::$strings["Birth Month"] = "Geburtsmonat";
+App::$strings["Birth Day"] = "Geburtstag";
+App::$strings["Birthdate"] = "Geburtsdatum";
+App::$strings["OpenID protocol error. No ID returned."] = "OpenID-Protokollfehler. Keine Kennung zurückgegeben.";
+App::$strings["Login failed."] = "Login fehlgeschlagen.";
+App::$strings["Male"] = "Männlich";
+App::$strings["Female"] = "Weiblich";
+App::$strings["You're welcome."] = "Gern geschehen.";
+App::$strings["Ah shucks..."] = "Ach Mist...";
+App::$strings["Don't mention it."] = "Keine Ursache.";
+App::$strings["&lt;blush&gt;"] = "";
+App::$strings["Page to load after login"] = "Seite, die nach dem Login geladen werden soll";
+App::$strings["Examples: &quot;apps&quot;, &quot;network?f=&gid=37&quot; (privacy collection), &quot;channel&quot; or &quot;notifications/system&quot; (leave blank for default network page (grid)."] = "Beispiele: &quot;apps&quot;, &quot;network?f=&gid=37&quot; (Gruppen-gefilterte Beiträge), &quot;channel&quot; oder &quot;notifications/system&quot; (freilassen für die Standard-Netzwerkseite (grid).";
+App::$strings["Startpage Settings"] = "Startseiteneinstellungen";
App::$strings["bitchslap"] = "Ohrfeige";
App::$strings["bitchslapped"] = "geohrfeigt";
App::$strings["shag"] = "bumsen";
@@ -1868,8 +2114,8 @@ App::$strings["hug"] = "umarmen";
App::$strings["hugged"] = "umarmt";
App::$strings["murder"] = "ermorden";
App::$strings["murdered"] = "ermordet";
-App::$strings["worship"] = "";
-App::$strings["worshipped"] = "";
+App::$strings["worship"] = "Anbetung";
+App::$strings["worshipped"] = "angebetet";
App::$strings["kiss"] = "küssen";
App::$strings["kissed"] = "geküsst";
App::$strings["tempt"] = "verlocken";
@@ -1896,50 +2142,55 @@ App::$strings["bonk"] = "";
App::$strings["bonked"] = "";
App::$strings["declare undying love for"] = "";
App::$strings["declared undying love for"] = "";
+App::$strings["Diaspora Protocol Settings updated."] = "Diaspora Protokoll Einstellungen aktualisiert";
+App::$strings["The Diaspora protocol does not support location independence. Connections you make within that network may be unreachable from alternate channel locations."] = "Das Diaspora-Protokoll unterstützt keine Server-unabhängigen Identitäten. Verbindungen, die Du mit diesem Netzwerk eingehst, können von anderen Orten (Klonen) dieses Kanals aus unerreichbar sein.";
+App::$strings["Enable the Diaspora protocol for this channel"] = "Das Diaspora Protokoll für diesen Kanal aktivieren";
+App::$strings["Allow any Diaspora member to comment on your public posts"] = "Erlaube jedem Diaspora Nutzer deine öffentlichen Beiträge zu kommentieren";
+App::$strings["Prevent your hashtags from being redirected to other sites"] = "Verhindern, dass Deine Hashtags zu anderen Seiten umgeleitet werden";
+App::$strings["Sign and forward posts and comments with no existing Diaspora signature"] = "Signieren und Weiterleiten von Beiträgen und Kommentaren ohne vorhandene Diaspora-Signatur";
+App::$strings["Followed hashtags (comma separated, do not include the #)"] = "Verfolgte Hashtags (Komma separierte Liste, ohne die #)";
+App::$strings["Diaspora Protocol Settings"] = "Diaspora Protokoll Einstellungen";
+App::$strings["No username found in import file."] = "Es wurde kein Nutzername in der importierten Datei gefunden.";
+App::$strings["Unable to create a unique channel address. Import failed."] = "Es war nicht möglich, eine eindeutige Kanal-Adresse zu erzeugen. Der Import ist fehlgeschlagen.";
+App::$strings["Your account on %s will expire in a few days."] = "Dein Account auf %s wird in ein paar Tagen ablaufen.";
+App::$strings["Your $Productname test account is about to expire."] = "Dein $Productname Test-Account wird bald auslaufen.";
+App::$strings["Enable Rainbowtag"] = "Rainbowtag aktivieren";
+App::$strings["Rainbowtag Settings"] = "Rainbowtag-Einstellungen";
+App::$strings["Rainbowtag Settings saved."] = "Rainbowtag-Einstellungen gespeichert.";
+App::$strings["Show Upload Limits"] = "Hochladebeschränkungen anzeigen";
+App::$strings["Hubzilla configured maximum size: "] = "Die in Hubzilla eingestellte maximale Größe:";
+App::$strings["PHP upload_max_filesize: "] = "PHP upload_max_filesize:";
+App::$strings["PHP post_max_size (must be larger than upload_max_filesize): "] = "PHP post_max_size (muss größer sein als upload_max_filesize):";
+App::$strings["generic profile image"] = "";
+App::$strings["random geometric pattern"] = "";
+App::$strings["monster face"] = "";
+App::$strings["computer generated face"] = "";
+App::$strings["retro arcade style face"] = "";
+App::$strings["Hub default profile photo"] = "Standard-Profilfoto für diesen Hub";
+App::$strings["Information"] = "Information";
+App::$strings["Libravatar addon is installed, too. Please disable Libravatar addon or this Gravatar addon.<br>The Libravatar addon will fall back to Gravatar if nothing was found at Libravatar."] = "";
App::$strings["Save Settings"] = "Einstellungen speichern";
-App::$strings["text to include in all outgoing posts from this site"] = "Test der in alle Beiträge angefügt werden soll, die von dieser Seite ausgehen";
-App::$strings["Federate"] = "";
-App::$strings["nofed Settings saved."] = "nofed Einstellungen gespeichert";
-App::$strings["Allow Federation Toggle"] = "";
-App::$strings["Federate posts by default"] = "";
-App::$strings["NoFed Settings"] = "NoFed-Einstellungen";
+App::$strings["Default avatar image"] = "";
+App::$strings["Select default avatar image if none was found at Gravatar. See README"] = "";
+App::$strings["Rating of images"] = "";
+App::$strings["Select the appropriate avatar rating for your site. See README"] = "";
+App::$strings["Gravatar settings updated."] = "";
+App::$strings["Recent Channel/Profile Viewers"] = "Kürzliche Kanal/Profil Besucher";
+App::$strings["This plugin/addon has not been configured."] = "Dieses Plugin/Addon wurde noch nicht konfiguriert.";
+App::$strings["Please visit the Visage settings on %s"] = "Bitte rufe die Visage Einstellungen auf %s auf";
+App::$strings["your feature settings page"] = "Die Funktions-Einstellungsseite";
+App::$strings["No entries."] = "Keine Einträge.";
+App::$strings["Enable Visage Visitor Logging"] = "Aktiviere das Visage-Besucher Logging";
+App::$strings["Visage Settings"] = "Visage-Einstellungen";
App::$strings["Nsabait Settings updated."] = "Nsabait-Einstellungen aktualisiert.";
-App::$strings["Enable NSAbait Plugin"] = "";
+App::$strings["Enable NSAbait Plugin"] = "Aktiviere das NSAbait Plugin";
App::$strings["NSAbait Settings"] = "NSAbait-Einstellungen";
-App::$strings["This plugin looks in posts for the words/text you specify below, and collapses any content containing those keywords so it is not displayed at inappropriate times, such as sexual innuendo that may be improper in a work setting. It is polite and recommended to tag any content containing nudity with #NSFW. This filter can also match any other word/text you specify, and can thereby be used as a general purpose content filter."] = "";
-App::$strings["Enable Content filter"] = "Inhaltsfilter aktivieren";
-App::$strings["Comma separated list of keywords to hide"] = "";
-App::$strings["Use /expression/ to provide regular expressions"] = "";
-App::$strings["Not Safe For Work Settings"] = "Not Safe For Work Einstellungen";
-App::$strings["General Purpose Content Filter"] = "Allzweck-Inhaltsfilter";
-App::$strings["NSFW Settings saved."] = "NSFW-Einstellungen gespeichert.";
-App::$strings["Possible adult content"] = "Möglicherweise nicht jugendfreie Inhalte";
-App::$strings["%s - click to open/close"] = "%s - zum öffnen/schließen anklicken";
-App::$strings["System defaults:"] = "Systemstandardeinstellungen:";
-App::$strings["Preferred Clipart IDs"] = "";
-App::$strings["List of preferred clipart ids. These will be shown first."] = "";
-App::$strings["Default Search Term"] = "";
-App::$strings["The default search term. These will be shown second."] = "";
-App::$strings["Return After"] = "";
-App::$strings["Page to load after image selection."] = "";
-App::$strings["Edit Profile"] = "Profile bearbeiten";
-App::$strings["Profile List"] = "Profilliste";
-App::$strings["Order of Preferred"] = "Bevorzugte Reihenfolge";
-App::$strings["Sort order of preferred clipart ids."] = "";
-App::$strings["Newest first"] = "Neueste zuerst";
-App::$strings["As entered"] = "Wie eingegeben";
-App::$strings["Order of other"] = "";
-App::$strings["Sort order of other clipart ids."] = "";
-App::$strings["Most downloaded first"] = "Meist heruntergeladene zuerst";
-App::$strings["Most liked first"] = "Beliebteste zuerst";
-App::$strings["Preferred IDs Message"] = "";
-App::$strings["Message to display above preferred results."] = "";
-App::$strings["Uploaded by: "] = "Hochgeladen von: ";
-App::$strings["Drawn by: "] = "Gezeichnet von: ";
-App::$strings["Or select from a free OpenClipart.org image:"] = "";
-App::$strings["Search Term"] = "Suchbegriff";
-App::$strings["Unknown error. Please try again later."] = "Unbekannter Fehler. Bitte versuchen Sie es später erneut.";
-App::$strings["Profile photo updated successfully."] = "Profilfoto erfolgreich aktualisiert.";
+App::$strings["Send test email"] = "Test-E-Mail senden";
+App::$strings["No recipients found."] = "Keine Empfänger gefunden.";
+App::$strings["Mail sent."] = "Mail gesendet.";
+App::$strings["Sending of mail failed."] = "Senden der E-Mail fehlgeschlagen.";
+App::$strings["Mail Test"] = "Mail Test";
+App::$strings["Message subject"] = "Betreff der Nachricht";
App::$strings["View Larger"] = "Größer anzeigen";
App::$strings["Tile Server URL"] = "Kachelserver-URL";
App::$strings["A list of <a href=\"http://wiki.openstreetmap.org/wiki/TMS\" target=\"_blank\">public tile servers</a>"] = "Eine Liste <a href=\"http://wiki.openstreetmap.org/wiki/TMS\" target=\"_blank\">öffentlicher Kachelserver</a>";
@@ -1949,90 +2200,108 @@ App::$strings["Default zoom"] = "Standardzoom";
App::$strings["The default zoom level. (1:world, 18:highest, also depends on tile server)"] = "Die Standard-Vergrößerungsstufe (1:Welt, 18:höchste, hängt außerdem vom Kachelserver ab).";
App::$strings["Include marker on map"] = "Markierung auf der Karte einschließen";
App::$strings["Include a marker on the map."] = "Binde eine Markierung auf der Karte ein.";
-App::$strings["Message to display on every page on this server"] = "Nachricht, die auf jeder Seite dieses Servers angezeigt werden soll";
-App::$strings["Pageheader Settings"] = "Nachrichtenkopf-Einstellungen";
-App::$strings["pageheader Settings saved."] = "Nachrichtenkopf-Einstellungen gespeichert.";
-App::$strings["This website is tracked using the <a href='http://www.piwik.org'>Piwik</a> analytics tool."] = "Diese Website verwendet <a href='http://www.piwik.org'>Piwik</a>, um die Besucherzugriffe auszuwerten.";
-App::$strings["If you do not want that your visits are logged this way you <a href='%s'>can set a cookie to prevent Piwik from tracking further visits of the site</a> (opt-out)."] = "Wenn Du nicht möchtest, dass Deine Besuche zu diesem Zweck gespeichert werden, kannst Du <a href='%s'>ein Cookie setzen, welches Piwik davon abhält, Deine weiteren Besuche auf dieser Website zu verfolgen</a> (Opt-out).";
-App::$strings["Piwik Base URL"] = "Piwik Basis-URL";
-App::$strings["Absolute path to your Piwik installation. (without protocol (http/s), with trailing slash)"] = "Der absolute Pfad zu Deiner Piwik-Installation (ohne Protokoll (http/s), aber mit abschließendem Schrägstrich / ).";
-App::$strings["Site ID"] = "Seitenkennung";
-App::$strings["Show opt-out cookie link?"] = "Den Opt-out Cookie-Link anzeigen?";
-App::$strings["Asynchronous tracking"] = "Asynchrones Tracking";
-App::$strings["Enable frontend JavaScript error tracking"] = "Ermögliche Frontend-JavaScript-Fehlertracking";
-App::$strings["This feature requires Piwik >= 2.2.0"] = "Diese Funktion erfordert Piwik >= 2.2.0";
-App::$strings["Planets Settings updated."] = "Planeten Einstellungen aktualisiert";
-App::$strings["Enable Planets Plugin"] = "Aktiviere Planeten Plugin";
-App::$strings["Planets Settings"] = "Planeten Einstellungen";
-App::$strings["You are now authenticated to pumpio."] = "Du bist nun bei pumpio authenzifiziert.";
-App::$strings["return to the featured settings page"] = "";
-App::$strings["Post to Pump.io"] = "Bei pumpio veröffentlichen";
-App::$strings["Pump.io servername"] = "Pump.io-Servername";
-App::$strings["Without \"http://\" or \"https://\""] = "Ohne \"http://\" oder \"https://\"";
-App::$strings["Pump.io username"] = "Pump.io-Benutzername";
-App::$strings["Without the servername"] = "Ohne dem Servernamen";
-App::$strings["You are not authenticated to pumpio"] = "Du bist nicht bei pumpio authentifiziert.";
-App::$strings["(Re-)Authenticate your pump.io connection"] = "Deine pumpio Verbindung (erneut) authentifizieren";
-App::$strings["Enable pump.io Post Plugin"] = "Aktiviere das pumpio-Plugin";
-App::$strings["Post to pump.io by default"] = "Standardmäßig bei pumpio veröffentlichen";
-App::$strings["Should posts be public"] = "Sollen die Beiträge öffentlich sein";
-App::$strings["Mirror all public posts"] = "Öffentliche Beiträge spiegeln";
-App::$strings["Pump.io Post Settings"] = "Pump.io-Beitragseinstellungen";
-App::$strings["PumpIO Settings saved."] = "PumpIO-Einstellungen gespeichert.";
-App::$strings["QR code"] = "QR-Code";
-App::$strings["QR Generator"] = "QR-Generator";
-App::$strings["Enter some text"] = "";
-App::$strings["Enable Rainbowtag"] = "Rainbowtag aktivieren";
-App::$strings["Rainbowtag Settings"] = "Rainbowtag-Einstellungen";
-App::$strings["Rainbowtag Settings saved."] = "Rainbowtag-Einstellungen gespeichert.";
-App::$strings["You're welcome."] = "Gern geschehen.";
-App::$strings["Ah shucks..."] = "";
-App::$strings["Don't mention it."] = "Keine Ursache.";
-App::$strings["&lt;blush&gt;"] = "";
-App::$strings["Redmatrix File Storage Import"] = "";
-App::$strings["This will import all your Redmatrix cloud files to this channel."] = "Hiermit werden alle deine Daten aus der Redmatrix Cloud in diesen Kanal importiert.";
-App::$strings["Redmatrix Server base URL"] = "Basis-URL des Redmatrix Servers";
-App::$strings["Redmatrix Login Username"] = "Redmatrix-Anmeldebenutzername";
-App::$strings["Redmatrix Login Password"] = "Redmatrix-Anmeldepasswort";
-App::$strings["file"] = "Datei";
-App::$strings["Photos imported"] = "Fotos importiert";
-App::$strings["Redmatrix Photo Album Import"] = "Redmatrix-Fotoalbumimport";
-App::$strings["This will import all your Redmatrix photo albums to this channel."] = "Hiermit werden all deine Fotoalben von Redmatrix in diesen Kanal importiert.";
-App::$strings["Import just this album"] = "Nur dieses Album importieren";
-App::$strings["Leave blank to import all albums"] = "Leer lassen um alle Alben zu importieren";
-App::$strings["Maximum count to import"] = "Maximal zu importierende Anzahl";
-App::$strings["0 or blank to import all available"] = "0 oder leer lassen um alles zu importieren";
+App::$strings["text to include in all outgoing posts from this site"] = "Test der in alle Beiträge angefügt werden soll, die von dieser Seite ausgehen";
+App::$strings["Post to Friendica"] = "Bei Friendica veröffentlichen";
+App::$strings["rtof Settings saved."] = "rtof-Einstellungen gespeichert.";
+App::$strings["Allow posting to Friendica"] = "Erlaube die Veröffentlichung bei Friendica";
+App::$strings["Send public postings to Friendica by default"] = "Standardmäßig öffentliche Beiträge bei Friendica veröffentlichen";
+App::$strings["Friendica API Path"] = "Friendica-API-Pfad";
+App::$strings["https://{sitename}/api"] = "https://{sitename}/api";
+App::$strings["Friendica login name"] = "Friendica-Anmeldename";
+App::$strings["Friendica password"] = "Friendica-Passwort";
+App::$strings["Hubzilla to Friendica Post Settings"] = "Hubzilla-zu-Friendica Beitragseinstellungen";
+App::$strings["Status:"] = "Status:";
+App::$strings["Activate addon"] = "Addon aktiviren";
+App::$strings["Hide Jappixmini Chat-Widget from the webinterface"] = "Jappix Mini Chat-Widget von der Weboberfläche verbergen";
+App::$strings["Jabber username"] = "Jabber-Benutzername";
+App::$strings["Jabber server"] = "Jabber-Server";
+App::$strings["Jabber BOSH host URL"] = "Jabber BOSH Host URL";
+App::$strings["Jabber password"] = "Jabber-Passwort";
+App::$strings["Encrypt Jabber password with Hubzilla password"] = "Jabber-Passwort mit Hubzilla-Passwort verschlüsseln";
+App::$strings["Hubzilla password"] = "Hubzilla-Passwort";
+App::$strings["Approve subscription requests from Hubzilla contacts automatically"] = "Verbindungsanfragen von Hubzilla-Kontakten automatisch annehmen";
+App::$strings["Purge internal list of jabber addresses of contacts"] = "Interne Liste der Jabber Adressen von Kontakten löschen";
+App::$strings["Configuration Help"] = "Konfigurationshilfe";
+App::$strings["Jappix Mini Settings"] = "Jappix Mini Einstellungen";
+App::$strings["Currently blocked"] = "Derzeit blockiert";
+App::$strings["No channels currently blocked"] = "Momentan sind keine Kanäle blockiert";
+App::$strings["\"Superblock\" Settings"] = "\"Superblock\"-Einstellungen";
+App::$strings["Block Completely"] = "Vollständig blockieren";
+App::$strings["superblock settings updated"] = "Superblock Einstellungen aktualisiert";
+App::$strings["Federate"] = "Beitrag verteilen";
+App::$strings["nofed Settings saved."] = "nofed Einstellungen gespeichert";
+App::$strings["Allow Federation Toggle"] = "Umschalter zur Beitragsverteilung bereitstellen";
+App::$strings["Federate posts by default"] = "Beiträge standardmäßig verteilen";
+App::$strings["NoFed Settings"] = "NoFed-Einstellungen";
App::$strings["Post to Red"] = "";
App::$strings["Channel is required."] = "Kanal ist erforderlich.";
-App::$strings["Invalid channel."] = "Ungültiger Kanal.";
App::$strings["redred Settings saved."] = "redred-Einstellungen gespeichert.";
App::$strings["Allow posting to another Hubzilla Channel"] = "Erlaube die Veröffentlichung in anderen Hubzilla Kanälen";
App::$strings["Send public postings to Hubzilla channel by default"] = "";
App::$strings["Hubzilla API Path"] = "Hubzilla-API-Pfad";
-App::$strings["https://{sitename}/api"] = "https://{sitename}/api";
App::$strings["Hubzilla login name"] = "Hubzilla-Anmeldename";
App::$strings["Hubzilla channel name"] = "Hubzilla-Kanalname";
-App::$strings["Nickname"] = "Spitzname";
App::$strings["Hubzilla Crosspost Settings"] = "";
-App::$strings["Post to Friendica"] = "Bei Friendica veröffentlichen";
-App::$strings["rtof Settings saved."] = "rtof-Einstellungen gespeichert.";
-App::$strings["Allow posting to Friendica"] = "Erlaube die Veröffentlichung bei Friendica";
-App::$strings["Send public postings to Friendica by default"] = "Standardmäßig öffentliche Beiträge bei Friendica veröffentlichen";
-App::$strings["Friendica API Path"] = "Friendica-API-Pfad";
-App::$strings["Friendica login name"] = "Friendica-Anmeldename";
-App::$strings["Friendica password"] = "Friendica-Passwort";
-App::$strings["Hubzilla to Friendica Post Settings"] = "";
-App::$strings["Extended Identity Sharing"] = "Erweitertes Teilen von Identitäten";
-App::$strings["Share your identity with all websites on the internet. When disabled, identity is only shared with sites in the matrix."] = "";
-App::$strings["Some setting"] = "";
-App::$strings["A setting"] = "Eine Einstellung";
-App::$strings["Skeleton Settings"] = "";
-App::$strings["Deactivate the feature"] = "Diese Funktion abschalten";
-App::$strings["Hide the button and show the smilies directly."] = "Verstecke die Schaltfläche und zeige die Smilies direkt an.";
-App::$strings["Smileybutton Settings"] = "Smileyknopf-Einstellungen";
-App::$strings["Page to load after login"] = "Seite, die nach dem Login geladen werden soll";
-App::$strings["Examples: &quot;apps&quot;, &quot;network?f=&gid=37&quot; (privacy collection), &quot;channel&quot; or &quot;notifications/system&quot; (leave blank for default network page (grid)."] = "Beispiele: &quot;apps&quot;, &quot;network?f=&gid=37&quot; (Gruppen-gefilterte Beiträge), &quot;channel&quot; oder &quot;notifications/system&quot; (freilassen für die Standard-Netzwerkseite (grid).";
-App::$strings["Startpage Settings"] = "Startseiteneinstellungen";
+App::$strings["Logfile archive directory"] = "Verzeichnis der Logdatei";
+App::$strings["Directory to store rotated logs"] = "Verzeichnis, in dem rotierte Logs gespeichert werden sollen";
+App::$strings["Logfile size in bytes before rotating"] = "zu erreichende Logdateigröße in Bytes, bevor rotiert wird";
+App::$strings["Number of logfiles to retain"] = "Anzahl aufzubewahrender rotierter Logdateien";
+App::$strings["Friendica Photo Album Import"] = "Friendica-Fotoalbumimport";
+App::$strings["This will import all your Friendica photo albums to this Red channel."] = "Hiermit werden all deine Fotoalben von Friendica in diesen Hubzilla Kanal importiert.";
+App::$strings["Friendica Server base URL"] = "BasisURL des Friendica Servers";
+App::$strings["Friendica Login Username"] = "Friendica-Anmeldebenutzername";
+App::$strings["Friendica Login Password"] = "Friendica-Anmeldepasswort";
+App::$strings["ActivityPub"] = "ActivityPub";
+App::$strings["ActivityPub Protocol Settings updated."] = "";
+App::$strings["The ActivityPub protocol does not support location independence. Connections you make within that network may be unreachable from alternate channel locations."] = "";
+App::$strings["Enable the ActivityPub protocol for this channel"] = "";
+App::$strings["ActivityPub Protocol Settings"] = "";
+App::$strings["Project Servers and Resources"] = "Projektserver und -ressourcen";
+App::$strings["Project Creator and Tech Lead"] = "Projektersteller und Technischer Leiter";
+App::$strings["Admin, developer, directorymin, support bloke"] = "Administrator, Entwickler, Verzeichnis Betreibender, Supportleistende";
+App::$strings["And the hundreds of other people and organisations who helped make the Hubzilla possible."] = "Und die hunderte anderen Menschen und Organisationen, die geholfen haben Hubzilla möglich zu machen.";
+App::$strings["The Redmatrix/Hubzilla projects are provided primarily by volunteers giving their time and expertise - and often paying out of pocket for services they share with others."] = "Die Redmatrix/Hubzilla Projekte werden hauptsächlich von Freiwilligen bereitgestellt, die ihre Zeit und Expertise zur Verfügung stellen - und oft aus eigener Tasche für die Dienste zahlen, die sie mit anderen teilen.";
+App::$strings["There is no corporate funding and no ads, and we do not collect and sell your personal information. (We don't control your personal information - <strong>you do</strong>.)"] = "Es gibt keine Finanzierung durch Firmen, keine Werbung und wir verkaufen Deine persönlichen Daten nicht. (Wir kontrollieren Deine persönlichen Daten nicht - <strong>das machst Du</strong>.)";
+App::$strings["Help support our ground-breaking work in decentralisation, web identity, and privacy."] = "Hilf uns bei unserer wegweisenden Arbeit im Bereich der Dezantralisation, von Web-Identitäten und Privatsphäre.";
+App::$strings["Your donations keep servers and services running and also helps us to provide innovative new features and continued development."] = "Die Spenden werden dafür verwendet Server und Dienste am laufen zu halten und helfen desweiteren innovative Neuerungen zu schaffen und die Entwicklung voran zu treiben.";
+App::$strings["Donate"] = "Spenden";
+App::$strings["Choose a project, developer, or public hub to support with a one-time donation"] = "Wähle ein Projekt, einen Entwickler oder einen öffentlichen Hub den du mit einer einmaligen Spende unterstützen willst.";
+App::$strings["Donate Now"] = "Jetzt spenden";
+App::$strings["<strong><em>Or</em></strong> become a project sponsor (Hubzilla Project only)"] = "<strong><em>Oder</em></strong> werde ein Unterstützer des Projekts (ausschließlich Hubzilla)";
+App::$strings["Please indicate if you would like your first name or full name (or nothing) to appear in our sponsor listing"] = "Bitte teile uns mit ob dein kompletter Name oder dein Vorname (oder gar nichts) auf unserer Sponsoren-Seite veröffentlicht werden soll.";
+App::$strings["Sponsor"] = "Sponsor";
+App::$strings["Special thanks to: "] = "Besonderer Dank an: ";
+App::$strings["This is a fairly comprehensive and complete guitar chord dictionary which will list most of the available ways to play a certain chord, starting from the base of the fingerboard up to a few frets beyond the twelfth fret (beyond which everything repeats). A couple of non-standard tunings are provided for the benefit of slide players, etc."] = "";
+App::$strings["Chord names start with a root note (A-G) and may include sharps (#) and flats (b). This software will parse most of the standard naming conventions such as maj, min, dim, sus(2 or 4), aug, with optional repeating elements."] = "";
+App::$strings["Valid examples include A, A7, Am7, Amaj7, Amaj9, Ammaj7, Aadd4, Asus2Add4, E7b13b11 ..."] = "Einige gültige Beispiele: A, A7, Am7, Amaj7, Amaj9, Ammaj7, Aadd4, Asus2Add4, E7b13b11 ...";
+App::$strings["Guitar Chords"] = "Gitarrenakkorde";
+App::$strings["The complete online chord dictionary"] = "Das komplette online Akkord-Verzeichnis";
+App::$strings["Tuning"] = "Stimmen";
+App::$strings["Chord name: example: Em7"] = "Beispiel Akkord Name: Em7";
+App::$strings["Show for left handed stringing"] = "Linkshänder-Besaitung anzeigen";
+App::$strings["Quick Reference"] = "Schnellreferenz";
+App::$strings["Post to Libertree"] = "Bei Libertree veröffentlichen";
+App::$strings["Enable Libertree Post Plugin"] = "Aktivire das Libertree-Plugin";
+App::$strings["Libertree API token"] = "Libertree API Token";
+App::$strings["Libertree site URL"] = "URL der Libertree Seite";
+App::$strings["Post to Libertree by default"] = "Standardmäßig bei Libertree veröffentlichen";
+App::$strings["Libertree Post Settings"] = "Libertree-Beitragseinstellungen";
+App::$strings["Libertree Settings saved."] = "Libertree-Einstellungen gespeichert.";
+App::$strings["Flattr this!"] = "Flattr this!";
+App::$strings["Flattr widget settings updated."] = "Flattr Widget Einstellungen aktualisiert";
+App::$strings["Flattr user"] = "Flattr Nutzer";
+App::$strings["URL of the Thing to flattr"] = "URL des Dings zum flattrn";
+App::$strings["If empty channel URL is used"] = "Falls leer wird die Channel URL verwendet";
+App::$strings["Title of the Thing to flattr"] = "Titel des Dings zum flattrn";
+App::$strings["If empty \"channel name on The Hubzilla\" will be used"] = "Falls leer wird \"Kanalname auf The Hubzilla\" verwendet";
+App::$strings["Static or dynamic flattr button"] = "Statischer oder dynamischer Flattr Button";
+App::$strings["static"] = "statisch";
+App::$strings["dynamic"] = "dynamisch";
+App::$strings["Alignment of the widget"] = "Ausrichtung des Widgets";
+App::$strings["left"] = "links";
+App::$strings["right"] = "rechts";
+App::$strings["Enable Flattr widget"] = "Flattr Widget verwenden";
+App::$strings["Flattr Widget Settings"] = "Flattr Widget Einstellungen";
App::$strings["Post to GNU social"] = "Bei GNU social veröffentlichen";
App::$strings["Please contact your site administrator.<br />The provided API URL is not valid."] = "Bitte kontaktiere den Administrator deines Hubs.<br />Die angegebene API URL ist nicht korrekt.";
App::$strings["We could not contact the GNU social API with the Path you entered."] = "Mit dem angegebenen Pfad war es uns nicht möglich, die GNU social API zu erreichen.";
@@ -2062,25 +2331,42 @@ App::$strings["Clear OAuth configuration"] = "OAuth Konfiguration löschen";
App::$strings["GNU social Post Settings"] = "GNU social Einstellungen";
App::$strings["API URL"] = "API-URL";
App::$strings["Application name"] = "Anwendungsname";
-App::$strings["Currently blocked"] = "Derzeit blockiert";
-App::$strings["No channels currently blocked"] = "Momentan sind keine Kanäle blockiert";
-App::$strings["\"Superblock\" Settings"] = "\"Superblock\"-Einstellungen";
-App::$strings["Block Completely"] = "Vollständig blockieren";
-App::$strings["superblock settings updated"] = "Superblock Einstellungen aktualisiert";
-App::$strings["Your account on %s will expire in a few days."] = "Dein Account auf %s wird in ein paar Tagen ablaufen.";
-App::$strings["Your $Productname test account is about to expire."] = "Dein $Productname Test-Account wird bald auslaufen.";
-App::$strings["Three Dimensional Tic-Tac-Toe"] = "Dreidimensionales Tic-Tac-Toe";
-App::$strings["3D Tic-Tac-Toe"] = "3D Tic-Tac-Toe";
-App::$strings["New game"] = "Neues Spiel";
-App::$strings["New game with handicap"] = "Neues Handicaü-Spiel";
-App::$strings["Three dimensional tic-tac-toe is just like the traditional game except that it is played on multiple levels simultaneously. "] = "3D Tic-Tac-Toe funktioniert wie das ursprüngliche Spiel, nur dass es auf mehreren Ebenen gleichzeitig gespielt wird.";
-App::$strings["In this case there are three levels. You win by getting three in a row on any level, as well as up, down, and diagonally across the different levels."] = "In diesem Fall sind es drei Ebenen. Du gewinnst, wenn es dir gelingt drei in einer Reihe auf einer beliebigen Ebene oder diagonal über die verschiedenen Ebenen hinweg zu erreichen.";
-App::$strings["The handicap game disables the center position on the middle level because the player claiming this square often has an unfair advantage."] = "Bei einem Handicap-Spiel wird die Position im Zentrum der mittleren Ebene gesperrt, da der Spieler der dieses Feld für sich beansprucht meist einen unfairen Vorteil hat.";
-App::$strings["You go first..."] = "Du darfst anfangen...";
-App::$strings["I'm going first this time..."] = "Diesmal werde ich anfangen...";
-App::$strings["You won!"] = "Sie haben gewonnen!";
-App::$strings["\"Cat\" game!"] = "";
-App::$strings["I won!"] = "Ich habe gewonnen!";
+App::$strings["QR code"] = "QR-Code";
+App::$strings["QR Generator"] = "QR-Generator";
+App::$strings["Enter some text"] = "Etwas Text eingeben";
+App::$strings["Invalid game."] = "Ungültiges Spiel.";
+App::$strings["You are not a player in this game."] = "Sie sind kein Spieler in diesem Spiel.";
+App::$strings["You must be a local channel to create a game."] = "Um ein Spiel zu eröffnen, musst du ein lokaler Kanal sein";
+App::$strings["You must select one opponent that is not yourself."] = "Du musst einen Gegner wählen, der nicht du selbst ist";
+App::$strings["You must select white or black."] = "Sie müssen weiß oder schwarz auswählen.";
+App::$strings["Error creating new game."] = "Fehler beim Erstellen eines neuen Spiels.";
+App::$strings["Requested channel is not available."] = "Angeforderte Kanal nicht verfügbar.";
+App::$strings["You must select a local channel /chess/channelname"] = "Du musst einen lokalen Kanal/Schach(Kanalnamen aufwählen";
+App::$strings["Enable notifications"] = "Benachrichtigungen aktivieren";
+App::$strings["Post to Twitter"] = "Bei Twitter veröffentlichen";
+App::$strings["Twitter settings updated."] = "Twitter-Einstellungen aktualisiert.";
+App::$strings["No consumer key pair for Twitter found. Please contact your site administrator."] = "Es wurde kein Consumer-Schlüsselpaar für Twitter gefunden. Bitte kontaktiere deinen Seiten-Administrator.";
+App::$strings["At this Hubzilla instance the Twitter plugin was enabled but you have not yet connected your account to your Twitter account. To do so click the button below to get a PIN from Twitter which you have to copy into the input box below and submit the form. Only your <strong>public</strong> posts will be posted to Twitter."] = "Auf diesem Hubzilla-Server ist das Twitter-Plugin aktiviert, aber Du hast Dich hier noch nicht mit Deinem Twitter-Konto verbunden. Um dies zu tun, klicke die Schaltfläche unten, um eine PIN von Twitter zu erhalten, die Du dann in das Eingabefeld darunter einfügen und das Formular bestätigen musst. Nur Deine <strong>öffentlichen</strong> Beiträge werden auf Twitter geteilt.";
+App::$strings["Log in with Twitter"] = "Mit Twitter anmelden";
+App::$strings["Copy the PIN from Twitter here"] = "PIN von Twitter hier her kopieren";
+App::$strings["<strong>Note:</strong> Due your privacy settings (<em>Hide your profile details from unknown viewers?</em>) the link potentially included in public postings relayed to Twitter will lead the visitor to a blank page informing the visitor that the access to your profile has been restricted."] = "<strong>Hinweis:</strong> Entsprechend Deiner Privatsphären-Einstellungen (<em>Profil-Details vor nicht angemeldeten Besuchern verbergen?</em>) kann ein ggf. zu Twitter geteilter Link Besucher auf eine leere Seite führen, die darüber informiert, dass der Zugriff zu Deinem Profil eingeschränkt ist.";
+App::$strings["Allow posting to Twitter"] = "Erlaube die Veröffentlichung bei Twitter";
+App::$strings["If enabled your public postings can be posted to the associated Twitter account"] = "Wenn aktiv können deine öffentlichen Beiträge bei dem verbundenen Twitter Account veröffentlicht werden.";
+App::$strings["Send public postings to Twitter by default"] = "Standardmäßig öffentliche Beiträge bei Twitter veröffentlichen";
+App::$strings["If enabled your public postings will be posted to the associated Twitter account by default"] = "Wenn aktiv können deine öffentlichen Beiträge bei dem verbundenen Twitter Account veröffentlicht werden.";
+App::$strings["Twitter Post Settings"] = "Twitter-Beitragseinstellungen";
+App::$strings["Deactivate the feature"] = "Diese Funktion abschalten";
+App::$strings["Hide the button and show the smilies directly."] = "Verstecke die Schaltfläche und zeige die Smilies direkt an.";
+App::$strings["Smileybutton Settings"] = "Smileyknopf-Einstellungen";
+App::$strings["This website is tracked using the <a href='http://www.piwik.org'>Piwik</a> analytics tool."] = "Diese Website verwendet <a href='http://www.piwik.org'>Piwik</a>, um die Besucherzugriffe auszuwerten.";
+App::$strings["If you do not want that your visits are logged this way you <a href='%s'>can set a cookie to prevent Piwik from tracking further visits of the site</a> (opt-out)."] = "Wenn Du nicht möchtest, dass Deine Besuche zu diesem Zweck gespeichert werden, kannst Du <a href='%s'>ein Cookie setzen, welches Piwik davon abhält, Deine weiteren Besuche auf dieser Website zu verfolgen</a> (Opt-out).";
+App::$strings["Piwik Base URL"] = "Piwik Basis-URL";
+App::$strings["Absolute path to your Piwik installation. (without protocol (http/s), with trailing slash)"] = "Der absolute Pfad zu Deiner Piwik-Installation (ohne Protokoll (http/s), aber mit abschließendem Schrägstrich / ).";
+App::$strings["Site ID"] = "Seitenkennung";
+App::$strings["Show opt-out cookie link?"] = "Den Opt-out Cookie-Link anzeigen?";
+App::$strings["Asynchronous tracking"] = "Asynchrones Tracking";
+App::$strings["Enable frontend JavaScript error tracking"] = "Ermögliche Frontend-JavaScript-Fehlertracking";
+App::$strings["This feature requires Piwik >= 2.2.0"] = "Diese Funktion erfordert Piwik >= 2.2.0";
App::$strings["Edit your profile and change settings."] = "Bearbeite dein Profil und ändere die Einstellungen.";
App::$strings["Click here to see activity from your connections."] = "Klicke hier, um die Aktivitäten Deiner Verbindungen zu sehen.";
App::$strings["Click here to see your channel home."] = "Klicke hier, um Deine Kanal-Hauptseite zu sehen.";
@@ -2116,43 +2402,49 @@ App::$strings["Save your search so you can repeat it at a later date."] = "Speic
App::$strings["If you see this icon you can be sure that the sender is who it say it is. It is normal that it is not always possible to verify the sender, so the icon will be missing sometimes. There is usually no need to worry about that."] = "Wenn Du dieses Symbol siehst, kannst Du weitgehend sicher sein, dass der Ansender dem angegebenen entspricht. Nicht immer ist es möglich, den Absender zu verifizieren, daher fehlt das Symbol mitunter. Das ist aber in der Regel kein Grund zur Sorge.";
App::$strings["Danger! It seems someone tried to forge a message! This message is not necessarily from who it says it is from!"] = "Vorsicht! Es kann sein, dass jemand versucht, eine Nachricht zu fälschen! Diese Nachricht muss nicht unbedingt vom angegebenen Absender stammen!";
App::$strings["Welcome to Hubzilla! Would you like to see a tour of the UI?</p> <p>You can pause it at any time and continue where you left off by reloading the page, or navigting to another page.</p><p>You can also advance by pressing the return key"] = "Willkommen zu Hubzilla! Möchtest Du eine Tour der Benutzeroberfläche angezeigt bekommen?</p><p>Du kannst zu jeder Zeit pausieren und fortsetzen, wo Du aufgehört hast, indem Du die Seite neu lädtst, oder zu einer anderen Seite springst.</p><p>Du kannst auc durch das Drücken der Enter-Taste weitergehen.";
-App::$strings["Post to Twitter"] = "Bei Twitter veröffentlichen";
-App::$strings["Twitter settings updated."] = "Twitter-Einstellungen aktualisiert.";
-App::$strings["No consumer key pair for Twitter found. Please contact your site administrator."] = "";
-App::$strings["At this Hubzilla instance the Twitter plugin was enabled but you have not yet connected your account to your Twitter account. To do so click the button below to get a PIN from Twitter which you have to copy into the input box below and submit the form. Only your <strong>public</strong> posts will be posted to Twitter."] = "";
-App::$strings["Log in with Twitter"] = "Mit Twitter anmelden";
-App::$strings["Copy the PIN from Twitter here"] = "PIN von Twitter hier her kopieren";
-App::$strings["<strong>Note:</strong> Due your privacy settings (<em>Hide your profile details from unknown viewers?</em>) the link potentially included in public postings relayed to Twitter will lead the visitor to a blank page informing the visitor that the access to your profile has been restricted."] = "";
-App::$strings["Allow posting to Twitter"] = "Erlaube die Veröffentlichung bei Twitter";
-App::$strings["If enabled your public postings can be posted to the associated Twitter account"] = "Wenn aktiv können deine öffentlichen Beiträge bei dem verbundenen Twitter Account veröffentlicht werden.";
-App::$strings["Send public postings to Twitter by default"] = "Standardmäßig öffentliche Beiträge bei Twitter veröffentlichen";
-App::$strings["If enabled your public postings will be posted to the associated Twitter account by default"] = "Wenn aktiv können deine öffentlichen Beiträge bei dem verbundenen Twitter Account veröffentlicht werden.";
-App::$strings["Twitter Post Settings"] = "Twitter-Beitragseinstellungen";
-App::$strings["Submit Settings"] = "Einstellungen absenden";
-App::$strings["Show Upload Limits"] = "Hochladebeschränkungen anzeigen";
-App::$strings["Hubzilla configured maximum size: "] = "Die in Hubzilla eingestellte maximale Größe:";
-App::$strings["PHP upload_max_filesize: "] = "PHP upload_max_filesize:";
-App::$strings["PHP post_max_size (must be larger than upload_max_filesize): "] = "PHP post_max_size (muss größer sein als upload_max_filesize):";
-App::$strings["Recent Channel/Profile Viewers"] = "Kürzliche Kanal/Profil Besucher";
-App::$strings["This plugin/addon has not been configured."] = "Dieses Plugin/Addon wurde noch nicht konfiguriert.";
-App::$strings["Please visit the Visage settings on %s"] = "Bitte rufe die Visage Einstellungen auf %s auf";
-App::$strings["your feature settings page"] = "";
-App::$strings["No entries."] = "Keine Einträge.";
-App::$strings["Enable Visage Visitor Logging"] = "Aktiviere das Visage-Besucher Logging";
-App::$strings["Visage Settings"] = "Visage-Einstellungen";
-App::$strings["Who likes me?"] = "Wer mag mich?";
-App::$strings["Post to WordPress"] = "Auf WordPress posten";
-App::$strings["Enable WordPress Post Plugin"] = "Aktiviere das WordPress-Plugin";
-App::$strings["WordPress username"] = "WordPress-Benutzername";
-App::$strings["WordPress password"] = "WordPress-Passwort";
-App::$strings["WordPress API URL"] = "WordPress-API-URL";
-App::$strings["Typically https://your-blog.tld/xmlrpc.php"] = "Normalerweise https://your-blog.tld/xmlrpc.php";
-App::$strings["WordPress blogid"] = "WordPress blogid";
-App::$strings["For multi-user sites such as wordpress.com, otherwise leave blank"] = "Nötig für Mehrbenutzer Seiten wie wordpress.com, andernfalls frei lassen";
-App::$strings["Post to WordPress by default"] = "Standardmäßig auf auf WordPress posten";
-App::$strings["Forward comments (requires hubzilla_wp plugin)"] = "Kommentare weiterleiten (benötigt hubzilla_wp Plugin)";
-App::$strings["WordPress Post Settings"] = "WordPress-Beitragseinstellungen";
-App::$strings["Wordpress Settings saved."] = "Wordpress-Einstellungen gespeichert.";
+App::$strings["Extended Identity Sharing"] = "Erweitertes Teilen von Identitäten";
+App::$strings["Share your identity with all websites on the internet. When disabled, identity is only shared with sites in the matrix."] = "Teile Deine Identität mit allen Webseiten im Internet. Ist dies deaktiviert, wird Deine Identität nur mit Hubzilla-Servern geteilt.";
+App::$strings["Three Dimensional Tic-Tac-Toe"] = "Dreidimensionales Tic-Tac-Toe";
+App::$strings["3D Tic-Tac-Toe"] = "3D Tic-Tac-Toe";
+App::$strings["New game"] = "Neues Spiel";
+App::$strings["New game with handicap"] = "Neues Handicaü-Spiel";
+App::$strings["Three dimensional tic-tac-toe is just like the traditional game except that it is played on multiple levels simultaneously. "] = "3D Tic-Tac-Toe funktioniert wie das ursprüngliche Spiel, nur dass es auf mehreren Ebenen gleichzeitig gespielt wird.";
+App::$strings["In this case there are three levels. You win by getting three in a row on any level, as well as up, down, and diagonally across the different levels."] = "In diesem Fall sind es drei Ebenen. Du gewinnst, wenn es dir gelingt drei in einer Reihe auf einer beliebigen Ebene oder diagonal über die verschiedenen Ebenen hinweg zu erreichen.";
+App::$strings["The handicap game disables the center position on the middle level because the player claiming this square often has an unfair advantage."] = "Bei einem Handicap-Spiel wird die Position im Zentrum der mittleren Ebene gesperrt, da der Spieler der dieses Feld für sich beansprucht meist einen unfairen Vorteil hat.";
+App::$strings["You go first..."] = "Du darfst anfangen...";
+App::$strings["I'm going first this time..."] = "Diesmal werde ich anfangen...";
+App::$strings["You won!"] = "Sie haben gewonnen!";
+App::$strings["\"Cat\" game!"] = "\"Katzen\"-Spiel!";
+App::$strings["I won!"] = "Ich habe gewonnen!";
+App::$strings["Message to display on every page on this server"] = "Nachricht, die auf jeder Seite dieses Servers angezeigt werden soll";
+App::$strings["Pageheader Settings"] = "Nachrichtenkopf-Einstellungen";
+App::$strings["pageheader Settings saved."] = "Nachrichtenkopf-Einstellungen gespeichert.";
+App::$strings["Only authenticate automatically to sites of your friends"] = "Authentifiziere Dich nur auf Seiten deiner Freunde automatisch";
+App::$strings["By default you are automatically authenticated anywhere in the network"] = "Authentifiziere Dich standardmäßig bei allen Seiten im Netzwerk automatisch";
+App::$strings["Authchoose Settings"] = "Einstellungen für automatische Authentifizierung";
+App::$strings["Atuhchoose Settings updated."] = "Einstellungen für automatische Authentifizierung aktualisiert.";
+App::$strings["lonely"] = "einsam";
+App::$strings["drunk"] = "betrunken";
+App::$strings["horny"] = "geil";
+App::$strings["stoned"] = "bekifft";
+App::$strings["fucked up"] = "beschissen";
+App::$strings["clusterfucked"] = "clusterfucked";
+App::$strings["crazy"] = "verrückt";
+App::$strings["hurt"] = "verletzt";
+App::$strings["sleepy"] = "müde";
+App::$strings["grumpy"] = "mürrisch";
+App::$strings["high"] = "hoch";
+App::$strings["semi-conscious"] = "halb bewusstlos";
+App::$strings["in love"] = "verliebt";
+App::$strings["in lust"] = "";
+App::$strings["naked"] = "nackt";
+App::$strings["stinky"] = "stinkend";
+App::$strings["sweaty"] = "verschwitzt";
+App::$strings["bleeding out"] = "blutend";
+App::$strings["victorious"] = "siegreich";
+App::$strings["defeated"] = "besiegt";
+App::$strings["envious"] = "neidisch";
+App::$strings["jealous"] = "eifersüchtig";
App::$strings["XMPP settings updated."] = "XMPP-Einstellungen aktualisiert.";
App::$strings["Enable Chat"] = "Chat aktivieren";
App::$strings["Individual credentials"] = "Individuelle Anmeldedaten";
@@ -2161,192 +2453,35 @@ App::$strings["XMPP Settings"] = "XMPP-Einstellungen";
App::$strings["Jabber BOSH host"] = "Jabber BOSH Host";
App::$strings["Use central userbase"] = "Zentrale Benutzerbasis verwenden";
App::$strings["If enabled, members will automatically login to an ejabberd server that has to be installed on this machine with synchronized credentials via the \"auth_ejabberd.php\" script."] = "";
-App::$strings["Select Channel"] = "Kanal auswählen";
-App::$strings["Read-write"] = "Lesen-schreiben";
-App::$strings["Read-only"] = "Nur Lesen";
-App::$strings["My Calendars"] = "Meine Kalender";
-App::$strings["Shared Calendars"] = "Geteilte Kalender";
-App::$strings["Share this calendar"] = "Diesen Kalender teilen";
-App::$strings["Calendar name and color"] = "Kalendername und -farbe";
-App::$strings["Create new calendar"] = "Neuen Kalender erstellen";
-App::$strings["Calendar Name"] = "Kalendername";
-App::$strings["Calendar Tools"] = "Kalenderwerkzeuge";
-App::$strings["Import calendar"] = "Kalender importieren";
-App::$strings["Select a calendar to import to"] = "Kalender zum Hineinimportieren auswählen";
-App::$strings["Addressbooks"] = "Adressbücher";
-App::$strings["Addressbook name"] = "Adressbuchname";
-App::$strings["Create new addressbook"] = "Neues Adressbuch erstellen";
-App::$strings["Addressbook Name"] = "Adressbuchname";
-App::$strings["Addressbook Tools"] = "Adressbuchwerkzeuge";
-App::$strings["Import addressbook"] = "Adressbuch importieren";
-App::$strings["Select an addressbook to import to"] = "Adressbuch zum Hineinimportieren auswählen";
-App::$strings["Errors encountered creating database table: "] = "";
-App::$strings["Default Calendar"] = "Standardkalender";
-App::$strings["Default Addressbook"] = "Standardadressbuch";
-App::$strings["CalDAV/CardDAV Settings saved."] = "CalDAV/CardDAV-Einstellungen gespeichert.";
-App::$strings["Enable CalDAV/CardDAV Server for this channel"] = "Aktiviere den CalDAV/CardDAV Server für diesen Kanal";
-App::$strings["Your CalDAV resources are located at %s "] = "Deine CalDAV Resourcen sind unter %s verfügbar";
-App::$strings["Your CardDAV resources are located at %s "] = "Deine CardDAV Ressourcen sind unter %s verfügbar";
-App::$strings["CalDAV/CardDAV Settings"] = "CalDAV/CardDAV-Einstellungen";
-App::$strings["Mobile"] = "Mobil";
-App::$strings["Home"] = "Home";
-App::$strings["Home, Voice"] = "Zuhause, Sprache";
-App::$strings["Home, Fax"] = "Zuhause, Fax";
-App::$strings["Work"] = "Arbeit";
-App::$strings["Work, Voice"] = "Arbeit, Sprache";
-App::$strings["Work, Fax"] = "Arbeit, Fax";
-App::$strings["INVALID EVENT DISMISSED!"] = "UNGÜLTIGEN TERMIN ABGELEHNT!";
-App::$strings["Summary: "] = "Zusammenfassung:";
-App::$strings["Date: "] = "Datum:";
-App::$strings["Reason: "] = "Grund:";
-App::$strings["INVALID CARD DISMISSED!"] = "UNGÜLTIGE KARTE ABGELEHNT!";
-App::$strings["Name: "] = "Name: ";
-App::$strings["You have to enable this plugin in Feature/Addon Settings > CalDAV/CardDAV Settings before you can use it."] = "";
-App::$strings["Example: YYYY-MM-DD HH:mm"] = "Beispiel: JJJJ-MM-TT HH:mm";
-App::$strings["End date and time"] = "Enddatum und -zeit";
-App::$strings["List month"] = "";
-App::$strings["List week"] = "";
-App::$strings["List day"] = "";
-App::$strings["More"] = "Mehr";
-App::$strings["Less"] = "Weniger";
-App::$strings["Select calendar"] = "Kalender auswählen";
-App::$strings["Delete all"] = "Alles löschen";
-App::$strings["Sorry! Editing of recurrent events is not yet implemented."] = "Entschuldigung, aber das Bearbeiten von wiederkehrenden Veranstaltungen ist leider noch nicht implementiert.";
-App::$strings["Organisation"] = "Organisation";
-App::$strings["Title"] = "Titel";
-App::$strings["Phone"] = "Telefon";
-App::$strings["Instant messenger"] = "";
-App::$strings["Website"] = "Webseite";
-App::$strings["Note"] = "Hinweis";
-App::$strings["Add Field"] = "Feld hinzufügen";
-App::$strings["P.O. Box"] = "";
-App::$strings["Additional"] = "Zusätzlich";
-App::$strings["Street"] = "Straße";
-App::$strings["Locality"] = "Ortschaft";
-App::$strings["Region"] = "Region";
-App::$strings["ZIP Code"] = "Postleitzahl";
-App::$strings["Invalid game."] = "Ungültiges Spiel.";
-App::$strings["You are not a player in this game."] = "Sie sind kein Spieler in diesem Spiel.";
-App::$strings["You must be a local channel to create a game."] = "Um ein Spiel zu eröffnen, musst du ein lokaler Kanal sein";
-App::$strings["You must select one opponent that is not yourself."] = "Du musst einen Gegner wählen, der nicht du selbst ist";
-App::$strings["Creating new game..."] = "Neues Spiel wird erstellt...";
-App::$strings["You must select white or black."] = "Sie müssen weiß oder schwarz auswählen.";
-App::$strings["Error creating new game."] = "Fehler beim Erstellen eines neuen Spiels.";
-App::$strings["Requested channel is not available."] = "Angeforderte Kanal nicht verfügbar.";
-App::$strings["You must select a local channel /chess/channelname"] = "Du musst einen lokalen Kanal/Schach(Kanalnamen aufwählen";
-App::$strings["Enable notifications"] = "Benachrichtigungen aktivieren";
-App::$strings["Your Webbie:"] = "Dein Webbie";
-App::$strings["Fontsize (px):"] = "Schriftgröße (px):";
-App::$strings["Link:"] = "Link:";
-App::$strings["Like us on Hubzilla"] = "Like us on Hubzilla";
-App::$strings["Embed:"] = "Einbetten";
-App::$strings["Male"] = "Männlich";
-App::$strings["Female"] = "Weiblich";
-App::$strings["OpenID protocol error. No ID returned."] = "OpenID-Protokollfehler. Keine Kennung zurückgegeben.";
-App::$strings["Login failed."] = "Login fehlgeschlagen.";
-App::$strings["First Name"] = "Vorname";
-App::$strings["Last Name"] = "Nachname";
-App::$strings["Full Name"] = "Voller Name";
-App::$strings["Profile Photo 16px"] = "Profilfoto 16 px";
-App::$strings["Profile Photo 32px"] = "Profilfoto 32 px";
-App::$strings["Profile Photo 48px"] = "Profilfoto 48 px";
-App::$strings["Profile Photo 64px"] = "Profilfoto 64 px";
-App::$strings["Profile Photo 80px"] = "Profilfoto 80 px";
-App::$strings["Profile Photo 128px"] = "Profilfoto 128 px";
-App::$strings["Timezone"] = "Zeitzone";
-App::$strings["Birth Year"] = "Geburtsjahr";
-App::$strings["Birth Month"] = "Geburtsmonat";
-App::$strings["Birth Day"] = "Geburtstag";
-App::$strings["Birthdate"] = "Geburtsdatum";
-App::$strings["We encountered a problem while logging in with the OpenID you provided. Please check the correct spelling of the ID."] = "Wir haben ein Problem mit der OpenID festgestellt, mit der Du Dich anmelden wolltest. Bitte überprüfe sie noch einmal.";
-App::$strings["The error message was:"] = "Die Fehlermeldung war:";
-App::$strings["Reconnecting %d connections"] = "Erneuere %d Verbindungen";
-App::$strings["Diaspora Reconnect"] = "";
-App::$strings["Use this form to re-establish Diaspora connections which were initially made from a different hub."] = "";
-App::$strings["Reconnect"] = "Erneut verbinden";
-App::$strings["Send test email"] = "Test-E-Mail senden";
-App::$strings["Mail sent."] = "Mail gesendet.";
-App::$strings["Sending of mail failed."] = "Senden der E-Mail fehlgeschlagen.";
-App::$strings["Mail Test"] = "Mail Test";
-App::$strings["Errors encountered deleting database table "] = "Beim Löschen der Datenbanktabelle sind Fehler aufgetreten.";
-App::$strings["Drop tables when uninstalling?"] = "Lösche Tabellen beim Deinstallieren?";
-App::$strings["If checked, the Rendezvous database tables will be deleted when the plugin is uninstalled."] = "Wenn ausgewählt, werden die Rendezvous-Tabellen in der Datenbank gelöscht, sobald das Plugin deinstalliert wird.";
-App::$strings["Mapbox Access Token"] = "Mapbox Zugangs-Token";
-App::$strings["If you enter a Mapbox access token, it will be used to retrieve map tiles from Mapbox instead of the default OpenStreetMap tile server."] = "Wenn Du ein Mapbox Zugangs-Token eingibst, werden die Kartendaten (Kacheln) damit von Mapbox geladen, anstatt von OpenStreetMap, welches die Voreinstellung ist.";
-App::$strings["Rendezvous"] = "Rendezvous";
-App::$strings["This identity has been deleted by another member due to inactivity. Please press the \"New identity\" button or refresh the page to register a new identity. You may use the same name."] = "Diese Identität wurde von einem anderen Mitglied aufgrund von Inaktivität gelöscht. Bitte klicke auf \"Neue Identität\" oder aktualisiere die Website im Browser, um eine neue Identität zu registrieren. Du kannst dabei den selben Namen verwenden.";
-App::$strings["Welcome to Rendezvous!"] = "Willkommen bei Rendezvous!";
-App::$strings["Enter your name to join this rendezvous. To begin sharing your location with the other members, tap the GPS control. When your location is discovered, a red dot will appear and others will be able to see you on the map."] = "Gib Deinen Namen ein, um diesem Rendezvous beizutreten. Um Deinen Standort mit anderen Mitgliedern zu teilen, klicke auf das GPS Symbol. Sobald Dein Standort ermittelt ist, erscheint ein roter Punkt, und die Anderen werden Dich auf der Karte sehen können.";
-App::$strings["Let's meet here"] = "Lasst uns hier treffen";
-App::$strings["New marker"] = "Neue Markierung";
-App::$strings["Edit marker"] = "Markierung bearbeiten";
-App::$strings["New identity"] = "Neue Identität";
-App::$strings["Delete marker"] = "Markierung löschen";
-App::$strings["Delete member"] = "Mitglied löschen";
-App::$strings["Edit proximity alert"] = "Annäherungsalarm bearbeiten";
-App::$strings["A proximity alert will be issued when this member is within a certain radius of you.<br><br>Enter a radius in meters (0 to disable):"] = "Ein Annäherungsalarm wird ausgelöst werden, sobald sich dieses Mitglied innerhalb eines bestimmten Radius von Dir aufhält.<br><br>Gib einen Radius in Metern ein (0 zum Abschalten der Funktion):";
-App::$strings["distance"] = "Entfernung";
-App::$strings["Add new rendezvous"] = "Neues Rendezvous hinzufügen";
-App::$strings["Create a new rendezvous and share the access link with those you wish to invite to the group. Those who open the link become members of the rendezvous. They can view other member locations, add markers to the map, or share their own locations with the group."] = "Erstelle ein neues Rendezvous und teile den Zugriffslink mit allen, die Du in die Gruppe einladen möchtest. Die, die den Link öffnen, werden Mitglieder des Rendezvous. Sie können die Standorte der anderen Mitglieder sehen, Marker zur Karte hinzufügen oder ihre eigenen Standorte mit der Gruppe teilen.";
-App::$strings["No username found in import file."] = "Kein Benutzername in der Importdatei gefunden.";
-App::$strings["Unable to create a unique channel address. Import failed."] = "Es war nicht möglich, eine eindeutige Kanal-Adresse zu erzeugen. Der Import ist fehlgeschlagen.";
-App::$strings["Cannot locate DNS info for database server '%s'"] = "Kann die DNS-Informationen für den Datenbank-Server '%s' nicht finden";
-App::$strings["Birthday"] = "Geburtstag";
-App::$strings["Age: "] = "Alter:";
-App::$strings["YYYY-MM-DD or MM-DD"] = "JJJJ-MM-TT oder MM-TT";
-App::$strings["never"] = "Nie";
-App::$strings["less than a second ago"] = "Vor weniger als einer Sekunde";
-App::$strings["__ctx:e.g. 22 hours ago, 1 minute ago__ %1\$d %2\$s ago"] = "vor %1\$d %2\$s";
-App::$strings["__ctx:relative_date__ year"] = array(
- 0 => "Jahr",
- 1 => "Jahre",
-);
-App::$strings["__ctx:relative_date__ month"] = array(
- 0 => "Monat",
- 1 => "Monate",
-);
-App::$strings["__ctx:relative_date__ week"] = array(
- 0 => "Woche",
- 1 => "Wochen",
-);
-App::$strings["__ctx:relative_date__ day"] = array(
- 0 => "Tag",
- 1 => "Tage",
-);
-App::$strings["__ctx:relative_date__ hour"] = array(
- 0 => "Stunde",
- 1 => "Stunden",
-);
-App::$strings["__ctx:relative_date__ minute"] = array(
- 0 => "Minute",
- 1 => "Minuten",
-);
-App::$strings["__ctx:relative_date__ second"] = array(
- 0 => "Sekunde",
- 1 => "Sekunden",
-);
-App::$strings["%1\$s's birthday"] = "%1\$ss Geburtstag";
-App::$strings["Happy Birthday %1\$s"] = "Alles Gute zum Geburtstag, %1\$s";
-App::$strings["Not a valid email address"] = "Ungültige E-Mail-Adresse";
-App::$strings["Your email domain is not among those allowed on this site"] = "Deine E-Mail-Adresse ist auf dieser Seite nicht erlaubt";
-App::$strings["Your email address is already registered at this site."] = "Deine E-Mail-Adresse ist auf dieser Seite bereits registriert.";
-App::$strings["An invitation is required."] = "Eine Einladung wird benötigt.";
-App::$strings["Invitation could not be verified."] = "Die Einladung konnte nicht bestätigt werden.";
-App::$strings["Please enter the required information."] = "Bitte gib die benötigten Informationen ein.";
-App::$strings["Failed to store account information."] = "Speichern der Nutzerkontodaten fehlgeschlagen.";
-App::$strings["Registration confirmation for %s"] = "Registrierungsbestätigung für %s";
-App::$strings["Registration request at %s"] = "Registrierungsanfrage auf %s";
-App::$strings["your registration password"] = "Dein Registrierungspasswort";
-App::$strings["Registration details for %s"] = "Registrierungsdetails für %s";
-App::$strings["Account approved."] = "Nutzerkonto bestätigt.";
-App::$strings["Registration revoked for %s"] = "Registrierung für %s wurde widerrufen";
-App::$strings["Click here to upgrade."] = "Klicke hier, um das Upgrade durchzuführen.";
-App::$strings["This action exceeds the limits set by your subscription plan."] = "Diese Aktion überschreitet die Grenzen Ihres Abonnements.";
-App::$strings["This action is not available under your subscription plan."] = "Diese Aktion ist in Ihrem Abonnement nicht verfügbar.";
-App::$strings["No recipient provided."] = "Kein Empfänger angegeben";
-App::$strings["[no subject]"] = "[no subject]";
-App::$strings["Unable to determine sender."] = "Kann Absender nicht bestimmen.";
-App::$strings["Stored post could not be verified."] = "Gespeicherter Beitrag konnten nicht überprüft werden.";
+App::$strings["Who likes me?"] = "Wer mag mich?";
+App::$strings["You are now authenticated to pumpio."] = "Du bist nun bei pumpio authenzifiziert.";
+App::$strings["return to the featured settings page"] = "";
+App::$strings["Post to Pump.io"] = "Bei pumpio veröffentlichen";
+App::$strings["Pump.io servername"] = "Pump.io-Servername";
+App::$strings["Without \"http://\" or \"https://\""] = "Ohne \"http://\" oder \"https://\"";
+App::$strings["Pump.io username"] = "Pump.io-Benutzername";
+App::$strings["Without the servername"] = "Ohne dem Servernamen";
+App::$strings["You are not authenticated to pumpio"] = "Du bist nicht bei pumpio authentifiziert.";
+App::$strings["(Re-)Authenticate your pump.io connection"] = "Deine pumpio Verbindung (erneut) authentifizieren";
+App::$strings["Enable pump.io Post Plugin"] = "Aktiviere das pumpio-Plugin";
+App::$strings["Post to pump.io by default"] = "Standardmäßig bei pumpio veröffentlichen";
+App::$strings["Should posts be public"] = "Sollen die Beiträge öffentlich sein";
+App::$strings["Mirror all public posts"] = "Öffentliche Beiträge spiegeln";
+App::$strings["Pump.io Post Settings"] = "Pump.io-Beitragseinstellungen";
+App::$strings["PumpIO Settings saved."] = "PumpIO-Einstellungen gespeichert.";
+App::$strings["An account has been created for you."] = "Ein Konto wurde für Sie erstellt.";
+App::$strings["Authentication successful but rejected: account creation is disabled."] = "Authentifizierung war erfolgreich wurde aber abgewiesen! Das Anlegen von Accounts wurde deaktiviert.";
+App::$strings["__ctx:opensearch__ Search %1\$s (%2\$s)"] = "Suche %1\$s (%2\$s)";
+App::$strings["__ctx:opensearch__ \$Projectname"] = "\$Projectname";
+App::$strings["Search \$Projectname"] = "\$Projectname suchen";
+App::$strings["Redmatrix File Storage Import"] = "";
+App::$strings["This will import all your Redmatrix cloud files to this channel."] = "Hiermit werden alle deine Daten aus der Redmatrix Cloud in diesen Kanal importiert.";
+App::$strings["file"] = "Datei";
+App::$strings["Send email to all members"] = "E-Mail an alle Mitglieder senden";
+App::$strings["%1\$d of %2\$d messages sent."] = "%1\$d von %2\$d Nachrichten gesendet.";
+App::$strings["Send email to all hub members."] = "Eine E-Mail an alle Mitglieder dieses Hubs senden.";
+App::$strings["Sender Email address"] = "E-Mail Adresse des Absenders";
+App::$strings["Test mode (only send to hub administrator)"] = "Test Modus (nur an Hub Administratoren senden)";
App::$strings["Frequently"] = "Häufig";
App::$strings["Hourly"] = "Stündlich";
App::$strings["Twice daily"] = "Zwei Mal am Tag";
@@ -2407,168 +2542,102 @@ App::$strings["Uncertain"] = "Ungewiss";
App::$strings["It's complicated"] = "Es ist kompliziert";
App::$strings["Don't care"] = "Interessiert mich nicht";
App::$strings["Ask me"] = "Frag mich mal";
-App::$strings["Unable to obtain identity information from database"] = "Kann keine Identitäts-Informationen aus Datenbank beziehen";
-App::$strings["Empty name"] = "Namensfeld leer";
-App::$strings["Name too long"] = "Name ist zu lang";
-App::$strings["No account identifier"] = "Keine Account-Kennung";
-App::$strings["Nickname is required."] = "Spitzname ist erforderlich.";
-App::$strings["Reserved nickname. Please choose another."] = "Reservierter Kurzname. Bitte wähle einen anderen.";
-App::$strings["Nickname has unsupported characters or is already being used on this site."] = "Der Spitzname enthält nicht-unterstütze Zeichen oder wird bereits auf dieser Seite genutzt.";
-App::$strings["Unable to retrieve created identity"] = "Kann die erstellte Identität nicht empfangen";
-App::$strings["Default Profile"] = "Standard-Profil";
-App::$strings["Create New Profile"] = "Neues Profil erstellen";
-App::$strings["Visible to everybody"] = "Für jeden sichtbar";
-App::$strings["Gender:"] = "Geschlecht:";
-App::$strings["Homepage:"] = "Homepage:";
-App::$strings["Online Now"] = "gerade online";
-App::$strings["Like this channel"] = "Dieser Kanal gefällt mir";
-App::$strings["j F, Y"] = "j. F Y";
-App::$strings["j F"] = "j. F";
-App::$strings["Birthday:"] = "Geburtstag:";
-App::$strings["for %1\$d %2\$s"] = "seit %1\$d %2\$s";
-App::$strings["Sexual Preference:"] = "Sexuelle Orientierung:";
-App::$strings["Tags:"] = "Schlagworte:";
-App::$strings["Political Views:"] = "Politische Ansichten:";
-App::$strings["Religion:"] = "Religion:";
-App::$strings["Hobbies/Interests:"] = "Hobbys/Interessen:";
-App::$strings["Likes:"] = "Gefällt:";
-App::$strings["Dislikes:"] = "Gefällt nicht:";
-App::$strings["Contact information and Social Networks:"] = "Kontaktinformation und soziale Netzwerke:";
-App::$strings["My other channels:"] = "Meine anderen Kanäle:";
-App::$strings["Musical interests:"] = "Musikalische Interessen:";
-App::$strings["Books, literature:"] = "Bücher, Literatur:";
-App::$strings["Television:"] = "Fernsehen:";
-App::$strings["Film/dance/culture/entertainment:"] = "Film/Tanz/Kultur/Unterhaltung:";
-App::$strings["Love/Romance:"] = "Liebe/Romantik:";
-App::$strings["Work/employment:"] = "Arbeit/Anstellung:";
-App::$strings["School/education:"] = "Schule/Ausbildung:";
-App::$strings["Like this thing"] = "Gefällt mir";
-App::$strings["New window"] = "Neues Fenster";
-App::$strings["Open the selected location in a different window or browser tab"] = "Öffne die markierte Adresse in einem neuen Browserfenster oder Tab";
-App::$strings["User '%s' deleted"] = "Benutzer '%s' gelöscht";
+App::$strings["%1\$s is now connected with %2\$s"] = "%1\$s ist jetzt mit %2\$s verbunden";
+App::$strings["%1\$s poked %2\$s"] = "%1\$s stupste %2\$s an";
+App::$strings["poked"] = "stupste";
+App::$strings["View %s's profile @ %s"] = "%ss Profil auf %s ansehen";
+App::$strings["Categories:"] = "Kategorien:";
+App::$strings["Filed under:"] = "Gespeichert unter:";
+App::$strings["View in context"] = "Im Zusammenhang anschauen";
+App::$strings["remove"] = "lösche";
+App::$strings["Delete Selected Items"] = "Lösche die ausgewählten Elemente";
+App::$strings["View Source"] = "Quelle anzeigen";
+App::$strings["Follow Thread"] = "Unterhaltung folgen";
+App::$strings["Unfollow Thread"] = "Unterhaltung nicht mehr folgen";
+App::$strings["Activity/Posts"] = "Aktivitäten/Beiträge";
+App::$strings["Edit Connection"] = "Verbindung bearbeiten";
+App::$strings["Message"] = "Nachricht";
+App::$strings["%s likes this."] = "%s gefällt das.";
+App::$strings["%s doesn't like this."] = "%s gefällt das nicht.";
+App::$strings["<span %1\$s>%2\$d people</span> like this."] = array(
+ 0 => "<span %1\$s>%2\$d Person</span> gefällt das.",
+ 1 => "<span %1\$s>%2\$d Leuten</span> gefällt das.",
+);
+App::$strings["<span %1\$s>%2\$d people</span> don't like this."] = array(
+ 0 => "<span %1\$s>%2\$d Person</span> gefällt das nicht.",
+ 1 => "<span %1\$s>%2\$d Leuten</span> gefällt das nicht.",
+);
+App::$strings["and"] = "und";
+App::$strings[", and %d other people"] = array(
+ 0 => "",
+ 1 => ", und %d andere",
+);
+App::$strings["%s like this."] = "%s gefällt das.";
+App::$strings["%s don't like this."] = "%s gefällt das nicht.";
+App::$strings["Set your location"] = "Standort";
+App::$strings["Clear browser location"] = "Browser-Standort löschen";
+App::$strings["Tag term:"] = "Schlagwort:";
+App::$strings["Where are you right now?"] = "Wo bist Du jetzt grade?";
+App::$strings["Choose a different album..."] = "Wählen Sie ein anderes Album aus...";
+App::$strings["Comments enabled"] = "Kommentare aktiviert";
+App::$strings["Comments disabled"] = "Kommentare deaktiviert";
+App::$strings["Page link name"] = "Link zur Seite";
+App::$strings["Post as"] = "Veröffentlichen als";
+App::$strings["Toggle voting"] = "Umfragewerkzeug aktivieren";
+App::$strings["Disable comments"] = "Kommentare deaktivieren";
+App::$strings["Toggle comments"] = "Kommentare umschalten";
+App::$strings["Categories (optional, comma-separated list)"] = "Kategorien (optional, kommagetrennte Liste)";
+App::$strings["Other networks and post services"] = "Andere Netzwerke und Platformen";
+App::$strings["Set publish date"] = "Veröffentlichungsdatum festlegen";
+App::$strings["Commented Order"] = "Neueste Kommentare";
+App::$strings["Sort by Comment Date"] = "Nach Kommentardatum sortiert";
+App::$strings["Posted Order"] = "Neueste Beiträge";
+App::$strings["Sort by Post Date"] = "Nach Beitragsdatum sortiert";
+App::$strings["Posts that mention or involve you"] = "Beiträge mit Beteiligung Deinerseits";
+App::$strings["Activity Stream - by date"] = "Activity Stream – nach Datum sortiert";
+App::$strings["Starred"] = "Markiert";
+App::$strings["Favourite Posts"] = "Markierte Beiträge";
+App::$strings["Spam"] = "Spam";
+App::$strings["Posts flagged as SPAM"] = "Nachrichten, die als SPAM markiert wurden";
+App::$strings["Status Messages and Posts"] = "Statusnachrichten und Beiträge";
+App::$strings["Profile Details"] = "Profil-Details";
+App::$strings["Photo Albums"] = "Fotoalben";
+App::$strings["Files and Storage"] = "Dateien und Speicher";
+App::$strings["Bookmarks"] = "Lesezeichen";
+App::$strings["Saved Bookmarks"] = "Gespeicherte Lesezeichen";
+App::$strings["View Cards"] = "";
+App::$strings["View Webpages"] = "Webseiten anzeigen";
+App::$strings["__ctx:noun__ Attending"] = array(
+ 0 => "Zusage",
+ 1 => "Zusagen",
+);
+App::$strings["__ctx:noun__ Not Attending"] = array(
+ 0 => "Absage",
+ 1 => "Absagen",
+);
+App::$strings["__ctx:noun__ Undecided"] = array(
+ 0 => " Unentschlossen",
+ 1 => "Unentschlossene",
+);
+App::$strings["__ctx:noun__ Agree"] = array(
+ 0 => "Zustimmung",
+ 1 => "Zustimmungen",
+);
+App::$strings["__ctx:noun__ Disagree"] = array(
+ 0 => "Ablehnung",
+ 1 => "Ablehnungen",
+);
+App::$strings["__ctx:noun__ Abstain"] = array(
+ 0 => "Enthaltung",
+ 1 => "Enthaltungen",
+);
App::$strings["Directory Options"] = "Verzeichnisoptionen";
App::$strings["Safe Mode"] = "Sicherer Modus";
App::$strings["Public Forums Only"] = "Nur öffentliche Foren";
App::$strings["This Website Only"] = "Nur dieser Hub";
-App::$strings["Logout"] = "Abmelden";
-App::$strings["End this session"] = "Beende diese Sitzung";
-App::$strings["Your posts and conversations"] = "Deine Beiträge und Unterhaltungen";
-App::$strings["Your profile page"] = "Deine Profilseite";
-App::$strings["Manage/Edit profiles"] = "Profile verwalten";
-App::$strings["Edit your profile"] = "Profil bearbeiten";
-App::$strings["Your photos"] = "Deine Bilder";
-App::$strings["Your files"] = "Deine Dateien";
-App::$strings["Your chatrooms"] = "Deine Chaträume";
-App::$strings["Bookmarks"] = "Lesezeichen";
-App::$strings["Your bookmarks"] = "Deine Lesezeichen";
-App::$strings["Your webpages"] = "Deine Webseiten";
-App::$strings["Your wikis"] = "Ihre Wikis";
-App::$strings["Sign in"] = "Anmelden";
-App::$strings["Remote authentication"] = "Über Konto auf anderem Server einloggen";
-App::$strings["Click to authenticate to your home hub"] = "Klicke, um Dich über Deinen Heimat-Server zu authentifizieren";
-App::$strings["Get me home"] = "Bringe mich nach Hause (eigener Kanal)";
-App::$strings["Log me out of this site"] = "Logge mich von dieser Seite aus";
-App::$strings["Create an account"] = "Erzeuge ein Konto";
-App::$strings["Help and documentation"] = "Hilfe und Dokumentation";
-App::$strings["Applications, utilities, links, games"] = "Anwendungen (Apps), Zubehör, Links, Spiele";
-App::$strings["Search site @name, #tag, ?docs, content"] = "Hub durchsuchen: @Name. #Schlagwort, ?Dokumentation, Inhalt";
-App::$strings["Channel Directory"] = "Kanal-Verzeichnis";
-App::$strings["Your grid"] = "Dein Grid";
-App::$strings["Mark all grid notifications seen"] = "Alle Grid-Benachrichtigungen als angesehen markieren";
-App::$strings["Channel home"] = "Mein Kanal";
-App::$strings["Mark all channel notifications seen"] = "Markiere alle Kanal-Benachrichtigungen als angesehen";
-App::$strings["Notices"] = "Benachrichtigungen";
-App::$strings["Notifications"] = "Benachrichtigungen";
-App::$strings["See all notifications"] = "Alle Benachrichtigungen ansehen";
-App::$strings["Private mail"] = "Persönliche Mail";
-App::$strings["See all private messages"] = "Alle persönlichen Nachrichten ansehen";
-App::$strings["Mark all private messages seen"] = "Markiere alle persönlichen Nachrichten als gesehen";
-App::$strings["Inbox"] = "Eingang";
-App::$strings["Outbox"] = "Ausgang";
-App::$strings["New Message"] = "Neue Nachricht";
-App::$strings["Event Calendar"] = "Terminkalender";
-App::$strings["See all events"] = "Alle Termine ansehen";
-App::$strings["Mark all events seen"] = "Markiere alle Termine als gesehen";
-App::$strings["Manage Your Channels"] = "Verwalte Deine Kanäle";
-App::$strings["Account/Channel Settings"] = "Konto-/Kanal-Einstellungen";
-App::$strings["Admin"] = "Administration";
-App::$strings["Site Setup and Configuration"] = "Seiten-Einrichtung und -Konfiguration";
-App::$strings["Loading..."] = "Lädt ...";
-App::$strings["@name, #tag, ?doc, content"] = "@Name, #Schlagwort, ?Dokumentation, Inhalt";
-App::$strings["Please wait..."] = "Bitte warten...";
-App::$strings["General Features"] = "Allgemeine Funktionen";
-App::$strings["Multiple Profiles"] = "Mehrfachprofile";
-App::$strings["Ability to create multiple profiles"] = "Ermöglicht das Anlegen mehrerer Profile pro Kanal";
-App::$strings["Advanced Profiles"] = "Erweiterte Profile";
-App::$strings["Additional profile sections and selections"] = "Stellt zusätzliche Bereiche und Felder im Profil zur Verfügung";
-App::$strings["Profile Import/Export"] = "Profil-Import/Export";
-App::$strings["Save and load profile details across sites/channels"] = "Ermöglicht das Speichern von Profilen, um sie in einen anderen Kanal zu importieren";
-App::$strings["Web Pages"] = "Webseiten";
-App::$strings["Provide managed web pages on your channel"] = "Ermöglicht das Erstellen von Webseiten in Deinem Kanal";
-App::$strings["Provide a wiki for your channel"] = "Stelle ein Wiki in Deinem Kanal zur Verfügung";
-App::$strings["Private Notes"] = "Private Notizen";
-App::$strings["Enables a tool to store notes and reminders (note: not encrypted)"] = "Aktiviert ein Werkzeug mit dem Notizen und Erinnerungen gespeichert werden können (Hinweis: nicht verschlüsselt)";
-App::$strings["Navigation Channel Select"] = "Kanal-Auswahl in der Navigationsleiste";
-App::$strings["Change channels directly from within the navigation dropdown menu"] = "Ermöglicht den direkten Wechsel zu anderen Kanälen über das Navigationsmenü";
-App::$strings["Photo Location"] = "Aufnahmeort";
-App::$strings["If location data is available on uploaded photos, link this to a map."] = "Verlinkt den Aufnahmeort von Fotos (falls verfügbar) auf einer Karte";
-App::$strings["Access Controlled Chatrooms"] = "Zugriffskontrollierte Chaträume";
-App::$strings["Provide chatrooms and chat services with access control."] = "Bieten Sie Chaträume und Chatdienste mit Zugriffskontrolle an.";
-App::$strings["Smart Birthdays"] = "Smarte Geburtstage";
-App::$strings["Make birthday events timezone aware in case your friends are scattered across the planet."] = "Stellt für Geburtstage einen Zeitzonenbezug her, falls deine Freunde über den ganzen Planeten verstreut sind.";
-App::$strings["Advanced Directory Search"] = "Erweiterte Verzeichnissuche";
-App::$strings["Allows creation of complex directory search queries"] = "Ermöglicht die Erstellung komplexer Verzeichnis-Suchabfragen";
-App::$strings["Advanced Theme and Layout Settings"] = "Erweiterte Design- und Layout-Einstellungen";
-App::$strings["Allows fine tuning of themes and page layouts"] = "Erlaubt die Feineinstellung von Designs und Seitenlayouts";
-App::$strings["Post Composition Features"] = "Nachbearbeitungsfunktionen";
-App::$strings["Large Photos"] = "Große Fotos";
-App::$strings["Include large (1024px) photo thumbnails in posts. If not enabled, use small (640px) photo thumbnails"] = "Große Vorschaubilder (1024px) in Beiträgen anzeigen. Falls nicht aktiviert, werden kleine Vorschaubilder (640px) verwendet.";
-App::$strings["Automatically import channel content from other channels or feeds"] = "Ermöglicht den automatischen Import von Inhalten für diesen Kanal von anderen Kanälen oder Feeds";
-App::$strings["Even More Encryption"] = "Noch mehr Verschlüsselung";
-App::$strings["Allow optional encryption of content end-to-end with a shared secret key"] = "Ermöglicht optional die zusätzliche Verschlüsselung von Inhalten (Ende-zu-Ende mit geteiltem Schlüssel)";
-App::$strings["Enable Voting Tools"] = "Umfragewerkzeuge aktivieren";
-App::$strings["Provide a class of post which others can vote on"] = "Aktiviert die Umfragewerkzeuge, um anderen die Möglichkeit zu geben, einem Beitrag zuzustimmen, ihn abzulehnen oder sich zu enthalten. (Muss im Beitrag selbst noch aktiviert werden.)";
-App::$strings["Disable Comments"] = "Kommentare deaktivieren";
-App::$strings["Provide the option to disable comments for a post"] = "Ermöglicht, die Kommentarfunktion für einzelne Beiträge abzuschalten";
-App::$strings["Delayed Posting"] = "Verzögertes Senden";
-App::$strings["Allow posts to be published at a later date"] = "Ermöglicht es, Beiträge zu einem späteren Zeitpunkt zu veröffentlichen";
-App::$strings["Content Expiration"] = "Verfall von Inhalten";
-App::$strings["Remove posts/comments and/or private messages at a future time"] = "Ermöglicht das automatische Löschen von Beiträgen, Kommentaren und/oder privaten Nachrichten zu einem zukünftigen Datum.";
-App::$strings["Suppress Duplicate Posts/Comments"] = "Doppelte Beiträge unterdrücken";
-App::$strings["Prevent posts with identical content to be published with less than two minutes in between submissions."] = "Verhindert, dass innerhalb von zwei Minuten Beiträge mit identischem Inhalt veröffentlicht werden.";
-App::$strings["Network and Stream Filtering"] = "Netzwerk- und Stream-Filter";
-App::$strings["Search by Date"] = "Suche nach Datum";
-App::$strings["Ability to select posts by date ranges"] = "Möglichkeit, Beiträge nach Zeiträumen auszuwählen";
-App::$strings["Privacy Groups"] = "Gruppen";
-App::$strings["Enable management and selection of privacy groups"] = "Auswahl und Verwaltung von Gruppen für Kanäle aktivieren";
-App::$strings["Saved Searches"] = "Gespeicherte Suchanfragen";
-App::$strings["Save search terms for re-use"] = "Ermöglicht das Abspeichern von Suchbegriffen zur Wiederverwendung";
-App::$strings["Network Personal Tab"] = "Persönlicher Netzwerkreiter";
-App::$strings["Enable tab to display only Network posts that you've interacted on"] = "Aktiviert einen Reiter in der Grid-Ansicht, der nur Netzwerk-Beiträge anzeigt, mit denen Du interagiert hast";
-App::$strings["Network New Tab"] = "Netzwerkreiter Neu";
-App::$strings["Enable tab to display all new Network activity"] = "Aktiviert einen Reiter in der Grid-Ansicht, der alle neuen Netzwerkaktivitäten anzeigt";
-App::$strings["Affinity Tool"] = "Beziehungs-Tool";
-App::$strings["Filter stream activity by depth of relationships"] = "Aktiviert ein Werkzeug in der Grid-Ansicht, das den Stream nach Grad der Beziehung filtern kann";
-App::$strings["Show friend and connection suggestions"] = "Freund- und Verbindungsvorschläge anzeigen";
-App::$strings["Connection Filtering"] = "Filter für Verbindungen";
-App::$strings["Filter incoming posts from connections based on keywords/content"] = "Ermöglicht die Filterung eingehender Beiträge anhand von Schlüsselwörtern (muss an der Verbindung konfiguriert werden)";
-App::$strings["Post/Comment Tools"] = "Beitrag-/Kommentar-Tools";
-App::$strings["Community Tagging"] = "Gemeinschaftliches Verschlagworten";
-App::$strings["Ability to tag existing posts"] = "Ermöglicht das Verschlagworten existierender Beiträge";
-App::$strings["Post Categories"] = "Beitrags-Kategorien";
-App::$strings["Add categories to your posts"] = "Aktiviert Kategorien für Beiträge";
-App::$strings["Emoji Reactions"] = "Emoji Reaktionen";
-App::$strings["Add emoji reaction ability to posts"] = "Aktiviert Emoji-Reaktionen für Beiträge";
-App::$strings["Saved Folders"] = "Gespeicherte Ordner";
-App::$strings["Ability to file posts under folders"] = "Möglichkeit, Beiträge in Verzeichnissen zu sammeln";
-App::$strings["Dislike Posts"] = "Gefällt-mir-nicht-Beiträge";
-App::$strings["Ability to dislike posts/comments"] = "Aktiviert die „Gefällt mir nicht“-Schaltfläche";
-App::$strings["Star Posts"] = "Beiträge mit Sternchen versehen";
-App::$strings["Ability to mark special posts with a star indicator"] = "Ermöglicht die lokale Markierung spezieller Beiträge mit einem Sternchen-Symbol";
-App::$strings["Tag Cloud"] = "Schlagwort-Wolke";
-App::$strings["Provide a personal tag cloud on your channel page"] = "Aktiviert die Anzeige einer Schlagwort-Wolke (Tag Cloud) auf Deiner Kanal-Seite";
-App::$strings["Premium Channel"] = "Premium-Kanal";
-App::$strings["Allows you to set restrictions and terms on those that connect with your channel"] = "Ermöglicht es, Einschränkungen und Bedingungen für Verbindungen dieses Kanals festzulegen";
+App::$strings["%1\$s's bookmarks"] = "%1\$ss Lesezeichen";
+App::$strings["Cannot create a duplicate channel identifier on this system. Import failed."] = "Kann keinen doppelten Kanal-Identifikator auf diesem System erzeugen (Spitzname oder Hash schon belegt). Import fehlgeschlagen.";
+App::$strings["Cloned channel not found. Import failed."] = "Geklonter Kanal nicht gefunden. Import fehlgeschlagen.";
App::$strings["prev"] = "vorherige";
App::$strings["first"] = "erste";
App::$strings["last"] = "letzte";
@@ -2578,7 +2647,6 @@ App::$strings["newer"] = "neuer";
App::$strings["No connections"] = "Keine Verbindungen";
App::$strings["View all %s connections"] = "Alle Verbindungen von %s anzeigen";
App::$strings["poke"] = "anstupsen";
-App::$strings["poked"] = "stupste";
App::$strings["ping"] = "anpingen";
App::$strings["pinged"] = "pingte";
App::$strings["prod"] = "knuffen";
@@ -2633,11 +2701,16 @@ App::$strings["Unknown Attachment"] = "Unbekannter Anhang";
App::$strings["unknown"] = "unbekannt";
App::$strings["remove category"] = "Kategorie entfernen";
App::$strings["remove from file"] = "aus der Datei entfernen";
+App::$strings["Download binary/encrypted content"] = "Binären/verschlüsselten Inhalt herunterladen";
App::$strings["default"] = "Standard";
App::$strings["Page layout"] = "Seiten-Layout";
App::$strings["You can create your own with the layouts tool"] = "Mit dem Gestaltungswerkzeug kannst Du Deine eigenen Layouts erstellen";
+App::$strings["HTML"] = "";
+App::$strings["Comanche Layout"] = "";
+App::$strings["PHP"] = "";
App::$strings["Page content type"] = "Art des Seiteninhalts";
App::$strings["activity"] = "Aktivität";
+App::$strings["a-z, 0-9, -, and _ only"] = "";
App::$strings["Design Tools"] = "Gestaltungswerkzeuge";
App::$strings["Pages"] = "Seiten";
App::$strings["Import website..."] = "Webseite importieren...";
@@ -2655,10 +2728,6 @@ App::$strings["Export to cloud files"] = "In Cloud-Dateien exportieren";
App::$strings["/path/to/export/folder"] = "/Pfad/zum/exportierenden/Ordner";
App::$strings["Enter a path to a cloud files destination."] = "Gib den Pfad zu einem Datei-Speicherort in der Cloud ein.";
App::$strings["Specify folder"] = "Ordner angeben";
-App::$strings["%1\$s's bookmarks"] = "%1\$ss Lesezeichen";
-App::$strings["Different viewers will see this text differently"] = "Verschiedene Betrachter werden diesen Text unterschiedlich sehen";
-App::$strings["Help:"] = "Hilfe:";
-App::$strings["New Page"] = "Neue Seite";
App::$strings["%d invitation available"] = array(
0 => "%d Einladung verfügbar",
1 => "%d Einladungen verfügbar",
@@ -2670,13 +2739,17 @@ App::$strings["Examples: Robert Morgenstein, Fishing"] = "Beispiele: Robert Morg
App::$strings["Random Profile"] = "Zufallsprofil";
App::$strings["Invite Friends"] = "Lade Freunde ein";
App::$strings["Advanced example: name=fred and country=iceland"] = "Fortgeschrittenes Beispiel: name=fred and country=iceland";
-App::$strings["Everything"] = "Alles";
-App::$strings["Categories"] = "Kategorien";
-App::$strings["%d connection in common"] = array(
- 0 => "%d gemeinsame Verbindung",
- 1 => "%d gemeinsame Verbindungen",
-);
-App::$strings["show more"] = "mehr zeigen";
+App::$strings["Common Connections"] = "";
+App::$strings["View all %d common connections"] = "";
+App::$strings["%1\$s wrote the following %2\$s %3\$s"] = "%1\$s schrieb den folgenden %2\$s %3\$s";
+App::$strings["Channel is blocked on this site."] = "Der Kanal ist auf dieser Seite blockiert ";
+App::$strings["Channel location missing."] = "Adresse des Kanals fehlt.";
+App::$strings["Response from remote channel was incomplete."] = "Antwort des entfernten Kanals war unvollständig.";
+App::$strings["Channel was deleted and no longer exists."] = "Kanal wurde gelöscht und existiert nicht mehr.";
+App::$strings["Remote channel or protocol unavailable."] = "";
+App::$strings["Channel discovery failed."] = "Kanalsuche fehlgeschlagen";
+App::$strings["Protocol disabled."] = "Protokoll deaktiviert.";
+App::$strings["Cannot connect to yourself."] = "Du kannst Dich nicht mit Dir selbst verbinden.";
App::$strings["Delete this item?"] = "Dieses Element löschen?";
App::$strings["%s show less"] = "%s weniger anzeigen";
App::$strings["%s expand"] = "%s aufklappen";
@@ -2704,7 +2777,7 @@ App::$strings["about an hour"] = "ungefähr eine Stunde";
App::$strings["about %d hours"] = "ungefähr %d Stunden";
App::$strings["a day"] = "ein Tag";
App::$strings["%d days"] = "%d Tage";
-App::$strings["about a month"] = "ungefähr ein Monat";
+App::$strings["about a month"] = "ungefähr einen Monat";
App::$strings["%d months"] = "%d Monate";
App::$strings["about a year"] = "ungefähr ein Jahr";
App::$strings["%d years"] = "%d Jahre";
@@ -2735,51 +2808,10 @@ App::$strings["__ctx:calendar__ month"] = "Monat";
App::$strings["__ctx:calendar__ week"] = "Woche";
App::$strings["__ctx:calendar__ day"] = "Tag";
App::$strings["__ctx:calendar__ All day"] = "Ganztägig";
-App::$strings["view full size"] = "In Vollbildansicht anschauen";
-App::$strings["No Subject"] = "Kein Betreff";
-App::$strings["OStatus"] = "OStatus";
-App::$strings["GNU-Social"] = "GNU-Social";
-App::$strings["RSS/Atom"] = "RSS/Atom";
-App::$strings["Facebook"] = "Facebook";
-App::$strings["Zot"] = "Zot!";
-App::$strings["LinkedIn"] = "LinkedIn";
-App::$strings["XMPP/IM"] = "XMPP/IM";
-App::$strings["MySpace"] = "MySpace";
-App::$strings["Tags"] = "Schlagwörter";
-App::$strings["Keywords"] = "Schlüsselwörter";
-App::$strings["have"] = "habe";
-App::$strings["has"] = "hat";
-App::$strings["want"] = "will";
-App::$strings["wants"] = "will";
-App::$strings["likes"] = "gefällt";
-App::$strings["dislikes"] = "missfällt";
-App::$strings["Cannot create a duplicate channel identifier on this system. Import failed."] = "Kann keinen doppelten Kanal-Identifikator auf diesem System erzeugen (Spitzname oder Hash schon belegt). Import fehlgeschlagen.";
-App::$strings["Channel clone failed. Import failed."] = "Klonen des Kanals fehlgeschlagen. Import fehlgeschlagen.";
-App::$strings["Unable to import element \""] = "Element konnte nicht importiert werden.";
-App::$strings["guest:"] = "Gast:";
-App::$strings["The form security token was not correct. This probably happened because the form has been opened for too long (>3 hours) before submitting it."] = "Das Security-Token des Formulars war nicht korrekt. Das ist wahrscheinlich passiert, weil das Formular zu lange (>3 Stunden) offen war, bevor es abgeschickt wurde.";
-App::$strings["Invalid data packet"] = "Ungültiges Datenpaket";
-App::$strings["Unable to verify channel signature"] = "Konnte die Signatur des Kanals nicht verifizieren";
-App::$strings["Unable to verify site signature for %s"] = "Kann die Signatur der Seite von %s nicht verifizieren";
-App::$strings["invalid target signature"] = "Ungültige Signatur des Ziels";
-App::$strings["(Unknown)"] = "(Unbekannt)";
-App::$strings["Visible to anybody on the internet."] = "Für jeden im Internet sichtbar.";
-App::$strings["Visible to you only."] = "Nur für Dich sichtbar.";
-App::$strings["Visible to anybody in this network."] = "Für jedes \$Projectname-Mitglied sichtbar.";
-App::$strings["Visible to anybody authenticated."] = "Für jeden sichtbar, der angemeldet ist.";
-App::$strings["Visible to anybody on %s."] = "Für jeden auf %s sichtbar.";
-App::$strings["Visible to all connections."] = "Für alle Verbindungen sichtbar.";
-App::$strings["Visible to approved connections."] = "Nur für akzeptierte Verbindungen sichtbar.";
-App::$strings["Visible to specific connections."] = "Sichtbar für bestimmte Verbindungen.";
-App::$strings["Privacy group is empty."] = "Gruppe ist leer.";
-App::$strings["Privacy group: %s"] = "Gruppe: %s";
-App::$strings["Connection not found."] = "Die Verbindung wurde nicht gefunden.";
-App::$strings["profile photo"] = "Profilfoto";
-App::$strings["[Edited %s]"] = "[%s wurde bearbeitet]";
-App::$strings["__ctx:edit_activity__ Post"] = "Beitrag";
-App::$strings["__ctx:edit_activity__ Comment"] = "Kommentar";
-App::$strings["Logged out."] = "Ausgeloggt.";
-App::$strings["Failed authentication"] = "Authentifizierung fehlgeschlagen";
+App::$strings["Unable to determine sender."] = "Kann Absender nicht bestimmen.";
+App::$strings["No recipient provided."] = "Kein Empfänger angegeben";
+App::$strings["[no subject]"] = "[no subject]";
+App::$strings["Stored post could not be verified."] = "Gespeicherter Beitrag konnten nicht überprüft werden.";
App::$strings[" and "] = "und";
App::$strings["public profile"] = "öffentliches Profil";
App::$strings["%1\$s changed %2\$s to &ldquo;%3\$s&rdquo;"] = "%1\$s hat %2\$s auf &ldquo;%3\$s&rdquo; geändert";
@@ -2800,6 +2832,59 @@ App::$strings["Path not found."] = "Pfad nicht gefunden.";
App::$strings["mkdir failed."] = "mkdir fehlgeschlagen.";
App::$strings["database storage failed."] = "Speichern in der Datenbank fehlgeschlagen.";
App::$strings["Empty path"] = "Leere Pfadangabe";
+App::$strings["The form security token was not correct. This probably happened because the form has been opened for too long (>3 hours) before submitting it."] = "Das Security-Token des Formulars war nicht korrekt. Das ist wahrscheinlich passiert, weil das Formular zu lange (>3 Stunden) offen war, bevor es abgeschickt wurde.";
+App::$strings["(Unknown)"] = "(Unbekannt)";
+App::$strings["Visible to anybody on the internet."] = "Für jeden im Internet sichtbar.";
+App::$strings["Visible to you only."] = "Nur für Dich sichtbar.";
+App::$strings["Visible to anybody in this network."] = "Für jedes \$Projectname-Mitglied sichtbar.";
+App::$strings["Visible to anybody authenticated."] = "Für jeden sichtbar, der angemeldet ist.";
+App::$strings["Visible to anybody on %s."] = "Für jeden auf %s sichtbar.";
+App::$strings["Visible to all connections."] = "Für alle Verbindungen sichtbar.";
+App::$strings["Visible to approved connections."] = "Nur für akzeptierte Verbindungen sichtbar.";
+App::$strings["Visible to specific connections."] = "Sichtbar für bestimmte Verbindungen.";
+App::$strings["Privacy group is empty."] = "Gruppe ist leer.";
+App::$strings["Privacy group: %s"] = "Gruppe: %s";
+App::$strings["Connection not found."] = "Die Verbindung wurde nicht gefunden.";
+App::$strings["profile photo"] = "Profilfoto";
+App::$strings["[Edited %s]"] = "[%s wurde bearbeitet]";
+App::$strings["__ctx:edit_activity__ Post"] = "Beitrag";
+App::$strings["__ctx:edit_activity__ Comment"] = "Kommentar";
+App::$strings["Unable to obtain identity information from database"] = "Kann keine Identitäts-Informationen aus Datenbank beziehen";
+App::$strings["Empty name"] = "Namensfeld leer";
+App::$strings["Name too long"] = "Name ist zu lang";
+App::$strings["No account identifier"] = "Keine Account-Kennung";
+App::$strings["Nickname is required."] = "Spitzname ist erforderlich.";
+App::$strings["Unable to retrieve created identity"] = "Kann die erstellte Identität nicht empfangen";
+App::$strings["Default Profile"] = "Standard-Profil";
+App::$strings["Unable to retrieve modified identity"] = "Geänderte Identität kann nicht empfangen werden";
+App::$strings["Create New Profile"] = "Neues Profil erstellen";
+App::$strings["Visible to everybody"] = "Für jeden sichtbar";
+App::$strings["Gender:"] = "Geschlecht:";
+App::$strings["Homepage:"] = "Homepage:";
+App::$strings["Online Now"] = "gerade online";
+App::$strings["Trans"] = "";
+App::$strings["Like this channel"] = "Dieser Kanal gefällt mir";
+App::$strings["j F, Y"] = "j. F Y";
+App::$strings["j F"] = "j. F";
+App::$strings["Birthday:"] = "Geburtstag:";
+App::$strings["for %1\$d %2\$s"] = "seit %1\$d %2\$s";
+App::$strings["Sexual Preference:"] = "Sexuelle Orientierung:";
+App::$strings["Tags:"] = "Schlagworte:";
+App::$strings["Political Views:"] = "Politische Ansichten:";
+App::$strings["Religion:"] = "Religion:";
+App::$strings["Hobbies/Interests:"] = "Hobbys/Interessen:";
+App::$strings["Likes:"] = "Gefällt:";
+App::$strings["Dislikes:"] = "Gefällt nicht:";
+App::$strings["Contact information and Social Networks:"] = "Kontaktinformation und soziale Netzwerke:";
+App::$strings["My other channels:"] = "Meine anderen Kanäle:";
+App::$strings["Musical interests:"] = "Musikalische Interessen:";
+App::$strings["Books, literature:"] = "Bücher, Literatur:";
+App::$strings["Television:"] = "Fernsehen:";
+App::$strings["Film/dance/culture/entertainment:"] = "Film/Tanz/Kultur/Unterhaltung:";
+App::$strings["Love/Romance:"] = "Liebe/Romantik:";
+App::$strings["Work/employment:"] = "Arbeit/Anstellung:";
+App::$strings["School/education:"] = "Schule/Ausbildung:";
+App::$strings["Like this thing"] = "Gefällt mir";
App::$strings["l F d, Y \\@ g:i A"] = "l, d. F Y, H:i";
App::$strings["Starts:"] = "Beginnt:";
App::$strings["Finishes:"] = "Endet:";
@@ -2809,246 +2894,228 @@ App::$strings["Needs Action"] = "Aktion erforderlich";
App::$strings["Completed"] = "Abgeschlossen";
App::$strings["In Process"] = "In Bearbeitung";
App::$strings["Cancelled"] = "gestrichen";
-App::$strings["Channel is blocked on this site."] = "Der Kanal ist auf dieser Seite blockiert ";
-App::$strings["Channel location missing."] = "Adresse des Kanals fehlt.";
-App::$strings["Response from remote channel was incomplete."] = "Antwort des entfernten Kanals war unvollständig.";
-App::$strings["Channel was deleted and no longer exists."] = "Kanal wurde gelöscht und existiert nicht mehr.";
-App::$strings["Protocol disabled."] = "Protokoll deaktiviert.";
-App::$strings["Channel discovery failed."] = "Kanalsuche fehlgeschlagen";
-App::$strings["Cannot connect to yourself."] = "Du kannst Dich nicht mit Dir selbst verbinden.";
-App::$strings["A deleted group with this name was revived. Existing item permissions <strong>may</strong> apply to this group and any future members. If this is not what you intended, please create another group with a different name."] = "Es hat früher schon einmal eine Gruppe mit diesem Namen existiert, die gelöscht wurde. Es <strong>könnten</strong> von damals noch Elemente (Beiträge, Dateien etc.) vorhanden sein, die allen jetzigen und zukünftigen Mitgliedern dieser Gruppe den Zugriff erlauben. Wenn das nicht Deine Absicht ist, erstelle bitte eine neue Gruppe mit einem anderen Namen.";
-App::$strings["Add new connections to this privacy group"] = "Neue Verbindung zu dieser Gruppe hinzufügen";
-App::$strings["edit"] = "Bearbeiten";
-App::$strings["Edit group"] = "Gruppe ändern";
-App::$strings["Add privacy group"] = "Gruppe hinzufügen";
-App::$strings["Channels not in any privacy group"] = "Kanäle, die in keiner Gruppe sind";
-App::$strings["add"] = "hinzufügen";
+App::$strings["Home, Voice"] = "Zuhause, Sprache";
+App::$strings["Home, Fax"] = "Zuhause, Fax";
+App::$strings["Work, Voice"] = "Arbeit, Sprache";
+App::$strings["Work, Fax"] = "Arbeit, Fax";
+App::$strings["view full size"] = "In Vollbildansicht anschauen";
+App::$strings["Friendica"] = "Friendica";
+App::$strings["OStatus"] = "OStatus";
+App::$strings["GNU-Social"] = "GNU-Social";
+App::$strings["RSS/Atom"] = "RSS/Atom";
+App::$strings["Diaspora"] = "Diaspora";
+App::$strings["Facebook"] = "Facebook";
+App::$strings["Zot"] = "Zot!";
+App::$strings["LinkedIn"] = "LinkedIn";
+App::$strings["XMPP/IM"] = "XMPP/IM";
+App::$strings["MySpace"] = "MySpace";
App::$strings["Select an alternate language"] = "Wähle eine alternative Sprache";
-App::$strings["Image exceeds website size limit of %lu bytes"] = "Bild überschreitet das Webseitenlimit von %lu Bytes";
-App::$strings["Image file is empty."] = "Bilddatei ist leer.";
-App::$strings["Photo storage failed."] = "Fotospeicherung fehlgeschlagen.";
-App::$strings["a new photo"] = "ein neues Foto";
-App::$strings["__ctx:photo_upload__ %1\$s posted %2\$s to %3\$s"] = "%1\$s hat %2\$s auf %3\$s veröffentlicht";
-App::$strings["Photo Albums"] = "Fotoalben";
-App::$strings["Upload New Photos"] = "Neue Fotos hochladen";
-App::$strings["System"] = "System";
-App::$strings["New App"] = "Neue App";
-App::$strings["Suggestions"] = "Vorschläge";
-App::$strings["See more..."] = "Mehr anzeigen …";
-App::$strings["You have %1$.0f of %2$.0f allowed connections."] = "Du bist %1$.0f von maximal %2$.0f erlaubten Verbindungen eingegangen.";
-App::$strings["Add New Connection"] = "Neue Verbindung hinzufügen";
-App::$strings["Enter channel address"] = "Adresse des Kanals eingeben";
-App::$strings["Examples: bob@example.com, https://example.com/barbara"] = "Beispiele: bob@beispiel.com, http://beispiel.com/barbara";
-App::$strings["Notes"] = "Notizen";
-App::$strings["Remove term"] = "Eintrag löschen";
-App::$strings["Archives"] = "Archive";
-App::$strings["Refresh"] = "Aktualisieren";
-App::$strings["Account settings"] = "Konto-Einstellungen";
-App::$strings["Channel settings"] = "Kanal-Einstellungen";
-App::$strings["Additional features"] = "Zusätzliche Funktionen";
-App::$strings["Feature/Addon settings"] = "Plugin-Einstellungen";
-App::$strings["Display settings"] = "Anzeige-Einstellungen";
-App::$strings["Manage locations"] = "Klon-Adressen verwalten";
-App::$strings["Export channel"] = "Kanal exportieren";
-App::$strings["Connected apps"] = "Verbundene Apps";
-App::$strings["Premium Channel Settings"] = "Premium-Kanal-Einstellungen";
-App::$strings["Private Mail Menu"] = "Private Nachrichten";
-App::$strings["Combined View"] = "Kombinierte Anzeige";
-App::$strings["Conversations"] = "Konversationen";
-App::$strings["Received Messages"] = "Erhaltene Nachrichten";
-App::$strings["Sent Messages"] = "Gesendete Nachrichten";
-App::$strings["No messages."] = "Keine Nachrichten.";
-App::$strings["Delete conversation"] = "Unterhaltung löschen";
-App::$strings["Events Tools"] = "Kalenderwerkzeuge";
-App::$strings["Export Calendar"] = "Kalender exportieren";
-App::$strings["Import Calendar"] = "Kalender importieren";
-App::$strings["Chatrooms"] = "Chaträume";
-App::$strings["Overview"] = "Übersicht";
-App::$strings["Chat Members"] = "Chatmitglieder";
-App::$strings["Wiki List"] = "Wikiliste";
-App::$strings["Create new wiki"] = "Neues Wiki erstellen";
-App::$strings["Send notification"] = "Benachrichtigung senden";
-App::$strings["Wiki Pages"] = "Wikiseiten";
-App::$strings["Add new page"] = "Neue Seite hinzufügen";
-App::$strings["Page name"] = "Seitenname";
-App::$strings["Bookmarked Chatrooms"] = "Gespeicherte Chatrooms";
-App::$strings["Suggested Chatrooms"] = "Chatraum-Vorschläge";
-App::$strings["photo/image"] = "Foto/Bild";
-App::$strings["Click to show more"] = "Klick, um mehr anzuzeigen";
-App::$strings["Rating Tools"] = "Bewertungswerkzeuge";
-App::$strings["Rate Me"] = "Bewerte mich";
-App::$strings["View Ratings"] = "Bewertungen ansehen";
-App::$strings["Forums"] = "Foren";
-App::$strings["Tasks"] = "Aufgaben";
-App::$strings["Documentation"] = "Dokumentation";
-App::$strings["Member registrations waiting for confirmation"] = "Nutzer-Anmeldungen, die auf Bestätigung warten";
-App::$strings["Inspect queue"] = "Warteschlange kontrollieren";
-App::$strings["DB updates"] = "DB-Aktualisierungen";
-App::$strings["Plugin Features"] = "Plug-In Funktionen";
App::$strings["Who can see this?"] = "Wer kann das sehen?";
App::$strings["Custom selection"] = "Benutzerdefinierte Auswahl";
App::$strings["Select \"Show\" to allow viewing. \"Don't show\" lets you override and limit the scope of \"Show\"."] = "Wähle \"Anzeigen\", um Betrachtung zuzulassen. \"Nicht anzeigen\" überstimmt und limitiert den Aktionsradius von \"Anzeigen\" für Ausnahmen.";
App::$strings["Show"] = "Anzeigen";
App::$strings["Don't show"] = "Nicht anzeigen";
App::$strings["Post permissions %s cannot be changed %s after a post is shared.</br />These permissions set who is allowed to view the post."] = "Beitragsberechtigungen %s können nicht geändert werden %s, nachdem der Beitrag gesendet wurde.<br />Diese Berechtigungen bestimmen, wer den Beitrag sehen kann.";
+App::$strings["Cannot locate DNS info for database server '%s'"] = "Kann die DNS-Informationen für den Datenbank-Server '%s' nicht finden";
+App::$strings["Image/photo"] = "Bild/Foto";
+App::$strings["Encrypted content"] = "Verschlüsselter Inhalt";
+App::$strings["Install %s element: "] = "Element %s installieren: ";
+App::$strings["This post contains an installable %s element, however you lack permissions to install it on this site."] = "Dieser Beitrag beinhaltet ein installierbares %s Element, aber Du hast nicht die nötigen Rechte, um es auf diesem Hub zu installieren.";
+App::$strings["card"] = "Karte";
+App::$strings["Click to open/close"] = "Klicke zum Öffnen/Schließen";
+App::$strings["spoiler"] = "Spoiler";
+App::$strings["$1 wrote:"] = "$1 schrieb:";
App::$strings[" by "] = "von";
App::$strings[" on "] = "am";
App::$strings["Embedded content"] = "Eingebetteter Inhalt";
App::$strings["Embedding disabled"] = "Einbetten deaktiviert";
-App::$strings["Attachments:"] = "Anhänge:";
-App::$strings["\$Projectname event notification:"] = "\$Projectname-Terminbenachrichtigung:";
-App::$strings["Can view my normal stream and posts"] = "Kann meine normalen Beiträge sehen";
-App::$strings["Can view my webpages"] = "Kann meine Webseiten sehen";
-App::$strings["Can post on my channel page (\"wall\")"] = "Kann auf meiner Kanal-Seite (\"wall\") Beiträge veröffentlichen";
-App::$strings["Can like/dislike stuff"] = "Kann andere Elemente mögen/nicht mögen";
-App::$strings["Profiles and things other than posts/comments"] = "Profile und alles außer Beiträge und Kommentare";
-App::$strings["Can forward to all my channel contacts via post @mentions"] = "Kann an alle meine Kontakte via @-Erwähnung Nachrichten weiterleiten";
-App::$strings["Advanced - useful for creating group forum channels"] = "Fortgeschritten - sinnvoll, um Gruppen-Kanäle/-Foren zu erstellen";
-App::$strings["Can chat with me (when available)"] = "Kann mit mir chatten (wenn verfügbar)";
-App::$strings["Can write to my file storage and photos"] = "Kann in meine Datei- und Bilderordner schreiben";
-App::$strings["Can edit my webpages"] = "Kann meine Webseiten bearbeiten";
-App::$strings["Somewhat advanced - very useful in open communities"] = "Etwas fortgeschritten – sehr nützlich in offenen Gemeinschaften";
-App::$strings["Can administer my channel resources"] = "Kann meine Kanäle administrieren";
-App::$strings["Extremely advanced. Leave this alone unless you know what you are doing"] = "Sehr fortgeschritten. Bearbeite das nur, wenn Du genau weißt, was Du tust";
-App::$strings["%1\$s is now connected with %2\$s"] = "%1\$s ist jetzt mit %2\$s verbunden";
-App::$strings["%1\$s poked %2\$s"] = "%1\$s stupste %2\$s an";
-App::$strings["View %s's profile @ %s"] = "%ss Profil auf %s ansehen";
-App::$strings["Categories:"] = "Kategorien:";
-App::$strings["Filed under:"] = "Gespeichert unter:";
-App::$strings["View in context"] = "Im Zusammenhang anschauen";
-App::$strings["remove"] = "lösche";
-App::$strings["Delete Selected Items"] = "Lösche die ausgewählten Elemente";
-App::$strings["View Source"] = "Quelle anzeigen";
-App::$strings["Follow Thread"] = "Unterhaltung folgen";
-App::$strings["Unfollow Thread"] = "Unterhaltung nicht mehr folgen";
-App::$strings["Activity/Posts"] = "Aktivitäten/Beiträge";
-App::$strings["Edit Connection"] = "Verbindung bearbeiten";
-App::$strings["Message"] = "Nachricht";
-App::$strings["%s likes this."] = "%s gefällt das.";
-App::$strings["%s doesn't like this."] = "%s gefällt das nicht.";
-App::$strings["<span %1\$s>%2\$d people</span> like this."] = array(
- 0 => "<span %1\$s>%2\$d Person</span> gefällt das.",
- 1 => "<span %1\$s>%2\$d Leuten</span> gefällt das.",
-);
-App::$strings["<span %1\$s>%2\$d people</span> don't like this."] = array(
- 0 => "<span %1\$s>%2\$d Person</span> gefällt das nicht.",
- 1 => "<span %1\$s>%2\$d Leuten</span> gefällt das nicht.",
-);
-App::$strings["and"] = "und";
-App::$strings[", and %d other people"] = array(
- 0 => "",
- 1 => ", und %d andere",
+App::$strings["OpenWebAuth: %1\$s welcomes %2\$s"] = "";
+App::$strings["General Features"] = "Allgemeine Funktionen";
+App::$strings["Multiple Profiles"] = "Mehrfachprofile";
+App::$strings["Ability to create multiple profiles"] = "Ermöglicht das Anlegen mehrerer Profile pro Kanal";
+App::$strings["Advanced Profiles"] = "Erweiterte Profile";
+App::$strings["Additional profile sections and selections"] = "Stellt zusätzliche Bereiche und Felder im Profil zur Verfügung";
+App::$strings["Profile Import/Export"] = "Profil-Import/Export";
+App::$strings["Save and load profile details across sites/channels"] = "Ermöglicht das Speichern von Profilen, um sie in einen anderen Kanal zu importieren";
+App::$strings["Web Pages"] = "Webseiten";
+App::$strings["Provide managed web pages on your channel"] = "Ermöglicht das Erstellen von Webseiten in Deinem Kanal";
+App::$strings["Provide a wiki for your channel"] = "Stelle ein Wiki in Deinem Kanal zur Verfügung";
+App::$strings["Private Notes"] = "Private Notizen";
+App::$strings["Enables a tool to store notes and reminders (note: not encrypted)"] = "Aktiviert ein Werkzeug mit dem Notizen und Erinnerungen gespeichert werden können (Hinweis: nicht verschlüsselt)";
+App::$strings["Create personal planning cards"] = "Erstelle persönliche (Notiz-)Karten zur Planung/Koordination oder ähnlichen Zwecken";
+App::$strings["Navigation Channel Select"] = "Kanal-Auswahl in der Navigationsleiste";
+App::$strings["Change channels directly from within the navigation dropdown menu"] = "Ermöglicht den direkten Wechsel zu anderen Kanälen über das Navigationsmenü";
+App::$strings["Photo Location"] = "Aufnahmeort";
+App::$strings["If location data is available on uploaded photos, link this to a map."] = "Verlinkt den Aufnahmeort von Fotos (falls verfügbar) auf einer Karte";
+App::$strings["Access Controlled Chatrooms"] = "Zugriffskontrollierte Chaträume";
+App::$strings["Provide chatrooms and chat services with access control."] = "Bieten Sie Chaträume und Chatdienste mit Zugriffskontrolle an.";
+App::$strings["Provide alternate connection permission roles."] = "Stelle benutzerdefinierte Berechtigungsrollen für Verbindungen zur Verfügung.";
+App::$strings["Smart Birthdays"] = "Smarte Geburtstage";
+App::$strings["Make birthday events timezone aware in case your friends are scattered across the planet."] = "Stellt für Geburtstage einen Zeitzonenbezug her, falls deine Freunde über den ganzen Planeten verstreut sind.";
+App::$strings["Event Timezone Selection"] = "Termin-Zeitzonenauswahl";
+App::$strings["Allow event creation in timezones other than your own."] = "Ermögliche das Erstellen von Terminen in anderen Zeitzonen als Deiner eigenen.";
+App::$strings["Advanced Directory Search"] = "Erweiterte Verzeichnissuche";
+App::$strings["Allows creation of complex directory search queries"] = "Ermöglicht die Erstellung komplexer Verzeichnis-Suchabfragen";
+App::$strings["Advanced Theme and Layout Settings"] = "Erweiterte Design- und Layout-Einstellungen";
+App::$strings["Allows fine tuning of themes and page layouts"] = "Erlaubt die Feineinstellung von Designs und Seitenlayouts";
+App::$strings["Post Composition Features"] = "Nachbearbeitungsfunktionen";
+App::$strings["Large Photos"] = "Große Fotos";
+App::$strings["Include large (1024px) photo thumbnails in posts. If not enabled, use small (640px) photo thumbnails"] = "Große Vorschaubilder (1024px) in Beiträgen anzeigen. Falls nicht aktiviert, werden kleine Vorschaubilder (640px) verwendet.";
+App::$strings["Automatically import channel content from other channels or feeds"] = "Ermöglicht den automatischen Import von Inhalten für diesen Kanal von anderen Kanälen oder Feeds";
+App::$strings["Even More Encryption"] = "Noch mehr Verschlüsselung";
+App::$strings["Allow optional encryption of content end-to-end with a shared secret key"] = "Ermöglicht optional die zusätzliche Verschlüsselung von Inhalten (Ende-zu-Ende mit geteiltem Schlüssel)";
+App::$strings["Enable Voting Tools"] = "Umfragewerkzeuge aktivieren";
+App::$strings["Provide a class of post which others can vote on"] = "Aktiviert die Umfragewerkzeuge, um anderen die Möglichkeit zu geben, einem Beitrag zuzustimmen, ihn abzulehnen oder sich zu enthalten. (Muss im Beitrag selbst noch aktiviert werden.)";
+App::$strings["Disable Comments"] = "Kommentare deaktivieren";
+App::$strings["Provide the option to disable comments for a post"] = "Ermöglicht, die Kommentarfunktion für einzelne Beiträge abzuschalten";
+App::$strings["Delayed Posting"] = "Verzögertes Senden";
+App::$strings["Allow posts to be published at a later date"] = "Ermöglicht es, Beiträge zu einem späteren Zeitpunkt zu veröffentlichen";
+App::$strings["Content Expiration"] = "Verfall von Inhalten";
+App::$strings["Remove posts/comments and/or private messages at a future time"] = "Ermöglicht das automatische Löschen von Beiträgen, Kommentaren und/oder privaten Nachrichten zu einem zukünftigen Datum.";
+App::$strings["Suppress Duplicate Posts/Comments"] = "Doppelte Beiträge unterdrücken";
+App::$strings["Prevent posts with identical content to be published with less than two minutes in between submissions."] = "Verhindert, dass innerhalb von zwei Minuten Beiträge mit identischem Inhalt veröffentlicht werden.";
+App::$strings["Network and Stream Filtering"] = "Netzwerk- und Stream-Filter";
+App::$strings["Search by Date"] = "Suche nach Datum";
+App::$strings["Ability to select posts by date ranges"] = "Möglichkeit, Beiträge nach Zeiträumen auszuwählen";
+App::$strings["Privacy Groups"] = "Gruppen";
+App::$strings["Enable management and selection of privacy groups"] = "Auswahl und Verwaltung von Gruppen für Kanäle aktivieren";
+App::$strings["Save search terms for re-use"] = "Ermöglicht das Abspeichern von Suchbegriffen zur Wiederverwendung";
+App::$strings["Network Personal Tab"] = "Persönlicher Netzwerkreiter";
+App::$strings["Enable tab to display only Network posts that you've interacted on"] = "Aktiviert einen Reiter in der Grid-Ansicht, der nur Netzwerk-Beiträge anzeigt, mit denen Du interagiert hast";
+App::$strings["Network New Tab"] = "Netzwerkreiter Neu";
+App::$strings["Enable tab to display all new Network activity"] = "Aktiviert einen Reiter in der Grid-Ansicht, der alle neuen Netzwerkaktivitäten anzeigt";
+App::$strings["Affinity Tool"] = "Beziehungs-Tool";
+App::$strings["Filter stream activity by depth of relationships"] = "Aktiviert ein Werkzeug in der Grid-Ansicht, das den Stream nach Grad der Beziehung filtern kann";
+App::$strings["Show friend and connection suggestions"] = "Freund- und Verbindungsvorschläge anzeigen";
+App::$strings["Connection Filtering"] = "Filter für Verbindungen";
+App::$strings["Filter incoming posts from connections based on keywords/content"] = "Ermöglicht die Filterung eingehender Beiträge anhand von Schlüsselwörtern (muss an der Verbindung konfiguriert werden)";
+App::$strings["Post/Comment Tools"] = "Beitrag-/Kommentar-Tools";
+App::$strings["Community Tagging"] = "Gemeinschaftliches Verschlagworten";
+App::$strings["Ability to tag existing posts"] = "Ermöglicht das Verschlagworten existierender Beiträge";
+App::$strings["Post Categories"] = "Beitrags-Kategorien";
+App::$strings["Add categories to your posts"] = "Aktiviert Kategorien für Beiträge";
+App::$strings["Emoji Reactions"] = "Emoji Reaktionen";
+App::$strings["Add emoji reaction ability to posts"] = "Aktiviert Emoji-Reaktionen für Beiträge";
+App::$strings["Ability to file posts under folders"] = "Möglichkeit, Beiträge in Verzeichnissen zu sammeln";
+App::$strings["Dislike Posts"] = "Gefällt-mir-nicht-Beiträge";
+App::$strings["Ability to dislike posts/comments"] = "Aktiviert die „Gefällt mir nicht“-Schaltfläche";
+App::$strings["Star Posts"] = "Beiträge mit Sternchen versehen";
+App::$strings["Ability to mark special posts with a star indicator"] = "Ermöglicht die lokale Markierung spezieller Beiträge mit einem Sternchen-Symbol";
+App::$strings["Tag Cloud"] = "Schlagwort-Wolke";
+App::$strings["Provide a personal tag cloud on your channel page"] = "Aktiviert die Anzeige einer Schlagwort-Wolke (Tag Cloud) auf Deiner Kanal-Seite";
+App::$strings["Premium Channel"] = "Premium-Kanal";
+App::$strings["Allows you to set restrictions and terms on those that connect with your channel"] = "Ermöglicht es, Einschränkungen und Bedingungen für Verbindungen dieses Kanals festzulegen";
+App::$strings["Tags"] = "Schlagwörter";
+App::$strings["Keywords"] = "Schlüsselwörter";
+App::$strings["have"] = "habe";
+App::$strings["has"] = "hat";
+App::$strings["want"] = "will";
+App::$strings["wants"] = "will";
+App::$strings["likes"] = "gefällt";
+App::$strings["dislikes"] = "missfällt";
+App::$strings["Not a valid email address"] = "Ungültige E-Mail-Adresse";
+App::$strings["Your email domain is not among those allowed on this site"] = "Deine E-Mail-Adresse ist auf dieser Seite nicht erlaubt";
+App::$strings["Your email address is already registered at this site."] = "Deine E-Mail-Adresse ist auf dieser Seite bereits registriert.";
+App::$strings["An invitation is required."] = "Eine Einladung wird benötigt.";
+App::$strings["Invitation could not be verified."] = "Die Einladung konnte nicht bestätigt werden.";
+App::$strings["Please enter the required information."] = "Bitte gib die benötigten Informationen ein.";
+App::$strings["Failed to store account information."] = "Speichern der Nutzerkontodaten fehlgeschlagen.";
+App::$strings["Registration confirmation for %s"] = "Registrierungsbestätigung für %s";
+App::$strings["Registration request at %s"] = "Registrierungsanfrage auf %s";
+App::$strings["your registration password"] = "Dein Registrierungspasswort";
+App::$strings["Registration details for %s"] = "Registrierungsdetails für %s";
+App::$strings["Account approved."] = "Nutzerkonto bestätigt.";
+App::$strings["Registration revoked for %s"] = "Registrierung für %s wurde widerrufen";
+App::$strings["Click here to upgrade."] = "Klicke hier, um das Upgrade durchzuführen.";
+App::$strings["This action exceeds the limits set by your subscription plan."] = "Diese Aktion überschreitet die Grenzen Ihres Abonnements.";
+App::$strings["This action is not available under your subscription plan."] = "Diese Aktion ist in Ihrem Abonnement nicht verfügbar.";
+App::$strings["Birthday"] = "Geburtstag";
+App::$strings["Age: "] = "Alter:";
+App::$strings["YYYY-MM-DD or MM-DD"] = "JJJJ-MM-TT oder MM-TT";
+App::$strings["less than a second ago"] = "Vor weniger als einer Sekunde";
+App::$strings["__ctx:e.g. 22 hours ago, 1 minute ago__ %1\$d %2\$s ago"] = "vor %1\$d %2\$s";
+App::$strings["__ctx:relative_date__ year"] = array(
+ 0 => "Jahr",
+ 1 => "Jahre",
);
-App::$strings["%s like this."] = "%s gefällt das.";
-App::$strings["%s don't like this."] = "%s gefällt das nicht.";
-App::$strings["Set your location"] = "Standort";
-App::$strings["Clear browser location"] = "Browser-Standort löschen";
-App::$strings["Tag term:"] = "Schlagwort:";
-App::$strings["Where are you right now?"] = "Wo bist Du jetzt grade?";
-App::$strings["Comments enabled"] = "Kommentare aktiviert";
-App::$strings["Comments disabled"] = "Kommentare deaktiviert";
-App::$strings["Page link name"] = "Link zur Seite";
-App::$strings["Post as"] = "Veröffentlichen als";
-App::$strings["Toggle voting"] = "Umfragewerkzeug aktivieren";
-App::$strings["Disable comments"] = "Kommentare deaktivieren";
-App::$strings["Toggle comments"] = "Kommentare umschalten";
-App::$strings["Categories (optional, comma-separated list)"] = "Kategorien (optional, kommagetrennte Liste)";
-App::$strings["Other networks and post services"] = "Andere Netzwerke und Platformen";
-App::$strings["Set publish date"] = "Veröffentlichungsdatum festlegen";
-App::$strings["Discover"] = "Entdecken";
-App::$strings["Imported public streams"] = "Importierte öffentliche Beiträge";
-App::$strings["Commented Order"] = "Neueste Kommentare";
-App::$strings["Sort by Comment Date"] = "Nach Kommentardatum sortiert";
-App::$strings["Posted Order"] = "Neueste Beiträge";
-App::$strings["Sort by Post Date"] = "Nach Beitragsdatum sortiert";
-App::$strings["Posts that mention or involve you"] = "Beiträge mit Beteiligung Deinerseits";
-App::$strings["Activity Stream - by date"] = "Activity Stream – nach Datum sortiert";
-App::$strings["Starred"] = "Markiert";
-App::$strings["Favourite Posts"] = "Markierte Beiträge";
-App::$strings["Spam"] = "Spam";
-App::$strings["Posts flagged as SPAM"] = "Nachrichten, die als SPAM markiert wurden";
-App::$strings["Status Messages and Posts"] = "Statusnachrichten und Beiträge";
-App::$strings["About"] = "Über";
-App::$strings["Profile Details"] = "Profil-Details";
-App::$strings["Files and Storage"] = "Dateien und Speicher";
-App::$strings["Saved Bookmarks"] = "Gespeicherte Lesezeichen";
-App::$strings["Manage Webpages"] = "Webseiten verwalten";
-App::$strings["__ctx:noun__ Attending"] = array(
- 0 => "Zusage",
- 1 => "Zusagen",
+App::$strings["__ctx:relative_date__ month"] = array(
+ 0 => "Monat",
+ 1 => "Monate",
);
-App::$strings["__ctx:noun__ Not Attending"] = array(
- 0 => "Absage",
- 1 => "Absagen",
+App::$strings["__ctx:relative_date__ week"] = array(
+ 0 => "Woche",
+ 1 => "Wochen",
);
-App::$strings["__ctx:noun__ Undecided"] = array(
- 0 => " Unentschlossen",
- 1 => "Unentschlossene",
+App::$strings["__ctx:relative_date__ day"] = array(
+ 0 => "Tag",
+ 1 => "Tage",
);
-App::$strings["__ctx:noun__ Agree"] = array(
- 0 => "Zustimmung",
- 1 => "Zustimmungen",
+App::$strings["__ctx:relative_date__ hour"] = array(
+ 0 => "Stunde",
+ 1 => "Stunden",
);
-App::$strings["__ctx:noun__ Disagree"] = array(
- 0 => "Ablehnung",
- 1 => "Ablehnungen",
+App::$strings["__ctx:relative_date__ minute"] = array(
+ 0 => "Minute",
+ 1 => "Minuten",
);
-App::$strings["__ctx:noun__ Abstain"] = array(
- 0 => "Enthaltung",
- 1 => "Enthaltungen",
+App::$strings["__ctx:relative_date__ second"] = array(
+ 0 => "Sekunde",
+ 1 => "Sekunden",
);
-App::$strings["Image/photo"] = "Bild/Foto";
-App::$strings["Encrypted content"] = "Verschlüsselter Inhalt";
-App::$strings["Install %s element: "] = "Element %s installieren: ";
-App::$strings["This post contains an installable %s element, however you lack permissions to install it on this site."] = "Dieser Beitrag beinhaltet ein installierbares %s Element, aber Du hast nicht die nötigen Rechte, um es auf diesem Hub zu installieren.";
-App::$strings["%1\$s wrote the following %2\$s %3\$s"] = "%1\$s schrieb den folgenden %2\$s %3\$s";
-App::$strings["Click to open/close"] = "Klicke zum Öffnen/Schließen";
-App::$strings["spoiler"] = "Spoiler";
-App::$strings["$1 wrote:"] = "$1 schrieb:";
-App::$strings["Focus (Hubzilla default)"] = "Focus (Voreinstellung für Hubzilla)";
-App::$strings["Theme settings"] = "Theme-Einstellungen";
-App::$strings["Narrow navbar"] = "Schmale Navigationsleiste";
-App::$strings["Navigation bar background color"] = "Hintergrundfarbe der Navigationsleiste";
-App::$strings["Navigation bar gradient top color"] = "Farbverlauf der Navigationsleiste: Farbe oben";
-App::$strings["Navigation bar gradient bottom color"] = "Farbverlauf der Navigationsleiste: Farbe unten";
-App::$strings["Navigation active button gradient top color"] = "Navigations-Button aktiv: Farbe für Farbverlauf oben";
-App::$strings["Navigation active button gradient bottom color"] = "Navigations-Button aktiv: Farbe für Farbverlauf unten";
-App::$strings["Navigation bar border color "] = "Farbe für den Rand der Navigationsleiste";
-App::$strings["Navigation bar icon color "] = "Farbe für die Icons der Navigationsleiste";
-App::$strings["Navigation bar active icon color "] = "Farbe für aktive Icons der Navigationsleiste";
-App::$strings["link color"] = "Farbe für Links";
-App::$strings["Set font-color for banner"] = "Farbe der Schrift des Banners";
-App::$strings["Set the background color"] = "Hintergrundfarbe";
-App::$strings["Set the background image"] = "Hintergrundbild";
-App::$strings["Set the background color of items"] = "Hintergrundfarbe für Beiträge";
-App::$strings["Set the background color of comments"] = "Hintergrundfarbe für Kommentare";
-App::$strings["Set the border color of comments"] = "Farbe des Randes von Kommentaren";
-App::$strings["Set the indent for comments"] = "Einzugsbreite für Kommentare";
-App::$strings["Set the basic color for item icons"] = "Grundfarbe für Beitrags-Icons";
-App::$strings["Set the hover color for item icons"] = "Farbe für Beitrags-Icons unter dem Mauszeiger";
-App::$strings["Set font-size for the entire application"] = "Schriftgröße für die gesamte Anwendung";
-App::$strings["Example: 14px"] = "Beispiel: 14px";
-App::$strings["Set font-size for posts and comments"] = "Schriftgröße für Beiträge und Kommentare";
-App::$strings["Set font-color for posts and comments"] = "Schriftfarbe für Beiträge und Kommentare";
-App::$strings["Set radius of corners"] = "Ecken-Radius";
-App::$strings["Set shadow depth of photos"] = "Schattentiefe von Fotos";
-App::$strings["Set maximum width of content region in pixel"] = "Maximalbreite des Inhaltsbereichs in Pixel festlegen";
-App::$strings["Leave empty for default width"] = "Leer lassen für Standardbreite";
-App::$strings["Left align page content"] = "Seiteninhalt linksbündig anzeigen";
-App::$strings["Set minimum opacity of nav bar - to hide it"] = "Mindest-Deckkraft der Navigationsleiste ( - versteckt sie)";
-App::$strings["Set size of conversation author photo"] = "Größe der Avatare von Themenstartern";
-App::$strings["Set size of followup author photos"] = "Größe der Avatare von Kommentatoren";
-App::$strings["__ctx:opensearch__ Search %1\$s (%2\$s)"] = "Suche %1\$s (%2\$s)";
-App::$strings["__ctx:opensearch__ \$Projectname"] = "\$Projectname";
-App::$strings["Update %s failed. See error logs."] = "Aktualisierung %s fehlgeschlagen. Details in den Fehlerprotokollen.";
-App::$strings["Update Error at %s"] = "Aktualisierungsfehler auf %s";
-App::$strings["Create an account to access services and applications within the Hubzilla"] = "Erstelle ein Konto, um Anwendungen und Dienste innerhalb von Hubzilla nutzen zu können.";
-App::$strings["Login/Email"] = "Anmelden/E-Mail";
-App::$strings["Password"] = "Kennwort";
-App::$strings["Remember me"] = "Angaben speichern";
-App::$strings["Forgot your password?"] = "Passwort vergessen?";
-App::$strings["toggle mobile"] = "auf/von mobile Ansicht wechseln";
-App::$strings["Website SSL certificate is not valid. Please correct."] = "Das SSL-Zertifikat der Website ist nicht gültig. Bitte beheben.";
-App::$strings["[hubzilla] Website SSL error for %s"] = "[hubzilla] Website-SSL-Fehler für %s";
-App::$strings["Cron/Scheduled tasks not running."] = "Cron-Aufgaben laufen nicht.";
-App::$strings["[hubzilla] Cron tasks not running on %s"] = "[hubzilla] Cron-Aufgaben für %s laufen nicht";
+App::$strings["%1\$s's birthday"] = "%1\$ss Geburtstag";
+App::$strings["Happy Birthday %1\$s"] = "Alles Gute zum Geburtstag, %1\$s";
+App::$strings["Remote authentication"] = "Über Konto auf anderem Server einloggen";
+App::$strings["Click to authenticate to your home hub"] = "Klicke, um Dich über Deinen Heimat-Server zu authentifizieren";
+App::$strings["Network Activity"] = "Netzwerk-Aktivitäten";
+App::$strings["Mark all activity notifications seen"] = "Alle Benachrichtigungen als gesehen markieren";
+App::$strings["Channel home"] = "Mein Kanal";
+App::$strings["View your channel home"] = "Zeige Deine Kanalseite an";
+App::$strings["Mark all channel notifications seen"] = "Markiere alle Kanal-Benachrichtigungen als angesehen";
+App::$strings["Registrations"] = "Registrierungen";
+App::$strings["Notifications"] = "Benachrichtigungen";
+App::$strings["View all notifications"] = "Alle Benachrichtigungen ansehen";
+App::$strings["Mark all system notifications seen"] = "Markiere alle System-Benachrichtigungen als gesehen";
+App::$strings["Private mail"] = "Persönliche Mail";
+App::$strings["View your private messages"] = "Zeige Deine persönlichen Nachrichten an";
+App::$strings["Mark all private messages seen"] = "Markiere alle persönlichen Nachrichten als gesehen";
+App::$strings["Event Calendar"] = "Terminkalender";
+App::$strings["Manage Your Channels"] = "Verwalte Deine Kanäle";
+App::$strings["Account/Channel Settings"] = "Konto-/Kanal-Einstellungen";
+App::$strings["End this session"] = "Beende diese Sitzung";
+App::$strings["Your profile page"] = "Deine Profilseite";
+App::$strings["Manage/Edit profiles"] = "Profile verwalten";
+App::$strings["Edit your profile"] = "Profil bearbeiten";
+App::$strings["Sign in"] = "Anmelden";
+App::$strings["Take me home"] = "Bringe mich nach Hause (eigener Kanal)";
+App::$strings["Log me out of this site"] = "Logge mich von dieser Seite aus";
+App::$strings["Create an account"] = "Erzeuge ein Konto";
+App::$strings["Help and documentation"] = "Hilfe und Dokumentation";
+App::$strings["Search site @name, #tag, ?docs, content"] = "Hub durchsuchen: @Name. #Schlagwort, ?Dokumentation, Inhalt";
+App::$strings["Site Setup and Configuration"] = "Seiten-Einrichtung und -Konfiguration";
+App::$strings["@name, #tag, ?doc, content"] = "@Name, #Schlagwort, ?Dokumentation, Inhalt";
+App::$strings["Please wait..."] = "Bitte warten...";
+App::$strings["Add Apps"] = "Apps hinzufügen";
+App::$strings["Arrange Apps"] = "Apps anordnen";
+App::$strings["Toggle System Apps"] = "System-Apps umschalten";
+App::$strings["Image exceeds website size limit of %lu bytes"] = "Bild überschreitet das Webseitenlimit von %lu Bytes";
+App::$strings["Image file is empty."] = "Bilddatei ist leer.";
+App::$strings["Photo storage failed."] = "Fotospeicherung fehlgeschlagen.";
+App::$strings["a new photo"] = "ein neues Foto";
+App::$strings["__ctx:photo_upload__ %1\$s posted %2\$s to %3\$s"] = "%1\$s hat %2\$s auf %3\$s veröffentlicht";
+App::$strings["Upload New Photos"] = "Neue Fotos hochladen";
+App::$strings["Invalid data packet"] = "Ungültiges Datenpaket";
+App::$strings["Unable to verify channel signature"] = "Konnte die Signatur des Kanals nicht verifizieren";
+App::$strings["Unable to verify site signature for %s"] = "Kann die Signatur der Seite von %s nicht verifizieren";
+App::$strings["A deleted group with this name was revived. Existing item permissions <strong>may</strong> apply to this group and any future members. If this is not what you intended, please create another group with a different name."] = "Es hat früher schon einmal eine Gruppe mit diesem Namen existiert, die gelöscht wurde. Es <strong>könnten</strong> von damals noch Elemente (Beiträge, Dateien etc.) vorhanden sein, die allen jetzigen und zukünftigen Mitgliedern dieser Gruppe den Zugriff erlauben. Wenn das nicht Deine Absicht ist, erstelle bitte eine neue Gruppe mit einem anderen Namen.";
+App::$strings["Add new connections to this privacy group"] = "Neue Verbindung zu dieser Gruppe hinzufügen";
+App::$strings["edit"] = "Bearbeiten";
+App::$strings["Edit group"] = "Gruppe ändern";
+App::$strings["Add privacy group"] = "Gruppe hinzufügen";
+App::$strings["Channels not in any privacy group"] = "Kanäle, die in keiner Gruppe sind";
+App::$strings["New window"] = "Neues Fenster";
+App::$strings["Open the selected location in a different window or browser tab"] = "Öffne die markierte Adresse in einem neuen Browserfenster oder Tab";
+App::$strings["Logged out."] = "Ausgeloggt.";
+App::$strings["Email validation is incomplete. Please check your email."] = "E-Mail-Bestätigung nicht abgeschlossen. Bitte prüfe Deine E-Mails (ggf. Spam-Filterung mit berücksichtigen).";
+App::$strings["Failed authentication"] = "Authentifizierung fehlgeschlagen";
+App::$strings["Help:"] = "Hilfe:";
+App::$strings["Not Found"] = "Nicht gefunden";
diff --git a/view/de/htconfig.tpl b/view/de/htconfig.tpl
index 9d4333fb0..46bf0de14 100644
--- a/view/de/htconfig.tpl
+++ b/view/de/htconfig.tpl
@@ -34,13 +34,6 @@ App::$config['system']['baseurl'] = '{{$siteurl}}';
App::$config['system']['sitename'] = "Hubzilla";
App::$config['system']['location_hash'] = '{{$site_id}}';
-// Choices are 'basic', 'standard', and 'pro'.
-// basic sets up the sevrer for basic social networking and removes "complicated" features
-// standard provides most desired features except e-commerce
-// pro gives you access to everything
-
-App::$config['system']['server_role'] = '{{$server_role}}';
-
// These lines set additional security headers to be sent with all responses
// You may wish to set transport_security_header to 0 if your server already sends
// this header. content_security_policy may need to be disabled if you wish to
diff --git a/view/en-au/htconfig.tpl b/view/en-au/htconfig.tpl
index 090bbf06f..cefcba727 100644
--- a/view/en-au/htconfig.tpl
+++ b/view/en-au/htconfig.tpl
@@ -34,13 +34,6 @@ App::$config['system']['baseurl'] = '{{$siteurl}}';
App::$config['system']['sitename'] = "Hubzilla";
App::$config['system']['location_hash'] = '{{$site_id}}';
-// Choices are 'basic', 'standard', and 'pro'.
-// basic sets up the sevrer for basic social networking and removes "complicated" features
-// standard provides most desired features except e-commerce
-// pro gives you access to everything
-
-App::$config['system']['server_role'] = '{{$server_role}}';
-
// These lines set additional security headers to be sent with all responses
// You may wish to set transport_security_header to 0 if your server already sends
// this header. content_security_policy may need to be disabled if you wish to
diff --git a/view/en-gb/htconfig.tpl b/view/en-gb/htconfig.tpl
index 515957b36..ea458d664 100644
--- a/view/en-gb/htconfig.tpl
+++ b/view/en-gb/htconfig.tpl
@@ -34,14 +34,6 @@ App::$config['system']['baseurl'] = '{{$siteurl}}';
App::$config['system']['sitename'] = "Hubzilla";
App::$config['system']['location_hash'] = '{{$site_id}}';
-
-// Choices are 'basic', 'standard', and 'pro'.
-// basic sets up the sevrer for basic social networking and removes "complicated" features
-// standard provides most desired features except e-commerce
-// pro gives you access to everything
-
-App::$config['system']['server_role'] = '{{$server_role}}';
-
// These lines set additional security headers to be sent with all responses
// You may wish to set transport_security_header to 0 if your server already sends
// this header. content_security_policy may need to be disabled if you wish to
diff --git a/view/en/htconfig.tpl b/view/en/htconfig.tpl
index 042c89797..8159b6d44 100644
--- a/view/en/htconfig.tpl
+++ b/view/en/htconfig.tpl
@@ -34,15 +34,6 @@ App::$config['system']['baseurl'] = '{{$siteurl}}';
App::$config['system']['sitename'] = "Hubzilla";
App::$config['system']['location_hash'] = '{{$site_id}}';
-// Choices are 'basic', 'standard', and 'pro'.
-// basic sets up the server for basic social networking and removes "complicated" features
-// standard provides most desired features except e-commerce
-// pro disables protocol federation plugins and only supports the zot protocol
-// if you are in doubt or are unsure, it is strongly advised that you select 'standard'.
-
-App::$config['system']['server_role'] = '{{$server_role}}';
-
-
// These lines set additional security headers to be sent with all responses
// You may wish to set transport_security_header to 0 if your server already sends
// this header. content_security_policy may need to be disabled if you wish to
diff --git a/view/fr/hmessages.po b/view/fr/hmessages.po
index 73d711700..6f0453f9d 100644
--- a/view/fr/hmessages.po
+++ b/view/fr/hmessages.po
@@ -1,16 +1,18 @@
-# Hubzilla Project
-# Copyright (C) 2012-2014 the Hubzilla Project
-# This file is distributed under the same license as the Red package.
+# hubzilla
+# Copyright (C) 2012-2016 hubzilla
+# This file is distributed under the same license as the hubzilla package.
#
# Translators:
# kris1373 <aktosc@gmail.com>, 2015-2016
-# Raymond Monret <raymond.monret@retmesagxo.net>, 2016
+# rmonret <raymond.monret@retmesagxo.net>, 2016
+# rmonret <raymond.monret@retmesagxo.net>, 2017
+# Seraph Ino, 2016
msgid ""
msgstr ""
"Project-Id-Version: Redmatrix\n"
"Report-Msgid-Bugs-To: \n"
-"POT-Creation-Date: 2016-06-10 00:02-0700\n"
-"PO-Revision-Date: 2016-06-10 09:14+0000\n"
+"POT-Creation-Date: 2017-03-31 10:53+0200\n"
+"PO-Revision-Date: 2017-04-01 09:31+0000\n"
"Last-Translator: fabrixxm <fabrix.xm@gmail.com>\n"
"Language-Team: French (http://www.transifex.com/Friendica/red-matrix/language/fr/)\n"
"MIME-Version: 1.0\n"
@@ -19,496 +21,1825 @@ msgstr ""
"Language: fr\n"
"Plural-Forms: nplurals=2; plural=(n > 1);\n"
-#: ../../Zotlabs/Storage/Browser.php:107 ../../Zotlabs/Storage/Browser.php:239
-msgid "parent"
-msgstr "retour"
+#: ../../Zotlabs/Access/Permissions.php:46
+msgid "Can view my channel stream and posts"
+msgstr "Peut voir mon canal et mes publicatiosn"
-#: ../../Zotlabs/Storage/Browser.php:131 ../../include/text.php:2620
-msgid "Collection"
-msgstr "Groupe de contacts"
+#: ../../Zotlabs/Access/Permissions.php:47 ../../include/permissions.php:42
+msgid "Can send me their channel stream and posts"
+msgstr "Peuvent m'envoyer leur flux et les publications de leur canal"
-#: ../../Zotlabs/Storage/Browser.php:134
-msgid "Principal"
-msgstr "Principal"
+#: ../../Zotlabs/Access/Permissions.php:48 ../../include/permissions.php:36
+msgid "Can view my default channel profile"
+msgstr "Peut voir le profil par défaut du canal."
-#: ../../Zotlabs/Storage/Browser.php:137
-msgid "Addressbook"
-msgstr "Carnet d'adresse"
+#: ../../Zotlabs/Access/Permissions.php:49 ../../include/permissions.php:37
+msgid "Can view my connections"
+msgstr "Peut voir mes contacts"
-#: ../../Zotlabs/Storage/Browser.php:140
-msgid "Calendar"
-msgstr "Calendrier"
+#: ../../Zotlabs/Access/Permissions.php:50 ../../include/permissions.php:38
+msgid "Can view my file storage and photos"
+msgstr "Peut voir mes fichiers et photos"
-#: ../../Zotlabs/Storage/Browser.php:143
-msgid "Schedule Inbox"
-msgstr "Calendrier - Messages entrants"
+#: ../../Zotlabs/Access/Permissions.php:51
+msgid "Can upload/modify my file storage and photos"
+msgstr "Peut télécharger/modifier mes fichiers et mes photos"
-#: ../../Zotlabs/Storage/Browser.php:146
-msgid "Schedule Outbox"
-msgstr "Calendrier - Messages sortants"
+#: ../../Zotlabs/Access/Permissions.php:52
+msgid "Can view my channel webpages"
+msgstr "Peut voir les pages web de mon canal"
-#: ../../Zotlabs/Storage/Browser.php:164 ../../Zotlabs/Module/Photos.php:798
-#: ../../Zotlabs/Module/Photos.php:1243 ../../Zotlabs/Lib/Apps.php:486
-#: ../../Zotlabs/Lib/Apps.php:561 ../../include/widgets.php:1505
-#: ../../include/conversation.php:1032
-msgid "Unknown"
-msgstr "Inconnu"
+#: ../../Zotlabs/Access/Permissions.php:53
+msgid "Can view my wiki pages"
+msgstr "Peut voir les pages de mon wiki"
-#: ../../Zotlabs/Storage/Browser.php:226 ../../Zotlabs/Module/Fbrowser.php:85
-#: ../../Zotlabs/Lib/Apps.php:216 ../../include/nav.php:93
-#: ../../include/conversation.php:1639
-msgid "Files"
-msgstr "Fichiers"
+#: ../../Zotlabs/Access/Permissions.php:54
+msgid "Can create/edit my channel webpages"
+msgstr "Peut créer ou modifier les pages web de mon canal"
-#: ../../Zotlabs/Storage/Browser.php:227
-msgid "Total"
-msgstr "Total"
+#: ../../Zotlabs/Access/Permissions.php:55
+msgid "Can write to my wiki pages"
+msgstr "Peut écrire sur mon wiki"
-#: ../../Zotlabs/Storage/Browser.php:229
-msgid "Shared"
-msgstr "Partagé"
+#: ../../Zotlabs/Access/Permissions.php:56
+msgid "Can post on my channel (wall) page"
+msgstr "Peut écrire sur le mur de mon canal (mur)"
-#: ../../Zotlabs/Storage/Browser.php:230 ../../Zotlabs/Storage/Browser.php:306
-#: ../../Zotlabs/Module/Blocks.php:156 ../../Zotlabs/Module/Layouts.php:182
-#: ../../Zotlabs/Module/Menu.php:118 ../../Zotlabs/Module/New_channel.php:142
-#: ../../Zotlabs/Module/Webpages.php:186
-msgid "Create"
-msgstr "Créer"
+#: ../../Zotlabs/Access/Permissions.php:57 ../../include/permissions.php:44
+msgid "Can comment on or like my posts"
+msgstr "Peuvent commenter et/ou aimer mes publications"
-#: ../../Zotlabs/Storage/Browser.php:231 ../../Zotlabs/Storage/Browser.php:308
-#: ../../Zotlabs/Module/Cover_photo.php:357
-#: ../../Zotlabs/Module/Photos.php:825 ../../Zotlabs/Module/Photos.php:1364
-#: ../../Zotlabs/Module/Profile_photo.php:368 ../../include/widgets.php:1518
-msgid "Upload"
-msgstr "Envoyer"
+#: ../../Zotlabs/Access/Permissions.php:58 ../../include/permissions.php:45
+msgid "Can send me private mail messages"
+msgstr "Peuvent m'envoyer des messages privés"
-#: ../../Zotlabs/Storage/Browser.php:235 ../../Zotlabs/Module/Chat.php:247
-#: ../../Zotlabs/Module/Admin.php:1223 ../../Zotlabs/Module/Settings.php:592
-#: ../../Zotlabs/Module/Settings.php:618
-#: ../../Zotlabs/Module/Sharedwithme.php:99
-msgid "Name"
-msgstr "Nom"
+#: ../../Zotlabs/Access/Permissions.php:59
+msgid "Can like/dislike profiles and profile things"
+msgstr "Peut aimer ou détester des profiles"
-#: ../../Zotlabs/Storage/Browser.php:236
-msgid "Type"
-msgstr "Type"
+#: ../../Zotlabs/Access/Permissions.php:60
+msgid "Can forward to all my channel connections via @+ mentions in posts"
+msgstr "Peut faire suivre à tous mes contacts avec la mention @+ dans une publication"
-#: ../../Zotlabs/Storage/Browser.php:237
-#: ../../Zotlabs/Module/Sharedwithme.php:101 ../../include/text.php:1344
-msgid "Size"
-msgstr "Taille"
+#: ../../Zotlabs/Access/Permissions.php:61
+msgid "Can chat with me"
+msgstr "Peut discuter avec moi"
-#: ../../Zotlabs/Storage/Browser.php:238
-#: ../../Zotlabs/Module/Sharedwithme.php:102
-msgid "Last Modified"
-msgstr "Modifié le"
+#: ../../Zotlabs/Access/Permissions.php:62 ../../include/permissions.php:53
+msgid "Can source my public posts in derived channels"
+msgstr "Peut rediriger mes publications publiques vers des canaux dérivés"
-#: ../../Zotlabs/Storage/Browser.php:240 ../../Zotlabs/Module/Blocks.php:157
-#: ../../Zotlabs/Module/Editblock.php:109
-#: ../../Zotlabs/Module/Connections.php:290
-#: ../../Zotlabs/Module/Connections.php:310
-#: ../../Zotlabs/Module/Editpost.php:84
-#: ../../Zotlabs/Module/Editlayout.php:113
-#: ../../Zotlabs/Module/Editwebpage.php:146
-#: ../../Zotlabs/Module/Layouts.php:190 ../../Zotlabs/Module/Menu.php:112
-#: ../../Zotlabs/Module/Admin.php:2113 ../../Zotlabs/Module/Settings.php:652
-#: ../../Zotlabs/Module/Thing.php:260 ../../Zotlabs/Module/Webpages.php:187
-#: ../../Zotlabs/Lib/Apps.php:337 ../../Zotlabs/Lib/ThreadItem.php:106
-#: ../../include/channel.php:937 ../../include/channel.php:941
-#: ../../include/menu.php:108 ../../include/page_widgets.php:8
-#: ../../include/page_widgets.php:36
-msgid "Edit"
-msgstr "Modifier"
+#: ../../Zotlabs/Access/Permissions.php:63
+msgid "Can administer my channel"
+msgstr "Peut administrer mon canal"
-#: ../../Zotlabs/Storage/Browser.php:241 ../../Zotlabs/Module/Blocks.php:159
-#: ../../Zotlabs/Module/Connedit.php:572
-#: ../../Zotlabs/Module/Editblock.php:134
-#: ../../Zotlabs/Module/Connections.php:263
-#: ../../Zotlabs/Module/Editlayout.php:136
-#: ../../Zotlabs/Module/Editwebpage.php:170 ../../Zotlabs/Module/Group.php:177
-#: ../../Zotlabs/Module/Photos.php:1173 ../../Zotlabs/Module/Admin.php:1039
-#: ../../Zotlabs/Module/Admin.php:1213 ../../Zotlabs/Module/Admin.php:2114
-#: ../../Zotlabs/Module/Settings.php:653 ../../Zotlabs/Module/Thing.php:261
-#: ../../Zotlabs/Module/Webpages.php:189 ../../Zotlabs/Lib/Apps.php:338
-#: ../../Zotlabs/Lib/ThreadItem.php:126 ../../include/conversation.php:657
-msgid "Delete"
-msgstr "Supprimer"
+#: ../../Zotlabs/Access/PermissionRoles.php:248
+#: ../../include/permissions.php:945
+msgid "Social Networking"
+msgstr "Réseau social"
-#: ../../Zotlabs/Storage/Browser.php:285
-#, php-format
-msgid "You are using %1$s of your available file storage."
-msgstr "Vous utilisez %1$s de votre espace de stockage."
+#: ../../Zotlabs/Access/PermissionRoles.php:249
+#: ../../include/permissions.php:945
+msgid "Social - Mostly Public"
+msgstr "Social - principalement public"
-#: ../../Zotlabs/Storage/Browser.php:290
-#, php-format
-msgid "You are using %1$s of %2$s available file storage. (%3$s&#37;)"
-msgstr "Vous utilisez %1$s sur %2$s d'espace disponible. (%3$s&#37;)"
+#: ../../Zotlabs/Access/PermissionRoles.php:250
+#: ../../include/permissions.php:945
+msgid "Social - Restricted"
+msgstr "Social - restreint"
-#: ../../Zotlabs/Storage/Browser.php:302
-msgid "WARNING:"
-msgstr "AVERTISSEMENT&nbsp;:"
+#: ../../Zotlabs/Access/PermissionRoles.php:251
+#: ../../include/permissions.php:945
+msgid "Social - Private"
+msgstr "Social - privé"
-#: ../../Zotlabs/Storage/Browser.php:305
-msgid "Create new folder"
-msgstr "Nouveau dossier"
+#: ../../Zotlabs/Access/PermissionRoles.php:254
+#: ../../include/permissions.php:946
+msgid "Community Forum"
+msgstr "Forum communautaire"
-#: ../../Zotlabs/Storage/Browser.php:307
-msgid "Upload file"
-msgstr "Téléverser un fichier"
+#: ../../Zotlabs/Access/PermissionRoles.php:255
+#: ../../include/permissions.php:946
+msgid "Forum - Mostly Public"
+msgstr "Forum - principalement public"
-#: ../../Zotlabs/Web/WebServer.php:120 ../../Zotlabs/Module/Dreport.php:10
-#: ../../Zotlabs/Module/Dreport.php:49 ../../Zotlabs/Module/Group.php:72
-#: ../../Zotlabs/Module/Like.php:284 ../../Zotlabs/Module/Import_items.php:112
-#: ../../Zotlabs/Module/Profperm.php:28 ../../Zotlabs/Module/Subthread.php:62
-#: ../../include/items.php:385
-msgid "Permission denied"
-msgstr "Accès refusé"
+#: ../../Zotlabs/Access/PermissionRoles.php:256
+#: ../../include/permissions.php:946
+msgid "Forum - Restricted"
+msgstr "Forum - restreint"
-#: ../../Zotlabs/Web/WebServer.php:121 ../../Zotlabs/Web/Router.php:65
-#: ../../Zotlabs/Module/Achievements.php:34 ../../Zotlabs/Module/Blocks.php:73
-#: ../../Zotlabs/Module/Blocks.php:80 ../../Zotlabs/Module/Channel.php:105
-#: ../../Zotlabs/Module/Channel.php:226 ../../Zotlabs/Module/Channel.php:267
-#: ../../Zotlabs/Module/Chat.php:100 ../../Zotlabs/Module/Chat.php:105
-#: ../../Zotlabs/Module/Authtest.php:16 ../../Zotlabs/Module/Block.php:26
-#: ../../Zotlabs/Module/Block.php:76 ../../Zotlabs/Module/Bookmarks.php:61
-#: ../../Zotlabs/Module/Connedit.php:366 ../../Zotlabs/Module/Editblock.php:67
-#: ../../Zotlabs/Module/Common.php:39 ../../Zotlabs/Module/Connections.php:33
-#: ../../Zotlabs/Module/Cover_photo.php:277
-#: ../../Zotlabs/Module/Cover_photo.php:290
-#: ../../Zotlabs/Module/Editpost.php:17 ../../Zotlabs/Module/Events.php:265
-#: ../../Zotlabs/Module/Editlayout.php:67
-#: ../../Zotlabs/Module/Editlayout.php:90
-#: ../../Zotlabs/Module/Editwebpage.php:69
-#: ../../Zotlabs/Module/Editwebpage.php:90
-#: ../../Zotlabs/Module/Editwebpage.php:105
-#: ../../Zotlabs/Module/Editwebpage.php:127 ../../Zotlabs/Module/Group.php:13
-#: ../../Zotlabs/Module/Api.php:13 ../../Zotlabs/Module/Api.php:18
-#: ../../Zotlabs/Module/Filestorage.php:24
-#: ../../Zotlabs/Module/Filestorage.php:79
-#: ../../Zotlabs/Module/Filestorage.php:94
-#: ../../Zotlabs/Module/Filestorage.php:121 ../../Zotlabs/Module/Item.php:210
-#: ../../Zotlabs/Module/Item.php:218 ../../Zotlabs/Module/Item.php:1070
-#: ../../Zotlabs/Module/Layouts.php:71 ../../Zotlabs/Module/Layouts.php:78
-#: ../../Zotlabs/Module/Layouts.php:89 ../../Zotlabs/Module/Id.php:76
-#: ../../Zotlabs/Module/Like.php:181 ../../Zotlabs/Module/Invite.php:17
-#: ../../Zotlabs/Module/Invite.php:91 ../../Zotlabs/Module/Locs.php:87
-#: ../../Zotlabs/Module/Mail.php:129 ../../Zotlabs/Module/Manage.php:10
-#: ../../Zotlabs/Module/Menu.php:78 ../../Zotlabs/Module/Message.php:18
-#: ../../Zotlabs/Module/Mood.php:116 ../../Zotlabs/Module/Network.php:17
-#: ../../Zotlabs/Module/Mitem.php:115 ../../Zotlabs/Module/New_channel.php:77
-#: ../../Zotlabs/Module/New_channel.php:104
-#: ../../Zotlabs/Module/Notifications.php:70
-#: ../../Zotlabs/Module/Photos.php:75 ../../Zotlabs/Module/Page.php:35
-#: ../../Zotlabs/Module/Page.php:90 ../../Zotlabs/Module/Pdledit.php:26
-#: ../../Zotlabs/Module/Poke.php:137 ../../Zotlabs/Module/Profile.php:68
-#: ../../Zotlabs/Module/Profile.php:76 ../../Zotlabs/Module/Profiles.php:203
-#: ../../Zotlabs/Module/Profiles.php:601
-#: ../../Zotlabs/Module/Profile_photo.php:256
-#: ../../Zotlabs/Module/Profile_photo.php:269
-#: ../../Zotlabs/Module/Rate.php:113 ../../Zotlabs/Module/Appman.php:75
-#: ../../Zotlabs/Module/Register.php:77 ../../Zotlabs/Module/Regmod.php:21
-#: ../../Zotlabs/Module/Service_limits.php:11
-#: ../../Zotlabs/Module/Settings.php:572 ../../Zotlabs/Module/Setup.php:215
-#: ../../Zotlabs/Module/Sharedwithme.php:11
-#: ../../Zotlabs/Module/Sources.php:74 ../../Zotlabs/Module/Suggest.php:30
-#: ../../Zotlabs/Module/Thing.php:274 ../../Zotlabs/Module/Thing.php:294
-#: ../../Zotlabs/Module/Thing.php:331
-#: ../../Zotlabs/Module/Viewconnections.php:25
-#: ../../Zotlabs/Module/Viewconnections.php:30
-#: ../../Zotlabs/Module/Viewsrc.php:18 ../../Zotlabs/Module/Webpages.php:74
-#: ../../Zotlabs/Lib/Chatroom.php:137 ../../include/items.php:3438
-#: ../../include/attach.php:141 ../../include/attach.php:189
-#: ../../include/attach.php:252 ../../include/attach.php:266
-#: ../../include/attach.php:273 ../../include/attach.php:338
-#: ../../include/attach.php:352 ../../include/attach.php:359
-#: ../../include/attach.php:437 ../../include/attach.php:895
-#: ../../include/attach.php:966 ../../include/attach.php:1118
-#: ../../include/photos.php:27
-msgid "Permission denied."
-msgstr "Permission refusée."
+#: ../../Zotlabs/Access/PermissionRoles.php:257
+#: ../../include/permissions.php:946
+msgid "Forum - Private"
+msgstr "Forum - privé"
-#: ../../Zotlabs/Web/Router.php:146 ../../Zotlabs/Module/Help.php:94
-msgid "Not Found"
-msgstr "Introuvable"
+#: ../../Zotlabs/Access/PermissionRoles.php:260
+#: ../../include/permissions.php:947
+msgid "Feed Republish"
+msgstr "Republication de flux"
-#: ../../Zotlabs/Web/Router.php:149 ../../Zotlabs/Module/Block.php:79
-#: ../../Zotlabs/Module/Display.php:117 ../../Zotlabs/Module/Help.php:97
-#: ../../Zotlabs/Module/Page.php:93
-msgid "Page not found."
-msgstr "Page introuvable."
+#: ../../Zotlabs/Access/PermissionRoles.php:261
+#: ../../include/permissions.php:947
+msgid "Feed - Mostly Public"
+msgstr "Flux - principalement public"
-#: ../../Zotlabs/Zot/Auth.php:138
-msgid ""
-"Remote authentication blocked. You are logged into this site locally. Please"
-" logout and retry."
-msgstr "Authentification distante bloquée. Vous êtes connecté(e) sur ce site localement. Merci de vous déconnecter et réessayer."
+#: ../../Zotlabs/Access/PermissionRoles.php:262
+#: ../../include/permissions.php:947
+msgid "Feed - Restricted"
+msgstr "Flux - restreint"
-#: ../../Zotlabs/Zot/Auth.php:246 ../../Zotlabs/Module/Openid.php:76
-#: ../../Zotlabs/Module/Openid.php:183
-#, php-format
-msgid "Welcome %s. Remote authentication successful."
-msgstr "Bienvenue %s. L'authentification distante a fonctionné."
+#: ../../Zotlabs/Access/PermissionRoles.php:265
+#: ../../include/permissions.php:948
+msgid "Special Purpose"
+msgstr "Utilisation spécifique"
+
+#: ../../Zotlabs/Access/PermissionRoles.php:266
+#: ../../include/permissions.php:948
+msgid "Special - Celebrity/Soapbox"
+msgstr "Spécial - célébrité/vitrine"
-#: ../../Zotlabs/Module/Achievements.php:15 ../../Zotlabs/Module/Blocks.php:33
-#: ../../Zotlabs/Module/Connect.php:17 ../../Zotlabs/Module/Editblock.php:31
-#: ../../Zotlabs/Module/Editlayout.php:31
-#: ../../Zotlabs/Module/Editwebpage.php:33
-#: ../../Zotlabs/Module/Filestorage.php:60 ../../Zotlabs/Module/Hcard.php:12
-#: ../../Zotlabs/Module/Layouts.php:31 ../../Zotlabs/Module/Profile.php:20
-#: ../../Zotlabs/Module/Webpages.php:34 ../../include/channel.php:837
+#: ../../Zotlabs/Access/PermissionRoles.php:267
+#: ../../include/permissions.php:948
+msgid "Special - Group Repository"
+msgstr "Spécial - dépôt partagé"
+
+#: ../../Zotlabs/Access/PermissionRoles.php:270
+#: ../../Zotlabs/Module/New_channel.php:132
+#: ../../Zotlabs/Module/Settings/Channel.php:463
+#: ../../Zotlabs/Module/Connedit.php:922 ../../Zotlabs/Module/Profiles.php:798
+#: ../../Zotlabs/Module/Register.php:213 ../../addon/cdav/Mod_Cdav.php:1148
+#: ../../addon/cdav/cdav.php:277 ../../addon/cdav/cdav.php:284
+#: ../../include/selectors.php:49 ../../include/selectors.php:66
+#: ../../include/selectors.php:104 ../../include/selectors.php:140
+#: ../../include/permissions.php:949 ../../include/connections.php:675
+#: ../../include/connections.php:682
+msgid "Other"
+msgstr "Autre"
+
+#: ../../Zotlabs/Access/PermissionRoles.php:271
+#: ../../include/permissions.php:949
+msgid "Custom/Expert Mode"
+msgstr "Mode expert/spécifique"
+
+#: ../../Zotlabs/Module/Blocks.php:33 ../../Zotlabs/Module/Editlayout.php:31
+#: ../../Zotlabs/Module/Connect.php:17
+#: ../../Zotlabs/Module/Achievements.php:15 ../../Zotlabs/Module/Hcard.php:12
+#: ../../Zotlabs/Module/Editblock.php:31 ../../Zotlabs/Module/Profile.php:20
+#: ../../Zotlabs/Module/Layouts.php:31 ../../Zotlabs/Module/Editwebpage.php:32
+#: ../../Zotlabs/Module/Webpages.php:33
+#: ../../Zotlabs/Module/Filestorage.php:59 ../../include/channel.php:943
msgid "Requested profile is not available."
msgstr "Profil demandé non disponible."
-#: ../../Zotlabs/Module/Achievements.php:38
-msgid "Some blurb about what to do when you're new here"
-msgstr "Quelques mots sur quoi faire quand on est nouveau ici"
+#: ../../Zotlabs/Module/Blocks.php:73 ../../Zotlabs/Module/Blocks.php:80
+#: ../../Zotlabs/Module/Invite.php:17 ../../Zotlabs/Module/Invite.php:94
+#: ../../Zotlabs/Module/Editlayout.php:67
+#: ../../Zotlabs/Module/Editlayout.php:90 ../../Zotlabs/Module/Channel.php:115
+#: ../../Zotlabs/Module/Channel.php:245 ../../Zotlabs/Module/Channel.php:285
+#: ../../Zotlabs/Module/Settings.php:59 ../../Zotlabs/Module/Locs.php:87
+#: ../../Zotlabs/Module/Mitem.php:115 ../../Zotlabs/Module/Events.php:271
+#: ../../Zotlabs/Module/Appman.php:82 ../../Zotlabs/Module/Regmod.php:21
+#: ../../Zotlabs/Module/New_channel.php:77
+#: ../../Zotlabs/Module/New_channel.php:104
+#: ../../Zotlabs/Module/Sharedwithme.php:11 ../../Zotlabs/Module/Setup.php:212
+#: ../../Zotlabs/Module/Achievements.php:34 ../../Zotlabs/Module/Thing.php:274
+#: ../../Zotlabs/Module/Thing.php:294 ../../Zotlabs/Module/Thing.php:335
+#: ../../Zotlabs/Module/Api.php:24 ../../Zotlabs/Module/Editblock.php:67
+#: ../../Zotlabs/Module/Profile.php:83 ../../Zotlabs/Module/Profile.php:100
+#: ../../Zotlabs/Module/Mood.php:116 ../../Zotlabs/Module/Connections.php:29
+#: ../../Zotlabs/Module/Viewsrc.php:18 ../../Zotlabs/Module/Bookmarks.php:61
+#: ../../Zotlabs/Module/Photos.php:69 ../../Zotlabs/Module/Wiki.php:50
+#: ../../Zotlabs/Module/Wiki.php:216 ../../Zotlabs/Module/Wiki.php:315
+#: ../../Zotlabs/Module/Pdledit.php:29 ../../Zotlabs/Module/Poke.php:137
+#: ../../Zotlabs/Module/Profile_photo.php:280
+#: ../../Zotlabs/Module/Profile_photo.php:293
+#: ../../Zotlabs/Module/Authtest.php:16 ../../Zotlabs/Module/Item.php:220
+#: ../../Zotlabs/Module/Item.php:230 ../../Zotlabs/Module/Item.php:1037
+#: ../../Zotlabs/Module/Page.php:35 ../../Zotlabs/Module/Page.php:91
+#: ../../Zotlabs/Module/Connedit.php:385 ../../Zotlabs/Module/Chat.php:98
+#: ../../Zotlabs/Module/Chat.php:103 ../../Zotlabs/Module/Menu.php:78
+#: ../../Zotlabs/Module/Layouts.php:71 ../../Zotlabs/Module/Layouts.php:78
+#: ../../Zotlabs/Module/Layouts.php:89 ../../Zotlabs/Module/Group.php:13
+#: ../../Zotlabs/Module/Profiles.php:198 ../../Zotlabs/Module/Profiles.php:635
+#: ../../Zotlabs/Module/Editwebpage.php:68
+#: ../../Zotlabs/Module/Editwebpage.php:89
+#: ../../Zotlabs/Module/Editwebpage.php:104
+#: ../../Zotlabs/Module/Editwebpage.php:126 ../../Zotlabs/Module/Manage.php:10
+#: ../../Zotlabs/Module/Webpages.php:116 ../../Zotlabs/Module/Block.php:26
+#: ../../Zotlabs/Module/Block.php:76 ../../Zotlabs/Module/Editpost.php:17
+#: ../../Zotlabs/Module/Sources.php:74 ../../Zotlabs/Module/Like.php:181
+#: ../../Zotlabs/Module/Suggest.php:28 ../../Zotlabs/Module/Message.php:18
+#: ../../Zotlabs/Module/Mail.php:164 ../../Zotlabs/Module/Register.php:77
+#: ../../Zotlabs/Module/Cover_photo.php:281
+#: ../../Zotlabs/Module/Cover_photo.php:294
+#: ../../Zotlabs/Module/Network.php:15 ../../Zotlabs/Module/Filestorage.php:23
+#: ../../Zotlabs/Module/Filestorage.php:78
+#: ../../Zotlabs/Module/Filestorage.php:93
+#: ../../Zotlabs/Module/Filestorage.php:120 ../../Zotlabs/Module/Common.php:39
+#: ../../Zotlabs/Module/Viewconnections.php:28
+#: ../../Zotlabs/Module/Viewconnections.php:33
+#: ../../Zotlabs/Module/Service_limits.php:11
+#: ../../Zotlabs/Module/Rate.php:113 ../../Zotlabs/Module/Notifications.php:11
+#: ../../Zotlabs/Lib/Chatroom.php:137 ../../Zotlabs/Web/WebServer.php:131
+#: ../../addon/keepout/keepout.php:36 ../../addon/openid/Mod_Id.php:53
+#: ../../addon/gitwiki/Mod_Gitwiki.php:196
+#: ../../addon/gitwiki/Mod_Gitwiki.php:292
+#: ../../addon/diaspora_reconnect/diaspora_reconnect.php:58
+#: ../../addon/pumpio/pumpio.php:40 ../../include/attach.php:144
+#: ../../include/attach.php:191 ../../include/attach.php:255
+#: ../../include/attach.php:269 ../../include/attach.php:276
+#: ../../include/attach.php:344 ../../include/attach.php:358
+#: ../../include/attach.php:365 ../../include/attach.php:442
+#: ../../include/attach.php:909 ../../include/attach.php:983
+#: ../../include/attach.php:1148 ../../include/items.php:3457
+#: ../../include/photos.php:27
+msgid "Permission denied."
+msgstr "Permission refusée."
-#: ../../Zotlabs/Module/Blocks.php:97 ../../Zotlabs/Module/Blocks.php:152
-#: ../../Zotlabs/Module/Editblock.php:108
+#: ../../Zotlabs/Module/Blocks.php:97 ../../Zotlabs/Module/Blocks.php:155
+#: ../../Zotlabs/Module/Editblock.php:113
msgid "Block Name"
msgstr "Nom du Bloc"
-#: ../../Zotlabs/Module/Blocks.php:151 ../../include/text.php:2265
+#: ../../Zotlabs/Module/Blocks.php:154 ../../include/text.php:2275
msgid "Blocks"
msgstr "Blocs"
-#: ../../Zotlabs/Module/Blocks.php:153
+#: ../../Zotlabs/Module/Blocks.php:156
msgid "Block Title"
msgstr "Titre du bloc"
-#: ../../Zotlabs/Module/Blocks.php:154 ../../Zotlabs/Module/Layouts.php:188
-#: ../../Zotlabs/Module/Menu.php:114 ../../Zotlabs/Module/Webpages.php:198
-#: ../../include/page_widgets.php:44
+#: ../../Zotlabs/Module/Blocks.php:157 ../../Zotlabs/Module/Menu.php:114
+#: ../../Zotlabs/Module/Layouts.php:191 ../../Zotlabs/Module/Webpages.php:256
+#: ../../include/page_widgets.php:47
msgid "Created"
msgstr "Créé(e)"
-#: ../../Zotlabs/Module/Blocks.php:155 ../../Zotlabs/Module/Layouts.php:189
-#: ../../Zotlabs/Module/Menu.php:115 ../../Zotlabs/Module/Webpages.php:199
-#: ../../include/page_widgets.php:45
+#: ../../Zotlabs/Module/Blocks.php:158 ../../Zotlabs/Module/Menu.php:115
+#: ../../Zotlabs/Module/Layouts.php:192 ../../Zotlabs/Module/Webpages.php:257
+#: ../../include/page_widgets.php:48
msgid "Edited"
msgstr "Modifié(e)"
-#: ../../Zotlabs/Module/Blocks.php:158 ../../Zotlabs/Module/Layouts.php:191
-#: ../../Zotlabs/Module/Photos.php:1072 ../../Zotlabs/Module/Webpages.php:188
-#: ../../include/conversation.php:1208
+#: ../../Zotlabs/Module/Blocks.php:159
+#: ../../Zotlabs/Module/New_channel.php:147
+#: ../../Zotlabs/Module/Connedit.php:925 ../../Zotlabs/Module/Menu.php:118
+#: ../../Zotlabs/Module/Layouts.php:185 ../../Zotlabs/Module/Profiles.php:801
+#: ../../Zotlabs/Module/Webpages.php:244 ../../Zotlabs/Storage/Browser.php:228
+#: ../../Zotlabs/Storage/Browser.php:332 ../../addon/cdav/Mod_Cdav.php:1151
+#: ../../addon/cdav/include/widgets.php:127
+#: ../../addon/cdav/include/widgets.php:164
+msgid "Create"
+msgstr "Créer"
+
+#: ../../Zotlabs/Module/Blocks.php:160 ../../Zotlabs/Module/Editlayout.php:114
+#: ../../Zotlabs/Module/Admin/Profs.php:154
+#: ../../Zotlabs/Module/Settings/Oauth.php:149
+#: ../../Zotlabs/Module/Thing.php:260 ../../Zotlabs/Module/Editblock.php:114
+#: ../../Zotlabs/Module/Connections.php:296
+#: ../../Zotlabs/Module/Connections.php:316 ../../Zotlabs/Module/Wiki.php:165
+#: ../../Zotlabs/Module/Wiki.php:275 ../../Zotlabs/Module/Menu.php:112
+#: ../../Zotlabs/Module/Layouts.php:193
+#: ../../Zotlabs/Module/Editwebpage.php:147
+#: ../../Zotlabs/Module/Webpages.php:245 ../../Zotlabs/Module/Editpost.php:85
+#: ../../Zotlabs/Lib/Apps.php:357 ../../Zotlabs/Lib/ThreadItem.php:107
+#: ../../Zotlabs/Storage/Browser.php:238
+#: ../../addon/cdav/include/widgets.php:125
+#: ../../addon/cdav/include/widgets.php:161
+#: ../../addon/gitwiki/Mod_Gitwiki.php:151
+#: ../../addon/gitwiki/Mod_Gitwiki.php:252 ../../include/channel.php:1042
+#: ../../include/channel.php:1046 ../../include/menu.php:113
+#: ../../include/page_widgets.php:9 ../../include/page_widgets.php:39
+msgid "Edit"
+msgstr "Modifier"
+
+#: ../../Zotlabs/Module/Blocks.php:161 ../../Zotlabs/Module/Photos.php:1042
+#: ../../Zotlabs/Module/Layouts.php:194 ../../Zotlabs/Module/Webpages.php:246
+#: ../../addon/cdav/include/widgets.php:123
+#: ../../include/conversation.php:1311
msgid "Share"
msgstr "Partager"
-#: ../../Zotlabs/Module/Blocks.php:163 ../../Zotlabs/Module/Layouts.php:195
-#: ../../Zotlabs/Module/Pubsites.php:47 ../../Zotlabs/Module/Webpages.php:193
-#: ../../include/page_widgets.php:39
+#: ../../Zotlabs/Module/Blocks.php:162 ../../Zotlabs/Module/Editlayout.php:138
+#: ../../Zotlabs/Module/Admin/Accounts.php:173
+#: ../../Zotlabs/Module/Admin/Channels.php:149
+#: ../../Zotlabs/Module/Admin/Profs.php:155
+#: ../../Zotlabs/Module/Settings/Oauth.php:150
+#: ../../Zotlabs/Module/Thing.php:261 ../../Zotlabs/Module/Editblock.php:139
+#: ../../Zotlabs/Module/Connections.php:267
+#: ../../Zotlabs/Module/Photos.php:1143 ../../Zotlabs/Module/Connedit.php:658
+#: ../../Zotlabs/Module/Connedit.php:927 ../../Zotlabs/Module/Group.php:177
+#: ../../Zotlabs/Module/Profiles.php:803
+#: ../../Zotlabs/Module/Editwebpage.php:172
+#: ../../Zotlabs/Module/Webpages.php:247 ../../Zotlabs/Lib/Apps.php:358
+#: ../../Zotlabs/Lib/ThreadItem.php:127 ../../Zotlabs/Storage/Browser.php:239
+#: ../../addon/cdav/Mod_Cdav.php:864 ../../addon/cdav/Mod_Cdav.php:1153
+#: ../../include/conversation.php:654
+msgid "Delete"
+msgstr "Supprimer"
+
+#: ../../Zotlabs/Module/Blocks.php:166 ../../Zotlabs/Module/Events.php:694
+#: ../../Zotlabs/Module/Wiki.php:167 ../../Zotlabs/Module/Layouts.php:198
+#: ../../Zotlabs/Module/Webpages.php:251 ../../Zotlabs/Module/Pubsites.php:59
+#: ../../addon/gitwiki/Mod_Gitwiki.php:153 ../../include/page_widgets.php:42
msgid "View"
msgstr "Voir"
-#: ../../Zotlabs/Module/Cal.php:62 ../../Zotlabs/Module/Block.php:43
-#: ../../Zotlabs/Module/Page.php:56 ../../Zotlabs/Module/Wall_upload.php:33
-msgid "Channel not found."
-msgstr "Canal introuvable."
+#: ../../Zotlabs/Module/Invite.php:29
+msgid "Total invitation limit exceeded."
+msgstr "Limite du nombre total d'invitation dépassée."
-#: ../../Zotlabs/Module/Cal.php:69
-msgid "Permissions denied."
-msgstr "Permissions refusées."
+#: ../../Zotlabs/Module/Invite.php:53
+#, php-format
+msgid "%s : Not a valid email address."
+msgstr "%s&nbsp;: adresse courriel invalide."
+
+#: ../../Zotlabs/Module/Invite.php:67
+msgid "Please join us on $Projectname"
+msgstr "Rejoignez-nous sur $Projectname"
+
+#: ../../Zotlabs/Module/Invite.php:77
+msgid "Invitation limit exceeded. Please contact your site administrator."
+msgstr "Limite d'invitations dépassée. Merci de contacter l'administration de votre site."
+
+#: ../../Zotlabs/Module/Invite.php:82
+#, php-format
+msgid "%s : Message delivery failed."
+msgstr "%s&nbsp;: Échec de distribution du message."
+
+#: ../../Zotlabs/Module/Invite.php:86
+#, php-format
+msgid "%d message sent."
+msgid_plural "%d messages sent."
+msgstr[0] "%d message envoyé."
+msgstr[1] "%d messages envoyés."
+
+#: ../../Zotlabs/Module/Invite.php:105
+msgid "You have no more invitations available"
+msgstr "Vous ne disposez plus d'aucune invitation"
+
+#: ../../Zotlabs/Module/Invite.php:136
+msgid "Send invitations"
+msgstr "Envoyer des invitations"
+
+#: ../../Zotlabs/Module/Invite.php:137
+msgid "Enter email addresses, one per line:"
+msgstr "Entrez les adresses de courriel, une par ligne&nbsp;:"
+
+#: ../../Zotlabs/Module/Invite.php:138 ../../Zotlabs/Module/Mail.php:284
+msgid "Your message:"
+msgstr "Votre message&nbsp;:"
+
+#: ../../Zotlabs/Module/Invite.php:139
+msgid "Please join my community on $Projectname."
+msgstr "Rejoignez ma communauté sur $Projectname."
+
+#: ../../Zotlabs/Module/Invite.php:141
+msgid "You will need to supply this invitation code:"
+msgstr "Vous devrez fournir le code suivant&nbsp;:"
+
+#: ../../Zotlabs/Module/Invite.php:142
+msgid ""
+"1. Register at any $Projectname location (they are all inter-connected)"
+msgstr "1. Enregistrez-vous sur n'importe quel serveur $Projectname (ils sont tous inter-connectés)"
+
+#: ../../Zotlabs/Module/Invite.php:144
+msgid "2. Enter my $Projectname network address into the site searchbar."
+msgstr "2. Saisissez l'adresse de mon canal $Projectname dans la barre de recherche du site."
+
+#: ../../Zotlabs/Module/Invite.php:145
+msgid "or visit"
+msgstr "ou rendez-vous sur"
+
+#: ../../Zotlabs/Module/Invite.php:147
+msgid "3. Click [Connect]"
+msgstr "3. Cliquez sur [Ajouter]"
+
+#: ../../Zotlabs/Module/Invite.php:149 ../../Zotlabs/Module/Locs.php:121
+#: ../../Zotlabs/Module/Mitem.php:243 ../../Zotlabs/Module/Events.php:493
+#: ../../Zotlabs/Module/Appman.php:134
+#: ../../Zotlabs/Module/Import_items.php:126
+#: ../../Zotlabs/Module/Setup.php:309 ../../Zotlabs/Module/Setup.php:357
+#: ../../Zotlabs/Module/Connect.php:98
+#: ../../Zotlabs/Module/Admin/Features.php:66
+#: ../../Zotlabs/Module/Admin/Plugins.php:438
+#: ../../Zotlabs/Module/Admin/Accounts.php:166
+#: ../../Zotlabs/Module/Admin/Logs.php:84
+#: ../../Zotlabs/Module/Admin/Channels.php:147
+#: ../../Zotlabs/Module/Admin/Themes.php:158
+#: ../../Zotlabs/Module/Admin/Site.php:279
+#: ../../Zotlabs/Module/Admin/Profs.php:157
+#: ../../Zotlabs/Module/Admin/Account_edit.php:74
+#: ../../Zotlabs/Module/Admin/Security.php:104
+#: ../../Zotlabs/Module/Settings/Permcats.php:110
+#: ../../Zotlabs/Module/Settings/Channel.php:476
+#: ../../Zotlabs/Module/Settings/Features.php:47
+#: ../../Zotlabs/Module/Settings/Tokens.php:168
+#: ../../Zotlabs/Module/Settings/Account.php:118
+#: ../../Zotlabs/Module/Settings/Featured.php:50
+#: ../../Zotlabs/Module/Settings/Display.php:203
+#: ../../Zotlabs/Module/Settings/Oauth.php:87
+#: ../../Zotlabs/Module/Thing.php:320 ../../Zotlabs/Module/Thing.php:370
+#: ../../Zotlabs/Module/Import.php:511 ../../Zotlabs/Module/Cal.php:343
+#: ../../Zotlabs/Module/Mood.php:139 ../../Zotlabs/Module/Photos.php:657
+#: ../../Zotlabs/Module/Photos.php:1022 ../../Zotlabs/Module/Photos.php:1062
+#: ../../Zotlabs/Module/Photos.php:1180 ../../Zotlabs/Module/Wiki.php:169
+#: ../../Zotlabs/Module/Pdledit.php:74 ../../Zotlabs/Module/Poke.php:186
+#: ../../Zotlabs/Module/Connedit.php:890 ../../Zotlabs/Module/Chat.php:194
+#: ../../Zotlabs/Module/Chat.php:240 ../../Zotlabs/Module/Pconfig.php:107
+#: ../../Zotlabs/Module/Group.php:85 ../../Zotlabs/Module/Profiles.php:726
+#: ../../Zotlabs/Module/Sources.php:114 ../../Zotlabs/Module/Sources.php:149
+#: ../../Zotlabs/Module/Xchan.php:15 ../../Zotlabs/Module/Mail.php:425
+#: ../../Zotlabs/Module/Filestorage.php:165 ../../Zotlabs/Module/Rate.php:166
+#: ../../Zotlabs/Lib/ThreadItem.php:732
+#: ../../Zotlabs/Widget/Eventstools.php:16
+#: ../../view/theme/redbasic/php/config.php:84
+#: ../../addon/skeleton/skeleton.php:65 ../../addon/gnusoc/gnusoc.php:133
+#: ../../addon/cdav/cdav.php:246 ../../addon/planets/planets.php:157
+#: ../../addon/openclipatar/openclipatar.php:53
+#: ../../addon/wppost/wppost.php:113 ../../addon/nsfw/nsfw.php:92
+#: ../../addon/ijpost/ijpost.php:89 ../../addon/dwpost/dwpost.php:89
+#: ../../addon/mailhost/mailhost.php:40
+#: ../../addon/likebanner/likebanner.php:57
+#: ../../addon/redphotos/redphotos.php:136 ../../addon/irc/irc.php:53
+#: ../../addon/ljpost/ljpost.php:86 ../../addon/startpage/startpage.php:113
+#: ../../addon/diaspora/diaspora.php:714
+#: ../../addon/gitwiki/Mod_Gitwiki.php:155
+#: ../../addon/rainbowtag/rainbowtag.php:85 ../../addon/visage/visage.php:170
+#: ../../addon/nsabait/nsabait.php:161 ../../addon/mailtest/mailtest.php:100
+#: ../../addon/openstreetmap/openstreetmap.php:168
+#: ../../addon/rtof/rtof.php:101 ../../addon/jappixmini/jappixmini.php:371
+#: ../../addon/superblock/superblock.php:120 ../../addon/nofed/nofed.php:80
+#: ../../addon/redred/redred.php:119 ../../addon/logrot/logrot.php:35
+#: ../../addon/frphotos/frphotos.php:96 ../../addon/chords/Mod_Chords.php:60
+#: ../../addon/libertree/libertree.php:85
+#: ../../addon/flattrwidget/flattrwidget.php:124
+#: ../../addon/statusnet/statusnet.php:322
+#: ../../addon/statusnet/statusnet.php:380
+#: ../../addon/statusnet/statusnet.php:432
+#: ../../addon/statusnet/statusnet.php:899 ../../addon/twitter/twitter.php:217
+#: ../../addon/twitter/twitter.php:259
+#: ../../addon/smileybutton/smileybutton.php:281
+#: ../../addon/piwik/piwik.php:95 ../../addon/pageheader/pageheader.php:48
+#: ../../addon/xmpp/xmpp.php:69 ../../addon/pumpio/pumpio.php:237
+#: ../../addon/redfiles/redfiles.php:124 ../../addon/hubwall/hubwall.php:95
+#: ../../include/js_strings.php:22
+msgid "Submit"
+msgstr "Envoyer"
+
+#: ../../Zotlabs/Module/Editlayout.php:79
+#: ../../Zotlabs/Module/Editblock.php:79 ../../Zotlabs/Module/Editblock.php:95
+#: ../../Zotlabs/Module/Editwebpage.php:80
+#: ../../Zotlabs/Module/Editpost.php:24
+msgid "Item not found"
+msgstr "Élément introuvable"
+
+#: ../../Zotlabs/Module/Editlayout.php:128
+#: ../../Zotlabs/Module/Layouts.php:129 ../../Zotlabs/Module/Layouts.php:189
+msgid "Layout Name"
+msgstr "Nom de la mise en page"
+
+#: ../../Zotlabs/Module/Editlayout.php:129
+#: ../../Zotlabs/Module/Layouts.php:132
+msgid "Layout Description (Optional)"
+msgstr "Description de la mise en page (facultatif)"
+
+#: ../../Zotlabs/Module/Editlayout.php:137
+msgid "Edit Layout"
+msgstr "Modifier la mise en page"
+
+#: ../../Zotlabs/Module/Profperm.php:28 ../../Zotlabs/Module/Subthread.php:62
+#: ../../Zotlabs/Module/Import_items.php:118 ../../Zotlabs/Module/Group.php:72
+#: ../../Zotlabs/Module/Dreport.php:10 ../../Zotlabs/Module/Dreport.php:68
+#: ../../Zotlabs/Module/Like.php:283 ../../Zotlabs/Web/WebServer.php:130
+#: ../../addon/redphotos/redphotos.php:119
+#: ../../addon/frphotos/frphotos.php:81 ../../addon/redfiles/redfiles.php:109
+#: ../../include/items.php:327
+msgid "Permission denied"
+msgstr "Accès refusé"
+
+#: ../../Zotlabs/Module/Profperm.php:34 ../../Zotlabs/Module/Profperm.php:63
+msgid "Invalid profile identifier."
+msgstr "Identifiant de profil invalide."
+
+#: ../../Zotlabs/Module/Profperm.php:111
+msgid "Profile Visibility Editor"
+msgstr "Éditeur de visibilité de profil"
+
+#: ../../Zotlabs/Module/Profperm.php:113 ../../include/channel.php:1360
+msgid "Profile"
+msgstr "Profil"
+
+#: ../../Zotlabs/Module/Profperm.php:115
+msgid "Click on a contact to add or remove."
+msgstr "Cliquer sur un contact pour l'ajouter ou le retirer."
-#: ../../Zotlabs/Module/Cal.php:259 ../../Zotlabs/Module/Events.php:588
+#: ../../Zotlabs/Module/Profperm.php:124
+msgid "Visible To"
+msgstr "Visible par"
+
+#: ../../Zotlabs/Module/Profperm.php:140
+#: ../../Zotlabs/Module/Connections.php:141
+msgid "All Connections"
+msgstr "Tous les contacts"
+
+#: ../../Zotlabs/Module/Regdir.php:49 ../../Zotlabs/Module/Dirsearch.php:25
+msgid "This site is not a directory server"
+msgstr "Ce site n'est pas un serveur d'annuaire"
+
+#: ../../Zotlabs/Module/Channel.php:32 ../../Zotlabs/Module/Chat.php:25
+#: ../../addon/gitwiki/Mod_Gitwiki.php:28 ../../addon/chess/chess.php:403
+msgid "You must be logged in to see this page."
+msgstr "Vous devez vous connecter pour voir cette page."
+
+#: ../../Zotlabs/Module/Channel.php:47 ../../Zotlabs/Module/Hcard.php:35
+#: ../../Zotlabs/Module/Profile.php:43
+msgid "Posts and comments"
+msgstr "Publications et commentaires"
+
+#: ../../Zotlabs/Module/Channel.php:54 ../../Zotlabs/Module/Hcard.php:42
+#: ../../Zotlabs/Module/Profile.php:50
+msgid "Only posts"
+msgstr "Seulement les publications"
+
+#: ../../Zotlabs/Module/Channel.php:112
+msgid "Insufficient permissions. Request redirected to profile page."
+msgstr "Permissions insuffisantes. Demande redirigée vers la page du profil."
+
+#: ../../Zotlabs/Module/Uexport.php:57 ../../Zotlabs/Module/Uexport.php:58
+msgid "Export Channel"
+msgstr "Exporter le canal"
+
+#: ../../Zotlabs/Module/Uexport.php:59
+msgid ""
+"Export your basic channel information to a file. This acts as a backup of "
+"your connections, permissions, profile and basic data, which can be used to "
+"import your data to a new server hub, but does not contain your content."
+msgstr "Exportez les principales informations de votre canal dans un fichier. Celui-ci pourra servir de sauvegarde de vos contacts, permissions, profils et données de base. Il pourra être importé sur un nouveau hub/serveur, mais n'embarquera pas vos contenus."
+
+#: ../../Zotlabs/Module/Uexport.php:60
+msgid "Export Content"
+msgstr "Exporter le contenu"
+
+#: ../../Zotlabs/Module/Uexport.php:61
+msgid ""
+"Export your channel information and recent content to a JSON backup that can"
+" be restored or imported to another server hub. This backs up all of your "
+"connections, permissions, profile data and several months of posts. This "
+"file may be VERY large. Please be patient - it may take several minutes for"
+" this download to begin."
+msgstr "Exportez les informations du canal et les contenus récents dans un fichier JSON. Celui-ci contiendra toutes vos relations, permissions, profils, et plusieurs mois de publications. Ce fichier peut être TRÈS gros. Armez-vous de patience - plusieurs minutes peuvent s'écouler avant que le téléchargement ne commence."
+
+#: ../../Zotlabs/Module/Uexport.php:63
+msgid "Export your posts from a given year."
+msgstr "Exporter vos publications d'une année en particulier"
+
+#: ../../Zotlabs/Module/Uexport.php:65
+msgid ""
+"You may also export your posts and conversations for a particular year or "
+"month. Adjust the date in your browser location bar to select other dates. "
+"If the export fails (possibly due to memory exhaustion on your server hub), "
+"please try again selecting a more limited date range."
+msgstr "Vous pouvez également exporter vos publications et conversations pour une année ou un mois particulier. Ajustez la date dans la barre de votre navigateur pour sélectionner d'autres dates. Si l'export échoue (possible en cas de pénurie de mémoire sur le serveur de votre hub), essayez à nouveau en sélectionnant un intervalle de dates plus petit."
+
+#: ../../Zotlabs/Module/Uexport.php:66
+#, php-format
+msgid ""
+"To select all posts for a given year, such as this year, visit <a "
+"href=\"%1$s\">%2$s</a>"
+msgstr "Pour sélectionner toutes les publications pour une année donnée, telle que cette année, visitez <a href=\"%1$s\">%2$s</a>"
+
+#: ../../Zotlabs/Module/Uexport.php:67
+#, php-format
+msgid ""
+"To select all posts for a given month, such as January of this year, visit "
+"<a href=\"%1$s\">%2$s</a>"
+msgstr "Pour sélectionner toutes les publications pour un mois donné, par exemple janvier, visitez <a href=\"%1$s\">%2$s</a>"
+
+#: ../../Zotlabs/Module/Uexport.php:68
+#, php-format
+msgid ""
+"These content files may be imported or restored by visiting <a "
+"href=\"%1$s\">%2$s</a> on any site containing your channel. For best results"
+" please import or restore these in date order (oldest first)."
+msgstr "Ces fichiers de contenu peuvent être importés ou restaurés en visitant <a href=\"%1$s\">%2$s</a> sur n'importe quel site hébergeant votre canal. Pour de meilleurs résultats merci de les importer par ordre chronologique (les plus anciens d'abord)."
+
+#: ../../Zotlabs/Module/Search.php:17 ../../Zotlabs/Module/Photos.php:490
+#: ../../Zotlabs/Module/Ratings.php:83 ../../Zotlabs/Module/Directory.php:63
+#: ../../Zotlabs/Module/Display.php:22
+#: ../../Zotlabs/Module/Viewconnections.php:23
+msgid "Public access denied."
+msgstr "Accès public refusé."
+
+#: ../../Zotlabs/Module/Search.php:44 ../../Zotlabs/Module/Connections.php:312
+#: ../../Zotlabs/Lib/Apps.php:237 ../../Zotlabs/Widget/Sitesearch.php:31
+#: ../../include/text.php:1027 ../../include/text.php:1039
+#: ../../include/acl_selectors.php:213 ../../include/nav.php:160
+msgid "Search"
+msgstr "Recherche"
+
+#: ../../Zotlabs/Module/Search.php:224
+#, php-format
+msgid "Items tagged with: %s"
+msgstr "Eléments étiquetés avec&nbsp;: %s"
+
+#: ../../Zotlabs/Module/Search.php:226
+#, php-format
+msgid "Search results for: %s"
+msgstr "Résultats de recherche pour&nbsp;: %s"
+
+#: ../../Zotlabs/Module/Locs.php:25 ../../Zotlabs/Module/Locs.php:54
+msgid "Location not found."
+msgstr "Emplacement introuvable."
+
+#: ../../Zotlabs/Module/Locs.php:62
+msgid "Location lookup failed."
+msgstr "Echec de la recherche de l'emplacement."
+
+#: ../../Zotlabs/Module/Locs.php:66
+msgid ""
+"Please select another location to become primary before removing the primary"
+" location."
+msgstr "Merci de sélectionner un autre emplacement comme nouvel emplacement primaire avant de supprimer l'emplacement primaire actuel."
+
+#: ../../Zotlabs/Module/Locs.php:95
+msgid "Syncing locations"
+msgstr "Synchronisation des emplacements"
+
+#: ../../Zotlabs/Module/Locs.php:105
+msgid "No locations found."
+msgstr "Emplacement(s) introuvable."
+
+#: ../../Zotlabs/Module/Locs.php:116
+msgid "Manage Channel Locations"
+msgstr "Gérer les emplacements des canaux"
+
+#: ../../Zotlabs/Module/Locs.php:117 ../../Zotlabs/Module/Events.php:475
+#: ../../Zotlabs/Module/Profiles.php:509 ../../Zotlabs/Module/Profiles.php:737
+#: ../../Zotlabs/Module/Pubsites.php:51 ../../addon/cdav/Mod_Cdav.php:839
+#: ../../include/js_strings.php:25
+msgid "Location"
+msgstr "Emplacement"
+
+#: ../../Zotlabs/Module/Locs.php:118
+#: ../../Zotlabs/Module/Admin/Channels.php:160
+#: ../../Zotlabs/Module/Connedit.php:917 ../../Zotlabs/Module/Profiles.php:502
+#: ../../Zotlabs/Module/Profiles.php:793 ../../addon/cdav/Mod_Cdav.php:1143
+msgid "Address"
+msgstr "Adresse"
+
+#: ../../Zotlabs/Module/Locs.php:119
+msgid "Primary"
+msgstr "Primaire"
+
+#: ../../Zotlabs/Module/Locs.php:120 ../../Zotlabs/Module/Menu.php:113
+msgid "Drop"
+msgstr "Supprimer"
+
+#: ../../Zotlabs/Module/Locs.php:122
+msgid "Sync Now"
+msgstr "Synchronisez maintenant"
+
+#: ../../Zotlabs/Module/Locs.php:123
+msgid "Please wait several minutes between consecutive operations."
+msgstr "Merci d'attendre plusieurs minutes entre opérations successives."
+
+#: ../../Zotlabs/Module/Locs.php:124
+msgid ""
+"When possible, drop a location by logging into that website/hub and removing"
+" your channel."
+msgstr "Quand c'est possible, abandonnez un emplacement en vous connectant sur le site/hub et en supprimant votre canal."
+
+#: ../../Zotlabs/Module/Locs.php:125
+msgid "Use this form to drop the location if the hub is no longer operating."
+msgstr "Utilisez ce formulaire pour abandonner l'emplacement si le hub n'est plus actif."
+
+#: ../../Zotlabs/Module/Mitem.php:28 ../../Zotlabs/Module/Menu.php:144
+msgid "Menu not found."
+msgstr "Menu introuvable."
+
+#: ../../Zotlabs/Module/Mitem.php:52
+msgid "Unable to create element."
+msgstr "Impossible de créer l'entrée."
+
+#: ../../Zotlabs/Module/Mitem.php:76
+msgid "Unable to update menu element."
+msgstr "Impossible de mettre à jour l'entrée de menu."
+
+#: ../../Zotlabs/Module/Mitem.php:92
+msgid "Unable to add menu element."
+msgstr "Impossible d'ajouter l'entrée de menu."
+
+#: ../../Zotlabs/Module/Mitem.php:120 ../../Zotlabs/Module/Menu.php:166
+#: ../../Zotlabs/Module/Xchan.php:41
+msgid "Not found."
+msgstr "Introuvable."
+
+#: ../../Zotlabs/Module/Mitem.php:153 ../../Zotlabs/Module/Mitem.php:230
+msgid "Menu Item Permissions"
+msgstr "Permissions de l'entrée de menu"
+
+#: ../../Zotlabs/Module/Mitem.php:154 ../../Zotlabs/Module/Mitem.php:231
+#: ../../Zotlabs/Module/Settings/Channel.php:510
+msgid "(click to open/close)"
+msgstr "(cliquer pour ouvrir/fermer)"
+
+#: ../../Zotlabs/Module/Mitem.php:160 ../../Zotlabs/Module/Mitem.php:176
+msgid "Link Name"
+msgstr "Nom du lien"
+
+#: ../../Zotlabs/Module/Mitem.php:161 ../../Zotlabs/Module/Mitem.php:239
+msgid "Link or Submenu Target"
+msgstr "Lien ou sous-menu cible"
+
+#: ../../Zotlabs/Module/Mitem.php:161
+msgid "Enter URL of the link or select a menu name to create a submenu"
+msgstr "Entrez l'URL du lien ou sélectionnez un nom de menu pour créer un sous-menu"
+
+#: ../../Zotlabs/Module/Mitem.php:162 ../../Zotlabs/Module/Mitem.php:240
+msgid "Use magic-auth if available"
+msgstr "Utiliser l'authentification distante, quand disponible"
+
+#: ../../Zotlabs/Module/Mitem.php:162 ../../Zotlabs/Module/Mitem.php:163
+#: ../../Zotlabs/Module/Mitem.php:240 ../../Zotlabs/Module/Mitem.php:241
+#: ../../Zotlabs/Module/Events.php:470 ../../Zotlabs/Module/Events.php:471
+#: ../../Zotlabs/Module/Removeme.php:63
+#: ../../Zotlabs/Module/Admin/Site.php:237
+#: ../../Zotlabs/Module/Settings/Channel.php:294
+#: ../../Zotlabs/Module/Settings/Display.php:103
+#: ../../Zotlabs/Module/Api.php:97 ../../Zotlabs/Module/Photos.php:642
+#: ../../Zotlabs/Module/Wiki.php:180 ../../Zotlabs/Module/Connedit.php:399
+#: ../../Zotlabs/Module/Connedit.php:783 ../../Zotlabs/Module/Menu.php:100
+#: ../../Zotlabs/Module/Menu.php:157 ../../Zotlabs/Module/Profiles.php:681
+#: ../../Zotlabs/Module/Filestorage.php:160
+#: ../../Zotlabs/Module/Filestorage.php:168 ../../boot.php:1635
+#: ../../view/theme/redbasic/php/config.php:89
+#: ../../view/theme/redbasic/php/config.php:104 ../../addon/cdav/cdav.php:234
+#: ../../addon/planets/planets.php:153 ../../addon/wppost/wppost.php:82
+#: ../../addon/wppost/wppost.php:105 ../../addon/wppost/wppost.php:109
+#: ../../addon/nsfw/nsfw.php:84 ../../addon/ijpost/ijpost.php:73
+#: ../../addon/ijpost/ijpost.php:85 ../../addon/dwpost/dwpost.php:73
+#: ../../addon/dwpost/dwpost.php:85 ../../addon/ljpost/ljpost.php:70
+#: ../../addon/ljpost/ljpost.php:82 ../../addon/gitwiki/Mod_Gitwiki.php:166
+#: ../../addon/rainbowtag/rainbowtag.php:81 ../../addon/visage/visage.php:166
+#: ../../addon/nsabait/nsabait.php:157 ../../addon/rtof/rtof.php:81
+#: ../../addon/rtof/rtof.php:85 ../../addon/jappixmini/jappixmini.php:309
+#: ../../addon/jappixmini/jappixmini.php:313
+#: ../../addon/jappixmini/jappixmini.php:343
+#: ../../addon/jappixmini/jappixmini.php:351
+#: ../../addon/jappixmini/jappixmini.php:355
+#: ../../addon/jappixmini/jappixmini.php:359 ../../addon/nofed/nofed.php:72
+#: ../../addon/nofed/nofed.php:76 ../../addon/redred/redred.php:95
+#: ../../addon/redred/redred.php:99 ../../addon/libertree/libertree.php:69
+#: ../../addon/libertree/libertree.php:81
+#: ../../addon/flattrwidget/flattrwidget.php:120
+#: ../../addon/statusnet/statusnet.php:389
+#: ../../addon/statusnet/statusnet.php:411
+#: ../../addon/statusnet/statusnet.php:415
+#: ../../addon/statusnet/statusnet.php:424 ../../addon/twitter/twitter.php:242
+#: ../../addon/twitter/twitter.php:246 ../../addon/twitter/twitter.php:255
+#: ../../addon/smileybutton/smileybutton.php:273
+#: ../../addon/smileybutton/smileybutton.php:277 ../../addon/xmpp/xmpp.php:53
+#: ../../addon/pumpio/pumpio.php:219 ../../addon/pumpio/pumpio.php:223
+#: ../../addon/pumpio/pumpio.php:227 ../../addon/pumpio/pumpio.php:231
+#: ../../include/dir_fns.php:143 ../../include/dir_fns.php:144
+#: ../../include/dir_fns.php:145
+msgid "No"
+msgstr "Non"
+
+#: ../../Zotlabs/Module/Mitem.php:162 ../../Zotlabs/Module/Mitem.php:163
+#: ../../Zotlabs/Module/Mitem.php:240 ../../Zotlabs/Module/Mitem.php:241
+#: ../../Zotlabs/Module/Events.php:470 ../../Zotlabs/Module/Events.php:471
+#: ../../Zotlabs/Module/Removeme.php:63
+#: ../../Zotlabs/Module/Admin/Site.php:239
+#: ../../Zotlabs/Module/Settings/Channel.php:294
+#: ../../Zotlabs/Module/Settings/Display.php:103
+#: ../../Zotlabs/Module/Api.php:96 ../../Zotlabs/Module/Photos.php:642
+#: ../../Zotlabs/Module/Wiki.php:180 ../../Zotlabs/Module/Connedit.php:399
+#: ../../Zotlabs/Module/Menu.php:100 ../../Zotlabs/Module/Menu.php:157
+#: ../../Zotlabs/Module/Profiles.php:681
+#: ../../Zotlabs/Module/Filestorage.php:160
+#: ../../Zotlabs/Module/Filestorage.php:168 ../../boot.php:1635
+#: ../../view/theme/redbasic/php/config.php:89
+#: ../../view/theme/redbasic/php/config.php:104 ../../addon/cdav/cdav.php:234
+#: ../../addon/planets/planets.php:153 ../../addon/wppost/wppost.php:82
+#: ../../addon/wppost/wppost.php:105 ../../addon/wppost/wppost.php:109
+#: ../../addon/nsfw/nsfw.php:84 ../../addon/ijpost/ijpost.php:73
+#: ../../addon/ijpost/ijpost.php:85 ../../addon/dwpost/dwpost.php:73
+#: ../../addon/dwpost/dwpost.php:85 ../../addon/ljpost/ljpost.php:70
+#: ../../addon/ljpost/ljpost.php:82 ../../addon/gitwiki/Mod_Gitwiki.php:166
+#: ../../addon/rainbowtag/rainbowtag.php:81 ../../addon/visage/visage.php:166
+#: ../../addon/nsabait/nsabait.php:157 ../../addon/rtof/rtof.php:81
+#: ../../addon/rtof/rtof.php:85 ../../addon/jappixmini/jappixmini.php:309
+#: ../../addon/jappixmini/jappixmini.php:313
+#: ../../addon/jappixmini/jappixmini.php:343
+#: ../../addon/jappixmini/jappixmini.php:351
+#: ../../addon/jappixmini/jappixmini.php:355
+#: ../../addon/jappixmini/jappixmini.php:359 ../../addon/nofed/nofed.php:72
+#: ../../addon/nofed/nofed.php:76 ../../addon/redred/redred.php:95
+#: ../../addon/redred/redred.php:99 ../../addon/libertree/libertree.php:69
+#: ../../addon/libertree/libertree.php:81
+#: ../../addon/flattrwidget/flattrwidget.php:120
+#: ../../addon/statusnet/statusnet.php:389
+#: ../../addon/statusnet/statusnet.php:411
+#: ../../addon/statusnet/statusnet.php:415
+#: ../../addon/statusnet/statusnet.php:424 ../../addon/twitter/twitter.php:242
+#: ../../addon/twitter/twitter.php:246 ../../addon/twitter/twitter.php:255
+#: ../../addon/smileybutton/smileybutton.php:273
+#: ../../addon/smileybutton/smileybutton.php:277 ../../addon/xmpp/xmpp.php:53
+#: ../../addon/pumpio/pumpio.php:219 ../../addon/pumpio/pumpio.php:223
+#: ../../addon/pumpio/pumpio.php:227 ../../addon/pumpio/pumpio.php:231
+#: ../../include/dir_fns.php:143 ../../include/dir_fns.php:144
+#: ../../include/dir_fns.php:145
+msgid "Yes"
+msgstr "Oui"
+
+#: ../../Zotlabs/Module/Mitem.php:163 ../../Zotlabs/Module/Mitem.php:241
+msgid "Open link in new window"
+msgstr "Ouvrir le lien dans une nouvelle fenêtre"
+
+#: ../../Zotlabs/Module/Mitem.php:164 ../../Zotlabs/Module/Mitem.php:242
+msgid "Order in list"
+msgstr "Ordre dans la liste"
+
+#: ../../Zotlabs/Module/Mitem.php:164 ../../Zotlabs/Module/Mitem.php:242
+msgid "Higher numbers will sink to bottom of listing"
+msgstr "Les nombres les plus élevés seront au bas de la liste"
+
+#: ../../Zotlabs/Module/Mitem.php:165
+msgid "Submit and finish"
+msgstr "Vadiler et terminer"
+
+#: ../../Zotlabs/Module/Mitem.php:166
+msgid "Submit and continue"
+msgstr "Valider et continuer"
+
+#: ../../Zotlabs/Module/Mitem.php:174
+msgid "Menu:"
+msgstr "Menu&nbsp;:"
+
+#: ../../Zotlabs/Module/Mitem.php:177
+msgid "Link Target"
+msgstr "Cible du lien"
+
+#: ../../Zotlabs/Module/Mitem.php:180
+msgid "Edit menu"
+msgstr "Modifier le menu"
+
+#: ../../Zotlabs/Module/Mitem.php:183
+msgid "Edit element"
+msgstr "Modifier l'entrée"
+
+#: ../../Zotlabs/Module/Mitem.php:184
+msgid "Drop element"
+msgstr "Supprimer l'entrée"
+
+#: ../../Zotlabs/Module/Mitem.php:185
+msgid "New element"
+msgstr "Nouvelle entrée"
+
+#: ../../Zotlabs/Module/Mitem.php:186
+msgid "Edit this menu container"
+msgstr "Éditer ce bloc de menu"
+
+#: ../../Zotlabs/Module/Mitem.php:187
+msgid "Add menu element"
+msgstr "Ajouter une entrée au menu"
+
+#: ../../Zotlabs/Module/Mitem.php:188
+msgid "Delete this menu item"
+msgstr "Supprimer cette entrée du menu"
+
+#: ../../Zotlabs/Module/Mitem.php:189
+msgid "Edit this menu item"
+msgstr "Modifier cette entrée du menu"
+
+#: ../../Zotlabs/Module/Mitem.php:206
+msgid "Menu item not found."
+msgstr "Entrée de menu introuvable."
+
+#: ../../Zotlabs/Module/Mitem.php:219
+msgid "Menu item deleted."
+msgstr "Entrée de menu supprimée."
+
+#: ../../Zotlabs/Module/Mitem.php:221
+msgid "Menu item could not be deleted."
+msgstr "Impossible de supprimer l'entrée de menu."
+
+#: ../../Zotlabs/Module/Mitem.php:228
+msgid "Edit Menu Element"
+msgstr "Modifier l'entrée de menu"
+
+#: ../../Zotlabs/Module/Mitem.php:238
+msgid "Link text"
+msgstr "Texte du lien"
+
+#: ../../Zotlabs/Module/Events.php:25
+msgid "Calendar entries imported."
+msgstr "Entrées du calendrier importées."
+
+#: ../../Zotlabs/Module/Events.php:27
+msgid "No calendar entries found."
+msgstr "Aucune entrée du calendrier trouvée."
+
+#: ../../Zotlabs/Module/Events.php:110
+msgid "Event can not end before it has started."
+msgstr "La fin de l'événement ne peut être antérieure à son début."
+
+#: ../../Zotlabs/Module/Events.php:112 ../../Zotlabs/Module/Events.php:121
+#: ../../Zotlabs/Module/Events.php:143
+msgid "Unable to generate preview."
+msgstr "Impossible de générer l'aperçu."
+
+#: ../../Zotlabs/Module/Events.php:119
+msgid "Event title and start time are required."
+msgstr "Un titre et une date de début sont requises pour l'événement."
+
+#: ../../Zotlabs/Module/Events.php:141 ../../Zotlabs/Module/Events.php:265
+msgid "Event not found."
+msgstr "Événement introuvable."
+
+#: ../../Zotlabs/Module/Events.php:260 ../../Zotlabs/Module/Tagger.php:51
+#: ../../Zotlabs/Module/Like.php:372 ../../include/conversation.php:119
+#: ../../include/text.php:1948 ../../include/event.php:1141
+msgid "event"
+msgstr "événement"
+
+#: ../../Zotlabs/Module/Events.php:460
+msgid "Edit event title"
+msgstr "Modifier le titre de l'événement"
+
+#: ../../Zotlabs/Module/Events.php:460 ../../addon/cdav/Mod_Cdav.php:835
+msgid "Event title"
+msgstr "Titre de l'événement"
+
+#: ../../Zotlabs/Module/Events.php:460 ../../Zotlabs/Module/Events.php:465
+#: ../../Zotlabs/Module/Appman.php:122 ../../Zotlabs/Module/Appman.php:123
+#: ../../Zotlabs/Module/Profiles.php:748 ../../Zotlabs/Module/Profiles.php:752
+#: ../../include/datetime.php:259
+msgid "Required"
+msgstr "Requis"
+
+#: ../../Zotlabs/Module/Events.php:462
+msgid "Categories (comma-separated list)"
+msgstr "Catégories (séparées par des virgules)"
+
+#: ../../Zotlabs/Module/Events.php:463
+msgid "Edit Category"
+msgstr "Modifier la catégorie"
+
+#: ../../Zotlabs/Module/Events.php:463
+msgid "Category"
+msgstr "Catégorie"
+
+#: ../../Zotlabs/Module/Events.php:466
+msgid "Edit start date and time"
+msgstr "Modifier la date et l'heure de début"
+
+#: ../../Zotlabs/Module/Events.php:466 ../../addon/cdav/Mod_Cdav.php:836
+msgid "Start date and time"
+msgstr "Date et heure de début"
+
+#: ../../Zotlabs/Module/Events.php:467 ../../Zotlabs/Module/Events.php:470
+msgid "Finish date and time are not known or not relevant"
+msgstr "Date et heure de fin inconnues ou sans objet"
+
+#: ../../Zotlabs/Module/Events.php:469
+msgid "Edit finish date and time"
+msgstr "Modifier la date et l'heure de fin"
+
+#: ../../Zotlabs/Module/Events.php:469
+msgid "Finish date and time"
+msgstr "Date et heure de fin"
+
+#: ../../Zotlabs/Module/Events.php:471 ../../Zotlabs/Module/Events.php:472
+msgid "Adjust for viewer timezone"
+msgstr "Ajuster au fuseau horaire du visiteur"
+
+#: ../../Zotlabs/Module/Events.php:471
+msgid ""
+"Important for events that happen in a particular place. Not practical for "
+"global holidays."
+msgstr "Important pour les événements se tenant en un lieu particulier. Pas pratique pour les vacances communes à de nombreux pays dans le monde."
+
+#: ../../Zotlabs/Module/Events.php:473
+msgid "Edit Description"
+msgstr "Modifier la description"
+
+#: ../../Zotlabs/Module/Events.php:473 ../../Zotlabs/Module/Appman.php:124
+#: ../../Zotlabs/Module/Rbmark.php:101
+#: ../../addon/rendezvous/rendezvous.php:173 ../../addon/cdav/Mod_Cdav.php:838
+msgid "Description"
+msgstr "Description"
+
+#: ../../Zotlabs/Module/Events.php:475
+msgid "Edit Location"
+msgstr "Modifier l'emplacement"
+
+#: ../../Zotlabs/Module/Events.php:478 ../../Zotlabs/Module/Photos.php:1063
+#: ../../Zotlabs/Module/Webpages.php:252 ../../Zotlabs/Lib/ThreadItem.php:741
+#: ../../include/conversation.php:1280 ../../include/page_widgets.php:43
+msgid "Preview"
+msgstr "Aperçu"
+
+#: ../../Zotlabs/Module/Events.php:479 ../../include/conversation.php:1343
+msgid "Permission settings"
+msgstr "Gérer les autorisations"
+
+#: ../../Zotlabs/Module/Events.php:489
+msgid "Timezone:"
+msgstr "Fuseau horaire&nbsp;:"
+
+#: ../../Zotlabs/Module/Events.php:494
+msgid "Advanced Options"
+msgstr "Options avancées"
+
+#: ../../Zotlabs/Module/Events.php:605 ../../Zotlabs/Module/Cal.php:264
msgid "l, F j"
msgstr "l, F j"
-#: ../../Zotlabs/Module/Cal.php:308 ../../Zotlabs/Module/Events.php:637
-#: ../../include/text.php:1732
+#: ../../Zotlabs/Module/Events.php:633
+msgid "Edit event"
+msgstr "Modifier l'événement"
+
+#: ../../Zotlabs/Module/Events.php:635
+msgid "Delete event"
+msgstr "Supprimer l'événement"
+
+#: ../../Zotlabs/Module/Events.php:660 ../../Zotlabs/Module/Cal.php:313
+#: ../../include/text.php:1767
msgid "Link to Source"
msgstr "Lien vers la Source"
-#: ../../Zotlabs/Module/Cal.php:331 ../../Zotlabs/Module/Events.php:665
+#: ../../Zotlabs/Module/Events.php:669
+msgid "calendar"
+msgstr "calendrier"
+
+#: ../../Zotlabs/Module/Events.php:688 ../../Zotlabs/Module/Cal.php:336
msgid "Edit Event"
msgstr "Modifier l'événement"
-#: ../../Zotlabs/Module/Cal.php:331 ../../Zotlabs/Module/Events.php:665
+#: ../../Zotlabs/Module/Events.php:688 ../../Zotlabs/Module/Cal.php:336
msgid "Create Event"
msgstr "Créer un événement"
-#: ../../Zotlabs/Module/Cal.php:332 ../../Zotlabs/Module/Cal.php:339
-#: ../../Zotlabs/Module/Events.php:666 ../../Zotlabs/Module/Events.php:673
-#: ../../Zotlabs/Module/Photos.php:949
+#: ../../Zotlabs/Module/Events.php:689 ../../Zotlabs/Module/Events.php:698
+#: ../../Zotlabs/Module/Cal.php:337 ../../Zotlabs/Module/Cal.php:344
+#: ../../Zotlabs/Module/Photos.php:911 ../../addon/cdav/Mod_Cdav.php:846
msgid "Previous"
msgstr "Précédent"
-#: ../../Zotlabs/Module/Cal.php:333 ../../Zotlabs/Module/Cal.php:340
-#: ../../Zotlabs/Module/Events.php:667 ../../Zotlabs/Module/Events.php:674
-#: ../../Zotlabs/Module/Photos.php:958 ../../Zotlabs/Module/Setup.php:267
+#: ../../Zotlabs/Module/Events.php:690 ../../Zotlabs/Module/Events.php:699
+#: ../../Zotlabs/Module/Setup.php:264 ../../Zotlabs/Module/Cal.php:338
+#: ../../Zotlabs/Module/Cal.php:345 ../../Zotlabs/Module/Photos.php:920
+#: ../../addon/cdav/Mod_Cdav.php:847
msgid "Next"
msgstr "Suivant"
-#: ../../Zotlabs/Module/Cal.php:334 ../../Zotlabs/Module/Events.php:668
-#: ../../include/widgets.php:755
+#: ../../Zotlabs/Module/Events.php:691 ../../Zotlabs/Module/Cal.php:339
+#: ../../include/channel.php:1363
msgid "Export"
msgstr "Export"
-#: ../../Zotlabs/Module/Cal.php:337 ../../Zotlabs/Module/Events.php:671
-#: ../../include/widgets.php:756
-msgid "Import"
-msgstr "Import"
+#: ../../Zotlabs/Module/Events.php:695 ../../addon/cdav/Mod_Cdav.php:849
+msgid "Month"
+msgstr "Mois"
-#: ../../Zotlabs/Module/Cal.php:338 ../../Zotlabs/Module/Chat.php:196
-#: ../../Zotlabs/Module/Chat.php:238 ../../Zotlabs/Module/Connect.php:98
-#: ../../Zotlabs/Module/Connedit.php:731 ../../Zotlabs/Module/Events.php:475
-#: ../../Zotlabs/Module/Events.php:672 ../../Zotlabs/Module/Group.php:85
-#: ../../Zotlabs/Module/Filestorage.php:162
-#: ../../Zotlabs/Module/Import.php:550
-#: ../../Zotlabs/Module/Import_items.php:120
-#: ../../Zotlabs/Module/Invite.php:146 ../../Zotlabs/Module/Locs.php:121
-#: ../../Zotlabs/Module/Mail.php:378 ../../Zotlabs/Module/Mood.php:139
-#: ../../Zotlabs/Module/Mitem.php:235 ../../Zotlabs/Module/Photos.php:677
-#: ../../Zotlabs/Module/Photos.php:1052 ../../Zotlabs/Module/Photos.php:1092
-#: ../../Zotlabs/Module/Photos.php:1210 ../../Zotlabs/Module/Pconfig.php:107
-#: ../../Zotlabs/Module/Pdledit.php:66 ../../Zotlabs/Module/Poke.php:186
-#: ../../Zotlabs/Module/Profiles.php:687 ../../Zotlabs/Module/Rate.php:170
-#: ../../Zotlabs/Module/Admin.php:492 ../../Zotlabs/Module/Admin.php:688
-#: ../../Zotlabs/Module/Admin.php:771 ../../Zotlabs/Module/Admin.php:1032
-#: ../../Zotlabs/Module/Admin.php:1211 ../../Zotlabs/Module/Admin.php:1421
-#: ../../Zotlabs/Module/Admin.php:1648 ../../Zotlabs/Module/Admin.php:1733
-#: ../../Zotlabs/Module/Admin.php:2116 ../../Zotlabs/Module/Appman.php:126
-#: ../../Zotlabs/Module/Settings.php:590 ../../Zotlabs/Module/Settings.php:703
-#: ../../Zotlabs/Module/Settings.php:731 ../../Zotlabs/Module/Settings.php:754
-#: ../../Zotlabs/Module/Settings.php:842
-#: ../../Zotlabs/Module/Settings.php:1034 ../../Zotlabs/Module/Setup.php:312
-#: ../../Zotlabs/Module/Setup.php:353 ../../Zotlabs/Module/Sources.php:114
-#: ../../Zotlabs/Module/Sources.php:149 ../../Zotlabs/Module/Thing.php:316
-#: ../../Zotlabs/Module/Thing.php:362 ../../Zotlabs/Module/Xchan.php:15
-#: ../../Zotlabs/Lib/ThreadItem.php:710 ../../include/widgets.php:757
-#: ../../include/widgets.php:769 ../../include/js_strings.php:22
-#: ../../view/theme/redbasic/php/config.php:99
-msgid "Submit"
-msgstr "Envoyer"
+#: ../../Zotlabs/Module/Events.php:696 ../../addon/cdav/Mod_Cdav.php:850
+msgid "Week"
+msgstr "Semaine"
-#: ../../Zotlabs/Module/Cal.php:341 ../../Zotlabs/Module/Events.php:675
+#: ../../Zotlabs/Module/Events.php:697 ../../addon/cdav/Mod_Cdav.php:851
+msgid "Day"
+msgstr "Jour"
+
+#: ../../Zotlabs/Module/Events.php:700 ../../Zotlabs/Module/Cal.php:346
+#: ../../addon/cdav/Mod_Cdav.php:848
msgid "Today"
msgstr "Aujourd'hui"
-#: ../../Zotlabs/Module/Channel.php:29 ../../Zotlabs/Module/Chat.php:25
-msgid "You must be logged in to see this page."
-msgstr "Vous devez vous connecter pour voir cette page."
+#: ../../Zotlabs/Module/Events.php:731
+msgid "Event removed"
+msgstr "Événement supprimé"
-#: ../../Zotlabs/Module/Channel.php:41
-msgid "Posts and comments"
-msgstr ""
+#: ../../Zotlabs/Module/Events.php:734
+msgid "Failed to remove event"
+msgstr "Impossible de supprimer l'événement"
-#: ../../Zotlabs/Module/Channel.php:42
-msgid "Only posts"
-msgstr ""
+#: ../../Zotlabs/Module/Appman.php:38 ../../Zotlabs/Module/Appman.php:55
+msgid "App installed."
+msgstr "Application installée."
-#: ../../Zotlabs/Module/Channel.php:102
-msgid "Insufficient permissions. Request redirected to profile page."
-msgstr "Permissions insuffisantes. Demande redirigée vers la page du profil."
+#: ../../Zotlabs/Module/Appman.php:48
+msgid "Malformed app."
+msgstr "Erreur de l'application - Malformée."
-#: ../../Zotlabs/Module/Chat.php:181
-msgid "Room not found"
-msgstr "Salon introuvable"
+#: ../../Zotlabs/Module/Appman.php:111
+msgid "Embed code"
+msgstr "Imbriquer le code"
-#: ../../Zotlabs/Module/Chat.php:197
-msgid "Leave Room"
-msgstr "Quitter le salon"
+#: ../../Zotlabs/Module/Appman.php:117
+msgid "Edit App"
+msgstr "Modifier l'application"
-#: ../../Zotlabs/Module/Chat.php:198
-msgid "Delete Room"
-msgstr ""
+#: ../../Zotlabs/Module/Appman.php:117
+msgid "Create App"
+msgstr "Créer une application"
-#: ../../Zotlabs/Module/Chat.php:199
-msgid "I am away right now"
-msgstr "Je suis absent en ce moment"
+#: ../../Zotlabs/Module/Appman.php:122
+msgid "Name of app"
+msgstr "Nom de l'application"
-#: ../../Zotlabs/Module/Chat.php:200
-msgid "I am online"
-msgstr "Je suis en ligne"
+#: ../../Zotlabs/Module/Appman.php:123
+msgid "Location (URL) of app"
+msgstr "Emplacement (URL) de l'application"
-#: ../../Zotlabs/Module/Chat.php:202
-msgid "Bookmark this room"
-msgstr "Marquer ce salon comme favori"
+#: ../../Zotlabs/Module/Appman.php:125
+msgid "Photo icon URL"
+msgstr "URL de l'icône à utiliser pour cette photo"
-#: ../../Zotlabs/Module/Chat.php:205 ../../Zotlabs/Module/Mail.php:205
-#: ../../Zotlabs/Module/Mail.php:314 ../../include/conversation.php:1176
-msgid "Please enter a link URL:"
-msgstr "Merci d'entrer l'URL d'un lien&nbsp;:"
+#: ../../Zotlabs/Module/Appman.php:125
+msgid "80 x 80 pixels - optional"
+msgstr "80 x 80 pixels - facultatif"
-#: ../../Zotlabs/Module/Chat.php:206 ../../Zotlabs/Module/Mail.php:258
-#: ../../Zotlabs/Module/Mail.php:383 ../../Zotlabs/Lib/ThreadItem.php:722
-#: ../../include/conversation.php:1256
-msgid "Encrypt text"
-msgstr "Chiffrer le texte"
+#: ../../Zotlabs/Module/Appman.php:126
+msgid "Categories (optional, comma separated list)"
+msgstr "Catégories (séparées par des virgules)"
-#: ../../Zotlabs/Module/Chat.php:207 ../../Zotlabs/Module/Editblock.php:111
-#: ../../Zotlabs/Module/Editwebpage.php:147 ../../Zotlabs/Module/Mail.php:252
-#: ../../Zotlabs/Module/Mail.php:377 ../../include/conversation.php:1143
-msgid "Insert web link"
-msgstr "Insérer lien web"
+#: ../../Zotlabs/Module/Appman.php:127
+msgid "Version ID"
+msgstr "Identifiant de version"
-#: ../../Zotlabs/Module/Chat.php:218
-msgid "Feature disabled."
-msgstr ""
+#: ../../Zotlabs/Module/Appman.php:128
+msgid "Price of app"
+msgstr "Prix de l'application"
-#: ../../Zotlabs/Module/Chat.php:232
-msgid "New Chatroom"
-msgstr "Nouveau salon de discussion"
+#: ../../Zotlabs/Module/Appman.php:129
+msgid "Location (URL) to purchase app"
+msgstr "Emplacement (URL) pour l'achat de l'application"
-#: ../../Zotlabs/Module/Chat.php:233
-msgid "Chatroom name"
-msgstr ""
+#: ../../Zotlabs/Module/Regmod.php:15
+msgid "Please login."
+msgstr "Merci de vous connecter."
-#: ../../Zotlabs/Module/Chat.php:234
-msgid "Expiration of chats (minutes)"
-msgstr "Expiration des discussions (en minutes)"
+#: ../../Zotlabs/Module/Magic.php:71
+msgid "Hub not found."
+msgstr "Hub introuvable."
-#: ../../Zotlabs/Module/Chat.php:235 ../../Zotlabs/Module/Filestorage.php:153
-#: ../../Zotlabs/Module/Photos.php:671 ../../Zotlabs/Module/Photos.php:1045
-#: ../../Zotlabs/Module/Thing.php:313 ../../Zotlabs/Module/Thing.php:359
-#: ../../include/acl_selectors.php:283
-msgid "Permissions"
-msgstr "Autorisations"
+#: ../../Zotlabs/Module/Subthread.php:87 ../../Zotlabs/Module/Tagger.php:47
+#: ../../Zotlabs/Module/Like.php:370
+#: ../../addon/redphotos/redphotohelper.php:74
+#: ../../addon/diaspora/inbound.php:1794 ../../include/conversation.php:116
+#: ../../include/text.php:1945
+msgid "photo"
+msgstr "photo"
-#: ../../Zotlabs/Module/Chat.php:246
+#: ../../Zotlabs/Module/Subthread.php:87 ../../Zotlabs/Module/Like.php:370
+#: ../../addon/diaspora/inbound.php:1794 ../../include/conversation.php:144
+#: ../../include/text.php:1951
+msgid "status"
+msgstr "état"
+
+#: ../../Zotlabs/Module/Subthread.php:118
#, php-format
-msgid "%1$s's Chatrooms"
-msgstr "Salons de %1$s"
+msgid "%1$s is following %2$s's %3$s"
+msgstr "%1$s suit %3$s de %2$s"
-#: ../../Zotlabs/Module/Chat.php:251
-msgid "No chatrooms available"
-msgstr ""
+#: ../../Zotlabs/Module/Subthread.php:120
+#, php-format
+msgid "%1$s stopped following %2$s's %3$s"
+msgstr "%1$s ne suit plus %3$s de %2$s"
-#: ../../Zotlabs/Module/Chat.php:252 ../../Zotlabs/Module/Manage.php:143
-#: ../../Zotlabs/Module/Profiles.php:778
-msgid "Create New"
-msgstr ""
+#: ../../Zotlabs/Module/Import_items.php:46 ../../Zotlabs/Module/Import.php:64
+msgid "Nothing to import."
+msgstr "Rien à importer."
-#: ../../Zotlabs/Module/Chat.php:255
-msgid "Expiration"
-msgstr ""
+#: ../../Zotlabs/Module/Import_items.php:70 ../../Zotlabs/Module/Import.php:79
+#: ../../Zotlabs/Module/Import.php:95
+msgid "Unable to download data from old server"
+msgstr "Impossible de récupérer les données de l'ancien serveur"
-#: ../../Zotlabs/Module/Chat.php:256
-msgid "min"
-msgstr ""
+#: ../../Zotlabs/Module/Import_items.php:75
+#: ../../Zotlabs/Module/Import.php:102
+msgid "Imported file is empty."
+msgstr "Le fichier importé est vide."
-#: ../../Zotlabs/Module/Chatsvc.php:117
-msgid "Away"
-msgstr "Absent"
+#: ../../Zotlabs/Module/Import_items.php:91
+#: ../../Zotlabs/Module/Import.php:121
+#, php-format
+msgid "Warning: Database versions differ by %1$d updates."
+msgstr "Attention&nbsp;: les versions de bases de données diffèrent de %1$d mises à jour."
-#: ../../Zotlabs/Module/Chatsvc.php:122
-msgid "Online"
-msgstr "En ligne"
+#: ../../Zotlabs/Module/Import_items.php:106
+msgid "Import completed"
+msgstr "L'import est terminé."
-#: ../../Zotlabs/Module/Block.php:31 ../../Zotlabs/Module/Page.php:40
-msgid "Invalid item."
-msgstr "Élément invalide."
+#: ../../Zotlabs/Module/Import_items.php:123
+msgid "Import Items"
+msgstr "Importer"
-#: ../../Zotlabs/Module/Bookmarks.php:53
-msgid "Bookmark added"
-msgstr "Favori ajouté"
+#: ../../Zotlabs/Module/Import_items.php:124
+msgid ""
+"Use this form to import existing posts and content from an export file."
+msgstr "Utiliser ce formulaire pour importer des publications et du contenu existant d'un fichier d'export."
-#: ../../Zotlabs/Module/Bookmarks.php:75
-msgid "My Bookmarks"
-msgstr "Mes Favoris"
+#: ../../Zotlabs/Module/Import_items.php:125
+#: ../../Zotlabs/Module/Import.php:499
+msgid "File to Upload"
+msgstr "Fichier à envoyer"
-#: ../../Zotlabs/Module/Bookmarks.php:86
-msgid "My Connections Bookmarks"
-msgstr "Favoris de mes contacts"
+#: ../../Zotlabs/Module/New_channel.php:121
+#: ../../Zotlabs/Module/Manage.php:136
+#, php-format
+msgid "You have created %1$.0f of %2$.0f allowed channels."
+msgstr "Vous avez créé %1$.0f des %2$.0f canaux autorisés."
+
+#: ../../Zotlabs/Module/New_channel.php:134
+#: ../../Zotlabs/Module/Register.php:237
+msgid "Name or caption"
+msgstr "Nom ou libellé"
+
+#: ../../Zotlabs/Module/New_channel.php:134
+#: ../../Zotlabs/Module/Register.php:237
+msgid "Examples: \"Bob Jameson\", \"Lisa and her Horses\", \"Soccer\", \"Aviation Group\""
+msgstr "Exemples&nbsp;: \"Jérôme Dutilleul\", \"Louise et ses chevaux\", \"Football\", \"Club d'aéromodélisme\""
+
+#: ../../Zotlabs/Module/New_channel.php:136
+#: ../../Zotlabs/Module/Register.php:239
+msgid "Choose a short nickname"
+msgstr "Choisissez un alias"
+
+#: ../../Zotlabs/Module/New_channel.php:136
+#: ../../Zotlabs/Module/Register.php:239
+#, php-format
+msgid ""
+"Your nickname will be used to create an easy to remember channel address "
+"e.g. nickname%s"
+msgstr "Votre pseudo sera utilisé pour créer une adresse de canal facile à mémoriser, par ex. pseudo%s"
+
+#: ../../Zotlabs/Module/New_channel.php:137
+#: ../../Zotlabs/Module/Register.php:240
+msgid "Channel role and privacy"
+msgstr "Rôle et confidentialité du canal"
+
+#: ../../Zotlabs/Module/New_channel.php:137
+#: ../../Zotlabs/Module/Register.php:240
+msgid "Select a channel role with your privacy requirements."
+msgstr "Sélectionner un rôle de canal adapté à vos besoins de confidentialité."
+
+#: ../../Zotlabs/Module/New_channel.php:137
+#: ../../Zotlabs/Module/Register.php:240
+msgid "Read more about roles"
+msgstr "En savoir plus sur les rôles"
+
+#: ../../Zotlabs/Module/New_channel.php:140
+msgid "Create Channel"
+msgstr "Créer le canal"
+
+#: ../../Zotlabs/Module/New_channel.php:141
+msgid ""
+"A channel is your identity on this network. It can represent a person, a "
+"blog, or a forum to name a few. Channels can make connections with other "
+"channels to share information with highly detailed permissions."
+msgstr "Un canal est votre identité sur ce réseau. Il peut représenter une personne, un blog, ou un forum par exemple. Les canaux peuvent entrer en contact les uns avec les autres pour partager des informations avec des permissions d'accès très fines."
+
+#: ../../Zotlabs/Module/New_channel.php:142
+msgid ""
+"or <a href=\"import\">import an existing channel</a> from another location."
+msgstr "ou <a href=\"import\">importer un canal existant</a> d'un autre serveur."
+
+#: ../../Zotlabs/Module/Removeme.php:35
+msgid ""
+"Channel removals are not allowed within 48 hours of changing the account "
+"password."
+msgstr "Il est impossible de supprimer un canal moins de 48 heures après avoir changé le mot de passe d'un compte."
+
+#: ../../Zotlabs/Module/Removeme.php:60
+msgid "Remove This Channel"
+msgstr "Supprimer ce canal"
+
+#: ../../Zotlabs/Module/Removeme.php:61
+#: ../../Zotlabs/Module/Removeaccount.php:58
+msgid "WARNING: "
+msgstr "AVERTISSEMENT&nbsp;:"
+
+#: ../../Zotlabs/Module/Removeme.php:61
+msgid "This channel will be completely removed from the network. "
+msgstr "Ce canal sera complètement supprimé du réseau."
+
+#: ../../Zotlabs/Module/Removeme.php:61
+#: ../../Zotlabs/Module/Removeaccount.php:58
+msgid "This action is permanent and can not be undone!"
+msgstr "Cette action est permanente et irréversible&nbsp;!"
+
+#: ../../Zotlabs/Module/Removeme.php:62
+#: ../../Zotlabs/Module/Removeaccount.php:59
+msgid "Please enter your password for verification:"
+msgstr "Merci de saisir votre mot de passe pour vérification&nbsp;:"
+
+#: ../../Zotlabs/Module/Removeme.php:63
+msgid "Remove this channel and all its clones from the network"
+msgstr "Supprimer ce canal ainsi que tous ses clones sur le réseau"
+
+#: ../../Zotlabs/Module/Removeme.php:63
+msgid ""
+"By default only the instance of the channel located on this hub will be "
+"removed from the network"
+msgstr "Par défaut, seule l'instance du canal présente sur ce hub sera supprimée du réseau"
+
+#: ../../Zotlabs/Module/Removeme.php:64
+#: ../../Zotlabs/Module/Settings/Channel.php:575
+msgid "Remove Channel"
+msgstr "Supprimer le canal"
+
+#: ../../Zotlabs/Module/Sharedwithme.php:99
+msgid "Files: shared with me"
+msgstr "Fichiers&nbsp;: partagés avec moi"
+
+#: ../../Zotlabs/Module/Sharedwithme.php:100
+#: ../../Zotlabs/Module/Admin/Channels.php:159
+#: ../../Zotlabs/Module/Settings/Oauth.php:89
+#: ../../Zotlabs/Module/Settings/Oauth.php:115
+#: ../../Zotlabs/Module/Wiki.php:172 ../../Zotlabs/Module/Connedit.php:910
+#: ../../Zotlabs/Module/Chat.php:249 ../../Zotlabs/Lib/NativeWikiPage.php:528
+#: ../../Zotlabs/Storage/Browser.php:233
+#: ../../Zotlabs/Widget/Wiki_page_history.php:22
+#: ../../addon/rendezvous/rendezvous.php:172
+#: ../../addon/cdav/Mod_Cdav.php:1136 ../../addon/gitwiki/Mod_Gitwiki.php:158
+msgid "Name"
+msgstr "Nom"
+
+#: ../../Zotlabs/Module/Sharedwithme.php:101
+msgid "NEW"
+msgstr "NOUVEAU"
+
+#: ../../Zotlabs/Module/Sharedwithme.php:102
+#: ../../Zotlabs/Storage/Browser.php:235 ../../include/text.php:1417
+msgid "Size"
+msgstr "Taille"
+
+#: ../../Zotlabs/Module/Sharedwithme.php:103
+#: ../../Zotlabs/Storage/Browser.php:236
+msgid "Last Modified"
+msgstr "Modifié le"
+
+#: ../../Zotlabs/Module/Sharedwithme.php:104
+msgid "Remove all files"
+msgstr "Supprimer tous les fichiers"
+
+#: ../../Zotlabs/Module/Sharedwithme.php:105
+msgid "Remove this file"
+msgstr "Supprimer ce fichier"
+
+#: ../../Zotlabs/Module/Setup.php:176
+msgid "$Projectname Server - Setup"
+msgstr "Serveur $Projectname - configuration"
+
+#: ../../Zotlabs/Module/Setup.php:180
+msgid "Could not connect to database."
+msgstr "Impossible de se connecter à la base de données."
+
+#: ../../Zotlabs/Module/Setup.php:184
+msgid ""
+"Could not connect to specified site URL. Possible SSL certificate or DNS "
+"issue."
+msgstr "Impossible de se connecter à l'URL indiquée. Problème potentiel de certificat SSL/TLS ou de DNS."
+
+#: ../../Zotlabs/Module/Setup.php:191
+msgid "Could not create table."
+msgstr "Impossible de créer la table."
+
+#: ../../Zotlabs/Module/Setup.php:196
+msgid "Your site database has been installed."
+msgstr "La base de données de votre site a été installée."
+
+#: ../../Zotlabs/Module/Setup.php:200
+msgid ""
+"You may need to import the file \"install/schema_xxx.sql\" manually using a "
+"database client."
+msgstr "Vous pourriez avoir besoin d'importer le fichier \"install/schema_xxx.sql\" manuellement via un client de base de données (ex: phpmyadmin)."
+
+#: ../../Zotlabs/Module/Setup.php:201 ../../Zotlabs/Module/Setup.php:263
+#: ../../Zotlabs/Module/Setup.php:748
+msgid "Please see the file \"install/INSTALL.txt\"."
+msgstr "Merci de consulter le fichier \"install/INSTALL.txt\"."
+
+#: ../../Zotlabs/Module/Setup.php:260
+msgid "System check"
+msgstr "Vérification du système"
+
+#: ../../Zotlabs/Module/Setup.php:265
+msgid "Check again"
+msgstr "Re-vérifier"
+
+#: ../../Zotlabs/Module/Setup.php:287
+msgid "Database connection"
+msgstr "Connexion à la base de données"
+
+#: ../../Zotlabs/Module/Setup.php:288
+msgid ""
+"In order to install $Projectname we need to know how to connect to your "
+"database."
+msgstr "Pour installer $Projectname, nous avons besoin de savoir comment se connecter à votre base de données."
+
+#: ../../Zotlabs/Module/Setup.php:289
+msgid ""
+"Please contact your hosting provider or site administrator if you have "
+"questions about these settings."
+msgstr "Merci de contacter votre prestataire d'hébergement ou votre administrateur de site si vous avez des questions à propos de ces paramètres."
+
+#: ../../Zotlabs/Module/Setup.php:290
+msgid ""
+"The database you specify below should already exist. If it does not, please "
+"create it before continuing."
+msgstr "La base de données que vous allez spécifier doit exister. Si ce n'est pas déjà le cas, merci de la créer avant de continuer."
+
+#: ../../Zotlabs/Module/Setup.php:294
+msgid "Database Server Name"
+msgstr "Nom du serveur de base de données"
+
+#: ../../Zotlabs/Module/Setup.php:294
+msgid "Default is 127.0.0.1"
+msgstr "Par défaut 127.0.0.1"
+
+#: ../../Zotlabs/Module/Setup.php:295
+msgid "Database Port"
+msgstr "Port de la base de données"
+
+#: ../../Zotlabs/Module/Setup.php:295
+msgid "Communication port number - use 0 for default"
+msgstr "Numéro TCP du port - utilisez 0 pour la valeur par défaut"
+
+#: ../../Zotlabs/Module/Setup.php:296
+msgid "Database Login Name"
+msgstr "Identifiant de connexion à la Base de Données"
+
+#: ../../Zotlabs/Module/Setup.php:297
+msgid "Database Login Password"
+msgstr "Mot de passe de connexion à la Base de Données"
+
+#: ../../Zotlabs/Module/Setup.php:298
+msgid "Database Name"
+msgstr "Nom de la Base de Données"
+
+#: ../../Zotlabs/Module/Setup.php:299
+msgid "Database Type"
+msgstr "Type de base de données"
+
+#: ../../Zotlabs/Module/Setup.php:301 ../../Zotlabs/Module/Setup.php:347
+msgid "Site administrator email address"
+msgstr "Adresse de courriel de l'administrateur du site"
+
+#: ../../Zotlabs/Module/Setup.php:301 ../../Zotlabs/Module/Setup.php:347
+msgid ""
+"Your account email address must match this in order to use the web admin "
+"panel."
+msgstr "Votre compte devra utiliser la même adresse de courriel pour pouvoir utiliser l'administration web."
+
+#: ../../Zotlabs/Module/Setup.php:302 ../../Zotlabs/Module/Setup.php:349
+msgid "Website URL"
+msgstr "URL du site web"
+
+#: ../../Zotlabs/Module/Setup.php:302 ../../Zotlabs/Module/Setup.php:349
+msgid "Please use SSL (https) URL if available."
+msgstr "Veuillez utiliser SSL/TLS (https) si disponible."
+
+#: ../../Zotlabs/Module/Setup.php:303 ../../Zotlabs/Module/Setup.php:353
+msgid "Please select a default timezone for your website"
+msgstr "Veuillez choisir un fuseau horaire par défaut pour votre site"
+
+#: ../../Zotlabs/Module/Setup.php:328 ../../Zotlabs/Module/Admin/Site.php:258
+msgid "Basic/Minimal Social Networking"
+msgstr "Réseau social de base"
+
+#: ../../Zotlabs/Module/Setup.php:329 ../../Zotlabs/Module/Admin/Site.php:259
+msgid "Standard Configuration (default)"
+msgstr "Configuration standard par défaut"
+
+#: ../../Zotlabs/Module/Setup.php:330 ../../Zotlabs/Module/Admin/Site.php:260
+msgid "Professional"
+msgstr "Professionel"
+
+#: ../../Zotlabs/Module/Setup.php:336
+msgid "Site settings"
+msgstr "Paramètres du site"
+
+#: ../../Zotlabs/Module/Setup.php:351 ../../Zotlabs/Module/Admin/Site.php:289
+msgid "Server Configuration/Role"
+msgstr "Configuration du site."
+
+#: ../../Zotlabs/Module/Setup.php:392
+msgid "PHP version 5.5 or greater is required."
+msgstr "PHP version 5.5 ou supérieur est requis"
+
+#: ../../Zotlabs/Module/Setup.php:393
+msgid "PHP version"
+msgstr "Version de PHP"
+
+#: ../../Zotlabs/Module/Setup.php:409
+msgid "Could not find a command line version of PHP in the web server PATH."
+msgstr "Impossible de trouver une version CLI de PHP dans le PATH du serveur web."
+
+#: ../../Zotlabs/Module/Setup.php:410
+msgid ""
+"If you don't have a command line version of PHP installed on server, you "
+"will not be able to run background polling via cron."
+msgstr "En l'absence de version CLI de PHP sur votre serveur, vous ne pourrez pas utiliser la synchronisation en arrière-plan via cron."
+
+#: ../../Zotlabs/Module/Setup.php:414
+msgid "PHP executable path"
+msgstr "Chemin vers l'éxecutable PHP"
+
+#: ../../Zotlabs/Module/Setup.php:414
+msgid ""
+"Enter full path to php executable. You can leave this blank to continue the "
+"installation."
+msgstr "Entrez le chemin complet vers l'exécutable php. Vous pouvez continuer l'installation sans."
+
+#: ../../Zotlabs/Module/Setup.php:419
+msgid "Command line PHP"
+msgstr "PHP en ligne de commande (CLI)"
+
+#: ../../Zotlabs/Module/Setup.php:429
+msgid ""
+"Unable to check command line PHP, as shell_exec() is disabled. This is "
+"required."
+msgstr "Impossible de vérifier la ligne de commande PHP, car shell_exec () est désactivé. Ceci est nécessaire."
+
+#: ../../Zotlabs/Module/Setup.php:432
+msgid ""
+"The command line version of PHP on your system does not have "
+"\"register_argc_argv\" enabled."
+msgstr "La version CLI de PHP sur votre système n'a pas l'option \"register_argc_argv\" activée."
+
+#: ../../Zotlabs/Module/Setup.php:433
+msgid "This is required for message delivery to work."
+msgstr "Elle est nécessaire pour la distribution des messages."
+
+#: ../../Zotlabs/Module/Setup.php:436
+msgid "PHP register_argc_argv"
+msgstr "PHP register_argc_argv"
+
+#: ../../Zotlabs/Module/Setup.php:454
+#, php-format
+msgid ""
+"Your max allowed total upload size is set to %s. Maximum size of one file to"
+" upload is set to %s. You are allowed to upload up to %d files at once."
+msgstr "Votre taille de téléversement maximale totale autorisée est fixée à %s. La taille maximale d'un seul fichier à téléverser est fixée à %s. Vous pouvez téléverser jusqu'à %d fichier(s) à la fois."
+
+#: ../../Zotlabs/Module/Setup.php:459
+msgid "You can adjust these settings in the server php.ini file."
+msgstr "Vous pouvez ajuster ces paramètres dans le fichier php.ini du serveur."
+
+#: ../../Zotlabs/Module/Setup.php:461
+msgid "PHP upload limits"
+msgstr "Limites de téléversement de PHP"
+
+#: ../../Zotlabs/Module/Setup.php:484
+msgid ""
+"Error: the \"openssl_pkey_new\" function on this system is not able to "
+"generate encryption keys"
+msgstr "Erreur&nbsp;: la fonction \"openssl_pkey_new\" de ce système n'est pas capable de générer des clefs de chiffrement"
+
+#: ../../Zotlabs/Module/Setup.php:485
+msgid ""
+"If running under Windows, please see "
+"\"http://www.php.net/manual/en/openssl.installation.php\"."
+msgstr "Si vous êtes sur un serveur Windows, merci de consulter \"http://www.php.net/manual/fr/openssl.installation.php\"."
+
+#: ../../Zotlabs/Module/Setup.php:488
+msgid "Generate encryption keys"
+msgstr "Générer les clefs de chiffrement"
+
+#: ../../Zotlabs/Module/Setup.php:505
+msgid "libCurl PHP module"
+msgstr "module PHP libCurl"
+
+#: ../../Zotlabs/Module/Setup.php:506
+msgid "GD graphics PHP module"
+msgstr "module PHP GD graphics"
+
+#: ../../Zotlabs/Module/Setup.php:507
+msgid "OpenSSL PHP module"
+msgstr "module PHP OpenSSL"
+
+#: ../../Zotlabs/Module/Setup.php:508
+msgid "PDO database PHP module"
+msgstr "module PDO de la base de données PHP"
+
+#: ../../Zotlabs/Module/Setup.php:509
+msgid "mb_string PHP module"
+msgstr "module PHP mb_string"
+
+#: ../../Zotlabs/Module/Setup.php:510
+msgid "xml PHP module"
+msgstr "module PHP xml"
+
+#: ../../Zotlabs/Module/Setup.php:514 ../../Zotlabs/Module/Setup.php:516
+msgid "Apache mod_rewrite module"
+msgstr "module Apache mod_rewrite"
+
+#: ../../Zotlabs/Module/Setup.php:514
+msgid ""
+"Error: Apache webserver mod-rewrite module is required but not installed."
+msgstr "Erreur&nbsp;: le module mod-rewrite du serveur web Apache est requis, mais pas installé."
+
+#: ../../Zotlabs/Module/Setup.php:520 ../../Zotlabs/Module/Setup.php:523
+msgid "exec"
+msgstr "exécuter"
+
+#: ../../Zotlabs/Module/Setup.php:520
+msgid ""
+"Error: exec is required but is either not installed or has been disabled in "
+"php.ini"
+msgstr "Erreur: exec est requis mais soit il n'est pas installé, soit il a été désactivé dans php.ini"
+
+#: ../../Zotlabs/Module/Setup.php:526 ../../Zotlabs/Module/Setup.php:529
+msgid "shell_exec"
+msgstr "shell_exec"
+
+#: ../../Zotlabs/Module/Setup.php:526
+msgid ""
+"Error: shell_exec is required but is either not installed or has been "
+"disabled in php.ini"
+msgstr "Erreur: shell_exec est requis mais soit il n'est pas installé, soit il a été désactivé dans php.ini"
+
+#: ../../Zotlabs/Module/Setup.php:534
+msgid "Error: libCURL PHP module required but not installed."
+msgstr "Erreur&nbsp;: le module libCURL de PHP est requis, mais pas installé."
+
+#: ../../Zotlabs/Module/Setup.php:538
+msgid ""
+"Error: GD graphics PHP module with JPEG support required but not installed."
+msgstr "Erreur&nbsp;: le module GD de PHP avec support JPEG est requis, mais pas installé."
+
+#: ../../Zotlabs/Module/Setup.php:542
+msgid "Error: openssl PHP module required but not installed."
+msgstr "Erreur&nbsp;: le module openssl de PHP est requis, mais pas installé."
+
+#: ../../Zotlabs/Module/Setup.php:546
+msgid "Error: PDO database PHP module required but not installed."
+msgstr "Erreur: le module PDO de base de données PHP est requis mais n'est pas installé."
+
+#: ../../Zotlabs/Module/Setup.php:550
+msgid "Error: mb_string PHP module required but not installed."
+msgstr "Erreur&nbsp;: le module mb_string de PHP est requis, mais pas installé."
+
+#: ../../Zotlabs/Module/Setup.php:554
+msgid "Error: xml PHP module required for DAV but not installed."
+msgstr "Erreur&nbsp;: le module xml de PHP est requis pour le DAV, mais pas installé."
+
+#: ../../Zotlabs/Module/Setup.php:572
+msgid ""
+"The web installer needs to be able to create a file called \".htconfig.php\""
+" in the top folder of your web server and it is unable to do so."
+msgstr "L'installeur web a besoin de créer un fichier \".htconfig.php\" à la racine de votre serveur web, mais en est incapable."
+
+#: ../../Zotlabs/Module/Setup.php:573
+msgid ""
+"This is most often a permission setting, as the web server may not be able "
+"to write files in your folder - even if you can."
+msgstr "C'est généralement lié à un problème de droits, à cause duquel le serveur web est interdit d'écriture dans le répertoire concerné - alors que votre propre utilisateur a le droit."
+
+#: ../../Zotlabs/Module/Setup.php:574
+msgid ""
+"At the end of this procedure, we will give you a text to save in a file "
+"named .htconfig.php in your Red top folder."
+msgstr "Au terme de cette procédure, nous vous transmettrons un texte à sauvegarder dans un fichier nommé .htconfig.php, à la racine de votre installation de $Projectname."
+
+#: ../../Zotlabs/Module/Setup.php:575
+msgid ""
+"You can alternatively skip this procedure and perform a manual installation."
+" Please see the file \"install/INSTALL.txt\" for instructions."
+msgstr "Autrement, vous pouvez contourner toute cette procédure et réaliser l'installation manuellement. Merci de consulter le fichier \"install/INSTALL.txt\" pour les instructions détaillées."
+
+#: ../../Zotlabs/Module/Setup.php:578
+msgid ".htconfig.php is writable"
+msgstr "Le fichier .htconfig.php est accessible en écriture"
+
+#: ../../Zotlabs/Module/Setup.php:592
+msgid ""
+"This software uses the Smarty3 template engine to render its web views. "
+"Smarty3 compiles templates to PHP to speed up rendering."
+msgstr "Ce logiciel utilise Smarty3 comme moteur de modèles pour afficher ses vues Web. Smarty3 compile ses modèles en PHP pour accélérer le rendu."
+
+#: ../../Zotlabs/Module/Setup.php:593
+#, php-format
+msgid ""
+"In order to store these compiled templates, the web server needs to have "
+"write access to the directory %s under the top level web folder."
+msgstr "Afin de stocker ces modèles compilés, le serveur Web doit disposer d'un accès en écriture au répertoire %s selon le dossier Web racine."
+
+#: ../../Zotlabs/Module/Setup.php:594 ../../Zotlabs/Module/Setup.php:615
+msgid ""
+"Please ensure that the user that your web server runs as (e.g. www-data) has"
+" write access to this folder."
+msgstr "Merci de vous assurer que l'utilisateur sous lequel le serveur web tourne (le plus souvent, www-data) a bien l'autorisation d'écrire dans ce répertoire."
+
+#: ../../Zotlabs/Module/Setup.php:595
+#, php-format
+msgid ""
+"Note: as a security measure, you should give the web server write access to "
+"%s only--not the template files (.tpl) that it contains."
+msgstr "Note: Comme mesure de sécurité, assurez vous de donner les droits d'écriture au serveur web sur %s uniquement, pas sur les fichiers individuels (.tpl) qu'il contient."
+
+#: ../../Zotlabs/Module/Setup.php:598
+#, php-format
+msgid "%s is writable"
+msgstr "Permission d'écriture sur %s activée"
+
+#: ../../Zotlabs/Module/Setup.php:614
+msgid ""
+"This software uses the store directory to save uploaded files. The web "
+"server needs to have write access to the store directory under the top level"
+" web folder"
+msgstr "Ce logiciel utilise le répertoire de stockage pour enregistrer les fichiers téléversés. Le serveur Web doit disposer d'un accès en écriture au répertoire de stockage selon le dossier web racine."
+
+#: ../../Zotlabs/Module/Setup.php:618
+msgid "store is writable"
+msgstr "'store' est accessible en écriture"
+
+#: ../../Zotlabs/Module/Setup.php:650
+msgid ""
+"SSL certificate cannot be validated. Fix certificate or disable https access"
+" to this site."
+msgstr "Le certificat SSL/TLS n'a pas pu être validé. Merci de le corriger, ou de désactiver l'accès https à ce site (non recommandé)."
+
+#: ../../Zotlabs/Module/Setup.php:651
+msgid ""
+"If you have https access to your website or allow connections to TCP port "
+"443 (the https: port), you MUST use a browser-valid certificate. You MUST "
+"NOT use self-signed certificates!"
+msgstr "Si votre serveur accepte les connexions https ou s'il permet les connexions sur le port TCP 443 (le port utilisé par le protocole https), vous DEVEZ utiliser un certificat valide. Vous ne DEVEZ PAS utiliser un certificat que vous avez vous-mêmes signé&nbsp;!"
+
+#: ../../Zotlabs/Module/Setup.php:652
+msgid ""
+"This restriction is incorporated because public posts from you may for "
+"example contain references to images on your own hub."
+msgstr "Nous avons ajouté cette contrainte pour éviter que vos publications publiques ne fassent référence par exemple à des images sur votre propre hub."
+
+#: ../../Zotlabs/Module/Setup.php:653
+msgid ""
+"If your certificate is not recognized, members of other sites (who may "
+"themselves have valid certificates) will get a warning message on their own "
+"site complaining about security issues."
+msgstr "Si votre certificat n'est pas reconnu, les membres des autres sites (qui eux peuvent avoir des certificats valides) recevront des messages d'avertissement sur leur propre site se plaignant de problèmes de sécurité."
+
+#: ../../Zotlabs/Module/Setup.php:654
+msgid ""
+"This can cause usability issues elsewhere (not just on your own site) so we "
+"must insist on this requirement."
+msgstr "Ceci peut causer des problèmes d'ergonomie ailleurs (pas seulement sur votre site), nous devons donc insister sur ce prérequis."
+
+#: ../../Zotlabs/Module/Setup.php:655
+msgid ""
+"Providers are available that issue free certificates which are browser-"
+"valid."
+msgstr "Il existe des autorités de certification qui vous fourniront gratuitement un certificat valide."
+
+#: ../../Zotlabs/Module/Setup.php:657
+msgid ""
+"If you are confident that the certificate is valid and signed by a trusted "
+"authority, check to see if you have failed to install an intermediate cert. "
+"These are not normally required by browsers, but are required for server-to-"
+"server communications."
+msgstr "Si vous êtes certain que le certificat est valide et signé par une autorité de confiance, vérifiez si l'installation d'un certificat intermédiaire aurait échoué. Ceux-ci ne sont normalement pas requis par les navigateurs, mais ils sont requis pour les communications entre serveurs."
+
+#: ../../Zotlabs/Module/Setup.php:659
+msgid "SSL certificate validation"
+msgstr "Validation du certificat SSL/TLS"
+
+#: ../../Zotlabs/Module/Setup.php:665
+msgid ""
+"Url rewrite in .htaccess is not working. Check your server "
+"configuration.Test: "
+msgstr "La réécriture d'URL définie dans le .htaccess ne fonctionne pas. Vérifiez votre configuration serveur. Test&nbsp;:"
+
+#: ../../Zotlabs/Module/Setup.php:668
+msgid "Url rewrite is working"
+msgstr "La réécriture d'URL fonctionne"
+
+#: ../../Zotlabs/Module/Setup.php:682
+msgid ""
+"The database configuration file \".htconfig.php\" could not be written. "
+"Please use the enclosed text to create a configuration file in your web "
+"server root."
+msgstr "Le fichier de configuration de la base de données - \".htconfig.php\" - ne peut être écrit. Merci de copier le texte généré dans un fichier à ce nom, à la racine de votre serveur web."
+
+#: ../../Zotlabs/Module/Setup.php:706
+#: ../../addon/rendezvous/rendezvous.php:401 ../../addon/cdav/cdav.php:41
+msgid "Errors encountered creating database tables."
+msgstr "Erreurs rencontrées pendant la création de tables de BDD."
+
+#: ../../Zotlabs/Module/Setup.php:746
+msgid "<h1>What next</h1>"
+msgstr "<h1>Et maintenant</h1>"
+
+#: ../../Zotlabs/Module/Setup.php:747
+msgid ""
+"IMPORTANT: You will need to [manually] setup a scheduled task for the "
+"poller."
+msgstr "IMPORTANT&nbsp;: Vous devez créer [manuellement] une tâche planifiée pour les mises à jour du réseau."
#: ../../Zotlabs/Module/Connect.php:61 ../../Zotlabs/Module/Connect.php:109
msgid "Continue"
@@ -553,2629 +1884,2842 @@ msgstr "(Aucune instruction spécifique n'a été fournie par le propriétaire d
msgid "Restricted or Premium Channel"
msgstr "Canal VIP ou restreint"
-#: ../../Zotlabs/Module/Connedit.php:80
-msgid "Could not access contact record."
-msgstr "Impossible d'accéder aux détails du contact."
+#: ../../Zotlabs/Module/Admin/Queue.php:35
+msgid "Queue Statistics"
+msgstr "Statistiques de file d'attente"
-#: ../../Zotlabs/Module/Connedit.php:104
-msgid "Could not locate selected profile."
-msgstr "Impossible de localiser le profil sélectionné."
+#: ../../Zotlabs/Module/Admin/Queue.php:36
+msgid "Total Entries"
+msgstr "Nombre d'entrées total"
-#: ../../Zotlabs/Module/Connedit.php:227
-msgid "Connection updated."
-msgstr "Contact mis à jour."
+#: ../../Zotlabs/Module/Admin/Queue.php:37
+msgid "Priority"
+msgstr "Priorité"
-#: ../../Zotlabs/Module/Connedit.php:229
-msgid "Failed to update connection record."
-msgstr "Impossible de mettre à jour les détails du contact."
+#: ../../Zotlabs/Module/Admin/Queue.php:38
+msgid "Destination URL"
+msgstr "URL de destination"
-#: ../../Zotlabs/Module/Connedit.php:276
-msgid "is now connected to"
-msgstr "est maintenant connecté avec"
+#: ../../Zotlabs/Module/Admin/Queue.php:39
+msgid "Mark hub permanently offline"
+msgstr "Marquer le hub comme étant hors ligne de manière permanente"
-#: ../../Zotlabs/Module/Connedit.php:379 ../../Zotlabs/Module/Connedit.php:654
-#: ../../Zotlabs/Module/Events.php:459 ../../Zotlabs/Module/Events.php:460
-#: ../../Zotlabs/Module/Events.php:469 ../../Zotlabs/Module/Api.php:89
-#: ../../Zotlabs/Module/Filestorage.php:157
-#: ../../Zotlabs/Module/Filestorage.php:165 ../../Zotlabs/Module/Menu.php:100
-#: ../../Zotlabs/Module/Menu.php:157 ../../Zotlabs/Module/Mitem.php:158
-#: ../../Zotlabs/Module/Mitem.php:159 ../../Zotlabs/Module/Mitem.php:232
-#: ../../Zotlabs/Module/Mitem.php:233 ../../Zotlabs/Module/Photos.php:666
-#: ../../Zotlabs/Module/Profiles.php:647 ../../Zotlabs/Module/Admin.php:459
-#: ../../Zotlabs/Module/Removeme.php:61 ../../Zotlabs/Module/Settings.php:581
-#: ../../include/dir_fns.php:143 ../../include/dir_fns.php:144
-#: ../../include/dir_fns.php:145 ../../view/theme/redbasic/php/config.php:105
-#: ../../view/theme/redbasic/php/config.php:130 ../../boot.php:1707
-msgid "No"
-msgstr "Non"
+#: ../../Zotlabs/Module/Admin/Queue.php:40
+msgid "Empty queue for this hub"
+msgstr "Vider la file d'attente pour ce hub"
-#: ../../Zotlabs/Module/Connedit.php:379 ../../Zotlabs/Module/Events.php:459
-#: ../../Zotlabs/Module/Events.php:460 ../../Zotlabs/Module/Events.php:469
-#: ../../Zotlabs/Module/Api.php:88 ../../Zotlabs/Module/Filestorage.php:157
-#: ../../Zotlabs/Module/Filestorage.php:165 ../../Zotlabs/Module/Menu.php:100
-#: ../../Zotlabs/Module/Menu.php:157 ../../Zotlabs/Module/Mitem.php:158
-#: ../../Zotlabs/Module/Mitem.php:159 ../../Zotlabs/Module/Mitem.php:232
-#: ../../Zotlabs/Module/Mitem.php:233 ../../Zotlabs/Module/Photos.php:666
-#: ../../Zotlabs/Module/Profiles.php:647 ../../Zotlabs/Module/Admin.php:461
-#: ../../Zotlabs/Module/Removeme.php:61 ../../Zotlabs/Module/Settings.php:581
-#: ../../include/dir_fns.php:143 ../../include/dir_fns.php:144
-#: ../../include/dir_fns.php:145 ../../view/theme/redbasic/php/config.php:105
-#: ../../view/theme/redbasic/php/config.php:130 ../../boot.php:1707
-msgid "Yes"
-msgstr "Oui"
+#: ../../Zotlabs/Module/Admin/Queue.php:41
+msgid "Last known contact"
+msgstr "Dernier contact connu"
-#: ../../Zotlabs/Module/Connedit.php:411
-msgid "Could not access address book record."
-msgstr "Impossible d'accéder aux détails du carnet d'adresses."
+#: ../../Zotlabs/Module/Admin/Features.php:55
+#: ../../Zotlabs/Module/Admin/Features.php:56
+#: ../../Zotlabs/Module/Settings/Features.php:38
+msgid "Off"
+msgstr "Inactif"
-#: ../../Zotlabs/Module/Connedit.php:425
-msgid "Refresh failed - channel is currently unavailable."
-msgstr "Actualisation impossible - le canal est indisponible."
+#: ../../Zotlabs/Module/Admin/Features.php:55
+#: ../../Zotlabs/Module/Admin/Features.php:56
+#: ../../Zotlabs/Module/Settings/Features.php:38
+msgid "On"
+msgstr "Actif"
-#: ../../Zotlabs/Module/Connedit.php:440 ../../Zotlabs/Module/Connedit.php:449
-#: ../../Zotlabs/Module/Connedit.php:458 ../../Zotlabs/Module/Connedit.php:467
-#: ../../Zotlabs/Module/Connedit.php:480
-msgid "Unable to set address book parameters."
-msgstr "Impossible de régler les paramètres du carnet d'adresses."
+#: ../../Zotlabs/Module/Admin/Features.php:56
+#, php-format
+msgid "Lock feature %s"
+msgstr "Verrouiller fonctionnalité %s"
-#: ../../Zotlabs/Module/Connedit.php:503
-msgid "Connection has been removed."
-msgstr "Le contact a été supprimé."
+#: ../../Zotlabs/Module/Admin/Features.php:64
+msgid "Manage Additional Features"
+msgstr "Gérer les fonctionnalités additionnelles"
-#: ../../Zotlabs/Module/Connedit.php:519 ../../Zotlabs/Lib/Apps.php:219
-#: ../../include/nav.php:86 ../../include/conversation.php:954
-msgid "View Profile"
-msgstr "Voir le profil"
+#: ../../Zotlabs/Module/Admin/Dbsync.php:19
+msgid "Update has been marked successful"
+msgstr "La mise à jour a été marquée comme réussie"
-#: ../../Zotlabs/Module/Connedit.php:522
+#: ../../Zotlabs/Module/Admin/Dbsync.php:29
#, php-format
-msgid "View %s's profile"
-msgstr "Voir le profil de %s"
+msgid "Executing %s failed. Check system logs."
+msgstr "L'éxecution de %s a échoué. Merci de vérifier les journaux du système."
-#: ../../Zotlabs/Module/Connedit.php:526
-msgid "Refresh Permissions"
-msgstr "Actualiser les autorisations"
+#: ../../Zotlabs/Module/Admin/Dbsync.php:32
+#, php-format
+msgid "Update %s was successfully applied."
+msgstr "La mise à jour %s a été appliquée avec succès."
-#: ../../Zotlabs/Module/Connedit.php:529
-msgid "Fetch updated permissions"
-msgstr "Récupérer les autorisations les plus récentes"
+#: ../../Zotlabs/Module/Admin/Dbsync.php:36
+#, php-format
+msgid "Update %s did not return a status. Unknown if it succeeded."
+msgstr "La mise à jour %s n'a pas retourné d'information. Impossible de savoir si elle a réussi ou non."
-#: ../../Zotlabs/Module/Connedit.php:533
-msgid "Recent Activity"
-msgstr "Activité récente"
+#: ../../Zotlabs/Module/Admin/Dbsync.php:39
+#, php-format
+msgid "Update function %s could not be found."
+msgstr "La fonction de mise à jour %s est introuvable."
-#: ../../Zotlabs/Module/Connedit.php:536
-msgid "View recent posts and comments"
-msgstr "Voir les publications et commentaires récents"
+#: ../../Zotlabs/Module/Admin/Dbsync.php:55
+msgid "No failed updates."
+msgstr "Aucune mise à jour défaillante."
-#: ../../Zotlabs/Module/Connedit.php:540 ../../Zotlabs/Module/Admin.php:1041
-msgid "Unblock"
-msgstr "Débloquer"
+#: ../../Zotlabs/Module/Admin/Dbsync.php:59
+msgid "Failed Updates"
+msgstr "Mises à jour défaillantes"
-#: ../../Zotlabs/Module/Connedit.php:540 ../../Zotlabs/Module/Admin.php:1040
-msgid "Block"
-msgstr "Bloquer"
+#: ../../Zotlabs/Module/Admin/Dbsync.php:61
+msgid "Mark success (if update was manually applied)"
+msgstr "Marquer comme réussie (si la mise à jour a été réalisée manuellement)"
-#: ../../Zotlabs/Module/Connedit.php:543
-msgid "Block (or Unblock) all communications with this connection"
-msgstr "Bloquer ou débloquer toute communication avec ce contact"
+#: ../../Zotlabs/Module/Admin/Dbsync.php:62
+msgid "Attempt to execute this update step automatically"
+msgstr "Tenter de réaliser cette étape de mise à jour automatiquement"
-#: ../../Zotlabs/Module/Connedit.php:544
-msgid "This connection is blocked!"
-msgstr "Ce contact est bloqué&nbsp;!"
+#: ../../Zotlabs/Module/Admin/Plugins.php:259
+#: ../../Zotlabs/Module/Admin/Themes.php:72 ../../Zotlabs/Module/Thing.php:89
+#: ../../Zotlabs/Module/Viewsrc.php:24 ../../Zotlabs/Module/Display.php:35
+#: ../../Zotlabs/Module/Filestorage.php:32 ../../Zotlabs/Module/Admin.php:60
+#: ../../include/items.php:3378
+msgid "Item not found."
+msgstr "Élément introuvable"
-#: ../../Zotlabs/Module/Connedit.php:548
-msgid "Unignore"
-msgstr "Ne plus ignorer"
+#: ../../Zotlabs/Module/Admin/Plugins.php:289
+#, php-format
+msgid "Plugin %s disabled."
+msgstr "Greffon %s désactivé."
-#: ../../Zotlabs/Module/Connedit.php:548
-#: ../../Zotlabs/Module/Connections.php:277
-#: ../../Zotlabs/Module/Notifications.php:55
-msgid "Ignore"
-msgstr "Ignorer"
+#: ../../Zotlabs/Module/Admin/Plugins.php:294
+#, php-format
+msgid "Plugin %s enabled."
+msgstr "Greffon %s activé."
-#: ../../Zotlabs/Module/Connedit.php:551
-msgid "Ignore (or Unignore) all inbound communications from this connection"
-msgstr "Ignorer ou ne plus ignorer toute communication venant de ce contact"
+#: ../../Zotlabs/Module/Admin/Plugins.php:310
+#: ../../Zotlabs/Module/Admin/Themes.php:95
+msgid "Disable"
+msgstr "Désactiver"
-#: ../../Zotlabs/Module/Connedit.php:552
-msgid "This connection is ignored!"
-msgstr "Ce contact est ignoré&nbsp;!"
+#: ../../Zotlabs/Module/Admin/Plugins.php:313
+#: ../../Zotlabs/Module/Admin/Themes.php:97
+msgid "Enable"
+msgstr "Activer"
-#: ../../Zotlabs/Module/Connedit.php:556
-msgid "Unarchive"
-msgstr "Désarchiver"
+#: ../../Zotlabs/Module/Admin/Plugins.php:341
+#: ../../Zotlabs/Module/Admin/Plugins.php:436
+#: ../../Zotlabs/Module/Admin/Accounts.php:164
+#: ../../Zotlabs/Module/Admin/Logs.php:82
+#: ../../Zotlabs/Module/Admin/Channels.php:145
+#: ../../Zotlabs/Module/Admin/Themes.php:122
+#: ../../Zotlabs/Module/Admin/Themes.php:156
+#: ../../Zotlabs/Module/Admin/Site.php:277
+#: ../../Zotlabs/Module/Admin/Security.php:86
+#: ../../Zotlabs/Module/Admin.php:137
+msgid "Administration"
+msgstr "Administration"
-#: ../../Zotlabs/Module/Connedit.php:556
-msgid "Archive"
-msgstr "Archiver"
+#: ../../Zotlabs/Module/Admin/Plugins.php:342
+#: ../../Zotlabs/Module/Admin/Plugins.php:437
+#: ../../Zotlabs/Widget/Admin.php:27
+msgid "Plugins"
+msgstr "Greffons"
-#: ../../Zotlabs/Module/Connedit.php:559
-msgid ""
-"Archive (or Unarchive) this connection - mark channel dead but keep content"
-msgstr "Archiver ou désarchiver ce contact - le marquer comme inactif mais conserver le contenu"
+#: ../../Zotlabs/Module/Admin/Plugins.php:343
+#: ../../Zotlabs/Module/Admin/Themes.php:124
+msgid "Toggle"
+msgstr "(Dés)activer"
-#: ../../Zotlabs/Module/Connedit.php:560
-msgid "This connection is archived!"
-msgstr "Ce contact est archivé&nbsp;!"
+#: ../../Zotlabs/Module/Admin/Plugins.php:344
+#: ../../Zotlabs/Module/Admin/Themes.php:125 ../../Zotlabs/Lib/Apps.php:223
+#: ../../Zotlabs/Widget/Settings_menu.php:131 ../../include/nav.php:203
+msgid "Settings"
+msgstr "Paramètres"
-#: ../../Zotlabs/Module/Connedit.php:564
-msgid "Unhide"
-msgstr "Ne plus cacher"
+#: ../../Zotlabs/Module/Admin/Plugins.php:351
+#: ../../Zotlabs/Module/Admin/Themes.php:134
+msgid "Author: "
+msgstr "Auteur&nbsp;:"
-#: ../../Zotlabs/Module/Connedit.php:564
-msgid "Hide"
-msgstr "Cacher"
+#: ../../Zotlabs/Module/Admin/Plugins.php:352
+#: ../../Zotlabs/Module/Admin/Themes.php:135
+msgid "Maintainer: "
+msgstr "Maintenu par&nbsp;:"
-#: ../../Zotlabs/Module/Connedit.php:567
-msgid "Hide or Unhide this connection from your other connections"
-msgstr "Cacher ou ne plus cacher ce contact vis-à-vis de vos autres contacts"
+#: ../../Zotlabs/Module/Admin/Plugins.php:353
+msgid "Minimum project version: "
+msgstr "Version minimum du projet&nbsp;:"
-#: ../../Zotlabs/Module/Connedit.php:568
-msgid "This connection is hidden!"
-msgstr "Ce contact est caché&nbsp;!"
+#: ../../Zotlabs/Module/Admin/Plugins.php:354
+msgid "Maximum project version: "
+msgstr "Version maximum du projet&nbsp;:"
-#: ../../Zotlabs/Module/Connedit.php:575
-msgid "Delete this connection"
-msgstr "Supprimer ce contact"
+#: ../../Zotlabs/Module/Admin/Plugins.php:355
+msgid "Minimum PHP version: "
+msgstr "Version minimum de PHP&nbsp;:"
-#: ../../Zotlabs/Module/Connedit.php:590 ../../include/widgets.php:493
-msgid "Me"
-msgstr "Moi"
+#: ../../Zotlabs/Module/Admin/Plugins.php:356
+msgid "Compatible Server Roles: "
+msgstr "Rôles du serveur "
-#: ../../Zotlabs/Module/Connedit.php:591 ../../include/widgets.php:494
-msgid "Family"
-msgstr "Famille"
+#: ../../Zotlabs/Module/Admin/Plugins.php:357
+msgid "Requires: "
+msgstr "Requiert&nbsp;:"
-#: ../../Zotlabs/Module/Connedit.php:592 ../../Zotlabs/Module/Settings.php:342
-#: ../../Zotlabs/Module/Settings.php:346 ../../Zotlabs/Module/Settings.php:347
-#: ../../Zotlabs/Module/Settings.php:350 ../../Zotlabs/Module/Settings.php:361
-#: ../../include/widgets.php:495 ../../include/selectors.php:123
-#: ../../include/channel.php:389 ../../include/channel.php:390
-#: ../../include/channel.php:397
-msgid "Friends"
-msgstr "Amis"
+#: ../../Zotlabs/Module/Admin/Plugins.php:358
+#: ../../Zotlabs/Module/Admin/Plugins.php:442
+msgid "Disabled - version incompatibility"
+msgstr "Désactivé - version incompatible"
-#: ../../Zotlabs/Module/Connedit.php:593 ../../include/widgets.php:496
-msgid "Acquaintances"
-msgstr "Connaissances"
+#: ../../Zotlabs/Module/Admin/Plugins.php:411
+msgid "Enter the public git repository URL of the plugin repo."
+msgstr "Entrer l'URL du dépôt git public pour les greffons"
-#: ../../Zotlabs/Module/Connedit.php:594
-#: ../../Zotlabs/Module/Connections.php:92
-#: ../../Zotlabs/Module/Connections.php:107 ../../include/widgets.php:497
-msgid "All"
-msgstr "Tous"
+#: ../../Zotlabs/Module/Admin/Plugins.php:412
+msgid "Plugin repo git URL"
+msgstr "URL du git pour les plugin"
-#: ../../Zotlabs/Module/Connedit.php:654
-msgid "Approve this connection"
-msgstr "Autoriser ce contact"
+#: ../../Zotlabs/Module/Admin/Plugins.php:413
+msgid "Custom repo name"
+msgstr "Nom du dépôt"
-#: ../../Zotlabs/Module/Connedit.php:654
-msgid "Accept connection to allow communication"
-msgstr "Accepter le contact pour permettre la communication"
+#: ../../Zotlabs/Module/Admin/Plugins.php:413
+msgid "(optional)"
+msgstr "(en option)"
-#: ../../Zotlabs/Module/Connedit.php:659
-msgid "Set Affinity"
-msgstr "Définir le degré d'affinité"
+#: ../../Zotlabs/Module/Admin/Plugins.php:414
+msgid "Download Plugin Repo"
+msgstr "Télécharger l'extension"
-#: ../../Zotlabs/Module/Connedit.php:662
-msgid "Set Profile"
-msgstr "Définir le profil"
+#: ../../Zotlabs/Module/Admin/Plugins.php:421
+msgid "Install new repo"
+msgstr "Installer un nouveau dépôt"
-#: ../../Zotlabs/Module/Connedit.php:665
-msgid "Set Affinity & Profile"
-msgstr "Définir le degré d'affinité et le profil"
+#: ../../Zotlabs/Module/Admin/Plugins.php:422 ../../Zotlabs/Lib/Apps.php:348
+msgid "Install"
+msgstr "Installer"
-#: ../../Zotlabs/Module/Connedit.php:698
-msgid "none"
-msgstr "Aucun"
+#: ../../Zotlabs/Module/Admin/Plugins.php:423
+#: ../../Zotlabs/Module/Settings/Oauth.php:88
+#: ../../Zotlabs/Module/Settings/Oauth.php:114
+#: ../../Zotlabs/Module/Wiki.php:265 ../../Zotlabs/Module/Wiki.php:290
+#: ../../Zotlabs/Module/Connedit.php:928 ../../Zotlabs/Module/Fbrowser.php:66
+#: ../../Zotlabs/Module/Fbrowser.php:88 ../../Zotlabs/Module/Profiles.php:804
+#: ../../Zotlabs/Module/Filer.php:55 ../../Zotlabs/Module/Tagrm.php:15
+#: ../../Zotlabs/Module/Tagrm.php:138 ../../addon/cdav/Mod_Cdav.php:866
+#: ../../addon/cdav/Mod_Cdav.php:1154 ../../addon/js_upload/js_upload.php:46
+#: ../../addon/gitwiki/Mod_Gitwiki.php:244
+#: ../../addon/gitwiki/Mod_Gitwiki.php:267 ../../include/conversation.php:1327
+#: ../../include/conversation.php:1376
+msgid "Cancel"
+msgstr "Annuler"
-#: ../../Zotlabs/Module/Connedit.php:702 ../../include/widgets.php:614
-msgid "Connection Default Permissions"
-msgstr "Autorisations par défaut des contacts"
+#: ../../Zotlabs/Module/Admin/Plugins.php:445
+msgid "Manage Repos"
+msgstr "Gérer les dépôts"
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:446
+msgid "Installed Plugin Repositories"
+msgstr "Dépôt des extensions installées"
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:447
+msgid "Install a New Plugin Repository"
+msgstr "Installer un nouveau dépôt pour extensions"
-#: ../../Zotlabs/Module/Connedit.php:702 ../../include/items.php:3926
+#: ../../Zotlabs/Module/Admin/Plugins.php:453
+#: ../../Zotlabs/Module/Settings/Oauth.php:42
+#: ../../Zotlabs/Module/Settings/Oauth.php:113
+#: ../../Zotlabs/Module/Connedit.php:926 ../../Zotlabs/Module/Profiles.php:802
+#: ../../Zotlabs/Lib/Apps.php:348 ../../addon/cdav/Mod_Cdav.php:1152
+msgid "Update"
+msgstr "Mise à jour"
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:454
+msgid "Switch branch"
+msgstr "Changer de branche"
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:455
+#: ../../Zotlabs/Module/Photos.php:960 ../../Zotlabs/Module/Tagrm.php:137
+#: ../../addon/superblock/superblock.php:116
+msgid "Remove"
+msgstr "Retirer"
+
+#: ../../Zotlabs/Module/Admin/Accounts.php:36
#, php-format
-msgid "Connection: %s"
-msgstr "Contact&nbsp;: %s"
+msgid "%s account blocked/unblocked"
+msgid_plural "%s account blocked/unblocked"
+msgstr[0] "%s compte bloqué/débloqué"
+msgstr[1] "%s comptes bloqués/débloqués"
-#: ../../Zotlabs/Module/Connedit.php:703
-msgid "Apply these permissions automatically"
-msgstr "Appliquer ces permissions automatiquement"
+#: ../../Zotlabs/Module/Admin/Accounts.php:43
+#, php-format
+msgid "%s account deleted"
+msgid_plural "%s accounts deleted"
+msgstr[0] "%s compte supprimé"
+msgstr[1] "%s comptes supprimés"
-#: ../../Zotlabs/Module/Connedit.php:703
-msgid "Connection requests will be approved without your interaction"
-msgstr "Les demandes de contact seront approuvées automatiquement"
+#: ../../Zotlabs/Module/Admin/Accounts.php:79
+msgid "Account not found"
+msgstr "Compte introuvable"
-#: ../../Zotlabs/Module/Connedit.php:705
-msgid "This connection's primary address is"
-msgstr "L'adresse principale de ce contact est"
+#: ../../Zotlabs/Module/Admin/Accounts.php:90
+#, php-format
+msgid "Account '%s' deleted"
+msgstr "Compte '%s' supprimé"
-#: ../../Zotlabs/Module/Connedit.php:706
-msgid "Available locations:"
-msgstr "Emplacements disponibles&nbsp;:"
+#: ../../Zotlabs/Module/Admin/Accounts.php:98
+#, php-format
+msgid "Account '%s' blocked"
+msgstr "Compte '%s' bloqué"
-#: ../../Zotlabs/Module/Connedit.php:710
-msgid ""
-"The permissions indicated on this page will be applied to all new "
-"connections."
-msgstr "Les permissions indiquées sur cette page seront appliquées à tous vos nouveaux contacts."
+#: ../../Zotlabs/Module/Admin/Accounts.php:106
+#, php-format
+msgid "Account '%s' unblocked"
+msgstr "Compte '%s' débloqué"
-#: ../../Zotlabs/Module/Connedit.php:711
-msgid "Connection Tools"
-msgstr ""
+#: ../../Zotlabs/Module/Admin/Accounts.php:165
+#: ../../Zotlabs/Module/Admin/Accounts.php:178
+#: ../../Zotlabs/Widget/Admin.php:23
+msgid "Accounts"
+msgstr "Comptes"
-#: ../../Zotlabs/Module/Connedit.php:713
-msgid "Slide to adjust your degree of friendship"
-msgstr "Faites glisser pour ajuster votre proximité avec le contact"
+#: ../../Zotlabs/Module/Admin/Accounts.php:167
+#: ../../Zotlabs/Module/Admin/Channels.php:148
+msgid "select all"
+msgstr "tout sélectionner"
-#: ../../Zotlabs/Module/Connedit.php:714 ../../Zotlabs/Module/Rate.php:159
-#: ../../include/js_strings.php:20
-msgid "Rating"
-msgstr "Evaluation"
+#: ../../Zotlabs/Module/Admin/Accounts.php:168
+msgid "Registrations waiting for confirm"
+msgstr "Inscriptions en attente d'approbation"
-#: ../../Zotlabs/Module/Connedit.php:715
-msgid "Slide to adjust your rating"
-msgstr "Faîtes glisser pour ajuster votre note"
+#: ../../Zotlabs/Module/Admin/Accounts.php:169
+msgid "Request date"
+msgstr "Date de la demande"
-#: ../../Zotlabs/Module/Connedit.php:716 ../../Zotlabs/Module/Connedit.php:721
-msgid "Optionally explain your rating"
-msgstr "Explication facultative de votre évaluation"
+#: ../../Zotlabs/Module/Admin/Accounts.php:169
+#: ../../Zotlabs/Module/Admin/Accounts.php:181
+#: ../../Zotlabs/Module/Connedit.php:914 ../../Zotlabs/Module/Profiles.php:790
+#: ../../addon/cdav/Mod_Cdav.php:1140 ../../addon/openid/MysqlProvider.php:56
+#: ../../addon/openid/MysqlProvider.php:57 ../../addon/rtof/rtof.php:93
+#: ../../addon/redred/redred.php:107 ../../include/network.php:2270
+msgid "Email"
+msgstr "Courriel"
-#: ../../Zotlabs/Module/Connedit.php:718
-msgid "Custom Filter"
-msgstr "Filtre personnalisé"
+#: ../../Zotlabs/Module/Admin/Accounts.php:170
+msgid "No registrations."
+msgstr "Pas d'inscriptions."
-#: ../../Zotlabs/Module/Connedit.php:719
-msgid "Only import posts with this text"
-msgstr "N'importer que les publications comprenant ce texte"
+#: ../../Zotlabs/Module/Admin/Accounts.php:171
+#: ../../Zotlabs/Module/Connections.php:281
+msgid "Approve"
+msgstr "Approuver"
-#: ../../Zotlabs/Module/Connedit.php:719 ../../Zotlabs/Module/Connedit.php:720
-msgid ""
-"words one per line or #tags or /patterns/ or lang=xx, leave blank to import "
-"all posts"
-msgstr "un mot par ligne ou #étiquettes ou /motif/ ou lang=xx, laisser vide pour importer toutes les publications"
+#: ../../Zotlabs/Module/Admin/Accounts.php:172
+msgid "Deny"
+msgstr "Refuser"
-#: ../../Zotlabs/Module/Connedit.php:720
-msgid "Do not import posts with this text"
-msgstr "Ne pas importer les publications comprenant ce texte"
+#: ../../Zotlabs/Module/Admin/Accounts.php:174
+#: ../../Zotlabs/Module/Connedit.php:626
+msgid "Block"
+msgstr "Bloquer"
-#: ../../Zotlabs/Module/Connedit.php:722
-msgid "This information is public!"
-msgstr "Cette information est publique&nbsp;!"
+#: ../../Zotlabs/Module/Admin/Accounts.php:175
+#: ../../Zotlabs/Module/Connedit.php:626
+msgid "Unblock"
+msgstr "Débloquer"
-#: ../../Zotlabs/Module/Connedit.php:727
-msgid "Connection Pending Approval"
-msgstr "Contact en attente d'approbation"
+#: ../../Zotlabs/Module/Admin/Accounts.php:180
+msgid "ID"
+msgstr "Identifiant"
-#: ../../Zotlabs/Module/Connedit.php:730
-msgid "inherited"
-msgstr "héritée"
+#: ../../Zotlabs/Module/Admin/Accounts.php:182 ../../include/group.php:287
+msgid "All Channels"
+msgstr "Tous les canaux"
-#: ../../Zotlabs/Module/Connedit.php:732
-#, php-format
-msgid ""
-"Please choose the profile you would like to display to %s when viewing your "
-"profile securely."
-msgstr "Merci de choisir le profil que vous souhaitez montrer quand %s visite votre profil de manière authentifiée."
+#: ../../Zotlabs/Module/Admin/Accounts.php:183
+msgid "Register date"
+msgstr "Date d'inscription"
-#: ../../Zotlabs/Module/Connedit.php:734
-msgid "Their Settings"
-msgstr "Leurs paramètres"
+#: ../../Zotlabs/Module/Admin/Accounts.php:184
+msgid "Last login"
+msgstr "Dernière connexion"
-#: ../../Zotlabs/Module/Connedit.php:735
-msgid "My Settings"
-msgstr "Mes paramètres"
+#: ../../Zotlabs/Module/Admin/Accounts.php:185
+msgid "Expires"
+msgstr "Expire le"
-#: ../../Zotlabs/Module/Connedit.php:737
-msgid "Individual Permissions"
-msgstr "Permissions individuelles"
+#: ../../Zotlabs/Module/Admin/Accounts.php:186
+msgid "Service Class"
+msgstr "Classe de service"
-#: ../../Zotlabs/Module/Connedit.php:738
+#: ../../Zotlabs/Module/Admin/Accounts.php:188
msgid ""
-"Some permissions may be inherited from your channel's <a "
-"href=\"settings\"><strong>privacy settings</strong></a>, which have higher "
-"priority than individual settings. You can <strong>not</strong> change those"
-" settings here."
-msgstr "Certaines permissions peuvent être héritées de vos <a href=\"settings\">paramètres de confidentialité</a> de canal, lesquels sont prioritaires sur les réglages individuels. Vous pouvez modifier ces permissions ici mais cela n'aura aucun effet à moins de changer les paramètres hérités."
+"Selected accounts will be deleted!\\n\\nEverything these accounts had posted"
+" on this site will be permanently deleted!\\n\\nAre you sure?"
+msgstr "Les comptes sélectionnés seront supprimés&nbsp;!\\n\\nTout ce que ces utilisateurs ont publié sur ce site sera détruit de manière définitive&nbsp;!\\n\\nÊtes-vous sûr&nbsp;?"
-#: ../../Zotlabs/Module/Connedit.php:739
+#: ../../Zotlabs/Module/Admin/Accounts.php:189
msgid ""
-"Some permissions may be inherited from your channel's <a "
-"href=\"settings\"><strong>privacy settings</strong></a>, which have higher "
-"priority than individual settings. You can change those settings here but "
-"they wont have any impact unless the inherited setting changes."
-msgstr "Certaines permissions peuvent être héritées de vos <a href=\"settings\">paramètres de confidentialité</a> de canal, lesquels sont prioritaires sur les réglages individuels. Vous pouvez modifier ces permissions ici mais cela n'aura aucun effet à moins de changer les paramètres hérités."
+"The account {0} will be deleted!\\n\\nEverything this account has posted on "
+"this site will be permanently deleted!\\n\\nAre you sure?"
+msgstr "Le compte {0} sera supprimé&nbsp;!\\n\\nTout ce que cet utilisateur a publié sur ce site sera détruit de manière définitive&nbsp;!\\n\\nÊtes-vous sûr&nbsp;?"
-#: ../../Zotlabs/Module/Connedit.php:740
-msgid "Last update:"
-msgstr "Dernière mise à jour&nbsp;:"
+#: ../../Zotlabs/Module/Admin/Logs.php:28
+msgid "Log settings updated."
+msgstr "Paramètres du journal mis à jour."
-#: ../../Zotlabs/Module/Directory.php:63 ../../Zotlabs/Module/Display.php:17
-#: ../../Zotlabs/Module/Photos.php:522 ../../Zotlabs/Module/Ratings.php:86
-#: ../../Zotlabs/Module/Search.php:17
-#: ../../Zotlabs/Module/Viewconnections.php:20
-msgid "Public access denied."
-msgstr "Accès public refusé."
+#: ../../Zotlabs/Module/Admin/Logs.php:83 ../../Zotlabs/Widget/Admin.php:48
+#: ../../Zotlabs/Widget/Admin.php:58
+msgid "Logs"
+msgstr "Journaux"
-#: ../../Zotlabs/Module/Directory.php:243
-#, php-format
-msgid "%d rating"
-msgid_plural "%d ratings"
-msgstr[0] "%d évaluation"
-msgstr[1] "%d évaluations"
+#: ../../Zotlabs/Module/Admin/Logs.php:85
+msgid "Clear"
+msgstr "Vider"
-#: ../../Zotlabs/Module/Directory.php:254
-msgid "Gender: "
-msgstr "Sexe/genre&nbsp;:"
+#: ../../Zotlabs/Module/Admin/Logs.php:91
+msgid "Debugging"
+msgstr "Débogage"
-#: ../../Zotlabs/Module/Directory.php:256
-msgid "Status: "
-msgstr "État&nbsp;:"
+#: ../../Zotlabs/Module/Admin/Logs.php:92
+msgid "Log file"
+msgstr "Fichier du journal"
-#: ../../Zotlabs/Module/Directory.php:258
-msgid "Homepage: "
-msgstr "Site web&nbsp;:"
+#: ../../Zotlabs/Module/Admin/Logs.php:92
+msgid ""
+"Must be writable by web server. Relative to your top-level webserver "
+"directory."
+msgstr "Doit être permettre d'écrire par le serveur web. En relation avec le répertoire de votre site."
-#: ../../Zotlabs/Module/Directory.php:306 ../../include/channel.php:1183
-msgid "Age:"
-msgstr "Age&nbsp;:"
+#: ../../Zotlabs/Module/Admin/Logs.php:93
+msgid "Log level"
+msgstr "Niveau de journalisation"
-#: ../../Zotlabs/Module/Directory.php:311 ../../include/event.php:52
-#: ../../include/event.php:84 ../../include/channel.php:1027
-#: ../../include/bb2diaspora.php:507
-msgid "Location:"
-msgstr "Emplacement&nbsp;:"
+#: ../../Zotlabs/Module/Admin/Channels.php:31
+#, php-format
+msgid "%s channel censored/uncensored"
+msgid_plural "%s channels censored/uncensored"
+msgstr[0] "%s canal censuré/dé-censuré"
+msgstr[1] "%s canaux censurés/dé-censurés"
-#: ../../Zotlabs/Module/Directory.php:317
-msgid "Description:"
-msgstr "Description&nbsp;:"
+#: ../../Zotlabs/Module/Admin/Channels.php:40
+#, php-format
+msgid "%s channel code allowed/disallowed"
+msgid_plural "%s channels code allowed/disallowed"
+msgstr[0] "code autorisé/interdit pour %s canal"
+msgstr[1] "code autorisé/interdit pour %s canaux"
-#: ../../Zotlabs/Module/Directory.php:322 ../../include/channel.php:1199
-msgid "Hometown:"
-msgstr "Ville natale&nbsp;:"
+#: ../../Zotlabs/Module/Admin/Channels.php:46
+#, php-format
+msgid "%s channel deleted"
+msgid_plural "%s channels deleted"
+msgstr[0] "%s canal supprimé"
+msgstr[1] "%s canaux supprimés"
-#: ../../Zotlabs/Module/Directory.php:324 ../../include/channel.php:1207
-msgid "About:"
-msgstr "À propos&nbsp;:"
+#: ../../Zotlabs/Module/Admin/Channels.php:65
+msgid "Channel not found"
+msgstr "Canal introuvable"
-#: ../../Zotlabs/Module/Directory.php:325 ../../Zotlabs/Module/Match.php:68
-#: ../../Zotlabs/Module/Suggest.php:56 ../../include/widgets.php:147
-#: ../../include/widgets.php:184 ../../include/connections.php:78
-#: ../../include/conversation.php:956 ../../include/channel.php:1012
-msgid "Connect"
-msgstr "Ajouter/Suivre"
+#: ../../Zotlabs/Module/Admin/Channels.php:75
+#, php-format
+msgid "Channel '%s' deleted"
+msgstr "Canal '%s' supprimé"
-#: ../../Zotlabs/Module/Directory.php:326
-msgid "Public Forum:"
-msgstr "Forum public&nbsp;:"
+#: ../../Zotlabs/Module/Admin/Channels.php:87
+#, php-format
+msgid "Channel '%s' censored"
+msgstr "Canal '%s' censuré"
-#: ../../Zotlabs/Module/Directory.php:329
-msgid "Keywords: "
-msgstr "Mots-clefs&nbsp;:"
+#: ../../Zotlabs/Module/Admin/Channels.php:87
+#, php-format
+msgid "Channel '%s' uncensored"
+msgstr "Canal '%s' non censuré"
-#: ../../Zotlabs/Module/Directory.php:332
-msgid "Don't suggest"
-msgstr "Ne pas suggérer"
+#: ../../Zotlabs/Module/Admin/Channels.php:98
+#, php-format
+msgid "Channel '%s' code allowed"
+msgstr "Code autorisé pour le canal '%s'"
-#: ../../Zotlabs/Module/Directory.php:334
-msgid "Common connections:"
-msgstr "Contacts en commun&nbsp;:"
+#: ../../Zotlabs/Module/Admin/Channels.php:98
+#, php-format
+msgid "Channel '%s' code disallowed"
+msgstr "Code interdit pour le canal '%s'"
-#: ../../Zotlabs/Module/Directory.php:383
-msgid "Global Directory"
-msgstr "Annuaire global"
+#: ../../Zotlabs/Module/Admin/Channels.php:146
+#: ../../Zotlabs/Widget/Admin.php:24
+msgid "Channels"
+msgstr "Canaux"
-#: ../../Zotlabs/Module/Directory.php:383
-msgid "Local Directory"
-msgstr "Annuaire local"
+#: ../../Zotlabs/Module/Admin/Channels.php:150
+msgid "Censor"
+msgstr "Censurer"
-#: ../../Zotlabs/Module/Directory.php:388
-#: ../../Zotlabs/Module/Directory.php:393
-#: ../../Zotlabs/Module/Connections.php:309
-#: ../../include/contact_widgets.php:23
-msgid "Find"
-msgstr "Trouver"
+#: ../../Zotlabs/Module/Admin/Channels.php:151
+msgid "Uncensor"
+msgstr "Ne plus censurer"
-#: ../../Zotlabs/Module/Directory.php:389
-msgid "Finding:"
-msgstr "Recherche&nbsp;:"
+#: ../../Zotlabs/Module/Admin/Channels.php:152
+msgid "Allow Code"
+msgstr "Autoriser le code"
-#: ../../Zotlabs/Module/Directory.php:392 ../../Zotlabs/Module/Suggest.php:64
-#: ../../include/contact_widgets.php:24
-msgid "Channel Suggestions"
-msgstr "Canaux suggérés"
+#: ../../Zotlabs/Module/Admin/Channels.php:153
+msgid "Disallow Code"
+msgstr "Interdire le code"
-#: ../../Zotlabs/Module/Directory.php:394
-msgid "next page"
-msgstr "page suivante"
+#: ../../Zotlabs/Module/Admin/Channels.php:154
+#: ../../include/conversation.php:1751
+msgid "Channel"
+msgstr "Canal"
-#: ../../Zotlabs/Module/Directory.php:394
-msgid "previous page"
-msgstr "page précédente"
+#: ../../Zotlabs/Module/Admin/Channels.php:158
+msgid "UID"
+msgstr "UID"
-#: ../../Zotlabs/Module/Directory.php:395
-msgid "Sort options"
-msgstr "Options de tri"
+#: ../../Zotlabs/Module/Admin/Channels.php:162
+msgid ""
+"Selected channels will be deleted!\\n\\nEverything that was posted in these "
+"channels on this site will be permanently deleted!\\n\\nAre you sure?"
+msgstr "Les canaux sélectionnés seront supprimés&nbsp;!\\n\\nTout ce qui a été publié dans ces canaux sur ce site sera définitivement supprimé&nbsp;!\\n\\nÊtes-vous sûr&nbsp;?"
-#: ../../Zotlabs/Module/Directory.php:396
-msgid "Alphabetic"
-msgstr "Alphabétique"
+#: ../../Zotlabs/Module/Admin/Channels.php:163
+msgid ""
+"The channel {0} will be deleted!\\n\\nEverything that was posted in this "
+"channel on this site will be permanently deleted!\\n\\nAre you sure?"
+msgstr "Le canal {0} sera supprimé&nbsp;!\\n\\nTout ce qui a été publié sur ce canal sera définitivement supprimé&nbsp;!\\n\\nÊtes-vous sûr(e)&nbsp;?"
-#: ../../Zotlabs/Module/Directory.php:397
-msgid "Reverse Alphabetic"
-msgstr "Alphabétique inversé"
+#: ../../Zotlabs/Module/Admin/Themes.php:26
+msgid "Theme settings updated."
+msgstr "Paramètres du thème mis à jour."
-#: ../../Zotlabs/Module/Directory.php:398
-msgid "Newest to Oldest"
-msgstr "Du plus récent au moins récent"
+#: ../../Zotlabs/Module/Admin/Themes.php:61
+msgid "No themes found."
+msgstr "Aucun thème trouvé."
-#: ../../Zotlabs/Module/Directory.php:399
-msgid "Oldest to Newest"
-msgstr "Du moins récent du plus récent"
+#: ../../Zotlabs/Module/Admin/Themes.php:116
+msgid "Screenshot"
+msgstr "Capture d'écran"
-#: ../../Zotlabs/Module/Directory.php:416
-msgid "No entries (some entries may be hidden)."
-msgstr "Pas d'entrées (certaines peuvent être cachées)."
+#: ../../Zotlabs/Module/Admin/Themes.php:123
+#: ../../Zotlabs/Module/Admin/Themes.php:157 ../../Zotlabs/Widget/Admin.php:28
+msgid "Themes"
+msgstr "Thèmes"
-#: ../../Zotlabs/Module/Display.php:40 ../../Zotlabs/Module/Filestorage.php:33
-#: ../../Zotlabs/Module/Admin.php:164 ../../Zotlabs/Module/Admin.php:1255
-#: ../../Zotlabs/Module/Admin.php:1561 ../../Zotlabs/Module/Thing.php:89
-#: ../../Zotlabs/Module/Viewsrc.php:24 ../../include/items.php:3359
-msgid "Item not found."
-msgstr "Élément introuvable"
+#: ../../Zotlabs/Module/Admin/Themes.php:162
+msgid "[Experimental]"
+msgstr "[Expérimental]"
-#: ../../Zotlabs/Module/Editblock.php:79 ../../Zotlabs/Module/Editblock.php:95
-#: ../../Zotlabs/Module/Editpost.php:24 ../../Zotlabs/Module/Editlayout.php:79
-#: ../../Zotlabs/Module/Editwebpage.php:81
-msgid "Item not found"
-msgstr "Élément introuvable"
+#: ../../Zotlabs/Module/Admin/Themes.php:163
+msgid "[Unsupported]"
+msgstr "[Non maintenu]"
-#: ../../Zotlabs/Module/Editblock.php:124 ../../include/conversation.php:1228
-msgid "Title (optional)"
-msgstr "Titre (facultatif)"
+#: ../../Zotlabs/Module/Admin/Site.php:144
+msgid "Site settings updated."
+msgstr "Paramètres du site sauvegardés."
-#: ../../Zotlabs/Module/Editblock.php:133
-msgid "Edit Block"
-msgstr "Modifier le bloc"
+#: ../../Zotlabs/Module/Admin/Site.php:170 ../../include/text.php:2923
+msgid "Default"
+msgstr "Défaut"
-#: ../../Zotlabs/Module/Common.php:14
-msgid "No channel."
-msgstr "Pas de canal."
+#: ../../Zotlabs/Module/Admin/Site.php:181
+#: ../../Zotlabs/Module/Settings/Display.php:137
+#, php-format
+msgid "%s - (Incompatible)"
+msgstr ""
-#: ../../Zotlabs/Module/Common.php:43
-msgid "Common connections"
-msgstr "Contacts en commun"
+#: ../../Zotlabs/Module/Admin/Site.php:188
+#: ../../Zotlabs/Module/Settings/Display.php:151
+msgid "mobile"
+msgstr "mobile"
-#: ../../Zotlabs/Module/Common.php:48
-msgid "No connections in common."
-msgstr "Pas de contacts en commun."
+#: ../../Zotlabs/Module/Admin/Site.php:190
+msgid "experimental"
+msgstr "expérimental"
-#: ../../Zotlabs/Module/Connections.php:56
-#: ../../Zotlabs/Module/Connections.php:161
-#: ../../Zotlabs/Module/Connections.php:242
-msgid "Blocked"
-msgstr "Bloqué(e)"
+#: ../../Zotlabs/Module/Admin/Site.php:192
+msgid "unsupported"
+msgstr "non maintenu"
-#: ../../Zotlabs/Module/Connections.php:61
-#: ../../Zotlabs/Module/Connections.php:168
-#: ../../Zotlabs/Module/Connections.php:241
-msgid "Ignored"
-msgstr "Ignoré(e)"
+#: ../../Zotlabs/Module/Admin/Site.php:238
+msgid "Yes - with approval"
+msgstr "Oui - avec approbation"
-#: ../../Zotlabs/Module/Connections.php:66
-#: ../../Zotlabs/Module/Connections.php:182
-#: ../../Zotlabs/Module/Connections.php:240
-msgid "Hidden"
-msgstr "Caché"
+#: ../../Zotlabs/Module/Admin/Site.php:244
+msgid "My site is not a public server"
+msgstr "Mon site n'est pas un serveur public"
-#: ../../Zotlabs/Module/Connections.php:71
-#: ../../Zotlabs/Module/Connections.php:175
-#: ../../Zotlabs/Module/Connections.php:239
-msgid "Archived"
-msgstr "Archivé"
+#: ../../Zotlabs/Module/Admin/Site.php:245
+msgid "My site has paid access only"
+msgstr "Mon site est à accès payant uniquement"
-#: ../../Zotlabs/Module/Connections.php:76
-#: ../../Zotlabs/Module/Connections.php:86 ../../Zotlabs/Module/Menu.php:116
-#: ../../include/conversation.php:1535
-msgid "New"
-msgstr "Nouveautés"
+#: ../../Zotlabs/Module/Admin/Site.php:246
+msgid "My site has free access only"
+msgstr "Mon site est gratuit uniquement"
-#: ../../Zotlabs/Module/Connections.php:138
-msgid "New Connections"
-msgstr "Nouveaux contacts"
+#: ../../Zotlabs/Module/Admin/Site.php:247
+msgid "My site offers free accounts with optional paid upgrades"
+msgstr "Mon site offre des comptes gratuits avec des améliorations payantes facultatives"
-#: ../../Zotlabs/Module/Connections.php:141
-msgid "Show pending (new) connections"
-msgstr "Voir les (nouveaux) contacts en attente"
+#: ../../Zotlabs/Module/Admin/Site.php:264 ../../Zotlabs/Lib/Techlevels.php:10
+msgid "Beginner/Basic"
+msgstr "Pour débutant/ de base"
-#: ../../Zotlabs/Module/Connections.php:145
-#: ../../Zotlabs/Module/Profperm.php:144
-msgid "All Connections"
-msgstr "Tous les contacts"
+#: ../../Zotlabs/Module/Admin/Site.php:265 ../../Zotlabs/Lib/Techlevels.php:11
+msgid "Novice - not skilled but willing to learn"
+msgstr "Novice - pas qualifiés, mais prêt à apprendre"
-#: ../../Zotlabs/Module/Connections.php:148
-msgid "Show all connections"
-msgstr "Voir tous les contacts"
+#: ../../Zotlabs/Module/Admin/Site.php:266 ../../Zotlabs/Lib/Techlevels.php:12
+msgid "Intermediate - somewhat comfortable"
+msgstr "Intermédiaire - assez confortable"
-#: ../../Zotlabs/Module/Connections.php:164
-msgid "Only show blocked connections"
-msgstr "Ne montrer que les contacts bloqués"
+#: ../../Zotlabs/Module/Admin/Site.php:267 ../../Zotlabs/Lib/Techlevels.php:13
+msgid "Advanced - very comfortable"
+msgstr "Niveau avancé - trés confortable"
-#: ../../Zotlabs/Module/Connections.php:171
-msgid "Only show ignored connections"
-msgstr "Ne montrer que les contacts ignorés"
+#: ../../Zotlabs/Module/Admin/Site.php:268 ../../Zotlabs/Lib/Techlevels.php:14
+msgid "Expert - I can write computer code"
+msgstr "Niveau expert - Je peux programmer"
-#: ../../Zotlabs/Module/Connections.php:178
-msgid "Only show archived connections"
-msgstr "Ne montrer que les contacts archivés"
+#: ../../Zotlabs/Module/Admin/Site.php:269 ../../Zotlabs/Lib/Techlevels.php:15
+msgid "Wizard - I probably know more than you do"
+msgstr "Crack - J'en sais probablement plus que beaucoup"
-#: ../../Zotlabs/Module/Connections.php:185
-msgid "Only show hidden connections"
-msgstr "Ne montrer que les contacts cachés"
+#: ../../Zotlabs/Module/Admin/Site.php:278 ../../Zotlabs/Widget/Admin.php:22
+msgid "Site"
+msgstr "Site"
-#: ../../Zotlabs/Module/Connections.php:238
-msgid "Pending approval"
-msgstr "En attente de validation"
+#: ../../Zotlabs/Module/Admin/Site.php:280
+#: ../../Zotlabs/Module/Register.php:253
+msgid "Registration"
+msgstr "Inscription"
-#: ../../Zotlabs/Module/Connections.php:254
-#, php-format
-msgid "%1$s [%2$s]"
-msgstr "%1$s [%2$s]"
+#: ../../Zotlabs/Module/Admin/Site.php:281
+msgid "File upload"
+msgstr "Envoi de fichier"
-#: ../../Zotlabs/Module/Connections.php:255
-msgid "Edit connection"
-msgstr "Modifier le contact"
+#: ../../Zotlabs/Module/Admin/Site.php:282
+msgid "Policies"
+msgstr "Stratégies"
-#: ../../Zotlabs/Module/Connections.php:256
-msgid "Delete connection"
-msgstr "Supprimer le contact"
+#: ../../Zotlabs/Module/Admin/Site.php:283
+#: ../../include/contact_widgets.php:16
+msgid "Advanced"
+msgstr "Avancé"
-#: ../../Zotlabs/Module/Connections.php:265
-msgid "Channel address"
-msgstr "Adresse du canal"
+#: ../../Zotlabs/Module/Admin/Site.php:287
+#: ../../addon/statusnet/statusnet.php:890
+msgid "Site name"
+msgstr "Nom du site"
-#: ../../Zotlabs/Module/Connections.php:267
-msgid "Network"
-msgstr "Réseau"
+#: ../../Zotlabs/Module/Admin/Site.php:291
+msgid "Site default technical skill level"
+msgstr "Niveau technique par défaut pour le site"
-#: ../../Zotlabs/Module/Connections.php:270 ../../Zotlabs/Module/Admin.php:710
-msgid "Status"
-msgstr "État"
+#: ../../Zotlabs/Module/Admin/Site.php:291
+msgid "Used to provide a member experience matched to technical comfort level"
+msgstr "Utilisé pour fournir une expérience utilisateur correspondant au niveau de confort technique"
-#: ../../Zotlabs/Module/Connections.php:272
-msgid "Connected"
-msgstr "Connecté"
+#: ../../Zotlabs/Module/Admin/Site.php:293
+msgid "Lock the technical skill level setting"
+msgstr "Bloque le niveau technique du paramétrage"
-#: ../../Zotlabs/Module/Connections.php:274
-msgid "Approve connection"
-msgstr "Valider le contact"
+#: ../../Zotlabs/Module/Admin/Site.php:293
+msgid "Members can set their own technical comfort level by default"
+msgstr "Les utilisateurs peuvent paramétrer leur propre niveau technique."
-#: ../../Zotlabs/Module/Connections.php:275
-#: ../../Zotlabs/Module/Admin.php:1037
-msgid "Approve"
-msgstr "Approuver"
+#: ../../Zotlabs/Module/Admin/Site.php:295
+msgid "Banner/Logo"
+msgstr "Bannière/logo"
-#: ../../Zotlabs/Module/Connections.php:276
-msgid "Ignore connection"
-msgstr "Ignorer le contact"
+#: ../../Zotlabs/Module/Admin/Site.php:296
+msgid "Administrator Information"
+msgstr "Informations de l'administrateur"
-#: ../../Zotlabs/Module/Connections.php:278
-msgid "Recent activity"
-msgstr "Activité récente"
+#: ../../Zotlabs/Module/Admin/Site.php:296
+msgid ""
+"Contact information for site administrators. Displayed on siteinfo page. "
+"BBCode can be used here"
+msgstr "Coordonnées de l'administrateur du site. Affichées sur la page 'siteinfo'. Vous pouvez utiliser du BBCode ici"
-#: ../../Zotlabs/Module/Connections.php:302 ../../Zotlabs/Lib/Apps.php:208
-#: ../../include/text.php:875 ../../include/nav.php:186
-msgid "Connections"
-msgstr "Contacts"
+#: ../../Zotlabs/Module/Admin/Site.php:297
+#: ../../Zotlabs/Module/Siteinfo.php:23
+msgid "Site Information"
+msgstr "Site information"
-#: ../../Zotlabs/Module/Connections.php:306 ../../Zotlabs/Module/Search.php:44
-#: ../../Zotlabs/Lib/Apps.php:228 ../../include/text.php:945
-#: ../../include/text.php:957 ../../include/nav.php:165
-#: ../../include/acl_selectors.php:276
-msgid "Search"
-msgstr "Recherche"
+#: ../../Zotlabs/Module/Admin/Site.php:297
+msgid ""
+"Publicly visible description of this site. Displayed on siteinfo page. "
+"BBCode can be used here"
+msgstr "Description du site visible publiquement. Affiché sur la page d'information du site. BBCode peut être utilisé ici."
-#: ../../Zotlabs/Module/Connections.php:307
-msgid "Search your connections"
-msgstr "Chercher parmi vos contacts"
+#: ../../Zotlabs/Module/Admin/Site.php:298
+msgid "System language"
+msgstr "Langue du système"
-#: ../../Zotlabs/Module/Connections.php:308
-msgid "Connections search"
-msgstr "Chercher des contacts"
+#: ../../Zotlabs/Module/Admin/Site.php:299
+msgid "System theme"
+msgstr "Thème du système"
-#: ../../Zotlabs/Module/Cover_photo.php:58
-#: ../../Zotlabs/Module/Profile_photo.php:79
-msgid "Image uploaded but image cropping failed."
-msgstr "L'image a été téléversée, mais le recadrage a échoué."
+#: ../../Zotlabs/Module/Admin/Site.php:299
+msgid ""
+"Default system theme - may be over-ridden by user profiles - <a href='#' "
+"id='cnftheme'>change theme settings</a>"
+msgstr "Thème par défaut - il peut être changé pour chaque profil utilisateur - <a href='#' id='cnftheme'>modifier le thème</a>"
-#: ../../Zotlabs/Module/Cover_photo.php:134
-#: ../../Zotlabs/Module/Cover_photo.php:181
-msgid "Cover Photos"
-msgstr "Photos de couverture"
+#: ../../Zotlabs/Module/Admin/Site.php:300
+msgid "Mobile system theme"
+msgstr "Thème par défaut pour les mobiles"
-#: ../../Zotlabs/Module/Cover_photo.php:154
-#: ../../Zotlabs/Module/Profile_photo.php:133
-msgid "Image resize failed."
-msgstr "Le redimensionnement de l'image a échoué."
+#: ../../Zotlabs/Module/Admin/Site.php:300
+msgid "Theme for mobile devices"
+msgstr "Thème pour les mobiles"
-#: ../../Zotlabs/Module/Cover_photo.php:168
-#: ../../Zotlabs/Module/Profile_photo.php:192 ../../include/photos.php:144
-msgid "Unable to process image"
-msgstr "Impossible de traiter l'image"
+#: ../../Zotlabs/Module/Admin/Site.php:302
+msgid "Allow Feeds as Connections"
+msgstr "Autoriser les Flux (RSS) comme contacts"
-#: ../../Zotlabs/Module/Cover_photo.php:192
-#: ../../Zotlabs/Module/Profile_photo.php:217
-msgid "Image upload failed."
-msgstr "Le téléversement de l'image a échoué."
+#: ../../Zotlabs/Module/Admin/Site.php:302
+msgid "(Heavy system resource usage)"
+msgstr "(Impact important sur les ressources)"
-#: ../../Zotlabs/Module/Cover_photo.php:210
-#: ../../Zotlabs/Module/Profile_photo.php:236
-msgid "Unable to process image."
-msgstr "Impossible de traîter l'image."
+#: ../../Zotlabs/Module/Admin/Site.php:303
+msgid "Maximum image size"
+msgstr "Taille maximale des images"
-#: ../../Zotlabs/Module/Cover_photo.php:233 ../../include/items.php:4270
-msgid "female"
-msgstr "femme"
+#: ../../Zotlabs/Module/Admin/Site.php:303
+msgid ""
+"Maximum size in bytes of uploaded images. Default is 0, which means no "
+"limits."
+msgstr "Taille maximum, en octets, des images envoyées. Par défaut 0, soit sans limite."
-#: ../../Zotlabs/Module/Cover_photo.php:234 ../../include/items.php:4271
-#, php-format
-msgid "%1$s updated her %2$s"
-msgstr "%1$s a mis à jour son %2$s"
+#: ../../Zotlabs/Module/Admin/Site.php:304
+msgid "Does this site allow new member registration?"
+msgstr "Est-ce que l'enregistrement de nouveaux membres est autorisé sur ce site&nbsp;?"
-#: ../../Zotlabs/Module/Cover_photo.php:235 ../../include/items.php:4272
-msgid "male"
-msgstr "homme"
+#: ../../Zotlabs/Module/Admin/Site.php:305
+msgid "Invitation only"
+msgstr "Sur invitation seulement"
-#: ../../Zotlabs/Module/Cover_photo.php:236 ../../include/items.php:4273
-#, php-format
-msgid "%1$s updated his %2$s"
-msgstr "%1$s a mis à jour son %2$s"
+#: ../../Zotlabs/Module/Admin/Site.php:305
+msgid ""
+"Only allow new member registrations with an invitation code. Above register "
+"policy must be set to Yes."
+msgstr "N'autoriser que les nouvelles inscriptions avec code d'invitation. La stratégie d'inscription ci-dessus doit être mise sur \"Oui\"."
-#: ../../Zotlabs/Module/Cover_photo.php:238 ../../include/items.php:4275
-#, php-format
-msgid "%1$s updated their %2$s"
-msgstr "%1$s a mis a jour sa %2$s"
+#: ../../Zotlabs/Module/Admin/Site.php:306
+msgid "Which best describes the types of account offered by this hub?"
+msgstr "Quelle est la meilleure description des types de comptes proposés sur ce hub&nbsp;?"
-#: ../../Zotlabs/Module/Cover_photo.php:240 ../../include/channel.php:1661
-msgid "cover photo"
-msgstr "Photo principale"
+#: ../../Zotlabs/Module/Admin/Site.php:307
+msgid "Register text"
+msgstr "Texte d'inscription"
-#: ../../Zotlabs/Module/Cover_photo.php:303
-#: ../../Zotlabs/Module/Cover_photo.php:318
-#: ../../Zotlabs/Module/Profile_photo.php:283
-#: ../../Zotlabs/Module/Profile_photo.php:324
-msgid "Photo not available."
-msgstr "Photo inaccessible."
+#: ../../Zotlabs/Module/Admin/Site.php:307
+msgid "Will be displayed prominently on the registration page."
+msgstr "Sera affiché de manière bien visible sur le formulaire d'inscription."
-#: ../../Zotlabs/Module/Cover_photo.php:354
-#: ../../Zotlabs/Module/Profile_photo.php:365
-msgid "Upload File:"
-msgstr "Téléverser fichier&nbsp;:"
+#: ../../Zotlabs/Module/Admin/Site.php:308
+msgid "Site homepage to show visitors (default: login box)"
+msgstr "Page d'accueil du site à montrer aux visiteurs (par défaut&nbsp;: boîte de dialogue de connexion)"
-#: ../../Zotlabs/Module/Cover_photo.php:355
-#: ../../Zotlabs/Module/Profile_photo.php:366
-msgid "Select a profile:"
-msgstr "Choisir un profil&nbsp;:"
+#: ../../Zotlabs/Module/Admin/Site.php:308
+msgid ""
+"example: 'public' to show public stream, 'page/sys/home' to show a system "
+"webpage called 'home' or 'include:home.html' to include a file."
+msgstr "exemple&nbsp;:'public' pour montrer le flux public, 'page/sys/home' pour montrer une page système appelée 'home' ou 'include:home.html' pour inclure un fichier."
-#: ../../Zotlabs/Module/Cover_photo.php:356
-msgid "Upload Cover Photo"
-msgstr "Téléverser une photo de couverture"
+#: ../../Zotlabs/Module/Admin/Site.php:309
+msgid "Preserve site homepage URL"
+msgstr "Préserver l'adresse d'accueil du site"
-#: ../../Zotlabs/Module/Cover_photo.php:361
-#: ../../Zotlabs/Module/Profile_photo.php:374
-#: ../../Zotlabs/Module/Settings.php:985
-msgid "or"
-msgstr "ou"
+#: ../../Zotlabs/Module/Admin/Site.php:309
+msgid ""
+"Present the site homepage in a frame at the original location instead of "
+"redirecting"
+msgstr "Présenter la page d'accueil du site dans un cadre à l'adresse d'origine, plutôt que de rediriger"
-#: ../../Zotlabs/Module/Cover_photo.php:361
-#: ../../Zotlabs/Module/Profile_photo.php:374
-msgid "skip this step"
-msgstr "passer cette étape"
+#: ../../Zotlabs/Module/Admin/Site.php:310
+msgid "Accounts abandoned after x days"
+msgstr "Les comptes sont abandonnés après x jours"
-#: ../../Zotlabs/Module/Cover_photo.php:361
-#: ../../Zotlabs/Module/Profile_photo.php:374
-msgid "select a photo from your photo albums"
-msgstr "choisir une photo dans vos albums"
+#: ../../Zotlabs/Module/Admin/Site.php:310
+msgid ""
+"Will not waste system resources polling external sites for abandonded "
+"accounts. Enter 0 for no time limit."
+msgstr "Eviter de gaspiller les ressources du système en interrogeant des hubs distants pour des canaux abandonnés. Mettez 0 pour ne pas avoir de limite de temps."
-#: ../../Zotlabs/Module/Cover_photo.php:377
-#: ../../Zotlabs/Module/Profile_photo.php:390
-msgid "Crop Image"
-msgstr "Recadrer l'image"
+#: ../../Zotlabs/Module/Admin/Site.php:311
+msgid "Allowed friend domains"
+msgstr "Domaines amicaux autorisés"
-#: ../../Zotlabs/Module/Cover_photo.php:378
-#: ../../Zotlabs/Module/Profile_photo.php:391
-msgid "Please adjust the image cropping for optimum viewing."
-msgstr "Merci d'ajuster le cadre pour une visualisation optimale."
+#: ../../Zotlabs/Module/Admin/Site.php:311
+msgid ""
+"Comma separated list of domains which are allowed to establish friendships "
+"with this site. Wildcards are accepted. Empty to allow any domains"
+msgstr "Liste de noms de domaines séparés par des virgules pour lesquels ce site acceptera les demandes d'amitié. Les caractères génériques (*) sont acceptés. Laissez vide pour accepter tous les domaines."
-#: ../../Zotlabs/Module/Cover_photo.php:380
-#: ../../Zotlabs/Module/Profile_photo.php:393
-msgid "Done Editing"
-msgstr "J'ai terminé"
+#: ../../Zotlabs/Module/Admin/Site.php:312
+msgid "Verify Email Addresses"
+msgstr "Demander vérification des adresses de courriel"
-#: ../../Zotlabs/Module/Editpost.php:35
-msgid "Item is not editable"
-msgstr "Elément non modifiable"
+#: ../../Zotlabs/Module/Admin/Site.php:312
+msgid ""
+"Check to verify email addresses used in account registration (recommended)."
+msgstr "Cocher pour que les adresses utilisées à l'inscription soient vérifiées (recommandé)."
-#: ../../Zotlabs/Module/Editpost.php:106 ../../Zotlabs/Module/Rpost.php:135
-msgid "Edit post"
-msgstr "Modifier la publication"
+#: ../../Zotlabs/Module/Admin/Site.php:313
+msgid "Force publish"
+msgstr "Publicité forcée"
-#: ../../Zotlabs/Module/Events.php:26
-msgid "Calendar entries imported."
-msgstr "Entrées du calendrier importées."
+#: ../../Zotlabs/Module/Admin/Site.php:313
+msgid ""
+"Check to force all profiles on this site to be listed in the site directory."
+msgstr "Cocher pour forcer la publication de tous les profils du site dans l'annuaire."
-#: ../../Zotlabs/Module/Events.php:28
-msgid "No calendar entries found."
-msgstr "Aucune entrée du calendrier trouvée."
+#: ../../Zotlabs/Module/Admin/Site.php:314
+msgid "Import Public Streams"
+msgstr "Flux publics importés"
-#: ../../Zotlabs/Module/Events.php:105
-msgid "Event can not end before it has started."
-msgstr "La fin de l'événement ne peut être antérieure à son début."
+#: ../../Zotlabs/Module/Admin/Site.php:314
+msgid ""
+"Import and allow access to public content pulled from other sites. Warning: "
+"this content is unmoderated."
+msgstr "Importer du contenu public à partir d'autres sites et autoriser l'accès à ce contenu. Attention&nbsp;: ce contenu n'est pas modéré."
-#: ../../Zotlabs/Module/Events.php:107 ../../Zotlabs/Module/Events.php:116
-#: ../../Zotlabs/Module/Events.php:136
-msgid "Unable to generate preview."
-msgstr "Impossible de générer l'aperçu."
+#: ../../Zotlabs/Module/Admin/Site.php:315
+msgid "Login on Homepage"
+msgstr "Connexion sur la page d'accueil"
-#: ../../Zotlabs/Module/Events.php:114
-msgid "Event title and start time are required."
-msgstr "Un titre et une date de début sont requises pour l'événement."
+#: ../../Zotlabs/Module/Admin/Site.php:315
+msgid ""
+"Present a login box to visitors on the home page if no other content has "
+"been configured."
+msgstr "Présenter une boîte de dialogue de connexion aux visiteurs sur la page d'accueil si aucun autre contenu n'a été configuré."
-#: ../../Zotlabs/Module/Events.php:134 ../../Zotlabs/Module/Events.php:259
-msgid "Event not found."
-msgstr "Événement introuvable."
+#: ../../Zotlabs/Module/Admin/Site.php:316
+msgid "Enable context help"
+msgstr "Permettre l'aide contextuelle"
-#: ../../Zotlabs/Module/Events.php:254 ../../Zotlabs/Module/Like.php:373
-#: ../../Zotlabs/Module/Tagger.php:51 ../../include/event.php:949
-#: ../../include/text.php:1943 ../../include/conversation.php:123
-msgid "event"
-msgstr "événement"
+#: ../../Zotlabs/Module/Admin/Site.php:316
+msgid ""
+"Display contextual help for the current page when the help button is "
+"pressed."
+msgstr "Afficher l'aide contextuel en cliquant sur le bouton aide."
-#: ../../Zotlabs/Module/Events.php:449
-msgid "Edit event title"
-msgstr "Modifier le titre de l'événement"
+#: ../../Zotlabs/Module/Admin/Site.php:318
+msgid "Reply-to email address for system generated email."
+msgstr ""
-#: ../../Zotlabs/Module/Events.php:449
-msgid "Event title"
-msgstr "Titre de l'événement"
+#: ../../Zotlabs/Module/Admin/Site.php:319
+msgid "Sender (From) email address for system generated email."
+msgstr ""
-#: ../../Zotlabs/Module/Events.php:449 ../../Zotlabs/Module/Events.php:454
-#: ../../Zotlabs/Module/Profiles.php:709 ../../Zotlabs/Module/Profiles.php:713
-#: ../../Zotlabs/Module/Appman.php:115 ../../Zotlabs/Module/Appman.php:116
-#: ../../include/datetime.php:245
-msgid "Required"
-msgstr "Requis"
+#: ../../Zotlabs/Module/Admin/Site.php:320
+msgid "Name of email sender for system generated email."
+msgstr ""
-#: ../../Zotlabs/Module/Events.php:451
-msgid "Categories (comma-separated list)"
-msgstr "Catégories (séparées par des virgules)"
+#: ../../Zotlabs/Module/Admin/Site.php:322
+msgid "Directory Server URL"
+msgstr "URL du serveur d'annuaire"
-#: ../../Zotlabs/Module/Events.php:452
-msgid "Edit Category"
-msgstr "Modifier la catégorie"
+#: ../../Zotlabs/Module/Admin/Site.php:322
+msgid "Default directory server"
+msgstr "Serveur d'annuaire par défaut"
-#: ../../Zotlabs/Module/Events.php:452
-msgid "Category"
-msgstr "Catégorie"
+#: ../../Zotlabs/Module/Admin/Site.php:324
+msgid "Proxy user"
+msgstr "Utilisateur du proxy"
-#: ../../Zotlabs/Module/Events.php:455
-msgid "Edit start date and time"
-msgstr "Modifier la date et l'heure de début"
+#: ../../Zotlabs/Module/Admin/Site.php:325
+msgid "Proxy URL"
+msgstr "URL du proxy"
-#: ../../Zotlabs/Module/Events.php:455
-msgid "Start date and time"
-msgstr "Date et heure de début"
+#: ../../Zotlabs/Module/Admin/Site.php:326
+msgid "Network timeout"
+msgstr "Délai maximal du réseau"
-#: ../../Zotlabs/Module/Events.php:456 ../../Zotlabs/Module/Events.php:459
-msgid "Finish date and time are not known or not relevant"
-msgstr "Date et heure de fin inconnues ou sans objet"
+#: ../../Zotlabs/Module/Admin/Site.php:326
+msgid "Value is in seconds. Set to 0 for unlimited (not recommended)."
+msgstr "En secondes. Mettre à 0 pour ne pas avoir de délai maximal (non recommandé)."
-#: ../../Zotlabs/Module/Events.php:458
-msgid "Edit finish date and time"
-msgstr "Modifier la date et l'heure de fin"
+#: ../../Zotlabs/Module/Admin/Site.php:327
+msgid "Delivery interval"
+msgstr "Intervalle de distribution"
-#: ../../Zotlabs/Module/Events.php:458
-msgid "Finish date and time"
-msgstr "Date et heure de fin"
+#: ../../Zotlabs/Module/Admin/Site.php:327
+msgid ""
+"Delay background delivery processes by this many seconds to reduce system "
+"load. Recommend: 4-5 for shared hosts, 2-3 for virtual private servers. 0-1 "
+"for large dedicated servers."
+msgstr "Temporise le processus de distribution de tant de secondes pour réduire la charge sur le système. Valeurs recommandées&nbsp;: 4-5 pour les serveurs mutualisés, 2-3 pour les VPS. 0-1 pour les gros serveurs dédiés."
-#: ../../Zotlabs/Module/Events.php:460 ../../Zotlabs/Module/Events.php:461
-msgid "Adjust for viewer timezone"
-msgstr "Ajuster au fuseau horaire du visiteur"
+#: ../../Zotlabs/Module/Admin/Site.php:328
+msgid "Deliveries per process"
+msgstr "Distributions par processus"
-#: ../../Zotlabs/Module/Events.php:460
+#: ../../Zotlabs/Module/Admin/Site.php:328
msgid ""
-"Important for events that happen in a particular place. Not practical for "
-"global holidays."
-msgstr "Important pour les événements se tenant en un lieu particulier. Pas pratique pour les vacances communes à de nombreux pays dans le monde."
+"Number of deliveries to attempt in a single operating system process. Adjust"
+" if necessary to tune system performance. Recommend: 1-5."
+msgstr "Nombre de distributions à tenter au sein d'un seul processus système. Ajuster si nécessaire pour affiner la performance du système. Recommandé&nbsp;:1-5."
-#: ../../Zotlabs/Module/Events.php:462
-msgid "Edit Description"
-msgstr "Modifier la description"
+#: ../../Zotlabs/Module/Admin/Site.php:329
+msgid "Poll interval"
+msgstr "Intervalle de scrutation"
-#: ../../Zotlabs/Module/Events.php:462 ../../Zotlabs/Module/Appman.php:117
-#: ../../Zotlabs/Module/Rbmark.php:101
-msgid "Description"
-msgstr "Description"
+#: ../../Zotlabs/Module/Admin/Site.php:329
+msgid ""
+"Delay background polling processes by this many seconds to reduce system "
+"load. If 0, use delivery interval."
+msgstr "Temporise le processus de scrutation en tâche de fond de tant de secondes, pour réduire la charge. Si 0, utilise l'intervalle de distribution."
-#: ../../Zotlabs/Module/Events.php:464
-msgid "Edit Location"
-msgstr "Modifier l'emplacement"
+#: ../../Zotlabs/Module/Admin/Site.php:330
+msgid "Maximum Load Average"
+msgstr "Charge maximale moyenne"
-#: ../../Zotlabs/Module/Events.php:464 ../../Zotlabs/Module/Locs.php:117
-#: ../../Zotlabs/Module/Profiles.php:477 ../../Zotlabs/Module/Profiles.php:698
-#: ../../Zotlabs/Module/Pubsites.php:41 ../../include/js_strings.php:25
-msgid "Location"
-msgstr "Emplacement"
+#: ../../Zotlabs/Module/Admin/Site.php:330
+msgid ""
+"Maximum system load before delivery and poll processes are deferred - "
+"default 50."
+msgstr "Charge système maximale au-delà de laquelle distribution et scrutation sont reportées - par défaut 50."
-#: ../../Zotlabs/Module/Events.php:467 ../../Zotlabs/Module/Events.php:469
-msgid "Share this event"
-msgstr "Partager cet événement"
+#: ../../Zotlabs/Module/Admin/Site.php:331
+msgid "Expiration period in days for imported (grid/network) content"
+msgstr "Délai d'expiration pour le contenu importé (réseau)"
-#: ../../Zotlabs/Module/Events.php:470 ../../Zotlabs/Module/Photos.php:1093
-#: ../../Zotlabs/Module/Webpages.php:194 ../../Zotlabs/Lib/ThreadItem.php:719
-#: ../../include/conversation.php:1187 ../../include/page_widgets.php:40
-msgid "Preview"
-msgstr "Aperçu"
+#: ../../Zotlabs/Module/Admin/Site.php:331
+msgid "0 for no expiration of imported content"
+msgstr "0 pour ne pas expirer le contenu importé"
-#: ../../Zotlabs/Module/Events.php:471 ../../include/conversation.php:1232
-msgid "Permission settings"
-msgstr "Gérer les autorisations"
+#: ../../Zotlabs/Module/Admin/Profs.php:69
+msgid "New Profile Field"
+msgstr "Nouveau champ de profil"
-#: ../../Zotlabs/Module/Events.php:476
-msgid "Advanced Options"
-msgstr "Options avancées"
+#: ../../Zotlabs/Module/Admin/Profs.php:70
+#: ../../Zotlabs/Module/Admin/Profs.php:90
+msgid "Field nickname"
+msgstr "Nom court du champ"
-#: ../../Zotlabs/Module/Events.php:610
-msgid "Edit event"
-msgstr "Modifier l'événement"
+#: ../../Zotlabs/Module/Admin/Profs.php:70
+#: ../../Zotlabs/Module/Admin/Profs.php:90
+msgid "System name of field"
+msgstr "Nom système du champ"
-#: ../../Zotlabs/Module/Events.php:612
-msgid "Delete event"
-msgstr "Supprimer l'événement"
+#: ../../Zotlabs/Module/Admin/Profs.php:71
+#: ../../Zotlabs/Module/Admin/Profs.php:91
+msgid "Input type"
+msgstr "Type de champ"
-#: ../../Zotlabs/Module/Events.php:646
-msgid "calendar"
-msgstr "calendrier"
+#: ../../Zotlabs/Module/Admin/Profs.php:72
+#: ../../Zotlabs/Module/Admin/Profs.php:92
+msgid "Field Name"
+msgstr "Nom du champ"
-#: ../../Zotlabs/Module/Events.php:706
-msgid "Event removed"
-msgstr "Événement supprimé"
+#: ../../Zotlabs/Module/Admin/Profs.php:72
+#: ../../Zotlabs/Module/Admin/Profs.php:92
+msgid "Label on profile pages"
+msgstr "Étiquette sur les pages de profil"
-#: ../../Zotlabs/Module/Events.php:709
-msgid "Failed to remove event"
-msgstr "Impossible de supprimer l'événement"
+#: ../../Zotlabs/Module/Admin/Profs.php:73
+#: ../../Zotlabs/Module/Admin/Profs.php:93
+msgid "Help text"
+msgstr "Aide à la saisie"
-#: ../../Zotlabs/Module/Fbrowser.php:29 ../../Zotlabs/Lib/Apps.php:220
-#: ../../include/nav.php:92 ../../include/conversation.php:1632
-msgid "Photos"
-msgstr "Photos"
+#: ../../Zotlabs/Module/Admin/Profs.php:73
+#: ../../Zotlabs/Module/Admin/Profs.php:93
+msgid "Additional info (optional)"
+msgstr "Informations additionnelles (facultatif)"
-#: ../../Zotlabs/Module/Fbrowser.php:66 ../../Zotlabs/Module/Fbrowser.php:88
-#: ../../Zotlabs/Module/Admin.php:1406 ../../Zotlabs/Module/Settings.php:591
-#: ../../Zotlabs/Module/Settings.php:617 ../../Zotlabs/Module/Tagrm.php:15
-#: ../../Zotlabs/Module/Tagrm.php:138 ../../include/conversation.php:1259
-msgid "Cancel"
-msgstr "Annuler"
+#: ../../Zotlabs/Module/Admin/Profs.php:74
+#: ../../Zotlabs/Module/Admin/Profs.php:94 ../../Zotlabs/Module/Rbmark.php:32
+#: ../../Zotlabs/Module/Rbmark.php:104 ../../Zotlabs/Module/Filer.php:53
+#: ../../Zotlabs/Widget/Notes.php:18 ../../include/text.php:1028
+#: ../../include/text.php:1040
+msgid "Save"
+msgstr "Enregistrer"
-#: ../../Zotlabs/Module/Dirsearch.php:25 ../../Zotlabs/Module/Regdir.php:49
-msgid "This site is not a directory server"
-msgstr "Ce site n'est pas un serveur d'annuaire"
+#: ../../Zotlabs/Module/Admin/Profs.php:83
+msgid "Field definition not found"
+msgstr "Définition du champ introuvable"
-#: ../../Zotlabs/Module/Dirsearch.php:33
-msgid "This directory server requires an access token"
-msgstr "Ce serveur d'annuaire requiert un jeton d'accès"
+#: ../../Zotlabs/Module/Admin/Profs.php:89
+msgid "Edit Profile Field"
+msgstr "Modifier le champ de profil"
-#: ../../Zotlabs/Module/Filer.php:52
-msgid "Save to Folder:"
-msgstr "Classer dans le dossier&nbsp;:"
+#: ../../Zotlabs/Module/Admin/Profs.php:147 ../../Zotlabs/Widget/Admin.php:30
+msgid "Profile Fields"
+msgstr "Champs de profil"
-#: ../../Zotlabs/Module/Filer.php:52
-msgid "- select -"
-msgstr "- choisir -"
+#: ../../Zotlabs/Module/Admin/Profs.php:148
+msgid "Basic Profile Fields"
+msgstr "Champs de profil de base"
-#: ../../Zotlabs/Module/Filer.php:53 ../../Zotlabs/Module/Admin.php:2033
-#: ../../Zotlabs/Module/Admin.php:2053 ../../Zotlabs/Module/Rbmark.php:32
-#: ../../Zotlabs/Module/Rbmark.php:104 ../../include/text.php:946
-#: ../../include/text.php:958 ../../include/widgets.php:201
-msgid "Save"
-msgstr "Enregistrer"
+#: ../../Zotlabs/Module/Admin/Profs.php:149
+msgid "Advanced Profile Fields"
+msgstr "Champs de profil avancés"
-#: ../../Zotlabs/Module/Dreport.php:27
-msgid "Invalid message"
-msgstr "Message non valide"
+#: ../../Zotlabs/Module/Admin/Profs.php:149
+msgid "(In addition to basic fields)"
+msgstr "(en plus des champs de base)"
-#: ../../Zotlabs/Module/Dreport.php:59
-msgid "no results"
-msgstr "aucun résultat"
+#: ../../Zotlabs/Module/Admin/Profs.php:151
+msgid "All available fields"
+msgstr "Tous les champs disponibles"
-#: ../../Zotlabs/Module/Dreport.php:64
-#, php-format
-msgid "Delivery report for %1$s"
-msgstr "Rapport de distribution pour %1$s"
+#: ../../Zotlabs/Module/Admin/Profs.php:152
+msgid "Custom Fields"
+msgstr "Champs personnalisés"
-#: ../../Zotlabs/Module/Dreport.php:78
-msgid "channel sync processed"
-msgstr "Synchro de canal effectuée"
+#: ../../Zotlabs/Module/Admin/Profs.php:156
+msgid "Create Custom Field"
+msgstr "Créer un champ personnalisé"
-#: ../../Zotlabs/Module/Dreport.php:82
-msgid "queued"
-msgstr "mis dans la file d'attente"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:29
+#, php-format
+msgid "Password changed for account %d."
+msgstr "Le mot de passe a été modifié pour le compte %d."
-#: ../../Zotlabs/Module/Dreport.php:86
-msgid "posted"
-msgstr "publié"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:46
+msgid "Account settings updated."
+msgstr "Paramétrage du compte mis à jour"
-#: ../../Zotlabs/Module/Dreport.php:90
-msgid "accepted for delivery"
-msgstr "accepté pour la distribution"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:61
+msgid "Account not found."
+msgstr "Compte introuvable"
-#: ../../Zotlabs/Module/Dreport.php:94
-msgid "updated"
-msgstr "mis à jour"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:68
+msgid "Account Edit"
+msgstr "Modifier votre compte"
-#: ../../Zotlabs/Module/Dreport.php:97
-msgid "update ignored"
-msgstr "mise à jour ignorée"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:69
+msgid "New Password"
+msgstr "Nouveau mot de passe"
-#: ../../Zotlabs/Module/Dreport.php:100
-msgid "permission denied"
-msgstr "permission refusée"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:70
+msgid "New Password again"
+msgstr "Nouveau mot de passe (encore)"
-#: ../../Zotlabs/Module/Dreport.php:104
-msgid "recipient not found"
-msgstr "destinataire introuvable"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:71
+msgid "Technical skill level"
+msgstr "Niveau technique"
-#: ../../Zotlabs/Module/Dreport.php:107
-msgid "mail recalled"
-msgstr "courriel rappelé"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:72
+msgid "Account language (for emails)"
+msgstr "Langue de votre compte (pour email)"
-#: ../../Zotlabs/Module/Dreport.php:110
-msgid "duplicate mail received"
-msgstr "courriel reçu en double"
+#: ../../Zotlabs/Module/Admin/Account_edit.php:73
+msgid "Service class"
+msgstr "Classe de service"
-#: ../../Zotlabs/Module/Dreport.php:113
-msgid "mail delivered"
-msgstr "courriel distribué"
+#: ../../Zotlabs/Module/Admin/Security.php:77
+msgid ""
+"By default, unfiltered HTML is allowed in embedded media. This is inherently"
+" insecure."
+msgstr "Par défaut le code HTML est autorisé pour les média par exemple les vidéos embarquées. Cependant cela peut poser un faille de sécurité."
-#: ../../Zotlabs/Module/Editlayout.php:126
-#: ../../Zotlabs/Module/Layouts.php:127 ../../Zotlabs/Module/Layouts.php:186
-msgid "Layout Name"
-msgstr "Nom de la mise en page"
+#: ../../Zotlabs/Module/Admin/Security.php:80
+msgid ""
+"The recommended setting is to only allow unfiltered HTML from the following "
+"sites:"
+msgstr "Ce paramétrage autorisant le HTML pour les sites suivants."
-#: ../../Zotlabs/Module/Editlayout.php:127
-#: ../../Zotlabs/Module/Layouts.php:130
-msgid "Layout Description (Optional)"
-msgstr "Description de la mise en page (facultatif)"
+#: ../../Zotlabs/Module/Admin/Security.php:81
+msgid ""
+"https://youtube.com/<br />https://www.youtube.com/<br />https://youtu.be/<br"
+" />https://vimeo.com/<br />https://soundcloud.com/<br />"
+msgstr "https://youtube.com/<br />https://www.youtube.com/<br />https://youtu.be/<br />https://vimeo.com/<br />https://soundcloud.com/<br />"
-#: ../../Zotlabs/Module/Editlayout.php:135
-msgid "Edit Layout"
-msgstr "Modifier la mise en page"
+#: ../../Zotlabs/Module/Admin/Security.php:82
+msgid ""
+"All other embedded content will be filtered, <strong>unless</strong> "
+"embedded content from that site is explicitly blocked."
+msgstr "Les contenus html seront filtrés <strong>sauf</strong> ceux des sites explicitement bloqués."
-#: ../../Zotlabs/Module/Editwebpage.php:143
-msgid "Page link"
-msgstr ""
+#: ../../Zotlabs/Module/Admin/Security.php:87
+#: ../../Zotlabs/Widget/Admin.php:25
+msgid "Security"
+msgstr "Sécurité"
-#: ../../Zotlabs/Module/Editwebpage.php:169
-msgid "Edit Webpage"
-msgstr "Modifier la page web"
+#: ../../Zotlabs/Module/Admin/Security.php:89
+msgid "Block public"
+msgstr "Bloquer \"public\""
-#: ../../Zotlabs/Module/Follow.php:34
-msgid "Channel added."
-msgstr "Canal ajouté."
+#: ../../Zotlabs/Module/Admin/Security.php:89
+msgid ""
+"Check to block public access to all otherwise public personal pages on this "
+"site unless you are currently authenticated."
+msgstr "Sélectionner pour ne permettre l'accès aux pages personnelles \"publiques\" du site qu'aux personnes authentifiées, pas aux personnes anonymes du web."
-#: ../../Zotlabs/Module/Acl.php:227
-msgid "network"
-msgstr "réseau"
+#: ../../Zotlabs/Module/Admin/Security.php:90
+msgid "Set \"Transport Security\" HTTP header"
+msgstr "Paramétrer \"Transport Security\" pour l'entête HTTP"
-#: ../../Zotlabs/Module/Acl.php:237
-msgid "RSS"
-msgstr "RSS"
+#: ../../Zotlabs/Module/Admin/Security.php:91
+msgid "Set \"Content Security Policy\" HTTP header"
+msgstr "Paramétrer \"Content Security Policy\" pour l'entête HTTP"
-#: ../../Zotlabs/Module/Group.php:24
-msgid "Privacy group created."
-msgstr "Groupe d'accès créé."
+#: ../../Zotlabs/Module/Admin/Security.php:92
+msgid "Allowed email domains"
+msgstr "Domaines de courriels autorisés"
-#: ../../Zotlabs/Module/Group.php:30
-msgid "Could not create privacy group."
-msgstr "Impossible de créer le groupe d'accès."
+#: ../../Zotlabs/Module/Admin/Security.php:92
+msgid ""
+"Comma separated list of domains which are allowed in email addresses for "
+"registrations to this site. Wildcards are accepted. Empty to allow any "
+"domains"
+msgstr "Liste de noms de domaines séparés par des virgules dont les adresses de courriel seront autorisées lors de l'inscription à ce site. Les caractères génériques (*) sont acceptés. Laissez vide pour accepter tous les domaines."
-#: ../../Zotlabs/Module/Group.php:42 ../../Zotlabs/Module/Group.php:141
-#: ../../include/items.php:3893
-msgid "Privacy group not found."
-msgstr "Groupe d'accès introuvable."
+#: ../../Zotlabs/Module/Admin/Security.php:93
+msgid "Not allowed email domains"
+msgstr "Domaines de courriel non autorisés"
-#: ../../Zotlabs/Module/Group.php:58
-msgid "Privacy group updated."
-msgstr "Groupe d'accès mis à jour."
+#: ../../Zotlabs/Module/Admin/Security.php:93
+msgid ""
+"Comma separated list of domains which are not allowed in email addresses for"
+" registrations to this site. Wildcards are accepted. Empty to allow any "
+"domains, unless allowed domains have been defined."
+msgstr "Liste de noms de domaines - séparés par des virgules - dont les adresses de courriel ne seront pas autorisées lors de l'inscription à ce site. Les caractères génériques (*) sont acceptés. Laissez vide pour accepter tous les domaines, sauf si des domaines autorisés ont été définis."
-#: ../../Zotlabs/Module/Group.php:90
-msgid "Create a group of channels."
-msgstr "Créer un groupe de canaux."
+#: ../../Zotlabs/Module/Admin/Security.php:94
+msgid "Allow communications only from these sites"
+msgstr "N'autorisez que les communications venant de ces sites"
-#: ../../Zotlabs/Module/Group.php:91 ../../Zotlabs/Module/Group.php:184
-msgid "Privacy group name: "
-msgstr "Nom du groupe d'accès&nbsp;:"
+#: ../../Zotlabs/Module/Admin/Security.php:94
+msgid ""
+"One site per line. Leave empty to allow communication from anywhere by "
+"default"
+msgstr "Un site par ligne. Laisser vide pour autoriser les communications de tous les sites, par défaut."
-#: ../../Zotlabs/Module/Group.php:93 ../../Zotlabs/Module/Group.php:187
-msgid "Members are visible to other channels"
-msgstr "Les membres sont visibles par les autres canaux"
+#: ../../Zotlabs/Module/Admin/Security.php:95
+msgid "Block communications from these sites"
+msgstr "Bloquer les communications de ces sites"
-#: ../../Zotlabs/Module/Group.php:111
-msgid "Privacy group removed."
-msgstr "Groupe d'accès supprimé."
+#: ../../Zotlabs/Module/Admin/Security.php:96
+msgid "Allow communications only from these channels"
+msgstr "N'autoriser que les communications de ces canaux"
-#: ../../Zotlabs/Module/Group.php:113
-msgid "Unable to remove privacy group."
-msgstr "Impossible de supprimer le groupe d'accès."
+#: ../../Zotlabs/Module/Admin/Security.php:96
+msgid ""
+"One channel (hash) per line. Leave empty to allow from any channel by "
+"default"
+msgstr "Un canal (adresse) par ligne. Laisser vide pour autoriser les communications de tous les canaux, par défaut"
-#: ../../Zotlabs/Module/Group.php:183
-msgid "Privacy group editor"
-msgstr "Editeur de groupe d'accès."
+#: ../../Zotlabs/Module/Admin/Security.php:97
+msgid "Block communications from these channels"
+msgstr "Bloquer les communications de ces canaux"
-#: ../../Zotlabs/Module/Group.php:197
-msgid "Members"
-msgstr "Membres"
+#: ../../Zotlabs/Module/Admin/Security.php:98
+msgid "Only allow embeds from secure (SSL) websites and links."
+msgstr "Seuls les sites et liens sécurisés sont autorisé pour intégrer du code HTML"
-#: ../../Zotlabs/Module/Group.php:199
-msgid "All Connected Channels"
-msgstr "Tous les canaux connectés"
+#: ../../Zotlabs/Module/Admin/Security.php:99
+msgid "Allow unfiltered embedded HTML content only from these domains"
+msgstr "Autoriser le contenu HTML embarqué uniquement à partir de ces domaines"
-#: ../../Zotlabs/Module/Group.php:231
-msgid "Click on a channel to add or remove."
-msgstr "Cliquer sur un canal pour l'ajouter ou le supprimer"
+#: ../../Zotlabs/Module/Admin/Security.php:99
+msgid "One site per line. By default embedded content is filtered."
+msgstr "Un site par ligne. Par défaut le contenu embarqué est filtré."
-#: ../../Zotlabs/Module/Ffsapi.php:12
-msgid "Share content from Firefox to $Projectname"
-msgstr "Partager du contenu depuis Firefox avec $Projectname"
+#: ../../Zotlabs/Module/Admin/Security.php:100
+msgid "Block embedded HTML from these domains"
+msgstr "Bloquer le HTML embarqué à partir de ces domaines"
-#: ../../Zotlabs/Module/Ffsapi.php:15
-msgid "Activate the Firefox $Projectname provider"
-msgstr "Activer le connecteur $Projectname pour Firefox"
+#: ../../Zotlabs/Module/Lockview.php:75
+msgid "Remote privacy information not available."
+msgstr "Les informations distantes de confidentialité ne sont pas disponibles."
-#: ../../Zotlabs/Module/Api.php:61 ../../Zotlabs/Module/Api.php:85
-msgid "Authorize application connection"
-msgstr "Autoriser l'application à se connecter"
+#: ../../Zotlabs/Module/Lockview.php:96
+msgid "Visible to:"
+msgstr "Visible par&nbsp;:"
-#: ../../Zotlabs/Module/Api.php:62
-msgid "Return to your app and insert this Securty Code:"
-msgstr "Merci de retourner vers votre application, et d'y insérer ce Code de Sécurité&nbsp;:"
+#: ../../Zotlabs/Module/Lockview.php:117 ../../Zotlabs/Module/Lockview.php:153
+#: ../../Zotlabs/Module/Acl.php:117 ../../include/acl_selectors.php:183
+msgctxt "acl"
+msgid "Profile"
+msgstr ""
-#: ../../Zotlabs/Module/Api.php:72
-msgid "Please login to continue."
-msgstr "Merci de vous identifier pour continuer."
+#: ../../Zotlabs/Module/Settings/Permcats.php:37
+msgid "Permission category saved."
+msgstr "Catégorie d'autorisation enregistrée."
-#: ../../Zotlabs/Module/Api.php:87
+#: ../../Zotlabs/Module/Settings/Permcats.php:61
msgid ""
-"Do you want to authorize this application to access your posts and contacts,"
-" and/or create new posts for you?"
-msgstr "Voulez-vous autoriser cette application à accéder à vos publications et contacts, et/ou à publier en votre nom?"
+"Use this form to create permission rules for various classes of people or "
+"connections."
+msgstr "Utilisez ce formulaire pour créer des règles d'accès pour différentes catégories de personnes ou de contacts."
-#: ../../Zotlabs/Module/Help.php:26
-msgid "Documentation Search"
-msgstr "Chercher dans la documentation"
+#: ../../Zotlabs/Module/Settings/Permcats.php:94
+msgid "Permission Categories"
+msgstr "Catégories d'autorisation"
-#: ../../Zotlabs/Module/Help.php:67 ../../Zotlabs/Module/Help.php:73
-#: ../../Zotlabs/Module/Help.php:79
-msgid "Help:"
-msgstr "Aide&nbsp;:"
+#: ../../Zotlabs/Module/Settings/Permcats.php:102
+msgid "Permission Name"
+msgstr "Nom de l'autorisation"
-#: ../../Zotlabs/Module/Help.php:85 ../../Zotlabs/Module/Help.php:90
-#: ../../Zotlabs/Module/Layouts.php:183 ../../Zotlabs/Lib/Apps.php:223
-#: ../../include/nav.php:159
-msgid "Help"
-msgstr "Aide"
+#: ../../Zotlabs/Module/Settings/Permcats.php:103
+#: ../../Zotlabs/Module/Settings/Tokens.php:161
+#: ../../Zotlabs/Module/Connedit.php:894
+msgid "My Settings"
+msgstr "Mes paramètres"
-#: ../../Zotlabs/Module/Help.php:120
-msgid "$Projectname Documentation"
-msgstr "Documentation $Projectname"
+#: ../../Zotlabs/Module/Settings/Permcats.php:105
+#: ../../Zotlabs/Module/Settings/Tokens.php:163
+#: ../../Zotlabs/Module/Connedit.php:889
+msgid "inherited"
+msgstr "héritée"
-#: ../../Zotlabs/Module/Filestorage.php:88
-msgid "Permission Denied."
-msgstr "Permission refusée."
+#: ../../Zotlabs/Module/Settings/Permcats.php:108
+#: ../../Zotlabs/Module/Settings/Tokens.php:166
+#: ../../Zotlabs/Module/Connedit.php:896
+msgid "Individual Permissions"
+msgstr "Permissions individuelles"
-#: ../../Zotlabs/Module/Filestorage.php:104
-msgid "File not found."
-msgstr "Fichier introuvable."
+#: ../../Zotlabs/Module/Settings/Permcats.php:109
+#: ../../Zotlabs/Module/Settings/Tokens.php:167
+#: ../../Zotlabs/Module/Connedit.php:897
+msgid ""
+"Some permissions may be inherited from your channel's <a "
+"href=\"settings\"><strong>privacy settings</strong></a>, which have higher "
+"priority than individual settings. You can <strong>not</strong> change those"
+" settings here."
+msgstr "Certaines permissions peuvent être héritées de vos <a href=\"settings\">paramètres de confidentialité</a> de canal, lesquels sont prioritaires sur les réglages individuels. Vous pouvez modifier ces permissions ici mais cela n'aura aucun effet à moins de changer les paramètres hérités."
-#: ../../Zotlabs/Module/Filestorage.php:147
-msgid "Edit file permissions"
-msgstr "Modifier les autorisations d'accès au fichier"
+#: ../../Zotlabs/Module/Settings/Channel.php:62
+#: ../../Zotlabs/Module/Settings/Channel.php:66
+#: ../../Zotlabs/Module/Settings/Channel.php:67
+#: ../../Zotlabs/Module/Settings/Channel.php:70
+#: ../../Zotlabs/Module/Settings/Channel.php:81
+#: ../../Zotlabs/Module/Connedit.php:715 ../../Zotlabs/Widget/Affinity.php:28
+#: ../../include/selectors.php:123 ../../include/channel.php:406
+#: ../../include/channel.php:407 ../../include/channel.php:414
+msgid "Friends"
+msgstr "Amis"
-#: ../../Zotlabs/Module/Filestorage.php:156
-msgid "Set/edit permissions"
-msgstr "Définir/modifier les autorisations"
+#: ../../Zotlabs/Module/Settings/Channel.php:251
+#: ../../addon/rendezvous/rendezvous.php:82
+#: ../../addon/openstreetmap/openstreetmap.php:184
+#: ../../addon/msgfooter/msgfooter.php:54 ../../addon/logrot/logrot.php:54
+#: ../../addon/twitter/twitter.php:766 ../../addon/piwik/piwik.php:116
+#: ../../addon/xmpp/xmpp.php:102
+msgid "Settings updated."
+msgstr "Paramètres mis à jour."
-#: ../../Zotlabs/Module/Filestorage.php:157
-msgid "Include all files and sub folders"
-msgstr "Inclure tous fichiers et sous-répertoires"
+#: ../../Zotlabs/Module/Settings/Channel.php:312
+msgid "Nobody except yourself"
+msgstr "Personne sauf vous"
-#: ../../Zotlabs/Module/Filestorage.php:158
-msgid "Return to file list"
-msgstr "Retourner à la liste des fichiers"
+#: ../../Zotlabs/Module/Settings/Channel.php:313
+msgid "Only those you specifically allow"
+msgstr "Seulement ceux que vous autorisez spécifiquement"
-#: ../../Zotlabs/Module/Filestorage.php:160
-msgid "Copy/paste this code to attach file to a post"
-msgstr "Copiez/collez ce code pour joindre le fichier à une publication"
+#: ../../Zotlabs/Module/Settings/Channel.php:314
+msgid "Approved connections"
+msgstr "Contacts approuvés"
-#: ../../Zotlabs/Module/Filestorage.php:161
-msgid "Copy/paste this URL to link file from a web page"
-msgstr "Copiez/collez cette URL pour pointer vers ce fichier depuis une page web"
+#: ../../Zotlabs/Module/Settings/Channel.php:315
+msgid "Any connections"
+msgstr "Tous les contacts"
-#: ../../Zotlabs/Module/Filestorage.php:163
-msgid "Share this file"
-msgstr "Partager ce fichier"
+#: ../../Zotlabs/Module/Settings/Channel.php:316
+msgid "Anybody on this website"
+msgstr "Tous les utilisateurs du hub"
-#: ../../Zotlabs/Module/Filestorage.php:164
-msgid "Show URL to this file"
-msgstr "Montrer l'URL de ce fichier"
+#: ../../Zotlabs/Module/Settings/Channel.php:317
+msgid "Anybody in this network"
+msgstr "Tous les utilisateurs sur ce réseau"
-#: ../../Zotlabs/Module/Filestorage.php:165
-msgid "Notify your contacts about this file"
-msgstr "Notifier vos contacts à propos de ce fichier"
+#: ../../Zotlabs/Module/Settings/Channel.php:318
+msgid "Anybody authenticated"
+msgstr "Tous les utilisateurs authentifiés"
-#: ../../Zotlabs/Module/Apps.php:47 ../../include/widgets.php:102
-#: ../../include/nav.php:163
-msgid "Apps"
-msgstr "Applications"
+#: ../../Zotlabs/Module/Settings/Channel.php:319
+msgid "Anybody on the internet"
+msgstr "Tous les utilisateurs d'Internet"
-#: ../../Zotlabs/Module/Attach.php:13
-msgid "Item not available."
-msgstr "Élément indisponible."
+#: ../../Zotlabs/Module/Settings/Channel.php:395
+msgid "Publish your default profile in the network directory"
+msgstr "Publier votre profil par défaut dans l'annuaire du réseau"
-#: ../../Zotlabs/Module/Import.php:32
-#, php-format
-msgid "Your service plan only allows %d channels."
-msgstr "Votre forfait n'autorise que %d canaux."
+#: ../../Zotlabs/Module/Settings/Channel.php:400
+msgid "Allow us to suggest you as a potential friend to new members?"
+msgstr "Nous autoriser à vous suggérer comme ami(e) potentiel(le) aux nouveaux membres?"
-#: ../../Zotlabs/Module/Import.php:70 ../../Zotlabs/Module/Import_items.php:42
-msgid "Nothing to import."
-msgstr "Rien à importer."
+#: ../../Zotlabs/Module/Settings/Channel.php:404
+#: ../../Zotlabs/Module/Profile_photo.php:429
+#: ../../Zotlabs/Module/Cover_photo.php:365
+msgid "or"
+msgstr "ou"
-#: ../../Zotlabs/Module/Import.php:94 ../../Zotlabs/Module/Import_items.php:66
-msgid "Unable to download data from old server"
-msgstr "Impossible de récupérer les données de l'ancien serveur"
+#: ../../Zotlabs/Module/Settings/Channel.php:409
+msgid "Your channel address is"
+msgstr "L'adresse de votre canal est"
-#: ../../Zotlabs/Module/Import.php:100
-#: ../../Zotlabs/Module/Import_items.php:72
-msgid "Imported file is empty."
-msgstr "Le fichier importé est vide."
+#: ../../Zotlabs/Module/Settings/Channel.php:412
+msgid "Your files/photos are accessible via WebDAV at"
+msgstr "Vos fichiers/photos sont accessibles via WebDAV à"
-#: ../../Zotlabs/Module/Import.php:122
-#: ../../Zotlabs/Module/Import_items.php:86
-#, php-format
-msgid "Warning: Database versions differ by %1$d updates."
-msgstr "Attention&nbsp;: les versions de bases de données diffèrent de %1$d mises à jour."
+#: ../../Zotlabs/Module/Settings/Channel.php:474
+msgid "Channel Settings"
+msgstr "Paramètres du canal"
-#: ../../Zotlabs/Module/Import.php:150 ../../include/import.php:86
-msgid "Cloned channel not found. Import failed."
-msgstr "Canal cloné non trouvé. Echec de l'import."
+#: ../../Zotlabs/Module/Settings/Channel.php:481
+msgid "Basic Settings"
+msgstr "Paramètres standard"
-#: ../../Zotlabs/Module/Import.php:160
-msgid "No channel. Import failed."
-msgstr "Pas de canal. Echec de l'import."
+#: ../../Zotlabs/Module/Settings/Channel.php:482
+#: ../../include/channel.php:1248
+msgid "Full Name:"
+msgstr "Nom complet&nbsp;:"
-#: ../../Zotlabs/Module/Import.php:510
-#: ../../include/Import/import_diaspora.php:142
-msgid "Import completed."
-msgstr "L'import est terminé."
+#: ../../Zotlabs/Module/Settings/Channel.php:483
+#: ../../Zotlabs/Module/Settings/Account.php:119
+msgid "Email Address:"
+msgstr "Adresse de courriel&nbsp;:"
-#: ../../Zotlabs/Module/Import.php:532
-msgid "You must be logged in to use this feature."
-msgstr "Vous devez vous connecter pour utiliser cette fonctionnalité."
+#: ../../Zotlabs/Module/Settings/Channel.php:484
+msgid "Your Timezone:"
+msgstr "Votre fureau horaire&nbsp;:"
-#: ../../Zotlabs/Module/Import.php:537
-msgid "Import Channel"
-msgstr "Importation de canal"
+#: ../../Zotlabs/Module/Settings/Channel.php:485
+msgid "Default Post Location:"
+msgstr "Emplacement de publication par défaut&nbsp;:"
-#: ../../Zotlabs/Module/Import.php:538
-msgid ""
-"Use this form to import an existing channel from a different server/hub. You"
-" may retrieve the channel identity from the old server/hub via the network "
-"or provide an export file."
-msgstr "Utilisez ce formulaire pour importer un canal existant sur un autre serveur. Vous pouvez récupérer l'identité du canal sur l'ancien serveur directement par le réseau, ou bien fournir un fichier d'export/import."
+#: ../../Zotlabs/Module/Settings/Channel.php:485
+msgid "Geographical location to display on your posts"
+msgstr "Emplacement géographique à afficher sur vos publications"
-#: ../../Zotlabs/Module/Import.php:539
-#: ../../Zotlabs/Module/Import_items.php:119
-msgid "File to Upload"
-msgstr "Fichier à envoyer"
+#: ../../Zotlabs/Module/Settings/Channel.php:486
+msgid "Use Browser Location:"
+msgstr "Utiliser la géolocalisation du navigateur&nbsp;:"
-#: ../../Zotlabs/Module/Import.php:540
-msgid "Or provide the old server/hub details"
-msgstr "Ou fournissez les détails de l'ancien serveur/hub"
+#: ../../Zotlabs/Module/Settings/Channel.php:488
+msgid "Adult Content"
+msgstr "Contenu \"adulte\""
-#: ../../Zotlabs/Module/Import.php:541
-msgid "Your old identity address (xyz@example.com)"
-msgstr "Votre ancienne identité (zyx@exemple.com)"
+#: ../../Zotlabs/Module/Settings/Channel.php:488
+msgid ""
+"This channel frequently or regularly publishes adult content. (Please tag "
+"any adult material and/or nudity with #NSFW)"
+msgstr "Ce canal publie plus ou moins fréquemment du contenu pour adultes. (Merci d'indiquer tout contenu pour adulte ou potentiellement choquant avec l'étiquette <em>#NSFW</em> - Not Safe For Work)"
-#: ../../Zotlabs/Module/Import.php:542
-msgid "Your old login email address"
-msgstr "Votre ancienne adresse de courriel"
+#: ../../Zotlabs/Module/Settings/Channel.php:490
+msgid "Security and Privacy Settings"
+msgstr "Paramètres de sécurité et de confidentialité"
-#: ../../Zotlabs/Module/Import.php:543
-msgid "Your old login password"
-msgstr "Votre ancien mot de passe"
+#: ../../Zotlabs/Module/Settings/Channel.php:493
+msgid "Your permissions are already configured. Click to view/adjust"
+msgstr "Vous permissions sont déjà paramétrées. Cliquer pour voir/ajuster"
-#: ../../Zotlabs/Module/Import.php:544
-msgid ""
-"For either option, please choose whether to make this hub your new primary "
-"address, or whether your old location should continue this role. You will be"
-" able to post from either location, but only one can be marked as the "
-"primary location for files, photos, and media."
-msgstr "Quelle que soit l'option choisie, merci de décider si ce hub sera votre nouvelle adresse primaire, ou si votre ancien hub continuera à jouer ce rôle. Vous pourrez publier depuis l'emplacement de votre choix, mais une seule peut être déclarée comme stockage primaire de vos fichiers/photos/media."
+#: ../../Zotlabs/Module/Settings/Channel.php:495
+msgid "Hide my online presence"
+msgstr "Cacher ma présence en ligne"
-#: ../../Zotlabs/Module/Import.php:545
-msgid "Make this hub my primary location"
-msgstr "Faire de ce hub mon emplacement primaire"
+#: ../../Zotlabs/Module/Settings/Channel.php:495
+msgid "Prevents displaying in your profile that you are online"
+msgstr "Cacher votre statut (en ligne/hors ligne) sur votre profil"
-#: ../../Zotlabs/Module/Import.php:546
+#: ../../Zotlabs/Module/Settings/Channel.php:497
+msgid "Simple Privacy Settings:"
+msgstr "Paramètres de confidentialité simplifiés&nbsp;:"
+
+#: ../../Zotlabs/Module/Settings/Channel.php:498
msgid ""
-"Import existing posts if possible (experimental - limited by available "
-"memory"
-msgstr "Importer les publications existantes si possible (expérimental - limité par la mémoire disponible)"
+"Very Public - <em>extremely permissive (should be used with caution)</em>"
+msgstr "Très public - <em>extrèmement permissif (à n'utiliser qu'en connaissance de cause)</em>"
-#: ../../Zotlabs/Module/Import.php:547
+#: ../../Zotlabs/Module/Settings/Channel.php:499
msgid ""
-"This process may take several minutes to complete. Please submit the form "
-"only once and leave this page open until finished."
-msgstr "Ce processus peut prendre plusieurs minutes. Merci de ne valider le formulaire qu'une seule fois et de laisser cette page ouverte jusqu'à la fin."
+"Typical - <em>default public, privacy when desired (similar to social "
+"network permissions but with improved privacy)</em>"
+msgstr "Classique - <em>public par défaut, privé en cas de besoin (comparable aux permissions type réseau social, avec une confidentialité améliorée)</em>"
-#: ../../Zotlabs/Module/Item.php:178
-msgid "Unable to locate original post."
-msgstr "Impossible de localiser la publication initiale."
+#: ../../Zotlabs/Module/Settings/Channel.php:500
+msgid "Private - <em>default private, never open or public</em>"
+msgstr "Privé - <em>privé par défaut, jamais ouvert ni public</em>"
-#: ../../Zotlabs/Module/Item.php:427
-msgid "Empty post discarded."
-msgstr "Publication vide annulée."
+#: ../../Zotlabs/Module/Settings/Channel.php:501
+msgid "Blocked - <em>default blocked to/from everybody</em>"
+msgstr "Bloqué - <em>par défaut, bloqué de/vers tout le monde</em>"
-#: ../../Zotlabs/Module/Item.php:467
-msgid "Executable content type not permitted to this channel."
-msgstr "Les contenus de type 'exécutable' ne sont pas autorisés sur ce canal."
+#: ../../Zotlabs/Module/Settings/Channel.php:503
+msgid "Allow others to tag your posts"
+msgstr "Autoriser les autres à \"étiqueter\" vos publications"
-#: ../../Zotlabs/Module/Item.php:847
-msgid "Duplicate post suppressed."
-msgstr "Publication en doublon supprimée."
+#: ../../Zotlabs/Module/Settings/Channel.php:503
+msgid ""
+"Often used by the community to retro-actively flag inappropriate content"
+msgstr "Souvent utilisé par la communauté pour identifier un contenu inapproprié a posteriori "
-#: ../../Zotlabs/Module/Item.php:977
-msgid "System error. Post not saved."
-msgstr "Erreur système. Publication non sauvegardée."
+#: ../../Zotlabs/Module/Settings/Channel.php:505
+msgid "Channel Permission Limits"
+msgstr "Limites des permissions du canal"
-#: ../../Zotlabs/Module/Item.php:1241
-msgid "Unable to obtain post information from database."
-msgstr "Impossible d'obtenir les informations de publication depuis la base de données."
+#: ../../Zotlabs/Module/Settings/Channel.php:507
+msgid "Expire other channel content after this many days"
+msgstr "Faire expirer le contenu des autres canaux après n jours"
-#: ../../Zotlabs/Module/Item.php:1248
-#, php-format
-msgid "You have reached your limit of %1$.0f top level posts."
-msgstr "Vous avez atteint votre limite de %1$.0f contributions \"racines\"."
+#: ../../Zotlabs/Module/Settings/Channel.php:507
+msgid "0 or blank to use the website limit."
+msgstr "0 ou vide pour utiliser la limite du site web"
-#: ../../Zotlabs/Module/Item.php:1255
+#: ../../Zotlabs/Module/Settings/Channel.php:507
#, php-format
-msgid "You have reached your limit of %1$.0f webpages."
-msgstr "Vous avez atteint votre limite de %1$.0f pages web."
+msgid "This website expires after %d days."
+msgstr "Ce site web expirera après %d jours."
-#: ../../Zotlabs/Module/Layouts.php:181 ../../include/text.php:2267
-msgid "Layouts"
-msgstr "Mises-en-page"
+#: ../../Zotlabs/Module/Settings/Channel.php:507
+msgid "This website does not expire imported content."
+msgstr "Ce site web ne périme pas le contenu importé."
-#: ../../Zotlabs/Module/Layouts.php:183
-msgid "Comanche page description language help"
-msgstr "Aide sur le langage de description de page Comanche"
+#: ../../Zotlabs/Module/Settings/Channel.php:507
+msgid "The website limit takes precedence if lower than your limit."
+msgstr "La limite du site Web a priorité si elle est inférieure à votre limite."
-#: ../../Zotlabs/Module/Layouts.php:187
-msgid "Layout Description"
-msgstr "Description de la mise en page"
+#: ../../Zotlabs/Module/Settings/Channel.php:508
+msgid "Maximum Friend Requests/Day:"
+msgstr "Nombre maximum de demandes de contact par jour&nbsp;:"
-#: ../../Zotlabs/Module/Layouts.php:192
-msgid "Download PDL file"
-msgstr "Télécharger le fichier PDL"
+#: ../../Zotlabs/Module/Settings/Channel.php:508
+msgid "May reduce spam activity"
+msgstr "Contribue à réduire l'impact des indésirables"
-#: ../../Zotlabs/Module/Home.php:61 ../../Zotlabs/Module/Home.php:69
-#: ../../Zotlabs/Module/Siteinfo.php:65
-msgid "$Projectname"
-msgstr "$Projectname"
+#: ../../Zotlabs/Module/Settings/Channel.php:509
+msgid "Default Access Control List (ACL)"
+msgstr "Default Access Control List (ACL)"
-#: ../../Zotlabs/Module/Home.php:79
-#, php-format
-msgid "Welcome to %s"
-msgstr "Bienvenue sur %s"
+#: ../../Zotlabs/Module/Settings/Channel.php:511
+msgid "Use my default audience setting for the type of object published"
+msgstr "Utiliser mon paramètre de publication par défaut pour le type d'objet publié"
-#: ../../Zotlabs/Module/Id.php:13
-msgid "First Name"
-msgstr "Prénom"
+#: ../../Zotlabs/Module/Settings/Channel.php:518
+msgid "Channel permissions category:"
+msgstr "Catégorie de permissions du canal&nbsp;:"
-#: ../../Zotlabs/Module/Id.php:14
-msgid "Last Name"
-msgstr "Nom de famille"
+#: ../../Zotlabs/Module/Settings/Channel.php:519
+msgid "Default Permissions Group"
+msgstr ""
-#: ../../Zotlabs/Module/Id.php:15
-msgid "Nickname"
-msgstr "Surnom"
+#: ../../Zotlabs/Module/Settings/Channel.php:525
+msgid "Maximum private messages per day from unknown people:"
+msgstr "Nombre maximum de messages privés émanant d'inconnus, par jour&nbsp;:"
-#: ../../Zotlabs/Module/Id.php:16
-msgid "Full Name"
-msgstr "Nom complet"
+#: ../../Zotlabs/Module/Settings/Channel.php:525
+msgid "Useful to reduce spamming"
+msgstr "Utile pour réduire les indésirables"
-#: ../../Zotlabs/Module/Id.php:17 ../../Zotlabs/Module/Id.php:18
-#: ../../Zotlabs/Module/Admin.php:1035 ../../Zotlabs/Module/Admin.php:1047
-#: ../../include/network.php:2151 ../../boot.php:1705
-msgid "Email"
-msgstr "Courriel"
+#: ../../Zotlabs/Module/Settings/Channel.php:528
+msgid "Notification Settings"
+msgstr "Paramètres de notification"
-#: ../../Zotlabs/Module/Id.php:19 ../../Zotlabs/Module/Id.php:20
-#: ../../Zotlabs/Module/Id.php:21 ../../Zotlabs/Lib/Apps.php:236
-msgid "Profile Photo"
-msgstr "Photo du Profil"
+#: ../../Zotlabs/Module/Settings/Channel.php:529
+msgid "By default post a status message when:"
+msgstr "Par défaut, publier un statut quand&nbsp;:"
-#: ../../Zotlabs/Module/Id.php:22
-msgid "Profile Photo 16px"
-msgstr "Photo de profil 16px"
+#: ../../Zotlabs/Module/Settings/Channel.php:530
+msgid "accepting a friend request"
+msgstr "vous acceptez une demande de contact"
-#: ../../Zotlabs/Module/Id.php:23
-msgid "Profile Photo 32px"
-msgstr "Photo de profil 32px"
+#: ../../Zotlabs/Module/Settings/Channel.php:531
+msgid "joining a forum/community"
+msgstr "vous rejoignez un forum ou une communauté"
-#: ../../Zotlabs/Module/Id.php:24
-msgid "Profile Photo 48px"
-msgstr "Photo de profil 48px"
+#: ../../Zotlabs/Module/Settings/Channel.php:532
+msgid "making an <em>interesting</em> profile change"
+msgstr "vous faîtes une modification <em>intéressante</em> de votre profil"
-#: ../../Zotlabs/Module/Id.php:25
-msgid "Profile Photo 64px"
-msgstr "Photo de profil 64px"
+#: ../../Zotlabs/Module/Settings/Channel.php:533
+msgid "Send a notification email when:"
+msgstr "Envoyer un courriel de notification quand&nbsp;:"
-#: ../../Zotlabs/Module/Id.php:26
-msgid "Profile Photo 80px"
-msgstr "Photo de profil 80px"
+#: ../../Zotlabs/Module/Settings/Channel.php:534
+msgid "You receive a connection request"
+msgstr "Vous recevez une demande de contact"
-#: ../../Zotlabs/Module/Id.php:27
-msgid "Profile Photo 128px"
-msgstr "Photo de profil 128px"
+#: ../../Zotlabs/Module/Settings/Channel.php:535
+msgid "Your connections are confirmed"
+msgstr "Vos contacts sont confirmés"
-#: ../../Zotlabs/Module/Id.php:28
-msgid "Timezone"
-msgstr "Fuseau horaire"
+#: ../../Zotlabs/Module/Settings/Channel.php:536
+msgid "Someone writes on your profile wall"
+msgstr "Quelqu'un a écrit sur votre mur"
-#: ../../Zotlabs/Module/Id.php:29 ../../Zotlabs/Module/Profiles.php:731
-msgid "Homepage URL"
-msgstr "URL de mon site Internet&nbsp;:"
+#: ../../Zotlabs/Module/Settings/Channel.php:537
+msgid "Someone writes a followup comment"
+msgstr "Quelqu'un a commenté vos publications"
-#: ../../Zotlabs/Module/Id.php:30 ../../Zotlabs/Lib/Apps.php:234
-msgid "Language"
-msgstr "Langue"
+#: ../../Zotlabs/Module/Settings/Channel.php:538
+msgid "You receive a private message"
+msgstr "Vous recevez un message privé"
-#: ../../Zotlabs/Module/Id.php:31
-msgid "Birth Year"
-msgstr "Année de naissance"
+#: ../../Zotlabs/Module/Settings/Channel.php:539
+msgid "You receive a friend suggestion"
+msgstr "Vous recevez une suggestion d'amitié/contact"
-#: ../../Zotlabs/Module/Id.php:32
-msgid "Birth Month"
-msgstr "Mois de naissance"
+#: ../../Zotlabs/Module/Settings/Channel.php:540
+msgid "You are tagged in a post"
+msgstr "Vous êtes étiqueté dans une publication"
-#: ../../Zotlabs/Module/Id.php:33
-msgid "Birth Day"
-msgstr "Jour de naissance"
+#: ../../Zotlabs/Module/Settings/Channel.php:541
+msgid "You are poked/prodded/etc. in a post"
+msgstr "Vous êtes tapoté/encouragé/etc. dans une publication"
-#: ../../Zotlabs/Module/Id.php:34
-msgid "Birthdate"
-msgstr "Date de naissance"
+#: ../../Zotlabs/Module/Settings/Channel.php:543
+msgid "Someone likes your post/comment"
+msgstr "Quelqu'un aime votre publication/commentaire"
-#: ../../Zotlabs/Module/Id.php:35 ../../Zotlabs/Module/Profiles.php:454
-msgid "Gender"
-msgstr "Sexe"
+#: ../../Zotlabs/Module/Settings/Channel.php:546
+msgid "Show visual notifications including:"
+msgstr "Afficher des notifications visuelles y compris&nbsp;:"
-#: ../../Zotlabs/Module/Id.php:108 ../../include/selectors.php:49
-#: ../../include/selectors.php:66
-msgid "Male"
-msgstr "Homme"
+#: ../../Zotlabs/Module/Settings/Channel.php:548
+msgid "Unseen grid activity"
+msgstr "Activité du réseau pas encore consultée"
-#: ../../Zotlabs/Module/Id.php:110 ../../include/selectors.php:49
-#: ../../include/selectors.php:66
-msgid "Female"
-msgstr "Femme"
+#: ../../Zotlabs/Module/Settings/Channel.php:549
+msgid "Unseen channel activity"
+msgstr "Activité non vue sur le canal"
-#: ../../Zotlabs/Module/Impel.php:41 ../../include/bbcode.php:192
-msgid "webpage"
-msgstr "pages web"
+#: ../../Zotlabs/Module/Settings/Channel.php:550
+msgid "Unseen private messages"
+msgstr "Messages privés non lus"
-#: ../../Zotlabs/Module/Impel.php:46 ../../include/bbcode.php:198
-msgid "block"
-msgstr "bloquer"
+#: ../../Zotlabs/Module/Settings/Channel.php:550
+#: ../../Zotlabs/Module/Settings/Channel.php:555
+#: ../../Zotlabs/Module/Settings/Channel.php:556
+#: ../../Zotlabs/Module/Settings/Channel.php:557
+#: ../../addon/jappixmini/jappixmini.php:343
+msgid "Recommended"
+msgstr "Recommandé"
-#: ../../Zotlabs/Module/Impel.php:51 ../../include/bbcode.php:195
-msgid "layout"
-msgstr "mise en page"
+#: ../../Zotlabs/Module/Settings/Channel.php:551
+msgid "Upcoming events"
+msgstr "Événements à venir"
-#: ../../Zotlabs/Module/Impel.php:58 ../../include/bbcode.php:201
-msgid "menu"
-msgstr "menu"
+#: ../../Zotlabs/Module/Settings/Channel.php:552
+msgid "Events today"
+msgstr "Événements aujourd'hui"
-#: ../../Zotlabs/Module/Impel.php:196
-#, php-format
-msgid "%s element installed"
-msgstr "Elément %s installé"
+#: ../../Zotlabs/Module/Settings/Channel.php:553
+msgid "Upcoming birthdays"
+msgstr "Anniversaires à venir"
-#: ../../Zotlabs/Module/Impel.php:199
-#, php-format
-msgid "%s element installation failed"
-msgstr "L'installation de l'élément %s a échoué"
+#: ../../Zotlabs/Module/Settings/Channel.php:553
+msgid "Not available in all themes"
+msgstr "Pas disponible dans tous les thèmes"
-#: ../../Zotlabs/Module/Like.php:19
-msgid "Like/Dislike"
-msgstr "Aime/n'aime pas"
+#: ../../Zotlabs/Module/Settings/Channel.php:554
+msgid "System (personal) notifications"
+msgstr "Notifications système (personnelles)"
-#: ../../Zotlabs/Module/Like.php:24
-msgid "This action is restricted to members."
-msgstr "Cette action est réservée aux membres."
+#: ../../Zotlabs/Module/Settings/Channel.php:555
+msgid "System info messages"
+msgstr "Messages d'info système"
-#: ../../Zotlabs/Module/Like.php:25
+#: ../../Zotlabs/Module/Settings/Channel.php:556
+msgid "System critical alerts"
+msgstr "Alertes critiques système"
+
+#: ../../Zotlabs/Module/Settings/Channel.php:557
+msgid "New connections"
+msgstr "Nouveaux contacts"
+
+#: ../../Zotlabs/Module/Settings/Channel.php:558
+msgid "System Registrations"
+msgstr "Inscriptions système"
+
+#: ../../Zotlabs/Module/Settings/Channel.php:559
msgid ""
-"Please <a href=\"rmagic\">login with your $Projectname ID</a> or <a "
-"href=\"register\">register as a new $Projectname member</a> to continue."
-msgstr "S'il vous plait, <a href=\"rmagic\">identifiez vous avec votre identifant de $Projectname </a> ou <a href=\"register\">inscrivez vous comme nouveau membre de $Projectname </a> pour continuer."
+"Also show new wall posts, private messages and connections under Notices"
+msgstr "Afficher également les nouvelles publications sur le mur, les messages privés et les contacts dans Notifications"
-#: ../../Zotlabs/Module/Like.php:105 ../../Zotlabs/Module/Like.php:131
-#: ../../Zotlabs/Module/Like.php:169
-msgid "Invalid request."
-msgstr "Requête invalide."
+#: ../../Zotlabs/Module/Settings/Channel.php:561
+msgid "Notify me of events this many days in advance"
+msgstr "Me prévenir d’événements à venir tant de jours en avance"
-#: ../../Zotlabs/Module/Like.php:117 ../../include/conversation.php:126
-msgid "channel"
-msgstr "canal"
+#: ../../Zotlabs/Module/Settings/Channel.php:561
+msgid "Must be greater than 0"
+msgstr "Doit être supérieur à 0"
-#: ../../Zotlabs/Module/Like.php:146
-msgid "thing"
-msgstr "chose"
+#: ../../Zotlabs/Module/Settings/Channel.php:567
+msgid "Advanced Account/Page Type Settings"
+msgstr "Paramètres avancés de compte/type de page"
-#: ../../Zotlabs/Module/Like.php:192
-msgid "Channel unavailable."
-msgstr "Canal indisponible."
+#: ../../Zotlabs/Module/Settings/Channel.php:568
+msgid "Change the behaviour of this account for special situations"
+msgstr "Modifie le comportement de ce compte pour des situations particulières"
-#: ../../Zotlabs/Module/Like.php:240
-msgid "Previous action reversed."
-msgstr "Action précédente annulée."
+#: ../../Zotlabs/Module/Settings/Channel.php:570
+msgid "Miscellaneous Settings"
+msgstr "Paramètres divers"
-#: ../../Zotlabs/Module/Like.php:371 ../../Zotlabs/Module/Subthread.php:87
-#: ../../Zotlabs/Module/Tagger.php:47 ../../include/text.php:1940
-#: ../../include/conversation.php:120
-msgid "photo"
-msgstr "photo"
+#: ../../Zotlabs/Module/Settings/Channel.php:571
+msgid "Default photo upload folder"
+msgstr "Répertoire par défaut pour les photos téléversées"
-#: ../../Zotlabs/Module/Like.php:371 ../../Zotlabs/Module/Subthread.php:87
-#: ../../include/text.php:1946 ../../include/conversation.php:148
-msgid "status"
-msgstr "état"
+#: ../../Zotlabs/Module/Settings/Channel.php:571
+#: ../../Zotlabs/Module/Settings/Channel.php:572
+msgid "%Y - current year, %m - current month"
+msgstr "%Y - année en cours, %m - mois en cours"
-#: ../../Zotlabs/Module/Like.php:420 ../../include/conversation.php:164
-#, php-format
-msgid "%1$s likes %2$s's %3$s"
-msgstr "%1$s aime %3$s de %2$s"
+#: ../../Zotlabs/Module/Settings/Channel.php:572
+msgid "Default file upload folder"
+msgstr "Répertoire par défaut pour les fichiers téléversés"
-#: ../../Zotlabs/Module/Like.php:422 ../../include/conversation.php:167
-#, php-format
-msgid "%1$s doesn't like %2$s's %3$s"
-msgstr "%1$s n'aime pas %3$s de %2$s"
+#: ../../Zotlabs/Module/Settings/Channel.php:574
+msgid "Personal menu to display in your channel pages"
+msgstr "Menu personnel à afficher sur les pages de votre canal"
-#: ../../Zotlabs/Module/Like.php:424
-#, php-format
-msgid "%1$s agrees with %2$s's %3$s"
-msgstr "%1$s approuve %3$s de %2$s"
+#: ../../Zotlabs/Module/Settings/Channel.php:576
+msgid "Remove this channel."
+msgstr "Supprimer ce canal"
-#: ../../Zotlabs/Module/Like.php:426
-#, php-format
-msgid "%1$s doesn't agree with %2$s's %3$s"
-msgstr "%1$s n'est pas d'accord avec %3$s de %2$s"
+#: ../../Zotlabs/Module/Settings/Channel.php:577
+msgid "Firefox Share $Projectname provider"
+msgstr "Connecteur $Projectname pour Firefox Share"
-#: ../../Zotlabs/Module/Like.php:428
-#, php-format
-msgid "%1$s abstains from a decision on %2$s's %3$s"
-msgstr "%1$s s'abstient de toute décision sur le %3$s de %2$s"
+#: ../../Zotlabs/Module/Settings/Channel.php:578
+msgid "Start calendar week on Monday"
+msgstr ""
-#: ../../Zotlabs/Module/Like.php:430
-#, php-format
-msgid "%1$s is attending %2$s's %3$s"
-msgstr "%1$s participe à %3$s de %2$s"
+#: ../../Zotlabs/Module/Settings/Features.php:45
+msgid "Additional Features"
+msgstr "Fonctionnalités additionnelles"
-#: ../../Zotlabs/Module/Like.php:432
+#: ../../Zotlabs/Module/Settings/Tokens.php:31
#, php-format
-msgid "%1$s is not attending %2$s's %3$s"
-msgstr "%1$s ne participe pas à %3$s de %2$s"
+msgid "This channel is limited to %d tokens"
+msgstr "Ce canal est limité à %d jetons"
-#: ../../Zotlabs/Module/Like.php:434
-#, php-format
-msgid "%1$s may attend %2$s's %3$s"
-msgstr "%1$s participe peut-être à %3$s de %2$s"
+#: ../../Zotlabs/Module/Settings/Tokens.php:37
+msgid "Name and Password are required."
+msgstr "Le nom et le mot de passe sont requis"
-#: ../../Zotlabs/Module/Like.php:537
-msgid "Action completed."
-msgstr "Action terminée."
+#: ../../Zotlabs/Module/Settings/Tokens.php:77
+msgid "Token saved."
+msgstr "Jeton sauvegardé"
-#: ../../Zotlabs/Module/Like.php:538
-msgid "Thank you."
-msgstr "Merci."
+#: ../../Zotlabs/Module/Settings/Tokens.php:113
+msgid ""
+"Use this form to create temporary access identifiers to share things with "
+"non-members. These identities may be used in Access Control Lists and "
+"visitors may login using these credentials to access private content."
+msgstr "Utilisez ce formulaire pour créer des identifiants d'accès temporaires pour partager des informations avec des non-membres. Ces identités peuvent être utilisées dans les listes de contrôle d'accès et les visiteurs peuvent se connecter en utilisant ces certificats d'identification pour accéder au contenu privé."
-#: ../../Zotlabs/Module/Import_items.php:102
-msgid "Import completed"
-msgstr "L'import est terminé."
+#: ../../Zotlabs/Module/Settings/Tokens.php:115
+msgid ""
+"You may also provide <em>dropbox</em> style access links to friends and "
+"associates by adding the Login Password to any specific site URL as shown. "
+"Examples:"
+msgstr "Vous pouvez également fournir des liens d'accès, style <em>dropbox</em>, aux amis et aux associés en ajoutant le mot de passe de connexion à l'URL d'un site spécifique, comme indiqué. Exemples:"
-#: ../../Zotlabs/Module/Import_items.php:117
-msgid "Import Items"
-msgstr "Importer"
+#: ../../Zotlabs/Module/Settings/Tokens.php:150
+#: ../../Zotlabs/Widget/Settings_menu.php:90
+msgid "Guest Access Tokens"
+msgstr "Jeton d'accès pour un invité"
-#: ../../Zotlabs/Module/Import_items.php:118
-msgid ""
-"Use this form to import existing posts and content from an export file."
-msgstr "Utiliser ce formulaire pour importer des publications et du contenu existant d'un fichier d'export."
+#: ../../Zotlabs/Module/Settings/Tokens.php:157
+msgid "Login Name"
+msgstr "Nom d'utilisateur"
-#: ../../Zotlabs/Module/Invite.php:29
-msgid "Total invitation limit exceeded."
-msgstr "Limite du nombre total d'invitation dépassée."
+#: ../../Zotlabs/Module/Settings/Tokens.php:158
+msgid "Login Password"
+msgstr "Mot de passe"
-#: ../../Zotlabs/Module/Invite.php:53
-#, php-format
-msgid "%s : Not a valid email address."
-msgstr "%s&nbsp;: adresse courriel invalide."
+#: ../../Zotlabs/Module/Settings/Tokens.php:159
+msgid "Expires (yyyy-mm-dd)"
+msgstr "Date d'expiration sous la forme année mois jour (AAAA-MM-JJ)"
-#: ../../Zotlabs/Module/Invite.php:63
-msgid "Please join us on $Projectname"
-msgstr "Rejoignez-nous sur $Projectname"
+#: ../../Zotlabs/Module/Settings/Tokens.php:160
+#: ../../Zotlabs/Module/Connedit.php:893
+msgid "Their Settings"
+msgstr "Leurs paramètres"
-#: ../../Zotlabs/Module/Invite.php:74
-msgid "Invitation limit exceeded. Please contact your site administrator."
-msgstr "Limite d'invitations dépassée. Merci de contacter l'administration de votre site."
+#: ../../Zotlabs/Module/Settings/Account.php:20
+msgid "Not valid email."
+msgstr "Adresse de courriel non valide."
-#: ../../Zotlabs/Module/Invite.php:79
-#, php-format
-msgid "%s : Message delivery failed."
-msgstr "%s&nbsp;: Échec de distribution du message."
+#: ../../Zotlabs/Module/Settings/Account.php:23
+msgid "Protected email address. Cannot change to that email."
+msgstr "Adresse de courriel protégée. Impossible de l'utiliser."
-#: ../../Zotlabs/Module/Invite.php:83
-#, php-format
-msgid "%d message sent."
-msgid_plural "%d messages sent."
-msgstr[0] "%d message envoyé."
-msgstr[1] "%d messages envoyés."
+#: ../../Zotlabs/Module/Settings/Account.php:32
+msgid "System failure storing new email. Please try again."
+msgstr "Défaillance système lors du stockage de la nouvelle adresse de courriel. Merci d'essayer à nouveau."
-#: ../../Zotlabs/Module/Invite.php:102
-msgid "You have no more invitations available"
-msgstr "Vous ne disposez plus d'aucune invitation"
+#: ../../Zotlabs/Module/Settings/Account.php:40
+msgid "Technical skill level updated"
+msgstr "Niveau technique mis à jour"
-#: ../../Zotlabs/Module/Invite.php:133
-msgid "Send invitations"
-msgstr "Envoyer des invitations"
+#: ../../Zotlabs/Module/Settings/Account.php:56
+msgid "Password verification failed."
+msgstr "La vérification du mot de passe a échoué."
-#: ../../Zotlabs/Module/Invite.php:134
-msgid "Enter email addresses, one per line:"
-msgstr "Entrez les adresses de courriel, une par ligne&nbsp;:"
+#: ../../Zotlabs/Module/Settings/Account.php:63
+msgid "Passwords do not match. Password unchanged."
+msgstr "Les deux saisies du mot de passe ne correspondent pas. Il n'a donc pas été changé."
-#: ../../Zotlabs/Module/Invite.php:135 ../../Zotlabs/Module/Mail.php:249
-msgid "Your message:"
-msgstr "Votre message&nbsp;:"
+#: ../../Zotlabs/Module/Settings/Account.php:67
+msgid "Empty passwords are not allowed. Password unchanged."
+msgstr "Le mot de passe ne peut pas être vide. Il n'a donc pas été changé."
-#: ../../Zotlabs/Module/Invite.php:136
-msgid "Please join my community on $Projectname."
-msgstr "Rejoignez ma communauté sur $Projectname."
+#: ../../Zotlabs/Module/Settings/Account.php:81
+msgid "Password changed."
+msgstr "Le mot de passe a été changé."
-#: ../../Zotlabs/Module/Invite.php:138
-msgid "You will need to supply this invitation code:"
-msgstr "Vous devrez fournir le code suivant&nbsp;:"
+#: ../../Zotlabs/Module/Settings/Account.php:83
+msgid "Password update failed. Please try again."
+msgstr "La mise à jour du mot de passe a échoué. Merci d'essayer à nouveau."
-#: ../../Zotlabs/Module/Invite.php:139
-msgid ""
-"1. Register at any $Projectname location (they are all inter-connected)"
-msgstr "1. Enregistrez-vous sur n'importe quel serveur $Projectname (ils sont tous inter-connectés)"
+#: ../../Zotlabs/Module/Settings/Account.php:112
+msgid "Account Settings"
+msgstr "Paramètres du compte"
-#: ../../Zotlabs/Module/Invite.php:141
-msgid "2. Enter my $Projectname network address into the site searchbar."
-msgstr "2. Saisissez l'adresse de mon canal $Projectname dans la barre de recherche du site."
+#: ../../Zotlabs/Module/Settings/Account.php:113
+msgid "Current Password"
+msgstr "Mot de passe actuel"
-#: ../../Zotlabs/Module/Invite.php:142
-msgid "or visit"
-msgstr "ou rendez-vous sur"
+#: ../../Zotlabs/Module/Settings/Account.php:114
+msgid "Enter New Password"
+msgstr "Entrez votre nouveau mot de passe"
-#: ../../Zotlabs/Module/Invite.php:144
-msgid "3. Click [Connect]"
-msgstr "3. Cliquez sur [Ajouter]"
+#: ../../Zotlabs/Module/Settings/Account.php:115
+msgid "Confirm New Password"
+msgstr "Confirmez le nouveau mot de passe"
-#: ../../Zotlabs/Module/Lockview.php:61
-msgid "Remote privacy information not available."
-msgstr "Les informations distantes de confidentialité ne sont pas disponibles."
+#: ../../Zotlabs/Module/Settings/Account.php:115
+msgid "Leave password fields blank unless changing"
+msgstr "Laissez les mots de passe vides si vous ne voulez pas les modifier"
-#: ../../Zotlabs/Module/Lockview.php:82
-msgid "Visible to:"
-msgstr "Visible par&nbsp;:"
+#: ../../Zotlabs/Module/Settings/Account.php:116
+msgid "Your technical skill level"
+msgstr "Votre niveau technique"
-#: ../../Zotlabs/Module/Locs.php:25 ../../Zotlabs/Module/Locs.php:54
-msgid "Location not found."
-msgstr "Emplacement introuvable."
+#: ../../Zotlabs/Module/Settings/Account.php:116
+msgid "Used to provide a member experience matched to your comfort level"
+msgstr "Utilisé pour fournir une expérience utilisateur correspondant à votre niveau de confort"
-#: ../../Zotlabs/Module/Locs.php:62
-msgid "Location lookup failed."
-msgstr "Echec de la recherche de l'emplacement."
+#: ../../Zotlabs/Module/Settings/Account.php:120
+#: ../../Zotlabs/Module/Removeaccount.php:61
+msgid "Remove Account"
+msgstr "Supprimer le compte"
-#: ../../Zotlabs/Module/Locs.php:66
-msgid ""
-"Please select another location to become primary before removing the primary"
-" location."
-msgstr "Merci de sélectionner un autre emplacement comme nouvel emplacement primaire avant de supprimer l'emplacement primaire actuel."
+#: ../../Zotlabs/Module/Settings/Account.php:121
+msgid "Remove this account including all its channels"
+msgstr "Supprimer ce compte et tous ses canaux"
-#: ../../Zotlabs/Module/Locs.php:95
-msgid "Syncing locations"
-msgstr "Synchronisation des emplacements"
+#: ../../Zotlabs/Module/Settings/Featured.php:20
+msgid "Affinity Slider settings updated."
+msgstr "Paramètres de la réglette d'affinité mis à jour."
-#: ../../Zotlabs/Module/Locs.php:105
-msgid "No locations found."
-msgstr "Emplacement(s) introuvable."
+#: ../../Zotlabs/Module/Settings/Featured.php:34
+msgid "No feature settings configured"
+msgstr "Aucun paramètre de fonctionnalité configuré"
-#: ../../Zotlabs/Module/Locs.php:116
-msgid "Manage Channel Locations"
-msgstr "Gérer les emplacements des canaux"
+#: ../../Zotlabs/Module/Settings/Featured.php:41
+msgid "Default maximum affinity level"
+msgstr "Niveau d'affinité maximum par défaut"
-#: ../../Zotlabs/Module/Locs.php:118 ../../Zotlabs/Module/Profiles.php:470
-#: ../../Zotlabs/Module/Admin.php:1224
-msgid "Address"
-msgstr "Adresse"
+#: ../../Zotlabs/Module/Settings/Featured.php:46
+msgid "Default minimum affinity level"
+msgstr "Niveau d'affinité minimum par défaut"
-#: ../../Zotlabs/Module/Locs.php:119
-msgid "Primary"
-msgstr ""
+#: ../../Zotlabs/Module/Settings/Featured.php:50
+msgid "Affinity Slider Settings"
+msgstr "Paramètres de la réglette d'affinité"
-#: ../../Zotlabs/Module/Locs.php:120 ../../Zotlabs/Module/Menu.php:113
-msgid "Drop"
-msgstr "Supprimer"
+#: ../../Zotlabs/Module/Settings/Featured.php:60
+msgid "Feature/Addon Settings"
+msgstr "Paramètres des extensions/greffons"
-#: ../../Zotlabs/Module/Locs.php:122
-msgid "Sync Now"
-msgstr ""
+#: ../../Zotlabs/Module/Settings/Display.php:145
+msgid "No special theme for mobile devices"
+msgstr "Pas de thème spécifique aux mobiles"
-#: ../../Zotlabs/Module/Locs.php:123
-msgid "Please wait several minutes between consecutive operations."
-msgstr "Merci d'attendre plusieurs minutes entre opérations successives."
+#: ../../Zotlabs/Module/Settings/Display.php:148
+#, php-format
+msgid "%s - (Experimental)"
+msgstr "%s - (Expérimental)"
-#: ../../Zotlabs/Module/Locs.php:124
-msgid ""
-"When possible, drop a location by logging into that website/hub and removing"
-" your channel."
-msgstr "Quand c'est possible, abandonnez un emplacement en vous connectant sur le site/hub et en supprimant votre canal."
+#: ../../Zotlabs/Module/Settings/Display.php:198
+msgid "Display Settings"
+msgstr "Afficher les paramètres"
-#: ../../Zotlabs/Module/Locs.php:125
-msgid "Use this form to drop the location if the hub is no longer operating."
-msgstr "Utilisez ce formulaire pour abandonner l'emplacement si le hub n'est plus actif."
+#: ../../Zotlabs/Module/Settings/Display.php:199
+msgid "Theme Settings"
+msgstr "Paramètres du thème"
-#: ../../Zotlabs/Module/Magic.php:71
-msgid "Hub not found."
-msgstr "Hub introuvable."
+#: ../../Zotlabs/Module/Settings/Display.php:200
+msgid "Custom Theme Settings"
+msgstr "Paramètres personnels du thème"
-#: ../../Zotlabs/Module/Mail.php:38
-msgid "Unable to lookup recipient."
-msgstr "Impossible de localiser le destinataire."
+#: ../../Zotlabs/Module/Settings/Display.php:201
+msgid "Content Settings"
+msgstr "Paramètres liés au contenu"
-#: ../../Zotlabs/Module/Mail.php:45
-msgid "Unable to communicate with requested channel."
-msgstr "Impossible de communiquer avec le canal demandé."
+#: ../../Zotlabs/Module/Settings/Display.php:207
+msgid "Display Theme:"
+msgstr "Afficher le thème&nbsp;:"
-#: ../../Zotlabs/Module/Mail.php:52
-msgid "Cannot verify requested channel."
-msgstr "Impossible de vérifier le canal demandé."
+#: ../../Zotlabs/Module/Settings/Display.php:208
+msgid "Select scheme"
+msgstr "Définir la palette de couleurs"
-#: ../../Zotlabs/Module/Mail.php:78
-msgid "Selected channel has private message restrictions. Send failed."
-msgstr "Le canal choisi a des restrictions quant aux messages privés. L'envoi a échoué."
+#: ../../Zotlabs/Module/Settings/Display.php:210
+msgid "Mobile Theme:"
+msgstr "Thème mobile&nbsp;:"
-#: ../../Zotlabs/Module/Mail.php:143
-msgid "Messages"
-msgstr "Messages"
+#: ../../Zotlabs/Module/Settings/Display.php:211
+msgid "Preload images before rendering the page"
+msgstr "Pré-charger les images avant d'afficher la page"
-#: ../../Zotlabs/Module/Mail.php:178
-msgid "Message recalled."
-msgstr "Message rappelé."
+#: ../../Zotlabs/Module/Settings/Display.php:211
+msgid ""
+"The subjective page load time will be longer but the page will be ready when"
+" displayed"
+msgstr "Le temps de charge perçu de la page sera plus long mais la page sera complète quand elle s'affichera"
-#: ../../Zotlabs/Module/Mail.php:191
-msgid "Conversation removed."
-msgstr "Conversation supprimée."
+#: ../../Zotlabs/Module/Settings/Display.php:212
+msgid "Enable user zoom on mobile devices"
+msgstr "Permettre à l'utilisateur d'un mobile d'agrandir le contenu"
-#: ../../Zotlabs/Module/Mail.php:206 ../../Zotlabs/Module/Mail.php:315
-msgid "Expires YYYY-MM-DD HH:MM"
-msgstr "Expire le YYYY-MM-DD à HH:MM"
+#: ../../Zotlabs/Module/Settings/Display.php:213
+msgid "Update browser every xx seconds"
+msgstr "Mettre à jour le navigateur toutes les xx secondes"
-#: ../../Zotlabs/Module/Mail.php:234
-msgid "Requested channel is not in this network"
-msgstr "Le canal demandé n'est pas sur ce réseau"
+#: ../../Zotlabs/Module/Settings/Display.php:213
+msgid "Minimum of 10 seconds, no maximum"
+msgstr "Minimum 10 secondes, pas de maximum"
-#: ../../Zotlabs/Module/Mail.php:242
-msgid "Send Private Message"
-msgstr "Envoyer un message privé"
+#: ../../Zotlabs/Module/Settings/Display.php:214
+msgid "Maximum number of conversations to load at any time:"
+msgstr "Nombre maximal de conversations pouvant être chargées en même temps&nbsp;:"
-#: ../../Zotlabs/Module/Mail.php:243 ../../Zotlabs/Module/Mail.php:368
-msgid "To:"
-msgstr "À&nbsp;:"
+#: ../../Zotlabs/Module/Settings/Display.php:214
+msgid "Maximum of 100 items"
+msgstr "100 éléments au maximum"
-#: ../../Zotlabs/Module/Mail.php:246 ../../Zotlabs/Module/Mail.php:370
-msgid "Subject:"
-msgstr "Objet&nbsp;:"
+#: ../../Zotlabs/Module/Settings/Display.php:215
+msgid "Show emoticons (smilies) as images"
+msgstr "Remplacer les émoticônes (smileys) par des images"
-#: ../../Zotlabs/Module/Mail.php:251 ../../Zotlabs/Module/Mail.php:376
-#: ../../include/conversation.php:1220
-msgid "Attach file"
-msgstr "Joindre un fichier"
+#: ../../Zotlabs/Module/Settings/Display.php:216
+msgid "Manual conversation updates"
+msgstr "Manuel de mises à jour des conversations"
-#: ../../Zotlabs/Module/Mail.php:253
-msgid "Send"
-msgstr "Envoyer"
+#: ../../Zotlabs/Module/Settings/Display.php:216
+msgid "Default is on, turning this off may increase screen jumping"
+msgstr "Activé par défaut, le désactiver peut accroître les sauts d'écran"
-#: ../../Zotlabs/Module/Mail.php:256 ../../Zotlabs/Module/Mail.php:381
-#: ../../include/conversation.php:1251
-msgid "Set expiration date"
-msgstr "Définir la date d'expiration"
+#: ../../Zotlabs/Module/Settings/Display.php:217
+msgid "Link post titles to source"
+msgstr "Lier les titres des publications à leur source"
-#: ../../Zotlabs/Module/Mail.php:340
-msgid "Delete message"
-msgstr "Supprimer le message"
+#: ../../Zotlabs/Module/Settings/Display.php:218
+msgid "System Page Layout Editor - (advanced)"
+msgstr "Editeur de mise en page des pages systèmes - (avancé)"
-#: ../../Zotlabs/Module/Mail.php:341
-msgid "Delivery report"
-msgstr "Rapport de distribution"
+#: ../../Zotlabs/Module/Settings/Display.php:221
+msgid "Use blog/list mode on channel page"
+msgstr "Utiliser le mode blog/liste sur la page du canal"
-#: ../../Zotlabs/Module/Mail.php:342
-msgid "Recall message"
-msgstr "Rappeler le message"
+#: ../../Zotlabs/Module/Settings/Display.php:221
+#: ../../Zotlabs/Module/Settings/Display.php:222
+msgid "(comments displayed separately)"
+msgstr "(commentaires affichés séparément)"
-#: ../../Zotlabs/Module/Mail.php:344
-msgid "Message has been recalled."
-msgstr "Le message a été rappelé."
+#: ../../Zotlabs/Module/Settings/Display.php:222
+msgid "Use blog/list mode on grid page"
+msgstr "Utiliser le mode blog/liste sur la page du réseau"
-#: ../../Zotlabs/Module/Mail.php:361
-msgid "Delete Conversation"
-msgstr "Supprimer la conversation"
+#: ../../Zotlabs/Module/Settings/Display.php:223
+msgid "Channel page max height of content (in pixels)"
+msgstr "Hauteur maximale du contenu pour la page du canal (en pixels)"
-#: ../../Zotlabs/Module/Mail.php:363
-msgid ""
-"No secure communications available. You <strong>may</strong> be able to "
-"respond from the sender's profile page."
-msgstr "Aucune communication sécurisée n'est possible. Vous pourrez <strong>peut-être</strong> répondre depuis la page de profil de l'émetteur."
+#: ../../Zotlabs/Module/Settings/Display.php:223
+#: ../../Zotlabs/Module/Settings/Display.php:224
+msgid "click to expand content exceeding this height"
+msgstr "cliquer pour dérouler le contenu dépassant cette limite"
-#: ../../Zotlabs/Module/Mail.php:367
-msgid "Send Reply"
-msgstr "Envoyer la réponse"
+#: ../../Zotlabs/Module/Settings/Display.php:224
+msgid "Grid page max height of content (in pixels)"
+msgstr "Hauteur maximale du contenu sur la page du réseau (en pixels)"
-#: ../../Zotlabs/Module/Mail.php:372
-#, php-format
-msgid "Your message for %s (%s):"
-msgstr "Votre message pour %s (%s)&nbsp;:"
+#: ../../Zotlabs/Module/Settings/Oauth.php:34
+msgid "Name is required"
+msgstr "Le nom est requis"
-#: ../../Zotlabs/Module/Manage.php:136
-#: ../../Zotlabs/Module/New_channel.php:121
-#, php-format
-msgid "You have created %1$.0f of %2$.0f allowed channels."
-msgstr "Vous avez créé %1$.0f des %2$.0f canaux autorisés."
+#: ../../Zotlabs/Module/Settings/Oauth.php:38
+msgid "Key and Secret are required"
+msgstr "Clef et secret sont requis"
-#: ../../Zotlabs/Module/Manage.php:143
-msgid "Create a new channel"
-msgstr "Créer un nouveau canal"
+#: ../../Zotlabs/Module/Settings/Oauth.php:86
+#: ../../Zotlabs/Module/Settings/Oauth.php:112
+#: ../../Zotlabs/Module/Settings/Oauth.php:148
+msgid "Add application"
+msgstr "Ajouter une application"
-#: ../../Zotlabs/Module/Manage.php:164 ../../Zotlabs/Lib/Apps.php:213
-#: ../../include/nav.php:206
-msgid "Channel Manager"
-msgstr "Gérer les canaux"
+#: ../../Zotlabs/Module/Settings/Oauth.php:89
+msgid "Name of application"
+msgstr "Nom de l'application"
-#: ../../Zotlabs/Module/Manage.php:165
-msgid "Current Channel"
-msgstr "Canal actif"
+#: ../../Zotlabs/Module/Settings/Oauth.php:90
+#: ../../Zotlabs/Module/Settings/Oauth.php:116
+#: ../../addon/statusnet/statusnet.php:893 ../../addon/twitter/twitter.php:775
+msgid "Consumer Key"
+msgstr "Clef client"
-#: ../../Zotlabs/Module/Manage.php:167
-msgid "Switch to one of your channels by selecting it."
-msgstr "Pour changer de canal, sélectionnez-en un"
+#: ../../Zotlabs/Module/Settings/Oauth.php:90
+#: ../../Zotlabs/Module/Settings/Oauth.php:91
+msgid "Automatically generated - change if desired. Max length 20"
+msgstr "Généré automatiquement - à changer si besoin. Longueur maximale 20 caractères."
-#: ../../Zotlabs/Module/Manage.php:168
-msgid "Default Channel"
-msgstr "Canal par défaut"
+#: ../../Zotlabs/Module/Settings/Oauth.php:91
+#: ../../Zotlabs/Module/Settings/Oauth.php:117
+#: ../../addon/statusnet/statusnet.php:892 ../../addon/twitter/twitter.php:776
+msgid "Consumer Secret"
+msgstr "Secret client"
-#: ../../Zotlabs/Module/Manage.php:169
-msgid "Make Default"
-msgstr "Définir comme défaut"
+#: ../../Zotlabs/Module/Settings/Oauth.php:92
+#: ../../Zotlabs/Module/Settings/Oauth.php:118
+msgid "Redirect"
+msgstr "Redirection"
-#: ../../Zotlabs/Module/Manage.php:172
-#, php-format
-msgid "%d new messages"
-msgstr "%d nouveaux messages"
+#: ../../Zotlabs/Module/Settings/Oauth.php:92
+msgid ""
+"Redirect URI - leave blank unless your application specifically requires "
+"this"
+msgstr "URI de redirection - laissez vide, sauf si votre application le requiert spécifiquement"
-#: ../../Zotlabs/Module/Manage.php:173
-#, php-format
-msgid "%d new introductions"
-msgstr "%d nouvelles présentations"
+#: ../../Zotlabs/Module/Settings/Oauth.php:93
+#: ../../Zotlabs/Module/Settings/Oauth.php:119
+msgid "Icon url"
+msgstr "URL de l'icône"
-#: ../../Zotlabs/Module/Manage.php:175
-msgid "Delegated Channel"
-msgstr ""
+#: ../../Zotlabs/Module/Settings/Oauth.php:93
+#: ../../Zotlabs/Module/Sources.php:112 ../../Zotlabs/Module/Sources.php:147
+msgid "Optional"
+msgstr "Facultatif"
-#: ../../Zotlabs/Module/Lostpass.php:19
-msgid "No valid account found."
-msgstr "Aucun compte valide trouvé."
+#: ../../Zotlabs/Module/Settings/Oauth.php:104
+msgid "Application not found."
+msgstr "Application introuvable."
-#: ../../Zotlabs/Module/Lostpass.php:33
-msgid "Password reset request issued. Check your email."
-msgstr "Demande de réinitialisation du mot de passe envoyée. Vérifiez vos courriels."
+#: ../../Zotlabs/Module/Settings/Oauth.php:147
+msgid "Connected Apps"
+msgstr "Applications connectées"
-#: ../../Zotlabs/Module/Lostpass.php:39 ../../Zotlabs/Module/Lostpass.php:107
-#, php-format
-msgid "Site Member (%s)"
-msgstr "Membre du site (%s)"
+#: ../../Zotlabs/Module/Settings/Oauth.php:151
+msgid "Client key starts with"
+msgstr "La clef partagée commence par"
-#: ../../Zotlabs/Module/Lostpass.php:44
-#, php-format
-msgid "Password reset requested at %s"
-msgstr "Demande de réinitialisation du mot de passe sur %s"
+#: ../../Zotlabs/Module/Settings/Oauth.php:152
+msgid "No name"
+msgstr "Sans nom"
-#: ../../Zotlabs/Module/Lostpass.php:67
-msgid ""
-"Request could not be verified. (You may have previously submitted it.) "
-"Password reset failed."
-msgstr "La demande n'a pas pu être vérifiée. (Peut-être l'avez vous déjà utilisée.) La réinitialisation a échoué."
+#: ../../Zotlabs/Module/Settings/Oauth.php:153
+msgid "Remove authorization"
+msgstr "Révoquer l'autorisation"
-#: ../../Zotlabs/Module/Lostpass.php:90 ../../boot.php:1711
-msgid "Password Reset"
-msgstr "Réinitialiser le mot de passe"
+#: ../../Zotlabs/Module/Embedphotos.php:139
+#: ../../Zotlabs/Module/Photos.php:751 ../../Zotlabs/Module/Photos.php:1290
+#: ../../Zotlabs/Widget/Album.php:78
+msgid "View Photo"
+msgstr "Voir la photo"
-#: ../../Zotlabs/Module/Lostpass.php:91
-msgid "Your password has been reset as requested."
-msgstr "Votre mot de passe a bien été réinitialisé."
+#: ../../Zotlabs/Module/Embedphotos.php:145
+#: ../../Zotlabs/Module/Photos.php:757 ../../Zotlabs/Module/Photos.php:1213
+#: ../../Zotlabs/Lib/Apps.php:561 ../../Zotlabs/Lib/Apps.php:639
+#: ../../Zotlabs/Storage/Browser.php:163 ../../Zotlabs/Widget/Album.php:84
+#: ../../addon/cdav/Mod_Cdav.php:745 ../../addon/cdav/Mod_Cdav.php:746
+#: ../../addon/cdav/Mod_Cdav.php:753 ../../include/conversation.php:1110
+msgid "Unknown"
+msgstr "Inconnu"
-#: ../../Zotlabs/Module/Lostpass.php:92
-msgid "Your new password is"
-msgstr "Votre nouveau mot de passe est"
+#: ../../Zotlabs/Module/Embedphotos.php:155
+#: ../../Zotlabs/Module/Photos.php:782 ../../Zotlabs/Widget/Album.php:95
+msgid "Edit Album"
+msgstr "Modifier l'album"
-#: ../../Zotlabs/Module/Lostpass.php:93
-msgid "Save or copy your new password - and then"
-msgstr "Enregistrez ou copiez votre nouveau mot de passe, puis"
+#: ../../Zotlabs/Module/Embedphotos.php:157
+#: ../../Zotlabs/Module/Photos.php:784 ../../Zotlabs/Module/Photos.php:1321
+#: ../../Zotlabs/Module/Profile_photo.php:423
+#: ../../Zotlabs/Module/Cover_photo.php:361
+#: ../../Zotlabs/Storage/Browser.php:229 ../../Zotlabs/Storage/Browser.php:334
+#: ../../Zotlabs/Widget/Album.php:97 ../../addon/cdav/include/widgets.php:132
+#: ../../addon/cdav/include/widgets.php:168
+msgid "Upload"
+msgstr "Envoyer"
-#: ../../Zotlabs/Module/Lostpass.php:94
-msgid "click here to login"
-msgstr "cliquez ici pour vous connecter"
+#: ../../Zotlabs/Module/Achievements.php:38
+msgid "Some blurb about what to do when you're new here"
+msgstr "Quelques mots sur quoi faire quand on est nouveau ici"
-#: ../../Zotlabs/Module/Lostpass.php:95
-msgid ""
-"Your password may be changed from the <em>Settings</em> page after "
-"successful login."
-msgstr "Votre mot de passe peut être changé depuis la page des <em>Paramètres</em> une fois connecté."
+#: ../../Zotlabs/Module/Thing.php:114
+msgid "Thing updated"
+msgstr "Elément mis à jour"
-#: ../../Zotlabs/Module/Lostpass.php:112
+#: ../../Zotlabs/Module/Thing.php:166
+msgid "Object store: failed"
+msgstr "Stockage de l'objet&nbsp;: échec"
+
+#: ../../Zotlabs/Module/Thing.php:170
+msgid "Thing added"
+msgstr "Elément ajouté"
+
+#: ../../Zotlabs/Module/Thing.php:196
#, php-format
-msgid "Your password has changed at %s"
-msgstr "Votre mot de passe de %s a été changé"
+msgid "OBJ: %1$s %2$s %3$s"
+msgstr "OBJ: %1$s %2$s %3$s"
-#: ../../Zotlabs/Module/Lostpass.php:127
-msgid "Forgot your Password?"
-msgstr "Mot de passe oublié&nbsp;?"
+#: ../../Zotlabs/Module/Thing.php:259
+msgid "Show Thing"
+msgstr "Montrer élément"
-#: ../../Zotlabs/Module/Lostpass.php:128
-msgid ""
-"Enter your email address and submit to have your password reset. Then check "
-"your email for further instructions."
-msgstr "Saisissez votre adresse de courriel, et validez, pour réinitialiser votre mot de passe. Vérifiez ensuite votre boîte aux lettres pour la suite des instructions."
+#: ../../Zotlabs/Module/Thing.php:266
+msgid "item not found."
+msgstr "élément introuvable."
-#: ../../Zotlabs/Module/Lostpass.php:129
-msgid "Email Address"
-msgstr "Adresse de courriel"
+#: ../../Zotlabs/Module/Thing.php:299
+msgid "Edit Thing"
+msgstr "Modifier élément"
-#: ../../Zotlabs/Module/Lostpass.php:130
-msgid "Reset"
-msgstr "Réinitialiser"
+#: ../../Zotlabs/Module/Thing.php:301 ../../Zotlabs/Module/Thing.php:355
+msgid "Select a profile"
+msgstr "Choisissez un profil"
-#: ../../Zotlabs/Module/Menu.php:49
-msgid "Unable to update menu."
-msgstr "Impossible de mettre le menu à jour."
+#: ../../Zotlabs/Module/Thing.php:305 ../../Zotlabs/Module/Thing.php:358
+msgid "Post an activity"
+msgstr "Publier une activité"
-#: ../../Zotlabs/Module/Menu.php:60
-msgid "Unable to create menu."
-msgstr "Impossible de créer le menu."
+#: ../../Zotlabs/Module/Thing.php:305 ../../Zotlabs/Module/Thing.php:358
+msgid "Only sends to viewers of the applicable profile"
+msgstr "Envoie exclusivement aux visiteurs du profil concerné"
-#: ../../Zotlabs/Module/Menu.php:98 ../../Zotlabs/Module/Menu.php:110
-msgid "Menu Name"
-msgstr "Nom du menu"
+#: ../../Zotlabs/Module/Thing.php:307 ../../Zotlabs/Module/Thing.php:360
+msgid "Name of thing e.g. something"
+msgstr "Nom de l'élément, p.ex. quelque-chose"
-#: ../../Zotlabs/Module/Menu.php:98
-msgid "Unique name (not visible on webpage) - required"
-msgstr "Nom unique (non visible sur la page web) - requis"
+#: ../../Zotlabs/Module/Thing.php:309 ../../Zotlabs/Module/Thing.php:361
+msgid "URL of thing (optional)"
+msgstr "URL de l'élément (facultatif)"
-#: ../../Zotlabs/Module/Menu.php:99 ../../Zotlabs/Module/Menu.php:111
-msgid "Menu Title"
-msgstr "Titre du menu"
+#: ../../Zotlabs/Module/Thing.php:311 ../../Zotlabs/Module/Thing.php:362
+msgid "URL for photo of thing (optional)"
+msgstr "URL d'une photo de l'élément (facultatif)"
-#: ../../Zotlabs/Module/Menu.php:99
-msgid "Visible on webpage - leave empty for no title"
-msgstr "Visible pour la page web - laisser vide pour qu'il n'y ait pas de titre"
+#: ../../Zotlabs/Module/Thing.php:313 ../../Zotlabs/Module/Thing.php:363
+#: ../../Zotlabs/Module/Photos.php:647 ../../Zotlabs/Module/Photos.php:1011
+#: ../../Zotlabs/Module/Connedit.php:680 ../../Zotlabs/Module/Chat.php:233
+#: ../../Zotlabs/Module/Filestorage.php:152
+#: ../../include/acl_selectors.php:218
+msgid "Permissions"
+msgstr "Autorisations"
-#: ../../Zotlabs/Module/Menu.php:100
-msgid "Allow Bookmarks"
-msgstr "Autoriser l'usage de favoris"
+#: ../../Zotlabs/Module/Thing.php:353
+msgid "Add Thing to your Profile"
+msgstr "Ajouter l'élément à votre profil"
-#: ../../Zotlabs/Module/Menu.php:100 ../../Zotlabs/Module/Menu.php:157
-msgid "Menu may be used to store saved bookmarks"
-msgstr "Le menu pourra être utilisé pour stocker des favoris"
+#: ../../Zotlabs/Module/Notify.php:57
+#: ../../Zotlabs/Module/Notifications.php:38
+msgid "No more system notifications."
+msgstr "Pas d'autre notification du système."
-#: ../../Zotlabs/Module/Menu.php:101 ../../Zotlabs/Module/Menu.php:159
-msgid "Submit and proceed"
-msgstr "Valider et continuer"
+#: ../../Zotlabs/Module/Notify.php:61
+#: ../../Zotlabs/Module/Notifications.php:42
+msgid "System Notifications"
+msgstr "Notifications du système"
-#: ../../Zotlabs/Module/Menu.php:107 ../../include/text.php:2266
-msgid "Menus"
-msgstr "Menus"
+#: ../../Zotlabs/Module/Follow.php:31
+msgid "Channel added."
+msgstr "Canal ajouté."
-#: ../../Zotlabs/Module/Menu.php:117
-msgid "Bookmarks allowed"
-msgstr "Favoris autorisés"
+#: ../../Zotlabs/Module/Import.php:144
+#, php-format
+msgid "Your service plan only allows %d channels."
+msgstr "Votre forfait n'autorise que %d canaux."
-#: ../../Zotlabs/Module/Menu.php:119
-msgid "Delete this menu"
-msgstr "Supprimer ce menu"
+#: ../../Zotlabs/Module/Import.php:158
+msgid "No channel. Import failed."
+msgstr "Pas de canal. Echec de l'import."
-#: ../../Zotlabs/Module/Menu.php:120 ../../Zotlabs/Module/Menu.php:154
-msgid "Edit menu contents"
-msgstr "Modifier le contenu du menu"
+#: ../../Zotlabs/Module/Import.php:466
+#: ../../addon/diaspora/import_diaspora.php:142
+msgid "Import completed."
+msgstr "L'import est terminé."
-#: ../../Zotlabs/Module/Menu.php:121
-msgid "Edit this menu"
-msgstr "Modifier ce menu"
+#: ../../Zotlabs/Module/Import.php:492
+msgid "You must be logged in to use this feature."
+msgstr "Vous devez vous connecter pour utiliser cette fonctionnalité."
-#: ../../Zotlabs/Module/Menu.php:136
-msgid "Menu could not be deleted."
-msgstr "Impossible de supprimer le menu."
+#: ../../Zotlabs/Module/Import.php:497
+msgid "Import Channel"
+msgstr "Importation de canal"
-#: ../../Zotlabs/Module/Menu.php:144 ../../Zotlabs/Module/Mitem.php:28
-msgid "Menu not found."
-msgstr "Menu introuvable."
+#: ../../Zotlabs/Module/Import.php:498
+msgid ""
+"Use this form to import an existing channel from a different server/hub. You"
+" may retrieve the channel identity from the old server/hub via the network "
+"or provide an export file."
+msgstr "Utilisez ce formulaire pour importer un canal existant sur un autre serveur. Vous pouvez récupérer l'identité du canal sur l'ancien serveur directement par le réseau, ou bien fournir un fichier d'export/import."
-#: ../../Zotlabs/Module/Menu.php:149
-msgid "Edit Menu"
-msgstr "Modifier le menu"
+#: ../../Zotlabs/Module/Import.php:500
+msgid "Or provide the old server/hub details"
+msgstr "Ou fournissez les détails de l'ancien serveur/hub"
-#: ../../Zotlabs/Module/Menu.php:153
-msgid "Add or remove entries to this menu"
-msgstr "Ajouter/supprimer des entrées à ce menu"
+#: ../../Zotlabs/Module/Import.php:501
+msgid "Your old identity address (xyz@example.com)"
+msgstr "Votre ancienne identité (zyx@exemple.com)"
-#: ../../Zotlabs/Module/Menu.php:155
-msgid "Menu name"
-msgstr "Nom du menu"
+#: ../../Zotlabs/Module/Import.php:502
+msgid "Your old login email address"
+msgstr "Votre ancienne adresse de courriel"
-#: ../../Zotlabs/Module/Menu.php:155
-msgid "Must be unique, only seen by you"
-msgstr "Doit être unique, ne sera vu que par vous"
+#: ../../Zotlabs/Module/Import.php:503
+msgid "Your old login password"
+msgstr "Votre ancien mot de passe"
-#: ../../Zotlabs/Module/Menu.php:156
-msgid "Menu title"
-msgstr "Titre du menu"
+#: ../../Zotlabs/Module/Import.php:504
+msgid ""
+"For either option, please choose whether to make this hub your new primary "
+"address, or whether your old location should continue this role. You will be"
+" able to post from either location, but only one can be marked as the "
+"primary location for files, photos, and media."
+msgstr "Quelle que soit l'option choisie, merci de décider si ce hub sera votre nouvelle adresse primaire, ou si votre ancien hub continuera à jouer ce rôle. Vous pourrez publier depuis l'emplacement de votre choix, mais une seule peut être déclarée comme stockage primaire de vos fichiers/photos/media."
-#: ../../Zotlabs/Module/Menu.php:156
-msgid "Menu title as seen by others"
-msgstr "Titre du menu tel que vu par les visiteurs"
+#: ../../Zotlabs/Module/Import.php:505
+msgid "Make this hub my primary location"
+msgstr "Faire de ce hub mon emplacement primaire"
-#: ../../Zotlabs/Module/Menu.php:157
-msgid "Allow bookmarks"
-msgstr "Autoriser l'usage de favoris"
+#: ../../Zotlabs/Module/Import.php:506
+msgid "Move this channel (disable all previous locations)"
+msgstr "Déplacer ce canal (désactiver tous les emplacements précédents)"
-#: ../../Zotlabs/Module/Menu.php:166 ../../Zotlabs/Module/Mitem.php:120
-#: ../../Zotlabs/Module/Xchan.php:41
-msgid "Not found."
-msgstr "Introuvable."
+#: ../../Zotlabs/Module/Import.php:507
+msgid "Import a few months of posts if possible (limited by available memory"
+msgstr "Importer plusieurs mois de messages si possible (limité par la mémoire disponible)"
-#: ../../Zotlabs/Module/Mood.php:67 ../../include/conversation.php:260
-#, php-format
-msgctxt "mood"
-msgid "%1$s is %2$s"
-msgstr "%1$s est %2$s"
+#: ../../Zotlabs/Module/Import.php:508
+msgid ""
+"This process may take several minutes to complete. Please submit the form "
+"only once and leave this page open until finished."
+msgstr "Ce processus peut prendre plusieurs minutes. Merci de ne valider le formulaire qu'une seule fois et de laisser cette page ouverte jusqu'à la fin."
-#: ../../Zotlabs/Module/Mood.php:135 ../../Zotlabs/Lib/Apps.php:225
-msgid "Mood"
-msgstr "Humeur"
+#: ../../Zotlabs/Module/Rmagic.php:35
+msgid "Authentication failed."
+msgstr "Échec de l'authentification."
-#: ../../Zotlabs/Module/Mood.php:136
-msgid "Set your current mood and tell your friends"
-msgstr "Indiquez votre humeur du moment à vos amis"
+#: ../../Zotlabs/Module/Rmagic.php:75 ../../include/channel.php:1982
+msgid "Remote Authentication"
+msgstr "Authentification distante"
-#: ../../Zotlabs/Module/Match.php:26
-msgid "Profile Match"
-msgstr "Profils similaires"
+#: ../../Zotlabs/Module/Rmagic.php:76 ../../include/channel.php:1983
+msgid "Enter your channel address (e.g. channel@example.com)"
+msgstr "Entrez l'adresse de votre canal (par ex. moncanal@monsite.com)"
-#: ../../Zotlabs/Module/Match.php:35
-msgid "No keywords to match. Please add keywords to your default profile."
-msgstr "Aucun mot-clef à comparer. Merci d'ajouter des mots-clefs à votre profil par défaut."
+#: ../../Zotlabs/Module/Rmagic.php:77 ../../include/channel.php:1984
+msgid "Authenticate"
+msgstr "Authentifier"
-#: ../../Zotlabs/Module/Match.php:67
-msgid "is interested in:"
-msgstr "s'intéresse à&nbsp;:"
+#: ../../Zotlabs/Module/Cal.php:62 ../../Zotlabs/Module/Chanview.php:96
+#: ../../Zotlabs/Module/Page.php:56 ../../Zotlabs/Module/Wall_upload.php:31
+#: ../../Zotlabs/Module/Block.php:43
+msgid "Channel not found."
+msgstr "Canal introuvable."
-#: ../../Zotlabs/Module/Match.php:74
-msgid "No matches"
-msgstr "Pas de correspondance"
+#: ../../Zotlabs/Module/Cal.php:69
+msgid "Permissions denied."
+msgstr "Permissions refusées."
-#: ../../Zotlabs/Module/Network.php:96
-msgid "No such group"
-msgstr "Groupe introuvable"
+#: ../../Zotlabs/Module/Cal.php:342 ../../include/text.php:2299
+msgid "Import"
+msgstr "Import"
-#: ../../Zotlabs/Module/Network.php:136
-msgid "No such channel"
-msgstr "Canal introuvable"
+#: ../../Zotlabs/Module/Api.php:72 ../../Zotlabs/Module/Api.php:93
+msgid "Authorize application connection"
+msgstr "Autoriser l'application à se connecter"
-#: ../../Zotlabs/Module/Network.php:141
-msgid "forum"
-msgstr "forum"
+#: ../../Zotlabs/Module/Api.php:73
+msgid "Return to your app and insert this Security Code:"
+msgstr "Revenez dans votre application et mettez le code de sécurité"
-#: ../../Zotlabs/Module/Network.php:153
-msgid "Search Results For:"
-msgstr "Résultats de recherche pour&nbsp;:"
+#: ../../Zotlabs/Module/Api.php:83
+msgid "Please login to continue."
+msgstr "Merci de vous identifier pour continuer."
-#: ../../Zotlabs/Module/Network.php:217
-msgid "Privacy group is empty"
-msgstr "Groupe d'accès vide"
+#: ../../Zotlabs/Module/Api.php:95
+msgid ""
+"Do you want to authorize this application to access your posts and contacts,"
+" and/or create new posts for you?"
+msgstr "Voulez-vous autoriser cette application à accéder à vos publications et contacts, et/ou à publier en votre nom?"
-#: ../../Zotlabs/Module/Network.php:226
-msgid "Privacy group: "
-msgstr "Groupe d'accès&nbsp;:"
+#: ../../Zotlabs/Module/Attach.php:13
+msgid "Item not available."
+msgstr "Élément indisponible."
-#: ../../Zotlabs/Module/Network.php:252
-msgid "Invalid connection."
-msgstr "Contact non valide."
+#: ../../Zotlabs/Module/Editblock.php:116 ../../Zotlabs/Module/Chat.php:205
+#: ../../Zotlabs/Module/Editwebpage.php:148 ../../Zotlabs/Module/Mail.php:287
+#: ../../Zotlabs/Module/Mail.php:424 ../../include/conversation.php:1228
+msgid "Insert web link"
+msgstr "Insérer lien web"
-#: ../../Zotlabs/Module/Notify.php:57
-#: ../../Zotlabs/Module/Notifications.php:98
-msgid "No more system notifications."
-msgstr "Pas d'autre notification du système."
+#: ../../Zotlabs/Module/Editblock.php:129 ../../include/conversation.php:1339
+msgid "Title (optional)"
+msgstr "Titre (facultatif)"
-#: ../../Zotlabs/Module/Notify.php:61
-#: ../../Zotlabs/Module/Notifications.php:102
-msgid "System Notifications"
-msgstr "Notifications du système"
+#: ../../Zotlabs/Module/Editblock.php:138
+msgid "Edit Block"
+msgstr "Modifier le bloc"
-#: ../../Zotlabs/Module/Mitem.php:52
-msgid "Unable to create element."
-msgstr "Impossible de créer l'entrée."
+#: ../../Zotlabs/Module/Profile.php:91
+msgid "vcard"
+msgstr "vcard"
-#: ../../Zotlabs/Module/Mitem.php:76
-msgid "Unable to update menu element."
-msgstr "Impossible de mettre à jour l'entrée de menu."
+#: ../../Zotlabs/Module/Apps.php:45
+msgid "Apps"
+msgstr "Applications"
-#: ../../Zotlabs/Module/Mitem.php:92
-msgid "Unable to add menu element."
-msgstr "Impossible d'ajouter l'entrée de menu."
+#: ../../Zotlabs/Module/Apps.php:48
+msgid "Manage apps"
+msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:153 ../../Zotlabs/Module/Mitem.php:226
-msgid "Menu Item Permissions"
-msgstr "Permissions de l'entrée de menu"
+#: ../../Zotlabs/Module/Apps.php:49
+msgid "Create new app"
+msgstr ""
-#: ../../Zotlabs/Module/Mitem.php:154 ../../Zotlabs/Module/Mitem.php:227
-#: ../../Zotlabs/Module/Settings.php:1068
-msgid "(click to open/close)"
-msgstr "(cliquer pour ouvrir/fermer)"
+#: ../../Zotlabs/Module/Mood.php:67 ../../include/conversation.php:256
+#, php-format
+msgctxt "mood"
+msgid "%1$s is %2$s"
+msgstr "%1$s est %2$s"
-#: ../../Zotlabs/Module/Mitem.php:156 ../../Zotlabs/Module/Mitem.php:172
-msgid "Link Name"
-msgstr "Nom du lien"
+#: ../../Zotlabs/Module/Mood.php:135 ../../Zotlabs/Lib/Apps.php:234
+msgid "Mood"
+msgstr "Humeur"
-#: ../../Zotlabs/Module/Mitem.php:157 ../../Zotlabs/Module/Mitem.php:231
-msgid "Link or Submenu Target"
-msgstr "Lien ou sous-menu cible"
+#: ../../Zotlabs/Module/Mood.php:136
+msgid "Set your current mood and tell your friends"
+msgstr "Indiquez votre humeur du moment à vos amis"
-#: ../../Zotlabs/Module/Mitem.php:157
-msgid "Enter URL of the link or select a menu name to create a submenu"
-msgstr "Entrez l'URL du lien ou sélectionnez un nom de menu pour créer un sous-menu"
+#: ../../Zotlabs/Module/Connections.php:52
+#: ../../Zotlabs/Module/Connections.php:157
+#: ../../Zotlabs/Module/Connections.php:246
+msgid "Blocked"
+msgstr "Bloqué(e)"
-#: ../../Zotlabs/Module/Mitem.php:158 ../../Zotlabs/Module/Mitem.php:232
-msgid "Use magic-auth if available"
-msgstr "Utiliser l'authentification distante, quand disponible"
+#: ../../Zotlabs/Module/Connections.php:57
+#: ../../Zotlabs/Module/Connections.php:164
+#: ../../Zotlabs/Module/Connections.php:245
+msgid "Ignored"
+msgstr "Ignoré(e)"
-#: ../../Zotlabs/Module/Mitem.php:159 ../../Zotlabs/Module/Mitem.php:233
-msgid "Open link in new window"
-msgstr "Ouvrir le lien dans une nouvelle fenêtre"
+#: ../../Zotlabs/Module/Connections.php:62
+#: ../../Zotlabs/Module/Connections.php:178
+#: ../../Zotlabs/Module/Connections.php:244
+msgid "Hidden"
+msgstr "Caché"
-#: ../../Zotlabs/Module/Mitem.php:160 ../../Zotlabs/Module/Mitem.php:234
-msgid "Order in list"
-msgstr "Ordre dans la liste"
+#: ../../Zotlabs/Module/Connections.php:67
+#: ../../Zotlabs/Module/Connections.php:171
+#: ../../Zotlabs/Module/Connections.php:243
+msgid "Archived"
+msgstr "Archivé"
-#: ../../Zotlabs/Module/Mitem.php:160 ../../Zotlabs/Module/Mitem.php:234
-msgid "Higher numbers will sink to bottom of listing"
-msgstr "Les nombres les plus élevés seront au bas de la liste"
+#: ../../Zotlabs/Module/Connections.php:72
+#: ../../Zotlabs/Module/Connections.php:82 ../../Zotlabs/Module/Menu.php:116
+#: ../../include/conversation.php:1657
+msgid "New"
+msgstr "Nouveautés"
-#: ../../Zotlabs/Module/Mitem.php:161
-msgid "Submit and finish"
-msgstr "Vadiler et terminer"
+#: ../../Zotlabs/Module/Connections.php:88
+#: ../../Zotlabs/Module/Connections.php:103
+#: ../../Zotlabs/Module/Connedit.php:717 ../../Zotlabs/Widget/Affinity.php:30
+msgid "All"
+msgstr "Tous"
-#: ../../Zotlabs/Module/Mitem.php:162
-msgid "Submit and continue"
-msgstr "Valider et continuer"
+#: ../../Zotlabs/Module/Connections.php:134
+msgid "New Connections"
+msgstr "Nouveaux contacts"
-#: ../../Zotlabs/Module/Mitem.php:170
-msgid "Menu:"
-msgstr "Menu&nbsp;:"
+#: ../../Zotlabs/Module/Connections.php:137
+msgid "Show pending (new) connections"
+msgstr "Voir les (nouveaux) contacts en attente"
-#: ../../Zotlabs/Module/Mitem.php:173
-msgid "Link Target"
-msgstr "Cible du lien"
+#: ../../Zotlabs/Module/Connections.php:144
+msgid "Show all connections"
+msgstr "Voir tous les contacts"
-#: ../../Zotlabs/Module/Mitem.php:176
-msgid "Edit menu"
-msgstr "Modifier le menu"
+#: ../../Zotlabs/Module/Connections.php:160
+msgid "Only show blocked connections"
+msgstr "Ne montrer que les contacts bloqués"
-#: ../../Zotlabs/Module/Mitem.php:179
-msgid "Edit element"
-msgstr "Modifier l'entrée"
+#: ../../Zotlabs/Module/Connections.php:167
+msgid "Only show ignored connections"
+msgstr "Ne montrer que les contacts ignorés"
-#: ../../Zotlabs/Module/Mitem.php:180
-msgid "Drop element"
-msgstr "Supprimer l'entrée"
+#: ../../Zotlabs/Module/Connections.php:174
+msgid "Only show archived connections"
+msgstr "Ne montrer que les contacts archivés"
-#: ../../Zotlabs/Module/Mitem.php:181
-msgid "New element"
-msgstr "Nouvelle entrée"
+#: ../../Zotlabs/Module/Connections.php:181
+msgid "Only show hidden connections"
+msgstr "Ne montrer que les contacts cachés"
-#: ../../Zotlabs/Module/Mitem.php:182
-msgid "Edit this menu container"
-msgstr "Éditer ce bloc de menu"
+#: ../../Zotlabs/Module/Connections.php:242
+msgid "Pending approval"
+msgstr "En attente de validation"
-#: ../../Zotlabs/Module/Mitem.php:183
-msgid "Add menu element"
-msgstr "Ajouter une entrée au menu"
+#: ../../Zotlabs/Module/Connections.php:258
+#, php-format
+msgid "%1$s [%2$s]"
+msgstr "%1$s [%2$s]"
-#: ../../Zotlabs/Module/Mitem.php:184
-msgid "Delete this menu item"
-msgstr "Supprimer cette entrée du menu"
+#: ../../Zotlabs/Module/Connections.php:259
+msgid "Edit connection"
+msgstr "Modifier le contact"
-#: ../../Zotlabs/Module/Mitem.php:185
-msgid "Edit this menu item"
-msgstr "Modifier cette entrée du menu"
+#: ../../Zotlabs/Module/Connections.php:260
+msgid "Delete connection"
+msgstr "Supprimer le contact"
-#: ../../Zotlabs/Module/Mitem.php:202
-msgid "Menu item not found."
-msgstr "Entrée de menu introuvable."
+#: ../../Zotlabs/Module/Connections.php:269
+msgid "Channel address"
+msgstr "Adresse du canal"
-#: ../../Zotlabs/Module/Mitem.php:215
-msgid "Menu item deleted."
-msgstr "Entrée de menu supprimée."
+#: ../../Zotlabs/Module/Connections.php:271
+msgid "Network"
+msgstr "Réseau"
-#: ../../Zotlabs/Module/Mitem.php:217
-msgid "Menu item could not be deleted."
-msgstr "Impossible de supprimer l'entrée de menu."
+#: ../../Zotlabs/Module/Connections.php:274
+msgid "Call"
+msgstr "Appeler"
-#: ../../Zotlabs/Module/Mitem.php:224
-msgid "Edit Menu Element"
-msgstr "Modifier l'entrée de menu"
+#: ../../Zotlabs/Module/Connections.php:276
+msgid "Status"
+msgstr "État"
-#: ../../Zotlabs/Module/Mitem.php:230
-msgid "Link text"
-msgstr "Texte du lien"
+#: ../../Zotlabs/Module/Connections.php:278
+msgid "Connected"
+msgstr "Ami depuis"
-#: ../../Zotlabs/Module/New_channel.php:128
-#: ../../Zotlabs/Module/Register.php:231
-msgid "Name or caption"
-msgstr "Nom ou libellé"
+#: ../../Zotlabs/Module/Connections.php:280
+msgid "Approve connection"
+msgstr "Valider le contact"
-#: ../../Zotlabs/Module/New_channel.php:128
-#: ../../Zotlabs/Module/Register.php:231
-msgid "Examples: \"Bob Jameson\", \"Lisa and her Horses\", \"Soccer\", \"Aviation Group\""
-msgstr "Exemples&nbsp;: \"Jérôme Dutilleul\", \"Louise et ses chevaux\", \"Football\", \"Club d'aéromodélisme\""
+#: ../../Zotlabs/Module/Connections.php:282
+msgid "Ignore connection"
+msgstr "Ignorer le contact"
-#: ../../Zotlabs/Module/New_channel.php:130
-#: ../../Zotlabs/Module/Register.php:233
-msgid "Choose a short nickname"
-msgstr "Choisissez un alias"
+#: ../../Zotlabs/Module/Connections.php:283
+#: ../../Zotlabs/Module/Connedit.php:634
+msgid "Ignore"
+msgstr "Ignorer"
-#: ../../Zotlabs/Module/New_channel.php:130
-#: ../../Zotlabs/Module/Register.php:233
-#, php-format
-msgid ""
-"Your nickname will be used to create an easy to remember channel address "
-"e.g. nickname%s"
-msgstr "Votre pseudo sera utilisé pour créer une adresse de canal facile à mémoriser, par ex. pseudo%s"
+#: ../../Zotlabs/Module/Connections.php:284
+msgid "Recent activity"
+msgstr "Activité récente"
-#: ../../Zotlabs/Module/New_channel.php:132
-#: ../../Zotlabs/Module/Register.php:235
-msgid "Channel role and privacy"
-msgstr "Rôle et confidentialité du canal"
+#: ../../Zotlabs/Module/Connections.php:308 ../../Zotlabs/Lib/Apps.php:216
+#: ../../include/text.php:957 ../../include/nav.php:181
+msgid "Connections"
+msgstr "Contacts"
-#: ../../Zotlabs/Module/New_channel.php:132
-#: ../../Zotlabs/Module/Register.php:235
-msgid "Select a channel role with your privacy requirements."
-msgstr "Sélectionner un rôle de canal adapté à vos besoins de confidentialité."
+#: ../../Zotlabs/Module/Connections.php:313
+msgid "Search your connections"
+msgstr "Chercher parmi vos contacts"
-#: ../../Zotlabs/Module/New_channel.php:132
-#: ../../Zotlabs/Module/Register.php:235
-msgid "Read more about roles"
-msgstr "En savoir plus sur les rôles"
+#: ../../Zotlabs/Module/Connections.php:314
+msgid "Connections search"
+msgstr "Chercher des contacts"
-#: ../../Zotlabs/Module/New_channel.php:135
-msgid "Create Channel"
-msgstr "Créer le canal"
+#: ../../Zotlabs/Module/Connections.php:315
+#: ../../Zotlabs/Module/Directory.php:391
+#: ../../Zotlabs/Module/Directory.php:396 ../../include/contact_widgets.php:23
+msgid "Find"
+msgstr "Trouver"
-#: ../../Zotlabs/Module/New_channel.php:136
-msgid ""
-"A channel is your identity on this network. It can represent a person, a "
-"blog, or a forum to name a few. Channels can make connections with other "
-"channels to share information with highly detailed permissions."
-msgstr "Un canal est votre identité sur ce réseau. Il peut représenter une personne, un blog, ou un forum par exemple. Les canaux peuvent entrer en contact les uns avec les autres pour partager des informations avec des permissions d'accès très fines."
+#: ../../Zotlabs/Module/Viewsrc.php:46
+msgid "Source of Item"
+msgstr "Source de l'élément"
-#: ../../Zotlabs/Module/New_channel.php:137
+#: ../../Zotlabs/Module/Bookmarks.php:53
+msgid "Bookmark added"
+msgstr "Favori ajouté"
+
+#: ../../Zotlabs/Module/Bookmarks.php:76
+msgid "My Bookmarks"
+msgstr "Mes Favoris"
+
+#: ../../Zotlabs/Module/Bookmarks.php:87
+msgid "My Connections Bookmarks"
+msgstr "Favoris de mes contacts"
+
+#: ../../Zotlabs/Module/Removeaccount.php:35
msgid ""
-"or <a href=\"import\">import an existing channel</a> from another location."
-msgstr "ou <a href=\"import\">importer un canal existant</a> d'un autre serveur."
+"Account removals are not allowed within 48 hours of changing the account "
+"password."
+msgstr "Il est impossible de supprimer un compte dans les 48 heures après avoir changé le mot de passe du compte."
-#: ../../Zotlabs/Module/Notifications.php:30
-msgid "Invalid request identifier."
-msgstr "Identifiant de requête invalide."
+#: ../../Zotlabs/Module/Removeaccount.php:57
+msgid "Remove This Account"
+msgstr "Supprimer ce compte"
-#: ../../Zotlabs/Module/Notifications.php:39
-msgid "Discard"
-msgstr "Annuler"
+#: ../../Zotlabs/Module/Removeaccount.php:58
+msgid ""
+"This account and all its channels will be completely removed from the "
+"network. "
+msgstr "Ce compte et tous ses canaux seront entièrement supprimés du réseau."
-#: ../../Zotlabs/Module/Notifications.php:103 ../../include/nav.php:191
-msgid "Mark all system notifications seen"
-msgstr "Marquer toutes les notifications système comme vues"
+#: ../../Zotlabs/Module/Removeaccount.php:60
+msgid ""
+"Remove this account, all its channels and all its channel clones from the "
+"network"
+msgstr "Supprimer du réseau ce compte, tous ses canaux et tous les clones de ses canaux."
-#: ../../Zotlabs/Module/Photos.php:84
+#: ../../Zotlabs/Module/Removeaccount.php:60
+msgid ""
+"By default only the instances of the channels located on this hub will be "
+"removed from the network"
+msgstr "Par défaut, seules les instances des canaux situés sur ce hub seront supprimées du réseau"
+
+#: ../../Zotlabs/Module/Photos.php:78
msgid "Page owner information could not be retrieved."
msgstr "Impossible d'obtenir des informations sur le propriétaire de la page."
-#: ../../Zotlabs/Module/Photos.php:99 ../../Zotlabs/Module/Photos.php:743
-#: ../../Zotlabs/Module/Profile_photo.php:114
-#: ../../Zotlabs/Module/Profile_photo.php:206
-#: ../../Zotlabs/Module/Profile_photo.php:294
-#: ../../include/photo/photo_driver.php:718
-msgid "Profile Photos"
-msgstr "Photos du profil"
-
-#: ../../Zotlabs/Module/Photos.php:105 ../../Zotlabs/Module/Photos.php:149
+#: ../../Zotlabs/Module/Photos.php:94 ../../Zotlabs/Module/Photos.php:120
msgid "Album not found."
msgstr "Album introuvable."
-#: ../../Zotlabs/Module/Photos.php:132
+#: ../../Zotlabs/Module/Photos.php:103
msgid "Delete Album"
msgstr "Supprimer l'album"
-#: ../../Zotlabs/Module/Photos.php:153
-msgid ""
-"Multiple storage folders exist with this album name, but within different "
-"directories. Please remove the desired folder or folders using the Files "
-"manager"
-msgstr ""
-
-#: ../../Zotlabs/Module/Photos.php:210 ../../Zotlabs/Module/Photos.php:1053
+#: ../../Zotlabs/Module/Photos.php:174 ../../Zotlabs/Module/Photos.php:1023
msgid "Delete Photo"
msgstr "Supprimer la photo"
-#: ../../Zotlabs/Module/Photos.php:533
+#: ../../Zotlabs/Module/Photos.php:501
msgid "No photos selected"
msgstr "Aucune photo selectionnée"
-#: ../../Zotlabs/Module/Photos.php:582
+#: ../../Zotlabs/Module/Photos.php:550
msgid "Access to this item is restricted."
msgstr "L'accès à l'élément est restreint."
-#: ../../Zotlabs/Module/Photos.php:621
+#: ../../Zotlabs/Module/Photos.php:591
#, php-format
msgid "%1$.2f MB of %2$.2f MB photo storage used."
msgstr "Vous avez utilisé %1$.2f mégaoctets sur les %2$.2f autorisés pour le stockage des photos."
-#: ../../Zotlabs/Module/Photos.php:624
+#: ../../Zotlabs/Module/Photos.php:594
#, php-format
msgid "%1$.2f MB photo storage used."
msgstr "%1$.2f méga-octets utilisés pour le stockage des photos."
-#: ../../Zotlabs/Module/Photos.php:660
+#: ../../Zotlabs/Module/Photos.php:636
msgid "Upload Photos"
msgstr "Téléverser des photos"
-#: ../../Zotlabs/Module/Photos.php:664
+#: ../../Zotlabs/Module/Photos.php:640
msgid "Enter an album name"
msgstr "Entrer un nom d'album"
-#: ../../Zotlabs/Module/Photos.php:665
+#: ../../Zotlabs/Module/Photos.php:641
msgid "or select an existing album (doubleclick)"
msgstr "ou sélectionner un album existant (double-clic)"
-#: ../../Zotlabs/Module/Photos.php:666
+#: ../../Zotlabs/Module/Photos.php:642
msgid "Create a status post for this upload"
msgstr "Créer une publication de statut pour cet envoi"
-#: ../../Zotlabs/Module/Photos.php:667
+#: ../../Zotlabs/Module/Photos.php:643
msgid "Caption (optional):"
msgstr "Légende (facultative)"
-#: ../../Zotlabs/Module/Photos.php:668
+#: ../../Zotlabs/Module/Photos.php:644
msgid "Description (optional):"
msgstr "Description (facultative)"
-#: ../../Zotlabs/Module/Photos.php:695
-msgid "Album name could not be decoded"
-msgstr "Le nom de l'Album n'a pu être décodé"
-
-#: ../../Zotlabs/Module/Photos.php:743
-msgid "Contact Photos"
-msgstr "Photos de contact"
-
-#: ../../Zotlabs/Module/Photos.php:766
+#: ../../Zotlabs/Module/Photos.php:725
msgid "Show Newest First"
msgstr "Les plus récent(e)s en premier"
-#: ../../Zotlabs/Module/Photos.php:768
+#: ../../Zotlabs/Module/Photos.php:727
msgid "Show Oldest First"
msgstr "Les moins récent(e)s en premier"
-#: ../../Zotlabs/Module/Photos.php:792 ../../Zotlabs/Module/Photos.php:1331
-#: ../../include/widgets.php:1499
-msgid "View Photo"
-msgstr "Voir la photo"
-
-#: ../../Zotlabs/Module/Photos.php:823 ../../include/widgets.php:1516
-msgid "Edit Album"
-msgstr "Modifier l'album"
-
-#: ../../Zotlabs/Module/Photos.php:870
+#: ../../Zotlabs/Module/Photos.php:832
msgid "Permission denied. Access to this item may be restricted."
msgstr "Permission refusée. L'accès à cet élément peut avoir été restreint."
-#: ../../Zotlabs/Module/Photos.php:872
+#: ../../Zotlabs/Module/Photos.php:834
msgid "Photo not available"
msgstr "Photo non disponible"
-#: ../../Zotlabs/Module/Photos.php:930
+#: ../../Zotlabs/Module/Photos.php:892
msgid "Use as profile photo"
msgstr "Utiliser comme photo du profil"
-#: ../../Zotlabs/Module/Photos.php:931
+#: ../../Zotlabs/Module/Photos.php:893
msgid "Use as cover photo"
-msgstr ""
+msgstr "Utilisez comme bannière"
-#: ../../Zotlabs/Module/Photos.php:938
+#: ../../Zotlabs/Module/Photos.php:900
msgid "Private Photo"
msgstr "Photo privée"
-#: ../../Zotlabs/Module/Photos.php:953
+#: ../../Zotlabs/Module/Photos.php:915
msgid "View Full Size"
msgstr "Voir en taille réelle"
-#: ../../Zotlabs/Module/Photos.php:998 ../../Zotlabs/Module/Admin.php:1437
-#: ../../Zotlabs/Module/Tagrm.php:137
-msgid "Remove"
-msgstr "Retirer"
-
-#: ../../Zotlabs/Module/Photos.php:1032
+#: ../../Zotlabs/Module/Photos.php:997
msgid "Edit photo"
msgstr "Modifier la photo"
-#: ../../Zotlabs/Module/Photos.php:1034
+#: ../../Zotlabs/Module/Photos.php:999
msgid "Rotate CW (right)"
msgstr "Rotation horaire (droite)"
-#: ../../Zotlabs/Module/Photos.php:1035
+#: ../../Zotlabs/Module/Photos.php:1000
msgid "Rotate CCW (left)"
msgstr "Rotation anti-horaire (gauche)"
-#: ../../Zotlabs/Module/Photos.php:1038
+#: ../../Zotlabs/Module/Photos.php:1003
+msgid "Move photo to album"
+msgstr "Déplacer la photo dans l'album"
+
+#: ../../Zotlabs/Module/Photos.php:1004
msgid "Enter a new album name"
msgstr "Entrer un nouveau nom d'album"
-#: ../../Zotlabs/Module/Photos.php:1039
+#: ../../Zotlabs/Module/Photos.php:1005
msgid "or select an existing one (doubleclick)"
msgstr "ou en sélectionner un existant (double-clic)"
-#: ../../Zotlabs/Module/Photos.php:1042
+#: ../../Zotlabs/Module/Photos.php:1008
msgid "Caption"
msgstr "Titre/légende"
-#: ../../Zotlabs/Module/Photos.php:1044
+#: ../../Zotlabs/Module/Photos.php:1010
msgid "Add a Tag"
msgstr "Ajouter une étiquette"
-#: ../../Zotlabs/Module/Photos.php:1048
+#: ../../Zotlabs/Module/Photos.php:1018
msgid "Example: @bob, @Barbara_Jensen, @jim@example.com"
msgstr "Exemple&nbsp;: @marc, @Barbara_Jensen, @charles@exemple.com, #Ile_de_France, #marathon"
-#: ../../Zotlabs/Module/Photos.php:1051
+#: ../../Zotlabs/Module/Photos.php:1021
msgid "Flag as adult in album view"
msgstr "Marquer comme \"adulte\" dans l'affichage de l'album"
-#: ../../Zotlabs/Module/Photos.php:1070 ../../Zotlabs/Lib/ThreadItem.php:261
+#: ../../Zotlabs/Module/Photos.php:1040 ../../Zotlabs/Lib/ThreadItem.php:269
msgid "I like this (toggle)"
msgstr "J'aime (oui/non)"
-#: ../../Zotlabs/Module/Photos.php:1071 ../../Zotlabs/Lib/ThreadItem.php:262
+#: ../../Zotlabs/Module/Photos.php:1041 ../../Zotlabs/Lib/ThreadItem.php:270
msgid "I don't like this (toggle)"
msgstr "Je n'aime pas (oui/non)"
-#: ../../Zotlabs/Module/Photos.php:1073 ../../Zotlabs/Lib/ThreadItem.php:397
-#: ../../include/conversation.php:740
+#: ../../Zotlabs/Module/Photos.php:1043 ../../Zotlabs/Lib/ThreadItem.php:412
+#: ../../include/conversation.php:739
msgid "Please wait"
msgstr "Merci de patienter"
-#: ../../Zotlabs/Module/Photos.php:1089 ../../Zotlabs/Module/Photos.php:1207
-#: ../../Zotlabs/Lib/ThreadItem.php:707
+#: ../../Zotlabs/Module/Photos.php:1059 ../../Zotlabs/Module/Photos.php:1177
+#: ../../Zotlabs/Lib/ThreadItem.php:729
msgid "This is you"
msgstr "C'est vous"
-#: ../../Zotlabs/Module/Photos.php:1091 ../../Zotlabs/Module/Photos.php:1209
-#: ../../Zotlabs/Lib/ThreadItem.php:709 ../../include/js_strings.php:6
+#: ../../Zotlabs/Module/Photos.php:1061 ../../Zotlabs/Module/Photos.php:1179
+#: ../../Zotlabs/Lib/ThreadItem.php:731 ../../include/js_strings.php:6
msgid "Comment"
msgstr "Commenter"
-#: ../../Zotlabs/Module/Photos.php:1107 ../../include/conversation.php:574
+#: ../../Zotlabs/Module/Photos.php:1077 ../../include/conversation.php:574
msgctxt "title"
msgid "Likes"
msgstr "Aime"
-#: ../../Zotlabs/Module/Photos.php:1107 ../../include/conversation.php:574
+#: ../../Zotlabs/Module/Photos.php:1077 ../../include/conversation.php:574
msgctxt "title"
msgid "Dislikes"
msgstr "N'aime pas"
-#: ../../Zotlabs/Module/Photos.php:1108 ../../include/conversation.php:575
+#: ../../Zotlabs/Module/Photos.php:1078 ../../include/conversation.php:575
msgctxt "title"
msgid "Agree"
msgstr "D'accord"
-#: ../../Zotlabs/Module/Photos.php:1108 ../../include/conversation.php:575
+#: ../../Zotlabs/Module/Photos.php:1078 ../../include/conversation.php:575
msgctxt "title"
msgid "Disagree"
msgstr "Pas d'accord"
-#: ../../Zotlabs/Module/Photos.php:1108 ../../include/conversation.php:575
+#: ../../Zotlabs/Module/Photos.php:1078 ../../include/conversation.php:575
msgctxt "title"
msgid "Abstain"
msgstr "Abstention"
-#: ../../Zotlabs/Module/Photos.php:1109 ../../include/conversation.php:576
+#: ../../Zotlabs/Module/Photos.php:1079 ../../include/conversation.php:576
msgctxt "title"
msgid "Attending"
msgstr "Participations"
-#: ../../Zotlabs/Module/Photos.php:1109 ../../include/conversation.php:576
+#: ../../Zotlabs/Module/Photos.php:1079 ../../include/conversation.php:576
msgctxt "title"
msgid "Not attending"
msgstr "Non-participations"
-#: ../../Zotlabs/Module/Photos.php:1109 ../../include/conversation.php:576
+#: ../../Zotlabs/Module/Photos.php:1079 ../../include/conversation.php:576
msgctxt "title"
msgid "Might attend"
msgstr "Participation possible"
-#: ../../Zotlabs/Module/Photos.php:1126 ../../Zotlabs/Module/Photos.php:1138
-#: ../../Zotlabs/Lib/ThreadItem.php:181 ../../Zotlabs/Lib/ThreadItem.php:193
-#: ../../include/conversation.php:1717
+#: ../../Zotlabs/Module/Photos.php:1096 ../../Zotlabs/Module/Photos.php:1108
+#: ../../Zotlabs/Lib/ThreadItem.php:187 ../../Zotlabs/Lib/ThreadItem.php:199
msgid "View all"
msgstr "Voir tout"
-#: ../../Zotlabs/Module/Photos.php:1130 ../../Zotlabs/Lib/ThreadItem.php:185
-#: ../../include/taxonomy.php:403 ../../include/conversation.php:1741
-#: ../../include/channel.php:1158
+#: ../../Zotlabs/Module/Photos.php:1100 ../../Zotlabs/Lib/ThreadItem.php:191
+#: ../../include/conversation.php:1898 ../../include/channel.php:1266
+#: ../../include/taxonomy.php:403
msgctxt "noun"
msgid "Like"
msgid_plural "Likes"
msgstr[0] "Aime"
msgstr[1] "Aime"
-#: ../../Zotlabs/Module/Photos.php:1135 ../../Zotlabs/Lib/ThreadItem.php:190
-#: ../../include/conversation.php:1744
+#: ../../Zotlabs/Module/Photos.php:1105 ../../Zotlabs/Lib/ThreadItem.php:196
+#: ../../include/conversation.php:1901
msgctxt "noun"
msgid "Dislike"
msgid_plural "Dislikes"
msgstr[0] "N'aime pas"
msgstr[1] "N'aime pas"
-#: ../../Zotlabs/Module/Photos.php:1235
+#: ../../Zotlabs/Module/Photos.php:1205
msgid "Photo Tools"
-msgstr ""
+msgstr "Ouitls pour photos"
-#: ../../Zotlabs/Module/Photos.php:1244
+#: ../../Zotlabs/Module/Photos.php:1214
msgid "In This Photo:"
msgstr "Dans cette photo&nbsp;:"
-#: ../../Zotlabs/Module/Photos.php:1249
+#: ../../Zotlabs/Module/Photos.php:1219
msgid "Map"
msgstr "Carte"
-#: ../../Zotlabs/Module/Photos.php:1257 ../../Zotlabs/Lib/ThreadItem.php:386
+#: ../../Zotlabs/Module/Photos.php:1227 ../../Zotlabs/Lib/ThreadItem.php:401
msgctxt "noun"
msgid "Likes"
msgstr "Aime"
-#: ../../Zotlabs/Module/Photos.php:1258 ../../Zotlabs/Lib/ThreadItem.php:387
+#: ../../Zotlabs/Module/Photos.php:1228 ../../Zotlabs/Lib/ThreadItem.php:402
msgctxt "noun"
msgid "Dislikes"
msgstr "N'aime pas"
-#: ../../Zotlabs/Module/Photos.php:1263 ../../Zotlabs/Lib/ThreadItem.php:392
-#: ../../include/acl_selectors.php:285
+#: ../../Zotlabs/Module/Photos.php:1233 ../../Zotlabs/Lib/ThreadItem.php:407
+#: ../../include/acl_selectors.php:220
msgid "Close"
msgstr "Fermer"
-#: ../../Zotlabs/Module/Photos.php:1337
-msgid "View Album"
-msgstr "Voir l'album"
-
-#: ../../Zotlabs/Module/Photos.php:1348 ../../Zotlabs/Module/Photos.php:1361
-#: ../../Zotlabs/Module/Photos.php:1362
+#: ../../Zotlabs/Module/Photos.php:1305 ../../Zotlabs/Module/Photos.php:1318
+#: ../../Zotlabs/Module/Photos.php:1319 ../../include/photos.php:528
msgid "Recent Photos"
msgstr "Photos récentes"
-#: ../../Zotlabs/Module/Ping.php:265
-msgid "sent you a private message"
-msgstr "vous a envoyé un message privé"
+#: ../../Zotlabs/Module/Wiki.php:30
+msgid "Profile Unavailable."
+msgstr "Profil non disponible."
-#: ../../Zotlabs/Module/Ping.php:313
-msgid "added your channel"
-msgstr "a ajouté votre canal"
+#: ../../Zotlabs/Module/Wiki.php:44 ../../addon/gitwiki/Mod_Gitwiki.php:42
+msgid "Not found"
+msgstr "Non trouvé"
-#: ../../Zotlabs/Module/Ping.php:323
-msgid "g A l F d"
-msgstr "g A l F d"
+#: ../../Zotlabs/Module/Wiki.php:68 ../../addon/gitwiki/Mod_Gitwiki.php:62
+msgid "Invalid channel"
+msgstr "Canal invalide."
-#: ../../Zotlabs/Module/Ping.php:346
-msgid "[today]"
-msgstr "[aujourd'hui]"
+#: ../../Zotlabs/Module/Wiki.php:160 ../../addon/gitwiki/Mod_Gitwiki.php:146
+#: ../../include/conversation.php:1845
+msgid "Wikis"
+msgstr "Wikis"
-#: ../../Zotlabs/Module/Ping.php:355
-msgid "posted an event"
-msgstr "a publié un événement"
+#: ../../Zotlabs/Module/Wiki.php:166 ../../addon/gitwiki/Mod_Gitwiki.php:152
+msgid "Download"
+msgstr "Téléchargement"
-#: ../../Zotlabs/Module/Oexchange.php:27
-msgid "Unable to find your hub."
-msgstr "Impossible de trouver votre hub."
+#: ../../Zotlabs/Module/Wiki.php:168 ../../Zotlabs/Module/Chat.php:254
+#: ../../Zotlabs/Module/Profiles.php:834 ../../Zotlabs/Module/Manage.php:143
+#: ../../addon/gitwiki/Mod_Gitwiki.php:154
+msgid "Create New"
+msgstr "Nouveau"
-#: ../../Zotlabs/Module/Oexchange.php:41
-msgid "Post successful."
-msgstr "Publication réussie."
+#: ../../Zotlabs/Module/Wiki.php:170 ../../addon/gitwiki/Mod_Gitwiki.php:156
+msgid "Wiki name"
+msgstr "Nom du wiki"
-#: ../../Zotlabs/Module/Openid.php:30
-msgid "OpenID protocol error. No ID returned."
-msgstr "Erreur du protocole OpenID. Pas d'ID retourné."
+#: ../../Zotlabs/Module/Wiki.php:171 ../../addon/gitwiki/Mod_Gitwiki.php:157
+msgid "Content type"
+msgstr "Type de contenu"
-#: ../../Zotlabs/Module/Openid.php:193 ../../include/auth.php:226
-msgid "Login failed."
-msgstr "Échec de la connexion."
+#: ../../Zotlabs/Module/Wiki.php:173 ../../Zotlabs/Storage/Browser.php:234
+#: ../../addon/gitwiki/Mod_Gitwiki.php:159
+msgid "Type"
+msgstr "Type"
-#: ../../Zotlabs/Module/Page.php:133
-msgid ""
-"Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod "
-"tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam,"
-" quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo "
-"consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse "
-"cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat "
-"non proident, sunt in culpa qui officia deserunt mollit anim id est laborum."
-msgstr "Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum."
+#: ../../Zotlabs/Module/Wiki.php:180 ../../addon/gitwiki/Mod_Gitwiki.php:166
+msgid "Create a status post for this wiki"
+msgstr "Créer un statut de publication pour ce wiki"
-#: ../../Zotlabs/Module/Pconfig.php:26 ../../Zotlabs/Module/Pconfig.php:59
-msgid "This setting requires special processing and editing has been blocked."
-msgstr "Ce paramètre nécessité un traitement spécial, les modifications ont été bloquées."
+#: ../../Zotlabs/Module/Wiki.php:205 ../../addon/gitwiki/Mod_Gitwiki.php:185
+msgid "Wiki not found"
+msgstr "Wiki introuvable"
-#: ../../Zotlabs/Module/Pconfig.php:48
-msgid "Configuration Editor"
-msgstr "Editeur de configuration"
+#: ../../Zotlabs/Module/Wiki.php:229 ../../addon/gitwiki/Mod_Gitwiki.php:210
+msgid "Rename page"
+msgstr "Renommer la page"
-#: ../../Zotlabs/Module/Pconfig.php:49
-msgid ""
-"Warning: Changing some settings could render your channel inoperable. Please"
-" leave this page unless you are comfortable with and knowledgeable about how"
-" to correctly use this feature."
-msgstr "Attention&nbsp;:modifier certains paramètres peut rendre votre canal inutilisable. Merci d'ignorer cette page à moins d'être suffisamment à l'aise de savoir comment utiliser correctement cette fonctionnalité."
+#: ../../Zotlabs/Module/Wiki.php:233 ../../addon/gitwiki/Mod_Gitwiki.php:214
+msgid "Error retrieving page content"
+msgstr "Erreur lors de la récupération du contenu de la page"
+
+#: ../../Zotlabs/Module/Wiki.php:239
+msgid "New page"
+msgstr ""
+
+#: ../../Zotlabs/Module/Wiki.php:263 ../../addon/gitwiki/Mod_Gitwiki.php:242
+msgid "Revision Comparison"
+msgstr "Comparaison des révisions"
+
+#: ../../Zotlabs/Module/Wiki.php:264 ../../addon/gitwiki/Mod_Gitwiki.php:243
+msgid "Revert"
+msgstr "Revenir"
+
+#: ../../Zotlabs/Module/Wiki.php:268
+msgid "Short description of your changes (optional)"
+msgstr "Description courte de vos modifications (optionnel)"
+
+#: ../../Zotlabs/Module/Wiki.php:275 ../../addon/gitwiki/Mod_Gitwiki.php:252
+msgid "Source"
+msgstr "Source"
+
+#: ../../Zotlabs/Module/Wiki.php:283 ../../addon/gitwiki/Mod_Gitwiki.php:260
+msgid "New page name"
+msgstr "Nouveau nom de la page"
+
+#: ../../Zotlabs/Module/Wiki.php:288 ../../addon/gitwiki/Mod_Gitwiki.php:265
+#: ../../include/conversation.php:1232
+msgid "Embed image from photo albums"
+msgstr "Intégrer une image d'un album photo"
+
+#: ../../Zotlabs/Module/Wiki.php:289 ../../addon/gitwiki/Mod_Gitwiki.php:266
+#: ../../include/conversation.php:1326
+msgid "Embed an image from your albums"
+msgstr "Intégrer une image de votre album photo"
+
+#: ../../Zotlabs/Module/Wiki.php:291 ../../addon/gitwiki/Mod_Gitwiki.php:268
+#: ../../include/conversation.php:1328 ../../include/conversation.php:1375
+msgid "OK"
+msgstr "OK"
+
+#: ../../Zotlabs/Module/Wiki.php:292 ../../addon/gitwiki/Mod_Gitwiki.php:269
+#: ../../include/conversation.php:1268
+msgid "Choose images to embed"
+msgstr "Choisissez des images à intégrer"
+
+#: ../../Zotlabs/Module/Wiki.php:293 ../../addon/gitwiki/Mod_Gitwiki.php:270
+#: ../../include/conversation.php:1269
+msgid "Choose an album"
+msgstr "Choisir un album"
+
+#: ../../Zotlabs/Module/Wiki.php:294 ../../addon/gitwiki/Mod_Gitwiki.php:271
+msgid "Choose a different album"
+msgstr "Choisissez un autre album"
+
+#: ../../Zotlabs/Module/Wiki.php:295 ../../addon/gitwiki/Mod_Gitwiki.php:272
+#: ../../include/conversation.php:1271
+msgid "Error getting album list"
+msgstr "Erreur venant de la liste de l'album"
+
+#: ../../Zotlabs/Module/Wiki.php:296 ../../addon/gitwiki/Mod_Gitwiki.php:273
+#: ../../include/conversation.php:1272
+msgid "Error getting photo link"
+msgstr "Erreur provenant du lien de la photo"
+
+#: ../../Zotlabs/Module/Wiki.php:297 ../../addon/gitwiki/Mod_Gitwiki.php:274
+#: ../../include/conversation.php:1273
+msgid "Error getting album"
+msgstr "Erreur venant de l'album"
+
+#: ../../Zotlabs/Module/Wiki.php:364 ../../addon/gitwiki/Mod_Gitwiki.php:337
+msgid "Error creating wiki. Invalid name."
+msgstr "Erreur lors de la création du wiki. Nom invalide."
+
+#: ../../Zotlabs/Module/Wiki.php:371
+msgid "A wiki with this name already exists."
+msgstr ""
+
+#: ../../Zotlabs/Module/Wiki.php:384 ../../addon/gitwiki/Mod_Gitwiki.php:348
+msgid "Wiki created, but error creating Home page."
+msgstr "Le wiki a été créé, mais une erreur est survenue lors de la création de sa page d'accueil."
+
+#: ../../Zotlabs/Module/Wiki.php:391 ../../addon/gitwiki/Mod_Gitwiki.php:353
+msgid "Error creating wiki"
+msgstr "Erreur lors de la création du wiki."
+
+#: ../../Zotlabs/Module/Wiki.php:403
+msgid "Wiki delete permission denied."
+msgstr "Permission de supprimer le wiki refusée."
+
+#: ../../Zotlabs/Module/Wiki.php:413
+msgid "Error deleting wiki"
+msgstr "Erreur durant la suppression du wiki"
+
+#: ../../Zotlabs/Module/Wiki.php:439 ../../addon/gitwiki/Mod_Gitwiki.php:400
+msgid "New page created"
+msgstr "Nouvelle page créée"
+
+#: ../../Zotlabs/Module/Wiki.php:558
+msgid "Cannot delete Home"
+msgstr "Impossible de supprimer la racine"
+
+#: ../../Zotlabs/Module/Wiki.php:622
+msgid "Current Revision"
+msgstr "Version actuelle"
+
+#: ../../Zotlabs/Module/Wiki.php:622
+msgid "Selected Revision"
+msgstr "Version sélectionnée"
-#: ../../Zotlabs/Module/Pdledit.php:18
+#: ../../Zotlabs/Module/Wiki.php:672
+msgid "You must be authenticated."
+msgstr "Vous devez être connecté."
+
+#: ../../Zotlabs/Module/Chanview.php:134
+msgid "toggle full screen mode"
+msgstr "Basculer en mode plein écran."
+
+#: ../../Zotlabs/Module/Pdledit.php:21
msgid "Layout updated."
msgstr "Mise en page mise à jour."
-#: ../../Zotlabs/Module/Pdledit.php:34 ../../Zotlabs/Module/Pdledit.php:61
+#: ../../Zotlabs/Module/Pdledit.php:34 ../../Zotlabs/Module/Chat.php:217
+msgid "Feature disabled."
+msgstr "Fonctionnalité désactivée"
+
+#: ../../Zotlabs/Module/Pdledit.php:42 ../../Zotlabs/Module/Pdledit.php:69
msgid "Edit System Page Description"
msgstr "Modifier la description de la page du système"
-#: ../../Zotlabs/Module/Pdledit.php:56
+#: ../../Zotlabs/Module/Pdledit.php:64
msgid "Layout not found."
msgstr "Mise en page introuvable."
-#: ../../Zotlabs/Module/Pdledit.php:62
+#: ../../Zotlabs/Module/Pdledit.php:70
msgid "Module Name:"
msgstr "Nom du module&nbsp;:"
-#: ../../Zotlabs/Module/Pdledit.php:63
+#: ../../Zotlabs/Module/Pdledit.php:71
msgid "Layout Help"
msgstr "Aide à la mise en page"
-#: ../../Zotlabs/Module/Poke.php:168 ../../Zotlabs/Lib/Apps.php:226
-#: ../../include/conversation.php:960
+#: ../../Zotlabs/Module/Poke.php:168 ../../Zotlabs/Lib/Apps.php:235
+#: ../../include/conversation.php:1042
msgid "Poke"
msgstr "Tapoter"
@@ -3203,13 +4747,838 @@ msgstr "Choisir ce que vous voulez faire au destinataire"
msgid "Make this post private"
msgstr "Rendre cette publication privée"
-#: ../../Zotlabs/Module/Probe.php:30 ../../Zotlabs/Module/Probe.php:34
+#: ../../Zotlabs/Module/Profile_photo.php:61
+#: ../../Zotlabs/Module/Cover_photo.php:56
+msgid "Image uploaded but image cropping failed."
+msgstr "L'image a été téléversée, mais le recadrage a échoué."
+
+#: ../../Zotlabs/Module/Profile_photo.php:115
+#: ../../Zotlabs/Module/Profile_photo.php:226
+#: ../../include/photo/photo_driver.php:646
+msgid "Profile Photos"
+msgstr "Photos du profil"
+
+#: ../../Zotlabs/Module/Profile_photo.php:137
+#: ../../Zotlabs/Module/Cover_photo.php:159
+msgid "Image resize failed."
+msgstr "Le redimensionnement de l'image a échoué."
+
+#: ../../Zotlabs/Module/Profile_photo.php:196
+#: ../../addon/openclipatar/openclipatar.php:298
+msgid ""
+"Shift-reload the page or clear browser cache if the new photo does not "
+"display immediately."
+msgstr "Shift-rechargez votre page, ou videz le cache du navigateur si la photo ne s'affiche pas immédiatement."
+
+#: ../../Zotlabs/Module/Profile_photo.php:203
+#: ../../Zotlabs/Module/Cover_photo.php:173 ../../include/photos.php:149
+msgid "Unable to process image"
+msgstr "Impossible de traiter l'image"
+
+#: ../../Zotlabs/Module/Profile_photo.php:238
+#: ../../Zotlabs/Module/Cover_photo.php:197
+msgid "Image upload failed."
+msgstr "Le téléversement de l'image a échoué."
+
+#: ../../Zotlabs/Module/Profile_photo.php:257
+#: ../../Zotlabs/Module/Cover_photo.php:214
+msgid "Unable to process image."
+msgstr "Impossible de traîter l'image."
+
+#: ../../Zotlabs/Module/Profile_photo.php:318
+#: ../../Zotlabs/Module/Profile_photo.php:365
+#: ../../Zotlabs/Module/Cover_photo.php:307
+#: ../../Zotlabs/Module/Cover_photo.php:322
+msgid "Photo not available."
+msgstr "Photo inaccessible."
+
+#: ../../Zotlabs/Module/Profile_photo.php:420
+#: ../../Zotlabs/Module/Cover_photo.php:358
+msgid "Upload File:"
+msgstr "Téléverser fichier&nbsp;:"
+
+#: ../../Zotlabs/Module/Profile_photo.php:421
+#: ../../Zotlabs/Module/Cover_photo.php:359
+msgid "Select a profile:"
+msgstr "Choisir un profil&nbsp;:"
+
+#: ../../Zotlabs/Module/Profile_photo.php:422
+msgid "Use Photo for Profile"
+msgstr "Utiliser la photo pour le profil"
+
+#: ../../Zotlabs/Module/Profile_photo.php:422
+msgid "Upload Profile Photo"
+msgstr "Téléverser une photo de profil"
+
+#: ../../Zotlabs/Module/Profile_photo.php:423
+#: ../../addon/openclipatar/openclipatar.php:182
+#: ../../addon/openclipatar/openclipatar.php:194
+msgid "Use"
+msgstr "Utiliser"
+
+#: ../../Zotlabs/Module/Profile_photo.php:429
+#: ../../Zotlabs/Module/Cover_photo.php:365
+msgid "skip this step"
+msgstr "passer cette étape"
+
+#: ../../Zotlabs/Module/Profile_photo.php:429
+#: ../../Zotlabs/Module/Cover_photo.php:365
+msgid "select a photo from your photo albums"
+msgstr "choisir une photo dans vos albums"
+
+#: ../../Zotlabs/Module/Profile_photo.php:448
+#: ../../Zotlabs/Module/Cover_photo.php:381
+msgid "Crop Image"
+msgstr "Recadrer l'image"
+
+#: ../../Zotlabs/Module/Profile_photo.php:449
+#: ../../Zotlabs/Module/Cover_photo.php:382
+msgid "Please adjust the image cropping for optimum viewing."
+msgstr "Merci d'ajuster le cadre pour une visualisation optimale."
+
+#: ../../Zotlabs/Module/Profile_photo.php:451
+#: ../../Zotlabs/Module/Cover_photo.php:384
+msgid "Done Editing"
+msgstr "J'ai terminé"
+
+#: ../../Zotlabs/Module/Chatsvc.php:131
+msgid "Away"
+msgstr "Absent"
+
+#: ../../Zotlabs/Module/Chatsvc.php:136
+msgid "Online"
+msgstr "En ligne"
+
+#: ../../Zotlabs/Module/Item.php:184
+msgid "Unable to locate original post."
+msgstr "Impossible de localiser la publication initiale."
+
+#: ../../Zotlabs/Module/Item.php:450
+msgid "Empty post discarded."
+msgstr "Publication vide annulée."
+
+#: ../../Zotlabs/Module/Item.php:824
+msgid "Duplicate post suppressed."
+msgstr "Publication en doublon supprimée."
+
+#: ../../Zotlabs/Module/Item.php:954
+msgid "System error. Post not saved."
+msgstr "Erreur système. Publication non sauvegardée."
+
+#: ../../Zotlabs/Module/Item.php:1084
+msgid "Unable to obtain post information from database."
+msgstr "Impossible d'obtenir les informations de publication depuis la base de données."
+
+#: ../../Zotlabs/Module/Item.php:1091
#, php-format
-msgid "Fetching URL returns error: %1$s"
-msgstr "Récupération d'URL échouée&nbsp;: %1$s"
+msgid "You have reached your limit of %1$.0f top level posts."
+msgstr "Vous avez atteint votre limite de %1$.0f contributions \"racines\"."
+
+#: ../../Zotlabs/Module/Item.php:1098
+#, php-format
+msgid "You have reached your limit of %1$.0f webpages."
+msgstr "Vous avez atteint votre limite de %1$.0f pages web."
+
+#: ../../Zotlabs/Module/Ping.php:254
+msgid "sent you a private message"
+msgstr "vous a envoyé un message privé"
+
+#: ../../Zotlabs/Module/Ping.php:302
+msgid "added your channel"
+msgstr "a ajouté votre canal"
+
+#: ../../Zotlabs/Module/Ping.php:312
+msgid "g A l F d"
+msgstr "g A l F d"
+
+#: ../../Zotlabs/Module/Ping.php:330
+msgid "[today]"
+msgstr "[aujourd'hui]"
+
+#: ../../Zotlabs/Module/Ping.php:339
+msgid "posted an event"
+msgstr "a publié un événement"
+
+#: ../../Zotlabs/Module/Page.php:40 ../../Zotlabs/Module/Block.php:31
+msgid "Invalid item."
+msgstr "Élément invalide."
+
+#: ../../Zotlabs/Module/Page.php:94 ../../Zotlabs/Module/Block.php:79
+#: ../../Zotlabs/Module/Display.php:122
+#: ../../Zotlabs/Lib/NativeWikiPage.php:489 ../../Zotlabs/Web/Router.php:146
+#: ../../include/help.php:68
+msgid "Page not found."
+msgstr "Page introuvable."
+
+#: ../../Zotlabs/Module/Page.php:131
+msgid ""
+"Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod "
+"tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam,"
+" quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo "
+"consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse "
+"cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat "
+"non proident, sunt in culpa qui officia deserunt mollit anim id est laborum."
+msgstr "Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum."
+
+#: ../../Zotlabs/Module/Connedit.php:79
+msgid "Could not access contact record."
+msgstr "Impossible d'accéder aux détails du contact."
+
+#: ../../Zotlabs/Module/Connedit.php:109
+msgid "Could not locate selected profile."
+msgstr "Impossible de localiser le profil sélectionné."
+
+#: ../../Zotlabs/Module/Connedit.php:246
+msgid "Connection updated."
+msgstr "Contact mis à jour."
+
+#: ../../Zotlabs/Module/Connedit.php:248
+msgid "Failed to update connection record."
+msgstr "Impossible de mettre à jour les détails du contact."
+
+#: ../../Zotlabs/Module/Connedit.php:298
+msgid "is now connected to"
+msgstr "est maintenant connecté avec"
+
+#: ../../Zotlabs/Module/Connedit.php:431
+msgid "Could not access address book record."
+msgstr "Impossible d'accéder aux détails du carnet d'adresses."
+
+#: ../../Zotlabs/Module/Connedit.php:479
+msgid "Refresh failed - channel is currently unavailable."
+msgstr "Actualisation impossible - le canal est indisponible."
+
+#: ../../Zotlabs/Module/Connedit.php:494 ../../Zotlabs/Module/Connedit.php:503
+#: ../../Zotlabs/Module/Connedit.php:512 ../../Zotlabs/Module/Connedit.php:521
+#: ../../Zotlabs/Module/Connedit.php:534
+msgid "Unable to set address book parameters."
+msgstr "Impossible de régler les paramètres du carnet d'adresses."
+
+#: ../../Zotlabs/Module/Connedit.php:558
+msgid "Connection has been removed."
+msgstr "Le contact a été supprimé."
+
+#: ../../Zotlabs/Module/Connedit.php:598 ../../Zotlabs/Lib/Apps.php:228
+#: ../../addon/openclipatar/openclipatar.php:57
+#: ../../include/conversation.php:982 ../../include/nav.php:102
+msgid "View Profile"
+msgstr "Voir mon profil"
+
+#: ../../Zotlabs/Module/Connedit.php:601
+#, php-format
+msgid "View %s's profile"
+msgstr "Voir le profil de %s"
+
+#: ../../Zotlabs/Module/Connedit.php:605
+msgid "Refresh Permissions"
+msgstr "Actualiser les autorisations"
+
+#: ../../Zotlabs/Module/Connedit.php:608
+msgid "Fetch updated permissions"
+msgstr "Récupérer les autorisations les plus récentes"
+
+#: ../../Zotlabs/Module/Connedit.php:612
+msgid "Refresh Photo"
+msgstr ""
+
+#: ../../Zotlabs/Module/Connedit.php:615
+msgid "Fetch updated photo"
+msgstr ""
+
+#: ../../Zotlabs/Module/Connedit.php:619
+msgid "Recent Activity"
+msgstr "Activité récente"
+
+#: ../../Zotlabs/Module/Connedit.php:622
+msgid "View recent posts and comments"
+msgstr "Voir les publications et commentaires récents"
+
+#: ../../Zotlabs/Module/Connedit.php:629
+msgid "Block (or Unblock) all communications with this connection"
+msgstr "Bloquer ou débloquer toute communication avec ce contact"
+
+#: ../../Zotlabs/Module/Connedit.php:630
+msgid "This connection is blocked!"
+msgstr "Ce contact est bloqué&nbsp;!"
+
+#: ../../Zotlabs/Module/Connedit.php:634
+msgid "Unignore"
+msgstr "Ne plus ignorer"
+
+#: ../../Zotlabs/Module/Connedit.php:637
+msgid "Ignore (or Unignore) all inbound communications from this connection"
+msgstr "Ignorer ou ne plus ignorer toute communication venant de ce contact"
+
+#: ../../Zotlabs/Module/Connedit.php:638
+msgid "This connection is ignored!"
+msgstr "Ce contact est ignoré&nbsp;!"
+
+#: ../../Zotlabs/Module/Connedit.php:642
+msgid "Unarchive"
+msgstr "Désarchiver"
+
+#: ../../Zotlabs/Module/Connedit.php:642
+msgid "Archive"
+msgstr "Archiver"
+
+#: ../../Zotlabs/Module/Connedit.php:645
+msgid ""
+"Archive (or Unarchive) this connection - mark channel dead but keep content"
+msgstr "Archiver ou désarchiver ce contact - le marquer comme inactif mais conserver le contenu"
+
+#: ../../Zotlabs/Module/Connedit.php:646
+msgid "This connection is archived!"
+msgstr "Ce contact est archivé&nbsp;!"
+
+#: ../../Zotlabs/Module/Connedit.php:650
+msgid "Unhide"
+msgstr "Ne plus cacher"
+
+#: ../../Zotlabs/Module/Connedit.php:650
+msgid "Hide"
+msgstr "Cacher"
+
+#: ../../Zotlabs/Module/Connedit.php:653
+msgid "Hide or Unhide this connection from your other connections"
+msgstr "Cacher ou ne plus cacher ce contact vis-à-vis de vos autres contacts"
+
+#: ../../Zotlabs/Module/Connedit.php:654
+msgid "This connection is hidden!"
+msgstr "Ce contact est caché&nbsp;!"
+
+#: ../../Zotlabs/Module/Connedit.php:661
+msgid "Delete this connection"
+msgstr "Supprimer ce contact"
+
+#: ../../Zotlabs/Module/Connedit.php:669
+msgid "Fetch Vcard"
+msgstr ""
+
+#: ../../Zotlabs/Module/Connedit.php:672
+msgid "Fetch electronic calling card for this connection"
+msgstr ""
+
+#: ../../Zotlabs/Module/Connedit.php:683
+msgid "Open Individual Permissions section by default"
+msgstr "Ouvrir par défaut la section des autorisations individuelles"
+
+#: ../../Zotlabs/Module/Connedit.php:706
+msgid "Affinity"
+msgstr "Affinité"
+
+#: ../../Zotlabs/Module/Connedit.php:709
+msgid "Open Set Affinity section by default"
+msgstr "Ouvrir par défaut la section Définir le degré d'affinité"
+
+#: ../../Zotlabs/Module/Connedit.php:713 ../../Zotlabs/Widget/Affinity.php:26
+msgid "Me"
+msgstr "Moi"
+
+#: ../../Zotlabs/Module/Connedit.php:714 ../../Zotlabs/Widget/Affinity.php:27
+msgid "Family"
+msgstr "Famille"
+
+#: ../../Zotlabs/Module/Connedit.php:716 ../../Zotlabs/Widget/Affinity.php:29
+msgid "Acquaintances"
+msgstr "Connaissances"
+
+#: ../../Zotlabs/Module/Connedit.php:743
+msgid "Filter"
+msgstr "Filtrer"
+
+#: ../../Zotlabs/Module/Connedit.php:746
+msgid "Open Custom Filter section by default"
+msgstr "Ouvrir par défaut la section Filtre personnalisé"
+
+#: ../../Zotlabs/Module/Connedit.php:783
+msgid "Approve this connection"
+msgstr "Autoriser ce contact"
+
+#: ../../Zotlabs/Module/Connedit.php:783
+msgid "Accept connection to allow communication"
+msgstr "Accepter le contact pour permettre la communication"
+
+#: ../../Zotlabs/Module/Connedit.php:788
+msgid "Set Affinity"
+msgstr "Définir le degré d'affinité"
+
+#: ../../Zotlabs/Module/Connedit.php:791
+msgid "Set Profile"
+msgstr "Définir le profil"
+
+#: ../../Zotlabs/Module/Connedit.php:794
+msgid "Set Affinity & Profile"
+msgstr "Définir le degré d'affinité et le profil"
+
+#: ../../Zotlabs/Module/Connedit.php:852
+msgid "none"
+msgstr "Aucun"
+
+#: ../../Zotlabs/Module/Connedit.php:855
+#: ../../Zotlabs/Widget/Settings_menu.php:107
+msgid "Connection Default Permissions"
+msgstr "Autorisations par défaut des contacts"
+
+#: ../../Zotlabs/Module/Connedit.php:855 ../../include/items.php:3942
+#, php-format
+msgid "Connection: %s"
+msgstr "Contact&nbsp;: %s"
+
+#: ../../Zotlabs/Module/Connedit.php:856
+msgid "Apply these permissions automatically"
+msgstr "Appliquer ces permissions automatiquement"
+
+#: ../../Zotlabs/Module/Connedit.php:856
+msgid "Connection requests will be approved without your interaction"
+msgstr "Les demandes de contact seront approuvées automatiquement"
+
+#: ../../Zotlabs/Module/Connedit.php:857
+msgid "Permission role"
+msgstr "Rôle d'accès"
+
+#: ../../Zotlabs/Module/Connedit.php:858
+msgid "Add permission role"
+msgstr "Ajouter un rôle d'accès"
+
+#: ../../Zotlabs/Module/Connedit.php:864
+msgid "This connection's primary address is"
+msgstr "L'adresse principale de ce contact est"
+
+#: ../../Zotlabs/Module/Connedit.php:865
+msgid "Available locations:"
+msgstr "Emplacements disponibles&nbsp;:"
+
+#: ../../Zotlabs/Module/Connedit.php:869
+msgid ""
+"The permissions indicated on this page will be applied to all new "
+"connections."
+msgstr "Les permissions indiquées sur cette page seront appliquées à tous vos nouveaux contacts."
+
+#: ../../Zotlabs/Module/Connedit.php:870
+msgid "Connection Tools"
+msgstr "Actions du contact"
+
+#: ../../Zotlabs/Module/Connedit.php:872
+msgid "Slide to adjust your degree of friendship"
+msgstr "Faites glisser pour ajuster votre proximité avec le contact"
+
+#: ../../Zotlabs/Module/Connedit.php:873 ../../Zotlabs/Module/Rate.php:155
+#: ../../include/js_strings.php:20
+msgid "Rating"
+msgstr "Evaluation"
+
+#: ../../Zotlabs/Module/Connedit.php:874
+msgid "Slide to adjust your rating"
+msgstr "Faîtes glisser pour ajuster votre note"
+
+#: ../../Zotlabs/Module/Connedit.php:875 ../../Zotlabs/Module/Connedit.php:880
+msgid "Optionally explain your rating"
+msgstr "Explication facultative de votre évaluation"
+
+#: ../../Zotlabs/Module/Connedit.php:877
+msgid "Custom Filter"
+msgstr "Filtre personnalisé"
+
+#: ../../Zotlabs/Module/Connedit.php:878
+msgid "Only import posts with this text"
+msgstr "N'importer que les publications comprenant ce texte"
+
+#: ../../Zotlabs/Module/Connedit.php:878 ../../Zotlabs/Module/Connedit.php:879
+msgid ""
+"words one per line or #tags or /patterns/ or lang=xx, leave blank to import "
+"all posts"
+msgstr "un mot par ligne ou #étiquettes ou /motif/ ou lang=xx, laisser vide pour importer toutes les publications"
+
+#: ../../Zotlabs/Module/Connedit.php:879
+msgid "Do not import posts with this text"
+msgstr "Ne pas importer les publications comprenant ce texte"
+
+#: ../../Zotlabs/Module/Connedit.php:881
+msgid "This information is public!"
+msgstr "Cette information est publique&nbsp;!"
+
+#: ../../Zotlabs/Module/Connedit.php:886
+msgid "Connection Pending Approval"
+msgstr "Contact en attente d'approbation"
+
+#: ../../Zotlabs/Module/Connedit.php:891
+#, php-format
+msgid ""
+"Please choose the profile you would like to display to %s when viewing your "
+"profile securely."
+msgstr "Merci de choisir le profil que vous souhaitez montrer quand %s visite votre profil de manière authentifiée."
+
+#: ../../Zotlabs/Module/Connedit.php:898
+msgid ""
+"Some permissions may be inherited from your channel's <a "
+"href=\"settings\"><strong>privacy settings</strong></a>, which have higher "
+"priority than individual settings. You can change those settings here but "
+"they wont have any impact unless the inherited setting changes."
+msgstr "Certaines permissions peuvent être héritées de vos <a href=\"settings\">paramètres de confidentialité</a> de canal, lesquels sont prioritaires sur les réglages individuels. Vous pouvez modifier ces permissions ici mais cela n'aura aucun effet à moins de changer les paramètres hérités."
+
+#: ../../Zotlabs/Module/Connedit.php:899
+msgid "Last update:"
+msgstr "Dernière mise à jour&nbsp;:"
+
+#: ../../Zotlabs/Module/Connedit.php:908
+msgid "Details"
+msgstr "Détails"
+
+#: ../../Zotlabs/Module/Connedit.php:911 ../../addon/cdav/Mod_Cdav.php:1137
+msgid "Organisation"
+msgstr "Organisation"
+
+#: ../../Zotlabs/Module/Connedit.php:912 ../../addon/cdav/Mod_Cdav.php:1138
+#: ../../include/page_widgets.php:46
+msgid "Title"
+msgstr "Titre"
+
+#: ../../Zotlabs/Module/Connedit.php:913 ../../Zotlabs/Module/Profiles.php:789
+#: ../../addon/cdav/Mod_Cdav.php:1139
+msgid "Phone"
+msgstr "Téléphone"
+
+#: ../../Zotlabs/Module/Connedit.php:915 ../../Zotlabs/Module/Profiles.php:791
+#: ../../addon/cdav/Mod_Cdav.php:1141
+msgid "Instant messenger"
+msgstr "Instant messenger"
+
+#: ../../Zotlabs/Module/Connedit.php:916 ../../Zotlabs/Module/Profiles.php:792
+#: ../../addon/cdav/Mod_Cdav.php:1142
+msgid "Website"
+msgstr "Site web"
+
+#: ../../Zotlabs/Module/Connedit.php:918 ../../Zotlabs/Module/Profiles.php:794
+#: ../../addon/cdav/Mod_Cdav.php:1144
+msgid "Note"
+msgstr "Note"
+
+#: ../../Zotlabs/Module/Connedit.php:919 ../../Zotlabs/Module/Profiles.php:795
+#: ../../addon/cdav/Mod_Cdav.php:1145 ../../addon/cdav/cdav.php:270
+#: ../../include/connections.php:668
+msgid "Mobile"
+msgstr "Mobile"
+
+#: ../../Zotlabs/Module/Connedit.php:920 ../../Zotlabs/Module/Profiles.php:796
+#: ../../addon/cdav/Mod_Cdav.php:1146 ../../addon/cdav/cdav.php:271
+#: ../../include/connections.php:669
+msgid "Home"
+msgstr "Mon canal"
+
+#: ../../Zotlabs/Module/Connedit.php:921 ../../Zotlabs/Module/Profiles.php:797
+#: ../../addon/cdav/Mod_Cdav.php:1147 ../../addon/cdav/cdav.php:274
+#: ../../include/connections.php:672
+msgid "Work"
+msgstr "Travail"
+
+#: ../../Zotlabs/Module/Connedit.php:923 ../../Zotlabs/Module/Profiles.php:799
+#: ../../addon/cdav/Mod_Cdav.php:1149
+#: ../../addon/jappixmini/jappixmini.php:368
+msgid "Add Contact"
+msgstr "Ajouter un contact"
+
+#: ../../Zotlabs/Module/Connedit.php:924 ../../Zotlabs/Module/Profiles.php:800
+#: ../../addon/cdav/Mod_Cdav.php:1150
+msgid "Add Field"
+msgstr "Ajouter un champ"
+
+#: ../../Zotlabs/Module/Connedit.php:929 ../../addon/cdav/Mod_Cdav.php:1155
+msgid "P.O. Box"
+msgstr "P.O. Box"
+
+#: ../../Zotlabs/Module/Connedit.php:930 ../../addon/cdav/Mod_Cdav.php:1156
+msgid "Additional"
+msgstr "Information complémentaires"
+
+#: ../../Zotlabs/Module/Connedit.php:931 ../../addon/cdav/Mod_Cdav.php:1157
+msgid "Street"
+msgstr "Rue"
+
+#: ../../Zotlabs/Module/Connedit.php:932 ../../addon/cdav/Mod_Cdav.php:1158
+msgid "Locality"
+msgstr "Localité"
+
+#: ../../Zotlabs/Module/Connedit.php:933 ../../addon/cdav/Mod_Cdav.php:1159
+msgid "Region"
+msgstr "Région"
+
+#: ../../Zotlabs/Module/Connedit.php:934 ../../addon/cdav/Mod_Cdav.php:1160
+msgid "ZIP Code"
+msgstr "ZIP code"
+
+#: ../../Zotlabs/Module/Connedit.php:935 ../../Zotlabs/Module/Profiles.php:760
+#: ../../addon/cdav/Mod_Cdav.php:1161
+msgid "Country"
+msgstr "Pays"
+
+#: ../../Zotlabs/Module/Chat.php:179
+msgid "Room not found"
+msgstr "Salon introuvable"
+
+#: ../../Zotlabs/Module/Chat.php:195
+msgid "Leave Room"
+msgstr "Quitter le salon"
+
+#: ../../Zotlabs/Module/Chat.php:196
+msgid "Delete Room"
+msgstr "Supprimer le salon"
+
+#: ../../Zotlabs/Module/Chat.php:197
+msgid "I am away right now"
+msgstr "Je suis absent en ce moment"
+
+#: ../../Zotlabs/Module/Chat.php:198
+msgid "I am online"
+msgstr "Je suis en ligne"
+
+#: ../../Zotlabs/Module/Chat.php:200
+msgid "Bookmark this room"
+msgstr "Marquer ce salon comme favori"
+
+#: ../../Zotlabs/Module/Chat.php:203 ../../Zotlabs/Module/Mail.php:240
+#: ../../Zotlabs/Module/Mail.php:361 ../../include/conversation.php:1263
+msgid "Please enter a link URL:"
+msgstr "Merci d'entrer l'URL d'un lien&nbsp;:"
+
+#: ../../Zotlabs/Module/Chat.php:204 ../../Zotlabs/Module/Mail.php:293
+#: ../../Zotlabs/Module/Mail.php:430 ../../Zotlabs/Lib/ThreadItem.php:744
+#: ../../include/conversation.php:1373
+msgid "Encrypt text"
+msgstr "Chiffrer le texte"
+
+#: ../../Zotlabs/Module/Chat.php:230
+msgid "New Chatroom"
+msgstr "Nouveau salon de discussion"
+
+#: ../../Zotlabs/Module/Chat.php:231
+msgid "Chatroom name"
+msgstr "Nom du salon de conversation"
+
+#: ../../Zotlabs/Module/Chat.php:232
+msgid "Expiration of chats (minutes)"
+msgstr "Expiration des discussions (en minutes)"
+
+#: ../../Zotlabs/Module/Chat.php:248
+#, php-format
+msgid "%1$s's Chatrooms"
+msgstr "Salons de %1$s"
+
+#: ../../Zotlabs/Module/Chat.php:253
+msgid "No chatrooms available"
+msgstr "Aucun salon de conversation disponible"
+
+#: ../../Zotlabs/Module/Chat.php:257
+msgid "Expiration"
+msgstr "Expiration"
+
+#: ../../Zotlabs/Module/Chat.php:258
+msgid "min"
+msgstr "min"
+
+#: ../../Zotlabs/Module/Fbrowser.php:29 ../../Zotlabs/Lib/Apps.php:229
+#: ../../include/conversation.php:1774
+msgid "Photos"
+msgstr "Photos"
+
+#: ../../Zotlabs/Module/Fbrowser.php:85 ../../Zotlabs/Lib/Apps.php:224
+#: ../../Zotlabs/Storage/Browser.php:224 ../../include/conversation.php:1782
+msgid "Files"
+msgstr "Fichiers"
+
+#: ../../Zotlabs/Module/Menu.php:49
+msgid "Unable to update menu."
+msgstr "Impossible de mettre le menu à jour."
+
+#: ../../Zotlabs/Module/Menu.php:60
+msgid "Unable to create menu."
+msgstr "Impossible de créer le menu."
+
+#: ../../Zotlabs/Module/Menu.php:98 ../../Zotlabs/Module/Menu.php:110
+msgid "Menu Name"
+msgstr "Nom du menu"
+
+#: ../../Zotlabs/Module/Menu.php:98
+msgid "Unique name (not visible on webpage) - required"
+msgstr "Nom unique (non visible sur la page web) - requis"
+
+#: ../../Zotlabs/Module/Menu.php:99 ../../Zotlabs/Module/Menu.php:111
+msgid "Menu Title"
+msgstr "Titre du menu"
+
+#: ../../Zotlabs/Module/Menu.php:99
+msgid "Visible on webpage - leave empty for no title"
+msgstr "Visible pour la page web - laisser vide pour qu'il n'y ait pas de titre"
+
+#: ../../Zotlabs/Module/Menu.php:100
+msgid "Allow Bookmarks"
+msgstr "Autoriser l'usage de favoris"
+
+#: ../../Zotlabs/Module/Menu.php:100 ../../Zotlabs/Module/Menu.php:157
+msgid "Menu may be used to store saved bookmarks"
+msgstr "Le menu pourra être utilisé pour stocker des favoris"
+
+#: ../../Zotlabs/Module/Menu.php:101 ../../Zotlabs/Module/Menu.php:159
+msgid "Submit and proceed"
+msgstr "Valider et continuer"
+
+#: ../../Zotlabs/Module/Menu.php:107 ../../include/text.php:2276
+msgid "Menus"
+msgstr "Menus"
+
+#: ../../Zotlabs/Module/Menu.php:117
+msgid "Bookmarks allowed"
+msgstr "Favoris autorisés"
+
+#: ../../Zotlabs/Module/Menu.php:119
+msgid "Delete this menu"
+msgstr "Supprimer ce menu"
+
+#: ../../Zotlabs/Module/Menu.php:120 ../../Zotlabs/Module/Menu.php:154
+msgid "Edit menu contents"
+msgstr "Modifier le contenu du menu"
+
+#: ../../Zotlabs/Module/Menu.php:121
+msgid "Edit this menu"
+msgstr "Modifier ce menu"
+
+#: ../../Zotlabs/Module/Menu.php:136
+msgid "Menu could not be deleted."
+msgstr "Impossible de supprimer le menu."
+
+#: ../../Zotlabs/Module/Menu.php:149
+msgid "Edit Menu"
+msgstr "Modifier le menu"
+
+#: ../../Zotlabs/Module/Menu.php:153
+msgid "Add or remove entries to this menu"
+msgstr "Ajouter/supprimer des entrées à ce menu"
+
+#: ../../Zotlabs/Module/Menu.php:155
+msgid "Menu name"
+msgstr "Nom du menu"
+
+#: ../../Zotlabs/Module/Menu.php:155
+msgid "Must be unique, only seen by you"
+msgstr "Doit être unique, ne sera vu que par vous"
+
+#: ../../Zotlabs/Module/Menu.php:156
+msgid "Menu title"
+msgstr "Titre du menu"
+
+#: ../../Zotlabs/Module/Menu.php:156
+msgid "Menu title as seen by others"
+msgstr "Titre du menu tel que vu par les visiteurs"
+
+#: ../../Zotlabs/Module/Menu.php:157
+msgid "Allow bookmarks"
+msgstr "Autoriser l'usage de favoris"
+
+#: ../../Zotlabs/Module/Layouts.php:184 ../../include/text.php:2277
+msgid "Layouts"
+msgstr "Mises-en-page"
+
+#: ../../Zotlabs/Module/Layouts.php:186 ../../Zotlabs/Lib/Apps.php:232
+#: ../../include/nav.php:157 ../../include/nav.php:264
+#: ../../include/help.php:55 ../../include/help.php:61
+msgid "Help"
+msgstr "Aide"
+
+#: ../../Zotlabs/Module/Layouts.php:186
+msgid "Comanche page description language help"
+msgstr "Aide sur le langage de description de page Comanche"
+
+#: ../../Zotlabs/Module/Layouts.php:190
+msgid "Layout Description"
+msgstr "Description de la mise en page"
+
+#: ../../Zotlabs/Module/Layouts.php:195
+msgid "Download PDL file"
+msgstr "Télécharger le fichier PDL"
+
+#: ../../Zotlabs/Module/Tagger.php:55 ../../include/bbcode.php:274
+msgid "post"
+msgstr "publication"
+
+#: ../../Zotlabs/Module/Tagger.php:57 ../../include/conversation.php:146
+#: ../../include/text.php:1953
+msgid "comment"
+msgstr "commentaire"
+
+#: ../../Zotlabs/Module/Tagger.php:95
+#, php-format
+msgid "%1$s tagged %2$s's %3$s with %4$s"
+msgstr "%1$s a étiqueté le %3$s de %2$s avec %4$s"
+
+#: ../../Zotlabs/Module/Pconfig.php:26 ../../Zotlabs/Module/Pconfig.php:59
+msgid "This setting requires special processing and editing has been blocked."
+msgstr "Ce paramètre nécessité un traitement spécial, les modifications ont été bloquées."
+
+#: ../../Zotlabs/Module/Pconfig.php:48
+msgid "Configuration Editor"
+msgstr "Editeur de configuration"
+
+#: ../../Zotlabs/Module/Pconfig.php:49
+msgid ""
+"Warning: Changing some settings could render your channel inoperable. Please"
+" leave this page unless you are comfortable with and knowledgeable about how"
+" to correctly use this feature."
+msgstr "Attention&nbsp;:modifier certains paramètres peut rendre votre canal inutilisable. Merci d'ignorer cette page à moins d'être suffisamment à l'aise de savoir comment utiliser correctement cette fonctionnalité."
+
+#: ../../Zotlabs/Module/Group.php:24
+msgid "Privacy group created."
+msgstr "Groupe de contacts créé."
+
+#: ../../Zotlabs/Module/Group.php:30
+msgid "Could not create privacy group."
+msgstr "Impossible de créer le groupe de contacts."
+
+#: ../../Zotlabs/Module/Group.php:42 ../../Zotlabs/Module/Group.php:141
+#: ../../include/items.php:3909
+msgid "Privacy group not found."
+msgstr "Groupe de contacts introuvable."
+
+#: ../../Zotlabs/Module/Group.php:58
+msgid "Privacy group updated."
+msgstr "Groupe de contacts mis à jour."
+
+#: ../../Zotlabs/Module/Group.php:90
+msgid "Create a group of channels."
+msgstr "Créer un groupe de contacts."
+
+#: ../../Zotlabs/Module/Group.php:91 ../../Zotlabs/Module/Group.php:184
+msgid "Privacy group name: "
+msgstr "Nom du groupe de contacts&nbsp;:"
+
+#: ../../Zotlabs/Module/Group.php:93 ../../Zotlabs/Module/Group.php:187
+msgid "Members are visible to other channels"
+msgstr "Les membres sont visibles par les autres canaux"
+
+#: ../../Zotlabs/Module/Group.php:111
+msgid "Privacy group removed."
+msgstr "Groupe de contacts supprimé."
+
+#: ../../Zotlabs/Module/Group.php:113
+msgid "Unable to remove privacy group."
+msgstr "Impossible de supprimer le groupe de canaux."
+
+#: ../../Zotlabs/Module/Group.php:183
+msgid "Privacy group editor"
+msgstr "Editeur de groupe de contacts."
+
+#: ../../Zotlabs/Module/Group.php:197 ../../Zotlabs/Module/Help.php:81
+msgid "Members"
+msgstr "Membres"
-#: ../../Zotlabs/Module/Profiles.php:24 ../../Zotlabs/Module/Profiles.php:189
-#: ../../Zotlabs/Module/Profiles.php:246 ../../Zotlabs/Module/Profiles.php:625
+#: ../../Zotlabs/Module/Group.php:199
+msgid "All Connected Channels"
+msgstr "Tous les canaux connectés"
+
+#: ../../Zotlabs/Module/Group.php:231
+msgid "Click on a channel to add or remove."
+msgstr "Cliquer sur un canal pour l'ajouter ou le supprimer"
+
+#: ../../Zotlabs/Module/Profiles.php:24 ../../Zotlabs/Module/Profiles.php:184
+#: ../../Zotlabs/Module/Profiles.php:241 ../../Zotlabs/Module/Profiles.php:659
msgid "Profile not found."
msgstr "Profil introuvable."
@@ -3217,4857 +5586,5188 @@ msgstr "Profil introuvable."
msgid "Profile deleted."
msgstr "Profil supprimé."
-#: ../../Zotlabs/Module/Profiles.php:68 ../../Zotlabs/Module/Profiles.php:104
+#: ../../Zotlabs/Module/Profiles.php:68 ../../Zotlabs/Module/Profiles.php:105
msgid "Profile-"
msgstr "Profil-"
-#: ../../Zotlabs/Module/Profiles.php:89 ../../Zotlabs/Module/Profiles.php:132
+#: ../../Zotlabs/Module/Profiles.php:90 ../../Zotlabs/Module/Profiles.php:127
msgid "New profile created."
msgstr "Nouveau profil créé."
-#: ../../Zotlabs/Module/Profiles.php:110
+#: ../../Zotlabs/Module/Profiles.php:111
msgid "Profile unavailable to clone."
msgstr "Profil impossible à cloner."
-#: ../../Zotlabs/Module/Profiles.php:151
+#: ../../Zotlabs/Module/Profiles.php:146
msgid "Profile unavailable to export."
msgstr "Impossible d'exporter le profil."
-#: ../../Zotlabs/Module/Profiles.php:256
+#: ../../Zotlabs/Module/Profiles.php:252
msgid "Profile Name is required."
msgstr "Le nom du profil est obligatoire."
-#: ../../Zotlabs/Module/Profiles.php:427
+#: ../../Zotlabs/Module/Profiles.php:459
msgid "Marital Status"
msgstr "Statut marital"
-#: ../../Zotlabs/Module/Profiles.php:431
+#: ../../Zotlabs/Module/Profiles.php:463
msgid "Romantic Partner"
msgstr "Partenaire amoureux"
-#: ../../Zotlabs/Module/Profiles.php:435 ../../Zotlabs/Module/Profiles.php:736
+#: ../../Zotlabs/Module/Profiles.php:467 ../../Zotlabs/Module/Profiles.php:775
msgid "Likes"
msgstr "Aime"
-#: ../../Zotlabs/Module/Profiles.php:439 ../../Zotlabs/Module/Profiles.php:737
+#: ../../Zotlabs/Module/Profiles.php:471 ../../Zotlabs/Module/Profiles.php:776
msgid "Dislikes"
msgstr "N'aime pas"
-#: ../../Zotlabs/Module/Profiles.php:443 ../../Zotlabs/Module/Profiles.php:744
+#: ../../Zotlabs/Module/Profiles.php:475 ../../Zotlabs/Module/Profiles.php:783
msgid "Work/Employment"
msgstr "Travail/Occupation"
-#: ../../Zotlabs/Module/Profiles.php:446
+#: ../../Zotlabs/Module/Profiles.php:478
msgid "Religion"
msgstr "Religion/Croyance"
-#: ../../Zotlabs/Module/Profiles.php:450
+#: ../../Zotlabs/Module/Profiles.php:482
msgid "Political Views"
msgstr "Opinions politiques"
-#: ../../Zotlabs/Module/Profiles.php:458
+#: ../../Zotlabs/Module/Profiles.php:486
+#: ../../addon/openid/MysqlProvider.php:74
+msgid "Gender"
+msgstr "Sexe"
+
+#: ../../Zotlabs/Module/Profiles.php:490
msgid "Sexual Preference"
msgstr "Préférences sexuelle"
-#: ../../Zotlabs/Module/Profiles.php:462
+#: ../../Zotlabs/Module/Profiles.php:494
msgid "Homepage"
msgstr "Site Internet"
-#: ../../Zotlabs/Module/Profiles.php:466
+#: ../../Zotlabs/Module/Profiles.php:498
msgid "Interests"
msgstr "Centres d'intérêt"
-#: ../../Zotlabs/Module/Profiles.php:560
+#: ../../Zotlabs/Module/Profiles.php:594
msgid "Profile updated."
msgstr "Profil mis à jour."
-#: ../../Zotlabs/Module/Profiles.php:644
+#: ../../Zotlabs/Module/Profiles.php:678
msgid "Hide your connections list from viewers of this profile"
-msgstr ""
+msgstr "Cacher la liste des relations pour les visiteurs de votre profile"
-#: ../../Zotlabs/Module/Profiles.php:686
+#: ../../Zotlabs/Module/Profiles.php:725
msgid "Edit Profile Details"
msgstr "Modifier les détails du profil"
-#: ../../Zotlabs/Module/Profiles.php:688
+#: ../../Zotlabs/Module/Profiles.php:727
msgid "View this profile"
msgstr "Voir ce profil"
-#: ../../Zotlabs/Module/Profiles.php:689 ../../Zotlabs/Module/Profiles.php:771
-#: ../../include/channel.php:959
+#: ../../Zotlabs/Module/Profiles.php:728 ../../Zotlabs/Module/Profiles.php:827
+#: ../../include/channel.php:1064
msgid "Edit visibility"
msgstr "Changer la visibilité"
-#: ../../Zotlabs/Module/Profiles.php:690
+#: ../../Zotlabs/Module/Profiles.php:729
msgid "Profile Tools"
-msgstr ""
+msgstr "Ouitls pour votre profile"
-#: ../../Zotlabs/Module/Profiles.php:691
+#: ../../Zotlabs/Module/Profiles.php:730
msgid "Change cover photo"
-msgstr ""
+msgstr "Modifier votre bannière"
-#: ../../Zotlabs/Module/Profiles.php:692 ../../include/channel.php:930
+#: ../../Zotlabs/Module/Profiles.php:731 ../../include/channel.php:1035
msgid "Change profile photo"
msgstr "Changer la photo du profil"
-#: ../../Zotlabs/Module/Profiles.php:693
+#: ../../Zotlabs/Module/Profiles.php:732
msgid "Create a new profile using these settings"
msgstr "Créer un nouveau profil avec ces paramètres"
-#: ../../Zotlabs/Module/Profiles.php:694
+#: ../../Zotlabs/Module/Profiles.php:733
msgid "Clone this profile"
msgstr "Cloner ce profil"
-#: ../../Zotlabs/Module/Profiles.php:695
+#: ../../Zotlabs/Module/Profiles.php:734
msgid "Delete this profile"
msgstr "Supprimer ce profil"
-#: ../../Zotlabs/Module/Profiles.php:696
+#: ../../Zotlabs/Module/Profiles.php:735
msgid "Add profile things"
msgstr "Ajouter des éléments de profil"
-#: ../../Zotlabs/Module/Profiles.php:697 ../../include/widgets.php:105
-#: ../../include/conversation.php:1526
+#: ../../Zotlabs/Module/Profiles.php:736 ../../include/conversation.php:1648
msgid "Personal"
msgstr "Me concernant"
-#: ../../Zotlabs/Module/Profiles.php:699
+#: ../../Zotlabs/Module/Profiles.php:738
msgid "Relation"
-msgstr ""
+msgstr "Contacts"
-#: ../../Zotlabs/Module/Profiles.php:700 ../../include/datetime.php:48
+#: ../../Zotlabs/Module/Profiles.php:739 ../../include/datetime.php:55
msgid "Miscellaneous"
msgstr "Divers"
-#: ../../Zotlabs/Module/Profiles.php:702
+#: ../../Zotlabs/Module/Profiles.php:741
msgid "Import profile from file"
msgstr "Importer le profil à partir d'un fichier"
-#: ../../Zotlabs/Module/Profiles.php:703
+#: ../../Zotlabs/Module/Profiles.php:742
msgid "Export profile to file"
msgstr "Exporter le profil vers un fichier."
-#: ../../Zotlabs/Module/Profiles.php:704
+#: ../../Zotlabs/Module/Profiles.php:743
msgid "Your gender"
-msgstr ""
+msgstr "Votre genre"
-#: ../../Zotlabs/Module/Profiles.php:705
+#: ../../Zotlabs/Module/Profiles.php:744
msgid "Marital status"
-msgstr ""
+msgstr "Etat civil"
-#: ../../Zotlabs/Module/Profiles.php:706
+#: ../../Zotlabs/Module/Profiles.php:745
msgid "Sexual preference"
-msgstr ""
+msgstr "préférence sexuelle"
-#: ../../Zotlabs/Module/Profiles.php:709
+#: ../../Zotlabs/Module/Profiles.php:748
msgid "Profile name"
-msgstr ""
+msgstr "Nom du profile"
-#: ../../Zotlabs/Module/Profiles.php:711
+#: ../../Zotlabs/Module/Profiles.php:750
msgid "This is your default profile."
msgstr "Ceci est votre profil par défaut."
-#: ../../Zotlabs/Module/Profiles.php:713
+#: ../../Zotlabs/Module/Profiles.php:752
msgid "Your full name"
-msgstr ""
+msgstr "Votre nom complet"
-#: ../../Zotlabs/Module/Profiles.php:714
+#: ../../Zotlabs/Module/Profiles.php:753
msgid "Title/Description"
msgstr "Titre/description"
-#: ../../Zotlabs/Module/Profiles.php:717
+#: ../../Zotlabs/Module/Profiles.php:756
msgid "Street address"
-msgstr ""
+msgstr "Rue"
-#: ../../Zotlabs/Module/Profiles.php:718
+#: ../../Zotlabs/Module/Profiles.php:757
msgid "Locality/City"
msgstr "Ville"
-#: ../../Zotlabs/Module/Profiles.php:719
+#: ../../Zotlabs/Module/Profiles.php:758
msgid "Region/State"
msgstr "Région"
-#: ../../Zotlabs/Module/Profiles.php:720
+#: ../../Zotlabs/Module/Profiles.php:759
msgid "Postal/Zip code"
-msgstr ""
+msgstr "Code postal"
-#: ../../Zotlabs/Module/Profiles.php:721
-msgid "Country"
-msgstr "Pays"
-
-#: ../../Zotlabs/Module/Profiles.php:726
+#: ../../Zotlabs/Module/Profiles.php:765
msgid "Who (if applicable)"
msgstr "Qui (si applicable)"
-#: ../../Zotlabs/Module/Profiles.php:726
+#: ../../Zotlabs/Module/Profiles.php:765
msgid "Examples: cathy123, Cathy Williams, cathy@example.com"
msgstr "Exemples&nbsp;: marie123, Marie Deschamps, marie@exemple.com"
-#: ../../Zotlabs/Module/Profiles.php:727
+#: ../../Zotlabs/Module/Profiles.php:766
msgid "Since (date)"
-msgstr ""
+msgstr "Depuis (date)"
-#: ../../Zotlabs/Module/Profiles.php:730
+#: ../../Zotlabs/Module/Profiles.php:769
msgid "Tell us about yourself"
-msgstr ""
+msgstr "Parlez nous de vous..."
-#: ../../Zotlabs/Module/Profiles.php:732
+#: ../../Zotlabs/Module/Profiles.php:770
+#: ../../addon/openid/MysqlProvider.php:68
+msgid "Homepage URL"
+msgstr "URL de mon site Internet&nbsp;:"
+
+#: ../../Zotlabs/Module/Profiles.php:771
msgid "Hometown"
msgstr "Ville de naissance"
-#: ../../Zotlabs/Module/Profiles.php:733
+#: ../../Zotlabs/Module/Profiles.php:772
msgid "Political views"
-msgstr ""
+msgstr "Opinions politiques"
-#: ../../Zotlabs/Module/Profiles.php:734
+#: ../../Zotlabs/Module/Profiles.php:773
msgid "Religious views"
-msgstr ""
+msgstr "Convictions religieuses"
-#: ../../Zotlabs/Module/Profiles.php:735
+#: ../../Zotlabs/Module/Profiles.php:774
msgid "Keywords used in directory listings"
-msgstr ""
+msgstr "Mots clés pour l'annuaire"
-#: ../../Zotlabs/Module/Profiles.php:735
+#: ../../Zotlabs/Module/Profiles.php:774
msgid "Example: fishing photography software"
msgstr "Exemple&nbsp;: escrime photographie modélisme"
-#: ../../Zotlabs/Module/Profiles.php:738
+#: ../../Zotlabs/Module/Profiles.php:777
msgid "Musical interests"
msgstr "Goûts musicaux"
-#: ../../Zotlabs/Module/Profiles.php:739
+#: ../../Zotlabs/Module/Profiles.php:778
msgid "Books, literature"
msgstr "Livres, littérature"
-#: ../../Zotlabs/Module/Profiles.php:740
+#: ../../Zotlabs/Module/Profiles.php:779
msgid "Television"
msgstr "Télévision"
-#: ../../Zotlabs/Module/Profiles.php:741
+#: ../../Zotlabs/Module/Profiles.php:780
msgid "Film/Dance/Culture/Entertainment"
-msgstr ""
+msgstr "Cinéma/Danse/Culture/Divertissement"
-#: ../../Zotlabs/Module/Profiles.php:742
+#: ../../Zotlabs/Module/Profiles.php:781
msgid "Hobbies/Interests"
msgstr "Loisirs/Centres d'intêret"
-#: ../../Zotlabs/Module/Profiles.php:743
+#: ../../Zotlabs/Module/Profiles.php:782
msgid "Love/Romance"
-msgstr ""
+msgstr "Amour/Relation amoureuse"
-#: ../../Zotlabs/Module/Profiles.php:745
+#: ../../Zotlabs/Module/Profiles.php:784
msgid "School/Education"
-msgstr ""
+msgstr "Niveau d'étude"
-#: ../../Zotlabs/Module/Profiles.php:746
+#: ../../Zotlabs/Module/Profiles.php:785
msgid "Contact information and social networks"
-msgstr ""
+msgstr "Coordonnées et autres réseaux sociaux"
-#: ../../Zotlabs/Module/Profiles.php:747
+#: ../../Zotlabs/Module/Profiles.php:786
msgid "My other channels"
msgstr "Mes autres canaux"
-#: ../../Zotlabs/Module/Profiles.php:767 ../../include/channel.php:955
+#: ../../Zotlabs/Module/Profiles.php:788
+msgid "Communications"
+msgstr ""
+
+#: ../../Zotlabs/Module/Profiles.php:823 ../../include/channel.php:1060
msgid "Profile Image"
msgstr "Image du profil"
-#: ../../Zotlabs/Module/Profiles.php:777 ../../include/nav.php:88
-#: ../../include/channel.php:937
+#: ../../Zotlabs/Module/Profiles.php:833 ../../include/channel.php:1042
+#: ../../include/nav.php:105
msgid "Edit Profiles"
-msgstr "Modifier les profils"
+msgstr "Modifier mes profils"
-#: ../../Zotlabs/Module/Profile_photo.php:179
-msgid ""
-"Shift-reload the page or clear browser cache if the new photo does not "
-"display immediately."
-msgstr "Shift-rechargez votre page, ou videz le cache du navigateur si la photo ne s'affiche pas immédiatement."
+#: ../../Zotlabs/Module/Editwebpage.php:144
+msgid "Page link"
+msgstr "Lien"
-#: ../../Zotlabs/Module/Profile_photo.php:367
-msgid "Upload Profile Photo"
-msgstr "Téléverser une photo de profil"
+#: ../../Zotlabs/Module/Editwebpage.php:171
+msgid "Edit Webpage"
+msgstr "Modifier la page web"
-#: ../../Zotlabs/Module/Profperm.php:34 ../../Zotlabs/Module/Profperm.php:63
-msgid "Invalid profile identifier."
-msgstr "Identifiant de profil invalide."
+#: ../../Zotlabs/Module/Manage.php:143
+msgid "Create a new channel"
+msgstr "Créer un nouveau canal"
-#: ../../Zotlabs/Module/Profperm.php:115
-msgid "Profile Visibility Editor"
-msgstr "Éditeur de visibilité de profil"
+#: ../../Zotlabs/Module/Manage.php:164 ../../Zotlabs/Lib/Apps.php:221
+#: ../../include/nav.php:201
+msgid "Channel Manager"
+msgstr "Gérer mes canaux"
-#: ../../Zotlabs/Module/Profperm.php:117 ../../include/channel.php:1249
-msgid "Profile"
-msgstr "Profil"
+#: ../../Zotlabs/Module/Manage.php:165
+msgid "Current Channel"
+msgstr "Canal actif"
-#: ../../Zotlabs/Module/Profperm.php:119
-msgid "Click on a contact to add or remove."
-msgstr "Cliquer sur un contact pour l'ajouter ou le retirer."
+#: ../../Zotlabs/Module/Manage.php:167
+msgid "Switch to one of your channels by selecting it."
+msgstr "Pour changer de canal, sélectionnez-en un"
-#: ../../Zotlabs/Module/Profperm.php:128
-msgid "Visible To"
-msgstr "Visible par"
+#: ../../Zotlabs/Module/Manage.php:168
+msgid "Default Channel"
+msgstr "Canal par défaut"
-#: ../../Zotlabs/Module/Pubsites.php:22 ../../include/widgets.php:1270
-msgid "Public Hubs"
-msgstr "Instances publiques"
+#: ../../Zotlabs/Module/Manage.php:169
+msgid "Make Default"
+msgstr "Définir comme défaut"
-#: ../../Zotlabs/Module/Pubsites.php:25
-msgid ""
-"The listed hubs allow public registration for the $Projectname network. All "
-"hubs in the network are interlinked so membership on any of them conveys "
-"membership in the network as a whole. Some hubs may require subscription or "
-"provide tiered service plans. The hub itself <strong>may</strong> provide "
-"additional details."
-msgstr "Les sites listés permettent l'enregistrement public de comptes pour le réseau $Projectname. Tous les sites du réseau sont reliés entre eux, être membre d'un site revient à être membre de tous. Certains sites peuvent demander une souscription ou proposer différents niveaux de service. Chaque site <strong>peut</strong> fournir des détails supplémentaires."
+#: ../../Zotlabs/Module/Manage.php:172
+#, php-format
+msgid "%d new messages"
+msgstr "%d nouveaux messages"
-#: ../../Zotlabs/Module/Pubsites.php:31
-msgid "Hub URL"
-msgstr "URL du site"
+#: ../../Zotlabs/Module/Manage.php:173
+#, php-format
+msgid "%d new introductions"
+msgstr "%d nouvelles relations"
-#: ../../Zotlabs/Module/Pubsites.php:31
-msgid "Access Type"
-msgstr "Type d'accès"
+#: ../../Zotlabs/Module/Manage.php:175
+msgid "Delegated Channel"
+msgstr "Canaux délégués"
-#: ../../Zotlabs/Module/Pubsites.php:31
-msgid "Registration Policy"
-msgstr "Politique d'inscription"
+#: ../../Zotlabs/Module/Dirsearch.php:33
+msgid "This directory server requires an access token"
+msgstr "Ce serveur d'annuaire requiert un jeton d'accès"
-#: ../../Zotlabs/Module/Pubsites.php:31
-msgid "Stats"
-msgstr ""
+#: ../../Zotlabs/Module/Siteinfo.php:20
+msgid "About this site"
+msgstr "À propos de ce site"
-#: ../../Zotlabs/Module/Pubsites.php:31
-msgid "Software"
-msgstr ""
+#: ../../Zotlabs/Module/Siteinfo.php:21
+msgid "Site Name"
+msgstr "Nom du site"
-#: ../../Zotlabs/Module/Pubsites.php:31 ../../Zotlabs/Module/Ratings.php:103
-#: ../../include/conversation.php:959
-msgid "Ratings"
-msgstr "Evaluations"
+#: ../../Zotlabs/Module/Siteinfo.php:25 ../../include/network.php:1995
+msgid "Administrator"
+msgstr "Administrateur"
-#: ../../Zotlabs/Module/Pubsites.php:38
-msgid "Rate"
-msgstr "Evaluer"
+#: ../../Zotlabs/Module/Siteinfo.php:27 ../../Zotlabs/Module/Register.php:221
+msgid "Terms of Service"
+msgstr "Conditions de service"
-#: ../../Zotlabs/Module/Rate.php:160
-msgid "Website:"
-msgstr "Site web&nbsp;:"
+#: ../../Zotlabs/Module/Siteinfo.php:28
+msgid "Software and Project information"
+msgstr "Informations sur le logiciel et le projet"
+
+#: ../../Zotlabs/Module/Siteinfo.php:29
+msgid "This site is powered by $Projectname"
+msgstr "Ce site est propulsé par "
+
+#: ../../Zotlabs/Module/Siteinfo.php:30
+msgid ""
+"Federated and decentralised networking and identity services provided by Zot"
+msgstr "Réseau fédéré et décentralisé, et services d'identification fournies par Zot"
-#: ../../Zotlabs/Module/Rate.php:163
+#: ../../Zotlabs/Module/Siteinfo.php:32
#, php-format
-msgid "Remote Channel [%s] (not yet known on this site)"
-msgstr "Canal distant [%s] (encore inconnu sur ce site)"
+msgid "Version %s"
+msgstr "Version %s"
-#: ../../Zotlabs/Module/Rate.php:164
-msgid "Rating (this information is public)"
-msgstr "Evaluation (cette information est publique)"
+#: ../../Zotlabs/Module/Siteinfo.php:33
+msgid "Project homepage"
+msgstr "Page d'accueil du projet"
-#: ../../Zotlabs/Module/Rate.php:165
-msgid "Optionally explain your rating (this information is public)"
-msgstr "Explication facultative de votre évaluation (cette information est publique)"
+#: ../../Zotlabs/Module/Siteinfo.php:34
+msgid "Developer homepage"
+msgstr "Page d'accueil des développeurs"
-#: ../../Zotlabs/Module/Ratings.php:73
+#: ../../Zotlabs/Module/Ratings.php:70
msgid "No ratings"
msgstr "Pas de note"
-#: ../../Zotlabs/Module/Ratings.php:104
+#: ../../Zotlabs/Module/Ratings.php:97 ../../Zotlabs/Module/Pubsites.php:35
+#: ../../include/conversation.php:1032
+msgid "Ratings"
+msgstr "Evaluations"
+
+#: ../../Zotlabs/Module/Ratings.php:98
msgid "Rating: "
msgstr "Evaluation&nbsp:"
-#: ../../Zotlabs/Module/Ratings.php:105
+#: ../../Zotlabs/Module/Ratings.php:99
msgid "Website: "
msgstr "Site web&nbsp;:"
-#: ../../Zotlabs/Module/Ratings.php:107
+#: ../../Zotlabs/Module/Ratings.php:101
msgid "Description: "
msgstr "Description&nbsp;:"
-#: ../../Zotlabs/Module/Admin.php:77
-msgid "Theme settings updated."
-msgstr "Paramètres du thème mis à jour."
+#: ../../Zotlabs/Module/Webpages.php:52
+msgid "Import Webpage Elements"
+msgstr "Importer éléments de page web"
-#: ../../Zotlabs/Module/Admin.php:197
-msgid "# Accounts"
-msgstr "# Comptes"
+#: ../../Zotlabs/Module/Webpages.php:53
+msgid "Import selected"
+msgstr "Importation sélectionnée"
-#: ../../Zotlabs/Module/Admin.php:198
-msgid "# blocked accounts"
-msgstr "# comptes bloqués"
+#: ../../Zotlabs/Module/Webpages.php:76
+msgid "Export Webpage Elements"
+msgstr "Exporter éléments de pages web"
-#: ../../Zotlabs/Module/Admin.php:199
-msgid "# expired accounts"
-msgstr "# comptes expirés"
+#: ../../Zotlabs/Module/Webpages.php:77
+msgid "Export selected"
+msgstr "Export sélectionné"
-#: ../../Zotlabs/Module/Admin.php:200
-msgid "# expiring accounts"
-msgstr "# comptes expirant"
+#: ../../Zotlabs/Module/Webpages.php:242 ../../Zotlabs/Lib/Apps.php:225
+#: ../../include/conversation.php:1832
+msgid "Webpages"
+msgstr "Pages web"
-#: ../../Zotlabs/Module/Admin.php:211
-msgid "# Channels"
-msgstr "# Canaux"
+#: ../../Zotlabs/Module/Webpages.php:253 ../../include/page_widgets.php:44
+msgid "Actions"
+msgstr "Actions"
-#: ../../Zotlabs/Module/Admin.php:212
-msgid "# primary"
-msgstr "# primaire"
+#: ../../Zotlabs/Module/Webpages.php:254 ../../include/page_widgets.php:45
+msgid "Page Link"
+msgstr "Lien vers la page"
-#: ../../Zotlabs/Module/Admin.php:213
-msgid "# clones"
-msgstr "# clones"
+#: ../../Zotlabs/Module/Webpages.php:255
+msgid "Page Title"
+msgstr "Titre de la page"
-#: ../../Zotlabs/Module/Admin.php:219
-msgid "Message queues"
-msgstr "File des messages"
+#: ../../Zotlabs/Module/Webpages.php:285
+msgid "Invalid file type."
+msgstr "Type de fichier invalide"
-#: ../../Zotlabs/Module/Admin.php:236
-msgid "Your software should be updated"
-msgstr ""
+#: ../../Zotlabs/Module/Webpages.php:297
+msgid "Error opening zip file"
+msgstr "Erreur lors de l'ouverture du fichier zip"
-#: ../../Zotlabs/Module/Admin.php:241 ../../Zotlabs/Module/Admin.php:490
-#: ../../Zotlabs/Module/Admin.php:711 ../../Zotlabs/Module/Admin.php:755
-#: ../../Zotlabs/Module/Admin.php:1030 ../../Zotlabs/Module/Admin.php:1209
-#: ../../Zotlabs/Module/Admin.php:1329 ../../Zotlabs/Module/Admin.php:1419
-#: ../../Zotlabs/Module/Admin.php:1612 ../../Zotlabs/Module/Admin.php:1646
-#: ../../Zotlabs/Module/Admin.php:1731
-msgid "Administration"
-msgstr "Administration"
+#: ../../Zotlabs/Module/Webpages.php:308
+msgid "Invalid folder path."
+msgstr "Chemin du dossier invalide"
-#: ../../Zotlabs/Module/Admin.php:242
-msgid "Summary"
-msgstr "Résumé"
+#: ../../Zotlabs/Module/Webpages.php:335
+msgid "No webpage elements detected."
+msgstr "Aucun élément de page Web détecté."
-#: ../../Zotlabs/Module/Admin.php:245
-msgid "Registered accounts"
-msgstr "Comptes enregistrés"
+#: ../../Zotlabs/Module/Webpages.php:410
+msgid "Import complete."
+msgstr "Importation terminée"
-#: ../../Zotlabs/Module/Admin.php:246 ../../Zotlabs/Module/Admin.php:715
-msgid "Pending registrations"
-msgstr "Inscriptions en attente"
+#: ../../Zotlabs/Module/Editpost.php:35
+msgid "Item is not editable"
+msgstr "Elément non modifiable"
-#: ../../Zotlabs/Module/Admin.php:247
-msgid "Registered channels"
-msgstr "Canaux enregistrés"
+#: ../../Zotlabs/Module/Editpost.php:108 ../../Zotlabs/Module/Rpost.php:138
+msgid "Edit post"
+msgstr "Modifier la publication"
-#: ../../Zotlabs/Module/Admin.php:248 ../../Zotlabs/Module/Admin.php:716
-msgid "Active plugins"
-msgstr "Greffons actifs"
+#: ../../Zotlabs/Module/Dreport.php:45
+msgid "Invalid message"
+msgstr "Message non valide"
-#: ../../Zotlabs/Module/Admin.php:249
-msgid "Version"
-msgstr "Version"
+#: ../../Zotlabs/Module/Dreport.php:78
+msgid "no results"
+msgstr "aucun résultat"
-#: ../../Zotlabs/Module/Admin.php:250
-msgid "Repository version (master)"
-msgstr ""
+#: ../../Zotlabs/Module/Dreport.php:93
+msgid "channel sync processed"
+msgstr "Synchro de canal effectuée"
-#: ../../Zotlabs/Module/Admin.php:251
-msgid "Repository version (dev)"
-msgstr ""
+#: ../../Zotlabs/Module/Dreport.php:97
+msgid "queued"
+msgstr "mis dans la file d'attente"
-#: ../../Zotlabs/Module/Admin.php:373
-msgid "Site settings updated."
-msgstr "Paramètres du site sauvegardés."
+#: ../../Zotlabs/Module/Dreport.php:101
+msgid "posted"
+msgstr "publié"
-#: ../../Zotlabs/Module/Admin.php:400 ../../include/text.php:2841
-msgid "Default"
-msgstr "Défaut"
+#: ../../Zotlabs/Module/Dreport.php:105
+msgid "accepted for delivery"
+msgstr "accepté pour la distribution"
-#: ../../Zotlabs/Module/Admin.php:410 ../../Zotlabs/Module/Settings.php:798
-msgid "mobile"
-msgstr "mobile"
+#: ../../Zotlabs/Module/Dreport.php:109
+msgid "updated"
+msgstr "mis à jour"
-#: ../../Zotlabs/Module/Admin.php:412
-msgid "experimental"
-msgstr "expérimental"
+#: ../../Zotlabs/Module/Dreport.php:112
+msgid "update ignored"
+msgstr "mise à jour ignorée"
-#: ../../Zotlabs/Module/Admin.php:414
-msgid "unsupported"
-msgstr "non maintenu"
+#: ../../Zotlabs/Module/Dreport.php:115
+msgid "permission denied"
+msgstr "permission refusée"
-#: ../../Zotlabs/Module/Admin.php:460
-msgid "Yes - with approval"
-msgstr "Oui - avec approbation"
+#: ../../Zotlabs/Module/Dreport.php:119
+msgid "recipient not found"
+msgstr "destinataire introuvable"
-#: ../../Zotlabs/Module/Admin.php:466
-msgid "My site is not a public server"
-msgstr "Mon site n'est pas un serveur public"
+#: ../../Zotlabs/Module/Dreport.php:122
+msgid "mail recalled"
+msgstr "courriel rappelé"
-#: ../../Zotlabs/Module/Admin.php:467
-msgid "My site has paid access only"
-msgstr "Mon site est à accès payant uniquement"
+#: ../../Zotlabs/Module/Dreport.php:125
+msgid "duplicate mail received"
+msgstr "courriel reçu en double"
-#: ../../Zotlabs/Module/Admin.php:468
-msgid "My site has free access only"
-msgstr "Mon site est gratuit uniquement"
+#: ../../Zotlabs/Module/Dreport.php:128
+msgid "mail delivered"
+msgstr "courriel distribué"
-#: ../../Zotlabs/Module/Admin.php:469
-msgid "My site offers free accounts with optional paid upgrades"
-msgstr "Mon site offre des comptes gratuits avec des améliorations payantes facultatives"
+#: ../../Zotlabs/Module/Dreport.php:148
+#, php-format
+msgid "Delivery report for %1$s"
+msgstr "Rapport de distribution pour %1$s"
-#: ../../Zotlabs/Module/Admin.php:491 ../../include/widgets.php:1382
-msgid "Site"
-msgstr "Site"
+#: ../../Zotlabs/Module/Dreport.php:151
+msgid "Options"
+msgstr "Options"
-#: ../../Zotlabs/Module/Admin.php:493 ../../Zotlabs/Module/Register.php:245
-msgid "Registration"
-msgstr "Inscription"
+#: ../../Zotlabs/Module/Dreport.php:152
+msgid "Redeliver"
+msgstr "Transférer à nouveau"
-#: ../../Zotlabs/Module/Admin.php:494
-msgid "File upload"
-msgstr "Envoi de fichier"
+#: ../../Zotlabs/Module/Sources.php:37
+msgid "Failed to create source. No channel selected."
+msgstr "Impossible de créer la source. Aucun canal selectionné."
-#: ../../Zotlabs/Module/Admin.php:495
-msgid "Policies"
-msgstr "Stratégies"
+#: ../../Zotlabs/Module/Sources.php:51
+msgid "Source created."
+msgstr "Source créée."
-#: ../../Zotlabs/Module/Admin.php:496 ../../include/contact_widgets.php:16
-msgid "Advanced"
-msgstr "Avancé"
+#: ../../Zotlabs/Module/Sources.php:64
+msgid "Source updated."
+msgstr "Source mise à jour."
-#: ../../Zotlabs/Module/Admin.php:500
-msgid "Site name"
-msgstr "Nom du site"
+#: ../../Zotlabs/Module/Sources.php:90
+msgid "*"
+msgstr "*"
-#: ../../Zotlabs/Module/Admin.php:501
-msgid "Banner/Logo"
-msgstr "Bannière/logo"
+#: ../../Zotlabs/Module/Sources.php:96
+#: ../../Zotlabs/Widget/Settings_menu.php:123 ../../include/features.php:213
+msgid "Channel Sources"
+msgstr "Sources du canal"
-#: ../../Zotlabs/Module/Admin.php:502
-msgid "Administrator Information"
-msgstr "Informations de l'administrateur"
+#: ../../Zotlabs/Module/Sources.php:97
+msgid "Manage remote sources of content for your channel."
+msgstr "Gérer les sources distantes de contenu pour votre canal."
+
+#: ../../Zotlabs/Module/Sources.php:98 ../../Zotlabs/Module/Sources.php:108
+msgid "New Source"
+msgstr "Nouvelle source"
-#: ../../Zotlabs/Module/Admin.php:502
+#: ../../Zotlabs/Module/Sources.php:109 ../../Zotlabs/Module/Sources.php:143
msgid ""
-"Contact information for site administrators. Displayed on siteinfo page. "
-"BBCode can be used here"
-msgstr "Coordonnées de l'administrateur du site. Affichées sur la page 'siteinfo'. Vous pouvez utiliser du BBCode ici"
+"Import all or selected content from the following channel into this channel "
+"and distribute it according to your channel settings."
+msgstr "Importer le contenu sélectionné ou tout le contenu du canal suivant vers ce canal et le distribuer selon vos paramètres de canal."
-#: ../../Zotlabs/Module/Admin.php:503
-msgid "System language"
-msgstr "Langue du système"
+#: ../../Zotlabs/Module/Sources.php:110 ../../Zotlabs/Module/Sources.php:144
+msgid "Only import content with these words (one per line)"
+msgstr "N'importer le contenu que s'il contient ces mots (un par ligne)"
-#: ../../Zotlabs/Module/Admin.php:504
-msgid "System theme"
-msgstr "Thème du système"
+#: ../../Zotlabs/Module/Sources.php:110 ../../Zotlabs/Module/Sources.php:144
+msgid "Leave blank to import all public content"
+msgstr "Laissez vide pour importer tout le contenu public"
-#: ../../Zotlabs/Module/Admin.php:504
+#: ../../Zotlabs/Module/Sources.php:111 ../../Zotlabs/Module/Sources.php:148
+msgid "Channel Name"
+msgstr "Nom du canal"
+
+#: ../../Zotlabs/Module/Sources.php:112 ../../Zotlabs/Module/Sources.php:147
msgid ""
-"Default system theme - may be over-ridden by user profiles - <a href='#' "
-"id='cnftheme'>change theme settings</a>"
-msgstr "Thème par défaut - il peut être changé pour chaque profil utilisateur - <a href='#' id='cnftheme'>modifier le thème</a>"
+"Add the following categories to posts imported from this source (comma "
+"separated)"
+msgstr "Ajouter les catégories suivantes aux publications importées à partir de cette source (séparer par des virgules)"
-#: ../../Zotlabs/Module/Admin.php:505
-msgid "Mobile system theme"
-msgstr "Thème par défaut pour les mobiles"
+#: ../../Zotlabs/Module/Sources.php:133 ../../Zotlabs/Module/Sources.php:161
+msgid "Source not found."
+msgstr "Source introuvable."
-#: ../../Zotlabs/Module/Admin.php:505
-msgid "Theme for mobile devices"
-msgstr "Thème pour les mobiles"
+#: ../../Zotlabs/Module/Sources.php:140
+msgid "Edit Source"
+msgstr "Modifier la source"
-#: ../../Zotlabs/Module/Admin.php:507
-msgid "Allow Feeds as Connections"
-msgstr "Autoriser les Flux (RSS) comme contacts"
+#: ../../Zotlabs/Module/Sources.php:141
+msgid "Delete Source"
+msgstr "Supprimer la source"
-#: ../../Zotlabs/Module/Admin.php:507
-msgid "(Heavy system resource usage)"
-msgstr "(Impact important sur les ressources)"
+#: ../../Zotlabs/Module/Sources.php:169
+msgid "Source removed"
+msgstr "Source supprimée"
-#: ../../Zotlabs/Module/Admin.php:508
-msgid "Maximum image size"
-msgstr "Taille maximale des images"
+#: ../../Zotlabs/Module/Sources.php:171
+msgid "Unable to remove source."
+msgstr "Impossible de supprimer la source."
+
+#: ../../Zotlabs/Module/Like.php:19
+msgid "Like/Dislike"
+msgstr "Aime/n'aime pas"
-#: ../../Zotlabs/Module/Admin.php:508
+#: ../../Zotlabs/Module/Like.php:24
+msgid "This action is restricted to members."
+msgstr "Cette action est réservée aux membres."
+
+#: ../../Zotlabs/Module/Like.php:25
msgid ""
-"Maximum size in bytes of uploaded images. Default is 0, which means no "
-"limits."
-msgstr "Taille maximum, en octets, des images envoyées. Par défaut 0, soit sans limite."
+"Please <a href=\"rmagic\">login with your $Projectname ID</a> or <a "
+"href=\"register\">register as a new $Projectname member</a> to continue."
+msgstr "S'il vous plait, <a href=\"rmagic\">identifiez vous avec votre identifant de $Projectname </a> ou <a href=\"register\">inscrivez vous comme nouveau membre de $Projectname </a> pour continuer."
-#: ../../Zotlabs/Module/Admin.php:509
-msgid "Does this site allow new member registration?"
-msgstr "Est-ce que l'enregistrement de nouveaux membres est autorisé sur ce site&nbsp;?"
+#: ../../Zotlabs/Module/Like.php:105 ../../Zotlabs/Module/Like.php:131
+#: ../../Zotlabs/Module/Like.php:169
+msgid "Invalid request."
+msgstr "Requête invalide."
-#: ../../Zotlabs/Module/Admin.php:510
-msgid "Invitation only"
-msgstr "Sur invitation seulement"
+#: ../../Zotlabs/Module/Like.php:117 ../../include/conversation.php:122
+msgid "channel"
+msgstr "canal"
-#: ../../Zotlabs/Module/Admin.php:510
-msgid ""
-"Only allow new member registrations with an invitation code. Above register "
-"policy must be set to Yes."
-msgstr "N'autoriser que les nouvelles inscriptions avec code d'invitation. La stratégie d'inscription ci-dessus doit être mise sur \"Oui\"."
+#: ../../Zotlabs/Module/Like.php:146
+msgid "thing"
+msgstr "chose"
-#: ../../Zotlabs/Module/Admin.php:511
-msgid "Which best describes the types of account offered by this hub?"
-msgstr "Quelle est la meilleure description des types de comptes proposés sur ce hub&nbsp;?"
+#: ../../Zotlabs/Module/Like.php:192
+msgid "Channel unavailable."
+msgstr "Canal indisponible."
-#: ../../Zotlabs/Module/Admin.php:512
-msgid "Register text"
-msgstr "Texte d'inscription"
+#: ../../Zotlabs/Module/Like.php:240
+msgid "Previous action reversed."
+msgstr "Action précédente annulée."
-#: ../../Zotlabs/Module/Admin.php:512
-msgid "Will be displayed prominently on the registration page."
-msgstr "Sera affiché de manière bien visible sur le formulaire d'inscription."
+#: ../../Zotlabs/Module/Like.php:419 ../../addon/diaspora/inbound.php:1823
+#: ../../include/conversation.php:160
+#, php-format
+msgid "%1$s likes %2$s's %3$s"
+msgstr "%1$s aime %3$s de %2$s"
-#: ../../Zotlabs/Module/Admin.php:513
-msgid "Site homepage to show visitors (default: login box)"
-msgstr "Page d'accueil du site à montrer aux visiteurs (par défaut&nbsp;:boîte de dialogue de connexion)"
+#: ../../Zotlabs/Module/Like.php:421 ../../include/conversation.php:163
+#, php-format
+msgid "%1$s doesn't like %2$s's %3$s"
+msgstr "%1$s n'aime pas %3$s de %2$s"
-#: ../../Zotlabs/Module/Admin.php:513
-msgid ""
-"example: 'public' to show public stream, 'page/sys/home' to show a system "
-"webpage called 'home' or 'include:home.html' to include a file."
-msgstr "exemple&nbsp;:'public' pour montrer le flux public, 'page/sys/home' pour montrer une page système appelée 'home' ou 'include:home.html' pour inclure un fichier."
+#: ../../Zotlabs/Module/Like.php:423
+#, php-format
+msgid "%1$s agrees with %2$s's %3$s"
+msgstr "%1$s approuve %3$s de %2$s"
-#: ../../Zotlabs/Module/Admin.php:514
-msgid "Preserve site homepage URL"
-msgstr "Préserver l'adresse d'accueil du site"
+#: ../../Zotlabs/Module/Like.php:425
+#, php-format
+msgid "%1$s doesn't agree with %2$s's %3$s"
+msgstr "%1$s n'est pas d'accord avec %3$s de %2$s"
-#: ../../Zotlabs/Module/Admin.php:514
-msgid ""
-"Present the site homepage in a frame at the original location instead of "
-"redirecting"
-msgstr "Présenter la page d'accueil du site dans un cadre à l'adresse d'origine, plutôt que de rediriger"
+#: ../../Zotlabs/Module/Like.php:427
+#, php-format
+msgid "%1$s abstains from a decision on %2$s's %3$s"
+msgstr "%1$s s'abstient de toute décision sur le %3$s de %2$s"
-#: ../../Zotlabs/Module/Admin.php:515
-msgid "Accounts abandoned after x days"
-msgstr "Les comptes sont abandonnés après x jours"
+#: ../../Zotlabs/Module/Like.php:429
+#, php-format
+msgid "%1$s is attending %2$s's %3$s"
+msgstr "%1$s participe à %3$s de %2$s"
-#: ../../Zotlabs/Module/Admin.php:515
-msgid ""
-"Will not waste system resources polling external sites for abandonded "
-"accounts. Enter 0 for no time limit."
-msgstr "Eviter de gaspiller les ressources du système en interrogeant des hubs distants pour des canaux abandonnés. Mettez 0 pour ne pas avoir de limite de temps."
+#: ../../Zotlabs/Module/Like.php:431
+#, php-format
+msgid "%1$s is not attending %2$s's %3$s"
+msgstr "%1$s ne participe pas à %3$s de %2$s"
-#: ../../Zotlabs/Module/Admin.php:516
-msgid "Allowed friend domains"
-msgstr "Domaines amicaux autorisés"
+#: ../../Zotlabs/Module/Like.php:433
+#, php-format
+msgid "%1$s may attend %2$s's %3$s"
+msgstr "%1$s participe peut-être à %3$s de %2$s"
-#: ../../Zotlabs/Module/Admin.php:516
-msgid ""
-"Comma separated list of domains which are allowed to establish friendships "
-"with this site. Wildcards are accepted. Empty to allow any domains"
-msgstr "Liste de noms de domaines séparés par des virgules pour lesquels ce site acceptera les demandes d'amitié. Les caractères génériques (*) sont acceptés. Laissez vide pour accepter tous les domaines."
+#: ../../Zotlabs/Module/Like.php:538
+msgid "Action completed."
+msgstr "Action terminée."
-#: ../../Zotlabs/Module/Admin.php:517
-msgid "Allowed email domains"
-msgstr "Domaines de courriels autorisés"
+#: ../../Zotlabs/Module/Like.php:539
+msgid "Thank you."
+msgstr "Merci."
-#: ../../Zotlabs/Module/Admin.php:517
-msgid ""
-"Comma separated list of domains which are allowed in email addresses for "
-"registrations to this site. Wildcards are accepted. Empty to allow any "
-"domains"
-msgstr "Liste de noms de domaines séparés par des virgules dont les adresses de courriel seront autorisées lors de l'inscription à ce site. Les caractères génériques (*) sont acceptés. Laissez vide pour accepter tous les domaines."
+#: ../../Zotlabs/Module/Directory.php:245
+#, php-format
+msgid "%d rating"
+msgid_plural "%d ratings"
+msgstr[0] "%d évaluation"
+msgstr[1] "%d évaluations"
-#: ../../Zotlabs/Module/Admin.php:518
-msgid "Not allowed email domains"
-msgstr "Domaines de courriel non autorisés"
+#: ../../Zotlabs/Module/Directory.php:256
+msgid "Gender: "
+msgstr "Sexe/genre&nbsp;:"
-#: ../../Zotlabs/Module/Admin.php:518
-msgid ""
-"Comma separated list of domains which are not allowed in email addresses for"
-" registrations to this site. Wildcards are accepted. Empty to allow any "
-"domains, unless allowed domains have been defined."
-msgstr "Liste de noms de domaines - séparés par des virgules - dont les adresses de courriel ne seront pas autorisées lors de l'inscription à ce site. Les caractères génériques (*) sont acceptés. Laissez vide pour accepter tous les domaines, sauf si des domaines autorisés ont été définis."
+#: ../../Zotlabs/Module/Directory.php:258
+msgid "Status: "
+msgstr "État&nbsp;:"
-#: ../../Zotlabs/Module/Admin.php:519
-msgid "Verify Email Addresses"
-msgstr "Demander vérification des adresses de courriel"
+#: ../../Zotlabs/Module/Directory.php:260
+msgid "Homepage: "
+msgstr "Site web&nbsp;:"
-#: ../../Zotlabs/Module/Admin.php:519
-msgid ""
-"Check to verify email addresses used in account registration (recommended)."
-msgstr "Cocher pour que les adresses utilisées à l'inscription soient vérifiées (recommandé)."
+#: ../../Zotlabs/Module/Directory.php:309 ../../include/channel.php:1291
+msgid "Age:"
+msgstr "Age&nbsp;:"
-#: ../../Zotlabs/Module/Admin.php:520
-msgid "Force publish"
-msgstr "Publicité forcée"
+#: ../../Zotlabs/Module/Directory.php:314 ../../include/markdown.php:560
+#: ../../include/channel.php:1132 ../../include/event.php:52
+#: ../../include/event.php:84
+msgid "Location:"
+msgstr "Emplacement&nbsp;:"
-#: ../../Zotlabs/Module/Admin.php:520
-msgid ""
-"Check to force all profiles on this site to be listed in the site directory."
-msgstr "Cocher pour forcer la publication de tous les profils du site dans l'annuaire."
+#: ../../Zotlabs/Module/Directory.php:320
+msgid "Description:"
+msgstr "Description&nbsp;:"
-#: ../../Zotlabs/Module/Admin.php:521
-msgid "Import Public Streams"
-msgstr "Flux publics importés"
+#: ../../Zotlabs/Module/Directory.php:325 ../../include/channel.php:1307
+msgid "Hometown:"
+msgstr "Ville natale&nbsp;:"
-#: ../../Zotlabs/Module/Admin.php:521
-msgid ""
-"Import and allow access to public content pulled from other sites. Warning: "
-"this content is unmoderated."
-msgstr "Importer du contenu public à partir d'autres sites et autoriser l'accès à ce contenu. Attention&nbsp;: ce contenu n'est pas modéré."
+#: ../../Zotlabs/Module/Directory.php:327 ../../include/channel.php:1315
+msgid "About:"
+msgstr "À propos&nbsp;:"
-#: ../../Zotlabs/Module/Admin.php:522
-msgid "Login on Homepage"
-msgstr ""
+#: ../../Zotlabs/Module/Directory.php:328 ../../Zotlabs/Module/Suggest.php:54
+#: ../../Zotlabs/Widget/Follow.php:32 ../../Zotlabs/Widget/Suggestions.php:44
+#: ../../include/conversation.php:1002 ../../include/channel.php:1117
+#: ../../include/connections.php:110
+msgid "Connect"
+msgstr "Ajouter/Suivre"
-#: ../../Zotlabs/Module/Admin.php:522
-msgid ""
-"Present a login box to visitors on the home page if no other content has "
-"been configured."
-msgstr "Présenter une boîte de dialogue de connexion aux visiteurs sur la page d'accueil si aucun autre contenu n'a été configuré."
+#: ../../Zotlabs/Module/Directory.php:329
+msgid "Public Forum:"
+msgstr "Forum public&nbsp;:"
-#: ../../Zotlabs/Module/Admin.php:523
-msgid "Enable context help"
-msgstr ""
+#: ../../Zotlabs/Module/Directory.php:332
+msgid "Keywords: "
+msgstr "Mots-clefs&nbsp;:"
-#: ../../Zotlabs/Module/Admin.php:523
-msgid ""
-"Display contextual help for the current page when the help button is "
-"pressed."
-msgstr ""
+#: ../../Zotlabs/Module/Directory.php:335
+msgid "Don't suggest"
+msgstr "Ne pas suggérer"
-#: ../../Zotlabs/Module/Admin.php:525
-msgid "Directory Server URL"
-msgstr "URL du serveur d'annuaire"
+#: ../../Zotlabs/Module/Directory.php:337
+msgid "Common connections:"
+msgstr "Contacts en commun&nbsp;:"
-#: ../../Zotlabs/Module/Admin.php:525
-msgid "Default directory server"
-msgstr "Serveur d'annuaire par défaut"
+#: ../../Zotlabs/Module/Directory.php:386
+msgid "Global Directory"
+msgstr "Annuaire global"
-#: ../../Zotlabs/Module/Admin.php:527
-msgid "Proxy user"
-msgstr "Utilisateur du proxy"
+#: ../../Zotlabs/Module/Directory.php:386
+msgid "Local Directory"
+msgstr "Annuaire local"
-#: ../../Zotlabs/Module/Admin.php:528
-msgid "Proxy URL"
-msgstr "URL du proxy"
+#: ../../Zotlabs/Module/Directory.php:392
+msgid "Finding:"
+msgstr "Recherche&nbsp;:"
-#: ../../Zotlabs/Module/Admin.php:529
-msgid "Network timeout"
-msgstr "Délai maximal du réseau"
+#: ../../Zotlabs/Module/Directory.php:395 ../../Zotlabs/Module/Suggest.php:62
+#: ../../include/contact_widgets.php:24
+msgid "Channel Suggestions"
+msgstr "Canaux suggérés"
-#: ../../Zotlabs/Module/Admin.php:529
-msgid "Value is in seconds. Set to 0 for unlimited (not recommended)."
-msgstr "En secondes. Mettre à 0 pour ne pas avoir de délai maximal (non recommandé)."
+#: ../../Zotlabs/Module/Directory.php:397
+msgid "next page"
+msgstr "page suivante"
-#: ../../Zotlabs/Module/Admin.php:530
-msgid "Delivery interval"
-msgstr "Intervalle de distribution"
+#: ../../Zotlabs/Module/Directory.php:397
+msgid "previous page"
+msgstr "page précédente"
-#: ../../Zotlabs/Module/Admin.php:530
-msgid ""
-"Delay background delivery processes by this many seconds to reduce system "
-"load. Recommend: 4-5 for shared hosts, 2-3 for virtual private servers. 0-1 "
-"for large dedicated servers."
-msgstr "Temporise le processus de distribution de tant de secondes pour réduire la charge sur le système. Valeurs recommandées&nbsp;: 4-5 pour les serveurs mutualisés, 2-3 pour les VPS. 0-1 pour les gros serveurs dédiés."
+#: ../../Zotlabs/Module/Directory.php:398
+msgid "Sort options"
+msgstr "Options de tri"
-#: ../../Zotlabs/Module/Admin.php:531
-msgid "Deliveries per process"
-msgstr "Distributions par processus"
+#: ../../Zotlabs/Module/Directory.php:399
+msgid "Alphabetic"
+msgstr "Alphabétique"
-#: ../../Zotlabs/Module/Admin.php:531
-msgid ""
-"Number of deliveries to attempt in a single operating system process. Adjust"
-" if necessary to tune system performance. Recommend: 1-5."
-msgstr "Nombre de distributions à tenter au sein d'un seul processus système. Ajuster si nécessaire pour affiner la performance du système. Recommandé&nbsp;:1-5."
+#: ../../Zotlabs/Module/Directory.php:400
+msgid "Reverse Alphabetic"
+msgstr "Alphabétique inversé"
-#: ../../Zotlabs/Module/Admin.php:532
-msgid "Poll interval"
-msgstr "Intervalle de scrutation"
+#: ../../Zotlabs/Module/Directory.php:401
+msgid "Newest to Oldest"
+msgstr "Du plus récent au moins récent"
-#: ../../Zotlabs/Module/Admin.php:532
-msgid ""
-"Delay background polling processes by this many seconds to reduce system "
-"load. If 0, use delivery interval."
-msgstr "Temporise le processus de scrutation en tâche de fond de tant de secondes, pour réduire la charge. Si 0, utilise l'intervalle de distribution."
+#: ../../Zotlabs/Module/Directory.php:402
+msgid "Oldest to Newest"
+msgstr "Du moins récent du plus récent"
-#: ../../Zotlabs/Module/Admin.php:533
-msgid "Maximum Load Average"
-msgstr "Charge maximale moyenne"
+#: ../../Zotlabs/Module/Directory.php:419
+msgid "No entries (some entries may be hidden)."
+msgstr "Pas d'entrées (certaines peuvent être cachées)."
+
+#: ../../Zotlabs/Module/Xchan.php:10
+msgid "Xchan Lookup"
+msgstr "Recherche xchan"
+
+#: ../../Zotlabs/Module/Xchan.php:13
+msgid "Lookup xchan beginning with (or webbie): "
+msgstr "Recherche xchan commençant par (ou adresse \"webbie\")&nbsp;:"
-#: ../../Zotlabs/Module/Admin.php:533
+#: ../../Zotlabs/Module/Suggest.php:37
msgid ""
-"Maximum system load before delivery and poll processes are deferred - "
-"default 50."
-msgstr "Charge système maximale au-delà de laquelle distribution et scrutation sont reportées - par défaut 50."
+"No suggestions available. If this is a new site, please try again in 24 "
+"hours."
+msgstr "Aucune suggestion disponible. Si le site est récent, merci de re-tenter dans 24 heures."
-#: ../../Zotlabs/Module/Admin.php:534
-msgid "Expiration period in days for imported (grid/network) content"
-msgstr "Délai d'expiration pour le contenu importé (réseau)"
+#: ../../Zotlabs/Module/Suggest.php:56 ../../Zotlabs/Widget/Suggestions.php:46
+msgid "Ignore/Hide"
+msgstr "Ignorer/Cacher"
-#: ../../Zotlabs/Module/Admin.php:534
-msgid "0 for no expiration of imported content"
-msgstr "0 pour ne pas expirer le contenu importé"
+#: ../../Zotlabs/Module/Oexchange.php:27
+msgid "Unable to find your hub."
+msgstr "Impossible de trouver votre hub."
-#: ../../Zotlabs/Module/Admin.php:677 ../../Zotlabs/Module/Admin.php:678
-#: ../../Zotlabs/Module/Settings.php:722
-msgid "Off"
-msgstr "Inactif"
+#: ../../Zotlabs/Module/Oexchange.php:41
+msgid "Post successful."
+msgstr "Publication réussie."
-#: ../../Zotlabs/Module/Admin.php:677 ../../Zotlabs/Module/Admin.php:678
-#: ../../Zotlabs/Module/Settings.php:722
-msgid "On"
-msgstr "Actif"
+#: ../../Zotlabs/Module/Mail.php:65
+msgid "Unable to lookup recipient."
+msgstr "Impossible de localiser le destinataire."
-#: ../../Zotlabs/Module/Admin.php:678
-#, php-format
-msgid "Lock feature %s"
-msgstr "Verrouiller fonctionnalité %s"
+#: ../../Zotlabs/Module/Mail.php:72
+msgid "Unable to communicate with requested channel."
+msgstr "Impossible de communiquer avec le canal demandé."
-#: ../../Zotlabs/Module/Admin.php:686
-msgid "Manage Additional Features"
-msgstr "Gérer les fonctionnalités additionnelles"
+#: ../../Zotlabs/Module/Mail.php:79
+msgid "Cannot verify requested channel."
+msgstr "Impossible de vérifier le canal demandé."
-#: ../../Zotlabs/Module/Admin.php:703
-msgid "No server found"
-msgstr "Serveur introuvable"
+#: ../../Zotlabs/Module/Mail.php:97
+msgid "Selected channel has private message restrictions. Send failed."
+msgstr "Le canal choisi a des restrictions quant aux messages privés. L'envoi a échoué."
-#: ../../Zotlabs/Module/Admin.php:710 ../../Zotlabs/Module/Admin.php:1046
-msgid "ID"
-msgstr "Identifiant"
+#: ../../Zotlabs/Module/Mail.php:178
+msgid "Messages"
+msgstr "Messages"
-#: ../../Zotlabs/Module/Admin.php:710
-msgid "for channel"
-msgstr "pour le canal"
+#: ../../Zotlabs/Module/Mail.php:213
+msgid "Message recalled."
+msgstr "Message rappelé."
-#: ../../Zotlabs/Module/Admin.php:710
-msgid "on server"
-msgstr "sur le serveur"
+#: ../../Zotlabs/Module/Mail.php:226
+msgid "Conversation removed."
+msgstr "Conversation supprimée."
-#: ../../Zotlabs/Module/Admin.php:712
-msgid "Server"
-msgstr "Serveur"
+#: ../../Zotlabs/Module/Mail.php:241 ../../Zotlabs/Module/Mail.php:362
+msgid "Expires YYYY-MM-DD HH:MM"
+msgstr "Expire le YYYY-MM-DD à HH:MM"
-#: ../../Zotlabs/Module/Admin.php:746
-msgid ""
-"By default, unfiltered HTML is allowed in embedded media. This is inherently"
-" insecure."
-msgstr ""
+#: ../../Zotlabs/Module/Mail.php:269
+msgid "Requested channel is not in this network"
+msgstr "Le canal demandé n'est pas sur ce réseau"
-#: ../../Zotlabs/Module/Admin.php:749
-msgid ""
-"The recommended setting is to only allow unfiltered HTML from the following "
-"sites:"
-msgstr ""
+#: ../../Zotlabs/Module/Mail.php:277
+msgid "Send Private Message"
+msgstr "Envoyer un message privé"
-#: ../../Zotlabs/Module/Admin.php:750
-msgid ""
-"https://youtube.com/<br />https://www.youtube.com/<br />https://youtu.be/<br"
-" />https://vimeo.com/<br />https://soundcloud.com/<br />"
-msgstr ""
+#: ../../Zotlabs/Module/Mail.php:278 ../../Zotlabs/Module/Mail.php:415
+msgid "To:"
+msgstr "À&nbsp;:"
-#: ../../Zotlabs/Module/Admin.php:751
-msgid ""
-"All other embedded content will be filtered, <strong>unless</strong> "
-"embedded content from that site is explicitly blocked."
-msgstr ""
+#: ../../Zotlabs/Module/Mail.php:281 ../../Zotlabs/Module/Mail.php:417
+msgid "Subject:"
+msgstr "Objet&nbsp;:"
-#: ../../Zotlabs/Module/Admin.php:756 ../../include/widgets.php:1385
-msgid "Security"
-msgstr "Sécurité"
+#: ../../Zotlabs/Module/Mail.php:286 ../../Zotlabs/Module/Mail.php:423
+#: ../../include/conversation.php:1323
+msgid "Attach file"
+msgstr "Joindre un fichier"
-#: ../../Zotlabs/Module/Admin.php:758
-msgid "Block public"
-msgstr "Bloquer \"public\""
+#: ../../Zotlabs/Module/Mail.php:288
+msgid "Send"
+msgstr "Envoyer"
-#: ../../Zotlabs/Module/Admin.php:758
-msgid ""
-"Check to block public access to all otherwise public personal pages on this "
-"site unless you are currently authenticated."
-msgstr "Sélectionner pour ne permettre l'accès aux pages personnelles \"publiques\" du site qu'aux personnes authentifiées, pas aux personnes anonymes du web."
+#: ../../Zotlabs/Module/Mail.php:291 ../../Zotlabs/Module/Mail.php:428
+#: ../../include/conversation.php:1368
+msgid "Set expiration date"
+msgstr "Définir la date d'expiration"
-#: ../../Zotlabs/Module/Admin.php:759
-msgid "Set \"Transport Security\" HTTP header"
-msgstr ""
+#: ../../Zotlabs/Module/Mail.php:387
+msgid "Delete message"
+msgstr "Supprimer le message"
-#: ../../Zotlabs/Module/Admin.php:760
-msgid "Set \"Content Security Policy\" HTTP header"
-msgstr ""
+#: ../../Zotlabs/Module/Mail.php:388
+msgid "Delivery report"
+msgstr "Rapport de distribution"
-#: ../../Zotlabs/Module/Admin.php:761
-msgid "Allow communications only from these sites"
-msgstr "N'autorisez que les communications venant de ces sites"
+#: ../../Zotlabs/Module/Mail.php:389
+msgid "Recall message"
+msgstr "Rappeler le message"
+
+#: ../../Zotlabs/Module/Mail.php:391
+msgid "Message has been recalled."
+msgstr "Le message a été rappelé."
+
+#: ../../Zotlabs/Module/Mail.php:408
+msgid "Delete Conversation"
+msgstr "Supprimer la conversation"
-#: ../../Zotlabs/Module/Admin.php:761
+#: ../../Zotlabs/Module/Mail.php:410
msgid ""
-"One site per line. Leave empty to allow communication from anywhere by "
-"default"
-msgstr "Un site par ligne. Laisser vide pour autoriser les communications de tous les sites, par défaut."
+"No secure communications available. You <strong>may</strong> be able to "
+"respond from the sender's profile page."
+msgstr "Aucune communication sécurisée n'est possible. Vous pourrez <strong>peut-être</strong> répondre depuis la page de profil de l'émetteur."
-#: ../../Zotlabs/Module/Admin.php:762
-msgid "Block communications from these sites"
-msgstr "Bloquer les communications de ces sites"
+#: ../../Zotlabs/Module/Mail.php:414
+msgid "Send Reply"
+msgstr "Envoyer la réponse"
-#: ../../Zotlabs/Module/Admin.php:763
-msgid "Allow communications only from these channels"
-msgstr "N'autoriser que les communications de ces canaux"
+#: ../../Zotlabs/Module/Mail.php:419
+#, php-format
+msgid "Your message for %s (%s):"
+msgstr "Votre message pour %s (%s)&nbsp;:"
+
+#: ../../Zotlabs/Module/Pubsites.php:24 ../../Zotlabs/Widget/Pubsites.php:12
+msgid "Public Hubs"
+msgstr "Instances publiques"
-#: ../../Zotlabs/Module/Admin.php:763
+#: ../../Zotlabs/Module/Pubsites.php:27
msgid ""
-"One channel (hash) per line. Leave empty to allow from any channel by "
-"default"
-msgstr "Un canal (adresse) par ligne. Laisser vide pour autoriser les communications de tous les canaux, par défaut"
+"The listed hubs allow public registration for the $Projectname network. All "
+"hubs in the network are interlinked so membership on any of them conveys "
+"membership in the network as a whole. Some hubs may require subscription or "
+"provide tiered service plans. The hub itself <strong>may</strong> provide "
+"additional details."
+msgstr "Les sites listés permettent l'enregistrement public de comptes pour le réseau $Projectname. Tous les sites du réseau sont reliés entre eux, être membre d'un site revient à être membre de tous. Certains sites peuvent demander une souscription ou proposer différents niveaux de service. Chaque site <strong>peut</strong> fournir des détails supplémentaires."
-#: ../../Zotlabs/Module/Admin.php:764
-msgid "Block communications from these channels"
-msgstr "Bloquer les communications de ces canaux"
+#: ../../Zotlabs/Module/Pubsites.php:33
+msgid "Hub URL"
+msgstr "URL du site"
-#: ../../Zotlabs/Module/Admin.php:765
-msgid "Only allow embeds from secure (SSL) websites and links."
-msgstr ""
+#: ../../Zotlabs/Module/Pubsites.php:33
+msgid "Access Type"
+msgstr "Type d'accès"
-#: ../../Zotlabs/Module/Admin.php:766
-msgid "Allow unfiltered embedded HTML content only from these domains"
-msgstr ""
+#: ../../Zotlabs/Module/Pubsites.php:33
+msgid "Registration Policy"
+msgstr "Politique d'inscription"
-#: ../../Zotlabs/Module/Admin.php:766
-msgid "One site per line. By default embedded content is filtered."
-msgstr ""
+#: ../../Zotlabs/Module/Pubsites.php:33
+msgid "Stats"
+msgstr "Statistiques"
-#: ../../Zotlabs/Module/Admin.php:767
-msgid "Block embedded HTML from these domains"
-msgstr "Bloquer le HTML embarqué à partir de ces domaines"
+#: ../../Zotlabs/Module/Pubsites.php:33
+msgid "Software"
+msgstr "Logiciel"
-#: ../../Zotlabs/Module/Admin.php:785
-msgid "Update has been marked successful"
-msgstr "La mise à jour a été marquée comme réussie"
+#: ../../Zotlabs/Module/Pubsites.php:48
+msgid "Rate"
+msgstr "Evaluer"
-#: ../../Zotlabs/Module/Admin.php:795
-#, php-format
-msgid "Executing %s failed. Check system logs."
-msgstr "L'éxecution de %s a échoué. Merci de vérifier les journaux du système."
+#: ../../Zotlabs/Module/Impel.php:41 ../../include/bbcode.php:203
+msgid "webpage"
+msgstr "pages web"
-#: ../../Zotlabs/Module/Admin.php:798
-#, php-format
-msgid "Update %s was successfully applied."
-msgstr "La mise à jour %s a été appliquée avec succès."
+#: ../../Zotlabs/Module/Impel.php:46 ../../include/bbcode.php:209
+msgid "block"
+msgstr "bloquer"
+
+#: ../../Zotlabs/Module/Impel.php:51 ../../include/bbcode.php:206
+msgid "layout"
+msgstr "mise en page"
+
+#: ../../Zotlabs/Module/Impel.php:58 ../../include/bbcode.php:212
+msgid "menu"
+msgstr "menu"
-#: ../../Zotlabs/Module/Admin.php:802
+#: ../../Zotlabs/Module/Impel.php:181
#, php-format
-msgid "Update %s did not return a status. Unknown if it succeeded."
-msgstr "La mise à jour %s n'a pas retourné d'information. Impossible de savoir si elle a réussi ou non."
+msgid "%s element installed"
+msgstr "Elément %s installé"
-#: ../../Zotlabs/Module/Admin.php:805
+#: ../../Zotlabs/Module/Impel.php:184
#, php-format
-msgid "Update function %s could not be found."
-msgstr "La fonction de mise à jour %s est introuvable."
+msgid "%s element installation failed"
+msgstr "L'installation de l'élément %s a échoué"
-#: ../../Zotlabs/Module/Admin.php:821
-msgid "No failed updates."
-msgstr "Aucune mise à jour défaillante."
+#: ../../Zotlabs/Module/Rbmark.php:94
+msgid "Select a bookmark folder"
+msgstr "Choisir un dossier de favoris"
-#: ../../Zotlabs/Module/Admin.php:825
-msgid "Failed Updates"
-msgstr "Mises à jour défaillantes"
+#: ../../Zotlabs/Module/Rbmark.php:99
+msgid "Save Bookmark"
+msgstr "Enregistrer le favori"
-#: ../../Zotlabs/Module/Admin.php:827
-msgid "Mark success (if update was manually applied)"
-msgstr "Marquer comme réussie (si la mise à jour a été réalisée manuellement)"
+#: ../../Zotlabs/Module/Rbmark.php:100
+msgid "URL of bookmark"
+msgstr "URL du favori"
-#: ../../Zotlabs/Module/Admin.php:828
-msgid "Attempt to execute this update step automatically"
-msgstr "Tenter de réaliser cette étape de mise à jour automatiquement"
+#: ../../Zotlabs/Module/Rbmark.php:105
+msgid "Or enter new bookmark folder name"
+msgstr "Ou entrez un nouveau nom de dossier de favoris"
-#: ../../Zotlabs/Module/Admin.php:859
-msgid "Queue Statistics"
-msgstr "Statistiques de file d'attente"
+#: ../../Zotlabs/Module/Filer.php:52
+msgid "Enter a folder name"
+msgstr ""
-#: ../../Zotlabs/Module/Admin.php:860
-msgid "Total Entries"
-msgstr "Nombre d'entrées total"
+#: ../../Zotlabs/Module/Filer.php:52
+msgid "or select an existing folder (doubleclick)"
+msgstr ""
-#: ../../Zotlabs/Module/Admin.php:861
-msgid "Priority"
-msgstr "Priorité"
+#: ../../Zotlabs/Module/Filer.php:54 ../../Zotlabs/Lib/ThreadItem.php:137
+msgid "Save to Folder"
+msgstr "Enregistrer dans le dossier"
-#: ../../Zotlabs/Module/Admin.php:862
-msgid "Destination URL"
-msgstr "URL de destination"
+#: ../../Zotlabs/Module/Probe.php:28 ../../Zotlabs/Module/Probe.php:32
+#, php-format
+msgid "Fetching URL returns error: %1$s"
+msgstr "Récupération d'URL échouée&nbsp;: %1$s"
-#: ../../Zotlabs/Module/Admin.php:863
-msgid "Mark hub permanently offline"
-msgstr "Marquer le hub comme étant hors ligne de manière permanente"
+#: ../../Zotlabs/Module/Register.php:49
+msgid "Maximum daily site registrations exceeded. Please try again tomorrow."
+msgstr "Nombre d'inscriptions quotidiennes dépassé. Merci d'essayer à nouveau demain."
-#: ../../Zotlabs/Module/Admin.php:864
-msgid "Empty queue for this hub"
-msgstr "Vider la file d'attente pour ce hub"
+#: ../../Zotlabs/Module/Register.php:55
+msgid ""
+"Please indicate acceptance of the Terms of Service. Registration failed."
+msgstr "Merci d'indiquer votre adhésion aux conditions de service. L'inscription a échoué."
-#: ../../Zotlabs/Module/Admin.php:865
-msgid "Last known contact"
-msgstr "Dernier contact connu"
+#: ../../Zotlabs/Module/Register.php:89
+msgid "Passwords do not match."
+msgstr "Les mots de passe ne concordent pas."
-#: ../../Zotlabs/Module/Admin.php:901
-#, php-format
-msgid "%s account blocked/unblocked"
-msgid_plural "%s account blocked/unblocked"
-msgstr[0] "%s compte bloqué/débloqué"
-msgstr[1] "%s comptes bloqués/débloqués"
+#: ../../Zotlabs/Module/Register.php:131
+msgid ""
+"Registration successful. Please check your email for validation "
+"instructions."
+msgstr "Inscription réussie. Merci de vérifier vos courriels pour valider votre compte."
-#: ../../Zotlabs/Module/Admin.php:908
-#, php-format
-msgid "%s account deleted"
-msgid_plural "%s accounts deleted"
-msgstr[0] "%s compte supprimé"
-msgstr[1] "%s comptes supprimés"
+#: ../../Zotlabs/Module/Register.php:137
+msgid "Your registration is pending approval by the site owner."
+msgstr "Votre inscription est en attente d'approbation par l'administrateur."
-#: ../../Zotlabs/Module/Admin.php:944
-msgid "Account not found"
-msgstr "Compte introuvable"
+#: ../../Zotlabs/Module/Register.php:140
+msgid "Your registration can not be processed."
+msgstr "Votre inscription ne peut être traîtée."
-#: ../../Zotlabs/Module/Admin.php:955
-#, php-format
-msgid "Account '%s' deleted"
-msgstr "Compte '%s' supprimé"
+#: ../../Zotlabs/Module/Register.php:184
+msgid "Registration on this hub is disabled."
+msgstr "La création de nouveaux comptes est désactivée pour ce site."
-#: ../../Zotlabs/Module/Admin.php:963
-#, php-format
-msgid "Account '%s' blocked"
-msgstr "Compte '%s' bloqué"
+#: ../../Zotlabs/Module/Register.php:193
+msgid "Registration on this hub is by approval only."
+msgstr "La création de compte sur ce site est soumise à approbation."
-#: ../../Zotlabs/Module/Admin.php:971
-#, php-format
-msgid "Account '%s' unblocked"
-msgstr "Compte '%s' débloqué"
+#: ../../Zotlabs/Module/Register.php:194
+msgid "<a href=\"pubsites\">Register at another affiliated hub.</a>"
+msgstr "<a href=\"pubsites\">S'enregistrer sur un autre site du réseau.</a>"
-#: ../../Zotlabs/Module/Admin.php:1031 ../../Zotlabs/Module/Admin.php:1044
-#: ../../include/widgets.php:1383
-msgid "Accounts"
-msgstr "Comptes"
+#: ../../Zotlabs/Module/Register.php:204
+msgid ""
+"This site has exceeded the number of allowed daily account registrations. "
+"Please try again tomorrow."
+msgstr "Ce site a dépassé le nombre de création de comptes autorisé chaque jour. Merci d'essayer à nouveau demain."
-#: ../../Zotlabs/Module/Admin.php:1033 ../../Zotlabs/Module/Admin.php:1212
-msgid "select all"
-msgstr "tout sélectionner"
+#: ../../Zotlabs/Module/Register.php:227
+#, php-format
+msgid "I accept the %s for this website"
+msgstr "J'accepte les %s de ce site"
-#: ../../Zotlabs/Module/Admin.php:1034
-msgid "Registrations waiting for confirm"
-msgstr ""
+#: ../../Zotlabs/Module/Register.php:229
+#, php-format
+msgid "I am over 13 years of age and accept the %s for this website"
+msgstr "J'ai plus de 13 ans et j'accepte les %s de ce site"
-#: ../../Zotlabs/Module/Admin.php:1035
-msgid "Request date"
-msgstr "Date de la demande"
+#: ../../Zotlabs/Module/Register.php:233
+msgid "Your email address"
+msgstr "Votre adresse de courriel"
-#: ../../Zotlabs/Module/Admin.php:1036
-msgid "No registrations."
-msgstr "Pas d'inscriptions."
+#: ../../Zotlabs/Module/Register.php:234
+msgid "Choose a password"
+msgstr "Choisissez un mot de passe"
-#: ../../Zotlabs/Module/Admin.php:1038
-msgid "Deny"
-msgstr "Refuser"
+#: ../../Zotlabs/Module/Register.php:235
+msgid "Please re-enter your password"
+msgstr "Merci de saisir à nouveau votre mot de passe"
-#: ../../Zotlabs/Module/Admin.php:1048 ../../include/group.php:267
-msgid "All Channels"
-msgstr "Tous les canaux"
+#: ../../Zotlabs/Module/Register.php:236
+msgid "Please enter your invitation code"
+msgstr "Merci de saisir votre code d'invitation"
-#: ../../Zotlabs/Module/Admin.php:1049
-msgid "Register date"
-msgstr "Date d'inscription"
+#: ../../Zotlabs/Module/Register.php:241
+msgid "no"
+msgstr "non"
-#: ../../Zotlabs/Module/Admin.php:1050
-msgid "Last login"
-msgstr "Dernière connexion"
+#: ../../Zotlabs/Module/Register.php:241
+msgid "yes"
+msgstr "oui"
-#: ../../Zotlabs/Module/Admin.php:1051
-msgid "Expires"
-msgstr "Expire le"
+#: ../../Zotlabs/Module/Register.php:258
+msgid "Membership on this site is by invitation only."
+msgstr "L'inscription à ce site se fait uniquement sur invitation."
-#: ../../Zotlabs/Module/Admin.php:1052
-msgid "Service Class"
-msgstr "Classe de service"
+#: ../../Zotlabs/Module/Register.php:270 ../../boot.php:1612
+#: ../../include/nav.php:145
+msgid "Register"
+msgstr "S'inscrire"
-#: ../../Zotlabs/Module/Admin.php:1054
+#: ../../Zotlabs/Module/Register.php:271
msgid ""
-"Selected accounts will be deleted!\\n\\nEverything these accounts had posted"
-" on this site will be permanently deleted!\\n\\nAre you sure?"
-msgstr "Les comptes sélectionnés seront supprimés&nbsp;!\\n\\nTout ce que ces utilisateurs ont publié sur ce site sera détruit de manière définitive&nbsp;!\\n\\nÊtes-vous sûr&nbsp;?"
+"This site may require email verification after submitting this form. If you "
+"are returned to a login page, please check your email for instructions."
+msgstr "Ce site peut demander une validation de votre email. Si vous revenez sur le formulaire de connexion, vérifiez vos emails et suivez les instructions. Regardez aussi les spams."
-#: ../../Zotlabs/Module/Admin.php:1055
-msgid ""
-"The account {0} will be deleted!\\n\\nEverything this account has posted on "
-"this site will be permanently deleted!\\n\\nAre you sure?"
-msgstr "Le compte {0} sera supprimé&nbsp;!\\n\\nTout ce que cet utilisateur a publié sur ce site sera détruit de manière définitive&nbsp;!\\n\\nÊtes-vous sûr&nbsp;?"
+#: ../../Zotlabs/Module/Cover_photo.php:136
+#: ../../Zotlabs/Module/Cover_photo.php:186
+msgid "Cover Photos"
+msgstr "Photos de couverture"
-#: ../../Zotlabs/Module/Admin.php:1091
+#: ../../Zotlabs/Module/Cover_photo.php:237 ../../include/items.php:4286
+msgid "female"
+msgstr "femme"
+
+#: ../../Zotlabs/Module/Cover_photo.php:238 ../../include/items.php:4287
#, php-format
-msgid "%s channel censored/uncensored"
-msgid_plural "%s channels censored/uncensored"
-msgstr[0] "%s canal censuré/dé-censuré"
-msgstr[1] "%s canaux censurés/dé-censurés"
+msgid "%1$s updated her %2$s"
+msgstr "%1$s a mis à jour son %2$s"
-#: ../../Zotlabs/Module/Admin.php:1100
+#: ../../Zotlabs/Module/Cover_photo.php:239 ../../include/items.php:4288
+msgid "male"
+msgstr "homme"
+
+#: ../../Zotlabs/Module/Cover_photo.php:240 ../../include/items.php:4289
#, php-format
-msgid "%s channel code allowed/disallowed"
-msgid_plural "%s channels code allowed/disallowed"
-msgstr[0] "code autorisé/interdit pour %s canal"
-msgstr[1] "code autorisé/interdit pour %s canaux"
+msgid "%1$s updated his %2$s"
+msgstr "%1$s a mis à jour son %2$s"
-#: ../../Zotlabs/Module/Admin.php:1106
+#: ../../Zotlabs/Module/Cover_photo.php:242 ../../include/items.php:4291
#, php-format
-msgid "%s channel deleted"
-msgid_plural "%s channels deleted"
-msgstr[0] "%s canal supprimé"
-msgstr[1] "%s canaux supprimés"
+msgid "%1$s updated their %2$s"
+msgstr "%1$s a mis a jour sa %2$s"
-#: ../../Zotlabs/Module/Admin.php:1126
-msgid "Channel not found"
-msgstr "Canal introuvable"
+#: ../../Zotlabs/Module/Cover_photo.php:244 ../../include/channel.php:1757
+msgid "cover photo"
+msgstr "Photo principale"
-#: ../../Zotlabs/Module/Admin.php:1136
-#, php-format
-msgid "Channel '%s' deleted"
-msgstr "Canal '%s' supprimé"
+#: ../../Zotlabs/Module/Cover_photo.php:360
+msgid "Upload Cover Photo"
+msgstr "Téléverser une photo de couverture"
-#: ../../Zotlabs/Module/Admin.php:1148
-#, php-format
-msgid "Channel '%s' censored"
-msgstr "Canal '%s' censuré"
+#: ../../Zotlabs/Module/Help.php:23
+msgid "Documentation Search"
+msgstr "Chercher dans la documentation"
-#: ../../Zotlabs/Module/Admin.php:1148
-#, php-format
-msgid "Channel '%s' uncensored"
-msgstr "Canal '%s' non censuré"
+#: ../../Zotlabs/Module/Help.php:80 ../../include/conversation.php:1764
+msgid "About"
+msgstr "À propos"
-#: ../../Zotlabs/Module/Admin.php:1159
-#, php-format
-msgid "Channel '%s' code allowed"
-msgstr "Code autorisé pour le canal '%s'"
+#: ../../Zotlabs/Module/Help.php:82
+msgid "Administrators"
+msgstr "Administrateurs"
-#: ../../Zotlabs/Module/Admin.php:1159
-#, php-format
-msgid "Channel '%s' code disallowed"
-msgstr "Code interdit pour le canal '%s'"
+#: ../../Zotlabs/Module/Help.php:83
+msgid "Developers"
+msgstr "Développeurs"
-#: ../../Zotlabs/Module/Admin.php:1210 ../../include/widgets.php:1384
-msgid "Channels"
-msgstr "Canaux"
+#: ../../Zotlabs/Module/Help.php:84
+msgid "Tutorials"
+msgstr "Tutoriels"
-#: ../../Zotlabs/Module/Admin.php:1214
-msgid "Censor"
-msgstr "Censurer"
+#: ../../Zotlabs/Module/Help.php:93
+msgid "$Projectname Documentation"
+msgstr "Documentation $Projectname"
-#: ../../Zotlabs/Module/Admin.php:1215
-msgid "Uncensor"
-msgstr "Ne plus censurer"
+#: ../../Zotlabs/Module/Help.php:94
+msgid "Contents"
+msgstr "Contenus"
-#: ../../Zotlabs/Module/Admin.php:1216
-msgid "Allow Code"
-msgstr "Autoriser le code"
+#: ../../Zotlabs/Module/Tagrm.php:48 ../../Zotlabs/Module/Tagrm.php:98
+msgid "Tag removed"
+msgstr "Étiquette retirée"
-#: ../../Zotlabs/Module/Admin.php:1217
-msgid "Disallow Code"
-msgstr "Interdire le code"
+#: ../../Zotlabs/Module/Tagrm.php:123
+msgid "Remove Item Tag"
+msgstr "Retirer une étiquette à l'élément"
-#: ../../Zotlabs/Module/Admin.php:1218 ../../include/conversation.php:1611
-msgid "Channel"
-msgstr "Canal"
+#: ../../Zotlabs/Module/Tagrm.php:125
+msgid "Select a tag to remove: "
+msgstr "Étiquette à retirer&nbsp;:"
-#: ../../Zotlabs/Module/Admin.php:1222
-msgid "UID"
-msgstr "UID"
+#: ../../Zotlabs/Module/Network.php:96
+msgid "No such group"
+msgstr "Groupe introuvable"
-#: ../../Zotlabs/Module/Admin.php:1226
-msgid ""
-"Selected channels will be deleted!\\n\\nEverything that was posted in these "
-"channels on this site will be permanently deleted!\\n\\nAre you sure?"
-msgstr "Les canaux sélectionnés seront supprimés&nbsp;!\\n\\nTout ce qui a été publié dans ces canaux sur ce site sera définitivement supprimé&nbsp;!\\n\\nÊtes-vous sûr&nbsp;?"
+#: ../../Zotlabs/Module/Network.php:136
+msgid "No such channel"
+msgstr "Canal introuvable"
-#: ../../Zotlabs/Module/Admin.php:1227
-msgid ""
-"The channel {0} will be deleted!\\n\\nEverything that was posted in this "
-"channel on this site will be permanently deleted!\\n\\nAre you sure?"
-msgstr "Le canal {0} sera supprimé&nbsp;!\\n\\nTout ce qui a été publié sur ce canal sera définitivement supprimé&nbsp;!\\n\\nÊtes-vous sûr(e)&nbsp;?"
+#: ../../Zotlabs/Module/Network.php:141
+msgid "forum"
+msgstr "forum"
-#: ../../Zotlabs/Module/Admin.php:1284
-#, php-format
-msgid "Plugin %s disabled."
-msgstr "Greffon %s désactivé."
+#: ../../Zotlabs/Module/Network.php:153
+msgid "Search Results For:"
+msgstr "Résultats de recherche pour&nbsp;:"
-#: ../../Zotlabs/Module/Admin.php:1288
-#, php-format
-msgid "Plugin %s enabled."
-msgstr "Greffon %s activé."
+#: ../../Zotlabs/Module/Network.php:221
+msgid "Privacy group is empty"
+msgstr "Groupe de contacts vide"
-#: ../../Zotlabs/Module/Admin.php:1298 ../../Zotlabs/Module/Admin.php:1585
-msgid "Disable"
-msgstr "Désactiver"
+#: ../../Zotlabs/Module/Network.php:230
+msgid "Privacy group: "
+msgstr "Groupe de contacts&nbsp;:"
-#: ../../Zotlabs/Module/Admin.php:1301 ../../Zotlabs/Module/Admin.php:1587
-msgid "Enable"
-msgstr "Activer"
+#: ../../Zotlabs/Module/Network.php:256
+msgid "Invalid connection."
+msgstr "Contact non valide."
-#: ../../Zotlabs/Module/Admin.php:1330 ../../Zotlabs/Module/Admin.php:1420
-#: ../../include/widgets.php:1387
-msgid "Plugins"
-msgstr "Greffons"
+#: ../../Zotlabs/Module/Network.php:275 ../../addon/redred/redred.php:65
+msgid "Invalid channel."
+msgstr "Canal invalide."
-#: ../../Zotlabs/Module/Admin.php:1331 ../../Zotlabs/Module/Admin.php:1614
-msgid "Toggle"
-msgstr "(Dés)activer"
+#: ../../Zotlabs/Module/Acl.php:344
+msgid "network"
+msgstr "réseau"
-#: ../../Zotlabs/Module/Admin.php:1332 ../../Zotlabs/Module/Admin.php:1615
-#: ../../Zotlabs/Lib/Apps.php:215 ../../include/widgets.php:638
-#: ../../include/nav.php:208
-msgid "Settings"
-msgstr "Paramètres"
+#: ../../Zotlabs/Module/Acl.php:354
+msgid "RSS"
+msgstr "RSS"
-#: ../../Zotlabs/Module/Admin.php:1339 ../../Zotlabs/Module/Admin.php:1624
-msgid "Author: "
-msgstr "Auteur&nbsp;:"
+#: ../../Zotlabs/Module/Home.php:74 ../../Zotlabs/Module/Home.php:82
+#: ../../addon/opensearch/opensearch.php:42
+msgid "$Projectname"
+msgstr "$Projectname"
-#: ../../Zotlabs/Module/Admin.php:1340 ../../Zotlabs/Module/Admin.php:1625
-msgid "Maintainer: "
-msgstr "Maintenu par&nbsp;:"
+#: ../../Zotlabs/Module/Home.php:92
+#, php-format
+msgid "Welcome to %s"
+msgstr "Bienvenue sur %s"
-#: ../../Zotlabs/Module/Admin.php:1341
-msgid "Minimum project version: "
-msgstr "Version minimum du projet&nbsp;:"
+#: ../../Zotlabs/Module/Filestorage.php:87
+msgid "Permission Denied."
+msgstr "Permission refusée."
-#: ../../Zotlabs/Module/Admin.php:1342
-msgid "Maximum project version: "
-msgstr "Version maximum du projet&nbsp;:"
+#: ../../Zotlabs/Module/Filestorage.php:103
+msgid "File not found."
+msgstr "Fichier introuvable."
-#: ../../Zotlabs/Module/Admin.php:1343
-msgid "Minimum PHP version: "
-msgstr "Version minimum de PHP&nbsp;:"
+#: ../../Zotlabs/Module/Filestorage.php:146
+msgid "Edit file permissions"
+msgstr "Modifier les autorisations d'accès au fichier"
-#: ../../Zotlabs/Module/Admin.php:1344
-msgid "Requires: "
-msgstr "Requiert&nbsp;:"
+#: ../../Zotlabs/Module/Filestorage.php:159
+msgid "Set/edit permissions"
+msgstr "Définir/modifier les autorisations"
-#: ../../Zotlabs/Module/Admin.php:1345 ../../Zotlabs/Module/Admin.php:1425
-msgid "Disabled - version incompatibility"
-msgstr "Désactivé - version incompatible"
+#: ../../Zotlabs/Module/Filestorage.php:160
+msgid "Include all files and sub folders"
+msgstr "Inclure tous fichiers et sous-répertoires"
-#: ../../Zotlabs/Module/Admin.php:1394
-msgid "Enter the public git repository URL of the plugin repo."
-msgstr ""
+#: ../../Zotlabs/Module/Filestorage.php:161
+msgid "Return to file list"
+msgstr "Retourner à la liste des fichiers"
-#: ../../Zotlabs/Module/Admin.php:1395
-msgid "Plugin repo git URL"
-msgstr ""
+#: ../../Zotlabs/Module/Filestorage.php:163
+msgid "Copy/paste this code to attach file to a post"
+msgstr "Copiez/collez ce code pour joindre le fichier à une publication"
-#: ../../Zotlabs/Module/Admin.php:1396
-msgid "Custom repo name"
-msgstr ""
+#: ../../Zotlabs/Module/Filestorage.php:164
+msgid "Copy/paste this URL to link file from a web page"
+msgstr "Copiez/collez cette URL pour pointer vers ce fichier depuis une page web"
-#: ../../Zotlabs/Module/Admin.php:1396
-msgid "(optional)"
-msgstr ""
+#: ../../Zotlabs/Module/Filestorage.php:166
+msgid "Share this file"
+msgstr "Partager ce fichier"
-#: ../../Zotlabs/Module/Admin.php:1397
-msgid "Download Plugin Repo"
-msgstr ""
+#: ../../Zotlabs/Module/Filestorage.php:167
+msgid "Show URL to this file"
+msgstr "Montrer l'URL de ce fichier"
-#: ../../Zotlabs/Module/Admin.php:1404
-msgid "Install new repo"
-msgstr ""
+#: ../../Zotlabs/Module/Filestorage.php:168
+msgid "Notify your contacts about this file"
+msgstr "Notifier vos contacts à propos de ce fichier"
-#: ../../Zotlabs/Module/Admin.php:1405 ../../Zotlabs/Lib/Apps.php:330
-msgid "Install"
-msgstr "Installer"
+#: ../../Zotlabs/Module/Common.php:14
+msgid "No channel."
+msgstr "Pas de canal."
-#: ../../Zotlabs/Module/Admin.php:1427
-msgid "Manage Repos"
-msgstr ""
+#: ../../Zotlabs/Module/Common.php:43
+msgid "Common connections"
+msgstr "Contacts en commun"
-#: ../../Zotlabs/Module/Admin.php:1428
-msgid "Installed Plugin Repositories"
-msgstr ""
+#: ../../Zotlabs/Module/Common.php:48
+msgid "No connections in common."
+msgstr "Pas de contacts en commun."
-#: ../../Zotlabs/Module/Admin.php:1429
-msgid "Install a New Plugin Repository"
-msgstr ""
+#: ../../Zotlabs/Module/Viewconnections.php:65
+msgid "No connections."
+msgstr "Aucun contact."
-#: ../../Zotlabs/Module/Admin.php:1435 ../../Zotlabs/Module/Settings.php:77
-#: ../../Zotlabs/Module/Settings.php:616 ../../Zotlabs/Lib/Apps.php:330
-msgid "Update"
-msgstr "Mise à jour"
+#: ../../Zotlabs/Module/Viewconnections.php:78
+#, php-format
+msgid "Visit %s's profile [%s]"
+msgstr "Visiter le profil de %s [%s]"
-#: ../../Zotlabs/Module/Admin.php:1436
-msgid "Switch branch"
-msgstr ""
+#: ../../Zotlabs/Module/Viewconnections.php:107
+msgid "View Connections"
+msgstr "Voir les contacts"
-#: ../../Zotlabs/Module/Admin.php:1550
-msgid "No themes found."
-msgstr "Aucun thème trouvé."
+#: ../../Zotlabs/Module/Admin.php:94
+msgid "# Accounts"
+msgstr "# Comptes"
-#: ../../Zotlabs/Module/Admin.php:1606
-msgid "Screenshot"
-msgstr "Capture d'écran"
+#: ../../Zotlabs/Module/Admin.php:95
+msgid "# blocked accounts"
+msgstr "# comptes bloqués"
-#: ../../Zotlabs/Module/Admin.php:1613 ../../Zotlabs/Module/Admin.php:1647
-#: ../../include/widgets.php:1388
-msgid "Themes"
-msgstr "Thèmes"
+#: ../../Zotlabs/Module/Admin.php:96
+msgid "# expired accounts"
+msgstr "# comptes expirés"
-#: ../../Zotlabs/Module/Admin.php:1652
-msgid "[Experimental]"
-msgstr "[Expérimental]"
+#: ../../Zotlabs/Module/Admin.php:97
+msgid "# expiring accounts"
+msgstr "# comptes expirant"
-#: ../../Zotlabs/Module/Admin.php:1653
-msgid "[Unsupported]"
-msgstr "[Non maintenu]"
+#: ../../Zotlabs/Module/Admin.php:108
+msgid "# Channels"
+msgstr "# Canaux"
-#: ../../Zotlabs/Module/Admin.php:1677
-msgid "Log settings updated."
-msgstr "Paramètres du journal mis à jour."
+#: ../../Zotlabs/Module/Admin.php:109
+msgid "# primary"
+msgstr "# primaire"
-#: ../../Zotlabs/Module/Admin.php:1732 ../../include/widgets.php:1409
-#: ../../include/widgets.php:1419
-msgid "Logs"
-msgstr "Journaux"
+#: ../../Zotlabs/Module/Admin.php:110
+msgid "# clones"
+msgstr "# clones"
-#: ../../Zotlabs/Module/Admin.php:1734
-msgid "Clear"
-msgstr "Vider"
+#: ../../Zotlabs/Module/Admin.php:116
+msgid "Message queues"
+msgstr "File des messages"
-#: ../../Zotlabs/Module/Admin.php:1740
-msgid "Debugging"
-msgstr "Débogage"
+#: ../../Zotlabs/Module/Admin.php:133
+msgid "Your software should be updated"
+msgstr "Votre logiciel doit d'être mis à jour"
-#: ../../Zotlabs/Module/Admin.php:1741
-msgid "Log file"
-msgstr "Fichier du journal"
+#: ../../Zotlabs/Module/Admin.php:138
+msgid "Summary"
+msgstr "Résumé"
-#: ../../Zotlabs/Module/Admin.php:1741
-msgid ""
-"Must be writable by web server. Relative to your top-level webserver "
-"directory."
-msgstr ""
+#: ../../Zotlabs/Module/Admin.php:141
+msgid "Registered accounts"
+msgstr "Comptes enregistrés"
-#: ../../Zotlabs/Module/Admin.php:1742
-msgid "Log level"
-msgstr "Niveau de journalisation"
+#: ../../Zotlabs/Module/Admin.php:142
+msgid "Pending registrations"
+msgstr "Inscriptions en attente"
-#: ../../Zotlabs/Module/Admin.php:2028
-msgid "New Profile Field"
-msgstr "Nouveau champ de profil"
+#: ../../Zotlabs/Module/Admin.php:143
+msgid "Registered channels"
+msgstr "Canaux enregistrés"
-#: ../../Zotlabs/Module/Admin.php:2029 ../../Zotlabs/Module/Admin.php:2049
-msgid "Field nickname"
-msgstr "Nom court du champ"
+#: ../../Zotlabs/Module/Admin.php:144
+msgid "Active plugins"
+msgstr "Greffons actifs"
-#: ../../Zotlabs/Module/Admin.php:2029 ../../Zotlabs/Module/Admin.php:2049
-msgid "System name of field"
-msgstr "Nom système du champ"
+#: ../../Zotlabs/Module/Admin.php:145
+msgid "Version"
+msgstr "Version"
-#: ../../Zotlabs/Module/Admin.php:2030 ../../Zotlabs/Module/Admin.php:2050
-msgid "Input type"
-msgstr "Type de champ"
+#: ../../Zotlabs/Module/Admin.php:146
+msgid "Repository version (master)"
+msgstr "Version du dépôt (maître)"
-#: ../../Zotlabs/Module/Admin.php:2031 ../../Zotlabs/Module/Admin.php:2051
-msgid "Field Name"
-msgstr "Nom du champ"
+#: ../../Zotlabs/Module/Admin.php:147
+msgid "Repository version (dev)"
+msgstr "Version du dépôt (développeur)"
-#: ../../Zotlabs/Module/Admin.php:2031 ../../Zotlabs/Module/Admin.php:2051
-msgid "Label on profile pages"
-msgstr "Étiquette sur les pages de profil"
+#: ../../Zotlabs/Module/Service_limits.php:23
+msgid "No service class restrictions found."
+msgstr "Aucune restriction de classe de service trouvée."
-#: ../../Zotlabs/Module/Admin.php:2032 ../../Zotlabs/Module/Admin.php:2052
-msgid "Help text"
-msgstr "Aide à la saisie"
+#: ../../Zotlabs/Module/Rate.php:156
+msgid "Website:"
+msgstr "Site web&nbsp;:"
-#: ../../Zotlabs/Module/Admin.php:2032 ../../Zotlabs/Module/Admin.php:2052
-msgid "Additional info (optional)"
-msgstr "Informations additionnelles (facultatif)"
+#: ../../Zotlabs/Module/Rate.php:159
+#, php-format
+msgid "Remote Channel [%s] (not yet known on this site)"
+msgstr "Canal distant [%s] (encore inconnu sur ce site)"
-#: ../../Zotlabs/Module/Admin.php:2042
-msgid "Field definition not found"
-msgstr "Définition du champ introuvable"
+#: ../../Zotlabs/Module/Rate.php:160
+msgid "Rating (this information is public)"
+msgstr "Evaluation (cette information est publique)"
-#: ../../Zotlabs/Module/Admin.php:2048
-msgid "Edit Profile Field"
-msgstr "Modifier le champ de profil"
+#: ../../Zotlabs/Module/Rate.php:161
+msgid "Optionally explain your rating (this information is public)"
+msgstr "Explication facultative de votre évaluation (cette information est publique)"
-#: ../../Zotlabs/Module/Admin.php:2106 ../../include/widgets.php:1390
-msgid "Profile Fields"
-msgstr "Champs de profil"
+#: ../../Zotlabs/Module/Lostpass.php:19
+msgid "No valid account found."
+msgstr "Aucun compte valide trouvé."
-#: ../../Zotlabs/Module/Admin.php:2107
-msgid "Basic Profile Fields"
-msgstr "Champs de profil de base"
+#: ../../Zotlabs/Module/Lostpass.php:33
+msgid "Password reset request issued. Check your email."
+msgstr "Demande de réinitialisation du mot de passe envoyée. Vérifiez vos courriels."
-#: ../../Zotlabs/Module/Admin.php:2108
-msgid "Advanced Profile Fields"
-msgstr "Champs de profil avancés"
+#: ../../Zotlabs/Module/Lostpass.php:39 ../../Zotlabs/Module/Lostpass.php:108
+#, php-format
+msgid "Site Member (%s)"
+msgstr "Membre du site (%s)"
-#: ../../Zotlabs/Module/Admin.php:2108
-msgid "(In addition to basic fields)"
-msgstr "(en plus des champs de base)"
+#: ../../Zotlabs/Module/Lostpass.php:44 ../../Zotlabs/Module/Lostpass.php:49
+#, php-format
+msgid "Password reset requested at %s"
+msgstr "Demande de réinitialisation du mot de passe sur %s"
-#: ../../Zotlabs/Module/Admin.php:2110
-msgid "All available fields"
-msgstr "Tous les champs disponibles"
+#: ../../Zotlabs/Module/Lostpass.php:68
+msgid ""
+"Request could not be verified. (You may have previously submitted it.) "
+"Password reset failed."
+msgstr "La demande n'a pas pu être vérifiée. (Peut-être l'avez vous déjà utilisée.) La réinitialisation a échoué."
-#: ../../Zotlabs/Module/Admin.php:2111
-msgid "Custom Fields"
-msgstr "Champs personnalisés"
+#: ../../Zotlabs/Module/Lostpass.php:91 ../../boot.php:1639
+msgid "Password Reset"
+msgstr "Réinitialiser le mot de passe"
-#: ../../Zotlabs/Module/Admin.php:2115
-msgid "Create Custom Field"
-msgstr "Créer un champ personnalisé"
+#: ../../Zotlabs/Module/Lostpass.php:92
+msgid "Your password has been reset as requested."
+msgstr "Votre mot de passe a bien été réinitialisé."
-#: ../../Zotlabs/Module/Appman.php:37 ../../Zotlabs/Module/Appman.php:53
-msgid "App installed."
-msgstr "Application installée."
+#: ../../Zotlabs/Module/Lostpass.php:93
+msgid "Your new password is"
+msgstr "Votre nouveau mot de passe est"
-#: ../../Zotlabs/Module/Appman.php:46
-msgid "Malformed app."
-msgstr "Erreur de l'application - Malformée."
+#: ../../Zotlabs/Module/Lostpass.php:94
+msgid "Save or copy your new password - and then"
+msgstr "Enregistrez ou copiez votre nouveau mot de passe, puis"
-#: ../../Zotlabs/Module/Appman.php:104
-msgid "Embed code"
-msgstr "Imbriquer le code"
+#: ../../Zotlabs/Module/Lostpass.php:95
+msgid "click here to login"
+msgstr "cliquez ici pour vous connecter"
-#: ../../Zotlabs/Module/Appman.php:110 ../../include/widgets.php:107
-msgid "Edit App"
-msgstr "Modifier l'application"
+#: ../../Zotlabs/Module/Lostpass.php:96
+msgid ""
+"Your password may be changed from the <em>Settings</em> page after "
+"successful login."
+msgstr "Votre mot de passe peut être changé depuis la page des <em>Paramètres</em> une fois connecté."
-#: ../../Zotlabs/Module/Appman.php:110
-msgid "Create App"
-msgstr "Créer une application"
+#: ../../Zotlabs/Module/Lostpass.php:117
+#, php-format
+msgid "Your password has changed at %s"
+msgstr "Votre mot de passe de %s a été changé"
-#: ../../Zotlabs/Module/Appman.php:115
-msgid "Name of app"
-msgstr "Nom de l'application"
+#: ../../Zotlabs/Module/Lostpass.php:130
+msgid "Forgot your Password?"
+msgstr "Mot de passe oublié&nbsp;?"
-#: ../../Zotlabs/Module/Appman.php:116
-msgid "Location (URL) of app"
-msgstr "Emplacement (URL) de l'application"
+#: ../../Zotlabs/Module/Lostpass.php:131
+msgid ""
+"Enter your email address and submit to have your password reset. Then check "
+"your email for further instructions."
+msgstr "Saisissez votre adresse de courriel, et validez, pour réinitialiser votre mot de passe. Vérifiez ensuite votre boîte aux lettres pour la suite des instructions."
-#: ../../Zotlabs/Module/Appman.php:118
-msgid "Photo icon URL"
-msgstr "URL de l'icône à utiliser pour cette photo"
+#: ../../Zotlabs/Module/Lostpass.php:132
+msgid "Email Address"
+msgstr "Adresse de courriel"
-#: ../../Zotlabs/Module/Appman.php:118
-msgid "80 x 80 pixels - optional"
-msgstr "80 x 80 pixels - facultatif"
+#: ../../Zotlabs/Module/Lostpass.php:133
+msgid "Reset"
+msgstr "Réinitialiser"
-#: ../../Zotlabs/Module/Appman.php:119
-msgid "Categories (optional, comma separated list)"
-msgstr ""
+#: ../../Zotlabs/Module/Notifications.php:43 ../../include/nav.php:186
+msgid "Mark all system notifications seen"
+msgstr "Marquer toutes les notifications système comme vues"
-#: ../../Zotlabs/Module/Appman.php:120
-msgid "Version ID"
-msgstr "Identifiant de version"
+#: ../../Zotlabs/Lib/Apps.php:212
+msgid "Site Admin"
+msgstr "Administrateur"
-#: ../../Zotlabs/Module/Appman.php:121
-msgid "Price of app"
-msgstr "Prix de l'application"
+#: ../../Zotlabs/Lib/Apps.php:213 ../../addon/buglink/buglink.php:16
+msgid "Report Bug"
+msgstr "Reporter des bogues"
-#: ../../Zotlabs/Module/Appman.php:122
-msgid "Location (URL) to purchase app"
-msgstr "Emplacement (URL) pour l'achat de l'application"
+#: ../../Zotlabs/Lib/Apps.php:214
+msgid "View Bookmarks"
+msgstr "Voir les marques-pages"
-#: ../../Zotlabs/Module/Rbmark.php:94
-msgid "Select a bookmark folder"
-msgstr "Choisir un dossier de favoris"
+#: ../../Zotlabs/Lib/Apps.php:215
+msgid "My Chatrooms"
+msgstr "Mes salons de discussions"
-#: ../../Zotlabs/Module/Rbmark.php:99
-msgid "Save Bookmark"
-msgstr "Enregistrer le favori"
+#: ../../Zotlabs/Lib/Apps.php:217
+msgid "Firefox Share"
+msgstr "Partager via Firefox"
-#: ../../Zotlabs/Module/Rbmark.php:100
-msgid "URL of bookmark"
-msgstr "URL du favori"
+#: ../../Zotlabs/Lib/Apps.php:218
+msgid "Remote Diagnostics"
+msgstr "Diagnostiques à distance"
-#: ../../Zotlabs/Module/Rbmark.php:105
-msgid "Or enter new bookmark folder name"
-msgstr "Ou entrez un nouveau nom de dossier de favoris"
+#: ../../Zotlabs/Lib/Apps.php:219 ../../include/features.php:337
+msgid "Suggest Channels"
+msgstr "Suggérer des canaux"
-#: ../../Zotlabs/Module/Register.php:49
-msgid "Maximum daily site registrations exceeded. Please try again tomorrow."
-msgstr "Nombre d'inscriptions quotidiennes dépassé. Merci d'essayer à nouveau demain."
+#: ../../Zotlabs/Lib/Apps.php:220 ../../boot.php:1631
+#: ../../include/nav.php:113
+msgid "Login"
+msgstr "Connexion"
-#: ../../Zotlabs/Module/Register.php:55
-msgid ""
-"Please indicate acceptance of the Terms of Service. Registration failed."
-msgstr "Merci d'indiquer votre adhésion aux conditions de service. L'inscription a échoué."
+#: ../../Zotlabs/Lib/Apps.php:222 ../../include/nav.php:172
+msgid "Grid"
+msgstr "Réseau"
-#: ../../Zotlabs/Module/Register.php:89
-msgid "Passwords do not match."
-msgstr "Les mots de passe ne concordent pas."
+#: ../../Zotlabs/Lib/Apps.php:226 ../../include/conversation.php:1848
+#: ../../include/features.php:99
+msgid "Wiki"
+msgstr "Wiki"
-#: ../../Zotlabs/Module/Register.php:131
-msgid ""
-"Registration successful. Please check your email for validation "
-"instructions."
-msgstr "Inscription réussie. Merci de vérifier vos courriels pour valider votre compte."
+#: ../../Zotlabs/Lib/Apps.php:227 ../../include/nav.php:176
+msgid "Channel Home"
+msgstr "Mon canal"
-#: ../../Zotlabs/Module/Register.php:137
-msgid "Your registration is pending approval by the site owner."
-msgstr "Votre inscription est en attente d'approbation par l'administrateur."
+#: ../../Zotlabs/Lib/Apps.php:230 ../../include/conversation.php:1793
+#: ../../include/conversation.php:1796 ../../include/nav.php:196
+msgid "Events"
+msgstr "Événements"
-#: ../../Zotlabs/Module/Register.php:140
-msgid "Your registration can not be processed."
-msgstr "Votre inscription ne peut être traîtée."
+#: ../../Zotlabs/Lib/Apps.php:231
+msgid "Directory"
+msgstr "Annuaire"
-#: ../../Zotlabs/Module/Register.php:184
-msgid "Registration on this hub is disabled."
-msgstr "La création de nouveaux comptes est désactivée pour ce site."
+#: ../../Zotlabs/Lib/Apps.php:233 ../../include/nav.php:188
+msgid "Mail"
+msgstr "Messages"
-#: ../../Zotlabs/Module/Register.php:193
-msgid "Registration on this hub is by approval only."
-msgstr "La création de compte sur ce site est soumise à approbation."
+#: ../../Zotlabs/Lib/Apps.php:236
+msgid "Chat"
+msgstr "Clavardage"
-#: ../../Zotlabs/Module/Register.php:194
-msgid "<a href=\"pubsites\">Register at another affiliated hub.</a>"
-msgstr "<a href=\"pubsites\">S'enregistrer sur un autre site du réseau.</a>"
+#: ../../Zotlabs/Lib/Apps.php:238
+msgid "Probe"
+msgstr "Sonder"
-#: ../../Zotlabs/Module/Register.php:204
-msgid ""
-"This site has exceeded the number of allowed daily account registrations. "
-"Please try again tomorrow."
-msgstr "Ce site a dépassé le nombre de création de comptes autorisé chaque jour. Merci d'essayer à nouveau demain."
+#: ../../Zotlabs/Lib/Apps.php:239
+msgid "Suggest"
+msgstr "Suggérer"
-#: ../../Zotlabs/Module/Register.php:215
-msgid "Terms of Service"
-msgstr "Conditions de service"
+#: ../../Zotlabs/Lib/Apps.php:240
+msgid "Random Channel"
+msgstr "Un canal au hasard"
-#: ../../Zotlabs/Module/Register.php:221
-#, php-format
-msgid "I accept the %s for this website"
-msgstr "J'accepte les %s de ce site"
+#: ../../Zotlabs/Lib/Apps.php:241
+msgid "Invite"
+msgstr "Invitation"
-#: ../../Zotlabs/Module/Register.php:223
-#, php-format
-msgid "I am over 13 years of age and accept the %s for this website"
-msgstr "J'ai plus de 13 ans et j'accepte les %s de ce site"
+#: ../../Zotlabs/Lib/Apps.php:242 ../../Zotlabs/Widget/Admin.php:26
+msgid "Features"
+msgstr "Fonctionalités"
-#: ../../Zotlabs/Module/Register.php:227
-msgid "Your email address"
-msgstr "Votre adresse de courriel"
+#: ../../Zotlabs/Lib/Apps.php:243 ../../addon/openid/MysqlProvider.php:69
+msgid "Language"
+msgstr "Langue"
-#: ../../Zotlabs/Module/Register.php:228
-msgid "Choose a password"
-msgstr "Choisissez un mot de passe"
+#: ../../Zotlabs/Lib/Apps.php:244
+msgid "Post"
+msgstr "Envoyer"
-#: ../../Zotlabs/Module/Register.php:229
-msgid "Please re-enter your password"
-msgstr "Merci de saisir à nouveau votre mot de passe"
+#: ../../Zotlabs/Lib/Apps.php:245 ../../addon/openid/MysqlProvider.php:58
+#: ../../addon/openid/MysqlProvider.php:59
+#: ../../addon/openid/MysqlProvider.php:60
+msgid "Profile Photo"
+msgstr "Photo du Profil"
-#: ../../Zotlabs/Module/Register.php:230
-msgid "Please enter your invitation code"
-msgstr "Merci de saisir votre code d'invitation"
+#: ../../Zotlabs/Lib/Apps.php:355
+msgid "Purchase"
+msgstr "Acheter"
-#: ../../Zotlabs/Module/Register.php:236
-msgid "no"
-msgstr "non"
+#: ../../Zotlabs/Lib/Apps.php:359
+msgid "Undelete"
+msgstr "Restaurer"
-#: ../../Zotlabs/Module/Register.php:236
-msgid "yes"
-msgstr "oui"
+#: ../../Zotlabs/Lib/Apps.php:364
+msgid "Add to app-tray"
+msgstr ""
-#: ../../Zotlabs/Module/Register.php:250
-msgid "Membership on this site is by invitation only."
-msgstr "L'inscription à ce site se fait uniquement sur invitation."
+#: ../../Zotlabs/Lib/Apps.php:365
+msgid "Remove from app-tray"
+msgstr ""
-#: ../../Zotlabs/Module/Register.php:262 ../../include/nav.php:147
-#: ../../boot.php:1685
-msgid "Register"
-msgstr "S'inscrire"
+#: ../../Zotlabs/Lib/Permcat.php:58
+msgctxt "permcat"
+msgid "default"
+msgstr "défaut"
-#: ../../Zotlabs/Module/Register.php:262
-msgid "Proceed to create your first channel"
-msgstr "Continuer pour créer votre premier canal"
+#: ../../Zotlabs/Lib/Permcat.php:96
+msgctxt "permcat"
+msgid "follower"
+msgstr "abonné"
+
+#: ../../Zotlabs/Lib/Permcat.php:100
+msgctxt "permcat"
+msgid "contributor"
+msgstr "contributeur"
+
+#: ../../Zotlabs/Lib/Permcat.php:104
+msgctxt "permcat"
+msgid "publisher"
+msgstr "rédacteur"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:31
+#: ../../Zotlabs/Lib/NativeWikiPage.php:72
+msgid "(No Title)"
+msgstr "(Pas de titre)"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:86
+msgid "Wiki page create failed."
+msgstr "Échec de création de la page wiki."
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:99
+msgid "Wiki not found."
+msgstr "Wiki introuvable."
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:110
+msgid "Destination name already exists"
+msgstr "Le nom de destination est déjà pris"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:136
+#: ../../Zotlabs/Lib/NativeWikiPage.php:331
+msgid "Page not found"
+msgstr "Page introuvable"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:166
+msgid "Error reading page content"
+msgstr "Erreur de lecture du contenu de la page"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:322
+#: ../../Zotlabs/Lib/NativeWikiPage.php:370
+#: ../../Zotlabs/Lib/NativeWikiPage.php:437
+#: ../../Zotlabs/Lib/NativeWikiPage.php:478
+msgid "Error reading wiki"
+msgstr "Erreur de lecture du wiki"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:358
+msgid "Page update failed."
+msgstr "Echec de modification de la page."
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:392
+msgid "Nothing deleted"
+msgstr "Rien n'a été supprimé"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:458
+msgid "Compare: object not found."
+msgstr "Comparaison&nbsp;: objet introuvable."
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:464
+msgid "Page updated"
+msgstr "Page modifiée"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:467
+msgid "Untitled"
+msgstr "Sans titre"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:473
+msgid "Wiki resource_id required for git commit"
+msgstr "\"resource_id\" du wiki nécessaire pour l'enregistrement dans git."
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:529
+#: ../../Zotlabs/Widget/Wiki_page_history.php:23
+msgctxt "wiki_history"
+msgid "Message"
+msgstr "Message"
-#: ../../Zotlabs/Module/Regmod.php:15
-msgid "Please login."
-msgstr "Merci de vous connecter."
+#: ../../Zotlabs/Lib/NativeWikiPage.php:567
+#: ../../addon/gitwiki/gitwiki_backend.php:579 ../../include/bbcode.php:610
+#: ../../include/bbcode.php:756
+msgid "Different viewers will see this text differently"
+msgstr "Ce texte aura un rendu différent en fonction des utilisateurs"
-#: ../../Zotlabs/Module/Removeaccount.php:34
-msgid ""
-"Account removals are not allowed within 48 hours of changing the account "
-"password."
-msgstr "Il est impossible de supprimer un compte dans les 48 heures après avoir changé le mot de passe du compte."
+#: ../../Zotlabs/Lib/PermissionDescription.php:34
+#: ../../include/acl_selectors.php:128
+msgid "Visible to your default audience"
+msgstr "Visible pour vos contacts seulement"
-#: ../../Zotlabs/Module/Removeaccount.php:56
-msgid "Remove This Account"
-msgstr "Supprimer ce compte"
+#: ../../Zotlabs/Lib/PermissionDescription.php:107
+#: ../../include/acl_selectors.php:201
+msgid "Only me"
+msgstr "Seulement moi"
-#: ../../Zotlabs/Module/Removeaccount.php:57
-#: ../../Zotlabs/Module/Removeme.php:59
-msgid "WARNING: "
-msgstr "AVERTISSEMENT&nbsp;:"
+#: ../../Zotlabs/Lib/PermissionDescription.php:108
+msgid "Public"
+msgstr "Public"
-#: ../../Zotlabs/Module/Removeaccount.php:57
-msgid ""
-"This account and all its channels will be completely removed from the "
-"network. "
-msgstr "Ce compte et tous ses canaux seront entièrement supprimés du réseau."
+#: ../../Zotlabs/Lib/PermissionDescription.php:109
+msgid "Anybody in the $Projectname network"
+msgstr "N'importe qui dans le réseau de $Projectname"
-#: ../../Zotlabs/Module/Removeaccount.php:57
-#: ../../Zotlabs/Module/Removeme.php:59
-msgid "This action is permanent and can not be undone!"
-msgstr "Cette action est permanente et irréversible&nbsp;!"
+#: ../../Zotlabs/Lib/PermissionDescription.php:110
+#, php-format
+msgid "Any account on %s"
+msgstr "N'importe quel compte sur %s"
-#: ../../Zotlabs/Module/Removeaccount.php:58
-#: ../../Zotlabs/Module/Removeme.php:60
-msgid "Please enter your password for verification:"
-msgstr "Merci de saisir votre mot de passe pour vérification&nbsp;:"
+#: ../../Zotlabs/Lib/PermissionDescription.php:111
+msgid "Any of my connections"
+msgstr "N'importe laquelle de mes connexions"
-#: ../../Zotlabs/Module/Removeaccount.php:59
+#: ../../Zotlabs/Lib/PermissionDescription.php:112
+msgid "Only connections I specifically allow"
+msgstr "Uniquement les connexions que j'ai expréssément autorisées"
+
+#: ../../Zotlabs/Lib/PermissionDescription.php:113
+msgid "Anybody authenticated (could include visitors from other networks)"
+msgstr "N'importe qui d'authentifié (cela peut inclure des visiteurs d'autres réseaux)"
+
+#: ../../Zotlabs/Lib/PermissionDescription.php:114
+msgid "Any connections including those who haven't yet been approved"
+msgstr "N'importe quelle connexions, y compris celles qui n'ont pas encore été approuvées"
+
+#: ../../Zotlabs/Lib/PermissionDescription.php:150
msgid ""
-"Remove this account, all its channels and all its channel clones from the "
-"network"
-msgstr "Supprimer du réseau ce compte, tous ses canaux et tous les clones de ses canaux."
+"This is your default setting for the audience of your normal stream, and "
+"posts."
+msgstr "Ceci est votre réglage par défaut de l'audience de vos publications sur votre canal normal."
-#: ../../Zotlabs/Module/Removeaccount.php:59
+#: ../../Zotlabs/Lib/PermissionDescription.php:151
msgid ""
-"By default only the instances of the channels located on this hub will be "
-"removed from the network"
-msgstr "Par défaut, seules les instances des canaux situés sur ce hub seront supprimées du réseau"
+"This is your default setting for who can view your default channel profile"
+msgstr "Ceci est votre réglage par défaut à propos de qui peut voir votre canal de profil par défaut."
-#: ../../Zotlabs/Module/Removeaccount.php:60
-#: ../../Zotlabs/Module/Settings.php:705
-msgid "Remove Account"
-msgstr "Supprimer le compte"
+#: ../../Zotlabs/Lib/PermissionDescription.php:152
+msgid "This is your default setting for who can view your connections"
+msgstr "Ceci est votre réglage par défaut à propos de qui peut voir vos relations."
-#: ../../Zotlabs/Module/Removeme.php:33
+#: ../../Zotlabs/Lib/PermissionDescription.php:153
msgid ""
-"Channel removals are not allowed within 48 hours of changing the account "
-"password."
-msgstr "Il est impossible de supprimer un canal moins de 48 heures après avoir changé le mot de passe d'un compte."
-
-#: ../../Zotlabs/Module/Removeme.php:58
-msgid "Remove This Channel"
-msgstr "Supprimer ce canal"
+"This is your default setting for who can view your file storage and photos"
+msgstr "Ceci est votre réglage par défaut à propos de qui peut voir vos fichiers ou photos stocké(e)s"
-#: ../../Zotlabs/Module/Removeme.php:59
-msgid "This channel will be completely removed from the network. "
-msgstr "Ce canal sera complètement supprimé du réseau."
+#: ../../Zotlabs/Lib/PermissionDescription.php:154
+msgid "This is your default setting for the audience of your webpages"
+msgstr "Ceci est votre réglage par défaut de l'audience de vos pages web."
-#: ../../Zotlabs/Module/Removeme.php:61
-msgid "Remove this channel and all its clones from the network"
-msgstr "Supprimer ce canal ainsi que tous ses clones sur le réseau"
+#: ../../Zotlabs/Lib/Chatroom.php:27
+msgid "Missing room name"
+msgstr "Il manque le nom du salon"
-#: ../../Zotlabs/Module/Removeme.php:61
-msgid ""
-"By default only the instance of the channel located on this hub will be "
-"removed from the network"
-msgstr "Par défaut, seule l'instance du canal présente sur ce hub sera supprimée du réseau"
+#: ../../Zotlabs/Lib/Chatroom.php:36
+msgid "Duplicate room name"
+msgstr "Un salon avec ce nom existe déjà"
-#: ../../Zotlabs/Module/Removeme.php:62 ../../Zotlabs/Module/Settings.php:1124
-msgid "Remove Channel"
-msgstr "Supprimer le canal"
+#: ../../Zotlabs/Lib/Chatroom.php:86 ../../Zotlabs/Lib/Chatroom.php:94
+msgid "Invalid room specifier."
+msgstr "Identifiant de salon invalide."
-#: ../../Zotlabs/Module/Rmagic.php:44
-msgid ""
-"We encountered a problem while logging in with the OpenID you provided. "
-"Please check the correct spelling of the ID."
-msgstr "Nous avons rencontré un problème avec l'OpenID que vous nous avez fourni. Merci de vérifier que l'ID est correctement saisi."
+#: ../../Zotlabs/Lib/Chatroom.php:126
+msgid "Room not found."
+msgstr "Salon introuvable."
-#: ../../Zotlabs/Module/Rmagic.php:44
-msgid "The error message was:"
-msgstr "Le message d'erreur était&nbsp;:"
+#: ../../Zotlabs/Lib/Chatroom.php:147
+msgid "Room is full"
+msgstr "Le salon est plein"
-#: ../../Zotlabs/Module/Rmagic.php:48
-msgid "Authentication failed."
-msgstr "Échec de l'authentification."
+#: ../../Zotlabs/Lib/Enotify.php:60 ../../include/network.php:1947
+msgid "$Projectname Notification"
+msgstr "Notification $Projectname"
-#: ../../Zotlabs/Module/Rmagic.php:88
-msgid "Remote Authentication"
-msgstr "Authentification distante"
+#: ../../Zotlabs/Lib/Enotify.php:61 ../../addon/diaspora/util.php:218
+#: ../../addon/diaspora/util.php:231 ../../addon/diaspora/p.php:46
+#: ../../include/network.php:1948
+msgid "$projectname"
+msgstr "$projectname"
-#: ../../Zotlabs/Module/Rmagic.php:89
-msgid "Enter your channel address (e.g. channel@example.com)"
-msgstr "Entrez l'adresse de votre canal (par ex. moncanal@monsite.com)"
+#: ../../Zotlabs/Lib/Enotify.php:63 ../../include/network.php:1950
+msgid "Thank You,"
+msgstr "Merci,"
-#: ../../Zotlabs/Module/Rmagic.php:90
-msgid "Authenticate"
-msgstr "Authentifier"
+#: ../../Zotlabs/Lib/Enotify.php:65 ../../include/network.php:1952
+#, php-format
+msgid "%s Administrator"
+msgstr "l'administrateur de %s"
-#: ../../Zotlabs/Module/Search.php:216
+#: ../../Zotlabs/Lib/Enotify.php:116
#, php-format
-msgid "Items tagged with: %s"
-msgstr "Eléments étiquetés avec&nbsp;: %s"
+msgid "%s <!item_type!>"
+msgstr "%s <!item_type!>"
-#: ../../Zotlabs/Module/Search.php:218
+#: ../../Zotlabs/Lib/Enotify.php:120
#, php-format
-msgid "Search results for: %s"
-msgstr "Résultats de recherche pour&nbsp;: %s"
+msgid "[$Projectname:Notify] New mail received at %s"
+msgstr "[$Projectname:Notify] Nouveau mail reçu sur %s"
-#: ../../Zotlabs/Module/Service_limits.php:23
-msgid "No service class restrictions found."
-msgstr "Aucune restriction de classe de service trouvée."
+#: ../../Zotlabs/Lib/Enotify.php:122
+#, php-format
+msgid "%1$s, %2$s sent you a new private message at %3$s."
+msgstr "%1$s, vous avez reçu un message privé sur %3$s, de la part de %2$s."
-#: ../../Zotlabs/Module/Settings.php:69
-msgid "Name is required"
-msgstr "Le nom est requis"
+#: ../../Zotlabs/Lib/Enotify.php:123
+#, php-format
+msgid "%1$s sent you %2$s."
+msgstr "%1$s vous a envoyé %2$s."
-#: ../../Zotlabs/Module/Settings.php:73
-msgid "Key and Secret are required"
-msgstr "Clef et secret sont requis"
+#: ../../Zotlabs/Lib/Enotify.php:123
+msgid "a private message"
+msgstr "un message privé"
-#: ../../Zotlabs/Module/Settings.php:225
-msgid "Not valid email."
-msgstr "Adresse de courriel non valide."
+#: ../../Zotlabs/Lib/Enotify.php:124
+#, php-format
+msgid "Please visit %s to view and/or reply to your private messages."
+msgstr "Merci de visiter %s pour voir et/ou répondre à vos messages privés."
-#: ../../Zotlabs/Module/Settings.php:228
-msgid "Protected email address. Cannot change to that email."
-msgstr "Adresse de courriel protégée. Impossible de l'utiliser."
+#: ../../Zotlabs/Lib/Enotify.php:183
+#, php-format
+msgid "%1$s, %2$s commented on [zrl=%3$s]a %4$s[/zrl]"
+msgstr "%1$s, %2$s a commenté sur [zrl=%3$s]%4$s[/zrl]"
-#: ../../Zotlabs/Module/Settings.php:237
-msgid "System failure storing new email. Please try again."
-msgstr "Défaillance système lors du stockage de la nouvelle adresse de courriel. Merci d'essayer à nouveau."
+#: ../../Zotlabs/Lib/Enotify.php:191
+#, php-format
+msgid "%1$s, %2$s commented on [zrl=%3$s]%4$s's %5$s[/zrl]"
+msgstr "%1$s, %2$s a commenté sur [zrl=%3$s]%5$s de %4$s[/zrl]"
-#: ../../Zotlabs/Module/Settings.php:254
-msgid "Password verification failed."
-msgstr "La vérification du mot de passe a échoué."
+#: ../../Zotlabs/Lib/Enotify.php:200
+#, php-format
+msgid "%1$s, %2$s commented on [zrl=%3$s]your %4$s[/zrl]"
+msgstr "%1$s, %2$s a commenté [zrl=%3$s]votre %4$s[/zrl]"
-#: ../../Zotlabs/Module/Settings.php:261
-msgid "Passwords do not match. Password unchanged."
-msgstr "Les deux saisies du mot de passe ne correspondent pas. Il n'a donc pas été changé."
+#: ../../Zotlabs/Lib/Enotify.php:211
+#, php-format
+msgid "[$Projectname:Notify] Comment to conversation #%1$d by %2$s"
+msgstr "[$Projectname:Notify] Commentaire effectué sur la conversation #%1$d par %2$s"
-#: ../../Zotlabs/Module/Settings.php:265
-msgid "Empty passwords are not allowed. Password unchanged."
-msgstr "Le mot de passe ne peut pas être vide. Il n'a donc pas été changé."
+#: ../../Zotlabs/Lib/Enotify.php:212
+#, php-format
+msgid "%1$s, %2$s commented on an item/conversation you have been following."
+msgstr "%1$s, %2$s a commenté un élément de conversation que vous suivez."
-#: ../../Zotlabs/Module/Settings.php:279
-msgid "Password changed."
-msgstr "Le mot de passe a été changé."
+#: ../../Zotlabs/Lib/Enotify.php:215 ../../Zotlabs/Lib/Enotify.php:292
+#: ../../Zotlabs/Lib/Enotify.php:309 ../../Zotlabs/Lib/Enotify.php:335
+#: ../../Zotlabs/Lib/Enotify.php:353 ../../Zotlabs/Lib/Enotify.php:367
+#, php-format
+msgid "Please visit %s to view and/or reply to the conversation."
+msgstr "Merci de visiter %s pour voir et/ou répondre sur cette conversation."
-#: ../../Zotlabs/Module/Settings.php:281
-msgid "Password update failed. Please try again."
-msgstr "La mise à jour du mot de passe a échoué. Merci d'essayer à nouveau."
+#: ../../Zotlabs/Lib/Enotify.php:273
+#, php-format
+msgid "%1$s, %2$s liked [zrl=%3$s]your %4$s[/zrl]"
+msgstr "%1$s, %2$s aiment [zrl=%3$s]votre %4$s[/zrl]"
-#: ../../Zotlabs/Module/Settings.php:525
-msgid "Settings updated."
-msgstr "Paramètres mis à jour."
+#: ../../Zotlabs/Lib/Enotify.php:288
+#, php-format
+msgid "[$Projectname:Notify] Like received to conversation #%1$d by %2$s"
+msgstr "[$Projectname:Notify] Aime reçu à la convesation #%1$d par %2$s"
-#: ../../Zotlabs/Module/Settings.php:589 ../../Zotlabs/Module/Settings.php:615
-#: ../../Zotlabs/Module/Settings.php:651
-msgid "Add application"
-msgstr "Ajouter une application"
+#: ../../Zotlabs/Lib/Enotify.php:289
+#, php-format
+msgid "%1$s, %2$s liked an item/conversation you created."
+msgstr "%1$s, %2$s a aimé un élément ou une conversation que vous avez créée."
-#: ../../Zotlabs/Module/Settings.php:592
-msgid "Name of application"
-msgstr "Nom de l'application"
+#: ../../Zotlabs/Lib/Enotify.php:300
+#, php-format
+msgid "[$Projectname:Notify] %s posted to your profile wall"
+msgstr "[$Projectname:Notify] %s a publié sur le mur de votre profil"
-#: ../../Zotlabs/Module/Settings.php:593 ../../Zotlabs/Module/Settings.php:619
-msgid "Consumer Key"
-msgstr "Clef client"
+#: ../../Zotlabs/Lib/Enotify.php:302
+#, php-format
+msgid "%1$s, %2$s posted to your profile wall at %3$s"
+msgstr "%1$s, %2$s a publié sur votre profil à %3$s"
-#: ../../Zotlabs/Module/Settings.php:593 ../../Zotlabs/Module/Settings.php:594
-msgid "Automatically generated - change if desired. Max length 20"
-msgstr "Généré automatiquement - à changer si besoin. Longueur maximale 20 caractères."
+#: ../../Zotlabs/Lib/Enotify.php:304
+#, php-format
+msgid "%1$s, %2$s posted to [zrl=%3$s]your wall[/zrl]"
+msgstr "%1$s, %2$s a publié sur [zrl=%3$s]votre profil[/zrl]"
-#: ../../Zotlabs/Module/Settings.php:594 ../../Zotlabs/Module/Settings.php:620
-msgid "Consumer Secret"
-msgstr "Secret client"
+#: ../../Zotlabs/Lib/Enotify.php:328
+#, php-format
+msgid "[$Projectname:Notify] %s tagged you"
+msgstr "[$Projectname:Notify] %s vous a étiquetté"
-#: ../../Zotlabs/Module/Settings.php:595 ../../Zotlabs/Module/Settings.php:621
-msgid "Redirect"
-msgstr "Redirection"
+#: ../../Zotlabs/Lib/Enotify.php:329
+#, php-format
+msgid "%1$s, %2$s tagged you at %3$s"
+msgstr "%1$s, vous avez été étiqueté sur %3$s par %2$s"
-#: ../../Zotlabs/Module/Settings.php:595
-msgid ""
-"Redirect URI - leave blank unless your application specifically requires "
-"this"
-msgstr "URI de redirection - laissez vide, sauf si votre application le requiert spécifiquement"
+#: ../../Zotlabs/Lib/Enotify.php:330
+#, php-format
+msgid "%1$s, %2$s [zrl=%3$s]tagged you[/zrl]."
+msgstr "%1$s, %2$s [zrl=%3$s]vous a étiqueté[/zrl]."
-#: ../../Zotlabs/Module/Settings.php:596 ../../Zotlabs/Module/Settings.php:622
-msgid "Icon url"
-msgstr "URL de l'icône"
+#: ../../Zotlabs/Lib/Enotify.php:342
+#, php-format
+msgid "[$Projectname:Notify] %1$s poked you"
+msgstr "[$Projectname:Notify] %1$s vous a poké"
-#: ../../Zotlabs/Module/Settings.php:596 ../../Zotlabs/Module/Sources.php:112
-#: ../../Zotlabs/Module/Sources.php:147
-msgid "Optional"
-msgstr "Facultatif"
+#: ../../Zotlabs/Lib/Enotify.php:343
+#, php-format
+msgid "%1$s, %2$s poked you at %3$s"
+msgstr "%1$s, %2$s vous a tapoté sur %3$s"
-#: ../../Zotlabs/Module/Settings.php:607
-msgid "Application not found."
-msgstr "Application introuvable."
+#: ../../Zotlabs/Lib/Enotify.php:344
+#, php-format
+msgid "%1$s, %2$s [zrl=%2$s]poked you[/zrl]."
+msgstr "%1$s, %2$s [zrl=%2$s]vous a tapoté[/zrl]."
-#: ../../Zotlabs/Module/Settings.php:650
-msgid "Connected Apps"
-msgstr "Applications connectées"
+#: ../../Zotlabs/Lib/Enotify.php:360
+#, php-format
+msgid "[$Projectname:Notify] %s tagged your post"
+msgstr "[$Projectname:Notify] %s a étiquetté votre publication"
-#: ../../Zotlabs/Module/Settings.php:654
-msgid "Client key starts with"
-msgstr "La clef partagée commence par"
+#: ../../Zotlabs/Lib/Enotify.php:361
+#, php-format
+msgid "%1$s, %2$s tagged your post at %3$s"
+msgstr "%1$s, %2$s a étiqueté votre publication sur %3$s"
-#: ../../Zotlabs/Module/Settings.php:655
-msgid "No name"
-msgstr "Sans nom"
+#: ../../Zotlabs/Lib/Enotify.php:362
+#, php-format
+msgid "%1$s, %2$s tagged [zrl=%3$s]your post[/zrl]"
+msgstr "%1$s, %2$s a étiqueté [zrl=%3$s]votre publication[/zrl]"
-#: ../../Zotlabs/Module/Settings.php:656
-msgid "Remove authorization"
-msgstr "Révoquer l'autorisation"
+#: ../../Zotlabs/Lib/Enotify.php:374
+msgid "[$Projectname:Notify] Introduction received"
+msgstr "[$Projectname:Notify] Demande de relation reçue"
-#: ../../Zotlabs/Module/Settings.php:669
-msgid "No feature settings configured"
-msgstr "Aucun paramètre de fonctionnalité configuré"
+#: ../../Zotlabs/Lib/Enotify.php:375
+#, php-format
+msgid "%1$s, you've received an new connection request from '%2$s' at %3$s"
+msgstr "%1$s, vous avez reçu une demande de contact de '%2$s' sur %3$s"
-#: ../../Zotlabs/Module/Settings.php:676
-msgid "Feature/Addon Settings"
-msgstr "Paramètres des extensions/greffons"
+#: ../../Zotlabs/Lib/Enotify.php:376
+#, php-format
+msgid ""
+"%1$s, you've received [zrl=%2$s]a new connection request[/zrl] from %3$s."
+msgstr "%1$s, vous avez reçu [zrl=%2$s]une demande de contact[/zrl] de %3$s."
-#: ../../Zotlabs/Module/Settings.php:699
-msgid "Account Settings"
-msgstr "Paramètres du compte"
+#: ../../Zotlabs/Lib/Enotify.php:380 ../../Zotlabs/Lib/Enotify.php:399
+#, php-format
+msgid "You may visit their profile at %s"
+msgstr "Vous pouvez visiter leur profil sur %s"
-#: ../../Zotlabs/Module/Settings.php:700
-msgid "Current Password"
-msgstr "Mot de passe actuel"
+#: ../../Zotlabs/Lib/Enotify.php:382
+#, php-format
+msgid "Please visit %s to approve or reject the connection request."
+msgstr "Merci de visiter %s avant d'approuver (ou non) cette demande de contact."
-#: ../../Zotlabs/Module/Settings.php:701
-msgid "Enter New Password"
-msgstr "Entrez votre nouveau mot de passe"
+#: ../../Zotlabs/Lib/Enotify.php:389
+msgid "[$Projectname:Notify] Friend suggestion received"
+msgstr "[$Projectname:Notify] Suggestion d'amitié reçue"
-#: ../../Zotlabs/Module/Settings.php:702
-msgid "Confirm New Password"
-msgstr "Confirmez le nouveau mot de passe"
+#: ../../Zotlabs/Lib/Enotify.php:390
+#, php-format
+msgid "%1$s, you've received a friend suggestion from '%2$s' at %3$s"
+msgstr "%1$s, vous avez reçu une suggestion d'ami(e) de '%2$s' à %3$s"
-#: ../../Zotlabs/Module/Settings.php:702
-msgid "Leave password fields blank unless changing"
-msgstr "Laissez les mots de passe vides si vous ne voulez pas les modifier"
+#: ../../Zotlabs/Lib/Enotify.php:391
+#, php-format
+msgid ""
+"%1$s, you've received [zrl=%2$s]a friend suggestion[/zrl] for %3$s from "
+"%4$s."
+msgstr "%1$s, avez reçu %3$s comme [zrl=%2$s]une suggestion d'ami(e)[/zrl] de %4$s."
-#: ../../Zotlabs/Module/Settings.php:704
-#: ../../Zotlabs/Module/Settings.php:1041
-msgid "Email Address:"
-msgstr "Adresse de courriel&nbsp;:"
+#: ../../Zotlabs/Lib/Enotify.php:397
+msgid "Name:"
+msgstr "Nom&nbsp;:"
-#: ../../Zotlabs/Module/Settings.php:706
-msgid "Remove this account including all its channels"
-msgstr "Supprimer ce compte et tous ses canaux"
+#: ../../Zotlabs/Lib/Enotify.php:398
+msgid "Photo:"
+msgstr "Photo&nbsp;:"
-#: ../../Zotlabs/Module/Settings.php:729
-msgid "Additional Features"
-msgstr "Fonctionnalités additionnelles"
+#: ../../Zotlabs/Lib/Enotify.php:401
+#, php-format
+msgid "Please visit %s to approve or reject the suggestion."
+msgstr "Merci de visiter %s pour donner suite (ou non) à cette suggestion."
-#: ../../Zotlabs/Module/Settings.php:753
-msgid "Connector Settings"
-msgstr "Paramètres du connecteur"
+#: ../../Zotlabs/Lib/Enotify.php:619
+msgid "[$Projectname:Notify]"
+msgstr "[$Projectname:Notify]"
-#: ../../Zotlabs/Module/Settings.php:792
-msgid "No special theme for mobile devices"
-msgstr "Pas de thème spécifique aux mobiles"
+#: ../../Zotlabs/Lib/Enotify.php:779
+msgid "created a new post"
+msgstr "a publié un nouveau message"
-#: ../../Zotlabs/Module/Settings.php:795
+#: ../../Zotlabs/Lib/Enotify.php:780
#, php-format
-msgid "%s - (Experimental)"
-msgstr "%s - (Expérimental)"
+msgid "commented on %s's post"
+msgstr "a commenté la publication de %s"
-#: ../../Zotlabs/Module/Settings.php:837
-msgid "Display Settings"
-msgstr "Afficher les paramètres"
+#: ../../Zotlabs/Lib/NativeWiki.php:128
+msgid "Wiki files deleted successfully"
+msgstr "Fichiers du wiki supprimés avec succès"
-#: ../../Zotlabs/Module/Settings.php:838
-msgid "Theme Settings"
-msgstr "Paramètres du thème"
+#: ../../Zotlabs/Lib/DB_Upgrade.php:93
+#, php-format
+msgid "Update Error at %s"
+msgstr "Erreur de mise à jour sur %s"
-#: ../../Zotlabs/Module/Settings.php:839
-msgid "Custom Theme Settings"
-msgstr "Paramètres personnels du thème"
+#: ../../Zotlabs/Lib/DB_Upgrade.php:99
+#, php-format
+msgid "Update %s failed. See error logs."
+msgstr "La mise-à-jour %s a échoué. Merci de consulter les journaux d'erreur."
-#: ../../Zotlabs/Module/Settings.php:840
-msgid "Content Settings"
-msgstr "Paramètres liés au contenu"
+#: ../../Zotlabs/Lib/ThreadItem.php:96 ../../include/conversation.php:661
+msgid "Private Message"
+msgstr "Message Privé"
-#: ../../Zotlabs/Module/Settings.php:846
-msgid "Display Theme:"
-msgstr "Afficher le thème&nbsp;:"
+#: ../../Zotlabs/Lib/ThreadItem.php:133 ../../include/conversation.php:653
+msgid "Select"
+msgstr "Sélectionner"
-#: ../../Zotlabs/Module/Settings.php:847
-msgid "Mobile Theme:"
-msgstr "Thème mobile&nbsp;:"
+#: ../../Zotlabs/Lib/ThreadItem.php:158
+msgid "I will attend"
+msgstr "Je participerai"
-#: ../../Zotlabs/Module/Settings.php:848
-msgid "Preload images before rendering the page"
-msgstr "Pré-charger les images avant d'afficher la page"
+#: ../../Zotlabs/Lib/ThreadItem.php:158
+msgid "I will not attend"
+msgstr "Je ne participerai pas"
-#: ../../Zotlabs/Module/Settings.php:848
-msgid ""
-"The subjective page load time will be longer but the page will be ready when"
-" displayed"
-msgstr "Le temps de charge perçu de la page sera plus long mais la page sera complète quand elle s'affichera"
+#: ../../Zotlabs/Lib/ThreadItem.php:158
+msgid "I might attend"
+msgstr "Je participerai peut-être"
-#: ../../Zotlabs/Module/Settings.php:849
-msgid "Enable user zoom on mobile devices"
-msgstr "Permettre à l'utilisateur d'un mobile d'agrandir le contenu"
+#: ../../Zotlabs/Lib/ThreadItem.php:168
+msgid "I agree"
+msgstr "Je suis d'accord"
-#: ../../Zotlabs/Module/Settings.php:850
-msgid "Update browser every xx seconds"
-msgstr "Mettre à jour le navigateur toutes les xx secondes"
+#: ../../Zotlabs/Lib/ThreadItem.php:168
+msgid "I disagree"
+msgstr "Je ne suis pas d'accord"
-#: ../../Zotlabs/Module/Settings.php:850
-msgid "Minimum of 10 seconds, no maximum"
-msgstr "Minimum 10 secondes, pas de maximum"
+#: ../../Zotlabs/Lib/ThreadItem.php:168
+msgid "I abstain"
+msgstr "Je m'abstiens"
-#: ../../Zotlabs/Module/Settings.php:851
-msgid "Maximum number of conversations to load at any time:"
-msgstr "Nombre maximal de conversations pouvant être chargées en même temps&nbsp;:"
+#: ../../Zotlabs/Lib/ThreadItem.php:224
+msgid "Add Star"
+msgstr "Mettre de côté (étoile)"
-#: ../../Zotlabs/Module/Settings.php:851
-msgid "Maximum of 100 items"
-msgstr "100 éléments au maximum"
+#: ../../Zotlabs/Lib/ThreadItem.php:225
+msgid "Remove Star"
+msgstr "Ne plus mettre de côté"
-#: ../../Zotlabs/Module/Settings.php:852
-msgid "Show emoticons (smilies) as images"
-msgstr "Remplacer les émoticônes (smileys) par des images"
+#: ../../Zotlabs/Lib/ThreadItem.php:226
+msgid "Toggle Star Status"
+msgstr "(Dés)activer l'étoile"
-#: ../../Zotlabs/Module/Settings.php:853
-msgid "Link post titles to source"
-msgstr "Lier les titres des publications à leur source"
+#: ../../Zotlabs/Lib/ThreadItem.php:230
+msgid "starred"
+msgstr "mis de côté"
-#: ../../Zotlabs/Module/Settings.php:854
-msgid "System Page Layout Editor - (advanced)"
-msgstr "Editeur de mise en page des pages systèmes - (avancé)"
+#: ../../Zotlabs/Lib/ThreadItem.php:240 ../../include/conversation.php:668
+msgid "Message signature validated"
+msgstr "Signature du message validée"
-#: ../../Zotlabs/Module/Settings.php:857
-msgid "Use blog/list mode on channel page"
-msgstr "Utiliser le mode blog/liste sur la page du canal"
+#: ../../Zotlabs/Lib/ThreadItem.php:241 ../../include/conversation.php:669
+msgid "Message signature incorrect"
+msgstr "Signature du message incorrecte"
-#: ../../Zotlabs/Module/Settings.php:857 ../../Zotlabs/Module/Settings.php:858
-msgid "(comments displayed separately)"
-msgstr "(commentaires affichés séparément)"
+#: ../../Zotlabs/Lib/ThreadItem.php:249
+msgid "Add Tag"
+msgstr "Ajouter une étiquette"
-#: ../../Zotlabs/Module/Settings.php:858
-msgid "Use blog/list mode on grid page"
-msgstr "Utiliser le mode blog/liste sur la page du réseau"
+#: ../../Zotlabs/Lib/ThreadItem.php:269 ../../include/taxonomy.php:316
+msgid "like"
+msgstr "aiment"
-#: ../../Zotlabs/Module/Settings.php:859
-msgid "Channel page max height of content (in pixels)"
-msgstr "Hauteur maximale du contenu pour la page du canal (en pixels)"
+#: ../../Zotlabs/Lib/ThreadItem.php:270 ../../include/taxonomy.php:317
+msgid "dislike"
+msgstr "n'aiment pas"
-#: ../../Zotlabs/Module/Settings.php:859 ../../Zotlabs/Module/Settings.php:860
-msgid "click to expand content exceeding this height"
-msgstr "cliquer pour dérouler le contenu dépassant cette limite"
+#: ../../Zotlabs/Lib/ThreadItem.php:274
+msgid "Share This"
+msgstr "Partager"
-#: ../../Zotlabs/Module/Settings.php:860
-msgid "Grid page max height of content (in pixels)"
-msgstr "Hauteur maximale du contenu sur la page du réseau (en pixels)"
+#: ../../Zotlabs/Lib/ThreadItem.php:274
+msgid "share"
+msgstr "partager"
-#: ../../Zotlabs/Module/Settings.php:894
-msgid "Nobody except yourself"
-msgstr "Personne sauf vous"
+#: ../../Zotlabs/Lib/ThreadItem.php:283
+msgid "Delivery Report"
+msgstr "Rapport de distribution"
-#: ../../Zotlabs/Module/Settings.php:895
-msgid "Only those you specifically allow"
-msgstr "Seulement ceux que vous autorisez spécifiquement"
+#: ../../Zotlabs/Lib/ThreadItem.php:301
+#, php-format
+msgid "%d comment"
+msgid_plural "%d comments"
+msgstr[0] "%d commentaire"
+msgstr[1] "%d commentaires"
-#: ../../Zotlabs/Module/Settings.php:896
-msgid "Approved connections"
-msgstr "Contacts approuvés"
+#: ../../Zotlabs/Lib/ThreadItem.php:330 ../../Zotlabs/Lib/ThreadItem.php:331
+#, php-format
+msgid "View %s's profile - %s"
+msgstr "Voir le profil de %s - %s"
-#: ../../Zotlabs/Module/Settings.php:897
-msgid "Any connections"
-msgstr "Tous les contacts"
+#: ../../Zotlabs/Lib/ThreadItem.php:334
+msgid "to"
+msgstr "à"
-#: ../../Zotlabs/Module/Settings.php:898
-msgid "Anybody on this website"
-msgstr "Tous les utilisateurs du hub"
+#: ../../Zotlabs/Lib/ThreadItem.php:335
+msgid "via"
+msgstr "via"
-#: ../../Zotlabs/Module/Settings.php:899
-msgid "Anybody in this network"
-msgstr "Tous les utilisateurs sur ce réseau"
+#: ../../Zotlabs/Lib/ThreadItem.php:336
+msgid "Wall-to-Wall"
+msgstr "Mur-à-mur"
-#: ../../Zotlabs/Module/Settings.php:900
-msgid "Anybody authenticated"
-msgstr "Tous les utilisateurs authentifiés"
+#: ../../Zotlabs/Lib/ThreadItem.php:337
+msgid "via Wall-To-Wall:"
+msgstr "par Mur-à-mur&nbsp;:"
-#: ../../Zotlabs/Module/Settings.php:901
-msgid "Anybody on the internet"
-msgstr "Tous les utilisateurs d'Internet"
+#: ../../Zotlabs/Lib/ThreadItem.php:350 ../../include/conversation.php:718
+#, php-format
+msgid "from %s"
+msgstr "de %s"
-#: ../../Zotlabs/Module/Settings.php:976
-msgid "Publish your default profile in the network directory"
-msgstr "Publier votre profil par défaut dans l'annuaire du réseau"
+#: ../../Zotlabs/Lib/ThreadItem.php:353 ../../include/conversation.php:721
+#, php-format
+msgid "last edited: %s"
+msgstr "dernière modification&nbsp;: %s"
-#: ../../Zotlabs/Module/Settings.php:981
-msgid "Allow us to suggest you as a potential friend to new members?"
-msgstr "Nous autoriser à vous suggérer comme ami(e) potentiel(le) aux nouveaux membres?"
+#: ../../Zotlabs/Lib/ThreadItem.php:354 ../../include/conversation.php:722
+#, php-format
+msgid "Expires: %s"
+msgstr "Expire&nbsp;: %s"
-#: ../../Zotlabs/Module/Settings.php:990
-msgid "Your channel address is"
-msgstr "L'adresse de votre canal est"
+#: ../../Zotlabs/Lib/ThreadItem.php:360
+msgid "Attend"
+msgstr "En attente"
-#: ../../Zotlabs/Module/Settings.php:1032
-msgid "Channel Settings"
-msgstr "Paramètres du canal"
+#: ../../Zotlabs/Lib/ThreadItem.php:361
+msgid "Attendance Options"
+msgstr "Options d'attente"
-#: ../../Zotlabs/Module/Settings.php:1039
-msgid "Basic Settings"
-msgstr "Paramètres standard"
+#: ../../Zotlabs/Lib/ThreadItem.php:362
+msgid "Vote"
+msgstr "Vote"
-#: ../../Zotlabs/Module/Settings.php:1040 ../../include/channel.php:1140
-msgid "Full Name:"
-msgstr "Nom complet&nbsp;:"
+#: ../../Zotlabs/Lib/ThreadItem.php:363
+msgid "Voting Options"
+msgstr "Options de vote"
-#: ../../Zotlabs/Module/Settings.php:1042
-msgid "Your Timezone:"
-msgstr "Votre fureau horaire&nbsp;:"
+#: ../../Zotlabs/Lib/ThreadItem.php:384
+#: ../../addon/bookmarker/bookmarker.php:38
+msgid "Save Bookmarks"
+msgstr "Enregistrer les favoris"
-#: ../../Zotlabs/Module/Settings.php:1043
-msgid "Default Post Location:"
-msgstr "Emplacement de publication par défaut&nbsp;:"
+#: ../../Zotlabs/Lib/ThreadItem.php:385
+msgid "Add to Calendar"
+msgstr "Ajouter au Calendrier"
-#: ../../Zotlabs/Module/Settings.php:1043
-msgid "Geographical location to display on your posts"
-msgstr "Emplacement géographique à afficher sur vos publications"
+#: ../../Zotlabs/Lib/ThreadItem.php:394
+msgid "Mark all seen"
+msgstr "Tout marquer comme vu"
-#: ../../Zotlabs/Module/Settings.php:1044
-msgid "Use Browser Location:"
-msgstr "Utiliser la géolocalisation du navigateur&nbsp;:"
+#: ../../Zotlabs/Lib/ThreadItem.php:443 ../../include/js_strings.php:7
+#, php-format
+msgid "%s show all"
+msgstr "%s montre tout"
-#: ../../Zotlabs/Module/Settings.php:1046
-msgid "Adult Content"
-msgstr "Contenu \"adulte\""
+#: ../../Zotlabs/Lib/ThreadItem.php:733 ../../include/conversation.php:1318
+msgid "Bold"
+msgstr "Gras"
-#: ../../Zotlabs/Module/Settings.php:1046
-msgid ""
-"This channel frequently or regularly publishes adult content. (Please tag "
-"any adult material and/or nudity with #NSFW)"
-msgstr "Ce canal publie plus ou moins fréquemment du contenu pour adultes. (Merci d'indiquer tout contenu pour adulte ou potentiellement choquant avec l'étiquette <em>#NSFW</em> - Not Safe For Work)"
+#: ../../Zotlabs/Lib/ThreadItem.php:734 ../../include/conversation.php:1319
+msgid "Italic"
+msgstr "Italique"
-#: ../../Zotlabs/Module/Settings.php:1048
-msgid "Security and Privacy Settings"
-msgstr "Paramètres de sécurité et de confidentialité"
+#: ../../Zotlabs/Lib/ThreadItem.php:735 ../../include/conversation.php:1320
+msgid "Underline"
+msgstr "Souligné"
-#: ../../Zotlabs/Module/Settings.php:1051
-msgid "Your permissions are already configured. Click to view/adjust"
-msgstr "Vous permissions sont déjà paramétrées. Cliquer pour voir/ajuster"
+#: ../../Zotlabs/Lib/ThreadItem.php:736 ../../include/conversation.php:1321
+msgid "Quote"
+msgstr "Citation"
-#: ../../Zotlabs/Module/Settings.php:1053
-msgid "Hide my online presence"
-msgstr "Cacher ma présence en ligne"
+#: ../../Zotlabs/Lib/ThreadItem.php:737 ../../include/conversation.php:1322
+msgid "Code"
+msgstr "Code"
-#: ../../Zotlabs/Module/Settings.php:1053
-msgid "Prevents displaying in your profile that you are online"
-msgstr "Cacher votre statut (en ligne/hors ligne) sur votre profil"
+#: ../../Zotlabs/Lib/ThreadItem.php:738
+msgid "Image"
+msgstr "Image"
-#: ../../Zotlabs/Module/Settings.php:1055
-msgid "Simple Privacy Settings:"
-msgstr "Paramètres de confidentialité simplifiés&nbsp;:"
+#: ../../Zotlabs/Lib/ThreadItem.php:739
+msgid "Insert Link"
+msgstr "Insérer un lien"
-#: ../../Zotlabs/Module/Settings.php:1056
-msgid ""
-"Very Public - <em>extremely permissive (should be used with caution)</em>"
-msgstr "Très public - <em>extrèmement permissif (à n'utiliser qu'en connaissance de cause)</em>"
+#: ../../Zotlabs/Lib/ThreadItem.php:740
+msgid "Video"
+msgstr "Vidéo"
-#: ../../Zotlabs/Module/Settings.php:1057
+#: ../../Zotlabs/Zot/Auth.php:138
msgid ""
-"Typical - <em>default public, privacy when desired (similar to social "
-"network permissions but with improved privacy)</em>"
-msgstr "Classique - <em>public par défaut, privé en cas de besoin (comparable aux permissions type réseau social, avec une confidentialité améliorée)</em>"
+"Remote authentication blocked. You are logged into this site locally. Please"
+" logout and retry."
+msgstr "Authentification distante bloquée. Vous êtes connecté(e) sur ce site localement. Merci de vous déconnecter et réessayer."
-#: ../../Zotlabs/Module/Settings.php:1058
-msgid "Private - <em>default private, never open or public</em>"
-msgstr "Privé - <em>privé par défaut, jamais ouvert ni public</em>"
+#: ../../Zotlabs/Zot/Auth.php:250 ../../addon/openid/Mod_Openid.php:76
+#: ../../addon/openid/Mod_Openid.php:178
+#, php-format
+msgid "Welcome %s. Remote authentication successful."
+msgstr "Bienvenue %s. L'authentification distante a fonctionné."
-#: ../../Zotlabs/Module/Settings.php:1059
-msgid "Blocked - <em>default blocked to/from everybody</em>"
-msgstr "Bloqué - <em>par défaut, bloqué de/vers tout le monde</em>"
+#: ../../Zotlabs/Storage/Browser.php:106 ../../Zotlabs/Storage/Browser.php:237
+msgid "parent"
+msgstr "retour"
-#: ../../Zotlabs/Module/Settings.php:1061
-msgid "Allow others to tag your posts"
-msgstr "Autoriser les autres à \"étiqueter\" vos publications"
+#: ../../Zotlabs/Storage/Browser.php:130 ../../include/text.php:2687
+msgid "Collection"
+msgstr "Groupe de contacts"
-#: ../../Zotlabs/Module/Settings.php:1061
-msgid ""
-"Often used by the community to retro-actively flag inappropriate content"
-msgstr "Souvent utilisé par la communauté pour identifier un contenu inapproprié a posteriori "
+#: ../../Zotlabs/Storage/Browser.php:133
+msgid "Principal"
+msgstr "Principal"
-#: ../../Zotlabs/Module/Settings.php:1063
-msgid "Advanced Privacy Settings"
-msgstr "Paramètres de confidentialité avancés"
+#: ../../Zotlabs/Storage/Browser.php:136
+msgid "Addressbook"
+msgstr "Carnet d'adresse"
-#: ../../Zotlabs/Module/Settings.php:1065
-msgid "Expire other channel content after this many days"
-msgstr "Faire expirer le contenu des autres canaux après n jours"
+#: ../../Zotlabs/Storage/Browser.php:139
+msgid "Calendar"
+msgstr "Calendrier"
-#: ../../Zotlabs/Module/Settings.php:1065
-msgid "0 or blank to use the website limit."
-msgstr ""
+#: ../../Zotlabs/Storage/Browser.php:142
+msgid "Schedule Inbox"
+msgstr "Calendrier - Messages entrants"
-#: ../../Zotlabs/Module/Settings.php:1065
-#, php-format
-msgid "This website expires after %d days."
-msgstr ""
+#: ../../Zotlabs/Storage/Browser.php:145
+msgid "Schedule Outbox"
+msgstr "Calendrier - Messages sortants"
-#: ../../Zotlabs/Module/Settings.php:1065
-msgid "This website does not expire imported content."
-msgstr ""
+#: ../../Zotlabs/Storage/Browser.php:225
+msgid "Total"
+msgstr "Total"
-#: ../../Zotlabs/Module/Settings.php:1065
-msgid "The website limit takes precedence if lower than your limit."
-msgstr ""
+#: ../../Zotlabs/Storage/Browser.php:227
+msgid "Shared"
+msgstr "Partagé"
-#: ../../Zotlabs/Module/Settings.php:1066
-msgid "Maximum Friend Requests/Day:"
-msgstr "Nombre maximum de demandes de contact par jour&nbsp;:"
+#: ../../Zotlabs/Storage/Browser.php:301
+#, php-format
+msgid "You are using %1$s of your available file storage."
+msgstr "Vous utilisez %1$s de votre espace de stockage."
-#: ../../Zotlabs/Module/Settings.php:1066
-msgid "May reduce spam activity"
-msgstr "Contribue à réduire l'impact des indésirables"
+#: ../../Zotlabs/Storage/Browser.php:306
+#, php-format
+msgid "You are using %1$s of %2$s available file storage. (%3$s&#37;)"
+msgstr "Vous utilisez %1$s sur %2$s d'espace disponible. (%3$s&#37;)"
-#: ../../Zotlabs/Module/Settings.php:1067
-msgid "Default Post and Publish Permissions"
-msgstr ""
+#: ../../Zotlabs/Storage/Browser.php:317
+msgid "WARNING:"
+msgstr "AVERTISSEMENT&nbsp;:"
-#: ../../Zotlabs/Module/Settings.php:1069
-msgid "Use my default audience setting for the type of object published"
+#: ../../Zotlabs/Storage/Browser.php:327
+msgid ""
+"Please use DAV to upload large (video, audio) files.<br>See <a class=\"zrl\""
+" href=\"help/member/member_guide#Cloud_Desktop_Clients\">Cloud Desktop "
+"Clients</a>"
msgstr ""
-#: ../../Zotlabs/Module/Settings.php:1072
-msgid "Channel permissions category:"
-msgstr "Catégorie de permissions du canal&nbsp;:"
-
-#: ../../Zotlabs/Module/Settings.php:1078
-msgid "Maximum private messages per day from unknown people:"
-msgstr "Nombre maximum de messages privés émanant d'inconnus, par jour&nbsp;:"
+#: ../../Zotlabs/Storage/Browser.php:331
+msgid "Create new folder"
+msgstr "Nouveau dossier"
-#: ../../Zotlabs/Module/Settings.php:1078
-msgid "Useful to reduce spamming"
-msgstr "Utile pour réduire les indésirables"
+#: ../../Zotlabs/Storage/Browser.php:333
+msgid "Upload file"
+msgstr "Téléverser un fichier"
-#: ../../Zotlabs/Module/Settings.php:1081
-msgid "Notification Settings"
-msgstr "Paramètres de notification"
+#: ../../Zotlabs/Storage/Browser.php:347
+msgid "Drop files here to immediately upload"
+msgstr "Mettez un fichier ici pour le télécharger immédiatement"
-#: ../../Zotlabs/Module/Settings.php:1082
-msgid "By default post a status message when:"
-msgstr "Par défaut, publier un statut quand&nbsp;:"
+#: ../../Zotlabs/Widget/Forums.php:85
+msgid "Forums"
+msgstr "Forums"
-#: ../../Zotlabs/Module/Settings.php:1083
-msgid "accepting a friend request"
-msgstr "vous acceptez une demande de contact"
+#: ../../Zotlabs/Widget/Appcategories.php:39
+#: ../../Zotlabs/Widget/Tagcloud.php:25 ../../include/contact_widgets.php:91
+#: ../../include/taxonomy.php:188 ../../include/taxonomy.php:270
+msgid "Categories"
+msgstr "Catégories"
-#: ../../Zotlabs/Module/Settings.php:1084
-msgid "joining a forum/community"
-msgstr "vous rejoignez un forum ou une communauté"
+#: ../../Zotlabs/Widget/Appcategories.php:42 ../../Zotlabs/Widget/Filer.php:31
+#: ../../include/contact_widgets.php:56 ../../include/contact_widgets.php:94
+msgid "Everything"
+msgstr "Tout"
-#: ../../Zotlabs/Module/Settings.php:1085
-msgid "making an <em>interesting</em> profile change"
-msgstr "vous faîtes une modification <em>intéressante</em> de votre profil"
+#: ../../Zotlabs/Widget/Eventstools.php:13
+msgid "Events Tools"
+msgstr "Outils Evènements"
-#: ../../Zotlabs/Module/Settings.php:1086
-msgid "Send a notification email when:"
-msgstr "Envoyer un courriel de notification quand&nbsp;:"
+#: ../../Zotlabs/Widget/Eventstools.php:14
+msgid "Export Calendar"
+msgstr "Exporter le calendrier"
-#: ../../Zotlabs/Module/Settings.php:1087
-msgid "You receive a connection request"
-msgstr "Vous recevez une demande de contact"
+#: ../../Zotlabs/Widget/Eventstools.php:15
+msgid "Import Calendar"
+msgstr "Importer un calendrier"
-#: ../../Zotlabs/Module/Settings.php:1088
-msgid "Your connections are confirmed"
-msgstr "Vos contacts sont confirmés"
+#: ../../Zotlabs/Widget/Suggestedchats.php:32
+msgid "Suggested Chatrooms"
+msgstr "Salons suggérés"
-#: ../../Zotlabs/Module/Settings.php:1089
-msgid "Someone writes on your profile wall"
-msgstr "Quelqu'un a écrit sur votre mur"
+#: ../../Zotlabs/Widget/Mailmenu.php:13
+msgid "Private Mail Menu"
+msgstr "Menu des messages privés"
-#: ../../Zotlabs/Module/Settings.php:1090
-msgid "Someone writes a followup comment"
-msgstr "Quelqu'un a commenté vos publications"
+#: ../../Zotlabs/Widget/Mailmenu.php:15
+msgid "Combined View"
+msgstr "Vue combinée"
-#: ../../Zotlabs/Module/Settings.php:1091
-msgid "You receive a private message"
-msgstr "Vous recevez un message privé"
+#: ../../Zotlabs/Widget/Mailmenu.php:20 ../../include/nav.php:191
+msgid "Inbox"
+msgstr "Boîte de réception"
-#: ../../Zotlabs/Module/Settings.php:1092
-msgid "You receive a friend suggestion"
-msgstr "Vous recevez une suggestion d'amitié/contact"
+#: ../../Zotlabs/Widget/Mailmenu.php:25 ../../include/nav.php:192
+msgid "Outbox"
+msgstr "Boîte d'envoi"
-#: ../../Zotlabs/Module/Settings.php:1093
-msgid "You are tagged in a post"
-msgstr "Vous êtes étiqueté dans une publication"
+#: ../../Zotlabs/Widget/Mailmenu.php:30 ../../include/nav.php:193
+msgid "New Message"
+msgstr "Nouveau message"
-#: ../../Zotlabs/Module/Settings.php:1094
-msgid "You are poked/prodded/etc. in a post"
-msgstr "Vous êtes tapoté/encouragé/etc. dans une publication"
+#: ../../Zotlabs/Widget/Chatroom_list.php:16
+#: ../../include/conversation.php:1807 ../../include/conversation.php:1810
+msgid "Chatrooms"
+msgstr "Salons de clavardage"
-#: ../../Zotlabs/Module/Settings.php:1097
-msgid "Show visual notifications including:"
-msgstr "Afficher des notifications visuelles y compris&nbsp;:"
+#: ../../Zotlabs/Widget/Chatroom_list.php:20
+msgid "Overview"
+msgstr "Aperçu"
-#: ../../Zotlabs/Module/Settings.php:1099
-msgid "Unseen grid activity"
-msgstr "Activité du réseau pas encore consultée"
+#: ../../Zotlabs/Widget/Rating.php:51
+msgid "Rating Tools"
+msgstr "Outils d'évaluation"
-#: ../../Zotlabs/Module/Settings.php:1100
-msgid "Unseen channel activity"
-msgstr "Activité non vue sur le canal"
+#: ../../Zotlabs/Widget/Rating.php:55 ../../Zotlabs/Widget/Rating.php:57
+msgid "Rate Me"
+msgstr "M'évaluer"
-#: ../../Zotlabs/Module/Settings.php:1101
-msgid "Unseen private messages"
-msgstr "Messages privés non lus"
+#: ../../Zotlabs/Widget/Rating.php:60
+msgid "View Ratings"
+msgstr "Voir mes évaluations"
-#: ../../Zotlabs/Module/Settings.php:1101
-#: ../../Zotlabs/Module/Settings.php:1106
-#: ../../Zotlabs/Module/Settings.php:1107
-#: ../../Zotlabs/Module/Settings.php:1108
-msgid "Recommended"
-msgstr "Recommandé"
+#: ../../Zotlabs/Widget/Activity.php:50
+msgctxt "widget"
+msgid "Activity"
+msgstr ""
-#: ../../Zotlabs/Module/Settings.php:1102
-msgid "Upcoming events"
-msgstr "Événements à venir"
+#: ../../Zotlabs/Widget/Follow.php:22
+#, php-format
+msgid "You have %1$.0f of %2$.0f allowed connections."
+msgstr "Vous avez %1$.0f sur %2$.0f contacts autorisés."
-#: ../../Zotlabs/Module/Settings.php:1103
-msgid "Events today"
-msgstr "Événements aujourd'hui"
+#: ../../Zotlabs/Widget/Follow.php:29
+msgid "Add New Connection"
+msgstr "Ajouter un nouveau contact"
-#: ../../Zotlabs/Module/Settings.php:1104
-msgid "Upcoming birthdays"
-msgstr "Anniversaires à venir"
+#: ../../Zotlabs/Widget/Follow.php:30
+msgid "Enter channel address"
+msgstr "Saisissez l'adresse du canal"
-#: ../../Zotlabs/Module/Settings.php:1104
-msgid "Not available in all themes"
-msgstr "Pas disponible dans tous les thèmes"
+#: ../../Zotlabs/Widget/Follow.php:31
+msgid "Examples: bob@example.com, https://example.com/barbara"
+msgstr "Exemples&nbsp;: pierre@exemple.com, https://exemple.com/sophie"
-#: ../../Zotlabs/Module/Settings.php:1105
-msgid "System (personal) notifications"
-msgstr "Notifications système (personnelles)"
+#: ../../Zotlabs/Widget/Wiki_list.php:15 ../../addon/gitwiki/gitwiki.php:95
+msgid "Wiki List"
+msgstr "Liste de wikis"
-#: ../../Zotlabs/Module/Settings.php:1106
-msgid "System info messages"
-msgstr "Messages d'info système"
+#: ../../Zotlabs/Widget/Archive.php:43
+msgid "Archives"
+msgstr "Archives"
-#: ../../Zotlabs/Module/Settings.php:1107
-msgid "System critical alerts"
-msgstr "Alertes critiques système"
+#: ../../Zotlabs/Widget/Conversations.php:17
+#: ../../Zotlabs/Widget/Conversations.php:29
+msgid "Conversations"
+msgstr "Conversations"
-#: ../../Zotlabs/Module/Settings.php:1108
-msgid "New connections"
-msgstr "Nouveaux contacts"
+#: ../../Zotlabs/Widget/Conversations.php:21
+msgid "Received Messages"
+msgstr "Messages reçus"
-#: ../../Zotlabs/Module/Settings.php:1109
-msgid "System Registrations"
-msgstr "Inscriptions système"
+#: ../../Zotlabs/Widget/Conversations.php:25
+msgid "Sent Messages"
+msgstr "Messages envoyés"
-#: ../../Zotlabs/Module/Settings.php:1110
-msgid ""
-"Also show new wall posts, private messages and connections under Notices"
-msgstr "Afficher également les nouvelles publications sur le mur, les messages privés et les contacts dans Notifications"
+#: ../../Zotlabs/Widget/Conversations.php:39
+msgid "No messages."
+msgstr "Pas de message."
-#: ../../Zotlabs/Module/Settings.php:1112
-msgid "Notify me of events this many days in advance"
-msgstr "Me prévenir d’événements à venir tant de jours en avance"
+#: ../../Zotlabs/Widget/Conversations.php:57
+msgid "Delete conversation"
+msgstr "Supprimer la conversation"
-#: ../../Zotlabs/Module/Settings.php:1112
-msgid "Must be greater than 0"
-msgstr "Doit être supérieur à 0"
+#: ../../Zotlabs/Widget/Chatroom_members.php:11
+msgid "Chat Members"
+msgstr "Membres du salon de discussion"
-#: ../../Zotlabs/Module/Settings.php:1114
-msgid "Advanced Account/Page Type Settings"
-msgstr "Paramètres avancés de compte/type de page"
+#: ../../Zotlabs/Widget/Photo.php:48 ../../Zotlabs/Widget/Photo_rand.php:58
+msgid "photo/image"
+msgstr "photo/image"
-#: ../../Zotlabs/Module/Settings.php:1115
-msgid "Change the behaviour of this account for special situations"
-msgstr "Modifie le comportement de ce compte pour des situations particulières"
+#: ../../Zotlabs/Widget/Savedsearch.php:75
+msgid "Remove term"
+msgstr "Retirer le terme"
-#: ../../Zotlabs/Module/Settings.php:1118
-msgid ""
-"Please enable expert mode (in <a href=\"settings/features\">Settings > "
-"Additional features</a>) to adjust!"
-msgstr "Mode expert requis (<a href=\"settings/features\">Paramètres > Fonctions supplémentaires</a>) pour ajuster&nbsp;!"
+#: ../../Zotlabs/Widget/Savedsearch.php:83 ../../include/features.php:301
+msgid "Saved Searches"
+msgstr "Recherches sauvegardées"
-#: ../../Zotlabs/Module/Settings.php:1119
-msgid "Miscellaneous Settings"
-msgstr "Paramètres divers"
+#: ../../Zotlabs/Widget/Savedsearch.php:84 ../../include/group.php:336
+msgid "add"
+msgstr "ajouter"
-#: ../../Zotlabs/Module/Settings.php:1120
-msgid "Default photo upload folder"
-msgstr "Répertoire par défaut pour les photos téléversées"
+#: ../../Zotlabs/Widget/Notes.php:16
+msgid "Notes"
+msgstr "Notes"
-#: ../../Zotlabs/Module/Settings.php:1120
-#: ../../Zotlabs/Module/Settings.php:1121
-msgid "%Y - current year, %m - current month"
-msgstr "%Y - année en cours, %m - mois en cours"
+#: ../../Zotlabs/Widget/Wiki_pages.php:54 ../../addon/gitwiki/gitwiki.php:76
+msgid "Wiki Pages"
+msgstr "Pages wiki"
-#: ../../Zotlabs/Module/Settings.php:1121
-msgid "Default file upload folder"
-msgstr "Répertoire par défaut pour les fichiers téléversés"
+#: ../../Zotlabs/Widget/Wiki_pages.php:60 ../../addon/gitwiki/gitwiki.php:81
+msgid "Add new page"
+msgstr "Ajouter une nouvelle page"
-#: ../../Zotlabs/Module/Settings.php:1123
-msgid "Personal menu to display in your channel pages"
-msgstr "Menu personnel à afficher sur les pages de votre canal"
+#: ../../Zotlabs/Widget/Wiki_pages.php:61 ../../addon/gitwiki/gitwiki.php:82
+msgid "Page name"
+msgstr "Nom de la page"
-#: ../../Zotlabs/Module/Settings.php:1125
-msgid "Remove this channel."
-msgstr "Supprimer ce canal"
+#: ../../Zotlabs/Widget/Affinity.php:49
+msgid "Refresh"
+msgstr "Actualiser"
-#: ../../Zotlabs/Module/Settings.php:1126
-msgid "Firefox Share $Projectname provider"
-msgstr "Connecteur $Projectname pour Firefox Share"
+#: ../../Zotlabs/Widget/Tasklist.php:23
+msgid "Tasks"
+msgstr "Tâches"
-#: ../../Zotlabs/Module/Settings.php:1127
-msgid "Start calendar week on monday"
-msgstr "Commencer la semaine du calendrier le lundi"
+#: ../../Zotlabs/Widget/Suggestions.php:51
+msgid "Suggestions"
+msgstr "Suggestions"
-#: ../../Zotlabs/Module/Setup.php:179
-msgid "$Projectname Server - Setup"
-msgstr "Serveur $Projectname - configuration"
+#: ../../Zotlabs/Widget/Suggestions.php:52
+msgid "See more..."
+msgstr "Voir plus..."
-#: ../../Zotlabs/Module/Setup.php:183
-msgid "Could not connect to database."
-msgstr "Impossible de se connecter à la base de données."
+#: ../../Zotlabs/Widget/Filer.php:28 ../../include/contact_widgets.php:53
+#: ../../include/features.php:390
+msgid "Saved Folders"
+msgstr "Dossiers sauvegardés"
-#: ../../Zotlabs/Module/Setup.php:187
-msgid ""
-"Could not connect to specified site URL. Possible SSL certificate or DNS "
-"issue."
-msgstr "Impossible de se connecter à l'URL indiquée. Problème potentiel de certificat SSL/TLS ou de DNS."
+#: ../../Zotlabs/Widget/Cover_photo.php:54
+msgid "Click to show more"
+msgstr "Cliquer pour voir plus"
-#: ../../Zotlabs/Module/Setup.php:194
-msgid "Could not create table."
-msgstr "Impossible de créer la table."
+#: ../../Zotlabs/Widget/Admin.php:23 ../../Zotlabs/Widget/Admin.php:60
+msgid "Member registrations waiting for confirmation"
+msgstr "Inscriptions en attente d'approbation"
-#: ../../Zotlabs/Module/Setup.php:199
-msgid "Your site database has been installed."
-msgstr "La base de données de votre site a été installée."
+#: ../../Zotlabs/Widget/Admin.php:29
+msgid "Inspect queue"
+msgstr "Analyser la file d'attente"
-#: ../../Zotlabs/Module/Setup.php:203
-msgid ""
-"You may need to import the file \"install/schema_xxx.sql\" manually using a "
-"database client."
-msgstr "Vous pourriez avoir besoin d'importer le fichier \"install/schema_xxx.sql\" manuellement via un client de base de données (ex: phpmyadmin)."
+#: ../../Zotlabs/Widget/Admin.php:31
+msgid "DB updates"
+msgstr "Mises à jour BDD"
-#: ../../Zotlabs/Module/Setup.php:204 ../../Zotlabs/Module/Setup.php:266
-#: ../../Zotlabs/Module/Setup.php:721
-msgid "Please see the file \"install/INSTALL.txt\"."
-msgstr "Merci de consulter le fichier \"install/INSTALL.txt\"."
+#: ../../Zotlabs/Widget/Admin.php:55 ../../include/nav.php:211
+msgid "Admin"
+msgstr "Administrateur"
-#: ../../Zotlabs/Module/Setup.php:263
-msgid "System check"
-msgstr "Vérification du système"
+#: ../../Zotlabs/Widget/Admin.php:56
+msgid "Plugin Features"
+msgstr "Fonctionnalités des greffons"
-#: ../../Zotlabs/Module/Setup.php:268
-msgid "Check again"
-msgstr "Re-vérifier"
+#: ../../Zotlabs/Widget/Settings_menu.php:35
+msgid "Account settings"
+msgstr "Paramètres du compte"
-#: ../../Zotlabs/Module/Setup.php:290
-msgid "Database connection"
-msgstr "Connexion à la base de données"
+#: ../../Zotlabs/Widget/Settings_menu.php:41
+msgid "Channel settings"
+msgstr "Paramètres du canal"
-#: ../../Zotlabs/Module/Setup.php:291
-msgid ""
-"In order to install $Projectname we need to know how to connect to your "
-"database."
-msgstr "Pour installer $Projectname, nous avons besoin de savoir comment se connecter à votre base de données."
+#: ../../Zotlabs/Widget/Settings_menu.php:50
+msgid "Additional features"
+msgstr "Fonctionnalités supplémentaires"
-#: ../../Zotlabs/Module/Setup.php:292
-msgid ""
-"Please contact your hosting provider or site administrator if you have "
-"questions about these settings."
-msgstr "Merci de contacter votre prestataire d'hébergement ou votre administrateur de site si vous avez des questions à propos de ces paramètres."
+#: ../../Zotlabs/Widget/Settings_menu.php:57
+msgid "Feature/Addon settings"
+msgstr "Paramètres des extensions/greffons"
-#: ../../Zotlabs/Module/Setup.php:293
-msgid ""
-"The database you specify below should already exist. If it does not, please "
-"create it before continuing."
-msgstr "La base de données que vous allez spécifier doit exister. Si ce n'est pas déjà le cas, merci de la créer avant de continuer."
+#: ../../Zotlabs/Widget/Settings_menu.php:63
+msgid "Display settings"
+msgstr "Paramètres d'affichage"
-#: ../../Zotlabs/Module/Setup.php:297
-msgid "Database Server Name"
-msgstr "Nom du serveur de base de données"
+#: ../../Zotlabs/Widget/Settings_menu.php:70
+msgid "Manage locations"
+msgstr "Gérer les emplacements"
-#: ../../Zotlabs/Module/Setup.php:297
-msgid "Default is 127.0.0.1"
-msgstr "Par défaut 127.0.0.1"
+#: ../../Zotlabs/Widget/Settings_menu.php:77
+msgid "Export channel"
+msgstr "Exporter le canal"
-#: ../../Zotlabs/Module/Setup.php:298
-msgid "Database Port"
-msgstr "Port de la base de données"
+#: ../../Zotlabs/Widget/Settings_menu.php:83
+msgid "Connected apps"
+msgstr "Applications connectées"
-#: ../../Zotlabs/Module/Setup.php:298
-msgid "Communication port number - use 0 for default"
-msgstr "Numéro TCP du port - utilisez 0 pour la valeur par défaut"
+#: ../../Zotlabs/Widget/Settings_menu.php:98 ../../include/features.php:153
+msgid "Permission Groups"
+msgstr "Groupes d'autorisation"
-#: ../../Zotlabs/Module/Setup.php:299
-msgid "Database Login Name"
-msgstr "Identifiant de connexion à la Base de Données"
+#: ../../Zotlabs/Widget/Settings_menu.php:115
+msgid "Premium Channel Settings"
+msgstr "Paramètres de canal VIP"
-#: ../../Zotlabs/Module/Setup.php:300
-msgid "Database Login Password"
-msgstr "Mot de passe de connexion à la Base de Données"
+#: ../../Zotlabs/Widget/Bookmarkedchats.php:24
+msgid "Bookmarked Chatrooms"
+msgstr "Salons favoris"
-#: ../../Zotlabs/Module/Setup.php:301
-msgid "Database Name"
-msgstr "Nom de la Base de Données"
+#: ../../util/nconfig.php:34
+msgid "Source channel not found."
+msgstr "Source du canal introuvable."
-#: ../../Zotlabs/Module/Setup.php:302
-msgid "Database Type"
-msgstr "Type de base de données"
+#: ../../boot.php:1164 ../../addon/opensearch/opensearch.php:26
+#, php-format
+msgctxt "opensearch"
+msgid "Search %1$s (%2$s)"
+msgstr "Recherche %1$s (%2$s)"
-#: ../../Zotlabs/Module/Setup.php:304 ../../Zotlabs/Module/Setup.php:344
-msgid "Site administrator email address"
-msgstr "Adresse de courriel de l'administrateur du site"
+#: ../../boot.php:1164 ../../addon/opensearch/opensearch.php:28
+msgctxt "opensearch"
+msgid "$Projectname"
+msgstr "$Projectname"
-#: ../../Zotlabs/Module/Setup.php:304 ../../Zotlabs/Module/Setup.php:344
-msgid ""
-"Your account email address must match this in order to use the web admin "
-"panel."
-msgstr "Votre compte devra utiliser la même adresse de courriel pour pouvoir utiliser l'administration web."
+#: ../../boot.php:1611
+msgid "Create an account to access services and applications"
+msgstr "Créer un compte pour accéder aux services et applications"
-#: ../../Zotlabs/Module/Setup.php:305 ../../Zotlabs/Module/Setup.php:346
-msgid "Website URL"
-msgstr "URL du site web"
+#: ../../boot.php:1630 ../../include/nav.php:99 ../../include/nav.php:123
+msgid "Logout"
+msgstr "Déconnexion"
-#: ../../Zotlabs/Module/Setup.php:305 ../../Zotlabs/Module/Setup.php:346
-msgid "Please use SSL (https) URL if available."
-msgstr "Veuillez utiliser SSL/TLS (https) si disponible."
+#: ../../boot.php:1633
+msgid "Login/Email"
+msgstr "pseudo / email"
-#: ../../Zotlabs/Module/Setup.php:306 ../../Zotlabs/Module/Setup.php:349
-msgid "Please select a default timezone for your website"
-msgstr "Veuillez choisir un fuseau horaire par défaut pour votre site"
+#: ../../boot.php:1634
+msgid "Password"
+msgstr "Mot de passe"
-#: ../../Zotlabs/Module/Setup.php:333
-msgid "Site settings"
-msgstr "Paramètres du site"
+#: ../../boot.php:1635
+msgid "Remember me"
+msgstr "Se souvenir de moi"
-#: ../../Zotlabs/Module/Setup.php:347
-msgid "Enable $Projectname <strong>advanced</strong> features?"
-msgstr "Activer les fonctionnalités <strong>avancées</strong> de $Projectname&nbsp;?"
+#: ../../boot.php:1638
+msgid "Forgot your password?"
+msgstr "Mot de passe oublié&nbsp;?"
-#: ../../Zotlabs/Module/Setup.php:347
-msgid ""
-"Some advanced features, while useful - may be best suited for technically "
-"proficient audiences"
-msgstr "Certaines fonctionnalités avancées, bien qu'utiles, sont plus adaptées aux utilisateurs chevronnés."
+#: ../../boot.php:2176
+msgid "toggle mobile"
+msgstr "(dés)activer mobile"
-#: ../../Zotlabs/Module/Setup.php:388
-msgid "PHP version 5.5 or greater is required."
+#: ../../boot.php:2329
+#, php-format
+msgid "[$Projectname] Website SSL error for %s"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:389
-msgid "PHP version"
+#: ../../boot.php:2334
+msgid "Website SSL certificate is not valid. Please correct."
+msgstr "Le certificat SSL n'est pas valide. Corrigez le."
+
+#: ../../boot.php:2452
+#, php-format
+msgid "[$Projectname] Cron tasks not running on %s"
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:404
-msgid "Could not find a command line version of PHP in the web server PATH."
-msgstr "Impossible de trouver une version CLI de PHP dans le PATH du serveur web."
+#: ../../boot.php:2457
+msgid "Cron/Scheduled tasks not running."
+msgstr "Les taches planifiées ne tournent pas."
-#: ../../Zotlabs/Module/Setup.php:405
-msgid ""
-"If you don't have a command line version of PHP installed on server, you "
-"will not be able to run background polling via cron."
-msgstr "En l'absence de version CLI de PHP sur votre serveur, vous ne pourrez pas utiliser la synchronisation en arrière-plan via cron."
+#: ../../boot.php:2458 ../../include/datetime.php:286
+msgid "never"
+msgstr "jamais"
-#: ../../Zotlabs/Module/Setup.php:409
-msgid "PHP executable path"
-msgstr "Chemin vers l'éxecutable PHP"
+#: ../../view/theme/redbasic/php/config.php:9
+msgid "Focus (Hubzilla default)"
+msgstr "Focus (par défaut pour Hubzilla)"
-#: ../../Zotlabs/Module/Setup.php:409
-msgid ""
-"Enter full path to php executable. You can leave this blank to continue the "
-"installation."
-msgstr "Entrez le chemin complet vers l'exécutable php. Vous pouvez continuer l'installation sans."
+#: ../../view/theme/redbasic/php/config.php:88
+msgid "Theme settings"
+msgstr "Paramètres du thème"
-#: ../../Zotlabs/Module/Setup.php:414
-msgid "Command line PHP"
-msgstr "PHP en ligne de commande (CLI)"
+#: ../../view/theme/redbasic/php/config.php:89
+msgid "Narrow navbar"
+msgstr "Barre de navigation fine"
-#: ../../Zotlabs/Module/Setup.php:423
-msgid ""
-"The command line version of PHP on your system does not have "
-"\"register_argc_argv\" enabled."
-msgstr "La version CLI de PHP sur votre système n'a pas l'option \"register_argc_argv\" activée."
+#: ../../view/theme/redbasic/php/config.php:90
+msgid "Navigation bar background color"
+msgstr "Couleur de fond de la barre de navigation"
-#: ../../Zotlabs/Module/Setup.php:424
-msgid "This is required for message delivery to work."
-msgstr "Elle est nécessaire pour la distribution des messages."
+#: ../../view/theme/redbasic/php/config.php:91
+msgid "Navigation bar icon color "
+msgstr "Couleur des icônes de la barre de navigation"
-#: ../../Zotlabs/Module/Setup.php:427
-msgid "PHP register_argc_argv"
-msgstr "PHP register_argc_argv"
+#: ../../view/theme/redbasic/php/config.php:92
+msgid "Navigation bar active icon color "
+msgstr "Couleur de l'icône active de la barre de navigation"
-#: ../../Zotlabs/Module/Setup.php:445
-#, php-format
-msgid ""
-"Your max allowed total upload size is set to %s. Maximum size of one file to"
-" upload is set to %s. You are allowed to upload up to %d files at once."
-msgstr "Votre taille de téléversement maximale totale autorisée est fixée à %s. La taille maximale d'un seul fichier à téléverser est fixée à %s. Vous pouvez téléverser jusqu'à %d fichier(s) à la fois."
+#: ../../view/theme/redbasic/php/config.php:93
+msgid "Link color"
+msgstr ""
-#: ../../Zotlabs/Module/Setup.php:450
-msgid "You can adjust these settings in the servers php.ini."
-msgstr "Vous pouvez ajuster ces paramètres dans le php.ini du serveur."
+#: ../../view/theme/redbasic/php/config.php:94
+msgid "Set font-color for banner"
+msgstr "Définir la couleur du texte de la bannière"
-#: ../../Zotlabs/Module/Setup.php:452
-msgid "PHP upload limits"
-msgstr "Limites de téléversement de PHP"
+#: ../../view/theme/redbasic/php/config.php:95
+msgid "Set the background color"
+msgstr "Définir la couleur d'arrière-plan"
-#: ../../Zotlabs/Module/Setup.php:475
-msgid ""
-"Error: the \"openssl_pkey_new\" function on this system is not able to "
-"generate encryption keys"
-msgstr "Erreur&nbsp;: la fonction \"openssl_pkey_new\" de ce système n'est pas capable de générer des clefs de chiffrement"
+#: ../../view/theme/redbasic/php/config.php:96
+msgid "Set the background image"
+msgstr "Définir l'image d'arrière-plan"
-#: ../../Zotlabs/Module/Setup.php:476
-msgid ""
-"If running under Windows, please see "
-"\"http://www.php.net/manual/en/openssl.installation.php\"."
-msgstr "Si vous êtes sur un serveur Windows, merci de consulter \"http://www.php.net/manual/fr/openssl.installation.php\"."
+#: ../../view/theme/redbasic/php/config.php:97
+msgid "Set the background color of items"
+msgstr "Définir la couleur de fond des contributions"
-#: ../../Zotlabs/Module/Setup.php:479
-msgid "Generate encryption keys"
-msgstr "Générer les clefs de chiffrement"
+#: ../../view/theme/redbasic/php/config.php:98
+msgid "Set the background color of comments"
+msgstr "Couleur de fond des commentaires"
-#: ../../Zotlabs/Module/Setup.php:491
-msgid "libCurl PHP module"
-msgstr "module PHP libCurl"
+#: ../../view/theme/redbasic/php/config.php:99
+msgid "Set font-size for the entire application"
+msgstr "Définir la taille de police pour l'application entière"
-#: ../../Zotlabs/Module/Setup.php:492
-msgid "GD graphics PHP module"
-msgstr "module PHP GD graphics"
+#: ../../view/theme/redbasic/php/config.php:99
+msgid "Examples: 87.5%, 14px"
+msgstr ""
-#: ../../Zotlabs/Module/Setup.php:493
-msgid "OpenSSL PHP module"
-msgstr "module PHP OpenSSL"
+#: ../../view/theme/redbasic/php/config.php:100
+msgid "Set font-color for posts and comments"
+msgstr "Définir la couleur de police pour les contributions et commentaires"
-#: ../../Zotlabs/Module/Setup.php:494
-msgid "mysqli or postgres PHP module"
-msgstr "module PHP postgres ou mysqli"
+#: ../../view/theme/redbasic/php/config.php:101
+msgid "Set radius of corners"
+msgstr "Définir le rayon des arrondis"
-#: ../../Zotlabs/Module/Setup.php:495
-msgid "mb_string PHP module"
-msgstr "module PHP mb_string"
+#: ../../view/theme/redbasic/php/config.php:101
+msgid "Example: 4px"
+msgstr ""
-#: ../../Zotlabs/Module/Setup.php:496
-msgid "mcrypt PHP module"
-msgstr "module PHP mcrypt"
+#: ../../view/theme/redbasic/php/config.php:102
+msgid "Set shadow depth of photos"
+msgstr "Définir la profondeur de l'ombre des photos"
-#: ../../Zotlabs/Module/Setup.php:497
-msgid "xml PHP module"
-msgstr "module PHP xml"
+#: ../../view/theme/redbasic/php/config.php:103
+msgid "Set maximum width of content region in pixel"
+msgstr "Définir la largeur maximale de la zone des contenus"
-#: ../../Zotlabs/Module/Setup.php:501 ../../Zotlabs/Module/Setup.php:503
-msgid "Apache mod_rewrite module"
-msgstr "module Apache mod_rewrite"
+#: ../../view/theme/redbasic/php/config.php:103
+msgid "Leave empty for default width"
+msgstr "Laissez vide pour avoir la largeur par défaut"
-#: ../../Zotlabs/Module/Setup.php:501
+#: ../../view/theme/redbasic/php/config.php:104
+msgid "Left align page content"
+msgstr "Aligner à gauche le contenu de la page"
+
+#: ../../view/theme/redbasic/php/config.php:105
+msgid "Set size of conversation author photo"
+msgstr "Définir la taille de la photo de l'auteur d'une conversation"
+
+#: ../../view/theme/redbasic/php/config.php:106
+msgid "Set size of followup author photos"
+msgstr "Définir la taille de la photo de l'auteur d'une réponse"
+
+#: ../../addon/rendezvous/rendezvous.php:57
+msgid "Errors encountered deleting database table "
+msgstr "Des erreurs ont eu lieu lors de la suppression de la table de la base de données."
+
+#: ../../addon/rendezvous/rendezvous.php:95
+#: ../../addon/twitter/twitter.php:773
+msgid "Submit Settings"
+msgstr "Emvoyer les paramètres"
+
+#: ../../addon/rendezvous/rendezvous.php:96
+msgid "Drop tables when uninstalling?"
+msgstr "Lors de la désinstallation, purger les tables?"
+
+#: ../../addon/rendezvous/rendezvous.php:96
msgid ""
-"Error: Apache webserver mod-rewrite module is required but not installed."
-msgstr "Erreur&nbsp;: le module mod-rewrite du serveur web Apache est requis, mais pas installé."
+"If checked, the Rendezvous database tables will be deleted when the plugin "
+"is uninstalled."
+msgstr "Si cette case est cochée, les tables de la base Rendezvous seront supprimées lorsque le plugin sera désinstallé."
-#: ../../Zotlabs/Module/Setup.php:507 ../../Zotlabs/Module/Setup.php:510
-msgid "proc_open"
-msgstr "proc_open"
+#: ../../addon/rendezvous/rendezvous.php:97
+msgid "Mapbox Access Token"
+msgstr "Jeton d'accès à la mapbox."
-#: ../../Zotlabs/Module/Setup.php:507
+#: ../../addon/rendezvous/rendezvous.php:97
msgid ""
-"Error: proc_open is required but is either not installed or has been "
-"disabled in php.ini"
-msgstr "Erreur&nbsp;: proc_open est requis, mais soit n'est pas installé, soit est désactivé dans le php.ini"
+"If you enter a Mapbox access token, it will be used to retrieve map tiles "
+"from Mapbox instead of the default OpenStreetMap tile server."
+msgstr "Si vous entrez un jeton d'accès Mapbox, il doit être utilisé pour récupérer les cartes à partir de Mapbox au lieu du serveur par défaut OpenStreetMap."
-#: ../../Zotlabs/Module/Setup.php:515
-msgid "Error: libCURL PHP module required but not installed."
-msgstr "Erreur&nbsp;: le module libCURL de PHP est requis, mais pas installé."
+#: ../../addon/rendezvous/rendezvous.php:162
+msgid "Rendezvous"
+msgstr "Rendezvous"
-#: ../../Zotlabs/Module/Setup.php:519
+#: ../../addon/rendezvous/rendezvous.php:167
msgid ""
-"Error: GD graphics PHP module with JPEG support required but not installed."
-msgstr "Erreur&nbsp;: le module GD de PHP avec support JPEG est requis, mais pas installé."
+"This identity has been deleted by another member due to inactivity. Please "
+"press the \"New identity\" button or refresh the page to register a new "
+"identity. You may use the same name."
+msgstr "Cette identité a été supprimée par un autre membre en raison de l'inactivité. Appuyez sur le bouton \"Nouvelle identité\" ou actualisez la page pour enregistrer une nouvelle identité. Vous pouvez utiliser le même nom."
-#: ../../Zotlabs/Module/Setup.php:523
-msgid "Error: openssl PHP module required but not installed."
-msgstr "Erreur&nbsp;: le module openssl de PHP est requis, mais pas installé."
+#: ../../addon/rendezvous/rendezvous.php:168
+msgid "Welcome to Rendezvous!"
+msgstr "Bienvenue dans Rendevzvous!"
-#: ../../Zotlabs/Module/Setup.php:527
+#: ../../addon/rendezvous/rendezvous.php:169
msgid ""
-"Error: mysqli or postgres PHP module required but neither are installed."
-msgstr "Erreur&nbsp;: un module PHP mysqli ou postgres est requis, mais aucun des deux n'est installé."
+"Enter your name to join this rendezvous. To begin sharing your location with"
+" the other members, tap the GPS control. When your location is discovered, a"
+" red dot will appear and others will be able to see you on the map."
+msgstr "Entrez votre nom pour rejoindre ce rendez-vous. Pour commencer à partager votre emplacement avec les autres membres, appuyez sur le contrôle GPS. Lorsque votre emplacement est découvert, un point rouge apparaîtra et les autres seront en mesure de vous voir sur la carte."
-#: ../../Zotlabs/Module/Setup.php:531
-msgid "Error: mb_string PHP module required but not installed."
-msgstr "Erreur&nbsp;: le module mb_string de PHP est requis, mais pas installé."
+#: ../../addon/rendezvous/rendezvous.php:171
+msgid "Let's meet here"
+msgstr "Rencontrez-vous ici"
-#: ../../Zotlabs/Module/Setup.php:535
-msgid "Error: mcrypt PHP module required but not installed."
-msgstr "Erreur&nbsp;: le module mcrypt de PHP est requis, mais pas installé."
+#: ../../addon/rendezvous/rendezvous.php:174
+msgid "New marker"
+msgstr "Nouveau marqueur"
-#: ../../Zotlabs/Module/Setup.php:539
-msgid "Error: xml PHP module required for DAV but not installed."
-msgstr "Erreur&nbsp;: le module xml de PHP est requis pour le DAV, mais pas installé."
+#: ../../addon/rendezvous/rendezvous.php:175
+msgid "Edit marker"
+msgstr "Éditer le marqueur"
-#: ../../Zotlabs/Module/Setup.php:557
-msgid ""
-"The web installer needs to be able to create a file called \".htconfig.php\""
-" in the top folder of your web server and it is unable to do so."
-msgstr "L'installeur web a besoin de créer un fichier \".htconfig.php\" à la racine de votre serveur web, mais en est incapable."
+#: ../../addon/rendezvous/rendezvous.php:176
+msgid "New identity"
+msgstr "Nouvelle identité"
-#: ../../Zotlabs/Module/Setup.php:558
-msgid ""
-"This is most often a permission setting, as the web server may not be able "
-"to write files in your folder - even if you can."
-msgstr "C'est généralement lié à un problème de droits, à cause duquel le serveur web est interdit d'écriture dans le répertoire concerné - alors que votre propre utilisateur a le droit."
+#: ../../addon/rendezvous/rendezvous.php:177
+msgid "Delete marker"
+msgstr "Supprimer le marqueur"
+
+#: ../../addon/rendezvous/rendezvous.php:178
+msgid "Delete member"
+msgstr "Supprimer le membre"
-#: ../../Zotlabs/Module/Setup.php:559
+#: ../../addon/rendezvous/rendezvous.php:179
+msgid "Edit proximity alert"
+msgstr "Éditer l'alerte de proximité"
+
+#: ../../addon/rendezvous/rendezvous.php:180
msgid ""
-"At the end of this procedure, we will give you a text to save in a file "
-"named .htconfig.php in your Red top folder."
-msgstr "Au terme de cette procédure, nous vous transmettrons un texte à sauvegarder dans un fichier nommé .htconfig.php, à la racine de votre installation de $Projectname."
+"A proximity alert will be issued when this member is within a certain radius"
+" of you.<br><br>Enter a radius in meters (0 to disable):"
+msgstr "Une alerte de proximité sera émise lorsque ce membre se trouve dans un certain périmètre autour de vous. Entrer un rayon en mètres (0 pour désactiver):"
+
+#: ../../addon/rendezvous/rendezvous.php:180
+#: ../../addon/rendezvous/rendezvous.php:185
+msgid "distance"
+msgstr "distance"
-#: ../../Zotlabs/Module/Setup.php:560
+#: ../../addon/rendezvous/rendezvous.php:181
+msgid "Proximity alert distance (meters)"
+msgstr "Distance d'alerte de proximité (mètres)"
+
+#: ../../addon/rendezvous/rendezvous.php:182
+#: ../../addon/rendezvous/rendezvous.php:184
msgid ""
-"You can alternatively skip this procedure and perform a manual installation."
-" Please see the file \"install/INSTALL.txt\" for instructions."
-msgstr "Autrement, vous pouvez contourner toute cette procédure et réaliser l'installation manuellement. Merci de consulter le fichier \"install/INSTALL.txt\" pour les instructions détaillées."
+"A proximity alert will be issued when you are within a certain radius of the"
+" marker location.<br><br>Enter a radius in meters (0 to disable):"
+msgstr "Une alerte de proximité sera déclenchée quand vous serez à une certaine distance du marqueur d'emplacement.<br><br>Indiquez une distance en mètres (0 pour désactiver)&nbsp;:"
-#: ../../Zotlabs/Module/Setup.php:563
-msgid ".htconfig.php is writable"
-msgstr "Le fichier .htconfig.php est accessible en écriture"
+#: ../../addon/rendezvous/rendezvous.php:183
+msgid "Marker proximity alert"
+msgstr "Alerte de proximité de marqueur"
+
+#: ../../addon/rendezvous/rendezvous.php:186
+msgid "Reminder note"
+msgstr "Note de rappel"
-#: ../../Zotlabs/Module/Setup.php:577
+#: ../../addon/rendezvous/rendezvous.php:187
msgid ""
-"Red uses the Smarty3 template engine to render its web views. Smarty3 "
-"compiles templates to PHP to speed up rendering."
-msgstr "$Projectname utilise le moteur de gabarits Smarty3 pour mettre son contenu en forme. Smarty3 compile ses modèles vers du PHP natif pour accélérer le rendu."
+"Enter a note to be displayed when you are within the specified proximity..."
+msgstr "Saisissez une note à afficher quand vous serez à la distance indiquée..."
-#: ../../Zotlabs/Module/Setup.php:578
-#, php-format
+#: ../../addon/rendezvous/rendezvous.php:199
+msgid "Add new rendezvous"
+msgstr "Ajouter un nouveau rendezvous"
+
+#: ../../addon/rendezvous/rendezvous.php:200
msgid ""
-"In order to store these compiled templates, the web server needs to have "
-"write access to the directory %s under the top level web folder."
+"Create a new rendezvous and share the access link with those you wish to "
+"invite to the group. Those who open the link become members of the "
+"rendezvous. They can view other member locations, add markers to the map, or"
+" share their own locations with the group."
+msgstr "Créez un nouveau rendez-vous et partagez le lien d'accès avec les gens que vous souhaitez inviter au groupe. Ceux qui ouvrent le lien deviennent membres du rendez-vous. Ils peuvent afficher les emplacements des autres membres, ajouter des marqueurs à la carte ou partager leurs propres emplacements avec le groupe."
+
+#: ../../addon/skeleton/skeleton.php:59
+msgid "Some setting"
+msgstr "Un certain paramètre"
+
+#: ../../addon/skeleton/skeleton.php:61
+msgid "A setting"
+msgstr "Un paramètre"
+
+#: ../../addon/skeleton/skeleton.php:64
+msgid "Skeleton Settings"
+msgstr "Paramètres du squelette"
+
+#: ../../addon/gnusoc/gnusoc.php:118
+msgid "GNU-Social Protocol Settings updated."
msgstr ""
-#: ../../Zotlabs/Module/Setup.php:579 ../../Zotlabs/Module/Setup.php:600
-msgid ""
-"Please ensure that the user that your web server runs as (e.g. www-data) has"
-" write access to this folder."
-msgstr "Merci de vous assurer que l'utilisateur sous lequel le serveur web tourne (le plus souvent, www-data) a bien l'autorisation d'écrire dans ce répertoire."
+#: ../../addon/gnusoc/gnusoc.php:129
+msgid "Enable the GNU-Social protocol for this channel"
+msgstr ""
-#: ../../Zotlabs/Module/Setup.php:580
-#, php-format
-msgid ""
-"Note: as a security measure, you should give the web server write access to "
-"%s only--not the template files (.tpl) that it contains."
-msgstr "Note: Comme mesure de sécurité, assurez vous de donner les droits d'écriture au serveur web sur %s uniquement, pas sur les fichiers individuels (.tpl) qu'il contient."
+#: ../../addon/gnusoc/gnusoc.php:133
+msgid "GNU-Social Protocol Settings"
+msgstr ""
-#: ../../Zotlabs/Module/Setup.php:583
+#: ../../addon/gnusoc/gnusoc.php:323
+msgid "Follow"
+msgstr ""
+
+#: ../../addon/gnusoc/gnusoc.php:326
#, php-format
-msgid "%s is writable"
-msgstr "Permission d'écriture sur %s activée"
+msgid "%1$s is now following %2$s"
+msgstr ""
-#: ../../Zotlabs/Module/Setup.php:599
-msgid ""
-"Red uses the store directory to save uploaded files. The web server needs to"
-" have write access to the store directory under the Red top level folder"
-msgstr "$Projectname utilise le répertoire 'store' - situé à la racine de votre installation de $Projectname - pour sauvegarder les fichiers envoyés. Le serveur web aura donc besoin de pouvoir y écrire."
+#: ../../addon/cdav/Mod_Cdav.php:744
+msgid "INVALID EVENT DISMISSED!"
+msgstr "ÉVÉNEMENT INVALIDE REJETÉ!"
-#: ../../Zotlabs/Module/Setup.php:603
-msgid "store is writable"
-msgstr "'store' est accessible en écriture"
+#: ../../addon/cdav/Mod_Cdav.php:745
+msgid "Summary: "
+msgstr "Sommaire :"
-#: ../../Zotlabs/Module/Setup.php:636
-msgid ""
-"SSL certificate cannot be validated. Fix certificate or disable https access"
-" to this site."
-msgstr "Le certificat SSL/TLS n'a pas pu être validé. Merci de le corriger, ou de désactiver l'accès https à ce site (non recommandé)."
+#: ../../addon/cdav/Mod_Cdav.php:746
+msgid "Date: "
+msgstr "Date :"
-#: ../../Zotlabs/Module/Setup.php:637
-msgid ""
-"If you have https access to your website or allow connections to TCP port "
-"443 (the https: port), you MUST use a browser-valid certificate. You MUST "
-"NOT use self-signed certificates!"
-msgstr "Si votre serveur accepte les connexions https ou s'il permet les connexions sur le port TCP 443 (le port utilisé par le protocole https), vous DEVEZ utiliser un certificat valide. Vous ne DEVEZ PAS utiliser un certificat que vous avez vous-mêmes signé&nbsp;!"
+#: ../../addon/cdav/Mod_Cdav.php:747 ../../addon/cdav/Mod_Cdav.php:754
+msgid "Reason: "
+msgstr "Raison :"
-#: ../../Zotlabs/Module/Setup.php:638
-msgid ""
-"This restriction is incorporated because public posts from you may for "
-"example contain references to images on your own hub."
-msgstr "Nous avons ajouté cette contrainte pour éviter que vos publications publiques ne fassent référence par exemple à des images sur votre propre hub."
+#: ../../addon/cdav/Mod_Cdav.php:752
+msgid "INVALID CARD DISMISSED!"
+msgstr "ÉVÉNEMENT INVALIDE REJETÉ!"
-#: ../../Zotlabs/Module/Setup.php:639
-msgid ""
-"If your certificate is not recognized, members of other sites (who may "
-"themselves have valid certificates) will get a warning message on their own "
-"site complaining about security issues."
-msgstr "Si votre certificat n'est pas reconnu, les membres des autres sites (qui eux peuvent avoir des certificats valides) recevront des messages d'avertissement sur leur propre site se plaignant de problèmes de sécurité."
+#: ../../addon/cdav/Mod_Cdav.php:753
+msgid "Name: "
+msgstr "Nom :"
-#: ../../Zotlabs/Module/Setup.php:640
+#: ../../addon/cdav/Mod_Cdav.php:770
msgid ""
-"This can cause usability issues elsewhere (not just on your own site) so we "
-"must insist on this requirement."
-msgstr "Ceci peut causer des problèmes d'ergonomie ailleurs (pas seulement sur votre site), nous devons donc insister sur ce prérequis."
+"You have to enable this plugin in Feature/Addon Settings > CalDAV/CardDAV "
+"Settings before you can use it."
+msgstr "Vous avez activé ce plugin dans Fonctionalités/Paramètres des extensions > CalDAV/CardDAV Paramètres avant que vous puissiez l'utiliser."
-#: ../../Zotlabs/Module/Setup.php:641
-msgid ""
-"Providers are available that issue free certificates which are browser-"
-"valid."
-msgstr "Il existe des autorités de certification qui vous fourniront gratuitement un certificat valide."
+#: ../../addon/cdav/Mod_Cdav.php:836 ../../addon/cdav/Mod_Cdav.php:837
+msgid "Example: YYYY-MM-DD HH:mm"
+msgstr "Exemple : YYYY-MM-DD HH:mm"
-#: ../../Zotlabs/Module/Setup.php:643
-msgid "SSL certificate validation"
-msgstr "Validation du certificat SSL/TLS"
+#: ../../addon/cdav/Mod_Cdav.php:837
+msgid "End date and time"
+msgstr "Date et heure de fin"
-#: ../../Zotlabs/Module/Setup.php:649
-msgid ""
-"Url rewrite in .htaccess is not working. Check your server "
-"configuration.Test: "
-msgstr "La réécriture d'URL définie dans le .htaccess ne fonctionne pas. Vérifiez votre configuration serveur. Test&nbsp;:"
+#: ../../addon/cdav/Mod_Cdav.php:852
+msgid "List month"
+msgstr "Liste mois"
-#: ../../Zotlabs/Module/Setup.php:652
-msgid "Url rewrite is working"
-msgstr "La réécriture d'URL fonctionne"
+#: ../../addon/cdav/Mod_Cdav.php:853
+msgid "List week"
+msgstr "Liste semaine"
-#: ../../Zotlabs/Module/Setup.php:661
-msgid ""
-"The database configuration file \".htconfig.php\" could not be written. "
-"Please use the enclosed text to create a configuration file in your web "
-"server root."
-msgstr "Le fichier de configuration de la base de données - \".htconfig.php\" - ne peut être écrit. Merci de copier le texte généré dans un fichier à ce nom, à la racine de votre serveur web."
+#: ../../addon/cdav/Mod_Cdav.php:854
+msgid "List day"
+msgstr "Liste jour"
-#: ../../Zotlabs/Module/Setup.php:685
-msgid "Errors encountered creating database tables."
-msgstr "Erreurs rencontrées pendant la création de tables de BDD."
+#: ../../addon/cdav/Mod_Cdav.php:861
+msgid "More"
+msgstr "Plus"
-#: ../../Zotlabs/Module/Setup.php:719
-msgid "<h1>What next</h1>"
-msgstr "<h1>Et maintenant</h1>"
+#: ../../addon/cdav/Mod_Cdav.php:862
+msgid "Less"
+msgstr "Moins"
-#: ../../Zotlabs/Module/Setup.php:720
-msgid ""
-"IMPORTANT: You will need to [manually] setup a scheduled task for the "
-"poller."
-msgstr "IMPORTANT&nbsp;: Vous devez créer [manuellement] une tâche planifiée pour les mises à jour du réseau."
+#: ../../addon/cdav/Mod_Cdav.php:863
+msgid "Select calendar"
+msgstr "Sélectionner un calendrier"
-#: ../../Zotlabs/Module/Sharedwithme.php:98
-msgid "Files: shared with me"
-msgstr "Fichiers&nbsp;: partagés avec moi"
+#: ../../addon/cdav/Mod_Cdav.php:865
+msgid "Delete all"
+msgstr "Tout supprimer"
-#: ../../Zotlabs/Module/Sharedwithme.php:100
-msgid "NEW"
-msgstr "NOUVEAU"
+#: ../../addon/cdav/Mod_Cdav.php:867
+msgid "Sorry! Editing of recurrent events is not yet implemented."
+msgstr "Désolé ! L'édition d'événements récurrents n'est pas encore implémenté."
-#: ../../Zotlabs/Module/Sharedwithme.php:103
-msgid "Remove all files"
-msgstr "Supprimer tous les fichiers"
+#: ../../addon/cdav/cdav.php:36
+msgid "Errors encountered creating database table: "
+msgstr "Des erreurs se sont produites lors de la création de la table de la base de données :"
-#: ../../Zotlabs/Module/Sharedwithme.php:104
-msgid "Remove this file"
-msgstr "Supprimer ce fichier"
+#: ../../addon/cdav/cdav.php:197
+msgid "Default Calendar"
+msgstr "Agenda par défaut"
-#: ../../Zotlabs/Module/Siteinfo.php:19
+#: ../../addon/cdav/cdav.php:206
+msgid "Default Addressbook"
+msgstr "Carnet d'adresses par défaut"
+
+#: ../../addon/cdav/cdav.php:215
+msgid "CalDAV/CardDAV Settings saved."
+msgstr "Les paramètres CalDAV/CardDAV ont été sauvegardés."
+
+#: ../../addon/cdav/cdav.php:234
+msgid "Enable CalDAV/CardDAV Server for this channel"
+msgstr "Activer le serveur CalDAV/CardDAV pour ce canal"
+
+#: ../../addon/cdav/cdav.php:237
#, php-format
-msgid "Version %s"
-msgstr "Version %s"
+msgid "Your CalDAV resources are located at %s "
+msgstr "Vos ressources CalDAV sont situées à %s"
-#: ../../Zotlabs/Module/Siteinfo.php:40
-msgid "Installed plugins/addons/apps:"
-msgstr "Greffons/extensions/applications installés&nbsp;:"
+#: ../../addon/cdav/cdav.php:240
+#, php-format
+msgid "Your CardDAV resources are located at %s "
+msgstr "Vos ressources CardDAV sont situées à %s"
-#: ../../Zotlabs/Module/Siteinfo.php:53
-msgid "No installed plugins/addons/apps"
-msgstr "Aucun greffon/extension/application installé"
+#: ../../addon/cdav/cdav.php:246
+msgid "CalDAV/CardDAV Settings"
+msgstr "Paramètres CalDAV/CardDAV"
-#: ../../Zotlabs/Module/Siteinfo.php:66
-msgid ""
-"This is a hub of $Projectname - a global cooperative network of "
-"decentralized privacy enhanced websites."
-msgstr "Ceci est un serveur $Projectname - un réseau collaboratif mondial de serveurs décentralisés à la confidentialité améliorée."
+#: ../../addon/cdav/cdav.php:272 ../../include/connections.php:670
+msgid "Home, Voice"
+msgstr "Domicile, Voix"
-#: ../../Zotlabs/Module/Siteinfo.php:68
-msgid "Tag: "
-msgstr "Étiquette&nbsp;:"
+#: ../../addon/cdav/cdav.php:273 ../../include/connections.php:671
+msgid "Home, Fax"
+msgstr "Domicile, Fax"
-#: ../../Zotlabs/Module/Siteinfo.php:70
-msgid "Last background fetch: "
-msgstr "Dernière récupération en tâche de fond&nbsp;:"
+#: ../../addon/cdav/cdav.php:275 ../../include/connections.php:673
+msgid "Work, Voice"
+msgstr "Travail, Voix"
-#: ../../Zotlabs/Module/Siteinfo.php:72
-msgid "Current load average: "
-msgstr "Charge moyenne actuelle&nbsp;:"
+#: ../../addon/cdav/cdav.php:276 ../../include/connections.php:674
+msgid "Work, Fax"
+msgstr "Travail, Fax"
-#: ../../Zotlabs/Module/Siteinfo.php:75
-msgid "Running at web location"
-msgstr "Tourne à l'adresse internet"
+#: ../../addon/cdav/include/widgets.php:37
+msgid "Select Channel"
+msgstr "Sélectionner un canal"
-#: ../../Zotlabs/Module/Siteinfo.php:76
-msgid ""
-"Please visit <a href=\"http://hubzilla.org\">hubzilla.org</a> to learn more "
-"about $Projectname."
-msgstr "Merci de visiter <a href=\"http://hubzilla.org\">hubzilla.org</a> pour en apprendre davantage sur $Projectname."
+#: ../../addon/cdav/include/widgets.php:42
+msgid "Read-write"
+msgstr "Lire et écrire"
-#: ../../Zotlabs/Module/Siteinfo.php:77
-msgid "Bug reports and issues: please visit"
-msgstr "Pour remonter bogues et problèmes, merci de visiter"
+#: ../../addon/cdav/include/widgets.php:43
+msgid "Read-only"
+msgstr "Lire uniquement"
-#: ../../Zotlabs/Module/Siteinfo.php:79
-msgid "$projectname issues"
-msgstr "Problèmes $projectname"
+#: ../../addon/cdav/include/widgets.php:116
+msgid "My Calendars"
+msgstr "Mes agendas"
-#: ../../Zotlabs/Module/Siteinfo.php:80
-msgid ""
-"Suggestions, praise, etc. - please email \"redmatrix\" at librelist - dot "
-"com"
-msgstr "Suggestions, demandes, etc. - merci de vous adresser à \"redmatrix\" à librelist - point com"
+#: ../../addon/cdav/include/widgets.php:118
+msgid "Shared Calendars"
+msgstr "Agendas partagés"
-#: ../../Zotlabs/Module/Siteinfo.php:82
-msgid "Site Administrators"
-msgstr "Administrateurs du site"
+#: ../../addon/cdav/include/widgets.php:122
+msgid "Share this calendar"
+msgstr "Partager cet agenda"
-#: ../../Zotlabs/Module/Sources.php:37
-msgid "Failed to create source. No channel selected."
-msgstr "Impossible de créer la source. Aucun canal selectionné."
+#: ../../addon/cdav/include/widgets.php:124
+msgid "Calendar name and color"
+msgstr "Nom et couleur de l'agenda"
-#: ../../Zotlabs/Module/Sources.php:51
-msgid "Source created."
-msgstr "Source créée."
+#: ../../addon/cdav/include/widgets.php:126
+msgid "Create new calendar"
+msgstr "Créer un nouvel agenda"
-#: ../../Zotlabs/Module/Sources.php:64
-msgid "Source updated."
-msgstr "Source mise à jour."
+#: ../../addon/cdav/include/widgets.php:128
+msgid "Calendar Name"
+msgstr "Nom de l'agenda"
-#: ../../Zotlabs/Module/Sources.php:90
-msgid "*"
-msgstr "*"
+#: ../../addon/cdav/include/widgets.php:129
+msgid "Calendar Tools"
+msgstr "Outils pour les agendas"
-#: ../../Zotlabs/Module/Sources.php:96 ../../include/widgets.php:630
-#: ../../include/features.php:71
-msgid "Channel Sources"
-msgstr "Sources du canal"
+#: ../../addon/cdav/include/widgets.php:130
+msgid "Import calendar"
+msgstr "Importer un agenda"
-#: ../../Zotlabs/Module/Sources.php:97
-msgid "Manage remote sources of content for your channel."
-msgstr "Gérer les sources distantes de contenu pour votre canal."
+#: ../../addon/cdav/include/widgets.php:131
+msgid "Select a calendar to import to"
+msgstr "Sélectionner un agenda à importer dans"
-#: ../../Zotlabs/Module/Sources.php:98 ../../Zotlabs/Module/Sources.php:108
-msgid "New Source"
-msgstr "Nouvelle source"
+#: ../../addon/cdav/include/widgets.php:158
+msgid "Addressbooks"
+msgstr "Carnet d'adresses"
-#: ../../Zotlabs/Module/Sources.php:109 ../../Zotlabs/Module/Sources.php:143
-msgid ""
-"Import all or selected content from the following channel into this channel "
-"and distribute it according to your channel settings."
-msgstr "Importer le contenu sélectionné ou tout le contenu du canal suivant vers ce canal et le distribuer selon vos paramètres de canal."
+#: ../../addon/cdav/include/widgets.php:160
+msgid "Addressbook name"
+msgstr "Nom du carnet d'adresses"
-#: ../../Zotlabs/Module/Sources.php:110 ../../Zotlabs/Module/Sources.php:144
-msgid "Only import content with these words (one per line)"
-msgstr "N'importer le contenu que s'il contient ces mots (un par ligne)"
+#: ../../addon/cdav/include/widgets.php:162
+msgid "Create new addressbook"
+msgstr "Créer un nouveau carnet d'adresses"
-#: ../../Zotlabs/Module/Sources.php:110 ../../Zotlabs/Module/Sources.php:144
-msgid "Leave blank to import all public content"
-msgstr "Laissez vide pour importer tout le contenu public"
+#: ../../addon/cdav/include/widgets.php:163
+msgid "Addressbook Name"
+msgstr "Nom du carnet d'adresses"
-#: ../../Zotlabs/Module/Sources.php:111 ../../Zotlabs/Module/Sources.php:148
-msgid "Channel Name"
-msgstr "Nom du canal"
+#: ../../addon/cdav/include/widgets.php:165
+msgid "Addressbook Tools"
+msgstr "Outils pour les carnets d'adresses"
-#: ../../Zotlabs/Module/Sources.php:112 ../../Zotlabs/Module/Sources.php:147
-msgid ""
-"Add the following categories to posts imported from this source (comma "
-"separated)"
-msgstr ""
+#: ../../addon/cdav/include/widgets.php:166
+msgid "Import addressbook"
+msgstr "Importer un carnet d'adresses"
-#: ../../Zotlabs/Module/Sources.php:133 ../../Zotlabs/Module/Sources.php:161
-msgid "Source not found."
-msgstr "Source introuvable."
+#: ../../addon/cdav/include/widgets.php:167
+msgid "Select an addressbook to import to"
+msgstr "Sélectionner un carnet d'adresses à importer dans"
-#: ../../Zotlabs/Module/Sources.php:140
-msgid "Edit Source"
-msgstr "Modifier la source"
+#: ../../addon/planets/planets.php:121
+msgid "Planets Settings updated."
+msgstr "Paramètres Planets mis à jour."
-#: ../../Zotlabs/Module/Sources.php:141
-msgid "Delete Source"
-msgstr "Supprimer la source"
+#: ../../addon/planets/planets.php:153
+msgid "Enable Planets Plugin"
+msgstr "Activer le plugin Planets"
-#: ../../Zotlabs/Module/Sources.php:169
-msgid "Source removed"
-msgstr "Source supprimée"
+#: ../../addon/planets/planets.php:157
+msgid "Planets Settings"
+msgstr "Paramètres Planets"
-#: ../../Zotlabs/Module/Sources.php:171
-msgid "Unable to remove source."
-msgstr "Impossible de supprimer la source."
+#: ../../addon/openclipatar/openclipatar.php:50
+#: ../../addon/openclipatar/openclipatar.php:128
+msgid "System defaults:"
+msgstr "Paramètres par défaut du système :"
-#: ../../Zotlabs/Module/Subthread.php:118
-#, php-format
-msgid "%1$s is following %2$s's %3$s"
-msgstr "%1$s suit %3$s de %2$s"
+#: ../../addon/openclipatar/openclipatar.php:54
+msgid "Preferred Clipart IDs"
+msgstr "ID Clipart préférées"
-#: ../../Zotlabs/Module/Subthread.php:120
-#, php-format
-msgid "%1$s stopped following %2$s's %3$s"
-msgstr "%1$s ne suit plus %3$s de %2$s"
+#: ../../addon/openclipatar/openclipatar.php:54
+msgid "List of preferred clipart ids. These will be shown first."
+msgstr "Liste des ids clipart préférése. Celles-ci seront montrées en premier."
-#: ../../Zotlabs/Module/Suggest.php:39
-msgid ""
-"No suggestions available. If this is a new site, please try again in 24 "
-"hours."
-msgstr "Aucune suggestion disponible. Si le site est récent, merci de re-tenter dans 24 heures."
+#: ../../addon/openclipatar/openclipatar.php:55
+msgid "Default Search Term"
+msgstr "Terme de recherche par défaut"
-#: ../../Zotlabs/Module/Suggest.php:58 ../../include/widgets.php:149
-msgid "Ignore/Hide"
-msgstr "Ignorer/Cacher"
+#: ../../addon/openclipatar/openclipatar.php:55
+msgid "The default search term. These will be shown second."
+msgstr "Le terme de recherche par défaut. Ceci sera affiché en second."
-#: ../../Zotlabs/Module/Tagger.php:55 ../../include/bbcode.php:256
-msgid "post"
-msgstr "publication"
+#: ../../addon/openclipatar/openclipatar.php:56
+msgid "Return After"
+msgstr "Retourner ensuite"
-#: ../../Zotlabs/Module/Tagger.php:57 ../../include/text.php:1948
-#: ../../include/conversation.php:150
-msgid "comment"
-msgstr "commentaire"
+#: ../../addon/openclipatar/openclipatar.php:56
+msgid "Page to load after image selection."
+msgstr "Page à afficher après la sélection de l'image."
-#: ../../Zotlabs/Module/Tagger.php:100
-#, php-format
-msgid "%1$s tagged %2$s's %3$s with %4$s"
-msgstr "%1$s a étiqueté le %3$s de %2$s avec %4$s"
+#: ../../addon/openclipatar/openclipatar.php:58 ../../include/channel.php:1046
+#: ../../include/nav.php:107
+msgid "Edit Profile"
+msgstr "Éditeur de profil"
-#: ../../Zotlabs/Module/Tagrm.php:48 ../../Zotlabs/Module/Tagrm.php:98
-msgid "Tag removed"
-msgstr "Étiquette retirée"
+#: ../../addon/openclipatar/openclipatar.php:59
+msgid "Profile List"
+msgstr "Liste de profil"
-#: ../../Zotlabs/Module/Tagrm.php:123
-msgid "Remove Item Tag"
-msgstr "Retirer une étiquette à l'élément"
+#: ../../addon/openclipatar/openclipatar.php:61
+msgid "Order of Preferred"
+msgstr "Tri selon les préférences"
-#: ../../Zotlabs/Module/Tagrm.php:125
-msgid "Select a tag to remove: "
-msgstr "Étiquette à retirer&nbsp;:"
+#: ../../addon/openclipatar/openclipatar.php:61
+msgid "Sort order of preferred clipart ids."
+msgstr "Ordre de tri des ids de clipart préférés."
-#: ../../Zotlabs/Module/Thing.php:114
-msgid "Thing updated"
-msgstr "Elément mis à jour"
+#: ../../addon/openclipatar/openclipatar.php:62
+#: ../../addon/openclipatar/openclipatar.php:68
+msgid "Newest first"
+msgstr "Les plus récents en premier"
-#: ../../Zotlabs/Module/Thing.php:166
-msgid "Object store: failed"
-msgstr "Stockage de l'objet&nbsp;: échec"
+#: ../../addon/openclipatar/openclipatar.php:65
+msgid "As entered"
+msgstr "Comme entrés"
-#: ../../Zotlabs/Module/Thing.php:170
-msgid "Thing added"
-msgstr "Elément ajouté"
+#: ../../addon/openclipatar/openclipatar.php:67
+msgid "Order of other"
+msgstr "Tri selon autre"
-#: ../../Zotlabs/Module/Thing.php:196
-#, php-format
-msgid "OBJ: %1$s %2$s %3$s"
-msgstr "OBJ: %1$s %2$s %3$s"
+#: ../../addon/openclipatar/openclipatar.php:67
+msgid "Sort order of other clipart ids."
+msgstr "Ordre de tri des autres clipart ids."
-#: ../../Zotlabs/Module/Thing.php:259
-msgid "Show Thing"
-msgstr "Montrer élément"
+#: ../../addon/openclipatar/openclipatar.php:69
+msgid "Most downloaded first"
+msgstr "Les plus téléchargés en premier"
-#: ../../Zotlabs/Module/Thing.php:266
-msgid "item not found."
-msgstr "élément introuvable."
+#: ../../addon/openclipatar/openclipatar.php:70
+msgid "Most liked first"
+msgstr "Les plus aimés en premier"
-#: ../../Zotlabs/Module/Thing.php:299
-msgid "Edit Thing"
-msgstr "Modifier élément"
+#: ../../addon/openclipatar/openclipatar.php:72
+msgid "Preferred IDs Message"
+msgstr "IDs des messages préférés"
-#: ../../Zotlabs/Module/Thing.php:301 ../../Zotlabs/Module/Thing.php:351
-msgid "Select a profile"
-msgstr "Choisissez un profil"
+#: ../../addon/openclipatar/openclipatar.php:72
+msgid "Message to display above preferred results."
+msgstr "Message à afficher au-dessus de la liste des résultats préférés."
-#: ../../Zotlabs/Module/Thing.php:305 ../../Zotlabs/Module/Thing.php:354
-msgid "Post an activity"
-msgstr "Publier une activité"
+#: ../../addon/openclipatar/openclipatar.php:78
+msgid "Uploaded by: "
+msgstr "Téléversé par :"
-#: ../../Zotlabs/Module/Thing.php:305 ../../Zotlabs/Module/Thing.php:354
-msgid "Only sends to viewers of the applicable profile"
-msgstr "Envoie exclusivement aux visiteurs du profil concerné"
+#: ../../addon/openclipatar/openclipatar.php:78
+msgid "Drawn by: "
+msgstr "Dessiné par :"
-#: ../../Zotlabs/Module/Thing.php:307 ../../Zotlabs/Module/Thing.php:356
-msgid "Name of thing e.g. something"
-msgstr "Nom de l'élément, p.ex. quelque-chose"
+#: ../../addon/openclipatar/openclipatar.php:192
+msgid "Or select from a free OpenClipart.org image:"
+msgstr "ou sélectionner une image libre d'OpenClipart.org :"
-#: ../../Zotlabs/Module/Thing.php:309 ../../Zotlabs/Module/Thing.php:357
-msgid "URL of thing (optional)"
-msgstr "URL de l'élément (facultatif)"
+#: ../../addon/openclipatar/openclipatar.php:195
+msgid "Search Term"
+msgstr "Terme de recherche"
-#: ../../Zotlabs/Module/Thing.php:311 ../../Zotlabs/Module/Thing.php:358
-msgid "URL for photo of thing (optional)"
-msgstr "URL d'une photo de l'élément (facultatif)"
+#: ../../addon/openclipatar/openclipatar.php:232
+msgid "Unknown error. Please try again later."
+msgstr "Erreur inconnue. Veuillez essayer à nouveau plus tard."
-#: ../../Zotlabs/Module/Thing.php:349
-msgid "Add Thing to your Profile"
-msgstr "Ajouter l'élément à votre profil"
+#: ../../addon/openclipatar/openclipatar.php:308
+msgid "Profile photo updated successfully."
+msgstr "Photo de profil actualisée avec succès."
-#: ../../Zotlabs/Module/Uexport.php:55 ../../Zotlabs/Module/Uexport.php:56
-msgid "Export Channel"
-msgstr "Exporter le canal"
+#: ../../addon/adultphotoflag/adultphotoflag.php:24
+msgid "Flag Adult Photos"
+msgstr "Photo pour adulte"
-#: ../../Zotlabs/Module/Uexport.php:57
+#: ../../addon/adultphotoflag/adultphotoflag.php:25
msgid ""
-"Export your basic channel information to a file. This acts as a backup of "
-"your connections, permissions, profile and basic data, which can be used to "
-"import your data to a new server hub, but does not contain your content."
-msgstr "Exportez les principales informations de votre canal dans un fichier. Celui-ci pourra servir de sauvegarde de vos contacts, permissions, profils et données de base. Il pourra être importé sur un nouveau hub/serveur, mais n'embarquera pas vos contenus."
+"Provide photo edit option to hide inappropriate photos from default album "
+"view"
+msgstr "Fourni l'option d'édition d'une photo afin de cacher des photos inappropriées de la vue d''album par défaut"
-#: ../../Zotlabs/Module/Uexport.php:58
-msgid "Export Content"
-msgstr "Exporter le contenu"
+#: ../../addon/wppost/wppost.php:45
+msgid "Post to WordPress"
+msgstr "Publier sur Wordpress"
-#: ../../Zotlabs/Module/Uexport.php:59
-msgid ""
-"Export your channel information and recent content to a JSON backup that can"
-" be restored or imported to another server hub. This backs up all of your "
-"connections, permissions, profile data and several months of posts. This "
-"file may be VERY large. Please be patient - it may take several minutes for"
-" this download to begin."
-msgstr "Exportez les informations du canal et les contenus récents dans un fichier JSON. Celui-ci contiendra toutes vos relations, permissions, profils, et plusieurs mois de publications. Ce fichier peut être TRÈS gros. Armez-vous de patience - plusieurs minutes peuvent s'écouler avant que le téléchargement ne commence."
+#: ../../addon/wppost/wppost.php:82
+msgid "Enable WordPress Post Plugin"
+msgstr "Activer l'extension de publication WordPress"
-#: ../../Zotlabs/Module/Uexport.php:60
-msgid "Export your posts from a given year."
-msgstr "Exporter vos publications d'une année en particulier"
+#: ../../addon/wppost/wppost.php:86
+msgid "WordPress username"
+msgstr "Identifiant de connexion WordPress"
-#: ../../Zotlabs/Module/Uexport.php:62
-msgid ""
-"You may also export your posts and conversations for a particular year or "
-"month. Adjust the date in your browser location bar to select other dates. "
-"If the export fails (possibly due to memory exhaustion on your server hub), "
-"please try again selecting a more limited date range."
-msgstr "Vous pouvez également exporter vos publications et conversations pour une année ou un mois particulier. Ajustez la date dans la barre de votre navigateur pour sélectionner d'autres dates. Si l'export échoue (possible en cas de pénurie de mémoire sur le serveur de votre hub), essayez à nouveau en sélectionnant un intervalle de dates plus petit."
+#: ../../addon/wppost/wppost.php:90
+msgid "WordPress password"
+msgstr "Mot de passe de connexion WordPress"
-#: ../../Zotlabs/Module/Uexport.php:63
-#, php-format
-msgid ""
-"To select all posts for a given year, such as this year, visit <a "
-"href=\"%1$s\">%2$s</a>"
-msgstr "Pour sélectionner toutes les publications pour une année donnée, telle que cette année, visitez <a href=\"%1$s\">%2$s</a>"
+#: ../../addon/wppost/wppost.php:94
+msgid "WordPress API URL"
+msgstr "URL de l'API WordPress"
-#: ../../Zotlabs/Module/Uexport.php:64
-#, php-format
-msgid ""
-"To select all posts for a given month, such as January of this year, visit "
-"<a href=\"%1$s\">%2$s</a>"
-msgstr "Pour sélectionner toutes les publications pour un mois donné, par exemple janvier, visitez <a href=\"%1$s\">%2$s</a>"
+#: ../../addon/wppost/wppost.php:95
+msgid "Typically https://your-blog.tld/xmlrpc.php"
+msgstr "Typiquement https://your-blog.tld/xmlrpc.php"
-#: ../../Zotlabs/Module/Uexport.php:65
-#, php-format
+#: ../../addon/wppost/wppost.php:98
+msgid "WordPress blogid"
+msgstr "ID de votre blog WordPress"
+
+#: ../../addon/wppost/wppost.php:99
+msgid "For multi-user sites such as wordpress.com, otherwise leave blank"
+msgstr "Pour les sites multi-utilisateurs comme wordpress.com, sinon laisser vide"
+
+#: ../../addon/wppost/wppost.php:105
+msgid "Post to WordPress by default"
+msgstr "Par défaut, publier sur WordPress"
+
+#: ../../addon/wppost/wppost.php:109
+msgid "Forward comments (requires hubzilla_wp plugin)"
+msgstr "Transférer les commentaires (nécessite le plugin hubzila_wp)"
+
+#: ../../addon/wppost/wppost.php:113
+msgid "WordPress Post Settings"
+msgstr "Paramètres de publications WordPress"
+
+#: ../../addon/wppost/wppost.php:129
+msgid "Wordpress Settings saved."
+msgstr "Les paramètres WordPress ont été sauvegardés."
+
+#: ../../addon/nsfw/nsfw.php:80
msgid ""
-"These content files may be imported or restored by visiting <a "
-"href=\"%1$s\">%2$s</a> on any site containing your channel. For best results"
-" please import or restore these in date order (oldest first)."
-msgstr "Ces fichiers de contenu peuvent être importés ou restaurés en visitant <a href=\"%1$s\">%2$s</a> sur n'importe quel site hébergeant votre canal. Pour de meilleurs résultats merci de les importer par ordre chronologique (les plus anciens d'abord)."
+"This plugin looks in posts for the words/text you specify below, and "
+"collapses any content containing those keywords so it is not displayed at "
+"inappropriate times, such as sexual innuendo that may be improper in a work "
+"setting. It is polite and recommended to tag any content containing nudity "
+"with #NSFW. This filter can also match any other word/text you specify, and"
+" can thereby be used as a general purpose content filter."
+msgstr "Ce plugin cherche dans les publications les mots/textes que vous spécifiez ci-dessous, et réduit tout contenu contenant ces mots-clés afin qu'ils ne s'affichent pas à des moments inappropriés, tels que les insinuations sexuelles qui peuvent être inappropriées dans un contexte de travail. Il est poli et recommandé de marquer tout contenu contenant de la nudité avec #NSFW. Ce filtre peut également correspondre à tout autre mot/texte que vous spécifiez et peut ainsi être utilisé comme un filtre de contenu à usage général."
-#: ../../Zotlabs/Module/Viewconnections.php:62
-msgid "No connections."
-msgstr "Aucun contact."
+#: ../../addon/nsfw/nsfw.php:84
+msgid "Enable Content filter"
+msgstr "Activer le filtrage des contenus"
-#: ../../Zotlabs/Module/Viewconnections.php:75
+#: ../../addon/nsfw/nsfw.php:88
+msgid "Comma separated list of keywords to hide"
+msgstr "Liste séparée par des virgules des mots-clés à cacher"
+
+#: ../../addon/nsfw/nsfw.php:88
+msgid "Word, /regular-expression/, lang=xx, lang!=xx"
+msgstr "Mot, /expression-régulière/, lang=xx, lang!=xx"
+
+#: ../../addon/nsfw/nsfw.php:92
+msgid "Not Safe For Work Settings"
+msgstr "Paramètres NSFW (Not Safe For Work)"
+
+#: ../../addon/nsfw/nsfw.php:92
+msgid "General Purpose Content Filter"
+msgstr "Filtre de contenu sujet général"
+
+#: ../../addon/nsfw/nsfw.php:110
+msgid "NSFW Settings saved."
+msgstr "Paramètres NSFW sauvegardés."
+
+#: ../../addon/nsfw/nsfw.php:207
+msgid "Possible adult content"
+msgstr "Contenu pour adulte probable"
+
+#: ../../addon/nsfw/nsfw.php:211
#, php-format
-msgid "Visit %s's profile [%s]"
-msgstr "Visiter le profil de %s [%s]"
+msgid "%s - view"
+msgstr ""
-#: ../../Zotlabs/Module/Viewconnections.php:104
-msgid "View Connections"
-msgstr "Voir les contacts"
+#: ../../addon/ijpost/ijpost.php:42
+msgid "Post to Insanejournal"
+msgstr "Publier sur InsaneJournal"
-#: ../../Zotlabs/Module/Viewsrc.php:44
-msgid "Source of Item"
-msgstr "Source de l'élément"
+#: ../../addon/ijpost/ijpost.php:73
+msgid "Enable InsaneJournal Post Plugin"
+msgstr "Activer le plugin de publication InsaneJournal"
-#: ../../Zotlabs/Module/Webpages.php:184 ../../Zotlabs/Lib/Apps.php:217
-#: ../../include/nav.php:106 ../../include/conversation.php:1685
-msgid "Webpages"
-msgstr "Pages web"
+#: ../../addon/ijpost/ijpost.php:77
+msgid "InsaneJournal username"
+msgstr "Identifiant InsaneJournal"
-#: ../../Zotlabs/Module/Webpages.php:195 ../../include/page_widgets.php:41
-msgid "Actions"
-msgstr "Actions"
+#: ../../addon/ijpost/ijpost.php:81
+msgid "InsaneJournal password"
+msgstr "Mot de passe InsaneJournal"
-#: ../../Zotlabs/Module/Webpages.php:196 ../../include/page_widgets.php:42
-msgid "Page Link"
-msgstr "Lien vers la page"
+#: ../../addon/ijpost/ijpost.php:85
+msgid "Post to InsaneJournal by default"
+msgstr "Par défaut, publier dans InsaneJournal"
-#: ../../Zotlabs/Module/Webpages.php:197
-msgid "Page Title"
-msgstr "Titre de la page"
+#: ../../addon/ijpost/ijpost.php:89
+msgid "InsaneJournal Post Settings"
+msgstr "Paramètres de publication de InsaneJournal"
-#: ../../Zotlabs/Module/Xchan.php:10
-msgid "Xchan Lookup"
-msgstr "Recherche xchan"
+#: ../../addon/ijpost/ijpost.php:104
+msgid "Insane Journal Settings saved."
+msgstr "Les paramètres d'InsaneJournal ont été sauvegardés"
-#: ../../Zotlabs/Module/Xchan.php:13
-msgid "Lookup xchan beginning with (or webbie): "
-msgstr "Recherche xchan commençant par (ou adresse \"webbie\")&nbsp;:"
+#: ../../addon/js_upload/js_upload.php:44
+msgid "Upload a file"
+msgstr "Téléverser un fichier"
-#: ../../Zotlabs/Lib/Apps.php:204
-msgid "Site Admin"
-msgstr "Administrateur"
+#: ../../addon/js_upload/js_upload.php:45
+msgid "Drop files here to upload"
+msgstr "Glisser les fichiers ici pour téléversement"
-#: ../../Zotlabs/Lib/Apps.php:205
-msgid "Bug Report"
-msgstr ""
+#: ../../addon/js_upload/js_upload.php:47
+msgid "Failed"
+msgstr "Échec"
-#: ../../Zotlabs/Lib/Apps.php:206
-msgid "View Bookmarks"
-msgstr ""
+#: ../../addon/js_upload/js_upload.php:315
+msgid "No files were uploaded."
+msgstr "Aucun fichier n'a été téléversé."
-#: ../../Zotlabs/Lib/Apps.php:207
-msgid "My Chatrooms"
-msgstr ""
+#: ../../addon/js_upload/js_upload.php:322
+msgid "Uploaded file is empty"
+msgstr "Le fichier téléversé est vide"
-#: ../../Zotlabs/Lib/Apps.php:209
-msgid "Firefox Share"
-msgstr ""
+#: ../../addon/js_upload/js_upload.php:335
+msgid "Image exceeds size limit of "
+msgstr "L'image excède la taille limite de"
-#: ../../Zotlabs/Lib/Apps.php:210
-msgid "Remote Diagnostics"
-msgstr ""
+#: ../../addon/js_upload/js_upload.php:347
+msgid "File has an invalid extension, it should be one of "
+msgstr "L'extension du fichier est invalide, elle doit être l'une des suivantes"
-#: ../../Zotlabs/Lib/Apps.php:211 ../../include/features.php:89
-msgid "Suggest Channels"
-msgstr "Suggérer des canaux"
+#: ../../addon/js_upload/js_upload.php:359
+msgid "Upload was cancelled, or server error encountered"
+msgstr "Le téléversement a été annulé, ou le serveur a rencontré une erreur"
-#: ../../Zotlabs/Lib/Apps.php:212 ../../include/nav.php:110
-#: ../../boot.php:1703
-msgid "Login"
-msgstr "Connexion"
+#: ../../addon/dwpost/dwpost.php:42
+msgid "Post to Dreamwidth"
+msgstr "Publier sur Dreamwidth"
-#: ../../Zotlabs/Lib/Apps.php:214 ../../include/nav.php:179
-msgid "Grid"
-msgstr "Réseau"
+#: ../../addon/dwpost/dwpost.php:73
+msgid "Enable Dreamwidth Post Plugin"
+msgstr "Activer le plugin de publication Dreamwidth"
-#: ../../Zotlabs/Lib/Apps.php:218 ../../include/nav.php:182
-msgid "Channel Home"
-msgstr "Mon canal"
+#: ../../addon/dwpost/dwpost.php:77
+msgid "Dreamwidth username"
+msgstr "Nom d'utilisateur Dreamwidth"
-#: ../../Zotlabs/Lib/Apps.php:221 ../../include/nav.php:201
-#: ../../include/conversation.php:1649 ../../include/conversation.php:1652
-msgid "Events"
-msgstr "Événements"
+#: ../../addon/dwpost/dwpost.php:81
+msgid "Dreamwidth password"
+msgstr "Mot de passe Dreamwidth"
-#: ../../Zotlabs/Lib/Apps.php:222 ../../include/nav.php:167
-msgid "Directory"
-msgstr "Annuaire"
+#: ../../addon/dwpost/dwpost.php:85
+msgid "Post to Dreamwidth by default"
+msgstr "Publication avec Dreamwidth par défaut"
-#: ../../Zotlabs/Lib/Apps.php:224 ../../include/nav.php:193
-msgid "Mail"
-msgstr "Messages"
+#: ../../addon/dwpost/dwpost.php:89
+msgid "Dreamwidth Post Settings"
+msgstr "Paramètres de publication Dreamwidth"
-#: ../../Zotlabs/Lib/Apps.php:227 ../../include/nav.php:96
-msgid "Chat"
-msgstr "Clavardage"
+#: ../../addon/firefox/firefox.php:23
+msgid "Install Firefox Sharing Tools"
+msgstr "Installer Firefox Sharing Tools"
-#: ../../Zotlabs/Lib/Apps.php:229
-msgid "Probe"
-msgstr "Sonder"
+#: ../../addon/firefox/firefox.php:34
+msgid "Share content from Firefox to $Projectname"
+msgstr "Partager du contenu depuis Firefox avec $Projectname"
-#: ../../Zotlabs/Lib/Apps.php:230
-msgid "Suggest"
-msgstr "Suggérer"
+#: ../../addon/firefox/firefox.php:37
+msgid "Install Firefox Sharing Tools to this web browser"
+msgstr "Installer Firefox Sharing Tools sur ce navigateur"
-#: ../../Zotlabs/Lib/Apps.php:231
-msgid "Random Channel"
-msgstr "Un canal au hasard"
+#: ../../addon/dirstats/dirstats.php:94
+msgid "Hubzilla Directory Stats"
+msgstr "Statistiques de l'annuaire Hubzilla"
-#: ../../Zotlabs/Lib/Apps.php:232
-msgid "Invite"
-msgstr "Invitation"
+#: ../../addon/dirstats/dirstats.php:95
+msgid "Total Hubs"
+msgstr "Total de Hubs"
-#: ../../Zotlabs/Lib/Apps.php:233 ../../include/widgets.php:1386
-msgid "Features"
-msgstr "Fonctionalités"
+#: ../../addon/dirstats/dirstats.php:97
+msgid "Hubzilla Hubs"
+msgstr "Hubs Hubzilla"
-#: ../../Zotlabs/Lib/Apps.php:235
-msgid "Post"
-msgstr "Envoyer"
+#: ../../addon/dirstats/dirstats.php:99
+msgid "Friendica Hubs"
+msgstr "Hubs Friendica"
-#: ../../Zotlabs/Lib/Apps.php:335
-msgid "Purchase"
-msgstr "Acheter"
+#: ../../addon/dirstats/dirstats.php:101
+msgid "Diaspora Pods"
+msgstr "Pods Diaspora"
-#: ../../Zotlabs/Lib/Chatroom.php:27
-msgid "Missing room name"
-msgstr "Il manque le nom du salon"
+#: ../../addon/dirstats/dirstats.php:103
+msgid "Hubzilla Channels"
+msgstr "Canaux Hubzilla"
-#: ../../Zotlabs/Lib/Chatroom.php:36
-msgid "Duplicate room name"
-msgstr "Un salon avec ce nom existe déjà"
+#: ../../addon/dirstats/dirstats.php:105
+msgid "Friendica Channels"
+msgstr "Canaux Friendica"
-#: ../../Zotlabs/Lib/Chatroom.php:86 ../../Zotlabs/Lib/Chatroom.php:94
-msgid "Invalid room specifier."
-msgstr "Identifiant de salon invalide."
+#: ../../addon/dirstats/dirstats.php:107
+msgid "Diaspora Channels"
+msgstr "Canaux Diaspora"
-#: ../../Zotlabs/Lib/Chatroom.php:126
-msgid "Room not found."
-msgstr "Salon introuvable."
+#: ../../addon/dirstats/dirstats.php:109
+msgid "Aged 35 and above"
+msgstr "Âgé de 35 ans et plus"
-#: ../../Zotlabs/Lib/Chatroom.php:147
-msgid "Room is full"
-msgstr "Le salon est plein"
+#: ../../addon/dirstats/dirstats.php:111
+msgid "Aged 34 and under"
+msgstr "Âgé de 34 et moins"
-#: ../../Zotlabs/Lib/Enotify.php:60 ../../include/network.php:1823
-msgid "$Projectname Notification"
-msgstr "Notification $Projectname"
+#: ../../addon/dirstats/dirstats.php:113
+msgid "Average Age"
+msgstr "Âge moyen"
-#: ../../Zotlabs/Lib/Enotify.php:61 ../../include/network.php:1824
-msgid "$projectname"
-msgstr "$projectname"
+#: ../../addon/dirstats/dirstats.php:115
+msgid "Known Chatrooms"
+msgstr "Salons de discussion connus"
-#: ../../Zotlabs/Lib/Enotify.php:63 ../../include/network.php:1826
-msgid "Thank You,"
-msgstr "Merci,"
+#: ../../addon/dirstats/dirstats.php:117
+msgid "Known Tags"
+msgstr "Étiquettes connues"
-#: ../../Zotlabs/Lib/Enotify.php:65 ../../include/network.php:1828
-#, php-format
-msgid "%s Administrator"
-msgstr "l'administrateur de %s"
+#: ../../addon/dirstats/dirstats.php:119
+msgid ""
+"Please note Diaspora and Friendica statistics are merely those **this "
+"directory** is aware of, and not all those known in the network. This also "
+"applies to chatrooms,"
+msgstr "Veuillez noter que les statistiques de Diaspora et Friendica sont simplement celles dont **ce répertoire** est au courant, et pas toutes celles connues dans le réseau. Cela s'applique également aux salles de discussion,"
-#: ../../Zotlabs/Lib/Enotify.php:100
-#, php-format
-msgid "%s <!item_type!>"
-msgstr "%s <!item_type!>"
+#: ../../addon/mailhost/mailhost.php:36
+msgid "Email notification hub"
+msgstr "Notification par mail du hub"
-#: ../../Zotlabs/Lib/Enotify.php:104
-#, php-format
-msgid "[Hubzilla:Notify] New mail received at %s"
-msgstr "[Hubzilla:Notify] Nouveau courriel reçu à %s"
+#: ../../addon/mailhost/mailhost.php:36
+msgid "Hostname"
+msgstr "Nom d'hôte"
-#: ../../Zotlabs/Lib/Enotify.php:106
-#, php-format
-msgid "%1$s, %2$s sent you a new private message at %3$s."
-msgstr "%1$s, vous avez reçu un message privé sur %3$s, de la part de %2$s."
+#: ../../addon/mailhost/mailhost.php:40
+msgid "Mailhost Settings"
+msgstr "Paramètres mail de l'hôte"
-#: ../../Zotlabs/Lib/Enotify.php:107
-#, php-format
-msgid "%1$s sent you %2$s."
-msgstr "%1$s vous a envoyé %2$s."
+#: ../../addon/mailhost/mailhost.php:54
+msgid "MAILHOST Settings saved."
+msgstr "Paramètres mail de l'hôte sauvegardés."
-#: ../../Zotlabs/Lib/Enotify.php:107
-msgid "a private message"
-msgstr "un message privé"
+#: ../../addon/likebanner/likebanner.php:51
+msgid "Your Webbie:"
+msgstr "Vous êtes Webbie :"
-#: ../../Zotlabs/Lib/Enotify.php:108
-#, php-format
-msgid "Please visit %s to view and/or reply to your private messages."
-msgstr "Merci de visiter %s pour voir et/ou répondre à vos messages privés."
+#: ../../addon/likebanner/likebanner.php:54
+msgid "Fontsize (px):"
+msgstr "Taille de la police (px) :"
-#: ../../Zotlabs/Lib/Enotify.php:164
-#, php-format
-msgid "%1$s, %2$s commented on [zrl=%3$s]a %4$s[/zrl]"
-msgstr "%1$s, %2$s a commenté sur [zrl=%3$s]%4$s[/zrl]"
+#: ../../addon/likebanner/likebanner.php:68
+msgid "Link:"
+msgstr "Lien :"
-#: ../../Zotlabs/Lib/Enotify.php:172
-#, php-format
-msgid "%1$s, %2$s commented on [zrl=%3$s]%4$s's %5$s[/zrl]"
-msgstr "%1$s, %2$s a commenté sur [zrl=%3$s]%5$s de %4$s[/zrl]"
+#: ../../addon/likebanner/likebanner.php:70
+msgid "Like us on Hubzilla"
+msgstr "Aimez-nous sur Hubzilla"
-#: ../../Zotlabs/Lib/Enotify.php:181
-#, php-format
-msgid "%1$s, %2$s commented on [zrl=%3$s]your %4$s[/zrl]"
-msgstr "%1$s, %2$s a commenté [zrl=%3$s]votre %4$s[/zrl]"
+#: ../../addon/likebanner/likebanner.php:72
+msgid "Embed:"
+msgstr "Embarqué :"
-#: ../../Zotlabs/Lib/Enotify.php:192
-#, php-format
-msgid "[Hubzilla:Notify] Comment to conversation #%1$d by %2$s"
-msgstr "[Hubzilla:Notify] Commentaire de %2$s sur conversation #%1$d"
+#: ../../addon/redphotos/redphotos.php:106
+msgid "Photos imported"
+msgstr "Photos importées"
-#: ../../Zotlabs/Lib/Enotify.php:193
-#, php-format
-msgid "%1$s, %2$s commented on an item/conversation you have been following."
-msgstr "%1$s, %2$s a commenté un élément de conversation que vous suivez."
+#: ../../addon/redphotos/redphotos.php:129
+msgid "Redmatrix Photo Album Import"
+msgstr "Import de l'album photo Redmatrix"
-#: ../../Zotlabs/Lib/Enotify.php:196 ../../Zotlabs/Lib/Enotify.php:211
-#: ../../Zotlabs/Lib/Enotify.php:237 ../../Zotlabs/Lib/Enotify.php:255
-#: ../../Zotlabs/Lib/Enotify.php:269
-#, php-format
-msgid "Please visit %s to view and/or reply to the conversation."
-msgstr "Merci de visiter %s pour voir et/ou répondre sur cette conversation."
+#: ../../addon/redphotos/redphotos.php:130
+msgid "This will import all your Redmatrix photo albums to this channel."
+msgstr "Ceci va importer l'intégralité de vos albums photos Redmatrix dans ce canal."
-#: ../../Zotlabs/Lib/Enotify.php:202
-#, php-format
-msgid "[Hubzilla:Notify] %s posted to your profile wall"
-msgstr "[Hubzilla:Notify] %s a publié sur votre profil"
+#: ../../addon/redphotos/redphotos.php:131
+#: ../../addon/redfiles/redfiles.php:121
+msgid "Redmatrix Server base URL"
+msgstr "URL de base du serveur Redmatrix"
-#: ../../Zotlabs/Lib/Enotify.php:204
-#, php-format
-msgid "%1$s, %2$s posted to your profile wall at %3$s"
-msgstr "%1$s, %2$s a publié sur votre profil à %3$s"
+#: ../../addon/redphotos/redphotos.php:132
+#: ../../addon/redfiles/redfiles.php:122
+msgid "Redmatrix Login Username"
+msgstr "Identifiant de connexion Redmatrix"
-#: ../../Zotlabs/Lib/Enotify.php:206
-#, php-format
-msgid "%1$s, %2$s posted to [zrl=%3$s]your wall[/zrl]"
-msgstr "%1$s, %2$s a publié sur [zrl=%3$s]votre profil[/zrl]"
+#: ../../addon/redphotos/redphotos.php:133
+#: ../../addon/redfiles/redfiles.php:123
+msgid "Redmatrix Login Password"
+msgstr "Mot de passe de connexion Redmatrix"
-#: ../../Zotlabs/Lib/Enotify.php:230
-#, php-format
-msgid "[Hubzilla:Notify] %s tagged you"
-msgstr "[Hubzilla:Notify] %s vous a étiqueté"
+#: ../../addon/redphotos/redphotos.php:134
+msgid "Import just this album"
+msgstr "Importer uniquement cet album"
-#: ../../Zotlabs/Lib/Enotify.php:231
-#, php-format
-msgid "%1$s, %2$s tagged you at %3$s"
-msgstr "%1$s, vous avez été étiqueté sur %3$s par %2$s"
+#: ../../addon/redphotos/redphotos.php:134
+msgid "Leave blank to import all albums"
+msgstr "Laisser vide pour importer tous les albums"
-#: ../../Zotlabs/Lib/Enotify.php:232
-#, php-format
-msgid "%1$s, %2$s [zrl=%3$s]tagged you[/zrl]."
-msgstr "%1$s, %2$s [zrl=%3$s]vous a étiqueté[/zrl]."
+#: ../../addon/redphotos/redphotos.php:135
+msgid "Maximum count to import"
+msgstr "Nombre maximum de comptes à importer"
-#: ../../Zotlabs/Lib/Enotify.php:244
-#, php-format
-msgid "[Hubzilla:Notify] %1$s poked you"
-msgstr "[Hubzilla:Notify] %1$s vous a tapoté"
+#: ../../addon/redphotos/redphotos.php:135
+msgid "0 or blank to import all available"
+msgstr "0 ou vide pour importer tout ce qui est disponible"
-#: ../../Zotlabs/Lib/Enotify.php:245
-#, php-format
-msgid "%1$s, %2$s poked you at %3$s"
-msgstr "%1$s, %2$s vous a tapoté sur %3$s"
+#: ../../addon/irc/irc.php:45
+msgid "Channels to auto connect"
+msgstr "Canaux à connecter automatiqument"
-#: ../../Zotlabs/Lib/Enotify.php:246
-#, php-format
-msgid "%1$s, %2$s [zrl=%2$s]poked you[/zrl]."
-msgstr "%1$s, %2$s [zrl=%2$s]vous a tapoté[/zrl]."
+#: ../../addon/irc/irc.php:45 ../../addon/irc/irc.php:49
+msgid "Comma separated list"
+msgstr "Liste séparée par des virgules"
-#: ../../Zotlabs/Lib/Enotify.php:262
-#, php-format
-msgid "[Hubzilla:Notify] %s tagged your post"
-msgstr "[Hubzilla:Notify] %s a étiqueté votre publication"
+#: ../../addon/irc/irc.php:49 ../../addon/irc/irc.php:96
+msgid "Popular Channels"
+msgstr "Canaux populaires"
-#: ../../Zotlabs/Lib/Enotify.php:263
-#, php-format
-msgid "%1$s, %2$s tagged your post at %3$s"
-msgstr "%1$s, %2$s a étiqueté votre publication sur %3$s"
+#: ../../addon/irc/irc.php:53
+msgid "IRC Settings"
+msgstr "Paramètres IRC"
-#: ../../Zotlabs/Lib/Enotify.php:264
-#, php-format
-msgid "%1$s, %2$s tagged [zrl=%3$s]your post[/zrl]"
-msgstr "%1$s, %2$s a étiqueté [zrl=%3$s]votre publication[/zrl]"
+#: ../../addon/irc/irc.php:69
+msgid "IRC settings saved."
+msgstr "Paramètres IRC sauvegardés"
-#: ../../Zotlabs/Lib/Enotify.php:276
-msgid "[Hubzilla:Notify] Introduction received"
-msgstr "[Hubzilla:Notify] Nouvelle présentation"
+#: ../../addon/irc/irc.php:74
+msgid "IRC Chatroom"
+msgstr "Salon de discussion IRC"
-#: ../../Zotlabs/Lib/Enotify.php:277
-#, php-format
-msgid "%1$s, you've received an new connection request from '%2$s' at %3$s"
-msgstr "%1$s, vous avez reçu une demande de contact de '%2$s' sur %3$s"
+#: ../../addon/ljpost/ljpost.php:42
+msgid "Post to LiveJournal"
+msgstr "Publier sur LiveJournal"
-#: ../../Zotlabs/Lib/Enotify.php:278
-#, php-format
-msgid ""
-"%1$s, you've received [zrl=%2$s]a new connection request[/zrl] from %3$s."
-msgstr "%1$s, vous avez reçu [zrl=%2$s]une demande de contact[/zrl] de %3$s."
+#: ../../addon/ljpost/ljpost.php:70
+msgid "Enable LiveJournal Post Plugin"
+msgstr "Activer le plugin de publication LiveJournal"
-#: ../../Zotlabs/Lib/Enotify.php:282 ../../Zotlabs/Lib/Enotify.php:301
-#, php-format
-msgid "You may visit their profile at %s"
-msgstr "Vous pouvez visiter leur profil sur %s"
+#: ../../addon/ljpost/ljpost.php:74
+msgid "LiveJournal username"
+msgstr "Identifiant LiveJournal"
-#: ../../Zotlabs/Lib/Enotify.php:284
-#, php-format
-msgid "Please visit %s to approve or reject the connection request."
-msgstr "Merci de visiter %s avant d'approuver (ou non) cette demande de contact."
+#: ../../addon/ljpost/ljpost.php:78
+msgid "LiveJournal password"
+msgstr "Mot de passe LiveJournal"
-#: ../../Zotlabs/Lib/Enotify.php:291
-msgid "[Hubzilla:Notify] Friend suggestion received"
-msgstr "[Hubzilla:Notify] Nouvel(le) ami(e) suggéré(e)"
+#: ../../addon/ljpost/ljpost.php:82
+msgid "Post to LiveJournal by default"
+msgstr "Par défaut, publier sur LiveJournal"
-#: ../../Zotlabs/Lib/Enotify.php:292
-#, php-format
-msgid "%1$s, you've received a friend suggestion from '%2$s' at %3$s"
-msgstr "%1$s, vous avez reçu une suggestion d'ami(e) de '%2$s' à %3$s"
+#: ../../addon/ljpost/ljpost.php:86
+msgid "LiveJournal Post Settings"
+msgstr "Paramètres de publication LiveJournal"
-#: ../../Zotlabs/Lib/Enotify.php:293
-#, php-format
+#: ../../addon/ljpost/ljpost.php:101
+msgid "LiveJournal Settings saved."
+msgstr "Paramètres LiveJournal sauvegardés."
+
+#: ../../addon/openid/openid.php:49
msgid ""
-"%1$s, you've received [zrl=%2$s]a friend suggestion[/zrl] for %3$s from "
-"%4$s."
-msgstr "%1$s, avez reçu %3$s comme [zrl=%2$s]une suggestion d'ami(e)[/zrl] de %4$s."
+"We encountered a problem while logging in with the OpenID you provided. "
+"Please check the correct spelling of the ID."
+msgstr "Nous avons rencontrons un problème lors de l'identification avec l'OpenID que vous avez fournie. Veuillez vérifier que vous avez correctement écrit votre ID."
-#: ../../Zotlabs/Lib/Enotify.php:299
-msgid "Name:"
-msgstr "Nom&nbsp;:"
+#: ../../addon/openid/openid.php:49
+msgid "The error message was:"
+msgstr "Le message d'erreur était :"
-#: ../../Zotlabs/Lib/Enotify.php:300
-msgid "Photo:"
-msgstr "Photo&nbsp;:"
+#: ../../addon/openid/MysqlProvider.php:52
+msgid "First Name"
+msgstr "Prénom"
-#: ../../Zotlabs/Lib/Enotify.php:303
-#, php-format
-msgid "Please visit %s to approve or reject the suggestion."
-msgstr "Merci de visiter %s pour donner suite (ou non) à cette suggestion."
+#: ../../addon/openid/MysqlProvider.php:53
+msgid "Last Name"
+msgstr "Nom"
-#: ../../Zotlabs/Lib/Enotify.php:518
-msgid "[Hubzilla:Notify]"
-msgstr "[Hubzilla:Notify]"
+#: ../../addon/openid/MysqlProvider.php:54 ../../addon/redred/redred.php:111
+msgid "Nickname"
+msgstr "Surnom"
-#: ../../Zotlabs/Lib/Enotify.php:667
-msgid "created a new post"
-msgstr "a publié un nouveau message"
+#: ../../addon/openid/MysqlProvider.php:55
+msgid "Full Name"
+msgstr "Nom complet"
-#: ../../Zotlabs/Lib/Enotify.php:668
-#, php-format
-msgid "commented on %s's post"
-msgstr "a commenté la publication de %s"
+#: ../../addon/openid/MysqlProvider.php:61
+msgid "Profile Photo 16px"
+msgstr "Photo de profil 16px"
-#: ../../Zotlabs/Lib/ThreadItem.php:95 ../../include/conversation.php:664
-msgid "Private Message"
-msgstr "Message Privé"
+#: ../../addon/openid/MysqlProvider.php:62
+msgid "Profile Photo 32px"
+msgstr "Photo de profil 32px"
-#: ../../Zotlabs/Lib/ThreadItem.php:132 ../../include/conversation.php:656
-msgid "Select"
-msgstr "Sélectionner"
+#: ../../addon/openid/MysqlProvider.php:63
+msgid "Profile Photo 48px"
+msgstr "Photo de profil 48px"
-#: ../../Zotlabs/Lib/ThreadItem.php:136
-msgid "Save to Folder"
-msgstr "Enregistrer dans le dossier"
+#: ../../addon/openid/MysqlProvider.php:64
+msgid "Profile Photo 64px"
+msgstr "Photo de profil 64px"
-#: ../../Zotlabs/Lib/ThreadItem.php:157
-msgid "I will attend"
-msgstr "Je participerai"
+#: ../../addon/openid/MysqlProvider.php:65
+msgid "Profile Photo 80px"
+msgstr "Photo de profil 80px"
-#: ../../Zotlabs/Lib/ThreadItem.php:157
-msgid "I will not attend"
-msgstr "Je ne participerai pas"
+#: ../../addon/openid/MysqlProvider.php:66
+msgid "Profile Photo 128px"
+msgstr "Photo de profil 128px"
-#: ../../Zotlabs/Lib/ThreadItem.php:157
-msgid "I might attend"
-msgstr "Je participerai peut-être"
+#: ../../addon/openid/MysqlProvider.php:67
+msgid "Timezone"
+msgstr "Fuseau horaire"
-#: ../../Zotlabs/Lib/ThreadItem.php:167
-msgid "I agree"
-msgstr "Je suis d'accord"
+#: ../../addon/openid/MysqlProvider.php:70
+msgid "Birth Year"
+msgstr "Années de naissance"
-#: ../../Zotlabs/Lib/ThreadItem.php:167
-msgid "I disagree"
-msgstr "Je ne suis pas d'accord"
+#: ../../addon/openid/MysqlProvider.php:71
+msgid "Birth Month"
+msgstr "Mois de naissance"
-#: ../../Zotlabs/Lib/ThreadItem.php:167
-msgid "I abstain"
-msgstr "Je m'abstiens"
+#: ../../addon/openid/MysqlProvider.php:72
+msgid "Birth Day"
+msgstr "Jour de naissance"
-#: ../../Zotlabs/Lib/ThreadItem.php:218
-msgid "Add Star"
-msgstr "Mettre en avant (étoile)"
+#: ../../addon/openid/MysqlProvider.php:73
+msgid "Birthdate"
+msgstr "Date de naissance"
-#: ../../Zotlabs/Lib/ThreadItem.php:219
-msgid "Remove Star"
-msgstr "Ne plus mettre en avant"
+#: ../../addon/openid/Mod_Openid.php:30
+msgid "OpenID protocol error. No ID returned."
+msgstr "Erreur du protocole OpenID. Aucune ID trouvée."
-#: ../../Zotlabs/Lib/ThreadItem.php:220
-msgid "Toggle Star Status"
-msgstr "(Dés)activer l'étoile"
+#: ../../addon/openid/Mod_Openid.php:188 ../../include/auth.php:286
+msgid "Login failed."
+msgstr "Échec de la connexion."
-#: ../../Zotlabs/Lib/ThreadItem.php:224
-msgid "starred"
-msgstr "mis en avant"
+#: ../../addon/openid/Mod_Id.php:85 ../../include/selectors.php:49
+#: ../../include/selectors.php:66
+msgid "Male"
+msgstr "Homme"
-#: ../../Zotlabs/Lib/ThreadItem.php:234 ../../include/conversation.php:671
-msgid "Message signature validated"
-msgstr "Signature du message validée"
+#: ../../addon/openid/Mod_Id.php:87 ../../include/selectors.php:49
+#: ../../include/selectors.php:66
+msgid "Female"
+msgstr "Femme"
-#: ../../Zotlabs/Lib/ThreadItem.php:235 ../../include/conversation.php:672
-msgid "Message signature incorrect"
-msgstr "Signature du message incorrecte"
+#: ../../addon/randpost/randpost.php:97
+msgid "You're welcome."
+msgstr "Bienvenue."
-#: ../../Zotlabs/Lib/ThreadItem.php:243
-msgid "Add Tag"
-msgstr "Ajouter une étiquette"
+#: ../../addon/randpost/randpost.php:98
+msgid "Ah shucks..."
+msgstr "Ah m…"
-#: ../../Zotlabs/Lib/ThreadItem.php:261 ../../include/taxonomy.php:316
-msgid "like"
-msgstr "aiment"
+#: ../../addon/randpost/randpost.php:99
+msgid "Don't mention it."
+msgstr "De rien."
-#: ../../Zotlabs/Lib/ThreadItem.php:262 ../../include/taxonomy.php:317
-msgid "dislike"
-msgstr "n'aiment pas"
+#: ../../addon/randpost/randpost.php:100
+msgid "&lt;blush&gt;"
+msgstr "&lt;rougit&gt;"
-#: ../../Zotlabs/Lib/ThreadItem.php:266
-msgid "Share This"
-msgstr "Partager"
+#: ../../addon/startpage/startpage.php:109
+msgid "Page to load after login"
+msgstr "Page à charger après l'identification"
-#: ../../Zotlabs/Lib/ThreadItem.php:266
-msgid "share"
-msgstr "partager"
+#: ../../addon/startpage/startpage.php:109
+msgid ""
+"Examples: &quot;apps&quot;, &quot;network?f=&gid=37&quot; (privacy "
+"collection), &quot;channel&quot; or &quot;notifications/system&quot; (leave "
+"blank for default network page (grid)."
+msgstr "Exemples: &quot;apps&quot;, &quot;network?f=&gid=37&quot; (privacy collection), &quot;channel&quot; or &quot;notifications/system&quot; (laisser vide pour la page par défaut du réseau (grille)."
-#: ../../Zotlabs/Lib/ThreadItem.php:275
-msgid "Delivery Report"
-msgstr "Rapport de distribution"
+#: ../../addon/startpage/startpage.php:113
+msgid "Startpage Settings"
+msgstr "Paramètres de la page de démarrage"
-#: ../../Zotlabs/Lib/ThreadItem.php:293
-#, php-format
-msgid "%d comment"
-msgid_plural "%d comments"
-msgstr[0] "%d commentaire"
-msgstr[1] "%d commentaires"
+#: ../../addon/morepokes/morepokes.php:19
+msgid "bitchslap"
+msgstr "giffler"
-#: ../../Zotlabs/Lib/ThreadItem.php:322 ../../Zotlabs/Lib/ThreadItem.php:323
-#, php-format
-msgid "View %s's profile - %s"
-msgstr "Voir le profil de %s - %s"
+#: ../../addon/morepokes/morepokes.php:19
+msgid "bitchslapped"
+msgstr "gifflé(e)"
-#: ../../Zotlabs/Lib/ThreadItem.php:326
-msgid "to"
-msgstr "à"
+#: ../../addon/morepokes/morepokes.php:20
+msgid "shag"
+msgstr "baiser"
-#: ../../Zotlabs/Lib/ThreadItem.php:327
-msgid "via"
-msgstr "via"
+#: ../../addon/morepokes/morepokes.php:20
+msgid "shagged"
+msgstr "baisé"
-#: ../../Zotlabs/Lib/ThreadItem.php:328
-msgid "Wall-to-Wall"
-msgstr "Mur-à-mur"
+#: ../../addon/morepokes/morepokes.php:21
+msgid "patent"
+msgstr "breveté"
-#: ../../Zotlabs/Lib/ThreadItem.php:329
-msgid "via Wall-To-Wall:"
-msgstr "par Mur-à-mur&nbsp;:"
+#: ../../addon/morepokes/morepokes.php:21
+msgid "patented"
+msgstr "être breveté"
-#: ../../Zotlabs/Lib/ThreadItem.php:341 ../../include/conversation.php:719
-#, php-format
-msgid "from %s"
-msgstr "de %s"
+#: ../../addon/morepokes/morepokes.php:22
+msgid "hug"
+msgstr "étreindre"
-#: ../../Zotlabs/Lib/ThreadItem.php:344 ../../include/conversation.php:722
-#, php-format
-msgid "last edited: %s"
-msgstr "dernière modification&nbsp;: %s"
+#: ../../addon/morepokes/morepokes.php:22
+msgid "hugged"
+msgstr "être étreint"
-#: ../../Zotlabs/Lib/ThreadItem.php:345 ../../include/conversation.php:723
-#, php-format
-msgid "Expires: %s"
-msgstr "Expire&nbsp;: %s"
+#: ../../addon/morepokes/morepokes.php:23
+msgid "murder"
+msgstr "assassiner"
-#: ../../Zotlabs/Lib/ThreadItem.php:370
-msgid "Save Bookmarks"
-msgstr "Enregistrer les favoris"
+#: ../../addon/morepokes/morepokes.php:23
+msgid "murdered"
+msgstr "être assassiné"
-#: ../../Zotlabs/Lib/ThreadItem.php:371
-msgid "Add to Calendar"
-msgstr "Ajouter au Calendrier"
+#: ../../addon/morepokes/morepokes.php:24
+msgid "worship"
+msgstr "vénérer"
-#: ../../Zotlabs/Lib/ThreadItem.php:380
-msgid "Mark all seen"
-msgstr "Tout marquer comme vu"
+#: ../../addon/morepokes/morepokes.php:24
+msgid "worshipped"
+msgstr "être vénéré"
-#: ../../Zotlabs/Lib/ThreadItem.php:421 ../../include/js_strings.php:7
-msgid "[+] show all"
-msgstr "[+] voir tous"
+#: ../../addon/morepokes/morepokes.php:25
+msgid "kiss"
+msgstr "embrasser"
-#: ../../Zotlabs/Lib/ThreadItem.php:711 ../../include/conversation.php:1215
-msgid "Bold"
-msgstr "Gras"
+#: ../../addon/morepokes/morepokes.php:25
+msgid "kissed"
+msgstr "embrassé"
-#: ../../Zotlabs/Lib/ThreadItem.php:712 ../../include/conversation.php:1216
-msgid "Italic"
-msgstr "Italique"
+#: ../../addon/morepokes/morepokes.php:26
+msgid "tempt"
+msgstr "tenter"
-#: ../../Zotlabs/Lib/ThreadItem.php:713 ../../include/conversation.php:1217
-msgid "Underline"
-msgstr "Souligné"
+#: ../../addon/morepokes/morepokes.php:26
+msgid "tempted"
+msgstr "tenté"
-#: ../../Zotlabs/Lib/ThreadItem.php:714 ../../include/conversation.php:1218
-msgid "Quote"
-msgstr "Citation"
+#: ../../addon/morepokes/morepokes.php:27
+msgid "raise eyebrows at"
+msgstr "soulever les sourcils à la vue de"
-#: ../../Zotlabs/Lib/ThreadItem.php:715 ../../include/conversation.php:1219
-msgid "Code"
-msgstr "Code"
+#: ../../addon/morepokes/morepokes.php:27
+msgid "raised their eyebrows at"
+msgstr "sourcils soulevés à la vue de"
-#: ../../Zotlabs/Lib/ThreadItem.php:716
-msgid "Image"
-msgstr "Image"
+#: ../../addon/morepokes/morepokes.php:28
+msgid "insult"
+msgstr "insulter"
-#: ../../Zotlabs/Lib/ThreadItem.php:717
-msgid "Insert Link"
-msgstr "Insérer un lien"
+#: ../../addon/morepokes/morepokes.php:28
+msgid "insulted"
+msgstr "insulté"
-#: ../../Zotlabs/Lib/ThreadItem.php:718
-msgid "Video"
-msgstr "Vidéo"
+#: ../../addon/morepokes/morepokes.php:29
+msgid "praise"
+msgstr "louer"
+
+#: ../../addon/morepokes/morepokes.php:29
+msgid "praised"
+msgstr "loué"
+
+#: ../../addon/morepokes/morepokes.php:30
+msgid "be dubious of"
+msgstr "douter de"
+
+#: ../../addon/morepokes/morepokes.php:30
+msgid "was dubious of"
+msgstr "avoir douté de"
+
+#: ../../addon/morepokes/morepokes.php:31
+msgid "eat"
+msgstr "manger"
+
+#: ../../addon/morepokes/morepokes.php:31
+msgid "ate"
+msgstr "a mangé"
+
+#: ../../addon/morepokes/morepokes.php:32
+msgid "giggle and fawn at"
+msgstr "séduire, charmer"
+
+#: ../../addon/morepokes/morepokes.php:32
+msgid "giggled and fawned at"
+msgstr "séduit(e), charmé(e)"
+
+#: ../../addon/morepokes/morepokes.php:33
+msgid "doubt"
+msgstr "doute"
+
+#: ../../addon/morepokes/morepokes.php:33
+msgid "doubted"
+msgstr "a douté"
+
+#: ../../addon/morepokes/morepokes.php:34
+msgid "glare"
+msgstr "jeter un regard"
+
+#: ../../addon/morepokes/morepokes.php:34
+msgid "glared at"
+msgstr "a jeté un regard à "
+
+#: ../../addon/morepokes/morepokes.php:35
+msgid "fuck"
+msgstr "baiser"
+
+#: ../../addon/morepokes/morepokes.php:35
+msgid "fucked"
+msgstr "être baisé"
+
+#: ../../addon/morepokes/morepokes.php:36
+msgid "bonk"
+msgstr "baiser"
+
+#: ../../addon/morepokes/morepokes.php:36
+msgid "bonked"
+msgstr "baisé(e)"
+
+#: ../../addon/morepokes/morepokes.php:37
+msgid "declare undying love for"
+msgstr "Déclarer un amour éternel pour"
+
+#: ../../addon/morepokes/morepokes.php:37
+msgid "declared undying love for"
+msgstr "A déclaré l'amour éternel pour"
-#: ../../include/Import/import_diaspora.php:16
+#: ../../addon/diaspora/diaspora.php:677
+msgid "Diaspora Protocol Settings updated."
+msgstr ""
+
+#: ../../addon/diaspora/diaspora.php:696
+msgid "Enable the Diaspora protocol for this channel"
+msgstr ""
+
+#: ../../addon/diaspora/diaspora.php:700
+msgid "Allow any Diaspora member to comment on your public posts"
+msgstr ""
+
+#: ../../addon/diaspora/diaspora.php:704
+msgid "Prevent your hashtags from being redirected to other sites"
+msgstr ""
+
+#: ../../addon/diaspora/diaspora.php:709
+msgid "Followed hashtags (comma separated, do not include the #)"
+msgstr ""
+
+#: ../../addon/diaspora/diaspora.php:714
+msgid "Diaspora Protocol Settings"
+msgstr ""
+
+#: ../../addon/diaspora/import_diaspora.php:16
msgid "No username found in import file."
-msgstr "Aucun nom d'utilisateur dans le fichier d'import."
+msgstr ""
-#: ../../include/Import/import_diaspora.php:41 ../../include/import.php:50
+#: ../../addon/diaspora/import_diaspora.php:41 ../../include/import.php:62
msgid "Unable to create a unique channel address. Import failed."
msgstr "Impossible de créer une adresse de canal unique. Echec de l'import."
-#: ../../include/dba/dba_driver.php:171
-#, php-format
-msgid "Cannot locate DNS info for database server '%s'"
-msgstr "Impossible de trouver les infos DNS du serveur de BDD '%s'"
+#: ../../addon/gitwiki/Mod_Gitwiki.php:107
+msgid "Error retrieving wiki"
+msgstr "Erreur lors de la récupération du wiki"
-#: ../../include/taxonomy.php:188 ../../include/taxonomy.php:270
-#: ../../include/widgets.php:46 ../../include/widgets.php:429
-#: ../../include/contact_widgets.php:91
-msgid "Categories"
-msgstr "Catégories"
+#: ../../addon/gitwiki/Mod_Gitwiki.php:114
+msgid "Error creating zip file export folder"
+msgstr "Erreur lors de la création du dossier d'exportation du fichier zip"
-#: ../../include/taxonomy.php:228 ../../include/taxonomy.php:249
-msgid "Tags"
-msgstr "Étiquettes"
+#: ../../addon/gitwiki/Mod_Gitwiki.php:132
+msgid "Error downloading wiki: "
+msgstr "Erreur lors du téléchargement du wiki:"
-#: ../../include/taxonomy.php:293
-msgid "Keywords"
-msgstr "Mots-clefs"
+#: ../../addon/testdrive/testdrive.php:104
+#, php-format
+msgid "Your account on %s will expire in a few days."
+msgstr "Votre compte sur %s expirera dans quelques jours."
-#: ../../include/taxonomy.php:314
-msgid "have"
-msgstr "ont"
+#: ../../addon/testdrive/testdrive.php:105
+msgid "Your $Productname test account is about to expire."
+msgstr "Votre compte de test $NomDeProduit est sur le point d'expirer."
-#: ../../include/taxonomy.php:314
-msgid "has"
-msgstr "a"
+#: ../../addon/rainbowtag/rainbowtag.php:81
+msgid "Enable Rainbowtag"
+msgstr "Activer Rainbowtag"
-#: ../../include/taxonomy.php:315
-msgid "want"
-msgstr "veulent"
+#: ../../addon/rainbowtag/rainbowtag.php:85
+msgid "Rainbowtag Settings"
+msgstr "Paramètres Rainbowtag"
-#: ../../include/taxonomy.php:315
-msgid "wants"
-msgstr "veut"
+#: ../../addon/rainbowtag/rainbowtag.php:101
+msgid "Rainbowtag Settings saved."
+msgstr "Paramètres Rainbowtag sauvegardés."
-#: ../../include/taxonomy.php:316
-msgid "likes"
-msgstr "aime"
+#: ../../addon/upload_limits/upload_limits.php:25
+msgid "Show Upload Limits"
+msgstr "Afficher les limites de débit ascendant (upload)"
-#: ../../include/taxonomy.php:317
-msgid "dislikes"
-msgstr "n'aime pas"
+#: ../../addon/upload_limits/upload_limits.php:27
+msgid "Hubzilla configured maximum size: "
+msgstr "Taille maximale configurée par Hubzilla:"
-#: ../../include/event.php:22 ../../include/event.php:69
-#: ../../include/bb2diaspora.php:485
-msgid "l F d, Y \\@ g:i A"
-msgstr "l d F Y \\à G\\hi"
+#: ../../addon/upload_limits/upload_limits.php:28
+msgid "PHP upload_max_filesize: "
+msgstr "PHP upload_max_filesize: "
-#: ../../include/event.php:30 ../../include/event.php:73
-#: ../../include/bb2diaspora.php:491
-msgid "Starts:"
-msgstr "Début&nbsp;:"
+#: ../../addon/upload_limits/upload_limits.php:29
+msgid "PHP post_max_size (must be larger than upload_max_filesize): "
+msgstr "PHP post_max_size (must be larger than upload_max_filesize): "
-#: ../../include/event.php:40 ../../include/event.php:77
-#: ../../include/bb2diaspora.php:499
-msgid "Finishes:"
-msgstr "Fin&nbsp;:"
+#: ../../addon/visage/visage.php:93
+msgid "Recent Channel/Profile Viewers"
+msgstr "Visiteurs récents du canal/profil"
-#: ../../include/event.php:812
-msgid "This event has been added to your calendar."
-msgstr "Cet évènement a été ajouté dans votre calendrier."
+#: ../../addon/visage/visage.php:98
+msgid "This plugin/addon has not been configured."
+msgstr "Cette extension n'a pas été configurée."
-#: ../../include/event.php:1012
-msgid "Not specified"
-msgstr "Non spécifié"
+#: ../../addon/visage/visage.php:99
+#, php-format
+msgid "Please visit the Visage settings on %s"
+msgstr "Veuillez visiter les paramètres de Visage sur %s"
-#: ../../include/event.php:1013
-msgid "Needs Action"
-msgstr "Besoin d'une action"
+#: ../../addon/visage/visage.php:99
+msgid "your feature settings page"
+msgstr "La page des paramètres de vos fonctionnalités"
-#: ../../include/event.php:1014
-msgid "Completed"
-msgstr "Terminé"
+#: ../../addon/visage/visage.php:112
+msgid "No entries."
+msgstr "Aucune entrée."
-#: ../../include/event.php:1015
-msgid "In Process"
-msgstr "En cours"
+#: ../../addon/visage/visage.php:166
+msgid "Enable Visage Visitor Logging"
+msgstr "Activer la connexion Visage Visitor"
-#: ../../include/event.php:1016
-msgid "Cancelled"
-msgstr "Annulé"
+#: ../../addon/visage/visage.php:170
+msgid "Visage Settings"
+msgstr "Paramètres Visage"
-#: ../../include/import.php:29
-msgid ""
-"Cannot create a duplicate channel identifier on this system. Import failed."
-msgstr "L'import a échoué. Un canal existe déjà avec ce nom"
+#: ../../addon/nsabait/nsabait.php:125
+msgid "Nsabait Settings updated."
+msgstr "Les paramètres Nsabait ont été enregistrés."
-#: ../../include/import.php:76
-msgid "Channel clone failed. Import failed."
-msgstr "Echec du clonage du canal. Echec de l'impot."
+#: ../../addon/nsabait/nsabait.php:157
+msgid "Enable NSAbait Plugin"
+msgstr "Activer le plugin NSAbait"
-#: ../../include/items.php:892 ../../include/items.php:937
-msgid "(Unknown)"
-msgstr "(Inconnu)"
+#: ../../addon/nsabait/nsabait.php:161
+msgid "NSAbait Settings"
+msgstr "Paramètres NSAbait"
-#: ../../include/items.php:1136
-msgid "Visible to anybody on the internet."
-msgstr "Visible pour tout le monde sur internet."
+#: ../../addon/mailtest/mailtest.php:19
+msgid "Send test email"
+msgstr "Envoyer un mail de test"
-#: ../../include/items.php:1138
-msgid "Visible to you only."
-msgstr "Visible pour vous seulement."
+#: ../../addon/mailtest/mailtest.php:50 ../../addon/hubwall/hubwall.php:50
+msgid "No recipients found."
+msgstr "Aucun destinataire trouvé."
-#: ../../include/items.php:1140
-msgid "Visible to anybody in this network."
-msgstr "Visible pour tout le monde sur ce réseau."
+#: ../../addon/mailtest/mailtest.php:66
+msgid "Mail sent."
+msgstr "Mail envoyé."
-#: ../../include/items.php:1142
-msgid "Visible to anybody authenticated."
-msgstr "Visible aux utilisateurs authentifiés."
+#: ../../addon/mailtest/mailtest.php:68
+msgid "Sending of mail failed."
+msgstr "L'envoi du mail a échoué."
+
+#: ../../addon/mailtest/mailtest.php:77
+msgid "Mail Test"
+msgstr "Test du mail"
+
+#: ../../addon/mailtest/mailtest.php:96 ../../addon/hubwall/hubwall.php:92
+msgid "Message subject"
+msgstr "Objet du message"
-#: ../../include/items.php:1144
+#: ../../addon/diaspora_reconnect/diaspora_reconnect.php:44
#, php-format
-msgid "Visible to anybody on %s."
-msgstr "Visible pour tous sur %s."
+msgid "Reconnecting %d connections"
+msgstr ""
-#: ../../include/items.php:1146
-msgid "Visible to all connections."
-msgstr "Visible pour tous les contacts."
+#: ../../addon/diaspora_reconnect/diaspora_reconnect.php:63
+msgid "Diaspora Reconnect"
+msgstr ""
-#: ../../include/items.php:1148
-msgid "Visible to approved connections."
-msgstr "Visible aux contacts approuvés."
+#: ../../addon/diaspora_reconnect/diaspora_reconnect.php:65
+msgid ""
+"Use this form to re-establish Diaspora connections which were initially made"
+" from a different hub."
+msgstr ""
-#: ../../include/items.php:1150
-msgid "Visible to specific connections."
-msgstr "Visible pour certains contacts."
+#: ../../addon/diaspora_reconnect/diaspora_reconnect.php:70
+msgid "Reconnect"
+msgstr ""
-#: ../../include/items.php:3909
-msgid "Privacy group is empty."
-msgstr "Groupe d'accès vide."
+#: ../../addon/openstreetmap/openstreetmap.php:146
+msgid "View Larger"
+msgstr "Afficher en plus grand"
-#: ../../include/items.php:3916
-#, php-format
-msgid "Privacy group: %s"
-msgstr "Groupe d'accès&nbsp;: %s"
+#: ../../addon/openstreetmap/openstreetmap.php:169
+msgid "Tile Server URL"
+msgstr "URL de la tuile du serveur"
-#: ../../include/items.php:3928
-msgid "Connection not found."
-msgstr "Contact non trouvé."
+#: ../../addon/openstreetmap/openstreetmap.php:169
+msgid ""
+"A list of <a href=\"http://wiki.openstreetmap.org/wiki/TMS\" "
+"target=\"_blank\">public tile servers</a>"
+msgstr "Une liste de <a href=\"http://wiki.openstreetmap.org/wiki/TMS\" target=\"_blank\">serveurs de cartes publics</a>"
-#: ../../include/items.php:4277
-msgid "profile photo"
-msgstr "photo de profil"
+#: ../../addon/openstreetmap/openstreetmap.php:170
+msgid "Nominatim (reverse geocoding) Server URL"
+msgstr "URL du serveur Nominatim (géocodage inversé)"
-#: ../../include/message.php:20
-msgid "No recipient provided."
-msgstr "Pas de destinataire."
+#: ../../addon/openstreetmap/openstreetmap.php:170
+msgid ""
+"A list of <a href=\"http://wiki.openstreetmap.org/wiki/Nominatim\" "
+"target=\"_blank\">Nominatim servers</a>"
+msgstr "Une liste de <a href=\"http://wiki.openstreetmap.org/wiki/Nominatim\" target=\"_blank\">serveurs Nominatim</a>"
-#: ../../include/message.php:25
-msgid "[no subject]"
-msgstr "[sans objet]"
+#: ../../addon/openstreetmap/openstreetmap.php:171
+msgid "Default zoom"
+msgstr "Zoom par défaut"
-#: ../../include/message.php:45
-msgid "Unable to determine sender."
-msgstr "Impossible de déterminer l'émetteur."
+#: ../../addon/openstreetmap/openstreetmap.php:171
+msgid ""
+"The default zoom level. (1:world, 18:highest, also depends on tile server)"
+msgstr "Le niveau de zoom par défaut. (1: monde, 18: plus élevé, dépend également du serveur de tuiles)"
-#: ../../include/message.php:222
-msgid "Stored post could not be verified."
-msgstr "Le message stocké n'a pas pu être vérifié."
+#: ../../addon/openstreetmap/openstreetmap.php:172
+msgid "Include marker on map"
+msgstr "Inclure le marqueur sur la carte"
-#: ../../include/text.php:428
-msgid "prev"
-msgstr "préc."
+#: ../../addon/openstreetmap/openstreetmap.php:172
+msgid "Include a marker on the map."
+msgstr "Inclure un marqueur sur la carte."
-#: ../../include/text.php:430
-msgid "first"
-msgstr "premier"
+#: ../../addon/msgfooter/msgfooter.php:46 ../../addon/xmpp/xmpp.php:91
+msgid "Save Settings"
+msgstr "Sauvegarder les paramètres"
-#: ../../include/text.php:459
-msgid "last"
-msgstr "dernier"
+#: ../../addon/msgfooter/msgfooter.php:47
+msgid "text to include in all outgoing posts from this site"
+msgstr "Texte à inclure dans tous les messages sortants de ce site"
-#: ../../include/text.php:462
-msgid "next"
-msgstr "Suivant"
+#: ../../addon/rtof/rtof.php:45
+msgid "Post to Friendica"
+msgstr "Publier sur Friendica"
-#: ../../include/text.php:472
-msgid "older"
-msgstr "plus ancien"
+#: ../../addon/rtof/rtof.php:62
+msgid "rtof Settings saved."
+msgstr "Paramètres rtof sauvegardés."
-#: ../../include/text.php:474
-msgid "newer"
-msgstr "plus récent"
+#: ../../addon/rtof/rtof.php:81
+msgid "Allow posting to Friendica"
+msgstr "Autoriser la publication sur Friendica"
-#: ../../include/text.php:863
-msgid "No connections"
-msgstr "Pas de relations."
+#: ../../addon/rtof/rtof.php:85
+msgid "Send public postings to Friendica by default"
+msgstr "Par défaut, envoyer les publications publiques sur Friendica"
-#: ../../include/text.php:888
-#, php-format
-msgid "View all %s connections"
-msgstr "Voir les %s contacts"
+#: ../../addon/rtof/rtof.php:89
+msgid "Friendica API Path"
+msgstr "Chemin de l'API Friendica"
-#: ../../include/text.php:1033 ../../include/text.php:1038
-msgid "poke"
-msgstr "tapoter"
+#: ../../addon/rtof/rtof.php:89 ../../addon/redred/redred.php:103
+msgid "https://{sitename}/api"
+msgstr "https://{nomdusite}/api"
-#: ../../include/text.php:1033 ../../include/text.php:1038
-#: ../../include/conversation.php:243
-msgid "poked"
-msgstr "a tapoté"
+#: ../../addon/rtof/rtof.php:93
+msgid "Friendica login name"
+msgstr "Identifiant de connexion Friendica"
-#: ../../include/text.php:1039
-msgid "ping"
-msgstr "ping"
+#: ../../addon/rtof/rtof.php:97
+msgid "Friendica password"
+msgstr "Mot de passe de connexion Friendica"
-#: ../../include/text.php:1039
-msgid "pinged"
-msgstr "pingé"
+#: ../../addon/rtof/rtof.php:101
+msgid "Hubzilla to Friendica Post Settings"
+msgstr "Paramètres de publication de Hubzilla vers Friendica"
-#: ../../include/text.php:1040
-msgid "prod"
-msgstr "encourager"
+#: ../../addon/jappixmini/jappixmini.php:305 ../../include/channel.php:1137
+#: ../../include/channel.php:1294
+msgid "Status:"
+msgstr "État&nbsp;:"
-#: ../../include/text.php:1040
-msgid "prodded"
-msgstr "encouragé"
+#: ../../addon/jappixmini/jappixmini.php:309
+msgid "Activate addon"
+msgstr "Activer l'extension"
-#: ../../include/text.php:1041
-msgid "slap"
-msgstr "giffler"
+#: ../../addon/jappixmini/jappixmini.php:313
+msgid "Hide Jappixmini Chat-Widget from the webinterface"
+msgstr "Cacher le widget de chat Jappixmini de l'interface web"
-#: ../../include/text.php:1041
-msgid "slapped"
-msgstr "gifflé(e)"
+#: ../../addon/jappixmini/jappixmini.php:318
+msgid "Jabber username"
+msgstr "Identifiant Jabber"
-#: ../../include/text.php:1042
-msgid "finger"
-msgstr "pointer"
+#: ../../addon/jappixmini/jappixmini.php:324
+msgid "Jabber server"
+msgstr "Serveur Jabber"
-#: ../../include/text.php:1042
-msgid "fingered"
-msgstr "pointé"
+#: ../../addon/jappixmini/jappixmini.php:330
+msgid "Jabber BOSH host URL"
+msgstr "Adresse hôte pour Jabber BOSH"
-#: ../../include/text.php:1043
-msgid "rebuff"
-msgstr "rejetter"
+#: ../../addon/jappixmini/jappixmini.php:337
+msgid "Jabber password"
+msgstr "Mot de passe Jabber"
-#: ../../include/text.php:1043
-msgid "rebuffed"
-msgstr "rejeté"
+#: ../../addon/jappixmini/jappixmini.php:343
+msgid "Encrypt Jabber password with Hubzilla password"
+msgstr "Chiffrer le mot de passe Jabber avec le mot de passe Hubzilla"
-#: ../../include/text.php:1055
-msgid "happy"
-msgstr "heureux"
+#: ../../addon/jappixmini/jappixmini.php:347 ../../addon/redred/redred.php:115
+msgid "Hubzilla password"
+msgstr "Mot de passe Hubzilla"
-#: ../../include/text.php:1056
-msgid "sad"
-msgstr "triste"
+#: ../../addon/jappixmini/jappixmini.php:351
+#: ../../addon/jappixmini/jappixmini.php:355
+msgid "Approve subscription requests from Hubzilla contacts automatically"
+msgstr "Approuver automatiquement les demandes de connexion des contacts Hubzilla"
-#: ../../include/text.php:1057
-msgid "mellow"
-msgstr "mélancolique"
+#: ../../addon/jappixmini/jappixmini.php:359
+msgid "Purge internal list of jabber addresses of contacts"
+msgstr "Purger la liste interne des adresses jabber des contacts"
-#: ../../include/text.php:1058
-msgid "tired"
-msgstr "fatigué"
+#: ../../addon/jappixmini/jappixmini.php:364
+msgid "Configuration Help"
+msgstr "Aide pour la configuration"
-#: ../../include/text.php:1059
-msgid "perky"
-msgstr "impertinent"
+#: ../../addon/jappixmini/jappixmini.php:371
+msgid "Jappix Mini Settings"
+msgstr "Paramètres de Jappix mini"
-#: ../../include/text.php:1060
-msgid "angry"
-msgstr "en colère"
+#: ../../addon/superblock/superblock.php:112
+msgid "Currently blocked"
+msgstr "Actuellement bloqué"
-#: ../../include/text.php:1061
-msgid "stupefied"
-msgstr "stupéfait"
+#: ../../addon/superblock/superblock.php:114
+msgid "No channels currently blocked"
+msgstr "Aucun canal n'est actuellement bloqué"
-#: ../../include/text.php:1062
-msgid "puzzled"
-msgstr "perplexe"
+#: ../../addon/superblock/superblock.php:120
+msgid "\"Superblock\" Settings"
+msgstr "Paramètres \"Superblock\""
-#: ../../include/text.php:1063
-msgid "interested"
-msgstr "intéressé"
+#: ../../addon/superblock/superblock.php:345
+msgid "Block Completely"
+msgstr "Bloquer complètement"
-#: ../../include/text.php:1064
-msgid "bitter"
-msgstr "amer"
+#: ../../addon/superblock/superblock.php:394
+msgid "superblock settings updated"
+msgstr "Les paramètres du superblock ont été mis à jour"
-#: ../../include/text.php:1065
-msgid "cheerful"
-msgstr "plein d'entrain"
+#: ../../addon/nofed/nofed.php:42
+msgid "Federate"
+msgstr "Fédérer"
-#: ../../include/text.php:1066
-msgid "alive"
-msgstr "vivant"
+#: ../../addon/nofed/nofed.php:56
+msgid "nofed Settings saved."
+msgstr "Les paramètres nfed ont été enregistrés."
-#: ../../include/text.php:1067
-msgid "annoyed"
-msgstr "agaçé"
+#: ../../addon/nofed/nofed.php:72
+msgid "Allow Federation Toggle"
+msgstr "Autoriser la fédération avec Toggle"
-#: ../../include/text.php:1068
-msgid "anxious"
-msgstr "anxieux"
+#: ../../addon/nofed/nofed.php:76
+msgid "Federate posts by default"
+msgstr "Par défaut, fédérer les publications."
-#: ../../include/text.php:1069
-msgid "cranky"
-msgstr "énervé"
+#: ../../addon/nofed/nofed.php:80
+msgid "NoFed Settings"
+msgstr "Paramètres NoFed"
-#: ../../include/text.php:1070
-msgid "disturbed"
-msgstr "perturbé"
+#: ../../addon/redred/redred.php:45
+msgid "Post to Red"
+msgstr "Publier sur Red"
-#: ../../include/text.php:1071
-msgid "frustrated"
-msgstr "frustré"
+#: ../../addon/redred/redred.php:60
+msgid "Channel is required."
+msgstr "Un canal est requis."
-#: ../../include/text.php:1072
-msgid "depressed"
-msgstr "déprimé"
+#: ../../addon/redred/redred.php:76
+msgid "redred Settings saved."
+msgstr "Paramètres redred sauvegardés."
-#: ../../include/text.php:1073
-msgid "motivated"
-msgstr "motivé"
+#: ../../addon/redred/redred.php:95
+msgid "Allow posting to another Hubzilla Channel"
+msgstr "Autoriser la publication sur un autre canal Hubzilla"
-#: ../../include/text.php:1074
-msgid "relaxed"
-msgstr "détendu"
+#: ../../addon/redred/redred.php:99
+msgid "Send public postings to Hubzilla channel by default"
+msgstr "Par défaut, envoyer les publications publiques sur le canal Hubzilla"
-#: ../../include/text.php:1075
-msgid "surprised"
-msgstr "surpris"
+#: ../../addon/redred/redred.php:103
+msgid "Hubzilla API Path"
+msgstr "Chemin de l'API Hubzilla"
-#: ../../include/text.php:1257 ../../include/js_strings.php:70
-msgid "Monday"
-msgstr "Lundi"
+#: ../../addon/redred/redred.php:107
+msgid "Hubzilla login name"
+msgstr "Identifiant de connexion Hubzilla"
-#: ../../include/text.php:1257 ../../include/js_strings.php:71
-msgid "Tuesday"
-msgstr "Mardi"
+#: ../../addon/redred/redred.php:111
+msgid "Hubzilla channel name"
+msgstr "Nom du canal Hubzilla"
-#: ../../include/text.php:1257 ../../include/js_strings.php:72
-msgid "Wednesday"
-msgstr "Mercredi"
+#: ../../addon/redred/redred.php:119
+msgid "Hubzilla Crosspost Settings"
+msgstr "Paramètres Crosspost Hubzilla"
-#: ../../include/text.php:1257 ../../include/js_strings.php:73
-msgid "Thursday"
-msgstr "Jeudi"
+#: ../../addon/logrot/logrot.php:36
+msgid "Logfile archive directory"
+msgstr "Répertoire d'archivage du fichier journal"
-#: ../../include/text.php:1257 ../../include/js_strings.php:74
-msgid "Friday"
-msgstr "Vendredi"
+#: ../../addon/logrot/logrot.php:36
+msgid "Directory to store rotated logs"
+msgstr "Répertoire où stocker les journaux de rotation"
-#: ../../include/text.php:1257 ../../include/js_strings.php:75
-msgid "Saturday"
-msgstr "Samedi"
+#: ../../addon/logrot/logrot.php:37
+msgid "Logfile size in bytes before rotating"
+msgstr "Taille du fichier journal en octets avant la rotation"
-#: ../../include/text.php:1257 ../../include/js_strings.php:69
-msgid "Sunday"
-msgstr "Dimanche"
+#: ../../addon/logrot/logrot.php:38
+msgid "Number of logfiles to retain"
+msgstr "Nombre de fichiers de journal à conserver"
-#: ../../include/text.php:1261 ../../include/js_strings.php:45
-msgid "January"
-msgstr "Janvier"
+#: ../../addon/frphotos/frphotos.php:91
+msgid "Friendica Photo Album Import"
+msgstr "Importation de l'album photo Friendica "
-#: ../../include/text.php:1261 ../../include/js_strings.php:46
-msgid "February"
-msgstr "Février"
+#: ../../addon/frphotos/frphotos.php:92
+msgid "This will import all your Friendica photo albums to this Red channel."
+msgstr "Ceci importera toutes vos albums photos Friendica dans ce canal Hubzilla."
-#: ../../include/text.php:1261 ../../include/js_strings.php:47
-msgid "March"
-msgstr "Mars"
+#: ../../addon/frphotos/frphotos.php:93
+msgid "Friendica Server base URL"
+msgstr "URL de base du serveur Friendica"
-#: ../../include/text.php:1261 ../../include/js_strings.php:48
-msgid "April"
-msgstr "Avril"
+#: ../../addon/frphotos/frphotos.php:94
+msgid "Friendica Login Username"
+msgstr "Identifiant de connexion Friendica"
-#: ../../include/text.php:1261
-msgid "May"
-msgstr "Mai"
+#: ../../addon/frphotos/frphotos.php:95
+msgid "Friendica Login Password"
+msgstr "Mot de passe de connexion Friendica"
-#: ../../include/text.php:1261 ../../include/js_strings.php:50
-msgid "June"
-msgstr "Juin"
+#: ../../addon/donate/donate.php:21
+msgid "Project Servers and Resources"
+msgstr "Serveurs et ressources du projet"
-#: ../../include/text.php:1261 ../../include/js_strings.php:51
-msgid "July"
-msgstr "Juillet"
+#: ../../addon/donate/donate.php:22
+msgid "Project Creator and Tech Lead"
+msgstr "Créateur et Responsable Technique du projet"
-#: ../../include/text.php:1261 ../../include/js_strings.php:52
-msgid "August"
-msgstr "Août"
+#: ../../addon/donate/donate.php:23
+msgid "Admin, developer, directorymin, support bloke"
+msgstr "Administrateur, développeur, responsable d'annuaire, équipe support"
-#: ../../include/text.php:1261 ../../include/js_strings.php:53
-msgid "September"
-msgstr "Septembre"
+#: ../../addon/donate/donate.php:50
+msgid ""
+"And the hundreds of other people and organisations who helped make the "
+"Hubzilla possible."
+msgstr "Et les centaines d'autres personnes et organisations qui ont contribué à rendre le Hubzilla possible."
-#: ../../include/text.php:1261 ../../include/js_strings.php:54
-msgid "October"
-msgstr "Octobre"
+#: ../../addon/donate/donate.php:53
+msgid ""
+"The Redmatrix/Hubzilla projects are provided primarily by volunteers giving "
+"their time and expertise - and often paying out of pocket for services they "
+"share with others."
+msgstr "Les projets Redmatrix / Hubzilla sont fournis principalement par des bénévoles qui donnent de leur temps et de leur expertise - et paient souvent de leur poche pour des services qu'ils partagent avec d'autres."
-#: ../../include/text.php:1261 ../../include/js_strings.php:55
-msgid "November"
-msgstr "Novembre"
+#: ../../addon/donate/donate.php:54
+msgid ""
+"There is no corporate funding and no ads, and we do not collect and sell "
+"your personal information. (We don't control your personal information - "
+"<strong>you do</strong>.)"
+msgstr "Il n'y a ni financement d'entreprise ni publicités, et nous ne recueillons ni ne vendons vos données personnelles. (Nous ne contrôlons pas vos informations personnelles - vous le faites !)"
-#: ../../include/text.php:1261 ../../include/js_strings.php:56
-msgid "December"
-msgstr "Décembre"
+#: ../../addon/donate/donate.php:55
+msgid ""
+"Help support our ground-breaking work in decentralisation, web identity, and"
+" privacy."
+msgstr "Aider à soutenir notre travail novateur en matière de décentralisation, d'identité Web et de confidentialité."
-#: ../../include/text.php:1338 ../../include/text.php:1342
-msgid "Unknown Attachment"
-msgstr "Pièce jointe inconnue"
+#: ../../addon/donate/donate.php:57
+msgid ""
+"Your donations keep servers and services running and also helps us to "
+"provide innovative new features and continued development."
+msgstr "Vos dons maintiennent les serveurs et les services en marche et nous aident également à fournir de nouvelles fonctionnalités innovantes et un développement continu."
-#: ../../include/text.php:1344
-msgid "unknown"
-msgstr "Inconnu"
+#: ../../addon/donate/donate.php:60
+msgid "Donate"
+msgstr "Donner"
-#: ../../include/text.php:1380
-msgid "remove category"
-msgstr "supprimer la catégorie"
+#: ../../addon/donate/donate.php:62
+msgid ""
+"Choose a project, developer, or public hub to support with a one-time "
+"donation"
+msgstr "Choisissez un projet, un développeur ou un hub public à soutenir à l'aide d'un don unique"
-#: ../../include/text.php:1457
-msgid "remove from file"
-msgstr "retirer du fichier"
+#: ../../addon/donate/donate.php:63
+msgid "Donate Now"
+msgstr "Donner maintenant"
-#: ../../include/text.php:1753 ../../include/text.php:1824
-msgid "default"
-msgstr "défaut"
+#: ../../addon/donate/donate.php:64
+msgid ""
+"<strong><em>Or</em></strong> become a project sponsor (Hubzilla Project "
+"only)"
+msgstr "Or devenez un sponsor du projet (projet Hubzilla uniquement)"
-#: ../../include/text.php:1761
-msgid "Page layout"
-msgstr "Mise en page"
+#: ../../addon/donate/donate.php:65
+msgid ""
+"Please indicate if you would like your first name or full name (or nothing) "
+"to appear in our sponsor listing"
+msgstr "Veuillez indiquer si vous souhaitez que votre nom ou prénom (ou rien) apparaisse dans la liste de nos sponsors."
-#: ../../include/text.php:1761
-msgid "You can create your own with the layouts tool"
-msgstr "Créez les vôtres avec les outils de mise en page"
+#: ../../addon/donate/donate.php:66
+msgid "Sponsor"
+msgstr "Sponsors"
-#: ../../include/text.php:1803
-msgid "Page content type"
-msgstr "Type de contenu de la page"
+#: ../../addon/donate/donate.php:69
+msgid "Special thanks to: "
+msgstr "Remerciements particuliers à :"
-#: ../../include/text.php:1836
-msgid "Select an alternate language"
-msgstr "Choisir une langue alternative"
+#: ../../addon/chords/Mod_Chords.php:44
+msgid ""
+"This is a fairly comprehensive and complete guitar chord dictionary which "
+"will list most of the available ways to play a certain chord, starting from "
+"the base of the fingerboard up to a few frets beyond the twelfth fret "
+"(beyond which everything repeats). A couple of non-standard tunings are "
+"provided for the benefit of slide players, etc."
+msgstr "Ceci est un dictionnaire d'accords de guitare assez complet et facile qui énumère la plupart des manières possibles de jouer un certain accord, à partir de la base de la touche jusqu'à quelques frettes au-delà de la douzième frette (au-delà de laquelle tout se répète). Un couple d'accordages non standard sont fournis au profit des joueurs de diapositives, etc."
-#: ../../include/text.php:1953
-msgid "activity"
-msgstr "activité"
+#: ../../addon/chords/Mod_Chords.php:46
+msgid ""
+"Chord names start with a root note (A-G) and may include sharps (#) and "
+"flats (b). This software will parse most of the standard naming conventions "
+"such as maj, min, dim, sus(2 or 4), aug, with optional repeating elements."
+msgstr "Les noms des accords commencent par une note racine (A-G) et peuvent inclure des dièses (#) et des bémols (b). Ce logiciel analysera la plupart des conventions de dénomination standard telles que maj, min, dim, sus (2 ou 4), aug, avec des éléments répétitifs facultatifs."
-#: ../../include/text.php:2262
-msgid "Design Tools"
-msgstr "Outils de conception"
+#: ../../addon/chords/Mod_Chords.php:48
+msgid ""
+"Valid examples include A, A7, Am7, Amaj7, Amaj9, Ammaj7, Aadd4, Asus2Add4, "
+"E7b13b11 ..."
+msgstr "Exemples valides comprennent A, A7, Am7, Amaj7, Amaj9, Ammaj7, Aadd4, Asus2Add4, E7b13b11 ..."
-#: ../../include/text.php:2268
-msgid "Pages"
-msgstr "Pages"
+#: ../../addon/chords/Mod_Chords.php:51
+msgid "Guitar Chords"
+msgstr "Acords de guitar"
-#: ../../include/widgets.php:103
-msgid "System"
-msgstr "Système"
+#: ../../addon/chords/Mod_Chords.php:52
+msgid "The complete online chord dictionary"
+msgstr "Le dictionnaire en ligne complet des accords"
-#: ../../include/widgets.php:106
-msgid "New App"
-msgstr ""
+#: ../../addon/chords/Mod_Chords.php:57
+msgid "Tuning"
+msgstr "Réglage"
-#: ../../include/widgets.php:154
-msgid "Suggestions"
-msgstr "Suggestions"
+#: ../../addon/chords/Mod_Chords.php:58
+msgid "Chord name: example: Em7"
+msgstr "Nom d'accord. Exemple : Em7."
-#: ../../include/widgets.php:155
-msgid "See more..."
-msgstr "Voir plus..."
+#: ../../addon/chords/Mod_Chords.php:59
+msgid "Show for left handed stringing"
+msgstr "Montrer pour les gauchers"
-#: ../../include/widgets.php:175
-#, php-format
-msgid "You have %1$.0f of %2$.0f allowed connections."
-msgstr "Vous avez %1$.0f sur %2$.0f contacts autorisés."
+#: ../../addon/chords/chords.php:33
+msgid "Quick Reference"
+msgstr "Référence rapide"
-#: ../../include/widgets.php:181
-msgid "Add New Connection"
-msgstr "Ajouter un nouveau contact"
+#: ../../addon/libertree/libertree.php:38
+msgid "Post to Libertree"
+msgstr "Publier sur Libertree"
-#: ../../include/widgets.php:182
-msgid "Enter channel address"
-msgstr "Saisissez l'adresse du canal"
+#: ../../addon/libertree/libertree.php:69
+msgid "Enable Libertree Post Plugin"
+msgstr "Activer le plugin de publication Libertree"
-#: ../../include/widgets.php:183
-msgid "Examples: bob@example.com, https://example.com/barbara"
-msgstr "Exemples&nbsp;: pierre@exemple.com, https://exemple.com/sophie"
+#: ../../addon/libertree/libertree.php:73
+msgid "Libertree API token"
+msgstr "Jeton de l'API Libertree"
-#: ../../include/widgets.php:199
-msgid "Notes"
-msgstr "Notes"
+#: ../../addon/libertree/libertree.php:77
+msgid "Libertree site URL"
+msgstr "Adresse du site Libertree"
-#: ../../include/widgets.php:273
-msgid "Remove term"
-msgstr "Retirer le terme"
+#: ../../addon/libertree/libertree.php:81
+msgid "Post to Libertree by default"
+msgstr "Par défaut, publier sur Libertree"
-#: ../../include/widgets.php:281 ../../include/features.php:84
-msgid "Saved Searches"
-msgstr "Recherches sauvegardées"
+#: ../../addon/libertree/libertree.php:85
+msgid "Libertree Post Settings"
+msgstr "Paramètres de publication pour Libertree"
-#: ../../include/widgets.php:282 ../../include/group.php:316
-msgid "add"
-msgstr "ajouter"
+#: ../../addon/libertree/libertree.php:99
+msgid "Libertree Settings saved."
+msgstr "Paramètres de Libertree sauvegardés."
-#: ../../include/widgets.php:310 ../../include/contact_widgets.php:53
-#: ../../include/features.php:98
-msgid "Saved Folders"
-msgstr "Dossiers sauvegardés"
+#: ../../addon/flattrwidget/flattrwidget.php:45
+msgid "Flattr this!"
+msgstr "Flattr this!"
-#: ../../include/widgets.php:313 ../../include/widgets.php:432
-#: ../../include/contact_widgets.php:56 ../../include/contact_widgets.php:94
-msgid "Everything"
-msgstr "Tout"
+#: ../../addon/flattrwidget/flattrwidget.php:83
+msgid "Flattr widget settings updated."
+msgstr "Les paramètres du widget Flattr ont été mis à jour"
-#: ../../include/widgets.php:354
-msgid "Archives"
-msgstr "Archives"
+#: ../../addon/flattrwidget/flattrwidget.php:100
+msgid "Flattr user"
+msgstr "Utilisateur de Flattr"
-#: ../../include/widgets.php:516
-msgid "Refresh"
-msgstr "Actualiser"
+#: ../../addon/flattrwidget/flattrwidget.php:104
+msgid "URL of the Thing to flattr"
+msgstr "URL de ce que vous voulez flattr"
-#: ../../include/widgets.php:556
-msgid "Account settings"
-msgstr "Paramètres du compte"
+#: ../../addon/flattrwidget/flattrwidget.php:104
+msgid "If empty channel URL is used"
+msgstr "Si une url vide est utilisée"
-#: ../../include/widgets.php:562
-msgid "Channel settings"
-msgstr "Paramètres du canal"
+#: ../../addon/flattrwidget/flattrwidget.php:108
+msgid "Title of the Thing to flattr"
+msgstr "Titre de ce que vous voulez flattr"
-#: ../../include/widgets.php:571
-msgid "Additional features"
-msgstr "Fonctionnalités supplémentaires"
+#: ../../addon/flattrwidget/flattrwidget.php:108
+msgid "If empty \"channel name on The Hubzilla\" will be used"
+msgstr "Si vide, \"nom du canal sur Hubzilla\" sera utilisé"
-#: ../../include/widgets.php:578
-msgid "Feature/Addon settings"
-msgstr "Paramètres des extensions/greffons"
+#: ../../addon/flattrwidget/flattrwidget.php:112
+msgid "Static or dynamic flattr button"
+msgstr "Statique ou dynamique bouton Flattr"
-#: ../../include/widgets.php:584
-msgid "Display settings"
-msgstr "Paramètres d'affichage"
+#: ../../addon/flattrwidget/flattrwidget.php:112
+msgid "static"
+msgstr "statique"
-#: ../../include/widgets.php:591
-msgid "Manage locations"
-msgstr ""
+#: ../../addon/flattrwidget/flattrwidget.php:112
+msgid "dynamic"
+msgstr "dynamique"
-#: ../../include/widgets.php:600
-msgid "Export channel"
-msgstr "Exporter le canal"
+#: ../../addon/flattrwidget/flattrwidget.php:116
+msgid "Alignment of the widget"
+msgstr "Alignement du widget"
-#: ../../include/widgets.php:607
-msgid "Connected apps"
-msgstr "Applications connectées"
+#: ../../addon/flattrwidget/flattrwidget.php:116
+msgid "left"
+msgstr "gauche"
-#: ../../include/widgets.php:622
-msgid "Premium Channel Settings"
-msgstr "Paramètres de canal VIP"
+#: ../../addon/flattrwidget/flattrwidget.php:116
+msgid "right"
+msgstr "droite"
-#: ../../include/widgets.php:651
-msgid "Private Mail Menu"
-msgstr "Menu des messages privés"
+#: ../../addon/flattrwidget/flattrwidget.php:120
+msgid "Enable Flattr widget"
+msgstr "Activer le widget Flattr"
-#: ../../include/widgets.php:653
-msgid "Combined View"
-msgstr "Vue combinée"
+#: ../../addon/flattrwidget/flattrwidget.php:124
+msgid "Flattr Widget Settings"
+msgstr "Paramètres du widget Flattr"
-#: ../../include/widgets.php:658 ../../include/nav.php:196
-msgid "Inbox"
-msgstr "Boîte de réception"
+#: ../../addon/statusnet/statusnet.php:143
+msgid "Post to GNU social"
+msgstr "Publier sur GNU-social"
-#: ../../include/widgets.php:663 ../../include/nav.php:197
-msgid "Outbox"
-msgstr "Boîte d'envoi"
+#: ../../addon/statusnet/statusnet.php:195
+msgid ""
+"Please contact your site administrator.<br />The provided API URL is not "
+"valid."
+msgstr "Veuillez contacter l'administrateur de votre site. L'URL de l'API n'est pas valide."
-#: ../../include/widgets.php:668 ../../include/nav.php:198
-msgid "New Message"
-msgstr "Nouveau message"
+#: ../../addon/statusnet/statusnet.php:232
+msgid "We could not contact the GNU social API with the Path you entered."
+msgstr "Nous ne pouvons pas contacter l'API de GNU-social avec le chemin que vous avez entré."
-#: ../../include/widgets.php:685 ../../include/widgets.php:697
-msgid "Conversations"
-msgstr "Conversations"
+#: ../../addon/statusnet/statusnet.php:266
+msgid "GNU social settings updated."
+msgstr "Les paramètres GNU-social ont été mis à jour."
-#: ../../include/widgets.php:689
-msgid "Received Messages"
-msgstr "Messages reçus"
+#: ../../addon/statusnet/statusnet.php:310
+msgid "Globally Available GNU social OAuthKeys"
+msgstr "Les OAuthKeys GNU-social sont globalement disponibles."
-#: ../../include/widgets.php:693
-msgid "Sent Messages"
-msgstr "Messages envoyés"
+#: ../../addon/statusnet/statusnet.php:312
+msgid ""
+"There are preconfigured OAuth key pairs for some GNU social servers "
+"available. If you are using one of them, please use these credentials.<br "
+"/>If not feel free to connect to any other GNU social instance (see below)."
+msgstr "Il existe des paires de clés OAuth préconfigurées pour certains serveurs GNU-social disponibles. Si vous utilisez l'un d'eux, utilisez ces informations d'identification.\nSi vous ne voulez pas vous connecter à une autre instance GNU social (voir ci-dessous)."
-#: ../../include/widgets.php:707
-msgid "No messages."
-msgstr "Pas de message."
+#: ../../addon/statusnet/statusnet.php:327
+msgid "Provide your own OAuth Credentials"
+msgstr "Fournissez vos propres informations d'identification OAuth"
-#: ../../include/widgets.php:725
-msgid "Delete conversation"
-msgstr "Supprimer la conversation"
+#: ../../addon/statusnet/statusnet.php:329
+msgid ""
+"No consumer key pair for GNU social found. Register your Hubzilla Account as"
+" an desktop client on your GNU social account, copy the consumer key pair "
+"here and enter the API base root.<br />Before you register your own OAuth "
+"key pair ask the administrator if there is already a key pair for this "
+"Hubzilla installation at your favourite GNU social installation."
+msgstr "Aucune paire de clés utilisateur n'a été trouvée pour GNU-social. Enregistrer votre compte Hubzilla en tant que client de bureau sur votre compte GNU-social, puis copier la paire de clés utilisateur ici et entrer la racine de base de l'API.\nAvant d'enregistrer votre propre paire de clés OAuth, demandez à l'administrateur s'il existe déjà une paire de clés pour cette installation de Hubzilla à votre installation GNU-social préférée."
-#: ../../include/widgets.php:751
-msgid "Events Menu"
-msgstr "Menu Evènements"
+#: ../../addon/statusnet/statusnet.php:333
+msgid "OAuth Consumer Key"
+msgstr "Clé d'utilisateur OAuth"
-#: ../../include/widgets.php:752
-msgid "Day View"
-msgstr "Vue Jour"
+#: ../../addon/statusnet/statusnet.php:337
+msgid "OAuth Consumer Secret"
+msgstr "Secret d'utilisateur OAuth"
-#: ../../include/widgets.php:753
-msgid "Week View"
-msgstr "Vue Semaine"
+#: ../../addon/statusnet/statusnet.php:341
+msgid "Base API Path"
+msgstr "Chemin de l'API de base"
-#: ../../include/widgets.php:754
-msgid "Month View"
-msgstr "Vue Mois"
+#: ../../addon/statusnet/statusnet.php:341
+msgid "Remember the trailing /"
+msgstr "N'oubliez pas le / final"
-#: ../../include/widgets.php:766
-msgid "Events Tools"
-msgstr "Outils Evènements"
+#: ../../addon/statusnet/statusnet.php:345
+msgid "GNU social application name"
+msgstr "Nom de l'application GNU-social"
-#: ../../include/widgets.php:767
-msgid "Export Calendar"
-msgstr "Exporter le calendrier"
+#: ../../addon/statusnet/statusnet.php:368
+msgid ""
+"To connect to your GNU social account click the button below to get a "
+"security code from GNU social which you have to copy into the input box "
+"below and submit the form. Only your <strong>public</strong> posts will be "
+"posted to GNU social."
+msgstr "Pour vous connecter à votre compte GNU-social, cliquez sur le bouton ci-dessous pour obtenir un code de sécurité de GNU-social. Vous devez le copier dans la zone de saisie ci-dessous, puis soumettre le formulaire. Seuls vos messages publics seront visibles sur GNU-social."
-#: ../../include/widgets.php:768
-msgid "Import Calendar"
-msgstr "Importer un calendrier"
+#: ../../addon/statusnet/statusnet.php:370
+msgid "Log in with GNU social"
+msgstr "Vous connecter avec GNU-social"
-#: ../../include/widgets.php:842 ../../include/conversation.php:1662
-#: ../../include/conversation.php:1665
-msgid "Chatrooms"
-msgstr "Salons de clavardage"
+#: ../../addon/statusnet/statusnet.php:373
+msgid "Copy the security code from GNU social here"
+msgstr "Copier ici le code de sécurité de GNU-social."
-#: ../../include/widgets.php:846
-msgid "Overview"
-msgstr ""
+#: ../../addon/statusnet/statusnet.php:383
+msgid "Cancel Connection Process"
+msgstr "Annuler le processus de connexion"
-#: ../../include/widgets.php:853
-msgid "Chat Members"
-msgstr ""
+#: ../../addon/statusnet/statusnet.php:385
+msgid "Current GNU social API is"
+msgstr "L'API GNU-social courante est"
-#: ../../include/widgets.php:876
-msgid "Bookmarked Chatrooms"
-msgstr "Salons favoris"
+#: ../../addon/statusnet/statusnet.php:389
+msgid "Cancel GNU social Connection"
+msgstr "Annuler la connexion GNU-social"
-#: ../../include/widgets.php:899
-msgid "Suggested Chatrooms"
-msgstr "Salons suggérés"
+#: ../../addon/statusnet/statusnet.php:401 ../../addon/twitter/twitter.php:232
+msgid "Currently connected to: "
+msgstr "Actuellement connecté à :"
-#: ../../include/widgets.php:1044 ../../include/widgets.php:1156
-msgid "photo/image"
-msgstr "photo/image"
+#: ../../addon/statusnet/statusnet.php:406
+msgid ""
+"<strong>Note</strong>: Due your privacy settings (<em>Hide your profile "
+"details from unknown viewers?</em>) the link potentially included in public "
+"postings relayed to GNU social will lead the visitor to a blank page "
+"informing the visitor that the access to your profile has been restricted."
+msgstr "Remarque : en raison de vos paramètres de confidentialité (masquer les détails de votre profil aux visiteurs inconnus? ), le lien potentiellement inclus dans les annonces publiques relayées sur GNU-social amènera le visiteur à une page vierge informant le visiteur que l'accès à votre profil a été restreint."
-#: ../../include/widgets.php:1099
-msgid "Click to show more"
-msgstr "Cliquer pour voir plus"
+#: ../../addon/statusnet/statusnet.php:411
+msgid "Allow posting to GNU social"
+msgstr "Autoriser la publication sur GNU-social"
-#: ../../include/widgets.php:1250
-msgid "Rating Tools"
-msgstr "Outils d'évaluation"
+#: ../../addon/statusnet/statusnet.php:411
+msgid ""
+"If enabled your public postings can be posted to the associated GNU-social "
+"account"
+msgstr "Si cette option est activée, vos publications publiques peuvent être publiées sur le compte GNU-social associé."
-#: ../../include/widgets.php:1254 ../../include/widgets.php:1256
-msgid "Rate Me"
-msgstr "M'évaluer"
+#: ../../addon/statusnet/statusnet.php:415
+msgid "Post to GNU social by default"
+msgstr "Par défaut, publier sur GNU-social"
-#: ../../include/widgets.php:1259
-msgid "View Ratings"
-msgstr "Voir mes évaluations"
+#: ../../addon/statusnet/statusnet.php:415
+msgid ""
+"If enabled your public postings will be posted to the associated GNU-social "
+"account by default"
+msgstr "Si cette option est activée, par défaut, vos publications publiques seront publiées sur le compte GNU-social associé"
-#: ../../include/widgets.php:1316
-msgid "Forums"
-msgstr "Membres du forum"
+#: ../../addon/statusnet/statusnet.php:424 ../../addon/twitter/twitter.php:255
+msgid "Clear OAuth configuration"
+msgstr "Effacer la configuration OAuth"
-#: ../../include/widgets.php:1345
-msgid "Tasks"
-msgstr "Tâches"
+#: ../../addon/statusnet/statusnet.php:432
+msgid "GNU social Post Settings"
+msgstr "Paramètres de publication GNU-social"
-#: ../../include/widgets.php:1354
-msgid "Documentation"
-msgstr "Documentation"
+#: ../../addon/statusnet/statusnet.php:891
+msgid "API URL"
+msgstr "URL de l'API"
-#: ../../include/widgets.php:1356
-msgid "Project/Site Information"
-msgstr "Information sur le site/projet"
+#: ../../addon/statusnet/statusnet.php:894
+msgid "Application name"
+msgstr "Nom de l'application"
-#: ../../include/widgets.php:1357
-msgid "For Members"
-msgstr "Pour les membres"
+#: ../../addon/qrator/qrator.php:48
+msgid "QR code"
+msgstr "QR code"
-#: ../../include/widgets.php:1358
-msgid "For Administrators"
-msgstr "Pour les administrateurs"
+#: ../../addon/qrator/qrator.php:63
+msgid "QR Generator"
+msgstr "Générateur de QRcode"
-#: ../../include/widgets.php:1359
-msgid "For Developers"
-msgstr "Pour les développeurs"
+#: ../../addon/qrator/qrator.php:64
+msgid "Enter some text"
+msgstr "Entrer du texte"
-#: ../../include/widgets.php:1383 ../../include/widgets.php:1421
-msgid "Member registrations waiting for confirmation"
-msgstr ""
+#: ../../addon/chess/chess.php:276 ../../addon/chess/chess.php:433
+msgid "Invalid game."
+msgstr "Jeu invalide"
-#: ../../include/widgets.php:1389
-msgid "Inspect queue"
-msgstr "Analyser la file d'attente"
+#: ../../addon/chess/chess.php:282 ../../addon/chess/chess.php:439
+msgid "You are not a player in this game."
+msgstr "Vous n'êtes pas un joueur de ce jeu."
-#: ../../include/widgets.php:1391
-msgid "DB updates"
-msgstr "Mises à jour BDD"
+#: ../../addon/chess/chess.php:315
+msgid "You must be a local channel to create a game."
+msgstr "Vous devez être un canal local pour créer un jeu."
-#: ../../include/widgets.php:1416 ../../include/nav.php:216
-msgid "Admin"
-msgstr "Administrateur"
+#: ../../addon/chess/chess.php:333
+msgid "You must select one opponent that is not yourself."
+msgstr "Vous devez sélectionner un adversaire qui ne soit pas vous-même."
-#: ../../include/widgets.php:1417
-msgid "Plugin Features"
-msgstr "Fonctionnalités des greffons"
+#: ../../addon/chess/chess.php:336
+msgid "Creating new game..."
+msgstr "en train de créer un nouveau jeu…"
-#: ../../include/follow.php:27
-msgid "Channel is blocked on this site."
-msgstr "Ce canal est bloqué sur ce site."
+#: ../../addon/chess/chess.php:342
+msgid "You must select white or black."
+msgstr "Vous devez sélectionner les blancs ou les noirs."
-#: ../../include/follow.php:32
-msgid "Channel location missing."
-msgstr "Emplacement du canal introuvable."
+#: ../../addon/chess/chess.php:349
+msgid "Error creating new game."
+msgstr "Erreur lors de la création du nouveau jeu."
-#: ../../include/follow.php:81
-msgid "Response from remote channel was incomplete."
-msgstr "La réponse du canal distant était incomplète."
+#: ../../addon/chess/chess.php:381 ../../include/channel.php:897
+msgid "Requested channel is not available."
+msgstr "Canal demandé non disponible."
-#: ../../include/follow.php:98
-msgid "Channel was deleted and no longer exists."
-msgstr "Le canal a été supprimé et n'existe plus."
+#: ../../addon/chess/chess.php:395
+msgid "You must select a local channel /chess/channelname"
+msgstr "Vous devez sélectionner un canal local /échecs/nomducanal"
-#: ../../include/follow.php:154 ../../include/follow.php:190
-msgid "Protocol disabled."
-msgstr "Protocole désactivé."
+#: ../../addon/chess/chess.php:923
+msgid "Enable notifications"
+msgstr "Activer les notifications"
-#: ../../include/follow.php:178
-msgid "Channel discovery failed."
-msgstr "La tentative d'accéder au canal a échoué."
+#: ../../addon/twitter/twitter.php:99
+msgid "Post to Twitter"
+msgstr "Publier sur Twitter"
-#: ../../include/follow.php:216
-msgid "Cannot connect to yourself."
-msgstr "Ne peut pas se connecter à vous."
+#: ../../addon/twitter/twitter.php:154
+msgid "Twitter settings updated."
+msgstr "Les paramètres de Twitter ont été mis à jour."
-#: ../../include/bookmarks.php:35
-#, php-format
-msgid "%1$s's bookmarks"
-msgstr "Favoris de %1$s"
+#: ../../addon/twitter/twitter.php:183
+msgid ""
+"No consumer key pair for Twitter found. Please contact your site "
+"administrator."
+msgstr "Aucune paire de clés d'utilisateur pour Twitter n'a été trouvée. Veuillez contacter l'administrateur de votre site."
-#: ../../include/api.php:1336
-msgid "Public Timeline"
-msgstr "Fil public"
-
-#: ../../include/bbcode.php:123 ../../include/bbcode.php:844
-#: ../../include/bbcode.php:847 ../../include/bbcode.php:852
-#: ../../include/bbcode.php:855 ../../include/bbcode.php:858
-#: ../../include/bbcode.php:861 ../../include/bbcode.php:866
-#: ../../include/bbcode.php:869 ../../include/bbcode.php:874
-#: ../../include/bbcode.php:877 ../../include/bbcode.php:880
-#: ../../include/bbcode.php:883
-msgid "Image/photo"
-msgstr "Image/photo"
+#: ../../addon/twitter/twitter.php:205
+msgid ""
+"At this Hubzilla instance the Twitter plugin was enabled but you have not "
+"yet connected your account to your Twitter account. To do so click the "
+"button below to get a PIN from Twitter which you have to copy into the input"
+" box below and submit the form. Only your <strong>public</strong> posts will"
+" be posted to Twitter."
+msgstr "Dans cette instance de Hubzilla, le plugin Twitter a été activé, mais vous n'avez pas encore connecté votre compte à votre compte Twitter. Pour ce faire, cliquez sur le bouton ci-dessous pour obtenir un code PIN de Twitter que vous devez copier dans la zone de saisie ci-dessous, puis soumettre le formulaire. Seuls vos messages publics seront publiés sur Twitter."
-#: ../../include/bbcode.php:162 ../../include/bbcode.php:894
-msgid "Encrypted content"
-msgstr "Contenu chiffré"
+#: ../../addon/twitter/twitter.php:207
+msgid "Log in with Twitter"
+msgstr "Connectez-vous avec votre compte Twitter"
-#: ../../include/bbcode.php:178
-#, php-format
-msgid "Install %s element: "
-msgstr "Installer %s élément"
+#: ../../addon/twitter/twitter.php:210
+msgid "Copy the PIN from Twitter here"
+msgstr "Copier ici le PIN fourni par Twitter"
-#: ../../include/bbcode.php:182
-#, php-format
+#: ../../addon/twitter/twitter.php:237
msgid ""
-"This post contains an installable %s element, however you lack permissions "
-"to install it on this site."
-msgstr "Ce message contient un élément installable %s, mais vous n'avez pas l'autorisation de l'installer sur ce site."
+"<strong>Note:</strong> Due your privacy settings (<em>Hide your profile "
+"details from unknown viewers?</em>) the link potentially included in public "
+"postings relayed to Twitter will lead the visitor to a blank page informing "
+"the visitor that the access to your profile has been restricted."
+msgstr "Note : En raison de vos paramètres de confidentialité (Masquer les détails de votre profil aux visiteurs inconnus?), le lien potentiellement inclus dans les annonces publiques relayées vers Twitter amènera le visiteur à une page vierge l'informant que l'accès à votre profil a été restreint."
-#: ../../include/bbcode.php:254
-#, php-format
-msgid "%1$s wrote the following %2$s %3$s"
-msgstr "%1$s a écrit %2$s qui suit %3$s"
+#: ../../addon/twitter/twitter.php:242
+msgid "Allow posting to Twitter"
+msgstr "Autoriser la publication sur Twitter"
-#: ../../include/bbcode.php:331 ../../include/bbcode.php:339
-msgid "Click to open/close"
-msgstr "Cliquer pour ouvrir/fermer"
+#: ../../addon/twitter/twitter.php:242
+msgid ""
+"If enabled your public postings can be posted to the associated Twitter "
+"account"
+msgstr "Si cette option est activée, vos publications publiques peuvent être publiées sur le compte Twitter associé."
-#: ../../include/bbcode.php:339
-msgid "spoiler"
-msgstr ""
+#: ../../addon/twitter/twitter.php:246
+msgid "Send public postings to Twitter by default"
+msgstr "Par défaut, envoyer vos publications publiques sur Twitter."
-#: ../../include/bbcode.php:585
-msgid "Different viewers will see this text differently"
-msgstr "Ce texte aura un rendu différent en fonction des utilisateurs"
+#: ../../addon/twitter/twitter.php:246
+msgid ""
+"If enabled your public postings will be posted to the associated Twitter "
+"account by default"
+msgstr "Si cette option est activée, par défaut, vos publications publiques seront publiées sur le compte Twitter associé."
-#: ../../include/bbcode.php:832
-msgid "$1 wrote:"
-msgstr "$1 a écrit&nbsp;:"
+#: ../../addon/twitter/twitter.php:264
+msgid "Twitter Post Settings"
+msgstr "Paramètres des publications Twitter"
-#: ../../include/dir_fns.php:141
-msgid "Directory Options"
-msgstr "Options d'annuaire"
+#: ../../addon/smileybutton/smileybutton.php:273
+msgid "Deactivate the feature"
+msgstr "Désactiver la fonctionnalité"
-#: ../../include/dir_fns.php:143
-msgid "Safe Mode"
-msgstr "Mode sûr"
+#: ../../addon/smileybutton/smileybutton.php:277
+msgid "Hide the button and show the smilies directly."
+msgstr "Cacher le bouton et afficher les émoticônes directement."
-#: ../../include/dir_fns.php:144
-msgid "Public Forums Only"
-msgstr "Les forums publics uniquement"
+#: ../../addon/smileybutton/smileybutton.php:281
+msgid "Smileybutton Settings"
+msgstr "Paramètres du bouton des émoticônes"
-#: ../../include/dir_fns.php:145
-msgid "This Website Only"
-msgstr "Ce site uniquement"
+#: ../../addon/piwik/piwik.php:85
+msgid ""
+"This website is tracked using the <a href='http://www.piwik.org'>Piwik</a> "
+"analytics tool."
+msgstr "Ce site web est surveillé grâce à l'outil d'analyse <a href='http://www.piwik.org'>Piwik</a>."
-#: ../../include/security.php:383
+#: ../../addon/piwik/piwik.php:88
+#, php-format
msgid ""
-"The form security token was not correct. This probably happened because the "
-"form has been opened for too long (>3 hours) before submitting it."
-msgstr "Le formulaire n'est plus sécurisé, probablement parce qu'il est ouvert depuis trop longtemps (plus de 3 heures)."
+"If you do not want that your visits are logged this way you <a href='%s'>can"
+" set a cookie to prevent Piwik from tracking further visits of the site</a> "
+"(opt-out)."
+msgstr "Si vous ne souhaitez pas que vos visites soient enregistrées de cette façon, <a href='%s'>vous pouvez\ndéfinir un cookie pour empêcher Piwik de suivre davantage de visites du site</a> (opt-out)."
-#: ../../include/nav.php:82 ../../include/nav.php:113 ../../boot.php:1702
-msgid "Logout"
-msgstr "Déconnexion"
+#: ../../addon/piwik/piwik.php:96
+msgid "Piwik Base URL"
+msgstr "URL de base Piwik"
-#: ../../include/nav.php:82 ../../include/nav.php:113
-msgid "End this session"
-msgstr "Mettre fin à la session"
+#: ../../addon/piwik/piwik.php:96
+msgid ""
+"Absolute path to your Piwik installation. (without protocol (http/s), with "
+"trailing slash)"
+msgstr "Chemin absolu vers votre installation Piwik. (sans le http/s, avec antislash)"
-#: ../../include/nav.php:85 ../../include/nav.php:144
-msgid "Home"
-msgstr "Mon canal"
+#: ../../addon/piwik/piwik.php:97
+msgid "Site ID"
+msgstr "ID du site"
-#: ../../include/nav.php:85
-msgid "Your posts and conversations"
-msgstr "Vos publications et conversations"
+#: ../../addon/piwik/piwik.php:98
+msgid "Show opt-out cookie link?"
+msgstr "Afficher le lien opt-out du cookie ?"
-#: ../../include/nav.php:86
-msgid "Your profile page"
-msgstr "Votre profil"
+#: ../../addon/piwik/piwik.php:99
+msgid "Asynchronous tracking"
+msgstr "Traqueur asynchrone"
-#: ../../include/nav.php:88
-msgid "Manage/Edit profiles"
-msgstr "Gérer/modifier les profils"
+#: ../../addon/piwik/piwik.php:100
+msgid "Enable frontend JavaScript error tracking"
+msgstr "Activer le traqueur d'erreur du frontend JavaScript"
-#: ../../include/nav.php:90 ../../include/channel.php:941
-msgid "Edit Profile"
-msgstr "Éditeur de profil"
+#: ../../addon/piwik/piwik.php:100
+msgid "This feature requires Piwik >= 2.2.0"
+msgstr "Cette fonctionnalité requiert une version de Piwik >=2.2.0"
-#: ../../include/nav.php:90
-msgid "Edit your profile"
-msgstr "Modifier votre profil"
+#: ../../addon/tour/tour.php:75
+msgid "Edit your profile and change settings."
+msgstr "Éditer votre profil et changer les paramètres."
-#: ../../include/nav.php:92
-msgid "Your photos"
-msgstr "Vos photos"
+#: ../../addon/tour/tour.php:76
+msgid "Click here to see activity from your connections."
+msgstr "Cliquer ici pour voir l'activité de vos connections."
-#: ../../include/nav.php:93
-msgid "Your files"
-msgstr "Vos fichiers"
+#: ../../addon/tour/tour.php:77
+msgid "Click here to see your channel home."
+msgstr "Cliquer ici pour voir votre canal principal."
-#: ../../include/nav.php:96
-msgid "Your chatrooms"
-msgstr "Vos salons"
+#: ../../addon/tour/tour.php:78
+msgid "You can access your private messages from here."
+msgstr "Vous pouvez accéder à vos messages privés à partir d'ici."
-#: ../../include/nav.php:102 ../../include/conversation.php:1675
-msgid "Bookmarks"
-msgstr "Favoris"
+#: ../../addon/tour/tour.php:79
+msgid "Create new events here."
+msgstr "Créer de nouveaux événements ici."
-#: ../../include/nav.php:102
-msgid "Your bookmarks"
-msgstr "Vos favoris"
+#: ../../addon/tour/tour.php:80
+msgid ""
+"You can accept new connections and change permissions for existing ones "
+"here. You can also e.g. create groups of contacts."
+msgstr "Vous pouvez accepter de nouvelles connections et changer les permissions des connections existantes. Vous pouvez également créer des groupes de contacts."
-#: ../../include/nav.php:106
-msgid "Your webpages"
-msgstr "Vos pages web"
+#: ../../addon/tour/tour.php:81
+msgid "System notifications will arrive here"
+msgstr "Les notifications du système arriveront ici."
-#: ../../include/nav.php:110
-msgid "Sign in"
-msgstr "Connexion"
+#: ../../addon/tour/tour.php:82
+msgid "Search for content and users"
+msgstr "Rechercher du contenu ou des utilisateurs"
-#: ../../include/nav.php:127
-#, php-format
-msgid "%s - click to logout"
-msgstr "%s - cliquer ici pour déconnecter"
+#: ../../addon/tour/tour.php:83
+msgid "Browse for new contacts"
+msgstr "Rechercher de nouveaux contacts"
-#: ../../include/nav.php:130
-msgid "Remote authentication"
-msgstr "Authentification distante"
+#: ../../addon/tour/tour.php:84
+msgid "Launch installed apps"
+msgstr "Démarrer des applications installées"
-#: ../../include/nav.php:130
-msgid "Click to authenticate to your home hub"
-msgstr "S'authentifier auprès de votre hub principal"
+#: ../../addon/tour/tour.php:85
+msgid "Looking for help? Click here."
+msgstr "Un peu d'aide ? Cliquer ici."
-#: ../../include/nav.php:144
-msgid "Home Page"
-msgstr "Page d'accueil"
+#: ../../addon/tour/tour.php:86
+msgid ""
+"New events have occurred in your network. Click here to see what has "
+"happened!"
+msgstr "De nouveaux événement se sont produits dans votre réseau. Cliquer ici pour voir ce qui s'est passé !"
-#: ../../include/nav.php:147
-msgid "Create an account"
-msgstr "Créer un compte"
+#: ../../addon/tour/tour.php:87
+msgid "You have received a new private message. Click here to see from who!"
+msgstr "Vous avez reçu un nouveau message privé. Cliquer ici pour voir qui vous écrit !"
-#: ../../include/nav.php:159
-msgid "Help and documentation"
-msgstr "Aide et documentation"
+#: ../../addon/tour/tour.php:88
+msgid "There are events this week. Click here too see which!"
+msgstr "Il y a des événements cette semaine. Cliquer ici pour voir lesquels !"
-#: ../../include/nav.php:163
-msgid "Applications, utilities, links, games"
-msgstr "Applications, utilitaires, liens, jeux"
+#: ../../addon/tour/tour.php:89
+msgid "You have received a new introduction. Click here to see who!"
+msgstr "Vous avez reçu une nouvelle demande de relation. Cliquer ici pour voir de qui !"
-#: ../../include/nav.php:165
-msgid "Search site @name, #tag, ?docs, content"
-msgstr "Recherche @nom, #tag, contenu"
+#: ../../addon/tour/tour.php:90
+msgid ""
+"There is a new system notification. Click here to see what has happened!"
+msgstr "Vous avez reçu une notification du système. Cliquer ici pour voir ce qui se passe !"
-#: ../../include/nav.php:167
-msgid "Channel Directory"
-msgstr "Annuaire des canaux"
+#: ../../addon/tour/tour.php:93
+msgid "Click here to share text, images, videos and sound."
+msgstr "Cliquer ici pour partager du texte, des images, des vidéos ou du son."
-#: ../../include/nav.php:179
-msgid "Your grid"
-msgstr "Votre réseau"
+#: ../../addon/tour/tour.php:94
+msgid "You can write an optional title for your update (good for long posts)."
+msgstr "Vous pouvez ajouter à votre mise à jour un titre facultatif (pratique pour de longues publications)."
-#: ../../include/nav.php:180
-msgid "Mark all grid notifications seen"
-msgstr "Marquer toutes les notifications du réseau comme vues"
+#: ../../addon/tour/tour.php:95
+msgid "Entering some categories here makes it easier to find your post later."
+msgstr "Renseigner certaines catégories ici permet de retrouver plus facilement votre message plus tard."
-#: ../../include/nav.php:182
-msgid "Channel home"
-msgstr "Mon canal"
+#: ../../addon/tour/tour.php:96
+msgid "Share photos, links, location, etc."
+msgstr "Partager des photos, des liens, des localisations, etc."
-#: ../../include/nav.php:183
-msgid "Mark all channel notifications seen"
-msgstr "Marquer toutes les notifications du canal comme vues"
+#: ../../addon/tour/tour.php:97
+msgid ""
+"Only want to share content for a while? Make it expire at a certain date."
+msgstr "Envie de partager un contenu pour une durée limitée ? Faites-le expirer à une certaine date."
-#: ../../include/nav.php:189
-msgid "Notices"
-msgstr "Notifications"
+#: ../../addon/tour/tour.php:98
+msgid "You can password protect content."
+msgstr "Vous pouvez protéger un contenu avec un mot de passe."
-#: ../../include/nav.php:189
-msgid "Notifications"
-msgstr "Notifications"
+#: ../../addon/tour/tour.php:99
+msgid "Choose who you share with."
+msgstr "Choisir avec qui vous partagez."
-#: ../../include/nav.php:190
-msgid "See all notifications"
-msgstr "Voir toutes les notifications"
+#: ../../addon/tour/tour.php:101
+msgid "Click here when you are done."
+msgstr "Cliquer ici quand vous avez fini."
-#: ../../include/nav.php:193
-msgid "Private mail"
-msgstr "Messages privés"
+#: ../../addon/tour/tour.php:104
+msgid "Adjust from which channels posts should be displayed."
+msgstr "Préciser de quels canaux les publications seront affichées."
-#: ../../include/nav.php:194
-msgid "See all private messages"
-msgstr "Voir tous les messages privés"
+#: ../../addon/tour/tour.php:105
+msgid "Only show posts from channels in the specified privacy group."
+msgstr "Afficher uniquement les messages des canaux appartenant au groupe de contacts spécifié."
-#: ../../include/nav.php:195
-msgid "Mark all private messages seen"
-msgstr "Marquer tous les messages privés comme vus"
+#: ../../addon/tour/tour.php:109
+msgid "Easily find posts containing tags (keywords preceded by the \"#\" symbol)."
+msgstr "Trouvez facilement des publications contenant des tags (mots-clés précédés du symbole \"#\")."
-#: ../../include/nav.php:201
-msgid "Event Calendar"
-msgstr "Calendrier des événements"
+#: ../../addon/tour/tour.php:110
+msgid "Easily find posts in given category."
+msgstr "Trouvez facilement des publications dans une catégorie donnée."
-#: ../../include/nav.php:202
-msgid "See all events"
-msgstr "Voir tous les événements"
+#: ../../addon/tour/tour.php:111
+msgid "Easily find posts by date."
+msgstr "Trouvez facilement des publications en fonction de leur date."
-#: ../../include/nav.php:203
-msgid "Mark all events seen"
-msgstr "Marquer tous les événements comme vus"
+#: ../../addon/tour/tour.php:112
+msgid ""
+"Suggested users who have volounteered to be shown as suggestions, and who we"
+" think you might find interesting."
+msgstr "Voici des utilisateurs que vous pourriez trouver intéressants. Ces utilisateurs se sont portés volontaires pour être affichés comme exemples."
-#: ../../include/nav.php:206
-msgid "Manage Your Channels"
-msgstr "Gérer vos canaux"
+#: ../../addon/tour/tour.php:113
+msgid "Here you see channels you have connected to."
+msgstr "Retrouvez ici les canaux auxquels vous vous êtes connectés."
-#: ../../include/nav.php:208
-msgid "Account/Channel Settings"
-msgstr "Paramètres du Compte/Canal"
+#: ../../addon/tour/tour.php:114
+msgid "Save your search so you can repeat it at a later date."
+msgstr "Enregistrer votre recherche de façon à pouvoir la répéter plus tard."
-#: ../../include/nav.php:216
-msgid "Site Setup and Configuration"
-msgstr "Configuration du site"
+#: ../../addon/tour/tour.php:117
+msgid ""
+"If you see this icon you can be sure that the sender is who it say it is. It"
+" is normal that it is not always possible to verify the sender, so the icon "
+"will be missing sometimes. There is usually no need to worry about that."
+msgstr "Si vous voyez cette icône, vous pouvez être sûr que l'expéditeur est qui il dit qu'il est. Il est normal qu'il ne soit pas toujours possible de vérifier l'expéditeur, donc l'icône manquera parfois. Il n'est généralement pas nécessaire de s'inquiéter à ce sujet."
-#: ../../include/nav.php:247 ../../include/conversation.php:851
-msgid "Loading..."
-msgstr "Chargement..."
+#: ../../addon/tour/tour.php:118
+msgid ""
+"Danger! It seems someone tried to forge a message! This message is not "
+"necessarily from who it says it is from!"
+msgstr "Attention ! Il semble que quelqu'un a essayé de contrefaire un message ! Ce message n'a pas nécessairement été envoyé par la personne annoncée !"
-#: ../../include/nav.php:252
-msgid "@name, #tag, ?doc, content"
-msgstr "@nom, #étiquette, ?doc, contenu"
+#: ../../addon/tour/tour.php:125
+msgid ""
+"Welcome to Hubzilla! Would you like to see a tour of the UI?</p> <p>You can "
+"pause it at any time and continue where you left off by reloading the page, "
+"or navigting to another page.</p><p>You can also advance by pressing the "
+"return key"
+msgstr "Bienvenue sur Hubzilla! Voulez-vous faire un tour de l'interface utilisateur? Vous pouvez le mettre en pause à tout moment et continuer où vous l'avez laissé en rechargeant la page ou en naviguant vers une autre page. Vous pouvez également avancer en appuyant sur la touche de retour."
-#: ../../include/nav.php:253
-msgid "Please wait..."
-msgstr "Merci de patienter..."
+#: ../../addon/sendzid/sendzid.php:25
+msgid "Extended Identity Sharing"
+msgstr "Partage d'identification étendu"
-#: ../../include/connections.php:95
-msgid "New window"
-msgstr "Nouvelle fenêtre"
+#: ../../addon/sendzid/sendzid.php:26
+msgid ""
+"Share your identity with all websites on the internet. When disabled, "
+"identity is only shared with sites in the matrix."
+msgstr "Partagez votre identification avec tous les sites Web sur Internet. Lorsqu'elle est désactivée, l'identification n'est partagée qu'avec les sites de la matrice."
-#: ../../include/connections.php:96
-msgid "Open the selected location in a different window or browser tab"
-msgstr "Ouvrir l'emplacement dans une fenêtre ou un onglet différent"
+#: ../../addon/tictac/tictac.php:21
+msgid "Three Dimensional Tic-Tac-Toe"
+msgstr "Tic-tac-toe en 3 dimensions"
-#: ../../include/connections.php:214
-#, php-format
-msgid "User '%s' deleted"
-msgstr "Utilisateur '%s' supprimé"
+#: ../../addon/tictac/tictac.php:54
+msgid "3D Tic-Tac-Toe"
+msgstr "3D Tic-Tac-Toe"
-#: ../../include/contact_widgets.php:11
-#, php-format
-msgid "%d invitation available"
-msgid_plural "%d invitations available"
-msgstr[0] "%d invitation disponible"
-msgstr[1] "%d invitations disponibles"
+#: ../../addon/tictac/tictac.php:59
+msgid "New game"
+msgstr "Nouveau jeu"
-#: ../../include/contact_widgets.php:19
-msgid "Find Channels"
-msgstr "Trouver des canaux"
+#: ../../addon/tictac/tictac.php:60
+msgid "New game with handicap"
+msgstr "Nouveau jeu avec handicap"
-#: ../../include/contact_widgets.php:20
-msgid "Enter name or interest"
-msgstr "Saisir nom ou centre d'intérêt"
+#: ../../addon/tictac/tictac.php:61
+msgid ""
+"Three dimensional tic-tac-toe is just like the traditional game except that "
+"it is played on multiple levels simultaneously. "
+msgstr "Trois dimensions tic-tac-toe est juste comme le jeu traditionnel, sauf qu'il est joué sur plusieurs niveaux simultanément."
-#: ../../include/contact_widgets.php:21
-msgid "Connect/Follow"
-msgstr "Ajouter/Suivre"
+#: ../../addon/tictac/tictac.php:62
+msgid ""
+"In this case there are three levels. You win by getting three in a row on "
+"any level, as well as up, down, and diagonally across the different levels."
+msgstr "Dans ce cas, il y a trois niveaux. Vous gagnez en obtenant trois dans une rangée à n'importe quel niveau, que ce soit vers le haut, le bas, ou en diagonale à travers les différents niveaux."
-#: ../../include/contact_widgets.php:22
-msgid "Examples: Robert Morgenstein, Fishing"
-msgstr "Exemples: Guillaume Martin, Course à pieds"
+#: ../../addon/tictac/tictac.php:64
+msgid ""
+"The handicap game disables the center position on the middle level because "
+"the player claiming this square often has an unfair advantage."
+msgstr "Le jeu handicap désactive la position centrale au niveau intermédiaire, car le joueur qui revendique ce carré a souvent un avantage indu."
-#: ../../include/contact_widgets.php:26
-msgid "Random Profile"
-msgstr "Un profil au hasard"
+#: ../../addon/tictac/tictac.php:183
+msgid "You go first..."
+msgstr "Vous commencez…"
-#: ../../include/contact_widgets.php:27
-msgid "Invite Friends"
-msgstr "Inviter des amis"
+#: ../../addon/tictac/tictac.php:188
+msgid "I'm going first this time..."
+msgstr "Cette fois, je commence…"
-#: ../../include/contact_widgets.php:29
-msgid "Advanced example: name=fred and country=iceland"
-msgstr "Exemple avancé&nbsp;: name=fred and country=iceland"
+#: ../../addon/tictac/tictac.php:194
+msgid "You won!"
+msgstr "Vous avez gagné !"
-#: ../../include/contact_widgets.php:122
-#, php-format
-msgid "%d connection in common"
-msgid_plural "%d connections in common"
-msgstr[0] "%d contact en commun"
-msgstr[1] "%d contacts en commun"
+#: ../../addon/tictac/tictac.php:200 ../../addon/tictac/tictac.php:225
+msgid "\"Cat\" game!"
+msgstr "Jeu de \"Chat\" !"
-#: ../../include/contact_widgets.php:127
-msgid "show more"
-msgstr "montrer plus"
+#: ../../addon/tictac/tictac.php:223
+msgid "I won!"
+msgstr "J'ai gagné !"
-#: ../../include/conversation.php:204
-#, php-format
-msgid "%1$s is now connected with %2$s"
-msgstr "%1$s ajoute %2$s à ses contacts"
+#: ../../addon/pageheader/pageheader.php:43
+msgid "Message to display on every page on this server"
+msgstr "Message à afficher sur chaque page de ce serveur"
-#: ../../include/conversation.php:239
-#, php-format
-msgid "%1$s poked %2$s"
-msgstr "%1$s a tapoté %2$s"
+#: ../../addon/pageheader/pageheader.php:48
+msgid "Pageheader Settings"
+msgstr "Paramètres du haut de page"
-#: ../../include/conversation.php:691
-#, php-format
-msgid "View %s's profile @ %s"
-msgstr "Voir le profil de %s @ %s"
+#: ../../addon/pageheader/pageheader.php:64
+msgid "pageheader Settings saved."
+msgstr "Paramètres du haut de page sauvegardés."
-#: ../../include/conversation.php:710
-msgid "Categories:"
-msgstr "Catégories&nbsp;:"
+#: ../../addon/moremoods/moremoods.php:19
+msgid "lonely"
+msgstr "isolé"
-#: ../../include/conversation.php:711
-msgid "Filed under:"
-msgstr "Classé sous&nbsp;:"
+#: ../../addon/moremoods/moremoods.php:20
+msgid "drunk"
+msgstr "saoul"
-#: ../../include/conversation.php:738
-msgid "View in context"
-msgstr "Voir en contexte"
+#: ../../addon/moremoods/moremoods.php:21
+msgid "horny"
+msgstr "libidineux"
-#: ../../include/conversation.php:847
-msgid "remove"
-msgstr "supprimer"
+#: ../../addon/moremoods/moremoods.php:22
+msgid "stoned"
+msgstr "défoncé"
-#: ../../include/conversation.php:852
-msgid "Delete Selected Items"
-msgstr "Supprimer les éléments selectionnés"
+#: ../../addon/moremoods/moremoods.php:23
+msgid "fucked up"
+msgstr "cramé"
-#: ../../include/conversation.php:948
-msgid "View Source"
-msgstr "Voir source"
+#: ../../addon/moremoods/moremoods.php:24
+msgid "clusterfucked"
+msgstr "énervé"
-#: ../../include/conversation.php:949
-msgid "Follow Thread"
-msgstr "Suivre la discussion"
+#: ../../addon/moremoods/moremoods.php:25
+msgid "crazy"
+msgstr "cinglé"
-#: ../../include/conversation.php:950
-msgid "Unfollow Thread"
-msgstr "Ne plus suivre la discussion"
+#: ../../addon/moremoods/moremoods.php:26
+msgid "hurt"
+msgstr "dommage"
-#: ../../include/conversation.php:955
-msgid "Activity/Posts"
-msgstr "Activité/Publications"
+#: ../../addon/moremoods/moremoods.php:27
+msgid "sleepy"
+msgstr "somnolent"
-#: ../../include/conversation.php:957
-msgid "Edit Connection"
-msgstr "Modifier le contact"
+#: ../../addon/moremoods/moremoods.php:28
+msgid "grumpy"
+msgstr "grognon"
-#: ../../include/conversation.php:958
-msgid "Message"
-msgstr "Message"
+#: ../../addon/moremoods/moremoods.php:29
+msgid "high"
+msgstr "allumé"
-#: ../../include/conversation.php:1075
-#, php-format
-msgid "%s likes this."
-msgstr "%s aime ça."
+#: ../../addon/moremoods/moremoods.php:30
+msgid "semi-conscious"
+msgstr "à demi-conscient"
-#: ../../include/conversation.php:1075
-#, php-format
-msgid "%s doesn't like this."
-msgstr "%s n'aime pas ça."
+#: ../../addon/moremoods/moremoods.php:31
+msgid "in love"
+msgstr "amoureux"
-#: ../../include/conversation.php:1079
-#, php-format
-msgid "<span %1$s>%2$d people</span> like this."
-msgid_plural "<span %1$s>%2$d people</span> like this."
-msgstr[0] "<span %1$s>%2$d personne</span> aime ceci."
-msgstr[1] "<span %1$s>%2$d personnes</span> aiment ceci."
+#: ../../addon/moremoods/moremoods.php:32
+msgid "in lust"
+msgstr "convoitise"
-#: ../../include/conversation.php:1081
-#, php-format
-msgid "<span %1$s>%2$d people</span> don't like this."
-msgid_plural "<span %1$s>%2$d people</span> don't like this."
-msgstr[0] "<span %1$s>%2$d personne</span> n'aime pas ça."
-msgstr[1] "<span %1$s>%2$d personnes</span> n'aiment pas ça."
+#: ../../addon/moremoods/moremoods.php:33
+msgid "naked"
+msgstr "nu"
-#: ../../include/conversation.php:1087
-msgid "and"
-msgstr "et"
+#: ../../addon/moremoods/moremoods.php:34
+msgid "stinky"
+msgstr "puant"
-#: ../../include/conversation.php:1090
-#, php-format
-msgid ", and %d other people"
-msgid_plural ", and %d other people"
-msgstr[0] ", et %d autre personne"
-msgstr[1] ", et %d autres personnes"
+#: ../../addon/moremoods/moremoods.php:35
+msgid "sweaty"
+msgstr "en sueur"
-#: ../../include/conversation.php:1091
-#, php-format
-msgid "%s like this."
-msgstr "%s aime ça."
+#: ../../addon/moremoods/moremoods.php:36
+msgid "bleeding out"
+msgstr "en sang"
-#: ../../include/conversation.php:1091
-#, php-format
-msgid "%s don't like this."
-msgstr "%s n'aime pas ça."
+#: ../../addon/moremoods/moremoods.php:37
+msgid "victorious"
+msgstr "victorieux"
-#: ../../include/conversation.php:1130
-msgid "Set your location"
-msgstr "Spécifier votre emplacement géographique"
+#: ../../addon/moremoods/moremoods.php:38
+msgid "defeated"
+msgstr "vaincu"
-#: ../../include/conversation.php:1131
-msgid "Clear browser location"
-msgstr "Supprimer l'emplacement géographique du navigateur"
+#: ../../addon/moremoods/moremoods.php:39
+msgid "envious"
+msgstr "envieux"
-#: ../../include/conversation.php:1177
-msgid "Tag term:"
-msgstr "Étiquette&nbsp;:"
+#: ../../addon/moremoods/moremoods.php:40
+msgid "jealous"
+msgstr "jaloux"
-#: ../../include/conversation.php:1178
-msgid "Where are you right now?"
-msgstr "Où êtes-vous en ce moment&nbsp;?"
+#: ../../addon/xmpp/xmpp.php:31
+msgid "XMPP settings updated."
+msgstr "Les paramètres XMPP ont été mis à jour."
-#: ../../include/conversation.php:1210
-msgid "Page link name"
-msgstr "Nom du lien vers la page"
+#: ../../addon/xmpp/xmpp.php:53
+msgid "Enable Chat"
+msgstr "Activer le Chat"
-#: ../../include/conversation.php:1213
-msgid "Post as"
-msgstr "Publier en tant que"
+#: ../../addon/xmpp/xmpp.php:58
+msgid "Individual credentials"
+msgstr "Informations d'identifications individuelles"
-#: ../../include/conversation.php:1223
-msgid "Toggle voting"
-msgstr "(Dés)activer le vote"
+#: ../../addon/xmpp/xmpp.php:64
+msgid "Jabber BOSH server"
+msgstr "serveur Jabber BOSH"
-#: ../../include/conversation.php:1231
-msgid "Categories (optional, comma-separated list)"
-msgstr "Catégories (facultatives, séparées par des virgules)"
+#: ../../addon/xmpp/xmpp.php:69
+msgid "XMPP Settings"
+msgstr "Paramètres XMPP"
-#: ../../include/conversation.php:1254
-msgid "Set publish date"
-msgstr "Définir la date de publication"
+#: ../../addon/xmpp/xmpp.php:92
+msgid "Jabber BOSH host"
+msgstr "Hôte Jabber BOSH"
-#: ../../include/conversation.php:1258
-msgid "OK"
-msgstr "OK"
+#: ../../addon/xmpp/xmpp.php:93
+msgid "Use central userbase"
+msgstr "Utiliser la base d'utilisateurs centrale"
-#: ../../include/conversation.php:1503
-msgid "Discover"
-msgstr "À découvrir"
+#: ../../addon/xmpp/xmpp.php:93
+msgid ""
+"If enabled, members will automatically login to an ejabberd server that has "
+"to be installed on this machine with synchronized credentials via the "
+"\"auth_ejabberd.php\" script."
+msgstr "Si cette option est activée, les membres se connecteront automatiquement à un serveur ejabberd qui doit être installé sur cette machine avec des informations d'identification synchronisées via le script \"auth_ejabberd.php\"."
-#: ../../include/conversation.php:1506
-msgid "Imported public streams"
-msgstr "Flux publics importés"
+#: ../../addon/wholikesme/wholikesme.php:29
+msgid "Who likes me?"
+msgstr "Qui m'aime?"
-#: ../../include/conversation.php:1511
-msgid "Commented Order"
-msgstr "Par date de commentaire"
+#: ../../addon/pumpio/pumpio.php:148
+msgid "You are now authenticated to pumpio."
+msgstr "Vous êtes maintenant connecté à pumpio."
-#: ../../include/conversation.php:1514
-msgid "Sort by Comment Date"
-msgstr "Trier par date de dernier commentaire"
+#: ../../addon/pumpio/pumpio.php:149
+msgid "return to the featured settings page"
+msgstr "retourner à la page des paramètres des fonctionnalités"
-#: ../../include/conversation.php:1518
-msgid "Posted Order"
-msgstr "Par date de publication"
+#: ../../addon/pumpio/pumpio.php:163
+msgid "Post to Pump.io"
+msgstr "Publier sur Pump.io"
-#: ../../include/conversation.php:1521
-msgid "Sort by Post Date"
-msgstr "Trier par date de publication"
+#: ../../addon/pumpio/pumpio.php:198
+msgid "Pump.io servername"
+msgstr "Nom du serveur Pump.io"
-#: ../../include/conversation.php:1529
-msgid "Posts that mention or involve you"
-msgstr "Publications qui vous mentionnent ou vous concernent d'une manière ou d'une autre"
+#: ../../addon/pumpio/pumpio.php:198
+msgid "Without \"http://\" or \"https://\""
+msgstr "Sans \"http://\" ou \"https://\""
-#: ../../include/conversation.php:1538
-msgid "Activity Stream - by date"
-msgstr "Flux d'activité - par date"
+#: ../../addon/pumpio/pumpio.php:202
+msgid "Pump.io username"
+msgstr "Identifiant Pump.io"
-#: ../../include/conversation.php:1544
-msgid "Starred"
-msgstr "Mis en avant (étoiles)"
+#: ../../addon/pumpio/pumpio.php:202
+msgid "Without the servername"
+msgstr "Sans le nom de serveur"
-#: ../../include/conversation.php:1547
-msgid "Favourite Posts"
-msgstr "Publications préférées"
+#: ../../addon/pumpio/pumpio.php:213
+msgid "You are not authenticated to pumpio"
+msgstr "Vous n'êtes pas connecté à Pump.io"
-#: ../../include/conversation.php:1554
-msgid "Spam"
-msgstr "Indésirable"
+#: ../../addon/pumpio/pumpio.php:215
+msgid "(Re-)Authenticate your pump.io connection"
+msgstr "Authentifiez-vous à nouveau auprès de Pump.io"
-#: ../../include/conversation.php:1557
-msgid "Posts flagged as SPAM"
-msgstr "Publications marquées comme indésirables"
+#: ../../addon/pumpio/pumpio.php:219
+msgid "Enable pump.io Post Plugin"
+msgstr "Activer le plugin de publication Pump.io"
-#: ../../include/conversation.php:1614
-msgid "Status Messages and Posts"
-msgstr "Messages d'état et contributions"
+#: ../../addon/pumpio/pumpio.php:223
+msgid "Post to pump.io by default"
+msgstr "Par défaut, publier sur Pump.io"
-#: ../../include/conversation.php:1623
-msgid "About"
-msgstr "À propos"
+#: ../../addon/pumpio/pumpio.php:227
+msgid "Should posts be public"
+msgstr "Les publications doivent-elles être publiques ?"
-#: ../../include/conversation.php:1626
-msgid "Profile Details"
-msgstr "Détails du profil"
+#: ../../addon/pumpio/pumpio.php:231
+msgid "Mirror all public posts"
+msgstr "Créer une copie miroir de toutes les publications publiques"
-#: ../../include/conversation.php:1635 ../../include/photos.php:502
-msgid "Photo Albums"
-msgstr "Albums photo"
+#: ../../addon/pumpio/pumpio.php:237
+msgid "Pump.io Post Settings"
+msgstr "Paramètres de publication Pump.io"
-#: ../../include/conversation.php:1642
-msgid "Files and Storage"
-msgstr "Fichiers et Stockage"
+#: ../../addon/pumpio/pumpio.php:266
+msgid "PumpIO Settings saved."
+msgstr "Paramètres Pump.io sauvegardés."
-#: ../../include/conversation.php:1678
-msgid "Saved Bookmarks"
-msgstr "Favoris sauvegardés"
+#: ../../addon/ldapauth/ldapauth.php:61
+msgid "An account has been created for you."
+msgstr "Un compte a été créé pour vous."
-#: ../../include/conversation.php:1688
-msgid "Manage Webpages"
-msgstr "Gérer les pages web"
+#: ../../addon/ldapauth/ldapauth.php:68
+msgid "Authentication successful but rejected: account creation is disabled."
+msgstr "L'authentification a réussi mais a été rejetée : la création de comptes est désactivée."
-#: ../../include/conversation.php:1747
-msgctxt "noun"
-msgid "Attending"
-msgid_plural "Attending"
-msgstr[0] "Participe"
-msgstr[1] "Participent"
+#: ../../addon/opensearch/opensearch.php:43
+msgid "Search $Projectname"
+msgstr "Chercher dans $Projectname"
-#: ../../include/conversation.php:1750
-msgctxt "noun"
-msgid "Not Attending"
-msgid_plural "Not Attending"
-msgstr[0] "Ne participe pas"
-msgstr[1] "Ne participent pas"
+#: ../../addon/redfiles/redfiles.php:119
+msgid "Redmatrix File Storage Import"
+msgstr "Importation du fichier de stockage Redmatrix"
-#: ../../include/conversation.php:1753
-msgctxt "noun"
-msgid "Undecided"
-msgid_plural "Undecided"
-msgstr[0] "Indécis(e)"
-msgstr[1] "Indécis(es)"
+#: ../../addon/redfiles/redfiles.php:120
+msgid "This will import all your Redmatrix cloud files to this channel."
+msgstr "Ceci importera tous vos fichiers Redmatrix dans ce canal."
-#: ../../include/conversation.php:1756
-msgctxt "noun"
-msgid "Agree"
-msgid_plural "Agrees"
-msgstr[0] "D'accord"
-msgstr[1] "D'accord"
+#: ../../addon/redfiles/redfilehelper.php:67
+msgid "file"
+msgstr "fichier"
-#: ../../include/conversation.php:1759
-msgctxt "noun"
-msgid "Disagree"
-msgid_plural "Disagrees"
-msgstr[0] "Pas d'accord"
-msgstr[1] "Pas d'accord"
+#: ../../addon/hubwall/hubwall.php:19
+msgid "Send email to all members"
+msgstr "Envoyer un mail à tous les membres"
-#: ../../include/conversation.php:1762
-msgctxt "noun"
-msgid "Abstain"
-msgid_plural "Abstains"
-msgstr[0] "S'abstient"
-msgstr[1] "S'abstiennent"
+#: ../../addon/hubwall/hubwall.php:33
+#, php-format
+msgid "$1%s Administrator"
+msgstr "$1%s administrateur"
+
+#: ../../addon/hubwall/hubwall.php:73
+#, php-format
+msgid "%1$d of %2$d messages sent."
+msgstr "%1$d message(s) envoyés sur %2$d."
+
+#: ../../addon/hubwall/hubwall.php:81
+msgid "Send email to all hub members."
+msgstr "Envoyer un e-mail à tous les membres du hub."
+
+#: ../../addon/hubwall/hubwall.php:93
+msgid "Sender Email address"
+msgstr "Adresse mail de l'expéditeur"
+
+#: ../../addon/hubwall/hubwall.php:94
+msgid "Test mode (only send to hub administrator)"
+msgstr "Mode test (uniquement envoyé à l'administrateur du hub)"
#: ../../include/selectors.php:30
msgid "Frequently"
@@ -8133,12 +10833,6 @@ msgstr "Neutre"
msgid "Non-specific"
msgstr "Non spécifique"
-#: ../../include/selectors.php:49 ../../include/selectors.php:66
-#: ../../include/selectors.php:104 ../../include/selectors.php:140
-#: ../../include/permissions.php:881
-msgid "Other"
-msgstr "Autre"
-
#: ../../include/selectors.php:49
msgid "Undecided"
msgstr "Indécis"
@@ -8315,821 +11009,836 @@ msgstr "S'en fiche"
msgid "Ask me"
msgstr "Me demander"
-#: ../../include/PermissionDescription.php:31
-#: ../../include/acl_selectors.php:232
-msgid "Visible to your default audience"
-msgstr "Visible pour vos contacts seulement"
-
-#: ../../include/PermissionDescription.php:115
-#: ../../include/acl_selectors.php:268
-msgid "Only me"
-msgstr ""
+#: ../../include/conversation.php:200
+#, php-format
+msgid "%1$s is now connected with %2$s"
+msgstr "%1$s ajoute %2$s à ses contacts"
-#: ../../include/PermissionDescription.php:116
-msgid "Public"
-msgstr "Public"
+#: ../../include/conversation.php:235
+#, php-format
+msgid "%1$s poked %2$s"
+msgstr "%1$s a tapoté %2$s"
-#: ../../include/PermissionDescription.php:117
-msgid "Anybody in the $Projectname network"
-msgstr ""
+#: ../../include/conversation.php:239 ../../include/text.php:1115
+#: ../../include/text.php:1120
+msgid "poked"
+msgstr "a tapoté"
-#: ../../include/PermissionDescription.php:118
+#: ../../include/conversation.php:691
#, php-format
-msgid "Any account on %s"
-msgstr ""
+msgid "View %s's profile @ %s"
+msgstr "Voir le profil de %s @ %s"
-#: ../../include/PermissionDescription.php:119
-msgid "Any of my connections"
-msgstr ""
+#: ../../include/conversation.php:711
+msgid "Categories:"
+msgstr "Catégories&nbsp;:"
-#: ../../include/PermissionDescription.php:120
-msgid "Only connections I specifically allow"
-msgstr ""
+#: ../../include/conversation.php:712
+msgid "Filed under:"
+msgstr "Classé sous&nbsp;:"
-#: ../../include/PermissionDescription.php:121
-msgid "Anybody authenticated (could include visitors from other networks)"
-msgstr ""
+#: ../../include/conversation.php:737
+msgid "View in context"
+msgstr "Voir en contexte"
-#: ../../include/PermissionDescription.php:122
-msgid "Any connections including those who haven't yet been approved"
-msgstr ""
+#: ../../include/conversation.php:834
+msgid "remove"
+msgstr "supprimer"
-#: ../../include/PermissionDescription.php:161
-msgid ""
-"This is your default setting for the audience of your normal stream, and "
-"posts."
-msgstr ""
+#: ../../include/conversation.php:838 ../../include/nav.php:268
+msgid "Loading..."
+msgstr "Chargement..."
-#: ../../include/PermissionDescription.php:162
-msgid ""
-"This is your default setting for who can view your default channel profile"
-msgstr ""
+#: ../../include/conversation.php:839
+msgid "Delete Selected Items"
+msgstr "Supprimer les éléments selectionnés"
-#: ../../include/PermissionDescription.php:163
-msgid "This is your default setting for who can view your connections"
-msgstr ""
+#: ../../include/conversation.php:882
+msgid "View Source"
+msgstr "Voir source"
-#: ../../include/PermissionDescription.php:164
-msgid ""
-"This is your default setting for who can view your file storage and photos"
-msgstr ""
+#: ../../include/conversation.php:892
+msgid "Follow Thread"
+msgstr "Suivre la discussion"
-#: ../../include/PermissionDescription.php:165
-msgid "This is your default setting for the audience of your webpages"
-msgstr ""
+#: ../../include/conversation.php:901
+msgid "Unfollow Thread"
+msgstr "Ne plus suivre la discussion"
-#: ../../include/account.php:28
-msgid "Not a valid email address"
-msgstr "Ce n'est pas une adresse de courriel valide"
+#: ../../include/conversation.php:992
+msgid "Activity/Posts"
+msgstr "Activité/Publications"
-#: ../../include/account.php:30
-msgid "Your email domain is not among those allowed on this site"
-msgstr "Votre domaine de courriel ne fait pas partie de ceux autorisés par ce site"
+#: ../../include/conversation.php:1012
+msgid "Edit Connection"
+msgstr "Modifier le contact"
-#: ../../include/account.php:36
-msgid "Your email address is already registered at this site."
-msgstr "Votre adresse de courriel est déjà inscrite sur ce site."
+#: ../../include/conversation.php:1022
+msgid "Message"
+msgstr "Message"
-#: ../../include/account.php:68
-msgid "An invitation is required."
-msgstr "Une invitation est requise."
+#: ../../include/conversation.php:1156
+#, php-format
+msgid "%s likes this."
+msgstr "%s aime ça."
-#: ../../include/account.php:72
-msgid "Invitation could not be verified."
-msgstr "Votre invitation n'a pas pu être vérifiée."
+#: ../../include/conversation.php:1156
+#, php-format
+msgid "%s doesn't like this."
+msgstr "%s n'aime pas ça."
-#: ../../include/account.php:122
-msgid "Please enter the required information."
-msgstr "Merci d'entrer les informations requises."
+#: ../../include/conversation.php:1160
+#, php-format
+msgid "<span %1$s>%2$d people</span> like this."
+msgid_plural "<span %1$s>%2$d people</span> like this."
+msgstr[0] "<span %1$s>%2$d personne</span> aime ceci."
+msgstr[1] "<span %1$s>%2$d personnes</span> aiment ceci."
-#: ../../include/account.php:189
-msgid "Failed to store account information."
-msgstr "Impossible de stocker les informations liées au compte."
+#: ../../include/conversation.php:1162
+#, php-format
+msgid "<span %1$s>%2$d people</span> don't like this."
+msgid_plural "<span %1$s>%2$d people</span> don't like this."
+msgstr[0] "<span %1$s>%2$d personne</span> n'aime pas ça."
+msgstr[1] "<span %1$s>%2$d personnes</span> n'aiment pas ça."
+
+#: ../../include/conversation.php:1168
+msgid "and"
+msgstr "et"
-#: ../../include/account.php:249
+#: ../../include/conversation.php:1171
#, php-format
-msgid "Registration confirmation for %s"
-msgstr "Confirmation de l'inscription pour %s"
+msgid ", and %d other people"
+msgid_plural ", and %d other people"
+msgstr[0] ", et %d autre personne"
+msgstr[1] ", et %d autres personnes"
-#: ../../include/account.php:315
+#: ../../include/conversation.php:1172
#, php-format
-msgid "Registration request at %s"
-msgstr "Demande d'inscription sur %s"
+msgid "%s like this."
+msgstr "%s aime ça."
-#: ../../include/account.php:317 ../../include/account.php:344
-#: ../../include/account.php:404 ../../include/network.php:1871
-msgid "Administrator"
-msgstr "Administrateur"
+#: ../../include/conversation.php:1172
+#, php-format
+msgid "%s don't like this."
+msgstr "%s n'aime pas ça."
-#: ../../include/account.php:339
-msgid "your registration password"
-msgstr "votre mot de passe d'inscription"
+#: ../../include/conversation.php:1215
+msgid "Set your location"
+msgstr "Spécifier votre emplacement géographique"
-#: ../../include/account.php:342 ../../include/account.php:402
-#, php-format
-msgid "Registration details for %s"
-msgstr "Détails de l'inscription pour %s"
+#: ../../include/conversation.php:1216
+msgid "Clear browser location"
+msgstr "Supprimer l'emplacement géographique du navigateur"
-#: ../../include/account.php:414
-msgid "Account approved."
-msgstr "Compte approuvé."
+#: ../../include/conversation.php:1264
+msgid "Tag term:"
+msgstr "Étiquette&nbsp;:"
-#: ../../include/account.php:454
-#, php-format
-msgid "Registration revoked for %s"
-msgstr "Inscription révoquée pour %s"
+#: ../../include/conversation.php:1265
+msgid "Where are you right now?"
+msgstr "Où êtes-vous en ce moment&nbsp;?"
-#: ../../include/account.php:506
-msgid "Account verified. Please login."
-msgstr "Compte vérifié. Veuillez vous connecter."
+#: ../../include/conversation.php:1270
+msgid "Choose a different album..."
+msgstr "Choisissez un autre album"
-#: ../../include/account.php:723 ../../include/account.php:725
-msgid "Click here to upgrade."
-msgstr "Cliquez ici pour mettre à jour."
+#: ../../include/conversation.php:1274
+msgid "Comments enabled"
+msgstr "Commentaires activés"
-#: ../../include/account.php:731
-msgid "This action exceeds the limits set by your subscription plan."
-msgstr "Cette action outrepasserait les limites prévues par votre forfait."
+#: ../../include/conversation.php:1275
+msgid "Comments disabled"
+msgstr "Commentaires désactivés"
-#: ../../include/account.php:736
-msgid "This action is not available under your subscription plan."
-msgstr "Cette action n'est pas disponible avec votre forfait."
+#: ../../include/conversation.php:1313
+msgid "Page link name"
+msgstr "Nom du lien vers la page"
-#: ../../include/attach.php:247 ../../include/attach.php:333
-msgid "Item was not found."
-msgstr "Élément introuvable."
+#: ../../include/conversation.php:1316
+msgid "Post as"
+msgstr "Publier en tant que"
-#: ../../include/attach.php:497
-msgid "No source file."
-msgstr "Pas de fichier source."
+#: ../../include/conversation.php:1330
+msgid "Toggle voting"
+msgstr "(Dés)activer le vote"
-#: ../../include/attach.php:519
-msgid "Cannot locate file to replace"
-msgstr "Impossible de trouver le fichier à remplacer."
+#: ../../include/conversation.php:1333
+msgid "Disable comments"
+msgstr "Désactiver les commentaires"
-#: ../../include/attach.php:537
-msgid "Cannot locate file to revise/update"
-msgstr "Impossible de trouver le fichier à corriger/mettre à jour"
+#: ../../include/conversation.php:1334
+msgid "Toggle comments"
+msgstr "Basculer les commentaires"
-#: ../../include/attach.php:672
-#, php-format
-msgid "File exceeds size limit of %d"
-msgstr "Le fichier dépasse la taille limite de %d"
+#: ../../include/conversation.php:1342
+msgid "Categories (optional, comma-separated list)"
+msgstr "Catégories (facultatives, séparées par des virgules)"
-#: ../../include/attach.php:686
-#, php-format
-msgid "You have reached your limit of %1$.0f Mbytes attachment storage."
-msgstr "Vous avez atteint votre limite de %1$.0f méga-octets autorisés pour le stockage des pièces-jointes."
+#: ../../include/conversation.php:1365
+msgid "Other networks and post services"
+msgstr "Autres réseaux et services de messagerie"
-#: ../../include/attach.php:842
-msgid "File upload failed. Possible system limit or action terminated."
-msgstr "Envoi du fichier impossible. Limite système ou action avortée."
+#: ../../include/conversation.php:1371
+msgid "Set publish date"
+msgstr "Définir la date de publication"
-#: ../../include/attach.php:855
-msgid "Stored file could not be verified. Upload failed."
-msgstr "Le fichier stocké n'a pu être vérifié. Echec de l'envoi."
+#: ../../include/conversation.php:1625
+msgid "Discover"
+msgstr "À découvrir"
-#: ../../include/attach.php:909 ../../include/attach.php:925
-msgid "Path not available."
-msgstr "Chemin non disponible."
+#: ../../include/conversation.php:1628
+msgid "Imported public streams"
+msgstr "Flux publics importés"
-#: ../../include/attach.php:971 ../../include/attach.php:1123
-msgid "Empty pathname"
-msgstr "Chemin vide"
+#: ../../include/conversation.php:1633
+msgid "Commented Order"
+msgstr "Par date de commentaire"
-#: ../../include/attach.php:997
-msgid "duplicate filename or path"
-msgstr "doublon de chemin ou de fichier"
+#: ../../include/conversation.php:1636
+msgid "Sort by Comment Date"
+msgstr "Trier par date de dernier commentaire"
-#: ../../include/attach.php:1019
-msgid "Path not found."
-msgstr "Chemin introuvable."
+#: ../../include/conversation.php:1640
+msgid "Posted Order"
+msgstr "Par date de publication"
-#: ../../include/attach.php:1077
-msgid "mkdir failed."
-msgstr "mkdir a échoué."
+#: ../../include/conversation.php:1643
+msgid "Sort by Post Date"
+msgstr "Trier par date de publication"
-#: ../../include/attach.php:1081
-msgid "database storage failed."
-msgstr "l'écriture dans la base de données a échoué."
+#: ../../include/conversation.php:1651
+msgid "Posts that mention or involve you"
+msgstr "Publications qui vous mentionnent ou vous concernent d'une manière ou d'une autre"
-#: ../../include/attach.php:1129
-msgid "Empty path"
-msgstr "Chemin vide"
+#: ../../include/conversation.php:1660
+msgid "Activity Stream - by date"
+msgstr "Flux d'activité - par date"
-#: ../../include/channel.php:32
-msgid "Unable to obtain identity information from database"
-msgstr "Impossible d'obtenir les données d'identité depuis la base de données"
+#: ../../include/conversation.php:1666
+msgid "Starred"
+msgstr "Avec étoile"
-#: ../../include/channel.php:66
-msgid "Empty name"
-msgstr "Nom vide"
+#: ../../include/conversation.php:1669
+msgid "Favourite Posts"
+msgstr "Publications préférées"
-#: ../../include/channel.php:69
-msgid "Name too long"
-msgstr "Nom trop long"
+#: ../../include/conversation.php:1676
+msgid "Spam"
+msgstr "Indésirable"
-#: ../../include/channel.php:180
-msgid "No account identifier"
-msgstr "Pas d'identifiant de compte"
+#: ../../include/conversation.php:1679
+msgid "Posts flagged as SPAM"
+msgstr "Publications marquées comme indésirables"
-#: ../../include/channel.php:192
-msgid "Nickname is required."
-msgstr "Un surnom est requis."
+#: ../../include/conversation.php:1754
+msgid "Status Messages and Posts"
+msgstr "Messages d'état et contributions"
-#: ../../include/channel.php:206
-msgid "Reserved nickname. Please choose another."
-msgstr "Surnom réservé. Merci d'en choisir un autre."
+#: ../../include/conversation.php:1767
+msgid "Profile Details"
+msgstr "Détails du profil"
-#: ../../include/channel.php:211
-msgid ""
-"Nickname has unsupported characters or is already being used on this site."
-msgstr "Le surnom contient des caractères interdits ou est déjà pris sur ce site."
+#: ../../include/conversation.php:1777 ../../include/photos.php:527
+msgid "Photo Albums"
+msgstr "Albums photo"
-#: ../../include/channel.php:287
-msgid "Unable to retrieve created identity"
-msgstr "Impossible de récupérer l'identité créée"
+#: ../../include/conversation.php:1785
+msgid "Files and Storage"
+msgstr "Fichiers et Stockage"
-#: ../../include/channel.php:345
-msgid "Default Profile"
-msgstr "Profil par défaut"
+#: ../../include/conversation.php:1821
+msgid "Bookmarks"
+msgstr "Favoris"
-#: ../../include/channel.php:791
-msgid "Requested channel is not available."
-msgstr "Canal demandé non disponible."
+#: ../../include/conversation.php:1824
+msgid "Saved Bookmarks"
+msgstr "Favoris sauvegardés"
-#: ../../include/channel.php:938
-msgid "Create New Profile"
-msgstr "Créer un nouveau profil"
+#: ../../include/conversation.php:1835
+msgid "View Webpages"
+msgstr "Voir les pages web"
-#: ../../include/channel.php:958
-msgid "Visible to everybody"
-msgstr "Visible de tous"
+#: ../../include/conversation.php:1904
+msgctxt "noun"
+msgid "Attending"
+msgid_plural "Attending"
+msgstr[0] "Participe"
+msgstr[1] "Participent"
-#: ../../include/channel.php:1031 ../../include/channel.php:1142
-msgid "Gender:"
-msgstr "Sexe&nbsp;:"
+#: ../../include/conversation.php:1907
+msgctxt "noun"
+msgid "Not Attending"
+msgid_plural "Not Attending"
+msgstr[0] "Ne participe pas"
+msgstr[1] "Ne participent pas"
-#: ../../include/channel.php:1032 ../../include/channel.php:1186
-msgid "Status:"
-msgstr "État&nbsp;:"
+#: ../../include/conversation.php:1910
+msgctxt "noun"
+msgid "Undecided"
+msgid_plural "Undecided"
+msgstr[0] "Indécis(e)"
+msgstr[1] "Indécis(es)"
-#: ../../include/channel.php:1033 ../../include/channel.php:1197
-msgid "Homepage:"
-msgstr "Site Internet&nbsp;:"
+#: ../../include/conversation.php:1913
+msgctxt "noun"
+msgid "Agree"
+msgid_plural "Agrees"
+msgstr[0] "D'accord"
+msgstr[1] "D'accord"
-#: ../../include/channel.php:1034
-msgid "Online Now"
-msgstr "Connecté"
+#: ../../include/conversation.php:1916
+msgctxt "noun"
+msgid "Disagree"
+msgid_plural "Disagrees"
+msgstr[0] "Pas d'accord"
+msgstr[1] "Pas d'accord"
-#: ../../include/channel.php:1147
-msgid "Like this channel"
-msgstr "J'aime ce canal"
+#: ../../include/conversation.php:1919
+msgctxt "noun"
+msgid "Abstain"
+msgid_plural "Abstains"
+msgstr[0] "S'abstient"
+msgstr[1] "S'abstiennent"
-#: ../../include/channel.php:1171
-msgid "j F, Y"
-msgstr "j F, Y"
+#: ../../include/permissions.php:35
+msgid "Can view my normal stream and posts"
+msgstr "Peut voir les publications ordinaires sur mon canal."
-#: ../../include/channel.php:1172
-msgid "j F"
-msgstr "j F"
+#: ../../include/permissions.php:39
+msgid "Can view my webpages"
+msgstr "Peut voir mes pages web"
-#: ../../include/channel.php:1179
-msgid "Birthday:"
-msgstr "Date de naissance&nbsp;:"
+#: ../../include/permissions.php:43
+msgid "Can post on my channel page (\"wall\")"
+msgstr "Peuvent poster sur la page de mon canal (\"mur\")"
-#: ../../include/channel.php:1192
-#, php-format
-msgid "for %1$d %2$s"
-msgstr "depuis %1$d %2$s"
+#: ../../include/permissions.php:46
+msgid "Can like/dislike stuff"
+msgstr "Peuvent aimer/ne pas aimer"
-#: ../../include/channel.php:1195
-msgid "Sexual Preference:"
-msgstr "Orientation sexuelle&nbsp;:"
+#: ../../include/permissions.php:46
+msgid "Profiles and things other than posts/comments"
+msgstr "Profils et autres excluant les publications/commentaires."
-#: ../../include/channel.php:1201
-msgid "Tags:"
-msgstr "Étiquettes&nbsp;:"
+#: ../../include/permissions.php:48
+msgid "Can forward to all my channel contacts via post @mentions"
+msgstr "Peut faire suivre à tous les contacts de mon canal via \"@mention\""
-#: ../../include/channel.php:1203
-msgid "Political Views:"
-msgstr "Opinions politiques&nbsp;:"
+#: ../../include/permissions.php:48
+msgid "Advanced - useful for creating group forum channels"
+msgstr "Avancé - utile pour les canaux de type \"forum/groupe\""
-#: ../../include/channel.php:1205
-msgid "Religion:"
-msgstr "Religion&nbsp;:"
+#: ../../include/permissions.php:49
+msgid "Can chat with me (when available)"
+msgstr "Peut discuter avec moi (quand disponibie)"
-#: ../../include/channel.php:1209
-msgid "Hobbies/Interests:"
-msgstr "Occupations/Centres d'intérêt&nbsp;:"
+#: ../../include/permissions.php:50
+msgid "Can write to my file storage and photos"
+msgstr "Peut charger des fichiers et des photos dans mon canal"
-#: ../../include/channel.php:1211
-msgid "Likes:"
-msgstr "Aime&nbsp;:"
+#: ../../include/permissions.php:51
+msgid "Can edit my webpages"
+msgstr "Peut modifier mes pages web"
-#: ../../include/channel.php:1213
-msgid "Dislikes:"
-msgstr "N'aime pas&nbsp;:"
+#: ../../include/permissions.php:53
+msgid "Somewhat advanced - very useful in open communities"
+msgstr "Plutôt avancé - très utile dans les communautés ouvertes"
-#: ../../include/channel.php:1215
-msgid "Contact information and Social Networks:"
-msgstr "Coordonnées et réseaux sociaux&nbsp;:"
+#: ../../include/permissions.php:55
+msgid "Can administer my channel resources"
+msgstr "Peut administrer les ressources de mon canal"
-#: ../../include/channel.php:1217
-msgid "My other channels:"
-msgstr "Mes autres canaux&nbsp;:"
+#: ../../include/permissions.php:55
+msgid ""
+"Extremely advanced. Leave this alone unless you know what you are doing"
+msgstr "Très avancé. Ne pas toucher, sauf si vous savez ce que vous faîtes"
-#: ../../include/channel.php:1219
-msgid "Musical interests:"
-msgstr "Goûts musicaux&nbsp;:"
+#: ../../include/dir_fns.php:141
+msgid "Directory Options"
+msgstr "Options d'annuaire"
-#: ../../include/channel.php:1221
-msgid "Books, literature:"
-msgstr "Lectures, goûts littéraires&nbsp;:"
+#: ../../include/dir_fns.php:143
+msgid "Safe Mode"
+msgstr "Mode sûr"
-#: ../../include/channel.php:1223
-msgid "Television:"
-msgstr "Télévision&nbsp;:"
+#: ../../include/dir_fns.php:144
+msgid "Public Forums Only"
+msgstr "Les forums publics uniquement"
-#: ../../include/channel.php:1225
-msgid "Film/dance/culture/entertainment:"
-msgstr "Cinéma/danse/culture/divertissement&nsbp;:"
+#: ../../include/dir_fns.php:145
+msgid "This Website Only"
+msgstr "Ce site uniquement"
-#: ../../include/channel.php:1227
-msgid "Love/Romance:"
-msgstr "Vie sentimentale/amoureuse&nbsp;:"
+#: ../../include/bookmarks.php:34
+#, php-format
+msgid "%1$s's bookmarks"
+msgstr "Favoris de %1$s"
-#: ../../include/channel.php:1229
-msgid "Work/employment:"
-msgstr "Travail/Occupation&nbsp;"
+#: ../../include/import.php:41
+msgid ""
+"Cannot create a duplicate channel identifier on this system. Import failed."
+msgstr "L'import a échoué. Un canal existe déjà avec ce nom"
-#: ../../include/channel.php:1231
-msgid "School/education:"
-msgstr "Études&nbsp;"
+#: ../../include/import.php:105
+msgid "Cloned channel not found. Import failed."
+msgstr "Canal cloné non trouvé. Echec de l'import."
-#: ../../include/channel.php:1251
-msgid "Like this thing"
-msgstr "J'aime ceci"
+#: ../../include/text.php:478
+msgid "prev"
+msgstr "préc."
-#: ../../include/features.php:48
-msgid "General Features"
-msgstr "Fonctionnalités générales"
+#: ../../include/text.php:480
+msgid "first"
+msgstr "premier"
-#: ../../include/features.php:50
-msgid "Content Expiration"
-msgstr "Expiration du contenu"
+#: ../../include/text.php:509
+msgid "last"
+msgstr "dernier"
-#: ../../include/features.php:50
-msgid "Remove posts/comments and/or private messages at a future time"
-msgstr "Supprimer les contributions/commentaires et/ou messages privés plus tard"
+#: ../../include/text.php:512
+msgid "next"
+msgstr "Suivant"
-#: ../../include/features.php:51
-msgid "Multiple Profiles"
-msgstr "Profils multiples"
+#: ../../include/text.php:523
+msgid "older"
+msgstr "plus ancien"
-#: ../../include/features.php:51
-msgid "Ability to create multiple profiles"
-msgstr "Possibilité de créer plusieurs profils"
+#: ../../include/text.php:525
+msgid "newer"
+msgstr "plus récent"
-#: ../../include/features.php:52
-msgid "Advanced Profiles"
-msgstr "Profils Avancés"
+#: ../../include/text.php:945
+msgid "No connections"
+msgstr "Pas de relations."
-#: ../../include/features.php:52
-msgid "Additional profile sections and selections"
-msgstr "Sections et sélections supplémentaires du profil"
+#: ../../include/text.php:970
+#, php-format
+msgid "View all %s connections"
+msgstr "Voir les %s contacts"
-#: ../../include/features.php:53
-msgid "Profile Import/Export"
-msgstr "Importer/Exporter le profil"
+#: ../../include/text.php:1115 ../../include/text.php:1120
+msgid "poke"
+msgstr "tapoter"
-#: ../../include/features.php:53
-msgid "Save and load profile details across sites/channels"
-msgstr "Sauvegarder et charger les détails d'un profil entre sites/canaux"
+#: ../../include/text.php:1121
+msgid "ping"
+msgstr "ping"
-#: ../../include/features.php:54
-msgid "Web Pages"
-msgstr "Pages web"
+#: ../../include/text.php:1121
+msgid "pinged"
+msgstr "pingé"
-#: ../../include/features.php:54
-msgid "Provide managed web pages on your channel"
-msgstr "Fournir des pages web, sous votre contrôle, sur votre canal"
+#: ../../include/text.php:1122
+msgid "prod"
+msgstr "encourager"
-#: ../../include/features.php:55
-msgid "Hide Rating"
-msgstr "Masquer l'évaluation"
+#: ../../include/text.php:1122
+msgid "prodded"
+msgstr "encouragé"
-#: ../../include/features.php:55
-msgid ""
-"Hide the rating buttons on your channel and profile pages. Note: People can "
-"still rate you somewhere else."
-msgstr "Masquer les boutons d'évaluation sur les pages de votre canal et de votre profil. NB : vous pourrez toujours être évalué(e) ailleurs."
+#: ../../include/text.php:1123
+msgid "slap"
+msgstr "giffler"
-#: ../../include/features.php:56
-msgid "Private Notes"
-msgstr "Notes privées"
+#: ../../include/text.php:1123
+msgid "slapped"
+msgstr "gifflé(e)"
-#: ../../include/features.php:56
-msgid "Enables a tool to store notes and reminders (note: not encrypted)"
-msgstr "Active un outil pour stocker des notes et des rappels (note&nbsp;:non chiffré)"
+#: ../../include/text.php:1124
+msgid "finger"
+msgstr "pointer"
-#: ../../include/features.php:57
-msgid "Navigation Channel Select"
-msgstr "Sélection du canal par la navigation"
+#: ../../include/text.php:1124
+msgid "fingered"
+msgstr "pointé"
-#: ../../include/features.php:57
-msgid "Change channels directly from within the navigation dropdown menu"
-msgstr "Changez de canal directement depuis le menu de navigation déroulant"
+#: ../../include/text.php:1125
+msgid "rebuff"
+msgstr "rejetter"
-#: ../../include/features.php:58
-msgid "Photo Location"
-msgstr "Site de prise de vue"
+#: ../../include/text.php:1125
+msgid "rebuffed"
+msgstr "rejeté"
-#: ../../include/features.php:58
-msgid "If location data is available on uploaded photos, link this to a map."
-msgstr "Si des informations géographiques sont présentes dans les images téléversées, les lier à une carte."
+#: ../../include/text.php:1137
+msgid "happy"
+msgstr "heureux"
-#: ../../include/features.php:59
-msgid "Access Controlled Chatrooms"
-msgstr ""
+#: ../../include/text.php:1138
+msgid "sad"
+msgstr "triste"
-#: ../../include/features.php:59
-msgid "Provide chatrooms and chat services with access control."
-msgstr ""
+#: ../../include/text.php:1139
+msgid "mellow"
+msgstr "mélancolique"
-#: ../../include/features.php:60
-msgid "Smart Birthdays"
-msgstr "Anniversaires intelligents"
+#: ../../include/text.php:1140
+msgid "tired"
+msgstr "fatigué"
-#: ../../include/features.php:60
-msgid ""
-"Make birthday events timezone aware in case your friends are scattered "
-"across the planet."
-msgstr "Adapter les anniversaires aux fuseaux horaires, utile pour vos amis sur d'autres continents."
+#: ../../include/text.php:1141
+msgid "perky"
+msgstr "impertinent"
-#: ../../include/features.php:61
-msgid "Expert Mode"
-msgstr "Mode expert"
+#: ../../include/text.php:1142
+msgid "angry"
+msgstr "en colère"
-#: ../../include/features.php:61
-msgid "Enable Expert Mode to provide advanced configuration options"
-msgstr "Activer le mode expert pour accéder aux options avancées"
+#: ../../include/text.php:1143
+msgid "stupefied"
+msgstr "stupéfait"
-#: ../../include/features.php:62
-msgid "Premium Channel"
-msgstr "Canal VIP"
+#: ../../include/text.php:1144
+msgid "puzzled"
+msgstr "perplexe"
-#: ../../include/features.php:62
-msgid ""
-"Allows you to set restrictions and terms on those that connect with your "
-"channel"
-msgstr "Vous permet d'appliquer des règles et restrictions aux contacts de votre canal"
+#: ../../include/text.php:1145
+msgid "interested"
+msgstr "intéressé"
-#: ../../include/features.php:67
-msgid "Post Composition Features"
-msgstr "Fonctionnalités de composition"
+#: ../../include/text.php:1146
+msgid "bitter"
+msgstr "amer"
-#: ../../include/features.php:70
-msgid "Large Photos"
-msgstr "Grandes photos"
+#: ../../include/text.php:1147
+msgid "cheerful"
+msgstr "plein d'entrain"
-#: ../../include/features.php:70
-msgid ""
-"Include large (1024px) photo thumbnails in posts. If not enabled, use small "
-"(640px) photo thumbnails"
-msgstr "Inclure de grands aperçus (1024px) dans les messages. Si désactivé, inclure de petits aperçus (640px)."
+#: ../../include/text.php:1148
+msgid "alive"
+msgstr "vivant"
-#: ../../include/features.php:71
-msgid "Automatically import channel content from other channels or feeds"
-msgstr "Importe automatiquement le contenus d'autres canaux ou flux dans le canal actif"
+#: ../../include/text.php:1149
+msgid "annoyed"
+msgstr "agaçé"
-#: ../../include/features.php:72
-msgid "Even More Encryption"
-msgstr "Encore plus de chiffrement"
+#: ../../include/text.php:1150
+msgid "anxious"
+msgstr "anxieux"
-#: ../../include/features.php:72
-msgid ""
-"Allow optional encryption of content end-to-end with a shared secret key"
-msgstr "Permettre le chiffrement optionnel du contenu de bout en bout au moyen d'un secret partagé"
+#: ../../include/text.php:1151
+msgid "cranky"
+msgstr "énervé"
-#: ../../include/features.php:73
-msgid "Enable Voting Tools"
-msgstr "Activer les outils de vote"
+#: ../../include/text.php:1152
+msgid "disturbed"
+msgstr "perturbé"
-#: ../../include/features.php:73
-msgid "Provide a class of post which others can vote on"
-msgstr "Fournit un type de publication sur lequel les utilisateurs peuvent voter"
+#: ../../include/text.php:1153
+msgid "frustrated"
+msgstr "frustré"
-#: ../../include/features.php:74
-msgid "Delayed Posting"
-msgstr "Publication plus tard"
+#: ../../include/text.php:1154
+msgid "depressed"
+msgstr "déprimé"
-#: ../../include/features.php:74
-msgid "Allow posts to be published at a later date"
-msgstr "Permettre de publier des messages à une date programmée"
+#: ../../include/text.php:1155
+msgid "motivated"
+msgstr "motivé"
-#: ../../include/features.php:75
-msgid "Suppress Duplicate Posts/Comments"
-msgstr "Supprimer les publications/commentaires en doublon"
+#: ../../include/text.php:1156
+msgid "relaxed"
+msgstr "détendu"
-#: ../../include/features.php:75
-msgid ""
-"Prevent posts with identical content to be published with less than two "
-"minutes in between submissions."
-msgstr "Empêcher des messages aux contenus identiques d'être publiés à moins de deux minutes d'intervalle"
+#: ../../include/text.php:1157
+msgid "surprised"
+msgstr "surpris"
-#: ../../include/features.php:81
-msgid "Network and Stream Filtering"
-msgstr "Filtrage du réseau et des flux"
+#: ../../include/text.php:1330 ../../include/js_strings.php:70
+msgid "Monday"
+msgstr "Lundi"
-#: ../../include/features.php:82
-msgid "Search by Date"
-msgstr "Chercher par date"
+#: ../../include/text.php:1330 ../../include/js_strings.php:71
+msgid "Tuesday"
+msgstr "Mardi"
-#: ../../include/features.php:82
-msgid "Ability to select posts by date ranges"
-msgstr "Pouvoir choisir des publications par date"
+#: ../../include/text.php:1330 ../../include/js_strings.php:72
+msgid "Wednesday"
+msgstr "Mercredi"
-#: ../../include/features.php:83 ../../include/group.php:311
-msgid "Privacy Groups"
-msgstr "Groupes d'accès"
+#: ../../include/text.php:1330 ../../include/js_strings.php:73
+msgid "Thursday"
+msgstr "Jeudi"
-#: ../../include/features.php:83
-msgid "Enable management and selection of privacy groups"
-msgstr "Active la gestion et la sélection des groupes d'accès"
+#: ../../include/text.php:1330 ../../include/js_strings.php:74
+msgid "Friday"
+msgstr "Vendredi"
-#: ../../include/features.php:84
-msgid "Save search terms for re-use"
-msgstr "Sauvegarder des termes de recherche pour utilisation ultérieure"
+#: ../../include/text.php:1330 ../../include/js_strings.php:75
+msgid "Saturday"
+msgstr "Samedi"
-#: ../../include/features.php:85
-msgid "Network Personal Tab"
-msgstr "Onglet \"Me concernant\""
+#: ../../include/text.php:1330 ../../include/js_strings.php:69
+msgid "Sunday"
+msgstr "Dimanche"
-#: ../../include/features.php:85
-msgid "Enable tab to display only Network posts that you've interacted on"
-msgstr "Activer un onglet affichant seulement les publications du réseau sur lesquelles vous êtes intervenu"
+#: ../../include/text.php:1334 ../../include/js_strings.php:45
+msgid "January"
+msgstr "Janvier"
-#: ../../include/features.php:86
-msgid "Network New Tab"
-msgstr "Onglet \"nouveautés réseau\""
+#: ../../include/text.php:1334 ../../include/js_strings.php:46
+msgid "February"
+msgstr "Février"
-#: ../../include/features.php:86
-msgid "Enable tab to display all new Network activity"
-msgstr "Activer un onglet présentant toute l'activité récente sur le réseau"
+#: ../../include/text.php:1334 ../../include/js_strings.php:47
+msgid "March"
+msgstr "Mars"
-#: ../../include/features.php:87
-msgid "Affinity Tool"
-msgstr "Gérer l'affinité"
+#: ../../include/text.php:1334 ../../include/js_strings.php:48
+msgid "April"
+msgstr "Avril"
-#: ../../include/features.php:87
-msgid "Filter stream activity by depth of relationships"
-msgstr "Filtrer le flux d'activité en fonction de la profondeur des relations"
+#: ../../include/text.php:1334
+msgid "May"
+msgstr "Mai"
-#: ../../include/features.php:88
-msgid "Connection Filtering"
-msgstr "Filtrage des contacts"
+#: ../../include/text.php:1334 ../../include/js_strings.php:50
+msgid "June"
+msgstr "Juin"
-#: ../../include/features.php:88
-msgid "Filter incoming posts from connections based on keywords/content"
-msgstr "Filtrer les publications entrantes de mes contacts sur la base de mots-clefs"
+#: ../../include/text.php:1334 ../../include/js_strings.php:51
+msgid "July"
+msgstr "Juillet"
-#: ../../include/features.php:89
-msgid "Show channel suggestions"
-msgstr "Montrer les suggestions de canaux"
+#: ../../include/text.php:1334 ../../include/js_strings.php:52
+msgid "August"
+msgstr "Août"
-#: ../../include/features.php:94
-msgid "Post/Comment Tools"
-msgstr "Gérer les publications/commentaires"
+#: ../../include/text.php:1334 ../../include/js_strings.php:53
+msgid "September"
+msgstr "Septembre"
-#: ../../include/features.php:95
-msgid "Community Tagging"
-msgstr "Etiquetage communautaire"
+#: ../../include/text.php:1334 ../../include/js_strings.php:54
+msgid "October"
+msgstr "Octobre"
-#: ../../include/features.php:95
-msgid "Ability to tag existing posts"
-msgstr "Permettre de marquer les publications existantes"
+#: ../../include/text.php:1334 ../../include/js_strings.php:55
+msgid "November"
+msgstr "Novembre"
-#: ../../include/features.php:96
-msgid "Post Categories"
-msgstr "Catégoriser les publications"
+#: ../../include/text.php:1334 ../../include/js_strings.php:56
+msgid "December"
+msgstr "Décembre"
-#: ../../include/features.php:96
-msgid "Add categories to your posts"
-msgstr "Ajouter des catégories à vos publications"
+#: ../../include/text.php:1411 ../../include/text.php:1415
+msgid "Unknown Attachment"
+msgstr "Pièce jointe inconnue"
-#: ../../include/features.php:97
-msgid "Emoji Reactions"
-msgstr ""
+#: ../../include/text.php:1417
+msgid "unknown"
+msgstr "Inconnu"
-#: ../../include/features.php:97
-msgid "Add emoji reaction ability to posts"
-msgstr ""
+#: ../../include/text.php:1453
+msgid "remove category"
+msgstr "supprimer la catégorie"
-#: ../../include/features.php:98
-msgid "Ability to file posts under folders"
-msgstr "Permettre de classer les publications dans des dossiers"
+#: ../../include/text.php:1527
+msgid "remove from file"
+msgstr "retirer du fichier"
-#: ../../include/features.php:99
-msgid "Dislike Posts"
-msgstr "\"Ne pas aimer\" les publications"
+#: ../../include/text.php:1789 ../../include/language.php:367
+msgid "default"
+msgstr "défaut"
-#: ../../include/features.php:99
-msgid "Ability to dislike posts/comments"
-msgstr "Possibilité de \"ne pas aimer\" les publications/commentaires"
+#: ../../include/text.php:1797
+msgid "Page layout"
+msgstr "Mise en page"
-#: ../../include/features.php:100
-msgid "Star Posts"
-msgstr "Pouvoir mettre en avant les publications"
+#: ../../include/text.php:1797
+msgid "You can create your own with the layouts tool"
+msgstr "Créez les vôtres avec les outils de mise en page"
-#: ../../include/features.php:100
-msgid "Ability to mark special posts with a star indicator"
-msgstr "Pouvoir marquer certaines publications d'une étoile"
+#: ../../include/text.php:1825
+msgid "Page content type"
+msgstr "Type de contenu de la page"
-#: ../../include/features.php:101
-msgid "Tag Cloud"
-msgstr "Nuage de tags"
+#: ../../include/text.php:1958
+msgid "activity"
+msgstr "activité"
-#: ../../include/features.php:101
-msgid "Provide a personal tag cloud on your channel page"
-msgstr "Afficher un nuage de vos tags sur votre canal"
+#: ../../include/text.php:2272
+msgid "Design Tools"
+msgstr "Outils de conception"
-#: ../../include/oembed.php:324
-msgid "Embedded content"
-msgstr "Contenu imbriqué"
+#: ../../include/text.php:2278
+msgid "Pages"
+msgstr "Pages"
-#: ../../include/oembed.php:333
-msgid "Embedding disabled"
-msgstr "Imbrication désactivée"
+#: ../../include/text.php:2300
+msgid "Import website..."
+msgstr "Importer le site web…"
-#: ../../include/acl_selectors.php:271
-msgid "Who can see this?"
-msgstr ""
+#: ../../include/text.php:2301
+msgid "Select folder to import"
+msgstr "Sélectionner le dossier à importer"
-#: ../../include/acl_selectors.php:272
-msgid "Custom selection"
-msgstr ""
+#: ../../include/text.php:2302
+msgid "Import from a zipped folder:"
+msgstr "Importer à partir d'un dossier zippé :"
-#: ../../include/acl_selectors.php:273
-msgid ""
-"Select \"Show\" to allow viewing. \"Don't show\" lets you override and limit"
-" the scope of \"Show\"."
-msgstr ""
+#: ../../include/text.php:2303
+msgid "Import from cloud files:"
+msgstr "Importer à partir de fichiers dans le cloud :"
-#: ../../include/acl_selectors.php:274
-msgid "Show"
-msgstr "Montrer"
+#: ../../include/text.php:2304
+msgid "/cloud/channel/path/to/folder"
+msgstr "/cloud/channel/chemain/du/repertoire"
-#: ../../include/acl_selectors.php:275
-msgid "Don't show"
-msgstr "Cacher"
+#: ../../include/text.php:2305
+msgid "Enter path to website files"
+msgstr "Entrer le chemin vers les fichiers du site web"
-#: ../../include/acl_selectors.php:281
-msgid "Other networks and post services"
-msgstr "Autres réseaux et services de messagerie"
+#: ../../include/text.php:2306
+msgid "Select folder"
+msgstr "Sélectionner un répertoire"
-#: ../../include/acl_selectors.php:311
-#, php-format
-msgid ""
-"Post permissions %s cannot be changed %s after a post is shared.</br />These"
-" permissions set who is allowed to view the post."
-msgstr ""
+#: ../../include/text.php:2307
+msgid "Export website..."
+msgstr "Exporter le site web…"
-#: ../../include/auth.php:105
-msgid "Logged out."
-msgstr "Deconnecté."
+#: ../../include/text.php:2308
+msgid "Export to a zip file"
+msgstr "Exporter dans un fichier zip"
-#: ../../include/auth.php:212
-msgid "Failed authentication"
-msgstr "Échec de l'authentification"
+#: ../../include/text.php:2309
+msgid "website.zip"
+msgstr "website.zip"
-#: ../../include/datetime.php:135
-msgid "Birthday"
-msgstr "Anniversaire"
+#: ../../include/text.php:2310
+msgid "Enter a name for the zip file."
+msgstr "Entrer un nom pour le fichier zip."
-#: ../../include/datetime.php:137
-msgid "Age: "
-msgstr "Age&nbsp;:"
+#: ../../include/text.php:2311
+msgid "Export to cloud files"
+msgstr "Exporter dans des fichiers sur le cloud"
-#: ../../include/datetime.php:139
-msgid "YYYY-MM-DD or MM-DD"
-msgstr "AAAA-MM-JJ ou MM-JJ"
+#: ../../include/text.php:2312
+msgid "/path/to/export/folder"
+msgstr "/chemin/vers/le/dossier/d'export"
-#: ../../include/datetime.php:272 ../../boot.php:2470
-msgid "never"
-msgstr "jamais"
+#: ../../include/text.php:2313
+msgid "Enter a path to a cloud files destination."
+msgstr "Entrer le chemin vers le cloud de fichiers"
-#: ../../include/datetime.php:278
-msgid "less than a second ago"
-msgstr "à l'instant"
+#: ../../include/text.php:2314
+msgid "Specify folder"
+msgstr "Spécifier un répertoire"
-#: ../../include/datetime.php:296
+#: ../../include/contact_widgets.php:11
#, php-format
-msgctxt "e.g. 22 hours ago, 1 minute ago"
-msgid "%1$d %2$s ago"
-msgstr "il y a %1$d %2$s"
+msgid "%d invitation available"
+msgid_plural "%d invitations available"
+msgstr[0] "%d invitation disponible"
+msgstr[1] "%d invitations disponibles"
-#: ../../include/datetime.php:307
-msgctxt "relative_date"
-msgid "year"
-msgid_plural "years"
-msgstr[0] "an"
-msgstr[1] "ans"
+#: ../../include/contact_widgets.php:19
+msgid "Find Channels"
+msgstr "Trouver des canaux"
-#: ../../include/datetime.php:310
-msgctxt "relative_date"
-msgid "month"
-msgid_plural "months"
-msgstr[0] "mois"
-msgstr[1] "mois"
+#: ../../include/contact_widgets.php:20
+msgid "Enter name or interest"
+msgstr "Saisir nom ou centre d'intérêt"
-#: ../../include/datetime.php:313
-msgctxt "relative_date"
-msgid "week"
-msgid_plural "weeks"
-msgstr[0] "semaine"
-msgstr[1] "semaines"
+#: ../../include/contact_widgets.php:21
+msgid "Connect/Follow"
+msgstr "Ajouter/Suivre"
-#: ../../include/datetime.php:316
-msgctxt "relative_date"
-msgid "day"
-msgid_plural "days"
-msgstr[0] "jour"
-msgstr[1] "jours"
+#: ../../include/contact_widgets.php:22
+msgid "Examples: Robert Morgenstein, Fishing"
+msgstr "Exemples: Guillaume Martin, Course à pieds"
-#: ../../include/datetime.php:319
-msgctxt "relative_date"
-msgid "hour"
-msgid_plural "hours"
-msgstr[0] "heure"
-msgstr[1] "heures"
+#: ../../include/contact_widgets.php:26
+msgid "Random Profile"
+msgstr "Un profil au hasard"
-#: ../../include/datetime.php:322
-msgctxt "relative_date"
-msgid "minute"
-msgid_plural "minutes"
-msgstr[0] "minute"
-msgstr[1] "minutes"
+#: ../../include/contact_widgets.php:27
+msgid "Invite Friends"
+msgstr "Inviter des amis"
-#: ../../include/datetime.php:325
-msgctxt "relative_date"
-msgid "second"
-msgid_plural "seconds"
-msgstr[0] "seconde"
-msgstr[1] "secondes"
+#: ../../include/contact_widgets.php:29
+msgid "Advanced example: name=fred and country=iceland"
+msgstr "Exemple avancé&nbsp;: name=fred and country=iceland"
-#: ../../include/datetime.php:562
+#: ../../include/contact_widgets.php:122
#, php-format
-msgid "%1$s's birthday"
-msgstr "Anniversaire de %1$s"
+msgid "%d connection in common"
+msgid_plural "%d connections in common"
+msgstr[0] "%d contact en commun"
+msgstr[1] "%d contacts en commun"
-#: ../../include/datetime.php:563
-#, php-format
-msgid "Happy Birthday %1$s"
-msgstr "Joyeux Anniversaire %1$s"
+#: ../../include/contact_widgets.php:127
+msgid "show more"
+msgstr "montrer plus"
-#: ../../include/group.php:26
-msgid ""
-"A deleted group with this name was revived. Existing item permissions "
-"<strong>may</strong> apply to this group and any future members. If this is "
-"not what you intended, please create another group with a different name."
-msgstr "Un groupe supprimé portant ce nom a été ressuscité. Les permissions liées aux éléments existants <strong>peuvent</strong> s'appliquer au groupe et aux membres futurs. Si ce n'est pas ce que vous attendiez, merci de créer un autre groupe avec un nom différent."
+#: ../../include/markdown.php:444
+msgid "Attachments:"
+msgstr ""
-#: ../../include/group.php:248
-msgid "Add new connections to this privacy group"
-msgstr "Ajouter de nouveaux contacts à ce groupe d'accès"
+#: ../../include/markdown.php:538 ../../include/event.php:22
+#: ../../include/event.php:69
+msgid "l F d, Y \\@ g:i A"
+msgstr "l d F Y \\à G\\hi"
-#: ../../include/group.php:289
-msgid "edit"
-msgstr "modifier"
+#: ../../include/markdown.php:540
+msgid "$Projectname event notification:"
+msgstr ""
-#: ../../include/group.php:312
-msgid "Edit group"
-msgstr "Modifier le groupe"
+#: ../../include/markdown.php:544 ../../include/event.php:30
+#: ../../include/event.php:73
+msgid "Starts:"
+msgstr "Début&nbsp;:"
-#: ../../include/group.php:313
-msgid "Add privacy group"
-msgstr "Ajouter un groupe d'accès"
+#: ../../include/markdown.php:552 ../../include/event.php:40
+#: ../../include/event.php:77
+msgid "Finishes:"
+msgstr "Fin&nbsp;:"
-#: ../../include/group.php:314
-msgid "Channels not in any privacy group"
-msgstr "Canaux n'étant dans aucun groupe d'accès"
+#: ../../include/follow.php:26
+msgid "Channel is blocked on this site."
+msgstr "Ce canal est bloqué sur ce site."
+
+#: ../../include/follow.php:31
+msgid "Channel location missing."
+msgstr "Emplacement du canal introuvable."
+
+#: ../../include/follow.php:73
+msgid "Response from remote channel was incomplete."
+msgstr "La réponse du canal distant était incomplète."
+
+#: ../../include/follow.php:90
+msgid "Channel was deleted and no longer exists."
+msgstr "Le canal a été supprimé et n'existe plus."
+
+#: ../../include/follow.php:140 ../../include/follow.php:175
+msgid "Protocol disabled."
+msgstr "Protocole désactivé."
+
+#: ../../include/follow.php:163
+msgid "Channel discovery failed."
+msgstr "La tentative d'accéder au canal a échoué."
+
+#: ../../include/follow.php:202
+msgid "Cannot connect to yourself."
+msgstr "Ne peut pas se connecter à vous."
#: ../../include/js_strings.php:5
msgid "Delete this item?"
msgstr "Supprimer cet élément?"
#: ../../include/js_strings.php:8
-msgid "[-] show less"
-msgstr "[-] montrer moins"
+#, php-format
+msgid "%s show less"
+msgstr "%s afficher moins"
#: ../../include/js_strings.php:9
-msgid "[+] expand"
-msgstr "[+] déplier"
+#, php-format
+msgid "%s expand"
+msgstr "%s dérouler"
#: ../../include/js_strings.php:10
-msgid "[-] collapse"
-msgstr "[-] replier"
+#, php-format
+msgid "%s collapse"
+msgstr "%s enrouler"
#: ../../include/js_strings.php:11
msgid "Password too short"
@@ -9246,7 +11955,7 @@ msgstr "%d années"
#: ../../include/js_strings.php:42
msgid " "
-msgstr ""
+msgstr " "
#: ../../include/js_strings.php:43
msgid "timeago.numbers"
@@ -9359,470 +12068,1219 @@ msgctxt "calendar"
msgid "All day"
msgstr "Toute la journée"
-#: ../../include/network.php:657
+#: ../../include/message.php:30
+msgid "Unable to determine sender."
+msgstr "Impossible de déterminer l'émetteur."
+
+#: ../../include/message.php:67
+msgid "No recipient provided."
+msgstr "Pas de destinataire."
+
+#: ../../include/message.php:72
+msgid "[no subject]"
+msgstr "[sans objet]"
+
+#: ../../include/message.php:223
+msgid "Stored post could not be verified."
+msgstr "Le message stocké n'a pas pu être vérifié."
+
+#: ../../include/activities.php:41
+msgid " and "
+msgstr "et"
+
+#: ../../include/activities.php:49
+msgid "public profile"
+msgstr "profil public"
+
+#: ../../include/activities.php:58
+#, php-format
+msgid "%1$s changed %2$s to &ldquo;%3$s&rdquo;"
+msgstr "%1$s a changé %2$s en &ldquo;%3$s&rdquo;"
+
+#: ../../include/activities.php:59
+#, php-format
+msgid "Visit %1$s's %2$s"
+msgstr "Visiter %2$s de %1$s"
+
+#: ../../include/activities.php:62
+#, php-format
+msgid "%1$s has an updated %2$s, changing %3$s."
+msgstr "%1$s a mis à jour %2$s, modifiant %3$s."
+
+#: ../../include/attach.php:250 ../../include/attach.php:339
+msgid "Item was not found."
+msgstr "Élément introuvable."
+
+#: ../../include/attach.php:500
+msgid "No source file."
+msgstr "Pas de fichier source."
+
+#: ../../include/attach.php:522
+msgid "Cannot locate file to replace"
+msgstr "Impossible de trouver le fichier à remplacer."
+
+#: ../../include/attach.php:540
+msgid "Cannot locate file to revise/update"
+msgstr "Impossible de trouver le fichier à corriger/mettre à jour"
+
+#: ../../include/attach.php:671
+#, php-format
+msgid "File exceeds size limit of %d"
+msgstr "Le fichier dépasse la taille limite de %d"
+
+#: ../../include/attach.php:685
+#, php-format
+msgid "You have reached your limit of %1$.0f Mbytes attachment storage."
+msgstr "Vous avez atteint votre limite de %1$.0f méga-octets autorisés pour le stockage des pièces-jointes."
+
+#: ../../include/attach.php:855
+msgid "File upload failed. Possible system limit or action terminated."
+msgstr "Envoi du fichier impossible. Limite système ou action avortée."
+
+#: ../../include/attach.php:868
+msgid "Stored file could not be verified. Upload failed."
+msgstr "Le fichier stocké n'a pu être vérifié. Echec de l'envoi."
+
+#: ../../include/attach.php:923 ../../include/attach.php:939
+msgid "Path not available."
+msgstr "Chemin non disponible."
+
+#: ../../include/attach.php:988 ../../include/attach.php:1153
+msgid "Empty pathname"
+msgstr "Chemin vide"
+
+#: ../../include/attach.php:1014
+msgid "duplicate filename or path"
+msgstr "doublon de chemin ou de fichier"
+
+#: ../../include/attach.php:1039
+msgid "Path not found."
+msgstr "Chemin introuvable."
+
+#: ../../include/attach.php:1107
+msgid "mkdir failed."
+msgstr "mkdir a échoué."
+
+#: ../../include/attach.php:1111
+msgid "database storage failed."
+msgstr "l'écriture dans la base de données a échoué."
+
+#: ../../include/attach.php:1159
+msgid "Empty path"
+msgstr "Chemin vide"
+
+#: ../../include/security.php:117
+msgid "guest:"
+msgstr "Visiteur"
+
+#: ../../include/security.php:532
+msgid ""
+"The form security token was not correct. This probably happened because the "
+"form has been opened for too long (>3 hours) before submitting it."
+msgstr "Le formulaire n'est plus sécurisé, probablement parce qu'il est ouvert depuis trop longtemps (plus de 3 heures)."
+
+#: ../../include/items.php:846 ../../include/items.php:893
+msgid "(Unknown)"
+msgstr "(Inconnu)"
+
+#: ../../include/items.php:1094
+msgid "Visible to anybody on the internet."
+msgstr "Visible pour tout le monde sur internet."
+
+#: ../../include/items.php:1096
+msgid "Visible to you only."
+msgstr "Visible pour vous seulement."
+
+#: ../../include/items.php:1098
+msgid "Visible to anybody in this network."
+msgstr "Visible pour tout le monde sur ce réseau."
+
+#: ../../include/items.php:1100
+msgid "Visible to anybody authenticated."
+msgstr "Visible aux utilisateurs authentifiés."
+
+#: ../../include/items.php:1102
+#, php-format
+msgid "Visible to anybody on %s."
+msgstr "Visible pour tous sur %s."
+
+#: ../../include/items.php:1104
+msgid "Visible to all connections."
+msgstr "Visible pour tous les contacts."
+
+#: ../../include/items.php:1106
+msgid "Visible to approved connections."
+msgstr "Visible aux contacts approuvés."
+
+#: ../../include/items.php:1108
+msgid "Visible to specific connections."
+msgstr "Visible pour certains contacts."
+
+#: ../../include/items.php:3925
+msgid "Privacy group is empty."
+msgstr "Groupe de contacts vide."
+
+#: ../../include/items.php:3932
+#, php-format
+msgid "Privacy group: %s"
+msgstr "Groupe de contacts&nbsp;: %s"
+
+#: ../../include/items.php:3944
+msgid "Connection not found."
+msgstr "Contact non trouvé."
+
+#: ../../include/items.php:4293
+msgid "profile photo"
+msgstr "photo de profil"
+
+#: ../../include/items.php:4489
+#, php-format
+msgid "[Edited %s]"
+msgstr "[%s édité]"
+
+#: ../../include/items.php:4489
+msgctxt "edit_activity"
+msgid "Post"
+msgstr "Publier"
+
+#: ../../include/items.php:4489
+msgctxt "edit_activity"
+msgid "Comment"
+msgstr "Commenter"
+
+#: ../../include/channel.php:33
+msgid "Unable to obtain identity information from database"
+msgstr "Impossible d'obtenir les données d'identité depuis la base de données"
+
+#: ../../include/channel.php:67
+msgid "Empty name"
+msgstr "Nom vide"
+
+#: ../../include/channel.php:70
+msgid "Name too long"
+msgstr "Nom trop long"
+
+#: ../../include/channel.php:181
+msgid "No account identifier"
+msgstr "Pas d'identifiant de compte"
+
+#: ../../include/channel.php:193
+msgid "Nickname is required."
+msgstr "Un surnom est requis."
+
+#: ../../include/channel.php:207
+msgid "Reserved nickname. Please choose another."
+msgstr "Surnom réservé. Merci d'en choisir un autre."
+
+#: ../../include/channel.php:212
+msgid ""
+"Nickname has unsupported characters or is already being used on this site."
+msgstr "Le surnom contient des caractères interdits ou est déjà pris sur ce site."
+
+#: ../../include/channel.php:270
+msgid "Unable to retrieve created identity"
+msgstr "Impossible de récupérer l'identité créée"
+
+#: ../../include/channel.php:342
+msgid "Default Profile"
+msgstr "Profil par défaut"
+
+#: ../../include/channel.php:1043
+msgid "Create New Profile"
+msgstr "Créer un nouveau profil"
+
+#: ../../include/channel.php:1063
+msgid "Visible to everybody"
+msgstr "Visible de tous"
+
+#: ../../include/channel.php:1136 ../../include/channel.php:1250
+msgid "Gender:"
+msgstr "Sexe&nbsp;:"
+
+#: ../../include/channel.php:1138 ../../include/channel.php:1305
+msgid "Homepage:"
+msgstr "Site Internet&nbsp;:"
+
+#: ../../include/channel.php:1139
+msgid "Online Now"
+msgstr "Connecté"
+
+#: ../../include/channel.php:1255
+msgid "Like this channel"
+msgstr "J'aime ce canal"
+
+#: ../../include/channel.php:1279
+msgid "j F, Y"
+msgstr "j F, Y"
+
+#: ../../include/channel.php:1280
+msgid "j F"
+msgstr "j F"
+
+#: ../../include/channel.php:1287
+msgid "Birthday:"
+msgstr "Date de naissance&nbsp;:"
+
+#: ../../include/channel.php:1300
+#, php-format
+msgid "for %1$d %2$s"
+msgstr "depuis %1$d %2$s"
+
+#: ../../include/channel.php:1303
+msgid "Sexual Preference:"
+msgstr "Orientation sexuelle&nbsp;:"
+
+#: ../../include/channel.php:1309
+msgid "Tags:"
+msgstr "Étiquettes&nbsp;:"
+
+#: ../../include/channel.php:1311
+msgid "Political Views:"
+msgstr "Opinions politiques&nbsp;:"
+
+#: ../../include/channel.php:1313
+msgid "Religion:"
+msgstr "Religion&nbsp;:"
+
+#: ../../include/channel.php:1317
+msgid "Hobbies/Interests:"
+msgstr "Occupations/Centres d'intérêt&nbsp;:"
+
+#: ../../include/channel.php:1319
+msgid "Likes:"
+msgstr "Aime&nbsp;:"
+
+#: ../../include/channel.php:1321
+msgid "Dislikes:"
+msgstr "N'aime pas&nbsp;:"
+
+#: ../../include/channel.php:1323
+msgid "Contact information and Social Networks:"
+msgstr "Coordonnées et réseaux sociaux&nbsp;:"
+
+#: ../../include/channel.php:1325
+msgid "My other channels:"
+msgstr "Mes autres canaux&nbsp;:"
+
+#: ../../include/channel.php:1327
+msgid "Musical interests:"
+msgstr "Goûts musicaux&nbsp;:"
+
+#: ../../include/channel.php:1329
+msgid "Books, literature:"
+msgstr "Lectures, goûts littéraires&nbsp;:"
+
+#: ../../include/channel.php:1331
+msgid "Television:"
+msgstr "Télévision&nbsp;:"
+
+#: ../../include/channel.php:1333
+msgid "Film/dance/culture/entertainment:"
+msgstr "Cinéma/danse/culture/divertissement&nsbp;:"
+
+#: ../../include/channel.php:1335
+msgid "Love/Romance:"
+msgstr "Vie sentimentale/amoureuse&nbsp;:"
+
+#: ../../include/channel.php:1337
+msgid "Work/employment:"
+msgstr "Travail/Occupation&nbsp;"
+
+#: ../../include/channel.php:1339
+msgid "School/education:"
+msgstr "Études&nbsp;"
+
+#: ../../include/channel.php:1362
+msgid "Like this thing"
+msgstr "J'aime ceci"
+
+#: ../../include/channel.php:2135
+#, php-format
+msgid "User '%s' deleted"
+msgstr "Utilisateur '%s' supprimé"
+
+#: ../../include/event.php:1004
+msgid "This event has been added to your calendar."
+msgstr "Cet évènement a été ajouté dans votre calendrier."
+
+#: ../../include/event.php:1204
+msgid "Not specified"
+msgstr "Non spécifié"
+
+#: ../../include/event.php:1205
+msgid "Needs Action"
+msgstr "Besoin d'une action"
+
+#: ../../include/event.php:1206
+msgid "Completed"
+msgstr "Terminé"
+
+#: ../../include/event.php:1207
+msgid "In Process"
+msgstr "En cours"
+
+#: ../../include/event.php:1208
+msgid "Cancelled"
+msgstr "Annulé"
+
+#: ../../include/network.php:756
msgid "view full size"
msgstr "voir en taille réelle"
-#: ../../include/network.php:1885
+#: ../../include/network.php:2011
msgid "No Subject"
msgstr "Pas d'objet"
-#: ../../include/network.php:2146 ../../include/network.php:2147
+#: ../../include/network.php:2265 ../../include/network.php:2266
msgid "Friendica"
msgstr "Friendica"
-#: ../../include/network.php:2148
+#: ../../include/network.php:2267
msgid "OStatus"
msgstr "OStatus"
-#: ../../include/network.php:2149
+#: ../../include/network.php:2268
msgid "GNU-Social"
-msgstr ""
+msgstr "GNU-Social"
-#: ../../include/network.php:2150
+#: ../../include/network.php:2269
msgid "RSS/Atom"
msgstr "RSS/Atom"
-#: ../../include/network.php:2152
+#: ../../include/network.php:2271
msgid "Diaspora"
msgstr "Diaspora"
-#: ../../include/network.php:2153
+#: ../../include/network.php:2272
msgid "Facebook"
msgstr "Facebook"
-#: ../../include/network.php:2154
+#: ../../include/network.php:2273
msgid "Zot"
msgstr "Zot"
-#: ../../include/network.php:2155
+#: ../../include/network.php:2274
msgid "LinkedIn"
msgstr "Linkedin"
-#: ../../include/network.php:2156
+#: ../../include/network.php:2275
msgid "XMPP/IM"
msgstr "XMPP/IM"
-#: ../../include/network.php:2157
+#: ../../include/network.php:2276
msgid "MySpace"
msgstr "MySpace"
-#: ../../include/photos.php:110
-#, php-format
-msgid "Image exceeds website size limit of %lu bytes"
-msgstr "L'image dépasse la taille limite de %lu octets"
+#: ../../include/page_widgets.php:7
+msgid "New Page"
+msgstr "Nouvelle page"
-#: ../../include/photos.php:117
-msgid "Image file is empty."
-msgstr "L'image est vide."
+#: ../../include/language.php:380
+msgid "Select an alternate language"
+msgstr "Choisir une langue alternative"
-#: ../../include/photos.php:255
-msgid "Photo storage failed."
-msgstr "Le stockage de l'image a échoué."
+#: ../../include/acl_selectors.php:208
+msgid "Who can see this?"
+msgstr "Qui peut voir cela"
-#: ../../include/photos.php:295
-msgid "a new photo"
-msgstr "une nouvelle photo"
+#: ../../include/acl_selectors.php:209
+msgid "Custom selection"
+msgstr "Sélection personnalisée"
-#: ../../include/photos.php:299
+#: ../../include/acl_selectors.php:210
+msgid ""
+"Select \"Show\" to allow viewing. \"Don't show\" lets you override and limit"
+" the scope of \"Show\"."
+msgstr "Sélectionnez \"Afficher\" pour permettre l'affichage. \"Ne pas afficher\" vous permet de remplacer et de limiter la portée de \"Afficher\"."
+
+#: ../../include/acl_selectors.php:211
+msgid "Show"
+msgstr "Montrer"
+
+#: ../../include/acl_selectors.php:212
+msgid "Don't show"
+msgstr "Cacher"
+
+#: ../../include/acl_selectors.php:245
#, php-format
-msgctxt "photo_upload"
-msgid "%1$s posted %2$s to %3$s"
-msgstr "%1$s a publié %2$s pour %3$s"
+msgid ""
+"Post permissions %s cannot be changed %s after a post is shared.</br />These"
+" permissions set who is allowed to view the post."
+msgstr "Les autorisations d'accès d'un message %s ne peuvent pas être modifiées %s une fois le message envoyé. Ces autorisations définissent qui est autorisé à afficher le message."
-#: ../../include/photos.php:506
-msgid "Upload New Photos"
-msgstr "Ajouter des photos"
+#: ../../include/dba/dba_driver.php:189
+#, php-format
+msgid "Cannot locate DNS info for database server '%s'"
+msgstr "Impossible de trouver les infos DNS du serveur de BDD '%s'"
-#: ../../include/zot.php:699
-msgid "Invalid data packet"
-msgstr "Paquet de données invalide"
+#: ../../include/bbcode.php:134 ../../include/bbcode.php:1040
+#: ../../include/bbcode.php:1043 ../../include/bbcode.php:1048
+#: ../../include/bbcode.php:1051 ../../include/bbcode.php:1054
+#: ../../include/bbcode.php:1057 ../../include/bbcode.php:1062
+#: ../../include/bbcode.php:1065 ../../include/bbcode.php:1070
+#: ../../include/bbcode.php:1073 ../../include/bbcode.php:1076
+#: ../../include/bbcode.php:1079
+msgid "Image/photo"
+msgstr "Image/photo"
-#: ../../include/zot.php:715
-msgid "Unable to verify channel signature"
-msgstr "Impossible de vérifier la signature du canal"
+#: ../../include/bbcode.php:173 ../../include/bbcode.php:1090
+msgid "Encrypted content"
+msgstr "Contenu chiffré"
-#: ../../include/zot.php:2363
+#: ../../include/bbcode.php:189
#, php-format
-msgid "Unable to verify site signature for %s"
-msgstr "Impossible de vérifier la signature de site pour %s"
+msgid "Install %s element: "
+msgstr "Installer %s élément"
-#: ../../include/zot.php:3712
-msgid "invalid target signature"
-msgstr "signature de la cible invalide"
+#: ../../include/bbcode.php:193
+#, php-format
+msgid ""
+"This post contains an installable %s element, however you lack permissions "
+"to install it on this site."
+msgstr "Ce message contient un élément installable %s, mais vous n'avez pas l'autorisation de l'installer sur ce site."
-#: ../../include/page_widgets.php:6
-msgid "New Page"
-msgstr "Nouvelle page"
+#: ../../include/bbcode.php:272
+#, php-format
+msgid "%1$s wrote the following %2$s %3$s"
+msgstr "%1$s a écrit %2$s qui suit %3$s"
-#: ../../include/page_widgets.php:43
-msgid "Title"
-msgstr "Titre"
+#: ../../include/bbcode.php:349 ../../include/bbcode.php:357
+msgid "Click to open/close"
+msgstr "Cliquer pour ouvrir/fermer"
-#: ../../include/permissions.php:26
-msgid "Can view my normal stream and posts"
-msgstr "Peut voir les publications ordinaires sur mon canal."
+#: ../../include/bbcode.php:357
+msgid "spoiler"
+msgstr "spoiler"
-#: ../../include/permissions.php:27
-msgid "Can view my default channel profile"
-msgstr "Peut voir le profil du canal par défaut."
+#: ../../include/bbcode.php:1028
+msgid "$1 wrote:"
+msgstr "$1 a écrit&nbsp;:"
-#: ../../include/permissions.php:28
-msgid "Can view my connections"
-msgstr "Peut voir mes contacts"
+#: ../../include/oembed.php:308
+msgid " by "
+msgstr "par"
-#: ../../include/permissions.php:29
-msgid "Can view my file storage and photos"
-msgstr "Peut voir mes fichiers et photos"
+#: ../../include/oembed.php:309
+msgid " on "
+msgstr "sur"
-#: ../../include/permissions.php:30
-msgid "Can view my webpages"
-msgstr "Peut voir mes pages web"
+#: ../../include/oembed.php:338
+msgid "Embedded content"
+msgstr "Contenu imbriqué"
-#: ../../include/permissions.php:33
-msgid "Can send me their channel stream and posts"
-msgstr "Peuvent m'envoyer leur flux et les publications de leur canal"
+#: ../../include/oembed.php:347
+msgid "Embedding disabled"
+msgstr "Imbrication désactivée"
-#: ../../include/permissions.php:34
-msgid "Can post on my channel page (\"wall\")"
-msgstr "Peuvent poster sur la page de mon canal (\"mur\")"
+#: ../../include/features.php:58
+msgid "General Features"
+msgstr "Fonctionnalités générales"
-#: ../../include/permissions.php:35
-msgid "Can comment on or like my posts"
-msgstr "Peuvent commenter et/ou aimer mes publications"
+#: ../../include/features.php:63
+msgid "Multiple Profiles"
+msgstr "Profils multiples"
-#: ../../include/permissions.php:36
-msgid "Can send me private mail messages"
-msgstr "Peuvent m'envoyer des messages privés"
+#: ../../include/features.php:64
+msgid "Ability to create multiple profiles"
+msgstr "Possibilité de créer plusieurs profils"
-#: ../../include/permissions.php:37
-msgid "Can like/dislike stuff"
-msgstr "Peuvent aimer/ne pas aimer"
+#: ../../include/features.php:72
+msgid "Advanced Profiles"
+msgstr "Profils Avancés"
-#: ../../include/permissions.php:37
-msgid "Profiles and things other than posts/comments"
-msgstr "Profils et autres excluant les publications/commentaires."
+#: ../../include/features.php:73
+msgid "Additional profile sections and selections"
+msgstr "Sections et sélections supplémentaires du profil"
-#: ../../include/permissions.php:39
-msgid "Can forward to all my channel contacts via post @mentions"
-msgstr "Peut faire suivre à tous les contacts de mon canal via \"@mention\""
+#: ../../include/features.php:81
+msgid "Profile Import/Export"
+msgstr "Importer/Exporter le profil"
-#: ../../include/permissions.php:39
-msgid "Advanced - useful for creating group forum channels"
-msgstr "Avancé - utile pour les canaux de type \"forum/groupe\""
+#: ../../include/features.php:82
+msgid "Save and load profile details across sites/channels"
+msgstr "Sauvegarder et charger les détails d'un profil entre sites/canaux"
-#: ../../include/permissions.php:40
-msgid "Can chat with me (when available)"
-msgstr "Peut discuter avec moi (quand disponibie)"
+#: ../../include/features.php:90
+msgid "Web Pages"
+msgstr "Pages web"
-#: ../../include/permissions.php:41
-msgid "Can write to my file storage and photos"
-msgstr "Peut charger des fichiers et des photos dans mon canal"
+#: ../../include/features.php:91
+msgid "Provide managed web pages on your channel"
+msgstr "Fournir des pages web, sous votre contrôle, sur votre canal"
-#: ../../include/permissions.php:42
-msgid "Can edit my webpages"
-msgstr "Peut modifier mes pages web"
+#: ../../include/features.php:100
+msgid "Provide a wiki for your channel"
+msgstr "Fournir un wiki pour votre canal."
-#: ../../include/permissions.php:44
-msgid "Can source my public posts in derived channels"
-msgstr "Peut rediriger mes publications publiques vers des canaux dérivés"
+#: ../../include/features.php:117
+msgid "Private Notes"
+msgstr "Notes privées"
-#: ../../include/permissions.php:44
-msgid "Somewhat advanced - very useful in open communities"
-msgstr "Plutôt avancé - très utile dans les communautés ouvertes"
+#: ../../include/features.php:118
+msgid "Enables a tool to store notes and reminders (note: not encrypted)"
+msgstr "Active un outil pour stocker des notes et des rappels (note&nbsp;:non chiffré)"
-#: ../../include/permissions.php:46
-msgid "Can administer my channel resources"
-msgstr "Peut administrer les ressources de mon canal"
+#: ../../include/features.php:126
+msgid "Navigation Channel Select"
+msgstr "Sélection du canal par la navigation"
-#: ../../include/permissions.php:46
+#: ../../include/features.php:127
+msgid "Change channels directly from within the navigation dropdown menu"
+msgstr "Changez de canal directement depuis le menu de navigation déroulant"
+
+#: ../../include/features.php:135
+msgid "Photo Location"
+msgstr "Site de prise de vue"
+
+#: ../../include/features.php:136
+msgid "If location data is available on uploaded photos, link this to a map."
+msgstr "Si des informations géographiques sont présentes dans les images téléversées, les lier à une carte."
+
+#: ../../include/features.php:144
+msgid "Access Controlled Chatrooms"
+msgstr "Accéder au salons de discussions contrôlés."
+
+#: ../../include/features.php:145
+msgid "Provide chatrooms and chat services with access control."
+msgstr "Fournir des salons de discussions et des services de discussions avec contrôle d'accès."
+
+#: ../../include/features.php:154
+msgid "Provide alternate connection permission roles."
+msgstr "Fournir des rôles d'autorisation différents pour ce contact."
+
+#: ../../include/features.php:162
+msgid "Smart Birthdays"
+msgstr "Anniversaires intelligents"
+
+#: ../../include/features.php:163
msgid ""
-"Extremely advanced. Leave this alone unless you know what you are doing"
-msgstr "Très avancé. Ne pas toucher, sauf si vous savez ce que vous faîtes"
+"Make birthday events timezone aware in case your friends are scattered "
+"across the planet."
+msgstr "Adapter les anniversaires aux fuseaux horaires, utile pour vos amis sur d'autres continents."
-#: ../../include/permissions.php:877
-msgid "Social Networking"
-msgstr "Réseau social"
+#: ../../include/features.php:171
+msgid "Event Timezone Selection"
+msgstr "Sélection du fuseau horaire de l'événement"
-#: ../../include/permissions.php:877
-msgid "Social - Mostly Public"
-msgstr "Social - surtout public"
+#: ../../include/features.php:172
+msgid "Allow event creation in timezones other than your own."
+msgstr "Autorise la création d’événements sur d'autres fuseaux horaires que le vôtre."
-#: ../../include/permissions.php:877
-msgid "Social - Restricted"
-msgstr "Social - restreint"
+#: ../../include/features.php:180
+msgid "Advanced Directory Search"
+msgstr "Recherche avancée dans les répertoires"
-#: ../../include/permissions.php:877
-msgid "Social - Private"
-msgstr "Social - privé"
+#: ../../include/features.php:181
+msgid "Allows creation of complex directory search queries"
+msgstr "Autoriser la création d'entrées complexes de recherche de répertoire"
-#: ../../include/permissions.php:878
-msgid "Community Forum"
-msgstr "Forum communautaire"
+#: ../../include/features.php:189
+msgid "Advanced Theme and Layout Settings"
+msgstr "Paramètres avancés du thème et de l'agencement."
-#: ../../include/permissions.php:878
-msgid "Forum - Mostly Public"
-msgstr "Forum - surtout public"
+#: ../../include/features.php:190
+msgid "Allows fine tuning of themes and page layouts"
+msgstr "Autoriser la personnalisation fine des thèmes et des agencements."
-#: ../../include/permissions.php:878
-msgid "Forum - Restricted"
-msgstr "Forum - restreint"
+#: ../../include/features.php:200
+msgid "Post Composition Features"
+msgstr "Fonctionnalités de composition"
-#: ../../include/permissions.php:878
-msgid "Forum - Private"
-msgstr "Forum - privé"
+#: ../../include/features.php:204
+msgid "Large Photos"
+msgstr "Grandes photos"
-#: ../../include/permissions.php:879
-msgid "Feed Republish"
-msgstr "Republication de flux"
+#: ../../include/features.php:205
+msgid ""
+"Include large (1024px) photo thumbnails in posts. If not enabled, use small "
+"(640px) photo thumbnails"
+msgstr "Inclure de grands aperçus (1024px) dans les messages. Si désactivé, inclure de petits aperçus (640px)."
-#: ../../include/permissions.php:879
-msgid "Feed - Mostly Public"
-msgstr "Flux - surtout public"
+#: ../../include/features.php:214
+msgid "Automatically import channel content from other channels or feeds"
+msgstr "Importe automatiquement le contenus d'autres canaux ou flux dans le canal actif"
-#: ../../include/permissions.php:879
-msgid "Feed - Restricted"
-msgstr "Flux - restreint"
+#: ../../include/features.php:222
+msgid "Even More Encryption"
+msgstr "Encore plus de chiffrement"
-#: ../../include/permissions.php:880
-msgid "Special Purpose"
-msgstr "Utilisation spécifique"
+#: ../../include/features.php:223
+msgid ""
+"Allow optional encryption of content end-to-end with a shared secret key"
+msgstr "Permettre le chiffrement optionnel du contenu de bout en bout au moyen d'un secret partagé"
-#: ../../include/permissions.php:880
-msgid "Special - Celebrity/Soapbox"
-msgstr "Spécial - célébrité/promotion"
+#: ../../include/features.php:231
+msgid "Enable Voting Tools"
+msgstr "Activer les outils de vote"
-#: ../../include/permissions.php:880
-msgid "Special - Group Repository"
-msgstr "Spécial - dépôt partagé"
+#: ../../include/features.php:232
+msgid "Provide a class of post which others can vote on"
+msgstr "Fournit un type de publication sur lequel les utilisateurs peuvent voter"
-#: ../../include/permissions.php:881
-msgid "Custom/Expert Mode"
-msgstr "Mode expert/spécifique"
+#: ../../include/features.php:240
+msgid "Disable Comments"
+msgstr "Désactiver les commentaires"
-#: ../../include/activities.php:41
-msgid " and "
-msgstr "et"
+#: ../../include/features.php:241
+msgid "Provide the option to disable comments for a post"
+msgstr "Fournir la possibilité de désactiver les commentaires pour une publication."
-#: ../../include/activities.php:49
-msgid "public profile"
-msgstr "profil public"
+#: ../../include/features.php:249
+msgid "Delayed Posting"
+msgstr "Publication plus tard"
-#: ../../include/activities.php:58
+#: ../../include/features.php:250
+msgid "Allow posts to be published at a later date"
+msgstr "Permettre de publier des messages à une date programmée"
+
+#: ../../include/features.php:258
+msgid "Content Expiration"
+msgstr "Expiration du contenu"
+
+#: ../../include/features.php:259
+msgid "Remove posts/comments and/or private messages at a future time"
+msgstr "Supprimer les contributions/commentaires et/ou messages privés plus tard"
+
+#: ../../include/features.php:267
+msgid "Suppress Duplicate Posts/Comments"
+msgstr "Supprimer les publications/commentaires en doublon"
+
+#: ../../include/features.php:268
+msgid ""
+"Prevent posts with identical content to be published with less than two "
+"minutes in between submissions."
+msgstr "Empêcher des messages aux contenus identiques d'être publiés à moins de deux minutes d'intervalle"
+
+#: ../../include/features.php:279
+msgid "Network and Stream Filtering"
+msgstr "Filtrage du réseau et des flux"
+
+#: ../../include/features.php:283
+msgid "Search by Date"
+msgstr "Chercher par date"
+
+#: ../../include/features.php:284
+msgid "Ability to select posts by date ranges"
+msgstr "Pouvoir choisir des publications par date"
+
+#: ../../include/features.php:292 ../../include/group.php:331
+msgid "Privacy Groups"
+msgstr "Groupes de contacts"
+
+#: ../../include/features.php:293
+msgid "Enable management and selection of privacy groups"
+msgstr "Active la gestion et la sélection des groupes de contacts"
+
+#: ../../include/features.php:302
+msgid "Save search terms for re-use"
+msgstr "Sauvegarder des termes de recherche pour utilisation ultérieure"
+
+#: ../../include/features.php:310
+msgid "Network Personal Tab"
+msgstr "Onglet \"Me concernant\""
+
+#: ../../include/features.php:311
+msgid "Enable tab to display only Network posts that you've interacted on"
+msgstr "Activer un onglet affichant seulement les publications du réseau sur lesquelles vous êtes intervenu"
+
+#: ../../include/features.php:319
+msgid "Network New Tab"
+msgstr "Onglet \"nouveautés réseau\""
+
+#: ../../include/features.php:320
+msgid "Enable tab to display all new Network activity"
+msgstr "Activer un onglet présentant toute l'activité récente sur le réseau"
+
+#: ../../include/features.php:328
+msgid "Affinity Tool"
+msgstr "Gérer l'affinité"
+
+#: ../../include/features.php:329
+msgid "Filter stream activity by depth of relationships"
+msgstr "Filtrer le flux d'activité en fonction de la profondeur des relations"
+
+#: ../../include/features.php:338
+msgid "Show friend and connection suggestions"
+msgstr "Afficher un ami et les suggestions de relations"
+
+#: ../../include/features.php:346
+msgid "Connection Filtering"
+msgstr "Filtrage des contacts"
+
+#: ../../include/features.php:347
+msgid "Filter incoming posts from connections based on keywords/content"
+msgstr "Filtrer les publications entrantes de mes contacts sur la base de mots-clefs"
+
+#: ../../include/features.php:359
+msgid "Post/Comment Tools"
+msgstr "Gérer les publications/commentaires"
+
+#: ../../include/features.php:363
+msgid "Community Tagging"
+msgstr "Etiquetage communautaire"
+
+#: ../../include/features.php:364
+msgid "Ability to tag existing posts"
+msgstr "Permettre de marquer les publications existantes"
+
+#: ../../include/features.php:372
+msgid "Post Categories"
+msgstr "Catégoriser les publications"
+
+#: ../../include/features.php:373
+msgid "Add categories to your posts"
+msgstr "Ajouter des catégories à vos publications"
+
+#: ../../include/features.php:381
+msgid "Emoji Reactions"
+msgstr "Réactions par émoticônes"
+
+#: ../../include/features.php:382
+msgid "Add emoji reaction ability to posts"
+msgstr "Ajouter la possibilité de réagir aux publications par émoticônes"
+
+#: ../../include/features.php:391
+msgid "Ability to file posts under folders"
+msgstr "Permettre de classer les publications dans des dossiers"
+
+#: ../../include/features.php:399
+msgid "Dislike Posts"
+msgstr "\"Ne pas aimer\" les publications"
+
+#: ../../include/features.php:400
+msgid "Ability to dislike posts/comments"
+msgstr "Possibilité de \"ne pas aimer\" les publications/commentaires"
+
+#: ../../include/features.php:408
+msgid "Star Posts"
+msgstr "Pouvoir mettre en avant les publications"
+
+#: ../../include/features.php:409
+msgid "Ability to mark special posts with a star indicator"
+msgstr "Pouvoir marquer certaines publications d'une étoile"
+
+#: ../../include/features.php:417
+msgid "Tag Cloud"
+msgstr "Nuage de tags"
+
+#: ../../include/features.php:418
+msgid "Provide a personal tag cloud on your channel page"
+msgstr "Afficher un nuage de vos tags sur votre canal"
+
+#: ../../include/features.php:430
+msgid "Premium Channel"
+msgstr "Canal VIP"
+
+#: ../../include/features.php:431
+msgid ""
+"Allows you to set restrictions and terms on those that connect with your "
+"channel"
+msgstr "Vous permet d'appliquer des règles et restrictions aux contacts de votre canal"
+
+#: ../../include/taxonomy.php:228 ../../include/taxonomy.php:249
+msgid "Tags"
+msgstr "Étiquettes"
+
+#: ../../include/taxonomy.php:293
+msgid "Keywords"
+msgstr "Mots-clefs"
+
+#: ../../include/taxonomy.php:314
+msgid "have"
+msgstr "ont"
+
+#: ../../include/taxonomy.php:314
+msgid "has"
+msgstr "a"
+
+#: ../../include/taxonomy.php:315
+msgid "want"
+msgstr "veulent"
+
+#: ../../include/taxonomy.php:315
+msgid "wants"
+msgstr "veut"
+
+#: ../../include/taxonomy.php:316
+msgid "likes"
+msgstr "aime"
+
+#: ../../include/taxonomy.php:317
+msgid "dislikes"
+msgstr "n'aime pas"
+
+#: ../../include/account.php:35
+msgid "Not a valid email address"
+msgstr "Ce n'est pas une adresse de courriel valide"
+
+#: ../../include/account.php:37
+msgid "Your email domain is not among those allowed on this site"
+msgstr "Votre domaine de courriel ne fait pas partie de ceux autorisés par ce site"
+
+#: ../../include/account.php:43
+msgid "Your email address is already registered at this site."
+msgstr "Votre adresse de courriel est déjà inscrite sur ce site."
+
+#: ../../include/account.php:75
+msgid "An invitation is required."
+msgstr "Une invitation est requise."
+
+#: ../../include/account.php:79
+msgid "Invitation could not be verified."
+msgstr "Votre invitation n'a pas pu être vérifiée."
+
+#: ../../include/account.php:130
+msgid "Please enter the required information."
+msgstr "Merci d'entrer les informations requises."
+
+#: ../../include/account.php:198
+msgid "Failed to store account information."
+msgstr "Impossible de stocker les informations liées au compte."
+
+#: ../../include/account.php:263
#, php-format
-msgid "%1$s changed %2$s to &ldquo;%3$s&rdquo;"
-msgstr "%1$s a changé %2$s en &ldquo;%3$s&rdquo;"
+msgid "Registration confirmation for %s"
+msgstr "Confirmation de l'inscription pour %s"
-#: ../../include/activities.php:59
+#: ../../include/account.php:330
#, php-format
-msgid "Visit %1$s's %2$s"
-msgstr "Visiter %2$s de %1$s"
+msgid "Registration request at %s"
+msgstr "Demande d'inscription sur %s"
-#: ../../include/activities.php:62
+#: ../../include/account.php:352
+msgid "your registration password"
+msgstr "votre mot de passe d'inscription"
+
+#: ../../include/account.php:358 ../../include/account.php:420
#, php-format
-msgid "%1$s has an updated %2$s, changing %3$s."
-msgstr "%1$s a mis à jour %2$s, modifiant %3$s."
+msgid "Registration details for %s"
+msgstr "Détails de l'inscription pour %s"
-#: ../../include/bb2diaspora.php:398
-msgid "Attachments:"
-msgstr "Pièces jointes&nbsp;:"
+#: ../../include/account.php:431
+msgid "Account approved."
+msgstr "Compte approuvé."
-#: ../../include/bb2diaspora.php:487
-msgid "$Projectname event notification:"
-msgstr "Notification d'événement de $Projectname&nbsp;:"
+#: ../../include/account.php:471
+#, php-format
+msgid "Registration revoked for %s"
+msgstr "Inscription révoquée pour %s"
-#: ../../view/theme/redbasic/php/config.php:82
-msgid "Focus (Hubzilla default)"
-msgstr "Focus (par défaut pour Hubzilla)"
+#: ../../include/account.php:756 ../../include/account.php:758
+msgid "Click here to upgrade."
+msgstr "Cliquez ici pour mettre à jour."
-#: ../../view/theme/redbasic/php/config.php:103
-msgid "Theme settings"
-msgstr "Paramètres du thème"
+#: ../../include/account.php:764
+msgid "This action exceeds the limits set by your subscription plan."
+msgstr "Cette action outrepasserait les limites prévues par votre forfait."
-#: ../../view/theme/redbasic/php/config.php:104
-msgid "Select scheme"
-msgstr "Définir la palette de couleurs"
+#: ../../include/account.php:769
+msgid "This action is not available under your subscription plan."
+msgstr "Cette action n'est pas disponible avec votre forfait."
-#: ../../view/theme/redbasic/php/config.php:105
-msgid "Narrow navbar"
-msgstr "Barre de navigation fine"
+#: ../../include/datetime.php:147
+msgid "Birthday"
+msgstr "Anniversaire"
-#: ../../view/theme/redbasic/php/config.php:106
-msgid "Navigation bar background color"
-msgstr "Couleur de fond de la barre de navigation"
+#: ../../include/datetime.php:149
+msgid "Age: "
+msgstr "Age&nbsp;:"
-#: ../../view/theme/redbasic/php/config.php:107
-msgid "Navigation bar gradient top color"
-msgstr "Dégradé de la barre de navigation - couleur du haut"
+#: ../../include/datetime.php:151
+msgid "YYYY-MM-DD or MM-DD"
+msgstr "AAAA-MM-JJ ou MM-JJ"
-#: ../../view/theme/redbasic/php/config.php:108
-msgid "Navigation bar gradient bottom color"
-msgstr "Dégradé de la barre de navigation - couleur du bas"
+#: ../../include/datetime.php:292
+msgid "less than a second ago"
+msgstr "à l'instant"
-#: ../../view/theme/redbasic/php/config.php:109
-msgid "Navigation active button gradient top color"
-msgstr "Dégradé du bouton de navigation actif - couleur du haut"
+#: ../../include/datetime.php:310
+#, php-format
+msgctxt "e.g. 22 hours ago, 1 minute ago"
+msgid "%1$d %2$s ago"
+msgstr "il y a %1$d %2$s"
-#: ../../view/theme/redbasic/php/config.php:110
-msgid "Navigation active button gradient bottom color"
-msgstr "Dégradé du bouton de navigation actif - couleur du bas"
+#: ../../include/datetime.php:321
+msgctxt "relative_date"
+msgid "year"
+msgid_plural "years"
+msgstr[0] "an"
+msgstr[1] "ans"
-#: ../../view/theme/redbasic/php/config.php:111
-msgid "Navigation bar border color "
-msgstr "Couleur de la bordure de la barre de navigation"
+#: ../../include/datetime.php:324
+msgctxt "relative_date"
+msgid "month"
+msgid_plural "months"
+msgstr[0] "mois"
+msgstr[1] "mois"
-#: ../../view/theme/redbasic/php/config.php:112
-msgid "Navigation bar icon color "
-msgstr "Couleur des icônes de la barre de navigation"
+#: ../../include/datetime.php:327
+msgctxt "relative_date"
+msgid "week"
+msgid_plural "weeks"
+msgstr[0] "semaine"
+msgstr[1] "semaines"
-#: ../../view/theme/redbasic/php/config.php:113
-msgid "Navigation bar active icon color "
-msgstr "Couleur de l'icône active de la barre de navigation"
+#: ../../include/datetime.php:330
+msgctxt "relative_date"
+msgid "day"
+msgid_plural "days"
+msgstr[0] "jour"
+msgstr[1] "jours"
-#: ../../view/theme/redbasic/php/config.php:114
-msgid "link color"
-msgstr "couleur des liens"
+#: ../../include/datetime.php:333
+msgctxt "relative_date"
+msgid "hour"
+msgid_plural "hours"
+msgstr[0] "heure"
+msgstr[1] "heures"
-#: ../../view/theme/redbasic/php/config.php:115
-msgid "Set font-color for banner"
-msgstr "Définir la couleur du texte de la bannière"
+#: ../../include/datetime.php:336
+msgctxt "relative_date"
+msgid "minute"
+msgid_plural "minutes"
+msgstr[0] "minute"
+msgstr[1] "minutes"
-#: ../../view/theme/redbasic/php/config.php:116
-msgid "Set the background color"
-msgstr "Définir la couleur d'arrière-plan"
+#: ../../include/datetime.php:339
+msgctxt "relative_date"
+msgid "second"
+msgid_plural "seconds"
+msgstr[0] "seconde"
+msgstr[1] "secondes"
-#: ../../view/theme/redbasic/php/config.php:117
-msgid "Set the background image"
-msgstr "Définir l'image d'arrière-plan"
+#: ../../include/datetime.php:576
+#, php-format
+msgid "%1$s's birthday"
+msgstr "Anniversaire de %1$s"
-#: ../../view/theme/redbasic/php/config.php:118
-msgid "Set the background color of items"
-msgstr "Définir la couleur de fond des contributions"
+#: ../../include/datetime.php:577
+#, php-format
+msgid "Happy Birthday %1$s"
+msgstr "Joyeux Anniversaire %1$s"
-#: ../../view/theme/redbasic/php/config.php:119
-msgid "Set the background color of comments"
-msgstr "Couleur de fond des commentaires"
+#: ../../include/nav.php:88
+msgid "Remote authentication"
+msgstr "Authentification distante"
-#: ../../view/theme/redbasic/php/config.php:120
-msgid "Set the border color of comments"
-msgstr "Couleur de la bordure des commentaires"
+#: ../../include/nav.php:88
+msgid "Click to authenticate to your home hub"
+msgstr "S'authentifier auprès de votre hub principal"
-#: ../../view/theme/redbasic/php/config.php:121
-msgid "Set the indent for comments"
-msgstr "Indentation des commentaires"
+#: ../../include/nav.php:99 ../../include/nav.php:123
+msgid "End this session"
+msgstr "Mettre fin à la session"
-#: ../../view/theme/redbasic/php/config.php:122
-msgid "Set the basic color for item icons"
-msgstr "Définir la couleur de base pour les icônes des éléments"
+#: ../../include/nav.php:102
+msgid "Your profile page"
+msgstr "Votre profil"
-#: ../../view/theme/redbasic/php/config.php:123
-msgid "Set the hover color for item icons"
-msgstr "Définir la couleur de survol des icônes des éléments"
+#: ../../include/nav.php:105
+msgid "Manage/Edit profiles"
+msgstr "Gérer/modifier vos profils"
-#: ../../view/theme/redbasic/php/config.php:124
-msgid "Set font-size for the entire application"
-msgstr "Définir la taille de police pour l'application entière"
+#: ../../include/nav.php:107
+msgid "Edit your profile"
+msgstr "Modifier votre profil"
-#: ../../view/theme/redbasic/php/config.php:124
-msgid "Example: 14px"
-msgstr "Exemple : 14px"
+#: ../../include/nav.php:113
+msgid "Sign in"
+msgstr "Connexion"
-#: ../../view/theme/redbasic/php/config.php:125
-msgid "Set font-size for posts and comments"
-msgstr "Définir la taille de police pour les contributions et commentaires"
+#: ../../include/nav.php:138
+msgid "Take me home"
+msgstr ""
-#: ../../view/theme/redbasic/php/config.php:126
-msgid "Set font-color for posts and comments"
-msgstr "Définir la couleur de police pour les contributions et commentaires"
+#: ../../include/nav.php:140
+msgid "Log me out of this site"
+msgstr "Déconnectez-moi de ce site"
-#: ../../view/theme/redbasic/php/config.php:127
-msgid "Set radius of corners"
-msgstr "Définir le rayon des arrondis"
+#: ../../include/nav.php:145
+msgid "Create an account"
+msgstr "Créer un compte"
-#: ../../view/theme/redbasic/php/config.php:128
-msgid "Set shadow depth of photos"
-msgstr "Définir la profondeur de l'ombre des photos"
+#: ../../include/nav.php:157
+msgid "Help and documentation"
+msgstr "Aide et documentation"
-#: ../../view/theme/redbasic/php/config.php:129
-msgid "Set maximum width of content region in pixel"
-msgstr "Définir la largeur maximale de la zone des contenus"
+#: ../../include/nav.php:160
+msgid "Search site @name, #tag, ?docs, content"
+msgstr "Recherche @nom, #tag, contenu"
-#: ../../view/theme/redbasic/php/config.php:129
-msgid "Leave empty for default width"
-msgstr "Laissez vide pour avoir la largeur par défaut"
+#: ../../include/nav.php:172
+msgid "Your grid"
+msgstr "Votre réseau"
-#: ../../view/theme/redbasic/php/config.php:130
-msgid "Left align page content"
-msgstr "Aligner à gauche le contenu de la page"
+#: ../../include/nav.php:173
+msgid "View your network/grid"
+msgstr "Voir votre réseau"
+
+#: ../../include/nav.php:174
+msgid "Mark all grid notifications seen"
+msgstr "Marquer toutes les notifications du réseau comme vues"
-#: ../../view/theme/redbasic/php/config.php:131
-msgid "Set minimum opacity of nav bar - to hide it"
-msgstr "Définir l'opacité minimum du bandeau de navigation - pour le cacher"
+#: ../../include/nav.php:176
+msgid "Channel home"
+msgstr "Mon canal"
-#: ../../view/theme/redbasic/php/config.php:132
-msgid "Set size of conversation author photo"
-msgstr "Définir la taille de la photo de l'auteur d'une conversation"
+#: ../../include/nav.php:177
+msgid "View your channel home"
+msgstr "Voir la page d'accueil de votre canal"
-#: ../../view/theme/redbasic/php/config.php:133
-msgid "Set size of followup author photos"
-msgstr "Définir la taille de la photo de l'auteur d'une réponse"
+#: ../../include/nav.php:178
+msgid "Mark all channel notifications seen"
+msgstr "Marquer toutes les notifications du canal comme vues"
-#: ../../boot.php:1162
-#, php-format
-msgctxt "opensearch"
-msgid "Search %1$s (%2$s)"
-msgstr ""
+#: ../../include/nav.php:184
+msgid "Notices"
+msgstr "Notifications"
-#: ../../boot.php:1162
-msgctxt "opensearch"
-msgid "$Projectname"
+#: ../../include/nav.php:184
+msgid "Notifications"
+msgstr "Notifications"
+
+#: ../../include/nav.php:185
+msgid "View all notifications"
+msgstr "Voir toutes les notifications"
+
+#: ../../include/nav.php:188
+msgid "Private mail"
+msgstr "Messages privés"
+
+#: ../../include/nav.php:189
+msgid "View your private messages"
+msgstr "Voir vos messages privés"
+
+#: ../../include/nav.php:190
+msgid "Mark all private messages seen"
+msgstr "Marquer tous les messages privés comme vus"
+
+#: ../../include/nav.php:196
+msgid "Event Calendar"
+msgstr "Calendrier des événements"
+
+#: ../../include/nav.php:197
+msgid "View events"
+msgstr "Voir les événements"
+
+#: ../../include/nav.php:198
+msgid "Mark all events seen"
+msgstr "Marquer tous les événements comme vus"
+
+#: ../../include/nav.php:201
+msgid "Manage Your Channels"
+msgstr "Gérer vos canaux"
+
+#: ../../include/nav.php:203
+msgid "Account/Channel Settings"
+msgstr "Paramètres du Compte/Canal"
+
+#: ../../include/nav.php:211
+msgid "Site Setup and Configuration"
+msgstr "Configuration du site"
+
+#: ../../include/nav.php:273
+msgid "@name, #tag, ?doc, content"
+msgstr "@nom, #étiquette, ?doc, contenu"
+
+#: ../../include/nav.php:274
+msgid "Please wait..."
+msgstr "Merci de patienter..."
+
+#: ../../include/nav.php:276
+msgid "Add Apps"
msgstr ""
-#: ../../boot.php:1480
+#: ../../include/photos.php:115
#, php-format
-msgid "Update %s failed. See error logs."
-msgstr "La mise-à-jour %s a échoué. Merci de consulter les journaux d'erreur."
+msgid "Image exceeds website size limit of %lu bytes"
+msgstr "L'image dépasse la taille limite de %lu octets"
+
+#: ../../include/photos.php:122
+msgid "Image file is empty."
+msgstr "L'image est vide."
+
+#: ../../include/photos.php:261
+msgid "Photo storage failed."
+msgstr "Le stockage de l'image a échoué."
-#: ../../boot.php:1483
+#: ../../include/photos.php:301
+msgid "a new photo"
+msgstr "une nouvelle photo"
+
+#: ../../include/photos.php:305
#, php-format
-msgid "Update Error at %s"
-msgstr "Erreur de mise à jour sur %s"
+msgctxt "photo_upload"
+msgid "%1$s posted %2$s to %3$s"
+msgstr "%1$s a publié %2$s pour %3$s"
+
+#: ../../include/photos.php:532
+msgid "Upload New Photos"
+msgstr "Ajouter des photos"
+
+#: ../../include/zot.php:649
+msgid "Invalid data packet"
+msgstr "Paquet de données invalide"
-#: ../../boot.php:1684
+#: ../../include/zot.php:665
+msgid "Unable to verify channel signature"
+msgstr "Impossible de vérifier la signature du canal"
+
+#: ../../include/zot.php:2316
+#, php-format
+msgid "Unable to verify site signature for %s"
+msgstr "Impossible de vérifier la signature de site pour %s"
+
+#: ../../include/zot.php:3722
+msgid "invalid target signature"
+msgstr "signature de la cible invalide"
+
+#: ../../include/group.php:26
msgid ""
-"Create an account to access services and applications within the Hubzilla"
-msgstr "Créez un compte pour pouvoir accéder aux services et applications de Hubzilla"
+"A deleted group with this name was revived. Existing item permissions "
+"<strong>may</strong> apply to this group and any future members. If this is "
+"not what you intended, please create another group with a different name."
+msgstr "Un groupe supprimé portant ce nom a été ressuscité. Les permissions liées aux éléments existants <strong>peuvent</strong> s'appliquer au groupe et aux membres futurs. Si ce n'est pas ce que vous attendiez, merci de créer un autre groupe avec un nom différent."
-#: ../../boot.php:1706
-msgid "Password"
-msgstr "Mot de passe"
+#: ../../include/group.php:268
+msgid "Add new connections to this privacy group"
+msgstr "Ajouter de nouveaux contacts à ce groupe de contacts"
-#: ../../boot.php:1707
-msgid "Remember me"
-msgstr "Se souvenir de moi"
+#: ../../include/group.php:309
+msgid "edit"
+msgstr "modifier"
-#: ../../boot.php:1710
-msgid "Forgot your password?"
-msgstr "Mot de passe oublié&nbsp;?"
+#: ../../include/group.php:332
+msgid "Edit group"
+msgstr "Modifier le groupe"
-#: ../../boot.php:2276
-msgid "toggle mobile"
-msgstr "(dés)activer mobile"
+#: ../../include/group.php:333
+msgid "Add privacy group"
+msgstr "Créer un groupe de contacts"
-#: ../../boot.php:2425
-msgid "Website SSL certificate is not valid. Please correct."
-msgstr "Le certificat SSL n'est pas valide. Corrigez le."
+#: ../../include/group.php:334
+msgid "Channels not in any privacy group"
+msgstr "Contacts n'étant dans aucun groupe de contacts"
-#: ../../boot.php:2428
-#, php-format
-msgid "[hubzilla] Website SSL error for %s"
-msgstr "[hubzilla] Erreur SSL pour %s"
+#: ../../include/connections.php:127
+msgid "New window"
+msgstr "Nouvelle fenêtre"
-#: ../../boot.php:2469
-msgid "Cron/Scheduled tasks not running."
-msgstr "Les taches planifiées ne tournent pas."
+#: ../../include/connections.php:128
+msgid "Open the selected location in a different window or browser tab"
+msgstr "Ouvrir l'emplacement dans une fenêtre ou un onglet différent"
-#: ../../boot.php:2473
-#, php-format
-msgid "[hubzilla] Cron tasks not running on %s"
-msgstr "[hubzilla] Les tâches planifiées ne tournent pas sur %s"
+#: ../../include/auth.php:148
+msgid "Logged out."
+msgstr "Deconnecté."
+
+#: ../../include/auth.php:275
+msgid "Failed authentication"
+msgstr "Échec de l'authentification"
+
+#: ../../include/help.php:33
+msgid "Help:"
+msgstr "Aide&nbsp;:"
+
+#: ../../include/help.php:65
+msgid "Not Found"
+msgstr "Introuvable"
diff --git a/view/fr/hstrings.php b/view/fr/hstrings.php
index a1ff9f868..d883cc240 100644
--- a/view/fr/hstrings.php
+++ b/view/fr/hstrings.php
@@ -4,441 +4,53 @@ if(! function_exists("string_plural_select_fr")) {
function string_plural_select_fr($n){
return ($n > 1);;
}}
-;
-App::$strings["parent"] = "retour";
-App::$strings["Collection"] = "Groupe de contacts";
-App::$strings["Principal"] = "Principal";
-App::$strings["Addressbook"] = "Carnet d'adresse";
-App::$strings["Calendar"] = "Calendrier";
-App::$strings["Schedule Inbox"] = "Calendrier - Messages entrants";
-App::$strings["Schedule Outbox"] = "Calendrier - Messages sortants";
-App::$strings["Unknown"] = "Inconnu";
-App::$strings["Files"] = "Fichiers";
-App::$strings["Total"] = "Total";
-App::$strings["Shared"] = "Partagé";
-App::$strings["Create"] = "Créer";
-App::$strings["Upload"] = "Envoyer";
-App::$strings["Name"] = "Nom";
-App::$strings["Type"] = "Type";
-App::$strings["Size"] = "Taille";
-App::$strings["Last Modified"] = "Modifié le";
-App::$strings["Edit"] = "Modifier";
-App::$strings["Delete"] = "Supprimer";
-App::$strings["You are using %1\$s of your available file storage."] = "Vous utilisez %1\$s de votre espace de stockage.";
-App::$strings["You are using %1\$s of %2\$s available file storage. (%3\$s&#37;)"] = "Vous utilisez %1\$s sur %2\$s d'espace disponible. (%3\$s&#37;)";
-App::$strings["WARNING:"] = "AVERTISSEMENT&nbsp;:";
-App::$strings["Create new folder"] = "Nouveau dossier";
-App::$strings["Upload file"] = "Téléverser un fichier";
-App::$strings["Permission denied"] = "Accès refusé";
-App::$strings["Permission denied."] = "Permission refusée.";
-App::$strings["Not Found"] = "Introuvable";
-App::$strings["Page not found."] = "Page introuvable.";
-App::$strings["Remote authentication blocked. You are logged into this site locally. Please logout and retry."] = "Authentification distante bloquée. Vous êtes connecté(e) sur ce site localement. Merci de vous déconnecter et réessayer.";
-App::$strings["Welcome %s. Remote authentication successful."] = "Bienvenue %s. L'authentification distante a fonctionné.";
+App::$rtl = 0;
+App::$strings["Can view my channel stream and posts"] = "Peut voir mon canal et mes publicatiosn";
+App::$strings["Can send me their channel stream and posts"] = "Peuvent m'envoyer leur flux et les publications de leur canal";
+App::$strings["Can view my default channel profile"] = "Peut voir le profil par défaut du canal.";
+App::$strings["Can view my connections"] = "Peut voir mes contacts";
+App::$strings["Can view my file storage and photos"] = "Peut voir mes fichiers et photos";
+App::$strings["Can upload/modify my file storage and photos"] = "Peut télécharger/modifier mes fichiers et mes photos";
+App::$strings["Can view my channel webpages"] = "Peut voir les pages web de mon canal";
+App::$strings["Can view my wiki pages"] = "Peut voir les pages de mon wiki";
+App::$strings["Can create/edit my channel webpages"] = "Peut créer ou modifier les pages web de mon canal";
+App::$strings["Can write to my wiki pages"] = "Peut écrire sur mon wiki";
+App::$strings["Can post on my channel (wall) page"] = "Peut écrire sur le mur de mon canal (mur)";
+App::$strings["Can comment on or like my posts"] = "Peuvent commenter et/ou aimer mes publications";
+App::$strings["Can send me private mail messages"] = "Peuvent m'envoyer des messages privés";
+App::$strings["Can like/dislike profiles and profile things"] = "Peut aimer ou détester des profiles";
+App::$strings["Can forward to all my channel connections via @+ mentions in posts"] = "Peut faire suivre à tous mes contacts avec la mention @+ dans une publication";
+App::$strings["Can chat with me"] = "Peut discuter avec moi";
+App::$strings["Can source my public posts in derived channels"] = "Peut rediriger mes publications publiques vers des canaux dérivés";
+App::$strings["Can administer my channel"] = "Peut administrer mon canal";
+App::$strings["Social Networking"] = "Réseau social";
+App::$strings["Social - Mostly Public"] = "Social - principalement public";
+App::$strings["Social - Restricted"] = "Social - restreint";
+App::$strings["Social - Private"] = "Social - privé";
+App::$strings["Community Forum"] = "Forum communautaire";
+App::$strings["Forum - Mostly Public"] = "Forum - principalement public";
+App::$strings["Forum - Restricted"] = "Forum - restreint";
+App::$strings["Forum - Private"] = "Forum - privé";
+App::$strings["Feed Republish"] = "Republication de flux";
+App::$strings["Feed - Mostly Public"] = "Flux - principalement public";
+App::$strings["Feed - Restricted"] = "Flux - restreint";
+App::$strings["Special Purpose"] = "Utilisation spécifique";
+App::$strings["Special - Celebrity/Soapbox"] = "Spécial - célébrité/vitrine";
+App::$strings["Special - Group Repository"] = "Spécial - dépôt partagé";
+App::$strings["Other"] = "Autre";
+App::$strings["Custom/Expert Mode"] = "Mode expert/spécifique";
App::$strings["Requested profile is not available."] = "Profil demandé non disponible.";
-App::$strings["Some blurb about what to do when you're new here"] = "Quelques mots sur quoi faire quand on est nouveau ici";
+App::$strings["Permission denied."] = "Permission refusée.";
App::$strings["Block Name"] = "Nom du Bloc";
App::$strings["Blocks"] = "Blocs";
App::$strings["Block Title"] = "Titre du bloc";
App::$strings["Created"] = "Créé(e)";
App::$strings["Edited"] = "Modifié(e)";
+App::$strings["Create"] = "Créer";
+App::$strings["Edit"] = "Modifier";
App::$strings["Share"] = "Partager";
+App::$strings["Delete"] = "Supprimer";
App::$strings["View"] = "Voir";
-App::$strings["Channel not found."] = "Canal introuvable.";
-App::$strings["Permissions denied."] = "Permissions refusées.";
-App::$strings["l, F j"] = "l, F j";
-App::$strings["Link to Source"] = "Lien vers la Source";
-App::$strings["Edit Event"] = "Modifier l'événement";
-App::$strings["Create Event"] = "Créer un événement";
-App::$strings["Previous"] = "Précédent";
-App::$strings["Next"] = "Suivant";
-App::$strings["Export"] = "Export";
-App::$strings["Import"] = "Import";
-App::$strings["Submit"] = "Envoyer";
-App::$strings["Today"] = "Aujourd'hui";
-App::$strings["You must be logged in to see this page."] = "Vous devez vous connecter pour voir cette page.";
-App::$strings["Posts and comments"] = "";
-App::$strings["Only posts"] = "";
-App::$strings["Insufficient permissions. Request redirected to profile page."] = "Permissions insuffisantes. Demande redirigée vers la page du profil.";
-App::$strings["Room not found"] = "Salon introuvable";
-App::$strings["Leave Room"] = "Quitter le salon";
-App::$strings["Delete Room"] = "";
-App::$strings["I am away right now"] = "Je suis absent en ce moment";
-App::$strings["I am online"] = "Je suis en ligne";
-App::$strings["Bookmark this room"] = "Marquer ce salon comme favori";
-App::$strings["Please enter a link URL:"] = "Merci d'entrer l'URL d'un lien&nbsp;:";
-App::$strings["Encrypt text"] = "Chiffrer le texte";
-App::$strings["Insert web link"] = "Insérer lien web";
-App::$strings["Feature disabled."] = "";
-App::$strings["New Chatroom"] = "Nouveau salon de discussion";
-App::$strings["Chatroom name"] = "";
-App::$strings["Expiration of chats (minutes)"] = "Expiration des discussions (en minutes)";
-App::$strings["Permissions"] = "Autorisations";
-App::$strings["%1\$s's Chatrooms"] = "Salons de %1\$s";
-App::$strings["No chatrooms available"] = "";
-App::$strings["Create New"] = "";
-App::$strings["Expiration"] = "";
-App::$strings["min"] = "";
-App::$strings["Away"] = "Absent";
-App::$strings["Online"] = "En ligne";
-App::$strings["Invalid item."] = "Élément invalide.";
-App::$strings["Bookmark added"] = "Favori ajouté";
-App::$strings["My Bookmarks"] = "Mes Favoris";
-App::$strings["My Connections Bookmarks"] = "Favoris de mes contacts";
-App::$strings["Continue"] = "Continuer";
-App::$strings["Premium Channel Setup"] = "Configuration du canal VIP";
-App::$strings["Enable premium channel connection restrictions"] = "Activer les restrictions liées au canal VIP";
-App::$strings["Please enter your restrictions or conditions, such as paypal receipt, usage guidelines, etc."] = "Merci de saisir les restrictions et/ou conditions - reçu Paypal, transaction Bitcoin, ligne de conduite, ...";
-App::$strings["This channel may require additional steps or acknowledgement of the following conditions prior to connecting:"] = "Avant d'autoriser la mise en relation, ce canal attire votre attention sur les conditions suivantes&nbsp;:";
-App::$strings["Potential connections will then see the following text before proceeding:"] = "Les contacts potentiels verront ce qui suit avant de pouvoir continuer&nbsp;:";
-App::$strings["By continuing, I certify that I have complied with any instructions provided on this page."] = "En continuant, je certifie que je me suis conformé à toutes les instructions indiquées sur cette page.";
-App::$strings["(No specific instructions have been provided by the channel owner.)"] = "(Aucune instruction spécifique n'a été fournie par le propriétaire du canal.)";
-App::$strings["Restricted or Premium Channel"] = "Canal VIP ou restreint";
-App::$strings["Could not access contact record."] = "Impossible d'accéder aux détails du contact.";
-App::$strings["Could not locate selected profile."] = "Impossible de localiser le profil sélectionné.";
-App::$strings["Connection updated."] = "Contact mis à jour.";
-App::$strings["Failed to update connection record."] = "Impossible de mettre à jour les détails du contact.";
-App::$strings["is now connected to"] = "est maintenant connecté avec";
-App::$strings["No"] = "Non";
-App::$strings["Yes"] = "Oui";
-App::$strings["Could not access address book record."] = "Impossible d'accéder aux détails du carnet d'adresses.";
-App::$strings["Refresh failed - channel is currently unavailable."] = "Actualisation impossible - le canal est indisponible.";
-App::$strings["Unable to set address book parameters."] = "Impossible de régler les paramètres du carnet d'adresses.";
-App::$strings["Connection has been removed."] = "Le contact a été supprimé.";
-App::$strings["View Profile"] = "Voir le profil";
-App::$strings["View %s's profile"] = "Voir le profil de %s";
-App::$strings["Refresh Permissions"] = "Actualiser les autorisations";
-App::$strings["Fetch updated permissions"] = "Récupérer les autorisations les plus récentes";
-App::$strings["Recent Activity"] = "Activité récente";
-App::$strings["View recent posts and comments"] = "Voir les publications et commentaires récents";
-App::$strings["Unblock"] = "Débloquer";
-App::$strings["Block"] = "Bloquer";
-App::$strings["Block (or Unblock) all communications with this connection"] = "Bloquer ou débloquer toute communication avec ce contact";
-App::$strings["This connection is blocked!"] = "Ce contact est bloqué&nbsp;!";
-App::$strings["Unignore"] = "Ne plus ignorer";
-App::$strings["Ignore"] = "Ignorer";
-App::$strings["Ignore (or Unignore) all inbound communications from this connection"] = "Ignorer ou ne plus ignorer toute communication venant de ce contact";
-App::$strings["This connection is ignored!"] = "Ce contact est ignoré&nbsp;!";
-App::$strings["Unarchive"] = "Désarchiver";
-App::$strings["Archive"] = "Archiver";
-App::$strings["Archive (or Unarchive) this connection - mark channel dead but keep content"] = "Archiver ou désarchiver ce contact - le marquer comme inactif mais conserver le contenu";
-App::$strings["This connection is archived!"] = "Ce contact est archivé&nbsp;!";
-App::$strings["Unhide"] = "Ne plus cacher";
-App::$strings["Hide"] = "Cacher";
-App::$strings["Hide or Unhide this connection from your other connections"] = "Cacher ou ne plus cacher ce contact vis-à-vis de vos autres contacts";
-App::$strings["This connection is hidden!"] = "Ce contact est caché&nbsp;!";
-App::$strings["Delete this connection"] = "Supprimer ce contact";
-App::$strings["Me"] = "Moi";
-App::$strings["Family"] = "Famille";
-App::$strings["Friends"] = "Amis";
-App::$strings["Acquaintances"] = "Connaissances";
-App::$strings["All"] = "Tous";
-App::$strings["Approve this connection"] = "Autoriser ce contact";
-App::$strings["Accept connection to allow communication"] = "Accepter le contact pour permettre la communication";
-App::$strings["Set Affinity"] = "Définir le degré d'affinité";
-App::$strings["Set Profile"] = "Définir le profil";
-App::$strings["Set Affinity & Profile"] = "Définir le degré d'affinité et le profil";
-App::$strings["none"] = "Aucun";
-App::$strings["Connection Default Permissions"] = "Autorisations par défaut des contacts";
-App::$strings["Connection: %s"] = "Contact&nbsp;: %s";
-App::$strings["Apply these permissions automatically"] = "Appliquer ces permissions automatiquement";
-App::$strings["Connection requests will be approved without your interaction"] = "Les demandes de contact seront approuvées automatiquement";
-App::$strings["This connection's primary address is"] = "L'adresse principale de ce contact est";
-App::$strings["Available locations:"] = "Emplacements disponibles&nbsp;:";
-App::$strings["The permissions indicated on this page will be applied to all new connections."] = "Les permissions indiquées sur cette page seront appliquées à tous vos nouveaux contacts.";
-App::$strings["Connection Tools"] = "";
-App::$strings["Slide to adjust your degree of friendship"] = "Faites glisser pour ajuster votre proximité avec le contact";
-App::$strings["Rating"] = "Evaluation";
-App::$strings["Slide to adjust your rating"] = "Faîtes glisser pour ajuster votre note";
-App::$strings["Optionally explain your rating"] = "Explication facultative de votre évaluation";
-App::$strings["Custom Filter"] = "Filtre personnalisé";
-App::$strings["Only import posts with this text"] = "N'importer que les publications comprenant ce texte";
-App::$strings["words one per line or #tags or /patterns/ or lang=xx, leave blank to import all posts"] = "un mot par ligne ou #étiquettes ou /motif/ ou lang=xx, laisser vide pour importer toutes les publications";
-App::$strings["Do not import posts with this text"] = "Ne pas importer les publications comprenant ce texte";
-App::$strings["This information is public!"] = "Cette information est publique&nbsp;!";
-App::$strings["Connection Pending Approval"] = "Contact en attente d'approbation";
-App::$strings["inherited"] = "héritée";
-App::$strings["Please choose the profile you would like to display to %s when viewing your profile securely."] = "Merci de choisir le profil que vous souhaitez montrer quand %s visite votre profil de manière authentifiée.";
-App::$strings["Their Settings"] = "Leurs paramètres";
-App::$strings["My Settings"] = "Mes paramètres";
-App::$strings["Individual Permissions"] = "Permissions individuelles";
-App::$strings["Some permissions may be inherited from your channel's <a href=\"settings\"><strong>privacy settings</strong></a>, which have higher priority than individual settings. You can <strong>not</strong> change those settings here."] = "Certaines permissions peuvent être héritées de vos <a href=\"settings\">paramètres de confidentialité</a> de canal, lesquels sont prioritaires sur les réglages individuels. Vous pouvez modifier ces permissions ici mais cela n'aura aucun effet à moins de changer les paramètres hérités.";
-App::$strings["Some permissions may be inherited from your channel's <a href=\"settings\"><strong>privacy settings</strong></a>, which have higher priority than individual settings. You can change those settings here but they wont have any impact unless the inherited setting changes."] = "Certaines permissions peuvent être héritées de vos <a href=\"settings\">paramètres de confidentialité</a> de canal, lesquels sont prioritaires sur les réglages individuels. Vous pouvez modifier ces permissions ici mais cela n'aura aucun effet à moins de changer les paramètres hérités.";
-App::$strings["Last update:"] = "Dernière mise à jour&nbsp;:";
-App::$strings["Public access denied."] = "Accès public refusé.";
-App::$strings["%d rating"] = array(
- 0 => "%d évaluation",
- 1 => "%d évaluations",
-);
-App::$strings["Gender: "] = "Sexe/genre&nbsp;:";
-App::$strings["Status: "] = "État&nbsp;:";
-App::$strings["Homepage: "] = "Site web&nbsp;:";
-App::$strings["Age:"] = "Age&nbsp;:";
-App::$strings["Location:"] = "Emplacement&nbsp;:";
-App::$strings["Description:"] = "Description&nbsp;:";
-App::$strings["Hometown:"] = "Ville natale&nbsp;:";
-App::$strings["About:"] = "À propos&nbsp;:";
-App::$strings["Connect"] = "Ajouter/Suivre";
-App::$strings["Public Forum:"] = "Forum public&nbsp;:";
-App::$strings["Keywords: "] = "Mots-clefs&nbsp;:";
-App::$strings["Don't suggest"] = "Ne pas suggérer";
-App::$strings["Common connections:"] = "Contacts en commun&nbsp;:";
-App::$strings["Global Directory"] = "Annuaire global";
-App::$strings["Local Directory"] = "Annuaire local";
-App::$strings["Find"] = "Trouver";
-App::$strings["Finding:"] = "Recherche&nbsp;:";
-App::$strings["Channel Suggestions"] = "Canaux suggérés";
-App::$strings["next page"] = "page suivante";
-App::$strings["previous page"] = "page précédente";
-App::$strings["Sort options"] = "Options de tri";
-App::$strings["Alphabetic"] = "Alphabétique";
-App::$strings["Reverse Alphabetic"] = "Alphabétique inversé";
-App::$strings["Newest to Oldest"] = "Du plus récent au moins récent";
-App::$strings["Oldest to Newest"] = "Du moins récent du plus récent";
-App::$strings["No entries (some entries may be hidden)."] = "Pas d'entrées (certaines peuvent être cachées).";
-App::$strings["Item not found."] = "Élément introuvable";
-App::$strings["Item not found"] = "Élément introuvable";
-App::$strings["Title (optional)"] = "Titre (facultatif)";
-App::$strings["Edit Block"] = "Modifier le bloc";
-App::$strings["No channel."] = "Pas de canal.";
-App::$strings["Common connections"] = "Contacts en commun";
-App::$strings["No connections in common."] = "Pas de contacts en commun.";
-App::$strings["Blocked"] = "Bloqué(e)";
-App::$strings["Ignored"] = "Ignoré(e)";
-App::$strings["Hidden"] = "Caché";
-App::$strings["Archived"] = "Archivé";
-App::$strings["New"] = "Nouveautés";
-App::$strings["New Connections"] = "Nouveaux contacts";
-App::$strings["Show pending (new) connections"] = "Voir les (nouveaux) contacts en attente";
-App::$strings["All Connections"] = "Tous les contacts";
-App::$strings["Show all connections"] = "Voir tous les contacts";
-App::$strings["Only show blocked connections"] = "Ne montrer que les contacts bloqués";
-App::$strings["Only show ignored connections"] = "Ne montrer que les contacts ignorés";
-App::$strings["Only show archived connections"] = "Ne montrer que les contacts archivés";
-App::$strings["Only show hidden connections"] = "Ne montrer que les contacts cachés";
-App::$strings["Pending approval"] = "En attente de validation";
-App::$strings["%1\$s [%2\$s]"] = "%1\$s [%2\$s]";
-App::$strings["Edit connection"] = "Modifier le contact";
-App::$strings["Delete connection"] = "Supprimer le contact";
-App::$strings["Channel address"] = "Adresse du canal";
-App::$strings["Network"] = "Réseau";
-App::$strings["Status"] = "État";
-App::$strings["Connected"] = "Connecté";
-App::$strings["Approve connection"] = "Valider le contact";
-App::$strings["Approve"] = "Approuver";
-App::$strings["Ignore connection"] = "Ignorer le contact";
-App::$strings["Recent activity"] = "Activité récente";
-App::$strings["Connections"] = "Contacts";
-App::$strings["Search"] = "Recherche";
-App::$strings["Search your connections"] = "Chercher parmi vos contacts";
-App::$strings["Connections search"] = "Chercher des contacts";
-App::$strings["Image uploaded but image cropping failed."] = "L'image a été téléversée, mais le recadrage a échoué.";
-App::$strings["Cover Photos"] = "Photos de couverture";
-App::$strings["Image resize failed."] = "Le redimensionnement de l'image a échoué.";
-App::$strings["Unable to process image"] = "Impossible de traiter l'image";
-App::$strings["Image upload failed."] = "Le téléversement de l'image a échoué.";
-App::$strings["Unable to process image."] = "Impossible de traîter l'image.";
-App::$strings["female"] = "femme";
-App::$strings["%1\$s updated her %2\$s"] = "%1\$s a mis à jour son %2\$s";
-App::$strings["male"] = "homme";
-App::$strings["%1\$s updated his %2\$s"] = "%1\$s a mis à jour son %2\$s";
-App::$strings["%1\$s updated their %2\$s"] = "%1\$s a mis a jour sa %2\$s";
-App::$strings["cover photo"] = "Photo principale";
-App::$strings["Photo not available."] = "Photo inaccessible.";
-App::$strings["Upload File:"] = "Téléverser fichier&nbsp;:";
-App::$strings["Select a profile:"] = "Choisir un profil&nbsp;:";
-App::$strings["Upload Cover Photo"] = "Téléverser une photo de couverture";
-App::$strings["or"] = "ou";
-App::$strings["skip this step"] = "passer cette étape";
-App::$strings["select a photo from your photo albums"] = "choisir une photo dans vos albums";
-App::$strings["Crop Image"] = "Recadrer l'image";
-App::$strings["Please adjust the image cropping for optimum viewing."] = "Merci d'ajuster le cadre pour une visualisation optimale.";
-App::$strings["Done Editing"] = "J'ai terminé";
-App::$strings["Item is not editable"] = "Elément non modifiable";
-App::$strings["Edit post"] = "Modifier la publication";
-App::$strings["Calendar entries imported."] = "Entrées du calendrier importées.";
-App::$strings["No calendar entries found."] = "Aucune entrée du calendrier trouvée.";
-App::$strings["Event can not end before it has started."] = "La fin de l'événement ne peut être antérieure à son début.";
-App::$strings["Unable to generate preview."] = "Impossible de générer l'aperçu.";
-App::$strings["Event title and start time are required."] = "Un titre et une date de début sont requises pour l'événement.";
-App::$strings["Event not found."] = "Événement introuvable.";
-App::$strings["event"] = "événement";
-App::$strings["Edit event title"] = "Modifier le titre de l'événement";
-App::$strings["Event title"] = "Titre de l'événement";
-App::$strings["Required"] = "Requis";
-App::$strings["Categories (comma-separated list)"] = "Catégories (séparées par des virgules)";
-App::$strings["Edit Category"] = "Modifier la catégorie";
-App::$strings["Category"] = "Catégorie";
-App::$strings["Edit start date and time"] = "Modifier la date et l'heure de début";
-App::$strings["Start date and time"] = "Date et heure de début";
-App::$strings["Finish date and time are not known or not relevant"] = "Date et heure de fin inconnues ou sans objet";
-App::$strings["Edit finish date and time"] = "Modifier la date et l'heure de fin";
-App::$strings["Finish date and time"] = "Date et heure de fin";
-App::$strings["Adjust for viewer timezone"] = "Ajuster au fuseau horaire du visiteur";
-App::$strings["Important for events that happen in a particular place. Not practical for global holidays."] = "Important pour les événements se tenant en un lieu particulier. Pas pratique pour les vacances communes à de nombreux pays dans le monde.";
-App::$strings["Edit Description"] = "Modifier la description";
-App::$strings["Description"] = "Description";
-App::$strings["Edit Location"] = "Modifier l'emplacement";
-App::$strings["Location"] = "Emplacement";
-App::$strings["Share this event"] = "Partager cet événement";
-App::$strings["Preview"] = "Aperçu";
-App::$strings["Permission settings"] = "Gérer les autorisations";
-App::$strings["Advanced Options"] = "Options avancées";
-App::$strings["Edit event"] = "Modifier l'événement";
-App::$strings["Delete event"] = "Supprimer l'événement";
-App::$strings["calendar"] = "calendrier";
-App::$strings["Event removed"] = "Événement supprimé";
-App::$strings["Failed to remove event"] = "Impossible de supprimer l'événement";
-App::$strings["Photos"] = "Photos";
-App::$strings["Cancel"] = "Annuler";
-App::$strings["This site is not a directory server"] = "Ce site n'est pas un serveur d'annuaire";
-App::$strings["This directory server requires an access token"] = "Ce serveur d'annuaire requiert un jeton d'accès";
-App::$strings["Save to Folder:"] = "Classer dans le dossier&nbsp;:";
-App::$strings["- select -"] = "- choisir -";
-App::$strings["Save"] = "Enregistrer";
-App::$strings["Invalid message"] = "Message non valide";
-App::$strings["no results"] = "aucun résultat";
-App::$strings["Delivery report for %1\$s"] = "Rapport de distribution pour %1\$s";
-App::$strings["channel sync processed"] = "Synchro de canal effectuée";
-App::$strings["queued"] = "mis dans la file d'attente";
-App::$strings["posted"] = "publié";
-App::$strings["accepted for delivery"] = "accepté pour la distribution";
-App::$strings["updated"] = "mis à jour";
-App::$strings["update ignored"] = "mise à jour ignorée";
-App::$strings["permission denied"] = "permission refusée";
-App::$strings["recipient not found"] = "destinataire introuvable";
-App::$strings["mail recalled"] = "courriel rappelé";
-App::$strings["duplicate mail received"] = "courriel reçu en double";
-App::$strings["mail delivered"] = "courriel distribué";
-App::$strings["Layout Name"] = "Nom de la mise en page";
-App::$strings["Layout Description (Optional)"] = "Description de la mise en page (facultatif)";
-App::$strings["Edit Layout"] = "Modifier la mise en page";
-App::$strings["Page link"] = "";
-App::$strings["Edit Webpage"] = "Modifier la page web";
-App::$strings["Channel added."] = "Canal ajouté.";
-App::$strings["network"] = "réseau";
-App::$strings["RSS"] = "RSS";
-App::$strings["Privacy group created."] = "Groupe d'accès créé.";
-App::$strings["Could not create privacy group."] = "Impossible de créer le groupe d'accès.";
-App::$strings["Privacy group not found."] = "Groupe d'accès introuvable.";
-App::$strings["Privacy group updated."] = "Groupe d'accès mis à jour.";
-App::$strings["Create a group of channels."] = "Créer un groupe de canaux.";
-App::$strings["Privacy group name: "] = "Nom du groupe d'accès&nbsp;:";
-App::$strings["Members are visible to other channels"] = "Les membres sont visibles par les autres canaux";
-App::$strings["Privacy group removed."] = "Groupe d'accès supprimé.";
-App::$strings["Unable to remove privacy group."] = "Impossible de supprimer le groupe d'accès.";
-App::$strings["Privacy group editor"] = "Editeur de groupe d'accès.";
-App::$strings["Members"] = "Membres";
-App::$strings["All Connected Channels"] = "Tous les canaux connectés";
-App::$strings["Click on a channel to add or remove."] = "Cliquer sur un canal pour l'ajouter ou le supprimer";
-App::$strings["Share content from Firefox to \$Projectname"] = "Partager du contenu depuis Firefox avec \$Projectname";
-App::$strings["Activate the Firefox \$Projectname provider"] = "Activer le connecteur \$Projectname pour Firefox";
-App::$strings["Authorize application connection"] = "Autoriser l'application à se connecter";
-App::$strings["Return to your app and insert this Securty Code:"] = "Merci de retourner vers votre application, et d'y insérer ce Code de Sécurité&nbsp;:";
-App::$strings["Please login to continue."] = "Merci de vous identifier pour continuer.";
-App::$strings["Do you want to authorize this application to access your posts and contacts, and/or create new posts for you?"] = "Voulez-vous autoriser cette application à accéder à vos publications et contacts, et/ou à publier en votre nom?";
-App::$strings["Documentation Search"] = "Chercher dans la documentation";
-App::$strings["Help:"] = "Aide&nbsp;:";
-App::$strings["Help"] = "Aide";
-App::$strings["\$Projectname Documentation"] = "Documentation \$Projectname";
-App::$strings["Permission Denied."] = "Permission refusée.";
-App::$strings["File not found."] = "Fichier introuvable.";
-App::$strings["Edit file permissions"] = "Modifier les autorisations d'accès au fichier";
-App::$strings["Set/edit permissions"] = "Définir/modifier les autorisations";
-App::$strings["Include all files and sub folders"] = "Inclure tous fichiers et sous-répertoires";
-App::$strings["Return to file list"] = "Retourner à la liste des fichiers";
-App::$strings["Copy/paste this code to attach file to a post"] = "Copiez/collez ce code pour joindre le fichier à une publication";
-App::$strings["Copy/paste this URL to link file from a web page"] = "Copiez/collez cette URL pour pointer vers ce fichier depuis une page web";
-App::$strings["Share this file"] = "Partager ce fichier";
-App::$strings["Show URL to this file"] = "Montrer l'URL de ce fichier";
-App::$strings["Notify your contacts about this file"] = "Notifier vos contacts à propos de ce fichier";
-App::$strings["Apps"] = "Applications";
-App::$strings["Item not available."] = "Élément indisponible.";
-App::$strings["Your service plan only allows %d channels."] = "Votre forfait n'autorise que %d canaux.";
-App::$strings["Nothing to import."] = "Rien à importer.";
-App::$strings["Unable to download data from old server"] = "Impossible de récupérer les données de l'ancien serveur";
-App::$strings["Imported file is empty."] = "Le fichier importé est vide.";
-App::$strings["Warning: Database versions differ by %1\$d updates."] = "Attention&nbsp;: les versions de bases de données diffèrent de %1\$d mises à jour.";
-App::$strings["Cloned channel not found. Import failed."] = "Canal cloné non trouvé. Echec de l'import.";
-App::$strings["No channel. Import failed."] = "Pas de canal. Echec de l'import.";
-App::$strings["Import completed."] = "L'import est terminé.";
-App::$strings["You must be logged in to use this feature."] = "Vous devez vous connecter pour utiliser cette fonctionnalité.";
-App::$strings["Import Channel"] = "Importation de canal";
-App::$strings["Use this form to import an existing channel from a different server/hub. You may retrieve the channel identity from the old server/hub via the network or provide an export file."] = "Utilisez ce formulaire pour importer un canal existant sur un autre serveur. Vous pouvez récupérer l'identité du canal sur l'ancien serveur directement par le réseau, ou bien fournir un fichier d'export/import.";
-App::$strings["File to Upload"] = "Fichier à envoyer";
-App::$strings["Or provide the old server/hub details"] = "Ou fournissez les détails de l'ancien serveur/hub";
-App::$strings["Your old identity address (xyz@example.com)"] = "Votre ancienne identité (zyx@exemple.com)";
-App::$strings["Your old login email address"] = "Votre ancienne adresse de courriel";
-App::$strings["Your old login password"] = "Votre ancien mot de passe";
-App::$strings["For either option, please choose whether to make this hub your new primary address, or whether your old location should continue this role. You will be able to post from either location, but only one can be marked as the primary location for files, photos, and media."] = "Quelle que soit l'option choisie, merci de décider si ce hub sera votre nouvelle adresse primaire, ou si votre ancien hub continuera à jouer ce rôle. Vous pourrez publier depuis l'emplacement de votre choix, mais une seule peut être déclarée comme stockage primaire de vos fichiers/photos/media.";
-App::$strings["Make this hub my primary location"] = "Faire de ce hub mon emplacement primaire";
-App::$strings["Import existing posts if possible (experimental - limited by available memory"] = "Importer les publications existantes si possible (expérimental - limité par la mémoire disponible)";
-App::$strings["This process may take several minutes to complete. Please submit the form only once and leave this page open until finished."] = "Ce processus peut prendre plusieurs minutes. Merci de ne valider le formulaire qu'une seule fois et de laisser cette page ouverte jusqu'à la fin.";
-App::$strings["Unable to locate original post."] = "Impossible de localiser la publication initiale.";
-App::$strings["Empty post discarded."] = "Publication vide annulée.";
-App::$strings["Executable content type not permitted to this channel."] = "Les contenus de type 'exécutable' ne sont pas autorisés sur ce canal.";
-App::$strings["Duplicate post suppressed."] = "Publication en doublon supprimée.";
-App::$strings["System error. Post not saved."] = "Erreur système. Publication non sauvegardée.";
-App::$strings["Unable to obtain post information from database."] = "Impossible d'obtenir les informations de publication depuis la base de données.";
-App::$strings["You have reached your limit of %1$.0f top level posts."] = "Vous avez atteint votre limite de %1$.0f contributions \"racines\".";
-App::$strings["You have reached your limit of %1$.0f webpages."] = "Vous avez atteint votre limite de %1$.0f pages web.";
-App::$strings["Layouts"] = "Mises-en-page";
-App::$strings["Comanche page description language help"] = "Aide sur le langage de description de page Comanche";
-App::$strings["Layout Description"] = "Description de la mise en page";
-App::$strings["Download PDL file"] = "Télécharger le fichier PDL";
-App::$strings["\$Projectname"] = "\$Projectname";
-App::$strings["Welcome to %s"] = "Bienvenue sur %s";
-App::$strings["First Name"] = "Prénom";
-App::$strings["Last Name"] = "Nom de famille";
-App::$strings["Nickname"] = "Surnom";
-App::$strings["Full Name"] = "Nom complet";
-App::$strings["Email"] = "Courriel";
-App::$strings["Profile Photo"] = "Photo du Profil";
-App::$strings["Profile Photo 16px"] = "Photo de profil 16px";
-App::$strings["Profile Photo 32px"] = "Photo de profil 32px";
-App::$strings["Profile Photo 48px"] = "Photo de profil 48px";
-App::$strings["Profile Photo 64px"] = "Photo de profil 64px";
-App::$strings["Profile Photo 80px"] = "Photo de profil 80px";
-App::$strings["Profile Photo 128px"] = "Photo de profil 128px";
-App::$strings["Timezone"] = "Fuseau horaire";
-App::$strings["Homepage URL"] = "URL de mon site Internet&nbsp;:";
-App::$strings["Language"] = "Langue";
-App::$strings["Birth Year"] = "Année de naissance";
-App::$strings["Birth Month"] = "Mois de naissance";
-App::$strings["Birth Day"] = "Jour de naissance";
-App::$strings["Birthdate"] = "Date de naissance";
-App::$strings["Gender"] = "Sexe";
-App::$strings["Male"] = "Homme";
-App::$strings["Female"] = "Femme";
-App::$strings["webpage"] = "pages web";
-App::$strings["block"] = "bloquer";
-App::$strings["layout"] = "mise en page";
-App::$strings["menu"] = "menu";
-App::$strings["%s element installed"] = "Elément %s installé";
-App::$strings["%s element installation failed"] = "L'installation de l'élément %s a échoué";
-App::$strings["Like/Dislike"] = "Aime/n'aime pas";
-App::$strings["This action is restricted to members."] = "Cette action est réservée aux membres.";
-App::$strings["Please <a href=\"rmagic\">login with your \$Projectname ID</a> or <a href=\"register\">register as a new \$Projectname member</a> to continue."] = "S'il vous plait, <a href=\"rmagic\">identifiez vous avec votre identifant de \$Projectname </a> ou <a href=\"register\">inscrivez vous comme nouveau membre de \$Projectname </a> pour continuer.";
-App::$strings["Invalid request."] = "Requête invalide.";
-App::$strings["channel"] = "canal";
-App::$strings["thing"] = "chose";
-App::$strings["Channel unavailable."] = "Canal indisponible.";
-App::$strings["Previous action reversed."] = "Action précédente annulée.";
-App::$strings["photo"] = "photo";
-App::$strings["status"] = "état";
-App::$strings["%1\$s likes %2\$s's %3\$s"] = "%1\$s aime %3\$s de %2\$s";
-App::$strings["%1\$s doesn't like %2\$s's %3\$s"] = "%1\$s n'aime pas %3\$s de %2\$s";
-App::$strings["%1\$s agrees with %2\$s's %3\$s"] = "%1\$s approuve %3\$s de %2\$s";
-App::$strings["%1\$s doesn't agree with %2\$s's %3\$s"] = "%1\$s n'est pas d'accord avec %3\$s de %2\$s";
-App::$strings["%1\$s abstains from a decision on %2\$s's %3\$s"] = "%1\$s s'abstient de toute décision sur le %3\$s de %2\$s";
-App::$strings["%1\$s is attending %2\$s's %3\$s"] = "%1\$s participe à %3\$s de %2\$s";
-App::$strings["%1\$s is not attending %2\$s's %3\$s"] = "%1\$s ne participe pas à %3\$s de %2\$s";
-App::$strings["%1\$s may attend %2\$s's %3\$s"] = "%1\$s participe peut-être à %3\$s de %2\$s";
-App::$strings["Action completed."] = "Action terminée.";
-App::$strings["Thank you."] = "Merci.";
-App::$strings["Import completed"] = "L'import est terminé.";
-App::$strings["Import Items"] = "Importer";
-App::$strings["Use this form to import existing posts and content from an export file."] = "Utiliser ce formulaire pour importer des publications et du contenu existant d'un fichier d'export.";
App::$strings["Total invitation limit exceeded."] = "Limite du nombre total d'invitation dépassée.";
App::$strings["%s : Not a valid email address."] = "%s&nbsp;: adresse courriel invalide.";
App::$strings["Please join us on \$Projectname"] = "Rejoignez-nous sur \$Projectname";
@@ -458,120 +70,63 @@ App::$strings["1. Register at any \$Projectname location (they are all inter-con
App::$strings["2. Enter my \$Projectname network address into the site searchbar."] = "2. Saisissez l'adresse de mon canal \$Projectname dans la barre de recherche du site.";
App::$strings["or visit"] = "ou rendez-vous sur";
App::$strings["3. Click [Connect]"] = "3. Cliquez sur [Ajouter]";
-App::$strings["Remote privacy information not available."] = "Les informations distantes de confidentialité ne sont pas disponibles.";
-App::$strings["Visible to:"] = "Visible par&nbsp;:";
+App::$strings["Submit"] = "Envoyer";
+App::$strings["Item not found"] = "Élément introuvable";
+App::$strings["Layout Name"] = "Nom de la mise en page";
+App::$strings["Layout Description (Optional)"] = "Description de la mise en page (facultatif)";
+App::$strings["Edit Layout"] = "Modifier la mise en page";
+App::$strings["Permission denied"] = "Accès refusé";
+App::$strings["Invalid profile identifier."] = "Identifiant de profil invalide.";
+App::$strings["Profile Visibility Editor"] = "Éditeur de visibilité de profil";
+App::$strings["Profile"] = "Profil";
+App::$strings["Click on a contact to add or remove."] = "Cliquer sur un contact pour l'ajouter ou le retirer.";
+App::$strings["Visible To"] = "Visible par";
+App::$strings["All Connections"] = "Tous les contacts";
+App::$strings["This site is not a directory server"] = "Ce site n'est pas un serveur d'annuaire";
+App::$strings["You must be logged in to see this page."] = "Vous devez vous connecter pour voir cette page.";
+App::$strings["Posts and comments"] = "Publications et commentaires";
+App::$strings["Only posts"] = "Seulement les publications";
+App::$strings["Insufficient permissions. Request redirected to profile page."] = "Permissions insuffisantes. Demande redirigée vers la page du profil.";
+App::$strings["Export Channel"] = "Exporter le canal";
+App::$strings["Export your basic channel information to a file. This acts as a backup of your connections, permissions, profile and basic data, which can be used to import your data to a new server hub, but does not contain your content."] = "Exportez les principales informations de votre canal dans un fichier. Celui-ci pourra servir de sauvegarde de vos contacts, permissions, profils et données de base. Il pourra être importé sur un nouveau hub/serveur, mais n'embarquera pas vos contenus.";
+App::$strings["Export Content"] = "Exporter le contenu";
+App::$strings["Export your channel information and recent content to a JSON backup that can be restored or imported to another server hub. This backs up all of your connections, permissions, profile data and several months of posts. This file may be VERY large. Please be patient - it may take several minutes for this download to begin."] = "Exportez les informations du canal et les contenus récents dans un fichier JSON. Celui-ci contiendra toutes vos relations, permissions, profils, et plusieurs mois de publications. Ce fichier peut être TRÈS gros. Armez-vous de patience - plusieurs minutes peuvent s'écouler avant que le téléchargement ne commence.";
+App::$strings["Export your posts from a given year."] = "Exporter vos publications d'une année en particulier";
+App::$strings["You may also export your posts and conversations for a particular year or month. Adjust the date in your browser location bar to select other dates. If the export fails (possibly due to memory exhaustion on your server hub), please try again selecting a more limited date range."] = "Vous pouvez également exporter vos publications et conversations pour une année ou un mois particulier. Ajustez la date dans la barre de votre navigateur pour sélectionner d'autres dates. Si l'export échoue (possible en cas de pénurie de mémoire sur le serveur de votre hub), essayez à nouveau en sélectionnant un intervalle de dates plus petit.";
+App::$strings["To select all posts for a given year, such as this year, visit <a href=\"%1\$s\">%2\$s</a>"] = "Pour sélectionner toutes les publications pour une année donnée, telle que cette année, visitez <a href=\"%1\$s\">%2\$s</a>";
+App::$strings["To select all posts for a given month, such as January of this year, visit <a href=\"%1\$s\">%2\$s</a>"] = "Pour sélectionner toutes les publications pour un mois donné, par exemple janvier, visitez <a href=\"%1\$s\">%2\$s</a>";
+App::$strings["These content files may be imported or restored by visiting <a href=\"%1\$s\">%2\$s</a> on any site containing your channel. For best results please import or restore these in date order (oldest first)."] = "Ces fichiers de contenu peuvent être importés ou restaurés en visitant <a href=\"%1\$s\">%2\$s</a> sur n'importe quel site hébergeant votre canal. Pour de meilleurs résultats merci de les importer par ordre chronologique (les plus anciens d'abord).";
+App::$strings["Public access denied."] = "Accès public refusé.";
+App::$strings["Search"] = "Recherche";
+App::$strings["Items tagged with: %s"] = "Eléments étiquetés avec&nbsp;: %s";
+App::$strings["Search results for: %s"] = "Résultats de recherche pour&nbsp;: %s";
App::$strings["Location not found."] = "Emplacement introuvable.";
App::$strings["Location lookup failed."] = "Echec de la recherche de l'emplacement.";
App::$strings["Please select another location to become primary before removing the primary location."] = "Merci de sélectionner un autre emplacement comme nouvel emplacement primaire avant de supprimer l'emplacement primaire actuel.";
App::$strings["Syncing locations"] = "Synchronisation des emplacements";
App::$strings["No locations found."] = "Emplacement(s) introuvable.";
App::$strings["Manage Channel Locations"] = "Gérer les emplacements des canaux";
+App::$strings["Location"] = "Emplacement";
App::$strings["Address"] = "Adresse";
-App::$strings["Primary"] = "";
+App::$strings["Primary"] = "Primaire";
App::$strings["Drop"] = "Supprimer";
-App::$strings["Sync Now"] = "";
+App::$strings["Sync Now"] = "Synchronisez maintenant";
App::$strings["Please wait several minutes between consecutive operations."] = "Merci d'attendre plusieurs minutes entre opérations successives.";
App::$strings["When possible, drop a location by logging into that website/hub and removing your channel."] = "Quand c'est possible, abandonnez un emplacement en vous connectant sur le site/hub et en supprimant votre canal.";
App::$strings["Use this form to drop the location if the hub is no longer operating."] = "Utilisez ce formulaire pour abandonner l'emplacement si le hub n'est plus actif.";
-App::$strings["Hub not found."] = "Hub introuvable.";
-App::$strings["Unable to lookup recipient."] = "Impossible de localiser le destinataire.";
-App::$strings["Unable to communicate with requested channel."] = "Impossible de communiquer avec le canal demandé.";
-App::$strings["Cannot verify requested channel."] = "Impossible de vérifier le canal demandé.";
-App::$strings["Selected channel has private message restrictions. Send failed."] = "Le canal choisi a des restrictions quant aux messages privés. L'envoi a échoué.";
-App::$strings["Messages"] = "Messages";
-App::$strings["Message recalled."] = "Message rappelé.";
-App::$strings["Conversation removed."] = "Conversation supprimée.";
-App::$strings["Expires YYYY-MM-DD HH:MM"] = "Expire le YYYY-MM-DD à HH:MM";
-App::$strings["Requested channel is not in this network"] = "Le canal demandé n'est pas sur ce réseau";
-App::$strings["Send Private Message"] = "Envoyer un message privé";
-App::$strings["To:"] = "À&nbsp;:";
-App::$strings["Subject:"] = "Objet&nbsp;:";
-App::$strings["Attach file"] = "Joindre un fichier";
-App::$strings["Send"] = "Envoyer";
-App::$strings["Set expiration date"] = "Définir la date d'expiration";
-App::$strings["Delete message"] = "Supprimer le message";
-App::$strings["Delivery report"] = "Rapport de distribution";
-App::$strings["Recall message"] = "Rappeler le message";
-App::$strings["Message has been recalled."] = "Le message a été rappelé.";
-App::$strings["Delete Conversation"] = "Supprimer la conversation";
-App::$strings["No secure communications available. You <strong>may</strong> be able to respond from the sender's profile page."] = "Aucune communication sécurisée n'est possible. Vous pourrez <strong>peut-être</strong> répondre depuis la page de profil de l'émetteur.";
-App::$strings["Send Reply"] = "Envoyer la réponse";
-App::$strings["Your message for %s (%s):"] = "Votre message pour %s (%s)&nbsp;:";
-App::$strings["You have created %1$.0f of %2$.0f allowed channels."] = "Vous avez créé %1$.0f des %2$.0f canaux autorisés.";
-App::$strings["Create a new channel"] = "Créer un nouveau canal";
-App::$strings["Channel Manager"] = "Gérer les canaux";
-App::$strings["Current Channel"] = "Canal actif";
-App::$strings["Switch to one of your channels by selecting it."] = "Pour changer de canal, sélectionnez-en un";
-App::$strings["Default Channel"] = "Canal par défaut";
-App::$strings["Make Default"] = "Définir comme défaut";
-App::$strings["%d new messages"] = "%d nouveaux messages";
-App::$strings["%d new introductions"] = "%d nouvelles présentations";
-App::$strings["Delegated Channel"] = "";
-App::$strings["No valid account found."] = "Aucun compte valide trouvé.";
-App::$strings["Password reset request issued. Check your email."] = "Demande de réinitialisation du mot de passe envoyée. Vérifiez vos courriels.";
-App::$strings["Site Member (%s)"] = "Membre du site (%s)";
-App::$strings["Password reset requested at %s"] = "Demande de réinitialisation du mot de passe sur %s";
-App::$strings["Request could not be verified. (You may have previously submitted it.) Password reset failed."] = "La demande n'a pas pu être vérifiée. (Peut-être l'avez vous déjà utilisée.) La réinitialisation a échoué.";
-App::$strings["Password Reset"] = "Réinitialiser le mot de passe";
-App::$strings["Your password has been reset as requested."] = "Votre mot de passe a bien été réinitialisé.";
-App::$strings["Your new password is"] = "Votre nouveau mot de passe est";
-App::$strings["Save or copy your new password - and then"] = "Enregistrez ou copiez votre nouveau mot de passe, puis";
-App::$strings["click here to login"] = "cliquez ici pour vous connecter";
-App::$strings["Your password may be changed from the <em>Settings</em> page after successful login."] = "Votre mot de passe peut être changé depuis la page des <em>Paramètres</em> une fois connecté.";
-App::$strings["Your password has changed at %s"] = "Votre mot de passe de %s a été changé";
-App::$strings["Forgot your Password?"] = "Mot de passe oublié&nbsp;?";
-App::$strings["Enter your email address and submit to have your password reset. Then check your email for further instructions."] = "Saisissez votre adresse de courriel, et validez, pour réinitialiser votre mot de passe. Vérifiez ensuite votre boîte aux lettres pour la suite des instructions.";
-App::$strings["Email Address"] = "Adresse de courriel";
-App::$strings["Reset"] = "Réinitialiser";
-App::$strings["Unable to update menu."] = "Impossible de mettre le menu à jour.";
-App::$strings["Unable to create menu."] = "Impossible de créer le menu.";
-App::$strings["Menu Name"] = "Nom du menu";
-App::$strings["Unique name (not visible on webpage) - required"] = "Nom unique (non visible sur la page web) - requis";
-App::$strings["Menu Title"] = "Titre du menu";
-App::$strings["Visible on webpage - leave empty for no title"] = "Visible pour la page web - laisser vide pour qu'il n'y ait pas de titre";
-App::$strings["Allow Bookmarks"] = "Autoriser l'usage de favoris";
-App::$strings["Menu may be used to store saved bookmarks"] = "Le menu pourra être utilisé pour stocker des favoris";
-App::$strings["Submit and proceed"] = "Valider et continuer";
-App::$strings["Menus"] = "Menus";
-App::$strings["Bookmarks allowed"] = "Favoris autorisés";
-App::$strings["Delete this menu"] = "Supprimer ce menu";
-App::$strings["Edit menu contents"] = "Modifier le contenu du menu";
-App::$strings["Edit this menu"] = "Modifier ce menu";
-App::$strings["Menu could not be deleted."] = "Impossible de supprimer le menu.";
App::$strings["Menu not found."] = "Menu introuvable.";
-App::$strings["Edit Menu"] = "Modifier le menu";
-App::$strings["Add or remove entries to this menu"] = "Ajouter/supprimer des entrées à ce menu";
-App::$strings["Menu name"] = "Nom du menu";
-App::$strings["Must be unique, only seen by you"] = "Doit être unique, ne sera vu que par vous";
-App::$strings["Menu title"] = "Titre du menu";
-App::$strings["Menu title as seen by others"] = "Titre du menu tel que vu par les visiteurs";
-App::$strings["Allow bookmarks"] = "Autoriser l'usage de favoris";
-App::$strings["Not found."] = "Introuvable.";
-App::$strings["__ctx:mood__ %1\$s is %2\$s"] = "%1\$s est %2\$s";
-App::$strings["Mood"] = "Humeur";
-App::$strings["Set your current mood and tell your friends"] = "Indiquez votre humeur du moment à vos amis";
-App::$strings["Profile Match"] = "Profils similaires";
-App::$strings["No keywords to match. Please add keywords to your default profile."] = "Aucun mot-clef à comparer. Merci d'ajouter des mots-clefs à votre profil par défaut.";
-App::$strings["is interested in:"] = "s'intéresse à&nbsp;:";
-App::$strings["No matches"] = "Pas de correspondance";
-App::$strings["No such group"] = "Groupe introuvable";
-App::$strings["No such channel"] = "Canal introuvable";
-App::$strings["forum"] = "forum";
-App::$strings["Search Results For:"] = "Résultats de recherche pour&nbsp;:";
-App::$strings["Privacy group is empty"] = "Groupe d'accès vide";
-App::$strings["Privacy group: "] = "Groupe d'accès&nbsp;:";
-App::$strings["Invalid connection."] = "Contact non valide.";
-App::$strings["No more system notifications."] = "Pas d'autre notification du système.";
-App::$strings["System Notifications"] = "Notifications du système";
App::$strings["Unable to create element."] = "Impossible de créer l'entrée.";
App::$strings["Unable to update menu element."] = "Impossible de mettre à jour l'entrée de menu.";
App::$strings["Unable to add menu element."] = "Impossible d'ajouter l'entrée de menu.";
+App::$strings["Not found."] = "Introuvable.";
App::$strings["Menu Item Permissions"] = "Permissions de l'entrée de menu";
App::$strings["(click to open/close)"] = "(cliquer pour ouvrir/fermer)";
App::$strings["Link Name"] = "Nom du lien";
App::$strings["Link or Submenu Target"] = "Lien ou sous-menu cible";
App::$strings["Enter URL of the link or select a menu name to create a submenu"] = "Entrez l'URL du lien ou sélectionnez un nom de menu pour créer un sous-menu";
App::$strings["Use magic-auth if available"] = "Utiliser l'authentification distante, quand disponible";
+App::$strings["No"] = "Non";
+App::$strings["Yes"] = "Oui";
App::$strings["Open link in new window"] = "Ouvrir le lien dans une nouvelle fenêtre";
App::$strings["Order in list"] = "Ordre dans la liste";
App::$strings["Higher numbers will sink to bottom of listing"] = "Les nombres les plus élevés seront au bas de la liste";
@@ -592,6 +147,77 @@ App::$strings["Menu item deleted."] = "Entrée de menu supprimée.";
App::$strings["Menu item could not be deleted."] = "Impossible de supprimer l'entrée de menu.";
App::$strings["Edit Menu Element"] = "Modifier l'entrée de menu";
App::$strings["Link text"] = "Texte du lien";
+App::$strings["Calendar entries imported."] = "Entrées du calendrier importées.";
+App::$strings["No calendar entries found."] = "Aucune entrée du calendrier trouvée.";
+App::$strings["Event can not end before it has started."] = "La fin de l'événement ne peut être antérieure à son début.";
+App::$strings["Unable to generate preview."] = "Impossible de générer l'aperçu.";
+App::$strings["Event title and start time are required."] = "Un titre et une date de début sont requises pour l'événement.";
+App::$strings["Event not found."] = "Événement introuvable.";
+App::$strings["event"] = "événement";
+App::$strings["Edit event title"] = "Modifier le titre de l'événement";
+App::$strings["Event title"] = "Titre de l'événement";
+App::$strings["Required"] = "Requis";
+App::$strings["Categories (comma-separated list)"] = "Catégories (séparées par des virgules)";
+App::$strings["Edit Category"] = "Modifier la catégorie";
+App::$strings["Category"] = "Catégorie";
+App::$strings["Edit start date and time"] = "Modifier la date et l'heure de début";
+App::$strings["Start date and time"] = "Date et heure de début";
+App::$strings["Finish date and time are not known or not relevant"] = "Date et heure de fin inconnues ou sans objet";
+App::$strings["Edit finish date and time"] = "Modifier la date et l'heure de fin";
+App::$strings["Finish date and time"] = "Date et heure de fin";
+App::$strings["Adjust for viewer timezone"] = "Ajuster au fuseau horaire du visiteur";
+App::$strings["Important for events that happen in a particular place. Not practical for global holidays."] = "Important pour les événements se tenant en un lieu particulier. Pas pratique pour les vacances communes à de nombreux pays dans le monde.";
+App::$strings["Edit Description"] = "Modifier la description";
+App::$strings["Description"] = "Description";
+App::$strings["Edit Location"] = "Modifier l'emplacement";
+App::$strings["Preview"] = "Aperçu";
+App::$strings["Permission settings"] = "Gérer les autorisations";
+App::$strings["Timezone:"] = "Fuseau horaire&nbsp;:";
+App::$strings["Advanced Options"] = "Options avancées";
+App::$strings["l, F j"] = "l, F j";
+App::$strings["Edit event"] = "Modifier l'événement";
+App::$strings["Delete event"] = "Supprimer l'événement";
+App::$strings["Link to Source"] = "Lien vers la Source";
+App::$strings["calendar"] = "calendrier";
+App::$strings["Edit Event"] = "Modifier l'événement";
+App::$strings["Create Event"] = "Créer un événement";
+App::$strings["Previous"] = "Précédent";
+App::$strings["Next"] = "Suivant";
+App::$strings["Export"] = "Export";
+App::$strings["Month"] = "Mois";
+App::$strings["Week"] = "Semaine";
+App::$strings["Day"] = "Jour";
+App::$strings["Today"] = "Aujourd'hui";
+App::$strings["Event removed"] = "Événement supprimé";
+App::$strings["Failed to remove event"] = "Impossible de supprimer l'événement";
+App::$strings["App installed."] = "Application installée.";
+App::$strings["Malformed app."] = "Erreur de l'application - Malformée.";
+App::$strings["Embed code"] = "Imbriquer le code";
+App::$strings["Edit App"] = "Modifier l'application";
+App::$strings["Create App"] = "Créer une application";
+App::$strings["Name of app"] = "Nom de l'application";
+App::$strings["Location (URL) of app"] = "Emplacement (URL) de l'application";
+App::$strings["Photo icon URL"] = "URL de l'icône à utiliser pour cette photo";
+App::$strings["80 x 80 pixels - optional"] = "80 x 80 pixels - facultatif";
+App::$strings["Categories (optional, comma separated list)"] = "Catégories (séparées par des virgules)";
+App::$strings["Version ID"] = "Identifiant de version";
+App::$strings["Price of app"] = "Prix de l'application";
+App::$strings["Location (URL) to purchase app"] = "Emplacement (URL) pour l'achat de l'application";
+App::$strings["Please login."] = "Merci de vous connecter.";
+App::$strings["Hub not found."] = "Hub introuvable.";
+App::$strings["photo"] = "photo";
+App::$strings["status"] = "état";
+App::$strings["%1\$s is following %2\$s's %3\$s"] = "%1\$s suit %3\$s de %2\$s";
+App::$strings["%1\$s stopped following %2\$s's %3\$s"] = "%1\$s ne suit plus %3\$s de %2\$s";
+App::$strings["Nothing to import."] = "Rien à importer.";
+App::$strings["Unable to download data from old server"] = "Impossible de récupérer les données de l'ancien serveur";
+App::$strings["Imported file is empty."] = "Le fichier importé est vide.";
+App::$strings["Warning: Database versions differ by %1\$d updates."] = "Attention&nbsp;: les versions de bases de données diffèrent de %1\$d mises à jour.";
+App::$strings["Import completed"] = "L'import est terminé.";
+App::$strings["Import Items"] = "Importer";
+App::$strings["Use this form to import existing posts and content from an export file."] = "Utiliser ce formulaire pour importer des publications et du contenu existant d'un fichier d'export.";
+App::$strings["File to Upload"] = "Fichier à envoyer";
+App::$strings["You have created %1$.0f of %2$.0f allowed channels."] = "Vous avez créé %1$.0f des %2$.0f canaux autorisés.";
App::$strings["Name or caption"] = "Nom ou libellé";
App::$strings["Examples: \"Bob Jameson\", \"Lisa and her Horses\", \"Soccer\", \"Aviation Group\""] = "Exemples&nbsp;: \"Jérôme Dutilleul\", \"Louise et ses chevaux\", \"Football\", \"Club d'aéromodélisme\"";
App::$strings["Choose a short nickname"] = "Choisissez un alias";
@@ -602,312 +228,134 @@ App::$strings["Read more about roles"] = "En savoir plus sur les rôles";
App::$strings["Create Channel"] = "Créer le canal";
App::$strings["A channel is your identity on this network. It can represent a person, a blog, or a forum to name a few. Channels can make connections with other channels to share information with highly detailed permissions."] = "Un canal est votre identité sur ce réseau. Il peut représenter une personne, un blog, ou un forum par exemple. Les canaux peuvent entrer en contact les uns avec les autres pour partager des informations avec des permissions d'accès très fines.";
App::$strings["or <a href=\"import\">import an existing channel</a> from another location."] = "ou <a href=\"import\">importer un canal existant</a> d'un autre serveur.";
-App::$strings["Invalid request identifier."] = "Identifiant de requête invalide.";
-App::$strings["Discard"] = "Annuler";
-App::$strings["Mark all system notifications seen"] = "Marquer toutes les notifications système comme vues";
-App::$strings["Page owner information could not be retrieved."] = "Impossible d'obtenir des informations sur le propriétaire de la page.";
-App::$strings["Profile Photos"] = "Photos du profil";
-App::$strings["Album not found."] = "Album introuvable.";
-App::$strings["Delete Album"] = "Supprimer l'album";
-App::$strings["Multiple storage folders exist with this album name, but within different directories. Please remove the desired folder or folders using the Files manager"] = "";
-App::$strings["Delete Photo"] = "Supprimer la photo";
-App::$strings["No photos selected"] = "Aucune photo selectionnée";
-App::$strings["Access to this item is restricted."] = "L'accès à l'élément est restreint.";
-App::$strings["%1$.2f MB of %2$.2f MB photo storage used."] = "Vous avez utilisé %1$.2f mégaoctets sur les %2$.2f autorisés pour le stockage des photos.";
-App::$strings["%1$.2f MB photo storage used."] = "%1$.2f méga-octets utilisés pour le stockage des photos.";
-App::$strings["Upload Photos"] = "Téléverser des photos";
-App::$strings["Enter an album name"] = "Entrer un nom d'album";
-App::$strings["or select an existing album (doubleclick)"] = "ou sélectionner un album existant (double-clic)";
-App::$strings["Create a status post for this upload"] = "Créer une publication de statut pour cet envoi";
-App::$strings["Caption (optional):"] = "Légende (facultative)";
-App::$strings["Description (optional):"] = "Description (facultative)";
-App::$strings["Album name could not be decoded"] = "Le nom de l'Album n'a pu être décodé";
-App::$strings["Contact Photos"] = "Photos de contact";
-App::$strings["Show Newest First"] = "Les plus récent(e)s en premier";
-App::$strings["Show Oldest First"] = "Les moins récent(e)s en premier";
-App::$strings["View Photo"] = "Voir la photo";
-App::$strings["Edit Album"] = "Modifier l'album";
-App::$strings["Permission denied. Access to this item may be restricted."] = "Permission refusée. L'accès à cet élément peut avoir été restreint.";
-App::$strings["Photo not available"] = "Photo non disponible";
-App::$strings["Use as profile photo"] = "Utiliser comme photo du profil";
-App::$strings["Use as cover photo"] = "";
-App::$strings["Private Photo"] = "Photo privée";
-App::$strings["View Full Size"] = "Voir en taille réelle";
-App::$strings["Remove"] = "Retirer";
-App::$strings["Edit photo"] = "Modifier la photo";
-App::$strings["Rotate CW (right)"] = "Rotation horaire (droite)";
-App::$strings["Rotate CCW (left)"] = "Rotation anti-horaire (gauche)";
-App::$strings["Enter a new album name"] = "Entrer un nouveau nom d'album";
-App::$strings["or select an existing one (doubleclick)"] = "ou en sélectionner un existant (double-clic)";
-App::$strings["Caption"] = "Titre/légende";
-App::$strings["Add a Tag"] = "Ajouter une étiquette";
-App::$strings["Example: @bob, @Barbara_Jensen, @jim@example.com"] = "Exemple&nbsp;: @marc, @Barbara_Jensen, @charles@exemple.com, #Ile_de_France, #marathon";
-App::$strings["Flag as adult in album view"] = "Marquer comme \"adulte\" dans l'affichage de l'album";
-App::$strings["I like this (toggle)"] = "J'aime (oui/non)";
-App::$strings["I don't like this (toggle)"] = "Je n'aime pas (oui/non)";
-App::$strings["Please wait"] = "Merci de patienter";
-App::$strings["This is you"] = "C'est vous";
-App::$strings["Comment"] = "Commenter";
-App::$strings["__ctx:title__ Likes"] = "Aime";
-App::$strings["__ctx:title__ Dislikes"] = "N'aime pas";
-App::$strings["__ctx:title__ Agree"] = "D'accord";
-App::$strings["__ctx:title__ Disagree"] = "Pas d'accord";
-App::$strings["__ctx:title__ Abstain"] = "Abstention";
-App::$strings["__ctx:title__ Attending"] = "Participations";
-App::$strings["__ctx:title__ Not attending"] = "Non-participations";
-App::$strings["__ctx:title__ Might attend"] = "Participation possible";
-App::$strings["View all"] = "Voir tout";
-App::$strings["__ctx:noun__ Like"] = array(
- 0 => "Aime",
- 1 => "Aime",
-);
-App::$strings["__ctx:noun__ Dislike"] = array(
- 0 => "N'aime pas",
- 1 => "N'aime pas",
-);
-App::$strings["Photo Tools"] = "";
-App::$strings["In This Photo:"] = "Dans cette photo&nbsp;:";
-App::$strings["Map"] = "Carte";
-App::$strings["__ctx:noun__ Likes"] = "Aime";
-App::$strings["__ctx:noun__ Dislikes"] = "N'aime pas";
-App::$strings["Close"] = "Fermer";
-App::$strings["View Album"] = "Voir l'album";
-App::$strings["Recent Photos"] = "Photos récentes";
-App::$strings["sent you a private message"] = "vous a envoyé un message privé";
-App::$strings["added your channel"] = "a ajouté votre canal";
-App::$strings["g A l F d"] = "g A l F d";
-App::$strings["[today]"] = "[aujourd'hui]";
-App::$strings["posted an event"] = "a publié un événement";
-App::$strings["Unable to find your hub."] = "Impossible de trouver votre hub.";
-App::$strings["Post successful."] = "Publication réussie.";
-App::$strings["OpenID protocol error. No ID returned."] = "Erreur du protocole OpenID. Pas d'ID retourné.";
-App::$strings["Login failed."] = "Échec de la connexion.";
-App::$strings["Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum."] = "Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.";
-App::$strings["This setting requires special processing and editing has been blocked."] = "Ce paramètre nécessité un traitement spécial, les modifications ont été bloquées.";
-App::$strings["Configuration Editor"] = "Editeur de configuration";
-App::$strings["Warning: Changing some settings could render your channel inoperable. Please leave this page unless you are comfortable with and knowledgeable about how to correctly use this feature."] = "Attention&nbsp;:modifier certains paramètres peut rendre votre canal inutilisable. Merci d'ignorer cette page à moins d'être suffisamment à l'aise de savoir comment utiliser correctement cette fonctionnalité.";
-App::$strings["Layout updated."] = "Mise en page mise à jour.";
-App::$strings["Edit System Page Description"] = "Modifier la description de la page du système";
-App::$strings["Layout not found."] = "Mise en page introuvable.";
-App::$strings["Module Name:"] = "Nom du module&nbsp;:";
-App::$strings["Layout Help"] = "Aide à la mise en page";
-App::$strings["Poke"] = "Tapoter";
-App::$strings["Poke somebody"] = "Taquiner quelqu'un";
-App::$strings["Poke/Prod"] = "Tapoter/Encourager";
-App::$strings["Poke, prod or do other things to somebody"] = "Taquiner, pousser ou faire autre chose à quelqu'un";
-App::$strings["Recipient"] = "Destinataire";
-App::$strings["Choose what you wish to do to recipient"] = "Choisir ce que vous voulez faire au destinataire";
-App::$strings["Make this post private"] = "Rendre cette publication privée";
-App::$strings["Fetching URL returns error: %1\$s"] = "Récupération d'URL échouée&nbsp;: %1\$s";
-App::$strings["Profile not found."] = "Profil introuvable.";
-App::$strings["Profile deleted."] = "Profil supprimé.";
-App::$strings["Profile-"] = "Profil-";
-App::$strings["New profile created."] = "Nouveau profil créé.";
-App::$strings["Profile unavailable to clone."] = "Profil impossible à cloner.";
-App::$strings["Profile unavailable to export."] = "Impossible d'exporter le profil.";
-App::$strings["Profile Name is required."] = "Le nom du profil est obligatoire.";
-App::$strings["Marital Status"] = "Statut marital";
-App::$strings["Romantic Partner"] = "Partenaire amoureux";
-App::$strings["Likes"] = "Aime";
-App::$strings["Dislikes"] = "N'aime pas";
-App::$strings["Work/Employment"] = "Travail/Occupation";
-App::$strings["Religion"] = "Religion/Croyance";
-App::$strings["Political Views"] = "Opinions politiques";
-App::$strings["Sexual Preference"] = "Préférences sexuelle";
-App::$strings["Homepage"] = "Site Internet";
-App::$strings["Interests"] = "Centres d'intérêt";
-App::$strings["Profile updated."] = "Profil mis à jour.";
-App::$strings["Hide your connections list from viewers of this profile"] = "";
-App::$strings["Edit Profile Details"] = "Modifier les détails du profil";
-App::$strings["View this profile"] = "Voir ce profil";
-App::$strings["Edit visibility"] = "Changer la visibilité";
-App::$strings["Profile Tools"] = "";
-App::$strings["Change cover photo"] = "";
-App::$strings["Change profile photo"] = "Changer la photo du profil";
-App::$strings["Create a new profile using these settings"] = "Créer un nouveau profil avec ces paramètres";
-App::$strings["Clone this profile"] = "Cloner ce profil";
-App::$strings["Delete this profile"] = "Supprimer ce profil";
-App::$strings["Add profile things"] = "Ajouter des éléments de profil";
-App::$strings["Personal"] = "Me concernant";
-App::$strings["Relation"] = "";
-App::$strings["Miscellaneous"] = "Divers";
-App::$strings["Import profile from file"] = "Importer le profil à partir d'un fichier";
-App::$strings["Export profile to file"] = "Exporter le profil vers un fichier.";
-App::$strings["Your gender"] = "";
-App::$strings["Marital status"] = "";
-App::$strings["Sexual preference"] = "";
-App::$strings["Profile name"] = "";
-App::$strings["This is your default profile."] = "Ceci est votre profil par défaut.";
-App::$strings["Your full name"] = "";
-App::$strings["Title/Description"] = "Titre/description";
-App::$strings["Street address"] = "";
-App::$strings["Locality/City"] = "Ville";
-App::$strings["Region/State"] = "Région";
-App::$strings["Postal/Zip code"] = "";
-App::$strings["Country"] = "Pays";
-App::$strings["Who (if applicable)"] = "Qui (si applicable)";
-App::$strings["Examples: cathy123, Cathy Williams, cathy@example.com"] = "Exemples&nbsp;: marie123, Marie Deschamps, marie@exemple.com";
-App::$strings["Since (date)"] = "";
-App::$strings["Tell us about yourself"] = "";
-App::$strings["Hometown"] = "Ville de naissance";
-App::$strings["Political views"] = "";
-App::$strings["Religious views"] = "";
-App::$strings["Keywords used in directory listings"] = "";
-App::$strings["Example: fishing photography software"] = "Exemple&nbsp;: escrime photographie modélisme";
-App::$strings["Musical interests"] = "Goûts musicaux";
-App::$strings["Books, literature"] = "Livres, littérature";
-App::$strings["Television"] = "Télévision";
-App::$strings["Film/Dance/Culture/Entertainment"] = "";
-App::$strings["Hobbies/Interests"] = "Loisirs/Centres d'intêret";
-App::$strings["Love/Romance"] = "";
-App::$strings["School/Education"] = "";
-App::$strings["Contact information and social networks"] = "";
-App::$strings["My other channels"] = "Mes autres canaux";
-App::$strings["Profile Image"] = "Image du profil";
-App::$strings["Edit Profiles"] = "Modifier les profils";
-App::$strings["Shift-reload the page or clear browser cache if the new photo does not display immediately."] = "Shift-rechargez votre page, ou videz le cache du navigateur si la photo ne s'affiche pas immédiatement.";
-App::$strings["Upload Profile Photo"] = "Téléverser une photo de profil";
-App::$strings["Invalid profile identifier."] = "Identifiant de profil invalide.";
-App::$strings["Profile Visibility Editor"] = "Éditeur de visibilité de profil";
-App::$strings["Profile"] = "Profil";
-App::$strings["Click on a contact to add or remove."] = "Cliquer sur un contact pour l'ajouter ou le retirer.";
-App::$strings["Visible To"] = "Visible par";
-App::$strings["Public Hubs"] = "Instances publiques";
-App::$strings["The listed hubs allow public registration for the \$Projectname network. All hubs in the network are interlinked so membership on any of them conveys membership in the network as a whole. Some hubs may require subscription or provide tiered service plans. The hub itself <strong>may</strong> provide additional details."] = "Les sites listés permettent l'enregistrement public de comptes pour le réseau \$Projectname. Tous les sites du réseau sont reliés entre eux, être membre d'un site revient à être membre de tous. Certains sites peuvent demander une souscription ou proposer différents niveaux de service. Chaque site <strong>peut</strong> fournir des détails supplémentaires.";
-App::$strings["Hub URL"] = "URL du site";
-App::$strings["Access Type"] = "Type d'accès";
-App::$strings["Registration Policy"] = "Politique d'inscription";
-App::$strings["Stats"] = "";
-App::$strings["Software"] = "";
-App::$strings["Ratings"] = "Evaluations";
-App::$strings["Rate"] = "Evaluer";
-App::$strings["Website:"] = "Site web&nbsp;:";
-App::$strings["Remote Channel [%s] (not yet known on this site)"] = "Canal distant [%s] (encore inconnu sur ce site)";
-App::$strings["Rating (this information is public)"] = "Evaluation (cette information est publique)";
-App::$strings["Optionally explain your rating (this information is public)"] = "Explication facultative de votre évaluation (cette information est publique)";
-App::$strings["No ratings"] = "Pas de note";
-App::$strings["Rating: "] = "Evaluation&nbsp:";
-App::$strings["Website: "] = "Site web&nbsp;:";
-App::$strings["Description: "] = "Description&nbsp;:";
-App::$strings["Theme settings updated."] = "Paramètres du thème mis à jour.";
-App::$strings["# Accounts"] = "# Comptes";
-App::$strings["# blocked accounts"] = "# comptes bloqués";
-App::$strings["# expired accounts"] = "# comptes expirés";
-App::$strings["# expiring accounts"] = "# comptes expirant";
-App::$strings["# Channels"] = "# Canaux";
-App::$strings["# primary"] = "# primaire";
-App::$strings["# clones"] = "# clones";
-App::$strings["Message queues"] = "File des messages";
-App::$strings["Your software should be updated"] = "";
-App::$strings["Administration"] = "Administration";
-App::$strings["Summary"] = "Résumé";
-App::$strings["Registered accounts"] = "Comptes enregistrés";
-App::$strings["Pending registrations"] = "Inscriptions en attente";
-App::$strings["Registered channels"] = "Canaux enregistrés";
-App::$strings["Active plugins"] = "Greffons actifs";
-App::$strings["Version"] = "Version";
-App::$strings["Repository version (master)"] = "";
-App::$strings["Repository version (dev)"] = "";
-App::$strings["Site settings updated."] = "Paramètres du site sauvegardés.";
-App::$strings["Default"] = "Défaut";
-App::$strings["mobile"] = "mobile";
-App::$strings["experimental"] = "expérimental";
-App::$strings["unsupported"] = "non maintenu";
-App::$strings["Yes - with approval"] = "Oui - avec approbation";
-App::$strings["My site is not a public server"] = "Mon site n'est pas un serveur public";
-App::$strings["My site has paid access only"] = "Mon site est à accès payant uniquement";
-App::$strings["My site has free access only"] = "Mon site est gratuit uniquement";
-App::$strings["My site offers free accounts with optional paid upgrades"] = "Mon site offre des comptes gratuits avec des améliorations payantes facultatives";
-App::$strings["Site"] = "Site";
-App::$strings["Registration"] = "Inscription";
-App::$strings["File upload"] = "Envoi de fichier";
-App::$strings["Policies"] = "Stratégies";
-App::$strings["Advanced"] = "Avancé";
-App::$strings["Site name"] = "Nom du site";
-App::$strings["Banner/Logo"] = "Bannière/logo";
-App::$strings["Administrator Information"] = "Informations de l'administrateur";
-App::$strings["Contact information for site administrators. Displayed on siteinfo page. BBCode can be used here"] = "Coordonnées de l'administrateur du site. Affichées sur la page 'siteinfo'. Vous pouvez utiliser du BBCode ici";
-App::$strings["System language"] = "Langue du système";
-App::$strings["System theme"] = "Thème du système";
-App::$strings["Default system theme - may be over-ridden by user profiles - <a href='#' id='cnftheme'>change theme settings</a>"] = "Thème par défaut - il peut être changé pour chaque profil utilisateur - <a href='#' id='cnftheme'>modifier le thème</a>";
-App::$strings["Mobile system theme"] = "Thème par défaut pour les mobiles";
-App::$strings["Theme for mobile devices"] = "Thème pour les mobiles";
-App::$strings["Allow Feeds as Connections"] = "Autoriser les Flux (RSS) comme contacts";
-App::$strings["(Heavy system resource usage)"] = "(Impact important sur les ressources)";
-App::$strings["Maximum image size"] = "Taille maximale des images";
-App::$strings["Maximum size in bytes of uploaded images. Default is 0, which means no limits."] = "Taille maximum, en octets, des images envoyées. Par défaut 0, soit sans limite.";
-App::$strings["Does this site allow new member registration?"] = "Est-ce que l'enregistrement de nouveaux membres est autorisé sur ce site&nbsp;?";
-App::$strings["Invitation only"] = "Sur invitation seulement";
-App::$strings["Only allow new member registrations with an invitation code. Above register policy must be set to Yes."] = "N'autoriser que les nouvelles inscriptions avec code d'invitation. La stratégie d'inscription ci-dessus doit être mise sur \"Oui\".";
-App::$strings["Which best describes the types of account offered by this hub?"] = "Quelle est la meilleure description des types de comptes proposés sur ce hub&nbsp;?";
-App::$strings["Register text"] = "Texte d'inscription";
-App::$strings["Will be displayed prominently on the registration page."] = "Sera affiché de manière bien visible sur le formulaire d'inscription.";
-App::$strings["Site homepage to show visitors (default: login box)"] = "Page d'accueil du site à montrer aux visiteurs (par défaut&nbsp;:boîte de dialogue de connexion)";
-App::$strings["example: 'public' to show public stream, 'page/sys/home' to show a system webpage called 'home' or 'include:home.html' to include a file."] = "exemple&nbsp;:'public' pour montrer le flux public, 'page/sys/home' pour montrer une page système appelée 'home' ou 'include:home.html' pour inclure un fichier.";
-App::$strings["Preserve site homepage URL"] = "Préserver l'adresse d'accueil du site";
-App::$strings["Present the site homepage in a frame at the original location instead of redirecting"] = "Présenter la page d'accueil du site dans un cadre à l'adresse d'origine, plutôt que de rediriger";
-App::$strings["Accounts abandoned after x days"] = "Les comptes sont abandonnés après x jours";
-App::$strings["Will not waste system resources polling external sites for abandonded accounts. Enter 0 for no time limit."] = "Eviter de gaspiller les ressources du système en interrogeant des hubs distants pour des canaux abandonnés. Mettez 0 pour ne pas avoir de limite de temps.";
-App::$strings["Allowed friend domains"] = "Domaines amicaux autorisés";
-App::$strings["Comma separated list of domains which are allowed to establish friendships with this site. Wildcards are accepted. Empty to allow any domains"] = "Liste de noms de domaines séparés par des virgules pour lesquels ce site acceptera les demandes d'amitié. Les caractères génériques (*) sont acceptés. Laissez vide pour accepter tous les domaines.";
-App::$strings["Allowed email domains"] = "Domaines de courriels autorisés";
-App::$strings["Comma separated list of domains which are allowed in email addresses for registrations to this site. Wildcards are accepted. Empty to allow any domains"] = "Liste de noms de domaines séparés par des virgules dont les adresses de courriel seront autorisées lors de l'inscription à ce site. Les caractères génériques (*) sont acceptés. Laissez vide pour accepter tous les domaines.";
-App::$strings["Not allowed email domains"] = "Domaines de courriel non autorisés";
-App::$strings["Comma separated list of domains which are not allowed in email addresses for registrations to this site. Wildcards are accepted. Empty to allow any domains, unless allowed domains have been defined."] = "Liste de noms de domaines - séparés par des virgules - dont les adresses de courriel ne seront pas autorisées lors de l'inscription à ce site. Les caractères génériques (*) sont acceptés. Laissez vide pour accepter tous les domaines, sauf si des domaines autorisés ont été définis.";
-App::$strings["Verify Email Addresses"] = "Demander vérification des adresses de courriel";
-App::$strings["Check to verify email addresses used in account registration (recommended)."] = "Cocher pour que les adresses utilisées à l'inscription soient vérifiées (recommandé).";
-App::$strings["Force publish"] = "Publicité forcée";
-App::$strings["Check to force all profiles on this site to be listed in the site directory."] = "Cocher pour forcer la publication de tous les profils du site dans l'annuaire.";
-App::$strings["Import Public Streams"] = "Flux publics importés";
-App::$strings["Import and allow access to public content pulled from other sites. Warning: this content is unmoderated."] = "Importer du contenu public à partir d'autres sites et autoriser l'accès à ce contenu. Attention&nbsp;: ce contenu n'est pas modéré.";
-App::$strings["Login on Homepage"] = "";
-App::$strings["Present a login box to visitors on the home page if no other content has been configured."] = "Présenter une boîte de dialogue de connexion aux visiteurs sur la page d'accueil si aucun autre contenu n'a été configuré.";
-App::$strings["Enable context help"] = "";
-App::$strings["Display contextual help for the current page when the help button is pressed."] = "";
-App::$strings["Directory Server URL"] = "URL du serveur d'annuaire";
-App::$strings["Default directory server"] = "Serveur d'annuaire par défaut";
-App::$strings["Proxy user"] = "Utilisateur du proxy";
-App::$strings["Proxy URL"] = "URL du proxy";
-App::$strings["Network timeout"] = "Délai maximal du réseau";
-App::$strings["Value is in seconds. Set to 0 for unlimited (not recommended)."] = "En secondes. Mettre à 0 pour ne pas avoir de délai maximal (non recommandé).";
-App::$strings["Delivery interval"] = "Intervalle de distribution";
-App::$strings["Delay background delivery processes by this many seconds to reduce system load. Recommend: 4-5 for shared hosts, 2-3 for virtual private servers. 0-1 for large dedicated servers."] = "Temporise le processus de distribution de tant de secondes pour réduire la charge sur le système. Valeurs recommandées&nbsp;: 4-5 pour les serveurs mutualisés, 2-3 pour les VPS. 0-1 pour les gros serveurs dédiés.";
-App::$strings["Deliveries per process"] = "Distributions par processus";
-App::$strings["Number of deliveries to attempt in a single operating system process. Adjust if necessary to tune system performance. Recommend: 1-5."] = "Nombre de distributions à tenter au sein d'un seul processus système. Ajuster si nécessaire pour affiner la performance du système. Recommandé&nbsp;:1-5.";
-App::$strings["Poll interval"] = "Intervalle de scrutation";
-App::$strings["Delay background polling processes by this many seconds to reduce system load. If 0, use delivery interval."] = "Temporise le processus de scrutation en tâche de fond de tant de secondes, pour réduire la charge. Si 0, utilise l'intervalle de distribution.";
-App::$strings["Maximum Load Average"] = "Charge maximale moyenne";
-App::$strings["Maximum system load before delivery and poll processes are deferred - default 50."] = "Charge système maximale au-delà de laquelle distribution et scrutation sont reportées - par défaut 50.";
-App::$strings["Expiration period in days for imported (grid/network) content"] = "Délai d'expiration pour le contenu importé (réseau)";
-App::$strings["0 for no expiration of imported content"] = "0 pour ne pas expirer le contenu importé";
+App::$strings["Channel removals are not allowed within 48 hours of changing the account password."] = "Il est impossible de supprimer un canal moins de 48 heures après avoir changé le mot de passe d'un compte.";
+App::$strings["Remove This Channel"] = "Supprimer ce canal";
+App::$strings["WARNING: "] = "AVERTISSEMENT&nbsp;:";
+App::$strings["This channel will be completely removed from the network. "] = "Ce canal sera complètement supprimé du réseau.";
+App::$strings["This action is permanent and can not be undone!"] = "Cette action est permanente et irréversible&nbsp;!";
+App::$strings["Please enter your password for verification:"] = "Merci de saisir votre mot de passe pour vérification&nbsp;:";
+App::$strings["Remove this channel and all its clones from the network"] = "Supprimer ce canal ainsi que tous ses clones sur le réseau";
+App::$strings["By default only the instance of the channel located on this hub will be removed from the network"] = "Par défaut, seule l'instance du canal présente sur ce hub sera supprimée du réseau";
+App::$strings["Remove Channel"] = "Supprimer le canal";
+App::$strings["Files: shared with me"] = "Fichiers&nbsp;: partagés avec moi";
+App::$strings["Name"] = "Nom";
+App::$strings["NEW"] = "NOUVEAU";
+App::$strings["Size"] = "Taille";
+App::$strings["Last Modified"] = "Modifié le";
+App::$strings["Remove all files"] = "Supprimer tous les fichiers";
+App::$strings["Remove this file"] = "Supprimer ce fichier";
+App::$strings["\$Projectname Server - Setup"] = "Serveur \$Projectname - configuration";
+App::$strings["Could not connect to database."] = "Impossible de se connecter à la base de données.";
+App::$strings["Could not connect to specified site URL. Possible SSL certificate or DNS issue."] = "Impossible de se connecter à l'URL indiquée. Problème potentiel de certificat SSL/TLS ou de DNS.";
+App::$strings["Could not create table."] = "Impossible de créer la table.";
+App::$strings["Your site database has been installed."] = "La base de données de votre site a été installée.";
+App::$strings["You may need to import the file \"install/schema_xxx.sql\" manually using a database client."] = "Vous pourriez avoir besoin d'importer le fichier \"install/schema_xxx.sql\" manuellement via un client de base de données (ex: phpmyadmin).";
+App::$strings["Please see the file \"install/INSTALL.txt\"."] = "Merci de consulter le fichier \"install/INSTALL.txt\".";
+App::$strings["System check"] = "Vérification du système";
+App::$strings["Check again"] = "Re-vérifier";
+App::$strings["Database connection"] = "Connexion à la base de données";
+App::$strings["In order to install \$Projectname we need to know how to connect to your database."] = "Pour installer \$Projectname, nous avons besoin de savoir comment se connecter à votre base de données.";
+App::$strings["Please contact your hosting provider or site administrator if you have questions about these settings."] = "Merci de contacter votre prestataire d'hébergement ou votre administrateur de site si vous avez des questions à propos de ces paramètres.";
+App::$strings["The database you specify below should already exist. If it does not, please create it before continuing."] = "La base de données que vous allez spécifier doit exister. Si ce n'est pas déjà le cas, merci de la créer avant de continuer.";
+App::$strings["Database Server Name"] = "Nom du serveur de base de données";
+App::$strings["Default is 127.0.0.1"] = "Par défaut 127.0.0.1";
+App::$strings["Database Port"] = "Port de la base de données";
+App::$strings["Communication port number - use 0 for default"] = "Numéro TCP du port - utilisez 0 pour la valeur par défaut";
+App::$strings["Database Login Name"] = "Identifiant de connexion à la Base de Données";
+App::$strings["Database Login Password"] = "Mot de passe de connexion à la Base de Données";
+App::$strings["Database Name"] = "Nom de la Base de Données";
+App::$strings["Database Type"] = "Type de base de données";
+App::$strings["Site administrator email address"] = "Adresse de courriel de l'administrateur du site";
+App::$strings["Your account email address must match this in order to use the web admin panel."] = "Votre compte devra utiliser la même adresse de courriel pour pouvoir utiliser l'administration web.";
+App::$strings["Website URL"] = "URL du site web";
+App::$strings["Please use SSL (https) URL if available."] = "Veuillez utiliser SSL/TLS (https) si disponible.";
+App::$strings["Please select a default timezone for your website"] = "Veuillez choisir un fuseau horaire par défaut pour votre site";
+App::$strings["Basic/Minimal Social Networking"] = "Réseau social de base";
+App::$strings["Standard Configuration (default)"] = "Configuration standard par défaut";
+App::$strings["Professional"] = "Professionel";
+App::$strings["Site settings"] = "Paramètres du site";
+App::$strings["Server Configuration/Role"] = "Configuration du site.";
+App::$strings["PHP version 5.5 or greater is required."] = "PHP version 5.5 ou supérieur est requis";
+App::$strings["PHP version"] = "Version de PHP";
+App::$strings["Could not find a command line version of PHP in the web server PATH."] = "Impossible de trouver une version CLI de PHP dans le PATH du serveur web.";
+App::$strings["If you don't have a command line version of PHP installed on server, you will not be able to run background polling via cron."] = "En l'absence de version CLI de PHP sur votre serveur, vous ne pourrez pas utiliser la synchronisation en arrière-plan via cron.";
+App::$strings["PHP executable path"] = "Chemin vers l'éxecutable PHP";
+App::$strings["Enter full path to php executable. You can leave this blank to continue the installation."] = "Entrez le chemin complet vers l'exécutable php. Vous pouvez continuer l'installation sans.";
+App::$strings["Command line PHP"] = "PHP en ligne de commande (CLI)";
+App::$strings["Unable to check command line PHP, as shell_exec() is disabled. This is required."] = "Impossible de vérifier la ligne de commande PHP, car shell_exec () est désactivé. Ceci est nécessaire.";
+App::$strings["The command line version of PHP on your system does not have \"register_argc_argv\" enabled."] = "La version CLI de PHP sur votre système n'a pas l'option \"register_argc_argv\" activée.";
+App::$strings["This is required for message delivery to work."] = "Elle est nécessaire pour la distribution des messages.";
+App::$strings["PHP register_argc_argv"] = "PHP register_argc_argv";
+App::$strings["Your max allowed total upload size is set to %s. Maximum size of one file to upload is set to %s. You are allowed to upload up to %d files at once."] = "Votre taille de téléversement maximale totale autorisée est fixée à %s. La taille maximale d'un seul fichier à téléverser est fixée à %s. Vous pouvez téléverser jusqu'à %d fichier(s) à la fois.";
+App::$strings["You can adjust these settings in the server php.ini file."] = "Vous pouvez ajuster ces paramètres dans le fichier php.ini du serveur.";
+App::$strings["PHP upload limits"] = "Limites de téléversement de PHP";
+App::$strings["Error: the \"openssl_pkey_new\" function on this system is not able to generate encryption keys"] = "Erreur&nbsp;: la fonction \"openssl_pkey_new\" de ce système n'est pas capable de générer des clefs de chiffrement";
+App::$strings["If running under Windows, please see \"http://www.php.net/manual/en/openssl.installation.php\"."] = "Si vous êtes sur un serveur Windows, merci de consulter \"http://www.php.net/manual/fr/openssl.installation.php\".";
+App::$strings["Generate encryption keys"] = "Générer les clefs de chiffrement";
+App::$strings["libCurl PHP module"] = "module PHP libCurl";
+App::$strings["GD graphics PHP module"] = "module PHP GD graphics";
+App::$strings["OpenSSL PHP module"] = "module PHP OpenSSL";
+App::$strings["PDO database PHP module"] = "module PDO de la base de données PHP";
+App::$strings["mb_string PHP module"] = "module PHP mb_string";
+App::$strings["xml PHP module"] = "module PHP xml";
+App::$strings["Apache mod_rewrite module"] = "module Apache mod_rewrite";
+App::$strings["Error: Apache webserver mod-rewrite module is required but not installed."] = "Erreur&nbsp;: le module mod-rewrite du serveur web Apache est requis, mais pas installé.";
+App::$strings["exec"] = "exécuter";
+App::$strings["Error: exec is required but is either not installed or has been disabled in php.ini"] = "Erreur: exec est requis mais soit il n'est pas installé, soit il a été désactivé dans php.ini";
+App::$strings["shell_exec"] = "shell_exec";
+App::$strings["Error: shell_exec is required but is either not installed or has been disabled in php.ini"] = "Erreur: shell_exec est requis mais soit il n'est pas installé, soit il a été désactivé dans php.ini";
+App::$strings["Error: libCURL PHP module required but not installed."] = "Erreur&nbsp;: le module libCURL de PHP est requis, mais pas installé.";
+App::$strings["Error: GD graphics PHP module with JPEG support required but not installed."] = "Erreur&nbsp;: le module GD de PHP avec support JPEG est requis, mais pas installé.";
+App::$strings["Error: openssl PHP module required but not installed."] = "Erreur&nbsp;: le module openssl de PHP est requis, mais pas installé.";
+App::$strings["Error: PDO database PHP module required but not installed."] = "Erreur: le module PDO de base de données PHP est requis mais n'est pas installé.";
+App::$strings["Error: mb_string PHP module required but not installed."] = "Erreur&nbsp;: le module mb_string de PHP est requis, mais pas installé.";
+App::$strings["Error: xml PHP module required for DAV but not installed."] = "Erreur&nbsp;: le module xml de PHP est requis pour le DAV, mais pas installé.";
+App::$strings["The web installer needs to be able to create a file called \".htconfig.php\" in the top folder of your web server and it is unable to do so."] = "L'installeur web a besoin de créer un fichier \".htconfig.php\" à la racine de votre serveur web, mais en est incapable.";
+App::$strings["This is most often a permission setting, as the web server may not be able to write files in your folder - even if you can."] = "C'est généralement lié à un problème de droits, à cause duquel le serveur web est interdit d'écriture dans le répertoire concerné - alors que votre propre utilisateur a le droit.";
+App::$strings["At the end of this procedure, we will give you a text to save in a file named .htconfig.php in your Red top folder."] = "Au terme de cette procédure, nous vous transmettrons un texte à sauvegarder dans un fichier nommé .htconfig.php, à la racine de votre installation de \$Projectname.";
+App::$strings["You can alternatively skip this procedure and perform a manual installation. Please see the file \"install/INSTALL.txt\" for instructions."] = "Autrement, vous pouvez contourner toute cette procédure et réaliser l'installation manuellement. Merci de consulter le fichier \"install/INSTALL.txt\" pour les instructions détaillées.";
+App::$strings[".htconfig.php is writable"] = "Le fichier .htconfig.php est accessible en écriture";
+App::$strings["This software uses the Smarty3 template engine to render its web views. Smarty3 compiles templates to PHP to speed up rendering."] = "Ce logiciel utilise Smarty3 comme moteur de modèles pour afficher ses vues Web. Smarty3 compile ses modèles en PHP pour accélérer le rendu.";
+App::$strings["In order to store these compiled templates, the web server needs to have write access to the directory %s under the top level web folder."] = "Afin de stocker ces modèles compilés, le serveur Web doit disposer d'un accès en écriture au répertoire %s selon le dossier Web racine.";
+App::$strings["Please ensure that the user that your web server runs as (e.g. www-data) has write access to this folder."] = "Merci de vous assurer que l'utilisateur sous lequel le serveur web tourne (le plus souvent, www-data) a bien l'autorisation d'écrire dans ce répertoire.";
+App::$strings["Note: as a security measure, you should give the web server write access to %s only--not the template files (.tpl) that it contains."] = "Note: Comme mesure de sécurité, assurez vous de donner les droits d'écriture au serveur web sur %s uniquement, pas sur les fichiers individuels (.tpl) qu'il contient.";
+App::$strings["%s is writable"] = "Permission d'écriture sur %s activée";
+App::$strings["This software uses the store directory to save uploaded files. The web server needs to have write access to the store directory under the top level web folder"] = "Ce logiciel utilise le répertoire de stockage pour enregistrer les fichiers téléversés. Le serveur Web doit disposer d'un accès en écriture au répertoire de stockage selon le dossier web racine.";
+App::$strings["store is writable"] = "'store' est accessible en écriture";
+App::$strings["SSL certificate cannot be validated. Fix certificate or disable https access to this site."] = "Le certificat SSL/TLS n'a pas pu être validé. Merci de le corriger, ou de désactiver l'accès https à ce site (non recommandé).";
+App::$strings["If you have https access to your website or allow connections to TCP port 443 (the https: port), you MUST use a browser-valid certificate. You MUST NOT use self-signed certificates!"] = "Si votre serveur accepte les connexions https ou s'il permet les connexions sur le port TCP 443 (le port utilisé par le protocole https), vous DEVEZ utiliser un certificat valide. Vous ne DEVEZ PAS utiliser un certificat que vous avez vous-mêmes signé&nbsp;!";
+App::$strings["This restriction is incorporated because public posts from you may for example contain references to images on your own hub."] = "Nous avons ajouté cette contrainte pour éviter que vos publications publiques ne fassent référence par exemple à des images sur votre propre hub.";
+App::$strings["If your certificate is not recognized, members of other sites (who may themselves have valid certificates) will get a warning message on their own site complaining about security issues."] = "Si votre certificat n'est pas reconnu, les membres des autres sites (qui eux peuvent avoir des certificats valides) recevront des messages d'avertissement sur leur propre site se plaignant de problèmes de sécurité.";
+App::$strings["This can cause usability issues elsewhere (not just on your own site) so we must insist on this requirement."] = "Ceci peut causer des problèmes d'ergonomie ailleurs (pas seulement sur votre site), nous devons donc insister sur ce prérequis.";
+App::$strings["Providers are available that issue free certificates which are browser-valid."] = "Il existe des autorités de certification qui vous fourniront gratuitement un certificat valide.";
+App::$strings["If you are confident that the certificate is valid and signed by a trusted authority, check to see if you have failed to install an intermediate cert. These are not normally required by browsers, but are required for server-to-server communications."] = "Si vous êtes certain que le certificat est valide et signé par une autorité de confiance, vérifiez si l'installation d'un certificat intermédiaire aurait échoué. Ceux-ci ne sont normalement pas requis par les navigateurs, mais ils sont requis pour les communications entre serveurs.";
+App::$strings["SSL certificate validation"] = "Validation du certificat SSL/TLS";
+App::$strings["Url rewrite in .htaccess is not working. Check your server configuration.Test: "] = "La réécriture d'URL définie dans le .htaccess ne fonctionne pas. Vérifiez votre configuration serveur. Test&nbsp;:";
+App::$strings["Url rewrite is working"] = "La réécriture d'URL fonctionne";
+App::$strings["The database configuration file \".htconfig.php\" could not be written. Please use the enclosed text to create a configuration file in your web server root."] = "Le fichier de configuration de la base de données - \".htconfig.php\" - ne peut être écrit. Merci de copier le texte généré dans un fichier à ce nom, à la racine de votre serveur web.";
+App::$strings["Errors encountered creating database tables."] = "Erreurs rencontrées pendant la création de tables de BDD.";
+App::$strings["<h1>What next</h1>"] = "<h1>Et maintenant</h1>";
+App::$strings["IMPORTANT: You will need to [manually] setup a scheduled task for the poller."] = "IMPORTANT&nbsp;: Vous devez créer [manuellement] une tâche planifiée pour les mises à jour du réseau.";
+App::$strings["Continue"] = "Continuer";
+App::$strings["Premium Channel Setup"] = "Configuration du canal VIP";
+App::$strings["Enable premium channel connection restrictions"] = "Activer les restrictions liées au canal VIP";
+App::$strings["Please enter your restrictions or conditions, such as paypal receipt, usage guidelines, etc."] = "Merci de saisir les restrictions et/ou conditions - reçu Paypal, transaction Bitcoin, ligne de conduite, ...";
+App::$strings["This channel may require additional steps or acknowledgement of the following conditions prior to connecting:"] = "Avant d'autoriser la mise en relation, ce canal attire votre attention sur les conditions suivantes&nbsp;:";
+App::$strings["Potential connections will then see the following text before proceeding:"] = "Les contacts potentiels verront ce qui suit avant de pouvoir continuer&nbsp;:";
+App::$strings["By continuing, I certify that I have complied with any instructions provided on this page."] = "En continuant, je certifie que je me suis conformé à toutes les instructions indiquées sur cette page.";
+App::$strings["(No specific instructions have been provided by the channel owner.)"] = "(Aucune instruction spécifique n'a été fournie par le propriétaire du canal.)";
+App::$strings["Restricted or Premium Channel"] = "Canal VIP ou restreint";
+App::$strings["Queue Statistics"] = "Statistiques de file d'attente";
+App::$strings["Total Entries"] = "Nombre d'entrées total";
+App::$strings["Priority"] = "Priorité";
+App::$strings["Destination URL"] = "URL de destination";
+App::$strings["Mark hub permanently offline"] = "Marquer le hub comme étant hors ligne de manière permanente";
+App::$strings["Empty queue for this hub"] = "Vider la file d'attente pour ce hub";
+App::$strings["Last known contact"] = "Dernier contact connu";
App::$strings["Off"] = "Inactif";
App::$strings["On"] = "Actif";
App::$strings["Lock feature %s"] = "Verrouiller fonctionnalité %s";
App::$strings["Manage Additional Features"] = "Gérer les fonctionnalités additionnelles";
-App::$strings["No server found"] = "Serveur introuvable";
-App::$strings["ID"] = "Identifiant";
-App::$strings["for channel"] = "pour le canal";
-App::$strings["on server"] = "sur le serveur";
-App::$strings["Server"] = "Serveur";
-App::$strings["By default, unfiltered HTML is allowed in embedded media. This is inherently insecure."] = "";
-App::$strings["The recommended setting is to only allow unfiltered HTML from the following sites:"] = "";
-App::$strings["https://youtube.com/<br />https://www.youtube.com/<br />https://youtu.be/<br />https://vimeo.com/<br />https://soundcloud.com/<br />"] = "";
-App::$strings["All other embedded content will be filtered, <strong>unless</strong> embedded content from that site is explicitly blocked."] = "";
-App::$strings["Security"] = "Sécurité";
-App::$strings["Block public"] = "Bloquer \"public\"";
-App::$strings["Check to block public access to all otherwise public personal pages on this site unless you are currently authenticated."] = "Sélectionner pour ne permettre l'accès aux pages personnelles \"publiques\" du site qu'aux personnes authentifiées, pas aux personnes anonymes du web.";
-App::$strings["Set \"Transport Security\" HTTP header"] = "";
-App::$strings["Set \"Content Security Policy\" HTTP header"] = "";
-App::$strings["Allow communications only from these sites"] = "N'autorisez que les communications venant de ces sites";
-App::$strings["One site per line. Leave empty to allow communication from anywhere by default"] = "Un site par ligne. Laisser vide pour autoriser les communications de tous les sites, par défaut.";
-App::$strings["Block communications from these sites"] = "Bloquer les communications de ces sites";
-App::$strings["Allow communications only from these channels"] = "N'autoriser que les communications de ces canaux";
-App::$strings["One channel (hash) per line. Leave empty to allow from any channel by default"] = "Un canal (adresse) par ligne. Laisser vide pour autoriser les communications de tous les canaux, par défaut";
-App::$strings["Block communications from these channels"] = "Bloquer les communications de ces canaux";
-App::$strings["Only allow embeds from secure (SSL) websites and links."] = "";
-App::$strings["Allow unfiltered embedded HTML content only from these domains"] = "";
-App::$strings["One site per line. By default embedded content is filtered."] = "";
-App::$strings["Block embedded HTML from these domains"] = "Bloquer le HTML embarqué à partir de ces domaines";
App::$strings["Update has been marked successful"] = "La mise à jour a été marquée comme réussie";
App::$strings["Executing %s failed. Check system logs."] = "L'éxecution de %s a échoué. Merci de vérifier les journaux du système.";
App::$strings["Update %s was successfully applied."] = "La mise à jour %s a été appliquée avec succès.";
@@ -917,13 +365,37 @@ App::$strings["No failed updates."] = "Aucune mise à jour défaillante.";
App::$strings["Failed Updates"] = "Mises à jour défaillantes";
App::$strings["Mark success (if update was manually applied)"] = "Marquer comme réussie (si la mise à jour a été réalisée manuellement)";
App::$strings["Attempt to execute this update step automatically"] = "Tenter de réaliser cette étape de mise à jour automatiquement";
-App::$strings["Queue Statistics"] = "Statistiques de file d'attente";
-App::$strings["Total Entries"] = "Nombre d'entrées total";
-App::$strings["Priority"] = "Priorité";
-App::$strings["Destination URL"] = "URL de destination";
-App::$strings["Mark hub permanently offline"] = "Marquer le hub comme étant hors ligne de manière permanente";
-App::$strings["Empty queue for this hub"] = "Vider la file d'attente pour ce hub";
-App::$strings["Last known contact"] = "Dernier contact connu";
+App::$strings["Item not found."] = "Élément introuvable";
+App::$strings["Plugin %s disabled."] = "Greffon %s désactivé.";
+App::$strings["Plugin %s enabled."] = "Greffon %s activé.";
+App::$strings["Disable"] = "Désactiver";
+App::$strings["Enable"] = "Activer";
+App::$strings["Administration"] = "Administration";
+App::$strings["Plugins"] = "Greffons";
+App::$strings["Toggle"] = "(Dés)activer";
+App::$strings["Settings"] = "Paramètres";
+App::$strings["Author: "] = "Auteur&nbsp;:";
+App::$strings["Maintainer: "] = "Maintenu par&nbsp;:";
+App::$strings["Minimum project version: "] = "Version minimum du projet&nbsp;:";
+App::$strings["Maximum project version: "] = "Version maximum du projet&nbsp;:";
+App::$strings["Minimum PHP version: "] = "Version minimum de PHP&nbsp;:";
+App::$strings["Compatible Server Roles: "] = "Rôles du serveur ";
+App::$strings["Requires: "] = "Requiert&nbsp;:";
+App::$strings["Disabled - version incompatibility"] = "Désactivé - version incompatible";
+App::$strings["Enter the public git repository URL of the plugin repo."] = "Entrer l'URL du dépôt git public pour les greffons";
+App::$strings["Plugin repo git URL"] = "URL du git pour les plugin";
+App::$strings["Custom repo name"] = "Nom du dépôt";
+App::$strings["(optional)"] = "(en option)";
+App::$strings["Download Plugin Repo"] = "Télécharger l'extension";
+App::$strings["Install new repo"] = "Installer un nouveau dépôt";
+App::$strings["Install"] = "Installer";
+App::$strings["Cancel"] = "Annuler";
+App::$strings["Manage Repos"] = "Gérer les dépôts";
+App::$strings["Installed Plugin Repositories"] = "Dépôt des extensions installées";
+App::$strings["Install a New Plugin Repository"] = "Installer un nouveau dépôt pour extensions";
+App::$strings["Update"] = "Mise à jour";
+App::$strings["Switch branch"] = "Changer de branche";
+App::$strings["Remove"] = "Retirer";
App::$strings["%s account blocked/unblocked"] = array(
0 => "%s compte bloqué/débloqué",
1 => "%s comptes bloqués/débloqués",
@@ -938,10 +410,15 @@ App::$strings["Account '%s' blocked"] = "Compte '%s' bloqué";
App::$strings["Account '%s' unblocked"] = "Compte '%s' débloqué";
App::$strings["Accounts"] = "Comptes";
App::$strings["select all"] = "tout sélectionner";
-App::$strings["Registrations waiting for confirm"] = "";
+App::$strings["Registrations waiting for confirm"] = "Inscriptions en attente d'approbation";
App::$strings["Request date"] = "Date de la demande";
+App::$strings["Email"] = "Courriel";
App::$strings["No registrations."] = "Pas d'inscriptions.";
+App::$strings["Approve"] = "Approuver";
App::$strings["Deny"] = "Refuser";
+App::$strings["Block"] = "Bloquer";
+App::$strings["Unblock"] = "Débloquer";
+App::$strings["ID"] = "Identifiant";
App::$strings["All Channels"] = "Tous les canaux";
App::$strings["Register date"] = "Date d'inscription";
App::$strings["Last login"] = "Dernière connexion";
@@ -949,6 +426,13 @@ App::$strings["Expires"] = "Expire le";
App::$strings["Service Class"] = "Classe de service";
App::$strings["Selected accounts will be deleted!\\n\\nEverything these accounts had posted on this site will be permanently deleted!\\n\\nAre you sure?"] = "Les comptes sélectionnés seront supprimés&nbsp;!\\n\\nTout ce que ces utilisateurs ont publié sur ce site sera détruit de manière définitive&nbsp;!\\n\\nÊtes-vous sûr&nbsp;?";
App::$strings["The account {0} will be deleted!\\n\\nEverything this account has posted on this site will be permanently deleted!\\n\\nAre you sure?"] = "Le compte {0} sera supprimé&nbsp;!\\n\\nTout ce que cet utilisateur a publié sur ce site sera détruit de manière définitive&nbsp;!\\n\\nÊtes-vous sûr&nbsp;?";
+App::$strings["Log settings updated."] = "Paramètres du journal mis à jour.";
+App::$strings["Logs"] = "Journaux";
+App::$strings["Clear"] = "Vider";
+App::$strings["Debugging"] = "Débogage";
+App::$strings["Log file"] = "Fichier du journal";
+App::$strings["Must be writable by web server. Relative to your top-level webserver directory."] = "Doit être permettre d'écrire par le serveur web. En relation avec le répertoire de votre site.";
+App::$strings["Log level"] = "Niveau de journalisation";
App::$strings["%s channel censored/uncensored"] = array(
0 => "%s canal censuré/dé-censuré",
1 => "%s canaux censurés/dé-censurés",
@@ -976,44 +460,96 @@ App::$strings["Channel"] = "Canal";
App::$strings["UID"] = "UID";
App::$strings["Selected channels will be deleted!\\n\\nEverything that was posted in these channels on this site will be permanently deleted!\\n\\nAre you sure?"] = "Les canaux sélectionnés seront supprimés&nbsp;!\\n\\nTout ce qui a été publié dans ces canaux sur ce site sera définitivement supprimé&nbsp;!\\n\\nÊtes-vous sûr&nbsp;?";
App::$strings["The channel {0} will be deleted!\\n\\nEverything that was posted in this channel on this site will be permanently deleted!\\n\\nAre you sure?"] = "Le canal {0} sera supprimé&nbsp;!\\n\\nTout ce qui a été publié sur ce canal sera définitivement supprimé&nbsp;!\\n\\nÊtes-vous sûr(e)&nbsp;?";
-App::$strings["Plugin %s disabled."] = "Greffon %s désactivé.";
-App::$strings["Plugin %s enabled."] = "Greffon %s activé.";
-App::$strings["Disable"] = "Désactiver";
-App::$strings["Enable"] = "Activer";
-App::$strings["Plugins"] = "Greffons";
-App::$strings["Toggle"] = "(Dés)activer";
-App::$strings["Settings"] = "Paramètres";
-App::$strings["Author: "] = "Auteur&nbsp;:";
-App::$strings["Maintainer: "] = "Maintenu par&nbsp;:";
-App::$strings["Minimum project version: "] = "Version minimum du projet&nbsp;:";
-App::$strings["Maximum project version: "] = "Version maximum du projet&nbsp;:";
-App::$strings["Minimum PHP version: "] = "Version minimum de PHP&nbsp;:";
-App::$strings["Requires: "] = "Requiert&nbsp;:";
-App::$strings["Disabled - version incompatibility"] = "Désactivé - version incompatible";
-App::$strings["Enter the public git repository URL of the plugin repo."] = "";
-App::$strings["Plugin repo git URL"] = "";
-App::$strings["Custom repo name"] = "";
-App::$strings["(optional)"] = "";
-App::$strings["Download Plugin Repo"] = "";
-App::$strings["Install new repo"] = "";
-App::$strings["Install"] = "Installer";
-App::$strings["Manage Repos"] = "";
-App::$strings["Installed Plugin Repositories"] = "";
-App::$strings["Install a New Plugin Repository"] = "";
-App::$strings["Update"] = "Mise à jour";
-App::$strings["Switch branch"] = "";
+App::$strings["Theme settings updated."] = "Paramètres du thème mis à jour.";
App::$strings["No themes found."] = "Aucun thème trouvé.";
App::$strings["Screenshot"] = "Capture d'écran";
App::$strings["Themes"] = "Thèmes";
App::$strings["[Experimental]"] = "[Expérimental]";
App::$strings["[Unsupported]"] = "[Non maintenu]";
-App::$strings["Log settings updated."] = "Paramètres du journal mis à jour.";
-App::$strings["Logs"] = "Journaux";
-App::$strings["Clear"] = "Vider";
-App::$strings["Debugging"] = "Débogage";
-App::$strings["Log file"] = "Fichier du journal";
-App::$strings["Must be writable by web server. Relative to your top-level webserver directory."] = "";
-App::$strings["Log level"] = "Niveau de journalisation";
+App::$strings["Site settings updated."] = "Paramètres du site sauvegardés.";
+App::$strings["Default"] = "Défaut";
+App::$strings["%s - (Incompatible)"] = "";
+App::$strings["mobile"] = "mobile";
+App::$strings["experimental"] = "expérimental";
+App::$strings["unsupported"] = "non maintenu";
+App::$strings["Yes - with approval"] = "Oui - avec approbation";
+App::$strings["My site is not a public server"] = "Mon site n'est pas un serveur public";
+App::$strings["My site has paid access only"] = "Mon site est à accès payant uniquement";
+App::$strings["My site has free access only"] = "Mon site est gratuit uniquement";
+App::$strings["My site offers free accounts with optional paid upgrades"] = "Mon site offre des comptes gratuits avec des améliorations payantes facultatives";
+App::$strings["Beginner/Basic"] = "Pour débutant/ de base";
+App::$strings["Novice - not skilled but willing to learn"] = "Novice - pas qualifiés, mais prêt à apprendre";
+App::$strings["Intermediate - somewhat comfortable"] = "Intermédiaire - assez confortable";
+App::$strings["Advanced - very comfortable"] = "Niveau avancé - trés confortable";
+App::$strings["Expert - I can write computer code"] = "Niveau expert - Je peux programmer";
+App::$strings["Wizard - I probably know more than you do"] = "Crack - J'en sais probablement plus que beaucoup";
+App::$strings["Site"] = "Site";
+App::$strings["Registration"] = "Inscription";
+App::$strings["File upload"] = "Envoi de fichier";
+App::$strings["Policies"] = "Stratégies";
+App::$strings["Advanced"] = "Avancé";
+App::$strings["Site name"] = "Nom du site";
+App::$strings["Site default technical skill level"] = "Niveau technique par défaut pour le site";
+App::$strings["Used to provide a member experience matched to technical comfort level"] = "Utilisé pour fournir une expérience utilisateur correspondant au niveau de confort technique";
+App::$strings["Lock the technical skill level setting"] = "Bloque le niveau technique du paramétrage";
+App::$strings["Members can set their own technical comfort level by default"] = "Les utilisateurs peuvent paramétrer leur propre niveau technique.";
+App::$strings["Banner/Logo"] = "Bannière/logo";
+App::$strings["Administrator Information"] = "Informations de l'administrateur";
+App::$strings["Contact information for site administrators. Displayed on siteinfo page. BBCode can be used here"] = "Coordonnées de l'administrateur du site. Affichées sur la page 'siteinfo'. Vous pouvez utiliser du BBCode ici";
+App::$strings["Site Information"] = "Site information";
+App::$strings["Publicly visible description of this site. Displayed on siteinfo page. BBCode can be used here"] = "Description du site visible publiquement. Affiché sur la page d'information du site. BBCode peut être utilisé ici.";
+App::$strings["System language"] = "Langue du système";
+App::$strings["System theme"] = "Thème du système";
+App::$strings["Default system theme - may be over-ridden by user profiles - <a href='#' id='cnftheme'>change theme settings</a>"] = "Thème par défaut - il peut être changé pour chaque profil utilisateur - <a href='#' id='cnftheme'>modifier le thème</a>";
+App::$strings["Mobile system theme"] = "Thème par défaut pour les mobiles";
+App::$strings["Theme for mobile devices"] = "Thème pour les mobiles";
+App::$strings["Allow Feeds as Connections"] = "Autoriser les Flux (RSS) comme contacts";
+App::$strings["(Heavy system resource usage)"] = "(Impact important sur les ressources)";
+App::$strings["Maximum image size"] = "Taille maximale des images";
+App::$strings["Maximum size in bytes of uploaded images. Default is 0, which means no limits."] = "Taille maximum, en octets, des images envoyées. Par défaut 0, soit sans limite.";
+App::$strings["Does this site allow new member registration?"] = "Est-ce que l'enregistrement de nouveaux membres est autorisé sur ce site&nbsp;?";
+App::$strings["Invitation only"] = "Sur invitation seulement";
+App::$strings["Only allow new member registrations with an invitation code. Above register policy must be set to Yes."] = "N'autoriser que les nouvelles inscriptions avec code d'invitation. La stratégie d'inscription ci-dessus doit être mise sur \"Oui\".";
+App::$strings["Which best describes the types of account offered by this hub?"] = "Quelle est la meilleure description des types de comptes proposés sur ce hub&nbsp;?";
+App::$strings["Register text"] = "Texte d'inscription";
+App::$strings["Will be displayed prominently on the registration page."] = "Sera affiché de manière bien visible sur le formulaire d'inscription.";
+App::$strings["Site homepage to show visitors (default: login box)"] = "Page d'accueil du site à montrer aux visiteurs (par défaut&nbsp;: boîte de dialogue de connexion)";
+App::$strings["example: 'public' to show public stream, 'page/sys/home' to show a system webpage called 'home' or 'include:home.html' to include a file."] = "exemple&nbsp;:'public' pour montrer le flux public, 'page/sys/home' pour montrer une page système appelée 'home' ou 'include:home.html' pour inclure un fichier.";
+App::$strings["Preserve site homepage URL"] = "Préserver l'adresse d'accueil du site";
+App::$strings["Present the site homepage in a frame at the original location instead of redirecting"] = "Présenter la page d'accueil du site dans un cadre à l'adresse d'origine, plutôt que de rediriger";
+App::$strings["Accounts abandoned after x days"] = "Les comptes sont abandonnés après x jours";
+App::$strings["Will not waste system resources polling external sites for abandonded accounts. Enter 0 for no time limit."] = "Eviter de gaspiller les ressources du système en interrogeant des hubs distants pour des canaux abandonnés. Mettez 0 pour ne pas avoir de limite de temps.";
+App::$strings["Allowed friend domains"] = "Domaines amicaux autorisés";
+App::$strings["Comma separated list of domains which are allowed to establish friendships with this site. Wildcards are accepted. Empty to allow any domains"] = "Liste de noms de domaines séparés par des virgules pour lesquels ce site acceptera les demandes d'amitié. Les caractères génériques (*) sont acceptés. Laissez vide pour accepter tous les domaines.";
+App::$strings["Verify Email Addresses"] = "Demander vérification des adresses de courriel";
+App::$strings["Check to verify email addresses used in account registration (recommended)."] = "Cocher pour que les adresses utilisées à l'inscription soient vérifiées (recommandé).";
+App::$strings["Force publish"] = "Publicité forcée";
+App::$strings["Check to force all profiles on this site to be listed in the site directory."] = "Cocher pour forcer la publication de tous les profils du site dans l'annuaire.";
+App::$strings["Import Public Streams"] = "Flux publics importés";
+App::$strings["Import and allow access to public content pulled from other sites. Warning: this content is unmoderated."] = "Importer du contenu public à partir d'autres sites et autoriser l'accès à ce contenu. Attention&nbsp;: ce contenu n'est pas modéré.";
+App::$strings["Login on Homepage"] = "Connexion sur la page d'accueil";
+App::$strings["Present a login box to visitors on the home page if no other content has been configured."] = "Présenter une boîte de dialogue de connexion aux visiteurs sur la page d'accueil si aucun autre contenu n'a été configuré.";
+App::$strings["Enable context help"] = "Permettre l'aide contextuelle";
+App::$strings["Display contextual help for the current page when the help button is pressed."] = "Afficher l'aide contextuel en cliquant sur le bouton aide.";
+App::$strings["Reply-to email address for system generated email."] = "";
+App::$strings["Sender (From) email address for system generated email."] = "";
+App::$strings["Name of email sender for system generated email."] = "";
+App::$strings["Directory Server URL"] = "URL du serveur d'annuaire";
+App::$strings["Default directory server"] = "Serveur d'annuaire par défaut";
+App::$strings["Proxy user"] = "Utilisateur du proxy";
+App::$strings["Proxy URL"] = "URL du proxy";
+App::$strings["Network timeout"] = "Délai maximal du réseau";
+App::$strings["Value is in seconds. Set to 0 for unlimited (not recommended)."] = "En secondes. Mettre à 0 pour ne pas avoir de délai maximal (non recommandé).";
+App::$strings["Delivery interval"] = "Intervalle de distribution";
+App::$strings["Delay background delivery processes by this many seconds to reduce system load. Recommend: 4-5 for shared hosts, 2-3 for virtual private servers. 0-1 for large dedicated servers."] = "Temporise le processus de distribution de tant de secondes pour réduire la charge sur le système. Valeurs recommandées&nbsp;: 4-5 pour les serveurs mutualisés, 2-3 pour les VPS. 0-1 pour les gros serveurs dédiés.";
+App::$strings["Deliveries per process"] = "Distributions par processus";
+App::$strings["Number of deliveries to attempt in a single operating system process. Adjust if necessary to tune system performance. Recommend: 1-5."] = "Nombre de distributions à tenter au sein d'un seul processus système. Ajuster si nécessaire pour affiner la performance du système. Recommandé&nbsp;:1-5.";
+App::$strings["Poll interval"] = "Intervalle de scrutation";
+App::$strings["Delay background polling processes by this many seconds to reduce system load. If 0, use delivery interval."] = "Temporise le processus de scrutation en tâche de fond de tant de secondes, pour réduire la charge. Si 0, utilise l'intervalle de distribution.";
+App::$strings["Maximum Load Average"] = "Charge maximale moyenne";
+App::$strings["Maximum system load before delivery and poll processes are deferred - default 50."] = "Charge système maximale au-delà de laquelle distribution et scrutation sont reportées - par défaut 50.";
+App::$strings["Expiration period in days for imported (grid/network) content"] = "Délai d'expiration pour le contenu importé (réseau)";
+App::$strings["0 for no expiration of imported content"] = "0 pour ne pas expirer le contenu importé";
App::$strings["New Profile Field"] = "Nouveau champ de profil";
App::$strings["Field nickname"] = "Nom court du champ";
App::$strings["System name of field"] = "Nom système du champ";
@@ -1022,6 +558,7 @@ App::$strings["Field Name"] = "Nom du champ";
App::$strings["Label on profile pages"] = "Étiquette sur les pages de profil";
App::$strings["Help text"] = "Aide à la saisie";
App::$strings["Additional info (optional)"] = "Informations additionnelles (facultatif)";
+App::$strings["Save"] = "Enregistrer";
App::$strings["Field definition not found"] = "Définition du champ introuvable";
App::$strings["Edit Profile Field"] = "Modifier le champ de profil";
App::$strings["Profile Fields"] = "Champs de profil";
@@ -1031,130 +568,51 @@ App::$strings["(In addition to basic fields)"] = "(en plus des champs de base)";
App::$strings["All available fields"] = "Tous les champs disponibles";
App::$strings["Custom Fields"] = "Champs personnalisés";
App::$strings["Create Custom Field"] = "Créer un champ personnalisé";
-App::$strings["App installed."] = "Application installée.";
-App::$strings["Malformed app."] = "Erreur de l'application - Malformée.";
-App::$strings["Embed code"] = "Imbriquer le code";
-App::$strings["Edit App"] = "Modifier l'application";
-App::$strings["Create App"] = "Créer une application";
-App::$strings["Name of app"] = "Nom de l'application";
-App::$strings["Location (URL) of app"] = "Emplacement (URL) de l'application";
-App::$strings["Photo icon URL"] = "URL de l'icône à utiliser pour cette photo";
-App::$strings["80 x 80 pixels - optional"] = "80 x 80 pixels - facultatif";
-App::$strings["Categories (optional, comma separated list)"] = "";
-App::$strings["Version ID"] = "Identifiant de version";
-App::$strings["Price of app"] = "Prix de l'application";
-App::$strings["Location (URL) to purchase app"] = "Emplacement (URL) pour l'achat de l'application";
-App::$strings["Select a bookmark folder"] = "Choisir un dossier de favoris";
-App::$strings["Save Bookmark"] = "Enregistrer le favori";
-App::$strings["URL of bookmark"] = "URL du favori";
-App::$strings["Or enter new bookmark folder name"] = "Ou entrez un nouveau nom de dossier de favoris";
-App::$strings["Maximum daily site registrations exceeded. Please try again tomorrow."] = "Nombre d'inscriptions quotidiennes dépassé. Merci d'essayer à nouveau demain.";
-App::$strings["Please indicate acceptance of the Terms of Service. Registration failed."] = "Merci d'indiquer votre adhésion aux conditions de service. L'inscription a échoué.";
-App::$strings["Passwords do not match."] = "Les mots de passe ne concordent pas.";
-App::$strings["Registration successful. Please check your email for validation instructions."] = "Inscription réussie. Merci de vérifier vos courriels pour valider votre compte.";
-App::$strings["Your registration is pending approval by the site owner."] = "Votre inscription est en attente d'approbation par l'administrateur.";
-App::$strings["Your registration can not be processed."] = "Votre inscription ne peut être traîtée.";
-App::$strings["Registration on this hub is disabled."] = "La création de nouveaux comptes est désactivée pour ce site.";
-App::$strings["Registration on this hub is by approval only."] = "La création de compte sur ce site est soumise à approbation.";
-App::$strings["<a href=\"pubsites\">Register at another affiliated hub.</a>"] = "<a href=\"pubsites\">S'enregistrer sur un autre site du réseau.</a>";
-App::$strings["This site has exceeded the number of allowed daily account registrations. Please try again tomorrow."] = "Ce site a dépassé le nombre de création de comptes autorisé chaque jour. Merci d'essayer à nouveau demain.";
-App::$strings["Terms of Service"] = "Conditions de service";
-App::$strings["I accept the %s for this website"] = "J'accepte les %s de ce site";
-App::$strings["I am over 13 years of age and accept the %s for this website"] = "J'ai plus de 13 ans et j'accepte les %s de ce site";
-App::$strings["Your email address"] = "Votre adresse de courriel";
-App::$strings["Choose a password"] = "Choisissez un mot de passe";
-App::$strings["Please re-enter your password"] = "Merci de saisir à nouveau votre mot de passe";
-App::$strings["Please enter your invitation code"] = "Merci de saisir votre code d'invitation";
-App::$strings["no"] = "non";
-App::$strings["yes"] = "oui";
-App::$strings["Membership on this site is by invitation only."] = "L'inscription à ce site se fait uniquement sur invitation.";
-App::$strings["Register"] = "S'inscrire";
-App::$strings["Proceed to create your first channel"] = "Continuer pour créer votre premier canal";
-App::$strings["Please login."] = "Merci de vous connecter.";
-App::$strings["Account removals are not allowed within 48 hours of changing the account password."] = "Il est impossible de supprimer un compte dans les 48 heures après avoir changé le mot de passe du compte.";
-App::$strings["Remove This Account"] = "Supprimer ce compte";
-App::$strings["WARNING: "] = "AVERTISSEMENT&nbsp;:";
-App::$strings["This account and all its channels will be completely removed from the network. "] = "Ce compte et tous ses canaux seront entièrement supprimés du réseau.";
-App::$strings["This action is permanent and can not be undone!"] = "Cette action est permanente et irréversible&nbsp;!";
-App::$strings["Please enter your password for verification:"] = "Merci de saisir votre mot de passe pour vérification&nbsp;:";
-App::$strings["Remove this account, all its channels and all its channel clones from the network"] = "Supprimer du réseau ce compte, tous ses canaux et tous les clones de ses canaux.";
-App::$strings["By default only the instances of the channels located on this hub will be removed from the network"] = "Par défaut, seules les instances des canaux situés sur ce hub seront supprimées du réseau";
-App::$strings["Remove Account"] = "Supprimer le compte";
-App::$strings["Channel removals are not allowed within 48 hours of changing the account password."] = "Il est impossible de supprimer un canal moins de 48 heures après avoir changé le mot de passe d'un compte.";
-App::$strings["Remove This Channel"] = "Supprimer ce canal";
-App::$strings["This channel will be completely removed from the network. "] = "Ce canal sera complètement supprimé du réseau.";
-App::$strings["Remove this channel and all its clones from the network"] = "Supprimer ce canal ainsi que tous ses clones sur le réseau";
-App::$strings["By default only the instance of the channel located on this hub will be removed from the network"] = "Par défaut, seule l'instance du canal présente sur ce hub sera supprimée du réseau";
-App::$strings["Remove Channel"] = "Supprimer le canal";
-App::$strings["We encountered a problem while logging in with the OpenID you provided. Please check the correct spelling of the ID."] = "Nous avons rencontré un problème avec l'OpenID que vous nous avez fourni. Merci de vérifier que l'ID est correctement saisi.";
-App::$strings["The error message was:"] = "Le message d'erreur était&nbsp;:";
-App::$strings["Authentication failed."] = "Échec de l'authentification.";
-App::$strings["Remote Authentication"] = "Authentification distante";
-App::$strings["Enter your channel address (e.g. channel@example.com)"] = "Entrez l'adresse de votre canal (par ex. moncanal@monsite.com)";
-App::$strings["Authenticate"] = "Authentifier";
-App::$strings["Items tagged with: %s"] = "Eléments étiquetés avec&nbsp;: %s";
-App::$strings["Search results for: %s"] = "Résultats de recherche pour&nbsp;: %s";
-App::$strings["No service class restrictions found."] = "Aucune restriction de classe de service trouvée.";
-App::$strings["Name is required"] = "Le nom est requis";
-App::$strings["Key and Secret are required"] = "Clef et secret sont requis";
-App::$strings["Not valid email."] = "Adresse de courriel non valide.";
-App::$strings["Protected email address. Cannot change to that email."] = "Adresse de courriel protégée. Impossible de l'utiliser.";
-App::$strings["System failure storing new email. Please try again."] = "Défaillance système lors du stockage de la nouvelle adresse de courriel. Merci d'essayer à nouveau.";
-App::$strings["Password verification failed."] = "La vérification du mot de passe a échoué.";
-App::$strings["Passwords do not match. Password unchanged."] = "Les deux saisies du mot de passe ne correspondent pas. Il n'a donc pas été changé.";
-App::$strings["Empty passwords are not allowed. Password unchanged."] = "Le mot de passe ne peut pas être vide. Il n'a donc pas été changé.";
-App::$strings["Password changed."] = "Le mot de passe a été changé.";
-App::$strings["Password update failed. Please try again."] = "La mise à jour du mot de passe a échoué. Merci d'essayer à nouveau.";
+App::$strings["Password changed for account %d."] = "Le mot de passe a été modifié pour le compte %d.";
+App::$strings["Account settings updated."] = "Paramétrage du compte mis à jour";
+App::$strings["Account not found."] = "Compte introuvable";
+App::$strings["Account Edit"] = "Modifier votre compte";
+App::$strings["New Password"] = "Nouveau mot de passe";
+App::$strings["New Password again"] = "Nouveau mot de passe (encore)";
+App::$strings["Technical skill level"] = "Niveau technique";
+App::$strings["Account language (for emails)"] = "Langue de votre compte (pour email)";
+App::$strings["Service class"] = "Classe de service";
+App::$strings["By default, unfiltered HTML is allowed in embedded media. This is inherently insecure."] = "Par défaut le code HTML est autorisé pour les média par exemple les vidéos embarquées. Cependant cela peut poser un faille de sécurité.";
+App::$strings["The recommended setting is to only allow unfiltered HTML from the following sites:"] = "Ce paramétrage autorisant le HTML pour les sites suivants.";
+App::$strings["https://youtube.com/<br />https://www.youtube.com/<br />https://youtu.be/<br />https://vimeo.com/<br />https://soundcloud.com/<br />"] = "https://youtube.com/<br />https://www.youtube.com/<br />https://youtu.be/<br />https://vimeo.com/<br />https://soundcloud.com/<br />";
+App::$strings["All other embedded content will be filtered, <strong>unless</strong> embedded content from that site is explicitly blocked."] = "Les contenus html seront filtrés <strong>sauf</strong> ceux des sites explicitement bloqués.";
+App::$strings["Security"] = "Sécurité";
+App::$strings["Block public"] = "Bloquer \"public\"";
+App::$strings["Check to block public access to all otherwise public personal pages on this site unless you are currently authenticated."] = "Sélectionner pour ne permettre l'accès aux pages personnelles \"publiques\" du site qu'aux personnes authentifiées, pas aux personnes anonymes du web.";
+App::$strings["Set \"Transport Security\" HTTP header"] = "Paramétrer \"Transport Security\" pour l'entête HTTP";
+App::$strings["Set \"Content Security Policy\" HTTP header"] = "Paramétrer \"Content Security Policy\" pour l'entête HTTP";
+App::$strings["Allowed email domains"] = "Domaines de courriels autorisés";
+App::$strings["Comma separated list of domains which are allowed in email addresses for registrations to this site. Wildcards are accepted. Empty to allow any domains"] = "Liste de noms de domaines séparés par des virgules dont les adresses de courriel seront autorisées lors de l'inscription à ce site. Les caractères génériques (*) sont acceptés. Laissez vide pour accepter tous les domaines.";
+App::$strings["Not allowed email domains"] = "Domaines de courriel non autorisés";
+App::$strings["Comma separated list of domains which are not allowed in email addresses for registrations to this site. Wildcards are accepted. Empty to allow any domains, unless allowed domains have been defined."] = "Liste de noms de domaines - séparés par des virgules - dont les adresses de courriel ne seront pas autorisées lors de l'inscription à ce site. Les caractères génériques (*) sont acceptés. Laissez vide pour accepter tous les domaines, sauf si des domaines autorisés ont été définis.";
+App::$strings["Allow communications only from these sites"] = "N'autorisez que les communications venant de ces sites";
+App::$strings["One site per line. Leave empty to allow communication from anywhere by default"] = "Un site par ligne. Laisser vide pour autoriser les communications de tous les sites, par défaut.";
+App::$strings["Block communications from these sites"] = "Bloquer les communications de ces sites";
+App::$strings["Allow communications only from these channels"] = "N'autoriser que les communications de ces canaux";
+App::$strings["One channel (hash) per line. Leave empty to allow from any channel by default"] = "Un canal (adresse) par ligne. Laisser vide pour autoriser les communications de tous les canaux, par défaut";
+App::$strings["Block communications from these channels"] = "Bloquer les communications de ces canaux";
+App::$strings["Only allow embeds from secure (SSL) websites and links."] = "Seuls les sites et liens sécurisés sont autorisé pour intégrer du code HTML";
+App::$strings["Allow unfiltered embedded HTML content only from these domains"] = "Autoriser le contenu HTML embarqué uniquement à partir de ces domaines";
+App::$strings["One site per line. By default embedded content is filtered."] = "Un site par ligne. Par défaut le contenu embarqué est filtré.";
+App::$strings["Block embedded HTML from these domains"] = "Bloquer le HTML embarqué à partir de ces domaines";
+App::$strings["Remote privacy information not available."] = "Les informations distantes de confidentialité ne sont pas disponibles.";
+App::$strings["Visible to:"] = "Visible par&nbsp;:";
+App::$strings["__ctx:acl__ Profile"] = "";
+App::$strings["Permission category saved."] = "Catégorie d'autorisation enregistrée.";
+App::$strings["Use this form to create permission rules for various classes of people or connections."] = "Utilisez ce formulaire pour créer des règles d'accès pour différentes catégories de personnes ou de contacts.";
+App::$strings["Permission Categories"] = "Catégories d'autorisation";
+App::$strings["Permission Name"] = "Nom de l'autorisation";
+App::$strings["My Settings"] = "Mes paramètres";
+App::$strings["inherited"] = "héritée";
+App::$strings["Individual Permissions"] = "Permissions individuelles";
+App::$strings["Some permissions may be inherited from your channel's <a href=\"settings\"><strong>privacy settings</strong></a>, which have higher priority than individual settings. You can <strong>not</strong> change those settings here."] = "Certaines permissions peuvent être héritées de vos <a href=\"settings\">paramètres de confidentialité</a> de canal, lesquels sont prioritaires sur les réglages individuels. Vous pouvez modifier ces permissions ici mais cela n'aura aucun effet à moins de changer les paramètres hérités.";
+App::$strings["Friends"] = "Amis";
App::$strings["Settings updated."] = "Paramètres mis à jour.";
-App::$strings["Add application"] = "Ajouter une application";
-App::$strings["Name of application"] = "Nom de l'application";
-App::$strings["Consumer Key"] = "Clef client";
-App::$strings["Automatically generated - change if desired. Max length 20"] = "Généré automatiquement - à changer si besoin. Longueur maximale 20 caractères.";
-App::$strings["Consumer Secret"] = "Secret client";
-App::$strings["Redirect"] = "Redirection";
-App::$strings["Redirect URI - leave blank unless your application specifically requires this"] = "URI de redirection - laissez vide, sauf si votre application le requiert spécifiquement";
-App::$strings["Icon url"] = "URL de l'icône";
-App::$strings["Optional"] = "Facultatif";
-App::$strings["Application not found."] = "Application introuvable.";
-App::$strings["Connected Apps"] = "Applications connectées";
-App::$strings["Client key starts with"] = "La clef partagée commence par";
-App::$strings["No name"] = "Sans nom";
-App::$strings["Remove authorization"] = "Révoquer l'autorisation";
-App::$strings["No feature settings configured"] = "Aucun paramètre de fonctionnalité configuré";
-App::$strings["Feature/Addon Settings"] = "Paramètres des extensions/greffons";
-App::$strings["Account Settings"] = "Paramètres du compte";
-App::$strings["Current Password"] = "Mot de passe actuel";
-App::$strings["Enter New Password"] = "Entrez votre nouveau mot de passe";
-App::$strings["Confirm New Password"] = "Confirmez le nouveau mot de passe";
-App::$strings["Leave password fields blank unless changing"] = "Laissez les mots de passe vides si vous ne voulez pas les modifier";
-App::$strings["Email Address:"] = "Adresse de courriel&nbsp;:";
-App::$strings["Remove this account including all its channels"] = "Supprimer ce compte et tous ses canaux";
-App::$strings["Additional Features"] = "Fonctionnalités additionnelles";
-App::$strings["Connector Settings"] = "Paramètres du connecteur";
-App::$strings["No special theme for mobile devices"] = "Pas de thème spécifique aux mobiles";
-App::$strings["%s - (Experimental)"] = "%s - (Expérimental)";
-App::$strings["Display Settings"] = "Afficher les paramètres";
-App::$strings["Theme Settings"] = "Paramètres du thème";
-App::$strings["Custom Theme Settings"] = "Paramètres personnels du thème";
-App::$strings["Content Settings"] = "Paramètres liés au contenu";
-App::$strings["Display Theme:"] = "Afficher le thème&nbsp;:";
-App::$strings["Mobile Theme:"] = "Thème mobile&nbsp;:";
-App::$strings["Preload images before rendering the page"] = "Pré-charger les images avant d'afficher la page";
-App::$strings["The subjective page load time will be longer but the page will be ready when displayed"] = "Le temps de charge perçu de la page sera plus long mais la page sera complète quand elle s'affichera";
-App::$strings["Enable user zoom on mobile devices"] = "Permettre à l'utilisateur d'un mobile d'agrandir le contenu";
-App::$strings["Update browser every xx seconds"] = "Mettre à jour le navigateur toutes les xx secondes";
-App::$strings["Minimum of 10 seconds, no maximum"] = "Minimum 10 secondes, pas de maximum";
-App::$strings["Maximum number of conversations to load at any time:"] = "Nombre maximal de conversations pouvant être chargées en même temps&nbsp;:";
-App::$strings["Maximum of 100 items"] = "100 éléments au maximum";
-App::$strings["Show emoticons (smilies) as images"] = "Remplacer les émoticônes (smileys) par des images";
-App::$strings["Link post titles to source"] = "Lier les titres des publications à leur source";
-App::$strings["System Page Layout Editor - (advanced)"] = "Editeur de mise en page des pages systèmes - (avancé)";
-App::$strings["Use blog/list mode on channel page"] = "Utiliser le mode blog/liste sur la page du canal";
-App::$strings["(comments displayed separately)"] = "(commentaires affichés séparément)";
-App::$strings["Use blog/list mode on grid page"] = "Utiliser le mode blog/liste sur la page du réseau";
-App::$strings["Channel page max height of content (in pixels)"] = "Hauteur maximale du contenu pour la page du canal (en pixels)";
-App::$strings["click to expand content exceeding this height"] = "cliquer pour dérouler le contenu dépassant cette limite";
-App::$strings["Grid page max height of content (in pixels)"] = "Hauteur maximale du contenu sur la page du réseau (en pixels)";
App::$strings["Nobody except yourself"] = "Personne sauf vous";
App::$strings["Only those you specifically allow"] = "Seulement ceux que vous autorisez spécifiquement";
App::$strings["Approved connections"] = "Contacts approuvés";
@@ -1165,10 +623,13 @@ App::$strings["Anybody authenticated"] = "Tous les utilisateurs authentifiés";
App::$strings["Anybody on the internet"] = "Tous les utilisateurs d'Internet";
App::$strings["Publish your default profile in the network directory"] = "Publier votre profil par défaut dans l'annuaire du réseau";
App::$strings["Allow us to suggest you as a potential friend to new members?"] = "Nous autoriser à vous suggérer comme ami(e) potentiel(le) aux nouveaux membres?";
+App::$strings["or"] = "ou";
App::$strings["Your channel address is"] = "L'adresse de votre canal est";
+App::$strings["Your files/photos are accessible via WebDAV at"] = "Vos fichiers/photos sont accessibles via WebDAV à";
App::$strings["Channel Settings"] = "Paramètres du canal";
App::$strings["Basic Settings"] = "Paramètres standard";
App::$strings["Full Name:"] = "Nom complet&nbsp;:";
+App::$strings["Email Address:"] = "Adresse de courriel&nbsp;:";
App::$strings["Your Timezone:"] = "Votre fureau horaire&nbsp;:";
App::$strings["Default Post Location:"] = "Emplacement de publication par défaut&nbsp;:";
App::$strings["Geographical location to display on your posts"] = "Emplacement géographique à afficher sur vos publications";
@@ -1186,17 +647,18 @@ App::$strings["Private - <em>default private, never open or public</em>"] = "Pri
App::$strings["Blocked - <em>default blocked to/from everybody</em>"] = "Bloqué - <em>par défaut, bloqué de/vers tout le monde</em>";
App::$strings["Allow others to tag your posts"] = "Autoriser les autres à \"étiqueter\" vos publications";
App::$strings["Often used by the community to retro-actively flag inappropriate content"] = "Souvent utilisé par la communauté pour identifier un contenu inapproprié a posteriori ";
-App::$strings["Advanced Privacy Settings"] = "Paramètres de confidentialité avancés";
+App::$strings["Channel Permission Limits"] = "Limites des permissions du canal";
App::$strings["Expire other channel content after this many days"] = "Faire expirer le contenu des autres canaux après n jours";
-App::$strings["0 or blank to use the website limit."] = "";
-App::$strings["This website expires after %d days."] = "";
-App::$strings["This website does not expire imported content."] = "";
-App::$strings["The website limit takes precedence if lower than your limit."] = "";
+App::$strings["0 or blank to use the website limit."] = "0 ou vide pour utiliser la limite du site web";
+App::$strings["This website expires after %d days."] = "Ce site web expirera après %d jours.";
+App::$strings["This website does not expire imported content."] = "Ce site web ne périme pas le contenu importé.";
+App::$strings["The website limit takes precedence if lower than your limit."] = "La limite du site Web a priorité si elle est inférieure à votre limite.";
App::$strings["Maximum Friend Requests/Day:"] = "Nombre maximum de demandes de contact par jour&nbsp;:";
App::$strings["May reduce spam activity"] = "Contribue à réduire l'impact des indésirables";
-App::$strings["Default Post and Publish Permissions"] = "";
-App::$strings["Use my default audience setting for the type of object published"] = "";
+App::$strings["Default Access Control List (ACL)"] = "Default Access Control List (ACL)";
+App::$strings["Use my default audience setting for the type of object published"] = "Utiliser mon paramètre de publication par défaut pour le type d'objet publié";
App::$strings["Channel permissions category:"] = "Catégorie de permissions du canal&nbsp;:";
+App::$strings["Default Permissions Group"] = "";
App::$strings["Maximum private messages per day from unknown people:"] = "Nombre maximum de messages privés émanant d'inconnus, par jour&nbsp;:";
App::$strings["Useful to reduce spamming"] = "Utile pour réduire les indésirables";
App::$strings["Notification Settings"] = "Paramètres de notification";
@@ -1213,6 +675,7 @@ App::$strings["You receive a private message"] = "Vous recevez un message privé
App::$strings["You receive a friend suggestion"] = "Vous recevez une suggestion d'amitié/contact";
App::$strings["You are tagged in a post"] = "Vous êtes étiqueté dans une publication";
App::$strings["You are poked/prodded/etc. in a post"] = "Vous êtes tapoté/encouragé/etc. dans une publication";
+App::$strings["Someone likes your post/comment"] = "Quelqu'un aime votre publication/commentaire";
App::$strings["Show visual notifications including:"] = "Afficher des notifications visuelles y compris&nbsp;:";
App::$strings["Unseen grid activity"] = "Activité du réseau pas encore consultée";
App::$strings["Unseen channel activity"] = "Activité non vue sur le canal";
@@ -1232,7 +695,6 @@ App::$strings["Notify me of events this many days in advance"] = "Me prévenir d
App::$strings["Must be greater than 0"] = "Doit être supérieur à 0";
App::$strings["Advanced Account/Page Type Settings"] = "Paramètres avancés de compte/type de page";
App::$strings["Change the behaviour of this account for special situations"] = "Modifie le comportement de ce compte pour des situations particulières";
-App::$strings["Please enable expert mode (in <a href=\"settings/features\">Settings > Additional features</a>) to adjust!"] = "Mode expert requis (<a href=\"settings/features\">Paramètres > Fonctions supplémentaires</a>) pour ajuster&nbsp;!";
App::$strings["Miscellaneous Settings"] = "Paramètres divers";
App::$strings["Default photo upload folder"] = "Répertoire par défaut pour les photos téléversées";
App::$strings["%Y - current year, %m - current month"] = "%Y - année en cours, %m - mois en cours";
@@ -1240,112 +702,611 @@ App::$strings["Default file upload folder"] = "Répertoire par défaut pour les
App::$strings["Personal menu to display in your channel pages"] = "Menu personnel à afficher sur les pages de votre canal";
App::$strings["Remove this channel."] = "Supprimer ce canal";
App::$strings["Firefox Share \$Projectname provider"] = "Connecteur \$Projectname pour Firefox Share";
-App::$strings["Start calendar week on monday"] = "Commencer la semaine du calendrier le lundi";
-App::$strings["\$Projectname Server - Setup"] = "Serveur \$Projectname - configuration";
-App::$strings["Could not connect to database."] = "Impossible de se connecter à la base de données.";
-App::$strings["Could not connect to specified site URL. Possible SSL certificate or DNS issue."] = "Impossible de se connecter à l'URL indiquée. Problème potentiel de certificat SSL/TLS ou de DNS.";
-App::$strings["Could not create table."] = "Impossible de créer la table.";
-App::$strings["Your site database has been installed."] = "La base de données de votre site a été installée.";
-App::$strings["You may need to import the file \"install/schema_xxx.sql\" manually using a database client."] = "Vous pourriez avoir besoin d'importer le fichier \"install/schema_xxx.sql\" manuellement via un client de base de données (ex: phpmyadmin).";
-App::$strings["Please see the file \"install/INSTALL.txt\"."] = "Merci de consulter le fichier \"install/INSTALL.txt\".";
-App::$strings["System check"] = "Vérification du système";
-App::$strings["Check again"] = "Re-vérifier";
-App::$strings["Database connection"] = "Connexion à la base de données";
-App::$strings["In order to install \$Projectname we need to know how to connect to your database."] = "Pour installer \$Projectname, nous avons besoin de savoir comment se connecter à votre base de données.";
-App::$strings["Please contact your hosting provider or site administrator if you have questions about these settings."] = "Merci de contacter votre prestataire d'hébergement ou votre administrateur de site si vous avez des questions à propos de ces paramètres.";
-App::$strings["The database you specify below should already exist. If it does not, please create it before continuing."] = "La base de données que vous allez spécifier doit exister. Si ce n'est pas déjà le cas, merci de la créer avant de continuer.";
-App::$strings["Database Server Name"] = "Nom du serveur de base de données";
-App::$strings["Default is 127.0.0.1"] = "Par défaut 127.0.0.1";
-App::$strings["Database Port"] = "Port de la base de données";
-App::$strings["Communication port number - use 0 for default"] = "Numéro TCP du port - utilisez 0 pour la valeur par défaut";
-App::$strings["Database Login Name"] = "Identifiant de connexion à la Base de Données";
-App::$strings["Database Login Password"] = "Mot de passe de connexion à la Base de Données";
-App::$strings["Database Name"] = "Nom de la Base de Données";
-App::$strings["Database Type"] = "Type de base de données";
-App::$strings["Site administrator email address"] = "Adresse de courriel de l'administrateur du site";
-App::$strings["Your account email address must match this in order to use the web admin panel."] = "Votre compte devra utiliser la même adresse de courriel pour pouvoir utiliser l'administration web.";
-App::$strings["Website URL"] = "URL du site web";
-App::$strings["Please use SSL (https) URL if available."] = "Veuillez utiliser SSL/TLS (https) si disponible.";
-App::$strings["Please select a default timezone for your website"] = "Veuillez choisir un fuseau horaire par défaut pour votre site";
-App::$strings["Site settings"] = "Paramètres du site";
-App::$strings["Enable \$Projectname <strong>advanced</strong> features?"] = "Activer les fonctionnalités <strong>avancées</strong> de \$Projectname&nbsp;?";
-App::$strings["Some advanced features, while useful - may be best suited for technically proficient audiences"] = "Certaines fonctionnalités avancées, bien qu'utiles, sont plus adaptées aux utilisateurs chevronnés.";
-App::$strings["PHP version 5.5 or greater is required."] = "";
-App::$strings["PHP version"] = "";
-App::$strings["Could not find a command line version of PHP in the web server PATH."] = "Impossible de trouver une version CLI de PHP dans le PATH du serveur web.";
-App::$strings["If you don't have a command line version of PHP installed on server, you will not be able to run background polling via cron."] = "En l'absence de version CLI de PHP sur votre serveur, vous ne pourrez pas utiliser la synchronisation en arrière-plan via cron.";
-App::$strings["PHP executable path"] = "Chemin vers l'éxecutable PHP";
-App::$strings["Enter full path to php executable. You can leave this blank to continue the installation."] = "Entrez le chemin complet vers l'exécutable php. Vous pouvez continuer l'installation sans.";
-App::$strings["Command line PHP"] = "PHP en ligne de commande (CLI)";
-App::$strings["The command line version of PHP on your system does not have \"register_argc_argv\" enabled."] = "La version CLI de PHP sur votre système n'a pas l'option \"register_argc_argv\" activée.";
-App::$strings["This is required for message delivery to work."] = "Elle est nécessaire pour la distribution des messages.";
-App::$strings["PHP register_argc_argv"] = "PHP register_argc_argv";
-App::$strings["Your max allowed total upload size is set to %s. Maximum size of one file to upload is set to %s. You are allowed to upload up to %d files at once."] = "Votre taille de téléversement maximale totale autorisée est fixée à %s. La taille maximale d'un seul fichier à téléverser est fixée à %s. Vous pouvez téléverser jusqu'à %d fichier(s) à la fois.";
-App::$strings["You can adjust these settings in the servers php.ini."] = "Vous pouvez ajuster ces paramètres dans le php.ini du serveur.";
-App::$strings["PHP upload limits"] = "Limites de téléversement de PHP";
-App::$strings["Error: the \"openssl_pkey_new\" function on this system is not able to generate encryption keys"] = "Erreur&nbsp;: la fonction \"openssl_pkey_new\" de ce système n'est pas capable de générer des clefs de chiffrement";
-App::$strings["If running under Windows, please see \"http://www.php.net/manual/en/openssl.installation.php\"."] = "Si vous êtes sur un serveur Windows, merci de consulter \"http://www.php.net/manual/fr/openssl.installation.php\".";
-App::$strings["Generate encryption keys"] = "Générer les clefs de chiffrement";
-App::$strings["libCurl PHP module"] = "module PHP libCurl";
-App::$strings["GD graphics PHP module"] = "module PHP GD graphics";
-App::$strings["OpenSSL PHP module"] = "module PHP OpenSSL";
-App::$strings["mysqli or postgres PHP module"] = "module PHP postgres ou mysqli";
-App::$strings["mb_string PHP module"] = "module PHP mb_string";
-App::$strings["mcrypt PHP module"] = "module PHP mcrypt";
-App::$strings["xml PHP module"] = "module PHP xml";
-App::$strings["Apache mod_rewrite module"] = "module Apache mod_rewrite";
-App::$strings["Error: Apache webserver mod-rewrite module is required but not installed."] = "Erreur&nbsp;: le module mod-rewrite du serveur web Apache est requis, mais pas installé.";
-App::$strings["proc_open"] = "proc_open";
-App::$strings["Error: proc_open is required but is either not installed or has been disabled in php.ini"] = "Erreur&nbsp;: proc_open est requis, mais soit n'est pas installé, soit est désactivé dans le php.ini";
-App::$strings["Error: libCURL PHP module required but not installed."] = "Erreur&nbsp;: le module libCURL de PHP est requis, mais pas installé.";
-App::$strings["Error: GD graphics PHP module with JPEG support required but not installed."] = "Erreur&nbsp;: le module GD de PHP avec support JPEG est requis, mais pas installé.";
-App::$strings["Error: openssl PHP module required but not installed."] = "Erreur&nbsp;: le module openssl de PHP est requis, mais pas installé.";
-App::$strings["Error: mysqli or postgres PHP module required but neither are installed."] = "Erreur&nbsp;: un module PHP mysqli ou postgres est requis, mais aucun des deux n'est installé.";
-App::$strings["Error: mb_string PHP module required but not installed."] = "Erreur&nbsp;: le module mb_string de PHP est requis, mais pas installé.";
-App::$strings["Error: mcrypt PHP module required but not installed."] = "Erreur&nbsp;: le module mcrypt de PHP est requis, mais pas installé.";
-App::$strings["Error: xml PHP module required for DAV but not installed."] = "Erreur&nbsp;: le module xml de PHP est requis pour le DAV, mais pas installé.";
-App::$strings["The web installer needs to be able to create a file called \".htconfig.php\" in the top folder of your web server and it is unable to do so."] = "L'installeur web a besoin de créer un fichier \".htconfig.php\" à la racine de votre serveur web, mais en est incapable.";
-App::$strings["This is most often a permission setting, as the web server may not be able to write files in your folder - even if you can."] = "C'est généralement lié à un problème de droits, à cause duquel le serveur web est interdit d'écriture dans le répertoire concerné - alors que votre propre utilisateur a le droit.";
-App::$strings["At the end of this procedure, we will give you a text to save in a file named .htconfig.php in your Red top folder."] = "Au terme de cette procédure, nous vous transmettrons un texte à sauvegarder dans un fichier nommé .htconfig.php, à la racine de votre installation de \$Projectname.";
-App::$strings["You can alternatively skip this procedure and perform a manual installation. Please see the file \"install/INSTALL.txt\" for instructions."] = "Autrement, vous pouvez contourner toute cette procédure et réaliser l'installation manuellement. Merci de consulter le fichier \"install/INSTALL.txt\" pour les instructions détaillées.";
-App::$strings[".htconfig.php is writable"] = "Le fichier .htconfig.php est accessible en écriture";
-App::$strings["Red uses the Smarty3 template engine to render its web views. Smarty3 compiles templates to PHP to speed up rendering."] = "\$Projectname utilise le moteur de gabarits Smarty3 pour mettre son contenu en forme. Smarty3 compile ses modèles vers du PHP natif pour accélérer le rendu.";
-App::$strings["In order to store these compiled templates, the web server needs to have write access to the directory %s under the top level web folder."] = "";
-App::$strings["Please ensure that the user that your web server runs as (e.g. www-data) has write access to this folder."] = "Merci de vous assurer que l'utilisateur sous lequel le serveur web tourne (le plus souvent, www-data) a bien l'autorisation d'écrire dans ce répertoire.";
-App::$strings["Note: as a security measure, you should give the web server write access to %s only--not the template files (.tpl) that it contains."] = "Note: Comme mesure de sécurité, assurez vous de donner les droits d'écriture au serveur web sur %s uniquement, pas sur les fichiers individuels (.tpl) qu'il contient.";
-App::$strings["%s is writable"] = "Permission d'écriture sur %s activée";
-App::$strings["Red uses the store directory to save uploaded files. The web server needs to have write access to the store directory under the Red top level folder"] = "\$Projectname utilise le répertoire 'store' - situé à la racine de votre installation de \$Projectname - pour sauvegarder les fichiers envoyés. Le serveur web aura donc besoin de pouvoir y écrire.";
-App::$strings["store is writable"] = "'store' est accessible en écriture";
-App::$strings["SSL certificate cannot be validated. Fix certificate or disable https access to this site."] = "Le certificat SSL/TLS n'a pas pu être validé. Merci de le corriger, ou de désactiver l'accès https à ce site (non recommandé).";
-App::$strings["If you have https access to your website or allow connections to TCP port 443 (the https: port), you MUST use a browser-valid certificate. You MUST NOT use self-signed certificates!"] = "Si votre serveur accepte les connexions https ou s'il permet les connexions sur le port TCP 443 (le port utilisé par le protocole https), vous DEVEZ utiliser un certificat valide. Vous ne DEVEZ PAS utiliser un certificat que vous avez vous-mêmes signé&nbsp;!";
-App::$strings["This restriction is incorporated because public posts from you may for example contain references to images on your own hub."] = "Nous avons ajouté cette contrainte pour éviter que vos publications publiques ne fassent référence par exemple à des images sur votre propre hub.";
-App::$strings["If your certificate is not recognized, members of other sites (who may themselves have valid certificates) will get a warning message on their own site complaining about security issues."] = "Si votre certificat n'est pas reconnu, les membres des autres sites (qui eux peuvent avoir des certificats valides) recevront des messages d'avertissement sur leur propre site se plaignant de problèmes de sécurité.";
-App::$strings["This can cause usability issues elsewhere (not just on your own site) so we must insist on this requirement."] = "Ceci peut causer des problèmes d'ergonomie ailleurs (pas seulement sur votre site), nous devons donc insister sur ce prérequis.";
-App::$strings["Providers are available that issue free certificates which are browser-valid."] = "Il existe des autorités de certification qui vous fourniront gratuitement un certificat valide.";
-App::$strings["SSL certificate validation"] = "Validation du certificat SSL/TLS";
-App::$strings["Url rewrite in .htaccess is not working. Check your server configuration.Test: "] = "La réécriture d'URL définie dans le .htaccess ne fonctionne pas. Vérifiez votre configuration serveur. Test&nbsp;:";
-App::$strings["Url rewrite is working"] = "La réécriture d'URL fonctionne";
-App::$strings["The database configuration file \".htconfig.php\" could not be written. Please use the enclosed text to create a configuration file in your web server root."] = "Le fichier de configuration de la base de données - \".htconfig.php\" - ne peut être écrit. Merci de copier le texte généré dans un fichier à ce nom, à la racine de votre serveur web.";
-App::$strings["Errors encountered creating database tables."] = "Erreurs rencontrées pendant la création de tables de BDD.";
-App::$strings["<h1>What next</h1>"] = "<h1>Et maintenant</h1>";
-App::$strings["IMPORTANT: You will need to [manually] setup a scheduled task for the poller."] = "IMPORTANT&nbsp;: Vous devez créer [manuellement] une tâche planifiée pour les mises à jour du réseau.";
-App::$strings["Files: shared with me"] = "Fichiers&nbsp;: partagés avec moi";
-App::$strings["NEW"] = "NOUVEAU";
-App::$strings["Remove all files"] = "Supprimer tous les fichiers";
-App::$strings["Remove this file"] = "Supprimer ce fichier";
+App::$strings["Start calendar week on Monday"] = "";
+App::$strings["Additional Features"] = "Fonctionnalités additionnelles";
+App::$strings["This channel is limited to %d tokens"] = "Ce canal est limité à %d jetons";
+App::$strings["Name and Password are required."] = "Le nom et le mot de passe sont requis";
+App::$strings["Token saved."] = "Jeton sauvegardé";
+App::$strings["Use this form to create temporary access identifiers to share things with non-members. These identities may be used in Access Control Lists and visitors may login using these credentials to access private content."] = "Utilisez ce formulaire pour créer des identifiants d'accès temporaires pour partager des informations avec des non-membres. Ces identités peuvent être utilisées dans les listes de contrôle d'accès et les visiteurs peuvent se connecter en utilisant ces certificats d'identification pour accéder au contenu privé.";
+App::$strings["You may also provide <em>dropbox</em> style access links to friends and associates by adding the Login Password to any specific site URL as shown. Examples:"] = "Vous pouvez également fournir des liens d'accès, style <em>dropbox</em>, aux amis et aux associés en ajoutant le mot de passe de connexion à l'URL d'un site spécifique, comme indiqué. Exemples:";
+App::$strings["Guest Access Tokens"] = "Jeton d'accès pour un invité";
+App::$strings["Login Name"] = "Nom d'utilisateur";
+App::$strings["Login Password"] = "Mot de passe";
+App::$strings["Expires (yyyy-mm-dd)"] = "Date d'expiration sous la forme année mois jour (AAAA-MM-JJ)";
+App::$strings["Their Settings"] = "Leurs paramètres";
+App::$strings["Not valid email."] = "Adresse de courriel non valide.";
+App::$strings["Protected email address. Cannot change to that email."] = "Adresse de courriel protégée. Impossible de l'utiliser.";
+App::$strings["System failure storing new email. Please try again."] = "Défaillance système lors du stockage de la nouvelle adresse de courriel. Merci d'essayer à nouveau.";
+App::$strings["Technical skill level updated"] = "Niveau technique mis à jour";
+App::$strings["Password verification failed."] = "La vérification du mot de passe a échoué.";
+App::$strings["Passwords do not match. Password unchanged."] = "Les deux saisies du mot de passe ne correspondent pas. Il n'a donc pas été changé.";
+App::$strings["Empty passwords are not allowed. Password unchanged."] = "Le mot de passe ne peut pas être vide. Il n'a donc pas été changé.";
+App::$strings["Password changed."] = "Le mot de passe a été changé.";
+App::$strings["Password update failed. Please try again."] = "La mise à jour du mot de passe a échoué. Merci d'essayer à nouveau.";
+App::$strings["Account Settings"] = "Paramètres du compte";
+App::$strings["Current Password"] = "Mot de passe actuel";
+App::$strings["Enter New Password"] = "Entrez votre nouveau mot de passe";
+App::$strings["Confirm New Password"] = "Confirmez le nouveau mot de passe";
+App::$strings["Leave password fields blank unless changing"] = "Laissez les mots de passe vides si vous ne voulez pas les modifier";
+App::$strings["Your technical skill level"] = "Votre niveau technique";
+App::$strings["Used to provide a member experience matched to your comfort level"] = "Utilisé pour fournir une expérience utilisateur correspondant à votre niveau de confort";
+App::$strings["Remove Account"] = "Supprimer le compte";
+App::$strings["Remove this account including all its channels"] = "Supprimer ce compte et tous ses canaux";
+App::$strings["Affinity Slider settings updated."] = "Paramètres de la réglette d'affinité mis à jour.";
+App::$strings["No feature settings configured"] = "Aucun paramètre de fonctionnalité configuré";
+App::$strings["Default maximum affinity level"] = "Niveau d'affinité maximum par défaut";
+App::$strings["Default minimum affinity level"] = "Niveau d'affinité minimum par défaut";
+App::$strings["Affinity Slider Settings"] = "Paramètres de la réglette d'affinité";
+App::$strings["Feature/Addon Settings"] = "Paramètres des extensions/greffons";
+App::$strings["No special theme for mobile devices"] = "Pas de thème spécifique aux mobiles";
+App::$strings["%s - (Experimental)"] = "%s - (Expérimental)";
+App::$strings["Display Settings"] = "Afficher les paramètres";
+App::$strings["Theme Settings"] = "Paramètres du thème";
+App::$strings["Custom Theme Settings"] = "Paramètres personnels du thème";
+App::$strings["Content Settings"] = "Paramètres liés au contenu";
+App::$strings["Display Theme:"] = "Afficher le thème&nbsp;:";
+App::$strings["Select scheme"] = "Définir la palette de couleurs";
+App::$strings["Mobile Theme:"] = "Thème mobile&nbsp;:";
+App::$strings["Preload images before rendering the page"] = "Pré-charger les images avant d'afficher la page";
+App::$strings["The subjective page load time will be longer but the page will be ready when displayed"] = "Le temps de charge perçu de la page sera plus long mais la page sera complète quand elle s'affichera";
+App::$strings["Enable user zoom on mobile devices"] = "Permettre à l'utilisateur d'un mobile d'agrandir le contenu";
+App::$strings["Update browser every xx seconds"] = "Mettre à jour le navigateur toutes les xx secondes";
+App::$strings["Minimum of 10 seconds, no maximum"] = "Minimum 10 secondes, pas de maximum";
+App::$strings["Maximum number of conversations to load at any time:"] = "Nombre maximal de conversations pouvant être chargées en même temps&nbsp;:";
+App::$strings["Maximum of 100 items"] = "100 éléments au maximum";
+App::$strings["Show emoticons (smilies) as images"] = "Remplacer les émoticônes (smileys) par des images";
+App::$strings["Manual conversation updates"] = "Manuel de mises à jour des conversations";
+App::$strings["Default is on, turning this off may increase screen jumping"] = "Activé par défaut, le désactiver peut accroître les sauts d'écran";
+App::$strings["Link post titles to source"] = "Lier les titres des publications à leur source";
+App::$strings["System Page Layout Editor - (advanced)"] = "Editeur de mise en page des pages systèmes - (avancé)";
+App::$strings["Use blog/list mode on channel page"] = "Utiliser le mode blog/liste sur la page du canal";
+App::$strings["(comments displayed separately)"] = "(commentaires affichés séparément)";
+App::$strings["Use blog/list mode on grid page"] = "Utiliser le mode blog/liste sur la page du réseau";
+App::$strings["Channel page max height of content (in pixels)"] = "Hauteur maximale du contenu pour la page du canal (en pixels)";
+App::$strings["click to expand content exceeding this height"] = "cliquer pour dérouler le contenu dépassant cette limite";
+App::$strings["Grid page max height of content (in pixels)"] = "Hauteur maximale du contenu sur la page du réseau (en pixels)";
+App::$strings["Name is required"] = "Le nom est requis";
+App::$strings["Key and Secret are required"] = "Clef et secret sont requis";
+App::$strings["Add application"] = "Ajouter une application";
+App::$strings["Name of application"] = "Nom de l'application";
+App::$strings["Consumer Key"] = "Clef client";
+App::$strings["Automatically generated - change if desired. Max length 20"] = "Généré automatiquement - à changer si besoin. Longueur maximale 20 caractères.";
+App::$strings["Consumer Secret"] = "Secret client";
+App::$strings["Redirect"] = "Redirection";
+App::$strings["Redirect URI - leave blank unless your application specifically requires this"] = "URI de redirection - laissez vide, sauf si votre application le requiert spécifiquement";
+App::$strings["Icon url"] = "URL de l'icône";
+App::$strings["Optional"] = "Facultatif";
+App::$strings["Application not found."] = "Application introuvable.";
+App::$strings["Connected Apps"] = "Applications connectées";
+App::$strings["Client key starts with"] = "La clef partagée commence par";
+App::$strings["No name"] = "Sans nom";
+App::$strings["Remove authorization"] = "Révoquer l'autorisation";
+App::$strings["View Photo"] = "Voir la photo";
+App::$strings["Unknown"] = "Inconnu";
+App::$strings["Edit Album"] = "Modifier l'album";
+App::$strings["Upload"] = "Envoyer";
+App::$strings["Some blurb about what to do when you're new here"] = "Quelques mots sur quoi faire quand on est nouveau ici";
+App::$strings["Thing updated"] = "Elément mis à jour";
+App::$strings["Object store: failed"] = "Stockage de l'objet&nbsp;: échec";
+App::$strings["Thing added"] = "Elément ajouté";
+App::$strings["OBJ: %1\$s %2\$s %3\$s"] = "OBJ: %1\$s %2\$s %3\$s";
+App::$strings["Show Thing"] = "Montrer élément";
+App::$strings["item not found."] = "élément introuvable.";
+App::$strings["Edit Thing"] = "Modifier élément";
+App::$strings["Select a profile"] = "Choisissez un profil";
+App::$strings["Post an activity"] = "Publier une activité";
+App::$strings["Only sends to viewers of the applicable profile"] = "Envoie exclusivement aux visiteurs du profil concerné";
+App::$strings["Name of thing e.g. something"] = "Nom de l'élément, p.ex. quelque-chose";
+App::$strings["URL of thing (optional)"] = "URL de l'élément (facultatif)";
+App::$strings["URL for photo of thing (optional)"] = "URL d'une photo de l'élément (facultatif)";
+App::$strings["Permissions"] = "Autorisations";
+App::$strings["Add Thing to your Profile"] = "Ajouter l'élément à votre profil";
+App::$strings["No more system notifications."] = "Pas d'autre notification du système.";
+App::$strings["System Notifications"] = "Notifications du système";
+App::$strings["Channel added."] = "Canal ajouté.";
+App::$strings["Your service plan only allows %d channels."] = "Votre forfait n'autorise que %d canaux.";
+App::$strings["No channel. Import failed."] = "Pas de canal. Echec de l'import.";
+App::$strings["Import completed."] = "L'import est terminé.";
+App::$strings["You must be logged in to use this feature."] = "Vous devez vous connecter pour utiliser cette fonctionnalité.";
+App::$strings["Import Channel"] = "Importation de canal";
+App::$strings["Use this form to import an existing channel from a different server/hub. You may retrieve the channel identity from the old server/hub via the network or provide an export file."] = "Utilisez ce formulaire pour importer un canal existant sur un autre serveur. Vous pouvez récupérer l'identité du canal sur l'ancien serveur directement par le réseau, ou bien fournir un fichier d'export/import.";
+App::$strings["Or provide the old server/hub details"] = "Ou fournissez les détails de l'ancien serveur/hub";
+App::$strings["Your old identity address (xyz@example.com)"] = "Votre ancienne identité (zyx@exemple.com)";
+App::$strings["Your old login email address"] = "Votre ancienne adresse de courriel";
+App::$strings["Your old login password"] = "Votre ancien mot de passe";
+App::$strings["For either option, please choose whether to make this hub your new primary address, or whether your old location should continue this role. You will be able to post from either location, but only one can be marked as the primary location for files, photos, and media."] = "Quelle que soit l'option choisie, merci de décider si ce hub sera votre nouvelle adresse primaire, ou si votre ancien hub continuera à jouer ce rôle. Vous pourrez publier depuis l'emplacement de votre choix, mais une seule peut être déclarée comme stockage primaire de vos fichiers/photos/media.";
+App::$strings["Make this hub my primary location"] = "Faire de ce hub mon emplacement primaire";
+App::$strings["Move this channel (disable all previous locations)"] = "Déplacer ce canal (désactiver tous les emplacements précédents)";
+App::$strings["Import a few months of posts if possible (limited by available memory"] = "Importer plusieurs mois de messages si possible (limité par la mémoire disponible)";
+App::$strings["This process may take several minutes to complete. Please submit the form only once and leave this page open until finished."] = "Ce processus peut prendre plusieurs minutes. Merci de ne valider le formulaire qu'une seule fois et de laisser cette page ouverte jusqu'à la fin.";
+App::$strings["Authentication failed."] = "Échec de l'authentification.";
+App::$strings["Remote Authentication"] = "Authentification distante";
+App::$strings["Enter your channel address (e.g. channel@example.com)"] = "Entrez l'adresse de votre canal (par ex. moncanal@monsite.com)";
+App::$strings["Authenticate"] = "Authentifier";
+App::$strings["Channel not found."] = "Canal introuvable.";
+App::$strings["Permissions denied."] = "Permissions refusées.";
+App::$strings["Import"] = "Import";
+App::$strings["Authorize application connection"] = "Autoriser l'application à se connecter";
+App::$strings["Return to your app and insert this Security Code:"] = "Revenez dans votre application et mettez le code de sécurité";
+App::$strings["Please login to continue."] = "Merci de vous identifier pour continuer.";
+App::$strings["Do you want to authorize this application to access your posts and contacts, and/or create new posts for you?"] = "Voulez-vous autoriser cette application à accéder à vos publications et contacts, et/ou à publier en votre nom?";
+App::$strings["Item not available."] = "Élément indisponible.";
+App::$strings["Insert web link"] = "Insérer lien web";
+App::$strings["Title (optional)"] = "Titre (facultatif)";
+App::$strings["Edit Block"] = "Modifier le bloc";
+App::$strings["vcard"] = "vcard";
+App::$strings["Apps"] = "Applications";
+App::$strings["Manage apps"] = "";
+App::$strings["Create new app"] = "";
+App::$strings["__ctx:mood__ %1\$s is %2\$s"] = "%1\$s est %2\$s";
+App::$strings["Mood"] = "Humeur";
+App::$strings["Set your current mood and tell your friends"] = "Indiquez votre humeur du moment à vos amis";
+App::$strings["Blocked"] = "Bloqué(e)";
+App::$strings["Ignored"] = "Ignoré(e)";
+App::$strings["Hidden"] = "Caché";
+App::$strings["Archived"] = "Archivé";
+App::$strings["New"] = "Nouveautés";
+App::$strings["All"] = "Tous";
+App::$strings["New Connections"] = "Nouveaux contacts";
+App::$strings["Show pending (new) connections"] = "Voir les (nouveaux) contacts en attente";
+App::$strings["Show all connections"] = "Voir tous les contacts";
+App::$strings["Only show blocked connections"] = "Ne montrer que les contacts bloqués";
+App::$strings["Only show ignored connections"] = "Ne montrer que les contacts ignorés";
+App::$strings["Only show archived connections"] = "Ne montrer que les contacts archivés";
+App::$strings["Only show hidden connections"] = "Ne montrer que les contacts cachés";
+App::$strings["Pending approval"] = "En attente de validation";
+App::$strings["%1\$s [%2\$s]"] = "%1\$s [%2\$s]";
+App::$strings["Edit connection"] = "Modifier le contact";
+App::$strings["Delete connection"] = "Supprimer le contact";
+App::$strings["Channel address"] = "Adresse du canal";
+App::$strings["Network"] = "Réseau";
+App::$strings["Call"] = "Appeler";
+App::$strings["Status"] = "État";
+App::$strings["Connected"] = "Ami depuis";
+App::$strings["Approve connection"] = "Valider le contact";
+App::$strings["Ignore connection"] = "Ignorer le contact";
+App::$strings["Ignore"] = "Ignorer";
+App::$strings["Recent activity"] = "Activité récente";
+App::$strings["Connections"] = "Contacts";
+App::$strings["Search your connections"] = "Chercher parmi vos contacts";
+App::$strings["Connections search"] = "Chercher des contacts";
+App::$strings["Find"] = "Trouver";
+App::$strings["Source of Item"] = "Source de l'élément";
+App::$strings["Bookmark added"] = "Favori ajouté";
+App::$strings["My Bookmarks"] = "Mes Favoris";
+App::$strings["My Connections Bookmarks"] = "Favoris de mes contacts";
+App::$strings["Account removals are not allowed within 48 hours of changing the account password."] = "Il est impossible de supprimer un compte dans les 48 heures après avoir changé le mot de passe du compte.";
+App::$strings["Remove This Account"] = "Supprimer ce compte";
+App::$strings["This account and all its channels will be completely removed from the network. "] = "Ce compte et tous ses canaux seront entièrement supprimés du réseau.";
+App::$strings["Remove this account, all its channels and all its channel clones from the network"] = "Supprimer du réseau ce compte, tous ses canaux et tous les clones de ses canaux.";
+App::$strings["By default only the instances of the channels located on this hub will be removed from the network"] = "Par défaut, seules les instances des canaux situés sur ce hub seront supprimées du réseau";
+App::$strings["Page owner information could not be retrieved."] = "Impossible d'obtenir des informations sur le propriétaire de la page.";
+App::$strings["Album not found."] = "Album introuvable.";
+App::$strings["Delete Album"] = "Supprimer l'album";
+App::$strings["Delete Photo"] = "Supprimer la photo";
+App::$strings["No photos selected"] = "Aucune photo selectionnée";
+App::$strings["Access to this item is restricted."] = "L'accès à l'élément est restreint.";
+App::$strings["%1$.2f MB of %2$.2f MB photo storage used."] = "Vous avez utilisé %1$.2f mégaoctets sur les %2$.2f autorisés pour le stockage des photos.";
+App::$strings["%1$.2f MB photo storage used."] = "%1$.2f méga-octets utilisés pour le stockage des photos.";
+App::$strings["Upload Photos"] = "Téléverser des photos";
+App::$strings["Enter an album name"] = "Entrer un nom d'album";
+App::$strings["or select an existing album (doubleclick)"] = "ou sélectionner un album existant (double-clic)";
+App::$strings["Create a status post for this upload"] = "Créer une publication de statut pour cet envoi";
+App::$strings["Caption (optional):"] = "Légende (facultative)";
+App::$strings["Description (optional):"] = "Description (facultative)";
+App::$strings["Show Newest First"] = "Les plus récent(e)s en premier";
+App::$strings["Show Oldest First"] = "Les moins récent(e)s en premier";
+App::$strings["Permission denied. Access to this item may be restricted."] = "Permission refusée. L'accès à cet élément peut avoir été restreint.";
+App::$strings["Photo not available"] = "Photo non disponible";
+App::$strings["Use as profile photo"] = "Utiliser comme photo du profil";
+App::$strings["Use as cover photo"] = "Utilisez comme bannière";
+App::$strings["Private Photo"] = "Photo privée";
+App::$strings["View Full Size"] = "Voir en taille réelle";
+App::$strings["Edit photo"] = "Modifier la photo";
+App::$strings["Rotate CW (right)"] = "Rotation horaire (droite)";
+App::$strings["Rotate CCW (left)"] = "Rotation anti-horaire (gauche)";
+App::$strings["Move photo to album"] = "Déplacer la photo dans l'album";
+App::$strings["Enter a new album name"] = "Entrer un nouveau nom d'album";
+App::$strings["or select an existing one (doubleclick)"] = "ou en sélectionner un existant (double-clic)";
+App::$strings["Caption"] = "Titre/légende";
+App::$strings["Add a Tag"] = "Ajouter une étiquette";
+App::$strings["Example: @bob, @Barbara_Jensen, @jim@example.com"] = "Exemple&nbsp;: @marc, @Barbara_Jensen, @charles@exemple.com, #Ile_de_France, #marathon";
+App::$strings["Flag as adult in album view"] = "Marquer comme \"adulte\" dans l'affichage de l'album";
+App::$strings["I like this (toggle)"] = "J'aime (oui/non)";
+App::$strings["I don't like this (toggle)"] = "Je n'aime pas (oui/non)";
+App::$strings["Please wait"] = "Merci de patienter";
+App::$strings["This is you"] = "C'est vous";
+App::$strings["Comment"] = "Commenter";
+App::$strings["__ctx:title__ Likes"] = "Aime";
+App::$strings["__ctx:title__ Dislikes"] = "N'aime pas";
+App::$strings["__ctx:title__ Agree"] = "D'accord";
+App::$strings["__ctx:title__ Disagree"] = "Pas d'accord";
+App::$strings["__ctx:title__ Abstain"] = "Abstention";
+App::$strings["__ctx:title__ Attending"] = "Participations";
+App::$strings["__ctx:title__ Not attending"] = "Non-participations";
+App::$strings["__ctx:title__ Might attend"] = "Participation possible";
+App::$strings["View all"] = "Voir tout";
+App::$strings["__ctx:noun__ Like"] = array(
+ 0 => "Aime",
+ 1 => "Aime",
+);
+App::$strings["__ctx:noun__ Dislike"] = array(
+ 0 => "N'aime pas",
+ 1 => "N'aime pas",
+);
+App::$strings["Photo Tools"] = "Ouitls pour photos";
+App::$strings["In This Photo:"] = "Dans cette photo&nbsp;:";
+App::$strings["Map"] = "Carte";
+App::$strings["__ctx:noun__ Likes"] = "Aime";
+App::$strings["__ctx:noun__ Dislikes"] = "N'aime pas";
+App::$strings["Close"] = "Fermer";
+App::$strings["Recent Photos"] = "Photos récentes";
+App::$strings["Profile Unavailable."] = "Profil non disponible.";
+App::$strings["Not found"] = "Non trouvé";
+App::$strings["Invalid channel"] = "Canal invalide.";
+App::$strings["Wikis"] = "Wikis";
+App::$strings["Download"] = "Téléchargement";
+App::$strings["Create New"] = "Nouveau";
+App::$strings["Wiki name"] = "Nom du wiki";
+App::$strings["Content type"] = "Type de contenu";
+App::$strings["Type"] = "Type";
+App::$strings["Create a status post for this wiki"] = "Créer un statut de publication pour ce wiki";
+App::$strings["Wiki not found"] = "Wiki introuvable";
+App::$strings["Rename page"] = "Renommer la page";
+App::$strings["Error retrieving page content"] = "Erreur lors de la récupération du contenu de la page";
+App::$strings["New page"] = "";
+App::$strings["Revision Comparison"] = "Comparaison des révisions";
+App::$strings["Revert"] = "Revenir";
+App::$strings["Short description of your changes (optional)"] = "Description courte de vos modifications (optionnel)";
+App::$strings["Source"] = "Source";
+App::$strings["New page name"] = "Nouveau nom de la page";
+App::$strings["Embed image from photo albums"] = "Intégrer une image d'un album photo";
+App::$strings["Embed an image from your albums"] = "Intégrer une image de votre album photo";
+App::$strings["OK"] = "OK";
+App::$strings["Choose images to embed"] = "Choisissez des images à intégrer";
+App::$strings["Choose an album"] = "Choisir un album";
+App::$strings["Choose a different album"] = "Choisissez un autre album";
+App::$strings["Error getting album list"] = "Erreur venant de la liste de l'album";
+App::$strings["Error getting photo link"] = "Erreur provenant du lien de la photo";
+App::$strings["Error getting album"] = "Erreur venant de l'album";
+App::$strings["Error creating wiki. Invalid name."] = "Erreur lors de la création du wiki. Nom invalide.";
+App::$strings["A wiki with this name already exists."] = "";
+App::$strings["Wiki created, but error creating Home page."] = "Le wiki a été créé, mais une erreur est survenue lors de la création de sa page d'accueil.";
+App::$strings["Error creating wiki"] = "Erreur lors de la création du wiki.";
+App::$strings["Wiki delete permission denied."] = "Permission de supprimer le wiki refusée.";
+App::$strings["Error deleting wiki"] = "Erreur durant la suppression du wiki";
+App::$strings["New page created"] = "Nouvelle page créée";
+App::$strings["Cannot delete Home"] = "Impossible de supprimer la racine";
+App::$strings["Current Revision"] = "Version actuelle";
+App::$strings["Selected Revision"] = "Version sélectionnée";
+App::$strings["You must be authenticated."] = "Vous devez être connecté.";
+App::$strings["toggle full screen mode"] = "Basculer en mode plein écran.";
+App::$strings["Layout updated."] = "Mise en page mise à jour.";
+App::$strings["Feature disabled."] = "Fonctionnalité désactivée";
+App::$strings["Edit System Page Description"] = "Modifier la description de la page du système";
+App::$strings["Layout not found."] = "Mise en page introuvable.";
+App::$strings["Module Name:"] = "Nom du module&nbsp;:";
+App::$strings["Layout Help"] = "Aide à la mise en page";
+App::$strings["Poke"] = "Tapoter";
+App::$strings["Poke somebody"] = "Taquiner quelqu'un";
+App::$strings["Poke/Prod"] = "Tapoter/Encourager";
+App::$strings["Poke, prod or do other things to somebody"] = "Taquiner, pousser ou faire autre chose à quelqu'un";
+App::$strings["Recipient"] = "Destinataire";
+App::$strings["Choose what you wish to do to recipient"] = "Choisir ce que vous voulez faire au destinataire";
+App::$strings["Make this post private"] = "Rendre cette publication privée";
+App::$strings["Image uploaded but image cropping failed."] = "L'image a été téléversée, mais le recadrage a échoué.";
+App::$strings["Profile Photos"] = "Photos du profil";
+App::$strings["Image resize failed."] = "Le redimensionnement de l'image a échoué.";
+App::$strings["Shift-reload the page or clear browser cache if the new photo does not display immediately."] = "Shift-rechargez votre page, ou videz le cache du navigateur si la photo ne s'affiche pas immédiatement.";
+App::$strings["Unable to process image"] = "Impossible de traiter l'image";
+App::$strings["Image upload failed."] = "Le téléversement de l'image a échoué.";
+App::$strings["Unable to process image."] = "Impossible de traîter l'image.";
+App::$strings["Photo not available."] = "Photo inaccessible.";
+App::$strings["Upload File:"] = "Téléverser fichier&nbsp;:";
+App::$strings["Select a profile:"] = "Choisir un profil&nbsp;:";
+App::$strings["Use Photo for Profile"] = "Utiliser la photo pour le profil";
+App::$strings["Upload Profile Photo"] = "Téléverser une photo de profil";
+App::$strings["Use"] = "Utiliser";
+App::$strings["skip this step"] = "passer cette étape";
+App::$strings["select a photo from your photo albums"] = "choisir une photo dans vos albums";
+App::$strings["Crop Image"] = "Recadrer l'image";
+App::$strings["Please adjust the image cropping for optimum viewing."] = "Merci d'ajuster le cadre pour une visualisation optimale.";
+App::$strings["Done Editing"] = "J'ai terminé";
+App::$strings["Away"] = "Absent";
+App::$strings["Online"] = "En ligne";
+App::$strings["Unable to locate original post."] = "Impossible de localiser la publication initiale.";
+App::$strings["Empty post discarded."] = "Publication vide annulée.";
+App::$strings["Duplicate post suppressed."] = "Publication en doublon supprimée.";
+App::$strings["System error. Post not saved."] = "Erreur système. Publication non sauvegardée.";
+App::$strings["Unable to obtain post information from database."] = "Impossible d'obtenir les informations de publication depuis la base de données.";
+App::$strings["You have reached your limit of %1$.0f top level posts."] = "Vous avez atteint votre limite de %1$.0f contributions \"racines\".";
+App::$strings["You have reached your limit of %1$.0f webpages."] = "Vous avez atteint votre limite de %1$.0f pages web.";
+App::$strings["sent you a private message"] = "vous a envoyé un message privé";
+App::$strings["added your channel"] = "a ajouté votre canal";
+App::$strings["g A l F d"] = "g A l F d";
+App::$strings["[today]"] = "[aujourd'hui]";
+App::$strings["posted an event"] = "a publié un événement";
+App::$strings["Invalid item."] = "Élément invalide.";
+App::$strings["Page not found."] = "Page introuvable.";
+App::$strings["Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum."] = "Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.";
+App::$strings["Could not access contact record."] = "Impossible d'accéder aux détails du contact.";
+App::$strings["Could not locate selected profile."] = "Impossible de localiser le profil sélectionné.";
+App::$strings["Connection updated."] = "Contact mis à jour.";
+App::$strings["Failed to update connection record."] = "Impossible de mettre à jour les détails du contact.";
+App::$strings["is now connected to"] = "est maintenant connecté avec";
+App::$strings["Could not access address book record."] = "Impossible d'accéder aux détails du carnet d'adresses.";
+App::$strings["Refresh failed - channel is currently unavailable."] = "Actualisation impossible - le canal est indisponible.";
+App::$strings["Unable to set address book parameters."] = "Impossible de régler les paramètres du carnet d'adresses.";
+App::$strings["Connection has been removed."] = "Le contact a été supprimé.";
+App::$strings["View Profile"] = "Voir mon profil";
+App::$strings["View %s's profile"] = "Voir le profil de %s";
+App::$strings["Refresh Permissions"] = "Actualiser les autorisations";
+App::$strings["Fetch updated permissions"] = "Récupérer les autorisations les plus récentes";
+App::$strings["Refresh Photo"] = "";
+App::$strings["Fetch updated photo"] = "";
+App::$strings["Recent Activity"] = "Activité récente";
+App::$strings["View recent posts and comments"] = "Voir les publications et commentaires récents";
+App::$strings["Block (or Unblock) all communications with this connection"] = "Bloquer ou débloquer toute communication avec ce contact";
+App::$strings["This connection is blocked!"] = "Ce contact est bloqué&nbsp;!";
+App::$strings["Unignore"] = "Ne plus ignorer";
+App::$strings["Ignore (or Unignore) all inbound communications from this connection"] = "Ignorer ou ne plus ignorer toute communication venant de ce contact";
+App::$strings["This connection is ignored!"] = "Ce contact est ignoré&nbsp;!";
+App::$strings["Unarchive"] = "Désarchiver";
+App::$strings["Archive"] = "Archiver";
+App::$strings["Archive (or Unarchive) this connection - mark channel dead but keep content"] = "Archiver ou désarchiver ce contact - le marquer comme inactif mais conserver le contenu";
+App::$strings["This connection is archived!"] = "Ce contact est archivé&nbsp;!";
+App::$strings["Unhide"] = "Ne plus cacher";
+App::$strings["Hide"] = "Cacher";
+App::$strings["Hide or Unhide this connection from your other connections"] = "Cacher ou ne plus cacher ce contact vis-à-vis de vos autres contacts";
+App::$strings["This connection is hidden!"] = "Ce contact est caché&nbsp;!";
+App::$strings["Delete this connection"] = "Supprimer ce contact";
+App::$strings["Fetch Vcard"] = "";
+App::$strings["Fetch electronic calling card for this connection"] = "";
+App::$strings["Open Individual Permissions section by default"] = "Ouvrir par défaut la section des autorisations individuelles";
+App::$strings["Affinity"] = "Affinité";
+App::$strings["Open Set Affinity section by default"] = "Ouvrir par défaut la section Définir le degré d'affinité";
+App::$strings["Me"] = "Moi";
+App::$strings["Family"] = "Famille";
+App::$strings["Acquaintances"] = "Connaissances";
+App::$strings["Filter"] = "Filtrer";
+App::$strings["Open Custom Filter section by default"] = "Ouvrir par défaut la section Filtre personnalisé";
+App::$strings["Approve this connection"] = "Autoriser ce contact";
+App::$strings["Accept connection to allow communication"] = "Accepter le contact pour permettre la communication";
+App::$strings["Set Affinity"] = "Définir le degré d'affinité";
+App::$strings["Set Profile"] = "Définir le profil";
+App::$strings["Set Affinity & Profile"] = "Définir le degré d'affinité et le profil";
+App::$strings["none"] = "Aucun";
+App::$strings["Connection Default Permissions"] = "Autorisations par défaut des contacts";
+App::$strings["Connection: %s"] = "Contact&nbsp;: %s";
+App::$strings["Apply these permissions automatically"] = "Appliquer ces permissions automatiquement";
+App::$strings["Connection requests will be approved without your interaction"] = "Les demandes de contact seront approuvées automatiquement";
+App::$strings["Permission role"] = "Rôle d'accès";
+App::$strings["Add permission role"] = "Ajouter un rôle d'accès";
+App::$strings["This connection's primary address is"] = "L'adresse principale de ce contact est";
+App::$strings["Available locations:"] = "Emplacements disponibles&nbsp;:";
+App::$strings["The permissions indicated on this page will be applied to all new connections."] = "Les permissions indiquées sur cette page seront appliquées à tous vos nouveaux contacts.";
+App::$strings["Connection Tools"] = "Actions du contact";
+App::$strings["Slide to adjust your degree of friendship"] = "Faites glisser pour ajuster votre proximité avec le contact";
+App::$strings["Rating"] = "Evaluation";
+App::$strings["Slide to adjust your rating"] = "Faîtes glisser pour ajuster votre note";
+App::$strings["Optionally explain your rating"] = "Explication facultative de votre évaluation";
+App::$strings["Custom Filter"] = "Filtre personnalisé";
+App::$strings["Only import posts with this text"] = "N'importer que les publications comprenant ce texte";
+App::$strings["words one per line or #tags or /patterns/ or lang=xx, leave blank to import all posts"] = "un mot par ligne ou #étiquettes ou /motif/ ou lang=xx, laisser vide pour importer toutes les publications";
+App::$strings["Do not import posts with this text"] = "Ne pas importer les publications comprenant ce texte";
+App::$strings["This information is public!"] = "Cette information est publique&nbsp;!";
+App::$strings["Connection Pending Approval"] = "Contact en attente d'approbation";
+App::$strings["Please choose the profile you would like to display to %s when viewing your profile securely."] = "Merci de choisir le profil que vous souhaitez montrer quand %s visite votre profil de manière authentifiée.";
+App::$strings["Some permissions may be inherited from your channel's <a href=\"settings\"><strong>privacy settings</strong></a>, which have higher priority than individual settings. You can change those settings here but they wont have any impact unless the inherited setting changes."] = "Certaines permissions peuvent être héritées de vos <a href=\"settings\">paramètres de confidentialité</a> de canal, lesquels sont prioritaires sur les réglages individuels. Vous pouvez modifier ces permissions ici mais cela n'aura aucun effet à moins de changer les paramètres hérités.";
+App::$strings["Last update:"] = "Dernière mise à jour&nbsp;:";
+App::$strings["Details"] = "Détails";
+App::$strings["Organisation"] = "Organisation";
+App::$strings["Title"] = "Titre";
+App::$strings["Phone"] = "Téléphone";
+App::$strings["Instant messenger"] = "Instant messenger";
+App::$strings["Website"] = "Site web";
+App::$strings["Note"] = "Note";
+App::$strings["Mobile"] = "Mobile";
+App::$strings["Home"] = "Mon canal";
+App::$strings["Work"] = "Travail";
+App::$strings["Add Contact"] = "Ajouter un contact";
+App::$strings["Add Field"] = "Ajouter un champ";
+App::$strings["P.O. Box"] = "P.O. Box";
+App::$strings["Additional"] = "Information complémentaires";
+App::$strings["Street"] = "Rue";
+App::$strings["Locality"] = "Localité";
+App::$strings["Region"] = "Région";
+App::$strings["ZIP Code"] = "ZIP code";
+App::$strings["Country"] = "Pays";
+App::$strings["Room not found"] = "Salon introuvable";
+App::$strings["Leave Room"] = "Quitter le salon";
+App::$strings["Delete Room"] = "Supprimer le salon";
+App::$strings["I am away right now"] = "Je suis absent en ce moment";
+App::$strings["I am online"] = "Je suis en ligne";
+App::$strings["Bookmark this room"] = "Marquer ce salon comme favori";
+App::$strings["Please enter a link URL:"] = "Merci d'entrer l'URL d'un lien&nbsp;:";
+App::$strings["Encrypt text"] = "Chiffrer le texte";
+App::$strings["New Chatroom"] = "Nouveau salon de discussion";
+App::$strings["Chatroom name"] = "Nom du salon de conversation";
+App::$strings["Expiration of chats (minutes)"] = "Expiration des discussions (en minutes)";
+App::$strings["%1\$s's Chatrooms"] = "Salons de %1\$s";
+App::$strings["No chatrooms available"] = "Aucun salon de conversation disponible";
+App::$strings["Expiration"] = "Expiration";
+App::$strings["min"] = "min";
+App::$strings["Photos"] = "Photos";
+App::$strings["Files"] = "Fichiers";
+App::$strings["Unable to update menu."] = "Impossible de mettre le menu à jour.";
+App::$strings["Unable to create menu."] = "Impossible de créer le menu.";
+App::$strings["Menu Name"] = "Nom du menu";
+App::$strings["Unique name (not visible on webpage) - required"] = "Nom unique (non visible sur la page web) - requis";
+App::$strings["Menu Title"] = "Titre du menu";
+App::$strings["Visible on webpage - leave empty for no title"] = "Visible pour la page web - laisser vide pour qu'il n'y ait pas de titre";
+App::$strings["Allow Bookmarks"] = "Autoriser l'usage de favoris";
+App::$strings["Menu may be used to store saved bookmarks"] = "Le menu pourra être utilisé pour stocker des favoris";
+App::$strings["Submit and proceed"] = "Valider et continuer";
+App::$strings["Menus"] = "Menus";
+App::$strings["Bookmarks allowed"] = "Favoris autorisés";
+App::$strings["Delete this menu"] = "Supprimer ce menu";
+App::$strings["Edit menu contents"] = "Modifier le contenu du menu";
+App::$strings["Edit this menu"] = "Modifier ce menu";
+App::$strings["Menu could not be deleted."] = "Impossible de supprimer le menu.";
+App::$strings["Edit Menu"] = "Modifier le menu";
+App::$strings["Add or remove entries to this menu"] = "Ajouter/supprimer des entrées à ce menu";
+App::$strings["Menu name"] = "Nom du menu";
+App::$strings["Must be unique, only seen by you"] = "Doit être unique, ne sera vu que par vous";
+App::$strings["Menu title"] = "Titre du menu";
+App::$strings["Menu title as seen by others"] = "Titre du menu tel que vu par les visiteurs";
+App::$strings["Allow bookmarks"] = "Autoriser l'usage de favoris";
+App::$strings["Layouts"] = "Mises-en-page";
+App::$strings["Help"] = "Aide";
+App::$strings["Comanche page description language help"] = "Aide sur le langage de description de page Comanche";
+App::$strings["Layout Description"] = "Description de la mise en page";
+App::$strings["Download PDL file"] = "Télécharger le fichier PDL";
+App::$strings["post"] = "publication";
+App::$strings["comment"] = "commentaire";
+App::$strings["%1\$s tagged %2\$s's %3\$s with %4\$s"] = "%1\$s a étiqueté le %3\$s de %2\$s avec %4\$s";
+App::$strings["This setting requires special processing and editing has been blocked."] = "Ce paramètre nécessité un traitement spécial, les modifications ont été bloquées.";
+App::$strings["Configuration Editor"] = "Editeur de configuration";
+App::$strings["Warning: Changing some settings could render your channel inoperable. Please leave this page unless you are comfortable with and knowledgeable about how to correctly use this feature."] = "Attention&nbsp;:modifier certains paramètres peut rendre votre canal inutilisable. Merci d'ignorer cette page à moins d'être suffisamment à l'aise de savoir comment utiliser correctement cette fonctionnalité.";
+App::$strings["Privacy group created."] = "Groupe de contacts créé.";
+App::$strings["Could not create privacy group."] = "Impossible de créer le groupe de contacts.";
+App::$strings["Privacy group not found."] = "Groupe de contacts introuvable.";
+App::$strings["Privacy group updated."] = "Groupe de contacts mis à jour.";
+App::$strings["Create a group of channels."] = "Créer un groupe de contacts.";
+App::$strings["Privacy group name: "] = "Nom du groupe de contacts&nbsp;:";
+App::$strings["Members are visible to other channels"] = "Les membres sont visibles par les autres canaux";
+App::$strings["Privacy group removed."] = "Groupe de contacts supprimé.";
+App::$strings["Unable to remove privacy group."] = "Impossible de supprimer le groupe de canaux.";
+App::$strings["Privacy group editor"] = "Editeur de groupe de contacts.";
+App::$strings["Members"] = "Membres";
+App::$strings["All Connected Channels"] = "Tous les canaux connectés";
+App::$strings["Click on a channel to add or remove."] = "Cliquer sur un canal pour l'ajouter ou le supprimer";
+App::$strings["Profile not found."] = "Profil introuvable.";
+App::$strings["Profile deleted."] = "Profil supprimé.";
+App::$strings["Profile-"] = "Profil-";
+App::$strings["New profile created."] = "Nouveau profil créé.";
+App::$strings["Profile unavailable to clone."] = "Profil impossible à cloner.";
+App::$strings["Profile unavailable to export."] = "Impossible d'exporter le profil.";
+App::$strings["Profile Name is required."] = "Le nom du profil est obligatoire.";
+App::$strings["Marital Status"] = "Statut marital";
+App::$strings["Romantic Partner"] = "Partenaire amoureux";
+App::$strings["Likes"] = "Aime";
+App::$strings["Dislikes"] = "N'aime pas";
+App::$strings["Work/Employment"] = "Travail/Occupation";
+App::$strings["Religion"] = "Religion/Croyance";
+App::$strings["Political Views"] = "Opinions politiques";
+App::$strings["Gender"] = "Sexe";
+App::$strings["Sexual Preference"] = "Préférences sexuelle";
+App::$strings["Homepage"] = "Site Internet";
+App::$strings["Interests"] = "Centres d'intérêt";
+App::$strings["Profile updated."] = "Profil mis à jour.";
+App::$strings["Hide your connections list from viewers of this profile"] = "Cacher la liste des relations pour les visiteurs de votre profile";
+App::$strings["Edit Profile Details"] = "Modifier les détails du profil";
+App::$strings["View this profile"] = "Voir ce profil";
+App::$strings["Edit visibility"] = "Changer la visibilité";
+App::$strings["Profile Tools"] = "Ouitls pour votre profile";
+App::$strings["Change cover photo"] = "Modifier votre bannière";
+App::$strings["Change profile photo"] = "Changer la photo du profil";
+App::$strings["Create a new profile using these settings"] = "Créer un nouveau profil avec ces paramètres";
+App::$strings["Clone this profile"] = "Cloner ce profil";
+App::$strings["Delete this profile"] = "Supprimer ce profil";
+App::$strings["Add profile things"] = "Ajouter des éléments de profil";
+App::$strings["Personal"] = "Me concernant";
+App::$strings["Relation"] = "Contacts";
+App::$strings["Miscellaneous"] = "Divers";
+App::$strings["Import profile from file"] = "Importer le profil à partir d'un fichier";
+App::$strings["Export profile to file"] = "Exporter le profil vers un fichier.";
+App::$strings["Your gender"] = "Votre genre";
+App::$strings["Marital status"] = "Etat civil";
+App::$strings["Sexual preference"] = "préférence sexuelle";
+App::$strings["Profile name"] = "Nom du profile";
+App::$strings["This is your default profile."] = "Ceci est votre profil par défaut.";
+App::$strings["Your full name"] = "Votre nom complet";
+App::$strings["Title/Description"] = "Titre/description";
+App::$strings["Street address"] = "Rue";
+App::$strings["Locality/City"] = "Ville";
+App::$strings["Region/State"] = "Région";
+App::$strings["Postal/Zip code"] = "Code postal";
+App::$strings["Who (if applicable)"] = "Qui (si applicable)";
+App::$strings["Examples: cathy123, Cathy Williams, cathy@example.com"] = "Exemples&nbsp;: marie123, Marie Deschamps, marie@exemple.com";
+App::$strings["Since (date)"] = "Depuis (date)";
+App::$strings["Tell us about yourself"] = "Parlez nous de vous...";
+App::$strings["Homepage URL"] = "URL de mon site Internet&nbsp;:";
+App::$strings["Hometown"] = "Ville de naissance";
+App::$strings["Political views"] = "Opinions politiques";
+App::$strings["Religious views"] = "Convictions religieuses";
+App::$strings["Keywords used in directory listings"] = "Mots clés pour l'annuaire";
+App::$strings["Example: fishing photography software"] = "Exemple&nbsp;: escrime photographie modélisme";
+App::$strings["Musical interests"] = "Goûts musicaux";
+App::$strings["Books, literature"] = "Livres, littérature";
+App::$strings["Television"] = "Télévision";
+App::$strings["Film/Dance/Culture/Entertainment"] = "Cinéma/Danse/Culture/Divertissement";
+App::$strings["Hobbies/Interests"] = "Loisirs/Centres d'intêret";
+App::$strings["Love/Romance"] = "Amour/Relation amoureuse";
+App::$strings["School/Education"] = "Niveau d'étude";
+App::$strings["Contact information and social networks"] = "Coordonnées et autres réseaux sociaux";
+App::$strings["My other channels"] = "Mes autres canaux";
+App::$strings["Communications"] = "";
+App::$strings["Profile Image"] = "Image du profil";
+App::$strings["Edit Profiles"] = "Modifier mes profils";
+App::$strings["Page link"] = "Lien";
+App::$strings["Edit Webpage"] = "Modifier la page web";
+App::$strings["Create a new channel"] = "Créer un nouveau canal";
+App::$strings["Channel Manager"] = "Gérer mes canaux";
+App::$strings["Current Channel"] = "Canal actif";
+App::$strings["Switch to one of your channels by selecting it."] = "Pour changer de canal, sélectionnez-en un";
+App::$strings["Default Channel"] = "Canal par défaut";
+App::$strings["Make Default"] = "Définir comme défaut";
+App::$strings["%d new messages"] = "%d nouveaux messages";
+App::$strings["%d new introductions"] = "%d nouvelles relations";
+App::$strings["Delegated Channel"] = "Canaux délégués";
+App::$strings["This directory server requires an access token"] = "Ce serveur d'annuaire requiert un jeton d'accès";
+App::$strings["About this site"] = "À propos de ce site";
+App::$strings["Site Name"] = "Nom du site";
+App::$strings["Administrator"] = "Administrateur";
+App::$strings["Terms of Service"] = "Conditions de service";
+App::$strings["Software and Project information"] = "Informations sur le logiciel et le projet";
+App::$strings["This site is powered by \$Projectname"] = "Ce site est propulsé par ";
+App::$strings["Federated and decentralised networking and identity services provided by Zot"] = "Réseau fédéré et décentralisé, et services d'identification fournies par Zot";
App::$strings["Version %s"] = "Version %s";
-App::$strings["Installed plugins/addons/apps:"] = "Greffons/extensions/applications installés&nbsp;:";
-App::$strings["No installed plugins/addons/apps"] = "Aucun greffon/extension/application installé";
-App::$strings["This is a hub of \$Projectname - a global cooperative network of decentralized privacy enhanced websites."] = "Ceci est un serveur \$Projectname - un réseau collaboratif mondial de serveurs décentralisés à la confidentialité améliorée.";
-App::$strings["Tag: "] = "Étiquette&nbsp;:";
-App::$strings["Last background fetch: "] = "Dernière récupération en tâche de fond&nbsp;:";
-App::$strings["Current load average: "] = "Charge moyenne actuelle&nbsp;:";
-App::$strings["Running at web location"] = "Tourne à l'adresse internet";
-App::$strings["Please visit <a href=\"http://hubzilla.org\">hubzilla.org</a> to learn more about \$Projectname."] = "Merci de visiter <a href=\"http://hubzilla.org\">hubzilla.org</a> pour en apprendre davantage sur \$Projectname.";
-App::$strings["Bug reports and issues: please visit"] = "Pour remonter bogues et problèmes, merci de visiter";
-App::$strings["\$projectname issues"] = "Problèmes \$projectname";
-App::$strings["Suggestions, praise, etc. - please email \"redmatrix\" at librelist - dot com"] = "Suggestions, demandes, etc. - merci de vous adresser à \"redmatrix\" à librelist - point com";
-App::$strings["Site Administrators"] = "Administrateurs du site";
+App::$strings["Project homepage"] = "Page d'accueil du projet";
+App::$strings["Developer homepage"] = "Page d'accueil des développeurs";
+App::$strings["No ratings"] = "Pas de note";
+App::$strings["Ratings"] = "Evaluations";
+App::$strings["Rating: "] = "Evaluation&nbsp:";
+App::$strings["Website: "] = "Site web&nbsp;:";
+App::$strings["Description: "] = "Description&nbsp;:";
+App::$strings["Import Webpage Elements"] = "Importer éléments de page web";
+App::$strings["Import selected"] = "Importation sélectionnée";
+App::$strings["Export Webpage Elements"] = "Exporter éléments de pages web";
+App::$strings["Export selected"] = "Export sélectionné";
+App::$strings["Webpages"] = "Pages web";
+App::$strings["Actions"] = "Actions";
+App::$strings["Page Link"] = "Lien vers la page";
+App::$strings["Page Title"] = "Titre de la page";
+App::$strings["Invalid file type."] = "Type de fichier invalide";
+App::$strings["Error opening zip file"] = "Erreur lors de l'ouverture du fichier zip";
+App::$strings["Invalid folder path."] = "Chemin du dossier invalide";
+App::$strings["No webpage elements detected."] = "Aucun élément de page Web détecté.";
+App::$strings["Import complete."] = "Importation terminée";
+App::$strings["Item is not editable"] = "Elément non modifiable";
+App::$strings["Edit post"] = "Modifier la publication";
+App::$strings["Invalid message"] = "Message non valide";
+App::$strings["no results"] = "aucun résultat";
+App::$strings["channel sync processed"] = "Synchro de canal effectuée";
+App::$strings["queued"] = "mis dans la file d'attente";
+App::$strings["posted"] = "publié";
+App::$strings["accepted for delivery"] = "accepté pour la distribution";
+App::$strings["updated"] = "mis à jour";
+App::$strings["update ignored"] = "mise à jour ignorée";
+App::$strings["permission denied"] = "permission refusée";
+App::$strings["recipient not found"] = "destinataire introuvable";
+App::$strings["mail recalled"] = "courriel rappelé";
+App::$strings["duplicate mail received"] = "courriel reçu en double";
+App::$strings["mail delivered"] = "courriel distribué";
+App::$strings["Delivery report for %1\$s"] = "Rapport de distribution pour %1\$s";
+App::$strings["Options"] = "Options";
+App::$strings["Redeliver"] = "Transférer à nouveau";
App::$strings["Failed to create source. No channel selected."] = "Impossible de créer la source. Aucun canal selectionné.";
App::$strings["Source created."] = "Source créée.";
App::$strings["Source updated."] = "Source mise à jour.";
@@ -1357,64 +1318,227 @@ App::$strings["Import all or selected content from the following channel into th
App::$strings["Only import content with these words (one per line)"] = "N'importer le contenu que s'il contient ces mots (un par ligne)";
App::$strings["Leave blank to import all public content"] = "Laissez vide pour importer tout le contenu public";
App::$strings["Channel Name"] = "Nom du canal";
-App::$strings["Add the following categories to posts imported from this source (comma separated)"] = "";
+App::$strings["Add the following categories to posts imported from this source (comma separated)"] = "Ajouter les catégories suivantes aux publications importées à partir de cette source (séparer par des virgules)";
App::$strings["Source not found."] = "Source introuvable.";
App::$strings["Edit Source"] = "Modifier la source";
App::$strings["Delete Source"] = "Supprimer la source";
App::$strings["Source removed"] = "Source supprimée";
App::$strings["Unable to remove source."] = "Impossible de supprimer la source.";
-App::$strings["%1\$s is following %2\$s's %3\$s"] = "%1\$s suit %3\$s de %2\$s";
-App::$strings["%1\$s stopped following %2\$s's %3\$s"] = "%1\$s ne suit plus %3\$s de %2\$s";
+App::$strings["Like/Dislike"] = "Aime/n'aime pas";
+App::$strings["This action is restricted to members."] = "Cette action est réservée aux membres.";
+App::$strings["Please <a href=\"rmagic\">login with your \$Projectname ID</a> or <a href=\"register\">register as a new \$Projectname member</a> to continue."] = "S'il vous plait, <a href=\"rmagic\">identifiez vous avec votre identifant de \$Projectname </a> ou <a href=\"register\">inscrivez vous comme nouveau membre de \$Projectname </a> pour continuer.";
+App::$strings["Invalid request."] = "Requête invalide.";
+App::$strings["channel"] = "canal";
+App::$strings["thing"] = "chose";
+App::$strings["Channel unavailable."] = "Canal indisponible.";
+App::$strings["Previous action reversed."] = "Action précédente annulée.";
+App::$strings["%1\$s likes %2\$s's %3\$s"] = "%1\$s aime %3\$s de %2\$s";
+App::$strings["%1\$s doesn't like %2\$s's %3\$s"] = "%1\$s n'aime pas %3\$s de %2\$s";
+App::$strings["%1\$s agrees with %2\$s's %3\$s"] = "%1\$s approuve %3\$s de %2\$s";
+App::$strings["%1\$s doesn't agree with %2\$s's %3\$s"] = "%1\$s n'est pas d'accord avec %3\$s de %2\$s";
+App::$strings["%1\$s abstains from a decision on %2\$s's %3\$s"] = "%1\$s s'abstient de toute décision sur le %3\$s de %2\$s";
+App::$strings["%1\$s is attending %2\$s's %3\$s"] = "%1\$s participe à %3\$s de %2\$s";
+App::$strings["%1\$s is not attending %2\$s's %3\$s"] = "%1\$s ne participe pas à %3\$s de %2\$s";
+App::$strings["%1\$s may attend %2\$s's %3\$s"] = "%1\$s participe peut-être à %3\$s de %2\$s";
+App::$strings["Action completed."] = "Action terminée.";
+App::$strings["Thank you."] = "Merci.";
+App::$strings["%d rating"] = array(
+ 0 => "%d évaluation",
+ 1 => "%d évaluations",
+);
+App::$strings["Gender: "] = "Sexe/genre&nbsp;:";
+App::$strings["Status: "] = "État&nbsp;:";
+App::$strings["Homepage: "] = "Site web&nbsp;:";
+App::$strings["Age:"] = "Age&nbsp;:";
+App::$strings["Location:"] = "Emplacement&nbsp;:";
+App::$strings["Description:"] = "Description&nbsp;:";
+App::$strings["Hometown:"] = "Ville natale&nbsp;:";
+App::$strings["About:"] = "À propos&nbsp;:";
+App::$strings["Connect"] = "Ajouter/Suivre";
+App::$strings["Public Forum:"] = "Forum public&nbsp;:";
+App::$strings["Keywords: "] = "Mots-clefs&nbsp;:";
+App::$strings["Don't suggest"] = "Ne pas suggérer";
+App::$strings["Common connections:"] = "Contacts en commun&nbsp;:";
+App::$strings["Global Directory"] = "Annuaire global";
+App::$strings["Local Directory"] = "Annuaire local";
+App::$strings["Finding:"] = "Recherche&nbsp;:";
+App::$strings["Channel Suggestions"] = "Canaux suggérés";
+App::$strings["next page"] = "page suivante";
+App::$strings["previous page"] = "page précédente";
+App::$strings["Sort options"] = "Options de tri";
+App::$strings["Alphabetic"] = "Alphabétique";
+App::$strings["Reverse Alphabetic"] = "Alphabétique inversé";
+App::$strings["Newest to Oldest"] = "Du plus récent au moins récent";
+App::$strings["Oldest to Newest"] = "Du moins récent du plus récent";
+App::$strings["No entries (some entries may be hidden)."] = "Pas d'entrées (certaines peuvent être cachées).";
+App::$strings["Xchan Lookup"] = "Recherche xchan";
+App::$strings["Lookup xchan beginning with (or webbie): "] = "Recherche xchan commençant par (ou adresse \"webbie\")&nbsp;:";
App::$strings["No suggestions available. If this is a new site, please try again in 24 hours."] = "Aucune suggestion disponible. Si le site est récent, merci de re-tenter dans 24 heures.";
App::$strings["Ignore/Hide"] = "Ignorer/Cacher";
-App::$strings["post"] = "publication";
-App::$strings["comment"] = "commentaire";
-App::$strings["%1\$s tagged %2\$s's %3\$s with %4\$s"] = "%1\$s a étiqueté le %3\$s de %2\$s avec %4\$s";
+App::$strings["Unable to find your hub."] = "Impossible de trouver votre hub.";
+App::$strings["Post successful."] = "Publication réussie.";
+App::$strings["Unable to lookup recipient."] = "Impossible de localiser le destinataire.";
+App::$strings["Unable to communicate with requested channel."] = "Impossible de communiquer avec le canal demandé.";
+App::$strings["Cannot verify requested channel."] = "Impossible de vérifier le canal demandé.";
+App::$strings["Selected channel has private message restrictions. Send failed."] = "Le canal choisi a des restrictions quant aux messages privés. L'envoi a échoué.";
+App::$strings["Messages"] = "Messages";
+App::$strings["Message recalled."] = "Message rappelé.";
+App::$strings["Conversation removed."] = "Conversation supprimée.";
+App::$strings["Expires YYYY-MM-DD HH:MM"] = "Expire le YYYY-MM-DD à HH:MM";
+App::$strings["Requested channel is not in this network"] = "Le canal demandé n'est pas sur ce réseau";
+App::$strings["Send Private Message"] = "Envoyer un message privé";
+App::$strings["To:"] = "À&nbsp;:";
+App::$strings["Subject:"] = "Objet&nbsp;:";
+App::$strings["Attach file"] = "Joindre un fichier";
+App::$strings["Send"] = "Envoyer";
+App::$strings["Set expiration date"] = "Définir la date d'expiration";
+App::$strings["Delete message"] = "Supprimer le message";
+App::$strings["Delivery report"] = "Rapport de distribution";
+App::$strings["Recall message"] = "Rappeler le message";
+App::$strings["Message has been recalled."] = "Le message a été rappelé.";
+App::$strings["Delete Conversation"] = "Supprimer la conversation";
+App::$strings["No secure communications available. You <strong>may</strong> be able to respond from the sender's profile page."] = "Aucune communication sécurisée n'est possible. Vous pourrez <strong>peut-être</strong> répondre depuis la page de profil de l'émetteur.";
+App::$strings["Send Reply"] = "Envoyer la réponse";
+App::$strings["Your message for %s (%s):"] = "Votre message pour %s (%s)&nbsp;:";
+App::$strings["Public Hubs"] = "Instances publiques";
+App::$strings["The listed hubs allow public registration for the \$Projectname network. All hubs in the network are interlinked so membership on any of them conveys membership in the network as a whole. Some hubs may require subscription or provide tiered service plans. The hub itself <strong>may</strong> provide additional details."] = "Les sites listés permettent l'enregistrement public de comptes pour le réseau \$Projectname. Tous les sites du réseau sont reliés entre eux, être membre d'un site revient à être membre de tous. Certains sites peuvent demander une souscription ou proposer différents niveaux de service. Chaque site <strong>peut</strong> fournir des détails supplémentaires.";
+App::$strings["Hub URL"] = "URL du site";
+App::$strings["Access Type"] = "Type d'accès";
+App::$strings["Registration Policy"] = "Politique d'inscription";
+App::$strings["Stats"] = "Statistiques";
+App::$strings["Software"] = "Logiciel";
+App::$strings["Rate"] = "Evaluer";
+App::$strings["webpage"] = "pages web";
+App::$strings["block"] = "bloquer";
+App::$strings["layout"] = "mise en page";
+App::$strings["menu"] = "menu";
+App::$strings["%s element installed"] = "Elément %s installé";
+App::$strings["%s element installation failed"] = "L'installation de l'élément %s a échoué";
+App::$strings["Select a bookmark folder"] = "Choisir un dossier de favoris";
+App::$strings["Save Bookmark"] = "Enregistrer le favori";
+App::$strings["URL of bookmark"] = "URL du favori";
+App::$strings["Or enter new bookmark folder name"] = "Ou entrez un nouveau nom de dossier de favoris";
+App::$strings["Enter a folder name"] = "";
+App::$strings["or select an existing folder (doubleclick)"] = "";
+App::$strings["Save to Folder"] = "Enregistrer dans le dossier";
+App::$strings["Fetching URL returns error: %1\$s"] = "Récupération d'URL échouée&nbsp;: %1\$s";
+App::$strings["Maximum daily site registrations exceeded. Please try again tomorrow."] = "Nombre d'inscriptions quotidiennes dépassé. Merci d'essayer à nouveau demain.";
+App::$strings["Please indicate acceptance of the Terms of Service. Registration failed."] = "Merci d'indiquer votre adhésion aux conditions de service. L'inscription a échoué.";
+App::$strings["Passwords do not match."] = "Les mots de passe ne concordent pas.";
+App::$strings["Registration successful. Please check your email for validation instructions."] = "Inscription réussie. Merci de vérifier vos courriels pour valider votre compte.";
+App::$strings["Your registration is pending approval by the site owner."] = "Votre inscription est en attente d'approbation par l'administrateur.";
+App::$strings["Your registration can not be processed."] = "Votre inscription ne peut être traîtée.";
+App::$strings["Registration on this hub is disabled."] = "La création de nouveaux comptes est désactivée pour ce site.";
+App::$strings["Registration on this hub is by approval only."] = "La création de compte sur ce site est soumise à approbation.";
+App::$strings["<a href=\"pubsites\">Register at another affiliated hub.</a>"] = "<a href=\"pubsites\">S'enregistrer sur un autre site du réseau.</a>";
+App::$strings["This site has exceeded the number of allowed daily account registrations. Please try again tomorrow."] = "Ce site a dépassé le nombre de création de comptes autorisé chaque jour. Merci d'essayer à nouveau demain.";
+App::$strings["I accept the %s for this website"] = "J'accepte les %s de ce site";
+App::$strings["I am over 13 years of age and accept the %s for this website"] = "J'ai plus de 13 ans et j'accepte les %s de ce site";
+App::$strings["Your email address"] = "Votre adresse de courriel";
+App::$strings["Choose a password"] = "Choisissez un mot de passe";
+App::$strings["Please re-enter your password"] = "Merci de saisir à nouveau votre mot de passe";
+App::$strings["Please enter your invitation code"] = "Merci de saisir votre code d'invitation";
+App::$strings["no"] = "non";
+App::$strings["yes"] = "oui";
+App::$strings["Membership on this site is by invitation only."] = "L'inscription à ce site se fait uniquement sur invitation.";
+App::$strings["Register"] = "S'inscrire";
+App::$strings["This site may require email verification after submitting this form. If you are returned to a login page, please check your email for instructions."] = "Ce site peut demander une validation de votre email. Si vous revenez sur le formulaire de connexion, vérifiez vos emails et suivez les instructions. Regardez aussi les spams.";
+App::$strings["Cover Photos"] = "Photos de couverture";
+App::$strings["female"] = "femme";
+App::$strings["%1\$s updated her %2\$s"] = "%1\$s a mis à jour son %2\$s";
+App::$strings["male"] = "homme";
+App::$strings["%1\$s updated his %2\$s"] = "%1\$s a mis à jour son %2\$s";
+App::$strings["%1\$s updated their %2\$s"] = "%1\$s a mis a jour sa %2\$s";
+App::$strings["cover photo"] = "Photo principale";
+App::$strings["Upload Cover Photo"] = "Téléverser une photo de couverture";
+App::$strings["Documentation Search"] = "Chercher dans la documentation";
+App::$strings["About"] = "À propos";
+App::$strings["Administrators"] = "Administrateurs";
+App::$strings["Developers"] = "Développeurs";
+App::$strings["Tutorials"] = "Tutoriels";
+App::$strings["\$Projectname Documentation"] = "Documentation \$Projectname";
+App::$strings["Contents"] = "Contenus";
App::$strings["Tag removed"] = "Étiquette retirée";
App::$strings["Remove Item Tag"] = "Retirer une étiquette à l'élément";
App::$strings["Select a tag to remove: "] = "Étiquette à retirer&nbsp;:";
-App::$strings["Thing updated"] = "Elément mis à jour";
-App::$strings["Object store: failed"] = "Stockage de l'objet&nbsp;: échec";
-App::$strings["Thing added"] = "Elément ajouté";
-App::$strings["OBJ: %1\$s %2\$s %3\$s"] = "OBJ: %1\$s %2\$s %3\$s";
-App::$strings["Show Thing"] = "Montrer élément";
-App::$strings["item not found."] = "élément introuvable.";
-App::$strings["Edit Thing"] = "Modifier élément";
-App::$strings["Select a profile"] = "Choisissez un profil";
-App::$strings["Post an activity"] = "Publier une activité";
-App::$strings["Only sends to viewers of the applicable profile"] = "Envoie exclusivement aux visiteurs du profil concerné";
-App::$strings["Name of thing e.g. something"] = "Nom de l'élément, p.ex. quelque-chose";
-App::$strings["URL of thing (optional)"] = "URL de l'élément (facultatif)";
-App::$strings["URL for photo of thing (optional)"] = "URL d'une photo de l'élément (facultatif)";
-App::$strings["Add Thing to your Profile"] = "Ajouter l'élément à votre profil";
-App::$strings["Export Channel"] = "Exporter le canal";
-App::$strings["Export your basic channel information to a file. This acts as a backup of your connections, permissions, profile and basic data, which can be used to import your data to a new server hub, but does not contain your content."] = "Exportez les principales informations de votre canal dans un fichier. Celui-ci pourra servir de sauvegarde de vos contacts, permissions, profils et données de base. Il pourra être importé sur un nouveau hub/serveur, mais n'embarquera pas vos contenus.";
-App::$strings["Export Content"] = "Exporter le contenu";
-App::$strings["Export your channel information and recent content to a JSON backup that can be restored or imported to another server hub. This backs up all of your connections, permissions, profile data and several months of posts. This file may be VERY large. Please be patient - it may take several minutes for this download to begin."] = "Exportez les informations du canal et les contenus récents dans un fichier JSON. Celui-ci contiendra toutes vos relations, permissions, profils, et plusieurs mois de publications. Ce fichier peut être TRÈS gros. Armez-vous de patience - plusieurs minutes peuvent s'écouler avant que le téléchargement ne commence.";
-App::$strings["Export your posts from a given year."] = "Exporter vos publications d'une année en particulier";
-App::$strings["You may also export your posts and conversations for a particular year or month. Adjust the date in your browser location bar to select other dates. If the export fails (possibly due to memory exhaustion on your server hub), please try again selecting a more limited date range."] = "Vous pouvez également exporter vos publications et conversations pour une année ou un mois particulier. Ajustez la date dans la barre de votre navigateur pour sélectionner d'autres dates. Si l'export échoue (possible en cas de pénurie de mémoire sur le serveur de votre hub), essayez à nouveau en sélectionnant un intervalle de dates plus petit.";
-App::$strings["To select all posts for a given year, such as this year, visit <a href=\"%1\$s\">%2\$s</a>"] = "Pour sélectionner toutes les publications pour une année donnée, telle que cette année, visitez <a href=\"%1\$s\">%2\$s</a>";
-App::$strings["To select all posts for a given month, such as January of this year, visit <a href=\"%1\$s\">%2\$s</a>"] = "Pour sélectionner toutes les publications pour un mois donné, par exemple janvier, visitez <a href=\"%1\$s\">%2\$s</a>";
-App::$strings["These content files may be imported or restored by visiting <a href=\"%1\$s\">%2\$s</a> on any site containing your channel. For best results please import or restore these in date order (oldest first)."] = "Ces fichiers de contenu peuvent être importés ou restaurés en visitant <a href=\"%1\$s\">%2\$s</a> sur n'importe quel site hébergeant votre canal. Pour de meilleurs résultats merci de les importer par ordre chronologique (les plus anciens d'abord).";
+App::$strings["No such group"] = "Groupe introuvable";
+App::$strings["No such channel"] = "Canal introuvable";
+App::$strings["forum"] = "forum";
+App::$strings["Search Results For:"] = "Résultats de recherche pour&nbsp;:";
+App::$strings["Privacy group is empty"] = "Groupe de contacts vide";
+App::$strings["Privacy group: "] = "Groupe de contacts&nbsp;:";
+App::$strings["Invalid connection."] = "Contact non valide.";
+App::$strings["Invalid channel."] = "Canal invalide.";
+App::$strings["network"] = "réseau";
+App::$strings["RSS"] = "RSS";
+App::$strings["\$Projectname"] = "\$Projectname";
+App::$strings["Welcome to %s"] = "Bienvenue sur %s";
+App::$strings["Permission Denied."] = "Permission refusée.";
+App::$strings["File not found."] = "Fichier introuvable.";
+App::$strings["Edit file permissions"] = "Modifier les autorisations d'accès au fichier";
+App::$strings["Set/edit permissions"] = "Définir/modifier les autorisations";
+App::$strings["Include all files and sub folders"] = "Inclure tous fichiers et sous-répertoires";
+App::$strings["Return to file list"] = "Retourner à la liste des fichiers";
+App::$strings["Copy/paste this code to attach file to a post"] = "Copiez/collez ce code pour joindre le fichier à une publication";
+App::$strings["Copy/paste this URL to link file from a web page"] = "Copiez/collez cette URL pour pointer vers ce fichier depuis une page web";
+App::$strings["Share this file"] = "Partager ce fichier";
+App::$strings["Show URL to this file"] = "Montrer l'URL de ce fichier";
+App::$strings["Notify your contacts about this file"] = "Notifier vos contacts à propos de ce fichier";
+App::$strings["No channel."] = "Pas de canal.";
+App::$strings["Common connections"] = "Contacts en commun";
+App::$strings["No connections in common."] = "Pas de contacts en commun.";
App::$strings["No connections."] = "Aucun contact.";
App::$strings["Visit %s's profile [%s]"] = "Visiter le profil de %s [%s]";
App::$strings["View Connections"] = "Voir les contacts";
-App::$strings["Source of Item"] = "Source de l'élément";
-App::$strings["Webpages"] = "Pages web";
-App::$strings["Actions"] = "Actions";
-App::$strings["Page Link"] = "Lien vers la page";
-App::$strings["Page Title"] = "Titre de la page";
-App::$strings["Xchan Lookup"] = "Recherche xchan";
-App::$strings["Lookup xchan beginning with (or webbie): "] = "Recherche xchan commençant par (ou adresse \"webbie\")&nbsp;:";
+App::$strings["# Accounts"] = "# Comptes";
+App::$strings["# blocked accounts"] = "# comptes bloqués";
+App::$strings["# expired accounts"] = "# comptes expirés";
+App::$strings["# expiring accounts"] = "# comptes expirant";
+App::$strings["# Channels"] = "# Canaux";
+App::$strings["# primary"] = "# primaire";
+App::$strings["# clones"] = "# clones";
+App::$strings["Message queues"] = "File des messages";
+App::$strings["Your software should be updated"] = "Votre logiciel doit d'être mis à jour";
+App::$strings["Summary"] = "Résumé";
+App::$strings["Registered accounts"] = "Comptes enregistrés";
+App::$strings["Pending registrations"] = "Inscriptions en attente";
+App::$strings["Registered channels"] = "Canaux enregistrés";
+App::$strings["Active plugins"] = "Greffons actifs";
+App::$strings["Version"] = "Version";
+App::$strings["Repository version (master)"] = "Version du dépôt (maître)";
+App::$strings["Repository version (dev)"] = "Version du dépôt (développeur)";
+App::$strings["No service class restrictions found."] = "Aucune restriction de classe de service trouvée.";
+App::$strings["Website:"] = "Site web&nbsp;:";
+App::$strings["Remote Channel [%s] (not yet known on this site)"] = "Canal distant [%s] (encore inconnu sur ce site)";
+App::$strings["Rating (this information is public)"] = "Evaluation (cette information est publique)";
+App::$strings["Optionally explain your rating (this information is public)"] = "Explication facultative de votre évaluation (cette information est publique)";
+App::$strings["No valid account found."] = "Aucun compte valide trouvé.";
+App::$strings["Password reset request issued. Check your email."] = "Demande de réinitialisation du mot de passe envoyée. Vérifiez vos courriels.";
+App::$strings["Site Member (%s)"] = "Membre du site (%s)";
+App::$strings["Password reset requested at %s"] = "Demande de réinitialisation du mot de passe sur %s";
+App::$strings["Request could not be verified. (You may have previously submitted it.) Password reset failed."] = "La demande n'a pas pu être vérifiée. (Peut-être l'avez vous déjà utilisée.) La réinitialisation a échoué.";
+App::$strings["Password Reset"] = "Réinitialiser le mot de passe";
+App::$strings["Your password has been reset as requested."] = "Votre mot de passe a bien été réinitialisé.";
+App::$strings["Your new password is"] = "Votre nouveau mot de passe est";
+App::$strings["Save or copy your new password - and then"] = "Enregistrez ou copiez votre nouveau mot de passe, puis";
+App::$strings["click here to login"] = "cliquez ici pour vous connecter";
+App::$strings["Your password may be changed from the <em>Settings</em> page after successful login."] = "Votre mot de passe peut être changé depuis la page des <em>Paramètres</em> une fois connecté.";
+App::$strings["Your password has changed at %s"] = "Votre mot de passe de %s a été changé";
+App::$strings["Forgot your Password?"] = "Mot de passe oublié&nbsp;?";
+App::$strings["Enter your email address and submit to have your password reset. Then check your email for further instructions."] = "Saisissez votre adresse de courriel, et validez, pour réinitialiser votre mot de passe. Vérifiez ensuite votre boîte aux lettres pour la suite des instructions.";
+App::$strings["Email Address"] = "Adresse de courriel";
+App::$strings["Reset"] = "Réinitialiser";
+App::$strings["Mark all system notifications seen"] = "Marquer toutes les notifications système comme vues";
App::$strings["Site Admin"] = "Administrateur";
-App::$strings["Bug Report"] = "";
-App::$strings["View Bookmarks"] = "";
-App::$strings["My Chatrooms"] = "";
-App::$strings["Firefox Share"] = "";
-App::$strings["Remote Diagnostics"] = "";
+App::$strings["Report Bug"] = "Reporter des bogues";
+App::$strings["View Bookmarks"] = "Voir les marques-pages";
+App::$strings["My Chatrooms"] = "Mes salons de discussions";
+App::$strings["Firefox Share"] = "Partager via Firefox";
+App::$strings["Remote Diagnostics"] = "Diagnostiques à distance";
App::$strings["Suggest Channels"] = "Suggérer des canaux";
App::$strings["Login"] = "Connexion";
App::$strings["Grid"] = "Réseau";
+App::$strings["Wiki"] = "Wiki";
App::$strings["Channel Home"] = "Mon canal";
App::$strings["Events"] = "Événements";
App::$strings["Directory"] = "Annuaire";
@@ -1425,8 +1549,46 @@ App::$strings["Suggest"] = "Suggérer";
App::$strings["Random Channel"] = "Un canal au hasard";
App::$strings["Invite"] = "Invitation";
App::$strings["Features"] = "Fonctionalités";
+App::$strings["Language"] = "Langue";
App::$strings["Post"] = "Envoyer";
+App::$strings["Profile Photo"] = "Photo du Profil";
App::$strings["Purchase"] = "Acheter";
+App::$strings["Undelete"] = "Restaurer";
+App::$strings["Add to app-tray"] = "";
+App::$strings["Remove from app-tray"] = "";
+App::$strings["__ctx:permcat__ default"] = "défaut";
+App::$strings["__ctx:permcat__ follower"] = "abonné";
+App::$strings["__ctx:permcat__ contributor"] = "contributeur";
+App::$strings["__ctx:permcat__ publisher"] = "rédacteur";
+App::$strings["(No Title)"] = "(Pas de titre)";
+App::$strings["Wiki page create failed."] = "Échec de création de la page wiki.";
+App::$strings["Wiki not found."] = "Wiki introuvable.";
+App::$strings["Destination name already exists"] = "Le nom de destination est déjà pris";
+App::$strings["Page not found"] = "Page introuvable";
+App::$strings["Error reading page content"] = "Erreur de lecture du contenu de la page";
+App::$strings["Error reading wiki"] = "Erreur de lecture du wiki";
+App::$strings["Page update failed."] = "Echec de modification de la page.";
+App::$strings["Nothing deleted"] = "Rien n'a été supprimé";
+App::$strings["Compare: object not found."] = "Comparaison&nbsp;: objet introuvable.";
+App::$strings["Page updated"] = "Page modifiée";
+App::$strings["Untitled"] = "Sans titre";
+App::$strings["Wiki resource_id required for git commit"] = "\"resource_id\" du wiki nécessaire pour l'enregistrement dans git.";
+App::$strings["__ctx:wiki_history__ Message"] = "Message";
+App::$strings["Different viewers will see this text differently"] = "Ce texte aura un rendu différent en fonction des utilisateurs";
+App::$strings["Visible to your default audience"] = "Visible pour vos contacts seulement";
+App::$strings["Only me"] = "Seulement moi";
+App::$strings["Public"] = "Public";
+App::$strings["Anybody in the \$Projectname network"] = "N'importe qui dans le réseau de \$Projectname";
+App::$strings["Any account on %s"] = "N'importe quel compte sur %s";
+App::$strings["Any of my connections"] = "N'importe laquelle de mes connexions";
+App::$strings["Only connections I specifically allow"] = "Uniquement les connexions que j'ai expréssément autorisées";
+App::$strings["Anybody authenticated (could include visitors from other networks)"] = "N'importe qui d'authentifié (cela peut inclure des visiteurs d'autres réseaux)";
+App::$strings["Any connections including those who haven't yet been approved"] = "N'importe quelle connexions, y compris celles qui n'ont pas encore été approuvées";
+App::$strings["This is your default setting for the audience of your normal stream, and posts."] = "Ceci est votre réglage par défaut de l'audience de vos publications sur votre canal normal.";
+App::$strings["This is your default setting for who can view your default channel profile"] = "Ceci est votre réglage par défaut à propos de qui peut voir votre canal de profil par défaut.";
+App::$strings["This is your default setting for who can view your connections"] = "Ceci est votre réglage par défaut à propos de qui peut voir vos relations.";
+App::$strings["This is your default setting for who can view your file storage and photos"] = "Ceci est votre réglage par défaut à propos de qui peut voir vos fichiers ou photos stocké(e)s";
+App::$strings["This is your default setting for the audience of your webpages"] = "Ceci est votre réglage par défaut de l'audience de vos pages web.";
App::$strings["Missing room name"] = "Il manque le nom du salon";
App::$strings["Duplicate room name"] = "Un salon avec ce nom existe déjà";
App::$strings["Invalid room specifier."] = "Identifiant de salon invalide.";
@@ -1437,7 +1599,7 @@ App::$strings["\$projectname"] = "\$projectname";
App::$strings["Thank You,"] = "Merci,";
App::$strings["%s Administrator"] = "l'administrateur de %s";
App::$strings["%s <!item_type!>"] = "%s <!item_type!>";
-App::$strings["[Hubzilla:Notify] New mail received at %s"] = "[Hubzilla:Notify] Nouveau courriel reçu à %s";
+App::$strings["[\$Projectname:Notify] New mail received at %s"] = "[\$Projectname:Notify] Nouveau mail reçu sur %s";
App::$strings["%1\$s, %2\$s sent you a new private message at %3\$s."] = "%1\$s, vous avez reçu un message privé sur %3\$s, de la part de %2\$s.";
App::$strings["%1\$s sent you %2\$s."] = "%1\$s vous a envoyé %2\$s.";
App::$strings["a private message"] = "un message privé";
@@ -1445,48 +1607,53 @@ App::$strings["Please visit %s to view and/or reply to your private messages."]
App::$strings["%1\$s, %2\$s commented on [zrl=%3\$s]a %4\$s[/zrl]"] = "%1\$s, %2\$s a commenté sur [zrl=%3\$s]%4\$s[/zrl]";
App::$strings["%1\$s, %2\$s commented on [zrl=%3\$s]%4\$s's %5\$s[/zrl]"] = "%1\$s, %2\$s a commenté sur [zrl=%3\$s]%5\$s de %4\$s[/zrl]";
App::$strings["%1\$s, %2\$s commented on [zrl=%3\$s]your %4\$s[/zrl]"] = "%1\$s, %2\$s a commenté [zrl=%3\$s]votre %4\$s[/zrl]";
-App::$strings["[Hubzilla:Notify] Comment to conversation #%1\$d by %2\$s"] = "[Hubzilla:Notify] Commentaire de %2\$s sur conversation #%1\$d";
+App::$strings["[\$Projectname:Notify] Comment to conversation #%1\$d by %2\$s"] = "[\$Projectname:Notify] Commentaire effectué sur la conversation #%1\$d par %2\$s";
App::$strings["%1\$s, %2\$s commented on an item/conversation you have been following."] = "%1\$s, %2\$s a commenté un élément de conversation que vous suivez.";
App::$strings["Please visit %s to view and/or reply to the conversation."] = "Merci de visiter %s pour voir et/ou répondre sur cette conversation.";
-App::$strings["[Hubzilla:Notify] %s posted to your profile wall"] = "[Hubzilla:Notify] %s a publié sur votre profil";
+App::$strings["%1\$s, %2\$s liked [zrl=%3\$s]your %4\$s[/zrl]"] = "%1\$s, %2\$s aiment [zrl=%3\$s]votre %4\$s[/zrl]";
+App::$strings["[\$Projectname:Notify] Like received to conversation #%1\$d by %2\$s"] = "[\$Projectname:Notify] Aime reçu à la convesation #%1\$d par %2\$s";
+App::$strings["%1\$s, %2\$s liked an item/conversation you created."] = "%1\$s, %2\$s a aimé un élément ou une conversation que vous avez créée.";
+App::$strings["[\$Projectname:Notify] %s posted to your profile wall"] = "[\$Projectname:Notify] %s a publié sur le mur de votre profil";
App::$strings["%1\$s, %2\$s posted to your profile wall at %3\$s"] = "%1\$s, %2\$s a publié sur votre profil à %3\$s";
App::$strings["%1\$s, %2\$s posted to [zrl=%3\$s]your wall[/zrl]"] = "%1\$s, %2\$s a publié sur [zrl=%3\$s]votre profil[/zrl]";
-App::$strings["[Hubzilla:Notify] %s tagged you"] = "[Hubzilla:Notify] %s vous a étiqueté";
+App::$strings["[\$Projectname:Notify] %s tagged you"] = "[\$Projectname:Notify] %s vous a étiquetté";
App::$strings["%1\$s, %2\$s tagged you at %3\$s"] = "%1\$s, vous avez été étiqueté sur %3\$s par %2\$s";
App::$strings["%1\$s, %2\$s [zrl=%3\$s]tagged you[/zrl]."] = "%1\$s, %2\$s [zrl=%3\$s]vous a étiqueté[/zrl].";
-App::$strings["[Hubzilla:Notify] %1\$s poked you"] = "[Hubzilla:Notify] %1\$s vous a tapoté";
+App::$strings["[\$Projectname:Notify] %1\$s poked you"] = "[\$Projectname:Notify] %1\$s vous a poké";
App::$strings["%1\$s, %2\$s poked you at %3\$s"] = "%1\$s, %2\$s vous a tapoté sur %3\$s";
App::$strings["%1\$s, %2\$s [zrl=%2\$s]poked you[/zrl]."] = "%1\$s, %2\$s [zrl=%2\$s]vous a tapoté[/zrl].";
-App::$strings["[Hubzilla:Notify] %s tagged your post"] = "[Hubzilla:Notify] %s a étiqueté votre publication";
+App::$strings["[\$Projectname:Notify] %s tagged your post"] = "[\$Projectname:Notify] %s a étiquetté votre publication";
App::$strings["%1\$s, %2\$s tagged your post at %3\$s"] = "%1\$s, %2\$s a étiqueté votre publication sur %3\$s";
App::$strings["%1\$s, %2\$s tagged [zrl=%3\$s]your post[/zrl]"] = "%1\$s, %2\$s a étiqueté [zrl=%3\$s]votre publication[/zrl]";
-App::$strings["[Hubzilla:Notify] Introduction received"] = "[Hubzilla:Notify] Nouvelle présentation";
+App::$strings["[\$Projectname:Notify] Introduction received"] = "[\$Projectname:Notify] Demande de relation reçue";
App::$strings["%1\$s, you've received an new connection request from '%2\$s' at %3\$s"] = "%1\$s, vous avez reçu une demande de contact de '%2\$s' sur %3\$s";
App::$strings["%1\$s, you've received [zrl=%2\$s]a new connection request[/zrl] from %3\$s."] = "%1\$s, vous avez reçu [zrl=%2\$s]une demande de contact[/zrl] de %3\$s.";
App::$strings["You may visit their profile at %s"] = "Vous pouvez visiter leur profil sur %s";
App::$strings["Please visit %s to approve or reject the connection request."] = "Merci de visiter %s avant d'approuver (ou non) cette demande de contact.";
-App::$strings["[Hubzilla:Notify] Friend suggestion received"] = "[Hubzilla:Notify] Nouvel(le) ami(e) suggéré(e)";
+App::$strings["[\$Projectname:Notify] Friend suggestion received"] = "[\$Projectname:Notify] Suggestion d'amitié reçue";
App::$strings["%1\$s, you've received a friend suggestion from '%2\$s' at %3\$s"] = "%1\$s, vous avez reçu une suggestion d'ami(e) de '%2\$s' à %3\$s";
App::$strings["%1\$s, you've received [zrl=%2\$s]a friend suggestion[/zrl] for %3\$s from %4\$s."] = "%1\$s, avez reçu %3\$s comme [zrl=%2\$s]une suggestion d'ami(e)[/zrl] de %4\$s.";
App::$strings["Name:"] = "Nom&nbsp;:";
App::$strings["Photo:"] = "Photo&nbsp;:";
App::$strings["Please visit %s to approve or reject the suggestion."] = "Merci de visiter %s pour donner suite (ou non) à cette suggestion.";
-App::$strings["[Hubzilla:Notify]"] = "[Hubzilla:Notify]";
+App::$strings["[\$Projectname:Notify]"] = "[\$Projectname:Notify]";
App::$strings["created a new post"] = "a publié un nouveau message";
App::$strings["commented on %s's post"] = "a commenté la publication de %s";
+App::$strings["Wiki files deleted successfully"] = "Fichiers du wiki supprimés avec succès";
+App::$strings["Update Error at %s"] = "Erreur de mise à jour sur %s";
+App::$strings["Update %s failed. See error logs."] = "La mise-à-jour %s a échoué. Merci de consulter les journaux d'erreur.";
App::$strings["Private Message"] = "Message Privé";
App::$strings["Select"] = "Sélectionner";
-App::$strings["Save to Folder"] = "Enregistrer dans le dossier";
App::$strings["I will attend"] = "Je participerai";
App::$strings["I will not attend"] = "Je ne participerai pas";
App::$strings["I might attend"] = "Je participerai peut-être";
App::$strings["I agree"] = "Je suis d'accord";
App::$strings["I disagree"] = "Je ne suis pas d'accord";
App::$strings["I abstain"] = "Je m'abstiens";
-App::$strings["Add Star"] = "Mettre en avant (étoile)";
-App::$strings["Remove Star"] = "Ne plus mettre en avant";
+App::$strings["Add Star"] = "Mettre de côté (étoile)";
+App::$strings["Remove Star"] = "Ne plus mettre de côté";
App::$strings["Toggle Star Status"] = "(Dés)activer l'étoile";
-App::$strings["starred"] = "mis en avant";
+App::$strings["starred"] = "mis de côté";
App::$strings["Message signature validated"] = "Signature du message validée";
App::$strings["Message signature incorrect"] = "Signature du message incorrecte";
App::$strings["Add Tag"] = "Ajouter une étiquette";
@@ -1507,10 +1674,14 @@ App::$strings["via Wall-To-Wall:"] = "par Mur-à-mur&nbsp;:";
App::$strings["from %s"] = "de %s";
App::$strings["last edited: %s"] = "dernière modification&nbsp;: %s";
App::$strings["Expires: %s"] = "Expire&nbsp;: %s";
+App::$strings["Attend"] = "En attente";
+App::$strings["Attendance Options"] = "Options d'attente";
+App::$strings["Vote"] = "Vote";
+App::$strings["Voting Options"] = "Options de vote";
App::$strings["Save Bookmarks"] = "Enregistrer les favoris";
App::$strings["Add to Calendar"] = "Ajouter au Calendrier";
App::$strings["Mark all seen"] = "Tout marquer comme vu";
-App::$strings["[+] show all"] = "[+] voir tous";
+App::$strings["%s show all"] = "%s montre tout";
App::$strings["Bold"] = "Gras";
App::$strings["Italic"] = "Italique";
App::$strings["Underline"] = "Souligné";
@@ -1519,274 +1690,783 @@ App::$strings["Code"] = "Code";
App::$strings["Image"] = "Image";
App::$strings["Insert Link"] = "Insérer un lien";
App::$strings["Video"] = "Vidéo";
-App::$strings["No username found in import file."] = "Aucun nom d'utilisateur dans le fichier d'import.";
-App::$strings["Unable to create a unique channel address. Import failed."] = "Impossible de créer une adresse de canal unique. Echec de l'import.";
-App::$strings["Cannot locate DNS info for database server '%s'"] = "Impossible de trouver les infos DNS du serveur de BDD '%s'";
+App::$strings["Remote authentication blocked. You are logged into this site locally. Please logout and retry."] = "Authentification distante bloquée. Vous êtes connecté(e) sur ce site localement. Merci de vous déconnecter et réessayer.";
+App::$strings["Welcome %s. Remote authentication successful."] = "Bienvenue %s. L'authentification distante a fonctionné.";
+App::$strings["parent"] = "retour";
+App::$strings["Collection"] = "Groupe de contacts";
+App::$strings["Principal"] = "Principal";
+App::$strings["Addressbook"] = "Carnet d'adresse";
+App::$strings["Calendar"] = "Calendrier";
+App::$strings["Schedule Inbox"] = "Calendrier - Messages entrants";
+App::$strings["Schedule Outbox"] = "Calendrier - Messages sortants";
+App::$strings["Total"] = "Total";
+App::$strings["Shared"] = "Partagé";
+App::$strings["You are using %1\$s of your available file storage."] = "Vous utilisez %1\$s de votre espace de stockage.";
+App::$strings["You are using %1\$s of %2\$s available file storage. (%3\$s&#37;)"] = "Vous utilisez %1\$s sur %2\$s d'espace disponible. (%3\$s&#37;)";
+App::$strings["WARNING:"] = "AVERTISSEMENT&nbsp;:";
+App::$strings["Please use DAV to upload large (video, audio) files.<br>See <a class=\"zrl\" href=\"help/member/member_guide#Cloud_Desktop_Clients\">Cloud Desktop Clients</a>"] = "";
+App::$strings["Create new folder"] = "Nouveau dossier";
+App::$strings["Upload file"] = "Téléverser un fichier";
+App::$strings["Drop files here to immediately upload"] = "Mettez un fichier ici pour le télécharger immédiatement";
+App::$strings["Forums"] = "Forums";
App::$strings["Categories"] = "Catégories";
-App::$strings["Tags"] = "Étiquettes";
-App::$strings["Keywords"] = "Mots-clefs";
-App::$strings["have"] = "ont";
-App::$strings["has"] = "a";
-App::$strings["want"] = "veulent";
-App::$strings["wants"] = "veut";
-App::$strings["likes"] = "aime";
-App::$strings["dislikes"] = "n'aime pas";
-App::$strings["l F d, Y \\@ g:i A"] = "l d F Y \\à G\\hi";
-App::$strings["Starts:"] = "Début&nbsp;:";
-App::$strings["Finishes:"] = "Fin&nbsp;:";
-App::$strings["This event has been added to your calendar."] = "Cet évènement a été ajouté dans votre calendrier.";
-App::$strings["Not specified"] = "Non spécifié";
-App::$strings["Needs Action"] = "Besoin d'une action";
-App::$strings["Completed"] = "Terminé";
-App::$strings["In Process"] = "En cours";
-App::$strings["Cancelled"] = "Annulé";
-App::$strings["Cannot create a duplicate channel identifier on this system. Import failed."] = "L'import a échoué. Un canal existe déjà avec ce nom";
-App::$strings["Channel clone failed. Import failed."] = "Echec du clonage du canal. Echec de l'impot.";
-App::$strings["(Unknown)"] = "(Inconnu)";
-App::$strings["Visible to anybody on the internet."] = "Visible pour tout le monde sur internet.";
-App::$strings["Visible to you only."] = "Visible pour vous seulement.";
-App::$strings["Visible to anybody in this network."] = "Visible pour tout le monde sur ce réseau.";
-App::$strings["Visible to anybody authenticated."] = "Visible aux utilisateurs authentifiés.";
-App::$strings["Visible to anybody on %s."] = "Visible pour tous sur %s.";
-App::$strings["Visible to all connections."] = "Visible pour tous les contacts.";
-App::$strings["Visible to approved connections."] = "Visible aux contacts approuvés.";
-App::$strings["Visible to specific connections."] = "Visible pour certains contacts.";
-App::$strings["Privacy group is empty."] = "Groupe d'accès vide.";
-App::$strings["Privacy group: %s"] = "Groupe d'accès&nbsp;: %s";
-App::$strings["Connection not found."] = "Contact non trouvé.";
-App::$strings["profile photo"] = "photo de profil";
-App::$strings["No recipient provided."] = "Pas de destinataire.";
-App::$strings["[no subject]"] = "[sans objet]";
-App::$strings["Unable to determine sender."] = "Impossible de déterminer l'émetteur.";
-App::$strings["Stored post could not be verified."] = "Le message stocké n'a pas pu être vérifié.";
-App::$strings["prev"] = "préc.";
-App::$strings["first"] = "premier";
-App::$strings["last"] = "dernier";
-App::$strings["next"] = "Suivant";
-App::$strings["older"] = "plus ancien";
-App::$strings["newer"] = "plus récent";
-App::$strings["No connections"] = "Pas de relations.";
-App::$strings["View all %s connections"] = "Voir les %s contacts";
-App::$strings["poke"] = "tapoter";
-App::$strings["poked"] = "a tapoté";
-App::$strings["ping"] = "ping";
-App::$strings["pinged"] = "pingé";
-App::$strings["prod"] = "encourager";
-App::$strings["prodded"] = "encouragé";
-App::$strings["slap"] = "giffler";
-App::$strings["slapped"] = "gifflé(e)";
-App::$strings["finger"] = "pointer";
-App::$strings["fingered"] = "pointé";
-App::$strings["rebuff"] = "rejetter";
-App::$strings["rebuffed"] = "rejeté";
-App::$strings["happy"] = "heureux";
-App::$strings["sad"] = "triste";
-App::$strings["mellow"] = "mélancolique";
-App::$strings["tired"] = "fatigué";
-App::$strings["perky"] = "impertinent";
-App::$strings["angry"] = "en colère";
-App::$strings["stupefied"] = "stupéfait";
-App::$strings["puzzled"] = "perplexe";
-App::$strings["interested"] = "intéressé";
-App::$strings["bitter"] = "amer";
-App::$strings["cheerful"] = "plein d'entrain";
-App::$strings["alive"] = "vivant";
-App::$strings["annoyed"] = "agaçé";
-App::$strings["anxious"] = "anxieux";
-App::$strings["cranky"] = "énervé";
-App::$strings["disturbed"] = "perturbé";
-App::$strings["frustrated"] = "frustré";
-App::$strings["depressed"] = "déprimé";
-App::$strings["motivated"] = "motivé";
-App::$strings["relaxed"] = "détendu";
-App::$strings["surprised"] = "surpris";
-App::$strings["Monday"] = "Lundi";
-App::$strings["Tuesday"] = "Mardi";
-App::$strings["Wednesday"] = "Mercredi";
-App::$strings["Thursday"] = "Jeudi";
-App::$strings["Friday"] = "Vendredi";
-App::$strings["Saturday"] = "Samedi";
-App::$strings["Sunday"] = "Dimanche";
-App::$strings["January"] = "Janvier";
-App::$strings["February"] = "Février";
-App::$strings["March"] = "Mars";
-App::$strings["April"] = "Avril";
-App::$strings["May"] = "Mai";
-App::$strings["June"] = "Juin";
-App::$strings["July"] = "Juillet";
-App::$strings["August"] = "Août";
-App::$strings["September"] = "Septembre";
-App::$strings["October"] = "Octobre";
-App::$strings["November"] = "Novembre";
-App::$strings["December"] = "Décembre";
-App::$strings["Unknown Attachment"] = "Pièce jointe inconnue";
-App::$strings["unknown"] = "Inconnu";
-App::$strings["remove category"] = "supprimer la catégorie";
-App::$strings["remove from file"] = "retirer du fichier";
-App::$strings["default"] = "défaut";
-App::$strings["Page layout"] = "Mise en page";
-App::$strings["You can create your own with the layouts tool"] = "Créez les vôtres avec les outils de mise en page";
-App::$strings["Page content type"] = "Type de contenu de la page";
-App::$strings["Select an alternate language"] = "Choisir une langue alternative";
-App::$strings["activity"] = "activité";
-App::$strings["Design Tools"] = "Outils de conception";
-App::$strings["Pages"] = "Pages";
-App::$strings["System"] = "Système";
-App::$strings["New App"] = "";
-App::$strings["Suggestions"] = "Suggestions";
-App::$strings["See more..."] = "Voir plus...";
-App::$strings["You have %1$.0f of %2$.0f allowed connections."] = "Vous avez %1$.0f sur %2$.0f contacts autorisés.";
-App::$strings["Add New Connection"] = "Ajouter un nouveau contact";
-App::$strings["Enter channel address"] = "Saisissez l'adresse du canal";
-App::$strings["Examples: bob@example.com, https://example.com/barbara"] = "Exemples&nbsp;: pierre@exemple.com, https://exemple.com/sophie";
-App::$strings["Notes"] = "Notes";
-App::$strings["Remove term"] = "Retirer le terme";
-App::$strings["Saved Searches"] = "Recherches sauvegardées";
-App::$strings["add"] = "ajouter";
-App::$strings["Saved Folders"] = "Dossiers sauvegardés";
App::$strings["Everything"] = "Tout";
-App::$strings["Archives"] = "Archives";
-App::$strings["Refresh"] = "Actualiser";
-App::$strings["Account settings"] = "Paramètres du compte";
-App::$strings["Channel settings"] = "Paramètres du canal";
-App::$strings["Additional features"] = "Fonctionnalités supplémentaires";
-App::$strings["Feature/Addon settings"] = "Paramètres des extensions/greffons";
-App::$strings["Display settings"] = "Paramètres d'affichage";
-App::$strings["Manage locations"] = "";
-App::$strings["Export channel"] = "Exporter le canal";
-App::$strings["Connected apps"] = "Applications connectées";
-App::$strings["Premium Channel Settings"] = "Paramètres de canal VIP";
+App::$strings["Events Tools"] = "Outils Evènements";
+App::$strings["Export Calendar"] = "Exporter le calendrier";
+App::$strings["Import Calendar"] = "Importer un calendrier";
+App::$strings["Suggested Chatrooms"] = "Salons suggérés";
App::$strings["Private Mail Menu"] = "Menu des messages privés";
App::$strings["Combined View"] = "Vue combinée";
App::$strings["Inbox"] = "Boîte de réception";
App::$strings["Outbox"] = "Boîte d'envoi";
App::$strings["New Message"] = "Nouveau message";
+App::$strings["Chatrooms"] = "Salons de clavardage";
+App::$strings["Overview"] = "Aperçu";
+App::$strings["Rating Tools"] = "Outils d'évaluation";
+App::$strings["Rate Me"] = "M'évaluer";
+App::$strings["View Ratings"] = "Voir mes évaluations";
+App::$strings["__ctx:widget__ Activity"] = "";
+App::$strings["You have %1$.0f of %2$.0f allowed connections."] = "Vous avez %1$.0f sur %2$.0f contacts autorisés.";
+App::$strings["Add New Connection"] = "Ajouter un nouveau contact";
+App::$strings["Enter channel address"] = "Saisissez l'adresse du canal";
+App::$strings["Examples: bob@example.com, https://example.com/barbara"] = "Exemples&nbsp;: pierre@exemple.com, https://exemple.com/sophie";
+App::$strings["Wiki List"] = "Liste de wikis";
+App::$strings["Archives"] = "Archives";
App::$strings["Conversations"] = "Conversations";
App::$strings["Received Messages"] = "Messages reçus";
App::$strings["Sent Messages"] = "Messages envoyés";
App::$strings["No messages."] = "Pas de message.";
App::$strings["Delete conversation"] = "Supprimer la conversation";
-App::$strings["Events Menu"] = "Menu Evènements";
-App::$strings["Day View"] = "Vue Jour";
-App::$strings["Week View"] = "Vue Semaine";
-App::$strings["Month View"] = "Vue Mois";
-App::$strings["Events Tools"] = "Outils Evènements";
-App::$strings["Export Calendar"] = "Exporter le calendrier";
-App::$strings["Import Calendar"] = "Importer un calendrier";
-App::$strings["Chatrooms"] = "Salons de clavardage";
-App::$strings["Overview"] = "";
-App::$strings["Chat Members"] = "";
-App::$strings["Bookmarked Chatrooms"] = "Salons favoris";
-App::$strings["Suggested Chatrooms"] = "Salons suggérés";
+App::$strings["Chat Members"] = "Membres du salon de discussion";
App::$strings["photo/image"] = "photo/image";
-App::$strings["Click to show more"] = "Cliquer pour voir plus";
-App::$strings["Rating Tools"] = "Outils d'évaluation";
-App::$strings["Rate Me"] = "M'évaluer";
-App::$strings["View Ratings"] = "Voir mes évaluations";
-App::$strings["Forums"] = "Membres du forum";
+App::$strings["Remove term"] = "Retirer le terme";
+App::$strings["Saved Searches"] = "Recherches sauvegardées";
+App::$strings["add"] = "ajouter";
+App::$strings["Notes"] = "Notes";
+App::$strings["Wiki Pages"] = "Pages wiki";
+App::$strings["Add new page"] = "Ajouter une nouvelle page";
+App::$strings["Page name"] = "Nom de la page";
+App::$strings["Refresh"] = "Actualiser";
App::$strings["Tasks"] = "Tâches";
-App::$strings["Documentation"] = "Documentation";
-App::$strings["Project/Site Information"] = "Information sur le site/projet";
-App::$strings["For Members"] = "Pour les membres";
-App::$strings["For Administrators"] = "Pour les administrateurs";
-App::$strings["For Developers"] = "Pour les développeurs";
-App::$strings["Member registrations waiting for confirmation"] = "";
+App::$strings["Suggestions"] = "Suggestions";
+App::$strings["See more..."] = "Voir plus...";
+App::$strings["Saved Folders"] = "Dossiers sauvegardés";
+App::$strings["Click to show more"] = "Cliquer pour voir plus";
+App::$strings["Member registrations waiting for confirmation"] = "Inscriptions en attente d'approbation";
App::$strings["Inspect queue"] = "Analyser la file d'attente";
App::$strings["DB updates"] = "Mises à jour BDD";
App::$strings["Admin"] = "Administrateur";
App::$strings["Plugin Features"] = "Fonctionnalités des greffons";
-App::$strings["Channel is blocked on this site."] = "Ce canal est bloqué sur ce site.";
-App::$strings["Channel location missing."] = "Emplacement du canal introuvable.";
-App::$strings["Response from remote channel was incomplete."] = "La réponse du canal distant était incomplète.";
-App::$strings["Channel was deleted and no longer exists."] = "Le canal a été supprimé et n'existe plus.";
-App::$strings["Protocol disabled."] = "Protocole désactivé.";
-App::$strings["Channel discovery failed."] = "La tentative d'accéder au canal a échoué.";
-App::$strings["Cannot connect to yourself."] = "Ne peut pas se connecter à vous.";
-App::$strings["%1\$s's bookmarks"] = "Favoris de %1\$s";
-App::$strings["Public Timeline"] = "Fil public";
-App::$strings["Image/photo"] = "Image/photo";
-App::$strings["Encrypted content"] = "Contenu chiffré";
-App::$strings["Install %s element: "] = "Installer %s élément";
-App::$strings["This post contains an installable %s element, however you lack permissions to install it on this site."] = "Ce message contient un élément installable %s, mais vous n'avez pas l'autorisation de l'installer sur ce site.";
-App::$strings["%1\$s wrote the following %2\$s %3\$s"] = "%1\$s a écrit %2\$s qui suit %3\$s";
-App::$strings["Click to open/close"] = "Cliquer pour ouvrir/fermer";
-App::$strings["spoiler"] = "";
-App::$strings["Different viewers will see this text differently"] = "Ce texte aura un rendu différent en fonction des utilisateurs";
-App::$strings["$1 wrote:"] = "$1 a écrit&nbsp;:";
-App::$strings["Directory Options"] = "Options d'annuaire";
-App::$strings["Safe Mode"] = "Mode sûr";
-App::$strings["Public Forums Only"] = "Les forums publics uniquement";
-App::$strings["This Website Only"] = "Ce site uniquement";
-App::$strings["The form security token was not correct. This probably happened because the form has been opened for too long (>3 hours) before submitting it."] = "Le formulaire n'est plus sécurisé, probablement parce qu'il est ouvert depuis trop longtemps (plus de 3 heures).";
+App::$strings["Account settings"] = "Paramètres du compte";
+App::$strings["Channel settings"] = "Paramètres du canal";
+App::$strings["Additional features"] = "Fonctionnalités supplémentaires";
+App::$strings["Feature/Addon settings"] = "Paramètres des extensions/greffons";
+App::$strings["Display settings"] = "Paramètres d'affichage";
+App::$strings["Manage locations"] = "Gérer les emplacements";
+App::$strings["Export channel"] = "Exporter le canal";
+App::$strings["Connected apps"] = "Applications connectées";
+App::$strings["Permission Groups"] = "Groupes d'autorisation";
+App::$strings["Premium Channel Settings"] = "Paramètres de canal VIP";
+App::$strings["Bookmarked Chatrooms"] = "Salons favoris";
+App::$strings["Source channel not found."] = "Source du canal introuvable.";
+App::$strings["__ctx:opensearch__ Search %1\$s (%2\$s)"] = "Recherche %1\$s (%2\$s)";
+App::$strings["__ctx:opensearch__ \$Projectname"] = "\$Projectname";
+App::$strings["Create an account to access services and applications"] = "Créer un compte pour accéder aux services et applications";
App::$strings["Logout"] = "Déconnexion";
-App::$strings["End this session"] = "Mettre fin à la session";
-App::$strings["Home"] = "Mon canal";
-App::$strings["Your posts and conversations"] = "Vos publications et conversations";
-App::$strings["Your profile page"] = "Votre profil";
-App::$strings["Manage/Edit profiles"] = "Gérer/modifier les profils";
+App::$strings["Login/Email"] = "pseudo / email";
+App::$strings["Password"] = "Mot de passe";
+App::$strings["Remember me"] = "Se souvenir de moi";
+App::$strings["Forgot your password?"] = "Mot de passe oublié&nbsp;?";
+App::$strings["toggle mobile"] = "(dés)activer mobile";
+App::$strings["[\$Projectname] Website SSL error for %s"] = "";
+App::$strings["Website SSL certificate is not valid. Please correct."] = "Le certificat SSL n'est pas valide. Corrigez le.";
+App::$strings["[\$Projectname] Cron tasks not running on %s"] = "";
+App::$strings["Cron/Scheduled tasks not running."] = "Les taches planifiées ne tournent pas.";
+App::$strings["never"] = "jamais";
+App::$strings["Focus (Hubzilla default)"] = "Focus (par défaut pour Hubzilla)";
+App::$strings["Theme settings"] = "Paramètres du thème";
+App::$strings["Narrow navbar"] = "Barre de navigation fine";
+App::$strings["Navigation bar background color"] = "Couleur de fond de la barre de navigation";
+App::$strings["Navigation bar icon color "] = "Couleur des icônes de la barre de navigation";
+App::$strings["Navigation bar active icon color "] = "Couleur de l'icône active de la barre de navigation";
+App::$strings["Link color"] = "";
+App::$strings["Set font-color for banner"] = "Définir la couleur du texte de la bannière";
+App::$strings["Set the background color"] = "Définir la couleur d'arrière-plan";
+App::$strings["Set the background image"] = "Définir l'image d'arrière-plan";
+App::$strings["Set the background color of items"] = "Définir la couleur de fond des contributions";
+App::$strings["Set the background color of comments"] = "Couleur de fond des commentaires";
+App::$strings["Set font-size for the entire application"] = "Définir la taille de police pour l'application entière";
+App::$strings["Examples: 87.5%, 14px"] = "";
+App::$strings["Set font-color for posts and comments"] = "Définir la couleur de police pour les contributions et commentaires";
+App::$strings["Set radius of corners"] = "Définir le rayon des arrondis";
+App::$strings["Example: 4px"] = "";
+App::$strings["Set shadow depth of photos"] = "Définir la profondeur de l'ombre des photos";
+App::$strings["Set maximum width of content region in pixel"] = "Définir la largeur maximale de la zone des contenus";
+App::$strings["Leave empty for default width"] = "Laissez vide pour avoir la largeur par défaut";
+App::$strings["Left align page content"] = "Aligner à gauche le contenu de la page";
+App::$strings["Set size of conversation author photo"] = "Définir la taille de la photo de l'auteur d'une conversation";
+App::$strings["Set size of followup author photos"] = "Définir la taille de la photo de l'auteur d'une réponse";
+App::$strings["Errors encountered deleting database table "] = "Des erreurs ont eu lieu lors de la suppression de la table de la base de données.";
+App::$strings["Submit Settings"] = "Emvoyer les paramètres";
+App::$strings["Drop tables when uninstalling?"] = "Lors de la désinstallation, purger les tables?";
+App::$strings["If checked, the Rendezvous database tables will be deleted when the plugin is uninstalled."] = "Si cette case est cochée, les tables de la base Rendezvous seront supprimées lorsque le plugin sera désinstallé.";
+App::$strings["Mapbox Access Token"] = "Jeton d'accès à la mapbox.";
+App::$strings["If you enter a Mapbox access token, it will be used to retrieve map tiles from Mapbox instead of the default OpenStreetMap tile server."] = "Si vous entrez un jeton d'accès Mapbox, il doit être utilisé pour récupérer les cartes à partir de Mapbox au lieu du serveur par défaut OpenStreetMap.";
+App::$strings["Rendezvous"] = "Rendezvous";
+App::$strings["This identity has been deleted by another member due to inactivity. Please press the \"New identity\" button or refresh the page to register a new identity. You may use the same name."] = "Cette identité a été supprimée par un autre membre en raison de l'inactivité. Appuyez sur le bouton \"Nouvelle identité\" ou actualisez la page pour enregistrer une nouvelle identité. Vous pouvez utiliser le même nom.";
+App::$strings["Welcome to Rendezvous!"] = "Bienvenue dans Rendevzvous!";
+App::$strings["Enter your name to join this rendezvous. To begin sharing your location with the other members, tap the GPS control. When your location is discovered, a red dot will appear and others will be able to see you on the map."] = "Entrez votre nom pour rejoindre ce rendez-vous. Pour commencer à partager votre emplacement avec les autres membres, appuyez sur le contrôle GPS. Lorsque votre emplacement est découvert, un point rouge apparaîtra et les autres seront en mesure de vous voir sur la carte.";
+App::$strings["Let's meet here"] = "Rencontrez-vous ici";
+App::$strings["New marker"] = "Nouveau marqueur";
+App::$strings["Edit marker"] = "Éditer le marqueur";
+App::$strings["New identity"] = "Nouvelle identité";
+App::$strings["Delete marker"] = "Supprimer le marqueur";
+App::$strings["Delete member"] = "Supprimer le membre";
+App::$strings["Edit proximity alert"] = "Éditer l'alerte de proximité";
+App::$strings["A proximity alert will be issued when this member is within a certain radius of you.<br><br>Enter a radius in meters (0 to disable):"] = "Une alerte de proximité sera émise lorsque ce membre se trouve dans un certain périmètre autour de vous. Entrer un rayon en mètres (0 pour désactiver):";
+App::$strings["distance"] = "distance";
+App::$strings["Proximity alert distance (meters)"] = "Distance d'alerte de proximité (mètres)";
+App::$strings["A proximity alert will be issued when you are within a certain radius of the marker location.<br><br>Enter a radius in meters (0 to disable):"] = "Une alerte de proximité sera déclenchée quand vous serez à une certaine distance du marqueur d'emplacement.<br><br>Indiquez une distance en mètres (0 pour désactiver)&nbsp;:";
+App::$strings["Marker proximity alert"] = "Alerte de proximité de marqueur";
+App::$strings["Reminder note"] = "Note de rappel";
+App::$strings["Enter a note to be displayed when you are within the specified proximity..."] = "Saisissez une note à afficher quand vous serez à la distance indiquée...";
+App::$strings["Add new rendezvous"] = "Ajouter un nouveau rendezvous";
+App::$strings["Create a new rendezvous and share the access link with those you wish to invite to the group. Those who open the link become members of the rendezvous. They can view other member locations, add markers to the map, or share their own locations with the group."] = "Créez un nouveau rendez-vous et partagez le lien d'accès avec les gens que vous souhaitez inviter au groupe. Ceux qui ouvrent le lien deviennent membres du rendez-vous. Ils peuvent afficher les emplacements des autres membres, ajouter des marqueurs à la carte ou partager leurs propres emplacements avec le groupe.";
+App::$strings["Some setting"] = "Un certain paramètre";
+App::$strings["A setting"] = "Un paramètre";
+App::$strings["Skeleton Settings"] = "Paramètres du squelette";
+App::$strings["GNU-Social Protocol Settings updated."] = "";
+App::$strings["Enable the GNU-Social protocol for this channel"] = "";
+App::$strings["GNU-Social Protocol Settings"] = "";
+App::$strings["Follow"] = "";
+App::$strings["%1\$s is now following %2\$s"] = "";
+App::$strings["INVALID EVENT DISMISSED!"] = "ÉVÉNEMENT INVALIDE REJETÉ!";
+App::$strings["Summary: "] = "Sommaire :";
+App::$strings["Date: "] = "Date :";
+App::$strings["Reason: "] = "Raison :";
+App::$strings["INVALID CARD DISMISSED!"] = "ÉVÉNEMENT INVALIDE REJETÉ!";
+App::$strings["Name: "] = "Nom :";
+App::$strings["You have to enable this plugin in Feature/Addon Settings > CalDAV/CardDAV Settings before you can use it."] = "Vous avez activé ce plugin dans Fonctionalités/Paramètres des extensions > CalDAV/CardDAV Paramètres avant que vous puissiez l'utiliser.";
+App::$strings["Example: YYYY-MM-DD HH:mm"] = "Exemple : YYYY-MM-DD HH:mm";
+App::$strings["End date and time"] = "Date et heure de fin";
+App::$strings["List month"] = "Liste mois";
+App::$strings["List week"] = "Liste semaine";
+App::$strings["List day"] = "Liste jour";
+App::$strings["More"] = "Plus";
+App::$strings["Less"] = "Moins";
+App::$strings["Select calendar"] = "Sélectionner un calendrier";
+App::$strings["Delete all"] = "Tout supprimer";
+App::$strings["Sorry! Editing of recurrent events is not yet implemented."] = "Désolé ! L'édition d'événements récurrents n'est pas encore implémenté.";
+App::$strings["Errors encountered creating database table: "] = "Des erreurs se sont produites lors de la création de la table de la base de données :";
+App::$strings["Default Calendar"] = "Agenda par défaut";
+App::$strings["Default Addressbook"] = "Carnet d'adresses par défaut";
+App::$strings["CalDAV/CardDAV Settings saved."] = "Les paramètres CalDAV/CardDAV ont été sauvegardés.";
+App::$strings["Enable CalDAV/CardDAV Server for this channel"] = "Activer le serveur CalDAV/CardDAV pour ce canal";
+App::$strings["Your CalDAV resources are located at %s "] = "Vos ressources CalDAV sont situées à %s";
+App::$strings["Your CardDAV resources are located at %s "] = "Vos ressources CardDAV sont situées à %s";
+App::$strings["CalDAV/CardDAV Settings"] = "Paramètres CalDAV/CardDAV";
+App::$strings["Home, Voice"] = "Domicile, Voix";
+App::$strings["Home, Fax"] = "Domicile, Fax";
+App::$strings["Work, Voice"] = "Travail, Voix";
+App::$strings["Work, Fax"] = "Travail, Fax";
+App::$strings["Select Channel"] = "Sélectionner un canal";
+App::$strings["Read-write"] = "Lire et écrire";
+App::$strings["Read-only"] = "Lire uniquement";
+App::$strings["My Calendars"] = "Mes agendas";
+App::$strings["Shared Calendars"] = "Agendas partagés";
+App::$strings["Share this calendar"] = "Partager cet agenda";
+App::$strings["Calendar name and color"] = "Nom et couleur de l'agenda";
+App::$strings["Create new calendar"] = "Créer un nouvel agenda";
+App::$strings["Calendar Name"] = "Nom de l'agenda";
+App::$strings["Calendar Tools"] = "Outils pour les agendas";
+App::$strings["Import calendar"] = "Importer un agenda";
+App::$strings["Select a calendar to import to"] = "Sélectionner un agenda à importer dans";
+App::$strings["Addressbooks"] = "Carnet d'adresses";
+App::$strings["Addressbook name"] = "Nom du carnet d'adresses";
+App::$strings["Create new addressbook"] = "Créer un nouveau carnet d'adresses";
+App::$strings["Addressbook Name"] = "Nom du carnet d'adresses";
+App::$strings["Addressbook Tools"] = "Outils pour les carnets d'adresses";
+App::$strings["Import addressbook"] = "Importer un carnet d'adresses";
+App::$strings["Select an addressbook to import to"] = "Sélectionner un carnet d'adresses à importer dans";
+App::$strings["Planets Settings updated."] = "Paramètres Planets mis à jour.";
+App::$strings["Enable Planets Plugin"] = "Activer le plugin Planets";
+App::$strings["Planets Settings"] = "Paramètres Planets";
+App::$strings["System defaults:"] = "Paramètres par défaut du système :";
+App::$strings["Preferred Clipart IDs"] = "ID Clipart préférées";
+App::$strings["List of preferred clipart ids. These will be shown first."] = "Liste des ids clipart préférése. Celles-ci seront montrées en premier.";
+App::$strings["Default Search Term"] = "Terme de recherche par défaut";
+App::$strings["The default search term. These will be shown second."] = "Le terme de recherche par défaut. Ceci sera affiché en second.";
+App::$strings["Return After"] = "Retourner ensuite";
+App::$strings["Page to load after image selection."] = "Page à afficher après la sélection de l'image.";
App::$strings["Edit Profile"] = "Éditeur de profil";
-App::$strings["Edit your profile"] = "Modifier votre profil";
-App::$strings["Your photos"] = "Vos photos";
-App::$strings["Your files"] = "Vos fichiers";
-App::$strings["Your chatrooms"] = "Vos salons";
-App::$strings["Bookmarks"] = "Favoris";
-App::$strings["Your bookmarks"] = "Vos favoris";
-App::$strings["Your webpages"] = "Vos pages web";
-App::$strings["Sign in"] = "Connexion";
-App::$strings["%s - click to logout"] = "%s - cliquer ici pour déconnecter";
-App::$strings["Remote authentication"] = "Authentification distante";
-App::$strings["Click to authenticate to your home hub"] = "S'authentifier auprès de votre hub principal";
-App::$strings["Home Page"] = "Page d'accueil";
-App::$strings["Create an account"] = "Créer un compte";
-App::$strings["Help and documentation"] = "Aide et documentation";
-App::$strings["Applications, utilities, links, games"] = "Applications, utilitaires, liens, jeux";
-App::$strings["Search site @name, #tag, ?docs, content"] = "Recherche @nom, #tag, contenu";
-App::$strings["Channel Directory"] = "Annuaire des canaux";
-App::$strings["Your grid"] = "Votre réseau";
-App::$strings["Mark all grid notifications seen"] = "Marquer toutes les notifications du réseau comme vues";
-App::$strings["Channel home"] = "Mon canal";
-App::$strings["Mark all channel notifications seen"] = "Marquer toutes les notifications du canal comme vues";
-App::$strings["Notices"] = "Notifications";
-App::$strings["Notifications"] = "Notifications";
-App::$strings["See all notifications"] = "Voir toutes les notifications";
-App::$strings["Private mail"] = "Messages privés";
-App::$strings["See all private messages"] = "Voir tous les messages privés";
-App::$strings["Mark all private messages seen"] = "Marquer tous les messages privés comme vus";
-App::$strings["Event Calendar"] = "Calendrier des événements";
-App::$strings["See all events"] = "Voir tous les événements";
-App::$strings["Mark all events seen"] = "Marquer tous les événements comme vus";
-App::$strings["Manage Your Channels"] = "Gérer vos canaux";
-App::$strings["Account/Channel Settings"] = "Paramètres du Compte/Canal";
-App::$strings["Site Setup and Configuration"] = "Configuration du site";
-App::$strings["Loading..."] = "Chargement...";
-App::$strings["@name, #tag, ?doc, content"] = "@nom, #étiquette, ?doc, contenu";
-App::$strings["Please wait..."] = "Merci de patienter...";
-App::$strings["New window"] = "Nouvelle fenêtre";
-App::$strings["Open the selected location in a different window or browser tab"] = "Ouvrir l'emplacement dans une fenêtre ou un onglet différent";
-App::$strings["User '%s' deleted"] = "Utilisateur '%s' supprimé";
-App::$strings["%d invitation available"] = array(
- 0 => "%d invitation disponible",
- 1 => "%d invitations disponibles",
-);
-App::$strings["Find Channels"] = "Trouver des canaux";
-App::$strings["Enter name or interest"] = "Saisir nom ou centre d'intérêt";
-App::$strings["Connect/Follow"] = "Ajouter/Suivre";
-App::$strings["Examples: Robert Morgenstein, Fishing"] = "Exemples: Guillaume Martin, Course à pieds";
-App::$strings["Random Profile"] = "Un profil au hasard";
-App::$strings["Invite Friends"] = "Inviter des amis";
-App::$strings["Advanced example: name=fred and country=iceland"] = "Exemple avancé&nbsp;: name=fred and country=iceland";
-App::$strings["%d connection in common"] = array(
- 0 => "%d contact en commun",
- 1 => "%d contacts en commun",
-);
-App::$strings["show more"] = "montrer plus";
+App::$strings["Profile List"] = "Liste de profil";
+App::$strings["Order of Preferred"] = "Tri selon les préférences";
+App::$strings["Sort order of preferred clipart ids."] = "Ordre de tri des ids de clipart préférés.";
+App::$strings["Newest first"] = "Les plus récents en premier";
+App::$strings["As entered"] = "Comme entrés";
+App::$strings["Order of other"] = "Tri selon autre";
+App::$strings["Sort order of other clipart ids."] = "Ordre de tri des autres clipart ids.";
+App::$strings["Most downloaded first"] = "Les plus téléchargés en premier";
+App::$strings["Most liked first"] = "Les plus aimés en premier";
+App::$strings["Preferred IDs Message"] = "IDs des messages préférés";
+App::$strings["Message to display above preferred results."] = "Message à afficher au-dessus de la liste des résultats préférés.";
+App::$strings["Uploaded by: "] = "Téléversé par :";
+App::$strings["Drawn by: "] = "Dessiné par :";
+App::$strings["Or select from a free OpenClipart.org image:"] = "ou sélectionner une image libre d'OpenClipart.org :";
+App::$strings["Search Term"] = "Terme de recherche";
+App::$strings["Unknown error. Please try again later."] = "Erreur inconnue. Veuillez essayer à nouveau plus tard.";
+App::$strings["Profile photo updated successfully."] = "Photo de profil actualisée avec succès.";
+App::$strings["Flag Adult Photos"] = "Photo pour adulte";
+App::$strings["Provide photo edit option to hide inappropriate photos from default album view"] = "Fourni l'option d'édition d'une photo afin de cacher des photos inappropriées de la vue d''album par défaut";
+App::$strings["Post to WordPress"] = "Publier sur Wordpress";
+App::$strings["Enable WordPress Post Plugin"] = "Activer l'extension de publication WordPress";
+App::$strings["WordPress username"] = "Identifiant de connexion WordPress";
+App::$strings["WordPress password"] = "Mot de passe de connexion WordPress";
+App::$strings["WordPress API URL"] = "URL de l'API WordPress";
+App::$strings["Typically https://your-blog.tld/xmlrpc.php"] = "Typiquement https://your-blog.tld/xmlrpc.php";
+App::$strings["WordPress blogid"] = "ID de votre blog WordPress";
+App::$strings["For multi-user sites such as wordpress.com, otherwise leave blank"] = "Pour les sites multi-utilisateurs comme wordpress.com, sinon laisser vide";
+App::$strings["Post to WordPress by default"] = "Par défaut, publier sur WordPress";
+App::$strings["Forward comments (requires hubzilla_wp plugin)"] = "Transférer les commentaires (nécessite le plugin hubzila_wp)";
+App::$strings["WordPress Post Settings"] = "Paramètres de publications WordPress";
+App::$strings["Wordpress Settings saved."] = "Les paramètres WordPress ont été sauvegardés.";
+App::$strings["This plugin looks in posts for the words/text you specify below, and collapses any content containing those keywords so it is not displayed at inappropriate times, such as sexual innuendo that may be improper in a work setting. It is polite and recommended to tag any content containing nudity with #NSFW. This filter can also match any other word/text you specify, and can thereby be used as a general purpose content filter."] = "Ce plugin cherche dans les publications les mots/textes que vous spécifiez ci-dessous, et réduit tout contenu contenant ces mots-clés afin qu'ils ne s'affichent pas à des moments inappropriés, tels que les insinuations sexuelles qui peuvent être inappropriées dans un contexte de travail. Il est poli et recommandé de marquer tout contenu contenant de la nudité avec #NSFW. Ce filtre peut également correspondre à tout autre mot/texte que vous spécifiez et peut ainsi être utilisé comme un filtre de contenu à usage général.";
+App::$strings["Enable Content filter"] = "Activer le filtrage des contenus";
+App::$strings["Comma separated list of keywords to hide"] = "Liste séparée par des virgules des mots-clés à cacher";
+App::$strings["Word, /regular-expression/, lang=xx, lang!=xx"] = "Mot, /expression-régulière/, lang=xx, lang!=xx";
+App::$strings["Not Safe For Work Settings"] = "Paramètres NSFW (Not Safe For Work)";
+App::$strings["General Purpose Content Filter"] = "Filtre de contenu sujet général";
+App::$strings["NSFW Settings saved."] = "Paramètres NSFW sauvegardés.";
+App::$strings["Possible adult content"] = "Contenu pour adulte probable";
+App::$strings["%s - view"] = "";
+App::$strings["Post to Insanejournal"] = "Publier sur InsaneJournal";
+App::$strings["Enable InsaneJournal Post Plugin"] = "Activer le plugin de publication InsaneJournal";
+App::$strings["InsaneJournal username"] = "Identifiant InsaneJournal";
+App::$strings["InsaneJournal password"] = "Mot de passe InsaneJournal";
+App::$strings["Post to InsaneJournal by default"] = "Par défaut, publier dans InsaneJournal";
+App::$strings["InsaneJournal Post Settings"] = "Paramètres de publication de InsaneJournal";
+App::$strings["Insane Journal Settings saved."] = "Les paramètres d'InsaneJournal ont été sauvegardés";
+App::$strings["Upload a file"] = "Téléverser un fichier";
+App::$strings["Drop files here to upload"] = "Glisser les fichiers ici pour téléversement";
+App::$strings["Failed"] = "Échec";
+App::$strings["No files were uploaded."] = "Aucun fichier n'a été téléversé.";
+App::$strings["Uploaded file is empty"] = "Le fichier téléversé est vide";
+App::$strings["Image exceeds size limit of "] = "L'image excède la taille limite de";
+App::$strings["File has an invalid extension, it should be one of "] = "L'extension du fichier est invalide, elle doit être l'une des suivantes";
+App::$strings["Upload was cancelled, or server error encountered"] = "Le téléversement a été annulé, ou le serveur a rencontré une erreur";
+App::$strings["Post to Dreamwidth"] = "Publier sur Dreamwidth";
+App::$strings["Enable Dreamwidth Post Plugin"] = "Activer le plugin de publication Dreamwidth";
+App::$strings["Dreamwidth username"] = "Nom d'utilisateur Dreamwidth";
+App::$strings["Dreamwidth password"] = "Mot de passe Dreamwidth";
+App::$strings["Post to Dreamwidth by default"] = "Publication avec Dreamwidth par défaut";
+App::$strings["Dreamwidth Post Settings"] = "Paramètres de publication Dreamwidth";
+App::$strings["Install Firefox Sharing Tools"] = "Installer Firefox Sharing Tools";
+App::$strings["Share content from Firefox to \$Projectname"] = "Partager du contenu depuis Firefox avec \$Projectname";
+App::$strings["Install Firefox Sharing Tools to this web browser"] = "Installer Firefox Sharing Tools sur ce navigateur";
+App::$strings["Hubzilla Directory Stats"] = "Statistiques de l'annuaire Hubzilla";
+App::$strings["Total Hubs"] = "Total de Hubs";
+App::$strings["Hubzilla Hubs"] = "Hubs Hubzilla";
+App::$strings["Friendica Hubs"] = "Hubs Friendica";
+App::$strings["Diaspora Pods"] = "Pods Diaspora";
+App::$strings["Hubzilla Channels"] = "Canaux Hubzilla";
+App::$strings["Friendica Channels"] = "Canaux Friendica";
+App::$strings["Diaspora Channels"] = "Canaux Diaspora";
+App::$strings["Aged 35 and above"] = "Âgé de 35 ans et plus";
+App::$strings["Aged 34 and under"] = "Âgé de 34 et moins";
+App::$strings["Average Age"] = "Âge moyen";
+App::$strings["Known Chatrooms"] = "Salons de discussion connus";
+App::$strings["Known Tags"] = "Étiquettes connues";
+App::$strings["Please note Diaspora and Friendica statistics are merely those **this directory** is aware of, and not all those known in the network. This also applies to chatrooms,"] = "Veuillez noter que les statistiques de Diaspora et Friendica sont simplement celles dont **ce répertoire** est au courant, et pas toutes celles connues dans le réseau. Cela s'applique également aux salles de discussion,";
+App::$strings["Email notification hub"] = "Notification par mail du hub";
+App::$strings["Hostname"] = "Nom d'hôte";
+App::$strings["Mailhost Settings"] = "Paramètres mail de l'hôte";
+App::$strings["MAILHOST Settings saved."] = "Paramètres mail de l'hôte sauvegardés.";
+App::$strings["Your Webbie:"] = "Vous êtes Webbie :";
+App::$strings["Fontsize (px):"] = "Taille de la police (px) :";
+App::$strings["Link:"] = "Lien :";
+App::$strings["Like us on Hubzilla"] = "Aimez-nous sur Hubzilla";
+App::$strings["Embed:"] = "Embarqué :";
+App::$strings["Photos imported"] = "Photos importées";
+App::$strings["Redmatrix Photo Album Import"] = "Import de l'album photo Redmatrix";
+App::$strings["This will import all your Redmatrix photo albums to this channel."] = "Ceci va importer l'intégralité de vos albums photos Redmatrix dans ce canal.";
+App::$strings["Redmatrix Server base URL"] = "URL de base du serveur Redmatrix";
+App::$strings["Redmatrix Login Username"] = "Identifiant de connexion Redmatrix";
+App::$strings["Redmatrix Login Password"] = "Mot de passe de connexion Redmatrix";
+App::$strings["Import just this album"] = "Importer uniquement cet album";
+App::$strings["Leave blank to import all albums"] = "Laisser vide pour importer tous les albums";
+App::$strings["Maximum count to import"] = "Nombre maximum de comptes à importer";
+App::$strings["0 or blank to import all available"] = "0 ou vide pour importer tout ce qui est disponible";
+App::$strings["Channels to auto connect"] = "Canaux à connecter automatiqument";
+App::$strings["Comma separated list"] = "Liste séparée par des virgules";
+App::$strings["Popular Channels"] = "Canaux populaires";
+App::$strings["IRC Settings"] = "Paramètres IRC";
+App::$strings["IRC settings saved."] = "Paramètres IRC sauvegardés";
+App::$strings["IRC Chatroom"] = "Salon de discussion IRC";
+App::$strings["Post to LiveJournal"] = "Publier sur LiveJournal";
+App::$strings["Enable LiveJournal Post Plugin"] = "Activer le plugin de publication LiveJournal";
+App::$strings["LiveJournal username"] = "Identifiant LiveJournal";
+App::$strings["LiveJournal password"] = "Mot de passe LiveJournal";
+App::$strings["Post to LiveJournal by default"] = "Par défaut, publier sur LiveJournal";
+App::$strings["LiveJournal Post Settings"] = "Paramètres de publication LiveJournal";
+App::$strings["LiveJournal Settings saved."] = "Paramètres LiveJournal sauvegardés.";
+App::$strings["We encountered a problem while logging in with the OpenID you provided. Please check the correct spelling of the ID."] = "Nous avons rencontrons un problème lors de l'identification avec l'OpenID que vous avez fournie. Veuillez vérifier que vous avez correctement écrit votre ID.";
+App::$strings["The error message was:"] = "Le message d'erreur était :";
+App::$strings["First Name"] = "Prénom";
+App::$strings["Last Name"] = "Nom";
+App::$strings["Nickname"] = "Surnom";
+App::$strings["Full Name"] = "Nom complet";
+App::$strings["Profile Photo 16px"] = "Photo de profil 16px";
+App::$strings["Profile Photo 32px"] = "Photo de profil 32px";
+App::$strings["Profile Photo 48px"] = "Photo de profil 48px";
+App::$strings["Profile Photo 64px"] = "Photo de profil 64px";
+App::$strings["Profile Photo 80px"] = "Photo de profil 80px";
+App::$strings["Profile Photo 128px"] = "Photo de profil 128px";
+App::$strings["Timezone"] = "Fuseau horaire";
+App::$strings["Birth Year"] = "Années de naissance";
+App::$strings["Birth Month"] = "Mois de naissance";
+App::$strings["Birth Day"] = "Jour de naissance";
+App::$strings["Birthdate"] = "Date de naissance";
+App::$strings["OpenID protocol error. No ID returned."] = "Erreur du protocole OpenID. Aucune ID trouvée.";
+App::$strings["Login failed."] = "Échec de la connexion.";
+App::$strings["Male"] = "Homme";
+App::$strings["Female"] = "Femme";
+App::$strings["You're welcome."] = "Bienvenue.";
+App::$strings["Ah shucks..."] = "Ah m…";
+App::$strings["Don't mention it."] = "De rien.";
+App::$strings["&lt;blush&gt;"] = "&lt;rougit&gt;";
+App::$strings["Page to load after login"] = "Page à charger après l'identification";
+App::$strings["Examples: &quot;apps&quot;, &quot;network?f=&gid=37&quot; (privacy collection), &quot;channel&quot; or &quot;notifications/system&quot; (leave blank for default network page (grid)."] = "Exemples: &quot;apps&quot;, &quot;network?f=&gid=37&quot; (privacy collection), &quot;channel&quot; or &quot;notifications/system&quot; (laisser vide pour la page par défaut du réseau (grille).";
+App::$strings["Startpage Settings"] = "Paramètres de la page de démarrage";
+App::$strings["bitchslap"] = "giffler";
+App::$strings["bitchslapped"] = "gifflé(e)";
+App::$strings["shag"] = "baiser";
+App::$strings["shagged"] = "baisé";
+App::$strings["patent"] = "breveté";
+App::$strings["patented"] = "être breveté";
+App::$strings["hug"] = "étreindre";
+App::$strings["hugged"] = "être étreint";
+App::$strings["murder"] = "assassiner";
+App::$strings["murdered"] = "être assassiné";
+App::$strings["worship"] = "vénérer";
+App::$strings["worshipped"] = "être vénéré";
+App::$strings["kiss"] = "embrasser";
+App::$strings["kissed"] = "embrassé";
+App::$strings["tempt"] = "tenter";
+App::$strings["tempted"] = "tenté";
+App::$strings["raise eyebrows at"] = "soulever les sourcils à la vue de";
+App::$strings["raised their eyebrows at"] = "sourcils soulevés à la vue de";
+App::$strings["insult"] = "insulter";
+App::$strings["insulted"] = "insulté";
+App::$strings["praise"] = "louer";
+App::$strings["praised"] = "loué";
+App::$strings["be dubious of"] = "douter de";
+App::$strings["was dubious of"] = "avoir douté de";
+App::$strings["eat"] = "manger";
+App::$strings["ate"] = "a mangé";
+App::$strings["giggle and fawn at"] = "séduire, charmer";
+App::$strings["giggled and fawned at"] = "séduit(e), charmé(e)";
+App::$strings["doubt"] = "doute";
+App::$strings["doubted"] = "a douté";
+App::$strings["glare"] = "jeter un regard";
+App::$strings["glared at"] = "a jeté un regard à ";
+App::$strings["fuck"] = "baiser";
+App::$strings["fucked"] = "être baisé";
+App::$strings["bonk"] = "baiser";
+App::$strings["bonked"] = "baisé(e)";
+App::$strings["declare undying love for"] = "Déclarer un amour éternel pour";
+App::$strings["declared undying love for"] = "A déclaré l'amour éternel pour";
+App::$strings["Diaspora Protocol Settings updated."] = "";
+App::$strings["Enable the Diaspora protocol for this channel"] = "";
+App::$strings["Allow any Diaspora member to comment on your public posts"] = "";
+App::$strings["Prevent your hashtags from being redirected to other sites"] = "";
+App::$strings["Followed hashtags (comma separated, do not include the #)"] = "";
+App::$strings["Diaspora Protocol Settings"] = "";
+App::$strings["No username found in import file."] = "";
+App::$strings["Unable to create a unique channel address. Import failed."] = "Impossible de créer une adresse de canal unique. Echec de l'import.";
+App::$strings["Error retrieving wiki"] = "Erreur lors de la récupération du wiki";
+App::$strings["Error creating zip file export folder"] = "Erreur lors de la création du dossier d'exportation du fichier zip";
+App::$strings["Error downloading wiki: "] = "Erreur lors du téléchargement du wiki:";
+App::$strings["Your account on %s will expire in a few days."] = "Votre compte sur %s expirera dans quelques jours.";
+App::$strings["Your $Productname test account is about to expire."] = "Votre compte de test $NomDeProduit est sur le point d'expirer.";
+App::$strings["Enable Rainbowtag"] = "Activer Rainbowtag";
+App::$strings["Rainbowtag Settings"] = "Paramètres Rainbowtag";
+App::$strings["Rainbowtag Settings saved."] = "Paramètres Rainbowtag sauvegardés.";
+App::$strings["Show Upload Limits"] = "Afficher les limites de débit ascendant (upload)";
+App::$strings["Hubzilla configured maximum size: "] = "Taille maximale configurée par Hubzilla:";
+App::$strings["PHP upload_max_filesize: "] = "PHP upload_max_filesize: ";
+App::$strings["PHP post_max_size (must be larger than upload_max_filesize): "] = "PHP post_max_size (must be larger than upload_max_filesize): ";
+App::$strings["Recent Channel/Profile Viewers"] = "Visiteurs récents du canal/profil";
+App::$strings["This plugin/addon has not been configured."] = "Cette extension n'a pas été configurée.";
+App::$strings["Please visit the Visage settings on %s"] = "Veuillez visiter les paramètres de Visage sur %s";
+App::$strings["your feature settings page"] = "La page des paramètres de vos fonctionnalités";
+App::$strings["No entries."] = "Aucune entrée.";
+App::$strings["Enable Visage Visitor Logging"] = "Activer la connexion Visage Visitor";
+App::$strings["Visage Settings"] = "Paramètres Visage";
+App::$strings["Nsabait Settings updated."] = "Les paramètres Nsabait ont été enregistrés.";
+App::$strings["Enable NSAbait Plugin"] = "Activer le plugin NSAbait";
+App::$strings["NSAbait Settings"] = "Paramètres NSAbait";
+App::$strings["Send test email"] = "Envoyer un mail de test";
+App::$strings["No recipients found."] = "Aucun destinataire trouvé.";
+App::$strings["Mail sent."] = "Mail envoyé.";
+App::$strings["Sending of mail failed."] = "L'envoi du mail a échoué.";
+App::$strings["Mail Test"] = "Test du mail";
+App::$strings["Message subject"] = "Objet du message";
+App::$strings["Reconnecting %d connections"] = "";
+App::$strings["Diaspora Reconnect"] = "";
+App::$strings["Use this form to re-establish Diaspora connections which were initially made from a different hub."] = "";
+App::$strings["Reconnect"] = "";
+App::$strings["View Larger"] = "Afficher en plus grand";
+App::$strings["Tile Server URL"] = "URL de la tuile du serveur";
+App::$strings["A list of <a href=\"http://wiki.openstreetmap.org/wiki/TMS\" target=\"_blank\">public tile servers</a>"] = "Une liste de <a href=\"http://wiki.openstreetmap.org/wiki/TMS\" target=\"_blank\">serveurs de cartes publics</a>";
+App::$strings["Nominatim (reverse geocoding) Server URL"] = "URL du serveur Nominatim (géocodage inversé)";
+App::$strings["A list of <a href=\"http://wiki.openstreetmap.org/wiki/Nominatim\" target=\"_blank\">Nominatim servers</a>"] = "Une liste de <a href=\"http://wiki.openstreetmap.org/wiki/Nominatim\" target=\"_blank\">serveurs Nominatim</a>";
+App::$strings["Default zoom"] = "Zoom par défaut";
+App::$strings["The default zoom level. (1:world, 18:highest, also depends on tile server)"] = "Le niveau de zoom par défaut. (1: monde, 18: plus élevé, dépend également du serveur de tuiles)";
+App::$strings["Include marker on map"] = "Inclure le marqueur sur la carte";
+App::$strings["Include a marker on the map."] = "Inclure un marqueur sur la carte.";
+App::$strings["Save Settings"] = "Sauvegarder les paramètres";
+App::$strings["text to include in all outgoing posts from this site"] = "Texte à inclure dans tous les messages sortants de ce site";
+App::$strings["Post to Friendica"] = "Publier sur Friendica";
+App::$strings["rtof Settings saved."] = "Paramètres rtof sauvegardés.";
+App::$strings["Allow posting to Friendica"] = "Autoriser la publication sur Friendica";
+App::$strings["Send public postings to Friendica by default"] = "Par défaut, envoyer les publications publiques sur Friendica";
+App::$strings["Friendica API Path"] = "Chemin de l'API Friendica";
+App::$strings["https://{sitename}/api"] = "https://{nomdusite}/api";
+App::$strings["Friendica login name"] = "Identifiant de connexion Friendica";
+App::$strings["Friendica password"] = "Mot de passe de connexion Friendica";
+App::$strings["Hubzilla to Friendica Post Settings"] = "Paramètres de publication de Hubzilla vers Friendica";
+App::$strings["Status:"] = "État&nbsp;:";
+App::$strings["Activate addon"] = "Activer l'extension";
+App::$strings["Hide Jappixmini Chat-Widget from the webinterface"] = "Cacher le widget de chat Jappixmini de l'interface web";
+App::$strings["Jabber username"] = "Identifiant Jabber";
+App::$strings["Jabber server"] = "Serveur Jabber";
+App::$strings["Jabber BOSH host URL"] = "Adresse hôte pour Jabber BOSH";
+App::$strings["Jabber password"] = "Mot de passe Jabber";
+App::$strings["Encrypt Jabber password with Hubzilla password"] = "Chiffrer le mot de passe Jabber avec le mot de passe Hubzilla";
+App::$strings["Hubzilla password"] = "Mot de passe Hubzilla";
+App::$strings["Approve subscription requests from Hubzilla contacts automatically"] = "Approuver automatiquement les demandes de connexion des contacts Hubzilla";
+App::$strings["Purge internal list of jabber addresses of contacts"] = "Purger la liste interne des adresses jabber des contacts";
+App::$strings["Configuration Help"] = "Aide pour la configuration";
+App::$strings["Jappix Mini Settings"] = "Paramètres de Jappix mini";
+App::$strings["Currently blocked"] = "Actuellement bloqué";
+App::$strings["No channels currently blocked"] = "Aucun canal n'est actuellement bloqué";
+App::$strings["\"Superblock\" Settings"] = "Paramètres \"Superblock\"";
+App::$strings["Block Completely"] = "Bloquer complètement";
+App::$strings["superblock settings updated"] = "Les paramètres du superblock ont été mis à jour";
+App::$strings["Federate"] = "Fédérer";
+App::$strings["nofed Settings saved."] = "Les paramètres nfed ont été enregistrés.";
+App::$strings["Allow Federation Toggle"] = "Autoriser la fédération avec Toggle";
+App::$strings["Federate posts by default"] = "Par défaut, fédérer les publications.";
+App::$strings["NoFed Settings"] = "Paramètres NoFed";
+App::$strings["Post to Red"] = "Publier sur Red";
+App::$strings["Channel is required."] = "Un canal est requis.";
+App::$strings["redred Settings saved."] = "Paramètres redred sauvegardés.";
+App::$strings["Allow posting to another Hubzilla Channel"] = "Autoriser la publication sur un autre canal Hubzilla";
+App::$strings["Send public postings to Hubzilla channel by default"] = "Par défaut, envoyer les publications publiques sur le canal Hubzilla";
+App::$strings["Hubzilla API Path"] = "Chemin de l'API Hubzilla";
+App::$strings["Hubzilla login name"] = "Identifiant de connexion Hubzilla";
+App::$strings["Hubzilla channel name"] = "Nom du canal Hubzilla";
+App::$strings["Hubzilla Crosspost Settings"] = "Paramètres Crosspost Hubzilla";
+App::$strings["Logfile archive directory"] = "Répertoire d'archivage du fichier journal";
+App::$strings["Directory to store rotated logs"] = "Répertoire où stocker les journaux de rotation";
+App::$strings["Logfile size in bytes before rotating"] = "Taille du fichier journal en octets avant la rotation";
+App::$strings["Number of logfiles to retain"] = "Nombre de fichiers de journal à conserver";
+App::$strings["Friendica Photo Album Import"] = "Importation de l'album photo Friendica ";
+App::$strings["This will import all your Friendica photo albums to this Red channel."] = "Ceci importera toutes vos albums photos Friendica dans ce canal Hubzilla.";
+App::$strings["Friendica Server base URL"] = "URL de base du serveur Friendica";
+App::$strings["Friendica Login Username"] = "Identifiant de connexion Friendica";
+App::$strings["Friendica Login Password"] = "Mot de passe de connexion Friendica";
+App::$strings["Project Servers and Resources"] = "Serveurs et ressources du projet";
+App::$strings["Project Creator and Tech Lead"] = "Créateur et Responsable Technique du projet";
+App::$strings["Admin, developer, directorymin, support bloke"] = "Administrateur, développeur, responsable d'annuaire, équipe support";
+App::$strings["And the hundreds of other people and organisations who helped make the Hubzilla possible."] = "Et les centaines d'autres personnes et organisations qui ont contribué à rendre le Hubzilla possible.";
+App::$strings["The Redmatrix/Hubzilla projects are provided primarily by volunteers giving their time and expertise - and often paying out of pocket for services they share with others."] = "Les projets Redmatrix / Hubzilla sont fournis principalement par des bénévoles qui donnent de leur temps et de leur expertise - et paient souvent de leur poche pour des services qu'ils partagent avec d'autres.";
+App::$strings["There is no corporate funding and no ads, and we do not collect and sell your personal information. (We don't control your personal information - <strong>you do</strong>.)"] = "Il n'y a ni financement d'entreprise ni publicités, et nous ne recueillons ni ne vendons vos données personnelles. (Nous ne contrôlons pas vos informations personnelles - vous le faites !)";
+App::$strings["Help support our ground-breaking work in decentralisation, web identity, and privacy."] = "Aider à soutenir notre travail novateur en matière de décentralisation, d'identité Web et de confidentialité.";
+App::$strings["Your donations keep servers and services running and also helps us to provide innovative new features and continued development."] = "Vos dons maintiennent les serveurs et les services en marche et nous aident également à fournir de nouvelles fonctionnalités innovantes et un développement continu.";
+App::$strings["Donate"] = "Donner";
+App::$strings["Choose a project, developer, or public hub to support with a one-time donation"] = "Choisissez un projet, un développeur ou un hub public à soutenir à l'aide d'un don unique";
+App::$strings["Donate Now"] = "Donner maintenant";
+App::$strings["<strong><em>Or</em></strong> become a project sponsor (Hubzilla Project only)"] = "Or devenez un sponsor du projet (projet Hubzilla uniquement)";
+App::$strings["Please indicate if you would like your first name or full name (or nothing) to appear in our sponsor listing"] = "Veuillez indiquer si vous souhaitez que votre nom ou prénom (ou rien) apparaisse dans la liste de nos sponsors.";
+App::$strings["Sponsor"] = "Sponsors";
+App::$strings["Special thanks to: "] = "Remerciements particuliers à :";
+App::$strings["This is a fairly comprehensive and complete guitar chord dictionary which will list most of the available ways to play a certain chord, starting from the base of the fingerboard up to a few frets beyond the twelfth fret (beyond which everything repeats). A couple of non-standard tunings are provided for the benefit of slide players, etc."] = "Ceci est un dictionnaire d'accords de guitare assez complet et facile qui énumère la plupart des manières possibles de jouer un certain accord, à partir de la base de la touche jusqu'à quelques frettes au-delà de la douzième frette (au-delà de laquelle tout se répète). Un couple d'accordages non standard sont fournis au profit des joueurs de diapositives, etc.";
+App::$strings["Chord names start with a root note (A-G) and may include sharps (#) and flats (b). This software will parse most of the standard naming conventions such as maj, min, dim, sus(2 or 4), aug, with optional repeating elements."] = "Les noms des accords commencent par une note racine (A-G) et peuvent inclure des dièses (#) et des bémols (b). Ce logiciel analysera la plupart des conventions de dénomination standard telles que maj, min, dim, sus (2 ou 4), aug, avec des éléments répétitifs facultatifs.";
+App::$strings["Valid examples include A, A7, Am7, Amaj7, Amaj9, Ammaj7, Aadd4, Asus2Add4, E7b13b11 ..."] = "Exemples valides comprennent A, A7, Am7, Amaj7, Amaj9, Ammaj7, Aadd4, Asus2Add4, E7b13b11 ...";
+App::$strings["Guitar Chords"] = "Acords de guitar";
+App::$strings["The complete online chord dictionary"] = "Le dictionnaire en ligne complet des accords";
+App::$strings["Tuning"] = "Réglage";
+App::$strings["Chord name: example: Em7"] = "Nom d'accord. Exemple : Em7.";
+App::$strings["Show for left handed stringing"] = "Montrer pour les gauchers";
+App::$strings["Quick Reference"] = "Référence rapide";
+App::$strings["Post to Libertree"] = "Publier sur Libertree";
+App::$strings["Enable Libertree Post Plugin"] = "Activer le plugin de publication Libertree";
+App::$strings["Libertree API token"] = "Jeton de l'API Libertree";
+App::$strings["Libertree site URL"] = "Adresse du site Libertree";
+App::$strings["Post to Libertree by default"] = "Par défaut, publier sur Libertree";
+App::$strings["Libertree Post Settings"] = "Paramètres de publication pour Libertree";
+App::$strings["Libertree Settings saved."] = "Paramètres de Libertree sauvegardés.";
+App::$strings["Flattr this!"] = "Flattr this!";
+App::$strings["Flattr widget settings updated."] = "Les paramètres du widget Flattr ont été mis à jour";
+App::$strings["Flattr user"] = "Utilisateur de Flattr";
+App::$strings["URL of the Thing to flattr"] = "URL de ce que vous voulez flattr";
+App::$strings["If empty channel URL is used"] = "Si une url vide est utilisée";
+App::$strings["Title of the Thing to flattr"] = "Titre de ce que vous voulez flattr";
+App::$strings["If empty \"channel name on The Hubzilla\" will be used"] = "Si vide, \"nom du canal sur Hubzilla\" sera utilisé";
+App::$strings["Static or dynamic flattr button"] = "Statique ou dynamique bouton Flattr";
+App::$strings["static"] = "statique";
+App::$strings["dynamic"] = "dynamique";
+App::$strings["Alignment of the widget"] = "Alignement du widget";
+App::$strings["left"] = "gauche";
+App::$strings["right"] = "droite";
+App::$strings["Enable Flattr widget"] = "Activer le widget Flattr";
+App::$strings["Flattr Widget Settings"] = "Paramètres du widget Flattr";
+App::$strings["Post to GNU social"] = "Publier sur GNU-social";
+App::$strings["Please contact your site administrator.<br />The provided API URL is not valid."] = "Veuillez contacter l'administrateur de votre site. L'URL de l'API n'est pas valide.";
+App::$strings["We could not contact the GNU social API with the Path you entered."] = "Nous ne pouvons pas contacter l'API de GNU-social avec le chemin que vous avez entré.";
+App::$strings["GNU social settings updated."] = "Les paramètres GNU-social ont été mis à jour.";
+App::$strings["Globally Available GNU social OAuthKeys"] = "Les OAuthKeys GNU-social sont globalement disponibles.";
+App::$strings["There are preconfigured OAuth key pairs for some GNU social servers available. If you are using one of them, please use these credentials.<br />If not feel free to connect to any other GNU social instance (see below)."] = "Il existe des paires de clés OAuth préconfigurées pour certains serveurs GNU-social disponibles. Si vous utilisez l'un d'eux, utilisez ces informations d'identification.\nSi vous ne voulez pas vous connecter à une autre instance GNU social (voir ci-dessous).";
+App::$strings["Provide your own OAuth Credentials"] = "Fournissez vos propres informations d'identification OAuth";
+App::$strings["No consumer key pair for GNU social found. Register your Hubzilla Account as an desktop client on your GNU social account, copy the consumer key pair here and enter the API base root.<br />Before you register your own OAuth key pair ask the administrator if there is already a key pair for this Hubzilla installation at your favourite GNU social installation."] = "Aucune paire de clés utilisateur n'a été trouvée pour GNU-social. Enregistrer votre compte Hubzilla en tant que client de bureau sur votre compte GNU-social, puis copier la paire de clés utilisateur ici et entrer la racine de base de l'API.\nAvant d'enregistrer votre propre paire de clés OAuth, demandez à l'administrateur s'il existe déjà une paire de clés pour cette installation de Hubzilla à votre installation GNU-social préférée.";
+App::$strings["OAuth Consumer Key"] = "Clé d'utilisateur OAuth";
+App::$strings["OAuth Consumer Secret"] = "Secret d'utilisateur OAuth";
+App::$strings["Base API Path"] = "Chemin de l'API de base";
+App::$strings["Remember the trailing /"] = "N'oubliez pas le / final";
+App::$strings["GNU social application name"] = "Nom de l'application GNU-social";
+App::$strings["To connect to your GNU social account click the button below to get a security code from GNU social which you have to copy into the input box below and submit the form. Only your <strong>public</strong> posts will be posted to GNU social."] = "Pour vous connecter à votre compte GNU-social, cliquez sur le bouton ci-dessous pour obtenir un code de sécurité de GNU-social. Vous devez le copier dans la zone de saisie ci-dessous, puis soumettre le formulaire. Seuls vos messages publics seront visibles sur GNU-social.";
+App::$strings["Log in with GNU social"] = "Vous connecter avec GNU-social";
+App::$strings["Copy the security code from GNU social here"] = "Copier ici le code de sécurité de GNU-social.";
+App::$strings["Cancel Connection Process"] = "Annuler le processus de connexion";
+App::$strings["Current GNU social API is"] = "L'API GNU-social courante est";
+App::$strings["Cancel GNU social Connection"] = "Annuler la connexion GNU-social";
+App::$strings["Currently connected to: "] = "Actuellement connecté à :";
+App::$strings["<strong>Note</strong>: Due your privacy settings (<em>Hide your profile details from unknown viewers?</em>) the link potentially included in public postings relayed to GNU social will lead the visitor to a blank page informing the visitor that the access to your profile has been restricted."] = "Remarque : en raison de vos paramètres de confidentialité (masquer les détails de votre profil aux visiteurs inconnus? ), le lien potentiellement inclus dans les annonces publiques relayées sur GNU-social amènera le visiteur à une page vierge informant le visiteur que l'accès à votre profil a été restreint.";
+App::$strings["Allow posting to GNU social"] = "Autoriser la publication sur GNU-social";
+App::$strings["If enabled your public postings can be posted to the associated GNU-social account"] = "Si cette option est activée, vos publications publiques peuvent être publiées sur le compte GNU-social associé.";
+App::$strings["Post to GNU social by default"] = "Par défaut, publier sur GNU-social";
+App::$strings["If enabled your public postings will be posted to the associated GNU-social account by default"] = "Si cette option est activée, par défaut, vos publications publiques seront publiées sur le compte GNU-social associé";
+App::$strings["Clear OAuth configuration"] = "Effacer la configuration OAuth";
+App::$strings["GNU social Post Settings"] = "Paramètres de publication GNU-social";
+App::$strings["API URL"] = "URL de l'API";
+App::$strings["Application name"] = "Nom de l'application";
+App::$strings["QR code"] = "QR code";
+App::$strings["QR Generator"] = "Générateur de QRcode";
+App::$strings["Enter some text"] = "Entrer du texte";
+App::$strings["Invalid game."] = "Jeu invalide";
+App::$strings["You are not a player in this game."] = "Vous n'êtes pas un joueur de ce jeu.";
+App::$strings["You must be a local channel to create a game."] = "Vous devez être un canal local pour créer un jeu.";
+App::$strings["You must select one opponent that is not yourself."] = "Vous devez sélectionner un adversaire qui ne soit pas vous-même.";
+App::$strings["Creating new game..."] = "en train de créer un nouveau jeu…";
+App::$strings["You must select white or black."] = "Vous devez sélectionner les blancs ou les noirs.";
+App::$strings["Error creating new game."] = "Erreur lors de la création du nouveau jeu.";
+App::$strings["Requested channel is not available."] = "Canal demandé non disponible.";
+App::$strings["You must select a local channel /chess/channelname"] = "Vous devez sélectionner un canal local /échecs/nomducanal";
+App::$strings["Enable notifications"] = "Activer les notifications";
+App::$strings["Post to Twitter"] = "Publier sur Twitter";
+App::$strings["Twitter settings updated."] = "Les paramètres de Twitter ont été mis à jour.";
+App::$strings["No consumer key pair for Twitter found. Please contact your site administrator."] = "Aucune paire de clés d'utilisateur pour Twitter n'a été trouvée. Veuillez contacter l'administrateur de votre site.";
+App::$strings["At this Hubzilla instance the Twitter plugin was enabled but you have not yet connected your account to your Twitter account. To do so click the button below to get a PIN from Twitter which you have to copy into the input box below and submit the form. Only your <strong>public</strong> posts will be posted to Twitter."] = "Dans cette instance de Hubzilla, le plugin Twitter a été activé, mais vous n'avez pas encore connecté votre compte à votre compte Twitter. Pour ce faire, cliquez sur le bouton ci-dessous pour obtenir un code PIN de Twitter que vous devez copier dans la zone de saisie ci-dessous, puis soumettre le formulaire. Seuls vos messages publics seront publiés sur Twitter.";
+App::$strings["Log in with Twitter"] = "Connectez-vous avec votre compte Twitter";
+App::$strings["Copy the PIN from Twitter here"] = "Copier ici le PIN fourni par Twitter";
+App::$strings["<strong>Note:</strong> Due your privacy settings (<em>Hide your profile details from unknown viewers?</em>) the link potentially included in public postings relayed to Twitter will lead the visitor to a blank page informing the visitor that the access to your profile has been restricted."] = "Note : En raison de vos paramètres de confidentialité (Masquer les détails de votre profil aux visiteurs inconnus?), le lien potentiellement inclus dans les annonces publiques relayées vers Twitter amènera le visiteur à une page vierge l'informant que l'accès à votre profil a été restreint.";
+App::$strings["Allow posting to Twitter"] = "Autoriser la publication sur Twitter";
+App::$strings["If enabled your public postings can be posted to the associated Twitter account"] = "Si cette option est activée, vos publications publiques peuvent être publiées sur le compte Twitter associé.";
+App::$strings["Send public postings to Twitter by default"] = "Par défaut, envoyer vos publications publiques sur Twitter.";
+App::$strings["If enabled your public postings will be posted to the associated Twitter account by default"] = "Si cette option est activée, par défaut, vos publications publiques seront publiées sur le compte Twitter associé.";
+App::$strings["Twitter Post Settings"] = "Paramètres des publications Twitter";
+App::$strings["Deactivate the feature"] = "Désactiver la fonctionnalité";
+App::$strings["Hide the button and show the smilies directly."] = "Cacher le bouton et afficher les émoticônes directement.";
+App::$strings["Smileybutton Settings"] = "Paramètres du bouton des émoticônes";
+App::$strings["This website is tracked using the <a href='http://www.piwik.org'>Piwik</a> analytics tool."] = "Ce site web est surveillé grâce à l'outil d'analyse <a href='http://www.piwik.org'>Piwik</a>.";
+App::$strings["If you do not want that your visits are logged this way you <a href='%s'>can set a cookie to prevent Piwik from tracking further visits of the site</a> (opt-out)."] = "Si vous ne souhaitez pas que vos visites soient enregistrées de cette façon, <a href='%s'>vous pouvez\ndéfinir un cookie pour empêcher Piwik de suivre davantage de visites du site</a> (opt-out).";
+App::$strings["Piwik Base URL"] = "URL de base Piwik";
+App::$strings["Absolute path to your Piwik installation. (without protocol (http/s), with trailing slash)"] = "Chemin absolu vers votre installation Piwik. (sans le http/s, avec antislash)";
+App::$strings["Site ID"] = "ID du site";
+App::$strings["Show opt-out cookie link?"] = "Afficher le lien opt-out du cookie ?";
+App::$strings["Asynchronous tracking"] = "Traqueur asynchrone";
+App::$strings["Enable frontend JavaScript error tracking"] = "Activer le traqueur d'erreur du frontend JavaScript";
+App::$strings["This feature requires Piwik >= 2.2.0"] = "Cette fonctionnalité requiert une version de Piwik >=2.2.0";
+App::$strings["Edit your profile and change settings."] = "Éditer votre profil et changer les paramètres.";
+App::$strings["Click here to see activity from your connections."] = "Cliquer ici pour voir l'activité de vos connections.";
+App::$strings["Click here to see your channel home."] = "Cliquer ici pour voir votre canal principal.";
+App::$strings["You can access your private messages from here."] = "Vous pouvez accéder à vos messages privés à partir d'ici.";
+App::$strings["Create new events here."] = "Créer de nouveaux événements ici.";
+App::$strings["You can accept new connections and change permissions for existing ones here. You can also e.g. create groups of contacts."] = "Vous pouvez accepter de nouvelles connections et changer les permissions des connections existantes. Vous pouvez également créer des groupes de contacts.";
+App::$strings["System notifications will arrive here"] = "Les notifications du système arriveront ici.";
+App::$strings["Search for content and users"] = "Rechercher du contenu ou des utilisateurs";
+App::$strings["Browse for new contacts"] = "Rechercher de nouveaux contacts";
+App::$strings["Launch installed apps"] = "Démarrer des applications installées";
+App::$strings["Looking for help? Click here."] = "Un peu d'aide ? Cliquer ici.";
+App::$strings["New events have occurred in your network. Click here to see what has happened!"] = "De nouveaux événement se sont produits dans votre réseau. Cliquer ici pour voir ce qui s'est passé !";
+App::$strings["You have received a new private message. Click here to see from who!"] = "Vous avez reçu un nouveau message privé. Cliquer ici pour voir qui vous écrit !";
+App::$strings["There are events this week. Click here too see which!"] = "Il y a des événements cette semaine. Cliquer ici pour voir lesquels !";
+App::$strings["You have received a new introduction. Click here to see who!"] = "Vous avez reçu une nouvelle demande de relation. Cliquer ici pour voir de qui !";
+App::$strings["There is a new system notification. Click here to see what has happened!"] = "Vous avez reçu une notification du système. Cliquer ici pour voir ce qui se passe !";
+App::$strings["Click here to share text, images, videos and sound."] = "Cliquer ici pour partager du texte, des images, des vidéos ou du son.";
+App::$strings["You can write an optional title for your update (good for long posts)."] = "Vous pouvez ajouter à votre mise à jour un titre facultatif (pratique pour de longues publications).";
+App::$strings["Entering some categories here makes it easier to find your post later."] = "Renseigner certaines catégories ici permet de retrouver plus facilement votre message plus tard.";
+App::$strings["Share photos, links, location, etc."] = "Partager des photos, des liens, des localisations, etc.";
+App::$strings["Only want to share content for a while? Make it expire at a certain date."] = "Envie de partager un contenu pour une durée limitée ? Faites-le expirer à une certaine date.";
+App::$strings["You can password protect content."] = "Vous pouvez protéger un contenu avec un mot de passe.";
+App::$strings["Choose who you share with."] = "Choisir avec qui vous partagez.";
+App::$strings["Click here when you are done."] = "Cliquer ici quand vous avez fini.";
+App::$strings["Adjust from which channels posts should be displayed."] = "Préciser de quels canaux les publications seront affichées.";
+App::$strings["Only show posts from channels in the specified privacy group."] = "Afficher uniquement les messages des canaux appartenant au groupe de contacts spécifié.";
+App::$strings["Easily find posts containing tags (keywords preceded by the \"#\" symbol)."] = "Trouvez facilement des publications contenant des tags (mots-clés précédés du symbole \"#\").";
+App::$strings["Easily find posts in given category."] = "Trouvez facilement des publications dans une catégorie donnée.";
+App::$strings["Easily find posts by date."] = "Trouvez facilement des publications en fonction de leur date.";
+App::$strings["Suggested users who have volounteered to be shown as suggestions, and who we think you might find interesting."] = "Voici des utilisateurs que vous pourriez trouver intéressants. Ces utilisateurs se sont portés volontaires pour être affichés comme exemples.";
+App::$strings["Here you see channels you have connected to."] = "Retrouvez ici les canaux auxquels vous vous êtes connectés.";
+App::$strings["Save your search so you can repeat it at a later date."] = "Enregistrer votre recherche de façon à pouvoir la répéter plus tard.";
+App::$strings["If you see this icon you can be sure that the sender is who it say it is. It is normal that it is not always possible to verify the sender, so the icon will be missing sometimes. There is usually no need to worry about that."] = "Si vous voyez cette icône, vous pouvez être sûr que l'expéditeur est qui il dit qu'il est. Il est normal qu'il ne soit pas toujours possible de vérifier l'expéditeur, donc l'icône manquera parfois. Il n'est généralement pas nécessaire de s'inquiéter à ce sujet.";
+App::$strings["Danger! It seems someone tried to forge a message! This message is not necessarily from who it says it is from!"] = "Attention ! Il semble que quelqu'un a essayé de contrefaire un message ! Ce message n'a pas nécessairement été envoyé par la personne annoncée !";
+App::$strings["Welcome to Hubzilla! Would you like to see a tour of the UI?</p> <p>You can pause it at any time and continue where you left off by reloading the page, or navigting to another page.</p><p>You can also advance by pressing the return key"] = "Bienvenue sur Hubzilla! Voulez-vous faire un tour de l'interface utilisateur? Vous pouvez le mettre en pause à tout moment et continuer où vous l'avez laissé en rechargeant la page ou en naviguant vers une autre page. Vous pouvez également avancer en appuyant sur la touche de retour.";
+App::$strings["Extended Identity Sharing"] = "Partage d'identification étendu";
+App::$strings["Share your identity with all websites on the internet. When disabled, identity is only shared with sites in the matrix."] = "Partagez votre identification avec tous les sites Web sur Internet. Lorsqu'elle est désactivée, l'identification n'est partagée qu'avec les sites de la matrice.";
+App::$strings["Three Dimensional Tic-Tac-Toe"] = "Tic-tac-toe en 3 dimensions";
+App::$strings["3D Tic-Tac-Toe"] = "3D Tic-Tac-Toe";
+App::$strings["New game"] = "Nouveau jeu";
+App::$strings["New game with handicap"] = "Nouveau jeu avec handicap";
+App::$strings["Three dimensional tic-tac-toe is just like the traditional game except that it is played on multiple levels simultaneously. "] = "Trois dimensions tic-tac-toe est juste comme le jeu traditionnel, sauf qu'il est joué sur plusieurs niveaux simultanément.";
+App::$strings["In this case there are three levels. You win by getting three in a row on any level, as well as up, down, and diagonally across the different levels."] = "Dans ce cas, il y a trois niveaux. Vous gagnez en obtenant trois dans une rangée à n'importe quel niveau, que ce soit vers le haut, le bas, ou en diagonale à travers les différents niveaux.";
+App::$strings["The handicap game disables the center position on the middle level because the player claiming this square often has an unfair advantage."] = "Le jeu handicap désactive la position centrale au niveau intermédiaire, car le joueur qui revendique ce carré a souvent un avantage indu.";
+App::$strings["You go first..."] = "Vous commencez…";
+App::$strings["I'm going first this time..."] = "Cette fois, je commence…";
+App::$strings["You won!"] = "Vous avez gagné !";
+App::$strings["\"Cat\" game!"] = "Jeu de \"Chat\" !";
+App::$strings["I won!"] = "J'ai gagné !";
+App::$strings["Message to display on every page on this server"] = "Message à afficher sur chaque page de ce serveur";
+App::$strings["Pageheader Settings"] = "Paramètres du haut de page";
+App::$strings["pageheader Settings saved."] = "Paramètres du haut de page sauvegardés.";
+App::$strings["lonely"] = "isolé";
+App::$strings["drunk"] = "saoul";
+App::$strings["horny"] = "libidineux";
+App::$strings["stoned"] = "défoncé";
+App::$strings["fucked up"] = "cramé";
+App::$strings["clusterfucked"] = "énervé";
+App::$strings["crazy"] = "cinglé";
+App::$strings["hurt"] = "dommage";
+App::$strings["sleepy"] = "somnolent";
+App::$strings["grumpy"] = "grognon";
+App::$strings["high"] = "allumé";
+App::$strings["semi-conscious"] = "à demi-conscient";
+App::$strings["in love"] = "amoureux";
+App::$strings["in lust"] = "convoitise";
+App::$strings["naked"] = "nu";
+App::$strings["stinky"] = "puant";
+App::$strings["sweaty"] = "en sueur";
+App::$strings["bleeding out"] = "en sang";
+App::$strings["victorious"] = "victorieux";
+App::$strings["defeated"] = "vaincu";
+App::$strings["envious"] = "envieux";
+App::$strings["jealous"] = "jaloux";
+App::$strings["XMPP settings updated."] = "Les paramètres XMPP ont été mis à jour.";
+App::$strings["Enable Chat"] = "Activer le Chat";
+App::$strings["Individual credentials"] = "Informations d'identifications individuelles";
+App::$strings["Jabber BOSH server"] = "serveur Jabber BOSH";
+App::$strings["XMPP Settings"] = "Paramètres XMPP";
+App::$strings["Jabber BOSH host"] = "Hôte Jabber BOSH";
+App::$strings["Use central userbase"] = "Utiliser la base d'utilisateurs centrale";
+App::$strings["If enabled, members will automatically login to an ejabberd server that has to be installed on this machine with synchronized credentials via the \"auth_ejabberd.php\" script."] = "Si cette option est activée, les membres se connecteront automatiquement à un serveur ejabberd qui doit être installé sur cette machine avec des informations d'identification synchronisées via le script \"auth_ejabberd.php\".";
+App::$strings["Who likes me?"] = "Qui m'aime?";
+App::$strings["You are now authenticated to pumpio."] = "Vous êtes maintenant connecté à pumpio.";
+App::$strings["return to the featured settings page"] = "retourner à la page des paramètres des fonctionnalités";
+App::$strings["Post to Pump.io"] = "Publier sur Pump.io";
+App::$strings["Pump.io servername"] = "Nom du serveur Pump.io";
+App::$strings["Without \"http://\" or \"https://\""] = "Sans \"http://\" ou \"https://\"";
+App::$strings["Pump.io username"] = "Identifiant Pump.io";
+App::$strings["Without the servername"] = "Sans le nom de serveur";
+App::$strings["You are not authenticated to pumpio"] = "Vous n'êtes pas connecté à Pump.io";
+App::$strings["(Re-)Authenticate your pump.io connection"] = "Authentifiez-vous à nouveau auprès de Pump.io";
+App::$strings["Enable pump.io Post Plugin"] = "Activer le plugin de publication Pump.io";
+App::$strings["Post to pump.io by default"] = "Par défaut, publier sur Pump.io";
+App::$strings["Should posts be public"] = "Les publications doivent-elles être publiques ?";
+App::$strings["Mirror all public posts"] = "Créer une copie miroir de toutes les publications publiques";
+App::$strings["Pump.io Post Settings"] = "Paramètres de publication Pump.io";
+App::$strings["PumpIO Settings saved."] = "Paramètres Pump.io sauvegardés.";
+App::$strings["An account has been created for you."] = "Un compte a été créé pour vous.";
+App::$strings["Authentication successful but rejected: account creation is disabled."] = "L'authentification a réussi mais a été rejetée : la création de comptes est désactivée.";
+App::$strings["Search \$Projectname"] = "Chercher dans \$Projectname";
+App::$strings["Redmatrix File Storage Import"] = "Importation du fichier de stockage Redmatrix";
+App::$strings["This will import all your Redmatrix cloud files to this channel."] = "Ceci importera tous vos fichiers Redmatrix dans ce canal.";
+App::$strings["file"] = "fichier";
+App::$strings["Send email to all members"] = "Envoyer un mail à tous les membres";
+App::$strings["$1%s Administrator"] = "$1%s administrateur";
+App::$strings["%1\$d of %2\$d messages sent."] = "%1\$d message(s) envoyés sur %2\$d.";
+App::$strings["Send email to all hub members."] = "Envoyer un e-mail à tous les membres du hub.";
+App::$strings["Sender Email address"] = "Adresse mail de l'expéditeur";
+App::$strings["Test mode (only send to hub administrator)"] = "Mode test (uniquement envoyé à l'administrateur du hub)";
+App::$strings["Frequently"] = "Fréquemment";
+App::$strings["Hourly"] = "Toutes les heures";
+App::$strings["Twice daily"] = "Deux fois par jour";
+App::$strings["Daily"] = "Chaque jour";
+App::$strings["Weekly"] = "Chaque semaine";
+App::$strings["Monthly"] = "Chaque mois";
+App::$strings["Currently Male"] = "Actuellement homme";
+App::$strings["Currently Female"] = "Actuellement femme";
+App::$strings["Mostly Male"] = "Surtout homme";
+App::$strings["Mostly Female"] = "Surtout femme";
+App::$strings["Transgender"] = "Transgenre";
+App::$strings["Intersex"] = "Intersexuel";
+App::$strings["Transsexual"] = "Transsexuel";
+App::$strings["Hermaphrodite"] = "Hermaphrodite";
+App::$strings["Neuter"] = "Neutre";
+App::$strings["Non-specific"] = "Non spécifique";
+App::$strings["Undecided"] = "Indécis";
+App::$strings["Males"] = "Hommes";
+App::$strings["Females"] = "Femmes";
+App::$strings["Gay"] = "Gay";
+App::$strings["Lesbian"] = "Lesbienne";
+App::$strings["No Preference"] = "Sans préférence";
+App::$strings["Bisexual"] = "Bisexuel";
+App::$strings["Autosexual"] = "Autosexuel";
+App::$strings["Abstinent"] = "Abstinent";
+App::$strings["Virgin"] = "Vierge";
+App::$strings["Deviant"] = "Déviant";
+App::$strings["Fetish"] = "Fétichiste";
+App::$strings["Oodles"] = "Une floppée";
+App::$strings["Nonsexual"] = "Non-sexuel";
+App::$strings["Single"] = "Célibataire";
+App::$strings["Lonely"] = "Solitaire";
+App::$strings["Available"] = "Disponible";
+App::$strings["Unavailable"] = "Indisponible";
+App::$strings["Has crush"] = "A un béguin";
+App::$strings["Infatuated"] = "Amoureux transi";
+App::$strings["Dating"] = "Sort avec quelqu'un";
+App::$strings["Unfaithful"] = "Infidèle";
+App::$strings["Sex Addict"] = "Accro au sexe";
+App::$strings["Friends/Benefits"] = "Amis avec bénéfices";
+App::$strings["Casual"] = "Sans engagement";
+App::$strings["Engaged"] = "Fiancé(e)";
+App::$strings["Married"] = "Marié(e)";
+App::$strings["Imaginarily married"] = "Marié(e) dans ses rêves";
+App::$strings["Partners"] = "Partenaires";
+App::$strings["Cohabiting"] = "En cohabitation";
+App::$strings["Common law"] = "Conjoints de fait";
+App::$strings["Happy"] = "Heureux";
+App::$strings["Not looking"] = "Pas en recherche";
+App::$strings["Swinger"] = "Echangiste";
+App::$strings["Betrayed"] = "Trahi(e)";
+App::$strings["Separated"] = "Séparé(e)";
+App::$strings["Unstable"] = "Instable";
+App::$strings["Divorced"] = "Divorcé(e)";
+App::$strings["Imaginarily divorced"] = "Divorcé(e) dans ses rêves";
+App::$strings["Widowed"] = "Veuf/veuve";
+App::$strings["Uncertain"] = "Incertain";
+App::$strings["It's complicated"] = "C'est compliqué";
+App::$strings["Don't care"] = "S'en fiche";
+App::$strings["Ask me"] = "Me demander";
App::$strings["%1\$s is now connected with %2\$s"] = "%1\$s ajoute %2\$s à ses contacts";
App::$strings["%1\$s poked %2\$s"] = "%1\$s a tapoté %2\$s";
+App::$strings["poked"] = "a tapoté";
App::$strings["View %s's profile @ %s"] = "Voir le profil de %s @ %s";
App::$strings["Categories:"] = "Catégories&nbsp;:";
App::$strings["Filed under:"] = "Classé sous&nbsp;:";
App::$strings["View in context"] = "Voir en contexte";
App::$strings["remove"] = "supprimer";
+App::$strings["Loading..."] = "Chargement...";
App::$strings["Delete Selected Items"] = "Supprimer les éléments selectionnés";
App::$strings["View Source"] = "Voir source";
App::$strings["Follow Thread"] = "Suivre la discussion";
@@ -1815,12 +2495,17 @@ App::$strings["Set your location"] = "Spécifier votre emplacement géographique
App::$strings["Clear browser location"] = "Supprimer l'emplacement géographique du navigateur";
App::$strings["Tag term:"] = "Étiquette&nbsp;:";
App::$strings["Where are you right now?"] = "Où êtes-vous en ce moment&nbsp;?";
+App::$strings["Choose a different album..."] = "Choisissez un autre album";
+App::$strings["Comments enabled"] = "Commentaires activés";
+App::$strings["Comments disabled"] = "Commentaires désactivés";
App::$strings["Page link name"] = "Nom du lien vers la page";
App::$strings["Post as"] = "Publier en tant que";
App::$strings["Toggle voting"] = "(Dés)activer le vote";
+App::$strings["Disable comments"] = "Désactiver les commentaires";
+App::$strings["Toggle comments"] = "Basculer les commentaires";
App::$strings["Categories (optional, comma-separated list)"] = "Catégories (facultatives, séparées par des virgules)";
+App::$strings["Other networks and post services"] = "Autres réseaux et services de messagerie";
App::$strings["Set publish date"] = "Définir la date de publication";
-App::$strings["OK"] = "OK";
App::$strings["Discover"] = "À découvrir";
App::$strings["Imported public streams"] = "Flux publics importés";
App::$strings["Commented Order"] = "Par date de commentaire";
@@ -1829,17 +2514,17 @@ App::$strings["Posted Order"] = "Par date de publication";
App::$strings["Sort by Post Date"] = "Trier par date de publication";
App::$strings["Posts that mention or involve you"] = "Publications qui vous mentionnent ou vous concernent d'une manière ou d'une autre";
App::$strings["Activity Stream - by date"] = "Flux d'activité - par date";
-App::$strings["Starred"] = "Mis en avant (étoiles)";
+App::$strings["Starred"] = "Avec étoile";
App::$strings["Favourite Posts"] = "Publications préférées";
App::$strings["Spam"] = "Indésirable";
App::$strings["Posts flagged as SPAM"] = "Publications marquées comme indésirables";
App::$strings["Status Messages and Posts"] = "Messages d'état et contributions";
-App::$strings["About"] = "À propos";
App::$strings["Profile Details"] = "Détails du profil";
App::$strings["Photo Albums"] = "Albums photo";
App::$strings["Files and Storage"] = "Fichiers et Stockage";
+App::$strings["Bookmarks"] = "Favoris";
App::$strings["Saved Bookmarks"] = "Favoris sauvegardés";
-App::$strings["Manage Webpages"] = "Gérer les pages web";
+App::$strings["View Webpages"] = "Voir les pages web";
App::$strings["__ctx:noun__ Attending"] = array(
0 => "Participe",
1 => "Participent",
@@ -1864,99 +2549,206 @@ App::$strings["__ctx:noun__ Abstain"] = array(
0 => "S'abstient",
1 => "S'abstiennent",
);
-App::$strings["Frequently"] = "Fréquemment";
-App::$strings["Hourly"] = "Toutes les heures";
-App::$strings["Twice daily"] = "Deux fois par jour";
-App::$strings["Daily"] = "Chaque jour";
-App::$strings["Weekly"] = "Chaque semaine";
-App::$strings["Monthly"] = "Chaque mois";
-App::$strings["Currently Male"] = "Actuellement homme";
-App::$strings["Currently Female"] = "Actuellement femme";
-App::$strings["Mostly Male"] = "Surtout homme";
-App::$strings["Mostly Female"] = "Surtout femme";
-App::$strings["Transgender"] = "Transgenre";
-App::$strings["Intersex"] = "Intersexuel";
-App::$strings["Transsexual"] = "Transsexuel";
-App::$strings["Hermaphrodite"] = "Hermaphrodite";
-App::$strings["Neuter"] = "Neutre";
-App::$strings["Non-specific"] = "Non spécifique";
-App::$strings["Other"] = "Autre";
-App::$strings["Undecided"] = "Indécis";
-App::$strings["Males"] = "Hommes";
-App::$strings["Females"] = "Femmes";
-App::$strings["Gay"] = "Gay";
-App::$strings["Lesbian"] = "Lesbienne";
-App::$strings["No Preference"] = "Sans préférence";
-App::$strings["Bisexual"] = "Bisexuel";
-App::$strings["Autosexual"] = "Autosexuel";
-App::$strings["Abstinent"] = "Abstinent";
-App::$strings["Virgin"] = "Vierge";
-App::$strings["Deviant"] = "Déviant";
-App::$strings["Fetish"] = "Fétichiste";
-App::$strings["Oodles"] = "Une floppée";
-App::$strings["Nonsexual"] = "Non-sexuel";
-App::$strings["Single"] = "Célibataire";
-App::$strings["Lonely"] = "Solitaire";
-App::$strings["Available"] = "Disponible";
-App::$strings["Unavailable"] = "Indisponible";
-App::$strings["Has crush"] = "A un béguin";
-App::$strings["Infatuated"] = "Amoureux transi";
-App::$strings["Dating"] = "Sort avec quelqu'un";
-App::$strings["Unfaithful"] = "Infidèle";
-App::$strings["Sex Addict"] = "Accro au sexe";
-App::$strings["Friends/Benefits"] = "Amis avec bénéfices";
-App::$strings["Casual"] = "Sans engagement";
-App::$strings["Engaged"] = "Fiancé(e)";
-App::$strings["Married"] = "Marié(e)";
-App::$strings["Imaginarily married"] = "Marié(e) dans ses rêves";
-App::$strings["Partners"] = "Partenaires";
-App::$strings["Cohabiting"] = "En cohabitation";
-App::$strings["Common law"] = "Conjoints de fait";
-App::$strings["Happy"] = "Heureux";
-App::$strings["Not looking"] = "Pas en recherche";
-App::$strings["Swinger"] = "Echangiste";
-App::$strings["Betrayed"] = "Trahi(e)";
-App::$strings["Separated"] = "Séparé(e)";
-App::$strings["Unstable"] = "Instable";
-App::$strings["Divorced"] = "Divorcé(e)";
-App::$strings["Imaginarily divorced"] = "Divorcé(e) dans ses rêves";
-App::$strings["Widowed"] = "Veuf/veuve";
-App::$strings["Uncertain"] = "Incertain";
-App::$strings["It's complicated"] = "C'est compliqué";
-App::$strings["Don't care"] = "S'en fiche";
-App::$strings["Ask me"] = "Me demander";
-App::$strings["Visible to your default audience"] = "Visible pour vos contacts seulement";
-App::$strings["Only me"] = "";
-App::$strings["Public"] = "Public";
-App::$strings["Anybody in the \$Projectname network"] = "";
-App::$strings["Any account on %s"] = "";
-App::$strings["Any of my connections"] = "";
-App::$strings["Only connections I specifically allow"] = "";
-App::$strings["Anybody authenticated (could include visitors from other networks)"] = "";
-App::$strings["Any connections including those who haven't yet been approved"] = "";
-App::$strings["This is your default setting for the audience of your normal stream, and posts."] = "";
-App::$strings["This is your default setting for who can view your default channel profile"] = "";
-App::$strings["This is your default setting for who can view your connections"] = "";
-App::$strings["This is your default setting for who can view your file storage and photos"] = "";
-App::$strings["This is your default setting for the audience of your webpages"] = "";
-App::$strings["Not a valid email address"] = "Ce n'est pas une adresse de courriel valide";
-App::$strings["Your email domain is not among those allowed on this site"] = "Votre domaine de courriel ne fait pas partie de ceux autorisés par ce site";
-App::$strings["Your email address is already registered at this site."] = "Votre adresse de courriel est déjà inscrite sur ce site.";
-App::$strings["An invitation is required."] = "Une invitation est requise.";
-App::$strings["Invitation could not be verified."] = "Votre invitation n'a pas pu être vérifiée.";
-App::$strings["Please enter the required information."] = "Merci d'entrer les informations requises.";
-App::$strings["Failed to store account information."] = "Impossible de stocker les informations liées au compte.";
-App::$strings["Registration confirmation for %s"] = "Confirmation de l'inscription pour %s";
-App::$strings["Registration request at %s"] = "Demande d'inscription sur %s";
-App::$strings["Administrator"] = "Administrateur";
-App::$strings["your registration password"] = "votre mot de passe d'inscription";
-App::$strings["Registration details for %s"] = "Détails de l'inscription pour %s";
-App::$strings["Account approved."] = "Compte approuvé.";
-App::$strings["Registration revoked for %s"] = "Inscription révoquée pour %s";
-App::$strings["Account verified. Please login."] = "Compte vérifié. Veuillez vous connecter.";
-App::$strings["Click here to upgrade."] = "Cliquez ici pour mettre à jour.";
-App::$strings["This action exceeds the limits set by your subscription plan."] = "Cette action outrepasserait les limites prévues par votre forfait.";
-App::$strings["This action is not available under your subscription plan."] = "Cette action n'est pas disponible avec votre forfait.";
+App::$strings["Can view my normal stream and posts"] = "Peut voir les publications ordinaires sur mon canal.";
+App::$strings["Can view my webpages"] = "Peut voir mes pages web";
+App::$strings["Can post on my channel page (\"wall\")"] = "Peuvent poster sur la page de mon canal (\"mur\")";
+App::$strings["Can like/dislike stuff"] = "Peuvent aimer/ne pas aimer";
+App::$strings["Profiles and things other than posts/comments"] = "Profils et autres excluant les publications/commentaires.";
+App::$strings["Can forward to all my channel contacts via post @mentions"] = "Peut faire suivre à tous les contacts de mon canal via \"@mention\"";
+App::$strings["Advanced - useful for creating group forum channels"] = "Avancé - utile pour les canaux de type \"forum/groupe\"";
+App::$strings["Can chat with me (when available)"] = "Peut discuter avec moi (quand disponibie)";
+App::$strings["Can write to my file storage and photos"] = "Peut charger des fichiers et des photos dans mon canal";
+App::$strings["Can edit my webpages"] = "Peut modifier mes pages web";
+App::$strings["Somewhat advanced - very useful in open communities"] = "Plutôt avancé - très utile dans les communautés ouvertes";
+App::$strings["Can administer my channel resources"] = "Peut administrer les ressources de mon canal";
+App::$strings["Extremely advanced. Leave this alone unless you know what you are doing"] = "Très avancé. Ne pas toucher, sauf si vous savez ce que vous faîtes";
+App::$strings["Directory Options"] = "Options d'annuaire";
+App::$strings["Safe Mode"] = "Mode sûr";
+App::$strings["Public Forums Only"] = "Les forums publics uniquement";
+App::$strings["This Website Only"] = "Ce site uniquement";
+App::$strings["%1\$s's bookmarks"] = "Favoris de %1\$s";
+App::$strings["Cannot create a duplicate channel identifier on this system. Import failed."] = "L'import a échoué. Un canal existe déjà avec ce nom";
+App::$strings["Cloned channel not found. Import failed."] = "Canal cloné non trouvé. Echec de l'import.";
+App::$strings["prev"] = "préc.";
+App::$strings["first"] = "premier";
+App::$strings["last"] = "dernier";
+App::$strings["next"] = "Suivant";
+App::$strings["older"] = "plus ancien";
+App::$strings["newer"] = "plus récent";
+App::$strings["No connections"] = "Pas de relations.";
+App::$strings["View all %s connections"] = "Voir les %s contacts";
+App::$strings["poke"] = "tapoter";
+App::$strings["ping"] = "ping";
+App::$strings["pinged"] = "pingé";
+App::$strings["prod"] = "encourager";
+App::$strings["prodded"] = "encouragé";
+App::$strings["slap"] = "giffler";
+App::$strings["slapped"] = "gifflé(e)";
+App::$strings["finger"] = "pointer";
+App::$strings["fingered"] = "pointé";
+App::$strings["rebuff"] = "rejetter";
+App::$strings["rebuffed"] = "rejeté";
+App::$strings["happy"] = "heureux";
+App::$strings["sad"] = "triste";
+App::$strings["mellow"] = "mélancolique";
+App::$strings["tired"] = "fatigué";
+App::$strings["perky"] = "impertinent";
+App::$strings["angry"] = "en colère";
+App::$strings["stupefied"] = "stupéfait";
+App::$strings["puzzled"] = "perplexe";
+App::$strings["interested"] = "intéressé";
+App::$strings["bitter"] = "amer";
+App::$strings["cheerful"] = "plein d'entrain";
+App::$strings["alive"] = "vivant";
+App::$strings["annoyed"] = "agaçé";
+App::$strings["anxious"] = "anxieux";
+App::$strings["cranky"] = "énervé";
+App::$strings["disturbed"] = "perturbé";
+App::$strings["frustrated"] = "frustré";
+App::$strings["depressed"] = "déprimé";
+App::$strings["motivated"] = "motivé";
+App::$strings["relaxed"] = "détendu";
+App::$strings["surprised"] = "surpris";
+App::$strings["Monday"] = "Lundi";
+App::$strings["Tuesday"] = "Mardi";
+App::$strings["Wednesday"] = "Mercredi";
+App::$strings["Thursday"] = "Jeudi";
+App::$strings["Friday"] = "Vendredi";
+App::$strings["Saturday"] = "Samedi";
+App::$strings["Sunday"] = "Dimanche";
+App::$strings["January"] = "Janvier";
+App::$strings["February"] = "Février";
+App::$strings["March"] = "Mars";
+App::$strings["April"] = "Avril";
+App::$strings["May"] = "Mai";
+App::$strings["June"] = "Juin";
+App::$strings["July"] = "Juillet";
+App::$strings["August"] = "Août";
+App::$strings["September"] = "Septembre";
+App::$strings["October"] = "Octobre";
+App::$strings["November"] = "Novembre";
+App::$strings["December"] = "Décembre";
+App::$strings["Unknown Attachment"] = "Pièce jointe inconnue";
+App::$strings["unknown"] = "Inconnu";
+App::$strings["remove category"] = "supprimer la catégorie";
+App::$strings["remove from file"] = "retirer du fichier";
+App::$strings["default"] = "défaut";
+App::$strings["Page layout"] = "Mise en page";
+App::$strings["You can create your own with the layouts tool"] = "Créez les vôtres avec les outils de mise en page";
+App::$strings["Page content type"] = "Type de contenu de la page";
+App::$strings["activity"] = "activité";
+App::$strings["Design Tools"] = "Outils de conception";
+App::$strings["Pages"] = "Pages";
+App::$strings["Import website..."] = "Importer le site web…";
+App::$strings["Select folder to import"] = "Sélectionner le dossier à importer";
+App::$strings["Import from a zipped folder:"] = "Importer à partir d'un dossier zippé :";
+App::$strings["Import from cloud files:"] = "Importer à partir de fichiers dans le cloud :";
+App::$strings["/cloud/channel/path/to/folder"] = "/cloud/channel/chemain/du/repertoire";
+App::$strings["Enter path to website files"] = "Entrer le chemin vers les fichiers du site web";
+App::$strings["Select folder"] = "Sélectionner un répertoire";
+App::$strings["Export website..."] = "Exporter le site web…";
+App::$strings["Export to a zip file"] = "Exporter dans un fichier zip";
+App::$strings["website.zip"] = "website.zip";
+App::$strings["Enter a name for the zip file."] = "Entrer un nom pour le fichier zip.";
+App::$strings["Export to cloud files"] = "Exporter dans des fichiers sur le cloud";
+App::$strings["/path/to/export/folder"] = "/chemin/vers/le/dossier/d'export";
+App::$strings["Enter a path to a cloud files destination."] = "Entrer le chemin vers le cloud de fichiers";
+App::$strings["Specify folder"] = "Spécifier un répertoire";
+App::$strings["%d invitation available"] = array(
+ 0 => "%d invitation disponible",
+ 1 => "%d invitations disponibles",
+);
+App::$strings["Find Channels"] = "Trouver des canaux";
+App::$strings["Enter name or interest"] = "Saisir nom ou centre d'intérêt";
+App::$strings["Connect/Follow"] = "Ajouter/Suivre";
+App::$strings["Examples: Robert Morgenstein, Fishing"] = "Exemples: Guillaume Martin, Course à pieds";
+App::$strings["Random Profile"] = "Un profil au hasard";
+App::$strings["Invite Friends"] = "Inviter des amis";
+App::$strings["Advanced example: name=fred and country=iceland"] = "Exemple avancé&nbsp;: name=fred and country=iceland";
+App::$strings["%d connection in common"] = array(
+ 0 => "%d contact en commun",
+ 1 => "%d contacts en commun",
+);
+App::$strings["show more"] = "montrer plus";
+App::$strings["Attachments:"] = "";
+App::$strings["l F d, Y \\@ g:i A"] = "l d F Y \\à G\\hi";
+App::$strings["\$Projectname event notification:"] = "";
+App::$strings["Starts:"] = "Début&nbsp;:";
+App::$strings["Finishes:"] = "Fin&nbsp;:";
+App::$strings["Channel is blocked on this site."] = "Ce canal est bloqué sur ce site.";
+App::$strings["Channel location missing."] = "Emplacement du canal introuvable.";
+App::$strings["Response from remote channel was incomplete."] = "La réponse du canal distant était incomplète.";
+App::$strings["Channel was deleted and no longer exists."] = "Le canal a été supprimé et n'existe plus.";
+App::$strings["Protocol disabled."] = "Protocole désactivé.";
+App::$strings["Channel discovery failed."] = "La tentative d'accéder au canal a échoué.";
+App::$strings["Cannot connect to yourself."] = "Ne peut pas se connecter à vous.";
+App::$strings["Delete this item?"] = "Supprimer cet élément?";
+App::$strings["%s show less"] = "%s afficher moins";
+App::$strings["%s expand"] = "%s dérouler";
+App::$strings["%s collapse"] = "%s enrouler";
+App::$strings["Password too short"] = "Mot de passe trop court";
+App::$strings["Passwords do not match"] = "Les mots de passe ne correspondent pas";
+App::$strings["everybody"] = "tout le monde";
+App::$strings["Secret Passphrase"] = "Phrase de passe secrète";
+App::$strings["Passphrase hint"] = "Indice pour la phrase de passe";
+App::$strings["Notice: Permissions have changed but have not yet been submitted."] = "Note&nbsp;: Les permissions ont changées, mais n'ont pas encore été sauvées.";
+App::$strings["close all"] = "fermer tout";
+App::$strings["Nothing new here"] = "Aucun nouveau contenu trouvé";
+App::$strings["Rate This Channel (this is public)"] = "Evaluer ce canal (publiquement)";
+App::$strings["Describe (optional)"] = "Description (facultative)";
+App::$strings["Please enter a link URL"] = "Merci d'insérer une URL";
+App::$strings["Unsaved changes. Are you sure you wish to leave this page?"] = "Changements en attente. Voulez-vous vraiment quitter cette page?";
+App::$strings["timeago.prefixAgo"] = "timeago.prefixAgo";
+App::$strings["timeago.prefixFromNow"] = "timeago.prefixFromNow";
+App::$strings["ago"] = "auparavant";
+App::$strings["from now"] = "de maintenant";
+App::$strings["less than a minute"] = "moins d'une minute";
+App::$strings["about a minute"] = "environ une minute";
+App::$strings["%d minutes"] = "%d minutes";
+App::$strings["about an hour"] = "environ une heure";
+App::$strings["about %d hours"] = "environ %d heures";
+App::$strings["a day"] = "un jour";
+App::$strings["%d days"] = "%d jours";
+App::$strings["about a month"] = "environ un mois";
+App::$strings["%d months"] = "%d mois";
+App::$strings["about a year"] = "environ un an";
+App::$strings["%d years"] = "%d années";
+App::$strings[" "] = " ";
+App::$strings["timeago.numbers"] = "timeago.numbers";
+App::$strings["__ctx:long__ May"] = "Mai";
+App::$strings["Jan"] = "Jan";
+App::$strings["Feb"] = "Fev";
+App::$strings["Mar"] = "Mar";
+App::$strings["Apr"] = "Avr";
+App::$strings["__ctx:short__ May"] = "Mai";
+App::$strings["Jun"] = "Jun";
+App::$strings["Jul"] = "Jul";
+App::$strings["Aug"] = "Aou";
+App::$strings["Sep"] = "Sep";
+App::$strings["Oct"] = "Oct";
+App::$strings["Nov"] = "Nov";
+App::$strings["Dec"] = "Dec";
+App::$strings["Sun"] = "Dim";
+App::$strings["Mon"] = "Lun";
+App::$strings["Tue"] = "Mar";
+App::$strings["Wed"] = "Mer";
+App::$strings["Thu"] = "Jeu";
+App::$strings["Fri"] = "Ven";
+App::$strings["Sat"] = "Sam";
+App::$strings["__ctx:calendar__ today"] = "aujourd'hui";
+App::$strings["__ctx:calendar__ month"] = "mois";
+App::$strings["__ctx:calendar__ week"] = "semaine";
+App::$strings["__ctx:calendar__ day"] = "jour";
+App::$strings["__ctx:calendar__ All day"] = "Toute la journée";
+App::$strings["Unable to determine sender."] = "Impossible de déterminer l'émetteur.";
+App::$strings["No recipient provided."] = "Pas de destinataire.";
+App::$strings["[no subject]"] = "[sans objet]";
+App::$strings["Stored post could not be verified."] = "Le message stocké n'a pas pu être vérifié.";
+App::$strings[" and "] = "et";
+App::$strings["public profile"] = "profil public";
+App::$strings["%1\$s changed %2\$s to &ldquo;%3\$s&rdquo;"] = "%1\$s a changé %2\$s en &ldquo;%3\$s&rdquo;";
+App::$strings["Visit %1\$s's %2\$s"] = "Visiter %2\$s de %1\$s";
+App::$strings["%1\$s has an updated %2\$s, changing %3\$s."] = "%1\$s a mis à jour %2\$s, modifiant %3\$s.";
App::$strings["Item was not found."] = "Élément introuvable.";
App::$strings["No source file."] = "Pas de fichier source.";
App::$strings["Cannot locate file to replace"] = "Impossible de trouver le fichier à remplacer.";
@@ -1972,6 +2764,24 @@ App::$strings["Path not found."] = "Chemin introuvable.";
App::$strings["mkdir failed."] = "mkdir a échoué.";
App::$strings["database storage failed."] = "l'écriture dans la base de données a échoué.";
App::$strings["Empty path"] = "Chemin vide";
+App::$strings["guest:"] = "Visiteur";
+App::$strings["The form security token was not correct. This probably happened because the form has been opened for too long (>3 hours) before submitting it."] = "Le formulaire n'est plus sécurisé, probablement parce qu'il est ouvert depuis trop longtemps (plus de 3 heures).";
+App::$strings["(Unknown)"] = "(Inconnu)";
+App::$strings["Visible to anybody on the internet."] = "Visible pour tout le monde sur internet.";
+App::$strings["Visible to you only."] = "Visible pour vous seulement.";
+App::$strings["Visible to anybody in this network."] = "Visible pour tout le monde sur ce réseau.";
+App::$strings["Visible to anybody authenticated."] = "Visible aux utilisateurs authentifiés.";
+App::$strings["Visible to anybody on %s."] = "Visible pour tous sur %s.";
+App::$strings["Visible to all connections."] = "Visible pour tous les contacts.";
+App::$strings["Visible to approved connections."] = "Visible aux contacts approuvés.";
+App::$strings["Visible to specific connections."] = "Visible pour certains contacts.";
+App::$strings["Privacy group is empty."] = "Groupe de contacts vide.";
+App::$strings["Privacy group: %s"] = "Groupe de contacts&nbsp;: %s";
+App::$strings["Connection not found."] = "Contact non trouvé.";
+App::$strings["profile photo"] = "photo de profil";
+App::$strings["[Edited %s]"] = "[%s édité]";
+App::$strings["__ctx:edit_activity__ Post"] = "Publier";
+App::$strings["__ctx:edit_activity__ Comment"] = "Commenter";
App::$strings["Unable to obtain identity information from database"] = "Impossible d'obtenir les données d'identité depuis la base de données";
App::$strings["Empty name"] = "Nom vide";
App::$strings["Name too long"] = "Nom trop long";
@@ -1981,11 +2791,9 @@ App::$strings["Reserved nickname. Please choose another."] = "Surnom réservé.
App::$strings["Nickname has unsupported characters or is already being used on this site."] = "Le surnom contient des caractères interdits ou est déjà pris sur ce site.";
App::$strings["Unable to retrieve created identity"] = "Impossible de récupérer l'identité créée";
App::$strings["Default Profile"] = "Profil par défaut";
-App::$strings["Requested channel is not available."] = "Canal demandé non disponible.";
App::$strings["Create New Profile"] = "Créer un nouveau profil";
App::$strings["Visible to everybody"] = "Visible de tous";
App::$strings["Gender:"] = "Sexe&nbsp;:";
-App::$strings["Status:"] = "État&nbsp;:";
App::$strings["Homepage:"] = "Site Internet&nbsp;:";
App::$strings["Online Now"] = "Connecté";
App::$strings["Like this channel"] = "J'aime ce canal";
@@ -2010,9 +2818,47 @@ App::$strings["Love/Romance:"] = "Vie sentimentale/amoureuse&nbsp;:";
App::$strings["Work/employment:"] = "Travail/Occupation&nbsp;";
App::$strings["School/education:"] = "Études&nbsp;";
App::$strings["Like this thing"] = "J'aime ceci";
+App::$strings["User '%s' deleted"] = "Utilisateur '%s' supprimé";
+App::$strings["This event has been added to your calendar."] = "Cet évènement a été ajouté dans votre calendrier.";
+App::$strings["Not specified"] = "Non spécifié";
+App::$strings["Needs Action"] = "Besoin d'une action";
+App::$strings["Completed"] = "Terminé";
+App::$strings["In Process"] = "En cours";
+App::$strings["Cancelled"] = "Annulé";
+App::$strings["view full size"] = "voir en taille réelle";
+App::$strings["No Subject"] = "Pas d'objet";
+App::$strings["Friendica"] = "Friendica";
+App::$strings["OStatus"] = "OStatus";
+App::$strings["GNU-Social"] = "GNU-Social";
+App::$strings["RSS/Atom"] = "RSS/Atom";
+App::$strings["Diaspora"] = "Diaspora";
+App::$strings["Facebook"] = "Facebook";
+App::$strings["Zot"] = "Zot";
+App::$strings["LinkedIn"] = "Linkedin";
+App::$strings["XMPP/IM"] = "XMPP/IM";
+App::$strings["MySpace"] = "MySpace";
+App::$strings["New Page"] = "Nouvelle page";
+App::$strings["Select an alternate language"] = "Choisir une langue alternative";
+App::$strings["Who can see this?"] = "Qui peut voir cela";
+App::$strings["Custom selection"] = "Sélection personnalisée";
+App::$strings["Select \"Show\" to allow viewing. \"Don't show\" lets you override and limit the scope of \"Show\"."] = "Sélectionnez \"Afficher\" pour permettre l'affichage. \"Ne pas afficher\" vous permet de remplacer et de limiter la portée de \"Afficher\".";
+App::$strings["Show"] = "Montrer";
+App::$strings["Don't show"] = "Cacher";
+App::$strings["Post permissions %s cannot be changed %s after a post is shared.</br />These permissions set who is allowed to view the post."] = "Les autorisations d'accès d'un message %s ne peuvent pas être modifiées %s une fois le message envoyé. Ces autorisations définissent qui est autorisé à afficher le message.";
+App::$strings["Cannot locate DNS info for database server '%s'"] = "Impossible de trouver les infos DNS du serveur de BDD '%s'";
+App::$strings["Image/photo"] = "Image/photo";
+App::$strings["Encrypted content"] = "Contenu chiffré";
+App::$strings["Install %s element: "] = "Installer %s élément";
+App::$strings["This post contains an installable %s element, however you lack permissions to install it on this site."] = "Ce message contient un élément installable %s, mais vous n'avez pas l'autorisation de l'installer sur ce site.";
+App::$strings["%1\$s wrote the following %2\$s %3\$s"] = "%1\$s a écrit %2\$s qui suit %3\$s";
+App::$strings["Click to open/close"] = "Cliquer pour ouvrir/fermer";
+App::$strings["spoiler"] = "spoiler";
+App::$strings["$1 wrote:"] = "$1 a écrit&nbsp;:";
+App::$strings[" by "] = "par";
+App::$strings[" on "] = "sur";
+App::$strings["Embedded content"] = "Contenu imbriqué";
+App::$strings["Embedding disabled"] = "Imbrication désactivée";
App::$strings["General Features"] = "Fonctionnalités générales";
-App::$strings["Content Expiration"] = "Expiration du contenu";
-App::$strings["Remove posts/comments and/or private messages at a future time"] = "Supprimer les contributions/commentaires et/ou messages privés plus tard";
App::$strings["Multiple Profiles"] = "Profils multiples";
App::$strings["Ability to create multiple profiles"] = "Possibilité de créer plusieurs profils";
App::$strings["Advanced Profiles"] = "Profils Avancés";
@@ -2021,22 +2867,24 @@ App::$strings["Profile Import/Export"] = "Importer/Exporter le profil";
App::$strings["Save and load profile details across sites/channels"] = "Sauvegarder et charger les détails d'un profil entre sites/canaux";
App::$strings["Web Pages"] = "Pages web";
App::$strings["Provide managed web pages on your channel"] = "Fournir des pages web, sous votre contrôle, sur votre canal";
-App::$strings["Hide Rating"] = "Masquer l'évaluation";
-App::$strings["Hide the rating buttons on your channel and profile pages. Note: People can still rate you somewhere else."] = "Masquer les boutons d'évaluation sur les pages de votre canal et de votre profil. NB : vous pourrez toujours être évalué(e) ailleurs.";
+App::$strings["Provide a wiki for your channel"] = "Fournir un wiki pour votre canal.";
App::$strings["Private Notes"] = "Notes privées";
App::$strings["Enables a tool to store notes and reminders (note: not encrypted)"] = "Active un outil pour stocker des notes et des rappels (note&nbsp;:non chiffré)";
App::$strings["Navigation Channel Select"] = "Sélection du canal par la navigation";
App::$strings["Change channels directly from within the navigation dropdown menu"] = "Changez de canal directement depuis le menu de navigation déroulant";
App::$strings["Photo Location"] = "Site de prise de vue";
App::$strings["If location data is available on uploaded photos, link this to a map."] = "Si des informations géographiques sont présentes dans les images téléversées, les lier à une carte.";
-App::$strings["Access Controlled Chatrooms"] = "";
-App::$strings["Provide chatrooms and chat services with access control."] = "";
+App::$strings["Access Controlled Chatrooms"] = "Accéder au salons de discussions contrôlés.";
+App::$strings["Provide chatrooms and chat services with access control."] = "Fournir des salons de discussions et des services de discussions avec contrôle d'accès.";
+App::$strings["Provide alternate connection permission roles."] = "Fournir des rôles d'autorisation différents pour ce contact.";
App::$strings["Smart Birthdays"] = "Anniversaires intelligents";
App::$strings["Make birthday events timezone aware in case your friends are scattered across the planet."] = "Adapter les anniversaires aux fuseaux horaires, utile pour vos amis sur d'autres continents.";
-App::$strings["Expert Mode"] = "Mode expert";
-App::$strings["Enable Expert Mode to provide advanced configuration options"] = "Activer le mode expert pour accéder aux options avancées";
-App::$strings["Premium Channel"] = "Canal VIP";
-App::$strings["Allows you to set restrictions and terms on those that connect with your channel"] = "Vous permet d'appliquer des règles et restrictions aux contacts de votre canal";
+App::$strings["Event Timezone Selection"] = "Sélection du fuseau horaire de l'événement";
+App::$strings["Allow event creation in timezones other than your own."] = "Autorise la création d’événements sur d'autres fuseaux horaires que le vôtre.";
+App::$strings["Advanced Directory Search"] = "Recherche avancée dans les répertoires";
+App::$strings["Allows creation of complex directory search queries"] = "Autoriser la création d'entrées complexes de recherche de répertoire";
+App::$strings["Advanced Theme and Layout Settings"] = "Paramètres avancés du thème et de l'agencement.";
+App::$strings["Allows fine tuning of themes and page layouts"] = "Autoriser la personnalisation fine des thèmes et des agencements.";
App::$strings["Post Composition Features"] = "Fonctionnalités de composition";
App::$strings["Large Photos"] = "Grandes photos";
App::$strings["Include large (1024px) photo thumbnails in posts. If not enabled, use small (640px) photo thumbnails"] = "Inclure de grands aperçus (1024px) dans les messages. Si désactivé, inclure de petits aperçus (640px).";
@@ -2045,15 +2893,19 @@ App::$strings["Even More Encryption"] = "Encore plus de chiffrement";
App::$strings["Allow optional encryption of content end-to-end with a shared secret key"] = "Permettre le chiffrement optionnel du contenu de bout en bout au moyen d'un secret partagé";
App::$strings["Enable Voting Tools"] = "Activer les outils de vote";
App::$strings["Provide a class of post which others can vote on"] = "Fournit un type de publication sur lequel les utilisateurs peuvent voter";
+App::$strings["Disable Comments"] = "Désactiver les commentaires";
+App::$strings["Provide the option to disable comments for a post"] = "Fournir la possibilité de désactiver les commentaires pour une publication.";
App::$strings["Delayed Posting"] = "Publication plus tard";
App::$strings["Allow posts to be published at a later date"] = "Permettre de publier des messages à une date programmée";
+App::$strings["Content Expiration"] = "Expiration du contenu";
+App::$strings["Remove posts/comments and/or private messages at a future time"] = "Supprimer les contributions/commentaires et/ou messages privés plus tard";
App::$strings["Suppress Duplicate Posts/Comments"] = "Supprimer les publications/commentaires en doublon";
App::$strings["Prevent posts with identical content to be published with less than two minutes in between submissions."] = "Empêcher des messages aux contenus identiques d'être publiés à moins de deux minutes d'intervalle";
App::$strings["Network and Stream Filtering"] = "Filtrage du réseau et des flux";
App::$strings["Search by Date"] = "Chercher par date";
App::$strings["Ability to select posts by date ranges"] = "Pouvoir choisir des publications par date";
-App::$strings["Privacy Groups"] = "Groupes d'accès";
-App::$strings["Enable management and selection of privacy groups"] = "Active la gestion et la sélection des groupes d'accès";
+App::$strings["Privacy Groups"] = "Groupes de contacts";
+App::$strings["Enable management and selection of privacy groups"] = "Active la gestion et la sélection des groupes de contacts";
App::$strings["Save search terms for re-use"] = "Sauvegarder des termes de recherche pour utilisation ultérieure";
App::$strings["Network Personal Tab"] = "Onglet \"Me concernant\"";
App::$strings["Enable tab to display only Network posts that you've interacted on"] = "Activer un onglet affichant seulement les publications du réseau sur lesquelles vous êtes intervenu";
@@ -2061,16 +2913,16 @@ App::$strings["Network New Tab"] = "Onglet \"nouveautés réseau\"";
App::$strings["Enable tab to display all new Network activity"] = "Activer un onglet présentant toute l'activité récente sur le réseau";
App::$strings["Affinity Tool"] = "Gérer l'affinité";
App::$strings["Filter stream activity by depth of relationships"] = "Filtrer le flux d'activité en fonction de la profondeur des relations";
+App::$strings["Show friend and connection suggestions"] = "Afficher un ami et les suggestions de relations";
App::$strings["Connection Filtering"] = "Filtrage des contacts";
App::$strings["Filter incoming posts from connections based on keywords/content"] = "Filtrer les publications entrantes de mes contacts sur la base de mots-clefs";
-App::$strings["Show channel suggestions"] = "Montrer les suggestions de canaux";
App::$strings["Post/Comment Tools"] = "Gérer les publications/commentaires";
App::$strings["Community Tagging"] = "Etiquetage communautaire";
App::$strings["Ability to tag existing posts"] = "Permettre de marquer les publications existantes";
App::$strings["Post Categories"] = "Catégoriser les publications";
App::$strings["Add categories to your posts"] = "Ajouter des catégories à vos publications";
-App::$strings["Emoji Reactions"] = "";
-App::$strings["Add emoji reaction ability to posts"] = "";
+App::$strings["Emoji Reactions"] = "Réactions par émoticônes";
+App::$strings["Add emoji reaction ability to posts"] = "Ajouter la possibilité de réagir aux publications par émoticônes";
App::$strings["Ability to file posts under folders"] = "Permettre de classer les publications dans des dossiers";
App::$strings["Dislike Posts"] = "\"Ne pas aimer\" les publications";
App::$strings["Ability to dislike posts/comments"] = "Possibilité de \"ne pas aimer\" les publications/commentaires";
@@ -2078,21 +2930,35 @@ App::$strings["Star Posts"] = "Pouvoir mettre en avant les publications";
App::$strings["Ability to mark special posts with a star indicator"] = "Pouvoir marquer certaines publications d'une étoile";
App::$strings["Tag Cloud"] = "Nuage de tags";
App::$strings["Provide a personal tag cloud on your channel page"] = "Afficher un nuage de vos tags sur votre canal";
-App::$strings["Embedded content"] = "Contenu imbriqué";
-App::$strings["Embedding disabled"] = "Imbrication désactivée";
-App::$strings["Who can see this?"] = "";
-App::$strings["Custom selection"] = "";
-App::$strings["Select \"Show\" to allow viewing. \"Don't show\" lets you override and limit the scope of \"Show\"."] = "";
-App::$strings["Show"] = "Montrer";
-App::$strings["Don't show"] = "Cacher";
-App::$strings["Other networks and post services"] = "Autres réseaux et services de messagerie";
-App::$strings["Post permissions %s cannot be changed %s after a post is shared.</br />These permissions set who is allowed to view the post."] = "";
-App::$strings["Logged out."] = "Deconnecté.";
-App::$strings["Failed authentication"] = "Échec de l'authentification";
+App::$strings["Premium Channel"] = "Canal VIP";
+App::$strings["Allows you to set restrictions and terms on those that connect with your channel"] = "Vous permet d'appliquer des règles et restrictions aux contacts de votre canal";
+App::$strings["Tags"] = "Étiquettes";
+App::$strings["Keywords"] = "Mots-clefs";
+App::$strings["have"] = "ont";
+App::$strings["has"] = "a";
+App::$strings["want"] = "veulent";
+App::$strings["wants"] = "veut";
+App::$strings["likes"] = "aime";
+App::$strings["dislikes"] = "n'aime pas";
+App::$strings["Not a valid email address"] = "Ce n'est pas une adresse de courriel valide";
+App::$strings["Your email domain is not among those allowed on this site"] = "Votre domaine de courriel ne fait pas partie de ceux autorisés par ce site";
+App::$strings["Your email address is already registered at this site."] = "Votre adresse de courriel est déjà inscrite sur ce site.";
+App::$strings["An invitation is required."] = "Une invitation est requise.";
+App::$strings["Invitation could not be verified."] = "Votre invitation n'a pas pu être vérifiée.";
+App::$strings["Please enter the required information."] = "Merci d'entrer les informations requises.";
+App::$strings["Failed to store account information."] = "Impossible de stocker les informations liées au compte.";
+App::$strings["Registration confirmation for %s"] = "Confirmation de l'inscription pour %s";
+App::$strings["Registration request at %s"] = "Demande d'inscription sur %s";
+App::$strings["your registration password"] = "votre mot de passe d'inscription";
+App::$strings["Registration details for %s"] = "Détails de l'inscription pour %s";
+App::$strings["Account approved."] = "Compte approuvé.";
+App::$strings["Registration revoked for %s"] = "Inscription révoquée pour %s";
+App::$strings["Click here to upgrade."] = "Cliquez ici pour mettre à jour.";
+App::$strings["This action exceeds the limits set by your subscription plan."] = "Cette action outrepasserait les limites prévues par votre forfait.";
+App::$strings["This action is not available under your subscription plan."] = "Cette action n'est pas disponible avec votre forfait.";
App::$strings["Birthday"] = "Anniversaire";
App::$strings["Age: "] = "Age&nbsp;:";
App::$strings["YYYY-MM-DD or MM-DD"] = "AAAA-MM-JJ ou MM-JJ";
-App::$strings["never"] = "jamais";
App::$strings["less than a second ago"] = "à l'instant";
App::$strings["__ctx:e.g. 22 hours ago, 1 minute ago__ %1\$d %2\$s ago"] = "il y a %1\$d %2\$s";
App::$strings["__ctx:relative_date__ year"] = array(
@@ -2125,82 +2991,39 @@ App::$strings["__ctx:relative_date__ second"] = array(
);
App::$strings["%1\$s's birthday"] = "Anniversaire de %1\$s";
App::$strings["Happy Birthday %1\$s"] = "Joyeux Anniversaire %1\$s";
-App::$strings["A deleted group with this name was revived. Existing item permissions <strong>may</strong> apply to this group and any future members. If this is not what you intended, please create another group with a different name."] = "Un groupe supprimé portant ce nom a été ressuscité. Les permissions liées aux éléments existants <strong>peuvent</strong> s'appliquer au groupe et aux membres futurs. Si ce n'est pas ce que vous attendiez, merci de créer un autre groupe avec un nom différent.";
-App::$strings["Add new connections to this privacy group"] = "Ajouter de nouveaux contacts à ce groupe d'accès";
-App::$strings["edit"] = "modifier";
-App::$strings["Edit group"] = "Modifier le groupe";
-App::$strings["Add privacy group"] = "Ajouter un groupe d'accès";
-App::$strings["Channels not in any privacy group"] = "Canaux n'étant dans aucun groupe d'accès";
-App::$strings["Delete this item?"] = "Supprimer cet élément?";
-App::$strings["[-] show less"] = "[-] montrer moins";
-App::$strings["[+] expand"] = "[+] déplier";
-App::$strings["[-] collapse"] = "[-] replier";
-App::$strings["Password too short"] = "Mot de passe trop court";
-App::$strings["Passwords do not match"] = "Les mots de passe ne correspondent pas";
-App::$strings["everybody"] = "tout le monde";
-App::$strings["Secret Passphrase"] = "Phrase de passe secrète";
-App::$strings["Passphrase hint"] = "Indice pour la phrase de passe";
-App::$strings["Notice: Permissions have changed but have not yet been submitted."] = "Note&nbsp;: Les permissions ont changées, mais n'ont pas encore été sauvées.";
-App::$strings["close all"] = "fermer tout";
-App::$strings["Nothing new here"] = "Aucun nouveau contenu trouvé";
-App::$strings["Rate This Channel (this is public)"] = "Evaluer ce canal (publiquement)";
-App::$strings["Describe (optional)"] = "Description (facultative)";
-App::$strings["Please enter a link URL"] = "Merci d'insérer une URL";
-App::$strings["Unsaved changes. Are you sure you wish to leave this page?"] = "Changements en attente. Voulez-vous vraiment quitter cette page?";
-App::$strings["timeago.prefixAgo"] = "timeago.prefixAgo";
-App::$strings["timeago.prefixFromNow"] = "timeago.prefixFromNow";
-App::$strings["ago"] = "auparavant";
-App::$strings["from now"] = "de maintenant";
-App::$strings["less than a minute"] = "moins d'une minute";
-App::$strings["about a minute"] = "environ une minute";
-App::$strings["%d minutes"] = "%d minutes";
-App::$strings["about an hour"] = "environ une heure";
-App::$strings["about %d hours"] = "environ %d heures";
-App::$strings["a day"] = "un jour";
-App::$strings["%d days"] = "%d jours";
-App::$strings["about a month"] = "environ un mois";
-App::$strings["%d months"] = "%d mois";
-App::$strings["about a year"] = "environ un an";
-App::$strings["%d years"] = "%d années";
-App::$strings[" "] = "";
-App::$strings["timeago.numbers"] = "timeago.numbers";
-App::$strings["__ctx:long__ May"] = "Mai";
-App::$strings["Jan"] = "Jan";
-App::$strings["Feb"] = "Fev";
-App::$strings["Mar"] = "Mar";
-App::$strings["Apr"] = "Avr";
-App::$strings["__ctx:short__ May"] = "Mai";
-App::$strings["Jun"] = "Jun";
-App::$strings["Jul"] = "Jul";
-App::$strings["Aug"] = "Aou";
-App::$strings["Sep"] = "Sep";
-App::$strings["Oct"] = "Oct";
-App::$strings["Nov"] = "Nov";
-App::$strings["Dec"] = "Dec";
-App::$strings["Sun"] = "Dim";
-App::$strings["Mon"] = "Lun";
-App::$strings["Tue"] = "Mar";
-App::$strings["Wed"] = "Mer";
-App::$strings["Thu"] = "Jeu";
-App::$strings["Fri"] = "Ven";
-App::$strings["Sat"] = "Sam";
-App::$strings["__ctx:calendar__ today"] = "aujourd'hui";
-App::$strings["__ctx:calendar__ month"] = "mois";
-App::$strings["__ctx:calendar__ week"] = "semaine";
-App::$strings["__ctx:calendar__ day"] = "jour";
-App::$strings["__ctx:calendar__ All day"] = "Toute la journée";
-App::$strings["view full size"] = "voir en taille réelle";
-App::$strings["No Subject"] = "Pas d'objet";
-App::$strings["Friendica"] = "Friendica";
-App::$strings["OStatus"] = "OStatus";
-App::$strings["GNU-Social"] = "";
-App::$strings["RSS/Atom"] = "RSS/Atom";
-App::$strings["Diaspora"] = "Diaspora";
-App::$strings["Facebook"] = "Facebook";
-App::$strings["Zot"] = "Zot";
-App::$strings["LinkedIn"] = "Linkedin";
-App::$strings["XMPP/IM"] = "XMPP/IM";
-App::$strings["MySpace"] = "MySpace";
+App::$strings["Remote authentication"] = "Authentification distante";
+App::$strings["Click to authenticate to your home hub"] = "S'authentifier auprès de votre hub principal";
+App::$strings["End this session"] = "Mettre fin à la session";
+App::$strings["Your profile page"] = "Votre profil";
+App::$strings["Manage/Edit profiles"] = "Gérer/modifier vos profils";
+App::$strings["Edit your profile"] = "Modifier votre profil";
+App::$strings["Sign in"] = "Connexion";
+App::$strings["Take me home"] = "";
+App::$strings["Log me out of this site"] = "Déconnectez-moi de ce site";
+App::$strings["Create an account"] = "Créer un compte";
+App::$strings["Help and documentation"] = "Aide et documentation";
+App::$strings["Search site @name, #tag, ?docs, content"] = "Recherche @nom, #tag, contenu";
+App::$strings["Your grid"] = "Votre réseau";
+App::$strings["View your network/grid"] = "Voir votre réseau";
+App::$strings["Mark all grid notifications seen"] = "Marquer toutes les notifications du réseau comme vues";
+App::$strings["Channel home"] = "Mon canal";
+App::$strings["View your channel home"] = "Voir la page d'accueil de votre canal";
+App::$strings["Mark all channel notifications seen"] = "Marquer toutes les notifications du canal comme vues";
+App::$strings["Notices"] = "Notifications";
+App::$strings["Notifications"] = "Notifications";
+App::$strings["View all notifications"] = "Voir toutes les notifications";
+App::$strings["Private mail"] = "Messages privés";
+App::$strings["View your private messages"] = "Voir vos messages privés";
+App::$strings["Mark all private messages seen"] = "Marquer tous les messages privés comme vus";
+App::$strings["Event Calendar"] = "Calendrier des événements";
+App::$strings["View events"] = "Voir les événements";
+App::$strings["Mark all events seen"] = "Marquer tous les événements comme vus";
+App::$strings["Manage Your Channels"] = "Gérer vos canaux";
+App::$strings["Account/Channel Settings"] = "Paramètres du Compte/Canal";
+App::$strings["Site Setup and Configuration"] = "Configuration du site";
+App::$strings["@name, #tag, ?doc, content"] = "@nom, #étiquette, ?doc, contenu";
+App::$strings["Please wait..."] = "Merci de patienter...";
+App::$strings["Add Apps"] = "";
App::$strings["Image exceeds website size limit of %lu bytes"] = "L'image dépasse la taille limite de %lu octets";
App::$strings["Image file is empty."] = "L'image est vide.";
App::$strings["Photo storage failed."] = "Le stockage de l'image a échoué.";
@@ -2211,94 +3034,15 @@ App::$strings["Invalid data packet"] = "Paquet de données invalide";
App::$strings["Unable to verify channel signature"] = "Impossible de vérifier la signature du canal";
App::$strings["Unable to verify site signature for %s"] = "Impossible de vérifier la signature de site pour %s";
App::$strings["invalid target signature"] = "signature de la cible invalide";
-App::$strings["New Page"] = "Nouvelle page";
-App::$strings["Title"] = "Titre";
-App::$strings["Can view my normal stream and posts"] = "Peut voir les publications ordinaires sur mon canal.";
-App::$strings["Can view my default channel profile"] = "Peut voir le profil du canal par défaut.";
-App::$strings["Can view my connections"] = "Peut voir mes contacts";
-App::$strings["Can view my file storage and photos"] = "Peut voir mes fichiers et photos";
-App::$strings["Can view my webpages"] = "Peut voir mes pages web";
-App::$strings["Can send me their channel stream and posts"] = "Peuvent m'envoyer leur flux et les publications de leur canal";
-App::$strings["Can post on my channel page (\"wall\")"] = "Peuvent poster sur la page de mon canal (\"mur\")";
-App::$strings["Can comment on or like my posts"] = "Peuvent commenter et/ou aimer mes publications";
-App::$strings["Can send me private mail messages"] = "Peuvent m'envoyer des messages privés";
-App::$strings["Can like/dislike stuff"] = "Peuvent aimer/ne pas aimer";
-App::$strings["Profiles and things other than posts/comments"] = "Profils et autres excluant les publications/commentaires.";
-App::$strings["Can forward to all my channel contacts via post @mentions"] = "Peut faire suivre à tous les contacts de mon canal via \"@mention\"";
-App::$strings["Advanced - useful for creating group forum channels"] = "Avancé - utile pour les canaux de type \"forum/groupe\"";
-App::$strings["Can chat with me (when available)"] = "Peut discuter avec moi (quand disponibie)";
-App::$strings["Can write to my file storage and photos"] = "Peut charger des fichiers et des photos dans mon canal";
-App::$strings["Can edit my webpages"] = "Peut modifier mes pages web";
-App::$strings["Can source my public posts in derived channels"] = "Peut rediriger mes publications publiques vers des canaux dérivés";
-App::$strings["Somewhat advanced - very useful in open communities"] = "Plutôt avancé - très utile dans les communautés ouvertes";
-App::$strings["Can administer my channel resources"] = "Peut administrer les ressources de mon canal";
-App::$strings["Extremely advanced. Leave this alone unless you know what you are doing"] = "Très avancé. Ne pas toucher, sauf si vous savez ce que vous faîtes";
-App::$strings["Social Networking"] = "Réseau social";
-App::$strings["Social - Mostly Public"] = "Social - surtout public";
-App::$strings["Social - Restricted"] = "Social - restreint";
-App::$strings["Social - Private"] = "Social - privé";
-App::$strings["Community Forum"] = "Forum communautaire";
-App::$strings["Forum - Mostly Public"] = "Forum - surtout public";
-App::$strings["Forum - Restricted"] = "Forum - restreint";
-App::$strings["Forum - Private"] = "Forum - privé";
-App::$strings["Feed Republish"] = "Republication de flux";
-App::$strings["Feed - Mostly Public"] = "Flux - surtout public";
-App::$strings["Feed - Restricted"] = "Flux - restreint";
-App::$strings["Special Purpose"] = "Utilisation spécifique";
-App::$strings["Special - Celebrity/Soapbox"] = "Spécial - célébrité/promotion";
-App::$strings["Special - Group Repository"] = "Spécial - dépôt partagé";
-App::$strings["Custom/Expert Mode"] = "Mode expert/spécifique";
-App::$strings[" and "] = "et";
-App::$strings["public profile"] = "profil public";
-App::$strings["%1\$s changed %2\$s to &ldquo;%3\$s&rdquo;"] = "%1\$s a changé %2\$s en &ldquo;%3\$s&rdquo;";
-App::$strings["Visit %1\$s's %2\$s"] = "Visiter %2\$s de %1\$s";
-App::$strings["%1\$s has an updated %2\$s, changing %3\$s."] = "%1\$s a mis à jour %2\$s, modifiant %3\$s.";
-App::$strings["Attachments:"] = "Pièces jointes&nbsp;:";
-App::$strings["\$Projectname event notification:"] = "Notification d'événement de \$Projectname&nbsp;:";
-App::$strings["Focus (Hubzilla default)"] = "Focus (par défaut pour Hubzilla)";
-App::$strings["Theme settings"] = "Paramètres du thème";
-App::$strings["Select scheme"] = "Définir la palette de couleurs";
-App::$strings["Narrow navbar"] = "Barre de navigation fine";
-App::$strings["Navigation bar background color"] = "Couleur de fond de la barre de navigation";
-App::$strings["Navigation bar gradient top color"] = "Dégradé de la barre de navigation - couleur du haut";
-App::$strings["Navigation bar gradient bottom color"] = "Dégradé de la barre de navigation - couleur du bas";
-App::$strings["Navigation active button gradient top color"] = "Dégradé du bouton de navigation actif - couleur du haut";
-App::$strings["Navigation active button gradient bottom color"] = "Dégradé du bouton de navigation actif - couleur du bas";
-App::$strings["Navigation bar border color "] = "Couleur de la bordure de la barre de navigation";
-App::$strings["Navigation bar icon color "] = "Couleur des icônes de la barre de navigation";
-App::$strings["Navigation bar active icon color "] = "Couleur de l'icône active de la barre de navigation";
-App::$strings["link color"] = "couleur des liens";
-App::$strings["Set font-color for banner"] = "Définir la couleur du texte de la bannière";
-App::$strings["Set the background color"] = "Définir la couleur d'arrière-plan";
-App::$strings["Set the background image"] = "Définir l'image d'arrière-plan";
-App::$strings["Set the background color of items"] = "Définir la couleur de fond des contributions";
-App::$strings["Set the background color of comments"] = "Couleur de fond des commentaires";
-App::$strings["Set the border color of comments"] = "Couleur de la bordure des commentaires";
-App::$strings["Set the indent for comments"] = "Indentation des commentaires";
-App::$strings["Set the basic color for item icons"] = "Définir la couleur de base pour les icônes des éléments";
-App::$strings["Set the hover color for item icons"] = "Définir la couleur de survol des icônes des éléments";
-App::$strings["Set font-size for the entire application"] = "Définir la taille de police pour l'application entière";
-App::$strings["Example: 14px"] = "Exemple : 14px";
-App::$strings["Set font-size for posts and comments"] = "Définir la taille de police pour les contributions et commentaires";
-App::$strings["Set font-color for posts and comments"] = "Définir la couleur de police pour les contributions et commentaires";
-App::$strings["Set radius of corners"] = "Définir le rayon des arrondis";
-App::$strings["Set shadow depth of photos"] = "Définir la profondeur de l'ombre des photos";
-App::$strings["Set maximum width of content region in pixel"] = "Définir la largeur maximale de la zone des contenus";
-App::$strings["Leave empty for default width"] = "Laissez vide pour avoir la largeur par défaut";
-App::$strings["Left align page content"] = "Aligner à gauche le contenu de la page";
-App::$strings["Set minimum opacity of nav bar - to hide it"] = "Définir l'opacité minimum du bandeau de navigation - pour le cacher";
-App::$strings["Set size of conversation author photo"] = "Définir la taille de la photo de l'auteur d'une conversation";
-App::$strings["Set size of followup author photos"] = "Définir la taille de la photo de l'auteur d'une réponse";
-App::$strings["__ctx:opensearch__ Search %1\$s (%2\$s)"] = "";
-App::$strings["__ctx:opensearch__ \$Projectname"] = "";
-App::$strings["Update %s failed. See error logs."] = "La mise-à-jour %s a échoué. Merci de consulter les journaux d'erreur.";
-App::$strings["Update Error at %s"] = "Erreur de mise à jour sur %s";
-App::$strings["Create an account to access services and applications within the Hubzilla"] = "Créez un compte pour pouvoir accéder aux services et applications de Hubzilla";
-App::$strings["Password"] = "Mot de passe";
-App::$strings["Remember me"] = "Se souvenir de moi";
-App::$strings["Forgot your password?"] = "Mot de passe oublié&nbsp;?";
-App::$strings["toggle mobile"] = "(dés)activer mobile";
-App::$strings["Website SSL certificate is not valid. Please correct."] = "Le certificat SSL n'est pas valide. Corrigez le.";
-App::$strings["[hubzilla] Website SSL error for %s"] = "[hubzilla] Erreur SSL pour %s";
-App::$strings["Cron/Scheduled tasks not running."] = "Les taches planifiées ne tournent pas.";
-App::$strings["[hubzilla] Cron tasks not running on %s"] = "[hubzilla] Les tâches planifiées ne tournent pas sur %s";
+App::$strings["A deleted group with this name was revived. Existing item permissions <strong>may</strong> apply to this group and any future members. If this is not what you intended, please create another group with a different name."] = "Un groupe supprimé portant ce nom a été ressuscité. Les permissions liées aux éléments existants <strong>peuvent</strong> s'appliquer au groupe et aux membres futurs. Si ce n'est pas ce que vous attendiez, merci de créer un autre groupe avec un nom différent.";
+App::$strings["Add new connections to this privacy group"] = "Ajouter de nouveaux contacts à ce groupe de contacts";
+App::$strings["edit"] = "modifier";
+App::$strings["Edit group"] = "Modifier le groupe";
+App::$strings["Add privacy group"] = "Créer un groupe de contacts";
+App::$strings["Channels not in any privacy group"] = "Contacts n'étant dans aucun groupe de contacts";
+App::$strings["New window"] = "Nouvelle fenêtre";
+App::$strings["Open the selected location in a different window or browser tab"] = "Ouvrir l'emplacement dans une fenêtre ou un onglet différent";
+App::$strings["Logged out."] = "Deconnecté.";
+App::$strings["Failed authentication"] = "Échec de l'authentification";
+App::$strings["Help:"] = "Aide&nbsp;:";
+App::$strings["Not Found"] = "Introuvable";
diff --git a/view/fr/htconfig.tpl b/view/fr/htconfig.tpl
index fae8e3f98..ddc1d1053 100644
--- a/view/fr/htconfig.tpl
+++ b/view/fr/htconfig.tpl
@@ -35,15 +35,6 @@ App::$config['system']['baseurl'] = '{{$siteurl}}';
App::$config['system']['sitename'] = "Hubzilla";
App::$config['system']['location_hash'] = '{{$site_id}}';
-// Choices are 'basic', 'standard', and 'pro'.
-// basic sets up the sevrer for basic social networking and removes "complicated" features
-// standard provides most desired features except e-commerce
-// pro gives you access to everything
-
-App::$config['system']['server_role'] = '{{$server_role}}';
-
-
-
// These lines set additional security headers to be sent with all responses
// You may wish to set transport_security_header to 0 if your server already sends
// this header. content_security_policy may need to be disabled if you wish to
diff --git a/view/it/htconfig.tpl b/view/it/htconfig.tpl
index ea3f5b5c2..5acb0ebe2 100644
--- a/view/it/htconfig.tpl
+++ b/view/it/htconfig.tpl
@@ -34,14 +34,6 @@ App::$config['system']['baseurl'] = '{{$siteurl}}';
App::$config['system']['sitename'] = "Hubzilla";
App::$config['system']['location_hash'] = '{{$site_id}}';
-// Choices are 'basic', 'standard', and 'pro'.
-// basic sets up the sevrer for basic social networking and removes "complicated" features
-// standard provides most desired features except e-commerce
-// pro gives you access to everything
-
-App::$config['system']['server_role'] = '{{$server_role}}';
-
-
// These lines set additional security headers to be sent with all responses
// You may wish to set transport_security_header to 0 if your server already sends
// this header. content_security_policy may need to be disabled if you wish to
diff --git a/view/js/acl.js b/view/js/acl.js
index 4dd60d303..e016158e9 100644
--- a/view/js/acl.js
+++ b/view/js/acl.js
@@ -333,20 +333,20 @@ ACL.prototype.update_view = function(value) {
type = itemid[0];
id = itemid.substr(1);
- btshow = $(this).children(".acl-button-show").removeClass("btn-success").addClass("btn-default");
- bthide = $(this).children(".acl-button-hide").removeClass("btn-danger").addClass("btn-default");
+ btshow = $(this).children(".acl-button-show").removeClass("btn-success").addClass("btn-outline-success");
+ bthide = $(this).children(".acl-button-hide").removeClass("btn-danger").addClass("btn-outline-danger");
switch(type) {
case "g":
var uclass = "";
if (that.allow_gid.indexOf(id)>=0) {
- btshow.removeClass("btn-default").addClass("btn-success");
- bthide.removeClass("btn-danger").addClass("btn-default");
+ btshow.removeClass("btn-outline-success").addClass("btn-success");
+ bthide.removeClass("btn-danger").addClass("btn-outline-danger");
uclass="groupshow";
}
if (that.deny_gid.indexOf(id)>=0) {
- btshow.removeClass("btn-success").addClass("btn-default");
- bthide.removeClass("btn-default").addClass("btn-danger");
+ btshow.removeClass("btn-success").addClass("btn-outline-success");
+ bthide.removeClass("btn-outline-danger").addClass("btn-danger");
uclass = "grouphide";
}
$(that.group_uids[id]).each(function(i, v) {
@@ -366,13 +366,13 @@ ACL.prototype.update_view = function(value) {
case "c":
if (that.allow_cid.indexOf(id)>=0){
if(!$(this).hasClass("grouphide") ) {
- btshow.removeClass("btn-default").addClass("btn-success");
- bthide.removeClass("btn-danger").addClass("btn-default");
+ btshow.removeClass("btn-outline-success").addClass("btn-success");
+ bthide.removeClass("btn-danger").addClass("btn-outline-danger");
}
}
if (that.deny_cid.indexOf(id)>=0){
- btshow.removeClass("btn-success").addClass("btn-default");
- bthide.removeClass("btn-default").addClass("btn-danger");
+ btshow.removeClass("btn-success").addClass("btn-outline-success");
+ bthide.removeClass("btn-outline-danger").addClass("btn-danger");
$(this).removeClass("groupshow");
}
}
diff --git a/view/js/autocomplete.js b/view/js/autocomplete.js
index 5a616b6fc..08cf97173 100644
--- a/view/js/autocomplete.js
+++ b/view/js/autocomplete.js
@@ -5,7 +5,7 @@
*/
function contact_search(term, callback, backend_url, type, extra_channels, spinelement) {
if(spinelement) {
- $(spinelement).spin('tiny');
+ $(spinelement).show();
}
// Check if there is a cached result that contains the same information we would get with a full server-side search
var bt = backend_url+type;
@@ -14,7 +14,7 @@ function contact_search(term, callback, backend_url, type, extra_channels, spine
var lterm = term.toLowerCase(); // Ignore case
for(var t in contact_search.cache[bt]) {
if(lterm.indexOf(t) >= 0) { // A more broad search has been performed already, so use those results
- $(spinelement).spin(false);
+ $(spinelement).hide();
// Filter old results locally
var matching = contact_search.cache[bt][t].filter(function (x) { return (x.name.toLowerCase().indexOf(lterm) >= 0 || (typeof x.nick !== 'undefined' && x.nick.toLowerCase().indexOf(lterm) >= 0)); }); // Need to check that nick exists because groups don't have one
matching.unshift({taggable:false, text: term, replace: term});
@@ -47,7 +47,7 @@ function contact_search(term, callback, backend_url, type, extra_channels, spine
var items = data.items.slice(0);
items.unshift({taggable:false, text: term, replace: term});
callback(items);
- $(spinelement).spin(false);
+ $(spinelement).hide();
},
}).fail(function () {callback([]); }); // Callback must be invoked even if something went wrong.
}
@@ -60,12 +60,20 @@ function contact_format(item) {
var desc = ((item.label) ? item.nick + ' ' + item.label : item.nick);
if(typeof desc === 'undefined') desc = '';
if(desc) desc = ' ('+desc+')';
- return "<div class='{0}' title='{4}'><img class='dropdown-menu-img-sm' src='{1}'><span class='contactname'>{2}</span><span class='dropdown-sub-text'>{3}</span><div class='clear'></div></div>".format(item.taggable, item.photo, item.name, desc, item.link);
+ return "<div class='{0} dropdown-item dropdown-notification clearfix' title='{4}'><img class='menu-img-2' src='{1}'><span class='contactname'>{2}</span><span class='dropdown-sub-text'>{3}</span></div>".format(item.taggable, item.photo, item.name, desc, item.link);
}
else
return "<div>" + item.text + "</div>";
}
+function smiley_format(item) {
+ return "<div class='dropdown-item'>" + item.icon + ' ' + item.text + "</div>";
+}
+
+function bbco_format(item) {
+ return "<div class='dropdown-item'>" + item + "</div>";
+}
+
function editor_replace(item) {
if(typeof item.replace !== 'undefined') {
return '$1$2' + item.replace;
@@ -181,18 +189,29 @@ function string2bb(element) {
index: 3,
search: function(term, callback) { contact_search(term, callback, backend_url, 'c', extra_channels, spinelement=false); },
replace: editor_replace,
- template: contact_format,
+ template: contact_format
+ };
+
+ // Autocomplete forums
+ forums = {
+ match: /(^|\s)(\!)([^ \n]+)$/,
+ index: 3,
+ search: function(term, callback) { contact_search(term, callback, backend_url, 'f', extra_channels, spinelement=false); },
+ replace: editor_replace,
+ template: contact_format
};
+
smilies = {
match: /(^|\s)(:[a-z_:]{2,})$/,
index: 2,
search: function(term, callback) { $.getJSON('/smilies/json').done(function(data) { callback($.map(data, function(entry) { return entry.text.indexOf(term) === 0 ? entry : null; })); }); },
- template: function(item) { return item.icon + item.text; },
+ //template: function(item) { return item.icon + item.text; },
replace: function(item) { return "$1" + item.text + ' '; },
+ template: smiley_format
};
this.attr('autocomplete','off');
- this.textcomplete([contacts,smilies], {className:'acpopup', zIndex:1020});
+ this.textcomplete([contacts,forums,smilies], {className:'acpopup', zIndex:1020});
};
})( jQuery );
@@ -321,7 +340,8 @@ function string2bb(element) {
else {
return '\[' + element + '\] ';
}
- }
+ },
+ template: bbco_format
};
this.attr('autocomplete','off');
diff --git a/view/js/jquery.js b/view/js/jquery.js
index 046447ce9..9ddbf00a9 100644
--- a/view/js/jquery.js
+++ b/view/js/jquery.js
@@ -1,5 +1,5 @@
-/*! jQuery v3.1.0 | (c) jQuery Foundation | jquery.org/license */
-!function(a,b){"use strict";"object"==typeof module&&"object"==typeof module.exports?module.exports=a.document?b(a,!0):function(a){if(!a.document)throw new Error("jQuery requires a window with a document");return b(a)}:b(a)}("undefined"!=typeof window?window:this,function(a,b){"use strict";var c=[],d=a.document,e=Object.getPrototypeOf,f=c.slice,g=c.concat,h=c.push,i=c.indexOf,j={},k=j.toString,l=j.hasOwnProperty,m=l.toString,n=m.call(Object),o={};function p(a,b){b=b||d;var c=b.createElement("script");c.text=a,b.head.appendChild(c).parentNode.removeChild(c)}var q="3.1.0",r=function(a,b){return new r.fn.init(a,b)},s=/^[\s\uFEFF\xA0]+|[\s\uFEFF\xA0]+$/g,t=/^-ms-/,u=/-([a-z])/g,v=function(a,b){return b.toUpperCase()};r.fn=r.prototype={jquery:q,constructor:r,length:0,toArray:function(){return f.call(this)},get:function(a){return null!=a?a<0?this[a+this.length]:this[a]:f.call(this)},pushStack:function(a){var b=r.merge(this.constructor(),a);return b.prevObject=this,b},each:function(a){return r.each(this,a)},map:function(a){return this.pushStack(r.map(this,function(b,c){return a.call(b,c,b)}))},slice:function(){return this.pushStack(f.apply(this,arguments))},first:function(){return this.eq(0)},last:function(){return this.eq(-1)},eq:function(a){var b=this.length,c=+a+(a<0?b:0);return this.pushStack(c>=0&&c<b?[this[c]]:[])},end:function(){return this.prevObject||this.constructor()},push:h,sort:c.sort,splice:c.splice},r.extend=r.fn.extend=function(){var a,b,c,d,e,f,g=arguments[0]||{},h=1,i=arguments.length,j=!1;for("boolean"==typeof g&&(j=g,g=arguments[h]||{},h++),"object"==typeof g||r.isFunction(g)||(g={}),h===i&&(g=this,h--);h<i;h++)if(null!=(a=arguments[h]))for(b in a)c=g[b],d=a[b],g!==d&&(j&&d&&(r.isPlainObject(d)||(e=r.isArray(d)))?(e?(e=!1,f=c&&r.isArray(c)?c:[]):f=c&&r.isPlainObject(c)?c:{},g[b]=r.extend(j,f,d)):void 0!==d&&(g[b]=d));return g},r.extend({expando:"jQuery"+(q+Math.random()).replace(/\D/g,""),isReady:!0,error:function(a){throw new Error(a)},noop:function(){},isFunction:function(a){return"function"===r.type(a)},isArray:Array.isArray,isWindow:function(a){return null!=a&&a===a.window},isNumeric:function(a){var b=r.type(a);return("number"===b||"string"===b)&&!isNaN(a-parseFloat(a))},isPlainObject:function(a){var b,c;return!(!a||"[object Object]"!==k.call(a))&&(!(b=e(a))||(c=l.call(b,"constructor")&&b.constructor,"function"==typeof c&&m.call(c)===n))},isEmptyObject:function(a){var b;for(b in a)return!1;return!0},type:function(a){return null==a?a+"":"object"==typeof a||"function"==typeof a?j[k.call(a)]||"object":typeof a},globalEval:function(a){p(a)},camelCase:function(a){return a.replace(t,"ms-").replace(u,v)},nodeName:function(a,b){return a.nodeName&&a.nodeName.toLowerCase()===b.toLowerCase()},each:function(a,b){var c,d=0;if(w(a)){for(c=a.length;d<c;d++)if(b.call(a[d],d,a[d])===!1)break}else for(d in a)if(b.call(a[d],d,a[d])===!1)break;return a},trim:function(a){return null==a?"":(a+"").replace(s,"")},makeArray:function(a,b){var c=b||[];return null!=a&&(w(Object(a))?r.merge(c,"string"==typeof a?[a]:a):h.call(c,a)),c},inArray:function(a,b,c){return null==b?-1:i.call(b,a,c)},merge:function(a,b){for(var c=+b.length,d=0,e=a.length;d<c;d++)a[e++]=b[d];return a.length=e,a},grep:function(a,b,c){for(var d,e=[],f=0,g=a.length,h=!c;f<g;f++)d=!b(a[f],f),d!==h&&e.push(a[f]);return e},map:function(a,b,c){var d,e,f=0,h=[];if(w(a))for(d=a.length;f<d;f++)e=b(a[f],f,c),null!=e&&h.push(e);else for(f in a)e=b(a[f],f,c),null!=e&&h.push(e);return g.apply([],h)},guid:1,proxy:function(a,b){var c,d,e;if("string"==typeof b&&(c=a[b],b=a,a=c),r.isFunction(a))return d=f.call(arguments,2),e=function(){return a.apply(b||this,d.concat(f.call(arguments)))},e.guid=a.guid=a.guid||r.guid++,e},now:Date.now,support:o}),"function"==typeof Symbol&&(r.fn[Symbol.iterator]=c[Symbol.iterator]),r.each("Boolean Number String Function Array Date RegExp Object Error Symbol".split(" "),function(a,b){j["[object "+b+"]"]=b.toLowerCase()});function w(a){var b=!!a&&"length"in a&&a.length,c=r.type(a);return"function"!==c&&!r.isWindow(a)&&("array"===c||0===b||"number"==typeof b&&b>0&&b-1 in a)}var x=function(a){var b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u="sizzle"+1*new Date,v=a.document,w=0,x=0,y=ha(),z=ha(),A=ha(),B=function(a,b){return a===b&&(l=!0),0},C={}.hasOwnProperty,D=[],E=D.pop,F=D.push,G=D.push,H=D.slice,I=function(a,b){for(var c=0,d=a.length;c<d;c++)if(a[c]===b)return c;return-1},J="checked|selected|async|autofocus|autoplay|controls|defer|disabled|hidden|ismap|loop|multiple|open|readonly|required|scoped",K="[\\x20\\t\\r\\n\\f]",L="(?:\\\\.|[\\w-]|[^\0-\\xa0])+",M="\\["+K+"*("+L+")(?:"+K+"*([*^$|!~]?=)"+K+"*(?:'((?:\\\\.|[^\\\\'])*)'|\"((?:\\\\.|[^\\\\\"])*)\"|("+L+"))|)"+K+"*\\]",N=":("+L+")(?:\\((('((?:\\\\.|[^\\\\'])*)'|\"((?:\\\\.|[^\\\\\"])*)\")|((?:\\\\.|[^\\\\()[\\]]|"+M+")*)|.*)\\)|)",O=new RegExp(K+"+","g"),P=new RegExp("^"+K+"+|((?:^|[^\\\\])(?:\\\\.)*)"+K+"+$","g"),Q=new RegExp("^"+K+"*,"+K+"*"),R=new RegExp("^"+K+"*([>+~]|"+K+")"+K+"*"),S=new RegExp("="+K+"*([^\\]'\"]*?)"+K+"*\\]","g"),T=new RegExp(N),U=new RegExp("^"+L+"$"),V={ID:new RegExp("^#("+L+")"),CLASS:new RegExp("^\\.("+L+")"),TAG:new RegExp("^("+L+"|[*])"),ATTR:new RegExp("^"+M),PSEUDO:new RegExp("^"+N),CHILD:new RegExp("^:(only|first|last|nth|nth-last)-(child|of-type)(?:\\("+K+"*(even|odd|(([+-]|)(\\d*)n|)"+K+"*(?:([+-]|)"+K+"*(\\d+)|))"+K+"*\\)|)","i"),bool:new RegExp("^(?:"+J+")$","i"),needsContext:new RegExp("^"+K+"*[>+~]|:(even|odd|eq|gt|lt|nth|first|last)(?:\\("+K+"*((?:-\\d)?\\d*)"+K+"*\\)|)(?=[^-]|$)","i")},W=/^(?:input|select|textarea|button)$/i,X=/^h\d$/i,Y=/^[^{]+\{\s*\[native \w/,Z=/^(?:#([\w-]+)|(\w+)|\.([\w-]+))$/,$=/[+~]/,_=new RegExp("\\\\([\\da-f]{1,6}"+K+"?|("+K+")|.)","ig"),aa=function(a,b,c){var d="0x"+b-65536;return d!==d||c?b:d<0?String.fromCharCode(d+65536):String.fromCharCode(d>>10|55296,1023&d|56320)},ba=/([\0-\x1f\x7f]|^-?\d)|^-$|[^\x80-\uFFFF\w-]/g,ca=function(a,b){return b?"\0"===a?"\ufffd":a.slice(0,-1)+"\\"+a.charCodeAt(a.length-1).toString(16)+" ":"\\"+a},da=function(){m()},ea=ta(function(a){return a.disabled===!0},{dir:"parentNode",next:"legend"});try{G.apply(D=H.call(v.childNodes),v.childNodes),D[v.childNodes.length].nodeType}catch(fa){G={apply:D.length?function(a,b){F.apply(a,H.call(b))}:function(a,b){var c=a.length,d=0;while(a[c++]=b[d++]);a.length=c-1}}}function ga(a,b,d,e){var f,h,j,k,l,o,r,s=b&&b.ownerDocument,w=b?b.nodeType:9;if(d=d||[],"string"!=typeof a||!a||1!==w&&9!==w&&11!==w)return d;if(!e&&((b?b.ownerDocument||b:v)!==n&&m(b),b=b||n,p)){if(11!==w&&(l=Z.exec(a)))if(f=l[1]){if(9===w){if(!(j=b.getElementById(f)))return d;if(j.id===f)return d.push(j),d}else if(s&&(j=s.getElementById(f))&&t(b,j)&&j.id===f)return d.push(j),d}else{if(l[2])return G.apply(d,b.getElementsByTagName(a)),d;if((f=l[3])&&c.getElementsByClassName&&b.getElementsByClassName)return G.apply(d,b.getElementsByClassName(f)),d}if(c.qsa&&!A[a+" "]&&(!q||!q.test(a))){if(1!==w)s=b,r=a;else if("object"!==b.nodeName.toLowerCase()){(k=b.getAttribute("id"))?k=k.replace(ba,ca):b.setAttribute("id",k=u),o=g(a),h=o.length;while(h--)o[h]="#"+k+" "+sa(o[h]);r=o.join(","),s=$.test(a)&&qa(b.parentNode)||b}if(r)try{return G.apply(d,s.querySelectorAll(r)),d}catch(x){}finally{k===u&&b.removeAttribute("id")}}}return i(a.replace(P,"$1"),b,d,e)}function ha(){var a=[];function b(c,e){return a.push(c+" ")>d.cacheLength&&delete b[a.shift()],b[c+" "]=e}return b}function ia(a){return a[u]=!0,a}function ja(a){var b=n.createElement("fieldset");try{return!!a(b)}catch(c){return!1}finally{b.parentNode&&b.parentNode.removeChild(b),b=null}}function ka(a,b){var c=a.split("|"),e=c.length;while(e--)d.attrHandle[c[e]]=b}function la(a,b){var c=b&&a,d=c&&1===a.nodeType&&1===b.nodeType&&a.sourceIndex-b.sourceIndex;if(d)return d;if(c)while(c=c.nextSibling)if(c===b)return-1;return a?1:-1}function ma(a){return function(b){var c=b.nodeName.toLowerCase();return"input"===c&&b.type===a}}function na(a){return function(b){var c=b.nodeName.toLowerCase();return("input"===c||"button"===c)&&b.type===a}}function oa(a){return function(b){return"label"in b&&b.disabled===a||"form"in b&&b.disabled===a||"form"in b&&b.disabled===!1&&(b.isDisabled===a||b.isDisabled!==!a&&("label"in b||!ea(b))!==a)}}function pa(a){return ia(function(b){return b=+b,ia(function(c,d){var e,f=a([],c.length,b),g=f.length;while(g--)c[e=f[g]]&&(c[e]=!(d[e]=c[e]))})})}function qa(a){return a&&"undefined"!=typeof a.getElementsByTagName&&a}c=ga.support={},f=ga.isXML=function(a){var b=a&&(a.ownerDocument||a).documentElement;return!!b&&"HTML"!==b.nodeName},m=ga.setDocument=function(a){var b,e,g=a?a.ownerDocument||a:v;return g!==n&&9===g.nodeType&&g.documentElement?(n=g,o=n.documentElement,p=!f(n),v!==n&&(e=n.defaultView)&&e.top!==e&&(e.addEventListener?e.addEventListener("unload",da,!1):e.attachEvent&&e.attachEvent("onunload",da)),c.attributes=ja(function(a){return a.className="i",!a.getAttribute("className")}),c.getElementsByTagName=ja(function(a){return a.appendChild(n.createComment("")),!a.getElementsByTagName("*").length}),c.getElementsByClassName=Y.test(n.getElementsByClassName),c.getById=ja(function(a){return o.appendChild(a).id=u,!n.getElementsByName||!n.getElementsByName(u).length}),c.getById?(d.find.ID=function(a,b){if("undefined"!=typeof b.getElementById&&p){var c=b.getElementById(a);return c?[c]:[]}},d.filter.ID=function(a){var b=a.replace(_,aa);return function(a){return a.getAttribute("id")===b}}):(delete d.find.ID,d.filter.ID=function(a){var b=a.replace(_,aa);return function(a){var c="undefined"!=typeof a.getAttributeNode&&a.getAttributeNode("id");return c&&c.value===b}}),d.find.TAG=c.getElementsByTagName?function(a,b){return"undefined"!=typeof b.getElementsByTagName?b.getElementsByTagName(a):c.qsa?b.querySelectorAll(a):void 0}:function(a,b){var c,d=[],e=0,f=b.getElementsByTagName(a);if("*"===a){while(c=f[e++])1===c.nodeType&&d.push(c);return d}return f},d.find.CLASS=c.getElementsByClassName&&function(a,b){if("undefined"!=typeof b.getElementsByClassName&&p)return b.getElementsByClassName(a)},r=[],q=[],(c.qsa=Y.test(n.querySelectorAll))&&(ja(function(a){o.appendChild(a).innerHTML="<a id='"+u+"'></a><select id='"+u+"-\r\\' msallowcapture=''><option selected=''></option></select>",a.querySelectorAll("[msallowcapture^='']").length&&q.push("[*^$]="+K+"*(?:''|\"\")"),a.querySelectorAll("[selected]").length||q.push("\\["+K+"*(?:value|"+J+")"),a.querySelectorAll("[id~="+u+"-]").length||q.push("~="),a.querySelectorAll(":checked").length||q.push(":checked"),a.querySelectorAll("a#"+u+"+*").length||q.push(".#.+[+~]")}),ja(function(a){a.innerHTML="<a href='' disabled='disabled'></a><select disabled='disabled'><option/></select>";var b=n.createElement("input");b.setAttribute("type","hidden"),a.appendChild(b).setAttribute("name","D"),a.querySelectorAll("[name=d]").length&&q.push("name"+K+"*[*^$|!~]?="),2!==a.querySelectorAll(":enabled").length&&q.push(":enabled",":disabled"),o.appendChild(a).disabled=!0,2!==a.querySelectorAll(":disabled").length&&q.push(":enabled",":disabled"),a.querySelectorAll("*,:x"),q.push(",.*:")})),(c.matchesSelector=Y.test(s=o.matches||o.webkitMatchesSelector||o.mozMatchesSelector||o.oMatchesSelector||o.msMatchesSelector))&&ja(function(a){c.disconnectedMatch=s.call(a,"*"),s.call(a,"[s!='']:x"),r.push("!=",N)}),q=q.length&&new RegExp(q.join("|")),r=r.length&&new RegExp(r.join("|")),b=Y.test(o.compareDocumentPosition),t=b||Y.test(o.contains)?function(a,b){var c=9===a.nodeType?a.documentElement:a,d=b&&b.parentNode;return a===d||!(!d||1!==d.nodeType||!(c.contains?c.contains(d):a.compareDocumentPosition&&16&a.compareDocumentPosition(d)))}:function(a,b){if(b)while(b=b.parentNode)if(b===a)return!0;return!1},B=b?function(a,b){if(a===b)return l=!0,0;var d=!a.compareDocumentPosition-!b.compareDocumentPosition;return d?d:(d=(a.ownerDocument||a)===(b.ownerDocument||b)?a.compareDocumentPosition(b):1,1&d||!c.sortDetached&&b.compareDocumentPosition(a)===d?a===n||a.ownerDocument===v&&t(v,a)?-1:b===n||b.ownerDocument===v&&t(v,b)?1:k?I(k,a)-I(k,b):0:4&d?-1:1)}:function(a,b){if(a===b)return l=!0,0;var c,d=0,e=a.parentNode,f=b.parentNode,g=[a],h=[b];if(!e||!f)return a===n?-1:b===n?1:e?-1:f?1:k?I(k,a)-I(k,b):0;if(e===f)return la(a,b);c=a;while(c=c.parentNode)g.unshift(c);c=b;while(c=c.parentNode)h.unshift(c);while(g[d]===h[d])d++;return d?la(g[d],h[d]):g[d]===v?-1:h[d]===v?1:0},n):n},ga.matches=function(a,b){return ga(a,null,null,b)},ga.matchesSelector=function(a,b){if((a.ownerDocument||a)!==n&&m(a),b=b.replace(S,"='$1']"),c.matchesSelector&&p&&!A[b+" "]&&(!r||!r.test(b))&&(!q||!q.test(b)))try{var d=s.call(a,b);if(d||c.disconnectedMatch||a.document&&11!==a.document.nodeType)return d}catch(e){}return ga(b,n,null,[a]).length>0},ga.contains=function(a,b){return(a.ownerDocument||a)!==n&&m(a),t(a,b)},ga.attr=function(a,b){(a.ownerDocument||a)!==n&&m(a);var e=d.attrHandle[b.toLowerCase()],f=e&&C.call(d.attrHandle,b.toLowerCase())?e(a,b,!p):void 0;return void 0!==f?f:c.attributes||!p?a.getAttribute(b):(f=a.getAttributeNode(b))&&f.specified?f.value:null},ga.escape=function(a){return(a+"").replace(ba,ca)},ga.error=function(a){throw new Error("Syntax error, unrecognized expression: "+a)},ga.uniqueSort=function(a){var b,d=[],e=0,f=0;if(l=!c.detectDuplicates,k=!c.sortStable&&a.slice(0),a.sort(B),l){while(b=a[f++])b===a[f]&&(e=d.push(f));while(e--)a.splice(d[e],1)}return k=null,a},e=ga.getText=function(a){var b,c="",d=0,f=a.nodeType;if(f){if(1===f||9===f||11===f){if("string"==typeof a.textContent)return a.textContent;for(a=a.firstChild;a;a=a.nextSibling)c+=e(a)}else if(3===f||4===f)return a.nodeValue}else while(b=a[d++])c+=e(b);return c},d=ga.selectors={cacheLength:50,createPseudo:ia,match:V,attrHandle:{},find:{},relative:{">":{dir:"parentNode",first:!0}," ":{dir:"parentNode"},"+":{dir:"previousSibling",first:!0},"~":{dir:"previousSibling"}},preFilter:{ATTR:function(a){return a[1]=a[1].replace(_,aa),a[3]=(a[3]||a[4]||a[5]||"").replace(_,aa),"~="===a[2]&&(a[3]=" "+a[3]+" "),a.slice(0,4)},CHILD:function(a){return a[1]=a[1].toLowerCase(),"nth"===a[1].slice(0,3)?(a[3]||ga.error(a[0]),a[4]=+(a[4]?a[5]+(a[6]||1):2*("even"===a[3]||"odd"===a[3])),a[5]=+(a[7]+a[8]||"odd"===a[3])):a[3]&&ga.error(a[0]),a},PSEUDO:function(a){var b,c=!a[6]&&a[2];return V.CHILD.test(a[0])?null:(a[3]?a[2]=a[4]||a[5]||"":c&&T.test(c)&&(b=g(c,!0))&&(b=c.indexOf(")",c.length-b)-c.length)&&(a[0]=a[0].slice(0,b),a[2]=c.slice(0,b)),a.slice(0,3))}},filter:{TAG:function(a){var b=a.replace(_,aa).toLowerCase();return"*"===a?function(){return!0}:function(a){return a.nodeName&&a.nodeName.toLowerCase()===b}},CLASS:function(a){var b=y[a+" "];return b||(b=new RegExp("(^|"+K+")"+a+"("+K+"|$)"))&&y(a,function(a){return b.test("string"==typeof a.className&&a.className||"undefined"!=typeof a.getAttribute&&a.getAttribute("class")||"")})},ATTR:function(a,b,c){return function(d){var e=ga.attr(d,a);return null==e?"!="===b:!b||(e+="","="===b?e===c:"!="===b?e!==c:"^="===b?c&&0===e.indexOf(c):"*="===b?c&&e.indexOf(c)>-1:"$="===b?c&&e.slice(-c.length)===c:"~="===b?(" "+e.replace(O," ")+" ").indexOf(c)>-1:"|="===b&&(e===c||e.slice(0,c.length+1)===c+"-"))}},CHILD:function(a,b,c,d,e){var f="nth"!==a.slice(0,3),g="last"!==a.slice(-4),h="of-type"===b;return 1===d&&0===e?function(a){return!!a.parentNode}:function(b,c,i){var j,k,l,m,n,o,p=f!==g?"nextSibling":"previousSibling",q=b.parentNode,r=h&&b.nodeName.toLowerCase(),s=!i&&!h,t=!1;if(q){if(f){while(p){m=b;while(m=m[p])if(h?m.nodeName.toLowerCase()===r:1===m.nodeType)return!1;o=p="only"===a&&!o&&"nextSibling"}return!0}if(o=[g?q.firstChild:q.lastChild],g&&s){m=q,l=m[u]||(m[u]={}),k=l[m.uniqueID]||(l[m.uniqueID]={}),j=k[a]||[],n=j[0]===w&&j[1],t=n&&j[2],m=n&&q.childNodes[n];while(m=++n&&m&&m[p]||(t=n=0)||o.pop())if(1===m.nodeType&&++t&&m===b){k[a]=[w,n,t];break}}else if(s&&(m=b,l=m[u]||(m[u]={}),k=l[m.uniqueID]||(l[m.uniqueID]={}),j=k[a]||[],n=j[0]===w&&j[1],t=n),t===!1)while(m=++n&&m&&m[p]||(t=n=0)||o.pop())if((h?m.nodeName.toLowerCase()===r:1===m.nodeType)&&++t&&(s&&(l=m[u]||(m[u]={}),k=l[m.uniqueID]||(l[m.uniqueID]={}),k[a]=[w,t]),m===b))break;return t-=e,t===d||t%d===0&&t/d>=0}}},PSEUDO:function(a,b){var c,e=d.pseudos[a]||d.setFilters[a.toLowerCase()]||ga.error("unsupported pseudo: "+a);return e[u]?e(b):e.length>1?(c=[a,a,"",b],d.setFilters.hasOwnProperty(a.toLowerCase())?ia(function(a,c){var d,f=e(a,b),g=f.length;while(g--)d=I(a,f[g]),a[d]=!(c[d]=f[g])}):function(a){return e(a,0,c)}):e}},pseudos:{not:ia(function(a){var b=[],c=[],d=h(a.replace(P,"$1"));return d[u]?ia(function(a,b,c,e){var f,g=d(a,null,e,[]),h=a.length;while(h--)(f=g[h])&&(a[h]=!(b[h]=f))}):function(a,e,f){return b[0]=a,d(b,null,f,c),b[0]=null,!c.pop()}}),has:ia(function(a){return function(b){return ga(a,b).length>0}}),contains:ia(function(a){return a=a.replace(_,aa),function(b){return(b.textContent||b.innerText||e(b)).indexOf(a)>-1}}),lang:ia(function(a){return U.test(a||"")||ga.error("unsupported lang: "+a),a=a.replace(_,aa).toLowerCase(),function(b){var c;do if(c=p?b.lang:b.getAttribute("xml:lang")||b.getAttribute("lang"))return c=c.toLowerCase(),c===a||0===c.indexOf(a+"-");while((b=b.parentNode)&&1===b.nodeType);return!1}}),target:function(b){var c=a.location&&a.location.hash;return c&&c.slice(1)===b.id},root:function(a){return a===o},focus:function(a){return a===n.activeElement&&(!n.hasFocus||n.hasFocus())&&!!(a.type||a.href||~a.tabIndex)},enabled:oa(!1),disabled:oa(!0),checked:function(a){var b=a.nodeName.toLowerCase();return"input"===b&&!!a.checked||"option"===b&&!!a.selected},selected:function(a){return a.parentNode&&a.parentNode.selectedIndex,a.selected===!0},empty:function(a){for(a=a.firstChild;a;a=a.nextSibling)if(a.nodeType<6)return!1;return!0},parent:function(a){return!d.pseudos.empty(a)},header:function(a){return X.test(a.nodeName)},input:function(a){return W.test(a.nodeName)},button:function(a){var b=a.nodeName.toLowerCase();return"input"===b&&"button"===a.type||"button"===b},text:function(a){var b;return"input"===a.nodeName.toLowerCase()&&"text"===a.type&&(null==(b=a.getAttribute("type"))||"text"===b.toLowerCase())},first:pa(function(){return[0]}),last:pa(function(a,b){return[b-1]}),eq:pa(function(a,b,c){return[c<0?c+b:c]}),even:pa(function(a,b){for(var c=0;c<b;c+=2)a.push(c);return a}),odd:pa(function(a,b){for(var c=1;c<b;c+=2)a.push(c);return a}),lt:pa(function(a,b,c){for(var d=c<0?c+b:c;--d>=0;)a.push(d);return a}),gt:pa(function(a,b,c){for(var d=c<0?c+b:c;++d<b;)a.push(d);return a})}},d.pseudos.nth=d.pseudos.eq;for(b in{radio:!0,checkbox:!0,file:!0,password:!0,image:!0})d.pseudos[b]=ma(b);for(b in{submit:!0,reset:!0})d.pseudos[b]=na(b);function ra(){}ra.prototype=d.filters=d.pseudos,d.setFilters=new ra,g=ga.tokenize=function(a,b){var c,e,f,g,h,i,j,k=z[a+" "];if(k)return b?0:k.slice(0);h=a,i=[],j=d.preFilter;while(h){c&&!(e=Q.exec(h))||(e&&(h=h.slice(e[0].length)||h),i.push(f=[])),c=!1,(e=R.exec(h))&&(c=e.shift(),f.push({value:c,type:e[0].replace(P," ")}),h=h.slice(c.length));for(g in d.filter)!(e=V[g].exec(h))||j[g]&&!(e=j[g](e))||(c=e.shift(),f.push({value:c,type:g,matches:e}),h=h.slice(c.length));if(!c)break}return b?h.length:h?ga.error(a):z(a,i).slice(0)};function sa(a){for(var b=0,c=a.length,d="";b<c;b++)d+=a[b].value;return d}function ta(a,b,c){var d=b.dir,e=b.next,f=e||d,g=c&&"parentNode"===f,h=x++;return b.first?function(b,c,e){while(b=b[d])if(1===b.nodeType||g)return a(b,c,e)}:function(b,c,i){var j,k,l,m=[w,h];if(i){while(b=b[d])if((1===b.nodeType||g)&&a(b,c,i))return!0}else while(b=b[d])if(1===b.nodeType||g)if(l=b[u]||(b[u]={}),k=l[b.uniqueID]||(l[b.uniqueID]={}),e&&e===b.nodeName.toLowerCase())b=b[d]||b;else{if((j=k[f])&&j[0]===w&&j[1]===h)return m[2]=j[2];if(k[f]=m,m[2]=a(b,c,i))return!0}}}function ua(a){return a.length>1?function(b,c,d){var e=a.length;while(e--)if(!a[e](b,c,d))return!1;return!0}:a[0]}function va(a,b,c){for(var d=0,e=b.length;d<e;d++)ga(a,b[d],c);return c}function wa(a,b,c,d,e){for(var f,g=[],h=0,i=a.length,j=null!=b;h<i;h++)(f=a[h])&&(c&&!c(f,d,e)||(g.push(f),j&&b.push(h)));return g}function xa(a,b,c,d,e,f){return d&&!d[u]&&(d=xa(d)),e&&!e[u]&&(e=xa(e,f)),ia(function(f,g,h,i){var j,k,l,m=[],n=[],o=g.length,p=f||va(b||"*",h.nodeType?[h]:h,[]),q=!a||!f&&b?p:wa(p,m,a,h,i),r=c?e||(f?a:o||d)?[]:g:q;if(c&&c(q,r,h,i),d){j=wa(r,n),d(j,[],h,i),k=j.length;while(k--)(l=j[k])&&(r[n[k]]=!(q[n[k]]=l))}if(f){if(e||a){if(e){j=[],k=r.length;while(k--)(l=r[k])&&j.push(q[k]=l);e(null,r=[],j,i)}k=r.length;while(k--)(l=r[k])&&(j=e?I(f,l):m[k])>-1&&(f[j]=!(g[j]=l))}}else r=wa(r===g?r.splice(o,r.length):r),e?e(null,g,r,i):G.apply(g,r)})}function ya(a){for(var b,c,e,f=a.length,g=d.relative[a[0].type],h=g||d.relative[" "],i=g?1:0,k=ta(function(a){return a===b},h,!0),l=ta(function(a){return I(b,a)>-1},h,!0),m=[function(a,c,d){var e=!g&&(d||c!==j)||((b=c).nodeType?k(a,c,d):l(a,c,d));return b=null,e}];i<f;i++)if(c=d.relative[a[i].type])m=[ta(ua(m),c)];else{if(c=d.filter[a[i].type].apply(null,a[i].matches),c[u]){for(e=++i;e<f;e++)if(d.relative[a[e].type])break;return xa(i>1&&ua(m),i>1&&sa(a.slice(0,i-1).concat({value:" "===a[i-2].type?"*":""})).replace(P,"$1"),c,i<e&&ya(a.slice(i,e)),e<f&&ya(a=a.slice(e)),e<f&&sa(a))}m.push(c)}return ua(m)}function za(a,b){var c=b.length>0,e=a.length>0,f=function(f,g,h,i,k){var l,o,q,r=0,s="0",t=f&&[],u=[],v=j,x=f||e&&d.find.TAG("*",k),y=w+=null==v?1:Math.random()||.1,z=x.length;for(k&&(j=g===n||g||k);s!==z&&null!=(l=x[s]);s++){if(e&&l){o=0,g||l.ownerDocument===n||(m(l),h=!p);while(q=a[o++])if(q(l,g||n,h)){i.push(l);break}k&&(w=y)}c&&((l=!q&&l)&&r--,f&&t.push(l))}if(r+=s,c&&s!==r){o=0;while(q=b[o++])q(t,u,g,h);if(f){if(r>0)while(s--)t[s]||u[s]||(u[s]=E.call(i));u=wa(u)}G.apply(i,u),k&&!f&&u.length>0&&r+b.length>1&&ga.uniqueSort(i)}return k&&(w=y,j=v),t};return c?ia(f):f}return h=ga.compile=function(a,b){var c,d=[],e=[],f=A[a+" "];if(!f){b||(b=g(a)),c=b.length;while(c--)f=ya(b[c]),f[u]?d.push(f):e.push(f);f=A(a,za(e,d)),f.selector=a}return f},i=ga.select=function(a,b,e,f){var i,j,k,l,m,n="function"==typeof a&&a,o=!f&&g(a=n.selector||a);if(e=e||[],1===o.length){if(j=o[0]=o[0].slice(0),j.length>2&&"ID"===(k=j[0]).type&&c.getById&&9===b.nodeType&&p&&d.relative[j[1].type]){if(b=(d.find.ID(k.matches[0].replace(_,aa),b)||[])[0],!b)return e;n&&(b=b.parentNode),a=a.slice(j.shift().value.length)}i=V.needsContext.test(a)?0:j.length;while(i--){if(k=j[i],d.relative[l=k.type])break;if((m=d.find[l])&&(f=m(k.matches[0].replace(_,aa),$.test(j[0].type)&&qa(b.parentNode)||b))){if(j.splice(i,1),a=f.length&&sa(j),!a)return G.apply(e,f),e;break}}}return(n||h(a,o))(f,b,!p,e,!b||$.test(a)&&qa(b.parentNode)||b),e},c.sortStable=u.split("").sort(B).join("")===u,c.detectDuplicates=!!l,m(),c.sortDetached=ja(function(a){return 1&a.compareDocumentPosition(n.createElement("fieldset"))}),ja(function(a){return a.innerHTML="<a href='#'></a>","#"===a.firstChild.getAttribute("href")})||ka("type|href|height|width",function(a,b,c){if(!c)return a.getAttribute(b,"type"===b.toLowerCase()?1:2)}),c.attributes&&ja(function(a){return a.innerHTML="<input/>",a.firstChild.setAttribute("value",""),""===a.firstChild.getAttribute("value")})||ka("value",function(a,b,c){if(!c&&"input"===a.nodeName.toLowerCase())return a.defaultValue}),ja(function(a){return null==a.getAttribute("disabled")})||ka(J,function(a,b,c){var d;if(!c)return a[b]===!0?b.toLowerCase():(d=a.getAttributeNode(b))&&d.specified?d.value:null}),ga}(a);r.find=x,r.expr=x.selectors,r.expr[":"]=r.expr.pseudos,r.uniqueSort=r.unique=x.uniqueSort,r.text=x.getText,r.isXMLDoc=x.isXML,r.contains=x.contains,r.escapeSelector=x.escape;var y=function(a,b,c){var d=[],e=void 0!==c;while((a=a[b])&&9!==a.nodeType)if(1===a.nodeType){if(e&&r(a).is(c))break;d.push(a)}return d},z=function(a,b){for(var c=[];a;a=a.nextSibling)1===a.nodeType&&a!==b&&c.push(a);return c},A=r.expr.match.needsContext,B=/^<([a-z][^\/\0>:\x20\t\r\n\f]*)[\x20\t\r\n\f]*\/?>(?:<\/\1>|)$/i,C=/^.[^:#\[\.,]*$/;function D(a,b,c){if(r.isFunction(b))return r.grep(a,function(a,d){return!!b.call(a,d,a)!==c});if(b.nodeType)return r.grep(a,function(a){return a===b!==c});if("string"==typeof b){if(C.test(b))return r.filter(b,a,c);b=r.filter(b,a)}return r.grep(a,function(a){return i.call(b,a)>-1!==c&&1===a.nodeType})}r.filter=function(a,b,c){var d=b[0];return c&&(a=":not("+a+")"),1===b.length&&1===d.nodeType?r.find.matchesSelector(d,a)?[d]:[]:r.find.matches(a,r.grep(b,function(a){return 1===a.nodeType}))},r.fn.extend({find:function(a){var b,c,d=this.length,e=this;if("string"!=typeof a)return this.pushStack(r(a).filter(function(){for(b=0;b<d;b++)if(r.contains(e[b],this))return!0}));for(c=this.pushStack([]),b=0;b<d;b++)r.find(a,e[b],c);return d>1?r.uniqueSort(c):c},filter:function(a){return this.pushStack(D(this,a||[],!1))},not:function(a){return this.pushStack(D(this,a||[],!0))},is:function(a){return!!D(this,"string"==typeof a&&A.test(a)?r(a):a||[],!1).length}});var E,F=/^(?:\s*(<[\w\W]+>)[^>]*|#([\w-]+))$/,G=r.fn.init=function(a,b,c){var e,f;if(!a)return this;if(c=c||E,"string"==typeof a){if(e="<"===a[0]&&">"===a[a.length-1]&&a.length>=3?[null,a,null]:F.exec(a),!e||!e[1]&&b)return!b||b.jquery?(b||c).find(a):this.constructor(b).find(a);if(e[1]){if(b=b instanceof r?b[0]:b,r.merge(this,r.parseHTML(e[1],b&&b.nodeType?b.ownerDocument||b:d,!0)),B.test(e[1])&&r.isPlainObject(b))for(e in b)r.isFunction(this[e])?this[e](b[e]):this.attr(e,b[e]);return this}return f=d.getElementById(e[2]),f&&(this[0]=f,this.length=1),this}return a.nodeType?(this[0]=a,this.length=1,this):r.isFunction(a)?void 0!==c.ready?c.ready(a):a(r):r.makeArray(a,this)};G.prototype=r.fn,E=r(d);var H=/^(?:parents|prev(?:Until|All))/,I={children:!0,contents:!0,next:!0,prev:!0};r.fn.extend({has:function(a){var b=r(a,this),c=b.length;return this.filter(function(){for(var a=0;a<c;a++)if(r.contains(this,b[a]))return!0})},closest:function(a,b){var c,d=0,e=this.length,f=[],g="string"!=typeof a&&r(a);if(!A.test(a))for(;d<e;d++)for(c=this[d];c&&c!==b;c=c.parentNode)if(c.nodeType<11&&(g?g.index(c)>-1:1===c.nodeType&&r.find.matchesSelector(c,a))){f.push(c);break}return this.pushStack(f.length>1?r.uniqueSort(f):f)},index:function(a){return a?"string"==typeof a?i.call(r(a),this[0]):i.call(this,a.jquery?a[0]:a):this[0]&&this[0].parentNode?this.first().prevAll().length:-1},add:function(a,b){return this.pushStack(r.uniqueSort(r.merge(this.get(),r(a,b))))},addBack:function(a){return this.add(null==a?this.prevObject:this.prevObject.filter(a))}});function J(a,b){while((a=a[b])&&1!==a.nodeType);return a}r.each({parent:function(a){var b=a.parentNode;return b&&11!==b.nodeType?b:null},parents:function(a){return y(a,"parentNode")},parentsUntil:function(a,b,c){return y(a,"parentNode",c)},next:function(a){return J(a,"nextSibling")},prev:function(a){return J(a,"previousSibling")},nextAll:function(a){return y(a,"nextSibling")},prevAll:function(a){return y(a,"previousSibling")},nextUntil:function(a,b,c){return y(a,"nextSibling",c)},prevUntil:function(a,b,c){return y(a,"previousSibling",c)},siblings:function(a){return z((a.parentNode||{}).firstChild,a)},children:function(a){return z(a.firstChild)},contents:function(a){return a.contentDocument||r.merge([],a.childNodes)}},function(a,b){r.fn[a]=function(c,d){var e=r.map(this,b,c);return"Until"!==a.slice(-5)&&(d=c),d&&"string"==typeof d&&(e=r.filter(d,e)),this.length>1&&(I[a]||r.uniqueSort(e),H.test(a)&&e.reverse()),this.pushStack(e)}});var K=/\S+/g;function L(a){var b={};return r.each(a.match(K)||[],function(a,c){b[c]=!0}),b}r.Callbacks=function(a){a="string"==typeof a?L(a):r.extend({},a);var b,c,d,e,f=[],g=[],h=-1,i=function(){for(e=a.once,d=b=!0;g.length;h=-1){c=g.shift();while(++h<f.length)f[h].apply(c[0],c[1])===!1&&a.stopOnFalse&&(h=f.length,c=!1)}a.memory||(c=!1),b=!1,e&&(f=c?[]:"")},j={add:function(){return f&&(c&&!b&&(h=f.length-1,g.push(c)),function d(b){r.each(b,function(b,c){r.isFunction(c)?a.unique&&j.has(c)||f.push(c):c&&c.length&&"string"!==r.type(c)&&d(c)})}(arguments),c&&!b&&i()),this},remove:function(){return r.each(arguments,function(a,b){var c;while((c=r.inArray(b,f,c))>-1)f.splice(c,1),c<=h&&h--}),this},has:function(a){return a?r.inArray(a,f)>-1:f.length>0},empty:function(){return f&&(f=[]),this},disable:function(){return e=g=[],f=c="",this},disabled:function(){return!f},lock:function(){return e=g=[],c||b||(f=c=""),this},locked:function(){return!!e},fireWith:function(a,c){return e||(c=c||[],c=[a,c.slice?c.slice():c],g.push(c),b||i()),this},fire:function(){return j.fireWith(this,arguments),this},fired:function(){return!!d}};return j};function M(a){return a}function N(a){throw a}function O(a,b,c){var d;try{a&&r.isFunction(d=a.promise)?d.call(a).done(b).fail(c):a&&r.isFunction(d=a.then)?d.call(a,b,c):b.call(void 0,a)}catch(a){c.call(void 0,a)}}r.extend({Deferred:function(b){var c=[["notify","progress",r.Callbacks("memory"),r.Callbacks("memory"),2],["resolve","done",r.Callbacks("once memory"),r.Callbacks("once memory"),0,"resolved"],["reject","fail",r.Callbacks("once memory"),r.Callbacks("once memory"),1,"rejected"]],d="pending",e={state:function(){return d},always:function(){return f.done(arguments).fail(arguments),this},"catch":function(a){return e.then(null,a)},pipe:function(){var a=arguments;return r.Deferred(function(b){r.each(c,function(c,d){var e=r.isFunction(a[d[4]])&&a[d[4]];f[d[1]](function(){var a=e&&e.apply(this,arguments);a&&r.isFunction(a.promise)?a.promise().progress(b.notify).done(b.resolve).fail(b.reject):b[d[0]+"With"](this,e?[a]:arguments)})}),a=null}).promise()},then:function(b,d,e){var f=0;function g(b,c,d,e){return function(){var h=this,i=arguments,j=function(){var a,j;if(!(b<f)){if(a=d.apply(h,i),a===c.promise())throw new TypeError("Thenable self-resolution");j=a&&("object"==typeof a||"function"==typeof a)&&a.then,r.isFunction(j)?e?j.call(a,g(f,c,M,e),g(f,c,N,e)):(f++,j.call(a,g(f,c,M,e),g(f,c,N,e),g(f,c,M,c.notifyWith))):(d!==M&&(h=void 0,i=[a]),(e||c.resolveWith)(h,i))}},k=e?j:function(){try{j()}catch(a){r.Deferred.exceptionHook&&r.Deferred.exceptionHook(a,k.stackTrace),b+1>=f&&(d!==N&&(h=void 0,i=[a]),c.rejectWith(h,i))}};b?k():(r.Deferred.getStackHook&&(k.stackTrace=r.Deferred.getStackHook()),a.setTimeout(k))}}return r.Deferred(function(a){c[0][3].add(g(0,a,r.isFunction(e)?e:M,a.notifyWith)),c[1][3].add(g(0,a,r.isFunction(b)?b:M)),c[2][3].add(g(0,a,r.isFunction(d)?d:N))}).promise()},promise:function(a){return null!=a?r.extend(a,e):e}},f={};return r.each(c,function(a,b){var g=b[2],h=b[5];e[b[1]]=g.add,h&&g.add(function(){d=h},c[3-a][2].disable,c[0][2].lock),g.add(b[3].fire),f[b[0]]=function(){return f[b[0]+"With"](this===f?void 0:this,arguments),this},f[b[0]+"With"]=g.fireWith}),e.promise(f),b&&b.call(f,f),f},when:function(a){var b=arguments.length,c=b,d=Array(c),e=f.call(arguments),g=r.Deferred(),h=function(a){return function(c){d[a]=this,e[a]=arguments.length>1?f.call(arguments):c,--b||g.resolveWith(d,e)}};if(b<=1&&(O(a,g.done(h(c)).resolve,g.reject),"pending"===g.state()||r.isFunction(e[c]&&e[c].then)))return g.then();while(c--)O(e[c],h(c),g.reject);return g.promise()}});var P=/^(Eval|Internal|Range|Reference|Syntax|Type|URI)Error$/;r.Deferred.exceptionHook=function(b,c){a.console&&a.console.warn&&b&&P.test(b.name)&&a.console.warn("jQuery.Deferred exception: "+b.message,b.stack,c)},r.readyException=function(b){a.setTimeout(function(){throw b})};var Q=r.Deferred();r.fn.ready=function(a){return Q.then(a)["catch"](function(a){r.readyException(a)}),this},r.extend({isReady:!1,readyWait:1,holdReady:function(a){a?r.readyWait++:r.ready(!0)},ready:function(a){(a===!0?--r.readyWait:r.isReady)||(r.isReady=!0,a!==!0&&--r.readyWait>0||Q.resolveWith(d,[r]))}}),r.ready.then=Q.then;function R(){d.removeEventListener("DOMContentLoaded",R),a.removeEventListener("load",R),r.ready()}"complete"===d.readyState||"loading"!==d.readyState&&!d.documentElement.doScroll?a.setTimeout(r.ready):(d.addEventListener("DOMContentLoaded",R),a.addEventListener("load",R));var S=function(a,b,c,d,e,f,g){var h=0,i=a.length,j=null==c;if("object"===r.type(c)){e=!0;for(h in c)S(a,b,h,c[h],!0,f,g)}else if(void 0!==d&&(e=!0,
-r.isFunction(d)||(g=!0),j&&(g?(b.call(a,d),b=null):(j=b,b=function(a,b,c){return j.call(r(a),c)})),b))for(;h<i;h++)b(a[h],c,g?d:d.call(a[h],h,b(a[h],c)));return e?a:j?b.call(a):i?b(a[0],c):f},T=function(a){return 1===a.nodeType||9===a.nodeType||!+a.nodeType};function U(){this.expando=r.expando+U.uid++}U.uid=1,U.prototype={cache:function(a){var b=a[this.expando];return b||(b={},T(a)&&(a.nodeType?a[this.expando]=b:Object.defineProperty(a,this.expando,{value:b,configurable:!0}))),b},set:function(a,b,c){var d,e=this.cache(a);if("string"==typeof b)e[r.camelCase(b)]=c;else for(d in b)e[r.camelCase(d)]=b[d];return e},get:function(a,b){return void 0===b?this.cache(a):a[this.expando]&&a[this.expando][r.camelCase(b)]},access:function(a,b,c){return void 0===b||b&&"string"==typeof b&&void 0===c?this.get(a,b):(this.set(a,b,c),void 0!==c?c:b)},remove:function(a,b){var c,d=a[this.expando];if(void 0!==d){if(void 0!==b){r.isArray(b)?b=b.map(r.camelCase):(b=r.camelCase(b),b=b in d?[b]:b.match(K)||[]),c=b.length;while(c--)delete d[b[c]]}(void 0===b||r.isEmptyObject(d))&&(a.nodeType?a[this.expando]=void 0:delete a[this.expando])}},hasData:function(a){var b=a[this.expando];return void 0!==b&&!r.isEmptyObject(b)}};var V=new U,W=new U,X=/^(?:\{[\w\W]*\}|\[[\w\W]*\])$/,Y=/[A-Z]/g;function Z(a,b,c){var d;if(void 0===c&&1===a.nodeType)if(d="data-"+b.replace(Y,"-$&").toLowerCase(),c=a.getAttribute(d),"string"==typeof c){try{c="true"===c||"false"!==c&&("null"===c?null:+c+""===c?+c:X.test(c)?JSON.parse(c):c)}catch(e){}W.set(a,b,c)}else c=void 0;return c}r.extend({hasData:function(a){return W.hasData(a)||V.hasData(a)},data:function(a,b,c){return W.access(a,b,c)},removeData:function(a,b){W.remove(a,b)},_data:function(a,b,c){return V.access(a,b,c)},_removeData:function(a,b){V.remove(a,b)}}),r.fn.extend({data:function(a,b){var c,d,e,f=this[0],g=f&&f.attributes;if(void 0===a){if(this.length&&(e=W.get(f),1===f.nodeType&&!V.get(f,"hasDataAttrs"))){c=g.length;while(c--)g[c]&&(d=g[c].name,0===d.indexOf("data-")&&(d=r.camelCase(d.slice(5)),Z(f,d,e[d])));V.set(f,"hasDataAttrs",!0)}return e}return"object"==typeof a?this.each(function(){W.set(this,a)}):S(this,function(b){var c;if(f&&void 0===b){if(c=W.get(f,a),void 0!==c)return c;if(c=Z(f,a),void 0!==c)return c}else this.each(function(){W.set(this,a,b)})},null,b,arguments.length>1,null,!0)},removeData:function(a){return this.each(function(){W.remove(this,a)})}}),r.extend({queue:function(a,b,c){var d;if(a)return b=(b||"fx")+"queue",d=V.get(a,b),c&&(!d||r.isArray(c)?d=V.access(a,b,r.makeArray(c)):d.push(c)),d||[]},dequeue:function(a,b){b=b||"fx";var c=r.queue(a,b),d=c.length,e=c.shift(),f=r._queueHooks(a,b),g=function(){r.dequeue(a,b)};"inprogress"===e&&(e=c.shift(),d--),e&&("fx"===b&&c.unshift("inprogress"),delete f.stop,e.call(a,g,f)),!d&&f&&f.empty.fire()},_queueHooks:function(a,b){var c=b+"queueHooks";return V.get(a,c)||V.access(a,c,{empty:r.Callbacks("once memory").add(function(){V.remove(a,[b+"queue",c])})})}}),r.fn.extend({queue:function(a,b){var c=2;return"string"!=typeof a&&(b=a,a="fx",c--),arguments.length<c?r.queue(this[0],a):void 0===b?this:this.each(function(){var c=r.queue(this,a,b);r._queueHooks(this,a),"fx"===a&&"inprogress"!==c[0]&&r.dequeue(this,a)})},dequeue:function(a){return this.each(function(){r.dequeue(this,a)})},clearQueue:function(a){return this.queue(a||"fx",[])},promise:function(a,b){var c,d=1,e=r.Deferred(),f=this,g=this.length,h=function(){--d||e.resolveWith(f,[f])};"string"!=typeof a&&(b=a,a=void 0),a=a||"fx";while(g--)c=V.get(f[g],a+"queueHooks"),c&&c.empty&&(d++,c.empty.add(h));return h(),e.promise(b)}});var $=/[+-]?(?:\d*\.|)\d+(?:[eE][+-]?\d+|)/.source,_=new RegExp("^(?:([+-])=|)("+$+")([a-z%]*)$","i"),aa=["Top","Right","Bottom","Left"],ba=function(a,b){return a=b||a,"none"===a.style.display||""===a.style.display&&r.contains(a.ownerDocument,a)&&"none"===r.css(a,"display")},ca=function(a,b,c,d){var e,f,g={};for(f in b)g[f]=a.style[f],a.style[f]=b[f];e=c.apply(a,d||[]);for(f in b)a.style[f]=g[f];return e};function da(a,b,c,d){var e,f=1,g=20,h=d?function(){return d.cur()}:function(){return r.css(a,b,"")},i=h(),j=c&&c[3]||(r.cssNumber[b]?"":"px"),k=(r.cssNumber[b]||"px"!==j&&+i)&&_.exec(r.css(a,b));if(k&&k[3]!==j){j=j||k[3],c=c||[],k=+i||1;do f=f||".5",k/=f,r.style(a,b,k+j);while(f!==(f=h()/i)&&1!==f&&--g)}return c&&(k=+k||+i||0,e=c[1]?k+(c[1]+1)*c[2]:+c[2],d&&(d.unit=j,d.start=k,d.end=e)),e}var ea={};function fa(a){var b,c=a.ownerDocument,d=a.nodeName,e=ea[d];return e?e:(b=c.body.appendChild(c.createElement(d)),e=r.css(b,"display"),b.parentNode.removeChild(b),"none"===e&&(e="block"),ea[d]=e,e)}function ga(a,b){for(var c,d,e=[],f=0,g=a.length;f<g;f++)d=a[f],d.style&&(c=d.style.display,b?("none"===c&&(e[f]=V.get(d,"display")||null,e[f]||(d.style.display="")),""===d.style.display&&ba(d)&&(e[f]=fa(d))):"none"!==c&&(e[f]="none",V.set(d,"display",c)));for(f=0;f<g;f++)null!=e[f]&&(a[f].style.display=e[f]);return a}r.fn.extend({show:function(){return ga(this,!0)},hide:function(){return ga(this)},toggle:function(a){return"boolean"==typeof a?a?this.show():this.hide():this.each(function(){ba(this)?r(this).show():r(this).hide()})}});var ha=/^(?:checkbox|radio)$/i,ia=/<([a-z][^\/\0>\x20\t\r\n\f]+)/i,ja=/^$|\/(?:java|ecma)script/i,ka={option:[1,"<select multiple='multiple'>","</select>"],thead:[1,"<table>","</table>"],col:[2,"<table><colgroup>","</colgroup></table>"],tr:[2,"<table><tbody>","</tbody></table>"],td:[3,"<table><tbody><tr>","</tr></tbody></table>"],_default:[0,"",""]};ka.optgroup=ka.option,ka.tbody=ka.tfoot=ka.colgroup=ka.caption=ka.thead,ka.th=ka.td;function la(a,b){var c="undefined"!=typeof a.getElementsByTagName?a.getElementsByTagName(b||"*"):"undefined"!=typeof a.querySelectorAll?a.querySelectorAll(b||"*"):[];return void 0===b||b&&r.nodeName(a,b)?r.merge([a],c):c}function ma(a,b){for(var c=0,d=a.length;c<d;c++)V.set(a[c],"globalEval",!b||V.get(b[c],"globalEval"))}var na=/<|&#?\w+;/;function oa(a,b,c,d,e){for(var f,g,h,i,j,k,l=b.createDocumentFragment(),m=[],n=0,o=a.length;n<o;n++)if(f=a[n],f||0===f)if("object"===r.type(f))r.merge(m,f.nodeType?[f]:f);else if(na.test(f)){g=g||l.appendChild(b.createElement("div")),h=(ia.exec(f)||["",""])[1].toLowerCase(),i=ka[h]||ka._default,g.innerHTML=i[1]+r.htmlPrefilter(f)+i[2],k=i[0];while(k--)g=g.lastChild;r.merge(m,g.childNodes),g=l.firstChild,g.textContent=""}else m.push(b.createTextNode(f));l.textContent="",n=0;while(f=m[n++])if(d&&r.inArray(f,d)>-1)e&&e.push(f);else if(j=r.contains(f.ownerDocument,f),g=la(l.appendChild(f),"script"),j&&ma(g),c){k=0;while(f=g[k++])ja.test(f.type||"")&&c.push(f)}return l}!function(){var a=d.createDocumentFragment(),b=a.appendChild(d.createElement("div")),c=d.createElement("input");c.setAttribute("type","radio"),c.setAttribute("checked","checked"),c.setAttribute("name","t"),b.appendChild(c),o.checkClone=b.cloneNode(!0).cloneNode(!0).lastChild.checked,b.innerHTML="<textarea>x</textarea>",o.noCloneChecked=!!b.cloneNode(!0).lastChild.defaultValue}();var pa=d.documentElement,qa=/^key/,ra=/^(?:mouse|pointer|contextmenu|drag|drop)|click/,sa=/^([^.]*)(?:\.(.+)|)/;function ta(){return!0}function ua(){return!1}function va(){try{return d.activeElement}catch(a){}}function wa(a,b,c,d,e,f){var g,h;if("object"==typeof b){"string"!=typeof c&&(d=d||c,c=void 0);for(h in b)wa(a,h,c,d,b[h],f);return a}if(null==d&&null==e?(e=c,d=c=void 0):null==e&&("string"==typeof c?(e=d,d=void 0):(e=d,d=c,c=void 0)),e===!1)e=ua;else if(!e)return a;return 1===f&&(g=e,e=function(a){return r().off(a),g.apply(this,arguments)},e.guid=g.guid||(g.guid=r.guid++)),a.each(function(){r.event.add(this,b,e,d,c)})}r.event={global:{},add:function(a,b,c,d,e){var f,g,h,i,j,k,l,m,n,o,p,q=V.get(a);if(q){c.handler&&(f=c,c=f.handler,e=f.selector),e&&r.find.matchesSelector(pa,e),c.guid||(c.guid=r.guid++),(i=q.events)||(i=q.events={}),(g=q.handle)||(g=q.handle=function(b){return"undefined"!=typeof r&&r.event.triggered!==b.type?r.event.dispatch.apply(a,arguments):void 0}),b=(b||"").match(K)||[""],j=b.length;while(j--)h=sa.exec(b[j])||[],n=p=h[1],o=(h[2]||"").split(".").sort(),n&&(l=r.event.special[n]||{},n=(e?l.delegateType:l.bindType)||n,l=r.event.special[n]||{},k=r.extend({type:n,origType:p,data:d,handler:c,guid:c.guid,selector:e,needsContext:e&&r.expr.match.needsContext.test(e),namespace:o.join(".")},f),(m=i[n])||(m=i[n]=[],m.delegateCount=0,l.setup&&l.setup.call(a,d,o,g)!==!1||a.addEventListener&&a.addEventListener(n,g)),l.add&&(l.add.call(a,k),k.handler.guid||(k.handler.guid=c.guid)),e?m.splice(m.delegateCount++,0,k):m.push(k),r.event.global[n]=!0)}},remove:function(a,b,c,d,e){var f,g,h,i,j,k,l,m,n,o,p,q=V.hasData(a)&&V.get(a);if(q&&(i=q.events)){b=(b||"").match(K)||[""],j=b.length;while(j--)if(h=sa.exec(b[j])||[],n=p=h[1],o=(h[2]||"").split(".").sort(),n){l=r.event.special[n]||{},n=(d?l.delegateType:l.bindType)||n,m=i[n]||[],h=h[2]&&new RegExp("(^|\\.)"+o.join("\\.(?:.*\\.|)")+"(\\.|$)"),g=f=m.length;while(f--)k=m[f],!e&&p!==k.origType||c&&c.guid!==k.guid||h&&!h.test(k.namespace)||d&&d!==k.selector&&("**"!==d||!k.selector)||(m.splice(f,1),k.selector&&m.delegateCount--,l.remove&&l.remove.call(a,k));g&&!m.length&&(l.teardown&&l.teardown.call(a,o,q.handle)!==!1||r.removeEvent(a,n,q.handle),delete i[n])}else for(n in i)r.event.remove(a,n+b[j],c,d,!0);r.isEmptyObject(i)&&V.remove(a,"handle events")}},dispatch:function(a){var b=r.event.fix(a),c,d,e,f,g,h,i=new Array(arguments.length),j=(V.get(this,"events")||{})[b.type]||[],k=r.event.special[b.type]||{};for(i[0]=b,c=1;c<arguments.length;c++)i[c]=arguments[c];if(b.delegateTarget=this,!k.preDispatch||k.preDispatch.call(this,b)!==!1){h=r.event.handlers.call(this,b,j),c=0;while((f=h[c++])&&!b.isPropagationStopped()){b.currentTarget=f.elem,d=0;while((g=f.handlers[d++])&&!b.isImmediatePropagationStopped())b.rnamespace&&!b.rnamespace.test(g.namespace)||(b.handleObj=g,b.data=g.data,e=((r.event.special[g.origType]||{}).handle||g.handler).apply(f.elem,i),void 0!==e&&(b.result=e)===!1&&(b.preventDefault(),b.stopPropagation()))}return k.postDispatch&&k.postDispatch.call(this,b),b.result}},handlers:function(a,b){var c,d,e,f,g=[],h=b.delegateCount,i=a.target;if(h&&i.nodeType&&("click"!==a.type||isNaN(a.button)||a.button<1))for(;i!==this;i=i.parentNode||this)if(1===i.nodeType&&(i.disabled!==!0||"click"!==a.type)){for(d=[],c=0;c<h;c++)f=b[c],e=f.selector+" ",void 0===d[e]&&(d[e]=f.needsContext?r(e,this).index(i)>-1:r.find(e,this,null,[i]).length),d[e]&&d.push(f);d.length&&g.push({elem:i,handlers:d})}return h<b.length&&g.push({elem:this,handlers:b.slice(h)}),g},addProp:function(a,b){Object.defineProperty(r.Event.prototype,a,{enumerable:!0,configurable:!0,get:r.isFunction(b)?function(){if(this.originalEvent)return b(this.originalEvent)}:function(){if(this.originalEvent)return this.originalEvent[a]},set:function(b){Object.defineProperty(this,a,{enumerable:!0,configurable:!0,writable:!0,value:b})}})},fix:function(a){return a[r.expando]?a:new r.Event(a)},special:{load:{noBubble:!0},focus:{trigger:function(){if(this!==va()&&this.focus)return this.focus(),!1},delegateType:"focusin"},blur:{trigger:function(){if(this===va()&&this.blur)return this.blur(),!1},delegateType:"focusout"},click:{trigger:function(){if("checkbox"===this.type&&this.click&&r.nodeName(this,"input"))return this.click(),!1},_default:function(a){return r.nodeName(a.target,"a")}},beforeunload:{postDispatch:function(a){void 0!==a.result&&a.originalEvent&&(a.originalEvent.returnValue=a.result)}}}},r.removeEvent=function(a,b,c){a.removeEventListener&&a.removeEventListener(b,c)},r.Event=function(a,b){return this instanceof r.Event?(a&&a.type?(this.originalEvent=a,this.type=a.type,this.isDefaultPrevented=a.defaultPrevented||void 0===a.defaultPrevented&&a.returnValue===!1?ta:ua,this.target=a.target&&3===a.target.nodeType?a.target.parentNode:a.target,this.currentTarget=a.currentTarget,this.relatedTarget=a.relatedTarget):this.type=a,b&&r.extend(this,b),this.timeStamp=a&&a.timeStamp||r.now(),void(this[r.expando]=!0)):new r.Event(a,b)},r.Event.prototype={constructor:r.Event,isDefaultPrevented:ua,isPropagationStopped:ua,isImmediatePropagationStopped:ua,isSimulated:!1,preventDefault:function(){var a=this.originalEvent;this.isDefaultPrevented=ta,a&&!this.isSimulated&&a.preventDefault()},stopPropagation:function(){var a=this.originalEvent;this.isPropagationStopped=ta,a&&!this.isSimulated&&a.stopPropagation()},stopImmediatePropagation:function(){var a=this.originalEvent;this.isImmediatePropagationStopped=ta,a&&!this.isSimulated&&a.stopImmediatePropagation(),this.stopPropagation()}},r.each({altKey:!0,bubbles:!0,cancelable:!0,changedTouches:!0,ctrlKey:!0,detail:!0,eventPhase:!0,metaKey:!0,pageX:!0,pageY:!0,shiftKey:!0,view:!0,"char":!0,charCode:!0,key:!0,keyCode:!0,button:!0,buttons:!0,clientX:!0,clientY:!0,offsetX:!0,offsetY:!0,pointerId:!0,pointerType:!0,screenX:!0,screenY:!0,targetTouches:!0,toElement:!0,touches:!0,which:function(a){var b=a.button;return null==a.which&&qa.test(a.type)?null!=a.charCode?a.charCode:a.keyCode:!a.which&&void 0!==b&&ra.test(a.type)?1&b?1:2&b?3:4&b?2:0:a.which}},r.event.addProp),r.each({mouseenter:"mouseover",mouseleave:"mouseout",pointerenter:"pointerover",pointerleave:"pointerout"},function(a,b){r.event.special[a]={delegateType:b,bindType:b,handle:function(a){var c,d=this,e=a.relatedTarget,f=a.handleObj;return e&&(e===d||r.contains(d,e))||(a.type=f.origType,c=f.handler.apply(this,arguments),a.type=b),c}}}),r.fn.extend({on:function(a,b,c,d){return wa(this,a,b,c,d)},one:function(a,b,c,d){return wa(this,a,b,c,d,1)},off:function(a,b,c){var d,e;if(a&&a.preventDefault&&a.handleObj)return d=a.handleObj,r(a.delegateTarget).off(d.namespace?d.origType+"."+d.namespace:d.origType,d.selector,d.handler),this;if("object"==typeof a){for(e in a)this.off(e,b,a[e]);return this}return b!==!1&&"function"!=typeof b||(c=b,b=void 0),c===!1&&(c=ua),this.each(function(){r.event.remove(this,a,c,b)})}});var xa=/<(?!area|br|col|embed|hr|img|input|link|meta|param)(([a-z][^\/\0>\x20\t\r\n\f]*)[^>]*)\/>/gi,ya=/<script|<style|<link/i,za=/checked\s*(?:[^=]|=\s*.checked.)/i,Aa=/^true\/(.*)/,Ba=/^\s*<!(?:\[CDATA\[|--)|(?:\]\]|--)>\s*$/g;function Ca(a,b){return r.nodeName(a,"table")&&r.nodeName(11!==b.nodeType?b:b.firstChild,"tr")?a.getElementsByTagName("tbody")[0]||a:a}function Da(a){return a.type=(null!==a.getAttribute("type"))+"/"+a.type,a}function Ea(a){var b=Aa.exec(a.type);return b?a.type=b[1]:a.removeAttribute("type"),a}function Fa(a,b){var c,d,e,f,g,h,i,j;if(1===b.nodeType){if(V.hasData(a)&&(f=V.access(a),g=V.set(b,f),j=f.events)){delete g.handle,g.events={};for(e in j)for(c=0,d=j[e].length;c<d;c++)r.event.add(b,e,j[e][c])}W.hasData(a)&&(h=W.access(a),i=r.extend({},h),W.set(b,i))}}function Ga(a,b){var c=b.nodeName.toLowerCase();"input"===c&&ha.test(a.type)?b.checked=a.checked:"input"!==c&&"textarea"!==c||(b.defaultValue=a.defaultValue)}function Ha(a,b,c,d){b=g.apply([],b);var e,f,h,i,j,k,l=0,m=a.length,n=m-1,q=b[0],s=r.isFunction(q);if(s||m>1&&"string"==typeof q&&!o.checkClone&&za.test(q))return a.each(function(e){var f=a.eq(e);s&&(b[0]=q.call(this,e,f.html())),Ha(f,b,c,d)});if(m&&(e=oa(b,a[0].ownerDocument,!1,a,d),f=e.firstChild,1===e.childNodes.length&&(e=f),f||d)){for(h=r.map(la(e,"script"),Da),i=h.length;l<m;l++)j=e,l!==n&&(j=r.clone(j,!0,!0),i&&r.merge(h,la(j,"script"))),c.call(a[l],j,l);if(i)for(k=h[h.length-1].ownerDocument,r.map(h,Ea),l=0;l<i;l++)j=h[l],ja.test(j.type||"")&&!V.access(j,"globalEval")&&r.contains(k,j)&&(j.src?r._evalUrl&&r._evalUrl(j.src):p(j.textContent.replace(Ba,""),k))}return a}function Ia(a,b,c){for(var d,e=b?r.filter(b,a):a,f=0;null!=(d=e[f]);f++)c||1!==d.nodeType||r.cleanData(la(d)),d.parentNode&&(c&&r.contains(d.ownerDocument,d)&&ma(la(d,"script")),d.parentNode.removeChild(d));return a}r.extend({htmlPrefilter:function(a){return a.replace(xa,"<$1></$2>")},clone:function(a,b,c){var d,e,f,g,h=a.cloneNode(!0),i=r.contains(a.ownerDocument,a);if(!(o.noCloneChecked||1!==a.nodeType&&11!==a.nodeType||r.isXMLDoc(a)))for(g=la(h),f=la(a),d=0,e=f.length;d<e;d++)Ga(f[d],g[d]);if(b)if(c)for(f=f||la(a),g=g||la(h),d=0,e=f.length;d<e;d++)Fa(f[d],g[d]);else Fa(a,h);return g=la(h,"script"),g.length>0&&ma(g,!i&&la(a,"script")),h},cleanData:function(a){for(var b,c,d,e=r.event.special,f=0;void 0!==(c=a[f]);f++)if(T(c)){if(b=c[V.expando]){if(b.events)for(d in b.events)e[d]?r.event.remove(c,d):r.removeEvent(c,d,b.handle);c[V.expando]=void 0}c[W.expando]&&(c[W.expando]=void 0)}}}),r.fn.extend({detach:function(a){return Ia(this,a,!0)},remove:function(a){return Ia(this,a)},text:function(a){return S(this,function(a){return void 0===a?r.text(this):this.empty().each(function(){1!==this.nodeType&&11!==this.nodeType&&9!==this.nodeType||(this.textContent=a)})},null,a,arguments.length)},append:function(){return Ha(this,arguments,function(a){if(1===this.nodeType||11===this.nodeType||9===this.nodeType){var b=Ca(this,a);b.appendChild(a)}})},prepend:function(){return Ha(this,arguments,function(a){if(1===this.nodeType||11===this.nodeType||9===this.nodeType){var b=Ca(this,a);b.insertBefore(a,b.firstChild)}})},before:function(){return Ha(this,arguments,function(a){this.parentNode&&this.parentNode.insertBefore(a,this)})},after:function(){return Ha(this,arguments,function(a){this.parentNode&&this.parentNode.insertBefore(a,this.nextSibling)})},empty:function(){for(var a,b=0;null!=(a=this[b]);b++)1===a.nodeType&&(r.cleanData(la(a,!1)),a.textContent="");return this},clone:function(a,b){return a=null!=a&&a,b=null==b?a:b,this.map(function(){return r.clone(this,a,b)})},html:function(a){return S(this,function(a){var b=this[0]||{},c=0,d=this.length;if(void 0===a&&1===b.nodeType)return b.innerHTML;if("string"==typeof a&&!ya.test(a)&&!ka[(ia.exec(a)||["",""])[1].toLowerCase()]){a=r.htmlPrefilter(a);try{for(;c<d;c++)b=this[c]||{},1===b.nodeType&&(r.cleanData(la(b,!1)),b.innerHTML=a);b=0}catch(e){}}b&&this.empty().append(a)},null,a,arguments.length)},replaceWith:function(){var a=[];return Ha(this,arguments,function(b){var c=this.parentNode;r.inArray(this,a)<0&&(r.cleanData(la(this)),c&&c.replaceChild(b,this))},a)}}),r.each({appendTo:"append",prependTo:"prepend",insertBefore:"before",insertAfter:"after",replaceAll:"replaceWith"},function(a,b){r.fn[a]=function(a){for(var c,d=[],e=r(a),f=e.length-1,g=0;g<=f;g++)c=g===f?this:this.clone(!0),r(e[g])[b](c),h.apply(d,c.get());return this.pushStack(d)}});var Ja=/^margin/,Ka=new RegExp("^("+$+")(?!px)[a-z%]+$","i"),La=function(b){var c=b.ownerDocument.defaultView;return c&&c.opener||(c=a),c.getComputedStyle(b)};!function(){function b(){if(i){i.style.cssText="box-sizing:border-box;position:relative;display:block;margin:auto;border:1px;padding:1px;top:1%;width:50%",i.innerHTML="",pa.appendChild(h);var b=a.getComputedStyle(i);c="1%"!==b.top,g="2px"===b.marginLeft,e="4px"===b.width,i.style.marginRight="50%",f="4px"===b.marginRight,pa.removeChild(h),i=null}}var c,e,f,g,h=d.createElement("div"),i=d.createElement("div");i.style&&(i.style.backgroundClip="content-box",i.cloneNode(!0).style.backgroundClip="",o.clearCloneStyle="content-box"===i.style.backgroundClip,h.style.cssText="border:0;width:8px;height:0;top:0;left:-9999px;padding:0;margin-top:1px;position:absolute",h.appendChild(i),r.extend(o,{pixelPosition:function(){return b(),c},boxSizingReliable:function(){return b(),e},pixelMarginRight:function(){return b(),f},reliableMarginLeft:function(){return b(),g}}))}();function Ma(a,b,c){var d,e,f,g,h=a.style;return c=c||La(a),c&&(g=c.getPropertyValue(b)||c[b],""!==g||r.contains(a.ownerDocument,a)||(g=r.style(a,b)),!o.pixelMarginRight()&&Ka.test(g)&&Ja.test(b)&&(d=h.width,e=h.minWidth,f=h.maxWidth,h.minWidth=h.maxWidth=h.width=g,g=c.width,h.width=d,h.minWidth=e,h.maxWidth=f)),void 0!==g?g+"":g}function Na(a,b){return{get:function(){return a()?void delete this.get:(this.get=b).apply(this,arguments)}}}var Oa=/^(none|table(?!-c[ea]).+)/,Pa={position:"absolute",visibility:"hidden",display:"block"},Qa={letterSpacing:"0",fontWeight:"400"},Ra=["Webkit","Moz","ms"],Sa=d.createElement("div").style;function Ta(a){if(a in Sa)return a;var b=a[0].toUpperCase()+a.slice(1),c=Ra.length;while(c--)if(a=Ra[c]+b,a in Sa)return a}function Ua(a,b,c){var d=_.exec(b);return d?Math.max(0,d[2]-(c||0))+(d[3]||"px"):b}function Va(a,b,c,d,e){for(var f=c===(d?"border":"content")?4:"width"===b?1:0,g=0;f<4;f+=2)"margin"===c&&(g+=r.css(a,c+aa[f],!0,e)),d?("content"===c&&(g-=r.css(a,"padding"+aa[f],!0,e)),"margin"!==c&&(g-=r.css(a,"border"+aa[f]+"Width",!0,e))):(g+=r.css(a,"padding"+aa[f],!0,e),"padding"!==c&&(g+=r.css(a,"border"+aa[f]+"Width",!0,e)));return g}function Wa(a,b,c){var d,e=!0,f=La(a),g="border-box"===r.css(a,"boxSizing",!1,f);if(a.getClientRects().length&&(d=a.getBoundingClientRect()[b]),d<=0||null==d){if(d=Ma(a,b,f),(d<0||null==d)&&(d=a.style[b]),Ka.test(d))return d;e=g&&(o.boxSizingReliable()||d===a.style[b]),d=parseFloat(d)||0}return d+Va(a,b,c||(g?"border":"content"),e,f)+"px"}r.extend({cssHooks:{opacity:{get:function(a,b){if(b){var c=Ma(a,"opacity");return""===c?"1":c}}}},cssNumber:{animationIterationCount:!0,columnCount:!0,fillOpacity:!0,flexGrow:!0,flexShrink:!0,fontWeight:!0,lineHeight:!0,opacity:!0,order:!0,orphans:!0,widows:!0,zIndex:!0,zoom:!0},cssProps:{"float":"cssFloat"},style:function(a,b,c,d){if(a&&3!==a.nodeType&&8!==a.nodeType&&a.style){var e,f,g,h=r.camelCase(b),i=a.style;return b=r.cssProps[h]||(r.cssProps[h]=Ta(h)||h),g=r.cssHooks[b]||r.cssHooks[h],void 0===c?g&&"get"in g&&void 0!==(e=g.get(a,!1,d))?e:i[b]:(f=typeof c,"string"===f&&(e=_.exec(c))&&e[1]&&(c=da(a,b,e),f="number"),null!=c&&c===c&&("number"===f&&(c+=e&&e[3]||(r.cssNumber[h]?"":"px")),o.clearCloneStyle||""!==c||0!==b.indexOf("background")||(i[b]="inherit"),g&&"set"in g&&void 0===(c=g.set(a,c,d))||(i[b]=c)),void 0)}},css:function(a,b,c,d){var e,f,g,h=r.camelCase(b);return b=r.cssProps[h]||(r.cssProps[h]=Ta(h)||h),g=r.cssHooks[b]||r.cssHooks[h],g&&"get"in g&&(e=g.get(a,!0,c)),void 0===e&&(e=Ma(a,b,d)),"normal"===e&&b in Qa&&(e=Qa[b]),""===c||c?(f=parseFloat(e),c===!0||isFinite(f)?f||0:e):e}}),r.each(["height","width"],function(a,b){r.cssHooks[b]={get:function(a,c,d){if(c)return!Oa.test(r.css(a,"display"))||a.getClientRects().length&&a.getBoundingClientRect().width?Wa(a,b,d):ca(a,Pa,function(){return Wa(a,b,d)})},set:function(a,c,d){var e,f=d&&La(a),g=d&&Va(a,b,d,"border-box"===r.css(a,"boxSizing",!1,f),f);return g&&(e=_.exec(c))&&"px"!==(e[3]||"px")&&(a.style[b]=c,c=r.css(a,b)),Ua(a,c,g)}}}),r.cssHooks.marginLeft=Na(o.reliableMarginLeft,function(a,b){if(b)return(parseFloat(Ma(a,"marginLeft"))||a.getBoundingClientRect().left-ca(a,{marginLeft:0},function(){return a.getBoundingClientRect().left}))+"px"}),r.each({margin:"",padding:"",border:"Width"},function(a,b){r.cssHooks[a+b]={expand:function(c){for(var d=0,e={},f="string"==typeof c?c.split(" "):[c];d<4;d++)e[a+aa[d]+b]=f[d]||f[d-2]||f[0];return e}},Ja.test(a)||(r.cssHooks[a+b].set=Ua)}),r.fn.extend({css:function(a,b){return S(this,function(a,b,c){var d,e,f={},g=0;if(r.isArray(b)){for(d=La(a),e=b.length;g<e;g++)f[b[g]]=r.css(a,b[g],!1,d);return f}return void 0!==c?r.style(a,b,c):r.css(a,b)},a,b,arguments.length>1)}});function Xa(a,b,c,d,e){return new Xa.prototype.init(a,b,c,d,e)}r.Tween=Xa,Xa.prototype={constructor:Xa,init:function(a,b,c,d,e,f){this.elem=a,this.prop=c,this.easing=e||r.easing._default,this.options=b,this.start=this.now=this.cur(),this.end=d,this.unit=f||(r.cssNumber[c]?"":"px")},cur:function(){var a=Xa.propHooks[this.prop];return a&&a.get?a.get(this):Xa.propHooks._default.get(this)},run:function(a){var b,c=Xa.propHooks[this.prop];return this.options.duration?this.pos=b=r.easing[this.easing](a,this.options.duration*a,0,1,this.options.duration):this.pos=b=a,this.now=(this.end-this.start)*b+this.start,this.options.step&&this.options.step.call(this.elem,this.now,this),c&&c.set?c.set(this):Xa.propHooks._default.set(this),this}},Xa.prototype.init.prototype=Xa.prototype,Xa.propHooks={_default:{get:function(a){var b;return 1!==a.elem.nodeType||null!=a.elem[a.prop]&&null==a.elem.style[a.prop]?a.elem[a.prop]:(b=r.css(a.elem,a.prop,""),b&&"auto"!==b?b:0)},set:function(a){r.fx.step[a.prop]?r.fx.step[a.prop](a):1!==a.elem.nodeType||null==a.elem.style[r.cssProps[a.prop]]&&!r.cssHooks[a.prop]?a.elem[a.prop]=a.now:r.style(a.elem,a.prop,a.now+a.unit)}}},Xa.propHooks.scrollTop=Xa.propHooks.scrollLeft={set:function(a){a.elem.nodeType&&a.elem.parentNode&&(a.elem[a.prop]=a.now)}},r.easing={linear:function(a){return a},swing:function(a){return.5-Math.cos(a*Math.PI)/2},_default:"swing"},r.fx=Xa.prototype.init,r.fx.step={};var Ya,Za,$a=/^(?:toggle|show|hide)$/,_a=/queueHooks$/;function ab(){Za&&(a.requestAnimationFrame(ab),r.fx.tick())}function bb(){return a.setTimeout(function(){Ya=void 0}),Ya=r.now()}function cb(a,b){var c,d=0,e={height:a};for(b=b?1:0;d<4;d+=2-b)c=aa[d],e["margin"+c]=e["padding"+c]=a;return b&&(e.opacity=e.width=a),e}function db(a,b,c){for(var d,e=(gb.tweeners[b]||[]).concat(gb.tweeners["*"]),f=0,g=e.length;f<g;f++)if(d=e[f].call(c,b,a))return d}function eb(a,b,c){var d,e,f,g,h,i,j,k,l="width"in b||"height"in b,m=this,n={},o=a.style,p=a.nodeType&&ba(a),q=V.get(a,"fxshow");c.queue||(g=r._queueHooks(a,"fx"),null==g.unqueued&&(g.unqueued=0,h=g.empty.fire,g.empty.fire=function(){g.unqueued||h()}),g.unqueued++,m.always(function(){m.always(function(){g.unqueued--,r.queue(a,"fx").length||g.empty.fire()})}));for(d in b)if(e=b[d],$a.test(e)){if(delete b[d],f=f||"toggle"===e,e===(p?"hide":"show")){if("show"!==e||!q||void 0===q[d])continue;p=!0}n[d]=q&&q[d]||r.style(a,d)}if(i=!r.isEmptyObject(b),i||!r.isEmptyObject(n)){l&&1===a.nodeType&&(c.overflow=[o.overflow,o.overflowX,o.overflowY],j=q&&q.display,null==j&&(j=V.get(a,"display")),k=r.css(a,"display"),"none"===k&&(j?k=j:(ga([a],!0),j=a.style.display||j,k=r.css(a,"display"),ga([a]))),("inline"===k||"inline-block"===k&&null!=j)&&"none"===r.css(a,"float")&&(i||(m.done(function(){o.display=j}),null==j&&(k=o.display,j="none"===k?"":k)),o.display="inline-block")),c.overflow&&(o.overflow="hidden",m.always(function(){o.overflow=c.overflow[0],o.overflowX=c.overflow[1],o.overflowY=c.overflow[2]})),i=!1;for(d in n)i||(q?"hidden"in q&&(p=q.hidden):q=V.access(a,"fxshow",{display:j}),f&&(q.hidden=!p),p&&ga([a],!0),m.done(function(){p||ga([a]),V.remove(a,"fxshow");for(d in n)r.style(a,d,n[d])})),i=db(p?q[d]:0,d,m),d in q||(q[d]=i.start,p&&(i.end=i.start,i.start=0))}}function fb(a,b){var c,d,e,f,g;for(c in a)if(d=r.camelCase(c),e=b[d],f=a[c],r.isArray(f)&&(e=f[1],f=a[c]=f[0]),c!==d&&(a[d]=f,delete a[c]),g=r.cssHooks[d],g&&"expand"in g){f=g.expand(f),delete a[d];for(c in f)c in a||(a[c]=f[c],b[c]=e)}else b[d]=e}function gb(a,b,c){var d,e,f=0,g=gb.prefilters.length,h=r.Deferred().always(function(){delete i.elem}),i=function(){if(e)return!1;for(var b=Ya||bb(),c=Math.max(0,j.startTime+j.duration-b),d=c/j.duration||0,f=1-d,g=0,i=j.tweens.length;g<i;g++)j.tweens[g].run(f);return h.notifyWith(a,[j,f,c]),f<1&&i?c:(h.resolveWith(a,[j]),!1)},j=h.promise({elem:a,props:r.extend({},b),opts:r.extend(!0,{specialEasing:{},easing:r.easing._default},c),originalProperties:b,originalOptions:c,startTime:Ya||bb(),duration:c.duration,tweens:[],createTween:function(b,c){var d=r.Tween(a,j.opts,b,c,j.opts.specialEasing[b]||j.opts.easing);return j.tweens.push(d),d},stop:function(b){var c=0,d=b?j.tweens.length:0;if(e)return this;for(e=!0;c<d;c++)j.tweens[c].run(1);return b?(h.notifyWith(a,[j,1,0]),h.resolveWith(a,[j,b])):h.rejectWith(a,[j,b]),this}}),k=j.props;for(fb(k,j.opts.specialEasing);f<g;f++)if(d=gb.prefilters[f].call(j,a,k,j.opts))return r.isFunction(d.stop)&&(r._queueHooks(j.elem,j.opts.queue).stop=r.proxy(d.stop,d)),d;return r.map(k,db,j),r.isFunction(j.opts.start)&&j.opts.start.call(a,j),r.fx.timer(r.extend(i,{elem:a,anim:j,queue:j.opts.queue})),j.progress(j.opts.progress).done(j.opts.done,j.opts.complete).fail(j.opts.fail).always(j.opts.always)}r.Animation=r.extend(gb,{tweeners:{"*":[function(a,b){var c=this.createTween(a,b);return da(c.elem,a,_.exec(b),c),c}]},tweener:function(a,b){r.isFunction(a)?(b=a,a=["*"]):a=a.match(K);for(var c,d=0,e=a.length;d<e;d++)c=a[d],gb.tweeners[c]=gb.tweeners[c]||[],gb.tweeners[c].unshift(b)},prefilters:[eb],prefilter:function(a,b){b?gb.prefilters.unshift(a):gb.prefilters.push(a)}}),r.speed=function(a,b,c){var e=a&&"object"==typeof a?r.extend({},a):{complete:c||!c&&b||r.isFunction(a)&&a,duration:a,easing:c&&b||b&&!r.isFunction(b)&&b};return r.fx.off||d.hidden?e.duration=0:e.duration="number"==typeof e.duration?e.duration:e.duration in r.fx.speeds?r.fx.speeds[e.duration]:r.fx.speeds._default,null!=e.queue&&e.queue!==!0||(e.queue="fx"),e.old=e.complete,e.complete=function(){r.isFunction(e.old)&&e.old.call(this),e.queue&&r.dequeue(this,e.queue)},e},r.fn.extend({fadeTo:function(a,b,c,d){return this.filter(ba).css("opacity",0).show().end().animate({opacity:b},a,c,d)},animate:function(a,b,c,d){var e=r.isEmptyObject(a),f=r.speed(b,c,d),g=function(){var b=gb(this,r.extend({},a),f);(e||V.get(this,"finish"))&&b.stop(!0)};return g.finish=g,e||f.queue===!1?this.each(g):this.queue(f.queue,g)},stop:function(a,b,c){var d=function(a){var b=a.stop;delete a.stop,b(c)};return"string"!=typeof a&&(c=b,b=a,a=void 0),b&&a!==!1&&this.queue(a||"fx",[]),this.each(function(){var b=!0,e=null!=a&&a+"queueHooks",f=r.timers,g=V.get(this);if(e)g[e]&&g[e].stop&&d(g[e]);else for(e in g)g[e]&&g[e].stop&&_a.test(e)&&d(g[e]);for(e=f.length;e--;)f[e].elem!==this||null!=a&&f[e].queue!==a||(f[e].anim.stop(c),b=!1,f.splice(e,1));!b&&c||r.dequeue(this,a)})},finish:function(a){return a!==!1&&(a=a||"fx"),this.each(function(){var b,c=V.get(this),d=c[a+"queue"],e=c[a+"queueHooks"],f=r.timers,g=d?d.length:0;for(c.finish=!0,r.queue(this,a,[]),e&&e.stop&&e.stop.call(this,!0),b=f.length;b--;)f[b].elem===this&&f[b].queue===a&&(f[b].anim.stop(!0),f.splice(b,1));for(b=0;b<g;b++)d[b]&&d[b].finish&&d[b].finish.call(this);delete c.finish})}}),r.each(["toggle","show","hide"],function(a,b){var c=r.fn[b];r.fn[b]=function(a,d,e){return null==a||"boolean"==typeof a?c.apply(this,arguments):this.animate(cb(b,!0),a,d,e)}}),r.each({slideDown:cb("show"),slideUp:cb("hide"),slideToggle:cb("toggle"),fadeIn:{opacity:"show"},fadeOut:{opacity:"hide"},fadeToggle:{opacity:"toggle"}},function(a,b){r.fn[a]=function(a,c,d){return this.animate(b,a,c,d)}}),r.timers=[],r.fx.tick=function(){var a,b=0,c=r.timers;for(Ya=r.now();b<c.length;b++)a=c[b],a()||c[b]!==a||c.splice(b--,1);c.length||r.fx.stop(),Ya=void 0},r.fx.timer=function(a){r.timers.push(a),a()?r.fx.start():r.timers.pop()},r.fx.interval=13,r.fx.start=function(){Za||(Za=a.requestAnimationFrame?a.requestAnimationFrame(ab):a.setInterval(r.fx.tick,r.fx.interval))},r.fx.stop=function(){a.cancelAnimationFrame?a.cancelAnimationFrame(Za):a.clearInterval(Za),Za=null},r.fx.speeds={slow:600,fast:200,_default:400},r.fn.delay=function(b,c){return b=r.fx?r.fx.speeds[b]||b:b,c=c||"fx",this.queue(c,function(c,d){var e=a.setTimeout(c,b);d.stop=function(){a.clearTimeout(e)}})},function(){var a=d.createElement("input"),b=d.createElement("select"),c=b.appendChild(d.createElement("option"));a.type="checkbox",o.checkOn=""!==a.value,o.optSelected=c.selected,a=d.createElement("input"),a.value="t",a.type="radio",o.radioValue="t"===a.value}();var hb,ib=r.expr.attrHandle;r.fn.extend({attr:function(a,b){return S(this,r.attr,a,b,arguments.length>1)},removeAttr:function(a){return this.each(function(){r.removeAttr(this,a)})}}),r.extend({attr:function(a,b,c){var d,e,f=a.nodeType;if(3!==f&&8!==f&&2!==f)return"undefined"==typeof a.getAttribute?r.prop(a,b,c):(1===f&&r.isXMLDoc(a)||(e=r.attrHooks[b.toLowerCase()]||(r.expr.match.bool.test(b)?hb:void 0)),void 0!==c?null===c?void r.removeAttr(a,b):e&&"set"in e&&void 0!==(d=e.set(a,c,b))?d:(a.setAttribute(b,c+""),c):e&&"get"in e&&null!==(d=e.get(a,b))?d:(d=r.find.attr(a,b),null==d?void 0:d))},attrHooks:{type:{set:function(a,b){if(!o.radioValue&&"radio"===b&&r.nodeName(a,"input")){var c=a.value;return a.setAttribute("type",b),c&&(a.value=c),b}}}},removeAttr:function(a,b){var c,d=0,e=b&&b.match(K);
-if(e&&1===a.nodeType)while(c=e[d++])a.removeAttribute(c)}}),hb={set:function(a,b,c){return b===!1?r.removeAttr(a,c):a.setAttribute(c,c),c}},r.each(r.expr.match.bool.source.match(/\w+/g),function(a,b){var c=ib[b]||r.find.attr;ib[b]=function(a,b,d){var e,f,g=b.toLowerCase();return d||(f=ib[g],ib[g]=e,e=null!=c(a,b,d)?g:null,ib[g]=f),e}});var jb=/^(?:input|select|textarea|button)$/i,kb=/^(?:a|area)$/i;r.fn.extend({prop:function(a,b){return S(this,r.prop,a,b,arguments.length>1)},removeProp:function(a){return this.each(function(){delete this[r.propFix[a]||a]})}}),r.extend({prop:function(a,b,c){var d,e,f=a.nodeType;if(3!==f&&8!==f&&2!==f)return 1===f&&r.isXMLDoc(a)||(b=r.propFix[b]||b,e=r.propHooks[b]),void 0!==c?e&&"set"in e&&void 0!==(d=e.set(a,c,b))?d:a[b]=c:e&&"get"in e&&null!==(d=e.get(a,b))?d:a[b]},propHooks:{tabIndex:{get:function(a){var b=r.find.attr(a,"tabindex");return b?parseInt(b,10):jb.test(a.nodeName)||kb.test(a.nodeName)&&a.href?0:-1}}},propFix:{"for":"htmlFor","class":"className"}}),o.optSelected||(r.propHooks.selected={get:function(a){var b=a.parentNode;return b&&b.parentNode&&b.parentNode.selectedIndex,null},set:function(a){var b=a.parentNode;b&&(b.selectedIndex,b.parentNode&&b.parentNode.selectedIndex)}}),r.each(["tabIndex","readOnly","maxLength","cellSpacing","cellPadding","rowSpan","colSpan","useMap","frameBorder","contentEditable"],function(){r.propFix[this.toLowerCase()]=this});var lb=/[\t\r\n\f]/g;function mb(a){return a.getAttribute&&a.getAttribute("class")||""}r.fn.extend({addClass:function(a){var b,c,d,e,f,g,h,i=0;if(r.isFunction(a))return this.each(function(b){r(this).addClass(a.call(this,b,mb(this)))});if("string"==typeof a&&a){b=a.match(K)||[];while(c=this[i++])if(e=mb(c),d=1===c.nodeType&&(" "+e+" ").replace(lb," ")){g=0;while(f=b[g++])d.indexOf(" "+f+" ")<0&&(d+=f+" ");h=r.trim(d),e!==h&&c.setAttribute("class",h)}}return this},removeClass:function(a){var b,c,d,e,f,g,h,i=0;if(r.isFunction(a))return this.each(function(b){r(this).removeClass(a.call(this,b,mb(this)))});if(!arguments.length)return this.attr("class","");if("string"==typeof a&&a){b=a.match(K)||[];while(c=this[i++])if(e=mb(c),d=1===c.nodeType&&(" "+e+" ").replace(lb," ")){g=0;while(f=b[g++])while(d.indexOf(" "+f+" ")>-1)d=d.replace(" "+f+" "," ");h=r.trim(d),e!==h&&c.setAttribute("class",h)}}return this},toggleClass:function(a,b){var c=typeof a;return"boolean"==typeof b&&"string"===c?b?this.addClass(a):this.removeClass(a):r.isFunction(a)?this.each(function(c){r(this).toggleClass(a.call(this,c,mb(this),b),b)}):this.each(function(){var b,d,e,f;if("string"===c){d=0,e=r(this),f=a.match(K)||[];while(b=f[d++])e.hasClass(b)?e.removeClass(b):e.addClass(b)}else void 0!==a&&"boolean"!==c||(b=mb(this),b&&V.set(this,"__className__",b),this.setAttribute&&this.setAttribute("class",b||a===!1?"":V.get(this,"__className__")||""))})},hasClass:function(a){var b,c,d=0;b=" "+a+" ";while(c=this[d++])if(1===c.nodeType&&(" "+mb(c)+" ").replace(lb," ").indexOf(b)>-1)return!0;return!1}});var nb=/\r/g,ob=/[\x20\t\r\n\f]+/g;r.fn.extend({val:function(a){var b,c,d,e=this[0];{if(arguments.length)return d=r.isFunction(a),this.each(function(c){var e;1===this.nodeType&&(e=d?a.call(this,c,r(this).val()):a,null==e?e="":"number"==typeof e?e+="":r.isArray(e)&&(e=r.map(e,function(a){return null==a?"":a+""})),b=r.valHooks[this.type]||r.valHooks[this.nodeName.toLowerCase()],b&&"set"in b&&void 0!==b.set(this,e,"value")||(this.value=e))});if(e)return b=r.valHooks[e.type]||r.valHooks[e.nodeName.toLowerCase()],b&&"get"in b&&void 0!==(c=b.get(e,"value"))?c:(c=e.value,"string"==typeof c?c.replace(nb,""):null==c?"":c)}}}),r.extend({valHooks:{option:{get:function(a){var b=r.find.attr(a,"value");return null!=b?b:r.trim(r.text(a)).replace(ob," ")}},select:{get:function(a){for(var b,c,d=a.options,e=a.selectedIndex,f="select-one"===a.type,g=f?null:[],h=f?e+1:d.length,i=e<0?h:f?e:0;i<h;i++)if(c=d[i],(c.selected||i===e)&&!c.disabled&&(!c.parentNode.disabled||!r.nodeName(c.parentNode,"optgroup"))){if(b=r(c).val(),f)return b;g.push(b)}return g},set:function(a,b){var c,d,e=a.options,f=r.makeArray(b),g=e.length;while(g--)d=e[g],(d.selected=r.inArray(r.valHooks.option.get(d),f)>-1)&&(c=!0);return c||(a.selectedIndex=-1),f}}}}),r.each(["radio","checkbox"],function(){r.valHooks[this]={set:function(a,b){if(r.isArray(b))return a.checked=r.inArray(r(a).val(),b)>-1}},o.checkOn||(r.valHooks[this].get=function(a){return null===a.getAttribute("value")?"on":a.value})});var pb=/^(?:focusinfocus|focusoutblur)$/;r.extend(r.event,{trigger:function(b,c,e,f){var g,h,i,j,k,m,n,o=[e||d],p=l.call(b,"type")?b.type:b,q=l.call(b,"namespace")?b.namespace.split("."):[];if(h=i=e=e||d,3!==e.nodeType&&8!==e.nodeType&&!pb.test(p+r.event.triggered)&&(p.indexOf(".")>-1&&(q=p.split("."),p=q.shift(),q.sort()),k=p.indexOf(":")<0&&"on"+p,b=b[r.expando]?b:new r.Event(p,"object"==typeof b&&b),b.isTrigger=f?2:3,b.namespace=q.join("."),b.rnamespace=b.namespace?new RegExp("(^|\\.)"+q.join("\\.(?:.*\\.|)")+"(\\.|$)"):null,b.result=void 0,b.target||(b.target=e),c=null==c?[b]:r.makeArray(c,[b]),n=r.event.special[p]||{},f||!n.trigger||n.trigger.apply(e,c)!==!1)){if(!f&&!n.noBubble&&!r.isWindow(e)){for(j=n.delegateType||p,pb.test(j+p)||(h=h.parentNode);h;h=h.parentNode)o.push(h),i=h;i===(e.ownerDocument||d)&&o.push(i.defaultView||i.parentWindow||a)}g=0;while((h=o[g++])&&!b.isPropagationStopped())b.type=g>1?j:n.bindType||p,m=(V.get(h,"events")||{})[b.type]&&V.get(h,"handle"),m&&m.apply(h,c),m=k&&h[k],m&&m.apply&&T(h)&&(b.result=m.apply(h,c),b.result===!1&&b.preventDefault());return b.type=p,f||b.isDefaultPrevented()||n._default&&n._default.apply(o.pop(),c)!==!1||!T(e)||k&&r.isFunction(e[p])&&!r.isWindow(e)&&(i=e[k],i&&(e[k]=null),r.event.triggered=p,e[p](),r.event.triggered=void 0,i&&(e[k]=i)),b.result}},simulate:function(a,b,c){var d=r.extend(new r.Event,c,{type:a,isSimulated:!0});r.event.trigger(d,null,b)}}),r.fn.extend({trigger:function(a,b){return this.each(function(){r.event.trigger(a,b,this)})},triggerHandler:function(a,b){var c=this[0];if(c)return r.event.trigger(a,b,c,!0)}}),r.each("blur focus focusin focusout resize scroll click dblclick mousedown mouseup mousemove mouseover mouseout mouseenter mouseleave change select submit keydown keypress keyup contextmenu".split(" "),function(a,b){r.fn[b]=function(a,c){return arguments.length>0?this.on(b,null,a,c):this.trigger(b)}}),r.fn.extend({hover:function(a,b){return this.mouseenter(a).mouseleave(b||a)}}),o.focusin="onfocusin"in a,o.focusin||r.each({focus:"focusin",blur:"focusout"},function(a,b){var c=function(a){r.event.simulate(b,a.target,r.event.fix(a))};r.event.special[b]={setup:function(){var d=this.ownerDocument||this,e=V.access(d,b);e||d.addEventListener(a,c,!0),V.access(d,b,(e||0)+1)},teardown:function(){var d=this.ownerDocument||this,e=V.access(d,b)-1;e?V.access(d,b,e):(d.removeEventListener(a,c,!0),V.remove(d,b))}}});var qb=a.location,rb=r.now(),sb=/\?/;r.parseXML=function(b){var c;if(!b||"string"!=typeof b)return null;try{c=(new a.DOMParser).parseFromString(b,"text/xml")}catch(d){c=void 0}return c&&!c.getElementsByTagName("parsererror").length||r.error("Invalid XML: "+b),c};var tb=/\[\]$/,ub=/\r?\n/g,vb=/^(?:submit|button|image|reset|file)$/i,wb=/^(?:input|select|textarea|keygen)/i;function xb(a,b,c,d){var e;if(r.isArray(b))r.each(b,function(b,e){c||tb.test(a)?d(a,e):xb(a+"["+("object"==typeof e&&null!=e?b:"")+"]",e,c,d)});else if(c||"object"!==r.type(b))d(a,b);else for(e in b)xb(a+"["+e+"]",b[e],c,d)}r.param=function(a,b){var c,d=[],e=function(a,b){var c=r.isFunction(b)?b():b;d[d.length]=encodeURIComponent(a)+"="+encodeURIComponent(null==c?"":c)};if(r.isArray(a)||a.jquery&&!r.isPlainObject(a))r.each(a,function(){e(this.name,this.value)});else for(c in a)xb(c,a[c],b,e);return d.join("&")},r.fn.extend({serialize:function(){return r.param(this.serializeArray())},serializeArray:function(){return this.map(function(){var a=r.prop(this,"elements");return a?r.makeArray(a):this}).filter(function(){var a=this.type;return this.name&&!r(this).is(":disabled")&&wb.test(this.nodeName)&&!vb.test(a)&&(this.checked||!ha.test(a))}).map(function(a,b){var c=r(this).val();return null==c?null:r.isArray(c)?r.map(c,function(a){return{name:b.name,value:a.replace(ub,"\r\n")}}):{name:b.name,value:c.replace(ub,"\r\n")}}).get()}});var yb=/%20/g,zb=/#.*$/,Ab=/([?&])_=[^&]*/,Bb=/^(.*?):[ \t]*([^\r\n]*)$/gm,Cb=/^(?:about|app|app-storage|.+-extension|file|res|widget):$/,Db=/^(?:GET|HEAD)$/,Eb=/^\/\//,Fb={},Gb={},Hb="*/".concat("*"),Ib=d.createElement("a");Ib.href=qb.href;function Jb(a){return function(b,c){"string"!=typeof b&&(c=b,b="*");var d,e=0,f=b.toLowerCase().match(K)||[];if(r.isFunction(c))while(d=f[e++])"+"===d[0]?(d=d.slice(1)||"*",(a[d]=a[d]||[]).unshift(c)):(a[d]=a[d]||[]).push(c)}}function Kb(a,b,c,d){var e={},f=a===Gb;function g(h){var i;return e[h]=!0,r.each(a[h]||[],function(a,h){var j=h(b,c,d);return"string"!=typeof j||f||e[j]?f?!(i=j):void 0:(b.dataTypes.unshift(j),g(j),!1)}),i}return g(b.dataTypes[0])||!e["*"]&&g("*")}function Lb(a,b){var c,d,e=r.ajaxSettings.flatOptions||{};for(c in b)void 0!==b[c]&&((e[c]?a:d||(d={}))[c]=b[c]);return d&&r.extend(!0,a,d),a}function Mb(a,b,c){var d,e,f,g,h=a.contents,i=a.dataTypes;while("*"===i[0])i.shift(),void 0===d&&(d=a.mimeType||b.getResponseHeader("Content-Type"));if(d)for(e in h)if(h[e]&&h[e].test(d)){i.unshift(e);break}if(i[0]in c)f=i[0];else{for(e in c){if(!i[0]||a.converters[e+" "+i[0]]){f=e;break}g||(g=e)}f=f||g}if(f)return f!==i[0]&&i.unshift(f),c[f]}function Nb(a,b,c,d){var e,f,g,h,i,j={},k=a.dataTypes.slice();if(k[1])for(g in a.converters)j[g.toLowerCase()]=a.converters[g];f=k.shift();while(f)if(a.responseFields[f]&&(c[a.responseFields[f]]=b),!i&&d&&a.dataFilter&&(b=a.dataFilter(b,a.dataType)),i=f,f=k.shift())if("*"===f)f=i;else if("*"!==i&&i!==f){if(g=j[i+" "+f]||j["* "+f],!g)for(e in j)if(h=e.split(" "),h[1]===f&&(g=j[i+" "+h[0]]||j["* "+h[0]])){g===!0?g=j[e]:j[e]!==!0&&(f=h[0],k.unshift(h[1]));break}if(g!==!0)if(g&&a["throws"])b=g(b);else try{b=g(b)}catch(l){return{state:"parsererror",error:g?l:"No conversion from "+i+" to "+f}}}return{state:"success",data:b}}r.extend({active:0,lastModified:{},etag:{},ajaxSettings:{url:qb.href,type:"GET",isLocal:Cb.test(qb.protocol),global:!0,processData:!0,async:!0,contentType:"application/x-www-form-urlencoded; charset=UTF-8",accepts:{"*":Hb,text:"text/plain",html:"text/html",xml:"application/xml, text/xml",json:"application/json, text/javascript"},contents:{xml:/\bxml\b/,html:/\bhtml/,json:/\bjson\b/},responseFields:{xml:"responseXML",text:"responseText",json:"responseJSON"},converters:{"* text":String,"text html":!0,"text json":JSON.parse,"text xml":r.parseXML},flatOptions:{url:!0,context:!0}},ajaxSetup:function(a,b){return b?Lb(Lb(a,r.ajaxSettings),b):Lb(r.ajaxSettings,a)},ajaxPrefilter:Jb(Fb),ajaxTransport:Jb(Gb),ajax:function(b,c){"object"==typeof b&&(c=b,b=void 0),c=c||{};var e,f,g,h,i,j,k,l,m,n,o=r.ajaxSetup({},c),p=o.context||o,q=o.context&&(p.nodeType||p.jquery)?r(p):r.event,s=r.Deferred(),t=r.Callbacks("once memory"),u=o.statusCode||{},v={},w={},x="canceled",y={readyState:0,getResponseHeader:function(a){var b;if(k){if(!h){h={};while(b=Bb.exec(g))h[b[1].toLowerCase()]=b[2]}b=h[a.toLowerCase()]}return null==b?null:b},getAllResponseHeaders:function(){return k?g:null},setRequestHeader:function(a,b){return null==k&&(a=w[a.toLowerCase()]=w[a.toLowerCase()]||a,v[a]=b),this},overrideMimeType:function(a){return null==k&&(o.mimeType=a),this},statusCode:function(a){var b;if(a)if(k)y.always(a[y.status]);else for(b in a)u[b]=[u[b],a[b]];return this},abort:function(a){var b=a||x;return e&&e.abort(b),A(0,b),this}};if(s.promise(y),o.url=((b||o.url||qb.href)+"").replace(Eb,qb.protocol+"//"),o.type=c.method||c.type||o.method||o.type,o.dataTypes=(o.dataType||"*").toLowerCase().match(K)||[""],null==o.crossDomain){j=d.createElement("a");try{j.href=o.url,j.href=j.href,o.crossDomain=Ib.protocol+"//"+Ib.host!=j.protocol+"//"+j.host}catch(z){o.crossDomain=!0}}if(o.data&&o.processData&&"string"!=typeof o.data&&(o.data=r.param(o.data,o.traditional)),Kb(Fb,o,c,y),k)return y;l=r.event&&o.global,l&&0===r.active++&&r.event.trigger("ajaxStart"),o.type=o.type.toUpperCase(),o.hasContent=!Db.test(o.type),f=o.url.replace(zb,""),o.hasContent?o.data&&o.processData&&0===(o.contentType||"").indexOf("application/x-www-form-urlencoded")&&(o.data=o.data.replace(yb,"+")):(n=o.url.slice(f.length),o.data&&(f+=(sb.test(f)?"&":"?")+o.data,delete o.data),o.cache===!1&&(f=f.replace(Ab,""),n=(sb.test(f)?"&":"?")+"_="+rb++ +n),o.url=f+n),o.ifModified&&(r.lastModified[f]&&y.setRequestHeader("If-Modified-Since",r.lastModified[f]),r.etag[f]&&y.setRequestHeader("If-None-Match",r.etag[f])),(o.data&&o.hasContent&&o.contentType!==!1||c.contentType)&&y.setRequestHeader("Content-Type",o.contentType),y.setRequestHeader("Accept",o.dataTypes[0]&&o.accepts[o.dataTypes[0]]?o.accepts[o.dataTypes[0]]+("*"!==o.dataTypes[0]?", "+Hb+"; q=0.01":""):o.accepts["*"]);for(m in o.headers)y.setRequestHeader(m,o.headers[m]);if(o.beforeSend&&(o.beforeSend.call(p,y,o)===!1||k))return y.abort();if(x="abort",t.add(o.complete),y.done(o.success),y.fail(o.error),e=Kb(Gb,o,c,y)){if(y.readyState=1,l&&q.trigger("ajaxSend",[y,o]),k)return y;o.async&&o.timeout>0&&(i=a.setTimeout(function(){y.abort("timeout")},o.timeout));try{k=!1,e.send(v,A)}catch(z){if(k)throw z;A(-1,z)}}else A(-1,"No Transport");function A(b,c,d,h){var j,m,n,v,w,x=c;k||(k=!0,i&&a.clearTimeout(i),e=void 0,g=h||"",y.readyState=b>0?4:0,j=b>=200&&b<300||304===b,d&&(v=Mb(o,y,d)),v=Nb(o,v,y,j),j?(o.ifModified&&(w=y.getResponseHeader("Last-Modified"),w&&(r.lastModified[f]=w),w=y.getResponseHeader("etag"),w&&(r.etag[f]=w)),204===b||"HEAD"===o.type?x="nocontent":304===b?x="notmodified":(x=v.state,m=v.data,n=v.error,j=!n)):(n=x,!b&&x||(x="error",b<0&&(b=0))),y.status=b,y.statusText=(c||x)+"",j?s.resolveWith(p,[m,x,y]):s.rejectWith(p,[y,x,n]),y.statusCode(u),u=void 0,l&&q.trigger(j?"ajaxSuccess":"ajaxError",[y,o,j?m:n]),t.fireWith(p,[y,x]),l&&(q.trigger("ajaxComplete",[y,o]),--r.active||r.event.trigger("ajaxStop")))}return y},getJSON:function(a,b,c){return r.get(a,b,c,"json")},getScript:function(a,b){return r.get(a,void 0,b,"script")}}),r.each(["get","post"],function(a,b){r[b]=function(a,c,d,e){return r.isFunction(c)&&(e=e||d,d=c,c=void 0),r.ajax(r.extend({url:a,type:b,dataType:e,data:c,success:d},r.isPlainObject(a)&&a))}}),r._evalUrl=function(a){return r.ajax({url:a,type:"GET",dataType:"script",cache:!0,async:!1,global:!1,"throws":!0})},r.fn.extend({wrapAll:function(a){var b;return this[0]&&(r.isFunction(a)&&(a=a.call(this[0])),b=r(a,this[0].ownerDocument).eq(0).clone(!0),this[0].parentNode&&b.insertBefore(this[0]),b.map(function(){var a=this;while(a.firstElementChild)a=a.firstElementChild;return a}).append(this)),this},wrapInner:function(a){return r.isFunction(a)?this.each(function(b){r(this).wrapInner(a.call(this,b))}):this.each(function(){var b=r(this),c=b.contents();c.length?c.wrapAll(a):b.append(a)})},wrap:function(a){var b=r.isFunction(a);return this.each(function(c){r(this).wrapAll(b?a.call(this,c):a)})},unwrap:function(a){return this.parent(a).not("body").each(function(){r(this).replaceWith(this.childNodes)}),this}}),r.expr.pseudos.hidden=function(a){return!r.expr.pseudos.visible(a)},r.expr.pseudos.visible=function(a){return!!(a.offsetWidth||a.offsetHeight||a.getClientRects().length)},r.ajaxSettings.xhr=function(){try{return new a.XMLHttpRequest}catch(b){}};var Ob={0:200,1223:204},Pb=r.ajaxSettings.xhr();o.cors=!!Pb&&"withCredentials"in Pb,o.ajax=Pb=!!Pb,r.ajaxTransport(function(b){var c,d;if(o.cors||Pb&&!b.crossDomain)return{send:function(e,f){var g,h=b.xhr();if(h.open(b.type,b.url,b.async,b.username,b.password),b.xhrFields)for(g in b.xhrFields)h[g]=b.xhrFields[g];b.mimeType&&h.overrideMimeType&&h.overrideMimeType(b.mimeType),b.crossDomain||e["X-Requested-With"]||(e["X-Requested-With"]="XMLHttpRequest");for(g in e)h.setRequestHeader(g,e[g]);c=function(a){return function(){c&&(c=d=h.onload=h.onerror=h.onabort=h.onreadystatechange=null,"abort"===a?h.abort():"error"===a?"number"!=typeof h.status?f(0,"error"):f(h.status,h.statusText):f(Ob[h.status]||h.status,h.statusText,"text"!==(h.responseType||"text")||"string"!=typeof h.responseText?{binary:h.response}:{text:h.responseText},h.getAllResponseHeaders()))}},h.onload=c(),d=h.onerror=c("error"),void 0!==h.onabort?h.onabort=d:h.onreadystatechange=function(){4===h.readyState&&a.setTimeout(function(){c&&d()})},c=c("abort");try{h.send(b.hasContent&&b.data||null)}catch(i){if(c)throw i}},abort:function(){c&&c()}}}),r.ajaxPrefilter(function(a){a.crossDomain&&(a.contents.script=!1)}),r.ajaxSetup({accepts:{script:"text/javascript, application/javascript, application/ecmascript, application/x-ecmascript"},contents:{script:/\b(?:java|ecma)script\b/},converters:{"text script":function(a){return r.globalEval(a),a}}}),r.ajaxPrefilter("script",function(a){void 0===a.cache&&(a.cache=!1),a.crossDomain&&(a.type="GET")}),r.ajaxTransport("script",function(a){if(a.crossDomain){var b,c;return{send:function(e,f){b=r("<script>").prop({charset:a.scriptCharset,src:a.url}).on("load error",c=function(a){b.remove(),c=null,a&&f("error"===a.type?404:200,a.type)}),d.head.appendChild(b[0])},abort:function(){c&&c()}}}});var Qb=[],Rb=/(=)\?(?=&|$)|\?\?/;r.ajaxSetup({jsonp:"callback",jsonpCallback:function(){var a=Qb.pop()||r.expando+"_"+rb++;return this[a]=!0,a}}),r.ajaxPrefilter("json jsonp",function(b,c,d){var e,f,g,h=b.jsonp!==!1&&(Rb.test(b.url)?"url":"string"==typeof b.data&&0===(b.contentType||"").indexOf("application/x-www-form-urlencoded")&&Rb.test(b.data)&&"data");if(h||"jsonp"===b.dataTypes[0])return e=b.jsonpCallback=r.isFunction(b.jsonpCallback)?b.jsonpCallback():b.jsonpCallback,h?b[h]=b[h].replace(Rb,"$1"+e):b.jsonp!==!1&&(b.url+=(sb.test(b.url)?"&":"?")+b.jsonp+"="+e),b.converters["script json"]=function(){return g||r.error(e+" was not called"),g[0]},b.dataTypes[0]="json",f=a[e],a[e]=function(){g=arguments},d.always(function(){void 0===f?r(a).removeProp(e):a[e]=f,b[e]&&(b.jsonpCallback=c.jsonpCallback,Qb.push(e)),g&&r.isFunction(f)&&f(g[0]),g=f=void 0}),"script"}),o.createHTMLDocument=function(){var a=d.implementation.createHTMLDocument("").body;return a.innerHTML="<form></form><form></form>",2===a.childNodes.length}(),r.parseHTML=function(a,b,c){if("string"!=typeof a)return[];"boolean"==typeof b&&(c=b,b=!1);var e,f,g;return b||(o.createHTMLDocument?(b=d.implementation.createHTMLDocument(""),e=b.createElement("base"),e.href=d.location.href,b.head.appendChild(e)):b=d),f=B.exec(a),g=!c&&[],f?[b.createElement(f[1])]:(f=oa([a],b,g),g&&g.length&&r(g).remove(),r.merge([],f.childNodes))},r.fn.load=function(a,b,c){var d,e,f,g=this,h=a.indexOf(" ");return h>-1&&(d=r.trim(a.slice(h)),a=a.slice(0,h)),r.isFunction(b)?(c=b,b=void 0):b&&"object"==typeof b&&(e="POST"),g.length>0&&r.ajax({url:a,type:e||"GET",dataType:"html",data:b}).done(function(a){f=arguments,g.html(d?r("<div>").append(r.parseHTML(a)).find(d):a)}).always(c&&function(a,b){g.each(function(){c.apply(this,f||[a.responseText,b,a])})}),this},r.each(["ajaxStart","ajaxStop","ajaxComplete","ajaxError","ajaxSuccess","ajaxSend"],function(a,b){r.fn[b]=function(a){return this.on(b,a)}}),r.expr.pseudos.animated=function(a){return r.grep(r.timers,function(b){return a===b.elem}).length};function Sb(a){return r.isWindow(a)?a:9===a.nodeType&&a.defaultView}r.offset={setOffset:function(a,b,c){var d,e,f,g,h,i,j,k=r.css(a,"position"),l=r(a),m={};"static"===k&&(a.style.position="relative"),h=l.offset(),f=r.css(a,"top"),i=r.css(a,"left"),j=("absolute"===k||"fixed"===k)&&(f+i).indexOf("auto")>-1,j?(d=l.position(),g=d.top,e=d.left):(g=parseFloat(f)||0,e=parseFloat(i)||0),r.isFunction(b)&&(b=b.call(a,c,r.extend({},h))),null!=b.top&&(m.top=b.top-h.top+g),null!=b.left&&(m.left=b.left-h.left+e),"using"in b?b.using.call(a,m):l.css(m)}},r.fn.extend({offset:function(a){if(arguments.length)return void 0===a?this:this.each(function(b){r.offset.setOffset(this,a,b)});var b,c,d,e,f=this[0];if(f)return f.getClientRects().length?(d=f.getBoundingClientRect(),d.width||d.height?(e=f.ownerDocument,c=Sb(e),b=e.documentElement,{top:d.top+c.pageYOffset-b.clientTop,left:d.left+c.pageXOffset-b.clientLeft}):d):{top:0,left:0}},position:function(){if(this[0]){var a,b,c=this[0],d={top:0,left:0};return"fixed"===r.css(c,"position")?b=c.getBoundingClientRect():(a=this.offsetParent(),b=this.offset(),r.nodeName(a[0],"html")||(d=a.offset()),d={top:d.top+r.css(a[0],"borderTopWidth",!0),left:d.left+r.css(a[0],"borderLeftWidth",!0)}),{top:b.top-d.top-r.css(c,"marginTop",!0),left:b.left-d.left-r.css(c,"marginLeft",!0)}}},offsetParent:function(){return this.map(function(){var a=this.offsetParent;while(a&&"static"===r.css(a,"position"))a=a.offsetParent;return a||pa})}}),r.each({scrollLeft:"pageXOffset",scrollTop:"pageYOffset"},function(a,b){var c="pageYOffset"===b;r.fn[a]=function(d){return S(this,function(a,d,e){var f=Sb(a);return void 0===e?f?f[b]:a[d]:void(f?f.scrollTo(c?f.pageXOffset:e,c?e:f.pageYOffset):a[d]=e)},a,d,arguments.length)}}),r.each(["top","left"],function(a,b){r.cssHooks[b]=Na(o.pixelPosition,function(a,c){if(c)return c=Ma(a,b),Ka.test(c)?r(a).position()[b]+"px":c})}),r.each({Height:"height",Width:"width"},function(a,b){r.each({padding:"inner"+a,content:b,"":"outer"+a},function(c,d){r.fn[d]=function(e,f){var g=arguments.length&&(c||"boolean"!=typeof e),h=c||(e===!0||f===!0?"margin":"border");return S(this,function(b,c,e){var f;return r.isWindow(b)?0===d.indexOf("outer")?b["inner"+a]:b.document.documentElement["client"+a]:9===b.nodeType?(f=b.documentElement,Math.max(b.body["scroll"+a],f["scroll"+a],b.body["offset"+a],f["offset"+a],f["client"+a])):void 0===e?r.css(b,c,h):r.style(b,c,e,h)},b,g?e:void 0,g)}})}),r.fn.extend({bind:function(a,b,c){return this.on(a,null,b,c)},unbind:function(a,b){return this.off(a,null,b)},delegate:function(a,b,c,d){return this.on(b,a,c,d)},undelegate:function(a,b,c){return 1===arguments.length?this.off(a,"**"):this.off(b,a||"**",c)}}),r.parseJSON=JSON.parse,"function"==typeof define&&define.amd&&define("jquery",[],function(){return r});var Tb=a.jQuery,Ub=a.$;return r.noConflict=function(b){return a.$===r&&(a.$=Ub),b&&a.jQuery===r&&(a.jQuery=Tb),r},b||(a.jQuery=a.$=r),r});
+/*! jQuery v3.2.1 | (c) JS Foundation and other contributors | jquery.org/license */
+!function(a,b){"use strict";"object"==typeof module&&"object"==typeof module.exports?module.exports=a.document?b(a,!0):function(a){if(!a.document)throw new Error("jQuery requires a window with a document");return b(a)}:b(a)}("undefined"!=typeof window?window:this,function(a,b){"use strict";var c=[],d=a.document,e=Object.getPrototypeOf,f=c.slice,g=c.concat,h=c.push,i=c.indexOf,j={},k=j.toString,l=j.hasOwnProperty,m=l.toString,n=m.call(Object),o={};function p(a,b){b=b||d;var c=b.createElement("script");c.text=a,b.head.appendChild(c).parentNode.removeChild(c)}var q="3.2.1",r=function(a,b){return new r.fn.init(a,b)},s=/^[\s\uFEFF\xA0]+|[\s\uFEFF\xA0]+$/g,t=/^-ms-/,u=/-([a-z])/g,v=function(a,b){return b.toUpperCase()};r.fn=r.prototype={jquery:q,constructor:r,length:0,toArray:function(){return f.call(this)},get:function(a){return null==a?f.call(this):a<0?this[a+this.length]:this[a]},pushStack:function(a){var b=r.merge(this.constructor(),a);return b.prevObject=this,b},each:function(a){return r.each(this,a)},map:function(a){return this.pushStack(r.map(this,function(b,c){return a.call(b,c,b)}))},slice:function(){return this.pushStack(f.apply(this,arguments))},first:function(){return this.eq(0)},last:function(){return this.eq(-1)},eq:function(a){var b=this.length,c=+a+(a<0?b:0);return this.pushStack(c>=0&&c<b?[this[c]]:[])},end:function(){return this.prevObject||this.constructor()},push:h,sort:c.sort,splice:c.splice},r.extend=r.fn.extend=function(){var a,b,c,d,e,f,g=arguments[0]||{},h=1,i=arguments.length,j=!1;for("boolean"==typeof g&&(j=g,g=arguments[h]||{},h++),"object"==typeof g||r.isFunction(g)||(g={}),h===i&&(g=this,h--);h<i;h++)if(null!=(a=arguments[h]))for(b in a)c=g[b],d=a[b],g!==d&&(j&&d&&(r.isPlainObject(d)||(e=Array.isArray(d)))?(e?(e=!1,f=c&&Array.isArray(c)?c:[]):f=c&&r.isPlainObject(c)?c:{},g[b]=r.extend(j,f,d)):void 0!==d&&(g[b]=d));return g},r.extend({expando:"jQuery"+(q+Math.random()).replace(/\D/g,""),isReady:!0,error:function(a){throw new Error(a)},noop:function(){},isFunction:function(a){return"function"===r.type(a)},isWindow:function(a){return null!=a&&a===a.window},isNumeric:function(a){var b=r.type(a);return("number"===b||"string"===b)&&!isNaN(a-parseFloat(a))},isPlainObject:function(a){var b,c;return!(!a||"[object Object]"!==k.call(a))&&(!(b=e(a))||(c=l.call(b,"constructor")&&b.constructor,"function"==typeof c&&m.call(c)===n))},isEmptyObject:function(a){var b;for(b in a)return!1;return!0},type:function(a){return null==a?a+"":"object"==typeof a||"function"==typeof a?j[k.call(a)]||"object":typeof a},globalEval:function(a){p(a)},camelCase:function(a){return a.replace(t,"ms-").replace(u,v)},each:function(a,b){var c,d=0;if(w(a)){for(c=a.length;d<c;d++)if(b.call(a[d],d,a[d])===!1)break}else for(d in a)if(b.call(a[d],d,a[d])===!1)break;return a},trim:function(a){return null==a?"":(a+"").replace(s,"")},makeArray:function(a,b){var c=b||[];return null!=a&&(w(Object(a))?r.merge(c,"string"==typeof a?[a]:a):h.call(c,a)),c},inArray:function(a,b,c){return null==b?-1:i.call(b,a,c)},merge:function(a,b){for(var c=+b.length,d=0,e=a.length;d<c;d++)a[e++]=b[d];return a.length=e,a},grep:function(a,b,c){for(var d,e=[],f=0,g=a.length,h=!c;f<g;f++)d=!b(a[f],f),d!==h&&e.push(a[f]);return e},map:function(a,b,c){var d,e,f=0,h=[];if(w(a))for(d=a.length;f<d;f++)e=b(a[f],f,c),null!=e&&h.push(e);else for(f in a)e=b(a[f],f,c),null!=e&&h.push(e);return g.apply([],h)},guid:1,proxy:function(a,b){var c,d,e;if("string"==typeof b&&(c=a[b],b=a,a=c),r.isFunction(a))return d=f.call(arguments,2),e=function(){return a.apply(b||this,d.concat(f.call(arguments)))},e.guid=a.guid=a.guid||r.guid++,e},now:Date.now,support:o}),"function"==typeof Symbol&&(r.fn[Symbol.iterator]=c[Symbol.iterator]),r.each("Boolean Number String Function Array Date RegExp Object Error Symbol".split(" "),function(a,b){j["[object "+b+"]"]=b.toLowerCase()});function w(a){var b=!!a&&"length"in a&&a.length,c=r.type(a);return"function"!==c&&!r.isWindow(a)&&("array"===c||0===b||"number"==typeof b&&b>0&&b-1 in a)}var x=function(a){var b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u="sizzle"+1*new Date,v=a.document,w=0,x=0,y=ha(),z=ha(),A=ha(),B=function(a,b){return a===b&&(l=!0),0},C={}.hasOwnProperty,D=[],E=D.pop,F=D.push,G=D.push,H=D.slice,I=function(a,b){for(var c=0,d=a.length;c<d;c++)if(a[c]===b)return c;return-1},J="checked|selected|async|autofocus|autoplay|controls|defer|disabled|hidden|ismap|loop|multiple|open|readonly|required|scoped",K="[\\x20\\t\\r\\n\\f]",L="(?:\\\\.|[\\w-]|[^\0-\\xa0])+",M="\\["+K+"*("+L+")(?:"+K+"*([*^$|!~]?=)"+K+"*(?:'((?:\\\\.|[^\\\\'])*)'|\"((?:\\\\.|[^\\\\\"])*)\"|("+L+"))|)"+K+"*\\]",N=":("+L+")(?:\\((('((?:\\\\.|[^\\\\'])*)'|\"((?:\\\\.|[^\\\\\"])*)\")|((?:\\\\.|[^\\\\()[\\]]|"+M+")*)|.*)\\)|)",O=new RegExp(K+"+","g"),P=new RegExp("^"+K+"+|((?:^|[^\\\\])(?:\\\\.)*)"+K+"+$","g"),Q=new RegExp("^"+K+"*,"+K+"*"),R=new RegExp("^"+K+"*([>+~]|"+K+")"+K+"*"),S=new RegExp("="+K+"*([^\\]'\"]*?)"+K+"*\\]","g"),T=new RegExp(N),U=new RegExp("^"+L+"$"),V={ID:new RegExp("^#("+L+")"),CLASS:new RegExp("^\\.("+L+")"),TAG:new RegExp("^("+L+"|[*])"),ATTR:new RegExp("^"+M),PSEUDO:new RegExp("^"+N),CHILD:new RegExp("^:(only|first|last|nth|nth-last)-(child|of-type)(?:\\("+K+"*(even|odd|(([+-]|)(\\d*)n|)"+K+"*(?:([+-]|)"+K+"*(\\d+)|))"+K+"*\\)|)","i"),bool:new RegExp("^(?:"+J+")$","i"),needsContext:new RegExp("^"+K+"*[>+~]|:(even|odd|eq|gt|lt|nth|first|last)(?:\\("+K+"*((?:-\\d)?\\d*)"+K+"*\\)|)(?=[^-]|$)","i")},W=/^(?:input|select|textarea|button)$/i,X=/^h\d$/i,Y=/^[^{]+\{\s*\[native \w/,Z=/^(?:#([\w-]+)|(\w+)|\.([\w-]+))$/,$=/[+~]/,_=new RegExp("\\\\([\\da-f]{1,6}"+K+"?|("+K+")|.)","ig"),aa=function(a,b,c){var d="0x"+b-65536;return d!==d||c?b:d<0?String.fromCharCode(d+65536):String.fromCharCode(d>>10|55296,1023&d|56320)},ba=/([\0-\x1f\x7f]|^-?\d)|^-$|[^\0-\x1f\x7f-\uFFFF\w-]/g,ca=function(a,b){return b?"\0"===a?"\ufffd":a.slice(0,-1)+"\\"+a.charCodeAt(a.length-1).toString(16)+" ":"\\"+a},da=function(){m()},ea=ta(function(a){return a.disabled===!0&&("form"in a||"label"in a)},{dir:"parentNode",next:"legend"});try{G.apply(D=H.call(v.childNodes),v.childNodes),D[v.childNodes.length].nodeType}catch(fa){G={apply:D.length?function(a,b){F.apply(a,H.call(b))}:function(a,b){var c=a.length,d=0;while(a[c++]=b[d++]);a.length=c-1}}}function ga(a,b,d,e){var f,h,j,k,l,o,r,s=b&&b.ownerDocument,w=b?b.nodeType:9;if(d=d||[],"string"!=typeof a||!a||1!==w&&9!==w&&11!==w)return d;if(!e&&((b?b.ownerDocument||b:v)!==n&&m(b),b=b||n,p)){if(11!==w&&(l=Z.exec(a)))if(f=l[1]){if(9===w){if(!(j=b.getElementById(f)))return d;if(j.id===f)return d.push(j),d}else if(s&&(j=s.getElementById(f))&&t(b,j)&&j.id===f)return d.push(j),d}else{if(l[2])return G.apply(d,b.getElementsByTagName(a)),d;if((f=l[3])&&c.getElementsByClassName&&b.getElementsByClassName)return G.apply(d,b.getElementsByClassName(f)),d}if(c.qsa&&!A[a+" "]&&(!q||!q.test(a))){if(1!==w)s=b,r=a;else if("object"!==b.nodeName.toLowerCase()){(k=b.getAttribute("id"))?k=k.replace(ba,ca):b.setAttribute("id",k=u),o=g(a),h=o.length;while(h--)o[h]="#"+k+" "+sa(o[h]);r=o.join(","),s=$.test(a)&&qa(b.parentNode)||b}if(r)try{return G.apply(d,s.querySelectorAll(r)),d}catch(x){}finally{k===u&&b.removeAttribute("id")}}}return i(a.replace(P,"$1"),b,d,e)}function ha(){var a=[];function b(c,e){return a.push(c+" ")>d.cacheLength&&delete b[a.shift()],b[c+" "]=e}return b}function ia(a){return a[u]=!0,a}function ja(a){var b=n.createElement("fieldset");try{return!!a(b)}catch(c){return!1}finally{b.parentNode&&b.parentNode.removeChild(b),b=null}}function ka(a,b){var c=a.split("|"),e=c.length;while(e--)d.attrHandle[c[e]]=b}function la(a,b){var c=b&&a,d=c&&1===a.nodeType&&1===b.nodeType&&a.sourceIndex-b.sourceIndex;if(d)return d;if(c)while(c=c.nextSibling)if(c===b)return-1;return a?1:-1}function ma(a){return function(b){var c=b.nodeName.toLowerCase();return"input"===c&&b.type===a}}function na(a){return function(b){var c=b.nodeName.toLowerCase();return("input"===c||"button"===c)&&b.type===a}}function oa(a){return function(b){return"form"in b?b.parentNode&&b.disabled===!1?"label"in b?"label"in b.parentNode?b.parentNode.disabled===a:b.disabled===a:b.isDisabled===a||b.isDisabled!==!a&&ea(b)===a:b.disabled===a:"label"in b&&b.disabled===a}}function pa(a){return ia(function(b){return b=+b,ia(function(c,d){var e,f=a([],c.length,b),g=f.length;while(g--)c[e=f[g]]&&(c[e]=!(d[e]=c[e]))})})}function qa(a){return a&&"undefined"!=typeof a.getElementsByTagName&&a}c=ga.support={},f=ga.isXML=function(a){var b=a&&(a.ownerDocument||a).documentElement;return!!b&&"HTML"!==b.nodeName},m=ga.setDocument=function(a){var b,e,g=a?a.ownerDocument||a:v;return g!==n&&9===g.nodeType&&g.documentElement?(n=g,o=n.documentElement,p=!f(n),v!==n&&(e=n.defaultView)&&e.top!==e&&(e.addEventListener?e.addEventListener("unload",da,!1):e.attachEvent&&e.attachEvent("onunload",da)),c.attributes=ja(function(a){return a.className="i",!a.getAttribute("className")}),c.getElementsByTagName=ja(function(a){return a.appendChild(n.createComment("")),!a.getElementsByTagName("*").length}),c.getElementsByClassName=Y.test(n.getElementsByClassName),c.getById=ja(function(a){return o.appendChild(a).id=u,!n.getElementsByName||!n.getElementsByName(u).length}),c.getById?(d.filter.ID=function(a){var b=a.replace(_,aa);return function(a){return a.getAttribute("id")===b}},d.find.ID=function(a,b){if("undefined"!=typeof b.getElementById&&p){var c=b.getElementById(a);return c?[c]:[]}}):(d.filter.ID=function(a){var b=a.replace(_,aa);return function(a){var c="undefined"!=typeof a.getAttributeNode&&a.getAttributeNode("id");return c&&c.value===b}},d.find.ID=function(a,b){if("undefined"!=typeof b.getElementById&&p){var c,d,e,f=b.getElementById(a);if(f){if(c=f.getAttributeNode("id"),c&&c.value===a)return[f];e=b.getElementsByName(a),d=0;while(f=e[d++])if(c=f.getAttributeNode("id"),c&&c.value===a)return[f]}return[]}}),d.find.TAG=c.getElementsByTagName?function(a,b){return"undefined"!=typeof b.getElementsByTagName?b.getElementsByTagName(a):c.qsa?b.querySelectorAll(a):void 0}:function(a,b){var c,d=[],e=0,f=b.getElementsByTagName(a);if("*"===a){while(c=f[e++])1===c.nodeType&&d.push(c);return d}return f},d.find.CLASS=c.getElementsByClassName&&function(a,b){if("undefined"!=typeof b.getElementsByClassName&&p)return b.getElementsByClassName(a)},r=[],q=[],(c.qsa=Y.test(n.querySelectorAll))&&(ja(function(a){o.appendChild(a).innerHTML="<a id='"+u+"'></a><select id='"+u+"-\r\\' msallowcapture=''><option selected=''></option></select>",a.querySelectorAll("[msallowcapture^='']").length&&q.push("[*^$]="+K+"*(?:''|\"\")"),a.querySelectorAll("[selected]").length||q.push("\\["+K+"*(?:value|"+J+")"),a.querySelectorAll("[id~="+u+"-]").length||q.push("~="),a.querySelectorAll(":checked").length||q.push(":checked"),a.querySelectorAll("a#"+u+"+*").length||q.push(".#.+[+~]")}),ja(function(a){a.innerHTML="<a href='' disabled='disabled'></a><select disabled='disabled'><option/></select>";var b=n.createElement("input");b.setAttribute("type","hidden"),a.appendChild(b).setAttribute("name","D"),a.querySelectorAll("[name=d]").length&&q.push("name"+K+"*[*^$|!~]?="),2!==a.querySelectorAll(":enabled").length&&q.push(":enabled",":disabled"),o.appendChild(a).disabled=!0,2!==a.querySelectorAll(":disabled").length&&q.push(":enabled",":disabled"),a.querySelectorAll("*,:x"),q.push(",.*:")})),(c.matchesSelector=Y.test(s=o.matches||o.webkitMatchesSelector||o.mozMatchesSelector||o.oMatchesSelector||o.msMatchesSelector))&&ja(function(a){c.disconnectedMatch=s.call(a,"*"),s.call(a,"[s!='']:x"),r.push("!=",N)}),q=q.length&&new RegExp(q.join("|")),r=r.length&&new RegExp(r.join("|")),b=Y.test(o.compareDocumentPosition),t=b||Y.test(o.contains)?function(a,b){var c=9===a.nodeType?a.documentElement:a,d=b&&b.parentNode;return a===d||!(!d||1!==d.nodeType||!(c.contains?c.contains(d):a.compareDocumentPosition&&16&a.compareDocumentPosition(d)))}:function(a,b){if(b)while(b=b.parentNode)if(b===a)return!0;return!1},B=b?function(a,b){if(a===b)return l=!0,0;var d=!a.compareDocumentPosition-!b.compareDocumentPosition;return d?d:(d=(a.ownerDocument||a)===(b.ownerDocument||b)?a.compareDocumentPosition(b):1,1&d||!c.sortDetached&&b.compareDocumentPosition(a)===d?a===n||a.ownerDocument===v&&t(v,a)?-1:b===n||b.ownerDocument===v&&t(v,b)?1:k?I(k,a)-I(k,b):0:4&d?-1:1)}:function(a,b){if(a===b)return l=!0,0;var c,d=0,e=a.parentNode,f=b.parentNode,g=[a],h=[b];if(!e||!f)return a===n?-1:b===n?1:e?-1:f?1:k?I(k,a)-I(k,b):0;if(e===f)return la(a,b);c=a;while(c=c.parentNode)g.unshift(c);c=b;while(c=c.parentNode)h.unshift(c);while(g[d]===h[d])d++;return d?la(g[d],h[d]):g[d]===v?-1:h[d]===v?1:0},n):n},ga.matches=function(a,b){return ga(a,null,null,b)},ga.matchesSelector=function(a,b){if((a.ownerDocument||a)!==n&&m(a),b=b.replace(S,"='$1']"),c.matchesSelector&&p&&!A[b+" "]&&(!r||!r.test(b))&&(!q||!q.test(b)))try{var d=s.call(a,b);if(d||c.disconnectedMatch||a.document&&11!==a.document.nodeType)return d}catch(e){}return ga(b,n,null,[a]).length>0},ga.contains=function(a,b){return(a.ownerDocument||a)!==n&&m(a),t(a,b)},ga.attr=function(a,b){(a.ownerDocument||a)!==n&&m(a);var e=d.attrHandle[b.toLowerCase()],f=e&&C.call(d.attrHandle,b.toLowerCase())?e(a,b,!p):void 0;return void 0!==f?f:c.attributes||!p?a.getAttribute(b):(f=a.getAttributeNode(b))&&f.specified?f.value:null},ga.escape=function(a){return(a+"").replace(ba,ca)},ga.error=function(a){throw new Error("Syntax error, unrecognized expression: "+a)},ga.uniqueSort=function(a){var b,d=[],e=0,f=0;if(l=!c.detectDuplicates,k=!c.sortStable&&a.slice(0),a.sort(B),l){while(b=a[f++])b===a[f]&&(e=d.push(f));while(e--)a.splice(d[e],1)}return k=null,a},e=ga.getText=function(a){var b,c="",d=0,f=a.nodeType;if(f){if(1===f||9===f||11===f){if("string"==typeof a.textContent)return a.textContent;for(a=a.firstChild;a;a=a.nextSibling)c+=e(a)}else if(3===f||4===f)return a.nodeValue}else while(b=a[d++])c+=e(b);return c},d=ga.selectors={cacheLength:50,createPseudo:ia,match:V,attrHandle:{},find:{},relative:{">":{dir:"parentNode",first:!0}," ":{dir:"parentNode"},"+":{dir:"previousSibling",first:!0},"~":{dir:"previousSibling"}},preFilter:{ATTR:function(a){return a[1]=a[1].replace(_,aa),a[3]=(a[3]||a[4]||a[5]||"").replace(_,aa),"~="===a[2]&&(a[3]=" "+a[3]+" "),a.slice(0,4)},CHILD:function(a){return a[1]=a[1].toLowerCase(),"nth"===a[1].slice(0,3)?(a[3]||ga.error(a[0]),a[4]=+(a[4]?a[5]+(a[6]||1):2*("even"===a[3]||"odd"===a[3])),a[5]=+(a[7]+a[8]||"odd"===a[3])):a[3]&&ga.error(a[0]),a},PSEUDO:function(a){var b,c=!a[6]&&a[2];return V.CHILD.test(a[0])?null:(a[3]?a[2]=a[4]||a[5]||"":c&&T.test(c)&&(b=g(c,!0))&&(b=c.indexOf(")",c.length-b)-c.length)&&(a[0]=a[0].slice(0,b),a[2]=c.slice(0,b)),a.slice(0,3))}},filter:{TAG:function(a){var b=a.replace(_,aa).toLowerCase();return"*"===a?function(){return!0}:function(a){return a.nodeName&&a.nodeName.toLowerCase()===b}},CLASS:function(a){var b=y[a+" "];return b||(b=new RegExp("(^|"+K+")"+a+"("+K+"|$)"))&&y(a,function(a){return b.test("string"==typeof a.className&&a.className||"undefined"!=typeof a.getAttribute&&a.getAttribute("class")||"")})},ATTR:function(a,b,c){return function(d){var e=ga.attr(d,a);return null==e?"!="===b:!b||(e+="","="===b?e===c:"!="===b?e!==c:"^="===b?c&&0===e.indexOf(c):"*="===b?c&&e.indexOf(c)>-1:"$="===b?c&&e.slice(-c.length)===c:"~="===b?(" "+e.replace(O," ")+" ").indexOf(c)>-1:"|="===b&&(e===c||e.slice(0,c.length+1)===c+"-"))}},CHILD:function(a,b,c,d,e){var f="nth"!==a.slice(0,3),g="last"!==a.slice(-4),h="of-type"===b;return 1===d&&0===e?function(a){return!!a.parentNode}:function(b,c,i){var j,k,l,m,n,o,p=f!==g?"nextSibling":"previousSibling",q=b.parentNode,r=h&&b.nodeName.toLowerCase(),s=!i&&!h,t=!1;if(q){if(f){while(p){m=b;while(m=m[p])if(h?m.nodeName.toLowerCase()===r:1===m.nodeType)return!1;o=p="only"===a&&!o&&"nextSibling"}return!0}if(o=[g?q.firstChild:q.lastChild],g&&s){m=q,l=m[u]||(m[u]={}),k=l[m.uniqueID]||(l[m.uniqueID]={}),j=k[a]||[],n=j[0]===w&&j[1],t=n&&j[2],m=n&&q.childNodes[n];while(m=++n&&m&&m[p]||(t=n=0)||o.pop())if(1===m.nodeType&&++t&&m===b){k[a]=[w,n,t];break}}else if(s&&(m=b,l=m[u]||(m[u]={}),k=l[m.uniqueID]||(l[m.uniqueID]={}),j=k[a]||[],n=j[0]===w&&j[1],t=n),t===!1)while(m=++n&&m&&m[p]||(t=n=0)||o.pop())if((h?m.nodeName.toLowerCase()===r:1===m.nodeType)&&++t&&(s&&(l=m[u]||(m[u]={}),k=l[m.uniqueID]||(l[m.uniqueID]={}),k[a]=[w,t]),m===b))break;return t-=e,t===d||t%d===0&&t/d>=0}}},PSEUDO:function(a,b){var c,e=d.pseudos[a]||d.setFilters[a.toLowerCase()]||ga.error("unsupported pseudo: "+a);return e[u]?e(b):e.length>1?(c=[a,a,"",b],d.setFilters.hasOwnProperty(a.toLowerCase())?ia(function(a,c){var d,f=e(a,b),g=f.length;while(g--)d=I(a,f[g]),a[d]=!(c[d]=f[g])}):function(a){return e(a,0,c)}):e}},pseudos:{not:ia(function(a){var b=[],c=[],d=h(a.replace(P,"$1"));return d[u]?ia(function(a,b,c,e){var f,g=d(a,null,e,[]),h=a.length;while(h--)(f=g[h])&&(a[h]=!(b[h]=f))}):function(a,e,f){return b[0]=a,d(b,null,f,c),b[0]=null,!c.pop()}}),has:ia(function(a){return function(b){return ga(a,b).length>0}}),contains:ia(function(a){return a=a.replace(_,aa),function(b){return(b.textContent||b.innerText||e(b)).indexOf(a)>-1}}),lang:ia(function(a){return U.test(a||"")||ga.error("unsupported lang: "+a),a=a.replace(_,aa).toLowerCase(),function(b){var c;do if(c=p?b.lang:b.getAttribute("xml:lang")||b.getAttribute("lang"))return c=c.toLowerCase(),c===a||0===c.indexOf(a+"-");while((b=b.parentNode)&&1===b.nodeType);return!1}}),target:function(b){var c=a.location&&a.location.hash;return c&&c.slice(1)===b.id},root:function(a){return a===o},focus:function(a){return a===n.activeElement&&(!n.hasFocus||n.hasFocus())&&!!(a.type||a.href||~a.tabIndex)},enabled:oa(!1),disabled:oa(!0),checked:function(a){var b=a.nodeName.toLowerCase();return"input"===b&&!!a.checked||"option"===b&&!!a.selected},selected:function(a){return a.parentNode&&a.parentNode.selectedIndex,a.selected===!0},empty:function(a){for(a=a.firstChild;a;a=a.nextSibling)if(a.nodeType<6)return!1;return!0},parent:function(a){return!d.pseudos.empty(a)},header:function(a){return X.test(a.nodeName)},input:function(a){return W.test(a.nodeName)},button:function(a){var b=a.nodeName.toLowerCase();return"input"===b&&"button"===a.type||"button"===b},text:function(a){var b;return"input"===a.nodeName.toLowerCase()&&"text"===a.type&&(null==(b=a.getAttribute("type"))||"text"===b.toLowerCase())},first:pa(function(){return[0]}),last:pa(function(a,b){return[b-1]}),eq:pa(function(a,b,c){return[c<0?c+b:c]}),even:pa(function(a,b){for(var c=0;c<b;c+=2)a.push(c);return a}),odd:pa(function(a,b){for(var c=1;c<b;c+=2)a.push(c);return a}),lt:pa(function(a,b,c){for(var d=c<0?c+b:c;--d>=0;)a.push(d);return a}),gt:pa(function(a,b,c){for(var d=c<0?c+b:c;++d<b;)a.push(d);return a})}},d.pseudos.nth=d.pseudos.eq;for(b in{radio:!0,checkbox:!0,file:!0,password:!0,image:!0})d.pseudos[b]=ma(b);for(b in{submit:!0,reset:!0})d.pseudos[b]=na(b);function ra(){}ra.prototype=d.filters=d.pseudos,d.setFilters=new ra,g=ga.tokenize=function(a,b){var c,e,f,g,h,i,j,k=z[a+" "];if(k)return b?0:k.slice(0);h=a,i=[],j=d.preFilter;while(h){c&&!(e=Q.exec(h))||(e&&(h=h.slice(e[0].length)||h),i.push(f=[])),c=!1,(e=R.exec(h))&&(c=e.shift(),f.push({value:c,type:e[0].replace(P," ")}),h=h.slice(c.length));for(g in d.filter)!(e=V[g].exec(h))||j[g]&&!(e=j[g](e))||(c=e.shift(),f.push({value:c,type:g,matches:e}),h=h.slice(c.length));if(!c)break}return b?h.length:h?ga.error(a):z(a,i).slice(0)};function sa(a){for(var b=0,c=a.length,d="";b<c;b++)d+=a[b].value;return d}function ta(a,b,c){var d=b.dir,e=b.next,f=e||d,g=c&&"parentNode"===f,h=x++;return b.first?function(b,c,e){while(b=b[d])if(1===b.nodeType||g)return a(b,c,e);return!1}:function(b,c,i){var j,k,l,m=[w,h];if(i){while(b=b[d])if((1===b.nodeType||g)&&a(b,c,i))return!0}else while(b=b[d])if(1===b.nodeType||g)if(l=b[u]||(b[u]={}),k=l[b.uniqueID]||(l[b.uniqueID]={}),e&&e===b.nodeName.toLowerCase())b=b[d]||b;else{if((j=k[f])&&j[0]===w&&j[1]===h)return m[2]=j[2];if(k[f]=m,m[2]=a(b,c,i))return!0}return!1}}function ua(a){return a.length>1?function(b,c,d){var e=a.length;while(e--)if(!a[e](b,c,d))return!1;return!0}:a[0]}function va(a,b,c){for(var d=0,e=b.length;d<e;d++)ga(a,b[d],c);return c}function wa(a,b,c,d,e){for(var f,g=[],h=0,i=a.length,j=null!=b;h<i;h++)(f=a[h])&&(c&&!c(f,d,e)||(g.push(f),j&&b.push(h)));return g}function xa(a,b,c,d,e,f){return d&&!d[u]&&(d=xa(d)),e&&!e[u]&&(e=xa(e,f)),ia(function(f,g,h,i){var j,k,l,m=[],n=[],o=g.length,p=f||va(b||"*",h.nodeType?[h]:h,[]),q=!a||!f&&b?p:wa(p,m,a,h,i),r=c?e||(f?a:o||d)?[]:g:q;if(c&&c(q,r,h,i),d){j=wa(r,n),d(j,[],h,i),k=j.length;while(k--)(l=j[k])&&(r[n[k]]=!(q[n[k]]=l))}if(f){if(e||a){if(e){j=[],k=r.length;while(k--)(l=r[k])&&j.push(q[k]=l);e(null,r=[],j,i)}k=r.length;while(k--)(l=r[k])&&(j=e?I(f,l):m[k])>-1&&(f[j]=!(g[j]=l))}}else r=wa(r===g?r.splice(o,r.length):r),e?e(null,g,r,i):G.apply(g,r)})}function ya(a){for(var b,c,e,f=a.length,g=d.relative[a[0].type],h=g||d.relative[" "],i=g?1:0,k=ta(function(a){return a===b},h,!0),l=ta(function(a){return I(b,a)>-1},h,!0),m=[function(a,c,d){var e=!g&&(d||c!==j)||((b=c).nodeType?k(a,c,d):l(a,c,d));return b=null,e}];i<f;i++)if(c=d.relative[a[i].type])m=[ta(ua(m),c)];else{if(c=d.filter[a[i].type].apply(null,a[i].matches),c[u]){for(e=++i;e<f;e++)if(d.relative[a[e].type])break;return xa(i>1&&ua(m),i>1&&sa(a.slice(0,i-1).concat({value:" "===a[i-2].type?"*":""})).replace(P,"$1"),c,i<e&&ya(a.slice(i,e)),e<f&&ya(a=a.slice(e)),e<f&&sa(a))}m.push(c)}return ua(m)}function za(a,b){var c=b.length>0,e=a.length>0,f=function(f,g,h,i,k){var l,o,q,r=0,s="0",t=f&&[],u=[],v=j,x=f||e&&d.find.TAG("*",k),y=w+=null==v?1:Math.random()||.1,z=x.length;for(k&&(j=g===n||g||k);s!==z&&null!=(l=x[s]);s++){if(e&&l){o=0,g||l.ownerDocument===n||(m(l),h=!p);while(q=a[o++])if(q(l,g||n,h)){i.push(l);break}k&&(w=y)}c&&((l=!q&&l)&&r--,f&&t.push(l))}if(r+=s,c&&s!==r){o=0;while(q=b[o++])q(t,u,g,h);if(f){if(r>0)while(s--)t[s]||u[s]||(u[s]=E.call(i));u=wa(u)}G.apply(i,u),k&&!f&&u.length>0&&r+b.length>1&&ga.uniqueSort(i)}return k&&(w=y,j=v),t};return c?ia(f):f}return h=ga.compile=function(a,b){var c,d=[],e=[],f=A[a+" "];if(!f){b||(b=g(a)),c=b.length;while(c--)f=ya(b[c]),f[u]?d.push(f):e.push(f);f=A(a,za(e,d)),f.selector=a}return f},i=ga.select=function(a,b,c,e){var f,i,j,k,l,m="function"==typeof a&&a,n=!e&&g(a=m.selector||a);if(c=c||[],1===n.length){if(i=n[0]=n[0].slice(0),i.length>2&&"ID"===(j=i[0]).type&&9===b.nodeType&&p&&d.relative[i[1].type]){if(b=(d.find.ID(j.matches[0].replace(_,aa),b)||[])[0],!b)return c;m&&(b=b.parentNode),a=a.slice(i.shift().value.length)}f=V.needsContext.test(a)?0:i.length;while(f--){if(j=i[f],d.relative[k=j.type])break;if((l=d.find[k])&&(e=l(j.matches[0].replace(_,aa),$.test(i[0].type)&&qa(b.parentNode)||b))){if(i.splice(f,1),a=e.length&&sa(i),!a)return G.apply(c,e),c;break}}}return(m||h(a,n))(e,b,!p,c,!b||$.test(a)&&qa(b.parentNode)||b),c},c.sortStable=u.split("").sort(B).join("")===u,c.detectDuplicates=!!l,m(),c.sortDetached=ja(function(a){return 1&a.compareDocumentPosition(n.createElement("fieldset"))}),ja(function(a){return a.innerHTML="<a href='#'></a>","#"===a.firstChild.getAttribute("href")})||ka("type|href|height|width",function(a,b,c){if(!c)return a.getAttribute(b,"type"===b.toLowerCase()?1:2)}),c.attributes&&ja(function(a){return a.innerHTML="<input/>",a.firstChild.setAttribute("value",""),""===a.firstChild.getAttribute("value")})||ka("value",function(a,b,c){if(!c&&"input"===a.nodeName.toLowerCase())return a.defaultValue}),ja(function(a){return null==a.getAttribute("disabled")})||ka(J,function(a,b,c){var d;if(!c)return a[b]===!0?b.toLowerCase():(d=a.getAttributeNode(b))&&d.specified?d.value:null}),ga}(a);r.find=x,r.expr=x.selectors,r.expr[":"]=r.expr.pseudos,r.uniqueSort=r.unique=x.uniqueSort,r.text=x.getText,r.isXMLDoc=x.isXML,r.contains=x.contains,r.escapeSelector=x.escape;var y=function(a,b,c){var d=[],e=void 0!==c;while((a=a[b])&&9!==a.nodeType)if(1===a.nodeType){if(e&&r(a).is(c))break;d.push(a)}return d},z=function(a,b){for(var c=[];a;a=a.nextSibling)1===a.nodeType&&a!==b&&c.push(a);return c},A=r.expr.match.needsContext;function B(a,b){return a.nodeName&&a.nodeName.toLowerCase()===b.toLowerCase()}var C=/^<([a-z][^\/\0>:\x20\t\r\n\f]*)[\x20\t\r\n\f]*\/?>(?:<\/\1>|)$/i,D=/^.[^:#\[\.,]*$/;function E(a,b,c){return r.isFunction(b)?r.grep(a,function(a,d){return!!b.call(a,d,a)!==c}):b.nodeType?r.grep(a,function(a){return a===b!==c}):"string"!=typeof b?r.grep(a,function(a){return i.call(b,a)>-1!==c}):D.test(b)?r.filter(b,a,c):(b=r.filter(b,a),r.grep(a,function(a){return i.call(b,a)>-1!==c&&1===a.nodeType}))}r.filter=function(a,b,c){var d=b[0];return c&&(a=":not("+a+")"),1===b.length&&1===d.nodeType?r.find.matchesSelector(d,a)?[d]:[]:r.find.matches(a,r.grep(b,function(a){return 1===a.nodeType}))},r.fn.extend({find:function(a){var b,c,d=this.length,e=this;if("string"!=typeof a)return this.pushStack(r(a).filter(function(){for(b=0;b<d;b++)if(r.contains(e[b],this))return!0}));for(c=this.pushStack([]),b=0;b<d;b++)r.find(a,e[b],c);return d>1?r.uniqueSort(c):c},filter:function(a){return this.pushStack(E(this,a||[],!1))},not:function(a){return this.pushStack(E(this,a||[],!0))},is:function(a){return!!E(this,"string"==typeof a&&A.test(a)?r(a):a||[],!1).length}});var F,G=/^(?:\s*(<[\w\W]+>)[^>]*|#([\w-]+))$/,H=r.fn.init=function(a,b,c){var e,f;if(!a)return this;if(c=c||F,"string"==typeof a){if(e="<"===a[0]&&">"===a[a.length-1]&&a.length>=3?[null,a,null]:G.exec(a),!e||!e[1]&&b)return!b||b.jquery?(b||c).find(a):this.constructor(b).find(a);if(e[1]){if(b=b instanceof r?b[0]:b,r.merge(this,r.parseHTML(e[1],b&&b.nodeType?b.ownerDocument||b:d,!0)),C.test(e[1])&&r.isPlainObject(b))for(e in b)r.isFunction(this[e])?this[e](b[e]):this.attr(e,b[e]);return this}return f=d.getElementById(e[2]),f&&(this[0]=f,this.length=1),this}return a.nodeType?(this[0]=a,this.length=1,this):r.isFunction(a)?void 0!==c.ready?c.ready(a):a(r):r.makeArray(a,this)};H.prototype=r.fn,F=r(d);var I=/^(?:parents|prev(?:Until|All))/,J={children:!0,contents:!0,next:!0,prev:!0};r.fn.extend({has:function(a){var b=r(a,this),c=b.length;return this.filter(function(){for(var a=0;a<c;a++)if(r.contains(this,b[a]))return!0})},closest:function(a,b){var c,d=0,e=this.length,f=[],g="string"!=typeof a&&r(a);if(!A.test(a))for(;d<e;d++)for(c=this[d];c&&c!==b;c=c.parentNode)if(c.nodeType<11&&(g?g.index(c)>-1:1===c.nodeType&&r.find.matchesSelector(c,a))){f.push(c);break}return this.pushStack(f.length>1?r.uniqueSort(f):f)},index:function(a){return a?"string"==typeof a?i.call(r(a),this[0]):i.call(this,a.jquery?a[0]:a):this[0]&&this[0].parentNode?this.first().prevAll().length:-1},add:function(a,b){return this.pushStack(r.uniqueSort(r.merge(this.get(),r(a,b))))},addBack:function(a){return this.add(null==a?this.prevObject:this.prevObject.filter(a))}});function K(a,b){while((a=a[b])&&1!==a.nodeType);return a}r.each({parent:function(a){var b=a.parentNode;return b&&11!==b.nodeType?b:null},parents:function(a){return y(a,"parentNode")},parentsUntil:function(a,b,c){return y(a,"parentNode",c)},next:function(a){return K(a,"nextSibling")},prev:function(a){return K(a,"previousSibling")},nextAll:function(a){return y(a,"nextSibling")},prevAll:function(a){return y(a,"previousSibling")},nextUntil:function(a,b,c){return y(a,"nextSibling",c)},prevUntil:function(a,b,c){return y(a,"previousSibling",c)},siblings:function(a){return z((a.parentNode||{}).firstChild,a)},children:function(a){return z(a.firstChild)},contents:function(a){return B(a,"iframe")?a.contentDocument:(B(a,"template")&&(a=a.content||a),r.merge([],a.childNodes))}},function(a,b){r.fn[a]=function(c,d){var e=r.map(this,b,c);return"Until"!==a.slice(-5)&&(d=c),d&&"string"==typeof d&&(e=r.filter(d,e)),this.length>1&&(J[a]||r.uniqueSort(e),I.test(a)&&e.reverse()),this.pushStack(e)}});var L=/[^\x20\t\r\n\f]+/g;function M(a){var b={};return r.each(a.match(L)||[],function(a,c){b[c]=!0}),b}r.Callbacks=function(a){a="string"==typeof a?M(a):r.extend({},a);var b,c,d,e,f=[],g=[],h=-1,i=function(){for(e=e||a.once,d=b=!0;g.length;h=-1){c=g.shift();while(++h<f.length)f[h].apply(c[0],c[1])===!1&&a.stopOnFalse&&(h=f.length,c=!1)}a.memory||(c=!1),b=!1,e&&(f=c?[]:"")},j={add:function(){return f&&(c&&!b&&(h=f.length-1,g.push(c)),function d(b){r.each(b,function(b,c){r.isFunction(c)?a.unique&&j.has(c)||f.push(c):c&&c.length&&"string"!==r.type(c)&&d(c)})}(arguments),c&&!b&&i()),this},remove:function(){return r.each(arguments,function(a,b){var c;while((c=r.inArray(b,f,c))>-1)f.splice(c,1),c<=h&&h--}),this},has:function(a){return a?r.inArray(a,f)>-1:f.length>0},empty:function(){return f&&(f=[]),this},disable:function(){return e=g=[],f=c="",this},disabled:function(){return!f},lock:function(){return e=g=[],c||b||(f=c=""),this},locked:function(){return!!e},fireWith:function(a,c){return e||(c=c||[],c=[a,c.slice?c.slice():c],g.push(c),b||i()),this},fire:function(){return j.fireWith(this,arguments),this},fired:function(){return!!d}};return j};function N(a){return a}function O(a){throw a}function P(a,b,c,d){var e;try{a&&r.isFunction(e=a.promise)?e.call(a).done(b).fail(c):a&&r.isFunction(e=a.then)?e.call(a,b,c):b.apply(void 0,[a].slice(d))}catch(a){c.apply(void 0,[a])}}r.extend({Deferred:function(b){var c=[["notify","progress",r.Callbacks("memory"),r.Callbacks("memory"),2],["resolve","done",r.Callbacks("once memory"),r.Callbacks("once memory"),0,"resolved"],["reject","fail",r.Callbacks("once memory"),r.Callbacks("once memory"),1,"rejected"]],d="pending",e={state:function(){return d},always:function(){return f.done(arguments).fail(arguments),this},"catch":function(a){return e.then(null,a)},pipe:function(){var a=arguments;return r.Deferred(function(b){r.each(c,function(c,d){var e=r.isFunction(a[d[4]])&&a[d[4]];f[d[1]](function(){var a=e&&e.apply(this,arguments);a&&r.isFunction(a.promise)?a.promise().progress(b.notify).done(b.resolve).fail(b.reject):b[d[0]+"With"](this,e?[a]:arguments)})}),a=null}).promise()},then:function(b,d,e){var f=0;function g(b,c,d,e){return function(){var h=this,i=arguments,j=function(){var a,j;if(!(b<f)){if(a=d.apply(h,i),a===c.promise())throw new TypeError("Thenable self-resolution");j=a&&("object"==typeof a||"function"==typeof a)&&a.then,r.isFunction(j)?e?j.call(a,g(f,c,N,e),g(f,c,O,e)):(f++,j.call(a,g(f,c,N,e),g(f,c,O,e),g(f,c,N,c.notifyWith))):(d!==N&&(h=void 0,i=[a]),(e||c.resolveWith)(h,i))}},k=e?j:function(){try{j()}catch(a){r.Deferred.exceptionHook&&r.Deferred.exceptionHook(a,k.stackTrace),b+1>=f&&(d!==O&&(h=void 0,i=[a]),c.rejectWith(h,i))}};b?k():(r.Deferred.getStackHook&&(k.stackTrace=r.Deferred.getStackHook()),a.setTimeout(k))}}return r.Deferred(function(a){c[0][3].add(g(0,a,r.isFunction(e)?e:N,a.notifyWith)),c[1][3].add(g(0,a,r.isFunction(b)?b:N)),c[2][3].add(g(0,a,r.isFunction(d)?d:O))}).promise()},promise:function(a){return null!=a?r.extend(a,e):e}},f={};return r.each(c,function(a,b){var g=b[2],h=b[5];e[b[1]]=g.add,h&&g.add(function(){d=h},c[3-a][2].disable,c[0][2].lock),g.add(b[3].fire),f[b[0]]=function(){return f[b[0]+"With"](this===f?void 0:this,arguments),this},f[b[0]+"With"]=g.fireWith}),e.promise(f),b&&b.call(f,f),f},when:function(a){var b=arguments.length,c=b,d=Array(c),e=f.call(arguments),g=r.Deferred(),h=function(a){return function(c){d[a]=this,e[a]=arguments.length>1?f.call(arguments):c,--b||g.resolveWith(d,e)}};if(b<=1&&(P(a,g.done(h(c)).resolve,g.reject,!b),"pending"===g.state()||r.isFunction(e[c]&&e[c].then)))return g.then();while(c--)P(e[c],h(c),g.reject);return g.promise()}});var Q=/^(Eval|Internal|Range|Reference|Syntax|Type|URI)Error$/;r.Deferred.exceptionHook=function(b,c){a.console&&a.console.warn&&b&&Q.test(b.name)&&a.console.warn("jQuery.Deferred exception: "+b.message,b.stack,c)},r.readyException=function(b){a.setTimeout(function(){throw b})};var R=r.Deferred();r.fn.ready=function(a){return R.then(a)["catch"](function(a){r.readyException(a)}),this},r.extend({isReady:!1,readyWait:1,ready:function(a){(a===!0?--r.readyWait:r.isReady)||(r.isReady=!0,a!==!0&&--r.readyWait>0||R.resolveWith(d,[r]))}}),r.ready.then=R.then;function S(){d.removeEventListener("DOMContentLoaded",S),
+a.removeEventListener("load",S),r.ready()}"complete"===d.readyState||"loading"!==d.readyState&&!d.documentElement.doScroll?a.setTimeout(r.ready):(d.addEventListener("DOMContentLoaded",S),a.addEventListener("load",S));var T=function(a,b,c,d,e,f,g){var h=0,i=a.length,j=null==c;if("object"===r.type(c)){e=!0;for(h in c)T(a,b,h,c[h],!0,f,g)}else if(void 0!==d&&(e=!0,r.isFunction(d)||(g=!0),j&&(g?(b.call(a,d),b=null):(j=b,b=function(a,b,c){return j.call(r(a),c)})),b))for(;h<i;h++)b(a[h],c,g?d:d.call(a[h],h,b(a[h],c)));return e?a:j?b.call(a):i?b(a[0],c):f},U=function(a){return 1===a.nodeType||9===a.nodeType||!+a.nodeType};function V(){this.expando=r.expando+V.uid++}V.uid=1,V.prototype={cache:function(a){var b=a[this.expando];return b||(b={},U(a)&&(a.nodeType?a[this.expando]=b:Object.defineProperty(a,this.expando,{value:b,configurable:!0}))),b},set:function(a,b,c){var d,e=this.cache(a);if("string"==typeof b)e[r.camelCase(b)]=c;else for(d in b)e[r.camelCase(d)]=b[d];return e},get:function(a,b){return void 0===b?this.cache(a):a[this.expando]&&a[this.expando][r.camelCase(b)]},access:function(a,b,c){return void 0===b||b&&"string"==typeof b&&void 0===c?this.get(a,b):(this.set(a,b,c),void 0!==c?c:b)},remove:function(a,b){var c,d=a[this.expando];if(void 0!==d){if(void 0!==b){Array.isArray(b)?b=b.map(r.camelCase):(b=r.camelCase(b),b=b in d?[b]:b.match(L)||[]),c=b.length;while(c--)delete d[b[c]]}(void 0===b||r.isEmptyObject(d))&&(a.nodeType?a[this.expando]=void 0:delete a[this.expando])}},hasData:function(a){var b=a[this.expando];return void 0!==b&&!r.isEmptyObject(b)}};var W=new V,X=new V,Y=/^(?:\{[\w\W]*\}|\[[\w\W]*\])$/,Z=/[A-Z]/g;function $(a){return"true"===a||"false"!==a&&("null"===a?null:a===+a+""?+a:Y.test(a)?JSON.parse(a):a)}function _(a,b,c){var d;if(void 0===c&&1===a.nodeType)if(d="data-"+b.replace(Z,"-$&").toLowerCase(),c=a.getAttribute(d),"string"==typeof c){try{c=$(c)}catch(e){}X.set(a,b,c)}else c=void 0;return c}r.extend({hasData:function(a){return X.hasData(a)||W.hasData(a)},data:function(a,b,c){return X.access(a,b,c)},removeData:function(a,b){X.remove(a,b)},_data:function(a,b,c){return W.access(a,b,c)},_removeData:function(a,b){W.remove(a,b)}}),r.fn.extend({data:function(a,b){var c,d,e,f=this[0],g=f&&f.attributes;if(void 0===a){if(this.length&&(e=X.get(f),1===f.nodeType&&!W.get(f,"hasDataAttrs"))){c=g.length;while(c--)g[c]&&(d=g[c].name,0===d.indexOf("data-")&&(d=r.camelCase(d.slice(5)),_(f,d,e[d])));W.set(f,"hasDataAttrs",!0)}return e}return"object"==typeof a?this.each(function(){X.set(this,a)}):T(this,function(b){var c;if(f&&void 0===b){if(c=X.get(f,a),void 0!==c)return c;if(c=_(f,a),void 0!==c)return c}else this.each(function(){X.set(this,a,b)})},null,b,arguments.length>1,null,!0)},removeData:function(a){return this.each(function(){X.remove(this,a)})}}),r.extend({queue:function(a,b,c){var d;if(a)return b=(b||"fx")+"queue",d=W.get(a,b),c&&(!d||Array.isArray(c)?d=W.access(a,b,r.makeArray(c)):d.push(c)),d||[]},dequeue:function(a,b){b=b||"fx";var c=r.queue(a,b),d=c.length,e=c.shift(),f=r._queueHooks(a,b),g=function(){r.dequeue(a,b)};"inprogress"===e&&(e=c.shift(),d--),e&&("fx"===b&&c.unshift("inprogress"),delete f.stop,e.call(a,g,f)),!d&&f&&f.empty.fire()},_queueHooks:function(a,b){var c=b+"queueHooks";return W.get(a,c)||W.access(a,c,{empty:r.Callbacks("once memory").add(function(){W.remove(a,[b+"queue",c])})})}}),r.fn.extend({queue:function(a,b){var c=2;return"string"!=typeof a&&(b=a,a="fx",c--),arguments.length<c?r.queue(this[0],a):void 0===b?this:this.each(function(){var c=r.queue(this,a,b);r._queueHooks(this,a),"fx"===a&&"inprogress"!==c[0]&&r.dequeue(this,a)})},dequeue:function(a){return this.each(function(){r.dequeue(this,a)})},clearQueue:function(a){return this.queue(a||"fx",[])},promise:function(a,b){var c,d=1,e=r.Deferred(),f=this,g=this.length,h=function(){--d||e.resolveWith(f,[f])};"string"!=typeof a&&(b=a,a=void 0),a=a||"fx";while(g--)c=W.get(f[g],a+"queueHooks"),c&&c.empty&&(d++,c.empty.add(h));return h(),e.promise(b)}});var aa=/[+-]?(?:\d*\.|)\d+(?:[eE][+-]?\d+|)/.source,ba=new RegExp("^(?:([+-])=|)("+aa+")([a-z%]*)$","i"),ca=["Top","Right","Bottom","Left"],da=function(a,b){return a=b||a,"none"===a.style.display||""===a.style.display&&r.contains(a.ownerDocument,a)&&"none"===r.css(a,"display")},ea=function(a,b,c,d){var e,f,g={};for(f in b)g[f]=a.style[f],a.style[f]=b[f];e=c.apply(a,d||[]);for(f in b)a.style[f]=g[f];return e};function fa(a,b,c,d){var e,f=1,g=20,h=d?function(){return d.cur()}:function(){return r.css(a,b,"")},i=h(),j=c&&c[3]||(r.cssNumber[b]?"":"px"),k=(r.cssNumber[b]||"px"!==j&&+i)&&ba.exec(r.css(a,b));if(k&&k[3]!==j){j=j||k[3],c=c||[],k=+i||1;do f=f||".5",k/=f,r.style(a,b,k+j);while(f!==(f=h()/i)&&1!==f&&--g)}return c&&(k=+k||+i||0,e=c[1]?k+(c[1]+1)*c[2]:+c[2],d&&(d.unit=j,d.start=k,d.end=e)),e}var ga={};function ha(a){var b,c=a.ownerDocument,d=a.nodeName,e=ga[d];return e?e:(b=c.body.appendChild(c.createElement(d)),e=r.css(b,"display"),b.parentNode.removeChild(b),"none"===e&&(e="block"),ga[d]=e,e)}function ia(a,b){for(var c,d,e=[],f=0,g=a.length;f<g;f++)d=a[f],d.style&&(c=d.style.display,b?("none"===c&&(e[f]=W.get(d,"display")||null,e[f]||(d.style.display="")),""===d.style.display&&da(d)&&(e[f]=ha(d))):"none"!==c&&(e[f]="none",W.set(d,"display",c)));for(f=0;f<g;f++)null!=e[f]&&(a[f].style.display=e[f]);return a}r.fn.extend({show:function(){return ia(this,!0)},hide:function(){return ia(this)},toggle:function(a){return"boolean"==typeof a?a?this.show():this.hide():this.each(function(){da(this)?r(this).show():r(this).hide()})}});var ja=/^(?:checkbox|radio)$/i,ka=/<([a-z][^\/\0>\x20\t\r\n\f]+)/i,la=/^$|\/(?:java|ecma)script/i,ma={option:[1,"<select multiple='multiple'>","</select>"],thead:[1,"<table>","</table>"],col:[2,"<table><colgroup>","</colgroup></table>"],tr:[2,"<table><tbody>","</tbody></table>"],td:[3,"<table><tbody><tr>","</tr></tbody></table>"],_default:[0,"",""]};ma.optgroup=ma.option,ma.tbody=ma.tfoot=ma.colgroup=ma.caption=ma.thead,ma.th=ma.td;function na(a,b){var c;return c="undefined"!=typeof a.getElementsByTagName?a.getElementsByTagName(b||"*"):"undefined"!=typeof a.querySelectorAll?a.querySelectorAll(b||"*"):[],void 0===b||b&&B(a,b)?r.merge([a],c):c}function oa(a,b){for(var c=0,d=a.length;c<d;c++)W.set(a[c],"globalEval",!b||W.get(b[c],"globalEval"))}var pa=/<|&#?\w+;/;function qa(a,b,c,d,e){for(var f,g,h,i,j,k,l=b.createDocumentFragment(),m=[],n=0,o=a.length;n<o;n++)if(f=a[n],f||0===f)if("object"===r.type(f))r.merge(m,f.nodeType?[f]:f);else if(pa.test(f)){g=g||l.appendChild(b.createElement("div")),h=(ka.exec(f)||["",""])[1].toLowerCase(),i=ma[h]||ma._default,g.innerHTML=i[1]+r.htmlPrefilter(f)+i[2],k=i[0];while(k--)g=g.lastChild;r.merge(m,g.childNodes),g=l.firstChild,g.textContent=""}else m.push(b.createTextNode(f));l.textContent="",n=0;while(f=m[n++])if(d&&r.inArray(f,d)>-1)e&&e.push(f);else if(j=r.contains(f.ownerDocument,f),g=na(l.appendChild(f),"script"),j&&oa(g),c){k=0;while(f=g[k++])la.test(f.type||"")&&c.push(f)}return l}!function(){var a=d.createDocumentFragment(),b=a.appendChild(d.createElement("div")),c=d.createElement("input");c.setAttribute("type","radio"),c.setAttribute("checked","checked"),c.setAttribute("name","t"),b.appendChild(c),o.checkClone=b.cloneNode(!0).cloneNode(!0).lastChild.checked,b.innerHTML="<textarea>x</textarea>",o.noCloneChecked=!!b.cloneNode(!0).lastChild.defaultValue}();var ra=d.documentElement,sa=/^key/,ta=/^(?:mouse|pointer|contextmenu|drag|drop)|click/,ua=/^([^.]*)(?:\.(.+)|)/;function va(){return!0}function wa(){return!1}function xa(){try{return d.activeElement}catch(a){}}function ya(a,b,c,d,e,f){var g,h;if("object"==typeof b){"string"!=typeof c&&(d=d||c,c=void 0);for(h in b)ya(a,h,c,d,b[h],f);return a}if(null==d&&null==e?(e=c,d=c=void 0):null==e&&("string"==typeof c?(e=d,d=void 0):(e=d,d=c,c=void 0)),e===!1)e=wa;else if(!e)return a;return 1===f&&(g=e,e=function(a){return r().off(a),g.apply(this,arguments)},e.guid=g.guid||(g.guid=r.guid++)),a.each(function(){r.event.add(this,b,e,d,c)})}r.event={global:{},add:function(a,b,c,d,e){var f,g,h,i,j,k,l,m,n,o,p,q=W.get(a);if(q){c.handler&&(f=c,c=f.handler,e=f.selector),e&&r.find.matchesSelector(ra,e),c.guid||(c.guid=r.guid++),(i=q.events)||(i=q.events={}),(g=q.handle)||(g=q.handle=function(b){return"undefined"!=typeof r&&r.event.triggered!==b.type?r.event.dispatch.apply(a,arguments):void 0}),b=(b||"").match(L)||[""],j=b.length;while(j--)h=ua.exec(b[j])||[],n=p=h[1],o=(h[2]||"").split(".").sort(),n&&(l=r.event.special[n]||{},n=(e?l.delegateType:l.bindType)||n,l=r.event.special[n]||{},k=r.extend({type:n,origType:p,data:d,handler:c,guid:c.guid,selector:e,needsContext:e&&r.expr.match.needsContext.test(e),namespace:o.join(".")},f),(m=i[n])||(m=i[n]=[],m.delegateCount=0,l.setup&&l.setup.call(a,d,o,g)!==!1||a.addEventListener&&a.addEventListener(n,g)),l.add&&(l.add.call(a,k),k.handler.guid||(k.handler.guid=c.guid)),e?m.splice(m.delegateCount++,0,k):m.push(k),r.event.global[n]=!0)}},remove:function(a,b,c,d,e){var f,g,h,i,j,k,l,m,n,o,p,q=W.hasData(a)&&W.get(a);if(q&&(i=q.events)){b=(b||"").match(L)||[""],j=b.length;while(j--)if(h=ua.exec(b[j])||[],n=p=h[1],o=(h[2]||"").split(".").sort(),n){l=r.event.special[n]||{},n=(d?l.delegateType:l.bindType)||n,m=i[n]||[],h=h[2]&&new RegExp("(^|\\.)"+o.join("\\.(?:.*\\.|)")+"(\\.|$)"),g=f=m.length;while(f--)k=m[f],!e&&p!==k.origType||c&&c.guid!==k.guid||h&&!h.test(k.namespace)||d&&d!==k.selector&&("**"!==d||!k.selector)||(m.splice(f,1),k.selector&&m.delegateCount--,l.remove&&l.remove.call(a,k));g&&!m.length&&(l.teardown&&l.teardown.call(a,o,q.handle)!==!1||r.removeEvent(a,n,q.handle),delete i[n])}else for(n in i)r.event.remove(a,n+b[j],c,d,!0);r.isEmptyObject(i)&&W.remove(a,"handle events")}},dispatch:function(a){var b=r.event.fix(a),c,d,e,f,g,h,i=new Array(arguments.length),j=(W.get(this,"events")||{})[b.type]||[],k=r.event.special[b.type]||{};for(i[0]=b,c=1;c<arguments.length;c++)i[c]=arguments[c];if(b.delegateTarget=this,!k.preDispatch||k.preDispatch.call(this,b)!==!1){h=r.event.handlers.call(this,b,j),c=0;while((f=h[c++])&&!b.isPropagationStopped()){b.currentTarget=f.elem,d=0;while((g=f.handlers[d++])&&!b.isImmediatePropagationStopped())b.rnamespace&&!b.rnamespace.test(g.namespace)||(b.handleObj=g,b.data=g.data,e=((r.event.special[g.origType]||{}).handle||g.handler).apply(f.elem,i),void 0!==e&&(b.result=e)===!1&&(b.preventDefault(),b.stopPropagation()))}return k.postDispatch&&k.postDispatch.call(this,b),b.result}},handlers:function(a,b){var c,d,e,f,g,h=[],i=b.delegateCount,j=a.target;if(i&&j.nodeType&&!("click"===a.type&&a.button>=1))for(;j!==this;j=j.parentNode||this)if(1===j.nodeType&&("click"!==a.type||j.disabled!==!0)){for(f=[],g={},c=0;c<i;c++)d=b[c],e=d.selector+" ",void 0===g[e]&&(g[e]=d.needsContext?r(e,this).index(j)>-1:r.find(e,this,null,[j]).length),g[e]&&f.push(d);f.length&&h.push({elem:j,handlers:f})}return j=this,i<b.length&&h.push({elem:j,handlers:b.slice(i)}),h},addProp:function(a,b){Object.defineProperty(r.Event.prototype,a,{enumerable:!0,configurable:!0,get:r.isFunction(b)?function(){if(this.originalEvent)return b(this.originalEvent)}:function(){if(this.originalEvent)return this.originalEvent[a]},set:function(b){Object.defineProperty(this,a,{enumerable:!0,configurable:!0,writable:!0,value:b})}})},fix:function(a){return a[r.expando]?a:new r.Event(a)},special:{load:{noBubble:!0},focus:{trigger:function(){if(this!==xa()&&this.focus)return this.focus(),!1},delegateType:"focusin"},blur:{trigger:function(){if(this===xa()&&this.blur)return this.blur(),!1},delegateType:"focusout"},click:{trigger:function(){if("checkbox"===this.type&&this.click&&B(this,"input"))return this.click(),!1},_default:function(a){return B(a.target,"a")}},beforeunload:{postDispatch:function(a){void 0!==a.result&&a.originalEvent&&(a.originalEvent.returnValue=a.result)}}}},r.removeEvent=function(a,b,c){a.removeEventListener&&a.removeEventListener(b,c)},r.Event=function(a,b){return this instanceof r.Event?(a&&a.type?(this.originalEvent=a,this.type=a.type,this.isDefaultPrevented=a.defaultPrevented||void 0===a.defaultPrevented&&a.returnValue===!1?va:wa,this.target=a.target&&3===a.target.nodeType?a.target.parentNode:a.target,this.currentTarget=a.currentTarget,this.relatedTarget=a.relatedTarget):this.type=a,b&&r.extend(this,b),this.timeStamp=a&&a.timeStamp||r.now(),void(this[r.expando]=!0)):new r.Event(a,b)},r.Event.prototype={constructor:r.Event,isDefaultPrevented:wa,isPropagationStopped:wa,isImmediatePropagationStopped:wa,isSimulated:!1,preventDefault:function(){var a=this.originalEvent;this.isDefaultPrevented=va,a&&!this.isSimulated&&a.preventDefault()},stopPropagation:function(){var a=this.originalEvent;this.isPropagationStopped=va,a&&!this.isSimulated&&a.stopPropagation()},stopImmediatePropagation:function(){var a=this.originalEvent;this.isImmediatePropagationStopped=va,a&&!this.isSimulated&&a.stopImmediatePropagation(),this.stopPropagation()}},r.each({altKey:!0,bubbles:!0,cancelable:!0,changedTouches:!0,ctrlKey:!0,detail:!0,eventPhase:!0,metaKey:!0,pageX:!0,pageY:!0,shiftKey:!0,view:!0,"char":!0,charCode:!0,key:!0,keyCode:!0,button:!0,buttons:!0,clientX:!0,clientY:!0,offsetX:!0,offsetY:!0,pointerId:!0,pointerType:!0,screenX:!0,screenY:!0,targetTouches:!0,toElement:!0,touches:!0,which:function(a){var b=a.button;return null==a.which&&sa.test(a.type)?null!=a.charCode?a.charCode:a.keyCode:!a.which&&void 0!==b&&ta.test(a.type)?1&b?1:2&b?3:4&b?2:0:a.which}},r.event.addProp),r.each({mouseenter:"mouseover",mouseleave:"mouseout",pointerenter:"pointerover",pointerleave:"pointerout"},function(a,b){r.event.special[a]={delegateType:b,bindType:b,handle:function(a){var c,d=this,e=a.relatedTarget,f=a.handleObj;return e&&(e===d||r.contains(d,e))||(a.type=f.origType,c=f.handler.apply(this,arguments),a.type=b),c}}}),r.fn.extend({on:function(a,b,c,d){return ya(this,a,b,c,d)},one:function(a,b,c,d){return ya(this,a,b,c,d,1)},off:function(a,b,c){var d,e;if(a&&a.preventDefault&&a.handleObj)return d=a.handleObj,r(a.delegateTarget).off(d.namespace?d.origType+"."+d.namespace:d.origType,d.selector,d.handler),this;if("object"==typeof a){for(e in a)this.off(e,b,a[e]);return this}return b!==!1&&"function"!=typeof b||(c=b,b=void 0),c===!1&&(c=wa),this.each(function(){r.event.remove(this,a,c,b)})}});var za=/<(?!area|br|col|embed|hr|img|input|link|meta|param)(([a-z][^\/\0>\x20\t\r\n\f]*)[^>]*)\/>/gi,Aa=/<script|<style|<link/i,Ba=/checked\s*(?:[^=]|=\s*.checked.)/i,Ca=/^true\/(.*)/,Da=/^\s*<!(?:\[CDATA\[|--)|(?:\]\]|--)>\s*$/g;function Ea(a,b){return B(a,"table")&&B(11!==b.nodeType?b:b.firstChild,"tr")?r(">tbody",a)[0]||a:a}function Fa(a){return a.type=(null!==a.getAttribute("type"))+"/"+a.type,a}function Ga(a){var b=Ca.exec(a.type);return b?a.type=b[1]:a.removeAttribute("type"),a}function Ha(a,b){var c,d,e,f,g,h,i,j;if(1===b.nodeType){if(W.hasData(a)&&(f=W.access(a),g=W.set(b,f),j=f.events)){delete g.handle,g.events={};for(e in j)for(c=0,d=j[e].length;c<d;c++)r.event.add(b,e,j[e][c])}X.hasData(a)&&(h=X.access(a),i=r.extend({},h),X.set(b,i))}}function Ia(a,b){var c=b.nodeName.toLowerCase();"input"===c&&ja.test(a.type)?b.checked=a.checked:"input"!==c&&"textarea"!==c||(b.defaultValue=a.defaultValue)}function Ja(a,b,c,d){b=g.apply([],b);var e,f,h,i,j,k,l=0,m=a.length,n=m-1,q=b[0],s=r.isFunction(q);if(s||m>1&&"string"==typeof q&&!o.checkClone&&Ba.test(q))return a.each(function(e){var f=a.eq(e);s&&(b[0]=q.call(this,e,f.html())),Ja(f,b,c,d)});if(m&&(e=qa(b,a[0].ownerDocument,!1,a,d),f=e.firstChild,1===e.childNodes.length&&(e=f),f||d)){for(h=r.map(na(e,"script"),Fa),i=h.length;l<m;l++)j=e,l!==n&&(j=r.clone(j,!0,!0),i&&r.merge(h,na(j,"script"))),c.call(a[l],j,l);if(i)for(k=h[h.length-1].ownerDocument,r.map(h,Ga),l=0;l<i;l++)j=h[l],la.test(j.type||"")&&!W.access(j,"globalEval")&&r.contains(k,j)&&(j.src?r._evalUrl&&r._evalUrl(j.src):p(j.textContent.replace(Da,""),k))}return a}function Ka(a,b,c){for(var d,e=b?r.filter(b,a):a,f=0;null!=(d=e[f]);f++)c||1!==d.nodeType||r.cleanData(na(d)),d.parentNode&&(c&&r.contains(d.ownerDocument,d)&&oa(na(d,"script")),d.parentNode.removeChild(d));return a}r.extend({htmlPrefilter:function(a){return a.replace(za,"<$1></$2>")},clone:function(a,b,c){var d,e,f,g,h=a.cloneNode(!0),i=r.contains(a.ownerDocument,a);if(!(o.noCloneChecked||1!==a.nodeType&&11!==a.nodeType||r.isXMLDoc(a)))for(g=na(h),f=na(a),d=0,e=f.length;d<e;d++)Ia(f[d],g[d]);if(b)if(c)for(f=f||na(a),g=g||na(h),d=0,e=f.length;d<e;d++)Ha(f[d],g[d]);else Ha(a,h);return g=na(h,"script"),g.length>0&&oa(g,!i&&na(a,"script")),h},cleanData:function(a){for(var b,c,d,e=r.event.special,f=0;void 0!==(c=a[f]);f++)if(U(c)){if(b=c[W.expando]){if(b.events)for(d in b.events)e[d]?r.event.remove(c,d):r.removeEvent(c,d,b.handle);c[W.expando]=void 0}c[X.expando]&&(c[X.expando]=void 0)}}}),r.fn.extend({detach:function(a){return Ka(this,a,!0)},remove:function(a){return Ka(this,a)},text:function(a){return T(this,function(a){return void 0===a?r.text(this):this.empty().each(function(){1!==this.nodeType&&11!==this.nodeType&&9!==this.nodeType||(this.textContent=a)})},null,a,arguments.length)},append:function(){return Ja(this,arguments,function(a){if(1===this.nodeType||11===this.nodeType||9===this.nodeType){var b=Ea(this,a);b.appendChild(a)}})},prepend:function(){return Ja(this,arguments,function(a){if(1===this.nodeType||11===this.nodeType||9===this.nodeType){var b=Ea(this,a);b.insertBefore(a,b.firstChild)}})},before:function(){return Ja(this,arguments,function(a){this.parentNode&&this.parentNode.insertBefore(a,this)})},after:function(){return Ja(this,arguments,function(a){this.parentNode&&this.parentNode.insertBefore(a,this.nextSibling)})},empty:function(){for(var a,b=0;null!=(a=this[b]);b++)1===a.nodeType&&(r.cleanData(na(a,!1)),a.textContent="");return this},clone:function(a,b){return a=null!=a&&a,b=null==b?a:b,this.map(function(){return r.clone(this,a,b)})},html:function(a){return T(this,function(a){var b=this[0]||{},c=0,d=this.length;if(void 0===a&&1===b.nodeType)return b.innerHTML;if("string"==typeof a&&!Aa.test(a)&&!ma[(ka.exec(a)||["",""])[1].toLowerCase()]){a=r.htmlPrefilter(a);try{for(;c<d;c++)b=this[c]||{},1===b.nodeType&&(r.cleanData(na(b,!1)),b.innerHTML=a);b=0}catch(e){}}b&&this.empty().append(a)},null,a,arguments.length)},replaceWith:function(){var a=[];return Ja(this,arguments,function(b){var c=this.parentNode;r.inArray(this,a)<0&&(r.cleanData(na(this)),c&&c.replaceChild(b,this))},a)}}),r.each({appendTo:"append",prependTo:"prepend",insertBefore:"before",insertAfter:"after",replaceAll:"replaceWith"},function(a,b){r.fn[a]=function(a){for(var c,d=[],e=r(a),f=e.length-1,g=0;g<=f;g++)c=g===f?this:this.clone(!0),r(e[g])[b](c),h.apply(d,c.get());return this.pushStack(d)}});var La=/^margin/,Ma=new RegExp("^("+aa+")(?!px)[a-z%]+$","i"),Na=function(b){var c=b.ownerDocument.defaultView;return c&&c.opener||(c=a),c.getComputedStyle(b)};!function(){function b(){if(i){i.style.cssText="box-sizing:border-box;position:relative;display:block;margin:auto;border:1px;padding:1px;top:1%;width:50%",i.innerHTML="",ra.appendChild(h);var b=a.getComputedStyle(i);c="1%"!==b.top,g="2px"===b.marginLeft,e="4px"===b.width,i.style.marginRight="50%",f="4px"===b.marginRight,ra.removeChild(h),i=null}}var c,e,f,g,h=d.createElement("div"),i=d.createElement("div");i.style&&(i.style.backgroundClip="content-box",i.cloneNode(!0).style.backgroundClip="",o.clearCloneStyle="content-box"===i.style.backgroundClip,h.style.cssText="border:0;width:8px;height:0;top:0;left:-9999px;padding:0;margin-top:1px;position:absolute",h.appendChild(i),r.extend(o,{pixelPosition:function(){return b(),c},boxSizingReliable:function(){return b(),e},pixelMarginRight:function(){return b(),f},reliableMarginLeft:function(){return b(),g}}))}();function Oa(a,b,c){var d,e,f,g,h=a.style;return c=c||Na(a),c&&(g=c.getPropertyValue(b)||c[b],""!==g||r.contains(a.ownerDocument,a)||(g=r.style(a,b)),!o.pixelMarginRight()&&Ma.test(g)&&La.test(b)&&(d=h.width,e=h.minWidth,f=h.maxWidth,h.minWidth=h.maxWidth=h.width=g,g=c.width,h.width=d,h.minWidth=e,h.maxWidth=f)),void 0!==g?g+"":g}function Pa(a,b){return{get:function(){return a()?void delete this.get:(this.get=b).apply(this,arguments)}}}var Qa=/^(none|table(?!-c[ea]).+)/,Ra=/^--/,Sa={position:"absolute",visibility:"hidden",display:"block"},Ta={letterSpacing:"0",fontWeight:"400"},Ua=["Webkit","Moz","ms"],Va=d.createElement("div").style;function Wa(a){if(a in Va)return a;var b=a[0].toUpperCase()+a.slice(1),c=Ua.length;while(c--)if(a=Ua[c]+b,a in Va)return a}function Xa(a){var b=r.cssProps[a];return b||(b=r.cssProps[a]=Wa(a)||a),b}function Ya(a,b,c){var d=ba.exec(b);return d?Math.max(0,d[2]-(c||0))+(d[3]||"px"):b}function Za(a,b,c,d,e){var f,g=0;for(f=c===(d?"border":"content")?4:"width"===b?1:0;f<4;f+=2)"margin"===c&&(g+=r.css(a,c+ca[f],!0,e)),d?("content"===c&&(g-=r.css(a,"padding"+ca[f],!0,e)),"margin"!==c&&(g-=r.css(a,"border"+ca[f]+"Width",!0,e))):(g+=r.css(a,"padding"+ca[f],!0,e),"padding"!==c&&(g+=r.css(a,"border"+ca[f]+"Width",!0,e)));return g}function $a(a,b,c){var d,e=Na(a),f=Oa(a,b,e),g="border-box"===r.css(a,"boxSizing",!1,e);return Ma.test(f)?f:(d=g&&(o.boxSizingReliable()||f===a.style[b]),"auto"===f&&(f=a["offset"+b[0].toUpperCase()+b.slice(1)]),f=parseFloat(f)||0,f+Za(a,b,c||(g?"border":"content"),d,e)+"px")}r.extend({cssHooks:{opacity:{get:function(a,b){if(b){var c=Oa(a,"opacity");return""===c?"1":c}}}},cssNumber:{animationIterationCount:!0,columnCount:!0,fillOpacity:!0,flexGrow:!0,flexShrink:!0,fontWeight:!0,lineHeight:!0,opacity:!0,order:!0,orphans:!0,widows:!0,zIndex:!0,zoom:!0},cssProps:{"float":"cssFloat"},style:function(a,b,c,d){if(a&&3!==a.nodeType&&8!==a.nodeType&&a.style){var e,f,g,h=r.camelCase(b),i=Ra.test(b),j=a.style;return i||(b=Xa(h)),g=r.cssHooks[b]||r.cssHooks[h],void 0===c?g&&"get"in g&&void 0!==(e=g.get(a,!1,d))?e:j[b]:(f=typeof c,"string"===f&&(e=ba.exec(c))&&e[1]&&(c=fa(a,b,e),f="number"),null!=c&&c===c&&("number"===f&&(c+=e&&e[3]||(r.cssNumber[h]?"":"px")),o.clearCloneStyle||""!==c||0!==b.indexOf("background")||(j[b]="inherit"),g&&"set"in g&&void 0===(c=g.set(a,c,d))||(i?j.setProperty(b,c):j[b]=c)),void 0)}},css:function(a,b,c,d){var e,f,g,h=r.camelCase(b),i=Ra.test(b);return i||(b=Xa(h)),g=r.cssHooks[b]||r.cssHooks[h],g&&"get"in g&&(e=g.get(a,!0,c)),void 0===e&&(e=Oa(a,b,d)),"normal"===e&&b in Ta&&(e=Ta[b]),""===c||c?(f=parseFloat(e),c===!0||isFinite(f)?f||0:e):e}}),r.each(["height","width"],function(a,b){r.cssHooks[b]={get:function(a,c,d){if(c)return!Qa.test(r.css(a,"display"))||a.getClientRects().length&&a.getBoundingClientRect().width?$a(a,b,d):ea(a,Sa,function(){return $a(a,b,d)})},set:function(a,c,d){var e,f=d&&Na(a),g=d&&Za(a,b,d,"border-box"===r.css(a,"boxSizing",!1,f),f);return g&&(e=ba.exec(c))&&"px"!==(e[3]||"px")&&(a.style[b]=c,c=r.css(a,b)),Ya(a,c,g)}}}),r.cssHooks.marginLeft=Pa(o.reliableMarginLeft,function(a,b){if(b)return(parseFloat(Oa(a,"marginLeft"))||a.getBoundingClientRect().left-ea(a,{marginLeft:0},function(){return a.getBoundingClientRect().left}))+"px"}),r.each({margin:"",padding:"",border:"Width"},function(a,b){r.cssHooks[a+b]={expand:function(c){for(var d=0,e={},f="string"==typeof c?c.split(" "):[c];d<4;d++)e[a+ca[d]+b]=f[d]||f[d-2]||f[0];return e}},La.test(a)||(r.cssHooks[a+b].set=Ya)}),r.fn.extend({css:function(a,b){return T(this,function(a,b,c){var d,e,f={},g=0;if(Array.isArray(b)){for(d=Na(a),e=b.length;g<e;g++)f[b[g]]=r.css(a,b[g],!1,d);return f}return void 0!==c?r.style(a,b,c):r.css(a,b)},a,b,arguments.length>1)}});function _a(a,b,c,d,e){return new _a.prototype.init(a,b,c,d,e)}r.Tween=_a,_a.prototype={constructor:_a,init:function(a,b,c,d,e,f){this.elem=a,this.prop=c,this.easing=e||r.easing._default,this.options=b,this.start=this.now=this.cur(),this.end=d,this.unit=f||(r.cssNumber[c]?"":"px")},cur:function(){var a=_a.propHooks[this.prop];return a&&a.get?a.get(this):_a.propHooks._default.get(this)},run:function(a){var b,c=_a.propHooks[this.prop];return this.options.duration?this.pos=b=r.easing[this.easing](a,this.options.duration*a,0,1,this.options.duration):this.pos=b=a,this.now=(this.end-this.start)*b+this.start,this.options.step&&this.options.step.call(this.elem,this.now,this),c&&c.set?c.set(this):_a.propHooks._default.set(this),this}},_a.prototype.init.prototype=_a.prototype,_a.propHooks={_default:{get:function(a){var b;return 1!==a.elem.nodeType||null!=a.elem[a.prop]&&null==a.elem.style[a.prop]?a.elem[a.prop]:(b=r.css(a.elem,a.prop,""),b&&"auto"!==b?b:0)},set:function(a){r.fx.step[a.prop]?r.fx.step[a.prop](a):1!==a.elem.nodeType||null==a.elem.style[r.cssProps[a.prop]]&&!r.cssHooks[a.prop]?a.elem[a.prop]=a.now:r.style(a.elem,a.prop,a.now+a.unit)}}},_a.propHooks.scrollTop=_a.propHooks.scrollLeft={set:function(a){a.elem.nodeType&&a.elem.parentNode&&(a.elem[a.prop]=a.now)}},r.easing={linear:function(a){return a},swing:function(a){return.5-Math.cos(a*Math.PI)/2},_default:"swing"},r.fx=_a.prototype.init,r.fx.step={};var ab,bb,cb=/^(?:toggle|show|hide)$/,db=/queueHooks$/;function eb(){bb&&(d.hidden===!1&&a.requestAnimationFrame?a.requestAnimationFrame(eb):a.setTimeout(eb,r.fx.interval),r.fx.tick())}function fb(){return a.setTimeout(function(){ab=void 0}),ab=r.now()}function gb(a,b){var c,d=0,e={height:a};for(b=b?1:0;d<4;d+=2-b)c=ca[d],e["margin"+c]=e["padding"+c]=a;return b&&(e.opacity=e.width=a),e}function hb(a,b,c){for(var d,e=(kb.tweeners[b]||[]).concat(kb.tweeners["*"]),f=0,g=e.length;f<g;f++)if(d=e[f].call(c,b,a))return d}function ib(a,b,c){var d,e,f,g,h,i,j,k,l="width"in b||"height"in b,m=this,n={},o=a.style,p=a.nodeType&&da(a),q=W.get(a,"fxshow");c.queue||(g=r._queueHooks(a,"fx"),null==g.unqueued&&(g.unqueued=0,h=g.empty.fire,g.empty.fire=function(){g.unqueued||h()}),g.unqueued++,m.always(function(){m.always(function(){g.unqueued--,r.queue(a,"fx").length||g.empty.fire()})}));for(d in b)if(e=b[d],cb.test(e)){if(delete b[d],f=f||"toggle"===e,e===(p?"hide":"show")){if("show"!==e||!q||void 0===q[d])continue;p=!0}n[d]=q&&q[d]||r.style(a,d)}if(i=!r.isEmptyObject(b),i||!r.isEmptyObject(n)){l&&1===a.nodeType&&(c.overflow=[o.overflow,o.overflowX,o.overflowY],j=q&&q.display,null==j&&(j=W.get(a,"display")),k=r.css(a,"display"),"none"===k&&(j?k=j:(ia([a],!0),j=a.style.display||j,k=r.css(a,"display"),ia([a]))),("inline"===k||"inline-block"===k&&null!=j)&&"none"===r.css(a,"float")&&(i||(m.done(function(){o.display=j}),null==j&&(k=o.display,j="none"===k?"":k)),o.display="inline-block")),c.overflow&&(o.overflow="hidden",m.always(function(){o.overflow=c.overflow[0],o.overflowX=c.overflow[1],o.overflowY=c.overflow[2]})),i=!1;for(d in n)i||(q?"hidden"in q&&(p=q.hidden):q=W.access(a,"fxshow",{display:j}),f&&(q.hidden=!p),p&&ia([a],!0),m.done(function(){p||ia([a]),W.remove(a,"fxshow");for(d in n)r.style(a,d,n[d])})),i=hb(p?q[d]:0,d,m),d in q||(q[d]=i.start,p&&(i.end=i.start,i.start=0))}}function jb(a,b){var c,d,e,f,g;for(c in a)if(d=r.camelCase(c),e=b[d],f=a[c],Array.isArray(f)&&(e=f[1],f=a[c]=f[0]),c!==d&&(a[d]=f,delete a[c]),g=r.cssHooks[d],g&&"expand"in g){f=g.expand(f),delete a[d];for(c in f)c in a||(a[c]=f[c],b[c]=e)}else b[d]=e}function kb(a,b,c){var d,e,f=0,g=kb.prefilters.length,h=r.Deferred().always(function(){delete i.elem}),i=function(){if(e)return!1;for(var b=ab||fb(),c=Math.max(0,j.startTime+j.duration-b),d=c/j.duration||0,f=1-d,g=0,i=j.tweens.length;g<i;g++)j.tweens[g].run(f);return h.notifyWith(a,[j,f,c]),f<1&&i?c:(i||h.notifyWith(a,[j,1,0]),h.resolveWith(a,[j]),!1)},j=h.promise({elem:a,props:r.extend({},b),opts:r.extend(!0,{specialEasing:{},easing:r.easing._default},c),originalProperties:b,originalOptions:c,startTime:ab||fb(),duration:c.duration,tweens:[],createTween:function(b,c){var d=r.Tween(a,j.opts,b,c,j.opts.specialEasing[b]||j.opts.easing);return j.tweens.push(d),d},stop:function(b){var c=0,d=b?j.tweens.length:0;if(e)return this;for(e=!0;c<d;c++)j.tweens[c].run(1);return b?(h.notifyWith(a,[j,1,0]),h.resolveWith(a,[j,b])):h.rejectWith(a,[j,b]),this}}),k=j.props;for(jb(k,j.opts.specialEasing);f<g;f++)if(d=kb.prefilters[f].call(j,a,k,j.opts))return r.isFunction(d.stop)&&(r._queueHooks(j.elem,j.opts.queue).stop=r.proxy(d.stop,d)),d;return r.map(k,hb,j),r.isFunction(j.opts.start)&&j.opts.start.call(a,j),j.progress(j.opts.progress).done(j.opts.done,j.opts.complete).fail(j.opts.fail).always(j.opts.always),r.fx.timer(r.extend(i,{elem:a,anim:j,queue:j.opts.queue})),j}r.Animation=r.extend(kb,{tweeners:{"*":[function(a,b){var c=this.createTween(a,b);return fa(c.elem,a,ba.exec(b),c),c}]},tweener:function(a,b){r.isFunction(a)?(b=a,a=["*"]):a=a.match(L);for(var c,d=0,e=a.length;d<e;d++)c=a[d],kb.tweeners[c]=kb.tweeners[c]||[],kb.tweeners[c].unshift(b)},prefilters:[ib],prefilter:function(a,b){b?kb.prefilters.unshift(a):kb.prefilters.push(a)}}),r.speed=function(a,b,c){var d=a&&"object"==typeof a?r.extend({},a):{complete:c||!c&&b||r.isFunction(a)&&a,duration:a,easing:c&&b||b&&!r.isFunction(b)&&b};return r.fx.off?d.duration=0:"number"!=typeof d.duration&&(d.duration in r.fx.speeds?d.duration=r.fx.speeds[d.duration]:d.duration=r.fx.speeds._default),null!=d.queue&&d.queue!==!0||(d.queue="fx"),d.old=d.complete,d.complete=function(){r.isFunction(d.old)&&d.old.call(this),d.queue&&r.dequeue(this,d.queue)},d},r.fn.extend({fadeTo:function(a,b,c,d){return this.filter(da).css("opacity",0).show().end().animate({opacity:b},a,c,d)},animate:function(a,b,c,d){var e=r.isEmptyObject(a),f=r.speed(b,c,d),g=function(){var b=kb(this,r.extend({},a),f);(e||W.get(this,"finish"))&&b.stop(!0)};return g.finish=g,e||f.queue===!1?this.each(g):this.queue(f.queue,g)},stop:function(a,b,c){var d=function(a){var b=a.stop;delete a.stop,b(c)};return"string"!=typeof a&&(c=b,b=a,a=void 0),b&&a!==!1&&this.queue(a||"fx",[]),this.each(function(){var b=!0,e=null!=a&&a+"queueHooks",f=r.timers,g=W.get(this);if(e)g[e]&&g[e].stop&&d(g[e]);else for(e in g)g[e]&&g[e].stop&&db.test(e)&&d(g[e]);for(e=f.length;e--;)f[e].elem!==this||null!=a&&f[e].queue!==a||(f[e].anim.stop(c),b=!1,f.splice(e,1));!b&&c||r.dequeue(this,a)})},finish:function(a){return a!==!1&&(a=a||"fx"),this.each(function(){var b,c=W.get(this),d=c[a+"queue"],e=c[a+"queueHooks"],f=r.timers,g=d?d.length:0;for(c.finish=!0,r.queue(this,a,[]),e&&e.stop&&e.stop.call(this,!0),b=f.length;b--;)f[b].elem===this&&f[b].queue===a&&(f[b].anim.stop(!0),f.splice(b,1));for(b=0;b<g;b++)d[b]&&d[b].finish&&d[b].finish.call(this);delete c.finish})}}),r.each(["toggle","show","hide"],function(a,b){var c=r.fn[b];r.fn[b]=function(a,d,e){return null==a||"boolean"==typeof a?c.apply(this,arguments):this.animate(gb(b,!0),a,d,e)}}),r.each({slideDown:gb("show"),slideUp:gb("hide"),slideToggle:gb("toggle"),fadeIn:{opacity:"show"},fadeOut:{opacity:"hide"},fadeToggle:{opacity:"toggle"}},function(a,b){r.fn[a]=function(a,c,d){return this.animate(b,a,c,d)}}),r.timers=[],r.fx.tick=function(){var a,b=0,c=r.timers;for(ab=r.now();b<c.length;b++)a=c[b],a()||c[b]!==a||c.splice(b--,1);c.length||r.fx.stop(),ab=void 0},r.fx.timer=function(a){r.timers.push(a),r.fx.start()},r.fx.interval=13,r.fx.start=function(){bb||(bb=!0,eb())},r.fx.stop=function(){bb=null},r.fx.speeds={slow:600,fast:200,_default:400},r.fn.delay=function(b,c){return b=r.fx?r.fx.speeds[b]||b:b,c=c||"fx",this.queue(c,function(c,d){var e=a.setTimeout(c,b);d.stop=function(){a.clearTimeout(e)}})},function(){var a=d.createElement("input"),b=d.createElement("select"),c=b.appendChild(d.createElement("option"));a.type="checkbox",o.checkOn=""!==a.value,o.optSelected=c.selected,a=d.createElement("input"),a.value="t",a.type="radio",o.radioValue="t"===a.value}();var lb,mb=r.expr.attrHandle;r.fn.extend({attr:function(a,b){return T(this,r.attr,a,b,arguments.length>1)},removeAttr:function(a){return this.each(function(){r.removeAttr(this,a)})}}),r.extend({attr:function(a,b,c){var d,e,f=a.nodeType;if(3!==f&&8!==f&&2!==f)return"undefined"==typeof a.getAttribute?r.prop(a,b,c):(1===f&&r.isXMLDoc(a)||(e=r.attrHooks[b.toLowerCase()]||(r.expr.match.bool.test(b)?lb:void 0)),void 0!==c?null===c?void r.removeAttr(a,b):e&&"set"in e&&void 0!==(d=e.set(a,c,b))?d:(a.setAttribute(b,c+""),c):e&&"get"in e&&null!==(d=e.get(a,b))?d:(d=r.find.attr(a,b),
+null==d?void 0:d))},attrHooks:{type:{set:function(a,b){if(!o.radioValue&&"radio"===b&&B(a,"input")){var c=a.value;return a.setAttribute("type",b),c&&(a.value=c),b}}}},removeAttr:function(a,b){var c,d=0,e=b&&b.match(L);if(e&&1===a.nodeType)while(c=e[d++])a.removeAttribute(c)}}),lb={set:function(a,b,c){return b===!1?r.removeAttr(a,c):a.setAttribute(c,c),c}},r.each(r.expr.match.bool.source.match(/\w+/g),function(a,b){var c=mb[b]||r.find.attr;mb[b]=function(a,b,d){var e,f,g=b.toLowerCase();return d||(f=mb[g],mb[g]=e,e=null!=c(a,b,d)?g:null,mb[g]=f),e}});var nb=/^(?:input|select|textarea|button)$/i,ob=/^(?:a|area)$/i;r.fn.extend({prop:function(a,b){return T(this,r.prop,a,b,arguments.length>1)},removeProp:function(a){return this.each(function(){delete this[r.propFix[a]||a]})}}),r.extend({prop:function(a,b,c){var d,e,f=a.nodeType;if(3!==f&&8!==f&&2!==f)return 1===f&&r.isXMLDoc(a)||(b=r.propFix[b]||b,e=r.propHooks[b]),void 0!==c?e&&"set"in e&&void 0!==(d=e.set(a,c,b))?d:a[b]=c:e&&"get"in e&&null!==(d=e.get(a,b))?d:a[b]},propHooks:{tabIndex:{get:function(a){var b=r.find.attr(a,"tabindex");return b?parseInt(b,10):nb.test(a.nodeName)||ob.test(a.nodeName)&&a.href?0:-1}}},propFix:{"for":"htmlFor","class":"className"}}),o.optSelected||(r.propHooks.selected={get:function(a){var b=a.parentNode;return b&&b.parentNode&&b.parentNode.selectedIndex,null},set:function(a){var b=a.parentNode;b&&(b.selectedIndex,b.parentNode&&b.parentNode.selectedIndex)}}),r.each(["tabIndex","readOnly","maxLength","cellSpacing","cellPadding","rowSpan","colSpan","useMap","frameBorder","contentEditable"],function(){r.propFix[this.toLowerCase()]=this});function pb(a){var b=a.match(L)||[];return b.join(" ")}function qb(a){return a.getAttribute&&a.getAttribute("class")||""}r.fn.extend({addClass:function(a){var b,c,d,e,f,g,h,i=0;if(r.isFunction(a))return this.each(function(b){r(this).addClass(a.call(this,b,qb(this)))});if("string"==typeof a&&a){b=a.match(L)||[];while(c=this[i++])if(e=qb(c),d=1===c.nodeType&&" "+pb(e)+" "){g=0;while(f=b[g++])d.indexOf(" "+f+" ")<0&&(d+=f+" ");h=pb(d),e!==h&&c.setAttribute("class",h)}}return this},removeClass:function(a){var b,c,d,e,f,g,h,i=0;if(r.isFunction(a))return this.each(function(b){r(this).removeClass(a.call(this,b,qb(this)))});if(!arguments.length)return this.attr("class","");if("string"==typeof a&&a){b=a.match(L)||[];while(c=this[i++])if(e=qb(c),d=1===c.nodeType&&" "+pb(e)+" "){g=0;while(f=b[g++])while(d.indexOf(" "+f+" ")>-1)d=d.replace(" "+f+" "," ");h=pb(d),e!==h&&c.setAttribute("class",h)}}return this},toggleClass:function(a,b){var c=typeof a;return"boolean"==typeof b&&"string"===c?b?this.addClass(a):this.removeClass(a):r.isFunction(a)?this.each(function(c){r(this).toggleClass(a.call(this,c,qb(this),b),b)}):this.each(function(){var b,d,e,f;if("string"===c){d=0,e=r(this),f=a.match(L)||[];while(b=f[d++])e.hasClass(b)?e.removeClass(b):e.addClass(b)}else void 0!==a&&"boolean"!==c||(b=qb(this),b&&W.set(this,"__className__",b),this.setAttribute&&this.setAttribute("class",b||a===!1?"":W.get(this,"__className__")||""))})},hasClass:function(a){var b,c,d=0;b=" "+a+" ";while(c=this[d++])if(1===c.nodeType&&(" "+pb(qb(c))+" ").indexOf(b)>-1)return!0;return!1}});var rb=/\r/g;r.fn.extend({val:function(a){var b,c,d,e=this[0];{if(arguments.length)return d=r.isFunction(a),this.each(function(c){var e;1===this.nodeType&&(e=d?a.call(this,c,r(this).val()):a,null==e?e="":"number"==typeof e?e+="":Array.isArray(e)&&(e=r.map(e,function(a){return null==a?"":a+""})),b=r.valHooks[this.type]||r.valHooks[this.nodeName.toLowerCase()],b&&"set"in b&&void 0!==b.set(this,e,"value")||(this.value=e))});if(e)return b=r.valHooks[e.type]||r.valHooks[e.nodeName.toLowerCase()],b&&"get"in b&&void 0!==(c=b.get(e,"value"))?c:(c=e.value,"string"==typeof c?c.replace(rb,""):null==c?"":c)}}}),r.extend({valHooks:{option:{get:function(a){var b=r.find.attr(a,"value");return null!=b?b:pb(r.text(a))}},select:{get:function(a){var b,c,d,e=a.options,f=a.selectedIndex,g="select-one"===a.type,h=g?null:[],i=g?f+1:e.length;for(d=f<0?i:g?f:0;d<i;d++)if(c=e[d],(c.selected||d===f)&&!c.disabled&&(!c.parentNode.disabled||!B(c.parentNode,"optgroup"))){if(b=r(c).val(),g)return b;h.push(b)}return h},set:function(a,b){var c,d,e=a.options,f=r.makeArray(b),g=e.length;while(g--)d=e[g],(d.selected=r.inArray(r.valHooks.option.get(d),f)>-1)&&(c=!0);return c||(a.selectedIndex=-1),f}}}}),r.each(["radio","checkbox"],function(){r.valHooks[this]={set:function(a,b){if(Array.isArray(b))return a.checked=r.inArray(r(a).val(),b)>-1}},o.checkOn||(r.valHooks[this].get=function(a){return null===a.getAttribute("value")?"on":a.value})});var sb=/^(?:focusinfocus|focusoutblur)$/;r.extend(r.event,{trigger:function(b,c,e,f){var g,h,i,j,k,m,n,o=[e||d],p=l.call(b,"type")?b.type:b,q=l.call(b,"namespace")?b.namespace.split("."):[];if(h=i=e=e||d,3!==e.nodeType&&8!==e.nodeType&&!sb.test(p+r.event.triggered)&&(p.indexOf(".")>-1&&(q=p.split("."),p=q.shift(),q.sort()),k=p.indexOf(":")<0&&"on"+p,b=b[r.expando]?b:new r.Event(p,"object"==typeof b&&b),b.isTrigger=f?2:3,b.namespace=q.join("."),b.rnamespace=b.namespace?new RegExp("(^|\\.)"+q.join("\\.(?:.*\\.|)")+"(\\.|$)"):null,b.result=void 0,b.target||(b.target=e),c=null==c?[b]:r.makeArray(c,[b]),n=r.event.special[p]||{},f||!n.trigger||n.trigger.apply(e,c)!==!1)){if(!f&&!n.noBubble&&!r.isWindow(e)){for(j=n.delegateType||p,sb.test(j+p)||(h=h.parentNode);h;h=h.parentNode)o.push(h),i=h;i===(e.ownerDocument||d)&&o.push(i.defaultView||i.parentWindow||a)}g=0;while((h=o[g++])&&!b.isPropagationStopped())b.type=g>1?j:n.bindType||p,m=(W.get(h,"events")||{})[b.type]&&W.get(h,"handle"),m&&m.apply(h,c),m=k&&h[k],m&&m.apply&&U(h)&&(b.result=m.apply(h,c),b.result===!1&&b.preventDefault());return b.type=p,f||b.isDefaultPrevented()||n._default&&n._default.apply(o.pop(),c)!==!1||!U(e)||k&&r.isFunction(e[p])&&!r.isWindow(e)&&(i=e[k],i&&(e[k]=null),r.event.triggered=p,e[p](),r.event.triggered=void 0,i&&(e[k]=i)),b.result}},simulate:function(a,b,c){var d=r.extend(new r.Event,c,{type:a,isSimulated:!0});r.event.trigger(d,null,b)}}),r.fn.extend({trigger:function(a,b){return this.each(function(){r.event.trigger(a,b,this)})},triggerHandler:function(a,b){var c=this[0];if(c)return r.event.trigger(a,b,c,!0)}}),r.each("blur focus focusin focusout resize scroll click dblclick mousedown mouseup mousemove mouseover mouseout mouseenter mouseleave change select submit keydown keypress keyup contextmenu".split(" "),function(a,b){r.fn[b]=function(a,c){return arguments.length>0?this.on(b,null,a,c):this.trigger(b)}}),r.fn.extend({hover:function(a,b){return this.mouseenter(a).mouseleave(b||a)}}),o.focusin="onfocusin"in a,o.focusin||r.each({focus:"focusin",blur:"focusout"},function(a,b){var c=function(a){r.event.simulate(b,a.target,r.event.fix(a))};r.event.special[b]={setup:function(){var d=this.ownerDocument||this,e=W.access(d,b);e||d.addEventListener(a,c,!0),W.access(d,b,(e||0)+1)},teardown:function(){var d=this.ownerDocument||this,e=W.access(d,b)-1;e?W.access(d,b,e):(d.removeEventListener(a,c,!0),W.remove(d,b))}}});var tb=a.location,ub=r.now(),vb=/\?/;r.parseXML=function(b){var c;if(!b||"string"!=typeof b)return null;try{c=(new a.DOMParser).parseFromString(b,"text/xml")}catch(d){c=void 0}return c&&!c.getElementsByTagName("parsererror").length||r.error("Invalid XML: "+b),c};var wb=/\[\]$/,xb=/\r?\n/g,yb=/^(?:submit|button|image|reset|file)$/i,zb=/^(?:input|select|textarea|keygen)/i;function Ab(a,b,c,d){var e;if(Array.isArray(b))r.each(b,function(b,e){c||wb.test(a)?d(a,e):Ab(a+"["+("object"==typeof e&&null!=e?b:"")+"]",e,c,d)});else if(c||"object"!==r.type(b))d(a,b);else for(e in b)Ab(a+"["+e+"]",b[e],c,d)}r.param=function(a,b){var c,d=[],e=function(a,b){var c=r.isFunction(b)?b():b;d[d.length]=encodeURIComponent(a)+"="+encodeURIComponent(null==c?"":c)};if(Array.isArray(a)||a.jquery&&!r.isPlainObject(a))r.each(a,function(){e(this.name,this.value)});else for(c in a)Ab(c,a[c],b,e);return d.join("&")},r.fn.extend({serialize:function(){return r.param(this.serializeArray())},serializeArray:function(){return this.map(function(){var a=r.prop(this,"elements");return a?r.makeArray(a):this}).filter(function(){var a=this.type;return this.name&&!r(this).is(":disabled")&&zb.test(this.nodeName)&&!yb.test(a)&&(this.checked||!ja.test(a))}).map(function(a,b){var c=r(this).val();return null==c?null:Array.isArray(c)?r.map(c,function(a){return{name:b.name,value:a.replace(xb,"\r\n")}}):{name:b.name,value:c.replace(xb,"\r\n")}}).get()}});var Bb=/%20/g,Cb=/#.*$/,Db=/([?&])_=[^&]*/,Eb=/^(.*?):[ \t]*([^\r\n]*)$/gm,Fb=/^(?:about|app|app-storage|.+-extension|file|res|widget):$/,Gb=/^(?:GET|HEAD)$/,Hb=/^\/\//,Ib={},Jb={},Kb="*/".concat("*"),Lb=d.createElement("a");Lb.href=tb.href;function Mb(a){return function(b,c){"string"!=typeof b&&(c=b,b="*");var d,e=0,f=b.toLowerCase().match(L)||[];if(r.isFunction(c))while(d=f[e++])"+"===d[0]?(d=d.slice(1)||"*",(a[d]=a[d]||[]).unshift(c)):(a[d]=a[d]||[]).push(c)}}function Nb(a,b,c,d){var e={},f=a===Jb;function g(h){var i;return e[h]=!0,r.each(a[h]||[],function(a,h){var j=h(b,c,d);return"string"!=typeof j||f||e[j]?f?!(i=j):void 0:(b.dataTypes.unshift(j),g(j),!1)}),i}return g(b.dataTypes[0])||!e["*"]&&g("*")}function Ob(a,b){var c,d,e=r.ajaxSettings.flatOptions||{};for(c in b)void 0!==b[c]&&((e[c]?a:d||(d={}))[c]=b[c]);return d&&r.extend(!0,a,d),a}function Pb(a,b,c){var d,e,f,g,h=a.contents,i=a.dataTypes;while("*"===i[0])i.shift(),void 0===d&&(d=a.mimeType||b.getResponseHeader("Content-Type"));if(d)for(e in h)if(h[e]&&h[e].test(d)){i.unshift(e);break}if(i[0]in c)f=i[0];else{for(e in c){if(!i[0]||a.converters[e+" "+i[0]]){f=e;break}g||(g=e)}f=f||g}if(f)return f!==i[0]&&i.unshift(f),c[f]}function Qb(a,b,c,d){var e,f,g,h,i,j={},k=a.dataTypes.slice();if(k[1])for(g in a.converters)j[g.toLowerCase()]=a.converters[g];f=k.shift();while(f)if(a.responseFields[f]&&(c[a.responseFields[f]]=b),!i&&d&&a.dataFilter&&(b=a.dataFilter(b,a.dataType)),i=f,f=k.shift())if("*"===f)f=i;else if("*"!==i&&i!==f){if(g=j[i+" "+f]||j["* "+f],!g)for(e in j)if(h=e.split(" "),h[1]===f&&(g=j[i+" "+h[0]]||j["* "+h[0]])){g===!0?g=j[e]:j[e]!==!0&&(f=h[0],k.unshift(h[1]));break}if(g!==!0)if(g&&a["throws"])b=g(b);else try{b=g(b)}catch(l){return{state:"parsererror",error:g?l:"No conversion from "+i+" to "+f}}}return{state:"success",data:b}}r.extend({active:0,lastModified:{},etag:{},ajaxSettings:{url:tb.href,type:"GET",isLocal:Fb.test(tb.protocol),global:!0,processData:!0,async:!0,contentType:"application/x-www-form-urlencoded; charset=UTF-8",accepts:{"*":Kb,text:"text/plain",html:"text/html",xml:"application/xml, text/xml",json:"application/json, text/javascript"},contents:{xml:/\bxml\b/,html:/\bhtml/,json:/\bjson\b/},responseFields:{xml:"responseXML",text:"responseText",json:"responseJSON"},converters:{"* text":String,"text html":!0,"text json":JSON.parse,"text xml":r.parseXML},flatOptions:{url:!0,context:!0}},ajaxSetup:function(a,b){return b?Ob(Ob(a,r.ajaxSettings),b):Ob(r.ajaxSettings,a)},ajaxPrefilter:Mb(Ib),ajaxTransport:Mb(Jb),ajax:function(b,c){"object"==typeof b&&(c=b,b=void 0),c=c||{};var e,f,g,h,i,j,k,l,m,n,o=r.ajaxSetup({},c),p=o.context||o,q=o.context&&(p.nodeType||p.jquery)?r(p):r.event,s=r.Deferred(),t=r.Callbacks("once memory"),u=o.statusCode||{},v={},w={},x="canceled",y={readyState:0,getResponseHeader:function(a){var b;if(k){if(!h){h={};while(b=Eb.exec(g))h[b[1].toLowerCase()]=b[2]}b=h[a.toLowerCase()]}return null==b?null:b},getAllResponseHeaders:function(){return k?g:null},setRequestHeader:function(a,b){return null==k&&(a=w[a.toLowerCase()]=w[a.toLowerCase()]||a,v[a]=b),this},overrideMimeType:function(a){return null==k&&(o.mimeType=a),this},statusCode:function(a){var b;if(a)if(k)y.always(a[y.status]);else for(b in a)u[b]=[u[b],a[b]];return this},abort:function(a){var b=a||x;return e&&e.abort(b),A(0,b),this}};if(s.promise(y),o.url=((b||o.url||tb.href)+"").replace(Hb,tb.protocol+"//"),o.type=c.method||c.type||o.method||o.type,o.dataTypes=(o.dataType||"*").toLowerCase().match(L)||[""],null==o.crossDomain){j=d.createElement("a");try{j.href=o.url,j.href=j.href,o.crossDomain=Lb.protocol+"//"+Lb.host!=j.protocol+"//"+j.host}catch(z){o.crossDomain=!0}}if(o.data&&o.processData&&"string"!=typeof o.data&&(o.data=r.param(o.data,o.traditional)),Nb(Ib,o,c,y),k)return y;l=r.event&&o.global,l&&0===r.active++&&r.event.trigger("ajaxStart"),o.type=o.type.toUpperCase(),o.hasContent=!Gb.test(o.type),f=o.url.replace(Cb,""),o.hasContent?o.data&&o.processData&&0===(o.contentType||"").indexOf("application/x-www-form-urlencoded")&&(o.data=o.data.replace(Bb,"+")):(n=o.url.slice(f.length),o.data&&(f+=(vb.test(f)?"&":"?")+o.data,delete o.data),o.cache===!1&&(f=f.replace(Db,"$1"),n=(vb.test(f)?"&":"?")+"_="+ub++ +n),o.url=f+n),o.ifModified&&(r.lastModified[f]&&y.setRequestHeader("If-Modified-Since",r.lastModified[f]),r.etag[f]&&y.setRequestHeader("If-None-Match",r.etag[f])),(o.data&&o.hasContent&&o.contentType!==!1||c.contentType)&&y.setRequestHeader("Content-Type",o.contentType),y.setRequestHeader("Accept",o.dataTypes[0]&&o.accepts[o.dataTypes[0]]?o.accepts[o.dataTypes[0]]+("*"!==o.dataTypes[0]?", "+Kb+"; q=0.01":""):o.accepts["*"]);for(m in o.headers)y.setRequestHeader(m,o.headers[m]);if(o.beforeSend&&(o.beforeSend.call(p,y,o)===!1||k))return y.abort();if(x="abort",t.add(o.complete),y.done(o.success),y.fail(o.error),e=Nb(Jb,o,c,y)){if(y.readyState=1,l&&q.trigger("ajaxSend",[y,o]),k)return y;o.async&&o.timeout>0&&(i=a.setTimeout(function(){y.abort("timeout")},o.timeout));try{k=!1,e.send(v,A)}catch(z){if(k)throw z;A(-1,z)}}else A(-1,"No Transport");function A(b,c,d,h){var j,m,n,v,w,x=c;k||(k=!0,i&&a.clearTimeout(i),e=void 0,g=h||"",y.readyState=b>0?4:0,j=b>=200&&b<300||304===b,d&&(v=Pb(o,y,d)),v=Qb(o,v,y,j),j?(o.ifModified&&(w=y.getResponseHeader("Last-Modified"),w&&(r.lastModified[f]=w),w=y.getResponseHeader("etag"),w&&(r.etag[f]=w)),204===b||"HEAD"===o.type?x="nocontent":304===b?x="notmodified":(x=v.state,m=v.data,n=v.error,j=!n)):(n=x,!b&&x||(x="error",b<0&&(b=0))),y.status=b,y.statusText=(c||x)+"",j?s.resolveWith(p,[m,x,y]):s.rejectWith(p,[y,x,n]),y.statusCode(u),u=void 0,l&&q.trigger(j?"ajaxSuccess":"ajaxError",[y,o,j?m:n]),t.fireWith(p,[y,x]),l&&(q.trigger("ajaxComplete",[y,o]),--r.active||r.event.trigger("ajaxStop")))}return y},getJSON:function(a,b,c){return r.get(a,b,c,"json")},getScript:function(a,b){return r.get(a,void 0,b,"script")}}),r.each(["get","post"],function(a,b){r[b]=function(a,c,d,e){return r.isFunction(c)&&(e=e||d,d=c,c=void 0),r.ajax(r.extend({url:a,type:b,dataType:e,data:c,success:d},r.isPlainObject(a)&&a))}}),r._evalUrl=function(a){return r.ajax({url:a,type:"GET",dataType:"script",cache:!0,async:!1,global:!1,"throws":!0})},r.fn.extend({wrapAll:function(a){var b;return this[0]&&(r.isFunction(a)&&(a=a.call(this[0])),b=r(a,this[0].ownerDocument).eq(0).clone(!0),this[0].parentNode&&b.insertBefore(this[0]),b.map(function(){var a=this;while(a.firstElementChild)a=a.firstElementChild;return a}).append(this)),this},wrapInner:function(a){return r.isFunction(a)?this.each(function(b){r(this).wrapInner(a.call(this,b))}):this.each(function(){var b=r(this),c=b.contents();c.length?c.wrapAll(a):b.append(a)})},wrap:function(a){var b=r.isFunction(a);return this.each(function(c){r(this).wrapAll(b?a.call(this,c):a)})},unwrap:function(a){return this.parent(a).not("body").each(function(){r(this).replaceWith(this.childNodes)}),this}}),r.expr.pseudos.hidden=function(a){return!r.expr.pseudos.visible(a)},r.expr.pseudos.visible=function(a){return!!(a.offsetWidth||a.offsetHeight||a.getClientRects().length)},r.ajaxSettings.xhr=function(){try{return new a.XMLHttpRequest}catch(b){}};var Rb={0:200,1223:204},Sb=r.ajaxSettings.xhr();o.cors=!!Sb&&"withCredentials"in Sb,o.ajax=Sb=!!Sb,r.ajaxTransport(function(b){var c,d;if(o.cors||Sb&&!b.crossDomain)return{send:function(e,f){var g,h=b.xhr();if(h.open(b.type,b.url,b.async,b.username,b.password),b.xhrFields)for(g in b.xhrFields)h[g]=b.xhrFields[g];b.mimeType&&h.overrideMimeType&&h.overrideMimeType(b.mimeType),b.crossDomain||e["X-Requested-With"]||(e["X-Requested-With"]="XMLHttpRequest");for(g in e)h.setRequestHeader(g,e[g]);c=function(a){return function(){c&&(c=d=h.onload=h.onerror=h.onabort=h.onreadystatechange=null,"abort"===a?h.abort():"error"===a?"number"!=typeof h.status?f(0,"error"):f(h.status,h.statusText):f(Rb[h.status]||h.status,h.statusText,"text"!==(h.responseType||"text")||"string"!=typeof h.responseText?{binary:h.response}:{text:h.responseText},h.getAllResponseHeaders()))}},h.onload=c(),d=h.onerror=c("error"),void 0!==h.onabort?h.onabort=d:h.onreadystatechange=function(){4===h.readyState&&a.setTimeout(function(){c&&d()})},c=c("abort");try{h.send(b.hasContent&&b.data||null)}catch(i){if(c)throw i}},abort:function(){c&&c()}}}),r.ajaxPrefilter(function(a){a.crossDomain&&(a.contents.script=!1)}),r.ajaxSetup({accepts:{script:"text/javascript, application/javascript, application/ecmascript, application/x-ecmascript"},contents:{script:/\b(?:java|ecma)script\b/},converters:{"text script":function(a){return r.globalEval(a),a}}}),r.ajaxPrefilter("script",function(a){void 0===a.cache&&(a.cache=!1),a.crossDomain&&(a.type="GET")}),r.ajaxTransport("script",function(a){if(a.crossDomain){var b,c;return{send:function(e,f){b=r("<script>").prop({charset:a.scriptCharset,src:a.url}).on("load error",c=function(a){b.remove(),c=null,a&&f("error"===a.type?404:200,a.type)}),d.head.appendChild(b[0])},abort:function(){c&&c()}}}});var Tb=[],Ub=/(=)\?(?=&|$)|\?\?/;r.ajaxSetup({jsonp:"callback",jsonpCallback:function(){var a=Tb.pop()||r.expando+"_"+ub++;return this[a]=!0,a}}),r.ajaxPrefilter("json jsonp",function(b,c,d){var e,f,g,h=b.jsonp!==!1&&(Ub.test(b.url)?"url":"string"==typeof b.data&&0===(b.contentType||"").indexOf("application/x-www-form-urlencoded")&&Ub.test(b.data)&&"data");if(h||"jsonp"===b.dataTypes[0])return e=b.jsonpCallback=r.isFunction(b.jsonpCallback)?b.jsonpCallback():b.jsonpCallback,h?b[h]=b[h].replace(Ub,"$1"+e):b.jsonp!==!1&&(b.url+=(vb.test(b.url)?"&":"?")+b.jsonp+"="+e),b.converters["script json"]=function(){return g||r.error(e+" was not called"),g[0]},b.dataTypes[0]="json",f=a[e],a[e]=function(){g=arguments},d.always(function(){void 0===f?r(a).removeProp(e):a[e]=f,b[e]&&(b.jsonpCallback=c.jsonpCallback,Tb.push(e)),g&&r.isFunction(f)&&f(g[0]),g=f=void 0}),"script"}),o.createHTMLDocument=function(){var a=d.implementation.createHTMLDocument("").body;return a.innerHTML="<form></form><form></form>",2===a.childNodes.length}(),r.parseHTML=function(a,b,c){if("string"!=typeof a)return[];"boolean"==typeof b&&(c=b,b=!1);var e,f,g;return b||(o.createHTMLDocument?(b=d.implementation.createHTMLDocument(""),e=b.createElement("base"),e.href=d.location.href,b.head.appendChild(e)):b=d),f=C.exec(a),g=!c&&[],f?[b.createElement(f[1])]:(f=qa([a],b,g),g&&g.length&&r(g).remove(),r.merge([],f.childNodes))},r.fn.load=function(a,b,c){var d,e,f,g=this,h=a.indexOf(" ");return h>-1&&(d=pb(a.slice(h)),a=a.slice(0,h)),r.isFunction(b)?(c=b,b=void 0):b&&"object"==typeof b&&(e="POST"),g.length>0&&r.ajax({url:a,type:e||"GET",dataType:"html",data:b}).done(function(a){f=arguments,g.html(d?r("<div>").append(r.parseHTML(a)).find(d):a)}).always(c&&function(a,b){g.each(function(){c.apply(this,f||[a.responseText,b,a])})}),this},r.each(["ajaxStart","ajaxStop","ajaxComplete","ajaxError","ajaxSuccess","ajaxSend"],function(a,b){r.fn[b]=function(a){return this.on(b,a)}}),r.expr.pseudos.animated=function(a){return r.grep(r.timers,function(b){return a===b.elem}).length},r.offset={setOffset:function(a,b,c){var d,e,f,g,h,i,j,k=r.css(a,"position"),l=r(a),m={};"static"===k&&(a.style.position="relative"),h=l.offset(),f=r.css(a,"top"),i=r.css(a,"left"),j=("absolute"===k||"fixed"===k)&&(f+i).indexOf("auto")>-1,j?(d=l.position(),g=d.top,e=d.left):(g=parseFloat(f)||0,e=parseFloat(i)||0),r.isFunction(b)&&(b=b.call(a,c,r.extend({},h))),null!=b.top&&(m.top=b.top-h.top+g),null!=b.left&&(m.left=b.left-h.left+e),"using"in b?b.using.call(a,m):l.css(m)}},r.fn.extend({offset:function(a){if(arguments.length)return void 0===a?this:this.each(function(b){r.offset.setOffset(this,a,b)});var b,c,d,e,f=this[0];if(f)return f.getClientRects().length?(d=f.getBoundingClientRect(),b=f.ownerDocument,c=b.documentElement,e=b.defaultView,{top:d.top+e.pageYOffset-c.clientTop,left:d.left+e.pageXOffset-c.clientLeft}):{top:0,left:0}},position:function(){if(this[0]){var a,b,c=this[0],d={top:0,left:0};return"fixed"===r.css(c,"position")?b=c.getBoundingClientRect():(a=this.offsetParent(),b=this.offset(),B(a[0],"html")||(d=a.offset()),d={top:d.top+r.css(a[0],"borderTopWidth",!0),left:d.left+r.css(a[0],"borderLeftWidth",!0)}),{top:b.top-d.top-r.css(c,"marginTop",!0),left:b.left-d.left-r.css(c,"marginLeft",!0)}}},offsetParent:function(){return this.map(function(){var a=this.offsetParent;while(a&&"static"===r.css(a,"position"))a=a.offsetParent;return a||ra})}}),r.each({scrollLeft:"pageXOffset",scrollTop:"pageYOffset"},function(a,b){var c="pageYOffset"===b;r.fn[a]=function(d){return T(this,function(a,d,e){var f;return r.isWindow(a)?f=a:9===a.nodeType&&(f=a.defaultView),void 0===e?f?f[b]:a[d]:void(f?f.scrollTo(c?f.pageXOffset:e,c?e:f.pageYOffset):a[d]=e)},a,d,arguments.length)}}),r.each(["top","left"],function(a,b){r.cssHooks[b]=Pa(o.pixelPosition,function(a,c){if(c)return c=Oa(a,b),Ma.test(c)?r(a).position()[b]+"px":c})}),r.each({Height:"height",Width:"width"},function(a,b){r.each({padding:"inner"+a,content:b,"":"outer"+a},function(c,d){r.fn[d]=function(e,f){var g=arguments.length&&(c||"boolean"!=typeof e),h=c||(e===!0||f===!0?"margin":"border");return T(this,function(b,c,e){var f;return r.isWindow(b)?0===d.indexOf("outer")?b["inner"+a]:b.document.documentElement["client"+a]:9===b.nodeType?(f=b.documentElement,Math.max(b.body["scroll"+a],f["scroll"+a],b.body["offset"+a],f["offset"+a],f["client"+a])):void 0===e?r.css(b,c,h):r.style(b,c,e,h)},b,g?e:void 0,g)}})}),r.fn.extend({bind:function(a,b,c){return this.on(a,null,b,c)},unbind:function(a,b){return this.off(a,null,b)},delegate:function(a,b,c,d){return this.on(b,a,c,d)},undelegate:function(a,b,c){return 1===arguments.length?this.off(a,"**"):this.off(b,a||"**",c)}}),r.holdReady=function(a){a?r.readyWait++:r.ready(!0)},r.isArray=Array.isArray,r.parseJSON=JSON.parse,r.nodeName=B,"function"==typeof define&&define.amd&&define("jquery",[],function(){return r});var Vb=a.jQuery,Wb=a.$;return r.noConflict=function(b){return a.$===r&&(a.$=Wb),b&&a.jQuery===r&&(a.jQuery=Vb),r},b||(a.jQuery=a.$=r),r});
diff --git a/view/js/jquery.spin.js b/view/js/jquery.spin.js
deleted file mode 100644
index 6b4fd656f..000000000
--- a/view/js/jquery.spin.js
+++ /dev/null
@@ -1,79 +0,0 @@
-/**
- * Copyright (c) 2011-2014 Felix Gnass
- * Licensed under the MIT license
- * http://spin.js.org/
- */
-
-/*
-
-Basic Usage:
-============
-
-$('#el').spin() // Creates a default Spinner using the text color of #el.
-$('#el').spin({ ... }) // Creates a Spinner using the provided options.
-
-$('#el').spin(false) // Stops and removes the spinner.
-
-Using Presets:
-==============
-
-$('#el').spin('small') // Creates a 'small' Spinner using the text color of #el.
-$('#el').spin('large', '#fff') // Creates a 'large' white Spinner.
-
-Adding a custom preset:
-=======================
-
-$.fn.spin.presets.flower = {
- lines: 9
-, length: 10
-, width: 20
-, radius: 0
-}
-
-$('#el').spin('flower', 'red')
-
-*/
-
-;(function(factory) {
-
- if (typeof exports == 'object') {
- // CommonJS
- factory(require('jquery'), require('spin.js'))
- } else if (typeof define == 'function' && define.amd) {
- // AMD, register as anonymous module
- define(['jquery', 'spin'], factory)
- } else {
- // Browser globals
- if (!window.Spinner) throw new Error('Spin.js not present')
- factory(window.jQuery, window.Spinner)
- }
-
-}(function($, Spinner) {
-
- $.fn.spin = function(opts, color) {
-
- return this.each(function() {
- var $this = $(this)
- , data = $this.data()
-
- if (data.spinner) {
- data.spinner.stop()
- delete data.spinner
- }
- if (opts !== false) {
- opts = $.extend(
- { color: color || $this.css('color') }
- , $.fn.spin.presets[opts] || opts
- )
- data.spinner = new Spinner(opts).spin(this)
- }
- })
- }
-
- $.fn.spin.presets = {
- tiny: { lines: 8, length: 2, width: 2, radius: 3, position: 'relative' }
- , small: { lines: 8, length: 4, width: 3, radius: 5, position: 'relative' }
- , large: { lines: 10, length: 8, width: 4, radius: 8, position: 'relative' }
- }
-
-}));
diff --git a/view/js/main.js b/view/js/main.js
index 5de4aa9a2..882f50e8a 100644
--- a/view/js/main.js
+++ b/view/js/main.js
@@ -1,6 +1,55 @@
function confirmDelete() { return confirm(aStr.delitem); }
+function handle_comment_form(e) {
+ e.stopPropagation();
+
+ //handle eventual expanded forms
+ var expanded = $('.comment-edit-text.expanded');
+ var i = 0;
+
+ if(expanded.length) {
+ expanded.each(function() {
+ var ex_form = $(expanded[i].form);
+ var ex_fields = ex_form.find(':input[type=text], textarea');
+ var ex_fields_empty = true;
+
+ ex_fields.each(function() {
+ if($(this).val() != '')
+ ex_fields_empty = false;
+ });
+ if(ex_fields_empty) {
+ ex_form.find('.comment-edit-text').removeClass('expanded').attr('placeholder', aStr.comment);
+ ex_form.find(':not(.comment-edit-text)').hide();
+ }
+ i++
+ });
+ }
+
+ // handle clicked form
+ var form = $(this);
+ var fields = form.find(':input[type=text], textarea');
+ var fields_empty = true;
+
+ if(form.find('.comment-edit-text').length) {
+ form.find('.comment-edit-text').addClass('expanded').removeAttr('placeholder');
+ form.find(':not(:visible)').show();
+ }
+
+ // handle click outside of form (close empty forms)
+ $(document).on('click', function(e) {
+ fields.each(function() {
+ if($(this).val() != '')
+ fields_empty = false;
+ });
+ if(fields_empty) {
+ form.find('.comment-edit-text').removeClass('expanded').attr('placeholder', aStr.comment);
+ form.find(':not(.comment-edit-text)').hide();
+ }
+ });
+}
+
+/*
function commentOpenUI(obj, id) {
$(document).unbind( "click.commentOpen", handler );
@@ -13,6 +62,7 @@ function commentOpenUI(obj, id) {
$("#comment-edit-text-" + id).attr('tabindex','9');
$("#comment-edit-submit-" + id).attr('tabindex','10');
$("#comment-tools-" + id).show();
+ $("#comment-edit-anon-" + id).show();
}
};
@@ -20,15 +70,20 @@ function commentOpenUI(obj, id) {
}
function commentCloseUI(obj, id) {
- $(document).unbind( "click.commentClose", handler );
+ var form_id = $(obj)[0].form.id;
+
+ $('#' + form_id).on('click', function(e) {
+ $(document).unbind( "click.commentClose", handler );
+ });
var handler = function() {
- if(obj.value === '') {
- obj.value = aStr.comment;
+ if($('#comment-edit-text-' + id).val() === '') {
+ $('#comment-edit-text-' + id).val(aStr.comment);
$("#comment-edit-text-" + id).removeClass("comment-edit-text-full").addClass("comment-edit-text-empty");
$("#comment-edit-text-" + id).removeAttr('tabindex');
$("#comment-edit-submit-" + id).removeAttr('tabindex');
$("#comment-tools-" + id).hide();
+ $("#comment-edit-anon-" + id).hide();
}
};
@@ -38,27 +93,28 @@ function commentCloseUI(obj, id) {
function commentOpen(obj, id) {
if(obj.value == aStr.comment) {
obj.value = '';
- $("#comment-edit-text-" + id).addClass("comment-edit-text-full");
- $("#comment-edit-text-" + id).removeClass("comment-edit-text-empty");
+ $("#comment-edit-text-" + id).addClass("expanded");
$("#mod-cmnt-wrap-" + id).show();
- openMenu("comment-tools-" + id);
+ $("#comment-tools-" + id).show();
+ $("#comment-edit-anon-" + id).show();
return true;
}
return false;
}
-
+*/
function commentClose(obj, id) {
if(obj.value === '') {
obj.value = aStr.comment;
- $("#comment-edit-text-" + id).removeClass("comment-edit-text-full");
- $("#comment-edit-text-" + id).addClass("comment-edit-text-empty");
+ $("#comment-edit-text-" + id).removeClass("expanded");
$("#mod-cmnt-wrap-" + id).hide();
- closeMenu("comment-tools-" + id);
+ $("#comment-tools-" + id).hide();
+ $("#comment-edit-anon-" + id).hide();
return true;
}
return false;
}
+
function showHideCommentBox(id) {
if( $('#comment-edit-form-' + id).is(':visible')) {
$('#comment-edit-form-' + id).hide();
@@ -71,8 +127,7 @@ function commentInsert(obj, id) {
var tmpStr = $("#comment-edit-text-" + id).val();
if(tmpStr == '$comment') {
tmpStr = '';
- $("#comment-edit-text-" + id).addClass("comment-edit-text-full");
- $("#comment-edit-text-" + id).removeClass("comment-edit-text-empty");
+ $("#comment-edit-text-" + id).addClass("expanded");
openMenu("comment-tools-" + id);
}
var ins = $(obj).html();
@@ -93,8 +148,7 @@ function insertbbcomment(comment, BBcode, id) {
var tmpStr = $("#comment-edit-text-" + id).val();
if(tmpStr == comment) {
tmpStr = "";
- $("#comment-edit-text-" + id).addClass("comment-edit-text-full");
- $("#comment-edit-text-" + id).removeClass("comment-edit-text-empty");
+ $("#comment-edit-text-" + id).addClass("expanded");
openMenu("comment-tools-" + id);
$("#comment-edit-text-" + id).val(tmpStr);
}
@@ -130,6 +184,19 @@ function inserteditortag(BBcode, id) {
return true;
}
+function insertCommentAttach(comment,id) {
+
+ activeCommentID = id;
+ activeCommentText = comment;
+
+ $('body').css('cursor', 'wait');
+
+ $('#invisible-comment-upload').trigger('click');
+
+ return false;
+
+}
+
function insertCommentURL(comment, id) {
reply = prompt(aStr.linkurl);
if(reply && reply.length) {
@@ -139,14 +206,14 @@ function insertCommentURL(comment, id) {
var tmpStr = $("#comment-edit-text-" + id).val();
if(tmpStr == comment) {
tmpStr = "";
- $("#comment-edit-text-" + id).addClass("comment-edit-text-full");
- $("#comment-edit-text-" + id).removeClass("comment-edit-text-empty");
+ $("#comment-edit-text-" + id).addClass("expanded");
openMenu("comment-tools-" + id);
$("#comment-edit-text-" + id).val(tmpStr);
}
textarea = document.getElementById("comment-edit-text-" +id);
textarea.value = textarea.value + data;
+ preview_comment(id);
$('body').css('cursor', 'auto');
});
}
@@ -161,8 +228,7 @@ function qCommentInsert(obj, id) {
var tmpStr = $("#comment-edit-text-" + id).val();
if(tmpStr == aStr.comment) {
tmpStr = '';
- $("#comment-edit-text-" + id).addClass("comment-edit-text-full");
- $("#comment-edit-text-" + id).removeClass("comment-edit-text-empty");
+ $("#comment-edit-text-" + id).addClass("expanded");
openMenu("comment-edit-submit-wrapper-" + id);
}
var ins = $(obj).val();
@@ -196,6 +262,14 @@ function openClose(theID) {
}
}
+function openCloseTR(theID) {
+ if(document.getElementById(theID).style.display == "table-row") {
+ document.getElementById(theID).style.display = "none";
+ } else {
+ document.getElementById(theID).style.display = "table-row";
+ }
+}
+
function closeOpen(theID) {
if(document.getElementById(theID).style.display == "none") {
document.getElementById(theID).style.display = "block";
@@ -215,7 +289,7 @@ function closeMenu(theID) {
function markRead(notifType) {
$.get('ping?f=&markRead='+notifType);
if(timer) clearTimeout(timer);
- $('#' + notifType + '-update').html('');
+ $('.' + notifType + '-button').hide();
timer = setTimeout(NavUpdate,2000);
}
@@ -250,6 +324,7 @@ var last_filestorage_id = null;
var mediaPlaying = false;
var contentHeightDiff = 0;
var liveRecurse = 0;
+var savedTitle = '';
$(function() {
$.ajaxSetup({cache: false});
@@ -290,11 +365,6 @@ $(function() {
return;
});
- $('span[rel^="#"]').click(function(e){
- manage_popup_menu(this, e);
- return;
- });
-
function manage_popup_menu(w,e) {
menu = $( $(w).attr('rel') );
@@ -339,12 +409,13 @@ $(function() {
function NavUpdate() {
if(liking)
- $('.like-rotator').spin(false);
+ $('.like-rotator').hide();
if((! stopped) && (! mediaPlaying)) {
var pingCmd = 'ping' + ((localUser != 0) ? '?f=&uid=' + localUser : '');
$.get(pingCmd,function(data) {
+
if(data.invalid == 1) {
window.location.href=window.location.href;
}
@@ -357,8 +428,9 @@ function NavUpdate() {
if($('#live-pubstream').length) { src = 'pubstream'; liveUpdate(); }
if($('#live-display').length) { src = 'display'; liveUpdate(); }
if($('#live-search').length) { src = 'search'; liveUpdate(); }
+ // if($('#live-cards').length) { src = 'cards'; liveUpdate(); }
- if($('#live-photos').length) {
+ if($('#live-photos').length || $('#live-cards').length) {
if(liking) {
liking = 0;
window.location.href=window.location.href;
@@ -368,54 +440,36 @@ function NavUpdate() {
updateCountsOnly = false;
- if(data.network || data.home || data.intros || data.mail || data.all_events || data.notify) {
- $('#notifications-btn').css('color', 'white').prop('disabled', false);
+ if(data.network || data.home || data.intros || data.register || data.mail || data.all_events || data.notify || data.files || data.pubs) {
+ $('#notifications-btn').css('opacity', 1);
}
else {
- $('#notifications-btn').css('color', 'grey').prop('disabled', true);
- $('#navbar-collapse-1').removeClass('in');
+ $('#notifications-btn').css('opacity', 0.5);
+ $('#navbar-collapse-1').removeClass('show');
}
- if(data.network == 0) {
- data.network = '';
- $('.net-update, .net-button').hide();
- } else {
- $('.net-update, .net-button').show();
+ if(data.home || data.intros || data.register || data.mail || data.notify || data.files) {
+ $('#notifications-btn-icon').removeClass('fa-exclamation-circle');
+ $('#notifications-btn-icon').addClass('fa-exclamation-triangle');
+ }
+ if(!data.home && !data.intros && !data.register && !data.mail && !data.notify && !data.files) {
+ $('#notifications-btn-icon').removeClass('fa-exclamation-triangle');
+ $('#notifications-btn-icon').addClass('fa-exclamation-circle');
}
- $('.net-update').html(data.network);
-
- if(data.home == 0) { data.home = ''; $('.home-update, .home-button').hide(); } else { $('.home-update, .home-button').show(); }
- $('.home-update').html(data.home);
-
- if(data.intros == 0) { data.intros = ''; $('.intro-update, .intro-button').hide(); } else { $('.intro-update, .intro-button').show(); }
- $('.intro-update').html(data.intros);
-
- if(data.mail == 0) { data.mail = ''; $('.mail-update, .mail-button').hide(); } else { $('.mail-update, .mail-button').show(); }
- $('.mail-update').html(data.mail);
-
- if(data.notify == 0) { data.notify = ''; $('.notify-update, .notify-button').hide(); } else { $('.notify-update, .notify-button').show(); }
- $('.notify-update').html(data.notify);
-
- if(data.register == 0) { data.register = ''; $('.register-update').removeClass('show'); } else { $('.register-update').addClass('show'); }
- $('.register-update').html(data.register);
-
- if(data.events == 0) { data.events = ''; $('.events-update, .events-button').hide(); } else { $('.events-update, .events-button').show(); }
- $('.events-update').html(data.events);
-
- if(data.events_today == 0) { data.events_today = ''; $('.events-today-update').removeClass('show'); } else { $('.events-today-update').addClass('show'); $('.events-update').html(data.events + '*'); }
- $('.events-today-update').html(data.events_today);
-
- if(data.birthdays == 0) { data.birthdays = ''; $('.birthdays-update').removeClass('show'); } else { $('.birthdays-update').addClass('show'); }
- $('.birthdays-update').html(data.birthdays);
-
- if(data.birthdays_today == 0) { data.birthdays_today = ''; $('.birthdays-today-update').removeClass('show'); } else { $('.birthdays-today-update').addClass('show'); $('.birthdays-update').html(data.birthdays + '*'); }
- $('.birthdays-today-update').html(data.birthdays_today);
-
- if(data.all_events == 0) { data.all_events = ''; $('.all_events-update, .all_events-button').hide(); } else { $('.all_events-update, .all_events-button').show(); }
- $('.all_events-update').html(data.all_events);
- if(data.all_events_today == 0) { data.all_events_today = ''; $('.all_events-today-update').removeClass('show'); } else { $('.all_events-today-update').addClass('show'); $('.all_events-update').html(data.all_events + '*'); }
- $('.all_events-today-update').html(data.all_events_today);
+ $.each(data, function(index, item) {
+ //do not process those
+ var arr = ['notice', 'info', 'invalid'];
+ if(arr.indexOf(index) !== -1)
+ return;
+
+ if(item == 0) {
+ $('.' + index + '-button').hide();
+ } else {
+ $('.' + index + '-button').show();
+ $('.' + index + '-update').html(item);
+ }
+ });
$.jGrowl.defaults.closerTemplate = '<div>[ ' + aStr.closeAll + ']</div>';
@@ -491,141 +545,88 @@ function updatePageItems(mode, data) {
function updateConvItems(mode,data) {
- if(mode === 'update') {
+ if(mode === 'update' || mode === 'replace') {
prev = 'threads-begin';
-
- $('.thread-wrapper.toplevel_item',data).each(function() {
-
- var ident = $(this).attr('id');
- // This should probably use the context argument instead
- var commentWrap = $('#'+ident+' .collapsed-comments').attr('id');
- var itmId = 0;
- var isVisible = false;
-
- if(typeof commentWrap !== 'undefined')
- itmId = commentWrap.replace('collapsed-comments-','');
-
- if($('#' + ident).length == 0 && profile_page == 1) {
- $('img',this).each(function() {
- $(this).attr('src',$(this).attr('dst'));
- });
- if($('#collapsed-comments-'+itmId).is(':visible'))
- isVisible = true;
- $('#' + prev).after($(this));
- if(isVisible)
- showHideComments(itmId);
- $("> .wall-item-outside-wrapper .autotime, > .thread-wrapper .autotime",this).timeago();
- $("> .shared_header .autotime",this).timeago();
- }
- else {
- $('img',this).each(function() {
- $(this).attr('src',$(this).attr('dst'));
- });
- if($('#collapsed-comments-'+itmId).is(':visible'))
- isVisible = true;
- $('#' + ident).replaceWith($(this));
- if(isVisible)
- showHideComments(itmId);
- $("> .wall-item-outside-wrapper .autotime, > .thread-wrapper .autotime",this).timeago();
- $("> .shared_header .autotime",this).timeago();
- }
- prev = ident;
- });
}
if(mode === 'append') {
-
next = 'threads-end';
+ }
+
+ if(mode === 'replace') {
+ $('.thread-wrapper').remove(); // clear existing content
+ }
- $('.thread-wrapper.toplevel_item',data).each(function() {
- var ident = $(this).attr('id');
- var commentWrap = $('#'+ident+' .collapsed-comments').attr('id');
- var itmId = 0;
- var isVisible = false;
+ $('.thread-wrapper.toplevel_item',data).each(function() {
- if(typeof commentWrap !== 'undefined')
- itmId = commentWrap.replace('collapsed-comments-', '');
+ var ident = $(this).attr('id');
- if($('#' + ident).length == 0) {
- $('img',this).each(function() {
- $(this).attr('src',$(this).attr('dst'));
- });
- if($('#collapsed-comments-'+itmId).is(':visible'))
- isVisible = true;
- $('#threads-end').before($(this));
- if(isVisible)
- showHideComments(itmId);
- $("> .wall-item-outside-wrapper .autotime, > .thread-wrapper .autotime",this).timeago();
- $("> .shared_header .autotime",this).timeago();
- }
- else {
- $('img',this).each(function() {
- $(this).attr('src', $(this).attr('dst'));
- });
- if($('#collapsed-comments-'+itmId).is(':visible'))
- isVisible = true;
- $('#' + ident).replaceWith($(this));
- if(isVisible)
- showHideComments(itmId);
- $("> .wall-item-outside-wrapper .autotime, > .thread-wrapper .autotime",this).timeago();
- $("> .shared_header .autotime",this).timeago();
- }
- });
+ var commentWrap = $('#'+ident+' .collapsed-comments').attr('id');
+ var itmId = 0;
+ var isVisible = false;
- if(loadingPage) {
- loadingPage = false;
- }
- }
- if(mode === 'replace') {
- // clear existing content
- $('.thread-wrapper').remove();
+ // figure out the comment state
+ if(typeof commentWrap !== 'undefined')
+ itmId = commentWrap.replace('collapsed-comments-','');
+
+ if($('#collapsed-comments-'+itmId).is(':visible'))
+ isVisible = true;
- prev = 'threads-begin';
+ // insert the content according to the mode and first_page
+ // and whether or not the content exists already (overwrite it)
- $('.thread-wrapper.toplevel_item',data).each(function() {
+ if($('#' + ident).length == 0) {
+ if((mode === 'update' || mode === 'replace') && profile_page == 1) {
+ $('#' + prev).after($(this));
+ prev = ident;
+ }
+ if(mode === 'append') {
+ $('#' + next).before($(this));
+ }
+ }
+ else {
+ $('#' + ident).replaceWith($(this));
+ }
- var ident = $(this).attr('id');
- var commentWrap = $('#'+ident+' .collapsed-comments').attr('id');
- var itmId = 0;
- var isVisible = false;
+ // set the comment state to the state we discovered earlier
- if(typeof commentWrap !== 'undefined')
- itmId = commentWrap.replace('collapsed-comments-','');
+ if(isVisible)
+ showHideComments(itmId);
- if($('#' + ident).length == 0 && profile_page == 1) {
- $('img',this).each(function() {
- $(this).attr('src',$(this).attr('dst'));
- });
- if($('#collapsed-comments-'+itmId).is(':visible'))
- isVisible = true;
- $('#' + prev).after($(this));
- if(isVisible)
- showHideComments(itmId);
- $("> .wall-item-outside-wrapper .autotime, > .thread-wrapper .autotime",this).timeago();
- $("> .shared_header .autotime",this).timeago();
- }
- prev = ident;
- });
+ // trigger the autotime function on all newly created content
- if(loadingPage) {
+ $("> .wall-item-outside-wrapper .autotime, > .thread-wrapper .autotime",this).timeago();
+ $("> .shared_header .autotime",this).timeago();
+
+ if((mode === 'append' || mode === 'replace') && (loadingPage)) {
loadingPage = false;
}
- if (window.location.search.indexOf("mid=") != -1 || window.location.pathname.indexOf("display") != -1) {
- var title = $(".wall-item-title").text();
- title.replace(/^\s+/, '');
- title.replace(/\s+$/, '');
- if (title)
- document.title = title + " - " + document.title;
+ // if single thread view and the item has a title, display it in the title bar
+
+ if(mode === 'replace') {
+ if (window.location.search.indexOf("mid=") != -1 || window.location.pathname.indexOf("display") != -1) {
+ var title = $(".wall-item-title").text();
+ title.replace(/^\s+/, '');
+ title.replace(/\s+$/, '');
+ if (title) {
+ savedTitle = title + " " + savedTitle;
+ }
+ }
}
- }
+ });
- $('.like-rotator').spin(false);
+ // reset rotators and cursors we may have set before reaching this place
+
+ $('.like-rotator').hide();
if(commentBusy) {
commentBusy = false;
$('body').css('cursor', 'auto');
}
+ // Setup to determine if the media player is playing. This affects
+ // some content loading decisions.
+
$('video').off('playing');
$('video').off('pause');
$('audio').off('playing');
@@ -665,10 +666,12 @@ function updateConvItems(mode,data) {
// auto-scroll to a particular comment in a thread (designated by mid) when in single-thread mode
// use the same method to generate the submid as we use in ThreadItem,
- // substr(0,32) + base64_encode + replace(['+','='],['','']);
- var submid = bParam_mid;
- var submid_encoded = ((submid.length) ? submid.substring(0,32) : 'abcdefg');
- submid_encoded = window.btoa(submid_encoded);
+ // base64_encode + replace(['+','='],['','']);
+
+ var submid = ((bParam_mid.length) ? bParam_mid : 'abcdefg');
+ var encoded = ((submid.substr(0,4) == 'b64.') ? true : false);
+ var submid_encoded = ((encoded) ? submid.substr(4) : window.btoa(submid));
+
submid_encoded = submid_encoded.replace(/[\+\=]/g,'');
if($('.item_' + submid_encoded).length && !$('.item_' + submid_encoded).hasClass('toplevel_item') && mode == 'replace') {
if($('.collapsed-comments').length) {
@@ -695,7 +698,7 @@ function collapseHeight() {
$(".wall-item-content, .directory-collapse").each(function() {
var orgHeight = $(this).outerHeight(true);
if(orgHeight > divmore_height) {
- if(! $(this).hasClass('divmore')) {
+ if(! $(this).hasClass('divmore') && $(this).has('div.no-collapse').length == 0) {
// check if we will collapse some content above the visible content and compensate the diff later
if($(this).offset().top + divmore_height - $(window).scrollTop() + cDiff - ($(".divgrow-showmore").outerHeight() * i) < 65) {
@@ -738,8 +741,8 @@ function collapseHeight() {
function liveUpdate() {
if(typeof profile_uid === 'undefined') profile_uid = false; /* Should probably be unified with channelId defined in head.tpl */
- if((src === null) || (stopped) || (! profile_uid)) { $('.like-rotator').spin(false); return; }
- if(($('.comment-edit-text-full').length) || (in_progress)) {
+ if((src === null) || (stopped) || (! profile_uid)) { $('.like-rotator').hide(); return; }
+ if(($('.comment-edit-text.expanded').length) || (in_progress)) {
if(livetime) {
clearTimeout(livetime);
}
@@ -767,7 +770,7 @@ function liveUpdate() {
update_url = buildCmd();
if(page_load) {
- $("#page-spinner").spin('small');
+ $("#page-spinner").show();
if(bParam_page == 1)
update_mode = 'replace';
else
@@ -816,8 +819,8 @@ function liveUpdate() {
page_load = false;
scroll_next = false;
updateConvItems(update_mode,data);
- $("#page-spinner").spin(false);
- $("#profile-jot-text-loading").spin(false);
+ $("#page-spinner").hide();
+ $("#profile-jot-text-loading").hide();
// adjust scroll position if new content was added above viewport
if(update_mode === 'update') {
@@ -846,8 +849,8 @@ function liveUpdate() {
page_load = false;
scroll_next = false;
updateConvItems(update_mode,data);
- $("#page-spinner").spin(false);
- $("#profile-jot-text-loading").spin(false);
+ $("#page-spinner").hide();
+ $("#profile-jot-text-loading").hide();
in_progress = false;
@@ -887,14 +890,14 @@ function pageUpdate() {
update_url = baseurl + '/' + page_query + '/?f=&aj=1&page=' + bParam_page + extra_args ;
- $("#page-spinner").spin('small');
+ $("#page-spinner").show();
update_mode = 'append';
$.get(update_url,function(data) {
page_load = false;
scroll_next = false;
updatePageItems(update_mode,data);
- $("#page-spinner").spin(false);
+ $("#page-spinner").hide();
$(".autotime").timeago();
in_progress = false;
});
@@ -902,6 +905,7 @@ function pageUpdate() {
function justifyPhotos(id) {
justifiedGalleryActive = true;
+ $('#' + id).show();
$('#' + id).justifiedGallery({
selector: 'a, div:not(.spinner, #page-end)',
margins: 3,
@@ -924,7 +928,8 @@ function justifyPhotosAjax(id) {
function notify_popup_loader(notifyType) {
- /* notifications template */
+ /* notifications template - different for navbar and notifications widget */
+ var navbar_notifications_tpl= unescape($("#navbar-notifications-template[rel=template]").html());
var notifications_tpl= unescape($("#nav-notifications-template[rel=template]").html());
var notifications_all = unescape($('<div>').append( $("#nav-" + notifyType + "-see-all").clone() ).html()); //outerHtml hack
var notifications_mark = unescape($('<div>').append( $("#nav-" + notifyType + "-mark-all").clone() ).html()); //outerHtml hack
@@ -939,22 +944,30 @@ function notify_popup_loader(notifyType) {
window.location.href=window.location.href;
}
- if(data.notify.length == 0){
- $("#nav-" + notifyType + "-menu").html(aStr[nothingnew]);
- } else {
- $("#nav-" + notifyType + "-menu").html(notifications_all + notifications_mark);
+ $("#navbar-" + notifyType + "-menu").html(notifications_all + notifications_mark);
+ $("#nav-" + notifyType + "-menu").html(notifications_all + notifications_mark);
+ $("." + notifyType + "-update").html(data.notify.length);
- $(data.notify).each(function() {
- html = notifications_tpl.format(this.notify_link,this.photo,this.name,this.message,this.when,this.hclass);
- $("#nav-" + notifyType + "-menu").append(html);
- });
- $(".dropdown-menu img[data-src]").each(function(i, el){
- // Replace data-src attribute with src attribute for every image
- $(el).attr('src', $(el).data("src"));
- $(el).removeAttr("data-src");
- });
- }
+ $(data.notify).each(function() {
+ html = navbar_notifications_tpl.format(this.notify_link,this.photo,this.name,this.message,this.when,this.hclass);
+ $("#navbar-" + notifyType + "-menu").append(html);
+ html = notifications_tpl.format(this.notify_link,this.photo,this.name,this.message,this.when,this.hclass);
+ $("#nav-" + notifyType + "-menu").append(html);
+ });
+
+ $(".dropdown-menu img[data-src], .notification img[data-src]").each(function(i, el){
+ // Replace data-src attribute with src attribute for every image
+ $(el).attr('src', $(el).data("src"));
+ $(el).removeAttr("data-src");
+ });
});
+
+ setTimeout(function() {
+ if(notify_menu.hasClass('show')) {
+ console.log('updating ' + notifyType + ' notifications...');
+ setTimeout(notify_popup_loader, updateInterval, notifyType);
+ }
+ }, 1000);
}
@@ -971,7 +984,7 @@ function notify_popup_loader(notifyType) {
function dolike(ident, verb) {
unpause();
- $('#like-rotator-' + ident.toString()).spin('tiny');
+ $('#like-rotator-' + ident.toString()).show();
$.get('like/' + ident.toString() + '?verb=' + verb, NavUpdate );
liking = 1;
}
@@ -1001,7 +1014,7 @@ function dropItem(url, object) {
function dosubthread(ident) {
unpause();
- $('#like-rotator-' + ident.toString()).spin('tiny');
+ $('#like-rotator-' + ident.toString()).show();
$.get('subthread/sub/' + ident.toString(), NavUpdate );
liking = 1;
}
@@ -1009,7 +1022,7 @@ function dosubthread(ident) {
function dounsubthread(ident) {
unpause();
- $('#like-rotator-' + ident.toString()).spin('tiny');
+ $('#like-rotator-' + ident.toString()).show();
$.get('subthread/unsub/' + ident.toString(), NavUpdate );
liking = 1;
}
@@ -1018,7 +1031,7 @@ function dounsubthread(ident) {
function dostar(ident) {
ident = ident.toString();
- $('#like-rotator-' + ident).spin('tiny');
+ $('#like-rotator-' + ident).show();
$.get('starred/' + ident, function(data) {
if(data.result == 1) {
$('#starred-' + ident).addClass('starred');
@@ -1036,7 +1049,7 @@ function dostar(ident) {
$('#star-' + ident).removeClass('hidden');
$('#unstar-' + ident).addClass('hidden');
}
- $('#like-rotator-' + ident).spin(false);
+ $('#like-rotator-' + ident).hide();
});
}
@@ -1070,11 +1083,11 @@ function lockview(type, id) {
function filestorage(event, nick, id) {
$('#cloud-index-' + last_filestorage_id).removeClass('cloud-index-active');
$('#perms-panel-' + last_filestorage_id).hide().html('');
- $('#file-edit-' + id).spin('tiny');
+ $('#file-edit-' + id).show();
$.get('filestorage/' + nick + '/' + id + '/edit', function(data) {
$('#cloud-index-' + id).addClass('cloud-index-active');
$('#perms-panel-' + id).html(data).show();
- $('#file-edit-' + id).spin(false);
+ $('#file-edit-' + id).hide();
last_filestorage_id = id;
});
}
@@ -1093,8 +1106,10 @@ function post_comment(id) {
$("#comment-edit-wrapper-" + id).hide();
$("#comment-edit-text-" + id).val('');
var tarea = document.getElementById("comment-edit-text-" + id);
- if(tarea)
+ if(tarea) {
commentClose(tarea, id);
+ $(document).unbind( "click.commentOpen");
+ }
if(timer) clearTimeout(timer);
timer = setTimeout(NavUpdate,1500);
}
@@ -1321,9 +1336,10 @@ Array.prototype.remove = function(item) {
return this.push.apply(this, rest);
};
-
$(document).ready(function() {
+ $(document).on('click focus', '.comment-edit-form', handle_comment_form);
+
jQuery.timeago.settings.strings = {
prefixAgo : aStr['t01'],
prefixFromNow : aStr['t02'],
@@ -1344,6 +1360,8 @@ $(document).ready(function() {
numbers : aStr['t17'],
};
+ savedTitle = document.title;
+
});
function zFormError(elm,x) {
diff --git a/view/js/mod_cards.js b/view/js/mod_cards.js
new file mode 100644
index 000000000..8b31c0f52
--- /dev/null
+++ b/view/js/mod_cards.js
@@ -0,0 +1,9 @@
+$(document).ready( function() {
+ $(".autotime").timeago();
+
+ /* autocomplete @nicknames */
+ $(".comment-edit-form textarea").editor_autocomplete(baseurl+"/acl?f=&n=1");
+ /* autocomplete bbcode */
+ $(".comment-edit-form textarea").bbco_autocomplete('bbcode');
+
+}); \ No newline at end of file
diff --git a/view/js/mod_cloud.js b/view/js/mod_cloud.js
index 8b8a3ba3f..8af90863e 100644
--- a/view/js/mod_cloud.js
+++ b/view/js/mod_cloud.js
@@ -91,7 +91,7 @@ function prepareHtml(f, i) {
'<td><i class="fa ' + getIconFromType(f.type) + '" title="' + f.type + '"></i></td>' +
'<td>' + f.name + '</td>' +
'<td id="upload-progress-' + i + '"></td><td></td><td></td><td></td><td></td>' +
- '<td class="hidden-xs">' + formatSizeUnits(f.size) + '</td><td class="hidden-xs"></td>' +
+ '<td class="d-none d-md-table-cell">' + formatSizeUnits(f.size) + '</td><td class="d-none d-md-table-cell"></td>' +
'</tr>' +
'<tr id="new-upload-progress-bar-' + i + '" class="new-upload">' +
'<td id="upload-progress-bar-' + i + '" colspan="9" class="upload-progress-bar"></td>' +
diff --git a/view/js/mod_connedit.js b/view/js/mod_connedit.js
index 4739c490c..7100e0d07 100644
--- a/view/js/mod_connedit.js
+++ b/view/js/mod_connedit.js
@@ -82,7 +82,7 @@ $(document).ready(function() {
function doRemove() {
var what = $(this).data('remove');
var element = $(this).parents('div.form-' + what);
- var where = '#abook_edit_form' + $(this).data('id');
+ var where = '#abook-edit-form' + $(this).data('id');
if(what === 'vcard-org' || what === 'vcard-title' || what === 'vcard-note') {
$(where + ' .add-' + what).show()
diff --git a/view/js/mod_display.js b/view/js/mod_display.js
new file mode 100644
index 000000000..7e24a7f86
--- /dev/null
+++ b/view/js/mod_display.js
@@ -0,0 +1,5 @@
+$(document).ready(function() {
+ $(".comment-edit-wrapper textarea").editor_autocomplete(baseurl+"/acl?f=&n=1");
+ // make auto-complete work in more places
+ $(".wall-item-comment-wrapper textarea").editor_autocomplete(baseurl+"/acl?f=&n=1");
+});
diff --git a/view/js/mod_help.js b/view/js/mod_help.js
new file mode 100644
index 000000000..8ee89dd61
--- /dev/null
+++ b/view/js/mod_help.js
@@ -0,0 +1,124 @@
+function docoTocToggle() {
+ if ($('#doco-top-toc').is(':visible')) {
+ $('#doco-toc-toggle').removeClass('fa-cog').addClass('fa-caret-right');
+ } else {
+ $('#doco-toc-toggle').removeClass('fa-caret-right').addClass('fa-caret-down');
+ }
+ $('#doco-top-toc').toggle();
+
+ return false;
+}
+
+toc = {};
+// Generate the table of contents in the side nav menu (see view/tpl/help.tpl)
+$(document).ready(function () {
+ // Generate the table of contents in the side nav menu (see view/tpl/help.tpl)
+ $('#doco-top-toc').toc({content: "#doco-content", headings: "h3,h4,h5,h6"});
+
+ $(".doco-section").find('a').each(function () {
+ var url = document.createElement('a');
+ url.href = window.location;
+ var pageName = url.href.split('/').pop().split('#').shift().split('?').shift();
+ var linkName = $(this).attr('href').split('/').pop();
+ if (pageName === linkName) {
+ var tocUl = $(this).closest('a').append('<ul>').find('ul');
+ tocUl.removeClass(); // Classes are automatically added to <ul> elements by something else
+ tocUl.toc({content: "#doco-content", headings: "h3"});
+ tocUl.addClass('toc-content');
+ tocUl.addClass('list-unstyled');
+ tocUl.attr('id', 'doco-side-toc');
+
+ }
+ });
+
+ $(document.body).trigger("sticky_kit:recalc");
+
+ toc.contentTop = [];
+ toc.edgeMargin = 20; // margin above the top or margin from the end of the page
+ toc.topRange = 200; // measure from the top of the viewport to X pixels down
+ // Set up content an array of locations
+ $('#doco-side-toc').find('a').each(function () {
+ toc.contentTop.push($('#' + $(this).attr('href').split('#').pop()).offset().top);
+ });
+
+
+ // adjust side menu
+ $(window).scroll(function () {
+ var winTop = $(window).scrollTop(),
+ bodyHt = $(document).height(),
+ vpHt = $(window).height() + toc.edgeMargin; // viewport height + margin
+ $.each(toc.contentTop, function (i, loc) {
+ if ((loc > winTop - toc.edgeMargin && (loc < winTop + toc.topRange || (winTop + vpHt) >= bodyHt))) {
+ $('#doco-side-toc li')
+ .removeClass('selected-doco-nav')
+ .eq(i).addClass('selected-doco-nav');
+ if (typeof ($('#doco-side-toc li').eq(i).find('a').attr('href').split('#')[1]) !== 'undefined') {
+ window.history.pushState({}, '', location.href.split('#')[0] + '#' + $('#doco-side-toc li').eq(i).find('a').attr('href').split('#')[1]);
+ }
+ }
+ });
+ });
+
+ // When the page loads, it does not scroll to the section specified in the URL because it
+ // has not been constructed yet by the script. This will reload the URL
+ if (typeof (location.href.split('#')[1]) !== 'undefined') {
+ var p = document.createElement('a');
+ p.href = location.href;
+ var portstr = '';
+ if (p.port !== '') {
+ portstr = ':' + p.port;
+ }
+ var newref = p.protocol + '//' + p.hostname + portstr + p.pathname + p.hash.split('?').shift();
+ location.replace(newref)
+ }
+
+
+ // Determine language translations available from the language selector menu itself
+ var langChoices = [];
+ $('.lang-selector').find('.lang-choice').each(function (idx, a) {
+ langChoices.push($(a).html());
+ });
+ // Parse the URL and insert the language code for the loaded language, based
+ // on the variable "help_language" that is declared in the help.tpl page template
+ var path = window.location.pathname.split('/');
+ var pathParts = [];
+ var pick_me = true;
+ for (var i = 0; i < path.length; i++) {
+ if(i === 2 && pick_me ) {
+ if(path[i].length > 0) {
+ pathParts.push(help_language);
+ pick_me = false;
+ if($.inArray(path[i], langChoices) < 0) {
+ i--;
+ }
+ }
+ } else {
+ if(path[i].length > 0) {
+ pathParts.push(path[i]);
+ }
+ }
+
+ }
+ // Update the address bar to reflect the loaded language
+ window.history.pushState({}, '', '/' + pathParts.join('/'));
+
+ // Highlight the language in the language selector that is currently viewed
+ $('.lang-selector').find('.lang-choice:contains("' + help_language + '")').addClass('active');
+
+ // Construct the links to the available translations based and populate the selector menu
+ $('.lang-selector').find('.lang-choice').each(function (idx, a) {
+ var langLink = [];
+
+ for (var i = 0; i < pathParts.length; i++) {
+
+ if(i === 1) {
+ langLink.push($(a).html());
+ } else {
+ langLink.push(pathParts[i]);
+ }
+
+ }
+ $(a).attr('href', '/' + langLink.join('/'));
+ });
+
+});
diff --git a/view/js/mod_network.js b/view/js/mod_network.js
index cd36786df..2899bbacd 100644
--- a/view/js/mod_network.js
+++ b/view/js/mod_network.js
@@ -1,5 +1,4 @@
$(document).ready(function() {
$("#search-text").contact_autocomplete(baseurl + '/search_ac','',true);
- $('.jslider-scale ins').addClass('hidden-xs');
});
diff --git a/view/js/mod_new_channel.js b/view/js/mod_new_channel.js
index 17b354a4b..e670e1a35 100644
--- a/view/js/mod_new_channel.js
+++ b/view/js/mod_new_channel.js
@@ -1,7 +1,7 @@
$(document).ready(function() {
// $("#id_permissions_role").sSelect();
$("#id_name").blur(function() {
- $("#name-spinner").spin('small');
+ $("#name-spinner").show();
var zreg_name = $("#id_name").val();
$.get("new_channel/autofill.json?f=&name=" + encodeURIComponent(zreg_name),function(data) {
$("#id_nickname").val(data);
@@ -9,12 +9,12 @@
$("#help_name").html("");
zFormError("#help_name",data.error);
}
- $("#name-spinner").spin(false);
+ $("#name-spinner").hide();
});
});
$("#id_nickname").blur(function() {
- $("#nick-spinner").spin('small');
+ $("#nick-spinner").show();
var zreg_nick = $("#id_nickname").val();
$.get("new_channel/checkaddr.json?f=&nick=" + encodeURIComponent(zreg_nick),function(data) {
$("#id_nickname").val(data);
@@ -22,7 +22,7 @@
$("#help_nickname").html("");
zFormError("#help_nickname",data.error);
}
- $("#nick-spinner").spin(false);
+ $("#nick-spinner").hide();
});
});
diff --git a/view/js/mod_profiles.js b/view/js/mod_profiles.js
index acc9f9953..784f64458 100644
--- a/view/js/mod_profiles.js
+++ b/view/js/mod_profiles.js
@@ -38,7 +38,7 @@ $(document).ready(function() {
var what = $(this).data('add');
var id = $(this).data('id');
var element = '#template-form-' + what;
- var where = '#abook-edit-form';
+ var where = '#profile-edit-form';
$(element + ' .remove-field').attr('data-id', id)
@@ -58,7 +58,7 @@ $(document).ready(function() {
function doRemove() {
var what = $(this).data('remove');
var element = $(this).parents('div.form-' + what);
- var where = '#abook_edit_form' + $(this).data('id');
+ var where = '#profile-edit-form' + $(this).data('id');
if(what === 'vcard-org' || what === 'vcard-title' || what === 'vcard-note') {
$(where + ' .add-' + what).show()
diff --git a/view/js/mod_register.js b/view/js/mod_register.js
index f1f3e7f71..6607579a2 100644
--- a/view/js/mod_register.js
+++ b/view/js/mod_register.js
@@ -28,7 +28,7 @@ $(document).ready(function() {
});
$("#id_name").blur(function() {
- $("#name-spinner").spin('small');
+ $("#name-spinner").show();
var zreg_name = $("#id_name").val();
$.get("new_channel/autofill.json?f=&name=" + encodeURIComponent(zreg_name),function(data) {
$("#id_nickname").val(data);
@@ -36,12 +36,12 @@ $(document).ready(function() {
$("#help_name").html("");
zFormError("#help_name",data.error);
}
- $("#name-spinner").spin(false);
+ $("#name-spinner").hide();
});
});
$("#id_nickname").blur(function() {
- $("#nick-spinner").spin('small');
+ $("#nick-spinner").show();
var zreg_nick = $("#id_nickname").val();
$.get("new_channel/checkaddr.json?f=&nick=" + encodeURIComponent(zreg_nick),function(data) {
$("#id_nickname").val(data);
@@ -49,7 +49,7 @@ $(document).ready(function() {
$("#help_nickname").html("");
zFormError("#help_nickname",data.error);
}
- $("#nick-spinner").spin(false);
+ $("#nick-spinner").hide();
});
});
diff --git a/view/js/mod_settings.js b/view/js/mod_settings.js
index 5c729fa48..f9faa3d5c 100644
--- a/view/js/mod_settings.js
+++ b/view/js/mod_settings.js
@@ -37,12 +37,19 @@ function setTheme(elm) {
function previewTheme(elm) {
theme = $(elm).val();
+ var schema = $('#id_schema').val();
$.getJSON('theme_info/' + theme,function(data) {
$('#theme-preview').html('<div id="theme-desc">' + data.desc + '</div><div id="theme-version">' + data.version + '</div><div id="theme-credits">' + data.credits + '</div><a href="' + data.img + '"><img src="' + data.img + '" style="max-width:100%; max-height:300px" alt="' + theme + '"></a>');
$('#id_schema').empty();
- $(data.schemas).each(function(index,item) {
- $('<option/>',{value:item['key'],text:item['val']}).appendTo('#id_schema');
- });
+ if(data.schemas.length) {
+ $(data.schemas).each(function(index,item) {
+ $('<option/>',{value:item['key'],text:item['val']}).appendTo('#id_schema');
+ });
+ $('#id_schema').val(schema ? schema : '---');
+ }
+ else {
+ $('<option/>',{value:'',text:'No schemes available'}).appendTo('#id_schema');
+ }
$('#custom-settings-content .section-content-tools-wrapper').html(data.config);
});
}
diff --git a/view/js/spin.js b/view/js/spin.js
deleted file mode 100644
index 145ce1baf..000000000
--- a/view/js/spin.js
+++ /dev/null
@@ -1,377 +0,0 @@
-/**
- * Copyright (c) 2011-2014 Felix Gnass
- * Licensed under the MIT license
- * http://spin.js.org/
- *
- * Example:
- var opts = {
- lines: 12, // The number of lines to draw
- , length: 7, // The length of each line
- , width: 5, // The line thickness
- , radius: 10 // The radius of the inner circle
- , scale: 1.0 // Scales overall size of the spinner
- , corners: 1 // Roundness (0..1)
- , color: '#000' // #rgb or #rrggbb
- , opacity: 1/4 // Opacity of the lines
- , rotate: 0 // Rotation offset
- , direction: 1 // 1: clockwise, -1: counterclockwise
- , speed: 1 // Rounds per second
- , trail: 100 // Afterglow percentage
- , fps: 20 // Frames per second when using setTimeout()
- , zIndex: 2e9 // Use a high z-index by default
- , className: 'spinner' // CSS class to assign to the element
- , top: '50%' // center vertically
- , left: '50%' // center horizontally
- , shadow: false // Whether to render a shadow
- , hwaccel: false // Whether to use hardware acceleration (might be buggy)
- , position: 'absolute' // Element positioning
- }
- var target = document.getElementById('foo')
- var spinner = new Spinner(opts).spin(target)
- */
-;(function (root, factory) {
-
- /* CommonJS */
- if (typeof exports == 'object') module.exports = factory()
-
- /* AMD module */
- else if (typeof define == 'function' && define.amd) define(factory)
-
- /* Browser global */
- else root.Spinner = factory()
-}(this, function () {
- "use strict"
-
- var prefixes = ['webkit', 'Moz', 'ms', 'O'] /* Vendor prefixes */
- , animations = {} /* Animation rules keyed by their name */
- , useCssAnimations /* Whether to use CSS animations or setTimeout */
- , sheet /* A stylesheet to hold the @keyframe or VML rules. */
-
- /**
- * Utility function to create elements. If no tag name is given,
- * a DIV is created. Optionally properties can be passed.
- */
- function createEl (tag, prop) {
- var el = document.createElement(tag || 'div')
- , n
-
- for (n in prop) el[n] = prop[n]
- return el
- }
-
- /**
- * Appends children and returns the parent.
- */
- function ins (parent /* child1, child2, ...*/) {
- for (var i = 1, n = arguments.length; i < n; i++) {
- parent.appendChild(arguments[i])
- }
-
- return parent
- }
-
- /**
- * Creates an opacity keyframe animation rule and returns its name.
- * Since most mobile Webkits have timing issues with animation-delay,
- * we create separate rules for each line/segment.
- */
- function addAnimation (alpha, trail, i, lines) {
- var name = ['opacity', trail, ~~(alpha * 100), i, lines].join('-')
- , start = 0.01 + i/lines * 100
- , z = Math.max(1 - (1-alpha) / trail * (100-start), alpha)
- , prefix = useCssAnimations.substring(0, useCssAnimations.indexOf('Animation')).toLowerCase()
- , pre = prefix && '-' + prefix + '-' || ''
-
- if (!animations[name]) {
- sheet.insertRule(
- '@' + pre + 'keyframes ' + name + '{' +
- '0%{opacity:' + z + '}' +
- start + '%{opacity:' + alpha + '}' +
- (start+0.01) + '%{opacity:1}' +
- (start+trail) % 100 + '%{opacity:' + alpha + '}' +
- '100%{opacity:' + z + '}' +
- '}', sheet.cssRules.length)
-
- animations[name] = 1
- }
-
- return name
- }
-
- /**
- * Tries various vendor prefixes and returns the first supported property.
- */
- function vendor (el, prop) {
- var s = el.style
- , pp
- , i
-
- prop = prop.charAt(0).toUpperCase() + prop.slice(1)
- if (s[prop] !== undefined) return prop
- for (i = 0; i < prefixes.length; i++) {
- pp = prefixes[i]+prop
- if (s[pp] !== undefined) return pp
- }
- }
-
- /**
- * Sets multiple style properties at once.
- */
- function css (el, prop) {
- for (var n in prop) {
- el.style[vendor(el, n) || n] = prop[n]
- }
-
- return el
- }
-
- /**
- * Fills in default values.
- */
- function merge (obj) {
- for (var i = 1; i < arguments.length; i++) {
- var def = arguments[i]
- for (var n in def) {
- if (obj[n] === undefined) obj[n] = def[n]
- }
- }
- return obj
- }
-
- /**
- * Returns the line color from the given string or array.
- */
- function getColor (color, idx) {
- return typeof color == 'string' ? color : color[idx % color.length]
- }
-
- // Built-in defaults
-
- var defaults = {
- lines: 12 // The number of lines to draw
- , length: 7 // The length of each line
- , width: 5 // The line thickness
- , radius: 10 // The radius of the inner circle
- , scale: 1.0 // Scales overall size of the spinner
- , corners: 1 // Roundness (0..1)
- , color: '#000' // #rgb or #rrggbb
- , opacity: 1/4 // Opacity of the lines
- , rotate: 0 // Rotation offset
- , direction: 1 // 1: clockwise, -1: counterclockwise
- , speed: 1 // Rounds per second
- , trail: 100 // Afterglow percentage
- , fps: 20 // Frames per second when using setTimeout()
- , zIndex: 2e9 // Use a high z-index by default
- , className: 'spinner' // CSS class to assign to the element
- , top: '50%' // center vertically
- , left: '50%' // center horizontally
- , shadow: false // Whether to render a shadow
- , hwaccel: false // Whether to use hardware acceleration (might be buggy)
- , position: 'absolute' // Element positioning
- }
-
- /** The constructor */
- function Spinner (o) {
- this.opts = merge(o || {}, Spinner.defaults, defaults)
- }
-
- // Global defaults that override the built-ins:
- Spinner.defaults = {}
-
- merge(Spinner.prototype, {
- /**
- * Adds the spinner to the given target element. If this instance is already
- * spinning, it is automatically removed from its previous target b calling
- * stop() internally.
- */
- spin: function (target) {
- this.stop()
-
- var self = this
- , o = self.opts
- , el = self.el = createEl(null, {className: o.className})
-
- css(el, {
- position: o.position
- , width: 0
- , zIndex: o.zIndex
- , left: o.left
- , top: o.top
- })
-
- if (target) {
- target.insertBefore(el, target.firstChild || null)
- }
-
- el.setAttribute('role', 'progressbar')
- self.lines(el, self.opts)
-
- if (!useCssAnimations) {
- // No CSS animation support, use setTimeout() instead
- var i = 0
- , start = (o.lines - 1) * (1 - o.direction) / 2
- , alpha
- , fps = o.fps
- , f = fps / o.speed
- , ostep = (1 - o.opacity) / (f * o.trail / 100)
- , astep = f / o.lines
-
- ;(function anim () {
- i++
- for (var j = 0; j < o.lines; j++) {
- alpha = Math.max(1 - (i + (o.lines - j) * astep) % f * ostep, o.opacity)
-
- self.opacity(el, j * o.direction + start, alpha, o)
- }
- self.timeout = self.el && setTimeout(anim, ~~(1000 / fps))
- })()
- }
- return self
- }
-
- /**
- * Stops and removes the Spinner.
- */
- , stop: function () {
- var el = this.el
- if (el) {
- clearTimeout(this.timeout)
- if (el.parentNode) el.parentNode.removeChild(el)
- this.el = undefined
- }
- return this
- }
-
- /**
- * Internal method that draws the individual lines. Will be overwritten
- * in VML fallback mode below.
- */
- , lines: function (el, o) {
- var i = 0
- , start = (o.lines - 1) * (1 - o.direction) / 2
- , seg
-
- function fill (color, shadow) {
- return css(createEl(), {
- position: 'absolute'
- , width: o.scale * (o.length + o.width) + 'px'
- , height: o.scale * o.width + 'px'
- , background: color
- , boxShadow: shadow
- , transformOrigin: 'left'
- , transform: 'rotate(' + ~~(360/o.lines*i + o.rotate) + 'deg) translate(' + o.scale*o.radius + 'px' + ',0)'
- , borderRadius: (o.corners * o.scale * o.width >> 1) + 'px'
- })
- }
-
- for (; i < o.lines; i++) {
- seg = css(createEl(), {
- position: 'absolute'
- , top: 1 + ~(o.scale * o.width / 2) + 'px'
- , transform: o.hwaccel ? 'translate3d(0,0,0)' : ''
- , opacity: o.opacity
- , animation: useCssAnimations && addAnimation(o.opacity, o.trail, start + i * o.direction, o.lines) + ' ' + 1 / o.speed + 's linear infinite'
- })
-
- if (o.shadow) ins(seg, css(fill('#000', '0 0 4px #000'), {top: '2px'}))
- ins(el, ins(seg, fill(getColor(o.color, i), '0 0 1px rgba(0,0,0,.1)')))
- }
- return el
- }
-
- /**
- * Internal method that adjusts the opacity of a single line.
- * Will be overwritten in VML fallback mode below.
- */
- , opacity: function (el, i, val) {
- if (i < el.childNodes.length) el.childNodes[i].style.opacity = val
- }
-
- })
-
-
- function initVML () {
-
- /* Utility function to create a VML tag */
- function vml (tag, attr) {
- return createEl('<' + tag + ' xmlns="urn:schemas-microsoft.com:vml" class="spin-vml">', attr)
- }
-
- // No CSS transforms but VML support, add a CSS rule for VML elements:
- sheet.addRule('.spin-vml', 'behavior:url(#default#VML)')
-
- Spinner.prototype.lines = function (el, o) {
- var r = o.scale * (o.length + o.width)
- , s = o.scale * 2 * r
-
- function grp () {
- return css(
- vml('group', {
- coordsize: s + ' ' + s
- , coordorigin: -r + ' ' + -r
- })
- , { width: s, height: s }
- )
- }
-
- var margin = -(o.width + o.length) * o.scale * 2 + 'px'
- , g = css(grp(), {position: 'absolute', top: margin, left: margin})
- , i
-
- function seg (i, dx, filter) {
- ins(
- g
- , ins(
- css(grp(), {rotation: 360 / o.lines * i + 'deg', left: ~~dx})
- , ins(
- css(
- vml('roundrect', {arcsize: o.corners})
- , { width: r
- , height: o.scale * o.width
- , left: o.scale * o.radius
- , top: -o.scale * o.width >> 1
- , filter: filter
- }
- )
- , vml('fill', {color: getColor(o.color, i), opacity: o.opacity})
- , vml('stroke', {opacity: 0}) // transparent stroke to fix color bleeding upon opacity change
- )
- )
- )
- }
-
- if (o.shadow)
- for (i = 1; i <= o.lines; i++) {
- seg(i, -2, 'progid:DXImageTransform.Microsoft.Blur(pixelradius=2,makeshadow=1,shadowopacity=.3)')
- }
-
- for (i = 1; i <= o.lines; i++) seg(i)
- return ins(el, g)
- }
-
- Spinner.prototype.opacity = function (el, i, val, o) {
- var c = el.firstChild
- o = o.shadow && o.lines || 0
- if (c && i + o < c.childNodes.length) {
- c = c.childNodes[i + o]; c = c && c.firstChild; c = c && c.firstChild
- if (c) c.opacity = val
- }
- }
- }
-
- if (typeof document !== 'undefined') {
- sheet = (function () {
- var el = createEl('style', {type : 'text/css'})
- ins(document.getElementsByTagName('head')[0], el)
- return el.sheet || el.styleSheet
- }())
-
- var probe = css(createEl('group'), {behavior: 'url(#default#VML)'})
-
- if (!vendor(probe, 'transform') && probe.adj) initVML()
- else useCssAnimations = vendor(probe, 'animation')
- }
-
- return Spinner
-
-}));
diff --git a/view/nb-no/htconfig.tpl b/view/nb-no/htconfig.tpl
index ea3f5b5c2..5acb0ebe2 100644
--- a/view/nb-no/htconfig.tpl
+++ b/view/nb-no/htconfig.tpl
@@ -34,14 +34,6 @@ App::$config['system']['baseurl'] = '{{$siteurl}}';
App::$config['system']['sitename'] = "Hubzilla";
App::$config['system']['location_hash'] = '{{$site_id}}';
-// Choices are 'basic', 'standard', and 'pro'.
-// basic sets up the sevrer for basic social networking and removes "complicated" features
-// standard provides most desired features except e-commerce
-// pro gives you access to everything
-
-App::$config['system']['server_role'] = '{{$server_role}}';
-
-
// These lines set additional security headers to be sent with all responses
// You may wish to set transport_security_header to 0 if your server already sends
// this header. content_security_policy may need to be disabled if you wish to
diff --git a/view/nl/hmessages.po b/view/nl/hmessages.po
index 55ce3e7b3..df00ee6b1 100644
--- a/view/nl/hmessages.po
+++ b/view/nl/hmessages.po
@@ -4,13 +4,13 @@
#
# Translators:
# jeroenpraat <social@jeroenvanrietpaap.nl>, 2015-2016
-# jeroenpraat <social@jeroenvanrietpaap.nl>, 2016
+# jeroenpraat <social@jeroenvanrietpaap.nl>, 2016-2017
msgid ""
msgstr ""
"Project-Id-Version: Redmatrix\n"
"Report-Msgid-Bugs-To: \n"
-"POT-Creation-Date: 2016-12-16 00:04-0800\n"
-"PO-Revision-Date: 2016-12-19 15:18+0000\n"
+"POT-Creation-Date: 2017-03-03 00:05-0800\n"
+"PO-Revision-Date: 2017-03-06 21:47+0000\n"
"Last-Translator: jeroenpraat <social@jeroenvanrietpaap.nl>\n"
"Language-Team: Dutch (http://www.transifex.com/Friendica/red-matrix/language/nl/)\n"
"MIME-Version: 1.0\n"
@@ -19,90 +19,91 @@ msgstr ""
"Language: nl\n"
"Plural-Forms: nplurals=2; plural=(n != 1);\n"
-#: ../../Zotlabs/Access/PermissionRoles.php:227
+#: ../../Zotlabs/Access/PermissionRoles.php:248
#: ../../include/permissions.php:945
msgid "Social Networking"
msgstr "Sociaal netwerk"
-#: ../../Zotlabs/Access/PermissionRoles.php:228
+#: ../../Zotlabs/Access/PermissionRoles.php:249
#: ../../include/permissions.php:945
msgid "Social - Mostly Public"
msgstr "Sociaal - Vrijwel alles openbaar"
-#: ../../Zotlabs/Access/PermissionRoles.php:229
+#: ../../Zotlabs/Access/PermissionRoles.php:250
#: ../../include/permissions.php:945
msgid "Social - Restricted"
msgstr "Sociaal - Beperkt zichtbaar"
-#: ../../Zotlabs/Access/PermissionRoles.php:230
+#: ../../Zotlabs/Access/PermissionRoles.php:251
#: ../../include/permissions.php:945
msgid "Social - Private"
msgstr "Sociaal - Verborgen kanaal"
-#: ../../Zotlabs/Access/PermissionRoles.php:233
+#: ../../Zotlabs/Access/PermissionRoles.php:254
#: ../../include/permissions.php:946
msgid "Community Forum"
msgstr "Groepsforum"
-#: ../../Zotlabs/Access/PermissionRoles.php:234
+#: ../../Zotlabs/Access/PermissionRoles.php:255
#: ../../include/permissions.php:946
msgid "Forum - Mostly Public"
msgstr "Forum - Vrijwel alles openbaar"
-#: ../../Zotlabs/Access/PermissionRoles.php:235
+#: ../../Zotlabs/Access/PermissionRoles.php:256
#: ../../include/permissions.php:946
msgid "Forum - Restricted"
msgstr "Forum - Beperkt zichtbaar"
-#: ../../Zotlabs/Access/PermissionRoles.php:236
+#: ../../Zotlabs/Access/PermissionRoles.php:257
#: ../../include/permissions.php:946
msgid "Forum - Private"
msgstr "Forum - Verborgen kanaal"
-#: ../../Zotlabs/Access/PermissionRoles.php:239
+#: ../../Zotlabs/Access/PermissionRoles.php:260
#: ../../include/permissions.php:947
msgid "Feed Republish"
msgstr "Feed herpubliceren"
-#: ../../Zotlabs/Access/PermissionRoles.php:240
+#: ../../Zotlabs/Access/PermissionRoles.php:261
#: ../../include/permissions.php:947
msgid "Feed - Mostly Public"
msgstr "Feed - Vrijwel alles openbaar"
-#: ../../Zotlabs/Access/PermissionRoles.php:241
+#: ../../Zotlabs/Access/PermissionRoles.php:262
#: ../../include/permissions.php:947
msgid "Feed - Restricted"
msgstr "Feed - Beperkt zichtbaar"
-#: ../../Zotlabs/Access/PermissionRoles.php:244
+#: ../../Zotlabs/Access/PermissionRoles.php:265
#: ../../include/permissions.php:948
msgid "Special Purpose"
msgstr "Speciaal doel"
-#: ../../Zotlabs/Access/PermissionRoles.php:245
+#: ../../Zotlabs/Access/PermissionRoles.php:266
#: ../../include/permissions.php:948
msgid "Special - Celebrity/Soapbox"
msgstr "Speciaal - Beroemdheid/alleen volgen"
-#: ../../Zotlabs/Access/PermissionRoles.php:246
+#: ../../Zotlabs/Access/PermissionRoles.php:267
#: ../../include/permissions.php:948
msgid "Special - Group Repository"
msgstr "Speciaal - Groepsopslag"
-#: ../../Zotlabs/Access/PermissionRoles.php:249
-#: ../../Zotlabs/Module/Register.php:213
+#: ../../Zotlabs/Access/PermissionRoles.php:270
+#: ../../Zotlabs/Module/Register.php:213 ../../Zotlabs/Module/Connedit.php:925
#: ../../Zotlabs/Module/New_channel.php:132
-#: ../../Zotlabs/Module/Settings/Channel.php:445
-#: ../../extend/addon/addon/cdav/cdav.php:277
-#: ../../extend/addon/addon/cdav/cdav.php:284
+#: ../../Zotlabs/Module/Profiles.php:798
+#: ../../Zotlabs/Module/Settings/Channel.php:463
#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1148
-#: ../../include/selectors.php:49 ../../include/selectors.php:66
-#: ../../include/selectors.php:104 ../../include/selectors.php:140
-#: ../../include/permissions.php:949
+#: ../../extend/addon/addon/cdav/cdav.php:277
+#: ../../extend/addon/addon/cdav/cdav.php:284 ../../include/selectors.php:49
+#: ../../include/selectors.php:66 ../../include/selectors.php:104
+#: ../../include/selectors.php:140 ../../include/connections.php:675
+#: ../../include/connections.php:682 ../../include/permissions.php:949
msgid "Other"
msgstr "Anders"
-#: ../../Zotlabs/Access/PermissionRoles.php:250
+#: ../../Zotlabs/Access/PermissionRoles.php:271
#: ../../include/permissions.php:949
msgid "Custom/Expert Mode"
msgstr "Expertmodus/handmatig aanpassen"
@@ -136,38 +137,46 @@ msgid "Can view my channel webpages"
msgstr "Kan de webpagina's van mijn kanaal bekijken"
#: ../../Zotlabs/Access/Permissions.php:53
+msgid "Can view my wiki pages"
+msgstr "Kan mijn wiki-pagina's bekijken"
+
+#: ../../Zotlabs/Access/Permissions.php:54
msgid "Can create/edit my channel webpages"
msgstr "Kan wegpagina's van mijn kanaal aanmaken en bewerken"
-#: ../../Zotlabs/Access/Permissions.php:54
+#: ../../Zotlabs/Access/Permissions.php:55
+msgid "Can write to my wiki pages"
+msgstr "Kan mijn wiki-pagina's bewerken"
+
+#: ../../Zotlabs/Access/Permissions.php:56
msgid "Can post on my channel (wall) page"
msgstr "Kan een bericht in mijn kanaal plaatsen"
-#: ../../Zotlabs/Access/Permissions.php:55 ../../include/permissions.php:44
+#: ../../Zotlabs/Access/Permissions.php:57 ../../include/permissions.php:44
msgid "Can comment on or like my posts"
msgstr "Kan op mijn berichten reageren of deze (niet) leuk vinden"
-#: ../../Zotlabs/Access/Permissions.php:56 ../../include/permissions.php:45
+#: ../../Zotlabs/Access/Permissions.php:58 ../../include/permissions.php:45
msgid "Can send me private mail messages"
msgstr "Kan mij privéberichten sturen"
-#: ../../Zotlabs/Access/Permissions.php:57
+#: ../../Zotlabs/Access/Permissions.php:59
msgid "Can like/dislike profiles and profile things"
msgstr "Kan profielen en profieldingen leuk en niet leuk vinden "
-#: ../../Zotlabs/Access/Permissions.php:58
+#: ../../Zotlabs/Access/Permissions.php:60
msgid "Can forward to all my channel connections via @+ mentions in posts"
msgstr "Kan naar al mijn kanaalconnecties berichten doorsturen met behulp van @vermeldingen+"
-#: ../../Zotlabs/Access/Permissions.php:59
+#: ../../Zotlabs/Access/Permissions.php:61
msgid "Can chat with me"
msgstr "Kan met mij chatten"
-#: ../../Zotlabs/Access/Permissions.php:60 ../../include/permissions.php:53
+#: ../../Zotlabs/Access/Permissions.php:62 ../../include/permissions.php:53
msgid "Can source my public posts in derived channels"
msgstr "Kan mijn openbare berichten als bron voor andere kanalen gebruiken"
-#: ../../Zotlabs/Access/Permissions.php:61
+#: ../../Zotlabs/Access/Permissions.php:63
msgid "Can administer my channel"
msgstr "Kan mijn kanaal beheren"
@@ -175,7 +184,7 @@ msgstr "Kan mijn kanaal beheren"
msgid "parent"
msgstr "omhoog"
-#: ../../Zotlabs/Storage/Browser.php:130 ../../include/text.php:2682
+#: ../../Zotlabs/Storage/Browser.php:130 ../../include/text.php:2700
msgid "Collection"
msgstr "map"
@@ -199,20 +208,19 @@ msgstr "Planning-postvak IN"
msgid "Schedule Outbox"
msgstr "Planning-postvak UIT"
-#: ../../Zotlabs/Storage/Browser.php:163 ../../Zotlabs/Module/Photos.php:789
-#: ../../Zotlabs/Module/Photos.php:1249
-#: ../../Zotlabs/Module/Embedphotos.php:145 ../../Zotlabs/Lib/Apps.php:526
-#: ../../Zotlabs/Lib/Apps.php:603
+#: ../../Zotlabs/Storage/Browser.php:163 ../../Zotlabs/Module/Photos.php:784
+#: ../../Zotlabs/Module/Photos.php:1244
+#: ../../Zotlabs/Module/Embedphotos.php:145 ../../Zotlabs/Lib/Apps.php:561
+#: ../../Zotlabs/Lib/Apps.php:639
#: ../../extend/addon/addon/cdav/Mod_Cdav.php:745
#: ../../extend/addon/addon/cdav/Mod_Cdav.php:746
#: ../../extend/addon/addon/cdav/Mod_Cdav.php:753
-#: ../../include/widgets.php:1684 ../../include/conversation.php:1029
+#: ../../include/widgets.php:1757 ../../include/conversation.php:1177
msgid "Unknown"
msgstr "Onbekend"
#: ../../Zotlabs/Storage/Browser.php:224 ../../Zotlabs/Module/Fbrowser.php:85
-#: ../../Zotlabs/Lib/Apps.php:219 ../../include/nav.php:96
-#: ../../include/conversation.php:1681
+#: ../../Zotlabs/Lib/Apps.php:224 ../../include/conversation.php:1843
msgid "Files"
msgstr "Bestanden"
@@ -224,44 +232,49 @@ msgstr "Totaal"
msgid "Shared"
msgstr "Gedeeld"
-#: ../../Zotlabs/Storage/Browser.php:228 ../../Zotlabs/Storage/Browser.php:321
-#: ../../Zotlabs/Module/Menu.php:118 ../../Zotlabs/Module/New_channel.php:147
-#: ../../Zotlabs/Module/Blocks.php:159 ../../Zotlabs/Module/Layouts.php:184
-#: ../../Zotlabs/Module/Webpages.php:239
+#: ../../Zotlabs/Storage/Browser.php:228 ../../Zotlabs/Storage/Browser.php:330
+#: ../../Zotlabs/Module/Menu.php:118 ../../Zotlabs/Module/Connedit.php:928
+#: ../../Zotlabs/Module/New_channel.php:147
+#: ../../Zotlabs/Module/Webpages.php:243 ../../Zotlabs/Module/Blocks.php:159
+#: ../../Zotlabs/Module/Layouts.php:184 ../../Zotlabs/Module/Profiles.php:801
#: ../../extend/addon/addon/cdav/include/widgets.php:127
#: ../../extend/addon/addon/cdav/include/widgets.php:164
#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1151
msgid "Create"
msgstr "Aanmaken"
-#: ../../Zotlabs/Storage/Browser.php:229 ../../Zotlabs/Storage/Browser.php:323
+#: ../../Zotlabs/Storage/Browser.php:229 ../../Zotlabs/Storage/Browser.php:332
#: ../../Zotlabs/Module/Cover_photo.php:357
-#: ../../Zotlabs/Module/Photos.php:816 ../../Zotlabs/Module/Photos.php:1370
-#: ../../Zotlabs/Module/Profile_photo.php:410
+#: ../../Zotlabs/Module/Photos.php:811 ../../Zotlabs/Module/Photos.php:1368
+#: ../../Zotlabs/Module/Profile_photo.php:421
#: ../../Zotlabs/Module/Embedphotos.php:157
#: ../../extend/addon/addon/cdav/include/widgets.php:132
#: ../../extend/addon/addon/cdav/include/widgets.php:168
-#: ../../include/widgets.php:1697
+#: ../../include/widgets.php:1770
msgid "Upload"
msgstr "Uploaden"
#: ../../Zotlabs/Storage/Browser.php:233
#: ../../Zotlabs/Module/Admin/Channels.php:159
-#: ../../Zotlabs/Module/Sharedwithme.php:99 ../../Zotlabs/Module/Wiki.php:151
+#: ../../Zotlabs/Module/Connedit.php:913
+#: ../../Zotlabs/Module/Sharedwithme.php:99
#: ../../Zotlabs/Module/Settings/Oauth.php:89
#: ../../Zotlabs/Module/Settings/Oauth.php:115
-#: ../../Zotlabs/Module/Chat.php:250
+#: ../../Zotlabs/Module/Wiki.php:171 ../../Zotlabs/Module/Chat.php:248
#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1136
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:164
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:172
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:156
+#: ../../include/widgets.php:976
msgid "Name"
msgstr "Naam"
-#: ../../Zotlabs/Storage/Browser.php:234 ../../Zotlabs/Module/Wiki.php:152
+#: ../../Zotlabs/Storage/Browser.php:234 ../../Zotlabs/Module/Wiki.php:172
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:157
msgid "Type"
msgstr "Type"
#: ../../Zotlabs/Storage/Browser.php:235
-#: ../../Zotlabs/Module/Sharedwithme.php:101 ../../include/text.php:1390
+#: ../../Zotlabs/Module/Sharedwithme.php:101 ../../include/text.php:1414
msgid "Size"
msgstr "Grootte"
@@ -271,39 +284,43 @@ msgid "Last Modified"
msgstr "Laatst gewijzigd"
#: ../../Zotlabs/Storage/Browser.php:238
-#: ../../Zotlabs/Module/Connections.php:290
-#: ../../Zotlabs/Module/Connections.php:310
+#: ../../Zotlabs/Module/Editblock.php:109
+#: ../../Zotlabs/Module/Connections.php:300
+#: ../../Zotlabs/Module/Connections.php:320
#: ../../Zotlabs/Module/Admin/Profs.php:154
#: ../../Zotlabs/Module/Editlayout.php:114
#: ../../Zotlabs/Module/Editwebpage.php:145 ../../Zotlabs/Module/Menu.php:112
-#: ../../Zotlabs/Module/Editblock.php:109 ../../Zotlabs/Module/Editpost.php:84
+#: ../../Zotlabs/Module/Editpost.php:85 ../../Zotlabs/Module/Webpages.php:244
#: ../../Zotlabs/Module/Blocks.php:160 ../../Zotlabs/Module/Layouts.php:192
-#: ../../Zotlabs/Module/Webpages.php:240 ../../Zotlabs/Module/Wiki.php:144
-#: ../../Zotlabs/Module/Wiki.php:246
#: ../../Zotlabs/Module/Settings/Oauth.php:149
-#: ../../Zotlabs/Module/Thing.php:260 ../../Zotlabs/Lib/ThreadItem.php:106
-#: ../../Zotlabs/Lib/Apps.php:346
+#: ../../Zotlabs/Module/Thing.php:260 ../../Zotlabs/Module/Wiki.php:164
+#: ../../Zotlabs/Module/Wiki.php:271 ../../Zotlabs/Lib/ThreadItem.php:106
+#: ../../Zotlabs/Lib/Apps.php:357
#: ../../extend/addon/addon/cdav/include/widgets.php:125
#: ../../extend/addon/addon/cdav/include/widgets.php:161
-#: ../../include/channel.php:961 ../../include/channel.php:965
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:149
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:251
#: ../../include/page_widgets.php:9 ../../include/page_widgets.php:39
-#: ../../include/menu.php:113
+#: ../../include/menu.php:113 ../../include/channel.php:1044
+#: ../../include/channel.php:1048
msgid "Edit"
msgstr "Bewerken"
-#: ../../Zotlabs/Storage/Browser.php:239 ../../Zotlabs/Module/Connedit.php:635
-#: ../../Zotlabs/Module/Connections.php:263
+#: ../../Zotlabs/Storage/Browser.php:239
+#: ../../Zotlabs/Module/Editblock.php:134
+#: ../../Zotlabs/Module/Connections.php:271
#: ../../Zotlabs/Module/Admin/Profs.php:155
#: ../../Zotlabs/Module/Admin/Accounts.php:173
#: ../../Zotlabs/Module/Admin/Channels.php:149
#: ../../Zotlabs/Module/Editlayout.php:137
#: ../../Zotlabs/Module/Editwebpage.php:170
-#: ../../Zotlabs/Module/Editblock.php:134 ../../Zotlabs/Module/Group.php:177
-#: ../../Zotlabs/Module/Photos.php:1179 ../../Zotlabs/Module/Blocks.php:162
-#: ../../Zotlabs/Module/Webpages.php:242
+#: ../../Zotlabs/Module/Connedit.php:661 ../../Zotlabs/Module/Connedit.php:930
+#: ../../Zotlabs/Module/Photos.php:1174 ../../Zotlabs/Module/Group.php:177
+#: ../../Zotlabs/Module/Webpages.php:246 ../../Zotlabs/Module/Blocks.php:162
+#: ../../Zotlabs/Module/Profiles.php:803
#: ../../Zotlabs/Module/Settings/Oauth.php:150
#: ../../Zotlabs/Module/Thing.php:261 ../../Zotlabs/Lib/ThreadItem.php:126
-#: ../../Zotlabs/Lib/Apps.php:347
+#: ../../Zotlabs/Lib/Apps.php:358
#: ../../extend/addon/addon/cdav/Mod_Cdav.php:864
#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1153
#: ../../include/conversation.php:656
@@ -324,24 +341,42 @@ msgstr "Je gebruikt %1$s van totaal %2$s beschikbare bestandsopslag. (%3$s&#37;)
msgid "WARNING:"
msgstr "WAARSCHUWING:"
-#: ../../Zotlabs/Storage/Browser.php:320
+#: ../../Zotlabs/Storage/Browser.php:325
+msgid ""
+"Please use DAV to upload large (video, audio) files.<br>See <a class=\"zrl\""
+" href=\"help/member/member_guide#Cloud_Desktop_Clients\">Cloud Desktop "
+"Clients</a>"
+msgstr "Gebruik DAV om grote (video-, audio-) bestanden te uploaden.<br>Zie hiervoor de documentatie over de <a class=\"zrl\" href=\"help/member/member_guide#Cloud_Desktop_Clients\">cloud en desktopclients</a>."
+
+#: ../../Zotlabs/Storage/Browser.php:329
msgid "Create new folder"
msgstr "Nieuwe map aanmaken"
-#: ../../Zotlabs/Storage/Browser.php:322
+#: ../../Zotlabs/Storage/Browser.php:331
msgid "Upload file"
msgstr "Bestand uploaden"
-#: ../../Zotlabs/Storage/Browser.php:335
+#: ../../Zotlabs/Storage/Browser.php:345
msgid "Drop files here to immediately upload"
msgstr "Sleep bestanden hierheen om ze onmiddellijk te uploaden"
-#: ../../Zotlabs/Web/Router.php:67 ../../Zotlabs/Web/WebServer.php:128
-#: ../../Zotlabs/Module/Achievements.php:34
-#: ../../Zotlabs/Module/Register.php:77 ../../Zotlabs/Module/Connedit.php:397
-#: ../../Zotlabs/Module/Authtest.php:16 ../../Zotlabs/Module/Bookmarks.php:61
-#: ../../Zotlabs/Module/Locs.php:87 ../../Zotlabs/Module/Page.php:35
-#: ../../Zotlabs/Module/Page.php:91 ../../Zotlabs/Module/Manage.php:10
+#: ../../Zotlabs/Web/WebServer.php:127 ../../Zotlabs/Module/Group.php:72
+#: ../../Zotlabs/Module/Dreport.php:10 ../../Zotlabs/Module/Dreport.php:68
+#: ../../Zotlabs/Module/Import_items.php:114
+#: ../../Zotlabs/Module/Profperm.php:28 ../../Zotlabs/Module/Like.php:283
+#: ../../Zotlabs/Module/Subthread.php:62
+#: ../../extend/addon/addon/frphotos/frphotos.php:81
+#: ../../extend/addon/addon/redfiles/redfiles.php:109
+#: ../../extend/addon/addon/redphotos/redphotos.php:119
+#: ../../include/items.php:327
+msgid "Permission denied"
+msgstr "Toegang geweigerd"
+
+#: ../../Zotlabs/Web/WebServer.php:128
+#: ../../Zotlabs/Module/Achievements.php:34 ../../Zotlabs/Module/Appman.php:82
+#: ../../Zotlabs/Module/Register.php:77 ../../Zotlabs/Module/Authtest.php:16
+#: ../../Zotlabs/Module/Bookmarks.php:61 ../../Zotlabs/Module/Editblock.php:67
+#: ../../Zotlabs/Module/Page.php:35 ../../Zotlabs/Module/Page.php:91
#: ../../Zotlabs/Module/Connections.php:33
#: ../../Zotlabs/Module/Cover_photo.php:277
#: ../../Zotlabs/Module/Cover_photo.php:290
@@ -351,78 +386,69 @@ msgstr "Sleep bestanden hierheen om ze onmiddellijk te uploaden"
#: ../../Zotlabs/Module/Editwebpage.php:89
#: ../../Zotlabs/Module/Editwebpage.php:104
#: ../../Zotlabs/Module/Editwebpage.php:126
-#: ../../Zotlabs/Module/Channel.php:107 ../../Zotlabs/Module/Channel.php:237
-#: ../../Zotlabs/Module/Channel.php:277 ../../Zotlabs/Module/Network.php:15
-#: ../../Zotlabs/Module/Menu.php:78 ../../Zotlabs/Module/Appman.php:76
-#: ../../Zotlabs/Module/Filestorage.php:23
+#: ../../Zotlabs/Module/Network.php:15 ../../Zotlabs/Module/Menu.php:78
+#: ../../Zotlabs/Module/Locs.php:87 ../../Zotlabs/Module/Connedit.php:388
+#: ../../Zotlabs/Module/Events.php:271 ../../Zotlabs/Module/Filestorage.php:23
#: ../../Zotlabs/Module/Filestorage.php:78
#: ../../Zotlabs/Module/Filestorage.php:93
-#: ../../Zotlabs/Module/Filestorage.php:120 ../../Zotlabs/Module/Item.php:220
-#: ../../Zotlabs/Module/Item.php:230 ../../Zotlabs/Module/Item.php:1064
-#: ../../Zotlabs/Module/Settings.php:59 ../../Zotlabs/Module/Mail.php:163
-#: ../../Zotlabs/Module/Block.php:26 ../../Zotlabs/Module/Block.php:76
+#: ../../Zotlabs/Module/Filestorage.php:120 ../../Zotlabs/Module/Photos.php:73
+#: ../../Zotlabs/Module/Settings.php:59 ../../Zotlabs/Module/Group.php:13
+#: ../../Zotlabs/Module/Mail.php:164 ../../Zotlabs/Module/Block.php:26
+#: ../../Zotlabs/Module/Block.php:76 ../../Zotlabs/Module/Manage.php:10
+#: ../../Zotlabs/Module/Message.php:18 ../../Zotlabs/Module/Mitem.php:115
+#: ../../Zotlabs/Module/Editpost.php:17 ../../Zotlabs/Module/Api.php:24
#: ../../Zotlabs/Module/Invite.php:17 ../../Zotlabs/Module/Invite.php:94
-#: ../../Zotlabs/Module/Editblock.php:67 ../../Zotlabs/Module/Group.php:13
-#: ../../Zotlabs/Module/Mitem.php:115 ../../Zotlabs/Module/Message.php:18
-#: ../../Zotlabs/Module/Mood.php:116 ../../Zotlabs/Module/Photos.php:73
-#: ../../Zotlabs/Module/Setup.php:212 ../../Zotlabs/Module/Editpost.php:17
#: ../../Zotlabs/Module/New_channel.php:77
#: ../../Zotlabs/Module/New_channel.php:104
+#: ../../Zotlabs/Module/Webpages.php:116
#: ../../Zotlabs/Module/Notifications.php:11 ../../Zotlabs/Module/Poke.php:137
-#: ../../Zotlabs/Module/Profiles.php:197 ../../Zotlabs/Module/Profiles.php:595
-#: ../../Zotlabs/Module/Profile.php:68 ../../Zotlabs/Module/Profile.php:76
-#: ../../Zotlabs/Module/Blocks.php:73 ../../Zotlabs/Module/Blocks.php:80
-#: ../../Zotlabs/Module/Layouts.php:71 ../../Zotlabs/Module/Layouts.php:78
-#: ../../Zotlabs/Module/Layouts.php:89 ../../Zotlabs/Module/Rate.php:113
-#: ../../Zotlabs/Module/Like.php:181
-#: ../../Zotlabs/Module/Profile_photo.php:273
-#: ../../Zotlabs/Module/Profile_photo.php:286
-#: ../../Zotlabs/Module/Common.php:39 ../../Zotlabs/Module/Api.php:24
+#: ../../Zotlabs/Module/Item.php:220 ../../Zotlabs/Module/Item.php:230
+#: ../../Zotlabs/Module/Item.php:1067 ../../Zotlabs/Module/Blocks.php:73
+#: ../../Zotlabs/Module/Blocks.php:80 ../../Zotlabs/Module/Layouts.php:71
+#: ../../Zotlabs/Module/Layouts.php:78 ../../Zotlabs/Module/Layouts.php:89
+#: ../../Zotlabs/Module/Rate.php:113
+#: ../../Zotlabs/Module/Profile_photo.php:278
+#: ../../Zotlabs/Module/Profile_photo.php:291
+#: ../../Zotlabs/Module/Like.php:181 ../../Zotlabs/Module/Common.php:39
+#: ../../Zotlabs/Module/Channel.php:115 ../../Zotlabs/Module/Channel.php:245
+#: ../../Zotlabs/Module/Channel.php:285 ../../Zotlabs/Module/Mood.php:116
#: ../../Zotlabs/Module/Regmod.php:21 ../../Zotlabs/Module/Pdledit.php:29
+#: ../../Zotlabs/Module/Profile.php:83 ../../Zotlabs/Module/Profile.php:100
+#: ../../Zotlabs/Module/Viewsrc.php:18
#: ../../Zotlabs/Module/Service_limits.php:11
-#: ../../Zotlabs/Module/Webpages.php:116
-#: ../../Zotlabs/Module/Sharedwithme.php:11 ../../Zotlabs/Module/Wiki.php:189
-#: ../../Zotlabs/Module/Wiki.php:286 ../../Zotlabs/Module/Sources.php:74
-#: ../../Zotlabs/Module/Suggest.php:30 ../../Zotlabs/Module/Thing.php:274
-#: ../../Zotlabs/Module/Thing.php:294 ../../Zotlabs/Module/Thing.php:335
+#: ../../Zotlabs/Module/Sharedwithme.php:11
+#: ../../Zotlabs/Module/Sources.php:74 ../../Zotlabs/Module/Suggest.php:30
+#: ../../Zotlabs/Module/Profiles.php:198 ../../Zotlabs/Module/Profiles.php:635
+#: ../../Zotlabs/Module/Thing.php:274 ../../Zotlabs/Module/Thing.php:294
+#: ../../Zotlabs/Module/Thing.php:335 ../../Zotlabs/Module/Setup.php:212
#: ../../Zotlabs/Module/Viewconnections.php:28
#: ../../Zotlabs/Module/Viewconnections.php:33
-#: ../../Zotlabs/Module/Viewsrc.php:18 ../../Zotlabs/Module/Chat.php:100
-#: ../../Zotlabs/Module/Chat.php:105 ../../Zotlabs/Module/Events.php:267
-#: ../../Zotlabs/Lib/Chatroom.php:137
+#: ../../Zotlabs/Module/Wiki.php:50 ../../Zotlabs/Module/Wiki.php:215
+#: ../../Zotlabs/Module/Wiki.php:311 ../../Zotlabs/Module/Chat.php:98
+#: ../../Zotlabs/Module/Chat.php:103 ../../Zotlabs/Lib/Chatroom.php:137
#: ../../extend/addon/addon/friendica/dfrn_confirm.php:55
#: ../../extend/addon/addon/keepout/keepout.php:36
#: ../../extend/addon/addon/pumpio/pumpio.php:40
#: ../../extend/addon/addon/openid/Mod_Id.php:53
#: ../../extend/addon/addon/diaspora_reconnect/diaspora_reconnect.php:58
-#: ../../include/items.php:3422 ../../include/attach.php:142
-#: ../../include/attach.php:189 ../../include/attach.php:253
-#: ../../include/attach.php:267 ../../include/attach.php:274
-#: ../../include/attach.php:341 ../../include/attach.php:355
-#: ../../include/attach.php:362 ../../include/attach.php:439
-#: ../../include/attach.php:906 ../../include/attach.php:977
-#: ../../include/attach.php:1135 ../../include/photos.php:27
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:194
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:291
+#: ../../include/items.php:3447 ../../include/attach.php:144
+#: ../../include/attach.php:191 ../../include/attach.php:255
+#: ../../include/attach.php:269 ../../include/attach.php:276
+#: ../../include/attach.php:343 ../../include/attach.php:357
+#: ../../include/attach.php:364 ../../include/attach.php:441
+#: ../../include/attach.php:908 ../../include/attach.php:979
+#: ../../include/attach.php:1137 ../../include/photos.php:27
msgid "Permission denied."
msgstr "Toegang geweigerd."
-#: ../../Zotlabs/Web/Router.php:157 ../../Zotlabs/Module/Page.php:94
-#: ../../Zotlabs/Module/Display.php:120 ../../Zotlabs/Module/Block.php:79
-#: ../../include/help.php:66
+#: ../../Zotlabs/Web/Router.php:146 ../../Zotlabs/Module/Page.php:94
+#: ../../Zotlabs/Module/Display.php:122 ../../Zotlabs/Module/Block.php:79
+#: ../../Zotlabs/Lib/NativeWikiPage.php:518 ../../include/help.php:68
msgid "Page not found."
msgstr "Pagina niet gevonden."
-#: ../../Zotlabs/Web/WebServer.php:127 ../../Zotlabs/Module/Dreport.php:10
-#: ../../Zotlabs/Module/Dreport.php:68
-#: ../../Zotlabs/Module/Import_items.php:114 ../../Zotlabs/Module/Group.php:72
-#: ../../Zotlabs/Module/Profperm.php:28 ../../Zotlabs/Module/Like.php:283
-#: ../../Zotlabs/Module/Subthread.php:62
-#: ../../extend/addon/addon/frphotos/frphotos.php:81
-#: ../../extend/addon/addon/redfiles/redfiles.php:109
-#: ../../extend/addon/addon/redphotos/redphotos.php:119
-#: ../../include/items.php:327
-msgid "Permission denied"
-msgstr "Toegang geweigerd"
-
#: ../../Zotlabs/Zot/Auth.php:138
msgid ""
"Remote authentication blocked. You are logged into this site locally. Please"
@@ -431,19 +457,19 @@ msgstr "Authenticatie op afstand geblokkeerd. Je bent lokaal op deze hub ingelog
#: ../../Zotlabs/Zot/Auth.php:250
#: ../../extend/addon/addon/openid/Mod_Openid.php:76
-#: ../../extend/addon/addon/openid/Mod_Openid.php:183
+#: ../../extend/addon/addon/openid/Mod_Openid.php:178
#, php-format
msgid "Welcome %s. Remote authentication successful."
msgstr "Welkom %s. Authenticatie op afstand geslaagd."
#: ../../Zotlabs/Module/Achievements.php:15
-#: ../../Zotlabs/Module/Connect.php:17 ../../Zotlabs/Module/Editlayout.php:31
+#: ../../Zotlabs/Module/Connect.php:17 ../../Zotlabs/Module/Editblock.php:31
+#: ../../Zotlabs/Module/Editlayout.php:31
#: ../../Zotlabs/Module/Editwebpage.php:32
#: ../../Zotlabs/Module/Filestorage.php:59
-#: ../../Zotlabs/Module/Editblock.php:31 ../../Zotlabs/Module/Hcard.php:12
-#: ../../Zotlabs/Module/Profile.php:20 ../../Zotlabs/Module/Blocks.php:33
-#: ../../Zotlabs/Module/Layouts.php:31 ../../Zotlabs/Module/Webpages.php:33
-#: ../../include/channel.php:862
+#: ../../Zotlabs/Module/Webpages.php:33 ../../Zotlabs/Module/Hcard.php:12
+#: ../../Zotlabs/Module/Blocks.php:33 ../../Zotlabs/Module/Layouts.php:31
+#: ../../Zotlabs/Module/Profile.php:20 ../../include/channel.php:945
msgid "Requested profile is not available."
msgstr "Opgevraagd profiel is niet beschikbaar"
@@ -451,13 +477,159 @@ msgstr "Opgevraagd profiel is niet beschikbaar"
msgid "Some blurb about what to do when you're new here"
msgstr "Welkom op $Projectname. Klik op de tab ontdekken of klik rechtsboven op de <a href=\"directory\">kanalengids</a>, om kanalen te vinden. Rechtsboven vind je ook <a href=\"directory\">apps</a>, waar je vrijwel alle functies van $Projectname kunt vinden. Voor <a href=\"directory\">hulp</a> met $Projectname klik je op het vraagteken."
-#: ../../Zotlabs/Module/Chatsvc.php:117
-msgid "Away"
-msgstr "Afwezig"
+#: ../../Zotlabs/Module/Appman.php:38 ../../Zotlabs/Module/Appman.php:55
+msgid "App installed."
+msgstr "App geïnstalleerd"
-#: ../../Zotlabs/Module/Chatsvc.php:122
-msgid "Online"
-msgstr "Online"
+#: ../../Zotlabs/Module/Appman.php:48
+msgid "Malformed app."
+msgstr "Misvormde app."
+
+#: ../../Zotlabs/Module/Appman.php:111
+msgid "Embed code"
+msgstr "Insluitcode"
+
+#: ../../Zotlabs/Module/Appman.php:117
+msgid "Edit App"
+msgstr "App bewerken"
+
+#: ../../Zotlabs/Module/Appman.php:117
+msgid "Create App"
+msgstr "App maken"
+
+#: ../../Zotlabs/Module/Appman.php:122
+msgid "Name of app"
+msgstr "Naam van app"
+
+#: ../../Zotlabs/Module/Appman.php:122 ../../Zotlabs/Module/Appman.php:123
+#: ../../Zotlabs/Module/Events.php:460 ../../Zotlabs/Module/Events.php:465
+#: ../../Zotlabs/Module/Profiles.php:748 ../../Zotlabs/Module/Profiles.php:752
+#: ../../include/datetime.php:259
+msgid "Required"
+msgstr "Vereist"
+
+#: ../../Zotlabs/Module/Appman.php:123
+msgid "Location (URL) of app"
+msgstr "Locatie (URL) van app"
+
+#: ../../Zotlabs/Module/Appman.php:124 ../../Zotlabs/Module/Events.php:473
+#: ../../Zotlabs/Module/Rbmark.php:101
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:838
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:173
+msgid "Description"
+msgstr "Omschrijving"
+
+#: ../../Zotlabs/Module/Appman.php:125
+msgid "Photo icon URL"
+msgstr "URL van pictogram"
+
+#: ../../Zotlabs/Module/Appman.php:125
+msgid "80 x 80 pixels - optional"
+msgstr "80 x 80 pixels (niet verplicht)"
+
+#: ../../Zotlabs/Module/Appman.php:126
+msgid "Categories (optional, comma separated list)"
+msgstr "Categorieën (niet verplicht, door komma's gescheiden lijst)"
+
+#: ../../Zotlabs/Module/Appman.php:127
+msgid "Version ID"
+msgstr "Versie-ID"
+
+#: ../../Zotlabs/Module/Appman.php:128
+msgid "Price of app"
+msgstr "Prijs van de app"
+
+#: ../../Zotlabs/Module/Appman.php:129
+msgid "Location (URL) to purchase app"
+msgstr "Locatie (URL) om de app aan te schaffen"
+
+#: ../../Zotlabs/Module/Appman.php:134 ../../Zotlabs/Module/Import.php:507
+#: ../../Zotlabs/Module/Connect.php:98
+#: ../../Zotlabs/Module/Admin/Features.php:66
+#: ../../Zotlabs/Module/Admin/Logs.php:84
+#: ../../Zotlabs/Module/Admin/Profs.php:157
+#: ../../Zotlabs/Module/Admin/Security.php:104
+#: ../../Zotlabs/Module/Admin/Account_edit.php:74
+#: ../../Zotlabs/Module/Admin/Accounts.php:166
+#: ../../Zotlabs/Module/Admin/Channels.php:147
+#: ../../Zotlabs/Module/Admin/Site.php:268
+#: ../../Zotlabs/Module/Admin/Plugins.php:438
+#: ../../Zotlabs/Module/Admin/Themes.php:158 ../../Zotlabs/Module/Locs.php:121
+#: ../../Zotlabs/Module/Connedit.php:893 ../../Zotlabs/Module/Events.php:493
+#: ../../Zotlabs/Module/Filestorage.php:165
+#: ../../Zotlabs/Module/Photos.php:667 ../../Zotlabs/Module/Photos.php:1053
+#: ../../Zotlabs/Module/Photos.php:1093 ../../Zotlabs/Module/Photos.php:1211
+#: ../../Zotlabs/Module/Group.php:85 ../../Zotlabs/Module/Mail.php:413
+#: ../../Zotlabs/Module/Import_items.php:122
+#: ../../Zotlabs/Module/Mitem.php:243 ../../Zotlabs/Module/Cal.php:342
+#: ../../Zotlabs/Module/Invite.php:149 ../../Zotlabs/Module/Poke.php:186
+#: ../../Zotlabs/Module/Pconfig.php:107 ../../Zotlabs/Module/Rate.php:166
+#: ../../Zotlabs/Module/Mood.php:139 ../../Zotlabs/Module/Pdledit.php:74
+#: ../../Zotlabs/Module/Sources.php:114 ../../Zotlabs/Module/Sources.php:149
+#: ../../Zotlabs/Module/Profiles.php:726
+#: ../../Zotlabs/Module/Settings/Features.php:47
+#: ../../Zotlabs/Module/Settings/Oauth.php:87
+#: ../../Zotlabs/Module/Settings/Account.php:118
+#: ../../Zotlabs/Module/Settings/Channel.php:476
+#: ../../Zotlabs/Module/Settings/Featured.php:50
+#: ../../Zotlabs/Module/Settings/Permcats.php:112
+#: ../../Zotlabs/Module/Settings/Tokens.php:168
+#: ../../Zotlabs/Module/Settings/Display.php:203
+#: ../../Zotlabs/Module/Thing.php:320 ../../Zotlabs/Module/Thing.php:370
+#: ../../Zotlabs/Module/Setup.php:309 ../../Zotlabs/Module/Setup.php:357
+#: ../../Zotlabs/Module/Wiki.php:168 ../../Zotlabs/Module/Chat.php:194
+#: ../../Zotlabs/Module/Chat.php:239 ../../Zotlabs/Module/Xchan.php:15
+#: ../../Zotlabs/Lib/ThreadItem.php:731
+#: ../../extend/addon/addon/chords/Mod_Chords.php:60
+#: ../../extend/addon/addon/diaspora/diaspora.php:714
+#: ../../extend/addon/addon/dwpost/dwpost.php:89
+#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:124
+#: ../../extend/addon/addon/friendica/friendica.php:128
+#: ../../extend/addon/addon/frphotos/frphotos.php:96
+#: ../../extend/addon/addon/hubwall/hubwall.php:95
+#: ../../extend/addon/addon/ijpost/ijpost.php:89
+#: ../../extend/addon/addon/irc/irc.php:53
+#: ../../extend/addon/addon/jappixmini/jappixmini.php:371
+#: ../../extend/addon/addon/libertree/libertree.php:85
+#: ../../extend/addon/addon/ljpost/ljpost.php:86
+#: ../../extend/addon/addon/logrot/logrot.php:35
+#: ../../extend/addon/addon/mailhost/mailhost.php:40
+#: ../../extend/addon/addon/nofed/nofed.php:80
+#: ../../extend/addon/addon/nsabait/nsabait.php:161
+#: ../../extend/addon/addon/nsfw/nsfw.php:92
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:53
+#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:168
+#: ../../extend/addon/addon/pageheader/pageheader.php:48
+#: ../../extend/addon/addon/piwik/piwik.php:95
+#: ../../extend/addon/addon/planets/planets.php:157
+#: ../../extend/addon/addon/pumpio/pumpio.php:237
+#: ../../extend/addon/addon/rainbowtag/rainbowtag.php:85
+#: ../../extend/addon/addon/redfiles/redfiles.php:124
+#: ../../extend/addon/addon/redphotos/redphotos.php:136
+#: ../../extend/addon/addon/redred/redred.php:119
+#: ../../extend/addon/addon/rtof/rtof.php:101
+#: ../../extend/addon/addon/skeleton/skeleton.php:65
+#: ../../extend/addon/addon/smileybutton/smileybutton.php:281
+#: ../../extend/addon/addon/startpage/startpage.php:113
+#: ../../extend/addon/addon/statusnet/statusnet.php:322
+#: ../../extend/addon/addon/statusnet/statusnet.php:380
+#: ../../extend/addon/addon/statusnet/statusnet.php:432
+#: ../../extend/addon/addon/statusnet/statusnet.php:899
+#: ../../extend/addon/addon/superblock/superblock.php:120
+#: ../../extend/addon/addon/twitter/twitter.php:217
+#: ../../extend/addon/addon/twitter/twitter.php:259
+#: ../../extend/addon/addon/visage/visage.php:170
+#: ../../extend/addon/addon/wppost/wppost.php:113
+#: ../../extend/addon/addon/xmpp/xmpp.php:69
+#: ../../extend/addon/addon/cdav/cdav.php:246
+#: ../../extend/addon/addon/likebanner/likebanner.php:57
+#: ../../extend/addon/addon/mailtest/mailtest.php:100
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:153
+#: ../../extend/addon/addon/gnusoc/gnusoc.php:133
+#: ../../include/widgets.php:801 ../../include/js_strings.php:22
+#: ../../view/theme/redbasic/php/config.php:106
+msgid "Submit"
+msgstr "Opslaan"
#: ../../Zotlabs/Module/Register.php:49
msgid "Maximum daily site registrations exceeded. Please try again tomorrow."
@@ -581,7 +753,7 @@ msgid "yes"
msgstr "Ja"
#: ../../Zotlabs/Module/Register.php:253
-#: ../../Zotlabs/Module/Admin/Site.php:261
+#: ../../Zotlabs/Module/Admin/Site.php:269
msgid "Registration"
msgstr "Registratie"
@@ -589,8 +761,8 @@ msgstr "Registratie"
msgid "Membership on this site is by invitation only."
msgstr "Registreren op deze $Projectname-hub kan alleen op uitnodiging."
-#: ../../Zotlabs/Module/Register.php:270 ../../include/nav.php:150
-#: ../../boot.php:1702
+#: ../../Zotlabs/Module/Register.php:270 ../../include/nav.php:162
+#: ../../boot.php:1730
msgid "Register"
msgstr "Registreren"
@@ -605,618 +777,156 @@ msgstr "Mogelijk moet op deze hub eerst jouw e-mail geverifieerd worden. Wanneer
msgid "Fetching URL returns error: %1$s"
msgstr "Ophalen URL gaf een foutmelding terug: %1$s"
-#: ../../Zotlabs/Module/Match.php:26
-msgid "Profile Match"
-msgstr "Profielovereenkomst"
-
-#: ../../Zotlabs/Module/Match.php:35
-msgid "No keywords to match. Please add keywords to your default profile."
-msgstr "Je hebt geen trefwoorden waarmee overeenkomsten gevonden kunnen worden. Voeg enkele trefwoorden aan je standaardprofiel toe."
-
-#: ../../Zotlabs/Module/Match.php:67
-msgid "is interested in:"
-msgstr "is geïnteresseerd in:"
-
-#: ../../Zotlabs/Module/Match.php:68 ../../Zotlabs/Module/Directory.php:328
-#: ../../Zotlabs/Module/Suggest.php:56 ../../include/channel.php:1036
-#: ../../include/connections.php:78 ../../include/widgets.php:147
-#: ../../include/widgets.php:184 ../../include/conversation.php:937
-msgid "Connect"
-msgstr "Verbinden"
-
-#: ../../Zotlabs/Module/Match.php:74
-msgid "No matches"
-msgstr "Geen overeenkomsten"
-
-#: ../../Zotlabs/Module/Connedit.php:82
-msgid "Could not access contact record."
-msgstr "Kon geen toegang krijgen tot de connectie-gegevens."
-
-#: ../../Zotlabs/Module/Connedit.php:106
-msgid "Could not locate selected profile."
-msgstr "Kon het gekozen profiel niet vinden."
-
-#: ../../Zotlabs/Module/Connedit.php:258
-msgid "Connection updated."
-msgstr "Connectie bijgewerkt."
-
-#: ../../Zotlabs/Module/Connedit.php:260
-msgid "Failed to update connection record."
-msgstr "Bijwerken van connectie-gegevens mislukt."
-
-#: ../../Zotlabs/Module/Connedit.php:310
-msgid "is now connected to"
-msgstr "is nu verbonden met"
-
-#: ../../Zotlabs/Module/Connedit.php:411 ../../Zotlabs/Module/Connedit.php:716
-#: ../../Zotlabs/Module/Admin/Site.php:218 ../../Zotlabs/Module/Menu.php:100
-#: ../../Zotlabs/Module/Menu.php:157 ../../Zotlabs/Module/Filestorage.php:160
-#: ../../Zotlabs/Module/Filestorage.php:168 ../../Zotlabs/Module/Mitem.php:162
-#: ../../Zotlabs/Module/Mitem.php:163 ../../Zotlabs/Module/Mitem.php:240
-#: ../../Zotlabs/Module/Mitem.php:241 ../../Zotlabs/Module/Photos.php:653
-#: ../../Zotlabs/Module/Profiles.php:641 ../../Zotlabs/Module/Api.php:97
-#: ../../Zotlabs/Module/Removeme.php:63 ../../Zotlabs/Module/Wiki.php:159
-#: ../../Zotlabs/Module/Settings/Channel.php:289
-#: ../../Zotlabs/Module/Settings/Display.php:103
-#: ../../Zotlabs/Module/Events.php:463 ../../Zotlabs/Module/Events.php:464
-#: ../../extend/addon/addon/dwpost/dwpost.php:73
-#: ../../extend/addon/addon/dwpost/dwpost.php:85
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:120
-#: ../../extend/addon/addon/friendica/dfrn_request.php:865
-#: ../../extend/addon/addon/ijpost/ijpost.php:73
-#: ../../extend/addon/addon/ijpost/ijpost.php:85
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:309
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:313
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:343
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:351
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:355
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:359
-#: ../../extend/addon/addon/libertree/libertree.php:69
-#: ../../extend/addon/addon/libertree/libertree.php:81
-#: ../../extend/addon/addon/ljpost/ljpost.php:70
-#: ../../extend/addon/addon/ljpost/ljpost.php:82
-#: ../../extend/addon/addon/nofed/nofed.php:72
-#: ../../extend/addon/addon/nofed/nofed.php:76
-#: ../../extend/addon/addon/nsabait/nsabait.php:157
-#: ../../extend/addon/addon/nsfw/nsfw.php:84
-#: ../../extend/addon/addon/planets/planets.php:153
-#: ../../extend/addon/addon/pumpio/pumpio.php:219
-#: ../../extend/addon/addon/pumpio/pumpio.php:223
-#: ../../extend/addon/addon/pumpio/pumpio.php:227
-#: ../../extend/addon/addon/pumpio/pumpio.php:231
-#: ../../extend/addon/addon/rainbowtag/rainbowtag.php:81
-#: ../../extend/addon/addon/redred/redred.php:95
-#: ../../extend/addon/addon/redred/redred.php:99
-#: ../../extend/addon/addon/rtof/rtof.php:81
-#: ../../extend/addon/addon/rtof/rtof.php:85
-#: ../../extend/addon/addon/smileybutton/smileybutton.php:273
-#: ../../extend/addon/addon/smileybutton/smileybutton.php:277
-#: ../../extend/addon/addon/statusnet/statusnet.php:389
-#: ../../extend/addon/addon/statusnet/statusnet.php:411
-#: ../../extend/addon/addon/statusnet/statusnet.php:415
-#: ../../extend/addon/addon/statusnet/statusnet.php:424
-#: ../../extend/addon/addon/twitter/twitter.php:242
-#: ../../extend/addon/addon/twitter/twitter.php:246
-#: ../../extend/addon/addon/twitter/twitter.php:255
-#: ../../extend/addon/addon/visage/visage.php:166
-#: ../../extend/addon/addon/wppost/wppost.php:82
-#: ../../extend/addon/addon/wppost/wppost.php:105
-#: ../../extend/addon/addon/wppost/wppost.php:109
-#: ../../extend/addon/addon/xmpp/xmpp.php:53
-#: ../../extend/addon/addon/cdav/cdav.php:234 ../../include/dir_fns.php:143
-#: ../../include/dir_fns.php:144 ../../include/dir_fns.php:145
-#: ../../view/theme/redbasic/php/config.php:111
-#: ../../view/theme/redbasic/php/config.php:136 ../../boot.php:1724
-msgid "No"
-msgstr "Nee"
+#: ../../Zotlabs/Module/Rmagic.php:35
+msgid "Authentication failed."
+msgstr "Authenticatie mislukt."
-#: ../../Zotlabs/Module/Connedit.php:411
-#: ../../Zotlabs/Module/Admin/Site.php:220 ../../Zotlabs/Module/Menu.php:100
-#: ../../Zotlabs/Module/Menu.php:157 ../../Zotlabs/Module/Filestorage.php:160
-#: ../../Zotlabs/Module/Filestorage.php:168 ../../Zotlabs/Module/Mitem.php:162
-#: ../../Zotlabs/Module/Mitem.php:163 ../../Zotlabs/Module/Mitem.php:240
-#: ../../Zotlabs/Module/Mitem.php:241 ../../Zotlabs/Module/Photos.php:653
-#: ../../Zotlabs/Module/Profiles.php:641 ../../Zotlabs/Module/Api.php:96
-#: ../../Zotlabs/Module/Removeme.php:63 ../../Zotlabs/Module/Wiki.php:159
-#: ../../Zotlabs/Module/Settings/Channel.php:289
-#: ../../Zotlabs/Module/Settings/Display.php:103
-#: ../../Zotlabs/Module/Events.php:463 ../../Zotlabs/Module/Events.php:464
-#: ../../extend/addon/addon/dwpost/dwpost.php:73
-#: ../../extend/addon/addon/dwpost/dwpost.php:85
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:120
-#: ../../extend/addon/addon/friendica/dfrn_request.php:865
-#: ../../extend/addon/addon/ijpost/ijpost.php:73
-#: ../../extend/addon/addon/ijpost/ijpost.php:85
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:309
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:313
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:343
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:351
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:355
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:359
-#: ../../extend/addon/addon/libertree/libertree.php:69
-#: ../../extend/addon/addon/libertree/libertree.php:81
-#: ../../extend/addon/addon/ljpost/ljpost.php:70
-#: ../../extend/addon/addon/ljpost/ljpost.php:82
-#: ../../extend/addon/addon/nofed/nofed.php:72
-#: ../../extend/addon/addon/nofed/nofed.php:76
-#: ../../extend/addon/addon/nsabait/nsabait.php:157
-#: ../../extend/addon/addon/nsfw/nsfw.php:84
-#: ../../extend/addon/addon/planets/planets.php:153
-#: ../../extend/addon/addon/pumpio/pumpio.php:219
-#: ../../extend/addon/addon/pumpio/pumpio.php:223
-#: ../../extend/addon/addon/pumpio/pumpio.php:227
-#: ../../extend/addon/addon/pumpio/pumpio.php:231
-#: ../../extend/addon/addon/rainbowtag/rainbowtag.php:81
-#: ../../extend/addon/addon/redred/redred.php:95
-#: ../../extend/addon/addon/redred/redred.php:99
-#: ../../extend/addon/addon/rtof/rtof.php:81
-#: ../../extend/addon/addon/rtof/rtof.php:85
-#: ../../extend/addon/addon/smileybutton/smileybutton.php:273
-#: ../../extend/addon/addon/smileybutton/smileybutton.php:277
-#: ../../extend/addon/addon/statusnet/statusnet.php:389
-#: ../../extend/addon/addon/statusnet/statusnet.php:411
-#: ../../extend/addon/addon/statusnet/statusnet.php:415
-#: ../../extend/addon/addon/statusnet/statusnet.php:424
-#: ../../extend/addon/addon/twitter/twitter.php:242
-#: ../../extend/addon/addon/twitter/twitter.php:246
-#: ../../extend/addon/addon/twitter/twitter.php:255
-#: ../../extend/addon/addon/visage/visage.php:166
-#: ../../extend/addon/addon/wppost/wppost.php:82
-#: ../../extend/addon/addon/wppost/wppost.php:105
-#: ../../extend/addon/addon/wppost/wppost.php:109
-#: ../../extend/addon/addon/xmpp/xmpp.php:53
-#: ../../extend/addon/addon/cdav/cdav.php:234 ../../include/dir_fns.php:143
-#: ../../include/dir_fns.php:144 ../../include/dir_fns.php:145
-#: ../../view/theme/redbasic/php/config.php:111
-#: ../../view/theme/redbasic/php/config.php:136 ../../boot.php:1724
-msgid "Yes"
-msgstr "Ja"
+#: ../../Zotlabs/Module/Rmagic.php:75 ../../include/channel.php:1989
+msgid "Remote Authentication"
+msgstr "Authenticatie op afstand"
-#: ../../Zotlabs/Module/Connedit.php:443
-msgid "Could not access address book record."
-msgstr "Kon geen toegang krijgen tot de record van de connectie."
+#: ../../Zotlabs/Module/Rmagic.php:76 ../../include/channel.php:1990
+msgid "Enter your channel address (e.g. channel@example.com)"
+msgstr "Vul jouw kanaaladres in (bijv. channel@example.com)"
-#: ../../Zotlabs/Module/Connedit.php:463
-msgid "Refresh failed - channel is currently unavailable."
-msgstr "Vernieuwen mislukt - kanaal is momenteel niet beschikbaar"
+#: ../../Zotlabs/Module/Rmagic.php:77 ../../include/channel.php:1991
+msgid "Authenticate"
+msgstr "Authenticeren"
-#: ../../Zotlabs/Module/Connedit.php:478 ../../Zotlabs/Module/Connedit.php:487
-#: ../../Zotlabs/Module/Connedit.php:496 ../../Zotlabs/Module/Connedit.php:505
-#: ../../Zotlabs/Module/Connedit.php:518
-msgid "Unable to set address book parameters."
-msgstr "Niet in staat om de parameters van connecties in te stellen."
+#: ../../Zotlabs/Module/Import.php:57 ../../Zotlabs/Module/Import_items.php:42
+msgid "Nothing to import."
+msgstr "Niets gevonden om te importeren"
-#: ../../Zotlabs/Module/Connedit.php:542
-msgid "Connection has been removed."
-msgstr "Connectie is verwijderd"
+#: ../../Zotlabs/Module/Import.php:69 ../../Zotlabs/Module/Import.php:84
+#: ../../Zotlabs/Module/Import_items.php:66
+msgid "Unable to download data from old server"
+msgstr "Niet in staat om gegevens van de oude hub te downloaden"
-#: ../../Zotlabs/Module/Connedit.php:582 ../../Zotlabs/Lib/Apps.php:223
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:56
-#: ../../include/nav.php:89 ../../include/conversation.php:935
-msgid "View Profile"
-msgstr "Profiel weergeven"
+#: ../../Zotlabs/Module/Import.php:91 ../../Zotlabs/Module/Import_items.php:72
+msgid "Imported file is empty."
+msgstr "Geïmporteerde bestand is leeg"
-#: ../../Zotlabs/Module/Connedit.php:585
+#: ../../Zotlabs/Module/Import.php:111
+#: ../../Zotlabs/Module/Import_items.php:88
#, php-format
-msgid "View %s's profile"
-msgstr "Profiel van %s weergeven"
-
-#: ../../Zotlabs/Module/Connedit.php:589
-msgid "Refresh Permissions"
-msgstr "Permissies vernieuwen"
-
-#: ../../Zotlabs/Module/Connedit.php:592
-msgid "Fetch updated permissions"
-msgstr "Aangepaste permissies ophalen"
-
-#: ../../Zotlabs/Module/Connedit.php:596
-msgid "Recent Activity"
-msgstr "Recente activiteit/berichten"
-
-#: ../../Zotlabs/Module/Connedit.php:599
-msgid "View recent posts and comments"
-msgstr "Recente berichten en reacties weergeven"
-
-#: ../../Zotlabs/Module/Connedit.php:603
-#: ../../Zotlabs/Module/Admin/Accounts.php:175
-msgid "Unblock"
-msgstr "Deblokkeren"
-
-#: ../../Zotlabs/Module/Connedit.php:603
-#: ../../Zotlabs/Module/Admin/Accounts.php:174
-msgid "Block"
-msgstr "Blokkeren"
-
-#: ../../Zotlabs/Module/Connedit.php:606
-msgid "Block (or Unblock) all communications with this connection"
-msgstr "Blokkeer (of deblokkeer) alle communicatie met deze connectie"
-
-#: ../../Zotlabs/Module/Connedit.php:607
-msgid "This connection is blocked!"
-msgstr "Deze connectie is geblokkeerd!"
-
-#: ../../Zotlabs/Module/Connedit.php:611
-msgid "Unignore"
-msgstr "Niet meer negeren"
-
-#: ../../Zotlabs/Module/Connedit.php:611
-#: ../../Zotlabs/Module/Connections.php:277
-msgid "Ignore"
-msgstr "Negeren"
-
-#: ../../Zotlabs/Module/Connedit.php:614
-msgid "Ignore (or Unignore) all inbound communications from this connection"
-msgstr "Negeer (of negeer niet meer) alle inkomende communicatie van deze connectie"
-
-#: ../../Zotlabs/Module/Connedit.php:615
-msgid "This connection is ignored!"
-msgstr "Deze connectie wordt genegeerd!"
-
-#: ../../Zotlabs/Module/Connedit.php:619
-msgid "Unarchive"
-msgstr "Niet meer archiveren"
-
-#: ../../Zotlabs/Module/Connedit.php:619
-msgid "Archive"
-msgstr "Archiveren"
-
-#: ../../Zotlabs/Module/Connedit.php:622
-msgid ""
-"Archive (or Unarchive) this connection - mark channel dead but keep content"
-msgstr "Archiveer (of dearchiveer) deze connectie - markeer het kanaal als dood, maar bewaar de inhoud"
-
-#: ../../Zotlabs/Module/Connedit.php:623
-msgid "This connection is archived!"
-msgstr "Deze connectie is gearchiveerd!"
-
-#: ../../Zotlabs/Module/Connedit.php:627
-msgid "Unhide"
-msgstr "Niet meer verbergen"
-
-#: ../../Zotlabs/Module/Connedit.php:627
-msgid "Hide"
-msgstr "Verbergen"
-
-#: ../../Zotlabs/Module/Connedit.php:630
-msgid "Hide or Unhide this connection from your other connections"
-msgstr "Deze connectie verbergen (of niet meer verbergen) voor jouw andere connecties"
-
-#: ../../Zotlabs/Module/Connedit.php:631
-msgid "This connection is hidden!"
-msgstr "Deze connectie is verborgen!"
-
-#: ../../Zotlabs/Module/Connedit.php:638
-msgid "Delete this connection"
-msgstr "Deze connectie verwijderen"
-
-#: ../../Zotlabs/Module/Connedit.php:655 ../../include/widgets.php:529
-msgid "Me"
-msgstr "Ik"
-
-#: ../../Zotlabs/Module/Connedit.php:656 ../../include/widgets.php:530
-msgid "Family"
-msgstr "Familie"
-
-#: ../../Zotlabs/Module/Connedit.php:657
-#: ../../Zotlabs/Module/Settings/Channel.php:61
-#: ../../Zotlabs/Module/Settings/Channel.php:65
-#: ../../Zotlabs/Module/Settings/Channel.php:66
-#: ../../Zotlabs/Module/Settings/Channel.php:69
-#: ../../Zotlabs/Module/Settings/Channel.php:80
-#: ../../include/selectors.php:123 ../../include/channel.php:402
-#: ../../include/channel.php:403 ../../include/channel.php:410
-#: ../../include/widgets.php:531
-msgid "Friends"
-msgstr "Vrienden"
-
-#: ../../Zotlabs/Module/Connedit.php:658 ../../include/widgets.php:532
-msgid "Acquaintances"
-msgstr "Kennissen"
-
-#: ../../Zotlabs/Module/Connedit.php:659
-#: ../../Zotlabs/Module/Connections.php:92
-#: ../../Zotlabs/Module/Connections.php:107 ../../include/widgets.php:533
-msgid "All"
-msgstr "Alles"
-
-#: ../../Zotlabs/Module/Connedit.php:716
-msgid "Approve this connection"
-msgstr "Deze connectie accepteren"
-
-#: ../../Zotlabs/Module/Connedit.php:716
-msgid "Accept connection to allow communication"
-msgstr "Keur deze connectie goed om communicatie toe te staan"
-
-#: ../../Zotlabs/Module/Connedit.php:721
-msgid "Set Affinity"
-msgstr "Verwantschapsfilter instellen"
-
-#: ../../Zotlabs/Module/Connedit.php:724
-msgid "Set Profile"
-msgstr "Profiel instellen"
-
-#: ../../Zotlabs/Module/Connedit.php:727
-msgid "Set Affinity & Profile"
-msgstr "Verwantschapsfilter en profiel instellen"
-
-#: ../../Zotlabs/Module/Connedit.php:776
-msgid "none"
-msgstr "geen"
-
-#: ../../Zotlabs/Module/Connedit.php:780 ../../include/widgets.php:656
-msgid "Connection Default Permissions"
-msgstr "Standaard permissies voor connecties"
+msgid "Warning: Database versions differ by %1$d updates."
+msgstr "Waarschuwing: database-versies lopen %1$d updates achter."
-#: ../../Zotlabs/Module/Connedit.php:780 ../../include/items.php:3909
+#: ../../Zotlabs/Module/Import.php:134
#, php-format
-msgid "Connection: %s"
-msgstr "Connectie: %s"
-
-#: ../../Zotlabs/Module/Connedit.php:781
-msgid "Apply these permissions automatically"
-msgstr "Deze permissies automatisch toepassen"
-
-#: ../../Zotlabs/Module/Connedit.php:781
-msgid "Connection requests will be approved without your interaction"
-msgstr "Connectieverzoeken zullen automatisch worden geaccepteerd"
-
-#: ../../Zotlabs/Module/Connedit.php:784
-msgid "This connection's primary address is"
-msgstr "Het primaire kanaaladres van deze connectie is"
-
-#: ../../Zotlabs/Module/Connedit.php:785
-msgid "Available locations:"
-msgstr "Beschikbare locaties:"
-
-#: ../../Zotlabs/Module/Connedit.php:789
-msgid ""
-"The permissions indicated on this page will be applied to all new "
-"connections."
-msgstr "Permissies die op deze pagina staan vermeld worden op alle nieuwe connecties toegepast."
-
-#: ../../Zotlabs/Module/Connedit.php:790
-msgid "Connection Tools"
-msgstr "Hulpmiddelen"
-
-#: ../../Zotlabs/Module/Connedit.php:792
-msgid "Slide to adjust your degree of friendship"
-msgstr "Schuif om te bepalen hoe goed je iemand kent en/of mag"
-
-#: ../../Zotlabs/Module/Connedit.php:793 ../../Zotlabs/Module/Rate.php:155
-#: ../../include/js_strings.php:20
-msgid "Rating"
-msgstr "Beoordeling"
+msgid "Your service plan only allows %d channels."
+msgstr "Jouw abonnement staat maar %d kanalen toe."
-#: ../../Zotlabs/Module/Connedit.php:794
-msgid "Slide to adjust your rating"
-msgstr "Gebruik de schuif om je beoordeling te geven"
+#: ../../Zotlabs/Module/Import.php:149
+msgid "No channel. Import failed."
+msgstr "Geen kanaal. Importeren mislukt."
-#: ../../Zotlabs/Module/Connedit.php:795 ../../Zotlabs/Module/Connedit.php:800
-msgid "Optionally explain your rating"
-msgstr "Verklaar jouw beoordeling (niet verplicht)"
+#: ../../Zotlabs/Module/Import.php:467
+#: ../../extend/addon/addon/diaspora/import_diaspora.php:142
+msgid "Import completed."
+msgstr "Import voltooid."
-#: ../../Zotlabs/Module/Connedit.php:797
-msgid "Custom Filter"
-msgstr "Berichtenfilter"
+#: ../../Zotlabs/Module/Import.php:488
+msgid "You must be logged in to use this feature."
+msgstr "Je moet ingelogd zijn om dit onderdeel te kunnen gebruiken."
-#: ../../Zotlabs/Module/Connedit.php:798
-msgid "Only import posts with this text"
-msgstr "Importeer alleen berichten met deze tekst"
+#: ../../Zotlabs/Module/Import.php:493
+msgid "Import Channel"
+msgstr "Kanaal importeren"
-#: ../../Zotlabs/Module/Connedit.php:798 ../../Zotlabs/Module/Connedit.php:799
+#: ../../Zotlabs/Module/Import.php:494
msgid ""
-"words one per line or #tags or /patterns/ or lang=xx, leave blank to import "
-"all posts"
-msgstr "woorden (één per regel), #tags, /regex/ of talen (lang=iso639-1) - laat leeg om alle berichten te importeren"
+"Use this form to import an existing channel from a different server/hub. You"
+" may retrieve the channel identity from the old server/hub via the network "
+"or provide an export file."
+msgstr "Gebruik dit formulier om een bestaand kanaal te importeren van een andere hub. Je kan de kanaal-identiteit van de oude hub via het netwerk ontvangen of een exportbestand verstrekken."
-#: ../../Zotlabs/Module/Connedit.php:799
-msgid "Do not import posts with this text"
-msgstr "Importeer geen berichten met deze tekst"
+#: ../../Zotlabs/Module/Import.php:495
+#: ../../Zotlabs/Module/Import_items.php:121
+msgid "File to Upload"
+msgstr "Bestand om te uploaden"
-#: ../../Zotlabs/Module/Connedit.php:801
-msgid "This information is public!"
-msgstr "Deze informatie is openbaar!"
+#: ../../Zotlabs/Module/Import.php:496
+msgid "Or provide the old server/hub details"
+msgstr "Of vul de gegevens van de oude hub in"
-#: ../../Zotlabs/Module/Connedit.php:806
-msgid "Connection Pending Approval"
-msgstr "Connectie moet nog geaccepteerd worden"
+#: ../../Zotlabs/Module/Import.php:497
+msgid "Your old identity address (xyz@example.com)"
+msgstr "Jouw oude kanaaladres (xyz@example.com)"
-#: ../../Zotlabs/Module/Connedit.php:809
-#: ../../Zotlabs/Module/Settings/Tokens.php:163
-msgid "inherited"
-msgstr "geërfd"
+#: ../../Zotlabs/Module/Import.php:498
+msgid "Your old login email address"
+msgstr "Het e-mailadres van je oude account"
-#: ../../Zotlabs/Module/Connedit.php:810 ../../Zotlabs/Module/Locs.php:121
-#: ../../Zotlabs/Module/Connect.php:98
-#: ../../Zotlabs/Module/Admin/Features.php:66
-#: ../../Zotlabs/Module/Admin/Logs.php:84
-#: ../../Zotlabs/Module/Admin/Plugins.php:429
-#: ../../Zotlabs/Module/Admin/Profs.php:157
-#: ../../Zotlabs/Module/Admin/Security.php:104
-#: ../../Zotlabs/Module/Admin/Themes.php:156
-#: ../../Zotlabs/Module/Admin/Account_edit.php:74
-#: ../../Zotlabs/Module/Admin/Accounts.php:166
-#: ../../Zotlabs/Module/Admin/Channels.php:147
-#: ../../Zotlabs/Module/Admin/Site.php:260 ../../Zotlabs/Module/Appman.php:127
-#: ../../Zotlabs/Module/Filestorage.php:165 ../../Zotlabs/Module/Mail.php:412
-#: ../../Zotlabs/Module/Import_items.php:122
-#: ../../Zotlabs/Module/Invite.php:149 ../../Zotlabs/Module/Group.php:85
-#: ../../Zotlabs/Module/Mitem.php:243 ../../Zotlabs/Module/Mood.php:139
-#: ../../Zotlabs/Module/Photos.php:668 ../../Zotlabs/Module/Photos.php:1058
-#: ../../Zotlabs/Module/Photos.php:1098 ../../Zotlabs/Module/Photos.php:1216
-#: ../../Zotlabs/Module/Setup.php:309 ../../Zotlabs/Module/Setup.php:357
-#: ../../Zotlabs/Module/Poke.php:186 ../../Zotlabs/Module/Profiles.php:681
-#: ../../Zotlabs/Module/Pconfig.php:107 ../../Zotlabs/Module/Rate.php:166
-#: ../../Zotlabs/Module/Pdledit.php:74 ../../Zotlabs/Module/Cal.php:342
-#: ../../Zotlabs/Module/Wiki.php:148 ../../Zotlabs/Module/Sources.php:114
-#: ../../Zotlabs/Module/Sources.php:149
-#: ../../Zotlabs/Module/Settings/Features.php:47
-#: ../../Zotlabs/Module/Settings/Oauth.php:87
-#: ../../Zotlabs/Module/Settings/Tokens.php:167
-#: ../../Zotlabs/Module/Settings/Account.php:118
-#: ../../Zotlabs/Module/Settings/Channel.php:455
-#: ../../Zotlabs/Module/Settings/Display.php:196
-#: ../../Zotlabs/Module/Thing.php:320 ../../Zotlabs/Module/Thing.php:370
-#: ../../Zotlabs/Module/Import.php:543 ../../Zotlabs/Module/Chat.php:196
-#: ../../Zotlabs/Module/Chat.php:241 ../../Zotlabs/Module/Xchan.php:15
-#: ../../Zotlabs/Module/Events.php:484 ../../Zotlabs/Lib/ThreadItem.php:729
-#: ../../extend/addon/addon/chords/Mod_Chords.php:60
-#: ../../extend/addon/addon/diaspora/diaspora.php:710
-#: ../../extend/addon/addon/dwpost/dwpost.php:89
-#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:124
-#: ../../extend/addon/addon/friendica/friendica.php:128
-#: ../../extend/addon/addon/frphotos/frphotos.php:96
-#: ../../extend/addon/addon/gnusoc/gnusoc.php:129
-#: ../../extend/addon/addon/hubwall/hubwall.php:95
-#: ../../extend/addon/addon/ijpost/ijpost.php:89
-#: ../../extend/addon/addon/irc/irc.php:53
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:371
-#: ../../extend/addon/addon/libertree/libertree.php:85
-#: ../../extend/addon/addon/ljpost/ljpost.php:86
-#: ../../extend/addon/addon/logrot/logrot.php:35
-#: ../../extend/addon/addon/mailhost/mailhost.php:40
-#: ../../extend/addon/addon/nofed/nofed.php:80
-#: ../../extend/addon/addon/nsabait/nsabait.php:161
-#: ../../extend/addon/addon/nsfw/nsfw.php:92
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:52
-#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:168
-#: ../../extend/addon/addon/pageheader/pageheader.php:48
-#: ../../extend/addon/addon/piwik/piwik.php:95
-#: ../../extend/addon/addon/planets/planets.php:157
-#: ../../extend/addon/addon/pumpio/pumpio.php:237
-#: ../../extend/addon/addon/rainbowtag/rainbowtag.php:85
-#: ../../extend/addon/addon/redfiles/redfiles.php:124
-#: ../../extend/addon/addon/redphotos/redphotos.php:136
-#: ../../extend/addon/addon/redred/redred.php:119
-#: ../../extend/addon/addon/rtof/rtof.php:101
-#: ../../extend/addon/addon/skeleton/skeleton.php:65
-#: ../../extend/addon/addon/smileybutton/smileybutton.php:281
-#: ../../extend/addon/addon/startpage/startpage.php:113
-#: ../../extend/addon/addon/statusnet/statusnet.php:322
-#: ../../extend/addon/addon/statusnet/statusnet.php:380
-#: ../../extend/addon/addon/statusnet/statusnet.php:432
-#: ../../extend/addon/addon/statusnet/statusnet.php:899
-#: ../../extend/addon/addon/superblock/superblock.php:118
-#: ../../extend/addon/addon/twitter/twitter.php:217
-#: ../../extend/addon/addon/twitter/twitter.php:259
-#: ../../extend/addon/addon/visage/visage.php:170
-#: ../../extend/addon/addon/wppost/wppost.php:113
-#: ../../extend/addon/addon/xmpp/xmpp.php:69
-#: ../../extend/addon/addon/cdav/cdav.php:246
-#: ../../extend/addon/addon/likebanner/likebanner.php:57
-#: ../../extend/addon/addon/mailtest/mailtest.php:100
-#: ../../include/js_strings.php:22 ../../include/widgets.php:796
-#: ../../view/theme/redbasic/php/config.php:106
-msgid "Submit"
-msgstr "Opslaan"
+#: ../../Zotlabs/Module/Import.php:499
+msgid "Your old login password"
+msgstr "Wachtwoord van jouw oude account"
-#: ../../Zotlabs/Module/Connedit.php:811
-#, php-format
+#: ../../Zotlabs/Module/Import.php:500
msgid ""
-"Please choose the profile you would like to display to %s when viewing your "
-"profile securely."
-msgstr "Kies het profiel dat je aan %s wil tonen wanneer hij/zij ingelogd jouw profiel wil bekijken."
-
-#: ../../Zotlabs/Module/Connedit.php:813
-#: ../../Zotlabs/Module/Settings/Tokens.php:160
-msgid "Their Settings"
-msgstr "Hun instellingen"
+"For either option, please choose whether to make this hub your new primary "
+"address, or whether your old location should continue this role. You will be"
+" able to post from either location, but only one can be marked as the "
+"primary location for files, photos, and media."
+msgstr "Voor elke optie geldt dat je moet kiezen of je jouw primaire kanaaladres op deze hub wil instellen of dat jouw oude hub deze rol blijft vervullen."
-#: ../../Zotlabs/Module/Connedit.php:814
-#: ../../Zotlabs/Module/Settings/Tokens.php:161
-msgid "My Settings"
-msgstr "Mijn instellingen"
+#: ../../Zotlabs/Module/Import.php:501
+msgid "Make this hub my primary location"
+msgstr "Stel deze hub als mijn primaire locatie in"
-#: ../../Zotlabs/Module/Connedit.php:816
-#: ../../Zotlabs/Module/Settings/Tokens.php:165
-msgid "Individual Permissions"
-msgstr "Individuele permissies"
+#: ../../Zotlabs/Module/Import.php:502
+msgid "Move this channel (disable all previous locations)"
+msgstr "Verplaats dit kanaal (schakelt alle voormalige locaties uit)"
-#: ../../Zotlabs/Module/Connedit.php:817
-#: ../../Zotlabs/Module/Settings/Tokens.php:166
-msgid ""
-"Some permissions may be inherited from your channel's <a "
-"href=\"settings\"><strong>privacy settings</strong></a>, which have higher "
-"priority than individual settings. You can <strong>not</strong> change those"
-" settings here."
-msgstr "Sommige permissies worden mogelijk overgeërfd van de <a href=\"settings\">privacy-instellingen</a> van jouw kanaal, die een hogere prioriteit hebben dan deze individuele instellingen. Je kan je deze overgeërfde permissies hier <strong>niet</strong> veranderen."
+#: ../../Zotlabs/Module/Import.php:503
+msgid "Import a few months of posts if possible (limited by available memory"
+msgstr "Importeer enkele maanden aan berichten wanneer mogelijk (afhankelijk van hoeveelheid geheugen hub)"
-#: ../../Zotlabs/Module/Connedit.php:818
+#: ../../Zotlabs/Module/Import.php:504
msgid ""
-"Some permissions may be inherited from your channel's <a "
-"href=\"settings\"><strong>privacy settings</strong></a>, which have higher "
-"priority than individual settings. You can change those settings here but "
-"they wont have any impact unless the inherited setting changes."
-msgstr "Sommige permissies worden mogelijk overgeërfd van de <a href=\"settings\">privacy-instellingen</a> van jouw kanaal, die een hogere prioriteit hebben dan deze individuele permissies. Je kan de permissies hier veranderen, maar die hebben geen effect, tenzij de overgeërfde permissies worden veranderd. "
-
-#: ../../Zotlabs/Module/Connedit.php:819
-msgid "Last update:"
-msgstr "Laatste wijziging:"
-
-#: ../../Zotlabs/Module/Dreport.php:45
-msgid "Invalid message"
-msgstr "Ongeldig bericht"
-
-#: ../../Zotlabs/Module/Dreport.php:78
-msgid "no results"
-msgstr "geen resultaten"
-
-#: ../../Zotlabs/Module/Dreport.php:93
-msgid "channel sync processed"
-msgstr "kanaalsync verwerkt"
-
-#: ../../Zotlabs/Module/Dreport.php:97
-msgid "queued"
-msgstr "in wachtrij"
-
-#: ../../Zotlabs/Module/Dreport.php:101
-msgid "posted"
-msgstr "verstuurd"
-
-#: ../../Zotlabs/Module/Dreport.php:105
-msgid "accepted for delivery"
-msgstr "geaccepteerd om afgeleverd te worden"
+"This process may take several minutes to complete. Please submit the form "
+"only once and leave this page open until finished."
+msgstr "Dit proces kan enkele minuten in beslag nemen. Klik maar één keer op opslaan en verlaat deze pagina niet alvorens het proces is voltooid."
-#: ../../Zotlabs/Module/Dreport.php:109
-msgid "updated"
-msgstr "geüpdatet"
+#: ../../Zotlabs/Module/Chatsvc.php:131
+msgid "Away"
+msgstr "Afwezig"
-#: ../../Zotlabs/Module/Dreport.php:112
-msgid "update ignored"
-msgstr "update genegeerd"
+#: ../../Zotlabs/Module/Chatsvc.php:136
+msgid "Online"
+msgstr "Online"
-#: ../../Zotlabs/Module/Dreport.php:115
-msgid "permission denied"
-msgstr "toegang geweigerd"
+#: ../../Zotlabs/Module/Help.php:23
+msgid "Documentation Search"
+msgstr "Zoek documentatie"
-#: ../../Zotlabs/Module/Dreport.php:119
-msgid "recipient not found"
-msgstr "ontvanger niet gevonden"
+#: ../../Zotlabs/Module/Help.php:80 ../../include/conversation.php:1827
+msgid "About"
+msgstr "Over"
-#: ../../Zotlabs/Module/Dreport.php:122
-msgid "mail recalled"
-msgstr "Privébericht ingetrokken"
+#: ../../Zotlabs/Module/Help.php:81 ../../Zotlabs/Module/Group.php:197
+msgid "Members"
+msgstr "Kanalen"
-#: ../../Zotlabs/Module/Dreport.php:125
-msgid "duplicate mail received"
-msgstr "dubbel privébericht ontvangen"
+#: ../../Zotlabs/Module/Help.php:82
+msgid "Administrators"
+msgstr "Beheerders"
-#: ../../Zotlabs/Module/Dreport.php:128
-msgid "mail delivered"
-msgstr "privébericht afgeleverd"
+#: ../../Zotlabs/Module/Help.php:83
+msgid "Developers"
+msgstr "Ontwikkelaars"
-#: ../../Zotlabs/Module/Dreport.php:148
-#, php-format
-msgid "Delivery report for %1$s"
-msgstr "Afleveringsrapport voor %1$s"
+#: ../../Zotlabs/Module/Help.php:84
+msgid "Tutorials"
+msgstr "Zelfstudie"
-#: ../../Zotlabs/Module/Dreport.php:151
-msgid "Options"
-msgstr "Opties"
+#: ../../Zotlabs/Module/Help.php:93
+msgid "$Projectname Documentation"
+msgstr "$Projectname-documentatie"
-#: ../../Zotlabs/Module/Dreport.php:152
-msgid "Redeliver"
-msgstr "Opnieuw afleveren"
+#: ../../Zotlabs/Module/Help.php:94
+msgid "Contents"
+msgstr "Inhoud"
#: ../../Zotlabs/Module/Bookmarks.php:53
msgid "Bookmark added"
@@ -1230,81 +940,6 @@ msgstr "Mijn bladwijzers"
msgid "My Connections Bookmarks"
msgstr "Bladwijzers van mijn connecties"
-#: ../../Zotlabs/Module/Acl.php:313
-msgid "network"
-msgstr "netwerk"
-
-#: ../../Zotlabs/Module/Acl.php:323
-msgid "RSS"
-msgstr "RSS"
-
-#: ../../Zotlabs/Module/Locs.php:25 ../../Zotlabs/Module/Locs.php:54
-msgid "Location not found."
-msgstr "Locatie niet gevonden."
-
-#: ../../Zotlabs/Module/Locs.php:62
-msgid "Location lookup failed."
-msgstr "Opzoeken locatie mislukt"
-
-#: ../../Zotlabs/Module/Locs.php:66
-msgid ""
-"Please select another location to become primary before removing the primary"
-" location."
-msgstr "Kies eerst een andere primaire locatie alvorens de huidige primaire locatie te verwijderen."
-
-#: ../../Zotlabs/Module/Locs.php:95
-msgid "Syncing locations"
-msgstr "Locaties synchronizeren"
-
-#: ../../Zotlabs/Module/Locs.php:105
-msgid "No locations found."
-msgstr "Geen locaties gevonden."
-
-#: ../../Zotlabs/Module/Locs.php:116
-msgid "Manage Channel Locations"
-msgstr "Kanaallocaties beheren"
-
-#: ../../Zotlabs/Module/Locs.php:117 ../../Zotlabs/Module/Pubsites.php:51
-#: ../../Zotlabs/Module/Profiles.php:471 ../../Zotlabs/Module/Profiles.php:692
-#: ../../Zotlabs/Module/Events.php:468
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:839
-#: ../../include/js_strings.php:25
-msgid "Location"
-msgstr "Locatie"
-
-#: ../../Zotlabs/Module/Locs.php:118
-#: ../../Zotlabs/Module/Admin/Channels.php:160
-#: ../../Zotlabs/Module/Profiles.php:464
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1143
-msgid "Address"
-msgstr "Adres"
-
-#: ../../Zotlabs/Module/Locs.php:119
-msgid "Primary"
-msgstr "Primair"
-
-#: ../../Zotlabs/Module/Locs.php:120 ../../Zotlabs/Module/Menu.php:113
-msgid "Drop"
-msgstr "Verwijderen"
-
-#: ../../Zotlabs/Module/Locs.php:122
-msgid "Sync Now"
-msgstr "Nu synchroniseren"
-
-#: ../../Zotlabs/Module/Locs.php:123
-msgid "Please wait several minutes between consecutive operations."
-msgstr "Wacht enkele minuten tussen opeenvolgende handelingen."
-
-#: ../../Zotlabs/Module/Locs.php:124
-msgid ""
-"When possible, drop a location by logging into that website/hub and removing"
-" your channel."
-msgstr "Wij adviseren, wanneer dit (nog) mogelijk is, de locatie te verwijderen door op de hub van de kloon in te loggen en het kanaal daar te verwijderen."
-
-#: ../../Zotlabs/Module/Locs.php:125
-msgid "Use this form to drop the location if the hub is no longer operating."
-msgstr "Gebruik dit formulier om de locatie te verwijderen wanneer de hub van de kloon niet meer operationeel is."
-
#: ../../Zotlabs/Module/Connect.php:61 ../../Zotlabs/Module/Connect.php:109
msgid "Continue"
msgstr "Ga verder"
@@ -1348,12 +983,128 @@ msgstr "(Er zijn geen speciale voorwaarden en aanwijzingen door de kanaal-eigena
msgid "Restricted or Premium Channel"
msgstr "Beperkt of premiumkanaal"
+#: ../../Zotlabs/Module/Admin.php:60
+#: ../../Zotlabs/Module/Admin/Plugins.php:259
+#: ../../Zotlabs/Module/Admin/Themes.php:72
+#: ../../Zotlabs/Module/Filestorage.php:32 ../../Zotlabs/Module/Display.php:35
+#: ../../Zotlabs/Module/Viewsrc.php:24 ../../Zotlabs/Module/Thing.php:89
+#: ../../include/items.php:3368
+msgid "Item not found."
+msgstr "Item niet gevonden."
+
+#: ../../Zotlabs/Module/Admin.php:94
+msgid "# Accounts"
+msgstr "# accounts"
+
+#: ../../Zotlabs/Module/Admin.php:95
+msgid "# blocked accounts"
+msgstr "# geblokkeerde accounts"
+
+#: ../../Zotlabs/Module/Admin.php:96
+msgid "# expired accounts"
+msgstr "# verlopen accounts"
+
+#: ../../Zotlabs/Module/Admin.php:97
+msgid "# expiring accounts"
+msgstr "# accounts die nog moeten verlopen"
+
+#: ../../Zotlabs/Module/Admin.php:108
+msgid "# Channels"
+msgstr "# Kanalen"
+
+#: ../../Zotlabs/Module/Admin.php:109
+msgid "# primary"
+msgstr "# primair"
+
+#: ../../Zotlabs/Module/Admin.php:110
+msgid "# clones"
+msgstr "# klonen"
+
+#: ../../Zotlabs/Module/Admin.php:116
+msgid "Message queues"
+msgstr "Berichtenwachtrij"
+
+#: ../../Zotlabs/Module/Admin.php:133
+msgid "Your software should be updated"
+msgstr "Jouw software moet worden bijgewerkt "
+
+#: ../../Zotlabs/Module/Admin.php:137 ../../Zotlabs/Module/Admin/Logs.php:82
+#: ../../Zotlabs/Module/Admin/Security.php:86
+#: ../../Zotlabs/Module/Admin/Accounts.php:164
+#: ../../Zotlabs/Module/Admin/Channels.php:145
+#: ../../Zotlabs/Module/Admin/Site.php:266
+#: ../../Zotlabs/Module/Admin/Plugins.php:341
+#: ../../Zotlabs/Module/Admin/Plugins.php:436
+#: ../../Zotlabs/Module/Admin/Themes.php:122
+#: ../../Zotlabs/Module/Admin/Themes.php:156
+msgid "Administration"
+msgstr "Beheer"
+
+#: ../../Zotlabs/Module/Admin.php:138
+msgid "Summary"
+msgstr "Samenvatting"
+
+#: ../../Zotlabs/Module/Admin.php:141
+msgid "Registered accounts"
+msgstr "Geregistreerde accounts"
+
+#: ../../Zotlabs/Module/Admin.php:142
+msgid "Pending registrations"
+msgstr "Accounts die op goedkeuring wachten"
+
+#: ../../Zotlabs/Module/Admin.php:143
+msgid "Registered channels"
+msgstr "Geregistreerde kanalen"
+
+#: ../../Zotlabs/Module/Admin.php:144
+msgid "Active plugins"
+msgstr "Ingeschakelde plugins"
+
+#: ../../Zotlabs/Module/Admin.php:145
+msgid "Version"
+msgstr "Versie"
+
+#: ../../Zotlabs/Module/Admin.php:146
+msgid "Repository version (master)"
+msgstr "Versie repository (master)"
+
+#: ../../Zotlabs/Module/Admin.php:147
+msgid "Repository version (dev)"
+msgstr "Versie repository (dev)"
+
+#: ../../Zotlabs/Module/Editblock.php:79 ../../Zotlabs/Module/Editblock.php:95
+#: ../../Zotlabs/Module/Editlayout.php:79
+#: ../../Zotlabs/Module/Editwebpage.php:80
+#: ../../Zotlabs/Module/Editpost.php:24
+msgid "Item not found"
+msgstr "Item niet gevonden"
+
+#: ../../Zotlabs/Module/Editblock.php:108 ../../Zotlabs/Module/Blocks.php:97
+#: ../../Zotlabs/Module/Blocks.php:155
+msgid "Block Name"
+msgstr "Bloknaam"
+
+#: ../../Zotlabs/Module/Editblock.php:111
+#: ../../Zotlabs/Module/Editwebpage.php:146 ../../Zotlabs/Module/Mail.php:287
+#: ../../Zotlabs/Module/Mail.php:412 ../../Zotlabs/Module/Chat.php:205
+#: ../../include/conversation.php:1295
+msgid "Insert web link"
+msgstr "Weblink invoegen"
+
+#: ../../Zotlabs/Module/Editblock.php:124 ../../include/conversation.php:1406
+msgid "Title (optional)"
+msgstr "Titel (niet verplicht)"
+
+#: ../../Zotlabs/Module/Editblock.php:133
+msgid "Edit Block"
+msgstr "Blok bewerken"
+
#: ../../Zotlabs/Module/Page.php:40 ../../Zotlabs/Module/Block.php:31
msgid "Invalid item."
msgstr "Ongeldig item."
-#: ../../Zotlabs/Module/Page.php:56 ../../Zotlabs/Module/Chanview.php:96
-#: ../../Zotlabs/Module/Block.php:43 ../../Zotlabs/Module/Cal.php:62
+#: ../../Zotlabs/Module/Page.php:56 ../../Zotlabs/Module/Block.php:43
+#: ../../Zotlabs/Module/Cal.php:62 ../../Zotlabs/Module/Chanview.php:96
#: ../../Zotlabs/Module/Wall_upload.php:31
msgid "Channel not found."
msgstr "Kanaal niet gevonden."
@@ -1378,91 +1129,67 @@ msgstr "- kies map -"
#: ../../Zotlabs/Module/Filer.php:53 ../../Zotlabs/Module/Admin/Profs.php:74
#: ../../Zotlabs/Module/Admin/Profs.php:94 ../../Zotlabs/Module/Rbmark.php:32
-#: ../../Zotlabs/Module/Rbmark.php:104 ../../include/text.php:987
-#: ../../include/text.php:999 ../../include/widgets.php:201
+#: ../../Zotlabs/Module/Rbmark.php:104 ../../include/widgets.php:188
+#: ../../include/text.php:1011 ../../include/text.php:1023
msgid "Save"
msgstr "Opslaan"
-#: ../../Zotlabs/Module/Manage.php:136
-#: ../../Zotlabs/Module/New_channel.php:121
-#, php-format
-msgid "You have created %1$.0f of %2$.0f allowed channels."
-msgstr "Je hebt %1$.0f van totaal %2$.0f toegestane kanalen aangemaakt."
-
-#: ../../Zotlabs/Module/Manage.php:143
-msgid "Create a new channel"
-msgstr "Nieuw kanaal aanmaken"
-
-#: ../../Zotlabs/Module/Manage.php:143 ../../Zotlabs/Module/Profiles.php:772
-#: ../../Zotlabs/Module/Wiki.php:147 ../../Zotlabs/Module/Chat.php:255
-msgid "Create New"
-msgstr "Nieuwe aanmaken"
-
-#: ../../Zotlabs/Module/Manage.php:164 ../../Zotlabs/Lib/Apps.php:216
-#: ../../include/nav.php:209
-msgid "Channel Manager"
-msgstr "Kanaalbeheer"
-
-#: ../../Zotlabs/Module/Manage.php:165
-msgid "Current Channel"
-msgstr "Huidig kanaal"
-
-#: ../../Zotlabs/Module/Manage.php:167
-msgid "Switch to one of your channels by selecting it."
-msgstr "Activeer een van jouw andere kanalen door er op te klikken."
-
-#: ../../Zotlabs/Module/Manage.php:168
-msgid "Default Channel"
-msgstr "Standaardkanaal"
+#: ../../Zotlabs/Module/Ping.php:254
+msgid "sent you a private message"
+msgstr "stuurde jou een privébericht"
-#: ../../Zotlabs/Module/Manage.php:169
-msgid "Make Default"
-msgstr "Als standaard instellen"
+#: ../../Zotlabs/Module/Ping.php:302
+msgid "added your channel"
+msgstr "voegde jouw kanaal toe"
-#: ../../Zotlabs/Module/Manage.php:172
-#, php-format
-msgid "%d new messages"
-msgstr "%d nieuwe berichten"
+#: ../../Zotlabs/Module/Ping.php:312
+msgid "g A l F d"
+msgstr "G:i, l d F"
-#: ../../Zotlabs/Module/Manage.php:173
-#, php-format
-msgid "%d new introductions"
-msgstr "%d nieuwe connectieverzoeken"
+#: ../../Zotlabs/Module/Ping.php:330
+msgid "[today]"
+msgstr "[vandaag]"
-#: ../../Zotlabs/Module/Manage.php:175
-msgid "Delegated Channel"
-msgstr "Uitbesteed kanaal"
+#: ../../Zotlabs/Module/Ping.php:339
+msgid "posted an event"
+msgstr "plaatste een gebeurtenis"
#: ../../Zotlabs/Module/Connections.php:56
#: ../../Zotlabs/Module/Connections.php:161
-#: ../../Zotlabs/Module/Connections.php:242
+#: ../../Zotlabs/Module/Connections.php:250
msgid "Blocked"
msgstr "Geblokkeerd"
#: ../../Zotlabs/Module/Connections.php:61
#: ../../Zotlabs/Module/Connections.php:168
-#: ../../Zotlabs/Module/Connections.php:241
+#: ../../Zotlabs/Module/Connections.php:249
msgid "Ignored"
msgstr "Genegeerd"
#: ../../Zotlabs/Module/Connections.php:66
#: ../../Zotlabs/Module/Connections.php:182
-#: ../../Zotlabs/Module/Connections.php:240
+#: ../../Zotlabs/Module/Connections.php:248
msgid "Hidden"
msgstr "Verborgen"
#: ../../Zotlabs/Module/Connections.php:71
#: ../../Zotlabs/Module/Connections.php:175
-#: ../../Zotlabs/Module/Connections.php:239
+#: ../../Zotlabs/Module/Connections.php:247
msgid "Archived"
msgstr "Gearchiveerd"
#: ../../Zotlabs/Module/Connections.php:76
#: ../../Zotlabs/Module/Connections.php:86 ../../Zotlabs/Module/Menu.php:116
-#: ../../include/conversation.php:1576
+#: ../../include/conversation.php:1724
msgid "New"
msgstr "Nieuw"
+#: ../../Zotlabs/Module/Connections.php:92
+#: ../../Zotlabs/Module/Connections.php:107
+#: ../../Zotlabs/Module/Connedit.php:720 ../../include/widgets.php:530
+msgid "All"
+msgstr "Alles"
+
#: ../../Zotlabs/Module/Connections.php:138
msgid "New Connections"
msgstr "Nieuwe connecties"
@@ -1472,7 +1199,7 @@ msgid "Show pending (new) connections"
msgstr "Nog te accepteren (nieuwe) connecties weergeven"
#: ../../Zotlabs/Module/Connections.php:145
-#: ../../Zotlabs/Module/Profperm.php:144
+#: ../../Zotlabs/Module/Profperm.php:140
msgid "All Connections"
msgstr "Alle connecties"
@@ -1496,79 +1223,88 @@ msgstr "Toon alleen gearchiveerde connecties"
msgid "Only show hidden connections"
msgstr "Toon alleen verborgen connecties"
-#: ../../Zotlabs/Module/Connections.php:238
+#: ../../Zotlabs/Module/Connections.php:246
msgid "Pending approval"
msgstr "Moet nog geaccepteerd worden"
-#: ../../Zotlabs/Module/Connections.php:254
+#: ../../Zotlabs/Module/Connections.php:262
#, php-format
msgid "%1$s [%2$s]"
msgstr "%1$s [%2$s]"
-#: ../../Zotlabs/Module/Connections.php:255
+#: ../../Zotlabs/Module/Connections.php:263
msgid "Edit connection"
msgstr "Connectie bewerken"
-#: ../../Zotlabs/Module/Connections.php:256
+#: ../../Zotlabs/Module/Connections.php:264
msgid "Delete connection"
msgstr "Connectie verwijderen"
-#: ../../Zotlabs/Module/Connections.php:265
+#: ../../Zotlabs/Module/Connections.php:273
msgid "Channel address"
msgstr "Kanaaladres"
-#: ../../Zotlabs/Module/Connections.php:267
+#: ../../Zotlabs/Module/Connections.php:275
msgid "Network"
msgstr "Netwerk"
-#: ../../Zotlabs/Module/Connections.php:270
+#: ../../Zotlabs/Module/Connections.php:278
+msgid "Call"
+msgstr "Bellen"
+
+#: ../../Zotlabs/Module/Connections.php:280
msgid "Status"
msgstr "Status"
-#: ../../Zotlabs/Module/Connections.php:272
+#: ../../Zotlabs/Module/Connections.php:282
msgid "Connected"
msgstr "Verbonden"
-#: ../../Zotlabs/Module/Connections.php:274
+#: ../../Zotlabs/Module/Connections.php:284
msgid "Approve connection"
msgstr "Connectie accepteren"
-#: ../../Zotlabs/Module/Connections.php:275
+#: ../../Zotlabs/Module/Connections.php:285
#: ../../Zotlabs/Module/Admin/Accounts.php:171
msgid "Approve"
msgstr "Goedkeuren"
-#: ../../Zotlabs/Module/Connections.php:276
+#: ../../Zotlabs/Module/Connections.php:286
msgid "Ignore connection"
msgstr "Connectie negeren"
-#: ../../Zotlabs/Module/Connections.php:278
+#: ../../Zotlabs/Module/Connections.php:287
+#: ../../Zotlabs/Module/Connedit.php:637
+msgid "Ignore"
+msgstr "Negeren"
+
+#: ../../Zotlabs/Module/Connections.php:288
msgid "Recent activity"
msgstr "Recente activiteit"
-#: ../../Zotlabs/Module/Connections.php:302 ../../Zotlabs/Lib/Apps.php:211
-#: ../../include/nav.php:189 ../../include/text.php:916
+#: ../../Zotlabs/Module/Connections.php:312 ../../Zotlabs/Lib/Apps.php:216
+#: ../../include/nav.php:203 ../../include/text.php:940
msgid "Connections"
msgstr "Connecties"
-#: ../../Zotlabs/Module/Connections.php:306 ../../Zotlabs/Module/Search.php:44
-#: ../../Zotlabs/Lib/Apps.php:232 ../../include/nav.php:168
-#: ../../include/text.php:986 ../../include/text.php:998
-#: ../../include/acl_selectors.php:203 ../../include/widgets.php:315
+#: ../../Zotlabs/Module/Connections.php:316 ../../Zotlabs/Module/Search.php:44
+#: ../../Zotlabs/Lib/Apps.php:237 ../../include/widgets.php:302
+#: ../../include/acl_selectors.php:213 ../../include/nav.php:180
+#: ../../include/text.php:1010 ../../include/text.php:1022
msgid "Search"
msgstr "Zoeken"
-#: ../../Zotlabs/Module/Connections.php:307
+#: ../../Zotlabs/Module/Connections.php:317
msgid "Search your connections"
msgstr "Doorzoek jouw connecties"
-#: ../../Zotlabs/Module/Connections.php:308
+#: ../../Zotlabs/Module/Connections.php:318
msgid "Connections search"
msgstr "Connecties zoeken"
-#: ../../Zotlabs/Module/Connections.php:309
-#: ../../Zotlabs/Module/Directory.php:391
-#: ../../Zotlabs/Module/Directory.php:396 ../../include/contact_widgets.php:23
+#: ../../Zotlabs/Module/Connections.php:319
+#: ../../Zotlabs/Module/Directory.php:392
+#: ../../Zotlabs/Module/Directory.php:397 ../../include/contact_widgets.php:23
msgid "Find"
msgstr "Vinden"
@@ -1588,61 +1324,61 @@ msgid "Image resize failed."
msgstr "Afbeelding kon niet van grootte veranderd worden."
#: ../../Zotlabs/Module/Cover_photo.php:168
-#: ../../Zotlabs/Module/Profile_photo.php:196 ../../include/photos.php:149
+#: ../../Zotlabs/Module/Profile_photo.php:201 ../../include/photos.php:149
msgid "Unable to process image"
msgstr "Afbeelding kan niet verwerkt worden"
#: ../../Zotlabs/Module/Cover_photo.php:192
-#: ../../Zotlabs/Module/Profile_photo.php:231
+#: ../../Zotlabs/Module/Profile_photo.php:236
msgid "Image upload failed."
msgstr "Uploaden afbeelding mislukt"
#: ../../Zotlabs/Module/Cover_photo.php:210
-#: ../../Zotlabs/Module/Profile_photo.php:250
+#: ../../Zotlabs/Module/Profile_photo.php:255
msgid "Unable to process image."
msgstr "Niet in staat om afbeelding te verwerken."
-#: ../../Zotlabs/Module/Cover_photo.php:233 ../../include/items.php:4253
+#: ../../Zotlabs/Module/Cover_photo.php:233 ../../include/items.php:4278
msgid "female"
msgstr "vrouw"
-#: ../../Zotlabs/Module/Cover_photo.php:234 ../../include/items.php:4254
+#: ../../Zotlabs/Module/Cover_photo.php:234 ../../include/items.php:4279
#, php-format
msgid "%1$s updated her %2$s"
msgstr "%1$s heeft haar %2$s bijgewerkt"
-#: ../../Zotlabs/Module/Cover_photo.php:235 ../../include/items.php:4255
+#: ../../Zotlabs/Module/Cover_photo.php:235 ../../include/items.php:4280
msgid "male"
msgstr "man"
-#: ../../Zotlabs/Module/Cover_photo.php:236 ../../include/items.php:4256
+#: ../../Zotlabs/Module/Cover_photo.php:236 ../../include/items.php:4281
#, php-format
msgid "%1$s updated his %2$s"
msgstr "%1$s heeft zijn %2$s bijgewerkt"
-#: ../../Zotlabs/Module/Cover_photo.php:238 ../../include/items.php:4258
+#: ../../Zotlabs/Module/Cover_photo.php:238 ../../include/items.php:4283
#, php-format
msgid "%1$s updated their %2$s"
msgstr "De %2$s van %1$s is bijgewerkt"
-#: ../../Zotlabs/Module/Cover_photo.php:240 ../../include/channel.php:1677
+#: ../../Zotlabs/Module/Cover_photo.php:240 ../../include/channel.php:1764
msgid "cover photo"
msgstr "omslagfoto"
#: ../../Zotlabs/Module/Cover_photo.php:303
#: ../../Zotlabs/Module/Cover_photo.php:318
-#: ../../Zotlabs/Module/Profile_photo.php:311
-#: ../../Zotlabs/Module/Profile_photo.php:352
+#: ../../Zotlabs/Module/Profile_photo.php:316
+#: ../../Zotlabs/Module/Profile_photo.php:363
msgid "Photo not available."
msgstr "Foto niet beschikbaar."
#: ../../Zotlabs/Module/Cover_photo.php:354
-#: ../../Zotlabs/Module/Profile_photo.php:407
+#: ../../Zotlabs/Module/Profile_photo.php:418
msgid "Upload File:"
msgstr "Bestand uploaden:"
#: ../../Zotlabs/Module/Cover_photo.php:355
-#: ../../Zotlabs/Module/Profile_photo.php:408
+#: ../../Zotlabs/Module/Profile_photo.php:419
msgid "Select a profile:"
msgstr "Kies een profiel:"
@@ -1651,33 +1387,33 @@ msgid "Upload Cover Photo"
msgstr "Omslagfoto uploaden"
#: ../../Zotlabs/Module/Cover_photo.php:361
-#: ../../Zotlabs/Module/Profile_photo.php:416
-#: ../../Zotlabs/Module/Settings/Channel.php:399
+#: ../../Zotlabs/Module/Profile_photo.php:427
+#: ../../Zotlabs/Module/Settings/Channel.php:404
msgid "or"
msgstr "of"
#: ../../Zotlabs/Module/Cover_photo.php:361
-#: ../../Zotlabs/Module/Profile_photo.php:416
+#: ../../Zotlabs/Module/Profile_photo.php:427
msgid "skip this step"
msgstr "sla deze stap over"
#: ../../Zotlabs/Module/Cover_photo.php:361
-#: ../../Zotlabs/Module/Profile_photo.php:416
+#: ../../Zotlabs/Module/Profile_photo.php:427
msgid "select a photo from your photo albums"
msgstr "Kies een foto uit jouw fotoalbums"
#: ../../Zotlabs/Module/Cover_photo.php:377
-#: ../../Zotlabs/Module/Profile_photo.php:435
+#: ../../Zotlabs/Module/Profile_photo.php:446
msgid "Crop Image"
msgstr "Afbeelding bijsnijden"
#: ../../Zotlabs/Module/Cover_photo.php:378
-#: ../../Zotlabs/Module/Profile_photo.php:436
+#: ../../Zotlabs/Module/Profile_photo.php:447
msgid "Please adjust the image cropping for optimum viewing."
msgstr "Snij de afbeelding zo uit dat deze optimaal wordt weergegeven."
#: ../../Zotlabs/Module/Cover_photo.php:380
-#: ../../Zotlabs/Module/Profile_photo.php:438
+#: ../../Zotlabs/Module/Profile_photo.php:449
msgid "Done Editing"
msgstr "Klaar met bewerken"
@@ -1706,20 +1442,8 @@ msgstr "Beheer - Extra functies"
msgid "Log settings updated."
msgstr "Logboek-instellingen bijgewerkt."
-#: ../../Zotlabs/Module/Admin/Logs.php:82
-#: ../../Zotlabs/Module/Admin/Plugins.php:336
-#: ../../Zotlabs/Module/Admin/Plugins.php:427
-#: ../../Zotlabs/Module/Admin/Security.php:86
-#: ../../Zotlabs/Module/Admin/Themes.php:120
-#: ../../Zotlabs/Module/Admin/Themes.php:154
-#: ../../Zotlabs/Module/Admin/Accounts.php:164
-#: ../../Zotlabs/Module/Admin/Channels.php:145
-#: ../../Zotlabs/Module/Admin/Site.php:258 ../../Zotlabs/Module/Admin.php:137
-msgid "Administration"
-msgstr "Beheer"
-
-#: ../../Zotlabs/Module/Admin/Logs.php:83 ../../include/widgets.php:1588
-#: ../../include/widgets.php:1598
+#: ../../Zotlabs/Module/Admin/Logs.php:83 ../../include/widgets.php:1661
+#: ../../include/widgets.php:1671
msgid "Logs"
msgstr "Logboeken"
@@ -1745,156 +1469,6 @@ msgstr "Moet door de webserver beschrijfbaar zijn. Relatief ten opzichte van de
msgid "Log level"
msgstr "Logniveau"
-#: ../../Zotlabs/Module/Admin/Plugins.php:254
-#: ../../Zotlabs/Module/Admin/Themes.php:69
-#: ../../Zotlabs/Module/Filestorage.php:32 ../../Zotlabs/Module/Display.php:40
-#: ../../Zotlabs/Module/Admin.php:60 ../../Zotlabs/Module/Thing.php:89
-#: ../../Zotlabs/Module/Viewsrc.php:24 ../../include/items.php:3343
-msgid "Item not found."
-msgstr "Item niet gevonden."
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:284
-#, php-format
-msgid "Plugin %s disabled."
-msgstr "Plugin %s uitgeschakeld."
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:289
-#, php-format
-msgid "Plugin %s enabled."
-msgstr "Plugin %s ingeschakeld"
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:305
-#: ../../Zotlabs/Module/Admin/Themes.php:93
-msgid "Disable"
-msgstr "Uitschakelen"
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:308
-#: ../../Zotlabs/Module/Admin/Themes.php:95
-msgid "Enable"
-msgstr "Inschakelen"
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:337
-#: ../../Zotlabs/Module/Admin/Plugins.php:428 ../../include/widgets.php:1566
-msgid "Plugins"
-msgstr "Plugins"
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:338
-#: ../../Zotlabs/Module/Admin/Themes.php:122
-msgid "Toggle"
-msgstr "Omschakelen"
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:339
-#: ../../Zotlabs/Module/Admin/Themes.php:123 ../../Zotlabs/Lib/Apps.php:218
-#: ../../include/nav.php:211 ../../include/widgets.php:680
-msgid "Settings"
-msgstr "Instellingen"
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:346
-#: ../../Zotlabs/Module/Admin/Themes.php:132
-msgid "Author: "
-msgstr "Auteur: "
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:347
-#: ../../Zotlabs/Module/Admin/Themes.php:133
-msgid "Maintainer: "
-msgstr "Beheerder: "
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:348
-msgid "Minimum project version: "
-msgstr "Minimum versie Hubzilla: "
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:349
-msgid "Maximum project version: "
-msgstr "Maximum versie Hubzilla:"
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:350
-msgid "Minimum PHP version: "
-msgstr "Minimum versie PHP: "
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:351
-msgid "Compatible Server Roles: "
-msgstr "Werkt met configuratietypes: "
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:352
-msgid "Requires: "
-msgstr "Vereist: "
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:353
-#: ../../Zotlabs/Module/Admin/Plugins.php:433
-msgid "Disabled - version incompatibility"
-msgstr "Uitgeschakeld - versie is incompatibel"
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:402
-msgid "Enter the public git repository URL of the plugin repo."
-msgstr "Vul de openbare Git-URL in van de plugin-repository."
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:403
-msgid "Plugin repo git URL"
-msgstr "Git-URL plugin-repository"
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:404
-msgid "Custom repo name"
-msgstr "Handmatige repository-naam"
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:404
-msgid "(optional)"
-msgstr "(optioneel)"
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:405
-msgid "Download Plugin Repo"
-msgstr "Plugin-repository downloaden"
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:412
-msgid "Install new repo"
-msgstr "Nieuwe repository installeren"
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:413 ../../Zotlabs/Lib/Apps.php:339
-msgid "Install"
-msgstr "Installeren"
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:414
-#: ../../Zotlabs/Module/Fbrowser.php:66 ../../Zotlabs/Module/Fbrowser.php:88
-#: ../../Zotlabs/Module/Wiki.php:238 ../../Zotlabs/Module/Wiki.php:261
-#: ../../Zotlabs/Module/Settings/Oauth.php:88
-#: ../../Zotlabs/Module/Settings/Oauth.php:114
-#: ../../Zotlabs/Module/Tagrm.php:15 ../../Zotlabs/Module/Tagrm.php:138
-#: ../../extend/addon/addon/friendica/dfrn_request.php:879
-#: ../../extend/addon/addon/js_upload/js_upload.php:46
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:866
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1154
-#: ../../include/conversation.php:1246 ../../include/conversation.php:1295
-msgid "Cancel"
-msgstr "Annuleren"
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:435
-msgid "Manage Repos"
-msgstr "Repositories beheren"
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:436
-msgid "Installed Plugin Repositories"
-msgstr "Toegevoegde plugin-repositories"
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:437
-msgid "Install a New Plugin Repository"
-msgstr "Nieuwe plugin-repository toevoegen"
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:443
-#: ../../Zotlabs/Module/Settings/Oauth.php:42
-#: ../../Zotlabs/Module/Settings/Oauth.php:113 ../../Zotlabs/Lib/Apps.php:339
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1152
-msgid "Update"
-msgstr "Bijwerken"
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:444
-msgid "Switch branch"
-msgstr "Branch veranderen"
-
-#: ../../Zotlabs/Module/Admin/Plugins.php:445
-#: ../../Zotlabs/Module/Photos.php:989 ../../Zotlabs/Module/Tagrm.php:137
-#: ../../extend/addon/addon/superblock/superblock.php:114
-msgid "Remove"
-msgstr "Verwijderen"
-
#: ../../Zotlabs/Module/Admin/Profs.php:69
msgid "New Profile Field"
msgstr "Nieuw profielveld"
@@ -1932,7 +1506,7 @@ msgstr "Helptekst"
#: ../../Zotlabs/Module/Admin/Profs.php:73
#: ../../Zotlabs/Module/Admin/Profs.php:93
msgid "Additional info (optional)"
-msgstr "Extra informatie (optioneel)"
+msgstr "Extra informatie (niet verplicht)"
#: ../../Zotlabs/Module/Admin/Profs.php:83
msgid "Field definition not found"
@@ -1942,7 +1516,7 @@ msgstr "Velddefinitie niet gevonden"
msgid "Edit Profile Field"
msgstr "Profielveld bewerken"
-#: ../../Zotlabs/Module/Admin/Profs.php:147 ../../include/widgets.php:1569
+#: ../../Zotlabs/Module/Admin/Profs.php:147 ../../include/widgets.php:1642
msgid "Profile Fields"
msgstr "Profielvelden"
@@ -1970,34 +1544,6 @@ msgstr "Extra (handmatig toegevoegde) velden"
msgid "Create Custom Field"
msgstr "Extra velden aanmaken"
-#: ../../Zotlabs/Module/Admin/Queue.php:36
-msgid "Queue Statistics"
-msgstr "Wachtrij-statistieken"
-
-#: ../../Zotlabs/Module/Admin/Queue.php:37
-msgid "Total Entries"
-msgstr "Aantal vermeldingen"
-
-#: ../../Zotlabs/Module/Admin/Queue.php:38
-msgid "Priority"
-msgstr "Prioriteit"
-
-#: ../../Zotlabs/Module/Admin/Queue.php:39
-msgid "Destination URL"
-msgstr "Doel-URL"
-
-#: ../../Zotlabs/Module/Admin/Queue.php:40
-msgid "Mark hub permanently offline"
-msgstr "Hub als permanent offline markeren"
-
-#: ../../Zotlabs/Module/Admin/Queue.php:41
-msgid "Empty queue for this hub"
-msgstr "Berichtenwachtrij voor deze hub legen"
-
-#: ../../Zotlabs/Module/Admin/Queue.php:42
-msgid "Last known contact"
-msgstr "Voor het laatst contact"
-
#: ../../Zotlabs/Module/Admin/Security.php:77
msgid ""
"By default, unfiltered HTML is allowed in embedded media. This is inherently"
@@ -2022,7 +1568,7 @@ msgid ""
"embedded content from that site is explicitly blocked."
msgstr "Alle andere ingesloten (embedded) inhoud wordt gefilterd, <strong>tenzij</strong> ingesloten (embedded) inhoud van een website expliciet wordt geblokkeerd."
-#: ../../Zotlabs/Module/Admin/Security.php:87 ../../include/widgets.php:1564
+#: ../../Zotlabs/Module/Admin/Security.php:87 ../../include/widgets.php:1637
msgid "Security"
msgstr "Beveiliging"
@@ -2110,31 +1656,6 @@ msgstr "Eén website per regel. Standaard wordt ingesloten (embedded) inhoud gef
msgid "Block embedded HTML from these domains"
msgstr "Ingesloten (embedded) HTML vanaf deze domeinen blokkeren"
-#: ../../Zotlabs/Module/Admin/Themes.php:18
-msgid "Theme settings updated."
-msgstr "Thema-instellingen bijgewerkt."
-
-#: ../../Zotlabs/Module/Admin/Themes.php:58
-msgid "No themes found."
-msgstr "Geen thema's gevonden"
-
-#: ../../Zotlabs/Module/Admin/Themes.php:114
-msgid "Screenshot"
-msgstr "Schermafdruk"
-
-#: ../../Zotlabs/Module/Admin/Themes.php:121
-#: ../../Zotlabs/Module/Admin/Themes.php:155 ../../include/widgets.php:1567
-msgid "Themes"
-msgstr "Thema's"
-
-#: ../../Zotlabs/Module/Admin/Themes.php:160
-msgid "[Experimental]"
-msgstr "[Experimenteel]"
-
-#: ../../Zotlabs/Module/Admin/Themes.php:161
-msgid "[Unsupported]"
-msgstr "[Niet ondersteund]"
-
#: ../../Zotlabs/Module/Admin/Account_edit.php:29
#, php-format
msgid "Password changed for account %d."
@@ -2206,7 +1727,7 @@ msgid "Account '%s' unblocked"
msgstr "Account '%s' gedeblokkeerd"
#: ../../Zotlabs/Module/Admin/Accounts.php:165
-#: ../../Zotlabs/Module/Admin/Accounts.php:178 ../../include/widgets.php:1562
+#: ../../Zotlabs/Module/Admin/Accounts.php:178 ../../include/widgets.php:1635
msgid "Accounts"
msgstr "Accounts"
@@ -2225,12 +1746,13 @@ msgstr "Tijd/datum verzoek"
#: ../../Zotlabs/Module/Admin/Accounts.php:169
#: ../../Zotlabs/Module/Admin/Accounts.php:181
+#: ../../Zotlabs/Module/Connedit.php:917 ../../Zotlabs/Module/Profiles.php:790
#: ../../extend/addon/addon/redred/redred.php:107
#: ../../extend/addon/addon/rtof/rtof.php:93
#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1140
#: ../../extend/addon/addon/openid/MysqlProvider.php:56
#: ../../extend/addon/addon/openid/MysqlProvider.php:57
-#: ../../include/network.php:2237
+#: ../../include/network.php:2270
msgid "Email"
msgstr "E-mail"
@@ -2242,11 +1764,21 @@ msgstr "Geen verzoeken."
msgid "Deny"
msgstr "Afkeuren"
+#: ../../Zotlabs/Module/Admin/Accounts.php:174
+#: ../../Zotlabs/Module/Connedit.php:629
+msgid "Block"
+msgstr "Blokkeren"
+
+#: ../../Zotlabs/Module/Admin/Accounts.php:175
+#: ../../Zotlabs/Module/Connedit.php:629
+msgid "Unblock"
+msgstr "Deblokkeren"
+
#: ../../Zotlabs/Module/Admin/Accounts.php:180
msgid "ID"
msgstr "ID"
-#: ../../Zotlabs/Module/Admin/Accounts.php:182 ../../include/group.php:267
+#: ../../Zotlabs/Module/Admin/Accounts.php:182 ../../include/group.php:287
msgid "All Channels"
msgstr "Alle kanalen"
@@ -2328,7 +1860,7 @@ msgstr "Scripts toegestaan voor kanaal '%s'"
msgid "Channel '%s' code disallowed"
msgstr "Scripts niet toegestaan voor kanaal '%s'"
-#: ../../Zotlabs/Module/Admin/Channels.php:146 ../../include/widgets.php:1563
+#: ../../Zotlabs/Module/Admin/Channels.php:146 ../../include/widgets.php:1636
msgid "Channels"
msgstr "Kanalen"
@@ -2349,7 +1881,7 @@ msgid "Disallow Code"
msgstr "Scripts niet toestaan"
#: ../../Zotlabs/Module/Admin/Channels.php:154
-#: ../../include/conversation.php:1653
+#: ../../include/conversation.php:1815
msgid "Channel"
msgstr "Kanaal"
@@ -2357,6 +1889,13 @@ msgstr "Kanaal"
msgid "UID"
msgstr "UID"
+#: ../../Zotlabs/Module/Admin/Channels.php:160
+#: ../../Zotlabs/Module/Locs.php:118 ../../Zotlabs/Module/Connedit.php:920
+#: ../../Zotlabs/Module/Profiles.php:502 ../../Zotlabs/Module/Profiles.php:793
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1143
+msgid "Address"
+msgstr "Adres"
+
#: ../../Zotlabs/Module/Admin/Channels.php:162
msgid ""
"Selected channels will be deleted!\\n\\nEverything that was posted in these "
@@ -2409,432 +1948,768 @@ msgstr "Markeer als geslaagd (wanneer de update handmatig was uitgevoerd)"
msgid "Attempt to execute this update step automatically"
msgstr "Poging om deze stap van de update automatisch uit te voeren."
+#: ../../Zotlabs/Module/Admin/Queue.php:35
+msgid "Queue Statistics"
+msgstr "Wachtrij-statistieken"
+
+#: ../../Zotlabs/Module/Admin/Queue.php:36
+msgid "Total Entries"
+msgstr "Aantal vermeldingen"
+
+#: ../../Zotlabs/Module/Admin/Queue.php:37
+msgid "Priority"
+msgstr "Prioriteit"
+
+#: ../../Zotlabs/Module/Admin/Queue.php:38
+msgid "Destination URL"
+msgstr "Doel-URL"
+
+#: ../../Zotlabs/Module/Admin/Queue.php:39
+msgid "Mark hub permanently offline"
+msgstr "Hub als permanent offline markeren"
+
+#: ../../Zotlabs/Module/Admin/Queue.php:40
+msgid "Empty queue for this hub"
+msgstr "Berichtenwachtrij voor deze hub legen"
+
+#: ../../Zotlabs/Module/Admin/Queue.php:41
+msgid "Last known contact"
+msgstr "Voor het laatst contact"
+
#: ../../Zotlabs/Module/Admin/Site.php:133
msgid "Site settings updated."
msgstr "Hub-instellingen bijgewerkt."
-#: ../../Zotlabs/Module/Admin/Site.php:159 ../../include/text.php:2918
+#: ../../Zotlabs/Module/Admin/Site.php:159 ../../include/text.php:2936
msgid "Default"
msgstr "Standaard"
-#: ../../Zotlabs/Module/Admin/Site.php:169
-#: ../../Zotlabs/Module/Settings/Display.php:143
+#: ../../Zotlabs/Module/Admin/Site.php:170
+#: ../../Zotlabs/Module/Settings/Display.php:137
+#, php-format
+msgid "%s - (Incompatible)"
+msgstr "%s - (niet compatible)"
+
+#: ../../Zotlabs/Module/Admin/Site.php:177
+#: ../../Zotlabs/Module/Settings/Display.php:151
msgid "mobile"
msgstr "mobiel"
-#: ../../Zotlabs/Module/Admin/Site.php:171
+#: ../../Zotlabs/Module/Admin/Site.php:179
msgid "experimental"
msgstr "experimenteel"
-#: ../../Zotlabs/Module/Admin/Site.php:173
+#: ../../Zotlabs/Module/Admin/Site.php:181
msgid "unsupported"
msgstr "Niet ondersteund"
-#: ../../Zotlabs/Module/Admin/Site.php:219
+#: ../../Zotlabs/Module/Admin/Site.php:226 ../../Zotlabs/Module/Menu.php:100
+#: ../../Zotlabs/Module/Menu.php:157 ../../Zotlabs/Module/Connedit.php:402
+#: ../../Zotlabs/Module/Connedit.php:786 ../../Zotlabs/Module/Events.php:470
+#: ../../Zotlabs/Module/Events.php:471
+#: ../../Zotlabs/Module/Filestorage.php:160
+#: ../../Zotlabs/Module/Filestorage.php:168
+#: ../../Zotlabs/Module/Photos.php:652 ../../Zotlabs/Module/Mitem.php:162
+#: ../../Zotlabs/Module/Mitem.php:163 ../../Zotlabs/Module/Mitem.php:240
+#: ../../Zotlabs/Module/Mitem.php:241 ../../Zotlabs/Module/Api.php:97
+#: ../../Zotlabs/Module/Removeme.php:63 ../../Zotlabs/Module/Profiles.php:681
+#: ../../Zotlabs/Module/Settings/Channel.php:294
+#: ../../Zotlabs/Module/Settings/Display.php:103
+#: ../../Zotlabs/Module/Wiki.php:179
+#: ../../extend/addon/addon/dwpost/dwpost.php:73
+#: ../../extend/addon/addon/dwpost/dwpost.php:85
+#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:120
+#: ../../extend/addon/addon/friendica/dfrn_request.php:865
+#: ../../extend/addon/addon/ijpost/ijpost.php:73
+#: ../../extend/addon/addon/ijpost/ijpost.php:85
+#: ../../extend/addon/addon/jappixmini/jappixmini.php:309
+#: ../../extend/addon/addon/jappixmini/jappixmini.php:313
+#: ../../extend/addon/addon/jappixmini/jappixmini.php:343
+#: ../../extend/addon/addon/jappixmini/jappixmini.php:351
+#: ../../extend/addon/addon/jappixmini/jappixmini.php:355
+#: ../../extend/addon/addon/jappixmini/jappixmini.php:359
+#: ../../extend/addon/addon/libertree/libertree.php:69
+#: ../../extend/addon/addon/libertree/libertree.php:81
+#: ../../extend/addon/addon/ljpost/ljpost.php:70
+#: ../../extend/addon/addon/ljpost/ljpost.php:82
+#: ../../extend/addon/addon/nofed/nofed.php:72
+#: ../../extend/addon/addon/nofed/nofed.php:76
+#: ../../extend/addon/addon/nsabait/nsabait.php:157
+#: ../../extend/addon/addon/nsfw/nsfw.php:84
+#: ../../extend/addon/addon/planets/planets.php:153
+#: ../../extend/addon/addon/pumpio/pumpio.php:219
+#: ../../extend/addon/addon/pumpio/pumpio.php:223
+#: ../../extend/addon/addon/pumpio/pumpio.php:227
+#: ../../extend/addon/addon/pumpio/pumpio.php:231
+#: ../../extend/addon/addon/rainbowtag/rainbowtag.php:81
+#: ../../extend/addon/addon/redred/redred.php:95
+#: ../../extend/addon/addon/redred/redred.php:99
+#: ../../extend/addon/addon/rtof/rtof.php:81
+#: ../../extend/addon/addon/rtof/rtof.php:85
+#: ../../extend/addon/addon/smileybutton/smileybutton.php:273
+#: ../../extend/addon/addon/smileybutton/smileybutton.php:277
+#: ../../extend/addon/addon/statusnet/statusnet.php:389
+#: ../../extend/addon/addon/statusnet/statusnet.php:411
+#: ../../extend/addon/addon/statusnet/statusnet.php:415
+#: ../../extend/addon/addon/statusnet/statusnet.php:424
+#: ../../extend/addon/addon/twitter/twitter.php:242
+#: ../../extend/addon/addon/twitter/twitter.php:246
+#: ../../extend/addon/addon/twitter/twitter.php:255
+#: ../../extend/addon/addon/visage/visage.php:166
+#: ../../extend/addon/addon/wppost/wppost.php:82
+#: ../../extend/addon/addon/wppost/wppost.php:105
+#: ../../extend/addon/addon/wppost/wppost.php:109
+#: ../../extend/addon/addon/xmpp/xmpp.php:53
+#: ../../extend/addon/addon/cdav/cdav.php:234
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:164
+#: ../../include/dir_fns.php:143 ../../include/dir_fns.php:144
+#: ../../include/dir_fns.php:145 ../../view/theme/redbasic/php/config.php:111
+#: ../../view/theme/redbasic/php/config.php:136 ../../boot.php:1753
+msgid "No"
+msgstr "Nee"
+
+#: ../../Zotlabs/Module/Admin/Site.php:227
msgid "Yes - with approval"
msgstr "Ja - met goedkeuring"
-#: ../../Zotlabs/Module/Admin/Site.php:225
+#: ../../Zotlabs/Module/Admin/Site.php:228 ../../Zotlabs/Module/Menu.php:100
+#: ../../Zotlabs/Module/Menu.php:157 ../../Zotlabs/Module/Connedit.php:402
+#: ../../Zotlabs/Module/Events.php:470 ../../Zotlabs/Module/Events.php:471
+#: ../../Zotlabs/Module/Filestorage.php:160
+#: ../../Zotlabs/Module/Filestorage.php:168
+#: ../../Zotlabs/Module/Photos.php:652 ../../Zotlabs/Module/Mitem.php:162
+#: ../../Zotlabs/Module/Mitem.php:163 ../../Zotlabs/Module/Mitem.php:240
+#: ../../Zotlabs/Module/Mitem.php:241 ../../Zotlabs/Module/Api.php:96
+#: ../../Zotlabs/Module/Removeme.php:63 ../../Zotlabs/Module/Profiles.php:681
+#: ../../Zotlabs/Module/Settings/Channel.php:294
+#: ../../Zotlabs/Module/Settings/Display.php:103
+#: ../../Zotlabs/Module/Wiki.php:179
+#: ../../extend/addon/addon/dwpost/dwpost.php:73
+#: ../../extend/addon/addon/dwpost/dwpost.php:85
+#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:120
+#: ../../extend/addon/addon/friendica/dfrn_request.php:865
+#: ../../extend/addon/addon/ijpost/ijpost.php:73
+#: ../../extend/addon/addon/ijpost/ijpost.php:85
+#: ../../extend/addon/addon/jappixmini/jappixmini.php:309
+#: ../../extend/addon/addon/jappixmini/jappixmini.php:313
+#: ../../extend/addon/addon/jappixmini/jappixmini.php:343
+#: ../../extend/addon/addon/jappixmini/jappixmini.php:351
+#: ../../extend/addon/addon/jappixmini/jappixmini.php:355
+#: ../../extend/addon/addon/jappixmini/jappixmini.php:359
+#: ../../extend/addon/addon/libertree/libertree.php:69
+#: ../../extend/addon/addon/libertree/libertree.php:81
+#: ../../extend/addon/addon/ljpost/ljpost.php:70
+#: ../../extend/addon/addon/ljpost/ljpost.php:82
+#: ../../extend/addon/addon/nofed/nofed.php:72
+#: ../../extend/addon/addon/nofed/nofed.php:76
+#: ../../extend/addon/addon/nsabait/nsabait.php:157
+#: ../../extend/addon/addon/nsfw/nsfw.php:84
+#: ../../extend/addon/addon/planets/planets.php:153
+#: ../../extend/addon/addon/pumpio/pumpio.php:219
+#: ../../extend/addon/addon/pumpio/pumpio.php:223
+#: ../../extend/addon/addon/pumpio/pumpio.php:227
+#: ../../extend/addon/addon/pumpio/pumpio.php:231
+#: ../../extend/addon/addon/rainbowtag/rainbowtag.php:81
+#: ../../extend/addon/addon/redred/redred.php:95
+#: ../../extend/addon/addon/redred/redred.php:99
+#: ../../extend/addon/addon/rtof/rtof.php:81
+#: ../../extend/addon/addon/rtof/rtof.php:85
+#: ../../extend/addon/addon/smileybutton/smileybutton.php:273
+#: ../../extend/addon/addon/smileybutton/smileybutton.php:277
+#: ../../extend/addon/addon/statusnet/statusnet.php:389
+#: ../../extend/addon/addon/statusnet/statusnet.php:411
+#: ../../extend/addon/addon/statusnet/statusnet.php:415
+#: ../../extend/addon/addon/statusnet/statusnet.php:424
+#: ../../extend/addon/addon/twitter/twitter.php:242
+#: ../../extend/addon/addon/twitter/twitter.php:246
+#: ../../extend/addon/addon/twitter/twitter.php:255
+#: ../../extend/addon/addon/visage/visage.php:166
+#: ../../extend/addon/addon/wppost/wppost.php:82
+#: ../../extend/addon/addon/wppost/wppost.php:105
+#: ../../extend/addon/addon/wppost/wppost.php:109
+#: ../../extend/addon/addon/xmpp/xmpp.php:53
+#: ../../extend/addon/addon/cdav/cdav.php:234
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:164
+#: ../../include/dir_fns.php:143 ../../include/dir_fns.php:144
+#: ../../include/dir_fns.php:145 ../../view/theme/redbasic/php/config.php:111
+#: ../../view/theme/redbasic/php/config.php:136 ../../boot.php:1753
+msgid "Yes"
+msgstr "Ja"
+
+#: ../../Zotlabs/Module/Admin/Site.php:233
msgid "My site is not a public server"
msgstr "Mijn $Projectname-hub is niet openbaar"
-#: ../../Zotlabs/Module/Admin/Site.php:226
+#: ../../Zotlabs/Module/Admin/Site.php:234
msgid "My site has paid access only"
msgstr "Mijn $Projectname-hub kent alleen betaalde toegang"
-#: ../../Zotlabs/Module/Admin/Site.php:227
+#: ../../Zotlabs/Module/Admin/Site.php:235
msgid "My site has free access only"
msgstr "Mijn $Projectname-hub kent alleen gratis toegang"
-#: ../../Zotlabs/Module/Admin/Site.php:228
+#: ../../Zotlabs/Module/Admin/Site.php:236
msgid "My site offers free accounts with optional paid upgrades"
msgstr "Mijn $Projectname-hub biedt gratis accounts aan met betaalde uitbreidingen als optie"
-#: ../../Zotlabs/Module/Admin/Site.php:239 ../../Zotlabs/Module/Setup.php:328
+#: ../../Zotlabs/Module/Admin/Site.php:247 ../../Zotlabs/Module/Setup.php:328
msgid "Basic/Minimal Social Networking"
msgstr "Basic/eenvoudig sociaal netwerk"
-#: ../../Zotlabs/Module/Admin/Site.php:240 ../../Zotlabs/Module/Setup.php:329
+#: ../../Zotlabs/Module/Admin/Site.php:248 ../../Zotlabs/Module/Setup.php:329
msgid "Standard Configuration (default)"
msgstr "Standaard (standaard)"
-#: ../../Zotlabs/Module/Admin/Site.php:241 ../../Zotlabs/Module/Setup.php:330
+#: ../../Zotlabs/Module/Admin/Site.php:249 ../../Zotlabs/Module/Setup.php:330
msgid "Professional"
msgstr "Professioneel "
-#: ../../Zotlabs/Module/Admin/Site.php:245 ../../Zotlabs/Lib/Techlevels.php:10
+#: ../../Zotlabs/Module/Admin/Site.php:253 ../../Zotlabs/Lib/Techlevels.php:10
msgid "Beginner/Basic"
msgstr "Beginner/basic"
-#: ../../Zotlabs/Module/Admin/Site.php:246 ../../Zotlabs/Lib/Techlevels.php:11
+#: ../../Zotlabs/Module/Admin/Site.php:254 ../../Zotlabs/Lib/Techlevels.php:11
msgid "Novice - not skilled but willing to learn"
msgstr "Onervaren - niet bekwaam, maar wil graag leren"
-#: ../../Zotlabs/Module/Admin/Site.php:247 ../../Zotlabs/Lib/Techlevels.php:12
+#: ../../Zotlabs/Module/Admin/Site.php:255 ../../Zotlabs/Lib/Techlevels.php:12
msgid "Intermediate - somewhat comfortable"
msgstr "Ervaren - voelt zich enigszins comfortabel"
-#: ../../Zotlabs/Module/Admin/Site.php:248 ../../Zotlabs/Lib/Techlevels.php:13
+#: ../../Zotlabs/Module/Admin/Site.php:256 ../../Zotlabs/Lib/Techlevels.php:13
msgid "Advanced - very comfortable"
msgstr "Gevorderd - voelt zich comfortabel"
-#: ../../Zotlabs/Module/Admin/Site.php:249 ../../Zotlabs/Lib/Techlevels.php:14
+#: ../../Zotlabs/Module/Admin/Site.php:257 ../../Zotlabs/Lib/Techlevels.php:14
msgid "Expert - I can write computer code"
msgstr "Expert - kan programmeren"
-#: ../../Zotlabs/Module/Admin/Site.php:250 ../../Zotlabs/Lib/Techlevels.php:15
+#: ../../Zotlabs/Module/Admin/Site.php:258 ../../Zotlabs/Lib/Techlevels.php:15
msgid "Wizard - I probably know more than you do"
msgstr "Tovenaar - ik weet waarschijnlijk meer dan jij"
-#: ../../Zotlabs/Module/Admin/Site.php:259 ../../include/widgets.php:1561
+#: ../../Zotlabs/Module/Admin/Site.php:267 ../../include/widgets.php:1634
msgid "Site"
msgstr "Hub-instellingen"
-#: ../../Zotlabs/Module/Admin/Site.php:262
+#: ../../Zotlabs/Module/Admin/Site.php:270
msgid "File upload"
msgstr "Bestand uploaden"
-#: ../../Zotlabs/Module/Admin/Site.php:263
+#: ../../Zotlabs/Module/Admin/Site.php:271
msgid "Policies"
msgstr "Beleid"
-#: ../../Zotlabs/Module/Admin/Site.php:264
+#: ../../Zotlabs/Module/Admin/Site.php:272
#: ../../include/contact_widgets.php:16
msgid "Advanced"
msgstr "Geavanceerd"
-#: ../../Zotlabs/Module/Admin/Site.php:268
+#: ../../Zotlabs/Module/Admin/Site.php:276
#: ../../extend/addon/addon/statusnet/statusnet.php:890
msgid "Site name"
msgstr "Hubnaam"
-#: ../../Zotlabs/Module/Admin/Site.php:270 ../../Zotlabs/Module/Setup.php:351
+#: ../../Zotlabs/Module/Admin/Site.php:278 ../../Zotlabs/Module/Setup.php:351
msgid "Server Configuration/Role"
msgstr "Configuratietype hub"
-#: ../../Zotlabs/Module/Admin/Site.php:272
+#: ../../Zotlabs/Module/Admin/Site.php:280
msgid "Site default technical skill level"
msgstr "Standaard technisch niveau voor deze hub"
-#: ../../Zotlabs/Module/Admin/Site.php:272
+#: ../../Zotlabs/Module/Admin/Site.php:280
msgid "Used to provide a member experience matched to technical comfort level"
msgstr "Wordt gebruikt om leden een gebruikerservaring te bieden die met hun technisch niveau overeenkomt"
-#: ../../Zotlabs/Module/Admin/Site.php:274
+#: ../../Zotlabs/Module/Admin/Site.php:282
msgid "Lock the technical skill level setting"
msgstr "Vergrendel de functie 'Standaard technisch niveau voor deze hub'"
-#: ../../Zotlabs/Module/Admin/Site.php:274
+#: ../../Zotlabs/Module/Admin/Site.php:282
msgid "Members can set their own technical comfort level by default"
msgstr "Leden kunnen hun eigen technisch niveau standaard instellen"
-#: ../../Zotlabs/Module/Admin/Site.php:276
+#: ../../Zotlabs/Module/Admin/Site.php:284
msgid "Banner/Logo"
msgstr "Banner/logo"
-#: ../../Zotlabs/Module/Admin/Site.php:277
+#: ../../Zotlabs/Module/Admin/Site.php:285
msgid "Administrator Information"
msgstr "Informatie over de beheerder"
-#: ../../Zotlabs/Module/Admin/Site.php:277
+#: ../../Zotlabs/Module/Admin/Site.php:285
msgid ""
"Contact information for site administrators. Displayed on siteinfo page. "
"BBCode can be used here"
msgstr "Contactinformatie voor hub-beheerders. Getoond op pagina met hub-informatie. Er kan hier bbcode gebruikt worden."
-#: ../../Zotlabs/Module/Admin/Site.php:278
+#: ../../Zotlabs/Module/Admin/Site.php:286
#: ../../Zotlabs/Module/Siteinfo.php:23
msgid "Site Information"
msgstr "Hub-informatie"
-#: ../../Zotlabs/Module/Admin/Site.php:278
+#: ../../Zotlabs/Module/Admin/Site.php:286
msgid ""
"Publicly visible description of this site. Displayed on siteinfo page. "
"BBCode can be used here"
msgstr "Openbaar zichtbare beschrijving van deze hub. Getoond op pagina met hub-informatie. Er kan hier bbcode gebruikt worden."
-#: ../../Zotlabs/Module/Admin/Site.php:279
+#: ../../Zotlabs/Module/Admin/Site.php:287
msgid "System language"
msgstr "Standaardtaal"
-#: ../../Zotlabs/Module/Admin/Site.php:280
+#: ../../Zotlabs/Module/Admin/Site.php:288
msgid "System theme"
msgstr "Standaardthema"
-#: ../../Zotlabs/Module/Admin/Site.php:280
+#: ../../Zotlabs/Module/Admin/Site.php:288
msgid ""
"Default system theme - may be over-ridden by user profiles - <a href='#' "
"id='cnftheme'>change theme settings</a>"
msgstr "Standaardthema voor $Projectname-hub (kan door lid veranderd worden) - <a href='#' id='cnftheme'>verander thema-instellingen</a>"
-#: ../../Zotlabs/Module/Admin/Site.php:281
+#: ../../Zotlabs/Module/Admin/Site.php:289
msgid "Mobile system theme"
msgstr "Standaardthema voor mobiel"
-#: ../../Zotlabs/Module/Admin/Site.php:281
+#: ../../Zotlabs/Module/Admin/Site.php:289
msgid "Theme for mobile devices"
msgstr "Thema voor mobiele apparaten"
-#: ../../Zotlabs/Module/Admin/Site.php:283
+#: ../../Zotlabs/Module/Admin/Site.php:291
msgid "Allow Feeds as Connections"
msgstr "Sta feeds toe als connecties"
-#: ../../Zotlabs/Module/Admin/Site.php:283
+#: ../../Zotlabs/Module/Admin/Site.php:291
msgid "(Heavy system resource usage)"
msgstr "(sterk negatieve invloed op systeembronnen hub)"
-#: ../../Zotlabs/Module/Admin/Site.php:284
+#: ../../Zotlabs/Module/Admin/Site.php:292
msgid "Maximum image size"
msgstr "Maximale grootte van afbeeldingen"
-#: ../../Zotlabs/Module/Admin/Site.php:284
+#: ../../Zotlabs/Module/Admin/Site.php:292
msgid ""
"Maximum size in bytes of uploaded images. Default is 0, which means no "
"limits."
msgstr "Maximale grootte in bytes voor afbeeldingen die worden geüpload. Standaard is 0, wat geen limiet betekend."
-#: ../../Zotlabs/Module/Admin/Site.php:285
+#: ../../Zotlabs/Module/Admin/Site.php:293
msgid "Does this site allow new member registration?"
msgstr "Staat deze hub nieuwe accounts toe?"
-#: ../../Zotlabs/Module/Admin/Site.php:286
+#: ../../Zotlabs/Module/Admin/Site.php:294
msgid "Invitation only"
msgstr "Alleen op uitnodiging"
-#: ../../Zotlabs/Module/Admin/Site.php:286
+#: ../../Zotlabs/Module/Admin/Site.php:294
msgid ""
"Only allow new member registrations with an invitation code. Above register "
"policy must be set to Yes."
msgstr "Sta alleen nieuwe registraties toe van mensen die een uitnodigingscode hebben. Bovenstaand accountbeleid moet op Ja staan."
-#: ../../Zotlabs/Module/Admin/Site.php:287
+#: ../../Zotlabs/Module/Admin/Site.php:295
msgid "Which best describes the types of account offered by this hub?"
msgstr "Wat voor soort accounts biedt deze $Projectname-hub aan? Kies wat het meest in de buurt komt."
-#: ../../Zotlabs/Module/Admin/Site.php:288
+#: ../../Zotlabs/Module/Admin/Site.php:296
msgid "Register text"
msgstr "Tekst tijdens registratie"
-#: ../../Zotlabs/Module/Admin/Site.php:288
+#: ../../Zotlabs/Module/Admin/Site.php:296
msgid "Will be displayed prominently on the registration page."
msgstr "Tekst dat op de pagina voor het registreren van nieuwe accounts wordt getoond."
-#: ../../Zotlabs/Module/Admin/Site.php:289
+#: ../../Zotlabs/Module/Admin/Site.php:297
msgid "Site homepage to show visitors (default: login box)"
msgstr "Homepagina van deze hub die aan bezoekers wordt getoond (standaard: inlogformulier)"
-#: ../../Zotlabs/Module/Admin/Site.php:289
+#: ../../Zotlabs/Module/Admin/Site.php:297
msgid ""
"example: 'public' to show public stream, 'page/sys/home' to show a system "
"webpage called 'home' or 'include:home.html' to include a file."
msgstr "voorbeeld: 'public' om de openbare stream te tonen, 'page/sys/home' om de webpagina 'home' van het systeemkanaal te tonen of 'include:home.html' om een gewoon bestand te gebruiken."
-#: ../../Zotlabs/Module/Admin/Site.php:290
+#: ../../Zotlabs/Module/Admin/Site.php:298
msgid "Preserve site homepage URL"
msgstr "Behoudt de URL van de hub (/)"
-#: ../../Zotlabs/Module/Admin/Site.php:290
+#: ../../Zotlabs/Module/Admin/Site.php:298
msgid ""
"Present the site homepage in a frame at the original location instead of "
"redirecting"
msgstr "Toon de homepagina van de hub in een frame op de oorspronkelijke locatie (/), i.p.v. een doorverwijzing naar een andere locatie (bv. .../home.html)"
-#: ../../Zotlabs/Module/Admin/Site.php:291
+#: ../../Zotlabs/Module/Admin/Site.php:299
msgid "Accounts abandoned after x days"
msgstr "Accounts als verlaten beschouwen na zoveel aantal dagen:"
-#: ../../Zotlabs/Module/Admin/Site.php:291
+#: ../../Zotlabs/Module/Admin/Site.php:299
msgid ""
"Will not waste system resources polling external sites for abandonded "
"accounts. Enter 0 for no time limit."
msgstr "Zal geen systeembronnen verspillen door polling van externe hubs voor verlaten accounts. Vul 0 in voor geen tijdslimiet."
-#: ../../Zotlabs/Module/Admin/Site.php:292
+#: ../../Zotlabs/Module/Admin/Site.php:300
msgid "Allowed friend domains"
msgstr "Toegestane domeinen"
-#: ../../Zotlabs/Module/Admin/Site.php:292
+#: ../../Zotlabs/Module/Admin/Site.php:300
msgid ""
"Comma separated list of domains which are allowed to establish friendships "
"with this site. Wildcards are accepted. Empty to allow any domains"
msgstr "Komma-gescheiden lijst van domeinen waarvan kanalen connecties kunnen aangaan met kanalen op deze $Projectname-hub. Wildcards zijn toegestaan.\nLaat leeg om alle domeinen toe te laten."
-#: ../../Zotlabs/Module/Admin/Site.php:293
+#: ../../Zotlabs/Module/Admin/Site.php:301
msgid "Verify Email Addresses"
msgstr "E-mailadres verifieren"
-#: ../../Zotlabs/Module/Admin/Site.php:293
+#: ../../Zotlabs/Module/Admin/Site.php:301
msgid ""
"Check to verify email addresses used in account registration (recommended)."
msgstr "Inschakelen om e-mailadressen te verifiëren die tijdens de accountregistratie worden gebruikt (aanbevolen)."
-#: ../../Zotlabs/Module/Admin/Site.php:294
+#: ../../Zotlabs/Module/Admin/Site.php:302
msgid "Force publish"
msgstr "Dwing kanaalvermelding af"
-#: ../../Zotlabs/Module/Admin/Site.php:294
+#: ../../Zotlabs/Module/Admin/Site.php:302
msgid ""
"Check to force all profiles on this site to be listed in the site directory."
msgstr "Vink dit aan om af te dwingen dat alle kanalen op deze hub in de kanalengids worden vermeld."
-#: ../../Zotlabs/Module/Admin/Site.php:295
+#: ../../Zotlabs/Module/Admin/Site.php:303
msgid "Import Public Streams"
msgstr "Openbare streams importeren"
-#: ../../Zotlabs/Module/Admin/Site.php:295
+#: ../../Zotlabs/Module/Admin/Site.php:303
msgid ""
"Import and allow access to public content pulled from other sites. Warning: "
"this content is unmoderated."
msgstr "Toegang verlenen tot openbare berichten die vanuit andere hubs worden geïmporteerd. Waarschuwing: de inhoud van deze berichten wordt niet gemodereerd."
-#: ../../Zotlabs/Module/Admin/Site.php:296
+#: ../../Zotlabs/Module/Admin/Site.php:304
msgid "Login on Homepage"
msgstr "Inlogformulier op de homepagina"
-#: ../../Zotlabs/Module/Admin/Site.php:296
+#: ../../Zotlabs/Module/Admin/Site.php:304
msgid ""
"Present a login box to visitors on the home page if no other content has "
"been configured."
msgstr "Toon een inlogformulier voor bezoekers op de homepagina wanneer geen andere inhoud is geconfigureerd. "
-#: ../../Zotlabs/Module/Admin/Site.php:297
+#: ../../Zotlabs/Module/Admin/Site.php:305
msgid "Enable context help"
msgstr "Schakel contextuele hulp in"
-#: ../../Zotlabs/Module/Admin/Site.php:297
+#: ../../Zotlabs/Module/Admin/Site.php:305
msgid ""
"Display contextual help for the current page when the help button is "
"pressed."
msgstr "Toon hulp en documentatie voor de op dat moment getoonde pagina, wanneer op de hulp-knop wordt geklikt."
-#: ../../Zotlabs/Module/Admin/Site.php:299
+#: ../../Zotlabs/Module/Admin/Site.php:307
msgid "Directory Server URL"
msgstr "Server-URL voor de kanalengids"
-#: ../../Zotlabs/Module/Admin/Site.php:299
+#: ../../Zotlabs/Module/Admin/Site.php:307
msgid "Default directory server"
msgstr "Standaardserver voor de kanalengids"
-#: ../../Zotlabs/Module/Admin/Site.php:301
+#: ../../Zotlabs/Module/Admin/Site.php:309
msgid "Proxy user"
msgstr "Gebruikersnaam proxy"
-#: ../../Zotlabs/Module/Admin/Site.php:302
+#: ../../Zotlabs/Module/Admin/Site.php:310
msgid "Proxy URL"
msgstr "Proxy-URL"
-#: ../../Zotlabs/Module/Admin/Site.php:303
+#: ../../Zotlabs/Module/Admin/Site.php:311
msgid "Network timeout"
msgstr "Netwerktimeout"
-#: ../../Zotlabs/Module/Admin/Site.php:303
+#: ../../Zotlabs/Module/Admin/Site.php:311
msgid "Value is in seconds. Set to 0 for unlimited (not recommended)."
msgstr "Waarde is in seconden. Zet op 0 voor onbeperkt (niet aanbevolen)"
-#: ../../Zotlabs/Module/Admin/Site.php:304
+#: ../../Zotlabs/Module/Admin/Site.php:312
msgid "Delivery interval"
msgstr "Afleveringsinterval"
-#: ../../Zotlabs/Module/Admin/Site.php:304
+#: ../../Zotlabs/Module/Admin/Site.php:312
msgid ""
"Delay background delivery processes by this many seconds to reduce system "
"load. Recommend: 4-5 for shared hosts, 2-3 for virtual private servers. 0-1 "
"for large dedicated servers."
msgstr "Vertraag de achtergrondprocessen voor het afleveren met een aantal seconden om de systeembelasting te verminderen. Aanbevolen: 4-5 voor shared hosts, 2-3 voor virtual private servers (VPS) en 0-1 voor grote dedicated servers."
-#: ../../Zotlabs/Module/Admin/Site.php:305
+#: ../../Zotlabs/Module/Admin/Site.php:313
msgid "Deliveries per process"
msgstr "Leveringen per serverproces"
-#: ../../Zotlabs/Module/Admin/Site.php:305
+#: ../../Zotlabs/Module/Admin/Site.php:313
msgid ""
"Number of deliveries to attempt in a single operating system process. Adjust"
" if necessary to tune system performance. Recommend: 1-5."
msgstr "Aantal leveringen die aan één serverproces worden meegegeven. Pas dit aan wanneer het nodig is om systeemprestaties te verbeteren. Aangeraden: 1-5"
-#: ../../Zotlabs/Module/Admin/Site.php:306
+#: ../../Zotlabs/Module/Admin/Site.php:314
msgid "Poll interval"
msgstr "Poll-interval"
-#: ../../Zotlabs/Module/Admin/Site.php:306
+#: ../../Zotlabs/Module/Admin/Site.php:314
msgid ""
"Delay background polling processes by this many seconds to reduce system "
"load. If 0, use delivery interval."
msgstr "De achtergrondprocessen voor het afleveren met zoveel seconden vertragen om de systeembelasting te verminderen. 0 om de afleveringsinterval te gebruiken."
-#: ../../Zotlabs/Module/Admin/Site.php:307
+#: ../../Zotlabs/Module/Admin/Site.php:315
msgid "Maximum Load Average"
msgstr "Maximaal gemiddelde systeembelasting"
-#: ../../Zotlabs/Module/Admin/Site.php:307
+#: ../../Zotlabs/Module/Admin/Site.php:315
msgid ""
"Maximum system load before delivery and poll processes are deferred - "
"default 50."
msgstr "Maximale systeembelasting voordat de afleverings- en polllingsprocessen worden uitgesteld. Standaard is 50."
-#: ../../Zotlabs/Module/Admin/Site.php:308
+#: ../../Zotlabs/Module/Admin/Site.php:316
msgid "Expiration period in days for imported (grid/network) content"
msgstr "Aantal dagen waarna geïmporteerde inhoud uit iemands grid/netwerk-pagina wordt verwijderd."
-#: ../../Zotlabs/Module/Admin/Site.php:308
+#: ../../Zotlabs/Module/Admin/Site.php:316
msgid "0 for no expiration of imported content"
msgstr "Dit geldt alleen voor inhoud van andere kanalen, dus niet voor iemands eigen kanaal. 0 voor het niet verwijderen van geïmporteerde inhoud."
-#: ../../Zotlabs/Module/Pubsites.php:24 ../../include/widgets.php:1385
-msgid "Public Hubs"
-msgstr "Openbare hubs"
+#: ../../Zotlabs/Module/Admin/Plugins.php:289
+#, php-format
+msgid "Plugin %s disabled."
+msgstr "Plugin %s uitgeschakeld."
-#: ../../Zotlabs/Module/Pubsites.php:27
-msgid ""
-"The listed hubs allow public registration for the $Projectname network. All "
-"hubs in the network are interlinked so membership on any of them conveys "
-"membership in the network as a whole. Some hubs may require subscription or "
-"provide tiered service plans. The hub itself <strong>may</strong> provide "
-"additional details."
-msgstr "Op de hier weergegeven hubs kan iedereen zich voor het $Projectname-netwerk aanmelden. Alle hubs in het netwerk zijn met elkaar verbonden, dus maakt het qua lidmaatschap niet uit waar je je aanmeldt. Op sommige hubs heb je eerst goedkeuring nodig en sommige hubs vereisen een financiële tegemoetkoming voor bepaalde uitbreidingen. <strong>Mogelijk</strong> wordt hierover op de hub zelf meer informatie gegeven."
+#: ../../Zotlabs/Module/Admin/Plugins.php:294
+#, php-format
+msgid "Plugin %s enabled."
+msgstr "Plugin %s ingeschakeld"
-#: ../../Zotlabs/Module/Pubsites.php:33
-msgid "Hub URL"
-msgstr "Hub-URL"
+#: ../../Zotlabs/Module/Admin/Plugins.php:310
+#: ../../Zotlabs/Module/Admin/Themes.php:95
+msgid "Disable"
+msgstr "Uitschakelen"
-#: ../../Zotlabs/Module/Pubsites.php:33
-msgid "Access Type"
-msgstr "Toegangs-<br/>&nbsp;type"
+#: ../../Zotlabs/Module/Admin/Plugins.php:313
+#: ../../Zotlabs/Module/Admin/Themes.php:97
+msgid "Enable"
+msgstr "Inschakelen"
-#: ../../Zotlabs/Module/Pubsites.php:33
-msgid "Registration Policy"
-msgstr "Registratie-<br/>&nbsp;beleid"
+#: ../../Zotlabs/Module/Admin/Plugins.php:342
+#: ../../Zotlabs/Module/Admin/Plugins.php:437 ../../include/widgets.php:1639
+msgid "Plugins"
+msgstr "Plugins"
-#: ../../Zotlabs/Module/Pubsites.php:33
-msgid "Stats"
-msgstr "Stats"
+#: ../../Zotlabs/Module/Admin/Plugins.php:343
+#: ../../Zotlabs/Module/Admin/Themes.php:124
+msgid "Toggle"
+msgstr "Omschakelen"
-#: ../../Zotlabs/Module/Pubsites.php:33
-msgid "Software"
-msgstr "Software"
+#: ../../Zotlabs/Module/Admin/Plugins.php:344
+#: ../../Zotlabs/Module/Admin/Themes.php:125 ../../Zotlabs/Lib/Apps.php:223
+#: ../../include/widgets.php:685 ../../include/nav.php:225
+msgid "Settings"
+msgstr "Instellingen"
-#: ../../Zotlabs/Module/Pubsites.php:35 ../../Zotlabs/Module/Ratings.php:97
-#: ../../include/conversation.php:940
-msgid "Ratings"
-msgstr "Beoordelingen"
+#: ../../Zotlabs/Module/Admin/Plugins.php:351
+#: ../../Zotlabs/Module/Admin/Themes.php:134
+msgid "Author: "
+msgstr "Auteur: "
-#: ../../Zotlabs/Module/Pubsites.php:48
-msgid "Rate"
-msgstr "Beoordeel"
+#: ../../Zotlabs/Module/Admin/Plugins.php:352
+#: ../../Zotlabs/Module/Admin/Themes.php:135
+msgid "Maintainer: "
+msgstr "Beheerder: "
-#: ../../Zotlabs/Module/Pubsites.php:59 ../../Zotlabs/Module/Blocks.php:166
-#: ../../Zotlabs/Module/Layouts.php:197 ../../Zotlabs/Module/Webpages.php:246
-#: ../../Zotlabs/Module/Wiki.php:146 ../../Zotlabs/Module/Events.php:685
-#: ../../include/page_widgets.php:42
-msgid "View"
-msgstr "Weergeven"
+#: ../../Zotlabs/Module/Admin/Plugins.php:353
+msgid "Minimum project version: "
+msgstr "Minimum versie Hubzilla: "
-#: ../../Zotlabs/Module/Editlayout.php:79
-#: ../../Zotlabs/Module/Editwebpage.php:80
-#: ../../Zotlabs/Module/Editblock.php:79 ../../Zotlabs/Module/Editblock.php:95
-#: ../../Zotlabs/Module/Editpost.php:24
-msgid "Item not found"
-msgstr "Item niet gevonden"
+#: ../../Zotlabs/Module/Admin/Plugins.php:354
+msgid "Maximum project version: "
+msgstr "Maximum versie Hubzilla:"
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:355
+msgid "Minimum PHP version: "
+msgstr "Minimum versie PHP: "
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:356
+msgid "Compatible Server Roles: "
+msgstr "Werkt met configuratietypes: "
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:357
+msgid "Requires: "
+msgstr "Vereist: "
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:358
+#: ../../Zotlabs/Module/Admin/Plugins.php:442
+msgid "Disabled - version incompatibility"
+msgstr "Uitgeschakeld - versie is incompatibel"
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:411
+msgid "Enter the public git repository URL of the plugin repo."
+msgstr "Vul de openbare Git-URL in van de plugin-repository."
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:412
+msgid "Plugin repo git URL"
+msgstr "Git-URL plugin-repository"
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:413
+msgid "Custom repo name"
+msgstr "Handmatige repository-naam"
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:413
+msgid "(optional)"
+msgstr "(niet verplicht)"
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:414
+msgid "Download Plugin Repo"
+msgstr "Plugin-repository downloaden"
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:421
+msgid "Install new repo"
+msgstr "Nieuwe repository installeren"
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:422 ../../Zotlabs/Lib/Apps.php:348
+msgid "Install"
+msgstr "Installeren"
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:423
+#: ../../Zotlabs/Module/Connedit.php:931 ../../Zotlabs/Module/Fbrowser.php:66
+#: ../../Zotlabs/Module/Fbrowser.php:88 ../../Zotlabs/Module/Profiles.php:804
+#: ../../Zotlabs/Module/Settings/Oauth.php:88
+#: ../../Zotlabs/Module/Settings/Oauth.php:114
+#: ../../Zotlabs/Module/Tagrm.php:15 ../../Zotlabs/Module/Tagrm.php:138
+#: ../../Zotlabs/Module/Wiki.php:261 ../../Zotlabs/Module/Wiki.php:286
+#: ../../extend/addon/addon/friendica/dfrn_request.php:879
+#: ../../extend/addon/addon/js_upload/js_upload.php:46
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:866
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1154
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:243
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:266
+#: ../../include/conversation.php:1394 ../../include/conversation.php:1443
+msgid "Cancel"
+msgstr "Annuleren"
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:445
+msgid "Manage Repos"
+msgstr "Repositories beheren"
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:446
+msgid "Installed Plugin Repositories"
+msgstr "Toegevoegde plugin-repositories"
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:447
+msgid "Install a New Plugin Repository"
+msgstr "Nieuwe plugin-repository toevoegen"
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:453
+#: ../../Zotlabs/Module/Connedit.php:929 ../../Zotlabs/Module/Profiles.php:802
+#: ../../Zotlabs/Module/Settings/Oauth.php:42
+#: ../../Zotlabs/Module/Settings/Oauth.php:113 ../../Zotlabs/Lib/Apps.php:348
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1152
+msgid "Update"
+msgstr "Bijwerken"
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:454
+msgid "Switch branch"
+msgstr "Branch veranderen"
+
+#: ../../Zotlabs/Module/Admin/Plugins.php:455
+#: ../../Zotlabs/Module/Photos.php:984 ../../Zotlabs/Module/Tagrm.php:137
+#: ../../extend/addon/addon/superblock/superblock.php:116
+msgid "Remove"
+msgstr "Verwijderen"
+
+#: ../../Zotlabs/Module/Admin/Themes.php:26
+msgid "Theme settings updated."
+msgstr "Thema-instellingen bijgewerkt."
+
+#: ../../Zotlabs/Module/Admin/Themes.php:61
+msgid "No themes found."
+msgstr "Geen thema's gevonden"
+
+#: ../../Zotlabs/Module/Admin/Themes.php:116
+msgid "Screenshot"
+msgstr "Schermafdruk"
+
+#: ../../Zotlabs/Module/Admin/Themes.php:123
+#: ../../Zotlabs/Module/Admin/Themes.php:157 ../../include/widgets.php:1640
+msgid "Themes"
+msgstr "Thema's"
+
+#: ../../Zotlabs/Module/Admin/Themes.php:162
+msgid "[Experimental]"
+msgstr "[Experimenteel]"
+
+#: ../../Zotlabs/Module/Admin/Themes.php:163
+msgid "[Unsupported]"
+msgstr "[Niet ondersteund]"
+
+#: ../../Zotlabs/Module/Uexport.php:57 ../../Zotlabs/Module/Uexport.php:58
+msgid "Export Channel"
+msgstr "Kanaal exporteren"
+
+#: ../../Zotlabs/Module/Uexport.php:59
+msgid ""
+"Export your basic channel information to a file. This acts as a backup of "
+"your connections, permissions, profile and basic data, which can be used to "
+"import your data to a new server hub, but does not contain your content."
+msgstr "Exporteer de basisinformatie van jouw kanaal naar een bestand. Dit fungeert als een back-up van jouw connecties, permissies, profiel en basisgegevens, die gebruikt kan worden om op een nieuwe hub jouw gegevens te importeren. Deze back-up bevat echter niet de inhoud van jouw kanaal."
+
+#: ../../Zotlabs/Module/Uexport.php:60
+msgid "Export Content"
+msgstr "Inhoud exporteren"
+
+#: ../../Zotlabs/Module/Uexport.php:61
+msgid ""
+"Export your channel information and recent content to a JSON backup that can"
+" be restored or imported to another server hub. This backs up all of your "
+"connections, permissions, profile data and several months of posts. This "
+"file may be VERY large. Please be patient - it may take several minutes for"
+" this download to begin."
+msgstr "Exporteer informatie en recente inhoud van jouw kanaal naar een JSON-back-up, wat kan worden gebruikt om jouw kanaal te herstellen of te importeren op een andere hub. Dit slaat al jouw connecties, permissies, profielgegevens en enkele maanden aan inhoud van jouw kanaal op. Dit bestand kan ZEER groot worden. Wees geduldig - het kan enkele minuten duren voordat de download begint."
+
+#: ../../Zotlabs/Module/Uexport.php:63
+msgid "Export your posts from a given year."
+msgstr "Exporteer jouw berichten uit een bepaald jaar."
+
+#: ../../Zotlabs/Module/Uexport.php:65
+msgid ""
+"You may also export your posts and conversations for a particular year or "
+"month. Adjust the date in your browser location bar to select other dates. "
+"If the export fails (possibly due to memory exhaustion on your server hub), "
+"please try again selecting a more limited date range."
+msgstr "Je kan ook berichten en conversaties uit een bepaald jaar of van een bepaalde maand exporteren. Verander de datum in de adresbalk van jouw webbrowser om andere jaren en maanden te selecteren. Wanneer het exporteren mislukt (waarschijnlijk door een gebrek aan beschikbaar servergeheugen), probeer het dan nogmaals met een beperkter tijdvak."
+
+#: ../../Zotlabs/Module/Uexport.php:66
+#, php-format
+msgid ""
+"To select all posts for a given year, such as this year, visit <a "
+"href=\"%1$s\">%2$s</a>"
+msgstr "Bezoek <a href=\"%1$s\">%2$s</a> om alle berichten van bijvoorbeeld dit jaar te selecteren. "
+
+#: ../../Zotlabs/Module/Uexport.php:67
+#, php-format
+msgid ""
+"To select all posts for a given month, such as January of this year, visit "
+"<a href=\"%1$s\">%2$s</a>"
+msgstr "Bezoek <a href=\"%1$s\">%2$s</a> om alle berichten van bijvoorbeeld januari dit jaar te selecteren."
+
+#: ../../Zotlabs/Module/Uexport.php:68
+#, php-format
+msgid ""
+"These content files may be imported or restored by visiting <a "
+"href=\"%1$s\">%2$s</a> on any site containing your channel. For best results"
+" please import or restore these in date order (oldest first)."
+msgstr "Deze back-up-bestanden kunnen geïmporteerd of hersteld worden door op jouw hub en met jouw kanaal <a href=\"%1$s\">%2$s</a> te bezoeken. Voor het beste resultaat kan je de bestanden in chronologische volgorde importeren of herstellen."
#: ../../Zotlabs/Module/Editlayout.php:127
#: ../../Zotlabs/Module/Layouts.php:128 ../../Zotlabs/Module/Layouts.php:188
@@ -2844,7 +2719,7 @@ msgstr "Naam lay-out"
#: ../../Zotlabs/Module/Editlayout.php:128
#: ../../Zotlabs/Module/Layouts.php:131
msgid "Layout Description (Optional)"
-msgstr "Lay-out-omschrijving (optioneel)"
+msgstr "Lay-out-omschrijving (niet verplicht)"
#: ../../Zotlabs/Module/Editlayout.php:136
msgid "Edit Layout"
@@ -2854,38 +2729,29 @@ msgstr "Lay-out bewerken"
msgid "Page link"
msgstr "Paginalink"
-#: ../../Zotlabs/Module/Editwebpage.php:146 ../../Zotlabs/Module/Mail.php:286
-#: ../../Zotlabs/Module/Mail.php:411 ../../Zotlabs/Module/Editblock.php:111
-#: ../../Zotlabs/Module/Chat.php:207 ../../include/conversation.php:1147
-msgid "Insert web link"
-msgstr "Weblink invoegen"
-
#: ../../Zotlabs/Module/Editwebpage.php:169
msgid "Edit Webpage"
msgstr "Webpagina bewerken"
-#: ../../Zotlabs/Module/Fbrowser.php:29 ../../Zotlabs/Lib/Apps.php:224
-#: ../../include/nav.php:95 ../../include/conversation.php:1674
-msgid "Photos"
-msgstr "Foto's"
+#: ../../Zotlabs/Module/Apps.php:45 ../../include/nav.php:178
+msgid "Apps"
+msgstr "Apps"
-#: ../../Zotlabs/Module/Channel.php:32 ../../Zotlabs/Module/Wiki.php:20
-#: ../../Zotlabs/Module/Chat.php:25
-#: ../../extend/addon/addon/chess/chess.php:400
-msgid "You must be logged in to see this page."
-msgstr "Je moet zijn ingelogd om deze pagina te kunnen bekijken."
+#: ../../Zotlabs/Module/Apps.php:48
+msgid "Manage apps"
+msgstr "Apps beheren"
-#: ../../Zotlabs/Module/Channel.php:44
-msgid "Posts and comments"
-msgstr "Berichten en reacties"
+#: ../../Zotlabs/Module/Apps.php:49
+msgid "Create new app"
+msgstr "Nieuwe app aanmaken"
-#: ../../Zotlabs/Module/Channel.php:45
-msgid "Only posts"
-msgstr "Alleen berichten"
+#: ../../Zotlabs/Module/Dirsearch.php:25 ../../Zotlabs/Module/Regdir.php:49
+msgid "This site is not a directory server"
+msgstr "Deze hub is geen kanalengidshub (directoryserver)"
-#: ../../Zotlabs/Module/Channel.php:104
-msgid "Insufficient permissions. Request redirected to profile page."
-msgstr "Onvoldoende permissies. Doorgestuurd naar profielpagina."
+#: ../../Zotlabs/Module/Dirsearch.php:33
+msgid "This directory server requires an access token"
+msgstr "Deze kanalengidshub (directoryserver) heeft een toegangs-token nodig"
#: ../../Zotlabs/Module/Network.php:96
msgid "No such group"
@@ -2915,6 +2781,11 @@ msgstr "Privacygroep: "
msgid "Invalid connection."
msgstr "Ongeldige connectie."
+#: ../../Zotlabs/Module/Network.php:275
+#: ../../extend/addon/addon/redred/redred.php:65
+msgid "Invalid channel."
+msgstr "Onbekend kanaal."
+
#: ../../Zotlabs/Module/Menu.php:49
msgid "Unable to update menu."
msgstr "Niet in staat om menu aan te passen"
@@ -2951,18 +2822,22 @@ msgstr "Menu kan gebruikt worden om bladwijzers in op te slaan"
msgid "Submit and proceed"
msgstr "Opslaan en doorgaan"
-#: ../../Zotlabs/Module/Menu.php:107 ../../include/text.php:2271
+#: ../../Zotlabs/Module/Menu.php:107 ../../include/text.php:2289
msgid "Menus"
msgstr "Menu's"
-#: ../../Zotlabs/Module/Menu.php:114 ../../Zotlabs/Module/Blocks.php:157
-#: ../../Zotlabs/Module/Layouts.php:190 ../../Zotlabs/Module/Webpages.php:251
+#: ../../Zotlabs/Module/Menu.php:113 ../../Zotlabs/Module/Locs.php:120
+msgid "Drop"
+msgstr "Verwijderen"
+
+#: ../../Zotlabs/Module/Menu.php:114 ../../Zotlabs/Module/Webpages.php:255
+#: ../../Zotlabs/Module/Blocks.php:157 ../../Zotlabs/Module/Layouts.php:190
#: ../../include/page_widgets.php:47
msgid "Created"
msgstr "Aangemaakt"
-#: ../../Zotlabs/Module/Menu.php:115 ../../Zotlabs/Module/Blocks.php:158
-#: ../../Zotlabs/Module/Layouts.php:191 ../../Zotlabs/Module/Webpages.php:252
+#: ../../Zotlabs/Module/Menu.php:115 ../../Zotlabs/Module/Webpages.php:256
+#: ../../Zotlabs/Module/Blocks.php:158 ../../Zotlabs/Module/Layouts.php:191
#: ../../include/page_widgets.php:48
msgid "Edited"
msgstr "Bewerkt"
@@ -3024,835 +2899,822 @@ msgstr "Bladwijzers toestaan"
msgid "Not found."
msgstr "Niet gevonden."
-#: ../../Zotlabs/Module/Appman.php:37 ../../Zotlabs/Module/Appman.php:53
-msgid "App installed."
-msgstr "App geïnstalleerd"
-
-#: ../../Zotlabs/Module/Appman.php:46
-msgid "Malformed app."
-msgstr "Misvormde app."
-
-#: ../../Zotlabs/Module/Appman.php:105
-msgid "Embed code"
-msgstr "Insluitcode"
-
-#: ../../Zotlabs/Module/Appman.php:111 ../../include/widgets.php:107
-msgid "Edit App"
-msgstr "App bewerken"
-
-#: ../../Zotlabs/Module/Appman.php:111
-msgid "Create App"
-msgstr "App maken"
-
-#: ../../Zotlabs/Module/Appman.php:116
-msgid "Name of app"
-msgstr "Naam van app"
-
-#: ../../Zotlabs/Module/Appman.php:116 ../../Zotlabs/Module/Appman.php:117
-#: ../../Zotlabs/Module/Profiles.php:703 ../../Zotlabs/Module/Profiles.php:707
-#: ../../Zotlabs/Module/Events.php:453 ../../Zotlabs/Module/Events.php:458
-#: ../../include/datetime.php:259
-msgid "Required"
-msgstr "Vereist"
-
-#: ../../Zotlabs/Module/Appman.php:117
-msgid "Location (URL) of app"
-msgstr "Locatie (URL) van app"
-
-#: ../../Zotlabs/Module/Appman.php:118 ../../Zotlabs/Module/Rbmark.php:101
-#: ../../Zotlabs/Module/Events.php:466
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:838
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:165
-msgid "Description"
-msgstr "Omschrijving"
-
-#: ../../Zotlabs/Module/Appman.php:119
-msgid "Photo icon URL"
-msgstr "URL van pictogram"
-
-#: ../../Zotlabs/Module/Appman.php:119
-msgid "80 x 80 pixels - optional"
-msgstr "80 x 80 pixels (optioneel)"
-
-#: ../../Zotlabs/Module/Appman.php:120
-msgid "Categories (optional, comma separated list)"
-msgstr "Categorieën (optioneel, door komma's gescheiden lijst)"
-
-#: ../../Zotlabs/Module/Appman.php:121
-msgid "Version ID"
-msgstr "Versie-ID"
-
-#: ../../Zotlabs/Module/Appman.php:122
-msgid "Price of app"
-msgstr "Prijs van de app"
-
-#: ../../Zotlabs/Module/Appman.php:123
-msgid "Location (URL) to purchase app"
-msgstr "Locatie (URL) om de app aan te schaffen"
-
-#: ../../Zotlabs/Module/Rpost.php:138 ../../Zotlabs/Module/Editpost.php:107
+#: ../../Zotlabs/Module/Rpost.php:138 ../../Zotlabs/Module/Editpost.php:108
msgid "Edit post"
msgstr "Bericht bewerken"
-#: ../../Zotlabs/Module/Help.php:23
-msgid "Documentation Search"
-msgstr "Zoek documentatie"
+#: ../../Zotlabs/Module/Locs.php:25 ../../Zotlabs/Module/Locs.php:54
+msgid "Location not found."
+msgstr "Locatie niet gevonden."
-#: ../../Zotlabs/Module/Help.php:80 ../../include/conversation.php:1665
-msgid "About"
-msgstr "Over"
+#: ../../Zotlabs/Module/Locs.php:62
+msgid "Location lookup failed."
+msgstr "Opzoeken locatie mislukt"
-#: ../../Zotlabs/Module/Help.php:81 ../../Zotlabs/Module/Group.php:197
-msgid "Members"
-msgstr "Kanalen"
+#: ../../Zotlabs/Module/Locs.php:66
+msgid ""
+"Please select another location to become primary before removing the primary"
+" location."
+msgstr "Kies eerst een andere primaire locatie alvorens de huidige primaire locatie te verwijderen."
-#: ../../Zotlabs/Module/Help.php:82
-msgid "Administrators"
-msgstr "Beheerders"
+#: ../../Zotlabs/Module/Locs.php:95
+msgid "Syncing locations"
+msgstr "Locaties synchronizeren"
-#: ../../Zotlabs/Module/Help.php:83
-msgid "Developers"
-msgstr "Ontwikkelaars"
+#: ../../Zotlabs/Module/Locs.php:105
+msgid "No locations found."
+msgstr "Geen locaties gevonden."
-#: ../../Zotlabs/Module/Help.php:84
-msgid "Tutorials"
-msgstr "Zelfstudie"
+#: ../../Zotlabs/Module/Locs.php:116
+msgid "Manage Channel Locations"
+msgstr "Kanaallocaties beheren"
-#: ../../Zotlabs/Module/Help.php:93
-msgid "$Projectname Documentation"
-msgstr "$Projectname-documentatie"
+#: ../../Zotlabs/Module/Locs.php:117 ../../Zotlabs/Module/Pubsites.php:51
+#: ../../Zotlabs/Module/Events.php:475 ../../Zotlabs/Module/Profiles.php:509
+#: ../../Zotlabs/Module/Profiles.php:737
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:839
+#: ../../include/js_strings.php:25
+msgid "Location"
+msgstr "Locatie"
-#: ../../Zotlabs/Module/Help.php:94
-msgid "Contents"
-msgstr "Inhoud"
+#: ../../Zotlabs/Module/Locs.php:119
+msgid "Primary"
+msgstr "Primair"
-#: ../../Zotlabs/Module/Ffsapi.php:12
-msgid "Share content from Firefox to $Projectname"
-msgstr "Deel webpagina's vanuit Firefox met "
+#: ../../Zotlabs/Module/Locs.php:122
+msgid "Sync Now"
+msgstr "Nu synchroniseren"
-#: ../../Zotlabs/Module/Ffsapi.php:15
-msgid "Activate the Firefox $Projectname provider"
-msgstr "Activeer de $Projectname-service in Firefox"
+#: ../../Zotlabs/Module/Locs.php:123
+msgid "Please wait several minutes between consecutive operations."
+msgstr "Wacht enkele minuten tussen opeenvolgende handelingen."
-#: ../../Zotlabs/Module/Apps.php:46 ../../include/nav.php:166
-#: ../../include/widgets.php:102
-msgid "Apps"
-msgstr "Apps"
+#: ../../Zotlabs/Module/Locs.php:124
+msgid ""
+"When possible, drop a location by logging into that website/hub and removing"
+" your channel."
+msgstr "Wij adviseren, wanneer dit (nog) mogelijk is, de locatie te verwijderen door op de hub van de kloon in te loggen en het kanaal daar te verwijderen."
-#: ../../Zotlabs/Module/Home.php:74 ../../Zotlabs/Module/Home.php:82
-msgid "$Projectname"
-msgstr "$Projectname"
+#: ../../Zotlabs/Module/Locs.php:125
+msgid "Use this form to drop the location if the hub is no longer operating."
+msgstr "Gebruik dit formulier om de locatie te verwijderen wanneer de hub van de kloon niet meer operationeel is."
-#: ../../Zotlabs/Module/Home.php:92
-#, php-format
-msgid "Welcome to %s"
-msgstr "Welkom op %s"
+#: ../../Zotlabs/Module/Pubsites.php:24 ../../include/widgets.php:1401
+msgid "Public Hubs"
+msgstr "Openbare hubs"
-#: ../../Zotlabs/Module/Filestorage.php:87
-msgid "Permission Denied."
-msgstr "Toegang geweigerd"
+#: ../../Zotlabs/Module/Pubsites.php:27
+msgid ""
+"The listed hubs allow public registration for the $Projectname network. All "
+"hubs in the network are interlinked so membership on any of them conveys "
+"membership in the network as a whole. Some hubs may require subscription or "
+"provide tiered service plans. The hub itself <strong>may</strong> provide "
+"additional details."
+msgstr "Op de hier weergegeven hubs kan iedereen zich voor het $Projectname-netwerk aanmelden. Alle hubs in het netwerk zijn met elkaar verbonden, dus maakt het qua lidmaatschap niet uit waar je je aanmeldt. Op sommige hubs heb je eerst goedkeuring nodig en sommige hubs vereisen een financiële tegemoetkoming voor bepaalde uitbreidingen. <strong>Mogelijk</strong> wordt hierover op de hub zelf meer informatie gegeven."
-#: ../../Zotlabs/Module/Filestorage.php:103
-msgid "File not found."
-msgstr "Bestand niet gevonden."
+#: ../../Zotlabs/Module/Pubsites.php:33
+msgid "Hub URL"
+msgstr "Hub-URL"
-#: ../../Zotlabs/Module/Filestorage.php:146
-msgid "Edit file permissions"
-msgstr "Bestandsrechten bewerken"
+#: ../../Zotlabs/Module/Pubsites.php:33
+msgid "Access Type"
+msgstr "Toegangs-<br/>&nbsp;type"
-#: ../../Zotlabs/Module/Filestorage.php:152
-#: ../../Zotlabs/Module/Photos.php:658 ../../Zotlabs/Module/Photos.php:1047
-#: ../../Zotlabs/Module/Thing.php:313 ../../Zotlabs/Module/Thing.php:363
-#: ../../Zotlabs/Module/Chat.php:234 ../../include/acl_selectors.php:208
-msgid "Permissions"
-msgstr "Permissies"
+#: ../../Zotlabs/Module/Pubsites.php:33
+msgid "Registration Policy"
+msgstr "Registratie-<br/>&nbsp;beleid"
-#: ../../Zotlabs/Module/Filestorage.php:159
-msgid "Set/edit permissions"
-msgstr "Rechten instellen/bewerken"
+#: ../../Zotlabs/Module/Pubsites.php:33
+msgid "Stats"
+msgstr "Stats"
-#: ../../Zotlabs/Module/Filestorage.php:160
-msgid "Include all files and sub folders"
-msgstr "Toepassen op alle bestanden en submappen"
+#: ../../Zotlabs/Module/Pubsites.php:33
+msgid "Software"
+msgstr "Software"
-#: ../../Zotlabs/Module/Filestorage.php:161
-msgid "Return to file list"
-msgstr "Terugkeren naar bestandlijst "
+#: ../../Zotlabs/Module/Pubsites.php:35 ../../Zotlabs/Module/Ratings.php:97
+#: ../../include/conversation.php:941 ../../include/conversation.php:1099
+msgid "Ratings"
+msgstr "Beoordelingen"
-#: ../../Zotlabs/Module/Filestorage.php:163
-msgid "Copy/paste this code to attach file to a post"
-msgstr "Kopieer/plak deze code om het bestand aan een bericht te koppelen"
+#: ../../Zotlabs/Module/Pubsites.php:48
+msgid "Rate"
+msgstr "Beoordeel"
-#: ../../Zotlabs/Module/Filestorage.php:164
-msgid "Copy/paste this URL to link file from a web page"
-msgstr "Kopieer/plak deze URL om het bestand aan een externe webpagina te koppelen"
+#: ../../Zotlabs/Module/Pubsites.php:59 ../../Zotlabs/Module/Events.php:694
+#: ../../Zotlabs/Module/Webpages.php:250 ../../Zotlabs/Module/Blocks.php:166
+#: ../../Zotlabs/Module/Layouts.php:197 ../../Zotlabs/Module/Wiki.php:166
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:151
+#: ../../include/page_widgets.php:42
+msgid "View"
+msgstr "Weergeven"
-#: ../../Zotlabs/Module/Filestorage.php:166
-msgid "Share this file"
-msgstr "Dit bestand delen"
+#: ../../Zotlabs/Module/Connedit.php:82
+msgid "Could not access contact record."
+msgstr "Kon geen toegang krijgen tot de connectie-gegevens."
-#: ../../Zotlabs/Module/Filestorage.php:167
-msgid "Show URL to this file"
-msgstr "Toon URL van dit bestand"
+#: ../../Zotlabs/Module/Connedit.php:112
+msgid "Could not locate selected profile."
+msgstr "Kon het gekozen profiel niet vinden."
-#: ../../Zotlabs/Module/Filestorage.php:168
-msgid "Notify your contacts about this file"
-msgstr "Jouw connecties over dit bestand berichten"
+#: ../../Zotlabs/Module/Connedit.php:249
+msgid "Connection updated."
+msgstr "Connectie bijgewerkt."
-#: ../../Zotlabs/Module/Directory.php:64 ../../Zotlabs/Module/Display.php:17
-#: ../../Zotlabs/Module/Ratings.php:83 ../../Zotlabs/Module/Photos.php:509
-#: ../../Zotlabs/Module/Search.php:17
-#: ../../Zotlabs/Module/Viewconnections.php:23
-#: ../../extend/addon/addon/friendica/dfrn_request.php:794
-msgid "Public access denied."
-msgstr "Openbare toegang geweigerd."
+#: ../../Zotlabs/Module/Connedit.php:251
+msgid "Failed to update connection record."
+msgstr "Bijwerken van connectie-gegevens mislukt."
-#: ../../Zotlabs/Module/Directory.php:245
-#, php-format
-msgid "%d rating"
-msgid_plural "%d ratings"
-msgstr[0] "%d beoordeling"
-msgstr[1] "%d beoordelingen"
+#: ../../Zotlabs/Module/Connedit.php:301
+msgid "is now connected to"
+msgstr "is nu verbonden met"
-#: ../../Zotlabs/Module/Directory.php:256
-msgid "Gender: "
-msgstr "Geslacht:"
+#: ../../Zotlabs/Module/Connedit.php:434
+msgid "Could not access address book record."
+msgstr "Kon geen toegang krijgen tot de record van de connectie."
-#: ../../Zotlabs/Module/Directory.php:258
-msgid "Status: "
-msgstr "Status: "
+#: ../../Zotlabs/Module/Connedit.php:482
+msgid "Refresh failed - channel is currently unavailable."
+msgstr "Vernieuwen mislukt - kanaal is momenteel niet beschikbaar"
-#: ../../Zotlabs/Module/Directory.php:260
-msgid "Homepage: "
-msgstr "Homepage: "
+#: ../../Zotlabs/Module/Connedit.php:497 ../../Zotlabs/Module/Connedit.php:506
+#: ../../Zotlabs/Module/Connedit.php:515 ../../Zotlabs/Module/Connedit.php:524
+#: ../../Zotlabs/Module/Connedit.php:537
+msgid "Unable to set address book parameters."
+msgstr "Niet in staat om de parameters van connecties in te stellen."
-#: ../../Zotlabs/Module/Directory.php:309 ../../include/channel.php:1215
-msgid "Age:"
-msgstr "Leeftijd:"
+#: ../../Zotlabs/Module/Connedit.php:561
+msgid "Connection has been removed."
+msgstr "Connectie is verwijderd"
-#: ../../Zotlabs/Module/Directory.php:314 ../../include/channel.php:1051
-#: ../../include/bb2diaspora.php:521 ../../include/event.php:52
-#: ../../include/event.php:84
-msgid "Location:"
-msgstr "Plaats:"
+#: ../../Zotlabs/Module/Connedit.php:601 ../../Zotlabs/Lib/Apps.php:228
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:57
+#: ../../include/conversation.php:936 ../../include/conversation.php:1049
+#: ../../include/nav.php:103
+msgid "View Profile"
+msgstr "Profiel weergeven"
-#: ../../Zotlabs/Module/Directory.php:320
-msgid "Description:"
-msgstr "Omschrijving:"
+#: ../../Zotlabs/Module/Connedit.php:604
+#, php-format
+msgid "View %s's profile"
+msgstr "Profiel van %s weergeven"
-#: ../../Zotlabs/Module/Directory.php:325 ../../include/channel.php:1231
-msgid "Hometown:"
-msgstr "Oorspronkelijk uit:"
+#: ../../Zotlabs/Module/Connedit.php:608
+msgid "Refresh Permissions"
+msgstr "Permissies vernieuwen"
-#: ../../Zotlabs/Module/Directory.php:327 ../../include/channel.php:1239
-msgid "About:"
-msgstr "Over:"
+#: ../../Zotlabs/Module/Connedit.php:611
+msgid "Fetch updated permissions"
+msgstr "Aangepaste permissies ophalen"
-#: ../../Zotlabs/Module/Directory.php:329
-msgid "Public Forum:"
-msgstr "Openbaar forum:"
+#: ../../Zotlabs/Module/Connedit.php:615
+msgid "Refresh Photo"
+msgstr "Foto vernieuwen"
-#: ../../Zotlabs/Module/Directory.php:332
-msgid "Keywords: "
-msgstr "Trefwoorden: "
+#: ../../Zotlabs/Module/Connedit.php:618
+msgid "Fetch updated photo"
+msgstr "Aangepaste foto ophalen"
-#: ../../Zotlabs/Module/Directory.php:335
-msgid "Don't suggest"
-msgstr "Niet voorstellen"
+#: ../../Zotlabs/Module/Connedit.php:622
+msgid "Recent Activity"
+msgstr "Recente activiteit/berichten"
-#: ../../Zotlabs/Module/Directory.php:337
-msgid "Common connections:"
-msgstr "Gemeenschappelijke connecties:"
+#: ../../Zotlabs/Module/Connedit.php:625
+msgid "View recent posts and comments"
+msgstr "Recente berichten en reacties weergeven"
-#: ../../Zotlabs/Module/Directory.php:386
-msgid "Global Directory"
-msgstr "Volledige kanalengids"
+#: ../../Zotlabs/Module/Connedit.php:632
+msgid "Block (or Unblock) all communications with this connection"
+msgstr "Blokkeer (of deblokkeer) alle communicatie met deze connectie"
-#: ../../Zotlabs/Module/Directory.php:386
-msgid "Local Directory"
-msgstr "Lokale kanalengids"
+#: ../../Zotlabs/Module/Connedit.php:633
+msgid "This connection is blocked!"
+msgstr "Deze connectie is geblokkeerd!"
-#: ../../Zotlabs/Module/Directory.php:392
-msgid "Finding:"
-msgstr "Gezocht naar:"
+#: ../../Zotlabs/Module/Connedit.php:637
+msgid "Unignore"
+msgstr "Niet meer negeren"
-#: ../../Zotlabs/Module/Directory.php:395 ../../Zotlabs/Module/Suggest.php:64
-#: ../../include/contact_widgets.php:24
-msgid "Channel Suggestions"
-msgstr "Voorgestelde kanalen"
+#: ../../Zotlabs/Module/Connedit.php:640
+msgid "Ignore (or Unignore) all inbound communications from this connection"
+msgstr "Negeer (of negeer niet meer) alle inkomende communicatie van deze connectie"
-#: ../../Zotlabs/Module/Directory.php:397
-msgid "next page"
-msgstr "volgende pagina"
+#: ../../Zotlabs/Module/Connedit.php:641
+msgid "This connection is ignored!"
+msgstr "Deze connectie wordt genegeerd!"
-#: ../../Zotlabs/Module/Directory.php:397
-msgid "previous page"
-msgstr "vorige pagina"
+#: ../../Zotlabs/Module/Connedit.php:645
+msgid "Unarchive"
+msgstr "Niet meer archiveren"
-#: ../../Zotlabs/Module/Directory.php:398
-msgid "Sort options"
-msgstr "Sorteeropties"
+#: ../../Zotlabs/Module/Connedit.php:645
+msgid "Archive"
+msgstr "Archiveren"
-#: ../../Zotlabs/Module/Directory.php:399
-msgid "Alphabetic"
-msgstr "Alfabetisch"
+#: ../../Zotlabs/Module/Connedit.php:648
+msgid ""
+"Archive (or Unarchive) this connection - mark channel dead but keep content"
+msgstr "Archiveer (of dearchiveer) deze connectie - markeer het kanaal als dood, maar bewaar de inhoud"
-#: ../../Zotlabs/Module/Directory.php:400
-msgid "Reverse Alphabetic"
-msgstr "Omgekeerd alfabetisch"
+#: ../../Zotlabs/Module/Connedit.php:649
+msgid "This connection is archived!"
+msgstr "Deze connectie is gearchiveerd!"
-#: ../../Zotlabs/Module/Directory.php:401
-msgid "Newest to Oldest"
-msgstr "Nieuw naar oud"
+#: ../../Zotlabs/Module/Connedit.php:653
+msgid "Unhide"
+msgstr "Niet meer verbergen"
-#: ../../Zotlabs/Module/Directory.php:402
-msgid "Oldest to Newest"
-msgstr "Oud naar nieuw"
+#: ../../Zotlabs/Module/Connedit.php:653
+msgid "Hide"
+msgstr "Verbergen"
-#: ../../Zotlabs/Module/Directory.php:419
-msgid "No entries (some entries may be hidden)."
-msgstr "Niets gevonden (sommige kanalen kunnen verborgen zijn)."
+#: ../../Zotlabs/Module/Connedit.php:656
+msgid "Hide or Unhide this connection from your other connections"
+msgstr "Deze connectie verbergen (of niet meer verbergen) voor jouw andere connecties"
-#: ../../Zotlabs/Module/Item.php:184
-msgid "Unable to locate original post."
-msgstr "Niet in staat om de originele locatie van het bericht te vinden. "
+#: ../../Zotlabs/Module/Connedit.php:657
+msgid "This connection is hidden!"
+msgstr "Deze connectie is verborgen!"
-#: ../../Zotlabs/Module/Item.php:447
-msgid "Empty post discarded."
-msgstr "Leeg bericht geannuleerd"
+#: ../../Zotlabs/Module/Connedit.php:664
+msgid "Delete this connection"
+msgstr "Deze connectie verwijderen"
-#: ../../Zotlabs/Module/Item.php:489
-msgid "Executable content type not permitted to this channel."
-msgstr "Uitvoerbare bestanden zijn niet toegestaan op dit kanaal."
+#: ../../Zotlabs/Module/Connedit.php:672
+msgid "Fetch Vcard"
+msgstr "Vcard ophalen"
-#: ../../Zotlabs/Module/Item.php:837
-msgid "Duplicate post suppressed."
-msgstr "Dubbel bericht tegengehouden."
+#: ../../Zotlabs/Module/Connedit.php:675
+msgid "Fetch electronic calling card for this connection"
+msgstr "Visitekaartje van deze connectie ophalen"
-#: ../../Zotlabs/Module/Item.php:979
-msgid "System error. Post not saved."
-msgstr "Systeemfout. Bericht niet opgeslagen."
+#: ../../Zotlabs/Module/Connedit.php:683
+#: ../../Zotlabs/Module/Filestorage.php:152
+#: ../../Zotlabs/Module/Photos.php:657 ../../Zotlabs/Module/Photos.php:1042
+#: ../../Zotlabs/Module/Thing.php:313 ../../Zotlabs/Module/Thing.php:363
+#: ../../Zotlabs/Module/Chat.php:232 ../../include/acl_selectors.php:218
+msgid "Permissions"
+msgstr "Permissies"
-#: ../../Zotlabs/Module/Item.php:1111
-msgid "Unable to obtain post information from database."
-msgstr "Niet in staat om informatie over dit bericht uit de database te verkrijgen."
+#: ../../Zotlabs/Module/Connedit.php:686
+msgid "Open Individual Permissions section by default"
+msgstr "Sectie met individuele permissies standaard openen"
-#: ../../Zotlabs/Module/Item.php:1118
-#, php-format
-msgid "You have reached your limit of %1$.0f top level posts."
-msgstr "Je hebt jouw limiet van %1$.0f berichten bereikt."
+#: ../../Zotlabs/Module/Connedit.php:709
+msgid "Affinity"
+msgstr "Affiniteit"
-#: ../../Zotlabs/Module/Item.php:1125
-#, php-format
-msgid "You have reached your limit of %1$.0f webpages."
-msgstr "Je hebt jouw limiet van %1$.0f webpagina's bereikt."
+#: ../../Zotlabs/Module/Connedit.php:712
+msgid "Open Set Affinity section by default"
+msgstr "Sectie met de affiniteitsinstelling standaard openen"
-#: ../../Zotlabs/Module/Chanview.php:134
-msgid "toggle full screen mode"
-msgstr "Volledig scherm"
+#: ../../Zotlabs/Module/Connedit.php:716 ../../include/widgets.php:526
+msgid "Me"
+msgstr "Ik"
-#: ../../Zotlabs/Module/Follow.php:31
-msgid "Channel added."
-msgstr "Kanaal toegevoegd."
+#: ../../Zotlabs/Module/Connedit.php:717 ../../include/widgets.php:527
+msgid "Family"
+msgstr "Familie"
-#: ../../Zotlabs/Module/Mail.php:66
-msgid "Unable to lookup recipient."
-msgstr "Niet in staat om ontvanger op te zoeken."
+#: ../../Zotlabs/Module/Connedit.php:718
+#: ../../Zotlabs/Module/Settings/Channel.php:62
+#: ../../Zotlabs/Module/Settings/Channel.php:66
+#: ../../Zotlabs/Module/Settings/Channel.php:67
+#: ../../Zotlabs/Module/Settings/Channel.php:70
+#: ../../Zotlabs/Module/Settings/Channel.php:81 ../../include/widgets.php:528
+#: ../../include/selectors.php:123 ../../include/channel.php:408
+#: ../../include/channel.php:409 ../../include/channel.php:416
+msgid "Friends"
+msgstr "Vrienden"
-#: ../../Zotlabs/Module/Mail.php:73
-msgid "Unable to communicate with requested channel."
-msgstr "Niet in staat om met het aangevraagde kanaal te communiceren."
+#: ../../Zotlabs/Module/Connedit.php:719 ../../include/widgets.php:529
+msgid "Acquaintances"
+msgstr "Kennissen"
-#: ../../Zotlabs/Module/Mail.php:80
-msgid "Cannot verify requested channel."
-msgstr "Kan opgevraagd kanaal niet verifieren"
+#: ../../Zotlabs/Module/Connedit.php:746
+msgid "Filter"
+msgstr "Filter"
-#: ../../Zotlabs/Module/Mail.php:98
-msgid "Selected channel has private message restrictions. Send failed."
-msgstr "Gekozen kanaal heeft restricties voor privéberichten. Verzenden mislukt."
+#: ../../Zotlabs/Module/Connedit.php:749
+msgid "Open Custom Filter section by default"
+msgstr "Sectie met de berichtenfilter standaard openen"
-#: ../../Zotlabs/Module/Mail.php:177
-msgid "Messages"
-msgstr "Berichten"
+#: ../../Zotlabs/Module/Connedit.php:786
+msgid "Approve this connection"
+msgstr "Deze connectie accepteren"
-#: ../../Zotlabs/Module/Mail.php:212
-msgid "Message recalled."
-msgstr "Bericht ingetrokken."
+#: ../../Zotlabs/Module/Connedit.php:786
+msgid "Accept connection to allow communication"
+msgstr "Keur deze connectie goed om communicatie toe te staan"
-#: ../../Zotlabs/Module/Mail.php:225
-msgid "Conversation removed."
-msgstr "Conversatie verwijderd"
+#: ../../Zotlabs/Module/Connedit.php:791
+msgid "Set Affinity"
+msgstr "Affiniteit instellen"
-#: ../../Zotlabs/Module/Mail.php:239 ../../Zotlabs/Module/Mail.php:348
-#: ../../Zotlabs/Module/Chat.php:205 ../../include/conversation.php:1182
-msgid "Please enter a link URL:"
-msgstr "Vul een URL in:"
+#: ../../Zotlabs/Module/Connedit.php:794
+msgid "Set Profile"
+msgstr "Profiel instellen"
-#: ../../Zotlabs/Module/Mail.php:240 ../../Zotlabs/Module/Mail.php:349
-msgid "Expires YYYY-MM-DD HH:MM"
-msgstr "Verloopt op DD-MM-YYYY om HH:MM"
+#: ../../Zotlabs/Module/Connedit.php:797
+msgid "Set Affinity & Profile"
+msgstr "Affiniteit en profiel instellen"
-#: ../../Zotlabs/Module/Mail.php:268
-msgid "Requested channel is not in this network"
-msgstr "Opgevraagd kanaal is niet in dit netwerk beschikbaar"
+#: ../../Zotlabs/Module/Connedit.php:855
+msgid "none"
+msgstr "geen"
-#: ../../Zotlabs/Module/Mail.php:276
-msgid "Send Private Message"
-msgstr "Privébericht versturen"
+#: ../../Zotlabs/Module/Connedit.php:858 ../../include/widgets.php:661
+msgid "Connection Default Permissions"
+msgstr "Standaard permissies voor connecties"
-#: ../../Zotlabs/Module/Mail.php:277 ../../Zotlabs/Module/Mail.php:402
-msgid "To:"
-msgstr "Aan:"
+#: ../../Zotlabs/Module/Connedit.php:858 ../../include/items.php:3934
+#, php-format
+msgid "Connection: %s"
+msgstr "Connectie: %s"
-#: ../../Zotlabs/Module/Mail.php:280 ../../Zotlabs/Module/Mail.php:404
-msgid "Subject:"
-msgstr "Onderwerp:"
+#: ../../Zotlabs/Module/Connedit.php:859
+msgid "Apply these permissions automatically"
+msgstr "Deze permissies automatisch toepassen"
-#: ../../Zotlabs/Module/Mail.php:283 ../../Zotlabs/Module/Invite.php:138
-msgid "Your message:"
-msgstr "Jouw bericht:"
+#: ../../Zotlabs/Module/Connedit.php:859
+msgid "Connection requests will be approved without your interaction"
+msgstr "Connectieverzoeken zullen automatisch worden geaccepteerd"
-#: ../../Zotlabs/Module/Mail.php:285 ../../Zotlabs/Module/Mail.php:410
-#: ../../include/conversation.php:1242
-msgid "Attach file"
-msgstr "Bestand toevoegen"
+#: ../../Zotlabs/Module/Connedit.php:860
+msgid "Permission role"
+msgstr "Permissietype"
-#: ../../Zotlabs/Module/Mail.php:287
-msgid "Send"
-msgstr "Verzenden"
+#: ../../Zotlabs/Module/Connedit.php:861
+msgid "Add permission role"
+msgstr "Permissietype toevoegen"
-#: ../../Zotlabs/Module/Mail.php:290 ../../Zotlabs/Module/Mail.php:415
-#: ../../include/conversation.php:1287
-msgid "Set expiration date"
-msgstr "Verloopdatum instellen"
+#: ../../Zotlabs/Module/Connedit.php:867
+msgid "This connection's primary address is"
+msgstr "Het primaire kanaaladres van deze connectie is"
-#: ../../Zotlabs/Module/Mail.php:292 ../../Zotlabs/Module/Mail.php:417
-#: ../../Zotlabs/Module/Chat.php:206 ../../Zotlabs/Lib/ThreadItem.php:741
-#: ../../include/conversation.php:1292
-msgid "Encrypt text"
-msgstr "Tekst versleutelen"
+#: ../../Zotlabs/Module/Connedit.php:868
+msgid "Available locations:"
+msgstr "Beschikbare locaties:"
-#: ../../Zotlabs/Module/Mail.php:374
-msgid "Delete message"
-msgstr "Bericht verwijderen"
+#: ../../Zotlabs/Module/Connedit.php:872
+msgid ""
+"The permissions indicated on this page will be applied to all new "
+"connections."
+msgstr "Permissies die op deze pagina staan vermeld worden op alle nieuwe connecties toegepast."
-#: ../../Zotlabs/Module/Mail.php:375
-msgid "Delivery report"
-msgstr "Afleveringsrapport"
+#: ../../Zotlabs/Module/Connedit.php:873
+msgid "Connection Tools"
+msgstr "Hulpmiddelen"
-#: ../../Zotlabs/Module/Mail.php:376
-msgid "Recall message"
-msgstr "Bericht intrekken"
+#: ../../Zotlabs/Module/Connedit.php:875
+msgid "Slide to adjust your degree of friendship"
+msgstr "Schuif om te bepalen hoe goed je iemand kent en/of mag"
-#: ../../Zotlabs/Module/Mail.php:378
-msgid "Message has been recalled."
-msgstr "Bericht is ingetrokken."
+#: ../../Zotlabs/Module/Connedit.php:876 ../../Zotlabs/Module/Rate.php:155
+#: ../../include/js_strings.php:20
+msgid "Rating"
+msgstr "Beoordeling"
-#: ../../Zotlabs/Module/Mail.php:395
-msgid "Delete Conversation"
-msgstr "Verwijder conversatie"
+#: ../../Zotlabs/Module/Connedit.php:877
+msgid "Slide to adjust your rating"
+msgstr "Gebruik de schuif om je beoordeling te geven"
-#: ../../Zotlabs/Module/Mail.php:397
-msgid ""
-"No secure communications available. You <strong>may</strong> be able to "
-"respond from the sender's profile page."
-msgstr "Geen veilige communicatie beschikbaar. <strong>Mogelijk</strong> kan je reageren op de kanaalpagina van de afzender."
+#: ../../Zotlabs/Module/Connedit.php:878 ../../Zotlabs/Module/Connedit.php:883
+msgid "Optionally explain your rating"
+msgstr "Verklaar jouw beoordeling (niet verplicht)"
-#: ../../Zotlabs/Module/Mail.php:401
-msgid "Send Reply"
-msgstr "Antwoord versturen"
+#: ../../Zotlabs/Module/Connedit.php:880
+msgid "Custom Filter"
+msgstr "Berichtenfilter"
-#: ../../Zotlabs/Module/Mail.php:406
-#, php-format
-msgid "Your message for %s (%s):"
-msgstr "Jouw privébericht aan %s (%s):"
+#: ../../Zotlabs/Module/Connedit.php:881
+msgid "Only import posts with this text"
+msgstr "Importeer alleen berichten met deze tekst"
-#: ../../Zotlabs/Module/Impel.php:41 ../../include/bbcode.php:203
-msgid "webpage"
-msgstr "Webpagina"
+#: ../../Zotlabs/Module/Connedit.php:881 ../../Zotlabs/Module/Connedit.php:882
+msgid ""
+"words one per line or #tags or /patterns/ or lang=xx, leave blank to import "
+"all posts"
+msgstr "woorden (één per regel), #tags, /regex/ of talen (lang=iso639-1) - laat leeg om alle berichten te importeren"
-#: ../../Zotlabs/Module/Impel.php:46 ../../include/bbcode.php:209
-msgid "block"
-msgstr "blok"
+#: ../../Zotlabs/Module/Connedit.php:882
+msgid "Do not import posts with this text"
+msgstr "Importeer geen berichten met deze tekst"
-#: ../../Zotlabs/Module/Impel.php:51 ../../include/bbcode.php:206
-msgid "layout"
-msgstr "lay-out"
+#: ../../Zotlabs/Module/Connedit.php:884
+msgid "This information is public!"
+msgstr "Deze informatie is openbaar!"
-#: ../../Zotlabs/Module/Impel.php:58 ../../include/bbcode.php:212
-msgid "menu"
-msgstr "menu"
+#: ../../Zotlabs/Module/Connedit.php:889
+msgid "Connection Pending Approval"
+msgstr "Connectie moet nog geaccepteerd worden"
-#: ../../Zotlabs/Module/Impel.php:191
-#, php-format
-msgid "%s element installed"
-msgstr "%s onderdeel geïnstalleerd"
+#: ../../Zotlabs/Module/Connedit.php:892
+#: ../../Zotlabs/Module/Settings/Permcats.php:107
+#: ../../Zotlabs/Module/Settings/Tokens.php:163
+msgid "inherited"
+msgstr "geërfd"
-#: ../../Zotlabs/Module/Impel.php:194
+#: ../../Zotlabs/Module/Connedit.php:894
#, php-format
-msgid "%s element installation failed"
-msgstr "Installatie %s-element mislukt"
-
-#: ../../Zotlabs/Module/Import_items.php:42 ../../Zotlabs/Module/Import.php:71
-msgid "Nothing to import."
-msgstr "Niets gevonden om te importeren"
-
-#: ../../Zotlabs/Module/Import_items.php:66 ../../Zotlabs/Module/Import.php:83
-#: ../../Zotlabs/Module/Import.php:98
-msgid "Unable to download data from old server"
-msgstr "Niet in staat om gegevens van de oude hub te downloaden"
-
-#: ../../Zotlabs/Module/Import_items.php:72
-#: ../../Zotlabs/Module/Import.php:105
-msgid "Imported file is empty."
-msgstr "Geïmporteerde bestand is leeg"
+msgid ""
+"Please choose the profile you would like to display to %s when viewing your "
+"profile securely."
+msgstr "Kies het profiel dat je aan %s wil tonen wanneer hij/zij ingelogd jouw profiel wil bekijken."
-#: ../../Zotlabs/Module/Import_items.php:88
-#: ../../Zotlabs/Module/Import.php:127
-#, php-format
-msgid "Warning: Database versions differ by %1$d updates."
-msgstr "Waarschuwing: database-versies lopen %1$d updates achter."
+#: ../../Zotlabs/Module/Connedit.php:896
+#: ../../Zotlabs/Module/Settings/Tokens.php:160
+msgid "Their Settings"
+msgstr "Hun instellingen"
-#: ../../Zotlabs/Module/Import_items.php:104
-msgid "Import completed"
-msgstr "Importeren voltooid"
+#: ../../Zotlabs/Module/Connedit.php:897
+#: ../../Zotlabs/Module/Settings/Permcats.php:105
+#: ../../Zotlabs/Module/Settings/Tokens.php:161
+msgid "My Settings"
+msgstr "Mijn instellingen"
-#: ../../Zotlabs/Module/Import_items.php:119
-msgid "Import Items"
-msgstr "Importeer items"
+#: ../../Zotlabs/Module/Connedit.php:899
+#: ../../Zotlabs/Module/Settings/Permcats.php:110
+#: ../../Zotlabs/Module/Settings/Tokens.php:166
+msgid "Individual Permissions"
+msgstr "Individuele permissies"
-#: ../../Zotlabs/Module/Import_items.php:120
+#: ../../Zotlabs/Module/Connedit.php:900
+#: ../../Zotlabs/Module/Settings/Permcats.php:111
+#: ../../Zotlabs/Module/Settings/Tokens.php:167
msgid ""
-"Use this form to import existing posts and content from an export file."
-msgstr "Gebruik dit formulier om bestaande berichten en andere inhoud vanuit een exportbestand te importeren."
+"Some permissions may be inherited from your channel's <a "
+"href=\"settings\"><strong>privacy settings</strong></a>, which have higher "
+"priority than individual settings. You can <strong>not</strong> change those"
+" settings here."
+msgstr "Sommige permissies worden mogelijk overgeërfd van de <a href=\"settings\">privacy-instellingen</a> van jouw kanaal, die een hogere prioriteit hebben dan deze individuele instellingen. Je kan je deze overgeërfde permissies hier <strong>niet</strong> veranderen."
-#: ../../Zotlabs/Module/Import_items.php:121
-#: ../../Zotlabs/Module/Import.php:532
-msgid "File to Upload"
-msgstr "Bestand om te uploaden"
+#: ../../Zotlabs/Module/Connedit.php:901
+msgid ""
+"Some permissions may be inherited from your channel's <a "
+"href=\"settings\"><strong>privacy settings</strong></a>, which have higher "
+"priority than individual settings. You can change those settings here but "
+"they wont have any impact unless the inherited setting changes."
+msgstr "Sommige permissies worden mogelijk overgeërfd van de <a href=\"settings\">privacy-instellingen</a> van jouw kanaal, die een hogere prioriteit hebben dan deze individuele permissies. Je kan de permissies hier veranderen, maar die hebben geen effect, tenzij de overgeërfde permissies worden veranderd. "
-#: ../../Zotlabs/Module/Invite.php:29
-msgid "Total invitation limit exceeded."
-msgstr "Limiet voor aantal uitnodigingen overschreden."
+#: ../../Zotlabs/Module/Connedit.php:902
+msgid "Last update:"
+msgstr "Laatste wijziging:"
-#: ../../Zotlabs/Module/Invite.php:53
-#, php-format
-msgid "%s : Not a valid email address."
-msgstr "%s : Geen geldig e-mailadres."
+#: ../../Zotlabs/Module/Connedit.php:911
+msgid "Details"
+msgstr "Details"
-#: ../../Zotlabs/Module/Invite.php:67
-msgid "Please join us on $Projectname"
-msgstr "Uitnodiging voor $Projectname"
+#: ../../Zotlabs/Module/Connedit.php:914
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1137
+msgid "Organisation"
+msgstr "Organisatie"
-#: ../../Zotlabs/Module/Invite.php:77
-msgid "Invitation limit exceeded. Please contact your site administrator."
-msgstr "Limiet voor aantal uitnodigingen overschreden. Neem contact op met je hub-beheerder."
+#: ../../Zotlabs/Module/Connedit.php:915
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1138
+#: ../../include/page_widgets.php:46
+msgid "Title"
+msgstr "Titel"
-#: ../../Zotlabs/Module/Invite.php:82
-#, php-format
-msgid "%s : Message delivery failed."
-msgstr "%s: Aflevering bericht mislukt."
+#: ../../Zotlabs/Module/Connedit.php:916 ../../Zotlabs/Module/Profiles.php:789
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1139
+msgid "Phone"
+msgstr "Telefoon"
-#: ../../Zotlabs/Module/Invite.php:86
-#, php-format
-msgid "%d message sent."
-msgid_plural "%d messages sent."
-msgstr[0] "%d bericht verzonden."
-msgstr[1] "%d berichten verzonden."
+#: ../../Zotlabs/Module/Connedit.php:918 ../../Zotlabs/Module/Profiles.php:791
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1141
+msgid "Instant messenger"
+msgstr "Instant messenger"
-#: ../../Zotlabs/Module/Invite.php:105
-msgid "You have no more invitations available"
-msgstr "Je hebt geen uitnodigingen meer beschikbaar"
+#: ../../Zotlabs/Module/Connedit.php:919 ../../Zotlabs/Module/Profiles.php:792
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1142
+msgid "Website"
+msgstr "Website"
-#: ../../Zotlabs/Module/Invite.php:136
-msgid "Send invitations"
-msgstr "Uitnodigingen verzenden"
+#: ../../Zotlabs/Module/Connedit.php:921 ../../Zotlabs/Module/Profiles.php:794
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1144
+msgid "Note"
+msgstr "Opmerking"
-#: ../../Zotlabs/Module/Invite.php:137
-msgid "Enter email addresses, one per line:"
-msgstr "Voer e-mailadressen in, één per regel:"
+#: ../../Zotlabs/Module/Connedit.php:922 ../../Zotlabs/Module/Profiles.php:795
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1145
+#: ../../extend/addon/addon/cdav/cdav.php:270
+#: ../../include/connections.php:668
+msgid "Mobile"
+msgstr "Mobiel"
-#: ../../Zotlabs/Module/Invite.php:139
-msgid "Please join my community on $Projectname."
-msgstr "Hierbij nodig ik je uit om mij, en andere vrienden en kennissen, op $Projectname te vergezellen. Lees meer over $Projectname op http://hubzilla.org"
+#: ../../Zotlabs/Module/Connedit.php:923 ../../Zotlabs/Module/Profiles.php:796
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1146
+#: ../../extend/addon/addon/cdav/cdav.php:271
+#: ../../include/connections.php:669
+msgid "Home"
+msgstr "Thuis"
-#: ../../Zotlabs/Module/Invite.php:141
-msgid "You will need to supply this invitation code:"
-msgstr "Je moet deze uitnodigingscode opgeven:"
+#: ../../Zotlabs/Module/Connedit.php:924 ../../Zotlabs/Module/Profiles.php:797
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1147
+#: ../../extend/addon/addon/cdav/cdav.php:274
+#: ../../include/connections.php:672
+msgid "Work"
+msgstr "Werk"
-#: ../../Zotlabs/Module/Invite.php:142
-msgid ""
-"1. Register at any $Projectname location (they are all inter-connected)"
-msgstr "1. Registreer je op een willekeurige $Projectname-hub (ze zijn allemaal onderling met elkaar verbonden):"
+#: ../../Zotlabs/Module/Connedit.php:926 ../../Zotlabs/Module/Profiles.php:799
+#: ../../extend/addon/addon/jappixmini/jappixmini.php:368
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1149
+msgid "Add Contact"
+msgstr "Contact toevoegen"
-#: ../../Zotlabs/Module/Invite.php:144
-msgid "2. Enter my $Projectname network address into the site searchbar."
-msgstr "2. Nadat je bent ingelogd en een kanaal hebt aangemaakt kan je mijn $Projectname-kanaaladres in het zoekveld invullen:"
+#: ../../Zotlabs/Module/Connedit.php:927 ../../Zotlabs/Module/Profiles.php:800
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1150
+msgid "Add Field"
+msgstr "Veld toevoegen"
-#: ../../Zotlabs/Module/Invite.php:145
-msgid "or visit"
-msgstr "of bezoek"
+#: ../../Zotlabs/Module/Connedit.php:932
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1155
+msgid "P.O. Box"
+msgstr "Postbus"
-#: ../../Zotlabs/Module/Invite.php:147
-msgid "3. Click [Connect]"
-msgstr "3. Klik op [+ Verbinden]"
+#: ../../Zotlabs/Module/Connedit.php:933
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1156
+msgid "Additional"
+msgstr "Extra"
-#: ../../Zotlabs/Module/Editblock.php:108 ../../Zotlabs/Module/Blocks.php:97
-#: ../../Zotlabs/Module/Blocks.php:155
-msgid "Block Name"
-msgstr "Bloknaam"
+#: ../../Zotlabs/Module/Connedit.php:934
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1157
+msgid "Street"
+msgstr "Straat en huisnummer"
-#: ../../Zotlabs/Module/Editblock.php:124 ../../include/conversation.php:1258
-msgid "Title (optional)"
-msgstr "Titel (optioneel)"
+#: ../../Zotlabs/Module/Connedit.php:935
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1158
+msgid "Locality"
+msgstr "Plaats"
-#: ../../Zotlabs/Module/Editblock.php:133
-msgid "Edit Block"
-msgstr "Blok bewerken"
+#: ../../Zotlabs/Module/Connedit.php:936
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1159
+msgid "Region"
+msgstr "Provincie/staat/regio/enz."
-#: ../../Zotlabs/Module/Group.php:24
-msgid "Privacy group created."
-msgstr "Privacygroep aangemaakt"
+#: ../../Zotlabs/Module/Connedit.php:937
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1160
+msgid "ZIP Code"
+msgstr "Postcode"
-#: ../../Zotlabs/Module/Group.php:30
-msgid "Could not create privacy group."
-msgstr "Kon privacygroep niet aanmaken"
+#: ../../Zotlabs/Module/Connedit.php:938 ../../Zotlabs/Module/Profiles.php:760
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1161
+msgid "Country"
+msgstr "Land"
-#: ../../Zotlabs/Module/Group.php:42 ../../Zotlabs/Module/Group.php:141
-#: ../../include/items.php:3876
-msgid "Privacy group not found."
-msgstr "Privacygroep niet gevonden"
+#: ../../Zotlabs/Module/Events.php:25
+msgid "Calendar entries imported."
+msgstr "Agenda-items geïmporteerd."
-#: ../../Zotlabs/Module/Group.php:58
-msgid "Privacy group updated."
-msgstr "Privacygroep bijgewerkt"
+#: ../../Zotlabs/Module/Events.php:27
+msgid "No calendar entries found."
+msgstr "Geen agenda-items gevonden."
-#: ../../Zotlabs/Module/Group.php:90
-msgid "Create a group of channels."
-msgstr "Privacygroep met kanalen aanmaken"
+#: ../../Zotlabs/Module/Events.php:110
+msgid "Event can not end before it has started."
+msgstr "Gebeurtenis kan niet eindigen voordat het is begonnen"
-#: ../../Zotlabs/Module/Group.php:91 ../../Zotlabs/Module/Group.php:184
-msgid "Privacy group name: "
-msgstr "Naam privacygroep: "
+#: ../../Zotlabs/Module/Events.php:112 ../../Zotlabs/Module/Events.php:121
+#: ../../Zotlabs/Module/Events.php:143
+msgid "Unable to generate preview."
+msgstr "Niet in staat om voorvertoning te genereren"
-#: ../../Zotlabs/Module/Group.php:93 ../../Zotlabs/Module/Group.php:187
-msgid "Members are visible to other channels"
-msgstr "Kanalen in deze privacygroep zijn zichtbaar voor andere kanalen"
+#: ../../Zotlabs/Module/Events.php:119
+msgid "Event title and start time are required."
+msgstr "Titel en begintijd van gebeurtenis zijn vereist."
-#: ../../Zotlabs/Module/Group.php:111
-msgid "Privacy group removed."
-msgstr "Privacygroep verwijderd."
+#: ../../Zotlabs/Module/Events.php:141 ../../Zotlabs/Module/Events.php:265
+msgid "Event not found."
+msgstr "Gebeurtenis niet gevonden"
-#: ../../Zotlabs/Module/Group.php:113
-msgid "Unable to remove privacy group."
-msgstr "Verwijderen privacygroep mislukt"
+#: ../../Zotlabs/Module/Events.php:260 ../../Zotlabs/Module/Like.php:372
+#: ../../Zotlabs/Module/Tagger.php:51 ../../include/event.php:1141
+#: ../../include/conversation.php:123 ../../include/text.php:1961
+msgid "event"
+msgstr "gebeurtenis"
-#: ../../Zotlabs/Module/Group.php:183
-msgid "Privacy group editor"
-msgstr "Privacygroep bewerken"
+#: ../../Zotlabs/Module/Events.php:460
+msgid "Edit event title"
+msgstr "Titel bewerken"
-#: ../../Zotlabs/Module/Group.php:199
-msgid "All Connected Channels"
-msgstr "Alle kanaalconnecties"
+#: ../../Zotlabs/Module/Events.php:460
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:835
+msgid "Event title"
+msgstr "Titel"
-#: ../../Zotlabs/Module/Group.php:231
-msgid "Click on a channel to add or remove."
-msgstr "Klik op een kanaal om deze toe te voegen of te verwijderen."
+#: ../../Zotlabs/Module/Events.php:462
+msgid "Categories (comma-separated list)"
+msgstr "Categorieën (door komma's gescheiden lijst)"
-#: ../../Zotlabs/Module/Profperm.php:34 ../../Zotlabs/Module/Profperm.php:63
-msgid "Invalid profile identifier."
-msgstr "Ongeldige profiel-identificator"
+#: ../../Zotlabs/Module/Events.php:463
+msgid "Edit Category"
+msgstr "Categorie"
-#: ../../Zotlabs/Module/Profperm.php:115
-msgid "Profile Visibility Editor"
-msgstr "Zichtbaarheid profiel "
+#: ../../Zotlabs/Module/Events.php:463
+msgid "Category"
+msgstr "Categorie"
-#: ../../Zotlabs/Module/Profperm.php:117 ../../include/channel.php:1282
-msgid "Profile"
-msgstr "Profiel"
+#: ../../Zotlabs/Module/Events.php:466
+msgid "Edit start date and time"
+msgstr "Begindatum en -tijd bewerken"
-#: ../../Zotlabs/Module/Profperm.php:119
-msgid "Click on a contact to add or remove."
-msgstr "Klik op een connectie om deze toe te voegen of te verwijderen"
+#: ../../Zotlabs/Module/Events.php:466
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:836
+msgid "Start date and time"
+msgstr "Begindatum en -tijd"
-#: ../../Zotlabs/Module/Profperm.php:128
-msgid "Visible To"
-msgstr "Zichtbaar voor"
+#: ../../Zotlabs/Module/Events.php:467 ../../Zotlabs/Module/Events.php:470
+msgid "Finish date and time are not known or not relevant"
+msgstr "Einddatum en -tijd zijn niet bekend of niet van toepassing"
-#: ../../Zotlabs/Module/Magic.php:71
-msgid "Hub not found."
-msgstr "Hub niet gevonden."
+#: ../../Zotlabs/Module/Events.php:469
+msgid "Edit finish date and time"
+msgstr "Einddatum en -tijd bewerken"
-#: ../../Zotlabs/Module/Mitem.php:52
-msgid "Unable to create element."
-msgstr "Niet in staat om onderdeel aan te maken."
+#: ../../Zotlabs/Module/Events.php:469
+msgid "Finish date and time"
+msgstr "Einddatum en -tijd"
-#: ../../Zotlabs/Module/Mitem.php:76
-msgid "Unable to update menu element."
-msgstr "Menu-onderdeel kan niet worden geüpdatet."
+#: ../../Zotlabs/Module/Events.php:471 ../../Zotlabs/Module/Events.php:472
+msgid "Adjust for viewer timezone"
+msgstr "Aanpassen aan de tijdzone van wie deze gebeurtenis bekijkt"
-#: ../../Zotlabs/Module/Mitem.php:92
-msgid "Unable to add menu element."
-msgstr "Menu-onderdeel kan niet worden toegevoegd."
+#: ../../Zotlabs/Module/Events.php:471
+msgid ""
+"Important for events that happen in a particular place. Not practical for "
+"global holidays."
+msgstr "Belangrijk voor gebeurtenissen die op een bepaalde locatie plaatsvinden. Niet praktisch voor wereldwijde feestdagen."
-#: ../../Zotlabs/Module/Mitem.php:153 ../../Zotlabs/Module/Mitem.php:230
-msgid "Menu Item Permissions"
-msgstr "Permissies menu-item"
+#: ../../Zotlabs/Module/Events.php:473
+msgid "Edit Description"
+msgstr "Omschrijving bewerken"
-#: ../../Zotlabs/Module/Mitem.php:154 ../../Zotlabs/Module/Mitem.php:231
-#: ../../Zotlabs/Module/Settings/Channel.php:489
-msgid "(click to open/close)"
-msgstr "(klik om te openen/sluiten)"
+#: ../../Zotlabs/Module/Events.php:475
+msgid "Edit Location"
+msgstr "Locatie bewerken"
-#: ../../Zotlabs/Module/Mitem.php:160 ../../Zotlabs/Module/Mitem.php:176
-msgid "Link Name"
-msgstr "Linknaam"
+#: ../../Zotlabs/Module/Events.php:478 ../../Zotlabs/Module/Photos.php:1094
+#: ../../Zotlabs/Module/Webpages.php:251 ../../Zotlabs/Lib/ThreadItem.php:740
+#: ../../include/page_widgets.php:43 ../../include/conversation.php:1347
+msgid "Preview"
+msgstr "Voorvertoning"
-#: ../../Zotlabs/Module/Mitem.php:161 ../../Zotlabs/Module/Mitem.php:239
-msgid "Link or Submenu Target"
-msgstr "Linkdoel of submenu-doel"
+#: ../../Zotlabs/Module/Events.php:479 ../../include/conversation.php:1410
+msgid "Permission settings"
+msgstr "Permissies"
-#: ../../Zotlabs/Module/Mitem.php:161
-msgid "Enter URL of the link or select a menu name to create a submenu"
-msgstr "Geef de URL van de link of kies een menunaam om een submenu aan te maken"
+#: ../../Zotlabs/Module/Events.php:489
+msgid "Timezone:"
+msgstr "Tijdzone:"
-#: ../../Zotlabs/Module/Mitem.php:162 ../../Zotlabs/Module/Mitem.php:240
-msgid "Use magic-auth if available"
-msgstr "Gebruik magic-auth wanneer beschikbaar"
+#: ../../Zotlabs/Module/Events.php:494
+msgid "Advanced Options"
+msgstr "Geavanceerde opties"
-#: ../../Zotlabs/Module/Mitem.php:163 ../../Zotlabs/Module/Mitem.php:241
-msgid "Open link in new window"
-msgstr "Open link in nieuw venster"
+#: ../../Zotlabs/Module/Events.php:605 ../../Zotlabs/Module/Cal.php:263
+msgid "l, F j"
+msgstr "l j F"
-#: ../../Zotlabs/Module/Mitem.php:164 ../../Zotlabs/Module/Mitem.php:242
-msgid "Order in list"
-msgstr "Volgorde in lijst"
+#: ../../Zotlabs/Module/Events.php:633
+msgid "Edit event"
+msgstr "Gebeurtenis bewerken"
-#: ../../Zotlabs/Module/Mitem.php:164 ../../Zotlabs/Module/Mitem.php:242
-msgid "Higher numbers will sink to bottom of listing"
-msgstr "Hogere nummers komen onderaan de lijst terecht"
+#: ../../Zotlabs/Module/Events.php:635
+msgid "Delete event"
+msgstr "Gebeurtenis verwijderen"
-#: ../../Zotlabs/Module/Mitem.php:165
-msgid "Submit and finish"
-msgstr "Opslaan en afsluiten"
+#: ../../Zotlabs/Module/Events.php:660 ../../Zotlabs/Module/Cal.php:312
+#: ../../include/text.php:1766
+msgid "Link to Source"
+msgstr "Originele locatie"
-#: ../../Zotlabs/Module/Mitem.php:166
-msgid "Submit and continue"
-msgstr "Opslaan en doorgaan"
+#: ../../Zotlabs/Module/Events.php:669
+msgid "calendar"
+msgstr "agenda"
-#: ../../Zotlabs/Module/Mitem.php:174
-msgid "Menu:"
-msgstr "Menu:"
+#: ../../Zotlabs/Module/Events.php:688 ../../Zotlabs/Module/Cal.php:335
+msgid "Edit Event"
+msgstr "Gebeurtenis bewerken"
-#: ../../Zotlabs/Module/Mitem.php:177
-msgid "Link Target"
-msgstr "Linkdoel"
+#: ../../Zotlabs/Module/Events.php:688 ../../Zotlabs/Module/Cal.php:335
+msgid "Create Event"
+msgstr "Gebeurtenis aanmaken"
-#: ../../Zotlabs/Module/Mitem.php:180
-msgid "Edit menu"
-msgstr "Menu bewerken"
+#: ../../Zotlabs/Module/Events.php:689 ../../Zotlabs/Module/Events.php:698
+#: ../../Zotlabs/Module/Photos.php:935 ../../Zotlabs/Module/Cal.php:336
+#: ../../Zotlabs/Module/Cal.php:343
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:846
+msgid "Previous"
+msgstr "Vorige"
-#: ../../Zotlabs/Module/Mitem.php:183
-msgid "Edit element"
-msgstr "Onderdeel bewerken"
+#: ../../Zotlabs/Module/Events.php:690 ../../Zotlabs/Module/Events.php:699
+#: ../../Zotlabs/Module/Photos.php:944 ../../Zotlabs/Module/Cal.php:337
+#: ../../Zotlabs/Module/Cal.php:344 ../../Zotlabs/Module/Setup.php:264
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:847
+msgid "Next"
+msgstr "Volgende"
-#: ../../Zotlabs/Module/Mitem.php:184
-msgid "Drop element"
-msgstr "Onderdeel verwijderen"
+#: ../../Zotlabs/Module/Events.php:691 ../../Zotlabs/Module/Cal.php:338
+#: ../../include/channel.php:1370
+msgid "Export"
+msgstr "Exporteren"
-#: ../../Zotlabs/Module/Mitem.php:185
-msgid "New element"
-msgstr "Nieuw element"
+#: ../../Zotlabs/Module/Events.php:695
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:849
+msgid "Month"
+msgstr "Maand"
-#: ../../Zotlabs/Module/Mitem.php:186
-msgid "Edit this menu container"
-msgstr "Deze menu-container bewerken"
+#: ../../Zotlabs/Module/Events.php:696
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:850
+msgid "Week"
+msgstr "Week"
-#: ../../Zotlabs/Module/Mitem.php:187
-msgid "Add menu element"
-msgstr "Menu-element toevoegen"
+#: ../../Zotlabs/Module/Events.php:697
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:851
+msgid "Day"
+msgstr "Dag"
-#: ../../Zotlabs/Module/Mitem.php:188
-msgid "Delete this menu item"
-msgstr "Dit menu-item verwijderen"
+#: ../../Zotlabs/Module/Events.php:700 ../../Zotlabs/Module/Cal.php:345
+#: ../../extend/addon/addon/cdav/Mod_Cdav.php:848
+msgid "Today"
+msgstr "Vandaag"
-#: ../../Zotlabs/Module/Mitem.php:189
-msgid "Edit this menu item"
-msgstr "Dit menu-item bewerken"
+#: ../../Zotlabs/Module/Events.php:731
+msgid "Event removed"
+msgstr "Gebeurtenis verwijderd"
-#: ../../Zotlabs/Module/Mitem.php:206
-msgid "Menu item not found."
-msgstr "Menu-item niet gevonden."
+#: ../../Zotlabs/Module/Events.php:734
+msgid "Failed to remove event"
+msgstr "Verwijderen gebeurtenis mislukt"
-#: ../../Zotlabs/Module/Mitem.php:219
-msgid "Menu item deleted."
-msgstr "Menu-item verwijderd."
+#: ../../Zotlabs/Module/Home.php:74 ../../Zotlabs/Module/Home.php:82
+#: ../../extend/addon/addon/opensearch/opensearch.php:42
+msgid "$Projectname"
+msgstr "$Projectname"
-#: ../../Zotlabs/Module/Mitem.php:221
-msgid "Menu item could not be deleted."
-msgstr "Menu-item kon niet worden verwijderd."
+#: ../../Zotlabs/Module/Home.php:92
+#, php-format
+msgid "Welcome to %s"
+msgstr "Welkom op %s"
-#: ../../Zotlabs/Module/Mitem.php:228
-msgid "Edit Menu Element"
-msgstr "Menu-element bewerken"
+#: ../../Zotlabs/Module/Filestorage.php:87
+msgid "Permission Denied."
+msgstr "Toegang geweigerd"
-#: ../../Zotlabs/Module/Mitem.php:238
-msgid "Link text"
-msgstr "Linktekst"
+#: ../../Zotlabs/Module/Filestorage.php:103
+msgid "File not found."
+msgstr "Bestand niet gevonden."
-#: ../../Zotlabs/Module/Ratings.php:70
-msgid "No ratings"
-msgstr "Geen beoordelingen"
+#: ../../Zotlabs/Module/Filestorage.php:146
+msgid "Edit file permissions"
+msgstr "Bestandsrechten bewerken"
-#: ../../Zotlabs/Module/Ratings.php:98
-msgid "Rating: "
-msgstr "Beoordeling: "
+#: ../../Zotlabs/Module/Filestorage.php:159
+msgid "Set/edit permissions"
+msgstr "Rechten instellen/bewerken"
-#: ../../Zotlabs/Module/Ratings.php:99
-msgid "Website: "
-msgstr "Website: "
+#: ../../Zotlabs/Module/Filestorage.php:160
+msgid "Include all files and sub folders"
+msgstr "Toepassen op alle bestanden en submappen"
-#: ../../Zotlabs/Module/Ratings.php:101
-msgid "Description: "
-msgstr "Omschrijving: "
+#: ../../Zotlabs/Module/Filestorage.php:161
+msgid "Return to file list"
+msgstr "Terugkeren naar bestandlijst "
-#: ../../Zotlabs/Module/Attach.php:13
-msgid "Item not available."
-msgstr "Item is niet aanwezig."
+#: ../../Zotlabs/Module/Filestorage.php:163
+msgid "Copy/paste this code to attach file to a post"
+msgstr "Kopieer/plak deze code om het bestand aan een bericht te koppelen"
-#: ../../Zotlabs/Module/Mood.php:67 ../../include/conversation.php:260
-#, php-format
-msgctxt "mood"
-msgid "%1$s is %2$s"
-msgstr "%1$s is %2$s"
+#: ../../Zotlabs/Module/Filestorage.php:164
+msgid "Copy/paste this URL to link file from a web page"
+msgstr "Kopieer/plak deze URL om het bestand aan een externe webpagina te koppelen"
-#: ../../Zotlabs/Module/Mood.php:135 ../../Zotlabs/Lib/Apps.php:229
-msgid "Mood"
-msgstr "Stemming"
+#: ../../Zotlabs/Module/Filestorage.php:166
+msgid "Share this file"
+msgstr "Dit bestand delen"
-#: ../../Zotlabs/Module/Mood.php:136
-msgid "Set your current mood and tell your friends"
-msgstr "Noteer je huidige stemming en toon het aan je connecties"
+#: ../../Zotlabs/Module/Filestorage.php:167
+msgid "Show URL to this file"
+msgstr "Toon URL van dit bestand"
-#: ../../Zotlabs/Module/Notify.php:57
-#: ../../Zotlabs/Module/Notifications.php:35
-msgid "No more system notifications."
-msgstr "Geen systeemnotificaties meer."
+#: ../../Zotlabs/Module/Filestorage.php:168
+msgid "Notify your contacts about this file"
+msgstr "Jouw connecties over dit bestand berichten"
-#: ../../Zotlabs/Module/Notify.php:61
-#: ../../Zotlabs/Module/Notifications.php:39
-msgid "System Notifications"
-msgstr "Systeemnotificaties"
+#: ../../Zotlabs/Module/Fbrowser.php:29 ../../Zotlabs/Lib/Apps.php:229
+#: ../../include/conversation.php:1836
+msgid "Photos"
+msgstr "Foto's"
#: ../../Zotlabs/Module/Photos.php:82
msgid "Page owner information could not be retrieved."
msgstr "Informatie over de pagina-eigenaar werd niet ontvangen."
-#: ../../Zotlabs/Module/Photos.php:97 ../../Zotlabs/Module/Photos.php:734
+#: ../../Zotlabs/Module/Photos.php:97 ../../Zotlabs/Module/Photos.php:729
#: ../../Zotlabs/Module/Profile_photo.php:115
-#: ../../Zotlabs/Module/Profile_photo.php:219
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:225
-#: ../../include/photo/photo_driver.php:728
+#: ../../Zotlabs/Module/Profile_photo.php:224
+#: ../../include/photo/photo_driver.php:730
msgid "Profile Photos"
msgstr "Profielfoto's"
@@ -3871,1070 +3733,1045 @@ msgid ""
"manager"
msgstr "Er bestaan meerdere submappen met deze albumnaam, maar verspreidt over verschillende mappen. Verwijder de gewenste map(pen) met de bestandsbeheerder."
-#: ../../Zotlabs/Module/Photos.php:190 ../../Zotlabs/Module/Photos.php:1059
+#: ../../Zotlabs/Module/Photos.php:190 ../../Zotlabs/Module/Photos.php:1054
msgid "Delete Photo"
msgstr "Verwijder foto"
-#: ../../Zotlabs/Module/Photos.php:520
+#: ../../Zotlabs/Module/Photos.php:508 ../../Zotlabs/Module/Display.php:22
+#: ../../Zotlabs/Module/Ratings.php:83 ../../Zotlabs/Module/Search.php:17
+#: ../../Zotlabs/Module/Directory.php:64
+#: ../../Zotlabs/Module/Viewconnections.php:23
+#: ../../extend/addon/addon/friendica/dfrn_request.php:794
+msgid "Public access denied."
+msgstr "Openbare toegang geweigerd."
+
+#: ../../Zotlabs/Module/Photos.php:519
msgid "No photos selected"
msgstr "Geen foto's geselecteerd"
-#: ../../Zotlabs/Module/Photos.php:569
+#: ../../Zotlabs/Module/Photos.php:568
msgid "Access to this item is restricted."
msgstr "Toegang tot dit item is beperkt."
-#: ../../Zotlabs/Module/Photos.php:608
+#: ../../Zotlabs/Module/Photos.php:607
#, php-format
msgid "%1$.2f MB of %2$.2f MB photo storage used."
msgstr "%1$.2f MB van %2$.2f MB aan foto-opslag gebruikt."
-#: ../../Zotlabs/Module/Photos.php:611
+#: ../../Zotlabs/Module/Photos.php:610
#, php-format
msgid "%1$.2f MB photo storage used."
msgstr "%1$.2f MB aan foto-opslag gebruikt."
-#: ../../Zotlabs/Module/Photos.php:647
+#: ../../Zotlabs/Module/Photos.php:646
msgid "Upload Photos"
msgstr "Foto's uploaden"
-#: ../../Zotlabs/Module/Photos.php:651
+#: ../../Zotlabs/Module/Photos.php:650
msgid "Enter an album name"
msgstr "Vul een albumnaam in"
-#: ../../Zotlabs/Module/Photos.php:652
+#: ../../Zotlabs/Module/Photos.php:651
msgid "or select an existing album (doubleclick)"
msgstr "of kies een bestaand album (dubbelklikken)"
-#: ../../Zotlabs/Module/Photos.php:653
+#: ../../Zotlabs/Module/Photos.php:652
msgid "Create a status post for this upload"
msgstr "Plaats een bericht voor deze upload."
-#: ../../Zotlabs/Module/Photos.php:654
+#: ../../Zotlabs/Module/Photos.php:653
msgid "Caption (optional):"
-msgstr "Bijschrift (optioneel):"
+msgstr "Bijschrift (niet verplicht):"
-#: ../../Zotlabs/Module/Photos.php:655
+#: ../../Zotlabs/Module/Photos.php:654
msgid "Description (optional):"
-msgstr "Omschrijving (optioneel):"
+msgstr "Omschrijving (niet verplicht):"
-#: ../../Zotlabs/Module/Photos.php:686
+#: ../../Zotlabs/Module/Photos.php:685
msgid "Album name could not be decoded"
msgstr "Albumnaam kon niet gedecodeerd worden"
-#: ../../Zotlabs/Module/Photos.php:734
+#: ../../Zotlabs/Module/Photos.php:729
msgid "Contact Photos"
msgstr "Connectiefoto's"
-#: ../../Zotlabs/Module/Photos.php:757
+#: ../../Zotlabs/Module/Photos.php:752
msgid "Show Newest First"
msgstr "Nieuwste eerst weergeven"
-#: ../../Zotlabs/Module/Photos.php:759
+#: ../../Zotlabs/Module/Photos.php:754
msgid "Show Oldest First"
msgstr "Oudste eerst weergeven"
-#: ../../Zotlabs/Module/Photos.php:783 ../../Zotlabs/Module/Photos.php:1337
-#: ../../Zotlabs/Module/Embedphotos.php:139 ../../include/widgets.php:1678
+#: ../../Zotlabs/Module/Photos.php:778 ../../Zotlabs/Module/Photos.php:1335
+#: ../../Zotlabs/Module/Embedphotos.php:139 ../../include/widgets.php:1751
msgid "View Photo"
msgstr "Foto weergeven"
-#: ../../Zotlabs/Module/Photos.php:814
-#: ../../Zotlabs/Module/Embedphotos.php:155 ../../include/widgets.php:1695
+#: ../../Zotlabs/Module/Photos.php:809
+#: ../../Zotlabs/Module/Embedphotos.php:155 ../../include/widgets.php:1768
msgid "Edit Album"
msgstr "Album bewerken"
-#: ../../Zotlabs/Module/Photos.php:861
+#: ../../Zotlabs/Module/Photos.php:856
msgid "Permission denied. Access to this item may be restricted."
msgstr "Toegang geweigerd. Toegang tot dit item kan zijn beperkt."
-#: ../../Zotlabs/Module/Photos.php:863
+#: ../../Zotlabs/Module/Photos.php:858
msgid "Photo not available"
msgstr "Foto niet aanwezig"
-#: ../../Zotlabs/Module/Photos.php:921
+#: ../../Zotlabs/Module/Photos.php:916
msgid "Use as profile photo"
msgstr "Als profielfoto gebruiken"
-#: ../../Zotlabs/Module/Photos.php:922
+#: ../../Zotlabs/Module/Photos.php:917
msgid "Use as cover photo"
msgstr "Als omslagfoto gebruiken"
-#: ../../Zotlabs/Module/Photos.php:929
+#: ../../Zotlabs/Module/Photos.php:924
msgid "Private Photo"
msgstr "Privéfoto"
-#: ../../Zotlabs/Module/Photos.php:940 ../../Zotlabs/Module/Cal.php:336
-#: ../../Zotlabs/Module/Cal.php:343 ../../Zotlabs/Module/Events.php:680
-#: ../../Zotlabs/Module/Events.php:689
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:846
-msgid "Previous"
-msgstr "Vorige"
-
-#: ../../Zotlabs/Module/Photos.php:944
+#: ../../Zotlabs/Module/Photos.php:939
msgid "View Full Size"
msgstr "Volledige grootte weergeven"
-#: ../../Zotlabs/Module/Photos.php:949 ../../Zotlabs/Module/Setup.php:264
-#: ../../Zotlabs/Module/Cal.php:337 ../../Zotlabs/Module/Cal.php:344
-#: ../../Zotlabs/Module/Events.php:681 ../../Zotlabs/Module/Events.php:690
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:847
-msgid "Next"
-msgstr "Volgende"
-
-#: ../../Zotlabs/Module/Photos.php:1033
+#: ../../Zotlabs/Module/Photos.php:1028
msgid "Edit photo"
msgstr "Foto bewerken"
-#: ../../Zotlabs/Module/Photos.php:1035
+#: ../../Zotlabs/Module/Photos.php:1030
msgid "Rotate CW (right)"
msgstr "Draai met de klok mee (naar rechts)"
-#: ../../Zotlabs/Module/Photos.php:1036
+#: ../../Zotlabs/Module/Photos.php:1031
msgid "Rotate CCW (left)"
msgstr "Draai tegen de klok in (naar links)"
-#: ../../Zotlabs/Module/Photos.php:1039
+#: ../../Zotlabs/Module/Photos.php:1034
msgid "Move photo to album"
msgstr "Verplaatst foto naar album"
-#: ../../Zotlabs/Module/Photos.php:1040
+#: ../../Zotlabs/Module/Photos.php:1035
msgid "Enter a new album name"
msgstr "Vul een nieuwe albumnaam in"
-#: ../../Zotlabs/Module/Photos.php:1041
+#: ../../Zotlabs/Module/Photos.php:1036
msgid "or select an existing one (doubleclick)"
msgstr "of kies een bestaand album (dubbelklikken)"
-#: ../../Zotlabs/Module/Photos.php:1044
+#: ../../Zotlabs/Module/Photos.php:1039
msgid "Caption"
msgstr "Bijschrift"
-#: ../../Zotlabs/Module/Photos.php:1046
+#: ../../Zotlabs/Module/Photos.php:1041
msgid "Add a Tag"
msgstr "Tag toevoegen"
-#: ../../Zotlabs/Module/Photos.php:1054
+#: ../../Zotlabs/Module/Photos.php:1049
msgid "Example: @bob, @Barbara_Jensen, @jim@example.com"
msgstr "Voorbeeld: @bob, @Barbara_Jansen, @jan@voorbeeld.nl"
-#: ../../Zotlabs/Module/Photos.php:1057
+#: ../../Zotlabs/Module/Photos.php:1052
msgid "Flag as adult in album view"
msgstr "Markeer als voor volwassenen in albumweergave"
-#: ../../Zotlabs/Module/Photos.php:1076 ../../Zotlabs/Lib/ThreadItem.php:268
+#: ../../Zotlabs/Module/Photos.php:1071 ../../Zotlabs/Lib/ThreadItem.php:268
msgid "I like this (toggle)"
msgstr "Vind ik leuk"
-#: ../../Zotlabs/Module/Photos.php:1077 ../../Zotlabs/Lib/ThreadItem.php:269
+#: ../../Zotlabs/Module/Photos.php:1072 ../../Zotlabs/Lib/ThreadItem.php:269
msgid "I don't like this (toggle)"
msgstr "Vind ik niet leuk"
-#: ../../Zotlabs/Module/Photos.php:1078 ../../Zotlabs/Module/Blocks.php:161
-#: ../../Zotlabs/Module/Layouts.php:193 ../../Zotlabs/Module/Webpages.php:241
+#: ../../Zotlabs/Module/Photos.php:1073 ../../Zotlabs/Module/Webpages.php:245
+#: ../../Zotlabs/Module/Blocks.php:161 ../../Zotlabs/Module/Layouts.php:193
#: ../../extend/addon/addon/cdav/include/widgets.php:123
-#: ../../include/conversation.php:1230
+#: ../../include/conversation.php:1378
msgid "Share"
msgstr "Delen"
-#: ../../Zotlabs/Module/Photos.php:1079 ../../Zotlabs/Lib/ThreadItem.php:409
-#: ../../include/conversation.php:737
+#: ../../Zotlabs/Module/Photos.php:1074 ../../Zotlabs/Lib/ThreadItem.php:411
+#: ../../include/conversation.php:738
msgid "Please wait"
msgstr "Even wachten"
-#: ../../Zotlabs/Module/Photos.php:1095 ../../Zotlabs/Module/Photos.php:1213
-#: ../../Zotlabs/Lib/ThreadItem.php:726
+#: ../../Zotlabs/Module/Photos.php:1090 ../../Zotlabs/Module/Photos.php:1208
+#: ../../Zotlabs/Lib/ThreadItem.php:728
msgid "This is you"
msgstr "Dit ben jij"
-#: ../../Zotlabs/Module/Photos.php:1097 ../../Zotlabs/Module/Photos.php:1215
-#: ../../Zotlabs/Lib/ThreadItem.php:728 ../../include/js_strings.php:6
+#: ../../Zotlabs/Module/Photos.php:1092 ../../Zotlabs/Module/Photos.php:1210
+#: ../../Zotlabs/Lib/ThreadItem.php:730 ../../include/js_strings.php:6
msgid "Comment"
msgstr "Reactie"
-#: ../../Zotlabs/Module/Photos.php:1099 ../../Zotlabs/Module/Webpages.php:247
-#: ../../Zotlabs/Module/Events.php:471 ../../Zotlabs/Lib/ThreadItem.php:738
-#: ../../include/page_widgets.php:43 ../../include/conversation.php:1199
-msgid "Preview"
-msgstr "Voorvertoning"
-
-#: ../../Zotlabs/Module/Photos.php:1113 ../../include/conversation.php:577
+#: ../../Zotlabs/Module/Photos.php:1108 ../../include/conversation.php:577
msgctxt "title"
msgid "Likes"
msgstr "vinden dit leuk"
-#: ../../Zotlabs/Module/Photos.php:1113 ../../include/conversation.php:577
+#: ../../Zotlabs/Module/Photos.php:1108 ../../include/conversation.php:577
msgctxt "title"
msgid "Dislikes"
msgstr "vinden dit niet leuk"
-#: ../../Zotlabs/Module/Photos.php:1114 ../../include/conversation.php:578
+#: ../../Zotlabs/Module/Photos.php:1109 ../../include/conversation.php:578
msgctxt "title"
msgid "Agree"
msgstr "eens"
-#: ../../Zotlabs/Module/Photos.php:1114 ../../include/conversation.php:578
+#: ../../Zotlabs/Module/Photos.php:1109 ../../include/conversation.php:578
msgctxt "title"
msgid "Disagree"
msgstr "oneens"
-#: ../../Zotlabs/Module/Photos.php:1114 ../../include/conversation.php:578
+#: ../../Zotlabs/Module/Photos.php:1109 ../../include/conversation.php:578
msgctxt "title"
msgid "Abstain"
msgstr "onthoudingen"
-#: ../../Zotlabs/Module/Photos.php:1115 ../../include/conversation.php:579
+#: ../../Zotlabs/Module/Photos.php:1110 ../../include/conversation.php:579
msgctxt "title"
msgid "Attending"
msgstr "aanwezig"
-#: ../../Zotlabs/Module/Photos.php:1115 ../../include/conversation.php:579
+#: ../../Zotlabs/Module/Photos.php:1110 ../../include/conversation.php:579
msgctxt "title"
msgid "Not attending"
msgstr "niet aanwezig"
-#: ../../Zotlabs/Module/Photos.php:1115 ../../include/conversation.php:579
+#: ../../Zotlabs/Module/Photos.php:1110 ../../include/conversation.php:579
msgctxt "title"
msgid "Might attend"
msgstr "mogelijk aanwezig"
-#: ../../Zotlabs/Module/Photos.php:1132 ../../Zotlabs/Module/Photos.php:1144
+#: ../../Zotlabs/Module/Photos.php:1127 ../../Zotlabs/Module/Photos.php:1139
#: ../../Zotlabs/Lib/ThreadItem.php:186 ../../Zotlabs/Lib/ThreadItem.php:198
-#: ../../include/conversation.php:1765
+#: ../../include/conversation.php:1928
msgid "View all"
msgstr "Toon alles"
-#: ../../Zotlabs/Module/Photos.php:1136 ../../Zotlabs/Lib/ThreadItem.php:190
-#: ../../include/channel.php:1190 ../../include/taxonomy.php:403
-#: ../../include/conversation.php:1789
+#: ../../Zotlabs/Module/Photos.php:1131 ../../Zotlabs/Lib/ThreadItem.php:190
+#: ../../include/taxonomy.php:403 ../../include/conversation.php:1952
+#: ../../include/channel.php:1273
msgctxt "noun"
msgid "Like"
msgid_plural "Likes"
msgstr[0] "vindt dit leuk"
msgstr[1] "vinden dit leuk"
-#: ../../Zotlabs/Module/Photos.php:1141 ../../Zotlabs/Lib/ThreadItem.php:195
-#: ../../include/conversation.php:1792
+#: ../../Zotlabs/Module/Photos.php:1136 ../../Zotlabs/Lib/ThreadItem.php:195
+#: ../../include/conversation.php:1955
msgctxt "noun"
msgid "Dislike"
msgid_plural "Dislikes"
msgstr[0] "vindt dit niet leuk"
msgstr[1] "vinden dit niet leuk"
-#: ../../Zotlabs/Module/Photos.php:1241
+#: ../../Zotlabs/Module/Photos.php:1236
msgid "Photo Tools"
msgstr "Hulpmiddelen"
-#: ../../Zotlabs/Module/Photos.php:1250
+#: ../../Zotlabs/Module/Photos.php:1245
msgid "In This Photo:"
msgstr "Op deze foto:"
-#: ../../Zotlabs/Module/Photos.php:1255
+#: ../../Zotlabs/Module/Photos.php:1250
msgid "Map"
msgstr "Kaart"
-#: ../../Zotlabs/Module/Photos.php:1263 ../../Zotlabs/Lib/ThreadItem.php:398
+#: ../../Zotlabs/Module/Photos.php:1258 ../../Zotlabs/Lib/ThreadItem.php:400
msgctxt "noun"
msgid "Likes"
msgstr "vinden dit leuk"
-#: ../../Zotlabs/Module/Photos.php:1264 ../../Zotlabs/Lib/ThreadItem.php:399
+#: ../../Zotlabs/Module/Photos.php:1259 ../../Zotlabs/Lib/ThreadItem.php:401
msgctxt "noun"
msgid "Dislikes"
msgstr "vinden dit niet leuk"
-#: ../../Zotlabs/Module/Photos.php:1269 ../../Zotlabs/Lib/ThreadItem.php:404
-#: ../../include/acl_selectors.php:210
+#: ../../Zotlabs/Module/Photos.php:1264 ../../Zotlabs/Lib/ThreadItem.php:406
+#: ../../include/acl_selectors.php:220
msgid "Close"
msgstr "Sluiten"
-#: ../../Zotlabs/Module/Photos.php:1343
+#: ../../Zotlabs/Module/Photos.php:1341
msgid "View Album"
msgstr "Album weergeven"
-#: ../../Zotlabs/Module/Photos.php:1354 ../../Zotlabs/Module/Photos.php:1367
-#: ../../Zotlabs/Module/Photos.php:1368
+#: ../../Zotlabs/Module/Photos.php:1352 ../../Zotlabs/Module/Photos.php:1365
+#: ../../Zotlabs/Module/Photos.php:1366
msgid "Recent Photos"
msgstr "Recente foto's"
-#: ../../Zotlabs/Module/Setup.php:176
-msgid "$Projectname Server - Setup"
-msgstr "$Projectname Hub - Setup"
+#: ../../Zotlabs/Module/Group.php:24
+msgid "Privacy group created."
+msgstr "Privacygroep aangemaakt"
-#: ../../Zotlabs/Module/Setup.php:180
-msgid "Could not connect to database."
-msgstr "Could not connect to database."
+#: ../../Zotlabs/Module/Group.php:30
+msgid "Could not create privacy group."
+msgstr "Kon privacygroep niet aanmaken"
-#: ../../Zotlabs/Module/Setup.php:184
-msgid ""
-"Could not connect to specified site URL. Possible SSL certificate or DNS "
-"issue."
-msgstr "Could not connect to specified hub URL. Possible SSL certificate or DNS issue."
+#: ../../Zotlabs/Module/Group.php:42 ../../Zotlabs/Module/Group.php:141
+#: ../../include/items.php:3901
+msgid "Privacy group not found."
+msgstr "Privacygroep niet gevonden"
-#: ../../Zotlabs/Module/Setup.php:191
-msgid "Could not create table."
-msgstr "Could not create table."
+#: ../../Zotlabs/Module/Group.php:58
+msgid "Privacy group updated."
+msgstr "Privacygroep bijgewerkt"
-#: ../../Zotlabs/Module/Setup.php:196
-msgid "Your site database has been installed."
-msgstr "Your hub database has been installed."
+#: ../../Zotlabs/Module/Group.php:90
+msgid "Create a group of channels."
+msgstr "Privacygroep met kanalen aanmaken"
-#: ../../Zotlabs/Module/Setup.php:200
-msgid ""
-"You may need to import the file \"install/schema_xxx.sql\" manually using a "
-"database client."
-msgstr "You may need to import the file \"install/schema_xxx.sql\" manually using a database client."
+#: ../../Zotlabs/Module/Group.php:91 ../../Zotlabs/Module/Group.php:184
+msgid "Privacy group name: "
+msgstr "Naam privacygroep: "
-#: ../../Zotlabs/Module/Setup.php:201 ../../Zotlabs/Module/Setup.php:263
-#: ../../Zotlabs/Module/Setup.php:745
-msgid "Please see the file \"install/INSTALL.txt\"."
-msgstr "Please see the file \"install/INSTALL.txt\"."
+#: ../../Zotlabs/Module/Group.php:93 ../../Zotlabs/Module/Group.php:187
+msgid "Members are visible to other channels"
+msgstr "Kanalen in deze privacygroep zijn zichtbaar voor andere kanalen"
-#: ../../Zotlabs/Module/Setup.php:260
-msgid "System check"
-msgstr "System check"
+#: ../../Zotlabs/Module/Group.php:111
+msgid "Privacy group removed."
+msgstr "Privacygroep verwijderd."
-#: ../../Zotlabs/Module/Setup.php:265
-msgid "Check again"
-msgstr "Check again"
+#: ../../Zotlabs/Module/Group.php:113
+msgid "Unable to remove privacy group."
+msgstr "Verwijderen privacygroep mislukt"
-#: ../../Zotlabs/Module/Setup.php:287
-msgid "Database connection"
-msgstr "Database connection"
+#: ../../Zotlabs/Module/Group.php:183
+msgid "Privacy group editor"
+msgstr "Privacygroep bewerken"
-#: ../../Zotlabs/Module/Setup.php:288
-msgid ""
-"In order to install $Projectname we need to know how to connect to your "
-"database."
-msgstr "In order to install $Projectname we need to know how to connect to your database."
+#: ../../Zotlabs/Module/Group.php:199
+msgid "All Connected Channels"
+msgstr "Alle kanaalconnecties"
-#: ../../Zotlabs/Module/Setup.php:289
-msgid ""
-"Please contact your hosting provider or site administrator if you have "
-"questions about these settings."
-msgstr "Please contact your hosting provider or server administrator if you have questions about these settings."
+#: ../../Zotlabs/Module/Group.php:231
+msgid "Click on a channel to add or remove."
+msgstr "Klik op een kanaal om deze toe te voegen of te verwijderen."
-#: ../../Zotlabs/Module/Setup.php:290
-msgid ""
-"The database you specify below should already exist. If it does not, please "
-"create it before continuing."
-msgstr "The database you specify below should already exist. If it does not, please create it before continuing."
+#: ../../Zotlabs/Module/Dreport.php:45
+msgid "Invalid message"
+msgstr "Ongeldig bericht"
-#: ../../Zotlabs/Module/Setup.php:294
-msgid "Database Server Name"
-msgstr "Database Server Name"
+#: ../../Zotlabs/Module/Dreport.php:78
+msgid "no results"
+msgstr "geen resultaten"
-#: ../../Zotlabs/Module/Setup.php:294
-msgid "Default is 127.0.0.1"
-msgstr "Default is 127.0.0.1"
+#: ../../Zotlabs/Module/Dreport.php:93
+msgid "channel sync processed"
+msgstr "kanaalsync verwerkt"
-#: ../../Zotlabs/Module/Setup.php:295
-msgid "Database Port"
-msgstr "Database Port"
+#: ../../Zotlabs/Module/Dreport.php:97
+msgid "queued"
+msgstr "in wachtrij"
-#: ../../Zotlabs/Module/Setup.php:295
-msgid "Communication port number - use 0 for default"
-msgstr "Communication port number - use 0 for default"
+#: ../../Zotlabs/Module/Dreport.php:101
+msgid "posted"
+msgstr "verstuurd"
-#: ../../Zotlabs/Module/Setup.php:296
-msgid "Database Login Name"
-msgstr "Database Login Name"
+#: ../../Zotlabs/Module/Dreport.php:105
+msgid "accepted for delivery"
+msgstr "geaccepteerd om afgeleverd te worden"
-#: ../../Zotlabs/Module/Setup.php:297
-msgid "Database Login Password"
-msgstr "Database Login Password"
+#: ../../Zotlabs/Module/Dreport.php:109
+msgid "updated"
+msgstr "geüpdatet"
-#: ../../Zotlabs/Module/Setup.php:298
-msgid "Database Name"
-msgstr "Database Name"
+#: ../../Zotlabs/Module/Dreport.php:112
+msgid "update ignored"
+msgstr "update genegeerd"
-#: ../../Zotlabs/Module/Setup.php:299
-msgid "Database Type"
-msgstr "Database Type"
+#: ../../Zotlabs/Module/Dreport.php:115
+msgid "permission denied"
+msgstr "toegang geweigerd"
-#: ../../Zotlabs/Module/Setup.php:301 ../../Zotlabs/Module/Setup.php:347
-msgid "Site administrator email address"
-msgstr "Hub administrator email address"
+#: ../../Zotlabs/Module/Dreport.php:119
+msgid "recipient not found"
+msgstr "ontvanger niet gevonden"
-#: ../../Zotlabs/Module/Setup.php:301 ../../Zotlabs/Module/Setup.php:347
-msgid ""
-"Your account email address must match this in order to use the web admin "
-"panel."
-msgstr "Your account email address must match this in order to use the web admin panel."
+#: ../../Zotlabs/Module/Dreport.php:122
+msgid "mail recalled"
+msgstr "Privébericht ingetrokken"
-#: ../../Zotlabs/Module/Setup.php:302 ../../Zotlabs/Module/Setup.php:349
-msgid "Website URL"
-msgstr "Hub URL"
+#: ../../Zotlabs/Module/Dreport.php:125
+msgid "duplicate mail received"
+msgstr "dubbel privébericht ontvangen"
-#: ../../Zotlabs/Module/Setup.php:302 ../../Zotlabs/Module/Setup.php:349
-msgid "Please use SSL (https) URL if available."
-msgstr "Please use SSL (https) URL if available."
+#: ../../Zotlabs/Module/Dreport.php:128
+msgid "mail delivered"
+msgstr "privébericht afgeleverd"
-#: ../../Zotlabs/Module/Setup.php:303 ../../Zotlabs/Module/Setup.php:353
-msgid "Please select a default timezone for your website"
-msgstr "Please select a default timezone for your hub"
+#: ../../Zotlabs/Module/Dreport.php:148
+#, php-format
+msgid "Delivery report for %1$s"
+msgstr "Afleveringsrapport voor %1$s"
-#: ../../Zotlabs/Module/Setup.php:336
-msgid "Site settings"
-msgstr "Hub settings"
+#: ../../Zotlabs/Module/Dreport.php:151
+msgid "Options"
+msgstr "Opties"
-#: ../../Zotlabs/Module/Setup.php:392
-msgid "PHP version 5.5 or greater is required."
-msgstr "PHP version 5.5 or greater is required."
+#: ../../Zotlabs/Module/Dreport.php:152
+msgid "Redeliver"
+msgstr "Opnieuw afleveren"
-#: ../../Zotlabs/Module/Setup.php:393
-msgid "PHP version"
-msgstr "PHP version"
+#: ../../Zotlabs/Module/Mail.php:65
+msgid "Unable to lookup recipient."
+msgstr "Niet in staat om ontvanger op te zoeken."
-#: ../../Zotlabs/Module/Setup.php:409
-msgid "Could not find a command line version of PHP in the web server PATH."
-msgstr "Could not find a command line version of PHP in the web server PATH."
+#: ../../Zotlabs/Module/Mail.php:72
+msgid "Unable to communicate with requested channel."
+msgstr "Niet in staat om met het aangevraagde kanaal te communiceren."
-#: ../../Zotlabs/Module/Setup.php:410
-msgid ""
-"If you don't have a command line version of PHP installed on server, you "
-"will not be able to run background polling via cron."
-msgstr "If you don't have a command line version of PHP installed on server, you will not be able to run background polling via cron."
+#: ../../Zotlabs/Module/Mail.php:79
+msgid "Cannot verify requested channel."
+msgstr "Kan opgevraagd kanaal niet verifieren"
-#: ../../Zotlabs/Module/Setup.php:414
-msgid "PHP executable path"
-msgstr "PHP executable path"
+#: ../../Zotlabs/Module/Mail.php:97
+msgid "Selected channel has private message restrictions. Send failed."
+msgstr "Gekozen kanaal heeft restricties voor privéberichten. Verzenden mislukt."
-#: ../../Zotlabs/Module/Setup.php:414
-msgid ""
-"Enter full path to php executable. You can leave this blank to continue the "
-"installation."
-msgstr "Enter full path to php executable. You can leave this blank to continue the installation."
+#: ../../Zotlabs/Module/Mail.php:178
+msgid "Messages"
+msgstr "Berichten"
-#: ../../Zotlabs/Module/Setup.php:419
-msgid "Command line PHP"
-msgstr "Command line PHP"
+#: ../../Zotlabs/Module/Mail.php:213
+msgid "Message recalled."
+msgstr "Bericht ingetrokken."
-#: ../../Zotlabs/Module/Setup.php:429
-msgid ""
-"Unable to check command line PHP, as shell_exec() is disabled. This is "
-"required."
-msgstr "Unable to check command line PHP, as shell_exec() is disabled. This is required."
+#: ../../Zotlabs/Module/Mail.php:226
+msgid "Conversation removed."
+msgstr "Conversatie verwijderd"
-#: ../../Zotlabs/Module/Setup.php:432
-msgid ""
-"The command line version of PHP on your system does not have "
-"\"register_argc_argv\" enabled."
-msgstr "The command line version of PHP on your system does not have \"register_argc_argv\" enabled."
+#: ../../Zotlabs/Module/Mail.php:240 ../../Zotlabs/Module/Mail.php:349
+#: ../../Zotlabs/Module/Chat.php:203 ../../include/conversation.php:1330
+msgid "Please enter a link URL:"
+msgstr "Vul een URL in:"
-#: ../../Zotlabs/Module/Setup.php:433
-msgid "This is required for message delivery to work."
-msgstr "This is required for message delivery to work."
+#: ../../Zotlabs/Module/Mail.php:241 ../../Zotlabs/Module/Mail.php:350
+msgid "Expires YYYY-MM-DD HH:MM"
+msgstr "Verloopt op DD-MM-YYYY om HH:MM"
-#: ../../Zotlabs/Module/Setup.php:436
-msgid "PHP register_argc_argv"
-msgstr "PHP register_argc_argv"
+#: ../../Zotlabs/Module/Mail.php:269
+msgid "Requested channel is not in this network"
+msgstr "Opgevraagd kanaal is niet in dit netwerk beschikbaar"
-#: ../../Zotlabs/Module/Setup.php:454
-#, php-format
-msgid ""
-"Your max allowed total upload size is set to %s. Maximum size of one file to"
-" upload is set to %s. You are allowed to upload up to %d files at once."
-msgstr "Your max allowed total upload size is set to %s. Maximum size of one file to upload is set to %s. You are allowed to upload up to %d files at once."
+#: ../../Zotlabs/Module/Mail.php:277
+msgid "Send Private Message"
+msgstr "Privébericht versturen"
-#: ../../Zotlabs/Module/Setup.php:459
-msgid "You can adjust these settings in the server php.ini file."
-msgstr "You can adjust these settings in the server php.ini file."
+#: ../../Zotlabs/Module/Mail.php:278 ../../Zotlabs/Module/Mail.php:403
+msgid "To:"
+msgstr "Aan:"
-#: ../../Zotlabs/Module/Setup.php:461
-msgid "PHP upload limits"
-msgstr "PHP upload limits"
+#: ../../Zotlabs/Module/Mail.php:281 ../../Zotlabs/Module/Mail.php:405
+msgid "Subject:"
+msgstr "Onderwerp:"
-#: ../../Zotlabs/Module/Setup.php:484
-msgid ""
-"Error: the \"openssl_pkey_new\" function on this system is not able to "
-"generate encryption keys"
-msgstr "Error: the \"openssl_pkey_new\" function on this system is not able to generate encryption keys"
+#: ../../Zotlabs/Module/Mail.php:284 ../../Zotlabs/Module/Invite.php:138
+msgid "Your message:"
+msgstr "Jouw bericht:"
-#: ../../Zotlabs/Module/Setup.php:485
-msgid ""
-"If running under Windows, please see "
-"\"http://www.php.net/manual/en/openssl.installation.php\"."
-msgstr "If running under Windows, please see \"http://www.php.net/manual/en/openssl.installation.php\"."
+#: ../../Zotlabs/Module/Mail.php:286 ../../Zotlabs/Module/Mail.php:411
+#: ../../include/conversation.php:1390
+msgid "Attach file"
+msgstr "Bestand toevoegen"
-#: ../../Zotlabs/Module/Setup.php:488
-msgid "Generate encryption keys"
-msgstr "Generate encryption keys"
+#: ../../Zotlabs/Module/Mail.php:288
+msgid "Send"
+msgstr "Verzenden"
-#: ../../Zotlabs/Module/Setup.php:500
-msgid "libCurl PHP module"
-msgstr "libCurl PHP module"
+#: ../../Zotlabs/Module/Mail.php:291 ../../Zotlabs/Module/Mail.php:416
+#: ../../include/conversation.php:1435
+msgid "Set expiration date"
+msgstr "Verloopdatum instellen"
-#: ../../Zotlabs/Module/Setup.php:501
-msgid "GD graphics PHP module"
-msgstr "GD graphics PHP module"
+#: ../../Zotlabs/Module/Mail.php:293 ../../Zotlabs/Module/Mail.php:418
+#: ../../Zotlabs/Module/Chat.php:204 ../../Zotlabs/Lib/ThreadItem.php:743
+#: ../../include/conversation.php:1440
+msgid "Encrypt text"
+msgstr "Tekst versleutelen"
-#: ../../Zotlabs/Module/Setup.php:502
-msgid "OpenSSL PHP module"
-msgstr "OpenSSL PHP module"
+#: ../../Zotlabs/Module/Mail.php:375
+msgid "Delete message"
+msgstr "Bericht verwijderen"
-#: ../../Zotlabs/Module/Setup.php:503
-msgid "PDO database PHP module"
-msgstr "PDO database PHP module"
+#: ../../Zotlabs/Module/Mail.php:376
+msgid "Delivery report"
+msgstr "Afleveringsrapport"
-#: ../../Zotlabs/Module/Setup.php:504
-msgid "mb_string PHP module"
-msgstr "mb_string PHP module"
+#: ../../Zotlabs/Module/Mail.php:377
+msgid "Recall message"
+msgstr "Bericht intrekken"
-#: ../../Zotlabs/Module/Setup.php:505
-msgid "xml PHP module"
-msgstr "xml PHP module"
+#: ../../Zotlabs/Module/Mail.php:379
+msgid "Message has been recalled."
+msgstr "Bericht is ingetrokken."
-#: ../../Zotlabs/Module/Setup.php:509 ../../Zotlabs/Module/Setup.php:511
-msgid "Apache mod_rewrite module"
-msgstr "Apache mod_rewrite module"
+#: ../../Zotlabs/Module/Mail.php:396
+msgid "Delete Conversation"
+msgstr "Verwijder conversatie"
-#: ../../Zotlabs/Module/Setup.php:509
+#: ../../Zotlabs/Module/Mail.php:398
msgid ""
-"Error: Apache webserver mod-rewrite module is required but not installed."
-msgstr "Error: Apache webserver mod-rewrite module is required but not installed."
+"No secure communications available. You <strong>may</strong> be able to "
+"respond from the sender's profile page."
+msgstr "Geen veilige communicatie beschikbaar. <strong>Mogelijk</strong> kan je reageren op de kanaalpagina van de afzender."
-#: ../../Zotlabs/Module/Setup.php:515 ../../Zotlabs/Module/Setup.php:518
-msgid "exec"
-msgstr "exec"
+#: ../../Zotlabs/Module/Mail.php:402
+msgid "Send Reply"
+msgstr "Antwoord versturen"
-#: ../../Zotlabs/Module/Setup.php:515
-msgid ""
-"Error: exec is required but is either not installed or has been disabled in "
-"php.ini"
-msgstr "Error: exec is required but is either not installed or has been disabled in php.ini"
+#: ../../Zotlabs/Module/Mail.php:407
+#, php-format
+msgid "Your message for %s (%s):"
+msgstr "Jouw privébericht aan %s (%s):"
-#: ../../Zotlabs/Module/Setup.php:521 ../../Zotlabs/Module/Setup.php:524
-msgid "shell_exec"
-msgstr "shell_exec"
+#: ../../Zotlabs/Module/Impel.php:41 ../../include/bbcode.php:203
+msgid "webpage"
+msgstr "Webpagina"
-#: ../../Zotlabs/Module/Setup.php:521
-msgid ""
-"Error: shell_exec is required but is either not installed or has been "
-"disabled in php.ini"
-msgstr "Error: shell_exec is required but is either not installed or has been disabled in php.ini"
+#: ../../Zotlabs/Module/Impel.php:46 ../../include/bbcode.php:209
+msgid "block"
+msgstr "blok"
-#: ../../Zotlabs/Module/Setup.php:529
-msgid "Error: libCURL PHP module required but not installed."
-msgstr "Error: libCURL PHP module required but not installed."
+#: ../../Zotlabs/Module/Impel.php:51 ../../include/bbcode.php:206
+msgid "layout"
+msgstr "lay-out"
-#: ../../Zotlabs/Module/Setup.php:533
-msgid ""
-"Error: GD graphics PHP module with JPEG support required but not installed."
-msgstr "Error: GD graphics PHP module with JPEG support required but not installed."
+#: ../../Zotlabs/Module/Impel.php:58 ../../include/bbcode.php:212
+msgid "menu"
+msgstr "menu"
-#: ../../Zotlabs/Module/Setup.php:537
-msgid "Error: openssl PHP module required but not installed."
-msgstr "Error: openssl PHP module required but not installed."
+#: ../../Zotlabs/Module/Impel.php:191
+#, php-format
+msgid "%s element installed"
+msgstr "%s onderdeel geïnstalleerd"
-#: ../../Zotlabs/Module/Setup.php:541
-msgid "Error: PDO database PHP module required but not installed."
-msgstr "Error: PDO database PHP module required but not installed."
+#: ../../Zotlabs/Module/Impel.php:194
+#, php-format
+msgid "%s element installation failed"
+msgstr "Installatie %s-element mislukt"
-#: ../../Zotlabs/Module/Setup.php:545
-msgid "Error: mb_string PHP module required but not installed."
-msgstr "Error: mb_string PHP module required but not installed."
+#: ../../Zotlabs/Module/Import_items.php:104
+msgid "Import completed"
+msgstr "Importeren voltooid"
-#: ../../Zotlabs/Module/Setup.php:549
-msgid "Error: xml PHP module required for DAV but not installed."
-msgstr "Error: xml PHP module required for DAV but not installed."
+#: ../../Zotlabs/Module/Import_items.php:119
+msgid "Import Items"
+msgstr "Importeer items"
-#: ../../Zotlabs/Module/Setup.php:567
+#: ../../Zotlabs/Module/Import_items.php:120
msgid ""
-"The web installer needs to be able to create a file called \".htconfig.php\""
-" in the top folder of your web server and it is unable to do so."
-msgstr "The web installer needs to be able to create a file called \".htconfig.php\" in the top folder of your web server and it is unable to do so."
+"Use this form to import existing posts and content from an export file."
+msgstr "Gebruik dit formulier om bestaande berichten en andere inhoud vanuit een exportbestand te importeren."
-#: ../../Zotlabs/Module/Setup.php:568
-msgid ""
-"This is most often a permission setting, as the web server may not be able "
-"to write files in your folder - even if you can."
-msgstr "This is most often a permission setting, as the web server may not be able to write files in your folder - even if you can."
+#: ../../Zotlabs/Module/Manage.php:136
+#: ../../Zotlabs/Module/New_channel.php:121
+#, php-format
+msgid "You have created %1$.0f of %2$.0f allowed channels."
+msgstr "Je hebt %1$.0f van totaal %2$.0f toegestane kanalen aangemaakt."
-#: ../../Zotlabs/Module/Setup.php:569
-msgid ""
-"At the end of this procedure, we will give you a text to save in a file "
-"named .htconfig.php in your Red top folder."
-msgstr "At the end of this procedure, we will give you a text to save in a file named .htconfig.php in your Red top folder."
+#: ../../Zotlabs/Module/Manage.php:143
+msgid "Create a new channel"
+msgstr "Nieuw kanaal aanmaken"
-#: ../../Zotlabs/Module/Setup.php:570
-msgid ""
-"You can alternatively skip this procedure and perform a manual installation."
-" Please see the file \"install/INSTALL.txt\" for instructions."
-msgstr "You can alternatively skip this procedure and perform a manual installation. Please see the file \"install/INSTALL.txt\" for instructions."
+#: ../../Zotlabs/Module/Manage.php:143 ../../Zotlabs/Module/Profiles.php:834
+#: ../../Zotlabs/Module/Wiki.php:167 ../../Zotlabs/Module/Chat.php:253
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:152
+msgid "Create New"
+msgstr "Nieuwe aanmaken"
-#: ../../Zotlabs/Module/Setup.php:573
-msgid ".htconfig.php is writable"
-msgstr ".htconfig.php is writable"
+#: ../../Zotlabs/Module/Manage.php:164 ../../Zotlabs/Lib/Apps.php:221
+#: ../../include/nav.php:223
+msgid "Channel Manager"
+msgstr "Kanaalbeheer"
-#: ../../Zotlabs/Module/Setup.php:587
-msgid ""
-"This software uses the Smarty3 template engine to render its web views. "
-"Smarty3 compiles templates to PHP to speed up rendering."
-msgstr "This software uses the Smarty3 template engine to render its web views. Smarty3 compiles templates to PHP to speed up rendering."
+#: ../../Zotlabs/Module/Manage.php:165
+msgid "Current Channel"
+msgstr "Huidig kanaal"
-#: ../../Zotlabs/Module/Setup.php:588
-#, php-format
-msgid ""
-"In order to store these compiled templates, the web server needs to have "
-"write access to the directory %s under the top level web folder."
-msgstr "In order to store these compiled templates, the web server needs to have write access to the directory %s under the top level web folder."
+#: ../../Zotlabs/Module/Manage.php:167
+msgid "Switch to one of your channels by selecting it."
+msgstr "Activeer een van jouw andere kanalen door er op te klikken."
-#: ../../Zotlabs/Module/Setup.php:589 ../../Zotlabs/Module/Setup.php:610
-msgid ""
-"Please ensure that the user that your web server runs as (e.g. www-data) has"
-" write access to this folder."
-msgstr "Please ensure that the user that your web server runs as (e.g. www-data) has write access to this folder."
+#: ../../Zotlabs/Module/Manage.php:168
+msgid "Default Channel"
+msgstr "Standaardkanaal"
+
+#: ../../Zotlabs/Module/Manage.php:169
+msgid "Make Default"
+msgstr "Als standaard instellen"
-#: ../../Zotlabs/Module/Setup.php:590
+#: ../../Zotlabs/Module/Manage.php:172
#, php-format
-msgid ""
-"Note: as a security measure, you should give the web server write access to "
-"%s only--not the template files (.tpl) that it contains."
-msgstr "Note: as a security measure, you should give the web server write access to %s only--not the template files (.tpl) that it contains."
+msgid "%d new messages"
+msgstr "%d nieuwe berichten"
-#: ../../Zotlabs/Module/Setup.php:593
+#: ../../Zotlabs/Module/Manage.php:173
#, php-format
-msgid "%s is writable"
-msgstr "%s is writable"
+msgid "%d new introductions"
+msgstr "%d nieuwe connectieverzoeken"
-#: ../../Zotlabs/Module/Setup.php:609
-msgid ""
-"This software uses the store directory to save uploaded files. The web "
-"server needs to have write access to the store directory under the top level"
-" web folder"
-msgstr "This software uses the store directory to save uploaded files. The web server needs to have write access to the store directory under the top level web folder"
+#: ../../Zotlabs/Module/Manage.php:175
+msgid "Delegated Channel"
+msgstr "Uitbesteed kanaal"
-#: ../../Zotlabs/Module/Setup.php:613
-msgid "store is writable"
-msgstr "store is writable"
+#: ../../Zotlabs/Module/Magic.php:71
+msgid "Hub not found."
+msgstr "Hub niet gevonden."
-#: ../../Zotlabs/Module/Setup.php:646
-msgid ""
-"SSL certificate cannot be validated. Fix certificate or disable https access"
-" to this site."
-msgstr "SSL certificate cannot be validated. Fix certificate or disable https access to this hub."
+#: ../../Zotlabs/Module/Mitem.php:52
+msgid "Unable to create element."
+msgstr "Niet in staat om onderdeel aan te maken."
-#: ../../Zotlabs/Module/Setup.php:647
-msgid ""
-"If you have https access to your website or allow connections to TCP port "
-"443 (the https: port), you MUST use a browser-valid certificate. You MUST "
-"NOT use self-signed certificates!"
-msgstr "If you have https access to your hub or allow connections to TCP port 443 (the https: port), you MUST use a browser-valid certificate. You MUST NOT use self-signed certificates!"
+#: ../../Zotlabs/Module/Mitem.php:76
+msgid "Unable to update menu element."
+msgstr "Menu-onderdeel kan niet worden geüpdatet."
-#: ../../Zotlabs/Module/Setup.php:648
-msgid ""
-"This restriction is incorporated because public posts from you may for "
-"example contain references to images on your own hub."
-msgstr "This restriction is incorporated because public posts from you may for example contain references to images on your own hub."
+#: ../../Zotlabs/Module/Mitem.php:92
+msgid "Unable to add menu element."
+msgstr "Menu-onderdeel kan niet worden toegevoegd."
-#: ../../Zotlabs/Module/Setup.php:649
-msgid ""
-"If your certificate is not recognized, members of other sites (who may "
-"themselves have valid certificates) will get a warning message on their own "
-"site complaining about security issues."
-msgstr "If your certificate is not recognized, members of other hubs (who may themselves have valid certificates) will get a warning message on their own hub complaining about security issues."
+#: ../../Zotlabs/Module/Mitem.php:153 ../../Zotlabs/Module/Mitem.php:230
+msgid "Menu Item Permissions"
+msgstr "Permissies menu-item"
-#: ../../Zotlabs/Module/Setup.php:650
-msgid ""
-"This can cause usability issues elsewhere (not just on your own site) so we "
-"must insist on this requirement."
-msgstr "This can cause usability issues elsewhere (not just on your own hub) so we must insist on this requirement."
+#: ../../Zotlabs/Module/Mitem.php:154 ../../Zotlabs/Module/Mitem.php:231
+#: ../../Zotlabs/Module/Settings/Channel.php:510
+msgid "(click to open/close)"
+msgstr "(klik om te openen/sluiten)"
-#: ../../Zotlabs/Module/Setup.php:651
-msgid ""
-"Providers are available that issue free certificates which are browser-"
-"valid."
-msgstr "Providers are available that issue free certificates which are browser-valid."
+#: ../../Zotlabs/Module/Mitem.php:160 ../../Zotlabs/Module/Mitem.php:176
+msgid "Link Name"
+msgstr "Linknaam"
-#: ../../Zotlabs/Module/Setup.php:653
-msgid ""
-"If you are confident that the certificate is valid and signed by a trusted "
-"authority, check to see if you have failed to install an intermediate cert. "
-"These are not normally required by browsers, but are required for server-to-"
-"server communications."
-msgstr "If you are confident that the certificate is valid and signed by a trusted authority, check to see if you have failed to install an intermediate cert. These are not normally required by browsers, but are required for server-to-server communications."
+#: ../../Zotlabs/Module/Mitem.php:161 ../../Zotlabs/Module/Mitem.php:239
+msgid "Link or Submenu Target"
+msgstr "Linkdoel of submenu-doel"
-#: ../../Zotlabs/Module/Setup.php:655
-msgid "SSL certificate validation"
-msgstr "SSL certificate validation"
+#: ../../Zotlabs/Module/Mitem.php:161
+msgid "Enter URL of the link or select a menu name to create a submenu"
+msgstr "Geef de URL van de link of kies een menunaam om een submenu aan te maken"
-#: ../../Zotlabs/Module/Setup.php:661
-msgid ""
-"Url rewrite in .htaccess is not working. Check your server "
-"configuration.Test: "
-msgstr "Url rewrite in .htaccess is not working. Check your server configuration.Test: "
+#: ../../Zotlabs/Module/Mitem.php:162 ../../Zotlabs/Module/Mitem.php:240
+msgid "Use magic-auth if available"
+msgstr "Gebruik magic-auth wanneer beschikbaar"
-#: ../../Zotlabs/Module/Setup.php:664
-msgid "Url rewrite is working"
-msgstr "Url rewrite is working"
+#: ../../Zotlabs/Module/Mitem.php:163 ../../Zotlabs/Module/Mitem.php:241
+msgid "Open link in new window"
+msgstr "Open link in nieuw venster"
-#: ../../Zotlabs/Module/Setup.php:678
-msgid ""
-"The database configuration file \".htconfig.php\" could not be written. "
-"Please use the enclosed text to create a configuration file in your web "
-"server root."
-msgstr "The database configuration file \".htconfig.php\" could not be written. Please use the enclosed text to create a configuration file in your web server root."
+#: ../../Zotlabs/Module/Mitem.php:164 ../../Zotlabs/Module/Mitem.php:242
+msgid "Order in list"
+msgstr "Volgorde in lijst"
-#: ../../Zotlabs/Module/Setup.php:702
-#: ../../extend/addon/addon/cdav/cdav.php:41
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:385
-msgid "Errors encountered creating database tables."
-msgstr "Errors encountered creating database tables."
+#: ../../Zotlabs/Module/Mitem.php:164 ../../Zotlabs/Module/Mitem.php:242
+msgid "Higher numbers will sink to bottom of listing"
+msgstr "Hogere nummers komen onderaan de lijst terecht"
-#: ../../Zotlabs/Module/Setup.php:743
-msgid "<h1>What next</h1>"
-msgstr "<h1>What next</h1>"
+#: ../../Zotlabs/Module/Mitem.php:165
+msgid "Submit and finish"
+msgstr "Opslaan en afsluiten"
-#: ../../Zotlabs/Module/Setup.php:744
-msgid ""
-"IMPORTANT: You will need to [manually] setup a scheduled task for the "
-"poller."
-msgstr "IMPORTANT: You will need to [manually] setup a scheduled task for the poller."
+#: ../../Zotlabs/Module/Mitem.php:166
+msgid "Submit and continue"
+msgstr "Opslaan en doorgaan"
-#: ../../Zotlabs/Module/Editpost.php:35
-msgid "Item is not editable"
-msgstr "Item is niet te bewerken"
+#: ../../Zotlabs/Module/Mitem.php:174
+msgid "Menu:"
+msgstr "Menu:"
-#: ../../Zotlabs/Module/Regdir.php:49 ../../Zotlabs/Module/Dirsearch.php:25
-msgid "This site is not a directory server"
-msgstr "Deze hub is geen kanalengidshub (directoryserver)"
+#: ../../Zotlabs/Module/Mitem.php:177
+msgid "Link Target"
+msgstr "Linkdoel"
-#: ../../Zotlabs/Module/New_channel.php:140
-msgid "Create Channel"
-msgstr "Kanaal aanmaken"
+#: ../../Zotlabs/Module/Mitem.php:180
+msgid "Edit menu"
+msgstr "Menu bewerken"
-#: ../../Zotlabs/Module/New_channel.php:141
-msgid ""
-"A channel is your identity on this network. It can represent a person, a "
-"blog, or a forum to name a few. Channels can make connections with other "
-"channels to share information with highly detailed permissions."
-msgstr "Een kanaal is jouw identiteit in dit netwerk. Het kan bijvoorbeeld een persoon, een blog of een forum vertegenwoordigen. Door met elkaar te verbinden kunnen kanalen, met behulp van uitgebreide permissies, informatie uitwisselen."
+#: ../../Zotlabs/Module/Mitem.php:183
+msgid "Edit element"
+msgstr "Onderdeel bewerken"
-#: ../../Zotlabs/Module/New_channel.php:142
-msgid ""
-"or <a href=\"import\">import an existing channel</a> from another location."
-msgstr "Of <a href=\"import\">importeer een bestaand kanaal</a> vanaf een andere locatie"
+#: ../../Zotlabs/Module/Mitem.php:184
+msgid "Drop element"
+msgstr "Onderdeel verwijderen"
-#: ../../Zotlabs/Module/Notifications.php:40 ../../include/nav.php:194
-msgid "Mark all system notifications seen"
-msgstr "Markeer alle systeemnotificaties als bekeken"
+#: ../../Zotlabs/Module/Mitem.php:185
+msgid "New element"
+msgstr "Nieuw element"
-#: ../../Zotlabs/Module/Poke.php:168 ../../Zotlabs/Lib/Apps.php:230
-#: ../../include/conversation.php:941
-msgid "Poke"
-msgstr "Aanstoten"
+#: ../../Zotlabs/Module/Mitem.php:186
+msgid "Edit this menu container"
+msgstr "Deze menu-container bewerken"
-#: ../../Zotlabs/Module/Poke.php:169
-msgid "Poke somebody"
-msgstr "Iemand aanstoten"
+#: ../../Zotlabs/Module/Mitem.php:187
+msgid "Add menu element"
+msgstr "Menu-element toevoegen"
-#: ../../Zotlabs/Module/Poke.php:172
-msgid "Poke/Prod"
-msgstr "Aanstoten/porren"
+#: ../../Zotlabs/Module/Mitem.php:188
+msgid "Delete this menu item"
+msgstr "Dit menu-item verwijderen"
-#: ../../Zotlabs/Module/Poke.php:173
-msgid "Poke, prod or do other things to somebody"
-msgstr "Iemand bijvoorbeeld aanstoten of poren"
+#: ../../Zotlabs/Module/Mitem.php:189
+msgid "Edit this menu item"
+msgstr "Dit menu-item bewerken"
-#: ../../Zotlabs/Module/Poke.php:180
-msgid "Recipient"
-msgstr "Ontvanger"
+#: ../../Zotlabs/Module/Mitem.php:206
+msgid "Menu item not found."
+msgstr "Menu-item niet gevonden."
-#: ../../Zotlabs/Module/Poke.php:181
-msgid "Choose what you wish to do to recipient"
-msgstr "Kies wat je met de ontvanger wil doen"
+#: ../../Zotlabs/Module/Mitem.php:219
+msgid "Menu item deleted."
+msgstr "Menu-item verwijderd."
-#: ../../Zotlabs/Module/Poke.php:184 ../../Zotlabs/Module/Poke.php:185
-msgid "Make this post private"
-msgstr "Maak dit bericht privé"
+#: ../../Zotlabs/Module/Mitem.php:221
+msgid "Menu item could not be deleted."
+msgstr "Menu-item kon niet worden verwijderd."
-#: ../../Zotlabs/Module/Profiles.php:24 ../../Zotlabs/Module/Profiles.php:183
-#: ../../Zotlabs/Module/Profiles.php:240 ../../Zotlabs/Module/Profiles.php:619
-#: ../../extend/addon/addon/friendica/dfrn_confirm.php:62
-msgid "Profile not found."
-msgstr "Profiel niet gevonden."
+#: ../../Zotlabs/Module/Mitem.php:228
+msgid "Edit Menu Element"
+msgstr "Menu-element bewerken"
-#: ../../Zotlabs/Module/Profiles.php:44
-msgid "Profile deleted."
-msgstr "Profiel verwijderd."
+#: ../../Zotlabs/Module/Mitem.php:238
+msgid "Link text"
+msgstr "Linktekst"
-#: ../../Zotlabs/Module/Profiles.php:68 ../../Zotlabs/Module/Profiles.php:104
-msgid "Profile-"
-msgstr "Profiel-"
+#: ../../Zotlabs/Module/Editpost.php:35
+msgid "Item is not editable"
+msgstr "Item is niet te bewerken"
-#: ../../Zotlabs/Module/Profiles.php:89 ../../Zotlabs/Module/Profiles.php:126
-msgid "New profile created."
-msgstr "Nieuw profiel aangemaakt."
+#: ../../Zotlabs/Module/Ratings.php:70
+msgid "No ratings"
+msgstr "Geen beoordelingen"
-#: ../../Zotlabs/Module/Profiles.php:110
-msgid "Profile unavailable to clone."
-msgstr "Profiel niet beschikbaar om te klonen"
+#: ../../Zotlabs/Module/Ratings.php:98
+msgid "Rating: "
+msgstr "Beoordeling: "
-#: ../../Zotlabs/Module/Profiles.php:145
-msgid "Profile unavailable to export."
-msgstr "Geen profiel beschikbaar om te exporteren"
+#: ../../Zotlabs/Module/Ratings.php:99
+msgid "Website: "
+msgstr "Website: "
-#: ../../Zotlabs/Module/Profiles.php:250
-msgid "Profile Name is required."
-msgstr "Profielnaam is vereist"
+#: ../../Zotlabs/Module/Ratings.php:101
+msgid "Description: "
+msgstr "Omschrijving: "
-#: ../../Zotlabs/Module/Profiles.php:421
-msgid "Marital Status"
-msgstr "Huwelijke status"
+#: ../../Zotlabs/Module/Attach.php:13
+msgid "Item not available."
+msgstr "Item is niet aanwezig."
-#: ../../Zotlabs/Module/Profiles.php:425
-msgid "Romantic Partner"
-msgstr "Romantische partner"
+#: ../../Zotlabs/Module/Cal.php:69
+msgid "Permissions denied."
+msgstr "Permissies niet toegestaan"
-#: ../../Zotlabs/Module/Profiles.php:429 ../../Zotlabs/Module/Profiles.php:730
-msgid "Likes"
-msgstr "Houdt van"
+#: ../../Zotlabs/Module/Cal.php:341 ../../include/text.php:2312
+msgid "Import"
+msgstr "Importeren"
-#: ../../Zotlabs/Module/Profiles.php:433 ../../Zotlabs/Module/Profiles.php:731
-msgid "Dislikes"
-msgstr "Houdt niet van"
+#: ../../Zotlabs/Module/Notify.php:57
+#: ../../Zotlabs/Module/Notifications.php:38
+msgid "No more system notifications."
+msgstr "Geen systeemnotificaties meer."
-#: ../../Zotlabs/Module/Profiles.php:437 ../../Zotlabs/Module/Profiles.php:738
-msgid "Work/Employment"
-msgstr "Werk/arbeid"
+#: ../../Zotlabs/Module/Notify.php:61
+#: ../../Zotlabs/Module/Notifications.php:42
+msgid "System Notifications"
+msgstr "Systeemnotificaties"
-#: ../../Zotlabs/Module/Profiles.php:440
-msgid "Religion"
-msgstr "Religie"
+#: ../../Zotlabs/Module/Api.php:72 ../../Zotlabs/Module/Api.php:93
+msgid "Authorize application connection"
+msgstr "Geef toestemming voor applicatiekoppeling"
-#: ../../Zotlabs/Module/Profiles.php:444
-msgid "Political Views"
-msgstr "Politieke overtuigingen"
+#: ../../Zotlabs/Module/Api.php:73
+msgid "Return to your app and insert this Security Code:"
+msgstr "Ga terug naar je app en voeg deze beveiligingscode in:"
-#: ../../Zotlabs/Module/Profiles.php:448
-#: ../../extend/addon/addon/openid/MysqlProvider.php:74
-msgid "Gender"
-msgstr "Geslacht"
+#: ../../Zotlabs/Module/Api.php:83
+msgid "Please login to continue."
+msgstr "Inloggen om verder te kunnen gaan."
-#: ../../Zotlabs/Module/Profiles.php:452
-msgid "Sexual Preference"
-msgstr "Seksuele voorkeur"
+#: ../../Zotlabs/Module/Api.php:95
+msgid ""
+"Do you want to authorize this application to access your posts and contacts,"
+" and/or create new posts for you?"
+msgstr "Wil je deze applicatie toestemming geven om jouw berichten en connecties te zien, en/of nieuwe berichten voor jou te plaatsen?"
-#: ../../Zotlabs/Module/Profiles.php:456
-msgid "Homepage"
-msgstr "Homepage"
+#: ../../Zotlabs/Module/Invite.php:29
+msgid "Total invitation limit exceeded."
+msgstr "Limiet voor aantal uitnodigingen overschreden."
-#: ../../Zotlabs/Module/Profiles.php:460
-msgid "Interests"
-msgstr "Interesses"
+#: ../../Zotlabs/Module/Invite.php:53
+#, php-format
+msgid "%s : Not a valid email address."
+msgstr "%s : Geen geldig e-mailadres."
-#: ../../Zotlabs/Module/Profiles.php:554
-msgid "Profile updated."
-msgstr "Profiel bijgewerkt"
+#: ../../Zotlabs/Module/Invite.php:67
+msgid "Please join us on $Projectname"
+msgstr "Uitnodiging voor $Projectname"
-#: ../../Zotlabs/Module/Profiles.php:638
-msgid "Hide your connections list from viewers of this profile"
-msgstr "Laat de lijst met connecties niet aan bezoekers van dit profiel zien."
+#: ../../Zotlabs/Module/Invite.php:77
+msgid "Invitation limit exceeded. Please contact your site administrator."
+msgstr "Limiet voor aantal uitnodigingen overschreden. Neem contact op met je hub-beheerder."
-#: ../../Zotlabs/Module/Profiles.php:680
-msgid "Edit Profile Details"
-msgstr "Profiel bewerken"
+#: ../../Zotlabs/Module/Invite.php:82
+#, php-format
+msgid "%s : Message delivery failed."
+msgstr "%s: Aflevering bericht mislukt."
-#: ../../Zotlabs/Module/Profiles.php:682
-msgid "View this profile"
-msgstr "Profiel weergeven"
+#: ../../Zotlabs/Module/Invite.php:86
+#, php-format
+msgid "%d message sent."
+msgid_plural "%d messages sent."
+msgstr[0] "%d bericht verzonden."
+msgstr[1] "%d berichten verzonden."
-#: ../../Zotlabs/Module/Profiles.php:683 ../../Zotlabs/Module/Profiles.php:765
-#: ../../include/channel.php:983
-msgid "Edit visibility"
-msgstr "Zichtbaarheid bewerken"
+#: ../../Zotlabs/Module/Invite.php:105
+msgid "You have no more invitations available"
+msgstr "Je hebt geen uitnodigingen meer beschikbaar"
-#: ../../Zotlabs/Module/Profiles.php:684
-msgid "Profile Tools"
-msgstr "Hulpmiddelen"
+#: ../../Zotlabs/Module/Invite.php:136
+msgid "Send invitations"
+msgstr "Uitnodigingen verzenden"
-#: ../../Zotlabs/Module/Profiles.php:685
-msgid "Change cover photo"
-msgstr "Omslagfoto wijzigen"
+#: ../../Zotlabs/Module/Invite.php:137
+msgid "Enter email addresses, one per line:"
+msgstr "Voer e-mailadressen in, één per regel:"
-#: ../../Zotlabs/Module/Profiles.php:686 ../../include/channel.php:954
-msgid "Change profile photo"
-msgstr "Profielfoto veranderen"
+#: ../../Zotlabs/Module/Invite.php:139
+msgid "Please join my community on $Projectname."
+msgstr "Hierbij nodig ik je uit om mij, en andere vrienden en kennissen, op $Projectname te vergezellen. Lees meer over $Projectname op http://hubzilla.org"
-#: ../../Zotlabs/Module/Profiles.php:687
-msgid "Create a new profile using these settings"
-msgstr "Een nieuw profiel aanmaken met dit profiel als basis"
+#: ../../Zotlabs/Module/Invite.php:141
+msgid "You will need to supply this invitation code:"
+msgstr "Je moet deze uitnodigingscode opgeven:"
-#: ../../Zotlabs/Module/Profiles.php:688
-msgid "Clone this profile"
-msgstr "Dit profiel klonen"
+#: ../../Zotlabs/Module/Invite.php:142
+msgid ""
+"1. Register at any $Projectname location (they are all inter-connected)"
+msgstr "1. Registreer je op een willekeurige $Projectname-hub (ze zijn allemaal onderling met elkaar verbonden):"
-#: ../../Zotlabs/Module/Profiles.php:689
-msgid "Delete this profile"
-msgstr "Dit profiel verwijderen"
+#: ../../Zotlabs/Module/Invite.php:144
+msgid "2. Enter my $Projectname network address into the site searchbar."
+msgstr "2. Nadat je bent ingelogd en een kanaal hebt aangemaakt kan je mijn $Projectname-kanaaladres in het zoekveld invullen:"
-#: ../../Zotlabs/Module/Profiles.php:690
-msgid "Add profile things"
-msgstr "Dingen aan je profiel toevoegen"
+#: ../../Zotlabs/Module/Invite.php:145
+msgid "or visit"
+msgstr "of bezoek"
-#: ../../Zotlabs/Module/Profiles.php:691 ../../include/widgets.php:105
-#: ../../include/conversation.php:1567
-msgid "Personal"
-msgstr "Persoonlijk"
+#: ../../Zotlabs/Module/Invite.php:147
+msgid "3. Click [Connect]"
+msgstr "3. Klik op [+ Verbinden]"
-#: ../../Zotlabs/Module/Profiles.php:693
-msgid "Relation"
-msgstr "Relatie"
+#: ../../Zotlabs/Module/Siteinfo.php:20
+msgid "About this site"
+msgstr "Over deze hub"
-#: ../../Zotlabs/Module/Profiles.php:694 ../../include/datetime.php:55
-msgid "Miscellaneous"
-msgstr "Diversen"
+#: ../../Zotlabs/Module/Siteinfo.php:21
+msgid "Site Name"
+msgstr "Hubnaam"
-#: ../../Zotlabs/Module/Profiles.php:696
-msgid "Import profile from file"
-msgstr "Profiel vanuit bestand importeren"
+#: ../../Zotlabs/Module/Siteinfo.php:25 ../../include/network.php:1995
+msgid "Administrator"
+msgstr "Beheerder"
-#: ../../Zotlabs/Module/Profiles.php:697
-msgid "Export profile to file"
-msgstr "Profiel naar bestand exporteren"
+#: ../../Zotlabs/Module/Siteinfo.php:28
+msgid "Software and Project information"
+msgstr "Software- en projectinformatie"
-#: ../../Zotlabs/Module/Profiles.php:698
-msgid "Your gender"
-msgstr "Jouw geslacht"
+#: ../../Zotlabs/Module/Siteinfo.php:29
+msgid "This site is powered by $Projectname"
+msgstr "Dit is een $Projectname-hub"
-#: ../../Zotlabs/Module/Profiles.php:699
-msgid "Marital status"
-msgstr "Burgerlijke staat"
+#: ../../Zotlabs/Module/Siteinfo.php:30
+msgid ""
+"Federated and decentralised networking and identity services provided by Zot"
+msgstr "Federatieve en gedecentraliseerde netwerk- en identiteitsdiensten, mogelijk gemaakt door Zot"
-#: ../../Zotlabs/Module/Profiles.php:700
-msgid "Sexual preference"
-msgstr "Seksuele voorkeur"
+#: ../../Zotlabs/Module/Siteinfo.php:32
+#, php-format
+msgid "Version %s"
+msgstr "Versie %s"
-#: ../../Zotlabs/Module/Profiles.php:703
-msgid "Profile name"
-msgstr "Profielnaam"
+#: ../../Zotlabs/Module/Siteinfo.php:33
+msgid "Project homepage"
+msgstr "Projectwebsite"
-#: ../../Zotlabs/Module/Profiles.php:705
-msgid "This is your default profile."
-msgstr "Dit is jouw standaardprofiel"
+#: ../../Zotlabs/Module/Siteinfo.php:34
+msgid "Developer homepage"
+msgstr "Ontwikkelaarswebsite"
-#: ../../Zotlabs/Module/Profiles.php:707
-msgid "Your full name"
-msgstr "Jouw volledige naam"
+#: ../../Zotlabs/Module/New_channel.php:140
+msgid "Create Channel"
+msgstr "Kanaal aanmaken"
-#: ../../Zotlabs/Module/Profiles.php:708
-msgid "Title/Description"
-msgstr "Titel/omschrijving"
+#: ../../Zotlabs/Module/New_channel.php:141
+msgid ""
+"A channel is your identity on this network. It can represent a person, a "
+"blog, or a forum to name a few. Channels can make connections with other "
+"channels to share information with highly detailed permissions."
+msgstr "Een kanaal is jouw identiteit in dit netwerk. Het kan bijvoorbeeld een persoon, een blog of een forum vertegenwoordigen. Door met elkaar te verbinden kunnen kanalen, met behulp van uitgebreide permissies, informatie uitwisselen."
-#: ../../Zotlabs/Module/Profiles.php:711
-msgid "Street address"
-msgstr "Straat en huisnummer"
+#: ../../Zotlabs/Module/New_channel.php:142
+msgid ""
+"or <a href=\"import\">import an existing channel</a> from another location."
+msgstr "Of <a href=\"import\">importeer een bestaand kanaal</a> vanaf een andere locatie"
-#: ../../Zotlabs/Module/Profiles.php:712
-msgid "Locality/City"
-msgstr "Woonplaats"
+#: ../../Zotlabs/Module/Webpages.php:52
+msgid "Import Webpage Elements"
+msgstr "Webpagina-elementen importeren"
-#: ../../Zotlabs/Module/Profiles.php:713
-msgid "Region/State"
-msgstr "Provincie/gewest/deelstaat"
+#: ../../Zotlabs/Module/Webpages.php:53
+msgid "Import selected"
+msgstr "Importbestand geselecteerd"
-#: ../../Zotlabs/Module/Profiles.php:714
-msgid "Postal/Zip code"
-msgstr "Postcode"
+#: ../../Zotlabs/Module/Webpages.php:76
+msgid "Export Webpage Elements"
+msgstr "Webpagina-elementen exporteren"
-#: ../../Zotlabs/Module/Profiles.php:715
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1161
-msgid "Country"
-msgstr "Land"
+#: ../../Zotlabs/Module/Webpages.php:77
+msgid "Export selected"
+msgstr "Selectie exporteren"
-#: ../../Zotlabs/Module/Profiles.php:720
-msgid "Who (if applicable)"
-msgstr "Wie (wanneer van toepassing)"
+#: ../../Zotlabs/Module/Webpages.php:241 ../../Zotlabs/Lib/Apps.php:225
+#: ../../include/conversation.php:1889
+msgid "Webpages"
+msgstr "Webpagina's"
-#: ../../Zotlabs/Module/Profiles.php:720
-msgid "Examples: cathy123, Cathy Williams, cathy@example.com"
-msgstr "Voorbeelden: petra123, Petra Jansen, petra@voorbeeld.nl"
+#: ../../Zotlabs/Module/Webpages.php:252 ../../include/page_widgets.php:44
+msgid "Actions"
+msgstr "Acties"
-#: ../../Zotlabs/Module/Profiles.php:721
-msgid "Since (date)"
-msgstr "Sinds (datum)"
+#: ../../Zotlabs/Module/Webpages.php:253 ../../include/page_widgets.php:45
+msgid "Page Link"
+msgstr "Paginalink"
-#: ../../Zotlabs/Module/Profiles.php:724
-msgid "Tell us about yourself"
-msgstr "Vertel ons iets over jezelf"
+#: ../../Zotlabs/Module/Webpages.php:254
+msgid "Page Title"
+msgstr "Paginatitel"
-#: ../../Zotlabs/Module/Profiles.php:725
-#: ../../extend/addon/addon/openid/MysqlProvider.php:68
-msgid "Homepage URL"
-msgstr "URL homepagina"
+#: ../../Zotlabs/Module/Webpages.php:284
+msgid "Invalid file type."
+msgstr "Ongeldig bestandsformaat"
-#: ../../Zotlabs/Module/Profiles.php:726
-msgid "Hometown"
-msgstr "Oorspronkelijk uit"
+#: ../../Zotlabs/Module/Webpages.php:296
+msgid "Error opening zip file"
+msgstr "Fout tijdens openen zipbestand"
-#: ../../Zotlabs/Module/Profiles.php:727
-msgid "Political views"
-msgstr "Politieke overtuigingen"
+#: ../../Zotlabs/Module/Webpages.php:307
+msgid "Invalid folder path."
+msgstr "Ongeldige maplocatie"
-#: ../../Zotlabs/Module/Profiles.php:728
-msgid "Religious views"
-msgstr "Religieuze overtuigingen"
+#: ../../Zotlabs/Module/Webpages.php:334
+msgid "No webpage elements detected."
+msgstr "Geen webpagina-elementen gedecteerd"
-#: ../../Zotlabs/Module/Profiles.php:729
-msgid "Keywords used in directory listings"
-msgstr "Trefwoorden voor in de kanalengids"
+#: ../../Zotlabs/Module/Webpages.php:409
+msgid "Import complete."
+msgstr "Importeren voltooid."
-#: ../../Zotlabs/Module/Profiles.php:729
-msgid "Example: fishing photography software"
-msgstr "Voorbeeld: muziek, fotografie, software"
+#: ../../Zotlabs/Module/Notifications.php:43 ../../include/nav.php:208
+msgid "Mark all system notifications seen"
+msgstr "Markeer alle systeemnotificaties als bekeken"
-#: ../../Zotlabs/Module/Profiles.php:732
-msgid "Musical interests"
-msgstr "Muzikale interesses"
+#: ../../Zotlabs/Module/Poke.php:168 ../../Zotlabs/Lib/Apps.php:235
+#: ../../include/conversation.php:942 ../../include/conversation.php:1109
+msgid "Poke"
+msgstr "Aanstoten"
-#: ../../Zotlabs/Module/Profiles.php:733
-msgid "Books, literature"
-msgstr "Boeken/literatuur"
+#: ../../Zotlabs/Module/Poke.php:169
+msgid "Poke somebody"
+msgstr "Iemand aanstoten"
-#: ../../Zotlabs/Module/Profiles.php:734
-msgid "Television"
-msgstr "Televisie"
+#: ../../Zotlabs/Module/Poke.php:172
+msgid "Poke/Prod"
+msgstr "Aanstoten/porren"
-#: ../../Zotlabs/Module/Profiles.php:735
-msgid "Film/Dance/Culture/Entertainment"
-msgstr "Film/dans/cultuur/entertainment"
+#: ../../Zotlabs/Module/Poke.php:173
+msgid "Poke, prod or do other things to somebody"
+msgstr "Iemand bijvoorbeeld aanstoten of poren"
-#: ../../Zotlabs/Module/Profiles.php:736
-msgid "Hobbies/Interests"
-msgstr "Hobby's/interesses"
+#: ../../Zotlabs/Module/Poke.php:180
+msgid "Recipient"
+msgstr "Ontvanger"
-#: ../../Zotlabs/Module/Profiles.php:737
-msgid "Love/Romance"
-msgstr "Liefde/romantiek"
+#: ../../Zotlabs/Module/Poke.php:181
+msgid "Choose what you wish to do to recipient"
+msgstr "Kies wat je met de ontvanger wil doen"
-#: ../../Zotlabs/Module/Profiles.php:739
-msgid "School/Education"
-msgstr "School/opleiding"
+#: ../../Zotlabs/Module/Poke.php:184 ../../Zotlabs/Module/Poke.php:185
+msgid "Make this post private"
+msgstr "Maak dit bericht privé"
-#: ../../Zotlabs/Module/Profiles.php:740
-msgid "Contact information and social networks"
-msgstr "Contactinformatie en sociale netwerken"
+#: ../../Zotlabs/Module/Profperm.php:34 ../../Zotlabs/Module/Profperm.php:63
+msgid "Invalid profile identifier."
+msgstr "Ongeldige profiel-identificator"
-#: ../../Zotlabs/Module/Profiles.php:741
-msgid "My other channels"
-msgstr "Mijn andere kanalen"
+#: ../../Zotlabs/Module/Profperm.php:111
+msgid "Profile Visibility Editor"
+msgstr "Zichtbaarheid profiel "
-#: ../../Zotlabs/Module/Profiles.php:761 ../../include/channel.php:979
-msgid "Profile Image"
-msgstr "Profielfoto"
+#: ../../Zotlabs/Module/Profperm.php:113 ../../include/channel.php:1367
+msgid "Profile"
+msgstr "Profiel"
-#: ../../Zotlabs/Module/Profiles.php:771 ../../include/channel.php:961
-#: ../../include/nav.php:91
-msgid "Edit Profiles"
-msgstr "Bewerk profielen"
+#: ../../Zotlabs/Module/Profperm.php:115
+msgid "Click on a contact to add or remove."
+msgstr "Klik op een connectie om deze toe te voegen of te verwijderen"
-#: ../../Zotlabs/Module/Oexchange.php:27
-msgid "Unable to find your hub."
-msgstr "Niet in staat om je hub te vinden"
+#: ../../Zotlabs/Module/Profperm.php:124
+msgid "Visible To"
+msgstr "Zichtbaar voor"
-#: ../../Zotlabs/Module/Oexchange.php:41
-msgid "Post successful."
-msgstr "Verzenden bericht geslaagd."
+#: ../../Zotlabs/Module/Hcard.php:35 ../../Zotlabs/Module/Channel.php:47
+#: ../../Zotlabs/Module/Profile.php:43
+msgid "Posts and comments"
+msgstr "Berichten en reacties"
+
+#: ../../Zotlabs/Module/Hcard.php:42 ../../Zotlabs/Module/Channel.php:54
+#: ../../Zotlabs/Module/Profile.php:50
+msgid "Only posts"
+msgstr "Alleen berichten"
+
+#: ../../Zotlabs/Module/Item.php:184
+msgid "Unable to locate original post."
+msgstr "Niet in staat om de originele locatie van het bericht te vinden. "
+
+#: ../../Zotlabs/Module/Item.php:450
+msgid "Empty post discarded."
+msgstr "Leeg bericht geannuleerd"
+
+#: ../../Zotlabs/Module/Item.php:492
+msgid "Executable content type not permitted to this channel."
+msgstr "Uitvoerbare bestanden zijn niet toegestaan op dit kanaal."
+
+#: ../../Zotlabs/Module/Item.php:842
+msgid "Duplicate post suppressed."
+msgstr "Dubbel bericht tegengehouden."
+
+#: ../../Zotlabs/Module/Item.php:984
+msgid "System error. Post not saved."
+msgstr "Systeemfout. Bericht niet opgeslagen."
+
+#: ../../Zotlabs/Module/Item.php:1114
+msgid "Unable to obtain post information from database."
+msgstr "Niet in staat om informatie over dit bericht uit de database te verkrijgen."
+
+#: ../../Zotlabs/Module/Item.php:1121
+#, php-format
+msgid "You have reached your limit of %1$.0f top level posts."
+msgstr "Je hebt jouw limiet van %1$.0f berichten bereikt."
+
+#: ../../Zotlabs/Module/Item.php:1128
+#, php-format
+msgid "You have reached your limit of %1$.0f webpages."
+msgstr "Je hebt jouw limiet van %1$.0f webpagina's bereikt."
#: ../../Zotlabs/Module/Pconfig.php:26 ../../Zotlabs/Module/Pconfig.php:59
msgid "This setting requires special processing and editing has been blocked."
@@ -4951,7 +4788,31 @@ msgid ""
" to correctly use this feature."
msgstr "Waarschuwing: het veranderen van sommige instellingen kunnen jouw kanaal onklaar maken. Verlaat deze pagina, tenzij je weet waar je mee bezig bent en voldoende kennis bezit over hoe je deze functies moet gebruiken. "
-#: ../../Zotlabs/Module/Blocks.php:154 ../../include/text.php:2270
+#: ../../Zotlabs/Module/Search.php:224
+#, php-format
+msgid "Items tagged with: %s"
+msgstr "Items getagd met %s"
+
+#: ../../Zotlabs/Module/Search.php:226
+#, php-format
+msgid "Search results for: %s"
+msgstr "Zoekresultaten voor %s"
+
+#: ../../Zotlabs/Module/Lockview.php:75
+msgid "Remote privacy information not available."
+msgstr "Privacy-informatie op afstand niet beschikbaar."
+
+#: ../../Zotlabs/Module/Lockview.php:96
+msgid "Visible to:"
+msgstr "Zichtbaar voor:"
+
+#: ../../Zotlabs/Module/Lockview.php:117 ../../Zotlabs/Module/Lockview.php:153
+#: ../../Zotlabs/Module/Acl.php:117 ../../include/acl_selectors.php:183
+msgctxt "acl"
+msgid "Profile"
+msgstr "Profiel"
+
+#: ../../Zotlabs/Module/Blocks.php:154 ../../include/text.php:2288
msgid "Blocks"
msgstr "Blokken"
@@ -4959,13 +4820,13 @@ msgstr "Blokken"
msgid "Block Title"
msgstr "Bloktitel"
-#: ../../Zotlabs/Module/Layouts.php:183 ../../include/text.php:2272
+#: ../../Zotlabs/Module/Layouts.php:183 ../../include/text.php:2290
msgid "Layouts"
msgstr "Lay-outs"
-#: ../../Zotlabs/Module/Layouts.php:185 ../../Zotlabs/Lib/Apps.php:227
-#: ../../include/nav.php:162 ../../include/help.php:53
-#: ../../include/help.php:59
+#: ../../Zotlabs/Module/Layouts.php:185 ../../Zotlabs/Lib/Apps.php:232
+#: ../../include/help.php:55 ../../include/help.php:61
+#: ../../include/nav.php:174 ../../include/nav.php:288
msgid "Help"
msgstr "Hulp"
@@ -4998,6 +4859,27 @@ msgstr "Beoordeling (deze informatie is openbaar)"
msgid "Optionally explain your rating (this information is public)"
msgstr "Verklaar jouw beoordeling (niet verplicht, deze informatie is openbaar)"
+#: ../../Zotlabs/Module/Profile_photo.php:194
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:298
+msgid ""
+"Shift-reload the page or clear browser cache if the new photo does not "
+"display immediately."
+msgstr "Vernieuw de pagina met shift+R of shift+F5, of leeg je browserbuffer, wanneer de nieuwe foto niet meteen wordt weergegeven."
+
+#: ../../Zotlabs/Module/Profile_photo.php:420
+msgid "Use Photo for Profile"
+msgstr "Als profielfoto gebruiken"
+
+#: ../../Zotlabs/Module/Profile_photo.php:420
+msgid "Upload Profile Photo"
+msgstr "Profielfoto uploaden"
+
+#: ../../Zotlabs/Module/Profile_photo.php:421
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:182
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:194
+msgid "Use"
+msgstr "Gebruiken"
+
#: ../../Zotlabs/Module/Like.php:19
msgid "Like/Dislike"
msgstr "Leuk/niet leuk"
@@ -5037,22 +4919,16 @@ msgstr "Vorige actie omgedraaid"
#: ../../Zotlabs/Module/Tagger.php:47
#: ../../extend/addon/addon/diaspora/inbound.php:1794
#: ../../extend/addon/addon/redphotos/redphotohelper.php:74
-#: ../../include/text.php:1940 ../../include/conversation.php:120
+#: ../../include/conversation.php:120 ../../include/text.php:1958
msgid "photo"
msgstr "foto"
#: ../../Zotlabs/Module/Like.php:370 ../../Zotlabs/Module/Subthread.php:87
#: ../../extend/addon/addon/diaspora/inbound.php:1794
-#: ../../include/text.php:1946 ../../include/conversation.php:148
+#: ../../include/conversation.php:148 ../../include/text.php:1964
msgid "status"
msgstr "bericht"
-#: ../../Zotlabs/Module/Like.php:372 ../../Zotlabs/Module/Tagger.php:51
-#: ../../Zotlabs/Module/Events.php:256 ../../include/text.php:1943
-#: ../../include/event.php:961 ../../include/conversation.php:123
-msgid "event"
-msgstr "gebeurtenis"
-
#: ../../Zotlabs/Module/Like.php:419
#: ../../extend/addon/addon/diaspora/inbound.php:1823
#: ../../include/conversation.php:164
@@ -5103,37 +4979,6 @@ msgstr "Actie voltooid"
msgid "Thank you."
msgstr "Bedankt"
-#: ../../Zotlabs/Module/Profile_photo.php:186
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:293
-msgid ""
-"Shift-reload the page or clear browser cache if the new photo does not "
-"display immediately."
-msgstr "Vernieuw de pagina met shift+R of shift+F5, of leeg je browserbuffer, wanneer de nieuwe foto niet meteen wordt weergegeven."
-
-#: ../../Zotlabs/Module/Profile_photo.php:409
-msgid "Use Photo for Profile"
-msgstr "Als profielfoto gebruiken"
-
-#: ../../Zotlabs/Module/Profile_photo.php:409
-msgid "Upload Profile Photo"
-msgstr "Profielfoto uploaden"
-
-#: ../../Zotlabs/Module/Profile_photo.php:410
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:181
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:193
-msgid "Use"
-msgstr "Gebruiken"
-
-#: ../../Zotlabs/Module/Search.php:223
-#, php-format
-msgid "Items tagged with: %s"
-msgstr "Items getagd met %s"
-
-#: ../../Zotlabs/Module/Search.php:225
-#, php-format
-msgid "Search results for: %s"
-msgstr "Zoekresultaten voor %s"
-
#: ../../Zotlabs/Module/Common.php:14
msgid "No channel."
msgstr "Geen kanaal."
@@ -5146,81 +4991,29 @@ msgstr "Veel voorkomende connecties"
msgid "No connections in common."
msgstr "Geen gemeenschappelijke connecties."
-#: ../../Zotlabs/Module/Api.php:72 ../../Zotlabs/Module/Api.php:93
-msgid "Authorize application connection"
-msgstr "Geef toestemming voor applicatiekoppeling"
-
-#: ../../Zotlabs/Module/Api.php:73
-msgid "Return to your app and insert this Security Code:"
-msgstr "Ga terug naar je app en voeg deze beveiligingscode in:"
-
-#: ../../Zotlabs/Module/Api.php:83
-msgid "Please login to continue."
-msgstr "Inloggen om verder te kunnen gaan."
-
-#: ../../Zotlabs/Module/Api.php:95
-msgid ""
-"Do you want to authorize this application to access your posts and contacts,"
-" and/or create new posts for you?"
-msgstr "Wil je deze applicatie toestemming geven om jouw berichten en connecties te zien, en/of nieuwe berichten voor jou te plaatsen?"
-
-#: ../../Zotlabs/Module/Ping.php:254
-msgid "sent you a private message"
-msgstr "stuurde jou een privébericht"
-
-#: ../../Zotlabs/Module/Ping.php:302
-msgid "added your channel"
-msgstr "voegde jouw kanaal toe"
-
-#: ../../Zotlabs/Module/Ping.php:312
-msgid "g A l F d"
-msgstr "G:i, l d F"
-
-#: ../../Zotlabs/Module/Ping.php:330
-msgid "[today]"
-msgstr "[vandaag]"
-
-#: ../../Zotlabs/Module/Ping.php:339
-msgid "posted an event"
-msgstr "plaatste een gebeurtenis"
-
-#: ../../Zotlabs/Module/Siteinfo.php:20
-msgid "About this site"
-msgstr "Over deze hub"
-
-#: ../../Zotlabs/Module/Siteinfo.php:21
-msgid "Site Name"
-msgstr "Hubnaam"
-
-#: ../../Zotlabs/Module/Siteinfo.php:25 ../../include/network.php:1962
-msgid "Administrator"
-msgstr "Beheerder"
-
-#: ../../Zotlabs/Module/Siteinfo.php:28
-msgid "Software and Project information"
-msgstr "Software- en projectinformatie"
-
-#: ../../Zotlabs/Module/Siteinfo.php:29
-msgid "This site is powered by $Projectname"
-msgstr "Dit is een $Projectname-hub"
+#: ../../Zotlabs/Module/Chanview.php:134
+msgid "toggle full screen mode"
+msgstr "Volledig scherm"
-#: ../../Zotlabs/Module/Siteinfo.php:30
-msgid ""
-"Federated and decentralised networking and identity services provided by Zot"
-msgstr "Federatieve en gedecentraliseerde netwerk- en identiteitsdiensten, mogelijk gemaakt door Zot"
+#: ../../Zotlabs/Module/Subthread.php:118
+#, php-format
+msgid "%1$s is following %2$s's %3$s"
+msgstr "%1$s volgt het %3$s van %2$s"
-#: ../../Zotlabs/Module/Siteinfo.php:32
+#: ../../Zotlabs/Module/Subthread.php:120
#, php-format
-msgid "Version %s"
-msgstr "Versie %s"
+msgid "%1$s stopped following %2$s's %3$s"
+msgstr "%1$s volgt het %3$s van %2$s niet meer"
-#: ../../Zotlabs/Module/Siteinfo.php:33
-msgid "Project homepage"
-msgstr "Projectwebsite"
+#: ../../Zotlabs/Module/Channel.php:32 ../../Zotlabs/Module/Chat.php:25
+#: ../../extend/addon/addon/chess/chess.php:403
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:26
+msgid "You must be logged in to see this page."
+msgstr "Je moet zijn ingelogd om deze pagina te kunnen bekijken."
-#: ../../Zotlabs/Module/Siteinfo.php:34
-msgid "Developer homepage"
-msgstr "Ontwikkelaarswebsite"
+#: ../../Zotlabs/Module/Channel.php:112
+msgid "Insufficient permissions. Request redirected to profile page."
+msgstr "Onvoldoende permissies. Doorgestuurd naar profielpagina."
#: ../../Zotlabs/Module/Lostpass.php:19
msgid "No valid account found."
@@ -5246,7 +5039,7 @@ msgid ""
"Password reset failed."
msgstr "Het verzoek kon niet worden geverifieerd. (Mogelijk heb je al eerder een verzoek ingediend.) Opnieuw instellen van wachtwoord is mislukt."
-#: ../../Zotlabs/Module/Lostpass.php:91 ../../boot.php:1728
+#: ../../Zotlabs/Module/Lostpass.php:91 ../../boot.php:1757
msgid "Password Reset"
msgstr "Wachtwoord vergeten?"
@@ -5311,25 +5104,23 @@ msgstr "URL van bladwijzer"
msgid "Or enter new bookmark folder name"
msgstr "Of geef de naam op van een nieuwe bladwijzermap"
-#: ../../Zotlabs/Module/Dirsearch.php:33
-msgid "This directory server requires an access token"
-msgstr "Deze kanalengidshub (directoryserver) heeft een toegangs-token nodig"
-
-#: ../../Zotlabs/Module/Rmagic.php:35
-msgid "Authentication failed."
-msgstr "Authenticatie mislukt."
+#: ../../Zotlabs/Module/Follow.php:31
+msgid "Channel added."
+msgstr "Kanaal toegevoegd."
-#: ../../Zotlabs/Module/Rmagic.php:75
-msgid "Remote Authentication"
-msgstr "Authenticatie op afstand"
+#: ../../Zotlabs/Module/Mood.php:67 ../../include/conversation.php:260
+#, php-format
+msgctxt "mood"
+msgid "%1$s is %2$s"
+msgstr "%1$s is %2$s"
-#: ../../Zotlabs/Module/Rmagic.php:76
-msgid "Enter your channel address (e.g. channel@example.com)"
-msgstr "Vul jouw kanaaladres in (bijv. channel@example.com)"
+#: ../../Zotlabs/Module/Mood.php:135 ../../Zotlabs/Lib/Apps.php:234
+msgid "Mood"
+msgstr "Stemming"
-#: ../../Zotlabs/Module/Rmagic.php:77
-msgid "Authenticate"
-msgstr "Authenticeren"
+#: ../../Zotlabs/Module/Mood.php:136
+msgid "Set your current mood and tell your friends"
+msgstr "Noteer je huidige stemming en toon het aan je connecties"
#: ../../Zotlabs/Module/Regmod.php:15
msgid "Please login."
@@ -5387,7 +5178,7 @@ msgstr "Account verwijderen"
msgid "Layout updated."
msgstr "Lay-out bijgewerkt."
-#: ../../Zotlabs/Module/Pdledit.php:34 ../../Zotlabs/Module/Chat.php:218
+#: ../../Zotlabs/Module/Pdledit.php:34 ../../Zotlabs/Module/Chat.php:216
msgid "Feature disabled."
msgstr "Functie uitgeschakeld."
@@ -5407,230 +5198,146 @@ msgstr "Modulenaam:"
msgid "Layout Help"
msgstr "Lay-out-hulp"
-#: ../../Zotlabs/Module/Uexport.php:55 ../../Zotlabs/Module/Uexport.php:56
-msgid "Export Channel"
-msgstr "Kanaal exporteren"
-
-#: ../../Zotlabs/Module/Uexport.php:57
-msgid ""
-"Export your basic channel information to a file. This acts as a backup of "
-"your connections, permissions, profile and basic data, which can be used to "
-"import your data to a new server hub, but does not contain your content."
-msgstr "Exporteer de basisinformatie van jouw kanaal naar een bestand. Dit fungeert als een back-up van jouw connecties, permissies, profiel en basisgegevens, die gebruikt kan worden om op een nieuwe hub jouw gegevens te importeren. Deze back-up bevat echter niet de inhoud van jouw kanaal."
-
-#: ../../Zotlabs/Module/Uexport.php:58
-msgid "Export Content"
-msgstr "Inhoud exporteren"
-
-#: ../../Zotlabs/Module/Uexport.php:59
-msgid ""
-"Export your channel information and recent content to a JSON backup that can"
-" be restored or imported to another server hub. This backs up all of your "
-"connections, permissions, profile data and several months of posts. This "
-"file may be VERY large. Please be patient - it may take several minutes for"
-" this download to begin."
-msgstr "Exporteer informatie en recente inhoud van jouw kanaal naar een JSON-back-up, wat kan worden gebruikt om jouw kanaal te herstellen of te importeren op een andere hub. Dit slaat al jouw connecties, permissies, profielgegevens en enkele maanden aan inhoud van jouw kanaal op. Dit bestand kan ZEER groot worden. Wees geduldig - het kan enkele minuten duren voordat de download begint."
-
-#: ../../Zotlabs/Module/Uexport.php:60
-msgid "Export your posts from a given year."
-msgstr "Exporteer jouw berichten uit een bepaald jaar."
-
-#: ../../Zotlabs/Module/Uexport.php:62
-msgid ""
-"You may also export your posts and conversations for a particular year or "
-"month. Adjust the date in your browser location bar to select other dates. "
-"If the export fails (possibly due to memory exhaustion on your server hub), "
-"please try again selecting a more limited date range."
-msgstr "Je kan ook berichten en conversaties uit een bepaald jaar of van een bepaalde maand exporteren. Verander de datum in de adresbalk van jouw webbrowser om andere jaren en maanden te selecteren. Wanneer het exporteren mislukt (waarschijnlijk door een gebrek aan beschikbaar servergeheugen), probeer het dan nogmaals met een beperkter tijdvak."
-
-#: ../../Zotlabs/Module/Uexport.php:63
+#: ../../Zotlabs/Module/Directory.php:246
#, php-format
-msgid ""
-"To select all posts for a given year, such as this year, visit <a "
-"href=\"%1$s\">%2$s</a>"
-msgstr "Bezoek <a href=\"%1$s\">%2$s</a> om alle berichten van bijvoorbeeld dit jaar te selecteren. "
+msgid "%d rating"
+msgid_plural "%d ratings"
+msgstr[0] "%d beoordeling"
+msgstr[1] "%d beoordelingen"
-#: ../../Zotlabs/Module/Uexport.php:64
-#, php-format
-msgid ""
-"To select all posts for a given month, such as January of this year, visit "
-"<a href=\"%1$s\">%2$s</a>"
-msgstr "Bezoek <a href=\"%1$s\">%2$s</a> om alle berichten van bijvoorbeeld januari dit jaar te selecteren."
+#: ../../Zotlabs/Module/Directory.php:257
+msgid "Gender: "
+msgstr "Geslacht:"
-#: ../../Zotlabs/Module/Uexport.php:65
-#, php-format
-msgid ""
-"These content files may be imported or restored by visiting <a "
-"href=\"%1$s\">%2$s</a> on any site containing your channel. For best results"
-" please import or restore these in date order (oldest first)."
-msgstr "Deze back-up-bestanden kunnen geïmporteerd of hersteld worden door op jouw hub en met jouw kanaal <a href=\"%1$s\">%2$s</a> te bezoeken. Voor het beste resultaat kan je de bestanden in chronologische volgorde importeren of herstellen."
+#: ../../Zotlabs/Module/Directory.php:259
+msgid "Status: "
+msgstr "Status: "
-#: ../../Zotlabs/Module/Cal.php:69
-msgid "Permissions denied."
-msgstr "Permissies niet toegestaan"
+#: ../../Zotlabs/Module/Directory.php:261
+msgid "Homepage: "
+msgstr "Homepage: "
-#: ../../Zotlabs/Module/Cal.php:263 ../../Zotlabs/Module/Events.php:596
-msgid "l, F j"
-msgstr "l j F"
+#: ../../Zotlabs/Module/Directory.php:310 ../../include/channel.php:1298
+msgid "Age:"
+msgstr "Leeftijd:"
-#: ../../Zotlabs/Module/Cal.php:312 ../../Zotlabs/Module/Events.php:651
-#: ../../include/text.php:1748
-msgid "Link to Source"
-msgstr "Originele locatie"
+#: ../../Zotlabs/Module/Directory.php:315 ../../include/event.php:52
+#: ../../include/event.php:84 ../../include/markdown.php:562
+#: ../../include/channel.php:1134
+msgid "Location:"
+msgstr "Plaats:"
-#: ../../Zotlabs/Module/Cal.php:335 ../../Zotlabs/Module/Events.php:679
-msgid "Edit Event"
-msgstr "Gebeurtenis bewerken"
+#: ../../Zotlabs/Module/Directory.php:321
+msgid "Description:"
+msgstr "Omschrijving:"
-#: ../../Zotlabs/Module/Cal.php:335 ../../Zotlabs/Module/Events.php:679
-msgid "Create Event"
-msgstr "Gebeurtenis aanmaken"
+#: ../../Zotlabs/Module/Directory.php:326 ../../include/channel.php:1314
+msgid "Hometown:"
+msgstr "Oorspronkelijk uit:"
-#: ../../Zotlabs/Module/Cal.php:338 ../../Zotlabs/Module/Events.php:682
-msgid "Export"
-msgstr "Exporteren"
+#: ../../Zotlabs/Module/Directory.php:328 ../../include/channel.php:1322
+msgid "About:"
+msgstr "Over:"
-#: ../../Zotlabs/Module/Cal.php:341 ../../include/text.php:2294
-msgid "Import"
-msgstr "Importeren"
+#: ../../Zotlabs/Module/Directory.php:329 ../../Zotlabs/Module/Suggest.php:56
+#: ../../include/widgets.php:134 ../../include/widgets.php:171
+#: ../../include/connections.php:110 ../../include/conversation.php:938
+#: ../../include/conversation.php:1069 ../../include/channel.php:1119
+msgid "Connect"
+msgstr "Verbinden"
-#: ../../Zotlabs/Module/Cal.php:345 ../../Zotlabs/Module/Events.php:691
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:848
-msgid "Today"
-msgstr "Vandaag"
+#: ../../Zotlabs/Module/Directory.php:330
+msgid "Public Forum:"
+msgstr "Openbaar forum:"
-#: ../../Zotlabs/Module/Admin.php:94
-msgid "# Accounts"
-msgstr "# accounts"
+#: ../../Zotlabs/Module/Directory.php:333
+msgid "Keywords: "
+msgstr "Trefwoorden: "
-#: ../../Zotlabs/Module/Admin.php:95
-msgid "# blocked accounts"
-msgstr "# geblokkeerde accounts"
+#: ../../Zotlabs/Module/Directory.php:336
+msgid "Don't suggest"
+msgstr "Niet voorstellen"
-#: ../../Zotlabs/Module/Admin.php:96
-msgid "# expired accounts"
-msgstr "# verlopen accounts"
+#: ../../Zotlabs/Module/Directory.php:338
+msgid "Common connections:"
+msgstr "Gemeenschappelijke connecties:"
-#: ../../Zotlabs/Module/Admin.php:97
-msgid "# expiring accounts"
-msgstr "# accounts die nog moeten verlopen"
+#: ../../Zotlabs/Module/Directory.php:387
+msgid "Global Directory"
+msgstr "Volledige kanalengids"
-#: ../../Zotlabs/Module/Admin.php:108
-msgid "# Channels"
-msgstr "# Kanalen"
+#: ../../Zotlabs/Module/Directory.php:387
+msgid "Local Directory"
+msgstr "Lokale kanalengids"
-#: ../../Zotlabs/Module/Admin.php:109
-msgid "# primary"
-msgstr "# primair"
+#: ../../Zotlabs/Module/Directory.php:393
+msgid "Finding:"
+msgstr "Gezocht naar:"
-#: ../../Zotlabs/Module/Admin.php:110
-msgid "# clones"
-msgstr "# klonen"
+#: ../../Zotlabs/Module/Directory.php:396 ../../Zotlabs/Module/Suggest.php:64
+#: ../../include/contact_widgets.php:24
+msgid "Channel Suggestions"
+msgstr "Voorgestelde kanalen"
-#: ../../Zotlabs/Module/Admin.php:116
-msgid "Message queues"
-msgstr "Berichtenwachtrij"
+#: ../../Zotlabs/Module/Directory.php:398
+msgid "next page"
+msgstr "volgende pagina"
-#: ../../Zotlabs/Module/Admin.php:133
-msgid "Your software should be updated"
-msgstr "Jouw software moet worden bijgewerkt "
+#: ../../Zotlabs/Module/Directory.php:398
+msgid "previous page"
+msgstr "vorige pagina"
-#: ../../Zotlabs/Module/Admin.php:138
-msgid "Summary"
-msgstr "Samenvatting"
+#: ../../Zotlabs/Module/Directory.php:399
+msgid "Sort options"
+msgstr "Sorteeropties"
-#: ../../Zotlabs/Module/Admin.php:141
-msgid "Registered accounts"
-msgstr "Geregistreerde accounts"
+#: ../../Zotlabs/Module/Directory.php:400
+msgid "Alphabetic"
+msgstr "Alfabetisch"
-#: ../../Zotlabs/Module/Admin.php:142
-msgid "Pending registrations"
-msgstr "Accounts die op goedkeuring wachten"
+#: ../../Zotlabs/Module/Directory.php:401
+msgid "Reverse Alphabetic"
+msgstr "Omgekeerd alfabetisch"
-#: ../../Zotlabs/Module/Admin.php:143
-msgid "Registered channels"
-msgstr "Geregistreerde kanalen"
+#: ../../Zotlabs/Module/Directory.php:402
+msgid "Newest to Oldest"
+msgstr "Nieuw naar oud"
-#: ../../Zotlabs/Module/Admin.php:144
-msgid "Active plugins"
-msgstr "Ingeschakelde plugins"
+#: ../../Zotlabs/Module/Directory.php:403
+msgid "Oldest to Newest"
+msgstr "Oud naar nieuw"
-#: ../../Zotlabs/Module/Admin.php:145
-msgid "Version"
-msgstr "Versie"
+#: ../../Zotlabs/Module/Directory.php:420
+msgid "No entries (some entries may be hidden)."
+msgstr "Niets gevonden (sommige kanalen kunnen verborgen zijn)."
-#: ../../Zotlabs/Module/Admin.php:146
-msgid "Repository version (master)"
-msgstr "Versie repository (master)"
+#: ../../Zotlabs/Module/Profile.php:91
+msgid "vcard"
+msgstr "vcard"
-#: ../../Zotlabs/Module/Admin.php:147
-msgid "Repository version (dev)"
-msgstr "Versie repository (dev)"
+#: ../../Zotlabs/Module/Oexchange.php:27
+msgid "Unable to find your hub."
+msgstr "Niet in staat om je hub te vinden"
-#: ../../Zotlabs/Module/Lockview.php:75
-msgid "Remote privacy information not available."
-msgstr "Privacy-informatie op afstand niet beschikbaar."
+#: ../../Zotlabs/Module/Oexchange.php:41
+msgid "Post successful."
+msgstr "Verzenden bericht geslaagd."
-#: ../../Zotlabs/Module/Lockview.php:96
-msgid "Visible to:"
-msgstr "Zichtbaar voor:"
+#: ../../Zotlabs/Module/Viewsrc.php:46
+msgid "Source of Item"
+msgstr "Bron van item"
#: ../../Zotlabs/Module/Service_limits.php:23
msgid "No service class restrictions found."
msgstr "Geen abonnementsbeperkingen gevonden."
-#: ../../Zotlabs/Module/Webpages.php:52
-msgid "Import Webpage Elements"
-msgstr "Webpagina-elementen importeren"
-
-#: ../../Zotlabs/Module/Webpages.php:53
-msgid "Import selected"
-msgstr "Importbestand geselecteerd"
-
-#: ../../Zotlabs/Module/Webpages.php:76
-msgid "Export Webpage Elements"
-msgstr "Webpagina-elementen exporteren"
-
-#: ../../Zotlabs/Module/Webpages.php:77
-msgid "Export selected"
-msgstr "Selectie exporteren"
-
-#: ../../Zotlabs/Module/Webpages.php:237 ../../Zotlabs/Lib/Apps.php:220
-#: ../../include/nav.php:109 ../../include/conversation.php:1727
-msgid "Webpages"
-msgstr "Webpagina's"
-
-#: ../../Zotlabs/Module/Webpages.php:248 ../../include/page_widgets.php:44
-msgid "Actions"
-msgstr "Acties"
-
-#: ../../Zotlabs/Module/Webpages.php:249 ../../include/page_widgets.php:45
-msgid "Page Link"
-msgstr "Paginalink"
-
-#: ../../Zotlabs/Module/Webpages.php:250
-msgid "Page Title"
-msgstr "Paginatitel"
-
-#: ../../Zotlabs/Module/Webpages.php:280
-msgid "Invalid file type."
-msgstr "Ongeldig bestandsformaat"
-
-#: ../../Zotlabs/Module/Webpages.php:292
-msgid "Error opening zip file"
-msgstr "Fout tijdens openen zipbestand"
-
-#: ../../Zotlabs/Module/Webpages.php:303
-msgid "Invalid folder path."
-msgstr "Ongeldige maplocatie"
-
-#: ../../Zotlabs/Module/Webpages.php:330
-msgid "No webpage elements detected."
-msgstr "Geen webpagina-elementen gedecteerd"
+#: ../../Zotlabs/Module/Acl.php:344
+msgid "network"
+msgstr "netwerk"
-#: ../../Zotlabs/Module/Webpages.php:405
-msgid "Import complete."
-msgstr "Importeren voltooid."
+#: ../../Zotlabs/Module/Acl.php:354
+msgid "RSS"
+msgstr "RSS"
#: ../../Zotlabs/Module/Removeme.php:35
msgid ""
@@ -5657,7 +5364,7 @@ msgid ""
msgstr "Standaard wordt alleen het kanaal dat zich op deze hub bevindt uit het $Projectname-netwerk verwijderd"
#: ../../Zotlabs/Module/Removeme.php:64
-#: ../../Zotlabs/Module/Settings/Channel.php:549
+#: ../../Zotlabs/Module/Settings/Channel.php:575
msgid "Remove Channel"
msgstr "Kanaal verwijderen"
@@ -5677,127 +5384,19 @@ msgstr "Verwijder alle bestanden"
msgid "Remove this file"
msgstr "Verwijder dit bestand"
-#: ../../Zotlabs/Module/Wiki.php:34
-msgid "Not found"
-msgstr "Niet gevonden"
-
-#: ../../Zotlabs/Module/Wiki.php:55
-msgid "Invalid channel"
-msgstr "Onbekend kanaal"
-
-#: ../../Zotlabs/Module/Wiki.php:100
-msgid "Error retrieving wiki"
-msgstr "Fout tijdens ophalen wiki"
-
-#: ../../Zotlabs/Module/Wiki.php:107
-msgid "Error creating zip file export folder"
-msgstr "Fout tijdens aanmaken exportmap zipbestand"
-
-#: ../../Zotlabs/Module/Wiki.php:125
-msgid "Error downloading wiki: "
-msgstr "Fout tijdens downloaden wiki: "
-
-#: ../../Zotlabs/Module/Wiki.php:139 ../../include/nav.php:111
-#: ../../include/conversation.php:1737
-msgid "Wikis"
-msgstr "Wiki's"
-
-#: ../../Zotlabs/Module/Wiki.php:145
-msgid "Download"
-msgstr "Download"
-
-#: ../../Zotlabs/Module/Wiki.php:149
-msgid "Wiki name"
-msgstr "Naam wiki"
-
-#: ../../Zotlabs/Module/Wiki.php:150
-msgid "Content type"
-msgstr "Opmaaktype"
-
-#: ../../Zotlabs/Module/Wiki.php:159
-msgid "Create a status post for this wiki"
-msgstr "Plaats een bericht over deze wiki"
-
-#: ../../Zotlabs/Module/Wiki.php:178
-msgid "Wiki not found"
-msgstr "Wiki is niet gevonden"
-
-#: ../../Zotlabs/Module/Wiki.php:203
-msgid "Rename page"
-msgstr "Pagina hernoemen"
-
-#: ../../Zotlabs/Module/Wiki.php:207
-msgid "Error retrieving page content"
-msgstr "Fout tijdens ophalen inhoud pagina"
-
-#: ../../Zotlabs/Module/Wiki.php:236
-msgid "Revision Comparison"
-msgstr "Revisies vergelijken"
-
-#: ../../Zotlabs/Module/Wiki.php:237
-msgid "Revert"
-msgstr "Ongedaan maken"
-
-#: ../../Zotlabs/Module/Wiki.php:246
-msgid "Source"
-msgstr "Bron"
-
-#: ../../Zotlabs/Module/Wiki.php:254
-msgid "New page name"
-msgstr "Nieuwe paginanaam"
-
-#: ../../Zotlabs/Module/Wiki.php:259 ../../include/conversation.php:1151
-msgid "Embed image from photo albums"
-msgstr "Afbeelding uit een fotoalbum invoegen"
-
-#: ../../Zotlabs/Module/Wiki.php:260 ../../include/conversation.php:1245
-msgid "Embed an image from your albums"
-msgstr "Afbeelding uit jouw albums invoegen"
-
-#: ../../Zotlabs/Module/Wiki.php:262 ../../include/conversation.php:1247
-#: ../../include/conversation.php:1294
-msgid "OK"
-msgstr "OK"
-
-#: ../../Zotlabs/Module/Wiki.php:263 ../../include/conversation.php:1187
-msgid "Choose images to embed"
-msgstr "Kies afbeeldingen om in te voegen"
-
-#: ../../Zotlabs/Module/Wiki.php:264 ../../include/conversation.php:1188
-msgid "Choose an album"
-msgstr "Kies een album"
-
-#: ../../Zotlabs/Module/Wiki.php:265
-msgid "Choose a different album"
-msgstr "Kies een ander album"
-
-#: ../../Zotlabs/Module/Wiki.php:266 ../../include/conversation.php:1190
-msgid "Error getting album list"
-msgstr "Fout tijdens ophalen albumlijst"
-
-#: ../../Zotlabs/Module/Wiki.php:267 ../../include/conversation.php:1191
-msgid "Error getting photo link"
-msgstr "Fout tijdens ophalen fotolink"
-
-#: ../../Zotlabs/Module/Wiki.php:268 ../../include/conversation.php:1192
-msgid "Error getting album"
-msgstr "Fout tijdens ophalen album"
-
-#: ../../Zotlabs/Module/Wiki.php:332
-msgid "Error creating wiki. Invalid name."
-msgstr "Fout tijdens aanmaken wiki. Ongeldige naam."
-
-#: ../../Zotlabs/Module/Wiki.php:343
-msgid "Wiki created, but error creating Home page."
-msgstr "Wiki aangemaakt, maar fout tijdens aanmaken homepagina."
+#: ../../Zotlabs/Module/Tagger.php:55 ../../include/bbcode.php:274
+msgid "post"
+msgstr "bericht"
-#: ../../Zotlabs/Module/Wiki.php:348
-msgid "Error creating wiki"
-msgstr "Fout tijdens aanmaken wiki."
+#: ../../Zotlabs/Module/Tagger.php:57 ../../include/conversation.php:150
+#: ../../include/text.php:1966
+msgid "comment"
+msgstr "reactie"
-#: ../../Zotlabs/Module/Wiki.php:394
-msgid "New page created"
-msgstr "Nieuwe pagina aangemaakt"
+#: ../../Zotlabs/Module/Tagger.php:95
+#, php-format
+msgid "%1$s tagged %2$s's %3$s with %4$s"
+msgstr "%1$s heeft het %3$s van %2$s getagd met %4$s"
#: ../../Zotlabs/Module/Sources.php:37
msgid "Failed to create source. No channel selected."
@@ -5815,8 +5414,8 @@ msgstr "Bron aangemaakt."
msgid "*"
msgstr "*"
-#: ../../Zotlabs/Module/Sources.php:96 ../../include/features.php:195
-#: ../../include/widgets.php:672
+#: ../../Zotlabs/Module/Sources.php:96 ../../include/widgets.php:677
+#: ../../include/features.php:213
msgid "Channel Sources"
msgstr "Kanaalbronnen"
@@ -5855,7 +5454,7 @@ msgstr "De volgende categorieën aan berichten toevoegen die uit deze bron zijn
#: ../../Zotlabs/Module/Sources.php:112 ../../Zotlabs/Module/Sources.php:147
#: ../../Zotlabs/Module/Settings/Oauth.php:93
msgid "Optional"
-msgstr "Optioneel"
+msgstr "Niet verplicht"
#: ../../Zotlabs/Module/Sources.php:133 ../../Zotlabs/Module/Sources.php:161
msgid "Source not found."
@@ -5877,39 +5476,293 @@ msgstr "Bron verwijderd"
msgid "Unable to remove source."
msgstr "Verwijderen bron mislukt."
-#: ../../Zotlabs/Module/Subthread.php:118
-#, php-format
-msgid "%1$s is following %2$s's %3$s"
-msgstr "%1$s volgt het %3$s van %2$s"
-
-#: ../../Zotlabs/Module/Subthread.php:120
-#, php-format
-msgid "%1$s stopped following %2$s's %3$s"
-msgstr "%1$s volgt het %3$s van %2$s niet meer"
-
#: ../../Zotlabs/Module/Suggest.php:39
msgid ""
"No suggestions available. If this is a new site, please try again in 24 "
"hours."
msgstr "Geen voorgestelde kanalen gevonden. Wanneer dit een nieuwe hub is, probeer het dan over 24 uur weer."
-#: ../../Zotlabs/Module/Suggest.php:58 ../../include/widgets.php:149
+#: ../../Zotlabs/Module/Suggest.php:58 ../../include/widgets.php:136
msgid "Ignore/Hide"
msgstr "Negeren/Verbergen"
-#: ../../Zotlabs/Module/Tagger.php:55 ../../include/bbcode.php:274
-msgid "post"
-msgstr "bericht"
+#: ../../Zotlabs/Module/Profiles.php:24 ../../Zotlabs/Module/Profiles.php:184
+#: ../../Zotlabs/Module/Profiles.php:241 ../../Zotlabs/Module/Profiles.php:659
+#: ../../extend/addon/addon/friendica/dfrn_confirm.php:62
+msgid "Profile not found."
+msgstr "Profiel niet gevonden."
-#: ../../Zotlabs/Module/Tagger.php:57 ../../include/text.php:1948
-#: ../../include/conversation.php:150
-msgid "comment"
-msgstr "reactie"
+#: ../../Zotlabs/Module/Profiles.php:44
+msgid "Profile deleted."
+msgstr "Profiel verwijderd."
-#: ../../Zotlabs/Module/Tagger.php:100
-#, php-format
-msgid "%1$s tagged %2$s's %3$s with %4$s"
-msgstr "%1$s heeft het %3$s van %2$s getagd met %4$s"
+#: ../../Zotlabs/Module/Profiles.php:68 ../../Zotlabs/Module/Profiles.php:105
+msgid "Profile-"
+msgstr "Profiel-"
+
+#: ../../Zotlabs/Module/Profiles.php:90 ../../Zotlabs/Module/Profiles.php:127
+msgid "New profile created."
+msgstr "Nieuw profiel aangemaakt."
+
+#: ../../Zotlabs/Module/Profiles.php:111
+msgid "Profile unavailable to clone."
+msgstr "Profiel niet beschikbaar om te klonen"
+
+#: ../../Zotlabs/Module/Profiles.php:146
+msgid "Profile unavailable to export."
+msgstr "Geen profiel beschikbaar om te exporteren"
+
+#: ../../Zotlabs/Module/Profiles.php:252
+msgid "Profile Name is required."
+msgstr "Profielnaam is vereist"
+
+#: ../../Zotlabs/Module/Profiles.php:459
+msgid "Marital Status"
+msgstr "Huwelijke status"
+
+#: ../../Zotlabs/Module/Profiles.php:463
+msgid "Romantic Partner"
+msgstr "Romantische partner"
+
+#: ../../Zotlabs/Module/Profiles.php:467 ../../Zotlabs/Module/Profiles.php:775
+msgid "Likes"
+msgstr "Houdt van"
+
+#: ../../Zotlabs/Module/Profiles.php:471 ../../Zotlabs/Module/Profiles.php:776
+msgid "Dislikes"
+msgstr "Houdt niet van"
+
+#: ../../Zotlabs/Module/Profiles.php:475 ../../Zotlabs/Module/Profiles.php:783
+msgid "Work/Employment"
+msgstr "Werk/arbeid"
+
+#: ../../Zotlabs/Module/Profiles.php:478
+msgid "Religion"
+msgstr "Religie"
+
+#: ../../Zotlabs/Module/Profiles.php:482
+msgid "Political Views"
+msgstr "Politieke overtuigingen"
+
+#: ../../Zotlabs/Module/Profiles.php:486
+#: ../../extend/addon/addon/openid/MysqlProvider.php:74
+msgid "Gender"
+msgstr "Geslacht"
+
+#: ../../Zotlabs/Module/Profiles.php:490
+msgid "Sexual Preference"
+msgstr "Seksuele voorkeur"
+
+#: ../../Zotlabs/Module/Profiles.php:494
+msgid "Homepage"
+msgstr "Homepage"
+
+#: ../../Zotlabs/Module/Profiles.php:498
+msgid "Interests"
+msgstr "Interesses"
+
+#: ../../Zotlabs/Module/Profiles.php:594
+msgid "Profile updated."
+msgstr "Profiel bijgewerkt"
+
+#: ../../Zotlabs/Module/Profiles.php:678
+msgid "Hide your connections list from viewers of this profile"
+msgstr "Laat de lijst met connecties niet aan bezoekers van dit profiel zien."
+
+#: ../../Zotlabs/Module/Profiles.php:725
+msgid "Edit Profile Details"
+msgstr "Profiel bewerken"
+
+#: ../../Zotlabs/Module/Profiles.php:727
+msgid "View this profile"
+msgstr "Profiel weergeven"
+
+#: ../../Zotlabs/Module/Profiles.php:728 ../../Zotlabs/Module/Profiles.php:827
+#: ../../include/channel.php:1066
+msgid "Edit visibility"
+msgstr "Zichtbaarheid bewerken"
+
+#: ../../Zotlabs/Module/Profiles.php:729
+msgid "Profile Tools"
+msgstr "Hulpmiddelen"
+
+#: ../../Zotlabs/Module/Profiles.php:730
+msgid "Change cover photo"
+msgstr "Omslagfoto wijzigen"
+
+#: ../../Zotlabs/Module/Profiles.php:731 ../../include/channel.php:1037
+msgid "Change profile photo"
+msgstr "Profielfoto veranderen"
+
+#: ../../Zotlabs/Module/Profiles.php:732
+msgid "Create a new profile using these settings"
+msgstr "Een nieuw profiel aanmaken met dit profiel als basis"
+
+#: ../../Zotlabs/Module/Profiles.php:733
+msgid "Clone this profile"
+msgstr "Dit profiel klonen"
+
+#: ../../Zotlabs/Module/Profiles.php:734
+msgid "Delete this profile"
+msgstr "Dit profiel verwijderen"
+
+#: ../../Zotlabs/Module/Profiles.php:735
+msgid "Add profile things"
+msgstr "Dingen aan je profiel toevoegen"
+
+#: ../../Zotlabs/Module/Profiles.php:736 ../../include/conversation.php:1715
+msgid "Personal"
+msgstr "Persoonlijk"
+
+#: ../../Zotlabs/Module/Profiles.php:738
+msgid "Relation"
+msgstr "Relatie"
+
+#: ../../Zotlabs/Module/Profiles.php:739 ../../include/datetime.php:55
+msgid "Miscellaneous"
+msgstr "Diversen"
+
+#: ../../Zotlabs/Module/Profiles.php:741
+msgid "Import profile from file"
+msgstr "Profiel vanuit bestand importeren"
+
+#: ../../Zotlabs/Module/Profiles.php:742
+msgid "Export profile to file"
+msgstr "Profiel naar bestand exporteren"
+
+#: ../../Zotlabs/Module/Profiles.php:743
+msgid "Your gender"
+msgstr "Jouw geslacht"
+
+#: ../../Zotlabs/Module/Profiles.php:744
+msgid "Marital status"
+msgstr "Burgerlijke staat"
+
+#: ../../Zotlabs/Module/Profiles.php:745
+msgid "Sexual preference"
+msgstr "Seksuele voorkeur"
+
+#: ../../Zotlabs/Module/Profiles.php:748
+msgid "Profile name"
+msgstr "Profielnaam"
+
+#: ../../Zotlabs/Module/Profiles.php:750
+msgid "This is your default profile."
+msgstr "Dit is jouw standaardprofiel"
+
+#: ../../Zotlabs/Module/Profiles.php:752
+msgid "Your full name"
+msgstr "Jouw volledige naam"
+
+#: ../../Zotlabs/Module/Profiles.php:753
+msgid "Title/Description"
+msgstr "Titel/omschrijving"
+
+#: ../../Zotlabs/Module/Profiles.php:756
+msgid "Street address"
+msgstr "Straat en huisnummer"
+
+#: ../../Zotlabs/Module/Profiles.php:757
+msgid "Locality/City"
+msgstr "Woonplaats"
+
+#: ../../Zotlabs/Module/Profiles.php:758
+msgid "Region/State"
+msgstr "Provincie/gewest/deelstaat"
+
+#: ../../Zotlabs/Module/Profiles.php:759
+msgid "Postal/Zip code"
+msgstr "Postcode"
+
+#: ../../Zotlabs/Module/Profiles.php:765
+msgid "Who (if applicable)"
+msgstr "Wie (wanneer van toepassing)"
+
+#: ../../Zotlabs/Module/Profiles.php:765
+msgid "Examples: cathy123, Cathy Williams, cathy@example.com"
+msgstr "Voorbeelden: petra123, Petra Jansen, petra@voorbeeld.nl"
+
+#: ../../Zotlabs/Module/Profiles.php:766
+msgid "Since (date)"
+msgstr "Sinds (datum)"
+
+#: ../../Zotlabs/Module/Profiles.php:769
+msgid "Tell us about yourself"
+msgstr "Vertel ons iets over jezelf"
+
+#: ../../Zotlabs/Module/Profiles.php:770
+#: ../../extend/addon/addon/openid/MysqlProvider.php:68
+msgid "Homepage URL"
+msgstr "URL homepagina"
+
+#: ../../Zotlabs/Module/Profiles.php:771
+msgid "Hometown"
+msgstr "Oorspronkelijk uit"
+
+#: ../../Zotlabs/Module/Profiles.php:772
+msgid "Political views"
+msgstr "Politieke overtuigingen"
+
+#: ../../Zotlabs/Module/Profiles.php:773
+msgid "Religious views"
+msgstr "Religieuze overtuigingen"
+
+#: ../../Zotlabs/Module/Profiles.php:774
+msgid "Keywords used in directory listings"
+msgstr "Trefwoorden voor in de kanalengids"
+
+#: ../../Zotlabs/Module/Profiles.php:774
+msgid "Example: fishing photography software"
+msgstr "Voorbeeld: muziek, fotografie, software"
+
+#: ../../Zotlabs/Module/Profiles.php:777
+msgid "Musical interests"
+msgstr "Muzikale interesses"
+
+#: ../../Zotlabs/Module/Profiles.php:778
+msgid "Books, literature"
+msgstr "Boeken/literatuur"
+
+#: ../../Zotlabs/Module/Profiles.php:779
+msgid "Television"
+msgstr "Televisie"
+
+#: ../../Zotlabs/Module/Profiles.php:780
+msgid "Film/Dance/Culture/Entertainment"
+msgstr "Film/dans/cultuur/entertainment"
+
+#: ../../Zotlabs/Module/Profiles.php:781
+msgid "Hobbies/Interests"
+msgstr "Hobby's/interesses"
+
+#: ../../Zotlabs/Module/Profiles.php:782
+msgid "Love/Romance"
+msgstr "Liefde/romantiek"
+
+#: ../../Zotlabs/Module/Profiles.php:784
+msgid "School/Education"
+msgstr "School/opleiding"
+
+#: ../../Zotlabs/Module/Profiles.php:785
+msgid "Contact information and social networks"
+msgstr "Contactinformatie en sociale netwerken"
+
+#: ../../Zotlabs/Module/Profiles.php:786
+msgid "My other channels"
+msgstr "Mijn andere kanalen"
+
+#: ../../Zotlabs/Module/Profiles.php:788
+msgid "Communications"
+msgstr "Communicatie"
+
+#: ../../Zotlabs/Module/Profiles.php:823 ../../include/channel.php:1062
+msgid "Profile Image"
+msgstr "Profielfoto"
+
+#: ../../Zotlabs/Module/Profiles.php:833 ../../include/nav.php:105
+#: ../../include/channel.php:1044
+msgid "Edit Profiles"
+msgstr "Bewerk profielen"
#: ../../Zotlabs/Module/Settings/Features.php:45
msgid "Additional Features"
@@ -5988,49 +5841,6 @@ msgstr "Geen naam"
msgid "Remove authorization"
msgstr "Autorisatie verwijderen"
-#: ../../Zotlabs/Module/Settings/Tokens.php:31
-#, php-format
-msgid "This channel is limited to %d tokens"
-msgstr "Dit kanaal heeft een limiet van %d tokens"
-
-#: ../../Zotlabs/Module/Settings/Tokens.php:37
-msgid "Name and Password are required."
-msgstr "Naam en wachtwoord zijn vereist"
-
-#: ../../Zotlabs/Module/Settings/Tokens.php:77
-msgid "Token saved."
-msgstr "Token opgeslagen."
-
-#: ../../Zotlabs/Module/Settings/Tokens.php:113
-msgid ""
-"Use this form to create temporary access identifiers to share things with "
-"non-members. These identities may be used in Access Control Lists and "
-"visitors may login using these credentials to access private content."
-msgstr "Gebruik dit formulier om tijdelijke identiteiten aan te maken, waarmee je bepaalde informatie met niet-leden kan delen. Deze identiteiten kunnen onder Permissies (handmatige selectie) worden gebruikt. Gasten kunnen inloggen met onderstaande gegevens om zo toegang te krijgen tot privéinhoud."
-
-#: ../../Zotlabs/Module/Settings/Tokens.php:115
-msgid ""
-"You may also provide <em>dropbox</em> style access links to friends and "
-"associates by adding the Login Password to any specific site URL as shown. "
-"Examples:"
-msgstr "Je kan ook <em>dropbox</em>-achtige links aan mensen geven door bovenstaand wachtwoord op onderstaande manier aan een hub-URL toe te voegen. Voorbeelden:"
-
-#: ../../Zotlabs/Module/Settings/Tokens.php:150 ../../include/widgets.php:647
-msgid "Guest Access Tokens"
-msgstr "Gasttoegang"
-
-#: ../../Zotlabs/Module/Settings/Tokens.php:157
-msgid "Login Name"
-msgstr "Inlognaam"
-
-#: ../../Zotlabs/Module/Settings/Tokens.php:158
-msgid "Login Password"
-msgstr "Wachtwoord:"
-
-#: ../../Zotlabs/Module/Settings/Tokens.php:159
-msgid "Expires (yyyy-mm-dd)"
-msgstr "Geldig t/m (yyyy-mm-dd)"
-
#: ../../Zotlabs/Module/Settings/Account.php:20
msgid "Not valid email."
msgstr "Geen geldig e-mailadres."
@@ -6096,7 +5906,7 @@ msgid "Used to provide a member experience matched to your comfort level"
msgstr "Wordt gebruikt om je een gebruikerservaring te bieden die met jouw technisch niveau overeenkomt"
#: ../../Zotlabs/Module/Settings/Account.php:119
-#: ../../Zotlabs/Module/Settings/Channel.php:462
+#: ../../Zotlabs/Module/Settings/Channel.php:483
msgid "Email Address:"
msgstr "E-mailadres:"
@@ -6104,7 +5914,7 @@ msgstr "E-mailadres:"
msgid "Remove this account including all its channels"
msgstr "Dit account en al zijn kanalen verwijderen"
-#: ../../Zotlabs/Module/Settings/Channel.php:246
+#: ../../Zotlabs/Module/Settings/Channel.php:251
#: ../../extend/addon/addon/logrot/logrot.php:54
#: ../../extend/addon/addon/msgfooter/msgfooter.php:54
#: ../../extend/addon/addon/openstreetmap/openstreetmap.php:184
@@ -6115,489 +5925,570 @@ msgstr "Dit account en al zijn kanalen verwijderen"
msgid "Settings updated."
msgstr "Instellingen bijgewerkt."
-#: ../../Zotlabs/Module/Settings/Channel.php:307
+#: ../../Zotlabs/Module/Settings/Channel.php:312
msgid "Nobody except yourself"
msgstr "Niemand, behalve jezelf"
-#: ../../Zotlabs/Module/Settings/Channel.php:308
+#: ../../Zotlabs/Module/Settings/Channel.php:313
msgid "Only those you specifically allow"
msgstr "Alleen connecties met uitdrukkelijke toestemming"
-#: ../../Zotlabs/Module/Settings/Channel.php:309
+#: ../../Zotlabs/Module/Settings/Channel.php:314
msgid "Approved connections"
msgstr "Geaccepteerde connecties"
-#: ../../Zotlabs/Module/Settings/Channel.php:310
+#: ../../Zotlabs/Module/Settings/Channel.php:315
msgid "Any connections"
msgstr "Alle connecties"
-#: ../../Zotlabs/Module/Settings/Channel.php:311
+#: ../../Zotlabs/Module/Settings/Channel.php:316
msgid "Anybody on this website"
msgstr "Iedereen op deze hub"
-#: ../../Zotlabs/Module/Settings/Channel.php:312
+#: ../../Zotlabs/Module/Settings/Channel.php:317
msgid "Anybody in this network"
msgstr "Iedereen in dit netwerk"
-#: ../../Zotlabs/Module/Settings/Channel.php:313
+#: ../../Zotlabs/Module/Settings/Channel.php:318
msgid "Anybody authenticated"
msgstr "Geauthenticeerd"
-#: ../../Zotlabs/Module/Settings/Channel.php:314
+#: ../../Zotlabs/Module/Settings/Channel.php:319
msgid "Anybody on the internet"
msgstr "Iedereen op het internet"
-#: ../../Zotlabs/Module/Settings/Channel.php:390
+#: ../../Zotlabs/Module/Settings/Channel.php:395
msgid "Publish your default profile in the network directory"
msgstr "Publiceer je standaardprofiel in de kanalengids"
-#: ../../Zotlabs/Module/Settings/Channel.php:395
+#: ../../Zotlabs/Module/Settings/Channel.php:400
msgid "Allow us to suggest you as a potential friend to new members?"
msgstr "Sta ons toe om jouw kanaal als mogelijke connectie voor te stellen aan nieuwe kanalen"
-#: ../../Zotlabs/Module/Settings/Channel.php:404
+#: ../../Zotlabs/Module/Settings/Channel.php:409
msgid "Your channel address is"
msgstr "Jouw kanaaladres is"
-#: ../../Zotlabs/Module/Settings/Channel.php:407
+#: ../../Zotlabs/Module/Settings/Channel.php:412
msgid "Your files/photos are accessible via WebDAV at"
msgstr "Jouw bestanden/foto's zijn beschikbaar via WebDAV op"
-#: ../../Zotlabs/Module/Settings/Channel.php:453
+#: ../../Zotlabs/Module/Settings/Channel.php:474
msgid "Channel Settings"
msgstr "Kanaal-instellingen"
-#: ../../Zotlabs/Module/Settings/Channel.php:460
+#: ../../Zotlabs/Module/Settings/Channel.php:481
msgid "Basic Settings"
msgstr "Basis-instellingen"
-#: ../../Zotlabs/Module/Settings/Channel.php:461
-#: ../../include/channel.php:1172
+#: ../../Zotlabs/Module/Settings/Channel.php:482
+#: ../../include/channel.php:1255
msgid "Full Name:"
msgstr "Volledige naam:"
-#: ../../Zotlabs/Module/Settings/Channel.php:463
+#: ../../Zotlabs/Module/Settings/Channel.php:484
msgid "Your Timezone:"
msgstr "Jouw tijdzone:"
-#: ../../Zotlabs/Module/Settings/Channel.php:464
+#: ../../Zotlabs/Module/Settings/Channel.php:485
msgid "Default Post Location:"
msgstr "Standaardlocatie bericht:"
-#: ../../Zotlabs/Module/Settings/Channel.php:464
+#: ../../Zotlabs/Module/Settings/Channel.php:485
msgid "Geographical location to display on your posts"
msgstr "Geografische locatie die bij het bericht moet worden vermeld"
-#: ../../Zotlabs/Module/Settings/Channel.php:465
+#: ../../Zotlabs/Module/Settings/Channel.php:486
msgid "Use Browser Location:"
msgstr "Locatie van webbrowser gebruiken:"
-#: ../../Zotlabs/Module/Settings/Channel.php:467
+#: ../../Zotlabs/Module/Settings/Channel.php:488
msgid "Adult Content"
msgstr "Inhoud voor volwassenen"
-#: ../../Zotlabs/Module/Settings/Channel.php:467
+#: ../../Zotlabs/Module/Settings/Channel.php:488
msgid ""
"This channel frequently or regularly publishes adult content. (Please tag "
"any adult material and/or nudity with #NSFW)"
msgstr "Dit kanaal publiceert regelmatig of vaak materiaal dat alleen geschikt is voor volwassenen. (Gebruik de tag #NSFW in berichten met een seksueel getinte inhoud of ander voor minderjarigen ongeschikt materiaal)"
-#: ../../Zotlabs/Module/Settings/Channel.php:469
+#: ../../Zotlabs/Module/Settings/Channel.php:490
msgid "Security and Privacy Settings"
msgstr "Veiligheids- en privacy-instellingen"
-#: ../../Zotlabs/Module/Settings/Channel.php:472
+#: ../../Zotlabs/Module/Settings/Channel.php:493
msgid "Your permissions are already configured. Click to view/adjust"
msgstr "Jouw permissies zijn al ingesteld. Klik om ze te bekijken of aan te passen."
-#: ../../Zotlabs/Module/Settings/Channel.php:474
+#: ../../Zotlabs/Module/Settings/Channel.php:495
msgid "Hide my online presence"
msgstr "Verberg mijn aanwezigheid"
-#: ../../Zotlabs/Module/Settings/Channel.php:474
+#: ../../Zotlabs/Module/Settings/Channel.php:495
msgid "Prevents displaying in your profile that you are online"
msgstr "Voorkomt dat op je kanaalpagina te zien valt dat je momenteel op $Projectname aanwezig bent"
-#: ../../Zotlabs/Module/Settings/Channel.php:476
+#: ../../Zotlabs/Module/Settings/Channel.php:497
msgid "Simple Privacy Settings:"
msgstr "Eenvoudige privacy-instellingen:"
-#: ../../Zotlabs/Module/Settings/Channel.php:477
+#: ../../Zotlabs/Module/Settings/Channel.php:498
msgid ""
"Very Public - <em>extremely permissive (should be used with caution)</em>"
msgstr "Zeer openbaar <em>(kanaal staat volledig open - moet met grote zorgvuldigheid gebruikt worden)</em>"
-#: ../../Zotlabs/Module/Settings/Channel.php:478
+#: ../../Zotlabs/Module/Settings/Channel.php:499
msgid ""
"Typical - <em>default public, privacy when desired (similar to social "
"network permissions but with improved privacy)</em>"
msgstr "Normaal <em>(standaard openbaar, maar privacy wanneer noodzakelijk - vergelijkbaar met die van sociale netwerken, maar met verbeterde privacy)</em>"
-#: ../../Zotlabs/Module/Settings/Channel.php:479
+#: ../../Zotlabs/Module/Settings/Channel.php:500
msgid "Private - <em>default private, never open or public</em>"
msgstr "Privé <em>(standaard privé en nooit openbaar)</em>"
-#: ../../Zotlabs/Module/Settings/Channel.php:480
+#: ../../Zotlabs/Module/Settings/Channel.php:501
msgid "Blocked - <em>default blocked to/from everybody</em>"
msgstr "Geblokkeerd <em>(standaard geblokkeerd naar/van iedereen)</em>"
-#: ../../Zotlabs/Module/Settings/Channel.php:482
+#: ../../Zotlabs/Module/Settings/Channel.php:503
msgid "Allow others to tag your posts"
msgstr "Anderen toestaan om je berichten te taggen"
-#: ../../Zotlabs/Module/Settings/Channel.php:482
+#: ../../Zotlabs/Module/Settings/Channel.php:503
msgid ""
"Often used by the community to retro-actively flag inappropriate content"
msgstr "Vaak in groepen/forums gebruikt om met terugwerkende kracht ongepast materiaal te markeren"
-#: ../../Zotlabs/Module/Settings/Channel.php:484
+#: ../../Zotlabs/Module/Settings/Channel.php:505
msgid "Channel Permission Limits"
msgstr "Geavanceerde permissies"
-#: ../../Zotlabs/Module/Settings/Channel.php:486
+#: ../../Zotlabs/Module/Settings/Channel.php:507
msgid "Expire other channel content after this many days"
msgstr "Inhoud van andere kanalen na zoveel aantal dagen laten verlopen:"
-#: ../../Zotlabs/Module/Settings/Channel.php:486
+#: ../../Zotlabs/Module/Settings/Channel.php:507
msgid "0 or blank to use the website limit."
msgstr "0 of leeg om het standaard aantal dagen van deze hub te gebruiken."
-#: ../../Zotlabs/Module/Settings/Channel.php:486
+#: ../../Zotlabs/Module/Settings/Channel.php:507
#, php-format
msgid "This website expires after %d days."
msgstr "Deze hub laat de inhoud van andere kanalen na %d dagen verlopen."
-#: ../../Zotlabs/Module/Settings/Channel.php:486
+#: ../../Zotlabs/Module/Settings/Channel.php:507
msgid "This website does not expire imported content."
msgstr "Deze hub laat de inhoud van andere kanalen niet verlopen."
-#: ../../Zotlabs/Module/Settings/Channel.php:486
+#: ../../Zotlabs/Module/Settings/Channel.php:507
msgid "The website limit takes precedence if lower than your limit."
msgstr "Wanneer de standaard aantal dagen van deze hub lager ligt dan jouw aantal, dan heeft de limiet van deze hub voorrang."
-#: ../../Zotlabs/Module/Settings/Channel.php:487
+#: ../../Zotlabs/Module/Settings/Channel.php:508
msgid "Maximum Friend Requests/Day:"
msgstr "Maximum aantal connectieverzoeken per dag:"
-#: ../../Zotlabs/Module/Settings/Channel.php:487
+#: ../../Zotlabs/Module/Settings/Channel.php:508
msgid "May reduce spam activity"
msgstr "Kan eventuele spam verminderen"
-#: ../../Zotlabs/Module/Settings/Channel.php:488
+#: ../../Zotlabs/Module/Settings/Channel.php:509
msgid "Default Access Control List (ACL)"
msgstr "Standaard permissies voor nieuwe berichten"
-#: ../../Zotlabs/Module/Settings/Channel.php:490
+#: ../../Zotlabs/Module/Settings/Channel.php:511
msgid "Use my default audience setting for the type of object published"
msgstr "Gebruik mijn standaard privacy-instelling voor dit type publicatie"
-#: ../../Zotlabs/Module/Settings/Channel.php:497
+#: ../../Zotlabs/Module/Settings/Channel.php:518
msgid "Channel permissions category:"
msgstr "Kanaaltype en -permissies:"
-#: ../../Zotlabs/Module/Settings/Channel.php:503
+#: ../../Zotlabs/Module/Settings/Channel.php:519
+msgid "Default Permissions Group"
+msgstr "Standaard permissiegroep"
+
+#: ../../Zotlabs/Module/Settings/Channel.php:525
msgid "Maximum private messages per day from unknown people:"
msgstr "Maximum aantal privé-berichten per dag van onbekende personen:"
-#: ../../Zotlabs/Module/Settings/Channel.php:503
+#: ../../Zotlabs/Module/Settings/Channel.php:525
msgid "Useful to reduce spamming"
msgstr "Kan eventuele spam verminderen"
-#: ../../Zotlabs/Module/Settings/Channel.php:506
+#: ../../Zotlabs/Module/Settings/Channel.php:528
msgid "Notification Settings"
msgstr "Notificatie-instellingen"
-#: ../../Zotlabs/Module/Settings/Channel.php:507
+#: ../../Zotlabs/Module/Settings/Channel.php:529
msgid "By default post a status message when:"
msgstr "Plaats automatisch een bericht wanneer:"
-#: ../../Zotlabs/Module/Settings/Channel.php:508
+#: ../../Zotlabs/Module/Settings/Channel.php:530
msgid "accepting a friend request"
msgstr "Een connectieverzoek wordt geaccepteerd"
-#: ../../Zotlabs/Module/Settings/Channel.php:509
+#: ../../Zotlabs/Module/Settings/Channel.php:531
msgid "joining a forum/community"
msgstr "Je lid wordt van een forum/groep"
-#: ../../Zotlabs/Module/Settings/Channel.php:510
+#: ../../Zotlabs/Module/Settings/Channel.php:532
msgid "making an <em>interesting</em> profile change"
msgstr "Er sprake is van een <em>interessante</em> profielwijziging"
-#: ../../Zotlabs/Module/Settings/Channel.php:511
+#: ../../Zotlabs/Module/Settings/Channel.php:533
msgid "Send a notification email when:"
msgstr "Verzend een notificatie per e-mail wanneer:"
-#: ../../Zotlabs/Module/Settings/Channel.php:512
+#: ../../Zotlabs/Module/Settings/Channel.php:534
msgid "You receive a connection request"
msgstr "Je een connectieverzoek ontvangt"
-#: ../../Zotlabs/Module/Settings/Channel.php:513
+#: ../../Zotlabs/Module/Settings/Channel.php:535
msgid "Your connections are confirmed"
msgstr "Jouw connecties zijn bevestigd"
-#: ../../Zotlabs/Module/Settings/Channel.php:514
+#: ../../Zotlabs/Module/Settings/Channel.php:536
msgid "Someone writes on your profile wall"
msgstr "Iemand iets op jouw kanaal heeft geschreven"
-#: ../../Zotlabs/Module/Settings/Channel.php:515
+#: ../../Zotlabs/Module/Settings/Channel.php:537
msgid "Someone writes a followup comment"
msgstr "Iemand een reactie schrijft"
-#: ../../Zotlabs/Module/Settings/Channel.php:516
+#: ../../Zotlabs/Module/Settings/Channel.php:538
msgid "You receive a private message"
msgstr "Je een privé-bericht ontvangt"
-#: ../../Zotlabs/Module/Settings/Channel.php:517
+#: ../../Zotlabs/Module/Settings/Channel.php:539
msgid "You receive a friend suggestion"
msgstr "Je een kanaalvoorstel ontvangt"
-#: ../../Zotlabs/Module/Settings/Channel.php:518
+#: ../../Zotlabs/Module/Settings/Channel.php:540
msgid "You are tagged in a post"
msgstr "Je expliciet in een bericht bent genoemd"
-#: ../../Zotlabs/Module/Settings/Channel.php:519
+#: ../../Zotlabs/Module/Settings/Channel.php:541
msgid "You are poked/prodded/etc. in a post"
msgstr "Je bent in een bericht aangestoten/gepord/etc."
-#: ../../Zotlabs/Module/Settings/Channel.php:521
+#: ../../Zotlabs/Module/Settings/Channel.php:543
msgid "Someone likes your post/comment"
msgstr "Iemand jouw bericht/reactie leuk vindt"
-#: ../../Zotlabs/Module/Settings/Channel.php:524
+#: ../../Zotlabs/Module/Settings/Channel.php:546
msgid "Show visual notifications including:"
msgstr "Toon de volgende zichtbare notificaties:"
-#: ../../Zotlabs/Module/Settings/Channel.php:526
+#: ../../Zotlabs/Module/Settings/Channel.php:548
msgid "Unseen grid activity"
msgstr "Niet bekeken grid-activiteit"
-#: ../../Zotlabs/Module/Settings/Channel.php:527
+#: ../../Zotlabs/Module/Settings/Channel.php:549
msgid "Unseen channel activity"
msgstr "Niet bekeken kanaal-activiteit"
-#: ../../Zotlabs/Module/Settings/Channel.php:528
+#: ../../Zotlabs/Module/Settings/Channel.php:550
msgid "Unseen private messages"
msgstr "Niet bekeken privéberichten"
-#: ../../Zotlabs/Module/Settings/Channel.php:528
-#: ../../Zotlabs/Module/Settings/Channel.php:533
-#: ../../Zotlabs/Module/Settings/Channel.php:534
-#: ../../Zotlabs/Module/Settings/Channel.php:535
+#: ../../Zotlabs/Module/Settings/Channel.php:550
+#: ../../Zotlabs/Module/Settings/Channel.php:555
+#: ../../Zotlabs/Module/Settings/Channel.php:556
+#: ../../Zotlabs/Module/Settings/Channel.php:557
#: ../../extend/addon/addon/jappixmini/jappixmini.php:343
msgid "Recommended"
msgstr "Aanbevolen"
-#: ../../Zotlabs/Module/Settings/Channel.php:529
+#: ../../Zotlabs/Module/Settings/Channel.php:551
msgid "Upcoming events"
msgstr "Aankomende gebeurtenissen"
-#: ../../Zotlabs/Module/Settings/Channel.php:530
+#: ../../Zotlabs/Module/Settings/Channel.php:552
msgid "Events today"
msgstr "Gebeurtenissen van vandaag"
-#: ../../Zotlabs/Module/Settings/Channel.php:531
+#: ../../Zotlabs/Module/Settings/Channel.php:553
msgid "Upcoming birthdays"
msgstr "Aankomende verjaardagen"
-#: ../../Zotlabs/Module/Settings/Channel.php:531
+#: ../../Zotlabs/Module/Settings/Channel.php:553
msgid "Not available in all themes"
msgstr "Niet in alle thema's beschikbaar"
-#: ../../Zotlabs/Module/Settings/Channel.php:532
+#: ../../Zotlabs/Module/Settings/Channel.php:554
msgid "System (personal) notifications"
msgstr "(Persoonlijke) systeemnotificaties"
-#: ../../Zotlabs/Module/Settings/Channel.php:533
+#: ../../Zotlabs/Module/Settings/Channel.php:555
msgid "System info messages"
msgstr "Systeemmededelingen"
-#: ../../Zotlabs/Module/Settings/Channel.php:534
+#: ../../Zotlabs/Module/Settings/Channel.php:556
msgid "System critical alerts"
msgstr "Kritische systeemwaarschuwingen"
-#: ../../Zotlabs/Module/Settings/Channel.php:535
+#: ../../Zotlabs/Module/Settings/Channel.php:557
msgid "New connections"
msgstr "Nieuwe connecties"
-#: ../../Zotlabs/Module/Settings/Channel.php:536
+#: ../../Zotlabs/Module/Settings/Channel.php:558
msgid "System Registrations"
msgstr "Nieuwe accountregistraties op deze hub"
-#: ../../Zotlabs/Module/Settings/Channel.php:537
+#: ../../Zotlabs/Module/Settings/Channel.php:559
msgid ""
"Also show new wall posts, private messages and connections under Notices"
msgstr "Toon tevens nieuwe kanaalberichten, privéberichten en connecties onder Notificaties"
-#: ../../Zotlabs/Module/Settings/Channel.php:539
+#: ../../Zotlabs/Module/Settings/Channel.php:561
msgid "Notify me of events this many days in advance"
msgstr "Herinner mij zoveel dagen van te voren aan gebeurtenissen"
-#: ../../Zotlabs/Module/Settings/Channel.php:539
+#: ../../Zotlabs/Module/Settings/Channel.php:561
msgid "Must be greater than 0"
msgstr "Moet hoger dan 0 zijn"
-#: ../../Zotlabs/Module/Settings/Channel.php:541
+#: ../../Zotlabs/Module/Settings/Channel.php:567
msgid "Advanced Account/Page Type Settings"
msgstr "Instellingen geavanceerd account/paginatype"
-#: ../../Zotlabs/Module/Settings/Channel.php:542
+#: ../../Zotlabs/Module/Settings/Channel.php:568
msgid "Change the behaviour of this account for special situations"
msgstr "Verander het gedrag van dit account voor speciale situaties"
-#: ../../Zotlabs/Module/Settings/Channel.php:544
+#: ../../Zotlabs/Module/Settings/Channel.php:570
msgid "Miscellaneous Settings"
msgstr "Diverse instellingen"
-#: ../../Zotlabs/Module/Settings/Channel.php:545
+#: ../../Zotlabs/Module/Settings/Channel.php:571
msgid "Default photo upload folder"
msgstr "Standaard fotoalbum voor uploads"
-#: ../../Zotlabs/Module/Settings/Channel.php:545
-#: ../../Zotlabs/Module/Settings/Channel.php:546
+#: ../../Zotlabs/Module/Settings/Channel.php:571
+#: ../../Zotlabs/Module/Settings/Channel.php:572
msgid "%Y - current year, %m - current month"
msgstr "%Y - dit jaar, %m - deze maand"
-#: ../../Zotlabs/Module/Settings/Channel.php:546
+#: ../../Zotlabs/Module/Settings/Channel.php:572
msgid "Default file upload folder"
msgstr "Standaard bestandsmap voor uploads"
-#: ../../Zotlabs/Module/Settings/Channel.php:548
+#: ../../Zotlabs/Module/Settings/Channel.php:574
msgid "Personal menu to display in your channel pages"
msgstr "Persoonlijk menu om op je kanaalpagina's weer te geven"
-#: ../../Zotlabs/Module/Settings/Channel.php:550
+#: ../../Zotlabs/Module/Settings/Channel.php:576
msgid "Remove this channel."
msgstr "Verwijder dit kanaal."
-#: ../../Zotlabs/Module/Settings/Channel.php:551
+#: ../../Zotlabs/Module/Settings/Channel.php:577
msgid "Firefox Share $Projectname provider"
msgstr "$Projectname-service voor Firefox Share"
-#: ../../Zotlabs/Module/Settings/Channel.php:552
+#: ../../Zotlabs/Module/Settings/Channel.php:578
msgid "Start calendar week on monday"
msgstr "Begin in de agenda de week op maandag"
-#: ../../Zotlabs/Module/Settings/Display.php:137
+#: ../../Zotlabs/Module/Settings/Featured.php:20
+msgid "Affinity Slider settings updated."
+msgstr "Affiniteitsinstellingen bijgewerkt."
+
+#: ../../Zotlabs/Module/Settings/Featured.php:34
+msgid "No feature settings configured"
+msgstr "Geen plugin-instellingen aanwezig"
+
+#: ../../Zotlabs/Module/Settings/Featured.php:41
+msgid "Default maximum affinity level"
+msgstr "Standaard hoogste affiniteitsniveau"
+
+#: ../../Zotlabs/Module/Settings/Featured.php:46
+msgid "Default minimum affinity level"
+msgstr "Standaard laagste affiniteitsniveau"
+
+#: ../../Zotlabs/Module/Settings/Featured.php:50
+msgid "Affinity Slider Settings"
+msgstr "Affiniteitsinstellingen"
+
+#: ../../Zotlabs/Module/Settings/Featured.php:60
+msgid "Feature/Addon Settings"
+msgstr "Plugin-instellingen"
+
+#: ../../Zotlabs/Module/Settings/Permcats.php:37
+msgid "Permission category saved."
+msgstr "Permissiegroep opgeslagen."
+
+#: ../../Zotlabs/Module/Settings/Permcats.php:63
+msgid ""
+"Use this form to create permission rules for various classes of people or "
+"connections."
+msgstr "Gebruik dit formulier om permissieregels voor diverse soorten mensen en connecties aan te maken."
+
+#: ../../Zotlabs/Module/Settings/Permcats.php:96
+msgid "Permission Categories"
+msgstr "Permissiegroepen"
+
+#: ../../Zotlabs/Module/Settings/Permcats.php:104
+msgid "Permission Name"
+msgstr "Permissienaam"
+
+#: ../../Zotlabs/Module/Settings/Tokens.php:31
+#, php-format
+msgid "This channel is limited to %d tokens"
+msgstr "Dit kanaal heeft een limiet van %d tokens"
+
+#: ../../Zotlabs/Module/Settings/Tokens.php:37
+msgid "Name and Password are required."
+msgstr "Naam en wachtwoord zijn vereist"
+
+#: ../../Zotlabs/Module/Settings/Tokens.php:77
+msgid "Token saved."
+msgstr "Token opgeslagen."
+
+#: ../../Zotlabs/Module/Settings/Tokens.php:113
+msgid ""
+"Use this form to create temporary access identifiers to share things with "
+"non-members. These identities may be used in Access Control Lists and "
+"visitors may login using these credentials to access private content."
+msgstr "Gebruik dit formulier om tijdelijke identiteiten aan te maken, waarmee je bepaalde informatie met niet-leden kan delen. Deze identiteiten kunnen onder Permissies (handmatige selectie) worden gebruikt. Gasten kunnen inloggen met onderstaande gegevens om zo toegang te krijgen tot privéinhoud."
+
+#: ../../Zotlabs/Module/Settings/Tokens.php:115
+msgid ""
+"You may also provide <em>dropbox</em> style access links to friends and "
+"associates by adding the Login Password to any specific site URL as shown. "
+"Examples:"
+msgstr "Je kan ook <em>dropbox</em>-achtige links aan mensen geven door bovenstaand wachtwoord op onderstaande manier aan een hub-URL toe te voegen. Voorbeelden:"
+
+#: ../../Zotlabs/Module/Settings/Tokens.php:150 ../../include/widgets.php:644
+msgid "Guest Access Tokens"
+msgstr "Gasttoegang"
+
+#: ../../Zotlabs/Module/Settings/Tokens.php:157
+msgid "Login Name"
+msgstr "Inlognaam"
+
+#: ../../Zotlabs/Module/Settings/Tokens.php:158
+msgid "Login Password"
+msgstr "Wachtwoord:"
+
+#: ../../Zotlabs/Module/Settings/Tokens.php:159
+msgid "Expires (yyyy-mm-dd)"
+msgstr "Geldig t/m (yyyy-mm-dd)"
+
+#: ../../Zotlabs/Module/Settings/Display.php:145
msgid "No special theme for mobile devices"
msgstr "Geen speciaal thema voor mobiele apparaten"
-#: ../../Zotlabs/Module/Settings/Display.php:140
+#: ../../Zotlabs/Module/Settings/Display.php:148
#, php-format
msgid "%s - (Experimental)"
msgstr "%s - (experimenteel)"
-#: ../../Zotlabs/Module/Settings/Display.php:191
+#: ../../Zotlabs/Module/Settings/Display.php:198
msgid "Display Settings"
msgstr "Weergave-instellingen"
-#: ../../Zotlabs/Module/Settings/Display.php:192
+#: ../../Zotlabs/Module/Settings/Display.php:199
msgid "Theme Settings"
msgstr "Thema-instellingen"
-#: ../../Zotlabs/Module/Settings/Display.php:193
+#: ../../Zotlabs/Module/Settings/Display.php:200
msgid "Custom Theme Settings"
msgstr "Handmatige thema-instellingen"
-#: ../../Zotlabs/Module/Settings/Display.php:194
+#: ../../Zotlabs/Module/Settings/Display.php:201
msgid "Content Settings"
msgstr "Inhoudsinstellingen"
-#: ../../Zotlabs/Module/Settings/Display.php:200
+#: ../../Zotlabs/Module/Settings/Display.php:207
msgid "Display Theme:"
msgstr "Gebruik thema:"
-#: ../../Zotlabs/Module/Settings/Display.php:201
+#: ../../Zotlabs/Module/Settings/Display.php:208
msgid "Select scheme"
msgstr "Kies schema van thema"
-#: ../../Zotlabs/Module/Settings/Display.php:203
+#: ../../Zotlabs/Module/Settings/Display.php:210
msgid "Mobile Theme:"
msgstr "Mobiel thema:"
-#: ../../Zotlabs/Module/Settings/Display.php:204
+#: ../../Zotlabs/Module/Settings/Display.php:211
msgid "Preload images before rendering the page"
msgstr "Afbeeldingen laden voordat de pagina wordt weergegeven"
-#: ../../Zotlabs/Module/Settings/Display.php:204
+#: ../../Zotlabs/Module/Settings/Display.php:211
msgid ""
"The subjective page load time will be longer but the page will be ready when"
" displayed"
msgstr "De laadtijd van een pagina lijkt langer, maar de pagina is wel meteen helemaal geladen wanneer deze wordt weergeven"
-#: ../../Zotlabs/Module/Settings/Display.php:205
+#: ../../Zotlabs/Module/Settings/Display.php:212
msgid "Enable user zoom on mobile devices"
msgstr "Inzoomen op smartphones en tablets toestaan"
-#: ../../Zotlabs/Module/Settings/Display.php:206
+#: ../../Zotlabs/Module/Settings/Display.php:213
msgid "Update browser every xx seconds"
msgstr "Ververs de webbrowser om de zoveel seconde"
-#: ../../Zotlabs/Module/Settings/Display.php:206
+#: ../../Zotlabs/Module/Settings/Display.php:213
msgid "Minimum of 10 seconds, no maximum"
msgstr "Minimaal 10 seconde, geen maximum"
-#: ../../Zotlabs/Module/Settings/Display.php:207
+#: ../../Zotlabs/Module/Settings/Display.php:214
msgid "Maximum number of conversations to load at any time:"
msgstr "Maximaal aantal conversaties die per keer geladen worden:"
-#: ../../Zotlabs/Module/Settings/Display.php:207
+#: ../../Zotlabs/Module/Settings/Display.php:214
msgid "Maximum of 100 items"
msgstr "Maximaal 100 conversaties"
-#: ../../Zotlabs/Module/Settings/Display.php:208
+#: ../../Zotlabs/Module/Settings/Display.php:215
msgid "Show emoticons (smilies) as images"
msgstr "Toon emoticons (smilies) als afbeeldingen"
-#: ../../Zotlabs/Module/Settings/Display.php:209
+#: ../../Zotlabs/Module/Settings/Display.php:216
msgid "Manual conversation updates"
msgstr "Handmatige conversatie-updates"
-#: ../../Zotlabs/Module/Settings/Display.php:209
-msgid "Default is automatic, which may increase screen jumping"
-msgstr "Standaard is automatisch, maar soms kan het zorgen voor het verspringen van items"
+#: ../../Zotlabs/Module/Settings/Display.php:216
+msgid "Default is on, turning this off may increase screen jumping"
+msgstr "Dit is standaard ingeschakeld en door dit uit te schakelen kunnen items soms verspringen."
-#: ../../Zotlabs/Module/Settings/Display.php:210
+#: ../../Zotlabs/Module/Settings/Display.php:217
msgid "Link post titles to source"
msgstr "Berichtkoppen naar originele locatie linken"
-#: ../../Zotlabs/Module/Settings/Display.php:211
+#: ../../Zotlabs/Module/Settings/Display.php:218
msgid "System Page Layout Editor - (advanced)"
msgstr "Lay-out bewerken van systeempagina's (geavanceerd)"
-#: ../../Zotlabs/Module/Settings/Display.php:214
+#: ../../Zotlabs/Module/Settings/Display.php:221
msgid "Use blog/list mode on channel page"
msgstr "Gebruik blog/lijst-modus op kanaalpagina"
-#: ../../Zotlabs/Module/Settings/Display.php:214
-#: ../../Zotlabs/Module/Settings/Display.php:215
+#: ../../Zotlabs/Module/Settings/Display.php:221
+#: ../../Zotlabs/Module/Settings/Display.php:222
msgid "(comments displayed separately)"
msgstr "(reacties worden afzonderlijk weergeven)"
-#: ../../Zotlabs/Module/Settings/Display.php:215
+#: ../../Zotlabs/Module/Settings/Display.php:222
msgid "Use blog/list mode on grid page"
msgstr "Gebruik blog/lijst-modus op gridpagina"
-#: ../../Zotlabs/Module/Settings/Display.php:216
+#: ../../Zotlabs/Module/Settings/Display.php:223
msgid "Channel page max height of content (in pixels)"
msgstr "Maximale hoogte berichtinhoud op kanaalpagina (in pixels)"
-#: ../../Zotlabs/Module/Settings/Display.php:216
-#: ../../Zotlabs/Module/Settings/Display.php:217
+#: ../../Zotlabs/Module/Settings/Display.php:223
+#: ../../Zotlabs/Module/Settings/Display.php:224
msgid "click to expand content exceeding this height"
msgstr "klik om inhoud uit te klappen die deze hoogte overschrijdt"
-#: ../../Zotlabs/Module/Settings/Display.php:217
+#: ../../Zotlabs/Module/Settings/Display.php:224
msgid "Grid page max height of content (in pixels)"
msgstr "Maximale hoogte berichtinhoud op gridpagina (in pixels)"
-#: ../../Zotlabs/Module/Settings/Featured.php:24
-msgid "No feature settings configured"
-msgstr "Geen plugin-instellingen aanwezig"
-
-#: ../../Zotlabs/Module/Settings/Featured.php:31
-msgid "Feature/Addon Settings"
-msgstr "Plugin-instellingen"
-
#: ../../Zotlabs/Module/Tagrm.php:48 ../../Zotlabs/Module/Tagrm.php:98
msgid "Tag removed"
msgstr "Tag verwijderd"
@@ -6657,88 +6548,450 @@ msgstr "Naam van ding"
#: ../../Zotlabs/Module/Thing.php:309 ../../Zotlabs/Module/Thing.php:361
msgid "URL of thing (optional)"
-msgstr "URL van ding (optioneel)"
+msgstr "URL van ding (niet verplicht)"
#: ../../Zotlabs/Module/Thing.php:311 ../../Zotlabs/Module/Thing.php:362
msgid "URL for photo of thing (optional)"
-msgstr "URL voor foto van ding (optioneel)"
+msgstr "URL voor foto van ding (niet verplicht)"
#: ../../Zotlabs/Module/Thing.php:353
msgid "Add Thing to your Profile"
msgstr "Ding aan je profiel toevoegen"
-#: ../../Zotlabs/Module/Import.php:33
+#: ../../Zotlabs/Module/Setup.php:176
+msgid "$Projectname Server - Setup"
+msgstr "$Projectname Hub - Setup"
+
+#: ../../Zotlabs/Module/Setup.php:180
+msgid "Could not connect to database."
+msgstr "Could not connect to database."
+
+#: ../../Zotlabs/Module/Setup.php:184
+msgid ""
+"Could not connect to specified site URL. Possible SSL certificate or DNS "
+"issue."
+msgstr "Could not connect to specified hub URL. Possible SSL certificate or DNS issue."
+
+#: ../../Zotlabs/Module/Setup.php:191
+msgid "Could not create table."
+msgstr "Could not create table."
+
+#: ../../Zotlabs/Module/Setup.php:196
+msgid "Your site database has been installed."
+msgstr "Your hub database has been installed."
+
+#: ../../Zotlabs/Module/Setup.php:200
+msgid ""
+"You may need to import the file \"install/schema_xxx.sql\" manually using a "
+"database client."
+msgstr "You may need to import the file \"install/schema_xxx.sql\" manually using a database client."
+
+#: ../../Zotlabs/Module/Setup.php:201 ../../Zotlabs/Module/Setup.php:263
+#: ../../Zotlabs/Module/Setup.php:750
+msgid "Please see the file \"install/INSTALL.txt\"."
+msgstr "Please see the file \"install/INSTALL.txt\"."
+
+#: ../../Zotlabs/Module/Setup.php:260
+msgid "System check"
+msgstr "System check"
+
+#: ../../Zotlabs/Module/Setup.php:265
+msgid "Check again"
+msgstr "Check again"
+
+#: ../../Zotlabs/Module/Setup.php:287
+msgid "Database connection"
+msgstr "Database connection"
+
+#: ../../Zotlabs/Module/Setup.php:288
+msgid ""
+"In order to install $Projectname we need to know how to connect to your "
+"database."
+msgstr "In order to install $Projectname we need to know how to connect to your database."
+
+#: ../../Zotlabs/Module/Setup.php:289
+msgid ""
+"Please contact your hosting provider or site administrator if you have "
+"questions about these settings."
+msgstr "Please contact your hosting provider or server administrator if you have questions about these settings."
+
+#: ../../Zotlabs/Module/Setup.php:290
+msgid ""
+"The database you specify below should already exist. If it does not, please "
+"create it before continuing."
+msgstr "The database you specify below should already exist. If it does not, please create it before continuing."
+
+#: ../../Zotlabs/Module/Setup.php:294
+msgid "Database Server Name"
+msgstr "Database Server Name"
+
+#: ../../Zotlabs/Module/Setup.php:294
+msgid "Default is 127.0.0.1"
+msgstr "Default is 127.0.0.1"
+
+#: ../../Zotlabs/Module/Setup.php:295
+msgid "Database Port"
+msgstr "Database Port"
+
+#: ../../Zotlabs/Module/Setup.php:295
+msgid "Communication port number - use 0 for default"
+msgstr "Communication port number - use 0 for default"
+
+#: ../../Zotlabs/Module/Setup.php:296
+msgid "Database Login Name"
+msgstr "Database Login Name"
+
+#: ../../Zotlabs/Module/Setup.php:297
+msgid "Database Login Password"
+msgstr "Database Login Password"
+
+#: ../../Zotlabs/Module/Setup.php:298
+msgid "Database Name"
+msgstr "Database Name"
+
+#: ../../Zotlabs/Module/Setup.php:299
+msgid "Database Type"
+msgstr "Database Type"
+
+#: ../../Zotlabs/Module/Setup.php:301 ../../Zotlabs/Module/Setup.php:347
+msgid "Site administrator email address"
+msgstr "Hub administrator email address"
+
+#: ../../Zotlabs/Module/Setup.php:301 ../../Zotlabs/Module/Setup.php:347
+msgid ""
+"Your account email address must match this in order to use the web admin "
+"panel."
+msgstr "Your account email address must match this in order to use the web admin panel."
+
+#: ../../Zotlabs/Module/Setup.php:302 ../../Zotlabs/Module/Setup.php:349
+msgid "Website URL"
+msgstr "Hub URL"
+
+#: ../../Zotlabs/Module/Setup.php:302 ../../Zotlabs/Module/Setup.php:349
+msgid "Please use SSL (https) URL if available."
+msgstr "Please use SSL (https) URL if available."
+
+#: ../../Zotlabs/Module/Setup.php:303 ../../Zotlabs/Module/Setup.php:353
+msgid "Please select a default timezone for your website"
+msgstr "Please select a default timezone for your hub"
+
+#: ../../Zotlabs/Module/Setup.php:336
+msgid "Site settings"
+msgstr "Hub settings"
+
+#: ../../Zotlabs/Module/Setup.php:392
+msgid "PHP version 5.5 or greater is required."
+msgstr "PHP version 5.5 or greater is required."
+
+#: ../../Zotlabs/Module/Setup.php:393
+msgid "PHP version"
+msgstr "PHP version"
+
+#: ../../Zotlabs/Module/Setup.php:409
+msgid "Could not find a command line version of PHP in the web server PATH."
+msgstr "Could not find a command line version of PHP in the web server PATH."
+
+#: ../../Zotlabs/Module/Setup.php:410
+msgid ""
+"If you don't have a command line version of PHP installed on server, you "
+"will not be able to run background polling via cron."
+msgstr "If you don't have a command line version of PHP installed on server, you will not be able to run background polling via cron."
+
+#: ../../Zotlabs/Module/Setup.php:414
+msgid "PHP executable path"
+msgstr "PHP executable path"
+
+#: ../../Zotlabs/Module/Setup.php:414
+msgid ""
+"Enter full path to php executable. You can leave this blank to continue the "
+"installation."
+msgstr "Enter full path to php executable. You can leave this blank to continue the installation."
+
+#: ../../Zotlabs/Module/Setup.php:419
+msgid "Command line PHP"
+msgstr "Command line PHP"
+
+#: ../../Zotlabs/Module/Setup.php:429
+msgid ""
+"Unable to check command line PHP, as shell_exec() is disabled. This is "
+"required."
+msgstr "Unable to check command line PHP, as shell_exec() is disabled. This is required."
+
+#: ../../Zotlabs/Module/Setup.php:432
+msgid ""
+"The command line version of PHP on your system does not have "
+"\"register_argc_argv\" enabled."
+msgstr "The command line version of PHP on your system does not have \"register_argc_argv\" enabled."
+
+#: ../../Zotlabs/Module/Setup.php:433
+msgid "This is required for message delivery to work."
+msgstr "This is required for message delivery to work."
+
+#: ../../Zotlabs/Module/Setup.php:436
+msgid "PHP register_argc_argv"
+msgstr "PHP register_argc_argv"
+
+#: ../../Zotlabs/Module/Setup.php:454
#, php-format
-msgid "Your service plan only allows %d channels."
-msgstr "Jouw abonnement staat maar %d kanalen toe."
+msgid ""
+"Your max allowed total upload size is set to %s. Maximum size of one file to"
+" upload is set to %s. You are allowed to upload up to %d files at once."
+msgstr "Your max allowed total upload size is set to %s. Maximum size of one file to upload is set to %s. You are allowed to upload up to %d files at once."
-#: ../../Zotlabs/Module/Import.php:157 ../../include/import.php:100
-msgid "Cloned channel not found. Import failed."
-msgstr "Gekloond kanaal niet gevonden. Importeren mislukt."
+#: ../../Zotlabs/Module/Setup.php:459
+msgid "You can adjust these settings in the server php.ini file."
+msgstr "You can adjust these settings in the server php.ini file."
-#: ../../Zotlabs/Module/Import.php:167
-msgid "No channel. Import failed."
-msgstr "Geen kanaal. Importeren mislukt."
+#: ../../Zotlabs/Module/Setup.php:461
+msgid "PHP upload limits"
+msgstr "PHP upload limits"
-#: ../../Zotlabs/Module/Import.php:503
-#: ../../include/Import/import_diaspora.php:142
-msgid "Import completed."
-msgstr "Import voltooid."
+#: ../../Zotlabs/Module/Setup.php:484
+msgid ""
+"Error: the \"openssl_pkey_new\" function on this system is not able to "
+"generate encryption keys"
+msgstr "Error: the \"openssl_pkey_new\" function on this system is not able to generate encryption keys"
-#: ../../Zotlabs/Module/Import.php:525
-msgid "You must be logged in to use this feature."
-msgstr "Je moet ingelogd zijn om dit onderdeel te kunnen gebruiken."
+#: ../../Zotlabs/Module/Setup.php:485
+msgid ""
+"If running under Windows, please see "
+"\"http://www.php.net/manual/en/openssl.installation.php\"."
+msgstr "If running under Windows, please see \"http://www.php.net/manual/en/openssl.installation.php\"."
-#: ../../Zotlabs/Module/Import.php:530
-msgid "Import Channel"
-msgstr "Kanaal importeren"
+#: ../../Zotlabs/Module/Setup.php:488
+msgid "Generate encryption keys"
+msgstr "Generate encryption keys"
+
+#: ../../Zotlabs/Module/Setup.php:505
+msgid "libCurl PHP module"
+msgstr "libCurl PHP module"
+
+#: ../../Zotlabs/Module/Setup.php:506
+msgid "GD graphics PHP module"
+msgstr "GD graphics PHP module"
+
+#: ../../Zotlabs/Module/Setup.php:507
+msgid "OpenSSL PHP module"
+msgstr "OpenSSL PHP module"
+
+#: ../../Zotlabs/Module/Setup.php:508
+msgid "PDO database PHP module"
+msgstr "PDO database PHP module"
-#: ../../Zotlabs/Module/Import.php:531
+#: ../../Zotlabs/Module/Setup.php:509
+msgid "mb_string PHP module"
+msgstr "mb_string PHP module"
+
+#: ../../Zotlabs/Module/Setup.php:510
+msgid "xml PHP module"
+msgstr "xml PHP module"
+
+#: ../../Zotlabs/Module/Setup.php:514 ../../Zotlabs/Module/Setup.php:516
+msgid "Apache mod_rewrite module"
+msgstr "Apache mod_rewrite module"
+
+#: ../../Zotlabs/Module/Setup.php:514
msgid ""
-"Use this form to import an existing channel from a different server/hub. You"
-" may retrieve the channel identity from the old server/hub via the network "
-"or provide an export file."
-msgstr "Gebruik dit formulier om een bestaand kanaal te importeren van een andere hub. Je kan de kanaal-identiteit van de oude hub via het netwerk ontvangen of een exportbestand verstrekken."
+"Error: Apache webserver mod-rewrite module is required but not installed."
+msgstr "Error: Apache webserver mod-rewrite module is required but not installed."
-#: ../../Zotlabs/Module/Import.php:533
-msgid "Or provide the old server/hub details"
-msgstr "Of vul de gegevens van de oude hub in"
+#: ../../Zotlabs/Module/Setup.php:520 ../../Zotlabs/Module/Setup.php:523
+msgid "exec"
+msgstr "exec"
-#: ../../Zotlabs/Module/Import.php:534
-msgid "Your old identity address (xyz@example.com)"
-msgstr "Jouw oude kanaaladres (xyz@example.com)"
+#: ../../Zotlabs/Module/Setup.php:520
+msgid ""
+"Error: exec is required but is either not installed or has been disabled in "
+"php.ini"
+msgstr "Error: exec is required but is either not installed or has been disabled in php.ini"
-#: ../../Zotlabs/Module/Import.php:535
-msgid "Your old login email address"
-msgstr "Het e-mailadres van je oude account"
+#: ../../Zotlabs/Module/Setup.php:526 ../../Zotlabs/Module/Setup.php:529
+msgid "shell_exec"
+msgstr "shell_exec"
-#: ../../Zotlabs/Module/Import.php:536
-msgid "Your old login password"
-msgstr "Wachtwoord van jouw oude account"
+#: ../../Zotlabs/Module/Setup.php:526
+msgid ""
+"Error: shell_exec is required but is either not installed or has been "
+"disabled in php.ini"
+msgstr "Error: shell_exec is required but is either not installed or has been disabled in php.ini"
+
+#: ../../Zotlabs/Module/Setup.php:534
+msgid "Error: libCURL PHP module required but not installed."
+msgstr "Error: libCURL PHP module required but not installed."
-#: ../../Zotlabs/Module/Import.php:537
+#: ../../Zotlabs/Module/Setup.php:538
msgid ""
-"For either option, please choose whether to make this hub your new primary "
-"address, or whether your old location should continue this role. You will be"
-" able to post from either location, but only one can be marked as the "
-"primary location for files, photos, and media."
-msgstr "Voor elke optie geldt dat je moet kiezen of je jouw primaire kanaaladres op deze hub wil instellen of dat jouw oude hub deze rol blijft vervullen."
+"Error: GD graphics PHP module with JPEG support required but not installed."
+msgstr "Error: GD graphics PHP module with JPEG support required but not installed."
-#: ../../Zotlabs/Module/Import.php:538
-msgid "Make this hub my primary location"
-msgstr "Stel deze hub als mijn primaire locatie in"
+#: ../../Zotlabs/Module/Setup.php:542
+msgid "Error: openssl PHP module required but not installed."
+msgstr "Error: openssl PHP module required but not installed."
+
+#: ../../Zotlabs/Module/Setup.php:546
+msgid "Error: PDO database PHP module required but not installed."
+msgstr "Error: PDO database PHP module required but not installed."
+
+#: ../../Zotlabs/Module/Setup.php:550
+msgid "Error: mb_string PHP module required but not installed."
+msgstr "Error: mb_string PHP module required but not installed."
+
+#: ../../Zotlabs/Module/Setup.php:554
+msgid "Error: xml PHP module required for DAV but not installed."
+msgstr "Error: xml PHP module required for DAV but not installed."
-#: ../../Zotlabs/Module/Import.php:539
+#: ../../Zotlabs/Module/Setup.php:572
msgid ""
-"Import existing posts if possible (experimental - limited by available "
-"memory"
-msgstr "Importeer bestaande berichten wanneer mogelijk (experimenteel - afhankelijk van beschikbaar servergeheugen)"
+"The web installer needs to be able to create a file called \".htconfig.php\""
+" in the top folder of your web server and it is unable to do so."
+msgstr "The web installer needs to be able to create a file called \".htconfig.php\" in the top folder of your web server and it is unable to do so."
-#: ../../Zotlabs/Module/Import.php:540
+#: ../../Zotlabs/Module/Setup.php:573
msgid ""
-"This process may take several minutes to complete. Please submit the form "
-"only once and leave this page open until finished."
-msgstr "Dit proces kan enkele minuten in beslag nemen. Klik maar één keer op opslaan en verlaat deze pagina niet alvorens het proces is voltooid."
+"This is most often a permission setting, as the web server may not be able "
+"to write files in your folder - even if you can."
+msgstr "This is most often a permission setting, as the web server may not be able to write files in your folder - even if you can."
+
+#: ../../Zotlabs/Module/Setup.php:574
+msgid ""
+"At the end of this procedure, we will give you a text to save in a file "
+"named .htconfig.php in your Red top folder."
+msgstr "At the end of this procedure, we will give you a text to save in a file named .htconfig.php in your Red top folder."
+
+#: ../../Zotlabs/Module/Setup.php:575
+msgid ""
+"You can alternatively skip this procedure and perform a manual installation."
+" Please see the file \"install/INSTALL.txt\" for instructions."
+msgstr "You can alternatively skip this procedure and perform a manual installation. Please see the file \"install/INSTALL.txt\" for instructions."
+
+#: ../../Zotlabs/Module/Setup.php:578
+msgid ".htconfig.php is writable"
+msgstr ".htconfig.php is writable"
+
+#: ../../Zotlabs/Module/Setup.php:592
+msgid ""
+"This software uses the Smarty3 template engine to render its web views. "
+"Smarty3 compiles templates to PHP to speed up rendering."
+msgstr "This software uses the Smarty3 template engine to render its web views. Smarty3 compiles templates to PHP to speed up rendering."
+
+#: ../../Zotlabs/Module/Setup.php:593
+#, php-format
+msgid ""
+"In order to store these compiled templates, the web server needs to have "
+"write access to the directory %s under the top level web folder."
+msgstr "In order to store these compiled templates, the web server needs to have write access to the directory %s under the top level web folder."
+
+#: ../../Zotlabs/Module/Setup.php:594 ../../Zotlabs/Module/Setup.php:615
+msgid ""
+"Please ensure that the user that your web server runs as (e.g. www-data) has"
+" write access to this folder."
+msgstr "Please ensure that the user that your web server runs as (e.g. www-data) has write access to this folder."
+
+#: ../../Zotlabs/Module/Setup.php:595
+#, php-format
+msgid ""
+"Note: as a security measure, you should give the web server write access to "
+"%s only--not the template files (.tpl) that it contains."
+msgstr "Note: as a security measure, you should give the web server write access to %s only--not the template files (.tpl) that it contains."
+
+#: ../../Zotlabs/Module/Setup.php:598
+#, php-format
+msgid "%s is writable"
+msgstr "%s is writable"
+
+#: ../../Zotlabs/Module/Setup.php:614
+msgid ""
+"This software uses the store directory to save uploaded files. The web "
+"server needs to have write access to the store directory under the top level"
+" web folder"
+msgstr "This software uses the store directory to save uploaded files. The web server needs to have write access to the store directory under the top level web folder"
+
+#: ../../Zotlabs/Module/Setup.php:618
+msgid "store is writable"
+msgstr "store is writable"
+
+#: ../../Zotlabs/Module/Setup.php:651
+msgid ""
+"SSL certificate cannot be validated. Fix certificate or disable https access"
+" to this site."
+msgstr "SSL certificate cannot be validated. Fix certificate or disable https access to this hub."
+
+#: ../../Zotlabs/Module/Setup.php:652
+msgid ""
+"If you have https access to your website or allow connections to TCP port "
+"443 (the https: port), you MUST use a browser-valid certificate. You MUST "
+"NOT use self-signed certificates!"
+msgstr "If you have https access to your hub or allow connections to TCP port 443 (the https: port), you MUST use a browser-valid certificate. You MUST NOT use self-signed certificates!"
+
+#: ../../Zotlabs/Module/Setup.php:653
+msgid ""
+"This restriction is incorporated because public posts from you may for "
+"example contain references to images on your own hub."
+msgstr "This restriction is incorporated because public posts from you may for example contain references to images on your own hub."
+
+#: ../../Zotlabs/Module/Setup.php:654
+msgid ""
+"If your certificate is not recognized, members of other sites (who may "
+"themselves have valid certificates) will get a warning message on their own "
+"site complaining about security issues."
+msgstr "If your certificate is not recognized, members of other hubs (who may themselves have valid certificates) will get a warning message on their own hub complaining about security issues."
+
+#: ../../Zotlabs/Module/Setup.php:655
+msgid ""
+"This can cause usability issues elsewhere (not just on your own site) so we "
+"must insist on this requirement."
+msgstr "This can cause usability issues elsewhere (not just on your own hub) so we must insist on this requirement."
+
+#: ../../Zotlabs/Module/Setup.php:656
+msgid ""
+"Providers are available that issue free certificates which are browser-"
+"valid."
+msgstr "Providers are available that issue free certificates which are browser-valid."
+
+#: ../../Zotlabs/Module/Setup.php:658
+msgid ""
+"If you are confident that the certificate is valid and signed by a trusted "
+"authority, check to see if you have failed to install an intermediate cert. "
+"These are not normally required by browsers, but are required for server-to-"
+"server communications."
+msgstr "If you are confident that the certificate is valid and signed by a trusted authority, check to see if you have failed to install an intermediate cert. These are not normally required by browsers, but are required for server-to-server communications."
+
+#: ../../Zotlabs/Module/Setup.php:660
+msgid "SSL certificate validation"
+msgstr "SSL certificate validation"
+
+#: ../../Zotlabs/Module/Setup.php:666
+msgid ""
+"Url rewrite in .htaccess is not working. Check your server "
+"configuration.Test: "
+msgstr "Url rewrite in .htaccess is not working. Check your server configuration.Test: "
+
+#: ../../Zotlabs/Module/Setup.php:669
+msgid "Url rewrite is working"
+msgstr "Url rewrite is working"
+
+#: ../../Zotlabs/Module/Setup.php:683
+msgid ""
+"The database configuration file \".htconfig.php\" could not be written. "
+"Please use the enclosed text to create a configuration file in your web "
+"server root."
+msgstr "The database configuration file \".htconfig.php\" could not be written. Please use the enclosed text to create a configuration file in your web server root."
+
+#: ../../Zotlabs/Module/Setup.php:707
+#: ../../extend/addon/addon/cdav/cdav.php:41
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:401
+msgid "Errors encountered creating database tables."
+msgstr "Errors encountered creating database tables."
+
+#: ../../Zotlabs/Module/Setup.php:748
+msgid "<h1>What next</h1>"
+msgstr "<h1>What next</h1>"
+
+#: ../../Zotlabs/Module/Setup.php:749
+msgid ""
+"IMPORTANT: You will need to [manually] setup a scheduled task for the "
+"poller."
+msgstr "IMPORTANT: You will need to [manually] setup a scheduled task for the poller."
#: ../../Zotlabs/Module/Viewconnections.php:65
msgid "No connections."
@@ -6753,60 +7006,232 @@ msgstr "Bezoek het profiel van %s [%s]"
msgid "View Connections"
msgstr "Connecties weergeven"
-#: ../../Zotlabs/Module/Viewsrc.php:44
-msgid "Source of Item"
-msgstr "Bron van item"
+#: ../../Zotlabs/Module/Wiki.php:30
+msgid "Profile Unavailable."
+msgstr "Profiel niet beschikbaar."
+
+#: ../../Zotlabs/Module/Wiki.php:44
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:40
+msgid "Not found"
+msgstr "Niet gevonden"
+
+#: ../../Zotlabs/Module/Wiki.php:68
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:60
+msgid "Invalid channel"
+msgstr "Onbekend kanaal"
+
+#: ../../Zotlabs/Module/Wiki.php:159
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:144
+#: ../../include/conversation.php:1900
+msgid "Wikis"
+msgstr "Wiki's"
+
+#: ../../Zotlabs/Module/Wiki.php:165
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:150
+msgid "Download"
+msgstr "Download"
+
+#: ../../Zotlabs/Module/Wiki.php:169
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:154
+msgid "Wiki name"
+msgstr "Naam wiki"
+
+#: ../../Zotlabs/Module/Wiki.php:170
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:155
+msgid "Content type"
+msgstr "Opmaaktype"
+
+#: ../../Zotlabs/Module/Wiki.php:179
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:164
+msgid "Create a status post for this wiki"
+msgstr "Plaats een bericht over deze wiki"
+
+#: ../../Zotlabs/Module/Wiki.php:204
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:183
+msgid "Wiki not found"
+msgstr "Wiki is niet gevonden"
+
+#: ../../Zotlabs/Module/Wiki.php:228
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:208
+msgid "Rename page"
+msgstr "Pagina hernoemen"
+
+#: ../../Zotlabs/Module/Wiki.php:232
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:212
+msgid "Error retrieving page content"
+msgstr "Fout tijdens ophalen inhoud pagina"
+
+#: ../../Zotlabs/Module/Wiki.php:259
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:241
+msgid "Revision Comparison"
+msgstr "Revisies vergelijken"
+
+#: ../../Zotlabs/Module/Wiki.php:260
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:242
+msgid "Revert"
+msgstr "Ongedaan maken"
+
+#: ../../Zotlabs/Module/Wiki.php:264
+msgid "Short description of your changes (optional)"
+msgstr "Korte omschrijving van jouw wijzigingen (niet verplicht)"
+
+#: ../../Zotlabs/Module/Wiki.php:271
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:251
+msgid "Source"
+msgstr "Bron"
+
+#: ../../Zotlabs/Module/Wiki.php:279
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:259
+msgid "New page name"
+msgstr "Nieuwe paginanaam"
+
+#: ../../Zotlabs/Module/Wiki.php:284
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:264
+#: ../../include/conversation.php:1299
+msgid "Embed image from photo albums"
+msgstr "Afbeelding uit een fotoalbum invoegen"
+
+#: ../../Zotlabs/Module/Wiki.php:285
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:265
+#: ../../include/conversation.php:1393
+msgid "Embed an image from your albums"
+msgstr "Afbeelding uit jouw albums invoegen"
+
+#: ../../Zotlabs/Module/Wiki.php:287
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:267
+#: ../../include/conversation.php:1395 ../../include/conversation.php:1442
+msgid "OK"
+msgstr "OK"
+
+#: ../../Zotlabs/Module/Wiki.php:288
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:268
+#: ../../include/conversation.php:1335
+msgid "Choose images to embed"
+msgstr "Kies afbeeldingen om in te voegen"
+
+#: ../../Zotlabs/Module/Wiki.php:289
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:269
+#: ../../include/conversation.php:1336
+msgid "Choose an album"
+msgstr "Kies een album"
+
+#: ../../Zotlabs/Module/Wiki.php:290
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:270
+msgid "Choose a different album"
+msgstr "Kies een ander album"
+
+#: ../../Zotlabs/Module/Wiki.php:291
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:271
+#: ../../include/conversation.php:1338
+msgid "Error getting album list"
+msgstr "Fout tijdens ophalen albumlijst"
+
+#: ../../Zotlabs/Module/Wiki.php:292
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:272
+#: ../../include/conversation.php:1339
+msgid "Error getting photo link"
+msgstr "Fout tijdens ophalen fotolink"
+
+#: ../../Zotlabs/Module/Wiki.php:293
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:273
+#: ../../include/conversation.php:1340
+msgid "Error getting album"
+msgstr "Fout tijdens ophalen album"
+
+#: ../../Zotlabs/Module/Wiki.php:357
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:337
+msgid "Error creating wiki. Invalid name."
+msgstr "Fout tijdens aanmaken wiki. Ongeldige naam."
+
+#: ../../Zotlabs/Module/Wiki.php:369
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:348
+msgid "Wiki created, but error creating Home page."
+msgstr "Wiki aangemaakt, maar fout tijdens aanmaken homepagina."
+
+#: ../../Zotlabs/Module/Wiki.php:376
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:353
+msgid "Error creating wiki"
+msgstr "Fout tijdens aanmaken wiki."
+
+#: ../../Zotlabs/Module/Wiki.php:388
+msgid "Wiki delete permission denied."
+msgstr "Toegang geweigerd tijdens verwijderen wiki."
+
+#: ../../Zotlabs/Module/Wiki.php:398
+msgid "Error deleting wiki"
+msgstr "Fout tijdens verwijderen wiki"
+
+#: ../../Zotlabs/Module/Wiki.php:424
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:400
+msgid "New page created"
+msgstr "Nieuwe pagina aangemaakt"
+
+#: ../../Zotlabs/Module/Wiki.php:539
+msgid "Cannot delete Home"
+msgstr "Kan Home niet verwijderen"
+
+#: ../../Zotlabs/Module/Wiki.php:603
+msgid "Current Revision"
+msgstr "Huidige revisie"
-#: ../../Zotlabs/Module/Chat.php:181
+#: ../../Zotlabs/Module/Wiki.php:603
+msgid "Selected Revision"
+msgstr "Geselecteerde revisie"
+
+#: ../../Zotlabs/Module/Wiki.php:653
+msgid "You must be authenticated."
+msgstr "Je moet geauthenticeerd zijn"
+
+#: ../../Zotlabs/Module/Chat.php:179
msgid "Room not found"
msgstr "Chatkanaal niet gevonden"
-#: ../../Zotlabs/Module/Chat.php:197
+#: ../../Zotlabs/Module/Chat.php:195
msgid "Leave Room"
msgstr "Chatkanaal verlaten"
-#: ../../Zotlabs/Module/Chat.php:198
+#: ../../Zotlabs/Module/Chat.php:196
msgid "Delete Room"
msgstr "Chatkanaal verwijderen"
-#: ../../Zotlabs/Module/Chat.php:199
+#: ../../Zotlabs/Module/Chat.php:197
msgid "I am away right now"
msgstr "Ik ben momenteel afwezig"
-#: ../../Zotlabs/Module/Chat.php:200
+#: ../../Zotlabs/Module/Chat.php:198
msgid "I am online"
msgstr "Ik ben online"
-#: ../../Zotlabs/Module/Chat.php:202
+#: ../../Zotlabs/Module/Chat.php:200
msgid "Bookmark this room"
msgstr "Chatkanaal aan bladwijzers toevoegen"
-#: ../../Zotlabs/Module/Chat.php:231
+#: ../../Zotlabs/Module/Chat.php:229
msgid "New Chatroom"
msgstr "Nieuw chatkanaal"
-#: ../../Zotlabs/Module/Chat.php:232
+#: ../../Zotlabs/Module/Chat.php:230
msgid "Chatroom name"
msgstr "Naam chatkanaal"
-#: ../../Zotlabs/Module/Chat.php:233
+#: ../../Zotlabs/Module/Chat.php:231
msgid "Expiration of chats (minutes)"
msgstr "Aantal minuten voordat chatberichten worden verwijderd"
-#: ../../Zotlabs/Module/Chat.php:249
+#: ../../Zotlabs/Module/Chat.php:247
#, php-format
msgid "%1$s's Chatrooms"
msgstr "Chatkanalen van %1$s"
-#: ../../Zotlabs/Module/Chat.php:254
+#: ../../Zotlabs/Module/Chat.php:252
msgid "No chatrooms available"
msgstr "Geen chatkanalen beschikbaar"
-#: ../../Zotlabs/Module/Chat.php:258
+#: ../../Zotlabs/Module/Chat.php:256
msgid "Expiration"
msgstr "Verloopt na"
-#: ../../Zotlabs/Module/Chat.php:259
+#: ../../Zotlabs/Module/Chat.php:257
msgid "min"
msgstr "min"
@@ -6818,153 +7243,248 @@ msgstr "Xchan opzoeken"
msgid "Lookup xchan beginning with (or webbie): "
msgstr "Zoek een xchan (of webbie) die begint met:"
-#: ../../Zotlabs/Module/Events.php:25
-msgid "Calendar entries imported."
-msgstr "Agenda-items geïmporteerd."
+#: ../../Zotlabs/Lib/Chatroom.php:27
+msgid "Missing room name"
+msgstr "Naam chatkanaal ontbreekt"
-#: ../../Zotlabs/Module/Events.php:27
-msgid "No calendar entries found."
-msgstr "Geen agenda-items gevonden."
+#: ../../Zotlabs/Lib/Chatroom.php:36
+msgid "Duplicate room name"
+msgstr "Naam chatkanaal bestaat al"
-#: ../../Zotlabs/Module/Events.php:106
-msgid "Event can not end before it has started."
-msgstr "Gebeurtenis kan niet eindigen voordat het is begonnen"
+#: ../../Zotlabs/Lib/Chatroom.php:86 ../../Zotlabs/Lib/Chatroom.php:94
+msgid "Invalid room specifier."
+msgstr "Ongeldige omschrijving chatkanaal"
-#: ../../Zotlabs/Module/Events.php:108 ../../Zotlabs/Module/Events.php:117
-#: ../../Zotlabs/Module/Events.php:139
-msgid "Unable to generate preview."
-msgstr "Niet in staat om voorvertoning te genereren"
+#: ../../Zotlabs/Lib/Chatroom.php:126
+msgid "Room not found."
+msgstr "Chatkanaal niet gevonden"
-#: ../../Zotlabs/Module/Events.php:115
-msgid "Event title and start time are required."
-msgstr "Titel en begintijd van gebeurtenis zijn vereist."
+#: ../../Zotlabs/Lib/Chatroom.php:147
+msgid "Room is full"
+msgstr "Chatkanaal is vol"
-#: ../../Zotlabs/Module/Events.php:137 ../../Zotlabs/Module/Events.php:261
-msgid "Event not found."
-msgstr "Gebeurtenis niet gevonden"
+#: ../../Zotlabs/Lib/Enotify.php:60 ../../include/network.php:1947
+msgid "$Projectname Notification"
+msgstr "$Projectname-notificatie"
-#: ../../Zotlabs/Module/Events.php:453
-msgid "Edit event title"
-msgstr "Titel bewerken"
+#: ../../Zotlabs/Lib/Enotify.php:61 ../../extend/addon/addon/diaspora/p.php:46
+#: ../../extend/addon/addon/diaspora/util.php:218
+#: ../../extend/addon/addon/diaspora/util.php:231
+#: ../../include/network.php:1948
+msgid "$projectname"
+msgstr "$projectname"
-#: ../../Zotlabs/Module/Events.php:453
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:835
-msgid "Event title"
-msgstr "Titel"
+#: ../../Zotlabs/Lib/Enotify.php:63 ../../include/network.php:1950
+msgid "Thank You,"
+msgstr "Bedankt,"
-#: ../../Zotlabs/Module/Events.php:455
-msgid "Categories (comma-separated list)"
-msgstr "Categorieën (door komma's gescheiden lijst)"
+#: ../../Zotlabs/Lib/Enotify.php:65 ../../include/network.php:1952
+#, php-format
+msgid "%s Administrator"
+msgstr "Beheerder %s"
-#: ../../Zotlabs/Module/Events.php:456
-msgid "Edit Category"
-msgstr "Categorie"
+#: ../../Zotlabs/Lib/Enotify.php:116
+#, php-format
+msgid "%s <!item_type!>"
+msgstr "%s <!item_type!>"
-#: ../../Zotlabs/Module/Events.php:456
-msgid "Category"
-msgstr "Categorie"
+#: ../../Zotlabs/Lib/Enotify.php:120
+#, php-format
+msgid "[$Projectname:Notify] New mail received at %s"
+msgstr "[$Projectname:Notificatie] Nieuw privébericht ontvangen op %s"
-#: ../../Zotlabs/Module/Events.php:459
-msgid "Edit start date and time"
-msgstr "Begindatum en -tijd bewerken"
+#: ../../Zotlabs/Lib/Enotify.php:122
+#, php-format
+msgid "%1$s, %2$s sent you a new private message at %3$s."
+msgstr "%1$s, %2$s zond jou een nieuw privébericht om %3$s."
-#: ../../Zotlabs/Module/Events.php:459
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:836
-msgid "Start date and time"
-msgstr "Begindatum en -tijd"
+#: ../../Zotlabs/Lib/Enotify.php:123
+#, php-format
+msgid "%1$s sent you %2$s."
+msgstr "%1$s zond jou %2$s."
-#: ../../Zotlabs/Module/Events.php:460 ../../Zotlabs/Module/Events.php:463
-msgid "Finish date and time are not known or not relevant"
-msgstr "Einddatum en -tijd zijn niet bekend of niet van toepassing"
+#: ../../Zotlabs/Lib/Enotify.php:123
+msgid "a private message"
+msgstr "een privébericht"
-#: ../../Zotlabs/Module/Events.php:462
-msgid "Edit finish date and time"
-msgstr "Einddatum en -tijd bewerken"
+#: ../../Zotlabs/Lib/Enotify.php:124
+#, php-format
+msgid "Please visit %s to view and/or reply to your private messages."
+msgstr "Bezoek %s om je privéberichten te bekijken en/of er op te reageren."
-#: ../../Zotlabs/Module/Events.php:462
-msgid "Finish date and time"
-msgstr "Einddatum en -tijd"
+#: ../../Zotlabs/Lib/Enotify.php:183
+#, php-format
+msgid "%1$s, %2$s commented on [zrl=%3$s]a %4$s[/zrl]"
+msgstr "%1$s, %2$s gaf een reactie op [zrl=%3$s]een %4$s[/zrl]"
-#: ../../Zotlabs/Module/Events.php:464 ../../Zotlabs/Module/Events.php:465
-msgid "Adjust for viewer timezone"
-msgstr "Aanpassen aan de tijdzone van wie deze gebeurtenis bekijkt"
+#: ../../Zotlabs/Lib/Enotify.php:191
+#, php-format
+msgid "%1$s, %2$s commented on [zrl=%3$s]%4$s's %5$s[/zrl]"
+msgstr "%1$s, %2$s gaf een reactie op [zrl=%3$s]een %5$s van %4$s[/zrl]"
-#: ../../Zotlabs/Module/Events.php:464
-msgid ""
-"Important for events that happen in a particular place. Not practical for "
-"global holidays."
-msgstr "Belangrijk voor gebeurtenissen die op een bepaalde locatie plaatsvinden. Niet praktisch voor wereldwijde feestdagen."
+#: ../../Zotlabs/Lib/Enotify.php:200
+#, php-format
+msgid "%1$s, %2$s commented on [zrl=%3$s]your %4$s[/zrl]"
+msgstr "%1$s, %2$s gaf een reactie op [zrl=%3$s]jouw %4$s[/zrl]"
-#: ../../Zotlabs/Module/Events.php:466
-msgid "Edit Description"
-msgstr "Omschrijving bewerken"
+#: ../../Zotlabs/Lib/Enotify.php:211
+#, php-format
+msgid "[$Projectname:Notify] Comment to conversation #%1$d by %2$s"
+msgstr "[$Projectname:Notificatie] %2$s gaf een reactie in conversatie #%1$d"
-#: ../../Zotlabs/Module/Events.php:468
-msgid "Edit Location"
-msgstr "Locatie bewerken"
+#: ../../Zotlabs/Lib/Enotify.php:212
+#, php-format
+msgid "%1$s, %2$s commented on an item/conversation you have been following."
+msgstr "%1$s, %2$s gaf een reactie in een conversatie die jij volgt."
-#: ../../Zotlabs/Module/Events.php:472 ../../include/conversation.php:1262
-msgid "Permission settings"
-msgstr "Permissies"
+#: ../../Zotlabs/Lib/Enotify.php:215 ../../Zotlabs/Lib/Enotify.php:292
+#: ../../Zotlabs/Lib/Enotify.php:309 ../../Zotlabs/Lib/Enotify.php:335
+#: ../../Zotlabs/Lib/Enotify.php:353 ../../Zotlabs/Lib/Enotify.php:367
+#, php-format
+msgid "Please visit %s to view and/or reply to the conversation."
+msgstr "Bezoek %s om de conversatie te bekijken en/of er op te reageren."
-#: ../../Zotlabs/Module/Events.php:485
-msgid "Advanced Options"
-msgstr "Geavanceerde opties"
+#: ../../Zotlabs/Lib/Enotify.php:273
+#, php-format
+msgid "%1$s, %2$s liked [zrl=%3$s]your %4$s[/zrl]"
+msgstr "%1$s, %2$s vindt [zrl=%3$s]jouw %4$s[/zrl] leuk"
-#: ../../Zotlabs/Module/Events.php:624
-msgid "Edit event"
-msgstr "Gebeurtenis bewerken"
+#: ../../Zotlabs/Lib/Enotify.php:288
+#, php-format
+msgid "[$Projectname:Notify] Like received to conversation #%1$d by %2$s"
+msgstr "[$Projectname:Notificatie] %2$s vindt iets leuk in conversatie #%1$d"
-#: ../../Zotlabs/Module/Events.php:626
-msgid "Delete event"
-msgstr "Gebeurtenis verwijderen"
+#: ../../Zotlabs/Lib/Enotify.php:289
+#, php-format
+msgid "%1$s, %2$s liked an item/conversation you created."
+msgstr "%1$s, %2$s vindt iets leuk in een conversatie die jij bent gestart."
-#: ../../Zotlabs/Module/Events.php:660
-msgid "calendar"
-msgstr "agenda"
+#: ../../Zotlabs/Lib/Enotify.php:300
+#, php-format
+msgid "[$Projectname:Notify] %s posted to your profile wall"
+msgstr "[$Projectname:Notificatie] %s heeft een bericht op jouw kanaal geplaatst"
-#: ../../Zotlabs/Module/Events.php:686
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:849
-msgid "Month"
-msgstr "Maand"
+#: ../../Zotlabs/Lib/Enotify.php:302
+#, php-format
+msgid "%1$s, %2$s posted to your profile wall at %3$s"
+msgstr "%1$s, %2$s heeft om %3$s een bericht op jouw kanaal geplaatst"
-#: ../../Zotlabs/Module/Events.php:687
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:850
-msgid "Week"
-msgstr "Week"
+#: ../../Zotlabs/Lib/Enotify.php:304
+#, php-format
+msgid "%1$s, %2$s posted to [zrl=%3$s]your wall[/zrl]"
+msgstr "%1$s, %2$s heeft een bericht op [zrl=%3$s]jouw kanaal[/zrl] geplaatst"
-#: ../../Zotlabs/Module/Events.php:688
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:851
-msgid "Day"
-msgstr "Dag"
+#: ../../Zotlabs/Lib/Enotify.php:328
+#, php-format
+msgid "[$Projectname:Notify] %s tagged you"
+msgstr "[$Projectname:Notificatie] %s heeft jou genoemd"
-#: ../../Zotlabs/Module/Events.php:722
-msgid "Event removed"
-msgstr "Gebeurtenis verwijderd"
+#: ../../Zotlabs/Lib/Enotify.php:329
+#, php-format
+msgid "%1$s, %2$s tagged you at %3$s"
+msgstr "%1$s, %2$s noemde jou op %3$s"
-#: ../../Zotlabs/Module/Events.php:725
-msgid "Failed to remove event"
-msgstr "Verwijderen gebeurtenis mislukt"
+#: ../../Zotlabs/Lib/Enotify.php:330
+#, php-format
+msgid "%1$s, %2$s [zrl=%3$s]tagged you[/zrl]."
+msgstr "%1$s, %2$s [zrl=%3$s]noemde jou[/zrl]."
-#: ../../Zotlabs/Lib/Chatroom.php:27
-msgid "Missing room name"
-msgstr "Naam chatkanaal ontbreekt"
+#: ../../Zotlabs/Lib/Enotify.php:342
+#, php-format
+msgid "[$Projectname:Notify] %1$s poked you"
+msgstr "[$Projectname:Notificatie] %1$s heeft jou aangestoten"
-#: ../../Zotlabs/Lib/Chatroom.php:36
-msgid "Duplicate room name"
-msgstr "Naam chatkanaal bestaat al"
+#: ../../Zotlabs/Lib/Enotify.php:343
+#, php-format
+msgid "%1$s, %2$s poked you at %3$s"
+msgstr "%1$s, %2$s heeft je aangestoten op %3$s"
-#: ../../Zotlabs/Lib/Chatroom.php:86 ../../Zotlabs/Lib/Chatroom.php:94
-msgid "Invalid room specifier."
-msgstr "Ongeldige omschrijving chatkanaal"
+#: ../../Zotlabs/Lib/Enotify.php:344
+#, php-format
+msgid "%1$s, %2$s [zrl=%2$s]poked you[/zrl]."
+msgstr "%1$s, %2$s [zrl=%2$s]heeft je aangestoten[/zrl]."
-#: ../../Zotlabs/Lib/Chatroom.php:126
-msgid "Room not found."
-msgstr "Chatkanaal niet gevonden"
+#: ../../Zotlabs/Lib/Enotify.php:360
+#, php-format
+msgid "[$Projectname:Notify] %s tagged your post"
+msgstr "[$Projectname:Notificatie] %s heeft jouw bericht getagd"
-#: ../../Zotlabs/Lib/Chatroom.php:147
-msgid "Room is full"
-msgstr "Chatkanaal is vol"
+#: ../../Zotlabs/Lib/Enotify.php:361
+#, php-format
+msgid "%1$s, %2$s tagged your post at %3$s"
+msgstr "%1$s, %2$s heeft jouw bericht om %3$s getagd"
+
+#: ../../Zotlabs/Lib/Enotify.php:362
+#, php-format
+msgid "%1$s, %2$s tagged [zrl=%3$s]your post[/zrl]"
+msgstr "%1$s, %2$s heeft [zrl=%3$s]jouw bericht[/zrl] getagd"
+
+#: ../../Zotlabs/Lib/Enotify.php:374
+msgid "[$Projectname:Notify] Introduction received"
+msgstr "[$Projectname:Notificatie] Connectieverzoek ontvangen"
+
+#: ../../Zotlabs/Lib/Enotify.php:375
+#, php-format
+msgid "%1$s, you've received an new connection request from '%2$s' at %3$s"
+msgstr "%1$s, je hebt een nieuw connectieverzoek ontvangen van '%2$s' op %3$s"
+
+#: ../../Zotlabs/Lib/Enotify.php:376
+#, php-format
+msgid ""
+"%1$s, you've received [zrl=%2$s]a new connection request[/zrl] from %3$s."
+msgstr "%1$s, je hebt een [zrl=%2$s]nieuw connectieverzoek[/zrl] ontvangen van %3$s."
+
+#: ../../Zotlabs/Lib/Enotify.php:380 ../../Zotlabs/Lib/Enotify.php:399
+#, php-format
+msgid "You may visit their profile at %s"
+msgstr "Je kan het profiel bekijken op %s"
+
+#: ../../Zotlabs/Lib/Enotify.php:382
+#, php-format
+msgid "Please visit %s to approve or reject the connection request."
+msgstr "Bezoek %s om het connectieverzoek te accepteren of af te wijzen."
+
+#: ../../Zotlabs/Lib/Enotify.php:389
+msgid "[$Projectname:Notify] Friend suggestion received"
+msgstr "[$Projectname:Notificatie] Kanaalvoorstel ontvangen"
+
+#: ../../Zotlabs/Lib/Enotify.php:390
+#, php-format
+msgid "%1$s, you've received a friend suggestion from '%2$s' at %3$s"
+msgstr "%1$s, je hebt een kanaalvoorstel ontvangen van '%2$s' om %3$s"
+
+#: ../../Zotlabs/Lib/Enotify.php:391
+#, php-format
+msgid ""
+"%1$s, you've received [zrl=%2$s]a friend suggestion[/zrl] for %3$s from "
+"%4$s."
+msgstr "%1$s, je hebt [zrl=%2$s]een kanaalvoorstel[/zrl] ontvangen voor %3$s van %4$s."
+
+#: ../../Zotlabs/Lib/Enotify.php:397
+msgid "Name:"
+msgstr "Naam:"
+
+#: ../../Zotlabs/Lib/Enotify.php:398
+msgid "Photo:"
+msgstr "Foto:"
+
+#: ../../Zotlabs/Lib/Enotify.php:401
+#, php-format
+msgid "Please visit %s to approve or reject the suggestion."
+msgstr "Bezoek %s om het voorstel te accepteren of af te wijzen."
+
+#: ../../Zotlabs/Lib/Enotify.php:619
+msgid "[$Projectname:Notify]"
+msgstr "[$Projectname:Notificatie]"
+
+#: ../../Zotlabs/Lib/Enotify.php:779
+msgid "created a new post"
+msgstr "maakte een nieuw bericht aan"
+
+#: ../../Zotlabs/Lib/Enotify.php:780
+#, php-format
+msgid "commented on %s's post"
+msgstr "gaf een reactie op een bericht van %s"
#: ../../Zotlabs/Lib/PermissionDescription.php:34
#: ../../include/acl_selectors.php:128
@@ -6972,7 +7492,7 @@ msgid "Visible to your default audience"
msgstr "Voor iedereen zichtbaar, mits niet anders ingesteld"
#: ../../Zotlabs/Lib/PermissionDescription.php:107
-#: ../../include/acl_selectors.php:191
+#: ../../include/acl_selectors.php:201
msgid "Only me"
msgstr "Alleen ik"
@@ -7029,6 +7549,89 @@ msgstr "Dit is de standaard privacy-instelling voor wie jouw bestanden en foto's
msgid "This is your default setting for the audience of your webpages"
msgstr "Dit is de standaard privacy-instelling voor wie jouw webpagina's kan bekijken"
+#: ../../Zotlabs/Lib/NativeWikiPage.php:31
+#: ../../Zotlabs/Lib/NativeWikiPage.php:70
+msgid "(No Title)"
+msgstr "(Geen titel)"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:84
+msgid "Wiki page create failed."
+msgstr "Aanmaken wiki-pagina mislukt."
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:97
+msgid "Wiki not found."
+msgstr "Wiki niet gevonden"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:108
+msgid "Destination name already exists"
+msgstr "Naam van doel bestaat al"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:134
+#: ../../Zotlabs/Lib/NativeWikiPage.php:361
+msgid "Page not found"
+msgstr "Pagina niet gevonden"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:164
+msgid "Error reading page content"
+msgstr "Fout tijdens lezen pagina-inhoud"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:346
+#: ../../Zotlabs/Lib/NativeWikiPage.php:399
+#: ../../Zotlabs/Lib/NativeWikiPage.php:466
+#: ../../Zotlabs/Lib/NativeWikiPage.php:507
+msgid "Error reading wiki"
+msgstr "Fout tijdens lezen wiki"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:387
+msgid "Page update failed."
+msgstr "Bijwerken van pagina mislukt."
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:421
+msgid "Nothing deleted"
+msgstr "Niets verwijderd"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:487
+msgid "Compare: object not found."
+msgstr "Vergelijken: object niet gevonden."
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:493
+msgid "Page updated"
+msgstr "Pagina bijgewerkt"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:496
+msgid "Untitled"
+msgstr "Naamloos"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:502
+msgid "Wiki resource_id required for git commit"
+msgstr "Resource_id wiki voor git commit vereist"
+
+#: ../../Zotlabs/Lib/NativeWikiPage.php:573
+#: ../../extend/addon/addon/gitwiki/gitwiki_backend.php:579
+#: ../../include/bbcode.php:610 ../../include/bbcode.php:756
+msgid "Different viewers will see this text differently"
+msgstr "Deze tekst wordt per persoon anders weergeven."
+
+#: ../../Zotlabs/Lib/Permcat.php:58
+msgctxt "permcat"
+msgid "default"
+msgstr "standaard"
+
+#: ../../Zotlabs/Lib/Permcat.php:96
+msgctxt "permcat"
+msgid "follower"
+msgstr "volger"
+
+#: ../../Zotlabs/Lib/Permcat.php:100
+msgctxt "permcat"
+msgid "contributor"
+msgstr "bijdrager"
+
+#: ../../Zotlabs/Lib/Permcat.php:104
+msgctxt "permcat"
+msgid "publisher"
+msgstr "publichist "
+
#: ../../Zotlabs/Lib/ThreadItem.php:95 ../../include/conversation.php:663
msgid "Private Message"
msgstr "Niet voor iedereen zichtbaar"
@@ -7141,417 +7744,206 @@ msgstr "Kanaal-naar-kanaal"
msgid "via Wall-To-Wall:"
msgstr "via kanaal-naar-kanaal"
-#: ../../Zotlabs/Lib/ThreadItem.php:348 ../../include/conversation.php:716
+#: ../../Zotlabs/Lib/ThreadItem.php:350 ../../include/conversation.php:717
#, php-format
msgid "from %s"
msgstr "van %s"
-#: ../../Zotlabs/Lib/ThreadItem.php:351 ../../include/conversation.php:719
+#: ../../Zotlabs/Lib/ThreadItem.php:353 ../../include/conversation.php:720
#, php-format
msgid "last edited: %s"
msgstr "laatst bewerkt: %s"
-#: ../../Zotlabs/Lib/ThreadItem.php:352 ../../include/conversation.php:720
+#: ../../Zotlabs/Lib/ThreadItem.php:354 ../../include/conversation.php:721
#, php-format
msgid "Expires: %s"
msgstr "Verloopt: %s"
-#: ../../Zotlabs/Lib/ThreadItem.php:358
+#: ../../Zotlabs/Lib/ThreadItem.php:360
msgid "Attend"
msgstr "Aanwezig"
-#: ../../Zotlabs/Lib/ThreadItem.php:359
+#: ../../Zotlabs/Lib/ThreadItem.php:361
msgid "Attendance Options"
msgstr "Aanwezigheidsopties"
-#: ../../Zotlabs/Lib/ThreadItem.php:360
+#: ../../Zotlabs/Lib/ThreadItem.php:362
msgid "Vote"
msgstr "Stem"
-#: ../../Zotlabs/Lib/ThreadItem.php:361
+#: ../../Zotlabs/Lib/ThreadItem.php:363
msgid "Voting Options"
msgstr "Stemopties"
-#: ../../Zotlabs/Lib/ThreadItem.php:381
+#: ../../Zotlabs/Lib/ThreadItem.php:383
#: ../../extend/addon/addon/bookmarker/bookmarker.php:38
msgid "Save Bookmarks"
msgstr "Bladwijzers opslaan"
-#: ../../Zotlabs/Lib/ThreadItem.php:382
+#: ../../Zotlabs/Lib/ThreadItem.php:384
msgid "Add to Calendar"
msgstr "Aan agenda toevoegen"
-#: ../../Zotlabs/Lib/ThreadItem.php:391
+#: ../../Zotlabs/Lib/ThreadItem.php:393
msgid "Mark all seen"
msgstr "Markeer alles als bekeken"
-#: ../../Zotlabs/Lib/ThreadItem.php:440 ../../include/js_strings.php:7
+#: ../../Zotlabs/Lib/ThreadItem.php:442 ../../include/js_strings.php:7
#, php-format
msgid "%s show all"
msgstr "%s alle"
-#: ../../Zotlabs/Lib/ThreadItem.php:730 ../../include/conversation.php:1237
+#: ../../Zotlabs/Lib/ThreadItem.php:732 ../../include/conversation.php:1385
msgid "Bold"
msgstr "Vet"
-#: ../../Zotlabs/Lib/ThreadItem.php:731 ../../include/conversation.php:1238
+#: ../../Zotlabs/Lib/ThreadItem.php:733 ../../include/conversation.php:1386
msgid "Italic"
msgstr "Cursief"
-#: ../../Zotlabs/Lib/ThreadItem.php:732 ../../include/conversation.php:1239
+#: ../../Zotlabs/Lib/ThreadItem.php:734 ../../include/conversation.php:1387
msgid "Underline"
msgstr "Onderstrepen"
-#: ../../Zotlabs/Lib/ThreadItem.php:733 ../../include/conversation.php:1240
+#: ../../Zotlabs/Lib/ThreadItem.php:735 ../../include/conversation.php:1388
msgid "Quote"
msgstr "Citeren"
-#: ../../Zotlabs/Lib/ThreadItem.php:734 ../../include/conversation.php:1241
+#: ../../Zotlabs/Lib/ThreadItem.php:736 ../../include/conversation.php:1389
msgid "Code"
msgstr "Broncode"
-#: ../../Zotlabs/Lib/ThreadItem.php:735
+#: ../../Zotlabs/Lib/ThreadItem.php:737
msgid "Image"
msgstr "Afbeelding"
-#: ../../Zotlabs/Lib/ThreadItem.php:736
+#: ../../Zotlabs/Lib/ThreadItem.php:738
msgid "Insert Link"
msgstr "Link invoegen"
-#: ../../Zotlabs/Lib/ThreadItem.php:737
+#: ../../Zotlabs/Lib/ThreadItem.php:739
msgid "Video"
msgstr "Video"
-#: ../../Zotlabs/Lib/Apps.php:207
+#: ../../Zotlabs/Lib/NativeWiki.php:126
+msgid "Wiki files deleted successfully"
+msgstr "Verwijderen wiki-bestanden geslaagd"
+
+#: ../../Zotlabs/Lib/Apps.php:212
msgid "Site Admin"
msgstr "Hubbeheerder"
-#: ../../Zotlabs/Lib/Apps.php:208
+#: ../../Zotlabs/Lib/Apps.php:213
#: ../../extend/addon/addon/buglink/buglink.php:16
msgid "Report Bug"
msgstr "Bugrapport indienen"
-#: ../../Zotlabs/Lib/Apps.php:209
+#: ../../Zotlabs/Lib/Apps.php:214
msgid "View Bookmarks"
msgstr "Bladwijzers bekijken"
-#: ../../Zotlabs/Lib/Apps.php:210
+#: ../../Zotlabs/Lib/Apps.php:215
msgid "My Chatrooms"
msgstr "Mijn chatkanalen"
-#: ../../Zotlabs/Lib/Apps.php:212
+#: ../../Zotlabs/Lib/Apps.php:217
msgid "Firefox Share"
msgstr "Firefox Share"
-#: ../../Zotlabs/Lib/Apps.php:213
+#: ../../Zotlabs/Lib/Apps.php:218
msgid "Remote Diagnostics"
msgstr "Diagnose op afstand"
-#: ../../Zotlabs/Lib/Apps.php:214 ../../include/features.php:319
+#: ../../Zotlabs/Lib/Apps.php:219 ../../include/features.php:337
msgid "Suggest Channels"
msgstr "Kanalen voorstellen"
-#: ../../Zotlabs/Lib/Apps.php:215 ../../include/nav.php:115
-#: ../../boot.php:1720
+#: ../../Zotlabs/Lib/Apps.php:220 ../../include/nav.php:130
+#: ../../boot.php:1749
msgid "Login"
msgstr "Inloggen"
-#: ../../Zotlabs/Lib/Apps.php:217 ../../include/nav.php:182
+#: ../../Zotlabs/Lib/Apps.php:222 ../../include/nav.php:194
msgid "Grid"
msgstr "Grid"
-#: ../../Zotlabs/Lib/Apps.php:221 ../../include/features.php:99
-#: ../../include/conversation.php:1740
+#: ../../Zotlabs/Lib/Apps.php:226 ../../include/conversation.php:1903
+#: ../../include/features.php:99
msgid "Wiki"
msgstr "Wiki"
-#: ../../Zotlabs/Lib/Apps.php:222 ../../include/nav.php:185
+#: ../../Zotlabs/Lib/Apps.php:227 ../../include/nav.php:198
msgid "Channel Home"
msgstr "Jouw kanaal"
-#: ../../Zotlabs/Lib/Apps.php:225 ../../include/nav.php:204
-#: ../../include/conversation.php:1691 ../../include/conversation.php:1694
+#: ../../Zotlabs/Lib/Apps.php:230 ../../include/conversation.php:1853
+#: ../../include/conversation.php:1856 ../../include/nav.php:218
msgid "Events"
msgstr "Agenda"
-#: ../../Zotlabs/Lib/Apps.php:226 ../../include/nav.php:170
+#: ../../Zotlabs/Lib/Apps.php:231 ../../include/nav.php:182
msgid "Directory"
msgstr "Kanalengids"
-#: ../../Zotlabs/Lib/Apps.php:228 ../../include/nav.php:196
+#: ../../Zotlabs/Lib/Apps.php:233 ../../include/nav.php:210
msgid "Mail"
msgstr "Privéberichten"
-#: ../../Zotlabs/Lib/Apps.php:231 ../../include/nav.php:99
+#: ../../Zotlabs/Lib/Apps.php:236
msgid "Chat"
msgstr "Chatten"
-#: ../../Zotlabs/Lib/Apps.php:233
+#: ../../Zotlabs/Lib/Apps.php:238
msgid "Probe"
msgstr "Onderzoeken"
-#: ../../Zotlabs/Lib/Apps.php:234
+#: ../../Zotlabs/Lib/Apps.php:239
msgid "Suggest"
msgstr "Voorstellen"
-#: ../../Zotlabs/Lib/Apps.php:235
+#: ../../Zotlabs/Lib/Apps.php:240
msgid "Random Channel"
msgstr "Willekeurig kanaal"
-#: ../../Zotlabs/Lib/Apps.php:236
+#: ../../Zotlabs/Lib/Apps.php:241
msgid "Invite"
msgstr "Uitnodigen "
-#: ../../Zotlabs/Lib/Apps.php:237 ../../include/widgets.php:1565
+#: ../../Zotlabs/Lib/Apps.php:242 ../../include/widgets.php:1638
msgid "Features"
msgstr "Extra functies"
-#: ../../Zotlabs/Lib/Apps.php:238
+#: ../../Zotlabs/Lib/Apps.php:243
#: ../../extend/addon/addon/openid/MysqlProvider.php:69
msgid "Language"
msgstr "Taal"
-#: ../../Zotlabs/Lib/Apps.php:239
+#: ../../Zotlabs/Lib/Apps.php:244
msgid "Post"
msgstr "Bericht"
-#: ../../Zotlabs/Lib/Apps.php:240
+#: ../../Zotlabs/Lib/Apps.php:245
#: ../../extend/addon/addon/openid/MysqlProvider.php:58
#: ../../extend/addon/addon/openid/MysqlProvider.php:59
#: ../../extend/addon/addon/openid/MysqlProvider.php:60
msgid "Profile Photo"
msgstr "Profielfoto"
-#: ../../Zotlabs/Lib/Apps.php:344
+#: ../../Zotlabs/Lib/Apps.php:355
msgid "Purchase"
msgstr "Aanschaffen"
-#: ../../Zotlabs/Lib/Apps.php:348
+#: ../../Zotlabs/Lib/Apps.php:359
msgid "Undelete"
msgstr "Verwijdering ongedaan maken"
-#: ../../Zotlabs/Lib/Enotify.php:60 ../../include/network.php:1914
-msgid "$Projectname Notification"
-msgstr "$Projectname-notificatie"
-
-#: ../../Zotlabs/Lib/Enotify.php:61 ../../extend/addon/addon/diaspora/p.php:46
-#: ../../extend/addon/addon/diaspora/util.php:218
-#: ../../extend/addon/addon/diaspora/util.php:231
-#: ../../include/network.php:1915
-msgid "$projectname"
-msgstr "$projectname"
-
-#: ../../Zotlabs/Lib/Enotify.php:63 ../../include/network.php:1917
-msgid "Thank You,"
-msgstr "Bedankt,"
-
-#: ../../Zotlabs/Lib/Enotify.php:65 ../../include/network.php:1919
-#, php-format
-msgid "%s Administrator"
-msgstr "Beheerder %s"
-
-#: ../../Zotlabs/Lib/Enotify.php:116
-#, php-format
-msgid "%s <!item_type!>"
-msgstr "%s <!item_type!>"
-
-#: ../../Zotlabs/Lib/Enotify.php:120
-#, php-format
-msgid "[$Projectname:Notify] New mail received at %s"
-msgstr "[$Projectname:Notificatie] Nieuw privébericht ontvangen op %s"
-
-#: ../../Zotlabs/Lib/Enotify.php:122
-#, php-format
-msgid "%1$s, %2$s sent you a new private message at %3$s."
-msgstr "%1$s, %2$s zond jou een nieuw privébericht om %3$s."
-
-#: ../../Zotlabs/Lib/Enotify.php:123
-#, php-format
-msgid "%1$s sent you %2$s."
-msgstr "%1$s zond jou %2$s."
+#: ../../Zotlabs/Lib/Apps.php:364
+msgid "Add to app-tray"
+msgstr "Aan appmenu toevoegen"
-#: ../../Zotlabs/Lib/Enotify.php:123
-msgid "a private message"
-msgstr "een privébericht"
-
-#: ../../Zotlabs/Lib/Enotify.php:124
-#, php-format
-msgid "Please visit %s to view and/or reply to your private messages."
-msgstr "Bezoek %s om je privéberichten te bekijken en/of er op te reageren."
-
-#: ../../Zotlabs/Lib/Enotify.php:183
-#, php-format
-msgid "%1$s, %2$s commented on [zrl=%3$s]a %4$s[/zrl]"
-msgstr "%1$s, %2$s gaf een reactie op [zrl=%3$s]een %4$s[/zrl]"
-
-#: ../../Zotlabs/Lib/Enotify.php:191
-#, php-format
-msgid "%1$s, %2$s commented on [zrl=%3$s]%4$s's %5$s[/zrl]"
-msgstr "%1$s, %2$s gaf een reactie op [zrl=%3$s]een %5$s van %4$s[/zrl]"
-
-#: ../../Zotlabs/Lib/Enotify.php:200
-#, php-format
-msgid "%1$s, %2$s commented on [zrl=%3$s]your %4$s[/zrl]"
-msgstr "%1$s, %2$s gaf een reactie op [zrl=%3$s]jouw %4$s[/zrl]"
-
-#: ../../Zotlabs/Lib/Enotify.php:211
-#, php-format
-msgid "[$Projectname:Notify] Comment to conversation #%1$d by %2$s"
-msgstr "[$Projectname:Notificatie] %2$s gaf een reactie in conversatie #%1$d"
-
-#: ../../Zotlabs/Lib/Enotify.php:212
-#, php-format
-msgid "%1$s, %2$s commented on an item/conversation you have been following."
-msgstr "%1$s, %2$s gaf een reactie in een conversatie die jij volgt."
-
-#: ../../Zotlabs/Lib/Enotify.php:215 ../../Zotlabs/Lib/Enotify.php:292
-#: ../../Zotlabs/Lib/Enotify.php:309 ../../Zotlabs/Lib/Enotify.php:335
-#: ../../Zotlabs/Lib/Enotify.php:353 ../../Zotlabs/Lib/Enotify.php:367
-#, php-format
-msgid "Please visit %s to view and/or reply to the conversation."
-msgstr "Bezoek %s om de conversatie te bekijken en/of er op te reageren."
-
-#: ../../Zotlabs/Lib/Enotify.php:273
-#, php-format
-msgid "%1$s, %2$s liked [zrl=%3$s]your %4$s[/zrl]"
-msgstr "%1$s, %2$s vindt [zrl=%3$s]jouw %4$s[/zrl] leuk"
-
-#: ../../Zotlabs/Lib/Enotify.php:288
-#, php-format
-msgid "[$Projectname:Notify] Like received to conversation #%1$d by %2$s"
-msgstr "[$Projectname:Notificatie] %2$s vindt iets leuk in conversatie #%1$d"
-
-#: ../../Zotlabs/Lib/Enotify.php:289
-#, php-format
-msgid "%1$s, %2$s liked an item/conversation you created."
-msgstr "%1$s, %2$s vindt iets leuk in een conversatie die jij bent gestart."
-
-#: ../../Zotlabs/Lib/Enotify.php:300
-#, php-format
-msgid "[$Projectname:Notify] %s posted to your profile wall"
-msgstr "[$Projectname:Notificatie] %s heeft een bericht op jouw kanaal geplaatst"
-
-#: ../../Zotlabs/Lib/Enotify.php:302
-#, php-format
-msgid "%1$s, %2$s posted to your profile wall at %3$s"
-msgstr "%1$s, %2$s heeft om %3$s een bericht op jouw kanaal geplaatst"
-
-#: ../../Zotlabs/Lib/Enotify.php:304
-#, php-format
-msgid "%1$s, %2$s posted to [zrl=%3$s]your wall[/zrl]"
-msgstr "%1$s, %2$s heeft een bericht op [zrl=%3$s]jouw kanaal[/zrl] geplaatst"
-
-#: ../../Zotlabs/Lib/Enotify.php:328
-#, php-format
-msgid "[$Projectname:Notify] %s tagged you"
-msgstr "[$Projectname:Notificatie] %s heeft jou genoemd"
-
-#: ../../Zotlabs/Lib/Enotify.php:329
-#, php-format
-msgid "%1$s, %2$s tagged you at %3$s"
-msgstr "%1$s, %2$s noemde jou op %3$s"
-
-#: ../../Zotlabs/Lib/Enotify.php:330
-#, php-format
-msgid "%1$s, %2$s [zrl=%3$s]tagged you[/zrl]."
-msgstr "%1$s, %2$s [zrl=%3$s]noemde jou[/zrl]."
-
-#: ../../Zotlabs/Lib/Enotify.php:342
-#, php-format
-msgid "[$Projectname:Notify] %1$s poked you"
-msgstr "[$Projectname:Notificatie] %1$s heeft jou aangestoten"
-
-#: ../../Zotlabs/Lib/Enotify.php:343
-#, php-format
-msgid "%1$s, %2$s poked you at %3$s"
-msgstr "%1$s, %2$s heeft je aangestoten op %3$s"
-
-#: ../../Zotlabs/Lib/Enotify.php:344
-#, php-format
-msgid "%1$s, %2$s [zrl=%2$s]poked you[/zrl]."
-msgstr "%1$s, %2$s [zrl=%2$s]heeft je aangestoten[/zrl]."
-
-#: ../../Zotlabs/Lib/Enotify.php:360
-#, php-format
-msgid "[$Projectname:Notify] %s tagged your post"
-msgstr "[$Projectname:Notificatie] %s heeft jouw bericht getagd"
-
-#: ../../Zotlabs/Lib/Enotify.php:361
-#, php-format
-msgid "%1$s, %2$s tagged your post at %3$s"
-msgstr "%1$s, %2$s heeft jouw bericht om %3$s getagd"
-
-#: ../../Zotlabs/Lib/Enotify.php:362
-#, php-format
-msgid "%1$s, %2$s tagged [zrl=%3$s]your post[/zrl]"
-msgstr "%1$s, %2$s heeft [zrl=%3$s]jouw bericht[/zrl] getagd"
-
-#: ../../Zotlabs/Lib/Enotify.php:374
-msgid "[$Projectname:Notify] Introduction received"
-msgstr "[$Projectname:Notificatie] Connectieverzoek ontvangen"
-
-#: ../../Zotlabs/Lib/Enotify.php:375
-#, php-format
-msgid "%1$s, you've received an new connection request from '%2$s' at %3$s"
-msgstr "%1$s, je hebt een nieuw connectieverzoek ontvangen van '%2$s' op %3$s"
-
-#: ../../Zotlabs/Lib/Enotify.php:376
-#, php-format
-msgid ""
-"%1$s, you've received [zrl=%2$s]a new connection request[/zrl] from %3$s."
-msgstr "%1$s, je hebt een [zrl=%2$s]nieuw connectieverzoek[/zrl] ontvangen van %3$s."
-
-#: ../../Zotlabs/Lib/Enotify.php:380 ../../Zotlabs/Lib/Enotify.php:399
-#, php-format
-msgid "You may visit their profile at %s"
-msgstr "Je kan het profiel bekijken op %s"
-
-#: ../../Zotlabs/Lib/Enotify.php:382
-#, php-format
-msgid "Please visit %s to approve or reject the connection request."
-msgstr "Bezoek %s om het connectieverzoek te accepteren of af te wijzen."
-
-#: ../../Zotlabs/Lib/Enotify.php:389
-msgid "[$Projectname:Notify] Friend suggestion received"
-msgstr "[$Projectname:Notificatie] Kanaalvoorstel ontvangen"
-
-#: ../../Zotlabs/Lib/Enotify.php:390
-#, php-format
-msgid "%1$s, you've received a friend suggestion from '%2$s' at %3$s"
-msgstr "%1$s, je hebt een kanaalvoorstel ontvangen van '%2$s' om %3$s"
-
-#: ../../Zotlabs/Lib/Enotify.php:391
-#, php-format
-msgid ""
-"%1$s, you've received [zrl=%2$s]a friend suggestion[/zrl] for %3$s from "
-"%4$s."
-msgstr "%1$s, je hebt [zrl=%2$s]een kanaalvoorstel[/zrl] ontvangen voor %3$s van %4$s."
-
-#: ../../Zotlabs/Lib/Enotify.php:397
-msgid "Name:"
-msgstr "Naam:"
-
-#: ../../Zotlabs/Lib/Enotify.php:398
-msgid "Photo:"
-msgstr "Foto:"
-
-#: ../../Zotlabs/Lib/Enotify.php:401
-#, php-format
-msgid "Please visit %s to approve or reject the suggestion."
-msgstr "Bezoek %s om het voorstel te accepteren of af te wijzen."
-
-#: ../../Zotlabs/Lib/Enotify.php:619
-msgid "[$Projectname:Notify]"
-msgstr "[$Projectname:Notificatie]"
-
-#: ../../Zotlabs/Lib/Enotify.php:779
-msgid "created a new post"
-msgstr "maakte een nieuw bericht aan"
-
-#: ../../Zotlabs/Lib/Enotify.php:780
-#, php-format
-msgid "commented on %s's post"
-msgstr "gaf een reactie op een bericht van %s"
+#: ../../Zotlabs/Lib/Apps.php:365
+msgid "Remove from app-tray"
+msgstr "Uit appmenu verwijderen"
#: ../../extend/addon/addon/adultphotoflag/adultphotoflag.php:24
msgid "Flag Adult Photos"
@@ -7609,27 +8001,36 @@ msgstr "Toon voor linkshandige gitaar"
msgid "Quick Reference"
msgstr "Beknopt overzicht"
-#: ../../extend/addon/addon/diaspora/diaspora.php:671
+#: ../../extend/addon/addon/diaspora/import_diaspora.php:16
+msgid "No username found in import file."
+msgstr "Geen gebruikersnaam in het importbestand gevonden."
+
+#: ../../extend/addon/addon/diaspora/import_diaspora.php:41
+#: ../../include/import.php:51
+msgid "Unable to create a unique channel address. Import failed."
+msgstr "Niet in staat om een uniek kanaaladres aan te maken. Importeren is mislukt."
+
+#: ../../extend/addon/addon/diaspora/diaspora.php:677
msgid "Diaspora Protocol Settings updated."
msgstr "Diaspora-protocol-instellingen bijgewerkt."
-#: ../../extend/addon/addon/diaspora/diaspora.php:692
+#: ../../extend/addon/addon/diaspora/diaspora.php:696
msgid "Enable the Diaspora protocol for this channel"
msgstr "Het Diaspora-protocol voor dit kanaal inschakelen"
-#: ../../extend/addon/addon/diaspora/diaspora.php:696
+#: ../../extend/addon/addon/diaspora/diaspora.php:700
msgid "Allow any Diaspora member to comment on your public posts"
msgstr "Geef elk Diaspora-lid toestemming om op jouw openbare berichten te reageren"
-#: ../../extend/addon/addon/diaspora/diaspora.php:700
+#: ../../extend/addon/addon/diaspora/diaspora.php:704
msgid "Prevent your hashtags from being redirected to other sites"
msgstr "Voorkom dat jouw hashtags naar andere websites worden doorverwezen"
-#: ../../extend/addon/addon/diaspora/diaspora.php:705
+#: ../../extend/addon/addon/diaspora/diaspora.php:709
msgid "Followed hashtags (comma separated, do not include the #)"
msgstr "Gevolgde hashtags (door komma's gescheiden lijst, zonder de #)"
-#: ../../extend/addon/addon/diaspora/diaspora.php:710
+#: ../../extend/addon/addon/diaspora/diaspora.php:714
msgid "Diaspora Protocol Settings"
msgstr "Diaspora-protocol (incl. Friendica)"
@@ -7772,7 +8173,7 @@ msgstr "Speciale dank gaat naar: "
#: ../../extend/addon/addon/dwpost/dwpost.php:42
msgid "Post to Dreamwidth"
-msgstr "Doorplaatsen naar Dreamwidth"
+msgstr "Dreamwidth"
#: ../../extend/addon/addon/dwpost/dwpost.php:73
msgid "Enable Dreamwidth Post Plugin"
@@ -7792,7 +8193,7 @@ msgstr "Standaard doorplaatsen naar Dreamwidth"
#: ../../extend/addon/addon/dwpost/dwpost.php:89
msgid "Dreamwidth Post Settings"
-msgstr "Doorplaatsen naar Dreamwidth"
+msgstr "Dreamwidth (berichten doorplaatsen)"
#: ../../extend/addon/addon/flattrwidget/flattrwidget.php:45
msgid "Flattr this!"
@@ -8112,7 +8513,7 @@ msgid "Add a personal note:"
msgstr "Add a personal note:"
#: ../../extend/addon/addon/friendica/dfrn_request.php:871
-#: ../../include/network.php:2232 ../../include/network.php:2233
+#: ../../include/network.php:2265 ../../include/network.php:2266
msgid "Friendica"
msgstr "Friendica"
@@ -8121,7 +8522,7 @@ msgid "StatusNet/Federated Social Web"
msgstr "StatusNet/Federated Social Web"
#: ../../extend/addon/addon/friendica/dfrn_request.php:873
-#: ../../include/network.php:2238
+#: ../../include/network.php:2271
msgid "Diaspora"
msgstr "Diaspora"
@@ -8141,7 +8542,7 @@ msgid "Submit Request"
msgstr "Submit Request"
#: ../../extend/addon/addon/friendica/friendica.php:113
-#: ../../extend/addon/addon/gnusoc/gnusoc.php:114
+#: ../../extend/addon/addon/gnusoc/gnusoc.php:118
msgid "GNU-Social Protocol Settings updated."
msgstr "GNU social-protocol-instellingen bijgewerkt."
@@ -8150,17 +8551,17 @@ msgid "Enable the (experimental) GNU-Social protocol for this channel"
msgstr "GNU social-protocol voor dit kanaal inschakelen (experimenteel)"
#: ../../extend/addon/addon/friendica/friendica.php:128
-#: ../../extend/addon/addon/gnusoc/gnusoc.php:129
+#: ../../extend/addon/addon/gnusoc/gnusoc.php:133
msgid "GNU-Social Protocol Settings"
msgstr "GNU social-protocol"
#: ../../extend/addon/addon/friendica/friendica.php:185
-#: ../../extend/addon/addon/gnusoc/gnusoc.php:319
+#: ../../extend/addon/addon/gnusoc/gnusoc.php:323
msgid "Follow"
msgstr "Volgen"
#: ../../extend/addon/addon/friendica/friendica.php:188
-#: ../../extend/addon/addon/gnusoc/gnusoc.php:322
+#: ../../extend/addon/addon/gnusoc/gnusoc.php:326
#, php-format
msgid "%1$s is now following %2$s"
msgstr "%1$s volgt nu %2$s"
@@ -8185,10 +8586,6 @@ msgstr "Gebruikersnaam Friendica"
msgid "Friendica Login Password"
msgstr "Wachtwoord Friendica"
-#: ../../extend/addon/addon/gnusoc/gnusoc.php:125
-msgid "Enable the GNU-Social protocol for this channel"
-msgstr "GNU social-protocol voor dit kanaal inschakelen"
-
#: ../../extend/addon/addon/hubwall/hubwall.php:19
msgid "Send email to all members"
msgstr "Naar alle leden e-mail versturen"
@@ -8227,7 +8624,7 @@ msgstr "Testmodus (alleen naar hubbeheerder sturen)"
#: ../../extend/addon/addon/ijpost/ijpost.php:42
msgid "Post to Insanejournal"
-msgstr "Doorplaatsen naar InsaneJournal"
+msgstr "InsaneJournal"
#: ../../extend/addon/addon/ijpost/ijpost.php:73
msgid "Enable InsaneJournal Post Plugin"
@@ -8247,7 +8644,7 @@ msgstr "Standaard doorplaatsen naar InsaneJournal"
#: ../../extend/addon/addon/ijpost/ijpost.php:89
msgid "InsaneJournal Post Settings"
-msgstr "Doorplaatsen naar InsaneJournal"
+msgstr "InsaneJournal (berichten doorplaatsen)"
#: ../../extend/addon/addon/ijpost/ijpost.php:104
msgid "Insane Journal Settings saved."
@@ -8280,7 +8677,7 @@ msgid "IRC Chatroom"
msgstr "IRC-chatkanaal"
#: ../../extend/addon/addon/jappixmini/jappixmini.php:305
-#: ../../include/channel.php:1056 ../../include/channel.php:1218
+#: ../../include/channel.php:1139 ../../include/channel.php:1301
msgid "Status:"
msgstr "Status:"
@@ -8330,11 +8727,6 @@ msgstr "Purge internal list of jabber addresses of contacts"
msgid "Configuration Help"
msgstr "Configuratiehulp"
-#: ../../extend/addon/addon/jappixmini/jappixmini.php:368
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1149
-msgid "Add Contact"
-msgstr "Contact toevoegen"
-
#: ../../extend/addon/addon/jappixmini/jappixmini.php:371
msgid "Jappix Mini Settings"
msgstr "Jappix Mini"
@@ -8381,7 +8773,7 @@ msgstr "Authenticatie geslaagd, maar afgekeurd: aanmaken accounts uitgeschakeld.
#: ../../extend/addon/addon/libertree/libertree.php:38
msgid "Post to Libertree"
-msgstr "Doorplaatsen naar Libertree"
+msgstr "Libertree"
#: ../../extend/addon/addon/libertree/libertree.php:69
msgid "Enable Libertree Post Plugin"
@@ -8401,7 +8793,7 @@ msgstr "Standaard doorplaatsen naar Libertree"
#: ../../extend/addon/addon/libertree/libertree.php:85
msgid "Libertree Post Settings"
-msgstr "Doorplaatsen naar Libertree"
+msgstr "Libertree (berichten doorplaatsen)"
#: ../../extend/addon/addon/libertree/libertree.php:99
msgid "Libertree Settings saved."
@@ -8409,7 +8801,7 @@ msgstr "Libertree-instellingen opgeslagen."
#: ../../extend/addon/addon/ljpost/ljpost.php:42
msgid "Post to LiveJournal"
-msgstr "Doorplaatsen naar LiveJournal"
+msgstr "LiveJournal"
#: ../../extend/addon/addon/ljpost/ljpost.php:70
msgid "Enable LiveJournal Post Plugin"
@@ -8425,11 +8817,11 @@ msgstr "Wachtwoord LiveJournal"
#: ../../extend/addon/addon/ljpost/ljpost.php:82
msgid "Post to LiveJournal by default"
-msgstr "Standaard doorplaatsen naar "
+msgstr "Standaard doorplaatsen naar LiveJournal"
#: ../../extend/addon/addon/ljpost/ljpost.php:86
msgid "LiveJournal Post Settings"
-msgstr "Doorplaatsen naar LiveJournal"
+msgstr "LiveJournal (berichten doorplaatsen)"
#: ../../extend/addon/addon/ljpost/ljpost.php:101
msgid "LiveJournal Settings saved."
@@ -8767,8 +9159,8 @@ msgid "Comma separated list of keywords to hide"
msgstr "Door komma's gescheiden lijst met woorden die gefilterd moeten worden."
#: ../../extend/addon/addon/nsfw/nsfw.php:88
-msgid "Use /expression/ to provide regular expressions"
-msgstr "Gebruik /expressie/ voor reguliere expressies"
+msgid "Word, /regular-expression/, lang=xx, lang!=xx"
+msgstr "Woord, /reguliere expressie/, lang=xx, lang!=xx"
#: ../../extend/addon/addon/nsfw/nsfw.php:92
msgid "Not Safe For Work Settings"
@@ -8788,109 +9180,109 @@ msgstr "Mogelijk inhoud voor volwassenen"
#: ../../extend/addon/addon/nsfw/nsfw.php:211
#, php-format
-msgid "%s - click to open/close"
-msgstr "%s - Klik om te openen of te sluiten"
+msgid "%s - view"
+msgstr "%s - tonen"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:49
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:127
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:50
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:128
msgid "System defaults:"
msgstr "Systeemstandaarden:"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:53
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:54
msgid "Preferred Clipart IDs"
msgstr "Voorkeursclipart"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:53
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:54
msgid "List of preferred clipart ids. These will be shown first."
msgstr "Lijst met clipartnummers die als eerste moeten worden getoond."
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:54
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:55
msgid "Default Search Term"
msgstr "Standaard zoekterm"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:54
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:55
msgid "The default search term. These will be shown second."
msgstr "Standaard zoekterm. Deze worden als tweede getoond."
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:55
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:56
msgid "Return After"
msgstr "Ga na afloop naar"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:55
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:56
msgid "Page to load after image selection."
msgstr "Pagina die na het kiezen van een afbeelding moet laden."
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:57
-#: ../../include/channel.php:965 ../../include/nav.php:93
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:58
+#: ../../include/nav.php:107 ../../include/channel.php:1048
msgid "Edit Profile"
msgstr "Profiel bewerken"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:58
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:59
msgid "Profile List"
msgstr "Profiellijst"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:60
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:61
msgid "Order of Preferred"
msgstr "Voorkeursclipart sorteren op"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:60
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:61
msgid "Sort order of preferred clipart ids."
msgstr "Als eerste getoonde clipart hierop sorteren."
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:61
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:67
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:62
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:68
msgid "Newest first"
msgstr "Nieuwste eerst"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:64
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:65
msgid "As entered"
msgstr "Zoals ingevoerd"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:66
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:67
msgid "Order of other"
msgstr "Overige clipart sorteren op"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:66
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:67
msgid "Sort order of other clipart ids."
msgstr "Overige clipart hierop sorteren."
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:68
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:69
msgid "Most downloaded first"
msgstr "Meest gedownload eerst"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:69
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:70
msgid "Most liked first"
msgstr "Meest geliked eerst"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:71
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:72
msgid "Preferred IDs Message"
msgstr "Tekst voorkeursclipart"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:71
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:72
msgid "Message to display above preferred results."
msgstr "Tekst die bovenaan de resultaten met voorkeursclipart moet worden getoond."
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:77
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:78
msgid "Uploaded by: "
msgstr "Geüpload door: "
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:77
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:78
msgid "Drawn by: "
msgstr "Getekend door: "
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:191
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:192
msgid "Or select from a free OpenClipart.org image:"
msgstr "Of kies uit een vrije OpenClipart.org-afbeelding:"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:194
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:195
msgid "Search Term"
msgstr "Zoekterm"
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:216
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:232
msgid "Unknown error. Please try again later."
msgstr "Onbekende fout. Probeer later nog eens."
-#: ../../extend/addon/addon/openclipatar/openclipatar.php:303
+#: ../../extend/addon/addon/openclipatar/openclipatar.php:308
msgid "Profile photo updated successfully."
msgstr "Bijwerken profielfoto geslaagd."
@@ -9013,7 +9405,7 @@ msgstr "Ga terug naar pagina met plugin-instellingen"
#: ../../extend/addon/addon/pumpio/pumpio.php:163
msgid "Post to Pump.io"
-msgstr "Doorplaatsen naar Pump.io"
+msgstr "Pump.io"
#: ../../extend/addon/addon/pumpio/pumpio.php:198
msgid "Pump.io servername"
@@ -9057,7 +9449,7 @@ msgstr "Alle openbare berichten doorplaatsen"
#: ../../extend/addon/addon/pumpio/pumpio.php:237
msgid "Pump.io Post Settings"
-msgstr "Doorplaatsen naar Pump.io"
+msgstr "Pump.io (berichten doorplaatsen)"
#: ../../extend/addon/addon/pumpio/pumpio.php:266
msgid "PumpIO Settings saved."
@@ -9160,16 +9552,12 @@ msgstr "0 of leeg om alles te importeren"
#: ../../extend/addon/addon/redred/redred.php:45
msgid "Post to Red"
-msgstr "Doorplaatsen naar Hubzilla"
+msgstr "Hubzilla"
#: ../../extend/addon/addon/redred/redred.php:60
msgid "Channel is required."
msgstr "Een kanaal is vereist."
-#: ../../extend/addon/addon/redred/redred.php:65
-msgid "Invalid channel."
-msgstr "Onbekend kanaal."
-
#: ../../extend/addon/addon/redred/redred.php:76
msgid "redred Settings saved."
msgstr "RedRed-instellingen opgeslagen."
@@ -9206,11 +9594,11 @@ msgstr "Bijnaam"
#: ../../extend/addon/addon/redred/redred.php:119
msgid "Hubzilla Crosspost Settings"
-msgstr "Doorplaatsen naar Hubzilla"
+msgstr "Hubzilla (berichten doorplaatsen)"
#: ../../extend/addon/addon/rtof/rtof.php:45
msgid "Post to Friendica"
-msgstr "Doorplaatsen naar Friendica"
+msgstr "Friendica"
#: ../../extend/addon/addon/rtof/rtof.php:62
msgid "rtof Settings saved."
@@ -9238,7 +9626,7 @@ msgstr "Wachtwoord Friendica"
#: ../../extend/addon/addon/rtof/rtof.php:101
msgid "Hubzilla to Friendica Post Settings"
-msgstr "Doorplaatsen naar Friendica"
+msgstr "Friendica (berichten doorplaatsen)"
#: ../../extend/addon/addon/sendzid/sendzid.php:25
msgid "Extended Identity Sharing"
@@ -9291,7 +9679,7 @@ msgstr "Startpagina"
#: ../../extend/addon/addon/statusnet/statusnet.php:143
msgid "Post to GNU social"
-msgstr "Doorplaatsen naar GNU social"
+msgstr "GNU social"
#: ../../extend/addon/addon/statusnet/statusnet.php:195
msgid ""
@@ -9419,7 +9807,7 @@ msgstr "OAuth-configuratie wissen"
#: ../../extend/addon/addon/statusnet/statusnet.php:432
msgid "GNU social Post Settings"
-msgstr "Doorplaatsen naar GNU social"
+msgstr "GNU social (berichten doorplaatsen)"
#: ../../extend/addon/addon/statusnet/statusnet.php:891
msgid "API URL"
@@ -9429,23 +9817,23 @@ msgstr "API-URL"
msgid "Application name"
msgstr "Naam applicatie"
-#: ../../extend/addon/addon/superblock/superblock.php:110
+#: ../../extend/addon/addon/superblock/superblock.php:112
msgid "Currently blocked"
msgstr "Momenteel geblokkeerd"
-#: ../../extend/addon/addon/superblock/superblock.php:112
+#: ../../extend/addon/addon/superblock/superblock.php:114
msgid "No channels currently blocked"
msgstr "Momenteel geen kanalen geblokkeerd"
-#: ../../extend/addon/addon/superblock/superblock.php:118
+#: ../../extend/addon/addon/superblock/superblock.php:120
msgid "\"Superblock\" Settings"
msgstr "Superblock"
-#: ../../extend/addon/addon/superblock/superblock.php:316
+#: ../../extend/addon/addon/superblock/superblock.php:345
msgid "Block Completely"
msgstr "Volledig blokkeren"
-#: ../../extend/addon/addon/superblock/superblock.php:361
+#: ../../extend/addon/addon/superblock/superblock.php:394
msgid "superblock settings updated"
msgstr "Superblock-instellingen bijgewerkt"
@@ -9588,7 +9976,7 @@ msgstr "Klik hier om tekst, afbeeldingen, video en audio te delen."
#: ../../extend/addon/addon/tour/tour.php:94
msgid "You can write an optional title for your update (good for long posts)."
-msgstr "Je kan optioneel een titel voor je nieuwe bericht verzinnen. Vooral goed voor langere berichten."
+msgstr "Je kan een titel voor je nieuwe bericht verzinnen, maar dit is niet verplicht. Vooral goed voor langere berichten."
#: ../../extend/addon/addon/tour/tour.php:95
msgid "Entering some categories here makes it easier to find your post later."
@@ -9672,7 +10060,7 @@ msgstr "Welkom op Hubzilla! Wil jij een rondleiding hebben langs de gebruikersin
#: ../../extend/addon/addon/twitter/twitter.php:99
msgid "Post to Twitter"
-msgstr "Doorplaatsen naar Twitter"
+msgstr "Twitter"
#: ../../extend/addon/addon/twitter/twitter.php:154
msgid "Twitter settings updated."
@@ -9731,7 +10119,7 @@ msgstr "Wanneer dit is ingeschakeld worden al jouw <strong>openbare</strong> ber
#: ../../extend/addon/addon/twitter/twitter.php:264
msgid "Twitter Post Settings"
-msgstr "Doorplaatsen naar Twitter"
+msgstr "Twitter (berichten doorplaatsen)"
#: ../../extend/addon/addon/twitter/twitter.php:773
#: ../../extend/addon/addon/rendezvous/rendezvous.php:95
@@ -9789,7 +10177,7 @@ msgstr "Wie vindt mij leuk?"
#: ../../extend/addon/addon/wppost/wppost.php:45
msgid "Post to WordPress"
-msgstr "Doorplaatsen naar WordPress"
+msgstr "WordPress"
#: ../../extend/addon/addon/wppost/wppost.php:82
msgid "Enable WordPress Post Plugin"
@@ -9829,7 +10217,7 @@ msgstr "Reacties doorplaatsen (Hubzilla_WP-plugin vereist)"
#: ../../extend/addon/addon/wppost/wppost.php:113
msgid "WordPress Post Settings"
-msgstr "Doorplaatsen naar WordPress"
+msgstr "WordPress (berichten doorplaatsen)"
#: ../../extend/addon/addon/wppost/wppost.php:129
msgid "Wordpress Settings saved."
@@ -9946,71 +10334,6 @@ msgstr "Importeren"
msgid "Select an addressbook to import to"
msgstr "Kies een adresboek om te importeren"
-#: ../../extend/addon/addon/cdav/cdav.php:36
-msgid "Errors encountered creating database table: "
-msgstr "Fouten opgetreden tijdens aanmaken databasetabel: "
-
-#: ../../extend/addon/addon/cdav/cdav.php:197
-msgid "Default Calendar"
-msgstr "Standaard agenda"
-
-#: ../../extend/addon/addon/cdav/cdav.php:206
-msgid "Default Addressbook"
-msgstr "Standaard adresboek"
-
-#: ../../extend/addon/addon/cdav/cdav.php:215
-msgid "CalDAV/CardDAV Settings saved."
-msgstr "CalDAV/CardDAV-instellingen opgeslagen."
-
-#: ../../extend/addon/addon/cdav/cdav.php:234
-msgid "Enable CalDAV/CardDAV Server for this channel"
-msgstr "CalDAV/CardDAV-server voor dit kanaal inschakelen"
-
-#: ../../extend/addon/addon/cdav/cdav.php:237
-#, php-format
-msgid "Your CalDAV resources are located at %s "
-msgstr "Jouw CalDAV-URL is %s "
-
-#: ../../extend/addon/addon/cdav/cdav.php:240
-#, php-format
-msgid "Your CardDAV resources are located at %s "
-msgstr "Jouw CardDAV-URL is %s "
-
-#: ../../extend/addon/addon/cdav/cdav.php:246
-msgid "CalDAV/CardDAV Settings"
-msgstr "CalDAV/CardDAV"
-
-#: ../../extend/addon/addon/cdav/cdav.php:270
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1145
-msgid "Mobile"
-msgstr "Mobiel"
-
-#: ../../extend/addon/addon/cdav/cdav.php:271
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1146 ../../include/nav.php:88
-msgid "Home"
-msgstr "Thuis"
-
-#: ../../extend/addon/addon/cdav/cdav.php:272
-msgid "Home, Voice"
-msgstr "Thuis, spraak"
-
-#: ../../extend/addon/addon/cdav/cdav.php:273
-msgid "Home, Fax"
-msgstr "Thuis, fax"
-
-#: ../../extend/addon/addon/cdav/cdav.php:274
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1147
-msgid "Work"
-msgstr "Werk"
-
-#: ../../extend/addon/addon/cdav/cdav.php:275
-msgid "Work, Voice"
-msgstr "Werk, spraak"
-
-#: ../../extend/addon/addon/cdav/cdav.php:276
-msgid "Work, Fax"
-msgstr "Werk, fax"
-
#: ../../extend/addon/addon/cdav/Mod_Cdav.php:744
msgid "INVALID EVENT DISMISSED!"
msgstr "ONGELDIGE GEBEURTENIS VERWIJDERD!"
@@ -10083,66 +10406,67 @@ msgstr "Alles verwijderen"
msgid "Sorry! Editing of recurrent events is not yet implemented."
msgstr "Excuses! Bewerken van herhalende gebeurtenissen is nog niet geïmplementeerd."
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1137
-msgid "Organisation"
-msgstr "Organisatie"
-
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1138
-#: ../../include/page_widgets.php:46
-msgid "Title"
-msgstr "Titel"
+#: ../../extend/addon/addon/cdav/cdav.php:36
+msgid "Errors encountered creating database table: "
+msgstr "Fouten opgetreden tijdens aanmaken databasetabel: "
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1139
-msgid "Phone"
-msgstr "Telefoon"
+#: ../../extend/addon/addon/cdav/cdav.php:197
+msgid "Default Calendar"
+msgstr "Standaard agenda"
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1141
-msgid "Instant messenger"
-msgstr "Instant messenger"
+#: ../../extend/addon/addon/cdav/cdav.php:206
+msgid "Default Addressbook"
+msgstr "Standaard adresboek"
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1142
-msgid "Website"
-msgstr "Website"
+#: ../../extend/addon/addon/cdav/cdav.php:215
+msgid "CalDAV/CardDAV Settings saved."
+msgstr "CalDAV/CardDAV-instellingen opgeslagen."
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1144
-msgid "Note"
-msgstr "Opmerking"
+#: ../../extend/addon/addon/cdav/cdav.php:234
+msgid "Enable CalDAV/CardDAV Server for this channel"
+msgstr "CalDAV/CardDAV-server voor dit kanaal inschakelen"
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1150
-msgid "Add Field"
-msgstr "Veld toevoegen"
+#: ../../extend/addon/addon/cdav/cdav.php:237
+#, php-format
+msgid "Your CalDAV resources are located at %s "
+msgstr "Jouw CalDAV-URL is %s "
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1155
-msgid "P.O. Box"
-msgstr "Postbus"
+#: ../../extend/addon/addon/cdav/cdav.php:240
+#, php-format
+msgid "Your CardDAV resources are located at %s "
+msgstr "Jouw CardDAV-URL is %s "
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1156
-msgid "Additional"
-msgstr "Extra"
+#: ../../extend/addon/addon/cdav/cdav.php:246
+msgid "CalDAV/CardDAV Settings"
+msgstr "CalDAV/CardDAV"
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1157
-msgid "Street"
-msgstr "Straat en huisnummer"
+#: ../../extend/addon/addon/cdav/cdav.php:272
+#: ../../include/connections.php:670
+msgid "Home, Voice"
+msgstr "Thuis, spraak"
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1158
-msgid "Locality"
-msgstr "Plaats"
+#: ../../extend/addon/addon/cdav/cdav.php:273
+#: ../../include/connections.php:671
+msgid "Home, Fax"
+msgstr "Thuis, fax"
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1159
-msgid "Region"
-msgstr "Provincie/staat/regio/enz."
+#: ../../extend/addon/addon/cdav/cdav.php:275
+#: ../../include/connections.php:673
+msgid "Work, Voice"
+msgstr "Werk, spraak"
-#: ../../extend/addon/addon/cdav/Mod_Cdav.php:1160
-msgid "ZIP Code"
-msgstr "Postcode"
+#: ../../extend/addon/addon/cdav/cdav.php:276
+#: ../../include/connections.php:674
+msgid "Work, Fax"
+msgstr "Werk, fax"
#: ../../extend/addon/addon/chess/chess.php:276
-#: ../../extend/addon/addon/chess/chess.php:430
+#: ../../extend/addon/addon/chess/chess.php:433
msgid "Invalid game."
msgstr "Ongeldig spel."
#: ../../extend/addon/addon/chess/chess.php:282
-#: ../../extend/addon/addon/chess/chess.php:436
+#: ../../extend/addon/addon/chess/chess.php:439
msgid "You are not a player in this game."
msgstr "Jij doet niet aan dit speel mee."
@@ -10166,15 +10490,15 @@ msgstr "Je moet wit of zwart kiezen."
msgid "Error creating new game."
msgstr "Fout tijdens aanmaken nieuw spel."
-#: ../../extend/addon/addon/chess/chess.php:379 ../../include/channel.php:816
+#: ../../extend/addon/addon/chess/chess.php:381 ../../include/channel.php:899
msgid "Requested channel is not available."
msgstr "Opgevraagd kanaal is niet beschikbaar."
-#: ../../extend/addon/addon/chess/chess.php:392
+#: ../../extend/addon/addon/chess/chess.php:395
msgid "You must select a local channel /chess/channelname"
msgstr "Je moet een lokaal kanaal kiezen: .../chess/kanaalnaam"
-#: ../../extend/addon/addon/chess/chess.php:920
+#: ../../extend/addon/addon/chess/chess.php:923
msgid "Enable notifications"
msgstr "Notificaties inschakelen"
@@ -10208,15 +10532,6 @@ msgstr "Man"
msgid "Female"
msgstr "Vrouw"
-#: ../../extend/addon/addon/openid/Mod_Openid.php:30
-msgid "OpenID protocol error. No ID returned."
-msgstr "OpenID-protocolfout. Geen ID terugontvangen."
-
-#: ../../extend/addon/addon/openid/Mod_Openid.php:193
-#: ../../include/auth.php:286
-msgid "Login failed."
-msgstr "Inloggen mislukt."
-
#: ../../extend/addon/addon/openid/MysqlProvider.php:52
msgid "First Name"
msgstr "Voornaam"
@@ -10283,6 +10598,15 @@ msgstr "We hebben een probleem ontdekt tijdens het inloggen met de OpenID die je
msgid "The error message was:"
msgstr "Foutmelding was:"
+#: ../../extend/addon/addon/openid/Mod_Openid.php:30
+msgid "OpenID protocol error. No ID returned."
+msgstr "OpenID-protocolfout. Geen ID terugontvangen."
+
+#: ../../extend/addon/addon/openid/Mod_Openid.php:188
+#: ../../include/auth.php:286
+msgid "Login failed."
+msgstr "Inloggen mislukt."
+
#: ../../extend/addon/addon/diaspora_reconnect/diaspora_reconnect.php:44
#, php-format
msgid "Reconnecting %d connections"
@@ -10342,71 +10666,96 @@ msgid ""
"from Mapbox instead of the default OpenStreetMap tile server."
msgstr "De Mapbox-toegangstoken wordt gebruikt om kaarttegels (tiles) van Mapbox op te halen in plaats van de standaard tile-server van OpenStreetMap."
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:154
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:162
msgid "Rendezvous"
msgstr "Rendezvous"
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:159
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:167
msgid ""
"This identity has been deleted by another member due to inactivity. Please "
"press the \"New identity\" button or refresh the page to register a new "
"identity. You may use the same name."
msgstr "Deze identiteit is door een ander lid verwijderd als gevolg van inactiviteit. Klik op de knop \"Nieuwe identiteit\" of herlaad de pagina om een nieuwe identiteit aan te maken. Je kan eventueel dezelfde naam gebruiken."
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:160
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:168
msgid "Welcome to Rendezvous!"
msgstr "Welkom bij Rendezvous!"
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:161
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:169
msgid ""
"Enter your name to join this rendezvous. To begin sharing your location with"
" the other members, tap the GPS control. When your location is discovered, a"
" red dot will appear and others will be able to see you on the map."
msgstr "Vul je naam in om deel te nemen aan deze rendezvous. Om met het delen van je locatie met de andere leden te beginnen, klik je op de locatieknop van je webbrowser. Nadat jouw locatie is gevonden verschijnt er een rode stip en kunnen andere leden jou zien op de kaart."
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:163
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:171
msgid "Let's meet here"
msgstr "Laten we elkaar hier ontmoeten"
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:166
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:174
msgid "New marker"
msgstr "Nieuwe markering"
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:167
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:175
msgid "Edit marker"
msgstr "Markering bewerken"
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:168
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:176
msgid "New identity"
msgstr "Nieuwe identiteit"
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:169
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:177
msgid "Delete marker"
msgstr "Markering verwijderen"
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:170
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:178
msgid "Delete member"
msgstr "Lid verwijderen"
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:171
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:179
msgid "Edit proximity alert"
msgstr "Nabijheidswaarschuwing bewerken"
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:172
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:180
msgid ""
"A proximity alert will be issued when this member is within a certain radius"
" of you.<br><br>Enter a radius in meters (0 to disable):"
-msgstr "Een nabijheidswaarschuwing wordt actief wanneer dit lid zich binnen een bepaalde straal bevindt.<br><br>Voer het aantal meters van de straal in (0 om uit te schakelen):"
+msgstr "Een nabijheidswaarschuwing wordt actief wanneer dit lid zich binnen een bepaalde straal rond jouw locatie bevindt.<br><br>Voer het aantal meters van de straal in (0 om uit te schakelen):"
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:172
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:180
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:185
msgid "distance"
msgstr "afstand"
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:181
+msgid "Proximity alert distance (meters)"
+msgstr "Afstand nabijheidswaarschuwing (meter)"
+
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:182
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:184
+msgid ""
+"A proximity alert will be issued when you are within a certain radius of the"
+" marker location.<br><br>Enter a radius in meters (0 to disable):"
+msgstr "Een nabijheidswaarschuwing wordt actief wanneer je je binnen een bepaalde straal rond een specifieke locatie bevindt.<br><br>Voer het aantal meters van de straal in (0 om uit te schakelen):"
+
#: ../../extend/addon/addon/rendezvous/rendezvous.php:183
+msgid "Marker proximity alert"
+msgstr "Locatiemarkering nabijheidswaarschuwing"
+
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:186
+msgid "Reminder note"
+msgstr "Herinnering"
+
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:187
+msgid ""
+"Enter a note to be displayed when you are within the specified proximity..."
+msgstr "Vul de tekst in die getoond moet worden wanneer je je op de aangegeven afstand bevindt..."
+
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:199
msgid "Add new rendezvous"
msgstr "Nieuwe rendezvous toevoegen"
-#: ../../extend/addon/addon/rendezvous/rendezvous.php:184
+#: ../../extend/addon/addon/rendezvous/rendezvous.php:200
msgid ""
"Create a new rendezvous and share the access link with those you wish to "
"invite to the group. Those who open the link become members of the "
@@ -10414,19 +10763,457 @@ msgid ""
" share their own locations with the group."
msgstr "Maak een nieuwe rendezvous aan en deel de toegangslink met wie je wil uitnodigen voor de groep. Wie op de link klikt wordt lid van rendezvous. Zij kunnen dan de locaties zien van andere leden, markeringen aan de kaart toevoegen of hun eigen locaties met de groep delen."
-#: ../../include/Import/import_diaspora.php:16
-msgid "No username found in import file."
-msgstr "Geen gebruikersnaam in het importbestand gevonden."
+#: ../../extend/addon/addon/firefox/firefox.php:23
+msgid "Install Firefox Sharing Tools"
+msgstr "Firefox Share"
-#: ../../include/Import/import_diaspora.php:41 ../../include/import.php:51
-msgid "Unable to create a unique channel address. Import failed."
-msgstr "Niet in staat om een uniek kanaaladres aan te maken. Importeren is mislukt."
+#: ../../extend/addon/addon/firefox/firefox.php:34
+msgid "Share content from Firefox to $Projectname"
+msgstr "Deel webpagina's vanuit Firefox met "
+
+#: ../../extend/addon/addon/firefox/firefox.php:37
+msgid "Install Firefox Sharing Tools to this web browser"
+msgstr "Activeer de $Projectname-service in Firefox"
+
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:105
+msgid "Error retrieving wiki"
+msgstr "Fout tijdens ophalen wiki"
+
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:112
+msgid "Error creating zip file export folder"
+msgstr "Fout tijdens aanmaken exportmap zipbestand"
+
+#: ../../extend/addon/addon/gitwiki/Mod_Gitwiki.php:130
+msgid "Error downloading wiki: "
+msgstr "Fout tijdens downloaden wiki: "
+
+#: ../../extend/addon/addon/gitwiki/gitwiki.php:76
+#: ../../include/widgets.php:956
+msgid "Wiki Pages"
+msgstr "Wikipagina's"
+
+#: ../../extend/addon/addon/gitwiki/gitwiki.php:81
+#: ../../include/widgets.php:962
+msgid "Add new page"
+msgstr "Nieuwe pagina toevoegen"
+
+#: ../../extend/addon/addon/gitwiki/gitwiki.php:82
+#: ../../include/widgets.php:963
+msgid "Page name"
+msgstr "Paginanaam"
+
+#: ../../extend/addon/addon/gitwiki/gitwiki.php:95
+#: ../../include/widgets.php:913
+msgid "Wiki List"
+msgstr "Wiki's"
+
+#: ../../extend/addon/addon/gnusoc/gnusoc.php:129
+msgid "Enable the GNU-Social protocol for this channel"
+msgstr "GNU social-protocol voor dit kanaal inschakelen"
+
+#: ../../extend/addon/addon/opensearch/opensearch.php:26 ../../boot.php:1186
+#, php-format
+msgctxt "opensearch"
+msgid "Search %1$s (%2$s)"
+msgstr "Zoek %1$s (%2$s)"
+
+#: ../../extend/addon/addon/opensearch/opensearch.php:28 ../../boot.php:1186
+msgctxt "opensearch"
+msgid "$Projectname"
+msgstr "$Projectname"
+
+#: ../../extend/addon/addon/opensearch/opensearch.php:43
+msgid "Search $Projectname"
+msgstr "Zoek in "
#: ../../include/dba/dba_driver.php:187
#, php-format
msgid "Cannot locate DNS info for database server '%s'"
msgstr "Kan DNS-informatie voor databaseserver '%s' niet vinden"
+#: ../../include/language.php:367 ../../include/text.php:1788
+msgid "default"
+msgstr "standaard"
+
+#: ../../include/language.php:380
+msgid "Select an alternate language"
+msgstr "Kies een andere taal"
+
+#: ../../include/account.php:35
+msgid "Not a valid email address"
+msgstr "Geen geldig e-mailadres"
+
+#: ../../include/account.php:37
+msgid "Your email domain is not among those allowed on this site"
+msgstr "Jouw e-maildomein is op deze hub niet toegestaan"
+
+#: ../../include/account.php:43
+msgid "Your email address is already registered at this site."
+msgstr "Jouw e-mailadres is al op deze hub geregistreerd."
+
+#: ../../include/account.php:75
+msgid "An invitation is required."
+msgstr "Een uitnodiging is vereist"
+
+#: ../../include/account.php:79
+msgid "Invitation could not be verified."
+msgstr "Uitnodiging kon niet geverifieerd worden"
+
+#: ../../include/account.php:130
+msgid "Please enter the required information."
+msgstr "Vul de vereiste informatie in."
+
+#: ../../include/account.php:198
+msgid "Failed to store account information."
+msgstr "Account-informatie kon niet opgeslagen worden."
+
+#: ../../include/account.php:263
+#, php-format
+msgid "Registration confirmation for %s"
+msgstr "Registratiebevestiging voor %s"
+
+#: ../../include/account.php:330
+#, php-format
+msgid "Registration request at %s"
+msgstr "Registratiebevestiging voor %s"
+
+#: ../../include/account.php:352
+msgid "your registration password"
+msgstr "jouw registratiewachtwoord"
+
+#: ../../include/account.php:358 ../../include/account.php:420
+#, php-format
+msgid "Registration details for %s"
+msgstr "Registratiegegevens voor %s"
+
+#: ../../include/account.php:431
+msgid "Account approved."
+msgstr "Account goedgekeurd"
+
+#: ../../include/account.php:471
+#, php-format
+msgid "Registration revoked for %s"
+msgstr "Registratie ingetrokken voor %s"
+
+#: ../../include/account.php:756 ../../include/account.php:758
+msgid "Click here to upgrade."
+msgstr "Klik hier om te upgraden."
+
+#: ../../include/account.php:764
+msgid "This action exceeds the limits set by your subscription plan."
+msgstr "Deze handeling overschrijdt de beperkingen die voor jouw abonnement gelden."
+
+#: ../../include/account.php:769
+msgid "This action is not available under your subscription plan."
+msgstr "Deze handeling is niet mogelijk met jouw abonnement."
+
+#: ../../include/widgets.php:46 ../../include/widgets.php:455
+#: ../../include/taxonomy.php:188 ../../include/taxonomy.php:270
+#: ../../include/contact_widgets.php:91
+msgid "Categories"
+msgstr "Categorieën"
+
+#: ../../include/widgets.php:141
+msgid "Suggestions"
+msgstr "Voorgestelde kanalen"
+
+#: ../../include/widgets.php:142
+msgid "See more..."
+msgstr "Meer..."
+
+#: ../../include/widgets.php:162
+#, php-format
+msgid "You have %1$.0f of %2$.0f allowed connections."
+msgstr "Je hebt %1$.0f van de %2$.0f toegestane connecties."
+
+#: ../../include/widgets.php:168
+msgid "Add New Connection"
+msgstr "Nieuwe connectie toevoegen"
+
+#: ../../include/widgets.php:169
+msgid "Enter channel address"
+msgstr "Vul kanaaladres in"
+
+#: ../../include/widgets.php:170
+msgid "Examples: bob@example.com, https://example.com/barbara"
+msgstr "Voorbeelden: bob@example.com, http://example.com/barbara"
+
+#: ../../include/widgets.php:186
+msgid "Notes"
+msgstr "Aantekeningen"
+
+#: ../../include/widgets.php:262
+msgid "Remove term"
+msgstr "Verwijder zoekterm"
+
+#: ../../include/widgets.php:270 ../../include/features.php:301
+msgid "Saved Searches"
+msgstr "Opgeslagen zoekopdrachten"
+
+#: ../../include/widgets.php:271 ../../include/group.php:336
+msgid "add"
+msgstr "toevoegen"
+
+#: ../../include/widgets.php:333 ../../include/contact_widgets.php:53
+#: ../../include/features.php:390
+msgid "Saved Folders"
+msgstr "Bewaarde mappen"
+
+#: ../../include/widgets.php:336 ../../include/widgets.php:458
+#: ../../include/contact_widgets.php:56 ../../include/contact_widgets.php:94
+msgid "Everything"
+msgstr "Alles"
+
+#: ../../include/widgets.php:377
+msgid "Archives"
+msgstr "Archieven"
+
+#: ../../include/widgets.php:549
+msgid "Refresh"
+msgstr "Vernieuwen"
+
+#: ../../include/widgets.php:589
+msgid "Account settings"
+msgstr "Account"
+
+#: ../../include/widgets.php:595
+msgid "Channel settings"
+msgstr "Kanaal"
+
+#: ../../include/widgets.php:604
+msgid "Additional features"
+msgstr "Extra functies"
+
+#: ../../include/widgets.php:611
+msgid "Feature/Addon settings"
+msgstr "Plugin-instellingen"
+
+#: ../../include/widgets.php:617
+msgid "Display settings"
+msgstr "Weergave"
+
+#: ../../include/widgets.php:624
+msgid "Manage locations"
+msgstr "Locaties beheren"
+
+#: ../../include/widgets.php:631
+msgid "Export channel"
+msgstr "Kanaal exporteren"
+
+#: ../../include/widgets.php:637
+msgid "Connected apps"
+msgstr "Verbonden applicaties"
+
+#: ../../include/widgets.php:652 ../../include/features.php:153
+msgid "Permission Groups"
+msgstr "Permissiegroepen"
+
+#: ../../include/widgets.php:669
+msgid "Premium Channel Settings"
+msgstr "Instellingen premiumkanaal"
+
+#: ../../include/widgets.php:698
+msgid "Private Mail Menu"
+msgstr "Privéberichten"
+
+#: ../../include/widgets.php:700
+msgid "Combined View"
+msgstr "Gecombineerd postvak"
+
+#: ../../include/widgets.php:705 ../../include/nav.php:213
+msgid "Inbox"
+msgstr "Postvak IN"
+
+#: ../../include/widgets.php:710 ../../include/nav.php:214
+msgid "Outbox"
+msgstr "Postvak UIT"
+
+#: ../../include/widgets.php:715 ../../include/nav.php:215
+msgid "New Message"
+msgstr "Nieuw bericht"
+
+#: ../../include/widgets.php:732 ../../include/widgets.php:744
+msgid "Conversations"
+msgstr "Conversaties"
+
+#: ../../include/widgets.php:736
+msgid "Received Messages"
+msgstr "Ontvangen berichten"
+
+#: ../../include/widgets.php:740
+msgid "Sent Messages"
+msgstr "Verzonden berichten"
+
+#: ../../include/widgets.php:754
+msgid "No messages."
+msgstr "Geen berichten"
+
+#: ../../include/widgets.php:772
+msgid "Delete conversation"
+msgstr "Verwijder conversatie"
+
+#: ../../include/widgets.php:798
+msgid "Events Tools"
+msgstr "Agenda-hulpmiddelen"
+
+#: ../../include/widgets.php:799
+msgid "Export Calendar"
+msgstr "Exporteren"
+
+#: ../../include/widgets.php:800
+msgid "Import Calendar"
+msgstr "Importeren"
+
+#: ../../include/widgets.php:888 ../../include/conversation.php:1866
+#: ../../include/conversation.php:1869
+msgid "Chatrooms"
+msgstr "Chatkanalen"
+
+#: ../../include/widgets.php:892
+msgid "Overview"
+msgstr "Overzicht"
+
+#: ../../include/widgets.php:899
+msgid "Chat Members"
+msgstr "Chatleden"
+
+#: ../../include/widgets.php:977
+msgctxt "wiki_history"
+msgid "Message"
+msgstr "Bericht"
+
+#: ../../include/widgets.php:999
+msgid "Bookmarked Chatrooms"
+msgstr "Bladwijzers van chatkanalen"
+
+#: ../../include/widgets.php:1030
+msgid "Suggested Chatrooms"
+msgstr "Voorgestelde chatkanalen"
+
+#: ../../include/widgets.php:1175 ../../include/widgets.php:1287
+msgid "photo/image"
+msgstr "foto/afbeelding"
+
+#: ../../include/widgets.php:1230
+msgid "Click to show more"
+msgstr "Klik voor meer"
+
+#: ../../include/widgets.php:1381
+msgid "Rating Tools"
+msgstr "Beoordelingen"
+
+#: ../../include/widgets.php:1385 ../../include/widgets.php:1387
+msgid "Rate Me"
+msgstr "Beoordeel mij"
+
+#: ../../include/widgets.php:1390
+msgid "View Ratings"
+msgstr "Bekijk beoordelingen"
+
+#: ../../include/widgets.php:1483
+msgid "Forums"
+msgstr "Forums"
+
+#: ../../include/widgets.php:1540
+msgctxt "widget"
+msgid "Activity"
+msgstr "Activiteit"
+
+#: ../../include/widgets.php:1569
+msgid "Tasks"
+msgstr "Taken"
+
+#: ../../include/widgets.php:1635 ../../include/widgets.php:1673
+msgid "Member registrations waiting for confirmation"
+msgstr "Accounts die op goedkeuring wachten"
+
+#: ../../include/widgets.php:1641
+msgid "Inspect queue"
+msgstr "Inspecteer berichtenwachtrij"
+
+#: ../../include/widgets.php:1643
+msgid "DB updates"
+msgstr "Database-updates"
+
+#: ../../include/widgets.php:1668 ../../include/nav.php:233
+msgid "Admin"
+msgstr "Beheer"
+
+#: ../../include/widgets.php:1669
+msgid "Plugin Features"
+msgstr "Plugin-opties"
+
+#: ../../include/taxonomy.php:228 ../../include/taxonomy.php:249
+msgid "Tags"
+msgstr "Tags"
+
+#: ../../include/taxonomy.php:293
+msgid "Keywords"
+msgstr "Trefwoorden"
+
+#: ../../include/taxonomy.php:314
+msgid "have"
+msgstr "heb"
+
+#: ../../include/taxonomy.php:314
+msgid "has"
+msgstr "heeft"
+
+#: ../../include/taxonomy.php:315
+msgid "want"
+msgstr "wil"
+
+#: ../../include/taxonomy.php:315
+msgid "wants"
+msgstr "wil"
+
+#: ../../include/taxonomy.php:316
+msgid "likes"
+msgstr "vindt dit leuk"
+
+#: ../../include/taxonomy.php:317
+msgid "dislikes"
+msgstr "vindt dit niet leuk"
+
+#: ../../include/event.php:22 ../../include/event.php:69
+#: ../../include/markdown.php:540
+msgid "l F d, Y \\@ g:i A"
+msgstr "l d F Y \\@ G:i"
+
+#: ../../include/event.php:30 ../../include/event.php:73
+#: ../../include/markdown.php:546
+msgid "Starts:"
+msgstr "Start:"
+
+#: ../../include/event.php:40 ../../include/event.php:77
+#: ../../include/markdown.php:554
+msgid "Finishes:"
+msgstr "Einde:"
+
+#: ../../include/event.php:1004
+msgid "This event has been added to your calendar."
+msgstr "Dit evenement is aan jouw agenda toegevoegd."
+
+#: ../../include/event.php:1204
+msgid "Not specified"
+msgstr "Niet aangegeven"
+
+#: ../../include/event.php:1205
+msgid "Needs Action"
+msgstr "Actie vereist"
+
+#: ../../include/event.php:1206
+msgid "Completed"
+msgstr "Voltooid"
+
+#: ../../include/event.php:1207
+msgid "In Process"
+msgstr "In behandeling"
+
+#: ../../include/event.php:1208
+msgid "Cancelled"
+msgstr "Geannuleerd"
+
#: ../../include/datetime.php:147
msgid "Birthday"
msgstr "Verjaardag of geboortedatum"
@@ -10439,7 +11226,7 @@ msgstr "Leeftijd:"
msgid "YYYY-MM-DD or MM-DD"
msgstr "JJJJ-MM-DD of MM-DD"
-#: ../../include/datetime.php:286 ../../boot.php:2564
+#: ../../include/datetime.php:286 ../../boot.php:2598
msgid "never"
msgstr "nooit"
@@ -10512,74 +11299,6 @@ msgstr "Verjaardag van %1$s"
msgid "Happy Birthday %1$s"
msgstr "Gefeliciteerd met je verjaardag %1$s"
-#: ../../include/account.php:35
-msgid "Not a valid email address"
-msgstr "Geen geldig e-mailadres"
-
-#: ../../include/account.php:37
-msgid "Your email domain is not among those allowed on this site"
-msgstr "Jouw e-maildomein is op deze hub niet toegestaan"
-
-#: ../../include/account.php:43
-msgid "Your email address is already registered at this site."
-msgstr "Jouw e-mailadres is al op deze hub geregistreerd."
-
-#: ../../include/account.php:75
-msgid "An invitation is required."
-msgstr "Een uitnodiging is vereist"
-
-#: ../../include/account.php:79
-msgid "Invitation could not be verified."
-msgstr "Uitnodiging kon niet geverifieerd worden"
-
-#: ../../include/account.php:130
-msgid "Please enter the required information."
-msgstr "Vul de vereiste informatie in."
-
-#: ../../include/account.php:198
-msgid "Failed to store account information."
-msgstr "Account-informatie kon niet opgeslagen worden."
-
-#: ../../include/account.php:263
-#, php-format
-msgid "Registration confirmation for %s"
-msgstr "Registratiebevestiging voor %s"
-
-#: ../../include/account.php:330
-#, php-format
-msgid "Registration request at %s"
-msgstr "Registratiebevestiging voor %s"
-
-#: ../../include/account.php:352
-msgid "your registration password"
-msgstr "jouw registratiewachtwoord"
-
-#: ../../include/account.php:358 ../../include/account.php:420
-#, php-format
-msgid "Registration details for %s"
-msgstr "Registratiegegevens voor %s"
-
-#: ../../include/account.php:431
-msgid "Account approved."
-msgstr "Account goedgekeurd"
-
-#: ../../include/account.php:471
-#, php-format
-msgid "Registration revoked for %s"
-msgstr "Registratie ingetrokken voor %s"
-
-#: ../../include/account.php:756 ../../include/account.php:758
-msgid "Click here to upgrade."
-msgstr "Klik hier om te upgraden."
-
-#: ../../include/account.php:764
-msgid "This action exceeds the limits set by your subscription plan."
-msgstr "Deze handeling overschrijdt de beperkingen die voor jouw abonnement gelden."
-
-#: ../../include/account.php:769
-msgid "This action is not available under your subscription plan."
-msgstr "Deze handeling is niet mogelijk met jouw abonnement."
-
#: ../../include/selectors.php:30
msgid "Frequently"
msgstr "Regelmatig"
@@ -10820,745 +11539,103 @@ msgstr "Maakt mij niks uit"
msgid "Ask me"
msgstr "Vraag het me"
-#: ../../include/channel.php:33
-msgid "Unable to obtain identity information from database"
-msgstr "Niet in staat om identiteitsinformatie uit de database te verkrijgen"
-
-#: ../../include/channel.php:67
-msgid "Empty name"
-msgstr "Ontbrekende naam"
-
-#: ../../include/channel.php:70
-msgid "Name too long"
-msgstr "Naam te lang"
-
-#: ../../include/channel.php:181
-msgid "No account identifier"
-msgstr "Geen account-identificator"
-
-#: ../../include/channel.php:193
-msgid "Nickname is required."
-msgstr "Bijnaam is verplicht"
+#: ../../include/acl_selectors.php:208
+msgid "Who can see this?"
+msgstr "Wie kan dit zien?"
-#: ../../include/channel.php:207
-msgid "Reserved nickname. Please choose another."
-msgstr "Deze naam is gereserveerd. Kies een andere."
+#: ../../include/acl_selectors.php:209
+msgid "Custom selection"
+msgstr "Handmatige selectie"
-#: ../../include/channel.php:212
+#: ../../include/acl_selectors.php:210
msgid ""
-"Nickname has unsupported characters or is already being used on this site."
-msgstr "Deze naam heeft niet ondersteunde karakters of is al op deze hub in gebruik."
-
-#: ../../include/channel.php:272
-msgid "Unable to retrieve created identity"
-msgstr "Niet in staat om aangemaakte identiteit te vinden"
-
-#: ../../include/channel.php:341
-msgid "Default Profile"
-msgstr "Standaardprofiel"
-
-#: ../../include/channel.php:962
-msgid "Create New Profile"
-msgstr "Nieuw profiel aanmaken"
-
-#: ../../include/channel.php:982
-msgid "Visible to everybody"
-msgstr "Voor iedereen zichtbaar"
-
-#: ../../include/channel.php:1055 ../../include/channel.php:1174
-msgid "Gender:"
-msgstr "Geslacht:"
-
-#: ../../include/channel.php:1057 ../../include/channel.php:1229
-msgid "Homepage:"
-msgstr "Homepagina:"
-
-#: ../../include/channel.php:1058
-msgid "Online Now"
-msgstr "Nu online"
-
-#: ../../include/channel.php:1179
-msgid "Like this channel"
-msgstr "Vind dit kanaal leuk"
-
-#: ../../include/channel.php:1203
-msgid "j F, Y"
-msgstr "F j Y"
+"Select \"Show\" to allow viewing. \"Don't show\" lets you override and limit"
+" the scope of \"Show\"."
+msgstr "Kies \"Tonen\" om weergave toe te staan. Met \"Niet tonen\" kan je uitzonderingen maken op \"Tonen\"."
-#: ../../include/channel.php:1204
-msgid "j F"
-msgstr "F j"
+#: ../../include/acl_selectors.php:211
+msgid "Show"
+msgstr "Tonen"
-#: ../../include/channel.php:1211
-msgid "Birthday:"
-msgstr "Geboortedatum:"
+#: ../../include/acl_selectors.php:212
+msgid "Don't show"
+msgstr "Niet tonen"
-#: ../../include/channel.php:1224
+#: ../../include/acl_selectors.php:245
#, php-format
-msgid "for %1$d %2$s"
-msgstr "voor %1$d %2$s"
-
-#: ../../include/channel.php:1227
-msgid "Sexual Preference:"
-msgstr "Seksuele voorkeur:"
-
-#: ../../include/channel.php:1233
-msgid "Tags:"
-msgstr "Tags:"
-
-#: ../../include/channel.php:1235
-msgid "Political Views:"
-msgstr "Politieke overtuigingen:"
-
-#: ../../include/channel.php:1237
-msgid "Religion:"
-msgstr "Religie:"
-
-#: ../../include/channel.php:1241
-msgid "Hobbies/Interests:"
-msgstr "Hobby's/interesses:"
-
-#: ../../include/channel.php:1243
-msgid "Likes:"
-msgstr "Houdt van:"
-
-#: ../../include/channel.php:1245
-msgid "Dislikes:"
-msgstr "Houdt niet van:"
-
-#: ../../include/channel.php:1247
-msgid "Contact information and Social Networks:"
-msgstr "Contactinformatie en sociale netwerken:"
+msgid ""
+"Post permissions %s cannot be changed %s after a post is shared.</br />These"
+" permissions set who is allowed to view the post."
+msgstr "Permissies van berichten %s zijn niet meer te veranderen %s nadat een bericht is gedeeld.</br />Met deze permissies bepaal je wie het bericht kan zien."
-#: ../../include/channel.php:1249
-msgid "My other channels:"
-msgstr "Mijn andere kanalen"
+#: ../../include/bbcode.php:134 ../../include/bbcode.php:1040
+#: ../../include/bbcode.php:1043 ../../include/bbcode.php:1048
+#: ../../include/bbcode.php:1051 ../../include/bbcode.php:1054
+#: ../../include/bbcode.php:1057 ../../include/bbcode.php:1062
+#: ../../include/bbcode.php:1065 ../../include/bbcode.php:1070
+#: ../../include/bbcode.php:1073 ../../include/bbcode.php:1076
+#: ../../include/bbcode.php:1079
+msgid "Image/photo"
+msgstr "Afbeelding/foto"
-#: ../../include/channel.php:1251
-msgid "Musical interests:"
-msgstr "Muzikale interesses:"
+#: ../../include/bbcode.php:173 ../../include/bbcode.php:1090
+msgid "Encrypted content"
+msgstr "Versleutelde inhoud"
-#: ../../include/channel.php:1253
-msgid "Books, literature:"
-msgstr "Boeken, literatuur:"
+#: ../../include/bbcode.php:189
+#, php-format
+msgid "Install %s element: "
+msgstr "Installeer %s-element: "
-#: ../../include/channel.php:1255
-msgid "Television:"
-msgstr "Televisie:"
+#: ../../include/bbcode.php:193
+#, php-format
+msgid ""
+"This post contains an installable %s element, however you lack permissions "
+"to install it on this site."
+msgstr "Dit bericht heeft een te installeren %s-element, maar je hebt geen permissies om het op deze hub te installeren."
-#: ../../include/channel.php:1257
-msgid "Film/dance/culture/entertainment:"
-msgstr "Films/dansen/cultuur/vermaak:"
+#: ../../include/bbcode.php:272
+#, php-format
+msgid "%1$s wrote the following %2$s %3$s"
+msgstr "%1$s schreef het volgende %2$s %3$s"
-#: ../../include/channel.php:1259
-msgid "Love/Romance:"
-msgstr "Liefde/romantiek:"
+#: ../../include/bbcode.php:349 ../../include/bbcode.php:357
+msgid "Click to open/close"
+msgstr "Klik om te openen of te sluiten"
-#: ../../include/channel.php:1261
-msgid "Work/employment:"
-msgstr "Werk/beroep:"
+#: ../../include/bbcode.php:357
+msgid "spoiler"
+msgstr "spoiler"
-#: ../../include/channel.php:1263
-msgid "School/education:"
-msgstr "School/opleiding:"
+#: ../../include/bbcode.php:1028
+msgid "$1 wrote:"
+msgstr "$1 schreef:"
-#: ../../include/channel.php:1284
-msgid "Like this thing"
-msgstr "Vind dit ding leuk"
+#: ../../include/bookmarks.php:34
+#, php-format
+msgid "%1$s's bookmarks"
+msgstr "Bladwijzers van %1$s"
-#: ../../include/connections.php:95
+#: ../../include/connections.php:127
msgid "New window"
msgstr "Nieuw venster"
-#: ../../include/connections.php:96
+#: ../../include/connections.php:128
msgid "Open the selected location in a different window or browser tab"
msgstr "Open de geselecteerde locatie in een ander venster of tab"
-#: ../../include/connections.php:214
-#, php-format
-msgid "User '%s' deleted"
-msgstr "Account '%s' verwijderd"
-
-#: ../../include/dir_fns.php:141
-msgid "Directory Options"
-msgstr "Opties kanalengids"
-
-#: ../../include/dir_fns.php:143
-msgid "Safe Mode"
-msgstr "Veilig zoeken"
-
-#: ../../include/dir_fns.php:144
-msgid "Public Forums Only"
-msgstr "Alleen openbare forums"
-
-#: ../../include/dir_fns.php:145
-msgid "This Website Only"
-msgstr "Alleen deze hub"
-
-#: ../../include/nav.php:85 ../../include/nav.php:118 ../../boot.php:1719
-msgid "Logout"
-msgstr "Uitloggen"
-
-#: ../../include/nav.php:85 ../../include/nav.php:118
-msgid "End this session"
-msgstr "Beëindig deze sessie"
-
-#: ../../include/nav.php:88
-msgid "Your posts and conversations"
-msgstr "Jouw kanaal"
-
-#: ../../include/nav.php:89
-msgid "Your profile page"
-msgstr "Jouw profielpagina"
-
-#: ../../include/nav.php:91
-msgid "Manage/Edit profiles"
-msgstr "Beheer/wijzig profielen"
-
-#: ../../include/nav.php:93
-msgid "Edit your profile"
-msgstr "Jouw profiel bewerken"
-
-#: ../../include/nav.php:95
-msgid "Your photos"
-msgstr "Jouw foto's"
-
-#: ../../include/nav.php:96
-msgid "Your files"
-msgstr "Jouw bestanden"
-
-#: ../../include/nav.php:99
-msgid "Your chatrooms"
-msgstr "Jouw chatkanalen"
-
-#: ../../include/nav.php:105 ../../include/conversation.php:1717
-msgid "Bookmarks"
-msgstr "Bladwijzers"
-
-#: ../../include/nav.php:105
-msgid "Your bookmarks"
-msgstr "Jouw bladwijzers"
-
-#: ../../include/nav.php:109
-msgid "Your webpages"
-msgstr "Jouw webpagina's"
-
-#: ../../include/nav.php:111
-msgid "Your wikis"
-msgstr "Jouw wiki's"
-
-#: ../../include/nav.php:115
-msgid "Sign in"
-msgstr "Inloggen"
-
-#: ../../include/nav.php:131
-msgid "Remote authentication"
-msgstr "Authenticatie op afstand"
-
-#: ../../include/nav.php:131
-msgid "Click to authenticate to your home hub"
-msgstr "Authenticeer jezelf via (bijvoorbeeld) jouw hub"
-
-#: ../../include/nav.php:143
-msgid "Get me home"
-msgstr "Terug naar mijn hub"
-
-#: ../../include/nav.php:145
-msgid "Log me out of this site"
-msgstr "Uitloggen op deze hub"
-
-#: ../../include/nav.php:150
-msgid "Create an account"
-msgstr "Maak een account aan"
-
-#: ../../include/nav.php:162
-msgid "Help and documentation"
-msgstr "Hulp en documentatie"
-
-#: ../../include/nav.php:166
-msgid "Applications, utilities, links, games"
-msgstr "Apps"
-
-#: ../../include/nav.php:168
-msgid "Search site @name, #tag, ?docs, content"
-msgstr "Zoek een @kanaal, doorzoek inhoud hub met tekst en #tags, of doorzoek ?documentatie "
-
-#: ../../include/nav.php:170
-msgid "Channel Directory"
-msgstr "Kanalengids"
-
-#: ../../include/nav.php:182
-msgid "Your grid"
-msgstr "Jouw grid"
-
-#: ../../include/nav.php:183
-msgid "Mark all grid notifications seen"
-msgstr "Markeer alle gridnotificaties als bekeken"
-
-#: ../../include/nav.php:185
-msgid "Channel home"
-msgstr "Jouw kanaal"
-
-#: ../../include/nav.php:186
-msgid "Mark all channel notifications seen"
-msgstr "Alle kanaalnotificaties als gelezen markeren"
-
-#: ../../include/nav.php:192
-msgid "Notices"
-msgstr "Notificaties"
-
-#: ../../include/nav.php:192
-msgid "Notifications"
-msgstr "Notificaties"
-
-#: ../../include/nav.php:193
-msgid "See all notifications"
-msgstr "Alle notificaties weergeven"
-
-#: ../../include/nav.php:196
-msgid "Private mail"
-msgstr "Privéberichten"
-
-#: ../../include/nav.php:197
-msgid "See all private messages"
-msgstr "Alle privéberichten weergeven"
-
-#: ../../include/nav.php:198
-msgid "Mark all private messages seen"
-msgstr "Markeer alle privéberichten als bekeken"
-
-#: ../../include/nav.php:199 ../../include/widgets.php:700
-msgid "Inbox"
-msgstr "Postvak IN"
-
-#: ../../include/nav.php:200 ../../include/widgets.php:705
-msgid "Outbox"
-msgstr "Postvak UIT"
-
-#: ../../include/nav.php:201 ../../include/widgets.php:710
-msgid "New Message"
-msgstr "Nieuw bericht"
-
-#: ../../include/nav.php:204
-msgid "Event Calendar"
-msgstr "Agenda"
-
-#: ../../include/nav.php:205
-msgid "See all events"
-msgstr "Alle gebeurtenissen weergeven"
-
-#: ../../include/nav.php:206
-msgid "Mark all events seen"
-msgstr "Markeer alle gebeurtenissen als bekeken"
-
-#: ../../include/nav.php:209
-msgid "Manage Your Channels"
-msgstr "Beheer je kanalen"
-
-#: ../../include/nav.php:211
-msgid "Account/Channel Settings"
-msgstr "Account-/kanaal-instellingen"
-
-#: ../../include/nav.php:219 ../../include/widgets.php:1595
-msgid "Admin"
-msgstr "Beheer"
-
-#: ../../include/nav.php:219
-msgid "Site Setup and Configuration"
-msgstr "Hub instellen en beheren"
-
-#: ../../include/nav.php:250 ../../include/conversation.php:835
-msgid "Loading..."
-msgstr "Aan het laden..."
-
-#: ../../include/nav.php:255
-msgid "@name, #tag, ?doc, content"
-msgstr "@kanaal, #tag, inhoud, ?hulp"
-
-#: ../../include/nav.php:256
-msgid "Please wait..."
-msgstr "Wachten aub..."
-
-#: ../../include/features.php:58
-msgid "General Features"
-msgstr "Algemene functies"
-
-#: ../../include/features.php:63
-msgid "Multiple Profiles"
-msgstr "Meerdere profielen"
-
-#: ../../include/features.php:64
-msgid "Ability to create multiple profiles"
-msgstr "Mogelijkheid om meerdere profielen aan te maken"
-
-#: ../../include/features.php:72
-msgid "Advanced Profiles"
-msgstr "Geavanceerde profielen"
-
-#: ../../include/features.php:73
-msgid "Additional profile sections and selections"
-msgstr "Extra onderdelen en keuzes voor je profiel"
-
-#: ../../include/features.php:81
-msgid "Profile Import/Export"
-msgstr "Profiel importen/exporteren"
-
-#: ../../include/features.php:82
-msgid "Save and load profile details across sites/channels"
-msgstr "Profielgegevens opslaan en in andere hubs/kanalen gebruiken."
-
-#: ../../include/features.php:90
-msgid "Web Pages"
-msgstr "Webpagina's"
-
-#: ../../include/features.php:91
-msgid "Provide managed web pages on your channel"
-msgstr "Sta beheerde webpagina's op jouw kanaal toe"
-
-#: ../../include/features.php:100
-msgid "Provide a wiki for your channel"
-msgstr "Voeg een wiki aan jouw kanaal toe"
-
-#: ../../include/features.php:117
-msgid "Private Notes"
-msgstr "Privé-aantekeningen"
-
-#: ../../include/features.php:118
-msgid "Enables a tool to store notes and reminders (note: not encrypted)"
-msgstr "Een eenvoudige toepassing om aantekeningen en herinneringen in te bewaren (let op: niet versleuteld)"
-
-#: ../../include/features.php:126
-msgid "Navigation Channel Select"
-msgstr "Kanaal kiezen in navigatiemenu"
-
-#: ../../include/features.php:127
-msgid "Change channels directly from within the navigation dropdown menu"
-msgstr "Kies een ander kanaal direct vanuit het dropdown-menu op de navigatiebalk"
-
-#: ../../include/features.php:135
-msgid "Photo Location"
-msgstr "Fotolocatie"
-
-#: ../../include/features.php:136
-msgid "If location data is available on uploaded photos, link this to a map."
-msgstr "Wanneer in de geüploade foto's locatiegegevens aanwezig zijn, link dit dan aan een kaart."
-
-#: ../../include/features.php:144
-msgid "Access Controlled Chatrooms"
-msgstr "Chatkanalen met toegangscontrole "
-
-#: ../../include/features.php:145
-msgid "Provide chatrooms and chat services with access control."
-msgstr "Chatkanalen en chatdiensten met toegangscontrole aanbieden."
-
-#: ../../include/features.php:153
-msgid "Smart Birthdays"
-msgstr "Slimme verjaardagen"
-
-#: ../../include/features.php:154
-msgid ""
-"Make birthday events timezone aware in case your friends are scattered "
-"across the planet."
-msgstr "Maak verjaardagen bewust van tijdzones. Voor het geval dat jouw vrienden over de hele wereld verspreid zijn."
-
-#: ../../include/features.php:162
-msgid "Advanced Directory Search"
-msgstr "Geavanceerd in de kanalengids zoeken"
-
-#: ../../include/features.php:163
-msgid "Allows creation of complex directory search queries"
-msgstr "Gebruik complexe zoekopdrachten in de kanalengids"
-
-#: ../../include/features.php:171
-msgid "Advanced Theme and Layout Settings"
-msgstr "Geavanceerde thema- en lay-out-instellingen"
-
-#: ../../include/features.php:172
-msgid "Allows fine tuning of themes and page layouts"
-msgstr "Maakt het mogelijk dat thema's en pagina-lay-outs preciezer ingesteld kunnen worden "
-
-#: ../../include/features.php:182
-msgid "Post Composition Features"
-msgstr "Functies voor het opstellen van berichten"
-
-#: ../../include/features.php:186
-msgid "Large Photos"
-msgstr "Grote foto's"
-
-#: ../../include/features.php:187
-msgid ""
-"Include large (1024px) photo thumbnails in posts. If not enabled, use small "
-"(640px) photo thumbnails"
-msgstr "Gebruik grotere foto's (1024px) in berichten. Wanneer dit is uitgeschakeld worden er kleinere foto's (640px) gebruikt."
-
-#: ../../include/features.php:196
-msgid "Automatically import channel content from other channels or feeds"
-msgstr "Automatisch inhoud uit andere kanalen of feeds importeren."
-
-#: ../../include/features.php:204
-msgid "Even More Encryption"
-msgstr "Extra encryptie"
-
-#: ../../include/features.php:205
-msgid ""
-"Allow optional encryption of content end-to-end with a shared secret key"
-msgstr "Sta toe dat inhoud extra end-to-end wordt versleuteld met een gedeelde geheime sleutel."
-
-#: ../../include/features.php:213
-msgid "Enable Voting Tools"
-msgstr "Peilingen inschakelen"
-
-#: ../../include/features.php:214
-msgid "Provide a class of post which others can vote on"
-msgstr "Maakt het mogelijk om een bericht op te stellen, waar mensen op kunnen stemmen."
-
-#: ../../include/features.php:222
-msgid "Disable Comments"
-msgstr "Reacties uitschakelen"
-
-#: ../../include/features.php:223
-msgid "Provide the option to disable comments for a post"
-msgstr "Maak het mogelijk dat reacties op een bericht kunnen worden uitgeschakeld"
-
-#: ../../include/features.php:231
-msgid "Delayed Posting"
-msgstr "Berichten uitstellen"
-
-#: ../../include/features.php:232
-msgid "Allow posts to be published at a later date"
-msgstr "Maakt het mogelijk dat berichten op een toekomstig moment gepubliceerd kunnen worden."
-
-#: ../../include/features.php:240
-msgid "Content Expiration"
-msgstr "Inhoud laten verlopen"
-
-#: ../../include/features.php:241
-msgid "Remove posts/comments and/or private messages at a future time"
-msgstr "Berichten, reacties en/of privéberichten na een bepaalde tijd verwijderen"
-
-#: ../../include/features.php:249
-msgid "Suppress Duplicate Posts/Comments"
-msgstr "Dubbele berichten/reacties tegenhouden"
-
-#: ../../include/features.php:250
-msgid ""
-"Prevent posts with identical content to be published with less than two "
-"minutes in between submissions."
-msgstr "Voorkomt dat berichten en reacties met identieke inhoud en die binnen twee minuten zijn verstuurd, worden gepubliceerd. "
-
-#: ../../include/features.php:261
-msgid "Network and Stream Filtering"
-msgstr "Netwerk- en streamfilter"
-
-#: ../../include/features.php:265
-msgid "Search by Date"
-msgstr "Zoek op datum"
-
-#: ../../include/features.php:266
-msgid "Ability to select posts by date ranges"
-msgstr "Mogelijkheid om berichten op datum te filteren "
-
-#: ../../include/features.php:274 ../../include/group.php:311
-msgid "Privacy Groups"
-msgstr "Privacygroepen"
-
-#: ../../include/features.php:275
-msgid "Enable management and selection of privacy groups"
-msgstr "Beheer en selectie van privacygroepen inschakelen"
-
-#: ../../include/features.php:283 ../../include/widgets.php:283
-msgid "Saved Searches"
-msgstr "Opgeslagen zoekopdrachten"
-
-#: ../../include/features.php:284
-msgid "Save search terms for re-use"
-msgstr "Sla zoekopdrachten op voor hergebruik"
-
-#: ../../include/features.php:292
-msgid "Network Personal Tab"
-msgstr "Persoonlijke netwerktab"
-
-#: ../../include/features.php:293
-msgid "Enable tab to display only Network posts that you've interacted on"
-msgstr "Sta het toe dat de tab netwerkberichten toont waarmee je interactie had"
-
-#: ../../include/features.php:301
-msgid "Network New Tab"
-msgstr "Nieuwe netwerktab"
-
-#: ../../include/features.php:302
-msgid "Enable tab to display all new Network activity"
-msgstr "Laat de tab alle nieuwe netwerkactiviteit tonen"
-
-#: ../../include/features.php:310
-msgid "Affinity Tool"
-msgstr "Verwantschapsfilter"
-
-#: ../../include/features.php:311
-msgid "Filter stream activity by depth of relationships"
-msgstr "Filter wat je in jouw grid ziet op hoe goed je iemand kent of mag"
-
-#: ../../include/features.php:320
-msgid "Show friend and connection suggestions"
-msgstr "Toon kanaalvoorstellen"
-
-#: ../../include/features.php:328
-msgid "Connection Filtering"
-msgstr "Berichtenfilters"
-
-#: ../../include/features.php:329
-msgid "Filter incoming posts from connections based on keywords/content"
-msgstr "Filter binnenkomende berichten van connecties aan de hand van trefwoorden en taal"
-
-#: ../../include/features.php:341
-msgid "Post/Comment Tools"
-msgstr "Bericht- en reactiehulpmiddelen"
-
-#: ../../include/features.php:345
-msgid "Community Tagging"
-msgstr "Taggen door anderen"
-
-#: ../../include/features.php:346
-msgid "Ability to tag existing posts"
-msgstr "Geeft andere mensen de mogelijkheid om jouw (bestaande) berichten te taggen"
-
-#: ../../include/features.php:354
-msgid "Post Categories"
-msgstr "Categorieën berichten"
-
-#: ../../include/features.php:355
-msgid "Add categories to your posts"
-msgstr "Voeg categorieën toe aan je berichten"
-
-#: ../../include/features.php:363
-msgid "Emoji Reactions"
-msgstr "Emoji-reacties"
-
-#: ../../include/features.php:364
-msgid "Add emoji reaction ability to posts"
-msgstr "Emoji-reacties in berichten toestaan"
-
-#: ../../include/features.php:372 ../../include/contact_widgets.php:53
-#: ../../include/widgets.php:346
-msgid "Saved Folders"
-msgstr "Bewaarde mappen"
-
-#: ../../include/features.php:373
-msgid "Ability to file posts under folders"
-msgstr "Mogelijkheid om berichten in mappen op te slaan"
-
-#: ../../include/features.php:381
-msgid "Dislike Posts"
-msgstr "Vind berichten niet leuk"
-
-#: ../../include/features.php:382
-msgid "Ability to dislike posts/comments"
-msgstr "Mogelijkheid om berichten en reacties niet leuk te vinden"
-
-#: ../../include/features.php:390
-msgid "Star Posts"
-msgstr "Geef berichten een ster"
-
-#: ../../include/features.php:391
-msgid "Ability to mark special posts with a star indicator"
-msgstr "Mogelijkheid om speciale berichten met een ster te markeren"
-
-#: ../../include/features.php:399
-msgid "Tag Cloud"
-msgstr "Tagwolk"
-
-#: ../../include/features.php:400
-msgid "Provide a personal tag cloud on your channel page"
-msgstr "Zorgt voor een persoonlijke wolk met tags op jouw kanaalpagina"
-
-#: ../../include/features.php:412
-msgid "Premium Channel"
-msgstr "Premiumkanaal"
-
-#: ../../include/features.php:413
-msgid ""
-"Allows you to set restrictions and terms on those that connect with your "
-"channel"
-msgstr "Stelt je in staat om beperkingen en voorwaarden in te stellen voor jouw kanaal"
-
-#: ../../include/bb2diaspora.php:404
-msgid "Attachments:"
-msgstr "Bijlagen:"
-
-#: ../../include/bb2diaspora.php:499 ../../include/event.php:22
-#: ../../include/event.php:69
-msgid "l F d, Y \\@ g:i A"
-msgstr "l d F Y \\@ G:i"
-
-#: ../../include/bb2diaspora.php:501
-msgid "$Projectname event notification:"
-msgstr "Notificatie $Projectname-gebeurtenis:"
-
-#: ../../include/bb2diaspora.php:505 ../../include/event.php:30
-#: ../../include/event.php:73
-msgid "Starts:"
-msgstr "Start:"
-
-#: ../../include/bb2diaspora.php:513 ../../include/event.php:40
-#: ../../include/event.php:77
-msgid "Finishes:"
-msgstr "Einde:"
-
-#: ../../include/bookmarks.php:35
-#, php-format
-msgid "%1$s's bookmarks"
-msgstr "Bladwijzers van %1$s"
-
-#: ../../include/help.php:31
+#: ../../include/help.php:33
msgid "Help:"
msgstr "Hulp:"
-#: ../../include/help.php:63
+#: ../../include/help.php:65
msgid "Not Found"
msgstr "Niet gevonden"
-#: ../../include/wiki.php:546 ../../include/bbcode.php:552
-#: ../../include/bbcode.php:683
-msgid "Different viewers will see this text differently"
-msgstr "Deze tekst wordt per persoon anders weergeven."
-
-#: ../../include/zot.php:667
-msgid "Invalid data packet"
-msgstr "Datapakket ongeldig"
-
-#: ../../include/zot.php:683
-msgid "Unable to verify channel signature"
-msgstr "Kanaalkenmerk kon niet worden geverifieerd. "
-
-#: ../../include/zot.php:2325
-#, php-format
-msgid "Unable to verify site signature for %s"
-msgstr "Hubkenmerk voor %s kon niet worden geverifieerd"
-
-#: ../../include/zot.php:3723
-msgid "invalid target signature"
-msgstr "ongeldig doelkenmerk"
-
#: ../../include/page_widgets.php:7
msgid "New Page"
msgstr "Nieuwe pagina"
-#: ../../include/message.php:32
-msgid "Unable to determine sender."
-msgstr "Afzender kan niet bepaald worden."
-
-#: ../../include/message.php:69
-msgid "No recipient provided."
-msgstr "Geen ontvanger opgegeven."
-
-#: ../../include/message.php:74
-msgid "[no subject]"
-msgstr "[geen onderwerp]"
-
-#: ../../include/message.php:225
-msgid "Stored post could not be verified."
-msgstr "Opgeslagen bericht kon niet worden geverifieerd."
-
#: ../../include/contact_widgets.php:11
#, php-format
msgid "%d invitation available"
@@ -11594,17 +11671,6 @@ msgstr "Vrienden uitnodigen"
msgid "Advanced example: name=fred and country=iceland"
msgstr "Geavanceerd voorbeeld (Engels): name=jan en country=nederland"
-#: ../../include/contact_widgets.php:56 ../../include/contact_widgets.php:94
-#: ../../include/widgets.php:349 ../../include/widgets.php:468
-msgid "Everything"
-msgstr "Alles"
-
-#: ../../include/contact_widgets.php:91 ../../include/taxonomy.php:188
-#: ../../include/taxonomy.php:270 ../../include/widgets.php:46
-#: ../../include/widgets.php:465
-msgid "Categories"
-msgstr "Categorieën"
-
#: ../../include/contact_widgets.php:122
#, php-format
msgid "%d connection in common"
@@ -11673,7 +11739,7 @@ msgstr "Beoordeel dit kanaal (dit is openbaar)"
#: ../../include/js_strings.php:21
msgid "Describe (optional)"
-msgstr "Omschrijving (optioneel)"
+msgstr "Omschrijving (niet verplicht)"
#: ../../include/js_strings.php:23
msgid "Please enter a link URL"
@@ -11756,19 +11822,19 @@ msgstr " "
msgid "timeago.numbers"
msgstr "timeago.numbers"
-#: ../../include/js_strings.php:45 ../../include/text.php:1307
+#: ../../include/js_strings.php:45 ../../include/text.php:1331
msgid "January"
msgstr "januari"
-#: ../../include/js_strings.php:46 ../../include/text.php:1307
+#: ../../include/js_strings.php:46 ../../include/text.php:1331
msgid "February"
msgstr "februari"
-#: ../../include/js_strings.php:47 ../../include/text.php:1307
+#: ../../include/js_strings.php:47 ../../include/text.php:1331
msgid "March"
msgstr "maart"
-#: ../../include/js_strings.php:48 ../../include/text.php:1307
+#: ../../include/js_strings.php:48 ../../include/text.php:1331
msgid "April"
msgstr "april"
@@ -11777,31 +11843,31 @@ msgctxt "long"
msgid "May"
msgstr "mei"
-#: ../../include/js_strings.php:50 ../../include/text.php:1307
+#: ../../include/js_strings.php:50 ../../include/text.php:1331
msgid "June"
msgstr "juni"
-#: ../../include/js_strings.php:51 ../../include/text.php:1307
+#: ../../include/js_strings.php:51 ../../include/text.php:1331
msgid "July"
msgstr "juli"
-#: ../../include/js_strings.php:52 ../../include/text.php:1307
+#: ../../include/js_strings.php:52 ../../include/text.php:1331
msgid "August"
msgstr "augustus"
-#: ../../include/js_strings.php:53 ../../include/text.php:1307
+#: ../../include/js_strings.php:53 ../../include/text.php:1331
msgid "September"
msgstr "september"
-#: ../../include/js_strings.php:54 ../../include/text.php:1307
+#: ../../include/js_strings.php:54 ../../include/text.php:1331
msgid "October"
msgstr "oktober"
-#: ../../include/js_strings.php:55 ../../include/text.php:1307
+#: ../../include/js_strings.php:55 ../../include/text.php:1331
msgid "November"
msgstr "november"
-#: ../../include/js_strings.php:56 ../../include/text.php:1307
+#: ../../include/js_strings.php:56 ../../include/text.php:1331
msgid "December"
msgstr "december"
@@ -11854,31 +11920,31 @@ msgstr "nov"
msgid "Dec"
msgstr "dec"
-#: ../../include/js_strings.php:69 ../../include/text.php:1303
+#: ../../include/js_strings.php:69 ../../include/text.php:1327
msgid "Sunday"
msgstr "zondag"
-#: ../../include/js_strings.php:70 ../../include/text.php:1303
+#: ../../include/js_strings.php:70 ../../include/text.php:1327
msgid "Monday"
msgstr "maandag"
-#: ../../include/js_strings.php:71 ../../include/text.php:1303
+#: ../../include/js_strings.php:71 ../../include/text.php:1327
msgid "Tuesday"
msgstr "dinsdag"
-#: ../../include/js_strings.php:72 ../../include/text.php:1303
+#: ../../include/js_strings.php:72 ../../include/text.php:1327
msgid "Wednesday"
msgstr "woensdag"
-#: ../../include/js_strings.php:73 ../../include/text.php:1303
+#: ../../include/js_strings.php:73 ../../include/text.php:1327
msgid "Thursday"
msgstr "donderdag"
-#: ../../include/js_strings.php:74 ../../include/text.php:1303
+#: ../../include/js_strings.php:74 ../../include/text.php:1327
msgid "Friday"
msgstr "vrijdag"
-#: ../../include/js_strings.php:75 ../../include/text.php:1303
+#: ../../include/js_strings.php:75 ../../include/text.php:1327
msgid "Saturday"
msgstr "zaterdag"
@@ -11935,905 +12001,1043 @@ msgctxt "calendar"
msgid "All day"
msgstr "hele dag"
-#: ../../include/taxonomy.php:228 ../../include/taxonomy.php:249
-msgid "Tags"
-msgstr "Tags"
-
-#: ../../include/taxonomy.php:293
-msgid "Keywords"
-msgstr "Trefwoorden"
+#: ../../include/dir_fns.php:141
+msgid "Directory Options"
+msgstr "Opties kanalengids"
-#: ../../include/taxonomy.php:314
-msgid "have"
-msgstr "heb"
+#: ../../include/dir_fns.php:143
+msgid "Safe Mode"
+msgstr "Veilig zoeken"
-#: ../../include/taxonomy.php:314
-msgid "has"
-msgstr "heeft"
+#: ../../include/dir_fns.php:144
+msgid "Public Forums Only"
+msgstr "Alleen openbare forums"
-#: ../../include/taxonomy.php:315
-msgid "want"
-msgstr "wil"
+#: ../../include/dir_fns.php:145
+msgid "This Website Only"
+msgstr "Alleen deze hub"
-#: ../../include/taxonomy.php:315
-msgid "wants"
-msgstr "wil"
+#: ../../include/network.php:756
+msgid "view full size"
+msgstr "volledige grootte tonen"
-#: ../../include/taxonomy.php:316
-msgid "likes"
-msgstr "vindt dit leuk"
+#: ../../include/network.php:2011
+msgid "No Subject"
+msgstr "Geen onderwerp"
-#: ../../include/taxonomy.php:317
-msgid "dislikes"
-msgstr "vindt dit niet leuk"
+#: ../../include/network.php:2267
+msgid "OStatus"
+msgstr "OStatus"
-#: ../../include/text.php:460
-msgid "prev"
-msgstr "vorige"
+#: ../../include/network.php:2268
+msgid "GNU-Social"
+msgstr "GNU social"
-#: ../../include/text.php:462
-msgid "first"
-msgstr "eerste"
+#: ../../include/network.php:2269
+msgid "RSS/Atom"
+msgstr "RSS/Atom"
-#: ../../include/text.php:491
-msgid "last"
-msgstr "laatste"
+#: ../../include/network.php:2272
+msgid "Facebook"
+msgstr "Facebook"
-#: ../../include/text.php:494
-msgid "next"
-msgstr "volgende"
+#: ../../include/network.php:2273
+msgid "Zot"
+msgstr "Zot"
-#: ../../include/text.php:505
-msgid "older"
-msgstr "ouder"
+#: ../../include/network.php:2274
+msgid "LinkedIn"
+msgstr "LinkedIn"
-#: ../../include/text.php:507
-msgid "newer"
-msgstr "nieuwer"
+#: ../../include/network.php:2275
+msgid "XMPP/IM"
+msgstr "XMPP/IM"
-#: ../../include/text.php:904
-msgid "No connections"
-msgstr "Geen connecties"
+#: ../../include/network.php:2276
+msgid "MySpace"
+msgstr "MySpace"
-#: ../../include/text.php:929
+#: ../../include/conversation.php:204
#, php-format
-msgid "View all %s connections"
-msgstr "Toon alle %s connecties"
+msgid "%1$s is now connected with %2$s"
+msgstr "%1$s is nu met %2$s verbonden"
-#: ../../include/text.php:1074 ../../include/text.php:1079
-msgid "poke"
-msgstr "aanstoten"
+#: ../../include/conversation.php:239
+#, php-format
+msgid "%1$s poked %2$s"
+msgstr "%1$s heeft %2$s aangestoten"
-#: ../../include/text.php:1074 ../../include/text.php:1079
-#: ../../include/conversation.php:243
+#: ../../include/conversation.php:243 ../../include/text.php:1098
+#: ../../include/text.php:1103
msgid "poked"
msgstr "aangestoten"
-#: ../../include/text.php:1080
-msgid "ping"
-msgstr "ping"
+#: ../../include/conversation.php:690
+#, php-format
+msgid "View %s's profile @ %s"
+msgstr "Bekijk het profiel van %s @ %s"
-#: ../../include/text.php:1080
-msgid "pinged"
-msgstr "gepingd"
+#: ../../include/conversation.php:710
+msgid "Categories:"
+msgstr "Categorieën:"
-#: ../../include/text.php:1081
-msgid "prod"
-msgstr "por"
+#: ../../include/conversation.php:711
+msgid "Filed under:"
+msgstr "Bewaard onder:"
-#: ../../include/text.php:1081
-msgid "prodded"
-msgstr "gepord"
+#: ../../include/conversation.php:736
+msgid "View in context"
+msgstr "In context bekijken"
-#: ../../include/text.php:1082
-msgid "slap"
-msgstr "slaan"
+#: ../../include/conversation.php:832
+msgid "remove"
+msgstr "verwijderen"
-#: ../../include/text.php:1082
-msgid "slapped"
-msgstr "sloeg"
+#: ../../include/conversation.php:836 ../../include/nav.php:292
+msgid "Loading..."
+msgstr "Aan het laden..."
-#: ../../include/text.php:1083
-msgid "finger"
-msgstr "finger"
+#: ../../include/conversation.php:837
+msgid "Delete Selected Items"
+msgstr "Verwijder de geselecteerde items"
-#: ../../include/text.php:1083
-msgid "fingered"
-msgstr "gefingerd"
+#: ../../include/conversation.php:930 ../../include/conversation.php:972
+msgid "View Source"
+msgstr "Bron weergeven"
-#: ../../include/text.php:1084
-msgid "rebuff"
-msgstr "afpoeieren"
+#: ../../include/conversation.php:931 ../../include/conversation.php:982
+msgid "Follow Thread"
+msgstr "Conversatie volgen"
-#: ../../include/text.php:1084
-msgid "rebuffed"
-msgstr "afgepoeierd"
+#: ../../include/conversation.php:932 ../../include/conversation.php:991
+msgid "Unfollow Thread"
+msgstr "Conversatie niet meer volgen"
-#: ../../include/text.php:1096
-msgid "happy"
-msgstr "gelukkig"
+#: ../../include/conversation.php:937 ../../include/conversation.php:1059
+msgid "Activity/Posts"
+msgstr "Activiteit/berichten connectie"
-#: ../../include/text.php:1097
-msgid "sad"
-msgstr "bedroefd"
+#: ../../include/conversation.php:939 ../../include/conversation.php:1079
+msgid "Edit Connection"
+msgstr "Connectie bewerken"
-#: ../../include/text.php:1098
-msgid "mellow"
-msgstr "mellow"
+#: ../../include/conversation.php:940 ../../include/conversation.php:1089
+msgid "Message"
+msgstr "Bericht"
-#: ../../include/text.php:1099
-msgid "tired"
-msgstr "moe"
+#: ../../include/conversation.php:1223
+#, php-format
+msgid "%s likes this."
+msgstr "%s vindt dit leuk."
-#: ../../include/text.php:1100
-msgid "perky"
-msgstr "parmantig"
+#: ../../include/conversation.php:1223
+#, php-format
+msgid "%s doesn't like this."
+msgstr "%s vindt dit niet leuk."
-#: ../../include/text.php:1101
-msgid "angry"
-msgstr "boos"
+#: ../../include/conversation.php:1227
+#, php-format
+msgid "<span %1$s>%2$d people</span> like this."
+msgid_plural "<span %1$s>%2$d people</span> like this."
+msgstr[0] "<span %1$s>%2$d persoon</span> vindt dit leuk."
+msgstr[1] "<span %1$s>%2$d personen</span> vinden dit leuk."
-#: ../../include/text.php:1102
-msgid "stupefied"
-msgstr "verbijsterd"
+#: ../../include/conversation.php:1229
+#, php-format
+msgid "<span %1$s>%2$d people</span> don't like this."
+msgid_plural "<span %1$s>%2$d people</span> don't like this."
+msgstr[0] "<span %1$s>%2$d persoon</span> vindt dit niet leuk."
+msgstr[1] "<span %1$s>%2$d personen</span> vinden dit niet leuk."
-#: ../../include/text.php:1103
-msgid "puzzled"
-msgstr "verward"
+#: ../../include/conversation.php:1235
+msgid "and"
+msgstr "en"
-#: ../../include/text.php:1104
-msgid "interested"
-msgstr "geïnteresseerd"
+#: ../../include/conversation.php:1238
+#, php-format
+msgid ", and %d other people"
+msgid_plural ", and %d other people"
+msgstr[0] ", en %d ander persoon"
+msgstr[1] ", en %d andere personen"
-#: ../../include/text.php:1105
-msgid "bitter"
-msgstr "verbitterd"
+#: ../../include/conversation.php:1239
+#, php-format
+msgid "%s like this."
+msgstr "%s vinden dit leuk."
-#: ../../include/text.php:1106
-msgid "cheerful"
-msgstr "vrolijk"
+#: ../../include/conversation.php:1239
+#, php-format
+msgid "%s don't like this."
+msgstr "%s vinden dit niet leuk."
-#: ../../include/text.php:1107
-msgid "alive"
-msgstr "levendig"
+#: ../../include/conversation.php:1282
+msgid "Set your location"
+msgstr "Locatie instellen"
-#: ../../include/text.php:1108
-msgid "annoyed"
-msgstr "geërgerd"
+#: ../../include/conversation.php:1283
+msgid "Clear browser location"
+msgstr "Locatie van webbrowser wissen"
-#: ../../include/text.php:1109
-msgid "anxious"
-msgstr "bezorgd"
+#: ../../include/conversation.php:1331
+msgid "Tag term:"
+msgstr "Tag:"
-#: ../../include/text.php:1110
-msgid "cranky"
-msgstr "humeurig"
+#: ../../include/conversation.php:1332
+msgid "Where are you right now?"
+msgstr "Waar bevind je je op dit moment?"
-#: ../../include/text.php:1111
-msgid "disturbed"
-msgstr "verontrust"
+#: ../../include/conversation.php:1337
+msgid "Choose a different album..."
+msgstr "Kies een ander album..."
-#: ../../include/text.php:1112
-msgid "frustrated"
-msgstr "gefrustreerd "
+#: ../../include/conversation.php:1341
+msgid "Comments enabled"
+msgstr "Reacties ingeschakeld"
-#: ../../include/text.php:1113
-msgid "depressed"
-msgstr "gedeprimeerd"
+#: ../../include/conversation.php:1342
+msgid "Comments disabled"
+msgstr "Reacties uitgeschakeld"
-#: ../../include/text.php:1114
-msgid "motivated"
-msgstr "gemotiveerd"
+#: ../../include/conversation.php:1380
+msgid "Page link name"
+msgstr "Linknaam pagina"
-#: ../../include/text.php:1115
-msgid "relaxed"
-msgstr "ontspannen"
+#: ../../include/conversation.php:1383
+msgid "Post as"
+msgstr "Bericht plaatsen als"
-#: ../../include/text.php:1116
-msgid "surprised"
-msgstr "verrast"
+#: ../../include/conversation.php:1397
+msgid "Toggle voting"
+msgstr "Peiling in- of uitschakelen"
-#: ../../include/text.php:1307
-msgid "May"
-msgstr "mei"
+#: ../../include/conversation.php:1400
+msgid "Disable comments"
+msgstr "Reacties uitschakelen"
-#: ../../include/text.php:1384 ../../include/text.php:1388
-msgid "Unknown Attachment"
-msgstr "Onbekende bijlage"
+#: ../../include/conversation.php:1401
+msgid "Toggle comments"
+msgstr "Reacties in- of uitschakelen"
-#: ../../include/text.php:1390
-msgid "unknown"
-msgstr "onbekend"
+#: ../../include/conversation.php:1409
+msgid "Categories (optional, comma-separated list)"
+msgstr "Categorieën (niet verplicht, door komma's gescheiden lijst)"
-#: ../../include/text.php:1426
-msgid "remove category"
-msgstr "categorie verwijderen"
+#: ../../include/conversation.php:1432
+msgid "Other networks and post services"
+msgstr "Andere netwerken en diensten"
-#: ../../include/text.php:1503
-msgid "remove from file"
-msgstr "uit map verwijderen"
+#: ../../include/conversation.php:1438
+msgid "Set publish date"
+msgstr "Publicatiedatum instellen"
-#: ../../include/text.php:1770 ../../include/language.php:367
-msgid "default"
-msgstr "standaard"
+#: ../../include/conversation.php:1692
+msgid "Discover"
+msgstr "Ontdekken"
-#: ../../include/text.php:1778
-msgid "Page layout"
-msgstr "Pagina-lay-out"
+#: ../../include/conversation.php:1695
+msgid "Imported public streams"
+msgstr "Openbare streams importeren"
-#: ../../include/text.php:1778
-msgid "You can create your own with the layouts tool"
-msgstr "Je kan jouw eigen lay-out ontwerpen onder lay-outs"
+#: ../../include/conversation.php:1700
+msgid "Commented Order"
+msgstr "Nieuwe reacties bovenaan"
-#: ../../include/text.php:1820
-msgid "Page content type"
-msgstr "Opmaaktype"
+#: ../../include/conversation.php:1703
+msgid "Sort by Comment Date"
+msgstr "Berichten met nieuwe reacties bovenaan"
-#: ../../include/text.php:1953
-msgid "activity"
-msgstr "activiteit"
+#: ../../include/conversation.php:1707
+msgid "Posted Order"
+msgstr "Nieuwe berichten bovenaan"
-#: ../../include/text.php:2267
-msgid "Design Tools"
-msgstr "Ontwerp-hulpmiddelen"
+#: ../../include/conversation.php:1710
+msgid "Sort by Post Date"
+msgstr "Nieuwe berichten bovenaan"
-#: ../../include/text.php:2273
-msgid "Pages"
-msgstr "Pagina's"
+#: ../../include/conversation.php:1718
+msgid "Posts that mention or involve you"
+msgstr "Alleen berichten die jou vermelden of waar je op een andere manier bij betrokken bent"
-#: ../../include/text.php:2295
-msgid "Import website..."
-msgstr "Website importeren..."
+#: ../../include/conversation.php:1727
+msgid "Activity Stream - by date"
+msgstr "Activiteitenstroom - volgens datum"
-#: ../../include/text.php:2296
-msgid "Select folder to import"
-msgstr "Kies een map om te importeren"
+#: ../../include/conversation.php:1733
+msgid "Starred"
+msgstr "Met ster"
-#: ../../include/text.php:2297
-msgid "Import from a zipped folder:"
-msgstr "Vanuit een zipbestand importeren:"
+#: ../../include/conversation.php:1736
+msgid "Favourite Posts"
+msgstr "Favoriete berichten"
-#: ../../include/text.php:2298
-msgid "Import from cloud files:"
-msgstr "Vanuit de cloud importeren:"
+#: ../../include/conversation.php:1743
+msgid "Spam"
+msgstr "Spam"
-#: ../../include/text.php:2299
-msgid "/cloud/channel/path/to/folder"
-msgstr "/cloud/channel/maplocatie"
+#: ../../include/conversation.php:1746
+msgid "Posts flagged as SPAM"
+msgstr "Berichten gemarkeerd als SPAM"
-#: ../../include/text.php:2300
-msgid "Enter path to website files"
-msgstr "Voer de locatie in van de websitebestanden"
+#: ../../include/conversation.php:1818
+msgid "Status Messages and Posts"
+msgstr "Berichten in dit kanaal"
-#: ../../include/text.php:2301
-msgid "Select folder"
-msgstr "Kies een map"
+#: ../../include/conversation.php:1830
+msgid "Profile Details"
+msgstr "Profiel"
-#: ../../include/text.php:2302
-msgid "Export website..."
-msgstr "Website exporteren..."
+#: ../../include/conversation.php:1839 ../../include/photos.php:515
+msgid "Photo Albums"
+msgstr "Fotoalbums"
-#: ../../include/text.php:2303
-msgid "Export to a zip file"
-msgstr "Naar een zipbestand exporteren"
+#: ../../include/conversation.php:1846
+msgid "Files and Storage"
+msgstr "Bestanden en opslagruimte"
-#: ../../include/text.php:2304
-msgid "website.zip"
-msgstr "website.zip"
+#: ../../include/conversation.php:1879
+msgid "Bookmarks"
+msgstr "Bladwijzers"
-#: ../../include/text.php:2305
-msgid "Enter a name for the zip file."
-msgstr "Vul een naam in voor het zipbestand."
+#: ../../include/conversation.php:1882
+msgid "Saved Bookmarks"
+msgstr "Opgeslagen bladwijzers"
-#: ../../include/text.php:2306
-msgid "Export to cloud files"
-msgstr "Naar de cloud exporteren"
+#: ../../include/conversation.php:1892
+msgid "View Webpages"
+msgstr "Webpagina's weergeven"
-#: ../../include/text.php:2307
-msgid "/path/to/export/folder"
-msgstr "/locatie/van/export/map"
+#: ../../include/conversation.php:1958
+msgctxt "noun"
+msgid "Attending"
+msgid_plural "Attending"
+msgstr[0] "aanwezig"
+msgstr[1] "aanwezig"
-#: ../../include/text.php:2308
-msgid "Enter a path to a cloud files destination."
-msgstr "Voer de locatie in van de cloudbestemming"
+#: ../../include/conversation.php:1961
+msgctxt "noun"
+msgid "Not Attending"
+msgid_plural "Not Attending"
+msgstr[0] "niet aanwezig"
+msgstr[1] "niet aanwezig"
-#: ../../include/text.php:2309
-msgid "Specify folder"
-msgstr "Selecteer een map"
+#: ../../include/conversation.php:1964
+msgctxt "noun"
+msgid "Undecided"
+msgid_plural "Undecided"
+msgstr[0] "nog niet beslist"
+msgstr[1] "nog niet beslist"
-#: ../../include/import.php:30
+#: ../../include/conversation.php:1967
+msgctxt "noun"
+msgid "Agree"
+msgid_plural "Agrees"
+msgstr[0] "eens"
+msgstr[1] "eens"
+
+#: ../../include/conversation.php:1970
+msgctxt "noun"
+msgid "Disagree"
+msgid_plural "Disagrees"
+msgstr[0] "oneens"
+msgstr[1] "oneens"
+
+#: ../../include/conversation.php:1973
+msgctxt "noun"
+msgid "Abstain"
+msgid_plural "Abstains"
+msgstr[0] "onthouding"
+msgstr[1] "onthoudingen"
+
+#: ../../include/group.php:26
msgid ""
-"Cannot create a duplicate channel identifier on this system. Import failed."
-msgstr "Kan geen dubbele kanaal-identificator op deze hub aanmaken. Importeren mislukt."
+"A deleted group with this name was revived. Existing item permissions "
+"<strong>may</strong> apply to this group and any future members. If this is "
+"not what you intended, please create another group with a different name."
+msgstr "Een verwijderde collectie met deze naam is gereactiveerd. Bestaande itemrechten <strong>kunnen</strong> van toepassing zijn op deze collectie en toekomstige leden. Wanneer je dit niet zo bedoeld hebt, moet je een nieuwe collectie met een andere naam aanmaken."
-#: ../../include/import.php:90
-msgid "Channel clone failed. Import failed."
-msgstr "Het klonen van het kanaal is mislukt. Importeren mislukt."
+#: ../../include/group.php:268
+msgid "Add new connections to this privacy group"
+msgstr "Voeg nieuwe connecties aan deze privacygroep toe"
-#: ../../include/import.php:1354
-msgid "Unable to import element \""
-msgstr "Niet in staat om dit element te importeren: \""
+#: ../../include/group.php:309
+msgid "edit"
+msgstr "bewerken"
-#: ../../include/security.php:117
-msgid "guest:"
-msgstr "gast:"
+#: ../../include/group.php:331 ../../include/features.php:292
+msgid "Privacy Groups"
+msgstr "Privacygroepen"
-#: ../../include/security.php:535
-msgid ""
-"The form security token was not correct. This probably happened because the "
-"form has been opened for too long (>3 hours) before submitting it."
-msgstr "De beveiligings-token van het tekstvak was ongeldig. Dit is mogelijk het gevolg van dat er te lang (meer dan 3 uur) gewacht is om de tekst op te slaan. "
+#: ../../include/group.php:332
+msgid "Edit group"
+msgstr "Privacygroep bewerken"
+
+#: ../../include/group.php:333
+msgid "Add privacy group"
+msgstr "Privacygroep toevoegen"
+
+#: ../../include/group.php:334
+msgid "Channels not in any privacy group"
+msgstr "Kanalen die zich in geen enkele privacygroep bevinden"
-#: ../../include/items.php:837 ../../include/items.php:882
+#: ../../include/items.php:843 ../../include/items.php:890
msgid "(Unknown)"
msgstr "(Onbekend)"
-#: ../../include/items.php:1080
+#: ../../include/items.php:1091
msgid "Visible to anybody on the internet."
msgstr "Voor iedereen op het internet zichtbaar."
-#: ../../include/items.php:1082
+#: ../../include/items.php:1093
msgid "Visible to you only."
msgstr "Alleen voor jou zichtbaar."
-#: ../../include/items.php:1084
+#: ../../include/items.php:1095
msgid "Visible to anybody in this network."
msgstr "Voor iedereen in dit netwerk zichtbaar."
-#: ../../include/items.php:1086
+#: ../../include/items.php:1097
msgid "Visible to anybody authenticated."
msgstr "Voor iedereen die geauthenticeerd is zichtbaar."
-#: ../../include/items.php:1088
+#: ../../include/items.php:1099
#, php-format
msgid "Visible to anybody on %s."
msgstr "Voor iedereen op %s zichtbaar."
-#: ../../include/items.php:1090
+#: ../../include/items.php:1101
msgid "Visible to all connections."
msgstr "Voor alle connecties zichtbaar."
-#: ../../include/items.php:1092
+#: ../../include/items.php:1103
msgid "Visible to approved connections."
msgstr "Voor alle geaccepteerde connecties zichtbaar."
-#: ../../include/items.php:1094
+#: ../../include/items.php:1105
msgid "Visible to specific connections."
msgstr "Voor specifieke connecties zichtbaar."
-#: ../../include/items.php:3892
+#: ../../include/items.php:3917
msgid "Privacy group is empty."
msgstr "Privacygroep is leeg"
-#: ../../include/items.php:3899
+#: ../../include/items.php:3924
#, php-format
msgid "Privacy group: %s"
msgstr "Privacygroep: %s"
-#: ../../include/items.php:3911
+#: ../../include/items.php:3936
msgid "Connection not found."
msgstr "Connectie niet gevonden."
-#: ../../include/items.php:4260
+#: ../../include/items.php:4285
msgid "profile photo"
msgstr "profielfoto"
-#: ../../include/items.php:4456
+#: ../../include/items.php:4481
#, php-format
msgid "[Edited %s]"
msgstr "[%s bewerkt]"
-#: ../../include/items.php:4456
+#: ../../include/items.php:4481
msgctxt "edit_activity"
msgid "Post"
msgstr "Bericht"
-#: ../../include/items.php:4456
+#: ../../include/items.php:4481
msgctxt "edit_activity"
msgid "Comment"
msgstr "Reactie"
-#: ../../include/auth.php:148
-msgid "Logged out."
-msgstr "Uitgelogd."
+#: ../../include/markdown.php:445
+msgid "Attachments:"
+msgstr "Bijlagen:"
-#: ../../include/auth.php:275
-msgid "Failed authentication"
-msgstr "Mislukte authenticatie"
+#: ../../include/markdown.php:542
+msgid "$Projectname event notification:"
+msgstr "Notificatie $Projectname-gebeurtenis:"
-#: ../../include/activities.php:41
-msgid " and "
-msgstr " en "
+#: ../../include/security.php:117
+msgid "guest:"
+msgstr "gast:"
-#: ../../include/activities.php:49
-msgid "public profile"
-msgstr "openbaar profiel"
+#: ../../include/security.php:532
+msgid ""
+"The form security token was not correct. This probably happened because the "
+"form has been opened for too long (>3 hours) before submitting it."
+msgstr "De beveiligings-token van het tekstvak was ongeldig. Dit is mogelijk het gevolg van dat er te lang (meer dan 3 uur) gewacht is om de tekst op te slaan. "
-#: ../../include/activities.php:58
-#, php-format
-msgid "%1$s changed %2$s to &ldquo;%3$s&rdquo;"
-msgstr "%1$s veranderde %2$s naar &ldquo;%3$s&rdquo;"
+#: ../../include/nav.php:88
+msgid "Remote authentication"
+msgstr "Authenticatie op afstand"
-#: ../../include/activities.php:59
-#, php-format
-msgid "Visit %1$s's %2$s"
-msgstr "Bezoek het %2$s van %1$s"
+#: ../../include/nav.php:88
+msgid "Click to authenticate to your home hub"
+msgstr "Authenticeer jezelf via (bijvoorbeeld) jouw hub"
-#: ../../include/activities.php:62
-#, php-format
-msgid "%1$s has an updated %2$s, changing %3$s."
-msgstr "%1$s heeft een aangepaste %2$s, %3$s veranderd."
+#: ../../include/nav.php:99 ../../include/nav.php:140 ../../boot.php:1748
+msgid "Logout"
+msgstr "Uitloggen"
+
+#: ../../include/nav.php:99 ../../include/nav.php:140
+msgid "End this session"
+msgstr "Beëindig deze sessie"
+
+#: ../../include/nav.php:103
+msgid "Your profile page"
+msgstr "Jouw profielpagina"
+
+#: ../../include/nav.php:105
+msgid "Manage/Edit profiles"
+msgstr "Beheer/wijzig profielen"
+
+#: ../../include/nav.php:107
+msgid "Edit your profile"
+msgstr "Jouw profiel bewerken"
+
+#: ../../include/nav.php:130
+msgid "Sign in"
+msgstr "Inloggen"
+
+#: ../../include/nav.php:155
+msgid "Get me home"
+msgstr "Terug naar mijn hub"
+
+#: ../../include/nav.php:157
+msgid "Log me out of this site"
+msgstr "Uitloggen op deze hub"
+
+#: ../../include/nav.php:162
+msgid "Create an account"
+msgstr "Maak een account aan"
+
+#: ../../include/nav.php:174
+msgid "Help and documentation"
+msgstr "Hulp en documentatie"
+
+#: ../../include/nav.php:178
+msgid "Applications, utilities, links, games"
+msgstr "Apps"
+
+#: ../../include/nav.php:180
+msgid "Search site @name, #tag, ?docs, content"
+msgstr "Zoek een @kanaal, doorzoek inhoud hub met tekst en #tags, of doorzoek ?documentatie "
+
+#: ../../include/nav.php:182
+msgid "Channel Directory"
+msgstr "Kanalengids"
+
+#: ../../include/nav.php:194
+msgid "Your grid"
+msgstr "Jouw grid"
+
+#: ../../include/nav.php:195
+msgid "View your network/grid"
+msgstr "Jouw grid/netwerk weergeven"
+
+#: ../../include/nav.php:196
+msgid "Mark all grid notifications seen"
+msgstr "Markeer alle gridnotificaties als bekeken"
+
+#: ../../include/nav.php:198
+msgid "Channel home"
+msgstr "Jouw kanaal"
+
+#: ../../include/nav.php:199
+msgid "View your channel home"
+msgstr "Jouw kanaal weergeven"
+
+#: ../../include/nav.php:200
+msgid "Mark all channel notifications seen"
+msgstr "Alle kanaalnotificaties als gelezen markeren"
+
+#: ../../include/nav.php:206
+msgid "Notices"
+msgstr "Notificaties"
+
+#: ../../include/nav.php:206
+msgid "Notifications"
+msgstr "Notificaties"
+
+#: ../../include/nav.php:207
+msgid "View all notifications"
+msgstr "Alle notificaties weergeven"
+
+#: ../../include/nav.php:210
+msgid "Private mail"
+msgstr "Privéberichten"
+
+#: ../../include/nav.php:211
+msgid "View your private messages"
+msgstr "Privéberichten weergeven"
+
+#: ../../include/nav.php:212
+msgid "Mark all private messages seen"
+msgstr "Markeer alle privéberichten als bekeken"
+
+#: ../../include/nav.php:218
+msgid "Event Calendar"
+msgstr "Agenda"
+
+#: ../../include/nav.php:219
+msgid "View events"
+msgstr "Agenda weergeven"
+
+#: ../../include/nav.php:220
+msgid "Mark all events seen"
+msgstr "Markeer alle gebeurtenissen als bekeken"
+
+#: ../../include/nav.php:223
+msgid "Manage Your Channels"
+msgstr "Beheer je kanalen"
+
+#: ../../include/nav.php:225
+msgid "Account/Channel Settings"
+msgstr "Account-/kanaal-instellingen"
+
+#: ../../include/nav.php:233
+msgid "Site Setup and Configuration"
+msgstr "Hub instellen en beheren"
+
+#: ../../include/nav.php:297
+msgid "@name, #tag, ?doc, content"
+msgstr "@kanaal, #tag, inhoud, ?hulp"
+
+#: ../../include/nav.php:298
+msgid "Please wait..."
+msgstr "Wachten aub..."
-#: ../../include/attach.php:248 ../../include/attach.php:336
+#: ../../include/nav.php:300
+msgid "Add Apps"
+msgstr "Apps toevoegen"
+
+#: ../../include/attach.php:250 ../../include/attach.php:338
msgid "Item was not found."
msgstr "Item niet gevonden"
-#: ../../include/attach.php:497
+#: ../../include/attach.php:499
msgid "No source file."
msgstr "Geen bronbestand."
-#: ../../include/attach.php:519
+#: ../../include/attach.php:521
msgid "Cannot locate file to replace"
msgstr "Kan het te vervangen bestand niet vinden"
-#: ../../include/attach.php:537
+#: ../../include/attach.php:539
msgid "Cannot locate file to revise/update"
msgstr "Kan het bestand wat aangepast moet worden niet vinden"
-#: ../../include/attach.php:668
+#: ../../include/attach.php:670
#, php-format
msgid "File exceeds size limit of %d"
msgstr "Bestand is groter dan de toegelaten %d"
-#: ../../include/attach.php:682
+#: ../../include/attach.php:684
#, php-format
msgid "You have reached your limit of %1$.0f Mbytes attachment storage."
msgstr "Je hebt jouw limiet van %1$.0f MB opslagruimte voor bijlagen bereikt."
-#: ../../include/attach.php:852
+#: ../../include/attach.php:854
msgid "File upload failed. Possible system limit or action terminated."
msgstr "Uploaden van bestand mislukt. Mogelijk systeemlimiet bereikt of actie afgebroken."
-#: ../../include/attach.php:865
+#: ../../include/attach.php:867
msgid "Stored file could not be verified. Upload failed."
msgstr "Opgeslagen bestand kon niet worden geverifieerd. Uploaden mislukt."
-#: ../../include/attach.php:920 ../../include/attach.php:936
+#: ../../include/attach.php:922 ../../include/attach.php:938
msgid "Path not available."
msgstr "Locatie niet beschikbaar."
-#: ../../include/attach.php:982 ../../include/attach.php:1140
+#: ../../include/attach.php:984 ../../include/attach.php:1142
msgid "Empty pathname"
msgstr "Ontbrekende locatienaam"
-#: ../../include/attach.php:1008
+#: ../../include/attach.php:1010
msgid "duplicate filename or path"
msgstr "dubbele bestandsnaam of locatie"
-#: ../../include/attach.php:1030
+#: ../../include/attach.php:1032
msgid "Path not found."
msgstr "Locatie niet gevonden"
-#: ../../include/attach.php:1094
+#: ../../include/attach.php:1096
msgid "mkdir failed."
msgstr "directory aanmaken (mkdir) mislukt."
-#: ../../include/attach.php:1098
+#: ../../include/attach.php:1100
msgid "database storage failed."
msgstr "opslag in database mislukt."
-#: ../../include/attach.php:1146
+#: ../../include/attach.php:1148
msgid "Empty path"
msgstr "Ontbrekende locatie"
-#: ../../include/event.php:824
-msgid "This event has been added to your calendar."
-msgstr "Dit evenement is aan jouw agenda toegevoegd."
-
-#: ../../include/event.php:1024
-msgid "Not specified"
-msgstr "Niet aangegeven"
-
-#: ../../include/event.php:1025
-msgid "Needs Action"
-msgstr "Actie vereist"
-
-#: ../../include/event.php:1026
-msgid "Completed"
-msgstr "Voltooid"
-
-#: ../../include/event.php:1027
-msgid "In Process"
-msgstr "In behandeling"
-
-#: ../../include/event.php:1028
-msgid "Cancelled"
-msgstr "Geannuleerd"
-
-#: ../../include/follow.php:27
-msgid "Channel is blocked on this site."
-msgstr "Kanaal is op deze hub geblokkeerd."
-
-#: ../../include/follow.php:32
-msgid "Channel location missing."
-msgstr "Ontbrekende kanaallocatie."
-
-#: ../../include/follow.php:80
-msgid "Response from remote channel was incomplete."
-msgstr "Antwoord van het kanaal op afstand was niet volledig."
+#: ../../include/text.php:461
+msgid "prev"
+msgstr "vorige"
-#: ../../include/follow.php:97
-msgid "Channel was deleted and no longer exists."
-msgstr "Kanaal is verwijderd en bestaat niet meer."
+#: ../../include/text.php:463
+msgid "first"
+msgstr "eerste"
-#: ../../include/follow.php:147 ../../include/follow.php:183
-msgid "Protocol disabled."
-msgstr "Protocol uitgeschakeld."
+#: ../../include/text.php:492
+msgid "last"
+msgstr "laatste"
-#: ../../include/follow.php:171
-msgid "Channel discovery failed."
-msgstr "Kanaal ontdekken mislukt."
+#: ../../include/text.php:495
+msgid "next"
+msgstr "volgende"
-#: ../../include/follow.php:210
-msgid "Cannot connect to yourself."
-msgstr "Kan niet met jezelf verbinden"
+#: ../../include/text.php:506
+msgid "older"
+msgstr "ouder"
-#: ../../include/group.php:26
-msgid ""
-"A deleted group with this name was revived. Existing item permissions "
-"<strong>may</strong> apply to this group and any future members. If this is "
-"not what you intended, please create another group with a different name."
-msgstr "Een verwijderde collectie met deze naam is gereactiveerd. Bestaande itemrechten <strong>kunnen</strong> van toepassing zijn op deze collectie en toekomstige leden. Wanneer je dit niet zo bedoeld hebt, moet je een nieuwe collectie met een andere naam aanmaken."
+#: ../../include/text.php:508
+msgid "newer"
+msgstr "nieuwer"
-#: ../../include/group.php:248
-msgid "Add new connections to this privacy group"
-msgstr "Voeg nieuwe connecties aan deze privacygroep toe"
+#: ../../include/text.php:928
+msgid "No connections"
+msgstr "Geen connecties"
-#: ../../include/group.php:289
-msgid "edit"
-msgstr "bewerken"
+#: ../../include/text.php:953
+#, php-format
+msgid "View all %s connections"
+msgstr "Toon alle %s connecties"
-#: ../../include/group.php:312
-msgid "Edit group"
-msgstr "Privacygroep bewerken"
+#: ../../include/text.php:1098 ../../include/text.php:1103
+msgid "poke"
+msgstr "aanstoten"
-#: ../../include/group.php:313
-msgid "Add privacy group"
-msgstr "Privacygroep toevoegen"
+#: ../../include/text.php:1104
+msgid "ping"
+msgstr "ping"
-#: ../../include/group.php:314
-msgid "Channels not in any privacy group"
-msgstr "Kanalen die zich in geen enkele privacygroep bevinden"
+#: ../../include/text.php:1104
+msgid "pinged"
+msgstr "gepingd"
-#: ../../include/group.php:316 ../../include/widgets.php:284
-msgid "add"
-msgstr "toevoegen"
+#: ../../include/text.php:1105
+msgid "prod"
+msgstr "por"
-#: ../../include/language.php:380
-msgid "Select an alternate language"
-msgstr "Kies een andere taal"
+#: ../../include/text.php:1105
+msgid "prodded"
+msgstr "gepord"
-#: ../../include/photos.php:115
-#, php-format
-msgid "Image exceeds website size limit of %lu bytes"
-msgstr "Afbeelding is groter dan op deze hub toegestane limiet van %lu bytes"
+#: ../../include/text.php:1106
+msgid "slap"
+msgstr "slaan"
-#: ../../include/photos.php:122
-msgid "Image file is empty."
-msgstr "Afbeeldingsbestand is leeg"
+#: ../../include/text.php:1106
+msgid "slapped"
+msgstr "sloeg"
-#: ../../include/photos.php:260
-msgid "Photo storage failed."
-msgstr "Foto kan niet worden opgeslagen"
+#: ../../include/text.php:1107
+msgid "finger"
+msgstr "finger"
-#: ../../include/photos.php:300
-msgid "a new photo"
-msgstr "een nieuwe foto"
+#: ../../include/text.php:1107
+msgid "fingered"
+msgstr "gefingerd"
-#: ../../include/photos.php:304
-#, php-format
-msgctxt "photo_upload"
-msgid "%1$s posted %2$s to %3$s"
-msgstr "%1$s plaatste %2$s op %3$s"
+#: ../../include/text.php:1108
+msgid "rebuff"
+msgstr "afpoeieren"
-#: ../../include/photos.php:507 ../../include/conversation.php:1677
-msgid "Photo Albums"
-msgstr "Fotoalbums"
+#: ../../include/text.php:1108
+msgid "rebuffed"
+msgstr "afgepoeierd"
-#: ../../include/photos.php:511
-msgid "Upload New Photos"
-msgstr "Nieuwe foto's uploaden"
+#: ../../include/text.php:1120
+msgid "happy"
+msgstr "gelukkig"
-#: ../../include/acl_selectors.php:198
-msgid "Who can see this?"
-msgstr "Wie kan dit zien?"
+#: ../../include/text.php:1121
+msgid "sad"
+msgstr "bedroefd"
-#: ../../include/acl_selectors.php:199
-msgid "Custom selection"
-msgstr "Handmatige selectie"
+#: ../../include/text.php:1122
+msgid "mellow"
+msgstr "mellow"
-#: ../../include/acl_selectors.php:200
-msgid ""
-"Select \"Show\" to allow viewing. \"Don't show\" lets you override and limit"
-" the scope of \"Show\"."
-msgstr "Kies \"Tonen\" om weergave toe te staan. Met \"Niet tonen\" kan je uitzonderingen maken op \"Tonen\"."
+#: ../../include/text.php:1123
+msgid "tired"
+msgstr "moe"
-#: ../../include/acl_selectors.php:201
-msgid "Show"
-msgstr "Tonen"
+#: ../../include/text.php:1124
+msgid "perky"
+msgstr "parmantig"
-#: ../../include/acl_selectors.php:202
-msgid "Don't show"
-msgstr "Niet tonen"
+#: ../../include/text.php:1125
+msgid "angry"
+msgstr "boos"
-#: ../../include/acl_selectors.php:235
-#, php-format
-msgid ""
-"Post permissions %s cannot be changed %s after a post is shared.</br />These"
-" permissions set who is allowed to view the post."
-msgstr "Permissies van berichten %s zijn niet meer te veranderen %s nadat een bericht is gedeeld.</br />Met deze permissies bepaal je wie het bericht kan zien."
+#: ../../include/text.php:1126
+msgid "stupefied"
+msgstr "verbijsterd"
-#: ../../include/oembed.php:312
-msgid " by "
-msgstr " door "
+#: ../../include/text.php:1127
+msgid "puzzled"
+msgstr "verward"
-#: ../../include/oembed.php:313
-msgid " on "
-msgstr " op "
+#: ../../include/text.php:1128
+msgid "interested"
+msgstr "geïnteresseerd"
-#: ../../include/oembed.php:342
-msgid "Embedded content"
-msgstr "Ingesloten (embedded) inhoud"
+#: ../../include/text.php:1129
+msgid "bitter"
+msgstr "verbitterd"
-#: ../../include/oembed.php:351
-msgid "Embedding disabled"
-msgstr "Insluiten (embedding) uitgeschakeld"
+#: ../../include/text.php:1130
+msgid "cheerful"
+msgstr "vrolijk"
-#: ../../include/widgets.php:103
-msgid "System"
-msgstr "Systeem"
+#: ../../include/text.php:1131
+msgid "alive"
+msgstr "levendig"
-#: ../../include/widgets.php:106
-msgid "New App"
-msgstr "Nieuwe app"
+#: ../../include/text.php:1132
+msgid "annoyed"
+msgstr "geërgerd"
-#: ../../include/widgets.php:154
-msgid "Suggestions"
-msgstr "Voorgestelde kanalen"
+#: ../../include/text.php:1133
+msgid "anxious"
+msgstr "bezorgd"
-#: ../../include/widgets.php:155
-msgid "See more..."
-msgstr "Meer..."
+#: ../../include/text.php:1134
+msgid "cranky"
+msgstr "humeurig"
-#: ../../include/widgets.php:175
-#, php-format
-msgid "You have %1$.0f of %2$.0f allowed connections."
-msgstr "Je hebt %1$.0f van de %2$.0f toegestane connecties."
+#: ../../include/text.php:1135
+msgid "disturbed"
+msgstr "verontrust"
-#: ../../include/widgets.php:181
-msgid "Add New Connection"
-msgstr "Nieuwe connectie toevoegen"
+#: ../../include/text.php:1136
+msgid "frustrated"
+msgstr "gefrustreerd "
-#: ../../include/widgets.php:182
-msgid "Enter channel address"
-msgstr "Vul kanaaladres in"
+#: ../../include/text.php:1137
+msgid "depressed"
+msgstr "gedeprimeerd"
-#: ../../include/widgets.php:183
-msgid "Examples: bob@example.com, https://example.com/barbara"
-msgstr "Voorbeelden: bob@example.com, http://example.com/barbara"
+#: ../../include/text.php:1138
+msgid "motivated"
+msgstr "gemotiveerd"
-#: ../../include/widgets.php:199
-msgid "Notes"
-msgstr "Aantekeningen"
+#: ../../include/text.php:1139
+msgid "relaxed"
+msgstr "ontspannen"
-#: ../../include/widgets.php:275
-msgid "Remove term"
-msgstr "Verwijder zoekterm"
+#: ../../include/text.php:1140
+msgid "surprised"
+msgstr "verrast"
-#: ../../include/widgets.php:390
-msgid "Archives"
-msgstr "Archieven"
+#: ../../include/text.php:1331
+msgid "May"
+msgstr "mei"
-#: ../../include/widgets.php:552
-msgid "Refresh"
-msgstr "Vernieuwen"
+#: ../../include/text.php:1408 ../../include/text.php:1412
+msgid "Unknown Attachment"
+msgstr "Onbekende bijlage"
-#: ../../include/widgets.php:592
-msgid "Account settings"
-msgstr "Account"
+#: ../../include/text.php:1414
+msgid "unknown"
+msgstr "onbekend"
-#: ../../include/widgets.php:598
-msgid "Channel settings"
-msgstr "Kanaal"
+#: ../../include/text.php:1450
+msgid "remove category"
+msgstr "categorie verwijderen"
-#: ../../include/widgets.php:607
-msgid "Additional features"
-msgstr "Extra functies"
+#: ../../include/text.php:1527
+msgid "remove from file"
+msgstr "uit map verwijderen"
-#: ../../include/widgets.php:614
-msgid "Feature/Addon settings"
-msgstr "Plugin-instellingen"
+#: ../../include/text.php:1796
+msgid "Page layout"
+msgstr "Pagina-lay-out"
-#: ../../include/widgets.php:620
-msgid "Display settings"
-msgstr "Weergave"
+#: ../../include/text.php:1796
+msgid "You can create your own with the layouts tool"
+msgstr "Je kan jouw eigen lay-out ontwerpen onder lay-outs"
-#: ../../include/widgets.php:627
-msgid "Manage locations"
-msgstr "Locaties beheren"
+#: ../../include/text.php:1838
+msgid "Page content type"
+msgstr "Opmaaktype"
-#: ../../include/widgets.php:634
-msgid "Export channel"
-msgstr "Kanaal exporteren"
+#: ../../include/text.php:1971
+msgid "activity"
+msgstr "activiteit"
-#: ../../include/widgets.php:640
-msgid "Connected apps"
-msgstr "Verbonden applicaties"
+#: ../../include/text.php:2285
+msgid "Design Tools"
+msgstr "Ontwerp-hulpmiddelen"
-#: ../../include/widgets.php:664
-msgid "Premium Channel Settings"
-msgstr "Instellingen premiumkanaal"
+#: ../../include/text.php:2291
+msgid "Pages"
+msgstr "Pagina's"
-#: ../../include/widgets.php:693
-msgid "Private Mail Menu"
-msgstr "Privéberichten"
+#: ../../include/text.php:2313
+msgid "Import website..."
+msgstr "Website importeren..."
-#: ../../include/widgets.php:695
-msgid "Combined View"
-msgstr "Gecombineerd postvak"
+#: ../../include/text.php:2314
+msgid "Select folder to import"
+msgstr "Kies een map om te importeren"
-#: ../../include/widgets.php:727 ../../include/widgets.php:739
-msgid "Conversations"
-msgstr "Conversaties"
+#: ../../include/text.php:2315
+msgid "Import from a zipped folder:"
+msgstr "Vanuit een zipbestand importeren:"
-#: ../../include/widgets.php:731
-msgid "Received Messages"
-msgstr "Ontvangen berichten"
+#: ../../include/text.php:2316
+msgid "Import from cloud files:"
+msgstr "Vanuit de cloud importeren:"
-#: ../../include/widgets.php:735
-msgid "Sent Messages"
-msgstr "Verzonden berichten"
+#: ../../include/text.php:2317
+msgid "/cloud/channel/path/to/folder"
+msgstr "/cloud/channel/maplocatie"
-#: ../../include/widgets.php:749
-msgid "No messages."
-msgstr "Geen berichten"
+#: ../../include/text.php:2318
+msgid "Enter path to website files"
+msgstr "Voer de locatie in van de websitebestanden"
-#: ../../include/widgets.php:767
-msgid "Delete conversation"
-msgstr "Verwijder conversatie"
+#: ../../include/text.php:2319
+msgid "Select folder"
+msgstr "Kies een map"
-#: ../../include/widgets.php:793
-msgid "Events Tools"
-msgstr "Agenda-hulpmiddelen"
+#: ../../include/text.php:2320
+msgid "Export website..."
+msgstr "Website exporteren..."
-#: ../../include/widgets.php:794
-msgid "Export Calendar"
-msgstr "Exporteren"
+#: ../../include/text.php:2321
+msgid "Export to a zip file"
+msgstr "Naar een zipbestand exporteren"
-#: ../../include/widgets.php:795
-msgid "Import Calendar"
-msgstr "Importeren"
+#: ../../include/text.php:2322
+msgid "website.zip"
+msgstr "website.zip"
-#: ../../include/widgets.php:883 ../../include/conversation.php:1704
-#: ../../include/conversation.php:1707
-msgid "Chatrooms"
-msgstr "Chatkanalen"
+#: ../../include/text.php:2323
+msgid "Enter a name for the zip file."
+msgstr "Vul een naam in voor het zipbestand."
-#: ../../include/widgets.php:887
-msgid "Overview"
-msgstr "Overzicht"
+#: ../../include/text.php:2324
+msgid "Export to cloud files"
+msgstr "Naar de cloud exporteren"
-#: ../../include/widgets.php:894
-msgid "Chat Members"
-msgstr "Chatleden"
+#: ../../include/text.php:2325
+msgid "/path/to/export/folder"
+msgstr "/locatie/van/export/map"
-#: ../../include/widgets.php:906
-msgid "Wiki List"
-msgstr "Wiki's"
+#: ../../include/text.php:2326
+msgid "Enter a path to a cloud files destination."
+msgstr "Voer de locatie in van de cloudbestemming"
-#: ../../include/widgets.php:944
-msgid "Wiki Pages"
-msgstr "Wikipagina's"
+#: ../../include/text.php:2327
+msgid "Specify folder"
+msgstr "Selecteer een map"
-#: ../../include/widgets.php:949
-msgid "Add new page"
-msgstr "Nieuwe pagina toevoegen"
+#: ../../include/auth.php:148
+msgid "Logged out."
+msgstr "Uitgelogd."
-#: ../../include/widgets.php:950
-msgid "Page name"
-msgstr "Paginanaam"
+#: ../../include/auth.php:275
+msgid "Failed authentication"
+msgstr "Mislukte authenticatie"
-#: ../../include/widgets.php:983
-msgid "Bookmarked Chatrooms"
-msgstr "Bladwijzers van chatkanalen"
+#: ../../include/follow.php:26
+msgid "Channel is blocked on this site."
+msgstr "Kanaal is op deze hub geblokkeerd."
-#: ../../include/widgets.php:1014
-msgid "Suggested Chatrooms"
-msgstr "Voorgestelde chatkanalen"
+#: ../../include/follow.php:31
+msgid "Channel location missing."
+msgstr "Ontbrekende kanaallocatie."
-#: ../../include/widgets.php:1159 ../../include/widgets.php:1271
-msgid "photo/image"
-msgstr "foto/afbeelding"
+#: ../../include/follow.php:73
+msgid "Response from remote channel was incomplete."
+msgstr "Antwoord van het kanaal op afstand was niet volledig."
-#: ../../include/widgets.php:1214
-msgid "Click to show more"
-msgstr "Klik voor meer"
+#: ../../include/follow.php:90
+msgid "Channel was deleted and no longer exists."
+msgstr "Kanaal is verwijderd en bestaat niet meer."
-#: ../../include/widgets.php:1365
-msgid "Rating Tools"
-msgstr "Beoordelingen"
+#: ../../include/follow.php:140 ../../include/follow.php:175
+msgid "Protocol disabled."
+msgstr "Protocol uitgeschakeld."
-#: ../../include/widgets.php:1369 ../../include/widgets.php:1371
-msgid "Rate Me"
-msgstr "Beoordeel mij"
+#: ../../include/follow.php:163
+msgid "Channel discovery failed."
+msgstr "Kanaal ontdekken mislukt."
-#: ../../include/widgets.php:1374
-msgid "View Ratings"
-msgstr "Bekijk beoordelingen"
+#: ../../include/follow.php:202
+msgid "Cannot connect to yourself."
+msgstr "Kan niet met jezelf verbinden"
-#: ../../include/widgets.php:1467
-msgid "Forums"
-msgstr "Forums"
+#: ../../include/import.php:30
+msgid ""
+"Cannot create a duplicate channel identifier on this system. Import failed."
+msgstr "Kan geen dubbele kanaal-identificator op deze hub aanmaken. Importeren mislukt."
-#: ../../include/widgets.php:1496
-msgid "Tasks"
-msgstr "Taken"
+#: ../../include/import.php:90
+msgid "Channel clone failed. Import failed."
+msgstr "Het klonen van het kanaal is mislukt. Importeren mislukt."
-#: ../../include/widgets.php:1562 ../../include/widgets.php:1600
-msgid "Member registrations waiting for confirmation"
-msgstr "Accounts die op goedkeuring wachten"
+#: ../../include/import.php:100
+msgid "Cloned channel not found. Import failed."
+msgstr "Gekloond kanaal niet gevonden. Importeren mislukt."
-#: ../../include/widgets.php:1568
-msgid "Inspect queue"
-msgstr "Inspecteer berichtenwachtrij"
+#: ../../include/import.php:1373
+msgid "Unable to import element \""
+msgstr "Niet in staat om dit element te importeren: \""
-#: ../../include/widgets.php:1570
-msgid "DB updates"
-msgstr "Database-updates"
+#: ../../include/message.php:32
+msgid "Unable to determine sender."
+msgstr "Afzender kan niet bepaald worden."
-#: ../../include/widgets.php:1596
-msgid "Plugin Features"
-msgstr "Plugin-opties"
+#: ../../include/message.php:69
+msgid "No recipient provided."
+msgstr "Geen ontvanger opgegeven."
-#: ../../include/network.php:729
-msgid "view full size"
-msgstr "volledige grootte tonen"
+#: ../../include/message.php:74
+msgid "[no subject]"
+msgstr "[geen onderwerp]"
-#: ../../include/network.php:1978
-msgid "No Subject"
-msgstr "Geen onderwerp"
+#: ../../include/message.php:225
+msgid "Stored post could not be verified."
+msgstr "Opgeslagen bericht kon niet worden geverifieerd."
-#: ../../include/network.php:2234
-msgid "OStatus"
-msgstr "OStatus"
+#: ../../include/oembed.php:308
+msgid " by "
+msgstr " door "
-#: ../../include/network.php:2235
-msgid "GNU-Social"
-msgstr "GNU social"
+#: ../../include/oembed.php:309
+msgid " on "
+msgstr " op "
-#: ../../include/network.php:2236
-msgid "RSS/Atom"
-msgstr "RSS/Atom"
+#: ../../include/oembed.php:338
+msgid "Embedded content"
+msgstr "Ingesloten (embedded) inhoud"
-#: ../../include/network.php:2239
-msgid "Facebook"
-msgstr "Facebook"
+#: ../../include/oembed.php:347
+msgid "Embedding disabled"
+msgstr "Insluiten (embedding) uitgeschakeld"
-#: ../../include/network.php:2240
-msgid "Zot"
-msgstr "Zot"
+#: ../../include/zot.php:649
+msgid "Invalid data packet"
+msgstr "Datapakket ongeldig"
-#: ../../include/network.php:2241
-msgid "LinkedIn"
-msgstr "LinkedIn"
+#: ../../include/zot.php:665
+msgid "Unable to verify channel signature"
+msgstr "Kanaalkenmerk kon niet worden geverifieerd. "
-#: ../../include/network.php:2242
-msgid "XMPP/IM"
-msgstr "XMPP/IM"
+#: ../../include/zot.php:2316
+#, php-format
+msgid "Unable to verify site signature for %s"
+msgstr "Hubkenmerk voor %s kon niet worden geverifieerd"
-#: ../../include/network.php:2243
-msgid "MySpace"
-msgstr "MySpace"
+#: ../../include/zot.php:3722
+msgid "invalid target signature"
+msgstr "ongeldig doelkenmerk"
#: ../../include/permissions.php:35
msgid "Can view my normal stream and posts"
@@ -12888,322 +13092,507 @@ msgid ""
"Extremely advanced. Leave this alone unless you know what you are doing"
msgstr "Zeer geavanceerd. Laat dit met rust, behalve als je weet wat je doet."
-#: ../../include/conversation.php:204
+#: ../../include/activities.php:41
+msgid " and "
+msgstr " en "
+
+#: ../../include/activities.php:49
+msgid "public profile"
+msgstr "openbaar profiel"
+
+#: ../../include/activities.php:58
#, php-format
-msgid "%1$s is now connected with %2$s"
-msgstr "%1$s is nu met %2$s verbonden"
+msgid "%1$s changed %2$s to &ldquo;%3$s&rdquo;"
+msgstr "%1$s veranderde %2$s naar &ldquo;%3$s&rdquo;"
-#: ../../include/conversation.php:239
+#: ../../include/activities.php:59
#, php-format
-msgid "%1$s poked %2$s"
-msgstr "%1$s heeft %2$s aangestoten"
+msgid "Visit %1$s's %2$s"
+msgstr "Bezoek het %2$s van %1$s"
-#: ../../include/conversation.php:690
+#: ../../include/activities.php:62
#, php-format
-msgid "View %s's profile @ %s"
-msgstr "Bekijk het profiel van %s @ %s"
+msgid "%1$s has an updated %2$s, changing %3$s."
+msgstr "%1$s heeft een aangepaste %2$s, %3$s veranderd."
-#: ../../include/conversation.php:709
-msgid "Categories:"
-msgstr "Categorieën:"
+#: ../../include/features.php:58
+msgid "General Features"
+msgstr "Algemene functies"
-#: ../../include/conversation.php:710
-msgid "Filed under:"
-msgstr "Bewaard onder:"
+#: ../../include/features.php:63
+msgid "Multiple Profiles"
+msgstr "Meerdere profielen"
-#: ../../include/conversation.php:735
-msgid "View in context"
-msgstr "In context bekijken"
+#: ../../include/features.php:64
+msgid "Ability to create multiple profiles"
+msgstr "Mogelijkheid om meerdere profielen aan te maken"
-#: ../../include/conversation.php:831
-msgid "remove"
-msgstr "verwijderen"
+#: ../../include/features.php:72
+msgid "Advanced Profiles"
+msgstr "Geavanceerde profielen"
-#: ../../include/conversation.php:836
-msgid "Delete Selected Items"
-msgstr "Verwijder de geselecteerde items"
+#: ../../include/features.php:73
+msgid "Additional profile sections and selections"
+msgstr "Extra onderdelen en keuzes voor je profiel"
-#: ../../include/conversation.php:929
-msgid "View Source"
-msgstr "Bron weergeven"
+#: ../../include/features.php:81
+msgid "Profile Import/Export"
+msgstr "Profiel importen/exporteren"
-#: ../../include/conversation.php:930
-msgid "Follow Thread"
-msgstr "Conversatie volgen"
+#: ../../include/features.php:82
+msgid "Save and load profile details across sites/channels"
+msgstr "Profielgegevens opslaan en in andere hubs/kanalen gebruiken."
-#: ../../include/conversation.php:931
-msgid "Unfollow Thread"
-msgstr "Conversatie niet meer volgen"
+#: ../../include/features.php:90
+msgid "Web Pages"
+msgstr "Webpagina's"
-#: ../../include/conversation.php:936
-msgid "Activity/Posts"
-msgstr "Activiteit/berichten connectie"
+#: ../../include/features.php:91
+msgid "Provide managed web pages on your channel"
+msgstr "Sta beheerde webpagina's op jouw kanaal toe"
-#: ../../include/conversation.php:938
-msgid "Edit Connection"
-msgstr "Connectie bewerken"
+#: ../../include/features.php:100
+msgid "Provide a wiki for your channel"
+msgstr "Voeg een wiki aan jouw kanaal toe"
-#: ../../include/conversation.php:939
-msgid "Message"
-msgstr "Bericht"
+#: ../../include/features.php:117
+msgid "Private Notes"
+msgstr "Privé-aantekeningen"
-#: ../../include/conversation.php:1075
-#, php-format
-msgid "%s likes this."
-msgstr "%s vindt dit leuk."
+#: ../../include/features.php:118
+msgid "Enables a tool to store notes and reminders (note: not encrypted)"
+msgstr "Een eenvoudige toepassing om aantekeningen en herinneringen in te bewaren (let op: niet versleuteld)"
-#: ../../include/conversation.php:1075
-#, php-format
-msgid "%s doesn't like this."
-msgstr "%s vindt dit niet leuk."
+#: ../../include/features.php:126
+msgid "Navigation Channel Select"
+msgstr "Kanaal kiezen in navigatiemenu"
-#: ../../include/conversation.php:1079
-#, php-format
-msgid "<span %1$s>%2$d people</span> like this."
-msgid_plural "<span %1$s>%2$d people</span> like this."
-msgstr[0] "<span %1$s>%2$d persoon</span> vindt dit leuk."
-msgstr[1] "<span %1$s>%2$d personen</span> vinden dit leuk."
+#: ../../include/features.php:127
+msgid "Change channels directly from within the navigation dropdown menu"
+msgstr "Kies een ander kanaal direct vanuit het dropdown-menu op de navigatiebalk"
-#: ../../include/conversation.php:1081
-#, php-format
-msgid "<span %1$s>%2$d people</span> don't like this."
-msgid_plural "<span %1$s>%2$d people</span> don't like this."
-msgstr[0] "<span %1$s>%2$d persoon</span> vindt dit niet leuk."
-msgstr[1] "<span %1$s>%2$d personen</span> vinden dit niet leuk."
+#: ../../include/features.php:135
+msgid "Photo Location"
+msgstr "Fotolocatie"
-#: ../../include/conversation.php:1087
-msgid "and"
-msgstr "en"
+#: ../../include/features.php:136
+msgid "If location data is available on uploaded photos, link this to a map."
+msgstr "Wanneer in de geüploade foto's locatiegegevens aanwezig zijn, link dit dan aan een kaart."
-#: ../../include/conversation.php:1090
-#, php-format
-msgid ", and %d other people"
-msgid_plural ", and %d other people"
-msgstr[0] ", en %d ander persoon"
-msgstr[1] ", en %d andere personen"
+#: ../../include/features.php:144
+msgid "Access Controlled Chatrooms"
+msgstr "Chatkanalen met toegangscontrole "
-#: ../../include/conversation.php:1091
-#, php-format
-msgid "%s like this."
-msgstr "%s vinden dit leuk."
+#: ../../include/features.php:145
+msgid "Provide chatrooms and chat services with access control."
+msgstr "Chatkanalen en chatdiensten met toegangscontrole aanbieden."
-#: ../../include/conversation.php:1091
-#, php-format
-msgid "%s don't like this."
-msgstr "%s vinden dit niet leuk."
+#: ../../include/features.php:154
+msgid "Provide alternate connection permission roles."
+msgstr "Extra permissietypes voor connecties aanmaken"
-#: ../../include/conversation.php:1134
-msgid "Set your location"
-msgstr "Locatie instellen"
+#: ../../include/features.php:162
+msgid "Smart Birthdays"
+msgstr "Slimme verjaardagen"
-#: ../../include/conversation.php:1135
-msgid "Clear browser location"
-msgstr "Locatie van webbrowser wissen"
+#: ../../include/features.php:163
+msgid ""
+"Make birthday events timezone aware in case your friends are scattered "
+"across the planet."
+msgstr "Maak verjaardagen bewust van tijdzones. Voor het geval dat jouw vrienden over de hele wereld verspreid zijn."
-#: ../../include/conversation.php:1183
-msgid "Tag term:"
-msgstr "Tag:"
+#: ../../include/features.php:171
+msgid "Event Timezone Selection"
+msgstr "Tijdzone gebeurtenis"
-#: ../../include/conversation.php:1184
-msgid "Where are you right now?"
-msgstr "Waar bevind je je op dit moment?"
+#: ../../include/features.php:172
+msgid "Allow event creation in timezones other than your own."
+msgstr "Sta het aanmaken van gebeurtenissen in andere tijdzones toe."
-#: ../../include/conversation.php:1189
-msgid "Choose a different album..."
-msgstr "Kies een ander album..."
+#: ../../include/features.php:180
+msgid "Advanced Directory Search"
+msgstr "Geavanceerd in de kanalengids zoeken"
-#: ../../include/conversation.php:1193
-msgid "Comments enabled"
-msgstr "Reacties ingeschakeld"
+#: ../../include/features.php:181
+msgid "Allows creation of complex directory search queries"
+msgstr "Gebruik complexe zoekopdrachten in de kanalengids"
-#: ../../include/conversation.php:1194
-msgid "Comments disabled"
-msgstr "Reacties uitgeschakeld"
+#: ../../include/features.php:189
+msgid "Advanced Theme and Layout Settings"
+msgstr "Geavanceerde thema- en lay-out-instellingen"
-#: ../../include/conversation.php:1232
-msgid "Page link name"
-msgstr "Linknaam pagina"
+#: ../../include/features.php:190
+msgid "Allows fine tuning of themes and page layouts"
+msgstr "Maakt het mogelijk dat thema's en pagina-lay-outs preciezer ingesteld kunnen worden "
-#: ../../include/conversation.php:1235
-msgid "Post as"
-msgstr "Bericht plaatsen als"
+#: ../../include/features.php:200
+msgid "Post Composition Features"
+msgstr "Functies voor het opstellen van berichten"
-#: ../../include/conversation.php:1249
-msgid "Toggle voting"
-msgstr "Peiling in- of uitschakelen"
+#: ../../include/features.php:204
+msgid "Large Photos"
+msgstr "Grote foto's"
-#: ../../include/conversation.php:1252
-msgid "Disable comments"
+#: ../../include/features.php:205
+msgid ""
+"Include large (1024px) photo thumbnails in posts. If not enabled, use small "
+"(640px) photo thumbnails"
+msgstr "Gebruik grotere foto's (1024px) in berichten. Wanneer dit is uitgeschakeld worden er kleinere foto's (640px) gebruikt."
+
+#: ../../include/features.php:214
+msgid "Automatically import channel content from other channels or feeds"
+msgstr "Automatisch inhoud uit andere kanalen of feeds importeren."
+
+#: ../../include/features.php:222
+msgid "Even More Encryption"
+msgstr "Extra encryptie"
+
+#: ../../include/features.php:223
+msgid ""
+"Allow optional encryption of content end-to-end with a shared secret key"
+msgstr "Sta toe dat inhoud extra end-to-end wordt versleuteld met een gedeelde geheime sleutel."
+
+#: ../../include/features.php:231
+msgid "Enable Voting Tools"
+msgstr "Peilingen inschakelen"
+
+#: ../../include/features.php:232
+msgid "Provide a class of post which others can vote on"
+msgstr "Maakt het mogelijk om een bericht op te stellen, waar mensen op kunnen stemmen."
+
+#: ../../include/features.php:240
+msgid "Disable Comments"
msgstr "Reacties uitschakelen"
-#: ../../include/conversation.php:1253
-msgid "Toggle comments"
-msgstr "Reacties in- of uitschakelen"
+#: ../../include/features.php:241
+msgid "Provide the option to disable comments for a post"
+msgstr "Maak het mogelijk dat reacties op een bericht kunnen worden uitgeschakeld"
-#: ../../include/conversation.php:1261
-msgid "Categories (optional, comma-separated list)"
-msgstr "Categorieën (optioneel, door komma's gescheiden lijst)"
+#: ../../include/features.php:249
+msgid "Delayed Posting"
+msgstr "Berichten uitstellen"
-#: ../../include/conversation.php:1284
-msgid "Other networks and post services"
-msgstr "Andere netwerken en diensten"
+#: ../../include/features.php:250
+msgid "Allow posts to be published at a later date"
+msgstr "Maakt het mogelijk dat berichten op een toekomstig moment gepubliceerd kunnen worden."
-#: ../../include/conversation.php:1290
-msgid "Set publish date"
-msgstr "Publicatiedatum instellen"
+#: ../../include/features.php:258
+msgid "Content Expiration"
+msgstr "Inhoud laten verlopen"
-#: ../../include/conversation.php:1544
-msgid "Discover"
-msgstr "Ontdekken"
+#: ../../include/features.php:259
+msgid "Remove posts/comments and/or private messages at a future time"
+msgstr "Berichten, reacties en/of privéberichten na een bepaalde tijd verwijderen"
-#: ../../include/conversation.php:1547
-msgid "Imported public streams"
-msgstr "Openbare streams importeren"
+#: ../../include/features.php:267
+msgid "Suppress Duplicate Posts/Comments"
+msgstr "Dubbele berichten/reacties tegenhouden"
-#: ../../include/conversation.php:1552
-msgid "Commented Order"
-msgstr "Nieuwe reacties bovenaan"
+#: ../../include/features.php:268
+msgid ""
+"Prevent posts with identical content to be published with less than two "
+"minutes in between submissions."
+msgstr "Voorkomt dat berichten en reacties met identieke inhoud en die binnen twee minuten zijn verstuurd, worden gepubliceerd. "
-#: ../../include/conversation.php:1555
-msgid "Sort by Comment Date"
-msgstr "Berichten met nieuwe reacties bovenaan"
+#: ../../include/features.php:279
+msgid "Network and Stream Filtering"
+msgstr "Netwerk- en streamfilter"
-#: ../../include/conversation.php:1559
-msgid "Posted Order"
-msgstr "Nieuwe berichten bovenaan"
+#: ../../include/features.php:283
+msgid "Search by Date"
+msgstr "Zoek op datum"
-#: ../../include/conversation.php:1562
-msgid "Sort by Post Date"
-msgstr "Nieuwe berichten bovenaan"
+#: ../../include/features.php:284
+msgid "Ability to select posts by date ranges"
+msgstr "Mogelijkheid om berichten op datum te filteren "
-#: ../../include/conversation.php:1570
-msgid "Posts that mention or involve you"
-msgstr "Alleen berichten die jou vermelden of waar je op een andere manier bij betrokken bent"
+#: ../../include/features.php:293
+msgid "Enable management and selection of privacy groups"
+msgstr "Beheer en selectie van privacygroepen inschakelen"
-#: ../../include/conversation.php:1579
-msgid "Activity Stream - by date"
-msgstr "Activiteitenstroom - volgens datum"
+#: ../../include/features.php:302
+msgid "Save search terms for re-use"
+msgstr "Sla zoekopdrachten op voor hergebruik"
-#: ../../include/conversation.php:1585
-msgid "Starred"
-msgstr "Met ster"
+#: ../../include/features.php:310
+msgid "Network Personal Tab"
+msgstr "Persoonlijke netwerktab"
-#: ../../include/conversation.php:1588
-msgid "Favourite Posts"
-msgstr "Favoriete berichten"
+#: ../../include/features.php:311
+msgid "Enable tab to display only Network posts that you've interacted on"
+msgstr "Sta het toe dat de tab netwerkberichten toont waarmee je interactie had"
-#: ../../include/conversation.php:1595
-msgid "Spam"
-msgstr "Spam"
+#: ../../include/features.php:319
+msgid "Network New Tab"
+msgstr "Nieuwe netwerktab"
-#: ../../include/conversation.php:1598
-msgid "Posts flagged as SPAM"
-msgstr "Berichten gemarkeerd als SPAM"
+#: ../../include/features.php:320
+msgid "Enable tab to display all new Network activity"
+msgstr "Laat de tab alle nieuwe netwerkactiviteit tonen"
-#: ../../include/conversation.php:1656
-msgid "Status Messages and Posts"
-msgstr "Berichten in dit kanaal"
+#: ../../include/features.php:328
+msgid "Affinity Tool"
+msgstr "Affiniteitsfilter"
-#: ../../include/conversation.php:1668
-msgid "Profile Details"
-msgstr "Profiel"
+#: ../../include/features.php:329
+msgid "Filter stream activity by depth of relationships"
+msgstr "Filter wat je in jouw grid ziet op hoe goed je iemand kent of mag"
-#: ../../include/conversation.php:1684
-msgid "Files and Storage"
-msgstr "Bestanden en opslagruimte"
+#: ../../include/features.php:338
+msgid "Show friend and connection suggestions"
+msgstr "Toon kanaalvoorstellen"
-#: ../../include/conversation.php:1720
-msgid "Saved Bookmarks"
-msgstr "Opgeslagen bladwijzers"
+#: ../../include/features.php:346
+msgid "Connection Filtering"
+msgstr "Berichtenfilters"
-#: ../../include/conversation.php:1730
-msgid "Manage Webpages"
-msgstr "Webpagina's beheren"
+#: ../../include/features.php:347
+msgid "Filter incoming posts from connections based on keywords/content"
+msgstr "Filter binnenkomende berichten van connecties aan de hand van trefwoorden en taal"
-#: ../../include/conversation.php:1795
-msgctxt "noun"
-msgid "Attending"
-msgid_plural "Attending"
-msgstr[0] "aanwezig"
-msgstr[1] "aanwezig"
+#: ../../include/features.php:359
+msgid "Post/Comment Tools"
+msgstr "Bericht- en reactiehulpmiddelen"
-#: ../../include/conversation.php:1798
-msgctxt "noun"
-msgid "Not Attending"
-msgid_plural "Not Attending"
-msgstr[0] "niet aanwezig"
-msgstr[1] "niet aanwezig"
+#: ../../include/features.php:363
+msgid "Community Tagging"
+msgstr "Taggen door anderen"
-#: ../../include/conversation.php:1801
-msgctxt "noun"
-msgid "Undecided"
-msgid_plural "Undecided"
-msgstr[0] "nog niet beslist"
-msgstr[1] "nog niet beslist"
+#: ../../include/features.php:364
+msgid "Ability to tag existing posts"
+msgstr "Geeft andere mensen de mogelijkheid om jouw (bestaande) berichten te taggen"
-#: ../../include/conversation.php:1804
-msgctxt "noun"
-msgid "Agree"
-msgid_plural "Agrees"
-msgstr[0] "eens"
-msgstr[1] "eens"
+#: ../../include/features.php:372
+msgid "Post Categories"
+msgstr "Categorieën berichten"
-#: ../../include/conversation.php:1807
-msgctxt "noun"
-msgid "Disagree"
-msgid_plural "Disagrees"
-msgstr[0] "oneens"
-msgstr[1] "oneens"
+#: ../../include/features.php:373
+msgid "Add categories to your posts"
+msgstr "Voeg categorieën toe aan je berichten"
-#: ../../include/conversation.php:1810
-msgctxt "noun"
-msgid "Abstain"
-msgid_plural "Abstains"
-msgstr[0] "onthouding"
-msgstr[1] "onthoudingen"
+#: ../../include/features.php:381
+msgid "Emoji Reactions"
+msgstr "Emoji-reacties"
-#: ../../include/bbcode.php:134 ../../include/bbcode.php:962
-#: ../../include/bbcode.php:965 ../../include/bbcode.php:970
-#: ../../include/bbcode.php:973 ../../include/bbcode.php:976
-#: ../../include/bbcode.php:979 ../../include/bbcode.php:984
-#: ../../include/bbcode.php:987 ../../include/bbcode.php:992
-#: ../../include/bbcode.php:995 ../../include/bbcode.php:998
-#: ../../include/bbcode.php:1001
-msgid "Image/photo"
-msgstr "Afbeelding/foto"
+#: ../../include/features.php:382
+msgid "Add emoji reaction ability to posts"
+msgstr "Emoji-reacties in berichten toestaan"
-#: ../../include/bbcode.php:173 ../../include/bbcode.php:1012
-msgid "Encrypted content"
-msgstr "Versleutelde inhoud"
+#: ../../include/features.php:391
+msgid "Ability to file posts under folders"
+msgstr "Mogelijkheid om berichten in mappen op te slaan"
-#: ../../include/bbcode.php:189
+#: ../../include/features.php:399
+msgid "Dislike Posts"
+msgstr "Vind berichten niet leuk"
+
+#: ../../include/features.php:400
+msgid "Ability to dislike posts/comments"
+msgstr "Mogelijkheid om berichten en reacties niet leuk te vinden"
+
+#: ../../include/features.php:408
+msgid "Star Posts"
+msgstr "Geef berichten een ster"
+
+#: ../../include/features.php:409
+msgid "Ability to mark special posts with a star indicator"
+msgstr "Mogelijkheid om speciale berichten met een ster te markeren"
+
+#: ../../include/features.php:417
+msgid "Tag Cloud"
+msgstr "Tagwolk"
+
+#: ../../include/features.php:418
+msgid "Provide a personal tag cloud on your channel page"
+msgstr "Zorgt voor een persoonlijke wolk met tags op jouw kanaalpagina"
+
+#: ../../include/features.php:430
+msgid "Premium Channel"
+msgstr "Premiumkanaal"
+
+#: ../../include/features.php:431
+msgid ""
+"Allows you to set restrictions and terms on those that connect with your "
+"channel"
+msgstr "Stelt je in staat om beperkingen en voorwaarden in te stellen voor jouw kanaal"
+
+#: ../../include/photos.php:115
#, php-format
-msgid "Install %s element: "
-msgstr "Installeer %s-element: "
+msgid "Image exceeds website size limit of %lu bytes"
+msgstr "Afbeelding is groter dan op deze hub toegestane limiet van %lu bytes"
-#: ../../include/bbcode.php:193
+#: ../../include/photos.php:122
+msgid "Image file is empty."
+msgstr "Afbeeldingsbestand is leeg"
+
+#: ../../include/photos.php:260
+msgid "Photo storage failed."
+msgstr "Foto kan niet worden opgeslagen"
+
+#: ../../include/photos.php:300
+msgid "a new photo"
+msgstr "een nieuwe foto"
+
+#: ../../include/photos.php:304
#, php-format
+msgctxt "photo_upload"
+msgid "%1$s posted %2$s to %3$s"
+msgstr "%1$s plaatste %2$s op %3$s"
+
+#: ../../include/photos.php:519
+msgid "Upload New Photos"
+msgstr "Nieuwe foto's uploaden"
+
+#: ../../include/channel.php:33
+msgid "Unable to obtain identity information from database"
+msgstr "Niet in staat om identiteitsinformatie uit de database te verkrijgen"
+
+#: ../../include/channel.php:67
+msgid "Empty name"
+msgstr "Ontbrekende naam"
+
+#: ../../include/channel.php:70
+msgid "Name too long"
+msgstr "Naam te lang"
+
+#: ../../include/channel.php:181
+msgid "No account identifier"
+msgstr "Geen account-identificator"
+
+#: ../../include/channel.php:193
+msgid "Nickname is required."
+msgstr "Bijnaam is verplicht"
+
+#: ../../include/channel.php:207
+msgid "Reserved nickname. Please choose another."
+msgstr "Deze naam is gereserveerd. Kies een andere."
+
+#: ../../include/channel.php:212
msgid ""
-"This post contains an installable %s element, however you lack permissions "
-"to install it on this site."
-msgstr "Dit bericht heeft een te installeren %s-element, maar je hebt geen permissies om het op deze hub te installeren."
+"Nickname has unsupported characters or is already being used on this site."
+msgstr "Deze naam heeft niet ondersteunde karakters of is al op deze hub in gebruik."
-#: ../../include/bbcode.php:272
+#: ../../include/channel.php:272
+msgid "Unable to retrieve created identity"
+msgstr "Niet in staat om aangemaakte identiteit te vinden"
+
+#: ../../include/channel.php:344
+msgid "Default Profile"
+msgstr "Standaardprofiel"
+
+#: ../../include/channel.php:1045
+msgid "Create New Profile"
+msgstr "Nieuw profiel aanmaken"
+
+#: ../../include/channel.php:1065
+msgid "Visible to everybody"
+msgstr "Voor iedereen zichtbaar"
+
+#: ../../include/channel.php:1138 ../../include/channel.php:1257
+msgid "Gender:"
+msgstr "Geslacht:"
+
+#: ../../include/channel.php:1140 ../../include/channel.php:1312
+msgid "Homepage:"
+msgstr "Homepagina:"
+
+#: ../../include/channel.php:1141
+msgid "Online Now"
+msgstr "Nu online"
+
+#: ../../include/channel.php:1262
+msgid "Like this channel"
+msgstr "Vind dit kanaal leuk"
+
+#: ../../include/channel.php:1286
+msgid "j F, Y"
+msgstr "F j Y"
+
+#: ../../include/channel.php:1287
+msgid "j F"
+msgstr "F j"
+
+#: ../../include/channel.php:1294
+msgid "Birthday:"
+msgstr "Geboortedatum:"
+
+#: ../../include/channel.php:1307
#, php-format
-msgid "%1$s wrote the following %2$s %3$s"
-msgstr "%1$s schreef het volgende %2$s %3$s"
+msgid "for %1$d %2$s"
+msgstr "voor %1$d %2$s"
-#: ../../include/bbcode.php:349 ../../include/bbcode.php:357
-msgid "Click to open/close"
-msgstr "Klik om te openen of te sluiten"
+#: ../../include/channel.php:1310
+msgid "Sexual Preference:"
+msgstr "Seksuele voorkeur:"
-#: ../../include/bbcode.php:357
-msgid "spoiler"
-msgstr "spoiler"
+#: ../../include/channel.php:1316
+msgid "Tags:"
+msgstr "Tags:"
-#: ../../include/bbcode.php:950
-msgid "$1 wrote:"
-msgstr "$1 schreef:"
+#: ../../include/channel.php:1318
+msgid "Political Views:"
+msgstr "Politieke overtuigingen:"
+
+#: ../../include/channel.php:1320
+msgid "Religion:"
+msgstr "Religie:"
+
+#: ../../include/channel.php:1324
+msgid "Hobbies/Interests:"
+msgstr "Hobby's/interesses:"
+
+#: ../../include/channel.php:1326
+msgid "Likes:"
+msgstr "Houdt van:"
+
+#: ../../include/channel.php:1328
+msgid "Dislikes:"
+msgstr "Houdt niet van:"
+
+#: ../../include/channel.php:1330
+msgid "Contact information and Social Networks:"
+msgstr "Contactinformatie en sociale netwerken:"
+
+#: ../../include/channel.php:1332
+msgid "My other channels:"
+msgstr "Mijn andere kanalen"
+
+#: ../../include/channel.php:1334
+msgid "Musical interests:"
+msgstr "Muzikale interesses:"
+
+#: ../../include/channel.php:1336
+msgid "Books, literature:"
+msgstr "Boeken, literatuur:"
+
+#: ../../include/channel.php:1338
+msgid "Television:"
+msgstr "Televisie:"
+
+#: ../../include/channel.php:1340
+msgid "Film/dance/culture/entertainment:"
+msgstr "Films/dansen/cultuur/vermaak:"
+
+#: ../../include/channel.php:1342
+msgid "Love/Romance:"
+msgstr "Liefde/romantiek:"
+
+#: ../../include/channel.php:1344
+msgid "Work/employment:"
+msgstr "Werk/beroep:"
+
+#: ../../include/channel.php:1346
+msgid "School/education:"
+msgstr "School/opleiding:"
+
+#: ../../include/channel.php:1369
+msgid "Like this thing"
+msgstr "Vind dit ding leuk"
+
+#: ../../include/channel.php:2103
+#, php-format
+msgid "User '%s' deleted"
+msgstr "Account '%s' verwijderd"
#: ../../util/nconfig.php:34
msgid "Source channel not found."
@@ -13341,66 +13730,54 @@ msgstr "Grootte profielfoto's van berichten instellen"
msgid "Set size of followup author photos"
msgstr "Grootte profielfoto's van reacties instellen"
-#: ../../boot.php:1176
-#, php-format
-msgctxt "opensearch"
-msgid "Search %1$s (%2$s)"
-msgstr "Zoek %1$s (%2$s)"
-
-#: ../../boot.php:1176
-msgctxt "opensearch"
-msgid "$Projectname"
-msgstr "$Projectname"
-
-#: ../../boot.php:1494
+#: ../../boot.php:1522
#, php-format
msgid "Update %s failed. See error logs."
msgstr "Update %s mislukt. Zie foutenlogboek."
-#: ../../boot.php:1497
+#: ../../boot.php:1525
#, php-format
msgid "Update Error at %s"
msgstr "Update-fout op %s"
-#: ../../boot.php:1701
-msgid ""
-"Create an account to access services and applications within the Hubzilla"
-msgstr "Maak een account aan om toegang te krijgen tot diensten en toepassingen van Hubzilla"
+#: ../../boot.php:1729
+msgid "Create an account to access services and applications"
+msgstr "Maak een account aan om toegang te krijgen tot diensten en toepassingen"
-#: ../../boot.php:1722
+#: ../../boot.php:1751
msgid "Login/Email"
msgstr "E-mailadres of inlognaam"
-#: ../../boot.php:1723
+#: ../../boot.php:1752
msgid "Password"
msgstr "Wachtwoord"
-#: ../../boot.php:1724
+#: ../../boot.php:1753
msgid "Remember me"
msgstr "Aangemeld blijven"
-#: ../../boot.php:1727
+#: ../../boot.php:1756
msgid "Forgot your password?"
msgstr "Wachtwoord vergeten?"
-#: ../../boot.php:2288
+#: ../../boot.php:2320
msgid "toggle mobile"
msgstr "mobiele weergave omschakelen"
-#: ../../boot.php:2443
+#: ../../boot.php:2475
msgid "Website SSL certificate is not valid. Please correct."
msgstr "Het SSL-certificaat van deze website is ongeldig. Corrigeer dit a.u.b."
-#: ../../boot.php:2446
+#: ../../boot.php:2478
#, php-format
msgid "[hubzilla] Website SSL error for %s"
msgstr "[hubzilla] Probleem met SSL-certificaat voor %s"
-#: ../../boot.php:2563
+#: ../../boot.php:2597
msgid "Cron/Scheduled tasks not running."
msgstr "Cron is niet actief"
-#: ../../boot.php:2567
+#: ../../boot.php:2601
#, php-format
msgid "[hubzilla] Cron tasks not running on %s"
msgstr "[hubzilla] Cron-taken zijn niet actief op %s"
diff --git a/view/nl/hstrings.php b/view/nl/hstrings.php
index 000c8043c..c221f6670 100644
--- a/view/nl/hstrings.php
+++ b/view/nl/hstrings.php
@@ -28,7 +28,9 @@ App::$strings["Can view my connections"] = "Kan een lijst met mijn connecties be
App::$strings["Can view my file storage and photos"] = "Kan mijn foto's en andere bestanden bekijken";
App::$strings["Can upload/modify my file storage and photos"] = "Kan foto's en andere bestanden aan mijn bestandsopslag toevoegen";
App::$strings["Can view my channel webpages"] = "Kan de webpagina's van mijn kanaal bekijken";
+App::$strings["Can view my wiki pages"] = "Kan mijn wiki-pagina's bekijken";
App::$strings["Can create/edit my channel webpages"] = "Kan wegpagina's van mijn kanaal aanmaken en bewerken";
+App::$strings["Can write to my wiki pages"] = "Kan mijn wiki-pagina's bewerken";
App::$strings["Can post on my channel (wall) page"] = "Kan een bericht in mijn kanaal plaatsen";
App::$strings["Can comment on or like my posts"] = "Kan op mijn berichten reageren of deze (niet) leuk vinden";
App::$strings["Can send me private mail messages"] = "Kan mij privéberichten sturen";
@@ -59,18 +61,33 @@ App::$strings["Delete"] = "Verwijderen";
App::$strings["You are using %1\$s of your available file storage."] = "Je gebruikt %1\$s van de beschikbare bestandsopslag.";
App::$strings["You are using %1\$s of %2\$s available file storage. (%3\$s&#37;)"] = "Je gebruikt %1\$s van totaal %2\$s beschikbare bestandsopslag. (%3\$s&#37;)";
App::$strings["WARNING:"] = "WAARSCHUWING:";
+App::$strings["Please use DAV to upload large (video, audio) files.<br>See <a class=\"zrl\" href=\"help/member/member_guide#Cloud_Desktop_Clients\">Cloud Desktop Clients</a>"] = "Gebruik DAV om grote (video-, audio-) bestanden te uploaden.<br>Zie hiervoor de documentatie over de <a class=\"zrl\" href=\"help/member/member_guide#Cloud_Desktop_Clients\">cloud en desktopclients</a>.";
App::$strings["Create new folder"] = "Nieuwe map aanmaken";
App::$strings["Upload file"] = "Bestand uploaden";
App::$strings["Drop files here to immediately upload"] = "Sleep bestanden hierheen om ze onmiddellijk te uploaden";
+App::$strings["Permission denied"] = "Toegang geweigerd";
App::$strings["Permission denied."] = "Toegang geweigerd.";
App::$strings["Page not found."] = "Pagina niet gevonden.";
-App::$strings["Permission denied"] = "Toegang geweigerd";
App::$strings["Remote authentication blocked. You are logged into this site locally. Please logout and retry."] = "Authenticatie op afstand geblokkeerd. Je bent lokaal op deze hub ingelogd. Uitloggen en opnieuw proberen.";
App::$strings["Welcome %s. Remote authentication successful."] = "Welkom %s. Authenticatie op afstand geslaagd.";
App::$strings["Requested profile is not available."] = "Opgevraagd profiel is niet beschikbaar";
App::$strings["Some blurb about what to do when you're new here"] = "Welkom op \$Projectname. Klik op de tab ontdekken of klik rechtsboven op de <a href=\"directory\">kanalengids</a>, om kanalen te vinden. Rechtsboven vind je ook <a href=\"directory\">apps</a>, waar je vrijwel alle functies van \$Projectname kunt vinden. Voor <a href=\"directory\">hulp</a> met \$Projectname klik je op het vraagteken.";
-App::$strings["Away"] = "Afwezig";
-App::$strings["Online"] = "Online";
+App::$strings["App installed."] = "App geïnstalleerd";
+App::$strings["Malformed app."] = "Misvormde app.";
+App::$strings["Embed code"] = "Insluitcode";
+App::$strings["Edit App"] = "App bewerken";
+App::$strings["Create App"] = "App maken";
+App::$strings["Name of app"] = "Naam van app";
+App::$strings["Required"] = "Vereist";
+App::$strings["Location (URL) of app"] = "Locatie (URL) van app";
+App::$strings["Description"] = "Omschrijving";
+App::$strings["Photo icon URL"] = "URL van pictogram";
+App::$strings["80 x 80 pixels - optional"] = "80 x 80 pixels (niet verplicht)";
+App::$strings["Categories (optional, comma separated list)"] = "Categorieën (niet verplicht, door komma's gescheiden lijst)";
+App::$strings["Version ID"] = "Versie-ID";
+App::$strings["Price of app"] = "Prijs van de app";
+App::$strings["Location (URL) to purchase app"] = "Locatie (URL) om de app aan te schaffen";
+App::$strings["Submit"] = "Opslaan";
App::$strings["Maximum daily site registrations exceeded. Please try again tomorrow."] = "Maximum toegestane dagelijkse registraties op deze \$Projectname-hub bereikt. Probeer het morgen (UTC) nogmaals.";
App::$strings["Please indicate acceptance of the Terms of Service. Registration failed."] = "Registratie mislukt. De gebruiksvoorwaarden dienen wel geaccepteerd te worden.";
App::$strings["Passwords do not match."] = "Wachtwoorden komen niet met elkaar overeen.";
@@ -102,118 +119,43 @@ App::$strings["Membership on this site is by invitation only."] = "Registreren o
App::$strings["Register"] = "Registreren";
App::$strings["This site may require email verification after submitting this form. If you are returned to a login page, please check your email for instructions."] = "Mogelijk moet op deze hub eerst jouw e-mail geverifieerd worden. Wanneer je na het indienen van dit formulier op de inlogpagina terecht komt, dan dien je jouw e-mail te controleren voor instructies. Controleer eventueel ook jouw spamfolder.";
App::$strings["Fetching URL returns error: %1\$s"] = "Ophalen URL gaf een foutmelding terug: %1\$s";
-App::$strings["Profile Match"] = "Profielovereenkomst";
-App::$strings["No keywords to match. Please add keywords to your default profile."] = "Je hebt geen trefwoorden waarmee overeenkomsten gevonden kunnen worden. Voeg enkele trefwoorden aan je standaardprofiel toe.";
-App::$strings["is interested in:"] = "is geïnteresseerd in:";
-App::$strings["Connect"] = "Verbinden";
-App::$strings["No matches"] = "Geen overeenkomsten";
-App::$strings["Could not access contact record."] = "Kon geen toegang krijgen tot de connectie-gegevens.";
-App::$strings["Could not locate selected profile."] = "Kon het gekozen profiel niet vinden.";
-App::$strings["Connection updated."] = "Connectie bijgewerkt.";
-App::$strings["Failed to update connection record."] = "Bijwerken van connectie-gegevens mislukt.";
-App::$strings["is now connected to"] = "is nu verbonden met";
-App::$strings["No"] = "Nee";
-App::$strings["Yes"] = "Ja";
-App::$strings["Could not access address book record."] = "Kon geen toegang krijgen tot de record van de connectie.";
-App::$strings["Refresh failed - channel is currently unavailable."] = "Vernieuwen mislukt - kanaal is momenteel niet beschikbaar";
-App::$strings["Unable to set address book parameters."] = "Niet in staat om de parameters van connecties in te stellen.";
-App::$strings["Connection has been removed."] = "Connectie is verwijderd";
-App::$strings["View Profile"] = "Profiel weergeven";
-App::$strings["View %s's profile"] = "Profiel van %s weergeven";
-App::$strings["Refresh Permissions"] = "Permissies vernieuwen";
-App::$strings["Fetch updated permissions"] = "Aangepaste permissies ophalen";
-App::$strings["Recent Activity"] = "Recente activiteit/berichten";
-App::$strings["View recent posts and comments"] = "Recente berichten en reacties weergeven";
-App::$strings["Unblock"] = "Deblokkeren";
-App::$strings["Block"] = "Blokkeren";
-App::$strings["Block (or Unblock) all communications with this connection"] = "Blokkeer (of deblokkeer) alle communicatie met deze connectie";
-App::$strings["This connection is blocked!"] = "Deze connectie is geblokkeerd!";
-App::$strings["Unignore"] = "Niet meer negeren";
-App::$strings["Ignore"] = "Negeren";
-App::$strings["Ignore (or Unignore) all inbound communications from this connection"] = "Negeer (of negeer niet meer) alle inkomende communicatie van deze connectie";
-App::$strings["This connection is ignored!"] = "Deze connectie wordt genegeerd!";
-App::$strings["Unarchive"] = "Niet meer archiveren";
-App::$strings["Archive"] = "Archiveren";
-App::$strings["Archive (or Unarchive) this connection - mark channel dead but keep content"] = "Archiveer (of dearchiveer) deze connectie - markeer het kanaal als dood, maar bewaar de inhoud";
-App::$strings["This connection is archived!"] = "Deze connectie is gearchiveerd!";
-App::$strings["Unhide"] = "Niet meer verbergen";
-App::$strings["Hide"] = "Verbergen";
-App::$strings["Hide or Unhide this connection from your other connections"] = "Deze connectie verbergen (of niet meer verbergen) voor jouw andere connecties";
-App::$strings["This connection is hidden!"] = "Deze connectie is verborgen!";
-App::$strings["Delete this connection"] = "Deze connectie verwijderen";
-App::$strings["Me"] = "Ik";
-App::$strings["Family"] = "Familie";
-App::$strings["Friends"] = "Vrienden";
-App::$strings["Acquaintances"] = "Kennissen";
-App::$strings["All"] = "Alles";
-App::$strings["Approve this connection"] = "Deze connectie accepteren";
-App::$strings["Accept connection to allow communication"] = "Keur deze connectie goed om communicatie toe te staan";
-App::$strings["Set Affinity"] = "Verwantschapsfilter instellen";
-App::$strings["Set Profile"] = "Profiel instellen";
-App::$strings["Set Affinity & Profile"] = "Verwantschapsfilter en profiel instellen";
-App::$strings["none"] = "geen";
-App::$strings["Connection Default Permissions"] = "Standaard permissies voor connecties";
-App::$strings["Connection: %s"] = "Connectie: %s";
-App::$strings["Apply these permissions automatically"] = "Deze permissies automatisch toepassen";
-App::$strings["Connection requests will be approved without your interaction"] = "Connectieverzoeken zullen automatisch worden geaccepteerd";
-App::$strings["This connection's primary address is"] = "Het primaire kanaaladres van deze connectie is";
-App::$strings["Available locations:"] = "Beschikbare locaties:";
-App::$strings["The permissions indicated on this page will be applied to all new connections."] = "Permissies die op deze pagina staan vermeld worden op alle nieuwe connecties toegepast.";
-App::$strings["Connection Tools"] = "Hulpmiddelen";
-App::$strings["Slide to adjust your degree of friendship"] = "Schuif om te bepalen hoe goed je iemand kent en/of mag";
-App::$strings["Rating"] = "Beoordeling";
-App::$strings["Slide to adjust your rating"] = "Gebruik de schuif om je beoordeling te geven";
-App::$strings["Optionally explain your rating"] = "Verklaar jouw beoordeling (niet verplicht)";
-App::$strings["Custom Filter"] = "Berichtenfilter";
-App::$strings["Only import posts with this text"] = "Importeer alleen berichten met deze tekst";
-App::$strings["words one per line or #tags or /patterns/ or lang=xx, leave blank to import all posts"] = "woorden (één per regel), #tags, /regex/ of talen (lang=iso639-1) - laat leeg om alle berichten te importeren";
-App::$strings["Do not import posts with this text"] = "Importeer geen berichten met deze tekst";
-App::$strings["This information is public!"] = "Deze informatie is openbaar!";
-App::$strings["Connection Pending Approval"] = "Connectie moet nog geaccepteerd worden";
-App::$strings["inherited"] = "geërfd";
-App::$strings["Submit"] = "Opslaan";
-App::$strings["Please choose the profile you would like to display to %s when viewing your profile securely."] = "Kies het profiel dat je aan %s wil tonen wanneer hij/zij ingelogd jouw profiel wil bekijken.";
-App::$strings["Their Settings"] = "Hun instellingen";
-App::$strings["My Settings"] = "Mijn instellingen";
-App::$strings["Individual Permissions"] = "Individuele permissies";
-App::$strings["Some permissions may be inherited from your channel's <a href=\"settings\"><strong>privacy settings</strong></a>, which have higher priority than individual settings. You can <strong>not</strong> change those settings here."] = "Sommige permissies worden mogelijk overgeërfd van de <a href=\"settings\">privacy-instellingen</a> van jouw kanaal, die een hogere prioriteit hebben dan deze individuele instellingen. Je kan je deze overgeërfde permissies hier <strong>niet</strong> veranderen.";
-App::$strings["Some permissions may be inherited from your channel's <a href=\"settings\"><strong>privacy settings</strong></a>, which have higher priority than individual settings. You can change those settings here but they wont have any impact unless the inherited setting changes."] = "Sommige permissies worden mogelijk overgeërfd van de <a href=\"settings\">privacy-instellingen</a> van jouw kanaal, die een hogere prioriteit hebben dan deze individuele permissies. Je kan de permissies hier veranderen, maar die hebben geen effect, tenzij de overgeërfde permissies worden veranderd. ";
-App::$strings["Last update:"] = "Laatste wijziging:";
-App::$strings["Invalid message"] = "Ongeldig bericht";
-App::$strings["no results"] = "geen resultaten";
-App::$strings["channel sync processed"] = "kanaalsync verwerkt";
-App::$strings["queued"] = "in wachtrij";
-App::$strings["posted"] = "verstuurd";
-App::$strings["accepted for delivery"] = "geaccepteerd om afgeleverd te worden";
-App::$strings["updated"] = "geüpdatet";
-App::$strings["update ignored"] = "update genegeerd";
-App::$strings["permission denied"] = "toegang geweigerd";
-App::$strings["recipient not found"] = "ontvanger niet gevonden";
-App::$strings["mail recalled"] = "Privébericht ingetrokken";
-App::$strings["duplicate mail received"] = "dubbel privébericht ontvangen";
-App::$strings["mail delivered"] = "privébericht afgeleverd";
-App::$strings["Delivery report for %1\$s"] = "Afleveringsrapport voor %1\$s";
-App::$strings["Options"] = "Opties";
-App::$strings["Redeliver"] = "Opnieuw afleveren";
+App::$strings["Authentication failed."] = "Authenticatie mislukt.";
+App::$strings["Remote Authentication"] = "Authenticatie op afstand";
+App::$strings["Enter your channel address (e.g. channel@example.com)"] = "Vul jouw kanaaladres in (bijv. channel@example.com)";
+App::$strings["Authenticate"] = "Authenticeren";
+App::$strings["Nothing to import."] = "Niets gevonden om te importeren";
+App::$strings["Unable to download data from old server"] = "Niet in staat om gegevens van de oude hub te downloaden";
+App::$strings["Imported file is empty."] = "Geïmporteerde bestand is leeg";
+App::$strings["Warning: Database versions differ by %1\$d updates."] = "Waarschuwing: database-versies lopen %1\$d updates achter.";
+App::$strings["Your service plan only allows %d channels."] = "Jouw abonnement staat maar %d kanalen toe.";
+App::$strings["No channel. Import failed."] = "Geen kanaal. Importeren mislukt.";
+App::$strings["Import completed."] = "Import voltooid.";
+App::$strings["You must be logged in to use this feature."] = "Je moet ingelogd zijn om dit onderdeel te kunnen gebruiken.";
+App::$strings["Import Channel"] = "Kanaal importeren";
+App::$strings["Use this form to import an existing channel from a different server/hub. You may retrieve the channel identity from the old server/hub via the network or provide an export file."] = "Gebruik dit formulier om een bestaand kanaal te importeren van een andere hub. Je kan de kanaal-identiteit van de oude hub via het netwerk ontvangen of een exportbestand verstrekken.";
+App::$strings["File to Upload"] = "Bestand om te uploaden";
+App::$strings["Or provide the old server/hub details"] = "Of vul de gegevens van de oude hub in";
+App::$strings["Your old identity address (xyz@example.com)"] = "Jouw oude kanaaladres (xyz@example.com)";
+App::$strings["Your old login email address"] = "Het e-mailadres van je oude account";
+App::$strings["Your old login password"] = "Wachtwoord van jouw oude account";
+App::$strings["For either option, please choose whether to make this hub your new primary address, or whether your old location should continue this role. You will be able to post from either location, but only one can be marked as the primary location for files, photos, and media."] = "Voor elke optie geldt dat je moet kiezen of je jouw primaire kanaaladres op deze hub wil instellen of dat jouw oude hub deze rol blijft vervullen.";
+App::$strings["Make this hub my primary location"] = "Stel deze hub als mijn primaire locatie in";
+App::$strings["Move this channel (disable all previous locations)"] = "Verplaats dit kanaal (schakelt alle voormalige locaties uit)";
+App::$strings["Import a few months of posts if possible (limited by available memory"] = "Importeer enkele maanden aan berichten wanneer mogelijk (afhankelijk van hoeveelheid geheugen hub)";
+App::$strings["This process may take several minutes to complete. Please submit the form only once and leave this page open until finished."] = "Dit proces kan enkele minuten in beslag nemen. Klik maar één keer op opslaan en verlaat deze pagina niet alvorens het proces is voltooid.";
+App::$strings["Away"] = "Afwezig";
+App::$strings["Online"] = "Online";
+App::$strings["Documentation Search"] = "Zoek documentatie";
+App::$strings["About"] = "Over";
+App::$strings["Members"] = "Kanalen";
+App::$strings["Administrators"] = "Beheerders";
+App::$strings["Developers"] = "Ontwikkelaars";
+App::$strings["Tutorials"] = "Zelfstudie";
+App::$strings["\$Projectname Documentation"] = "\$Projectname-documentatie";
+App::$strings["Contents"] = "Inhoud";
App::$strings["Bookmark added"] = "Bladwijzer toegevoegd";
App::$strings["My Bookmarks"] = "Mijn bladwijzers";
App::$strings["My Connections Bookmarks"] = "Bladwijzers van mijn connecties";
-App::$strings["network"] = "netwerk";
-App::$strings["RSS"] = "RSS";
-App::$strings["Location not found."] = "Locatie niet gevonden.";
-App::$strings["Location lookup failed."] = "Opzoeken locatie mislukt";
-App::$strings["Please select another location to become primary before removing the primary location."] = "Kies eerst een andere primaire locatie alvorens de huidige primaire locatie te verwijderen.";
-App::$strings["Syncing locations"] = "Locaties synchronizeren";
-App::$strings["No locations found."] = "Geen locaties gevonden.";
-App::$strings["Manage Channel Locations"] = "Kanaallocaties beheren";
-App::$strings["Location"] = "Locatie";
-App::$strings["Address"] = "Adres";
-App::$strings["Primary"] = "Primair";
-App::$strings["Drop"] = "Verwijderen";
-App::$strings["Sync Now"] = "Nu synchroniseren";
-App::$strings["Please wait several minutes between consecutive operations."] = "Wacht enkele minuten tussen opeenvolgende handelingen.";
-App::$strings["When possible, drop a location by logging into that website/hub and removing your channel."] = "Wij adviseren, wanneer dit (nog) mogelijk is, de locatie te verwijderen door op de hub van de kloon in te loggen en het kanaal daar te verwijderen.";
-App::$strings["Use this form to drop the location if the hub is no longer operating."] = "Gebruik dit formulier om de locatie te verwijderen wanneer de hub van de kloon niet meer operationeel is.";
App::$strings["Continue"] = "Ga verder";
App::$strings["Premium Channel Setup"] = "Instellen premiumkanaal ";
App::$strings["Enable premium channel connection restrictions"] = "Restricties voor connecties van premiumkanaal toestaan";
@@ -223,28 +165,47 @@ App::$strings["Potential connections will then see the following text before pro
App::$strings["By continuing, I certify that I have complied with any instructions provided on this page."] = "Door verder te gaan ga ik automatisch akkoord met alle voorwaarden en aanwijzingen op deze pagina.";
App::$strings["(No specific instructions have been provided by the channel owner.)"] = "(Er zijn geen speciale voorwaarden en aanwijzingen door de kanaal-eigenaar verstrekt) ";
App::$strings["Restricted or Premium Channel"] = "Beperkt of premiumkanaal";
+App::$strings["Item not found."] = "Item niet gevonden.";
+App::$strings["# Accounts"] = "# accounts";
+App::$strings["# blocked accounts"] = "# geblokkeerde accounts";
+App::$strings["# expired accounts"] = "# verlopen accounts";
+App::$strings["# expiring accounts"] = "# accounts die nog moeten verlopen";
+App::$strings["# Channels"] = "# Kanalen";
+App::$strings["# primary"] = "# primair";
+App::$strings["# clones"] = "# klonen";
+App::$strings["Message queues"] = "Berichtenwachtrij";
+App::$strings["Your software should be updated"] = "Jouw software moet worden bijgewerkt ";
+App::$strings["Administration"] = "Beheer";
+App::$strings["Summary"] = "Samenvatting";
+App::$strings["Registered accounts"] = "Geregistreerde accounts";
+App::$strings["Pending registrations"] = "Accounts die op goedkeuring wachten";
+App::$strings["Registered channels"] = "Geregistreerde kanalen";
+App::$strings["Active plugins"] = "Ingeschakelde plugins";
+App::$strings["Version"] = "Versie";
+App::$strings["Repository version (master)"] = "Versie repository (master)";
+App::$strings["Repository version (dev)"] = "Versie repository (dev)";
+App::$strings["Item not found"] = "Item niet gevonden";
+App::$strings["Block Name"] = "Bloknaam";
+App::$strings["Insert web link"] = "Weblink invoegen";
+App::$strings["Title (optional)"] = "Titel (niet verplicht)";
+App::$strings["Edit Block"] = "Blok bewerken";
App::$strings["Invalid item."] = "Ongeldig item.";
App::$strings["Channel not found."] = "Kanaal niet gevonden.";
App::$strings["Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum."] = "Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.";
App::$strings["Save to Folder:"] = "Bewaar in map: ";
App::$strings["- select -"] = "- kies map -";
App::$strings["Save"] = "Opslaan";
-App::$strings["You have created %1$.0f of %2$.0f allowed channels."] = "Je hebt %1$.0f van totaal %2$.0f toegestane kanalen aangemaakt.";
-App::$strings["Create a new channel"] = "Nieuw kanaal aanmaken";
-App::$strings["Create New"] = "Nieuwe aanmaken";
-App::$strings["Channel Manager"] = "Kanaalbeheer";
-App::$strings["Current Channel"] = "Huidig kanaal";
-App::$strings["Switch to one of your channels by selecting it."] = "Activeer een van jouw andere kanalen door er op te klikken.";
-App::$strings["Default Channel"] = "Standaardkanaal";
-App::$strings["Make Default"] = "Als standaard instellen";
-App::$strings["%d new messages"] = "%d nieuwe berichten";
-App::$strings["%d new introductions"] = "%d nieuwe connectieverzoeken";
-App::$strings["Delegated Channel"] = "Uitbesteed kanaal";
+App::$strings["sent you a private message"] = "stuurde jou een privébericht";
+App::$strings["added your channel"] = "voegde jouw kanaal toe";
+App::$strings["g A l F d"] = "G:i, l d F";
+App::$strings["[today]"] = "[vandaag]";
+App::$strings["posted an event"] = "plaatste een gebeurtenis";
App::$strings["Blocked"] = "Geblokkeerd";
App::$strings["Ignored"] = "Genegeerd";
App::$strings["Hidden"] = "Verborgen";
App::$strings["Archived"] = "Gearchiveerd";
App::$strings["New"] = "Nieuw";
+App::$strings["All"] = "Alles";
App::$strings["New Connections"] = "Nieuwe connecties";
App::$strings["Show pending (new) connections"] = "Nog te accepteren (nieuwe) connecties weergeven";
App::$strings["All Connections"] = "Alle connecties";
@@ -259,11 +220,13 @@ App::$strings["Edit connection"] = "Connectie bewerken";
App::$strings["Delete connection"] = "Connectie verwijderen";
App::$strings["Channel address"] = "Kanaaladres";
App::$strings["Network"] = "Netwerk";
+App::$strings["Call"] = "Bellen";
App::$strings["Status"] = "Status";
App::$strings["Connected"] = "Verbonden";
App::$strings["Approve connection"] = "Connectie accepteren";
App::$strings["Approve"] = "Goedkeuren";
App::$strings["Ignore connection"] = "Connectie negeren";
+App::$strings["Ignore"] = "Negeren";
App::$strings["Recent activity"] = "Recente activiteit";
App::$strings["Connections"] = "Connecties";
App::$strings["Search"] = "Zoeken";
@@ -297,43 +260,12 @@ App::$strings["On"] = "Aan";
App::$strings["Lock feature %s"] = " Vergrendel de functie '%s'";
App::$strings["Manage Additional Features"] = "Beheer - Extra functies";
App::$strings["Log settings updated."] = "Logboek-instellingen bijgewerkt.";
-App::$strings["Administration"] = "Beheer";
App::$strings["Logs"] = "Logboeken";
App::$strings["Clear"] = "Leegmaken";
App::$strings["Debugging"] = "Debuggen";
App::$strings["Log file"] = "Logbestand";
App::$strings["Must be writable by web server. Relative to your top-level webserver directory."] = "Moet door de webserver beschrijfbaar zijn. Relatief ten opzichte van de bovenste map van je \$Projectname-installatie.";
App::$strings["Log level"] = "Logniveau";
-App::$strings["Item not found."] = "Item niet gevonden.";
-App::$strings["Plugin %s disabled."] = "Plugin %s uitgeschakeld.";
-App::$strings["Plugin %s enabled."] = "Plugin %s ingeschakeld";
-App::$strings["Disable"] = "Uitschakelen";
-App::$strings["Enable"] = "Inschakelen";
-App::$strings["Plugins"] = "Plugins";
-App::$strings["Toggle"] = "Omschakelen";
-App::$strings["Settings"] = "Instellingen";
-App::$strings["Author: "] = "Auteur: ";
-App::$strings["Maintainer: "] = "Beheerder: ";
-App::$strings["Minimum project version: "] = "Minimum versie Hubzilla: ";
-App::$strings["Maximum project version: "] = "Maximum versie Hubzilla:";
-App::$strings["Minimum PHP version: "] = "Minimum versie PHP: ";
-App::$strings["Compatible Server Roles: "] = "Werkt met configuratietypes: ";
-App::$strings["Requires: "] = "Vereist: ";
-App::$strings["Disabled - version incompatibility"] = "Uitgeschakeld - versie is incompatibel";
-App::$strings["Enter the public git repository URL of the plugin repo."] = "Vul de openbare Git-URL in van de plugin-repository.";
-App::$strings["Plugin repo git URL"] = "Git-URL plugin-repository";
-App::$strings["Custom repo name"] = "Handmatige repository-naam";
-App::$strings["(optional)"] = "(optioneel)";
-App::$strings["Download Plugin Repo"] = "Plugin-repository downloaden";
-App::$strings["Install new repo"] = "Nieuwe repository installeren";
-App::$strings["Install"] = "Installeren";
-App::$strings["Cancel"] = "Annuleren";
-App::$strings["Manage Repos"] = "Repositories beheren";
-App::$strings["Installed Plugin Repositories"] = "Toegevoegde plugin-repositories";
-App::$strings["Install a New Plugin Repository"] = "Nieuwe plugin-repository toevoegen";
-App::$strings["Update"] = "Bijwerken";
-App::$strings["Switch branch"] = "Branch veranderen";
-App::$strings["Remove"] = "Verwijderen";
App::$strings["New Profile Field"] = "Nieuw profielveld";
App::$strings["Field nickname"] = "Bijnaam voor veld";
App::$strings["System name of field"] = "Systeemnaam voor veld";
@@ -341,7 +273,7 @@ App::$strings["Input type"] = "Invoertype";
App::$strings["Field Name"] = "Veldnaam";
App::$strings["Label on profile pages"] = "Tekstlabel voor op profielpagina's";
App::$strings["Help text"] = "Helptekst";
-App::$strings["Additional info (optional)"] = "Extra informatie (optioneel)";
+App::$strings["Additional info (optional)"] = "Extra informatie (niet verplicht)";
App::$strings["Field definition not found"] = "Velddefinitie niet gevonden";
App::$strings["Edit Profile Field"] = "Profielveld bewerken";
App::$strings["Profile Fields"] = "Profielvelden";
@@ -351,13 +283,6 @@ App::$strings["(In addition to basic fields)"] = "(als toevoeging op de standaar
App::$strings["All available fields"] = "Alle beschikbare velden";
App::$strings["Custom Fields"] = "Extra (handmatig toegevoegde) velden";
App::$strings["Create Custom Field"] = "Extra velden aanmaken";
-App::$strings["Queue Statistics"] = "Wachtrij-statistieken";
-App::$strings["Total Entries"] = "Aantal vermeldingen";
-App::$strings["Priority"] = "Prioriteit";
-App::$strings["Destination URL"] = "Doel-URL";
-App::$strings["Mark hub permanently offline"] = "Hub als permanent offline markeren";
-App::$strings["Empty queue for this hub"] = "Berichtenwachtrij voor deze hub legen";
-App::$strings["Last known contact"] = "Voor het laatst contact";
App::$strings["By default, unfiltered HTML is allowed in embedded media. This is inherently insecure."] = "Standaard is ongefilterde HTML in ingesloten (embedded) media toegestaan. Dit is inherent onveilig.";
App::$strings["The recommended setting is to only allow unfiltered HTML from the following sites:"] = "Het wordt aanbevolen om alleen ongefilterde HTML van de volgende websites toe te staan:";
App::$strings["https://youtube.com/<br />https://www.youtube.com/<br />https://youtu.be/<br />https://vimeo.com/<br />https://soundcloud.com/<br />"] = "https://youtube.com/<br />https://www.youtube.com/<br />https://youtu.be/<br />https://vimeo.com/<br />https://soundcloud.com/<br />";
@@ -381,12 +306,6 @@ App::$strings["Only allow embeds from secure (SSL) websites and links."] = "Alle
App::$strings["Allow unfiltered embedded HTML content only from these domains"] = "Alleen ongefilterde ingesloten (embedded) HTML van deze websites toestaan";
App::$strings["One site per line. By default embedded content is filtered."] = "Eén website per regel. Standaard wordt ingesloten (embedded) inhoud gefilterd.";
App::$strings["Block embedded HTML from these domains"] = "Ingesloten (embedded) HTML vanaf deze domeinen blokkeren";
-App::$strings["Theme settings updated."] = "Thema-instellingen bijgewerkt.";
-App::$strings["No themes found."] = "Geen thema's gevonden";
-App::$strings["Screenshot"] = "Schermafdruk";
-App::$strings["Themes"] = "Thema's";
-App::$strings["[Experimental]"] = "[Experimenteel]";
-App::$strings["[Unsupported]"] = "[Niet ondersteund]";
App::$strings["Password changed for account %d."] = "Wachtwoord veranderd voor account %d.";
App::$strings["Account settings updated."] = "Account-instellingen bijgewerkt.";
App::$strings["Account not found."] = "Account niet gevonden.";
@@ -415,6 +334,8 @@ App::$strings["Request date"] = "Tijd/datum verzoek";
App::$strings["Email"] = "E-mail";
App::$strings["No registrations."] = "Geen verzoeken.";
App::$strings["Deny"] = "Afkeuren";
+App::$strings["Block"] = "Blokkeren";
+App::$strings["Unblock"] = "Deblokkeren";
App::$strings["ID"] = "ID";
App::$strings["All Channels"] = "Alle kanalen";
App::$strings["Register date"] = "Geregistreerd";
@@ -448,6 +369,7 @@ App::$strings["Allow Code"] = "Scripts toestaan";
App::$strings["Disallow Code"] = "Scripts niet toestaan";
App::$strings["Channel"] = "Kanaal";
App::$strings["UID"] = "UID";
+App::$strings["Address"] = "Adres";
App::$strings["Selected channels will be deleted!\\n\\nEverything that was posted in these channels on this site will be permanently deleted!\\n\\nAre you sure?"] = "Geselecteerde kanalen worden verwijderd!\\n\\nAlles wat in deze kanalen op deze hub werd gepubliceerd wordt definitief verwijderd!\\n\\nWeet je het zeker?";
App::$strings["The channel {0} will be deleted!\\n\\nEverything that was posted in this channel on this site will be permanently deleted!\\n\\nAre you sure?"] = "Kanaal {0} wordt verwijderd!\\n\\nAlles wat in dit kanaal op deze hub werd gepubliceerd wordt definitief verwijderd!\\n\\nWeet je het zeker?";
App::$strings["Update has been marked successful"] = "Update is als succesvol gemarkeerd";
@@ -459,12 +381,22 @@ App::$strings["No failed updates."] = "Geen mislukte updates.";
App::$strings["Failed Updates"] = "Mislukte updates";
App::$strings["Mark success (if update was manually applied)"] = "Markeer als geslaagd (wanneer de update handmatig was uitgevoerd)";
App::$strings["Attempt to execute this update step automatically"] = "Poging om deze stap van de update automatisch uit te voeren.";
+App::$strings["Queue Statistics"] = "Wachtrij-statistieken";
+App::$strings["Total Entries"] = "Aantal vermeldingen";
+App::$strings["Priority"] = "Prioriteit";
+App::$strings["Destination URL"] = "Doel-URL";
+App::$strings["Mark hub permanently offline"] = "Hub als permanent offline markeren";
+App::$strings["Empty queue for this hub"] = "Berichtenwachtrij voor deze hub legen";
+App::$strings["Last known contact"] = "Voor het laatst contact";
App::$strings["Site settings updated."] = "Hub-instellingen bijgewerkt.";
App::$strings["Default"] = "Standaard";
+App::$strings["%s - (Incompatible)"] = "%s - (niet compatible)";
App::$strings["mobile"] = "mobiel";
App::$strings["experimental"] = "experimenteel";
App::$strings["unsupported"] = "Niet ondersteund";
+App::$strings["No"] = "Nee";
App::$strings["Yes - with approval"] = "Ja - met goedkeuring";
+App::$strings["Yes"] = "Ja";
App::$strings["My site is not a public server"] = "Mijn \$Projectname-hub is niet openbaar";
App::$strings["My site has paid access only"] = "Mijn \$Projectname-hub kent alleen betaalde toegang";
App::$strings["My site has free access only"] = "Mijn \$Projectname-hub kent alleen gratis toegang";
@@ -542,28 +474,60 @@ App::$strings["Maximum Load Average"] = "Maximaal gemiddelde systeembelasting";
App::$strings["Maximum system load before delivery and poll processes are deferred - default 50."] = "Maximale systeembelasting voordat de afleverings- en polllingsprocessen worden uitgesteld. Standaard is 50.";
App::$strings["Expiration period in days for imported (grid/network) content"] = "Aantal dagen waarna geïmporteerde inhoud uit iemands grid/netwerk-pagina wordt verwijderd.";
App::$strings["0 for no expiration of imported content"] = "Dit geldt alleen voor inhoud van andere kanalen, dus niet voor iemands eigen kanaal. 0 voor het niet verwijderen van geïmporteerde inhoud.";
-App::$strings["Public Hubs"] = "Openbare hubs";
-App::$strings["The listed hubs allow public registration for the \$Projectname network. All hubs in the network are interlinked so membership on any of them conveys membership in the network as a whole. Some hubs may require subscription or provide tiered service plans. The hub itself <strong>may</strong> provide additional details."] = "Op de hier weergegeven hubs kan iedereen zich voor het \$Projectname-netwerk aanmelden. Alle hubs in het netwerk zijn met elkaar verbonden, dus maakt het qua lidmaatschap niet uit waar je je aanmeldt. Op sommige hubs heb je eerst goedkeuring nodig en sommige hubs vereisen een financiële tegemoetkoming voor bepaalde uitbreidingen. <strong>Mogelijk</strong> wordt hierover op de hub zelf meer informatie gegeven.";
-App::$strings["Hub URL"] = "Hub-URL";
-App::$strings["Access Type"] = "Toegangs-<br/>&nbsp;type";
-App::$strings["Registration Policy"] = "Registratie-<br/>&nbsp;beleid";
-App::$strings["Stats"] = "Stats";
-App::$strings["Software"] = "Software";
-App::$strings["Ratings"] = "Beoordelingen";
-App::$strings["Rate"] = "Beoordeel";
-App::$strings["View"] = "Weergeven";
-App::$strings["Item not found"] = "Item niet gevonden";
+App::$strings["Plugin %s disabled."] = "Plugin %s uitgeschakeld.";
+App::$strings["Plugin %s enabled."] = "Plugin %s ingeschakeld";
+App::$strings["Disable"] = "Uitschakelen";
+App::$strings["Enable"] = "Inschakelen";
+App::$strings["Plugins"] = "Plugins";
+App::$strings["Toggle"] = "Omschakelen";
+App::$strings["Settings"] = "Instellingen";
+App::$strings["Author: "] = "Auteur: ";
+App::$strings["Maintainer: "] = "Beheerder: ";
+App::$strings["Minimum project version: "] = "Minimum versie Hubzilla: ";
+App::$strings["Maximum project version: "] = "Maximum versie Hubzilla:";
+App::$strings["Minimum PHP version: "] = "Minimum versie PHP: ";
+App::$strings["Compatible Server Roles: "] = "Werkt met configuratietypes: ";
+App::$strings["Requires: "] = "Vereist: ";
+App::$strings["Disabled - version incompatibility"] = "Uitgeschakeld - versie is incompatibel";
+App::$strings["Enter the public git repository URL of the plugin repo."] = "Vul de openbare Git-URL in van de plugin-repository.";
+App::$strings["Plugin repo git URL"] = "Git-URL plugin-repository";
+App::$strings["Custom repo name"] = "Handmatige repository-naam";
+App::$strings["(optional)"] = "(niet verplicht)";
+App::$strings["Download Plugin Repo"] = "Plugin-repository downloaden";
+App::$strings["Install new repo"] = "Nieuwe repository installeren";
+App::$strings["Install"] = "Installeren";
+App::$strings["Cancel"] = "Annuleren";
+App::$strings["Manage Repos"] = "Repositories beheren";
+App::$strings["Installed Plugin Repositories"] = "Toegevoegde plugin-repositories";
+App::$strings["Install a New Plugin Repository"] = "Nieuwe plugin-repository toevoegen";
+App::$strings["Update"] = "Bijwerken";
+App::$strings["Switch branch"] = "Branch veranderen";
+App::$strings["Remove"] = "Verwijderen";
+App::$strings["Theme settings updated."] = "Thema-instellingen bijgewerkt.";
+App::$strings["No themes found."] = "Geen thema's gevonden";
+App::$strings["Screenshot"] = "Schermafdruk";
+App::$strings["Themes"] = "Thema's";
+App::$strings["[Experimental]"] = "[Experimenteel]";
+App::$strings["[Unsupported]"] = "[Niet ondersteund]";
+App::$strings["Export Channel"] = "Kanaal exporteren";
+App::$strings["Export your basic channel information to a file. This acts as a backup of your connections, permissions, profile and basic data, which can be used to import your data to a new server hub, but does not contain your content."] = "Exporteer de basisinformatie van jouw kanaal naar een bestand. Dit fungeert als een back-up van jouw connecties, permissies, profiel en basisgegevens, die gebruikt kan worden om op een nieuwe hub jouw gegevens te importeren. Deze back-up bevat echter niet de inhoud van jouw kanaal.";
+App::$strings["Export Content"] = "Inhoud exporteren";
+App::$strings["Export your channel information and recent content to a JSON backup that can be restored or imported to another server hub. This backs up all of your connections, permissions, profile data and several months of posts. This file may be VERY large. Please be patient - it may take several minutes for this download to begin."] = "Exporteer informatie en recente inhoud van jouw kanaal naar een JSON-back-up, wat kan worden gebruikt om jouw kanaal te herstellen of te importeren op een andere hub. Dit slaat al jouw connecties, permissies, profielgegevens en enkele maanden aan inhoud van jouw kanaal op. Dit bestand kan ZEER groot worden. Wees geduldig - het kan enkele minuten duren voordat de download begint.";
+App::$strings["Export your posts from a given year."] = "Exporteer jouw berichten uit een bepaald jaar.";
+App::$strings["You may also export your posts and conversations for a particular year or month. Adjust the date in your browser location bar to select other dates. If the export fails (possibly due to memory exhaustion on your server hub), please try again selecting a more limited date range."] = "Je kan ook berichten en conversaties uit een bepaald jaar of van een bepaalde maand exporteren. Verander de datum in de adresbalk van jouw webbrowser om andere jaren en maanden te selecteren. Wanneer het exporteren mislukt (waarschijnlijk door een gebrek aan beschikbaar servergeheugen), probeer het dan nogmaals met een beperkter tijdvak.";
+App::$strings["To select all posts for a given year, such as this year, visit <a href=\"%1\$s\">%2\$s</a>"] = "Bezoek <a href=\"%1\$s\">%2\$s</a> om alle berichten van bijvoorbeeld dit jaar te selecteren. ";
+App::$strings["To select all posts for a given month, such as January of this year, visit <a href=\"%1\$s\">%2\$s</a>"] = "Bezoek <a href=\"%1\$s\">%2\$s</a> om alle berichten van bijvoorbeeld januari dit jaar te selecteren.";
+App::$strings["These content files may be imported or restored by visiting <a href=\"%1\$s\">%2\$s</a> on any site containing your channel. For best results please import or restore these in date order (oldest first)."] = "Deze back-up-bestanden kunnen geïmporteerd of hersteld worden door op jouw hub en met jouw kanaal <a href=\"%1\$s\">%2\$s</a> te bezoeken. Voor het beste resultaat kan je de bestanden in chronologische volgorde importeren of herstellen.";
App::$strings["Layout Name"] = "Naam lay-out";
-App::$strings["Layout Description (Optional)"] = "Lay-out-omschrijving (optioneel)";
+App::$strings["Layout Description (Optional)"] = "Lay-out-omschrijving (niet verplicht)";
App::$strings["Edit Layout"] = "Lay-out bewerken";
App::$strings["Page link"] = "Paginalink";
-App::$strings["Insert web link"] = "Weblink invoegen";
App::$strings["Edit Webpage"] = "Webpagina bewerken";
-App::$strings["Photos"] = "Foto's";
-App::$strings["You must be logged in to see this page."] = "Je moet zijn ingelogd om deze pagina te kunnen bekijken.";
-App::$strings["Posts and comments"] = "Berichten en reacties";
-App::$strings["Only posts"] = "Alleen berichten";
-App::$strings["Insufficient permissions. Request redirected to profile page."] = "Onvoldoende permissies. Doorgestuurd naar profielpagina.";
+App::$strings["Apps"] = "Apps";
+App::$strings["Manage apps"] = "Apps beheren";
+App::$strings["Create new app"] = "Nieuwe app aanmaken";
+App::$strings["This site is not a directory server"] = "Deze hub is geen kanalengidshub (directoryserver)";
+App::$strings["This directory server requires an access token"] = "Deze kanalengidshub (directoryserver) heeft een toegangs-token nodig";
App::$strings["No such group"] = "Collectie niet gevonden";
App::$strings["No such channel"] = "Niet zo'n kanaal";
App::$strings["forum"] = "forum";
@@ -571,6 +535,7 @@ App::$strings["Search Results For:"] = "Zoekresultaten voor:";
App::$strings["Privacy group is empty"] = "Privacygroep is leeg";
App::$strings["Privacy group: "] = "Privacygroep: ";
App::$strings["Invalid connection."] = "Ongeldige connectie.";
+App::$strings["Invalid channel."] = "Onbekend kanaal.";
App::$strings["Unable to update menu."] = "Niet in staat om menu aan te passen";
App::$strings["Unable to create menu."] = "Niet in staat om menu aan te maken.";
App::$strings["Menu Name"] = "Menunaam";
@@ -581,6 +546,7 @@ App::$strings["Allow Bookmarks"] = "Bladwijzers toestaan";
App::$strings["Menu may be used to store saved bookmarks"] = "Menu kan gebruikt worden om bladwijzers in op te slaan";
App::$strings["Submit and proceed"] = "Opslaan en doorgaan";
App::$strings["Menus"] = "Menu's";
+App::$strings["Drop"] = "Verwijderen";
App::$strings["Created"] = "Aangemaakt";
App::$strings["Edited"] = "Bewerkt";
App::$strings["Bookmarks allowed"] = "Bladwijzers toegestaan";
@@ -597,39 +563,171 @@ App::$strings["Menu title"] = "Titel van menu";
App::$strings["Menu title as seen by others"] = "Titel van menu zoals anderen dat zien.";
App::$strings["Allow bookmarks"] = "Bladwijzers toestaan";
App::$strings["Not found."] = "Niet gevonden.";
-App::$strings["App installed."] = "App geïnstalleerd";
-App::$strings["Malformed app."] = "Misvormde app.";
-App::$strings["Embed code"] = "Insluitcode";
-App::$strings["Edit App"] = "App bewerken";
-App::$strings["Create App"] = "App maken";
-App::$strings["Name of app"] = "Naam van app";
-App::$strings["Required"] = "Vereist";
-App::$strings["Location (URL) of app"] = "Locatie (URL) van app";
-App::$strings["Description"] = "Omschrijving";
-App::$strings["Photo icon URL"] = "URL van pictogram";
-App::$strings["80 x 80 pixels - optional"] = "80 x 80 pixels (optioneel)";
-App::$strings["Categories (optional, comma separated list)"] = "Categorieën (optioneel, door komma's gescheiden lijst)";
-App::$strings["Version ID"] = "Versie-ID";
-App::$strings["Price of app"] = "Prijs van de app";
-App::$strings["Location (URL) to purchase app"] = "Locatie (URL) om de app aan te schaffen";
App::$strings["Edit post"] = "Bericht bewerken";
-App::$strings["Documentation Search"] = "Zoek documentatie";
-App::$strings["About"] = "Over";
-App::$strings["Members"] = "Kanalen";
-App::$strings["Administrators"] = "Beheerders";
-App::$strings["Developers"] = "Ontwikkelaars";
-App::$strings["Tutorials"] = "Zelfstudie";
-App::$strings["\$Projectname Documentation"] = "\$Projectname-documentatie";
-App::$strings["Contents"] = "Inhoud";
-App::$strings["Share content from Firefox to \$Projectname"] = "Deel webpagina's vanuit Firefox met ";
-App::$strings["Activate the Firefox \$Projectname provider"] = "Activeer de \$Projectname-service in Firefox";
-App::$strings["Apps"] = "Apps";
+App::$strings["Location not found."] = "Locatie niet gevonden.";
+App::$strings["Location lookup failed."] = "Opzoeken locatie mislukt";
+App::$strings["Please select another location to become primary before removing the primary location."] = "Kies eerst een andere primaire locatie alvorens de huidige primaire locatie te verwijderen.";
+App::$strings["Syncing locations"] = "Locaties synchronizeren";
+App::$strings["No locations found."] = "Geen locaties gevonden.";
+App::$strings["Manage Channel Locations"] = "Kanaallocaties beheren";
+App::$strings["Location"] = "Locatie";
+App::$strings["Primary"] = "Primair";
+App::$strings["Sync Now"] = "Nu synchroniseren";
+App::$strings["Please wait several minutes between consecutive operations."] = "Wacht enkele minuten tussen opeenvolgende handelingen.";
+App::$strings["When possible, drop a location by logging into that website/hub and removing your channel."] = "Wij adviseren, wanneer dit (nog) mogelijk is, de locatie te verwijderen door op de hub van de kloon in te loggen en het kanaal daar te verwijderen.";
+App::$strings["Use this form to drop the location if the hub is no longer operating."] = "Gebruik dit formulier om de locatie te verwijderen wanneer de hub van de kloon niet meer operationeel is.";
+App::$strings["Public Hubs"] = "Openbare hubs";
+App::$strings["The listed hubs allow public registration for the \$Projectname network. All hubs in the network are interlinked so membership on any of them conveys membership in the network as a whole. Some hubs may require subscription or provide tiered service plans. The hub itself <strong>may</strong> provide additional details."] = "Op de hier weergegeven hubs kan iedereen zich voor het \$Projectname-netwerk aanmelden. Alle hubs in het netwerk zijn met elkaar verbonden, dus maakt het qua lidmaatschap niet uit waar je je aanmeldt. Op sommige hubs heb je eerst goedkeuring nodig en sommige hubs vereisen een financiële tegemoetkoming voor bepaalde uitbreidingen. <strong>Mogelijk</strong> wordt hierover op de hub zelf meer informatie gegeven.";
+App::$strings["Hub URL"] = "Hub-URL";
+App::$strings["Access Type"] = "Toegangs-<br/>&nbsp;type";
+App::$strings["Registration Policy"] = "Registratie-<br/>&nbsp;beleid";
+App::$strings["Stats"] = "Stats";
+App::$strings["Software"] = "Software";
+App::$strings["Ratings"] = "Beoordelingen";
+App::$strings["Rate"] = "Beoordeel";
+App::$strings["View"] = "Weergeven";
+App::$strings["Could not access contact record."] = "Kon geen toegang krijgen tot de connectie-gegevens.";
+App::$strings["Could not locate selected profile."] = "Kon het gekozen profiel niet vinden.";
+App::$strings["Connection updated."] = "Connectie bijgewerkt.";
+App::$strings["Failed to update connection record."] = "Bijwerken van connectie-gegevens mislukt.";
+App::$strings["is now connected to"] = "is nu verbonden met";
+App::$strings["Could not access address book record."] = "Kon geen toegang krijgen tot de record van de connectie.";
+App::$strings["Refresh failed - channel is currently unavailable."] = "Vernieuwen mislukt - kanaal is momenteel niet beschikbaar";
+App::$strings["Unable to set address book parameters."] = "Niet in staat om de parameters van connecties in te stellen.";
+App::$strings["Connection has been removed."] = "Connectie is verwijderd";
+App::$strings["View Profile"] = "Profiel weergeven";
+App::$strings["View %s's profile"] = "Profiel van %s weergeven";
+App::$strings["Refresh Permissions"] = "Permissies vernieuwen";
+App::$strings["Fetch updated permissions"] = "Aangepaste permissies ophalen";
+App::$strings["Refresh Photo"] = "Foto vernieuwen";
+App::$strings["Fetch updated photo"] = "Aangepaste foto ophalen";
+App::$strings["Recent Activity"] = "Recente activiteit/berichten";
+App::$strings["View recent posts and comments"] = "Recente berichten en reacties weergeven";
+App::$strings["Block (or Unblock) all communications with this connection"] = "Blokkeer (of deblokkeer) alle communicatie met deze connectie";
+App::$strings["This connection is blocked!"] = "Deze connectie is geblokkeerd!";
+App::$strings["Unignore"] = "Niet meer negeren";
+App::$strings["Ignore (or Unignore) all inbound communications from this connection"] = "Negeer (of negeer niet meer) alle inkomende communicatie van deze connectie";
+App::$strings["This connection is ignored!"] = "Deze connectie wordt genegeerd!";
+App::$strings["Unarchive"] = "Niet meer archiveren";
+App::$strings["Archive"] = "Archiveren";
+App::$strings["Archive (or Unarchive) this connection - mark channel dead but keep content"] = "Archiveer (of dearchiveer) deze connectie - markeer het kanaal als dood, maar bewaar de inhoud";
+App::$strings["This connection is archived!"] = "Deze connectie is gearchiveerd!";
+App::$strings["Unhide"] = "Niet meer verbergen";
+App::$strings["Hide"] = "Verbergen";
+App::$strings["Hide or Unhide this connection from your other connections"] = "Deze connectie verbergen (of niet meer verbergen) voor jouw andere connecties";
+App::$strings["This connection is hidden!"] = "Deze connectie is verborgen!";
+App::$strings["Delete this connection"] = "Deze connectie verwijderen";
+App::$strings["Fetch Vcard"] = "Vcard ophalen";
+App::$strings["Fetch electronic calling card for this connection"] = "Visitekaartje van deze connectie ophalen";
+App::$strings["Permissions"] = "Permissies";
+App::$strings["Open Individual Permissions section by default"] = "Sectie met individuele permissies standaard openen";
+App::$strings["Affinity"] = "Affiniteit";
+App::$strings["Open Set Affinity section by default"] = "Sectie met de affiniteitsinstelling standaard openen";
+App::$strings["Me"] = "Ik";
+App::$strings["Family"] = "Familie";
+App::$strings["Friends"] = "Vrienden";
+App::$strings["Acquaintances"] = "Kennissen";
+App::$strings["Filter"] = "Filter";
+App::$strings["Open Custom Filter section by default"] = "Sectie met de berichtenfilter standaard openen";
+App::$strings["Approve this connection"] = "Deze connectie accepteren";
+App::$strings["Accept connection to allow communication"] = "Keur deze connectie goed om communicatie toe te staan";
+App::$strings["Set Affinity"] = "Affiniteit instellen";
+App::$strings["Set Profile"] = "Profiel instellen";
+App::$strings["Set Affinity & Profile"] = "Affiniteit en profiel instellen";
+App::$strings["none"] = "geen";
+App::$strings["Connection Default Permissions"] = "Standaard permissies voor connecties";
+App::$strings["Connection: %s"] = "Connectie: %s";
+App::$strings["Apply these permissions automatically"] = "Deze permissies automatisch toepassen";
+App::$strings["Connection requests will be approved without your interaction"] = "Connectieverzoeken zullen automatisch worden geaccepteerd";
+App::$strings["Permission role"] = "Permissietype";
+App::$strings["Add permission role"] = "Permissietype toevoegen";
+App::$strings["This connection's primary address is"] = "Het primaire kanaaladres van deze connectie is";
+App::$strings["Available locations:"] = "Beschikbare locaties:";
+App::$strings["The permissions indicated on this page will be applied to all new connections."] = "Permissies die op deze pagina staan vermeld worden op alle nieuwe connecties toegepast.";
+App::$strings["Connection Tools"] = "Hulpmiddelen";
+App::$strings["Slide to adjust your degree of friendship"] = "Schuif om te bepalen hoe goed je iemand kent en/of mag";
+App::$strings["Rating"] = "Beoordeling";
+App::$strings["Slide to adjust your rating"] = "Gebruik de schuif om je beoordeling te geven";
+App::$strings["Optionally explain your rating"] = "Verklaar jouw beoordeling (niet verplicht)";
+App::$strings["Custom Filter"] = "Berichtenfilter";
+App::$strings["Only import posts with this text"] = "Importeer alleen berichten met deze tekst";
+App::$strings["words one per line or #tags or /patterns/ or lang=xx, leave blank to import all posts"] = "woorden (één per regel), #tags, /regex/ of talen (lang=iso639-1) - laat leeg om alle berichten te importeren";
+App::$strings["Do not import posts with this text"] = "Importeer geen berichten met deze tekst";
+App::$strings["This information is public!"] = "Deze informatie is openbaar!";
+App::$strings["Connection Pending Approval"] = "Connectie moet nog geaccepteerd worden";
+App::$strings["inherited"] = "geërfd";
+App::$strings["Please choose the profile you would like to display to %s when viewing your profile securely."] = "Kies het profiel dat je aan %s wil tonen wanneer hij/zij ingelogd jouw profiel wil bekijken.";
+App::$strings["Their Settings"] = "Hun instellingen";
+App::$strings["My Settings"] = "Mijn instellingen";
+App::$strings["Individual Permissions"] = "Individuele permissies";
+App::$strings["Some permissions may be inherited from your channel's <a href=\"settings\"><strong>privacy settings</strong></a>, which have higher priority than individual settings. You can <strong>not</strong> change those settings here."] = "Sommige permissies worden mogelijk overgeërfd van de <a href=\"settings\">privacy-instellingen</a> van jouw kanaal, die een hogere prioriteit hebben dan deze individuele instellingen. Je kan je deze overgeërfde permissies hier <strong>niet</strong> veranderen.";
+App::$strings["Some permissions may be inherited from your channel's <a href=\"settings\"><strong>privacy settings</strong></a>, which have higher priority than individual settings. You can change those settings here but they wont have any impact unless the inherited setting changes."] = "Sommige permissies worden mogelijk overgeërfd van de <a href=\"settings\">privacy-instellingen</a> van jouw kanaal, die een hogere prioriteit hebben dan deze individuele permissies. Je kan de permissies hier veranderen, maar die hebben geen effect, tenzij de overgeërfde permissies worden veranderd. ";
+App::$strings["Last update:"] = "Laatste wijziging:";
+App::$strings["Details"] = "Details";
+App::$strings["Organisation"] = "Organisatie";
+App::$strings["Title"] = "Titel";
+App::$strings["Phone"] = "Telefoon";
+App::$strings["Instant messenger"] = "Instant messenger";
+App::$strings["Website"] = "Website";
+App::$strings["Note"] = "Opmerking";
+App::$strings["Mobile"] = "Mobiel";
+App::$strings["Home"] = "Thuis";
+App::$strings["Work"] = "Werk";
+App::$strings["Add Contact"] = "Contact toevoegen";
+App::$strings["Add Field"] = "Veld toevoegen";
+App::$strings["P.O. Box"] = "Postbus";
+App::$strings["Additional"] = "Extra";
+App::$strings["Street"] = "Straat en huisnummer";
+App::$strings["Locality"] = "Plaats";
+App::$strings["Region"] = "Provincie/staat/regio/enz.";
+App::$strings["ZIP Code"] = "Postcode";
+App::$strings["Country"] = "Land";
+App::$strings["Calendar entries imported."] = "Agenda-items geïmporteerd.";
+App::$strings["No calendar entries found."] = "Geen agenda-items gevonden.";
+App::$strings["Event can not end before it has started."] = "Gebeurtenis kan niet eindigen voordat het is begonnen";
+App::$strings["Unable to generate preview."] = "Niet in staat om voorvertoning te genereren";
+App::$strings["Event title and start time are required."] = "Titel en begintijd van gebeurtenis zijn vereist.";
+App::$strings["Event not found."] = "Gebeurtenis niet gevonden";
+App::$strings["event"] = "gebeurtenis";
+App::$strings["Edit event title"] = "Titel bewerken";
+App::$strings["Event title"] = "Titel";
+App::$strings["Categories (comma-separated list)"] = "Categorieën (door komma's gescheiden lijst)";
+App::$strings["Edit Category"] = "Categorie";
+App::$strings["Category"] = "Categorie";
+App::$strings["Edit start date and time"] = "Begindatum en -tijd bewerken";
+App::$strings["Start date and time"] = "Begindatum en -tijd";
+App::$strings["Finish date and time are not known or not relevant"] = "Einddatum en -tijd zijn niet bekend of niet van toepassing";
+App::$strings["Edit finish date and time"] = "Einddatum en -tijd bewerken";
+App::$strings["Finish date and time"] = "Einddatum en -tijd";
+App::$strings["Adjust for viewer timezone"] = "Aanpassen aan de tijdzone van wie deze gebeurtenis bekijkt";
+App::$strings["Important for events that happen in a particular place. Not practical for global holidays."] = "Belangrijk voor gebeurtenissen die op een bepaalde locatie plaatsvinden. Niet praktisch voor wereldwijde feestdagen.";
+App::$strings["Edit Description"] = "Omschrijving bewerken";
+App::$strings["Edit Location"] = "Locatie bewerken";
+App::$strings["Preview"] = "Voorvertoning";
+App::$strings["Permission settings"] = "Permissies";
+App::$strings["Timezone:"] = "Tijdzone:";
+App::$strings["Advanced Options"] = "Geavanceerde opties";
+App::$strings["l, F j"] = "l j F";
+App::$strings["Edit event"] = "Gebeurtenis bewerken";
+App::$strings["Delete event"] = "Gebeurtenis verwijderen";
+App::$strings["Link to Source"] = "Originele locatie";
+App::$strings["calendar"] = "agenda";
+App::$strings["Edit Event"] = "Gebeurtenis bewerken";
+App::$strings["Create Event"] = "Gebeurtenis aanmaken";
+App::$strings["Previous"] = "Vorige";
+App::$strings["Next"] = "Volgende";
+App::$strings["Export"] = "Exporteren";
+App::$strings["Month"] = "Maand";
+App::$strings["Week"] = "Week";
+App::$strings["Day"] = "Dag";
+App::$strings["Today"] = "Vandaag";
+App::$strings["Event removed"] = "Gebeurtenis verwijderd";
+App::$strings["Failed to remove event"] = "Verwijderen gebeurtenis mislukt";
App::$strings["\$Projectname"] = "\$Projectname";
App::$strings["Welcome to %s"] = "Welkom op %s";
App::$strings["Permission Denied."] = "Toegang geweigerd";
App::$strings["File not found."] = "Bestand niet gevonden.";
App::$strings["Edit file permissions"] = "Bestandsrechten bewerken";
-App::$strings["Permissions"] = "Permissies";
App::$strings["Set/edit permissions"] = "Rechten instellen/bewerken";
App::$strings["Include all files and sub folders"] = "Toepassen op alle bestanden en submappen";
App::$strings["Return to file list"] = "Terugkeren naar bestandlijst ";
@@ -638,45 +736,105 @@ App::$strings["Copy/paste this URL to link file from a web page"] = "Kopieer/pla
App::$strings["Share this file"] = "Dit bestand delen";
App::$strings["Show URL to this file"] = "Toon URL van dit bestand";
App::$strings["Notify your contacts about this file"] = "Jouw connecties over dit bestand berichten";
+App::$strings["Photos"] = "Foto's";
+App::$strings["Page owner information could not be retrieved."] = "Informatie over de pagina-eigenaar werd niet ontvangen.";
+App::$strings["Profile Photos"] = "Profielfoto's";
+App::$strings["Album not found."] = "Album niet gevonden.";
+App::$strings["Delete Album"] = "Verwijder album";
+App::$strings["Multiple storage folders exist with this album name, but within different directories. Please remove the desired folder or folders using the Files manager"] = "Er bestaan meerdere submappen met deze albumnaam, maar verspreidt over verschillende mappen. Verwijder de gewenste map(pen) met de bestandsbeheerder.";
+App::$strings["Delete Photo"] = "Verwijder foto";
App::$strings["Public access denied."] = "Openbare toegang geweigerd.";
-App::$strings["%d rating"] = array(
- 0 => "%d beoordeling",
- 1 => "%d beoordelingen",
+App::$strings["No photos selected"] = "Geen foto's geselecteerd";
+App::$strings["Access to this item is restricted."] = "Toegang tot dit item is beperkt.";
+App::$strings["%1$.2f MB of %2$.2f MB photo storage used."] = "%1$.2f MB van %2$.2f MB aan foto-opslag gebruikt.";
+App::$strings["%1$.2f MB photo storage used."] = "%1$.2f MB aan foto-opslag gebruikt.";
+App::$strings["Upload Photos"] = "Foto's uploaden";
+App::$strings["Enter an album name"] = "Vul een albumnaam in";
+App::$strings["or select an existing album (doubleclick)"] = "of kies een bestaand album (dubbelklikken)";
+App::$strings["Create a status post for this upload"] = "Plaats een bericht voor deze upload.";
+App::$strings["Caption (optional):"] = "Bijschrift (niet verplicht):";
+App::$strings["Description (optional):"] = "Omschrijving (niet verplicht):";
+App::$strings["Album name could not be decoded"] = "Albumnaam kon niet gedecodeerd worden";
+App::$strings["Contact Photos"] = "Connectiefoto's";
+App::$strings["Show Newest First"] = "Nieuwste eerst weergeven";
+App::$strings["Show Oldest First"] = "Oudste eerst weergeven";
+App::$strings["View Photo"] = "Foto weergeven";
+App::$strings["Edit Album"] = "Album bewerken";
+App::$strings["Permission denied. Access to this item may be restricted."] = "Toegang geweigerd. Toegang tot dit item kan zijn beperkt.";
+App::$strings["Photo not available"] = "Foto niet aanwezig";
+App::$strings["Use as profile photo"] = "Als profielfoto gebruiken";
+App::$strings["Use as cover photo"] = "Als omslagfoto gebruiken";
+App::$strings["Private Photo"] = "Privéfoto";
+App::$strings["View Full Size"] = "Volledige grootte weergeven";
+App::$strings["Edit photo"] = "Foto bewerken";
+App::$strings["Rotate CW (right)"] = "Draai met de klok mee (naar rechts)";
+App::$strings["Rotate CCW (left)"] = "Draai tegen de klok in (naar links)";
+App::$strings["Move photo to album"] = "Verplaatst foto naar album";
+App::$strings["Enter a new album name"] = "Vul een nieuwe albumnaam in";
+App::$strings["or select an existing one (doubleclick)"] = "of kies een bestaand album (dubbelklikken)";
+App::$strings["Caption"] = "Bijschrift";
+App::$strings["Add a Tag"] = "Tag toevoegen";
+App::$strings["Example: @bob, @Barbara_Jensen, @jim@example.com"] = "Voorbeeld: @bob, @Barbara_Jansen, @jan@voorbeeld.nl";
+App::$strings["Flag as adult in album view"] = "Markeer als voor volwassenen in albumweergave";
+App::$strings["I like this (toggle)"] = "Vind ik leuk";
+App::$strings["I don't like this (toggle)"] = "Vind ik niet leuk";
+App::$strings["Share"] = "Delen";
+App::$strings["Please wait"] = "Even wachten";
+App::$strings["This is you"] = "Dit ben jij";
+App::$strings["Comment"] = "Reactie";
+App::$strings["__ctx:title__ Likes"] = "vinden dit leuk";
+App::$strings["__ctx:title__ Dislikes"] = "vinden dit niet leuk";
+App::$strings["__ctx:title__ Agree"] = "eens";
+App::$strings["__ctx:title__ Disagree"] = "oneens";
+App::$strings["__ctx:title__ Abstain"] = "onthoudingen";
+App::$strings["__ctx:title__ Attending"] = "aanwezig";
+App::$strings["__ctx:title__ Not attending"] = "niet aanwezig";
+App::$strings["__ctx:title__ Might attend"] = "mogelijk aanwezig";
+App::$strings["View all"] = "Toon alles";
+App::$strings["__ctx:noun__ Like"] = array(
+ 0 => "vindt dit leuk",
+ 1 => "vinden dit leuk",
);
-App::$strings["Gender: "] = "Geslacht:";
-App::$strings["Status: "] = "Status: ";
-App::$strings["Homepage: "] = "Homepage: ";
-App::$strings["Age:"] = "Leeftijd:";
-App::$strings["Location:"] = "Plaats:";
-App::$strings["Description:"] = "Omschrijving:";
-App::$strings["Hometown:"] = "Oorspronkelijk uit:";
-App::$strings["About:"] = "Over:";
-App::$strings["Public Forum:"] = "Openbaar forum:";
-App::$strings["Keywords: "] = "Trefwoorden: ";
-App::$strings["Don't suggest"] = "Niet voorstellen";
-App::$strings["Common connections:"] = "Gemeenschappelijke connecties:";
-App::$strings["Global Directory"] = "Volledige kanalengids";
-App::$strings["Local Directory"] = "Lokale kanalengids";
-App::$strings["Finding:"] = "Gezocht naar:";
-App::$strings["Channel Suggestions"] = "Voorgestelde kanalen";
-App::$strings["next page"] = "volgende pagina";
-App::$strings["previous page"] = "vorige pagina";
-App::$strings["Sort options"] = "Sorteeropties";
-App::$strings["Alphabetic"] = "Alfabetisch";
-App::$strings["Reverse Alphabetic"] = "Omgekeerd alfabetisch";
-App::$strings["Newest to Oldest"] = "Nieuw naar oud";
-App::$strings["Oldest to Newest"] = "Oud naar nieuw";
-App::$strings["No entries (some entries may be hidden)."] = "Niets gevonden (sommige kanalen kunnen verborgen zijn).";
-App::$strings["Unable to locate original post."] = "Niet in staat om de originele locatie van het bericht te vinden. ";
-App::$strings["Empty post discarded."] = "Leeg bericht geannuleerd";
-App::$strings["Executable content type not permitted to this channel."] = "Uitvoerbare bestanden zijn niet toegestaan op dit kanaal.";
-App::$strings["Duplicate post suppressed."] = "Dubbel bericht tegengehouden.";
-App::$strings["System error. Post not saved."] = "Systeemfout. Bericht niet opgeslagen.";
-App::$strings["Unable to obtain post information from database."] = "Niet in staat om informatie over dit bericht uit de database te verkrijgen.";
-App::$strings["You have reached your limit of %1$.0f top level posts."] = "Je hebt jouw limiet van %1$.0f berichten bereikt.";
-App::$strings["You have reached your limit of %1$.0f webpages."] = "Je hebt jouw limiet van %1$.0f webpagina's bereikt.";
-App::$strings["toggle full screen mode"] = "Volledig scherm";
-App::$strings["Channel added."] = "Kanaal toegevoegd.";
+App::$strings["__ctx:noun__ Dislike"] = array(
+ 0 => "vindt dit niet leuk",
+ 1 => "vinden dit niet leuk",
+);
+App::$strings["Photo Tools"] = "Hulpmiddelen";
+App::$strings["In This Photo:"] = "Op deze foto:";
+App::$strings["Map"] = "Kaart";
+App::$strings["__ctx:noun__ Likes"] = "vinden dit leuk";
+App::$strings["__ctx:noun__ Dislikes"] = "vinden dit niet leuk";
+App::$strings["Close"] = "Sluiten";
+App::$strings["View Album"] = "Album weergeven";
+App::$strings["Recent Photos"] = "Recente foto's";
+App::$strings["Privacy group created."] = "Privacygroep aangemaakt";
+App::$strings["Could not create privacy group."] = "Kon privacygroep niet aanmaken";
+App::$strings["Privacy group not found."] = "Privacygroep niet gevonden";
+App::$strings["Privacy group updated."] = "Privacygroep bijgewerkt";
+App::$strings["Create a group of channels."] = "Privacygroep met kanalen aanmaken";
+App::$strings["Privacy group name: "] = "Naam privacygroep: ";
+App::$strings["Members are visible to other channels"] = "Kanalen in deze privacygroep zijn zichtbaar voor andere kanalen";
+App::$strings["Privacy group removed."] = "Privacygroep verwijderd.";
+App::$strings["Unable to remove privacy group."] = "Verwijderen privacygroep mislukt";
+App::$strings["Privacy group editor"] = "Privacygroep bewerken";
+App::$strings["All Connected Channels"] = "Alle kanaalconnecties";
+App::$strings["Click on a channel to add or remove."] = "Klik op een kanaal om deze toe te voegen of te verwijderen.";
+App::$strings["Invalid message"] = "Ongeldig bericht";
+App::$strings["no results"] = "geen resultaten";
+App::$strings["channel sync processed"] = "kanaalsync verwerkt";
+App::$strings["queued"] = "in wachtrij";
+App::$strings["posted"] = "verstuurd";
+App::$strings["accepted for delivery"] = "geaccepteerd om afgeleverd te worden";
+App::$strings["updated"] = "geüpdatet";
+App::$strings["update ignored"] = "update genegeerd";
+App::$strings["permission denied"] = "toegang geweigerd";
+App::$strings["recipient not found"] = "ontvanger niet gevonden";
+App::$strings["mail recalled"] = "Privébericht ingetrokken";
+App::$strings["duplicate mail received"] = "dubbel privébericht ontvangen";
+App::$strings["mail delivered"] = "privébericht afgeleverd";
+App::$strings["Delivery report for %1\$s"] = "Afleveringsrapport voor %1\$s";
+App::$strings["Options"] = "Opties";
+App::$strings["Redeliver"] = "Opnieuw afleveren";
App::$strings["Unable to lookup recipient."] = "Niet in staat om ontvanger op te zoeken.";
App::$strings["Unable to communicate with requested channel."] = "Niet in staat om met het aangevraagde kanaal te communiceren.";
App::$strings["Cannot verify requested channel."] = "Kan opgevraagd kanaal niet verifieren";
@@ -709,52 +867,20 @@ App::$strings["layout"] = "lay-out";
App::$strings["menu"] = "menu";
App::$strings["%s element installed"] = "%s onderdeel geïnstalleerd";
App::$strings["%s element installation failed"] = "Installatie %s-element mislukt";
-App::$strings["Nothing to import."] = "Niets gevonden om te importeren";
-App::$strings["Unable to download data from old server"] = "Niet in staat om gegevens van de oude hub te downloaden";
-App::$strings["Imported file is empty."] = "Geïmporteerde bestand is leeg";
-App::$strings["Warning: Database versions differ by %1\$d updates."] = "Waarschuwing: database-versies lopen %1\$d updates achter.";
App::$strings["Import completed"] = "Importeren voltooid";
App::$strings["Import Items"] = "Importeer items";
App::$strings["Use this form to import existing posts and content from an export file."] = "Gebruik dit formulier om bestaande berichten en andere inhoud vanuit een exportbestand te importeren.";
-App::$strings["File to Upload"] = "Bestand om te uploaden";
-App::$strings["Total invitation limit exceeded."] = "Limiet voor aantal uitnodigingen overschreden.";
-App::$strings["%s : Not a valid email address."] = "%s : Geen geldig e-mailadres.";
-App::$strings["Please join us on \$Projectname"] = "Uitnodiging voor \$Projectname";
-App::$strings["Invitation limit exceeded. Please contact your site administrator."] = "Limiet voor aantal uitnodigingen overschreden. Neem contact op met je hub-beheerder.";
-App::$strings["%s : Message delivery failed."] = "%s: Aflevering bericht mislukt.";
-App::$strings["%d message sent."] = array(
- 0 => "%d bericht verzonden.",
- 1 => "%d berichten verzonden.",
-);
-App::$strings["You have no more invitations available"] = "Je hebt geen uitnodigingen meer beschikbaar";
-App::$strings["Send invitations"] = "Uitnodigingen verzenden";
-App::$strings["Enter email addresses, one per line:"] = "Voer e-mailadressen in, één per regel:";
-App::$strings["Please join my community on \$Projectname."] = "Hierbij nodig ik je uit om mij, en andere vrienden en kennissen, op \$Projectname te vergezellen. Lees meer over \$Projectname op http://hubzilla.org";
-App::$strings["You will need to supply this invitation code:"] = "Je moet deze uitnodigingscode opgeven:";
-App::$strings["1. Register at any \$Projectname location (they are all inter-connected)"] = "1. Registreer je op een willekeurige \$Projectname-hub (ze zijn allemaal onderling met elkaar verbonden):";
-App::$strings["2. Enter my \$Projectname network address into the site searchbar."] = "2. Nadat je bent ingelogd en een kanaal hebt aangemaakt kan je mijn \$Projectname-kanaaladres in het zoekveld invullen:";
-App::$strings["or visit"] = "of bezoek";
-App::$strings["3. Click [Connect]"] = "3. Klik op [+ Verbinden]";
-App::$strings["Block Name"] = "Bloknaam";
-App::$strings["Title (optional)"] = "Titel (optioneel)";
-App::$strings["Edit Block"] = "Blok bewerken";
-App::$strings["Privacy group created."] = "Privacygroep aangemaakt";
-App::$strings["Could not create privacy group."] = "Kon privacygroep niet aanmaken";
-App::$strings["Privacy group not found."] = "Privacygroep niet gevonden";
-App::$strings["Privacy group updated."] = "Privacygroep bijgewerkt";
-App::$strings["Create a group of channels."] = "Privacygroep met kanalen aanmaken";
-App::$strings["Privacy group name: "] = "Naam privacygroep: ";
-App::$strings["Members are visible to other channels"] = "Kanalen in deze privacygroep zijn zichtbaar voor andere kanalen";
-App::$strings["Privacy group removed."] = "Privacygroep verwijderd.";
-App::$strings["Unable to remove privacy group."] = "Verwijderen privacygroep mislukt";
-App::$strings["Privacy group editor"] = "Privacygroep bewerken";
-App::$strings["All Connected Channels"] = "Alle kanaalconnecties";
-App::$strings["Click on a channel to add or remove."] = "Klik op een kanaal om deze toe te voegen of te verwijderen.";
-App::$strings["Invalid profile identifier."] = "Ongeldige profiel-identificator";
-App::$strings["Profile Visibility Editor"] = "Zichtbaarheid profiel ";
-App::$strings["Profile"] = "Profiel";
-App::$strings["Click on a contact to add or remove."] = "Klik op een connectie om deze toe te voegen of te verwijderen";
-App::$strings["Visible To"] = "Zichtbaar voor";
+App::$strings["You have created %1$.0f of %2$.0f allowed channels."] = "Je hebt %1$.0f van totaal %2$.0f toegestane kanalen aangemaakt.";
+App::$strings["Create a new channel"] = "Nieuw kanaal aanmaken";
+App::$strings["Create New"] = "Nieuwe aanmaken";
+App::$strings["Channel Manager"] = "Kanaalbeheer";
+App::$strings["Current Channel"] = "Huidig kanaal";
+App::$strings["Switch to one of your channels by selecting it."] = "Activeer een van jouw andere kanalen door er op te klikken.";
+App::$strings["Default Channel"] = "Standaardkanaal";
+App::$strings["Make Default"] = "Als standaard instellen";
+App::$strings["%d new messages"] = "%d nieuwe berichten";
+App::$strings["%d new introductions"] = "%d nieuwe connectieverzoeken";
+App::$strings["Delegated Channel"] = "Uitbesteed kanaal";
App::$strings["Hub not found."] = "Hub niet gevonden.";
App::$strings["Unable to create element."] = "Niet in staat om onderdeel aan te maken.";
App::$strings["Unable to update menu element."] = "Menu-onderdeel kan niet worden geüpdatet.";
@@ -785,181 +911,63 @@ App::$strings["Menu item deleted."] = "Menu-item verwijderd.";
App::$strings["Menu item could not be deleted."] = "Menu-item kon niet worden verwijderd.";
App::$strings["Edit Menu Element"] = "Menu-element bewerken";
App::$strings["Link text"] = "Linktekst";
+App::$strings["Item is not editable"] = "Item is niet te bewerken";
App::$strings["No ratings"] = "Geen beoordelingen";
App::$strings["Rating: "] = "Beoordeling: ";
App::$strings["Website: "] = "Website: ";
App::$strings["Description: "] = "Omschrijving: ";
App::$strings["Item not available."] = "Item is niet aanwezig.";
-App::$strings["__ctx:mood__ %1\$s is %2\$s"] = "%1\$s is %2\$s";
-App::$strings["Mood"] = "Stemming";
-App::$strings["Set your current mood and tell your friends"] = "Noteer je huidige stemming en toon het aan je connecties";
+App::$strings["Permissions denied."] = "Permissies niet toegestaan";
+App::$strings["Import"] = "Importeren";
App::$strings["No more system notifications."] = "Geen systeemnotificaties meer.";
App::$strings["System Notifications"] = "Systeemnotificaties";
-App::$strings["Page owner information could not be retrieved."] = "Informatie over de pagina-eigenaar werd niet ontvangen.";
-App::$strings["Profile Photos"] = "Profielfoto's";
-App::$strings["Album not found."] = "Album niet gevonden.";
-App::$strings["Delete Album"] = "Verwijder album";
-App::$strings["Multiple storage folders exist with this album name, but within different directories. Please remove the desired folder or folders using the Files manager"] = "Er bestaan meerdere submappen met deze albumnaam, maar verspreidt over verschillende mappen. Verwijder de gewenste map(pen) met de bestandsbeheerder.";
-App::$strings["Delete Photo"] = "Verwijder foto";
-App::$strings["No photos selected"] = "Geen foto's geselecteerd";
-App::$strings["Access to this item is restricted."] = "Toegang tot dit item is beperkt.";
-App::$strings["%1$.2f MB of %2$.2f MB photo storage used."] = "%1$.2f MB van %2$.2f MB aan foto-opslag gebruikt.";
-App::$strings["%1$.2f MB photo storage used."] = "%1$.2f MB aan foto-opslag gebruikt.";
-App::$strings["Upload Photos"] = "Foto's uploaden";
-App::$strings["Enter an album name"] = "Vul een albumnaam in";
-App::$strings["or select an existing album (doubleclick)"] = "of kies een bestaand album (dubbelklikken)";
-App::$strings["Create a status post for this upload"] = "Plaats een bericht voor deze upload.";
-App::$strings["Caption (optional):"] = "Bijschrift (optioneel):";
-App::$strings["Description (optional):"] = "Omschrijving (optioneel):";
-App::$strings["Album name could not be decoded"] = "Albumnaam kon niet gedecodeerd worden";
-App::$strings["Contact Photos"] = "Connectiefoto's";
-App::$strings["Show Newest First"] = "Nieuwste eerst weergeven";
-App::$strings["Show Oldest First"] = "Oudste eerst weergeven";
-App::$strings["View Photo"] = "Foto weergeven";
-App::$strings["Edit Album"] = "Album bewerken";
-App::$strings["Permission denied. Access to this item may be restricted."] = "Toegang geweigerd. Toegang tot dit item kan zijn beperkt.";
-App::$strings["Photo not available"] = "Foto niet aanwezig";
-App::$strings["Use as profile photo"] = "Als profielfoto gebruiken";
-App::$strings["Use as cover photo"] = "Als omslagfoto gebruiken";
-App::$strings["Private Photo"] = "Privéfoto";
-App::$strings["Previous"] = "Vorige";
-App::$strings["View Full Size"] = "Volledige grootte weergeven";
-App::$strings["Next"] = "Volgende";
-App::$strings["Edit photo"] = "Foto bewerken";
-App::$strings["Rotate CW (right)"] = "Draai met de klok mee (naar rechts)";
-App::$strings["Rotate CCW (left)"] = "Draai tegen de klok in (naar links)";
-App::$strings["Move photo to album"] = "Verplaatst foto naar album";
-App::$strings["Enter a new album name"] = "Vul een nieuwe albumnaam in";
-App::$strings["or select an existing one (doubleclick)"] = "of kies een bestaand album (dubbelklikken)";
-App::$strings["Caption"] = "Bijschrift";
-App::$strings["Add a Tag"] = "Tag toevoegen";
-App::$strings["Example: @bob, @Barbara_Jensen, @jim@example.com"] = "Voorbeeld: @bob, @Barbara_Jansen, @jan@voorbeeld.nl";
-App::$strings["Flag as adult in album view"] = "Markeer als voor volwassenen in albumweergave";
-App::$strings["I like this (toggle)"] = "Vind ik leuk";
-App::$strings["I don't like this (toggle)"] = "Vind ik niet leuk";
-App::$strings["Share"] = "Delen";
-App::$strings["Please wait"] = "Even wachten";
-App::$strings["This is you"] = "Dit ben jij";
-App::$strings["Comment"] = "Reactie";
-App::$strings["Preview"] = "Voorvertoning";
-App::$strings["__ctx:title__ Likes"] = "vinden dit leuk";
-App::$strings["__ctx:title__ Dislikes"] = "vinden dit niet leuk";
-App::$strings["__ctx:title__ Agree"] = "eens";
-App::$strings["__ctx:title__ Disagree"] = "oneens";
-App::$strings["__ctx:title__ Abstain"] = "onthoudingen";
-App::$strings["__ctx:title__ Attending"] = "aanwezig";
-App::$strings["__ctx:title__ Not attending"] = "niet aanwezig";
-App::$strings["__ctx:title__ Might attend"] = "mogelijk aanwezig";
-App::$strings["View all"] = "Toon alles";
-App::$strings["__ctx:noun__ Like"] = array(
- 0 => "vindt dit leuk",
- 1 => "vinden dit leuk",
-);
-App::$strings["__ctx:noun__ Dislike"] = array(
- 0 => "vindt dit niet leuk",
- 1 => "vinden dit niet leuk",
+App::$strings["Authorize application connection"] = "Geef toestemming voor applicatiekoppeling";
+App::$strings["Return to your app and insert this Security Code:"] = "Ga terug naar je app en voeg deze beveiligingscode in:";
+App::$strings["Please login to continue."] = "Inloggen om verder te kunnen gaan.";
+App::$strings["Do you want to authorize this application to access your posts and contacts, and/or create new posts for you?"] = "Wil je deze applicatie toestemming geven om jouw berichten en connecties te zien, en/of nieuwe berichten voor jou te plaatsen?";
+App::$strings["Total invitation limit exceeded."] = "Limiet voor aantal uitnodigingen overschreden.";
+App::$strings["%s : Not a valid email address."] = "%s : Geen geldig e-mailadres.";
+App::$strings["Please join us on \$Projectname"] = "Uitnodiging voor \$Projectname";
+App::$strings["Invitation limit exceeded. Please contact your site administrator."] = "Limiet voor aantal uitnodigingen overschreden. Neem contact op met je hub-beheerder.";
+App::$strings["%s : Message delivery failed."] = "%s: Aflevering bericht mislukt.";
+App::$strings["%d message sent."] = array(
+ 0 => "%d bericht verzonden.",
+ 1 => "%d berichten verzonden.",
);
-App::$strings["Photo Tools"] = "Hulpmiddelen";
-App::$strings["In This Photo:"] = "Op deze foto:";
-App::$strings["Map"] = "Kaart";
-App::$strings["__ctx:noun__ Likes"] = "vinden dit leuk";
-App::$strings["__ctx:noun__ Dislikes"] = "vinden dit niet leuk";
-App::$strings["Close"] = "Sluiten";
-App::$strings["View Album"] = "Album weergeven";
-App::$strings["Recent Photos"] = "Recente foto's";
-App::$strings["\$Projectname Server - Setup"] = "\$Projectname Hub - Setup";
-App::$strings["Could not connect to database."] = "Could not connect to database.";
-App::$strings["Could not connect to specified site URL. Possible SSL certificate or DNS issue."] = "Could not connect to specified hub URL. Possible SSL certificate or DNS issue.";
-App::$strings["Could not create table."] = "Could not create table.";
-App::$strings["Your site database has been installed."] = "Your hub database has been installed.";
-App::$strings["You may need to import the file \"install/schema_xxx.sql\" manually using a database client."] = "You may need to import the file \"install/schema_xxx.sql\" manually using a database client.";
-App::$strings["Please see the file \"install/INSTALL.txt\"."] = "Please see the file \"install/INSTALL.txt\".";
-App::$strings["System check"] = "System check";
-App::$strings["Check again"] = "Check again";
-App::$strings["Database connection"] = "Database connection";
-App::$strings["In order to install \$Projectname we need to know how to connect to your database."] = "In order to install \$Projectname we need to know how to connect to your database.";
-App::$strings["Please contact your hosting provider or site administrator if you have questions about these settings."] = "Please contact your hosting provider or server administrator if you have questions about these settings.";
-App::$strings["The database you specify below should already exist. If it does not, please create it before continuing."] = "The database you specify below should already exist. If it does not, please create it before continuing.";
-App::$strings["Database Server Name"] = "Database Server Name";
-App::$strings["Default is 127.0.0.1"] = "Default is 127.0.0.1";
-App::$strings["Database Port"] = "Database Port";
-App::$strings["Communication port number - use 0 for default"] = "Communication port number - use 0 for default";
-App::$strings["Database Login Name"] = "Database Login Name";
-App::$strings["Database Login Password"] = "Database Login Password";
-App::$strings["Database Name"] = "Database Name";
-App::$strings["Database Type"] = "Database Type";
-App::$strings["Site administrator email address"] = "Hub administrator email address";
-App::$strings["Your account email address must match this in order to use the web admin panel."] = "Your account email address must match this in order to use the web admin panel.";
-App::$strings["Website URL"] = "Hub URL";
-App::$strings["Please use SSL (https) URL if available."] = "Please use SSL (https) URL if available.";
-App::$strings["Please select a default timezone for your website"] = "Please select a default timezone for your hub";
-App::$strings["Site settings"] = "Hub settings";
-App::$strings["PHP version 5.5 or greater is required."] = "PHP version 5.5 or greater is required.";
-App::$strings["PHP version"] = "PHP version";
-App::$strings["Could not find a command line version of PHP in the web server PATH."] = "Could not find a command line version of PHP in the web server PATH.";
-App::$strings["If you don't have a command line version of PHP installed on server, you will not be able to run background polling via cron."] = "If you don't have a command line version of PHP installed on server, you will not be able to run background polling via cron.";
-App::$strings["PHP executable path"] = "PHP executable path";
-App::$strings["Enter full path to php executable. You can leave this blank to continue the installation."] = "Enter full path to php executable. You can leave this blank to continue the installation.";
-App::$strings["Command line PHP"] = "Command line PHP";
-App::$strings["Unable to check command line PHP, as shell_exec() is disabled. This is required."] = "Unable to check command line PHP, as shell_exec() is disabled. This is required.";
-App::$strings["The command line version of PHP on your system does not have \"register_argc_argv\" enabled."] = "The command line version of PHP on your system does not have \"register_argc_argv\" enabled.";
-App::$strings["This is required for message delivery to work."] = "This is required for message delivery to work.";
-App::$strings["PHP register_argc_argv"] = "PHP register_argc_argv";
-App::$strings["Your max allowed total upload size is set to %s. Maximum size of one file to upload is set to %s. You are allowed to upload up to %d files at once."] = "Your max allowed total upload size is set to %s. Maximum size of one file to upload is set to %s. You are allowed to upload up to %d files at once.";
-App::$strings["You can adjust these settings in the server php.ini file."] = "You can adjust these settings in the server php.ini file.";
-App::$strings["PHP upload limits"] = "PHP upload limits";
-App::$strings["Error: the \"openssl_pkey_new\" function on this system is not able to generate encryption keys"] = "Error: the \"openssl_pkey_new\" function on this system is not able to generate encryption keys";
-App::$strings["If running under Windows, please see \"http://www.php.net/manual/en/openssl.installation.php\"."] = "If running under Windows, please see \"http://www.php.net/manual/en/openssl.installation.php\".";
-App::$strings["Generate encryption keys"] = "Generate encryption keys";
-App::$strings["libCurl PHP module"] = "libCurl PHP module";
-App::$strings["GD graphics PHP module"] = "GD graphics PHP module";
-App::$strings["OpenSSL PHP module"] = "OpenSSL PHP module";
-App::$strings["PDO database PHP module"] = "PDO database PHP module";
-App::$strings["mb_string PHP module"] = "mb_string PHP module";
-App::$strings["xml PHP module"] = "xml PHP module";
-App::$strings["Apache mod_rewrite module"] = "Apache mod_rewrite module";
-App::$strings["Error: Apache webserver mod-rewrite module is required but not installed."] = "Error: Apache webserver mod-rewrite module is required but not installed.";
-App::$strings["exec"] = "exec";
-App::$strings["Error: exec is required but is either not installed or has been disabled in php.ini"] = "Error: exec is required but is either not installed or has been disabled in php.ini";
-App::$strings["shell_exec"] = "shell_exec";
-App::$strings["Error: shell_exec is required but is either not installed or has been disabled in php.ini"] = "Error: shell_exec is required but is either not installed or has been disabled in php.ini";
-App::$strings["Error: libCURL PHP module required but not installed."] = "Error: libCURL PHP module required but not installed.";
-App::$strings["Error: GD graphics PHP module with JPEG support required but not installed."] = "Error: GD graphics PHP module with JPEG support required but not installed.";
-App::$strings["Error: openssl PHP module required but not installed."] = "Error: openssl PHP module required but not installed.";
-App::$strings["Error: PDO database PHP module required but not installed."] = "Error: PDO database PHP module required but not installed.";
-App::$strings["Error: mb_string PHP module required but not installed."] = "Error: mb_string PHP module required but not installed.";
-App::$strings["Error: xml PHP module required for DAV but not installed."] = "Error: xml PHP module required for DAV but not installed.";
-App::$strings["The web installer needs to be able to create a file called \".htconfig.php\" in the top folder of your web server and it is unable to do so."] = "The web installer needs to be able to create a file called \".htconfig.php\" in the top folder of your web server and it is unable to do so.";
-App::$strings["This is most often a permission setting, as the web server may not be able to write files in your folder - even if you can."] = "This is most often a permission setting, as the web server may not be able to write files in your folder - even if you can.";
-App::$strings["At the end of this procedure, we will give you a text to save in a file named .htconfig.php in your Red top folder."] = "At the end of this procedure, we will give you a text to save in a file named .htconfig.php in your Red top folder.";
-App::$strings["You can alternatively skip this procedure and perform a manual installation. Please see the file \"install/INSTALL.txt\" for instructions."] = "You can alternatively skip this procedure and perform a manual installation. Please see the file \"install/INSTALL.txt\" for instructions.";
-App::$strings[".htconfig.php is writable"] = ".htconfig.php is writable";
-App::$strings["This software uses the Smarty3 template engine to render its web views. Smarty3 compiles templates to PHP to speed up rendering."] = "This software uses the Smarty3 template engine to render its web views. Smarty3 compiles templates to PHP to speed up rendering.";
-App::$strings["In order to store these compiled templates, the web server needs to have write access to the directory %s under the top level web folder."] = "In order to store these compiled templates, the web server needs to have write access to the directory %s under the top level web folder.";
-App::$strings["Please ensure that the user that your web server runs as (e.g. www-data) has write access to this folder."] = "Please ensure that the user that your web server runs as (e.g. www-data) has write access to this folder.";
-App::$strings["Note: as a security measure, you should give the web server write access to %s only--not the template files (.tpl) that it contains."] = "Note: as a security measure, you should give the web server write access to %s only--not the template files (.tpl) that it contains.";
-App::$strings["%s is writable"] = "%s is writable";
-App::$strings["This software uses the store directory to save uploaded files. The web server needs to have write access to the store directory under the top level web folder"] = "This software uses the store directory to save uploaded files. The web server needs to have write access to the store directory under the top level web folder";
-App::$strings["store is writable"] = "store is writable";
-App::$strings["SSL certificate cannot be validated. Fix certificate or disable https access to this site."] = "SSL certificate cannot be validated. Fix certificate or disable https access to this hub.";
-App::$strings["If you have https access to your website or allow connections to TCP port 443 (the https: port), you MUST use a browser-valid certificate. You MUST NOT use self-signed certificates!"] = "If you have https access to your hub or allow connections to TCP port 443 (the https: port), you MUST use a browser-valid certificate. You MUST NOT use self-signed certificates!";
-App::$strings["This restriction is incorporated because public posts from you may for example contain references to images on your own hub."] = "This restriction is incorporated because public posts from you may for example contain references to images on your own hub.";
-App::$strings["If your certificate is not recognized, members of other sites (who may themselves have valid certificates) will get a warning message on their own site complaining about security issues."] = "If your certificate is not recognized, members of other hubs (who may themselves have valid certificates) will get a warning message on their own hub complaining about security issues.";
-App::$strings["This can cause usability issues elsewhere (not just on your own site) so we must insist on this requirement."] = "This can cause usability issues elsewhere (not just on your own hub) so we must insist on this requirement.";
-App::$strings["Providers are available that issue free certificates which are browser-valid."] = "Providers are available that issue free certificates which are browser-valid.";
-App::$strings["If you are confident that the certificate is valid and signed by a trusted authority, check to see if you have failed to install an intermediate cert. These are not normally required by browsers, but are required for server-to-server communications."] = "If you are confident that the certificate is valid and signed by a trusted authority, check to see if you have failed to install an intermediate cert. These are not normally required by browsers, but are required for server-to-server communications.";
-App::$strings["SSL certificate validation"] = "SSL certificate validation";
-App::$strings["Url rewrite in .htaccess is not working. Check your server configuration.Test: "] = "Url rewrite in .htaccess is not working. Check your server configuration.Test: ";
-App::$strings["Url rewrite is working"] = "Url rewrite is working";
-App::$strings["The database configuration file \".htconfig.php\" could not be written. Please use the enclosed text to create a configuration file in your web server root."] = "The database configuration file \".htconfig.php\" could not be written. Please use the enclosed text to create a configuration file in your web server root.";
-App::$strings["Errors encountered creating database tables."] = "Errors encountered creating database tables.";
-App::$strings["<h1>What next</h1>"] = "<h1>What next</h1>";
-App::$strings["IMPORTANT: You will need to [manually] setup a scheduled task for the poller."] = "IMPORTANT: You will need to [manually] setup a scheduled task for the poller.";
-App::$strings["Item is not editable"] = "Item is niet te bewerken";
-App::$strings["This site is not a directory server"] = "Deze hub is geen kanalengidshub (directoryserver)";
+App::$strings["You have no more invitations available"] = "Je hebt geen uitnodigingen meer beschikbaar";
+App::$strings["Send invitations"] = "Uitnodigingen verzenden";
+App::$strings["Enter email addresses, one per line:"] = "Voer e-mailadressen in, één per regel:";
+App::$strings["Please join my community on \$Projectname."] = "Hierbij nodig ik je uit om mij, en andere vrienden en kennissen, op \$Projectname te vergezellen. Lees meer over \$Projectname op http://hubzilla.org";
+App::$strings["You will need to supply this invitation code:"] = "Je moet deze uitnodigingscode opgeven:";
+App::$strings["1. Register at any \$Projectname location (they are all inter-connected)"] = "1. Registreer je op een willekeurige \$Projectname-hub (ze zijn allemaal onderling met elkaar verbonden):";
+App::$strings["2. Enter my \$Projectname network address into the site searchbar."] = "2. Nadat je bent ingelogd en een kanaal hebt aangemaakt kan je mijn \$Projectname-kanaaladres in het zoekveld invullen:";
+App::$strings["or visit"] = "of bezoek";
+App::$strings["3. Click [Connect]"] = "3. Klik op [+ Verbinden]";
+App::$strings["About this site"] = "Over deze hub";
+App::$strings["Site Name"] = "Hubnaam";
+App::$strings["Administrator"] = "Beheerder";
+App::$strings["Software and Project information"] = "Software- en projectinformatie";
+App::$strings["This site is powered by \$Projectname"] = "Dit is een \$Projectname-hub";
+App::$strings["Federated and decentralised networking and identity services provided by Zot"] = "Federatieve en gedecentraliseerde netwerk- en identiteitsdiensten, mogelijk gemaakt door Zot";
+App::$strings["Version %s"] = "Versie %s";
+App::$strings["Project homepage"] = "Projectwebsite";
+App::$strings["Developer homepage"] = "Ontwikkelaarswebsite";
App::$strings["Create Channel"] = "Kanaal aanmaken";
App::$strings["A channel is your identity on this network. It can represent a person, a blog, or a forum to name a few. Channels can make connections with other channels to share information with highly detailed permissions."] = "Een kanaal is jouw identiteit in dit netwerk. Het kan bijvoorbeeld een persoon, een blog of een forum vertegenwoordigen. Door met elkaar te verbinden kunnen kanalen, met behulp van uitgebreide permissies, informatie uitwisselen.";
App::$strings["or <a href=\"import\">import an existing channel</a> from another location."] = "Of <a href=\"import\">importeer een bestaand kanaal</a> vanaf een andere locatie";
+App::$strings["Import Webpage Elements"] = "Webpagina-elementen importeren";
+App::$strings["Import selected"] = "Importbestand geselecteerd";
+App::$strings["Export Webpage Elements"] = "Webpagina-elementen exporteren";
+App::$strings["Export selected"] = "Selectie exporteren";
+App::$strings["Webpages"] = "Webpagina's";
+App::$strings["Actions"] = "Acties";
+App::$strings["Page Link"] = "Paginalink";
+App::$strings["Page Title"] = "Paginatitel";
+App::$strings["Invalid file type."] = "Ongeldig bestandsformaat";
+App::$strings["Error opening zip file"] = "Fout tijdens openen zipbestand";
+App::$strings["Invalid folder path."] = "Ongeldige maplocatie";
+App::$strings["No webpage elements detected."] = "Geen webpagina-elementen gedecteerd";
+App::$strings["Import complete."] = "Importeren voltooid.";
App::$strings["Mark all system notifications seen"] = "Markeer alle systeemnotificaties als bekeken";
App::$strings["Poke"] = "Aanstoten";
App::$strings["Poke somebody"] = "Iemand aanstoten";
@@ -968,79 +976,29 @@ App::$strings["Poke, prod or do other things to somebody"] = "Iemand bijvoorbeel
App::$strings["Recipient"] = "Ontvanger";
App::$strings["Choose what you wish to do to recipient"] = "Kies wat je met de ontvanger wil doen";
App::$strings["Make this post private"] = "Maak dit bericht privé";
-App::$strings["Profile not found."] = "Profiel niet gevonden.";
-App::$strings["Profile deleted."] = "Profiel verwijderd.";
-App::$strings["Profile-"] = "Profiel-";
-App::$strings["New profile created."] = "Nieuw profiel aangemaakt.";
-App::$strings["Profile unavailable to clone."] = "Profiel niet beschikbaar om te klonen";
-App::$strings["Profile unavailable to export."] = "Geen profiel beschikbaar om te exporteren";
-App::$strings["Profile Name is required."] = "Profielnaam is vereist";
-App::$strings["Marital Status"] = "Huwelijke status";
-App::$strings["Romantic Partner"] = "Romantische partner";
-App::$strings["Likes"] = "Houdt van";
-App::$strings["Dislikes"] = "Houdt niet van";
-App::$strings["Work/Employment"] = "Werk/arbeid";
-App::$strings["Religion"] = "Religie";
-App::$strings["Political Views"] = "Politieke overtuigingen";
-App::$strings["Gender"] = "Geslacht";
-App::$strings["Sexual Preference"] = "Seksuele voorkeur";
-App::$strings["Homepage"] = "Homepage";
-App::$strings["Interests"] = "Interesses";
-App::$strings["Profile updated."] = "Profiel bijgewerkt";
-App::$strings["Hide your connections list from viewers of this profile"] = "Laat de lijst met connecties niet aan bezoekers van dit profiel zien.";
-App::$strings["Edit Profile Details"] = "Profiel bewerken";
-App::$strings["View this profile"] = "Profiel weergeven";
-App::$strings["Edit visibility"] = "Zichtbaarheid bewerken";
-App::$strings["Profile Tools"] = "Hulpmiddelen";
-App::$strings["Change cover photo"] = "Omslagfoto wijzigen";
-App::$strings["Change profile photo"] = "Profielfoto veranderen";
-App::$strings["Create a new profile using these settings"] = "Een nieuw profiel aanmaken met dit profiel als basis";
-App::$strings["Clone this profile"] = "Dit profiel klonen";
-App::$strings["Delete this profile"] = "Dit profiel verwijderen";
-App::$strings["Add profile things"] = "Dingen aan je profiel toevoegen";
-App::$strings["Personal"] = "Persoonlijk";
-App::$strings["Relation"] = "Relatie";
-App::$strings["Miscellaneous"] = "Diversen";
-App::$strings["Import profile from file"] = "Profiel vanuit bestand importeren";
-App::$strings["Export profile to file"] = "Profiel naar bestand exporteren";
-App::$strings["Your gender"] = "Jouw geslacht";
-App::$strings["Marital status"] = "Burgerlijke staat";
-App::$strings["Sexual preference"] = "Seksuele voorkeur";
-App::$strings["Profile name"] = "Profielnaam";
-App::$strings["This is your default profile."] = "Dit is jouw standaardprofiel";
-App::$strings["Your full name"] = "Jouw volledige naam";
-App::$strings["Title/Description"] = "Titel/omschrijving";
-App::$strings["Street address"] = "Straat en huisnummer";
-App::$strings["Locality/City"] = "Woonplaats";
-App::$strings["Region/State"] = "Provincie/gewest/deelstaat";
-App::$strings["Postal/Zip code"] = "Postcode";
-App::$strings["Country"] = "Land";
-App::$strings["Who (if applicable)"] = "Wie (wanneer van toepassing)";
-App::$strings["Examples: cathy123, Cathy Williams, cathy@example.com"] = "Voorbeelden: petra123, Petra Jansen, petra@voorbeeld.nl";
-App::$strings["Since (date)"] = "Sinds (datum)";
-App::$strings["Tell us about yourself"] = "Vertel ons iets over jezelf";
-App::$strings["Homepage URL"] = "URL homepagina";
-App::$strings["Hometown"] = "Oorspronkelijk uit";
-App::$strings["Political views"] = "Politieke overtuigingen";
-App::$strings["Religious views"] = "Religieuze overtuigingen";
-App::$strings["Keywords used in directory listings"] = "Trefwoorden voor in de kanalengids";
-App::$strings["Example: fishing photography software"] = "Voorbeeld: muziek, fotografie, software";
-App::$strings["Musical interests"] = "Muzikale interesses";
-App::$strings["Books, literature"] = "Boeken/literatuur";
-App::$strings["Television"] = "Televisie";
-App::$strings["Film/Dance/Culture/Entertainment"] = "Film/dans/cultuur/entertainment";
-App::$strings["Hobbies/Interests"] = "Hobby's/interesses";
-App::$strings["Love/Romance"] = "Liefde/romantiek";
-App::$strings["School/Education"] = "School/opleiding";
-App::$strings["Contact information and social networks"] = "Contactinformatie en sociale netwerken";
-App::$strings["My other channels"] = "Mijn andere kanalen";
-App::$strings["Profile Image"] = "Profielfoto";
-App::$strings["Edit Profiles"] = "Bewerk profielen";
-App::$strings["Unable to find your hub."] = "Niet in staat om je hub te vinden";
-App::$strings["Post successful."] = "Verzenden bericht geslaagd.";
+App::$strings["Invalid profile identifier."] = "Ongeldige profiel-identificator";
+App::$strings["Profile Visibility Editor"] = "Zichtbaarheid profiel ";
+App::$strings["Profile"] = "Profiel";
+App::$strings["Click on a contact to add or remove."] = "Klik op een connectie om deze toe te voegen of te verwijderen";
+App::$strings["Visible To"] = "Zichtbaar voor";
+App::$strings["Posts and comments"] = "Berichten en reacties";
+App::$strings["Only posts"] = "Alleen berichten";
+App::$strings["Unable to locate original post."] = "Niet in staat om de originele locatie van het bericht te vinden. ";
+App::$strings["Empty post discarded."] = "Leeg bericht geannuleerd";
+App::$strings["Executable content type not permitted to this channel."] = "Uitvoerbare bestanden zijn niet toegestaan op dit kanaal.";
+App::$strings["Duplicate post suppressed."] = "Dubbel bericht tegengehouden.";
+App::$strings["System error. Post not saved."] = "Systeemfout. Bericht niet opgeslagen.";
+App::$strings["Unable to obtain post information from database."] = "Niet in staat om informatie over dit bericht uit de database te verkrijgen.";
+App::$strings["You have reached your limit of %1$.0f top level posts."] = "Je hebt jouw limiet van %1$.0f berichten bereikt.";
+App::$strings["You have reached your limit of %1$.0f webpages."] = "Je hebt jouw limiet van %1$.0f webpagina's bereikt.";
App::$strings["This setting requires special processing and editing has been blocked."] = "Deze instelling vereist een speciaal proces en bewerken is geblokkeerd.";
App::$strings["Configuration Editor"] = "Configuratiebewerker";
App::$strings["Warning: Changing some settings could render your channel inoperable. Please leave this page unless you are comfortable with and knowledgeable about how to correctly use this feature."] = "Waarschuwing: het veranderen van sommige instellingen kunnen jouw kanaal onklaar maken. Verlaat deze pagina, tenzij je weet waar je mee bezig bent en voldoende kennis bezit over hoe je deze functies moet gebruiken. ";
+App::$strings["Items tagged with: %s"] = "Items getagd met %s";
+App::$strings["Search results for: %s"] = "Zoekresultaten voor %s";
+App::$strings["Remote privacy information not available."] = "Privacy-informatie op afstand niet beschikbaar.";
+App::$strings["Visible to:"] = "Zichtbaar voor:";
+App::$strings["__ctx:acl__ Profile"] = "Profiel";
App::$strings["Blocks"] = "Blokken";
App::$strings["Block Title"] = "Bloktitel";
App::$strings["Layouts"] = "Lay-outs";
@@ -1052,6 +1010,10 @@ App::$strings["Website:"] = "Website:";
App::$strings["Remote Channel [%s] (not yet known on this site)"] = "Kanaal op afstand [%s] (nog niet op deze hub bekend)";
App::$strings["Rating (this information is public)"] = "Beoordeling (deze informatie is openbaar)";
App::$strings["Optionally explain your rating (this information is public)"] = "Verklaar jouw beoordeling (niet verplicht, deze informatie is openbaar)";
+App::$strings["Shift-reload the page or clear browser cache if the new photo does not display immediately."] = "Vernieuw de pagina met shift+R of shift+F5, of leeg je browserbuffer, wanneer de nieuwe foto niet meteen wordt weergegeven.";
+App::$strings["Use Photo for Profile"] = "Als profielfoto gebruiken";
+App::$strings["Upload Profile Photo"] = "Profielfoto uploaden";
+App::$strings["Use"] = "Gebruiken";
App::$strings["Like/Dislike"] = "Leuk/niet leuk";
App::$strings["This action is restricted to members."] = "Deze actie kan alleen door \$Projectname-leden worden uitgevoerd.";
App::$strings["Please <a href=\"rmagic\">login with your \$Projectname ID</a> or <a href=\"register\">register as a new \$Projectname member</a> to continue."] = "Je dient <a href=\"rmagic\">in te loggen met je \$Projectname-account</a> of <a href=\"register\">een nieuw \$Projectname-account aan te maken</a> om verder te kunnen gaan.";
@@ -1062,7 +1024,6 @@ App::$strings["Channel unavailable."] = "Kanaal niet beschikbaar.";
App::$strings["Previous action reversed."] = "Vorige actie omgedraaid";
App::$strings["photo"] = "foto";
App::$strings["status"] = "bericht";
-App::$strings["event"] = "gebeurtenis";
App::$strings["%1\$s likes %2\$s's %3\$s"] = "%1\$s vindt %3\$s van %2\$s leuk";
App::$strings["%1\$s doesn't like %2\$s's %3\$s"] = "%1\$s vindt %3\$s van %2\$s niet leuk";
App::$strings["%1\$s agrees with %2\$s's %3\$s"] = "%1\$s is het eens met %2\$s's %3\$s";
@@ -1073,33 +1034,14 @@ App::$strings["%1\$s is not attending %2\$s's %3\$s"] = "%1\$s is niet aanwezig
App::$strings["%1\$s may attend %2\$s's %3\$s"] = "%1\$s is mogelijk aanwezig op %2\$s's %3\$s";
App::$strings["Action completed."] = "Actie voltooid";
App::$strings["Thank you."] = "Bedankt";
-App::$strings["Shift-reload the page or clear browser cache if the new photo does not display immediately."] = "Vernieuw de pagina met shift+R of shift+F5, of leeg je browserbuffer, wanneer de nieuwe foto niet meteen wordt weergegeven.";
-App::$strings["Use Photo for Profile"] = "Als profielfoto gebruiken";
-App::$strings["Upload Profile Photo"] = "Profielfoto uploaden";
-App::$strings["Use"] = "Gebruiken";
-App::$strings["Items tagged with: %s"] = "Items getagd met %s";
-App::$strings["Search results for: %s"] = "Zoekresultaten voor %s";
App::$strings["No channel."] = "Geen kanaal.";
App::$strings["Common connections"] = "Veel voorkomende connecties";
App::$strings["No connections in common."] = "Geen gemeenschappelijke connecties.";
-App::$strings["Authorize application connection"] = "Geef toestemming voor applicatiekoppeling";
-App::$strings["Return to your app and insert this Security Code:"] = "Ga terug naar je app en voeg deze beveiligingscode in:";
-App::$strings["Please login to continue."] = "Inloggen om verder te kunnen gaan.";
-App::$strings["Do you want to authorize this application to access your posts and contacts, and/or create new posts for you?"] = "Wil je deze applicatie toestemming geven om jouw berichten en connecties te zien, en/of nieuwe berichten voor jou te plaatsen?";
-App::$strings["sent you a private message"] = "stuurde jou een privébericht";
-App::$strings["added your channel"] = "voegde jouw kanaal toe";
-App::$strings["g A l F d"] = "G:i, l d F";
-App::$strings["[today]"] = "[vandaag]";
-App::$strings["posted an event"] = "plaatste een gebeurtenis";
-App::$strings["About this site"] = "Over deze hub";
-App::$strings["Site Name"] = "Hubnaam";
-App::$strings["Administrator"] = "Beheerder";
-App::$strings["Software and Project information"] = "Software- en projectinformatie";
-App::$strings["This site is powered by \$Projectname"] = "Dit is een \$Projectname-hub";
-App::$strings["Federated and decentralised networking and identity services provided by Zot"] = "Federatieve en gedecentraliseerde netwerk- en identiteitsdiensten, mogelijk gemaakt door Zot";
-App::$strings["Version %s"] = "Versie %s";
-App::$strings["Project homepage"] = "Projectwebsite";
-App::$strings["Developer homepage"] = "Ontwikkelaarswebsite";
+App::$strings["toggle full screen mode"] = "Volledig scherm";
+App::$strings["%1\$s is following %2\$s's %3\$s"] = "%1\$s volgt het %3\$s van %2\$s";
+App::$strings["%1\$s stopped following %2\$s's %3\$s"] = "%1\$s volgt het %3\$s van %2\$s niet meer";
+App::$strings["You must be logged in to see this page."] = "Je moet zijn ingelogd om deze pagina te kunnen bekijken.";
+App::$strings["Insufficient permissions. Request redirected to profile page."] = "Onvoldoende permissies. Doorgestuurd naar profielpagina.";
App::$strings["No valid account found."] = "Geen geldige account gevonden.";
App::$strings["Password reset request issued. Check your email."] = "Het verzoek om je wachtwoord opnieuw in te stellen is behandeld. Controleer je e-mail.";
App::$strings["Site Member (%s)"] = "Lid van hub (%s)";
@@ -1120,11 +1062,10 @@ App::$strings["Select a bookmark folder"] = "Kies een bladwijzermap";
App::$strings["Save Bookmark"] = "Bladwijzer opslaan";
App::$strings["URL of bookmark"] = "URL van bladwijzer";
App::$strings["Or enter new bookmark folder name"] = "Of geef de naam op van een nieuwe bladwijzermap";
-App::$strings["This directory server requires an access token"] = "Deze kanalengidshub (directoryserver) heeft een toegangs-token nodig";
-App::$strings["Authentication failed."] = "Authenticatie mislukt.";
-App::$strings["Remote Authentication"] = "Authenticatie op afstand";
-App::$strings["Enter your channel address (e.g. channel@example.com)"] = "Vul jouw kanaaladres in (bijv. channel@example.com)";
-App::$strings["Authenticate"] = "Authenticeren";
+App::$strings["Channel added."] = "Kanaal toegevoegd.";
+App::$strings["__ctx:mood__ %1\$s is %2\$s"] = "%1\$s is %2\$s";
+App::$strings["Mood"] = "Stemming";
+App::$strings["Set your current mood and tell your friends"] = "Noteer je huidige stemming en toon het aan je connecties";
App::$strings["Please login."] = "Inloggen.";
App::$strings["Account removals are not allowed within 48 hours of changing the account password."] = "Het verwijderen van een account is niet toegestaan binnen 48 uur nadat het wachtwoord is veranderd.";
App::$strings["Remove This Account"] = "Verwijder dit account";
@@ -1141,56 +1082,42 @@ App::$strings["Edit System Page Description"] = "Systeempagina's bewerken";
App::$strings["Layout not found."] = "Lay-out niet gevonden.";
App::$strings["Module Name:"] = "Modulenaam:";
App::$strings["Layout Help"] = "Lay-out-hulp";
-App::$strings["Export Channel"] = "Kanaal exporteren";
-App::$strings["Export your basic channel information to a file. This acts as a backup of your connections, permissions, profile and basic data, which can be used to import your data to a new server hub, but does not contain your content."] = "Exporteer de basisinformatie van jouw kanaal naar een bestand. Dit fungeert als een back-up van jouw connecties, permissies, profiel en basisgegevens, die gebruikt kan worden om op een nieuwe hub jouw gegevens te importeren. Deze back-up bevat echter niet de inhoud van jouw kanaal.";
-App::$strings["Export Content"] = "Inhoud exporteren";
-App::$strings["Export your channel information and recent content to a JSON backup that can be restored or imported to another server hub. This backs up all of your connections, permissions, profile data and several months of posts. This file may be VERY large. Please be patient - it may take several minutes for this download to begin."] = "Exporteer informatie en recente inhoud van jouw kanaal naar een JSON-back-up, wat kan worden gebruikt om jouw kanaal te herstellen of te importeren op een andere hub. Dit slaat al jouw connecties, permissies, profielgegevens en enkele maanden aan inhoud van jouw kanaal op. Dit bestand kan ZEER groot worden. Wees geduldig - het kan enkele minuten duren voordat de download begint.";
-App::$strings["Export your posts from a given year."] = "Exporteer jouw berichten uit een bepaald jaar.";
-App::$strings["You may also export your posts and conversations for a particular year or month. Adjust the date in your browser location bar to select other dates. If the export fails (possibly due to memory exhaustion on your server hub), please try again selecting a more limited date range."] = "Je kan ook berichten en conversaties uit een bepaald jaar of van een bepaalde maand exporteren. Verander de datum in de adresbalk van jouw webbrowser om andere jaren en maanden te selecteren. Wanneer het exporteren mislukt (waarschijnlijk door een gebrek aan beschikbaar servergeheugen), probeer het dan nogmaals met een beperkter tijdvak.";
-App::$strings["To select all posts for a given year, such as this year, visit <a href=\"%1\$s\">%2\$s</a>"] = "Bezoek <a href=\"%1\$s\">%2\$s</a> om alle berichten van bijvoorbeeld dit jaar te selecteren. ";
-App::$strings["To select all posts for a given month, such as January of this year, visit <a href=\"%1\$s\">%2\$s</a>"] = "Bezoek <a href=\"%1\$s\">%2\$s</a> om alle berichten van bijvoorbeeld januari dit jaar te selecteren.";
-App::$strings["These content files may be imported or restored by visiting <a href=\"%1\$s\">%2\$s</a> on any site containing your channel. For best results please import or restore these in date order (oldest first)."] = "Deze back-up-bestanden kunnen geïmporteerd of hersteld worden door op jouw hub en met jouw kanaal <a href=\"%1\$s\">%2\$s</a> te bezoeken. Voor het beste resultaat kan je de bestanden in chronologische volgorde importeren of herstellen.";
-App::$strings["Permissions denied."] = "Permissies niet toegestaan";
-App::$strings["l, F j"] = "l j F";
-App::$strings["Link to Source"] = "Originele locatie";
-App::$strings["Edit Event"] = "Gebeurtenis bewerken";
-App::$strings["Create Event"] = "Gebeurtenis aanmaken";
-App::$strings["Export"] = "Exporteren";
-App::$strings["Import"] = "Importeren";
-App::$strings["Today"] = "Vandaag";
-App::$strings["# Accounts"] = "# accounts";
-App::$strings["# blocked accounts"] = "# geblokkeerde accounts";
-App::$strings["# expired accounts"] = "# verlopen accounts";
-App::$strings["# expiring accounts"] = "# accounts die nog moeten verlopen";
-App::$strings["# Channels"] = "# Kanalen";
-App::$strings["# primary"] = "# primair";
-App::$strings["# clones"] = "# klonen";
-App::$strings["Message queues"] = "Berichtenwachtrij";
-App::$strings["Your software should be updated"] = "Jouw software moet worden bijgewerkt ";
-App::$strings["Summary"] = "Samenvatting";
-App::$strings["Registered accounts"] = "Geregistreerde accounts";
-App::$strings["Pending registrations"] = "Accounts die op goedkeuring wachten";
-App::$strings["Registered channels"] = "Geregistreerde kanalen";
-App::$strings["Active plugins"] = "Ingeschakelde plugins";
-App::$strings["Version"] = "Versie";
-App::$strings["Repository version (master)"] = "Versie repository (master)";
-App::$strings["Repository version (dev)"] = "Versie repository (dev)";
-App::$strings["Remote privacy information not available."] = "Privacy-informatie op afstand niet beschikbaar.";
-App::$strings["Visible to:"] = "Zichtbaar voor:";
+App::$strings["%d rating"] = array(
+ 0 => "%d beoordeling",
+ 1 => "%d beoordelingen",
+);
+App::$strings["Gender: "] = "Geslacht:";
+App::$strings["Status: "] = "Status: ";
+App::$strings["Homepage: "] = "Homepage: ";
+App::$strings["Age:"] = "Leeftijd:";
+App::$strings["Location:"] = "Plaats:";
+App::$strings["Description:"] = "Omschrijving:";
+App::$strings["Hometown:"] = "Oorspronkelijk uit:";
+App::$strings["About:"] = "Over:";
+App::$strings["Connect"] = "Verbinden";
+App::$strings["Public Forum:"] = "Openbaar forum:";
+App::$strings["Keywords: "] = "Trefwoorden: ";
+App::$strings["Don't suggest"] = "Niet voorstellen";
+App::$strings["Common connections:"] = "Gemeenschappelijke connecties:";
+App::$strings["Global Directory"] = "Volledige kanalengids";
+App::$strings["Local Directory"] = "Lokale kanalengids";
+App::$strings["Finding:"] = "Gezocht naar:";
+App::$strings["Channel Suggestions"] = "Voorgestelde kanalen";
+App::$strings["next page"] = "volgende pagina";
+App::$strings["previous page"] = "vorige pagina";
+App::$strings["Sort options"] = "Sorteeropties";
+App::$strings["Alphabetic"] = "Alfabetisch";
+App::$strings["Reverse Alphabetic"] = "Omgekeerd alfabetisch";
+App::$strings["Newest to Oldest"] = "Nieuw naar oud";
+App::$strings["Oldest to Newest"] = "Oud naar nieuw";
+App::$strings["No entries (some entries may be hidden)."] = "Niets gevonden (sommige kanalen kunnen verborgen zijn).";
+App::$strings["vcard"] = "vcard";
+App::$strings["Unable to find your hub."] = "Niet in staat om je hub te vinden";
+App::$strings["Post successful."] = "Verzenden bericht geslaagd.";
+App::$strings["Source of Item"] = "Bron van item";
App::$strings["No service class restrictions found."] = "Geen abonnementsbeperkingen gevonden.";
-App::$strings["Import Webpage Elements"] = "Webpagina-elementen importeren";
-App::$strings["Import selected"] = "Importbestand geselecteerd";
-App::$strings["Export Webpage Elements"] = "Webpagina-elementen exporteren";
-App::$strings["Export selected"] = "Selectie exporteren";
-App::$strings["Webpages"] = "Webpagina's";
-App::$strings["Actions"] = "Acties";
-App::$strings["Page Link"] = "Paginalink";
-App::$strings["Page Title"] = "Paginatitel";
-App::$strings["Invalid file type."] = "Ongeldig bestandsformaat";
-App::$strings["Error opening zip file"] = "Fout tijdens openen zipbestand";
-App::$strings["Invalid folder path."] = "Ongeldige maplocatie";
-App::$strings["No webpage elements detected."] = "Geen webpagina-elementen gedecteerd";
-App::$strings["Import complete."] = "Importeren voltooid.";
+App::$strings["network"] = "netwerk";
+App::$strings["RSS"] = "RSS";
App::$strings["Channel removals are not allowed within 48 hours of changing the account password."] = "Het verwijderen van een kanaal is niet toegestaan binnen 48 uur nadat het wachtwoord van het account is veranderd.";
App::$strings["Remove This Channel"] = "Verwijder dit kanaal";
App::$strings["This channel will be completely removed from the network. "] = "Dit kanaal wordt volledig uit het \$Projectname-netwerk verwijderd.";
@@ -1201,36 +1128,9 @@ App::$strings["Files: shared with me"] = "Bestanden: met mij gedeeld";
App::$strings["NEW"] = "NIEUW";
App::$strings["Remove all files"] = "Verwijder alle bestanden";
App::$strings["Remove this file"] = "Verwijder dit bestand";
-App::$strings["Not found"] = "Niet gevonden";
-App::$strings["Invalid channel"] = "Onbekend kanaal";
-App::$strings["Error retrieving wiki"] = "Fout tijdens ophalen wiki";
-App::$strings["Error creating zip file export folder"] = "Fout tijdens aanmaken exportmap zipbestand";
-App::$strings["Error downloading wiki: "] = "Fout tijdens downloaden wiki: ";
-App::$strings["Wikis"] = "Wiki's";
-App::$strings["Download"] = "Download";
-App::$strings["Wiki name"] = "Naam wiki";
-App::$strings["Content type"] = "Opmaaktype";
-App::$strings["Create a status post for this wiki"] = "Plaats een bericht over deze wiki";
-App::$strings["Wiki not found"] = "Wiki is niet gevonden";
-App::$strings["Rename page"] = "Pagina hernoemen";
-App::$strings["Error retrieving page content"] = "Fout tijdens ophalen inhoud pagina";
-App::$strings["Revision Comparison"] = "Revisies vergelijken";
-App::$strings["Revert"] = "Ongedaan maken";
-App::$strings["Source"] = "Bron";
-App::$strings["New page name"] = "Nieuwe paginanaam";
-App::$strings["Embed image from photo albums"] = "Afbeelding uit een fotoalbum invoegen";
-App::$strings["Embed an image from your albums"] = "Afbeelding uit jouw albums invoegen";
-App::$strings["OK"] = "OK";
-App::$strings["Choose images to embed"] = "Kies afbeeldingen om in te voegen";
-App::$strings["Choose an album"] = "Kies een album";
-App::$strings["Choose a different album"] = "Kies een ander album";
-App::$strings["Error getting album list"] = "Fout tijdens ophalen albumlijst";
-App::$strings["Error getting photo link"] = "Fout tijdens ophalen fotolink";
-App::$strings["Error getting album"] = "Fout tijdens ophalen album";
-App::$strings["Error creating wiki. Invalid name."] = "Fout tijdens aanmaken wiki. Ongeldige naam.";
-App::$strings["Wiki created, but error creating Home page."] = "Wiki aangemaakt, maar fout tijdens aanmaken homepagina.";
-App::$strings["Error creating wiki"] = "Fout tijdens aanmaken wiki.";
-App::$strings["New page created"] = "Nieuwe pagina aangemaakt";
+App::$strings["post"] = "bericht";
+App::$strings["comment"] = "reactie";
+App::$strings["%1\$s tagged %2\$s's %3\$s with %4\$s"] = "%1\$s heeft het %3\$s van %2\$s getagd met %4\$s";
App::$strings["Failed to create source. No channel selected."] = "Aanmaken bron mislukt. Geen kanaal geselecteerd.";
App::$strings["Source created."] = "Bron aangemaakt.";
App::$strings["Source updated."] = "Bron aangemaakt.";
@@ -1243,19 +1143,82 @@ App::$strings["Only import content with these words (one per line)"] = "Importee
App::$strings["Leave blank to import all public content"] = "Laat leeg om alle openbare inhoud te importeren";
App::$strings["Channel Name"] = "Kanaalnaam";
App::$strings["Add the following categories to posts imported from this source (comma separated)"] = "De volgende categorieën aan berichten toevoegen die uit deze bron zijn geïmporteerd (door komma's gescheiden)";
-App::$strings["Optional"] = "Optioneel";
+App::$strings["Optional"] = "Niet verplicht";
App::$strings["Source not found."] = "Bron niet gevonden";
App::$strings["Edit Source"] = "Bron bewerken";
App::$strings["Delete Source"] = "Bron verwijderen";
App::$strings["Source removed"] = "Bron verwijderd";
App::$strings["Unable to remove source."] = "Verwijderen bron mislukt.";
-App::$strings["%1\$s is following %2\$s's %3\$s"] = "%1\$s volgt het %3\$s van %2\$s";
-App::$strings["%1\$s stopped following %2\$s's %3\$s"] = "%1\$s volgt het %3\$s van %2\$s niet meer";
App::$strings["No suggestions available. If this is a new site, please try again in 24 hours."] = "Geen voorgestelde kanalen gevonden. Wanneer dit een nieuwe hub is, probeer het dan over 24 uur weer.";
App::$strings["Ignore/Hide"] = "Negeren/Verbergen";
-App::$strings["post"] = "bericht";
-App::$strings["comment"] = "reactie";
-App::$strings["%1\$s tagged %2\$s's %3\$s with %4\$s"] = "%1\$s heeft het %3\$s van %2\$s getagd met %4\$s";
+App::$strings["Profile not found."] = "Profiel niet gevonden.";
+App::$strings["Profile deleted."] = "Profiel verwijderd.";
+App::$strings["Profile-"] = "Profiel-";
+App::$strings["New profile created."] = "Nieuw profiel aangemaakt.";
+App::$strings["Profile unavailable to clone."] = "Profiel niet beschikbaar om te klonen";
+App::$strings["Profile unavailable to export."] = "Geen profiel beschikbaar om te exporteren";
+App::$strings["Profile Name is required."] = "Profielnaam is vereist";
+App::$strings["Marital Status"] = "Huwelijke status";
+App::$strings["Romantic Partner"] = "Romantische partner";
+App::$strings["Likes"] = "Houdt van";
+App::$strings["Dislikes"] = "Houdt niet van";
+App::$strings["Work/Employment"] = "Werk/arbeid";
+App::$strings["Religion"] = "Religie";
+App::$strings["Political Views"] = "Politieke overtuigingen";
+App::$strings["Gender"] = "Geslacht";
+App::$strings["Sexual Preference"] = "Seksuele voorkeur";
+App::$strings["Homepage"] = "Homepage";
+App::$strings["Interests"] = "Interesses";
+App::$strings["Profile updated."] = "Profiel bijgewerkt";
+App::$strings["Hide your connections list from viewers of this profile"] = "Laat de lijst met connecties niet aan bezoekers van dit profiel zien.";
+App::$strings["Edit Profile Details"] = "Profiel bewerken";
+App::$strings["View this profile"] = "Profiel weergeven";
+App::$strings["Edit visibility"] = "Zichtbaarheid bewerken";
+App::$strings["Profile Tools"] = "Hulpmiddelen";
+App::$strings["Change cover photo"] = "Omslagfoto wijzigen";
+App::$strings["Change profile photo"] = "Profielfoto veranderen";
+App::$strings["Create a new profile using these settings"] = "Een nieuw profiel aanmaken met dit profiel als basis";
+App::$strings["Clone this profile"] = "Dit profiel klonen";
+App::$strings["Delete this profile"] = "Dit profiel verwijderen";
+App::$strings["Add profile things"] = "Dingen aan je profiel toevoegen";
+App::$strings["Personal"] = "Persoonlijk";
+App::$strings["Relation"] = "Relatie";
+App::$strings["Miscellaneous"] = "Diversen";
+App::$strings["Import profile from file"] = "Profiel vanuit bestand importeren";
+App::$strings["Export profile to file"] = "Profiel naar bestand exporteren";
+App::$strings["Your gender"] = "Jouw geslacht";
+App::$strings["Marital status"] = "Burgerlijke staat";
+App::$strings["Sexual preference"] = "Seksuele voorkeur";
+App::$strings["Profile name"] = "Profielnaam";
+App::$strings["This is your default profile."] = "Dit is jouw standaardprofiel";
+App::$strings["Your full name"] = "Jouw volledige naam";
+App::$strings["Title/Description"] = "Titel/omschrijving";
+App::$strings["Street address"] = "Straat en huisnummer";
+App::$strings["Locality/City"] = "Woonplaats";
+App::$strings["Region/State"] = "Provincie/gewest/deelstaat";
+App::$strings["Postal/Zip code"] = "Postcode";
+App::$strings["Who (if applicable)"] = "Wie (wanneer van toepassing)";
+App::$strings["Examples: cathy123, Cathy Williams, cathy@example.com"] = "Voorbeelden: petra123, Petra Jansen, petra@voorbeeld.nl";
+App::$strings["Since (date)"] = "Sinds (datum)";
+App::$strings["Tell us about yourself"] = "Vertel ons iets over jezelf";
+App::$strings["Homepage URL"] = "URL homepagina";
+App::$strings["Hometown"] = "Oorspronkelijk uit";
+App::$strings["Political views"] = "Politieke overtuigingen";
+App::$strings["Religious views"] = "Religieuze overtuigingen";
+App::$strings["Keywords used in directory listings"] = "Trefwoorden voor in de kanalengids";
+App::$strings["Example: fishing photography software"] = "Voorbeeld: muziek, fotografie, software";
+App::$strings["Musical interests"] = "Muzikale interesses";
+App::$strings["Books, literature"] = "Boeken/literatuur";
+App::$strings["Television"] = "Televisie";
+App::$strings["Film/Dance/Culture/Entertainment"] = "Film/dans/cultuur/entertainment";
+App::$strings["Hobbies/Interests"] = "Hobby's/interesses";
+App::$strings["Love/Romance"] = "Liefde/romantiek";
+App::$strings["School/Education"] = "School/opleiding";
+App::$strings["Contact information and social networks"] = "Contactinformatie en sociale netwerken";
+App::$strings["My other channels"] = "Mijn andere kanalen";
+App::$strings["Communications"] = "Communicatie";
+App::$strings["Profile Image"] = "Profielfoto";
+App::$strings["Edit Profiles"] = "Bewerk profielen";
App::$strings["Additional Features"] = "Extra functies";
App::$strings["Name is required"] = "Naam is vereist";
App::$strings["Key and Secret are required"] = "Key en secret zijn vereist";
@@ -1272,15 +1235,6 @@ App::$strings["Connected Apps"] = "Verbonden applicaties";
App::$strings["Client key starts with"] = "Client key begint met";
App::$strings["No name"] = "Geen naam";
App::$strings["Remove authorization"] = "Autorisatie verwijderen";
-App::$strings["This channel is limited to %d tokens"] = "Dit kanaal heeft een limiet van %d tokens";
-App::$strings["Name and Password are required."] = "Naam en wachtwoord zijn vereist";
-App::$strings["Token saved."] = "Token opgeslagen.";
-App::$strings["Use this form to create temporary access identifiers to share things with non-members. These identities may be used in Access Control Lists and visitors may login using these credentials to access private content."] = "Gebruik dit formulier om tijdelijke identiteiten aan te maken, waarmee je bepaalde informatie met niet-leden kan delen. Deze identiteiten kunnen onder Permissies (handmatige selectie) worden gebruikt. Gasten kunnen inloggen met onderstaande gegevens om zo toegang te krijgen tot privéinhoud.";
-App::$strings["You may also provide <em>dropbox</em> style access links to friends and associates by adding the Login Password to any specific site URL as shown. Examples:"] = "Je kan ook <em>dropbox</em>-achtige links aan mensen geven door bovenstaand wachtwoord op onderstaande manier aan een hub-URL toe te voegen. Voorbeelden:";
-App::$strings["Guest Access Tokens"] = "Gasttoegang";
-App::$strings["Login Name"] = "Inlognaam";
-App::$strings["Login Password"] = "Wachtwoord:";
-App::$strings["Expires (yyyy-mm-dd)"] = "Geldig t/m (yyyy-mm-dd)";
App::$strings["Not valid email."] = "Geen geldig e-mailadres.";
App::$strings["Protected email address. Cannot change to that email."] = "Beschermd e-mailadres. Kan dat e-mailadres niet gebruiken.";
App::$strings["System failure storing new email. Please try again."] = "Systeemfout opslaan van nieuwe e-mail. Probeer het nog een keer.";
@@ -1343,6 +1297,7 @@ App::$strings["May reduce spam activity"] = "Kan eventuele spam verminderen";
App::$strings["Default Access Control List (ACL)"] = "Standaard permissies voor nieuwe berichten";
App::$strings["Use my default audience setting for the type of object published"] = "Gebruik mijn standaard privacy-instelling voor dit type publicatie";
App::$strings["Channel permissions category:"] = "Kanaaltype en -permissies:";
+App::$strings["Default Permissions Group"] = "Standaard permissiegroep";
App::$strings["Maximum private messages per day from unknown people:"] = "Maximum aantal privé-berichten per dag van onbekende personen:";
App::$strings["Useful to reduce spamming"] = "Kan eventuele spam verminderen";
App::$strings["Notification Settings"] = "Notificatie-instellingen";
@@ -1387,6 +1342,25 @@ App::$strings["Personal menu to display in your channel pages"] = "Persoonlijk m
App::$strings["Remove this channel."] = "Verwijder dit kanaal.";
App::$strings["Firefox Share \$Projectname provider"] = "\$Projectname-service voor Firefox Share";
App::$strings["Start calendar week on monday"] = "Begin in de agenda de week op maandag";
+App::$strings["Affinity Slider settings updated."] = "Affiniteitsinstellingen bijgewerkt.";
+App::$strings["No feature settings configured"] = "Geen plugin-instellingen aanwezig";
+App::$strings["Default maximum affinity level"] = "Standaard hoogste affiniteitsniveau";
+App::$strings["Default minimum affinity level"] = "Standaard laagste affiniteitsniveau";
+App::$strings["Affinity Slider Settings"] = "Affiniteitsinstellingen";
+App::$strings["Feature/Addon Settings"] = "Plugin-instellingen";
+App::$strings["Permission category saved."] = "Permissiegroep opgeslagen.";
+App::$strings["Use this form to create permission rules for various classes of people or connections."] = "Gebruik dit formulier om permissieregels voor diverse soorten mensen en connecties aan te maken.";
+App::$strings["Permission Categories"] = "Permissiegroepen";
+App::$strings["Permission Name"] = "Permissienaam";
+App::$strings["This channel is limited to %d tokens"] = "Dit kanaal heeft een limiet van %d tokens";
+App::$strings["Name and Password are required."] = "Naam en wachtwoord zijn vereist";
+App::$strings["Token saved."] = "Token opgeslagen.";
+App::$strings["Use this form to create temporary access identifiers to share things with non-members. These identities may be used in Access Control Lists and visitors may login using these credentials to access private content."] = "Gebruik dit formulier om tijdelijke identiteiten aan te maken, waarmee je bepaalde informatie met niet-leden kan delen. Deze identiteiten kunnen onder Permissies (handmatige selectie) worden gebruikt. Gasten kunnen inloggen met onderstaande gegevens om zo toegang te krijgen tot privéinhoud.";
+App::$strings["You may also provide <em>dropbox</em> style access links to friends and associates by adding the Login Password to any specific site URL as shown. Examples:"] = "Je kan ook <em>dropbox</em>-achtige links aan mensen geven door bovenstaand wachtwoord op onderstaande manier aan een hub-URL toe te voegen. Voorbeelden:";
+App::$strings["Guest Access Tokens"] = "Gasttoegang";
+App::$strings["Login Name"] = "Inlognaam";
+App::$strings["Login Password"] = "Wachtwoord:";
+App::$strings["Expires (yyyy-mm-dd)"] = "Geldig t/m (yyyy-mm-dd)";
App::$strings["No special theme for mobile devices"] = "Geen speciaal thema voor mobiele apparaten";
App::$strings["%s - (Experimental)"] = "%s - (experimenteel)";
App::$strings["Display Settings"] = "Weergave-instellingen";
@@ -1405,7 +1379,7 @@ App::$strings["Maximum number of conversations to load at any time:"] = "Maximaa
App::$strings["Maximum of 100 items"] = "Maximaal 100 conversaties";
App::$strings["Show emoticons (smilies) as images"] = "Toon emoticons (smilies) als afbeeldingen";
App::$strings["Manual conversation updates"] = "Handmatige conversatie-updates";
-App::$strings["Default is automatic, which may increase screen jumping"] = "Standaard is automatisch, maar soms kan het zorgen voor het verspringen van items";
+App::$strings["Default is on, turning this off may increase screen jumping"] = "Dit is standaard ingeschakeld en door dit uit te schakelen kunnen items soms verspringen.";
App::$strings["Link post titles to source"] = "Berichtkoppen naar originele locatie linken";
App::$strings["System Page Layout Editor - (advanced)"] = "Lay-out bewerken van systeempagina's (geavanceerd)";
App::$strings["Use blog/list mode on channel page"] = "Gebruik blog/lijst-modus op kanaalpagina";
@@ -1414,8 +1388,6 @@ App::$strings["Use blog/list mode on grid page"] = "Gebruik blog/lijst-modus op
App::$strings["Channel page max height of content (in pixels)"] = "Maximale hoogte berichtinhoud op kanaalpagina (in pixels)";
App::$strings["click to expand content exceeding this height"] = "klik om inhoud uit te klappen die deze hoogte overschrijdt";
App::$strings["Grid page max height of content (in pixels)"] = "Maximale hoogte berichtinhoud op gridpagina (in pixels)";
-App::$strings["No feature settings configured"] = "Geen plugin-instellingen aanwezig";
-App::$strings["Feature/Addon Settings"] = "Plugin-instellingen";
App::$strings["Tag removed"] = "Tag verwijderd";
App::$strings["Remove Item Tag"] = "Verwijder item-tag";
App::$strings["Select a tag to remove: "] = "Kies een tag om te verwijderen";
@@ -1430,28 +1402,135 @@ App::$strings["Select a profile"] = "Kies een profiel";
App::$strings["Post an activity"] = "Plaats een bericht";
App::$strings["Only sends to viewers of the applicable profile"] = "Toont dit alleen aan diegene die het gekozen profiel mogen zien.";
App::$strings["Name of thing e.g. something"] = "Naam van ding";
-App::$strings["URL of thing (optional)"] = "URL van ding (optioneel)";
-App::$strings["URL for photo of thing (optional)"] = "URL voor foto van ding (optioneel)";
+App::$strings["URL of thing (optional)"] = "URL van ding (niet verplicht)";
+App::$strings["URL for photo of thing (optional)"] = "URL voor foto van ding (niet verplicht)";
App::$strings["Add Thing to your Profile"] = "Ding aan je profiel toevoegen";
-App::$strings["Your service plan only allows %d channels."] = "Jouw abonnement staat maar %d kanalen toe.";
-App::$strings["Cloned channel not found. Import failed."] = "Gekloond kanaal niet gevonden. Importeren mislukt.";
-App::$strings["No channel. Import failed."] = "Geen kanaal. Importeren mislukt.";
-App::$strings["Import completed."] = "Import voltooid.";
-App::$strings["You must be logged in to use this feature."] = "Je moet ingelogd zijn om dit onderdeel te kunnen gebruiken.";
-App::$strings["Import Channel"] = "Kanaal importeren";
-App::$strings["Use this form to import an existing channel from a different server/hub. You may retrieve the channel identity from the old server/hub via the network or provide an export file."] = "Gebruik dit formulier om een bestaand kanaal te importeren van een andere hub. Je kan de kanaal-identiteit van de oude hub via het netwerk ontvangen of een exportbestand verstrekken.";
-App::$strings["Or provide the old server/hub details"] = "Of vul de gegevens van de oude hub in";
-App::$strings["Your old identity address (xyz@example.com)"] = "Jouw oude kanaaladres (xyz@example.com)";
-App::$strings["Your old login email address"] = "Het e-mailadres van je oude account";
-App::$strings["Your old login password"] = "Wachtwoord van jouw oude account";
-App::$strings["For either option, please choose whether to make this hub your new primary address, or whether your old location should continue this role. You will be able to post from either location, but only one can be marked as the primary location for files, photos, and media."] = "Voor elke optie geldt dat je moet kiezen of je jouw primaire kanaaladres op deze hub wil instellen of dat jouw oude hub deze rol blijft vervullen.";
-App::$strings["Make this hub my primary location"] = "Stel deze hub als mijn primaire locatie in";
-App::$strings["Import existing posts if possible (experimental - limited by available memory"] = "Importeer bestaande berichten wanneer mogelijk (experimenteel - afhankelijk van beschikbaar servergeheugen)";
-App::$strings["This process may take several minutes to complete. Please submit the form only once and leave this page open until finished."] = "Dit proces kan enkele minuten in beslag nemen. Klik maar één keer op opslaan en verlaat deze pagina niet alvorens het proces is voltooid.";
+App::$strings["\$Projectname Server - Setup"] = "\$Projectname Hub - Setup";
+App::$strings["Could not connect to database."] = "Could not connect to database.";
+App::$strings["Could not connect to specified site URL. Possible SSL certificate or DNS issue."] = "Could not connect to specified hub URL. Possible SSL certificate or DNS issue.";
+App::$strings["Could not create table."] = "Could not create table.";
+App::$strings["Your site database has been installed."] = "Your hub database has been installed.";
+App::$strings["You may need to import the file \"install/schema_xxx.sql\" manually using a database client."] = "You may need to import the file \"install/schema_xxx.sql\" manually using a database client.";
+App::$strings["Please see the file \"install/INSTALL.txt\"."] = "Please see the file \"install/INSTALL.txt\".";
+App::$strings["System check"] = "System check";
+App::$strings["Check again"] = "Check again";
+App::$strings["Database connection"] = "Database connection";
+App::$strings["In order to install \$Projectname we need to know how to connect to your database."] = "In order to install \$Projectname we need to know how to connect to your database.";
+App::$strings["Please contact your hosting provider or site administrator if you have questions about these settings."] = "Please contact your hosting provider or server administrator if you have questions about these settings.";
+App::$strings["The database you specify below should already exist. If it does not, please create it before continuing."] = "The database you specify below should already exist. If it does not, please create it before continuing.";
+App::$strings["Database Server Name"] = "Database Server Name";
+App::$strings["Default is 127.0.0.1"] = "Default is 127.0.0.1";
+App::$strings["Database Port"] = "Database Port";
+App::$strings["Communication port number - use 0 for default"] = "Communication port number - use 0 for default";
+App::$strings["Database Login Name"] = "Database Login Name";
+App::$strings["Database Login Password"] = "Database Login Password";
+App::$strings["Database Name"] = "Database Name";
+App::$strings["Database Type"] = "Database Type";
+App::$strings["Site administrator email address"] = "Hub administrator email address";
+App::$strings["Your account email address must match this in order to use the web admin panel."] = "Your account email address must match this in order to use the web admin panel.";
+App::$strings["Website URL"] = "Hub URL";
+App::$strings["Please use SSL (https) URL if available."] = "Please use SSL (https) URL if available.";
+App::$strings["Please select a default timezone for your website"] = "Please select a default timezone for your hub";
+App::$strings["Site settings"] = "Hub settings";
+App::$strings["PHP version 5.5 or greater is required."] = "PHP version 5.5 or greater is required.";
+App::$strings["PHP version"] = "PHP version";
+App::$strings["Could not find a command line version of PHP in the web server PATH."] = "Could not find a command line version of PHP in the web server PATH.";
+App::$strings["If you don't have a command line version of PHP installed on server, you will not be able to run background polling via cron."] = "If you don't have a command line version of PHP installed on server, you will not be able to run background polling via cron.";
+App::$strings["PHP executable path"] = "PHP executable path";
+App::$strings["Enter full path to php executable. You can leave this blank to continue the installation."] = "Enter full path to php executable. You can leave this blank to continue the installation.";
+App::$strings["Command line PHP"] = "Command line PHP";
+App::$strings["Unable to check command line PHP, as shell_exec() is disabled. This is required."] = "Unable to check command line PHP, as shell_exec() is disabled. This is required.";
+App::$strings["The command line version of PHP on your system does not have \"register_argc_argv\" enabled."] = "The command line version of PHP on your system does not have \"register_argc_argv\" enabled.";
+App::$strings["This is required for message delivery to work."] = "This is required for message delivery to work.";
+App::$strings["PHP register_argc_argv"] = "PHP register_argc_argv";
+App::$strings["Your max allowed total upload size is set to %s. Maximum size of one file to upload is set to %s. You are allowed to upload up to %d files at once."] = "Your max allowed total upload size is set to %s. Maximum size of one file to upload is set to %s. You are allowed to upload up to %d files at once.";
+App::$strings["You can adjust these settings in the server php.ini file."] = "You can adjust these settings in the server php.ini file.";
+App::$strings["PHP upload limits"] = "PHP upload limits";
+App::$strings["Error: the \"openssl_pkey_new\" function on this system is not able to generate encryption keys"] = "Error: the \"openssl_pkey_new\" function on this system is not able to generate encryption keys";
+App::$strings["If running under Windows, please see \"http://www.php.net/manual/en/openssl.installation.php\"."] = "If running under Windows, please see \"http://www.php.net/manual/en/openssl.installation.php\".";
+App::$strings["Generate encryption keys"] = "Generate encryption keys";
+App::$strings["libCurl PHP module"] = "libCurl PHP module";
+App::$strings["GD graphics PHP module"] = "GD graphics PHP module";
+App::$strings["OpenSSL PHP module"] = "OpenSSL PHP module";
+App::$strings["PDO database PHP module"] = "PDO database PHP module";
+App::$strings["mb_string PHP module"] = "mb_string PHP module";
+App::$strings["xml PHP module"] = "xml PHP module";
+App::$strings["Apache mod_rewrite module"] = "Apache mod_rewrite module";
+App::$strings["Error: Apache webserver mod-rewrite module is required but not installed."] = "Error: Apache webserver mod-rewrite module is required but not installed.";
+App::$strings["exec"] = "exec";
+App::$strings["Error: exec is required but is either not installed or has been disabled in php.ini"] = "Error: exec is required but is either not installed or has been disabled in php.ini";
+App::$strings["shell_exec"] = "shell_exec";
+App::$strings["Error: shell_exec is required but is either not installed or has been disabled in php.ini"] = "Error: shell_exec is required but is either not installed or has been disabled in php.ini";
+App::$strings["Error: libCURL PHP module required but not installed."] = "Error: libCURL PHP module required but not installed.";
+App::$strings["Error: GD graphics PHP module with JPEG support required but not installed."] = "Error: GD graphics PHP module with JPEG support required but not installed.";
+App::$strings["Error: openssl PHP module required but not installed."] = "Error: openssl PHP module required but not installed.";
+App::$strings["Error: PDO database PHP module required but not installed."] = "Error: PDO database PHP module required but not installed.";
+App::$strings["Error: mb_string PHP module required but not installed."] = "Error: mb_string PHP module required but not installed.";
+App::$strings["Error: xml PHP module required for DAV but not installed."] = "Error: xml PHP module required for DAV but not installed.";
+App::$strings["The web installer needs to be able to create a file called \".htconfig.php\" in the top folder of your web server and it is unable to do so."] = "The web installer needs to be able to create a file called \".htconfig.php\" in the top folder of your web server and it is unable to do so.";
+App::$strings["This is most often a permission setting, as the web server may not be able to write files in your folder - even if you can."] = "This is most often a permission setting, as the web server may not be able to write files in your folder - even if you can.";
+App::$strings["At the end of this procedure, we will give you a text to save in a file named .htconfig.php in your Red top folder."] = "At the end of this procedure, we will give you a text to save in a file named .htconfig.php in your Red top folder.";
+App::$strings["You can alternatively skip this procedure and perform a manual installation. Please see the file \"install/INSTALL.txt\" for instructions."] = "You can alternatively skip this procedure and perform a manual installation. Please see the file \"install/INSTALL.txt\" for instructions.";
+App::$strings[".htconfig.php is writable"] = ".htconfig.php is writable";
+App::$strings["This software uses the Smarty3 template engine to render its web views. Smarty3 compiles templates to PHP to speed up rendering."] = "This software uses the Smarty3 template engine to render its web views. Smarty3 compiles templates to PHP to speed up rendering.";
+App::$strings["In order to store these compiled templates, the web server needs to have write access to the directory %s under the top level web folder."] = "In order to store these compiled templates, the web server needs to have write access to the directory %s under the top level web folder.";
+App::$strings["Please ensure that the user that your web server runs as (e.g. www-data) has write access to this folder."] = "Please ensure that the user that your web server runs as (e.g. www-data) has write access to this folder.";
+App::$strings["Note: as a security measure, you should give the web server write access to %s only--not the template files (.tpl) that it contains."] = "Note: as a security measure, you should give the web server write access to %s only--not the template files (.tpl) that it contains.";
+App::$strings["%s is writable"] = "%s is writable";
+App::$strings["This software uses the store directory to save uploaded files. The web server needs to have write access to the store directory under the top level web folder"] = "This software uses the store directory to save uploaded files. The web server needs to have write access to the store directory under the top level web folder";
+App::$strings["store is writable"] = "store is writable";
+App::$strings["SSL certificate cannot be validated. Fix certificate or disable https access to this site."] = "SSL certificate cannot be validated. Fix certificate or disable https access to this hub.";
+App::$strings["If you have https access to your website or allow connections to TCP port 443 (the https: port), you MUST use a browser-valid certificate. You MUST NOT use self-signed certificates!"] = "If you have https access to your hub or allow connections to TCP port 443 (the https: port), you MUST use a browser-valid certificate. You MUST NOT use self-signed certificates!";
+App::$strings["This restriction is incorporated because public posts from you may for example contain references to images on your own hub."] = "This restriction is incorporated because public posts from you may for example contain references to images on your own hub.";
+App::$strings["If your certificate is not recognized, members of other sites (who may themselves have valid certificates) will get a warning message on their own site complaining about security issues."] = "If your certificate is not recognized, members of other hubs (who may themselves have valid certificates) will get a warning message on their own hub complaining about security issues.";
+App::$strings["This can cause usability issues elsewhere (not just on your own site) so we must insist on this requirement."] = "This can cause usability issues elsewhere (not just on your own hub) so we must insist on this requirement.";
+App::$strings["Providers are available that issue free certificates which are browser-valid."] = "Providers are available that issue free certificates which are browser-valid.";
+App::$strings["If you are confident that the certificate is valid and signed by a trusted authority, check to see if you have failed to install an intermediate cert. These are not normally required by browsers, but are required for server-to-server communications."] = "If you are confident that the certificate is valid and signed by a trusted authority, check to see if you have failed to install an intermediate cert. These are not normally required by browsers, but are required for server-to-server communications.";
+App::$strings["SSL certificate validation"] = "SSL certificate validation";
+App::$strings["Url rewrite in .htaccess is not working. Check your server configuration.Test: "] = "Url rewrite in .htaccess is not working. Check your server configuration.Test: ";
+App::$strings["Url rewrite is working"] = "Url rewrite is working";
+App::$strings["The database configuration file \".htconfig.php\" could not be written. Please use the enclosed text to create a configuration file in your web server root."] = "The database configuration file \".htconfig.php\" could not be written. Please use the enclosed text to create a configuration file in your web server root.";
+App::$strings["Errors encountered creating database tables."] = "Errors encountered creating database tables.";
+App::$strings["<h1>What next</h1>"] = "<h1>What next</h1>";
+App::$strings["IMPORTANT: You will need to [manually] setup a scheduled task for the poller."] = "IMPORTANT: You will need to [manually] setup a scheduled task for the poller.";
App::$strings["No connections."] = "Geen connecties.";
App::$strings["Visit %s's profile [%s]"] = "Bezoek het profiel van %s [%s]";
App::$strings["View Connections"] = "Connecties weergeven";
-App::$strings["Source of Item"] = "Bron van item";
+App::$strings["Profile Unavailable."] = "Profiel niet beschikbaar.";
+App::$strings["Not found"] = "Niet gevonden";
+App::$strings["Invalid channel"] = "Onbekend kanaal";
+App::$strings["Wikis"] = "Wiki's";
+App::$strings["Download"] = "Download";
+App::$strings["Wiki name"] = "Naam wiki";
+App::$strings["Content type"] = "Opmaaktype";
+App::$strings["Create a status post for this wiki"] = "Plaats een bericht over deze wiki";
+App::$strings["Wiki not found"] = "Wiki is niet gevonden";
+App::$strings["Rename page"] = "Pagina hernoemen";
+App::$strings["Error retrieving page content"] = "Fout tijdens ophalen inhoud pagina";
+App::$strings["Revision Comparison"] = "Revisies vergelijken";
+App::$strings["Revert"] = "Ongedaan maken";
+App::$strings["Short description of your changes (optional)"] = "Korte omschrijving van jouw wijzigingen (niet verplicht)";
+App::$strings["Source"] = "Bron";
+App::$strings["New page name"] = "Nieuwe paginanaam";
+App::$strings["Embed image from photo albums"] = "Afbeelding uit een fotoalbum invoegen";
+App::$strings["Embed an image from your albums"] = "Afbeelding uit jouw albums invoegen";
+App::$strings["OK"] = "OK";
+App::$strings["Choose images to embed"] = "Kies afbeeldingen om in te voegen";
+App::$strings["Choose an album"] = "Kies een album";
+App::$strings["Choose a different album"] = "Kies een ander album";
+App::$strings["Error getting album list"] = "Fout tijdens ophalen albumlijst";
+App::$strings["Error getting photo link"] = "Fout tijdens ophalen fotolink";
+App::$strings["Error getting album"] = "Fout tijdens ophalen album";
+App::$strings["Error creating wiki. Invalid name."] = "Fout tijdens aanmaken wiki. Ongeldige naam.";
+App::$strings["Wiki created, but error creating Home page."] = "Wiki aangemaakt, maar fout tijdens aanmaken homepagina.";
+App::$strings["Error creating wiki"] = "Fout tijdens aanmaken wiki.";
+App::$strings["Wiki delete permission denied."] = "Toegang geweigerd tijdens verwijderen wiki.";
+App::$strings["Error deleting wiki"] = "Fout tijdens verwijderen wiki";
+App::$strings["New page created"] = "Nieuwe pagina aangemaakt";
+App::$strings["Cannot delete Home"] = "Kan Home niet verwijderen";
+App::$strings["Current Revision"] = "Huidige revisie";
+App::$strings["Selected Revision"] = "Geselecteerde revisie";
+App::$strings["You must be authenticated."] = "Je moet geauthenticeerd zijn";
App::$strings["Room not found"] = "Chatkanaal niet gevonden";
App::$strings["Leave Room"] = "Chatkanaal verlaten";
App::$strings["Delete Room"] = "Chatkanaal verwijderen";
@@ -1467,41 +1546,56 @@ App::$strings["Expiration"] = "Verloopt na";
App::$strings["min"] = "min";
App::$strings["Xchan Lookup"] = "Xchan opzoeken";
App::$strings["Lookup xchan beginning with (or webbie): "] = "Zoek een xchan (of webbie) die begint met:";
-App::$strings["Calendar entries imported."] = "Agenda-items geïmporteerd.";
-App::$strings["No calendar entries found."] = "Geen agenda-items gevonden.";
-App::$strings["Event can not end before it has started."] = "Gebeurtenis kan niet eindigen voordat het is begonnen";
-App::$strings["Unable to generate preview."] = "Niet in staat om voorvertoning te genereren";
-App::$strings["Event title and start time are required."] = "Titel en begintijd van gebeurtenis zijn vereist.";
-App::$strings["Event not found."] = "Gebeurtenis niet gevonden";
-App::$strings["Edit event title"] = "Titel bewerken";
-App::$strings["Event title"] = "Titel";
-App::$strings["Categories (comma-separated list)"] = "Categorieën (door komma's gescheiden lijst)";
-App::$strings["Edit Category"] = "Categorie";
-App::$strings["Category"] = "Categorie";
-App::$strings["Edit start date and time"] = "Begindatum en -tijd bewerken";
-App::$strings["Start date and time"] = "Begindatum en -tijd";
-App::$strings["Finish date and time are not known or not relevant"] = "Einddatum en -tijd zijn niet bekend of niet van toepassing";
-App::$strings["Edit finish date and time"] = "Einddatum en -tijd bewerken";
-App::$strings["Finish date and time"] = "Einddatum en -tijd";
-App::$strings["Adjust for viewer timezone"] = "Aanpassen aan de tijdzone van wie deze gebeurtenis bekijkt";
-App::$strings["Important for events that happen in a particular place. Not practical for global holidays."] = "Belangrijk voor gebeurtenissen die op een bepaalde locatie plaatsvinden. Niet praktisch voor wereldwijde feestdagen.";
-App::$strings["Edit Description"] = "Omschrijving bewerken";
-App::$strings["Edit Location"] = "Locatie bewerken";
-App::$strings["Permission settings"] = "Permissies";
-App::$strings["Advanced Options"] = "Geavanceerde opties";
-App::$strings["Edit event"] = "Gebeurtenis bewerken";
-App::$strings["Delete event"] = "Gebeurtenis verwijderen";
-App::$strings["calendar"] = "agenda";
-App::$strings["Month"] = "Maand";
-App::$strings["Week"] = "Week";
-App::$strings["Day"] = "Dag";
-App::$strings["Event removed"] = "Gebeurtenis verwijderd";
-App::$strings["Failed to remove event"] = "Verwijderen gebeurtenis mislukt";
App::$strings["Missing room name"] = "Naam chatkanaal ontbreekt";
App::$strings["Duplicate room name"] = "Naam chatkanaal bestaat al";
App::$strings["Invalid room specifier."] = "Ongeldige omschrijving chatkanaal";
App::$strings["Room not found."] = "Chatkanaal niet gevonden";
App::$strings["Room is full"] = "Chatkanaal is vol";
+App::$strings["\$Projectname Notification"] = "\$Projectname-notificatie";
+App::$strings["\$projectname"] = "\$projectname";
+App::$strings["Thank You,"] = "Bedankt,";
+App::$strings["%s Administrator"] = "Beheerder %s";
+App::$strings["%s <!item_type!>"] = "%s <!item_type!>";
+App::$strings["[\$Projectname:Notify] New mail received at %s"] = "[\$Projectname:Notificatie] Nieuw privébericht ontvangen op %s";
+App::$strings["%1\$s, %2\$s sent you a new private message at %3\$s."] = "%1\$s, %2\$s zond jou een nieuw privébericht om %3\$s.";
+App::$strings["%1\$s sent you %2\$s."] = "%1\$s zond jou %2\$s.";
+App::$strings["a private message"] = "een privébericht";
+App::$strings["Please visit %s to view and/or reply to your private messages."] = "Bezoek %s om je privéberichten te bekijken en/of er op te reageren.";
+App::$strings["%1\$s, %2\$s commented on [zrl=%3\$s]a %4\$s[/zrl]"] = "%1\$s, %2\$s gaf een reactie op [zrl=%3\$s]een %4\$s[/zrl]";
+App::$strings["%1\$s, %2\$s commented on [zrl=%3\$s]%4\$s's %5\$s[/zrl]"] = "%1\$s, %2\$s gaf een reactie op [zrl=%3\$s]een %5\$s van %4\$s[/zrl]";
+App::$strings["%1\$s, %2\$s commented on [zrl=%3\$s]your %4\$s[/zrl]"] = "%1\$s, %2\$s gaf een reactie op [zrl=%3\$s]jouw %4\$s[/zrl]";
+App::$strings["[\$Projectname:Notify] Comment to conversation #%1\$d by %2\$s"] = "[\$Projectname:Notificatie] %2\$s gaf een reactie in conversatie #%1\$d";
+App::$strings["%1\$s, %2\$s commented on an item/conversation you have been following."] = "%1\$s, %2\$s gaf een reactie in een conversatie die jij volgt.";
+App::$strings["Please visit %s to view and/or reply to the conversation."] = "Bezoek %s om de conversatie te bekijken en/of er op te reageren.";
+App::$strings["%1\$s, %2\$s liked [zrl=%3\$s]your %4\$s[/zrl]"] = "%1\$s, %2\$s vindt [zrl=%3\$s]jouw %4\$s[/zrl] leuk";
+App::$strings["[\$Projectname:Notify] Like received to conversation #%1\$d by %2\$s"] = "[\$Projectname:Notificatie] %2\$s vindt iets leuk in conversatie #%1\$d";
+App::$strings["%1\$s, %2\$s liked an item/conversation you created."] = "%1\$s, %2\$s vindt iets leuk in een conversatie die jij bent gestart.";
+App::$strings["[\$Projectname:Notify] %s posted to your profile wall"] = "[\$Projectname:Notificatie] %s heeft een bericht op jouw kanaal geplaatst";
+App::$strings["%1\$s, %2\$s posted to your profile wall at %3\$s"] = "%1\$s, %2\$s heeft om %3\$s een bericht op jouw kanaal geplaatst";
+App::$strings["%1\$s, %2\$s posted to [zrl=%3\$s]your wall[/zrl]"] = "%1\$s, %2\$s heeft een bericht op [zrl=%3\$s]jouw kanaal[/zrl] geplaatst";
+App::$strings["[\$Projectname:Notify] %s tagged you"] = "[\$Projectname:Notificatie] %s heeft jou genoemd";
+App::$strings["%1\$s, %2\$s tagged you at %3\$s"] = "%1\$s, %2\$s noemde jou op %3\$s";
+App::$strings["%1\$s, %2\$s [zrl=%3\$s]tagged you[/zrl]."] = "%1\$s, %2\$s [zrl=%3\$s]noemde jou[/zrl].";
+App::$strings["[\$Projectname:Notify] %1\$s poked you"] = "[\$Projectname:Notificatie] %1\$s heeft jou aangestoten";
+App::$strings["%1\$s, %2\$s poked you at %3\$s"] = "%1\$s, %2\$s heeft je aangestoten op %3\$s";
+App::$strings["%1\$s, %2\$s [zrl=%2\$s]poked you[/zrl]."] = "%1\$s, %2\$s [zrl=%2\$s]heeft je aangestoten[/zrl].";
+App::$strings["[\$Projectname:Notify] %s tagged your post"] = "[\$Projectname:Notificatie] %s heeft jouw bericht getagd";
+App::$strings["%1\$s, %2\$s tagged your post at %3\$s"] = "%1\$s, %2\$s heeft jouw bericht om %3\$s getagd";
+App::$strings["%1\$s, %2\$s tagged [zrl=%3\$s]your post[/zrl]"] = "%1\$s, %2\$s heeft [zrl=%3\$s]jouw bericht[/zrl] getagd";
+App::$strings["[\$Projectname:Notify] Introduction received"] = "[\$Projectname:Notificatie] Connectieverzoek ontvangen";
+App::$strings["%1\$s, you've received an new connection request from '%2\$s' at %3\$s"] = "%1\$s, je hebt een nieuw connectieverzoek ontvangen van '%2\$s' op %3\$s";
+App::$strings["%1\$s, you've received [zrl=%2\$s]a new connection request[/zrl] from %3\$s."] = "%1\$s, je hebt een [zrl=%2\$s]nieuw connectieverzoek[/zrl] ontvangen van %3\$s.";
+App::$strings["You may visit their profile at %s"] = "Je kan het profiel bekijken op %s";
+App::$strings["Please visit %s to approve or reject the connection request."] = "Bezoek %s om het connectieverzoek te accepteren of af te wijzen.";
+App::$strings["[\$Projectname:Notify] Friend suggestion received"] = "[\$Projectname:Notificatie] Kanaalvoorstel ontvangen";
+App::$strings["%1\$s, you've received a friend suggestion from '%2\$s' at %3\$s"] = "%1\$s, je hebt een kanaalvoorstel ontvangen van '%2\$s' om %3\$s";
+App::$strings["%1\$s, you've received [zrl=%2\$s]a friend suggestion[/zrl] for %3\$s from %4\$s."] = "%1\$s, je hebt [zrl=%2\$s]een kanaalvoorstel[/zrl] ontvangen voor %3\$s van %4\$s.";
+App::$strings["Name:"] = "Naam:";
+App::$strings["Photo:"] = "Foto:";
+App::$strings["Please visit %s to approve or reject the suggestion."] = "Bezoek %s om het voorstel te accepteren of af te wijzen.";
+App::$strings["[\$Projectname:Notify]"] = "[\$Projectname:Notificatie]";
+App::$strings["created a new post"] = "maakte een nieuw bericht aan";
+App::$strings["commented on %s's post"] = "gaf een reactie op een bericht van %s";
App::$strings["Visible to your default audience"] = "Voor iedereen zichtbaar, mits niet anders ingesteld";
App::$strings["Only me"] = "Alleen ik";
App::$strings["Public"] = "Openbaar";
@@ -1516,6 +1610,24 @@ App::$strings["This is your default setting for who can view your default channe
App::$strings["This is your default setting for who can view your connections"] = "Dit is de standaard privacy-instelling voor wie een lijst met jouw connecties kan bekijken";
App::$strings["This is your default setting for who can view your file storage and photos"] = "Dit is de standaard privacy-instelling voor wie jouw bestanden en foto's kan bekijken";
App::$strings["This is your default setting for the audience of your webpages"] = "Dit is de standaard privacy-instelling voor wie jouw webpagina's kan bekijken";
+App::$strings["(No Title)"] = "(Geen titel)";
+App::$strings["Wiki page create failed."] = "Aanmaken wiki-pagina mislukt.";
+App::$strings["Wiki not found."] = "Wiki niet gevonden";
+App::$strings["Destination name already exists"] = "Naam van doel bestaat al";
+App::$strings["Page not found"] = "Pagina niet gevonden";
+App::$strings["Error reading page content"] = "Fout tijdens lezen pagina-inhoud";
+App::$strings["Error reading wiki"] = "Fout tijdens lezen wiki";
+App::$strings["Page update failed."] = "Bijwerken van pagina mislukt.";
+App::$strings["Nothing deleted"] = "Niets verwijderd";
+App::$strings["Compare: object not found."] = "Vergelijken: object niet gevonden.";
+App::$strings["Page updated"] = "Pagina bijgewerkt";
+App::$strings["Untitled"] = "Naamloos";
+App::$strings["Wiki resource_id required for git commit"] = "Resource_id wiki voor git commit vereist";
+App::$strings["Different viewers will see this text differently"] = "Deze tekst wordt per persoon anders weergeven.";
+App::$strings["__ctx:permcat__ default"] = "standaard";
+App::$strings["__ctx:permcat__ follower"] = "volger";
+App::$strings["__ctx:permcat__ contributor"] = "bijdrager";
+App::$strings["__ctx:permcat__ publisher"] = "publichist ";
App::$strings["Private Message"] = "Niet voor iedereen zichtbaar";
App::$strings["Select"] = "Kies";
App::$strings["Save to Folder"] = "In map opslaan";
@@ -1565,6 +1677,7 @@ App::$strings["Code"] = "Broncode";
App::$strings["Image"] = "Afbeelding";
App::$strings["Insert Link"] = "Link invoegen";
App::$strings["Video"] = "Video";
+App::$strings["Wiki files deleted successfully"] = "Verwijderen wiki-bestanden geslaagd";
App::$strings["Site Admin"] = "Hubbeheerder";
App::$strings["Report Bug"] = "Bugrapport indienen";
App::$strings["View Bookmarks"] = "Bladwijzers bekijken";
@@ -1590,51 +1703,8 @@ App::$strings["Post"] = "Bericht";
App::$strings["Profile Photo"] = "Profielfoto";
App::$strings["Purchase"] = "Aanschaffen";
App::$strings["Undelete"] = "Verwijdering ongedaan maken";
-App::$strings["\$Projectname Notification"] = "\$Projectname-notificatie";
-App::$strings["\$projectname"] = "\$projectname";
-App::$strings["Thank You,"] = "Bedankt,";
-App::$strings["%s Administrator"] = "Beheerder %s";
-App::$strings["%s <!item_type!>"] = "%s <!item_type!>";
-App::$strings["[\$Projectname:Notify] New mail received at %s"] = "[\$Projectname:Notificatie] Nieuw privébericht ontvangen op %s";
-App::$strings["%1\$s, %2\$s sent you a new private message at %3\$s."] = "%1\$s, %2\$s zond jou een nieuw privébericht om %3\$s.";
-App::$strings["%1\$s sent you %2\$s."] = "%1\$s zond jou %2\$s.";
-App::$strings["a private message"] = "een privébericht";
-App::$strings["Please visit %s to view and/or reply to your private messages."] = "Bezoek %s om je privéberichten te bekijken en/of er op te reageren.";
-App::$strings["%1\$s, %2\$s commented on [zrl=%3\$s]a %4\$s[/zrl]"] = "%1\$s, %2\$s gaf een reactie op [zrl=%3\$s]een %4\$s[/zrl]";
-App::$strings["%1\$s, %2\$s commented on [zrl=%3\$s]%4\$s's %5\$s[/zrl]"] = "%1\$s, %2\$s gaf een reactie op [zrl=%3\$s]een %5\$s van %4\$s[/zrl]";
-App::$strings["%1\$s, %2\$s commented on [zrl=%3\$s]your %4\$s[/zrl]"] = "%1\$s, %2\$s gaf een reactie op [zrl=%3\$s]jouw %4\$s[/zrl]";
-App::$strings["[\$Projectname:Notify] Comment to conversation #%1\$d by %2\$s"] = "[\$Projectname:Notificatie] %2\$s gaf een reactie in conversatie #%1\$d";
-App::$strings["%1\$s, %2\$s commented on an item/conversation you have been following."] = "%1\$s, %2\$s gaf een reactie in een conversatie die jij volgt.";
-App::$strings["Please visit %s to view and/or reply to the conversation."] = "Bezoek %s om de conversatie te bekijken en/of er op te reageren.";
-App::$strings["%1\$s, %2\$s liked [zrl=%3\$s]your %4\$s[/zrl]"] = "%1\$s, %2\$s vindt [zrl=%3\$s]jouw %4\$s[/zrl] leuk";
-App::$strings["[\$Projectname:Notify] Like received to conversation #%1\$d by %2\$s"] = "[\$Projectname:Notificatie] %2\$s vindt iets leuk in conversatie #%1\$d";
-App::$strings["%1\$s, %2\$s liked an item/conversation you created."] = "%1\$s, %2\$s vindt iets leuk in een conversatie die jij bent gestart.";
-App::$strings["[\$Projectname:Notify] %s posted to your profile wall"] = "[\$Projectname:Notificatie] %s heeft een bericht op jouw kanaal geplaatst";
-App::$strings["%1\$s, %2\$s posted to your profile wall at %3\$s"] = "%1\$s, %2\$s heeft om %3\$s een bericht op jouw kanaal geplaatst";
-App::$strings["%1\$s, %2\$s posted to [zrl=%3\$s]your wall[/zrl]"] = "%1\$s, %2\$s heeft een bericht op [zrl=%3\$s]jouw kanaal[/zrl] geplaatst";
-App::$strings["[\$Projectname:Notify] %s tagged you"] = "[\$Projectname:Notificatie] %s heeft jou genoemd";
-App::$strings["%1\$s, %2\$s tagged you at %3\$s"] = "%1\$s, %2\$s noemde jou op %3\$s";
-App::$strings["%1\$s, %2\$s [zrl=%3\$s]tagged you[/zrl]."] = "%1\$s, %2\$s [zrl=%3\$s]noemde jou[/zrl].";
-App::$strings["[\$Projectname:Notify] %1\$s poked you"] = "[\$Projectname:Notificatie] %1\$s heeft jou aangestoten";
-App::$strings["%1\$s, %2\$s poked you at %3\$s"] = "%1\$s, %2\$s heeft je aangestoten op %3\$s";
-App::$strings["%1\$s, %2\$s [zrl=%2\$s]poked you[/zrl]."] = "%1\$s, %2\$s [zrl=%2\$s]heeft je aangestoten[/zrl].";
-App::$strings["[\$Projectname:Notify] %s tagged your post"] = "[\$Projectname:Notificatie] %s heeft jouw bericht getagd";
-App::$strings["%1\$s, %2\$s tagged your post at %3\$s"] = "%1\$s, %2\$s heeft jouw bericht om %3\$s getagd";
-App::$strings["%1\$s, %2\$s tagged [zrl=%3\$s]your post[/zrl]"] = "%1\$s, %2\$s heeft [zrl=%3\$s]jouw bericht[/zrl] getagd";
-App::$strings["[\$Projectname:Notify] Introduction received"] = "[\$Projectname:Notificatie] Connectieverzoek ontvangen";
-App::$strings["%1\$s, you've received an new connection request from '%2\$s' at %3\$s"] = "%1\$s, je hebt een nieuw connectieverzoek ontvangen van '%2\$s' op %3\$s";
-App::$strings["%1\$s, you've received [zrl=%2\$s]a new connection request[/zrl] from %3\$s."] = "%1\$s, je hebt een [zrl=%2\$s]nieuw connectieverzoek[/zrl] ontvangen van %3\$s.";
-App::$strings["You may visit their profile at %s"] = "Je kan het profiel bekijken op %s";
-App::$strings["Please visit %s to approve or reject the connection request."] = "Bezoek %s om het connectieverzoek te accepteren of af te wijzen.";
-App::$strings["[\$Projectname:Notify] Friend suggestion received"] = "[\$Projectname:Notificatie] Kanaalvoorstel ontvangen";
-App::$strings["%1\$s, you've received a friend suggestion from '%2\$s' at %3\$s"] = "%1\$s, je hebt een kanaalvoorstel ontvangen van '%2\$s' om %3\$s";
-App::$strings["%1\$s, you've received [zrl=%2\$s]a friend suggestion[/zrl] for %3\$s from %4\$s."] = "%1\$s, je hebt [zrl=%2\$s]een kanaalvoorstel[/zrl] ontvangen voor %3\$s van %4\$s.";
-App::$strings["Name:"] = "Naam:";
-App::$strings["Photo:"] = "Foto:";
-App::$strings["Please visit %s to approve or reject the suggestion."] = "Bezoek %s om het voorstel te accepteren of af te wijzen.";
-App::$strings["[\$Projectname:Notify]"] = "[\$Projectname:Notificatie]";
-App::$strings["created a new post"] = "maakte een nieuw bericht aan";
-App::$strings["commented on %s's post"] = "gaf een reactie op een bericht van %s";
+App::$strings["Add to app-tray"] = "Aan appmenu toevoegen";
+App::$strings["Remove from app-tray"] = "Uit appmenu verwijderen";
App::$strings["Flag Adult Photos"] = "Markeer foto's als voor volwassenen";
App::$strings["Provide photo edit option to hide inappropriate photos from default album view"] = "Zorgt voor een optie om foto's met inhoud voor volwassenen in de standaard albumweergave te verbergen";
App::$strings["This is a fairly comprehensive and complete guitar chord dictionary which will list most of the available ways to play a certain chord, starting from the base of the fingerboard up to a few frets beyond the twelfth fret (beyond which everything repeats). A couple of non-standard tunings are provided for the benefit of slide players, etc."] = "This is a fairly comprehensive and complete guitar chord dictionary which will list most of the available ways to play a certain chord, starting from the base of the fingerboard up to a few frets beyond the twelfth fret (beyond which everything repeats). A couple of non-standard tunings are provided for the benefit of slide players, etc.";
@@ -1646,6 +1716,8 @@ App::$strings["Tuning"] = "Stemmen";
App::$strings["Chord name: example: Em7"] = "Akkoordnaam: bijvoorbeeld: Em7";
App::$strings["Show for left handed stringing"] = "Toon voor linkshandige gitaar";
App::$strings["Quick Reference"] = "Beknopt overzicht";
+App::$strings["No username found in import file."] = "Geen gebruikersnaam in het importbestand gevonden.";
+App::$strings["Unable to create a unique channel address. Import failed."] = "Niet in staat om een uniek kanaaladres aan te maken. Importeren is mislukt.";
App::$strings["Diaspora Protocol Settings updated."] = "Diaspora-protocol-instellingen bijgewerkt.";
App::$strings["Enable the Diaspora protocol for this channel"] = "Het Diaspora-protocol voor dit kanaal inschakelen";
App::$strings["Allow any Diaspora member to comment on your public posts"] = "Geef elk Diaspora-lid toestemming om op jouw openbare berichten te reageren";
@@ -1681,12 +1753,12 @@ App::$strings["<strong><em>Or</em></strong> become a project sponsor (Hubzilla P
App::$strings["Please indicate if you would like your first name or full name (or nothing) to appear in our sponsor listing"] = "Geef aan of jouw voornaam of volledige naam (of niets) op onze sponsorlijst moet verschijnen";
App::$strings["Sponsor"] = "Sponsor";
App::$strings["Special thanks to: "] = "Speciale dank gaat naar: ";
-App::$strings["Post to Dreamwidth"] = "Doorplaatsen naar Dreamwidth";
+App::$strings["Post to Dreamwidth"] = "Dreamwidth";
App::$strings["Enable Dreamwidth Post Plugin"] = "Doorplaatsen naar Dreamwidth inschakelen";
App::$strings["Dreamwidth username"] = "Gebruikersnaam Dreamwidth";
App::$strings["Dreamwidth password"] = "Wachtwoord Dreamwidth";
App::$strings["Post to Dreamwidth by default"] = "Standaard doorplaatsen naar Dreamwidth";
-App::$strings["Dreamwidth Post Settings"] = "Doorplaatsen naar Dreamwidth";
+App::$strings["Dreamwidth Post Settings"] = "Dreamwidth (berichten doorplaatsen)";
App::$strings["Flattr this!"] = "Flattr this!";
App::$strings["Flattr widget settings updated."] = "Instellingen Flattrwidget bijgewerkt.";
App::$strings["Flattr user"] = "Gebruikersnaam Flattr";
@@ -1776,7 +1848,6 @@ App::$strings["This will import all your Friendica photo albums to this Red chan
App::$strings["Friendica Server base URL"] = "Basis-URL van Friendica-server";
App::$strings["Friendica Login Username"] = "Gebruikersnaam Friendica";
App::$strings["Friendica Login Password"] = "Wachtwoord Friendica";
-App::$strings["Enable the GNU-Social protocol for this channel"] = "GNU social-protocol voor dit kanaal inschakelen";
App::$strings["Send email to all members"] = "Naar alle leden e-mail versturen";
App::$strings["$1%s Administrator"] = "Beheerder $1%s";
App::$strings["No recipients found."] = "Geen ontvangers gevonden";
@@ -1785,12 +1856,12 @@ App::$strings["Send email to all hub members."] = "Naar alle leden van deze hub
App::$strings["Message subject"] = "Onderwerp e-mailbericht";
App::$strings["Sender Email address"] = "E-mailadres afzender";
App::$strings["Test mode (only send to hub administrator)"] = "Testmodus (alleen naar hubbeheerder sturen)";
-App::$strings["Post to Insanejournal"] = "Doorplaatsen naar InsaneJournal";
+App::$strings["Post to Insanejournal"] = "InsaneJournal";
App::$strings["Enable InsaneJournal Post Plugin"] = "Doorplaatsen naar InsaneJournal inschakelen";
App::$strings["InsaneJournal username"] = "Gebruikersnaam InsaneJournal";
App::$strings["InsaneJournal password"] = "Wachtwoord InsaneJournal";
App::$strings["Post to InsaneJournal by default"] = "Standaard doorplaatsen naar InsaneJournal";
-App::$strings["InsaneJournal Post Settings"] = "Doorplaatsen naar InsaneJournal";
+App::$strings["InsaneJournal Post Settings"] = "InsaneJournal (berichten doorplaatsen)";
App::$strings["Insane Journal Settings saved."] = "InsaneJournal-instellingen opgeslagen.";
App::$strings["Channels to auto connect"] = "Kanalen om automatisch mee te verbinden";
App::$strings["Comma separated list"] = "Door komma's gescheiden lijst";
@@ -1810,7 +1881,6 @@ App::$strings["Hubzilla password"] = "Wachtwoord Hubzilla";
App::$strings["Approve subscription requests from Hubzilla contacts automatically"] = "Approve subscription requests from Hubzilla contacts automatically";
App::$strings["Purge internal list of jabber addresses of contacts"] = "Purge internal list of jabber addresses of contacts";
App::$strings["Configuration Help"] = "Configuratiehulp";
-App::$strings["Add Contact"] = "Contact toevoegen";
App::$strings["Jappix Mini Settings"] = "Jappix Mini";
App::$strings["Upload a file"] = "Bestand uploaden";
App::$strings["Drop files here to upload"] = "Sleep bestanden hierheen om ze te uploaden";
@@ -1822,19 +1892,19 @@ App::$strings["File has an invalid extension, it should be one of "] = "Bestand
App::$strings["Upload was cancelled, or server error encountered"] = "Upload werd geannuleerd of er was een serverfout";
App::$strings["An account has been created for you."] = "Er is voor jou een account aangemaakt.";
App::$strings["Authentication successful but rejected: account creation is disabled."] = "Authenticatie geslaagd, maar afgekeurd: aanmaken accounts uitgeschakeld.";
-App::$strings["Post to Libertree"] = "Doorplaatsen naar Libertree";
+App::$strings["Post to Libertree"] = "Libertree";
App::$strings["Enable Libertree Post Plugin"] = "Doorplaatsen naar Libertree inschakelen";
App::$strings["Libertree API token"] = "API-token Libertree";
App::$strings["Libertree site URL"] = "Website-URL Libertree";
App::$strings["Post to Libertree by default"] = "Standaard doorplaatsen naar Libertree";
-App::$strings["Libertree Post Settings"] = "Doorplaatsen naar Libertree";
+App::$strings["Libertree Post Settings"] = "Libertree (berichten doorplaatsen)";
App::$strings["Libertree Settings saved."] = "Libertree-instellingen opgeslagen.";
-App::$strings["Post to LiveJournal"] = "Doorplaatsen naar LiveJournal";
+App::$strings["Post to LiveJournal"] = "LiveJournal";
App::$strings["Enable LiveJournal Post Plugin"] = "Doorplaatsen naar LiveJournal inschakelen";
App::$strings["LiveJournal username"] = "Gebruikersnaam LiveJournal";
App::$strings["LiveJournal password"] = "Wachtwoord LiveJournal";
-App::$strings["Post to LiveJournal by default"] = "Standaard doorplaatsen naar ";
-App::$strings["LiveJournal Post Settings"] = "Doorplaatsen naar LiveJournal";
+App::$strings["Post to LiveJournal by default"] = "Standaard doorplaatsen naar LiveJournal";
+App::$strings["LiveJournal Post Settings"] = "LiveJournal (berichten doorplaatsen)";
App::$strings["LiveJournal Settings saved."] = "LiveJournal-instellingen opgeslagen.";
App::$strings["Logfile archive directory"] = "Logbestand archiefmap";
App::$strings["Directory to store rotated logs"] = "Map om geroteerde logbestanden in op te slaan";
@@ -1917,12 +1987,12 @@ App::$strings["NSAbait Settings"] = "NSAbait";
App::$strings["This plugin looks in posts for the words/text you specify below, and collapses any content containing those keywords so it is not displayed at inappropriate times, such as sexual innuendo that may be improper in a work setting. It is polite and recommended to tag any content containing nudity with #NSFW. This filter can also match any other word/text you specify, and can thereby be used as a general purpose content filter."] = "Deze plug-in controleert berichten op woorden die je hieronder kunt opgeven en klapt berichten in die deze woorden bevatten, zodat die berichten niet worden weergegeven op ongeschikte momenten. Denk hierbij aan berichten met erotische afbeeldingen, die waarschijnlijk niet geschikt zijn binnen (bijvoorbeeld) een werkomgeving. Het is beleefd en het wordt aangeraden om zulke berichten met #NSFW te taggen. Dit filter kan ook gebruikt worden met andere woorden en is dus voor alles inzetbaar.";
App::$strings["Enable Content filter"] = "Inhoudsfilter inschakelen";
App::$strings["Comma separated list of keywords to hide"] = "Door komma's gescheiden lijst met woorden die gefilterd moeten worden.";
-App::$strings["Use /expression/ to provide regular expressions"] = "Gebruik /expressie/ voor reguliere expressies";
+App::$strings["Word, /regular-expression/, lang=xx, lang!=xx"] = "Woord, /reguliere expressie/, lang=xx, lang!=xx";
App::$strings["Not Safe For Work Settings"] = "Not Safe For Work (inhoudsfilter)";
App::$strings["General Purpose Content Filter"] = "Voor alles te gebruiken inhoudsfilter";
App::$strings["NSFW Settings saved."] = "NSFW-instellingen opgeslagen.";
App::$strings["Possible adult content"] = "Mogelijk inhoud voor volwassenen";
-App::$strings["%s - click to open/close"] = "%s - Klik om te openen of te sluiten";
+App::$strings["%s - view"] = "%s - tonen";
App::$strings["System defaults:"] = "Systeemstandaarden:";
App::$strings["Preferred Clipart IDs"] = "Voorkeursclipart";
App::$strings["List of preferred clipart ids. These will be shown first."] = "Lijst met clipartnummers die als eerste moeten worden getoond.";
@@ -1974,7 +2044,7 @@ App::$strings["Enable Planets Plugin"] = "Planets inschakelen";
App::$strings["Planets Settings"] = "Planets";
App::$strings["You are now authenticated to pumpio."] = "De verbinding met pump.io is geverifieerd";
App::$strings["return to the featured settings page"] = "Ga terug naar pagina met plugin-instellingen";
-App::$strings["Post to Pump.io"] = "Doorplaatsen naar Pump.io";
+App::$strings["Post to Pump.io"] = "Pump.io";
App::$strings["Pump.io servername"] = "Pump.io-servernaam";
App::$strings["Without \"http://\" or \"https://\""] = "Zonder \"http://\" of \"https://\"";
App::$strings["Pump.io username"] = "Gebruikersnaam Pump.io";
@@ -1985,7 +2055,7 @@ App::$strings["Enable pump.io Post Plugin"] = "Doorplaatsen naar Pump.io inschak
App::$strings["Post to pump.io by default"] = "Standaard doorplaatsen naar Pump.io";
App::$strings["Should posts be public"] = "Moeten berichten openbaar zijn";
App::$strings["Mirror all public posts"] = "Alle openbare berichten doorplaatsen";
-App::$strings["Pump.io Post Settings"] = "Doorplaatsen naar Pump.io";
+App::$strings["Pump.io Post Settings"] = "Pump.io (berichten doorplaatsen)";
App::$strings["PumpIO Settings saved."] = "Pump.io-instellingen opgeslagen.";
App::$strings["QR code"] = "QR-code";
App::$strings["QR Generator"] = "QR-code-generator";
@@ -2010,9 +2080,8 @@ App::$strings["Import just this album"] = "Alleen dit album importeren";
App::$strings["Leave blank to import all albums"] = "Laat leeg om alle albums te importeren";
App::$strings["Maximum count to import"] = "Maximaal aantal om te importeren";
App::$strings["0 or blank to import all available"] = "0 of leeg om alles te importeren";
-App::$strings["Post to Red"] = "Doorplaatsen naar Hubzilla";
+App::$strings["Post to Red"] = "Hubzilla";
App::$strings["Channel is required."] = "Een kanaal is vereist.";
-App::$strings["Invalid channel."] = "Onbekend kanaal.";
App::$strings["redred Settings saved."] = "RedRed-instellingen opgeslagen.";
App::$strings["Allow posting to another Hubzilla Channel"] = "Doorplaatsen naar een ander Hubzilla-kanaal toestaan";
App::$strings["Send public postings to Hubzilla channel by default"] = "Standaard doorplaatsen naar een ander Hubzilla-kanaal toestaan";
@@ -2021,15 +2090,15 @@ App::$strings["https://{sitename}/api"] = "https://{hubnaam}/api";
App::$strings["Hubzilla login name"] = "Gebruikersnaam Hubzilla";
App::$strings["Hubzilla channel name"] = "Kanaalnaam Hubzilla";
App::$strings["Nickname"] = "Bijnaam";
-App::$strings["Hubzilla Crosspost Settings"] = "Doorplaatsen naar Hubzilla";
-App::$strings["Post to Friendica"] = "Doorplaatsen naar Friendica";
+App::$strings["Hubzilla Crosspost Settings"] = "Hubzilla (berichten doorplaatsen)";
+App::$strings["Post to Friendica"] = "Friendica";
App::$strings["rtof Settings saved."] = "RTOF-instellingen opgeslagen.";
App::$strings["Allow posting to Friendica"] = "Doorplaatsen naar Friendica toestaan";
App::$strings["Send public postings to Friendica by default"] = "Standaard doorplaatsen naar Friendica";
App::$strings["Friendica API Path"] = "API-pad Friendica";
App::$strings["Friendica login name"] = "Gebruikersnaam Friendica";
App::$strings["Friendica password"] = "Wachtwoord Friendica";
-App::$strings["Hubzilla to Friendica Post Settings"] = "Doorplaatsen naar Friendica";
+App::$strings["Hubzilla to Friendica Post Settings"] = "Friendica (berichten doorplaatsen)";
App::$strings["Extended Identity Sharing"] = "Uitgebreid identiteit delen";
App::$strings["Share your identity with all websites on the internet. When disabled, identity is only shared with sites in the matrix."] = "Deel jouw Hubzilla-identiteit met alle websites op het internet. Wanneer dit is uitgeschakeld wordt je identiteit alleen binnen het Hubzilla-netwerk gedeeld. Schakel dit alleen in als je weet wat je doet.";
App::$strings["Some setting"] = "Een of andere instelling";
@@ -2041,7 +2110,7 @@ App::$strings["Smileybutton Settings"] = "Smileyknop";
App::$strings["Page to load after login"] = "Pagina die na het inloggen getoond moet worden";
App::$strings["Examples: &quot;apps&quot;, &quot;network?f=&gid=37&quot; (privacy collection), &quot;channel&quot; or &quot;notifications/system&quot; (leave blank for default network page (grid)."] = "Voorbeelden: &quot;apps&quot;, &quot;network?f=&gid=37&quot; (privacygroep), &quot;channel&quot; of &quot;notifications/system&quot; (laat leeg voor de standaard netwerkpagina (grid).";
App::$strings["Startpage Settings"] = "Startpagina";
-App::$strings["Post to GNU social"] = "Doorplaatsen naar GNU social";
+App::$strings["Post to GNU social"] = "GNU social";
App::$strings["Please contact your site administrator.<br />The provided API URL is not valid."] = "De verstrekte API-URL is ongeldig.<br />Neem contact op met jouw hubbeheerder.";
App::$strings["We could not contact the GNU social API with the Path you entered."] = "Wij konden de GNU social-API niet bereiken door middel van het ingevulde pad.";
App::$strings["GNU social settings updated."] = "GNU social-instellingen bijgewerkt.";
@@ -2067,7 +2136,7 @@ App::$strings["If enabled your public postings can be posted to the associated G
App::$strings["Post to GNU social by default"] = "Standaard doorplaatsen naar GNU social";
App::$strings["If enabled your public postings will be posted to the associated GNU-social account by default"] = "Wanneer dit is ingeschakeld worden al jouw openbare berichten standaard naar het gekoppelde GNU social-account doorgeplaatst";
App::$strings["Clear OAuth configuration"] = "OAuth-configuratie wissen";
-App::$strings["GNU social Post Settings"] = "Doorplaatsen naar GNU social";
+App::$strings["GNU social Post Settings"] = "GNU social (berichten doorplaatsen)";
App::$strings["API URL"] = "API-URL";
App::$strings["Application name"] = "Naam applicatie";
App::$strings["Currently blocked"] = "Momenteel geblokkeerd";
@@ -2106,7 +2175,7 @@ App::$strings["There are events this week. Click here too see which!"] = "Er vin
App::$strings["You have received a new introduction. Click here to see who!"] = "Je hebt een nieuw connectieverzoek ontvangen. Klik hier om te kijken van wie.";
App::$strings["There is a new system notification. Click here to see what has happened!"] = "Er is een nieuwe systeemnotificatie. Klik hier om te zien wat er aan de hand is.";
App::$strings["Click here to share text, images, videos and sound."] = "Klik hier om tekst, afbeeldingen, video en audio te delen.";
-App::$strings["You can write an optional title for your update (good for long posts)."] = "Je kan optioneel een titel voor je nieuwe bericht verzinnen. Vooral goed voor langere berichten.";
+App::$strings["You can write an optional title for your update (good for long posts)."] = "Je kan een titel voor je nieuwe bericht verzinnen, maar dit is niet verplicht. Vooral goed voor langere berichten.";
App::$strings["Entering some categories here makes it easier to find your post later."] = "Het invullen van enkele categorieën, maakt het later terugvinden van je berichten gemakkelijker. Dit is niet verplicht.";
App::$strings["Share photos, links, location, etc."] = "Deel foto's, links, locaties, enz.";
App::$strings["Only want to share content for a while? Make it expire at a certain date."] = "Wil je alleen iets tot een bepaald moment delen? Dan kan je het hiermee op een bepaalde datum en tijd laten verlopen.";
@@ -2124,7 +2193,7 @@ App::$strings["Save your search so you can repeat it at a later date."] = "Sla j
App::$strings["If you see this icon you can be sure that the sender is who it say it is. It is normal that it is not always possible to verify the sender, so the icon will be missing sometimes. There is usually no need to worry about that."] = "Wanneer je dit pictogram ziet, kan je er van uitgaan dat de afzender is wie hij/zij beweert te zijn. Het is niet altijd mogelijk om de afzender te verifiëren, waardoor het pictogram soms ontbreekt. Dit is meestal geen reden voor ongerustheid.";
App::$strings["Danger! It seems someone tried to forge a message! This message is not necessarily from who it says it is from!"] = "Gevaar! Het lijkt er op dat iemand een bericht heeft proberen te vervalsen! Dit bericht is mogelijk niet afkomstig van de vermelde afzender!";
App::$strings["Welcome to Hubzilla! Would you like to see a tour of the UI?</p> <p>You can pause it at any time and continue where you left off by reloading the page, or navigting to another page.</p><p>You can also advance by pressing the return key"] = "Welkom op Hubzilla! Wil jij een rondleiding hebben langs de gebruikersinterface?</p> <p>Je kan dit op elk moment pauzeren en weer hervatten door de pagina te herladen of naar een andere pagina te gaan.</p><p>Je kan ook vooruitgaan met behulp van de entertoets.";
-App::$strings["Post to Twitter"] = "Doorplaatsen naar Twitter";
+App::$strings["Post to Twitter"] = "Twitter";
App::$strings["Twitter settings updated."] = "Twitter-instellingen bijgewerkt.";
App::$strings["No consumer key pair for Twitter found. Please contact your site administrator."] = "Geen consumerkeys voor Twitter gevonden. Neem contact op met jouw hubbeheerder.";
App::$strings["At this Hubzilla instance the Twitter plugin was enabled but you have not yet connected your account to your Twitter account. To do so click the button below to get a PIN from Twitter which you have to copy into the input box below and submit the form. Only your <strong>public</strong> posts will be posted to Twitter."] = "De Twitter-plugin is op deze Hubzilla-hub ingeschakeld, maar je hebt nog niet jouw Hubzilla-kanaal met jouw Twitter-account gekoppeld. Om dit te doen klik je op de knop hieronder om een PIN-code van Twitter te krijgen. Deze dien je te kopiëren en in het invoegveld beneden te plakken. Vervolgens klik je op Opslaan. Alleen jouw <strong>openbare</strong> berichten kunnen op Twitter worden geplaatst.";
@@ -2135,7 +2204,7 @@ App::$strings["Allow posting to Twitter"] = "Doorplaatsen naar Twitter toestaan"
App::$strings["If enabled your public postings can be posted to the associated Twitter account"] = "Wanneer dit is ingeschakeld kunnen jouw <strong>openbare</strong> berichten naar het gekoppelde Twitter-account worden doorgeplaatst";
App::$strings["Send public postings to Twitter by default"] = "Standaard doorplaatsen naar Twitter";
App::$strings["If enabled your public postings will be posted to the associated Twitter account by default"] = "Wanneer dit is ingeschakeld worden al jouw <strong>openbare</strong> berichten standaard naar het gekoppelde Twitter-account doorgeplaatst";
-App::$strings["Twitter Post Settings"] = "Doorplaatsen naar Twitter";
+App::$strings["Twitter Post Settings"] = "Twitter (berichten doorplaatsen)";
App::$strings["Submit Settings"] = "Instellingen toepassen";
App::$strings["Show Upload Limits"] = "Uploadlimieten tonen";
App::$strings["Hubzilla configured maximum size: "] = "Op Hubzilla configureerde maximale grootte: ";
@@ -2149,7 +2218,7 @@ App::$strings["No entries."] = "Niets aanwezig.";
App::$strings["Enable Visage Visitor Logging"] = "Visage inschakelen ";
App::$strings["Visage Settings"] = "Visage";
App::$strings["Who likes me?"] = "Wie vindt mij leuk?";
-App::$strings["Post to WordPress"] = "Doorplaatsen naar WordPress";
+App::$strings["Post to WordPress"] = "WordPress";
App::$strings["Enable WordPress Post Plugin"] = "Doorplaatsen naar WordPress inschakelen";
App::$strings["WordPress username"] = "Gebruikersnaam WordPress";
App::$strings["WordPress password"] = "Wachtwoord WordPress";
@@ -2159,7 +2228,7 @@ App::$strings["WordPress blogid"] = "Blog ID WordPress";
App::$strings["For multi-user sites such as wordpress.com, otherwise leave blank"] = "Voor websites met meerdere gebruikers, zoals wordpress.com. Anders leeg laten.";
App::$strings["Post to WordPress by default"] = "Standaard naar WordPress doorplaatsen";
App::$strings["Forward comments (requires hubzilla_wp plugin)"] = "Reacties doorplaatsen (Hubzilla_WP-plugin vereist)";
-App::$strings["WordPress Post Settings"] = "Doorplaatsen naar WordPress";
+App::$strings["WordPress Post Settings"] = "WordPress (berichten doorplaatsen)";
App::$strings["Wordpress Settings saved."] = "WordPress-instellingen opgeslagen.";
App::$strings["XMPP settings updated."] = "XMPP-instellingen bijgewerkt.";
App::$strings["Enable Chat"] = "Chatten inschakelen";
@@ -2188,21 +2257,6 @@ App::$strings["Addressbook Name"] = "Naam adresboek";
App::$strings["Addressbook Tools"] = "Adresboek-hulpmiddelen";
App::$strings["Import addressbook"] = "Importeren";
App::$strings["Select an addressbook to import to"] = "Kies een adresboek om te importeren";
-App::$strings["Errors encountered creating database table: "] = "Fouten opgetreden tijdens aanmaken databasetabel: ";
-App::$strings["Default Calendar"] = "Standaard agenda";
-App::$strings["Default Addressbook"] = "Standaard adresboek";
-App::$strings["CalDAV/CardDAV Settings saved."] = "CalDAV/CardDAV-instellingen opgeslagen.";
-App::$strings["Enable CalDAV/CardDAV Server for this channel"] = "CalDAV/CardDAV-server voor dit kanaal inschakelen";
-App::$strings["Your CalDAV resources are located at %s "] = "Jouw CalDAV-URL is %s ";
-App::$strings["Your CardDAV resources are located at %s "] = "Jouw CardDAV-URL is %s ";
-App::$strings["CalDAV/CardDAV Settings"] = "CalDAV/CardDAV";
-App::$strings["Mobile"] = "Mobiel";
-App::$strings["Home"] = "Thuis";
-App::$strings["Home, Voice"] = "Thuis, spraak";
-App::$strings["Home, Fax"] = "Thuis, fax";
-App::$strings["Work"] = "Werk";
-App::$strings["Work, Voice"] = "Werk, spraak";
-App::$strings["Work, Fax"] = "Werk, fax";
App::$strings["INVALID EVENT DISMISSED!"] = "ONGELDIGE GEBEURTENIS VERWIJDERD!";
App::$strings["Summary: "] = "Samenvatting: ";
App::$strings["Date: "] = "Datum: ";
@@ -2220,19 +2274,18 @@ App::$strings["Less"] = "Minder";
App::$strings["Select calendar"] = "Kies agenda";
App::$strings["Delete all"] = "Alles verwijderen";
App::$strings["Sorry! Editing of recurrent events is not yet implemented."] = "Excuses! Bewerken van herhalende gebeurtenissen is nog niet geïmplementeerd.";
-App::$strings["Organisation"] = "Organisatie";
-App::$strings["Title"] = "Titel";
-App::$strings["Phone"] = "Telefoon";
-App::$strings["Instant messenger"] = "Instant messenger";
-App::$strings["Website"] = "Website";
-App::$strings["Note"] = "Opmerking";
-App::$strings["Add Field"] = "Veld toevoegen";
-App::$strings["P.O. Box"] = "Postbus";
-App::$strings["Additional"] = "Extra";
-App::$strings["Street"] = "Straat en huisnummer";
-App::$strings["Locality"] = "Plaats";
-App::$strings["Region"] = "Provincie/staat/regio/enz.";
-App::$strings["ZIP Code"] = "Postcode";
+App::$strings["Errors encountered creating database table: "] = "Fouten opgetreden tijdens aanmaken databasetabel: ";
+App::$strings["Default Calendar"] = "Standaard agenda";
+App::$strings["Default Addressbook"] = "Standaard adresboek";
+App::$strings["CalDAV/CardDAV Settings saved."] = "CalDAV/CardDAV-instellingen opgeslagen.";
+App::$strings["Enable CalDAV/CardDAV Server for this channel"] = "CalDAV/CardDAV-server voor dit kanaal inschakelen";
+App::$strings["Your CalDAV resources are located at %s "] = "Jouw CalDAV-URL is %s ";
+App::$strings["Your CardDAV resources are located at %s "] = "Jouw CardDAV-URL is %s ";
+App::$strings["CalDAV/CardDAV Settings"] = "CalDAV/CardDAV";
+App::$strings["Home, Voice"] = "Thuis, spraak";
+App::$strings["Home, Fax"] = "Thuis, fax";
+App::$strings["Work, Voice"] = "Werk, spraak";
+App::$strings["Work, Fax"] = "Werk, fax";
App::$strings["Invalid game."] = "Ongeldig spel.";
App::$strings["You are not a player in this game."] = "Jij doet niet aan dit speel mee.";
App::$strings["You must be a local channel to create a game."] = "Je moet een lokaal kanaal zijn om een spel aan te maken.";
@@ -2250,8 +2303,6 @@ App::$strings["Like us on Hubzilla"] = "Like ons op Hubzilla";
App::$strings["Embed:"] = "Insluiten (embed):";
App::$strings["Male"] = "Man";
App::$strings["Female"] = "Vrouw";
-App::$strings["OpenID protocol error. No ID returned."] = "OpenID-protocolfout. Geen ID terugontvangen.";
-App::$strings["Login failed."] = "Inloggen mislukt.";
App::$strings["First Name"] = "Voornaam";
App::$strings["Last Name"] = "Achternaam";
App::$strings["Full Name"] = "Volledige naam";
@@ -2268,6 +2319,8 @@ App::$strings["Birth Day"] = "Geboortedag";
App::$strings["Birthdate"] = "Geboortedatum";
App::$strings["We encountered a problem while logging in with the OpenID you provided. Please check the correct spelling of the ID."] = "We hebben een probleem ontdekt tijdens het inloggen met de OpenID die je hebt verstrekt. Controleer de ID op typefouten.";
App::$strings["The error message was:"] = "Foutmelding was:";
+App::$strings["OpenID protocol error. No ID returned."] = "OpenID-protocolfout. Geen ID terugontvangen.";
+App::$strings["Login failed."] = "Inloggen mislukt.";
App::$strings["Reconnecting %d connections"] = "%d connecties opnieuw aan het verbinden";
App::$strings["Diaspora Reconnect"] = "Diaspora opnieuw verbinden";
App::$strings["Use this form to re-establish Diaspora connections which were initially made from a different hub."] = "Gebruik dit formulier om opnieuw met Diaspora-connecties te verbinden, die oorspronkelijk op een andere hub waren verbonden.";
@@ -2292,13 +2345,122 @@ App::$strings["New identity"] = "Nieuwe identiteit";
App::$strings["Delete marker"] = "Markering verwijderen";
App::$strings["Delete member"] = "Lid verwijderen";
App::$strings["Edit proximity alert"] = "Nabijheidswaarschuwing bewerken";
-App::$strings["A proximity alert will be issued when this member is within a certain radius of you.<br><br>Enter a radius in meters (0 to disable):"] = "Een nabijheidswaarschuwing wordt actief wanneer dit lid zich binnen een bepaalde straal bevindt.<br><br>Voer het aantal meters van de straal in (0 om uit te schakelen):";
+App::$strings["A proximity alert will be issued when this member is within a certain radius of you.<br><br>Enter a radius in meters (0 to disable):"] = "Een nabijheidswaarschuwing wordt actief wanneer dit lid zich binnen een bepaalde straal rond jouw locatie bevindt.<br><br>Voer het aantal meters van de straal in (0 om uit te schakelen):";
App::$strings["distance"] = "afstand";
+App::$strings["Proximity alert distance (meters)"] = "Afstand nabijheidswaarschuwing (meter)";
+App::$strings["A proximity alert will be issued when you are within a certain radius of the marker location.<br><br>Enter a radius in meters (0 to disable):"] = "Een nabijheidswaarschuwing wordt actief wanneer je je binnen een bepaalde straal rond een specifieke locatie bevindt.<br><br>Voer het aantal meters van de straal in (0 om uit te schakelen):";
+App::$strings["Marker proximity alert"] = "Locatiemarkering nabijheidswaarschuwing";
+App::$strings["Reminder note"] = "Herinnering";
+App::$strings["Enter a note to be displayed when you are within the specified proximity..."] = "Vul de tekst in die getoond moet worden wanneer je je op de aangegeven afstand bevindt...";
App::$strings["Add new rendezvous"] = "Nieuwe rendezvous toevoegen";
App::$strings["Create a new rendezvous and share the access link with those you wish to invite to the group. Those who open the link become members of the rendezvous. They can view other member locations, add markers to the map, or share their own locations with the group."] = "Maak een nieuwe rendezvous aan en deel de toegangslink met wie je wil uitnodigen voor de groep. Wie op de link klikt wordt lid van rendezvous. Zij kunnen dan de locaties zien van andere leden, markeringen aan de kaart toevoegen of hun eigen locaties met de groep delen.";
-App::$strings["No username found in import file."] = "Geen gebruikersnaam in het importbestand gevonden.";
-App::$strings["Unable to create a unique channel address. Import failed."] = "Niet in staat om een uniek kanaaladres aan te maken. Importeren is mislukt.";
+App::$strings["Install Firefox Sharing Tools"] = "Firefox Share";
+App::$strings["Share content from Firefox to \$Projectname"] = "Deel webpagina's vanuit Firefox met ";
+App::$strings["Install Firefox Sharing Tools to this web browser"] = "Activeer de \$Projectname-service in Firefox";
+App::$strings["Error retrieving wiki"] = "Fout tijdens ophalen wiki";
+App::$strings["Error creating zip file export folder"] = "Fout tijdens aanmaken exportmap zipbestand";
+App::$strings["Error downloading wiki: "] = "Fout tijdens downloaden wiki: ";
+App::$strings["Wiki Pages"] = "Wikipagina's";
+App::$strings["Add new page"] = "Nieuwe pagina toevoegen";
+App::$strings["Page name"] = "Paginanaam";
+App::$strings["Wiki List"] = "Wiki's";
+App::$strings["Enable the GNU-Social protocol for this channel"] = "GNU social-protocol voor dit kanaal inschakelen";
+App::$strings["__ctx:opensearch__ Search %1\$s (%2\$s)"] = "Zoek %1\$s (%2\$s)";
+App::$strings["__ctx:opensearch__ \$Projectname"] = "\$Projectname";
+App::$strings["Search \$Projectname"] = "Zoek in ";
App::$strings["Cannot locate DNS info for database server '%s'"] = "Kan DNS-informatie voor databaseserver '%s' niet vinden";
+App::$strings["default"] = "standaard";
+App::$strings["Select an alternate language"] = "Kies een andere taal";
+App::$strings["Not a valid email address"] = "Geen geldig e-mailadres";
+App::$strings["Your email domain is not among those allowed on this site"] = "Jouw e-maildomein is op deze hub niet toegestaan";
+App::$strings["Your email address is already registered at this site."] = "Jouw e-mailadres is al op deze hub geregistreerd.";
+App::$strings["An invitation is required."] = "Een uitnodiging is vereist";
+App::$strings["Invitation could not be verified."] = "Uitnodiging kon niet geverifieerd worden";
+App::$strings["Please enter the required information."] = "Vul de vereiste informatie in.";
+App::$strings["Failed to store account information."] = "Account-informatie kon niet opgeslagen worden.";
+App::$strings["Registration confirmation for %s"] = "Registratiebevestiging voor %s";
+App::$strings["Registration request at %s"] = "Registratiebevestiging voor %s";
+App::$strings["your registration password"] = "jouw registratiewachtwoord";
+App::$strings["Registration details for %s"] = "Registratiegegevens voor %s";
+App::$strings["Account approved."] = "Account goedgekeurd";
+App::$strings["Registration revoked for %s"] = "Registratie ingetrokken voor %s";
+App::$strings["Click here to upgrade."] = "Klik hier om te upgraden.";
+App::$strings["This action exceeds the limits set by your subscription plan."] = "Deze handeling overschrijdt de beperkingen die voor jouw abonnement gelden.";
+App::$strings["This action is not available under your subscription plan."] = "Deze handeling is niet mogelijk met jouw abonnement.";
+App::$strings["Categories"] = "Categorieën";
+App::$strings["Suggestions"] = "Voorgestelde kanalen";
+App::$strings["See more..."] = "Meer...";
+App::$strings["You have %1$.0f of %2$.0f allowed connections."] = "Je hebt %1$.0f van de %2$.0f toegestane connecties.";
+App::$strings["Add New Connection"] = "Nieuwe connectie toevoegen";
+App::$strings["Enter channel address"] = "Vul kanaaladres in";
+App::$strings["Examples: bob@example.com, https://example.com/barbara"] = "Voorbeelden: bob@example.com, http://example.com/barbara";
+App::$strings["Notes"] = "Aantekeningen";
+App::$strings["Remove term"] = "Verwijder zoekterm";
+App::$strings["Saved Searches"] = "Opgeslagen zoekopdrachten";
+App::$strings["add"] = "toevoegen";
+App::$strings["Saved Folders"] = "Bewaarde mappen";
+App::$strings["Everything"] = "Alles";
+App::$strings["Archives"] = "Archieven";
+App::$strings["Refresh"] = "Vernieuwen";
+App::$strings["Account settings"] = "Account";
+App::$strings["Channel settings"] = "Kanaal";
+App::$strings["Additional features"] = "Extra functies";
+App::$strings["Feature/Addon settings"] = "Plugin-instellingen";
+App::$strings["Display settings"] = "Weergave";
+App::$strings["Manage locations"] = "Locaties beheren";
+App::$strings["Export channel"] = "Kanaal exporteren";
+App::$strings["Connected apps"] = "Verbonden applicaties";
+App::$strings["Permission Groups"] = "Permissiegroepen";
+App::$strings["Premium Channel Settings"] = "Instellingen premiumkanaal";
+App::$strings["Private Mail Menu"] = "Privéberichten";
+App::$strings["Combined View"] = "Gecombineerd postvak";
+App::$strings["Inbox"] = "Postvak IN";
+App::$strings["Outbox"] = "Postvak UIT";
+App::$strings["New Message"] = "Nieuw bericht";
+App::$strings["Conversations"] = "Conversaties";
+App::$strings["Received Messages"] = "Ontvangen berichten";
+App::$strings["Sent Messages"] = "Verzonden berichten";
+App::$strings["No messages."] = "Geen berichten";
+App::$strings["Delete conversation"] = "Verwijder conversatie";
+App::$strings["Events Tools"] = "Agenda-hulpmiddelen";
+App::$strings["Export Calendar"] = "Exporteren";
+App::$strings["Import Calendar"] = "Importeren";
+App::$strings["Chatrooms"] = "Chatkanalen";
+App::$strings["Overview"] = "Overzicht";
+App::$strings["Chat Members"] = "Chatleden";
+App::$strings["__ctx:wiki_history__ Message"] = "Bericht";
+App::$strings["Bookmarked Chatrooms"] = "Bladwijzers van chatkanalen";
+App::$strings["Suggested Chatrooms"] = "Voorgestelde chatkanalen";
+App::$strings["photo/image"] = "foto/afbeelding";
+App::$strings["Click to show more"] = "Klik voor meer";
+App::$strings["Rating Tools"] = "Beoordelingen";
+App::$strings["Rate Me"] = "Beoordeel mij";
+App::$strings["View Ratings"] = "Bekijk beoordelingen";
+App::$strings["Forums"] = "Forums";
+App::$strings["__ctx:widget__ Activity"] = "Activiteit";
+App::$strings["Tasks"] = "Taken";
+App::$strings["Member registrations waiting for confirmation"] = "Accounts die op goedkeuring wachten";
+App::$strings["Inspect queue"] = "Inspecteer berichtenwachtrij";
+App::$strings["DB updates"] = "Database-updates";
+App::$strings["Admin"] = "Beheer";
+App::$strings["Plugin Features"] = "Plugin-opties";
+App::$strings["Tags"] = "Tags";
+App::$strings["Keywords"] = "Trefwoorden";
+App::$strings["have"] = "heb";
+App::$strings["has"] = "heeft";
+App::$strings["want"] = "wil";
+App::$strings["wants"] = "wil";
+App::$strings["likes"] = "vindt dit leuk";
+App::$strings["dislikes"] = "vindt dit niet leuk";
+App::$strings["l F d, Y \\@ g:i A"] = "l d F Y \\@ G:i";
+App::$strings["Starts:"] = "Start:";
+App::$strings["Finishes:"] = "Einde:";
+App::$strings["This event has been added to your calendar."] = "Dit evenement is aan jouw agenda toegevoegd.";
+App::$strings["Not specified"] = "Niet aangegeven";
+App::$strings["Needs Action"] = "Actie vereist";
+App::$strings["Completed"] = "Voltooid";
+App::$strings["In Process"] = "In behandeling";
+App::$strings["Cancelled"] = "Geannuleerd";
App::$strings["Birthday"] = "Verjaardag of geboortedatum";
App::$strings["Age: "] = "Leeftijd:";
App::$strings["YYYY-MM-DD or MM-DD"] = "JJJJ-MM-DD of MM-DD";
@@ -2335,22 +2497,6 @@ App::$strings["__ctx:relative_date__ second"] = array(
);
App::$strings["%1\$s's birthday"] = "Verjaardag van %1\$s";
App::$strings["Happy Birthday %1\$s"] = "Gefeliciteerd met je verjaardag %1\$s";
-App::$strings["Not a valid email address"] = "Geen geldig e-mailadres";
-App::$strings["Your email domain is not among those allowed on this site"] = "Jouw e-maildomein is op deze hub niet toegestaan";
-App::$strings["Your email address is already registered at this site."] = "Jouw e-mailadres is al op deze hub geregistreerd.";
-App::$strings["An invitation is required."] = "Een uitnodiging is vereist";
-App::$strings["Invitation could not be verified."] = "Uitnodiging kon niet geverifieerd worden";
-App::$strings["Please enter the required information."] = "Vul de vereiste informatie in.";
-App::$strings["Failed to store account information."] = "Account-informatie kon niet opgeslagen worden.";
-App::$strings["Registration confirmation for %s"] = "Registratiebevestiging voor %s";
-App::$strings["Registration request at %s"] = "Registratiebevestiging voor %s";
-App::$strings["your registration password"] = "jouw registratiewachtwoord";
-App::$strings["Registration details for %s"] = "Registratiegegevens voor %s";
-App::$strings["Account approved."] = "Account goedgekeurd";
-App::$strings["Registration revoked for %s"] = "Registratie ingetrokken voor %s";
-App::$strings["Click here to upgrade."] = "Klik hier om te upgraden.";
-App::$strings["This action exceeds the limits set by your subscription plan."] = "Deze handeling overschrijdt de beperkingen die voor jouw abonnement gelden.";
-App::$strings["This action is not available under your subscription plan."] = "Deze handeling is niet mogelijk met jouw abonnement.";
App::$strings["Frequently"] = "Regelmatig";
App::$strings["Hourly"] = "Elk uur";
App::$strings["Twice daily"] = "Twee keer per dag";
@@ -2411,186 +2557,26 @@ App::$strings["Uncertain"] = "Onzeker";
App::$strings["It's complicated"] = "Het is ingewikkeld";
App::$strings["Don't care"] = "Maakt mij niks uit";
App::$strings["Ask me"] = "Vraag het me";
-App::$strings["Unable to obtain identity information from database"] = "Niet in staat om identiteitsinformatie uit de database te verkrijgen";
-App::$strings["Empty name"] = "Ontbrekende naam";
-App::$strings["Name too long"] = "Naam te lang";
-App::$strings["No account identifier"] = "Geen account-identificator";
-App::$strings["Nickname is required."] = "Bijnaam is verplicht";
-App::$strings["Reserved nickname. Please choose another."] = "Deze naam is gereserveerd. Kies een andere.";
-App::$strings["Nickname has unsupported characters or is already being used on this site."] = "Deze naam heeft niet ondersteunde karakters of is al op deze hub in gebruik.";
-App::$strings["Unable to retrieve created identity"] = "Niet in staat om aangemaakte identiteit te vinden";
-App::$strings["Default Profile"] = "Standaardprofiel";
-App::$strings["Create New Profile"] = "Nieuw profiel aanmaken";
-App::$strings["Visible to everybody"] = "Voor iedereen zichtbaar";
-App::$strings["Gender:"] = "Geslacht:";
-App::$strings["Homepage:"] = "Homepagina:";
-App::$strings["Online Now"] = "Nu online";
-App::$strings["Like this channel"] = "Vind dit kanaal leuk";
-App::$strings["j F, Y"] = "F j Y";
-App::$strings["j F"] = "F j";
-App::$strings["Birthday:"] = "Geboortedatum:";
-App::$strings["for %1\$d %2\$s"] = "voor %1\$d %2\$s";
-App::$strings["Sexual Preference:"] = "Seksuele voorkeur:";
-App::$strings["Tags:"] = "Tags:";
-App::$strings["Political Views:"] = "Politieke overtuigingen:";
-App::$strings["Religion:"] = "Religie:";
-App::$strings["Hobbies/Interests:"] = "Hobby's/interesses:";
-App::$strings["Likes:"] = "Houdt van:";
-App::$strings["Dislikes:"] = "Houdt niet van:";
-App::$strings["Contact information and Social Networks:"] = "Contactinformatie en sociale netwerken:";
-App::$strings["My other channels:"] = "Mijn andere kanalen";
-App::$strings["Musical interests:"] = "Muzikale interesses:";
-App::$strings["Books, literature:"] = "Boeken, literatuur:";
-App::$strings["Television:"] = "Televisie:";
-App::$strings["Film/dance/culture/entertainment:"] = "Films/dansen/cultuur/vermaak:";
-App::$strings["Love/Romance:"] = "Liefde/romantiek:";
-App::$strings["Work/employment:"] = "Werk/beroep:";
-App::$strings["School/education:"] = "School/opleiding:";
-App::$strings["Like this thing"] = "Vind dit ding leuk";
+App::$strings["Who can see this?"] = "Wie kan dit zien?";
+App::$strings["Custom selection"] = "Handmatige selectie";
+App::$strings["Select \"Show\" to allow viewing. \"Don't show\" lets you override and limit the scope of \"Show\"."] = "Kies \"Tonen\" om weergave toe te staan. Met \"Niet tonen\" kan je uitzonderingen maken op \"Tonen\".";
+App::$strings["Show"] = "Tonen";
+App::$strings["Don't show"] = "Niet tonen";
+App::$strings["Post permissions %s cannot be changed %s after a post is shared.</br />These permissions set who is allowed to view the post."] = "Permissies van berichten %s zijn niet meer te veranderen %s nadat een bericht is gedeeld.</br />Met deze permissies bepaal je wie het bericht kan zien.";
+App::$strings["Image/photo"] = "Afbeelding/foto";
+App::$strings["Encrypted content"] = "Versleutelde inhoud";
+App::$strings["Install %s element: "] = "Installeer %s-element: ";
+App::$strings["This post contains an installable %s element, however you lack permissions to install it on this site."] = "Dit bericht heeft een te installeren %s-element, maar je hebt geen permissies om het op deze hub te installeren.";
+App::$strings["%1\$s wrote the following %2\$s %3\$s"] = "%1\$s schreef het volgende %2\$s %3\$s";
+App::$strings["Click to open/close"] = "Klik om te openen of te sluiten";
+App::$strings["spoiler"] = "spoiler";
+App::$strings["$1 wrote:"] = "$1 schreef:";
+App::$strings["%1\$s's bookmarks"] = "Bladwijzers van %1\$s";
App::$strings["New window"] = "Nieuw venster";
App::$strings["Open the selected location in a different window or browser tab"] = "Open de geselecteerde locatie in een ander venster of tab";
-App::$strings["User '%s' deleted"] = "Account '%s' verwijderd";
-App::$strings["Directory Options"] = "Opties kanalengids";
-App::$strings["Safe Mode"] = "Veilig zoeken";
-App::$strings["Public Forums Only"] = "Alleen openbare forums";
-App::$strings["This Website Only"] = "Alleen deze hub";
-App::$strings["Logout"] = "Uitloggen";
-App::$strings["End this session"] = "Beëindig deze sessie";
-App::$strings["Your posts and conversations"] = "Jouw kanaal";
-App::$strings["Your profile page"] = "Jouw profielpagina";
-App::$strings["Manage/Edit profiles"] = "Beheer/wijzig profielen";
-App::$strings["Edit your profile"] = "Jouw profiel bewerken";
-App::$strings["Your photos"] = "Jouw foto's";
-App::$strings["Your files"] = "Jouw bestanden";
-App::$strings["Your chatrooms"] = "Jouw chatkanalen";
-App::$strings["Bookmarks"] = "Bladwijzers";
-App::$strings["Your bookmarks"] = "Jouw bladwijzers";
-App::$strings["Your webpages"] = "Jouw webpagina's";
-App::$strings["Your wikis"] = "Jouw wiki's";
-App::$strings["Sign in"] = "Inloggen";
-App::$strings["Remote authentication"] = "Authenticatie op afstand";
-App::$strings["Click to authenticate to your home hub"] = "Authenticeer jezelf via (bijvoorbeeld) jouw hub";
-App::$strings["Get me home"] = "Terug naar mijn hub";
-App::$strings["Log me out of this site"] = "Uitloggen op deze hub";
-App::$strings["Create an account"] = "Maak een account aan";
-App::$strings["Help and documentation"] = "Hulp en documentatie";
-App::$strings["Applications, utilities, links, games"] = "Apps";
-App::$strings["Search site @name, #tag, ?docs, content"] = "Zoek een @kanaal, doorzoek inhoud hub met tekst en #tags, of doorzoek ?documentatie ";
-App::$strings["Channel Directory"] = "Kanalengids";
-App::$strings["Your grid"] = "Jouw grid";
-App::$strings["Mark all grid notifications seen"] = "Markeer alle gridnotificaties als bekeken";
-App::$strings["Channel home"] = "Jouw kanaal";
-App::$strings["Mark all channel notifications seen"] = "Alle kanaalnotificaties als gelezen markeren";
-App::$strings["Notices"] = "Notificaties";
-App::$strings["Notifications"] = "Notificaties";
-App::$strings["See all notifications"] = "Alle notificaties weergeven";
-App::$strings["Private mail"] = "Privéberichten";
-App::$strings["See all private messages"] = "Alle privéberichten weergeven";
-App::$strings["Mark all private messages seen"] = "Markeer alle privéberichten als bekeken";
-App::$strings["Inbox"] = "Postvak IN";
-App::$strings["Outbox"] = "Postvak UIT";
-App::$strings["New Message"] = "Nieuw bericht";
-App::$strings["Event Calendar"] = "Agenda";
-App::$strings["See all events"] = "Alle gebeurtenissen weergeven";
-App::$strings["Mark all events seen"] = "Markeer alle gebeurtenissen als bekeken";
-App::$strings["Manage Your Channels"] = "Beheer je kanalen";
-App::$strings["Account/Channel Settings"] = "Account-/kanaal-instellingen";
-App::$strings["Admin"] = "Beheer";
-App::$strings["Site Setup and Configuration"] = "Hub instellen en beheren";
-App::$strings["Loading..."] = "Aan het laden...";
-App::$strings["@name, #tag, ?doc, content"] = "@kanaal, #tag, inhoud, ?hulp";
-App::$strings["Please wait..."] = "Wachten aub...";
-App::$strings["General Features"] = "Algemene functies";
-App::$strings["Multiple Profiles"] = "Meerdere profielen";
-App::$strings["Ability to create multiple profiles"] = "Mogelijkheid om meerdere profielen aan te maken";
-App::$strings["Advanced Profiles"] = "Geavanceerde profielen";
-App::$strings["Additional profile sections and selections"] = "Extra onderdelen en keuzes voor je profiel";
-App::$strings["Profile Import/Export"] = "Profiel importen/exporteren";
-App::$strings["Save and load profile details across sites/channels"] = "Profielgegevens opslaan en in andere hubs/kanalen gebruiken.";
-App::$strings["Web Pages"] = "Webpagina's";
-App::$strings["Provide managed web pages on your channel"] = "Sta beheerde webpagina's op jouw kanaal toe";
-App::$strings["Provide a wiki for your channel"] = "Voeg een wiki aan jouw kanaal toe";
-App::$strings["Private Notes"] = "Privé-aantekeningen";
-App::$strings["Enables a tool to store notes and reminders (note: not encrypted)"] = "Een eenvoudige toepassing om aantekeningen en herinneringen in te bewaren (let op: niet versleuteld)";
-App::$strings["Navigation Channel Select"] = "Kanaal kiezen in navigatiemenu";
-App::$strings["Change channels directly from within the navigation dropdown menu"] = "Kies een ander kanaal direct vanuit het dropdown-menu op de navigatiebalk";
-App::$strings["Photo Location"] = "Fotolocatie";
-App::$strings["If location data is available on uploaded photos, link this to a map."] = "Wanneer in de geüploade foto's locatiegegevens aanwezig zijn, link dit dan aan een kaart.";
-App::$strings["Access Controlled Chatrooms"] = "Chatkanalen met toegangscontrole ";
-App::$strings["Provide chatrooms and chat services with access control."] = "Chatkanalen en chatdiensten met toegangscontrole aanbieden.";
-App::$strings["Smart Birthdays"] = "Slimme verjaardagen";
-App::$strings["Make birthday events timezone aware in case your friends are scattered across the planet."] = "Maak verjaardagen bewust van tijdzones. Voor het geval dat jouw vrienden over de hele wereld verspreid zijn.";
-App::$strings["Advanced Directory Search"] = "Geavanceerd in de kanalengids zoeken";
-App::$strings["Allows creation of complex directory search queries"] = "Gebruik complexe zoekopdrachten in de kanalengids";
-App::$strings["Advanced Theme and Layout Settings"] = "Geavanceerde thema- en lay-out-instellingen";
-App::$strings["Allows fine tuning of themes and page layouts"] = "Maakt het mogelijk dat thema's en pagina-lay-outs preciezer ingesteld kunnen worden ";
-App::$strings["Post Composition Features"] = "Functies voor het opstellen van berichten";
-App::$strings["Large Photos"] = "Grote foto's";
-App::$strings["Include large (1024px) photo thumbnails in posts. If not enabled, use small (640px) photo thumbnails"] = "Gebruik grotere foto's (1024px) in berichten. Wanneer dit is uitgeschakeld worden er kleinere foto's (640px) gebruikt.";
-App::$strings["Automatically import channel content from other channels or feeds"] = "Automatisch inhoud uit andere kanalen of feeds importeren.";
-App::$strings["Even More Encryption"] = "Extra encryptie";
-App::$strings["Allow optional encryption of content end-to-end with a shared secret key"] = "Sta toe dat inhoud extra end-to-end wordt versleuteld met een gedeelde geheime sleutel.";
-App::$strings["Enable Voting Tools"] = "Peilingen inschakelen";
-App::$strings["Provide a class of post which others can vote on"] = "Maakt het mogelijk om een bericht op te stellen, waar mensen op kunnen stemmen.";
-App::$strings["Disable Comments"] = "Reacties uitschakelen";
-App::$strings["Provide the option to disable comments for a post"] = "Maak het mogelijk dat reacties op een bericht kunnen worden uitgeschakeld";
-App::$strings["Delayed Posting"] = "Berichten uitstellen";
-App::$strings["Allow posts to be published at a later date"] = "Maakt het mogelijk dat berichten op een toekomstig moment gepubliceerd kunnen worden.";
-App::$strings["Content Expiration"] = "Inhoud laten verlopen";
-App::$strings["Remove posts/comments and/or private messages at a future time"] = "Berichten, reacties en/of privéberichten na een bepaalde tijd verwijderen";
-App::$strings["Suppress Duplicate Posts/Comments"] = "Dubbele berichten/reacties tegenhouden";
-App::$strings["Prevent posts with identical content to be published with less than two minutes in between submissions."] = "Voorkomt dat berichten en reacties met identieke inhoud en die binnen twee minuten zijn verstuurd, worden gepubliceerd. ";
-App::$strings["Network and Stream Filtering"] = "Netwerk- en streamfilter";
-App::$strings["Search by Date"] = "Zoek op datum";
-App::$strings["Ability to select posts by date ranges"] = "Mogelijkheid om berichten op datum te filteren ";
-App::$strings["Privacy Groups"] = "Privacygroepen";
-App::$strings["Enable management and selection of privacy groups"] = "Beheer en selectie van privacygroepen inschakelen";
-App::$strings["Saved Searches"] = "Opgeslagen zoekopdrachten";
-App::$strings["Save search terms for re-use"] = "Sla zoekopdrachten op voor hergebruik";
-App::$strings["Network Personal Tab"] = "Persoonlijke netwerktab";
-App::$strings["Enable tab to display only Network posts that you've interacted on"] = "Sta het toe dat de tab netwerkberichten toont waarmee je interactie had";
-App::$strings["Network New Tab"] = "Nieuwe netwerktab";
-App::$strings["Enable tab to display all new Network activity"] = "Laat de tab alle nieuwe netwerkactiviteit tonen";
-App::$strings["Affinity Tool"] = "Verwantschapsfilter";
-App::$strings["Filter stream activity by depth of relationships"] = "Filter wat je in jouw grid ziet op hoe goed je iemand kent of mag";
-App::$strings["Show friend and connection suggestions"] = "Toon kanaalvoorstellen";
-App::$strings["Connection Filtering"] = "Berichtenfilters";
-App::$strings["Filter incoming posts from connections based on keywords/content"] = "Filter binnenkomende berichten van connecties aan de hand van trefwoorden en taal";
-App::$strings["Post/Comment Tools"] = "Bericht- en reactiehulpmiddelen";
-App::$strings["Community Tagging"] = "Taggen door anderen";
-App::$strings["Ability to tag existing posts"] = "Geeft andere mensen de mogelijkheid om jouw (bestaande) berichten te taggen";
-App::$strings["Post Categories"] = "Categorieën berichten";
-App::$strings["Add categories to your posts"] = "Voeg categorieën toe aan je berichten";
-App::$strings["Emoji Reactions"] = "Emoji-reacties";
-App::$strings["Add emoji reaction ability to posts"] = "Emoji-reacties in berichten toestaan";
-App::$strings["Saved Folders"] = "Bewaarde mappen";
-App::$strings["Ability to file posts under folders"] = "Mogelijkheid om berichten in mappen op te slaan";
-App::$strings["Dislike Posts"] = "Vind berichten niet leuk";
-App::$strings["Ability to dislike posts/comments"] = "Mogelijkheid om berichten en reacties niet leuk te vinden";
-App::$strings["Star Posts"] = "Geef berichten een ster";
-App::$strings["Ability to mark special posts with a star indicator"] = "Mogelijkheid om speciale berichten met een ster te markeren";
-App::$strings["Tag Cloud"] = "Tagwolk";
-App::$strings["Provide a personal tag cloud on your channel page"] = "Zorgt voor een persoonlijke wolk met tags op jouw kanaalpagina";
-App::$strings["Premium Channel"] = "Premiumkanaal";
-App::$strings["Allows you to set restrictions and terms on those that connect with your channel"] = "Stelt je in staat om beperkingen en voorwaarden in te stellen voor jouw kanaal";
-App::$strings["Attachments:"] = "Bijlagen:";
-App::$strings["l F d, Y \\@ g:i A"] = "l d F Y \\@ G:i";
-App::$strings["\$Projectname event notification:"] = "Notificatie \$Projectname-gebeurtenis:";
-App::$strings["Starts:"] = "Start:";
-App::$strings["Finishes:"] = "Einde:";
-App::$strings["%1\$s's bookmarks"] = "Bladwijzers van %1\$s";
App::$strings["Help:"] = "Hulp:";
App::$strings["Not Found"] = "Niet gevonden";
-App::$strings["Different viewers will see this text differently"] = "Deze tekst wordt per persoon anders weergeven.";
-App::$strings["Invalid data packet"] = "Datapakket ongeldig";
-App::$strings["Unable to verify channel signature"] = "Kanaalkenmerk kon niet worden geverifieerd. ";
-App::$strings["Unable to verify site signature for %s"] = "Hubkenmerk voor %s kon niet worden geverifieerd";
-App::$strings["invalid target signature"] = "ongeldig doelkenmerk";
App::$strings["New Page"] = "Nieuwe pagina";
-App::$strings["Unable to determine sender."] = "Afzender kan niet bepaald worden.";
-App::$strings["No recipient provided."] = "Geen ontvanger opgegeven.";
-App::$strings["[no subject]"] = "[geen onderwerp]";
-App::$strings["Stored post could not be verified."] = "Opgeslagen bericht kon niet worden geverifieerd.";
App::$strings["%d invitation available"] = array(
0 => "%d uitnodiging beschikbaar",
1 => "%d uitnodigingen beschikbaar",
@@ -2602,8 +2588,6 @@ App::$strings["Examples: Robert Morgenstein, Fishing"] = "Voorbeeld: Robert Morg
App::$strings["Random Profile"] = "Willekeurig profiel";
App::$strings["Invite Friends"] = "Vrienden uitnodigen";
App::$strings["Advanced example: name=fred and country=iceland"] = "Geavanceerd voorbeeld (Engels): name=jan en country=nederland";
-App::$strings["Everything"] = "Alles";
-App::$strings["Categories"] = "Categorieën";
App::$strings["%d connection in common"] = array(
0 => "%d gemeenschappelijke connectie",
1 => "%d gemeenschappelijke connecties",
@@ -2622,7 +2606,7 @@ App::$strings["Notice: Permissions have changed but have not yet been submitted.
App::$strings["close all"] = "Alles sluiten";
App::$strings["Nothing new here"] = "Niets nieuw hier";
App::$strings["Rate This Channel (this is public)"] = "Beoordeel dit kanaal (dit is openbaar)";
-App::$strings["Describe (optional)"] = "Omschrijving (optioneel)";
+App::$strings["Describe (optional)"] = "Omschrijving (niet verplicht)";
App::$strings["Please enter a link URL"] = "Vul een URL in:";
App::$strings["Unsaved changes. Are you sure you wish to leave this page?"] = "Niet opgeslagen wijzigingen. Ben je er zeker van dat je deze pagina wil verlaten?";
App::$strings["timeago.prefixAgo"] = "timeago.prefixAgo";
@@ -2685,214 +2669,10 @@ App::$strings["__ctx:calendar__ month"] = "maand";
App::$strings["__ctx:calendar__ week"] = "week";
App::$strings["__ctx:calendar__ day"] = "dag";
App::$strings["__ctx:calendar__ All day"] = "hele dag";
-App::$strings["Tags"] = "Tags";
-App::$strings["Keywords"] = "Trefwoorden";
-App::$strings["have"] = "heb";
-App::$strings["has"] = "heeft";
-App::$strings["want"] = "wil";
-App::$strings["wants"] = "wil";
-App::$strings["likes"] = "vindt dit leuk";
-App::$strings["dislikes"] = "vindt dit niet leuk";
-App::$strings["prev"] = "vorige";
-App::$strings["first"] = "eerste";
-App::$strings["last"] = "laatste";
-App::$strings["next"] = "volgende";
-App::$strings["older"] = "ouder";
-App::$strings["newer"] = "nieuwer";
-App::$strings["No connections"] = "Geen connecties";
-App::$strings["View all %s connections"] = "Toon alle %s connecties";
-App::$strings["poke"] = "aanstoten";
-App::$strings["poked"] = "aangestoten";
-App::$strings["ping"] = "ping";
-App::$strings["pinged"] = "gepingd";
-App::$strings["prod"] = "por";
-App::$strings["prodded"] = "gepord";
-App::$strings["slap"] = "slaan";
-App::$strings["slapped"] = "sloeg";
-App::$strings["finger"] = "finger";
-App::$strings["fingered"] = "gefingerd";
-App::$strings["rebuff"] = "afpoeieren";
-App::$strings["rebuffed"] = "afgepoeierd";
-App::$strings["happy"] = "gelukkig";
-App::$strings["sad"] = "bedroefd";
-App::$strings["mellow"] = "mellow";
-App::$strings["tired"] = "moe";
-App::$strings["perky"] = "parmantig";
-App::$strings["angry"] = "boos";
-App::$strings["stupefied"] = "verbijsterd";
-App::$strings["puzzled"] = "verward";
-App::$strings["interested"] = "geïnteresseerd";
-App::$strings["bitter"] = "verbitterd";
-App::$strings["cheerful"] = "vrolijk";
-App::$strings["alive"] = "levendig";
-App::$strings["annoyed"] = "geërgerd";
-App::$strings["anxious"] = "bezorgd";
-App::$strings["cranky"] = "humeurig";
-App::$strings["disturbed"] = "verontrust";
-App::$strings["frustrated"] = "gefrustreerd ";
-App::$strings["depressed"] = "gedeprimeerd";
-App::$strings["motivated"] = "gemotiveerd";
-App::$strings["relaxed"] = "ontspannen";
-App::$strings["surprised"] = "verrast";
-App::$strings["May"] = "mei";
-App::$strings["Unknown Attachment"] = "Onbekende bijlage";
-App::$strings["unknown"] = "onbekend";
-App::$strings["remove category"] = "categorie verwijderen";
-App::$strings["remove from file"] = "uit map verwijderen";
-App::$strings["default"] = "standaard";
-App::$strings["Page layout"] = "Pagina-lay-out";
-App::$strings["You can create your own with the layouts tool"] = "Je kan jouw eigen lay-out ontwerpen onder lay-outs";
-App::$strings["Page content type"] = "Opmaaktype";
-App::$strings["activity"] = "activiteit";
-App::$strings["Design Tools"] = "Ontwerp-hulpmiddelen";
-App::$strings["Pages"] = "Pagina's";
-App::$strings["Import website..."] = "Website importeren...";
-App::$strings["Select folder to import"] = "Kies een map om te importeren";
-App::$strings["Import from a zipped folder:"] = "Vanuit een zipbestand importeren:";
-App::$strings["Import from cloud files:"] = "Vanuit de cloud importeren:";
-App::$strings["/cloud/channel/path/to/folder"] = "/cloud/channel/maplocatie";
-App::$strings["Enter path to website files"] = "Voer de locatie in van de websitebestanden";
-App::$strings["Select folder"] = "Kies een map";
-App::$strings["Export website..."] = "Website exporteren...";
-App::$strings["Export to a zip file"] = "Naar een zipbestand exporteren";
-App::$strings["website.zip"] = "website.zip";
-App::$strings["Enter a name for the zip file."] = "Vul een naam in voor het zipbestand.";
-App::$strings["Export to cloud files"] = "Naar de cloud exporteren";
-App::$strings["/path/to/export/folder"] = "/locatie/van/export/map";
-App::$strings["Enter a path to a cloud files destination."] = "Voer de locatie in van de cloudbestemming";
-App::$strings["Specify folder"] = "Selecteer een map";
-App::$strings["Cannot create a duplicate channel identifier on this system. Import failed."] = "Kan geen dubbele kanaal-identificator op deze hub aanmaken. Importeren mislukt.";
-App::$strings["Channel clone failed. Import failed."] = "Het klonen van het kanaal is mislukt. Importeren mislukt.";
-App::$strings["Unable to import element \""] = "Niet in staat om dit element te importeren: \"";
-App::$strings["guest:"] = "gast:";
-App::$strings["The form security token was not correct. This probably happened because the form has been opened for too long (>3 hours) before submitting it."] = "De beveiligings-token van het tekstvak was ongeldig. Dit is mogelijk het gevolg van dat er te lang (meer dan 3 uur) gewacht is om de tekst op te slaan. ";
-App::$strings["(Unknown)"] = "(Onbekend)";
-App::$strings["Visible to anybody on the internet."] = "Voor iedereen op het internet zichtbaar.";
-App::$strings["Visible to you only."] = "Alleen voor jou zichtbaar.";
-App::$strings["Visible to anybody in this network."] = "Voor iedereen in dit netwerk zichtbaar.";
-App::$strings["Visible to anybody authenticated."] = "Voor iedereen die geauthenticeerd is zichtbaar.";
-App::$strings["Visible to anybody on %s."] = "Voor iedereen op %s zichtbaar.";
-App::$strings["Visible to all connections."] = "Voor alle connecties zichtbaar.";
-App::$strings["Visible to approved connections."] = "Voor alle geaccepteerde connecties zichtbaar.";
-App::$strings["Visible to specific connections."] = "Voor specifieke connecties zichtbaar.";
-App::$strings["Privacy group is empty."] = "Privacygroep is leeg";
-App::$strings["Privacy group: %s"] = "Privacygroep: %s";
-App::$strings["Connection not found."] = "Connectie niet gevonden.";
-App::$strings["profile photo"] = "profielfoto";
-App::$strings["[Edited %s]"] = "[%s bewerkt]";
-App::$strings["__ctx:edit_activity__ Post"] = "Bericht";
-App::$strings["__ctx:edit_activity__ Comment"] = "Reactie";
-App::$strings["Logged out."] = "Uitgelogd.";
-App::$strings["Failed authentication"] = "Mislukte authenticatie";
-App::$strings[" and "] = " en ";
-App::$strings["public profile"] = "openbaar profiel";
-App::$strings["%1\$s changed %2\$s to &ldquo;%3\$s&rdquo;"] = "%1\$s veranderde %2\$s naar &ldquo;%3\$s&rdquo;";
-App::$strings["Visit %1\$s's %2\$s"] = "Bezoek het %2\$s van %1\$s";
-App::$strings["%1\$s has an updated %2\$s, changing %3\$s."] = "%1\$s heeft een aangepaste %2\$s, %3\$s veranderd.";
-App::$strings["Item was not found."] = "Item niet gevonden";
-App::$strings["No source file."] = "Geen bronbestand.";
-App::$strings["Cannot locate file to replace"] = "Kan het te vervangen bestand niet vinden";
-App::$strings["Cannot locate file to revise/update"] = "Kan het bestand wat aangepast moet worden niet vinden";
-App::$strings["File exceeds size limit of %d"] = "Bestand is groter dan de toegelaten %d";
-App::$strings["You have reached your limit of %1$.0f Mbytes attachment storage."] = "Je hebt jouw limiet van %1$.0f MB opslagruimte voor bijlagen bereikt.";
-App::$strings["File upload failed. Possible system limit or action terminated."] = "Uploaden van bestand mislukt. Mogelijk systeemlimiet bereikt of actie afgebroken.";
-App::$strings["Stored file could not be verified. Upload failed."] = "Opgeslagen bestand kon niet worden geverifieerd. Uploaden mislukt.";
-App::$strings["Path not available."] = "Locatie niet beschikbaar.";
-App::$strings["Empty pathname"] = "Ontbrekende locatienaam";
-App::$strings["duplicate filename or path"] = "dubbele bestandsnaam of locatie";
-App::$strings["Path not found."] = "Locatie niet gevonden";
-App::$strings["mkdir failed."] = "directory aanmaken (mkdir) mislukt.";
-App::$strings["database storage failed."] = "opslag in database mislukt.";
-App::$strings["Empty path"] = "Ontbrekende locatie";
-App::$strings["This event has been added to your calendar."] = "Dit evenement is aan jouw agenda toegevoegd.";
-App::$strings["Not specified"] = "Niet aangegeven";
-App::$strings["Needs Action"] = "Actie vereist";
-App::$strings["Completed"] = "Voltooid";
-App::$strings["In Process"] = "In behandeling";
-App::$strings["Cancelled"] = "Geannuleerd";
-App::$strings["Channel is blocked on this site."] = "Kanaal is op deze hub geblokkeerd.";
-App::$strings["Channel location missing."] = "Ontbrekende kanaallocatie.";
-App::$strings["Response from remote channel was incomplete."] = "Antwoord van het kanaal op afstand was niet volledig.";
-App::$strings["Channel was deleted and no longer exists."] = "Kanaal is verwijderd en bestaat niet meer.";
-App::$strings["Protocol disabled."] = "Protocol uitgeschakeld.";
-App::$strings["Channel discovery failed."] = "Kanaal ontdekken mislukt.";
-App::$strings["Cannot connect to yourself."] = "Kan niet met jezelf verbinden";
-App::$strings["A deleted group with this name was revived. Existing item permissions <strong>may</strong> apply to this group and any future members. If this is not what you intended, please create another group with a different name."] = "Een verwijderde collectie met deze naam is gereactiveerd. Bestaande itemrechten <strong>kunnen</strong> van toepassing zijn op deze collectie en toekomstige leden. Wanneer je dit niet zo bedoeld hebt, moet je een nieuwe collectie met een andere naam aanmaken.";
-App::$strings["Add new connections to this privacy group"] = "Voeg nieuwe connecties aan deze privacygroep toe";
-App::$strings["edit"] = "bewerken";
-App::$strings["Edit group"] = "Privacygroep bewerken";
-App::$strings["Add privacy group"] = "Privacygroep toevoegen";
-App::$strings["Channels not in any privacy group"] = "Kanalen die zich in geen enkele privacygroep bevinden";
-App::$strings["add"] = "toevoegen";
-App::$strings["Select an alternate language"] = "Kies een andere taal";
-App::$strings["Image exceeds website size limit of %lu bytes"] = "Afbeelding is groter dan op deze hub toegestane limiet van %lu bytes";
-App::$strings["Image file is empty."] = "Afbeeldingsbestand is leeg";
-App::$strings["Photo storage failed."] = "Foto kan niet worden opgeslagen";
-App::$strings["a new photo"] = "een nieuwe foto";
-App::$strings["__ctx:photo_upload__ %1\$s posted %2\$s to %3\$s"] = "%1\$s plaatste %2\$s op %3\$s";
-App::$strings["Photo Albums"] = "Fotoalbums";
-App::$strings["Upload New Photos"] = "Nieuwe foto's uploaden";
-App::$strings["Who can see this?"] = "Wie kan dit zien?";
-App::$strings["Custom selection"] = "Handmatige selectie";
-App::$strings["Select \"Show\" to allow viewing. \"Don't show\" lets you override and limit the scope of \"Show\"."] = "Kies \"Tonen\" om weergave toe te staan. Met \"Niet tonen\" kan je uitzonderingen maken op \"Tonen\".";
-App::$strings["Show"] = "Tonen";
-App::$strings["Don't show"] = "Niet tonen";
-App::$strings["Post permissions %s cannot be changed %s after a post is shared.</br />These permissions set who is allowed to view the post."] = "Permissies van berichten %s zijn niet meer te veranderen %s nadat een bericht is gedeeld.</br />Met deze permissies bepaal je wie het bericht kan zien.";
-App::$strings[" by "] = " door ";
-App::$strings[" on "] = " op ";
-App::$strings["Embedded content"] = "Ingesloten (embedded) inhoud";
-App::$strings["Embedding disabled"] = "Insluiten (embedding) uitgeschakeld";
-App::$strings["System"] = "Systeem";
-App::$strings["New App"] = "Nieuwe app";
-App::$strings["Suggestions"] = "Voorgestelde kanalen";
-App::$strings["See more..."] = "Meer...";
-App::$strings["You have %1$.0f of %2$.0f allowed connections."] = "Je hebt %1$.0f van de %2$.0f toegestane connecties.";
-App::$strings["Add New Connection"] = "Nieuwe connectie toevoegen";
-App::$strings["Enter channel address"] = "Vul kanaaladres in";
-App::$strings["Examples: bob@example.com, https://example.com/barbara"] = "Voorbeelden: bob@example.com, http://example.com/barbara";
-App::$strings["Notes"] = "Aantekeningen";
-App::$strings["Remove term"] = "Verwijder zoekterm";
-App::$strings["Archives"] = "Archieven";
-App::$strings["Refresh"] = "Vernieuwen";
-App::$strings["Account settings"] = "Account";
-App::$strings["Channel settings"] = "Kanaal";
-App::$strings["Additional features"] = "Extra functies";
-App::$strings["Feature/Addon settings"] = "Plugin-instellingen";
-App::$strings["Display settings"] = "Weergave";
-App::$strings["Manage locations"] = "Locaties beheren";
-App::$strings["Export channel"] = "Kanaal exporteren";
-App::$strings["Connected apps"] = "Verbonden applicaties";
-App::$strings["Premium Channel Settings"] = "Instellingen premiumkanaal";
-App::$strings["Private Mail Menu"] = "Privéberichten";
-App::$strings["Combined View"] = "Gecombineerd postvak";
-App::$strings["Conversations"] = "Conversaties";
-App::$strings["Received Messages"] = "Ontvangen berichten";
-App::$strings["Sent Messages"] = "Verzonden berichten";
-App::$strings["No messages."] = "Geen berichten";
-App::$strings["Delete conversation"] = "Verwijder conversatie";
-App::$strings["Events Tools"] = "Agenda-hulpmiddelen";
-App::$strings["Export Calendar"] = "Exporteren";
-App::$strings["Import Calendar"] = "Importeren";
-App::$strings["Chatrooms"] = "Chatkanalen";
-App::$strings["Overview"] = "Overzicht";
-App::$strings["Chat Members"] = "Chatleden";
-App::$strings["Wiki List"] = "Wiki's";
-App::$strings["Wiki Pages"] = "Wikipagina's";
-App::$strings["Add new page"] = "Nieuwe pagina toevoegen";
-App::$strings["Page name"] = "Paginanaam";
-App::$strings["Bookmarked Chatrooms"] = "Bladwijzers van chatkanalen";
-App::$strings["Suggested Chatrooms"] = "Voorgestelde chatkanalen";
-App::$strings["photo/image"] = "foto/afbeelding";
-App::$strings["Click to show more"] = "Klik voor meer";
-App::$strings["Rating Tools"] = "Beoordelingen";
-App::$strings["Rate Me"] = "Beoordeel mij";
-App::$strings["View Ratings"] = "Bekijk beoordelingen";
-App::$strings["Forums"] = "Forums";
-App::$strings["Tasks"] = "Taken";
-App::$strings["Member registrations waiting for confirmation"] = "Accounts die op goedkeuring wachten";
-App::$strings["Inspect queue"] = "Inspecteer berichtenwachtrij";
-App::$strings["DB updates"] = "Database-updates";
-App::$strings["Plugin Features"] = "Plugin-opties";
+App::$strings["Directory Options"] = "Opties kanalengids";
+App::$strings["Safe Mode"] = "Veilig zoeken";
+App::$strings["Public Forums Only"] = "Alleen openbare forums";
+App::$strings["This Website Only"] = "Alleen deze hub";
App::$strings["view full size"] = "volledige grootte tonen";
App::$strings["No Subject"] = "Geen onderwerp";
App::$strings["OStatus"] = "OStatus";
@@ -2903,26 +2683,15 @@ App::$strings["Zot"] = "Zot";
App::$strings["LinkedIn"] = "LinkedIn";
App::$strings["XMPP/IM"] = "XMPP/IM";
App::$strings["MySpace"] = "MySpace";
-App::$strings["Can view my normal stream and posts"] = "Kan mijn normale kanaalstream en berichten bekijken";
-App::$strings["Can view my webpages"] = "Kan mijn pagina's bekijken";
-App::$strings["Can post on my channel page (\"wall\")"] = "Kan een bericht in mijn kanaal plaatsen";
-App::$strings["Can like/dislike stuff"] = "Kan dingen leuk of niet leuk vinden";
-App::$strings["Profiles and things other than posts/comments"] = "Profielen en dingen, buiten berichten en reacties";
-App::$strings["Can forward to all my channel contacts via post @mentions"] = "Kan naar al mijn kanaalconnecties berichten doorsturen met behulp van @vermeldingen+";
-App::$strings["Advanced - useful for creating group forum channels"] = "Geavanceerd - nuttig voor groepforums";
-App::$strings["Can chat with me (when available)"] = "Kan met mij chatten (wanneer beschikbaar)";
-App::$strings["Can write to my file storage and photos"] = "Kan foto's en andere bestanden aan mijn bestandsopslag toevoegen";
-App::$strings["Can edit my webpages"] = "Kan mijn pagina's bewerken";
-App::$strings["Somewhat advanced - very useful in open communities"] = "Enigszins geavanceerd (erg nuttig voor kanalen van forums/groepen)";
-App::$strings["Can administer my channel resources"] = "Kan mijn kanaal beheren";
-App::$strings["Extremely advanced. Leave this alone unless you know what you are doing"] = "Zeer geavanceerd. Laat dit met rust, behalve als je weet wat je doet.";
App::$strings["%1\$s is now connected with %2\$s"] = "%1\$s is nu met %2\$s verbonden";
App::$strings["%1\$s poked %2\$s"] = "%1\$s heeft %2\$s aangestoten";
+App::$strings["poked"] = "aangestoten";
App::$strings["View %s's profile @ %s"] = "Bekijk het profiel van %s @ %s";
App::$strings["Categories:"] = "Categorieën:";
App::$strings["Filed under:"] = "Bewaard onder:";
App::$strings["View in context"] = "In context bekijken";
App::$strings["remove"] = "verwijderen";
+App::$strings["Loading..."] = "Aan het laden...";
App::$strings["Delete Selected Items"] = "Verwijder de geselecteerde items";
App::$strings["View Source"] = "Bron weergeven";
App::$strings["Follow Thread"] = "Conversatie volgen";
@@ -2959,7 +2728,7 @@ App::$strings["Post as"] = "Bericht plaatsen als";
App::$strings["Toggle voting"] = "Peiling in- of uitschakelen";
App::$strings["Disable comments"] = "Reacties uitschakelen";
App::$strings["Toggle comments"] = "Reacties in- of uitschakelen";
-App::$strings["Categories (optional, comma-separated list)"] = "Categorieën (optioneel, door komma's gescheiden lijst)";
+App::$strings["Categories (optional, comma-separated list)"] = "Categorieën (niet verplicht, door komma's gescheiden lijst)";
App::$strings["Other networks and post services"] = "Andere netwerken en diensten";
App::$strings["Set publish date"] = "Publicatiedatum instellen";
App::$strings["Discover"] = "Ontdekken";
@@ -2976,9 +2745,11 @@ App::$strings["Spam"] = "Spam";
App::$strings["Posts flagged as SPAM"] = "Berichten gemarkeerd als SPAM";
App::$strings["Status Messages and Posts"] = "Berichten in dit kanaal";
App::$strings["Profile Details"] = "Profiel";
+App::$strings["Photo Albums"] = "Fotoalbums";
App::$strings["Files and Storage"] = "Bestanden en opslagruimte";
+App::$strings["Bookmarks"] = "Bladwijzers";
App::$strings["Saved Bookmarks"] = "Opgeslagen bladwijzers";
-App::$strings["Manage Webpages"] = "Webpagina's beheren";
+App::$strings["View Webpages"] = "Webpagina's weergeven";
App::$strings["__ctx:noun__ Attending"] = array(
0 => "aanwezig",
1 => "aanwezig",
@@ -3003,14 +2774,309 @@ App::$strings["__ctx:noun__ Abstain"] = array(
0 => "onthouding",
1 => "onthoudingen",
);
-App::$strings["Image/photo"] = "Afbeelding/foto";
-App::$strings["Encrypted content"] = "Versleutelde inhoud";
-App::$strings["Install %s element: "] = "Installeer %s-element: ";
-App::$strings["This post contains an installable %s element, however you lack permissions to install it on this site."] = "Dit bericht heeft een te installeren %s-element, maar je hebt geen permissies om het op deze hub te installeren.";
-App::$strings["%1\$s wrote the following %2\$s %3\$s"] = "%1\$s schreef het volgende %2\$s %3\$s";
-App::$strings["Click to open/close"] = "Klik om te openen of te sluiten";
-App::$strings["spoiler"] = "spoiler";
-App::$strings["$1 wrote:"] = "$1 schreef:";
+App::$strings["A deleted group with this name was revived. Existing item permissions <strong>may</strong> apply to this group and any future members. If this is not what you intended, please create another group with a different name."] = "Een verwijderde collectie met deze naam is gereactiveerd. Bestaande itemrechten <strong>kunnen</strong> van toepassing zijn op deze collectie en toekomstige leden. Wanneer je dit niet zo bedoeld hebt, moet je een nieuwe collectie met een andere naam aanmaken.";
+App::$strings["Add new connections to this privacy group"] = "Voeg nieuwe connecties aan deze privacygroep toe";
+App::$strings["edit"] = "bewerken";
+App::$strings["Privacy Groups"] = "Privacygroepen";
+App::$strings["Edit group"] = "Privacygroep bewerken";
+App::$strings["Add privacy group"] = "Privacygroep toevoegen";
+App::$strings["Channels not in any privacy group"] = "Kanalen die zich in geen enkele privacygroep bevinden";
+App::$strings["(Unknown)"] = "(Onbekend)";
+App::$strings["Visible to anybody on the internet."] = "Voor iedereen op het internet zichtbaar.";
+App::$strings["Visible to you only."] = "Alleen voor jou zichtbaar.";
+App::$strings["Visible to anybody in this network."] = "Voor iedereen in dit netwerk zichtbaar.";
+App::$strings["Visible to anybody authenticated."] = "Voor iedereen die geauthenticeerd is zichtbaar.";
+App::$strings["Visible to anybody on %s."] = "Voor iedereen op %s zichtbaar.";
+App::$strings["Visible to all connections."] = "Voor alle connecties zichtbaar.";
+App::$strings["Visible to approved connections."] = "Voor alle geaccepteerde connecties zichtbaar.";
+App::$strings["Visible to specific connections."] = "Voor specifieke connecties zichtbaar.";
+App::$strings["Privacy group is empty."] = "Privacygroep is leeg";
+App::$strings["Privacy group: %s"] = "Privacygroep: %s";
+App::$strings["Connection not found."] = "Connectie niet gevonden.";
+App::$strings["profile photo"] = "profielfoto";
+App::$strings["[Edited %s]"] = "[%s bewerkt]";
+App::$strings["__ctx:edit_activity__ Post"] = "Bericht";
+App::$strings["__ctx:edit_activity__ Comment"] = "Reactie";
+App::$strings["Attachments:"] = "Bijlagen:";
+App::$strings["\$Projectname event notification:"] = "Notificatie \$Projectname-gebeurtenis:";
+App::$strings["guest:"] = "gast:";
+App::$strings["The form security token was not correct. This probably happened because the form has been opened for too long (>3 hours) before submitting it."] = "De beveiligings-token van het tekstvak was ongeldig. Dit is mogelijk het gevolg van dat er te lang (meer dan 3 uur) gewacht is om de tekst op te slaan. ";
+App::$strings["Remote authentication"] = "Authenticatie op afstand";
+App::$strings["Click to authenticate to your home hub"] = "Authenticeer jezelf via (bijvoorbeeld) jouw hub";
+App::$strings["Logout"] = "Uitloggen";
+App::$strings["End this session"] = "Beëindig deze sessie";
+App::$strings["Your profile page"] = "Jouw profielpagina";
+App::$strings["Manage/Edit profiles"] = "Beheer/wijzig profielen";
+App::$strings["Edit your profile"] = "Jouw profiel bewerken";
+App::$strings["Sign in"] = "Inloggen";
+App::$strings["Get me home"] = "Terug naar mijn hub";
+App::$strings["Log me out of this site"] = "Uitloggen op deze hub";
+App::$strings["Create an account"] = "Maak een account aan";
+App::$strings["Help and documentation"] = "Hulp en documentatie";
+App::$strings["Applications, utilities, links, games"] = "Apps";
+App::$strings["Search site @name, #tag, ?docs, content"] = "Zoek een @kanaal, doorzoek inhoud hub met tekst en #tags, of doorzoek ?documentatie ";
+App::$strings["Channel Directory"] = "Kanalengids";
+App::$strings["Your grid"] = "Jouw grid";
+App::$strings["View your network/grid"] = "Jouw grid/netwerk weergeven";
+App::$strings["Mark all grid notifications seen"] = "Markeer alle gridnotificaties als bekeken";
+App::$strings["Channel home"] = "Jouw kanaal";
+App::$strings["View your channel home"] = "Jouw kanaal weergeven";
+App::$strings["Mark all channel notifications seen"] = "Alle kanaalnotificaties als gelezen markeren";
+App::$strings["Notices"] = "Notificaties";
+App::$strings["Notifications"] = "Notificaties";
+App::$strings["View all notifications"] = "Alle notificaties weergeven";
+App::$strings["Private mail"] = "Privéberichten";
+App::$strings["View your private messages"] = "Privéberichten weergeven";
+App::$strings["Mark all private messages seen"] = "Markeer alle privéberichten als bekeken";
+App::$strings["Event Calendar"] = "Agenda";
+App::$strings["View events"] = "Agenda weergeven";
+App::$strings["Mark all events seen"] = "Markeer alle gebeurtenissen als bekeken";
+App::$strings["Manage Your Channels"] = "Beheer je kanalen";
+App::$strings["Account/Channel Settings"] = "Account-/kanaal-instellingen";
+App::$strings["Site Setup and Configuration"] = "Hub instellen en beheren";
+App::$strings["@name, #tag, ?doc, content"] = "@kanaal, #tag, inhoud, ?hulp";
+App::$strings["Please wait..."] = "Wachten aub...";
+App::$strings["Add Apps"] = "Apps toevoegen";
+App::$strings["Item was not found."] = "Item niet gevonden";
+App::$strings["No source file."] = "Geen bronbestand.";
+App::$strings["Cannot locate file to replace"] = "Kan het te vervangen bestand niet vinden";
+App::$strings["Cannot locate file to revise/update"] = "Kan het bestand wat aangepast moet worden niet vinden";
+App::$strings["File exceeds size limit of %d"] = "Bestand is groter dan de toegelaten %d";
+App::$strings["You have reached your limit of %1$.0f Mbytes attachment storage."] = "Je hebt jouw limiet van %1$.0f MB opslagruimte voor bijlagen bereikt.";
+App::$strings["File upload failed. Possible system limit or action terminated."] = "Uploaden van bestand mislukt. Mogelijk systeemlimiet bereikt of actie afgebroken.";
+App::$strings["Stored file could not be verified. Upload failed."] = "Opgeslagen bestand kon niet worden geverifieerd. Uploaden mislukt.";
+App::$strings["Path not available."] = "Locatie niet beschikbaar.";
+App::$strings["Empty pathname"] = "Ontbrekende locatienaam";
+App::$strings["duplicate filename or path"] = "dubbele bestandsnaam of locatie";
+App::$strings["Path not found."] = "Locatie niet gevonden";
+App::$strings["mkdir failed."] = "directory aanmaken (mkdir) mislukt.";
+App::$strings["database storage failed."] = "opslag in database mislukt.";
+App::$strings["Empty path"] = "Ontbrekende locatie";
+App::$strings["prev"] = "vorige";
+App::$strings["first"] = "eerste";
+App::$strings["last"] = "laatste";
+App::$strings["next"] = "volgende";
+App::$strings["older"] = "ouder";
+App::$strings["newer"] = "nieuwer";
+App::$strings["No connections"] = "Geen connecties";
+App::$strings["View all %s connections"] = "Toon alle %s connecties";
+App::$strings["poke"] = "aanstoten";
+App::$strings["ping"] = "ping";
+App::$strings["pinged"] = "gepingd";
+App::$strings["prod"] = "por";
+App::$strings["prodded"] = "gepord";
+App::$strings["slap"] = "slaan";
+App::$strings["slapped"] = "sloeg";
+App::$strings["finger"] = "finger";
+App::$strings["fingered"] = "gefingerd";
+App::$strings["rebuff"] = "afpoeieren";
+App::$strings["rebuffed"] = "afgepoeierd";
+App::$strings["happy"] = "gelukkig";
+App::$strings["sad"] = "bedroefd";
+App::$strings["mellow"] = "mellow";
+App::$strings["tired"] = "moe";
+App::$strings["perky"] = "parmantig";
+App::$strings["angry"] = "boos";
+App::$strings["stupefied"] = "verbijsterd";
+App::$strings["puzzled"] = "verward";
+App::$strings["interested"] = "geïnteresseerd";
+App::$strings["bitter"] = "verbitterd";
+App::$strings["cheerful"] = "vrolijk";
+App::$strings["alive"] = "levendig";
+App::$strings["annoyed"] = "geërgerd";
+App::$strings["anxious"] = "bezorgd";
+App::$strings["cranky"] = "humeurig";
+App::$strings["disturbed"] = "verontrust";
+App::$strings["frustrated"] = "gefrustreerd ";
+App::$strings["depressed"] = "gedeprimeerd";
+App::$strings["motivated"] = "gemotiveerd";
+App::$strings["relaxed"] = "ontspannen";
+App::$strings["surprised"] = "verrast";
+App::$strings["May"] = "mei";
+App::$strings["Unknown Attachment"] = "Onbekende bijlage";
+App::$strings["unknown"] = "onbekend";
+App::$strings["remove category"] = "categorie verwijderen";
+App::$strings["remove from file"] = "uit map verwijderen";
+App::$strings["Page layout"] = "Pagina-lay-out";
+App::$strings["You can create your own with the layouts tool"] = "Je kan jouw eigen lay-out ontwerpen onder lay-outs";
+App::$strings["Page content type"] = "Opmaaktype";
+App::$strings["activity"] = "activiteit";
+App::$strings["Design Tools"] = "Ontwerp-hulpmiddelen";
+App::$strings["Pages"] = "Pagina's";
+App::$strings["Import website..."] = "Website importeren...";
+App::$strings["Select folder to import"] = "Kies een map om te importeren";
+App::$strings["Import from a zipped folder:"] = "Vanuit een zipbestand importeren:";
+App::$strings["Import from cloud files:"] = "Vanuit de cloud importeren:";
+App::$strings["/cloud/channel/path/to/folder"] = "/cloud/channel/maplocatie";
+App::$strings["Enter path to website files"] = "Voer de locatie in van de websitebestanden";
+App::$strings["Select folder"] = "Kies een map";
+App::$strings["Export website..."] = "Website exporteren...";
+App::$strings["Export to a zip file"] = "Naar een zipbestand exporteren";
+App::$strings["website.zip"] = "website.zip";
+App::$strings["Enter a name for the zip file."] = "Vul een naam in voor het zipbestand.";
+App::$strings["Export to cloud files"] = "Naar de cloud exporteren";
+App::$strings["/path/to/export/folder"] = "/locatie/van/export/map";
+App::$strings["Enter a path to a cloud files destination."] = "Voer de locatie in van de cloudbestemming";
+App::$strings["Specify folder"] = "Selecteer een map";
+App::$strings["Logged out."] = "Uitgelogd.";
+App::$strings["Failed authentication"] = "Mislukte authenticatie";
+App::$strings["Channel is blocked on this site."] = "Kanaal is op deze hub geblokkeerd.";
+App::$strings["Channel location missing."] = "Ontbrekende kanaallocatie.";
+App::$strings["Response from remote channel was incomplete."] = "Antwoord van het kanaal op afstand was niet volledig.";
+App::$strings["Channel was deleted and no longer exists."] = "Kanaal is verwijderd en bestaat niet meer.";
+App::$strings["Protocol disabled."] = "Protocol uitgeschakeld.";
+App::$strings["Channel discovery failed."] = "Kanaal ontdekken mislukt.";
+App::$strings["Cannot connect to yourself."] = "Kan niet met jezelf verbinden";
+App::$strings["Cannot create a duplicate channel identifier on this system. Import failed."] = "Kan geen dubbele kanaal-identificator op deze hub aanmaken. Importeren mislukt.";
+App::$strings["Channel clone failed. Import failed."] = "Het klonen van het kanaal is mislukt. Importeren mislukt.";
+App::$strings["Cloned channel not found. Import failed."] = "Gekloond kanaal niet gevonden. Importeren mislukt.";
+App::$strings["Unable to import element \""] = "Niet in staat om dit element te importeren: \"";
+App::$strings["Unable to determine sender."] = "Afzender kan niet bepaald worden.";
+App::$strings["No recipient provided."] = "Geen ontvanger opgegeven.";
+App::$strings["[no subject]"] = "[geen onderwerp]";
+App::$strings["Stored post could not be verified."] = "Opgeslagen bericht kon niet worden geverifieerd.";
+App::$strings[" by "] = " door ";
+App::$strings[" on "] = " op ";
+App::$strings["Embedded content"] = "Ingesloten (embedded) inhoud";
+App::$strings["Embedding disabled"] = "Insluiten (embedding) uitgeschakeld";
+App::$strings["Invalid data packet"] = "Datapakket ongeldig";
+App::$strings["Unable to verify channel signature"] = "Kanaalkenmerk kon niet worden geverifieerd. ";
+App::$strings["Unable to verify site signature for %s"] = "Hubkenmerk voor %s kon niet worden geverifieerd";
+App::$strings["invalid target signature"] = "ongeldig doelkenmerk";
+App::$strings["Can view my normal stream and posts"] = "Kan mijn normale kanaalstream en berichten bekijken";
+App::$strings["Can view my webpages"] = "Kan mijn pagina's bekijken";
+App::$strings["Can post on my channel page (\"wall\")"] = "Kan een bericht in mijn kanaal plaatsen";
+App::$strings["Can like/dislike stuff"] = "Kan dingen leuk of niet leuk vinden";
+App::$strings["Profiles and things other than posts/comments"] = "Profielen en dingen, buiten berichten en reacties";
+App::$strings["Can forward to all my channel contacts via post @mentions"] = "Kan naar al mijn kanaalconnecties berichten doorsturen met behulp van @vermeldingen+";
+App::$strings["Advanced - useful for creating group forum channels"] = "Geavanceerd - nuttig voor groepforums";
+App::$strings["Can chat with me (when available)"] = "Kan met mij chatten (wanneer beschikbaar)";
+App::$strings["Can write to my file storage and photos"] = "Kan foto's en andere bestanden aan mijn bestandsopslag toevoegen";
+App::$strings["Can edit my webpages"] = "Kan mijn pagina's bewerken";
+App::$strings["Somewhat advanced - very useful in open communities"] = "Enigszins geavanceerd (erg nuttig voor kanalen van forums/groepen)";
+App::$strings["Can administer my channel resources"] = "Kan mijn kanaal beheren";
+App::$strings["Extremely advanced. Leave this alone unless you know what you are doing"] = "Zeer geavanceerd. Laat dit met rust, behalve als je weet wat je doet.";
+App::$strings[" and "] = " en ";
+App::$strings["public profile"] = "openbaar profiel";
+App::$strings["%1\$s changed %2\$s to &ldquo;%3\$s&rdquo;"] = "%1\$s veranderde %2\$s naar &ldquo;%3\$s&rdquo;";
+App::$strings["Visit %1\$s's %2\$s"] = "Bezoek het %2\$s van %1\$s";
+App::$strings["%1\$s has an updated %2\$s, changing %3\$s."] = "%1\$s heeft een aangepaste %2\$s, %3\$s veranderd.";
+App::$strings["General Features"] = "Algemene functies";
+App::$strings["Multiple Profiles"] = "Meerdere profielen";
+App::$strings["Ability to create multiple profiles"] = "Mogelijkheid om meerdere profielen aan te maken";
+App::$strings["Advanced Profiles"] = "Geavanceerde profielen";
+App::$strings["Additional profile sections and selections"] = "Extra onderdelen en keuzes voor je profiel";
+App::$strings["Profile Import/Export"] = "Profiel importen/exporteren";
+App::$strings["Save and load profile details across sites/channels"] = "Profielgegevens opslaan en in andere hubs/kanalen gebruiken.";
+App::$strings["Web Pages"] = "Webpagina's";
+App::$strings["Provide managed web pages on your channel"] = "Sta beheerde webpagina's op jouw kanaal toe";
+App::$strings["Provide a wiki for your channel"] = "Voeg een wiki aan jouw kanaal toe";
+App::$strings["Private Notes"] = "Privé-aantekeningen";
+App::$strings["Enables a tool to store notes and reminders (note: not encrypted)"] = "Een eenvoudige toepassing om aantekeningen en herinneringen in te bewaren (let op: niet versleuteld)";
+App::$strings["Navigation Channel Select"] = "Kanaal kiezen in navigatiemenu";
+App::$strings["Change channels directly from within the navigation dropdown menu"] = "Kies een ander kanaal direct vanuit het dropdown-menu op de navigatiebalk";
+App::$strings["Photo Location"] = "Fotolocatie";
+App::$strings["If location data is available on uploaded photos, link this to a map."] = "Wanneer in de geüploade foto's locatiegegevens aanwezig zijn, link dit dan aan een kaart.";
+App::$strings["Access Controlled Chatrooms"] = "Chatkanalen met toegangscontrole ";
+App::$strings["Provide chatrooms and chat services with access control."] = "Chatkanalen en chatdiensten met toegangscontrole aanbieden.";
+App::$strings["Provide alternate connection permission roles."] = "Extra permissietypes voor connecties aanmaken";
+App::$strings["Smart Birthdays"] = "Slimme verjaardagen";
+App::$strings["Make birthday events timezone aware in case your friends are scattered across the planet."] = "Maak verjaardagen bewust van tijdzones. Voor het geval dat jouw vrienden over de hele wereld verspreid zijn.";
+App::$strings["Event Timezone Selection"] = "Tijdzone gebeurtenis";
+App::$strings["Allow event creation in timezones other than your own."] = "Sta het aanmaken van gebeurtenissen in andere tijdzones toe.";
+App::$strings["Advanced Directory Search"] = "Geavanceerd in de kanalengids zoeken";
+App::$strings["Allows creation of complex directory search queries"] = "Gebruik complexe zoekopdrachten in de kanalengids";
+App::$strings["Advanced Theme and Layout Settings"] = "Geavanceerde thema- en lay-out-instellingen";
+App::$strings["Allows fine tuning of themes and page layouts"] = "Maakt het mogelijk dat thema's en pagina-lay-outs preciezer ingesteld kunnen worden ";
+App::$strings["Post Composition Features"] = "Functies voor het opstellen van berichten";
+App::$strings["Large Photos"] = "Grote foto's";
+App::$strings["Include large (1024px) photo thumbnails in posts. If not enabled, use small (640px) photo thumbnails"] = "Gebruik grotere foto's (1024px) in berichten. Wanneer dit is uitgeschakeld worden er kleinere foto's (640px) gebruikt.";
+App::$strings["Automatically import channel content from other channels or feeds"] = "Automatisch inhoud uit andere kanalen of feeds importeren.";
+App::$strings["Even More Encryption"] = "Extra encryptie";
+App::$strings["Allow optional encryption of content end-to-end with a shared secret key"] = "Sta toe dat inhoud extra end-to-end wordt versleuteld met een gedeelde geheime sleutel.";
+App::$strings["Enable Voting Tools"] = "Peilingen inschakelen";
+App::$strings["Provide a class of post which others can vote on"] = "Maakt het mogelijk om een bericht op te stellen, waar mensen op kunnen stemmen.";
+App::$strings["Disable Comments"] = "Reacties uitschakelen";
+App::$strings["Provide the option to disable comments for a post"] = "Maak het mogelijk dat reacties op een bericht kunnen worden uitgeschakeld";
+App::$strings["Delayed Posting"] = "Berichten uitstellen";
+App::$strings["Allow posts to be published at a later date"] = "Maakt het mogelijk dat berichten op een toekomstig moment gepubliceerd kunnen worden.";
+App::$strings["Content Expiration"] = "Inhoud laten verlopen";
+App::$strings["Remove posts/comments and/or private messages at a future time"] = "Berichten, reacties en/of privéberichten na een bepaalde tijd verwijderen";
+App::$strings["Suppress Duplicate Posts/Comments"] = "Dubbele berichten/reacties tegenhouden";
+App::$strings["Prevent posts with identical content to be published with less than two minutes in between submissions."] = "Voorkomt dat berichten en reacties met identieke inhoud en die binnen twee minuten zijn verstuurd, worden gepubliceerd. ";
+App::$strings["Network and Stream Filtering"] = "Netwerk- en streamfilter";
+App::$strings["Search by Date"] = "Zoek op datum";
+App::$strings["Ability to select posts by date ranges"] = "Mogelijkheid om berichten op datum te filteren ";
+App::$strings["Enable management and selection of privacy groups"] = "Beheer en selectie van privacygroepen inschakelen";
+App::$strings["Save search terms for re-use"] = "Sla zoekopdrachten op voor hergebruik";
+App::$strings["Network Personal Tab"] = "Persoonlijke netwerktab";
+App::$strings["Enable tab to display only Network posts that you've interacted on"] = "Sta het toe dat de tab netwerkberichten toont waarmee je interactie had";
+App::$strings["Network New Tab"] = "Nieuwe netwerktab";
+App::$strings["Enable tab to display all new Network activity"] = "Laat de tab alle nieuwe netwerkactiviteit tonen";
+App::$strings["Affinity Tool"] = "Affiniteitsfilter";
+App::$strings["Filter stream activity by depth of relationships"] = "Filter wat je in jouw grid ziet op hoe goed je iemand kent of mag";
+App::$strings["Show friend and connection suggestions"] = "Toon kanaalvoorstellen";
+App::$strings["Connection Filtering"] = "Berichtenfilters";
+App::$strings["Filter incoming posts from connections based on keywords/content"] = "Filter binnenkomende berichten van connecties aan de hand van trefwoorden en taal";
+App::$strings["Post/Comment Tools"] = "Bericht- en reactiehulpmiddelen";
+App::$strings["Community Tagging"] = "Taggen door anderen";
+App::$strings["Ability to tag existing posts"] = "Geeft andere mensen de mogelijkheid om jouw (bestaande) berichten te taggen";
+App::$strings["Post Categories"] = "Categorieën berichten";
+App::$strings["Add categories to your posts"] = "Voeg categorieën toe aan je berichten";
+App::$strings["Emoji Reactions"] = "Emoji-reacties";
+App::$strings["Add emoji reaction ability to posts"] = "Emoji-reacties in berichten toestaan";
+App::$strings["Ability to file posts under folders"] = "Mogelijkheid om berichten in mappen op te slaan";
+App::$strings["Dislike Posts"] = "Vind berichten niet leuk";
+App::$strings["Ability to dislike posts/comments"] = "Mogelijkheid om berichten en reacties niet leuk te vinden";
+App::$strings["Star Posts"] = "Geef berichten een ster";
+App::$strings["Ability to mark special posts with a star indicator"] = "Mogelijkheid om speciale berichten met een ster te markeren";
+App::$strings["Tag Cloud"] = "Tagwolk";
+App::$strings["Provide a personal tag cloud on your channel page"] = "Zorgt voor een persoonlijke wolk met tags op jouw kanaalpagina";
+App::$strings["Premium Channel"] = "Premiumkanaal";
+App::$strings["Allows you to set restrictions and terms on those that connect with your channel"] = "Stelt je in staat om beperkingen en voorwaarden in te stellen voor jouw kanaal";
+App::$strings["Image exceeds website size limit of %lu bytes"] = "Afbeelding is groter dan op deze hub toegestane limiet van %lu bytes";
+App::$strings["Image file is empty."] = "Afbeeldingsbestand is leeg";
+App::$strings["Photo storage failed."] = "Foto kan niet worden opgeslagen";
+App::$strings["a new photo"] = "een nieuwe foto";
+App::$strings["__ctx:photo_upload__ %1\$s posted %2\$s to %3\$s"] = "%1\$s plaatste %2\$s op %3\$s";
+App::$strings["Upload New Photos"] = "Nieuwe foto's uploaden";
+App::$strings["Unable to obtain identity information from database"] = "Niet in staat om identiteitsinformatie uit de database te verkrijgen";
+App::$strings["Empty name"] = "Ontbrekende naam";
+App::$strings["Name too long"] = "Naam te lang";
+App::$strings["No account identifier"] = "Geen account-identificator";
+App::$strings["Nickname is required."] = "Bijnaam is verplicht";
+App::$strings["Reserved nickname. Please choose another."] = "Deze naam is gereserveerd. Kies een andere.";
+App::$strings["Nickname has unsupported characters or is already being used on this site."] = "Deze naam heeft niet ondersteunde karakters of is al op deze hub in gebruik.";
+App::$strings["Unable to retrieve created identity"] = "Niet in staat om aangemaakte identiteit te vinden";
+App::$strings["Default Profile"] = "Standaardprofiel";
+App::$strings["Create New Profile"] = "Nieuw profiel aanmaken";
+App::$strings["Visible to everybody"] = "Voor iedereen zichtbaar";
+App::$strings["Gender:"] = "Geslacht:";
+App::$strings["Homepage:"] = "Homepagina:";
+App::$strings["Online Now"] = "Nu online";
+App::$strings["Like this channel"] = "Vind dit kanaal leuk";
+App::$strings["j F, Y"] = "F j Y";
+App::$strings["j F"] = "F j";
+App::$strings["Birthday:"] = "Geboortedatum:";
+App::$strings["for %1\$d %2\$s"] = "voor %1\$d %2\$s";
+App::$strings["Sexual Preference:"] = "Seksuele voorkeur:";
+App::$strings["Tags:"] = "Tags:";
+App::$strings["Political Views:"] = "Politieke overtuigingen:";
+App::$strings["Religion:"] = "Religie:";
+App::$strings["Hobbies/Interests:"] = "Hobby's/interesses:";
+App::$strings["Likes:"] = "Houdt van:";
+App::$strings["Dislikes:"] = "Houdt niet van:";
+App::$strings["Contact information and Social Networks:"] = "Contactinformatie en sociale netwerken:";
+App::$strings["My other channels:"] = "Mijn andere kanalen";
+App::$strings["Musical interests:"] = "Muzikale interesses:";
+App::$strings["Books, literature:"] = "Boeken, literatuur:";
+App::$strings["Television:"] = "Televisie:";
+App::$strings["Film/dance/culture/entertainment:"] = "Films/dansen/cultuur/vermaak:";
+App::$strings["Love/Romance:"] = "Liefde/romantiek:";
+App::$strings["Work/employment:"] = "Werk/beroep:";
+App::$strings["School/education:"] = "School/opleiding:";
+App::$strings["Like this thing"] = "Vind dit ding leuk";
+App::$strings["User '%s' deleted"] = "Account '%s' verwijderd";
App::$strings["Source channel not found."] = "Bron van kanaal niet gevonden";
App::$strings["Focus (Hubzilla default)"] = "Focus (Hubzilla-standaard)";
App::$strings["Theme settings"] = "Thema-instellingen";
@@ -3045,11 +3111,9 @@ App::$strings["Left align page content"] = "Inhoud links uitlijnen";
App::$strings["Set minimum opacity of nav bar - to hide it"] = "Minimale ondoorzichtigheid navigatiebalk (- om te verbergen)";
App::$strings["Set size of conversation author photo"] = "Grootte profielfoto's van berichten instellen";
App::$strings["Set size of followup author photos"] = "Grootte profielfoto's van reacties instellen";
-App::$strings["__ctx:opensearch__ Search %1\$s (%2\$s)"] = "Zoek %1\$s (%2\$s)";
-App::$strings["__ctx:opensearch__ \$Projectname"] = "\$Projectname";
App::$strings["Update %s failed. See error logs."] = "Update %s mislukt. Zie foutenlogboek.";
App::$strings["Update Error at %s"] = "Update-fout op %s";
-App::$strings["Create an account to access services and applications within the Hubzilla"] = "Maak een account aan om toegang te krijgen tot diensten en toepassingen van Hubzilla";
+App::$strings["Create an account to access services and applications"] = "Maak een account aan om toegang te krijgen tot diensten en toepassingen";
App::$strings["Login/Email"] = "E-mailadres of inlognaam";
App::$strings["Password"] = "Wachtwoord";
App::$strings["Remember me"] = "Aangemeld blijven";
diff --git a/view/pdl/mod_admin.pdl b/view/pdl/mod_admin.pdl
index 5bd47ea37..deee4551b 100644
--- a/view/pdl/mod_admin.pdl
+++ b/view/pdl/mod_admin.pdl
@@ -1,3 +1,6 @@
[region=aside]
[widget=admin][/widget]
-[/region] \ No newline at end of file
+[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_appman.pdl b/view/pdl/mod_appman.pdl
index 1209d85b9..d2b1379a5 100644
--- a/view/pdl/mod_appman.pdl
+++ b/view/pdl/mod_appman.pdl
@@ -1,3 +1,6 @@
[region=aside]
[widget=appcategories][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_apps.pdl b/view/pdl/mod_apps.pdl
index 32fef28e9..d2b1379a5 100644
--- a/view/pdl/mod_apps.pdl
+++ b/view/pdl/mod_apps.pdl
@@ -1,4 +1,6 @@
[region=aside]
-[widget=appselect][/widget]
[widget=appcategories][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_blocks.pdl b/view/pdl/mod_blocks.pdl
index cef69f194..6ef7993b5 100644
--- a/view/pdl/mod_blocks.pdl
+++ b/view/pdl/mod_blocks.pdl
@@ -1,3 +1,6 @@
[region=aside]
[widget=design_tools][/widget]
-[/region] \ No newline at end of file
+[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_cal.pdl b/view/pdl/mod_cal.pdl
index f12bf39c3..c34898dd5 100644
--- a/view/pdl/mod_cal.pdl
+++ b/view/pdl/mod_cal.pdl
@@ -1,3 +1,6 @@
[region=aside]
[widget=fullprofile][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_cards.pdl b/view/pdl/mod_cards.pdl
new file mode 100644
index 000000000..f5606dcb8
--- /dev/null
+++ b/view/pdl/mod_cards.pdl
@@ -0,0 +1,8 @@
+[region=aside]
+[widget=categories][var=cards]1[/var][/widget]
+[widget=tasklist][/widget]
+[widget=notes][/widget]
+[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_cdav.pdl b/view/pdl/mod_cdav.pdl
new file mode 100644
index 000000000..d31308d90
--- /dev/null
+++ b/view/pdl/mod_cdav.pdl
@@ -0,0 +1,6 @@
+[region=aside]
+[widget=cdav][/widget]
+[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_channel.pdl b/view/pdl/mod_channel.pdl
index 98dc71915..f7ac0b4ef 100644
--- a/view/pdl/mod_channel.pdl
+++ b/view/pdl/mod_channel.pdl
@@ -3,8 +3,11 @@
[/region]
[region=aside]
[widget=fullprofile][/widget]
+[widget=common_friends][/widget]
[widget=archive][var=wall]1[/var][/widget]
[widget=categories][/widget]
[widget=tagcloud_wall][var=limit]24[/var][/widget]
[/region]
-
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_chanview.pdl b/view/pdl/mod_chanview.pdl
index d8f50ad7a..5c8ca77d5 100644
--- a/view/pdl/mod_chanview.pdl
+++ b/view/pdl/mod_chanview.pdl
@@ -1,3 +1,6 @@
[region=aside]
[widget=vcard][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_chat.pdl b/view/pdl/mod_chat.pdl
index 664e77f53..2f1f5c8d1 100644
--- a/view/pdl/mod_chat.pdl
+++ b/view/pdl/mod_chat.pdl
@@ -5,3 +5,6 @@
[widget=suggestedchats][/widget]
[widget=chatroom_members][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_cloud.pdl b/view/pdl/mod_cloud.pdl
index d8f50ad7a..5c8ca77d5 100644
--- a/view/pdl/mod_cloud.pdl
+++ b/view/pdl/mod_cloud.pdl
@@ -1,3 +1,6 @@
[region=aside]
[widget=vcard][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_common.pdl b/view/pdl/mod_common.pdl
index f12bf39c3..c34898dd5 100644
--- a/view/pdl/mod_common.pdl
+++ b/view/pdl/mod_common.pdl
@@ -1,3 +1,6 @@
[region=aside]
[widget=fullprofile][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_connect.pdl b/view/pdl/mod_connect.pdl
index 6b1d2a15e..23b8d9f71 100644
--- a/view/pdl/mod_connect.pdl
+++ b/view/pdl/mod_connect.pdl
@@ -1,3 +1,6 @@
[region=aside]
[widget=profile][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_connections.pdl b/view/pdl/mod_connections.pdl
index fd3f25483..7cead4fe8 100644
--- a/view/pdl/mod_connections.pdl
+++ b/view/pdl/mod_connections.pdl
@@ -4,3 +4,6 @@
[widget=suggestions][/widget]
[widget=findpeople][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_connedit.pdl b/view/pdl/mod_connedit.pdl
index 4b468e34c..3f57ed87b 100644
--- a/view/pdl/mod_connedit.pdl
+++ b/view/pdl/mod_connedit.pdl
@@ -4,3 +4,6 @@
[widget=suggestions][/widget]
[widget=findpeople][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_directory.pdl b/view/pdl/mod_directory.pdl
index 452ab66c7..7b430738b 100644
--- a/view/pdl/mod_directory.pdl
+++ b/view/pdl/mod_directory.pdl
@@ -4,3 +4,6 @@
[widget=dirtags][/widget]
[widget=suggestions][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_display.pdl b/view/pdl/mod_display.pdl
new file mode 100644
index 000000000..e657fa88b
--- /dev/null
+++ b/view/pdl/mod_display.pdl
@@ -0,0 +1,3 @@
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_editblock.pdl b/view/pdl/mod_editblock.pdl
index cef69f194..6ef7993b5 100644
--- a/view/pdl/mod_editblock.pdl
+++ b/view/pdl/mod_editblock.pdl
@@ -1,3 +1,6 @@
[region=aside]
[widget=design_tools][/widget]
-[/region] \ No newline at end of file
+[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_editlayout.pdl b/view/pdl/mod_editlayout.pdl
index cef69f194..6ef7993b5 100644
--- a/view/pdl/mod_editlayout.pdl
+++ b/view/pdl/mod_editlayout.pdl
@@ -1,3 +1,6 @@
[region=aside]
[widget=design_tools][/widget]
-[/region] \ No newline at end of file
+[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_editwebpage.pdl b/view/pdl/mod_editwebpage.pdl
index cef69f194..6ef7993b5 100644
--- a/view/pdl/mod_editwebpage.pdl
+++ b/view/pdl/mod_editwebpage.pdl
@@ -1,3 +1,6 @@
[region=aside]
[widget=design_tools][/widget]
-[/region] \ No newline at end of file
+[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_events.pdl b/view/pdl/mod_events.pdl
index 8347d4c59..b26f3b0d0 100644
--- a/view/pdl/mod_events.pdl
+++ b/view/pdl/mod_events.pdl
@@ -2,3 +2,6 @@
[widget=eventstools][/widget]
[widget=tasklist][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_group.pdl b/view/pdl/mod_group.pdl
index 8db29cf78..0a31e17d9 100644
--- a/view/pdl/mod_group.pdl
+++ b/view/pdl/mod_group.pdl
@@ -1,3 +1,6 @@
[region=aside]
[widget=collections][var=mode]groups[/var][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_help.pdl b/view/pdl/mod_help.pdl
index bafad3839..2eab7aa63 100644
--- a/view/pdl/mod_help.pdl
+++ b/view/pdl/mod_help.pdl
@@ -1,3 +1,6 @@
[region=aside]
[widget=helpindex][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_id.pdl b/view/pdl/mod_id.pdl
index 71ef7f898..c34898dd5 100644
--- a/view/pdl/mod_id.pdl
+++ b/view/pdl/mod_id.pdl
@@ -1,4 +1,6 @@
[region=aside]
[widget=fullprofile][/widget]
[/region]
-
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_layouts.pdl b/view/pdl/mod_layouts.pdl
index cef69f194..6ef7993b5 100644
--- a/view/pdl/mod_layouts.pdl
+++ b/view/pdl/mod_layouts.pdl
@@ -1,3 +1,6 @@
[region=aside]
[widget=design_tools][/widget]
-[/region] \ No newline at end of file
+[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_locs.pdl b/view/pdl/mod_locs.pdl
index 0b0a99638..53a3ac9e5 100644
--- a/view/pdl/mod_locs.pdl
+++ b/view/pdl/mod_locs.pdl
@@ -1,4 +1,6 @@
[region=aside]
[widget=settings_menu][/widget]
[/region]
-
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_mail.pdl b/view/pdl/mod_mail.pdl
index 67632619e..52f908919 100644
--- a/view/pdl/mod_mail.pdl
+++ b/view/pdl/mod_mail.pdl
@@ -2,3 +2,6 @@
[widget=mailmenu][/widget]
[widget=conversations][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_menu.pdl b/view/pdl/mod_menu.pdl
index cef69f194..6ef7993b5 100644
--- a/view/pdl/mod_menu.pdl
+++ b/view/pdl/mod_menu.pdl
@@ -1,3 +1,6 @@
[region=aside]
[widget=design_tools][/widget]
-[/region] \ No newline at end of file
+[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_message.pdl b/view/pdl/mod_message.pdl
index 2efb3de79..f9dd8f623 100644
--- a/view/pdl/mod_message.pdl
+++ b/view/pdl/mod_message.pdl
@@ -1,3 +1,6 @@
[region=aside]
[widget=mailmenu][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_mitem.pdl b/view/pdl/mod_mitem.pdl
index c210606d0..4db06cb49 100644
--- a/view/pdl/mod_mitem.pdl
+++ b/view/pdl/mod_mitem.pdl
@@ -1,4 +1,7 @@
[region=aside]
[widget=design_tools][/widget]
[widget=menu_preview][/widget]
-[/region] \ No newline at end of file
+[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_network.pdl b/view/pdl/mod_network.pdl
index b8817fd99..44e29ffbd 100644
--- a/view/pdl/mod_network.pdl
+++ b/view/pdl/mod_network.pdl
@@ -1,5 +1,3 @@
-[region=nav]$nav[/region]
-
[region=aside]
[widget=collections][/widget]
[widget=forums][/widget]
@@ -14,3 +12,6 @@
$content
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_photos.pdl b/view/pdl/mod_photos.pdl
index c37cf02fe..4d1a5b2ea 100644
--- a/view/pdl/mod_photos.pdl
+++ b/view/pdl/mod_photos.pdl
@@ -2,3 +2,6 @@
[widget=vcard][/widget]
[widget=photo_albums][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_profile.pdl b/view/pdl/mod_profile.pdl
index f12bf39c3..c34898dd5 100644
--- a/view/pdl/mod_profile.pdl
+++ b/view/pdl/mod_profile.pdl
@@ -1,3 +1,6 @@
[region=aside]
[widget=fullprofile][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_profile_photo.pdl b/view/pdl/mod_profile_photo.pdl
index f12bf39c3..c34898dd5 100644
--- a/view/pdl/mod_profile_photo.pdl
+++ b/view/pdl/mod_profile_photo.pdl
@@ -1,3 +1,6 @@
[region=aside]
[widget=fullprofile][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_profiles.pdl b/view/pdl/mod_profiles.pdl
index f12bf39c3..c34898dd5 100644
--- a/view/pdl/mod_profiles.pdl
+++ b/view/pdl/mod_profiles.pdl
@@ -1,3 +1,6 @@
[region=aside]
[widget=fullprofile][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_profperm.pdl b/view/pdl/mod_profperm.pdl
index f12bf39c3..c34898dd5 100644
--- a/view/pdl/mod_profperm.pdl
+++ b/view/pdl/mod_profperm.pdl
@@ -1,3 +1,6 @@
[region=aside]
[widget=fullprofile][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_pubstream.pdl b/view/pdl/mod_pubstream.pdl
new file mode 100644
index 000000000..e657fa88b
--- /dev/null
+++ b/view/pdl/mod_pubstream.pdl
@@ -0,0 +1,3 @@
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_rate.pdl b/view/pdl/mod_rate.pdl
index d8f50ad7a..5c8ca77d5 100644
--- a/view/pdl/mod_rate.pdl
+++ b/view/pdl/mod_rate.pdl
@@ -1,3 +1,6 @@
[region=aside]
[widget=vcard][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_ratings.pdl b/view/pdl/mod_ratings.pdl
index df1486c9b..cfa39e408 100644
--- a/view/pdl/mod_ratings.pdl
+++ b/view/pdl/mod_ratings.pdl
@@ -5,3 +5,6 @@
[widget=suggestions][/widget]
[widget=findpeople][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_search.pdl b/view/pdl/mod_search.pdl
index 5096508fa..8353b4571 100644
--- a/view/pdl/mod_search.pdl
+++ b/view/pdl/mod_search.pdl
@@ -1,3 +1,6 @@
[region=aside]
[comment][widget=sitesearch][/widget][/comment]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_settings.pdl b/view/pdl/mod_settings.pdl
index 0b0a99638..53a3ac9e5 100644
--- a/view/pdl/mod_settings.pdl
+++ b/view/pdl/mod_settings.pdl
@@ -1,4 +1,6 @@
[region=aside]
[widget=settings_menu][/widget]
[/region]
-
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_sharedwithme.pdl b/view/pdl/mod_sharedwithme.pdl
new file mode 100644
index 000000000..e657fa88b
--- /dev/null
+++ b/view/pdl/mod_sharedwithme.pdl
@@ -0,0 +1,3 @@
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_suggest.pdl b/view/pdl/mod_suggest.pdl
index c2889f2fe..392a36dd6 100644
--- a/view/pdl/mod_suggest.pdl
+++ b/view/pdl/mod_suggest.pdl
@@ -1,4 +1,7 @@
[region=aside]
[widget=follow][/widget]
[widget=findpeople][/widget]
-[/region] \ No newline at end of file
+[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_uexport.pdl b/view/pdl/mod_uexport.pdl
index 0b0a99638..53a3ac9e5 100644
--- a/view/pdl/mod_uexport.pdl
+++ b/view/pdl/mod_uexport.pdl
@@ -1,4 +1,6 @@
[region=aside]
[widget=settings_menu][/widget]
[/region]
-
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_viewconnections.pdl b/view/pdl/mod_viewconnections.pdl
index f12bf39c3..c34898dd5 100644
--- a/view/pdl/mod_viewconnections.pdl
+++ b/view/pdl/mod_viewconnections.pdl
@@ -1,3 +1,6 @@
[region=aside]
[widget=fullprofile][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_webpages.pdl b/view/pdl/mod_webpages.pdl
index 9e4d604ba..4e60dc2a7 100644
--- a/view/pdl/mod_webpages.pdl
+++ b/view/pdl/mod_webpages.pdl
@@ -1,4 +1,7 @@
[region=aside]
[widget=design_tools][/widget]
[widget=website_portation_tools][/widget]
-[/region] \ No newline at end of file
+[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/pdl/mod_wiki.pdl b/view/pdl/mod_wiki.pdl
index 052ae61a1..1b98b6379 100644
--- a/view/pdl/mod_wiki.pdl
+++ b/view/pdl/mod_wiki.pdl
@@ -2,3 +2,6 @@
[widget=vcard][/widget]
[widget=wiki_pages][/widget]
[/region]
+[region=right_aside]
+[widget=notifications][/widget]
+[/region]
diff --git a/view/php/default.php b/view/php/default.php
index 373fa2fd0..b180a6eb8 100644
--- a/view/php/default.php
+++ b/view/php/default.php
@@ -8,14 +8,14 @@
<body <?php if($page['direction']) echo 'dir="rtl"' ?> >
<?php if(x($page,'banner')) echo $page['banner']; ?>
<header><?php if(x($page,'header')) echo $page['header']; ?></header>
- <nav class="navbar navbar-inverse navbar-fixed-top" role="navigation"><?php if(x($page,'nav')) echo $page['nav']; ?></nav>
+ <nav class="navbar fixed-top navbar-expand-xl navbar-dark bg-dark"><?php if(x($page,'nav')) echo $page['nav']; ?></nav>
<main>
<aside id="region_1"><div id="left_aside_spacer"><div id="left_aside_wrapper"><?php if(x($page,'aside')) echo $page['aside']; ?></div></div></aside>
<section id="region_2"><?php if(x($page,'content')) echo $page['content']; ?>
<div id="page-footer"></div>
<div id="pause"></div>
</section>
- <aside id="region_3" class="hidden-sm hidden-xs hidden-md"><?php if(x($page,'right_aside')) echo $page['right_aside']; ?></aside>
+ <aside id="region_3" class="d-none d-xl-table-cell"><div id="right_aside_spacer"><div id="right_aside_wrapper"><?php if(x($page,'right_aside')) echo $page['right_aside']; ?></div></div></aside>
</main>
<footer><?php if(x($page,'footer')) echo $page['footer']; ?></footer>
</body>
diff --git a/view/php/full.php b/view/php/full.php
index 9cf567a67..094874766 100644
--- a/view/php/full.php
+++ b/view/php/full.php
@@ -7,7 +7,7 @@
</head>
<body>
<header><?php if(x($page,'header')) echo $page['header']; ?></header>
- <nav class="navbar navbar-inverse navbar-fixed-top" role="navigation"><?php if(x($page,'nav')) echo $page['nav']; ?></nav>
+ <nav class="navbar fixed-top navbar-expand-md navbar-dark bg-dark"><?php if(x($page,'nav')) echo $page['nav']; ?></nav>
<section><?php if(x($page,'content')) echo $page['content']; ?>
<div id="page-footer"></div>
</section>
diff --git a/view/php/mod_import.php b/view/php/mod_import.php
deleted file mode 100644
index 56c4eff86..000000000
--- a/view/php/mod_import.php
+++ /dev/null
@@ -1,2 +0,0 @@
-<?php
-App::$page['template'] = 'full';
diff --git a/view/php/mod_setup.php b/view/php/mod_setup.php
new file mode 100644
index 000000000..f0ed2742d
--- /dev/null
+++ b/view/php/mod_setup.php
@@ -0,0 +1,2 @@
+<?php
+App::$page['template'] = 'zen';
diff --git a/view/php/theme_init.php b/view/php/theme_init.php
index 85da4d782..1e066c570 100644
--- a/view/php/theme_init.php
+++ b/view/php/theme_init.php
@@ -2,51 +2,42 @@
require_once('include/plugin.php');
-head_add_css('library/tiptip/tipTip.css');
-head_add_css('library/jgrowl/jquery.jgrowl.css');
-head_add_css('library/jRange/jquery.range.css');
+head_add_css('/library/tiptip/tipTip.css');
+head_add_css('/library/jgrowl/jquery.jgrowl.css');
+head_add_css('/library/jRange/jquery.range.css');
-head_add_css('view/css/conversation.css');
-head_add_css('view/css/widgets.css');
-head_add_css('view/css/colorbox.css');
-head_add_css('library/justifiedGallery/justifiedGallery.min.css');
-head_add_css('library/Text_Highlighter/sample.css');
+head_add_css('/view/css/conversation.css');
+head_add_css('/view/css/widgets.css');
+head_add_css('/view/css/colorbox.css');
+head_add_css('/library/justifiedGallery/justifiedGallery.min.css');
head_add_js('jquery.js');
-//head_add_js('jquery.migrate-3.0.0.js');
-head_add_js('library/justifiedGallery/jquery.justifiedGallery.min.js');
-head_add_js('library/sprintf.js/dist/sprintf.min.js');
+head_add_js('/library/justifiedGallery/jquery.justifiedGallery.min.js');
+head_add_js('/library/sprintf.js/dist/sprintf.min.js');
-//head_add_js('jquery-compat.js');
-head_add_js('spin.js');
-head_add_js('jquery.spin.js');
head_add_js('jquery.textinputs.js');
head_add_js('autocomplete.js');
-head_add_js('library/jquery-textcomplete/jquery.textcomplete.js');
-//head_add_js('library/colorbox/jquery.colorbox.js');
-head_add_js('library/jquery.timeago.js');
-head_add_js('library/readmore.js/readmore.js');
-head_add_js('library/sticky-kit/sticky-kit.js');
-//head_add_js('library/jquery_ac/friendica.complete.js');
-//head_add_js('library/tiptip/jquery.tipTip.minified.js');
-head_add_js('library/jgrowl/jquery.jgrowl_minimized.js');
-//head_add_js('library/tinymce/jscripts/tiny_mce/tiny_mce.js');
-head_add_js('library/cryptojs/components/core-min.js');
-head_add_js('library/cryptojs/rollups/aes.js');
-head_add_js('library/cryptojs/rollups/rabbit.js');
-head_add_js('library/cryptojs/rollups/tripledes.js');
-//head_add_js('library/stylish_select/jquery.stylish-select.js');
+head_add_js('/library/jquery-textcomplete/jquery.textcomplete.js');
+
+head_add_js('/library/jquery.timeago.js');
+head_add_js('/library/readmore.js/readmore.js');
+head_add_js('/library/sticky-kit/sticky-kit.min.js');
+head_add_js('/library/jgrowl/jquery.jgrowl_minimized.js');
+head_add_js('/library/cryptojs/components/core-min.js');
+head_add_js('/library/cryptojs/rollups/aes.js');
+head_add_js('/library/cryptojs/rollups/rabbit.js');
+head_add_js('/library/cryptojs/rollups/tripledes.js');
+
head_add_js('acl.js');
head_add_js('webtoolkit.base64.js');
head_add_js('main.js');
head_add_js('crypto.js');
-head_add_js('library/jRange/jquery.range.js');
-//head_add_js('docready.js');
-head_add_js('library/colorbox/jquery.colorbox-min.js');
+head_add_js('/library/jRange/jquery.range.js');
+head_add_js('/library/colorbox/jquery.colorbox-min.js');
-head_add_js('library/jquery.AreYouSure/jquery.are-you-sure.js');
-head_add_js('library/tableofcontents/jquery.toc.js');
-head_add_js('library/imagesloaded/imagesloaded.pkgd.min.js');
+head_add_js('/library/jquery.AreYouSure/jquery.are-you-sure.js');
+head_add_js('/library/tableofcontents/jquery.toc.js');
+head_add_js('/library/imagesloaded/imagesloaded.pkgd.min.js');
/**
* Those who require this feature will know what to do with it.
* Those who don't, won't.
diff --git a/view/pt-br/htconfig.tpl b/view/pt-br/htconfig.tpl
index ea3f5b5c2..5acb0ebe2 100644
--- a/view/pt-br/htconfig.tpl
+++ b/view/pt-br/htconfig.tpl
@@ -34,14 +34,6 @@ App::$config['system']['baseurl'] = '{{$siteurl}}';
App::$config['system']['sitename'] = "Hubzilla";
App::$config['system']['location_hash'] = '{{$site_id}}';
-// Choices are 'basic', 'standard', and 'pro'.
-// basic sets up the sevrer for basic social networking and removes "complicated" features
-// standard provides most desired features except e-commerce
-// pro gives you access to everything
-
-App::$config['system']['server_role'] = '{{$server_role}}';
-
-
// These lines set additional security headers to be sent with all responses
// You may wish to set transport_security_header to 0 if your server already sends
// this header. content_security_policy may need to be disabled if you wish to
diff --git a/view/ru/htconfig.tpl b/view/ru/htconfig.tpl
index 00da08c91..58a18fbd0 100644
--- a/view/ru/htconfig.tpl
+++ b/view/ru/htconfig.tpl
@@ -34,13 +34,6 @@ App::$config['system']['baseurl'] = '{{$siteurl}}';
App::$config['system']['sitename'] = "Hubzilla";
App::$config['system']['location_hash'] = '{{$site_id}}';
-// Choices are 'basic', 'standard', and 'pro'.
-// basic sets up the sevrer for basic social networking and removes "complicated" features
-// standard provides most desired features except e-commerce
-// pro gives you access to everything
-
-App::$config['system']['server_role'] = '{{$server_role}}';
-
// Your choices are REGISTER_OPEN, REGISTER_APPROVE, or REGISTER_CLOSED.
// Be certain to create your own personal account before setting
// REGISTER_CLOSED. 'register_text' (if set) will be displayed prominently on
diff --git a/view/sv/htconfig.tpl b/view/sv/htconfig.tpl
index 00da08c91..58a18fbd0 100644
--- a/view/sv/htconfig.tpl
+++ b/view/sv/htconfig.tpl
@@ -34,13 +34,6 @@ App::$config['system']['baseurl'] = '{{$siteurl}}';
App::$config['system']['sitename'] = "Hubzilla";
App::$config['system']['location_hash'] = '{{$site_id}}';
-// Choices are 'basic', 'standard', and 'pro'.
-// basic sets up the sevrer for basic social networking and removes "complicated" features
-// standard provides most desired features except e-commerce
-// pro gives you access to everything
-
-App::$config['system']['server_role'] = '{{$server_role}}';
-
// Your choices are REGISTER_OPEN, REGISTER_APPROVE, or REGISTER_CLOSED.
// Be certain to create your own personal account before setting
// REGISTER_CLOSED. 'register_text' (if set) will be displayed prominently on
diff --git a/view/theme/redbasic/css/align_left.css b/view/theme/redbasic/css/align_left.css
deleted file mode 100644
index acb2893e3..000000000
--- a/view/theme/redbasic/css/align_left.css
+++ /dev/null
@@ -1,8 +0,0 @@
-main {
- margin-left: 0px;
-}
-
-aside#region_3 {
- width: auto;
- padding: 0px 0px 0px 0px;
-}
diff --git a/view/theme/redbasic/css/narrow_navbar.css b/view/theme/redbasic/css/narrow_navbar.css
index 6b09b031a..99f083638 100644
--- a/view/theme/redbasic/css/narrow_navbar.css
+++ b/view/theme/redbasic/css/narrow_navbar.css
@@ -1,68 +1,30 @@
-@media screen and (min-width: 760px) {
+@media screen and (min-width: 767px) {
- aside {
- padding-top: 52px;
- }
-
- section {
- padding-top: 52px;
+ nav.navbar {
+ padding-top: 1px;
+ padding-bottom: 1px
}
- .navbar-nav > li > a {
- padding-top:7px !important;
- padding-bottom:3px !important;
- }
-
- .navbar {
- min-height:25px !important;
- }
-
- nav .navbar-header img {
- height: 29px;
- width: 29px;
- margin-top: 1px;
- border-radius: 4px;
- }
-
- .navbar-left {
- height: 29px;
- }
-
- .container-fluid {
- min-height:29px;
- }
-
- .collapse .navbar-collapse {
- min-height:29px;
- }
-
- #nav-search-text {
- margin:6px 15px 4px 15px;
- }
-
- #nav-search-spinner {
- margin: 16px 0px 0px 25px;
+ nav .badge {
+ top: 0px;
+ left: -0.25rem;
}
- header #banner {
- margin-top:5px;
+ .contextual-help-content-open {
+ top: 2.5rem;
}
- nav .dropdown-menu,
- nav .acpopup {
- top: 30px !important;
+ aside {
+ padding-top: 3.5rem;
}
- nav .badge {
- top: -29px;
+ section {
+ padding-top: 3.5rem;
}
#jGrowl.top-right {
- top: 30px;
+ top: 3.5rem;
right: 15px;
}
- .contextual-help-content-open {
- top: 31px;
- }
}
diff --git a/view/theme/redbasic/css/style.css b/view/theme/redbasic/css/style.css
index 7551dfe87..aea75df65 100644
--- a/view/theme/redbasic/css/style.css
+++ b/view/theme/redbasic/css/style.css
@@ -7,13 +7,13 @@
/* generals */
+
html {
- font-size: 100%;
+ font-size: $font_size;
}
body {
- font-family: sans-serif, arial, freesans;
- font-size: $body_font_size;
+ font-size: 0.9rem;
background-color: $bgcolour;
background-image: url('$background_image');
background-attachment: fixed;
@@ -48,35 +48,47 @@ main {
left: 0;
width: 100%;
height: 100%;
+ background: rgba(0, 0, 0, .5);
cursor: pointer;
- z-index: 1029;
+ z-index: 1028;
}
h1, .h1 {
- font-size: 2em;
+ font-size: 2rem;
}
h2, .h2 {
- font-size: 1.667em;
+ font-size: 1.6rem;
}
h3, .h3 {
- font-size: 1.334em;
+ font-size: 1.2rem;
}
h4, .h4 {
- font-size: 1em;
- font-weight: bold;
+ font-size: 1.05rem;
}
h5, .h5 {
- font-size: 1em;
+ font-size: 0.9rem;
}
h6, .h6 {
- font-size: 0.75em;
+ font-size: 0.75rem;
+}
+
+#banner {
+ color: $banner_colour;
+ font-weight: bold;
+ white-space: nowrap;
+ overflow: hidden;
+ text-overflow: ellipsis;
}
+#banner img {
+ max-height: 1.35rem;
+ width: auto;
+}
.jslider {
font-family: sans-serif, arial, freesans;
@@ -87,10 +99,6 @@ abbr {
}
/* icons */
-.tool-icons,
-.cat-icons {
- color: $toolicon_colour;
-}
a,
.fakelink {
@@ -108,34 +116,8 @@ a:focus,
cursor: pointer;
}
-input[type="text"],
-input[type="password"],
-input[type="submit"],
-input[type="file"],
-select,
-textarea {
- font-family: sans-serif, arial, freesans;
- font-size: $body_font_size;
-}
-
-input {
- padding: 5px;
- line-height: 1.5;
- border: 1px solid #ccc;
- -moz-border-radius: $radiuspx;
- border-radius: $radiuspx;
-}
-
-input[type="submit"] {
- background-color: #F0F0F0;
- font-weight: bold;
- color: #0080FF;
- text-decoration: none;
- padding: 6px 12px;
-}
-
input, optgroup, select, textarea {
- color: #333;
+ font-size: 0.9rem !important;
resize: vertical;
}
@@ -155,6 +137,7 @@ input, optgroup, select, textarea {
pre code {
border: none;
+ padding: 1em 1.5em;
}
code {
@@ -166,18 +149,22 @@ pre {
background: #F5F5F5;
color: #333;
border:1px solid #ccc;
+ border-radius: $radius;
}
.heart {
color: #FF0000;
}
-nav,
-header {
+nav {
opacity: $nav_float_min_opacity;
filter:alpha(opacity=$nav_percent_min_opacity);
}
+#nav-app-link {
+ white-space: nowrap;
+}
+
#powered-by {
font-size: 0.5rem;
position: absolute;
@@ -199,49 +186,8 @@ header {
padding: 10px;
}
-nav #banner #logo-text a {
- font-size: 40px;
- font-weight: bold;
- margin-left: 3px;
- color: #000000;
-
-}
-nav #banner #logo-text a:hover { text-decoration: none; }
-
.nav-channel-select { margin-left: 8px; }
-header #banner {
- z-index: 1040;
- margin-top: 14px;
- text-align: center;
- text-shadow: 1px 1px 2px rgba(0,0,0,.5);
- font-size: 14px;
- font-family: tahoma, "Lucida Sans", sans;
- color: $banner_colour;
- font-weight: bold;
- whitespace: nowrap;
-}
-
-header #banner a,
-header #banner a:active,
-header #banner a:visited,
-header #banner a:link,
-header #banner a:hover {
- color: $banner_colour;
- text-decoration: none;
- outline: none;
- vertical-align: bottom;
-}
-
-header #banner #logo-img {
- height: 22px;
- margin-top: 5px;
-}
-
-header #banner #logo-text {
- font-size: 22px;
-}
-
/* contextual help */
.contextual-help-content {
display: none;
@@ -251,11 +197,12 @@ header #banner #logo-text {
.contextual-help-content-open {
display: block;
position: fixed;
- top: 51px;
+ top: 3.35rem;
left: 0px;
+ width: 100%;
max-height: 50%;
background: $comment_item_colour;
- padding: 20px;
+ padding: 1rem;
border-bottom: #ccc 1px solid;
overflow: auto;
-moz-box-shadow: 0px 3px 3px rgba(0,0,0,0.2);
@@ -270,22 +217,97 @@ header #banner #logo-text {
.contextual-help-tool {
padding: 7px;
filter: alpha(opacity=20);
- opacity: .2;
+ opacity: .5;
}
.contextual-help-tool:hover {
filter: alpha(opacity=50);
- opacity: .5;
+ opacity: 1;
text-decoration: none;
}
.contextual-help-tool i {
- color: #000;
- font-size: 16px;
+ color: $font_colour;
+ font-size: 1.05rem;
}
/* contextual help end */
+/* spinner */
+
+.spinner-wrapper {
+ display: none;
+}
+
+.spinner.s {
+ height: 1rem;
+ width: 1rem;
+}
+
+.spinner.m {
+ height: 2rem;
+ width: 2rem;
+}
+
+.spinner.l {
+ height: 3rem;
+ width: 3rem;
+}
+
+.spinner.s,
+.spinner.m,
+.spinner.l {
+ margin: 0 auto;
+ position: relative;
+ -webkit-animation: rotation 1s infinite linear;
+ -moz-animation: rotation 1s infinite linear;
+ -o-animation: rotation 1s infinite linear;
+ animation: rotation 1s infinite linear;
+ border-left: .2rem solid rgba(77, 77, 77, .15);
+ border-right: .2rem solid rgba(77, 77, 77, .15);
+ border-bottom: .2rem solid rgba(77, 77, 77, .15);
+ border-top: .2rem solid rgba(77, 77, 77, .5);
+ border-radius: 100%;
+}
+
+@-webkit-keyframes rotation {
+ from {
+ -webkit-transform: rotate(0deg);
+ }
+ to {
+ -webkit-transform: rotate(359deg);
+ }
+}
+
+@-moz-keyframes rotation {
+ from {
+ -moz-transform: rotate(0deg);
+ }
+ to {
+ -moz-transform: rotate(359deg);
+ }
+}
+
+@-o-keyframes rotation {
+ from {
+ -o-transform: rotate(0deg);
+ }
+ to {
+ -o-transform: rotate(359deg);
+ }
+}
+
+@keyframes rotation {
+ from {
+ transform: rotate(0deg);
+ }
+ to {
+ transform: rotate(359deg);
+ }
+}
+
+/* spinner end */
+
/* footer */
footer {
@@ -311,29 +333,13 @@ footer {
margin-top: 15px;
}
-.preview {
- background: url('../img/gray_and_white_diagonal_stripes_background_seamless.gif');
+.preview-indicator {
}
#theme-preview {
margin: 15px 0px;
}
-/*TODO: we should use one class for all this. */
-
-.group-selected,
-.fileas-selected,
-.categories-selected,
-.search-selected,
-.active,
-.group-selected:hover,
-.fileas-selected:hover,
-.categories-selected:hover,
-.search-selected:hover,
-.active:hover {
- color: $font_colour;
-}
-
#cropimage-wrapper, #cropimage-preview-wrapper {
float: left;
padding: 30px;
@@ -346,7 +352,7 @@ footer {
.fn {
font-weight: bold;
- font-size: 16px;
+ font-size: 1rem;
color: #444444;
}
@@ -355,9 +361,7 @@ footer {
padding: 0px 10px 10px 10px;
background-color: rgba(254,254,254,0.5);
border: 1px solid rgba(254,254,254,0.5);
- -moz-border-radius: $radiuspx;
- -webkit-border-radius: $radiuspx;
- border-radius: $radiuspx;
+ border-radius: $radius;
word-wrap: break-word;
}
@@ -384,10 +388,6 @@ footer {
filter:alpha(opacity=100);
}
-#view-contact-end {
- clear: both;
-}
-
#profile-photo-wrapper img {
width: 100%;
height: 100%;
@@ -399,7 +399,7 @@ footer {
width: 251px;
height: 251px;
margin-bottom: 10px;
- border-radius: $radiuspx;
+ border-radius: $radius;
}
#hide-friends-yes-label,
@@ -453,8 +453,7 @@ footer {
.photo,
.contact-block-img {
- border-radius: $radiuspx;
- -moz-border-radius: $radiuspx;
+ border-radius: $radius;
box-shadow: $shadowpx $shadowpx $shadowpx 0 #444444;
}
@@ -468,8 +467,7 @@ footer {
.profile-match-photo img,
.directory-photo-img {
- border-radius: $radiuspx;
- -moz-border-radius: $radiuspx;
+ border-radius: $radius;
box-shadow: $shadowpx $shadowpx $shadowpx 0 #444444;
}
@@ -528,10 +526,6 @@ footer {
height: 34px;
}
-#contact-block-end {
- clear: both;
-}
-
.contact-block-img {
width:47px;
height:47px;
@@ -555,47 +549,23 @@ footer {
}
.wall-item-conv {
- padding: 7px 10px;
background-color: $comment_item_colour;
}
-
-#conversation-end {
- clear: both;
-}
-
#nav-notifications-template {
display: none;
}
-#nav-searchbar {
- float: right;
- margin-top: 2px;
- margin-right: 10px;
-}
-
#nav-search-spinner {
- float: left;
- margin: 25px 0px 0px 25px;
- color: $nav_active_icon_colour;
+ float: right;
+ margin-top: -1.4rem;
+ margin-right: 1rem;
}
-#nav-search-text:hover,
-#nav-search-text:focus {
- background-color: #fff;
- color: #000;
-}
#nav-search-text {
- font-size: 12px;
- width: 200px;
- height: 20px;
- margin: 15px;
- padding: 0px 5px 0px 5px;
- border-radius: $radiuspx;
- border-color: $nav_bd;
- background-color: #eee;
- transition: background-color 300ms ease 0s;
+ width: 280px;
+ padding: .15rem .5rem;
}
#nav-search-text::-webkit-input-placeholder {
@@ -607,7 +577,7 @@ footer {
}
nav .acpopup {
- top: 50px !important;
+ top: 46px !important;
margin-left: -35px;
width: 290px;
}
@@ -644,7 +614,7 @@ nav .acpopup {
#cboxContent {
padding: 3px;
border: 0px solid #fff;
- border-radius: $radiuspx;
+ border-radius: $radius;
background-color: #fff;
z-index: 1052;
}
@@ -667,11 +637,6 @@ nav .acpopup {
text-align: center;
}
-.profile-match-break,
-.profile-match-end {
- clear: both;
-}
-
.profile-match-connect {
text-align: center;
font-weight: bold;
@@ -690,9 +655,6 @@ nav .acpopup {
float: right;
}
-#profile-match-wrapper-end {
- clear: both;
-}
.side-link {
margin-bottom: 15px;
}
@@ -705,10 +667,6 @@ nav .acpopup {
border: 1px solid #ddd;
}
-#group-members-end {
- clear: both;
-}
-
#group-separator {
margin-top: 10px;
margin-bottom: 10px;
@@ -721,11 +679,6 @@ nav .acpopup {
border: 1px solid #ddd;
}
-#group-all-contacts-end {
- clear: both;
- margin-bottom: 10px;
-}
-
#group-edit-desc {
margin-top: 15px;
}
@@ -739,10 +692,6 @@ nav .acpopup {
border: 1px solid #ddd;
}
-#prof-members-end {
- clear: both;
-}
-
#prof-separator {
margin-top: 10px;
margin-bottom: 10px;
@@ -755,11 +704,6 @@ nav .acpopup {
border: 1px solid #ddd;
}
-#prof-all-contacts-end {
- clear: both;
- margin-bottom: 10px;
-}
-
#prof-edit-desc {
margin-top: 15px;
}
@@ -773,10 +717,6 @@ nav .acpopup {
width: 80px;
margin-right: 15px;
}
-.notification-listing-end {
- clear: both;
- margin-bottom: 15px;
-}
/**
* OAuth
@@ -826,7 +766,7 @@ div.jGrowl div.info {
padding-left: 58px;
}
#jGrowl.top-right {
- top: 65px;
+ top: 4.5rem;
right: 15px;
}
@@ -834,140 +774,34 @@ div.jGrowl div.jGrowl-notification {
min-height: 60px;
}
-#id_term_label {
- width:75px;
-}
-#id_term {
- width:100px;
-}
-
-#nav-search-text-ac .autocomplete {
- position: fixed;
- top: 51px;
- border: 1px solid $nav_bd;
- border-top: none;
-}
-
-#recip-ac .autocomplete,
-#poke-recip-ac .autocomplete,
-#id-name-ac .autocomplete,
-#contact-search-ac .autocomplete {
- margin-top: 2px;
- margin-left: $radiuspx;
- margin-right: $radiuspx;
- border: 1px solid #666;
- border-top: none;
-
-}
-
-.autocomplete {
- color: $font_colour;
- cursor: pointer;
- text-align: left;
- max-height: 350px;
- overflow: auto;
- border-bottom-left-radius: $radiuspx;
- border-bottom-right-radius: $radiuspx;
-}
-
-.autocomplete .selected {
- background: #eee;
-}
-
-.autocomplete div {
- padding: 2px 5px;
- white-space: nowrap;
- overflow: hidden;
- text-overflow: ellipsis;
-}
-
.jslider .jslider-scale ins {
color: #333;
- font-size: $body_font_size;
+ font-size: 0.9rem;
width: 100px;
text-align: center;
}
-a.rconnect, a.rateme, div.rateme {
- color: $nav_active_icon_colour;
- text-decoration: none;
- font-weight: normal;
- outline: none;
-}
-
-a.rconnect:hover, a.rateme:hover, div.rateme:hover {
- color: #0080FF;
- text-decoration: none;
-}
-
-.widget.rateme {
- margin-top: 15px;
- padding: 0;
-}
-
-.widget .conv-participants {
+.conv-participants {
color: $font_colour;
}
-.notif-item a {
- color: #000;
-}
-
-.notif-item a:hover {
- text-decoration: underline;
- color: #000;
-}
-
-.notif-image {
- width: 32px;
- height: 32px;
- padding: 7px 7px 0px 0px;
-}
-
.contactname {
- padding-top: 2px;
font-weight: bold;
- line-height: 1em;
- white-space: nowrap;
+ color: $font_colour;
+ display: block;
overflow: hidden;
text-overflow: ellipsis;
- display: block;
}
-.dropdown-sub-text {
- line-height: 1em;
+.dropdown-notification,
+.notification,
+.member-item {
+ line-height: 1.1em;
+ font-size: 0.75rem;
overflow: hidden;
text-overflow: ellipsis;
display: block;
-}
-
-.notify-seen a {
- background: #ddd;
-}
-
-#page-spinner {
- color: #777;
- margin: 24px;
-}
-
-.tabs-end {
- clear: both;
-}
-
-.modal-header .contextual-help-tool {
- /* Mostly duplicating ".modal-header .close" and ".close" layout settings from bootstrap */
- float: right;
- font-size: 21px;
- padding: 0;
- margin-top: -4px;
- margin-right: 15px;
- line-height: 1;
-}
-
-#acl-search {
- padding: 4px;
- border: 1px solid #ccc;
- width: 100%;
+ white-space: nowrap;
}
#acl-search::-webkit-input-placeholder {
@@ -980,59 +814,17 @@ a.rconnect:hover, a.rateme:hover, div.rateme:hover {
font-family: FontAwesome, sans-serif, arial, freesans;
}
-#aclModal .modal-body {
- padding-top: 10px;
-}
-
-#acl-showlimited-description {
- font-size: 90%;
- color: #888;
- margin-left: 10px;
- margin-bottom: 4px;
-}
-
-#acl-list {
- border: 1px solid #ccc;
- -webkit-border-radius: $radiuspx ;
- -moz-border-radius: $radiuspx;
- border-radius: $radiuspx;
-}
-
-#acl-search-wrapper {
- padding: 7px 10px;
- background-color: $item_colour;
- border-top-left-radius: $radiuspx;
- border-top-right-radius: $radiuspx;
- border-bottom: 1px solid #ccc;
-}
-
-#acl-list-content-wrapper {
- display: block;
- overflow: auto;
- clear: both;
- min-height: 62px;
- padding: 10px 10px 0px 0px;
-
-}
-
-#jotnets-wrapper, #jotnets-collapse {
- margin-bottom: 18px;
-}
-
-#jot-preview-content {
- margin-top: 10px;
-}
.acl-list-item {
- width: 48%; /* fallback if browser does not support calc() */
- width: calc(50% - 10px);
+ width: 100%;
+ padding: 0.5rem;
+ margin-bottom: 0.5rem;
border: 1px solid #ccc;
- margin: 0px 0px 10px 10px;
- padding: 5px;
float: left;
- -webkit-border-radius: $radiuspx ;
- -moz-border-radius: $radiuspx;
- border-radius: $radiuspx;
- background-color: white;
+ border-radius: $radius;
+}
+
+.acl-item-header {
+ width: 100%;
}
.acl-list-item.grouphide {
@@ -1043,66 +835,20 @@ a.rconnect:hover, a.rateme:hover, div.rateme:hover {
border: 1px solid green;
}
-.acl-list-item img {
- width: 40px;
- height: 40px;
- float: left;
- margin-right: 5px;
- -webkit-border-radius: $radiuspx ;
- -moz-border-radius: $radiuspx;
- border-radius: $radiuspx;
-}
-
.acl-list-item.taggable {
background-color: #ddddff;
}
-.acl-list-item p {
- font-size: $font_size;
- margin: 0px;
- white-space: nowrap;
- overflow: hidden;
- text-overflow: ellipsis;
-}
-
.acl-button-show,
.acl-button-hide {
float: right;
margin-left: 5px;
}
-#acl-showlimited-caption,
-#acl-showall-caption {
- font-size: 115%;
-}
-
-#acl-radiowrapper-showall {
- margin-top: 20px;
- margin-bottom: 20px;
-}
-#acl-radiowrapper-showlimited {
- margin-bottom: 0;
-}
-
-#acl-showall + i {
- font-size: 140%;
-}
-
-#acl-info-icon,
-#acl-info-icon:active {
- font-size: 110%;
- color: $link_colour;
- text-decoration: none;
-}
-
-#acl-showall-caption {
- margin-left: 0.35em;
-}
-
.contact-block-content {
margin-top: 10px;
}
-.contact-block-img.archived, .app-deleted {
+.contact-block-img.archived, .app-deleted, .dim {
opacity: 0.3;
filter:alpha(opacity=30);
}
@@ -1112,7 +858,7 @@ a.rconnect:hover, a.rateme:hover, div.rateme:hover {
.reshared-content { margin-left: 20px; }
.shared_header img {
- border-radius: $radiuspx;
+ border-radius: $radius;
margin-right: 10px;
}
@@ -1178,36 +924,39 @@ margin-right: 50px;
list-style-type: none;
}
-.generic-icons {
- font-size: 1.2em;
- color: $toolicon_colour;
- margin-right: 7px;
+.generic-icons,
+a .generic-icons {
+ font-size: 1rem;
+ margin-right: 0.5rem;
+ color: $font_colour;
}
-.generic-icons:hover {
- color: $toolicon_colour;
+.generic-icons:hover,
+a .generic-icons:hover {
+ color: $font_colour;
}
-.generic-icons-nav {
- font-size: 1.2em;
- margin-right: 7px;
+.generic-icons-right {
+ font-size: 1rem;
+ margin-left: 0.5rem;
+ color: $font_colour;
}
-nav .navbar-collapse.in .generic-icons,
-nav .navbar-collapse.collapsing .generic-icons {
- color: $nav_active_icon_colour;
+
+.generic-icons-nav {
+ font-size: 1rem;
+ margin-right: 7px;
}
.admin-icons {
font-size: 1.2em;
- color: $toolicon_colour;
margin-right: 7px;
}
.drop-icons,
a .drop-icons {
- color: $toolicon_colour;
- font-size: 1.2em;
+ font-size: 1rem;
+ color: $font_colour;
text-decoration: none;
cursor: pointer;
}
@@ -1217,7 +966,8 @@ a .drop-icons:hover {
color: #FF0000;
}
-.lockview {
+.lockview,
+.sys-apps-toggle {
cursor: pointer;
}
@@ -1252,8 +1002,7 @@ th,td {
/* mail */
img.mail-conv-sender-photo {
- -moz-border-radius: $radiuspx;
- border-radius: $radiuspx;
+ border-radius: $radius;
}
/* jot */
@@ -1270,25 +1019,23 @@ img.mail-conv-sender-photo {
font-weight: bold;
}
-
-
#profile-jot-wrapper {
background-color: rgba(254,254,254,1);
border: 1px solid #ccc;
- border-radius: $radiuspx;
+ border-radius: $radius;
}
#profile-jot-text {
- border-radius: $radiuspx;
+ border-radius: $radius;
}
#profile-jot-text::-webkit-input-placeholder {
- font-size: 16px;
+ font-size: 1.2rem;
}
#profile-jot-text::-moz-placeholder {
- font-size: 16px;
+ font-size: 1.2rem;
}
#profile-jot-text:focus::-webkit-input-placeholder {
@@ -1304,52 +1051,41 @@ img.mail-conv-sender-photo {
display: none;
}
-#profile-rotator {
- color: #777;
-}
-
-.jot-icons {
- color: $toolicon_colour;
-}
-
.jot-icons.jot-lock-warn {
color: darkorange;
}
/* conversation */
-.nsfw-wrap {
- text-align: center;
- font-size: $body_font_size;
+
+.top-radius {
+ border-top-right-radius: $radius;
+ border-top-left-radius: $radius;
}
.wall-event-item {
padding: 10px;
color: #fff;
background-color: #3A87AD; /* should reflect calendar color */
- border-top-left-radius: $radiuspx;
- border-top-right-radius: $radiuspx;
+ border-top-left-radius: $radius;
+ border-top-right-radius: $radius;
}
.wall-photo-item img {
max-width: 100% !important;
- border-top-right-radius: $radiuspx;
- border-top-left-radius: $radiuspx;
-}
-
-.wall-item-title {
- font-size: $font_size;
+ border-top-right-radius: $radius;
+ border-top-left-radius: $radius;
}
.wall-item-footer {
- font-size: $body_font_size;
+ font-size: 0.75rem;
margin-top: 2em;
}
.wall-item-content-wrapper {
background-color: $item_colour;
- border-top-right-radius: $radiuspx;
- border-top-left-radius: $radiuspx;
+ border-top-right-radius: $radius;
+ border-top-left-radius: $radius;
}
.wall-item-content-wrapper.comment {
@@ -1376,8 +1112,8 @@ img.mail-conv-sender-photo {
padding: 7px 10px;
background-color: $item_colour;
border-radius: 0px;
- border-bottom-right-radius: $radiuspx;
- border-bottom-left-radius: $radiuspx;
+ border-bottom-right-radius: $radius;
+ border-bottom-left-radius: $radius;
border-top: 3px solid $comment_item_colour;
}
@@ -1385,37 +1121,23 @@ img.mail-conv-sender-photo {
border-top: 0px solid $comment_item_colour;
}
-.wall-item-like,
-.wall-item-dislike {
- font-size: 11px;
-}
.wall-item-photo {
+ width: $top_photo;
+ height: $top_photo;
border: none;
- width: $top_photo !important;
- height: $top_photo !important;
-
+ border-radius: $radius;
+ box-shadow: $shadowpx $shadowpx $shadowpx 0 #444444;
}
.comment .wall-item-photo {
- width: $reply_photo !important;
- height: $reply_photo !important;
-}
-
-.wall-item-photo {
- border-radius: $radiuspx;
- -moz-border-radius: $radiuspx;
- box-shadow: $shadowpx $shadowpx $shadowpx 0 #444444;
+ width: $reply_photo;
+ height: $reply_photo;
}
.wall-item-ago,
.dropdown-sub-text {
color: #777;
- font-size: 0.833em;
-}
-
-.wall-item-ago i {
- font-size: 0.833em;
}
.wall-item-content,
@@ -1423,37 +1145,13 @@ img.mail-conv-sender-photo {
.page-body,
.chat-item-text,
.chat-item-text-self {
- font-size: $font_size;
- clear: both;
-}
-
-.item-tool {
- font-size: 1.2em;
- color: $toolicon_colour;
-}
-
-.like-rotator {
- color: $toolicon_colour;
+ font-size: 1rem;
}
-.comment-icon {
- font-size: 0.833em;
- color: $toolicon_colour;
-}
-.comment-edit-text-empty,
-.comment-edit-text-full {
+.comment-edit-text {
border: 1px solid #ccc;
- border-radius: $radiuspx;
-}
-
-.comment-edit-text-empty {
- color: gray;
- font-size: 12px;
-}
-
-.comment-edit-text-full {
- color: black;
+ border-radius: $radius;
}
.divgrow-showmore {
@@ -1475,19 +1173,12 @@ img.mail-conv-sender-photo {
.widget {
background-color: rgba(254,254,254,.5);
border: 1px solid rgba(254,254,254,.5);
- -moz-border-radius: $radiuspx;
- -webkit-border-radius: $radiuspx;
- border-radius: $radiuspx;
-}
-
-.widget h3 {
- color: $toolicon_colour;
+ border-radius: $radius;
}
#note-text {
border: 1px solid #ccc;
- border-radius: $radiuspx;
- -moz-border-radius: $radiuspx;
+ border-radius: $radius;
}
.fileas-ul {
@@ -1496,8 +1187,7 @@ img.mail-conv-sender-photo {
#datebrowse-sidebar select {
border: 1px solid #ccc;
- border-radius: $radiuspx;
- -moz-border-radius: $radiuspx;
+ border-radius: $radius;
}
.thing-show img {
@@ -1519,63 +1209,50 @@ img.mail-conv-sender-photo {
.chat-item-photo,
.chat-item-photo-self {
- border-radius: $radiuspx;
+ border-radius: $radius;
}
.chat-item-title,
.chat-item-title-self {
- border-radius: $radiuspx;
+ border-radius: $radius;
background-color: $item_colour;
}
#chatMembers img {
- border-radius: $radiuspx;
-}
-
-/* nav bootstrap */
-
-nav img {
- border-radius: $radiuspx;
-}
-
-nav .dropdown-menu {
- font-size: $body_font_size;
- border-top-right-radius: 0px;
- border-top-left-radius: 0px;
- border-bottom-right-radius: $radiuspx;
- border-bottom-left-radius: $radiuspx;
+ border-radius: $radius;
}
-.dropdown-menu > .active > a,
-.dropdown-menu > .active > a:focus,
-.dropdown-menu > .active > a:hover {
- color: #333;
- background-color: #f5f5f5;
-}
-
-.dropdown-menu-img-sm {
- float: left;
- width: 36px;
- height: 36px;
+.menu-img-3 {
+ width: 3.3em;
+ height: 3.3em;
margin-right: 5px;
+ border-radius: $radius;
+ float: left;
}
-.dropdown-menu-img-xs {
- height: 18px;
- width: 18px;
+.menu-img-2 {
+ height: 2.2em;
+ width: 2.2em;
margin-right: 5px;
+ border-radius: $radius;
+ float: left;
}
-#usermenu-caret {
- color: $nav_icon_colour;
+.menu-img-1 {
+ height: 1.5em;
+ width: 1.5em;
+ margin-right: 5px;
+ border-radius: $radius;
}
-.usermenu-head {
- float: left;
+.usermenu {
+ width: 3.75rem;
}
-.usermenu-head:hover #usermenu-caret {
- color: $nav_active_icon_colour;
+#avatar {
+ width: 2.35rem;
+ height: 2.35rem;
+ border-radius: $radius;
}
.page-title {
@@ -1585,20 +1262,21 @@ nav .dropdown-menu {
.generic-content-wrapper-styled {
background-color: $bgcolour;
padding: 10px;
- border-radius: $radiuspx;
+ border-radius: $radius;
}
.generic-content-wrapper {
border: 1px solid #ccc;
box-shadow: 0px 0px 5px 1px rgba(0,0,0,0.2);
- border-radius: $radiuspx;
+ border-radius: $radius;
+ margin-bottom: 1.5rem;
}
.section-title-wrapper {
padding: 7px 10px;
background-color: $item_colour;
- border-top-left-radius: $radiuspx;
- border-top-right-radius: $radiuspx;
+ border-top-left-radius: $radius;
+ border-top-right-radius: $radius;
border-bottom: 3px solid $comment_item_colour;
}
@@ -1611,8 +1289,12 @@ nav .dropdown-menu {
text-overflow: ellipsis;
}
+.section-subtitle-wrapper h3 {
+ padding: 3px;
+}
+
.section-subtitle-wrapper {
- padding: 7px 10px;
+ padding: 4px 10px;
background-color: $item_colour;
border-bottom: 3px solid $comment_item_colour;
}
@@ -1625,24 +1307,24 @@ nav .dropdown-menu {
.section-content-info-wrapper {
padding: 21px 10px;
- color: #31708f;
- background-color: #d9edf7;
+ color: #0c5460;
+ background-color: #d1ecf1;
border-bottom: 3px solid $comment_item_colour;
text-align: center;
}
.section-content-warning-wrapper {
padding: 21px 10px;
- color: #8a6d3b;
- background-color: #fcf8e3;
+ color: #856404;
+ background-color: #fff3cd;
border-bottom: 3px solid $comment_item_colour;
text-align: center;
}
.section-content-danger-wrapper {
padding: 21px 10px;
- color: #a94442;
- background-color: #f2dede;
+ color: #721c24;
+ background-color: #f8d7da;
border-bottom: 3px solid $comment_item_colour;
text-align: center;
}
@@ -1655,22 +1337,22 @@ nav .dropdown-menu {
.section-content-wrapper .section-content-danger-wrapper {
margin-bottom: 10px;
border-bottom: none;
- border-radius: $radiuspx;
+ border-radius: $radius;
}
.section-content-wrapper {
padding: 7px 10px;
background-color: $comment_item_colour;
- border-bottom-left-radius: $radiuspx;
- border-bottom-right-radius: $radiuspx;
+ border-bottom-left-radius: $radius;
+ border-bottom-right-radius: $radius;
word-wrap: break-word;
}
.section-content-wrapper-np {
background-color: $comment_item_colour;
- border-bottom-left-radius: $radiuspx;
- border-bottom-right-radius: $radiuspx;
+ border-bottom-left-radius: $radius;
+ border-bottom-right-radius: $radius;
word-wrap: break-word;
}
@@ -1687,6 +1369,7 @@ main.fullscreen .generic-content-wrapper {
top: 0px;
left: 0px;
border-radius: 0px;
+ border-width: 0px;
}
main.fullscreen .section-title-wrapper {
@@ -1723,157 +1406,80 @@ main.fullscreen .section-content-wrapper-np {
background-color: $item_colour;
}
-nav ul li .undefined,
-nav ul li .notify-seen,
-nav ul li .notify-unseen
- {
- max-height: 3rem;
+.notify-seen {
+ background-color: $item_colour;
}
-
/* bootstrap overrides */
-.panel {
- background-color: transparent;
- border: 0px solid transparent;
- border-radius: 0px;
- -webkit-box-shadow: 0 0px 0px rgba(0, 0, 0, .0);
- box-shadow: 0 0px 0px rgba(0, 0, 0, .0);
+.btn,
+.form-control,
+.nav-pills .nav-link,
+.nav-tabs .nav-link {
+ border-radius: $radius;
}
-.panel-group .panel + .panel {
- margin-top: 0px;
+.rounded-top {
+ border-top-left-radius: $radius !important;
+ border-top-right-radius: $radius !important;
}
blockquote {
- font-size: $font_size;
+ font-size: 1rem;
font-style: italic;
border-left: 3px solid #ccc;
padding: 1em 0px 1em 1.5em;
margin: 0px;
}
-.badge {
- border-radius: $radiuspx;
-}
-
-nav .badge.home-update,
-nav .badge.notify-update,
-nav .badge.intro-update,
-nav .badge.mail-update {
- background-color: #C9302C;
-}
-
.dropdown-menu {
- font-size: $body_font_size;
- border-radius: $radiuspx;
-}
-
-.dropdown-menu img {
- border-radius: $radiuspx;
-}
-
-.navbar-inverse {
- background-image: -webkit-linear-gradient(top, $nav_gradient_top 0%, $nav_gradient_bottom 100%);
- background-image: linear-gradient(to bottom, $nav_gradient_top 0%, $nav_gradient_bottom 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr=$nav_gradient_top, endColorstr=$nav_gradient_bottom, GradientType=0);
- background-color: $nav_bg;
- border-color: $nav_bd;
-}
-
-.navbar-inverse .navbar-collapse {
- border-color: $nav_bd;
-}
-
-.navbar-inverse .navbar-nav > .active > a {
- background-image: -webkit-linear-gradient(top, $nav_active_gradient_top 0%, $nav_active_gradient_bottom 100%);
- background-image: linear-gradient(to bottom, $nav_active_gradient_top 0%, $nav_active_gradient_bottom 100%);
- filter: progid:DXImageTransform.Microsoft.gradient(startColorstr=$nav_active_gradient_top, endColorstr=$nav_active_gradient_bottom, GradientType=0);
+ color: $font_colour;
+ font-size: 0.9rem;
+ border-radius: $radius;
}
-
-.navbar-inverse .navbar-nav > li > a {
- color: $nav_icon_colour;
+.dropdown-item {
+ color: $font_colour;
}
-.navbar-inverse .navbar-nav > li > a:hover,
-.navbar-inverse .navbar-nav > li > a:focus {
- color: $nav_active_icon_colour;
+.dropdown-item:active,
+.dropdown-item:focus,
+.dropdown-item:hover,
+.textcomplete-item:focus .dropdown-item,
+.textcomplete-item:hover .dropdown-item,
+.textcomplete-item.active .dropdown-item,
+.textcomplete-item:active .dropdown-item {
+ color: $font_colour;
+ background-color: $item_colour;
}
-.navbar-inverse .navbar-nav > .active > a,
-.navbar-inverse .navbar-nav > .active > a:hover,
-.navbar-inverse .navbar-nav > .active > a:focus {
- color: $nav_active_icon_colour;
+.dropdown-item.active {
+ color: #fff;
+ background-color: #007bff;
}
-.navbar-inverse .navbar-nav > .open > a,
-.navbar-inverse .navbar-nav > .open > a:hover,
-.navbar-inverse .navbar-nav > .open > a:focus {
- background-color: $nav_bd;
- color: $nav_active_icon_colour;
+.bg-dark {
+ background-color: $nav_bg !important;
}
-.navbar-inverse .navbar-toggle {
- border-color: $nav_bd;
-}
-.navbar-inverse .navbar-toggle:hover,
-.navbar-inverse .navbar-toggle:focus {
- background-color: $nav_bg;
+.navbar {
+ z-index:1030;
}
-.navbar-inverse .navbar-toggle .icon-bar {
- background-color: $nav_active_icon_colour;
+.navbar-dark .navbar-nav .nav-link,
+.usermenu i {
+ color: $nav_icon_colour;
}
-#expand-aside,
-#expand-tabs,
-#doco-return-to-top-btn,
-#context-help-btn,
-#notifications-btn,
-#login_nav_btn_collapse {
+.navbar-dark .navbar-nav .nav-link:focus,
+.navbar-dark .navbar-nav .nav-link:hover,
+.usermenu:focus i,
+.usermenu:hover i {
color: $nav_active_icon_colour;
- padding: 7px 10px;
-}
-
-.nav-tabs.nav-justified {
- background-color: rgba(254,254,254,.5);
- border-top-left-radius: 4px;
- border-top-right-radius: 4px;
-}
-
-.nav-tabs.nav-justified > .active > a,
-.nav-tabs.nav-justified > .active > a:hover,
-.nav-tabs.nav-justified > .active > a:focus {
- border-bottom-color: transparent;
-}
-
-.nav-tabs > li.active > a,
-.nav-tabs > li.active > a:hover,
-.nav-tabs > li.active > a:focus {
- background-color: transparent;
-}
-
-#tabs-collapse-1 {
- padding: 0px;
- margin-bottom: 25px;
-}
-
-.btn {
- font-size: $body_font_size;
-}
-
-.btn-xs {
- font-size: 0.75rem;
-}
-
-.btn-default {
- background-color: transparent;
}
@media screen and (max-width: 767px) {
aside#region_1 {
- background: rgba(0, 0, 0, .1);
border-right: 1px solid $nav_bd;
}
@@ -1886,33 +1492,6 @@ nav .badge.mail-update {
left: 0px;
}
- .thread-wrapper.toplevel_item {
- width: 100%;
- border:1px;
- }
-
- .wall-item-photo {
- width: 48px !important;
- height: 48px !important;
- }
-
- .comment .wall-item-photo {
- width: 32px !important;
- height: 32px !important;
- }
-
- .acl-list-item {
- width: 98%; /* fallback if browser does not support calc() */
- width: calc(100% - 10px);
- }
-
-}
-
-/* release the navbar in landscape view on small devices */
-@media screen and (max-height: 320px) {
- .navbar-fixed-top {
- position: absolute;
- }
}
.shareable_element_text {
@@ -1961,7 +1540,7 @@ dl.bb-dl > dd > li {
font-weight: normal;
font-style: normal;
text-decoration: inherit;
- content:"\f069";
+ content:"\f069 ";
}
/* Modified original CSS to match input in Redbasic */
@@ -1970,7 +1549,7 @@ dl.bb-dl > dd > li {
margin-bottom: 0px;
box-shadow: none;
display: inline-block;
- border-radius: $radiuspx;
+ border-radius: $radius;
cursor: text;
padding: 0px 10px;
width: 100%;
@@ -1988,31 +1567,31 @@ dl.bb-dl > dd > li {
/* Turn checkboxes into switches */
-.field.checkbox > div {
+.form-group.checkbox > div {
position: relative; width: 60px;
-webkit-user-select:none; -moz-user-select:none; -ms-user-select: none;
display:inline-block;
}
-.field.checkbox input {
+.form-group.checkbox input {
display: none;
}
-.field.checkbox > div label {
+.form-group.checkbox > div label {
display: block; overflow: hidden; cursor: pointer;
border: 1px solid #ccc;
- border-radius: 4px;
+ border-radius: $radius;
margin:0px;
-webkit-transition: border-color ease-in-out .15s, -webkit-box-shadow ease-in-out .15s;
-o-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
}
-.field.checkbox:hover label {
+.form-group.checkbox:hover label {
color: $link_colour;
}
-.field.checkbox:hover > div label {
+.form-group.checkbox:hover > div label {
border-color: $link_colour;
}
@@ -2051,13 +1630,13 @@ dl.bb-dl > dd > li {
-o-transition: all 0.3s ease-in 0s; transition: all 0.3s ease-in 0s;
}
-.field.checkbox > div > input:checked + label .onoffswitch-inner {
+.form-group.checkbox > div > input:checked + label .onoffswitch-inner {
margin-left: 0px;
}
-.field.checkbox > div > input:checked + label .onoffswitch-switch {
+.form-group.checkbox > div > input:checked + label .onoffswitch-switch {
right: 0px;
- background-color: #337AB7;
+ background-color: #0275d8;
}
.help-searchlist {
@@ -2080,30 +1659,25 @@ dl.bb-dl > dd > li {
#ace-editor,
#editor {
- border-bottom-left-radius: $radiuspx;
- border-bottom-right-radius: $radiuspx;
+ border-bottom-left-radius: $radius;
+ border-bottom-right-radius: $radius;
}
-.sub-menu {
- margin-top: 10px;
- padding-left: 15px;
- border-left: 3px solid #eee;
-}
-
-.nav-pills-stacked-icons {
- padding: 6px 10px;
- float: right;
- position: relative;
- z-index:1;
+.sub-menu-wrapper {
+ padding-left: 1rem;
+ display: none;
}
-.nav-pills-stacked-icons:hover + a {
- background-color: #eee;
+.sub-menu {
+ width: 100%;
+ margin-top: 0.5rem;
+ padding-left: 1rem;
+ border-left: 0.2rem solid #eee;
}
.app-icon {
+ color: #777;
font-size: 80px;
- color: $toolicon_colour;
text-shadow: 3px 3px 3px lightgrey;
}
@@ -2117,6 +1691,7 @@ dl.bb-dl > dd > li {
margin-left: auto;
margin-right: auto;
}
+
#permcat-index {
margin: 10px;
}
diff --git a/view/theme/redbasic/img/bbedit.png b/view/theme/redbasic/img/bbedit.png
deleted file mode 100644
index b89f2f7a8..000000000
--- a/view/theme/redbasic/img/bbedit.png
+++ /dev/null
Binary files differ
diff --git a/view/theme/redbasic/img/border.jpg b/view/theme/redbasic/img/border.jpg
deleted file mode 100644
index 034a1cb63..000000000
--- a/view/theme/redbasic/img/border.jpg
+++ /dev/null
Binary files differ
diff --git a/view/theme/redbasic/img/editicons.png b/view/theme/redbasic/img/editicons.png
deleted file mode 100644
index 171a40876..000000000
--- a/view/theme/redbasic/img/editicons.png
+++ /dev/null
Binary files differ
diff --git a/view/theme/redbasic/img/ff-16.jpg b/view/theme/redbasic/img/ff-16.jpg
deleted file mode 100644
index 3621f5914..000000000
--- a/view/theme/redbasic/img/ff-16.jpg
+++ /dev/null
Binary files differ
diff --git a/view/theme/redbasic/img/file.gif b/view/theme/redbasic/img/file.gif
deleted file mode 100644
index c532335ed..000000000
--- a/view/theme/redbasic/img/file.gif
+++ /dev/null
Binary files differ
diff --git a/view/theme/redbasic/img/friendika-16.png b/view/theme/redbasic/img/friendika-16.png
deleted file mode 100644
index 1a742ecdc..000000000
--- a/view/theme/redbasic/img/friendika-16.png
+++ /dev/null
Binary files differ
diff --git a/view/theme/redbasic/img/jotperms.png b/view/theme/redbasic/img/jotperms.png
deleted file mode 100644
index d133a6e01..000000000
--- a/view/theme/redbasic/img/jotperms.png
+++ /dev/null
Binary files differ
diff --git a/view/theme/redbasic/img/login-bg.gif b/view/theme/redbasic/img/login-bg.gif
deleted file mode 100644
index cde836c89..000000000
--- a/view/theme/redbasic/img/login-bg.gif
+++ /dev/null
Binary files differ
diff --git a/view/theme/redbasic/img/notify_on.png b/view/theme/redbasic/img/notify_on.png
deleted file mode 100644
index 18002e15c..000000000
--- a/view/theme/redbasic/img/notify_on.png
+++ /dev/null
Binary files differ
diff --git a/view/theme/redbasic/img/photo-menu.jpg b/view/theme/redbasic/img/photo-menu.jpg
deleted file mode 100644
index fde5eb535..000000000
--- a/view/theme/redbasic/img/photo-menu.jpg
+++ /dev/null
Binary files differ
diff --git a/view/theme/redbasic/img/shiny.png b/view/theme/redbasic/img/shiny.png
deleted file mode 100644
index 994c0d05d..000000000
--- a/view/theme/redbasic/img/shiny.png
+++ /dev/null
Binary files differ
diff --git a/view/theme/redbasic/js/redbasic.js b/view/theme/redbasic/js/redbasic.js
index 81a95c68b..04199ea95 100644
--- a/view/theme/redbasic/js/redbasic.js
+++ b/view/theme/redbasic/js/redbasic.js
@@ -16,14 +16,27 @@ $(document).ready(function() {
}
$('#css3-calc').remove(); // Remove the test element
- if($(window).width() > 767) {
+ if($(window).width() >= 767) {
$('#left_aside_wrapper').stick_in_parent({
- offset_top: $('nav').outerHeight(true),
- parent: '#region_1',
+ offset_top: parseInt($('aside').css('padding-top')),
+ parent: 'main',
spacer: '#left_aside_spacer'
});
}
+ if($(window).width() >= 1200) {
+ $('#right_aside_wrapper').stick_in_parent({
+ offset_top: parseInt($('aside').css('padding-top')),
+ parent: 'main',
+ spacer: '#right_aside_spacer'
+ });
+ }
+
+
+ $('#notifications_wrapper.fs #notifications').stick_in_parent({
+ parent: '#notifications_wrapper'
+ });
+
$('#expand-aside').on('click', toggleAside);
$('section').on('click', function() {
@@ -41,29 +54,49 @@ $(document).ready(function() {
}
});
- if($('#left_aside_wrapper').length && $('#left_aside_wrapper').html().length === 0) {
- $('#expand-aside').hide();
- }
- $('#expand-tabs').click(function() {
- if(!$('#tabs-collapse-1').hasClass('in')){
- $('html, body').animate({ scrollTop: 0 }, 'slow');
+ var right_aside_height = $('#rightt_aside_wrapper').height();
+
+ $('#right_aside_wrapper').on('click', function() {
+ if(right_aside_height != $('#right_aside_wrapper').height()) {
+ $(document.body).trigger("sticky_kit:recalc");
+ right_aside_height = $('#right_aside_wrapper').height();
}
- $('#expand-tabs-icon').toggleClass('fa-arrow-circle-down').toggleClass('fa-arrow-circle-up');
});
- $('.usermenu-head').click(function() {
- if($('#navbar-collapse-1, #navbar-collapse-2').hasClass('in')){
- $('#navbar-collapse-1, #navbar-collapse-2').removeClass('in');
+ $('.usermenu').click(function() {
+ if($('#navbar-collapse-1, #navbar-collapse-2').hasClass('show')){
+ $('#navbar-collapse-1, #navbar-collapse-2').removeClass('show');
+ }
+ });
+
+ $('#menu-btn').click(function() {
+ if($('#navbar-collapse-1').hasClass('show')){
+ $('#navbar-collapse-1').removeClass('show');
+ }
+ });
+
+ $('#notifications-btn').click(function() {
+ if($('#navbar-collapse-2').hasClass('show')){
+ $('#navbar-collapse-2').removeClass('show');
+ }
+ });
+
+ var notifications_parent = $('#notifications_wrapper')[0].parentElement.id;
+ $('#notifications-btn').click(function() {
+ if($('#notifications_wrapper').hasClass('fs'))
+ $('#notifications_wrapper').prependTo('#' + notifications_parent);
+ else
+ $('#notifications_wrapper').prependTo('section');
+
+ $('#notifications_wrapper').toggleClass('fs');
+ if($('#navbar-collapse-2').hasClass('show')){
+ $('#navbar-collapse-2').removeClass('show');
}
});
-
- if($('#tabs-collapse-1').length === 0) {
- $('#expand-tabs').hide();
- }
$("input[data-role=cat-tagsinput]").tagsinput({
- tagClass: 'label label-primary'
+ tagClass: 'badge badge-pill badge-warning text-dark'
});
var doctitle = document.title;
@@ -81,17 +114,14 @@ $(document).ready(function() {
function makeFullScreen(full) {
if(typeof full=='undefined' || full == true) {
- $('main').css({'transition': 'none'}).addClass('fullscreen');
- $('header, nav, aside, #fullscreen-btn').hide();
- $('#tabs-collapse-1').css({'visibility': 'hidden'});
+ $('main').addClass('fullscreen');
+ $('header, nav, aside, #fullscreen-btn').attr('style','display:none !important');
$('#inline-btn').show();
}
else {
$('main').removeClass('fullscreen');
$('header, nav, aside, #fullscreen-btn').show();
- $('#tabs-collapse-1').css({'visibility': ''});
$('#inline-btn').hide();
- $('main').css({'transition': ''});
$(document.body).trigger("sticky_kit:recalc");
}
}
@@ -109,7 +139,7 @@ function toggleAside() {
$('main').addClass('region_1-on')
$('<div id="overlay"></div>').appendTo('section');
$('#left_aside_wrapper').stick_in_parent({
- offset_top: $('nav').outerHeight(true) - 10,
+ offset_top: $('nav').outerHeight(true) + 10,
parent: '#region_1',
spacer: '#left_aside_spacer'
});
diff --git a/view/theme/redbasic/php/config.php b/view/theme/redbasic/php/config.php
index b03e94e46..f98182739 100644
--- a/view/theme/redbasic/php/config.php
+++ b/view/theme/redbasic/php/config.php
@@ -5,10 +5,20 @@ namespace Zotlabs\Theme;
class RedbasicConfig {
function get_schemas() {
- $scheme_choices = array();
- $scheme_choices["---"] = t("Focus (Hubzilla default)");
$files = glob('view/theme/redbasic/schema/*.php');
+
+ $scheme_choices = [];
+
if($files) {
+
+ if(in_array('view/theme/redbasic/schema/default.php', $files)) {
+ $scheme_choices['---'] = t('Default');
+ $scheme_choices['focus'] = t('Focus (Hubzilla default)');
+ }
+ else {
+ $scheme_choices['---'] = t('Focus (Hubzilla default)');
+ }
+
foreach($files as $file) {
$f = basename($file, ".php");
if($f != 'default') {
@@ -17,6 +27,7 @@ class RedbasicConfig {
}
}
}
+
return $scheme_choices;
}
@@ -28,11 +39,6 @@ class RedbasicConfig {
$arr = array();
$arr['narrow_navbar'] = get_pconfig(local_channel(),'redbasic', 'narrow_navbar' );
$arr['nav_bg'] = get_pconfig(local_channel(),'redbasic', 'nav_bg' );
- $arr['nav_gradient_top'] = get_pconfig(local_channel(),'redbasic', 'nav_gradient_top' );
- $arr['nav_gradient_bottom'] = get_pconfig(local_channel(),'redbasic', 'nav_gradient_bottom' );
- $arr['nav_active_gradient_top'] = get_pconfig(local_channel(),'redbasic', 'nav_active_gradient_top' );
- $arr['nav_active_gradient_bottom'] = get_pconfig(local_channel(),'redbasic', 'nav_active_gradient_bottom' );
- $arr['nav_bd'] = get_pconfig(local_channel(),'redbasic', 'nav_bd' );
$arr['nav_icon_colour'] = get_pconfig(local_channel(),'redbasic', 'nav_icon_colour' );
$arr['nav_active_icon_colour'] = get_pconfig(local_channel(),'redbasic', 'nav_active_icon_colour' );
$arr['link_colour'] = get_pconfig(local_channel(),'redbasic', 'link_colour' );
@@ -41,18 +47,11 @@ class RedbasicConfig {
$arr['background_image'] = get_pconfig(local_channel(),'redbasic', 'background_image' );
$arr['item_colour'] = get_pconfig(local_channel(),'redbasic', 'item_colour' );
$arr['comment_item_colour'] = get_pconfig(local_channel(),'redbasic', 'comment_item_colour' );
- $arr['comment_border_colour'] = get_pconfig(local_channel(),'redbasic', 'comment_border_colour' );
- $arr['comment_indent'] = get_pconfig(local_channel(),'redbasic', 'comment_indent' );
- $arr['toolicon_colour'] = get_pconfig(local_channel(),'redbasic','toolicon_colour');
- $arr['toolicon_activecolour'] = get_pconfig(local_channel(),'redbasic','toolicon_activecolour');
$arr['font_size'] = get_pconfig(local_channel(),'redbasic', 'font_size' );
- $arr['body_font_size'] = get_pconfig(local_channel(),'redbasic', 'body_font_size' );
$arr['font_colour'] = get_pconfig(local_channel(),'redbasic', 'font_colour' );
$arr['radius'] = get_pconfig(local_channel(),'redbasic', 'radius' );
$arr['shadow'] = get_pconfig(local_channel(),'redbasic', 'photo_shadow' );
$arr['converse_width']=get_pconfig(local_channel(),"redbasic","converse_width");
- $arr['align_left']=get_pconfig(local_channel(),"redbasic","align_left");
- $arr['nav_min_opacity']=get_pconfig(local_channel(),"redbasic","nav_min_opacity");
$arr['top_photo']=get_pconfig(local_channel(),"redbasic","top_photo");
$arr['reply_photo']=get_pconfig(local_channel(),"redbasic","reply_photo");
return $this->form($arr);
@@ -66,11 +65,6 @@ class RedbasicConfig {
if (isset($_POST['redbasic-settings-submit'])) {
set_pconfig(local_channel(), 'redbasic', 'narrow_navbar', $_POST['redbasic_narrow_navbar']);
set_pconfig(local_channel(), 'redbasic', 'nav_bg', $_POST['redbasic_nav_bg']);
- set_pconfig(local_channel(), 'redbasic', 'nav_gradient_top', $_POST['redbasic_nav_gradient_top']);
- set_pconfig(local_channel(), 'redbasic', 'nav_gradient_bottom', $_POST['redbasic_nav_gradient_bottom']);
- set_pconfig(local_channel(), 'redbasic', 'nav_active_gradient_top', $_POST['redbasic_nav_active_gradient_top']);
- set_pconfig(local_channel(), 'redbasic', 'nav_active_gradient_bottom', $_POST['redbasic_nav_active_gradient_bottom']);
- set_pconfig(local_channel(), 'redbasic', 'nav_bd', $_POST['redbasic_nav_bd']);
set_pconfig(local_channel(), 'redbasic', 'nav_icon_colour', $_POST['redbasic_nav_icon_colour']);
set_pconfig(local_channel(), 'redbasic', 'nav_active_icon_colour', $_POST['redbasic_nav_active_icon_colour']);
set_pconfig(local_channel(), 'redbasic', 'link_colour', $_POST['redbasic_link_colour']);
@@ -79,18 +73,11 @@ class RedbasicConfig {
set_pconfig(local_channel(), 'redbasic', 'background_image', $_POST['redbasic_background_image']);
set_pconfig(local_channel(), 'redbasic', 'item_colour', $_POST['redbasic_item_colour']);
set_pconfig(local_channel(), 'redbasic', 'comment_item_colour', $_POST['redbasic_comment_item_colour']);
- set_pconfig(local_channel(), 'redbasic', 'comment_border_colour', $_POST['redbasic_comment_border_colour']);
- set_pconfig(local_channel(), 'redbasic', 'comment_indent', $_POST['redbasic_comment_indent']);
- set_pconfig(local_channel(), 'redbasic', 'toolicon_colour', $_POST['redbasic_toolicon_colour']);
- set_pconfig(local_channel(), 'redbasic', 'toolicon_activecolour', $_POST['redbasic_toolicon_activecolour']);
set_pconfig(local_channel(), 'redbasic', 'font_size', $_POST['redbasic_font_size']);
- set_pconfig(local_channel(), 'redbasic', 'body_font_size', $_POST['redbasic_body_font_size']);
set_pconfig(local_channel(), 'redbasic', 'font_colour', $_POST['redbasic_font_colour']);
set_pconfig(local_channel(), 'redbasic', 'radius', $_POST['redbasic_radius']);
set_pconfig(local_channel(), 'redbasic', 'photo_shadow', $_POST['redbasic_shadow']);
set_pconfig(local_channel(), 'redbasic', 'converse_width', $_POST['redbasic_converse_width']);
- set_pconfig(local_channel(), 'redbasic', 'align_left', $_POST['redbasic_align_left']);
- set_pconfig(local_channel(), 'redbasic', 'nav_min_opacity', $_POST['redbasic_nav_min_opacity']);
set_pconfig(local_channel(), 'redbasic', 'top_photo', $_POST['redbasic_top_photo']);
set_pconfig(local_channel(), 'redbasic', 'reply_photo', $_POST['redbasic_reply_photo']);
}
@@ -110,31 +97,19 @@ class RedbasicConfig {
'$title' => t("Theme settings"),
'$narrow_navbar' => array('redbasic_narrow_navbar',t('Narrow navbar'),$arr['narrow_navbar'], '', array(t('No'),t('Yes'))),
'$nav_bg' => array('redbasic_nav_bg', t('Navigation bar background color'), $arr['nav_bg']),
- '$nav_gradient_top' => array('redbasic_nav_gradient_top', t('Navigation bar gradient top color'), $arr['nav_gradient_top']),
- '$nav_gradient_bottom' => array('redbasic_nav_gradient_bottom', t('Navigation bar gradient bottom color'), $arr['nav_gradient_bottom']),
- '$nav_active_gradient_top' => array('redbasic_nav_active_gradient_top', t('Navigation active button gradient top color'), $arr['nav_active_gradient_top']),
- '$nav_active_gradient_bottom' => array('redbasic_nav_active_gradient_bottom', t('Navigation active button gradient bottom color'), $arr['nav_active_gradient_bottom']),
- '$nav_bd' => array('redbasic_nav_bd', t('Navigation bar border color '), $arr['nav_bd']),
'$nav_icon_colour' => array('redbasic_nav_icon_colour', t('Navigation bar icon color '), $arr['nav_icon_colour']),
'$nav_active_icon_colour' => array('redbasic_nav_active_icon_colour', t('Navigation bar active icon color '), $arr['nav_active_icon_colour']),
- '$link_colour' => array('redbasic_link_colour', t('link color'), $arr['link_colour'], '', $link_colours),
+ '$link_colour' => array('redbasic_link_colour', t('Link color'), $arr['link_colour'], '', $link_colours),
'$banner_colour' => array('redbasic_banner_colour', t('Set font-color for banner'), $arr['banner_colour']),
'$bgcolour' => array('redbasic_background_colour', t('Set the background color'), $arr['bgcolour']),
'$background_image' => array('redbasic_background_image', t('Set the background image'), $arr['background_image']),
'$item_colour' => array('redbasic_item_colour', t('Set the background color of items'), $arr['item_colour']),
'$comment_item_colour' => array('redbasic_comment_item_colour', t('Set the background color of comments'), $arr['comment_item_colour']),
- '$comment_border_colour' => array('redbasic_comment_border_colour', t('Set the border color of comments'), $arr['comment_border_colour']),
- '$comment_indent' => array('redbasic_comment_indent', t('Set the indent for comments'), $arr['comment_indent']),
- '$toolicon_colour' => array('redbasic_toolicon_colour',t('Set the basic color for item icons'),$arr['toolicon_colour']),
- '$toolicon_activecolour' => array('redbasic_toolicon_activecolour',t('Set the hover color for item icons'),$arr['toolicon_activecolour']),
- '$body_font_size' => array('redbasic_body_font_size', t('Set font-size for the entire application'), $arr['body_font_size'], t('Example: 14px')),
- '$font_size' => array('redbasic_font_size', t('Set font-size for posts and comments'), $arr['font_size']),
+ '$font_size' => array('redbasic_font_size', t('Set font-size for the entire application'), $arr['font_size'], t('Examples: 1rem, 100%, 16px')),
'$font_colour' => array('redbasic_font_colour', t('Set font-color for posts and comments'), $arr['font_colour']),
- '$radius' => array('redbasic_radius', t('Set radius of corners'), $arr['radius']),
+ '$radius' => array('redbasic_radius', t('Set radius of corners'), $arr['radius'], t('Example: 4px')),
'$shadow' => array('redbasic_shadow', t('Set shadow depth of photos'), $arr['shadow']),
'$converse_width' => array('redbasic_converse_width',t('Set maximum width of content region in pixel'),$arr['converse_width'], t('Leave empty for default width')),
- '$align_left' => array('redbasic_align_left',t('Left align page content'),$arr['align_left'], '', array(t('No'),t('Yes'))),
- '$nav_min_opacity' => array('redbasic_nav_min_opacity',t('Set minimum opacity of nav bar - to hide it'),$arr['nav_min_opacity']),
'$top_photo' => array('redbasic_top_photo', t('Set size of conversation author photo'), $arr['top_photo']),
'$reply_photo' => array('redbasic_reply_photo', t('Set size of followup author photos'), $arr['reply_photo']),
));
diff --git a/view/theme/redbasic/php/style.php b/view/theme/redbasic/php/style.php
index 9b994ebdf..91cc0b85b 100644
--- a/view/theme/redbasic/php/style.php
+++ b/view/theme/redbasic/php/style.php
@@ -10,34 +10,22 @@ if(! App::$install) {
}
// Load the owners pconfig
- $nav_bg = get_pconfig($uid, "redbasic", "nav_bg");
- $nav_gradient_top = get_pconfig($uid, "redbasic", "nav_gradient_top");
- $nav_gradient_bottom = get_pconfig($uid, "redbasic", "nav_gradient_bottom");
- $nav_active_gradient_top = get_pconfig($uid, "redbasic", "nav_active_gradient_top");
- $nav_active_gradient_bottom = get_pconfig($uid, "redbasic", "nav_active_gradient_bottom");
- $nav_bd = get_pconfig($uid, "redbasic", "nav_bd");
- $nav_icon_colour = get_pconfig($uid, "redbasic", "nav_icon_colour");
- $nav_active_icon_colour = get_pconfig($uid, "redbasic", "nav_active_icon_colour");
- $narrow_navbar = get_pconfig($uid,'redbasic','narrow_navbar');
+ $nav_bg = get_pconfig($uid, 'redbasic', 'nav_bg');
+ $nav_icon_colour = get_pconfig($uid, 'redbasic', 'nav_icon_colour');
+ $nav_active_icon_colour = get_pconfig($uid, 'redbasic', 'nav_active_icon_colour');
$banner_colour = get_pconfig($uid,'redbasic','banner_colour');
- $link_colour = get_pconfig($uid, "redbasic", "link_colour");
+ $narrow_navbar = get_pconfig($uid,'redbasic','narrow_navbar');
+ $link_colour = get_pconfig($uid, 'redbasic', 'link_colour');
$schema = get_pconfig($uid,'redbasic','schema');
- $bgcolour = get_pconfig($uid, "redbasic", "background_colour");
- $background_image = get_pconfig($uid, "redbasic", "background_image");
- $toolicon_colour = get_pconfig($uid,'redbasic','toolicon_colour');
- $toolicon_activecolour = get_pconfig($uid,'redbasic','toolicon_activecolour');
- $item_colour = get_pconfig($uid, "redbasic", "item_colour");
- $comment_item_colour = get_pconfig($uid, "redbasic", "comment_item_colour");
- $comment_border_colour = get_pconfig($uid, "redbasic", "comment_border_colour");
- $comment_indent = get_pconfig($uid, "redbasic", "comment_indent");
- $body_font_size = get_pconfig($uid, "redbasic", "body_font_size");
- $font_size = get_pconfig($uid, "redbasic", "font_size");
- $font_colour = get_pconfig($uid, "redbasic", "font_colour");
- $radius = get_pconfig($uid, "redbasic", "radius");
- $shadow = get_pconfig($uid,"redbasic","photo_shadow");
- $converse_width=get_pconfig($uid,"redbasic","converse_width");
- $align_left=get_pconfig($uid,"redbasic","align_left");
- $nav_min_opacity=get_pconfig($uid,'redbasic','nav_min_opacity');
+ $bgcolour = get_pconfig($uid, 'redbasic', 'background_colour');
+ $background_image = get_pconfig($uid, 'redbasic', 'background_image');
+ $item_colour = get_pconfig($uid, 'redbasic', 'item_colour');
+ $comment_item_colour = get_pconfig($uid, 'redbasic', 'comment_item_colour');
+ $font_size = get_pconfig($uid, 'redbasic', 'font_size');
+ $font_colour = get_pconfig($uid, 'redbasic', 'font_colour');
+ $radius = get_pconfig($uid, 'redbasic', 'radius');
+ $shadow = get_pconfig($uid,'redbasic','photo_shadow');
+ $converse_width=get_pconfig($uid,'redbasic','converse_width');
$top_photo=get_pconfig($uid,'redbasic','top_photo');
$reply_photo=get_pconfig($uid,'redbasic','reply_photo');
}
@@ -67,10 +55,9 @@ if (($schema) && ($schema != '---')) {
}
-// If we haven't got a schema, load the default. We shouldn't touch this - we
-// should leave it for admins to define for themselves.
-// default.php and default.css MUST be symlinks to existing schema files.
-if (! $schema) {
+// Allow admins to set a default schema for the hub.
+// default.php and default.css MUST be symlinks to existing schema files in view/theme/redbasic/schema
+if ((!$schema) || ($schema == '---')) {
if(file_exists('view/theme/redbasic/schema/default.php')) {
$schemefile = 'view/theme/redbasic/schema/default.php';
@@ -86,67 +73,39 @@ if (! $schema) {
//Set some defaults - we have to do this after pulling owner settings, and we have to check for each setting
//individually. If we don't, we'll have problems if a user has set one, but not all options.
if (! $nav_bg)
- $nav_bg = "#222";
-if (! $nav_gradient_top)
- $nav_gradient_top = "#3c3c3c";
-if (! $nav_gradient_bottom)
- $nav_gradient_bottom = "#222";
-if (! $nav_active_gradient_top)
- $nav_active_gradient_top = "#222";
-if (! $nav_active_gradient_bottom)
- $nav_active_gradient_bottom = "#282828";
-if (! $nav_bd)
- $nav_bd = "#222";
+ $nav_bg = '#343a40';
if (! $nav_icon_colour)
- $nav_icon_colour = "#999";
+ $nav_icon_colour = 'rgba(255, 255, 255, 0.5)';
if (! $nav_active_icon_colour)
- $nav_active_icon_colour = "#fff";
+ $nav_active_icon_colour = 'rgba(255, 255, 255, 0.75)';
if (! $link_colour)
- $link_colour = "#337AB7";
+ $link_colour = '#007bff';
if (! $banner_colour)
- $banner_colour = "#fff";
+ $banner_colour = '#fff';
if (! $bgcolour)
- $bgcolour = "rgb(254,254,254)";
+ $bgcolour = 'rgb(254,254,254)';
if (! $background_image)
$background_image ='';
if (! $item_colour)
- $item_colour = "rgb(238,238,238)";
+ $item_colour = 'rgb(238,238,238)';
if (! $comment_item_colour)
- $comment_item_colour = "rgb(255,255,255)";
-if (! $comment_border_colour)
- $comment_border_colour = "rgb(255,255,255)";
-if (! $toolicon_colour)
- $toolicon_colour = '#777';
-if (! $toolicon_activecolour)
- $toolicon_activecolour = '#000';
+ $comment_item_colour = 'rgb(255,255,255)';
if (! $item_opacity)
- $item_opacity = "1";
+ $item_opacity = '1';
if (! $font_size)
- $font_size = "0.9rem";
-if (! $body_font_size)
- $body_font_size = "0.75rem";
+ $font_size = '0.875rem';
if (! $font_colour)
- $font_colour = "#4d4d4d";
+ $font_colour = '#4d4d4d';
if (! $radius)
- $radius = "4";
+ $radius = '0.25rem';
if (! $shadow)
- $shadow = "0";
+ $shadow = '0';
if (! $converse_width)
- $converse_width = "790";
+ $converse_width = '790';
if(! $top_photo)
- $top_photo = '48px';
-if(! $comment_indent)
- $comment_indent = '0px';
+ $top_photo = '2.3rem';
if(! $reply_photo)
- $reply_photo = '32px';
-if($nav_min_opacity === false || $nav_min_opacity === '') {
- $nav_float_min_opacity = 1.0;
- $nav_percent_min_opacity = 100;
-}
-else {
- $nav_float_min_opacity = (float) $nav_min_opacity;
- $nav_percent_min_opacity = (int) 100 * $nav_min_opacity;
-}
+ $reply_photo = '2.3rem';
// Apply the settings
if(file_exists('view/theme/redbasic/css/style.css')) {
@@ -157,10 +116,6 @@ if(file_exists('view/theme/redbasic/css/style.css')) {
$x .= file_get_contents('view/theme/redbasic/css/narrow_navbar.css');
}
- if($align_left && file_exists('view/theme/redbasic/css/align_left.css')) {
- $x .= file_get_contents('view/theme/redbasic/css/align_left.css');
- }
-
if($schemecss) {
$x .= $schemecss;
}
@@ -168,22 +123,13 @@ if(file_exists('view/theme/redbasic/css/style.css')) {
$aside_width = 288;
// left aside and right aside are 285px + converse width
- if($align_left) {
- $main_width = (($aside_width) + intval($converse_width));
- }
- else {
- $main_width = (($aside_width * 2) + intval($converse_width));
- }
+ $main_width = (($aside_width * 2) + intval($converse_width));
+
// prevent main_width smaller than 768px
$main_width = (($main_width < 768) ? 768 : $main_width);
$options = array (
'$nav_bg' => $nav_bg,
- '$nav_gradient_top' => $nav_gradient_top,
- '$nav_gradient_bottom' => $nav_gradient_bottom,
- '$nav_active_gradient_top' => $nav_active_gradient_top,
- '$nav_active_gradient_bottom' => $nav_active_gradient_bottom,
- '$nav_bd' => $nav_bd,
'$nav_icon_colour' => $nav_icon_colour,
'$nav_active_icon_colour' => $nav_active_icon_colour,
'$link_colour' => $link_colour,
@@ -192,12 +138,8 @@ if(file_exists('view/theme/redbasic/css/style.css')) {
'$background_image' => $background_image,
'$item_colour' => $item_colour,
'$comment_item_colour' => $comment_item_colour,
- '$comment_border_colour' => $comment_border_colour,
- '$toolicon_colour' => $toolicon_colour,
- '$toolicon_activecolour' => $toolicon_activecolour,
'$font_size' => $font_size,
'$font_colour' => $font_colour,
- '$body_font_size' => $body_font_size,
'$radius' => $radius,
'$shadow' => $shadow,
'$converse_width' => $converse_width,
@@ -207,7 +149,6 @@ if(file_exists('view/theme/redbasic/css/style.css')) {
'$reply_photo' => $reply_photo,
'$pmenu_top' => $pmenu_top,
'$pmenu_reply' => $pmenu_reply,
- '$comment_indent' => $comment_indent,
'$main_width' => $main_width,
'$aside_width' => $aside_width
);
diff --git a/view/theme/redbasic/php/theme.php b/view/theme/redbasic/php/theme.php
index 997b59750..2b90ae85f 100644
--- a/view/theme/redbasic/php/theme.php
+++ b/view/theme/redbasic/php/theme.php
@@ -3,7 +3,9 @@
/**
* * Name: Redbasic
* * Description: Hubzilla standard theme
- * * Version: 1.0
+ * * Version: 2.1
+ * * MinVersion: 2.3.1
+ * * MaxVersion: 6.0
* * Author: Fabrixxm
* * Maintainer: Mike Macgirvin
* * Maintainer: Mario Vavti
diff --git a/view/theme/redbasic/php/theme_init.php b/view/theme/redbasic/php/theme_init.php
index 3179c7078..b12d80ea5 100644
--- a/view/theme/redbasic/php/theme_init.php
+++ b/view/theme/redbasic/php/theme_init.php
@@ -1,19 +1,18 @@
<?php
-head_add_css('library/font_awesome/css/font-awesome.min.css');
-head_add_css('library/bootstrap/css/bootstrap.min.css');
-head_add_css('library/bootstrap-tagsinput/bootstrap-tagsinput.css');
-head_add_css('view/css/bootstrap-red.css');
-head_add_css('library/datetimepicker/jquery.datetimepicker.css');
-//head_add_css('library/colorpicker/css/colorpicker.css');
-head_add_css('library/bootstrap-colorpicker/dist/css/bootstrap-colorpicker.min.css');
+head_add_css('/library/font_awesome/css/font-awesome.min.css');
+head_add_css('/library/bootstrap/css/bootstrap.min.css');
+head_add_css('/library/bootstrap-tagsinput/bootstrap-tagsinput.css');
+head_add_css('/view/css/bootstrap-red.css');
+head_add_css('/library/datetimepicker/jquery.datetimepicker.css');
+head_add_css('/library/bootstrap-colorpicker/dist/css/bootstrap-colorpicker.min.css');
require_once('view/php/theme_init.php');
-head_add_js('library/bootstrap/js/bootstrap.min.js');
-head_add_js('library/bootbox/bootbox.min.js');
-head_add_js('library/bootstrap-tagsinput/bootstrap-tagsinput.js');
-head_add_js('library/datetimepicker/jquery.datetimepicker.js');
-//head_add_js('library/colorpicker/js/colorpicker.js');
-head_add_js('library/bootstrap-colorpicker/dist/js/bootstrap-colorpicker.js');
-//head_add_js('library/bootstrap-colorpicker/src/js/docs.js');
+head_add_js('/library/popper/popper.min.js');
+head_add_js('/library/bootstrap/js/bootstrap.min.js');
+head_add_js('/library/bootbox/bootbox.min.js');
+head_add_js('/library/bootstrap-tagsinput/bootstrap-tagsinput.js');
+head_add_js('/library/datetimepicker/jquery.datetimepicker.js');
+head_add_js('/library/bootstrap-colorpicker/dist/js/bootstrap-colorpicker.js');
+
diff --git a/view/theme/redbasic/schema/BS-Default.css b/view/theme/redbasic/schema/BS-Default.css
new file mode 100644
index 000000000..9045d3b97
--- /dev/null
+++ b/view/theme/redbasic/schema/BS-Default.css
@@ -0,0 +1,7 @@
+.navbar-dark .navbar-toggler {
+ color: rgba(0,0,0,0.7);
+}
+
+#notifications-btn.text-white {
+ color: #777 !important;
+}
diff --git a/view/theme/redbasic/schema/BS-Default.php b/view/theme/redbasic/schema/BS-Default.php
index ce464fe2c..14ee130d9 100644
--- a/view/theme/redbasic/schema/BS-Default.php
+++ b/view/theme/redbasic/schema/BS-Default.php
@@ -1,22 +1,12 @@
<?php
if (! $nav_bg)
- $nav_bg = "#f8f8f8";
- if (! $nav_bd)
- $nav_bd = "#e7e7e7";
- if (! $nav_gradient_top)
- $nav_gradient_top = "#fff";
- if (! $nav_gradient_bottom)
- $nav_gradient_bottom = "#f8f8f8";
- if (! $nav_active_gradient_top)
- $nav_active_gradient_top = "#ebebeb";
- if (! $nav_active_gradient_bottom)
- $nav_active_gradient_bottom = "#f3f3f3";
+ $nav_bg = "#f8f9fa";
if (! $nav_icon_colour)
- $nav_icon_colour = "#777";
+ $nav_icon_colour = "rgba(0, 0, 0, 0.5);";
if (! $nav_active_icon_colour)
- $nav_active_icon_colour = "#555";
+ $nav_active_icon_colour = "rgba(0, 0, 0, 0.7)";
if (! $radius)
- $radius = "4";
+ $radius = "4px";
if (! $banner_colour)
- $banner_colour = "#777";
+ $banner_colour = "rgba(0, 0, 0, 0.7)";
diff --git a/view/theme/redbasic/schema/bluegrid.css b/view/theme/redbasic/schema/bluegrid.css
deleted file mode 100644
index 64e5a2c95..000000000
--- a/view/theme/redbasic/schema/bluegrid.css
+++ /dev/null
@@ -1,491 +0,0 @@
-body {
- background-size: auto;
-}
-
-.generic-content-wrapper-styled {
- background-color: rgba(67,72,138,.8);
- color: #FFF;
-}
-
-.generic-content-wrapper-styled .btn-default:hover, #profile-jot-wrapper .btn-default:hover {
- border: 1px solid #FFF;
-}
-
-#profile-jot-wrapper {
- background-color: inherit;
- border: none;
-}
-
-.generic-content-wrapper-styled a:hover, .generic-content-wrapper-styled a:focus, .generic-content-wrapper-styled .field.checkbox:hover label, .generic-content-wrapper-styled .field.checkbox:focus label, .allcontact-link:hover, .allcontact-link:focus {
- color: rgba(255,255,255,.8);
-}
-
-.generic-content-wrapper, .profile-jot-text, .comment-edit-text-empty, .comment-edit-text-full, input.widget-input, .wall-item-content-wrapper, .section-title-wrapper, .section-content-wrapper {
- border-radius: 0px !important;
-}
-
-.generic-content-wrapper {
- background-color: rgba(255,255,255,.8);
- color: #4d4d4d;
-}
-
-.wall-item-content-wrapper {
- background-color: #FFF;
-}
-
-.hide-comments-outer, .wall-item-content-wrapper.comment, .wall-item-comment-wrapper {
- background-color: transparent;
-}
-
-.generic-content-wrapper-styled .generic-content-wrapper {
- color: #4D4D4D;
-}
-
-.generic-content-wrapper-styled .generic-content-wrapper a {
- color: #43488A;
-}
-
-.generic-content-wrapper #profile-jot-wrapper {
- background-color: transparent;
- color: #4D4D4D;
-}
-
-.generic-content-wrapper input#jot-title, .generic-content-wrapper input#jot-pagetitle {
- color: #4D4D4D;
-}
-
-.generic-content-wrapper input#jot-title:hover, .generic-content-wrapper input#jot-title:focus {
- color: #4D4D4D;
- border-radius: 0px;
-}
-
-
-.fn, .widget h3, .nav-tabs a, .generic-content-wrapper-styled a, .dropdown-menu > li > a, #channels-desc, input#jot-title {
- color: #fff;
- border-radius: 0px
-}
-
-ul.dropdown-menu.acpopup > li.textcomplete-item > a {
- color: #43488A;
-}
-
-ul.dropdown-menu.acpopup > li.textcomplete-item > a:hover, ul.dropdown-menu.acpopup > li.textcomplete-item > a:focus {
- background-color: #43488A;
- color: #FFF;
- cursor: pointer;
-}
-
-input#jot-title:hover, input#jot-title:focus {
- color: #43488A;
- border-radius: 0px;
-}
-
-.navbar-inverse {
- background-color: transparent;
- border-color: transparent;
- background-image: none;
-}
-
-.navbar-inverse .navbar-nav > .active > a {
- background-image: none;
- background: rgba(255,255,255,.5);
-}
-
-.navbar-inverse .navbar-nav > .active > a:hover, .navbar-inverse .navbar-nav > .active > a:focus {
- background: rgba(255,255,255,.5);
-}
-
-.navbar-inverse .navbar-nav > li > a:hover,
-.navbar-inverse .navbar-nav > li > a:focus {
- color: #43488A;
- background: rgba(255,255,255,.5);
-}
-
-.navbar-inverse .navbar-nav > .open > a,
-.navbar-inverse .navbar-nav > .open > a:hover,
-.navbar-inverse .navbar-nav > .open > a:focus {
- background-color: #43488A;
- color: #fff;
-}
-
-#nav-search-text {
- color: #fff;
- background-color: #43488A;
- border-radius: 0px;
- border-color: transparent;
-}
-
-nav .dropdown-menu, .wall-item-tools .dropdown-menu, .section-title-wrapper .dropdown-menu, .section-content-wrapper .dropdown-menu {
- background-color: rgba(67,72,138,.97);
- color: #fff;
- border-radius: 0;
- border: none;
- box-shadow: 0px 6px 12px rgba(45,48,92,.176);
-}
-
-.dropdown-menu > li > a:focus, .dropdown-menu > li > a:hover {
- color: #43488A;
- background-color: rgba(255,255,255,.7);
- text-decoration: underline;
-}
-
-.vcard .dropdown-menu {
- background-color: rgba(255,255,255,.97);
- border-radius: 0;
- border: none;
- box-shadow: 0px 6px 12px rgba(169,169,169,.176);
-}
-
-.vcard .dropdown-menu a, .fc-today {
- color: #43488A;
-}
-
-.vcard .dropdown-menu > li > a:focus, .vcard .dropdown-menu > li > a:hover {
- color: #43488A;
- background-color: rgba( 255,255,255,.7);
- text-decoration: underline;
-}
-
-nav .badge {
- background-color: rgba(255,255,255,.8);
- color: #43488A;
- border-radius: 0px !important;
-}
-
-nav .badge:hover, nav .badge:focus {
- background-color: rgba(67,72,138,.8);
- color: #FFF;
-}
-
-.field.checkbox > div > input:checked + label .onoffswitch-switch {
- background-color: #43488A;
-}
-
-.widget .field.checkbox:hover label {
- color: rgba(255,255,255,.8);
-}
-
-.widget .conv-participants {
- color: #BBB;
-}
-
-.widget .active:hover .conv-participants, .widget .active:focus .conv-participants {
- color: inherit;
-}
-
-.help-block, .comment-icon, .jot-icons, .admin-icons {
- color: inherit;
-}
-
-#adminpage table tr:hover, #adminpage table tr:hover a, #adminpage table tr td.tools a:hover, #adminpage table tr:focus, #adminpage table tr:focus a, #adminpage table tr td.tools a:focus {
- color: #43488A;
-}
-
-#adminpage table tr:hover .tools a, #adminpage table tr:focus .tools a, .generic-content-wrapper-styled > .descriptive-text {
- color: #FFF;
-}
-
-.generic-content-wrapper-styled > .sources-links {
- font-weight: bold;
-}
-
-.wall-item-tools .btn {
- border-color: #43488A;
-}
-
-.vcard, #contact-block, .widget {
- background-color: rgba(67,72,138,.8);
- color: #fff;
- border-radius: 0;
- border: none;
- box-shadow: 0px 6px 12px rgba(45,48,92,.176);
-}
-
-.tags a {
- color: inherit;
-}
-
-#profile-photo-wrapper {
- border: none;
-}
-
-.nav-tabs > li.active > a, .nav-tabs > li.active > a:hover, .nav-tabs > li.active > a:focus {
- color: #43488A;
- text-decoration: none;
- border: none;
-}
-
-.nav-tabs > li.active {
- background-color: rgba(255,255,255,.5);
-}
-
-.nav-tabs.nav-justified > .active > a, .nav-tabs.nav-justified > .active > a:hover {
- border-color: transparent;
-}
-
-.nav-tabs.nav-justified {
- background-color: rgba(67,72,138,.8);
- border-bottom: 1px solid rgba(255,255,255,.5);
- border-radius: 0px;
-}
-
-.nav-tabs.nav-justified > li > a {
- border-bottom: 1px solid transparent;
- border-radius: 0px;
-}
-
-.nav > li > a:focus, .nav > li > a:hover {
- text-decoration: underline;
- background-color: rgba(255,255,255,.5);
- color: #43488A;
- border-radius: 0;
- border-color: transparent;
-}
-
-.nav > li > a {
- color: #FFF;
- border-radius: 0px;
-}
-
-.fc-event {
- border: none !important;
- background-color: rgba(255,255,255,.7) !important;
- color: #43488A !important;
- text-shadow: none !important;
-}
-
-div.rateme {
- border-radius: 0px;
- font-weight: 400;
-}
-
-div.rateme:hover, div.rateme:focus, a.rateme:hover, a.rateme:focus {
- background-color: #43488A;
- border-radius: 0px;
- color: #FFF;
- font-weight: 400;
- -webkit-transition: all .3s ease-in-out;
- -moz-transition: all .3s ease-in-out;
- transition: all .3s ease-in-out;
-}
-
-.info {
- background: rgba(255,255,255,.7) url("/images/hz-32.png") no-repeat scroll 15px center !important;
- color: #43488A !important;
-}
-
-.notice {
- background: rgba(215,43,52,.7) url("/images/hz-white-32.png") no-repeat scroll 15px center !important;
- color: #FFF !important;
-}
-
-#chatTopBar {
- background-color: rgba(255,255,255,.8);
- color: #4d4d4d;
- height: 500px;
- width: 596px;
- overflow-y: auto;
-}
-
-.chat-item-text {
- border-radius: 0px;
- padding: 5px;
- background-color: #FFF;
-}
-
-input {
- border-radius: 0px;
-}
-
-.home-welcome {
- color: #FFF;
- margin-bottom: 30px;
-}
-
-#login-main {
- margin-top: 0;
-}
-
-.directory-item {
- margin-bottom: 0px;
- padding-bottom: 20px;
- background-color: #FFF;
-}
-
-.directory-item.lframe {
- background-color: transparent !important;
-}
-
-.contact-entry-wrapper {
- border: 1px solid rgba(255,255,255,.5);
-}
-
-.contact-entry-edit:hover a, .contact-entry-edit:focus a, .generic-content-wrapper-styled > p > span.btn.btn-default > a:hover,.generic-content-wrapper-styled > p > span.btn.btn-default > a:focus, div#profile-edit-links a:hover, div#profile-edit-links a:focus {
- color: #43488A;
-}
-
-.profile-edit-side-link, input#profile-photo-upload, .allcontact-link, #newchannel-form .descriptive-paragraph {
- color: #FFF;
-}
-
-.profile-edit-side-link:hover, .profile-edit-side-link:focus {
- color: #FFF;
- text-decoration: none;
-}
-
-.section-content-info-wrapper {
- color: #fff;
- background-color: #43488A;
-}
-
-.section-content-info-wrapper a {
- color: #fff;
-}
-
-.btn, #event-edit-form .btn, input.directory-rating-submit {
- border: 1px solid #FFF;
- color: #FFF;
- background-color: #43488A;
- border-radius: 0;
- font-weight: 400;
- -webkit-transition: all .3s ease-in-out;
- -moz-transition: all .3s ease-in-out;
- transition: all .3s ease-in-out;
-}
-
-.btn:hover, .btn:focus, #event-edit-form .btn:hover, #event-edit-form .btn:focus {
- border: 1px solid #FFF;
- outline: 0;
- color: #43488A;
- background-color: #FFF;
-}
-
-.btn-default:hover, .btn-default:focus, .open > .dropdown-toggle.btn-default, input.directory-rating-submit:hover, input.directory-rating-submit:focus {
- border: 1px solid #43488A;
- outline: 0;
- color: #43488A;
- background-color: #FFF;
-}
-
-.btn-primary, input#event-submit, input#rmagic-submit-button, input#lostpass-submit-button, input#side-follow-submit, .profile-edit-submit-wrapper > input.profile-edit-submit-button, input#profile-photo-submit, form#chat-form > input, div#adminpage > form > div.submit > input, input.sources-submit, input.contact-edit-submit, input#dbtn-submit, input#newchannel-submit-button, input#contacts-search-submit, input#register-submit-button {
- background-color: #FFF;
- color: #43488A;
- border-radius: 0px;
- -webkit-transition: all .3s ease-in-out;
- -moz-transition: all .3s ease-in-out;
- transition: all .3s ease-in-out;
-}
-
-.btn-primary:hover, .btn-primary:focus, input#event-submit:hover, input#event-submit:focus, input#rmagic-submit-button:hover, input#rmagic-submit-button:focus, input#lostpass-submit-button:hover, input#lostpass-submit-button:focus, input#side-follow-submit:hover, input#side-follow-submit:focus, .profile-edit-submit-wrapper > input.profile-edit-submit-button:hover, .profile-edit-submit-wrapper > input.profile-edit-submit-button:focus, input#profile-photo-submit:hover, input#profile-photo-submit:focus, form#chat-form > input:hover, form#chat-form > input:focus, div#adminpage > form > div.submit > input:hover, div#adminpage > form > div.submit > input:focus, input.sources-submit:hover, input.sources-submit:focus, input.contact-edit-submit:focus, input.contact-edit-submit:hover, input#dbtn-submit:hover, input#dbtn-submit:focus, input#newchannel-submit-button:hover, input#newchannel-submit-button:focus, input#contacts-search-submit:hover, input#contacts-search-submit:focus, input#register-submit-button:hover, input#register-submit-button:focus {
- border-color: #FFF;
- background-color: #43488A;
- color: #FFF;
- border-radius: 0px;
-}
-
-.comment-tools .btn, #prvmail-tools .btn, .generic-content-wrapper .btn {
- border: 1px solid #43488A;
- color: #43488A;
- background-color: #FFF;
-}
-
-.comment-tools .btn:hover, .comment-tools .btn:focus, #prvmail-tools .btn:hover, #prvmail-tools .btn:focus, .generic-content-wrapper .btn:hover, .generic-content-wrapper .btn:focus {
- border: 1px solid #43488A !important;
- color: #FFF;
- background-color: #43488A;
-}
-
-.comment-tools .btn-primary, #prvmail-submit .btn-primary, .settings-submit-wrapper .btn-primary, .generic-content-wrapper .btn-primary {
- background-color: #43488A;
- color: #FFF;
- border: 1px solid #43488A;
-}
-
-.comment-tools .btn-primary:hover, .comment-tools .btn-primary:focus, #prvmail-submit .btn-primary:hover, #prvmail-submit .btn-primary:focus, .settings-submit-wrapper .btn-primary:hover, .settings-submit-wrapper .btn-primary:focus, .generic-content-wrapper .btn-primary:hover, .generic-content-wrapper .btn-primary:focus {
- border-color: #43488A;
- background-color: #FFF;
- color: #43488A;
-}
-
-.btn-success {
- color: #FFF !important;
- background-color: #5CB85C !important;
- border-color: #4CAE4C !important;
-}
-
-.btn-success:hover, .btn-success:focus {
- color: #FFF !important;
- background-color: #449D44 !important;
- border-color: #398439 !important;
-}
-
-.btn-warning {
- color: #FFF !important;
- background-color: #F0AD4E !important;
- border-color: #EEA236 !important;
-}
-
-.btn-warning:hover, .btn-warning:focus {
- color: #FFF !important;
- background-color: #EC971F !important;
- border-color: #D58512 !important;
-}
-
-.btn-danger, form#chat-destroy > input {
- background-color: #D9534F !important;
- border-color: #D43F3A !important;
- color: #FFF !important;
-}
-.btn-danger:hover, .btn-danger:focus, form#chat-destroy > input:hover, form#chat-destroy > input:focus {
- color: #FFF !important;
- background-color: #C9302C !important;
- border-color: #AC2925 !important;
-}
-
-a:hover > .fa-trash-o {
- color: #C9302C !important;
-}
-
-@media screen and (max-width: 767px) {
- .navbar-inverse .navbar-collapse {
- background-color: #43488A;
- border: none;
- }
- .navbar-inverse .navbar-toggle {
- border-color: #576295;
- background-color: #43488A;
- border-radius: 0px;
- }
- .navbar-inverse .navbar-toggle .icon-bar {
- background-color: #FFF;
- }
- .navbar-inverse .navbar-toggle .fa-arrow-circle-down, .navbar-inverse .navbar-toggle .fa-arrow-circle-right, .navbar-inverse .navbar-toggle .fa-arrow-circle-up, .navbar-inverse .navbar-toggle .fa-arrow-circle-left, .navbar-inverse .navbar-toggle .fa-question-circle {
- color: #FFF;
- }
- .navbar-inverse .navbar-toggle:hover .fa-arrow-circle-down, .navbar-inverse .navbar-toggle:focus .fa-arrow-circle-down, .navbar-inverse .navbar-toggle:hover .fa-arrow-circle-right, .navbar-inverse .navbar-toggle:focus .fa-arrow-circle-right, .navbar-inverse .navbar-toggle:hover .fa-arrow-circle-up, .navbar-inverse .navbar-toggle:focus .fa-arrow-circle-up, .navbar-inverse .navbar-toggle:hover .fa-arrow-circle-left, .navbar-inverse .navbar-toggle:focus .fa-arrow-circle-left {
- color: #43488A;
- }
- .navbar-inverse .navbar-toggle:hover, .navbar-inverse .navbar-toggle:focus {
- background-color: #FFF !important;
- }
- .navbar-toggle:hover .icon-bar , .navbar-toggle:focus .icon-bar {
- background-color: #43488A !important;
- }
-}
-
-.help-content {
- color: #FFF;
- border: none;
-}
-
-.help-content a {
- color: #FFF;
- font-weight: 600;
-}
-
-.help-content-open {
- -moz-box-shadow: none;
- -webkit-box-shadow: none;
- box-shadow: none;
-}
-
diff --git a/view/theme/redbasic/schema/bluegrid.php b/view/theme/redbasic/schema/bluegrid.php
deleted file mode 100644
index fdb552611..000000000
--- a/view/theme/redbasic/schema/bluegrid.php
+++ /dev/null
@@ -1,28 +0,0 @@
-<?php
-
- if (! $nav_bg)
- $nav_bg = "#FFF";
- if (! $nav_active_gradient_top)
- $nav_active_gradient_top = "#FFF";
- if (! $nav_active_gradient_bottom)
- $nav_active_gradient_bottom = "#43488A";
- if (! $nav_bd)
- $nav_bd = "#fff";
- if (! $nav_icon_colour)
- $nav_icon_colour = "#FFF";
- if (! $nav_active_icon_colour)
- $nav_active_icon_colour = "#43488A";
- if (! $banner_colour)
- $banner_colour = "#fff";
- if (! $bgcolour)
- $bgcolour = "#43488A";
- if (! $background_image)
- $background_image = "/images/bggrid.png";
- if (! $link_colour)
- $link_colour = "#43488A";
-
-
-
-
-
-
diff --git a/view/theme/redbasic/schema/dark.css b/view/theme/redbasic/schema/dark.css
index f9114141d..b1aa5e07a 100644
--- a/view/theme/redbasic/schema/dark.css
+++ b/view/theme/redbasic/schema/dark.css
@@ -139,6 +139,10 @@ option {
background-color: #111;
}
+.nav-link.active {
+ color:#000 !important;
+}
+
a.btn, aside a {
font-weight: 400 !important;
}
@@ -270,26 +274,20 @@ nav .dropdown-menu {
background: #999;
}
-.nav-tabs{
+.nav-tabs {
border-bottom:1px solid #333;
}
-.nav-tabs.nav-justified>.active>a,.nav-tabs.nav-justified>.active>a:hover,.nav-tabs.nav-justified>.active>a:focus{
- border:1px solid #333;
-}
-
-.nav-tabs>li.active>a,.nav-tabs>li.active>a:hover,.nav-tabs>li.active>a:focus {
+.nav-tabs .nav-link.active {
color: #fff;
- background-color: #111;
-}
-
-.nav-tabs.nav-justified > li > a {
- color: #ccc;
+ background-color: #111;
+ border-color: #333;
}
-.nav-tabs > li > a:hover, .nav-tabs > li > a:focus {
- text-decoration: underline;
- background-color: #222;
+.nav-tabs .nav-link:hover,
+.nav-tabs .nav-link:focus {
+ text-decoration: underline;
+ background-color: #222;
color: #ccc;
border-color: #333;
}
@@ -417,7 +415,6 @@ pre {
.contextual-help-content-open {
background: $nav_bg;
- top: 50px;
border-bottom: #555 1px solid;
box-shadow: 0px 3px 3px rgba(85,85,85,0.2);
}
diff --git a/view/theme/redbasic/schema/simple_black_on_white.css b/view/theme/redbasic/schema/simple_black_on_white.css
index f06fd3667..915cc4e18 100644
--- a/view/theme/redbasic/schema/simple_black_on_white.css
+++ b/view/theme/redbasic/schema/simple_black_on_white.css
@@ -294,8 +294,6 @@ pre {
.contextual-help-content-open {
background: #FFF;
- top: 50px;
-
}
.profile-match-wrapper {
diff --git a/view/theme/redbasic/schema/simple_green_on_black.css b/view/theme/redbasic/schema/simple_green_on_black.css
index c7bb99334..7f3f99fce 100644
--- a/view/theme/redbasic/schema/simple_green_on_black.css
+++ b/view/theme/redbasic/schema/simple_green_on_black.css
@@ -367,7 +367,6 @@ pre {
.contextual-help-content-open {
background: $nav_bg;
- top: 50px;
border-bottom: #1C5419 1px solid;
box-shadow: 0px 3px 3px rgba(28,84,25,0.2);
}
diff --git a/view/theme/redbasic/schema/simple_white_on_black.css b/view/theme/redbasic/schema/simple_white_on_black.css
index dabc26743..7e7f80f2f 100644
--- a/view/theme/redbasic/schema/simple_white_on_black.css
+++ b/view/theme/redbasic/schema/simple_white_on_black.css
@@ -340,7 +340,6 @@ pre {
.contextual-help-content-open {
background: $nav_bg;
- top: 50px;
border-bottom: #FFF 1px solid;
box-shadow: 0px 3px 3px rgba(255,255,255,0.2);
}
diff --git a/view/theme/redbasic/tpl/theme_settings.tpl b/view/theme/redbasic/tpl/theme_settings.tpl
index 9672d3d05..7c552b49e 100644
--- a/view/theme/redbasic/tpl/theme_settings.tpl
+++ b/view/theme/redbasic/tpl/theme_settings.tpl
@@ -1,29 +1,19 @@
-{{include file="field_checkbox.tpl" field=$align_left}}
{{include file="field_checkbox.tpl" field=$narrow_navbar}}
{{include file="field_input.tpl" field=$converse_width}}
+{{include file="field_input.tpl" field=$font_size}}
{{if $expert}}
{{include file="field_colorinput.tpl" field=$nav_bg}}
- {{include file="field_colorinput.tpl" field=$nav_gradient_top}}
- {{include file="field_colorinput.tpl" field=$nav_gradient_bottom}}
- {{include file="field_colorinput.tpl" field=$nav_active_gradient_top}}
- {{include file="field_colorinput.tpl" field=$nav_active_gradient_bottom}}
- {{include file="field_colorinput.tpl" field=$nav_bd}}
{{include file="field_colorinput.tpl" field=$nav_icon_colour}}
{{include file="field_colorinput.tpl" field=$nav_active_icon_colour}}
- {{include file="field_input.tpl" field=$nav_min_opacity}}
+ {{include file="field_colorinput.tpl" field=$banner_colour}}
{{include file="field_colorinput.tpl" field=$bgcolour}}
{{include file="field_colorinput.tpl" field=$background_image}}
{{include file="field_colorinput.tpl" field=$item_colour}}
{{include file="field_colorinput.tpl" field=$comment_item_colour}}
{{*include file="field_colorinput.tpl" field=$comment_border_colour*}}
{{*include file="field_input.tpl" field=$comment_indent*}}
- {{include file="field_input.tpl" field=$body_font_size}}
- {{include file="field_input.tpl" field=$font_size}}
{{include file="field_colorinput.tpl" field=$font_colour}}
{{include file="field_colorinput.tpl" field=$link_colour}}
- {{include file="field_colorinput.tpl" field=$banner_colour}}
- {{include file="field_colorinput.tpl" field=$toolicon_colour}}
- {{include file="field_colorinput.tpl" field=$toolicon_activecolour}}
{{include file="field_input.tpl" field=$radius}}
{{include file="field_input.tpl" field=$shadow}}
{{include file="field_input.tpl" field=$top_photo}}
@@ -31,8 +21,8 @@
<script>
$(function(){
- $('#id_redbasic_nav_bg,#id_redbasic_nav_gradient_top,#id_redbasic_nav_gradient_bottom,#id_redbasic_nav_active_gradient_top,#id_redbasic_nav_active_gradient_bottom').colorpicker({format: 'rgba'});
- $('#id_redbasic_nav_bd,#id_redbasic_nav_icon_colour ,#id_redbasic_nav_active_icon_colour,#id_redbasic_banner_colour,#id_redbasic_link_colour,#id_redbasic_background_colour').colorpicker();
+ $('#id_redbasic_nav_bg, #id_redbasic_nav_icon_colour, #id_redbasic_nav_active_icon_colour, #id_redbasic_banner_colour').colorpicker({format: 'rgba'});
+ $('#id_redbasic_link_colour,#id_redbasic_background_colour').colorpicker();
$('#id_redbasic_toolicon_colour,#id_redbasic_toolicon_activecolour,#id_redbasic_font_colour').colorpicker();
$('#id_redbasic_item_colour,#id_redbasic_comment_item_colour,#id_redbasic_comment_border_colour').colorpicker({format: 'rgba'});
});
diff --git a/view/tpl/abook_edit.tpl b/view/tpl/abook_edit.tpl
index ebc69c5f8..13b94a560 100755
--- a/view/tpl/abook_edit.tpl
+++ b/view/tpl/abook_edit.tpl
@@ -3,31 +3,36 @@
{{if $notself}}
<div class="pull-right">
<div class="btn-group">
- <button id="connection-dropdown" class="btn btn-default btn-xs dropdown-toggle" type="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
- <i class="fa fa-caret-down"></i>&nbsp;{{$tools_label}}
+ <button id="connection-dropdown" class="btn btn-outline-secondary btn-sm dropdown-toggle" type="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
+ <i class="fa fa-cog"></i>&nbsp;{{$tools_label}}
</button>
- <ul class="dropdown-menu dropdown-menu-right" aria-labelledby="dLabel">
- <li><a href="{{$tools.view.url}}" title="{{$tools.view.title}}">{{$tools.view.label}}</a></li>
- <li><a href="{{$tools.recent.url}}" title="{{$tools.recent.title}}">{{$tools.recent.label}}</a></li>
- <li class="divider"></li>
- <li><a href="#" title="{{$tools.refresh.title}}" onclick="window.location.href='{{$tools.refresh.url}}'; return false;">{{$tools.refresh.label}}</a></li>
- <li><a href="#" title="{{$tools.block.title}}" onclick="window.location.href='{{$tools.block.url}}'; return false;">{{$tools.block.label}}</a></li>
- <li><a href="#" title="{{$tools.ignore.title}}" onclick="window.location.href='{{$tools.ignore.url}}'; return false;">{{$tools.ignore.label}}</a></li>
- <li><a href="#" title="{{$tools.archive.title}}" onclick="window.location.href='{{$tools.archive.url}}'; return false;">{{$tools.archive.label}}</a></li>
- <li><a href="#" title="{{$tools.hide.title}}" onclick="window.location.href='{{$tools.hide.url}}'; return false;">{{$tools.hide.label}}</a></li>
- <li><a href="#" title="{{$tools.delete.title}}" onclick="window.location.href='{{$tools.delete.url}}'; return false;">{{$tools.delete.label}}</a></li>
- </ul>
+ <div class="dropdown-menu dropdown-menu-right" aria-labelledby="dLabel">
+ <a class="dropdown-item" href="{{$tools.view.url}}" title="{{$tools.view.title}}">{{$tools.view.label}}</a>
+ <a class="dropdown-item" href="{{$tools.recent.url}}" title="{{$tools.recent.title}}">{{$tools.recent.label}}</a>
+ {{if $tools.fetchvc}}
+ <a class="dropdown-item" href="{{$tools.fetchvc.url}}" title="{{$tools.fetchvc.title}}">{{$tools.fetchvc.label}}</a>
+ {{/if}}
+ <a class="dropdown-item" href="#" title="{{$tools.refresh.title}}" onclick="window.location.href='{{$tools.refresh.url}}'; return false;">{{$tools.refresh.label}}</a>
+ <a class="dropdown-item" href="#" title="{{$tools.rephoto.title}}" onclick="window.location.href='{{$tools.rephoto.url}}'; return false;">{{$tools.rephoto.label}}</a>
+ <div class="dropdown-divider"></div>
+ <a class="dropdown-item" href="#" title="{{$tools.block.title}}" onclick="window.location.href='{{$tools.block.url}}'; return false;">{{$tools.block.label}}</a>
+ <a class="dropdown-item" href="#" title="{{$tools.ignore.title}}" onclick="window.location.href='{{$tools.ignore.url}}'; return false;">{{$tools.ignore.label}}</a>
+ <a class="dropdown-item" href="#" title="{{$tools.archive.title}}" onclick="window.location.href='{{$tools.archive.url}}'; return false;">{{$tools.archive.label}}</a> <a class="dropdown-item" href="#" title="{{$tools.hide.title}}" onclick="window.location.href='{{$tools.hide.url}}'; return false;">{{$tools.hide.label}}</a>
+ <a class="dropdown-item" href="#" title="{{$tools.delete.title}}" onclick="window.location.href='{{$tools.delete.url}}'; return false;">{{$tools.delete.label}}</a>
+ </div>
</div>
{{if $abook_prev || $abook_next}}
<div class="btn-group">
- <a href="connedit/{{$abook_prev}}{{if $section}}?f=&section={{$section}}{{/if}}" class="btn btn-default btn-xs{{if ! $abook_prev}} disabled{{/if}}" ><i class="fa fa-backward"></i></a>
- <button class="btn btn-default btn-xs{{if $is_pending}} disabled{{/if}}" type="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false"><i class="fa fa-bars"></i></button>
- <a href="connedit/{{$abook_next}}{{if $section}}?f=&section={{$section}}{{/if}}" class="btn btn-default btn-xs{{if ! $abook_next}} disabled{{/if}}" ><i class="fa fa-forward"></i></a>
- <ul class="dropdown-menu dropdown-menu-right" aria-labelledby="dLabel">
- {{foreach $sections as $s}}
- <li><a href="{{$s.url}}" title="{{$s.title}}">{{$s.label}}</a></li>
- {{/foreach}}
- </ul>
+ <a href="connedit/{{$abook_prev}}{{if $section}}?f=&section={{$section}}{{/if}}" class="btn btn-outline-secondary btn-sm{{if ! $abook_prev}} disabled{{/if}}" ><i class="fa fa-backward"></i></a>
+ <div class="btn-group" >
+ <button class="btn btn-outline-secondary btn-sm{{if $is_pending}} disabled{{/if}}" type="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false"><i class="fa fa-bars"></i></button>
+ <div class="dropdown-menu dropdown-menu-right" aria-labelledby="dLabel">
+ {{foreach $sections as $s}}
+ <a class="dropdown-item" href="{{$s.url}}" title="{{$s.title}}">{{$s.label}}</a>
+ {{/foreach}}
+ </div>
+ </div>
+ <a href="connedit/{{$abook_next}}{{if $section}}?f=&section={{$section}}{{/if}}" class="btn btn-outline-secondary btn-sm{{if ! $abook_next}} disabled{{/if}}" ><i class="fa fa-forward"></i></a>
</div>
{{/if}}
</div>
@@ -47,13 +52,19 @@
{{/foreach}}
<div class="section-content-info-wrapper">
<div>
- {{$addr_text}} <strong>'{{$addr}}'</strong>
+ {{$addr_text}} <strong>'{{if $addr}}{{$addr}}{{else}}{{$primeurl}}{{/if}}'</strong>
</div>
{{if $locstr}}
<div>
{{$loc_text}} {{$locstr}}
</div>
{{/if}}
+ {{if $unclonable}}
+ <div>
+ <br>{{$unclonable}}
+ </div>
+ <br>
+ {{/if}}
{{if $last_update}}
<div>
{{$lastupdtext}} {{$last_update}}
@@ -79,7 +90,7 @@
</a>
</h3>
</div>
- <div id="pending-tool-collapse" class="panel-collapse collapse in" role="tabpanel" aria-labelledby="pending-tool">
+ <div id="pending-tool-collapse" class="panel-collapse collapse show" role="tabpanel" aria-labelledby="pending-tool">
<div class="section-content-tools-wrapper">
{{include file="field_checkbox.tpl" field=$unapproved}}
<div class="settings-submit-wrapper" >
@@ -187,7 +198,7 @@
<div class="section-content-wrapper-np">
<div id="vcard-cancel-{{$vcard.id}}" class="vcard-cancel vcard-cancel-btn" data-id="{{$vcard.id}}" data-action="cancel"><i class="fa fa-close"></i></div>
<div id="vcard-add-field-{{$vcard.id}}" class="dropdown pull-right vcard-add-field">
- <button data-toggle="dropdown" type="button" class="btn btn-default btn-sm dropdown-toggle"><i class="fa fa-plus"></i> {{$add_field}}</button>
+ <button data-toggle="dropdown" type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle"><i class="fa fa-plus"></i> {{$add_field}}</button>
<ul class="dropdown-menu">
<li class="add-vcard-org"{{if $vcard.org}} style="display: none"{{/if}}><a href="#" data-add="vcard-org" data-id="{{$vcard.id}}" class="add-field" onclick="return false;">{{$org_label}}</a></li>
<li class="add-vcard-title"{{if $vcard.title}} style="display: none"{{/if}}><a href="#" data-add="vcard-title" data-id="{{$vcard.id}}" class="add-field" onclick="return false;">{{$title_label}}</a></li>
@@ -203,8 +214,8 @@
<i class="vcard-fn-preview fa fa-address-card-o"></i>
<span id="vcard-preview-{{$vcard.id}}" class="vcard-preview">
{{if $vcard.fn}}<span class="vcard-fn-preview">{{$vcard.fn}}</span>{{/if}}
- {{if $vcard.emails.0.address}}<span class="vcard-email-preview hidden-xs"><a href="mailto:{{$vcard.emails.0.address}}">{{$vcard.emails.0.address}}</a></span>{{/if}}
- {{if $vcard.tels.0}}<span class="vcard-tel-preview hidden-xs">{{$vcard.tels.0.nr}}{{if $is_mobile}} <a class="btn btn-default btn-xs" href="tel:{{$vcard.tels.0.nr}}"><i class="fa fa-phone connphone"></i></a>{{/if}}</span>{{/if}}
+ {{if $vcard.emails.0.address}}<span class="vcard-email-preview d-none d-md-table-cell"><a href="mailto:{{$vcard.emails.0.address}}">{{$vcard.emails.0.address}}</a></span>{{/if}}
+ {{if $vcard.tels.0}}<span class="vcard-tel-preview d-none d-md-table-cell">{{$vcard.tels.0.nr}}{{if $is_mobile}} <a class="btn btn-outline-secondary btn-sm" href="tel:{{$vcard.tels.0.nr}}"><i class="fa fa-phone connphone"></i></a>{{/if}}</span>{{/if}}
</span>
<input id="vcard-fn-{{$vcard.id}}" class="vcard-fn" type="text" name="fn" value="{{$vcard.fn}}" size="{{$vcard.fn|count_characters:true}}" placeholder="{{$name_label}}">
</div>
@@ -381,7 +392,7 @@
</a>
</h3>
</div>
- <div id="affinity-tool-collapse" class="panel-collapse collapse{{if $section == 'affinity'}} in{{/if}}" role="tabpanel" aria-labelledby="affinity-tool">
+ <div id="affinity-tool-collapse" class="panel-collapse collapse{{if $section == 'affinity'}} show{{/if}}" role="tabpanel" aria-labelledby="affinity-tool">
<div class="section-content-tools-wrapper">
{{if $slide}}
<div class="form-group"><strong>{{$lbl_slider}}</strong></div>
@@ -412,7 +423,7 @@
</a>
</h3>
</div>
- <div id="fitert-tool-collapse" class="panel-collapse collapse{{if $section == 'filter' }} in{{/if}}" role="tabpanel" aria-labelledby="fitert-tool">
+ <div id="fitert-tool-collapse" class="panel-collapse collapse{{if $section == 'filter' }} show{{/if}}" role="tabpanel" aria-labelledby="fitert-tool">
<div class="section-content-tools-wrapper">
{{include file="field_textarea.tpl" field=$incl}}
{{include file="field_textarea.tpl" field=$excl}}
@@ -466,7 +477,7 @@
</h3>
</div>
{{/if}}
- <div id="perms-tool-collapse" class="panel-collapse collapse{{if $self || $section === 'perms'}} in{{/if}}" role="tabpanel" aria-labelledby="perms-tool">
+ <div id="perms-tool-collapse" class="panel-collapse collapse{{if $self || $section === 'perms'}} show{{/if}}" role="tabpanel" aria-labelledby="perms-tool">
<div class="section-content-tools-wrapper">
<div class="section-content-warning-wrapper">
{{if $notself}}{{$permnote}}{{/if}}
diff --git a/view/tpl/acl_selector.tpl b/view/tpl/acl_selector.tpl
index c23840c16..f4f851c8a 100755
--- a/view/tpl/acl_selector.tpl
+++ b/view/tpl/acl_selector.tpl
@@ -3,11 +3,13 @@
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
+ <h4 class="modal-title">
+ <i id="dialog-perms-icon" class="fa fa-fw"></i> {{$aclModalTitle}}
+ {{if $helpUrl}}
+ <a target="hubzilla-help" href="{{$helpUrl}}" class="contextual-help-tool" title="Help and documentation"><i class="fa fa-fw fa-question"></i></a>
+ {{/if}}
+ </h4>
<button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button>
- {{if $helpUrl}}
- <a type="button" target="hubzilla-help" href="{{$helpUrl}}" class="contextual-help-tool" title="Help and documentation"><i class="fa fa-question"></i></a>
- {{/if}}
- <h4 class="modal-title"><i id="dialog-perms-icon" class="fa fa-fw"></i> {{$aclModalTitle}}</h4>
</div>
<div class="section-content-wrapper">
{{if $aclModalDesc}}
@@ -29,32 +31,30 @@
<div id="acl-wrapper">
<div id="acl-list">
- <div id="acl-search-wrapper">
- <input type="text" id="acl-search" placeholder="&#xf002; {{$search}}">
- </div>
- <div id="acl-list-content-wrapper">
- <div id=acl-showlimited-description>{{$showlimitedDesc}}</div>
- <div id="acl-list-content"></div>
- </div>
+ <input class="form-control" type="text" id="acl-search" placeholder="&#xf002; {{$search}}">
+ <small class="text-muted">{{$showlimitedDesc}}</small>
+ <div id="acl-list-content"></div>
</div>
</div>
<div class="acl-list-item" rel="acl-template" style="display:none">
- <img data-src="{0}"><p>{1}</p>
- <button class="acl-button-hide btn btn-xs btn-default"><i class="fa fa-times"></i> {{$hide}}</button>
- <button class="acl-button-show btn btn-xs btn-default"><i class="fa fa-check"></i> {{$show}}</button>
+ <div class="acl-item-header">
+ <img class="menu-img-1" data-src="{0}"> {1}
+ </div>
+ <button class="acl-button-hide btn btn-sm btn-outline-danger"><i class="fa fa-times"></i> {{$hide}}</button>
+ <button class="acl-button-show btn btn-sm btn-outline-success"><i class="fa fa-check"></i> {{$show}}</button>
</div>
-
</div>
<div class="modal-footer clear">
- <button type="button" class="btn btn-default" data-dismiss="modal">{{$aclModalDismiss}}</button>
+ <button type="button" class="btn btn-outline-secondary" data-dismiss="modal">{{$aclModalDismiss}}</button>
</div>
</div><!-- /.modal-content -->
</div><!-- /.modal-dialog -->
</div><!-- /.modal -->
</form>
<script>
- $('[data-toggle="popover"]').popover(); // Init the popover, if present
+ // compatibility issue with bootstrap v4
+ //$('[data-toggle="popover"]').popover(); // Init the popover, if present
if(typeof acl=="undefined"){
acl = new ACL(
diff --git a/view/tpl/admin_account_edit.tpl b/view/tpl/admin_account_edit.tpl
index 82d137de4..239d9084a 100644
--- a/view/tpl/admin_account_edit.tpl
+++ b/view/tpl/admin_account_edit.tpl
@@ -8,12 +8,7 @@
{{include file="field_password.tpl" field=$pass1}}
{{include file="field_password.tpl" field=$pass2}}
-
-{{if $z_server_role == 'pro'}}
{{include file="field_select.tpl" field=$account_level}}
-{{else}}
-<input type="hidden" name="account_level" value="{{$account_level.2}}" />
-{{/if}}
{{include file="field_select.tpl" field=$account_language}}
{{include file="field_input.tpl" field=$service_class}}
diff --git a/view/tpl/admin_accounts.tpl b/view/tpl/admin_accounts.tpl
index c2a50e3ff..3535363a0 100755
--- a/view/tpl/admin_accounts.tpl
+++ b/view/tpl/admin_accounts.tpl
@@ -33,8 +33,8 @@
<td class="email">{{$u.account_email}}</td>
<td class="checkbox_bulkedit"><input type="checkbox" class="pending_ckbx" id="id_pending_{{$u.hash}}" name="pending[]" value="{{$u.hash}}"></td>
<td class="tools">
- <a href="{{$baseurl}}/regmod/allow/{{$u.hash}}" class="btn btn-default btn-xs" title="{{$approve}}"><i class="fa fa-thumbs-o-up admin-icons"></i></a>
- <a href="{{$baseurl}}/regmod/deny/{{$u.hash}}" class="btn btn-default btn-xs" title="{{$deny}}"><i class="fa fa-thumbs-o-down admin-icons"></i></a>
+ <a href="{{$baseurl}}/regmod/allow/{{$u.hash}}" class="btn btn-outline-secondary btn-sm" title="{{$approve}}"><i class="fa fa-thumbs-o-up admin-icons"></i></a>
+ <a href="{{$baseurl}}/regmod/deny/{{$u.hash}}" class="btn btn-outline-secondary btn-sm" title="{{$deny}}"><i class="fa fa-thumbs-o-down admin-icons"></i></a>
</td>
</tr>
{{/foreach}}
@@ -73,7 +73,7 @@
<td class="service_class">{{$u.account_service_class}}</td>
<td class="checkbox_bulkedit"><input type="checkbox" class="users_ckbx" id="id_user_{{$u.account_id}}" name="user[]" value="{{$u.account_id}}"><input type="hidden" name="blocked[]" value="{{$u.blocked}}"></td>
<td class="tools">
- <a href="{{$baseurl}}/admin/accounts/{{if ($u.blocked)}}un{{/if}}block/{{$u.account_id}}?t={{$form_security_token}}" class="btn btn-default btn-xs" title='{{if ($u.blocked)}}{{$unblock}}{{else}}{{$block}}{{/if}}'><i class="fa fa-ban admin-icons{{if ($u.blocked)}} dim{{/if}}"></i></a><a href="{{$baseurl}}/admin/accounts/delete/{{$u.account_id}}?t={{$form_security_token}}" class="btn btn-default btn-xs" title='{{$delete}}' onclick="return confirm_delete('{{$u.name}}')"><i class="fa fa-trash-o admin-icons"></i></a>
+ <a href="{{$baseurl}}/admin/accounts/{{if ($u.blocked)}}un{{/if}}block/{{$u.account_id}}?t={{$form_security_token}}" class="btn btn-outline-secondary btn-sm" title='{{if ($u.blocked)}}{{$unblock}}{{else}}{{$block}}{{/if}}'><i class="fa fa-ban admin-icons{{if ($u.blocked)}} dim{{/if}}"></i></a><a href="{{$baseurl}}/admin/accounts/delete/{{$u.account_id}}?t={{$form_security_token}}" class="btn btn-outline-secondary btn-sm" title='{{$delete}}' onclick="return confirm_delete('{{$u.name}}')"><i class="fa fa-trash-o admin-icons"></i></a>
</td>
</tr>
{{/foreach}}
diff --git a/view/tpl/admin_aside.tpl b/view/tpl/admin_aside.tpl
index 70e1677af..99f139e57 100755
--- a/view/tpl/admin_aside.tpl
+++ b/view/tpl/admin_aside.tpl
@@ -12,17 +12,17 @@
</script>
<div class="widget">
<h3>{{$admtxt}}</h3>
-<ul class="nav nav-pills nav-stacked">
+<ul class="nav nav-pills flex-column">
{{foreach $admin as $link}}
- <li><a href='{{$link.0}}'>{{$link.1}}{{if $link.3}}<span id='{{$link.3}}' title='{{$link.4}}'></span>{{/if}}</a></li>
+ <li class="nav-item"><a class="nav-link" href='{{$link.0}}'>{{$link.1}}{{if $link.3}}<span id='{{$link.3}}' title='{{$link.4}}'></span>{{/if}}</a></li>
{{/foreach}}
</ul>
</div>
{{if $admin.update}}
-<ul class="nav nav-pills nav-stacked">
- <li><a href='{{$admin.update.0}}'>{{$admin.update.1}}</a></li>
- <li><a href=''>Important Changes</a></li>
+<ul class="nav nav-pills flex-column">
+ <li class="nav-item"><a class="nav-link" href='{{$admin.update.0}}'>{{$admin.update.1}}</a></li>
+ <li class="nav-item"><a class="nav-link" href=''>Important Changes</a></li>
</ul>
{{/if}}
@@ -30,9 +30,9 @@
{{if $plugins}}
<div class="widget">
<h3>{{$plugadmtxt}}</h3>
-<ul class="nav nav-pills nav-stacked">
+<ul class="nav nav-pills flex-column">
{{foreach $plugins as $l}}
- <li><a href='{{$l.0}}'>{{$l.1}}</a></li>
+ <li class="nav-item"><a class="nav-link" href='{{$l.0}}'>{{$l.1}}</a></li>
{{/foreach}}
</ul>
</div>
@@ -40,7 +40,7 @@
<div class="widget">
<h3>{{$logtxt}}</h3>
-<ul class="nav nav-pills nav-stacked">
- <li><a href='{{$logs.0}}'>{{$logs.1}}</a></li>
+<ul class="nav nav-pills flex-column">
+ <li class="nav-item"><a class="nav-link" href='{{$logs.0}}'>{{$logs.1}}</a></li>
</ul>
</div>
diff --git a/view/tpl/admin_channels.tpl b/view/tpl/admin_channels.tpl
index f15742f78..452e0eeec 100755
--- a/view/tpl/admin_channels.tpl
+++ b/view/tpl/admin_channels.tpl
@@ -35,7 +35,7 @@
<td class="checkbox_bulkedit"><input type="checkbox" class="channels_ckbx" id="id_channel_{{$c.channel_id}}" name="channel[]" value="{{$c.channel_id}}"/></td>
<td class="tools">
<a href="{{$baseurl}}/admin/channels/block/{{$c.channel_id}}?t={{$form_security_token}}" class="btn btn-default btn-xs" title='{{if ($c.blocked)}}{{$unblock}}{{else}}{{$block}}{{/if}}'><i class='fa fa-ban admin-icons {{if ($c.blocked)}}dim{{/if}}'></i></a>
- <a href="{{$baseurl}}/admin/channels/code/{{$c.channel_id}}?t={{$form_security_token}}" class="btn btn-default btn-xs" title='{{if ($c.allowcode)}}{{$uncode}}{{else}}{{$code}}{{/if}}'><i class='fa fa-terminal admin-icons {{if ($c.allowcode)}}dim{{/if}}'></i></a>
+ <a href="{{$baseurl}}/admin/channels/code/{{$c.channel_id}}?t={{$form_security_token}}" class="btn btn-default btn-xs{{if ($c.allowcode)}} btn-danger{{/if}}" title='{{if ($c.allowcode)}}{{$uncode}}{{else}}{{$code}}{{/if}}'><i class='fa fa-terminal admin-icons {{if ($c.allowcode)}}dim{{/if}}'></i></a>
<a href="{{$baseurl}}/admin/channels/delete/{{$c.channel_id}}?t={{$form_security_token}}" class="btn btn-default btn-xs" title='{{$delete}}' onclick="return confirm_delete('{{$c.channel_name}}')"><i class='fa fa-trash-o admin-icons'></i></a>
</td>
</tr>
diff --git a/view/tpl/admin_plugins.tpl b/view/tpl/admin_plugins.tpl
index 4360aa30c..adc0db434 100755
--- a/view/tpl/admin_plugins.tpl
+++ b/view/tpl/admin_plugins.tpl
@@ -2,7 +2,7 @@
<div class="section-title-wrapper">
{{if $allowManageRepos}}
<div class="pull-right">
- <button class="btn btn-success btn-xs" onclick="openClose('form');">{{$managerepos}}</button>
+ <button class="btn btn-success btn-sm" onclick="openClose('form');">{{$managerepos}}</button>
</div>
{{/if}}
<h2 id="title">{{$title}} - {{$page}}</h2>
@@ -23,10 +23,10 @@
<span class="pull-left">{{$repo.name}}</span><span id="update-message-{{$repo.name}}" style="margin-left: 20px;"></span>
</td>
<td style="width: 15%;">
- <button class="btn btn-xs btn-primary pull-right" style="margin-left: 10px; margin-right: 10px;" onclick="updateAddonRepo('{{$repo.name}}'); return false;"><i class='fa fa-download'></i>&nbsp;{{$repoUpdateButton}}</button>
+ <button class="btn btn-sm btn-primary pull-right" style="margin-left: 10px; margin-right: 10px;" onclick="updateAddonRepo('{{$repo.name}}'); return false;"><i class='fa fa-download'></i>&nbsp;{{$repoUpdateButton}}</button>
</td>
<td style="width: 15%;">
- <button class="btn btn-xs btn-danger pull-right" style="margin-left: 10px; margin-right: 0px;" onclick="removeAddonRepo('{{$repo.name}}'); return false;"><i class='fa fa-trash-o'></i>&nbsp;{{$repoRemoveButton}}</button>
+ <button class="btn btn-sm btn-danger pull-right" style="margin-left: 10px; margin-right: 0px;" onclick="removeAddonRepo('{{$repo.name}}'); return false;"><i class='fa fa-trash-o'></i>&nbsp;{{$repoRemoveButton}}</button>
</td>
<div class="clear"></div>
</td></tr>
@@ -41,8 +41,8 @@
{{$form}}
</div>
<div class="clear"></div>
- <div id="chat-rotator-wrapper" class="center-block">
- <div id="chat-rotator"></div>
+ <div id="chat-rotator" class="spinner-wrapper">
+ <div class="spinner s"></div>
</div>
<div class="clear"></div>
<div class="section-content-wrapper-np">
@@ -75,11 +75,11 @@
$("#generic-modal-ok-{{$newRepoModalID}}").addClass('btn-primary');
var repoURL = $('#id_repoURL').val();
var repoName = $('#id_repoName').val();
- $('#chat-rotator').spin('tiny');
+ $('#chat-rotator').show();
$.post(
"/admin/plugins/addrepo", {repoURL: repoURL, repoName: repoName},
function(response) {
- $('#chat-rotator').spin(false);
+ $('#chat-rotator').hide();
if (response.success) {
var modalBody = $('#generic-modal-body-{{$newRepoModalID}}');
modalBody.html('<div>'+response.repo.readme+'</div>');
@@ -187,4 +187,4 @@
}
}
-</script> \ No newline at end of file
+</script>
diff --git a/view/tpl/admin_profiles.tpl b/view/tpl/admin_profiles.tpl
index 35685505f..e3a08449c 100644
--- a/view/tpl/admin_profiles.tpl
+++ b/view/tpl/admin_profiles.tpl
@@ -1,5 +1,5 @@
<div class="generic-content-wrapper">
-<div class="section-title-wrapper"><a title="{{$new}}" class="btn btn-primary btn-xs pull-right" href="admin/profs/new"><i class="fa fa-plus-circle"></i>&nbsp;{{$new}}</a><h2>{{$title}}</h2>
+<div class="section-title-wrapper"><a title="{{$new}}" class="btn btn-primary btn-sm pull-right" href="admin/profs/new"><i class="fa fa-plus-circle"></i>&nbsp;{{$new}}</a><h2>{{$title}}</h2>
<div class="clear"></div>
</div>
@@ -28,7 +28,7 @@
<table width="100%">
{{foreach $cust_fields as $field}}
-<tr><td>{{$field.field_name}}</td><td>{{$field.field_desc}}</td><td><a class="btn btn-danger btn-xs" href="admin/profs/drop/{{$field.id}}" title="{{$drop}}"><i class="fa fa-trash-o"></i>&nbsp;{{$drop}}</a> <a class="btn btn-xs" title="{{$edit}}" href="admin/profs/{{$field.id}}" ><i class="fa fa-pencil"></i></a></td></tr>
+<tr><td>{{$field.field_name}}</td><td>{{$field.field_desc}}</td><td><a class="btn btn-danger btn-sm" href="admin/profs/drop/{{$field.id}}" title="{{$drop}}"><i class="fa fa-trash-o"></i>&nbsp;{{$drop}}</a> <a class="btn btn-sm" title="{{$edit}}" href="admin/profs/{{$field.id}}" ><i class="fa fa-pencil"></i></a></td></tr>
{{/foreach}}
</table>
{{/if}}
diff --git a/view/tpl/admin_queue.tpl b/view/tpl/admin_queue.tpl
index 35c2e644a..9d3d848c9 100644
--- a/view/tpl/admin_queue.tpl
+++ b/view/tpl/admin_queue.tpl
@@ -7,7 +7,7 @@
{{foreach $entries as $e}}
-<tr><td>{{$e.total}}</td><td>{{$e.outq_posturl}}</td><td>{{$e.priority}}</td>{{if $expert}}<td><a href="admin/queue?f=&drophub={{$e.eurl}}" title="{{$nukehub}}" class="btn btn-default"><i class="fa fa-times"></i><a></td><td><a href="admin/queue?f=&emptyhub={{$e.eurl}}" title="{{$empty}}" class="btn btn-default"><i class="fa fa-trash-o"></i></a></td>{{/if}}</tr>
+<tr><td>{{$e.total}}</td><td>{{$e.outq_posturl}}</td><td>{{$e.priority}}</td>{{if $expert}}<td><a href="admin/queue?f=&drophub={{$e.eurl}}" title="{{$nukehub}}" class="btn btn-outline-secondary"><i class="fa fa-times"></i><a></td><td><a href="admin/queue?f=&emptyhub={{$e.eurl}}" title="{{$empty}}" class="btn btn-outline-secondary"><i class="fa fa-trash-o"></i></a></td>{{/if}}</tr>
{{/foreach}}
</table>
diff --git a/view/tpl/admin_site.tpl b/view/tpl/admin_site.tpl
index 0bb3ceb15..d6ff34f93 100755
--- a/view/tpl/admin_site.tpl
+++ b/view/tpl/admin_site.tpl
@@ -41,16 +41,18 @@
<input type='hidden' name='form_security_token' value='{{$form_security_token}}'>
{{include file="field_input.tpl" field=$sitename}}
- {{include file="field_select.tpl" field=$server_role}}
- {{if $z_server_role == 'pro'}}
{{include file="field_select.tpl" field=$techlevel}}
{{include file="field_checkbox.tpl" field=$techlock}}
- {{/if}}
{{include file="field_textarea.tpl" field=$banner}}
{{include file="field_textarea.tpl" field=$siteinfo}}
{{include file="field_textarea.tpl" field=$admininfo}}
+
+ {{include file="field_input.tpl" field=$reply_address}}
+ {{include file="field_input.tpl" field=$from_email}}
+ {{include file="field_input.tpl" field=$from_email_name}}
+
{{include file="field_select.tpl" field=$language}}
{{include file="field_select.tpl" field=$theme}}
{{include file="field_select.tpl" field=$theme_mobile}}
@@ -71,9 +73,6 @@
{{include file="field_select.tpl" field=$access_policy}}
<div class="submit"><input type="submit" name="page_site" value="{{$submit}}" /></div>
- <h3>{{$upload}}</h3>
- {{include file="field_input.tpl" field=$maximagesize}}
-
<h3>{{$corporate}}</h3>
{{include file="field_checkbox.tpl" field=$verify_email}}
{{include file="field_checkbox.tpl" field=$feed_contacts}}
@@ -83,6 +82,7 @@
<div class="submit"><input type="submit" name="page_site" value="{{$submit}}" /></div>
<h3>{{$advanced}}</h3>
+ {{include file="field_input.tpl" field=$imagick_path}}
{{include file="field_input.tpl" field=$proxy}}
{{include file="field_input.tpl" field=$proxyuser}}
{{include file="field_input.tpl" field=$timeout}}
diff --git a/view/tpl/admin_summary.tpl b/view/tpl/admin_summary.tpl
index ca94b0ef7..8125703d7 100755
--- a/view/tpl/admin_summary.tpl
+++ b/view/tpl/admin_summary.tpl
@@ -12,7 +12,7 @@
</dl>
<dl>
<dt>{{$accounts.0}}</dt>
- <dd>{{foreach from=$accounts.1 item=acc name=account}}<span title="{{$acc.label}}">{{$acc.val}}</span>{{if !$smarty.foreach.account.last}} / {{/if}}{{/foreach}}</dd>
+ <dd>{{foreach from=$accounts.1 item=acc name=account}}<span title="{{$acc.label}}">{{$acc.val}} {{$acc.label}}</span>{{if !$smarty.foreach.account.last}} / {{/if}}{{/foreach}}</dd>
</dl>
<dl>
<dt>{{$pending.0}}</dt>
@@ -20,7 +20,7 @@
</dl>
<dl>
<dt>{{$channels.0}}</dt>
- <dd>{{foreach from=$channels.1 item=ch name=chan}}<span title="{{$ch.label}}">{{$ch.val}}</span>{{if !$smarty.foreach.chan.last}} / {{/if}}{{/foreach}}</dd>
+ <dd>{{foreach from=$channels.1 item=ch name=chan}}<span title="{{$ch.label}}">{{$ch.val}} {{$ch.label}}</span>{{if !$smarty.foreach.chan.last}} / {{/if}}{{/foreach}}</dd>
</dl>
<dl>
<dt>{{$plugins.0}}</dt>
diff --git a/view/tpl/app.tpl b/view/tpl/app.tpl
index ba97ad501..ac5c18deb 100644
--- a/view/tpl/app.tpl
+++ b/view/tpl/app.tpl
@@ -1,4 +1,4 @@
-{{if !$navapps}}
+{{if ! ($navapps || $order)}}
<div class="app-container">
<div class="app-detail{{if $deleted}} app-deleted{{/if}}">
<a href="{{$app.url}}"{{if $app.target}} target="{{$app.target}}"{{/if}}{{if $app.desc}} title="{{$app.desc}}{{if $app.price}} ({{$app.price}}){{/if}}"{{else}}title="{{$app.name}}"{{/if}}>{{if $icon}}<i class="app-icon fa fa-fw fa-{{$icon}}"></i>{{else}}<img src="{{$app.photo}}" width="80" height="80" />{{/if}}
@@ -8,23 +8,29 @@
{{if $app.type !== 'system'}}
{{if $purchase}}
<div class="app-purchase">
- <a href="{{$app.page}}" class="btn btn-default" title="{{$purchase}}" ><i class="fa fa-external"></i></a>
+ <a href="{{$app.page}}" class="btn btn-outline-secondary" title="{{$purchase}}" ><i class="fa fa-external"></i></a>
</div>
{{/if}}
{{if $install || $update || $delete || $feature}}
<div class="app-tools">
<form action="{{$hosturl}}appman" method="post">
<input type="hidden" name="papp" value="{{$app.papp}}" />
- {{if $install}}<button type="submit" name="install" value="{{$install}}" class="btn btn-default btn-xs" title="{{$install}}" ><i class="fa fa-arrow-circle-o-down" ></i></button>{{/if}}
- {{if $edit}}<input type="hidden" name="appid" value="{{$app.guid}}" /><button type="submit" name="edit" value="{{$edit}}" class="btn btn-default btn-xs" title="{{$edit}}" ><i class="fa fa-pencil" ></i></button>{{/if}}
- {{if $delete}}<button type="submit" name="delete" value="{{if $deleted}}{{$undelete}}{{else}}{{$delete}}{{/if}}" class="btn btn-default btn-xs" title="{{if $deleted}}{{$undelete}}{{else}}{{$delete}}{{/if}}" ><i class="fa fa-trash-o drop-icons"></i></button>{{/if}}
- {{if $feature}}<button type="submit" name="feature" value="feature" class="btn btn-default btn-xs" ><i class="fa fa-star"{{if $featured}} style="color: gold"{{/if}}></i></button>{{/if}}
+ {{if $install}}<button type="submit" name="install" value="{{$install}}" class="btn btn-outline-secondary btn-sm" title="{{$install}}" ><i class="fa fa-arrow-circle-o-down" ></i></button>{{/if}}
+ {{if $edit}}<input type="hidden" name="appid" value="{{$app.guid}}" /><button type="submit" name="edit" value="{{$edit}}" class="btn btn-outline-secondary btn-sm" title="{{$edit}}" ><i class="fa fa-pencil" ></i></button>{{/if}}
+ {{if $delete}}<button type="submit" name="delete" value="{{if $deleted}}{{$undelete}}{{else}}{{$delete}}{{/if}}" class="btn btn-outline-secondary btn-sm" title="{{if $deleted}}{{$undelete}}{{else}}{{$delete}}{{/if}}" ><i class="fa fa-trash-o drop-icons"></i></button>{{/if}}
+ {{if $feature}}<button type="submit" name="feature" value="feature" class="btn btn-outline-secondary btn-sm" title="{{if $featured}}{{$remove}}{{else}}{{$add}}{{/if}}"><i class="fa fa-star"{{if $featured}} style="color: gold"{{/if}}></i></button>{{/if}}
</form>
</div>
{{/if}}
{{/if}}
</div>
-{{else}}
-<li><a href="{{$app.url}}">{{if $icon}}<i class="generic-icons-nav fa fa-fw fa-{{$icon}}"></i>{{else}}<img src="{{$app.photo}}" width="16" height="16" style="margin-right:9px;"/>{{/if}}{{$app.name}}</a></li>
+{{/if}}
+{{if $navapps}}
+<a class="dropdown-item{{if $app.active}} active{{/if}}" href="{{$app.url}}">{{if $icon}}<i class="generic-icons-nav fa fa-fw fa-{{$icon}}"></i>{{else}}<img src="{{$app.photo}}" width="16" height="16" style="margin-right:9px;"/>{{/if}}{{$app.name}}</a>
+{{/if}}
+{{if $order}}
+<a href="{{$hosturl}}appman/{{$app.guid}}/moveup" class="btn btn-outline-secondary btn-sm" style="margin-bottom: 5px;"><i class="generic-icons-nav fa fa-fw fa-arrow-up"></i></a>
+<a href="{{$hosturl}}appman/{{$app.guid}}/movedown" class="btn btn-outline-secondary btn-sm" style="margin-bottom: 5px;"><i class="generic-icons-nav fa fa-fw fa-arrow-down"></i></a>
+{{if $icon}}<i class="generic-icons-nav fa fa-fw fa-{{$icon}}"></i>{{else}}<img src="{{$app.photo}}" width="16" height="16" style="margin-right:9px;"/>{{/if}}{{$app.name}}<br>
{{/if}}
diff --git a/view/tpl/app_create.tpl b/view/tpl/app_create.tpl
index 7a0521436..5075ce5e2 100644
--- a/view/tpl/app_create.tpl
+++ b/view/tpl/app_create.tpl
@@ -3,7 +3,7 @@
<h2>{{$banner}}</h2>
</div>
- <div class="section-content-wrapper">
+ <div class="clearfix section-content-wrapper">
<form action="appman" method="post">
{{if $guid}}
<input type="hidden" name="guid" value="{{$guid}}" />
@@ -33,7 +33,7 @@
{{include file="field_textarea.tpl" field=$embed}}
{{/if}}
- <input type="submit" name="submit" value="{{$submit}}" />
+ <button class="btn btn-primary float-right" type="submit" name="submit" value="{{$submit}}">{{$submit}}</button>
</form>
</div>
diff --git a/view/tpl/app_nav.tpl b/view/tpl/app_nav.tpl
new file mode 100644
index 000000000..046cd7237
--- /dev/null
+++ b/view/tpl/app_nav.tpl
@@ -0,0 +1 @@
+<a class="navbar-app nav-link{{if $app.active}} active{{/if}}" href="{{$app.url}}" title="{{$app.name}}" >{{if $icon}}<i class="fa fa-fw fa-{{$icon}}"></i>{{else}}<img src="{{$app.photo}}" width="16" height="16" />{{/if}}</a>
diff --git a/view/tpl/app_select.tpl b/view/tpl/app_select.tpl
deleted file mode 100644
index 86ea0b1de..000000000
--- a/view/tpl/app_select.tpl
+++ /dev/null
@@ -1,10 +0,0 @@
-{{if $authed}}
-<div class="widget">
-<h3>{{$title}}</h3>
-<ul class="nav nav-pills nav-stacked">
-<li><a href="appman"><i class="fa fa-plus"></i>&nbsp;&nbsp;{{$new}}</a></li>
-<li><a href="apps/edit{{if $cat}}/?f=&cat={{$cat}}{{/if}}"><i class="fa fa-pencil"></i>&nbsp;&nbsp;{{$edit}}</a></li>
-</ul>
-</div>
-{{/if}}
-
diff --git a/view/tpl/apporder.tpl b/view/tpl/apporder.tpl
new file mode 100644
index 000000000..fdb726131
--- /dev/null
+++ b/view/tpl/apporder.tpl
@@ -0,0 +1,7 @@
+<h2>{{$header}}</h2>
+
+<div class="descriptive-text">{{$desc}}</div>
+<br><br><br>
+{{foreach $nav_apps as $nav_app}}
+{{$nav_app}}
+{{/foreach}}
diff --git a/view/tpl/atom_feed.tpl b/view/tpl/atom_feed.tpl
index 37eaf954a..b1e92cdbf 100755
--- a/view/tpl/atom_feed.tpl
+++ b/view/tpl/atom_feed.tpl
@@ -3,31 +3,25 @@
xmlns:thr="http://purl.org/syndication/thread/1.0"
xmlns:at="http://purl.org/atompub/tombstones/1.0"
xmlns:media="http://purl.org/syndication/atommedia"
- xmlns:dfrn="http://purl.org/macgirvin/dfrn/1.0"
+ xmlns:dfrn="http://purl.org/macgirvin/dfrn/1.0"
xmlns:zot="http://purl.org/zot"
xmlns:as="http://activitystrea.ms/spec/1.0/"
- xmlns:georss="http://www.georss.org/georss"
- xmlns:poco="http://portablecontacts.net/spec/1.0"
- xmlns:ostatus="http://ostatus.org/schema/1.0"
- xmlns:statusnet="http://status.net/schema/api/1/" >
+ xmlns:georss="http://www.georss.org/georss"
+ xmlns:poco="http://portablecontacts.net/spec/1.0"
+ xmlns:ostatus="http://ostatus.org/schema/1.0"
+ xmlns:statusnet="http://status.net/schema/api/1/" >
<id>{{$feed_id}}</id>
<title>{{$feed_title}}</title>
<generator uri="http://hubzilla.org" version="{{$version}}">{{$red}}</generator>
<link rel="license" href="http://creativecommons.org/licenses/by/3.0/" />
+ {{if $profile_page}}
<link rel="alternate" type="text/html" href="{{$profile_page}}" />
-{{if $hub}}
- {{$hub}}
-{{/if}}
-{{if $salmon}}
- {{$salmon}}
+ {{/if}}
+{{if $author}}
+{{$author}}
{{/if}}
<updated>{{$feed_updated}}</updated>
- <zot:owner>
- <name>{{$name}}</name>
- <uri>{{$profile_page}}</uri>
- <link rel="photo" type="{{$mimephoto}}" media:width="175" media:height="175" href="{{$photo}}" />
- <link rel="avatar" type="{{$mimephoto}}" media:width="175" media:height="175" href="{{$photo}}" />
- </zot:owner>
+{{$owner}}
diff --git a/view/tpl/attach_edit.tpl b/view/tpl/attach_edit.tpl
index 1d58004e5..62442ff7a 100644
--- a/view/tpl/attach_edit.tpl
+++ b/view/tpl/attach_edit.tpl
@@ -7,19 +7,19 @@
{{if $isadir}}{{include file="field_checkbox.tpl" field=$recurse}}{{/if}}
<div id="attach-edit-tools-share" class="btn-group form-group">
{{if !$isadir}}
- <a href="/rpost?attachment=[attachment]{{$file.hash}},{{$file.revision}}[/attachment]" id="attach-btn" class="btn btn-default btn-xs" title="{{$attach_btn_title}}">
+ <a href="/rpost?attachment=[attachment]{{$file.hash}},{{$file.revision}}[/attachment]" id="attach-btn" class="btn btn-outline-secondary btn-sm" title="{{$attach_btn_title}}">
<i class="fa fa-share-square-o jot-icons"></i>
</a>
{{/if}}
- <button id="link-btn" class="btn btn-default btn-xs" type="button" onclick="openClose('link-code');" title="{{$link_btn_title}}">
+ <button id="link-btn" class="btn btn-outline-secondary btn-sm" type="button" onclick="openClose('link-code');" title="{{$link_btn_title}}">
<i class="fa fa-link jot-icons"></i>
</button>
</div>
<div id="attach-edit-perms" class="btn-group pull-right">
- <button id="dbtn-acl" class="btn btn-default btn-xs" data-toggle="modal" data-target="#aclModal" title="{{$permset}}" type="button">
+ <button id="dbtn-acl" class="btn btn-outline-secondary btn-sm" data-toggle="modal" data-target="#aclModal" title="{{$permset}}" type="button">
<i id="jot-perms-icon" class="fa fa-{{$lockstate}} jot-icons"></i>
</button>
- <button id="dbtn-submit" class="btn btn-primary btn-xs" type="submit" name="submit">
+ <button id="dbtn-submit" class="btn btn-primary btn-sm" type="submit" name="submit">
{{$submit}}
</button>
</div>
diff --git a/view/tpl/blocklist.tpl b/view/tpl/blocklist.tpl
index c88d91463..7f400bba2 100644
--- a/view/tpl/blocklist.tpl
+++ b/view/tpl/blocklist.tpl
@@ -2,7 +2,7 @@
<div class="section-title-wrapper">
{{if $editor}}
<div class="pull-right">
- <button id="webpage-create-btn" class="btn btn-xs btn-success" onclick="openClose('block-editor');"><i class="fa fa-pencil-square-o"></i>&nbsp;{{$create}}</button>
+ <button id="webpage-create-btn" class="btn btn-sm btn-success" onclick="openClose('block-editor');"><i class="fa fa-pencil-square-o"></i>&nbsp;{{$create}}</button>
</div>
{{/if}}
<h2>{{$title}}</h2>
@@ -22,8 +22,8 @@
<th width="1%"></th>
<th width="1%"></th>
<th width="1%"></th>
- <th width="1%" class="hidden-xs">{{$created}}</th>
- <th width="1%" class="hidden-xs">{{$edited}}</th>
+ <th width="1%" class="d-none d-md-table-cell">{{$created}}</th>
+ <th width="1%" class="d-none d-md-table-cell">{{$edited}}</th>
</tr>
{{foreach $pages as $key => $items}}
{{foreach $items as $item}}
@@ -53,10 +53,10 @@
<a href="#" title="{{$delete}}" onclick="dropItem('item/drop/{{$item.url}}', '#block-list-item-{{$item.url}}'); return false;"><i class="fa fa-trash-o drop-icons"></i></a>
{{/if}}
</td>
- <td class="hidden-xs">
+ <td class="d-none d-md-table-cell">
{{$item.created}}
</td>
- <td class="hidden-xs">
+ <td class="d-none d-md-table-cell">
{{$item.edited}}
</td>
</tr>
diff --git a/view/tpl/build_query.tpl b/view/tpl/build_query.tpl
index 91bb0bfc0..a76d4e549 100755
--- a/view/tpl/build_query.tpl
+++ b/view/tpl/build_query.tpl
@@ -20,6 +20,7 @@
var bParam_static = {{$static}};
var bParam_search = "{{$search}}";
+ var bParam_xchan = "{{$xchan}}";
var bParam_order = "{{$order}}";
var bParam_file = "{{$file}}";
var bParam_cats = "{{$cats}}";
@@ -47,6 +48,7 @@
if(bParam_list != 0) bCmd = bCmd + "&list=" + bParam_list;
if(bParam_fh != 0) bCmd = bCmd + "&fh=" + bParam_fh;
if(bParam_search != "") bCmd = bCmd + "&search=" + bParam_search;
+ if(bParam_xchan != "") bCmd = bCmd + "&xchan=" + bParam_xchan;
if(bParam_order != "") bCmd = bCmd + "&order=" + bParam_order;
if(bParam_file != "") bCmd = bCmd + "&file=" + bParam_file;
if(bParam_cats != "") bCmd = bCmd + "&cat=" + bParam_cats;
diff --git a/view/tpl/cards.tpl b/view/tpl/cards.tpl
new file mode 100644
index 000000000..60e6163ae
--- /dev/null
+++ b/view/tpl/cards.tpl
@@ -0,0 +1,4 @@
+<div id="live-cards"></div>
+{{$editor}}
+{{$content}}
+{{$pager}}
diff --git a/view/tpl/categories_widget.tpl b/view/tpl/categories_widget.tpl
index ea6d28dfc..72478aa3d 100755
--- a/view/tpl/categories_widget.tpl
+++ b/view/tpl/categories_widget.tpl
@@ -2,10 +2,10 @@
<h3>{{$title}}</h3>
<div id="categories-sidebar-desc">{{$desc}}</div>
- <ul class="nav nav-pills nav-stacked">
- <li><a href="{{$base}}"{{if $sel_all}} class="categories-selected"{{/if}}>{{$all}}</a></li>
+ <ul class="nav nav-pills flex-column">
+ <li class="nav-item"><a href="{{$base}}" class="nav-link{{if $sel_all}} active{{/if}}">{{$all}}</a></li>
{{foreach $terms as $term}}
- <li><a href="{{$base}}?f=&cat={{$term.name}}"{{if $term.selected}} class="categories-selected"{{/if}}>{{$term.name}}</a></li>
+ <li class="nav-item"><a href="{{$base}}?f=&cat={{$term.name}}" class="nav-link{{if $term.selected}} active{{/if}}">{{$term.name}}</a></li>
{{/foreach}}
</ul>
diff --git a/view/tpl/cdav_addressbook.tpl b/view/tpl/cdav_addressbook.tpl
new file mode 100644
index 000000000..587a95caa
--- /dev/null
+++ b/view/tpl/cdav_addressbook.tpl
@@ -0,0 +1,462 @@
+<script>
+$(document).ready(function() {
+
+ $(document).on('click', '.vcard-header, .vcard-cancel-btn', updateView);
+ $(document).on('click', '.add-field', doAdd);
+ $(document).on('click', '.remove-field', doRemove);
+
+ function updateView() {
+ var id = $(this).data('id');
+ var action = $(this).data('action');
+ var header = $('#vcard-header-' + id);
+ var cancel = $('#vcard-cancel-' + id);
+ var addField = $('#vcard-add-field-' + id);
+ var info = $('#vcard-info-' + id);
+ var vcardPreview = $('#vcard-preview-' + id);
+ var fn = $('#vcard-fn-' + id);
+
+ if(action === 'open') {
+ $(header).addClass('active');
+ $(cancel).show();
+ $(addField).show();
+ $(info).show();
+ $(fn).show();
+ $(vcardPreview).hide();
+ }
+ else {
+ $(header).removeClass('active');
+ $(cancel).hide();
+ $(addField).hide();
+ $(info).hide();
+ $(fn).hide();
+ $(vcardPreview).show();
+ }
+ }
+
+ function doAdd(e) {
+ e.preventDefault();
+ var what = $(this).data('add');
+ var id = $(this).data('id');
+ var element = '#template-form-' + what;
+ var where = '#card_form_' + id;
+
+ $(element + ' .remove-field').attr('data-id', id)
+
+ if(what === 'vcard-adr') {
+ var adrCount = $(where + ' .form-' + what).length;
+ var attrName = 'adr[' + adrCount + '][]';
+ $(element + ' input').attr('name', attrName);
+ }
+
+ if(what === 'vcard-org' || what === 'vcard-title' || what === 'vcard-note') {
+ $(where + ' .add-' + what).hide()
+ }
+
+ $(element).clone().removeAttr('id').appendTo(where + ' .form-' + what + '-wrapper');
+ }
+
+ function doRemove() {
+ var what = $(this).data('remove');
+ var element = $(this).parents('div.form-' + what);
+ var where = '#card_form_' + $(this).data('id');
+
+ if(what === 'vcard-org' || what === 'vcard-title' || what === 'vcard-note') {
+ $(where + ' .add-' + what).show()
+ }
+
+ $(element).remove();
+ }
+
+});
+</script>
+<div id="template-form-vcard-org" class="form-group form-vcard-org">
+ <div class="form-group form-vcard-org">
+ <input type="text" name="org" value="" placeholder="{{$org_label}}">
+ <i data-remove="vcard-org" data-id="" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+ </div>
+</div>
+
+<div id="template-form-vcard-title" class="form-group form-vcard-title">
+ <div class="form-group form-vcard-title">
+ <input type="text" name="title" value="" placeholder="{{$title_label}}">
+ <i data-remove="vcard-title" data-id="" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+ </div>
+</div>
+
+<div id="template-form-vcard-tel" class="form-group form-vcard-tel">
+ <select name="tel_type[]">
+ <option value="CELL">{{$mobile}}</option>
+ <option value="HOME">{{$home}}</option>
+ <option value="WORK">{{$work}}</option>
+ <option value="OTHER">{{$other}}</option>
+ </select>
+ <input type="text" name="tel[]" value="" placeholder="{{$tel_label}}">
+ <i data-remove="vcard-tel" data-id="" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+</div>
+
+<div id="template-form-vcard-email" class="form-group form-vcard-email">
+ <select name="email_type[]">
+ <option value="HOME">{{$home}}</option>
+ <option value="WORK">{{$work}}</option>
+ <option value="OTHER">{{$other}}</option>
+ </select>
+ <input type="text" name="email[]" value="" placeholder="{{$email_label}}">
+ <i data-remove="vcard-email" data-id="" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+</div>
+
+<div id="template-form-vcard-impp" class="form-group form-vcard-impp">
+ <select name="impp_type[]">
+ <option value="HOME">{{$home}}</option>
+ <option value="WORK">{{$work}}</option>
+ <option value="OTHER">{{$other}}</option>
+ </select>
+ <input type="text" name="impp[]" value="" placeholder="{{$impp_label}}">
+ <i data-remove="vcard-impp" data-id="" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+</div>
+
+<div id="template-form-vcard-url" class="form-group form-vcard-url">
+ <select name="url_type[]">
+ <option value="HOME">{{$home}}</option>
+ <option value="WORK">{{$work}}</option>
+ <option value="OTHER">{{$other}}</option>
+ </select>
+ <input type="text" name="url[]" value="" placeholder="{{$url_label}}">
+ <i data-remove="vcard-url" data-id="" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+</div>
+
+<div id="template-form-vcard-adr" class="form-group form-vcard-adr">
+ <div class="form-group">
+ <select name="adr_type[]">
+ <option value="HOME">{{$home}}</option>
+ <option value="WORK">{{$work}}</option>
+ <option value="OTHER">{{$other}}</option>
+ </select>
+ <label>{{$adr_label}}</label>
+ <i data-remove="vcard-adr" data-id="" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+ </div>
+ <div class="form-group">
+ <input type="text" name="" value="" placeholder="{{$po_box}}">
+ </div>
+ <div class="form-group">
+ <input type="text" name="" value="" placeholder="{{$extra}}">
+ </div>
+ <div class="form-group">
+ <input type="text" name="" value="" placeholder="{{$street}}">
+ </div>
+ <div class="form-group">
+ <input type="text" name="" value="" placeholder="{{$locality}}">
+ </div>
+ <div class="form-group">
+ <input type="text" name="" value="" placeholder="{{$region}}">
+ </div>
+ <div class="form-group">
+ <input type="text" name="" value="" placeholder="{{$zip_code}}">
+ </div>
+ <div class="form-group">
+ <input type="text" name="" value="" placeholder="{{$country}}">
+ </div>
+</div>
+
+<div id="template-form-vcard-note" class="form-group form-vcard-note">
+ <label>{{$note_label}}</label>
+ <i data-remove="vcard-note" data-id="" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+ <textarea name="note" class="form-control"></textarea>
+</div>
+
+<div class="generic-content-wrapper">
+ <div class="section-title-wrapper">
+ <button type="button" class="btn btn-success btn-sm float-right" onclick="openClose('create_form')"><i class="fa fa-plus-circle"></i> {{$add_card}}</button>
+ <h2>{{$displayname}}</h2>
+ </div>
+ <div id="create_form" class="section-content-tools-wrapper">
+ <form id="card_form_new" method="post" action="">
+ <input type="hidden" name="target" value="{{$id}}">
+ <div class="dropdown pull-right">
+ <button data-toggle="dropdown" type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle"><i class="fa fa-plus"></i> {{$add_field}}</button>
+ <div class="dropdown-menu dropdown-menu-right">
+ <a class="dropdown-item add-vcard-org add-field" style="display: none" href="#" data-add="vcard-org" data-id="new">{{$org_label}}</a>
+ <a class="dropdown-item add-vcard-title add-field" style="display: none" href="#" data-add="vcard-title" data-id="new">{{$title_label}}</a>
+ <a class="dropdown-item add-vcard-tel add-field" href="#" data-add="vcard-tel" data-id="new">{{$tel_label}}</a>
+ <a class="dropdown-item add-vcard-email add-field" href="#" data-add="vcard-email" data-id="new">{{$email_label}}</a>
+ <a class="dropdown-item add-vcard-impp add-field" href="#" data-add="vcard-impp" data-id="new">{{$impp_label}}</a>
+ <a class="dropdown-item add-vcard-url add-field" href="#" data-add="vcard-url" data-id="new">{{$url_label}}</a>
+ <a class="dropdown-item add-vcard-adr add-field" href="#" data-add="vcard-adr" data-id="new">{{$adr_label}}</a>
+ <a class="dropdown-item add-vcard-note add-field" href="#" data-add="vcard-note" data-id="new">{{$note_label}}</a>
+ </div>
+ </div>
+
+ <div class="vcard-fn-create form-group">
+ <div class="form-vcard-fn-wrapper">
+ <div class="form-group form-vcard-fn">
+ <div class="vcard-nophoto"><i class="fa fa-user"></i></div><input type="text" name="fn" value="" placeholder="{{$name_label}}">
+ </div>
+ </div>
+ </div>
+
+ <div class="vcard-org form-group">
+ <div class="form-vcard-org-wrapper">
+ <div class="form-group form-vcard-org">
+ <input type="text" name="org" value="" placeholder="{{$org_label}}">
+ <i data-remove="vcard-org" data-id="new" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+ </div>
+ </div>
+ </div>
+
+ <div class="vcard-title form-group">
+ <div class="form-vcard-title-wrapper">
+ <div class="form-group form-vcard-title">
+ <input type="text" name="title" value="" placeholder="{{$title_label}}">
+ <i data-remove="vcard-title" data-id="new" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+ </div>
+ </div>
+ </div>
+
+ <div class="vcard-tel form-group">
+ <div class="form-vcard-tel-wrapper">
+ <div class="form-group form-vcard-tel">
+ <select name="tel_type[]">
+ <option value="CELL">{{$mobile}}</option>
+ <option value="HOME">{{$home}}</option>
+ <option value="WORK">{{$work}}</option>
+ <option value="OTHER">{{$other}}</option>
+ </select>
+ <input type="text" name="tel[]" value="" placeholder="{{$tel_label}}">
+ <i data-remove="vcard-tel" data-id="new" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+ </div>
+ </div>
+ </div>
+
+
+ <div class="vcard-email form-group">
+ <div class="form-vcard-email-wrapper">
+ <div class="form-group form-vcard-email">
+ <select name="email_type[]">
+ <option value="HOME">{{$home}}</option>
+ <option value="WORK">{{$work}}</option>
+ <option value="OTHER">{{$other}}</option>
+ </select>
+ <input type="text" name="email[]" value="" placeholder="{{$email_label}}">
+ <i data-remove="vcard-email" data-id="new" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+ </div>
+ </div>
+ </div>
+
+ <div class="vcard-impp form-group">
+ <div class="form-vcard-impp-wrapper">
+ </div>
+ </div>
+
+ <div class="vcard-url form-group">
+ <div class="form-vcard-url-wrapper">
+ </div>
+ </div>
+
+ <div class="vcard-adr form-group">
+ <div class="form-vcard-adr-wrapper">
+ </div>
+ </div>
+
+ <div class="vcard-note form-group">
+ <div class="form-vcard-note-wrapper">
+ </div>
+ </div>
+
+ <button type="submit" name="create" value="create_card" class="btn btn-primary btn-sm pull-right">{{$create}}</button>
+ <button type="button" class="btn btn-outline-secondary btn-sm" onclick="openClose('create_form')">{{$cancel}}</button>
+ <div class="clear"></div>
+ </form>
+ </div>
+
+ {{foreach $cards as $card}}
+ <form id="card_form_{{$card.id}}" method="post" action="">
+ <input type="hidden" name="target" value="{{$id}}">
+ <input type="hidden" name="uri" value="{{$card.uri}}">
+ <div class="section-content-wrapper-np">
+ <div id="vcard-cancel-{{$card.id}}" class="vcard-cancel vcard-cancel-btn" data-id="{{$card.id}}" data-action="cancel"><i class="fa fa-close"></i></div>
+ <div id="vcard-add-field-{{$card.id}}" class="dropdown pull-right vcard-add-field">
+ <button data-toggle="dropdown" type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle"><i class="fa fa-plus"></i> {{$add_field}}</button>
+ <div class="dropdown-menu dropdown-menu-right">
+ <a class="dropdown-item add-vcard-org add-field"{{if $card.org}} style="display: none"{{/if}} href="#" data-add="vcard-org" data-id="{{$card.id}}">{{$org_label}}</a>
+ <a class="dropdown-item add-vcard-title add-field"{{if $card.title}} style="display: none"{{/if}} href="#" data-add="vcard-title" data-id="{{$card.id}}">{{$title_label}}</a>
+ <a class="dropdown-item add-vcard-tel add-field" href="#" data-add="vcard-tel" data-id="{{$card.id}}">{{$tel_label}}</a>
+ <a class="dropdown-item add-vcard-email add-field" href="#" data-add="vcard-email" data-id="{{$card.id}}">{{$email_label}}</a>
+ <a class="dropdown-item add-vcard-impp add-field" href="#" data-add="vcard-impp" data-id="{{$card.id}}">{{$impp_label}}</a>
+ <a class="dropdown-item add-vcard-url add-field" href="#" data-add="vcard-url" data-id="{{$card.id}}">{{$url_label}}</a>
+ <a class="dropdown-item add-vcard-adr add-field" href="#" data-add="vcard-adr" data-id="{{$card.id}}">{{$adr_label}}</a>
+ <a class="dropdown-item add-vcard-note add-field"{{if $card.note}} style="display: none"{{/if}} href="#" data-add="vcard-note" data-id="{{$card.id}}">{{$note_label}}</a>
+ </div>
+ </div>
+ <div id="vcard-header-{{$card.id}}" class="vcard-header" data-id="{{$card.id}}" data-action="open">
+ {{if $card.photo}}<img class="vcard-photo" src="{{$card.photo}}" width="32px" height="32px">{{else}}<div class="vcard-nophoto"><i class="fa fa-user"></i></div>{{/if}}
+ <span id="vcard-preview-{{$card.id}}" class="vcard-preview">
+ {{if $card.fn}}<span class="vcard-fn-preview">{{$card.fn}}</span>{{/if}}
+ {{if $card.emails.0.address}}<span class="vcard-email-preview hidden-xs">{{$card.emails.0.address}}</span>{{/if}}
+ {{if $card.tels.0}}<span class="vcard-tel-preview hidden-xs">{{$card.tels.0.nr}}</span>{{/if}}
+ </span>
+ <input id="vcard-fn-{{$card.id}}" class="vcard-fn" type="text" name="fn" value="{{$card.fn}}" size="{{$card.fn|count_characters:true}}" placeholder="{{$name_label}}">
+ </div>
+ </div>
+ <div id="vcard-info-{{$card.id}}" class="vcard-info section-content-wrapper">
+
+ <div class="vcard-org form-group">
+ <div class="form-vcard-org-wrapper">
+ {{if $card.org}}
+ <div class="form-group form-vcard-org">
+ <input type="text" name="org" value="{{$card.org}}" size="{{$card.org|count_characters:true}}" placeholder="{{$org_label}}">
+ <i data-remove="vcard-org" data-id="{{$card.id}}" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+ </div>
+ {{/if}}
+ </div>
+ </div>
+
+ <div class="vcard-title form-group">
+ <div class="form-vcard-title-wrapper">
+ {{if $card.title}}
+ <div class="form-group form-vcard-title">
+ <input type="text" name="title" value="{{$card.title}}" size="{{$card.title|count_characters:true}}" placeholder="{{$title_label}}">
+ <i data-remove="vcard-title" data-id="{{$card.id}}" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+ </div>
+ {{/if}}
+ </div>
+ </div>
+
+
+ <div class="vcard-tel form-group">
+ <div class="form-vcard-tel-wrapper">
+ {{if $card.tels}}
+ {{foreach $card.tels as $tel}}
+ <div class="form-group form-vcard-tel">
+ <select name="tel_type[]">
+ <option value=""{{if $tel.type.0 != 'CELL' && $tel.type.0 != 'HOME' && $tel.type.0 != 'WORK' && $tel.type.0 != 'OTHER'}} selected="selected"{{/if}}>{{$tel.type.1}}</option>
+ <option value="CELL"{{if $tel.type.0 == 'CELL'}} selected="selected"{{/if}}>{{$mobile}}</option>
+ <option value="HOME"{{if $tel.type.0 == 'HOME'}} selected="selected"{{/if}}>{{$home}}</option>
+ <option value="WORK"{{if $tel.type.0 == 'WORK'}} selected="selected"{{/if}}>{{$work}}</option>
+ <option value="OTHER"{{if $tel.type.0 == 'OTHER'}} selected="selected"{{/if}}>{{$other}}</option>
+ </select>
+ <input type="text" name="tel[]" value="{{$tel.nr}}" size="{{$tel.nr|count_characters:true}}" placeholder="{{$tel_label}}">
+ <i data-remove="vcard-tel" data-id="{{$card.id}}" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+ </div>
+ {{/foreach}}
+ {{/if}}
+ </div>
+ </div>
+
+
+ <div class="vcard-email form-group">
+ <div class="form-vcard-email-wrapper">
+ {{if $card.emails}}
+ {{foreach $card.emails as $email}}
+ <div class="form-group form-vcard-email">
+ <select name="email_type[]">
+ <option value=""{{if $email.type.0 != 'HOME' && $email.type.0 != 'WORK' && $email.type.0 != 'OTHER'}} selected="selected"{{/if}}>{{$email.type.1}}</option>
+ <option value="HOME"{{if $email.type.0 == 'HOME'}} selected="selected"{{/if}}>{{$home}}</option>
+ <option value="WORK"{{if $email.type.0 == 'WORK'}} selected="selected"{{/if}}>{{$work}}</option>
+ <option value="OTHER"{{if $email.type.0 == 'OTHER'}} selected="selected"{{/if}}>{{$other}}</option>
+ </select>
+ <input type="text" name="email[]" value="{{$email.address}}" size="{{$email.address|count_characters:true}}" placeholder="{{$email_label}}">
+ <i data-remove="vcard-email" data-id="{{$card.id}}" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+ </div>
+ {{/foreach}}
+ {{/if}}
+ </div>
+ </div>
+
+ <div class="vcard-impp form-group">
+ <div class="form-vcard-impp-wrapper">
+ {{if $card.impps}}
+ {{foreach $card.impps as $impp}}
+ <div class="form-group form-vcard-impp">
+ <select name="impp_type[]">
+ <option value=""{{if $impp.type.0 != 'HOME' && $impp.type.0 != 'WORK' && $impp.type.0 != 'OTHER'}} selected="selected"{{/if}}>{{$impp.type.1}}</option>
+ <option value="HOME"{{if $impp.type.0 == 'HOME'}} selected="selected"{{/if}}>{{$home}}</option>
+ <option value="WORK"{{if $impp.type.0 == 'WORK'}} selected="selected"{{/if}}>{{$work}}</option>
+ <option value="OTHER"{{if $impp.type.0 == 'OTHER'}} selected="selected"{{/if}}>{{$other}}</option>
+ </select>
+ <input type="text" name="impp[]" value="{{$impp.address}}" size="{{$impp.address|count_characters:true}}" placeholder="{{$impp_label}}">
+ <i data-remove="vcard-impp" data-id="{{$card.id}}" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+ </div>
+ {{/foreach}}
+ {{/if}}
+ </div>
+ </div>
+
+ <div class="vcard-url form-group">
+ <div class="form-vcard-url-wrapper">
+ {{if $card.urls}}
+ {{foreach $card.urls as $url}}
+ <div class="form-group form-vcard-url">
+ <select name="url_type[]">
+ <option value=""{{if $url.type.0 != 'HOME' && $url.type.0 != 'WORK' && $url.type.0 != 'OTHER'}} selected="selected"{{/if}}>{{$url.type.1}}</option>
+ <option value="HOME"{{if $url.type.0 == 'HOME'}} selected="selected"{{/if}}>{{$home}}</option>
+ <option value="WORK"{{if $url.type.0 == 'WORK'}} selected="selected"{{/if}}>{{$work}}</option>
+ <option value="OTHER"{{if $url.type.0 == 'OTHER'}} selected="selected"{{/if}}>{{$other}}</option>
+ </select>
+ <input type="text" name="url[]" value="{{$url.address}}" size="{{$url.address|count_characters:true}}" placeholder="{{$url_label}}">
+ <i data-remove="vcard-url" data-id="{{$card.id}}" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+ </div>
+ {{/foreach}}
+ {{/if}}
+ </div>
+ </div>
+
+ <div class="vcard-adr form-group">
+ <div class="form-vcard-adr-wrapper">
+ {{if $card.adrs}}
+ {{foreach $card.adrs as $adr}}
+ <div class="form-group form-vcard-adr">
+ <div class="form-group">
+ <label>{{$adr_label}}</label>
+ <select name="adr_type[]">
+ <option value=""{{if $adr.type.0 != 'HOME' && $adr.type.0 != 'WORK' && $adr.type.0 != 'OTHER'}} selected="selected"{{/if}}>{{$adr.type.1}}</option>
+ <option value="HOME"{{if $adr.type.0 == 'HOME'}} selected="selected"{{/if}}>{{$home}}</option>
+ <option value="WORK"{{if $adr.type.0 == 'WORK'}} selected="selected"{{/if}}>{{$work}}</option>
+ <option value="OTHER"{{if $adr.type.0 == 'OTHER'}} selected="selected"{{/if}}>{{$other}}</option>
+ </select>
+ <i data-remove="vcard-adr" data-id="{{$card.id}}" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+ </div>
+ <div class="form-group">
+ <input type="text" name="adr[{{$adr@index}}][]" value="{{$adr.address.0}}" size="{{$adr.address.0|count_characters:true}}" placeholder="{{$po_box}}">
+ </div>
+ <div class="form-group">
+ <input type="text" name="adr[{{$adr@index}}][]" value="{{$adr.address.1}}" size="{{$adr.address.1|count_characters:true}}" placeholder="{{$extra}}">
+ </div>
+ <div class="form-group">
+ <input type="text" name="adr[{{$adr@index}}][]" value="{{$adr.address.2}}" size="{{$adr.address.2|count_characters:true}}" placeholder="{{$street}}">
+ </div>
+ <div class="form-group">
+ <input type="text" name="adr[{{$adr@index}}][]" value="{{$adr.address.3}}" size="{{$adr.address.3|count_characters:true}}" placeholder="{{$locality}}">
+ </div>
+ <div class="form-group">
+ <input type="text" name="adr[{{$adr@index}}][]" value="{{$adr.address.4}}" size="{{$adr.address.4|count_characters:true}}" placeholder="{{$region}}">
+ </div>
+ <div class="form-group">
+ <input type="text" name="adr[{{$adr@index}}][]" value="{{$adr.address.5}}" size="{{$adr.address.5|count_characters:true}}" placeholder="{{$zip_code}}">
+ </div>
+ <div class="form-group">
+ <input type="text" name="adr[{{$adr@index}}][]" value="{{$adr.address.6}}" size="{{$adr.address.6|count_characters:true}}" placeholder="{{$country}}">
+ </div>
+ </div>
+ {{/foreach}}
+ {{/if}}
+ </div>
+ </div>
+
+ <div class="vcard-note form-group form-vcard-note">
+ <div class="form-vcard-note-wrapper">
+ {{if $card.note}}
+ <label>{{$note_label}}</label>
+ <i data-remove="vcard-note" data-id="{{$card.id}}" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+ <textarea name="note" class="form-control">{{$card.note}}</textarea>
+ {{/if}}
+ </div>
+ </div>
+
+
+ <button type="submit" name="update" value="update_card" class="btn btn-primary btn-sm pull-right">{{$update}}</button>
+ <button type="submit" name="delete" value="delete_card" class="btn btn-danger btn-sm">{{$delete}}</button>
+ <button type="button" class="btn btn-outline-secondary btn-sm vcard-cancel-btn" data-id="{{$card.id}}" data-action="cancel">{{$cancel}}</button>
+ <div class="clear"></div>
+ </div>
+ </form>
+ {{/foreach}}
+</div>
diff --git a/view/tpl/cdav_calendar.tpl b/view/tpl/cdav_calendar.tpl
new file mode 100644
index 000000000..b0245e853
--- /dev/null
+++ b/view/tpl/cdav_calendar.tpl
@@ -0,0 +1,349 @@
+<script>
+
+var new_event = [];
+var new_event_id = Math.random().toString(36).substring(7);
+var views = {'month' : '{{$month}}', 'agendaWeek' : '{{$week}}', 'agendaDay' : '{{$day}}', 'listMonth' : '{{$list_month}}', 'listWeek' : '{{$list_week}}', 'listDay' : '{{$list_day}}'};
+
+$(document).ready(function() {
+ $('#calendar').fullCalendar({
+ eventSources: [ {{$sources}} ],
+
+ header: false,
+ eventTextColor: 'white',
+
+ lang: '{{$lang}}',
+ firstDay: {{$first_day}},
+
+ monthNames: aStr['monthNames'],
+ monthNamesShort: aStr['monthNamesShort'],
+ dayNames: aStr['dayNames'],
+ dayNamesShort: aStr['dayNamesShort'],
+ allDayText: aStr['allday'],
+
+ timeFormat: 'HH:mm',
+ timezone: 'local',
+
+ defaultTimedEventDuration: '01:00:00',
+ snapDuration: '00:15:00',
+
+ dayClick: function(date, jsEvent, view) {
+
+ if(new_event.length)
+ $('#calendar').fullCalendar( 'removeEventSource', new_event);
+
+ $('#event_uri').val('');
+ $('#id_title').val('New event');
+ $('#calendar_select').val($("#calendar_select option:first").val()).attr('disabled', false);
+ $('#id_dtstart').val(date.format());
+ $('#id_dtend').val(date.hasTime() ? date.add(1, 'hours').format() : date.add(1, 'days').format());
+ $('#id_description').val('');
+ $('#id_location').val('');
+ $('#event_submit').val('create_event').html('Create');
+ $('#event_delete').hide();
+
+ new_event = [{ id: new_event_id, title : 'New event', start: $('#id_dtstart').val(), end: $('#id_dtend').val(), editable: true, color: '#bbb' }]
+ $('#calendar').fullCalendar( 'addEventSource', new_event);
+ },
+
+ eventClick: function(event, jsEvent, view) {
+
+ if(event.id == new_event_id) {
+ $(window).scrollTop(0);
+ $('.section-content-tools-wrapper, #event_form_wrapper').show();
+ $('#recurrence_warning').hide();
+ $('#id_title').focus().val('');
+ return false;
+ }
+
+ if($('main').hasClass('fullscreen') && view.type !== 'month' && event.rw)
+ $('#calendar').fullCalendar('option', 'height', 'auto');
+
+ if(new_event.length && event.rw) {
+ $('#calendar').fullCalendar( 'removeEventSource', new_event);
+ }
+
+ if(!event.recurrent && event.rw) {
+ var start_clone = moment(event.start);
+ var noend_allday = start_clone.add(1, 'day').format('YYYY-MM-DD');
+
+ $(window).scrollTop(0);
+ $('.section-content-tools-wrapper, #event_form_wrapper').show();
+ $('#recurrence_warning').hide();
+ $('#id_title').focus();
+
+ $('#event_uri').val(event.uri);
+ $('#id_title').val(event.title);
+ $('#calendar_select').val(event.calendar_id[0] + ':' + event.calendar_id[1]).attr('disabled', true);
+ $('#id_dtstart').val(event.start.format());
+ $('#id_dtend').val(event.end ? event.end.format() : event.start.hasTime() ? '' : noend_allday);
+ $('#id_description').val(event.description);
+ $('#id_location').val(event.location);
+ $('#event_submit').val('update_event').html('Update');
+ $('#event_delete').show();
+ }
+ else if(event.recurrent && event.rw) {
+ $('.section-content-tools-wrapper, #recurrence_warning').show();
+ $('#event_form_wrapper').hide();
+ $('#event_uri').val(event.uri);
+ $('#calendar_select').val(event.calendar_id[0] + ':' + event.calendar_id[1]).attr('disabled', true);
+ }
+ },
+
+ eventResize: function(event, delta, revertFunc) {
+
+ $('#id_title').val(event.title);
+ $('#id_dtstart').val(event.start.format());
+ $('#id_dtend').val(event.end.format());
+
+ $.post( 'cdav/calendar', {
+ 'update': 'resize',
+ 'id[]': event.calendar_id,
+ 'uri': event.uri,
+ 'dtstart': event.start ? event.start.format() : '',
+ 'dtend': event.end ? event.end.format() : ''
+ })
+ .fail(function() {
+ revertFunc();
+ });
+ },
+
+ eventDrop: function(event, delta, revertFunc) {
+
+ var start_clone = moment(event.start);
+ var noend_allday = start_clone.add(1, 'day').format('YYYY-MM-DD');
+
+ $('#id_title').val(event.title);
+ $('#id_dtstart').val(event.start.format());
+ $('#id_dtend').val(event.end ? event.end.format() : event.start.hasTime() ? '' : noend_allday);
+
+ $.post( 'cdav/calendar', {
+ 'update': 'drop',
+ 'id[]': event.calendar_id,
+ 'uri': event.uri,
+ 'dtstart': event.start ? event.start.format() : '',
+ 'dtend': event.end ? event.end.format() : event.start.hasTime() ? '' : noend_allday
+ })
+ .fail(function() {
+ revertFunc();
+ });
+ },
+
+ loading: function(isLoading, view) {
+ $('#events-spinner').show();
+ $('#today-btn > i').hide();
+ if(!isLoading) {
+ $('#events-spinner').hide();
+ $('#today-btn > i').show();
+ }
+ }
+ });
+
+ // echo the title
+ var view = $('#calendar').fullCalendar('getView');
+
+ $('#title').text(view.title);
+
+ $('#view_selector').html(views[view.name]);
+
+ $('.color-edit').colorpicker({ input: '.color-edit-input' });
+
+ $(document).on('click','#fullscreen-btn', on_fullscreen);
+ $(document).on('click','#inline-btn', on_inline);
+
+ $(document).on('click','#event_submit', on_submit);
+ $(document).on('click','#event_more', on_more);
+ $(document).on('click','#event_cancel, #event_cancel_recurrent', reset_form);
+ $(document).on('click','#event_delete, #event_delete_recurrent', on_delete);
+
+});
+
+function changeView(action, viewName) {
+ $('#calendar').fullCalendar(action, viewName);
+ var view = $('#calendar').fullCalendar('getView');
+
+ if($('main').hasClass('fullscreen'))
+ if(view.name !== 'month')
+ $('.section-content-tools-wrapper').css('display') === 'none' ? on_fullscreen() : on_inline() ;
+ else
+ on_fullscreen();
+ else
+ on_inline();
+
+ $('#title').text(view.title);
+ $('#view_selector').html(views[view.name]);
+}
+
+function add_remove_json_source(source, color, editable, status) {
+
+ if(status === undefined)
+ status = 'fa-calendar-check-o';
+
+ if(status === 'drop') {
+ reset_form();
+ $('#calendar').fullCalendar( 'removeEventSource', source );
+ return;
+ }
+
+ var parts = source.split('/');
+ var id = parts[4];
+
+ var selector = '#calendar-btn-' + id;
+
+ if($(selector).hasClass('fa-calendar-o')) {
+ $('#calendar').fullCalendar( 'addEventSource', { url: source, color: color, editable: editable });
+ $(selector).removeClass('fa-calendar-o');
+ $(selector).addClass(status);
+ $.get('/cdav/calendar/switch/' + id + '/1');
+ }
+ else {
+ $('#calendar').fullCalendar( 'removeEventSource', source );
+ $(selector).removeClass(status);
+ $(selector).addClass('fa-calendar-o');
+ $.get('/cdav/calendar/switch/' + id + '/0');
+ }
+}
+
+function on_fullscreen() {
+ var view = $('#calendar').fullCalendar('getView');
+ if(($('.section-content-tools-wrapper').css('display') === 'none') || ($('.section-content-tools-wrapper').css('display') !== 'none' && view.type === 'month'))
+ $('#calendar').fullCalendar('option', 'height', $(window).height() - $('.section-title-wrapper').outerHeight(true) - 2); // -2 is for border width (.generic-content-wrapper top and bottom) of .generic-content-wrapper
+}
+
+function on_inline() {
+ var view = $('#calendar').fullCalendar('getView');
+ ((view.type === 'month') ? $('#calendar').fullCalendar('option', 'height', '') : $('#calendar').fullCalendar('option', 'height', 'auto'));
+}
+
+function on_submit() {
+ $.post( 'cdav/calendar', {
+ 'submit': $('#event_submit').val(),
+ 'target': $('#calendar_select').val(),
+ 'uri': $('#event_uri').val(),
+ 'title': $('#id_title').val(),
+ 'dtstart': $('#id_dtstart').val(),
+ 'dtend': $('#id_dtend').val(),
+ 'description': $('#id_description').val(),
+ 'location': $('#id_location').val()
+ })
+ .done(function() {
+ $('#calendar').fullCalendar( 'refetchEventSources', [ {{$sources}} ] );
+ reset_form();
+ });
+}
+
+function on_delete() {
+ $.post( 'cdav/calendar', {
+ 'delete': 'delete',
+ 'target': $('#calendar_select').val(),
+ 'uri': $('#event_uri').val(),
+ })
+ .done(function() {
+ $('#calendar').fullCalendar( 'refetchEventSources', [ {{$sources}} ] );
+ reset_form();
+ });
+}
+
+function reset_form() {
+ $('.section-content-tools-wrapper, #event_form_wrapper, #recurrence_warning').hide();
+
+ $('#event_submit').val('');
+ $('#calendar_select').val('');
+ $('#event_uri').val('');
+ $('#id_title').val('');
+ $('#id_dtstart').val('');
+ $('#id_dtend').val('');
+
+ if(new_event.length)
+ $('#calendar').fullCalendar( 'removeEventSource', new_event);
+
+ if($('#more_block').hasClass('open'))
+ on_more();
+
+ if($('main').hasClass('fullscreen'))
+ on_fullscreen();
+}
+
+function on_more() {
+ if($('#more_block').hasClass('open')) {
+ $('#event_more').html('<i class="fa fa-caret-down"></i> {{$more}}');
+ $('#more_block').removeClass('open').hide();
+ }
+ else {
+ $('#event_more').html('<i class="fa fa-caret-up"></i> {{$less}}');
+ $('#more_block').addClass('open').show();
+ }
+}
+
+</script>
+
+<div class="generic-content-wrapper">
+ <div class="section-title-wrapper">
+ <div class="float-right">
+ <div class="dropdown">
+ <button id="view_selector" type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown"></button>
+ <div class="dropdown-menu">
+ <a class="dropdown-item" href="#" onclick="changeView('changeView', 'month'); return false;">{{$month}}</a></li>
+ <a class="dropdown-item" href="#" onclick="changeView('changeView', 'agendaWeek'); return false;">{{$week}}</a></li>
+ <a class="dropdown-item" href="#" onclick="changeView('changeView', 'agendaDay'); return false;">{{$day}}</a></li>
+ <div class="dropdown-divider"></div>
+ <a class="dropdown-item" href="#" onclick="changeView('changeView', 'listMonth'); return false;">{{$list_month}}</a></li>
+ <a class="dropdown-item" href="#" onclick="changeView('changeView', 'listWeek'); return false;">{{$list_week}}</a></li>
+ <a class="dropdown-item" href="#" onclick="changeView('changeView', 'listDay'); return false;">{{$list_day}}</a></li>
+ </div>
+ <div class="btn-group">
+ <button class="btn btn-outline-secondary btn-sm" onclick="changeView('prev', false);" title="{{$prev}}"><i class="fa fa-backward"></i></button>
+ <button id="today-btn" class="btn btn-outline-secondary btn-sm" onclick="changeView('today', false);" title="{{$today}}"><div id="events-spinner" class="spinner s"></div><i class="fa fa-bullseye" style="display: none; width: 1rem;"></i></button>
+ <button class="btn btn-outline-secondary btn-sm" onclick="changeView('next', false);" title="{{$next}}"><i class="fa fa-forward"></i></button>
+ </div>
+ <button id="fullscreen-btn" type="button" class="btn btn-outline-secondary btn-sm" onclick="makeFullScreen();"><i class="fa fa-expand"></i></button>
+ <button id="inline-btn" type="button" class="btn btn-outline-secondary btn-sm" onclick="makeFullScreen(false);"><i class="fa fa-compress"></i></button>
+ </div>
+ </div>
+ <h2 id="title"></h2>
+ <div class="clear"></div>
+ </div>
+ <div class="section-content-tools-wrapper" style="display: none">
+ <div id="recurrence_warning" style="display: none">
+ <div class="section-content-warning-wrapper">
+ {{$recurrence_warning}}
+ </div>
+ <div>
+ <button id="event_delete_recurrent" type="button" class="btn btn-danger btn-sm">{{$delete_all}}</button>
+ <button id="event_cancel_recurrent" type="button" class="btn btn-outline-secondary btn-sm">{{$cancel}}</button>
+ </div>
+ </div>
+ <div id="event_form_wrapper" style="display: none">
+ <form id="event_form" method="post" action="">
+ <input id="event_uri" type="hidden" name="uri" value="">
+ {{include file="field_input.tpl" field=$title}}
+ <label for="calendar_select">{{$calendar_select_label}}</label>
+ <select id="calendar_select" name="target" class="form-control form-group">
+ {{foreach $writable_calendars as $writable_calendar}}
+ <option value="{{$writable_calendar.id.0}}:{{$writable_calendar.id.1}}">{{$writable_calendar.displayname}}{{if $writable_calendar.sharer}} ({{$writable_calendar.sharer}}){{/if}}</option>
+ {{/foreach}}
+ </select>
+ <div id="more_block" style="display: none;">
+ {{include file="field_input.tpl" field=$dtstart}}
+ {{include file="field_input.tpl" field=$dtend}}
+ {{include file="field_textarea.tpl" field=$description}}
+ {{include file="field_textarea.tpl" field=$location}}
+ </div>
+ <div class="form-group">
+ <div class="pull-right">
+ <button id="event_more" type="button" class="btn btn-outline-secondary btn-sm"><i class="fa fa-caret-down"></i> {{$more}}</button>
+ <button id="event_submit" type="button" value="" class="btn btn-primary btn-sm"></button>
+
+ </div>
+ <div>
+ <button id="event_delete" type="button" class="btn btn-danger btn-sm">{{$delete}}</button>
+ <button id="event_cancel" type="button" class="btn btn-outline-secondary btn-sm">{{$cancel}}</button>
+ </div>
+ <div class="clear"></div>
+ </div>
+ </form>
+ </div>
+ </div>
+ <div class="section-content-wrapper-np">
+ <div id="calendar"></div>
+ </div>
+</div>
diff --git a/view/tpl/cdav_widget_addressbook.tpl b/view/tpl/cdav_widget_addressbook.tpl
new file mode 100644
index 000000000..80b5feaf6
--- /dev/null
+++ b/view/tpl/cdav_widget_addressbook.tpl
@@ -0,0 +1,67 @@
+<div class="widget">
+ <h3>{{$addressbooks_label}}</h3>
+ {{foreach $addressbooks as $addressbook}}
+ <div id="addressbook-{{$addressbook.id}}" class="ml-3">
+ <div class="form-group">
+ <i class="fa fa-user generic-icons"></i><a href="/cdav/addressbook/{{$addressbook.id}}">{{$addressbook.displayname}}</a>
+ <div class="float-right">
+ <i id="edit-icon" class="fa fa-pencil fakelink generic-icons" onclick="openClose('edit-addressbook-{{$addressbook.id}}')"></i>
+ <a href="/cdav/addressbooks/{{$addressbook.ownernick}}/{{$addressbook.uri}}/?export"><i id="download-icon" class="fa fa-cloud-download fakelink generic-icons"></i></a>
+ <a href="#" onclick="dropItem('/cdav/addressbook/drop/{{$addressbook.id}}', '#addressbook-{{$addressbook.id}}'); return false;"><i class="fa fa-trash-o drop-icons"></i></a>
+ </div>
+ </div>
+ <div id="edit-addressbook-{{$addressbook.id}}" class="sub-menu" style="display: none;">
+ <form id="edit-addressbook-{{$addressbook.id}}" method="post" action="">
+ <label for="edit-{{$addressbook.id}}">{{$edit_label}}</label>
+ <div id="edit-form-{{$addressbook.id}}" class="form-group">
+ <input id="id-{{$addressbook.id}}" name="id" type="hidden" value="{{$addressbook.id}}">
+ <input id="edit-{{$addressbook.id}}" name="{DAV:}displayname" type="text" value="{{$addressbook.displayname}}" class="form-control">
+ </div>
+ <div class="form-group">
+ <button type="submit" name="edit" value="edit" class="btn btn-primary btn-sm">{{$edit}}</button>
+ </div>
+ </form>
+ </div>
+ </div>
+ {{/foreach}}
+</div>
+
+<div class="widget">
+ <h3>{{$tools_label}}</h3>
+ <ul class="nav nav-pills flex-column">
+ <li class="nav-item">
+ <a class="nav-link" href="#" onclick="openClose('create-addressbook'); return false;"><i class="fa fa-user-plus generic-icons"></i> {{$create_label}}</a>
+ </li>
+ <div id="create-addressbook" class="sub-menu-wrapper">
+ <div class="sub-menu">
+ <form method="post" action="">
+ <div class="form-group">
+ <input id="create" name="{DAV:}displayname" type="text" placeholder="{{$create_placeholder}}" class="form-control form-group">
+ <button type="submit" name="create" value="create" class="btn btn-primary btn-sm">{{$create}}</button>
+ </div>
+ </form>
+ </div>
+ </div>
+ <li class="nav-item">
+ <a class="nav-link" href="#" onclick="openClose('upload-form'); return false;"><i class="fa fa-cloud-upload generic-icons"></i> {{$import_label}}</a>
+ </li>
+ <div id="upload-form" class="sub-menu-wrapper">
+ <div class="sub-menu">
+ <form enctype="multipart/form-data" method="post" action="">
+ <div class="form-group">
+ <select id="import" name="target" class="form-control">
+ <option value="">{{$import_placeholder}}</option>
+ {{foreach $addressbooks as $addressbook}}
+ <option value="{{$addressbook.id}}">{{$addressbook.displayname}}</option>
+ {{/foreach}}
+ </select>
+ </div>
+ <div class="form-group">
+ <input class="form-control-file w-100" id="addressbook-upload-choose" type="file" name="userfile" />
+ </div>
+ <button class="btn btn-primary btn-sm" type="submit" name="a_upload" value="a_upload">{{$upload}}</button>
+ </form>
+ </div>
+ </div>
+ </ul>
+</div>
diff --git a/view/tpl/cdav_widget_calendar.tpl b/view/tpl/cdav_widget_calendar.tpl
new file mode 100644
index 000000000..ec2257a19
--- /dev/null
+++ b/view/tpl/cdav_widget_calendar.tpl
@@ -0,0 +1,121 @@
+{{if $my_calendars}}
+<div class="widget">
+ <h3>{{$my_calendars_label}}</h3>
+ {{foreach $my_calendars as $calendar}}
+ <div id="calendar-{{$calendar.calendarid}}">
+ <div class="ml-3{{if !$calendar@last}} form-group{{/if}}">
+ <i id="calendar-btn-{{$calendar.calendarid}}" class="fa {{if $calendar.switch}}fa-calendar-check-o{{else}}fa-calendar-o{{/if}} generic-icons fakelink" onclick="add_remove_json_source('{{$calendar.json_source}}', '{{$calendar.color}}', {{$calendar.editable}})" style="color: {{$calendar.color}};"></i>{{$calendar.displayname}}
+ <div class="float-right">
+ <i id="edit-icon" class="fa fa-pencil fakelink generic-icons" onclick="openClose('edit-calendar-{{$calendar.calendarid}}')"></i>
+ <a href="/cdav/calendars/{{$calendar.ownernick}}/{{$calendar.uri}}/?export"><i id="download-icon" class="fa fa-cloud-download fakelink generic-icons"></i></a>
+ <i id="share-icon" class="fa fa-share-alt fakelink generic-icons" onclick="openClose('share-calendar-{{$calendar.calendarid}}')"></i>
+ <a href="#" onclick="var drop = dropItem('/cdav/calendar/drop/{{$calendar.calendarid}}/{{$calendar.instanceid}}', '#calendar-{{$calendar.calendarid}}'); if(drop) { add_remove_json_source('{{$calendar.json_source}}', '{{$calendar.color}}', {{$calendar.editable}}, 'drop'); } return false;"><i class="fa fa-trash-o drop-icons"></i></a>
+ </div>
+ <div id="share-calendar-{{$calendar.calendarid}}" class="sub-menu" style="display: none; border-color: {{$calendar.color}};">
+ {{if $calendar.sharees}}
+ {{foreach $calendar.sharees as $sharee}}
+ <div id="sharee-{{$calendar.calendarid}}" class="form-group">
+ <i class="fa fa-share generic-icons"></i>{{$sharee.name}}&nbsp;{{$sharee.access}}
+ <div class="pull-right">
+ <a href="#" onclick="dropItem('/cdav/calendar/dropsharee/{{$calendar.calendarid}}/{{$calendar.instanceid}}/{{$sharee.hash}}', '#sharee-{{$calendar.calendarid}}'); return false;"><i class="fa fa-trash-o drop-icons"></i></a>
+ </div>
+ </div>
+ {{/foreach}}
+ {{/if}}
+ <form method="post" action="">
+ <label for="share-{{$calendar.calendarid}}">{{$share_label}}</label>
+ <input name="calendarid" type="hidden" value="{{$calendar.calendarid}}">
+ <input name="instanceid" type="hidden" value="{{$calendar.instanceid}}">
+ <div class="form-group">
+ <select id="share-{{$calendar.calendarid}}" name="sharee" class="form-control">
+ {{$sharee_options}}
+ </select>
+ </div>
+ <div class="form-group">
+ <select name="access" class="form-control">
+ {{$access_options}}
+ </select>
+ </div>
+ <div class="form-group">
+ <button type="submit" name="share" value="share" class="btn btn-primary btn-sm">{{$share}}</button>
+ </div>
+ </form>
+ </div>
+ <div id="edit-calendar-{{$calendar.calendarid}}" class="sub-menu" style="display: none; border-color: {{$calendar.color}};">
+ <form id="edit-calendar-{{$calendar.calendarid}}" method="post" action="" class="colorpicker-component color-edit">
+ <input id="id-{{$calendar.calendarid}}" name="id" type="hidden" value="{{$calendar.calendarid}}:{{$calendar.instanceid}}">
+ <input id="color-{{$calendar.calendarid}}" name="color" type="hidden" value="{{$calendar.color}}" class="color-edit-input">
+ <label for="edit-form-{{$calendar.calendarid}}">{{$edit_label}}</label>
+ <div id="edit-form-{{$calendar.calendarid}}" class="input-group form-group">
+ <input id="create-{{$calendar.calendarid}}" name="{DAV:}displayname" type="text" value="{{$calendar.displayname}}" class="form-control">
+ <span class="input-group-addon"><i></i></span>
+ </div>
+ <div class="form-group">
+ <button type="submit" name="edit" value="edit" class="btn btn-primary btn-sm">{{$edit}}</button>
+ </div>
+ </form>
+ </div>
+ </div>
+ </div>
+ {{/foreach}}
+</div>
+{{/if}}
+
+{{if $shared_calendars}}
+<div class="widget">
+ <h3>{{$shared_calendars_label}}</h3>
+ {{foreach $shared_calendars as $calendar}}
+ <div id="shared-calendar-{{$calendar.calendarid}}" class="ml-3{{if !$calendar@last}} form-group{{/if}}">
+ <i id="calendar-btn-{{$calendar.calendarid}}" class="fa {{if $calendar.switch}}{{if $calendar.access == 'read-write'}}fa-calendar-check-o{{else}}fa-calendar-times-o{{/if}}{{else}}fa-calendar-o{{/if}} generic-icons fakelink" onclick="add_remove_json_source('{{$calendar.json_source}}', '{{$calendar.color}}', {{$calendar.editable}}, {{if $calendar.access == 'read-write'}}'fa-calendar-check-o'{{else}}'fa-calendar-times-o'{{/if}})" style="color: {{$calendar.color}};"></i>{{$calendar.displayname}} ({{$calendar.sharer}})
+ <div class="pull-right">
+ <a href="/cdav/calendars/{{$calendar.ownernick}}/{{$calendar.uri}}/?export"><i id="download-icon" class="fa fa-cloud-download fakelink generic-icons"></i></a>
+ <a href="#" onclick="var drop = dropItem('/cdav/calendar/drop/{{$calendar.calendarid}}/{{$calendar.instanceid}}', '#shared-calendar-{{$calendar.calendarid}}'); if(drop) { add_remove_json_source('{{$calendar.json_source}}', '{{$calendar.color}}', {{$calendar.editable}}, 'drop'); } return false;"><i class="fa fa-trash-o drop-icons"></i></a>
+ </div>
+ </div>
+ {{/foreach}}
+</div>
+{{/if}}
+
+<div class="widget">
+ <h3>{{$tools_label}}</h3>
+ <div class="nav nav-pills flex-column">
+ <li class="nav-item">
+ <a class="nav-link" href="#" onclick="openClose('create-calendar'); return false;"><i class="fa fa-calendar-plus-o generic-icons"></i> {{$create_label}}</a>
+ </li>
+ <div id="create-calendar" class="sub-menu-wrapper">
+ <div class="sub-menu">
+ <form method="post" action="" class="colorpicker-component color-edit">
+ <input id="color" name="color" type="hidden" value="#3a87ad" class="color-edit-input">
+ <div id="create-form" class="input-group form-group">
+ <input id="create" name="{DAV:}displayname" type="text" placeholder="{{$create_placeholder}}" class="form-control">
+ <span class="input-group-addon"><i></i></span>
+ </div>
+ <div class="form-group">
+ <button type="submit" name="create" value="create" class="btn btn-primary btn-sm">{{$create}}</button>
+ </div>
+ </form>
+ </div>
+ </div>
+ <li class="nav-item">
+ <a class="nav-link" href="#" onclick="openClose('upload-form'); return false;"><i class="fa fa-cloud-upload generic-icons"></i> {{$import_label}}</a>
+ </li>
+ <div id="upload-form" class="sub-menu-wrapper">
+ <div class="sub-menu">
+ <form enctype="multipart/form-data" method="post" action="">
+ <div class="form-group">
+ <select id="import" name="target" class="form-control">
+ <option value="">{{$import_placeholder}}</option>
+ {{foreach $writable_calendars as $writable_calendar}}
+ <option value="{{$writable_calendar.id.0}}:{{$writable_calendar.id.1}}">{{$writable_calendar.displayname}}</option>
+ {{/foreach}}
+ </select>
+ </div>
+ <div class="form-group">
+ <input class="form-control-file w-100" id="event-upload-choose" type="file" name="userfile" />
+ </div>
+ <button class="btn btn-primary btn-sm" type="submit" name="c_upload" value="c_upload">{{$upload}}</button>
+ </form>
+ </div>
+ </div>
+ </div>
+</div>
diff --git a/view/tpl/channel.tpl b/view/tpl/channel.tpl
index 1a84f1e66..63e09ec05 100755
--- a/view/tpl/channel.tpl
+++ b/view/tpl/channel.tpl
@@ -17,7 +17,7 @@
</div>
<h3>
{{if $selected == $channel.channel_id}}
- <i class="selected-channel fa fa-circle" title="{{$msg_selected}}"></i>
+ <i class="fa fa-circle text-success" title="{{$msg_selected}}"></i>
{{/if}}
{{if $channel.delegate}}
<i class="fa fa-arrow-circle-right" title="{{$delegated_desc}}"></i>
@@ -37,11 +37,11 @@
<div class="channel-notifications-wrapper">
{{if !$channel.delegate}}
<div class="channel-notification">
- <i class="fa fa-envelope{{if $channel.mail != 0}} new-notification{{/if}}"></i>
+ <i class="fa fa-fw fa-envelope{{if $channel.mail != 0}} text-danger{{/if}}"></i>
{{if $channel.mail != 0}}<a href="manage/{{$channel.channel_id}}/mail/combined">{{/if}}{{$channel.mail|string_format:$mail_format}}{{if $channel.mail != 0}}</a>{{/if}}
</div>
<div class="channel-notification">
- <i class="fa fa-user{{if $channel.intros != 0}} new-notification{{/if}}"></i>
+ <i class="fa fa-fw fa-user{{if $channel.intros != 0}} text-danger{{/if}}"></i>
{{if $channel.intros != 0}}<a href='manage/{{$channel.channel_id}}/connections/ifpending'>{{/if}}{{$channel.intros|string_format:$intros_format}}{{if $channel.intros != 0}}</a>{{/if}}
</div>
{{/if}}
diff --git a/view/tpl/channel_import.tpl b/view/tpl/channel_import.tpl
index 2028d6181..baffe9b06 100755
--- a/view/tpl/channel_import.tpl
+++ b/view/tpl/channel_import.tpl
@@ -1,7 +1,7 @@
<h2>{{$title}}</h2>
<form action="import" method="post" enctype="multipart/form-data" id="import-channel-form">
-
+ <input type="hidden" name="form_security_token" value="{{$form_security_token}}">
<div id="import-desc" class="descriptive-paragraph">{{$desc}}</div>
<label for="import-filename" id="label-import-filename" class="import-label" >{{$label_filename}}</label>
@@ -40,7 +40,4 @@
<div id="import-submit-end" class="import-field-end"></div>
<div id="import-common-desc" class="descriptive-paragraph">{{$pleasewait}}</div>
-
-
</form>
-
diff --git a/view/tpl/channel_rename.tpl b/view/tpl/channel_rename.tpl
new file mode 100755
index 000000000..9948dc647
--- /dev/null
+++ b/view/tpl/channel_rename.tpl
@@ -0,0 +1,20 @@
+<div class="generic-content-wrapper">
+ <div class="section-title-wrapper">
+ <h2>{{$title}}</h2>
+ </div>
+ <div class="section-content-danger-wrapper" id="rename-channel-desc">
+ <strong>{{$desc.0}}</strong><strong>{{$desc.1}}</strong>
+ </div>
+ <div class="section-content-tools-wrapper">
+ <form action="{{$basedir}}/changeaddr" autocomplete="off" method="post" >
+ <input type="hidden" name="verify" value="{{$hash}}" />
+ <div class="form-group" id="rename-channel-pass-wrapper">
+ <label id="rename-channel-pass-label" for="rename-channel-pass">{{$passwd}}</label>
+ <input class="form-control" type="password" id="rename-channel-pass" autocomplete="off" name="qxz_password" value=" " />
+ </div>
+ {{include file="field_input.tpl" field=$newname}}
+ <button type="submit" name="submit" class="btn btn-danger">{{$submit}}</button>
+ </form>
+ </div>
+</div>
+
diff --git a/view/tpl/channels.tpl b/view/tpl/channels.tpl
index 171f833ee..f484b49e5 100755
--- a/view/tpl/channels.tpl
+++ b/view/tpl/channels.tpl
@@ -1,6 +1,6 @@
<div class="generic-content-wrapper">
<div class="section-title-wrapper">
- <a class="btn btn-success btn-xs pull-right" href="{{$create.0}}" title="{{$create.1}}"><i class="fa fa-plus-circle"></i>&nbsp;{{$create.2}}</a>
+ <a class="btn btn-success btn-sm pull-right" href="{{$create.0}}" title="{{$create.1}}"><i class="fa fa-plus-circle"></i>&nbsp;{{$create.2}}</a>
<h2>{{$header}}</h2>
</div>
<div class="section-content-wrapper-np">
diff --git a/view/tpl/chat.tpl b/view/tpl/chat.tpl
index 31be4136f..c189cbd15 100644
--- a/view/tpl/chat.tpl
+++ b/view/tpl/chat.tpl
@@ -5,17 +5,20 @@
<form id="chat-destroy" method="post" action="chat">
<input type="hidden" name="room_name" value="{{$room_name}}" />
<input type="hidden" name="action" value="drop" />
- <button class="btn btn-danger btn-xs" type="submit" name="submit" value="{{$drop}}" onclick="return confirmDelete();"><i class="fa fa-trash-o"></i>&nbsp;{{$drop}}</button>
+ <button class="btn btn-danger btn-sm" type="submit" name="submit" value="{{$drop}}" onclick="return confirmDelete();"><i class="fa fa-trash-o"></i>&nbsp;{{$drop}}</button>
</form>
{{/if}}
- <button id="fullscreen-btn" type="button" class="btn btn-default btn-xs" onclick="makeFullScreen(); adjustFullscreenTopBarHeight();"><i class="fa fa-expand"></i></button>
- <button id="inline-btn" type="button" class="btn btn-default btn-xs" onclick="makeFullScreen(false); adjustInlineTopBarHeight();"><i class="fa fa-compress"></i></button>
+ <button id="fullscreen-btn" type="button" class="btn btn-outline-secondary btn-sm" onclick="makeFullScreen(); adjustFullscreenTopBarHeight();"><i class="fa fa-expand"></i></button>
+ <button id="inline-btn" type="button" class="btn btn-outline-secondary btn-sm" onclick="makeFullScreen(false); adjustInlineTopBarHeight();"><i class="fa fa-compress"></i></button>
</div>
<h2>{{$room_name}}</h2>
<div class="clear"></div>
</div>
<div id="chatContainer" class="section-content-wrapper">
<div id="chatTopBar">
+ <div id="chat-top-spinner" class="spinner-wrapper">
+ <div class="spinner m"></div>
+ </div>
<div id="chatLineHolder"></div>
</div>
<div class="clear"></div>
@@ -25,70 +28,71 @@
<div class="form-group">
<textarea id="chatText" name="chat_text" class="form-control"></textarea>
</div>
- <div id="chat-submit-wrapper">
+ <div id="chat-submit-wrapper" class="clearfix">
<div id="chat-submit" class="dropup pull-right">
- <button class="btn btn-default btn-sm dropdown-toggle" type="button" data-toggle="dropdown"><i class="fa fa-caret-up"></i></button>
+ <button class="btn btn-outline-secondary btn-sm dropdown-toggle" type="button" data-toggle="dropdown"><i class="fa fa-cog"></i></button>
<button class="btn btn-primary btn-sm" type="submit" id="chat-submit" name="submit" value="{{$submit}}">{{$submit}}</button>
- <ul class="dropdown-menu">
- <li class="nav-item"><a class="nav-link" href="{{$baseurl}}/chatsvc?f=&room_id={{$room_id}}&status=online"><i class="fa fa-circle online"></i>&nbsp;{{$online}}</a></li>
- <li class="nav-item"><a class="nav-link" href="{{$baseurl}}/chatsvc?f=&room_id={{$room_id}}&status=away"><i class="fa fa-circle away"></i>&nbsp;{{$away}}</a></li>
- <li class="nav-item"><a class="nav-link" href="{{$baseurl}}/chat/{{$nickname}}/{{$room_id}}/leave"><i class="fa fa-circle leave"></i>&nbsp;{{$leave}}</a></li>
- <li class="divider"></li>
- <li class="nav-item" id="toggle-notifications"><a class="nav-link" href="" onclick="toggleChatNotifications(); return false;"><i id="toggle-notifications-icon" class="fa fa-bell-slash-o"></i>&nbsp;Toggle notifications</a></li>
- <li class="nav-item disabled" id="toggle-notifications-audio"><a class="nav-link" href="" onclick="toggleChatNotificationAudio(); return false;"><i id="toggle-notifications-audio-icon" class="fa fa-volume-off"></i>&nbsp;Toggle sound</a></li>
+ <div class="dropdown-menu dropdown-menu-right">
+ <a class="dropdown-item" href="{{$baseurl}}/chatsvc?f=&room_id={{$room_id}}&status=online"><i class="fa fa-circle online"></i>&nbsp;{{$online}}</a>
+ <a class="dropdown-item" href="{{$baseurl}}/chatsvc?f=&room_id={{$room_id}}&status=away"><i class="fa fa-circle away"></i>&nbsp;{{$away}}</a>
+ <a class="dropdown-item" href="{{$baseurl}}/chat/{{$nickname}}/{{$room_id}}/leave"><i class="fa fa-circle leave"></i>&nbsp;{{$leave}}</a>
+ <div class="dropdown-divider"></div>
+ <a id="toggle-notifications" class="dropdown-item" href="" onclick="toggleChatNotifications(); return false;"><i id="toggle-notifications-icon" class="fa fa-bell-slash-o"></i>&nbsp;Toggle notifications</a>
+ <a id="toggle-notifications-audio" class="dropdown-item disabled" href="" onclick="toggleChatNotificationAudio(); return false;"><i id="toggle-notifications-audio-icon" class="fa fa-volume-off"></i>&nbsp;Toggle sound</a>
{{if $bookmark_link}}
- <li class="divider"></li>
- <li class="nav-item"><a class="nav-link" href="{{$bookmark_link}}" target="_blank" ><i class="fa fa-bookmark"></i>&nbsp;{{$bookmark}}</a></li>
+ <div class="dropdown-divider"></div>
+ <a class="dropdown-item" href="{{$bookmark_link}}" target="_blank" ><i class="fa fa-bookmark"></i>&nbsp;{{$bookmark}}</a>
{{/if}}
- </ul>
+ </div>
</div>
- <div id="chat-tools" class="btn-toolbar pull-left">
- <div class="btn-group">
- <button id="main-editor-bold" class="btn btn-default btn-sm" title="{{$bold}}" onclick="inserteditortag('b', 'chatText'); return false;">
+ <div id="chat-tools" class="btn-toolbar">
+ <div class="btn-group mr-2">
+ <button id="main-editor-bold" class="btn btn-outline-secondary btn-sm" title="{{$bold}}" onclick="inserteditortag('b', 'chatText'); return false;">
<i class="fa fa-bold jot-icons"></i>
</button>
- <button id="main-editor-italic" class="btn btn-default btn-sm" title="{{$italic}}" onclick="inserteditortag('i', 'chatText'); return false;">
+ <button id="main-editor-italic" class="btn btn-outline-secondary btn-sm" title="{{$italic}}" onclick="inserteditortag('i', 'chatText'); return false;">
<i class="fa fa-italic jot-icons"></i>
</button>
- <button id="main-editor-underline" class="btn btn-default btn-sm" title="{{$underline}}" onclick="inserteditortag('u', 'chatText'); return false;">
+ <button id="main-editor-underline" class="btn btn-outline-secondary btn-sm" title="{{$underline}}" onclick="inserteditortag('u', 'chatText'); return false;">
<i class="fa fa-underline jot-icons"></i>
</button>
- <button id="main-editor-quote" class="btn btn-default btn-sm" title="{{$quote}}" onclick="inserteditortag('quote', 'chatText'); return false;">
+ <button id="main-editor-quote" class="btn btn-outline-secondary btn-sm" title="{{$quote}}" onclick="inserteditortag('quote', 'chatText'); return false;">
<i class="fa fa-quote-left jot-icons"></i>
</button>
- <button id="main-editor-code" class="btn btn-default btn-sm" title="{{$code}}" onclick="inserteditortag('code', 'chatText'); return false;">
+ <button id="main-editor-code" class="btn btn-outline-secondary btn-sm" title="{{$code}}" onclick="inserteditortag('code', 'chatText'); return false;">
<i class="fa fa-terminal jot-icons"></i>
</button>
</div>
- <div class="btn-group hidden-xs">
- <button id="chat-link-wrapper" class="btn btn-default btn-sm" onclick="chatJotGetLink(); return false;" >
+ <div class="btn-group mr-2 d-none d-md-flex">
+ <button id="chat-link-wrapper" class="btn btn-outline-secondary btn-sm" onclick="chatJotGetLink(); return false;" >
<i id="chat-link" class="fa fa-link jot-icons" title="{{$insert}}" ></i>
</button>
</div>
{{if $feature_encrypt}}
- <div class="btn-group hidden-xs">
- <button id="chat-encrypt-wrapper" class="btn btn-default btn-sm" onclick="red_encrypt('{{$cipher}}', '#chatText', $('#chatText').val()); return false;">
+ <div class="btn-group mr-2 d-none d-md-flex">
+ <button id="chat-encrypt-wrapper" class="btn btn-outline-secondary btn-sm" onclick="red_encrypt('{{$cipher}}', '#chatText', $('#chatText').val()); return false;">
<i id="chat-encrypt" class="fa fa-key jot-icons" title="{{$encrypt}}" ></i>
</button>
</div>
{{/if}}
- <div class="btn-group dropup visible-xs">
- <button type="button" id="more-tools" class="btn btn-default btn-sm dropdown-toggle" data-toggle="dropdown" aria-expanded="false">
- <i id="more-tools-icon" class="fa fa-caret-up jot-icons"></i>
+ <div class="btn-group dropup d-md-none">
+ <button type="button" id="more-tools" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown" aria-expanded="false">
+ <i id="more-tools-icon" class="fa fa-cog jot-icons"></i>
</button>
- <ul class="dropdown-menu dropdown-menu-right" role="menu">
- <li class="visible-xs"><a href="#" onclick="chatJotGetLink(); return false;" ><i class="fa fa-link"></i>&nbsp;{{$insert}}</a></li>
+ <div class="dropdown-menu">
+ <a class="dropdown-item" href="#" onclick="chatJotGetLink(); return false;" ><i class="fa fa-link"></i>&nbsp;{{$insert}}</a>
{{if $feature_encrypt}}
- <li class="divider"></li>
- <li class="visible-xs"><a href="#" onclick="red_encrypt('{{$cipher}}', '#chatText' ,$('#chatText').val()); return false;"><i class="fa fa-key"></i>&nbsp;{{$encrypt}}</a></li>
+ <div class="dropdown-divider"></div>
+ <a class="dropdown-item" href="#" onclick="red_encrypt('{{$cipher}}', '#chatText' ,$('#chatText').val()); return false;"><i class="fa fa-key"></i>&nbsp;{{$encrypt}}</a>
{{/if}}
- </ul>
+ </div>
+ </div>
+ <div class="btn-group">
+ <div id="chat-rotator" class="mt-2 spinner-wrapper">
+ <div class="spinner s"></div>
+ </div>
</div>
</div>
- <div id="chat-rotator-wrapper" class="pull-left">
- <div id="chat-rotator"></div>
- </div>
- <div class="clear"></div>
</div>
</form>
</div>
@@ -101,7 +105,7 @@ var last_chat = 0;
var chat_timer = null;
$(document).ready(function() {
- $('#chatTopBar').spin('small');
+ $('#chat-top-spinner').show();
chat_timer = setTimeout(load_chats,300);
$('#chatroom_bookmarks, #vcard').hide();
$('#chatroom_list, #chatroom_members').show();
@@ -134,7 +138,7 @@ function load_chats() {
if(data.success && (! stopped)) {
update_inroom(data.inroom);
update_chats(data.chats);
- $('#chatTopBar').spin(false);
+ $('#chat-top-spinner').hide();
}
});
@@ -150,7 +154,7 @@ function update_inroom(inroom) {
$.each( inroom, function(index, item) {
var newNode = document.createElement('div');
newNode.setAttribute('class', 'member-item');
- $(newNode).html('<img style="height: 32px; width: 32px;" src="' + item.img + '" alt="' + item.name + '" /> ' + '<span class="name">' + item.name + '</span><br /><span class="' + item.status_class + '">' + item.status + '</span>');
+ $(newNode).html('<img class="menu-img-2" src="' + item.img + '" alt="' + item.name + '" /> ' + '<span class="contactname">' + item.name + '</span><span class="' + item.status_class + '">' + item.status + '</span>');
html.appendChild(newNode);
});
memberChange = chatRoomMembersChange(inroom); // get list of arrivals and departures
@@ -293,10 +297,10 @@ function toggleChatNotifications() {
function chatJotGetLink() {
reply = prompt("{{$linkurl}}");
if(reply && reply.length) {
- $('#chat-rotator').spin('tiny');
+ $('#chat-rotator').show();
$.get('linkinfo?f=&url=' + reply, function(data) {
addmailtext(data);
- $('#chat-rotator').spin(false);
+ $('#chat-rotator').hide();
});
}
}
diff --git a/view/tpl/chatroom_new.tpl b/view/tpl/chatroom_new.tpl
index 1b7e0501a..1497939f6 100644
--- a/view/tpl/chatroom_new.tpl
+++ b/view/tpl/chatroom_new.tpl
@@ -3,7 +3,7 @@
{{include file="field_input.tpl" field=$name}}
{{include file="field_input.tpl" field=$chat_expire}}
<div class="btn-group pull-right">
- <button id="dbtn-acl" class="btn btn-default" data-toggle="modal" data-target="#aclModal" title="{{$permissions}}" onclick="return false;" ><i id="jot-perms-icon" class="fa fa-{{$lockstate}}"></i></button>
+ <button id="dbtn-acl" class="btn btn-outline-secondary" data-toggle="modal" data-target="#aclModal" title="{{$permissions}}" onclick="return false;" ><i id="jot-perms-icon" class="fa fa-{{$lockstate}}"></i></button>
<button id="dbtn-submit" class="acl-submit btn btn-primary" type="submit" name="submit" value="{{$submit}}" data-formid="chatroom-new-form">{{$submit}}</button>
</div>
<div class="clear"></div>
diff --git a/view/tpl/chatroomlist.tpl b/view/tpl/chatroomlist.tpl
index ff4b79a4b..a81b8ec1e 100644
--- a/view/tpl/chatroomlist.tpl
+++ b/view/tpl/chatroomlist.tpl
@@ -1,9 +1,9 @@
<div id="chatroom_list" class="widget">
<h3>{{$header}}</h3>
- <ul class="nav nav-pills nav-stacked">
- <li><a href="{{$baseurl}}/chat/{{$nickname}}">{{$overview}}</a></li>
+ <ul class="nav nav-pills flex-column">
+ <li class="nav-item"><a class="nav-link" href="{{$baseurl}}/chat/{{$nickname}}">{{$overview}}</a></li>
{{foreach $items as $item}}
- <li><a href="{{$baseurl}}/chat/{{$nickname}}/{{$item.cr_id}}"><span class="badge pull-right">{{$item.cr_inroom}}</span>{{$item.cr_name}}</a></li>
+ <li class="nav-item"><a class="nav-link" href="{{$baseurl}}/chat/{{$nickname}}/{{$item.cr_id}}"><span class="badge pull-right">{{$item.cr_inroom}}</span>{{$item.cr_name}}</a></li>
{{/foreach}}
</ul>
</div>
diff --git a/view/tpl/chatrooms.tpl b/view/tpl/chatrooms.tpl
index 64f6e8d0f..0e6847608 100644
--- a/view/tpl/chatrooms.tpl
+++ b/view/tpl/chatrooms.tpl
@@ -1,7 +1,7 @@
<div class="generic-content-wrapper">
- <div class="section-title-wrapper">
+ <div class="section-title-wrapper clearfix">
{{if $is_owner}}
- <button type="button" class="btn btn-success btn-xs pull-right acl-form-trigger" onclick="openClose('chatroom-new');" data-form_id="chatroom-new-form"><i class="fa fa-plus-circle"></i>&nbsp;{{$newroom}}</button>
+ <button type="button" class="btn btn-success btn-sm pull-right acl-form-trigger" onclick="openClose('chatroom-new');" data-form_id="chatroom-new-form"><i class="fa fa-plus-circle"></i>&nbsp;{{$newroom}}</button>
{{/if}}
<h2>{{$header}}</h2>
</div>
@@ -21,13 +21,13 @@
<tr class="chatroom-index-row">
<td><a href="{{$baseurl}}/chat/{{$nickname}}/{{$room.cr_id}}">{{$room.cr_name}}</a></td>
<td>{{$room.cr_expire}}&nbsp;min</td>
- <td class="chatrooms-index-tool{{if $room.allow_cid || $room.allow_gid || $room.deny_cid || $room.deny_gid}} dropdown pull-right{{/if}}">
+ <td class="chatrooms-index-tool{{if $room.allow_cid || $room.allow_gid || $room.deny_cid || $room.deny_gid}} dropdown float-right{{/if}}">
{{if $room.allow_cid || $room.allow_gid || $room.deny_cid || $room.deny_gid}}
- <i class="fa fa-lock lockview dropdown-toggle" data-toggle="dropdown" onclick="lockview('chatroom',{{$room.cr_id}});"></i>
+ <i class="fa fa-lock lockview" data-toggle="dropdown" onclick="lockview('chatroom',{{$room.cr_id}});"></i>
<ul id="panel-{{$room.cr_id}}" class="lockview-panel dropdown-menu"></ul>
{{/if}}
</td>
- <td><span class="badge">{{$room.cr_inroom}}</span></td>
+ <td><span class="badge badge-secondary">{{$room.cr_inroom}}</span></td>
</tr>
{{/foreach}}
</table>
diff --git a/view/tpl/cloud_actionspanel.tpl b/view/tpl/cloud_actionspanel.tpl
index 36edc3b44..baee48da3 100644
--- a/view/tpl/cloud_actionspanel.tpl
+++ b/view/tpl/cloud_actionspanel.tpl
@@ -8,7 +8,7 @@
<div class="pull-right btn-group">
<div class="btn-group">
{{if $lockstate}}
- <button class="btn btn-default btn-sm" data-toggle="modal" data-target="#aclModal" type="button">
+ <button class="btn btn-outline-secondary btn-sm" data-toggle="modal" data-target="#aclModal" type="button">
<i class="jot-perms-icon fa fa-{{$lockstate}}"></i>
</button>
{{/if}}
@@ -19,17 +19,18 @@
<div class="clear"></div>
</div>
<div id="files-upload-tools" class="section-content-tools-wrapper">
- {{if $quota.limit || $quota.used}}<div class="{{if $quota.warning}}section-content-danger-wrapper{{else}}section-content-info-wrapper{{/if}}">{{if $quota.warning}}<strong>{{$quota.warning}} </strong>{{/if}}{{$quota.desc}}</div>{{/if}}
+ {{if $quota.limit || $quota.used}}<div class="{{if $quota.warning}}section-content-danger-wrapper{{else}}section-content-info-wrapper{{/if}}">{{if $quota.warning}}<strong>{{$quota.warning}} </strong>{{/if}}{{if $quota.desc}}{{$quota.desc}}<br><br>{{/if}}{{$info}}</div>{{/if}}
<form id="ajax-upload-files" method="post" action="file_upload" enctype="multipart/form-data" class="acl-form" data-form_id="ajax-upload-files" data-allow_cid='{{$allow_cid}}' data-allow_gid='{{$allow_gid}}' data-deny_cid='{{$deny_cid}}' data-deny_gid='{{$deny_gid}}'>
<input type="hidden" name="directory" value="{{$path}}" />
<input type="hidden" name="channick" value="{{$channick}}" />
<input type="hidden" name="return_url" value="{{$return_url}}" />
<label for="files-upload">{{$upload_header}}</label>
<input class="form-group pull-left" id="files-upload" type="file" name="userfile">
+ {{**include file="field_checkbox.tpl" field=$notify**}}
<div class="pull-right btn-group">
<div class="btn-group">
{{if $lockstate}}
- <button class="btn btn-default btn-sm" data-toggle="modal" data-target="#aclModal" type="button">
+ <button class="btn btn-outline-secondary btn-sm" data-toggle="modal" data-target="#aclModal" type="button">
<i class="jot-perms-icon fa fa-{{$lockstate}}"></i>
</button>
{{/if}}
diff --git a/view/tpl/cloud_directory.tpl b/view/tpl/cloud_directory.tpl
index 5a84028c1..e8ae6a590 100644
--- a/view/tpl/cloud_directory.tpl
+++ b/view/tpl/cloud_directory.tpl
@@ -5,8 +5,8 @@
<th width="92%">{{$name}}</th>
<th width="1%"></th><th width="1%"></th><th width="1%"></th><th width="1%"></th>
<th width="1%">{{*{{$type}}*}}</th>
- <th width="1%" class="hidden-xs">{{$size}}</th>
- <th width="1%" class="hidden-xs">{{$lastmod}}</th>
+ <th width="1%" class="d-none d-md-table-cell">{{$size}}</th>
+ <th width="1%" class="d-none d-md-table-cell">{{$lastmod}}</th>
</tr>
{{if $parentpath}}
<tr>
@@ -14,8 +14,8 @@
<td><a href="{{$parentpath.path}}" title="{{$parent}}">..</a></td>
<td></td><td></td><td></td><td></td>
<td>{{*[{{$parent}}]*}}</td>
- <td class="hidden-xs"></td>
- <td class="hidden-xs"></td>
+ <td class="d-none d-md-table-cell"></td>
+ <td class="d-none d-md-table-cell"></td>
</tr>
{{/if}}
<tr id="new-upload-progress-bar--1"></tr> {{* this is needed to append the upload files in the right order *}}
@@ -25,7 +25,7 @@
<td><a href="{{$item.fullPath}}">{{$item.displayName}}</a></td>
{{if $item.is_owner}}
<td class="cloud-index-tool">{{$item.attachIcon}}</td>
- <td id="file-edit-{{$item.attachId}}" class="cloud-index-tool"></td>
+ <td class="cloud-index-tool"><div id="file-edit-{{$item.attachId}}" class="spinner-wrapper"><div class="spinner s"></div></div></td>
<td class="cloud-index-tool"><i class="fakelink fa fa-pencil" onclick="filestorage(event, '{{$nick}}', {{$item.attachId}});"></i></td>
<td class="cloud-index-tool"><a href="#" title="{{$delete}}" onclick="dropItem('{{$item.fileStorageUrl}}/{{$item.attachId}}/delete', '#cloud-index-{{$item.attachId}},#cloud-tools-{{$item.attachId}}'); return false;"><i class="fa fa-trash-o drop-icons"></i></a></td>
@@ -33,8 +33,8 @@
<td></td><td></td><td></td><td></td>
{{/if}}
<td>{{*{{$item.type}}*}}</td>
- <td class="hidden-xs">{{$item.sizeFormatted}}</td>
- <td class="hidden-xs">{{$item.lastmodified}}</td>
+ <td class="d-none d-md-table-cell">{{$item.sizeFormatted}}</td>
+ <td class="d-none d-md-table-cell">{{$item.lastmodified}}</td>
</tr>
<tr id="cloud-tools-{{$item.attachId}}">
<td id="perms-panel-{{$item.attachId}}" colspan="9"></td>
diff --git a/view/tpl/cloud_header.tpl b/view/tpl/cloud_header.tpl
index d41cc9d67..c1e589341 100644
--- a/view/tpl/cloud_header.tpl
+++ b/view/tpl/cloud_header.tpl
@@ -2,10 +2,10 @@
{{if $actionspanel}}
<div class="pull-right">
{{if $is_owner}}
- <a href="/sharedwithme" class="btn btn-xs btn-default"><i class="fa fa-cloud-download"></i>&nbsp;{{$shared}}</a>
+ <a href="/sharedwithme" class="btn btn-sm btn-outline-secondary"><i class="fa fa-cloud-download"></i>&nbsp;{{$shared}}</a>
{{/if}}
- <button id="files-create-btn" class="btn btn-xs btn-primary" onclick="openClose('files-mkdir-tools'); closeMenu('files-upload-tools');"><i class="fa fa-folder-o"></i>&nbsp;{{$create}}</button>
- <button id="files-upload-btn" class="btn btn-xs btn-success" onclick="openClose('files-upload-tools'); closeMenu('files-mkdir-tools');"><i class="fa fa-arrow-circle-o-up"></i>&nbsp;{{$upload}}</button>
+ <button id="files-create-btn" class="btn btn-sm btn-primary" onclick="openClose('files-mkdir-tools'); closeMenu('files-upload-tools');"><i class="fa fa-folder-o"></i>&nbsp;{{$create}}</button>
+ <button id="files-upload-btn" class="btn btn-sm btn-success" onclick="openClose('files-upload-tools'); closeMenu('files-mkdir-tools');"><i class="fa fa-arrow-circle-o-up"></i>&nbsp;{{$upload}}</button>
</div>
{{/if}}
<h2>{{$header}}</h2>
diff --git a/view/tpl/comment_item.tpl b/view/tpl/comment_item.tpl
index a98b9e5eb..62530c1de 100755
--- a/view/tpl/comment_item.tpl
+++ b/view/tpl/comment_item.tpl
@@ -10,7 +10,15 @@
<input type="hidden" name="return" value="{{$return_path}}" />
<input type="hidden" name="jsreload" value="{{$jsreload}}" />
<input type="hidden" name="preview" id="comment-preview-inp-{{$id}}" value="0" />
- <textarea id="comment-edit-text-{{$id}}" class="comment-edit-text-empty" name="body" onFocus="commentOpenUI(this,{{$id}});" onBlur="commentCloseUI(this,{{$id}});" ondragenter="linkdropper(event);" ondragleave="linkdropexit(event);" ondragover="linkdropper(event);" ondrop="linkdrop(event);" >{{$comment}}</textarea>
+ {{if $anoncomments && ! $observer}}
+ <div id="comment-edit-anon-{{$id}}" style="display: none;" >
+ {{include file="field_input.tpl" field=$anonname}}
+ {{include file="field_input.tpl" field=$anonmail}}
+ {{include file="field_input.tpl" field=$anonurl}}
+ {{$anon_extras}}
+ </div>
+ {{/if}}
+ <textarea id="comment-edit-text-{{$id}}" class="comment-edit-text" placeholder="{{$comment}}" name="body" ondragenter="linkdropper(event);" ondragleave="linkdropexit(event);" ondragover="linkdropper(event);" ondrop="linkdrop(event);" ></textarea>
{{if $qcomment}}
<select id="qcomment-select-{{$id}}" name="qcomment-{{$id}}" class="qcomment" onchange="qCommentInsert(this,{{$id}});" >
<option value=""></option>
@@ -19,56 +27,54 @@
{{/foreach}}
</select>
{{/if}}
- <div class="clear"></div>
- <div id="comment-tools-{{$id}}" class="comment-tools">
+ <div id="comment-tools-{{$id}}" class="pt-2 comment-tools">
<div id="comment-edit-bb-{{$id}}" class="btn-toolbar pull-left">
- <div class='btn-group'>
- <button class="btn btn-default btn-xs" title="{{$edbold}}" onclick="insertbbcomment('{{$comment}}','b', {{$id}}); return false;">
+ <div class="btn-group mr-2">
+ <button class="btn btn-outline-secondary btn-sm" title="{{$edbold}}" onclick="insertbbcomment('{{$comment}}','b', {{$id}}); return false;">
<i class="fa fa-bold comment-icon"></i>
</button>
- <button class="btn btn-default btn-xs" title="{{$editalic}}" onclick="insertbbcomment('{{$comment}}','i', {{$id}}); return false;">
+ <button class="btn btn-outline-secondary btn-sm" title="{{$editalic}}" onclick="insertbbcomment('{{$comment}}','i', {{$id}}); return false;">
<i class="fa fa-italic comment-icon"></i>
</button>
- <button class="btn btn-default btn-xs" title="{{$eduline}}" onclick="insertbbcomment('{{$comment}}','u', {{$id}}); return false;">
+ <button class="btn btn-outline-secondary btn-sm" title="{{$eduline}}" onclick="insertbbcomment('{{$comment}}','u', {{$id}}); return false;">
<i class="fa fa-underline comment-icon"></i>
</button>
- <button class="btn btn-default btn-xs" title="{{$edquote}}" onclick="insertbbcomment('{{$comment}}','quote', {{$id}}); return false;">
+ <button class="btn btn-outline-secondary btn-sm" title="{{$edquote}}" onclick="insertbbcomment('{{$comment}}','quote', {{$id}}); return false;">
<i class="fa fa-quote-left comment-icon"></i>
</button>
- <button class="btn btn-default btn-xs" title="{{$edcode}}" onclick="insertbbcomment('{{$comment}}','code', {{$id}}); return false;">
+ <button class="btn btn-outline-secondary btn-sm" title="{{$edcode}}" onclick="insertbbcomment('{{$comment}}','code', {{$id}}); return false;">
<i class="fa fa-terminal comment-icon"></i>
</button>
</div>
- <div class='btn-group'>
- <!--button class="btn btn-default btn-xs" title="{{$edimg}}" onclick="insertbbcomment('{{$comment}}','img', {{$id}}); return false;">
- <i class="fa fa-camera comment-icon"></i>
- </button-->
- <button class="btn btn-default btn-xs" title="{{$edurl}}" onclick="insertCommentURL('{{$comment}}',{{$id}}); return false;">
+ <div class="btn-group mr-2">
+ {{if $can_upload}}
+ <button class="btn btn-outline-secondary btn-sm" title="{{$edatt}}" onclick="insertCommentAttach('{{$comment}}',{{$id}}); return false;">
+ <i class="fa fa-paperclip comment-icon"></i>
+ </button>
+ {{/if}}
+ <button class="btn btn-outline-secondary btn-sm" title="{{$edurl}}" onclick="insertCommentURL('{{$comment}}',{{$id}}); return false;">
<i class="fa fa-link comment-icon"></i>
</button>
- <!--button class="btn btn-default btn-xs" title="{{$edvideo}}" onclick="insertbbcomment('{{$comment}}','video', {{$id}}); return false;">
- <i class="fa fa-video-camera comment-icon"></i>
- </button-->
</div>
{{if $feature_encrypt}}
- <div class='btn-group'>
- <button class="btn btn-default btn-xs" title="{{$encrypt}}" onclick="red_encrypt('{{$cipher}}','#comment-edit-text-' + '{{$id}}',''); return false;">
+ <div class="btn-group mr-2">
+ <button class="btn btn-outline-secondary btn-sm" title="{{$encrypt}}" onclick="red_encrypt('{{$cipher}}','#comment-edit-text-' + '{{$id}}',''); return false;">
<i class="fa fa-key comment-icon"></i>
</button>
</div>
{{/if}}
{{$comment_buttons}}
</div>
- <div class="btn-group pull-right" id="comment-edit-submit-wrapper-{{$id}}">
+ <div class="btn-group float-right" id="comment-edit-submit-wrapper-{{$id}}">
{{if $preview}}
- <button id="comment-edit-presubmit-{{$id}}" class="btn btn-default btn-xs" onclick="preview_comment({{$id}}); return false;" title="{{$preview}}">
+ <button id="comment-edit-presubmit-{{$id}}" class="btn btn-outline-secondary btn-sm" onclick="preview_comment({{$id}}); return false;" title="{{$preview}}">
<i class="fa fa-eye comment-icon" ></i>
</button>
{{/if}}
- <button id="comment-edit-submit-{{$id}}" class="btn btn-primary btn-xs" type="submit" name="button-submit" onclick="post_comment({{$id}}); return false;">{{$submit}}</button>
+ <button id="comment-edit-submit-{{$id}}" class="btn btn-primary btn-sm" type="submit" name="button-submit" onclick="post_comment({{$id}}); return false;">{{$submit}}</button>
</div>
</div>
<div class="clear"></div>
</form>
</div>
- <div id="comment-edit-preview-{{$id}}" class="comment-edit-preview"></div>
+ <div id="comment-edit-preview-{{$id}}" class="comment-edit-preview mt-4"></div>
diff --git a/view/tpl/common_friends.tpl b/view/tpl/common_friends.tpl
index 489717e78..b99075210 100755
--- a/view/tpl/common_friends.tpl
+++ b/view/tpl/common_friends.tpl
@@ -1,15 +1,17 @@
-<div class="profile-match-wrapper">
- <div class="profile-match-photo">
- <a href="{{$url}}">
- <img src="{{$photo}}" alt="{{$name}}" width="80" height="80" title="{{$name}} [{{$url}}]" />
- </a>
+<div class="generic-content-wrapper">
+ <div class="section-title-wrapper">
+ <h2>{{$title}}</h2>
</div>
- <div class="profile-match-break"></div>
- <div class="profile-match-name">
- <a href="{{$url}}" title="{{$name}}[{{$tags}}]">{{$name}}</a>
+ <div class="section-content-wrapper clearfix">
+ {{foreach $items as $item}}
+ <div class="float-left mr-4">
+ <a href="{{$item.url}}">
+ <img class="contact-block-img" src="{{$item.photo}}" alt="{{$item.name}}" title="{{$item.name}} [{{$item.url}}]" />
+ </a>
+ <div>
+ {{$item.name}}
+ </div>
+ </div>
+ {{/foreach}}
</div>
- {{if $note}}
- <div class="profile-match-note">{{$note}}</div>
- {{/if}}
- <div class="profile-match-end"></div>
</div>
diff --git a/view/tpl/common_tabs.tpl b/view/tpl/common_tabs.tpl
index fa6bfbdfa..29c46369b 100755
--- a/view/tpl/common_tabs.tpl
+++ b/view/tpl/common_tabs.tpl
@@ -1,8 +1,17 @@
-<div id="tabs-collapse-1" class="navbar-collapse collapse">
- <ul class="nav nav-tabs nav-justified">
+<div class="mb-4 d-none d-md-block">
+ <ul class="nav nav-tabs nav-fill">
{{foreach $tabs as $tab}}
- <li class="{{$tab.sel}}" {{if $tab.id}}id="{{$tab.id}}"{{/if}}><a href="{{$tab.url}}"{{if $tab.title}} title="{{$tab.title}}"{{/if}}>{{$tab.label}}</a></li>
+ <li class="nav-item"{{if $tab.id}} id="{{$tab.id}}"{{/if}}><a class="nav-link{{if $tab.sel}} {{$tab.sel}}{{/if}}" href="{{$tab.url}}"{{if $tab.title}} title="{{$tab.title}}"{{/if}}>{{$tab.label}}</a></li>
{{/foreach}}
</ul>
</div>
-<div class="tabs-end"></div>
+<div class="d-md-none dropdown clearfix" style="position:fixed; right:7px; top:4.5rem; z-index:1020">
+ <button type="button" class="btn btn-outline-secondary btn-sm float-right" data-toggle="dropdown">
+ <i class="fa fa-bars"></i>
+ </button>
+ <div class="dropdown-menu dropdown-menu-right">
+ {{foreach $tabs as $tab}}
+ <a class="dropdown-item{{if $tab.sel}} {{$tab.sel}}{{/if}}" href="{{$tab.url}}"{{if $tab.title}} title="{{$tab.title}}"{{/if}}>{{$tab.label}}</a>
+ {{/foreach}}
+ </div>
+</div>
diff --git a/view/tpl/connection_template.tpl b/view/tpl/connection_template.tpl
index 64d27e609..8e49c9e27 100755
--- a/view/tpl/connection_template.tpl
+++ b/view/tpl/connection_template.tpl
@@ -1,20 +1,20 @@
<div id="contact-entry-wrapper-{{$contact.id}}">
- <div class="section-subtitle-wrapper">
+ <div class="section-subtitle-wrapper clearfix">
<div class="pull-right">
{{if $contact.approve && $contact.ignore}}
<form action="connedit/{{$contact.id}}" method="post" >
- <button type="submit" class="btn btn-success btn-xs" name="pending" value="1" title="{{$contact.approve_hover}}"><i class="fa fa-check"></i> {{$contact.approve}}</button>
+ <button type="submit" class="btn btn-success btn-sm" name="pending" value="1" title="{{$contact.approve_hover}}"><i class="fa fa-check"></i> {{$contact.approve}}</button>
- <a href="connedit/{{$contact.id}}/ignore" class="btn btn-warning btn-xs" title="{{$contact.ignore_hover}}"><i class="fa fa-ban"></i> {{$contact.ignore}}</a>
+ <a href="connedit/{{$contact.id}}/ignore" class="btn btn-warning btn-sm" title="{{$contact.ignore_hover}}"><i class="fa fa-ban"></i> {{$contact.ignore}}</a>
{{/if}}
- <a href="#" class="btn btn-danger btn-xs" title="{{$contact.delete_hover}}" onclick="dropItem('{{$contact.deletelink}}', '#contact-entry-wrapper-{{$contact.id}}'); return false;"><i class="fa fa-trash-o"></i> {{$contact.delete}}</a>
- <a href="{{$contact.link}}" class="btn btn-default btn-xs" title="{{$contact.edit_hover}}"><i class="fa fa-pencil"></i></a>
+ <a href="#" class="btn btn-danger btn-sm contact-delete-btn" title="{{$contact.delete_hover}}" onclick="dropItem('{{$contact.deletelink}}', '#contact-entry-wrapper-{{$contact.id}}'); return false;"><i class="fa fa-trash-o"></i> {{$contact.delete}}</a>
+ <a href="{{$contact.link}}" class="btn btn-outline-secondary btn-sm" title="{{$contact.edit_hover}}"><i class="fa fa-pencil"></i> {{$contact.edit}}</a>
{{if $contact.approve}}
</form>
{{/if}}
</div>
- <h3>{{if $contact.public_forum}}<i class="fa fa-comments-o"></i>&nbsp;{{/if}}<a href="{{$contact.url}}" title="{{$contact.img_hover}}" >{{$contact.name}}</a>{{if $contact.phone}}&nbsp;<a class="btn btn-default btn-xs" href="tel:{{$contact.phone}}" title="{{$contact.call}}"><i class="fa fa-phone connphone"></i></a>{{/if}}</h3>
+ <h3>{{if $contact.public_forum}}<i class="fa fa-comments-o"></i>&nbsp;{{/if}}<a href="{{$contact.url}}" title="{{$contact.img_hover}}" >{{$contact.name}}</a>{{if $contact.phone}}&nbsp;<a class="btn btn-outline-secondary btn-sm" href="tel:{{$contact.phone}}" title="{{$contact.call}}"><i class="fa fa-phone connphone"></i></a>{{/if}}</h3>
</div>
<div class="section-content-tools-wrapper">
<div class="contact-photo-wrapper" >
diff --git a/view/tpl/connections.tpl b/view/tpl/connections.tpl
index 1f7aa05b7..3b152ef5e 100755
--- a/view/tpl/connections.tpl
+++ b/view/tpl/connections.tpl
@@ -1,33 +1,31 @@
<div class="generic-content-wrapper">
- <div class="section-title-wrapper">
+ <div class="section-title-wrapper clearfix">
<div class="dropdown pull-right">
- <button type="button" class="btn btn-primary btn-xs" onclick="openClose('contacts-search-form');">
+ <button type="button" class="btn btn-primary btn-sm" onclick="openClose('contacts-search-form'); $('#contacts-search').focus()">
<i class="fa fa-search"></i>&nbsp;{{$label}}
</button>
- <button type="button" class="btn btn-default btn-xs dropdown-toggle" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false" title="{{$sort}}">
+ <button type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false" title="{{$sort}}">
<i class="fa fa-sort"></i>
</button>
- <ul class="dropdown-menu">
+ <div class="dropdown-menu dropdown-menu-right">
{{foreach $tabs as $menu}}
- <li><a href="{{$menu.url}}">{{$menu.label}}</a></li>
+ <a class="dropdown-item" href="{{$menu.url}}">{{$menu.label}}</a>
{{/foreach}}
- </ul>
+ </div>
</div>
{{if $finding}}<h2>{{$finding}}</h2>{{else}}<h2>{{$header}}{{if $total}} ({{$total}}){{/if}}</h2>{{/if}}
</div>
<div id="contacts-search-form" class="section-content-tools-wrapper">
<form action="{{$cmd}}" method="get" >
- <div class="form-group">
- <div class="input-group">
- <input type="text" name="search" id="contacts-search" class="widget-input" onfocus="this.select();" value="{{$search}}" placeholder="{{$desc}}" />
- <div class="input-group-btn">
- <button id="contacts-search-submit" class="btn btn-default btn-sm" type="submit" name="submit" value="{{$submit}}"><i class="fa fa-search"></i></button>
- </div>
+ <div class="input-group form-group">
+ <input type="text" name="search" id="contacts-search" class="form-control" onfocus="this.select();" value="{{$search}}" placeholder="{{$desc}}" />
+ <div class="input-group-btn">
+ <button id="contacts-search-submit" class="btn btn-outline-secondary" type="submit" name="submit" value="{{$submit}}"><i class="fa fa-fw fa-search"></i></button>
</div>
</div>
</form>
</div>
- <div id="connections-wrapper">
+ <div id="connections-wrapper clearfix">
{{foreach $contacts as $contact}}
{{include file="connection_template.tpl"}}
{{/foreach}}
@@ -35,4 +33,6 @@
</div>
</div>
<script>$(document).ready(function() { loadingPage = false;});</script>
-<div id="page-spinner"></div>
+<div id="page-spinner" class="spinner-wrapper">
+ <div class="spinner m"></div>
+</div>
diff --git a/view/tpl/contact_slider.tpl b/view/tpl/contact_slider.tpl
index 550abc147..0848df673 100755
--- a/view/tpl/contact_slider.tpl
+++ b/view/tpl/contact_slider.tpl
@@ -4,10 +4,10 @@ $(document).ready(function() {
// The slider does not render correct if width is given in % and
// the slider container is hidden (display: none) during rendering.
// So let's unhide it to render and hide again afterwards.
- if(!$("#affinity-tool-collapse").hasClass("in")) {
- $("#affinity-tool-collapse").addClass("in");
+ if(!$("#affinity-tool-collapse").hasClass("show")) {
+ $("#affinity-tool-collapse").addClass("show");
makeContactSlider();
- $("#affinity-tool-collapse").removeClass("in");
+ $("#affinity-tool-collapse").removeClass("show");
}
else {
makeContactSlider();
diff --git a/view/tpl/conv_frame.tpl b/view/tpl/conv_frame.tpl
index aa7b55e9b..8aa865076 100755
--- a/view/tpl/conv_frame.tpl
+++ b/view/tpl/conv_frame.tpl
@@ -1,5 +1,8 @@
<div id="threads-begin"></div>
<div id="threads-end"></div>
<div id="conversation-end"></div>
-<div id="page-spinner"></div>
+<div id="page-spinner" class="spinner-wrapper">
+ <div class="spinner m"></div>
+</div>
+
diff --git a/view/tpl/conv_item.tpl b/view/tpl/conv_item.tpl
index b5ff475b2..b0e1cb6fb 100755
--- a/view/tpl/conv_item.tpl
+++ b/view/tpl/conv_item.tpl
@@ -6,8 +6,8 @@
{{/if}}
<div id="thread-wrapper-{{$item.id}}" class="thread-wrapper{{if $item.toplevel}} {{$item.toplevel}} generic-content-wrapper h-entry {{else}} u-comment h-cite {{/if}} item_{{$item.submid}}">
<a name="item_{{$item.id}}" ></a>
- <div class="wall-item-outside-wrapper {{$item.indent}}{{$item.previewing}}" id="wall-item-outside-wrapper-{{$item.id}}" >
- <div class="wall-item-content-wrapper {{$item.indent}}" id="wall-item-content-wrapper-{{$item.id}}" style="clear:both;">
+ <div class="wall-item-outside-wrapper{{if $item.is_comment}} comment{{/if}}{{if $item.previewing}} preview{{/if}}" id="wall-item-outside-wrapper-{{$item.id}}" >
+ <div class="clearfix wall-item-content-wrapper{{if $item.is_comment}} comment{{/if}}" id="wall-item-content-wrapper-{{$item.id}}">
{{if $item.photo}}
<div class="wall-photo-item" id="wall-photo-item-{{$item.id}}">
{{$item.photo}}
@@ -18,42 +18,49 @@
{{$item.event}}
</div>
{{/if}}
- <div class="wall-item-head">
+ {{if $item.title && !$item.event}}
+ <div class="p-2{{if $item.is_new}} bg-primary text-white{{/if}} wall-item-title h3{{if !$item.photo}} rounded-top{{/if}}" id="wall-item-title-{{$item.id}}">
+ {{if $item.title_tosource}}{{if $item.plink}}<a href="{{$item.plink.href}}" title="{{$item.title}} ({{$item.plink.title}})">{{/if}}{{/if}}{{$item.title}}{{if $item.title_tosource}}{{if $item.plink}}</a>{{/if}}{{/if}}
+ </div>
+ {{if ! $item.is_new}}
+ <hr class="m-0">
+ {{/if}}
+ {{/if}}
+ <div class="p-2 clearfix wall-item-head{{if $item.is_new && !$item.title && !$item.event && !$item.is_comment}} wall-item-head-new rounded-top{{/if}}">
<div class="wall-item-info" id="wall-item-info-{{$item.id}}" >
<div class="wall-item-photo-wrapper{{if $item.owner_url}} wwfrom{{/if}} h-card p-author" id="wall-item-photo-wrapper-{{$item.id}}">
<a href="{{$item.profile_url}}" title="{{$item.linktitle}}" class="wall-item-photo-link u-url" id="wall-item-photo-link-{{$item.id}}"><img src="{{$item.thumb}}" class="wall-item-photo{{$item.sparkle}} u-photo p-name" id="wall-item-photo-{{$item.id}}" alt="{{$item.name}}" /></a>
</div>
- <div class="wall-item-photo-end" style="clear:both"></div>
</div>
- {{if $item.title}}
- <div class="wall-item-title" id="wall-item-title-{{$item.id}}" title="{{$item.title}}">
- <h3>{{if $item.title_tosource}}{{if $item.plink}}<a href="{{$item.plink.href}}" title="{{$item.title}} ({{$item.plink.title}})">{{/if}}{{/if}}{{$item.title}}{{if $item.title_tosource}}{{if $item.plink}}</a>{{/if}}{{/if}}</h3>
- </div>
- {{/if}}
{{if $item.lock}}
<div class="wall-item-lock dropdown">
- <i class="fa fa-lock lockview dropdown-toggle" data-toggle="dropdown" title="{{$item.lock}}" onclick="lockview('item',{{$item.id}});" ></i><ul id="panel-{{$item.id}}" class="lockview-panel dropdown-menu"></ul>&nbsp;
+ <i class="fa fa-lock lockview" data-toggle="dropdown" title="{{$item.lock}}" onclick="lockview('item',{{$item.id}});" ></i>&nbsp;
+ <div id="panel-{{$item.id}}" class="dropdown-menu"></div>
</div>
{{/if}}
<div class="wall-item-author">
+ {{if $item.previewing}}<span class="preview-indicator"><i class="fa fa-eye" title="{{$item.preview_lbl}}"></i></span>&nbsp;{{/if}}
<a href="{{$item.profile_url}}" title="{{$item.linktitle}}" class="wall-item-name-link"><span class="wall-item-name{{$item.sparkle}}" id="wall-item-name-{{$item.id}}" >{{$item.name}}</span></a>{{if $item.owner_url}}&nbsp;{{$item.via}}&nbsp;<a href="{{$item.owner_url}}" title="{{$item.olinktitle}}" class="wall-item-name-link"><span class="wall-item-name{{$item.osparkle}}" id="wall-item-ownername-{{$item.id}}">{{$item.owner_name}}</span></a>{{/if}}
</div>
<div class="wall-item-ago" id="wall-item-ago-{{$item.id}}">
{{if $item.verified}}<i class="fa fa-check item-verified" title="{{$item.verified}}"></i>&nbsp;{{elseif $item.forged}}<i class="fa fa-exclamation item-forged" title="{{$item.forged}}"></i>&nbsp;{{/if}}{{if $item.location}}<span class="wall-item-location p-location" id="wall-item-location-{{$item.id}}">{{$item.location}},&nbsp;</span>{{/if}}<span class="autotime" title="{{$item.isotime}}"><time class="dt-published" datetime="{{$item.isotime}}">{{$item.localtime}}</time>{{if $item.editedtime}}&nbsp;{{$item.editedtime}}{{/if}}{{if $item.expiretime}}&nbsp;{{$item.expiretime}}{{/if}}</span>{{if $item.editedtime}}&nbsp;<i class="fa fa-pencil"></i>{{/if}}&nbsp;{{if $item.app}}<span class="item.app">{{$item.str_app}}</span>{{/if}}
</div>
- <div class="clear"></div>
</div>
{{if $item.body}}
- <div class="wall-item-content" id="wall-item-content-{{$item.id}}">
+ <div class="p-2 wall-item-content clearfix" id="wall-item-content-{{$item.id}}">
<div class="wall-item-body e-content" id="wall-item-body-{{$item.id}}" >
{{$item.body}}
</div>
- <div class="clear"></div>
</div>
{{/if}}
{{if $item.has_tags}}
- <div class="wall-item-tools">
+ <div class="p-2 wall-item-tools clearfix">
+
+ <div class="body-tags">
+ <span class="tag">{{$item.mentions}} {{$item.tags}} {{$item.categories}} {{$item.folders}}</span>
+ </div>
+ {{**
{{if $item.mentions}}
<div class="body-tags" id="item-mentions">
<span class="tag">{{$item.mentions}}</span>
@@ -74,169 +81,165 @@
<span class="tag">{{$item.folders}}</span>
</div>
{{/if}}
- <div class="clear"></div>
+ **}}
</div>
{{/if}}
- <div class="wall-item-tools">
- <div class="wall-item-tools-right pull-right">
+ <div class="p-2 clearfix wall-item-tools">
+ <div class="float-right wall-item-tools-right">
+ <div class="btn-group">
+ <div id="like-rotator-{{$item.id}}" class="spinner-wrapper">
+ <div class="spinner s"></div>
+ </div>
+ </div>
{{if $item.toplevel && $item.emojis && $item.reactions}}
- <div class="btn-group dropdown">
- <button type="button" class="btn btn-default btn-sm dropdown-toggle" data-toggle="dropdown" id="wall-item-react-{{$item.id}}">
+ <div class="btn-group">
+ <button type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown" id="wall-item-react-{{$item.id}}">
<i class="fa fa-smile-o"></i>
</button>
- <ul class="dropdown-menu dropdown-menu-left" role="menu" aria-labelledby="wall-item-react-{{$item.id}}">
+ <div class="dropdown-menu dropdown-menu-right">
{{foreach $item.reactions as $react}}
- <li role="presentation"><a role="menuitem" href="#" onclick="jotReact({{$item.id}},'{{$react}}'); return false;"><img class="dropdown-menu-img-sm" src="/images/emoji/{{$react}}.png" alt="{{$react}}" /></a></li>
+ <a class="dropdown-item clearfix" href="#" onclick="jotReact({{$item.id}},'{{$react}}'); return false;"><img class="menu-img-2" src="/images/emoji/{{$react}}.png" alt="{{$react}}" /></a>
{{/foreach}}
- </ul>
+ </div>
</div>
{{/if}}
- <div class="btn-group dropdown">
+ <div class="btn-group">
{{if $item.like}}
- <button type="button" title="{{$item.like.0}}" class="btn btn-default btn-sm" onclick="dolike({{$item.id}},'like'); return false;">
+ <button type="button" title="{{$item.like.0}}" class="btn btn-outline-secondary btn-sm" onclick="dolike({{$item.id}},'like'); return false;">
<i class="fa fa-thumbs-o-up{{if $item.my_responses.like}} ivoted{{/if}}" ></i>
</button>
{{/if}}
{{if $item.dislike}}
- <button type="button" title="{{$item.dislike.0}}" class="btn btn-default btn-sm" onclick="dolike({{$item.id}},'dislike'); return false;">
+ <button type="button" title="{{$item.dislike.0}}" class="btn btn-outline-secondary btn-sm" onclick="dolike({{$item.id}},'dislike'); return false;">
<i class="fa fa-thumbs-o-down{{if $item.my_responses.dislike}} ivoted{{/if}}" ></i>
</button>
{{/if}}
{{if $item.isevent}}
- <div class="btn-group dropdown">
- <button type="button" class="btn btn-default btn-sm dropdown-toggle" data-toggle="dropdown" id="wall-item-attend-menu-{{$item.id}}" title="{{$item.attend_title}}">
+ <div class="btn-group">
+ <button type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown" id="wall-item-attend-menu-{{$item.id}}" title="{{$item.attend_title}}">
<i class="fa fa-calendar-check-o"></i>
</button>
- <ul class="dropdown-menu" role="menu" aria-labelledby="wall-item-attend-menu-{{$item.id}}">
- <li role="presentation"><a class="menuitem" href="#" title="{{$item.attend.0}}" onclick="itemAddToCal({{$item.id}}); dolike({{$item.id}},'attendyes'); return false;">
- <i class="item-act-list fa fa-check{{if $item.my_responses.attend}} ivoted{{/if}}" ></i> {{$item.attend.0}}</a>
- </li>
- <li role="presentation"><a class="menuitem" href="#" title="{{$item.attend.1}}" onclick="itemAddToCal({{$item.id}}), dolike({{$item.id}},'attendno'); return false;">
- <i class="item-act-list fa fa-times{{if $item.my_responses.attendno}} ivoted{{/if}}" ></i> {{$item.attend.1}}</a>
- </li>
- <li role="presentation"><a class="menuitem" href="#" title="{{$item.attend.2}}" onclick="itemAddToCal({{$item.id}}); dolike({{$item.id}},'attendmaybe'); return false;">
- <i class="item-act-list fa fa-question{{if $item.my_responses.attendmaybe}} ivoted{{/if}}" ></i> {{$item.attend.2}}</a>
- </li>
- </ul>
+ <div class="dropdown-menu dropdown-menu-right">
+ <a class="dropdown-item" href="#" title="{{$item.attend.0}}" onclick="itemAddToCal({{$item.id}}); dolike({{$item.id}},'attendyes'); return false;">
+ <i class="item-act-list fa fa-check{{if $item.my_responses.attend}} ivoted{{/if}}" ></i> {{$item.attend.0}}
+ </a>
+ <a class="dropdown-item" href="#" title="{{$item.attend.1}}" onclick="itemAddToCal({{$item.id}}), dolike({{$item.id}},'attendno'); return false;">
+ <i class="item-act-list fa fa-times{{if $item.my_responses.attendno}} ivoted{{/if}}" ></i> {{$item.attend.1}}
+ </a>
+ <a class="dropdown-item" href="#" title="{{$item.attend.2}}" onclick="itemAddToCal({{$item.id}}); dolike({{$item.id}},'attendmaybe'); return false;">
+ <i class="item-act-list fa fa-question{{if $item.my_responses.attendmaybe}} ivoted{{/if}}" ></i> {{$item.attend.2}}
+ </a>
+ </div>
</div>
{{/if}}
{{if $item.canvote}}
- <div class="btn-group dropdown">
- <button type="button" class="btn btn-default btn-sm dropdown-toggle" data-toggle="dropdown" id="wall-item-consensus-menu-{{$item.id}}" title="{{$item.vote_title}}">
+ <div class="btn-group">
+ <button type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown" id="wall-item-consensus-menu-{{$item.id}}" title="{{$item.vote_title}}">
<i class="fa fa-check-square-o"></i>
</button>
- <ul class="dropdown-menu" role="menu" aria-labelledby="wall-item-consensus-menu-{{$item.id}}">
- <li role="presentation"><a class="menuitem" href="#" title="{{$item.conlabels.0}}" onclick="dolike({{$item.id}},'agree'); return false;">
- <i class="item-act-list fa fa-check{{if $item.my_responses.agree}} ivoted{{/if}}" ></i> {{$item.conlabels.0}}</a>
- </li>
- <li role="presentation"><a class="menuitem" href="#" title="{{$item.conlabels.1}}" onclick="dolike({{$item.id}},'disagree'); return false;">
- <i class="item-act-list fa fa-times{{if $item.my_responses.disagree}} ivoted{{/if}}" ></i> {{$item.conlabels.1}}</a>
- </li>
- <li role="presentation"><a class="menuitem" href="#" title="{{$item.conlabels.2}}" onclick="dolike({{$item.id}},'abstain'); return false;">
- <i class="item-act-list fa fa-question{{if $item.my_responses.abstain}} ivoted{{/if}}" ></i> {{$item.conlabels.2}}</a>
- </li>
- </ul>
+ <div class="dropdown-menu dropdown-menu-right" role="menu" aria-labelledby="wall-item-consensus-menu-{{$item.id}}">
+ <a class="dropdown-item" href="#" title="{{$item.conlabels.0}}" onclick="dolike({{$item.id}},'agree'); return false;">
+ <i class="item-act-list fa fa-check{{if $item.my_responses.agree}} ivoted{{/if}}" ></i> {{$item.conlabels.0}}
+ </a>
+ <a class="dropdown-item" href="#" title="{{$item.conlabels.1}}" onclick="dolike({{$item.id}},'disagree'); return false;">
+ <i class="item-act-list fa fa-times{{if $item.my_responses.disagree}} ivoted{{/if}}" ></i> {{$item.conlabels.1}}
+ </a>
+ <a class="dropdown-item" href="#" title="{{$item.conlabels.2}}" onclick="dolike({{$item.id}},'abstain'); return false;">
+ <i class="item-act-list fa fa-question{{if $item.my_responses.abstain}} ivoted{{/if}}" ></i> {{$item.conlabels.2}}
+ </a>
+ </div>
</div>
{{/if}}
- <button type="button" class="btn btn-default btn-sm dropdown-toggle" data-toggle="dropdown" id="wall-item-menu-{{$item.id}}">
- <i class="fa fa-caret-down"></i>
- </button>
- <ul class="dropdown-menu dropdown-menu-right" role="menu" aria-labelledby="wall-item-menu-{{$item.id}}">
- {{if $item.share}}
- <li role="presentation"><a role="menuitem" href="#" onclick="jotShare({{$item.id}}); return false"><i class="fa fa-retweet" title="{{$item.share.0}}"></i> {{$item.share.0}}</a></li>
- {{/if}}
- {{if $item.plink}}
- <li role="presentation"><a role="menuitem" href="{{$item.plink.href}}" title="{{$item.plink.title}}" class="u-url"><i class="fa fa-external-link"></i> {{$item.plink.title}}</a></li>
- {{/if}}
- {{if $item.edpost}}
- <li role="presentation"><a role="menuitem" href="{{$item.edpost.0}}" title="{{$item.edpost.1}}"><i class="editpost fa fa-pencil"></i> {{$item.edpost.1}}</a></li>
- {{/if}}
- {{if $item.tagger}}
- <li role="presentation"><a role="menuitem" href="#" onclick="itemTag({{$item.id}}); return false;"><i id="tagger-{{$item.id}}" class="fa fa-tag" title="{{$item.tagger.tagit}}"></i> {{$item.tagger.tagit}}</a></li>
- {{/if}}
- {{if $item.filer}}
- <li role="presentation"><a role="menuitem" href="#" onclick="itemFiler({{$item.id}}); return false;"><i id="filer-{{$item.id}}" class="fa fa-folder-open" title="{{$item.filer}}"></i> {{$item.filer}}</a></li>
- {{/if}}
- {{if $item.bookmark}}
- <li role="presentation"><a role="menuitem" href="#" onclick="itemBookmark({{$item.id}}); return false;"><i id="bookmarker-{{$item.id}}" class="fa fa-bookmark" title="{{$item.bookmark}}"></i> {{$item.bookmark}}</a></li>
- {{/if}}
- {{if $item.addtocal}}
- <li role="presentation"><a role="menuitem" href="#" onclick="itemAddToCal({{$item.id}}); return false;"><i id="addtocal-{{$item.id}}" class="fa fa-calendar" title="{{$item.addtocal}}"></i> {{$item.addtocal}}</a></li>
- {{/if}}
- {{if $item.star}}
- <li role="presentation"><a role="menuitem" href="#" onclick="dostar({{$item.id}}); return false;"><i id="starred-{{$item.id}}" class="fa fa-star {{$item.star.isstarred}}" title="{{$item.star.toggle}}"></i> {{$item.star.toggle}}</a></li>
- {{/if}}
-
- {{if $item.thread_action_menu}}
- {{foreach $item.thread_action_menu as $mitem}}
- <li role="presentation"><a role="menuitem" {{if $mitem.href}}href="{{$mitem.href}}"{{/if}} {{if $mitem.action}}onclick="{{$mitem.action}}"{{/if}} {{if $mitem.title}}title="{{$mitem.title}}"{{/if}} ><i class="fa fa-{{$mitem.icon}}"></i> {{$mitem.title}}</a></li>
- {{/foreach}}
- {{/if}}
-
- {{if $item.drop.dropping}}
- <li role="presentation"><a role="menuitem" href="#" onclick="dropItem('item/drop/{{$item.id}}', '#thread-wrapper-{{$item.id}}'); return false;" title="{{$item.drop.delete}}" ><i class="fa fa-trash-o"></i> {{$item.drop.delete}}</a></li>
- {{/if}}
-
- {{if $item.thread_author_menu}}
- <li role="presentation" class="divider"></li>
- {{foreach $item.thread_author_menu as $mitem}}
- <li role="presentation"><a role="menuitem" {{if $mitem.href}}href="{{$mitem.href}}"{{/if}} {{if $mitem.action}}onclick="{{$mitem.action}}"{{/if}} {{if $mitem.title}}title="{{$mitem.title}}"{{/if}} >{{$mitem.title}}</a></li>
- {{/foreach}}
- {{/if}}
-
- {{if $item.edpost && $item.dreport}}
- <li role="presentation"><a role="menuitem" href="dreport/{{$item.mid}}">{{$item.dreport}}</a></li>
- {{/if}}
- </ul>
+ <div class="btn-group">
+ <button type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown" id="wall-item-menu-{{$item.id}}">
+ <i class="fa fa-cog"></i>
+ </button>
+ <div class="dropdown-menu dropdown-menu-right" role="menu" aria-labelledby="wall-item-menu-{{$item.id}}">
+ {{if $item.share}}
+ <a class="dropdown-item" href="#" onclick="jotShare({{$item.id}},{{$item.item_type}}); return false"><i class="generic-icons-nav fa fa-fw fa-retweet" title="{{$item.share.0}}"></i>{{$item.share.0}}</a>
+ {{/if}}
+ {{if $item.plink}}
+ <a class="dropdown-item" href="{{$item.plink.href}}" title="{{$item.plink.title}}" class="u-url"><i class="generic-icons-nav fa fa-fw fa-external-link"></i>{{$item.plink.title}}</a>
+ {{/if}}
+ {{if $item.edpost}}
+ <a class="dropdown-item" href="{{$item.edpost.0}}" title="{{$item.edpost.1}}"><i class="generic-icons-nav fa fa-fw fa-pencil"></i>{{$item.edpost.1}}</a>
+ {{/if}}
+ {{if $item.tagger}}
+ <a class="dropdown-item" href="#" onclick="itemTag({{$item.id}}); return false;"><i id="tagger-{{$item.id}}" class="generic-icons-nav fa fa-fw fa-tag" title="{{$item.tagger.tagit}}"></i>{{$item.tagger.tagit}}</a>
+ {{/if}}
+ {{if $item.filer}}
+ <a class="dropdown-item" href="#" onclick="itemFiler({{$item.id}}); return false;"><i id="filer-{{$item.id}}" class="generic-icons-nav fa fa-fw fa-folder-open" title="{{$item.filer}}"></i>{{$item.filer}}</a>
+ {{/if}}
+ {{if $item.bookmark}}
+ <a class="dropdown-item" href="#" onclick="itemBookmark({{$item.id}}); return false;"><i id="bookmarker-{{$item.id}}" class="generic-icons-nav fa fa-fw fa-bookmark" title="{{$item.bookmark}}"></i>{{$item.bookmark}}</a>
+ {{/if}}
+ {{if $item.addtocal}}
+ <a class="dropdown-item" href="#" onclick="itemAddToCal({{$item.id}}); return false;"><i id="addtocal-{{$item.id}}" class="generic-icons-nav fa fa-fw fa-calendar" title="{{$item.addtocal}}"></i>{{$item.addtocal}}</a>
+ {{/if}}
+ {{if $item.star}}
+ <a class="dropdown-item" href="#" onclick="dostar({{$item.id}}); return false;"><i id="starred-{{$item.id}}" class="generic-icons-nav fa fa-fw fa-star {{$item.star.isstarred}}" title="{{$item.star.toggle}}"></i>{{$item.star.toggle}}</a>
+ {{/if}}
+ {{if $item.thread_action_menu}}
+ {{foreach $item.thread_action_menu as $mitem}}
+ <a class="dropdown-item" {{if $mitem.href}}href="{{$mitem.href}}"{{/if}} {{if $mitem.action}}onclick="{{$mitem.action}}"{{/if}} {{if $mitem.title}}title="{{$mitem.title}}"{{/if}} ><i class="generic-icons-nav fa fa-fw fa-{{$mitem.icon}}"></i>{{$mitem.title}}</a>
+ {{/foreach}}
+ {{/if}}
+ {{if $item.drop.dropping}}
+ <a class="dropdown-item" href="#" onclick="dropItem('item/drop/{{$item.id}}', '#thread-wrapper-{{$item.id}}'); return false;" title="{{$item.drop.delete}}" ><i class="generic-icons-nav fa fa-fw fa-trash-o"></i>{{$item.drop.delete}}</a>
+ {{/if}}
+ {{if $item.thread_author_menu}}
+ <div class="dropdown-divider"></div>
+ {{foreach $item.thread_author_menu as $mitem}}
+ <a class="dropdown-item" {{if $mitem.href}}href="{{$mitem.href}}"{{/if}} {{if $mitem.action}}onclick="{{$mitem.action}}"{{/if}} {{if $mitem.title}}title="{{$mitem.title}}"{{/if}} >{{$mitem.title}}</a>
+ {{/foreach}}
+ {{/if}}
+ {{if $item.edpost && $item.dreport}}
+ <a class="dropdown-item" href="dreport/{{$item.mid}}">{{$item.dreport}}</a>
+ {{/if}}
+ </div>
+ </div>
</div>
</div>
- <div id="like-rotator-{{$item.id}}" class="like-rotator"></div>
{{if $item.responses || $item.attachments}}
<div class="wall-item-tools-left{{if ($item.responses.count > 1) || ($item.responses.count && $item.attachments)}} btn-group{{/if}}">
{{if $item.attachments}}
<div class="btn-group">
- <button type="button" class="btn btn-default btn-sm wall-item-like dropdown-toggle" data-toggle="dropdown" id="attachment-menu-{{$item.id}}"><i class="fa fa-paperclip"></i></button>
- <ul class="dropdown-menu" role="menu" aria-labelledby="attachment-menu-{{$item.id}}">{{$item.attachments}}</ul>
+ <button type="button" class="btn btn-outline-secondary btn-sm wall-item-like dropdown-toggle" data-toggle="dropdown" id="attachment-menu-{{$item.id}}"><i class="fa fa-paperclip"></i></button>
+ <div class="dropdown-menu">{{$item.attachments}}</div>
</div>
{{/if}}
{{foreach $item.responses as $verb=>$response}}
{{if $response.count}}
<div class="btn-group">
- <button type="button" class="btn btn-default btn-sm wall-item-like dropdown-toggle" data-toggle="dropdown" id="wall-item-{{$verb}}-{{$item.id}}">{{$response.count}} {{$response.button}}</button>
- {{if $response.list_part}}
- <ul class="dropdown-menu" role="menu" aria-labelledby="wall-item-{{$verb}}-{{$item.id}}">{{foreach $response.list_part as $liker}}<li role="presentation">{{$liker}}</li>{{/foreach}}</ul>
- {{else}}
- <ul class="dropdown-menu" role="menu" aria-labelledby="wall-item-{{$verb}}-{{$item.id}}">{{foreach $response.list as $liker}}<li role="presentation">{{$liker}}</li>{{/foreach}}</ul>
- {{/if}}
- {{if $response.list_part}}
+ <button type="button" class="btn btn-outline-secondary btn-sm wall-item-like dropdown-toggle"{{if $response.modal}} data-toggle="modal" data-target="#{{$verb}}Modal-{{$item.id}}"{{else}} data-toggle="dropdown"{{/if}} id="wall-item-{{$verb}}-{{$item.id}}">{{$response.count}} {{$response.button}}</button>
+ {{if $response.modal}}
<div class="modal" id="{{$verb}}Modal-{{$item.id}}">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
+ <h4 class="modal-title">{{$response.count}} {{$response.button}}</h4>
<button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button>
- <h4 class="modal-title">{{$response.title}}</h4>
</div>
<div class="modal-body response-list">
- <ul class="nav nav-pills nav-stacked">{{foreach $response.list as $liker}}<li role="presentation">{{$liker}}</li>{{/foreach}}</ul>
+ <ul class="nav nav-pills flex-column">{{foreach $response.list as $liker}}<li class="nav-item">{{$liker}}</li>{{/foreach}}</ul>
</div>
<div class="modal-footer clear">
- <button type="button" class="btn btn-default" data-dismiss="modal">{{$item.modal_dismiss}}</button>
+ <button type="button" class="btn btn-outline-secondary" data-dismiss="modal">{{$item.modal_dismiss}}</button>
</div>
</div><!-- /.modal-content -->
</div><!-- /.modal-dialog -->
</div><!-- /.modal -->
+ {{else}}
+ <div class="dropdown-menu">{{foreach $response.list as $liker}}{{$liker}}{{/foreach}}</div>
{{/if}}
</div>
{{/if}}
{{/foreach}}
</div>
{{/if}}
- <div class="clear"></div>
</div>
- <div class="clear"></div>
</div>
- <div class="clear{{if $indent}} {{$indent}}{{/if}}"></div>
</div>
{{if $item.toplevel}}
{{foreach $item.children as $child}}
@@ -244,10 +247,9 @@
{{/foreach}}
{{/if}}
{{if $item.comment}}
- <div class="wall-item-comment-wrapper{{if $item.children}} wall-item-comment-wrapper-wc{{/if}}" >
+ <div class="p-2 wall-item-comment-wrapper{{if $item.children}} wall-item-comment-wrapper-wc{{/if}}" >
{{$item.comment}}
</div>
- <div class="clear"></div>
{{/if}}
</div>
{{if $item.comment_lastcollapsed}}
diff --git a/view/tpl/conv_list.tpl b/view/tpl/conv_list.tpl
index b1080af34..97fd50d01 100755
--- a/view/tpl/conv_list.tpl
+++ b/view/tpl/conv_list.tpl
@@ -4,10 +4,10 @@
</div>
<div id="collapsed-comments-{{$item.id}}" class="collapsed-comments" style="display: none;">
{{/if}}
- <div id="thread-wrapper-{{$item.id}}" class="thread-wrapper conv-list-mode{{if $item.toplevel}} {{$item.toplevel}} generic-content-wrapper{{/if}}">
- <a name="{{$item.id}}" ></a>
- <div class="wall-item-outside-wrapper {{$item.indent}}{{$item.previewing}}" id="wall-item-outside-wrapper-{{$item.id}}" >
- <div class="wall-item-content-wrapper {{$item.indent}}" id="wall-item-content-wrapper-{{$item.id}}" style="clear:both;">
+ <div id="thread-wrapper-{{$item.id}}" class="thread-wrapper{{if $item.toplevel}} {{$item.toplevel}} generic-content-wrapper h-entry {{else}} u-comment h-cite {{/if}} item_{{$item.submid}}">
+ <a name="item_{{$item.id}}" ></a>
+ <div class="wall-item-outside-wrapper{{if $item.is_comment}} comment{{/if}}{{if $item.previewing}} preview{{/if}}" id="wall-item-outside-wrapper-{{$item.id}}" >
+ <div class="clearfix wall-item-content-wrapper{{if $item.is_comment}} comment{{/if}}" id="wall-item-content-wrapper-{{$item.id}}">
{{if $item.photo}}
<div class="wall-photo-item" id="wall-photo-item-{{$item.id}}">
{{$item.photo}}
@@ -18,39 +18,48 @@
{{$item.event}}
</div>
{{/if}}
- <div class="wall-item-head">
+ {{if $item.title && !$item.event}}
+ <div class="p-2{{if $item.is_new}} bg-primary text-white{{/if}} wall-item-title h3{{if !$item.photo}} rounded-top{{/if}}" id="wall-item-title-{{$item.id}}">
+ {{if $item.title_tosource}}{{if $item.plink}}<a href="{{$item.plink.href}}" title="{{$item.title}} ({{$item.plink.title}})">{{/if}}{{/if}}{{$item.title}}{{if $item.title_tosource}}{{if $item.plink}}</a>{{/if}}{{/if}}
+ </div>
+ {{if ! $item.is_new}}
+ <hr class="m-0">
+ {{/if}}
+ {{/if}}
+ <div class="p-2 clearfix wall-item-head{{if $item.is_new && !$item.title && !$item.event && !$item.is_comment}} wall-item-head-new rounded-top{{/if}}">
<div class="wall-item-info" id="wall-item-info-{{$item.id}}" >
- <div class="wall-item-photo-wrapper{{if $item.owner_url}} wwfrom{{/if}}" id="wall-item-photo-wrapper-{{$item.id}}">
- <a href="{{$item.profile_url}}" title="{{$item.linktitle}}" class="wall-item-photo-link" id="wall-item-photo-link-{{$item.id}}"><img src="{{$item.thumb}}" class="wall-item-photo{{$item.sparkle}}" id="wall-item-photo-{{$item.id}}" alt="{{$item.name}}" /></a>
+ <div class="wall-item-photo-wrapper{{if $item.owner_url}} wwfrom{{/if}} h-card p-author" id="wall-item-photo-wrapper-{{$item.id}}">
+ <a href="{{$item.profile_url}}" title="{{$item.linktitle}}" class="wall-item-photo-link u-url" id="wall-item-photo-link-{{$item.id}}"><img src="{{$item.thumb}}" class="wall-item-photo{{$item.sparkle}} u-photo p-name" id="wall-item-photo-{{$item.id}}" alt="{{$item.name}}" /></a>
</div>
- <div class="wall-item-photo-end" style="clear:both"></div>
</div>
- {{if $item.title}}
- <div class="wall-item-title" id="wall-item-title-{{$item.id}}" title="{{$item.title}}">
- <h3>{{if $item.title_tosource}}{{if $item.plink}}<a href="{{$item.plink.href}}" title="{{$item.title}} ({{$item.plink.title}})">{{/if}}{{/if}}{{$item.title}}{{if $item.title_tosource}}{{if $item.plink}}</a>{{/if}}{{/if}}</h3>
- </div>
- {{/if}}
{{if $item.lock}}
<div class="wall-item-lock dropdown">
- <i class="fa fa-lock lockview dropdown-toggle" data-toggle="dropdown" title="{{$item.lock}}" onclick="lockview('item',{{$item.id}});" ></i><ul id="panel-{{$item.id}}" class="lockview-panel dropdown-menu"></ul>&nbsp;
+ <i class="fa fa-lock lockview" data-toggle="dropdown" title="{{$item.lock}}" onclick="lockview('item',{{$item.id}});" ></i>&nbsp;
+ <div id="panel-{{$item.id}}" class="dropdown-menu"></div>
</div>
{{/if}}
<div class="wall-item-author">
<a href="{{$item.profile_url}}" title="{{$item.linktitle}}" class="wall-item-name-link"><span class="wall-item-name{{$item.sparkle}}" id="wall-item-name-{{$item.id}}" >{{$item.name}}</span></a>{{if $item.owner_url}}&nbsp;{{$item.via}}&nbsp;<a href="{{$item.owner_url}}" title="{{$item.olinktitle}}" class="wall-item-name-link"><span class="wall-item-name{{$item.osparkle}}" id="wall-item-ownername-{{$item.id}}">{{$item.owner_name}}</span></a>{{/if}}
</div>
<div class="wall-item-ago" id="wall-item-ago-{{$item.id}}">
- {{if $item.verified}}<i class="fa fa-check item-verified" title="{{$item.verified}}"></i>&nbsp;{{elseif $item.forged}}<i class="fa fa-exclamation item-forged" title="{{$item.forged}}"></i>&nbsp;{{/if}}{{if $item.location}}<span class="wall-item-location" id="wall-item-location-{{$item.id}}">{{$item.location}},&nbsp;</span>{{/if}}<span class="autotime" title="{{$item.isotime}}">{{$item.localtime}}{{if $item.editedtime}}&nbsp;{{$item.editedtime}}{{/if}}{{if $item.expiretime}}&nbsp;{{$item.expiretime}}{{/if}}</span>{{if $item.editedtime}}&nbsp;<i class="fa fa-pencil"></i>{{/if}}&nbsp;{{if $item.app}}<span class="item.app">{{$item.str_app}}</span>{{/if}}
+ {{if $item.verified}}<i class="fa fa-check item-verified" title="{{$item.verified}}"></i>&nbsp;{{elseif $item.forged}}<i class="fa fa-exclamation item-forged" title="{{$item.forged}}"></i>&nbsp;{{/if}}{{if $item.location}}<span class="wall-item-location p-location" id="wall-item-location-{{$item.id}}">{{$item.location}},&nbsp;</span>{{/if}}<span class="autotime" title="{{$item.isotime}}"><time class="dt-published" datetime="{{$item.isotime}}">{{$item.localtime}}</time>{{if $item.editedtime}}&nbsp;{{$item.editedtime}}{{/if}}{{if $item.expiretime}}&nbsp;{{$item.expiretime}}{{/if}}</span>{{if $item.editedtime}}&nbsp;<i class="fa fa-pencil"></i>{{/if}}&nbsp;{{if $item.app}}<span class="item.app">{{$item.str_app}}</span>{{/if}}
</div>
- <div class="clear"></div>
</div>
- <div class="{{if $item.is_photo}}wall-photo-item{{else}}wall-item-content{{/if}}" id="wall-item-content-{{$item.id}}">
- <div class="wall-item-body" id="wall-item-body-{{$item.id}}" >
+
+ {{if $item.body}}
+ <div class="p-2 wall-item-content clearfix" id="wall-item-content-{{$item.id}}">
+ <div class="wall-item-body e-content" id="wall-item-body-{{$item.id}}" >
{{$item.body}}
</div>
- <div class="clear"></div>
</div>
+ {{/if}}
{{if $item.has_tags}}
- <div class="wall-item-tools">
+ <div class="p-2 wall-item-tools clearfix">
+
+ <div class="body-tags">
+ <span class="tag">{{$item.mentions}} {{$item.tags}} {{$item.categories}} {{$item.folders}}</span>
+ </div>
+ {{**
{{if $item.mentions}}
<div class="body-tags" id="item-mentions">
<span class="tag">{{$item.mentions}}</span>
@@ -63,7 +72,7 @@
{{/if}}
{{if $item.categories}}
<div class="body-tags" id="item-categories">
- <span class="tag">{{$item.categories}}</span>
+ <span class="tag p-category">{{$item.categories}}</span>
</div>
{{/if}}
{{if $item.folders}}
@@ -71,101 +80,136 @@
<span class="tag">{{$item.folders}}</span>
</div>
{{/if}}
- <div class="clear"></div>
+ **}}
</div>
{{/if}}
-
- <div class="wall-item-tools">
- <div class="wall-item-tools-right btn-group pull-right">
- {{if $item.like}}
- <button type="button" class="btn btn-default btn-sm" onclick="dolike({{$item.id}},'like'); return false">
- <i class="fa fa-thumbs-o-up" title="{{$item.like.0}}"></i>
- </button>
- {{/if}}
- {{if $item.dislike}}
- <button type="button" class="btn btn-default btn-sm" onclick="dolike({{$item.id}},'dislike'); return false">
- <i class="fa fa-thumbs-o-down" title="{{$item.dislike.0}}"></i>
- </button>
- {{/if}}
-
- {{if $item.isevent}}
- <button type="button" title="{{$item.attend.0}}" class="btn btn-default btn-sm" onclick="itemAddToCal({{$item.id}}); dolike({{$item.id}},'attendyes'); return false;">
- <i class="fa fa-check" ></i>
- </button>
- <button type="button" title="{{$item.attend.1}}" class="btn btn-default btn-sm" onclick="itemAddToCal({{$item.id}}); dolike({{$item.id}},'attendno'); return false;">
- <i class="fa fa-times" ></i>
- </button>
- <button type="button" title="{{$item.attend.2}}" class="btn btn-default btn-sm" onclick="itemAddToCal({{$item.id}}); dolike({{$item.id}},'attendmaybe'); return false;">
- <i class="fa fa-question" ></i>
- </button>
- {{/if}}
-
- {{if $item.canvote}}
- <button type="button" title="{{$item.conlabels.0}}" class="btn btn-default btn-sm" onclick="dolike({{$item.id}},'agree'); return false;">
- <i class="fa fa-check" ></i>
- </button>
- <button type="button" title="{{$item.conlabels.1}}" class="btn btn-default btn-sm" onclick="dolike({{$item.id}},'disagree'); return false;">
- <i class="fa fa-times" ></i>
- </button>
- <button type="button" title="{{$item.conlabels.2}}" class="btn btn-default btn-sm" onclick="dolike({{$item.id}},'abstain'); return false;">
- <i class="fa fa-question" ></i>
- </button>
+ <div class="p-2 clearfix wall-item-tools">
+ <div class="float-right wall-item-tools-right">
+ {{if $item.toplevel && $item.emojis && $item.reactions}}
+ <div class="btn-group">
+ <button type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown" id="wall-item-react-{{$item.id}}">
+ <i class="fa fa-smile-o"></i>
+ </button>
+ <div class="dropdown-menu dropdown-menu-right">
+ {{foreach $item.reactions as $react}}
+ <a class="dropdown-item clearfix" href="#" onclick="jotReact({{$item.id}},'{{$react}}'); return false;"><img class="menu-img-2" src="/images/emoji/{{$react}}.png" alt="{{$react}}" /></a>
+ {{/foreach}}
+ </div>
+ </div>
{{/if}}
-
- <button type="button" class="btn btn-default btn-sm dropdown-toggle" data-toggle="dropdown" id="wall-item-menu-{{$item.id}}">
- <i class="fa fa-caret-down"></i>
- </button>
- <ul class="dropdown-menu" role="menu" aria-labelledby="wall-item-menu-{{$item.id}}">
- {{if $item.share}}
- <li role="presentation"><a role="menuitem" href="#" onclick="jotShare({{$item.id}}); return false"><i class="fa fa-retweet" title="{{$item.share.0}}"></i> {{$item.share.0}}</a></li>
- {{/if}}
- {{if $item.plink}}
- <li role="presentation"><a role="menuitem" href="{{$item.plink.href}}" title="{{$item.plink.title}}" ><i class="fa fa-external-link"></i> {{$item.plink.title}}</a></li>
- {{/if}}
- {{if $item.edpost}}
- <li role="presentation"><a role="menuitem" href="{{$item.edpost.0}}" title="{{$item.edpost.1}}"><i class="editpost fa fa-pencil"></i> {{$item.edpost.1}}</a></li>
- {{/if}}
- {{if $item.tagger}}
- <li role="presentation"><a role="menuitem" href="#" onclick="itemTag({{$item.id}}); return false;"><i id="tagger-{{$item.id}}" class="fa fa-tag" title="{{$item.tagger.tagit}}"></i> {{$item.tagger.tagit}}</a></li>
- {{/if}}
- {{if $item.filer}}
- <li role="presentation"><a role="menuitem" href="#" onclick="itemFiler({{$item.id}}); return false;"><i id="filer-{{$item.id}}" class="fa fa-folder-open" title="{{$item.filer}}"></i> {{$item.filer}}</a></li>
- {{/if}}
- {{if $item.bookmark}}
- <li role="presentation"><a role="menuitem" href="#" onclick="itemBookmark({{$item.id}}); return false;"><i id="bookmarker-{{$item.id}}" class="fa fa-bookmark" title="{{$item.bookmark}}"></i> {{$item.bookmark}}</a></li>
- {{/if}}
- {{if $item.addtocal}}
- <li role="presentation"><a role="menuitem" href="#" onclick="itemAddToCal({{$item.id}}); return false;"><i id="addtocal-{{$item.id}}" class="fa fa-calendar" title="{{$item.addtocal}}"></i> {{$item.addtocal}}</a></li>
+ <div class="btn-group">
+ {{if $item.like}}
+ <button type="button" title="{{$item.like.0}}" class="btn btn-outline-secondary btn-sm" onclick="dolike({{$item.id}},'like'); return false;">
+ <i class="fa fa-thumbs-o-up{{if $item.my_responses.like}} ivoted{{/if}}" ></i>
+ </button>
{{/if}}
- {{if $item.star}}
- <li role="presentation"><a role="menuitem" href="#" onclick="dostar({{$item.id}}); return false;"><i id="starred-{{$item.id}}" class="fa fa-star {{$item.star.isstarred}}" title="{{$item.star.toggle}}"></i> {{$item.star.toggle}}</a></li>
+ {{if $item.dislike}}
+ <button type="button" title="{{$item.dislike.0}}" class="btn btn-outline-secondary btn-sm" onclick="dolike({{$item.id}},'dislike'); return false;">
+ <i class="fa fa-thumbs-o-down{{if $item.my_responses.dislike}} ivoted{{/if}}" ></i>
+ </button>
{{/if}}
- {{if $item.drop.dropping}}
- <li role="presentation"><a role="menuitem" href="#" onclick="dropItem('item/drop/{{$item.id}}', '#thread-wrapper-{{$item.id}}'); return false;" title="{{$item.drop.delete}}" ><i class="fa fa-trash-o"></i> {{$item.drop.delete}}</a></li>
+ {{if $item.isevent}}
+ <div class="btn-group">
+ <button type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown" id="wall-item-attend-menu-{{$item.id}}" title="{{$item.attend_title}}">
+ <i class="fa fa-calendar-check-o"></i>
+ </button>
+ <div class="dropdown-menu">
+ <a class="dropdown-item" href="#" title="{{$item.attend.0}}" onclick="itemAddToCal({{$item.id}}); dolike({{$item.id}},'attendyes'); return false;">
+ <i class="item-act-list fa fa-check{{if $item.my_responses.attend}} ivoted{{/if}}" ></i> {{$item.attend.0}}
+ </a>
+ <a class="dropdown-item" href="#" title="{{$item.attend.1}}" onclick="itemAddToCal({{$item.id}}), dolike({{$item.id}},'attendno'); return false;">
+ <i class="item-act-list fa fa-times{{if $item.my_responses.attendno}} ivoted{{/if}}" ></i> {{$item.attend.1}}
+ </a>
+ <a class="dropdown-item" href="#" title="{{$item.attend.2}}" onclick="itemAddToCal({{$item.id}}); dolike({{$item.id}},'attendmaybe'); return false;">
+ <i class="item-act-list fa fa-question{{if $item.my_responses.attendmaybe}} ivoted{{/if}}" ></i> {{$item.attend.2}}
+ </a>
+ </div>
+ </div>
{{/if}}
- {{if $item.item_photo_menu}}
- <li role="presentation" class="divider"></li>
- {{$item.item_photo_menu}}
+ {{if $item.canvote}}
+ <div class="btn-group">
+ <button type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown" id="wall-item-consensus-menu-{{$item.id}}" title="{{$item.vote_title}}">
+ <i class="fa fa-check-square-o"></i>
+ </button>
+ <div class="dropdown-menu" role="menu" aria-labelledby="wall-item-consensus-menu-{{$item.id}}">
+ <a class="dropdown-item" href="#" title="{{$item.conlabels.0}}" onclick="dolike({{$item.id}},'agree'); return false;">
+ <i class="item-act-list fa fa-check{{if $item.my_responses.agree}} ivoted{{/if}}" ></i> {{$item.conlabels.0}}
+ </a>
+ <a class="dropdown-item" href="#" title="{{$item.conlabels.1}}" onclick="dolike({{$item.id}},'disagree'); return false;">
+ <i class="item-act-list fa fa-times{{if $item.my_responses.disagree}} ivoted{{/if}}" ></i> {{$item.conlabels.1}}
+ </a>
+ <a class="dropdown-item" href="#" title="{{$item.conlabels.2}}" onclick="dolike({{$item.id}},'abstain'); return false;">
+ <i class="item-act-list fa fa-question{{if $item.my_responses.abstain}} ivoted{{/if}}" ></i> {{$item.conlabels.2}}
+ </a>
+ </div>
+ </div>
{{/if}}
-
- </ul>
+ <div class="btn-group">
+ <button type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown" id="wall-item-menu-{{$item.id}}">
+ <i class="fa fa-cog"></i>
+ </button>
+ <div class="dropdown-menu dropdown-menu-right" role="menu" aria-labelledby="wall-item-menu-{{$item.id}}">
+ {{if $item.share}}
+ <a class="dropdown-item" href="#" onclick="jotShare({{$item.id}},{{$item.item_type}}); return false"><i class="generic-icons-nav fa fa-fw fa-retweet" title="{{$item.share.0}}"></i>{{$item.share.0}}</a>
+ {{/if}}
+ {{if $item.plink}}
+ <a class="dropdown-item" href="{{$item.plink.href}}" title="{{$item.plink.title}}" class="u-url"><i class="generic-icons-nav fa fa-fw fa-external-link"></i>{{$item.plink.title}}</a>
+ {{/if}}
+ {{if $item.edpost}}
+ <a class="dropdown-item" href="{{$item.edpost.0}}" title="{{$item.edpost.1}}"><i class="generic-icons-nav fa fa-fw fa-pencil"></i>{{$item.edpost.1}}</a>
+ {{/if}}
+ {{if $item.tagger}}
+ <a class="dropdown-item" href="#" onclick="itemTag({{$item.id}}); return false;"><i id="tagger-{{$item.id}}" class="generic-icons-nav fa fa-fw fa-tag" title="{{$item.tagger.tagit}}"></i>{{$item.tagger.tagit}}</a>
+ {{/if}}
+ {{if $item.filer}}
+ <a class="dropdown-item" href="#" onclick="itemFiler({{$item.id}}); return false;"><i id="filer-{{$item.id}}" class="generic-icons-nav fa fa-fw fa-folder-open" title="{{$item.filer}}"></i>{{$item.filer}}</a>
+ {{/if}}
+ {{if $item.bookmark}}
+ <a class="dropdown-item" href="#" onclick="itemBookmark({{$item.id}}); return false;"><i id="bookmarker-{{$item.id}}" class="generic-icons-nav fa fa-fw fa-bookmark" title="{{$item.bookmark}}"></i>{{$item.bookmark}}</a>
+ {{/if}}
+ {{if $item.addtocal}}
+ <a class="dropdown-item" href="#" onclick="itemAddToCal({{$item.id}}); return false;"><i id="addtocal-{{$item.id}}" class="generic-icons-nav fa fa-fw fa-calendar" title="{{$item.addtocal}}"></i>{{$item.addtocal}}</a>
+ {{/if}}
+ {{if $item.star}}
+ <a class="dropdown-item" href="#" onclick="dostar({{$item.id}}); return false;"><i id="starred-{{$item.id}}" class="generic-icons-nav fa fa-fw fa-star {{$item.star.isstarred}}" title="{{$item.star.toggle}}"></i>{{$item.star.toggle}}</a>
+ {{/if}}
+ {{if $item.thread_action_menu}}
+ {{foreach $item.thread_action_menu as $mitem}}
+ <a class="dropdown-item" {{if $mitem.href}}href="{{$mitem.href}}"{{/if}} {{if $mitem.action}}onclick="{{$mitem.action}}"{{/if}} {{if $mitem.title}}title="{{$mitem.title}}"{{/if}} ><i class="generic-icons-nav fa fa-fw fa-{{$mitem.icon}}"></i>{{$mitem.title}}</a>
+ {{/foreach}}
+ {{/if}}
+ {{if $item.drop.dropping}}
+ <a class="dropdown-item" href="#" onclick="dropItem('item/drop/{{$item.id}}', '#thread-wrapper-{{$item.id}}'); return false;" title="{{$item.drop.delete}}" ><i class="generic-icons-nav fa fa-fw fa-trash-o"></i>{{$item.drop.delete}}</a>
+ {{/if}}
+ {{if $item.thread_author_menu}}
+ <div class="dropdown-divider"></div>
+ {{foreach $item.thread_author_menu as $mitem}}
+ <a class="dropdown-item" {{if $mitem.href}}href="{{$mitem.href}}"{{/if}} {{if $mitem.action}}onclick="{{$mitem.action}}"{{/if}} {{if $mitem.title}}title="{{$mitem.title}}"{{/if}} >{{$mitem.title}}</a>
+ {{/foreach}}
+ {{/if}}
+ {{if $item.edpost && $item.dreport}}
+ <a class="dropdown-item" href="dreport/{{$item.mid}}">{{$item.dreport}}</a>
+ {{/if}}
+ </div>
+ </div>
+ </div>
</div>
<div id="like-rotator-{{$item.id}}" class="like-rotator"></div>
<div class="wall-item-tools-left{{if $item.unseen_comments || $item.like_count || $item.dislike_count || $item.attachments}} btn-group{{/if}}">
{{if $item.attachments}}
<div class="btn-group">
- <button type="button" class="btn btn-default btn-sm wall-item-like dropdown-toggle" data-toggle="dropdown" id="attachment-menu-{{$item.id}}"><i class="fa fa-paperclip"></i></button>
+ <button type="button" class="btn btn-outline-secondary btn-sm wall-item-like dropdown-toggle" data-toggle="dropdown" id="attachment-menu-{{$item.id}}"><i class="fa fa-paperclip"></i></button>
<ul class="dropdown-menu" role="menu" aria-labelledby="attachment-menu-{{$item.id}}">{{$item.attachments}}</ul>
</div>
{{/if}}
<div class="wall-item-list-comments btn-group">
- <button class="btn btn-default btn-sm" onclick="window.location.href='{{$item.viewthread}}'; return false;">
+ <a class="btn btn-outline-secondary btn-sm" href="{{$item.viewthread}}">
{{$item.comment_count_txt}}{{if $item.unseen_comments}}<span class="unseen-wall-indicator-{{$item.id}}">, {{$item.list_unseen_txt}}</span>{{/if}}
- </button>
+ </a>
</div>
{{if $item.unseen_comments}}
<div class="unseen-wall-indicator-{{$item.id}} btn-group">
- <button class="btn btn-default btn-sm" title="{{$item.markseen}}" onclick="markItemRead({{$item.id}}); return false;">
+ <button class="btn btn-outline-secondary btn-sm" title="{{$item.markseen}}" onclick="markItemRead({{$item.id}}); return false;">
<i class="fa fa-check-square-o"></i>
</button>
</div>
@@ -174,40 +218,34 @@
{{foreach $item.responses as $verb=>$response}}
{{if $response.count}}
<div class="btn-group">
- <button type="button" class="btn btn-default btn-sm wall-item-like dropdown-toggle" data-toggle="dropdown" id="wall-item-{{$verb}}-{{$item.id}}">{{$response.count}} {{$response.button}}</button>
- {{if $response.list_part}}
- <ul class="dropdown-menu" role="menu" aria-labelledby="wall-item-{{$verb}}-{{$item.id}}">{{foreach $response.list_part as $liker}}<li role="presentation">{{$liker}}</li>{{/foreach}}</ul>
- {{else}}
- <ul class="dropdown-menu" role="menu" aria-labelledby="wall-item-{{$verb}}-{{$item.id}}">{{foreach $response.list as $liker}}<li role="presentation">{{$liker}}</li>{{/foreach}}</ul>
- {{/if}}
- {{if $response.list_part}}
+ <button type="button" class="btn btn-outline-secondary btn-sm wall-item-like dropdown-toggle"{{if $response.modal}} data-toggle="modal" data-target="#{{$verb}}Modal-{{$item.id}}"{{else}} data-toggle="dropdown"{{/if}} id="wall-item-{{$verb}}-{{$item.id}}">{{$response.count}} {{$response.button}}</button>
+ {{if $response.modal}}
<div class="modal" id="{{$verb}}Modal-{{$item.id}}">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
+ <h4 class="modal-title">{{$response.count}} {{$response.button}}</h4>
<button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button>
- <h4 class="modal-title">{{$response.title}}</h4>
</div>
- <div class="modal-body">
- <ul>{{foreach $response.list as $liker}}<li role="presentation">{{$liker}}</li>{{/foreach}}</ul>
+ <div class="modal-body response-list">
+ <ul class="nav nav-pills flex-column">{{foreach $response.list as $liker}}<li class="nav-item">{{$liker}}</li>{{/foreach}}</ul>
</div>
<div class="modal-footer clear">
- <button type="button" class="btn btn-default" data-dismiss="modal">{{$item.modal_dismiss}}</button>
+ <button type="button" class="btn btn-outline-secondary" data-dismiss="modal">{{$item.modal_dismiss}}</button>
</div>
</div><!-- /.modal-content -->
</div><!-- /.modal-dialog -->
</div><!-- /.modal -->
+ {{else}}
+ <div class="dropdown-menu">{{foreach $response.list as $liker}}{{$liker}}{{/foreach}}</div>
{{/if}}
</div>
{{/if}}
{{/foreach}}
{{/if}}
</div>
- <div class="clear"></div>
</div>
- <div class="clear"></div>
</div>
- <div class="clear{{if $indent}} {{$indent}}{{/if}}"></div>
</div>
</div>
{{if $item.comment_lastcollapsed}}
diff --git a/view/tpl/cover_photo_widget.tpl b/view/tpl/cover_photo_widget.tpl
index bc1f421bd..7404a740c 100755
--- a/view/tpl/cover_photo_widget.tpl
+++ b/view/tpl/cover_photo_widget.tpl
@@ -8,16 +8,14 @@
aside_padding_top = parseInt($('aside').css('padding-top'));
section_padding_top = parseInt($('section').css('padding-top'));
- $(document).on('click', slideUpCover);
+ $('#cover-photo').on('click', slideUpCover);
+ $('#cover-photo').on('keyup', slideUpCover);
if($('#cover-photo').length && $(window).width() > 755) {
if($(window).scrollTop() < $('#cover-photo').height()) {
+ $('.navbar').removeClass('fixed-top');
$('main').css('margin-top', - $('nav').outerHeight(true) + 'px');
- $('aside').css('padding-top', aside_padding_top - $('nav').outerHeight() + 'px');
- $('section').css('padding-top', section_padding_top - $('nav').outerHeight() + 'px');
- $('.navbar-fixed-top').css('position', 'relative');
$('main').css('opacity', 0);
- $('header').hide();
}
}
else {
@@ -28,12 +26,9 @@
$(window).scroll(function () {
if($('#cover-photo').length && $(window).width() > 755 && $(window).scrollTop() >= $('#cover-photo').height()) {
- $('header').fadeIn();
- $('main').css('opacity', 1);
- $('aside').css('padding-top', aside_padding_top + 'px');
- $('section').css('padding-top', section_padding_top + 'px');
- $('.navbar-fixed-top').css('position', '');
+ $('.navbar').addClass('fixed-top');
$('main').css('margin-top', '');
+ $('main').css('opacity', 1);
coverSlid = true;
}
else if ($('#cover-photo').length && $(window).width() > 755 && $(window).scrollTop() < $('#cover-photo').height()){
@@ -43,13 +38,9 @@
}
else {
if($(window).scrollTop() < $('#cover-photo').height()) {
+ $('.navbar').removeClass('fixed-top');
$('main').css('margin-top', - $('nav').outerHeight(true) + 'px');
- $('aside').css('padding-top', aside_padding_top - $('nav').outerHeight() + 'px');
- $('section').css('padding-top', section_padding_top - $('nav').outerHeight() + 'px');
-
- $('.navbar-fixed-top').css('position', 'relative');
$('main').css('opacity', 0);
- $('header').hide();
}
}
}
@@ -61,10 +52,8 @@
$(window).resize(function () {
if($('#cover-photo').length && $(window).width() < 755) {
$('#cover-photo').remove();
+ $('.navbar').addClass('fixed-top');
$('main').css('opacity', 1);
- $('aside').css('padding-top', aside_padding_top + 'px');
- $('section').css('padding-top', section_padding_top + 'px');
- $('.navbar-fixed-top').css('position', '');
coverSlid = true;
}
@@ -82,11 +71,7 @@
<div id="cover-photo" title="{{$hovertitle}}">
{{$photo_html}}
<div id="cover-photo-caption">
- <div class="cover-photo-title">
- {{$title}}
- </div>
- <div class="cover-photo-subtitle">
- {{$subtitle}}
- </div>
+ <h1>{{$title}}</h1>
+ <h3>{{$subtitle}}</h3>
</div>
</div>
diff --git a/view/tpl/design_tools.tpl b/view/tpl/design_tools.tpl
index dffeeafa0..bc7d46dc1 100644
--- a/view/tpl/design_tools.tpl
+++ b/view/tpl/design_tools.tpl
@@ -1,9 +1,9 @@
<div id="design-tools" class="widget design-tools">
-<h3>{{$title}}</h3>
-<ul class="nav nav-pills nav-stacked">
-<li><a href="blocks/{{$who}}">{{$blocks}}</a></li>
-<li><a href="menu{{if $sys}}?f=&sys=1{{/if}}">{{$menus}}</a></li>
-<li><a href="layouts/{{$who}}">{{$layout}}</a></li>
-<li><a href="webpages/{{$who}}">{{$pages}}</a></li>
-</ul>
+ <h3>{{$title}}</h3>
+ <div class="nav nav-pills flex-column">
+ <a class="nav-link" href="blocks/{{$who}}">{{$blocks}}</a>
+ <a class="nav-link" href="menu{{if $sys}}?f=&sys=1{{/if}}">{{$menus}}</a>
+ <a class="nav-link" href="layouts/{{$who}}">{{$layout}}</a>
+ <a class="nav-link" href="webpages/{{$who}}">{{$pages}}</a>
+ </div>
</div>
diff --git a/view/tpl/diaspora_vcard.tpl b/view/tpl/diaspora_vcard.tpl
deleted file mode 100644
index 017eb555c..000000000
--- a/view/tpl/diaspora_vcard.tpl
+++ /dev/null
@@ -1,69 +0,0 @@
-<div style="display:none;">
- <dl class="entity_uid">
- <dt>Uid</dt>
- <dd>
- <span class="uid p-uid">{{$diaspora.guid}}</span>
- </dd>
- </dl>
- <dl class='entity_nickname'>
- <dt>Nickname</dt>
- <dd>
- <span class="nickname p-nickname">{{$diaspora.nickname}}</span>
- </dd>
- </dl>
- <dl class='entity_full_name'>
- <dt>Full name</dt>
- <dd>
- <span class='fn p-name'>{{$diaspora.fullname}}</span>
- </dd>
- </dl>
-
- <dl class='entity_first_name'>
- <dt>First name</dt>
- <dd>
- <span class='given_name p-given-name'>{{$diaspora.firstname}}</span>
- </dd>
- </dl>
- <dl class='entity_family_name'>
- <dt>Family name</dt>
- <dd>
- <span class='family_name p-family-name'>{{$diaspora.lastname}}</span>
- </dd>
- </dl>
- <dl class="entity_url">
- <dt>URL</dt>
- <dd>
- <a href="{{$diaspora.podloc}}/" id="pod_location" class="url" rel="me" >{{$diaspora.podloc}}/</a>
- </dd>
- </dl>
- <dl class="entity_photo">
- <dt>Photo</dt>
- <dd>
- <img class="photo u-photo avatar" height="300" width="300" src="{{$diaspora.photo300}}" />
- </dd>
- </dl>
- <dl class="entity_photo_medium">
- <dt>Photo</dt>
- <dd>
- <img class="photo u-photo avatar" height="100" width="100" src="{{$diaspora.photo100}}" />
- </dd>
- </dl>
- <dl class="entity_photo_small">
- <dt>Photo</dt>
- <dd>
- <img class="photo u-photo avatar" height="50" width="50" src="{{$diaspora.photo50}}" />
- </dd>
- </dl>
- <dl class="entity_searchable">
- <dt>Searchable</dt>
- <dd>
- <span class="searchable">{{$diaspora.searchable}}</span>
- </dd>
- </dl>
- <dl class="entity_key">
- <dt>Key</dt>
- <dd>
- <pre class="key">{{$diaspora.pubkey}}</pre>
- </dd>
- </dl>
-</div>
diff --git a/view/tpl/directory_header.tpl b/view/tpl/directory_header.tpl
index c82fada45..3ee9ee326 100755
--- a/view/tpl/directory_header.tpl
+++ b/view/tpl/directory_header.tpl
@@ -1,24 +1,24 @@
<div class="generic-content-wrapper">
- <div class="section-title-wrapper">
+ <div class="section-title-wrapper clearfix">
<div class="btn-group pull-right">
- <button type="button" class="btn btn-default btn-xs dropdown-toggle" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false" title="{{$sort}}">
+ <button type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false" title="{{$sort}}">
<i class="fa fa-sort"></i>
</button>
- <ul class="dropdown-menu">
- <li><a href="directory?f=&order=date{{$suggest}}">{{$date}}</a></li>
- <li><a href="directory?f=&order=normal{{$suggest}}">{{$normal}}</a></li>
- <li><a href="directory?f=&order=reversedate{{$suggest}}">{{$reversedate}}</a></li>
- <li><a href="directory?f=&order=reverse{{$suggest}}">{{$reverse}}</a></li>
- </ul>
+ <div class="dropdown-menu dropdown-menu-right">
+ <a class="dropdown-item" href="directory?f=&order=date{{$suggest}}">{{$date}}</a>
+ <a class="dropdown-item" href="directory?f=&order=normal{{$suggest}}">{{$normal}}</a>
+ <a class="dropdown-item" href="directory?f=&order=reversedate{{$suggest}}">{{$reversedate}}</a>
+ <a class="dropdown-item" href="directory?f=&order=reverse{{$suggest}}">{{$reverse}}</a>
+ </div>
</div>
<h2>{{$dirlbl}}{{if $search}}:&nbsp;{{$safetxt}}{{/if}}</h2>
- <div class="clear"></div>
</div>
{{foreach $entries as $entry}}
{{include file="direntry.tpl"}}
{{/foreach}}
<div id="page-end"></div>
- <div class="clear"></div>
</div>
<script>$(document).ready(function() { loadingPage = false;});</script>
-<div id="page-spinner"></div>
+<div id="page-spinner" class="spinner-wrapper">
+ <div class="spinner m"></div>
+</div>
diff --git a/view/tpl/direntry.tpl b/view/tpl/direntry.tpl
index c9940a347..f7ec7db23 100755
--- a/view/tpl/direntry.tpl
+++ b/view/tpl/direntry.tpl
@@ -1,17 +1,17 @@
<div class="directory-item{{if $entry.safe}} safe{{/if}}" id="directory-item-{{$entry.hash}}" >
- <div class="section-subtitle-wrapper">
+ <div class="section-subtitle-wrapper clearfix">
<div class="pull-right">
{{if $entry.viewrate}}
- {{if $entry.total_ratings}}<a href="ratings/{{$entry.hash}}" id="dir-rating-{{$entry.hash}}" class="btn btn-default btn-xs">{{$entry.total_ratings}}</a>{{/if}}
+ {{if $entry.total_ratings}}<a href="ratings/{{$entry.hash}}" id="dir-rating-{{$entry.hash}}" class="btn btn-outline-secondary btn-sm">{{$entry.total_ratings}}</a>{{/if}}
{{/if}}
{{if $entry.ignlink}}
- <a class="directory-ignore btn btn-warning btn-xs" href="{{$entry.ignlink}}"> {{$entry.ignore_label}}</a>
+ <a class="directory-ignore btn btn-warning btn-sm" href="{{$entry.ignlink}}"> {{$entry.ignore_label}}</a>
{{/if}}
{{if $entry.connect}}
- <a class="btn btn-success btn-xs" href="{{$entry.connect}}"><i class="fa fa-plus connect-icon"></i> {{$entry.conn_label}}</a>
+ <a class="btn btn-success btn-sm" href="{{$entry.connect}}"><i class="fa fa-plus connect-icon"></i> {{$entry.conn_label}}</a>
{{/if}}
{{if $entry.viewrate}}
- {{if $entry.canrate}}<button class="btn btn-default btn-xs" onclick="doRatings('{{$entry.hash}}'); return false;" ><i class="fa fa-pencil"></i><span id="edited-{{$entry.hash}}" class="required" id="edited-{{$entry.hash}}" style="display: none;" >&nbsp;*</span></button>{{/if}}
+ {{if $entry.canrate}}<button class="btn btn-outline-secondary btn-sm" onclick="doRatings('{{$entry.hash}}'); return false;" ><i class="fa fa-pencil"></i><span id="edited-{{$entry.hash}}" class="required" id="edited-{{$entry.hash}}" style="display: none;" >&nbsp;*</span></button>{{/if}}
{{/if}}
</div>
<h3>{{if $entry.public_forum}}<i class="fa fa-comments-o" title="{{$entry.forum_label}} @{{$entry.nickname}}+"></i>&nbsp;{{/if}}<a href='{{$entry.profile_link}}' >{{$entry.name}}</a>{{if $entry.online}}&nbsp;<i class="fa fa-asterisk online-now" title="{{$entry.online}}"></i>{{/if}}</h3>
diff --git a/view/tpl/dreport.tpl b/view/tpl/dreport.tpl
index 8aa5e2cd1..1f5915609 100644
--- a/view/tpl/dreport.tpl
+++ b/view/tpl/dreport.tpl
@@ -2,7 +2,7 @@
<div class="section-title-wrapper">
{{if $table == 'item'}}
<div class="dropdown pull-right">
- <button type="button" class="btn btn-default btn-xs dropdown-toggle" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false" title="{{$options}}">
+ <button type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false" title="{{$options}}">
<i class="fa fa-sort-desc"></i>
</button>
<ul class="dropdown-menu">
diff --git a/view/tpl/edpost_head.tpl b/view/tpl/edpost_head.tpl
index 79a8f347f..b2ab5db4e 100755
--- a/view/tpl/edpost_head.tpl
+++ b/view/tpl/edpost_head.tpl
@@ -2,7 +2,7 @@
<div class="section-title-wrapper">
{{if $delete}}
<div class="pull-right">
- <a href="item/drop/{{$id}}" id="delete-btn" class="btn btn-xs btn-danger" onclick="return confirmDelete();"><i class="fa fa-trash-o"></i>&nbsp;{{$delete}}</a>
+ <a href="item/drop/{{$id}}" id="delete-btn" class="btn btn-sm btn-danger" onclick="return confirmDelete();"><i class="fa fa-trash-o"></i>&nbsp;{{$delete}}</a>
</div>
{{/if}}
<h2>{{$title}}</h2>
diff --git a/view/tpl/event.tpl b/view/tpl/event.tpl
index fe3cfc517..cc0bfc1c7 100755
--- a/view/tpl/event.tpl
+++ b/view/tpl/event.tpl
@@ -6,9 +6,9 @@
</div>
{{$event.html}}
<div class="event-buttons">
- {{if $event.item.plink}}<a href="{{$event.plink.0}}" title="{{$event.plink.1}}" class="plink-event-link"><i class="fa fa-external-link btn btn-default" ></i></a>{{/if}}
- {{if $event.edit}}<a href="{{$event.edit.0}}" title="{{$event.edit.1}}" class="edit-event-link"><i class="fa fa-pencil btn btn-default"></i></a>{{/if}}
- {{if $event.drop}}<a href="{{$event.drop.0}}" title="{{$event.drop.1}}" class="drop-event-link"><i class="fa fa-trash-o btn btn-default"></i></a>{{/if}}
+ {{if $event.item.plink}}<a href="{{$event.plink.0}}" title="{{$event.plink.1}}" class="plink-event-link"><i class="fa fa-external-link btn btn-outline-secondary" ></i></a>{{/if}}
+ {{if $event.edit}}<a href="{{$event.edit.0}}" title="{{$event.edit.1}}" class="edit-event-link"><i class="fa fa-pencil btn btn-outline-secondary"></i></a>{{/if}}
+ {{if $event.drop}}<a href="{{$event.drop.0}}" title="{{$event.drop.1}}" class="drop-event-link"><i class="fa fa-trash-o btn btn-outline-secondary"></i></a>{{/if}}
</div>
<div class="clear"></div>
</div>
diff --git a/view/tpl/event_cal.tpl b/view/tpl/event_cal.tpl
index a88df6d18..d7662786b 100755
--- a/view/tpl/event_cal.tpl
+++ b/view/tpl/event_cal.tpl
@@ -6,7 +6,7 @@
</div>
{{$event.html}}
<div class="event-buttons">
- {{if $event.item.plink}}<a href="{{$event.plink.0}}" title="{{$event.plink.1}}" class="plink-event-link"><i class="fa fa-external-link btn btn-default" ></i></a>{{/if}}
+ {{if $event.item.plink}}<a href="{{$event.plink.0}}" title="{{$event.plink.1}}" class="plink-event-link"><i class="fa fa-external-link btn btn-outline-secondary" ></i></a>{{/if}}
</div>
<div class="clear"></div>
</div>
diff --git a/view/tpl/event_form.tpl b/view/tpl/event_form.tpl
index 8a06567c1..d07a06b67 100755
--- a/view/tpl/event_form.tpl
+++ b/view/tpl/event_form.tpl
@@ -32,35 +32,37 @@
{{/if}}
<div class="form-group">
- <div id="event-desc-text"><b>{{$d_text}}</b></div>
- <textarea id="comment-edit-text-desc" class="form-control" name="desc" >{{$d_orig}}</textarea>
+ <div class="form-group">
+ <div id="event-desc-text"><b>{{$d_text}}</b></div>
+ <textarea id="comment-edit-text-desc" class="form-control" name="desc" >{{$d_orig}}</textarea>
+ </div>
<div id="comment-tools-desc" class="comment-tools" style="display: block;" >
<div id="comment-edit-bb-desc" class="btn-toolbar">
- <div class='btn-group'>
- <button type="button" class="btn btn-default btn-xs" title="{{$edbold}}" onclick="insertbbcomment('none','b', 'desc');">
+ <div class='btn-group mr-2'>
+ <button type="button" class="btn btn-outline-secondary btn-sm" title="{{$edbold}}" onclick="insertbbcomment('none','b', 'desc');">
<i class="fa fa-bold comment-icon"></i>
</button>
- <button type="button" class="btn btn-default btn-xs" title="{{$editalic}}" onclick="insertbbcomment('none','i', 'desc');">
+ <button type="button" class="btn btn-outline-secondary btn-sm" title="{{$editalic}}" onclick="insertbbcomment('none','i', 'desc');">
<i class="fa fa-italic comment-icon"></i>
</button>
- <button type="button" class="btn btn-default btn-xs" title="{{$eduline}}" onclick="insertbbcomment('none','u', 'desc');">
+ <button type="button" class="btn btn-outline-secondary btn-sm" title="{{$eduline}}" onclick="insertbbcomment('none','u', 'desc');">
<i class="fa fa-underline comment-icon"></i>
</button>
- <button type="button" class="btn btn-default btn-xs" title="{{$edquote}}" onclick="insertbbcomment('none','quote','desc');">
+ <button type="button" class="btn btn-outline-secondary btn-sm" title="{{$edquote}}" onclick="insertbbcomment('none','quote','desc');">
<i class="fa fa-quote-left comment-icon"></i>
</button>
- <button type="button" class="btn btn-default btn-xs" title="{{$edcode}}" onclick="insertbbcomment('none','code', 'desc');">
+ <button type="button" class="btn btn-outline-secondary btn-sm" title="{{$edcode}}" onclick="insertbbcomment('none','code', 'desc');">
<i class="fa fa-terminal comment-icon"></i>
</button>
</div>
<div class='btn-group'>
- <button type="button" class="btn btn-default btn-xs" title="{{$edimg}}" onclick="insertbbcomment('none','img', 'desc');">
+ <button type="button" class="btn btn-outline-secondary btn-sm" title="{{$edimg}}" onclick="insertbbcomment('none','img', 'desc');">
<i class="fa fa-camera comment-icon"></i>
</button>
- <button type="button" class="btn btn-default btn-xs" title="{{$edurl}}" onclick="insertbbcomment('none','url', 'desc');">
+ <button type="button" class="btn btn-outline-secondary btn-sm" title="{{$edurl}}" onclick="insertbbcomment('none','url', 'desc');">
<i class="fa fa-link comment-icon"></i>
</button>
- <button type="button" class="btn btn-default btn-xs" title="{{$edvideo}}" onclick="insertbbcomment('none','video', 'desc');">
+ <button type="button" class="btn btn-outline-secondary btn-sm" title="{{$edvideo}}" onclick="insertbbcomment('none','video', 'desc');">
<i class="fa fa-video-camera comment-icon"></i>
</button>
</div>
@@ -68,38 +70,40 @@
</div>
</div>
<div class="form-group">
- <div id="event-location-text"><b>{{$l_text}}</b></div>
- <textarea id="comment-edit-text-loc" class="form-control" name="location">{{$l_orig}}</textarea>
+ <div class="form-group">
+ <div id="event-location-text"><b>{{$l_text}}</b></div>
+ <textarea id="comment-edit-text-loc" class="form-control" name="location">{{$l_orig}}</textarea>
+ </div>
<div id="comment-tools-loc" class="comment-tools" style="display: block;" >
<div id="comment-edit-bb-loc" class="btn-toolbar">
- <div class='btn-group'>
- <button type="button" class="btn btn-default btn-xs" title="{{$edbold}}" onclick="insertbbcomment('none','b', 'loc');">
+ <div class='btn-group mr-2'>
+ <button type="button" class="btn btn-outline-secondary btn-sm" title="{{$edbold}}" onclick="insertbbcomment('none','b', 'loc');">
<i class="fa fa-bold comment-icon"></i>
</button>
- <button type="button" class="btn btn-default btn-xs" title="{{$editalic}}" onclick="insertbbcomment('none','i', 'loc');">
+ <button type="button" class="btn btn-outline-secondary btn-sm" title="{{$editalic}}" onclick="insertbbcomment('none','i', 'loc');">
<i class="fa fa-italic comment-icon"></i>
</button>
- <button type="button" class="btn btn-default btn-xs" title="{{$eduline}}" onclick="insertbbcomment('none','u', 'loc');">
+ <button type="button" class="btn btn-outline-secondary btn-sm" title="{{$eduline}}" onclick="insertbbcomment('none','u', 'loc');">
<i class="fa fa-underline comment-icon"></i>
</button>
- <button type="button" class="btn btn-default btn-xs" title="{{$edquote}}" onclick="insertbbcomment('none','quote','loc');">
+ <button type="button" class="btn btn-outline-secondary btn-sm" title="{{$edquote}}" onclick="insertbbcomment('none','quote','loc');">
<i class="fa fa-quote-left comment-icon"></i>
</button>
- <button type="button" class="btn btn-default btn-xs" title="{{$edcode}}" onclick="insertbbcomment('none','code', 'loc');">
+ <button type="button" class="btn btn-outline-secondary btn-sm" title="{{$edcode}}" onclick="insertbbcomment('none','code', 'loc');">
<i class="fa fa-terminal comment-icon"></i>
</button>
</div>
<div class='btn-group'>
- <button type="button" class="btn btn-default btn-xs" title="{{$edimg}}" onclick="insertbbcomment('none','img', 'loc');">
+ <button type="button" class="btn btn-outline-secondary btn-sm" title="{{$edimg}}" onclick="insertbbcomment('none','img', 'loc');">
<i class="fa fa-camera comment-icon"></i>
</button>
- <button type="button" class="btn btn-default btn-xs" title="{{$edurl}}" onclick="insertbbcomment('none','url', 'loc');">
+ <button type="button" class="btn btn-outline-secondary btn-sm" title="{{$edurl}}" onclick="insertbbcomment('none','url', 'loc');">
<i class="fa fa-link comment-icon"></i>
</button>
- <button type="button" class="btn btn-default btn-xs" title="{{$edvideo}}" onclick="insertbbcomment('none','video', 'loc');">
+ <button type="button" class="btn btn-outline-secondary btn-sm" title="{{$edvideo}}" onclick="insertbbcomment('none','video', 'loc');">
<i class="fa fa-video-camera comment-icon"></i>
</button>
- <button type="button" class="btn btn-default btn-xs" title="{{$mapper}}" onclick="insertbbcomment('none','map','loc');">
+ <button type="button" class="btn btn-outline-secondary btn-sm" title="{{$mapper}}" onclick="insertbbcomment('none','map','loc');">
<i class="fa fa-globe comment-icon"></i>
</button>
</div>
@@ -111,13 +115,13 @@
<div class="clear"></div>
- <button type="button" class="btn btn-default" onclick="openClose('advanced');">{{$advanced}}</button>
- <div class="btn-group pull-right">
- <button id="event-edit-preview-btn" class="btn btn-default" type="button" title="{{$preview}}" onclick="doEventPreview();"><i class="fa fa-eye" ></i></button>
+ <button type="button" class="btn btn-outline-secondary btn-sm" onclick="openClose('advanced');">{{$advanced}}</button>
+ <div class="btn-group float-right">
+ <button id="event-edit-preview-btn" class="btn btn-outline-secondary btn-sm" type="button" title="{{$preview}}" onclick="doEventPreview();"><i class="fa fa-eye" ></i></button>
{{if ! $eid}}
- <button id="dbtn-acl" class="btn btn-default" type="button" data-toggle="modal" data-target="#aclModal" title="{{$perms_label}}"><i id="jot-perms-icon" class="fa fa-{{$lockstate}}"></i></button>
+ <button id="dbtn-acl" class="btn btn-outline-secondary btn-sm" type="button" data-toggle="modal" data-target="#aclModal" title="{{$perms_label}}"><i id="jot-perms-icon" class="fa fa-{{$lockstate}}"></i></button>
{{/if}}
- <button id="event-submit" class="btn btn-primary" type="submit" name="submit">{{$submit}}</button>
+ <button id="event-submit" class="btn btn-primary btn-sm" type="submit" name="submit">{{$submit}}</button>
</div>
</form>
diff --git a/view/tpl/event_head.tpl b/view/tpl/event_head.tpl
index 1d1b6f15b..2f440e826 100755
--- a/view/tpl/event_head.tpl
+++ b/view/tpl/event_head.tpl
@@ -50,6 +50,7 @@
$('#events-calendar').fullCalendar({
events: '{{$baseurl}}{{$module_url}}/json',
header: false,
+ eventTextColor: 'white',
lang: '{{$lang}}',
firstDay: {{$first_day}},
@@ -66,11 +67,11 @@
showEvent(calEvent.id);
},
loading: function(isLoading, view) {
- $('#events-spinner').spin('tiny');
- $('#events-spinner > i').css('color', 'transparent');
+ $('#events-spinner').show();
+ $('#today-btn > i').hide();
if(!isLoading) {
- $('#events-spinner').spin(false);
- $('#events-spinner > i').css('color', '');
+ $('#events-spinner').hide();
+ $('#today-btn > i').show();
$('td.fc-day').dblclick(function() {
openMenu('form');
//window.location.href='/events/new?start='+$(this).data('date');
diff --git a/view/tpl/events-js.tpl b/view/tpl/events-js.tpl
index 6299242ce..d3f3414ff 100755
--- a/view/tpl/events-js.tpl
+++ b/view/tpl/events-js.tpl
@@ -2,20 +2,20 @@
<div class="section-title-wrapper">
<div class="pull-right">
<div class="dropdown">
- <button type="button" class="btn btn-default btn-xs dropdown-toggle" data-toggle="dropdown"><i class="fa fa-caret-down"></i>&nbsp;{{$view_label}}</button>
- <ul class="dropdown-menu">
- <li><a href="#" onclick="changeView('changeView', 'month'); return false;">{{$month}}</a></li>
- <li><a href="#" onclick="changeView('changeView', 'agendaWeek'); return false;">{{$week}}</a></li>
- <li><a href="#" onclick="changeView('changeView', 'agendaDay'); return false;">{{$day}}</a></li>
- </ul>
- <button class="btn btn-success btn-xs" onclick="openClose('form');">{{$new_event.1}}</button>
+ <button type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown"><i class="fa fa-cog"></i>&nbsp;{{$view_label}}</button>
+ <div class="dropdown-menu">
+ <a class="dropdown-item" href="#" onclick="changeView('changeView', 'month'); return false;">{{$month}}</a>
+ <a class="dropdown-item" href="#" onclick="changeView('changeView', 'agendaWeek'); return false;">{{$week}}</a>
+ <a class="dropdown-item" href="#" onclick="changeView('changeView', 'agendaDay'); return false;">{{$day}}</a>
+ </div>
+ <button class="btn btn-success btn-sm" onclick="openClose('form');">{{$new_event.1}}</button>
<div class="btn-group">
- <button class="btn btn-default btn-xs" onclick="changeView('prev', false);" title="{{$prev}}"><i class="fa fa-backward"></i></button>
- <button id="events-spinner" class="btn btn-default btn-xs" onclick="changeView('today', false);" title="{{$today}}"><i class="fa fa-bullseye"></i></button>
- <button class="btn btn-default btn-xs" onclick="changeView('next', false);" title="{{$next}}"><i class="fa fa-forward"></i></button>
+ <button class="btn btn-outline-secondary btn-sm" onclick="changeView('prev', false);" title="{{$prev}}"><i class="fa fa-backward"></i></button>
+ <button id="today-btn" class="btn btn-outline-secondary btn-sm" onclick="changeView('today', false);" title="{{$today}}"><div id="events-spinner" class="spinner s"></div><i class="fa fa-bullseye" style="display: none; width: 1rem;"></i></button>
+ <button class="btn btn-outline-secondary btn-sm" onclick="changeView('next', false);" title="{{$next}}"><i class="fa fa-forward"></i></button>
</div>
- <button id="fullscreen-btn" type="button" class="btn btn-default btn-xs" onclick="makeFullScreen();"><i class="fa fa-expand"></i></button>
- <button id="inline-btn" type="button" class="btn btn-default btn-xs" onclick="makeFullScreen(false);"><i class="fa fa-compress"></i></button>
+ <button id="fullscreen-btn" type="button" class="btn btn-outline-secondary btn-sm" onclick="makeFullScreen();"><i class="fa fa-expand"></i></button>
+ <button id="inline-btn" type="button" class="btn btn-outline-secondary btn-sm" onclick="makeFullScreen(false);"><i class="fa fa-compress"></i></button>
</div>
</div>
<h2 id="title"></h2>
diff --git a/view/tpl/events_cal-js.tpl b/view/tpl/events_cal-js.tpl
index b7836cfab..2c4d961f9 100755
--- a/view/tpl/events_cal-js.tpl
+++ b/view/tpl/events_cal-js.tpl
@@ -3,12 +3,12 @@
<div class="section-title-wrapper">
<div class="pull-right">
<div class="btn-group">
- <button class="btn btn-default btn-xs" onclick="changeView('prev', false);" title="{{$prev}}"><i class="fa fa-backward"></i></button>
- <button id="events-spinner" class="btn btn-default btn-xs" onclick="changeView('today', false);" title="{{$today}}"><i class="fa fa-bullseye"></i></button>
- <button class="btn btn-default btn-xs" onclick="changeView('next', false);" title="{{$next}}"><i class="fa fa-forward"></i></button>
+ <button class="btn btn-outline-secondary btn-sm" onclick="changeView('prev', false);" title="{{$prev}}"><i class="fa fa-backward"></i></button>
+ <button id="today-btn" class="btn btn-outline-secondary btn-sm" onclick="changeView('today', false);" title="{{$today}}"><div id="events-spinner" class="spinner s"></div><i class="fa fa-bullseye" style="display: none; width: 1rem;"></i></button>
+ <button class="btn btn-outline-secondary btn-sm" onclick="changeView('next', false);" title="{{$next}}"><i class="fa fa-forward"></i></button>
</div>
- <button id="fullscreen-btn" type="button" class="btn btn-default btn-xs" onclick="makeFullScreen();"><i class="fa fa-expand"></i></button>
- <button id="inline-btn" type="button" class="btn btn-default btn-xs" onclick="makeFullScreen(false);"><i class="fa fa-compress"></i></button>
+ <button id="fullscreen-btn" type="button" class="btn btn-outline-secondary btn-sm" onclick="makeFullScreen();"><i class="fa fa-expand"></i></button>
+ <button id="inline-btn" type="button" class="btn btn-outline-secondary btn-sm" onclick="makeFullScreen(false);"><i class="fa fa-compress"></i></button>
</div>
<h2 id="title"></h2>
<div class="clear"></div>
diff --git a/view/tpl/events_tools_side.tpl b/view/tpl/events_tools_side.tpl
index 4f5ef2eb0..e22f95c1e 100755
--- a/view/tpl/events_tools_side.tpl
+++ b/view/tpl/events_tools_side.tpl
@@ -1,15 +1,17 @@
<div class="widget">
<h3>{{$title}}</h3>
- <ul class="nav nav-pills nav-stacked">
- <li><a href="#" onclick="exportDate(); return false;"><i class="fa fa-arrow-circle-o-down"></i>&nbsp;{{$export}}</a></li>
- <li><a href="#" onclick="openClose('event-upload-form'); return false;"><i class="fa fa-arrow-circle-o-up"></i>&nbsp;{{$import}}</a></li>
+ <ul class="nav nav-pills flex-column">
+ <li class="nav-item"><a class="nav-link" href="#" onclick="exportDate(); return false;"><i class="fa fa-arrow-circle-o-down"></i>&nbsp;{{$export}}</a></li>
+ <li class="nav-item"><a class="nav-link" href="#" onclick="openClose('event-upload-form'); return false;"><i class="fa fa-arrow-circle-o-up"></i>&nbsp;{{$import}}</a></li>
</ul>
- <div id="event-upload-form" style="display: none;">
- <form action="events" enctype="multipart/form-data" method="post" name="event-upload-form" id="event-upload-form">
- <div class="form-group">
- <input id="event-upload-choose" type="file" name="userfile" />
- </div>
- <button id="dbtn-submit" class="btn btn-primary btn-xs" type="submit" name="submit" >{{$submit}}</button>
- </form>
+ <div id="event-upload-form" class="sub-menu-wrapper">
+ <div class="sub-menu">
+ <form action="events" enctype="multipart/form-data" method="post" name="event-upload-form" id="event-upload-form">
+ <div class="form-group">
+ <input id="event-upload-choose" class="form-control-file w-100" type="file" name="userfile" />
+ </div>
+ <button id="dbtn-submit" class="btn btn-primary btn-sm" type="submit" name="submit" >{{$submit}}</button>
+ </form>
+ </div>
</div>
</div>
diff --git a/view/tpl/field_checkbox.tpl b/view/tpl/field_checkbox.tpl
index 6785e522a..f779f937c 100755
--- a/view/tpl/field_checkbox.tpl
+++ b/view/tpl/field_checkbox.tpl
@@ -1,6 +1,5 @@
- <div id="{{$field.0}}_container" class="form-group field checkbox">
+ <div id="{{$field.0}}_container" class="clearfix form-group checkbox">
<label for="id_{{$field.0}}">{{$field.1}}</label>
- <div class="pull-right"><input type="checkbox" name='{{$field.0}}' id='id_{{$field.0}}' value="1" {{if $field.2}}checked="checked"{{/if}} {{if $field.5}}{{$field.5}}{{/if}} /><label class="switchlabel" for='id_{{$field.0}}'> <span class="onoffswitch-inner" data-on='{{if $field.4}}{{$field.4.1}}{{/if}}' data-off='{{if $field.4}}{{$field.4.0}}{{/if}}'></span><span class="onoffswitch-switch"></span></label></div>
- <span class="help-block">{{$field.3}}</span>
+ <div class="float-right"><input type="checkbox" name='{{$field.0}}' id='id_{{$field.0}}' value="1" {{if $field.2}}checked="checked"{{/if}} {{if $field.5}}{{$field.5}}{{/if}} /><label class="switchlabel" for='id_{{$field.0}}'> <span class="onoffswitch-inner" data-on='{{if $field.4}}{{$field.4.1}}{{/if}}' data-off='{{if $field.4}}{{$field.4.0}}{{/if}}'></span><span class="onoffswitch-switch"></span></label></div>
+ <small class="form-text text-muted">{{$field.3}}</small>
</div>
- <div class="clear"></div>
diff --git a/view/tpl/field_combobox.tpl b/view/tpl/field_combobox.tpl
index 523595c0b..12d00a08d 100755
--- a/view/tpl/field_combobox.tpl
+++ b/view/tpl/field_combobox.tpl
@@ -1,17 +1,18 @@
- <div class='field combobox input form-group'>
- <label class="mainlabel" for='id_{{$field.0}}' id='id_{{$field.0}}_label'>{{$field.1}}</label>
- {{*
- <input id="id_{{$field.0}}" type="text" list="data_{{$field.0}}" >
- <datalist id="data_{{$field.0}}" >
- {{foreach $field.4 as $opt=>$val}}<option value="{{$val}}">{{/foreach}}
- </datalist>*}}
-
- <input id="id_{{$field.0}}" class="form-control" type="text" value="{{$field.2}}">
- <select id="select_{{$field.0}}" class="form-control" onChange="$('#id_{{$field.0}}').val($(this).val())">
- <option value="">{{$field.5}}</option>
- {{foreach $field.4 as $opt=>$val}}<option value="{{$val}}">{{$val}}</option>{{/foreach}}
- </select>
-
- <span class='field_help'>{{$field.3}}</span>
- </div>
+<div class="form-group">
+ <label class="" for='id_{{$field.0}}' id='id_{{$field.0}}_label'>{{$field.1}}</label>
+ <input class="form-control" id="id_{{$field.0}}" type="text" list="data_{{$field.0}}"{{if $field.5}} {{$field.5}}{{/if}}>
+ <datalist id="data_{{$field.0}}" >
+ {{foreach $field.4 as $opt=>$val}}
+ <option value="{{$val}}">
+ {{/foreach}}
+ </datalist>
+ {{**
+ <input id="id_{{$field.0}}" class="form-control" type="text" value="{{$field.2}}">
+ <select id="select_{{$field.0}}" class="form-control" onChange="$('#id_{{$field.0}}').val($(this).val())">
+ <option value="">{{$field.5}}</option>
+ {{foreach $field.4 as $opt=>$val}}<option value="{{$val}}">{{$val}}</option>{{/foreach}}
+ </select>
+ **}}
+ <span class='field_help'>{{$field.3}}</span>
+</div>
diff --git a/view/tpl/field_input.tpl b/view/tpl/field_input.tpl
index d6a7f56b2..65a837e5f 100755
--- a/view/tpl/field_input.tpl
+++ b/view/tpl/field_input.tpl
@@ -1,6 +1,5 @@
- <div id="id_{{$field.0}}_wrapper" class='form-group field input'>
- <label for='id_{{$field.0}}' id='label_{{$field.0}}'>{{$field.1}}{{if $field.4}}<span class="required"> {{$field.4}}</span>{{/if}}</label>
- <input class="form-control" name='{{$field.0}}' id='id_{{$field.0}}' type="text" value="{{$field.2}}"{{if $field.5}} {{$field.5}}{{/if}}>
- <span id='help_{{$field.0}}' class='help-block'>{{$field.3}}</span>
- <div class="clear"></div>
+ <div id="id_{{$field.0}}_wrapper" class="form-group">
+ <label for="id_{{$field.0}}" id="label_{{$field.0}}">{{$field.1}}{{if $field.4}}<span class="required"> {{$field.4}}</span>{{/if}}</label>
+ <input class="form-control" name="{{$field.0}}" id="id_{{$field.0}}" type="text" value="{{$field.2}}"{{if $field.5}} {{$field.5}}{{/if}}>
+ <small id="help_{{$field.0}}" class="form-text text-muted">{{$field.3}}</small>
</div>
diff --git a/view/tpl/field_intcheckbox.tpl b/view/tpl/field_intcheckbox.tpl
index 565f97760..abfe6e189 100755
--- a/view/tpl/field_intcheckbox.tpl
+++ b/view/tpl/field_intcheckbox.tpl
@@ -1,6 +1,5 @@
- <div class="form-group field checkbox">
- <label for='id_{{$field.0}}'>{{$field.1}}</label>
- <div class="pull-right"><input type="checkbox" name='{{$field.0}}' id='id_{{$field.0}}' value="{{$field.3}}" {{if $field.2}}checked="checked"{{/if}}><label class="switchlabel" for='id_{{$field.0}}'> <span class="onoffswitch-inner" data-on='{{if $field.5}}{{$field.5.1}}{{/if}}' data-off='{{if $field.5}}{{$field.5.0}}{{/if}}'></span><span class="onoffswitch-switch"></span> </label></div>
- <span class='help-block'>{{$field.4}}</span>
+ <div class="clearfix form-group checkbox">
+ <label for="id_{{$field.0}}">{{$field.1}}</label>
+ <div class="pull-right"><input type="checkbox" name="{{$field.0}}" id="id_{{$field.0}}" value="{{$field.3}}" {{if $field.2}}checked="checked"{{/if}}><label class="switchlabel" for="id_{{$field.0}}"> <span class="onoffswitch-inner" data-on="{{if $field.5}}{{$field.5.1}}{{/if}}" data-off="{{if $field.5}}{{$field.5.0}}{{/if}}"></span><span class="onoffswitch-switch"></span> </label></div>
+ <small class="form-text text-muted">{{$field.4}}</small>
</div>
- <div class="clear"></div>
diff --git a/view/tpl/field_password.tpl b/view/tpl/field_password.tpl
index 1643fa855..fa5e14582 100755
--- a/view/tpl/field_password.tpl
+++ b/view/tpl/field_password.tpl
@@ -1,5 +1,5 @@
- <div class='form-group field password'>
- <label for='id_{{$field.0}}'>{{$field.1}}</label>
- <input class="form-control" type='password' name='{{$field.0}}' id='id_{{$field.0}}' value="{{$field.2}}"{{if $field.5}} {{$field.5}}{{/if}}>{{if $field.4}} <span class="required">{{$field.4}}</span> {{/if}}
- <span id="help_{{$field.0}}" class="help-block">{{$field.3}}</span>
+ <div class="form-group">
+ <label for="id_{{$field.0}}">{{$field.1}}</label>
+ <input class="form-control" type="password" name="{{$field.0}}" id="id_{{$field.0}}" value="{{$field.2}}"{{if $field.5}} {{$field.5}}{{/if}}>{{if $field.4}} <span class="required">{{$field.4}}</span> {{/if}}
+ <small id="help_{{$field.0}}" class="form-text text-muted">{{$field.3}}</small>
</div>
diff --git a/view/tpl/field_select.tpl b/view/tpl/field_select.tpl
index 762447290..cda9a823a 100755
--- a/view/tpl/field_select.tpl
+++ b/view/tpl/field_select.tpl
@@ -1,7 +1,7 @@
- <div class='form-group field select'>
- <label for='id_{{$field.0}}'>{{$field.1}}</label>
- <select class="form-control" name='{{$field.0}}' id='id_{{$field.0}}'>
+ <div class="form-group">
+ <label for="id_{{$field.0}}">{{$field.1}}</label>
+ <select class="form-control" name="{{$field.0}}" id="id_{{$field.0}}">
{{foreach $field.4 as $opt=>$val}}<option value="{{$opt}}" {{if $opt==$field.2}}selected="selected"{{/if}}>{{$val}}</option>{{/foreach}}
</select>
- <span class='help-block'>{{$field.3}}</span>
+ <small class="form-text text-muted">{{$field.3}}</small>
</div>
diff --git a/view/tpl/field_textarea.tpl b/view/tpl/field_textarea.tpl
index 01fdc23f5..437dece93 100755
--- a/view/tpl/field_textarea.tpl
+++ b/view/tpl/field_textarea.tpl
@@ -1,5 +1,5 @@
- <div class='form-group field textarea'>
- <label for='id_{{$field.0}}'>{{$field.1}}</label>
- <textarea class="form-control" name='{{$field.0}}' id='id_{{$field.0}}' {{if $field.4}}{{$field.4}}{{/if}} >{{$field.2}}</textarea>
- <span class='help-block'>{{$field.3}}</span>
+ <div class="form-group">
+ <label for="id_{{$field.0}}">{{$field.1}}</label>
+ <textarea class="form-control" name="{{$field.0}}" id="id_{{$field.0}}" {{if $field.4}}{{$field.4}}{{/if}} >{{$field.2}}</textarea>
+ <small class="form-text text-muted">{{$field.3}}</small>
</div>
diff --git a/view/tpl/field_yesno.tpl b/view/tpl/field_yesno.tpl
index f5a909833..8a4cda55b 100755
--- a/view/tpl/field_yesno.tpl
+++ b/view/tpl/field_yesno.tpl
@@ -1,4 +1,4 @@
- <div class='field yesno'>
+ <div class='clearfix form-group'>
<label class="mainlabel" for='id_{{$field.0}}'>{{$field.1}}</label>
<div class='onoff' id="id_{{$field.0}}_onoff">
<input type="hidden" name='{{$field.0}}' id='id_{{$field.0}}' value="{{$field.2}}">
@@ -9,5 +9,5 @@
{{if $field.4}}{{$field.4.1}}{{else}}ON{{/if}}
</a>
</div>
- <span class='field_help'>{{$field.3}}</span>
+ <small class='form-text text-muted'>{{$field.3}}</small>
</div>
diff --git a/view/tpl/fileas_widget.tpl b/view/tpl/fileas_widget.tpl
index a92440cb0..a6a69b89c 100755
--- a/view/tpl/fileas_widget.tpl
+++ b/view/tpl/fileas_widget.tpl
@@ -2,10 +2,10 @@
<h3>{{$title}}</h3>
<div id="nets-desc">{{$desc}}</div>
- <ul class="nav nav-pills nav-stacked">
- <li><a href="{{$base}}"{{if $sel_all}} class="fileas-selected"{{/if}}>{{$all}}</a></li>
+ <ul class="nav nav-pills flex-column">
+ <li class="nav-item"><a class="nav-link{{if $sel_all}} active{{/if}}" href="{{$base}}">{{$all}}</a></li>
{{foreach $terms as $term}}
- <li><a href="{{$base}}?f=&file={{$term.name}}"{{if $term.selected}} class="fileas-selected"{{/if}}>{{$term.name}}</a></li>
+ <li class="nav-item"><a class="nav-link{{if $term.selected}} active{{/if}}" href="{{$base}}?f=&file={{$term.name}}">{{$term.name}}</a></li>
{{/foreach}}
</ul>
diff --git a/view/tpl/filer_dialog.tpl b/view/tpl/filer_dialog.tpl
index 71e075958..61860d10f 100755
--- a/view/tpl/filer_dialog.tpl
+++ b/view/tpl/filer_dialog.tpl
@@ -1,6 +1,19 @@
-<div class="item-filer-dialog">
-{{include file="field_combobox.tpl"}}
-<div class="settings-submit-wrapper" >
- <input id="filer_save" type="button" class="settings-submit" value="{{$submit}}" />
-</div>
+<div class="modal" id="item-filer-dialog">
+ <div class="modal-dialog" role="document">
+ <div class="modal-content">
+ <div class="modal-header">
+ <h4 class="modal-title">{{$title}}</h4>
+ <button type="button" class="close" data-dismiss="modal" aria-label="Close">
+ <span aria-hidden="true">&times;</span>
+ </button>
+ </div>
+ <div class="modal-body">
+ {{include file="field_combobox.tpl"}}
+ </div>
+ <div class="modal-footer">
+ <button type="button" class="btn btn-secondary" data-dismiss="modal">{{$cancel}}</button>
+ <button id="filer_save" type="button" class="btn btn-primary">{{$submit}}</button>
+ </div>
+ </div>
+ </div>
</div>
diff --git a/view/tpl/follow.tpl b/view/tpl/follow.tpl
index 9c19a288d..4def1415d 100755
--- a/view/tpl/follow.tpl
+++ b/view/tpl/follow.tpl
@@ -1,12 +1,10 @@
<div id="follow-sidebar" class="widget">
<h3>{{$connect}}</h3>
<form action="follow" method="post" />
- <div class="form-group">
- <div class="input-group">
- <input class="widget-input" type="text" name="url" title="{{$hint}}" placeholder="{{$desc}}" />
- <div class="input-group-btn">
- <button class="btn btn-default btn-sm" type="submit" name="submit" value="{{$follow}}"><i class="fa fa-plus"></i></button>
- </div>
+ <div class="input-group">
+ <input class="form-control form-control-sm" type="text" name="url" title="{{$hint}}" placeholder="{{$desc}}" />
+ <div class="input-group-btn">
+ <button class="btn btn-success" type="submit" name="submit" value="{{$follow}}" title="{{$follow}}"><i class="fa fa-fw fa-plus"></i></button>
</div>
</div>
</form>
@@ -14,4 +12,3 @@
<div class="usage-message" id="abook-usage-message">{{$abook_usage_message}}</div>
{{/if}}
</div>
-
diff --git a/view/tpl/generic_links_widget.tpl b/view/tpl/generic_links_widget.tpl
index d7c234a84..67801e666 100755
--- a/view/tpl/generic_links_widget.tpl
+++ b/view/tpl/generic_links_widget.tpl
@@ -2,9 +2,9 @@
{{if $title}}<h3>{{$title}}</h3>{{/if}}
{{if $desc}}<div class="desc">{{$desc}}</div>{{/if}}
- <ul class="nav nav-pills nav-stacked">
+ <ul class="nav nav-pills flex-column">
{{foreach $items as $item}}
- <li><a href="{{$item.url}}" class="{{if $item.selected}}active{{/if}}">{{$item.label}}</a></li>
+ <li class="nav-item"><a href="{{$item.url}}" class="nav-link{{if $item.selected}} active{{/if}}">{{$item.label}}</a></li>
{{/foreach}}
</ul>
diff --git a/view/tpl/generic_modal.tpl b/view/tpl/generic_modal.tpl
index 2bbea42b3..18279b6f7 100644
--- a/view/tpl/generic_modal.tpl
+++ b/view/tpl/generic_modal.tpl
@@ -2,12 +2,12 @@
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
- <button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button>
<h4 class="modal-title" id="generic-modal-title-{{$id}}">{{$title}}</h4>
+ <button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button>
</div>
<div class="modal-body" id="generic-modal-body-{{$id}}"></div>
<div class="modal-footer">
- <button id="generic-modal-cancel-{{$id}}" type="button" class="btn btn-default" data-dismiss="modal">{{$cancel}}</button>
+ <button id="generic-modal-cancel-{{$id}}" type="button" class="btn btn-outline-secondary" data-dismiss="modal">{{$cancel}}</button>
{{if $ok}}
<button id="generic-modal-ok-{{$id}}" type="button" class="btn btn-primary">{{$ok}}</button>
{{/if}}
diff --git a/view/tpl/group_drop.tpl b/view/tpl/group_drop.tpl
index 34d0096e0..627debc80 100755
--- a/view/tpl/group_drop.tpl
+++ b/view/tpl/group_drop.tpl
@@ -2,6 +2,6 @@
<a href="group/drop/{{$id}}?t={{$form_security_token}}"
onclick="return confirmDelete();"
id="group-delete-icon-{{$id}}"
- class="group-delete-icon btn btn-default" title="{{$delete}}" ><i class="fa fa-trash-o drop-icons"></i></a>
+ class="group-delete-icon btn btn-outline-secondary" title="{{$delete}}" ><i class="fa fa-trash-o drop-icons"></i></a>
</div>
<div class="group-delete-end"></div>
diff --git a/view/tpl/group_side.tpl b/view/tpl/group_side.tpl
index 35f79a07e..14f714ae9 100755
--- a/view/tpl/group_side.tpl
+++ b/view/tpl/group_side.tpl
@@ -1,20 +1,20 @@
<div class="widget" id="group-sidebar">
<h3>{{$title}}</h3>
<div>
- <ul class="nav nav-pills nav-stacked">
+ <ul class="nav nav-pills flex-column">
{{foreach $groups as $group}}
- <li>
+ <li class="nav-item nav-item-hack">
{{if $group.cid}}
- <i id="group-{{$group.id}}" class="widget-nav-pills-checkbox fa {{if $group.ismember}}fa-check-square-o{{else}}fa-square-o{{/if}}" onclick="contactgroupChangeMember('{{$group.id}}','{{$group.enc_cid}}'); return true;"></i>
+ <i id="group-{{$group.id}}" class="widget-nav-pills-checkbox fa fa-fw {{if $group.ismember}}fa-check-square-o{{else}}fa-square-o{{/if}}" onclick="contactgroupChangeMember('{{$group.id}}','{{$group.enc_cid}}'); return true;"></i>
{{/if}}
{{if $group.edit}}
- <a href="{{$group.edit.href}}" class="widget-nav-pills-icons" title="{{$edittext}}"><i class="fa fa-pencil"></i></a>
+ <a href="{{$group.edit.href}}" class="nav-link{{if $group.selected}} active{{/if}} widget-nav-pills-icons" title="{{$edittext}}"><i class="fa fa-fw fa-pencil"></i></a>
{{/if}}
- <a{{if $group.selected}} class="group-selected"{{/if}} href="{{$group.href}}">{{$group.text}}</a>
+ <a class="nav-link{{if $group.selected}} active{{/if}}" href="{{$group.href}}">{{$group.text}}</a>
</li>
{{/foreach}}
- <li>
- <a href="group/new" title="{{$createtext}}" ><i class="fa fa-plus-circle"></i> {{$createtext}}</a>
+ <li class="nav-item">
+ <a class="nav-link" href="group/new" title="{{$createtext}}" ><i class="fa fa-plus-circle"></i> {{$createtext}}</a>
</li>
</ul>
diff --git a/view/tpl/hdr.tpl b/view/tpl/hdr.tpl
index 6a14906f6..29137c740 100644
--- a/view/tpl/hdr.tpl
+++ b/view/tpl/hdr.tpl
@@ -1,5 +1,3 @@
-<div id="banner" class="hidden-sm hidden-xs">{{$banner}}</div>
-
-<ul id="nav-notifications-template" rel="template">
- <li class="{5}"><a href="{0}" title="{2} {3}"><img class="dropdown-menu-img-sm" data-src="{1}"><span class="contactname">{2}</span><span class="dropdown-sub-text">{3}<br>{4}</span></a></li>
-</ul>
+<div id="navbar-notifications-template" rel="template" style="display:none;">
+ <a class="dropdown-item clearfix dropdown-notification {5}" href="{0}" title="{2} {3}"><img class="menu-img-3" data-src="{1}"><span class="contactname">{2}</span><span class="dropdown-sub-text">{3}<br>{4}</span></a>
+</div> \ No newline at end of file
diff --git a/view/tpl/help.tpl b/view/tpl/help.tpl
index 10e0a4957..d36494123 100644
--- a/view/tpl/help.tpl
+++ b/view/tpl/help.tpl
@@ -1,11 +1,23 @@
<div id="help-content" class="generic-content-wrapper">
- <div class="section-title-wrapper">
+ <div class="clearfix section-title-wrapper">
+ <div class="pull-right">
+ <div class="btn-group">
+ <button type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown">
+ <i class="fa fa-language" style="font-size: 1.4em;"></i>
+ </button>
+ <div class="dropdown-menu dropdown-menu-right flex-column lang-selector">
+ <a class="dropdown-item lang-choice" href="/help">de</a>
+ <a class="dropdown-item lang-choice" href="/help">en</a>
+ <a class="dropdown-item lang-choice" href="/help">es</a>
+ </div>
+ </div>
+ </div>
<h2>{{$title}}: {{$heading}}</h2>
</div>
<div class="section-content-wrapper" id="doco-content">
<h3 id="doco-top-toc-heading">
<span class="fakelink" onclick="docoTocToggle(); return false;">
- <i class="fakelink fa fa-caret-right" id="doco-toc-toggle"></i>
+ <i class="fa fa-fw fa-caret-right fakelink" id="doco-toc-toggle"></i>
{{$tocHeading}}
</span>
</h3>
@@ -13,21 +25,6 @@
{{$content}}
</div>
</div>
-
<script>
- // Generate the table of contents in the side nav menu (see view/tpl/help.tpl)
- $(document).ready(function () {
- $('#doco-top-toc').toc({content: "#doco-content", headings: "h3,h4,h5,h6"});
- });
-
- function docoTocToggle() {
- if($('#doco-top-toc').is(':visible')) {
- $('#doco-toc-toggle').removeClass('fa-caret-down').addClass('fa-caret-right');
- } else {
- $('#doco-toc-toggle').removeClass('fa-caret-right').addClass('fa-caret-down');
- }
- $('#doco-top-toc').toggle();
-
- return false;
- }
+ var help_language = '{{$language}}'
</script>
diff --git a/view/tpl/install.tpl b/view/tpl/install.tpl
index 0e77aa97b..5ab722b12 100755
--- a/view/tpl/install.tpl
+++ b/view/tpl/install.tpl
@@ -1,9 +1,15 @@
-<h1>{{$title}}</h1>
-<h2>{{$pass}}</h2>
+<div class="container mt-4 mb-4">
+ <div class="jumbotron">
+ <h1>{{$title}}</h1>
+ <hr class="my-4">
+ <h2><i class="fa fa-{{$icon}}"></i>&nbsp; {{$pass}}</h2>
+ </div>
+ {{if $status}}
+ <div class="alert alert-danger">{{$status}}</div>
+ {{/if}}
-{{if $status}}
-<h3 class="error-message">{{$status}}</h3>
-{{/if}}
-
-{{$text}}
+ <div class="alert alert-info">{{$text}}</div>
+ <br>
+ {{$what_next}}
+</div>
diff --git a/view/tpl/install_checks.tpl b/view/tpl/install_checks.tpl
index ad0aef6a3..8bbb9f26d 100755
--- a/view/tpl/install_checks.tpl
+++ b/view/tpl/install_checks.tpl
@@ -1,24 +1,29 @@
-<h1>{{$title}}</h1>
-<h2>{{$pass}}</h2>
-<form action="{{$baseurl}}/index.php?q=setup" method="post">
-<table>
-{{foreach $checks as $check}}
- <tr><td>{{$check.title}} </td><td><i class="fa {{if $check.status}}fa-check-square-o{{else}}{{if $check.required}}fa-square-o{{else}}fa-exclamation{{/if}}{{/if}}"></i></td><td>{{if $check.required}}(required){{/if}}</td></tr>
- {{if $check.help}}
- <tr><td colspan="3"><blockquote>{{$check.help}}</blockquote></td></tr>
- {{/if}}
-{{/foreach}}
-</table>
+<div class="container mt-4 mb-4">
+ <div class="jumbotron">
+ <h1>{{$title}}</h1>
+ <hr class="my-4">
+ <h2><i class="fa fa-heartbeat"></i>&nbsp; {{$pass}}</h2>
+ </div>
+ <form action="{{$baseurl}}/index.php?q=setup" method="post">
+ <table class="table">
+ {{foreach $checks as $check}}
+ <tr><td{{if ! $check.status}} class="text-danger"{{/if}}>{{$check.title}}</td><td><i class="fa {{if $check.status}}fa-check-square-o{{else}}{{if $check.required}}fa-square-o{{else}}fa-exclamation text-danger{{/if}}{{/if}}"></i></td><td>{{if $check.required}}(required){{/if}}</td></tr>
+ {{if $check.help}}
+ <tr><td colspan="3" class="border-top-0 pt-0 pb-0"><div class="alert alert-info">{{$check.help}}</div></td></tr>
+ {{/if}}
+ {{/foreach}}
+ </table>
-{{if $phpath}}
- <input type="hidden" name="phpath" value="{{$phpath}}">
-{{/if}}
+ {{if $phpath}}
+ <input type="hidden" name="phpath" value="{{$phpath}}">
+ {{/if}}
-{{if $passed}}
- <input type="hidden" name="pass" value="2">
- <input type="submit" value="{{$next}}">
-{{else}}
- <input type="hidden" name="pass" value="1">
- <input type="submit" value="{{$reload}}">
-{{/if}}
-</form>
+ {{if $passed}}
+ <input type="hidden" name="pass" value="2">
+ <button class="btn btn-success" type="submit"><i class="fa fa-check"></i> {{$next}}</button>
+ {{else}}
+ <input type="hidden" name="pass" value="1">
+ <button class="btn btn-warning" type="submit"><i class="fa fa-refresh"></i> {{$reload}}</button>
+ {{/if}}
+ </form>
+</div>
diff --git a/view/tpl/install_db.tpl b/view/tpl/install_db.tpl
index 1a58de129..8b9023443 100755
--- a/view/tpl/install_db.tpl
+++ b/view/tpl/install_db.tpl
@@ -1,30 +1,31 @@
-<h1>{{$title}}</h1>
-<h2>{{$pass}}</h2>
-
-
-<p>
-{{$info_01}}<br>
-{{$info_02}}<br>
-{{$info_03}}
-</p>
-
-{{if $status}}
-<h3 class="error-message">{{$status}}</h3>
-{{/if}}
-
-<form id="install-form" action="{{$baseurl}}/setup" method="post">
-
-<input type="hidden" name="phpath" value="{{$phpath}}" />
-<input type="hidden" name="pass" value="3" />
-
-{{include file="field_input.tpl" field=$dbhost}}
-{{include file="field_input.tpl" field=$dbport}}
-{{include file="field_input.tpl" field=$dbuser}}
-{{include file="field_password.tpl" field=$dbpass}}
-{{include file="field_input.tpl" field=$dbdata}}
-{{include file="field_select.tpl" field=$dbtype}}
-
-<input id="install-submit" type="submit" name="submit" value="{{$submit}}" />
-
-</form>
+<div class="container mt-4 mb-4">
+ <div class="jumbotron">
+ <h1>{{$title}}</h1>
+ <hr class="my-4">
+ <h2><i class="fa fa-database"></i>&nbsp; {{$pass}}</h2>
+ </div>
+ <div class="alert alert-info">
+ {{$info_01}}<br>
+ {{$info_02}}<br>
+ {{$info_03}}
+ </div>
+
+ {{if $status}}
+ <div class="alert alert-danger">{{$status}}</div>
+ {{/if}}
+
+ <form id="install-form" action="{{$baseurl}}/setup" method="post">
+ <input type="hidden" name="phpath" value="{{$phpath}}" />
+ <input type="hidden" name="pass" value="3" />
+
+ {{include file="field_input.tpl" field=$dbhost}}
+ {{include file="field_input.tpl" field=$dbport}}
+ {{include file="field_input.tpl" field=$dbuser}}
+ {{include file="field_password.tpl" field=$dbpass}}
+ {{include file="field_input.tpl" field=$dbdata}}
+ {{include file="field_select.tpl" field=$dbtype}}
+
+ <button class="btn btn-primary" id="install-submit" type="submit" name="submit" value="{{$submit}}">{{$submit}}</button>
+ </form>
+</div>
diff --git a/view/tpl/install_settings.tpl b/view/tpl/install_settings.tpl
index f7a0108a8..b62f8508b 100755
--- a/view/tpl/install_settings.tpl
+++ b/view/tpl/install_settings.tpl
@@ -1,29 +1,28 @@
-<h1>{{$title}}</h1>
-<h2>{{$pass}}</h2>
-
-
-{{if $status}}
-<h3 class="error-message">{{$status}}</h3>
-{{/if}}
-
-<form id="install-form" action="{{$baseurl}}/setup" method="post">
-
-<input type="hidden" name="phpath" value="{{$phpath}}" />
-<input type="hidden" name="dbhost" value="{{$dbhost}}" />
-<input type="hidden" name="dbport" value="{{$dbport}}" />
-<input type="hidden" name="dbuser" value="{{$dbuser}}" />
-<input type="hidden" name="dbpass" value="{{$dbpass}}" />
-<input type="hidden" name="dbdata" value="{{$dbdata}}" />
-<input type="hidden" name="dbtype" value="{{$dbtype}}" />
-<input type="hidden" name="pass" value="4" />
-
-{{include file="field_input.tpl" field=$adminmail}}
-{{include file="field_input.tpl" field=$siteurl}}
-{{include file="field_select.tpl" field=$server_role}}
-
-{{include file="field_select_grouped.tpl" field=$timezone}}
-
-<input id="install-submit" type="submit" name="submit" value="{{$submit}}" />
-
-</form>
-
+<div class="container mt-4 mb-4">
+ <div class="jumbotron">
+ <h1>{{$title}}</h1>
+ <hr class="my-4">
+ <h2><i class="fa fa-cogs"></i>&nbsp; {{$pass}}</h2>
+ </div>
+
+ {{if $status}}
+ <div class="alert alert-danger">{{$status}}</div>
+ {{/if}}
+
+ <form id="install-form" action="{{$baseurl}}/setup" method="post">
+ <input type="hidden" name="phpath" value="{{$phpath}}" />
+ <input type="hidden" name="dbhost" value="{{$dbhost}}" />
+ <input type="hidden" name="dbport" value="{{$dbport}}" />
+ <input type="hidden" name="dbuser" value="{{$dbuser}}" />
+ <input type="hidden" name="dbpass" value="{{$dbpass}}" />
+ <input type="hidden" name="dbdata" value="{{$dbdata}}" />
+ <input type="hidden" name="dbtype" value="{{$dbtype}}" />
+ <input type="hidden" name="pass" value="4" />
+
+ {{include file="field_input.tpl" field=$adminmail}}
+ {{include file="field_input.tpl" field=$siteurl}}
+ {{include file="field_select_grouped.tpl" field=$timezone}}
+
+ <button class="btn btn-primary" id="install-submit" type="submit" name="submit" value="{{$submit}}">{{$submit}}</button>
+ </form>
+</div>
diff --git a/view/tpl/item_attach.tpl b/view/tpl/item_attach.tpl
index 83cc9a3cd..95e38c0bd 100644
--- a/view/tpl/item_attach.tpl
+++ b/view/tpl/item_attach.tpl
@@ -1,5 +1,5 @@
{{if $attaches}}
{{foreach $attaches as $a}}
-<li><a href="{{$a.url}}" title="{{$a.title}}"><i class="fa {{$a.icon}} attach-icons"></i>&nbsp;{{$a.label}}</a></li>
+<a class="dropdown-item" href="{{$a.url}}" title="{{$a.title}}"><i class="fa {{$a.icon}} attach-icons"></i>&nbsp;{{$a.label}}</a>
{{/foreach}}
{{/if}}
diff --git a/view/tpl/item_binary.tpl b/view/tpl/item_binary.tpl
new file mode 100644
index 000000000..b19f7e7dd
--- /dev/null
+++ b/view/tpl/item_binary.tpl
@@ -0,0 +1,3 @@
+<p>
+<center><a class="zrl" href="{{$url}}"><button class="btn btn-warning fakelink">{{$download}}</button></a></center>
+</p>
diff --git a/view/tpl/item_categories.tpl b/view/tpl/item_categories.tpl
index 9ff291747..fa07fa39f 100644
--- a/view/tpl/item_categories.tpl
+++ b/view/tpl/item_categories.tpl
@@ -1,8 +1,8 @@
{{if $categories}}
-<div class="categorytags">
+<!--div class="categorytags"-->
{{foreach $categories as $cat}}
-<span class="item-category"><i class="fa fa-asterisk cat-icons"></i>{{if $cat.url}}<a href="{{$cat.url}}">{{$cat.term}}</a>{{else}}{{$cat.term}}{{/if}}</span>
+<span class="item-category badge badge-pill badge-warning"><i class="fa fa-asterisk"></i>&nbsp;{{if $cat.url}}<a class="text-dark" href="{{$cat.url}}">{{$cat.term}}</a>{{else}}{{$cat.term}}{{/if}}</span>
{{/foreach}}
-</div>
+<!--/div-->
{{/if}}
diff --git a/view/tpl/item_filer.tpl b/view/tpl/item_filer.tpl
index 0cde5caf7..4eb621f93 100644
--- a/view/tpl/item_filer.tpl
+++ b/view/tpl/item_filer.tpl
@@ -1,8 +1,8 @@
{{if $categories}}
-<div class="filesavetags">
+<!--div class="filesavetags"-->
{{foreach $categories as $cat}}
-<span class="item-category"><i class="fa fa-folder cat-icons"></i>&nbsp;{{$cat.term}}&nbsp;<a href="{{$cat.removelink}}" class="category-remove-link" title="{{$remove}}"><i class="fa fa-trash-o drop-icons"></i></a></span>
+<span class="item-category badge badge-pill badge-danger"><i class="fa fa-folder-o"></i>&nbsp;{{$cat.term}}&nbsp;<a href="{{$cat.removelink}}" class="text-white" title="{{$remove}}"><i class="fa fa-close"></i></a></span>
{{/foreach}}
-</div>
+<!--/div-->
{{/if}}
diff --git a/view/tpl/item_import.tpl b/view/tpl/item_import.tpl
index 65de7fcaf..e976417e1 100755
--- a/view/tpl/item_import.tpl
+++ b/view/tpl/item_import.tpl
@@ -1,7 +1,7 @@
<h2>{{$title}}</h2>
<form action="import_items" method="post" enctype="multipart/form-data" id="import-channel-form">
-
+ <input type="hidden" name="form_security_token" value="{{$form_security_token}}">
<div id="import-desc" class="descriptive-paragraph">{{$desc}}</div>
<label for="import-filename" id="label-import-filename" class="import-label" >{{$label_filename}}</label>
@@ -10,6 +10,4 @@
<input type="submit" name="submit" id="import-submit-button" value="{{$submit}}" />
<div id="import-submit-end" class="import-field-end"></div>
-
</form>
-
diff --git a/view/tpl/jot-header.tpl b/view/tpl/jot-header.tpl
index d846f3e34..2f9dd9f15 100755
--- a/view/tpl/jot-header.tpl
+++ b/view/tpl/jot-header.tpl
@@ -6,11 +6,11 @@ var pretext = '{{$pretext}}';
function initEditor(cb){
if (editor==false){
- $("#profile-jot-text-loading").spin('small').show();
+ $("#profile-jot-text-loading").show();
{{$geotag}}
if(plaintext == 'none') {
- $("#profile-jot-text-loading").spin(false).hide();
- $("#profile-jot-text").css({ 'height': 200, 'color': '#000', 'line-height': 'inherit' });
+ $("#profile-jot-text-loading").hide();
+ $("#profile-jot-text").css({ 'height': 200 });
{{if $bbco_autocomplete}}
$("#profile-jot-text").bbco_autocomplete('{{$bbco_autocomplete}}'); // autocomplete bbcode
{{/if}}
@@ -80,7 +80,7 @@ function initEditor(cb){
ed.onInit.add(function(ed) {
ed.pasteAsPlainText = true;
- $("#profile-jot-text-loading").spin(false).hide();
+ $("#profile-jot-text-loading").hide();
$(".jothidden").show();
if (typeof cb!="undefined") cb();
});
@@ -100,77 +100,76 @@ function enableOnUser(){
initEditor();
}
</script>
-<script type="text/javascript" src="{{$baseurl}}/view/js/ajaxupload.js" ></script>
+
+<script src="library/blueimp_upload/js/vendor/jquery.ui.widget.js"></script>
+<script src="library/blueimp_upload/js/jquery.iframe-transport.js"></script>
+<script src="library/blueimp_upload/js/jquery.fileupload.js"></script>
+
<script>
+var activeCommentID = 0;
+var activeCommentText = '';
+
$(document).ready(function() {
/* enable tinymce on focus and click */
$("#profile-jot-text").focus(enableOnUser);
$("#profile-jot-text").click(enableOnUser);
- var upload_title = $('#wall-image-upload').attr('title');
- var attach_title = $('#wall-file-upload').attr('title');
- try {
- var uploader = new window.AjaxUpload('wall-image-upload',
- { action: '{{$baseurl}}/wall_upload/{{$nickname}}',
- name: 'userfile',
- title: upload_title,
- onSubmit: function(file,ext) { $('#profile-rotator').spin('tiny'); },
- onComplete: function(file,response) {
- addeditortext(response);
- $('#jot-media').val($('#jot-media').val() + response);
- $('#profile-rotator').spin(false);
- }
- });
- } catch (e) {
- }
- try {
- var uploader_sub = new window.AjaxUpload('wall-image-upload-sub',
- { action: '{{$baseurl}}/wall_upload/{{$nickname}}',
- name: 'userfile',
- title: upload_title,
- onSubmit: function(file,ext) { $('#profile-rotator').spin('tiny'); },
- onComplete: function(file,response) {
- addeditortext(response);
- $('#jot-media').val($('#jot-media').val() + response);
- $('#profile-rotator').spin(false);
- }
- });
- } catch(e) {
- }
- try {
- var file_uploader = new window.AjaxUpload('wall-file-upload',
- { action: '{{$baseurl}}/wall_attach/{{$nickname}}',
- name: 'userfile',
- title: attach_title,
- onSubmit: function(file,ext) { $('#profile-rotator').spin('tiny'); },
- onComplete: function(file,response) {
- addeditortext(response);
- $('#jot-media').val($('#jot-media').val() + response);
- $('#profile-rotator').spin(false);
- }
- });
- } catch(e) {
- }
- try {
- var file_uploader_sub = new window.AjaxUpload('wall-file-upload-sub',
- { action: '{{$baseurl}}/wall_attach/{{$nickname}}',
- name: 'userfile',
- title: attach_title,
- onSubmit: function(file,ext) { $('#profile-rotator').spin('tiny'); },
- onComplete: function(file,response) {
- addeditortext(response);
- $('#jot-media').val($('#jot-media').val() + response);
- $('#profile-rotator').spin(false);
- }
- });
- } catch(e) {
- }
-
-
+
+ $('#invisible-wall-file-upload').fileupload({
+ url: 'wall_attach/{{$nickname}}',
+ dataType: 'json',
+ dropZone: $('#profile-jot-text'),
+ maxChunkSize: 4 * 1024 * 1024,
+ add: function(e,data) {
+ $('#profile-rotator').show();
+ data.submit();
+ },
+ done: function(e,data) {
+ addeditortext(data.result.message);
+ $('#jot-media').val($('#jot-media').val() + data.result.message);
+ },
+ stop: function(e,data) {
+ preview_post();
+ $('#profile-rotator').hide();
+ },
+ });
+
+ $('#wall-file-upload').click(function(event) { event.preventDefault(); $('#invisible-wall-file-upload').trigger('click'); return false;});
+ $('#wall-file-upload-sub').click(function(event) { event.preventDefault(); $('#invisible-wall-file-upload').trigger('click'); return false;});
+
// call initialization file
if (window.File && window.FileList && window.FileReader) {
DragDropUploadInit();
}
+
+
+ $('#invisible-comment-upload').fileupload({
+ url: 'wall_attach/{{$nickname}}',
+ dataType: 'json',
+ maxChunkSize: 4 * 1024 * 1024,
+ add: function(e,data) {
+
+ var tmpStr = $("#comment-edit-text-" + activeCommentID).val();
+ if(tmpStr == activeCommentText) {
+ tmpStr = "";
+ $("#comment-edit-text-" + activeCommentID).addClass("comment-edit-text-full");
+ $("#comment-edit-text-" + activeCommentID).removeClass("comment-edit-text-empty");
+ openMenu("comment-tools-" + activeCommentID);
+ $("#comment-edit-text-" + activeCommentID).val(tmpStr);
+ }
+ data.submit();
+ },
+
+ done: function(e,data) {
+ textarea = document.getElementById("comment-edit-text-" + activeCommentID);
+ textarea.value = textarea.value + data.result.message;
+ },
+ stop: function(e,data) {
+ $('body').css('cursor', 'auto');
+ preview_comment(activeCommentID);
+ activeCommentID = 0;
+ },
+ });
});
function deleteCheckedItems() {
@@ -205,10 +204,11 @@ function enableOnUser(){
reply = prompt("{{$linkurl}}");
if(reply && reply.length) {
reply = bin2hex(reply);
- $('#profile-rotator').spin('tiny');
+ $('#profile-rotator').show();
$.get('{{$baseurl}}/linkinfo?f=&binurl=' + reply, function(data) {
addeditortext(data);
- $('#profile-rotator').spin(false);
+ preview_post();
+ $('#profile-rotator').hide();
});
}
}
@@ -247,18 +247,23 @@ function enableOnUser(){
}
- function jotShare(id) {
- if ($('#jot-popup').length != 0) $('#jot-popup').show();
+ function jotShare(id,post_type) {
+ if(post_type == 6) {
+ window.location.href = 'rpost?f=&post_id='+id;
+ }
+ else {
+ if ($('#jot-popup').length != 0) $('#jot-popup').show();
- $('#like-rotator-' + id).spin('tiny');
- $.get('{{$baseurl}}/share/' + id, function(data) {
- if (!editor) $("#profile-jot-text").val("");
- initEditor(function(){
- addeditortext(data);
- $('#like-rotator-' + id).spin(false);
- $(window).scrollTop(0);
+ $('#like-rotator-' + id).show();
+ $.get('{{$baseurl}}/share/' + id, function(data) {
+ if (!editor) $("#profile-jot-text").val("");
+ initEditor(function(){
+ addeditortext(data);
+ $('#like-rotator-' + id).hide();
+ $(window).scrollTop(0);
+ });
});
- });
+ }
}
function linkdropper(event) {
@@ -291,31 +296,33 @@ function enableOnUser(){
function linkdrop(event) {
var reply = event.dataTransfer.getData("text/uri-list");
- event.preventDefault();
- var editwin = '#' + event.target.id;
- var commentwin = false;
- if(editwin) {
- commentwin = ((editwin.indexOf('comment') >= 0) ? true : false);
- if(commentwin) {
- var commentid = editwin.substring(editwin.lastIndexOf('-') + 1);
- commentOpen(document.getElementById(event.target.id),commentid);
+ if(reply) {
+ event.preventDefault();
+ var editwin = '#' + event.target.id;
+ var commentwin = false;
+ if(editwin) {
+ commentwin = ((editwin.indexOf('comment') >= 0) ? true : false);
+ if(commentwin) {
+ var commentid = editwin.substring(editwin.lastIndexOf('-') + 1);
+ commentOpen(document.getElementById(event.target.id),commentid);
+ }
}
}
if(reply && reply.length) {
reply = bin2hex(reply);
- $('#profile-rotator').spin('tiny');
+ $('#profile-rotator').show();
$.get('{{$baseurl}}/linkinfo?f=&binurl=' + reply, function(data) {
if(commentwin) {
$(editwin).val( $(editwin).val() + data );
- $('#profile-rotator').spin(false);
+ $('#profile-rotator').hide();
}
else {
if (!editor) $("#profile-jot-text").val("");
initEditor(function(){
addeditortext(data);
- $('#profile-rotator').spin(false);
+ $('#profile-rotator').hide();
});
}
});
@@ -340,18 +347,12 @@ function enableOnUser(){
}
function itemFiler(id) {
-
- var bordercolor = $("input").css("border-color");
+ if($('#item-filer-dialog').length)
+ $('#item-filer-dialog').remove();
$.get('filer/', function(data){
- $.colorbox({html:data});
- $("#id_term").keypress(function(){
- $(this).css("border-color",bordercolor);
- })
- $("#select_term").change(function(){
- $("#id_term").css("border-color",bordercolor);
- })
-
+ $('body').append(data);
+ $('#item-filer-dialog').modal('show');
$("#filer_save").click(function(e){
e.preventDefault();
reply = $("#id_term").val();
@@ -359,12 +360,8 @@ function enableOnUser(){
commentBusy = true;
$('body').css('cursor', 'wait');
$.get('{{$baseurl}}/filer/' + id + '?term=' + reply, NavUpdate);
-// if(timer) clearTimeout(timer);
-// timer = setTimeout(NavUpdate,3000);
liking = 1;
- $.colorbox.close();
- } else {
- $("#id_term").css("border-color","#FF0000");
+ $('#item-filer-dialog').modal('hide');
}
return false;
});
@@ -428,7 +425,7 @@ function enableOnUser(){
});
getPhotoAlbumList();
$('#embedPhotoModalBodyAlbumDialog').off('click');
- $('#embedPhotoModal').modal();
+ $('#embedPhotoModal').modal('show');
};
var choosePhotoFromAlbum = function (album) {
@@ -437,13 +434,13 @@ function enableOnUser(){
if (data['status']) {
$('#embedPhotoModalLabel').html("{{$modalchooseimages}}");
$('#embedPhotoModalBodyAlbumDialog').html('\
- <div><ul class="nav">\n\
- <li><a href="#" onclick="initializeEmbedPhotoDialog();return false;">\n\
+ <div><div class="nav nav-pills flex-column">\n\
+ <li class="nav-item"><a class="nav-link" href="#" onclick="initializeEmbedPhotoDialog();return false;">\n\
<i class="fa fa-chevron-left"></i>&nbsp\n\
{{$modaldiffalbum}}\n\
</a>\n\
</li>\n\
- </ul><br></div>')
+ </div><br></div>')
$('#embedPhotoModalBodyAlbumDialog').append(data['content']);
$('#embedPhotoModalBodyAlbumDialog').click(function (evt) {
evt.preventDefault();
@@ -453,8 +450,8 @@ function enableOnUser(){
$(imageparent).toggleClass('embed-photo-selected-photo');
}
});
- $('#embedPhotoModalBodyAlbumListDialog').addClass('hide');
- $('#embedPhotoModalBodyAlbumDialog').removeClass('hide');
+ $('#embedPhotoModalBodyAlbumListDialog').addClass('d-none');
+ $('#embedPhotoModalBodyAlbumDialog').removeClass('d-none');
$('#embed-photo-OKButton').click(function () {
$('.embed-photo-selected-photo').each(function (index) {
var href = $(this).attr('href');
@@ -462,6 +459,7 @@ function enableOnUser(){
function(ddata) {
if (ddata['status']) {
addeditortext(ddata['photolink']);
+ preview_post();
} else {
window.console.log("{{$modalerrorlink}}" + ':' + ddata['errormsg']);
}
@@ -487,17 +485,17 @@ function enableOnUser(){
if (data['status']) {
var albums = data['albumlist']; //JSON.parse(data['albumlist']);
$('#embedPhotoModalLabel').html("{{$modalchoosealbum}}");
- $('#embedPhotoModalBodyAlbumList').html('<ul class="nav"></ul>');
+ $('#embedPhotoModalBodyAlbumList').html('<ul class="nav nav-pills flex-column"></ul>');
for(var i=0; i<albums.length; i++) {
var albumName = albums[i].text;
var jsAlbumName = albums[i].jstext;
- var albumLink = '<li>';
- albumLink += '<a href="#" onclick="choosePhotoFromAlbum(\'' + jsAlbumName + '\'); return false;">' + albumName + '</a>';
+ var albumLink = '<li class="nav-item">';
+ albumLink += '<a class="nav-link" href="#" onclick="choosePhotoFromAlbum(\'' + jsAlbumName + '\'); return false;">' + albumName + '</a>';
albumLink += '</li>';
$('#embedPhotoModalBodyAlbumList').find('ul').append(albumLink);
}
- $('#embedPhotoModalBodyAlbumDialog').addClass('hide');
- $('#embedPhotoModalBodyAlbumListDialog').removeClass('hide');
+ $('#embedPhotoModalBodyAlbumDialog').addClass('d-none');
+ $('#embedPhotoModalBodyAlbumListDialog').removeClass('d-none');
} else {
window.console.log("{{$modalerrorlist}}" + ':' + data['errormsg']);
}
@@ -507,32 +505,20 @@ function enableOnUser(){
};
//
- // initialize
+ // initialize drag-drop
function DragDropUploadInit() {
var filedrag = $("#profile-jot-text");
- // is XHR2 available?
- var xhr = new XMLHttpRequest();
- if (xhr.upload) {
-
- // file drop
+ // file drop
filedrag.on("dragover", DragDropUploadFileHover);
filedrag.on("dragleave", DragDropUploadFileHover);
filedrag.on("drop", DragDropUploadFileSelectHandler);
- }
-
- window.filesToUpload = 0;
- window.fileUploadsCompleted = 0;
-
-
}
// file drag hover
function DragDropUploadFileHover(e) {
- e.stopPropagation();
- e.preventDefault();
e.target.className = (e.type == "dragover" ? "hover" : "");
}
@@ -541,49 +527,12 @@ function enableOnUser(){
// cancel event and hover styling
DragDropUploadFileHover(e);
- if (!editor) $("#profile-jot-text").val("");
-
-
- // fetch FileList object
- var files = e.target.files || e.originalEvent.dataTransfer.files;
- // process all File objects
- for (var i = 0, f; f = files[i]; i++) {
- DragDropUploadFile(f, i);
- }
-
- }
-
- // upload files
- function DragDropUploadFile(file, idx) {
-
- window.filesToUpload = window.filesToUpload + 1;
-
- var xhr = new XMLHttpRequest();
- xhr.withCredentials = true; // Include the SESSION cookie info for authentication
- (xhr.upload || xhr).addEventListener('progress', function (e) {
- $('#profile-rotator').spin('tiny');
- });
- xhr.addEventListener('load', function (e) {
- //console.log('xhr upload complete', e);
- window.fileUploadsCompleted = window.fileUploadsCompleted + 1;
-
- initEditor(function() {
- addeditortext(xhr.responseText);
- });
-
- $('#jot-media').val($('#jot-media').val() + xhr.responseText);
- // When all the uploads have completed, refresh the page
- if (window.filesToUpload > 0 && window.fileUploadsCompleted === window.filesToUpload) {
- $('#profile-rotator').spin(false);
- window.fileUploadsCompleted = window.filesToUpload = 0;
- }
- });
- // POST to the wall_upload endpoint
- xhr.open('post', '{{$baseurl}}/wall_attach/{{$nickname}}', true);
+ // open editor if it isn't yet initialised
+ if (!editor) {
+ initEditor();
+ }
+ linkdrop(e);
- var data = new FormData();
- data.append('userfile', file);
- xhr.send(data);
}
</script>
diff --git a/view/tpl/jot.tpl b/view/tpl/jot.tpl
index 377eef453..13e7602be 100755
--- a/view/tpl/jot.tpl
+++ b/view/tpl/jot.tpl
@@ -1,3 +1,5 @@
+<input id="invisible-wall-file-upload" type="file" name="files" style="visibility:hidden;position:absolute;top:-50;left:-50;width:0;height:0;" multiple>
+<input id="invisible-comment-upload" type="file" name="files" style="visibility:hidden;position:absolute;top:-50;left:-50;width:0;height:0;" multiple>
<form id="profile-jot-form" action="{{$action}}" method="post" class="acl-form" data-form_id="profile-jot-form" data-allow_cid='{{$allow_cid}}' data-allow_gid='{{$allow_gid}}' data-deny_cid='{{$deny_cid}}' data-deny_gid='{{$deny_gid}}'>
{{$mimeselect}}
{{$layoutselect}}
@@ -6,7 +8,7 @@
<span class="channel-id-select-desc">{{$id_seltext}}</span> {{$id_select}}
</div>
{{/if}}
- <div id="profile-jot-wrapper">
+ <div class="mb-4" id="profile-jot-wrapper">
{{if $parent}}
<input type="hidden" name="parent" value="{{$parent}}" />
{{/if}}
@@ -31,7 +33,7 @@
</div>
{{/if}}
<div id="jot-title-wrap" class="jothidden">
- <input name="title" id="jot-title" type="text" placeholder="{{$placeholdertitle}}" tabindex=1 value="{{$title}}">
+ <input name="title" id="jot-title" type="text" placeholder="{{$placeholdertitle}}" tabindex="1" value="{{$title}}">
</div>
{{if $catsenabled}}
<div id="jot-category-wrap" class="jothidden">
@@ -39,147 +41,152 @@
</div>
{{/if}}
<div id="jot-text-wrap">
- <textarea class="profile-jot-text" id="profile-jot-text" name="body" tabindex=2 placeholder="{{$share}}" ondragenter="linkdropper(event);" ondragover="linkdropper(event);" ondrop="linkdrop(event);" >{{$content}}</textarea>
+ <textarea class="profile-jot-text" id="profile-jot-text" name="body" tabindex="2" placeholder="{{$placeholdtext}}" >{{$content}}</textarea>
</div>
{{if $attachment}}
<div id="jot-attachment-wrap">
<input class="jot-attachment" name="attachment" id="jot-attachment" type="text" value="{{$attachment}}" readonly="readonly" onclick="this.select();">
</div>
{{/if}}
- <div id="profile-jot-submit-wrapper" class="jothidden">
- <div id="profile-jot-submit-left" class="btn-toolbar pull-left">
+ <div id="profile-jot-submit-wrapper" class="clearfix p-2 jothidden">
+ <div id="profile-jot-submit-left" class="btn-toolbar float-left">
{{if $bbcode}}
- <div class="btn-group">
- <button id="main-editor-bold" class="btn btn-default btn-sm" title="{{$bold}}" onclick="inserteditortag('b', 'profile-jot-text'); return false;">
+ <div class="btn-group mr-2">
+ <button id="main-editor-bold" class="btn btn-outline-secondary btn-sm" title="{{$bold}}" onclick="inserteditortag('b', 'profile-jot-text'); return false;">
<i class="fa fa-bold jot-icons"></i>
</button>
- <button id="main-editor-italic" class="btn btn-default btn-sm" title="{{$italic}}" onclick="inserteditortag('i', 'profile-jot-text'); return false;">
+ <button id="main-editor-italic" class="btn btn-outline-secondary btn-sm" title="{{$italic}}" onclick="inserteditortag('i', 'profile-jot-text'); return false;">
<i class="fa fa-italic jot-icons"></i>
</button>
- <button id="main-editor-underline" class="btn btn-default btn-sm" title="{{$underline}}" onclick="inserteditortag('u', 'profile-jot-text'); return false;">
+ <button id="main-editor-underline" class="btn btn-outline-secondary btn-sm" title="{{$underline}}" onclick="inserteditortag('u', 'profile-jot-text'); return false;">
<i class="fa fa-underline jot-icons"></i>
</button>
- <button id="main-editor-quote" class="btn btn-default btn-sm" title="{{$quote}}" onclick="inserteditortag('quote', 'profile-jot-text'); return false;">
+ <button id="main-editor-quote" class="btn btn-outline-secondary btn-sm" title="{{$quote}}" onclick="inserteditortag('quote', 'profile-jot-text'); return false;">
<i class="fa fa-quote-left jot-icons"></i>
</button>
- <button id="main-editor-code" class="btn btn-default btn-sm" title="{{$code}}" onclick="inserteditortag('code', 'profile-jot-text'); return false;">
+ <button id="main-editor-code" class="btn btn-outline-secondary btn-sm" title="{{$code}}" onclick="inserteditortag('code', 'profile-jot-text'); return false;">
<i class="fa fa-terminal jot-icons"></i>
</button>
</div>
{{/if}}
{{if $visitor}}
- <div class="btn-group hidden-xs hidden-sm">
+ <div class="btn-group mr-2 d-none d-lg-flex">
{{if $writefiles}}
- <button id="wall-file-upload" class="btn btn-default btn-sm" title="{{$attach}}" >
+ <button id="wall-file-upload" class="btn btn-outline-secondary btn-sm" title="{{$attach}}" >
<i id="wall-file-upload-icon" class="fa fa-paperclip jot-icons"></i>
</button>
{{/if}}
{{if $weblink}}
- <button id="profile-link-wrapper" class="btn btn-default btn-sm" title="{{$weblink}}" ondragenter="linkdropper(event);" ondragover="linkdropper(event);" ondrop="linkdrop(event);" onclick="jotGetLink(); return false;">
+ <button id="profile-link-wrapper" class="btn btn-outline-secondary btn-sm" title="{{$weblink}}" ondragenter="linkdropper(event);" ondragover="linkdropper(event);" ondrop="linkdrop(event);" onclick="jotGetLink(); return false;">
<i id="profile-link" class="fa fa-link jot-icons"></i>
</button>
{{/if}}
{{if $embedPhotos}}
- <button id="embed-photo-wrapper" class="btn btn-default btn-sm" title="{{$embedPhotos}}" onclick="initializeEmbedPhotoDialog();return false;">
+ <button id="embed-photo-wrapper" class="btn btn-outline-secondary btn-sm" title="{{$embedPhotos}}" onclick="initializeEmbedPhotoDialog();return false;">
<i id="embed-photo" class="fa fa-file-image-o jot-icons"></i>
</button>
{{/if}}
</div>
- <div class="btn-group hidden-xs hidden-sm">
+ <div class="btn-group mr-2 d-none d-lg-flex">
{{if $setloc}}
- <button id="profile-location-wrapper" class="btn btn-default btn-sm" title="{{$setloc}}" onclick="jotGetLocation();return false;">
+ <button id="profile-location-wrapper" class="btn btn-outline-secondary btn-sm" title="{{$setloc}}" onclick="jotGetLocation();return false;">
<i id="profile-location" class="fa fa-globe jot-icons"></i>
</button>
{{/if}}
{{if $clearloc}}
- <button id="profile-nolocation-wrapper" class="btn btn-default btn-sm" title="{{$clearloc}}" onclick="jotClearLocation();return false;" disabled="disabled">
+ <button id="profile-nolocation-wrapper" class="btn btn-outline-secondary btn-sm" title="{{$clearloc}}" onclick="jotClearLocation();return false;" disabled="disabled">
<i id="profile-nolocation" class="fa fa-circle-o jot-icons"></i>
</button>
{{/if}}
{{else}}
- <div class="btn-group hidden-xs hidden-sm">
+ <div class="btn-group d-none d-lg-flex">
{{/if}}
{{if $feature_expire}}
- <button id="profile-expire-wrapper" class="btn btn-default btn-sm" title="{{$expires}}" onclick="jotGetExpiry();return false;">
+ <button id="profile-expire-wrapper" class="btn btn-outline-secondary btn-sm" title="{{$expires}}" onclick="jotGetExpiry();return false;">
<i id="profile-expires" class="fa fa-eraser jot-icons"></i>
</button>
{{/if}}
{{if $feature_future}}
- <button id="profile-future-wrapper" class="btn btn-default btn-sm" title="{{$future_txt}}" onclick="jotGetPubDate();return false;">
+ <button id="profile-future-wrapper" class="btn btn-outline-secondary btn-sm" title="{{$future_txt}}" onclick="jotGetPubDate();return false;">
<i id="profile-future" class="fa fa-clock-o jot-icons"></i>
</button>
{{/if}}
{{if $feature_encrypt}}
- <button id="profile-encrypt-wrapper" class="btn btn-default btn-sm" title="{{$encrypt}}" onclick="red_encrypt('{{$cipher}}','#profile-jot-text',$('#profile-jot-text').val());return false;">
+ <button id="profile-encrypt-wrapper" class="btn btn-outline-secondary btn-sm" title="{{$encrypt}}" onclick="red_encrypt('{{$cipher}}','#profile-jot-text',$('#profile-jot-text').val());return false;">
<i id="profile-encrypt" class="fa fa-key jot-icons"></i>
</button>
{{/if}}
{{if $feature_voting}}
- <button id="profile-voting-wrapper" class="btn btn-default btn-sm" title="{{$voting}}" onclick="toggleVoting();return false;">
+ <button id="profile-voting-wrapper" class="btn btn-outline-secondary btn-sm" title="{{$voting}}" onclick="toggleVoting();return false;">
<i id="profile-voting" class="fa fa-square-o jot-icons"></i>
</button>
{{/if}}
{{if $feature_nocomment}}
- <button id="profile-nocomment-wrapper" class="btn btn-default btn-sm" title="{{$nocommenttitle}}" onclick="toggleNoComment();return false;">
+ <button id="profile-nocomment-wrapper" class="btn btn-outline-secondary btn-sm" title="{{$nocommenttitle}}" onclick="toggleNoComment();return false;">
<i id="profile-nocomment" class="fa fa-comments jot-icons"></i>
</button>
{{/if}}
</div>
{{if $writefiles || $weblink || $setloc || $clearloc || $feature_expire || $feature_encrypt || $feature_voting}}
- <div class="btn-group visible-xs visible-sm">
- <button type="button" id="more-tools" class="btn btn-default btn-sm dropdown-toggle" data-toggle="dropdown" aria-expanded="false">
- <i id="more-tools-icon" class="fa fa-caret-down jot-icons"></i>
+ <div class="btn-group d-lg-none">
+ <button type="button" id="more-tools" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown" aria-expanded="false">
+ <i id="more-tools-icon" class="fa fa-cog jot-icons"></i>
</button>
- <ul class="dropdown-menu" role="menu">
+ <div class="dropdown-menu">
{{if $visitor}}
{{if $writefiles}}
- <li><a id="wall-file-upload-sub" href="#" ><i class="fa fa-paperclip"></i>&nbsp;{{$attach}}</a></li>
+ <a class="dropdown-item" id="wall-file-upload-sub" href="#" ><i class="fa fa-paperclip"></i>&nbsp;{{$attach}}</a>
{{/if}}
{{if $weblink}}
- <li><a href="#" onclick="jotGetLink(); return false;"><i class="fa fa-link"></i>&nbsp;{{$weblink}}</a></li>
+ <a class="dropdown-item" href="#" onclick="jotGetLink(); return false;"><i class="fa fa-link"></i>&nbsp;{{$weblink}}</a>
+ {{/if}}
+ {{if $embedPhotos}}
+ <a class="dropdown-item" href="#" onclick="initializeEmbedPhotoDialog(); return false;"><i class="fa fa-file-image-o jot-icons"></i>&nbsp;{{$embedPhotos}}</a>
{{/if}}
{{if $setloc}}
- <li><a href="#" onclick="jotGetLocation(); return false;"><i class="fa fa-globe"></i>&nbsp;{{$setloc}}</a></li>
+ <a class="dropdown-item" href="#" onclick="jotGetLocation(); return false;"><i class="fa fa-globe"></i>&nbsp;{{$setloc}}</a>
{{/if}}
{{if $clearloc}}
- <li><a href="#" onclick="jotClearLocation(); return false;"><i class="fa fa-circle-o"></i>&nbsp;{{$clearloc}}</a></li>
+ <a class="dropdown-item" href="#" onclick="jotClearLocation(); return false;"><i class="fa fa-circle-o"></i>&nbsp;{{$clearloc}}</a>
{{/if}}
{{/if}}
{{if $feature_expire}}
- <li><a href="#" onclick="jotGetExpiry(); return false;"><i class="fa fa-eraser"></i>&nbsp;{{$expires}}</a></li>
+ <a class="dropdown-item" href="#" onclick="jotGetExpiry(); return false;"><i class="fa fa-eraser"></i>&nbsp;{{$expires}}</a>
{{/if}}
{{if $feature_future}}
- <li><a href="#" onclick="jotGetPubDate();return false;"><i class="fa fa-clock-o"></i>&nbsp;{{$future_txt}}</a></li>
+ <a class="dropdown-item" href="#" onclick="jotGetPubDate();return false;"><i class="fa fa-clock-o"></i>&nbsp;{{$future_txt}}</a>
{{/if}}
{{if $feature_encrypt}}
- <li><a href="#" onclick="red_encrypt('{{$cipher}}','#profile-jot-text',$('#profile-jot-text').val());return false;"><i class="fa fa-key"></i>&nbsp;{{$encrypt}}</a></li>
+ <a class="dropdown-item" href="#" onclick="red_encrypt('{{$cipher}}','#profile-jot-text',$('#profile-jot-text').val());return false;"><i class="fa fa-key"></i>&nbsp;{{$encrypt}}</a>
{{/if}}
{{if $feature_voting}}
- <li><a href="#" onclick="toggleVoting(); return false;"><i id="profile-voting-sub" class="fa fa-square-o"></i>&nbsp;{{$voting}}</a></li>
+ <a class="dropdown-item" href="#" onclick="toggleVoting(); return false;"><i id="profile-voting-sub" class="fa fa-square-o"></i>&nbsp;{{$voting}}</a>
{{/if}}
{{if $feature_nocomment}}
- <li><a href="#" onclick="toggleNoComment(); return false;"><i id="profile-nocomment-sub" class="fa fa-comments"></i>&nbsp;{{$nocommenttitlesub}}</a></li>
+ <a class="dropdown-item" href="#" onclick="toggleNoComment(); return false;"><i id="profile-nocomment-sub" class="fa fa-comments"></i>&nbsp;{{$nocommenttitlesub}}</a>
{{/if}}
- </ul>
+ </div>
</div>
{{/if}}
+ <div class="btn-group">
+ <div id="profile-rotator" class="mt-2 spinner-wrapper">
+ <div class="spinner s"></div>
+ </div>
+ </div>
</div>
- <div id="profile-rotator-wrapper">
- <div id="profile-rotator"></div>
- </div>
- <div id="profile-jot-submit-right" class="btn-group pull-right">
+ <div id="profile-jot-submit-right" class="btn-group float-right">
{{if $preview}}
- <button class="btn btn-default btn-sm" onclick="preview_post();return false;" title="{{$preview}}">
+ <button class="btn btn-outline-secondary btn-sm" onclick="preview_post();return false;" title="{{$preview}}">
<i class="fa fa-eye jot-icons" ></i>
</button>
{{/if}}
{{if $jotnets}}
- <button id="dbtn-jotnets" class="btn btn-default btn-sm" data-toggle="modal" data-target="#jotnetsModal" type="button" title="{{$jotnets_label}}" style="{{if $lockstate == 'lock'}}display: none;{{/if}}">
+ <button id="dbtn-jotnets" class="btn btn-outline-secondary btn-sm" data-toggle="modal" data-target="#jotnetsModal" type="button" title="{{$jotnets_label}}" style="{{if $lockstate == 'lock'}}display: none;{{/if}}">
<i class="fa fa-share-alt jot-icons"></i>
</button>
{{/if}}
{{if $showacl}}
- <button id="dbtn-acl" class="btn btn-default btn-sm" data-toggle="modal" data-target="#aclModal" title="{{$permset}}" type="button" data-form_id="profile-jot-form">
+ <button id="dbtn-acl" class="btn btn-outline-secondary btn-sm" data-toggle="modal" data-target="#aclModal" title="{{$permset}}" type="button" data-form_id="profile-jot-form">
<i id="jot-perms-icon" class="fa fa-{{$lockstate}} jot-icons{{if $bang}} jot-lock-warn{{/if}}"></i>
</button>
{{/if}}
@@ -187,7 +194,7 @@
</div>
<div class="clear"></div>
{{if $jotplugins}}
- <div id="profile-jot-plugin-wrapper">
+ <div id="profile-jot-plugin-wrapper" class="mt-2">
{{$jotplugins}}
</div>
{{/if}}
@@ -196,28 +203,26 @@
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
- <button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button>
<h4 class="modal-title" id="expiryModalLabel">{{$jotnets_label}}</h4>
+ <button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button>
</div>
<div class="modal-body">
{{$jotnets}}
</div>
<div class="modal-footer">
- <button type="button" class="btn btn-default" data-dismiss="modal">Close</button>
+ <button type="button" class="btn btn-outline-secondary" data-dismiss="modal">Close</button>
</div>
</div><!-- /.modal-content -->
</div><!-- /.modal-dialog -->
</div><!-- /.modal -->
{{/if}}
</div>
- <div id="profile-jot-text-loading"></div>
- <div id="profile-jot-end" class="clear"></div>
</div>
</form>
<div id="jot-preview-content" style="display:none;"></div>
-{{if $showacl}}{{$acl}}{{/if}}
+{{$acl}}
{{if $feature_expire}}
<!-- Modal for item expiry-->
@@ -225,8 +230,8 @@
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
- <button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button>
<h4 class="modal-title" id="expiryModalLabel">{{$expires}}</h4>
+ <button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button>
</div>
<div class="modal-body form-group" style="width:90%">
<div class="date">
@@ -239,7 +244,7 @@
</script>
</div>
<div class="modal-footer">
- <button type="button" class="btn btn-default" data-dismiss="modal">{{$expiryModalCANCEL}}</button>
+ <button type="button" class="btn btn-outline-secondary" data-dismiss="modal">{{$expiryModalCANCEL}}</button>
<button id="expiry-modal-OKButton" type="button" class="btn btn-primary">{{$expiryModalOK}}</button>
</div>
</div><!-- /.modal-content -->
@@ -252,8 +257,8 @@
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
- <button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button>
<h4 class="modal-title" id="createdModalLabel">{{$future_txt}}</h4>
+ <button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button>
</div>
<div class="modal-body form-group" style="width:90%">
<div class="date">
@@ -266,7 +271,7 @@
</script>
</div>
<div class="modal-footer">
- <button type="button" class="btn btn-default" data-dismiss="modal">{{$expiryModalCANCEL}}</button>
+ <button type="button" class="btn btn-outline-secondary" data-dismiss="modal">{{$expiryModalCANCEL}}</button>
<button id="created-modal-OKButton" type="button" class="btn btn-primary">{{$expiryModalOK}}</button>
</div>
</div><!-- /.modal-content -->
@@ -279,17 +284,17 @@
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
- <button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button>
<h4 class="modal-title" id="embedPhotoModalLabel">{{$embedPhotosModalTitle}}</h4>
+ <button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button>
</div>
<div class="modal-body" id="embedPhotoModalBody" >
- <div id="embedPhotoModalBodyAlbumListDialog" class="hide">
+ <div id="embedPhotoModalBodyAlbumListDialog" class="d-none">
<div id="embedPhotoModalBodyAlbumList"></div>
</div>
- <div id="embedPhotoModalBodyAlbumDialog" class="hide"></div>
+ <div id="embedPhotoModalBodyAlbumDialog" class="d-none"></div>
</div>
<div class="modal-footer">
- <button type="button" class="btn btn-default" data-dismiss="modal">{{$embedPhotosModalCancel}}</button>
+ <button type="button" class="btn btn-outline-secondary" data-dismiss="modal">{{$embedPhotosModalCancel}}</button>
<button id="embed-photo-OKButton" type="button" class="btn btn-primary">{{$embedPhotosModalOK}}</button>
</div>
</div><!-- /.modal-content -->
diff --git a/view/tpl/layoutlist.tpl b/view/tpl/layoutlist.tpl
index d0b81af0c..1bbe14893 100644
--- a/view/tpl/layoutlist.tpl
+++ b/view/tpl/layoutlist.tpl
@@ -2,8 +2,8 @@
<div class="section-title-wrapper">
{{if $editor}}
<div class="pull-right">
- <button id="webpage-create-btn" class="btn btn-xs btn-success" onclick="openClose('layout-editor');"><i class="fa fa-pencil-square-o"></i>&nbsp;{{$create}}</button>
- <a href="{{$help.url}}" target="_blank" class="btn btn-xs btn-warning" title="{{$help.title}}"><i class="fa fa-info"></i>&nbsp;{{$help.text}}</a>
+ <button id="webpage-create-btn" class="btn btn-sm btn-success" onclick="openClose('layout-editor');"><i class="fa fa-pencil-square-o"></i>&nbsp;{{$create}}</button>
+ <a href="{{$help.url}}" target="_blank" class="btn btn-sm btn-warning" title="{{$help.title}}"><i class="fa fa-info"></i>&nbsp;{{$help.text}}</a>
</div>
{{/if}}
<h2>{{$title}}</h2>
@@ -24,8 +24,8 @@
<th width="1%"></th>
<th width="1%"></th>
<th width="1%"></th>
- <th width="1%" class="hidden-xs">{{$created}}</th>
- <th width="1%" class="hidden-xs">{{$edited}}</th>
+ <th width="1%" class="d-none d-md-table-cell">{{$created}}</th>
+ <th width="1%" class="d-none d-md-table-cell">{{$edited}}</th>
</tr>
{{foreach $pages as $key => $items}}
{{foreach $items as $item}}
@@ -55,10 +55,10 @@
<a href="#" title="{{$delete}}" onclick="dropItem('item/drop/{{$item.url}}', '#layout-list-item-{{$item.url}}'); return false;"><i class="fa fa-trash-o drop-icons"></i></a>
{{/if}}
</td>
- <td class="hidden-xs">
+ <td class="d-none d-md-table-cell">
{{$item.created}}
</td>
- <td class="hidden-xs">
+ <td class="d-none d-md-table-cell">
{{$item.edited}}
</td>
</tr>
diff --git a/view/tpl/like_noshare.tpl b/view/tpl/like_noshare.tpl
index 67f5868cb..e83b885fe 100755
--- a/view/tpl/like_noshare.tpl
+++ b/view/tpl/like_noshare.tpl
@@ -1,5 +1,5 @@
<div class="wall-item-like-buttons" id="wall-item-like-buttons-{{$id}}">
- <i class="fa fa-thumbs-o-up item-tool btn btn-default" title="{{$likethis}}" onclick="dolike({{$id}},'like'); return false"></i>
- <i class="fa fa-thumbs-o-down item-tool btn btn-default" title="{{$nolike}}" onclick="dolike({{$id}},'dislike'); return false"></i>
+ <i class="fa fa-thumbs-o-up item-tool btn btn-outline-secondary" title="{{$likethis}}" onclick="dolike({{$id}},'like'); return false"></i>
+ <i class="fa fa-thumbs-o-down item-tool btn btn-outline-secondary" title="{{$nolike}}" onclick="dolike({{$id}},'dislike'); return false"></i>
<div id="like-rotator-{{$id}}" class="like-rotator"></div>
</div>
diff --git a/view/tpl/locmanage.tpl b/view/tpl/locmanage.tpl
index fe2d5ec84..a8c75b6a8 100644
--- a/view/tpl/locmanage.tpl
+++ b/view/tpl/locmanage.tpl
@@ -8,7 +8,7 @@
$.post(baseurl + '/locs','drop='+id,function(data) { window.location.href=window.location.href; });
}
</script>
- <button class="btn btn-success btn-xs pull-right" onclick="window.location.href='/locs/f=&sync=1'; return false;"><i class="fa fa-refresh"></i>&nbsp;{{$sync}}</button>
+ <button class="btn btn-success btn-sm pull-right" onclick="window.location.href='/locs/f=&sync=1'; return false;"><i class="fa fa-refresh"></i>&nbsp;{{$sync}}</button>
<h2>{{$header}}</h2>
</div>
<div class="section-content-wrapper-np">
@@ -22,7 +22,7 @@
<table id="locs-index">
<tr>
<th>{{$addr}}</th>
- <th class="hidden-xs hidden-sm">{{$loc}}</th>
+ <th class="d-none d-md-table-cell">{{$loc}}</th>
<th>{{$mkprm}}</th>
<th>{{$drop}}</th>
</tr>
@@ -30,7 +30,7 @@
{{if ! $hub.deleted }}
<tr class="locs-index-row">
<td>{{$hub.hubloc_addr}}</td>
- <td class="hidden-xs hidden-sm">{{$hub.hubloc_url}}</td>
+ <td class="d-none d-md-table-cell">{{$hub.hubloc_url}}</td>
<td>{{if $hub.primary}}<i class="fa fa-check-square-o"></i>{{else}}<i class="fa fa-square-o primehub" onclick="primehub({{$hub.hubloc_id}}); return false;"></i>{{/if}}</td>
<td><i class="fa fa-trash-o drophub" onclick="drophub({{$hub.hubloc_id}}); return false;"></i></td>
</tr>
diff --git a/view/tpl/login.tpl b/view/tpl/login.tpl
index 3d3faa41c..492149abb 100755
--- a/view/tpl/login.tpl
+++ b/view/tpl/login.tpl
@@ -11,6 +11,8 @@
{{if $register}}<a href="{{$register.link}}" title="{{$register.title}}" id="register-link" class="pull-right">{{$register.desc}}</a>{{/if}}
<a href="lostpass" title="{{$lostpass}}" id="lost-password-link" >{{$lostlink}}</a>
</div>
+ <hr>
+ <a href="rmagic" class="btn btn-block btn-outline-success rmagic-button">{{$remote_login}}</a>
</div>
{{foreach $hiddens as $k=>$v}}
<input type="hidden" name="{{$k}}" value="{{$v}}" />
diff --git a/view/tpl/mail_conv.tpl b/view/tpl/mail_conv.tpl
index 249e13a04..759517b7f 100755
--- a/view/tpl/mail_conv.tpl
+++ b/view/tpl/mail_conv.tpl
@@ -1,47 +1,38 @@
-<div id="mail-{{$mail.id}}" class="mail-conv-outside-wrapper">
- <div class="mail-conv-sender" >
- <a href="{{$mail.from_url}}"><img class="mail-conv-sender-photo" src="{{$mail.from_photo}}" alt="{{$mail.from_name}}" /></a>
- </div>
- <div class="mail-conv-detail">
- {{if $mail.is_recalled}}<strong>{{$mail.is_recalled}}</strong>{{/if}}
- <div class="mail-conv-sender-name"><a href="{{$mail.from_url}}">{{$mail.from_name}}</a></div>
- <div class="mail-conv-date autotime wall-item-ago" title="{{$mail.date}}">{{$mail.date}}</div>
+<div id="mail-{{$mail.id}}" class="mb-2 clearfix mail-conv-outside-wrapper">
+ <div class="mb-2 clearfix wall-item-head">
+ <div class="wall-item-info" >
+ <a href="{{$mail.from_url}}"><img class="wall-item-photo" src="{{$mail.from_photo}}" alt="{{$mail.from_name}}" /></a>
+ </div>
+ <div class="mail-conv-detail">
+ {{if $mail.is_recalled}}<strong>{{$mail.is_recalled}}</strong>{{/if}}
+ <div class="wall-item-name"><a class="wall-item-name-link" href="{{$mail.from_url}}">{{$mail.from_name}}</a></div>
+ <div class="autotime wall-item-ago" title="{{$mail.date}}">{{$mail.date}}</div>
+ </div>
</div>
- <div class="clear"></div>
- <div class="mail-conv-content">
- <div class="mail-conv-body">
+ <div class="clearfix mail-conv-content">
+ <div class="clearfix mail-conv-body">
{{$mail.body}}
- <div class="clear"></div>
</div>
{{if $mail.attachments}}
- <div class="dropdown pull-left">
- <button type="button" class="btn btn-default btn-sm wall-item-like dropdown-toggle" data-toggle="dropdown" id="attachment-menu-{{$item.id}}"><i class="fa fa-paperclip"></i></button>
- <ul class="dropdown-menu" role="menu" aria-labelledby="attachment-menu-{{$item.id}}">{{$mail.attachments}}</ul>
+ <div class="dropdown float-left">
+ <button type="button" class="btn btn-outline-secondary btn-sm wall-item-like dropdown-toggle" data-toggle="dropdown" id="attachment-menu-{{$item.id}}"><i class="fa fa-fw fa-paperclip"></i></button>
+ <div class="dropdown-menu" role="menu" aria-labelledby="attachment-menu-{{$item.id}}">{{$mail.attachments}}</div>
</div>
{{/if}}
- <div class="pull-right dropdown">
- <button type="button" class="btn btn-default btn-sm dropdown-toggle" data-toggle="dropdown" id="mail-item-menu-{{$mail.id}}">
- <i class="fa fa-caret-down"></i>
+ <div class="float-right dropdown">
+ <button type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown" id="mail-item-menu-{{$mail.id}}">
+ <i class="fa fa-cog"></i>
</button>
- <ul class="dropdown-menu" role="menu" aria-labelledby="mail-item-menu-{{$mail.id}}">
+ <div class="dropdown-menu dropdown-menu-right" role="menu" aria-labelledby="mail-item-menu-{{$mail.id}}">
{{if $mail.can_recall}}
- <li>
- <a href="mail/{{$mail.mailbox}}/recall/{{$mail.id}}" title="{{$mail.recall}}" id="mail-conv-recall-icon-{{$mail.id}}"><i class="fa fa-undo mail-icons"></i>&nbsp;{{$mail.recall}}</a>
- </li>
+ <a class="dropdown-item" href="mail/{{$mail.mailbox}}/recall/{{$mail.id}}" title="{{$mail.recall}}" id="mail-conv-recall-icon-{{$mail.id}}"><i class="fa fa-fw fa-undo"></i>&nbsp;{{$mail.recall}}</a>
{{/if}}
- <li>
- <a href="#" onclick="dropItem('mail/{{$mail.mailbox}}/drop/{{$mail.id}}', '#mail-{{$mail.id}}'); return false;" title="{{$mail.delete}}" id="mail-conv-delete-icon-{{$mail.id}}"><i class="fa fa-trash-o mail-icons"></i>&nbsp;{{$mail.delete}}</a>
- </li>
+ <a class="dropdown-item" href="#" onclick="dropItem('mail/{{$mail.mailbox}}/drop/{{$mail.id}}', '#mail-{{$mail.id}}'); return false;" title="{{$mail.delete}}" id="mail-conv-delete-icon-{{$mail.id}}"><i class="fa fa-fw fa-trash-o"></i>&nbsp;{{$mail.delete}}</a>
{{if $mail.can_recall}}
- <li class="divider"></li>
- <li>
- <a href="dreport/mail/{{$mail.mid}}" title="{{$mail.dreport}}" id="mail-conv-dreport-icon-{{$mail.id}}">{{$mail.dreport}}</a>
- </li>
+ <div class="dropdown-divider"></div>
+ <a class="dropdown-item" href="dreport/mail/{{$mail.mid}}" title="{{$mail.dreport}}" id="mail-conv-dreport-icon-{{$mail.id}}">{{$mail.dreport}}</a>
{{/if}}
- </ul>
-
+ </div>
</div>
- <div class="clear"></div>
</div>
- <div class="clear"></div>
</div>
diff --git a/view/tpl/mail_display.tpl b/view/tpl/mail_display.tpl
index 748c118ef..e8549a49b 100755
--- a/view/tpl/mail_display.tpl
+++ b/view/tpl/mail_display.tpl
@@ -1,10 +1,10 @@
<div class="generic-content-wrapper">
<div class="section-title-wrapper">
<div class="pull-right">
- <button id="fullscreen-btn" type="button" class="btn btn-default btn-xs" onclick="makeFullScreen();"><i class="fa fa-expand"></i></button>
- <button id="inline-btn" type="button" class="btn btn-default btn-xs" onclick="makeFullScreen(false);"><i class="fa fa-compress"></i></button>
+ <button id="fullscreen-btn" type="button" class="btn btn-outline-secondary btn-sm" onclick="makeFullScreen();"><i class="fa fa-expand"></i></button>
+ <button id="inline-btn" type="button" class="btn btn-outline-secondary btn-sm" onclick="makeFullScreen(false);"><i class="fa fa-compress"></i></button>
{{if $mailbox == 'combined'}}
- <a class="btn btn-xs btn-danger" href="mail/{{$mailbox}}/dropconv/{{$thread_id}}" onclick="return confirmDelete();"><i class="fa fa-trash-o"></i> {{$delete}}</a>
+ <a class="btn btn-sm btn-danger" href="mail/{{$mailbox}}/dropconv/{{$thread_id}}" onclick="return confirmDelete();"><i class="fa fa-trash-o"></i> {{$delete}}</a>
{{/if}}
</div>
<h2>{{$prvmsg_header}}</h2>
diff --git a/view/tpl/mail_head.tpl b/view/tpl/mail_head.tpl
index d52fa40e0..aac592a5f 100755
--- a/view/tpl/mail_head.tpl
+++ b/view/tpl/mail_head.tpl
@@ -1,6 +1,6 @@
<div class="widget">
<h3>{{$header}}</h3>
- <ul class="nav nav-pills nav-stacked">
+ <ul class="nav nav-pills flex-column">
{{foreach $messages as $message}}
{{include file="mail_list.tpl"}}
{{/foreach}}
diff --git a/view/tpl/mail_list.tpl b/view/tpl/mail_list.tpl
index fc9b5afa8..65d8dcdb4 100755
--- a/view/tpl/mail_list.tpl
+++ b/view/tpl/mail_list.tpl
@@ -1,6 +1,6 @@
-<li>
- <a href="mail/{{$message.mailbox}}/{{$message.id}}" class="{{if $message.selected}}active{{/if}}">
- <span class="{{if $message.seen}}seen{{else}}unseen{{/if}}">{{$message.subject}}</span><br>
+<li class="nav-item">
+ <a href="mail/{{$message.mailbox}}/{{$message.id}}" class="nav-link{{if $message.selected}} active{{/if}}">
+ <span class="{{if ! $message.seen || $message.selected}}font-weight-bold{{/if}}">{{$message.subject}}</span><br>
<span class="conv-participants">{{$message.from_name}} > {{$message.to_name}}</span><br>
<span class="wall-item-ago autotime" title="{{$message.date}}">{{$message.date}}</span>
</a>
diff --git a/view/tpl/main_slider.tpl b/view/tpl/main_slider.tpl
index a4e2e1925..f5c573970 100755
--- a/view/tpl/main_slider.tpl
+++ b/view/tpl/main_slider.tpl
@@ -1,4 +1,9 @@
-<div id="main-slider" class="slider" ><input id="main-range" type="text" name="cminmax" value="{{$val}}" /></div>
+<div id="main-slider" class="slider" >
+ <input id="main-range" type="text" name="cminmax" value="{{$val}}" />
+ <div id="profile-jot-text-loading" class="spinner-wrapper">
+ <div class="spinner m"></div>
+ </div>
+</div>
<script>
$(document).ready(function() {
var old_cmin = 0;
@@ -19,13 +24,14 @@ $(document).ready(function() {
var slideTimer = null;
function networkRefresh() {
+
$("#profile-jot-text-loading").show();
if((document.readyState !== "complete") || (slideTimer !== null))
return;
if((bParam_cmin == old_cmin) && (bParam_cmax == old_cmax))
return;
- setTimeout(function() { $("#profile-jot-text-loading").spin('small'); }, 1000 );
+
slideTimer = setTimeout(networkTimerRefresh,2000);
}
diff --git a/view/tpl/menuedit.tpl b/view/tpl/menuedit.tpl
index 28236ff15..84b16dc0b 100644
--- a/view/tpl/menuedit.tpl
+++ b/view/tpl/menuedit.tpl
@@ -3,7 +3,7 @@
<div class="section-title-wrapper">
{{if $menu_edit_link}}
<div class="pull-right">
- <a href="{{$menu_edit_link}}" title="{{$hintedit}}" class="btn btn-xs btn-success"><i class="fa fa-pencil-square-o"></i>&nbsp;{{$editcontents}}</a>
+ <a href="{{$menu_edit_link}}" title="{{$hintedit}}" class="btn btn-sm btn-success"><i class="fa fa-pencil-square-o"></i>&nbsp;{{$editcontents}}</a>
</div>
{{/if}}
<h2>{{$header}}</h2>
diff --git a/view/tpl/menulist.tpl b/view/tpl/menulist.tpl
index f38619923..e23035062 100644
--- a/view/tpl/menulist.tpl
+++ b/view/tpl/menulist.tpl
@@ -1,7 +1,7 @@
<div class="generic-content-wrapper">
<div class="section-title-wrapper">
<div class="pull-right">
- <button id="webpage-create-btn" class="btn btn-xs btn-success" onclick="openClose('menu-creator');"><i class="fa fa-pencil-square-o"></i>&nbsp;{{$hintnew}}</button>
+ <button id="webpage-create-btn" class="btn btn-sm btn-success" onclick="openClose('menu-creator');"><i class="fa fa-pencil-square-o"></i>&nbsp;{{$hintnew}}</button>
</div>
<h2>{{$title}}</h2>
<div class="clear"></div>
@@ -19,8 +19,8 @@
<th width="1%"></th>
<th width="1%"></th>
<th width="1%"></th>
- <th width="1%" class="hidden-xs">{{$created}}</th>
- <th width="1%" class="hidden-xs">{{$edited}}</th>
+ <th width="1%" class="d-none d-md-table-cell">{{$created}}</th>
+ <th width="1%" class="d-none d-md-table-cell">{{$edited}}</th>
</tr>
{{foreach $menus as $m }}
<tr id="menu-list-item-{{$m.menu_id}}">
@@ -30,8 +30,8 @@
<td class="menu-list-tool"><a href="menu/{{$m.menu_id}}{{if $sys}}?f=&sys=1{{/if}}" title="{{$hintedit}}"><i class="fa fa-pencil"></i></a></td>
<td class="menu-list-tool"><a href="rpost?attachment={{$m.element}}" title="{{$share}}"><i class="fa fa-share-square-o"></i></a></td>
<td class="menu-list-tool"><a href="#" title="{{$hintdrop}}" onclick="dropItem('menu/{{$m.menu_id}}/drop{{if $sys}}?f=&sys=1{{/if}}', '#menu-list-item-{{$m.menu_id}}'); return false;"><i class="fa fa-trash-o drop-icons"></i></a></td>
- <td class="hidden-xs">{{$m.menu_created}}</td>
- <td class="hidden-xs">{{$m.menu_edited}}</td>
+ <td class="d-none d-md-table-cell">{{$m.menu_created}}</td>
+ <td class="d-none d-md-table-cell">{{$m.menu_edited}}</td>
</tr>
{{/foreach}}
</table>
diff --git a/view/tpl/message_side.tpl b/view/tpl/message_side.tpl
index 6ea63c21e..2ac61bf76 100755
--- a/view/tpl/message_side.tpl
+++ b/view/tpl/message_side.tpl
@@ -1,9 +1,9 @@
<div class="widget">
<h3>{{$title}}</h3>
- <ul class="nav nav-pills nav-stacked">
- <li><a href="{{$combined.url}}"{{if $combined.sel}} class="active"{{/if}}>{{$combined.label}}</a></li>
- <li><a href="{{$inbox.url}}"{{if $inbox.sel}} class="active"{{/if}}>{{$inbox.label}}</a></li>
- <li><a href="{{$outbox.url}}"{{if $outbox.sel}} class="active"{{/if}}>{{$outbox.label}}</a></li>
- <li><a href="{{$new.url}}"{{if $new.sel}} class="active"{{/if}}>{{$new.label}}</a></li>
+ <ul class="nav nav-pills flex-column">
+ <li class="nav-item"><a href="{{$combined.url}}" class="nav-link{{if $combined.sel}} active{{/if}}">{{$combined.label}}</a></li>
+ <li class="nav-item"><a href="{{$inbox.url}}" class="nav-link{{if $inbox.sel}} active{{/if}}">{{$inbox.label}}</a></li>
+ <li class="nav-item"><a href="{{$outbox.url}}" class="nav-link{{if $outbox.sel}} active{{/if}}">{{$outbox.label}}</a></li>
+ <li class="nav-item"><a href="{{$new.url}}" class="nav-link{{if $new.sel}} active{{/if}}">{{$new.label}}</a></li>
</ul>
</div>
diff --git a/view/tpl/mitemedit.tpl b/view/tpl/mitemedit.tpl
index a06203244..9f696fc23 100644
--- a/view/tpl/mitemedit.tpl
+++ b/view/tpl/mitemedit.tpl
@@ -24,7 +24,7 @@
{{include file="field_checkbox.tpl" field=$newwin}}
<div class="pull-right form-group">
<div class="btn-group">
- <button id="dbtn-acl" class="btn btn-default btn-sm" data-toggle="modal" data-target="#aclModal" onclick="return false;">
+ <button id="dbtn-acl" class="btn btn-outline-secondary btn-sm" data-toggle="modal" data-target="#aclModal" onclick="return false;">
<i id="jot-perms-icon" class="fa fa-{{$lockstate}}"></i>
</button>
{{if $submit_more}}
diff --git a/view/tpl/mitemlist.tpl b/view/tpl/mitemlist.tpl
index 90388ece2..b28cdfc7e 100644
--- a/view/tpl/mitemlist.tpl
+++ b/view/tpl/mitemlist.tpl
@@ -1,7 +1,7 @@
<div class="generic-content-wrapper">
<div class="section-title-wrapper">
<div class="pull-right">
- <button id="webpage-create-btn" class="btn btn-xs btn-success" onclick="openClose('menu-element-creator');"><i class="fa fa-pencil-square-o"></i>&nbsp;{{$hintnew}}</button>
+ <button id="webpage-create-btn" class="btn btn-sm btn-success" onclick="openClose('menu-element-creator');"><i class="fa fa-pencil-square-o"></i>&nbsp;{{$hintnew}}</button>
</div>
<h2>{{$title}} {{if $menudesc}}{{$menudesc}}{{else}}{{$menuname}}{{/if}}</h2>
<div class="clear"></div>
@@ -23,7 +23,7 @@
<tr id="mitem-list-item-{{$m.mitem_id}}">
<td width="1%">{{$m.mitem_desc}}</td>
<td width="96%"><a href="{{$m.mitem_link}}">{{$m.mitem_link}}</a></td>
- <td width="1%" class="mitem-list-tool dropdown">{{if $m.allow_cid || $m.allow_gid || $m.deny_cid || $m.deny_gid}}<i class="fa fa-lock dropdown-toggle lockview" data-toggle="dropdown" onclick="lockview('menu_item',{{$m.mitem_id}});" ></i><ul id="panel-{{$m.mitem_id}}" class="lockview-panel dropdown-menu"></ul>{{/if}}</td>
+ <td width="1%" class="mitem-list-tool dropdown">{{if $m.allow_cid || $m.allow_gid || $m.deny_cid || $m.deny_gid}}<i class="fa fa-lock lockview" data-toggle="dropdown" onclick="lockview('menu_item',{{$m.mitem_id}});" ></i><ul id="panel-{{$m.mitem_id}}" class="lockview-panel dropdown-menu"></ul>{{/if}}</td>
<td width="1%" class="mitem-list-tool"><a href="mitem/{{$menu_id}}/{{$m.mitem_id}}" title="{{$hintedit}}"><i class="fa fa-pencil"></i></a></td>
<td width="1%" class="mitem-list-tool"><a href="#" title="{{$hintdrop}}" onclick="dropItem('mitem/{{$menu_id}}/{{$m.mitem_id}}/drop', '#mitem-list-item-{{$m.mitem_id}}, #pmenu-item-{{$m.mitem_id}}'); return false;"><i class="fa fa-trash-o drop-icons"></i></a></td>
</tr>
diff --git a/view/tpl/msg-header.tpl b/view/tpl/msg-header.tpl
index 013e1cfdc..d71d432fb 100755
--- a/view/tpl/msg-header.tpl
+++ b/view/tpl/msg-header.tpl
@@ -1,34 +1,32 @@
-<script type="text/javascript" src="view/js/ajaxupload.js" ></script>
-<script language="javascript" type="text/javascript">
-
- $("#prvmail-text").editor_autocomplete(baseurl+"/acl");
-
-
+<script src="library/blueimp_upload/js/vendor/jquery.ui.widget.js"></script>
+<script src="library/blueimp_upload/js/jquery.iframe-transport.js"></script>
+<script src="library/blueimp_upload/js/jquery.fileupload.js"></script>
+<script>
$(document).ready(function() {
- var file_uploader = new window.AjaxUpload(
- 'prvmail-attach-wrapper',
- { action: 'wall_attach/{{$nickname}}',
- name: 'userfile',
- onSubmit: function(file,ext) { $('#prvmail-rotator').spin('tiny'); },
- onComplete: function(file,response) {
- addmailtext(response);
- $('#prvmail-rotator').spin(false);
- }
- }
- );
-
- var file_uploader_sub = new window.AjaxUpload(
- 'prvmail-attach-sub',
- { action: 'wall_attach/{{$nickname}}',
- name: 'userfile',
- onSubmit: function(file,ext) { $('#prvmail-rotator').spin('tiny'); },
- onComplete: function(file,response) {
- addmailtext(response);
- $('#prvmail-rotator').spin(false);
- }
- }
- );
+ $("#prvmail-text").editor_autocomplete(baseurl+"/acl");
+
+ $('#invisible-wall-file-upload').fileupload({
+ url: 'wall_attach/{{$nickname}}',
+ dataType: 'json',
+ dropZone: $('#prvmail-text'),
+ maxChunkSize: 4 * 1024 * 1024,
+ add: function(e,data) {
+ $('#prvmail-rotator').show();
+ data.submit();
+ },
+ done: function(e,data) {
+ addmailtext(data.result.message);
+ $('#jot-media').val($('#jot-media').val() + data.result.message);
+ },
+ stop: function(e,data) {
+ preview_mail();
+ $('#prvmail-rotator').hide();
+ },
+ });
+
+ $('#prvmail-attach-wrapper').click(function(event) { event.preventDefault(); $('#invisible-wall-file-upload').trigger('click'); return false;});
+ $('#prvmail-attach-wrapper-sub').click(function(event) { event.preventDefault(); $('#invisible-wall-file-upload').trigger('click'); return false;});
});
@@ -36,10 +34,11 @@
function prvmailJotGetLink() {
reply = prompt("{{$linkurl}}");
if(reply && reply.length) {
- $('#prvmail-rotator').spin('tiny');
+ $('#prvmail-rotator').show();
$.get('linkinfo?f=&url=' + reply, function(data) {
addmailtext(data);
- $('#prvmail-rotator').spin(false);
+ preview_mail();
+ $('#prvmail-rotator').hide();
});
}
}
@@ -62,10 +61,11 @@
event.target.textContent = reply;
event.preventDefault();
if(reply && reply.length) {
- $('#prvmail-rotator').spin('tiny');
+ $('#prvmail-rotator').show();
$.get('linkinfo?f=&url=' + reply, function(data) {
addmailtext(data);
- $('#prvmail-rotator').spin(false);
+ preview_mail();
+ $('#prvmail-rotator').hide();
});
}
}
diff --git a/view/tpl/myapps.tpl b/view/tpl/myapps.tpl
index 074965985..dd2a67a63 100755
--- a/view/tpl/myapps.tpl
+++ b/view/tpl/myapps.tpl
@@ -1,11 +1,17 @@
<div class="generic-content-wrapper">
- <div class="section-title-wrapper">
- <h2>{{$title}}{{$cat}}</h2>
+ <div class="section-title-wrapper clearfix">
+ {{if $authed}}
+ {{if $create}}
+ <a href="appman" class="pull-right btn btn-success btn-sm"><i class="fa fa-pencil-square-o"></i>&nbsp;{{$create}}</a>
+ {{else}}
+ <a href="apps/edit{{if $cat}}/?f=&cat={{$cat}}{{/if}}" class="pull-right btn btn-primary btn-sm">{{$manage}}</a>
+ {{/if}}
+ {{/if}}
+ <h2>{{$title}}{{if $cat}} - {{$cat}}{{/if}}</h2>
</div>
- <div class="section-content-wrapper">
+ <div class="clearfix section-content-wrapper">
{{foreach $apps as $ap}}
{{$ap}}
{{/foreach}}
- <div class="clear"></div>
</div>
</div>
diff --git a/view/tpl/nav.tpl b/view/tpl/nav.tpl
deleted file mode 100755
index 7037881ec..000000000
--- a/view/tpl/nav.tpl
+++ /dev/null
@@ -1,210 +0,0 @@
-<div class="container-fluid">
- <div class="navbar-header">
- <button type="button" class="navbar-toggle" data-toggle="collapse" data-target="#navbar-collapse-2">
- <span class="icon-bar"></span>
- <span class="icon-bar"></span>
- <span class="icon-bar"></span>
- </button>
- {{if $nav.login && !$userinfo}}
- <button type="button" class="navbar-toggle" title="{{$nav.loginmenu.1.3}}" id="{{$nav.loginmenu.1.4}}_collapse" data-toggle="modal" data-target="#nav-login">
- {{$nav.loginmenu.1.1}}
- </button>
- {{/if}}
- {{if $localuser}}
- <button id="notifications-btn" type="button" class="navbar-toggle" data-toggle="collapse" data-target="#navbar-collapse-1" style="color: grey;">
- <i class="fa fa-exclamation-circle"></i>
- </button>
- {{/if}}
- <button id="expand-tabs" type="button" class="navbar-toggle" data-toggle="collapse" data-target="#tabs-collapse-1">
- <i class="fa fa-arrow-circle-down" id="expand-tabs-icon"></i>
- </button>
- <button id="expand-aside" type="button" class="navbar-toggle" data-toggle="offcanvas" data-target="#region_1">
- <i class="fa fa-arrow-circle-right" id="expand-aside-icon"></i>
- </button>
- {{if $nav.help.6}}
- <button id="context-help-btn" class="navbar-toggle" type="button" onclick="contextualHelp(); return false;">
- <i class="fa fa-question-circle"></i>
- </button>
- {{/if}}
- {{if $userinfo}}
- <div class="usermenu-head dropdown-toggle fakelink" data-toggle="dropdown">
- <img id="avatar" src="{{$userinfo.icon}}" alt="{{$userinfo.name}}">
- <span class="caret" id="usermenu-caret"></span>
- </div>
- {{if $localuser}}
- <ul class="dropdown-menu" role="menu" aria-labelledby="avatar">
- {{foreach $nav.usermenu as $usermenu}}
- <li role="presentation"><a href="{{$usermenu.0}}" title="{{$usermenu.3}}" role="menuitem" id="{{$usermenu.4}}">{{$usermenu.1}}</a></li>
- {{/foreach}}
- {{if $nav.manage}}
- <li role="presentation"><a href="{{$nav.manage.0}}" title="{{$nav.manage.3}}" role="menuitem" id="{{$nav.manage.4}}">{{$nav.manage.1}}</a></li>
- {{/if}}
- {{if $nav.channels}}
- {{foreach $nav.channels as $chan}}
- <li role="presentation" class="nav-channel-select"><a href="manage/{{$chan.channel_id}}" title="{{$chan.channel_name}}" role="menuitem">{{$chan.channel_name}}</a></li>
- {{/foreach}}
- {{/if}}
- <li role="presentation" class="divider"></li>
- {{if $nav.profiles}}
- <li role="presentation"><a href="{{$nav.profiles.0}}" title="{{$nav.profiles.3}}" role="menuitem" id="{{$nav.profiles.4}}">{{$nav.profiles.1}}</a></li>
- {{/if}}
- {{if $nav.settings}}
- <li role="presentation"><a href="{{$nav.settings.0}}" title="{{$nav.settings.3}}" role="menuitem" id="{{$nav.settings.4}}">{{$nav.settings.1}}</a></li>
- {{/if}}
- {{if $nav.admin}}
- <li role="presentation" class="divider"></li>
- <li role="presentation"><a href="{{$nav.admin.0}}" title="{{$nav.admin.3}}" role="menuitem" id="{{$nav.admin.4}}">{{$nav.admin.1}}</a></li>
- {{/if}}
- {{if $nav.logout}}
- <li role="presentation" class="divider"></li>
- <li role="presentation"><a href="{{$nav.logout.0}}" title="{{$nav.logout.3}}" role="menuitem" id="{{$nav.logout.4}}">{{$nav.logout.1}}</a></li>
- {{/if}}
- </ul>
- {{else}}
- {{if $nav.rusermenu}}
- <ul class="dropdown-menu" role="menu" aria-labelledby="avatar">
- <li role="presentation"><a href="{{$nav.rusermenu.0}}" role="menuitem">{{$nav.rusermenu.1}}</a></li>
- <li role="presentation"><a href="{{$nav.rusermenu.2}}" role="menuitem">{{$nav.rusermenu.3}}</a></li>
- </ul>
- {{/if}}
- {{/if}}
- {{/if}}
- </div>
- <div class="collapse navbar-collapse" id="navbar-collapse-1">
- <ul class="nav navbar-nav navbar-left">
- {{if $nav.network}}
- <li class="{{$sel.network}} net-button" style="display: none;">
- <a href="#" title="{{$nav.network.3}}" id="{{$nav.network.4}}" data-toggle="dropdown" rel="#nav-network-menu">
- <i class="fa fa-fw fa-th"></i>
- <span class="net-update badge"></span>
- </a>
- <ul id="nav-network-menu" role="menu" class="dropdown-menu" rel="network">
- <li id="nav-network-see-all"><a href="{{$nav.network.all.0}}">{{$nav.network.all.1}}</a></li>
- <li id="nav-network-mark-all"><a href="#" onclick="markRead('network'); return false;">{{$nav.network.mark.1}}</a></li>
- <li class="empty">{{$emptynotifications}}</li>
- </ul>
- </li>
- {{/if}}
- {{if $nav.home}}
- <li class="{{$sel.home}} home-button" style="display: none;">
- <a class="{{$nav.home.2}}" href="#" title="{{$nav.home.3}}" id="{{$nav.home.4}}" data-toggle="dropdown" rel="#nav-home-menu">
- <i class="fa fa-fw fa-home"></i>
- <span class="home-update badge"></span>
- </a>
- <ul id="nav-home-menu" class="dropdown-menu" rel="home">
- <li id="nav-home-see-all"><a href="{{$nav.home.all.0}}">{{$nav.home.all.1}}</a></li>
- <li id="nav-home-mark-all"><a href="#" onclick="markRead('home'); return false;">{{$nav.home.mark.1}}</a></li>
- <li class="empty">{{$emptynotifications}}</li>
- </ul>
- </li>
- {{/if}}
- {{if $nav.messages}}
- <li class="{{$sel.messages}} mail-button" style="display: none;">
- <a class="{{$nav.messages.2}}" href="#" title="{{$nav.messages.3}}" id="{{$nav.messages.4}}" data-toggle="dropdown" rel="#nav-messages-menu">
- <i class="fa fa-fw fa-envelope"></i>
- <span class="mail-update badge"></span>
- </a>
- <ul id="nav-messages-menu" class="dropdown-menu" rel="messages">
- <li id="nav-messages-see-all"><a href="{{$nav.messages.all.0}}">{{$nav.messages.all.1}}</a></li>
- <li id="nav-messages-mark-all"><a href="#" onclick="markRead('messages'); return false;">{{$nav.messages.mark.1}}</a></li>
- <li class="empty">{{$emptynotifications}}</li>
- </ul>
- </li>
- {{/if}}
- {{if $nav.all_events}}
- <li class="{{$sel.all_events}} all_events-button" style="display: none;">
- <a class="{{$nav.all_events.2}}" href="#" title="{{$nav.all_events.3}}" id="{{$nav.all_events.4}}" data-toggle="dropdown" rel="#nav-all_events-menu">
- <i class="fa fa-fw fa-calendar"></i>
- <span class="all_events-update badge"></span>
- </a>
- <ul id="nav-all_events-menu" class="dropdown-menu" rel="all_events">
- <li id="nav-all_events-see-all"><a href="{{$nav.all_events.all.0}}">{{$nav.all_events.all.1}}</a></li>
- <li id="nav-all_events-mark-all"><a href="#" onclick="markRead('all_events'); return false;">{{$nav.all_events.mark.1}}</a></li>
- <li class="empty">{{$emptynotifications}}</li>
- </ul>
- </li>
- {{/if}}
- {{if $nav.intros}}
- <li class="{{$sel.intros}} intro-button" style="display: none;">
- <a class="{{$nav.intros.2}}" href="{{$nav.intros.0}}" title="{{$nav.intros.3}}" id="{{$nav.intros.4}}" data-toggle="dropdown" rel="#nav-intros-menu">
- <i class="fa fa-fw fa-users"></i>
- <span class="intro-update badge"></span>
- </a>
- <ul id="nav-intros-menu" class="dropdown-menu" rel="intros">
- <li id="nav-intros-see-all"><a href="{{$nav.intros.all.0}}">{{$nav.intros.all.1}}</a></li>
- <li class="empty">{{$emptynotifications}}</li>
- </ul>
- </li>
- {{/if}}
- {{if $nav.notifications}}
- <li class="{{$sel.notifications}} notify-button" style="display: none;">
- <a href="{{$nav.notifications.0}}" title="{{$nav.notifications.1}}" id="{{$nav.notifications.4}}" data-toggle="dropdown" rel="#nav-notify-menu">
- <i class="fa fa-fw fa-exclamation"></i>
- <span class="notify-update badge"></span>
- </a>
- <ul id="nav-notify-menu" class="dropdown-menu" rel="notify">
- <li id="nav-notify-see-all"><a href="{{$nav.notifications.all.0}}">{{$nav.notifications.all.1}}</a></li>
- <li id="nav-notify-mark-all"><a href="#" onclick="markRead('notify'); return false;">{{$nav.notifications.mark.1}}</a></li>
- <li class="empty">{{$emptynotifications}}</li>
- </ul>
- </li>
- {{/if}}
- {{if $nav.login && !$userinfo}}
- <li class="">
- <a href="#" title="{{$nav.loginmenu.1.3}}" id="{{$nav.loginmenu.1.4}}" data-toggle="modal" data-target="#nav-login">{{$nav.loginmenu.1.1}}</a>
- </li>
- {{/if}}
- {{if $nav.register}}
- <li class="{{$nav.register.2}} hidden-xs"><a href="{{$nav.register.0}}" title="{{$nav.register.3}}" id="{{$nav.register.4}}">{{$nav.register.1}}</a></li>
- {{/if}}
- {{if $nav.alogout}}
- <li class="{{$nav}}-alogout.2 hidden-xs"><a href="{{$nav.alogout.0}}" title="{{$nav.alogout.3}}" id="{{$nav.alogout.4}}">{{$nav.alogout.1}}</a></li>
- {{/if}}
- </ul>
- <ul class="nav navbar-nav navbar-right hidden-xs">
- <li class="">
- <form method="get" action="search" role="search">
- <div id="nav-search-spinner"></div><input class="fa-search" id="nav-search-text" type="text" value="" placeholder="&#xf002; {{$help}}" name="search" title="{{$nav.search.3}}" onclick="this.submit();"/>
- </form>
- </li>
- {{if $nav.help.6}}
- <li class="{{$sel.help}}">
- <a class="{{$nav.help.2}}" target="hubzilla-help" href="{{$nav.help.0}}" title="{{$nav.help.3}}" id="{{$nav.help.4}}" onclick="contextualHelp(); return false;"><i class="fa fa-question-circle"></i></a>
- </li>
- {{/if}}
- <li class="">
- <a href="#" data-toggle="dropdown"><i class="fa fa-bars"></i></a>
- <ul class="dropdown-menu">
- {{foreach $navapps as $navapp}}
- {{$navapp}}
- {{/foreach}}
- {{if $localuser}}
- <li class="divider"></li>
- <li><a href="/apps"><i class="generic-icons-nav fa fa-fw fa-plus-circle"></i>Add Apps</a></li>
- {{/if}}
- </ul>
- </li>
- </ul>
- </div>
- <div class="collapse navbar-collapse" id="navbar-collapse-2">
- <ul class="nav navbar-nav navbar-left hidden-sm hidden-md hidden-lg">
- {{foreach $navapps as $navapp}}
- {{$navapp}}
- {{/foreach}}
- {{if $localuser}}
- <li class="divider"></li>
- <li><a href="/apps"><i class="generic-icons-nav fa fa-fw fa-plus-circle"></i>Add Apps</a></li>
- {{/if}}
- </ul>
- </div>
-
- {{if $nav.help.6}}
- <div id="contextual-help-content" class="contextual-help-content">
- {{$nav.help.5}}
- <div class="pull-right">
- <a class="contextual-help-tool btn btn-primary btn-xs" target="hubzilla-help" href="{{$nav.help.0}}" title="{{$nav.help.3}}"><i class="fa fa-question"></i>&nbsp;{{$fulldocs}}</a>
- <a class="contextual-help-tool btn btn-default btn-xs" href="#" onclick="contextualHelp(); return false;"><i class="fa fa-times"></i></a>
- </div>
- </div>
- {{/if}}
-</div>
diff --git a/view/tpl/nav_login.tpl b/view/tpl/nav_login.tpl
index 8f106b41c..4a94908f0 100644
--- a/view/tpl/nav_login.tpl
+++ b/view/tpl/nav_login.tpl
@@ -3,13 +3,12 @@
<div class="modal-dialog" role="document">
<div class="modal-content">
<div class="modal-header">
+ <h4 class="modal-title">{{$nav.loginmenu.1.1}}</h4>
<button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">&times;</span></button>
- <h3 class="modal-title">{{$nav.loginmenu.1.1}}</h3>
</div>
<div class="modal-body">
<div class="form-group">
{{$nav.login}}
- {{$nav.remote_login}}
</div>
</div>
</div>
diff --git a/view/tpl/navbar_default.tpl b/view/tpl/navbar_default.tpl
new file mode 100755
index 000000000..b330993c8
--- /dev/null
+++ b/view/tpl/navbar_default.tpl
@@ -0,0 +1,207 @@
+{{if $nav.login && !$userinfo}}
+<div class="d-xl-none pt-1 pb-1">
+ {{if $nav.loginmenu.1.4}}
+ <a class="btn btn-primary btn-sm text-white" href="#" title="{{$nav.loginmenu.1.3}}" id="{{$nav.loginmenu.1.4}}_collapse" data-toggle="modal" data-target="#nav-login">
+ {{$nav.loginmenu.1.1}}
+ </a>
+ {{else}}
+ <a class="btn btn-primary btn-sm text-white" href="login" title="{{$nav.loginmenu.1.3}}">
+ {{$nav.loginmenu.1.1}}
+ </a>
+ {{/if}}
+ {{if $nav.register}}
+ <a class="btn btn-warning btn-sm text-dark" href="{{$nav.register.0}}" title="{{$nav.register.3}}" id="{{$nav.register.4}}" >
+ {{$nav.register.1}}
+ </a>
+ {{/if}}
+</div>
+{{/if}}
+{{if $userinfo}}
+<div class="dropdown usermenu">
+ <div class="fakelink" data-toggle="dropdown">
+ <img id="avatar" src="{{$userinfo.icon}}" alt="{{$userinfo.name}}">
+ <i class="fa fa-caret-down"></i>
+ </div>
+ {{if $is_owner}}
+ <div class="dropdown-menu">
+ {{foreach $nav.usermenu as $usermenu}}
+ <a class="dropdown-item{{if $usermenu.2}} active{{/if}}" href="{{$usermenu.0}}" title="{{$usermenu.3}}" role="menuitem" id="{{$usermenu.4}}">{{$usermenu.1}}</a>
+ {{/foreach}}
+ {{if $nav.manage}}
+ <a class="dropdown-item{{if $sel.name == Manage}} active{{/if}}" href="{{$nav.manage.0}}" title="{{$nav.manage.3}}" role="menuitem" id="{{$nav.manage.4}}">{{$nav.manage.1}}</a>
+ {{/if}}
+ {{if $nav.channels}}
+ {{foreach $nav.channels as $chan}}
+ <a class="dropdown-item" href="manage/{{$chan.channel_id}}" title="{{$chan.channel_name}}" role="menuitem"><i class="fa fa-circle{{if $localuser == $chan.channel_id}} text-success{{else}} invisible{{/if}}"></i> {{$chan.channel_name}}</a>
+ {{/foreach}}
+ {{/if}}
+ {{if $nav.profiles}}
+ <a class="dropdown-item" href="{{$nav.profiles.0}}" title="{{$nav.profiles.3}}" role="menuitem" id="{{$nav.profiles.4}}">{{$nav.profiles.1}}</a>
+ {{/if}}
+ {{if $nav.settings}}
+ <div class="dropdown-divider"></div>
+ <a class="dropdown-item{{if $sel.name == Settings}} active{{/if}}" href="{{$nav.settings.0}}" title="{{$nav.settings.3}}" role="menuitem" id="{{$nav.settings.4}}">{{$nav.settings.1}}</a>
+ {{/if}}
+ {{if $nav.admin}}
+ <div class="dropdown-divider"></div>
+ <a class="dropdown-item{{if $sel.name == Admin}} active{{/if}}" href="{{$nav.admin.0}}" title="{{$nav.admin.3}}" role="menuitem" id="{{$nav.admin.4}}">{{$nav.admin.1}}</a>
+ {{/if}}
+ {{if $nav.logout}}
+ <div class="dropdown-divider"></div>
+ <a class="dropdown-item" href="{{$nav.logout.0}}" title="{{$nav.logout.3}}" role="menuitem" id="{{$nav.logout.4}}">{{$nav.logout.1}}</a>
+ {{/if}}
+ </div>
+ {{/if}}
+ {{if ! $is_owner}}
+ <div class="dropdown-menu" role="menu" aria-labelledby="avatar">
+ <a class="dropdown-item" href="{{$nav.rusermenu.0}}" role="menuitem">{{$nav.rusermenu.1}}</a>
+ <a class="dropdown-item" href="{{$nav.rusermenu.2}}" role="menuitem">{{$nav.rusermenu.3}}</a>
+ </div>
+ {{/if}}
+</div>
+<div class="navbar-nav mr-auto">
+ <div><a id="nav-app-link" href="{{$url}}" class="nav-link">{{$sel.name}}</a></div>
+</div>
+{{/if}}
+<div class="navbar-toggler-right">
+ {{if $nav.help.6}}
+ <button id="context-help-btn" class="navbar-toggler border-0" type="button" onclick="contextualHelp(); return false;">
+ <i class="fa fa-question-circle"></i>
+ </button>
+ {{/if}}
+ <button id="expand-aside" type="button" class="d-md-none navbar-toggler border-0" data-toggle="offcanvas" data-target="#region_1">
+ <i class="fa fa-arrow-circle-right" id="expand-aside-icon"></i>
+ </button>
+ {{if $localuser || $nav.pubs}}
+ <button id="notifications-btn" type="button" class="navbar-toggler border-0 text-white">
+ <i id="notifications-btn-icon" class="fa fa-exclamation-circle"></i>
+ </button>
+ {{/if}}
+ <button id="menu-btn" class="navbar-toggler border-0" type="button" data-toggle="collapse" data-target="#navbar-collapse-2">
+ <i class="fa fa-bars"></i>
+ </button>
+</div>
+<div class="collapse navbar-collapse" id="navbar-collapse-1">
+ <ul class="navbar-nav mr-auto">
+ {{if $nav.login && !$userinfo}}
+ <li class="nav-item d-none d-xl-flex">
+ {{if $nav.loginmenu.1.4}}
+ <a class="nav-link" href="#" title="{{$nav.loginmenu.1.3}}" id="{{$nav.loginmenu.1.4}}" data-toggle="modal" data-target="#nav-login">
+ {{$nav.loginmenu.1.1}}
+ </a>
+ {{else}}
+ <a class="nav-link" href="login" title="{{$nav.loginmenu.1.3}}">
+ {{$nav.loginmenu.1.1}}
+ </a>
+ {{/if}}
+ </li>
+ {{/if}}
+ {{if $nav.register}}
+ <li class="nav-item {{$nav.register.2}} d-none d-xl-flex">
+ <a class="nav-link" href="{{$nav.register.0}}" title="{{$nav.register.3}}" id="{{$nav.register.4}}">{{$nav.register.1}}</a>
+ </li>
+ {{/if}}
+ {{if $nav.alogout}}
+ <li class="nav-item {{$nav.alogout.2}} d-none d-xl-flex">
+ <a class="nav-link" href="{{$nav.alogout.0}}" title="{{$nav.alogout.3}}" id="{{$nav.alogout.4}}">{{$nav.alogout.1}}</a>
+ </li>
+ {{/if}}
+ </ul>
+
+ <div id="banner" class="navbar-text">{{$banner}}</div>
+
+ <ul id="nav-right" class="navbar-nav ml-auto">
+ <li class="nav-item collapse clearfix" id="nav-search">
+ <form class="form-inline" method="get" action="search" role="search">
+ <input class="form-control form-control-sm mt-1 mr-2" id="nav-search-text" type="text" value="" placeholder="&#xf002; {{$help}}" name="search" title="{{$nav.search.3}}" onclick="this.submit();" onblur="closeMenu('nav-search'); openMenu('nav-search-btn');"/>
+ </form>
+ <div id="nav-search-spinner" class="spinner-wrapper">
+ <div class="spinner s"></div>
+ </div>
+ </li>
+ <li class="nav-item" id="nav-search-btn">
+ <a class="nav-link" href="#nav-search" title="{{$nav.search.3}}" onclick="openMenu('nav-search'); closeMenu('nav-search-btn'); $('#nav-search-text').focus(); return false;"><i class="fa fa-fw fa-search"></i></a>
+ </li>
+ {{if $nav.help.6}}
+ <li class="nav-item dropdown {{$sel.help}}">
+ <a class="nav-link {{$nav.help.2}}" target="hubzilla-help" href="{{$nav.help.0}}" title="{{$nav.help.3}}" id="{{$nav.help.4}}" onclick="contextualHelp(); return false;"><i class="fa fa-fw fa-question-circle"></i></a>
+ </li>
+ {{/if}}
+ {{if $channel_menu && $channel_apps.0}}
+ <li class="nav-item dropdown" id="channel-menu">
+ <a class="nav-link" href="#" data-toggle="dropdown"><img src="{{$channel_thumb}}" style="height:14px; width:14px;position:relative; top:-2px;" /></a>
+ <div id="dropdown-menu" class="dropdown-menu dropdown-menu-right">
+ {{foreach $channel_apps as $channel_app}}
+ {{$channel_app}}
+ {{/foreach}}
+ </div>
+ </li>
+ {{/if}}
+ {{if $navbar_apps}}
+ {{foreach $navbar_apps as $navbar_app}}
+ <li>
+ {{$navbar_app}}
+ </li>
+ {{/foreach}}
+ {{/if}}
+ <li class="nav-item dropdown" id="app-menu">
+ <a class="nav-link" href="#" data-toggle="dropdown"><i class="fa fa-fw fa-bars"></i></a>
+ <div id="dropdown-menu" class="dropdown-menu dropdown-menu-right">
+ {{if $channel_apps.0 && ! $channel_menu}}
+ {{foreach $channel_apps as $channel_app}}
+ {{$channel_app}}
+ {{/foreach}}
+ <div class="dropdown-divider"></div>
+ <div class="dropdown-header sys-apps-toggle" onclick="$('#dropdown-menu').click(function(e) { e.stopPropagation(); }); openClose('sys_apps');">
+ {{$sysapps_toggle}}
+ </div>
+ <div id="sys_apps" style="display:none;">
+ {{/if}}
+ {{foreach $nav_apps as $nav_app}}
+ {{$nav_app}}
+ {{/foreach}}
+ {{if $channel_apps.0 && ! $channel_menu}}
+ </div>
+ {{/if}}
+ {{if $is_owner}}
+ <div class="dropdown-divider"></div>
+ <a class="dropdown-item" href="/apps"><i class="generic-icons-nav fa fa-fw fa-plus-circle"></i>{{$addapps}}</a>
+ <a class="dropdown-item" href="/apporder"><i class="generic-icons-nav fa fa-fw fa-sort"></i>{{$orderapps}}</a>
+ {{/if}}
+ </div>
+ </li>
+ </ul>
+</div>
+<div class="collapse d-xl-none" id="navbar-collapse-2">
+ <div class="navbar-nav mr-auto">
+ {{if $channel_apps.0}}
+ {{foreach $channel_apps as $channel_app}}
+ {{$channel_app|replace:'dropdown-item':'nav-link'}}
+ {{/foreach}}
+ <div class="dropdown-header sys-apps-toggle" onclick="openClose('sys-apps-collapsed');">
+ {{$sysapps_toggle}}
+ </div>
+ <div id="sys-apps-collapsed" style="display:none;">
+ {{/if}}
+ {{foreach $nav_apps as $nav_app}}
+ {{$nav_app|replace:'dropdown-item':'nav-link'}}
+ {{/foreach}}
+ {{if $channel_apps.0}}
+ </div>
+ {{/if}}
+ {{if $is_owner}}
+ <div class="dropdown-divider"></div>
+ <a class="nav-link" href="/apps"><i class="generic-icons-nav fa fa-fw fa-plus-circle"></i>{{$addapps}}</a>
+ <a class="nav-link" href="/apporder"><i class="generic-icons-nav fa fa-fw fa-sort"></i>{{$orderapps}}</a>
+ {{/if}}
+ </div>
+</div>
+{{if $nav.help.6}}
+<div id="contextual-help-content" class="contextual-help-content">
+ {{$nav.help.5}}
+ <div class="float-right">
+ <a class="btn btn-primary btn-sm" target="hubzilla-help" href="{{$nav.help.0}}" title="{{$nav.help.3}}"><i class="fa fa-question"></i>&nbsp;{{$fulldocs}}</a>
+ <a class="contextual-help-tool" href="#" onclick="contextualHelp(); return false;"><i class="fa fa-times"></i></a>
+ </div>
+</div>
+{{/if}}
diff --git a/view/tpl/navbar_tucson.tpl b/view/tpl/navbar_tucson.tpl
new file mode 100755
index 000000000..faf8b5b4a
--- /dev/null
+++ b/view/tpl/navbar_tucson.tpl
@@ -0,0 +1,293 @@
+{{if $nav.login && !$userinfo}}
+<div class="d-xl-none pt-1 pb-1">
+ {{if $nav.loginmenu.1.4}}
+ <a class="btn btn-primary btn-sm text-white" href="#" title="{{$nav.loginmenu.1.3}}" id="{{$nav.loginmenu.1.4}}_collapse" data-toggle="modal" data-target="#nav-login">
+ {{$nav.loginmenu.1.1}}
+ </a>
+ {{else}}
+ <a class="btn btn-primary btn-sm text-white" href="login" title="{{$nav.loginmenu.1.3}}">
+ {{$nav.loginmenu.1.1}}
+ </a>
+ {{/if}}
+ {{if $nav.register}}
+ <a class="btn btn-warning btn-sm text-dark" href="{{$nav.register.0}}" title="{{$nav.register.3}}" id="{{$nav.register.4}}" >
+ {{$nav.register.1}}
+ </a>
+ {{/if}}
+</div>
+{{/if}}
+
+
+
+{{if $userinfo}}
+<div class="dropdown usermenu">
+ <div class="fakelink" data-toggle="dropdown">
+ <img id="avatar" src="{{$userinfo.icon}}" alt="{{$userinfo.name}}">
+ <i class="fa fa-caret-down"></i>
+ </div>
+ {{if $is_owner}}
+ <div class="dropdown-menu">
+ {{foreach $nav.usermenu as $usermenu}}
+ <a class="dropdown-item{{if $usermenu.2}} active{{/if}}" href="{{$usermenu.0}}" title="{{$usermenu.3}}" role="menuitem" id="{{$usermenu.4}}">{{$usermenu.1}}</a>
+ {{/foreach}}
+ {{if $nav.manage}}
+ <a class="dropdown-item{{if $sel.active == Manage}} active{{/if}}" href="{{$nav.manage.0}}" title="{{$nav.manage.3}}" role="menuitem" id="{{$nav.manage.4}}">{{$nav.manage.1}}</a>
+ {{/if}}
+ {{if $nav.channels}}
+ {{foreach $nav.channels as $chan}}
+ <a class="dropdown-item" href="manage/{{$chan.channel_id}}" title="{{$chan.channel_name}}" role="menuitem"><i class="fa fa-circle{{if $localuser == $chan.channel_id}} text-success{{else}} invisible{{/if}}"></i> {{$chan.channel_name}}</a>
+ {{/foreach}}
+ {{/if}}
+ {{if $nav.profiles}}
+ <a class="dropdown-item" href="{{$nav.profiles.0}}" title="{{$nav.profiles.3}}" role="menuitem" id="{{$nav.profiles.4}}">{{$nav.profiles.1}}</a>
+ {{/if}}
+ {{if $nav.settings}}
+ <div class="dropdown-divider"></div>
+ <a class="dropdown-item{{if $sel.active == Settings}} active{{/if}}" href="{{$nav.settings.0}}" title="{{$nav.settings.3}}" role="menuitem" id="{{$nav.settings.4}}">{{$nav.settings.1}}</a>
+ {{/if}}
+ {{if $nav.logout}}
+ <div class="dropdown-divider"></div>
+ <a class="dropdown-item" href="{{$nav.logout.0}}" title="{{$nav.logout.3}}" role="menuitem" id="{{$nav.logout.4}}">{{$nav.logout.1}}</a>
+ {{/if}}
+ </div>
+ {{/if}}
+
+ {{if ! $is_owner}}
+ <div class="dropdown-menu" role="menu" aria-labelledby="avatar">
+ <a class="dropdown-item" href="{{$nav.rusermenu.0}}" role="menuitem">{{$nav.rusermenu.1}}</a>
+ <a class="dropdown-item" href="{{$nav.rusermenu.2}}" role="menuitem">{{$nav.rusermenu.3}}</a>
+ </div>
+ {{/if}}
+</div>
+{{/if}}
+
+
+
+{{if $navbar_apps}}
+<ul class="navbar-nav mr-auto d-none d-xl-flex">
+{{foreach $navbar_apps as $navbar_app}}
+<li>
+{{$navbar_app}}
+</li>
+{{/foreach}}
+</ul>
+{{/if}}
+
+
+<div class="navbar-toggler-right">
+
+ {{if $nav.help.6}}
+ <button id="context-help-btn" class="navbar-toggler border-0" type="button" onclick="contextualHelp(); return false;">
+ <i class="fa fa-question-circle"></i>
+ </button>
+ {{/if}}
+
+ <button id="expand-aside" type="button" class="navbar-toggler border-0" data-toggle="offcanvas" data-target="#region_1">
+ <i class="fa fa-arrow-circle-right" id="expand-aside-icon"></i>
+ </button>
+
+ {{if $localuser || $nav.pubs}}
+ <button id="notifications-btn" type="button" class="navbar-toggler border-0 text-white" data-toggle="collapse" data-target="#navbar-collapse-1">
+ <i id="notifications-btn-icon" class="fa fa-exclamation"></i>
+ </button>
+ {{/if}}
+
+ <button id="menu-btn" class="navbar-toggler border-0" type="button" data-toggle="collapse" data-target="#navbar-collapse-2">
+ <i class="fa fa-bars"></i>
+ </button>
+</div>
+
+
+
+
+
+<div class="collapse navbar-collapse" id="navbar-collapse-1">
+
+ <ul class="navbar-nav mr-auto">
+ {{if $nav.network}}
+ <li class="nav-item dropdown network-button" style="display: none;">
+ <a class="nav-link" href="#" title="{{$nav.network.3}}" id="{{$nav.network.4}}" data-toggle="dropdown" rel="#navbar-network-menu">
+ <i class="fa fa-fw fa-th"></i>
+ <span class="badge badge-pill badge-secondary network-update"></span>
+ </a>
+ <div id="navbar-network-menu" class="dropdown-menu" rel="network">
+ <a class="dropdown-item" id="nav-network-see-all" href="{{$nav.network.all.0}}">{{$nav.network.all.1}}</a>
+ <a class="dropdown-item" id="nav-network-mark-all" href="#" onclick="markRead('network'); return false;">{{$nav.network.mark.1}}</a>
+ {{$emptynotifications}}
+ </div>
+ </li>
+ {{/if}}
+ {{if $nav.home}}
+ <li class="nav-item dropdown home-button" style="display: none;">
+ <a class="nav-link" href="#" title="{{$nav.home.3}}" id="{{$nav.home.4}}" data-toggle="dropdown" rel="#navbar-home-menu">
+ <i class="fa fa-fw fa-home"></i>
+ <span class="badge badge-pill badge-danger home-update"></span>
+ </a>
+ <div id="navbar-home-menu" class="dropdown-menu" rel="home">
+ <a class="dropdown-item" id="nav-home-see-all" href="{{$nav.home.all.0}}">{{$nav.home.all.1}}</a>
+ <a class="dropdown-item" id="nav-home-mark-all" href="#" onclick="markRead('home'); return false;">{{$nav.home.mark.1}}</a>
+ {{$emptynotifications}}
+ </div>
+ </li>
+ {{/if}}
+ {{if $nav.messages}}
+ <li class="nav-item dropdown mail-button" style="display: none;">
+ <a class="nav-link" href="#" title="{{$nav.messages.3}}" id="{{$nav.messages.4}}" data-toggle="dropdown" rel="#navbar-mail-menu">
+ <i class="fa fa-fw fa-envelope"></i>
+ <span class="badge badge-pill badge-danger mail-update"></span>
+ </a>
+ <div id="navbar-mail-menu" class="dropdown-menu" rel="messages">
+ <a class="dropdown-item" id="nav-messages-see-all" href="{{$nav.messages.all.0}}">{{$nav.messages.all.1}}</a>
+ <a class="dropdown-item" id="nav-messages-mark-all" href="#" onclick="markRead('messages'); return false;">{{$nav.messages.mark.1}}</a>
+ {{$emptynotifications}}
+ </div>
+ </li>
+ {{/if}}
+ {{if $nav.all_events}}
+ <li class="nav-item dropdown all_events-button" style="display: none;">
+ <a class="nav-link" href="#" title="{{$nav.all_events.3}}" id="{{$nav.all_events.4}}" data-toggle="dropdown" rel="#navbar-all_events-menu">
+ <i class="fa fa-fw fa-calendar"></i>
+ <span class="badge badge-pill badge-secondary all_events-update"></span>
+ </a>
+ <div id="navbar-all_events-menu" class="dropdown-menu" rel="all_events">
+ <a class="dropdown-item" id="nav-all_events-see-all" href="{{$nav.all_events.all.0}}">{{$nav.all_events.all.1}}</a>
+ <a class="dropdown-item" id="nav-all_events-mark-all" href="#" onclick="markRead('all_events'); return false;">{{$nav.all_events.mark.1}}</a>
+ {{$emptynotifications}}
+ </div>
+ </li>
+ {{/if}}
+ {{if $nav.intros}}
+ <li class="nav-item dropdown intros-button" style="display: none;">
+ <a class="nav-link" href="#" title="{{$nav.intros.3}}" id="{{$nav.intros.4}}" data-toggle="dropdown" rel="#navbar-intros-menu">
+ <i class="fa fa-fw fa-users"></i>
+ <span class="badge badge-pill badge-danger intros-update"></span>
+ </a>
+ <div id="navbar-intros-menu" class="dropdown-menu" rel="intros">
+ <a class="dropdown-item" id="nav-intros-see-all" href="{{$nav.intros.all.0}}">{{$nav.intros.all.1}}</a>
+ {{$emptynotifications}}
+ </div>
+ </li>
+ {{/if}}
+ {{if $nav.notifications}}
+ <li class="nav-item dropdown notify-button" style="display: none;">
+ <a class="nav-link" href="#" title="{{$nav.notifications.1}}" id="{{$nav.notifications.4}}" data-toggle="dropdown" rel="#navbar-notify-menu">
+ <i class="fa fa-fw fa-exclamation"></i>
+ <span class="badge badge-pill badge-danger notify-update"></span>
+ </a>
+ <div id="navbar-notify-menu" class="dropdown-menu" rel="notify">
+ <a class="dropdown-item" id="nav-notify-see-all" href="{{$nav.notifications.all.0}}">{{$nav.notifications.all.1}}</a>
+ <a class="dropdown-item" id="nav-notify-mark-all" href="#" onclick="markRead('notify'); return false;">{{$nav.notifications.mark.1}}</a>
+ {{$emptynotifications}}
+ </div>
+ </li>
+ {{/if}}
+
+ {{if $nav.login && !$userinfo}}
+ <li class="nav-item d-none d-xl-flex">
+ {{if $nav.loginmenu.1.4}}
+ <a class="nav-link" href="#" title="{{$nav.loginmenu.1.3}}" id="{{$nav.loginmenu.1.4}}" data-toggle="modal" data-target="#nav-login">
+ {{$nav.loginmenu.1.1}}
+ </a>
+ {{else}}
+ <a class="nav-link" href="login" title="{{$nav.loginmenu.1.3}}">
+ {{$nav.loginmenu.1.1}}
+ </a>
+ {{/if}}
+ </li>
+ {{/if}}
+ {{if $nav.register}}
+ <li class="nav-item {{$nav.register.2}} d-none d-xl-flex">
+ <a class="nav-link" href="{{$nav.register.0}}" title="{{$nav.register.3}}" id="{{$nav.register.4}}">{{$nav.register.1}}</a>
+ </li>
+ {{/if}}
+ {{if $nav.alogout}}
+ <li class="nav-item {{$nav.alogout.2}} d-none d-xl-flex">
+ <a class="nav-link" href="{{$nav.alogout.0}}" title="{{$nav.alogout.3}}" id="{{$nav.alogout.4}}">{{$nav.alogout.1}}</a>
+ </li>
+ {{/if}}
+
+ </ul>
+
+
+
+
+ <div id="banner" class="navbar-text d-none d-xl-flex">{{$banner}}</div>
+
+
+ <ul id="nav-right" class="navbar-nav ml-auto d-none d-xl-flex">
+ <li class="nav-item collapse clearfix" id="nav-search">
+ <form class="form-inline" method="get" action="search" role="search">
+ <input class="form-control form-control-sm mt-1 mr-2" id="nav-search-text" type="text" value="" placeholder="&#xf002; {{$help}}" name="search" title="{{$nav.search.3}}" onclick="this.submit();" onblur="closeMenu('nav-search'); openMenu('nav-search-btn');"/>
+ </form>
+ <div id="nav-search-spinner" class="spinner-wrapper">
+ <div class="spinner s"></div>
+ </div>
+ </li>
+ <li class="nav-item" id="nav-search-btn">
+ <a class="nav-link" href="#nav-search" title="{{$nav.search.3}}" onclick="openMenu('nav-search'); closeMenu('nav-search-btn'); $('#nav-search-text').focus(); return false;"><i class="fa fa-fw fa-search"></i></a>
+ </li>
+ {{if $nav.help.6}}
+ <li class="nav-item dropdown {{$sel.help}}">
+ <a class="nav-link {{$nav.help.2}}" target="hubzilla-help" href="{{$nav.help.0}}" title="{{$nav.help.3}}" id="{{$nav.help.4}}" onclick="contextualHelp(); return false;"><i class="fa fa-fw fa-question-circle"></i></a>
+ </li>
+ {{/if}}
+ {{if $channel_apps.0}}
+ <li class="nav-item dropdown" id="channel-menu">
+ <a class="nav-link" href="#" data-toggle="dropdown"><img src="{{$channel_thumb}}" style="height:14px; width:14px;position:relative; top:-2px;" /></a>
+ <div id="dropdown-menu" class="dropdown-menu dropdown-menu-right">
+ {{foreach $channel_apps as $channel_app}}
+ {{$channel_app}}
+ {{/foreach}}
+ </div>
+ </li>
+ {{/if}}
+ <li class="nav-item dropdown" id="app-menu">
+ <a class="nav-link" href="#" data-toggle="dropdown"><i class="fa fa-fw fa-bars"></i></a>
+ <div id="dropdown-menu" class="dropdown-menu dropdown-menu-right">
+ {{foreach $nav_apps as $nav_app}}
+ {{$nav_app}}
+ {{/foreach}}
+ {{if $is_owner}}
+ <div class="dropdown-divider"></div>
+ <a class="dropdown-item" href="/apps"><i class="generic-icons-nav fa fa-fw fa-plus-circle"></i>{{$addapps}}</a>
+ <a class="dropdown-item" href="/apporder"><i class="generic-icons-nav fa fa-fw fa-sort"></i>{{$orderapps}}</a>
+ {{/if}}
+ </div>
+ </li>
+ </ul>
+</div>
+
+
+<div class="collapse d-xl-none" id="navbar-collapse-2">
+ <div class="navbar-nav mr-auto">
+ {{if $channel_apps.0}}
+ {{foreach $channel_apps as $channel_app}}
+ {{$channel_app|replace:'dropdown-item':'nav-link'}}
+ {{/foreach}}
+ <div class="dropdown-header sys-apps-toggle" onclick="openClose('sys-apps-collapsed');">
+ {{$sysapps_toggle}}
+ </div>
+ <div id="sys-apps-collapsed" style="display:none;">
+ {{/if}}
+ {{foreach $nav_apps as $nav_app}}
+ {{$nav_app|replace:'dropdown-item':'nav-link'}}
+ {{/foreach}}
+ {{if $channel_apps.0}}
+ </div>
+ {{/if}}
+ {{if $is_owner}}
+ <div class="dropdown-divider"></div>
+ <a class="nav-link" href="/apps"><i class="generic-icons-nav fa fa-fw fa-plus-circle"></i>{{$addapps}}</a>
+ <a class="nav-link" href="/apporder"><i class="generic-icons-nav fa fa-fw fa-sort"></i>{{$orderapps}}</a>
+ {{/if}}
+ </div>
+</div>
+{{if $nav.help.6}}
+<div id="contextual-help-content" class="contextual-help-content">
+ {{$nav.help.5}}
+ <div class="float-right">
+ <a class="btn btn-primary btn-sm" target="hubzilla-help" href="{{$nav.help.0}}" title="{{$nav.help.3}}"><i class="fa fa-question"></i>&nbsp;{{$fulldocs}}</a>
+ <a class="contextual-help-tool" href="#" onclick="contextualHelp(); return false;"><i class="fa fa-times"></i></a>
+ </div>
+</div>
+{{/if}}
diff --git a/view/tpl/new_channel.tpl b/view/tpl/new_channel.tpl
index cc1983ac4..c4837064f 100755
--- a/view/tpl/new_channel.tpl
+++ b/view/tpl/new_channel.tpl
@@ -19,10 +19,10 @@
{{/if}}
{{include file="field_input.tpl" field=$name}}
- <div id="name-spinner"></div>
+ <div id="name-spinner" class="spinner-wrapper"><div class="spinner m"></div></div>
{{include file="field_input.tpl" field=$nickname}}
- <div id="nick-spinner"></div>
+ <div id="nick-spinner" class="spinner-wrapper"><div class="spinner m"></div></div>
<button class="btn btn-primary" type="submit" name="submit" id="newchannel-submit-button" value="{{$submit}}">{{$submit}}</button>
<div id="newchannel-submit-end" class="clear"></div>
diff --git a/view/tpl/notifications.tpl b/view/tpl/notifications.tpl
index 0b24da7c3..53ff8de52 100755
--- a/view/tpl/notifications.tpl
+++ b/view/tpl/notifications.tpl
@@ -1,11 +1,11 @@
-<div class="generic-content-wrapper-styled">
-
-<h1>{{$notif_header}}</h1>
-
-{{if $notifications_available}}
-<a href="#" onclick="markRead('notify'); setTimeout(function() { window.location.href=window.location.href; },1500); return false;">{{$notif_link_mark_seen}}</a>
-{{/if}}
-<div class="notif-network-wrapper">
- {{$notif_content}}
-</div>
+<div class="generic-content-wrapper">
+ <div class="section-title-wrapper clearfix">
+ {{if $notifications_available}}
+ <a href="#" class="btn btn-outline-secondary btn-sm float-right" onclick="markRead('notify'); setTimeout(function() { window.location.href=window.location.href; },1500); return false;">{{$notif_link_mark_seen}}</a>
+ {{/if}}
+ <h2>{{$notif_header}}</h2>
+ </div>
+ <div class="section-content-wrapper">
+ {{$notif_content}}
+ </div>
</div>
diff --git a/view/tpl/notifications_widget.tpl b/view/tpl/notifications_widget.tpl
new file mode 100644
index 000000000..6865879ad
--- /dev/null
+++ b/view/tpl/notifications_widget.tpl
@@ -0,0 +1,62 @@
+<style>
+ .notification-content {
+ max-height: 70vh;
+ overflow: auto;
+ }
+
+ .notification-content.collapsing {
+ overflow: hidden;
+ }
+
+ .fs {
+ position: fixed;
+ top: 0px;
+ left: 0px;
+ padding: 4.5rem .5rem 1rem .5rem;
+ background-color: white;
+ width: 100%;
+ max-width: 100%;
+ height: 100%;
+ z-index: 1029;
+ overflow: auto;
+ }
+
+ #notifications {
+ margin-bottom: 1rem;
+ }
+</style>
+
+{{if $notifications}}
+<div id="notifications_wrapper">
+ <div id="notifications" class="navbar-nav" data-children=".nav-item">
+ <div id="nav-notifications-template" rel="template">
+ <a class="list-group-item clearfix notification {5}" href="{0}" title="{2} {3}">
+ <img class="menu-img-3" data-src="{1}">
+ <span class="contactname">{2}</span>
+ <span class="dropdown-sub-text">{3}<br>{4}</span>
+ </a>
+ </div>
+ {{foreach $notifications as $notification}}
+ <div class="collapse {{$notification.type}}-button">
+ <a class="list-group-item" href="#nav-{{$notification.type}}-menu" title="{{$notification.title}}" data-toggle="collapse" data-parent="#notifications" rel="#nav-{{$notification.type}}-menu">
+ <i class="fa fa-fw fa-{{$notification.icon}}"></i> {{$notification.label}}
+ <span class="float-right badge badge-{{$notification.severity}} {{$notification.type}}-update"></span>
+ </a>
+ <div id="nav-{{$notification.type}}-menu" class="collapse notification-content" rel="{{$notification.type}}">
+ {{if $notification.viewall}}
+ <a class="list-group-item text-dark" id="nav-{{$notification.type}}-see-all" href="{{$notification.viewall.url}}">
+ <i class="fa fa-fw fa-external-link"></i> {{$notification.viewall.label}}
+ </a>
+ {{/if}}
+ {{if $notification.markall}}
+ <a class="list-group-item text-dark" id="nav-{{$notification.type}}-mark-all" href="{{$notification.markall.url}}" onclick="markRead('{{$notification.type}}'); return false;">
+ <i class="fa fa-fw fa-check"></i> {{$notification.markall.label}}
+ </a>
+ {{/if}}
+ {{$loading}}
+ </div>
+ </div>
+ {{/foreach}}
+ </div>
+</div>
+{{/if}}
diff --git a/view/tpl/notify.tpl b/view/tpl/notify.tpl
index d3c79be82..b5bccc8a4 100755
--- a/view/tpl/notify.tpl
+++ b/view/tpl/notify.tpl
@@ -1,3 +1,10 @@
-<div class="notif-item">
- <a href="{{$item_link}}"><img src="{{$item_image}}" class="notif-image">{{$item_text}} <span class="notif-when">{{$item_when}}</span></a>
+<div class="mb-4 notif-item">
+ {{if ! $item_seen}}
+ <span class="float-right badge badge-pill badge-success text-uppercase">{{$new}}</span>
+ {{/if}}
+ <a href="{{$item_link}}">
+ <img src="{{$item_image}}" class="menu-img-3">
+ <span class="{{if $item_seen}}text-muted{{/if}}">{{$item_text}}</span><br>
+ <span class="dropdown-sub-text">{{$item_when}}</span>
+ </a>
</div>
diff --git a/view/tpl/nwiki_page_history.tpl b/view/tpl/nwiki_page_history.tpl
index d99f83863..b1c6c9284 100644
--- a/view/tpl/nwiki_page_history.tpl
+++ b/view/tpl/nwiki_page_history.tpl
@@ -39,17 +39,17 @@
background:rgb(224,255,224);
}
</style>
-<table class="table-striped table-responsive table-hover" style="width: 100%;">
+<table class="" style="width: 100%;">
{{foreach $pageHistory as $commit}}
- <tr><td>
- <table id="rev-{{$commit.revision}}" onclick="$('#details-{{$commit.revision}}').show()" width="100%">
+ <tr class="wikis-index-row"><td>
+ <table id="rev-{{$commit.revision}}" onclick="$('#details-{{$commit.revision}}').show()" style="width: 100%;">
<tr><td width="10%">Date</td><td width="70%">{{$commit.date}}</td>
<td rowspan="3" width="20%" align="right">
{{if $permsWrite}}
- <button id="revert-{{$commit.revision}}" class="btn btn-danger btn-xs" onclick="wiki_revert_page('{{$commit.revision}}')">Revert</button>
+ <button id="revert-{{$commit.revision}}" class="btn btn-danger btn-sm" onclick="wiki_revert_page('{{$commit.revision}}')">Revert</button>
<br><br>
{{/if}}
- <button id="compare-{{$commit.revision}}" class="btn btn-warning btn-xs" onclick="wiki_compare_page('{{$commit.revision}}')">Compare</button>
+ <button id="compare-{{$commit.revision}}" class="btn btn-warning btn-sm" onclick="wiki_compare_page('{{$commit.revision}}')">Compare</button>
</td></tr>
<tr><td>{{$name_lbl}}</td><td>{{$commit.name}}</td></tr>
<tr><td>{{$msg_label}}</td><td>{{$commit.title}}</td></tr>
diff --git a/view/tpl/page_display_empty.tpl b/view/tpl/page_display_empty.tpl
new file mode 100644
index 000000000..9f000dee8
--- /dev/null
+++ b/view/tpl/page_display_empty.tpl
@@ -0,0 +1 @@
+{{$body}} \ No newline at end of file
diff --git a/view/tpl/pdledit.tpl b/view/tpl/pdledit.tpl
index cef93d324..2ea89b6c1 100644
--- a/view/tpl/pdledit.tpl
+++ b/view/tpl/pdledit.tpl
@@ -5,6 +5,9 @@
<br />
<a href="help/comanche" target="hubzilla-help">{{$help}}</a>
+<br>
+<br>
+<a href="pdledit">{{$another}}</a>
<br />
<br />
diff --git a/view/tpl/peoplefind.tpl b/view/tpl/peoplefind.tpl
index ae0b7f1ea..2ecfbaff9 100755
--- a/view/tpl/peoplefind.tpl
+++ b/view/tpl/peoplefind.tpl
@@ -1,19 +1,17 @@
<div id="peoplefind-sidebar" class="widget">
<h3>{{$findpeople}}</h3>
<form action="directory" method="post" />
- <div class="form-group">
- <div class="input-group">
- <input class="widget-input" type="text" name="search" title="{{$hint}}{{if $advanced_search}}{{$advanced_hint}}{{/if}}" placeholder="{{$desc}}" />
- <div class="input-group-btn">
- <button class="btn btn-default btn-sm" type="submit" name="submit"><i class="fa fa-search"></i></button>
- </div>
+ <div class="input-group form-group">
+ <input class="form-control form-control-sm" type="text" name="search" title="{{$hint}}{{if $advanced_search}}{{$advanced_hint}}{{/if}}" placeholder="{{$desc}}" />
+ <div class="input-group-btn">
+ <button class="btn btn-outline-secondary" type="submit" name="submit"><i class="fa fa-fw fa-search"></i></button>
</div>
</div>
</form>
- <ul class="nav nav-pills nav-stacked">
- {{if $similar}}<li><a href="match" >{{$similar}}</a></li>{{/if}}
- {{if $loggedin}}<li><a href="directory?suggest=1" >{{$suggest}}</a></li>{{/if}}
- <li><a href="randprof" >{{$random}}</a></li>
- {{if $loggedin}}{{if $inv}}<li><a href="invite" >{{$inv}}</a></li>{{/if}}{{/if}}
+ <ul class="nav nav-pills flex-column">
+ {{if $similar}}<li class="nav-item"><a class="nav-link" href="match" >{{$similar}}</a></li>{{/if}}
+ {{if $loggedin}}<li class="nav-item"><a class="nav-link" href="directory?suggest=1" >{{$suggest}}</a></li>{{/if}}
+ <li class="nav-item"><a class="nav-link" href="randprof" >{{$random}}</a></li>
+ {{if $loggedin}}{{if $inv}}<li class="nav-item"><a class="nav-link" href="invite" >{{$inv}}</a></li>{{/if}}{{/if}}
</ul>
</div>
diff --git a/view/tpl/photo_album.tpl b/view/tpl/photo_album.tpl
index 6289f5321..58b843bf0 100755
--- a/view/tpl/photo_album.tpl
+++ b/view/tpl/photo_album.tpl
@@ -2,14 +2,14 @@
<div class="section-title-wrapper">
<div class="pull-right">
{{if $order}}
- <a class="btn btn-default btn-xs" href="{{$order.1}}" title="{{$order.0}}"><i class="fa fa-sort"></i></a>
+ <a class="btn btn-outline-secondary btn-sm" href="{{$order.1}}" title="{{$order.0}}"><i class="fa fa-sort"></i></a>
{{/if}}
<div class="btn-group btn-group">
{{if $album_edit.1}}
- <i class="fa fa-pencil btn btn-default btn-xs" title="{{$album_edit.0}}" onclick="openClose('photo-album-edit-wrapper'); closeMenu('photo-upload-form');"></i>
+ <i class="fa fa-pencil btn btn-outline-secondary btn-sm" title="{{$album_edit.0}}" onclick="openClose('photo-album-edit-wrapper'); closeMenu('photo-upload-form');"></i>
{{/if}}
{{if $can_post}}
- <button class="btn btn-xs btn-success btn-xs" title="{{$usage}}" onclick="openClose('photo-upload-form'); closeMenu('photo-album-edit-wrapper');"><i class="fa fa-arrow-circle-o-up"></i>&nbsp;{{$upload.0}}</button>
+ <button class="btn btn-sm btn-success btn-sm" title="{{$usage}}" onclick="openClose('photo-upload-form'); closeMenu('photo-album-edit-wrapper');"><i class="fa fa-arrow-circle-o-up"></i>&nbsp;{{$upload.0}}</button>
{{/if}}
</div>
</div>
@@ -19,7 +19,7 @@
{{$upload_form}}
{{$album_edit.1}}
<div class="section-content-wrapper-np">
- <div id="photo-album-contents-{{$album_id}}">
+ <div id="photo-album-contents-{{$album_id}}" style="display: none">
{{foreach $photos as $photo}}
{{include file="photo_top.tpl"}}
{{/foreach}}
@@ -28,5 +28,12 @@
</div>
</div>
<div class="photos-end"></div>
-<script>$(document).ready(function() { loadingPage = false; justifyPhotos('photo-album-contents-{{$album_id}}'); });</script>
-<div id="page-spinner"></div>
+<div id="page-spinner" class="spinner-wrapper">
+ <div class="spinner m"></div>
+</div>
+<script>
+$(document).ready(function() {
+ loadingPage = false;
+ justifyPhotos('photo-album-contents-{{$album_id}}');
+});
+</script>
diff --git a/view/tpl/photo_album_portfolio.tpl b/view/tpl/photo_album_portfolio.tpl
new file mode 100755
index 000000000..1635e0ae1
--- /dev/null
+++ b/view/tpl/photo_album_portfolio.tpl
@@ -0,0 +1,49 @@
+{{if isset($mode) && $mode == 'orbit'}}
+<div class="row">
+ <div class="orbit small-12 medium-9 large-9 columns" id="photo-album-contents-{{$album_id}}" role="region" aria-label="portfolioOrbit-{{$album_id}}" data-orbit data-options="animInFromLeft:fade-in; animInFromRight:fade-in; animOutToLeft:fade-out; animOutToRight:fade-out;">
+
+ <ul class="orbit-container">
+ <button class="orbit-previous"><span class="show-for-sr">Previous Slide</span>&#9664;&#xFE0E;</button>
+ <button class="orbit-next"><span class="show-for-sr">Next Slide</span>&#9654;&#xFE0E;</button>
+ {{foreach $photos as $photo}}
+ {{include file="photo_portfolio_orbit.tpl"}}
+ {{/foreach}}
+ </ul>
+ <nav class="orbit-bullets">
+ <button class="is-active" data-slide="0"><span class="show-for-sr">First slide details.</span><span class="show-for-sr">Current Slide</span></button>
+ <button data-slide="1"><span class="show-for-sr">Second slide details.</span></button>
+ <button data-slide="2"><span class="show-for-sr">Third slide details.</span></button>
+ <button data-slide="3"><span class="show-for-sr">Fourth slide details.</span></button>
+ </nav>
+ <div id="page-end"></div>
+ </div>
+<div class="photos-end"></div>
+<script>$(document).ready(function() { loadingPage = false; justifyPhotos('photo-album-contents-{{$album_id}}'); });</script>
+<div id="page-spinner"></div>
+</div>
+{{elseif isset($mode) && $mode =='card'}}
+<div class="row">
+ <div class="small-12 medium-9 large-9 columns" id="photo-album-contents-{{$album_id}}">
+ {{foreach $photos as $photo}}
+ {{include file="photo_portfolio_card.tpl"}}
+ {{/foreach}}
+ <div id="page-end"></div>
+ </div>
+<div class="photos-end"></div>
+<script>$(document).ready(function() { loadingPage = false; justifyPhotos('photo-album-contents-{{$album_id}}'); });</script>
+<div id="page-spinner"></div>
+</div>
+{{else}}
+<div class="row column">
+ <div id="photo-album-contents-{{$album_id}}">
+ {{foreach $photos as $photo}}
+ {{include file="photo_portfolio.tpl"}}
+ {{/foreach}}
+ <div id="page-end"></div>
+ </div>
+<div class="photos-end"></div>
+<script>$(document).ready(function() { loadingPage = false; justifyPhotos('photo-album-contents-{{$album_id}}'); });</script>
+<div id="page-spinner"></div>
+</div>
+{{/if}}
+
diff --git a/view/tpl/photo_albums.tpl b/view/tpl/photo_albums.tpl
index de1105bbc..83bdd95e7 100755
--- a/view/tpl/photo_albums.tpl
+++ b/view/tpl/photo_albums.tpl
@@ -1,11 +1,11 @@
<div id="side-bar-photos-albums" class="widget">
<h3>{{$title}}</h3>
- <ul class="nav nav-pills nav-stacked">
- <li><a href="{{$baseurl}}/photos/{{$nick}}" title="{{$title}}" >Recent Photos</a></li>
+ <ul class="nav nav-pills flex-column">
+ <li class="nav-item"><a class="nav-link" href="{{$baseurl}}/photos/{{$nick}}" title="{{$title}}" >{{$recent}}</a></li>
{{if $albums}}
{{foreach $albums as $al}}
- {{if $al.text}}
- <li><a href="{{$baseurl}}/photos/{{$nick}}/album/{{$al.bin2hex}}"><span class="badge pull-right">{{$al.total}}</span>{{$al.text}}</a></li>
+ {{if $al.shorttext}}
+ <li class="nav-item"><a class="nav-link" href="{{$baseurl}}/photos/{{$nick}}/album/{{$al.bin2hex}}"><span class="badge badge-secondary float-right">{{$al.total}}</span>{{$al.shorttext}}</a></li>
{{/if}}
{{/foreach}}
{{/if}}
diff --git a/view/tpl/photo_drop.tpl b/view/tpl/photo_drop.tpl
index 9c0a65d1c..664e5338c 100755
--- a/view/tpl/photo_drop.tpl
+++ b/view/tpl/photo_drop.tpl
@@ -1,3 +1,3 @@
<div class="wall-item-delete-wrapper" id="wall-item-delete-wrapper-{{$id}}" >
- <a class="btn btn-default btn-sm" href="#" onclick="dropItem('item/drop/{{$id}}', '#wall-item-outside-wrapper-{{$id}}'); return false;" title="{{$delete}}" ><i class="fa fa-trash-o"></i></a>
+ <a class="btn btn-outline-secondary btn-sm" href="#" onclick="dropItem('item/drop/{{$id}}', '#wall-item-outside-wrapper-{{$id}}'); return false;" title="{{$delete}}" ><i class="fa fa-trash-o"></i></a>
</div>
diff --git a/view/tpl/photo_item.tpl b/view/tpl/photo_item.tpl
index ec643c4a9..b6ee4508b 100755
--- a/view/tpl/photo_item.tpl
+++ b/view/tpl/photo_item.tpl
@@ -1,10 +1,10 @@
<div class="wall-item-outside-wrapper{{if $indent}} {{$indent}}{{/if}}" id="wall-item-outside-wrapper-{{$id}}" >
- <div class="wall-item-content-wrapper{{if $indent}} {{$indent}}{{/if}}" id="wall-item-content-wrapper-{{$id}}" style="clear:both;">
- <div class="wall-item-head">
+ <div class="clearfix wall-item-content-wrapper{{if $indent}} {{$indent}}{{/if}}" id="wall-item-content-wrapper-{{$id}}">
+ <div class="p-2 clearfix wall-item-head">
<div class="wall-item-info" id="wall-item-info-{{$id}}" >
<div class="wall-item-photo-wrapper" id="wall-item-photo-wrapper-{{$id}}" >
<a href="{{$profile_url}}" title="View {{$name}}'s profile" class="wall-item-photo-link" id="wall-item-photo-link-{{$id}}">
- <img src="{{$thumb}}" class="wall-item-photo" id="wall-item-photo-{{$id}}" style="height: 80px; width: 80px;" alt="{{$name}}" /></a>
+ <img src="{{$thumb}}" class="wall-item-photo" id="wall-item-photo-{{$id}}" alt="{{$name}}" /></a>
</div>
</div>
<div class="wall-item-wrapper" id="wall-item-wrapper-{{$id}}" >
@@ -14,20 +14,18 @@
<div class="wall-item-ago" id="wall-item-ago-{{$id}}">{{$ago}}</div>
</div>
</div>
- <div class="wall-item-content" id="wall-item-content-{{$id}}" >
+ <div class="p-2 clearfix wall-item-content" id="wall-item-content-{{$id}}" >
<div class="wall-item-title" id="wall-item-title-{{$id}}">{{$title}}</div>
<div class="wall-item-body" id="wall-item-body-{{$id}}" >{{$body}}</div>
</div>
{{if $drop}}
- <div class="wall-item-tools" id="wall-item-tools-{{$id}}" >
+ <div class="p-2 clearfix wall-item-tools" id="wall-item-tools-{{$id}}" >
<div class="wall-item-tools-right pull-right">
{{$drop}}
</div>
- <div class="clear"></div>
</div>
{{/if}}
- <div class="clear"></div>
{{$comment}}
</div>
</div>
diff --git a/view/tpl/photo_portfolio.tpl b/view/tpl/photo_portfolio.tpl
new file mode 100755
index 000000000..cbc8ea214
--- /dev/null
+++ b/view/tpl/photo_portfolio.tpl
@@ -0,0 +1,13 @@
+
+
+ <a data-open="portfolioModal-{{$photo.resource_id}}" aria-controls="portfolioModal-{{$photo.resource_id}}" aria-haspopup="true" tabindex="0">
+ <img class="thumbnail" src="{{$photo.src}}" alt="{{if $photo.album.name}}{{$photo.album.name}}{{elseif $photo.desc}}{{$photo.desc}}{{elseif $photo.alt}}{{$photo.alt}}{{else}}{{$photo.unknown}}{{/if}}" title="{{$photo.desc}}" id="photo-top-photo-{{$photo.resource_id}}">
+ </a>
+
+ <div class="full reveal without-overlay" id="portfolioModal-{{$photo.resource_id}}" data-reveal="f175mw-reveal" role="dialog" aria-hidden="true" data-yeti-box="portfolioModal-{{$photo.resource_id}}" data-resize="portfolioModal-{{$photo.resource_id}}">
+ <h5>{{$photo.desc}}</h5>
+ <img class="thumbnail" src="{{$photo.fullsrc}}" alt="{{if $photo.album.name}}{{$photo.album.name}}{{elseif $photo.desc}}{{$photo.desc}}{{elseif $photo.alt}}{{$photo.alt}}{{else}}{{$photo.unknown}}{{/if}}" title="{{$photo.desc}}" id="photo-top-photo-{{$photo.resource_id}}x">
+ <button class="close-button" data-close="" aria-label="Close reveal" type="button">
+ <span aria-hidden="true">×</span>
+ </button>
+ </div>
diff --git a/view/tpl/photo_portfolio_card.tpl b/view/tpl/photo_portfolio_card.tpl
new file mode 100644
index 000000000..5fddd3d37
--- /dev/null
+++ b/view/tpl/photo_portfolio_card.tpl
@@ -0,0 +1,6 @@
+<div class="card" style="width: 300px;box-shadow: 0px 10px 6px -6px rgba(119,119,119,0.6);border-style: solid;border-width: 1px;border=color: rgba(230,230,230,0.6);margin:10px 5px 10px 5px;">
+ <img src="{{$photo.src}}" alt="{{if $photo.album.name}}{{$photo.album.name}}{{elseif $photo.desc}}{{$photo.desc}}{{elseif $photo.alt}}{{$photo.alt}}{{else}}{{$photo.unknown}}{{/if}}" title="{{$photo.desc}}" id="photo-top-photo-{{$photo.resource_id}}">
+ <div class="card-divider">
+ <h4>{{$photo.desc}}</h4>
+ </div>
+</div>
diff --git a/view/tpl/photo_portfolio_orbit.tpl b/view/tpl/photo_portfolio_orbit.tpl
new file mode 100644
index 000000000..b2883265c
--- /dev/null
+++ b/view/tpl/photo_portfolio_orbit.tpl
@@ -0,0 +1,5 @@
+
+ <li class="orbit-slide">
+ <img class="orbit-image" src="{{$photo.src}}" alt="{{if $photo.album.name}}{{$photo.album.name}}{{elseif $photo.desc}}{{$photo.desc}}{{elseif $photo.alt}}{{$photo.alt}}{{else}}{{$photo.unknown}}{{/if}}" title="{{$photo.desc}}" id="photo-top-photo-{{$photo.resource_id}}o">
+ <figcaption class="orbit-caption">{{$photo.desc}}</figcaption>
+ </li>
diff --git a/view/tpl/photo_view.tpl b/view/tpl/photo_view.tpl
index 967abea71..2431329ec 100755
--- a/view/tpl/photo_view.tpl
+++ b/view/tpl/photo_view.tpl
@@ -4,44 +4,36 @@
<div class="pull-right">
{{if $tools || $map || $edit}}
<div class="btn-group">
- <button type="button" class="btn btn-default btn-xs dropdown-toggle" data-toggle="dropdown">
- <i class="fa fa-caret-down"></i>&nbsp;{{$tools_label}}
+ <button type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown">
+ <i class="fa fa-cog"></i>&nbsp;{{$tools_label}}
</button>
- <ul class="dropdown-menu dropdown-menu-right">
+ <div class="dropdown-menu dropdown-menu-right flex-column">
{{if $tools}}
- <li class="nav-item">
- <a class="nav-link" href="{{$tools.profile.0}}"><i class="fa fa-user"></i>&nbsp;{{$tools.profile.1}}</a>
- </li>
- <li class="nav-item">
- <a class="nav-link" href="{{$tools.cover.0}}"><i class="fa fa-picture-o"></i>&nbsp;{{$tools.cover.1}}</a>
- </li>
+ <a class="dropdown-item" href="{{$tools.profile.0}}"><i class="fa fa-user"></i>&nbsp;{{$tools.profile.1}}</a>
+ <a class="dropdown-item" href="{{$tools.cover.0}}"><i class="fa fa-picture-o"></i>&nbsp;{{$tools.cover.1}}</a>
{{/if}}
{{if $map}}
- <li class="nav-item">
- <a class="nav-link" href="#" onclick="var pos = $('#photo-map').css('position'); if(pos === 'absolute') { $('#photo-map').css( { position: 'relative', left: 'auto', top: 'auto' }); } else { $('#photo-map').css( { position: 'absolute', left: '-9999px', top: '-9999px' }); } return false; " ><i class="fa fa-globe"></i>&nbsp;{{$map_text}}</a>
- </li>
+ <a class="dropdown-item" href="#" onclick="var pos = $('#photo-map').css('position'); if(pos === 'absolute') { $('#photo-map').css( { position: 'relative', left: 'auto', top: 'auto' }); } else { $('#photo-map').css( { position: 'absolute', left: '-9999px', top: '-9999px' }); } return false; " ><i class="fa fa-globe"></i>&nbsp;{{$map_text}}</a>
{{/if}}
{{if $edit}}
- <li class="nav-item">
- <a class="nav-link acl-form-trigger" href="#" title="" onclick="openClose('photo-edit'); return false;" data-form_id="photo_edit_form"><i class="fa fa-pencil"></i>&nbsp;{{$edit.edit}}</a>
- </li>
+ <a class="dropdown-item acl-form-trigger" href="#" title="" onclick="openClose('photo-edit'); return false;" data-form_id="photo_edit_form"><i class="fa fa-pencil"></i>&nbsp;{{$edit.edit}}</a>
{{/if}}
- </ul>
+ </div>
</div>
{{/if}}
{{if $lock}}
<div class="btn-group">
- <button id="lockview" class="btn btn-default btn-xs dropdown-toggle" data-toggle="dropdown" title="{{$lock}}" onclick="lockview('photo',{{$id}});" ><i class="fa fa-lock"></i></button>
+ <button id="lockview" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown" title="{{$lock}}" onclick="lockview('photo',{{$id}});" ><i class="fa fa-lock"></i></button>
<ul id="panel-{{$id}}" class="lockview-panel dropdown-menu dropdown-menu-right"></ul>
</div>
{{/if}}
{{if $prevlink || $nextlink}}
<div class="btn-group">
{{if $prevlink}}
- <a href="{{$prevlink.0}}" class="btn btn-default btn-xs" title="{{$prevlink.1}}"><i class="fa fa-backward"></i></a>
+ <a href="{{$prevlink.0}}" class="btn btn-outline-secondary btn-sm" title="{{$prevlink.1}}"><i class="fa fa-backward"></i></a>
{{/if}}
{{if $nextlink}}
- <a href="{{$nextlink.0}}" class="btn btn-default btn-xs" title="{{$nextlink.1}}"><i class="fa fa-forward"></i></a>
+ <a href="{{$nextlink.0}}" class="btn btn-outline-secondary btn-sm" title="{{$nextlink.1}}"><i class="fa fa-forward"></i></a>
{{/if}}
</div>
{{/if}}
@@ -96,7 +88,7 @@
</div>
<div class="form-group btn-group pull-right">
{{if $edit.aclselect}}
- <button id="dbtn-acl" class="btn btn-default btn-sm" data-toggle="modal" data-target="#aclModal" onclick="return false;">
+ <button id="dbtn-acl" class="btn btn-outline-secondary btn-sm" data-toggle="modal" data-target="#aclModal" onclick="return false;">
<i id="jot-perms-icon" class="fa fa-{{$edit.lockstate}}"></i>
</button>
{{/if}}
@@ -124,7 +116,7 @@
{{foreach $responses as $verb=>$response}}
{{if $response.count}}
<div class="btn-group">
- <button type="button" class="btn btn-default btn-sm wall-item-like dropdown-toggle" data-toggle="dropdown" id="wall-item-{{$verb}}-{{$id}}">{{$response.count}} {{$response.button}}</button>
+ <button type="button" class="btn btn-outline-secondary btn-sm wall-item-like dropdown-toggle" data-toggle="dropdown" id="wall-item-{{$verb}}-{{$id}}">{{$response.count}} {{$response.button}}</button>
{{if $response.list_part}}
<ul class="dropdown-menu" role="menu" aria-labelledby="wall-item-{{$verb}}-{{$id}}">{{foreach $response.list_part as $liker}}<li role="presentation">{{$liker}}</li>{{/foreach}}</ul>
{{else}}
@@ -142,7 +134,7 @@
<ul>{{foreach $response.list as $liker}}<li role="presentation">{{$liker}}</li>{{/foreach}}</ul>
</div>
<div class="modal-footer clear">
- <button type="button" class="btn btn-default" data-dismiss="modal">{{$modal_dismiss}}</button>
+ <button type="button" class="btn btn-outline-secondary" data-dismiss="modal">{{$modal_dismiss}}</button>
</div>
</div><!-- /.modal-content -->
</div><!-- /.modal-dialog -->
@@ -156,10 +148,10 @@
{{/if}}
{{if $likebuttons}}
<div class="photo-item-tools-right btn-group pull-right">
- <button type="button" class="btn btn-default btn-sm" onclick="dolike({{$likebuttons.id}},'like'); return false">
+ <button type="button" class="btn btn-outline-secondary btn-sm" onclick="dolike({{$likebuttons.id}},'like'); return false">
<i class="fa fa-thumbs-o-up" title="{{$likebuttons.likethis}}"></i>
</button>
- <button type="button" class="btn btn-default btn-sm" onclick="dolike({{$likebuttons.id}},'dislike'); return false">
+ <button type="button" class="btn btn-outline-secondary btn-sm" onclick="dolike({{$likebuttons.id}},'dislike'); return false">
<i class="fa fa-thumbs-o-down" title="{{$likebuttons.nolike}}"></i>
</button>
</div>
diff --git a/view/tpl/photos_recent.tpl b/view/tpl/photos_recent.tpl
index 92e70692f..a9574aade 100755
--- a/view/tpl/photos_recent.tpl
+++ b/view/tpl/photos_recent.tpl
@@ -2,7 +2,7 @@
<div class="section-title-wrapper">
<div class="pull-right">
{{if $can_post}}
- <button class="btn btn-xs btn-success acl-form-trigger" title="{{$usage}}" onclick="openClose('photo-upload-form');" data-form_id="photos-upload-form"><i class="fa fa-arrow-circle-o-up"></i>&nbsp;{{$upload.0}}</button>
+ <button class="btn btn-sm btn-success acl-form-trigger" title="{{$usage}}" onclick="openClose('photo-upload-form');" data-form_id="photos-upload-form"><i class="fa fa-arrow-circle-o-up"></i>&nbsp;{{$upload.0}}</button>
{{/if}}
</div>
<h2>{{$title}}</h2>
@@ -10,7 +10,7 @@
</div>
{{$upload_form}}
<div class="section-content-wrapper-np">
- <div id="photo-album-contents-{{$album_id}}">
+ <div id="photo-album-contents-{{$album_id}}" style="display: none">
{{foreach $photos as $photo}}
{{include file="photo_top.tpl"}}
{{/foreach}}
@@ -19,5 +19,12 @@
</div>
</div>
<div class="photos-end"></div>
-<script>$(document).ready(function() { loadingPage = false; justifyPhotos('photo-album-contents-{{$album_id}}'); });</script>
-<div id="page-spinner"></div>
+<div id="page-spinner" class="spinner-wrapper">
+ <div class="spinner m"></div>
+</div>
+<script>
+$(document).ready(function() {
+ loadingPage = false;
+ justifyPhotos('photo-album-contents-{{$album_id}}');
+});
+</script>
diff --git a/view/tpl/photos_upload.tpl b/view/tpl/photos_upload.tpl
index 90cd0e84a..d52bad5a2 100755
--- a/view/tpl/photos_upload.tpl
+++ b/view/tpl/photos_upload.tpl
@@ -26,7 +26,7 @@
<div class="pull-right btn-group">
<div class="btn-group">
{{if $lockstate}}
- <button id="dbtn-acl" class="btn btn-default btn-sm" data-toggle="modal" data-target="#aclModal" onclick="return false;">
+ <button id="dbtn-acl" class="btn btn-outline-secondary btn-sm" data-toggle="modal" data-target="#aclModal" onclick="return false;">
<i id="jot-perms-icon" class="fa fa-{{$lockstate}}"></i>
</button>
{{/if}}
@@ -45,7 +45,7 @@
</div>
<div id="photos-upload-perms" class="btn-group pull-right">
{{if $lockstate}}
- <button class="btn btn-default btn-sm" data-toggle="modal" data-target="#aclModal" onclick="return false;">
+ <button class="btn btn-outline-secondary btn-sm" data-toggle="modal" data-target="#aclModal" onclick="return false;">
<i id="jot-perms-icon" class="fa fa-{{$lockstate}}"></i>
</button>
{{/if}}
diff --git a/view/tpl/posted_date_widget.tpl b/view/tpl/posted_date_widget.tpl
index 8b442e4b9..fb43c744b 100755
--- a/view/tpl/posted_date_widget.tpl
+++ b/view/tpl/posted_date_widget.tpl
@@ -3,12 +3,12 @@
function toggle_posted_date_button() {
if($('#posted-date-dropdown').is(':visible')) {
$('#posted-date-icon').removeClass('fa-caret-up');
- $('#posted-date-icon').addClass('fa-caret-down');
+ $('#posted-date-icon').addClass('fa-cog');
$('#posted-date-dropdown').hide();
}
else {
$('#posted-date-icon').addClass('fa-caret-up');
- $('#posted-date-icon').removeClass('fa-caret-down');
+ $('#posted-date-icon').removeClass('fa-cog');
$('#posted-date-dropdown').show();
}
}
@@ -18,21 +18,21 @@ function toggle_posted_date_button() {
<div id="datebrowse-sidebar" class="widget">
<h3>{{$title}}</h3>
<script>function dateSubmit(dateurl) { window.location.href = dateurl; } </script>
- <ul id="posted-date-selector" class="nav nav-pills nav-stacked">
+ <ul id="posted-date-selector" class="nav nav-pills flex-column">
{{foreach $dates as $y => $arr}}
{{if $y == $cutoff_year}}
</ul>
<div id="posted-date-dropdown" style="display: none;">
- <ul id="posted-date-selector-drop" class="nav nav-pills nav-stacked">
+ <ul id="posted-date-selector-drop" class="nav nav-pills flex-column">
{{/if}}
- <li id="posted-date-selector-year-{{$y}}">
- <a href="#" onclick="openClose('posted-date-selector-{{$y}}'); return false;">{{$y}}</a>
+ <li class="nav-item" id="posted-date-selector-year-{{$y}}">
+ <a class="nav-link" href="#" onclick="openClose('posted-date-selector-{{$y}}'); return false;">{{$y}}</a>
</li>
<div id="posted-date-selector-{{$y}}" style="display: none;">
- <ul class="posted-date-selector-months nav nav-pills nav-stacked">
+ <ul class="posted-date-selector-months nav nav-pills flex-column">
{{foreach $arr as $d}}
- <li>
- <a href="#" onclick="dateSubmit('{{$url}}?f=&dend={{$d.1}}{{if $showend}}&dbegin={{$d.2}}{{/if}}'); return false;">{{$d.0}}</a>
+ <li class="nav-item">
+ <a class="nav-link" href="#" onclick="dateSubmit('{{$url}}?f=&dend={{$d.1}}{{if $showend}}&dbegin={{$d.2}}{{/if}}'); return false;">{{$d.0}}</a>
</li>
{{/foreach}}
</ul>
@@ -40,7 +40,7 @@ function toggle_posted_date_button() {
{{/foreach}}
{{if $cutoff}}
</div>
- <button class="btn btn-default btn-sm" onclick="toggle_posted_date_button(); return false;"><i id="posted-date-icon" class="fa fa-caret-down"></i></button>
+ <button class="btn btn-outline-secondary btn-sm" onclick="toggle_posted_date_button(); return false;"><i id="posted-date-icon" class="fa fa-cog"></i></button>
{{/if}}
</ul>
</div>
diff --git a/view/tpl/profile_advanced.tpl b/view/tpl/profile_advanced.tpl
index 4000f39d6..c56062459 100755
--- a/view/tpl/profile_advanced.tpl
+++ b/view/tpl/profile_advanced.tpl
@@ -1,9 +1,9 @@
<div id="profile-content-wrapper" class="generic-content-wrapper">
<div class="section-title-wrapper">
- <div class="pull-right">
+ <div class="float-right">
{{if $profile.like_count}}
<div class="btn-group">
- <button type="button" class="btn btn-default btn-xs dropdown-toggle" data-toggle="dropdown" id="profile-like">{{$profile.like_count}} {{$profile.like_button_label}}</button>
+ <button type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown" id="profile-like">{{$profile.like_count}} {{$profile.like_button_label}}</button>
{{if $profile.likers}}
<ul class="dropdown-menu dropdown-menu-right" role="menu" aria-labelledby="profile-like">{{foreach $profile.likers as $liker}}<li role="presentation"><a href="{{$liker.url}}"><img class="dropdown-menu-img-xs" src="{{$liker.photo}}" alt="{{$liker.name}}" /> {{$liker.name}}</a></li>{{/foreach}}</ul>
{{/if}}
@@ -11,32 +11,32 @@
{{/if}}
{{if $profile.canlike}}
<div class="btn-group">
- <button type="button" class="btn btn-success btn-xs" onclick="doprofilelike('profile/' + '{{$profile.profile_guid}}','like'); return false;" title="{{$profile.likethis}}" >
+ <button type="button" class="btn btn-success btn-sm" onclick="doprofilelike('profile/' + '{{$profile.profile_guid}}','like'); return false;" title="{{$profile.likethis}}" >
<i class="fa fa-thumbs-o-up" title="{{$profile.likethis}}"></i>
</button>
</div>
{{/if}}
{{if $editmenu.multi}}
<div class="btn-group">
- <a class="btn btn-primary btn-xs dropdown-toggle" data-toggle="dropdown" href="#" ><i class="fa fa-pencil"></i>&nbsp;{{$editmenu.edit.3}}</a>
- <ul class="dropdown-menu dropdown-menu-right" role="menu">
+ <a class="btn btn-primary btn-sm dropdown-toggle" data-toggle="dropdown" href="#" ><i class="fa fa-pencil"></i>&nbsp;{{$editmenu.edit.3}}</a>
+ <div class="dropdown-menu dropdown-menu-right">
{{foreach $editmenu.menu.entries as $e}}
- <li>
- <a href="profiles/{{$e.id}}"><img class="dropdown-menu-img-xs" src='{{$e.photo}}'>{{$e.profile_name}}<div class='clear'></div></a>
- </li>
+ <a class="dropdown-item" href="profiles/{{$e.id}}"><img class="dropdown-menu-img-xs" src='{{$e.photo}}'> {{$e.profile_name}}</a>
{{/foreach}}
- <li><a href="profile_photo" >{{$editmenu.menu.chg_photo}}</a></li>
- {{if $editmenu.menu.cr_new}}<li><a href="profiles/new" id="profile-listing-new-link">{{$editmenu.menu.cr_new}}</a></li>{{/if}}
- </ul>
+ <a class="dropdown-item" href="profile_photo" >{{$editmenu.menu.chg_photo}}</a>
+ {{if $editmenu.menu.cr_new}}
+ <a class="dropdown-item" href="profiles/new" id="profile-listing-new-link">{{$editmenu.menu.cr_new}}</a>
+ {{/if}}
+ </div>
</div>
{{elseif $editmenu}}
<div class="btn-group">
- <a class="btn btn-primary btn-xs" href="{{$editmenu.edit.0}}" ><i class="fa fa-pencil"></i>&nbsp;{{$editmenu.edit.3}}</a>
+ <a class="btn btn-primary btn-sm" href="{{$editmenu.edit.0}}" ><i class="fa fa-pencil"></i>&nbsp;{{$editmenu.edit.3}}</a>
</div>
{{/if}}
{{if $exportlink}}
<div class="btn-group">
- <a class="btn btn-default btn-xs" href="{{$exportlink}}" ><i class="fa fa-vcard"></i>&nbsp;{{$export}}</a>
+ <a class="btn btn-outline-secondary btn-sm" href="{{$exportlink}}" ><i class="fa fa-vcard"></i>&nbsp;{{$export}}</a>
</div>
{{/if}}
</div>
@@ -47,6 +47,28 @@
{{foreach $fields as $f}}
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
{{if $f == 'name'}}
<dl id="aprofile-fullname" class="aprofile">
<dt>{{$profile.fullname.0}}</dt>
@@ -297,13 +319,13 @@
<li>{{if $item.img}}<a href="{{$item.url}}" ><img src="{{$item.img}}" class="profile-thing-img" width="100" height="100" alt="{{$item.term}}" /></a>{{/if}}
<a href="{{$item.editurl}}" >{{$item.term}}</a>
{{if $profile.canlike}}<br />
- <button type="button" class="btn btn-default btn-sm" onclick="doprofilelike('thing/' + '{{$item.term_hash}}','like'); return false;" title="{{$likethis}}" >
+ <button type="button" class="btn btn-outline-secondary btn-sm" onclick="doprofilelike('thing/' + '{{$item.term_hash}}','like'); return false;" title="{{$likethis}}" >
<i class="fa fa-thumbs-o-up" title="{{$likethis}}"></i>
</button>
{{/if}}
{{if $item.like_count}}
<div class="btn-group">
- <button type="button" class="btn btn-default btn-sm dropdown-toggle" data-toggle="dropdown" id="thing-like-{{$item.term_hash}}">{{$item.like_count}} {{$item.like_label}}</button>
+ <button type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown" id="thing-like-{{$item.term_hash}}">{{$item.like_count}} {{$item.like_label}}</button>
{{if $item.likes}}
<ul class="dropdown-menu" role="menu" aria-labelledby="thing-like-{{$item.term_hash}}">{{foreach $item.likes as $liker}}<li role="presentation"><a href="{{$liker.xchan_url}}"><img class="dropdown-menu-img-xs" src="{{$liker.xchan_photo_s}}" alt="{{$liker.name}}" /> {{$liker.xchan_name}}</a></li>{{/foreach}}</ul>
{{/if}}
diff --git a/view/tpl/profile_edit.tpl b/view/tpl/profile_edit.tpl
index b0211d697..05137479f 100755
--- a/view/tpl/profile_edit.tpl
+++ b/view/tpl/profile_edit.tpl
@@ -1,53 +1,34 @@
<div class="generic-content-wrapper">
<div class="section-title-wrapper">
- <div class="dropdown pull-right" id="profile-edit-links">
- <button type="button" class="btn btn-default btn-xs dropdown-toggle" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
- <i class="fa fa-caret-down"></i>&nbsp;{{$tools_label}}
+ <div class="dropdown float-right" id="profile-edit-links">
+ <button type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
+ <i class="fa fa-cog"></i>&nbsp;{{$tools_label}}
</button>
- <ul class="dropdown-menu">
- <li class="nav-item">
- <a class="nav-link" href="profile_photo" id="profile-photo_upload-link" title="{{$profpic}}"><i class="fa fa-user"></i>&nbsp;{{$profpic}}</a>
- </li>
+ <div class="dropdown-menu">
+ <a class="dropdown-item" href="profile_photo" id="profile-photo_upload-link" title="{{$profpic}}"><i class="fa fa-fw fa-user"></i>&nbsp;{{$profpic}}</a>
{{if $is_default}}
- <li class="nav-item">
- <a href="cover_photo" id="cover-photo_upload-link" title="{{$coverpic}}"><i class="fa fa-picture-o"></i>&nbsp;{{$coverpic}}</a>
- </li>
+ <a class="dropdown-item" href="cover_photo" id="cover-photo_upload-link" title="{{$coverpic}}"><i class="fa fa-fw fa-picture-o"></i>&nbsp;{{$coverpic}}</a>
{{/if}}
{{if ! $is_default}}
- <li class="nav-item">
- <a href="profperm/{{$profile_id}}" id="profile-edit-visibility-link" title="{{$editvis}}"><i class="fa fa-pencil"></i>&nbsp;{{$editvis}}</a>
- </li>
+ <a class="dropdown-item" href="profperm/{{$profile_id}}" id="profile-edit-visibility-link" title="{{$editvis}}"><i class="fa fa-fw fa-pencil"></i>&nbsp;{{$editvis}}</a>
{{/if}}
- <li class="nav-item">
- <a href="thing" id="profile-edit-thing-link" title="{{$addthing}}"><i class="fa fa-plus-circle"></i>&nbsp;{{$addthing}}</a>
- </li>
- <li class="divider"></li>
- <li class="nav-item">
- <a href="profile/{{$profile_id}}/view" id="profile-edit-view-link" title="{{$viewprof}}">{{$viewprof}}</a>
- </li>
-
+ <a class="dropdown-item" href="thing" id="profile-edit-thing-link" title="{{$addthing}}"><i class="fa fa-fw fa-plus-circle"></i>&nbsp;{{$addthing}}</a>
+ <div class="dropdown-divider"></div>
+ <a class="dropdown-item" href="profile/{{$profile_id}}/view" id="profile-edit-view-link" title="{{$viewprof}}">{{$viewprof}}</a>
{{if $profile_clone_link}}
- <li class="divider"></li>
- <li class="nav-item">
- <a href="{{$profile_clone_link}}" id="profile-edit-clone-link" title="{{$cr_prof}}">{{$cl_prof}}</a>
- </li>
+ <div class="dropdown-divider"></div>
+ <a class="dropdown-item" href="{{$profile_clone_link}}" id="profile-edit-clone-link" title="{{$cr_prof}}">{{$cl_prof}}</a>
{{/if}}
{{if $exportable}}
- <li class="divider"></li>
- <li class="nav-item">
- <a href="profiles/export/{{$profile_id}}">{{$lbl_export}}</a>
- </li>
- <li class="nav-item">
- <a href="#" onClick="openClose('profile-upload-form'); return false;">{{$lbl_import}}</a>
- </li>
+ <div class="dropdown-divider"></div>
+ <a class="dropdown-item" href="profiles/export/{{$profile_id}}">{{$lbl_export}}</a>
+ <a class="dropdown-item" href="#" onClick="openClose('profile-upload-form'); return false;">{{$lbl_import}}</a>
{{/if}}
{{if ! $is_default}}
- <li class="divider"></li>
- <li class="nav-item">
- <a href="{{$profile_drop_link}}" id="profile-edit-drop-link" title="{{$del_prof}}" onclick="return confirmDelete();"><i class="fa fa-trash-o"></i>&nbsp;{{$del_prof}}</a>
- </li>
+ <div class="dropdown-divider"></div>
+ <a class="dropdown-item" href="{{$profile_drop_link}}" id="profile-edit-drop-link" title="{{$del_prof}}" onclick="return confirmDelete();"><i class="fa fa-trash-o"></i>&nbsp;{{$del_prof}}</a>
{{/if}}
- <ul>
+ </div>
</div>
<h2>{{$banner}}</h2>
<div class="clear"></div>
@@ -108,6 +89,128 @@
</div>
</div>
</div>
+
+ {{if $fields.comms }}
+
+ <div id="template-form-vcard-tel" class="form-group form-vcard-tel">
+ <select name="tel_type[]">
+ <option value="CELL">{{$mobile}}</option>
+ <option value="HOME">{{$home}}</option>
+ <option value="WORK">{{$work}}</option>
+ <option value="OTHER">{{$other}}</option>
+ </select>
+ <input type="text" name="tel[]" value="" placeholder="{{$tel_label}}">
+ <i data-remove="vcard-tel" data-id="" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+ </div>
+
+ <div id="template-form-vcard-email" class="form-group form-vcard-email">
+ <select name="email_type[]">
+ <option value="HOME">{{$home}}</option>
+ <option value="WORK">{{$work}}</option>
+ <option value="OTHER">{{$other}}</option>
+ </select>
+ <input type="text" name="email[]" value="" placeholder="{{$email_label}}">
+ <i data-remove="vcard-email" data-id="" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+ </div>
+
+ <div id="template-form-vcard-impp" class="form-group form-vcard-impp">
+ <select name="impp_type[]">
+ <option value="HOME">{{$home}}</option>
+ <option value="WORK">{{$work}}</option>
+ <option value="OTHER">{{$other}}</option>
+ </select>
+ <input type="text" name="impp[]" value="" placeholder="{{$impp_label}}">
+ <i data-remove="vcard-impp" data-id="" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+ </div>
+
+ <div class="section-content-wrapper-np">
+ <div id="vcard-cancel-{{$vcard.id}}" class="vcard-cancel vcard-cancel-btn" data-id="{{$vcard.id}}" data-action="cancel"><i class="fa fa-close"></i></div>
+ <div id="vcard-add-field-{{$vcard.id}}" class="dropdown pull-right vcard-add-field">
+ <button data-toggle="dropdown" type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle"><i class="fa fa-plus"></i> {{$add_field}}</button>
+ <ul class="dropdown-menu">
+ <li class="add-vcard-tel"><a href="#" data-add="vcard-tel" data-id="{{$vcard.id}}" class="add-field" onclick="return false;">{{$tel_label}}</a></li>
+ <li class="add-vcard-email"><a href="#" data-add="vcard-email" data-id="{{$vcard.id}}" class="add-field" onclick="return false;">{{$email_label}}</a></li>
+ <li class="add-vcard-impp"><a href="#" data-add="vcard-impp" data-id="{{$vcard.id}}" class="add-field" onclick="return false;">{{$impp_label}}</a></li>
+ </ul>
+ </div>
+ <div id="vcard-header-{{$vcard.id}}" class="vcard-header" data-id="{{$vcard.id}}" data-action="open">
+ <i class="vcard-fn-preview fa fa-address-card-o"></i>
+ <span id="vcard-preview-{{$vcard.id}}" class="vcard-preview">
+ {{if $vcard.fn}}<span class="vcard-fn-preview">{{$vcard.fn}}</span>{{/if}}
+ {{if $vcard.emails.0.address}}<span class="vcard-email-preview hidden-xs"><a href="mailto:{{$vcard.emails.0.address}}">{{$vcard.emails.0.address}}</a></span>{{/if}}
+ {{if $vcard.tels.0}}<span class="vcard-tel-preview hidden-xs">{{$vcard.tels.0.nr}}{{if $is_mobile}} <a class="btn btn-outline-secondary btn-sm" href="tel:{{$vcard.tels.0.nr}}"><i class="fa fa-phone connphone"></i></a>{{/if}}</span>{{/if}}
+ </span>
+ <input id="vcard-fn-{{$vcard.id}}" class="vcard-fn" type="text" name="fn" value="{{$vcard.fn}}" size="{{$vcard.fn|count_characters:true}}" placeholder="{{$name_label}}">
+ </div>
+ </div>
+ <div id="vcard-info-{{$vcard.id}}" class="vcard-info section-content-wrapper">
+
+ <div class="vcard-tel form-group">
+ <div class="form-vcard-tel-wrapper">
+ {{if $vcard.tels}}
+ {{foreach $vcard.tels as $tel}}
+ <div class="form-group form-vcard-tel">
+ <select name="tel_type[]">
+ <option value=""{{if $tel.type.0 != 'CELL' && $tel.type.0 != 'HOME' && $tel.type.0 != 'WORK' && $tel.type.0 != 'OTHER'}} selected="selected"{{/if}}>{{$tel.type.1}}</option>
+ <option value="CELL"{{if $tel.type.0 == 'CELL'}} selected="selected"{{/if}}>{{$mobile}}</option>
+ <option value="HOME"{{if $tel.type.0 == 'HOME'}} selected="selected"{{/if}}>{{$home}}</option>
+ <option value="WORK"{{if $tel.type.0 == 'WORK'}} selected="selected"{{/if}}>{{$work}}</option>
+ <option value="OTHER"{{if $tel.type.0 == 'OTHER'}} selected="selected"{{/if}}>{{$other}}</option>
+ </select>
+ <input type="text" name="tel[]" value="{{$tel.nr}}" size="{{$tel.nr|count_characters:true}}" placeholder="{{$tel_label}}">
+ <i data-remove="vcard-tel" data-id="{{$vcard.id}}" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+ </div>
+ {{/foreach}}
+ {{/if}}
+ </div>
+ </div>
+
+
+ <div class="vcard-email form-group">
+ <div class="form-vcard-email-wrapper">
+ {{if $vcard.emails}}
+ {{foreach $vcard.emails as $email}}
+ <div class="form-group form-vcard-email">
+ <select name="email_type[]">
+ <option value=""{{if $email.type.0 != 'HOME' && $email.type.0 != 'WORK' && $email.type.0 != 'OTHER'}} selected="selected"{{/if}}>{{$email.type.1}}</option>
+ <option value="HOME"{{if $email.type.0 == 'HOME'}} selected="selected"{{/if}}>{{$home}}</option>
+ <option value="WORK"{{if $email.type.0 == 'WORK'}} selected="selected"{{/if}}>{{$work}}</option>
+ <option value="OTHER"{{if $email.type.0 == 'OTHER'}} selected="selected"{{/if}}>{{$other}}</option>
+ </select>
+ <input type="text" name="email[]" value="{{$email.address}}" size="{{$email.address|count_characters:true}}" placeholder="{{$email_label}}">
+ <i data-remove="vcard-email" data-id="{{$vcard.id}}" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+ </div>
+ {{/foreach}}
+ {{/if}}
+ </div>
+ </div>
+
+ <div class="vcard-impp form-group">
+ <div class="form-vcard-impp-wrapper">
+ {{if $vcard.impps}}
+ {{foreach $vcard.impps as $impp}}
+ <div class="form-group form-vcard-impp">
+ <select name="impp_type[]">
+ <option value=""{{if $impp.type.0 != 'HOME' && $impp.type.0 != 'WORK' && $impp.type.0 != 'OTHER'}} selected="selected"{{/if}}>{{$impp.type.1}}</option>
+ <option value="HOME"{{if $impp.type.0 == 'HOME'}} selected="selected"{{/if}}>{{$home}}</option>
+ <option value="WORK"{{if $impp.type.0 == 'WORK'}} selected="selected"{{/if}}>{{$work}}</option>
+ <option value="OTHER"{{if $impp.type.0 == 'OTHER'}} selected="selected"{{/if}}>{{$other}}</option>
+ </select>
+ <input type="text" name="impp[]" value="{{$impp.address}}" size="{{$impp.address|count_characters:true}}" placeholder="{{$impp_label}}">
+ <i data-remove="vcard-impp" data-id="{{$vcard.id}}" class="fa fa-trash-o remove-field drop-icons fakelink"></i>
+ </div>
+ {{/foreach}}
+ {{/if}}
+ </div>
+ </div>
+
+ <div class="settings-submit-wrapper" >
+ <button type="submit" name="done" value="{{$submit}}" class="btn btn-primary">{{$submit}}</button>
+ </div>
+ </div>
+ {{/if}}
+
+
{{if $fields.address || $fields.locality || $fields.postal_code || $fields.region || $fields.country_name || $fields.hometown}}
<div class="panel">
<div class="section-subtitle-wrapper" role="tab" id="location">
@@ -150,7 +253,9 @@
</div>
</div>
</div>
+
{{/if}}
+
{{if $fields.marital || $fields.sexual}}
<div class="panel">
<div class="section-subtitle-wrapper" role="tab" id="relation">
@@ -270,7 +375,7 @@
{{/if}}
{{if $fields.employment}}
- {{include file="field_textarea.tpl" field=$work}}
+ {{include file="field_textarea.tpl" field=$employ}}
{{/if}}
{{if $fields.education}}
diff --git a/view/tpl/profile_listing_header.tpl b/view/tpl/profile_listing_header.tpl
index fade7be7c..42abf2735 100755
--- a/view/tpl/profile_listing_header.tpl
+++ b/view/tpl/profile_listing_header.tpl
@@ -1,6 +1,6 @@
<div class="generic-content-wrapper">
<div class="section-title-wrapper">
- <a class="btn btn-success btn-xs pull-right" href="{{$cr_new_link}}" id="profile-listing-new-link" title="{{$cr_new}}" ><i class="fa fa-plus-circle"></i>&nbsp;{{$cr_new}}</a>
+ <a class="btn btn-success btn-sm pull-right" href="{{$cr_new_link}}" id="profile-listing-new-link" title="{{$cr_new}}" ><i class="fa fa-plus-circle"></i>&nbsp;{{$cr_new}}</a>
<h2>{{$header}}</h2>
</div>
<div class="section-content-wrapper">
diff --git a/view/tpl/profile_tabs.tpl b/view/tpl/profile_tabs.tpl
new file mode 100644
index 000000000..72e98ae82
--- /dev/null
+++ b/view/tpl/profile_tabs.tpl
@@ -0,0 +1,4 @@
+<div class="dropdown-header"><img src="{{$thumb}}" class="menu-img-1">{{$name}}</div>
+{{foreach $tabs as $tab}}
+<a class="dropdown-item{{if $tab.sel}} {{$tab.sel}}{{/if}}" href="{{$tab.url}}"{{if $tab.title}} title="{{$tab.title}}"{{/if}}><i class="fa fa-fw fa-{{$tab.icon}} generic-icons-nav"></i>{{$tab.label}}</a>
+{{/foreach}}
diff --git a/view/tpl/profile_vcard.tpl b/view/tpl/profile_vcard.tpl
index 9bd534fd8..0f30e5816 100755
--- a/view/tpl/profile_vcard.tpl
+++ b/view/tpl/profile_vcard.tpl
@@ -7,17 +7,15 @@
{{/if}}
{{if ! $zcard}}
{{if $editmenu.multi}}
- <div class="dropdown">
- <a class="profile-edit-side-link dropdown-toggle" data-toggle="dropdown" href="#" ><i class="fa fa-pencil" title="{{$editmenu.edit.1}}"></i></a>
- <ul class="dropdown-menu" role="menu">
- {{foreach $editmenu.menu.entries as $e}}
- <li>
- <a href="profiles/{{$e.id}}"><img class="dropdown-menu-img-xs" src='{{$e.photo}}'>{{$e.profile_name}}</a>
- </li>
- {{/foreach}}
- <li><a href="profile_photo" >{{$editmenu.menu.chg_photo}}</a></li>
- {{if $editmenu.menu.cr_new}}<li><a href="profiles/new" id="profile-listing-new-link">{{$editmenu.menu.cr_new}}</a></li>{{/if}}
- </ul>
+ <div class="dropdown float-right">
+ <a class="dropdown-toggle" data-toggle="dropdown" href="#" ><i class="fa fa-pencil" title="{{$editmenu.edit.1}}"></i></a>
+ <div class="dropdown-menu dropdown-menu-right" role="menu">
+ {{foreach $editmenu.menu.entries as $e}}
+ <a href="profiles/{{$e.id}}" class="dropdown-item"><img class="menu-img-1" src='{{$e.photo}}'>{{$e.profile_name}}</a>
+ {{/foreach}}
+ <a href="profile_photo" class="dropdown-item">{{$editmenu.menu.chg_photo}}</a>
+ {{if $editmenu.menu.cr_new}}<a href="profiles/new" id="profile-listing-new-link" class="dropdown-item">{{$editmenu.menu.cr_new}}</a>{{/if}}
+ </div>
</div>
{{elseif $editmenu}}
<a class="profile-edit-side-link" href="{{$editmenu.edit.0}}" ><i class="fa fa-pencil" title="{{$editmenu.edit.1}}"></i></a>
@@ -43,18 +41,15 @@
</dl>
{{/if}}
- {{if $gender}}<dl class="mf"><dt class="gender-label">{{$gender}}</dt> <dd class="p-gender">{{$profile.gender}}</dd></dl>{{/if}}
+ {{if $gender}}<dl class="mf"><dt class="gender-label">{{$gender}}</dt> <dd class="p-gender">{{if $profile.gender_icon}}<i class="fa fa-{{$profile.gender_icon}}"></i>&nbsp;{{/if}}{{$profile.gender}}</dd></dl>{{/if}}
{{if $marital}}<dl class="marital"><dt class="marital-label"><span class="heart"><i class="fa fa-heart"></i>&nbsp;</span>{{$marital}}</dt><dd class="marital-text">{{$profile.marital}}</dd></dl>{{/if}}
{{if $homepage}}<dl class="homepage"><dt class="homepage-label">{{$homepage}}</dt><dd class="homepage-url u-url">{{$profile.homepage}}</dd></dl>{{/if}}
- {{if $diaspora}}
- {{include file="diaspora_vcard.tpl"}}
- {{/if}}
-
+<div class="hcard-addon"></div>
</div>
-<div id="clear"></div>
+<div class="clear"></div>
{{$rating}}
diff --git a/view/tpl/profile_vcard_short.tpl b/view/tpl/profile_vcard_short.tpl
index 0984a4e5f..5d87d52c6 100755
--- a/view/tpl/profile_vcard_short.tpl
+++ b/view/tpl/profile_vcard_short.tpl
@@ -30,10 +30,6 @@
{{if $homepage}}<dl class="homepage"><dt class="homepage-label">{{$homepage}}</dt><dd class="homepage-url">{{$profile.homepage}}</dd></dl>{{/if}}
- {{if $diaspora}}
- {{include file="diaspora_vcard.tpl"}}
- {{/if}}
-
<div id="clear"></div>
{{$chanmenu}}
diff --git a/view/tpl/prv_message.tpl b/view/tpl/prv_message.tpl
index e4e923ddb..59472f7d4 100755
--- a/view/tpl/prv_message.tpl
+++ b/view/tpl/prv_message.tpl
@@ -5,7 +5,8 @@
</div>
<div class="section-content-wrapper">
{{/if}}
- <div id="prvmail-wrapper" >
+ <div id="prvmail-wrapper">
+ <input id="invisible-wall-file-upload" type="file" name="files" style="visibility:hidden;position:absolute;top:-50;left:-50;width:0;height:0;" multiple>
<form id="prvmail-form" action="mail" method="post" >
<input type="hidden" id="inp-prvmail-expires" name="expires" value="{{$defexpire}}" />
<input type="hidden" name="media_str" id="jot-media" value="" />
@@ -28,72 +29,73 @@
{{/if}}
<div class="form-group">
<label for="prvmail-text">{{$yourmessage}}</label>
- <textarea class="form-control" id="prvmail-text" name="body">{{$text}}</textarea>
+ <textarea class="form-control" id="prvmail-text" name="body"{{if $new}} style="height: 10em;"{{/if}}>{{$text}}</textarea>
</div>
- <div id="prvmail-submit-wrapper" class="form-group">
- <div id="prvmail-submit" class="pull-right btn-group">
- <button class="btn btn-default btn-sm" id="prvmail-preview" title="{{$preview}}" onclick="preview_mail(); return false;"><i class="fa fa-eye"></i></button>
+ <div id="prvmail-submit-wrapper" class="form-group clearfix">
+ <div id="prvmail-submit" class="float-right btn-group">
+ <button class="btn btn-outline-secondary btn-sm" id="prvmail-preview" title="{{$preview}}" onclick="preview_mail(); return false;"><i class="fa fa-eye"></i></button>
<button class="btn btn-primary btn-sm" type="submit" id="prvmail-submit" name="submit" value="{{$submit}}">{{$submit}}</button>
</div>
- <div id="prvmail-tools" class="btn-toolbar pull-left">
- <div class="btn-group">
- <button id="main-editor-bold" class="btn btn-default btn-sm" title="{{$bold}}" onclick="inserteditortag('b', 'prvmail-text'); return false;">
+ <div id="prvmail-tools" class="btn-toolbar">
+ <div class="btn-group mr-2">
+ <button id="main-editor-bold" class="btn btn-outline-secondary btn-sm" title="{{$bold}}" onclick="inserteditortag('b', 'prvmail-text'); return false;">
<i class="fa fa-bold jot-icons"></i>
</button>
- <button id="main-editor-italic" class="btn btn-default btn-sm" title="{{$italic}}" onclick="inserteditortag('i', 'prvmail-text'); return false;">
+ <button id="main-editor-italic" class="btn btn-outline-secondary btn-sm" title="{{$italic}}" onclick="inserteditortag('i', 'prvmail-text'); return false;">
<i class="fa fa-italic jot-icons"></i>
</button>
- <button id="main-editor-underline" class="btn btn-default btn-sm" title="{{$underline}}" onclick="inserteditortag('u', 'prvmail-text'); return false;">
+ <button id="main-editor-underline" class="btn btn-outline-secondary btn-sm" title="{{$underline}}" onclick="inserteditortag('u', 'prvmail-text'); return false;">
<i class="fa fa-underline jot-icons"></i>
</button>
- <button id="main-editor-quote" class="btn btn-default btn-sm" title="{{$quote}}" onclick="inserteditortag('quote', 'prvmail-text'); return false;">
+ <button id="main-editor-quote" class="btn btn-outline-secondary btn-sm" title="{{$quote}}" onclick="inserteditortag('quote', 'prvmail-text'); return false;">
<i class="fa fa-quote-left jot-icons"></i>
</button>
- <button id="main-editor-code" class="btn btn-default btn-sm" title="{{$code}}" onclick="inserteditortag('code', 'prvmail-text'); return false;">
+ <button id="main-editor-code" class="btn btn-outline-secondary btn-sm" title="{{$code}}" onclick="inserteditortag('code', 'prvmail-text'); return false;">
<i class="fa fa-terminal jot-icons"></i>
</button>
</div>
- <div class="btn-group hidden-xs">
- <button id="prvmail-attach-wrapper" class="btn btn-default btn-sm" >
+ <div class="btn-group d-none d-lg-flex mr-2">
+ <button id="prvmail-attach-wrapper" class="btn btn-outline-secondary btn-sm" >
<i id="prvmail-attach" class="fa fa-paperclip jot-icons" title="{{$attach}}"></i>
</button>
- <button id="prvmail-link-wrapper" class="btn btn-default btn-sm" onclick="prvmailJotGetLink(); return false;" >
+ <button id="prvmail-link-wrapper" class="btn btn-outline-secondary btn-sm" onclick="prvmailJotGetLink(); return false;" >
<i id="prvmail-link" class="fa fa-link jot-icons" title="{{$insert}}" ></i>
</button>
</div>
{{if $feature_expire || $feature_encrypt}}
- <div class="btn-group hidden-sm hidden-xs">
+ <div class="btn-group d-none d-lg-flex">
{{if $feature_expire}}
- <button id="prvmail-expire-wrapper" class="btn btn-default btn-sm" onclick="prvmailGetExpiry();return false;" >
+ <button id="prvmail-expire-wrapper" class="btn btn-outline-secondary btn-sm" onclick="prvmailGetExpiry();return false;" >
<i id="prvmail-expires" class="fa fa-eraser jot-icons" title="{{$expires}}" ></i>
</button>
{{/if}}
{{if $feature_encrypt}}
- <button id="prvmail-encrypt-wrapper" class="btn btn-default btn-sm" onclick="red_encrypt('{{$cipher}}','#prvmail-text',$('#prvmail-text').val());return false;">
+ <button id="prvmail-encrypt-wrapper" class="btn btn-outline-secondary btn-sm" onclick="red_encrypt('{{$cipher}}','#prvmail-text',$('#prvmail-text').val());return false;">
<i id="prvmail-encrypt" class="fa fa-key jot-icons" title="{{$encrypt}}" ></i>
</button>
{{/if}}
</div>
{{/if}}
- <div class="btn-group visible-xs visible-sm">
- <button type="button" id="more-tools" class="btn btn-default btn-sm dropdown-toggle" data-toggle="dropdown" aria-expanded="false">
- <i id="more-tools-icon" class="fa fa-caret-down jot-icons"></i>
+ <div class="btn-group d-lg-none">
+ <button type="button" id="more-tools" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown" aria-expanded="false">
+ <i id="more-tools-icon" class="fa fa-cog jot-icons"></i>
</button>
- <ul class="dropdown-menu dropdown-menu-right" role="menu">
- <li class="visible-xs"><a href="#" id="prvmail-attach-sub"><i class="fa fa-paperclip"></i>&nbsp;{{$attach}}</a></li>
- <li class="visible-xs"><a href="#" onclick="prvmailJotGetLink(); return false;" ><i class="fa fa-link"></i>&nbsp;{{$insert}}</a></li>
+ <div class="dropdown-menu dropdown-menu-right" role="menu">
+ <a class="dropdown-item" href="#" id="prvmail-attach-sub"><i class="fa fa-paperclip"></i>&nbsp;{{$attach}}</a>
+ <a class="dropdown-item" href="#" onclick="prvmailJotGetLink(); return false;" ><i class="fa fa-link"></i>&nbsp;{{$insert}}</a>
{{if $feature_expire || $feature_encrypt}}
- <li class="divider visible-xs"></li>
- <li class="visible-sm visible-xs"><a href="#" onclick="prvmailGetExpiry(); return false;"><i id="prvmail-expires" class="fa fa-eraser"></i>&nbsp;{{$expires}}</a></li>
- <li class="visible-sm visible-xs"><a href="#" onclick="red_encrypt('{{$cipher}}','#prvmail-text',$('#prvmail-text').val()); return false;"><i class="fa fa-key"></i>&nbsp;{{$encrypt}}</a></li>
+ <div class="dropdown-divider"></div>
+ <a class="dropdown-item" href="#" onclick="prvmailGetExpiry(); return false;"><i id="prvmail-expires" class="fa fa-eraser"></i>&nbsp;{{$expires}}</a>
+ <a class="dropdown-item" href="#" onclick="red_encrypt('{{$cipher}}','#prvmail-text',$('#prvmail-text').val()); return false;"><i class="fa fa-key"></i>&nbsp;{{$encrypt}}</a>
{{/if}}
- </ul>
+ </div>
+ </div>
+ <div class="btn-group">
+ <div id="prvmail-rotator" class="m-2 spinner-wrapper">
+ <div class="spinner s"></div>
+ </div>
</div>
</div>
- <div id="prvmail-rotator-wrapper" class="pull-left">
- <div id="prvmail-rotator"></div>
- </div>
- <div class="clear"></div>
</div>
<div id="mail-preview-content" style="display: none;"></div>
</form>
diff --git a/view/tpl/register.tpl b/view/tpl/register.tpl
index c84934626..493dba4c8 100755
--- a/view/tpl/register.tpl
+++ b/view/tpl/register.tpl
@@ -39,10 +39,10 @@
{{/if}}
{{include file="field_input.tpl" field=$name}}
- <div id="name-spinner"></div>
+ <div id="name-spinner" class="spinner-wrapper"><div class="spinner m"></div></div>
{{include file="field_input.tpl" field=$nickname}}
- <div id="nick-spinner"></div>
+ <div id="nick-spinner" class="spinner-wrapper"><div class="spinner m"></div></div>
{{/if}}
{{if $enable_tos}}
diff --git a/view/tpl/remote_friends_common.tpl b/view/tpl/remote_friends_common.tpl
index d6d2fd211..9e149b574 100755
--- a/view/tpl/remote_friends_common.tpl
+++ b/view/tpl/remote_friends_common.tpl
@@ -1,21 +1,16 @@
-<div id="remote-friends-in-common" class="bigwidget">
- <div id="rfic-desc">{{$desc}} &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;{{if $linkmore}}<a href="{{$base}}/common/{{$uid}}">{{$more}}</a>{{/if}}</div>
+<div class="widget">
+ <h3>{{$desc}}</h3>
+ {{if $linkmore}}
+ <a class="allcontact-link" href="{{$base}}/common/{{$uid}}">{{$more}}</a>
+ {{/if}}
{{if $items}}
- {{foreach $items as $item}}
- <div class="profile-match-wrapper">
- <div class="profile-match-photo">
- <a href="{{$base}}/chanview?f=&url={{$item.xchan_url}}">
- <img src="{{$item.xchan_photo_m}}" width="80" height="80" alt="{{$item.xchan_name}}" title="{{$item.xchan_name}}" />
- </a>
- </div>
- <div class="profile-match-break"></div>
- <div class="profile-match-name">
- <a href="{{$base}}/chanview?f=&url={{$item.xchan_url}}" title="{{$item.xchan_name}}">{{$item.xchan_name}}</a>
+ <div class="contact-block-content">
+ {{foreach $items as $item}}
+ <div class="contact-block-div">
+ <a class="contact-block-link mpfriend" href="{{$base}}/chanview?f=&url={{$item.xchan_url}}"><img class="contact-block-img mpfriend" src="{{$item.xchan_photo_s}}"alt="{{$item.xchan_name}}" title="{{$item.xchan_name}} [{{$item.xchan_addr}}]" /></a>
</div>
- <div class="profile-match-end"></div>
+ {{/foreach}}
</div>
- {{/foreach}}
{{/if}}
- <div id="rfic-end" class="clear"></div>
-</div>
+<div>
diff --git a/view/tpl/saved_searches.tpl b/view/tpl/saved_searches.tpl
index 2065cd714..ff2d044ef 100644
--- a/view/tpl/saved_searches.tpl
+++ b/view/tpl/saved_searches.tpl
@@ -1,14 +1,12 @@
-<div class="widget saved-search-widget">
+<div class="widget saved-search-widget clearfix">
<h3 id="search">{{$title}}</h3>
{{$searchbox}}
-
- <ul id="saved-search-list" class="nav nav-pills nav-stacked">
+ <ul id="saved-search-list" class="nav nav-pills flex-column">
{{foreach $saved as $search}}
- <li id="search-term-{{$search.id}}">
- <a class="pull-right group-edit-tool" title="{{$search.delete}}" onclick="return confirmDelete();" id="drop-saved-search-term-{{$search.id}}" href="{{$search.dellink}}"><i id="dropfa-floppy-od-search-term-{{$search.id}}" class="group-edit-icon fa fa-trash-o" ></i></a>
- <a id="saved-search-term-{{$search.id}}"{{if $search.selected}} class="search-selected"{{/if}} href="{{$search.srchlink}}">{{$search.displayterm}}</a>
+ <li class="nav-item nav-item-hack" id="search-term-{{$search.id}}">
+ <a class="nav-link widget-nav-pills-icons" title="{{$search.delete}}" onclick="return confirmDelete();" id="drop-saved-search-term-{{$search.id}}" href="{{$search.dellink}}"><i id="dropfa-floppy-od-search-term-{{$search.id}}" class="fa fa-trash-o drop-icons" ></i></a>
+ <a id="saved-search-term-{{$search.id}}" class="nav-link{{if $search.selected}} active{{/if}}" href="{{$search.srchlink}}">{{$search.displayterm}}</a>
</li>
{{/foreach}}
</ul>
- <div class="clear"></div>
</div>
diff --git a/view/tpl/search_item.tpl b/view/tpl/search_item.tpl
index a490cb473..0a8f12d4f 100755
--- a/view/tpl/search_item.tpl
+++ b/view/tpl/search_item.tpl
@@ -1,7 +1,7 @@
-<div id="thread-wrapper-{{$item.id}}" class="thread-wrapper{{if $item.toplevel}} {{$item.toplevel}} generic-content-wrapper{{/if}}">
+<div id="thread-wrapper-{{$item.id}}" class="thread-wrapper{{if $item.toplevel}} {{$item.toplevel}} clearfix generic-content-wrapper{{/if}}">
<a name="{{$item.id}}" ></a>
- <div class="wall-item-outside-wrapper {{$item.indent}}{{$item.previewing}}{{if $item.owner_url}} wallwall{{/if}}" id="wall-item-outside-wrapper-{{$item.id}}" >
- <div class="wall-item-content-wrapper {{$item.indent}}" id="wall-item-content-wrapper-{{$item.id}}" style="clear:both;">
+ <div class="clearfix wall-item-outside-wrapper {{$item.indent}}{{$item.previewing}}{{if $item.owner_url}} wallwall{{/if}}" id="wall-item-outside-wrapper-{{$item.id}}" >
+ <div class="wall-item-content-wrapper {{$item.indent}}" id="wall-item-content-wrapper-{{$item.id}}">
{{if $item.photo}}
<div class="wall-photo-item" id="wall-photo-item-{{$item.id}}">
{{$item.photo}}
@@ -12,39 +12,46 @@
{{$item.event}}
</div>
{{/if}}
- <div class="wall-item-head">
+ {{if $item.title && !$item.event}}
+ <div class="p-2{{if $item.is_new}} bg-primary text-white{{/if}} wall-item-title h3{{if !$item.photo}} rounded-top{{/if}}" id="wall-item-title-{{$item.id}}">
+ {{if $item.title_tosource}}{{if $item.plink}}<a href="{{$item.plink.href}}" title="{{$item.title}} ({{$item.plink.title}})">{{/if}}{{/if}}{{$item.title}}{{if $item.title_tosource}}{{if $item.plink}}</a>{{/if}}{{/if}}
+ </div>
+ {{if ! $item.is_new}}
+ <hr class="m-0">
+ {{/if}}
+ {{/if}}
+ <div class="p-2 clearfix wall-item-head{{if $item.is_new && !$item.title && !$item.event && !$item.is_comment}} wall-item-head-new rounded-top{{/if}}">
<div class="wall-item-info" id="wall-item-info-{{$item.id}}" >
<div class="wall-item-photo-wrapper{{if $item.owner_url}} wwfrom{{/if}}" id="wall-item-photo-wrapper-{{$item.id}}">
<a href="{{$item.profile_url}}" title="{{$item.linktitle}}" class="wall-item-photo-link" id="wall-item-photo-link-{{$item.id}}"><img src="{{$item.thumb}}" class="wall-item-photo{{$item.sparkle}}" id="wall-item-photo-{{$item.id}}" alt="{{$item.name}}" /></a>
</div>
- <div class="wall-item-photo-end" style="clear:both"></div>
- </div>
- {{if $item.title}}
- <div class="wall-item-title" id="wall-item-title-{{$item.id}}" title="{{$item.title}}">
- <h3>{{if $item.title_tosource}}{{if $item.plink}}<a href="{{$item.plink.href}}" title="{{$item.title}} ({{$item.plink.title}})">{{/if}}{{/if}}{{$item.title}}{{if $item.title_tosource}}{{if $item.plink}}</a>{{/if}}{{/if}}</h3>
</div>
- {{/if}}
{{if $item.lock}}
<div class="wall-item-lock dropdown">
- <i class="fa fa-lock lockview dropdown-toggle" data-toggle="dropdown" title="{{$item.lock}}" onclick="lockview('item',{{$item.id}});" ></i><ul id="panel-{{$item.id}}" class="lockview-panel dropdown-menu"></ul>&nbsp;
+ <i class="fa fa-lock lockview" data-toggle="dropdown" title="{{$item.lock}}" onclick="lockview('item',{{$item.id}});" ></i><ul id="panel-{{$item.id}}" class="lockview-panel dropdown-menu"></ul>&nbsp;
</div>
{{/if}}
<div class="wall-item-author">
+ {{if $item.previewing}}<span class="preview-indicator"><i class="fa fa-eye" title="{{$item.preview_lbl}}"></i></span>&nbsp;{{/if}}
<a href="{{$item.profile_url}}" title="{{$item.linktitle}}" class="wall-item-name-link"><span class="wall-item-name{{$item.sparkle}}" id="wall-item-name-{{$item.id}}" >{{$item.name}}</span></a>{{if $item.owner_url}}&nbsp;{{$item.via}}&nbsp;<a href="{{$item.owner_url}}" title="{{$item.olinktitle}}" class="wall-item-name-link"><span class="wall-item-name{{$item.osparkle}}" id="wall-item-ownername-{{$item.id}}">{{$item.owner_name}}</span></a>{{/if}}
</div>
<div class="wall-item-ago" id="wall-item-ago-{{$item.id}}">
{{if $item.verified}}<i class="fa fa-check item-verified" title="{{$item.verified}}"></i>&nbsp;{{elseif $item.forged}}<i class="fa fa-exclamation item-forged" title="{{$item.forged}}"></i>&nbsp;{{/if}}{{if $item.location}}<span class="wall-item-location" id="wall-item-location-{{$item.id}}">{{$item.location}},&nbsp;</span>{{/if}}<span class="autotime" title="{{$item.isotime}}">{{$item.localtime}}{{if $item.editedtime}}&nbsp;{{$item.editedtime}}{{/if}}{{if $item.expiretime}}&nbsp;{{$item.expiretime}}{{/if}}</span>{{if $item.editedtime}}&nbsp;<i class="fa fa-pencil"></i>{{/if}}&nbsp;{{if $item.app}}<span class="item.app">{{$item.str_app}}</span>{{/if}}
</div>
- <div class="clear"></div>
</div>
- <div class="{{if $item.is_photo}}wall-photo-item{{else}}wall-item-content{{/if}}" id="wall-item-content-{{$item.id}}">
+ {{if $item.body}}
+ <div class="p-2 clrearfix {{if $item.is_photo}} wall-photo-item{{else}} wall-item-content{{/if}}" id="wall-item-content-{{$item.id}}">
<div class="wall-item-body" id="wall-item-body-{{$item.id}}" >
{{$item.body}}
</div>
- <div class="clear"></div>
</div>
+ {{/if}}
{{if $item.has_tags}}
- <div class="wall-item-tools">
+ <div class="p-2 wall-item-tools clearfix">
+ <div class="body-tags">
+ <span class="tag">{{$item.mentions}} {{$item.tags}} {{$item.categories}} {{$item.folders}}</span>
+ </div>
+ {{**
{{if $item.mentions}}
<div class="body-tags" id="item-mentions">
<span class="tag">{{$item.mentions}}</span>
@@ -65,48 +72,55 @@
<span class="tag">{{$item.folders}}</span>
</div>
{{/if}}
- <div class="clear"></div>
+ **}}
</div>
{{/if}}
- <div class="wall-item-tools">
+ <div class="p-2 clearfix wall-item-tools">
<div class="wall-item-tools-right btn-group pull-right">
- <button type="button" class="btn btn-default btn-sm dropdown-toggle" data-toggle="dropdown">
- <i class="fa fa-caret-down"></i>
+ <button type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown">
+ <i class="fa fa-cog"></i>
</button>
- <ul class="dropdown-menu">
+ <div class="dropdown-menu dropdown-menu-right">
{{if $item.thread_action_menu}}
{{foreach $item.thread_action_menu as $mitem}}
- <li role="presentation"><a role="menuitem" {{if $mitem.href}}href="{{$mitem.href}}"{{/if}} {{if $mitem.action}}onclick="{{$mitem.action}}"{{/if}} {{if $mitem.title}}title="{{$mitem.title}}"{{/if}} ><i class="fa fa-{{$mitem.icon}}"></i> {{$mitem.title}}</a></li>
+ <a class="dropdown-item" {{if $mitem.href}}href="{{$mitem.href}}"{{/if}} {{if $mitem.action}}onclick="{{$mitem.action}}"{{/if}} {{if $mitem.title}}title="{{$mitem.title}}"{{/if}} ><i class="fa fa-{{$mitem.icon}}"></i> {{$mitem.title}}</a></li>
{{/foreach}}
{{/if}}
{{if $item.drop.dropping}}
- <li><a href="item/drop/{{$item.id}}" onclick="return confirmDelete();" title="{{$item.drop.delete}}" ><i class="fa fa-trash-o"></i> {{$item.drop.delete}}</a></li>
+ <a class="dropdown-item" href="item/drop/{{$item.id}}" onclick="return confirmDelete();" title="{{$item.drop.delete}}" ><i class="fa fa-trash-o"></i> {{$item.drop.delete}}</a></li>
{{/if}}
{{if $item.thread_author_menu}}
- <li role="presentation" class="divider"></li>
+ <div class="dropdown-divider"></div>
{{foreach $item.thread_author_menu as $mitem}}
- <li role="presentation"><a role="menuitem" {{if $mitem.href}}href="{{$mitem.href}}"{{/if}} {{if $mitem.action}}onclick="{{$mitem.action}}"{{/if}} {{if $mitem.title}}title="{{$mitem.title}}"{{/if}} >{{$mitem.title}}</a></li>
+ <a class="dropdown-item" {{if $mitem.href}}href="{{$mitem.href}}"{{/if}} {{if $mitem.action}}onclick="{{$mitem.action}}"{{/if}} {{if $mitem.title}}title="{{$mitem.title}}"{{/if}} >{{$mitem.title}}</a></li>
{{/foreach}}
{{/if}}
- </ul>
+ </div>
</div>
{{if $item.attachments}}
<div class="wall-item-tools-left btn-group">
- <button type="button" class="btn btn-default btn-sm wall-item-like dropdown-toggle" data-toggle="dropdown" id="attachment-menu-{{$item.id}}"><i class="fa fa-paperclip"></i></button>
- <ul class="dropdown-menu" role="menu" aria-labelledby="attachment-menu-{{$item.id}}">{{$item.attachments}}</ul>
+ <button type="button" class="btn btn-outline-secondary btn-sm wall-item-like dropdown-toggle" data-toggle="dropdown" id="attachment-menu-{{$item.id}}"><i class="fa fa-paperclip"></i></button>
+ <div class="dropdown-menu">{{$item.attachments}}</div>
</div>
{{/if}}
- <div class="clear"></div>
+ {{if $item.mode === 'moderate'}}
+
+ <div class="wall-item-tools-left btn-group">
+ <a href="moderate/{{$item.id}}/approve" class="btn btn-success btn-sm">{{$item.approve}}</a>
+ <a href="moderate/{{$item.id}}/drop" class="btn btn-danger btn-sm">{{$item.delete}}</a>
+
+ </div>
+
+
+
+ {{/if}}
</div>
- <div class="clear"></div>
</div>
- <div class="wall-item-wrapper-end"></div>
{{if $item.conv}}
- <div class="wall-item-conv" id="wall-item-conv-{{$item.id}}" >
+ <div class="p-2 wall-item-conv" id="wall-item-conv-{{$item.id}}" >
<a href='{{$item.conv.href}}' id='context-{{$item.id}}' title='{{$item.conv.title}}'>{{$item.conv.title}}</a>
</div>
{{/if}}
- <div class="clear{{if $indent}} {{$indent}}{{/if}}"></div>
</div>
</div>
diff --git a/view/tpl/searchbox.tpl b/view/tpl/searchbox.tpl
index 8eb169b4a..8f7ac5162 100644
--- a/view/tpl/searchbox.tpl
+++ b/view/tpl/searchbox.tpl
@@ -1,11 +1,11 @@
<form action="{{$action_url}}" method="get" >
<input type="hidden" name="f" value="" />
<div id="{{$id}}" class="input-group">
- <input class="widget-input" type="text" name="search" id="search-text" value="{{$s}}" onclick="this.submit();" />
+ <input class="form-control form-control-sm" type="text" name="search" id="search-text" value="{{$s}}" onclick="this.submit();" />
<div class="input-group-btn">
- <button type="submit" name="submit" class="btn btn-default btn-sm" id="search-submit" value="{{$search_label}}"><i class="fa fa-search"></i></button>
+ <button type="submit" name="submit" class="btn btn-outline-secondary" id="search-submit" value="{{$search_label}}"><i class="fa fa-search"></i></button>
{{if $savedsearch}}
- <button type="submit" name="searchsave" class="btn btn-default btn-sm" id="search-save" value="{{$save_label}}"><i class="fa fa-floppy-o"></i></button>
+ <button type="submit" name="searchsave" class="btn btn-outline-secondary" id="search-save" value="{{$save_label}}"><i class="fa fa-floppy-o"></i></button>
{{/if}}
</div>
</div>
diff --git a/view/tpl/settings.tpl b/view/tpl/settings.tpl
index 19c2b42d5..704d89bdd 100755
--- a/view/tpl/settings.tpl
+++ b/view/tpl/settings.tpl
@@ -1,6 +1,6 @@
<div class="generic-content-wrapper">
<div class="section-title-wrapper">
- {{if $server_role != 'basic'}}<a title="{{$removechannel}}" class="btn btn-danger btn-xs pull-right" href="removeme"><i class="fa fa-trash-o"></i>&nbsp;{{$removeme}}</a>{{/if}}
+ <a title="{{$removechannel}}" class="btn btn-danger btn-sm pull-right" href="removeme"><i class="fa fa-trash-o"></i>&nbsp;{{$removeme}}</a>
<h2>{{$ptitle}}</h2>
<div class="clear"></div>
</div>
@@ -11,12 +11,12 @@
<div class="panel">
<div class="section-subtitle-wrapper" role="tab" id="basic-settings">
<h3>
- <a data-toggle="collapse" data-parent="#settings" href="#basic-settings-collapse" aria-expanded="true" aria-controls="basic-settings-collapse">
+ <a data-toggle="collapse" data-parent="#settings" href="#basic-settings-collapse">
{{$h_basic}}
</a>
</h3>
</div>
- <div id="basic-settings-collapse" class="panel-collapse collapse in" role="tabpanel" aria-labelledby="basic-settings">
+ <div id="basic-settings-collapse" class="collapse show" role="tabpanel" aria-labelledby="basic-settings">
<div class="section-content-tools-wrapper">
{{include file="field_input.tpl" field=$username}}
{{include file="field_select_grouped.tpl" field=$timezone}}
@@ -37,28 +37,24 @@
<div class="panel">
<div class="section-subtitle-wrapper" role="tab" id="privacy-settings">
<h3>
- <a data-toggle="collapse" data-parent="#settings" href="#privacy-settings-collapse" aria-expanded="true" aria-controls="privacy-settings-collapse">
+ <a data-toggle="collapse" data-parent="#settings" href="#privacy-settings-collapse">
{{$h_prv}}
</a>
</h3>
</div>
- <div id="privacy-settings-collapse" class="panel-collapse collapse" role="tabpanel" aria-labelledby="privacy-settings">
+ <div id="privacy-settings-collapse" class="collapse" role="tabpanel" aria-labelledby="privacy-settings">
<div class="section-content-tools-wrapper">
- {{if $server_role != 'basic'}}
{{include file="field_select_grouped.tpl" field=$role}}
- {{/if}}
- <div id="advanced-perm" style="display:{{if $permissions_set && $server_role != 'basic' }}none{{else}}block{{/if}};">
-
- {{if $server_role != 'basic'}}
+ <div id="advanced-perm" style="display:{{if $permissions_set}}none{{else}}block{{/if}};">
<div class="form-group">
- <button type="button" class="btn btn-default" data-toggle="modal" data-target="#apsModal">{{$lbl_p2macro}}</button>
+ <button type="button" class="btn btn-outline-secondary" data-toggle="modal" data-target="#apsModal">{{$lbl_p2macro}}</button>
</div>
<div class="modal" id="apsModal">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
- <button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title">{{$lbl_p2macro}}</h4>
+ <button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">&times;</span></button>
</div>
<div class="modal-body">
{{foreach $permiss_arr as $permit}}
@@ -66,14 +62,14 @@
{{/foreach}}
</div>
<div class="modal-footer">
- <button type="button" class="btn btn-default" data-dismiss="modal">Close</button>
+ <button type="button" class="btn btn-outline-secondary" data-dismiss="modal">Close</button>
</div>
</div><!-- /.modal-content -->
</div><!-- /.modal-dialog -->
</div><!-- /.modal -->
- {{/if}}
+
<div id="settings-default-perms" class="form-group" >
- <button type="button" class="btn btn-default" data-toggle="modal" data-target="#aclModal"><i id="jot-perms-icon" class="fa"></i>&nbsp;{{$permissions}}</button>
+ <button type="button" class="btn btn-outline-secondary" data-toggle="modal" data-target="#aclModal"><i id="jot-perms-icon" class="fa"></i>&nbsp;{{$permissions}}</button>
</div>
{{$group_select}}
{{include file="field_checkbox.tpl" field=$hide_presence}}
@@ -100,12 +96,12 @@
<div class="panel">
<div class="section-subtitle-wrapper" role="tab" id="notification-settings">
<h3>
- <a data-toggle="collapse" data-parent="#settings" href="#notification-settings-collapse" aria-expanded="true" aria-controls="notification-settings-collapse">
+ <a data-toggle="collapse" data-parent="#settings" href="#notification-settings-collapse">
{{$h_not}}
</a>
</h3>
</div>
- <div id="notification-settings-collapse" class="panel-collapse collapse" role="tabpanel" aria-labelledby="notification-settings">
+ <div id="notification-settings-collapse" class="collapse" role="tabpanel" aria-labelledby="notification-settings">
<div class="section-content-tools-wrapper">
<div id="settings-notifications">
<h3>{{$activity_options}}</h3>
@@ -140,6 +136,10 @@
{{include file="field_intcheckbox.tpl" field=$vnotify8}}
{{include file="field_intcheckbox.tpl" field=$vnotify9}}
{{include file="field_intcheckbox.tpl" field=$vnotify11}}
+ {{include file="field_intcheckbox.tpl" field=$vnotify12}}
+ {{if $vnotify13}}
+ {{include file="field_intcheckbox.tpl" field=$vnotify13}}
+ {{/if}}
{{include file="field_intcheckbox.tpl" field=$always_show_in_notices}}
{{include file="field_input.tpl" field=$evdays}}
</div>
@@ -162,7 +162,7 @@
</a>
</h3>
</div>
- <div id="miscellaneous-settings-collapse" class="panel-collapse collapse" role="tabpanel" aria-labelledby="miscellaneous-settings">
+ <div id="miscellaneous-settings-collapse" class="collapse" role="tabpanel" aria-labelledby="miscellaneous-settings">
<div class="section-content-tools-wrapper">
{{if $menus}}
<div class="form-group channel-menu">
diff --git a/view/tpl/settings_account.tpl b/view/tpl/settings_account.tpl
index 8ff846518..dd1d0d0c9 100755
--- a/view/tpl/settings_account.tpl
+++ b/view/tpl/settings_account.tpl
@@ -1,6 +1,6 @@
<div class="generic-content-wrapper">
<div class="section-title-wrapper">
- <a title="{{$removeaccount}}" class="btn btn-danger btn-xs pull-right" href="removeaccount"><i class="fa fa-trash-o"></i>&nbsp;{{$removeme}}</a>
+ <a title="{{$removeaccount}}" class="btn btn-danger btn-sm pull-right" href="removeaccount"><i class="fa fa-trash-o"></i>&nbsp;{{$removeme}}</a>
<h2>{{$title}}</h2>
<div class="clear"></div>
</div>
@@ -12,7 +12,7 @@
{{include file="field_password.tpl" field=$password1}}
{{include file="field_password.tpl" field=$password2}}
- {{if $z_server_role == 'pro' && ! $techlock}}
+ {{if ! $techlock}}
{{include file="field_select.tpl" field=$techlevel}}
{{else}}
<input type="hidden" name="techlevel" value="{{$techlevel.2}}" />
diff --git a/view/tpl/settings_display.tpl b/view/tpl/settings_display.tpl
index a85a067be..d8c1ac7aa 100755
--- a/view/tpl/settings_display.tpl
+++ b/view/tpl/settings_display.tpl
@@ -15,7 +15,7 @@
</a>
</h3>
</div>
- <div id="theme-settings-content" class="panel-collapse collapse in" role="tabpanel" aria-labelledby="theme-settings">
+ <div id="theme-settings-content" class="collapse show" role="tabpanel" aria-labelledby="theme-settings">
<div class="section-content-tools-wrapper">
{{if $theme}}
{{include file="field_themeselect.tpl" field=$theme}}
@@ -41,7 +41,7 @@
</a>
</h3>
</div>
- <div id="custom-settings-content" class="panel-collapse collapse{{if !$theme && !$mobile_theme}} in{{/if}}" role="tabpanel" aria-labelledby="custom-settings">
+ <div id="custom-settings-content" class="collapse{{if !$theme && !$mobile_theme}} in{{/if}}" role="tabpanel" aria-labelledby="custom-settings">
<div class="section-content-tools-wrapper">
{{if $theme_config}}
{{$theme_config}}
@@ -57,7 +57,7 @@
</a>
</h3>
</div>
- <div id="content-settings-content" class="panel-collapse collapse{{if !$theme && !$mobile_theme && !$theme_config}} in{{/if}}" role="tabpanel" aria-labelledby="content-settings">
+ <div id="content-settings-content" class="collapse{{if !$theme && !$mobile_theme && !$theme_config}} in{{/if}}" role="tabpanel" aria-labelledby="content-settings">
<div class="section-content-wrapper">
{{include file="field_input.tpl" field=$ajaxint}}
{{include file="field_input.tpl" field=$itemspage}}
@@ -72,7 +72,7 @@
{{include file="field_checkbox.tpl" field=$manual_update}}
{{if $expert}}
<div class="form-group">
- <a class="btn btn-default "href="pdledit">{{$layout_editor}}</a>
+ <a class="btn btn-outline-secondary "href="pdledit">{{$layout_editor}}</a>
</div>
{{/if}}
<div class="settings-submit-wrapper" >
diff --git a/view/tpl/settings_features.tpl b/view/tpl/settings_features.tpl
index 75eb34fb9..dfe049a7a 100755
--- a/view/tpl/settings_features.tpl
+++ b/view/tpl/settings_features.tpl
@@ -14,7 +14,7 @@
</a>
</h3>
</div>
- <div id="{{$g}}-settings-content" class="panel-collapse collapse{{if $g == 'general'}} in{{/if}}" role="tabpanel" aria-labelledby="{{$g}}-settings-title">
+ <div id="{{$g}}-settings-content" class="collapse{{if $g == 'general'}} show{{/if}}" role="tabpanel" aria-labelledby="{{$g}}-settings-title">
<div class="section-content-tools-wrapper">
{{foreach $f.1 as $fcat}}
{{include file="field_checkbox.tpl" field=$fcat}}
diff --git a/view/tpl/settings_oauth.tpl b/view/tpl/settings_oauth.tpl
index 9582ef52d..811cfcec5 100755
--- a/view/tpl/settings_oauth.tpl
+++ b/view/tpl/settings_oauth.tpl
@@ -25,8 +25,8 @@
{{/if}}
{{/if}}
{{if $app.my}}
- <a href="{{$baseurl}}/settings/oauth/edit/{{$app.client_id}}" title="{{$edit}}"><i class="fa fa-pencil btn btn-default"></i></a>
- <a href="{{$baseurl}}/settings/oauth/delete/{{$app.client_id}}?t={{$form_security_token}}" title="{{$delete}}"><i class="fa fa-trash-o btn btn-default"></i></a>
+ <a href="{{$baseurl}}/settings/oauth/edit/{{$app.client_id}}" title="{{$edit}}"><i class="fa fa-pencil btn btn-outline-secondary"></i></a>
+ <a href="{{$baseurl}}/settings/oauth/delete/{{$app.client_id}}?t={{$form_security_token}}" title="{{$delete}}"><i class="fa fa-trash-o btn btn-outline-secondary"></i></a>
{{/if}}
</div>
{{/foreach}}
diff --git a/view/tpl/sharedwithme.tpl b/view/tpl/sharedwithme.tpl
index c764dc4f0..8474ccd52 100644
--- a/view/tpl/sharedwithme.tpl
+++ b/view/tpl/sharedwithme.tpl
@@ -1,6 +1,6 @@
<div class="generic-content-wrapper">
<div class="section-title-wrapper">
- <a href="/sharedwithme/dropall" onclick="return confirmDelete();" class="btn btn-xs btn-default pull-right"><i class="fa fa-trash-o"></i>&nbsp;{{$dropall}}</a>
+ <a href="/sharedwithme/dropall" onclick="return confirmDelete();" class="btn btn-sm btn-outline-secondary pull-right"><i class="fa fa-trash-o"></i>&nbsp;{{$dropall}}</a>
<h2>{{$header}}</h2>
</div>
<div class="section-content-wrapper-np">
@@ -9,16 +9,16 @@
<th width="1%"></th>
<th width="92%">{{$name}}</th>
<th width="1%"></th>
- <th width="1%" class="hidden-xs">{{$size}}</th>
- <th width="1%" class="hidden-xs">{{$lastmod}}</th>
+ <th width="1%" class="d-none d-md-table-cell">{{$size}}</th>
+ <th width="1%" class="d-none d-md-table-cell">{{$lastmod}}</th>
</tr>
{{foreach $items as $item}}
<tr id="cloud-index-{{$item.id}}">
<td><i class="fa {{$item.objfiletypeclass}}" title="{{$item.objfiletype}}"></i></td>
- <td><a href="{{$item.objurl}}">{{$item.objfilename}}</a>{{if $item.unseen}}&nbsp;<span class="label label-success">{{$label_new}}</span>{{/if}}</td>
+ <td><a href="{{$item.objurl}}">{{$item.objfilename}}</a>{{if $item.unseen}}&nbsp;<span class="badge badge-pill badge-success">{{$label_new}}</span>{{/if}}</td>
<td class="cloud-index-tool"><a href="#" title="{{$drop}}" onclick="dropItem('/sharedwithme/{{$item.id}}/drop', '#cloud-index-{{$item.id}}'); return false;"><i class="fa fa-trash-o drop-icons"></i></a></td>
- <td class="hidden-xs">{{$item.objfilesize}}</td>
- <td class="hidden-xs">{{$item.objedited}}</td>
+ <td class="d-none d-md-table-cell">{{$item.objfilesize}}</td>
+ <td class="d-none d-md-table-cell">{{$item.objedited}}</td>
</tr>
{{/foreach}}
</table>
diff --git a/view/tpl/show_thing.tpl b/view/tpl/show_thing.tpl
index 85d7934b5..d738c9fc9 100644
--- a/view/tpl/show_thing.tpl
+++ b/view/tpl/show_thing.tpl
@@ -6,8 +6,8 @@
</div>
{{if $canedit}}
<div class="thing-edit-links">
-<a href="thing/edit/{{$thing.obj_obj}}" title="{{$edit}}" class="btn btn-default" ><i class="fa fa-pencil thing-edit-icon"></i></a>
-<a href="thing/drop/{{$thing.obj_obj}}" onclick="return confirmDelete();" title="{{$delete}}" class="btn btn-default" ><i class="fa fa-trash-o drop-icons"></i></a>
+<a href="thing/edit/{{$thing.obj_obj}}" title="{{$edit}}" class="btn btn-outline-secondary" ><i class="fa fa-pencil thing-edit-icon"></i></a>
+<a href="thing/drop/{{$thing.obj_obj}}" onclick="return confirmDelete();" title="{{$delete}}" class="btn btn-outline-secondary" ><i class="fa fa-trash-o drop-icons"></i></a>
</div>
<div class="thing-edit-links-end"></div>
{{/if}}
diff --git a/view/tpl/suggest_friends.tpl b/view/tpl/suggest_friends.tpl
index 26d9da7ce..95f24cd63 100755
--- a/view/tpl/suggest_friends.tpl
+++ b/view/tpl/suggest_friends.tpl
@@ -4,13 +4,13 @@
<img src="{{$entry.photo}}" alt="{{$entry.name}}" width="80" height="80" title="{{$entry.name}} [{{$entry.profile}}]" />
</a>
</div>
- <a href="{{$entry.ignlnk}}" title="{{$entry.ignore}}" class="profile-match-ignore" onclick="return confirmDelete();" ><i class="fa fa-times drop-icons btn btn-default"></i></a>
+ <a href="{{$entry.ignlnk}}" title="{{$entry.ignore}}" class="profile-match-ignore" onclick="return confirmDelete();" ><i class="fa fa-times drop-icons btn btn-outline-secondary"></i></a>
<div class="profile-match-break"></div>
<div class="profile-match-name">
<a href="{{$entry.url}}" title="{{$entry.name}}">{{$entry.name}}</a>
</div>
<div class="profile-match-end"></div>
{{if $entry.connlnk}}
- <div class="profile-match-connect btn btn-default"><a href="{{$entry.connlnk}}" title="{{$entry.conntxt}}"><i class="fa fa-plus connect-icon"></i> {{$entry.conntxt}}</a></div>
+ <div class="profile-match-connect btn btn-outline-secondary"><a href="{{$entry.connlnk}}" title="{{$entry.conntxt}}"><i class="fa fa-plus connect-icon"></i> {{$entry.conntxt}}</a></div>
{{/if}}
</div>
diff --git a/view/tpl/thing_edit.tpl b/view/tpl/thing_edit.tpl
index b23584fe1..62a7c02c8 100644
--- a/view/tpl/thing_edit.tpl
+++ b/view/tpl/thing_edit.tpl
@@ -30,7 +30,7 @@
<div class="thing-end"></div>
{{if $lockstate}}
- <button id="dbtn-acl" class="btn btn-default btn-sm" data-toggle="modal" data-target="#aclModal" onclick="return false;">
+ <button id="dbtn-acl" class="btn btn-outline-secondary btn-sm" data-toggle="modal" data-target="#aclModal" onclick="return false;">
<i id="jot-perms-icon" class="fa fa-{{$lockstate}}"></i>
</button>
{{/if}}
diff --git a/view/tpl/thing_input.tpl b/view/tpl/thing_input.tpl
index 3e178925c..90fb093e4 100644
--- a/view/tpl/thing_input.tpl
+++ b/view/tpl/thing_input.tpl
@@ -30,7 +30,7 @@
<div class="thing-end"></div>
{{if $lockstate}}
- <button id="dbtn-acl" class="btn btn-default btn-sm" data-toggle="modal" data-target="#aclModal" onclick="return false;">
+ <button id="dbtn-acl" class="btn btn-outline-secondary btn-sm" data-toggle="modal" data-target="#aclModal" onclick="return false;">
<i id="jot-perms-icon" class="fa fa-{{$lockstate}}"></i>
</button>
{{/if}}
diff --git a/view/tpl/threaded_conversation.tpl b/view/tpl/threaded_conversation.tpl
index ea5c3c281..5bc7d8386 100755
--- a/view/tpl/threaded_conversation.tpl
+++ b/view/tpl/threaded_conversation.tpl
@@ -1,8 +1,9 @@
+<div id="threads-begin"></div>
{{if $photo_item}}
{{$photo_item}}
{{/if}}
{{foreach $threads as $thread_item}}
{{include file="{{$thread_item.template}}" item=$thread_item}}
{{/foreach}}
-
+<div id="threads-end"></div>
<div id="conversation-end"></div>
diff --git a/view/tpl/usermenu.tpl b/view/tpl/usermenu.tpl
index 547c5f308..c51728c34 100644
--- a/view/tpl/usermenu.tpl
+++ b/view/tpl/usermenu.tpl
@@ -5,10 +5,10 @@
<h3 class="pmenu-title">{{$menu.menu_desc}}{{if $edit}} <a href="mitem/{{$menu.menu_id}}" title="{{$edit}}"><i class="fa fa-pencil fakelink" title="{{$edit}}"></i></a>{{/if}}</h3>
{{/if}}
{{if $items}}
- <ul class="pmenu-body{{if $wrap || !$class}} nav nav-pills nav-stacked{{elseif !$wrap || $class}} {{$class}}{{/if}}">
+ <ul class="pmenu-body{{if $wrap || !$class}} nav nav-pills flex-column{{elseif !$wrap || $class}} {{$class}}{{/if}}">
{{foreach $items as $mitem }}
- <li id="pmenu-item-{{$mitem.mitem_id}}" class="pmenu-item{{if $mitem.submenu}} dropdown{{/if}}">
- <a href="{{if $mitem.submenu}}#{{else}}{{$mitem.mitem_link}}{{/if}}"{{if $mitem.submenu}} class="dropdown-toggle" data-toggle="dropdown"{{/if}}{{if $mitem.newwin}}target="_blank"{{/if}}>{{$mitem.mitem_desc}}{{if $mitem.submenu}}<span class="caret"></span>{{/if}}</a>
+ <li id="pmenu-item-{{$mitem.mitem_id}}" class="nav-item pmenu-item{{if $mitem.submenu}} dropdown{{/if}}">
+ <a href="{{if $mitem.submenu}}#{{else}}{{$mitem.mitem_link}}{{/if}}" class="nav-link {{if $mitem.submenu}} dropdown-toggle{{/if}}"{{if $mitem.submenu}} data-toggle="dropdown"{{/if}}{{if $mitem.newwin}}target="_blank"{{/if}}>{{$mitem.mitem_desc}}{{if $mitem.submenu}}<span class="caret"></span>{{/if}}</a>
{{if $mitem.submenu}}{{$mitem.submenu}}{{/if}}
</li>
{{/foreach }}
diff --git a/view/tpl/viewcontact_template.tpl b/view/tpl/viewcontact_template.tpl
index 83cd80959..005fe17ce 100755
--- a/view/tpl/viewcontact_template.tpl
+++ b/view/tpl/viewcontact_template.tpl
@@ -1,15 +1,15 @@
-<div class="generic-content-wrapper generic-content-wrapper-styled">
-<h3>{{$title}}</h3>
-
-
-<div id="connections-wrapper">
-{{foreach $contacts as $contact}}
- {{include file="contact_template.tpl"}}
-{{/foreach}}
-<div id="page-end"></div>
-</div>
-<div id="view-contact-end"></div>
-{{$paginate}}
+<div class="generic-content-wrapper">
+ <div class="section-title-wrapper">
+ <h2>{{$title}}</h2>
+ </div>
+ <div class="section-content-wrapper clearfix">
+ {{foreach $contacts as $contact}}
+ {{include file="contact_template.tpl"}}
+ {{/foreach}}
+ <div id="page-end"></div>
+ </div>
</div>
<script>$(document).ready(function() { loadingPage = false;});</script>
-<div id="page-spinner"></div>
+<div id="page-spinner" class="spinner-wrapper">
+ <div class="spinner m"></div>
+</div>
diff --git a/view/tpl/webpage_export_list.tpl b/view/tpl/webpage_export_list.tpl
index 1d28f62df..b22b3818a 100644
--- a/view/tpl/webpage_export_list.tpl
+++ b/view/tpl/webpage_export_list.tpl
@@ -10,7 +10,7 @@
</div>
<div id="import-website-content-wrapper" class="section-content-wrapper">
<div class="pull-left">
- <button id="toggle-select-all" class="btn btn-xs btn-primary" onclick="checkedAll(window.isChecked); return false;"><i class="fa fa-check"></i>&nbsp;Toggle Select All</button>
+ <button id="toggle-select-all" class="btn btn-sm btn-primary" onclick="checkedAll(window.isChecked); return false;"><i class="fa fa-check"></i>&nbsp;Toggle Select All</button>
</div>
<div class="clear"></div>
<hr>
diff --git a/view/tpl/webpage_import.tpl b/view/tpl/webpage_import.tpl
index fdc983932..955288c1e 100644
--- a/view/tpl/webpage_import.tpl
+++ b/view/tpl/webpage_import.tpl
@@ -10,7 +10,7 @@
</div>
<div id="import-website-content-wrapper" class="section-content-wrapper">
<div class="pull-left">
- <button id="toggle-select-all" class="btn btn-xs btn-primary" onclick="checkedAll(window.isChecked); return false;"><i class="fa fa-check"></i>&nbsp;Toggle Select All</button>
+ <button id="toggle-select-all" class="btn btn-sm btn-primary" onclick="checkedAll(window.isChecked); return false;"><i class="fa fa-check"></i>&nbsp;Toggle Select All</button>
</div>
<div class="clear"></div>
<h4>Scanned Pages</h4>
diff --git a/view/tpl/webpagelist.tpl b/view/tpl/webpagelist.tpl
index 4dec7518f..1c909b9b8 100644
--- a/view/tpl/webpagelist.tpl
+++ b/view/tpl/webpagelist.tpl
@@ -2,7 +2,7 @@
<div class="section-title-wrapper">
{{if $editor}}
<div class="pull-right">
- <button id="webpage-create-btn" class="btn btn-xs btn-success acl-form-trigger" onclick="openClose('webpage-editor');" data-form_id="profile-jot-form"><i class="fa fa-pencil-square-o"></i>&nbsp;{{$create}}</button>
+ <button id="webpage-create-btn" class="btn btn-sm btn-success acl-form-trigger" onclick="openClose('webpage-editor');" data-form_id="profile-jot-form"><i class="fa fa-pencil-square-o"></i>&nbsp;{{$create}}</button>
</div>
{{/if}}
<h2>{{$listtitle}}</h2>
@@ -23,15 +23,15 @@
<th width="1%"></th>
<th width="1%"></th>
<th width="1%"></th>
- <th width="1%" class="hidden-xs">{{$created_txt}}</th>
- <th width="1%" class="hidden-xs">{{$edited_txt}}</th>
+ <th width="1%" class="d-none d-md-table-cell">{{$created_txt}}</th>
+ <th width="1%" class="d-none d-md-table-cell">{{$edited_txt}}</th>
</tr>
{{foreach $pages as $key => $items}}
{{foreach $items as $item}}
<tr id="webpage-list-item-{{$item.url}}">
<td>
{{if $view}}
- <a href="page/{{$channel}}/{{$item.pagetitle}}" title="{{$view}}">{{$item.pagetitle}}</a>
+ <a href="page/{{$channel}}/{{$item.pageurl}}" title="{{$view}}">{{$item.pagetitle}}</a>
{{else}}
{{$item.pagetitle}}
{{/if}}
@@ -41,7 +41,7 @@
</td>
<td class="webpage-list-tool dropdown">
{{if $item.lockstate=='lock'}}
- <i class="fa fa-lock dropdown-toggle lockview" data-toggle="dropdown" onclick="lockview('item',{{$item.url}});" ></i>
+ <i class="fa fa-lock lockview" data-toggle="dropdown" onclick="lockview('item',{{$item.url}});" ></i>
<ul id="panel-{{$item.url}}" class="lockview-panel dropdown-menu"></ul>
{{/if}}
</td>
@@ -60,10 +60,10 @@
<a href="#" title="{{$delete}}" onclick="dropItem('item/drop/{{$item.url}}', '#webpage-list-item-{{$item.url}}'); return false;"><i class="fa fa-trash-o drop-icons"></i></a>
{{/if}}
</td>
- <td class="hidden-xs">
+ <td class="d-none d-md-table-cell">
{{$item.created}}
</td>
- <td class="hidden-xs">
+ <td class="d-none d-md-table-cell">
{{$item.edited}}
</td>
</tr>
diff --git a/view/tpl/website_portation_tools.tpl b/view/tpl/website_portation_tools.tpl
index 10468b64e..0d131cb17 100644
--- a/view/tpl/website_portation_tools.tpl
+++ b/view/tpl/website_portation_tools.tpl
@@ -1,72 +1,60 @@
<div id="website-portation-tools" class="widget">
- <ul class="nav nav-pills nav-stacked">
- <li>
- <a href="#" onclick="openClose('import-form');
- return false;"><i class="fa fa-cloud-upload generic-icons"></i> {{$import_label}}</a>
- </li>
- <li style="margin-left: 12px;" >
- <form id="import-form" enctype="multipart/form-data" method="post" action="" style="display: none;" class="sub-menu">
-
- <input type="hidden" name="action" value="scan">
-
- <p style="margin-top: 10px;" class="descriptive-text">{{$file_import_text}}</p>
- <div class="form-group">
- <div class="input-group">
- <input class="widget-input" type="text" name="path" title="{{$hint}}" placeholder="{{$desc}}" />
- <div class="input-group-btn">
- <button class="btn btn-default btn-sm" type="submit" name="cloudsubmit" value="{{$select}}"><i class="fa fa-folder-open generic-icons"></i></button>
- </div>
- </div>
- </div>
-
- <!-- Or upload a zipped file containing the website -->
- <p class="descriptive-text">{{$file_upload_text}}</p>
- <div class="form-group">
-
- <div class="input-group">
- <input class="widget-input" type="file" name="zip_file" />
- <div class="input-group-btn">
- <button class="btn btn-default btn-sm" type="submit" name="w_upload" value="w_upload"><i class="fa fa-file-archive-o generic-icons"></i></button>
- </div>
- </div>
- </div>
- </form>
- </li>
- </ul>
- <ul class="nav nav-pills nav-stacked">
- <li>
- <a href="#" onclick="openClose('export-form'); openClose('export-cloud-form');
- return false;"><i class="fa fa-share-square-o generic-icons"></i> {{$export_label}}</a>
- </li>
- <li style="margin-left: 12px;" >
- <form id="export-form" enctype="multipart/form-data" method="post" action="" style="display: none;" class="sub-menu">
- <input type="hidden" name="action" value="exportzipfile">
- <!-- Or download a zipped file containing the website -->
- <p style="margin-top: 10px;" class="descriptive-text">{{$file_download_text}}</p>
- <div class="form-group">
-
- <div class="input-group">
- <input class="widget-input" type="text" name="zipfilename" title="{{$filename_hint}}" placeholder="{{$filename_desc}}" value="" />
- <div class="input-group-btn">
- <button class="btn btn-default btn-sm" type="submit" name="w_download" value="w_download"><i class="fa fa-download generic-icons"></i></button>
- </div>
- </div>
- </div>
- </form>
- <form id="export-cloud-form" enctype="multipart/form-data" method="post" action="" style="display: none;" class="sub-menu">
- <input type="hidden" name="action" value="exportcloud">
- <!-- Or export the website elements to a cloud files folder -->
- <p style="margin-top: 10px;" class="descriptive-text">{{$cloud_export_text}}</p>
- <div class="form-group">
-
- <div class="input-group">
- <input class="widget-input" type="text" name="exportcloudpath" title="{{$cloud_export_hint}}" placeholder="{{$cloud_export_desc}}" />
- <div class="input-group-btn">
- <button class="btn btn-default btn-sm" type="submit" name="exportcloudsubmit" value="{{$cloud_export_select}}"><i class="fa fa-folder-open generic-icons"></i></button>
- </div>
- </div>
- </div>
- </form>
- </li>
- </ul>
+ <div class="nav nav-pills flex-column">
+ <a class="nav-link" href="#" onclick="openClose('import-form'); return false;"><i class="fa fa-cloud-upload generic-icons"></i> {{$import_label}}</a>
+ <div id="import-form" class="sub-menu-wrapper">
+ <div class="sub-menu">
+ <form enctype="multipart/form-data" method="post" action="">
+ <input type="hidden" name="action" value="scan">
+ <p class="descriptive-text">{{$file_import_text}}</p>
+ <div class="form-group">
+ <input class="form-control" type="text" name="path" title="{{$hint}}" placeholder="{{$desc}}" />
+ </div>
+ <div class="form-group">
+ <button class="btn btn-primary btn-sm" type="submit" name="cloudsubmit" value="{{$select}}">Submit</button>
+ </div>
+ <!-- Or upload a zipped file containing the website -->
+ <p class="descriptive-text">{{$file_upload_text}}</p>
+ <div class="form-group">
+ <input class="form-control-file w-100" type="file" name="zip_file" />
+ </div>
+ <div class="form-group">
+ <button class="btn btn-primary btn-sm" type="submit" name="w_upload" value="w_upload">Submit</button>
+ </div>
+ </form>
+ </div>
+ </div>
+ </div>
+ <div class="nav nav-pills flex-column">
+ <a class="nav-link" href="#" onclick="openClose('export-form'); openClose('export-cloud-form'); return false;"><i class="fa fa-share-square-o generic-icons"></i> {{$export_label}}</a>
+ <div id="export-form" class="sub-menu-wrapper">
+ <div class="sub-menu">
+ <form enctype="multipart/form-data" method="post" action="">
+ <input type="hidden" name="action" value="exportzipfile">
+ <!-- Or download a zipped file containing the website -->
+ <p class="descriptive-text">{{$file_download_text}}</p>
+ <div class="form-group">
+ <input class="form-control" type="text" name="zipfilename" title="{{$filename_hint}}" placeholder="{{$filename_desc}}" value="" />
+ </div>
+ <div class="form-group">
+ <button class="btn btn-primary btn-sm" type="submit" name="w_download" value="w_download">Submit</button>
+ </div>
+ </form>
+ </div>
+ </div>
+ <div id="export-cloud-form" class="sub-menu-wrapper">
+ <div class="sub-menu">
+ <form enctype="multipart/form-data" method="post" action="">
+ <input type="hidden" name="action" value="exportcloud">
+ <!-- Or export the website elements to a cloud files folder -->
+ <p style="margin-top: 10px;" class="descriptive-text">{{$cloud_export_text}}</p>
+ <div class="form-group">
+ <input class="form-control" type="text" name="exportcloudpath" title="{{$cloud_export_hint}}" placeholder="{{$cloud_export_desc}}" />
+ </div>
+ <div class="form-group">
+ <button class="btn btn-primary btn-sm" type="submit" name="exportcloudsubmit" value="{{$cloud_export_select}}">Submit</button>
+ </div>
+ </form>
+ </div>
+ </div>
+ </div>
</div>
diff --git a/view/tpl/wiki.tpl b/view/tpl/wiki.tpl
index af6b6800e..22480be5b 100644
--- a/view/tpl/wiki.tpl
+++ b/view/tpl/wiki.tpl
@@ -1,25 +1,22 @@
-<div class="generic-content-wrapper" {{if $hideEditor}}style="display: none;"{{/if}}>
+<div class="generic-content-wrapper">
<div class="section-title-wrapper">
<div class="pull-right">
+ <span class="text-muted wiki-typename">[{{$typename}}]&nbsp;</span>
{{if $showPageControls}}
<div id="page-tools" class="btn-group" style="display: none;">
- <button type="button" class="btn btn-default btn-xs dropdown-toggle" data-toggle="dropdown">
- <i class="fa fa-caret-down"></i>&nbsp;{{$tools_label}}
+ <button type="button" class="btn btn-outline-secondary btn-sm dropdown-toggle" data-toggle="dropdown">
+ <i class="fa fa-cog"></i>&nbsp;{{$tools_label}}
</button>
- <ul class="dropdown-menu dropdown-menu-right">
+ <div class="dropdown-menu dropdown-menu-right">
{{if $renamePage}}
- <li class="nav-item">
- <a class="nav-link rename-page" href="#"><i class="fa fa-edit"></i>&nbsp;{{$renamePage}}</a>
- </li>
+ <a class="dropdown-item rename-page" href="#"><i class="fa fa-fw fa-edit"></i>&nbsp;{{$renamePage}}</a>
{{/if}}
- <li class="nav-item">
- <a id="embed-image" class="nav-link" href="#"><i class="fa fa-picture-o"></i>&nbsp;Embed Image</a>
- </li>
- </ul>
+ <a id="embed-image" class="dropdown-item" href="#"><i class="fa fa-fw fa-picture-o"></i>&nbsp;Embed Image</a>
+ </div>
</div>
{{/if}}
- <button id="fullscreen-btn" type="button" class="btn btn-default btn-xs" onclick="makeFullScreen(); adjustFullscreenEditorHeight();"><i class="fa fa-expand"></i></button>
- <button id="inline-btn" type="button" class="btn btn-default btn-xs" onclick="makeFullScreen(false); adjustInlineEditorHeight()"><i class="fa fa-compress"></i></button>
+ <button id="fullscreen-btn" type="button" class="btn btn-outline-secondary btn-sm" onclick="makeFullScreen(); adjustFullscreenEditorHeight();"><i class="fa fa-expand"></i></button>
+ <button id="inline-btn" type="button" class="btn btn-outline-secondary btn-sm" onclick="makeFullScreen(false); adjustInlineEditorHeight()"><i class="fa fa-compress"></i></button>
</div>
<h2>
<span id="wiki-header-name">{{$wikiheaderName}}</span>:
@@ -35,7 +32,7 @@
<button id="rename-page-submit" class="btn btn-primary" type="submit" name="submit">Submit</button>
</div>
<div>
- <button class="btn btn-default rename-page" type="button">Cancel</button>
+ <button class="btn btn-outline-secondary rename-page" type="button">Cancel</button>
</div>
<div class="clear"></div>
</div>
@@ -43,12 +40,12 @@
</div>
<div id="wiki-content-container" class="section-content-wrapper">
<ul class="nav nav-tabs" id="wiki-nav-tabs">
- <li id="edit-pane-tab"><a data-toggle="tab" href="#edit-pane">{{$editOrSourceLabel}}</a></li>
- <li class="active"><a data-toggle="tab" href="#preview-pane" id="wiki-get-preview">View</a></li>
- <li><a data-toggle="tab" href="#page-history-pane" id="wiki-get-history">History</a></li>
+ <li class="nav-item" id="edit-pane-tab"><a class="nav-link" data-toggle="tab" href="#edit-pane">{{$editOrSourceLabel}}</a></li>
+ <li class="nav-item"><a class="nav-link active" data-toggle="tab" href="#preview-pane" id="wiki-get-preview">View</a></li>
+ <li class="nav-item"><a class="nav-link" data-toggle="tab" href="#page-history-pane" id="wiki-get-history">History</a></li>
</ul>
<div class="tab-content" id="wiki-page-tabs">
- <div id="edit-pane" class="tab-pane fade">
+ <div id="edit-pane" class="tab-pane">
{{if !$mimeType || $mimeType == 'text/markdown'}}
<div id="ace-editor"></div>
{{else}}
@@ -56,27 +53,25 @@
<textarea id="editor">{{$content}}</textarea>
</div>
{{/if}}
- {{if $showPageControls}}
- <div>
- <div id="id_{{$commitMsg.0}}_wrapper" class="field input">
- <div class="input-group">
- <input class="widget-input" name="{{$commitMsg.0}}" id="id_{{$commitMsg.0}}" type="text" value="{{$commitMsg.2}}"{{if $commitMsg.5}} {{$commitMsg.5}}{{/if}}>
- <div class="input-group-btn">
- <button id="save-page" type="button" class="btn btn-primary btn-sm disabled">Save</button>
- </div>
- </div>
- </div>
- </div>
- {{/if}}
</div>
- <div id="preview-pane" class="tab-pane fade in active">
+ <div id="preview-pane" class="tab-pane active">
<div id="wiki-preview">
{{$renderedContent}}
</div>
</div>
- <div id="page-history-pane" class="tab-pane fade">
+ <div id="page-history-pane" class="tab-pane">
<div id="page-history-list"></div>
</div>
+ {{if $showPageControls}}
+ <div id="id_{{$commitMsg.0}}_wrapper" class="field input" style="display: none">
+ <div class="input-group">
+ <input class="form-control form-control-sm" name="{{$commitMsg.0}}" id="id_{{$commitMsg.0}}" type="text" value="{{$commitMsg.2}}"{{if $commitMsg.5}} {{$commitMsg.5}}{{/if}}>
+ <div class="input-group-btn">
+ <button id="save-page" type="button" class="btn btn-primary disabled">Save</button>
+ </div>
+ </div>
+ </div>
+ {{/if}}
</div>
</div>
</div>
@@ -87,17 +82,17 @@
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
- <button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button>
<h4 class="modal-title" id="embedPhotoModalLabel">{{$embedPhotosModalTitle}}</h4>
+ <button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button>
</div>
<div class="modal-body" id="embedPhotoModalBody" >
- <div id="embedPhotoModalBodyAlbumListDialog" class="hide">
+ <div id="embedPhotoModalBodyAlbumListDialog" class="d-none">
<div id="embedPhotoModalBodyAlbumList"></div>
</div>
- <div id="embedPhotoModalBodyAlbumDialog" class="hide"></div>
+ <div id="embedPhotoModalBodyAlbumDialog" class="d-none"></div>
</div>
<div class="modal-footer">
- <button type="button" class="btn btn-default" data-dismiss="modal">{{$embedPhotosModalCancel}}</button>
+ <button type="button" class="btn btn-outline-secondary" data-dismiss="modal">{{$embedPhotosModalCancel}}</button>
<button id="embed-photo-OKButton" type="button" class="btn btn-primary">{{$embedPhotosModalOK}}</button>
</div>
</div><!-- /.modal-content -->
@@ -107,8 +102,9 @@
<script>
window.wiki_resource_id = '{{$resource_id}}';
window.wiki_page_name = '{{$page}}';
- window.wiki_page_content = {{if !$mimeType || $mimeType == 'text/markdown'}}{{$content}}{{else}}`{{$content}}`{{/if}};
+ window.wiki_page_content = '{{$content|escape:'javascript'}}';
window.wiki_page_commit = '{{$commit}}';
+ window.saved = true;
$("#generic-modal-ok-{{$wikiModalID}}").removeClass('btn-primary');
$("#generic-modal-ok-{{$wikiModalID}}").addClass('btn-danger');
@@ -119,7 +115,7 @@
});
$( "#rename-page-form" ).submit(function( event ) {
- $.post("wiki/{{$channel}}/rename/page",
+ $.post("wiki/{{$channel_address}}/rename/page",
{
oldName: window.wiki_page_name,
newName: $('#id_pageRename').val(),
@@ -177,52 +173,62 @@
adjustInlineEditorHeight();
}
}, 500); // Return the focus to the editor allowing immediate text entry
- $('#page-tools').show();
+ $('#page-tools, #id_{{$commitMsg.0}}_wrapper').show();
});
$('#wiki-get-preview').click(function (ev) {
- $.post("wiki/{{$channel}}/preview", {
+ if(window.saved) {
+ $('#page-tools, #id_{{$commitMsg.0}}_wrapper').hide();
+ }
+ else {
+ $('#page-tools').hide();
+ }
+ $.post("wiki/{{$channel_address}}/preview", {
{{if !$mimeType || $mimeType == 'text/markdown'}}
content: editor.getValue(),
{{else}}
content: editor.val(),
{{/if}}
- resource_id: window.wiki_resource_id
+ resource_id: window.wiki_resource_id,
+ mimetype: '{{$mimeType}}'
},
function (data) {
- if (data.success) {
- $('#wiki-preview').html(data.html);
- {{if !$mimeType || $mimeType == 'text/markdown'}}
- $("#wiki-toc").toc({content: "#wiki-preview", headings: "h1,h2,h3,h4"});
- {{/if}}
- $('#page-tools').hide();
- } else {
- window.console.log('Error previewing page.');
- }
+ if (data.success) {
+ $('#wiki-preview').html(data.html);
+ {{if !$mimeType || $mimeType == 'text/markdown'}}
+ $("#wiki-toc").toc({content: "#wiki-preview", headings: "h1,h2,h3,h4"});
+ {{/if}}
+ } else {
+ window.console.log('Error previewing page.');
+ }
}, 'json');
ev.preventDefault();
});
$('#wiki-get-history').click(function (ev) {
- $.post("wiki/{{$channel}}/history/page", {name: window.wiki_page_name, resource_id: window.wiki_resource_id}, function (data) {
+ if(window.saved) {
+ $('#page-tools, #id_{{$commitMsg.0}}_wrapper').hide();
+ }
+ else {
+ $('#page-tools').hide();
+ }
+ $.post("wiki/{{$channel_address}}/history/page", {name: window.wiki_page_name, resource_id: window.wiki_resource_id}, function (data) {
if (data.success) {
$('#page-history-list').html(data.historyHTML);
- $('#page-tools').hide();
} else {
window.console.log('Error getting page history.');
}
- }, 'json');
- ev.preventDefault();
- });
+ }, 'json');
+ ev.preventDefault();
+ });
function wiki_refresh_page_list() {
if (window.wiki_resource_id === '') {
return false;
}
- $.post("wiki/{{$channel}}/get/page/list/", {resource_id: window.wiki_resource_id}, function (data) {
+ $.post("wiki/{{$channel_address}}/get/page/list/", {channel_id: '{{$channel_id}}', resource_id: window.wiki_resource_id}, function (data) {
if (data.success) {
- $('#wiki_page_list_container').html(data.pages);
- $('#wiki_page_list_container').show();
+ $('#wiki_page_list').html(data.pages);
} else {
alert('Error fetching page list!');
window.console.log('Error fetching page list!');
@@ -249,7 +255,7 @@
ev.preventDefault();
return false;
}
- $.post("wiki/{{$channel}}/save/page", {
+ $.post("wiki/{{$channel_address}}/save/page", {
content: currentContent,
commitMsg: $('#id_commitMsg').val(),
name: window.wiki_page_name,
@@ -257,6 +263,7 @@
},
function (data) {
if (data.success) {
+ window.saved = true;
window.console.log('Page saved successfully.');
window.wiki_page_content = currentContent;
$('#id_commitMsg').val(''); // Clear the commit message box
@@ -280,7 +287,7 @@
window.console.log('You must have a wiki page open in order to revert pages.');
return false;
}
- $.post("wiki/{{$channel}}/revert/page", {commitHash: commitHash, name: window.wiki_page_name, resource_id: window.wiki_resource_id},
+ $.post("wiki/{{$channel_address}}/revert/page", {commitHash: commitHash, name: window.wiki_page_name, resource_id: window.wiki_resource_id},
function (data) {
if (data.success) {
$('button[id^=revert-]').removeClass('btn-success');
@@ -303,7 +310,7 @@
window.console.log('You must have a wiki page open in order to revert pages.');
return false;
}
- $.post("wiki/{{$channel}}/compare/page", {
+ $.post("wiki/{{$channel_address}}/compare/page", {
compareCommit: compareCommit,
currentCommit: window.wiki_page_commit,
name: window.wiki_page_name,
@@ -370,8 +377,8 @@
if (data['status']) {
$('#embedPhotoModalLabel').html("{{$modalchooseimages}}");
$('#embedPhotoModalBodyAlbumDialog').html('\
- <div><ul class="nav">\n\
- <li><a href="#" onclick="initializeEmbedPhotoDialog();return false;">\n\
+ <div><ul class="nav nav-pills flex-column">\n\
+ <li class="nav-item"><a class="nav-link" href="#" onclick="initializeEmbedPhotoDialog();return false;">\n\
<i class="fa fa-chevron-left"></i>&nbsp;\n\
{{$modaldiffalbum}}\n\
</a>\n\
@@ -386,8 +393,8 @@
$(imageparent).toggleClass('embed-photo-selected-photo');
}
});
- $('#embedPhotoModalBodyAlbumListDialog').addClass('hide');
- $('#embedPhotoModalBodyAlbumDialog').removeClass('hide');
+ $('#embedPhotoModalBodyAlbumListDialog').addClass('d-none');
+ $('#embedPhotoModalBodyAlbumDialog').removeClass('d-none');
$('#embed-photo-OKButton').click(function () {
$('.embed-photo-selected-photo').each(function (index) {
var href = $(this).attr('href');
@@ -426,17 +433,17 @@
if (data['status']) {
var albums = data['albumlist']; //JSON.parse(data['albumlist']);
$('#embedPhotoModalLabel').html("{{$modalchoosealbum}}");
- $('#embedPhotoModalBodyAlbumList').html('<ul class="nav"></ul>');
+ $('#embedPhotoModalBodyAlbumList').html('<ul class="nav nav-pills flex-column"></ul>');
for(var i = 0; i < albums.length; i++) {
var albumName = albums[i].text;
var jsAlbumName = albums[i].jstext;
- var albumLink = '<li>';
- albumLink += '<a href="#" onclick="choosePhotoFromAlbum(\'' + jsAlbumName + '\'); return false;">' + albumName + '</a>';
+ var albumLink = '<li class="nav-item">';
+ albumLink += '<a class="nav-link" href="#" onclick="choosePhotoFromAlbum(\'' + jsAlbumName + '\'); return false;">' + albumName + '</a>';
albumLink += '</li>';
$('#embedPhotoModalBodyAlbumList').find('ul').append(albumLink);
}
- $('#embedPhotoModalBodyAlbumDialog').addClass('hide');
- $('#embedPhotoModalBodyAlbumListDialog').removeClass('hide');
+ $('#embedPhotoModalBodyAlbumDialog').addClass('d-none');
+ $('#embedPhotoModalBodyAlbumListDialog').removeClass('d-none');
} else {
window.console.log("{{$modalerrorlist}}" + ':' + data['errormsg']);
}
@@ -446,11 +453,10 @@
};
$(document).ready(function () {
- wiki_refresh_page_list();
-
{{if !$mimeType || $mimeType == 'text/markdown'}}
$("#wiki-toc").toc({content: "#wiki-preview", headings: "h1,h2,h3,h4"});
window.editor.on("input", function() {
+ window.saved = false;
if(window.editor.getSession().getUndoManager().isClean()) {
$('#save-page').addClass('disabled');
} else {
@@ -459,10 +465,13 @@
});
{{else}}
window.editor.on("input", function() {
+ window.saved = false;
$('#save-page').removeClass('disabled');
});
+ {{if $mimeType == 'text/bbcode'}}
window.editor.bbco_autocomplete('bbcode');
{{/if}}
+ {{/if}}
});
$(window).resize(function () {
diff --git a/view/tpl/wiki_page_history.tpl b/view/tpl/wiki_page_history.tpl
index ca16e8333..9e5ba0f9c 100644
--- a/view/tpl/wiki_page_history.tpl
+++ b/view/tpl/wiki_page_history.tpl
@@ -46,10 +46,10 @@
<tr><td width="10%">Date</td><td width="70%">{{$commit.date}}</td>
<td rowspan="3" width="20%" align="right">
{{if $permsWrite}}
- <button id="revert-{{$commit.hash}}" class="btn btn-danger btn-xs" onclick="wiki_revert_page('{{$commit.hash}}')">Revert</button>
+ <button id="revert-{{$commit.hash}}" class="btn btn-danger btn-sm" onclick="wiki_revert_page('{{$commit.hash}}')">Revert</button>
<br><br>
{{/if}}
- <button id="compare-{{$commit.hash}}" class="btn btn-warning btn-xs" onclick="wiki_compare_page('{{$commit.hash}}')">Compare</button>
+ <button id="compare-{{$commit.hash}}" class="btn btn-warning btn-sm" onclick="wiki_compare_page('{{$commit.hash}}')">Compare</button>
</td></tr>
<tr><td>Name</td><td>{{$commit.name}} &lt;{{$commit.email}}&gt;</td></tr>
<tr><td>Message</td><td>{{$commit.title}}</td></tr>
diff --git a/view/tpl/wiki_page_list.tpl b/view/tpl/wiki_page_list.tpl
index 78657ec10..d75f22f64 100644
--- a/view/tpl/wiki_page_list.tpl
+++ b/view/tpl/wiki_page_list.tpl
@@ -1,36 +1,49 @@
-{{if $not_refresh}}<div id="wiki_page_list_container" {{if $hide}} style="display: none;" {{/if}}>{{/if}}
+{{if ! $refresh}}
<div id="wiki_page_list" class="widget" >
+{{/if}}
<h3>{{$header}}</h3>
- <ul class="nav nav-pills nav-stacked">
+ <ul class="nav nav-pills flex-column">
{{if $pages}}
{{foreach $pages as $page}}
- <li id="{{$page.link_id}}">
+ <li class="nav-item nav-item-hack" id="{{$page.link_id}}">
{{if $page.resource_id && $candel}}
- <i class="widget-nav-pills-icons fa fa-trash-o drop-icons" onclick="wiki_delete_page('{{$page.title}}', '{{$page.url}}', '{{$page.resource_id}}', '{{$page.link_id}}')"></i>
+ <i class="nav-link widget-nav-pills-icons fa fa-trash-o drop-icons" onclick="wiki_delete_page('{{$page.title}}', '{{$page.title}}', '{{$page.resource_id}}', '{{$page.link_id}}')"></i>
{{/if}}
- <a href="/wiki/{{$channel}}/{{$wikiname}}/{{$page.url}}">{{$page.title}}</a>
+ <a class="nav-link" href="/wiki/{{$channel_address}}/{{$wikiname}}/{{$page.url}}">{{$page.title}}</a>
</li>
{{/foreach}}
{{/if}}
{{if $canadd}}
- <li><a href="#" onclick="wiki_show_new_page_form(); return false;"><i class="fa fa-plus-circle"></i>&nbsp;{{$addnew}}</a></li>
+ <li class="nav-item"><a class="nav-link" href="#" onclick="wiki_show_new_page_form(); return false;"><i class="fa fa-plus-circle"></i>&nbsp;{{$addnew}}</a></li>
+ {{/if}}
+ {{if $canadd}}
+ <div id="new-page-form-wrapper" class="clearfix sub-menu" style="display:none;">
+ <form id="new-page-form" action="wiki/{{$channel_address}}/create/page" method="post" >
+ <input type="hidden" name="resource_id" value="{{$resource_id}}">
+ {{include file="field_input.tpl" field=$pageName}}
+ {{if $typelock}}
+ <input id="id_mimetype" type="hidden" name="mimetype" value="{{$lockedtype}}">
+ {{else}}
+ <div id="wiki_page_options" style="display: none">
+ {{$mimetype}}
+ </div>
+ <div class="float-right fakelink" onClick="openClose('wiki_page_options')">
+ {{$options}}
+ </div>
+ {{/if}}
+ <button id="new-page-submit" class="btn btn-primary" type="submit" name="submit" >{{$submit}}</button>
+ </form>
+ </div>
{{/if}}
</ul>
- {{if $canadd}}
- <div id="new-page-form-wrapper" class="sub-menu" style="display:none;">
- <form id="new-page-form" action="wiki/{{$channel}}/create/page" method="post" >
- <input type="hidden" name="resource_id" value="{{$resource_id}}">
- {{include file="field_input.tpl" field=$pageName}}
- <button id="new-page-submit" class="btn btn-primary" type="submit" name="submit" >Submit</button>
- </form>
- </div>
- {{/if}}
+{{if ! $refresh}}
</div>
-{{if $not_refresh}}</div>{{/if}}
+{{/if}}
+{{if $canadd}}
<script>
$('#new-page-submit').click(function (ev) {
- $.post("wiki/{{$channel}}/create/page", {pageName: $('#id_pageName').val(), resource_id: window.wiki_resource_id},
+ $.post("wiki/{{$channel_address}}/create/page", {pageName: $('#id_pageName').val(), resource_id: window.wiki_resource_id, mimetype: $('#id_mimetype').val() },
function(data) {
if(data.success) {
window.location = data.url;
@@ -45,7 +58,7 @@
if(!confirm('Are you sure you want to delete the page: ' + wiki_page_name)) {
return;
}
- $.post("wiki/{{$channel}}/delete/page", {name: wiki_page_url, resource_id: wiki_resource_id},
+ $.post("wiki/{{$channel_address}}/delete/page", {name: wiki_page_url, resource_id: wiki_resource_id},
function (data) {
if (data.success) {
window.console.log('Page deleted successfully.');
@@ -74,3 +87,4 @@
return false;
}
</script>
+{{/if}}
diff --git a/view/tpl/wikilist.tpl b/view/tpl/wikilist.tpl
index 916552e03..801cb17fd 100644
--- a/view/tpl/wikilist.tpl
+++ b/view/tpl/wikilist.tpl
@@ -1,7 +1,7 @@
<div class="generic-content-wrapper">
- <div class="section-title-wrapper">
+ <div class="section-title-wrapper clearfix">
{{if $owner}}
- <button type="button" class="btn btn-success btn-xs pull-right acl-form-trigger" onclick="openClose('new-wiki-form-wrapper');" data-form_id="new-wiki-form"><i class="fa fa-plus-circle"></i>&nbsp;{{$create}}</button>
+ <button type="button" class="btn btn-success btn-sm pull-right acl-form-trigger" onclick="openClose('new-wiki-form-wrapper');" data-form_id="new-wiki-form"><i class="fa fa-plus-circle"></i>&nbsp;{{$create}}</button>
{{/if}}
<h2>{{$header}}</h2>
</div>
@@ -10,17 +10,17 @@
<form id="new-wiki-form" action="wiki/{{$channel}}/create/wiki" method="post" class="acl-form" data-form_id="new-wiki-form" data-allow_cid='{{$allow_cid}}' data-allow_gid='{{$allow_gid}}' data-deny_cid='{{$deny_cid}}' data-deny_gid='{{$deny_gid}}'>
{{include file="field_input.tpl" field=$wikiName}}
{{include file="field_select.tpl" field=$mimeType}}
+ {{include file="field_checkbox.tpl" field=$typelock}}
{{include file="field_checkbox.tpl" field=$notify}}
<div>
<div class="btn-group pull-right">
- <button id="dbtn-acl" class="btn btn-default btn-sm" data-toggle="modal" data-target="#aclModal" title="Permission settings" onclick="return false;">
+ <button id="dbtn-acl" class="btn btn-outline-secondary btn-sm" data-toggle="modal" data-target="#aclModal" title="Permission settings" onclick="return false;">
<i id="jot-perms-icon" class="fa fa-{{$lockstate}} jot-icons"></i>
</button>
<button id="new-wiki-submit" class="btn btn-primary btn-sm" type="submit" name="submit" >{{$submit}}</button>
</div>
</div>
</form>
- {{$acl}}
<div class="clear"></div>
</div>
{{/if}}
@@ -29,8 +29,11 @@
<tr>
<th width="96%">{{$name}}</th>
<th width="1%">{{$type}}</th>
- <th width="1%" class="wikis-index-tool"></th>
- <!-- th width="1%" class="wikis-index-tool"></th -->
+ <th width="1%"></th>
+ {{if $owner}}
+ <th width="1%"></th>
+ {{/if}}
+ <th width="1%"></th>
{{if $owner}}
<th width="1%"></th>
{{/if}}
@@ -38,22 +41,42 @@
{{foreach $wikis as $wiki}}
<tr class="wikis-index-row">
<td><a href="/wiki/{{$channel}}/{{$wiki.urlName}}/Home" title="{{$view}}"{{if $wiki.active}} class="active"{{/if}}>{{$wiki.title}}</a></td>
- <td>{{$wiki.mimeType}}</td>
- <td class="wiki-index-tool dropdown">
- {{if $wiki.lock}}
- <i class="fa fa-lock dropdown-toggle lockview" data-toggle="dropdown" onclick="lockview('item',{{$wiki.id}});"></i></button>
+ <td>{{if $wiki.typelock}}{{$wiki.mimeType}}{{else}}{{$unlocked}}{{/if}}</td>
+ {{if $owner}}
+ <td><i class="fa fa-pencil" onclick="openCloseTR('wikis-index-edit-{{$wiki.id}}')"></i></td>
+ {{/if}}
+ <td class="dropdown">
+ {{if $wiki.lockstate == 'lock'}}
+ <i class="fa fa-lock lockview" data-toggle="dropdown" onclick="lockview('item',{{$wiki.id}});"></i>
<ul id="panel-{{$wiki.id}}" class="lockview-panel dropdown-menu dropdown-menu-right"></ul>
{{/if}}
</td>
- <!-- td class="wiki-index-tool"><i class="fa fa-download fakelink" onclick="wiki_download_wiki('{{$wiki.resource_id}}'); return false;"></i></td -->
+ <td><i class="fa fa-download" onclick="wiki_download_wiki('{{$wiki.resource_id}}'); return false;"></i></td>
{{if $owner}}
<td><i class="fa fa-trash-o drop-icons" onclick="wiki_delete_wiki('{{$wiki.title}}', '{{$wiki.resource_id}}'); return false;"></i></td>
{{/if}}
</tr>
+ {{if $owner}}
+ <tr id="wikis-index-edit-{{$wiki.id}}" style="display:none">
+ <td colspan="6">
+ <form id="edit-wiki-form-{{$wiki.id}}" method="post" action="wiki/{{$channel}}/update/wiki" class="acl-form" data-form_id="edit-wiki-form-{{$wiki.id}}" data-allow_cid='{{$wiki.json_allow_cid}}' data-allow_gid='{{$wiki.json_allow_gid}}' data-deny_cid='{{$wiki.json_deny_cid}}' data-deny_gid='{{$wiki.json_deny_gid}}'>
+ <input type="hidden" name="origRawName" value="{{$wiki.title}}">
+ {{include file="field_input.tpl" field=['updateRawName', $edit_wiki_name, $wiki.title]}}
+ <div class="btn-group float-right">
+ <button class="btn btn-outline-secondary btn-sm" data-toggle="modal" data-target="#aclModal" type="button">
+ <i class="jot-perms-icon fa fa-{{$wiki.lockstate}}"></i>
+ </button>
+ <button class="btn btn-primary btn-sm" type="submit" value="edit">Submit</button>
+ </div>
+ </form>
+ </td>
+ </tr>
+ {{/if}}
{{/foreach}}
</table>
</div>
</div>
+{{$acl}}
<script>
{{if $owner}}
function wiki_delete_wiki(wikiHtmlName, resource_id) {
diff --git a/view/tpl/wikilist_widget.tpl b/view/tpl/wikilist_widget.tpl
index 1f92b5807..9853f9850 100644
--- a/view/tpl/wikilist_widget.tpl
+++ b/view/tpl/wikilist_widget.tpl
@@ -1,8 +1,8 @@
<div id="wiki_list" class="widget">
<h3>{{$header}}</h3>
- <ul class="nav nav-pills nav-stacked">
+ <ul class="nav nav-pills flex-column">
{{foreach $wikis as $wiki}}
- <li><a href="/wiki/{{$channel}}/{{$wiki.urlName}}/Home" title="{{$view}}">{{$wiki.title}}</a></li>
+ <li class="nav-item"><a class="nav-link" href="/wiki/{{$channel}}/{{$wiki.urlName}}/Home" title="{{$view}}">{{$wiki.title}}</a></li>
{{/foreach}}
</ul>
</div>
diff --git a/view/tpl/xrd_diaspora.tpl b/view/tpl/xrd_diaspora.tpl
deleted file mode 100644
index aa0d8c740..000000000
--- a/view/tpl/xrd_diaspora.tpl
+++ /dev/null
@@ -1,3 +0,0 @@
- <Link rel="http://joindiaspora.com/seed_location" type="text/html" href="{{$baseurl}}/" />
- <Link rel="http://joindiaspora.com/guid" type="text/html" href="{{$dspr_guid}}" />
- <Link rel="diaspora-public-key" type="RSA" href="{{$dspr_key}}" />
diff --git a/view/tpl/xrd_person.tpl b/view/tpl/xrd_person.tpl
index 93fdcb1df..52adb54e3 100755
--- a/view/tpl/xrd_person.tpl
+++ b/view/tpl/xrd_person.tpl
@@ -1,7 +1,7 @@
<?xml version="1.0" encoding="UTF-8"?>
<XRD xmlns="http://docs.oasis-open.org/ns/xri/xrd-1.0">
- <Subject>{{$accturi}}</Subject>
+ <Subject>{{$subject}}</Subject>
{{if $aliases}}{{foreach $aliases as $a}}
<Alias>{{$a}}</Alias>
{{/foreach}}{{/if}}
@@ -22,10 +22,7 @@
href="{{$hcard_url}}" />
<Link rel="http://ostatus.org/schema/1.0/subscribe"
template="{{$subscribe}}" />
-
- <Link rel="magic-public-key"
+ <Link rel="magic-public-key"
href="{{$modexp}}" />
- {{$dspr}}
-
</XRD>